diff --git a/.gitmodules b/.gitmodules new file mode 100644 index 0000000..6fbcd88 --- /dev/null +++ b/.gitmodules @@ -0,0 +1,3 @@ +[submodule "app/jni/src/libultraship"] + path = app/jni/src/libultraship + url = https://github.com/Waterdish/libultraship.git diff --git a/app/jni/src/libultraship b/app/jni/src/libultraship new file mode 160000 index 0000000..40ddf3b --- /dev/null +++ b/app/jni/src/libultraship @@ -0,0 +1 @@ +Subproject commit 40ddf3bb5544a4ccbfdb8b502e7cc4f7e9684acb diff --git a/app/jni/src/libultraship/.clang-format b/app/jni/src/libultraship/.clang-format deleted file mode 100644 index c7b900f..0000000 --- a/app/jni/src/libultraship/.clang-format +++ /dev/null @@ -1,23 +0,0 @@ -IndentWidth: 4 -Language: Cpp -UseTab: Never -ColumnLimit: 120 -PointerAlignment: Left -BreakBeforeBraces: Attach -SpaceAfterCStyleCast: false -Cpp11BracedListStyle: false -IndentCaseLabels: true -BinPackArguments: true -BinPackParameters: true -AlignAfterOpenBracket: Align -AlignOperands: true -BreakBeforeTernaryOperators: true -BreakBeforeBinaryOperators: None -AllowShortBlocksOnASingleLine: true -AllowShortIfStatementsOnASingleLine: false -AllowShortLoopsOnASingleLine: false -AllowShortCaseLabelsOnASingleLine: false -AllowShortFunctionsOnASingleLine: false -AlignEscapedNewlines: Left -AlignTrailingComments: true -SortIncludes: false diff --git a/app/jni/src/libultraship/.clang-tidy b/app/jni/src/libultraship/.clang-tidy deleted file mode 100644 index 516584a..0000000 --- a/app/jni/src/libultraship/.clang-tidy +++ /dev/null @@ -1,30 +0,0 @@ -Checks: '-*,readability-braces-around-statements,readability-inconsistent-declaration-parameter-name,readability-identifier-naming' -WarningsAsErrors: '' -HeaderFilterRegex: '(src|include)\/.*\.h$' -FormatStyle: 'file' -CheckOptions: - - { key: readability-identifier-naming.NamespaceCase, value: CamelCase } - - { key: readability-identifier-naming.ClassCase, value: CamelCase } - - { key: readability-identifier-naming.PrivateMemberPrefix, value: m } - - { key: readability-identifier-naming.ProtectedMemberPrefix, value: m } - - { key: readability-identifier-naming.PrivateMemberCase, value: CamelCase } - - { key: readability-identifier-naming.ProtectedMemberCase, value: CamelCase } - - { key: readability-identifier-naming.PublicMemberCase, value: CamelCase } - - { key: readability-identifier-naming.MemberCase, value: CamelCase } - - { key: readability-identifier-naming.StructCase, value: CamelCase } - #- { key: readability-identifier-naming.EnumCase, value: CamelCase } - #- { key: readability-identifier-naming.EnumConstantCase, value: UPPER_CASE } - - { key: readability-identifier-naming.VariableCase, value: CamelCase } - - { key: readability-identifier-naming.StaticVariableCase, value: CamelCase } - - { key: readability-identifier-naming.StaticVariablePrefix, value: s } - - { key: readability-identifier-naming.GlobalConstantCase, value: CamelCase } - - { key: readability-identifier-naming.GlobalConstantPrefix, value: g } - - { key: readability-identifier-naming.MethodCase, value: CamelCase } - - { key: readability-identifier-naming.FunctionCase, value: CamelCase } - - { key: readability-identifier-naming.VariableCase, value: camelBack } - - { key: readability-identifier-naming.LocalVariableCase, value: camelBack } - - { key: readability-identifier-naming.ParameterCase, value: camelBack } - # Require argument names to match exactly (instead of allowing a name to be a prefix/suffix of another) - # Note: 'true' is expected by clang-tidy 12+ but '1' is used for compatibility with older versions - - key: readability-inconsistent-declaration-parameter-name.Strict - value: 1 diff --git a/app/jni/src/libultraship/.github/workflows/build-validation.yml b/app/jni/src/libultraship/.github/workflows/build-validation.yml deleted file mode 100644 index 5801437..0000000 --- a/app/jni/src/libultraship/.github/workflows/build-validation.yml +++ /dev/null @@ -1,94 +0,0 @@ -name: build-validation -on: - push: - branches: - - 'main' - pull_request: -concurrency: - group: ${{ github.workflow }}-${{ github.ref }} - cancel-in-progress: true -jobs: - build-macos: - runs-on: macos-12 - steps: - - name: Install dependencies - run: | - brew install sdl2 libpng glew ninja - - uses: actions/checkout@v2 - - name: ccache - uses: hendrikmuhs/ccache-action@v1.2 - with: - key: ${{ runner.os }}-ccache - - name: Build libultraship - run: | - export PATH="/usr/lib/ccache:/usr/local/opt/ccache/libexec:$PATH" - cmake --no-warn-unused-cli -H. -Bbuild-cmake -GNinja -DCMAKE_BUILD_TYPE:STRING=Release - cmake --build build-cmake --config Release --parallel 10 - - name: Upload build - uses: actions/upload-artifact@v3 - with: - name: soh-mac - path: build-cmake/src/*.a - if-no-files-found: error - build-linux: - runs-on: ubuntu-latest - steps: - - name: Install dependencies - run: | - sudo apt-get update - sudo apt-get install -y libsdl2-dev libpng-dev libglew-dev ninja-build - - uses: actions/checkout@v2 - - name: ccache - uses: hendrikmuhs/ccache-action@v1.2 - with: - key: ${{ runner.os }}-ccache - - name: Install latest SDL - run: | - export PATH="/usr/lib/ccache:/usr/local/opt/ccache/libexec:$PATH" - wget https://www.libsdl.org/release/SDL2-2.24.1.tar.gz - tar -xzf SDL2-2.24.1.tar.gz - cd SDL2-2.24.1 - ./configure - make -j 10 - sudo make install - - name: Build libultraship - run: | - export PATH="/usr/lib/ccache:/usr/local/opt/ccache/libexec:$PATH" - cmake --no-warn-unused-cli -H. -Bbuild-cmake -GNinja -DCMAKE_BUILD_TYPE:STRING=Release - cmake --build build-cmake --config Release --parallel 10 - env: - CC: gcc-10 - CXX: g++-10 - - name: Upload build - uses: actions/upload-artifact@v3 - with: - name: soh-linux - path: build-cmake/src/*.a - if-no-files-found: error - build-windows: - runs-on: windows-latest - steps: - - name: Install dependencies - run: | - choco install ninja - Remove-Item -Path "C:\ProgramData\Chocolatey\bin\ccache.exe" -Force - - uses: actions/checkout@v2 - - name: ccache - uses: dcvz/ccache-action@27b9f33213c0079872f064f6b6ba0233dfa16ba2 - with: - key: ${{ runner.os }}-ccache - - name: Setup MSVC - uses: ilammy/msvc-dev-cmd@v1 - - name: Build libultraship - env: - VCPKG_ROOT: D:/a/vcpkg - run: | - set $env:PATH="$env:USERPROFILE/.cargo/bin;$env:PATH" - cmake --no-warn-unused-cli -S. -Bbuild-cmake -GNinja -DCMAKE_MAKE_PROGRAM=ninja -DCMAKE_BUILD_TYPE:STRING=Release -DCMAKE_C_COMPILER_LAUNCHER=ccache -DCMAKE_CXX_COMPILER_LAUNCHER=ccache -DUSE_AUTO_VCPKG=ON -DCMAKE_VS_PLATFORM_NAME=x64 - cmake --build build-cmake --config Release --parallel 10 - - name: Upload build - uses: actions/upload-artifact@v3 - with: - name: soh-windows - path: build-cmake/src/**/*.lib - if-no-files-found: error diff --git a/app/jni/src/libultraship/.github/workflows/tidy-format-validation.yml b/app/jni/src/libultraship/.github/workflows/tidy-format-validation.yml deleted file mode 100644 index 4ad7a93..0000000 --- a/app/jni/src/libultraship/.github/workflows/tidy-format-validation.yml +++ /dev/null @@ -1,51 +0,0 @@ -name: tidy-format-validation -on: [pull_request] -concurrency: - group: ${{ github.workflow }}-${{ github.ref }} - cancel-in-progress: true -jobs: - tidy-format: - runs-on: ubuntu-latest - steps: - - name: Install dependencies - run: | - sudo apt-get update - sudo apt-get install -y libsdl2-dev libpng-dev libglew-dev ninja-build clang-tidy clang-format-12 - - uses: actions/checkout@v3 - with: - fetch-depth: 2 - - name: ccache - uses: hendrikmuhs/ccache-action@v1.2 - with: - key: ${{ runner.os }}-ccache - - name: Run clang-format - run: | - find src include -name "*.cpp" -o -name "*.h" | sed 's| |\\ |g' | xargs clang-format-12 -i - git diff --exit-code - - name: Install latest SDL - run: | - export PATH="/usr/lib/ccache:/usr/local/opt/ccache/libexec:$PATH" - wget https://www.libsdl.org/release/SDL2-2.24.1.tar.gz - tar -xzf SDL2-2.24.1.tar.gz - cd SDL2-2.24.1 - ./configure - make -j 10 - sudo make install - - name: Prepare compile_commands.json - run: | - cmake -B build -DCMAKE_EXPORT_COMPILE_COMMANDS=ON - - name: Create results directory - run: | - mkdir clang-tidy-result - - name: Analyze - run: | - git diff -U0 HEAD^ -- 'src' 'include' ':!include/color.h' ':!include/libultra/*' ':!src/public/libultra/*' ':!src/graphic/Fast3D/*' ':!src/log/spd' | clang-tidy-diff -p1 -path build -export-fixes clang-tidy-result/fixes.yml - - name: Save PR metadata - run: | - echo ${{ github.event.number }} > clang-tidy-result/pr-id.txt - echo ${{ github.event.pull_request.head.repo.full_name }} > clang-tidy-result/pr-head-repo.txt - echo ${{ github.event.pull_request.head.ref }} > clang-tidy-result/pr-head-ref.txt - - uses: actions/upload-artifact@v2 - with: - name: clang-tidy-result - path: clang-tidy-result/ diff --git a/app/jni/src/libultraship/.github/workflows/tidy-result-publish.yml b/app/jni/src/libultraship/.github/workflows/tidy-result-publish.yml deleted file mode 100644 index e743cd6..0000000 --- a/app/jni/src/libultraship/.github/workflows/tidy-result-publish.yml +++ /dev/null @@ -1,74 +0,0 @@ -name: tidy-result-publish -on: - workflow_run: - workflows: [ tidy-format-validation ] - types: [ completed ] -jobs: - clang-tidy-results: - # Trigger the job only if the previous (insecure) workflow completed successfully - if: ${{ github.event.workflow_run.event == 'pull_request' && github.event.workflow_run.conclusion == 'success' }} - runs-on: ubuntu-20.04 - steps: - - name: Download analysis results - uses: actions/github-script@v3.1.0 - with: - script: | - let artifacts = await github.actions.listWorkflowRunArtifacts({ - owner: context.repo.owner, - repo: context.repo.repo, - run_id: ${{github.event.workflow_run.id }}, - }); - let matchArtifact = artifacts.data.artifacts.filter((artifact) => { - return artifact.name == "clang-tidy-result" - })[0]; - let download = await github.actions.downloadArtifact({ - owner: context.repo.owner, - repo: context.repo.repo, - artifact_id: matchArtifact.id, - archive_format: "zip", - }); - let fs = require("fs"); - fs.writeFileSync("${{github.workspace}}/clang-tidy-result.zip", Buffer.from(download.data)); - - name: Set environment variables - run: | - mkdir clang-tidy-result - unzip clang-tidy-result.zip -d clang-tidy-result - echo "pr_id=$(cat clang-tidy-result/pr-id.txt)" >> $GITHUB_ENV - echo "pr_head_repo=$(cat clang-tidy-result/pr-head-repo.txt)" >> $GITHUB_ENV - echo "pr_head_ref=$(cat clang-tidy-result/pr-head-ref.txt)" >> $GITHUB_ENV - - uses: actions/checkout@v2 - with: - repository: ${{ env.pr_head_repo }} - ref: ${{ env.pr_head_ref }} - persist-credentials: false - - name: Redownload analysis results - uses: actions/github-script@v3.1.0 - with: - script: | - let artifacts = await github.actions.listWorkflowRunArtifacts({ - owner: context.repo.owner, - repo: context.repo.repo, - run_id: ${{github.event.workflow_run.id }}, - }); - let matchArtifact = artifacts.data.artifacts.filter((artifact) => { - return artifact.name == "clang-tidy-result" - })[0]; - let download = await github.actions.downloadArtifact({ - owner: context.repo.owner, - repo: context.repo.repo, - artifact_id: matchArtifact.id, - archive_format: "zip", - }); - let fs = require("fs"); - fs.writeFileSync("${{github.workspace}}/clang-tidy-result.zip", Buffer.from(download.data)); - - name: Extract analysis results - run: | - mkdir clang-tidy-result - unzip clang-tidy-result.zip -d clang-tidy-result - - name: Run clang-tidy-pr-comments action - uses: platisd/clang-tidy-pr-comments@master - with: - github_token: ${{ secrets.GITHUB_TOKEN }} - clang_tidy_fixes: clang-tidy-result/fixes.yml - pull_request_id: ${{ env.pr_id }} - request_changes: true diff --git a/app/jni/src/libultraship/.gitignore b/app/jni/src/libultraship/.gitignore deleted file mode 100644 index fea92c6..0000000 --- a/app/jni/src/libultraship/.gitignore +++ /dev/null @@ -1,348 +0,0 @@ -## Ignore Visual Studio temporary files, build results, and -## files generated by popular Visual Studio add-ons. -## -## Get latest from https://github.com/github/gitignore/blob/master/VisualStudio.gitignore - -# User-specific files -*.rsuser -*.suo -*.user -*.userosscache -*.sln.docstates - -# User-specific files (MonoDevelop/Xamarin Studio) -*.userprefs - -# Mono auto generated files -mono_crash.* - -# Visual Studio 2015/2017 cache/options directory -.vs/ -# Uncomment if you have tasks that create the project's static files in wwwroot -#wwwroot/ - -# Visual Studio 2017 auto generated files -Generated\ Files/ - -# MSTest test Results -[Tt]est[Rr]esult*/ -[Bb]uild[Ll]og.* - -# NUnit -*.VisualState.xml -TestResult.xml -nunit-*.xml - -# Build Results of an ATL Project -[Dd]ebugPS/ -[Rr]eleasePS/ -dlldata.c - -# Benchmark Results -BenchmarkDotNet.Artifacts/ - -# .NET Core -project.lock.json -project.fragment.lock.json -artifacts/ - -# StyleCop -StyleCopReport.xml - -# Files built by Visual Studio -*_i.c -*_p.c -*_h.h -*.ilk -*.meta -*.obj -*.iobj -*.pch -*.pdb -*.ipdb -*.pgc -*.pgd -*.rsp -*.sbr -*.tlb -*.tli -*.tlh -*.tmp -*.tmp_proj -*_wpftmp.csproj -*.log -*.vspscc -*.vssscc -.builds -*.pidb -*.svclog -*.scc - -# Chutzpah Test files -_Chutzpah* - -# Visual C++ cache files -ipch/ -*.aps -*.ncb -*.opendb -*.opensdf -*.sdf -*.cachefile -*.VC.db -*.VC.VC.opendb - -# Visual Studio profiler -*.psess -*.vsp -*.vspx -*.sap - -# Visual Studio Trace Files -*.e2e - -# TFS 2012 Local Workspace -$tf/ - -# Guidance Automation Toolkit -*.gpState - -# ReSharper is a .NET coding add-in -_ReSharper*/ -*.[Rr]e[Ss]harper -*.DotSettings.user - -# TeamCity is a build add-in -_TeamCity* - -# DotCover is a Code Coverage Tool -*.dotCover - -# AxoCover is a Code Coverage Tool -.axoCover/* -!.axoCover/settings.json - -# Visual Studio code coverage results -*.coverage -*.coveragexml - -# NCrunch -_NCrunch_* -.*crunch*.local.xml -nCrunchTemp_* - -# MightyMoose -*.mm.* -AutoTest.Net/ - -# Web workbench (sass) -.sass-cache/ - -# Installshield output folder -[Ee]xpress/ - -# DocProject is a documentation generator add-in -DocProject/buildhelp/ -DocProject/Help/*.HxT -DocProject/Help/*.HxC -DocProject/Help/*.hhc -DocProject/Help/*.hhk -DocProject/Help/*.hhp -DocProject/Help/Html2 -DocProject/Help/html - -# Click-Once directory -publish/ - -# Publish Web Output -*.[Pp]ublish.xml -*.azurePubxml -# Note: Comment the next line if you want to checkin your web deploy settings, -# but database connection strings (with potential passwords) will be unencrypted -*.pubxml -*.publishproj - -# Microsoft Azure Web App publish settings. Comment the next line if you want to -# checkin your Azure Web App publish settings, but sensitive information contained -# in these scripts will be unencrypted -PublishScripts/ - -# NuGet Packages -*.nupkg -# NuGet Symbol Packages -*.snupkg -# The packages folder can be ignored because of Package Restore -**/[Pp]ackages/* -# except build/, which is used as an MSBuild target. -!**/[Pp]ackages/build/ -# Uncomment if necessary however generally it will be regenerated when needed -#!**/[Pp]ackages/repositories.config -# NuGet v3's project.json files produces more ignorable files -*.nuget.props -*.nuget.targets - -# Microsoft Azure Build Output -csx/ -*.build.csdef - -# Microsoft Azure Emulator -ecf/ -rcf/ - -# Windows Store app package directories and files -AppPackages/ -BundleArtifacts/ -Package.StoreAssociation.xml -_pkginfo.txt -*.appx -*.appxbundle -*.appxupload - -# Visual Studio cache files -# files ending in .cache can be ignored -*.[Cc]ache -# but keep track of directories ending in .cache -!?*.[Cc]ache/ - -# Others -ClientBin/ -~$* -*~ -*.dbmdl -*.dbproj.schemaview -*.jfm -*.pfx -*.publishsettings -orleans.codegen.cs - -# Including strong name files can present a security risk -# (https://github.com/github/gitignore/pull/2483#issue-259490424) -#*.snk - -# Since there are multiple workflows, uncomment next line to ignore bower_components -# (https://github.com/github/gitignore/pull/1529#issuecomment-104372622) -#bower_components/ - -# RIA/Silverlight projects -Generated_Code/ - -# Backup & report files from converting an old project file -# to a newer Visual Studio version. Backup files are not needed, -# because we have git ;-) -_UpgradeReport_Files/ -Backup*/ -UpgradeLog*.XML -UpgradeLog*.htm -ServiceFabricBackup/ -*.rptproj.bak - -# SQL Server files -*.mdf -*.ldf -*.ndf - -# Business Intelligence projects -*.rdl.data -*.bim.layout -*.bim_*.settings -*.rptproj.rsuser -*- [Bb]ackup.rdl -*- [Bb]ackup ([0-9]).rdl -*- [Bb]ackup ([0-9][0-9]).rdl - -# Microsoft Fakes -FakesAssemblies/ - -# GhostDoc plugin setting file -*.GhostDoc.xml - -# Node.js Tools for Visual Studio -.ntvs_analysis.dat -node_modules/ - -# Visual Studio 6 build log -*.plg - -# Visual Studio 6 workspace options file -*.opt - -# Visual Studio 6 auto-generated workspace file (contains which files were open etc.) -*.vbw - -# Visual Studio LightSwitch build output -**/*.HTMLClient/GeneratedArtifacts -**/*.DesktopClient/GeneratedArtifacts -**/*.DesktopClient/ModelManifest.xml -**/*.Server/GeneratedArtifacts -**/*.Server/ModelManifest.xml -_Pvt_Extensions - -# Paket dependency manager -.paket/paket.exe -paket-files/ - -# FAKE - F# Make -.fake/ - -# CodeRush personal settings -.cr/personal - -# Python Tools for Visual Studio (PTVS) -__pycache__/ -*.pyc - -# Cake - Uncomment if you are using it -# tools/** -# !tools/packages.config - -# Tabs Studio -*.tss - -# Telerik's JustMock configuration file -*.jmconfig - -# BizTalk build output -*.btp.cs -*.btm.cs -*.odx.cs -*.xsd.cs - -# OpenCover UI analysis results -OpenCover/ - -# Azure Stream Analytics local run output -ASALocalRun/ - -# MSBuild Binary and Structured Log -*.binlog - -# NVidia Nsight GPU debugger configuration file -*.nvuser - -# MFractors (Xamarin productivity tool) working folder -.mfractor/ - -# Local History for Visual Studio -.localhistory/ - -# BeatPulse healthcheck temp database -healthchecksdb - -# Backup folder for Package Reference Convert tool in Visual Studio 2017 -MigrationBackup/ - -# Ionide (cross platform F# VS Code tools) working folder -.ionide/ - -!libultraship/Lib/** -libultraship/DebugObj/* -build/ -build-cmake/ -libultraship.a -libultraship.lib -ZAPDUtils.lib -.DS_Store -.vscode/ -.vs/ -.idea/ -cmake-build-** diff --git a/app/jni/src/libultraship/CMakeLists.txt b/app/jni/src/libultraship/CMakeLists.txt deleted file mode 100644 index c4e44de..0000000 --- a/app/jni/src/libultraship/CMakeLists.txt +++ /dev/null @@ -1,29 +0,0 @@ -cmake_minimum_required(VERSION 3.16.0) - -option(NON_PORTABLE "Build a non-portable version" OFF) - -project(libultraship LANGUAGES C CXX) -if (CMAKE_SYSTEM_NAME STREQUAL "Darwin") - enable_language(OBJCXX) - set(CMAKE_OBJC_FLAGS "${CMAKE_OBJC_FLAGS} -fobjc-arc") - set(CMAKE_OBJCXX_FLAGS "${CMAKE_OBJCXX_FLAGS} -fobjc-arc") -endif() - -if (CMAKE_SYSTEM_NAME STREQUAL "Windows") - set(CMAKE_MSVC_RUNTIME_LIBRARY "MultiThreaded$<$:Debug>") -endif() - -include(cmake/Utils.cmake) - -if (CMAKE_SYSTEM_NAME STREQUAL "Windows" AND USE_AUTO_VCPKG) - include(cmake/automate-vcpkg.cmake) - - set(VCPKG_TRIPLET x64-windows-static) - set(VCPKG_TARGET_TRIPLET x64-windows-static) - - vcpkg_bootstrap() - vcpkg_install_packages(zlib bzip2 sdl2 glew) -endif() - -add_subdirectory("extern") -add_subdirectory("src") diff --git a/app/jni/src/libultraship/CODE_OF_CONDUCT.md b/app/jni/src/libultraship/CODE_OF_CONDUCT.md deleted file mode 100644 index e893f1a..0000000 --- a/app/jni/src/libultraship/CODE_OF_CONDUCT.md +++ /dev/null @@ -1,134 +0,0 @@ - -# Contributor Covenant Code of Conduct - -## Our Pledge - -We as members, contributors, and leaders pledge to make participation in our -community a harassment-free experience for everyone, regardless of age, body -size, visible or invisible disability, ethnicity, sex characteristics, gender -identity and expression, level of experience, education, socio-economic status, -nationality, personal appearance, race, caste, color, religion, or sexual -identity and orientation. - -We pledge to act and interact in ways that contribute to an open, welcoming, -diverse, inclusive, and healthy community. - -## Our Standards - -Examples of behavior that contributes to a positive environment for our -community include: - -* Demonstrating empathy and kindness toward other people -* Being respectful of differing opinions, viewpoints, and experiences -* Giving and gracefully accepting constructive feedback -* Accepting responsibility and apologizing to those affected by our mistakes, - and learning from the experience -* Focusing on what is best not just for us as individuals, but for the overall - community - -Examples of unacceptable behavior include: - -* The use of sexualized language or imagery, and sexual attention or advances of - any kind -* Trolling, insulting or derogatory comments, and personal or political attacks -* Public or private harassment -* Publishing others' private information, such as a physical or email address, - without their explicit permission -* Other conduct which could reasonably be considered inappropriate in a - professional setting - -## Enforcement Responsibilities - -Community leaders are responsible for clarifying and enforcing our standards of -acceptable behavior and will take appropriate and fair corrective action in -response to any behavior that they deem inappropriate, threatening, offensive, -or harmful. - -Community leaders have the right and responsibility to remove, edit, or reject -comments, commits, code, wiki edits, issues, and other contributions that are -not aligned to this Code of Conduct, and will communicate reasons for moderation -decisions when appropriate. - -## Scope - -This Code of Conduct applies within all community spaces, and also applies when -an individual is officially representing the community in public spaces. -Examples of representing our community include using an official e-mail address, -posting via an official social media account, or acting as an appointed -representative at an online or offline event. - -## Enforcement - -Instances of abusive, harassing, or otherwise unacceptable behavior may be -reported to the community leaders responsible for enforcement at -kenixwhisperwind@gmail.com. -All complaints will be reviewed and investigated promptly and fairly. - -All community leaders are obligated to respect the privacy and security of the -reporter of any incident. - -## Enforcement Guidelines - -Community leaders will follow these Community Impact Guidelines in determining -the consequences for any action they deem in violation of this Code of Conduct: - -### 1. Correction - -**Community Impact**: Use of inappropriate language or other behavior deemed -unprofessional or unwelcome in the community. - -**Consequence**: A private, written warning from community leaders, providing -clarity around the nature of the violation and an explanation of why the -behavior was inappropriate. A public apology may be requested. - -### 2. Warning - -**Community Impact**: A violation through a single incident or series of -actions. - -**Consequence**: A warning with consequences for continued behavior. No -interaction with the people involved, including unsolicited interaction with -those enforcing the Code of Conduct, for a specified period of time. This -includes avoiding interactions in community spaces as well as external channels -like social media. Violating these terms may lead to a temporary or permanent -ban. - -### 3. Temporary Ban - -**Community Impact**: A serious violation of community standards, including -sustained inappropriate behavior. - -**Consequence**: A temporary ban from any sort of interaction or public -communication with the community for a specified period of time. No public or -private interaction with the people involved, including unsolicited interaction -with those enforcing the Code of Conduct, is allowed during this period. -Violating these terms may lead to a permanent ban. - -### 4. Permanent Ban - -**Community Impact**: Demonstrating a pattern of violation of community -standards, including sustained inappropriate behavior, harassment of an -individual, or aggression toward or disparagement of classes of individuals. - -**Consequence**: A permanent ban from any sort of public interaction within the -community. - -## Attribution - -This Code of Conduct is adapted from the [Contributor Covenant][homepage], -version 2.1, available at -[https://www.contributor-covenant.org/version/2/1/code_of_conduct.html][v2.1]. - -Community Impact Guidelines were inspired by -[Mozilla's code of conduct enforcement ladder][Mozilla CoC]. - -For answers to common questions about this code of conduct, see the FAQ at -[https://www.contributor-covenant.org/faq][FAQ]. Translations are available at -[https://www.contributor-covenant.org/translations][translations]. - -[homepage]: https://www.contributor-covenant.org -[v2.1]: https://www.contributor-covenant.org/version/2/1/code_of_conduct.html -[Mozilla CoC]: https://github.com/mozilla/diversity -[FAQ]: https://www.contributor-covenant.org/faq -[translations]: https://www.contributor-covenant.org/translations - diff --git a/app/jni/src/libultraship/CONTRIBUTING.md b/app/jni/src/libultraship/CONTRIBUTING.md deleted file mode 100644 index 8f9c357..0000000 --- a/app/jni/src/libultraship/CONTRIBUTING.md +++ /dev/null @@ -1,19 +0,0 @@ -# Preface -LUS accepts any and all contributions. You can interact with the project via PRs, issues, email (kenixwhisperwind@gmail.com), or [Discord](https://discord.gg/RQvdvavB). - -# Code of Conduct -Please review and abide by our [code of conduct](https://github.com/Kenix3/libultraship/blob/main/CODE_OF_CONDUCT.md). - -# Building -Please see the [readme](https://github.com/Kenix3/libultraship/blob/main/README.md) for building instructions. - -# Pull Requests -## Procedures -Our CI system will automatically check your PR to ensure that it fits [formatting guidelines](https://github.com/Kenix3/libultraship/blob/main/.clang-format), [linter guidelines](https://github.com/Kenix3/libultraship/blob/main/.clang-tidy), and that the code builds. The submitter of a PR is required to ensure their PR passes all CI checks. The submitter of the PR is encouraged to address all PR review comments in a timely manner to ensure a timely merge of the PR. -### Troubleshooting CI Errors -#### tidy-format-validation -If the tidy-format-validation check fails, then you need to run clang-format. Below is a command that can be used on Linux. Most modern IDEs have a clang-format plugin that can be used. The [.clang-format file can be found here](https://github.com/Kenix3/libultraship/blob/main/.clang-format) -##### Running clang-format -``` -find src include -name "*.cpp" -o -name "*.h" | sed 's| |\\ |g' | xargs clang-format-12 -i -``` diff --git a/app/jni/src/libultraship/LICENSE b/app/jni/src/libultraship/LICENSE deleted file mode 100644 index 90e752c..0000000 --- a/app/jni/src/libultraship/LICENSE +++ /dev/null @@ -1,21 +0,0 @@ -MIT License - -Copyright (c) 2022 kenix3 kenixwhisperwind@gmail.com - -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. diff --git a/app/jni/src/libultraship/README.md b/app/jni/src/libultraship/README.md deleted file mode 100644 index 77c75c6..0000000 --- a/app/jni/src/libultraship/README.md +++ /dev/null @@ -1,54 +0,0 @@ -# libultraship -libultraship (LUS) is a library meant to provide reimplementations of libultra (n64 sdk) functions that run on modern hardware. - -LUS uses an asset loading system where data is stored separately from the executable in an archive file ending in `.otr`, which is an [`.mpq`](http://www.zezula.net/en/mpq/main.html) compatible file. This separation the data from the executable follows modern design practices and that it is more mod friendly. All one needs to do is supply a patch `.otr` and the system will automatically replace the data. - -## Contributing -LUS accepts any and all contributions. You can interact with the project via PRs, issues, email (kenixwhisperwind@gmail.com), or [Discord](https://discord.gg/shipofharkinian). -Please see [CONTRIBUTING.md](https://github.com/Kenix3/libultraship/blob/main/CONTRIBUTING.md) file for more information. - -## Versioning -We use semantic versioning. We have defined the API as: every C linkage function, variable, struct, class, public class method, or enum included from libultraship.h. - -## Building on Linux/Mac -``` -cmake -H. -Bbuild -cmake --build build -``` - -## Generating a Visual Studio `.sln` on Windows -``` -# Visual Studio 2022 -& 'C:\Program Files\CMake\bin\cmake' -DUSE_AUTO_VCPKG=true -S . -B "build/x64" -G "Visual Studio 17 2022" -T v142 -A x64 -# Visual Studio 2019 -& 'C:\Program Files\CMake\bin\cmake' -DUSE_AUTO_VCPKG=true -S . -B "build/x64" -G "Visual Studio 16 2019" -T v142 -A x64 -``` - -## To build on Windows -``` -& 'C:\Program Files\CMake\bin\cmake' --build .\build\x64 -``` - -## Sponsors -Thankyou to JetBrains for providing their IDE [CLion](https://www.jetbrains.com/clion/) to me for free! - -## License -LUS is licensed under the [MIT](https://github.com/Kenix3/libultraship/blob/main/LICENSE) license. - -LUS makes use of the following third party libraries and resources: -- [Fast3D](https://github.com/Kenix3/libultraship/tree/main/src/graphic/Fast3D) (MIT) render display lists. -- [ImGui](https://github.com/ocornut/imgui) (MIT) display UI. -- [StormLib](https://github.com/ladislav-zezula/StormLib) (MIT) create and read `.mpq` compatible archive files. -- [StrHash64](https://github.com/Kenix3/libultraship/blob/main/extern/StrHash64/StrHash64.h) (MIT, zlib, BSD-3-Clause) provide crc64 implementation. -- [ZAPD](https://github.com/zeldaret/ZAPD) (MIT) asset utilities. -- [dr_libs](https://github.com/mackron/dr_libs) (MIT-0) mp3 and wav file conversion. -- [metal-cpp](https://github.com/bkaradzic/metal-cpp) (Apache 2.0) interface to the Apple Metal rendering backend. -- [nlohmann-json](https://github.com/nlohmann/json) (MIT) json parsing and saving. -- [spdlog](https://github.com/gabime/spdlog) (MIT) logging -- [stb](https://github.com/nothings/stb) (MIT) image conversion -- [thread-pool](https://github.com/bshoshany/thread-pool) (MIT) thread pool for the resource manager -- [tinyxml2](https://github.com/leethomason/tinyxml2) (zlib) parse XML files for resource loaders -- [zlib](https://github.com/madler/zlib) (zlib) compression used in StormLib -- [bzip2](https://github.com/libarchive/bzip2) (bzip2) compression used in StormLib -- [sdl2](https://github.com/libsdl-org/SDL) (zlib) window manager, controllers, and audio player -- [glew](https://github.com/nigels-com/glew) (modified BSD-3-Clause and MIT) OpenGL extension loading library. diff --git a/app/jni/src/libultraship/cmake/Default.cmake b/app/jni/src/libultraship/cmake/Default.cmake deleted file mode 100644 index 70bfa90..0000000 --- a/app/jni/src/libultraship/cmake/Default.cmake +++ /dev/null @@ -1,65 +0,0 @@ -################################################################################ -# Command for variable_watch. This command issues error message, if a variable -# is changed. If variable PROPERTY_READER_GUARD_DISABLED is TRUE nothing happens -# variable_watch( property_reader_guard) -################################################################################ -function(property_reader_guard VARIABLE ACCESS VALUE CURRENT_LIST_FILE STACK) - if("${PROPERTY_READER_GUARD_DISABLED}") - return() - endif() - - if("${ACCESS}" STREQUAL "MODIFIED_ACCESS") - message(FATAL_ERROR - " Variable ${VARIABLE} is not supposed to be changed.\n" - " It is used only for reading target property ${VARIABLE}.\n" - " Use\n" - " set_target_properties(\"\" PROPERTIES \"${VARIABLE}\" \"\")\n" - " or\n" - " set_target_properties(\"\" PROPERTIES \"${VARIABLE}_\" \"\")\n" - " instead.\n") - endif() -endfunction() - -################################################################################ -# Create variable with generator expression that expands to value of -# target property _. If property is empty or not set then property -# is used instead. Variable has watcher property_reader_guard that -# doesn't allow to edit it. -# create_property_reader() -# Input: -# name - Name of watched property and output variable -################################################################################ -function(create_property_reader NAME) - set(PROPERTY_READER_GUARD_DISABLED TRUE) - set(CONFIG_VALUE "$>>>") - set(IS_CONFIG_VALUE_EMPTY "$") - set(GENERAL_VALUE "$>") - set("${NAME}" "$" PARENT_SCOPE) - variable_watch("${NAME}" property_reader_guard) -endfunction() - -################################################################################ -# Set property $_${PROPS_CONFIG_U} of ${PROPS_TARGET} to -# set_config_specific_property( ) -# Input: -# name - Prefix of property name -# value - New value -################################################################################ -function(set_config_specific_property NAME VALUE) - set_target_properties("${PROPS_TARGET}" PROPERTIES "${NAME}_${PROPS_CONFIG_U}" "${VALUE}") -endfunction() - -################################################################################ - -create_property_reader("TARGET_NAME") -create_property_reader("OUTPUT_DIRECTORY") - -set_config_specific_property("TARGET_NAME" "${PROPS_TARGET}") -set_config_specific_property("OUTPUT_NAME" "${TARGET_NAME}") -set_config_specific_property("ARCHIVE_OUTPUT_NAME" "${TARGET_NAME}") -set_config_specific_property("LIBRARY_OUTPUT_NAME" "${TARGET_NAME}") -set_config_specific_property("RUNTIME_OUTPUT_NAME" "${TARGET_NAME}") - -set_config_specific_property("ARCHIVE_OUTPUT_DIRECTORY" "${OUTPUT_DIRECTORY}") -set_config_specific_property("LIBRARY_OUTPUT_DIRECTORY" "${OUTPUT_DIRECTORY}") -set_config_specific_property("RUNTIME_OUTPUT_DIRECTORY" "${OUTPUT_DIRECTORY}") \ No newline at end of file diff --git a/app/jni/src/libultraship/cmake/DefaultCXX.cmake b/app/jni/src/libultraship/cmake/DefaultCXX.cmake deleted file mode 100644 index 9305278..0000000 --- a/app/jni/src/libultraship/cmake/DefaultCXX.cmake +++ /dev/null @@ -1,12 +0,0 @@ -include("${CMAKE_CURRENT_LIST_DIR}/Default.cmake") - -set_config_specific_property("OUTPUT_DIRECTORY" "${CMAKE_SOURCE_DIR}$<$>:/${CMAKE_VS_PLATFORM_NAME}>/${PROPS_CONFIG}") - -if(MSVC) - create_property_reader("DEFAULT_CXX_EXCEPTION_HANDLING") - create_property_reader("DEFAULT_CXX_DEBUG_INFORMATION_FORMAT") - - # set_target_properties("${PROPS_TARGET}" PROPERTIES MSVC_RUNTIME_LIBRARY "MultiThreaded$<$:Debug>DLL") - set_config_specific_property("DEFAULT_CXX_EXCEPTION_HANDLING" "/EHsc") - set_config_specific_property("DEFAULT_CXX_DEBUG_INFORMATION_FORMAT" "/Zi") -endif() \ No newline at end of file diff --git a/app/jni/src/libultraship/cmake/HandleCompilerRT.cmake b/app/jni/src/libultraship/cmake/HandleCompilerRT.cmake deleted file mode 100644 index dad2634..0000000 --- a/app/jni/src/libultraship/cmake/HandleCompilerRT.cmake +++ /dev/null @@ -1,123 +0,0 @@ -# Check if the compiler-rt library file path exists. -# If found, cache the path in: -# COMPILER_RT_LIBRARY-- -# If err_flag is true OR path not found, emit a message and set: -# COMPILER_RT_LIBRARY-- to NOTFOUND -function(cache_compiler_rt_library err_flag name target library_file) - if(err_flag OR NOT EXISTS "${library_file}") - message(STATUS "Failed to find compiler-rt ${name} library for ${target}") - set(COMPILER_RT_LIBRARY_${name}_${target} "NOTFOUND" CACHE INTERNAL - "compiler-rt ${name} library for ${target}") - else() - message(STATUS "Found compiler-rt ${name} library: ${library_file}") - set(COMPILER_RT_LIBRARY_${name}_${target} "${library_file}" CACHE INTERNAL - "compiler-rt ${name} library for ${target}") - endif() -endfunction() - -function(get_component_name name variable) - if(APPLE) - if(NOT name MATCHES "builtins.*") - set(component_name "${name}_") - endif() - if (CMAKE_OSX_SYSROOT MATCHES ".+MacOSX.+") - set(component_name "${component_name}osx") - - elseif (CMAKE_OSX_SYSROOT MATCHES ".+iPhoneOS.+") - set(component_name "${component_name}ios") - elseif (CMAKE_OSX_SYSROOT MATCHES ".+iPhoneSimulator.+") - set(component_name "${component_name}iossim") - - elseif (CMAKE_OSX_SYSROOT MATCHES ".+AppleTVOS.+") - set(component_name "${component_name}tvos") - elseif (CMAKE_OSX_SYSROOT MATCHES ".+AppleTVSimulator.+") - set(component_name "${component_name}tvossim") - - elseif (CMAKE_OSX_SYSROOT MATCHES ".+WatchOS.+") - set(component_name "${component_name}watchos") - elseif (CMAKE_OSX_SYSROOT MATCHES ".+WatchSimulator.+") - set(component_name "${component_name}watchossim") - else() - message(WARNING "Unknown Apple SDK ${CMAKE_OSX_SYSROOT}, we don't know which compiler-rt library suffix to use.") - endif() - else() - set(component_name "${name}") - endif() - set(${variable} "${component_name}" PARENT_SCOPE) -endfunction() - -# Find the path to compiler-rt library `name` (e.g. "builtins") for the -# specified `TARGET` (e.g. "x86_64-linux-gnu") and return it in `variable`. -# This calls cache_compiler_rt_library that caches the path to speed up -# repeated invocations with the same `name` and `target`. -function(find_compiler_rt_library name variable) - cmake_parse_arguments(ARG "" "TARGET;FLAGS" "" ${ARGN}) - # While we can use compiler-rt runtimes with other compilers, we need to - # query the compiler for runtime location and thus we require Clang. - if(NOT CMAKE_CXX_COMPILER_ID MATCHES Clang) - set(${variable} "NOTFOUND" PARENT_SCOPE) - return() - endif() - set(target "${ARG_TARGET}") - if(NOT target AND CMAKE_CXX_COMPILER_TARGET) - set(target "${CMAKE_CXX_COMPILER_TARGET}") - endif() - if(NOT DEFINED COMPILER_RT_LIBRARY_builtins_${target}) - # If the cache variable is not defined, invoke Clang and then - # set it with cache_compiler_rt_library. - set(clang_command ${CMAKE_CXX_COMPILER} "${ARG_FLAGS}") - if(target) - list(APPEND clang_command "--target=${target}") - endif() - get_property(cxx_flags CACHE CMAKE_CXX_FLAGS PROPERTY VALUE) - string(REPLACE " " ";" cxx_flags "${cxx_flags}") - list(APPEND clang_command ${cxx_flags}) - set(cmd_prefix "") - if(MSVC AND ${CMAKE_CXX_COMPILER_ID} MATCHES "Clang") - set(cmd_prefix "/clang:") - endif() - execute_process( - COMMAND ${clang_command} "${cmd_prefix}--rtlib=compiler-rt" "${cmd_prefix}-print-libgcc-file-name" - RESULT_VARIABLE had_error - OUTPUT_VARIABLE library_file - ) - string(STRIP "${library_file}" library_file) - file(TO_CMAKE_PATH "${library_file}" library_file) - get_filename_component(dirname ${library_file} DIRECTORY) - if(APPLE) - execute_process( - COMMAND ${clang_command} "--print-resource-dir" - RESULT_VARIABLE had_error - OUTPUT_VARIABLE resource_dir - ) - string(STRIP "${resource_dir}" resource_dir) - set(dirname "${resource_dir}/lib/darwin") - endif() - get_filename_component(basename ${library_file} NAME) - if(basename MATCHES ".*clang_rt\.([a-z0-9_\-]+)\.(a|lib)") - set(from_name ${CMAKE_MATCH_1}) - get_component_name(${CMAKE_MATCH_1} to_name) - string(REPLACE "${from_name}" "${to_name}" basename "${basename}") - set(library_file "${dirname}/${basename}") - cache_compiler_rt_library(${had_error} builtins "${target}" "${library_file}") - endif() - endif() - if(NOT COMPILER_RT_LIBRARY_builtins_${target}) - set(${variable} "NOTFOUND" PARENT_SCOPE) - return() - endif() - if(NOT DEFINED COMPILER_RT_LIBRARY_${name}_${target}) - # Clang gives only the builtins library path. Other library paths are - # obtained by substituting "builtins" with ${name} in the builtins - # path and then checking if the resultant path exists. The result of - # this check is also cached by cache_compiler_rt_library. - set(library_file "${COMPILER_RT_LIBRARY_builtins_${target}}") - if(library_file MATCHES ".*clang_rt\.([a-z0-9_\-]+)\.(a|lib)") - set(from_name ${CMAKE_MATCH_0}) - get_component_name(${name} to_name) - string(REPLACE "${from_name}" "${to_name}" library_file "${library_file}") - cache_compiler_rt_library(FALSE "${name}" "${target}" "${library_file}") - endif() - endif() - set(${variable} "${COMPILER_RT_LIBRARY_${name}_${target}}" PARENT_SCOPE) -endfunction() \ No newline at end of file diff --git a/app/jni/src/libultraship/cmake/Utils.cmake b/app/jni/src/libultraship/cmake/Utils.cmake deleted file mode 100644 index c691eef..0000000 --- a/app/jni/src/libultraship/cmake/Utils.cmake +++ /dev/null @@ -1,248 +0,0 @@ -# utils file for projects came from visual studio solution with cmake-converter. - -################################################################################ -# Wrap each token of the command with condition -################################################################################ -cmake_policy(PUSH) -cmake_policy(SET CMP0054 NEW) -macro(prepare_commands) - unset(TOKEN_ROLE) - unset(COMMANDS) - foreach(TOKEN ${ARG_COMMANDS}) - if("${TOKEN}" STREQUAL "COMMAND") - set(TOKEN_ROLE "KEYWORD") - elseif("${TOKEN_ROLE}" STREQUAL "KEYWORD") - set(TOKEN_ROLE "CONDITION") - elseif("${TOKEN_ROLE}" STREQUAL "CONDITION") - set(TOKEN_ROLE "COMMAND") - elseif("${TOKEN_ROLE}" STREQUAL "COMMAND") - set(TOKEN_ROLE "ARG") - endif() - - if("${TOKEN_ROLE}" STREQUAL "KEYWORD") - list(APPEND COMMANDS "${TOKEN}") - elseif("${TOKEN_ROLE}" STREQUAL "CONDITION") - set(CONDITION ${TOKEN}) - elseif("${TOKEN_ROLE}" STREQUAL "COMMAND") - list(APPEND COMMANDS "$<$:${DUMMY}>$<${CONDITION}:${TOKEN}>") - elseif("${TOKEN_ROLE}" STREQUAL "ARG") - list(APPEND COMMANDS "$<${CONDITION}:${TOKEN}>") - endif() - endforeach() -endmacro() -cmake_policy(POP) - -################################################################################ -# Transform all the tokens to absolute paths -################################################################################ -macro(prepare_output) - unset(OUTPUT) - foreach(TOKEN ${ARG_OUTPUT}) - if(IS_ABSOLUTE ${TOKEN}) - list(APPEND OUTPUT "${TOKEN}") - else() - list(APPEND OUTPUT "${CMAKE_CURRENT_SOURCE_DIR}/${TOKEN}") - endif() - endforeach() -endmacro() - -################################################################################ -# Parse add_custom_command_if args. -# -# Input: -# PRE_BUILD - Pre build event option -# PRE_LINK - Pre link event option -# POST_BUILD - Post build event option -# TARGET - Target -# OUTPUT - List of output files -# DEPENDS - List of files on which the command depends -# COMMANDS - List of commands(COMMAND condition1 commannd1 args1 COMMAND -# condition2 commannd2 args2 ...) -# Output: -# OUTPUT - Output files -# DEPENDS - Files on which the command depends -# COMMENT - Comment -# PRE_BUILD - TRUE/FALSE -# PRE_LINK - TRUE/FALSE -# POST_BUILD - TRUE/FALSE -# TARGET - Target name -# COMMANDS - Prepared commands(every token is wrapped in CONDITION) -# NAME - Unique name for custom target -# STEP - PRE_BUILD/PRE_LINK/POST_BUILD -################################################################################ -function(add_custom_command_if_parse_arguments) - cmake_parse_arguments("ARG" "PRE_BUILD;PRE_LINK;POST_BUILD" "TARGET;COMMENT" "DEPENDS;OUTPUT;COMMANDS" ${ARGN}) - - if(WIN32) - set(DUMMY "cd.") - elseif(UNIX) - set(DUMMY "true") - endif() - - prepare_commands() - prepare_output() - - set(DEPENDS "${ARG_DEPENDS}") - set(COMMENT "${ARG_COMMENT}") - set(PRE_BUILD "${ARG_PRE_BUILD}") - set(PRE_LINK "${ARG_PRE_LINK}") - set(POST_BUILD "${ARG_POST_BUILD}") - set(TARGET "${ARG_TARGET}") - if(PRE_BUILD) - set(STEP "PRE_BUILD") - elseif(PRE_LINK) - set(STEP "PRE_LINK") - elseif(POST_BUILD) - set(STEP "POST_BUILD") - endif() - set(NAME "${TARGET}_${STEP}") - - set(OUTPUT "${OUTPUT}" PARENT_SCOPE) - set(DEPENDS "${DEPENDS}" PARENT_SCOPE) - set(COMMENT "${COMMENT}" PARENT_SCOPE) - set(PRE_BUILD "${PRE_BUILD}" PARENT_SCOPE) - set(PRE_LINK "${PRE_LINK}" PARENT_SCOPE) - set(POST_BUILD "${POST_BUILD}" PARENT_SCOPE) - set(TARGET "${TARGET}" PARENT_SCOPE) - set(COMMANDS "${COMMANDS}" PARENT_SCOPE) - set(STEP "${STEP}" PARENT_SCOPE) - set(NAME "${NAME}" PARENT_SCOPE) -endfunction() - -################################################################################ -# Add conditional custom command -# -# Generating Files -# The first signature is for adding a custom command to produce an output: -# add_custom_command_if( -# -# -# -# [COMMAND condition command2 [args2...]] -# [DEPENDS [depends...]] -# [COMMENT comment] -# -# Build Events -# add_custom_command_if( -# -# -# -# [COMMAND condition command2 [args2...]] -# [COMMENT comment] -# -# Input: -# output - Output files the command is expected to produce -# condition - Generator expression for wrapping the command -# command - Command-line(s) to execute at build time. -# args - Command`s args -# depends - Files on which the command depends -# comment - Display the given message before the commands are executed at -# build time. -# PRE_BUILD - Run before any other rules are executed within the target -# PRE_LINK - Run after sources have been compiled but before linking the -# binary -# POST_BUILD - Run after all other rules within the target have been -# executed -################################################################################ -function(add_custom_command_if) - add_custom_command_if_parse_arguments(${ARGN}) - - if(OUTPUT AND TARGET) - message(FATAL_ERROR "Wrong syntax. A TARGET and OUTPUT can not both be specified.") - endif() - - if(OUTPUT) - add_custom_command(OUTPUT ${OUTPUT} - ${COMMANDS} - DEPENDS ${DEPENDS} - WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR} - COMMENT ${COMMENT}) - elseif(TARGET) - if(PRE_BUILD AND NOT ${CMAKE_GENERATOR} MATCHES "Visual Studio") - add_custom_target( - ${NAME} - ${COMMANDS} - WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR} - COMMENT ${COMMENT}) - add_dependencies(${TARGET} ${NAME}) - else() - add_custom_command( - TARGET ${TARGET} - ${STEP} - ${COMMANDS} - WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR} - COMMENT ${COMMENT}) - endif() - else() - message(FATAL_ERROR "Wrong syntax. A TARGET or OUTPUT must be specified.") - endif() -endfunction() - -################################################################################ -# Use props file for a target and configs -# use_props( ) -# Inside there are following variables: -# PROPS_TARGET - -# PROPS_CONFIG - One of -# PROPS_CONFIG_U - Uppercase PROPS_CONFIG -# Input: -# target - Target to apply props file -# configs - Build configurations to apply props file -# props_file - CMake script -################################################################################ -macro(use_props TARGET CONFIGS PROPS_FILE) - set(PROPS_TARGET "${TARGET}") - foreach(PROPS_CONFIG ${CONFIGS}) - string(TOUPPER "${PROPS_CONFIG}" PROPS_CONFIG_U) - - get_filename_component(ABSOLUTE_PROPS_FILE "${PROPS_FILE}" ABSOLUTE BASE_DIR "${CMAKE_CURRENT_LIST_DIR}") - if(EXISTS "${ABSOLUTE_PROPS_FILE}") - include("${ABSOLUTE_PROPS_FILE}") - else() - message(WARNING "Corresponding cmake file from props \"${ABSOLUTE_PROPS_FILE}\" doesn't exist") - endif() - endforeach() -endmacro() - -################################################################################ -# Add compile options to source file -# source_file_compile_options( [compile_options...]) -# Input: -# source_file - Source file -# compile_options - Options to add to COMPILE_FLAGS property -################################################################################ -function(source_file_compile_options SOURCE_FILE) - if("${ARGC}" LESS_EQUAL "1") - return() - endif() - - get_source_file_property(COMPILE_OPTIONS "${SOURCE_FILE}" COMPILE_OPTIONS) - - if(COMPILE_OPTIONS) - list(APPEND COMPILE_OPTIONS ${ARGN}) - else() - set(COMPILE_OPTIONS "${ARGN}") - endif() - - set_source_files_properties("${SOURCE_FILE}" PROPERTIES COMPILE_OPTIONS "${COMPILE_OPTIONS}") -endfunction() - -################################################################################ -# Default properties of visual studio projects -################################################################################ -set(DEFAULT_CXX_PROPS "${CMAKE_CURRENT_LIST_DIR}/DefaultCXX.cmake") - -function(get_linux_lsb_release_information) - find_program(LSB_RELEASE_EXEC lsb_release) - if(NOT LSB_RELEASE_EXEC) - message(FATAL_ERROR "Could not detect lsb_release executable, can not gather required information") - endif() - - execute_process(COMMAND "${LSB_RELEASE_EXEC}" --short --id OUTPUT_VARIABLE LSB_RELEASE_ID_SHORT OUTPUT_STRIP_TRAILING_WHITESPACE) - execute_process(COMMAND "${LSB_RELEASE_EXEC}" --short --release OUTPUT_VARIABLE LSB_RELEASE_VERSION_SHORT OUTPUT_STRIP_TRAILING_WHITESPACE) - execute_process(COMMAND "${LSB_RELEASE_EXEC}" --short --codename OUTPUT_VARIABLE LSB_RELEASE_CODENAME_SHORT OUTPUT_STRIP_TRAILING_WHITESPACE) - - set(LSB_RELEASE_ID_SHORT "${LSB_RELEASE_ID_SHORT}" PARENT_SCOPE) - set(LSB_RELEASE_VERSION_SHORT "${LSB_RELEASE_VERSION_SHORT}" PARENT_SCOPE) - set(LSB_RELEASE_CODENAME_SHORT "${LSB_RELEASE_CODENAME_SHORT}" PARENT_SCOPE) -endfunction() diff --git a/app/jni/src/libultraship/cmake/automate-vcpkg.cmake b/app/jni/src/libultraship/cmake/automate-vcpkg.cmake deleted file mode 100644 index ee07f6b..0000000 --- a/app/jni/src/libultraship/cmake/automate-vcpkg.cmake +++ /dev/null @@ -1,191 +0,0 @@ -#------------------------------------------------------------------------------------------------------------ -# -# Automate-VCPKG by Andre Taulien -# =============================== -# -# Project Repository: https://github.com/REGoth-project/Automate-VCPKG -# License ..........: MIT, see end of file. -# -# Based on: https://github.com/sutambe/cpptruths/blob/vcpkg_cmake_blog/cpp0x/vcpkg_test/CMakeLists.txt -# -# -# While [Vcpkg](https://github.com/microsoft/vcpkg) on it's own is awesome, it does add -# a little bit of complexity to getting a project to build. Even more if the one trying -# to compile your application is not too fond of the commandline. Additionally, CMake -# commands tend to get rather long with the toolchain path. -# -# To keep things simple for new users who just want to get the project to build, this -# script offers a solution. -# -# Lets assume your main `CMakelists.txt` looks something like this: -# -# cmake_minimum_required (VERSION 3.12.0) -# project (MyProject) -# -# add_executable(MyExecutable main.c) -# -# To integrate Vcpkg into that `CMakelists.txt`, simple put the following lines before the -# call to `project(MyProject)`: -# -# include(cmake/automate-vcpkg.cmake) -# -# vcpkg_bootstrap() -# vcpkg_install_packages(libsquish physfs) -# -# The call to `vcpkg_bootstrap()` will clone the official Vcpkg repository and bootstrap it. -# If it detected an existing environment variable defining a valid `VCPKG_ROOT`, it will -# update the existing installation of Vcpkg. -# -# Arguments to `vcpkg_install_packages()` are the packages you want to install using Vcpkg. -# -# If you want to keep the possibility for users to chose their own copy of Vcpkg, you can -# simply not run the code snippet mentioned above, something like this will work: -# -# option(SKIP_AUTOMATE_VCPKG "When ON, you will need to built the packages -# required by MyProject on your own or supply your own vcpkg toolchain.") -# -# if (NOT SKIP_AUTOMATE_VCPKG) -# include(cmake/automate-vcpkg.cmake) -# -# vcpkg_bootstrap() -# vcpkg_install_packages(libsquish physfs) -# endif() -# -# Then, the user has to supply the packages on their own, be it through Vcpkg or manually -# specifying their locations. -#------------------------------------------------------------------------------------------------------------ - -cmake_minimum_required (VERSION 3.12) - -if(WIN32) - set(VCPKG_FALLBACK_ROOT ${CMAKE_CURRENT_BINARY_DIR}/vcpkg CACHE STRING "vcpkg configuration directory to use if vcpkg was not installed on the system before") -else() - set(VCPKG_FALLBACK_ROOT ${CMAKE_CURRENT_BINARY_DIR}/.vcpkg CACHE STRING "vcpkg configuration directory to use if vcpkg was not installed on the system before") -endif() - -# On Windows, Vcpkg defaults to x86, even on x64 systems. If we're -# doing a 64-bit build, we need to fix that. -if (WIN32) - - # Since the compiler checks haven't run yet, we need to figure - # out the value of CMAKE_SIZEOF_VOID_P ourselfs - - include(CheckTypeSize) - enable_language(C) - check_type_size("void*" SIZEOF_VOID_P BUILTIN_TYPES_ONLY) - - if (SIZEOF_VOID_P EQUAL 8) - message(STATUS "Using Vcpkg triplet 'x64-windows'") - - set(VCPKG_TRIPLET x64-windows) - endif() -endif() - -if(NOT DEFINED VCPKG_ROOT) - if(NOT DEFINED ENV{VCPKG_ROOT}) - set(VCPKG_ROOT ${VCPKG_FALLBACK_ROOT}) - else() - set(VCPKG_ROOT $ENV{VCPKG_ROOT}) - endif() -endif() - -# Installs a new copy of Vcpkg or updates an existing one -macro(vcpkg_bootstrap) - _install_or_update_vcpkg() - - # Find out whether the user supplied their own VCPKG toolchain file - if(NOT DEFINED ${CMAKE_TOOLCHAIN_FILE}) - # We know this wasn't set before so we need point the toolchain file to the newly found VCPKG_ROOT - set(CMAKE_TOOLCHAIN_FILE ${VCPKG_ROOT}/scripts/buildsystems/vcpkg.cmake CACHE STRING "") - - # Just setting vcpkg.cmake as toolchain file does not seem to actually pull in the code - include(${VCPKG_ROOT}/scripts/buildsystems/vcpkg.cmake) - - set(AUTOMATE_VCPKG_USE_SYSTEM_VCPKG OFF) - else() - # VCPKG_ROOT has been defined by the toolchain file already - set(AUTOMATE_VCPKG_USE_SYSTEM_VCPKG ON) - endif() - - message(STATUS "Automate VCPKG status:") - message(STATUS " VCPKG_ROOT.....: ${VCPKG_ROOT}") - message(STATUS " VCPKG_EXEC.....: ${VCPKG_EXEC}") - message(STATUS " VCPKG_BOOTSTRAP: ${VCPKG_BOOTSTRAP}") -endmacro() - -macro(_install_or_update_vcpkg) - if(NOT EXISTS ${VCPKG_ROOT}) - message(STATUS "Cloning vcpkg in ${VCPKG_ROOT}") - execute_process(COMMAND git clone https://github.com/Microsoft/vcpkg.git ${VCPKG_ROOT}) - - # If a reproducible build is desired (and potentially old libraries are # ok), uncomment the - # following line and pin the vcpkg repository to a specific githash. - # execute_process(COMMAND git checkout 745a0aea597771a580d0b0f4886ea1e3a94dbca6 WORKING_DIRECTORY ${VCPKG_ROOT}) - else() - # The following command has no effect if the vcpkg repository is in a detached head state. - message(STATUS "Auto-updating vcpkg in ${VCPKG_ROOT}") - execute_process(COMMAND git pull WORKING_DIRECTORY ${VCPKG_ROOT}) - endif() - - if(NOT EXISTS ${VCPKG_ROOT}/README.md) - message(FATAL_ERROR "***** FATAL ERROR: Could not clone vcpkg *****") - endif() - - if(WIN32) - set(VCPKG_EXEC ${VCPKG_ROOT}/vcpkg.exe) - set(VCPKG_BOOTSTRAP ${VCPKG_ROOT}/bootstrap-vcpkg.bat) - else() - set(VCPKG_EXEC ${VCPKG_ROOT}/vcpkg) - set(VCPKG_BOOTSTRAP ${VCPKG_ROOT}/bootstrap-vcpkg.sh) - endif() - - if(NOT EXISTS ${VCPKG_EXEC}) - message("Bootstrapping vcpkg in ${VCPKG_ROOT}") - execute_process(COMMAND ${VCPKG_BOOTSTRAP} WORKING_DIRECTORY ${VCPKG_ROOT}) - endif() - - if(NOT EXISTS ${VCPKG_EXEC}) - message(FATAL_ERROR "***** FATAL ERROR: Could not bootstrap vcpkg *****") - endif() - -endmacro() - -# Installs the list of packages given as parameters using Vcpkg -macro(vcpkg_install_packages) - - # Need the given list to be space-separated - #string (REPLACE ";" " " PACKAGES_LIST_STR "${ARGN}") - - message(STATUS "Installing/Updating the following vcpkg-packages: ${PACKAGES_LIST_STR}") - - if (VCPKG_TRIPLET) - set(ENV{VCPKG_DEFAULT_TRIPLET} "${VCPKG_TRIPLET}") - endif() - - execute_process( - COMMAND ${VCPKG_EXEC} install ${ARGN} - WORKING_DIRECTORY ${VCPKG_ROOT} - ) -endmacro() - -# MIT License -# -# Copyright (c) 2019 REGoth-project -# -# 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. diff --git a/app/jni/src/libultraship/extern/CMakeLists.txt b/app/jni/src/libultraship/extern/CMakeLists.txt deleted file mode 100644 index 9a4eca3..0000000 --- a/app/jni/src/libultraship/extern/CMakeLists.txt +++ /dev/null @@ -1,142 +0,0 @@ -#find_package(OpenGL QUIET) -find_library(OPENGL_LIBRARY GLESv2) - -if (CMAKE_SYSTEM_NAME MATCHES "Windows") - find_package(SDL2 CONFIG REQUIRED) -else() - #find_package(SDL2 REQUIRED) -endif() - -#=================== DrLibs =================== - -set(DRLIBS_DIR ${CMAKE_CURRENT_SOURCE_DIR}/dr_libs) -add_library(DrLibs INTERFACE) - -target_include_directories(DrLibs INTERFACE ${DRLIBS_DIR}) - -#=================== Storm =================== - -set(STORMLIB_DIR ${CMAKE_CURRENT_SOURCE_DIR}/StormLib) -add_subdirectory(${STORMLIB_DIR}) -if((CMAKE_SYSTEM_NAME MATCHES "Windows") AND ("${CMAKE_CXX_COMPILER_ID}" MATCHES "Clang")) - include(../cmake/HandleCompilerRT.cmake) - find_compiler_rt_library(builtins CLANG_RT_BUILTINS_LIBRARY) - get_filename_component(LIBDIR "${CLANG_RT_BUILTINS_LIBRARY}" DIRECTORY) - if(IS_DIRECTORY "${LIBDIR}") - target_link_libraries(storm ${CLANG_RT_BUILTINS_LIBRARY}) - endif() -endif() -if (CMAKE_SYSTEM_NAME STREQUAL "NintendoSwitch") - target_compile_definitions(storm PRIVATE -D_POSIX_C_SOURCE=200809L) -endif() - -#=================== ImGui =================== - -set(IMGUI_DIR ${CMAKE_CURRENT_SOURCE_DIR}/ImGui) -add_library(ImGui STATIC) -set_property(TARGET ImGui PROPERTY CXX_STANDARD 20) - -target_sources(ImGui - PRIVATE - ${IMGUI_DIR}/imgui_demo.cpp - ${IMGUI_DIR}/imgui_draw.cpp - ${IMGUI_DIR}/imgui_tables.cpp - ${IMGUI_DIR}/imgui_widgets.cpp - ${IMGUI_DIR}/imgui.cpp -) - -if (CMAKE_SYSTEM_NAME STREQUAL "NintendoSwitch") - target_include_directories(ImGui PRIVATE ${DEVKITPRO}/portlibs/switch/include/) -endif() - -if (NOT CMAKE_SYSTEM_NAME STREQUAL "CafeOS") - target_sources(ImGui - PRIVATE - ${IMGUI_DIR}/backends/imgui_impl_opengl3.cpp - ${IMGUI_DIR}/backends/imgui_impl_sdl2.cpp - ) -endif() - -if (CMAKE_SYSTEM_NAME STREQUAL "Windows") - target_sources(ImGui - PRIVATE - ${IMGUI_DIR}/backends/imgui_impl_dx11.cpp - ${IMGUI_DIR}/backends/imgui_impl_win32.cpp - ) -elseif (CMAKE_SYSTEM_NAME STREQUAL "Darwin") - target_sources(ImGui - PRIVATE - ${IMGUI_DIR}/backends/imgui_impl_metal.mm - ) -elseif (CMAKE_SYSTEM_NAME STREQUAL "CafeOS") - target_sources(ImGui - PRIVATE - ${IMGUI_DIR}/backends/wiiu/imgui_impl_wiiu.cpp - ${IMGUI_DIR}/backends/wiiu/imgui_impl_gx2.cpp - ) -endif() - -target_include_directories(ImGui PUBLIC ${IMGUI_DIR} ${IMGUI_DIR}/backends PRIVATE ${SDL2_INCLUDE_DIRS}) - -if (CMAKE_SYSTEM_NAME STREQUAL "Darwin") - target_include_directories(ImGui PRIVATE ${CMAKE_CURRENT_SOURCE_DIR}/metal-cpp) - target_compile_definitions(ImGui PUBLIC IMGUI_IMPL_METAL_CPP) -endif() - -if (CMAKE_SYSTEM_NAME STREQUAL "Windows") - target_link_libraries(ImGui PUBLIC SDL2::SDL2 SDL2::SDL2main) -elseif (CMAKE_SYSTEM_NAME STREQUAL "CafeOS") - target_link_libraries(ImGui PUBLIC SDL2::SDL2-static) -else() - target_link_libraries(ImGui PUBLIC SDL2::SDL2) -endif() - -if (CMAKE_SYSTEM_NAME STREQUAL "Windows") - find_package(GLEW REQUIRED) - target_link_libraries(ImGui PUBLIC opengl32 GLEW::GLEW) -elseif (CMAKE_SYSTEM_NAME STREQUAL "Darwin") - find_package(GLEW REQUIRED) - target_link_libraries(ImGui PUBLIC ${OPENGL_opengl_LIBRARY} GLEW::GLEW) - set_target_properties(ImGui PROPERTIES - XCODE_ATTRIBUTE_CLANG_ENABLE_OBJC_ARC YES - ) -elseif (CMAKE_SYSTEM_NAME STREQUAL "Linux") - find_package(GLEW REQUIRED) - target_link_libraries(ImGui PUBLIC ${OPENGL_glx_LIBRARY} ${OPENGL_opengl_LIBRARY} GLEW::GLEW) -endif() - -#=================== tinyxml2 =================== - -set(TINYXML2_DIR ${CMAKE_CURRENT_SOURCE_DIR}/tinyxml2) -add_library(tinyxml2 STATIC) - -target_sources(tinyxml2 PRIVATE ${TINYXML2_DIR}/tinyxml2.cpp) -target_include_directories(tinyxml2 PUBLIC ${TINYXML2_DIR}) - -#=================== ZAPDUtils =================== - -set(ZAPDUTILS_DIR ${CMAKE_CURRENT_SOURCE_DIR}/ZAPDUtils) -add_subdirectory(${ZAPDUTILS_DIR}) - -#=================== nlohmann-json =================== - -set(JSON_BuildTests OFF CACHE INTERNAL "") - -set(NLOHMANN_JSON_DIR ${CMAKE_CURRENT_SOURCE_DIR}/nlohmann-json) -add_subdirectory(${NLOHMANN_JSON_DIR}) - -#=================== StrHash64 =================== - -set(STRHASH64_DIR ${CMAKE_CURRENT_SOURCE_DIR}/StrHash64) -add_library(StrHash64 STATIC) - -target_sources(StrHash64 PRIVATE ${STRHASH64_DIR}/StrHash64.cpp) - -target_include_directories(StrHash64 PUBLIC ${STRHASH64_DIR}) - -#=================== thread-pool =================== - -set(THREADPOOL_DIR ${CMAKE_CURRENT_SOURCE_DIR}/thread-pool) -add_library(ThreadPool INTERFACE) - -target_include_directories(ThreadPool INTERFACE ${THREADPOOL_DIR}) diff --git a/app/jni/src/libultraship/extern/ImGui/.editorconfig b/app/jni/src/libultraship/extern/ImGui/.editorconfig deleted file mode 100644 index 5adfefa..0000000 --- a/app/jni/src/libultraship/extern/ImGui/.editorconfig +++ /dev/null @@ -1,28 +0,0 @@ -# See http://editorconfig.org to read about the EditorConfig format. -# - In theory automatically supported by VS2017+ and most common IDE or text editors. -# - In practice VS2019-VS2022 stills don't trim trailing whitespaces correctly :( -# - Suggest installing this to trim whitespaces: -# GitHub https://github.com/madskristensen/TrailingWhitespace -# VS2019 https://marketplace.visualstudio.com/items?itemName=MadsKristensen.TrailingWhitespaceVisualizer -# VS2022 https://marketplace.visualstudio.com/items?itemName=MadsKristensen.TrailingWhitespace64 -# (in spite of its name doesn't only visualize but also trims) -# - Alternative for older VS2010 to VS2015: https://marketplace.visualstudio.com/items?itemName=EditorConfigTeam.EditorConfig - -# top-most EditorConfig file -root = true - -# Default settings: -# Use 4 spaces as indentation -[*] -indent_style = space -indent_size = 4 -insert_final_newline = true -trim_trailing_whitespace = true - -[imstb_*] -indent_size = 3 -trim_trailing_whitespace = false - -[Makefile] -indent_style = tab -indent_size = 4 diff --git a/app/jni/src/libultraship/extern/ImGui/.gitattributes b/app/jni/src/libultraship/extern/ImGui/.gitattributes deleted file mode 100644 index d48470e..0000000 --- a/app/jni/src/libultraship/extern/ImGui/.gitattributes +++ /dev/null @@ -1,30 +0,0 @@ -* text=auto - -*.c text -*.cpp text -*.h text -*.m text -*.mm text -*.md text -*.txt text -*.html text -*.bat text -*.frag text -*.vert text -*.mkb text -*.icf text - -*.sln text eol=crlf -*.vcxproj text eol=crlf -*.vcxproj.filters text eol=crlf -*.natvis text eol=crlf - -Makefile text eol=lf -*.sh text eol=lf -*.pbxproj text eol=lf -*.storyboard text eol=lf -*.plist text eol=lf - -*.png binary -*.ttf binary -*.lib binary diff --git a/app/jni/src/libultraship/extern/ImGui/.github/FUNDING.yml b/app/jni/src/libultraship/extern/ImGui/.github/FUNDING.yml deleted file mode 100644 index 2aa08b4..0000000 --- a/app/jni/src/libultraship/extern/ImGui/.github/FUNDING.yml +++ /dev/null @@ -1 +0,0 @@ -custom: ['https://github.com/ocornut/imgui/wiki/Sponsors'] diff --git a/app/jni/src/libultraship/extern/ImGui/.github/issue_template.md b/app/jni/src/libultraship/extern/ImGui/.github/issue_template.md deleted file mode 100644 index 0172e09..0000000 --- a/app/jni/src/libultraship/extern/ImGui/.github/issue_template.md +++ /dev/null @@ -1,46 +0,0 @@ -(Click "Preview" above ^ to turn URL into clickable links) - -1. FOR FIRST-TIME USERS PROBLEMS COMPILING/LINKING/RUNNING or LOADING FONTS, please use [GitHub Discussions](https://github.com/ocornut/imgui/discussions). EVERYTHING ELSE CAN BE POSTED HERE! - -2. PLEASE CAREFULLY READ: [FAQ](https://github.com/ocornut/imgui/blob/master/docs/FAQ.md) - -3. PLEASE CAREFULLY READ: [Contributing Guidelines](https://github.com/ocornut/imgui/blob/master/docs/CONTRIBUTING.md) - -4. PLEASE MAKE SURE that you have: read the FAQ; explored the contents of `ShowDemoWindow()` including the Examples menu; searched among Issues; used your IDE to search for keywords in all sources and text files; and read the links above. - -5. Be mindful that messages are being sent to the e-mail box of "Watching" users. Try to proof-read your messages before sending them. Edits are not seen by those users. - -6. Delete points 1-6 and PLEASE FILL THE TEMPLATE BELOW before submitting your issue. - -Thank you! - ----- - -_(you may also go to Demo>About Window, and click "Config/Build Information" to obtain a bunch of detailed information that you can paste here)_ - -**Version/Branch of Dear ImGui:** - -Version: XXX -Branch: XXX _(master/viewport/docking/etc.)_ - -**Back-end/Renderer/Compiler/OS** - -Back-ends: imgui_impl_XXX.cpp + imgui_impl_XXX.cpp _(or specify if using a custom engine/back-end)_ -Compiler: XXX _(if the question is related to building or platform specific features)_ -Operating System: XXX - -**My Issue/Question:** - -XXX _(please provide as much context as possible)_ - -**Screenshots/Video** - -XXX _(you can drag files here)_ - -**Standalone, minimal, complete and verifiable example:** _(see https://github.com/ocornut/imgui/issues/2261)_ -``` -// Here's some code anyone can copy and paste to reproduce your issue -ImGui::Begin("Example Bug"); -MoreCodeToExplainMyIssue(); -ImGui::End(); -``` diff --git a/app/jni/src/libultraship/extern/ImGui/.github/pull_request_template.md b/app/jni/src/libultraship/extern/ImGui/.github/pull_request_template.md deleted file mode 100644 index 638545b..0000000 --- a/app/jni/src/libultraship/extern/ImGui/.github/pull_request_template.md +++ /dev/null @@ -1,6 +0,0 @@ -(Click "Preview" to turn any http URL into a clickable link) - -1. PLEASE CAREFULLY READ: [Contributing Guidelines](https://github.com/ocornut/imgui/blob/master/docs/CONTRIBUTING.md) - -2. Clear this template before submitting your PR. - diff --git a/app/jni/src/libultraship/extern/ImGui/.github/workflows/build.yml b/app/jni/src/libultraship/extern/ImGui/.github/workflows/build.yml deleted file mode 100644 index 45688c4..0000000 --- a/app/jni/src/libultraship/extern/ImGui/.github/workflows/build.yml +++ /dev/null @@ -1,507 +0,0 @@ -name: build - -on: - push: - pull_request: - workflow_run: - # Use a workflow as a trigger of scheduled builds. Forked repositories can disable scheduled builds by disabling - # "scheduled" workflow, while maintaining ability to perform local CI builds. - workflows: - - scheduled - branches: - - master - - docking - types: - - requested - -jobs: - Windows: - runs-on: windows-2019 - env: - VS_PATH: C:\Program Files (x86)\Microsoft Visual Studio\2019\Enterprise\ - MSBUILD_PATH: C:\Program Files (x86)\Microsoft Visual Studio\2019\Enterprise\MSBuild\Current\Bin\ - steps: - - uses: actions/checkout@v3 - - - name: Install Dependencies - shell: powershell - run: | - Invoke-WebRequest -Uri "https://www.libsdl.org/release/SDL2-devel-2.26.3-VC.zip" -OutFile "SDL2-devel-2.26.3-VC.zip" - Expand-Archive -Path SDL2-devel-2.26.3-VC.zip - echo "SDL2_DIR=$(pwd)\SDL2-devel-2.26.3-VC\SDL2-2.26.3\" >>${env:GITHUB_ENV} - - Invoke-WebRequest -Uri "https://github.com/ocornut/imgui/files/3789205/vulkan-sdk-1.1.121.2.zip" -OutFile vulkan-sdk-1.1.121.2.zip - Expand-Archive -Path vulkan-sdk-1.1.121.2.zip - echo "VULKAN_SDK=$(pwd)\vulkan-sdk-1.1.121.2\" >>${env:GITHUB_ENV} - - - name: Fix Projects - shell: powershell - run: | - # CI workers do not supporter older Visual Studio versions. Fix projects to target newer available version. - gci -recurse -filter "*.vcxproj" | ForEach-Object { - (Get-Content $_.FullName) -Replace "v\d{3}","v142" | Set-Content -Path $_.FullName - (Get-Content $_.FullName) -Replace "[\d\.]+","10.0.18362.0" | Set-Content -Path $_.FullName - } - - # Not using matrix here because it would inflate job count too much. Check out and setup is done for every job and that makes build times way too long. - - name: Build example_null (extra warnings, mingw 64-bit) - run: mingw32-make -C examples/example_null WITH_EXTRA_WARNINGS=1 - - - name: Build example_null (mingw 64-bit, as DLL) - shell: bash - run: | - echo '#ifdef _EXPORT' > example_single_file.cpp - echo '# define IMGUI_API __declspec(dllexport)' >> example_single_file.cpp - echo '#else' >> example_single_file.cpp - echo '# define IMGUI_API __declspec(dllimport)' >> example_single_file.cpp - echo '#endif' >> example_single_file.cpp - echo '#define IMGUI_IMPLEMENTATION' >> example_single_file.cpp - echo '#include "misc/single_file/imgui_single_file.h"' >> example_single_file.cpp - g++ -I. -Wall -Wformat -D_EXPORT -shared -o libimgui.dll -Wl,--out-implib,libimgui.a example_single_file.cpp -limm32 - g++ -I. -Wall -Wformat -o example_null.exe examples/example_null/main.cpp -L. -limgui - rm -f example_null.exe libimgui.* example_single_file.* - - - name: Build example_null (extra warnings, msvc 64-bit) - shell: cmd - run: | - cd examples\example_null - call "%VS_PATH%\VC\Auxiliary\Build\vcvars64.bat" - .\build_win32.bat /W4 - - - name: Build example_null (single file build) - shell: bash - run: | - cat > example_single_file.cpp <<'EOF' - - #define IMGUI_IMPLEMENTATION - #include "misc/single_file/imgui_single_file.h" - #include "examples/example_null/main.cpp" - - EOF - g++ -I. -Wall -Wformat -o example_single_file.exe example_single_file.cpp -limm32 - - - name: Build example_null (with IMGUI_DISABLE_WIN32_FUNCTIONS) - shell: bash - run: | - cat > example_single_file.cpp <<'EOF' - - #define IMGUI_DISABLE_WIN32_FUNCTIONS - #define IMGUI_IMPLEMENTATION - #include "misc/single_file/imgui_single_file.h" - #include "examples/example_null/main.cpp" - - EOF - g++ -I. -Wall -Wformat -o example_single_file.exe example_single_file.cpp -limm32 - - - name: Build example_null (as DLL) - shell: cmd - run: | - call "%VS_PATH%\VC\Auxiliary\Build\vcvars64.bat" - - echo #ifdef _EXPORT > example_single_file.cpp - echo # define IMGUI_API __declspec(dllexport) >> example_single_file.cpp - echo #else >> example_single_file.cpp - echo # define IMGUI_API __declspec(dllimport) >> example_single_file.cpp - echo #endif >> example_single_file.cpp - echo #define IMGUI_IMPLEMENTATION >> example_single_file.cpp - echo #include "misc/single_file/imgui_single_file.h" >> example_single_file.cpp - - cl.exe /D_USRDLL /D_WINDLL /D_EXPORT /I. example_single_file.cpp /LD /FeImGui.dll /link - cl.exe /I. ImGui.lib /Feexample_null.exe examples/example_null/main.cpp - - - name: Build Win32 example_glfw_opengl2 - shell: cmd - run: '"%MSBUILD_PATH%\MSBuild.exe" examples/example_glfw_opengl2/example_glfw_opengl2.vcxproj /p:Platform=Win32 /p:Configuration=Release' - - - name: Build Win32 example_glfw_opengl3 - shell: cmd - run: '"%MSBUILD_PATH%\MSBuild.exe" examples/example_glfw_opengl3/example_glfw_opengl3.vcxproj /p:Platform=Win32 /p:Configuration=Release' - if: github.event_name == 'workflow_run' - - - name: Build Win32 example_glfw_vulkan - shell: cmd - run: '"%MSBUILD_PATH%\MSBuild.exe" examples/example_glfw_vulkan/example_glfw_vulkan.vcxproj /p:Platform=Win32 /p:Configuration=Release' - if: github.event_name == 'workflow_run' - - - name: Build Win32 example_sdl2_vulkan - shell: cmd - run: '"%MSBUILD_PATH%\MSBuild.exe" examples/example_sdl2_vulkan/example_sdl2_vulkan.vcxproj /p:Platform=Win32 /p:Configuration=Release' - if: github.event_name == 'workflow_run' - - - name: Build Win32 example_sdl2_opengl2 - shell: cmd - run: '"%MSBUILD_PATH%\MSBuild.exe" examples/example_sdl2_opengl2/example_sdl2_opengl2.vcxproj /p:Platform=Win32 /p:Configuration=Release' - if: github.event_name == 'workflow_run' - - - name: Build Win32 example_sdl2_opengl3 - shell: cmd - run: '"%MSBUILD_PATH%\MSBuild.exe" examples/example_sdl2_opengl3/example_sdl2_opengl3.vcxproj /p:Platform=Win32 /p:Configuration=Release' - - - name: Build Win32 example_sdl2_directx11 - shell: cmd - run: '"%MSBUILD_PATH%\MSBuild.exe" examples/example_sdl2_directx11/example_sdl2_directx11.vcxproj /p:Platform=Win32 /p:Configuration=Release' - if: github.event_name == 'workflow_run' - - - name: Build Win32 example_win32_directx9 - shell: cmd - run: '"%MSBUILD_PATH%\MSBuild.exe" examples/example_win32_directx9/example_win32_directx9.vcxproj /p:Platform=Win32 /p:Configuration=Release' - - - name: Build Win32 example_win32_directx10 - shell: cmd - run: '"%MSBUILD_PATH%\MSBuild.exe" examples/example_win32_directx10/example_win32_directx10.vcxproj /p:Platform=Win32 /p:Configuration=Release' - - - name: Build Win32 example_win32_directx11 - shell: cmd - run: '"%MSBUILD_PATH%\MSBuild.exe" examples/example_win32_directx11/example_win32_directx11.vcxproj /p:Platform=Win32 /p:Configuration=Release' - if: github.event_name == 'workflow_run' - - - name: Build x64 example_glfw_opengl2 - shell: cmd - run: '"%MSBUILD_PATH%\MSBuild.exe" examples/example_glfw_opengl2/example_glfw_opengl2.vcxproj /p:Platform=x64 /p:Configuration=Release' - if: github.event_name == 'workflow_run' - - - name: Build x64 example_glfw_opengl3 - shell: cmd - run: '"%MSBUILD_PATH%\MSBuild.exe" examples/example_glfw_opengl3/example_glfw_opengl3.vcxproj /p:Platform=x64 /p:Configuration=Release' - - - name: Build x64 example_glfw_vulkan - shell: cmd - run: '"%MSBUILD_PATH%\MSBuild.exe" examples/example_glfw_vulkan/example_glfw_vulkan.vcxproj /p:Platform=x64 /p:Configuration=Release' - - - name: Build x64 example_sdl2_vulkan - shell: cmd - run: '"%MSBUILD_PATH%\MSBuild.exe" examples/example_sdl2_vulkan/example_sdl2_vulkan.vcxproj /p:Platform=x64 /p:Configuration=Release' - if: github.event_name == 'workflow_run' - - - name: Build x64 example_sdl2_opengl2 - shell: cmd - run: '"%MSBUILD_PATH%\MSBuild.exe" examples/example_sdl2_opengl2/example_sdl2_opengl2.vcxproj /p:Platform=x64 /p:Configuration=Release' - if: github.event_name == 'workflow_run' - - - name: Build x64 example_sdl2_opengl3 - shell: cmd - run: '"%MSBUILD_PATH%\MSBuild.exe" examples/example_sdl2_opengl3/example_sdl2_opengl3.vcxproj /p:Platform=x64 /p:Configuration=Release' - if: github.event_name == 'workflow_run' - - - name: Build x64 example_sdl2_directx11 - shell: cmd - run: '"%MSBUILD_PATH%\MSBuild.exe" examples/example_sdl2_directx11/example_sdl2_directx11.vcxproj /p:Platform=x64 /p:Configuration=Release' - - - name: Build x64 example_win32_directx9 - shell: cmd - run: '"%MSBUILD_PATH%\MSBuild.exe" examples/example_win32_directx9/example_win32_directx9.vcxproj /p:Platform=x64 /p:Configuration=Release' - if: github.event_name == 'workflow_run' - - - name: Build x64 example_win32_directx10 - shell: cmd - run: '"%MSBUILD_PATH%\MSBuild.exe" examples/example_win32_directx10/example_win32_directx10.vcxproj /p:Platform=x64 /p:Configuration=Release' - if: github.event_name == 'workflow_run' - - - name: Build x64 example_win32_directx11 - shell: cmd - run: '"%MSBUILD_PATH%\MSBuild.exe" examples/example_win32_directx11/example_win32_directx11.vcxproj /p:Platform=x64 /p:Configuration=Release' - if: github.event_name == 'workflow_run' - - - name: Build x64 example_win32_directx12 - shell: cmd - run: '"%MSBUILD_PATH%\MSBuild.exe" examples/example_win32_directx12/example_win32_directx12.vcxproj /p:Platform=x64 /p:Configuration=Release' - - Linux: - runs-on: ubuntu-22.04 - steps: - - uses: actions/checkout@v3 - - - name: Install Dependencies - run: | - sudo apt-get update - sudo apt-get install -y libglfw3-dev libsdl2-dev gcc-multilib g++-multilib libfreetype6-dev libvulkan-dev - - - name: Build example_null (extra warnings, gcc 32-bit) - run: | - make -C examples/example_null clean - CXXFLAGS="$CXXFLAGS -m32 -Werror" make -C examples/example_null WITH_EXTRA_WARNINGS=1 - - - name: Build example_null (extra warnings, gcc 64-bit) - run: | - make -C examples/example_null clean - CXXFLAGS="$CXXFLAGS -m64 -Werror" make -C examples/example_null WITH_EXTRA_WARNINGS=1 - - - name: Build example_null (extra warnings, clang 32-bit) - run: | - make -C examples/example_null clean - CXXFLAGS="$CXXFLAGS -m32 -Werror" CXX=clang++ make -C examples/example_null WITH_EXTRA_WARNINGS=1 - - - name: Build example_null (extra warnings, clang 64-bit) - run: | - make -C examples/example_null clean - CXXFLAGS="$CXXFLAGS -m64 -Werror" CXX=clang++ make -C examples/example_null WITH_EXTRA_WARNINGS=1 - - - name: Build example_null (extra warnings, empty IM_ASSERT) - run: | - cat > example_single_file.cpp <<'EOF' - - #define IM_ASSERT(x) - #define IMGUI_IMPLEMENTATION - #include "misc/single_file/imgui_single_file.h" - #include "examples/example_null/main.cpp" - - EOF - g++ -I. -std=c++11 -Wall -Wformat -Wextra -Werror -Wno-zero-as-null-pointer-constant -Wno-double-promotion -Wno-variadic-macros -Wno-empty-body -o example_single_file example_single_file.cpp - - - name: Build example_null (freetype) - run: | - make -C examples/example_null clean - make -C examples/example_null WITH_FREETYPE=1 - - - name: Build example_null (single file build) - run: | - cat > example_single_file.cpp <<'EOF' - - #define IMGUI_IMPLEMENTATION - #include "misc/single_file/imgui_single_file.h" - #include "examples/example_null/main.cpp" - - EOF - g++ -I. -std=c++11 -Wall -Wformat -o example_single_file example_single_file.cpp - - - name: Build example_null (with ImWchar32) - run: | - cat > example_single_file.cpp <<'EOF' - - #define IMGUI_USE_WCHAR32 - #define IMGUI_IMPLEMENTATION - #include "misc/single_file/imgui_single_file.h" - #include "examples/example_null/main.cpp" - - EOF - g++ -I. -std=c++11 -Wall -Wformat -o example_single_file example_single_file.cpp - - - name: Build example_null (with large ImDrawIdx + pointer ImTextureID) - run: | - cat > example_single_file.cpp <<'EOF' - - #define ImTextureID void* - #define ImDrawIdx unsigned int - #define IMGUI_IMPLEMENTATION - #include "misc/single_file/imgui_single_file.h" - #include "examples/example_null/main.cpp" - - EOF - g++ -I. -std=c++11 -Wall -Wformat -o example_single_file example_single_file.cpp - - - name: Build example_null (with IMGUI_DISABLE_OBSOLETE_FUNCTIONS) - run: | - cat > example_single_file.cpp <<'EOF' - - #define IMGUI_DISABLE_OBSOLETE_FUNCTIONS - #define IMGUI_IMPLEMENTATION - #include "misc/single_file/imgui_single_file.h" - #include "examples/example_null/main.cpp" - - EOF - g++ -I. -std=c++11 -Wall -Wformat -o example_single_file example_single_file.cpp - - - name: Build example_null (with IMGUI_DISABLE_OBSOLETE_KEYIO) - run: | - cat > example_single_file.cpp <<'EOF' - - #define IMGUI_DISABLE_OBSOLETE_KEYIO - #define IMGUI_IMPLEMENTATION - #include "misc/single_file/imgui_single_file.h" - #include "examples/example_null/main.cpp" - - EOF - g++ -I. -std=c++11 -Wall -Wformat -o example_single_file example_single_file.cpp - - - name: Build example_null (with IMGUI_DISABLE_DEMO_WINDOWS and IMGUI_DISABLE_DEBUG_TOOLS) - run: | - cat > example_single_file.cpp <<'EOF' - - #define IMGUI_DISABLE_DEMO_WINDOWS - #define IMGUI_DISABLE_DEBUG_TOOLS - #define IMGUI_IMPLEMENTATION - #include "misc/single_file/imgui_single_file.h" - #include "examples/example_null/main.cpp" - - EOF - g++ -I. -std=c++11 -Wall -Wformat -o example_single_file example_single_file.cpp - - - name: Build example_null (with IMGUI_DISABLE_FILE_FUNCTIONS) - run: | - cat > example_single_file.cpp <<'EOF' - - #define IMGUI_DISABLE_FILE_FUNCTIONS - #define IMGUI_IMPLEMENTATION - #include "misc/single_file/imgui_single_file.h" - #include "examples/example_null/main.cpp" - - EOF - g++ -I. -std=c++11 -Wall -Wformat -o example_single_file example_single_file.cpp - - - name: Build example_null (with IMGUI_USE_BGRA_PACKED_COLOR) - run: | - cat > example_single_file.cpp <<'EOF' - - #define IMGUI_USE_BGRA_PACKED_COLOR - #define IMGUI_IMPLEMENTATION - #include "misc/single_file/imgui_single_file.h" - #include "examples/example_null/main.cpp" - - EOF - g++ -I. -std=c++11 -Wall -Wformat -o example_single_file example_single_file.cpp - - - name: Build example_null (with IM_VEC2_CLASS_EXTRA and IM_VEC4_CLASS_EXTRA) - run: | - cat > example_single_file.cpp <<'EOF' - - struct MyVec2 { float x; float y; MyVec2(float x, float y) : x(x), y(y) { } }; - struct MyVec4 { float x; float y; float z; float w; - MyVec4(float x, float y, float z, float w) : x(x), y(y), z(z), w(w) { } }; - #define IM_VEC2_CLASS_EXTRA \ - ImVec2(const MyVec2& f) { x = f.x; y = f.y; } \ - operator MyVec2() const { return MyVec2(x, y); } - #define IM_VEC4_CLASS_EXTRA \ - ImVec4(const MyVec4& f) { x = f.x; y = f.y; z = f.z; w = f.w; } \ - operator MyVec4() const { return MyVec4(x, y, z, w); } - #define IMGUI_IMPLEMENTATION - #include "misc/single_file/imgui_single_file.h" - #include "examples/example_null/main.cpp" - - EOF - g++ -I. -std=c++11 -Wall -Wformat -o example_single_file example_single_file.cpp - - - name: Build example_null (without c++ runtime, Clang) - run: | - cat > example_single_file.cpp <<'EOF' - - #define IMGUI_IMPLEMENTATION - #define IMGUI_DISABLE_DEMO_WINDOWS - #include "misc/single_file/imgui_single_file.h" - #include "examples/example_null/main.cpp" - - EOF - clang++ -I. -std=c++11 -Wall -Wformat -nodefaultlibs -fno-rtti -fno-exceptions -fno-threadsafe-statics -lc -lm -o example_single_file example_single_file.cpp - - - name: Build example_glfw_opengl2 - run: make -C examples/example_glfw_opengl2 - - - name: Build example_glfw_opengl3 - run: make -C examples/example_glfw_opengl3 - if: github.event_name == 'workflow_run' - - - name: Build example_sdl2_opengl2 - run: make -C examples/example_sdl2_opengl2 - if: github.event_name == 'workflow_run' - - - name: Build example_sdl2_opengl3 - run: make -C examples/example_sdl2_opengl3 - - - name: Build with IMGUI_IMPL_VULKAN_NO_PROTOTYPES - run: g++ -c -I. -std=c++11 -DIMGUI_IMPL_VULKAN_NO_PROTOTYPES=1 backends/imgui_impl_vulkan.cpp - - MacOS: - runs-on: macos-latest - steps: - - uses: actions/checkout@v3 - - - name: Install Dependencies - run: | - brew install glfw3 sdl2 - - - name: Build example_null (extra warnings, clang 64-bit) - run: make -C examples/example_null WITH_EXTRA_WARNINGS=1 - - - name: Build example_null (single file build) - run: | - cat > example_single_file.cpp <<'EOF' - - #define IMGUI_IMPLEMENTATION - #include "misc/single_file/imgui_single_file.h" - #include "examples/example_null/main.cpp" - - EOF - clang++ -I. -std=c++11 -Wall -Wformat -o example_single_file example_single_file.cpp - - - name: Build example_null (without c++ runtime) - run: | - cat > example_single_file.cpp <<'EOF' - - #define IMGUI_IMPLEMENTATION - #include "misc/single_file/imgui_single_file.h" - #include "examples/example_null/main.cpp" - - EOF - clang++ -I. -std=c++11 -Wall -Wformat -nodefaultlibs -fno-rtti -fno-exceptions -fno-threadsafe-statics -lc -lm -o example_single_file example_single_file.cpp - - - name: Build example_glfw_opengl2 - run: make -C examples/example_glfw_opengl2 - - - name: Build example_glfw_opengl3 - run: make -C examples/example_glfw_opengl3 - if: github.event_name == 'workflow_run' - - - name: Build example_glfw_metal - run: make -C examples/example_glfw_metal - - - name: Build example_sdl2_metal - run: make -C examples/example_sdl2_metal - - - name: Build example_sdl2_opengl2 - run: make -C examples/example_sdl2_opengl2 - if: github.event_name == 'workflow_run' - - - name: Build example_sdl2_opengl3 - run: make -C examples/example_sdl2_opengl3 - - - name: Build example_apple_metal - run: xcodebuild -project examples/example_apple_metal/example_apple_metal.xcodeproj -target example_apple_metal_macos - - - name: Build example_apple_opengl2 - run: xcodebuild -project examples/example_apple_opengl2/example_apple_opengl2.xcodeproj -target example_osx_opengl2 - - iOS: - runs-on: macos-latest - steps: - - uses: actions/checkout@v3 - - - name: Build example_apple_metal - run: | - # Code signing is required, but we disable it because it is irrelevant for CI builds. - xcodebuild -project examples/example_apple_metal/example_apple_metal.xcodeproj -target example_apple_metal_ios CODE_SIGN_IDENTITY="" CODE_SIGNING_REQUIRED=NO CODE_SIGNING_ALLOWED=NO - - Emscripten: - runs-on: ubuntu-22.04 - steps: - - uses: actions/checkout@v3 - - - name: Install Dependencies - run: | - wget -q https://github.com/emscripten-core/emsdk/archive/master.tar.gz - tar -xvf master.tar.gz - emsdk-master/emsdk update - emsdk-master/emsdk install latest - emsdk-master/emsdk activate latest - - - name: Build example_sdl2_opengl3 with Emscripten - run: | - pushd emsdk-master - source ./emsdk_env.sh - popd - make -C examples/example_sdl2_opengl3 -f Makefile.emscripten - - - name: Build example_emscripten_wgpu - run: | - pushd emsdk-master - source ./emsdk_env.sh - popd - make -C examples/example_emscripten_wgpu - - Android: - runs-on: ubuntu-22.04 - steps: - - uses: actions/checkout@v3 - - - name: Build example_android_opengl3 - run: | - cd examples/example_android_opengl3/android - gradle assembleDebug --stacktrace diff --git a/app/jni/src/libultraship/extern/ImGui/.github/workflows/scheduled.yml b/app/jni/src/libultraship/extern/ImGui/.github/workflows/scheduled.yml deleted file mode 100644 index 2a08578..0000000 --- a/app/jni/src/libultraship/extern/ImGui/.github/workflows/scheduled.yml +++ /dev/null @@ -1,15 +0,0 @@ -# -# This is a dummy workflow used to trigger scheduled builds. Forked repositories most likely should disable this -# workflow to avoid daily builds of inactive repositories. -# -name: scheduled - -on: - schedule: - - cron: '0 9 * * *' - -jobs: - scheduled: - runs-on: ubuntu-latest - steps: - - run: exit 0 diff --git a/app/jni/src/libultraship/extern/ImGui/.github/workflows/static-analysis.yml b/app/jni/src/libultraship/extern/ImGui/.github/workflows/static-analysis.yml deleted file mode 100644 index caa9b3a..0000000 --- a/app/jni/src/libultraship/extern/ImGui/.github/workflows/static-analysis.yml +++ /dev/null @@ -1,46 +0,0 @@ -name: static-analysis - -on: - workflow_run: - # Perform static analysis together with build workflow. Build triggers of "build" workflow do not need to be repeated here. - workflows: - - build - types: - - requested - -jobs: - PVS-Studio: - runs-on: ubuntu-22.04 - steps: - - uses: actions/checkout@v3 - with: - fetch-depth: 1 - - - name: Install Dependencies - env: - # The Secret variable setup in GitHub must be in format: "name_or_email key", on a single line - PVS_STUDIO_LICENSE: ${{ secrets.PVS_STUDIO_LICENSE }} - run: | - if [[ "$PVS_STUDIO_LICENSE" != "" ]]; - then - wget -q https://files.viva64.com/etc/pubkey.txt - sudo apt-key add pubkey.txt - sudo wget -O /etc/apt/sources.list.d/viva64.list https://files.viva64.com/etc/viva64.list - sudo apt-get update - sudo apt-get install -y pvs-studio - pvs-studio-analyzer credentials -o pvs-studio.lic $PVS_STUDIO_LICENSE - fi - - - name: PVS-Studio static analysis - run: | - if [[ ! -f pvs-studio.lic ]]; - then - echo "PVS Studio license is missing. No analysis will be performed." - echo "If you have a PVS Studio license please create a project secret named PVS_STUDIO_LICENSE with your license." - echo "You may use a free license. More information at https://www.viva64.com/en/b/0457/" - exit 0 - fi - cd examples/example_null - pvs-studio-analyzer trace -- make WITH_EXTRA_WARNINGS=1 - pvs-studio-analyzer analyze -e ../../imstb_rectpack.h -e ../../imstb_textedit.h -e ../../imstb_truetype.h -l ../../pvs-studio.lic -o pvs-studio.log - plog-converter -a 'GA:1,2;OP:1' -d V1071 -t errorfile -w pvs-studio.log diff --git a/app/jni/src/libultraship/extern/ImGui/.gitignore b/app/jni/src/libultraship/extern/ImGui/.gitignore deleted file mode 100644 index 211d21d..0000000 --- a/app/jni/src/libultraship/extern/ImGui/.gitignore +++ /dev/null @@ -1,59 +0,0 @@ -## OSX artifacts -.DS_Store - -## Dear ImGui artifacts -imgui.ini - -## General build artifacts -*.o -*.obj -*.exe -examples/*/Debug/* -examples/*/Release/* -examples/*/x64/* - -## Visual Studio artifacts -.vs -ipch -*.opensdf -*.log -*.pdb -*.ilk -*.user -*.sdf -*.suo -*.VC.db -*.VC.VC.opendb - -## Getting files created in JSON/Schemas/Catalog/ from a VS2022 update -JSON/ - -## Commonly used CMake directories -build*/ - -## Xcode artifacts -project.xcworkspace -xcuserdata - -## Emscripten artifacts -examples/*.o.tmp -examples/*.out.js -examples/*.out.wasm -examples/example_glfw_opengl3/web/* -examples/example_sdl2_opengl3/web/* -examples/example_emscripten_wgpu/web/* - -## JetBrains IDE artifacts -.idea -cmake-build-* - -## Unix executables from our example Makefiles -examples/example_glfw_metal/example_glfw_metal -examples/example_glfw_opengl2/example_glfw_opengl2 -examples/example_glfw_opengl3/example_glfw_opengl3 -examples/example_glut_opengl2/example_glut_opengl2 -examples/example_null/example_null -examples/example_sdl2_metal/example_sdl2_metal -examples/example_sdl2_opengl2/example_sdl2_opengl2 -examples/example_sdl2_opengl3/example_sdl2_opengl3 -examples/example_sdl2_sdlrenderer/example_sdl2_sdlrenderer diff --git a/app/jni/src/libultraship/extern/ImGui/LICENSE.txt b/app/jni/src/libultraship/extern/ImGui/LICENSE.txt deleted file mode 100644 index fb715bd..0000000 --- a/app/jni/src/libultraship/extern/ImGui/LICENSE.txt +++ /dev/null @@ -1,21 +0,0 @@ -The MIT License (MIT) - -Copyright (c) 2014-2023 Omar Cornut - -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. diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_allegro5.cpp b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_allegro5.cpp deleted file mode 100644 index 3d98636..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_allegro5.cpp +++ /dev/null @@ -1,614 +0,0 @@ -// dear imgui: Renderer + Platform Backend for Allegro 5 -// (Info: Allegro 5 is a cross-platform general purpose library for handling windows, inputs, graphics, etc.) - -// Implemented features: -// [X] Renderer: User texture binding. Use 'ALLEGRO_BITMAP*' as ImTextureID. Read the FAQ about ImTextureID! -// [X] Platform: Keyboard support. Since 1.87 we are using the io.AddKeyEvent() function. Pass ImGuiKey values to all key functions e.g. ImGui::IsKeyPressed(ImGuiKey_Space). [Legacy ALLEGRO_KEY_* values will also be supported unless IMGUI_DISABLE_OBSOLETE_KEYIO is set] -// [X] Platform: Clipboard support (from Allegro 5.1.12) -// [X] Platform: Mouse cursor shape and visibility. Disable with 'io.ConfigFlags |= ImGuiConfigFlags_NoMouseCursorChange'. -// Missing features: -// [ ] Renderer: Multi-viewport support (multiple windows).. -// [ ] Renderer: The renderer is suboptimal as we need to convert vertices manually. -// [ ] Platform: Missing gamepad support. - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -// CHANGELOG -// (minor and older changes stripped away, please see git history for details) -// 2022-11-30: Renderer: Restoring using al_draw_indexed_prim() when Allegro version is >= 5.2.5. -// 2022-10-11: Using 'nullptr' instead of 'NULL' as per our switch to C++11. -// 2022-09-26: Inputs: Renamed ImGuiKey_ModXXX introduced in 1.87 to ImGuiMod_XXX (old names still supported). -// 2022-01-26: Inputs: replaced short-lived io.AddKeyModsEvent() (added two weeks ago) with io.AddKeyEvent() using ImGuiKey_ModXXX flags. Sorry for the confusion. -// 2022-01-17: Inputs: calling new io.AddMousePosEvent(), io.AddMouseButtonEvent(), io.AddMouseWheelEvent() API (1.87+). -// 2022-01-17: Inputs: always calling io.AddKeyModsEvent() next and before key event (not in NewFrame) to fix input queue with very low framerates. -// 2022-01-10: Inputs: calling new io.AddKeyEvent(), io.AddKeyModsEvent() + io.SetKeyEventNativeData() API (1.87+). Support for full ImGuiKey range. -// 2021-12-08: Renderer: Fixed mishandling of the the ImDrawCmd::IdxOffset field! This is an old bug but it never had an effect until some internal rendering changes in 1.86. -// 2021-08-17: Calling io.AddFocusEvent() on ALLEGRO_EVENT_DISPLAY_SWITCH_OUT/ALLEGRO_EVENT_DISPLAY_SWITCH_IN events. -// 2021-06-29: Reorganized backend to pull data from a single structure to facilitate usage with multiple-contexts (all g_XXXX access changed to bd->XXXX). -// 2021-05-19: Renderer: Replaced direct access to ImDrawCmd::TextureId with a call to ImDrawCmd::GetTexID(). (will become a requirement) -// 2021-02-18: Change blending equation to preserve alpha in output buffer. -// 2020-08-10: Inputs: Fixed horizontal mouse wheel direction. -// 2019-12-05: Inputs: Added support for ImGuiMouseCursor_NotAllowed mouse cursor. -// 2019-07-21: Inputs: Added mapping for ImGuiKey_KeyPadEnter. -// 2019-05-11: Inputs: Don't filter character value from ALLEGRO_EVENT_KEY_CHAR before calling AddInputCharacter(). -// 2019-04-30: Renderer: Added support for special ImDrawCallback_ResetRenderState callback to reset render state. -// 2018-11-30: Platform: Added touchscreen support. -// 2018-11-30: Misc: Setting up io.BackendPlatformName/io.BackendRendererName so they can be displayed in the About Window. -// 2018-06-13: Platform: Added clipboard support (from Allegro 5.1.12). -// 2018-06-13: Renderer: Use draw_data->DisplayPos and draw_data->DisplaySize to setup projection matrix and clipping rectangle. -// 2018-06-13: Renderer: Stopped using al_draw_indexed_prim() as it is buggy in Allegro's DX9 backend. -// 2018-06-13: Renderer: Backup/restore transform and clipping rectangle. -// 2018-06-11: Misc: Setup io.BackendFlags ImGuiBackendFlags_HasMouseCursors flag + honor ImGuiConfigFlags_NoMouseCursorChange flag. -// 2018-04-18: Misc: Renamed file from imgui_impl_a5.cpp to imgui_impl_allegro5.cpp. -// 2018-04-18: Misc: Added support for 32-bit vertex indices to avoid conversion at runtime. Added imconfig_allegro5.h to enforce 32-bit indices when included from imgui.h. -// 2018-02-16: Misc: Obsoleted the io.RenderDrawListsFn callback and exposed ImGui_ImplAllegro5_RenderDrawData() in the .h file so you can call it yourself. -// 2018-02-06: Misc: Removed call to ImGui::Shutdown() which is not available from 1.60 WIP, user needs to call CreateContext/DestroyContext themselves. -// 2018-02-06: Inputs: Added mapping for ImGuiKey_Space. - -#include "imgui.h" -#ifndef IMGUI_DISABLE -#include "imgui_impl_allegro5.h" -#include // uint64_t -#include // memcpy - -// Allegro -#include -#include -#ifdef _WIN32 -#include -#endif -#define ALLEGRO_HAS_CLIPBOARD (ALLEGRO_VERSION_INT >= ((5 << 24) | (1 << 16) | (12 << 8))) // Clipboard only supported from Allegro 5.1.12 -#define ALLEGRO_HAS_DRAW_INDEXED_PRIM (ALLEGRO_VERSION_INT >= ((5 << 24) | (2 << 16) | ( 5 << 8))) // DX9 implementation of al_draw_indexed_prim() got fixed in Allegro 5.2.5 - -// Visual Studio warnings -#ifdef _MSC_VER -#pragma warning (disable: 4127) // condition expression is constant -#endif - -struct ImDrawVertAllegro -{ - ImVec2 pos; - ImVec2 uv; - ALLEGRO_COLOR col; -}; - -// FIXME-OPT: Unfortunately Allegro doesn't support 32-bit packed colors so we have to convert them to 4 float as well.. -// FIXME-OPT: Consider inlining al_map_rgba()? -// see https://github.com/liballeg/allegro5/blob/master/src/pixels.c#L554 -// and https://github.com/liballeg/allegro5/blob/master/include/allegro5/internal/aintern_pixels.h -#define DRAW_VERT_IMGUI_TO_ALLEGRO(DST, SRC) { (DST)->pos = (SRC)->pos; (DST)->uv = (SRC)->uv; unsigned char* c = (unsigned char*)&(SRC)->col; (DST)->col = al_map_rgba(c[0], c[1], c[2], c[3]); } - -// Allegro Data -struct ImGui_ImplAllegro5_Data -{ - ALLEGRO_DISPLAY* Display; - ALLEGRO_BITMAP* Texture; - double Time; - ALLEGRO_MOUSE_CURSOR* MouseCursorInvisible; - ALLEGRO_VERTEX_DECL* VertexDecl; - char* ClipboardTextData; - - ImVector BufVertices; - ImVector BufIndices; - - ImGui_ImplAllegro5_Data() { memset((void*)this, 0, sizeof(*this)); } -}; - -// Backend data stored in io.BackendPlatformUserData to allow support for multiple Dear ImGui contexts -// It is STRONGLY preferred that you use docking branch with multi-viewports (== single Dear ImGui context + multiple windows) instead of multiple Dear ImGui contexts. -// FIXME: multi-context support is not well tested and probably dysfunctional in this backend. -static ImGui_ImplAllegro5_Data* ImGui_ImplAllegro5_GetBackendData() { return ImGui::GetCurrentContext() ? (ImGui_ImplAllegro5_Data*)ImGui::GetIO().BackendPlatformUserData : nullptr; } - -static void ImGui_ImplAllegro5_SetupRenderState(ImDrawData* draw_data) -{ - // Setup blending - al_set_separate_blender(ALLEGRO_ADD, ALLEGRO_ALPHA, ALLEGRO_INVERSE_ALPHA, ALLEGRO_ADD, ALLEGRO_ONE, ALLEGRO_INVERSE_ALPHA); - - // Setup orthographic projection matrix - // Our visible imgui space lies from draw_data->DisplayPos (top left) to draw_data->DisplayPos+data_data->DisplaySize (bottom right). - { - float L = draw_data->DisplayPos.x; - float R = draw_data->DisplayPos.x + draw_data->DisplaySize.x; - float T = draw_data->DisplayPos.y; - float B = draw_data->DisplayPos.y + draw_data->DisplaySize.y; - ALLEGRO_TRANSFORM transform; - al_identity_transform(&transform); - al_use_transform(&transform); - al_orthographic_transform(&transform, L, T, 1.0f, R, B, -1.0f); - al_use_projection_transform(&transform); - } -} - -// Render function. -void ImGui_ImplAllegro5_RenderDrawData(ImDrawData* draw_data) -{ - // Avoid rendering when minimized - if (draw_data->DisplaySize.x <= 0.0f || draw_data->DisplaySize.y <= 0.0f) - return; - - // Backup Allegro state that will be modified - ImGui_ImplAllegro5_Data* bd = ImGui_ImplAllegro5_GetBackendData(); - ALLEGRO_TRANSFORM last_transform = *al_get_current_transform(); - ALLEGRO_TRANSFORM last_projection_transform = *al_get_current_projection_transform(); - int last_clip_x, last_clip_y, last_clip_w, last_clip_h; - al_get_clipping_rectangle(&last_clip_x, &last_clip_y, &last_clip_w, &last_clip_h); - int last_blender_op, last_blender_src, last_blender_dst; - al_get_blender(&last_blender_op, &last_blender_src, &last_blender_dst); - - // Setup desired render state - ImGui_ImplAllegro5_SetupRenderState(draw_data); - - // Render command lists - for (int n = 0; n < draw_data->CmdListsCount; n++) - { - const ImDrawList* cmd_list = draw_data->CmdLists[n]; - - ImVector& vertices = bd->BufVertices; -#if ALLEGRO_HAS_DRAW_INDEXED_PRIM - vertices.resize(cmd_list->VtxBuffer.Size); - for (int i = 0; i < cmd_list->VtxBuffer.Size; i++) - { - const ImDrawVert* src_v = &cmd_list->VtxBuffer[i]; - ImDrawVertAllegro* dst_v = &vertices[i]; - DRAW_VERT_IMGUI_TO_ALLEGRO(dst_v, src_v); - } - const int* indices = nullptr; - if (sizeof(ImDrawIdx) == 2) - { - // FIXME-OPT: Allegro doesn't support 16-bit indices. - // You can '#define ImDrawIdx int' in imconfig.h to request Dear ImGui to output 32-bit indices. - // Otherwise, we convert them from 16-bit to 32-bit at runtime here, which works perfectly but is a little wasteful. - bd->BufIndices.resize(cmd_list->IdxBuffer.Size); - for (int i = 0; i < cmd_list->IdxBuffer.Size; ++i) - bd->BufIndices[i] = (int)cmd_list->IdxBuffer.Data[i]; - indices = bd->BufIndices.Data; - } - else if (sizeof(ImDrawIdx) == 4) - { - indices = (const int*)cmd_list->IdxBuffer.Data; - } -#else - // Allegro's implementation of al_draw_indexed_prim() for DX9 was broken until 5.2.5. Unindex buffers ourselves while converting vertex format. - vertices.resize(cmd_list->IdxBuffer.Size); - for (int i = 0; i < cmd_list->IdxBuffer.Size; i++) - { - const ImDrawVert* src_v = &cmd_list->VtxBuffer[cmd_list->IdxBuffer[i]]; - ImDrawVertAllegro* dst_v = &vertices[i]; - DRAW_VERT_IMGUI_TO_ALLEGRO(dst_v, src_v); - } -#endif - - // Render command lists - ImVec2 clip_off = draw_data->DisplayPos; - for (int cmd_i = 0; cmd_i < cmd_list->CmdBuffer.Size; cmd_i++) - { - const ImDrawCmd* pcmd = &cmd_list->CmdBuffer[cmd_i]; - if (pcmd->UserCallback) - { - // User callback, registered via ImDrawList::AddCallback() - // (ImDrawCallback_ResetRenderState is a special callback value used by the user to request the renderer to reset render state.) - if (pcmd->UserCallback == ImDrawCallback_ResetRenderState) - ImGui_ImplAllegro5_SetupRenderState(draw_data); - else - pcmd->UserCallback(cmd_list, pcmd); - } - else - { - // Project scissor/clipping rectangles into framebuffer space - ImVec2 clip_min(pcmd->ClipRect.x - clip_off.x, pcmd->ClipRect.y - clip_off.y); - ImVec2 clip_max(pcmd->ClipRect.z - clip_off.x, pcmd->ClipRect.w - clip_off.y); - if (clip_max.x <= clip_min.x || clip_max.y <= clip_min.y) - continue; - - // Apply scissor/clipping rectangle, Draw - ALLEGRO_BITMAP* texture = (ALLEGRO_BITMAP*)pcmd->GetTexID(); - al_set_clipping_rectangle(clip_min.x, clip_min.y, clip_max.x - clip_min.x, clip_max.y - clip_min.y); -#if ALLEGRO_HAS_DRAW_INDEXED_PRIM - al_draw_indexed_prim(&vertices[0], bd->VertexDecl, texture, &indices[pcmd->IdxOffset], pcmd->ElemCount, ALLEGRO_PRIM_TRIANGLE_LIST); -#else - al_draw_prim(&vertices[0], bd->VertexDecl, texture, pcmd->IdxOffset, pcmd->IdxOffset + pcmd->ElemCount, ALLEGRO_PRIM_TRIANGLE_LIST); -#endif - } - } - } - - // Restore modified Allegro state - al_set_blender(last_blender_op, last_blender_src, last_blender_dst); - al_set_clipping_rectangle(last_clip_x, last_clip_y, last_clip_w, last_clip_h); - al_use_transform(&last_transform); - al_use_projection_transform(&last_projection_transform); -} - -bool ImGui_ImplAllegro5_CreateDeviceObjects() -{ - // Build texture atlas - ImGui_ImplAllegro5_Data* bd = ImGui_ImplAllegro5_GetBackendData(); - ImGuiIO& io = ImGui::GetIO(); - unsigned char* pixels; - int width, height; - io.Fonts->GetTexDataAsRGBA32(&pixels, &width, &height); - - // Create texture - // (Bilinear sampling is required by default. Set 'io.Fonts->Flags |= ImFontAtlasFlags_NoBakedLines' or 'style.AntiAliasedLinesUseTex = false' to allow point/nearest sampling) - int flags = al_get_new_bitmap_flags(); - int fmt = al_get_new_bitmap_format(); - al_set_new_bitmap_flags(ALLEGRO_MEMORY_BITMAP | ALLEGRO_MIN_LINEAR | ALLEGRO_MAG_LINEAR); - al_set_new_bitmap_format(ALLEGRO_PIXEL_FORMAT_ABGR_8888_LE); - ALLEGRO_BITMAP* img = al_create_bitmap(width, height); - al_set_new_bitmap_flags(flags); - al_set_new_bitmap_format(fmt); - if (!img) - return false; - - ALLEGRO_LOCKED_REGION* locked_img = al_lock_bitmap(img, al_get_bitmap_format(img), ALLEGRO_LOCK_WRITEONLY); - if (!locked_img) - { - al_destroy_bitmap(img); - return false; - } - memcpy(locked_img->data, pixels, sizeof(int) * width * height); - al_unlock_bitmap(img); - - // Convert software texture to hardware texture. - ALLEGRO_BITMAP* cloned_img = al_clone_bitmap(img); - al_destroy_bitmap(img); - if (!cloned_img) - return false; - - // Store our identifier - io.Fonts->SetTexID((ImTextureID)(intptr_t)cloned_img); - bd->Texture = cloned_img; - - // Create an invisible mouse cursor - // Because al_hide_mouse_cursor() seems to mess up with the actual inputs.. - ALLEGRO_BITMAP* mouse_cursor = al_create_bitmap(8, 8); - bd->MouseCursorInvisible = al_create_mouse_cursor(mouse_cursor, 0, 0); - al_destroy_bitmap(mouse_cursor); - - return true; -} - -void ImGui_ImplAllegro5_InvalidateDeviceObjects() -{ - ImGuiIO& io = ImGui::GetIO(); - ImGui_ImplAllegro5_Data* bd = ImGui_ImplAllegro5_GetBackendData(); - if (bd->Texture) - { - io.Fonts->SetTexID(0); - al_destroy_bitmap(bd->Texture); - bd->Texture = nullptr; - } - if (bd->MouseCursorInvisible) - { - al_destroy_mouse_cursor(bd->MouseCursorInvisible); - bd->MouseCursorInvisible = nullptr; - } -} - -#if ALLEGRO_HAS_CLIPBOARD -static const char* ImGui_ImplAllegro5_GetClipboardText(void*) -{ - ImGui_ImplAllegro5_Data* bd = ImGui_ImplAllegro5_GetBackendData(); - if (bd->ClipboardTextData) - al_free(bd->ClipboardTextData); - bd->ClipboardTextData = al_get_clipboard_text(bd->Display); - return bd->ClipboardTextData; -} - -static void ImGui_ImplAllegro5_SetClipboardText(void*, const char* text) -{ - ImGui_ImplAllegro5_Data* bd = ImGui_ImplAllegro5_GetBackendData(); - al_set_clipboard_text(bd->Display, text); -} -#endif - -static ImGuiKey ImGui_ImplAllegro5_KeyCodeToImGuiKey(int key_code) -{ - switch (key_code) - { - case ALLEGRO_KEY_TAB: return ImGuiKey_Tab; - case ALLEGRO_KEY_LEFT: return ImGuiKey_LeftArrow; - case ALLEGRO_KEY_RIGHT: return ImGuiKey_RightArrow; - case ALLEGRO_KEY_UP: return ImGuiKey_UpArrow; - case ALLEGRO_KEY_DOWN: return ImGuiKey_DownArrow; - case ALLEGRO_KEY_PGUP: return ImGuiKey_PageUp; - case ALLEGRO_KEY_PGDN: return ImGuiKey_PageDown; - case ALLEGRO_KEY_HOME: return ImGuiKey_Home; - case ALLEGRO_KEY_END: return ImGuiKey_End; - case ALLEGRO_KEY_INSERT: return ImGuiKey_Insert; - case ALLEGRO_KEY_DELETE: return ImGuiKey_Delete; - case ALLEGRO_KEY_BACKSPACE: return ImGuiKey_Backspace; - case ALLEGRO_KEY_SPACE: return ImGuiKey_Space; - case ALLEGRO_KEY_ENTER: return ImGuiKey_Enter; - case ALLEGRO_KEY_ESCAPE: return ImGuiKey_Escape; - case ALLEGRO_KEY_QUOTE: return ImGuiKey_Apostrophe; - case ALLEGRO_KEY_COMMA: return ImGuiKey_Comma; - case ALLEGRO_KEY_MINUS: return ImGuiKey_Minus; - case ALLEGRO_KEY_FULLSTOP: return ImGuiKey_Period; - case ALLEGRO_KEY_SLASH: return ImGuiKey_Slash; - case ALLEGRO_KEY_SEMICOLON: return ImGuiKey_Semicolon; - case ALLEGRO_KEY_EQUALS: return ImGuiKey_Equal; - case ALLEGRO_KEY_OPENBRACE: return ImGuiKey_LeftBracket; - case ALLEGRO_KEY_BACKSLASH: return ImGuiKey_Backslash; - case ALLEGRO_KEY_CLOSEBRACE: return ImGuiKey_RightBracket; - case ALLEGRO_KEY_TILDE: return ImGuiKey_GraveAccent; - case ALLEGRO_KEY_CAPSLOCK: return ImGuiKey_CapsLock; - case ALLEGRO_KEY_SCROLLLOCK: return ImGuiKey_ScrollLock; - case ALLEGRO_KEY_NUMLOCK: return ImGuiKey_NumLock; - case ALLEGRO_KEY_PRINTSCREEN: return ImGuiKey_PrintScreen; - case ALLEGRO_KEY_PAUSE: return ImGuiKey_Pause; - case ALLEGRO_KEY_PAD_0: return ImGuiKey_Keypad0; - case ALLEGRO_KEY_PAD_1: return ImGuiKey_Keypad1; - case ALLEGRO_KEY_PAD_2: return ImGuiKey_Keypad2; - case ALLEGRO_KEY_PAD_3: return ImGuiKey_Keypad3; - case ALLEGRO_KEY_PAD_4: return ImGuiKey_Keypad4; - case ALLEGRO_KEY_PAD_5: return ImGuiKey_Keypad5; - case ALLEGRO_KEY_PAD_6: return ImGuiKey_Keypad6; - case ALLEGRO_KEY_PAD_7: return ImGuiKey_Keypad7; - case ALLEGRO_KEY_PAD_8: return ImGuiKey_Keypad8; - case ALLEGRO_KEY_PAD_9: return ImGuiKey_Keypad9; - case ALLEGRO_KEY_PAD_DELETE: return ImGuiKey_KeypadDecimal; - case ALLEGRO_KEY_PAD_SLASH: return ImGuiKey_KeypadDivide; - case ALLEGRO_KEY_PAD_ASTERISK: return ImGuiKey_KeypadMultiply; - case ALLEGRO_KEY_PAD_MINUS: return ImGuiKey_KeypadSubtract; - case ALLEGRO_KEY_PAD_PLUS: return ImGuiKey_KeypadAdd; - case ALLEGRO_KEY_PAD_ENTER: return ImGuiKey_KeypadEnter; - case ALLEGRO_KEY_PAD_EQUALS: return ImGuiKey_KeypadEqual; - case ALLEGRO_KEY_LCTRL: return ImGuiKey_LeftCtrl; - case ALLEGRO_KEY_LSHIFT: return ImGuiKey_LeftShift; - case ALLEGRO_KEY_ALT: return ImGuiKey_LeftAlt; - case ALLEGRO_KEY_LWIN: return ImGuiKey_LeftSuper; - case ALLEGRO_KEY_RCTRL: return ImGuiKey_RightCtrl; - case ALLEGRO_KEY_RSHIFT: return ImGuiKey_RightShift; - case ALLEGRO_KEY_ALTGR: return ImGuiKey_RightAlt; - case ALLEGRO_KEY_RWIN: return ImGuiKey_RightSuper; - case ALLEGRO_KEY_MENU: return ImGuiKey_Menu; - case ALLEGRO_KEY_0: return ImGuiKey_0; - case ALLEGRO_KEY_1: return ImGuiKey_1; - case ALLEGRO_KEY_2: return ImGuiKey_2; - case ALLEGRO_KEY_3: return ImGuiKey_3; - case ALLEGRO_KEY_4: return ImGuiKey_4; - case ALLEGRO_KEY_5: return ImGuiKey_5; - case ALLEGRO_KEY_6: return ImGuiKey_6; - case ALLEGRO_KEY_7: return ImGuiKey_7; - case ALLEGRO_KEY_8: return ImGuiKey_8; - case ALLEGRO_KEY_9: return ImGuiKey_9; - case ALLEGRO_KEY_A: return ImGuiKey_A; - case ALLEGRO_KEY_B: return ImGuiKey_B; - case ALLEGRO_KEY_C: return ImGuiKey_C; - case ALLEGRO_KEY_D: return ImGuiKey_D; - case ALLEGRO_KEY_E: return ImGuiKey_E; - case ALLEGRO_KEY_F: return ImGuiKey_F; - case ALLEGRO_KEY_G: return ImGuiKey_G; - case ALLEGRO_KEY_H: return ImGuiKey_H; - case ALLEGRO_KEY_I: return ImGuiKey_I; - case ALLEGRO_KEY_J: return ImGuiKey_J; - case ALLEGRO_KEY_K: return ImGuiKey_K; - case ALLEGRO_KEY_L: return ImGuiKey_L; - case ALLEGRO_KEY_M: return ImGuiKey_M; - case ALLEGRO_KEY_N: return ImGuiKey_N; - case ALLEGRO_KEY_O: return ImGuiKey_O; - case ALLEGRO_KEY_P: return ImGuiKey_P; - case ALLEGRO_KEY_Q: return ImGuiKey_Q; - case ALLEGRO_KEY_R: return ImGuiKey_R; - case ALLEGRO_KEY_S: return ImGuiKey_S; - case ALLEGRO_KEY_T: return ImGuiKey_T; - case ALLEGRO_KEY_U: return ImGuiKey_U; - case ALLEGRO_KEY_V: return ImGuiKey_V; - case ALLEGRO_KEY_W: return ImGuiKey_W; - case ALLEGRO_KEY_X: return ImGuiKey_X; - case ALLEGRO_KEY_Y: return ImGuiKey_Y; - case ALLEGRO_KEY_Z: return ImGuiKey_Z; - case ALLEGRO_KEY_F1: return ImGuiKey_F1; - case ALLEGRO_KEY_F2: return ImGuiKey_F2; - case ALLEGRO_KEY_F3: return ImGuiKey_F3; - case ALLEGRO_KEY_F4: return ImGuiKey_F4; - case ALLEGRO_KEY_F5: return ImGuiKey_F5; - case ALLEGRO_KEY_F6: return ImGuiKey_F6; - case ALLEGRO_KEY_F7: return ImGuiKey_F7; - case ALLEGRO_KEY_F8: return ImGuiKey_F8; - case ALLEGRO_KEY_F9: return ImGuiKey_F9; - case ALLEGRO_KEY_F10: return ImGuiKey_F10; - case ALLEGRO_KEY_F11: return ImGuiKey_F11; - case ALLEGRO_KEY_F12: return ImGuiKey_F12; - default: return ImGuiKey_None; - } -} - -bool ImGui_ImplAllegro5_Init(ALLEGRO_DISPLAY* display) -{ - ImGuiIO& io = ImGui::GetIO(); - IM_ASSERT(io.BackendPlatformUserData == nullptr && "Already initialized a platform backend!"); - - // Setup backend capabilities flags - ImGui_ImplAllegro5_Data* bd = IM_NEW(ImGui_ImplAllegro5_Data)(); - io.BackendPlatformUserData = (void*)bd; - io.BackendPlatformName = io.BackendRendererName = "imgui_impl_allegro5"; - io.BackendFlags |= ImGuiBackendFlags_HasMouseCursors; // We can honor GetMouseCursor() values (optional) - - bd->Display = display; - - // Create custom vertex declaration. - // Unfortunately Allegro doesn't support 32-bit packed colors so we have to convert them to 4 floats. - // We still use a custom declaration to use 'ALLEGRO_PRIM_TEX_COORD' instead of 'ALLEGRO_PRIM_TEX_COORD_PIXEL' else we can't do a reliable conversion. - ALLEGRO_VERTEX_ELEMENT elems[] = - { - { ALLEGRO_PRIM_POSITION, ALLEGRO_PRIM_FLOAT_2, IM_OFFSETOF(ImDrawVertAllegro, pos) }, - { ALLEGRO_PRIM_TEX_COORD, ALLEGRO_PRIM_FLOAT_2, IM_OFFSETOF(ImDrawVertAllegro, uv) }, - { ALLEGRO_PRIM_COLOR_ATTR, 0, IM_OFFSETOF(ImDrawVertAllegro, col) }, - { 0, 0, 0 } - }; - bd->VertexDecl = al_create_vertex_decl(elems, sizeof(ImDrawVertAllegro)); - -#if ALLEGRO_HAS_CLIPBOARD - io.SetClipboardTextFn = ImGui_ImplAllegro5_SetClipboardText; - io.GetClipboardTextFn = ImGui_ImplAllegro5_GetClipboardText; - io.ClipboardUserData = nullptr; -#endif - - return true; -} - -void ImGui_ImplAllegro5_Shutdown() -{ - ImGui_ImplAllegro5_Data* bd = ImGui_ImplAllegro5_GetBackendData(); - IM_ASSERT(bd != nullptr && "No platform backend to shutdown, or already shutdown?"); - ImGuiIO& io = ImGui::GetIO(); - - ImGui_ImplAllegro5_InvalidateDeviceObjects(); - if (bd->VertexDecl) - al_destroy_vertex_decl(bd->VertexDecl); - if (bd->ClipboardTextData) - al_free(bd->ClipboardTextData); - - io.BackendPlatformName = io.BackendRendererName = nullptr; - io.BackendPlatformUserData = nullptr; - io.BackendFlags &= ~ImGuiBackendFlags_HasMouseCursors; - IM_DELETE(bd); -} - -// ev->keyboard.modifiers seems always zero so using that... -static void ImGui_ImplAllegro5_UpdateKeyModifiers() -{ - ImGuiIO& io = ImGui::GetIO(); - ALLEGRO_KEYBOARD_STATE keys; - al_get_keyboard_state(&keys); - io.AddKeyEvent(ImGuiMod_Ctrl, al_key_down(&keys, ALLEGRO_KEY_LCTRL) || al_key_down(&keys, ALLEGRO_KEY_RCTRL)); - io.AddKeyEvent(ImGuiMod_Shift, al_key_down(&keys, ALLEGRO_KEY_LSHIFT) || al_key_down(&keys, ALLEGRO_KEY_RSHIFT)); - io.AddKeyEvent(ImGuiMod_Alt, al_key_down(&keys, ALLEGRO_KEY_ALT) || al_key_down(&keys, ALLEGRO_KEY_ALTGR)); - io.AddKeyEvent(ImGuiMod_Super, al_key_down(&keys, ALLEGRO_KEY_LWIN) || al_key_down(&keys, ALLEGRO_KEY_RWIN)); -} - -// You can read the io.WantCaptureMouse, io.WantCaptureKeyboard flags to tell if dear imgui wants to use your inputs. -// - When io.WantCaptureMouse is true, do not dispatch mouse input data to your main application, or clear/overwrite your copy of the mouse data. -// - When io.WantCaptureKeyboard is true, do not dispatch keyboard input data to your main application, or clear/overwrite your copy of the keyboard data. -// Generally you may always pass all inputs to dear imgui, and hide them from your application based on those two flags. -bool ImGui_ImplAllegro5_ProcessEvent(ALLEGRO_EVENT* ev) -{ - ImGuiIO& io = ImGui::GetIO(); - ImGui_ImplAllegro5_Data* bd = ImGui_ImplAllegro5_GetBackendData(); - - switch (ev->type) - { - case ALLEGRO_EVENT_MOUSE_AXES: - if (ev->mouse.display == bd->Display) - { - io.AddMousePosEvent(ev->mouse.x, ev->mouse.y); - io.AddMouseWheelEvent(-ev->mouse.dw, ev->mouse.dz); - } - return true; - case ALLEGRO_EVENT_MOUSE_BUTTON_DOWN: - case ALLEGRO_EVENT_MOUSE_BUTTON_UP: - if (ev->mouse.display == bd->Display && ev->mouse.button > 0 && ev->mouse.button <= 5) - io.AddMouseButtonEvent(ev->mouse.button - 1, ev->type == ALLEGRO_EVENT_MOUSE_BUTTON_DOWN); - return true; - case ALLEGRO_EVENT_TOUCH_MOVE: - if (ev->touch.display == bd->Display) - io.AddMousePosEvent(ev->touch.x, ev->touch.y); - return true; - case ALLEGRO_EVENT_TOUCH_BEGIN: - case ALLEGRO_EVENT_TOUCH_END: - case ALLEGRO_EVENT_TOUCH_CANCEL: - if (ev->touch.display == bd->Display && ev->touch.primary) - io.AddMouseButtonEvent(0, ev->type == ALLEGRO_EVENT_TOUCH_BEGIN); - return true; - case ALLEGRO_EVENT_MOUSE_LEAVE_DISPLAY: - if (ev->mouse.display == bd->Display) - io.AddMousePosEvent(-FLT_MAX, -FLT_MAX); - return true; - case ALLEGRO_EVENT_KEY_CHAR: - if (ev->keyboard.display == bd->Display) - if (ev->keyboard.unichar != 0) - io.AddInputCharacter((unsigned int)ev->keyboard.unichar); - return true; - case ALLEGRO_EVENT_KEY_DOWN: - case ALLEGRO_EVENT_KEY_UP: - if (ev->keyboard.display == bd->Display) - { - ImGui_ImplAllegro5_UpdateKeyModifiers(); - ImGuiKey key = ImGui_ImplAllegro5_KeyCodeToImGuiKey(ev->keyboard.keycode); - io.AddKeyEvent(key, (ev->type == ALLEGRO_EVENT_KEY_DOWN)); - io.SetKeyEventNativeData(key, ev->keyboard.keycode, -1); // To support legacy indexing (<1.87 user code) - } - return true; - case ALLEGRO_EVENT_DISPLAY_SWITCH_OUT: - if (ev->display.source == bd->Display) - io.AddFocusEvent(false); - return true; - case ALLEGRO_EVENT_DISPLAY_SWITCH_IN: - if (ev->display.source == bd->Display) - { - io.AddFocusEvent(true); -#if defined(ALLEGRO_UNSTABLE) - al_clear_keyboard_state(bd->Display); -#endif - } - return true; - } - return false; -} - -static void ImGui_ImplAllegro5_UpdateMouseCursor() -{ - ImGuiIO& io = ImGui::GetIO(); - if (io.ConfigFlags & ImGuiConfigFlags_NoMouseCursorChange) - return; - - ImGui_ImplAllegro5_Data* bd = ImGui_ImplAllegro5_GetBackendData(); - ImGuiMouseCursor imgui_cursor = ImGui::GetMouseCursor(); - if (io.MouseDrawCursor || imgui_cursor == ImGuiMouseCursor_None) - { - // Hide OS mouse cursor if imgui is drawing it or if it wants no cursor - al_set_mouse_cursor(bd->Display, bd->MouseCursorInvisible); - } - else - { - ALLEGRO_SYSTEM_MOUSE_CURSOR cursor_id = ALLEGRO_SYSTEM_MOUSE_CURSOR_DEFAULT; - switch (imgui_cursor) - { - case ImGuiMouseCursor_TextInput: cursor_id = ALLEGRO_SYSTEM_MOUSE_CURSOR_EDIT; break; - case ImGuiMouseCursor_ResizeAll: cursor_id = ALLEGRO_SYSTEM_MOUSE_CURSOR_MOVE; break; - case ImGuiMouseCursor_ResizeNS: cursor_id = ALLEGRO_SYSTEM_MOUSE_CURSOR_RESIZE_N; break; - case ImGuiMouseCursor_ResizeEW: cursor_id = ALLEGRO_SYSTEM_MOUSE_CURSOR_RESIZE_E; break; - case ImGuiMouseCursor_ResizeNESW: cursor_id = ALLEGRO_SYSTEM_MOUSE_CURSOR_RESIZE_NE; break; - case ImGuiMouseCursor_ResizeNWSE: cursor_id = ALLEGRO_SYSTEM_MOUSE_CURSOR_RESIZE_NW; break; - case ImGuiMouseCursor_NotAllowed: cursor_id = ALLEGRO_SYSTEM_MOUSE_CURSOR_UNAVAILABLE; break; - } - al_set_system_mouse_cursor(bd->Display, cursor_id); - } -} - -void ImGui_ImplAllegro5_NewFrame() -{ - ImGui_ImplAllegro5_Data* bd = ImGui_ImplAllegro5_GetBackendData(); - IM_ASSERT(bd != nullptr && "Did you call ImGui_ImplAllegro5_Init()?"); - - if (!bd->Texture) - ImGui_ImplAllegro5_CreateDeviceObjects(); - - ImGuiIO& io = ImGui::GetIO(); - - // Setup display size (every frame to accommodate for window resizing) - int w, h; - w = al_get_display_width(bd->Display); - h = al_get_display_height(bd->Display); - io.DisplaySize = ImVec2((float)w, (float)h); - - // Setup time step - double current_time = al_get_time(); - io.DeltaTime = bd->Time > 0.0 ? (float)(current_time - bd->Time) : (float)(1.0f / 60.0f); - bd->Time = current_time; - - // Setup mouse cursor shape - ImGui_ImplAllegro5_UpdateMouseCursor(); -} - -//----------------------------------------------------------------------------- - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_allegro5.h b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_allegro5.h deleted file mode 100644 index a7f7c0e..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_allegro5.h +++ /dev/null @@ -1,39 +0,0 @@ -// dear imgui: Renderer + Platform Backend for Allegro 5 -// (Info: Allegro 5 is a cross-platform general purpose library for handling windows, inputs, graphics, etc.) - -// Implemented features: -// [X] Renderer: User texture binding. Use 'ALLEGRO_BITMAP*' as ImTextureID. Read the FAQ about ImTextureID! -// [X] Platform: Keyboard support. Since 1.87 we are using the io.AddKeyEvent() function. Pass ImGuiKey values to all key functions e.g. ImGui::IsKeyPressed(ImGuiKey_Space). [Legacy ALLEGRO_KEY_* values will also be supported unless IMGUI_DISABLE_OBSOLETE_KEYIO is set] -// [X] Platform: Clipboard support (from Allegro 5.1.12) -// [X] Platform: Mouse cursor shape and visibility. Disable with 'io.ConfigFlags |= ImGuiConfigFlags_NoMouseCursorChange'. -// Missing features: -// [ ] Renderer: Multi-viewport support (multiple windows).. -// [ ] Renderer: The renderer is suboptimal as we need to unindex our buffers and convert vertices manually. -// [ ] Platform: Missing gamepad support. - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#pragma once -#include "imgui.h" // IMGUI_IMPL_API -#ifndef IMGUI_DISABLE - -struct ALLEGRO_DISPLAY; -union ALLEGRO_EVENT; - -IMGUI_IMPL_API bool ImGui_ImplAllegro5_Init(ALLEGRO_DISPLAY* display); -IMGUI_IMPL_API void ImGui_ImplAllegro5_Shutdown(); -IMGUI_IMPL_API void ImGui_ImplAllegro5_NewFrame(); -IMGUI_IMPL_API void ImGui_ImplAllegro5_RenderDrawData(ImDrawData* draw_data); -IMGUI_IMPL_API bool ImGui_ImplAllegro5_ProcessEvent(ALLEGRO_EVENT* event); - -// Use if you want to reset your rendering device without losing Dear ImGui state. -IMGUI_IMPL_API bool ImGui_ImplAllegro5_CreateDeviceObjects(); -IMGUI_IMPL_API void ImGui_ImplAllegro5_InvalidateDeviceObjects(); - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_android.cpp b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_android.cpp deleted file mode 100644 index b679ac3..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_android.cpp +++ /dev/null @@ -1,305 +0,0 @@ -// dear imgui: Platform Binding for Android native app -// This needs to be used along with the OpenGL 3 Renderer (imgui_impl_opengl3) - -// Implemented features: -// [X] Platform: Keyboard support. Since 1.87 we are using the io.AddKeyEvent() function. Pass ImGuiKey values to all key functions e.g. ImGui::IsKeyPressed(ImGuiKey_Space). [Legacy AKEYCODE_* values will also be supported unless IMGUI_DISABLE_OBSOLETE_KEYIO is set] -// [X] Platform: Mouse support. Can discriminate Mouse/TouchScreen/Pen. -// Missing features: -// [ ] Platform: Clipboard support. -// [ ] Platform: Gamepad support. Enable with 'io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad'. -// [ ] Platform: Mouse cursor shape and visibility. Disable with 'io.ConfigFlags |= ImGuiConfigFlags_NoMouseCursorChange'. FIXME: Check if this is even possible with Android. -// [ ] Platform: Multi-viewport support (multiple windows). Not meaningful on Android. -// Important: -// - Consider using SDL or GLFW backend on Android, which will be more full-featured than this. -// - FIXME: On-screen keyboard currently needs to be enabled by the application (see examples/ and issue #3446) -// - FIXME: Unicode character inputs needs to be passed by Dear ImGui by the application (see examples/ and issue #3446) - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -// CHANGELOG -// (minor and older changes stripped away, please see git history for details) -// 2022-09-26: Inputs: Renamed ImGuiKey_ModXXX introduced in 1.87 to ImGuiMod_XXX (old names still supported). -// 2022-01-26: Inputs: replaced short-lived io.AddKeyModsEvent() (added two weeks ago) with io.AddKeyEvent() using ImGuiKey_ModXXX flags. Sorry for the confusion. -// 2022-01-17: Inputs: calling new io.AddMousePosEvent(), io.AddMouseButtonEvent(), io.AddMouseWheelEvent() API (1.87+). -// 2022-01-10: Inputs: calling new io.AddKeyEvent(), io.AddKeyModsEvent() + io.SetKeyEventNativeData() API (1.87+). Support for full ImGuiKey range. -// 2021-03-04: Initial version. - -#include "imgui.h" -#ifndef IMGUI_DISABLE -#include "imgui_impl_android.h" -#include -#include -#include -#include -#include - -// Android data -static double g_Time = 0.0; -static ANativeWindow* g_Window; -static char g_LogTag[] = "ImGuiExample"; - -static ImGuiKey ImGui_ImplAndroid_KeyCodeToImGuiKey(int32_t key_code) -{ - switch (key_code) - { - case AKEYCODE_TAB: return ImGuiKey_Tab; - case AKEYCODE_DPAD_LEFT: return ImGuiKey_LeftArrow; - case AKEYCODE_DPAD_RIGHT: return ImGuiKey_RightArrow; - case AKEYCODE_DPAD_UP: return ImGuiKey_UpArrow; - case AKEYCODE_DPAD_DOWN: return ImGuiKey_DownArrow; - case AKEYCODE_PAGE_UP: return ImGuiKey_PageUp; - case AKEYCODE_PAGE_DOWN: return ImGuiKey_PageDown; - case AKEYCODE_MOVE_HOME: return ImGuiKey_Home; - case AKEYCODE_MOVE_END: return ImGuiKey_End; - case AKEYCODE_INSERT: return ImGuiKey_Insert; - case AKEYCODE_FORWARD_DEL: return ImGuiKey_Delete; - case AKEYCODE_DEL: return ImGuiKey_Backspace; - case AKEYCODE_SPACE: return ImGuiKey_Space; - case AKEYCODE_ENTER: return ImGuiKey_Enter; - case AKEYCODE_ESCAPE: return ImGuiKey_Escape; - case AKEYCODE_APOSTROPHE: return ImGuiKey_Apostrophe; - case AKEYCODE_COMMA: return ImGuiKey_Comma; - case AKEYCODE_MINUS: return ImGuiKey_Minus; - case AKEYCODE_PERIOD: return ImGuiKey_Period; - case AKEYCODE_SLASH: return ImGuiKey_Slash; - case AKEYCODE_SEMICOLON: return ImGuiKey_Semicolon; - case AKEYCODE_EQUALS: return ImGuiKey_Equal; - case AKEYCODE_LEFT_BRACKET: return ImGuiKey_LeftBracket; - case AKEYCODE_BACKSLASH: return ImGuiKey_Backslash; - case AKEYCODE_RIGHT_BRACKET: return ImGuiKey_RightBracket; - case AKEYCODE_GRAVE: return ImGuiKey_GraveAccent; - case AKEYCODE_CAPS_LOCK: return ImGuiKey_CapsLock; - case AKEYCODE_SCROLL_LOCK: return ImGuiKey_ScrollLock; - case AKEYCODE_NUM_LOCK: return ImGuiKey_NumLock; - case AKEYCODE_SYSRQ: return ImGuiKey_PrintScreen; - case AKEYCODE_BREAK: return ImGuiKey_Pause; - case AKEYCODE_NUMPAD_0: return ImGuiKey_Keypad0; - case AKEYCODE_NUMPAD_1: return ImGuiKey_Keypad1; - case AKEYCODE_NUMPAD_2: return ImGuiKey_Keypad2; - case AKEYCODE_NUMPAD_3: return ImGuiKey_Keypad3; - case AKEYCODE_NUMPAD_4: return ImGuiKey_Keypad4; - case AKEYCODE_NUMPAD_5: return ImGuiKey_Keypad5; - case AKEYCODE_NUMPAD_6: return ImGuiKey_Keypad6; - case AKEYCODE_NUMPAD_7: return ImGuiKey_Keypad7; - case AKEYCODE_NUMPAD_8: return ImGuiKey_Keypad8; - case AKEYCODE_NUMPAD_9: return ImGuiKey_Keypad9; - case AKEYCODE_NUMPAD_DOT: return ImGuiKey_KeypadDecimal; - case AKEYCODE_NUMPAD_DIVIDE: return ImGuiKey_KeypadDivide; - case AKEYCODE_NUMPAD_MULTIPLY: return ImGuiKey_KeypadMultiply; - case AKEYCODE_NUMPAD_SUBTRACT: return ImGuiKey_KeypadSubtract; - case AKEYCODE_NUMPAD_ADD: return ImGuiKey_KeypadAdd; - case AKEYCODE_NUMPAD_ENTER: return ImGuiKey_KeypadEnter; - case AKEYCODE_NUMPAD_EQUALS: return ImGuiKey_KeypadEqual; - case AKEYCODE_CTRL_LEFT: return ImGuiKey_LeftCtrl; - case AKEYCODE_SHIFT_LEFT: return ImGuiKey_LeftShift; - case AKEYCODE_ALT_LEFT: return ImGuiKey_LeftAlt; - case AKEYCODE_META_LEFT: return ImGuiKey_LeftSuper; - case AKEYCODE_CTRL_RIGHT: return ImGuiKey_RightCtrl; - case AKEYCODE_SHIFT_RIGHT: return ImGuiKey_RightShift; - case AKEYCODE_ALT_RIGHT: return ImGuiKey_RightAlt; - case AKEYCODE_META_RIGHT: return ImGuiKey_RightSuper; - case AKEYCODE_MENU: return ImGuiKey_Menu; - case AKEYCODE_0: return ImGuiKey_0; - case AKEYCODE_1: return ImGuiKey_1; - case AKEYCODE_2: return ImGuiKey_2; - case AKEYCODE_3: return ImGuiKey_3; - case AKEYCODE_4: return ImGuiKey_4; - case AKEYCODE_5: return ImGuiKey_5; - case AKEYCODE_6: return ImGuiKey_6; - case AKEYCODE_7: return ImGuiKey_7; - case AKEYCODE_8: return ImGuiKey_8; - case AKEYCODE_9: return ImGuiKey_9; - case AKEYCODE_A: return ImGuiKey_A; - case AKEYCODE_B: return ImGuiKey_B; - case AKEYCODE_C: return ImGuiKey_C; - case AKEYCODE_D: return ImGuiKey_D; - case AKEYCODE_E: return ImGuiKey_E; - case AKEYCODE_F: return ImGuiKey_F; - case AKEYCODE_G: return ImGuiKey_G; - case AKEYCODE_H: return ImGuiKey_H; - case AKEYCODE_I: return ImGuiKey_I; - case AKEYCODE_J: return ImGuiKey_J; - case AKEYCODE_K: return ImGuiKey_K; - case AKEYCODE_L: return ImGuiKey_L; - case AKEYCODE_M: return ImGuiKey_M; - case AKEYCODE_N: return ImGuiKey_N; - case AKEYCODE_O: return ImGuiKey_O; - case AKEYCODE_P: return ImGuiKey_P; - case AKEYCODE_Q: return ImGuiKey_Q; - case AKEYCODE_R: return ImGuiKey_R; - case AKEYCODE_S: return ImGuiKey_S; - case AKEYCODE_T: return ImGuiKey_T; - case AKEYCODE_U: return ImGuiKey_U; - case AKEYCODE_V: return ImGuiKey_V; - case AKEYCODE_W: return ImGuiKey_W; - case AKEYCODE_X: return ImGuiKey_X; - case AKEYCODE_Y: return ImGuiKey_Y; - case AKEYCODE_Z: return ImGuiKey_Z; - case AKEYCODE_F1: return ImGuiKey_F1; - case AKEYCODE_F2: return ImGuiKey_F2; - case AKEYCODE_F3: return ImGuiKey_F3; - case AKEYCODE_F4: return ImGuiKey_F4; - case AKEYCODE_F5: return ImGuiKey_F5; - case AKEYCODE_F6: return ImGuiKey_F6; - case AKEYCODE_F7: return ImGuiKey_F7; - case AKEYCODE_F8: return ImGuiKey_F8; - case AKEYCODE_F9: return ImGuiKey_F9; - case AKEYCODE_F10: return ImGuiKey_F10; - case AKEYCODE_F11: return ImGuiKey_F11; - case AKEYCODE_F12: return ImGuiKey_F12; - default: return ImGuiKey_None; - } -} - -int32_t ImGui_ImplAndroid_HandleInputEvent(AInputEvent* input_event) -{ - ImGuiIO& io = ImGui::GetIO(); - int32_t event_type = AInputEvent_getType(input_event); - switch (event_type) - { - case AINPUT_EVENT_TYPE_KEY: - { - int32_t event_key_code = AKeyEvent_getKeyCode(input_event); - int32_t event_scan_code = AKeyEvent_getScanCode(input_event); - int32_t event_action = AKeyEvent_getAction(input_event); - int32_t event_meta_state = AKeyEvent_getMetaState(input_event); - - io.AddKeyEvent(ImGuiMod_Ctrl, (event_meta_state & AMETA_CTRL_ON) != 0); - io.AddKeyEvent(ImGuiMod_Shift, (event_meta_state & AMETA_SHIFT_ON) != 0); - io.AddKeyEvent(ImGuiMod_Alt, (event_meta_state & AMETA_ALT_ON) != 0); - io.AddKeyEvent(ImGuiMod_Super, (event_meta_state & AMETA_META_ON) != 0); - - switch (event_action) - { - // FIXME: AKEY_EVENT_ACTION_DOWN and AKEY_EVENT_ACTION_UP occur at once as soon as a touch pointer - // goes up from a key. We use a simple key event queue/ and process one event per key per frame in - // ImGui_ImplAndroid_NewFrame()...or consider using IO queue, if suitable: https://github.com/ocornut/imgui/issues/2787 - case AKEY_EVENT_ACTION_DOWN: - case AKEY_EVENT_ACTION_UP: - { - ImGuiKey key = ImGui_ImplAndroid_KeyCodeToImGuiKey(event_key_code); - if (key != ImGuiKey_None && (event_action == AKEY_EVENT_ACTION_DOWN || event_action == AKEY_EVENT_ACTION_UP)) - { - io.AddKeyEvent(key, event_action == AKEY_EVENT_ACTION_DOWN); - io.SetKeyEventNativeData(key, event_key_code, event_scan_code); - } - - break; - } - default: - break; - } - break; - } - case AINPUT_EVENT_TYPE_MOTION: - { - int32_t event_action = AMotionEvent_getAction(input_event); - int32_t event_pointer_index = (event_action & AMOTION_EVENT_ACTION_POINTER_INDEX_MASK) >> AMOTION_EVENT_ACTION_POINTER_INDEX_SHIFT; - event_action &= AMOTION_EVENT_ACTION_MASK; - - switch (AMotionEvent_getToolType(input_event, event_pointer_index)) - { - case AMOTION_EVENT_TOOL_TYPE_MOUSE: - io.AddMouseSourceEvent(ImGuiMouseSource_Mouse); - break; - case AMOTION_EVENT_TOOL_TYPE_STYLUS: - case AMOTION_EVENT_TOOL_TYPE_ERASER: - io.AddMouseSourceEvent(ImGuiMouseSource_Pen); - break; - case AMOTION_EVENT_TOOL_TYPE_FINGER: - default: - io.AddMouseSourceEvent(ImGuiMouseSource_TouchScreen); - break; - } - - switch (event_action) - { - case AMOTION_EVENT_ACTION_DOWN: - case AMOTION_EVENT_ACTION_UP: - // Physical mouse buttons (and probably other physical devices) also invoke the actions AMOTION_EVENT_ACTION_DOWN/_UP, - // but we have to process them separately to identify the actual button pressed. This is done below via - // AMOTION_EVENT_ACTION_BUTTON_PRESS/_RELEASE. Here, we only process "FINGER" input (and "UNKNOWN", as a fallback). - if((AMotionEvent_getToolType(input_event, event_pointer_index) == AMOTION_EVENT_TOOL_TYPE_FINGER) - || (AMotionEvent_getToolType(input_event, event_pointer_index) == AMOTION_EVENT_TOOL_TYPE_UNKNOWN)) - { - io.AddMousePosEvent(AMotionEvent_getX(input_event, event_pointer_index), AMotionEvent_getY(input_event, event_pointer_index)); - io.AddMouseButtonEvent(0, event_action == AMOTION_EVENT_ACTION_DOWN); - } - break; - case AMOTION_EVENT_ACTION_BUTTON_PRESS: - case AMOTION_EVENT_ACTION_BUTTON_RELEASE: - { - int32_t button_state = AMotionEvent_getButtonState(input_event); - io.AddMouseButtonEvent(0, (button_state & AMOTION_EVENT_BUTTON_PRIMARY) != 0); - io.AddMouseButtonEvent(1, (button_state & AMOTION_EVENT_BUTTON_SECONDARY) != 0); - io.AddMouseButtonEvent(2, (button_state & AMOTION_EVENT_BUTTON_TERTIARY) != 0); - } - break; - case AMOTION_EVENT_ACTION_HOVER_MOVE: // Hovering: Tool moves while NOT pressed (such as a physical mouse) - case AMOTION_EVENT_ACTION_MOVE: // Touch pointer moves while DOWN - io.AddMousePosEvent(AMotionEvent_getX(input_event, event_pointer_index), AMotionEvent_getY(input_event, event_pointer_index)); - break; - case AMOTION_EVENT_ACTION_SCROLL: - io.AddMouseWheelEvent(AMotionEvent_getAxisValue(input_event, AMOTION_EVENT_AXIS_HSCROLL, event_pointer_index), AMotionEvent_getAxisValue(input_event, AMOTION_EVENT_AXIS_VSCROLL, event_pointer_index)); - break; - default: - break; - } - } - return 1; - default: - break; - } - - return 0; -} - -bool ImGui_ImplAndroid_Init(ANativeWindow* window) -{ - g_Window = window; - g_Time = 0.0; - - // Setup backend capabilities flags - ImGuiIO& io = ImGui::GetIO(); - io.BackendPlatformName = "imgui_impl_android"; - - return true; -} - -void ImGui_ImplAndroid_Shutdown() -{ - ImGuiIO& io = ImGui::GetIO(); - io.BackendPlatformName = nullptr; -} - -void ImGui_ImplAndroid_NewFrame() -{ - ImGuiIO& io = ImGui::GetIO(); - - // Setup display size (every frame to accommodate for window resizing) - int32_t window_width = ANativeWindow_getWidth(g_Window); - int32_t window_height = ANativeWindow_getHeight(g_Window); - int display_width = window_width; - int display_height = window_height; - - io.DisplaySize = ImVec2((float)window_width, (float)window_height); - if (window_width > 0 && window_height > 0) - io.DisplayFramebufferScale = ImVec2((float)display_width / window_width, (float)display_height / window_height); - - // Setup time step - struct timespec current_timespec; - clock_gettime(CLOCK_MONOTONIC, ¤t_timespec); - double current_time = (double)(current_timespec.tv_sec) + (current_timespec.tv_nsec / 1000000000.0); - io.DeltaTime = g_Time > 0.0 ? (float)(current_time - g_Time) : (float)(1.0f / 60.0f); - g_Time = current_time; -} - -//----------------------------------------------------------------------------- - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_android.h b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_android.h deleted file mode 100644 index e078b25..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_android.h +++ /dev/null @@ -1,37 +0,0 @@ -// dear imgui: Platform Binding for Android native app -// This needs to be used along with the OpenGL 3 Renderer (imgui_impl_opengl3) - -// Implemented features: -// [X] Platform: Keyboard support. Since 1.87 we are using the io.AddKeyEvent() function. Pass ImGuiKey values to all key functions e.g. ImGui::IsKeyPressed(ImGuiKey_Space). [Legacy AKEYCODE_* values will also be supported unless IMGUI_DISABLE_OBSOLETE_KEYIO is set] -// [X] Platform: Mouse support. Can discriminate Mouse/TouchScreen/Pen. -// Missing features: -// [ ] Platform: Clipboard support. -// [ ] Platform: Gamepad support. Enable with 'io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad'. -// [ ] Platform: Mouse cursor shape and visibility. Disable with 'io.ConfigFlags |= ImGuiConfigFlags_NoMouseCursorChange'. FIXME: Check if this is even possible with Android. -// [ ] Platform: Multi-viewport support (multiple windows). Not meaningful on Android. -// Important: -// - Consider using SDL or GLFW backend on Android, which will be more full-featured than this. -// - FIXME: On-screen keyboard currently needs to be enabled by the application (see examples/ and issue #3446) -// - FIXME: Unicode character inputs needs to be passed by Dear ImGui by the application (see examples/ and issue #3446) - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#pragma once -#include "imgui.h" // IMGUI_IMPL_API -#ifndef IMGUI_DISABLE - -struct ANativeWindow; -struct AInputEvent; - -IMGUI_IMPL_API bool ImGui_ImplAndroid_Init(ANativeWindow* window); -IMGUI_IMPL_API int32_t ImGui_ImplAndroid_HandleInputEvent(AInputEvent* input_event); -IMGUI_IMPL_API void ImGui_ImplAndroid_Shutdown(); -IMGUI_IMPL_API void ImGui_ImplAndroid_NewFrame(); - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_dx10.cpp b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_dx10.cpp deleted file mode 100644 index 2d53e18..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_dx10.cpp +++ /dev/null @@ -1,722 +0,0 @@ -// dear imgui: Renderer Backend for DirectX10 -// This needs to be used along with a Platform Backend (e.g. Win32) - -// Implemented features: -// [X] Renderer: User texture binding. Use 'ID3D10ShaderResourceView*' as ImTextureID. Read the FAQ about ImTextureID! -// [X] Renderer: Large meshes support (64k+ vertices) with 16-bit indices. -// [X] Renderer: Multi-viewport support (multiple windows). Enable with 'io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable'. - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -// CHANGELOG -// (minor and older changes stripped away, please see git history for details) -// 2023-XX-XX: Platform: Added support for multiple windows via the ImGuiPlatformIO interface. -// 2022-10-11: Using 'nullptr' instead of 'NULL' as per our switch to C++11. -// 2021-06-29: Reorganized backend to pull data from a single structure to facilitate usage with multiple-contexts (all g_XXXX access changed to bd->XXXX). -// 2021-05-19: DirectX10: Replaced direct access to ImDrawCmd::TextureId with a call to ImDrawCmd::GetTexID(). (will become a requirement) -// 2021-02-18: DirectX10: Change blending equation to preserve alpha in output buffer. -// 2019-07-21: DirectX10: Backup, clear and restore Geometry Shader is any is bound when calling ImGui_ImplDX10_RenderDrawData(). -// 2019-05-29: DirectX10: Added support for large mesh (64K+ vertices), enable ImGuiBackendFlags_RendererHasVtxOffset flag. -// 2019-04-30: DirectX10: Added support for special ImDrawCallback_ResetRenderState callback to reset render state. -// 2018-12-03: Misc: Added #pragma comment statement to automatically link with d3dcompiler.lib when using D3DCompile(). -// 2018-11-30: Misc: Setting up io.BackendRendererName so it can be displayed in the About Window. -// 2018-07-13: DirectX10: Fixed unreleased resources in Init and Shutdown functions. -// 2018-06-08: Misc: Extracted imgui_impl_dx10.cpp/.h away from the old combined DX10+Win32 example. -// 2018-06-08: DirectX10: Use draw_data->DisplayPos and draw_data->DisplaySize to setup projection matrix and clipping rectangle. -// 2018-04-09: Misc: Fixed erroneous call to io.Fonts->ClearInputData() + ClearTexData() that was left in DX10 example but removed in 1.47 (Nov 2015) on other backends. -// 2018-02-16: Misc: Obsoleted the io.RenderDrawListsFn callback and exposed ImGui_ImplDX10_RenderDrawData() in the .h file so you can call it yourself. -// 2018-02-06: Misc: Removed call to ImGui::Shutdown() which is not available from 1.60 WIP, user needs to call CreateContext/DestroyContext themselves. -// 2016-05-07: DirectX10: Disabling depth-write. - -#include "imgui.h" -#ifndef IMGUI_DISABLE -#include "imgui_impl_dx10.h" - -// DirectX -#include -#include -#include -#include -#ifdef _MSC_VER -#pragma comment(lib, "d3dcompiler") // Automatically link with d3dcompiler.lib as we are using D3DCompile() below. -#endif - -// DirectX data -struct ImGui_ImplDX10_Data -{ - ID3D10Device* pd3dDevice; - IDXGIFactory* pFactory; - ID3D10Buffer* pVB; - ID3D10Buffer* pIB; - ID3D10VertexShader* pVertexShader; - ID3D10InputLayout* pInputLayout; - ID3D10Buffer* pVertexConstantBuffer; - ID3D10PixelShader* pPixelShader; - ID3D10SamplerState* pFontSampler; - ID3D10ShaderResourceView* pFontTextureView; - ID3D10RasterizerState* pRasterizerState; - ID3D10BlendState* pBlendState; - ID3D10DepthStencilState* pDepthStencilState; - int VertexBufferSize; - int IndexBufferSize; - - ImGui_ImplDX10_Data() { memset((void*)this, 0, sizeof(*this)); VertexBufferSize = 5000; IndexBufferSize = 10000; } -}; - -struct VERTEX_CONSTANT_BUFFER_DX10 -{ - float mvp[4][4]; -}; - -// Backend data stored in io.BackendRendererUserData to allow support for multiple Dear ImGui contexts -// It is STRONGLY preferred that you use docking branch with multi-viewports (== single Dear ImGui context + multiple windows) instead of multiple Dear ImGui contexts. -static ImGui_ImplDX10_Data* ImGui_ImplDX10_GetBackendData() -{ - return ImGui::GetCurrentContext() ? (ImGui_ImplDX10_Data*)ImGui::GetIO().BackendRendererUserData : nullptr; -} - -// Forward Declarations -static void ImGui_ImplDX10_InitPlatformInterface(); -static void ImGui_ImplDX10_ShutdownPlatformInterface(); - -// Functions -static void ImGui_ImplDX10_SetupRenderState(ImDrawData* draw_data, ID3D10Device* ctx) -{ - ImGui_ImplDX10_Data* bd = ImGui_ImplDX10_GetBackendData(); - - // Setup viewport - D3D10_VIEWPORT vp; - memset(&vp, 0, sizeof(D3D10_VIEWPORT)); - vp.Width = (UINT)draw_data->DisplaySize.x; - vp.Height = (UINT)draw_data->DisplaySize.y; - vp.MinDepth = 0.0f; - vp.MaxDepth = 1.0f; - vp.TopLeftX = vp.TopLeftY = 0; - ctx->RSSetViewports(1, &vp); - - // Bind shader and vertex buffers - unsigned int stride = sizeof(ImDrawVert); - unsigned int offset = 0; - ctx->IASetInputLayout(bd->pInputLayout); - ctx->IASetVertexBuffers(0, 1, &bd->pVB, &stride, &offset); - ctx->IASetIndexBuffer(bd->pIB, sizeof(ImDrawIdx) == 2 ? DXGI_FORMAT_R16_UINT : DXGI_FORMAT_R32_UINT, 0); - ctx->IASetPrimitiveTopology(D3D10_PRIMITIVE_TOPOLOGY_TRIANGLELIST); - ctx->VSSetShader(bd->pVertexShader); - ctx->VSSetConstantBuffers(0, 1, &bd->pVertexConstantBuffer); - ctx->PSSetShader(bd->pPixelShader); - ctx->PSSetSamplers(0, 1, &bd->pFontSampler); - ctx->GSSetShader(nullptr); - - // Setup render state - const float blend_factor[4] = { 0.f, 0.f, 0.f, 0.f }; - ctx->OMSetBlendState(bd->pBlendState, blend_factor, 0xffffffff); - ctx->OMSetDepthStencilState(bd->pDepthStencilState, 0); - ctx->RSSetState(bd->pRasterizerState); -} - -// Render function -void ImGui_ImplDX10_RenderDrawData(ImDrawData* draw_data) -{ - // Avoid rendering when minimized - if (draw_data->DisplaySize.x <= 0.0f || draw_data->DisplaySize.y <= 0.0f) - return; - - ImGui_ImplDX10_Data* bd = ImGui_ImplDX10_GetBackendData(); - ID3D10Device* ctx = bd->pd3dDevice; - - // Create and grow vertex/index buffers if needed - if (!bd->pVB || bd->VertexBufferSize < draw_data->TotalVtxCount) - { - if (bd->pVB) { bd->pVB->Release(); bd->pVB = nullptr; } - bd->VertexBufferSize = draw_data->TotalVtxCount + 5000; - D3D10_BUFFER_DESC desc; - memset(&desc, 0, sizeof(D3D10_BUFFER_DESC)); - desc.Usage = D3D10_USAGE_DYNAMIC; - desc.ByteWidth = bd->VertexBufferSize * sizeof(ImDrawVert); - desc.BindFlags = D3D10_BIND_VERTEX_BUFFER; - desc.CPUAccessFlags = D3D10_CPU_ACCESS_WRITE; - desc.MiscFlags = 0; - if (ctx->CreateBuffer(&desc, nullptr, &bd->pVB) < 0) - return; - } - - if (!bd->pIB || bd->IndexBufferSize < draw_data->TotalIdxCount) - { - if (bd->pIB) { bd->pIB->Release(); bd->pIB = nullptr; } - bd->IndexBufferSize = draw_data->TotalIdxCount + 10000; - D3D10_BUFFER_DESC desc; - memset(&desc, 0, sizeof(D3D10_BUFFER_DESC)); - desc.Usage = D3D10_USAGE_DYNAMIC; - desc.ByteWidth = bd->IndexBufferSize * sizeof(ImDrawIdx); - desc.BindFlags = D3D10_BIND_INDEX_BUFFER; - desc.CPUAccessFlags = D3D10_CPU_ACCESS_WRITE; - if (ctx->CreateBuffer(&desc, nullptr, &bd->pIB) < 0) - return; - } - - // Copy and convert all vertices into a single contiguous buffer - ImDrawVert* vtx_dst = nullptr; - ImDrawIdx* idx_dst = nullptr; - bd->pVB->Map(D3D10_MAP_WRITE_DISCARD, 0, (void**)&vtx_dst); - bd->pIB->Map(D3D10_MAP_WRITE_DISCARD, 0, (void**)&idx_dst); - for (int n = 0; n < draw_data->CmdListsCount; n++) - { - const ImDrawList* cmd_list = draw_data->CmdLists[n]; - memcpy(vtx_dst, cmd_list->VtxBuffer.Data, cmd_list->VtxBuffer.Size * sizeof(ImDrawVert)); - memcpy(idx_dst, cmd_list->IdxBuffer.Data, cmd_list->IdxBuffer.Size * sizeof(ImDrawIdx)); - vtx_dst += cmd_list->VtxBuffer.Size; - idx_dst += cmd_list->IdxBuffer.Size; - } - bd->pVB->Unmap(); - bd->pIB->Unmap(); - - // Setup orthographic projection matrix into our constant buffer - // Our visible imgui space lies from draw_data->DisplayPos (top left) to draw_data->DisplayPos+data_data->DisplaySize (bottom right). DisplayPos is (0,0) for single viewport apps. - { - void* mapped_resource; - if (bd->pVertexConstantBuffer->Map(D3D10_MAP_WRITE_DISCARD, 0, &mapped_resource) != S_OK) - return; - VERTEX_CONSTANT_BUFFER_DX10* constant_buffer = (VERTEX_CONSTANT_BUFFER_DX10*)mapped_resource; - float L = draw_data->DisplayPos.x; - float R = draw_data->DisplayPos.x + draw_data->DisplaySize.x; - float T = draw_data->DisplayPos.y; - float B = draw_data->DisplayPos.y + draw_data->DisplaySize.y; - float mvp[4][4] = - { - { 2.0f/(R-L), 0.0f, 0.0f, 0.0f }, - { 0.0f, 2.0f/(T-B), 0.0f, 0.0f }, - { 0.0f, 0.0f, 0.5f, 0.0f }, - { (R+L)/(L-R), (T+B)/(B-T), 0.5f, 1.0f }, - }; - memcpy(&constant_buffer->mvp, mvp, sizeof(mvp)); - bd->pVertexConstantBuffer->Unmap(); - } - - // Backup DX state that will be modified to restore it afterwards (unfortunately this is very ugly looking and verbose. Close your eyes!) - struct BACKUP_DX10_STATE - { - UINT ScissorRectsCount, ViewportsCount; - D3D10_RECT ScissorRects[D3D10_VIEWPORT_AND_SCISSORRECT_OBJECT_COUNT_PER_PIPELINE]; - D3D10_VIEWPORT Viewports[D3D10_VIEWPORT_AND_SCISSORRECT_OBJECT_COUNT_PER_PIPELINE]; - ID3D10RasterizerState* RS; - ID3D10BlendState* BlendState; - FLOAT BlendFactor[4]; - UINT SampleMask; - UINT StencilRef; - ID3D10DepthStencilState* DepthStencilState; - ID3D10ShaderResourceView* PSShaderResource; - ID3D10SamplerState* PSSampler; - ID3D10PixelShader* PS; - ID3D10VertexShader* VS; - ID3D10GeometryShader* GS; - D3D10_PRIMITIVE_TOPOLOGY PrimitiveTopology; - ID3D10Buffer* IndexBuffer, *VertexBuffer, *VSConstantBuffer; - UINT IndexBufferOffset, VertexBufferStride, VertexBufferOffset; - DXGI_FORMAT IndexBufferFormat; - ID3D10InputLayout* InputLayout; - }; - BACKUP_DX10_STATE old = {}; - old.ScissorRectsCount = old.ViewportsCount = D3D10_VIEWPORT_AND_SCISSORRECT_OBJECT_COUNT_PER_PIPELINE; - ctx->RSGetScissorRects(&old.ScissorRectsCount, old.ScissorRects); - ctx->RSGetViewports(&old.ViewportsCount, old.Viewports); - ctx->RSGetState(&old.RS); - ctx->OMGetBlendState(&old.BlendState, old.BlendFactor, &old.SampleMask); - ctx->OMGetDepthStencilState(&old.DepthStencilState, &old.StencilRef); - ctx->PSGetShaderResources(0, 1, &old.PSShaderResource); - ctx->PSGetSamplers(0, 1, &old.PSSampler); - ctx->PSGetShader(&old.PS); - ctx->VSGetShader(&old.VS); - ctx->VSGetConstantBuffers(0, 1, &old.VSConstantBuffer); - ctx->GSGetShader(&old.GS); - ctx->IAGetPrimitiveTopology(&old.PrimitiveTopology); - ctx->IAGetIndexBuffer(&old.IndexBuffer, &old.IndexBufferFormat, &old.IndexBufferOffset); - ctx->IAGetVertexBuffers(0, 1, &old.VertexBuffer, &old.VertexBufferStride, &old.VertexBufferOffset); - ctx->IAGetInputLayout(&old.InputLayout); - - // Setup desired DX state - ImGui_ImplDX10_SetupRenderState(draw_data, ctx); - - // Render command lists - // (Because we merged all buffers into a single one, we maintain our own offset into them) - int global_vtx_offset = 0; - int global_idx_offset = 0; - ImVec2 clip_off = draw_data->DisplayPos; - for (int n = 0; n < draw_data->CmdListsCount; n++) - { - const ImDrawList* cmd_list = draw_data->CmdLists[n]; - for (int cmd_i = 0; cmd_i < cmd_list->CmdBuffer.Size; cmd_i++) - { - const ImDrawCmd* pcmd = &cmd_list->CmdBuffer[cmd_i]; - if (pcmd->UserCallback) - { - // User callback, registered via ImDrawList::AddCallback() - // (ImDrawCallback_ResetRenderState is a special callback value used by the user to request the renderer to reset render state.) - if (pcmd->UserCallback == ImDrawCallback_ResetRenderState) - ImGui_ImplDX10_SetupRenderState(draw_data, ctx); - else - pcmd->UserCallback(cmd_list, pcmd); - } - else - { - // Project scissor/clipping rectangles into framebuffer space - ImVec2 clip_min(pcmd->ClipRect.x - clip_off.x, pcmd->ClipRect.y - clip_off.y); - ImVec2 clip_max(pcmd->ClipRect.z - clip_off.x, pcmd->ClipRect.w - clip_off.y); - if (clip_max.x <= clip_min.x || clip_max.y <= clip_min.y) - continue; - - // Apply scissor/clipping rectangle - const D3D10_RECT r = { (LONG)clip_min.x, (LONG)clip_min.y, (LONG)clip_max.x, (LONG)clip_max.y }; - ctx->RSSetScissorRects(1, &r); - - // Bind texture, Draw - ID3D10ShaderResourceView* texture_srv = (ID3D10ShaderResourceView*)pcmd->GetTexID(); - ctx->PSSetShaderResources(0, 1, &texture_srv); - ctx->DrawIndexed(pcmd->ElemCount, pcmd->IdxOffset + global_idx_offset, pcmd->VtxOffset + global_vtx_offset); - } - } - global_idx_offset += cmd_list->IdxBuffer.Size; - global_vtx_offset += cmd_list->VtxBuffer.Size; - } - - // Restore modified DX state - ctx->RSSetScissorRects(old.ScissorRectsCount, old.ScissorRects); - ctx->RSSetViewports(old.ViewportsCount, old.Viewports); - ctx->RSSetState(old.RS); if (old.RS) old.RS->Release(); - ctx->OMSetBlendState(old.BlendState, old.BlendFactor, old.SampleMask); if (old.BlendState) old.BlendState->Release(); - ctx->OMSetDepthStencilState(old.DepthStencilState, old.StencilRef); if (old.DepthStencilState) old.DepthStencilState->Release(); - ctx->PSSetShaderResources(0, 1, &old.PSShaderResource); if (old.PSShaderResource) old.PSShaderResource->Release(); - ctx->PSSetSamplers(0, 1, &old.PSSampler); if (old.PSSampler) old.PSSampler->Release(); - ctx->PSSetShader(old.PS); if (old.PS) old.PS->Release(); - ctx->VSSetShader(old.VS); if (old.VS) old.VS->Release(); - ctx->GSSetShader(old.GS); if (old.GS) old.GS->Release(); - ctx->VSSetConstantBuffers(0, 1, &old.VSConstantBuffer); if (old.VSConstantBuffer) old.VSConstantBuffer->Release(); - ctx->IASetPrimitiveTopology(old.PrimitiveTopology); - ctx->IASetIndexBuffer(old.IndexBuffer, old.IndexBufferFormat, old.IndexBufferOffset); if (old.IndexBuffer) old.IndexBuffer->Release(); - ctx->IASetVertexBuffers(0, 1, &old.VertexBuffer, &old.VertexBufferStride, &old.VertexBufferOffset); if (old.VertexBuffer) old.VertexBuffer->Release(); - ctx->IASetInputLayout(old.InputLayout); if (old.InputLayout) old.InputLayout->Release(); -} - -static void ImGui_ImplDX10_CreateFontsTexture() -{ - // Build texture atlas - ImGui_ImplDX10_Data* bd = ImGui_ImplDX10_GetBackendData(); - ImGuiIO& io = ImGui::GetIO(); - unsigned char* pixels; - int width, height; - io.Fonts->GetTexDataAsRGBA32(&pixels, &width, &height); - - // Upload texture to graphics system - { - D3D10_TEXTURE2D_DESC desc; - ZeroMemory(&desc, sizeof(desc)); - desc.Width = width; - desc.Height = height; - desc.MipLevels = 1; - desc.ArraySize = 1; - desc.Format = DXGI_FORMAT_R8G8B8A8_UNORM; - desc.SampleDesc.Count = 1; - desc.Usage = D3D10_USAGE_DEFAULT; - desc.BindFlags = D3D10_BIND_SHADER_RESOURCE; - desc.CPUAccessFlags = 0; - - ID3D10Texture2D* pTexture = nullptr; - D3D10_SUBRESOURCE_DATA subResource; - subResource.pSysMem = pixels; - subResource.SysMemPitch = desc.Width * 4; - subResource.SysMemSlicePitch = 0; - bd->pd3dDevice->CreateTexture2D(&desc, &subResource, &pTexture); - IM_ASSERT(pTexture != nullptr); - - // Create texture view - D3D10_SHADER_RESOURCE_VIEW_DESC srv_desc; - ZeroMemory(&srv_desc, sizeof(srv_desc)); - srv_desc.Format = DXGI_FORMAT_R8G8B8A8_UNORM; - srv_desc.ViewDimension = D3D10_SRV_DIMENSION_TEXTURE2D; - srv_desc.Texture2D.MipLevels = desc.MipLevels; - srv_desc.Texture2D.MostDetailedMip = 0; - bd->pd3dDevice->CreateShaderResourceView(pTexture, &srv_desc, &bd->pFontTextureView); - pTexture->Release(); - } - - // Store our identifier - io.Fonts->SetTexID((ImTextureID)bd->pFontTextureView); - - // Create texture sampler - // (Bilinear sampling is required by default. Set 'io.Fonts->Flags |= ImFontAtlasFlags_NoBakedLines' or 'style.AntiAliasedLinesUseTex = false' to allow point/nearest sampling) - { - D3D10_SAMPLER_DESC desc; - ZeroMemory(&desc, sizeof(desc)); - desc.Filter = D3D10_FILTER_MIN_MAG_MIP_LINEAR; - desc.AddressU = D3D10_TEXTURE_ADDRESS_WRAP; - desc.AddressV = D3D10_TEXTURE_ADDRESS_WRAP; - desc.AddressW = D3D10_TEXTURE_ADDRESS_WRAP; - desc.MipLODBias = 0.f; - desc.ComparisonFunc = D3D10_COMPARISON_ALWAYS; - desc.MinLOD = 0.f; - desc.MaxLOD = 0.f; - bd->pd3dDevice->CreateSamplerState(&desc, &bd->pFontSampler); - } -} - -bool ImGui_ImplDX10_CreateDeviceObjects() -{ - ImGui_ImplDX10_Data* bd = ImGui_ImplDX10_GetBackendData(); - if (!bd->pd3dDevice) - return false; - if (bd->pFontSampler) - ImGui_ImplDX10_InvalidateDeviceObjects(); - - // By using D3DCompile() from / d3dcompiler.lib, we introduce a dependency to a given version of d3dcompiler_XX.dll (see D3DCOMPILER_DLL_A) - // If you would like to use this DX10 sample code but remove this dependency you can: - // 1) compile once, save the compiled shader blobs into a file or source code and pass them to CreateVertexShader()/CreatePixelShader() [preferred solution] - // 2) use code to detect any version of the DLL and grab a pointer to D3DCompile from the DLL. - // See https://github.com/ocornut/imgui/pull/638 for sources and details. - - // Create the vertex shader - { - static const char* vertexShader = - "cbuffer vertexBuffer : register(b0) \ - {\ - float4x4 ProjectionMatrix; \ - };\ - struct VS_INPUT\ - {\ - float2 pos : POSITION;\ - float4 col : COLOR0;\ - float2 uv : TEXCOORD0;\ - };\ - \ - struct PS_INPUT\ - {\ - float4 pos : SV_POSITION;\ - float4 col : COLOR0;\ - float2 uv : TEXCOORD0;\ - };\ - \ - PS_INPUT main(VS_INPUT input)\ - {\ - PS_INPUT output;\ - output.pos = mul( ProjectionMatrix, float4(input.pos.xy, 0.f, 1.f));\ - output.col = input.col;\ - output.uv = input.uv;\ - return output;\ - }"; - - ID3DBlob* vertexShaderBlob; - if (FAILED(D3DCompile(vertexShader, strlen(vertexShader), nullptr, nullptr, nullptr, "main", "vs_4_0", 0, 0, &vertexShaderBlob, nullptr))) - return false; // NB: Pass ID3DBlob* pErrorBlob to D3DCompile() to get error showing in (const char*)pErrorBlob->GetBufferPointer(). Make sure to Release() the blob! - if (bd->pd3dDevice->CreateVertexShader(vertexShaderBlob->GetBufferPointer(), vertexShaderBlob->GetBufferSize(), &bd->pVertexShader) != S_OK) - { - vertexShaderBlob->Release(); - return false; - } - - // Create the input layout - D3D10_INPUT_ELEMENT_DESC local_layout[] = - { - { "POSITION", 0, DXGI_FORMAT_R32G32_FLOAT, 0, (UINT)IM_OFFSETOF(ImDrawVert, pos), D3D10_INPUT_PER_VERTEX_DATA, 0 }, - { "TEXCOORD", 0, DXGI_FORMAT_R32G32_FLOAT, 0, (UINT)IM_OFFSETOF(ImDrawVert, uv), D3D10_INPUT_PER_VERTEX_DATA, 0 }, - { "COLOR", 0, DXGI_FORMAT_R8G8B8A8_UNORM, 0, (UINT)IM_OFFSETOF(ImDrawVert, col), D3D10_INPUT_PER_VERTEX_DATA, 0 }, - }; - if (bd->pd3dDevice->CreateInputLayout(local_layout, 3, vertexShaderBlob->GetBufferPointer(), vertexShaderBlob->GetBufferSize(), &bd->pInputLayout) != S_OK) - { - vertexShaderBlob->Release(); - return false; - } - vertexShaderBlob->Release(); - - // Create the constant buffer - { - D3D10_BUFFER_DESC desc; - desc.ByteWidth = sizeof(VERTEX_CONSTANT_BUFFER_DX10); - desc.Usage = D3D10_USAGE_DYNAMIC; - desc.BindFlags = D3D10_BIND_CONSTANT_BUFFER; - desc.CPUAccessFlags = D3D10_CPU_ACCESS_WRITE; - desc.MiscFlags = 0; - bd->pd3dDevice->CreateBuffer(&desc, nullptr, &bd->pVertexConstantBuffer); - } - } - - // Create the pixel shader - { - static const char* pixelShader = - "struct PS_INPUT\ - {\ - float4 pos : SV_POSITION;\ - float4 col : COLOR0;\ - float2 uv : TEXCOORD0;\ - };\ - sampler sampler0;\ - Texture2D texture0;\ - \ - float4 main(PS_INPUT input) : SV_Target\ - {\ - float4 out_col = input.col * texture0.Sample(sampler0, input.uv); \ - return out_col; \ - }"; - - ID3DBlob* pixelShaderBlob; - if (FAILED(D3DCompile(pixelShader, strlen(pixelShader), nullptr, nullptr, nullptr, "main", "ps_4_0", 0, 0, &pixelShaderBlob, nullptr))) - return false; // NB: Pass ID3DBlob* pErrorBlob to D3DCompile() to get error showing in (const char*)pErrorBlob->GetBufferPointer(). Make sure to Release() the blob! - if (bd->pd3dDevice->CreatePixelShader(pixelShaderBlob->GetBufferPointer(), pixelShaderBlob->GetBufferSize(), &bd->pPixelShader) != S_OK) - { - pixelShaderBlob->Release(); - return false; - } - pixelShaderBlob->Release(); - } - - // Create the blending setup - { - D3D10_BLEND_DESC desc; - ZeroMemory(&desc, sizeof(desc)); - desc.AlphaToCoverageEnable = false; - desc.BlendEnable[0] = true; - desc.SrcBlend = D3D10_BLEND_SRC_ALPHA; - desc.DestBlend = D3D10_BLEND_INV_SRC_ALPHA; - desc.BlendOp = D3D10_BLEND_OP_ADD; - desc.SrcBlendAlpha = D3D10_BLEND_ONE; - desc.DestBlendAlpha = D3D10_BLEND_INV_SRC_ALPHA; - desc.BlendOpAlpha = D3D10_BLEND_OP_ADD; - desc.RenderTargetWriteMask[0] = D3D10_COLOR_WRITE_ENABLE_ALL; - bd->pd3dDevice->CreateBlendState(&desc, &bd->pBlendState); - } - - // Create the rasterizer state - { - D3D10_RASTERIZER_DESC desc; - ZeroMemory(&desc, sizeof(desc)); - desc.FillMode = D3D10_FILL_SOLID; - desc.CullMode = D3D10_CULL_NONE; - desc.ScissorEnable = true; - desc.DepthClipEnable = true; - bd->pd3dDevice->CreateRasterizerState(&desc, &bd->pRasterizerState); - } - - // Create depth-stencil State - { - D3D10_DEPTH_STENCIL_DESC desc; - ZeroMemory(&desc, sizeof(desc)); - desc.DepthEnable = false; - desc.DepthWriteMask = D3D10_DEPTH_WRITE_MASK_ALL; - desc.DepthFunc = D3D10_COMPARISON_ALWAYS; - desc.StencilEnable = false; - desc.FrontFace.StencilFailOp = desc.FrontFace.StencilDepthFailOp = desc.FrontFace.StencilPassOp = D3D10_STENCIL_OP_KEEP; - desc.FrontFace.StencilFunc = D3D10_COMPARISON_ALWAYS; - desc.BackFace = desc.FrontFace; - bd->pd3dDevice->CreateDepthStencilState(&desc, &bd->pDepthStencilState); - } - - ImGui_ImplDX10_CreateFontsTexture(); - - return true; -} - -void ImGui_ImplDX10_InvalidateDeviceObjects() -{ - ImGui_ImplDX10_Data* bd = ImGui_ImplDX10_GetBackendData(); - if (!bd->pd3dDevice) - return; - - if (bd->pFontSampler) { bd->pFontSampler->Release(); bd->pFontSampler = nullptr; } - if (bd->pFontTextureView) { bd->pFontTextureView->Release(); bd->pFontTextureView = nullptr; ImGui::GetIO().Fonts->SetTexID(0); } // We copied bd->pFontTextureView to io.Fonts->TexID so let's clear that as well. - if (bd->pIB) { bd->pIB->Release(); bd->pIB = nullptr; } - if (bd->pVB) { bd->pVB->Release(); bd->pVB = nullptr; } - if (bd->pBlendState) { bd->pBlendState->Release(); bd->pBlendState = nullptr; } - if (bd->pDepthStencilState) { bd->pDepthStencilState->Release(); bd->pDepthStencilState = nullptr; } - if (bd->pRasterizerState) { bd->pRasterizerState->Release(); bd->pRasterizerState = nullptr; } - if (bd->pPixelShader) { bd->pPixelShader->Release(); bd->pPixelShader = nullptr; } - if (bd->pVertexConstantBuffer) { bd->pVertexConstantBuffer->Release(); bd->pVertexConstantBuffer = nullptr; } - if (bd->pInputLayout) { bd->pInputLayout->Release(); bd->pInputLayout = nullptr; } - if (bd->pVertexShader) { bd->pVertexShader->Release(); bd->pVertexShader = nullptr; } -} - -bool ImGui_ImplDX10_Init(ID3D10Device* device) -{ - ImGuiIO& io = ImGui::GetIO(); - IM_ASSERT(io.BackendRendererUserData == nullptr && "Already initialized a renderer backend!"); - - // Setup backend capabilities flags - ImGui_ImplDX10_Data* bd = IM_NEW(ImGui_ImplDX10_Data)(); - io.BackendRendererUserData = (void*)bd; - io.BackendRendererName = "imgui_impl_dx10"; - io.BackendFlags |= ImGuiBackendFlags_RendererHasVtxOffset; // We can honor the ImDrawCmd::VtxOffset field, allowing for large meshes. - io.BackendFlags |= ImGuiBackendFlags_RendererHasViewports; // We can create multi-viewports on the Renderer side (optional) - - // Get factory from device - IDXGIDevice* pDXGIDevice = nullptr; - IDXGIAdapter* pDXGIAdapter = nullptr; - IDXGIFactory* pFactory = nullptr; - if (device->QueryInterface(IID_PPV_ARGS(&pDXGIDevice)) == S_OK) - if (pDXGIDevice->GetParent(IID_PPV_ARGS(&pDXGIAdapter)) == S_OK) - if (pDXGIAdapter->GetParent(IID_PPV_ARGS(&pFactory)) == S_OK) - { - bd->pd3dDevice = device; - bd->pFactory = pFactory; - } - if (pDXGIDevice) pDXGIDevice->Release(); - if (pDXGIAdapter) pDXGIAdapter->Release(); - bd->pd3dDevice->AddRef(); - - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - ImGui_ImplDX10_InitPlatformInterface(); - return true; -} - -void ImGui_ImplDX10_Shutdown() -{ - ImGui_ImplDX10_Data* bd = ImGui_ImplDX10_GetBackendData(); - IM_ASSERT(bd != nullptr && "No renderer backend to shutdown, or already shutdown?"); - ImGuiIO& io = ImGui::GetIO(); - - ImGui_ImplDX10_ShutdownPlatformInterface(); - ImGui_ImplDX10_InvalidateDeviceObjects(); - if (bd->pFactory) { bd->pFactory->Release(); } - if (bd->pd3dDevice) { bd->pd3dDevice->Release(); } - io.BackendRendererName = nullptr; - io.BackendRendererUserData = nullptr; - io.BackendFlags &= ~(ImGuiBackendFlags_RendererHasVtxOffset | ImGuiBackendFlags_RendererHasViewports); - IM_DELETE(bd); -} - -void ImGui_ImplDX10_NewFrame() -{ - ImGui_ImplDX10_Data* bd = ImGui_ImplDX10_GetBackendData(); - IM_ASSERT(bd != nullptr && "Did you call ImGui_ImplDX10_Init()?"); - - if (!bd->pFontSampler) - ImGui_ImplDX10_CreateDeviceObjects(); -} - -//-------------------------------------------------------------------------------------------------------- -// MULTI-VIEWPORT / PLATFORM INTERFACE SUPPORT -// This is an _advanced_ and _optional_ feature, allowing the backend to create and handle multiple viewports simultaneously. -// If you are new to dear imgui or creating a new binding for dear imgui, it is recommended that you completely ignore this section first.. -//-------------------------------------------------------------------------------------------------------- - -// Helper structure we store in the void* RendererUserData field of each ImGuiViewport to easily retrieve our backend data. -struct ImGui_ImplDX10_ViewportData -{ - IDXGISwapChain* SwapChain; - ID3D10RenderTargetView* RTView; - - ImGui_ImplDX10_ViewportData() { SwapChain = nullptr; RTView = nullptr; } - ~ImGui_ImplDX10_ViewportData() { IM_ASSERT(SwapChain == nullptr && RTView == nullptr); } -}; - -static void ImGui_ImplDX10_CreateWindow(ImGuiViewport* viewport) -{ - ImGui_ImplDX10_Data* bd = ImGui_ImplDX10_GetBackendData(); - ImGui_ImplDX10_ViewportData* vd = IM_NEW(ImGui_ImplDX10_ViewportData)(); - viewport->RendererUserData = vd; - - // PlatformHandleRaw should always be a HWND, whereas PlatformHandle might be a higher-level handle (e.g. GLFWWindow*, SDL_Window*). - // Some backends will leave PlatformHandleRaw == 0, in which case we assume PlatformHandle will contain the HWND. - HWND hwnd = viewport->PlatformHandleRaw ? (HWND)viewport->PlatformHandleRaw : (HWND)viewport->PlatformHandle; - IM_ASSERT(hwnd != 0); - - // Create swap chain - DXGI_SWAP_CHAIN_DESC sd; - ZeroMemory(&sd, sizeof(sd)); - sd.BufferDesc.Width = (UINT)viewport->Size.x; - sd.BufferDesc.Height = (UINT)viewport->Size.y; - sd.BufferDesc.Format = DXGI_FORMAT_R8G8B8A8_UNORM; - sd.SampleDesc.Count = 1; - sd.SampleDesc.Quality = 0; - sd.BufferUsage = DXGI_USAGE_RENDER_TARGET_OUTPUT; - sd.BufferCount = 1; - sd.OutputWindow = hwnd; - sd.Windowed = TRUE; - sd.SwapEffect = DXGI_SWAP_EFFECT_DISCARD; - sd.Flags = 0; - - IM_ASSERT(vd->SwapChain == nullptr && vd->RTView == nullptr); - bd->pFactory->CreateSwapChain(bd->pd3dDevice, &sd, &vd->SwapChain); - - // Create the render target - if (vd->SwapChain) - { - ID3D10Texture2D* pBackBuffer; - vd->SwapChain->GetBuffer(0, IID_PPV_ARGS(&pBackBuffer)); - bd->pd3dDevice->CreateRenderTargetView(pBackBuffer, nullptr, &vd->RTView); - pBackBuffer->Release(); - } -} - -static void ImGui_ImplDX10_DestroyWindow(ImGuiViewport* viewport) -{ - // The main viewport (owned by the application) will always have RendererUserData == 0 here since we didn't create the data for it. - if (ImGui_ImplDX10_ViewportData* vd = (ImGui_ImplDX10_ViewportData*)viewport->RendererUserData) - { - if (vd->SwapChain) - vd->SwapChain->Release(); - vd->SwapChain = nullptr; - if (vd->RTView) - vd->RTView->Release(); - vd->RTView = nullptr; - IM_DELETE(vd); - } - viewport->RendererUserData = nullptr; -} - -static void ImGui_ImplDX10_SetWindowSize(ImGuiViewport* viewport, ImVec2 size) -{ - ImGui_ImplDX10_Data* bd = ImGui_ImplDX10_GetBackendData(); - ImGui_ImplDX10_ViewportData* vd = (ImGui_ImplDX10_ViewportData*)viewport->RendererUserData; - if (vd->RTView) - { - vd->RTView->Release(); - vd->RTView = nullptr; - } - if (vd->SwapChain) - { - ID3D10Texture2D* pBackBuffer = nullptr; - vd->SwapChain->ResizeBuffers(0, (UINT)size.x, (UINT)size.y, DXGI_FORMAT_UNKNOWN, 0); - vd->SwapChain->GetBuffer(0, IID_PPV_ARGS(&pBackBuffer)); - if (pBackBuffer == nullptr) { fprintf(stderr, "ImGui_ImplDX10_SetWindowSize() failed creating buffers.\n"); return; } - bd->pd3dDevice->CreateRenderTargetView(pBackBuffer, nullptr, &vd->RTView); - pBackBuffer->Release(); - } -} - -static void ImGui_ImplDX10_RenderViewport(ImGuiViewport* viewport, void*) -{ - ImGui_ImplDX10_Data* bd = ImGui_ImplDX10_GetBackendData(); - ImGui_ImplDX10_ViewportData* vd = (ImGui_ImplDX10_ViewportData*)viewport->RendererUserData; - ImVec4 clear_color = ImVec4(0.0f, 0.0f, 0.0f, 1.0f); - bd->pd3dDevice->OMSetRenderTargets(1, &vd->RTView, nullptr); - if (!(viewport->Flags & ImGuiViewportFlags_NoRendererClear)) - bd->pd3dDevice->ClearRenderTargetView(vd->RTView, (float*)&clear_color); - ImGui_ImplDX10_RenderDrawData(viewport->DrawData); -} - -static void ImGui_ImplDX10_SwapBuffers(ImGuiViewport* viewport, void*) -{ - ImGui_ImplDX10_ViewportData* vd = (ImGui_ImplDX10_ViewportData*)viewport->RendererUserData; - vd->SwapChain->Present(0, 0); // Present without vsync -} - -void ImGui_ImplDX10_InitPlatformInterface() -{ - ImGuiPlatformIO& platform_io = ImGui::GetPlatformIO(); - platform_io.Renderer_CreateWindow = ImGui_ImplDX10_CreateWindow; - platform_io.Renderer_DestroyWindow = ImGui_ImplDX10_DestroyWindow; - platform_io.Renderer_SetWindowSize = ImGui_ImplDX10_SetWindowSize; - platform_io.Renderer_RenderWindow = ImGui_ImplDX10_RenderViewport; - platform_io.Renderer_SwapBuffers = ImGui_ImplDX10_SwapBuffers; -} - -void ImGui_ImplDX10_ShutdownPlatformInterface() -{ - ImGui::DestroyPlatformWindows(); -} - -//----------------------------------------------------------------------------- - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_dx10.h b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_dx10.h deleted file mode 100644 index 39259bd..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_dx10.h +++ /dev/null @@ -1,32 +0,0 @@ -// dear imgui: Renderer Backend for DirectX10 -// This needs to be used along with a Platform Backend (e.g. Win32) - -// Implemented features: -// [X] Renderer: User texture binding. Use 'ID3D10ShaderResourceView*' as ImTextureID. Read the FAQ about ImTextureID! -// [X] Renderer: Large meshes support (64k+ vertices) with 16-bit indices. -// [X] Renderer: Multi-viewport support (multiple windows). Enable with 'io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable'. - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#pragma once -#include "imgui.h" // IMGUI_IMPL_API -#ifndef IMGUI_DISABLE - -struct ID3D10Device; - -IMGUI_IMPL_API bool ImGui_ImplDX10_Init(ID3D10Device* device); -IMGUI_IMPL_API void ImGui_ImplDX10_Shutdown(); -IMGUI_IMPL_API void ImGui_ImplDX10_NewFrame(); -IMGUI_IMPL_API void ImGui_ImplDX10_RenderDrawData(ImDrawData* draw_data); - -// Use if you want to reset your rendering device without losing Dear ImGui state. -IMGUI_IMPL_API void ImGui_ImplDX10_InvalidateDeviceObjects(); -IMGUI_IMPL_API bool ImGui_ImplDX10_CreateDeviceObjects(); - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_dx11.cpp b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_dx11.cpp deleted file mode 100644 index f2b20e4..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_dx11.cpp +++ /dev/null @@ -1,739 +0,0 @@ -// dear imgui: Renderer Backend for DirectX11 -// This needs to be used along with a Platform Backend (e.g. Win32) - -// Implemented features: -// [X] Renderer: User texture binding. Use 'ID3D11ShaderResourceView*' as ImTextureID. Read the FAQ about ImTextureID! -// [X] Renderer: Large meshes support (64k+ vertices) with 16-bit indices. -// [X] Renderer: Multi-viewport support (multiple windows). Enable with 'io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable'. - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -// CHANGELOG -// (minor and older changes stripped away, please see git history for details) -// 2023-XX-XX: Platform: Added support for multiple windows via the ImGuiPlatformIO interface. -// 2022-10-11: Using 'nullptr' instead of 'NULL' as per our switch to C++11. -// 2021-06-29: Reorganized backend to pull data from a single structure to facilitate usage with multiple-contexts (all g_XXXX access changed to bd->XXXX). -// 2021-05-19: DirectX11: Replaced direct access to ImDrawCmd::TextureId with a call to ImDrawCmd::GetTexID(). (will become a requirement) -// 2021-02-18: DirectX11: Change blending equation to preserve alpha in output buffer. -// 2019-08-01: DirectX11: Fixed code querying the Geometry Shader state (would generally error with Debug layer enabled). -// 2019-07-21: DirectX11: Backup, clear and restore Geometry Shader is any is bound when calling ImGui_ImplDX10_RenderDrawData. Clearing Hull/Domain/Compute shaders without backup/restore. -// 2019-05-29: DirectX11: Added support for large mesh (64K+ vertices), enable ImGuiBackendFlags_RendererHasVtxOffset flag. -// 2019-04-30: DirectX11: Added support for special ImDrawCallback_ResetRenderState callback to reset render state. -// 2018-12-03: Misc: Added #pragma comment statement to automatically link with d3dcompiler.lib when using D3DCompile(). -// 2018-11-30: Misc: Setting up io.BackendRendererName so it can be displayed in the About Window. -// 2018-08-01: DirectX11: Querying for IDXGIFactory instead of IDXGIFactory1 to increase compatibility. -// 2018-07-13: DirectX11: Fixed unreleased resources in Init and Shutdown functions. -// 2018-06-08: Misc: Extracted imgui_impl_dx11.cpp/.h away from the old combined DX11+Win32 example. -// 2018-06-08: DirectX11: Use draw_data->DisplayPos and draw_data->DisplaySize to setup projection matrix and clipping rectangle. -// 2018-02-16: Misc: Obsoleted the io.RenderDrawListsFn callback and exposed ImGui_ImplDX11_RenderDrawData() in the .h file so you can call it yourself. -// 2018-02-06: Misc: Removed call to ImGui::Shutdown() which is not available from 1.60 WIP, user needs to call CreateContext/DestroyContext themselves. -// 2016-05-07: DirectX11: Disabling depth-write. - -#include "imgui.h" -#ifndef IMGUI_DISABLE -#include "imgui_impl_dx11.h" - -// DirectX -#include -#include -#include -#ifdef _MSC_VER -#pragma comment(lib, "d3dcompiler") // Automatically link with d3dcompiler.lib as we are using D3DCompile() below. -#endif - -// DirectX11 data -struct ImGui_ImplDX11_Data -{ - ID3D11Device* pd3dDevice; - ID3D11DeviceContext* pd3dDeviceContext; - IDXGIFactory* pFactory; - ID3D11Buffer* pVB; - ID3D11Buffer* pIB; - ID3D11VertexShader* pVertexShader; - ID3D11InputLayout* pInputLayout; - ID3D11Buffer* pVertexConstantBuffer; - ID3D11PixelShader* pPixelShader; - ID3D11SamplerState* pFontSampler; - ID3D11ShaderResourceView* pFontTextureView; - ID3D11RasterizerState* pRasterizerState; - ID3D11BlendState* pBlendState; - ID3D11DepthStencilState* pDepthStencilState; - int VertexBufferSize; - int IndexBufferSize; - - ImGui_ImplDX11_Data() { memset((void*)this, 0, sizeof(*this)); VertexBufferSize = 5000; IndexBufferSize = 10000; } -}; - -struct VERTEX_CONSTANT_BUFFER_DX11 -{ - float mvp[4][4]; -}; - -// Backend data stored in io.BackendRendererUserData to allow support for multiple Dear ImGui contexts -// It is STRONGLY preferred that you use docking branch with multi-viewports (== single Dear ImGui context + multiple windows) instead of multiple Dear ImGui contexts. -static ImGui_ImplDX11_Data* ImGui_ImplDX11_GetBackendData() -{ - return ImGui::GetCurrentContext() ? (ImGui_ImplDX11_Data*)ImGui::GetIO().BackendRendererUserData : nullptr; -} - -// Forward Declarations -static void ImGui_ImplDX11_InitPlatformInterface(); -static void ImGui_ImplDX11_ShutdownPlatformInterface(); - -// Functions -static void ImGui_ImplDX11_SetupRenderState(ImDrawData* draw_data, ID3D11DeviceContext* ctx) -{ - ImGui_ImplDX11_Data* bd = ImGui_ImplDX11_GetBackendData(); - - // Setup viewport - D3D11_VIEWPORT vp; - memset(&vp, 0, sizeof(D3D11_VIEWPORT)); - vp.Width = draw_data->DisplaySize.x; - vp.Height = draw_data->DisplaySize.y; - vp.MinDepth = 0.0f; - vp.MaxDepth = 1.0f; - vp.TopLeftX = vp.TopLeftY = 0; - ctx->RSSetViewports(1, &vp); - - // Setup shader and vertex buffers - unsigned int stride = sizeof(ImDrawVert); - unsigned int offset = 0; - ctx->IASetInputLayout(bd->pInputLayout); - ctx->IASetVertexBuffers(0, 1, &bd->pVB, &stride, &offset); - ctx->IASetIndexBuffer(bd->pIB, sizeof(ImDrawIdx) == 2 ? DXGI_FORMAT_R16_UINT : DXGI_FORMAT_R32_UINT, 0); - ctx->IASetPrimitiveTopology(D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST); - ctx->VSSetShader(bd->pVertexShader, nullptr, 0); - ctx->VSSetConstantBuffers(0, 1, &bd->pVertexConstantBuffer); - ctx->PSSetShader(bd->pPixelShader, nullptr, 0); - ctx->PSSetSamplers(0, 1, &bd->pFontSampler); - ctx->GSSetShader(nullptr, nullptr, 0); - ctx->HSSetShader(nullptr, nullptr, 0); // In theory we should backup and restore this as well.. very infrequently used.. - ctx->DSSetShader(nullptr, nullptr, 0); // In theory we should backup and restore this as well.. very infrequently used.. - ctx->CSSetShader(nullptr, nullptr, 0); // In theory we should backup and restore this as well.. very infrequently used.. - - // Setup blend state - const float blend_factor[4] = { 0.f, 0.f, 0.f, 0.f }; - ctx->OMSetBlendState(bd->pBlendState, blend_factor, 0xffffffff); - ctx->OMSetDepthStencilState(bd->pDepthStencilState, 0); - ctx->RSSetState(bd->pRasterizerState); -} - -// Render function -void ImGui_ImplDX11_RenderDrawData(ImDrawData* draw_data) -{ - // Avoid rendering when minimized - if (draw_data->DisplaySize.x <= 0.0f || draw_data->DisplaySize.y <= 0.0f) - return; - - ImGui_ImplDX11_Data* bd = ImGui_ImplDX11_GetBackendData(); - ID3D11DeviceContext* ctx = bd->pd3dDeviceContext; - - // Create and grow vertex/index buffers if needed - if (!bd->pVB || bd->VertexBufferSize < draw_data->TotalVtxCount) - { - if (bd->pVB) { bd->pVB->Release(); bd->pVB = nullptr; } - bd->VertexBufferSize = draw_data->TotalVtxCount + 5000; - D3D11_BUFFER_DESC desc; - memset(&desc, 0, sizeof(D3D11_BUFFER_DESC)); - desc.Usage = D3D11_USAGE_DYNAMIC; - desc.ByteWidth = bd->VertexBufferSize * sizeof(ImDrawVert); - desc.BindFlags = D3D11_BIND_VERTEX_BUFFER; - desc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE; - desc.MiscFlags = 0; - if (bd->pd3dDevice->CreateBuffer(&desc, nullptr, &bd->pVB) < 0) - return; - } - if (!bd->pIB || bd->IndexBufferSize < draw_data->TotalIdxCount) - { - if (bd->pIB) { bd->pIB->Release(); bd->pIB = nullptr; } - bd->IndexBufferSize = draw_data->TotalIdxCount + 10000; - D3D11_BUFFER_DESC desc; - memset(&desc, 0, sizeof(D3D11_BUFFER_DESC)); - desc.Usage = D3D11_USAGE_DYNAMIC; - desc.ByteWidth = bd->IndexBufferSize * sizeof(ImDrawIdx); - desc.BindFlags = D3D11_BIND_INDEX_BUFFER; - desc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE; - if (bd->pd3dDevice->CreateBuffer(&desc, nullptr, &bd->pIB) < 0) - return; - } - - // Upload vertex/index data into a single contiguous GPU buffer - D3D11_MAPPED_SUBRESOURCE vtx_resource, idx_resource; - if (ctx->Map(bd->pVB, 0, D3D11_MAP_WRITE_DISCARD, 0, &vtx_resource) != S_OK) - return; - if (ctx->Map(bd->pIB, 0, D3D11_MAP_WRITE_DISCARD, 0, &idx_resource) != S_OK) - return; - ImDrawVert* vtx_dst = (ImDrawVert*)vtx_resource.pData; - ImDrawIdx* idx_dst = (ImDrawIdx*)idx_resource.pData; - for (int n = 0; n < draw_data->CmdListsCount; n++) - { - const ImDrawList* cmd_list = draw_data->CmdLists[n]; - memcpy(vtx_dst, cmd_list->VtxBuffer.Data, cmd_list->VtxBuffer.Size * sizeof(ImDrawVert)); - memcpy(idx_dst, cmd_list->IdxBuffer.Data, cmd_list->IdxBuffer.Size * sizeof(ImDrawIdx)); - vtx_dst += cmd_list->VtxBuffer.Size; - idx_dst += cmd_list->IdxBuffer.Size; - } - ctx->Unmap(bd->pVB, 0); - ctx->Unmap(bd->pIB, 0); - - // Setup orthographic projection matrix into our constant buffer - // Our visible imgui space lies from draw_data->DisplayPos (top left) to draw_data->DisplayPos+data_data->DisplaySize (bottom right). DisplayPos is (0,0) for single viewport apps. - { - D3D11_MAPPED_SUBRESOURCE mapped_resource; - if (ctx->Map(bd->pVertexConstantBuffer, 0, D3D11_MAP_WRITE_DISCARD, 0, &mapped_resource) != S_OK) - return; - VERTEX_CONSTANT_BUFFER_DX11* constant_buffer = (VERTEX_CONSTANT_BUFFER_DX11*)mapped_resource.pData; - float L = draw_data->DisplayPos.x; - float R = draw_data->DisplayPos.x + draw_data->DisplaySize.x; - float T = draw_data->DisplayPos.y; - float B = draw_data->DisplayPos.y + draw_data->DisplaySize.y; - float mvp[4][4] = - { - { 2.0f/(R-L), 0.0f, 0.0f, 0.0f }, - { 0.0f, 2.0f/(T-B), 0.0f, 0.0f }, - { 0.0f, 0.0f, 0.5f, 0.0f }, - { (R+L)/(L-R), (T+B)/(B-T), 0.5f, 1.0f }, - }; - memcpy(&constant_buffer->mvp, mvp, sizeof(mvp)); - ctx->Unmap(bd->pVertexConstantBuffer, 0); - } - - // Backup DX state that will be modified to restore it afterwards (unfortunately this is very ugly looking and verbose. Close your eyes!) - struct BACKUP_DX11_STATE - { - UINT ScissorRectsCount, ViewportsCount; - D3D11_RECT ScissorRects[D3D11_VIEWPORT_AND_SCISSORRECT_OBJECT_COUNT_PER_PIPELINE]; - D3D11_VIEWPORT Viewports[D3D11_VIEWPORT_AND_SCISSORRECT_OBJECT_COUNT_PER_PIPELINE]; - ID3D11RasterizerState* RS; - ID3D11BlendState* BlendState; - FLOAT BlendFactor[4]; - UINT SampleMask; - UINT StencilRef; - ID3D11DepthStencilState* DepthStencilState; - ID3D11ShaderResourceView* PSShaderResource; - ID3D11SamplerState* PSSampler; - ID3D11PixelShader* PS; - ID3D11VertexShader* VS; - ID3D11GeometryShader* GS; - UINT PSInstancesCount, VSInstancesCount, GSInstancesCount; - ID3D11ClassInstance *PSInstances[256], *VSInstances[256], *GSInstances[256]; // 256 is max according to PSSetShader documentation - D3D11_PRIMITIVE_TOPOLOGY PrimitiveTopology; - ID3D11Buffer* IndexBuffer, *VertexBuffer, *VSConstantBuffer; - UINT IndexBufferOffset, VertexBufferStride, VertexBufferOffset; - DXGI_FORMAT IndexBufferFormat; - ID3D11InputLayout* InputLayout; - }; - BACKUP_DX11_STATE old = {}; - old.ScissorRectsCount = old.ViewportsCount = D3D11_VIEWPORT_AND_SCISSORRECT_OBJECT_COUNT_PER_PIPELINE; - ctx->RSGetScissorRects(&old.ScissorRectsCount, old.ScissorRects); - ctx->RSGetViewports(&old.ViewportsCount, old.Viewports); - ctx->RSGetState(&old.RS); - ctx->OMGetBlendState(&old.BlendState, old.BlendFactor, &old.SampleMask); - ctx->OMGetDepthStencilState(&old.DepthStencilState, &old.StencilRef); - ctx->PSGetShaderResources(0, 1, &old.PSShaderResource); - ctx->PSGetSamplers(0, 1, &old.PSSampler); - old.PSInstancesCount = old.VSInstancesCount = old.GSInstancesCount = 256; - ctx->PSGetShader(&old.PS, old.PSInstances, &old.PSInstancesCount); - ctx->VSGetShader(&old.VS, old.VSInstances, &old.VSInstancesCount); - ctx->VSGetConstantBuffers(0, 1, &old.VSConstantBuffer); - ctx->GSGetShader(&old.GS, old.GSInstances, &old.GSInstancesCount); - - ctx->IAGetPrimitiveTopology(&old.PrimitiveTopology); - ctx->IAGetIndexBuffer(&old.IndexBuffer, &old.IndexBufferFormat, &old.IndexBufferOffset); - ctx->IAGetVertexBuffers(0, 1, &old.VertexBuffer, &old.VertexBufferStride, &old.VertexBufferOffset); - ctx->IAGetInputLayout(&old.InputLayout); - - // Setup desired DX state - ImGui_ImplDX11_SetupRenderState(draw_data, ctx); - - // Render command lists - // (Because we merged all buffers into a single one, we maintain our own offset into them) - int global_idx_offset = 0; - int global_vtx_offset = 0; - ImVec2 clip_off = draw_data->DisplayPos; - for (int n = 0; n < draw_data->CmdListsCount; n++) - { - const ImDrawList* cmd_list = draw_data->CmdLists[n]; - for (int cmd_i = 0; cmd_i < cmd_list->CmdBuffer.Size; cmd_i++) - { - const ImDrawCmd* pcmd = &cmd_list->CmdBuffer[cmd_i]; - if (pcmd->UserCallback != nullptr) - { - // User callback, registered via ImDrawList::AddCallback() - // (ImDrawCallback_ResetRenderState is a special callback value used by the user to request the renderer to reset render state.) - if (pcmd->UserCallback == ImDrawCallback_ResetRenderState) - ImGui_ImplDX11_SetupRenderState(draw_data, ctx); - else - pcmd->UserCallback(cmd_list, pcmd); - } - else - { - // Project scissor/clipping rectangles into framebuffer space - ImVec2 clip_min(pcmd->ClipRect.x - clip_off.x, pcmd->ClipRect.y - clip_off.y); - ImVec2 clip_max(pcmd->ClipRect.z - clip_off.x, pcmd->ClipRect.w - clip_off.y); - if (clip_max.x <= clip_min.x || clip_max.y <= clip_min.y) - continue; - - // Apply scissor/clipping rectangle - const D3D11_RECT r = { (LONG)clip_min.x, (LONG)clip_min.y, (LONG)clip_max.x, (LONG)clip_max.y }; - ctx->RSSetScissorRects(1, &r); - - // Bind texture, Draw - ID3D11ShaderResourceView* texture_srv = (ID3D11ShaderResourceView*)pcmd->GetTexID(); - ctx->PSSetShaderResources(0, 1, &texture_srv); - ctx->DrawIndexed(pcmd->ElemCount, pcmd->IdxOffset + global_idx_offset, pcmd->VtxOffset + global_vtx_offset); - } - } - global_idx_offset += cmd_list->IdxBuffer.Size; - global_vtx_offset += cmd_list->VtxBuffer.Size; - } - - // Restore modified DX state - ctx->RSSetScissorRects(old.ScissorRectsCount, old.ScissorRects); - ctx->RSSetViewports(old.ViewportsCount, old.Viewports); - ctx->RSSetState(old.RS); if (old.RS) old.RS->Release(); - ctx->OMSetBlendState(old.BlendState, old.BlendFactor, old.SampleMask); if (old.BlendState) old.BlendState->Release(); - ctx->OMSetDepthStencilState(old.DepthStencilState, old.StencilRef); if (old.DepthStencilState) old.DepthStencilState->Release(); - ctx->PSSetShaderResources(0, 1, &old.PSShaderResource); if (old.PSShaderResource) old.PSShaderResource->Release(); - ctx->PSSetSamplers(0, 1, &old.PSSampler); if (old.PSSampler) old.PSSampler->Release(); - ctx->PSSetShader(old.PS, old.PSInstances, old.PSInstancesCount); if (old.PS) old.PS->Release(); - for (UINT i = 0; i < old.PSInstancesCount; i++) if (old.PSInstances[i]) old.PSInstances[i]->Release(); - ctx->VSSetShader(old.VS, old.VSInstances, old.VSInstancesCount); if (old.VS) old.VS->Release(); - ctx->VSSetConstantBuffers(0, 1, &old.VSConstantBuffer); if (old.VSConstantBuffer) old.VSConstantBuffer->Release(); - ctx->GSSetShader(old.GS, old.GSInstances, old.GSInstancesCount); if (old.GS) old.GS->Release(); - for (UINT i = 0; i < old.VSInstancesCount; i++) if (old.VSInstances[i]) old.VSInstances[i]->Release(); - ctx->IASetPrimitiveTopology(old.PrimitiveTopology); - ctx->IASetIndexBuffer(old.IndexBuffer, old.IndexBufferFormat, old.IndexBufferOffset); if (old.IndexBuffer) old.IndexBuffer->Release(); - ctx->IASetVertexBuffers(0, 1, &old.VertexBuffer, &old.VertexBufferStride, &old.VertexBufferOffset); if (old.VertexBuffer) old.VertexBuffer->Release(); - ctx->IASetInputLayout(old.InputLayout); if (old.InputLayout) old.InputLayout->Release(); -} - -static void ImGui_ImplDX11_CreateFontsTexture() -{ - // Build texture atlas - ImGuiIO& io = ImGui::GetIO(); - ImGui_ImplDX11_Data* bd = ImGui_ImplDX11_GetBackendData(); - unsigned char* pixels; - int width, height; - io.Fonts->GetTexDataAsRGBA32(&pixels, &width, &height); - - // Upload texture to graphics system - { - D3D11_TEXTURE2D_DESC desc; - ZeroMemory(&desc, sizeof(desc)); - desc.Width = width; - desc.Height = height; - desc.MipLevels = 1; - desc.ArraySize = 1; - desc.Format = DXGI_FORMAT_R8G8B8A8_UNORM; - desc.SampleDesc.Count = 1; - desc.Usage = D3D11_USAGE_DEFAULT; - desc.BindFlags = D3D11_BIND_SHADER_RESOURCE; - desc.CPUAccessFlags = 0; - - ID3D11Texture2D* pTexture = nullptr; - D3D11_SUBRESOURCE_DATA subResource; - subResource.pSysMem = pixels; - subResource.SysMemPitch = desc.Width * 4; - subResource.SysMemSlicePitch = 0; - bd->pd3dDevice->CreateTexture2D(&desc, &subResource, &pTexture); - IM_ASSERT(pTexture != nullptr); - - // Create texture view - D3D11_SHADER_RESOURCE_VIEW_DESC srvDesc; - ZeroMemory(&srvDesc, sizeof(srvDesc)); - srvDesc.Format = DXGI_FORMAT_R8G8B8A8_UNORM; - srvDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2D; - srvDesc.Texture2D.MipLevels = desc.MipLevels; - srvDesc.Texture2D.MostDetailedMip = 0; - bd->pd3dDevice->CreateShaderResourceView(pTexture, &srvDesc, &bd->pFontTextureView); - pTexture->Release(); - } - - // Store our identifier - io.Fonts->SetTexID((ImTextureID)bd->pFontTextureView); - - // Create texture sampler - // (Bilinear sampling is required by default. Set 'io.Fonts->Flags |= ImFontAtlasFlags_NoBakedLines' or 'style.AntiAliasedLinesUseTex = false' to allow point/nearest sampling) - { - D3D11_SAMPLER_DESC desc; - ZeroMemory(&desc, sizeof(desc)); - desc.Filter = D3D11_FILTER_MIN_MAG_MIP_LINEAR; - desc.AddressU = D3D11_TEXTURE_ADDRESS_WRAP; - desc.AddressV = D3D11_TEXTURE_ADDRESS_WRAP; - desc.AddressW = D3D11_TEXTURE_ADDRESS_WRAP; - desc.MipLODBias = 0.f; - desc.ComparisonFunc = D3D11_COMPARISON_ALWAYS; - desc.MinLOD = 0.f; - desc.MaxLOD = 0.f; - bd->pd3dDevice->CreateSamplerState(&desc, &bd->pFontSampler); - } -} - -bool ImGui_ImplDX11_CreateDeviceObjects() -{ - ImGui_ImplDX11_Data* bd = ImGui_ImplDX11_GetBackendData(); - if (!bd->pd3dDevice) - return false; - if (bd->pFontSampler) - ImGui_ImplDX11_InvalidateDeviceObjects(); - - // By using D3DCompile() from / d3dcompiler.lib, we introduce a dependency to a given version of d3dcompiler_XX.dll (see D3DCOMPILER_DLL_A) - // If you would like to use this DX11 sample code but remove this dependency you can: - // 1) compile once, save the compiled shader blobs into a file or source code and pass them to CreateVertexShader()/CreatePixelShader() [preferred solution] - // 2) use code to detect any version of the DLL and grab a pointer to D3DCompile from the DLL. - // See https://github.com/ocornut/imgui/pull/638 for sources and details. - - // Create the vertex shader - { - static const char* vertexShader = - "cbuffer vertexBuffer : register(b0) \ - {\ - float4x4 ProjectionMatrix; \ - };\ - struct VS_INPUT\ - {\ - float2 pos : POSITION;\ - float4 col : COLOR0;\ - float2 uv : TEXCOORD0;\ - };\ - \ - struct PS_INPUT\ - {\ - float4 pos : SV_POSITION;\ - float4 col : COLOR0;\ - float2 uv : TEXCOORD0;\ - };\ - \ - PS_INPUT main(VS_INPUT input)\ - {\ - PS_INPUT output;\ - output.pos = mul( ProjectionMatrix, float4(input.pos.xy, 0.f, 1.f));\ - output.col = input.col;\ - output.uv = input.uv;\ - return output;\ - }"; - - ID3DBlob* vertexShaderBlob; - if (FAILED(D3DCompile(vertexShader, strlen(vertexShader), nullptr, nullptr, nullptr, "main", "vs_4_0", 0, 0, &vertexShaderBlob, nullptr))) - return false; // NB: Pass ID3DBlob* pErrorBlob to D3DCompile() to get error showing in (const char*)pErrorBlob->GetBufferPointer(). Make sure to Release() the blob! - if (bd->pd3dDevice->CreateVertexShader(vertexShaderBlob->GetBufferPointer(), vertexShaderBlob->GetBufferSize(), nullptr, &bd->pVertexShader) != S_OK) - { - vertexShaderBlob->Release(); - return false; - } - - // Create the input layout - D3D11_INPUT_ELEMENT_DESC local_layout[] = - { - { "POSITION", 0, DXGI_FORMAT_R32G32_FLOAT, 0, (UINT)IM_OFFSETOF(ImDrawVert, pos), D3D11_INPUT_PER_VERTEX_DATA, 0 }, - { "TEXCOORD", 0, DXGI_FORMAT_R32G32_FLOAT, 0, (UINT)IM_OFFSETOF(ImDrawVert, uv), D3D11_INPUT_PER_VERTEX_DATA, 0 }, - { "COLOR", 0, DXGI_FORMAT_R8G8B8A8_UNORM, 0, (UINT)IM_OFFSETOF(ImDrawVert, col), D3D11_INPUT_PER_VERTEX_DATA, 0 }, - }; - if (bd->pd3dDevice->CreateInputLayout(local_layout, 3, vertexShaderBlob->GetBufferPointer(), vertexShaderBlob->GetBufferSize(), &bd->pInputLayout) != S_OK) - { - vertexShaderBlob->Release(); - return false; - } - vertexShaderBlob->Release(); - - // Create the constant buffer - { - D3D11_BUFFER_DESC desc; - desc.ByteWidth = sizeof(VERTEX_CONSTANT_BUFFER_DX11); - desc.Usage = D3D11_USAGE_DYNAMIC; - desc.BindFlags = D3D11_BIND_CONSTANT_BUFFER; - desc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE; - desc.MiscFlags = 0; - bd->pd3dDevice->CreateBuffer(&desc, nullptr, &bd->pVertexConstantBuffer); - } - } - - // Create the pixel shader - { - static const char* pixelShader = - "struct PS_INPUT\ - {\ - float4 pos : SV_POSITION;\ - float4 col : COLOR0;\ - float2 uv : TEXCOORD0;\ - };\ - sampler sampler0;\ - Texture2D texture0;\ - \ - float4 main(PS_INPUT input) : SV_Target\ - {\ - float4 out_col = input.col * texture0.Sample(sampler0, input.uv); \ - return out_col; \ - }"; - - ID3DBlob* pixelShaderBlob; - if (FAILED(D3DCompile(pixelShader, strlen(pixelShader), nullptr, nullptr, nullptr, "main", "ps_4_0", 0, 0, &pixelShaderBlob, nullptr))) - return false; // NB: Pass ID3DBlob* pErrorBlob to D3DCompile() to get error showing in (const char*)pErrorBlob->GetBufferPointer(). Make sure to Release() the blob! - if (bd->pd3dDevice->CreatePixelShader(pixelShaderBlob->GetBufferPointer(), pixelShaderBlob->GetBufferSize(), nullptr, &bd->pPixelShader) != S_OK) - { - pixelShaderBlob->Release(); - return false; - } - pixelShaderBlob->Release(); - } - - // Create the blending setup - { - D3D11_BLEND_DESC desc; - ZeroMemory(&desc, sizeof(desc)); - desc.AlphaToCoverageEnable = false; - desc.RenderTarget[0].BlendEnable = true; - desc.RenderTarget[0].SrcBlend = D3D11_BLEND_SRC_ALPHA; - desc.RenderTarget[0].DestBlend = D3D11_BLEND_INV_SRC_ALPHA; - desc.RenderTarget[0].BlendOp = D3D11_BLEND_OP_ADD; - desc.RenderTarget[0].SrcBlendAlpha = D3D11_BLEND_ONE; - desc.RenderTarget[0].DestBlendAlpha = D3D11_BLEND_INV_SRC_ALPHA; - desc.RenderTarget[0].BlendOpAlpha = D3D11_BLEND_OP_ADD; - desc.RenderTarget[0].RenderTargetWriteMask = D3D11_COLOR_WRITE_ENABLE_ALL; - bd->pd3dDevice->CreateBlendState(&desc, &bd->pBlendState); - } - - // Create the rasterizer state - { - D3D11_RASTERIZER_DESC desc; - ZeroMemory(&desc, sizeof(desc)); - desc.FillMode = D3D11_FILL_SOLID; - desc.CullMode = D3D11_CULL_NONE; - desc.ScissorEnable = true; - desc.DepthClipEnable = true; - bd->pd3dDevice->CreateRasterizerState(&desc, &bd->pRasterizerState); - } - - // Create depth-stencil State - { - D3D11_DEPTH_STENCIL_DESC desc; - ZeroMemory(&desc, sizeof(desc)); - desc.DepthEnable = false; - desc.DepthWriteMask = D3D11_DEPTH_WRITE_MASK_ALL; - desc.DepthFunc = D3D11_COMPARISON_ALWAYS; - desc.StencilEnable = false; - desc.FrontFace.StencilFailOp = desc.FrontFace.StencilDepthFailOp = desc.FrontFace.StencilPassOp = D3D11_STENCIL_OP_KEEP; - desc.FrontFace.StencilFunc = D3D11_COMPARISON_ALWAYS; - desc.BackFace = desc.FrontFace; - bd->pd3dDevice->CreateDepthStencilState(&desc, &bd->pDepthStencilState); - } - - ImGui_ImplDX11_CreateFontsTexture(); - - return true; -} - -void ImGui_ImplDX11_InvalidateDeviceObjects() -{ - ImGui_ImplDX11_Data* bd = ImGui_ImplDX11_GetBackendData(); - if (!bd->pd3dDevice) - return; - - if (bd->pFontSampler) { bd->pFontSampler->Release(); bd->pFontSampler = nullptr; } - if (bd->pFontTextureView) { bd->pFontTextureView->Release(); bd->pFontTextureView = nullptr; ImGui::GetIO().Fonts->SetTexID(0); } // We copied data->pFontTextureView to io.Fonts->TexID so let's clear that as well. - if (bd->pIB) { bd->pIB->Release(); bd->pIB = nullptr; } - if (bd->pVB) { bd->pVB->Release(); bd->pVB = nullptr; } - if (bd->pBlendState) { bd->pBlendState->Release(); bd->pBlendState = nullptr; } - if (bd->pDepthStencilState) { bd->pDepthStencilState->Release(); bd->pDepthStencilState = nullptr; } - if (bd->pRasterizerState) { bd->pRasterizerState->Release(); bd->pRasterizerState = nullptr; } - if (bd->pPixelShader) { bd->pPixelShader->Release(); bd->pPixelShader = nullptr; } - if (bd->pVertexConstantBuffer) { bd->pVertexConstantBuffer->Release(); bd->pVertexConstantBuffer = nullptr; } - if (bd->pInputLayout) { bd->pInputLayout->Release(); bd->pInputLayout = nullptr; } - if (bd->pVertexShader) { bd->pVertexShader->Release(); bd->pVertexShader = nullptr; } -} - -bool ImGui_ImplDX11_Init(ID3D11Device* device, ID3D11DeviceContext* device_context) -{ - ImGuiIO& io = ImGui::GetIO(); - IM_ASSERT(io.BackendRendererUserData == nullptr && "Already initialized a renderer backend!"); - - // Setup backend capabilities flags - ImGui_ImplDX11_Data* bd = IM_NEW(ImGui_ImplDX11_Data)(); - io.BackendRendererUserData = (void*)bd; - io.BackendRendererName = "imgui_impl_dx11"; - io.BackendFlags |= ImGuiBackendFlags_RendererHasVtxOffset; // We can honor the ImDrawCmd::VtxOffset field, allowing for large meshes. - io.BackendFlags |= ImGuiBackendFlags_RendererHasViewports; // We can create multi-viewports on the Renderer side (optional) - - // Get factory from device - IDXGIDevice* pDXGIDevice = nullptr; - IDXGIAdapter* pDXGIAdapter = nullptr; - IDXGIFactory* pFactory = nullptr; - - if (device->QueryInterface(IID_PPV_ARGS(&pDXGIDevice)) == S_OK) - if (pDXGIDevice->GetParent(IID_PPV_ARGS(&pDXGIAdapter)) == S_OK) - if (pDXGIAdapter->GetParent(IID_PPV_ARGS(&pFactory)) == S_OK) - { - bd->pd3dDevice = device; - bd->pd3dDeviceContext = device_context; - bd->pFactory = pFactory; - } - if (pDXGIDevice) pDXGIDevice->Release(); - if (pDXGIAdapter) pDXGIAdapter->Release(); - bd->pd3dDevice->AddRef(); - bd->pd3dDeviceContext->AddRef(); - - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - ImGui_ImplDX11_InitPlatformInterface(); - - return true; -} - -void ImGui_ImplDX11_Shutdown() -{ - ImGui_ImplDX11_Data* bd = ImGui_ImplDX11_GetBackendData(); - IM_ASSERT(bd != nullptr && "No renderer backend to shutdown, or already shutdown?"); - ImGuiIO& io = ImGui::GetIO(); - - ImGui_ImplDX11_ShutdownPlatformInterface(); - ImGui_ImplDX11_InvalidateDeviceObjects(); - if (bd->pFactory) { bd->pFactory->Release(); } - if (bd->pd3dDevice) { bd->pd3dDevice->Release(); } - if (bd->pd3dDeviceContext) { bd->pd3dDeviceContext->Release(); } - io.BackendRendererName = nullptr; - io.BackendRendererUserData = nullptr; - io.BackendFlags &= ~(ImGuiBackendFlags_RendererHasVtxOffset | ImGuiBackendFlags_RendererHasViewports); - IM_DELETE(bd); -} - -void ImGui_ImplDX11_NewFrame() -{ - ImGui_ImplDX11_Data* bd = ImGui_ImplDX11_GetBackendData(); - IM_ASSERT(bd != nullptr && "Did you call ImGui_ImplDX11_Init()?"); - - if (!bd->pFontSampler) - ImGui_ImplDX11_CreateDeviceObjects(); -} - -//-------------------------------------------------------------------------------------------------------- -// MULTI-VIEWPORT / PLATFORM INTERFACE SUPPORT -// This is an _advanced_ and _optional_ feature, allowing the backend to create and handle multiple viewports simultaneously. -// If you are new to dear imgui or creating a new binding for dear imgui, it is recommended that you completely ignore this section first.. -//-------------------------------------------------------------------------------------------------------- - -// Helper structure we store in the void* RendererUserData field of each ImGuiViewport to easily retrieve our backend data. -struct ImGui_ImplDX11_ViewportData -{ - IDXGISwapChain* SwapChain; - ID3D11RenderTargetView* RTView; - - ImGui_ImplDX11_ViewportData() { SwapChain = nullptr; RTView = nullptr; } - ~ImGui_ImplDX11_ViewportData() { IM_ASSERT(SwapChain == nullptr && RTView == nullptr); } -}; - -static void ImGui_ImplDX11_CreateWindow(ImGuiViewport* viewport) -{ - ImGui_ImplDX11_Data* bd = ImGui_ImplDX11_GetBackendData(); - ImGui_ImplDX11_ViewportData* vd = IM_NEW(ImGui_ImplDX11_ViewportData)(); - viewport->RendererUserData = vd; - - // PlatformHandleRaw should always be a HWND, whereas PlatformHandle might be a higher-level handle (e.g. GLFWWindow*, SDL_Window*). - // Some backends will leave PlatformHandleRaw == 0, in which case we assume PlatformHandle will contain the HWND. - HWND hwnd = viewport->PlatformHandleRaw ? (HWND)viewport->PlatformHandleRaw : (HWND)viewport->PlatformHandle; - IM_ASSERT(hwnd != 0); - - // Create swap chain - DXGI_SWAP_CHAIN_DESC sd; - ZeroMemory(&sd, sizeof(sd)); - sd.BufferDesc.Width = (UINT)viewport->Size.x; - sd.BufferDesc.Height = (UINT)viewport->Size.y; - sd.BufferDesc.Format = DXGI_FORMAT_R8G8B8A8_UNORM; - sd.SampleDesc.Count = 1; - sd.SampleDesc.Quality = 0; - sd.BufferUsage = DXGI_USAGE_RENDER_TARGET_OUTPUT; - sd.BufferCount = 1; - sd.OutputWindow = hwnd; - sd.Windowed = TRUE; - sd.SwapEffect = DXGI_SWAP_EFFECT_DISCARD; - sd.Flags = 0; - - IM_ASSERT(vd->SwapChain == nullptr && vd->RTView == nullptr); - bd->pFactory->CreateSwapChain(bd->pd3dDevice, &sd, &vd->SwapChain); - - // Create the render target - if (vd->SwapChain) - { - ID3D11Texture2D* pBackBuffer; - vd->SwapChain->GetBuffer(0, IID_PPV_ARGS(&pBackBuffer)); - bd->pd3dDevice->CreateRenderTargetView(pBackBuffer, nullptr, &vd->RTView); - pBackBuffer->Release(); - } -} - -static void ImGui_ImplDX11_DestroyWindow(ImGuiViewport* viewport) -{ - // The main viewport (owned by the application) will always have RendererUserData == nullptr since we didn't create the data for it. - if (ImGui_ImplDX11_ViewportData* vd = (ImGui_ImplDX11_ViewportData*)viewport->RendererUserData) - { - if (vd->SwapChain) - vd->SwapChain->Release(); - vd->SwapChain = nullptr; - if (vd->RTView) - vd->RTView->Release(); - vd->RTView = nullptr; - IM_DELETE(vd); - } - viewport->RendererUserData = nullptr; -} - -static void ImGui_ImplDX11_SetWindowSize(ImGuiViewport* viewport, ImVec2 size) -{ - ImGui_ImplDX11_Data* bd = ImGui_ImplDX11_GetBackendData(); - ImGui_ImplDX11_ViewportData* vd = (ImGui_ImplDX11_ViewportData*)viewport->RendererUserData; - if (vd->RTView) - { - vd->RTView->Release(); - vd->RTView = nullptr; - } - if (vd->SwapChain) - { - ID3D11Texture2D* pBackBuffer = nullptr; - vd->SwapChain->ResizeBuffers(0, (UINT)size.x, (UINT)size.y, DXGI_FORMAT_UNKNOWN, 0); - vd->SwapChain->GetBuffer(0, IID_PPV_ARGS(&pBackBuffer)); - if (pBackBuffer == nullptr) { fprintf(stderr, "ImGui_ImplDX11_SetWindowSize() failed creating buffers.\n"); return; } - bd->pd3dDevice->CreateRenderTargetView(pBackBuffer, nullptr, &vd->RTView); - pBackBuffer->Release(); - } -} - -static void ImGui_ImplDX11_RenderWindow(ImGuiViewport* viewport, void*) -{ - ImGui_ImplDX11_Data* bd = ImGui_ImplDX11_GetBackendData(); - ImGui_ImplDX11_ViewportData* vd = (ImGui_ImplDX11_ViewportData*)viewport->RendererUserData; - ImVec4 clear_color = ImVec4(0.0f, 0.0f, 0.0f, 1.0f); - bd->pd3dDeviceContext->OMSetRenderTargets(1, &vd->RTView, nullptr); - if (!(viewport->Flags & ImGuiViewportFlags_NoRendererClear)) - bd->pd3dDeviceContext->ClearRenderTargetView(vd->RTView, (float*)&clear_color); - ImGui_ImplDX11_RenderDrawData(viewport->DrawData); -} - -static void ImGui_ImplDX11_SwapBuffers(ImGuiViewport* viewport, void*) -{ - ImGui_ImplDX11_ViewportData* vd = (ImGui_ImplDX11_ViewportData*)viewport->RendererUserData; - vd->SwapChain->Present(0, 0); // Present without vsync -} - -static void ImGui_ImplDX11_InitPlatformInterface() -{ - ImGuiPlatformIO& platform_io = ImGui::GetPlatformIO(); - platform_io.Renderer_CreateWindow = ImGui_ImplDX11_CreateWindow; - platform_io.Renderer_DestroyWindow = ImGui_ImplDX11_DestroyWindow; - platform_io.Renderer_SetWindowSize = ImGui_ImplDX11_SetWindowSize; - platform_io.Renderer_RenderWindow = ImGui_ImplDX11_RenderWindow; - platform_io.Renderer_SwapBuffers = ImGui_ImplDX11_SwapBuffers; -} - -static void ImGui_ImplDX11_ShutdownPlatformInterface() -{ - ImGui::DestroyPlatformWindows(); -} - -//----------------------------------------------------------------------------- - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_dx11.h b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_dx11.h deleted file mode 100644 index 1713fbd..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_dx11.h +++ /dev/null @@ -1,33 +0,0 @@ -// dear imgui: Renderer Backend for DirectX11 -// This needs to be used along with a Platform Backend (e.g. Win32) - -// Implemented features: -// [X] Renderer: User texture binding. Use 'ID3D11ShaderResourceView*' as ImTextureID. Read the FAQ about ImTextureID! -// [X] Renderer: Large meshes support (64k+ vertices) with 16-bit indices. -// [X] Renderer: Multi-viewport support (multiple windows). Enable with 'io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable'. - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#pragma once -#include "imgui.h" // IMGUI_IMPL_API -#ifndef IMGUI_DISABLE - -struct ID3D11Device; -struct ID3D11DeviceContext; - -IMGUI_IMPL_API bool ImGui_ImplDX11_Init(ID3D11Device* device, ID3D11DeviceContext* device_context); -IMGUI_IMPL_API void ImGui_ImplDX11_Shutdown(); -IMGUI_IMPL_API void ImGui_ImplDX11_NewFrame(); -IMGUI_IMPL_API void ImGui_ImplDX11_RenderDrawData(ImDrawData* draw_data); - -// Use if you want to reset your rendering device without losing Dear ImGui state. -IMGUI_IMPL_API void ImGui_ImplDX11_InvalidateDeviceObjects(); -IMGUI_IMPL_API bool ImGui_ImplDX11_CreateDeviceObjects(); - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_dx12.cpp b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_dx12.cpp deleted file mode 100644 index 22261a1..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_dx12.cpp +++ /dev/null @@ -1,1084 +0,0 @@ -// dear imgui: Renderer Backend for DirectX12 -// This needs to be used along with a Platform Backend (e.g. Win32) - -// Implemented features: -// [X] Renderer: User texture binding. Use 'D3D12_GPU_DESCRIPTOR_HANDLE' as ImTextureID. Read the FAQ about ImTextureID! -// [X] Renderer: Large meshes support (64k+ vertices) with 16-bit indices. -// [X] Renderer: Multi-viewport support (multiple windows). Enable with 'io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable'. -// FIXME: The transition from removing a viewport and moving the window in an existing hosted viewport tends to flicker. - -// Important: to compile on 32-bit systems, this backend requires code to be compiled with '#define ImTextureID ImU64'. -// This is because we need ImTextureID to carry a 64-bit value and by default ImTextureID is defined as void*. -// To build this on 32-bit systems: -// - [Solution 1] IDE/msbuild: in "Properties/C++/Preprocessor Definitions" add 'ImTextureID=ImU64' (this is what we do in the 'example_win32_direct12/example_win32_direct12.vcxproj' project file) -// - [Solution 2] IDE/msbuild: in "Properties/C++/Preprocessor Definitions" add 'IMGUI_USER_CONFIG="my_imgui_config.h"' and inside 'my_imgui_config.h' add '#define ImTextureID ImU64' and as many other options as you like. -// - [Solution 3] IDE/msbuild: edit imconfig.h and add '#define ImTextureID ImU64' (prefer solution 2 to create your own config file!) -// - [Solution 4] command-line: add '/D ImTextureID=ImU64' to your cl.exe command-line (this is what we do in the example_win32_direct12/build_win32.bat file) - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -// CHANGELOG -// (minor and older changes stripped away, please see git history for details) -// 2023-XX-XX: Platform: Added support for multiple windows via the ImGuiPlatformIO interface. -// 2022-10-11: Using 'nullptr' instead of 'NULL' as per our switch to C++11. -// 2021-06-29: Reorganized backend to pull data from a single structure to facilitate usage with multiple-contexts (all g_XXXX access changed to bd->XXXX). -// 2021-05-19: DirectX12: Replaced direct access to ImDrawCmd::TextureId with a call to ImDrawCmd::GetTexID(). (will become a requirement) -// 2021-02-18: DirectX12: Change blending equation to preserve alpha in output buffer. -// 2021-01-11: DirectX12: Improve Windows 7 compatibility (for D3D12On7) by loading d3d12.dll dynamically. -// 2020-09-16: DirectX12: Avoid rendering calls with zero-sized scissor rectangle since it generates a validation layer warning. -// 2020-09-08: DirectX12: Clarified support for building on 32-bit systems by redefining ImTextureID. -// 2019-10-18: DirectX12: *BREAKING CHANGE* Added extra ID3D12DescriptorHeap parameter to ImGui_ImplDX12_Init() function. -// 2019-05-29: DirectX12: Added support for large mesh (64K+ vertices), enable ImGuiBackendFlags_RendererHasVtxOffset flag. -// 2019-04-30: DirectX12: Added support for special ImDrawCallback_ResetRenderState callback to reset render state. -// 2019-03-29: Misc: Various minor tidying up. -// 2018-12-03: Misc: Added #pragma comment statement to automatically link with d3dcompiler.lib when using D3DCompile(). -// 2018-11-30: Misc: Setting up io.BackendRendererName so it can be displayed in the About Window. -// 2018-06-12: DirectX12: Moved the ID3D12GraphicsCommandList* parameter from NewFrame() to RenderDrawData(). -// 2018-06-08: Misc: Extracted imgui_impl_dx12.cpp/.h away from the old combined DX12+Win32 example. -// 2018-06-08: DirectX12: Use draw_data->DisplayPos and draw_data->DisplaySize to setup projection matrix and clipping rectangle (to ease support for future multi-viewport). -// 2018-02-22: Merged into master with all Win32 code synchronized to other examples. - -#include "imgui.h" -#ifndef IMGUI_DISABLE -#include "imgui_impl_dx12.h" - -// DirectX -#include -#include -#include -#ifdef _MSC_VER -#pragma comment(lib, "d3dcompiler") // Automatically link with d3dcompiler.lib as we are using D3DCompile() below. -#endif - -// DirectX data -struct ImGui_ImplDX12_Data -{ - ID3D12Device* pd3dDevice; - ID3D12RootSignature* pRootSignature; - ID3D12PipelineState* pPipelineState; - DXGI_FORMAT RTVFormat; - ID3D12Resource* pFontTextureResource; - D3D12_CPU_DESCRIPTOR_HANDLE hFontSrvCpuDescHandle; - D3D12_GPU_DESCRIPTOR_HANDLE hFontSrvGpuDescHandle; - ID3D12DescriptorHeap* pd3dSrvDescHeap; - UINT numFramesInFlight; - - ImGui_ImplDX12_Data() { memset((void*)this, 0, sizeof(*this)); } -}; - -// Backend data stored in io.BackendRendererUserData to allow support for multiple Dear ImGui contexts -// It is STRONGLY preferred that you use docking branch with multi-viewports (== single Dear ImGui context + multiple windows) instead of multiple Dear ImGui contexts. -static ImGui_ImplDX12_Data* ImGui_ImplDX12_GetBackendData() -{ - return ImGui::GetCurrentContext() ? (ImGui_ImplDX12_Data*)ImGui::GetIO().BackendRendererUserData : nullptr; -} - -// Buffers used during the rendering of a frame -struct ImGui_ImplDX12_RenderBuffers -{ - ID3D12Resource* IndexBuffer; - ID3D12Resource* VertexBuffer; - int IndexBufferSize; - int VertexBufferSize; -}; - -// Buffers used for secondary viewports created by the multi-viewports systems -struct ImGui_ImplDX12_FrameContext -{ - ID3D12CommandAllocator* CommandAllocator; - ID3D12Resource* RenderTarget; - D3D12_CPU_DESCRIPTOR_HANDLE RenderTargetCpuDescriptors; -}; - -// Helper structure we store in the void* RendererUserData field of each ImGuiViewport to easily retrieve our backend data. -// Main viewport created by application will only use the Resources field. -// Secondary viewports created by this backend will use all the fields (including Window fields), -struct ImGui_ImplDX12_ViewportData -{ - // Window - ID3D12CommandQueue* CommandQueue; - ID3D12GraphicsCommandList* CommandList; - ID3D12DescriptorHeap* RtvDescHeap; - IDXGISwapChain3* SwapChain; - ID3D12Fence* Fence; - UINT64 FenceSignaledValue; - HANDLE FenceEvent; - UINT NumFramesInFlight; - ImGui_ImplDX12_FrameContext* FrameCtx; - - // Render buffers - UINT FrameIndex; - ImGui_ImplDX12_RenderBuffers* FrameRenderBuffers; - - ImGui_ImplDX12_ViewportData(UINT num_frames_in_flight) - { - CommandQueue = nullptr; - CommandList = nullptr; - RtvDescHeap = nullptr; - SwapChain = nullptr; - Fence = nullptr; - FenceSignaledValue = 0; - FenceEvent = nullptr; - NumFramesInFlight = num_frames_in_flight; - FrameCtx = new ImGui_ImplDX12_FrameContext[NumFramesInFlight]; - FrameIndex = UINT_MAX; - FrameRenderBuffers = new ImGui_ImplDX12_RenderBuffers[NumFramesInFlight]; - - for (UINT i = 0; i < NumFramesInFlight; ++i) - { - FrameCtx[i].CommandAllocator = nullptr; - FrameCtx[i].RenderTarget = nullptr; - - // Create buffers with a default size (they will later be grown as needed) - FrameRenderBuffers[i].IndexBuffer = nullptr; - FrameRenderBuffers[i].VertexBuffer = nullptr; - FrameRenderBuffers[i].VertexBufferSize = 5000; - FrameRenderBuffers[i].IndexBufferSize = 10000; - } - } - ~ImGui_ImplDX12_ViewportData() - { - IM_ASSERT(CommandQueue == nullptr && CommandList == nullptr); - IM_ASSERT(RtvDescHeap == nullptr); - IM_ASSERT(SwapChain == nullptr); - IM_ASSERT(Fence == nullptr); - IM_ASSERT(FenceEvent == nullptr); - - for (UINT i = 0; i < NumFramesInFlight; ++i) - { - IM_ASSERT(FrameCtx[i].CommandAllocator == nullptr && FrameCtx[i].RenderTarget == nullptr); - IM_ASSERT(FrameRenderBuffers[i].IndexBuffer == nullptr && FrameRenderBuffers[i].VertexBuffer == nullptr); - } - - delete[] FrameCtx; FrameCtx = nullptr; - delete[] FrameRenderBuffers; FrameRenderBuffers = nullptr; - } -}; - -struct VERTEX_CONSTANT_BUFFER_DX12 -{ - float mvp[4][4]; -}; - -// Forward Declarations -static void ImGui_ImplDX12_InitPlatformInterface(); -static void ImGui_ImplDX12_ShutdownPlatformInterface(); - -// Functions -static void ImGui_ImplDX12_SetupRenderState(ImDrawData* draw_data, ID3D12GraphicsCommandList* ctx, ImGui_ImplDX12_RenderBuffers* fr) -{ - ImGui_ImplDX12_Data* bd = ImGui_ImplDX12_GetBackendData(); - - // Setup orthographic projection matrix into our constant buffer - // Our visible imgui space lies from draw_data->DisplayPos (top left) to draw_data->DisplayPos+data_data->DisplaySize (bottom right). - VERTEX_CONSTANT_BUFFER_DX12 vertex_constant_buffer; - { - float L = draw_data->DisplayPos.x; - float R = draw_data->DisplayPos.x + draw_data->DisplaySize.x; - float T = draw_data->DisplayPos.y; - float B = draw_data->DisplayPos.y + draw_data->DisplaySize.y; - float mvp[4][4] = - { - { 2.0f/(R-L), 0.0f, 0.0f, 0.0f }, - { 0.0f, 2.0f/(T-B), 0.0f, 0.0f }, - { 0.0f, 0.0f, 0.5f, 0.0f }, - { (R+L)/(L-R), (T+B)/(B-T), 0.5f, 1.0f }, - }; - memcpy(&vertex_constant_buffer.mvp, mvp, sizeof(mvp)); - } - - // Setup viewport - D3D12_VIEWPORT vp; - memset(&vp, 0, sizeof(D3D12_VIEWPORT)); - vp.Width = draw_data->DisplaySize.x; - vp.Height = draw_data->DisplaySize.y; - vp.MinDepth = 0.0f; - vp.MaxDepth = 1.0f; - vp.TopLeftX = vp.TopLeftY = 0.0f; - ctx->RSSetViewports(1, &vp); - - // Bind shader and vertex buffers - unsigned int stride = sizeof(ImDrawVert); - unsigned int offset = 0; - D3D12_VERTEX_BUFFER_VIEW vbv; - memset(&vbv, 0, sizeof(D3D12_VERTEX_BUFFER_VIEW)); - vbv.BufferLocation = fr->VertexBuffer->GetGPUVirtualAddress() + offset; - vbv.SizeInBytes = fr->VertexBufferSize * stride; - vbv.StrideInBytes = stride; - ctx->IASetVertexBuffers(0, 1, &vbv); - D3D12_INDEX_BUFFER_VIEW ibv; - memset(&ibv, 0, sizeof(D3D12_INDEX_BUFFER_VIEW)); - ibv.BufferLocation = fr->IndexBuffer->GetGPUVirtualAddress(); - ibv.SizeInBytes = fr->IndexBufferSize * sizeof(ImDrawIdx); - ibv.Format = sizeof(ImDrawIdx) == 2 ? DXGI_FORMAT_R16_UINT : DXGI_FORMAT_R32_UINT; - ctx->IASetIndexBuffer(&ibv); - ctx->IASetPrimitiveTopology(D3D_PRIMITIVE_TOPOLOGY_TRIANGLELIST); - ctx->SetPipelineState(bd->pPipelineState); - ctx->SetGraphicsRootSignature(bd->pRootSignature); - ctx->SetGraphicsRoot32BitConstants(0, 16, &vertex_constant_buffer, 0); - - // Setup blend factor - const float blend_factor[4] = { 0.f, 0.f, 0.f, 0.f }; - ctx->OMSetBlendFactor(blend_factor); -} - -template -static inline void SafeRelease(T*& res) -{ - if (res) - res->Release(); - res = nullptr; -} - -// Render function -void ImGui_ImplDX12_RenderDrawData(ImDrawData* draw_data, ID3D12GraphicsCommandList* ctx) -{ - // Avoid rendering when minimized - if (draw_data->DisplaySize.x <= 0.0f || draw_data->DisplaySize.y <= 0.0f) - return; - - ImGui_ImplDX12_Data* bd = ImGui_ImplDX12_GetBackendData(); - ImGui_ImplDX12_ViewportData* vd = (ImGui_ImplDX12_ViewportData*)draw_data->OwnerViewport->RendererUserData; - vd->FrameIndex++; - ImGui_ImplDX12_RenderBuffers* fr = &vd->FrameRenderBuffers[vd->FrameIndex % bd->numFramesInFlight]; - - // Create and grow vertex/index buffers if needed - if (fr->VertexBuffer == nullptr || fr->VertexBufferSize < draw_data->TotalVtxCount) - { - SafeRelease(fr->VertexBuffer); - fr->VertexBufferSize = draw_data->TotalVtxCount + 5000; - D3D12_HEAP_PROPERTIES props; - memset(&props, 0, sizeof(D3D12_HEAP_PROPERTIES)); - props.Type = D3D12_HEAP_TYPE_UPLOAD; - props.CPUPageProperty = D3D12_CPU_PAGE_PROPERTY_UNKNOWN; - props.MemoryPoolPreference = D3D12_MEMORY_POOL_UNKNOWN; - D3D12_RESOURCE_DESC desc; - memset(&desc, 0, sizeof(D3D12_RESOURCE_DESC)); - desc.Dimension = D3D12_RESOURCE_DIMENSION_BUFFER; - desc.Width = fr->VertexBufferSize * sizeof(ImDrawVert); - desc.Height = 1; - desc.DepthOrArraySize = 1; - desc.MipLevels = 1; - desc.Format = DXGI_FORMAT_UNKNOWN; - desc.SampleDesc.Count = 1; - desc.Layout = D3D12_TEXTURE_LAYOUT_ROW_MAJOR; - desc.Flags = D3D12_RESOURCE_FLAG_NONE; - if (bd->pd3dDevice->CreateCommittedResource(&props, D3D12_HEAP_FLAG_NONE, &desc, D3D12_RESOURCE_STATE_GENERIC_READ, nullptr, IID_PPV_ARGS(&fr->VertexBuffer)) < 0) - return; - } - if (fr->IndexBuffer == nullptr || fr->IndexBufferSize < draw_data->TotalIdxCount) - { - SafeRelease(fr->IndexBuffer); - fr->IndexBufferSize = draw_data->TotalIdxCount + 10000; - D3D12_HEAP_PROPERTIES props; - memset(&props, 0, sizeof(D3D12_HEAP_PROPERTIES)); - props.Type = D3D12_HEAP_TYPE_UPLOAD; - props.CPUPageProperty = D3D12_CPU_PAGE_PROPERTY_UNKNOWN; - props.MemoryPoolPreference = D3D12_MEMORY_POOL_UNKNOWN; - D3D12_RESOURCE_DESC desc; - memset(&desc, 0, sizeof(D3D12_RESOURCE_DESC)); - desc.Dimension = D3D12_RESOURCE_DIMENSION_BUFFER; - desc.Width = fr->IndexBufferSize * sizeof(ImDrawIdx); - desc.Height = 1; - desc.DepthOrArraySize = 1; - desc.MipLevels = 1; - desc.Format = DXGI_FORMAT_UNKNOWN; - desc.SampleDesc.Count = 1; - desc.Layout = D3D12_TEXTURE_LAYOUT_ROW_MAJOR; - desc.Flags = D3D12_RESOURCE_FLAG_NONE; - if (bd->pd3dDevice->CreateCommittedResource(&props, D3D12_HEAP_FLAG_NONE, &desc, D3D12_RESOURCE_STATE_GENERIC_READ, nullptr, IID_PPV_ARGS(&fr->IndexBuffer)) < 0) - return; - } - - // Upload vertex/index data into a single contiguous GPU buffer - void* vtx_resource, *idx_resource; - D3D12_RANGE range; - memset(&range, 0, sizeof(D3D12_RANGE)); - if (fr->VertexBuffer->Map(0, &range, &vtx_resource) != S_OK) - return; - if (fr->IndexBuffer->Map(0, &range, &idx_resource) != S_OK) - return; - ImDrawVert* vtx_dst = (ImDrawVert*)vtx_resource; - ImDrawIdx* idx_dst = (ImDrawIdx*)idx_resource; - for (int n = 0; n < draw_data->CmdListsCount; n++) - { - const ImDrawList* cmd_list = draw_data->CmdLists[n]; - memcpy(vtx_dst, cmd_list->VtxBuffer.Data, cmd_list->VtxBuffer.Size * sizeof(ImDrawVert)); - memcpy(idx_dst, cmd_list->IdxBuffer.Data, cmd_list->IdxBuffer.Size * sizeof(ImDrawIdx)); - vtx_dst += cmd_list->VtxBuffer.Size; - idx_dst += cmd_list->IdxBuffer.Size; - } - fr->VertexBuffer->Unmap(0, &range); - fr->IndexBuffer->Unmap(0, &range); - - // Setup desired DX state - ImGui_ImplDX12_SetupRenderState(draw_data, ctx, fr); - - // Render command lists - // (Because we merged all buffers into a single one, we maintain our own offset into them) - int global_vtx_offset = 0; - int global_idx_offset = 0; - ImVec2 clip_off = draw_data->DisplayPos; - for (int n = 0; n < draw_data->CmdListsCount; n++) - { - const ImDrawList* cmd_list = draw_data->CmdLists[n]; - for (int cmd_i = 0; cmd_i < cmd_list->CmdBuffer.Size; cmd_i++) - { - const ImDrawCmd* pcmd = &cmd_list->CmdBuffer[cmd_i]; - if (pcmd->UserCallback != nullptr) - { - // User callback, registered via ImDrawList::AddCallback() - // (ImDrawCallback_ResetRenderState is a special callback value used by the user to request the renderer to reset render state.) - if (pcmd->UserCallback == ImDrawCallback_ResetRenderState) - ImGui_ImplDX12_SetupRenderState(draw_data, ctx, fr); - else - pcmd->UserCallback(cmd_list, pcmd); - } - else - { - // Project scissor/clipping rectangles into framebuffer space - ImVec2 clip_min(pcmd->ClipRect.x - clip_off.x, pcmd->ClipRect.y - clip_off.y); - ImVec2 clip_max(pcmd->ClipRect.z - clip_off.x, pcmd->ClipRect.w - clip_off.y); - if (clip_max.x <= clip_min.x || clip_max.y <= clip_min.y) - continue; - - // Apply Scissor/clipping rectangle, Bind texture, Draw - const D3D12_RECT r = { (LONG)clip_min.x, (LONG)clip_min.y, (LONG)clip_max.x, (LONG)clip_max.y }; - D3D12_GPU_DESCRIPTOR_HANDLE texture_handle = {}; - texture_handle.ptr = (UINT64)pcmd->GetTexID(); - ctx->SetGraphicsRootDescriptorTable(1, texture_handle); - ctx->RSSetScissorRects(1, &r); - ctx->DrawIndexedInstanced(pcmd->ElemCount, 1, pcmd->IdxOffset + global_idx_offset, pcmd->VtxOffset + global_vtx_offset, 0); - } - } - global_idx_offset += cmd_list->IdxBuffer.Size; - global_vtx_offset += cmd_list->VtxBuffer.Size; - } -} - -static void ImGui_ImplDX12_CreateFontsTexture() -{ - // Build texture atlas - ImGuiIO& io = ImGui::GetIO(); - ImGui_ImplDX12_Data* bd = ImGui_ImplDX12_GetBackendData(); - unsigned char* pixels; - int width, height; - io.Fonts->GetTexDataAsRGBA32(&pixels, &width, &height); - - // Upload texture to graphics system - { - D3D12_HEAP_PROPERTIES props; - memset(&props, 0, sizeof(D3D12_HEAP_PROPERTIES)); - props.Type = D3D12_HEAP_TYPE_DEFAULT; - props.CPUPageProperty = D3D12_CPU_PAGE_PROPERTY_UNKNOWN; - props.MemoryPoolPreference = D3D12_MEMORY_POOL_UNKNOWN; - - D3D12_RESOURCE_DESC desc; - ZeroMemory(&desc, sizeof(desc)); - desc.Dimension = D3D12_RESOURCE_DIMENSION_TEXTURE2D; - desc.Alignment = 0; - desc.Width = width; - desc.Height = height; - desc.DepthOrArraySize = 1; - desc.MipLevels = 1; - desc.Format = DXGI_FORMAT_R8G8B8A8_UNORM; - desc.SampleDesc.Count = 1; - desc.SampleDesc.Quality = 0; - desc.Layout = D3D12_TEXTURE_LAYOUT_UNKNOWN; - desc.Flags = D3D12_RESOURCE_FLAG_NONE; - - ID3D12Resource* pTexture = nullptr; - bd->pd3dDevice->CreateCommittedResource(&props, D3D12_HEAP_FLAG_NONE, &desc, - D3D12_RESOURCE_STATE_COPY_DEST, nullptr, IID_PPV_ARGS(&pTexture)); - - UINT uploadPitch = (width * 4 + D3D12_TEXTURE_DATA_PITCH_ALIGNMENT - 1u) & ~(D3D12_TEXTURE_DATA_PITCH_ALIGNMENT - 1u); - UINT uploadSize = height * uploadPitch; - desc.Dimension = D3D12_RESOURCE_DIMENSION_BUFFER; - desc.Alignment = 0; - desc.Width = uploadSize; - desc.Height = 1; - desc.DepthOrArraySize = 1; - desc.MipLevels = 1; - desc.Format = DXGI_FORMAT_UNKNOWN; - desc.SampleDesc.Count = 1; - desc.SampleDesc.Quality = 0; - desc.Layout = D3D12_TEXTURE_LAYOUT_ROW_MAJOR; - desc.Flags = D3D12_RESOURCE_FLAG_NONE; - - props.Type = D3D12_HEAP_TYPE_UPLOAD; - props.CPUPageProperty = D3D12_CPU_PAGE_PROPERTY_UNKNOWN; - props.MemoryPoolPreference = D3D12_MEMORY_POOL_UNKNOWN; - - ID3D12Resource* uploadBuffer = nullptr; - HRESULT hr = bd->pd3dDevice->CreateCommittedResource(&props, D3D12_HEAP_FLAG_NONE, &desc, - D3D12_RESOURCE_STATE_GENERIC_READ, nullptr, IID_PPV_ARGS(&uploadBuffer)); - IM_ASSERT(SUCCEEDED(hr)); - - void* mapped = nullptr; - D3D12_RANGE range = { 0, uploadSize }; - hr = uploadBuffer->Map(0, &range, &mapped); - IM_ASSERT(SUCCEEDED(hr)); - for (int y = 0; y < height; y++) - memcpy((void*) ((uintptr_t) mapped + y * uploadPitch), pixels + y * width * 4, width * 4); - uploadBuffer->Unmap(0, &range); - - D3D12_TEXTURE_COPY_LOCATION srcLocation = {}; - srcLocation.pResource = uploadBuffer; - srcLocation.Type = D3D12_TEXTURE_COPY_TYPE_PLACED_FOOTPRINT; - srcLocation.PlacedFootprint.Footprint.Format = DXGI_FORMAT_R8G8B8A8_UNORM; - srcLocation.PlacedFootprint.Footprint.Width = width; - srcLocation.PlacedFootprint.Footprint.Height = height; - srcLocation.PlacedFootprint.Footprint.Depth = 1; - srcLocation.PlacedFootprint.Footprint.RowPitch = uploadPitch; - - D3D12_TEXTURE_COPY_LOCATION dstLocation = {}; - dstLocation.pResource = pTexture; - dstLocation.Type = D3D12_TEXTURE_COPY_TYPE_SUBRESOURCE_INDEX; - dstLocation.SubresourceIndex = 0; - - D3D12_RESOURCE_BARRIER barrier = {}; - barrier.Type = D3D12_RESOURCE_BARRIER_TYPE_TRANSITION; - barrier.Flags = D3D12_RESOURCE_BARRIER_FLAG_NONE; - barrier.Transition.pResource = pTexture; - barrier.Transition.Subresource = D3D12_RESOURCE_BARRIER_ALL_SUBRESOURCES; - barrier.Transition.StateBefore = D3D12_RESOURCE_STATE_COPY_DEST; - barrier.Transition.StateAfter = D3D12_RESOURCE_STATE_PIXEL_SHADER_RESOURCE; - - ID3D12Fence* fence = nullptr; - hr = bd->pd3dDevice->CreateFence(0, D3D12_FENCE_FLAG_NONE, IID_PPV_ARGS(&fence)); - IM_ASSERT(SUCCEEDED(hr)); - - HANDLE event = CreateEvent(0, 0, 0, 0); - IM_ASSERT(event != nullptr); - - D3D12_COMMAND_QUEUE_DESC queueDesc = {}; - queueDesc.Type = D3D12_COMMAND_LIST_TYPE_DIRECT; - queueDesc.Flags = D3D12_COMMAND_QUEUE_FLAG_NONE; - queueDesc.NodeMask = 1; - - ID3D12CommandQueue* cmdQueue = nullptr; - hr = bd->pd3dDevice->CreateCommandQueue(&queueDesc, IID_PPV_ARGS(&cmdQueue)); - IM_ASSERT(SUCCEEDED(hr)); - - ID3D12CommandAllocator* cmdAlloc = nullptr; - hr = bd->pd3dDevice->CreateCommandAllocator(D3D12_COMMAND_LIST_TYPE_DIRECT, IID_PPV_ARGS(&cmdAlloc)); - IM_ASSERT(SUCCEEDED(hr)); - - ID3D12GraphicsCommandList* cmdList = nullptr; - hr = bd->pd3dDevice->CreateCommandList(0, D3D12_COMMAND_LIST_TYPE_DIRECT, cmdAlloc, nullptr, IID_PPV_ARGS(&cmdList)); - IM_ASSERT(SUCCEEDED(hr)); - - cmdList->CopyTextureRegion(&dstLocation, 0, 0, 0, &srcLocation, nullptr); - cmdList->ResourceBarrier(1, &barrier); - - hr = cmdList->Close(); - IM_ASSERT(SUCCEEDED(hr)); - - cmdQueue->ExecuteCommandLists(1, (ID3D12CommandList* const*)&cmdList); - hr = cmdQueue->Signal(fence, 1); - IM_ASSERT(SUCCEEDED(hr)); - - fence->SetEventOnCompletion(1, event); - WaitForSingleObject(event, INFINITE); - - cmdList->Release(); - cmdAlloc->Release(); - cmdQueue->Release(); - CloseHandle(event); - fence->Release(); - uploadBuffer->Release(); - - // Create texture view - D3D12_SHADER_RESOURCE_VIEW_DESC srvDesc; - ZeroMemory(&srvDesc, sizeof(srvDesc)); - srvDesc.Format = DXGI_FORMAT_R8G8B8A8_UNORM; - srvDesc.ViewDimension = D3D12_SRV_DIMENSION_TEXTURE2D; - srvDesc.Texture2D.MipLevels = desc.MipLevels; - srvDesc.Texture2D.MostDetailedMip = 0; - srvDesc.Shader4ComponentMapping = D3D12_DEFAULT_SHADER_4_COMPONENT_MAPPING; - bd->pd3dDevice->CreateShaderResourceView(pTexture, &srvDesc, bd->hFontSrvCpuDescHandle); - SafeRelease(bd->pFontTextureResource); - bd->pFontTextureResource = pTexture; - } - - // Store our identifier - // READ THIS IF THE STATIC_ASSERT() TRIGGERS: - // - Important: to compile on 32-bit systems, this backend requires code to be compiled with '#define ImTextureID ImU64'. - // - This is because we need ImTextureID to carry a 64-bit value and by default ImTextureID is defined as void*. - // [Solution 1] IDE/msbuild: in "Properties/C++/Preprocessor Definitions" add 'ImTextureID=ImU64' (this is what we do in the 'example_win32_direct12/example_win32_direct12.vcxproj' project file) - // [Solution 2] IDE/msbuild: in "Properties/C++/Preprocessor Definitions" add 'IMGUI_USER_CONFIG="my_imgui_config.h"' and inside 'my_imgui_config.h' add '#define ImTextureID ImU64' and as many other options as you like. - // [Solution 3] IDE/msbuild: edit imconfig.h and add '#define ImTextureID ImU64' (prefer solution 2 to create your own config file!) - // [Solution 4] command-line: add '/D ImTextureID=ImU64' to your cl.exe command-line (this is what we do in the example_win32_direct12/build_win32.bat file) - static_assert(sizeof(ImTextureID) >= sizeof(bd->hFontSrvGpuDescHandle.ptr), "Can't pack descriptor handle into TexID, 32-bit not supported yet."); - io.Fonts->SetTexID((ImTextureID)bd->hFontSrvGpuDescHandle.ptr); -} - -bool ImGui_ImplDX12_CreateDeviceObjects() -{ - ImGui_ImplDX12_Data* bd = ImGui_ImplDX12_GetBackendData(); - if (!bd || !bd->pd3dDevice) - return false; - if (bd->pPipelineState) - ImGui_ImplDX12_InvalidateDeviceObjects(); - - // Create the root signature - { - D3D12_DESCRIPTOR_RANGE descRange = {}; - descRange.RangeType = D3D12_DESCRIPTOR_RANGE_TYPE_SRV; - descRange.NumDescriptors = 1; - descRange.BaseShaderRegister = 0; - descRange.RegisterSpace = 0; - descRange.OffsetInDescriptorsFromTableStart = 0; - - D3D12_ROOT_PARAMETER param[2] = {}; - - param[0].ParameterType = D3D12_ROOT_PARAMETER_TYPE_32BIT_CONSTANTS; - param[0].Constants.ShaderRegister = 0; - param[0].Constants.RegisterSpace = 0; - param[0].Constants.Num32BitValues = 16; - param[0].ShaderVisibility = D3D12_SHADER_VISIBILITY_VERTEX; - - param[1].ParameterType = D3D12_ROOT_PARAMETER_TYPE_DESCRIPTOR_TABLE; - param[1].DescriptorTable.NumDescriptorRanges = 1; - param[1].DescriptorTable.pDescriptorRanges = &descRange; - param[1].ShaderVisibility = D3D12_SHADER_VISIBILITY_PIXEL; - - // Bilinear sampling is required by default. Set 'io.Fonts->Flags |= ImFontAtlasFlags_NoBakedLines' or 'style.AntiAliasedLinesUseTex = false' to allow point/nearest sampling. - D3D12_STATIC_SAMPLER_DESC staticSampler = {}; - staticSampler.Filter = D3D12_FILTER_MIN_MAG_MIP_LINEAR; - staticSampler.AddressU = D3D12_TEXTURE_ADDRESS_MODE_WRAP; - staticSampler.AddressV = D3D12_TEXTURE_ADDRESS_MODE_WRAP; - staticSampler.AddressW = D3D12_TEXTURE_ADDRESS_MODE_WRAP; - staticSampler.MipLODBias = 0.f; - staticSampler.MaxAnisotropy = 0; - staticSampler.ComparisonFunc = D3D12_COMPARISON_FUNC_ALWAYS; - staticSampler.BorderColor = D3D12_STATIC_BORDER_COLOR_TRANSPARENT_BLACK; - staticSampler.MinLOD = 0.f; - staticSampler.MaxLOD = 0.f; - staticSampler.ShaderRegister = 0; - staticSampler.RegisterSpace = 0; - staticSampler.ShaderVisibility = D3D12_SHADER_VISIBILITY_PIXEL; - - D3D12_ROOT_SIGNATURE_DESC desc = {}; - desc.NumParameters = _countof(param); - desc.pParameters = param; - desc.NumStaticSamplers = 1; - desc.pStaticSamplers = &staticSampler; - desc.Flags = - D3D12_ROOT_SIGNATURE_FLAG_ALLOW_INPUT_ASSEMBLER_INPUT_LAYOUT | - D3D12_ROOT_SIGNATURE_FLAG_DENY_HULL_SHADER_ROOT_ACCESS | - D3D12_ROOT_SIGNATURE_FLAG_DENY_DOMAIN_SHADER_ROOT_ACCESS | - D3D12_ROOT_SIGNATURE_FLAG_DENY_GEOMETRY_SHADER_ROOT_ACCESS; - - // Load d3d12.dll and D3D12SerializeRootSignature() function address dynamically to facilitate using with D3D12On7. - // See if any version of d3d12.dll is already loaded in the process. If so, give preference to that. - static HINSTANCE d3d12_dll = ::GetModuleHandleA("d3d12.dll"); - if (d3d12_dll == nullptr) - { - // Attempt to load d3d12.dll from local directories. This will only succeed if - // (1) the current OS is Windows 7, and - // (2) there exists a version of d3d12.dll for Windows 7 (D3D12On7) in one of the following directories. - // See https://github.com/ocornut/imgui/pull/3696 for details. - const char* localD3d12Paths[] = { ".\\d3d12.dll", ".\\d3d12on7\\d3d12.dll", ".\\12on7\\d3d12.dll" }; // A. current directory, B. used by some games, C. used in Microsoft D3D12On7 sample - for (int i = 0; i < IM_ARRAYSIZE(localD3d12Paths); i++) - if ((d3d12_dll = ::LoadLibraryA(localD3d12Paths[i])) != nullptr) - break; - - // If failed, we are on Windows >= 10. - if (d3d12_dll == nullptr) - d3d12_dll = ::LoadLibraryA("d3d12.dll"); - - if (d3d12_dll == nullptr) - return false; - } - - PFN_D3D12_SERIALIZE_ROOT_SIGNATURE D3D12SerializeRootSignatureFn = (PFN_D3D12_SERIALIZE_ROOT_SIGNATURE)::GetProcAddress(d3d12_dll, "D3D12SerializeRootSignature"); - if (D3D12SerializeRootSignatureFn == nullptr) - return false; - - ID3DBlob* blob = nullptr; - if (D3D12SerializeRootSignatureFn(&desc, D3D_ROOT_SIGNATURE_VERSION_1, &blob, nullptr) != S_OK) - return false; - - bd->pd3dDevice->CreateRootSignature(0, blob->GetBufferPointer(), blob->GetBufferSize(), IID_PPV_ARGS(&bd->pRootSignature)); - blob->Release(); - } - - // By using D3DCompile() from / d3dcompiler.lib, we introduce a dependency to a given version of d3dcompiler_XX.dll (see D3DCOMPILER_DLL_A) - // If you would like to use this DX12 sample code but remove this dependency you can: - // 1) compile once, save the compiled shader blobs into a file or source code and assign them to psoDesc.VS/PS [preferred solution] - // 2) use code to detect any version of the DLL and grab a pointer to D3DCompile from the DLL. - // See https://github.com/ocornut/imgui/pull/638 for sources and details. - - D3D12_GRAPHICS_PIPELINE_STATE_DESC psoDesc; - memset(&psoDesc, 0, sizeof(D3D12_GRAPHICS_PIPELINE_STATE_DESC)); - psoDesc.NodeMask = 1; - psoDesc.PrimitiveTopologyType = D3D12_PRIMITIVE_TOPOLOGY_TYPE_TRIANGLE; - psoDesc.pRootSignature = bd->pRootSignature; - psoDesc.SampleMask = UINT_MAX; - psoDesc.NumRenderTargets = 1; - psoDesc.RTVFormats[0] = bd->RTVFormat; - psoDesc.SampleDesc.Count = 1; - psoDesc.Flags = D3D12_PIPELINE_STATE_FLAG_NONE; - - ID3DBlob* vertexShaderBlob; - ID3DBlob* pixelShaderBlob; - - // Create the vertex shader - { - static const char* vertexShader = - "cbuffer vertexBuffer : register(b0) \ - {\ - float4x4 ProjectionMatrix; \ - };\ - struct VS_INPUT\ - {\ - float2 pos : POSITION;\ - float4 col : COLOR0;\ - float2 uv : TEXCOORD0;\ - };\ - \ - struct PS_INPUT\ - {\ - float4 pos : SV_POSITION;\ - float4 col : COLOR0;\ - float2 uv : TEXCOORD0;\ - };\ - \ - PS_INPUT main(VS_INPUT input)\ - {\ - PS_INPUT output;\ - output.pos = mul( ProjectionMatrix, float4(input.pos.xy, 0.f, 1.f));\ - output.col = input.col;\ - output.uv = input.uv;\ - return output;\ - }"; - - if (FAILED(D3DCompile(vertexShader, strlen(vertexShader), nullptr, nullptr, nullptr, "main", "vs_5_0", 0, 0, &vertexShaderBlob, nullptr))) - return false; // NB: Pass ID3DBlob* pErrorBlob to D3DCompile() to get error showing in (const char*)pErrorBlob->GetBufferPointer(). Make sure to Release() the blob! - psoDesc.VS = { vertexShaderBlob->GetBufferPointer(), vertexShaderBlob->GetBufferSize() }; - - // Create the input layout - static D3D12_INPUT_ELEMENT_DESC local_layout[] = - { - { "POSITION", 0, DXGI_FORMAT_R32G32_FLOAT, 0, (UINT)IM_OFFSETOF(ImDrawVert, pos), D3D12_INPUT_CLASSIFICATION_PER_VERTEX_DATA, 0 }, - { "TEXCOORD", 0, DXGI_FORMAT_R32G32_FLOAT, 0, (UINT)IM_OFFSETOF(ImDrawVert, uv), D3D12_INPUT_CLASSIFICATION_PER_VERTEX_DATA, 0 }, - { "COLOR", 0, DXGI_FORMAT_R8G8B8A8_UNORM, 0, (UINT)IM_OFFSETOF(ImDrawVert, col), D3D12_INPUT_CLASSIFICATION_PER_VERTEX_DATA, 0 }, - }; - psoDesc.InputLayout = { local_layout, 3 }; - } - - // Create the pixel shader - { - static const char* pixelShader = - "struct PS_INPUT\ - {\ - float4 pos : SV_POSITION;\ - float4 col : COLOR0;\ - float2 uv : TEXCOORD0;\ - };\ - SamplerState sampler0 : register(s0);\ - Texture2D texture0 : register(t0);\ - \ - float4 main(PS_INPUT input) : SV_Target\ - {\ - float4 out_col = input.col * texture0.Sample(sampler0, input.uv); \ - return out_col; \ - }"; - - if (FAILED(D3DCompile(pixelShader, strlen(pixelShader), nullptr, nullptr, nullptr, "main", "ps_5_0", 0, 0, &pixelShaderBlob, nullptr))) - { - vertexShaderBlob->Release(); - return false; // NB: Pass ID3DBlob* pErrorBlob to D3DCompile() to get error showing in (const char*)pErrorBlob->GetBufferPointer(). Make sure to Release() the blob! - } - psoDesc.PS = { pixelShaderBlob->GetBufferPointer(), pixelShaderBlob->GetBufferSize() }; - } - - // Create the blending setup - { - D3D12_BLEND_DESC& desc = psoDesc.BlendState; - desc.AlphaToCoverageEnable = false; - desc.RenderTarget[0].BlendEnable = true; - desc.RenderTarget[0].SrcBlend = D3D12_BLEND_SRC_ALPHA; - desc.RenderTarget[0].DestBlend = D3D12_BLEND_INV_SRC_ALPHA; - desc.RenderTarget[0].BlendOp = D3D12_BLEND_OP_ADD; - desc.RenderTarget[0].SrcBlendAlpha = D3D12_BLEND_ONE; - desc.RenderTarget[0].DestBlendAlpha = D3D12_BLEND_INV_SRC_ALPHA; - desc.RenderTarget[0].BlendOpAlpha = D3D12_BLEND_OP_ADD; - desc.RenderTarget[0].RenderTargetWriteMask = D3D12_COLOR_WRITE_ENABLE_ALL; - } - - // Create the rasterizer state - { - D3D12_RASTERIZER_DESC& desc = psoDesc.RasterizerState; - desc.FillMode = D3D12_FILL_MODE_SOLID; - desc.CullMode = D3D12_CULL_MODE_NONE; - desc.FrontCounterClockwise = FALSE; - desc.DepthBias = D3D12_DEFAULT_DEPTH_BIAS; - desc.DepthBiasClamp = D3D12_DEFAULT_DEPTH_BIAS_CLAMP; - desc.SlopeScaledDepthBias = D3D12_DEFAULT_SLOPE_SCALED_DEPTH_BIAS; - desc.DepthClipEnable = true; - desc.MultisampleEnable = FALSE; - desc.AntialiasedLineEnable = FALSE; - desc.ForcedSampleCount = 0; - desc.ConservativeRaster = D3D12_CONSERVATIVE_RASTERIZATION_MODE_OFF; - } - - // Create depth-stencil State - { - D3D12_DEPTH_STENCIL_DESC& desc = psoDesc.DepthStencilState; - desc.DepthEnable = false; - desc.DepthWriteMask = D3D12_DEPTH_WRITE_MASK_ALL; - desc.DepthFunc = D3D12_COMPARISON_FUNC_ALWAYS; - desc.StencilEnable = false; - desc.FrontFace.StencilFailOp = desc.FrontFace.StencilDepthFailOp = desc.FrontFace.StencilPassOp = D3D12_STENCIL_OP_KEEP; - desc.FrontFace.StencilFunc = D3D12_COMPARISON_FUNC_ALWAYS; - desc.BackFace = desc.FrontFace; - } - - HRESULT result_pipeline_state = bd->pd3dDevice->CreateGraphicsPipelineState(&psoDesc, IID_PPV_ARGS(&bd->pPipelineState)); - vertexShaderBlob->Release(); - pixelShaderBlob->Release(); - if (result_pipeline_state != S_OK) - return false; - - ImGui_ImplDX12_CreateFontsTexture(); - - return true; -} - -static void ImGui_ImplDX12_DestroyRenderBuffers(ImGui_ImplDX12_RenderBuffers* render_buffers) -{ - SafeRelease(render_buffers->IndexBuffer); - SafeRelease(render_buffers->VertexBuffer); - render_buffers->IndexBufferSize = render_buffers->VertexBufferSize = 0; -} - -void ImGui_ImplDX12_InvalidateDeviceObjects() -{ - ImGui_ImplDX12_Data* bd = ImGui_ImplDX12_GetBackendData(); - if (!bd || !bd->pd3dDevice) - return; - - ImGuiIO& io = ImGui::GetIO(); - SafeRelease(bd->pRootSignature); - SafeRelease(bd->pPipelineState); - SafeRelease(bd->pFontTextureResource); - io.Fonts->SetTexID(0); // We copied bd->pFontTextureView to io.Fonts->TexID so let's clear that as well. -} - -bool ImGui_ImplDX12_Init(ID3D12Device* device, int num_frames_in_flight, DXGI_FORMAT rtv_format, ID3D12DescriptorHeap* cbv_srv_heap, - D3D12_CPU_DESCRIPTOR_HANDLE font_srv_cpu_desc_handle, D3D12_GPU_DESCRIPTOR_HANDLE font_srv_gpu_desc_handle) -{ - ImGuiIO& io = ImGui::GetIO(); - IM_ASSERT(io.BackendRendererUserData == nullptr && "Already initialized a renderer backend!"); - - // Setup backend capabilities flags - ImGui_ImplDX12_Data* bd = IM_NEW(ImGui_ImplDX12_Data)(); - io.BackendRendererUserData = (void*)bd; - io.BackendRendererName = "imgui_impl_dx12"; - io.BackendFlags |= ImGuiBackendFlags_RendererHasVtxOffset; // We can honor the ImDrawCmd::VtxOffset field, allowing for large meshes. - io.BackendFlags |= ImGuiBackendFlags_RendererHasViewports; // We can create multi-viewports on the Renderer side (optional) - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - ImGui_ImplDX12_InitPlatformInterface(); - - bd->pd3dDevice = device; - bd->RTVFormat = rtv_format; - bd->hFontSrvCpuDescHandle = font_srv_cpu_desc_handle; - bd->hFontSrvGpuDescHandle = font_srv_gpu_desc_handle; - bd->numFramesInFlight = num_frames_in_flight; - bd->pd3dSrvDescHeap = cbv_srv_heap; - - // Create a dummy ImGui_ImplDX12_ViewportData holder for the main viewport, - // Since this is created and managed by the application, we will only use the ->Resources[] fields. - ImGuiViewport* main_viewport = ImGui::GetMainViewport(); - main_viewport->RendererUserData = IM_NEW(ImGui_ImplDX12_ViewportData)(bd->numFramesInFlight); - - return true; -} - -void ImGui_ImplDX12_Shutdown() -{ - ImGui_ImplDX12_Data* bd = ImGui_ImplDX12_GetBackendData(); - IM_ASSERT(bd != nullptr && "No renderer backend to shutdown, or already shutdown?"); - ImGuiIO& io = ImGui::GetIO(); - - // Manually delete main viewport render resources in-case we haven't initialized for viewports - ImGuiViewport* main_viewport = ImGui::GetMainViewport(); - if (ImGui_ImplDX12_ViewportData* vd = (ImGui_ImplDX12_ViewportData*)main_viewport->RendererUserData) - { - // We could just call ImGui_ImplDX12_DestroyWindow(main_viewport) as a convenience but that would be misleading since we only use data->Resources[] - for (UINT i = 0; i < bd->numFramesInFlight; i++) - ImGui_ImplDX12_DestroyRenderBuffers(&vd->FrameRenderBuffers[i]); - IM_DELETE(vd); - main_viewport->RendererUserData = nullptr; - } - - // Clean up windows and device objects - ImGui_ImplDX12_ShutdownPlatformInterface(); - ImGui_ImplDX12_InvalidateDeviceObjects(); - - io.BackendRendererName = nullptr; - io.BackendRendererUserData = nullptr; - io.BackendFlags &= ~(ImGuiBackendFlags_RendererHasVtxOffset | ImGuiBackendFlags_RendererHasViewports); - IM_DELETE(bd); -} - -void ImGui_ImplDX12_NewFrame() -{ - ImGui_ImplDX12_Data* bd = ImGui_ImplDX12_GetBackendData(); - IM_ASSERT(bd != nullptr && "Did you call ImGui_ImplDX12_Init()?"); - - if (!bd->pPipelineState) - ImGui_ImplDX12_CreateDeviceObjects(); -} - -//-------------------------------------------------------------------------------------------------------- -// MULTI-VIEWPORT / PLATFORM INTERFACE SUPPORT -// This is an _advanced_ and _optional_ feature, allowing the backend to create and handle multiple viewports simultaneously. -// If you are new to dear imgui or creating a new binding for dear imgui, it is recommended that you completely ignore this section first.. -//-------------------------------------------------------------------------------------------------------- - -static void ImGui_ImplDX12_CreateWindow(ImGuiViewport* viewport) -{ - ImGui_ImplDX12_Data* bd = ImGui_ImplDX12_GetBackendData(); - ImGui_ImplDX12_ViewportData* vd = IM_NEW(ImGui_ImplDX12_ViewportData)(bd->numFramesInFlight); - viewport->RendererUserData = vd; - - // PlatformHandleRaw should always be a HWND, whereas PlatformHandle might be a higher-level handle (e.g. GLFWWindow*, SDL_Window*). - // Some backends will leave PlatformHandleRaw == 0, in which case we assume PlatformHandle will contain the HWND. - HWND hwnd = viewport->PlatformHandleRaw ? (HWND)viewport->PlatformHandleRaw : (HWND)viewport->PlatformHandle; - IM_ASSERT(hwnd != 0); - - vd->FrameIndex = UINT_MAX; - - // Create command queue. - D3D12_COMMAND_QUEUE_DESC queue_desc = {}; - queue_desc.Flags = D3D12_COMMAND_QUEUE_FLAG_NONE; - queue_desc.Type = D3D12_COMMAND_LIST_TYPE_DIRECT; - - HRESULT res = S_OK; - res = bd->pd3dDevice->CreateCommandQueue(&queue_desc, IID_PPV_ARGS(&vd->CommandQueue)); - IM_ASSERT(res == S_OK); - - // Create command allocator. - for (UINT i = 0; i < bd->numFramesInFlight; ++i) - { - res = bd->pd3dDevice->CreateCommandAllocator(D3D12_COMMAND_LIST_TYPE_DIRECT, IID_PPV_ARGS(&vd->FrameCtx[i].CommandAllocator)); - IM_ASSERT(res == S_OK); - } - - // Create command list. - res = bd->pd3dDevice->CreateCommandList(0, D3D12_COMMAND_LIST_TYPE_DIRECT, vd->FrameCtx[0].CommandAllocator, nullptr, IID_PPV_ARGS(&vd->CommandList)); - IM_ASSERT(res == S_OK); - vd->CommandList->Close(); - - // Create fence. - res = bd->pd3dDevice->CreateFence(0, D3D12_FENCE_FLAG_NONE, IID_PPV_ARGS(&vd->Fence)); - IM_ASSERT(res == S_OK); - - vd->FenceEvent = CreateEvent(nullptr, FALSE, FALSE, nullptr); - IM_ASSERT(vd->FenceEvent != nullptr); - - // Create swap chain - // FIXME-VIEWPORT: May want to copy/inherit swap chain settings from the user/application. - DXGI_SWAP_CHAIN_DESC1 sd1; - ZeroMemory(&sd1, sizeof(sd1)); - sd1.BufferCount = bd->numFramesInFlight; - sd1.Width = (UINT)viewport->Size.x; - sd1.Height = (UINT)viewport->Size.y; - sd1.Format = bd->RTVFormat; - sd1.BufferUsage = DXGI_USAGE_RENDER_TARGET_OUTPUT; - sd1.SampleDesc.Count = 1; - sd1.SampleDesc.Quality = 0; - sd1.SwapEffect = DXGI_SWAP_EFFECT_FLIP_DISCARD; - sd1.AlphaMode = DXGI_ALPHA_MODE_UNSPECIFIED; - sd1.Scaling = DXGI_SCALING_STRETCH; - sd1.Stereo = FALSE; - - IDXGIFactory4* dxgi_factory = nullptr; - res = ::CreateDXGIFactory1(IID_PPV_ARGS(&dxgi_factory)); - IM_ASSERT(res == S_OK); - - IDXGISwapChain1* swap_chain = nullptr; - res = dxgi_factory->CreateSwapChainForHwnd(vd->CommandQueue, hwnd, &sd1, nullptr, nullptr, &swap_chain); - IM_ASSERT(res == S_OK); - - dxgi_factory->Release(); - - // Or swapChain.As(&mSwapChain) - IM_ASSERT(vd->SwapChain == nullptr); - swap_chain->QueryInterface(IID_PPV_ARGS(&vd->SwapChain)); - swap_chain->Release(); - - // Create the render targets - if (vd->SwapChain) - { - D3D12_DESCRIPTOR_HEAP_DESC desc = {}; - desc.Type = D3D12_DESCRIPTOR_HEAP_TYPE_RTV; - desc.NumDescriptors = bd->numFramesInFlight; - desc.Flags = D3D12_DESCRIPTOR_HEAP_FLAG_NONE; - desc.NodeMask = 1; - - HRESULT hr = bd->pd3dDevice->CreateDescriptorHeap(&desc, IID_PPV_ARGS(&vd->RtvDescHeap)); - IM_ASSERT(hr == S_OK); - - SIZE_T rtv_descriptor_size = bd->pd3dDevice->GetDescriptorHandleIncrementSize(D3D12_DESCRIPTOR_HEAP_TYPE_RTV); - D3D12_CPU_DESCRIPTOR_HANDLE rtv_handle = vd->RtvDescHeap->GetCPUDescriptorHandleForHeapStart(); - for (UINT i = 0; i < bd->numFramesInFlight; i++) - { - vd->FrameCtx[i].RenderTargetCpuDescriptors = rtv_handle; - rtv_handle.ptr += rtv_descriptor_size; - } - - ID3D12Resource* back_buffer; - for (UINT i = 0; i < bd->numFramesInFlight; i++) - { - IM_ASSERT(vd->FrameCtx[i].RenderTarget == nullptr); - vd->SwapChain->GetBuffer(i, IID_PPV_ARGS(&back_buffer)); - bd->pd3dDevice->CreateRenderTargetView(back_buffer, nullptr, vd->FrameCtx[i].RenderTargetCpuDescriptors); - vd->FrameCtx[i].RenderTarget = back_buffer; - } - } - - for (UINT i = 0; i < bd->numFramesInFlight; i++) - ImGui_ImplDX12_DestroyRenderBuffers(&vd->FrameRenderBuffers[i]); -} - -static void ImGui_WaitForPendingOperations(ImGui_ImplDX12_ViewportData* vd) -{ - HRESULT hr = S_FALSE; - if (vd && vd->CommandQueue && vd->Fence && vd->FenceEvent) - { - hr = vd->CommandQueue->Signal(vd->Fence, ++vd->FenceSignaledValue); - IM_ASSERT(hr == S_OK); - ::WaitForSingleObject(vd->FenceEvent, 0); // Reset any forgotten waits - hr = vd->Fence->SetEventOnCompletion(vd->FenceSignaledValue, vd->FenceEvent); - IM_ASSERT(hr == S_OK); - ::WaitForSingleObject(vd->FenceEvent, INFINITE); - } -} - -static void ImGui_ImplDX12_DestroyWindow(ImGuiViewport* viewport) -{ - // The main viewport (owned by the application) will always have RendererUserData == 0 since we didn't create the data for it. - ImGui_ImplDX12_Data* bd = ImGui_ImplDX12_GetBackendData(); - if (ImGui_ImplDX12_ViewportData* vd = (ImGui_ImplDX12_ViewportData*)viewport->RendererUserData) - { - ImGui_WaitForPendingOperations(vd); - - SafeRelease(vd->CommandQueue); - SafeRelease(vd->CommandList); - SafeRelease(vd->SwapChain); - SafeRelease(vd->RtvDescHeap); - SafeRelease(vd->Fence); - ::CloseHandle(vd->FenceEvent); - vd->FenceEvent = nullptr; - - for (UINT i = 0; i < bd->numFramesInFlight; i++) - { - SafeRelease(vd->FrameCtx[i].RenderTarget); - SafeRelease(vd->FrameCtx[i].CommandAllocator); - ImGui_ImplDX12_DestroyRenderBuffers(&vd->FrameRenderBuffers[i]); - } - IM_DELETE(vd); - } - viewport->RendererUserData = nullptr; -} - -static void ImGui_ImplDX12_SetWindowSize(ImGuiViewport* viewport, ImVec2 size) -{ - ImGui_ImplDX12_Data* bd = ImGui_ImplDX12_GetBackendData(); - ImGui_ImplDX12_ViewportData* vd = (ImGui_ImplDX12_ViewportData*)viewport->RendererUserData; - - ImGui_WaitForPendingOperations(vd); - - for (UINT i = 0; i < bd->numFramesInFlight; i++) - SafeRelease(vd->FrameCtx[i].RenderTarget); - - if (vd->SwapChain) - { - ID3D12Resource* back_buffer = nullptr; - vd->SwapChain->ResizeBuffers(0, (UINT)size.x, (UINT)size.y, DXGI_FORMAT_UNKNOWN, 0); - for (UINT i = 0; i < bd->numFramesInFlight; i++) - { - vd->SwapChain->GetBuffer(i, IID_PPV_ARGS(&back_buffer)); - bd->pd3dDevice->CreateRenderTargetView(back_buffer, nullptr, vd->FrameCtx[i].RenderTargetCpuDescriptors); - vd->FrameCtx[i].RenderTarget = back_buffer; - } - } -} - -static void ImGui_ImplDX12_RenderWindow(ImGuiViewport* viewport, void*) -{ - ImGui_ImplDX12_Data* bd = ImGui_ImplDX12_GetBackendData(); - ImGui_ImplDX12_ViewportData* vd = (ImGui_ImplDX12_ViewportData*)viewport->RendererUserData; - - ImGui_ImplDX12_FrameContext* frame_context = &vd->FrameCtx[vd->FrameIndex % bd->numFramesInFlight]; - UINT back_buffer_idx = vd->SwapChain->GetCurrentBackBufferIndex(); - - const ImVec4 clear_color = ImVec4(0.0f, 0.0f, 0.0f, 1.0f); - D3D12_RESOURCE_BARRIER barrier = {}; - barrier.Type = D3D12_RESOURCE_BARRIER_TYPE_TRANSITION; - barrier.Flags = D3D12_RESOURCE_BARRIER_FLAG_NONE; - barrier.Transition.pResource = vd->FrameCtx[back_buffer_idx].RenderTarget; - barrier.Transition.Subresource = D3D12_RESOURCE_BARRIER_ALL_SUBRESOURCES; - barrier.Transition.StateBefore = D3D12_RESOURCE_STATE_PRESENT; - barrier.Transition.StateAfter = D3D12_RESOURCE_STATE_RENDER_TARGET; - - // Draw - ID3D12GraphicsCommandList* cmd_list = vd->CommandList; - - frame_context->CommandAllocator->Reset(); - cmd_list->Reset(frame_context->CommandAllocator, nullptr); - cmd_list->ResourceBarrier(1, &barrier); - cmd_list->OMSetRenderTargets(1, &vd->FrameCtx[back_buffer_idx].RenderTargetCpuDescriptors, FALSE, nullptr); - if (!(viewport->Flags & ImGuiViewportFlags_NoRendererClear)) - cmd_list->ClearRenderTargetView(vd->FrameCtx[back_buffer_idx].RenderTargetCpuDescriptors, (float*)&clear_color, 0, nullptr); - cmd_list->SetDescriptorHeaps(1, &bd->pd3dSrvDescHeap); - - ImGui_ImplDX12_RenderDrawData(viewport->DrawData, cmd_list); - - barrier.Transition.StateBefore = D3D12_RESOURCE_STATE_RENDER_TARGET; - barrier.Transition.StateAfter = D3D12_RESOURCE_STATE_PRESENT; - cmd_list->ResourceBarrier(1, &barrier); - cmd_list->Close(); - - vd->CommandQueue->Wait(vd->Fence, vd->FenceSignaledValue); - vd->CommandQueue->ExecuteCommandLists(1, (ID3D12CommandList* const*)&cmd_list); - vd->CommandQueue->Signal(vd->Fence, ++vd->FenceSignaledValue); -} - -static void ImGui_ImplDX12_SwapBuffers(ImGuiViewport* viewport, void*) -{ - ImGui_ImplDX12_ViewportData* vd = (ImGui_ImplDX12_ViewportData*)viewport->RendererUserData; - - vd->SwapChain->Present(0, 0); - while (vd->Fence->GetCompletedValue() < vd->FenceSignaledValue) - ::SwitchToThread(); -} - -void ImGui_ImplDX12_InitPlatformInterface() -{ - ImGuiPlatformIO& platform_io = ImGui::GetPlatformIO(); - platform_io.Renderer_CreateWindow = ImGui_ImplDX12_CreateWindow; - platform_io.Renderer_DestroyWindow = ImGui_ImplDX12_DestroyWindow; - platform_io.Renderer_SetWindowSize = ImGui_ImplDX12_SetWindowSize; - platform_io.Renderer_RenderWindow = ImGui_ImplDX12_RenderWindow; - platform_io.Renderer_SwapBuffers = ImGui_ImplDX12_SwapBuffers; -} - -void ImGui_ImplDX12_ShutdownPlatformInterface() -{ - ImGui::DestroyPlatformWindows(); -} - -//----------------------------------------------------------------------------- - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_dx12.h b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_dx12.h deleted file mode 100644 index f304cca..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_dx12.h +++ /dev/null @@ -1,45 +0,0 @@ -// dear imgui: Renderer Backend for DirectX12 -// This needs to be used along with a Platform Backend (e.g. Win32) - -// Implemented features: -// [X] Renderer: User texture binding. Use 'D3D12_GPU_DESCRIPTOR_HANDLE' as ImTextureID. Read the FAQ about ImTextureID! -// [X] Renderer: Large meshes support (64k+ vertices) with 16-bit indices. -// [X] Renderer: Multi-viewport support (multiple windows). Enable with 'io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable'. - -// Important: to compile on 32-bit systems, this backend requires code to be compiled with '#define ImTextureID ImU64'. -// See imgui_impl_dx12.cpp file for details. - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#pragma once -#include "imgui.h" // IMGUI_IMPL_API -#ifndef IMGUI_DISABLE -#include // DXGI_FORMAT - -struct ID3D12Device; -struct ID3D12DescriptorHeap; -struct ID3D12GraphicsCommandList; -struct D3D12_CPU_DESCRIPTOR_HANDLE; -struct D3D12_GPU_DESCRIPTOR_HANDLE; - -// cmd_list is the command list that the implementation will use to render imgui draw lists. -// Before calling the render function, caller must prepare cmd_list by resetting it and setting the appropriate -// render target and descriptor heap that contains font_srv_cpu_desc_handle/font_srv_gpu_desc_handle. -// font_srv_cpu_desc_handle and font_srv_gpu_desc_handle are handles to a single SRV descriptor to use for the internal font texture. -IMGUI_IMPL_API bool ImGui_ImplDX12_Init(ID3D12Device* device, int num_frames_in_flight, DXGI_FORMAT rtv_format, ID3D12DescriptorHeap* cbv_srv_heap, - D3D12_CPU_DESCRIPTOR_HANDLE font_srv_cpu_desc_handle, D3D12_GPU_DESCRIPTOR_HANDLE font_srv_gpu_desc_handle); -IMGUI_IMPL_API void ImGui_ImplDX12_Shutdown(); -IMGUI_IMPL_API void ImGui_ImplDX12_NewFrame(); -IMGUI_IMPL_API void ImGui_ImplDX12_RenderDrawData(ImDrawData* draw_data, ID3D12GraphicsCommandList* graphics_command_list); - -// Use if you want to reset your rendering device without losing Dear ImGui state. -IMGUI_IMPL_API void ImGui_ImplDX12_InvalidateDeviceObjects(); -IMGUI_IMPL_API bool ImGui_ImplDX12_CreateDeviceObjects(); - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_dx9.cpp b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_dx9.cpp deleted file mode 100644 index 0aeb43d..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_dx9.cpp +++ /dev/null @@ -1,550 +0,0 @@ -// dear imgui: Renderer Backend for DirectX9 -// This needs to be used along with a Platform Backend (e.g. Win32) - -// Implemented features: -// [X] Renderer: User texture binding. Use 'LPDIRECT3DTEXTURE9' as ImTextureID. Read the FAQ about ImTextureID! -// [X] Renderer: Large meshes support (64k+ vertices) with 16-bit indices. -// [X] Renderer: Multi-viewport support (multiple windows). Enable with 'io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable'. - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -// CHANGELOG -// (minor and older changes stripped away, please see git history for details) -// 2023-XX-XX: Platform: Added support for multiple windows via the ImGuiPlatformIO interface. -// 2022-10-11: Using 'nullptr' instead of 'NULL' as per our switch to C++11. -// 2021-06-29: Reorganized backend to pull data from a single structure to facilitate usage with multiple-contexts (all g_XXXX access changed to bd->XXXX). -// 2021-06-25: DirectX9: Explicitly disable texture state stages after >= 1. -// 2021-05-19: DirectX9: Replaced direct access to ImDrawCmd::TextureId with a call to ImDrawCmd::GetTexID(). (will become a requirement) -// 2021-04-23: DirectX9: Explicitly setting up more graphics states to increase compatibility with unusual non-default states. -// 2021-03-18: DirectX9: Calling IDirect3DStateBlock9::Capture() after CreateStateBlock() as a workaround for state restoring issues (see #3857). -// 2021-03-03: DirectX9: Added support for IMGUI_USE_BGRA_PACKED_COLOR in user's imconfig file. -// 2021-02-18: DirectX9: Change blending equation to preserve alpha in output buffer. -// 2019-05-29: DirectX9: Added support for large mesh (64K+ vertices), enable ImGuiBackendFlags_RendererHasVtxOffset flag. -// 2019-04-30: DirectX9: Added support for special ImDrawCallback_ResetRenderState callback to reset render state. -// 2019-03-29: Misc: Fixed erroneous assert in ImGui_ImplDX9_InvalidateDeviceObjects(). -// 2019-01-16: Misc: Disabled fog before drawing UI's. Fixes issue #2288. -// 2018-11-30: Misc: Setting up io.BackendRendererName so it can be displayed in the About Window. -// 2018-06-08: Misc: Extracted imgui_impl_dx9.cpp/.h away from the old combined DX9+Win32 example. -// 2018-06-08: DirectX9: Use draw_data->DisplayPos and draw_data->DisplaySize to setup projection matrix and clipping rectangle. -// 2018-05-07: Render: Saving/restoring Transform because they don't seem to be included in the StateBlock. Setting shading mode to Gouraud. -// 2018-02-16: Misc: Obsoleted the io.RenderDrawListsFn callback and exposed ImGui_ImplDX9_RenderDrawData() in the .h file so you can call it yourself. -// 2018-02-06: Misc: Removed call to ImGui::Shutdown() which is not available from 1.60 WIP, user needs to call CreateContext/DestroyContext themselves. - -#include "imgui.h" -#ifndef IMGUI_DISABLE -#include "imgui_impl_dx9.h" - -// DirectX -#include - -// DirectX data -struct ImGui_ImplDX9_Data -{ - LPDIRECT3DDEVICE9 pd3dDevice; - LPDIRECT3DVERTEXBUFFER9 pVB; - LPDIRECT3DINDEXBUFFER9 pIB; - LPDIRECT3DTEXTURE9 FontTexture; - int VertexBufferSize; - int IndexBufferSize; - - ImGui_ImplDX9_Data() { memset((void*)this, 0, sizeof(*this)); VertexBufferSize = 5000; IndexBufferSize = 10000; } -}; - -struct CUSTOMVERTEX -{ - float pos[3]; - D3DCOLOR col; - float uv[2]; -}; -#define D3DFVF_CUSTOMVERTEX (D3DFVF_XYZ|D3DFVF_DIFFUSE|D3DFVF_TEX1) - -#ifdef IMGUI_USE_BGRA_PACKED_COLOR -#define IMGUI_COL_TO_DX9_ARGB(_COL) (_COL) -#else -#define IMGUI_COL_TO_DX9_ARGB(_COL) (((_COL) & 0xFF00FF00) | (((_COL) & 0xFF0000) >> 16) | (((_COL) & 0xFF) << 16)) -#endif - -// Backend data stored in io.BackendRendererUserData to allow support for multiple Dear ImGui contexts -// It is STRONGLY preferred that you use docking branch with multi-viewports (== single Dear ImGui context + multiple windows) instead of multiple Dear ImGui contexts. -static ImGui_ImplDX9_Data* ImGui_ImplDX9_GetBackendData() -{ - return ImGui::GetCurrentContext() ? (ImGui_ImplDX9_Data*)ImGui::GetIO().BackendRendererUserData : nullptr; -} - -// Forward Declarations -static void ImGui_ImplDX9_InitPlatformInterface(); -static void ImGui_ImplDX9_ShutdownPlatformInterface(); -static void ImGui_ImplDX9_CreateDeviceObjectsForPlatformWindows(); -static void ImGui_ImplDX9_InvalidateDeviceObjectsForPlatformWindows(); - -// Functions -static void ImGui_ImplDX9_SetupRenderState(ImDrawData* draw_data) -{ - ImGui_ImplDX9_Data* bd = ImGui_ImplDX9_GetBackendData(); - - // Setup viewport - D3DVIEWPORT9 vp; - vp.X = vp.Y = 0; - vp.Width = (DWORD)draw_data->DisplaySize.x; - vp.Height = (DWORD)draw_data->DisplaySize.y; - vp.MinZ = 0.0f; - vp.MaxZ = 1.0f; - bd->pd3dDevice->SetViewport(&vp); - - // Setup render state: fixed-pipeline, alpha-blending, no face culling, no depth testing, shade mode (for gradient), bilinear sampling. - bd->pd3dDevice->SetPixelShader(nullptr); - bd->pd3dDevice->SetVertexShader(nullptr); - bd->pd3dDevice->SetRenderState(D3DRS_FILLMODE, D3DFILL_SOLID); - bd->pd3dDevice->SetRenderState(D3DRS_SHADEMODE, D3DSHADE_GOURAUD); - bd->pd3dDevice->SetRenderState(D3DRS_ZWRITEENABLE, FALSE); - bd->pd3dDevice->SetRenderState(D3DRS_ALPHATESTENABLE, FALSE); - bd->pd3dDevice->SetRenderState(D3DRS_CULLMODE, D3DCULL_NONE); - bd->pd3dDevice->SetRenderState(D3DRS_ZENABLE, FALSE); - bd->pd3dDevice->SetRenderState(D3DRS_ALPHABLENDENABLE, TRUE); - bd->pd3dDevice->SetRenderState(D3DRS_BLENDOP, D3DBLENDOP_ADD); - bd->pd3dDevice->SetRenderState(D3DRS_SRCBLEND, D3DBLEND_SRCALPHA); - bd->pd3dDevice->SetRenderState(D3DRS_DESTBLEND, D3DBLEND_INVSRCALPHA); - bd->pd3dDevice->SetRenderState(D3DRS_SEPARATEALPHABLENDENABLE, TRUE); - bd->pd3dDevice->SetRenderState(D3DRS_SRCBLENDALPHA, D3DBLEND_ONE); - bd->pd3dDevice->SetRenderState(D3DRS_DESTBLENDALPHA, D3DBLEND_INVSRCALPHA); - bd->pd3dDevice->SetRenderState(D3DRS_SCISSORTESTENABLE, TRUE); - bd->pd3dDevice->SetRenderState(D3DRS_FOGENABLE, FALSE); - bd->pd3dDevice->SetRenderState(D3DRS_RANGEFOGENABLE, FALSE); - bd->pd3dDevice->SetRenderState(D3DRS_SPECULARENABLE, FALSE); - bd->pd3dDevice->SetRenderState(D3DRS_STENCILENABLE, FALSE); - bd->pd3dDevice->SetRenderState(D3DRS_CLIPPING, TRUE); - bd->pd3dDevice->SetRenderState(D3DRS_LIGHTING, FALSE); - bd->pd3dDevice->SetTextureStageState(0, D3DTSS_COLOROP, D3DTOP_MODULATE); - bd->pd3dDevice->SetTextureStageState(0, D3DTSS_COLORARG1, D3DTA_TEXTURE); - bd->pd3dDevice->SetTextureStageState(0, D3DTSS_COLORARG2, D3DTA_DIFFUSE); - bd->pd3dDevice->SetTextureStageState(0, D3DTSS_ALPHAOP, D3DTOP_MODULATE); - bd->pd3dDevice->SetTextureStageState(0, D3DTSS_ALPHAARG1, D3DTA_TEXTURE); - bd->pd3dDevice->SetTextureStageState(0, D3DTSS_ALPHAARG2, D3DTA_DIFFUSE); - bd->pd3dDevice->SetTextureStageState(1, D3DTSS_COLOROP, D3DTOP_DISABLE); - bd->pd3dDevice->SetTextureStageState(1, D3DTSS_ALPHAOP, D3DTOP_DISABLE); - bd->pd3dDevice->SetSamplerState(0, D3DSAMP_MINFILTER, D3DTEXF_LINEAR); - bd->pd3dDevice->SetSamplerState(0, D3DSAMP_MAGFILTER, D3DTEXF_LINEAR); - - // Setup orthographic projection matrix - // Our visible imgui space lies from draw_data->DisplayPos (top left) to draw_data->DisplayPos+data_data->DisplaySize (bottom right). DisplayPos is (0,0) for single viewport apps. - // Being agnostic of whether or can be used, we aren't relying on D3DXMatrixIdentity()/D3DXMatrixOrthoOffCenterLH() or DirectX::XMMatrixIdentity()/DirectX::XMMatrixOrthographicOffCenterLH() - { - float L = draw_data->DisplayPos.x + 0.5f; - float R = draw_data->DisplayPos.x + draw_data->DisplaySize.x + 0.5f; - float T = draw_data->DisplayPos.y + 0.5f; - float B = draw_data->DisplayPos.y + draw_data->DisplaySize.y + 0.5f; - D3DMATRIX mat_identity = { { { 1.0f, 0.0f, 0.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 0.0f, 0.0f, 1.0f } } }; - D3DMATRIX mat_projection = - { { { - 2.0f/(R-L), 0.0f, 0.0f, 0.0f, - 0.0f, 2.0f/(T-B), 0.0f, 0.0f, - 0.0f, 0.0f, 0.5f, 0.0f, - (L+R)/(L-R), (T+B)/(B-T), 0.5f, 1.0f - } } }; - bd->pd3dDevice->SetTransform(D3DTS_WORLD, &mat_identity); - bd->pd3dDevice->SetTransform(D3DTS_VIEW, &mat_identity); - bd->pd3dDevice->SetTransform(D3DTS_PROJECTION, &mat_projection); - } -} - -// Render function. -void ImGui_ImplDX9_RenderDrawData(ImDrawData* draw_data) -{ - // Avoid rendering when minimized - if (draw_data->DisplaySize.x <= 0.0f || draw_data->DisplaySize.y <= 0.0f) - return; - - // Create and grow buffers if needed - ImGui_ImplDX9_Data* bd = ImGui_ImplDX9_GetBackendData(); - if (!bd->pVB || bd->VertexBufferSize < draw_data->TotalVtxCount) - { - if (bd->pVB) { bd->pVB->Release(); bd->pVB = nullptr; } - bd->VertexBufferSize = draw_data->TotalVtxCount + 5000; - if (bd->pd3dDevice->CreateVertexBuffer(bd->VertexBufferSize * sizeof(CUSTOMVERTEX), D3DUSAGE_DYNAMIC | D3DUSAGE_WRITEONLY, D3DFVF_CUSTOMVERTEX, D3DPOOL_DEFAULT, &bd->pVB, nullptr) < 0) - return; - } - if (!bd->pIB || bd->IndexBufferSize < draw_data->TotalIdxCount) - { - if (bd->pIB) { bd->pIB->Release(); bd->pIB = nullptr; } - bd->IndexBufferSize = draw_data->TotalIdxCount + 10000; - if (bd->pd3dDevice->CreateIndexBuffer(bd->IndexBufferSize * sizeof(ImDrawIdx), D3DUSAGE_DYNAMIC | D3DUSAGE_WRITEONLY, sizeof(ImDrawIdx) == 2 ? D3DFMT_INDEX16 : D3DFMT_INDEX32, D3DPOOL_DEFAULT, &bd->pIB, nullptr) < 0) - return; - } - - // Backup the DX9 state - IDirect3DStateBlock9* d3d9_state_block = nullptr; - if (bd->pd3dDevice->CreateStateBlock(D3DSBT_ALL, &d3d9_state_block) < 0) - return; - if (d3d9_state_block->Capture() < 0) - { - d3d9_state_block->Release(); - return; - } - - // Backup the DX9 transform (DX9 documentation suggests that it is included in the StateBlock but it doesn't appear to) - D3DMATRIX last_world, last_view, last_projection; - bd->pd3dDevice->GetTransform(D3DTS_WORLD, &last_world); - bd->pd3dDevice->GetTransform(D3DTS_VIEW, &last_view); - bd->pd3dDevice->GetTransform(D3DTS_PROJECTION, &last_projection); - - // Allocate buffers - CUSTOMVERTEX* vtx_dst; - ImDrawIdx* idx_dst; - if (bd->pVB->Lock(0, (UINT)(draw_data->TotalVtxCount * sizeof(CUSTOMVERTEX)), (void**)&vtx_dst, D3DLOCK_DISCARD) < 0) - { - d3d9_state_block->Release(); - return; - } - if (bd->pIB->Lock(0, (UINT)(draw_data->TotalIdxCount * sizeof(ImDrawIdx)), (void**)&idx_dst, D3DLOCK_DISCARD) < 0) - { - bd->pVB->Unlock(); - d3d9_state_block->Release(); - return; - } - - // Copy and convert all vertices into a single contiguous buffer, convert colors to DX9 default format. - // FIXME-OPT: This is a minor waste of resource, the ideal is to use imconfig.h and - // 1) to avoid repacking colors: #define IMGUI_USE_BGRA_PACKED_COLOR - // 2) to avoid repacking vertices: #define IMGUI_OVERRIDE_DRAWVERT_STRUCT_LAYOUT struct ImDrawVert { ImVec2 pos; float z; ImU32 col; ImVec2 uv; } - for (int n = 0; n < draw_data->CmdListsCount; n++) - { - const ImDrawList* cmd_list = draw_data->CmdLists[n]; - const ImDrawVert* vtx_src = cmd_list->VtxBuffer.Data; - for (int i = 0; i < cmd_list->VtxBuffer.Size; i++) - { - vtx_dst->pos[0] = vtx_src->pos.x; - vtx_dst->pos[1] = vtx_src->pos.y; - vtx_dst->pos[2] = 0.0f; - vtx_dst->col = IMGUI_COL_TO_DX9_ARGB(vtx_src->col); - vtx_dst->uv[0] = vtx_src->uv.x; - vtx_dst->uv[1] = vtx_src->uv.y; - vtx_dst++; - vtx_src++; - } - memcpy(idx_dst, cmd_list->IdxBuffer.Data, cmd_list->IdxBuffer.Size * sizeof(ImDrawIdx)); - idx_dst += cmd_list->IdxBuffer.Size; - } - bd->pVB->Unlock(); - bd->pIB->Unlock(); - bd->pd3dDevice->SetStreamSource(0, bd->pVB, 0, sizeof(CUSTOMVERTEX)); - bd->pd3dDevice->SetIndices(bd->pIB); - bd->pd3dDevice->SetFVF(D3DFVF_CUSTOMVERTEX); - - // Setup desired DX state - ImGui_ImplDX9_SetupRenderState(draw_data); - - // Render command lists - // (Because we merged all buffers into a single one, we maintain our own offset into them) - int global_vtx_offset = 0; - int global_idx_offset = 0; - ImVec2 clip_off = draw_data->DisplayPos; - for (int n = 0; n < draw_data->CmdListsCount; n++) - { - const ImDrawList* cmd_list = draw_data->CmdLists[n]; - for (int cmd_i = 0; cmd_i < cmd_list->CmdBuffer.Size; cmd_i++) - { - const ImDrawCmd* pcmd = &cmd_list->CmdBuffer[cmd_i]; - if (pcmd->UserCallback != nullptr) - { - // User callback, registered via ImDrawList::AddCallback() - // (ImDrawCallback_ResetRenderState is a special callback value used by the user to request the renderer to reset render state.) - if (pcmd->UserCallback == ImDrawCallback_ResetRenderState) - ImGui_ImplDX9_SetupRenderState(draw_data); - else - pcmd->UserCallback(cmd_list, pcmd); - } - else - { - // Project scissor/clipping rectangles into framebuffer space - ImVec2 clip_min(pcmd->ClipRect.x - clip_off.x, pcmd->ClipRect.y - clip_off.y); - ImVec2 clip_max(pcmd->ClipRect.z - clip_off.x, pcmd->ClipRect.w - clip_off.y); - if (clip_max.x <= clip_min.x || clip_max.y <= clip_min.y) - continue; - - // Apply Scissor/clipping rectangle, Bind texture, Draw - const RECT r = { (LONG)clip_min.x, (LONG)clip_min.y, (LONG)clip_max.x, (LONG)clip_max.y }; - const LPDIRECT3DTEXTURE9 texture = (LPDIRECT3DTEXTURE9)pcmd->GetTexID(); - bd->pd3dDevice->SetTexture(0, texture); - bd->pd3dDevice->SetScissorRect(&r); - bd->pd3dDevice->DrawIndexedPrimitive(D3DPT_TRIANGLELIST, pcmd->VtxOffset + global_vtx_offset, 0, (UINT)cmd_list->VtxBuffer.Size, pcmd->IdxOffset + global_idx_offset, pcmd->ElemCount / 3); - } - } - global_idx_offset += cmd_list->IdxBuffer.Size; - global_vtx_offset += cmd_list->VtxBuffer.Size; - } - - // When using multi-viewports, it appears that there's an odd logic in DirectX9 which prevent subsequent windows - // from rendering until the first window submits at least one draw call, even once. That's our workaround. (see #2560) - if (global_vtx_offset == 0) - bd->pd3dDevice->DrawIndexedPrimitive(D3DPT_TRIANGLELIST, 0, 0, 0, 0, 0); - - // Restore the DX9 transform - bd->pd3dDevice->SetTransform(D3DTS_WORLD, &last_world); - bd->pd3dDevice->SetTransform(D3DTS_VIEW, &last_view); - bd->pd3dDevice->SetTransform(D3DTS_PROJECTION, &last_projection); - - // Restore the DX9 state - d3d9_state_block->Apply(); - d3d9_state_block->Release(); -} - -bool ImGui_ImplDX9_Init(IDirect3DDevice9* device) -{ - ImGuiIO& io = ImGui::GetIO(); - IM_ASSERT(io.BackendRendererUserData == nullptr && "Already initialized a renderer backend!"); - - // Setup backend capabilities flags - ImGui_ImplDX9_Data* bd = IM_NEW(ImGui_ImplDX9_Data)(); - io.BackendRendererUserData = (void*)bd; - io.BackendRendererName = "imgui_impl_dx9"; - io.BackendFlags |= ImGuiBackendFlags_RendererHasVtxOffset; // We can honor the ImDrawCmd::VtxOffset field, allowing for large meshes. - io.BackendFlags |= ImGuiBackendFlags_RendererHasViewports; // We can create multi-viewports on the Renderer side (optional) - - bd->pd3dDevice = device; - bd->pd3dDevice->AddRef(); - - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - ImGui_ImplDX9_InitPlatformInterface(); - - return true; -} - -void ImGui_ImplDX9_Shutdown() -{ - ImGui_ImplDX9_Data* bd = ImGui_ImplDX9_GetBackendData(); - IM_ASSERT(bd != nullptr && "No renderer backend to shutdown, or already shutdown?"); - ImGuiIO& io = ImGui::GetIO(); - - ImGui_ImplDX9_ShutdownPlatformInterface(); - ImGui_ImplDX9_InvalidateDeviceObjects(); - if (bd->pd3dDevice) { bd->pd3dDevice->Release(); } - io.BackendRendererName = nullptr; - io.BackendRendererUserData = nullptr; - io.BackendFlags &= ~(ImGuiBackendFlags_RendererHasVtxOffset | ImGuiBackendFlags_RendererHasViewports); - IM_DELETE(bd); -} - -static bool ImGui_ImplDX9_CreateFontsTexture() -{ - // Build texture atlas - ImGuiIO& io = ImGui::GetIO(); - ImGui_ImplDX9_Data* bd = ImGui_ImplDX9_GetBackendData(); - unsigned char* pixels; - int width, height, bytes_per_pixel; - io.Fonts->GetTexDataAsRGBA32(&pixels, &width, &height, &bytes_per_pixel); - - // Convert RGBA32 to BGRA32 (because RGBA32 is not well supported by DX9 devices) -#ifndef IMGUI_USE_BGRA_PACKED_COLOR - if (io.Fonts->TexPixelsUseColors) - { - ImU32* dst_start = (ImU32*)ImGui::MemAlloc((size_t)width * height * bytes_per_pixel); - for (ImU32* src = (ImU32*)pixels, *dst = dst_start, *dst_end = dst_start + (size_t)width * height; dst < dst_end; src++, dst++) - *dst = IMGUI_COL_TO_DX9_ARGB(*src); - pixels = (unsigned char*)dst_start; - } -#endif - - // Upload texture to graphics system - bd->FontTexture = nullptr; - if (bd->pd3dDevice->CreateTexture(width, height, 1, D3DUSAGE_DYNAMIC, D3DFMT_A8R8G8B8, D3DPOOL_DEFAULT, &bd->FontTexture, nullptr) < 0) - return false; - D3DLOCKED_RECT tex_locked_rect; - if (bd->FontTexture->LockRect(0, &tex_locked_rect, nullptr, 0) != D3D_OK) - return false; - for (int y = 0; y < height; y++) - memcpy((unsigned char*)tex_locked_rect.pBits + (size_t)tex_locked_rect.Pitch * y, pixels + (size_t)width * bytes_per_pixel * y, (size_t)width * bytes_per_pixel); - bd->FontTexture->UnlockRect(0); - - // Store our identifier - io.Fonts->SetTexID((ImTextureID)bd->FontTexture); - -#ifndef IMGUI_USE_BGRA_PACKED_COLOR - if (io.Fonts->TexPixelsUseColors) - ImGui::MemFree(pixels); -#endif - - return true; -} - -bool ImGui_ImplDX9_CreateDeviceObjects() -{ - ImGui_ImplDX9_Data* bd = ImGui_ImplDX9_GetBackendData(); - if (!bd || !bd->pd3dDevice) - return false; - if (!ImGui_ImplDX9_CreateFontsTexture()) - return false; - ImGui_ImplDX9_CreateDeviceObjectsForPlatformWindows(); - return true; -} - -void ImGui_ImplDX9_InvalidateDeviceObjects() -{ - ImGui_ImplDX9_Data* bd = ImGui_ImplDX9_GetBackendData(); - if (!bd || !bd->pd3dDevice) - return; - if (bd->pVB) { bd->pVB->Release(); bd->pVB = nullptr; } - if (bd->pIB) { bd->pIB->Release(); bd->pIB = nullptr; } - if (bd->FontTexture) { bd->FontTexture->Release(); bd->FontTexture = nullptr; ImGui::GetIO().Fonts->SetTexID(0); } // We copied bd->pFontTextureView to io.Fonts->TexID so let's clear that as well. - ImGui_ImplDX9_InvalidateDeviceObjectsForPlatformWindows(); -} - -void ImGui_ImplDX9_NewFrame() -{ - ImGui_ImplDX9_Data* bd = ImGui_ImplDX9_GetBackendData(); - IM_ASSERT(bd != nullptr && "Did you call ImGui_ImplDX9_Init()?"); - - if (!bd->FontTexture) - ImGui_ImplDX9_CreateDeviceObjects(); -} - -//-------------------------------------------------------------------------------------------------------- -// MULTI-VIEWPORT / PLATFORM INTERFACE SUPPORT -// This is an _advanced_ and _optional_ feature, allowing the backend to create and handle multiple viewports simultaneously. -// If you are new to dear imgui or creating a new binding for dear imgui, it is recommended that you completely ignore this section first.. -//-------------------------------------------------------------------------------------------------------- - -// Helper structure we store in the void* RendererUserData field of each ImGuiViewport to easily retrieve our backend data. -struct ImGui_ImplDX9_ViewportData -{ - IDirect3DSwapChain9* SwapChain; - D3DPRESENT_PARAMETERS d3dpp; - - ImGui_ImplDX9_ViewportData() { SwapChain = nullptr; ZeroMemory(&d3dpp, sizeof(D3DPRESENT_PARAMETERS)); } - ~ImGui_ImplDX9_ViewportData() { IM_ASSERT(SwapChain == nullptr); } -}; - -static void ImGui_ImplDX9_CreateWindow(ImGuiViewport* viewport) -{ - ImGui_ImplDX9_Data* bd = ImGui_ImplDX9_GetBackendData(); - ImGui_ImplDX9_ViewportData* vd = IM_NEW(ImGui_ImplDX9_ViewportData)(); - viewport->RendererUserData = vd; - - // PlatformHandleRaw should always be a HWND, whereas PlatformHandle might be a higher-level handle (e.g. GLFWWindow*, SDL_Window*). - // Some backends will leave PlatformHandleRaw == 0, in which case we assume PlatformHandle will contain the HWND. - HWND hwnd = viewport->PlatformHandleRaw ? (HWND)viewport->PlatformHandleRaw : (HWND)viewport->PlatformHandle; - IM_ASSERT(hwnd != 0); - - ZeroMemory(&vd->d3dpp, sizeof(D3DPRESENT_PARAMETERS)); - vd->d3dpp.Windowed = TRUE; - vd->d3dpp.SwapEffect = D3DSWAPEFFECT_DISCARD; - vd->d3dpp.BackBufferWidth = (UINT)viewport->Size.x; - vd->d3dpp.BackBufferHeight = (UINT)viewport->Size.y; - vd->d3dpp.BackBufferFormat = D3DFMT_UNKNOWN; - vd->d3dpp.hDeviceWindow = hwnd; - vd->d3dpp.EnableAutoDepthStencil = FALSE; - vd->d3dpp.AutoDepthStencilFormat = D3DFMT_D16; - vd->d3dpp.PresentationInterval = D3DPRESENT_INTERVAL_IMMEDIATE; // Present without vsync - - HRESULT hr = bd->pd3dDevice->CreateAdditionalSwapChain(&vd->d3dpp, &vd->SwapChain); IM_UNUSED(hr); - IM_ASSERT(hr == D3D_OK); - IM_ASSERT(vd->SwapChain != nullptr); -} - -static void ImGui_ImplDX9_DestroyWindow(ImGuiViewport* viewport) -{ - // The main viewport (owned by the application) will always have RendererUserData == 0 since we didn't create the data for it. - if (ImGui_ImplDX9_ViewportData* vd = (ImGui_ImplDX9_ViewportData*)viewport->RendererUserData) - { - if (vd->SwapChain) - vd->SwapChain->Release(); - vd->SwapChain = nullptr; - ZeroMemory(&vd->d3dpp, sizeof(D3DPRESENT_PARAMETERS)); - IM_DELETE(vd); - } - viewport->RendererUserData = nullptr; -} - -static void ImGui_ImplDX9_SetWindowSize(ImGuiViewport* viewport, ImVec2 size) -{ - ImGui_ImplDX9_Data* bd = ImGui_ImplDX9_GetBackendData(); - ImGui_ImplDX9_ViewportData* vd = (ImGui_ImplDX9_ViewportData*)viewport->RendererUserData; - if (vd->SwapChain) - { - vd->SwapChain->Release(); - vd->SwapChain = nullptr; - vd->d3dpp.BackBufferWidth = (UINT)size.x; - vd->d3dpp.BackBufferHeight = (UINT)size.y; - HRESULT hr = bd->pd3dDevice->CreateAdditionalSwapChain(&vd->d3dpp, &vd->SwapChain); IM_UNUSED(hr); - IM_ASSERT(hr == D3D_OK); - } -} - -static void ImGui_ImplDX9_RenderWindow(ImGuiViewport* viewport, void*) -{ - ImGui_ImplDX9_Data* bd = ImGui_ImplDX9_GetBackendData(); - ImGui_ImplDX9_ViewportData* vd = (ImGui_ImplDX9_ViewportData*)viewport->RendererUserData; - ImVec4 clear_color = ImVec4(0.0f, 0.0f, 0.0f, 1.0f); - - LPDIRECT3DSURFACE9 render_target = nullptr; - LPDIRECT3DSURFACE9 last_render_target = nullptr; - LPDIRECT3DSURFACE9 last_depth_stencil = nullptr; - vd->SwapChain->GetBackBuffer(0, D3DBACKBUFFER_TYPE_MONO, &render_target); - bd->pd3dDevice->GetRenderTarget(0, &last_render_target); - bd->pd3dDevice->GetDepthStencilSurface(&last_depth_stencil); - bd->pd3dDevice->SetRenderTarget(0, render_target); - bd->pd3dDevice->SetDepthStencilSurface(nullptr); - - if (!(viewport->Flags & ImGuiViewportFlags_NoRendererClear)) - { - D3DCOLOR clear_col_dx = D3DCOLOR_RGBA((int)(clear_color.x*255.0f), (int)(clear_color.y*255.0f), (int)(clear_color.z*255.0f), (int)(clear_color.w*255.0f)); - bd->pd3dDevice->Clear(0, nullptr, D3DCLEAR_TARGET, clear_col_dx, 1.0f, 0); - } - - ImGui_ImplDX9_RenderDrawData(viewport->DrawData); - - // Restore render target - bd->pd3dDevice->SetRenderTarget(0, last_render_target); - bd->pd3dDevice->SetDepthStencilSurface(last_depth_stencil); - render_target->Release(); - last_render_target->Release(); - if (last_depth_stencil) last_depth_stencil->Release(); -} - -static void ImGui_ImplDX9_SwapBuffers(ImGuiViewport* viewport, void*) -{ - ImGui_ImplDX9_ViewportData* vd = (ImGui_ImplDX9_ViewportData*)viewport->RendererUserData; - HRESULT hr = vd->SwapChain->Present(nullptr, nullptr, vd->d3dpp.hDeviceWindow, nullptr, 0); - // Let main application handle D3DERR_DEVICELOST by resetting the device. - IM_ASSERT(SUCCEEDED(hr) || hr == D3DERR_DEVICELOST); -} - -static void ImGui_ImplDX9_InitPlatformInterface() -{ - ImGuiPlatformIO& platform_io = ImGui::GetPlatformIO(); - platform_io.Renderer_CreateWindow = ImGui_ImplDX9_CreateWindow; - platform_io.Renderer_DestroyWindow = ImGui_ImplDX9_DestroyWindow; - platform_io.Renderer_SetWindowSize = ImGui_ImplDX9_SetWindowSize; - platform_io.Renderer_RenderWindow = ImGui_ImplDX9_RenderWindow; - platform_io.Renderer_SwapBuffers = ImGui_ImplDX9_SwapBuffers; -} - -static void ImGui_ImplDX9_ShutdownPlatformInterface() -{ - ImGui::DestroyPlatformWindows(); -} - -static void ImGui_ImplDX9_CreateDeviceObjectsForPlatformWindows() -{ - ImGuiPlatformIO& platform_io = ImGui::GetPlatformIO(); - for (int i = 1; i < platform_io.Viewports.Size; i++) - if (!platform_io.Viewports[i]->RendererUserData) - ImGui_ImplDX9_CreateWindow(platform_io.Viewports[i]); -} - -static void ImGui_ImplDX9_InvalidateDeviceObjectsForPlatformWindows() -{ - ImGuiPlatformIO& platform_io = ImGui::GetPlatformIO(); - for (int i = 1; i < platform_io.Viewports.Size; i++) - if (platform_io.Viewports[i]->RendererUserData) - ImGui_ImplDX9_DestroyWindow(platform_io.Viewports[i]); -} - -//----------------------------------------------------------------------------- - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_dx9.h b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_dx9.h deleted file mode 100644 index ecf7181..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_dx9.h +++ /dev/null @@ -1,32 +0,0 @@ -// dear imgui: Renderer Backend for DirectX9 -// This needs to be used along with a Platform Backend (e.g. Win32) - -// Implemented features: -// [X] Renderer: User texture binding. Use 'LPDIRECT3DTEXTURE9' as ImTextureID. Read the FAQ about ImTextureID! -// [X] Renderer: Large meshes support (64k+ vertices) with 16-bit indices. -// [X] Renderer: Multi-viewport support (multiple windows). Enable with 'io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable'. - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#pragma once -#include "imgui.h" // IMGUI_IMPL_API -#ifndef IMGUI_DISABLE - -struct IDirect3DDevice9; - -IMGUI_IMPL_API bool ImGui_ImplDX9_Init(IDirect3DDevice9* device); -IMGUI_IMPL_API void ImGui_ImplDX9_Shutdown(); -IMGUI_IMPL_API void ImGui_ImplDX9_NewFrame(); -IMGUI_IMPL_API void ImGui_ImplDX9_RenderDrawData(ImDrawData* draw_data); - -// Use if you want to reset your rendering device without losing Dear ImGui state. -IMGUI_IMPL_API bool ImGui_ImplDX9_CreateDeviceObjects(); -IMGUI_IMPL_API void ImGui_ImplDX9_InvalidateDeviceObjects(); - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_glfw.cpp b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_glfw.cpp deleted file mode 100644 index d5d3769..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_glfw.cpp +++ /dev/null @@ -1,1324 +0,0 @@ -// dear imgui: Platform Backend for GLFW -// This needs to be used along with a Renderer (e.g. OpenGL3, Vulkan, WebGPU..) -// (Info: GLFW is a cross-platform general purpose library for handling windows, inputs, OpenGL/Vulkan graphics context creation, etc.) -// (Requires: GLFW 3.1+. Prefer GLFW 3.3+ or GLFW 3.4+ for full feature support.) - -// Implemented features: -// [X] Platform: Clipboard support. -// [X] Platform: Mouse support. Can discriminate Mouse/TouchScreen/Pen (Windows only). -// [X] Platform: Keyboard support. Since 1.87 we are using the io.AddKeyEvent() function. Pass ImGuiKey values to all key functions e.g. ImGui::IsKeyPressed(ImGuiKey_Space). [Legacy GLFW_KEY_* values will also be supported unless IMGUI_DISABLE_OBSOLETE_KEYIO is set] -// [X] Platform: Gamepad support. Enable with 'io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad'. -// [X] Platform: Mouse cursor shape and visibility. Disable with 'io.ConfigFlags |= ImGuiConfigFlags_NoMouseCursorChange' (note: the resizing cursors requires GLFW 3.4+). -// [X] Platform: Multi-viewport support (multiple windows). Enable with 'io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable'. - -// Issues: -// [ ] Platform: Multi-viewport support: ParentViewportID not honored, and so io.ConfigViewportsNoDefaultParent has no effect (minor). - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -// CHANGELOG -// (minor and older changes stripped away, please see git history for details) -// 2023-XX-XX: Platform: Added support for multiple windows via the ImGuiPlatformIO interface. -// 2023-10-05: Inputs: Added support for extra ImGuiKey values: F13 to F24 function keys. -// 2023-07-18: Inputs: Revert ignoring mouse data on GLFW_CURSOR_DISABLED as it can be used differently. User may set ImGuiConfigFLags_NoMouse if desired. (#5625, #6609) -// 2023-06-12: Accept glfwGetTime() not returning a monotonically increasing value. This seems to happens on some Windows setup when peripherals disconnect, and is likely to also happen on browser + Emscripten. (#6491) -// 2023-04-04: Inputs: Added support for io.AddMouseSourceEvent() to discriminate ImGuiMouseSource_Mouse/ImGuiMouseSource_TouchScreen/ImGuiMouseSource_Pen on Windows ONLY, using a custom WndProc hook. (#2702) -// 2023-03-16: Inputs: Fixed key modifiers handling on secondary viewports (docking branch). Broken on 2023/01/04. (#6248, #6034) -// 2023-03-14: Emscripten: Avoid using glfwGetError() and glfwGetGamepadState() which are not correctly implemented in Emscripten emulation. (#6240) -// 2023-02-03: Emscripten: Registering custom low-level mouse wheel handler to get more accurate scrolling impulses on Emscripten. (#4019, #6096) -// 2023-01-18: Handle unsupported glfwGetVideoMode() call on e.g. Emscripten. -// 2023-01-04: Inputs: Fixed mods state on Linux when using Alt-GR text input (e.g. German keyboard layout), could lead to broken text input. Revert a 2022/01/17 change were we resumed using mods provided by GLFW, turns out they were faulty. -// 2022-11-22: Perform a dummy glfwGetError() read to cancel missing names with glfwGetKeyName(). (#5908) -// 2022-10-18: Perform a dummy glfwGetError() read to cancel missing mouse cursors errors. Using GLFW_VERSION_COMBINED directly. (#5785) -// 2022-10-11: Using 'nullptr' instead of 'NULL' as per our switch to C++11. -// 2022-09-26: Inputs: Renamed ImGuiKey_ModXXX introduced in 1.87 to ImGuiMod_XXX (old names still supported). -// 2022-09-01: Inputs: Honor GLFW_CURSOR_DISABLED by not setting mouse position *EDIT* Reverted 2023-07-18. -// 2022-04-30: Inputs: Fixed ImGui_ImplGlfw_TranslateUntranslatedKey() for lower case letters on OSX. -// 2022-03-23: Inputs: Fixed a regression in 1.87 which resulted in keyboard modifiers events being reported incorrectly on Linux/X11. -// 2022-02-07: Added ImGui_ImplGlfw_InstallCallbacks()/ImGui_ImplGlfw_RestoreCallbacks() helpers to facilitate user installing callbacks after initializing backend. -// 2022-01-26: Inputs: replaced short-lived io.AddKeyModsEvent() (added two weeks ago) with io.AddKeyEvent() using ImGuiKey_ModXXX flags. Sorry for the confusion. -// 2021-01-20: Inputs: calling new io.AddKeyAnalogEvent() for gamepad support, instead of writing directly to io.NavInputs[]. -// 2022-01-17: Inputs: calling new io.AddMousePosEvent(), io.AddMouseButtonEvent(), io.AddMouseWheelEvent() API (1.87+). -// 2022-01-17: Inputs: always update key mods next and before key event (not in NewFrame) to fix input queue with very low framerates. -// 2022-01-12: *BREAKING CHANGE*: Now using glfwSetCursorPosCallback(). If you called ImGui_ImplGlfw_InitXXX() with install_callbacks = false, you MUST install glfwSetCursorPosCallback() and forward it to the backend via ImGui_ImplGlfw_CursorPosCallback(). -// 2022-01-10: Inputs: calling new io.AddKeyEvent(), io.AddKeyModsEvent() + io.SetKeyEventNativeData() API (1.87+). Support for full ImGuiKey range. -// 2022-01-05: Inputs: Converting GLFW untranslated keycodes back to translated keycodes (in the ImGui_ImplGlfw_KeyCallback() function) in order to match the behavior of every other backend, and facilitate the use of GLFW with lettered-shortcuts API. -// 2021-08-17: *BREAKING CHANGE*: Now using glfwSetWindowFocusCallback() to calling io.AddFocusEvent(). If you called ImGui_ImplGlfw_InitXXX() with install_callbacks = false, you MUST install glfwSetWindowFocusCallback() and forward it to the backend via ImGui_ImplGlfw_WindowFocusCallback(). -// 2021-07-29: *BREAKING CHANGE*: Now using glfwSetCursorEnterCallback(). MousePos is correctly reported when the host platform window is hovered but not focused. If you called ImGui_ImplGlfw_InitXXX() with install_callbacks = false, you MUST install glfwSetWindowFocusCallback() callback and forward it to the backend via ImGui_ImplGlfw_CursorEnterCallback(). -// 2021-06-29: Reorganized backend to pull data from a single structure to facilitate usage with multiple-contexts (all g_XXXX access changed to bd->XXXX). -// 2020-01-17: Inputs: Disable error callback while assigning mouse cursors because some X11 setup don't have them and it generates errors. -// 2019-12-05: Inputs: Added support for new mouse cursors added in GLFW 3.4+ (resizing cursors, not allowed cursor). -// 2019-10-18: Misc: Previously installed user callbacks are now restored on shutdown. -// 2019-07-21: Inputs: Added mapping for ImGuiKey_KeyPadEnter. -// 2019-05-11: Inputs: Don't filter value from character callback before calling AddInputCharacter(). -// 2019-03-12: Misc: Preserve DisplayFramebufferScale when main window is minimized. -// 2018-11-30: Misc: Setting up io.BackendPlatformName so it can be displayed in the About Window. -// 2018-11-07: Inputs: When installing our GLFW callbacks, we save user's previously installed ones - if any - and chain call them. -// 2018-08-01: Inputs: Workaround for Emscripten which doesn't seem to handle focus related calls. -// 2018-06-29: Inputs: Added support for the ImGuiMouseCursor_Hand cursor. -// 2018-06-08: Misc: Extracted imgui_impl_glfw.cpp/.h away from the old combined GLFW+OpenGL/Vulkan examples. -// 2018-03-20: Misc: Setup io.BackendFlags ImGuiBackendFlags_HasMouseCursors flag + honor ImGuiConfigFlags_NoMouseCursorChange flag. -// 2018-02-20: Inputs: Added support for mouse cursors (ImGui::GetMouseCursor() value, passed to glfwSetCursor()). -// 2018-02-06: Misc: Removed call to ImGui::Shutdown() which is not available from 1.60 WIP, user needs to call CreateContext/DestroyContext themselves. -// 2018-02-06: Inputs: Added mapping for ImGuiKey_Space. -// 2018-01-25: Inputs: Added gamepad support if ImGuiConfigFlags_NavEnableGamepad is set. -// 2018-01-25: Inputs: Honoring the io.WantSetMousePos by repositioning the mouse (when using navigation and ImGuiConfigFlags_NavMoveMouse is set). -// 2018-01-20: Inputs: Added Horizontal Mouse Wheel support. -// 2018-01-18: Inputs: Added mapping for ImGuiKey_Insert. -// 2017-08-25: Inputs: MousePos set to -FLT_MAX,-FLT_MAX when mouse is unavailable/missing (instead of -1,-1). -// 2016-10-15: Misc: Added a void* user_data parameter to Clipboard function handlers. - -#include "imgui.h" -#ifndef IMGUI_DISABLE -#include "imgui_impl_glfw.h" - -// Clang warnings with -Weverything -#if defined(__clang__) -#pragma clang diagnostic push -#pragma clang diagnostic ignored "-Wold-style-cast" // warning: use of old-style cast -#pragma clang diagnostic ignored "-Wsign-conversion" // warning: implicit conversion changes signedness -#endif - -// GLFW -#include - -#ifdef _WIN32 -#undef APIENTRY -#define GLFW_EXPOSE_NATIVE_WIN32 -#include // for glfwGetWin32Window() -#endif -#ifdef __APPLE__ -#define GLFW_EXPOSE_NATIVE_COCOA -#include // for glfwGetCocoaWindow() -#endif - -#ifdef __EMSCRIPTEN__ -#include -#include -#endif - -// We gather version tests as define in order to easily see which features are version-dependent. -#define GLFW_VERSION_COMBINED (GLFW_VERSION_MAJOR * 1000 + GLFW_VERSION_MINOR * 100 + GLFW_VERSION_REVISION) -#define GLFW_HAS_WINDOW_TOPMOST (GLFW_VERSION_COMBINED >= 3200) // 3.2+ GLFW_FLOATING -#define GLFW_HAS_WINDOW_HOVERED (GLFW_VERSION_COMBINED >= 3300) // 3.3+ GLFW_HOVERED -#define GLFW_HAS_WINDOW_ALPHA (GLFW_VERSION_COMBINED >= 3300) // 3.3+ glfwSetWindowOpacity -#define GLFW_HAS_PER_MONITOR_DPI (GLFW_VERSION_COMBINED >= 3300) // 3.3+ glfwGetMonitorContentScale -#if defined(__EMSCRIPTEN__) || defined(__SWITCH__) // no Vulkan support in GLFW for Emscripten or homebrew Nintendo Switch -#define GLFW_HAS_VULKAN (0) -#else -#define GLFW_HAS_VULKAN (GLFW_VERSION_COMBINED >= 3200) // 3.2+ glfwCreateWindowSurface -#endif -#define GLFW_HAS_FOCUS_WINDOW (GLFW_VERSION_COMBINED >= 3200) // 3.2+ glfwFocusWindow -#define GLFW_HAS_FOCUS_ON_SHOW (GLFW_VERSION_COMBINED >= 3300) // 3.3+ GLFW_FOCUS_ON_SHOW -#define GLFW_HAS_MONITOR_WORK_AREA (GLFW_VERSION_COMBINED >= 3300) // 3.3+ glfwGetMonitorWorkarea -#define GLFW_HAS_OSX_WINDOW_POS_FIX (GLFW_VERSION_COMBINED >= 3301) // 3.3.1+ Fixed: Resizing window repositions it on MacOS #1553 -#ifdef GLFW_RESIZE_NESW_CURSOR // Let's be nice to people who pulled GLFW between 2019-04-16 (3.4 define) and 2019-11-29 (cursors defines) // FIXME: Remove when GLFW 3.4 is released? -#define GLFW_HAS_NEW_CURSORS (GLFW_VERSION_COMBINED >= 3400) // 3.4+ GLFW_RESIZE_ALL_CURSOR, GLFW_RESIZE_NESW_CURSOR, GLFW_RESIZE_NWSE_CURSOR, GLFW_NOT_ALLOWED_CURSOR -#else -#define GLFW_HAS_NEW_CURSORS (0) -#endif -#ifdef GLFW_MOUSE_PASSTHROUGH // Let's be nice to people who pulled GLFW between 2019-04-16 (3.4 define) and 2020-07-17 (passthrough) -#define GLFW_HAS_MOUSE_PASSTHROUGH (GLFW_VERSION_COMBINED >= 3400) // 3.4+ GLFW_MOUSE_PASSTHROUGH -#else -#define GLFW_HAS_MOUSE_PASSTHROUGH (0) -#endif -#define GLFW_HAS_GAMEPAD_API (GLFW_VERSION_COMBINED >= 3300) // 3.3+ glfwGetGamepadState() new api -#define GLFW_HAS_GETKEYNAME (GLFW_VERSION_COMBINED >= 3200) // 3.2+ glfwGetKeyName() -#define GLFW_HAS_GETERROR (GLFW_VERSION_COMBINED >= 3300) // 3.3+ glfwGetError() - -// GLFW data -enum GlfwClientApi -{ - GlfwClientApi_Unknown, - GlfwClientApi_OpenGL, - GlfwClientApi_Vulkan -}; - -struct ImGui_ImplGlfw_Data -{ - GLFWwindow* Window; - GlfwClientApi ClientApi; - double Time; - GLFWwindow* MouseWindow; - GLFWcursor* MouseCursors[ImGuiMouseCursor_COUNT]; - ImVec2 LastValidMousePos; - GLFWwindow* KeyOwnerWindows[GLFW_KEY_LAST]; - bool InstalledCallbacks; - bool CallbacksChainForAllWindows; - bool WantUpdateMonitors; - - // Chain GLFW callbacks: our callbacks will call the user's previously installed callbacks, if any. - GLFWwindowfocusfun PrevUserCallbackWindowFocus; - GLFWcursorposfun PrevUserCallbackCursorPos; - GLFWcursorenterfun PrevUserCallbackCursorEnter; - GLFWmousebuttonfun PrevUserCallbackMousebutton; - GLFWscrollfun PrevUserCallbackScroll; - GLFWkeyfun PrevUserCallbackKey; - GLFWcharfun PrevUserCallbackChar; - GLFWmonitorfun PrevUserCallbackMonitor; -#ifdef _WIN32 - WNDPROC PrevWndProc; -#endif - - ImGui_ImplGlfw_Data() { memset((void*)this, 0, sizeof(*this)); } -}; - -// Backend data stored in io.BackendPlatformUserData to allow support for multiple Dear ImGui contexts -// It is STRONGLY preferred that you use docking branch with multi-viewports (== single Dear ImGui context + multiple windows) instead of multiple Dear ImGui contexts. -// FIXME: multi-context support is not well tested and probably dysfunctional in this backend. -// - Because glfwPollEvents() process all windows and some events may be called outside of it, you will need to register your own callbacks -// (passing install_callbacks=false in ImGui_ImplGlfw_InitXXX functions), set the current dear imgui context and then call our callbacks. -// - Otherwise we may need to store a GLFWWindow* -> ImGuiContext* map and handle this in the backend, adding a little bit of extra complexity to it. -// FIXME: some shared resources (mouse cursor shape, gamepad) are mishandled when using multi-context. -static ImGui_ImplGlfw_Data* ImGui_ImplGlfw_GetBackendData() -{ - return ImGui::GetCurrentContext() ? (ImGui_ImplGlfw_Data*)ImGui::GetIO().BackendPlatformUserData : nullptr; -} - -// Forward Declarations -static void ImGui_ImplGlfw_UpdateMonitors(); -static void ImGui_ImplGlfw_InitPlatformInterface(); -static void ImGui_ImplGlfw_ShutdownPlatformInterface(); - -// Functions -static const char* ImGui_ImplGlfw_GetClipboardText(void* user_data) -{ - return glfwGetClipboardString((GLFWwindow*)user_data); -} - -static void ImGui_ImplGlfw_SetClipboardText(void* user_data, const char* text) -{ - glfwSetClipboardString((GLFWwindow*)user_data, text); -} - -static ImGuiKey ImGui_ImplGlfw_KeyToImGuiKey(int key) -{ - switch (key) - { - case GLFW_KEY_TAB: return ImGuiKey_Tab; - case GLFW_KEY_LEFT: return ImGuiKey_LeftArrow; - case GLFW_KEY_RIGHT: return ImGuiKey_RightArrow; - case GLFW_KEY_UP: return ImGuiKey_UpArrow; - case GLFW_KEY_DOWN: return ImGuiKey_DownArrow; - case GLFW_KEY_PAGE_UP: return ImGuiKey_PageUp; - case GLFW_KEY_PAGE_DOWN: return ImGuiKey_PageDown; - case GLFW_KEY_HOME: return ImGuiKey_Home; - case GLFW_KEY_END: return ImGuiKey_End; - case GLFW_KEY_INSERT: return ImGuiKey_Insert; - case GLFW_KEY_DELETE: return ImGuiKey_Delete; - case GLFW_KEY_BACKSPACE: return ImGuiKey_Backspace; - case GLFW_KEY_SPACE: return ImGuiKey_Space; - case GLFW_KEY_ENTER: return ImGuiKey_Enter; - case GLFW_KEY_ESCAPE: return ImGuiKey_Escape; - case GLFW_KEY_APOSTROPHE: return ImGuiKey_Apostrophe; - case GLFW_KEY_COMMA: return ImGuiKey_Comma; - case GLFW_KEY_MINUS: return ImGuiKey_Minus; - case GLFW_KEY_PERIOD: return ImGuiKey_Period; - case GLFW_KEY_SLASH: return ImGuiKey_Slash; - case GLFW_KEY_SEMICOLON: return ImGuiKey_Semicolon; - case GLFW_KEY_EQUAL: return ImGuiKey_Equal; - case GLFW_KEY_LEFT_BRACKET: return ImGuiKey_LeftBracket; - case GLFW_KEY_BACKSLASH: return ImGuiKey_Backslash; - case GLFW_KEY_RIGHT_BRACKET: return ImGuiKey_RightBracket; - case GLFW_KEY_GRAVE_ACCENT: return ImGuiKey_GraveAccent; - case GLFW_KEY_CAPS_LOCK: return ImGuiKey_CapsLock; - case GLFW_KEY_SCROLL_LOCK: return ImGuiKey_ScrollLock; - case GLFW_KEY_NUM_LOCK: return ImGuiKey_NumLock; - case GLFW_KEY_PRINT_SCREEN: return ImGuiKey_PrintScreen; - case GLFW_KEY_PAUSE: return ImGuiKey_Pause; - case GLFW_KEY_KP_0: return ImGuiKey_Keypad0; - case GLFW_KEY_KP_1: return ImGuiKey_Keypad1; - case GLFW_KEY_KP_2: return ImGuiKey_Keypad2; - case GLFW_KEY_KP_3: return ImGuiKey_Keypad3; - case GLFW_KEY_KP_4: return ImGuiKey_Keypad4; - case GLFW_KEY_KP_5: return ImGuiKey_Keypad5; - case GLFW_KEY_KP_6: return ImGuiKey_Keypad6; - case GLFW_KEY_KP_7: return ImGuiKey_Keypad7; - case GLFW_KEY_KP_8: return ImGuiKey_Keypad8; - case GLFW_KEY_KP_9: return ImGuiKey_Keypad9; - case GLFW_KEY_KP_DECIMAL: return ImGuiKey_KeypadDecimal; - case GLFW_KEY_KP_DIVIDE: return ImGuiKey_KeypadDivide; - case GLFW_KEY_KP_MULTIPLY: return ImGuiKey_KeypadMultiply; - case GLFW_KEY_KP_SUBTRACT: return ImGuiKey_KeypadSubtract; - case GLFW_KEY_KP_ADD: return ImGuiKey_KeypadAdd; - case GLFW_KEY_KP_ENTER: return ImGuiKey_KeypadEnter; - case GLFW_KEY_KP_EQUAL: return ImGuiKey_KeypadEqual; - case GLFW_KEY_LEFT_SHIFT: return ImGuiKey_LeftShift; - case GLFW_KEY_LEFT_CONTROL: return ImGuiKey_LeftCtrl; - case GLFW_KEY_LEFT_ALT: return ImGuiKey_LeftAlt; - case GLFW_KEY_LEFT_SUPER: return ImGuiKey_LeftSuper; - case GLFW_KEY_RIGHT_SHIFT: return ImGuiKey_RightShift; - case GLFW_KEY_RIGHT_CONTROL: return ImGuiKey_RightCtrl; - case GLFW_KEY_RIGHT_ALT: return ImGuiKey_RightAlt; - case GLFW_KEY_RIGHT_SUPER: return ImGuiKey_RightSuper; - case GLFW_KEY_MENU: return ImGuiKey_Menu; - case GLFW_KEY_0: return ImGuiKey_0; - case GLFW_KEY_1: return ImGuiKey_1; - case GLFW_KEY_2: return ImGuiKey_2; - case GLFW_KEY_3: return ImGuiKey_3; - case GLFW_KEY_4: return ImGuiKey_4; - case GLFW_KEY_5: return ImGuiKey_5; - case GLFW_KEY_6: return ImGuiKey_6; - case GLFW_KEY_7: return ImGuiKey_7; - case GLFW_KEY_8: return ImGuiKey_8; - case GLFW_KEY_9: return ImGuiKey_9; - case GLFW_KEY_A: return ImGuiKey_A; - case GLFW_KEY_B: return ImGuiKey_B; - case GLFW_KEY_C: return ImGuiKey_C; - case GLFW_KEY_D: return ImGuiKey_D; - case GLFW_KEY_E: return ImGuiKey_E; - case GLFW_KEY_F: return ImGuiKey_F; - case GLFW_KEY_G: return ImGuiKey_G; - case GLFW_KEY_H: return ImGuiKey_H; - case GLFW_KEY_I: return ImGuiKey_I; - case GLFW_KEY_J: return ImGuiKey_J; - case GLFW_KEY_K: return ImGuiKey_K; - case GLFW_KEY_L: return ImGuiKey_L; - case GLFW_KEY_M: return ImGuiKey_M; - case GLFW_KEY_N: return ImGuiKey_N; - case GLFW_KEY_O: return ImGuiKey_O; - case GLFW_KEY_P: return ImGuiKey_P; - case GLFW_KEY_Q: return ImGuiKey_Q; - case GLFW_KEY_R: return ImGuiKey_R; - case GLFW_KEY_S: return ImGuiKey_S; - case GLFW_KEY_T: return ImGuiKey_T; - case GLFW_KEY_U: return ImGuiKey_U; - case GLFW_KEY_V: return ImGuiKey_V; - case GLFW_KEY_W: return ImGuiKey_W; - case GLFW_KEY_X: return ImGuiKey_X; - case GLFW_KEY_Y: return ImGuiKey_Y; - case GLFW_KEY_Z: return ImGuiKey_Z; - case GLFW_KEY_F1: return ImGuiKey_F1; - case GLFW_KEY_F2: return ImGuiKey_F2; - case GLFW_KEY_F3: return ImGuiKey_F3; - case GLFW_KEY_F4: return ImGuiKey_F4; - case GLFW_KEY_F5: return ImGuiKey_F5; - case GLFW_KEY_F6: return ImGuiKey_F6; - case GLFW_KEY_F7: return ImGuiKey_F7; - case GLFW_KEY_F8: return ImGuiKey_F8; - case GLFW_KEY_F9: return ImGuiKey_F9; - case GLFW_KEY_F10: return ImGuiKey_F10; - case GLFW_KEY_F11: return ImGuiKey_F11; - case GLFW_KEY_F12: return ImGuiKey_F12; - case GLFW_KEY_F13: return ImGuiKey_F13; - case GLFW_KEY_F14: return ImGuiKey_F14; - case GLFW_KEY_F15: return ImGuiKey_F15; - case GLFW_KEY_F16: return ImGuiKey_F16; - case GLFW_KEY_F17: return ImGuiKey_F17; - case GLFW_KEY_F18: return ImGuiKey_F18; - case GLFW_KEY_F19: return ImGuiKey_F19; - case GLFW_KEY_F20: return ImGuiKey_F20; - case GLFW_KEY_F21: return ImGuiKey_F21; - case GLFW_KEY_F22: return ImGuiKey_F22; - case GLFW_KEY_F23: return ImGuiKey_F23; - case GLFW_KEY_F24: return ImGuiKey_F24; - default: return ImGuiKey_None; - } -} - -// X11 does not include current pressed/released modifier key in 'mods' flags submitted by GLFW -// See https://github.com/ocornut/imgui/issues/6034 and https://github.com/glfw/glfw/issues/1630 -static void ImGui_ImplGlfw_UpdateKeyModifiers(GLFWwindow* window) -{ - ImGuiIO& io = ImGui::GetIO(); - io.AddKeyEvent(ImGuiMod_Ctrl, (glfwGetKey(window, GLFW_KEY_LEFT_CONTROL) == GLFW_PRESS) || (glfwGetKey(window, GLFW_KEY_RIGHT_CONTROL) == GLFW_PRESS)); - io.AddKeyEvent(ImGuiMod_Shift, (glfwGetKey(window, GLFW_KEY_LEFT_SHIFT) == GLFW_PRESS) || (glfwGetKey(window, GLFW_KEY_RIGHT_SHIFT) == GLFW_PRESS)); - io.AddKeyEvent(ImGuiMod_Alt, (glfwGetKey(window, GLFW_KEY_LEFT_ALT) == GLFW_PRESS) || (glfwGetKey(window, GLFW_KEY_RIGHT_ALT) == GLFW_PRESS)); - io.AddKeyEvent(ImGuiMod_Super, (glfwGetKey(window, GLFW_KEY_LEFT_SUPER) == GLFW_PRESS) || (glfwGetKey(window, GLFW_KEY_RIGHT_SUPER) == GLFW_PRESS)); -} - -static bool ImGui_ImplGlfw_ShouldChainCallback(GLFWwindow* window) -{ - ImGui_ImplGlfw_Data* bd = ImGui_ImplGlfw_GetBackendData(); - return bd->CallbacksChainForAllWindows ? true : (window == bd->Window); -} - -void ImGui_ImplGlfw_MouseButtonCallback(GLFWwindow* window, int button, int action, int mods) -{ - ImGui_ImplGlfw_Data* bd = ImGui_ImplGlfw_GetBackendData(); - if (bd->PrevUserCallbackMousebutton != nullptr && ImGui_ImplGlfw_ShouldChainCallback(window)) - bd->PrevUserCallbackMousebutton(window, button, action, mods); - - ImGui_ImplGlfw_UpdateKeyModifiers(window); - - ImGuiIO& io = ImGui::GetIO(); - if (button >= 0 && button < ImGuiMouseButton_COUNT) - io.AddMouseButtonEvent(button, action == GLFW_PRESS); -} - -void ImGui_ImplGlfw_ScrollCallback(GLFWwindow* window, double xoffset, double yoffset) -{ - ImGui_ImplGlfw_Data* bd = ImGui_ImplGlfw_GetBackendData(); - if (bd->PrevUserCallbackScroll != nullptr && ImGui_ImplGlfw_ShouldChainCallback(window)) - bd->PrevUserCallbackScroll(window, xoffset, yoffset); - -#ifdef __EMSCRIPTEN__ - // Ignore GLFW events: will be processed in ImGui_ImplEmscripten_WheelCallback(). - return; -#endif - - ImGuiIO& io = ImGui::GetIO(); - io.AddMouseWheelEvent((float)xoffset, (float)yoffset); -} - -static int ImGui_ImplGlfw_TranslateUntranslatedKey(int key, int scancode) -{ -#if GLFW_HAS_GETKEYNAME && !defined(__EMSCRIPTEN__) - // GLFW 3.1+ attempts to "untranslate" keys, which goes the opposite of what every other framework does, making using lettered shortcuts difficult. - // (It had reasons to do so: namely GLFW is/was more likely to be used for WASD-type game controls rather than lettered shortcuts, but IHMO the 3.1 change could have been done differently) - // See https://github.com/glfw/glfw/issues/1502 for details. - // Adding a workaround to undo this (so our keys are translated->untranslated->translated, likely a lossy process). - // This won't cover edge cases but this is at least going to cover common cases. - if (key >= GLFW_KEY_KP_0 && key <= GLFW_KEY_KP_EQUAL) - return key; - GLFWerrorfun prev_error_callback = glfwSetErrorCallback(nullptr); - const char* key_name = glfwGetKeyName(key, scancode); - glfwSetErrorCallback(prev_error_callback); -#if GLFW_HAS_GETERROR && !defined(__EMSCRIPTEN__) // Eat errors (see #5908) - (void)glfwGetError(nullptr); -#endif - if (key_name && key_name[0] != 0 && key_name[1] == 0) - { - const char char_names[] = "`-=[]\\,;\'./"; - const int char_keys[] = { GLFW_KEY_GRAVE_ACCENT, GLFW_KEY_MINUS, GLFW_KEY_EQUAL, GLFW_KEY_LEFT_BRACKET, GLFW_KEY_RIGHT_BRACKET, GLFW_KEY_BACKSLASH, GLFW_KEY_COMMA, GLFW_KEY_SEMICOLON, GLFW_KEY_APOSTROPHE, GLFW_KEY_PERIOD, GLFW_KEY_SLASH, 0 }; - IM_ASSERT(IM_ARRAYSIZE(char_names) == IM_ARRAYSIZE(char_keys)); - if (key_name[0] >= '0' && key_name[0] <= '9') { key = GLFW_KEY_0 + (key_name[0] - '0'); } - else if (key_name[0] >= 'A' && key_name[0] <= 'Z') { key = GLFW_KEY_A + (key_name[0] - 'A'); } - else if (key_name[0] >= 'a' && key_name[0] <= 'z') { key = GLFW_KEY_A + (key_name[0] - 'a'); } - else if (const char* p = strchr(char_names, key_name[0])) { key = char_keys[p - char_names]; } - } - // if (action == GLFW_PRESS) printf("key %d scancode %d name '%s'\n", key, scancode, key_name); -#else - IM_UNUSED(scancode); -#endif - return key; -} - -void ImGui_ImplGlfw_KeyCallback(GLFWwindow* window, int keycode, int scancode, int action, int mods) -{ - ImGui_ImplGlfw_Data* bd = ImGui_ImplGlfw_GetBackendData(); - if (bd->PrevUserCallbackKey != nullptr && ImGui_ImplGlfw_ShouldChainCallback(window)) - bd->PrevUserCallbackKey(window, keycode, scancode, action, mods); - - if (action != GLFW_PRESS && action != GLFW_RELEASE) - return; - - ImGui_ImplGlfw_UpdateKeyModifiers(window); - - if (keycode >= 0 && keycode < IM_ARRAYSIZE(bd->KeyOwnerWindows)) - bd->KeyOwnerWindows[keycode] = (action == GLFW_PRESS) ? window : nullptr; - - keycode = ImGui_ImplGlfw_TranslateUntranslatedKey(keycode, scancode); - - ImGuiIO& io = ImGui::GetIO(); - ImGuiKey imgui_key = ImGui_ImplGlfw_KeyToImGuiKey(keycode); - io.AddKeyEvent(imgui_key, (action == GLFW_PRESS)); - io.SetKeyEventNativeData(imgui_key, keycode, scancode); // To support legacy indexing (<1.87 user code) -} - -void ImGui_ImplGlfw_WindowFocusCallback(GLFWwindow* window, int focused) -{ - ImGui_ImplGlfw_Data* bd = ImGui_ImplGlfw_GetBackendData(); - if (bd->PrevUserCallbackWindowFocus != nullptr && ImGui_ImplGlfw_ShouldChainCallback(window)) - bd->PrevUserCallbackWindowFocus(window, focused); - - ImGuiIO& io = ImGui::GetIO(); - io.AddFocusEvent(focused != 0); -} - -void ImGui_ImplGlfw_CursorPosCallback(GLFWwindow* window, double x, double y) -{ - ImGui_ImplGlfw_Data* bd = ImGui_ImplGlfw_GetBackendData(); - if (bd->PrevUserCallbackCursorPos != nullptr && ImGui_ImplGlfw_ShouldChainCallback(window)) - bd->PrevUserCallbackCursorPos(window, x, y); - - ImGuiIO& io = ImGui::GetIO(); - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - int window_x, window_y; - glfwGetWindowPos(window, &window_x, &window_y); - x += window_x; - y += window_y; - } - io.AddMousePosEvent((float)x, (float)y); - bd->LastValidMousePos = ImVec2((float)x, (float)y); -} - -// Workaround: X11 seems to send spurious Leave/Enter events which would make us lose our position, -// so we back it up and restore on Leave/Enter (see https://github.com/ocornut/imgui/issues/4984) -void ImGui_ImplGlfw_CursorEnterCallback(GLFWwindow* window, int entered) -{ - ImGui_ImplGlfw_Data* bd = ImGui_ImplGlfw_GetBackendData(); - if (bd->PrevUserCallbackCursorEnter != nullptr && ImGui_ImplGlfw_ShouldChainCallback(window)) - bd->PrevUserCallbackCursorEnter(window, entered); - - ImGuiIO& io = ImGui::GetIO(); - if (entered) - { - bd->MouseWindow = window; - io.AddMousePosEvent(bd->LastValidMousePos.x, bd->LastValidMousePos.y); - } - else if (!entered && bd->MouseWindow == window) - { - bd->LastValidMousePos = io.MousePos; - bd->MouseWindow = nullptr; - io.AddMousePosEvent(-FLT_MAX, -FLT_MAX); - } -} - -void ImGui_ImplGlfw_CharCallback(GLFWwindow* window, unsigned int c) -{ - ImGui_ImplGlfw_Data* bd = ImGui_ImplGlfw_GetBackendData(); - if (bd->PrevUserCallbackChar != nullptr && ImGui_ImplGlfw_ShouldChainCallback(window)) - bd->PrevUserCallbackChar(window, c); - - ImGuiIO& io = ImGui::GetIO(); - io.AddInputCharacter(c); -} - -void ImGui_ImplGlfw_MonitorCallback(GLFWmonitor*, int) -{ - ImGui_ImplGlfw_Data* bd = ImGui_ImplGlfw_GetBackendData(); - bd->WantUpdateMonitors = true; -} - -#ifdef __EMSCRIPTEN__ -static EM_BOOL ImGui_ImplEmscripten_WheelCallback(int, const EmscriptenWheelEvent* ev, void*) -{ - // Mimic Emscripten_HandleWheel() in SDL. - // Corresponding equivalent in GLFW JS emulation layer has incorrect quantizing preventing small values. See #6096 - float multiplier = 0.0f; - if (ev->deltaMode == DOM_DELTA_PIXEL) { multiplier = 1.0f / 100.0f; } // 100 pixels make up a step. - else if (ev->deltaMode == DOM_DELTA_LINE) { multiplier = 1.0f / 3.0f; } // 3 lines make up a step. - else if (ev->deltaMode == DOM_DELTA_PAGE) { multiplier = 80.0f; } // A page makes up 80 steps. - float wheel_x = ev->deltaX * -multiplier; - float wheel_y = ev->deltaY * -multiplier; - ImGuiIO& io = ImGui::GetIO(); - io.AddMouseWheelEvent(wheel_x, wheel_y); - //IMGUI_DEBUG_LOG("[Emsc] mode %d dx: %.2f, dy: %.2f, dz: %.2f --> feed %.2f %.2f\n", (int)ev->deltaMode, ev->deltaX, ev->deltaY, ev->deltaZ, wheel_x, wheel_y); - return EM_TRUE; -} -#endif - -#ifdef _WIN32 -static LRESULT CALLBACK ImGui_ImplGlfw_WndProc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam); -#endif - -void ImGui_ImplGlfw_InstallCallbacks(GLFWwindow* window) -{ - ImGui_ImplGlfw_Data* bd = ImGui_ImplGlfw_GetBackendData(); - IM_ASSERT(bd->InstalledCallbacks == false && "Callbacks already installed!"); - IM_ASSERT(bd->Window == window); - - bd->PrevUserCallbackWindowFocus = glfwSetWindowFocusCallback(window, ImGui_ImplGlfw_WindowFocusCallback); - bd->PrevUserCallbackCursorEnter = glfwSetCursorEnterCallback(window, ImGui_ImplGlfw_CursorEnterCallback); - bd->PrevUserCallbackCursorPos = glfwSetCursorPosCallback(window, ImGui_ImplGlfw_CursorPosCallback); - bd->PrevUserCallbackMousebutton = glfwSetMouseButtonCallback(window, ImGui_ImplGlfw_MouseButtonCallback); - bd->PrevUserCallbackScroll = glfwSetScrollCallback(window, ImGui_ImplGlfw_ScrollCallback); - bd->PrevUserCallbackKey = glfwSetKeyCallback(window, ImGui_ImplGlfw_KeyCallback); - bd->PrevUserCallbackChar = glfwSetCharCallback(window, ImGui_ImplGlfw_CharCallback); - bd->PrevUserCallbackMonitor = glfwSetMonitorCallback(ImGui_ImplGlfw_MonitorCallback); - bd->InstalledCallbacks = true; -} - -void ImGui_ImplGlfw_RestoreCallbacks(GLFWwindow* window) -{ - ImGui_ImplGlfw_Data* bd = ImGui_ImplGlfw_GetBackendData(); - IM_ASSERT(bd->InstalledCallbacks == true && "Callbacks not installed!"); - IM_ASSERT(bd->Window == window); - - glfwSetWindowFocusCallback(window, bd->PrevUserCallbackWindowFocus); - glfwSetCursorEnterCallback(window, bd->PrevUserCallbackCursorEnter); - glfwSetCursorPosCallback(window, bd->PrevUserCallbackCursorPos); - glfwSetMouseButtonCallback(window, bd->PrevUserCallbackMousebutton); - glfwSetScrollCallback(window, bd->PrevUserCallbackScroll); - glfwSetKeyCallback(window, bd->PrevUserCallbackKey); - glfwSetCharCallback(window, bd->PrevUserCallbackChar); - glfwSetMonitorCallback(bd->PrevUserCallbackMonitor); - bd->InstalledCallbacks = false; - bd->PrevUserCallbackWindowFocus = nullptr; - bd->PrevUserCallbackCursorEnter = nullptr; - bd->PrevUserCallbackCursorPos = nullptr; - bd->PrevUserCallbackMousebutton = nullptr; - bd->PrevUserCallbackScroll = nullptr; - bd->PrevUserCallbackKey = nullptr; - bd->PrevUserCallbackChar = nullptr; - bd->PrevUserCallbackMonitor = nullptr; -} - -// Set to 'true' to enable chaining installed callbacks for all windows (including secondary viewports created by backends or by user. -// This is 'false' by default meaning we only chain callbacks for the main viewport. -// We cannot set this to 'true' by default because user callbacks code may be not testing the 'window' parameter of their callback. -// If you set this to 'true' your user callback code will need to make sure you are testing the 'window' parameter. -void ImGui_ImplGlfw_SetCallbacksChainForAllWindows(bool chain_for_all_windows) -{ - ImGui_ImplGlfw_Data* bd = ImGui_ImplGlfw_GetBackendData(); - bd->CallbacksChainForAllWindows = chain_for_all_windows; -} - -static bool ImGui_ImplGlfw_Init(GLFWwindow* window, bool install_callbacks, GlfwClientApi client_api) -{ - ImGuiIO& io = ImGui::GetIO(); - IM_ASSERT(io.BackendPlatformUserData == nullptr && "Already initialized a platform backend!"); - //printf("GLFW_VERSION: %d.%d.%d (%d)", GLFW_VERSION_MAJOR, GLFW_VERSION_MINOR, GLFW_VERSION_REVISION, GLFW_VERSION_COMBINED); - - // Setup backend capabilities flags - ImGui_ImplGlfw_Data* bd = IM_NEW(ImGui_ImplGlfw_Data)(); - io.BackendPlatformUserData = (void*)bd; - io.BackendPlatformName = "imgui_impl_glfw"; - io.BackendFlags |= ImGuiBackendFlags_HasMouseCursors; // We can honor GetMouseCursor() values (optional) - io.BackendFlags |= ImGuiBackendFlags_HasSetMousePos; // We can honor io.WantSetMousePos requests (optional, rarely used) -#ifndef __EMSCRIPTEN__ - io.BackendFlags |= ImGuiBackendFlags_PlatformHasViewports; // We can create multi-viewports on the Platform side (optional) -#endif -#if GLFW_HAS_MOUSE_PASSTHROUGH || (GLFW_HAS_WINDOW_HOVERED && defined(_WIN32)) - io.BackendFlags |= ImGuiBackendFlags_HasMouseHoveredViewport; // We can call io.AddMouseViewportEvent() with correct data (optional) -#endif - - bd->Window = window; - bd->Time = 0.0; - bd->WantUpdateMonitors = true; - - io.SetClipboardTextFn = ImGui_ImplGlfw_SetClipboardText; - io.GetClipboardTextFn = ImGui_ImplGlfw_GetClipboardText; - io.ClipboardUserData = bd->Window; - - // Create mouse cursors - // (By design, on X11 cursors are user configurable and some cursors may be missing. When a cursor doesn't exist, - // GLFW will emit an error which will often be printed by the app, so we temporarily disable error reporting. - // Missing cursors will return nullptr and our _UpdateMouseCursor() function will use the Arrow cursor instead.) - GLFWerrorfun prev_error_callback = glfwSetErrorCallback(nullptr); - bd->MouseCursors[ImGuiMouseCursor_Arrow] = glfwCreateStandardCursor(GLFW_ARROW_CURSOR); - bd->MouseCursors[ImGuiMouseCursor_TextInput] = glfwCreateStandardCursor(GLFW_IBEAM_CURSOR); - bd->MouseCursors[ImGuiMouseCursor_ResizeNS] = glfwCreateStandardCursor(GLFW_VRESIZE_CURSOR); - bd->MouseCursors[ImGuiMouseCursor_ResizeEW] = glfwCreateStandardCursor(GLFW_HRESIZE_CURSOR); - bd->MouseCursors[ImGuiMouseCursor_Hand] = glfwCreateStandardCursor(GLFW_HAND_CURSOR); -#if GLFW_HAS_NEW_CURSORS - bd->MouseCursors[ImGuiMouseCursor_ResizeAll] = glfwCreateStandardCursor(GLFW_RESIZE_ALL_CURSOR); - bd->MouseCursors[ImGuiMouseCursor_ResizeNESW] = glfwCreateStandardCursor(GLFW_RESIZE_NESW_CURSOR); - bd->MouseCursors[ImGuiMouseCursor_ResizeNWSE] = glfwCreateStandardCursor(GLFW_RESIZE_NWSE_CURSOR); - bd->MouseCursors[ImGuiMouseCursor_NotAllowed] = glfwCreateStandardCursor(GLFW_NOT_ALLOWED_CURSOR); -#else - bd->MouseCursors[ImGuiMouseCursor_ResizeAll] = glfwCreateStandardCursor(GLFW_ARROW_CURSOR); - bd->MouseCursors[ImGuiMouseCursor_ResizeNESW] = glfwCreateStandardCursor(GLFW_ARROW_CURSOR); - bd->MouseCursors[ImGuiMouseCursor_ResizeNWSE] = glfwCreateStandardCursor(GLFW_ARROW_CURSOR); - bd->MouseCursors[ImGuiMouseCursor_NotAllowed] = glfwCreateStandardCursor(GLFW_ARROW_CURSOR); -#endif - glfwSetErrorCallback(prev_error_callback); -#if GLFW_HAS_GETERROR && !defined(__EMSCRIPTEN__) // Eat errors (see #5908) - (void)glfwGetError(nullptr); -#endif - - // Chain GLFW callbacks: our callbacks will call the user's previously installed callbacks, if any. - if (install_callbacks) - ImGui_ImplGlfw_InstallCallbacks(window); - // Register Emscripten Wheel callback to workaround issue in Emscripten GLFW Emulation (#6096) - // We intentionally do not check 'if (install_callbacks)' here, as some users may set it to false and call GLFW callback themselves. - // FIXME: May break chaining in case user registered their own Emscripten callback? -#ifdef __EMSCRIPTEN__ - emscripten_set_wheel_callback(EMSCRIPTEN_EVENT_TARGET_DOCUMENT, nullptr, false, ImGui_ImplEmscripten_WheelCallback); -#endif - - // Update monitors the first time (note: monitor callback are broken in GLFW 3.2 and earlier, see github.com/glfw/glfw/issues/784) - ImGui_ImplGlfw_UpdateMonitors(); - glfwSetMonitorCallback(ImGui_ImplGlfw_MonitorCallback); - - // Set platform dependent data in viewport - ImGuiViewport* main_viewport = ImGui::GetMainViewport(); - main_viewport->PlatformHandle = (void*)bd->Window; -#ifdef _WIN32 - main_viewport->PlatformHandleRaw = glfwGetWin32Window(bd->Window); -#elif defined(__APPLE__) - main_viewport->PlatformHandleRaw = (void*)glfwGetCocoaWindow(bd->Window); -#else - IM_UNUSED(main_viewport); -#endif - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - ImGui_ImplGlfw_InitPlatformInterface(); - - // Windows: register a WndProc hook so we can intercept some messages. -#ifdef _WIN32 - bd->PrevWndProc = (WNDPROC)::GetWindowLongPtr((HWND)main_viewport->PlatformHandleRaw, GWLP_WNDPROC); - IM_ASSERT(bd->PrevWndProc != nullptr); - ::SetWindowLongPtr((HWND)main_viewport->PlatformHandleRaw, GWLP_WNDPROC, (LONG_PTR)ImGui_ImplGlfw_WndProc); -#endif - - bd->ClientApi = client_api; - return true; -} - -bool ImGui_ImplGlfw_InitForOpenGL(GLFWwindow* window, bool install_callbacks) -{ - return ImGui_ImplGlfw_Init(window, install_callbacks, GlfwClientApi_OpenGL); -} - -bool ImGui_ImplGlfw_InitForVulkan(GLFWwindow* window, bool install_callbacks) -{ - return ImGui_ImplGlfw_Init(window, install_callbacks, GlfwClientApi_Vulkan); -} - -bool ImGui_ImplGlfw_InitForOther(GLFWwindow* window, bool install_callbacks) -{ - return ImGui_ImplGlfw_Init(window, install_callbacks, GlfwClientApi_Unknown); -} - -void ImGui_ImplGlfw_Shutdown() -{ - ImGui_ImplGlfw_Data* bd = ImGui_ImplGlfw_GetBackendData(); - IM_ASSERT(bd != nullptr && "No platform backend to shutdown, or already shutdown?"); - ImGuiIO& io = ImGui::GetIO(); - - ImGui_ImplGlfw_ShutdownPlatformInterface(); - - if (bd->InstalledCallbacks) - ImGui_ImplGlfw_RestoreCallbacks(bd->Window); -#ifdef __EMSCRIPTEN__ - emscripten_set_wheel_callback(EMSCRIPTEN_EVENT_TARGET_DOCUMENT, nullptr, false, nullptr); -#endif - - for (ImGuiMouseCursor cursor_n = 0; cursor_n < ImGuiMouseCursor_COUNT; cursor_n++) - glfwDestroyCursor(bd->MouseCursors[cursor_n]); - - // Windows: restore our WndProc hook -#ifdef _WIN32 - ImGuiViewport* main_viewport = ImGui::GetMainViewport(); - ::SetWindowLongPtr((HWND)main_viewport->PlatformHandleRaw, GWLP_WNDPROC, (LONG_PTR)bd->PrevWndProc); - bd->PrevWndProc = nullptr; -#endif - - io.BackendPlatformName = nullptr; - io.BackendPlatformUserData = nullptr; - io.BackendFlags &= ~(ImGuiBackendFlags_HasMouseCursors | ImGuiBackendFlags_HasSetMousePos | ImGuiBackendFlags_HasGamepad | ImGuiBackendFlags_PlatformHasViewports | ImGuiBackendFlags_HasMouseHoveredViewport); - IM_DELETE(bd); -} - -static void ImGui_ImplGlfw_UpdateMouseData() -{ - ImGui_ImplGlfw_Data* bd = ImGui_ImplGlfw_GetBackendData(); - ImGuiIO& io = ImGui::GetIO(); - ImGuiPlatformIO& platform_io = ImGui::GetPlatformIO(); - - - ImGuiID mouse_viewport_id = 0; - const ImVec2 mouse_pos_prev = io.MousePos; - for (int n = 0; n < platform_io.Viewports.Size; n++) - { - ImGuiViewport* viewport = platform_io.Viewports[n]; - GLFWwindow* window = (GLFWwindow*)viewport->PlatformHandle; - -#ifdef __EMSCRIPTEN__ - const bool is_window_focused = true; -#else - const bool is_window_focused = glfwGetWindowAttrib(window, GLFW_FOCUSED) != 0; -#endif - if (is_window_focused) - { - // (Optional) Set OS mouse position from Dear ImGui if requested (rarely used, only when ImGuiConfigFlags_NavEnableSetMousePos is enabled by user) - // When multi-viewports are enabled, all Dear ImGui positions are same as OS positions. - if (io.WantSetMousePos) - glfwSetCursorPos(window, (double)(mouse_pos_prev.x - viewport->Pos.x), (double)(mouse_pos_prev.y - viewport->Pos.y)); - - // (Optional) Fallback to provide mouse position when focused (ImGui_ImplGlfw_CursorPosCallback already provides this when hovered or captured) - if (bd->MouseWindow == nullptr) - { - double mouse_x, mouse_y; - glfwGetCursorPos(window, &mouse_x, &mouse_y); - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - // Single viewport mode: mouse position in client window coordinates (io.MousePos is (0,0) when the mouse is on the upper-left corner of the app window) - // Multi-viewport mode: mouse position in OS absolute coordinates (io.MousePos is (0,0) when the mouse is on the upper-left of the primary monitor) - int window_x, window_y; - glfwGetWindowPos(window, &window_x, &window_y); - mouse_x += window_x; - mouse_y += window_y; - } - bd->LastValidMousePos = ImVec2((float)mouse_x, (float)mouse_y); - io.AddMousePosEvent((float)mouse_x, (float)mouse_y); - } - } - - // (Optional) When using multiple viewports: call io.AddMouseViewportEvent() with the viewport the OS mouse cursor is hovering. - // If ImGuiBackendFlags_HasMouseHoveredViewport is not set by the backend, Dear imGui will ignore this field and infer the information using its flawed heuristic. - // - [X] GLFW >= 3.3 backend ON WINDOWS ONLY does correctly ignore viewports with the _NoInputs flag. - // - [!] GLFW <= 3.2 backend CANNOT correctly ignore viewports with the _NoInputs flag, and CANNOT reported Hovered Viewport because of mouse capture. - // Some backend are not able to handle that correctly. If a backend report an hovered viewport that has the _NoInputs flag (e.g. when dragging a window - // for docking, the viewport has the _NoInputs flag in order to allow us to find the viewport under), then Dear ImGui is forced to ignore the value reported - // by the backend, and use its flawed heuristic to guess the viewport behind. - // - [X] GLFW backend correctly reports this regardless of another viewport behind focused and dragged from (we need this to find a useful drag and drop target). - // FIXME: This is currently only correct on Win32. See what we do below with the WM_NCHITTEST, missing an equivalent for other systems. - // See https://github.com/glfw/glfw/issues/1236 if you want to help in making this a GLFW feature. -#if GLFW_HAS_MOUSE_PASSTHROUGH || (GLFW_HAS_WINDOW_HOVERED && defined(_WIN32)) - const bool window_no_input = (viewport->Flags & ImGuiViewportFlags_NoInputs) != 0; -#if GLFW_HAS_MOUSE_PASSTHROUGH - glfwSetWindowAttrib(window, GLFW_MOUSE_PASSTHROUGH, window_no_input); -#endif - if (glfwGetWindowAttrib(window, GLFW_HOVERED) && !window_no_input) - mouse_viewport_id = viewport->ID; -#else - // We cannot use bd->MouseWindow maintained from CursorEnter/Leave callbacks, because it is locked to the window capturing mouse. -#endif - } - - if (io.BackendFlags & ImGuiBackendFlags_HasMouseHoveredViewport) - io.AddMouseViewportEvent(mouse_viewport_id); -} - -static void ImGui_ImplGlfw_UpdateMouseCursor() -{ - ImGuiIO& io = ImGui::GetIO(); - ImGui_ImplGlfw_Data* bd = ImGui_ImplGlfw_GetBackendData(); - if ((io.ConfigFlags & ImGuiConfigFlags_NoMouseCursorChange) || glfwGetInputMode(bd->Window, GLFW_CURSOR) == GLFW_CURSOR_DISABLED) - return; - - ImGuiMouseCursor imgui_cursor = ImGui::GetMouseCursor(); - ImGuiPlatformIO& platform_io = ImGui::GetPlatformIO(); - for (int n = 0; n < platform_io.Viewports.Size; n++) - { - GLFWwindow* window = (GLFWwindow*)platform_io.Viewports[n]->PlatformHandle; - if (imgui_cursor == ImGuiMouseCursor_None || io.MouseDrawCursor) - { - // Hide OS mouse cursor if imgui is drawing it or if it wants no cursor - glfwSetInputMode(window, GLFW_CURSOR, GLFW_CURSOR_HIDDEN); - } - else - { - // Show OS mouse cursor - // FIXME-PLATFORM: Unfocused windows seems to fail changing the mouse cursor with GLFW 3.2, but 3.3 works here. - glfwSetCursor(window, bd->MouseCursors[imgui_cursor] ? bd->MouseCursors[imgui_cursor] : bd->MouseCursors[ImGuiMouseCursor_Arrow]); - glfwSetInputMode(window, GLFW_CURSOR, GLFW_CURSOR_NORMAL); - } - } -} - -// Update gamepad inputs -static inline float Saturate(float v) { return v < 0.0f ? 0.0f : v > 1.0f ? 1.0f : v; } -static void ImGui_ImplGlfw_UpdateGamepads() -{ - ImGuiIO& io = ImGui::GetIO(); - if ((io.ConfigFlags & ImGuiConfigFlags_NavEnableGamepad) == 0) // FIXME: Technically feeding gamepad shouldn't depend on this now that they are regular inputs. - return; - - io.BackendFlags &= ~ImGuiBackendFlags_HasGamepad; -#if GLFW_HAS_GAMEPAD_API && !defined(__EMSCRIPTEN__) - GLFWgamepadstate gamepad; - if (!glfwGetGamepadState(GLFW_JOYSTICK_1, &gamepad)) - return; - #define MAP_BUTTON(KEY_NO, BUTTON_NO, _UNUSED) do { io.AddKeyEvent(KEY_NO, gamepad.buttons[BUTTON_NO] != 0); } while (0) - #define MAP_ANALOG(KEY_NO, AXIS_NO, _UNUSED, V0, V1) do { float v = gamepad.axes[AXIS_NO]; v = (v - V0) / (V1 - V0); io.AddKeyAnalogEvent(KEY_NO, v > 0.10f, Saturate(v)); } while (0) -#else - int axes_count = 0, buttons_count = 0; - const float* axes = glfwGetJoystickAxes(GLFW_JOYSTICK_1, &axes_count); - const unsigned char* buttons = glfwGetJoystickButtons(GLFW_JOYSTICK_1, &buttons_count); - if (axes_count == 0 || buttons_count == 0) - return; - #define MAP_BUTTON(KEY_NO, _UNUSED, BUTTON_NO) do { io.AddKeyEvent(KEY_NO, (buttons_count > BUTTON_NO && buttons[BUTTON_NO] == GLFW_PRESS)); } while (0) - #define MAP_ANALOG(KEY_NO, _UNUSED, AXIS_NO, V0, V1) do { float v = (axes_count > AXIS_NO) ? axes[AXIS_NO] : V0; v = (v - V0) / (V1 - V0); io.AddKeyAnalogEvent(KEY_NO, v > 0.10f, Saturate(v)); } while (0) -#endif - io.BackendFlags |= ImGuiBackendFlags_HasGamepad; - MAP_BUTTON(ImGuiKey_GamepadStart, GLFW_GAMEPAD_BUTTON_START, 7); - MAP_BUTTON(ImGuiKey_GamepadBack, GLFW_GAMEPAD_BUTTON_BACK, 6); - MAP_BUTTON(ImGuiKey_GamepadFaceLeft, GLFW_GAMEPAD_BUTTON_X, 2); // Xbox X, PS Square - MAP_BUTTON(ImGuiKey_GamepadFaceRight, GLFW_GAMEPAD_BUTTON_B, 1); // Xbox B, PS Circle - MAP_BUTTON(ImGuiKey_GamepadFaceUp, GLFW_GAMEPAD_BUTTON_Y, 3); // Xbox Y, PS Triangle - MAP_BUTTON(ImGuiKey_GamepadFaceDown, GLFW_GAMEPAD_BUTTON_A, 0); // Xbox A, PS Cross - MAP_BUTTON(ImGuiKey_GamepadDpadLeft, GLFW_GAMEPAD_BUTTON_DPAD_LEFT, 13); - MAP_BUTTON(ImGuiKey_GamepadDpadRight, GLFW_GAMEPAD_BUTTON_DPAD_RIGHT, 11); - MAP_BUTTON(ImGuiKey_GamepadDpadUp, GLFW_GAMEPAD_BUTTON_DPAD_UP, 10); - MAP_BUTTON(ImGuiKey_GamepadDpadDown, GLFW_GAMEPAD_BUTTON_DPAD_DOWN, 12); - MAP_BUTTON(ImGuiKey_GamepadL1, GLFW_GAMEPAD_BUTTON_LEFT_BUMPER, 4); - MAP_BUTTON(ImGuiKey_GamepadR1, GLFW_GAMEPAD_BUTTON_RIGHT_BUMPER, 5); - MAP_ANALOG(ImGuiKey_GamepadL2, GLFW_GAMEPAD_AXIS_LEFT_TRIGGER, 4, -0.75f, +1.0f); - MAP_ANALOG(ImGuiKey_GamepadR2, GLFW_GAMEPAD_AXIS_RIGHT_TRIGGER, 5, -0.75f, +1.0f); - MAP_BUTTON(ImGuiKey_GamepadL3, GLFW_GAMEPAD_BUTTON_LEFT_THUMB, 8); - MAP_BUTTON(ImGuiKey_GamepadR3, GLFW_GAMEPAD_BUTTON_RIGHT_THUMB, 9); - MAP_ANALOG(ImGuiKey_GamepadLStickLeft, GLFW_GAMEPAD_AXIS_LEFT_X, 0, -0.25f, -1.0f); - MAP_ANALOG(ImGuiKey_GamepadLStickRight, GLFW_GAMEPAD_AXIS_LEFT_X, 0, +0.25f, +1.0f); - MAP_ANALOG(ImGuiKey_GamepadLStickUp, GLFW_GAMEPAD_AXIS_LEFT_Y, 1, -0.25f, -1.0f); - MAP_ANALOG(ImGuiKey_GamepadLStickDown, GLFW_GAMEPAD_AXIS_LEFT_Y, 1, +0.25f, +1.0f); - MAP_ANALOG(ImGuiKey_GamepadRStickLeft, GLFW_GAMEPAD_AXIS_RIGHT_X, 2, -0.25f, -1.0f); - MAP_ANALOG(ImGuiKey_GamepadRStickRight, GLFW_GAMEPAD_AXIS_RIGHT_X, 2, +0.25f, +1.0f); - MAP_ANALOG(ImGuiKey_GamepadRStickUp, GLFW_GAMEPAD_AXIS_RIGHT_Y, 3, -0.25f, -1.0f); - MAP_ANALOG(ImGuiKey_GamepadRStickDown, GLFW_GAMEPAD_AXIS_RIGHT_Y, 3, +0.25f, +1.0f); - #undef MAP_BUTTON - #undef MAP_ANALOG -} - -static void ImGui_ImplGlfw_UpdateMonitors() -{ - ImGui_ImplGlfw_Data* bd = ImGui_ImplGlfw_GetBackendData(); - ImGuiPlatformIO& platform_io = ImGui::GetPlatformIO(); - bd->WantUpdateMonitors = false; - - int monitors_count = 0; - GLFWmonitor** glfw_monitors = glfwGetMonitors(&monitors_count); - if (monitors_count == 0) // Preserve existing monitor list if there are none. Happens on macOS sleeping (#5683) - return; - - platform_io.Monitors.resize(0); - for (int n = 0; n < monitors_count; n++) - { - ImGuiPlatformMonitor monitor; - int x, y; - glfwGetMonitorPos(glfw_monitors[n], &x, &y); - const GLFWvidmode* vid_mode = glfwGetVideoMode(glfw_monitors[n]); - if (vid_mode == nullptr) - continue; // Failed to get Video mode (e.g. Emscripten does not support this function) - monitor.MainPos = monitor.WorkPos = ImVec2((float)x, (float)y); - monitor.MainSize = monitor.WorkSize = ImVec2((float)vid_mode->width, (float)vid_mode->height); -#if GLFW_HAS_MONITOR_WORK_AREA - int w, h; - glfwGetMonitorWorkarea(glfw_monitors[n], &x, &y, &w, &h); - if (w > 0 && h > 0) // Workaround a small GLFW issue reporting zero on monitor changes: https://github.com/glfw/glfw/pull/1761 - { - monitor.WorkPos = ImVec2((float)x, (float)y); - monitor.WorkSize = ImVec2((float)w, (float)h); - } -#endif -#if GLFW_HAS_PER_MONITOR_DPI - // Warning: the validity of monitor DPI information on Windows depends on the application DPI awareness settings, which generally needs to be set in the manifest or at runtime. - float x_scale, y_scale; - glfwGetMonitorContentScale(glfw_monitors[n], &x_scale, &y_scale); - monitor.DpiScale = x_scale; -#endif - monitor.PlatformHandle = (void*)glfw_monitors[n]; // [...] GLFW doc states: "guaranteed to be valid only until the monitor configuration changes" - platform_io.Monitors.push_back(monitor); - } -} - -void ImGui_ImplGlfw_NewFrame() -{ - ImGuiIO& io = ImGui::GetIO(); - ImGui_ImplGlfw_Data* bd = ImGui_ImplGlfw_GetBackendData(); - IM_ASSERT(bd != nullptr && "Did you call ImGui_ImplGlfw_InitForXXX()?"); - - // Setup display size (every frame to accommodate for window resizing) - int w, h; - int display_w, display_h; - glfwGetWindowSize(bd->Window, &w, &h); - glfwGetFramebufferSize(bd->Window, &display_w, &display_h); - io.DisplaySize = ImVec2((float)w, (float)h); - if (w > 0 && h > 0) - io.DisplayFramebufferScale = ImVec2((float)display_w / (float)w, (float)display_h / (float)h); - if (bd->WantUpdateMonitors) - ImGui_ImplGlfw_UpdateMonitors(); - - // Setup time step - // (Accept glfwGetTime() not returning a monotonically increasing value. Seems to happens on disconnecting peripherals and probably on VMs and Emscripten, see #6491, #6189, #6114, #3644) - double current_time = glfwGetTime(); - if (current_time <= bd->Time) - current_time = bd->Time + 0.00001f; - io.DeltaTime = bd->Time > 0.0 ? (float)(current_time - bd->Time) : (float)(1.0f / 60.0f); - bd->Time = current_time; - - ImGui_ImplGlfw_UpdateMouseData(); - ImGui_ImplGlfw_UpdateMouseCursor(); - - // Update game controllers (if enabled and available) - ImGui_ImplGlfw_UpdateGamepads(); -} - -//-------------------------------------------------------------------------------------------------------- -// MULTI-VIEWPORT / PLATFORM INTERFACE SUPPORT -// This is an _advanced_ and _optional_ feature, allowing the backend to create and handle multiple viewports simultaneously. -// If you are new to dear imgui or creating a new binding for dear imgui, it is recommended that you completely ignore this section first.. -//-------------------------------------------------------------------------------------------------------- - -// Helper structure we store in the void* RendererUserData field of each ImGuiViewport to easily retrieve our backend data. -struct ImGui_ImplGlfw_ViewportData -{ - GLFWwindow* Window; - bool WindowOwned; - int IgnoreWindowPosEventFrame; - int IgnoreWindowSizeEventFrame; -#ifdef _WIN32 - WNDPROC PrevWndProc; -#endif - - ImGui_ImplGlfw_ViewportData() { memset(this, 0, sizeof(*this)); IgnoreWindowSizeEventFrame = IgnoreWindowPosEventFrame = -1; } - ~ImGui_ImplGlfw_ViewportData() { IM_ASSERT(Window == nullptr); } -}; - -static void ImGui_ImplGlfw_WindowCloseCallback(GLFWwindow* window) -{ - if (ImGuiViewport* viewport = ImGui::FindViewportByPlatformHandle(window)) - viewport->PlatformRequestClose = true; -} - -// GLFW may dispatch window pos/size events after calling glfwSetWindowPos()/glfwSetWindowSize(). -// However: depending on the platform the callback may be invoked at different time: -// - on Windows it appears to be called within the glfwSetWindowPos()/glfwSetWindowSize() call -// - on Linux it is queued and invoked during glfwPollEvents() -// Because the event doesn't always fire on glfwSetWindowXXX() we use a frame counter tag to only -// ignore recent glfwSetWindowXXX() calls. -static void ImGui_ImplGlfw_WindowPosCallback(GLFWwindow* window, int, int) -{ - if (ImGuiViewport* viewport = ImGui::FindViewportByPlatformHandle(window)) - { - if (ImGui_ImplGlfw_ViewportData* vd = (ImGui_ImplGlfw_ViewportData*)viewport->PlatformUserData) - { - bool ignore_event = (ImGui::GetFrameCount() <= vd->IgnoreWindowPosEventFrame + 1); - //data->IgnoreWindowPosEventFrame = -1; - if (ignore_event) - return; - } - viewport->PlatformRequestMove = true; - } -} - -static void ImGui_ImplGlfw_WindowSizeCallback(GLFWwindow* window, int, int) -{ - if (ImGuiViewport* viewport = ImGui::FindViewportByPlatformHandle(window)) - { - if (ImGui_ImplGlfw_ViewportData* vd = (ImGui_ImplGlfw_ViewportData*)viewport->PlatformUserData) - { - bool ignore_event = (ImGui::GetFrameCount() <= vd->IgnoreWindowSizeEventFrame + 1); - //data->IgnoreWindowSizeEventFrame = -1; - if (ignore_event) - return; - } - viewport->PlatformRequestResize = true; - } -} - -static void ImGui_ImplGlfw_CreateWindow(ImGuiViewport* viewport) -{ - ImGui_ImplGlfw_Data* bd = ImGui_ImplGlfw_GetBackendData(); - ImGui_ImplGlfw_ViewportData* vd = IM_NEW(ImGui_ImplGlfw_ViewportData)(); - viewport->PlatformUserData = vd; - - // GLFW 3.2 unfortunately always set focus on glfwCreateWindow() if GLFW_VISIBLE is set, regardless of GLFW_FOCUSED - // With GLFW 3.3, the hint GLFW_FOCUS_ON_SHOW fixes this problem - glfwWindowHint(GLFW_VISIBLE, false); - glfwWindowHint(GLFW_FOCUSED, false); -#if GLFW_HAS_FOCUS_ON_SHOW - glfwWindowHint(GLFW_FOCUS_ON_SHOW, false); - #endif - glfwWindowHint(GLFW_DECORATED, (viewport->Flags & ImGuiViewportFlags_NoDecoration) ? false : true); -#if GLFW_HAS_WINDOW_TOPMOST - glfwWindowHint(GLFW_FLOATING, (viewport->Flags & ImGuiViewportFlags_TopMost) ? true : false); -#endif - GLFWwindow* share_window = (bd->ClientApi == GlfwClientApi_OpenGL) ? bd->Window : nullptr; - vd->Window = glfwCreateWindow((int)viewport->Size.x, (int)viewport->Size.y, "No Title Yet", nullptr, share_window); - vd->WindowOwned = true; - viewport->PlatformHandle = (void*)vd->Window; -#ifdef _WIN32 - viewport->PlatformHandleRaw = glfwGetWin32Window(vd->Window); -#elif defined(__APPLE__) - viewport->PlatformHandleRaw = (void*)glfwGetCocoaWindow(vd->Window); -#endif - glfwSetWindowPos(vd->Window, (int)viewport->Pos.x, (int)viewport->Pos.y); - - // Install GLFW callbacks for secondary viewports - glfwSetWindowFocusCallback(vd->Window, ImGui_ImplGlfw_WindowFocusCallback); - glfwSetCursorEnterCallback(vd->Window, ImGui_ImplGlfw_CursorEnterCallback); - glfwSetCursorPosCallback(vd->Window, ImGui_ImplGlfw_CursorPosCallback); - glfwSetMouseButtonCallback(vd->Window, ImGui_ImplGlfw_MouseButtonCallback); - glfwSetScrollCallback(vd->Window, ImGui_ImplGlfw_ScrollCallback); - glfwSetKeyCallback(vd->Window, ImGui_ImplGlfw_KeyCallback); - glfwSetCharCallback(vd->Window, ImGui_ImplGlfw_CharCallback); - glfwSetWindowCloseCallback(vd->Window, ImGui_ImplGlfw_WindowCloseCallback); - glfwSetWindowPosCallback(vd->Window, ImGui_ImplGlfw_WindowPosCallback); - glfwSetWindowSizeCallback(vd->Window, ImGui_ImplGlfw_WindowSizeCallback); - if (bd->ClientApi == GlfwClientApi_OpenGL) - { - glfwMakeContextCurrent(vd->Window); - glfwSwapInterval(0); - } -} - -static void ImGui_ImplGlfw_DestroyWindow(ImGuiViewport* viewport) -{ - ImGui_ImplGlfw_Data* bd = ImGui_ImplGlfw_GetBackendData(); - if (ImGui_ImplGlfw_ViewportData* vd = (ImGui_ImplGlfw_ViewportData*)viewport->PlatformUserData) - { - if (vd->WindowOwned) - { -#if !GLFW_HAS_MOUSE_PASSTHROUGH && GLFW_HAS_WINDOW_HOVERED && defined(_WIN32) - HWND hwnd = (HWND)viewport->PlatformHandleRaw; - ::RemovePropA(hwnd, "IMGUI_VIEWPORT"); -#endif - - // Release any keys that were pressed in the window being destroyed and are still held down, - // because we will not receive any release events after window is destroyed. - for (int i = 0; i < IM_ARRAYSIZE(bd->KeyOwnerWindows); i++) - if (bd->KeyOwnerWindows[i] == vd->Window) - ImGui_ImplGlfw_KeyCallback(vd->Window, i, 0, GLFW_RELEASE, 0); // Later params are only used for main viewport, on which this function is never called. - - glfwDestroyWindow(vd->Window); - } - vd->Window = nullptr; - IM_DELETE(vd); - } - viewport->PlatformUserData = viewport->PlatformHandle = nullptr; -} - -static void ImGui_ImplGlfw_ShowWindow(ImGuiViewport* viewport) -{ - ImGui_ImplGlfw_ViewportData* vd = (ImGui_ImplGlfw_ViewportData*)viewport->PlatformUserData; - -#if defined(_WIN32) - // GLFW hack: Hide icon from task bar - HWND hwnd = (HWND)viewport->PlatformHandleRaw; - if (viewport->Flags & ImGuiViewportFlags_NoTaskBarIcon) - { - LONG ex_style = ::GetWindowLong(hwnd, GWL_EXSTYLE); - ex_style &= ~WS_EX_APPWINDOW; - ex_style |= WS_EX_TOOLWINDOW; - ::SetWindowLong(hwnd, GWL_EXSTYLE, ex_style); - } - - // GLFW hack: install hook for WM_NCHITTEST message handler -#if !GLFW_HAS_MOUSE_PASSTHROUGH && GLFW_HAS_WINDOW_HOVERED && defined(_WIN32) - ::SetPropA(hwnd, "IMGUI_VIEWPORT", viewport); - vd->PrevWndProc = (WNDPROC)::GetWindowLongPtr(hwnd, GWLP_WNDPROC); - ::SetWindowLongPtr(hwnd, GWLP_WNDPROC, (LONG_PTR)ImGui_ImplGlfw_WndProc); -#endif - -#if !GLFW_HAS_FOCUS_ON_SHOW - // GLFW hack: GLFW 3.2 has a bug where glfwShowWindow() also activates/focus the window. - // The fix was pushed to GLFW repository on 2018/01/09 and should be included in GLFW 3.3 via a GLFW_FOCUS_ON_SHOW window attribute. - // See https://github.com/glfw/glfw/issues/1189 - // FIXME-VIEWPORT: Implement same work-around for Linux/OSX in the meanwhile. - if (viewport->Flags & ImGuiViewportFlags_NoFocusOnAppearing) - { - ::ShowWindow(hwnd, SW_SHOWNA); - return; - } -#endif -#endif - - glfwShowWindow(vd->Window); -} - -static ImVec2 ImGui_ImplGlfw_GetWindowPos(ImGuiViewport* viewport) -{ - ImGui_ImplGlfw_ViewportData* vd = (ImGui_ImplGlfw_ViewportData*)viewport->PlatformUserData; - int x = 0, y = 0; - glfwGetWindowPos(vd->Window, &x, &y); - return ImVec2((float)x, (float)y); -} - -static void ImGui_ImplGlfw_SetWindowPos(ImGuiViewport* viewport, ImVec2 pos) -{ - ImGui_ImplGlfw_ViewportData* vd = (ImGui_ImplGlfw_ViewportData*)viewport->PlatformUserData; - vd->IgnoreWindowPosEventFrame = ImGui::GetFrameCount(); - glfwSetWindowPos(vd->Window, (int)pos.x, (int)pos.y); -} - -static ImVec2 ImGui_ImplGlfw_GetWindowSize(ImGuiViewport* viewport) -{ - ImGui_ImplGlfw_ViewportData* vd = (ImGui_ImplGlfw_ViewportData*)viewport->PlatformUserData; - int w = 0, h = 0; - glfwGetWindowSize(vd->Window, &w, &h); - return ImVec2((float)w, (float)h); -} - -static void ImGui_ImplGlfw_SetWindowSize(ImGuiViewport* viewport, ImVec2 size) -{ - ImGui_ImplGlfw_ViewportData* vd = (ImGui_ImplGlfw_ViewportData*)viewport->PlatformUserData; -#if __APPLE__ && !GLFW_HAS_OSX_WINDOW_POS_FIX - // Native OS windows are positioned from the bottom-left corner on macOS, whereas on other platforms they are - // positioned from the upper-left corner. GLFW makes an effort to convert macOS style coordinates, however it - // doesn't handle it when changing size. We are manually moving the window in order for changes of size to be based - // on the upper-left corner. - int x, y, width, height; - glfwGetWindowPos(vd->Window, &x, &y); - glfwGetWindowSize(vd->Window, &width, &height); - glfwSetWindowPos(vd->Window, x, y - height + size.y); -#endif - vd->IgnoreWindowSizeEventFrame = ImGui::GetFrameCount(); - glfwSetWindowSize(vd->Window, (int)size.x, (int)size.y); -} - -static void ImGui_ImplGlfw_SetWindowTitle(ImGuiViewport* viewport, const char* title) -{ - ImGui_ImplGlfw_ViewportData* vd = (ImGui_ImplGlfw_ViewportData*)viewport->PlatformUserData; - glfwSetWindowTitle(vd->Window, title); -} - -static void ImGui_ImplGlfw_SetWindowFocus(ImGuiViewport* viewport) -{ -#if GLFW_HAS_FOCUS_WINDOW - ImGui_ImplGlfw_ViewportData* vd = (ImGui_ImplGlfw_ViewportData*)viewport->PlatformUserData; - glfwFocusWindow(vd->Window); -#else - // FIXME: What are the effect of not having this function? At the moment imgui doesn't actually call SetWindowFocus - we set that up ahead, will answer that question later. - (void)viewport; -#endif -} - -static bool ImGui_ImplGlfw_GetWindowFocus(ImGuiViewport* viewport) -{ - ImGui_ImplGlfw_ViewportData* vd = (ImGui_ImplGlfw_ViewportData*)viewport->PlatformUserData; - return glfwGetWindowAttrib(vd->Window, GLFW_FOCUSED) != 0; -} - -static bool ImGui_ImplGlfw_GetWindowMinimized(ImGuiViewport* viewport) -{ - ImGui_ImplGlfw_ViewportData* vd = (ImGui_ImplGlfw_ViewportData*)viewport->PlatformUserData; - return glfwGetWindowAttrib(vd->Window, GLFW_ICONIFIED) != 0; -} - -#if GLFW_HAS_WINDOW_ALPHA -static void ImGui_ImplGlfw_SetWindowAlpha(ImGuiViewport* viewport, float alpha) -{ - ImGui_ImplGlfw_ViewportData* vd = (ImGui_ImplGlfw_ViewportData*)viewport->PlatformUserData; - glfwSetWindowOpacity(vd->Window, alpha); -} -#endif - -static void ImGui_ImplGlfw_RenderWindow(ImGuiViewport* viewport, void*) -{ - ImGui_ImplGlfw_Data* bd = ImGui_ImplGlfw_GetBackendData(); - ImGui_ImplGlfw_ViewportData* vd = (ImGui_ImplGlfw_ViewportData*)viewport->PlatformUserData; - if (bd->ClientApi == GlfwClientApi_OpenGL) - glfwMakeContextCurrent(vd->Window); -} - -static void ImGui_ImplGlfw_SwapBuffers(ImGuiViewport* viewport, void*) -{ - ImGui_ImplGlfw_Data* bd = ImGui_ImplGlfw_GetBackendData(); - ImGui_ImplGlfw_ViewportData* vd = (ImGui_ImplGlfw_ViewportData*)viewport->PlatformUserData; - if (bd->ClientApi == GlfwClientApi_OpenGL) - { - glfwMakeContextCurrent(vd->Window); - glfwSwapBuffers(vd->Window); - } -} - -//-------------------------------------------------------------------------------------------------------- -// Vulkan support (the Vulkan renderer needs to call a platform-side support function to create the surface) -//-------------------------------------------------------------------------------------------------------- - -// Avoid including so we can build without it -#if GLFW_HAS_VULKAN -#ifndef VULKAN_H_ -#define VK_DEFINE_HANDLE(object) typedef struct object##_T* object; -#if defined(__LP64__) || defined(_WIN64) || defined(__x86_64__) || defined(_M_X64) || defined(__ia64) || defined (_M_IA64) || defined(__aarch64__) || defined(__powerpc64__) -#define VK_DEFINE_NON_DISPATCHABLE_HANDLE(object) typedef struct object##_T *object; -#else -#define VK_DEFINE_NON_DISPATCHABLE_HANDLE(object) typedef uint64_t object; -#endif -VK_DEFINE_HANDLE(VkInstance) -VK_DEFINE_NON_DISPATCHABLE_HANDLE(VkSurfaceKHR) -struct VkAllocationCallbacks; -enum VkResult { VK_RESULT_MAX_ENUM = 0x7FFFFFFF }; -#endif // VULKAN_H_ -extern "C" { extern GLFWAPI VkResult glfwCreateWindowSurface(VkInstance instance, GLFWwindow* window, const VkAllocationCallbacks* allocator, VkSurfaceKHR* surface); } -static int ImGui_ImplGlfw_CreateVkSurface(ImGuiViewport* viewport, ImU64 vk_instance, const void* vk_allocator, ImU64* out_vk_surface) -{ - ImGui_ImplGlfw_Data* bd = ImGui_ImplGlfw_GetBackendData(); - ImGui_ImplGlfw_ViewportData* vd = (ImGui_ImplGlfw_ViewportData*)viewport->PlatformUserData; - IM_UNUSED(bd); - IM_ASSERT(bd->ClientApi == GlfwClientApi_Vulkan); - VkResult err = glfwCreateWindowSurface((VkInstance)vk_instance, vd->Window, (const VkAllocationCallbacks*)vk_allocator, (VkSurfaceKHR*)out_vk_surface); - return (int)err; -} -#endif // GLFW_HAS_VULKAN - -static void ImGui_ImplGlfw_InitPlatformInterface() -{ - // Register platform interface (will be coupled with a renderer interface) - ImGui_ImplGlfw_Data* bd = ImGui_ImplGlfw_GetBackendData(); - ImGuiPlatformIO& platform_io = ImGui::GetPlatformIO(); - platform_io.Platform_CreateWindow = ImGui_ImplGlfw_CreateWindow; - platform_io.Platform_DestroyWindow = ImGui_ImplGlfw_DestroyWindow; - platform_io.Platform_ShowWindow = ImGui_ImplGlfw_ShowWindow; - platform_io.Platform_SetWindowPos = ImGui_ImplGlfw_SetWindowPos; - platform_io.Platform_GetWindowPos = ImGui_ImplGlfw_GetWindowPos; - platform_io.Platform_SetWindowSize = ImGui_ImplGlfw_SetWindowSize; - platform_io.Platform_GetWindowSize = ImGui_ImplGlfw_GetWindowSize; - platform_io.Platform_SetWindowFocus = ImGui_ImplGlfw_SetWindowFocus; - platform_io.Platform_GetWindowFocus = ImGui_ImplGlfw_GetWindowFocus; - platform_io.Platform_GetWindowMinimized = ImGui_ImplGlfw_GetWindowMinimized; - platform_io.Platform_SetWindowTitle = ImGui_ImplGlfw_SetWindowTitle; - platform_io.Platform_RenderWindow = ImGui_ImplGlfw_RenderWindow; - platform_io.Platform_SwapBuffers = ImGui_ImplGlfw_SwapBuffers; -#if GLFW_HAS_WINDOW_ALPHA - platform_io.Platform_SetWindowAlpha = ImGui_ImplGlfw_SetWindowAlpha; -#endif -#if GLFW_HAS_VULKAN - platform_io.Platform_CreateVkSurface = ImGui_ImplGlfw_CreateVkSurface; -#endif - - // Register main window handle (which is owned by the main application, not by us) - // This is mostly for simplicity and consistency, so that our code (e.g. mouse handling etc.) can use same logic for main and secondary viewports. - ImGuiViewport* main_viewport = ImGui::GetMainViewport(); - ImGui_ImplGlfw_ViewportData* vd = IM_NEW(ImGui_ImplGlfw_ViewportData)(); - vd->Window = bd->Window; - vd->WindowOwned = false; - main_viewport->PlatformUserData = vd; - main_viewport->PlatformHandle = (void*)bd->Window; -} - -static void ImGui_ImplGlfw_ShutdownPlatformInterface() -{ - ImGui::DestroyPlatformWindows(); -} - -//----------------------------------------------------------------------------- - -// WndProc hook (declared here because we will need access to ImGui_ImplGlfw_ViewportData) -#ifdef _WIN32 -static ImGuiMouseSource GetMouseSourceFromMessageExtraInfo() -{ - LPARAM extra_info = ::GetMessageExtraInfo(); - if ((extra_info & 0xFFFFFF80) == 0xFF515700) - return ImGuiMouseSource_Pen; - if ((extra_info & 0xFFFFFF80) == 0xFF515780) - return ImGuiMouseSource_TouchScreen; - return ImGuiMouseSource_Mouse; -} -static LRESULT CALLBACK ImGui_ImplGlfw_WndProc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam) -{ - ImGui_ImplGlfw_Data* bd = ImGui_ImplGlfw_GetBackendData(); - WNDPROC prev_wndproc = bd->PrevWndProc; - ImGuiViewport* viewport = (ImGuiViewport*)::GetPropA(hWnd, "IMGUI_VIEWPORT"); - if (viewport != NULL) - if (ImGui_ImplGlfw_ViewportData* vd = (ImGui_ImplGlfw_ViewportData*)viewport->PlatformUserData) - prev_wndproc = vd->PrevWndProc; - - switch (msg) - { - // GLFW doesn't allow to distinguish Mouse vs TouchScreen vs Pen. - // Add support for Win32 (based on imgui_impl_win32), because we rely on _TouchScreen info to trickle inputs differently. - case WM_MOUSEMOVE: case WM_NCMOUSEMOVE: - case WM_LBUTTONDOWN: case WM_LBUTTONDBLCLK: case WM_LBUTTONUP: - case WM_RBUTTONDOWN: case WM_RBUTTONDBLCLK: case WM_RBUTTONUP: - case WM_MBUTTONDOWN: case WM_MBUTTONDBLCLK: case WM_MBUTTONUP: - case WM_XBUTTONDOWN: case WM_XBUTTONDBLCLK: case WM_XBUTTONUP: - ImGui::GetIO().AddMouseSourceEvent(GetMouseSourceFromMessageExtraInfo()); - break; - - // We have submitted https://github.com/glfw/glfw/pull/1568 to allow GLFW to support "transparent inputs". - // In the meanwhile we implement custom per-platform workarounds here (FIXME-VIEWPORT: Implement same work-around for Linux/OSX!) -#if !GLFW_HAS_MOUSE_PASSTHROUGH && GLFW_HAS_WINDOW_HOVERED - case WM_NCHITTEST: - { - // Let mouse pass-through the window. This will allow the backend to call io.AddMouseViewportEvent() properly (which is OPTIONAL). - // The ImGuiViewportFlags_NoInputs flag is set while dragging a viewport, as want to detect the window behind the one we are dragging. - // If you cannot easily access those viewport flags from your windowing/event code: you may manually synchronize its state e.g. in - // your main loop after calling UpdatePlatformWindows(). Iterate all viewports/platform windows and pass the flag to your windowing system. - if (viewport && (viewport->Flags & ImGuiViewportFlags_NoInputs)) - return HTTRANSPARENT; - break; - } -#endif - } - return ::CallWindowProc(prev_wndproc, hWnd, msg, wParam, lParam); -} -#endif // #ifdef _WIN32 - -//----------------------------------------------------------------------------- - -#if defined(__clang__) -#pragma clang diagnostic pop -#endif - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_glfw.h b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_glfw.h deleted file mode 100644 index d2fcbbb..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_glfw.h +++ /dev/null @@ -1,58 +0,0 @@ -// dear imgui: Platform Backend for GLFW -// This needs to be used along with a Renderer (e.g. OpenGL3, Vulkan, WebGPU..) -// (Info: GLFW is a cross-platform general purpose library for handling windows, inputs, OpenGL/Vulkan graphics context creation, etc.) -// (Requires: GLFW 3.1+. Prefer GLFW 3.3+ for full feature support.) - -// Implemented features: -// [X] Platform: Clipboard support. -// [X] Platform: Mouse support. Can discriminate Mouse/TouchScreen/Pen (Windows only). -// [X] Platform: Keyboard support. Since 1.87 we are using the io.AddKeyEvent() function. Pass ImGuiKey values to all key functions e.g. ImGui::IsKeyPressed(ImGuiKey_Space). [Legacy GLFW_KEY_* values will also be supported unless IMGUI_DISABLE_OBSOLETE_KEYIO is set] -// [X] Platform: Gamepad support. Enable with 'io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad'. -// [x] Platform: Mouse cursor shape and visibility. Disable with 'io.ConfigFlags |= ImGuiConfigFlags_NoMouseCursorChange' (note: the resizing cursors requires GLFW 3.4+). -// [X] Platform: Multi-viewport support (multiple windows). Enable with 'io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable'. - -// Issues: -// [ ] Platform: Multi-viewport support: ParentViewportID not honored, and so io.ConfigViewportsNoDefaultParent has no effect (minor). - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#pragma once -#include "imgui.h" // IMGUI_IMPL_API -#ifndef IMGUI_DISABLE - -struct GLFWwindow; -struct GLFWmonitor; - -IMGUI_IMPL_API bool ImGui_ImplGlfw_InitForOpenGL(GLFWwindow* window, bool install_callbacks); -IMGUI_IMPL_API bool ImGui_ImplGlfw_InitForVulkan(GLFWwindow* window, bool install_callbacks); -IMGUI_IMPL_API bool ImGui_ImplGlfw_InitForOther(GLFWwindow* window, bool install_callbacks); -IMGUI_IMPL_API void ImGui_ImplGlfw_Shutdown(); -IMGUI_IMPL_API void ImGui_ImplGlfw_NewFrame(); - -// GLFW callbacks install -// - When calling Init with 'install_callbacks=true': ImGui_ImplGlfw_InstallCallbacks() is called. GLFW callbacks will be installed for you. They will chain-call user's previously installed callbacks, if any. -// - When calling Init with 'install_callbacks=false': GLFW callbacks won't be installed. You will need to call individual function yourself from your own GLFW callbacks. -IMGUI_IMPL_API void ImGui_ImplGlfw_InstallCallbacks(GLFWwindow* window); -IMGUI_IMPL_API void ImGui_ImplGlfw_RestoreCallbacks(GLFWwindow* window); - -// GFLW callbacks options: -// - Set 'chain_for_all_windows=true' to enable chaining callbacks for all windows (including secondary viewports created by backends or by user) -IMGUI_IMPL_API void ImGui_ImplGlfw_SetCallbacksChainForAllWindows(bool chain_for_all_windows); - -// GLFW callbacks (individual callbacks to call yourself if you didn't install callbacks) -IMGUI_IMPL_API void ImGui_ImplGlfw_WindowFocusCallback(GLFWwindow* window, int focused); // Since 1.84 -IMGUI_IMPL_API void ImGui_ImplGlfw_CursorEnterCallback(GLFWwindow* window, int entered); // Since 1.84 -IMGUI_IMPL_API void ImGui_ImplGlfw_CursorPosCallback(GLFWwindow* window, double x, double y); // Since 1.87 -IMGUI_IMPL_API void ImGui_ImplGlfw_MouseButtonCallback(GLFWwindow* window, int button, int action, int mods); -IMGUI_IMPL_API void ImGui_ImplGlfw_ScrollCallback(GLFWwindow* window, double xoffset, double yoffset); -IMGUI_IMPL_API void ImGui_ImplGlfw_KeyCallback(GLFWwindow* window, int key, int scancode, int action, int mods); -IMGUI_IMPL_API void ImGui_ImplGlfw_CharCallback(GLFWwindow* window, unsigned int c); -IMGUI_IMPL_API void ImGui_ImplGlfw_MonitorCallback(GLFWmonitor* monitor, int event); - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_glut.cpp b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_glut.cpp deleted file mode 100644 index a6f02d7..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_glut.cpp +++ /dev/null @@ -1,308 +0,0 @@ -// dear imgui: Platform Backend for GLUT/FreeGLUT -// This needs to be used along with a Renderer (e.g. OpenGL2) - -// !!! GLUT/FreeGLUT IS OBSOLETE PREHISTORIC SOFTWARE. Using GLUT is not recommended unless you really miss the 90's. !!! -// !!! If someone or something is teaching you GLUT today, you are being abused. Please show some resistance. !!! -// !!! Nowadays, prefer using GLFW or SDL instead! - -// Implemented features: -// [X] Platform: Partial keyboard support. Since 1.87 we are using the io.AddKeyEvent() function. Pass ImGuiKey values to all key functions e.g. ImGui::IsKeyPressed(ImGuiKey_Space). [Legacy GLUT values will also be supported unless IMGUI_DISABLE_OBSOLETE_KEYIO is set] -// Missing features: -// [ ] Platform: GLUT is unable to distinguish e.g. Backspace from CTRL+H or TAB from CTRL+I -// [ ] Platform: Missing horizontal mouse wheel support. -// [ ] Platform: Missing mouse cursor shape/visibility support. -// [ ] Platform: Missing clipboard support (not supported by Glut). -// [ ] Platform: Missing gamepad support. - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -// CHANGELOG -// (minor and older changes stripped away, please see git history for details) -// 2023-04-17: BREAKING: Removed call to ImGui::NewFrame() from ImGui_ImplGLUT_NewFrame(). Needs to be called from the main application loop, like with every other backends. -// 2022-09-26: Inputs: Renamed ImGuiKey_ModXXX introduced in 1.87 to ImGuiMod_XXX (old names still supported). -// 2022-01-26: Inputs: replaced short-lived io.AddKeyModsEvent() (added two weeks ago) with io.AddKeyEvent() using ImGuiKey_ModXXX flags. Sorry for the confusion. -// 2022-01-17: Inputs: calling new io.AddMousePosEvent(), io.AddMouseButtonEvent(), io.AddMouseWheelEvent() API (1.87+). -// 2022-01-10: Inputs: calling new io.AddKeyEvent(), io.AddKeyModsEvent() + io.SetKeyEventNativeData() API (1.87+). Support for full ImGuiKey range. -// 2019-04-03: Misc: Renamed imgui_impl_freeglut.cpp/.h to imgui_impl_glut.cpp/.h. -// 2019-03-25: Misc: Made io.DeltaTime always above zero. -// 2018-11-30: Misc: Setting up io.BackendPlatformName so it can be displayed in the About Window. -// 2018-03-22: Added GLUT Platform binding. - -#include "imgui.h" -#ifndef IMGUI_DISABLE -#include "imgui_impl_glut.h" -#define GL_SILENCE_DEPRECATION -#ifdef __APPLE__ -#include -#else -#include -#endif - -#ifdef _MSC_VER -#pragma warning (disable: 4505) // unreferenced local function has been removed (stb stuff) -#endif - -static int g_Time = 0; // Current time, in milliseconds - -// Glut has 1 function for characters and one for "special keys". We map the characters in the 0..255 range and the keys above. -static ImGuiKey ImGui_ImplGLUT_KeyToImGuiKey(int key) -{ - switch (key) - { - case '\t': return ImGuiKey_Tab; - case 256 + GLUT_KEY_LEFT: return ImGuiKey_LeftArrow; - case 256 + GLUT_KEY_RIGHT: return ImGuiKey_RightArrow; - case 256 + GLUT_KEY_UP: return ImGuiKey_UpArrow; - case 256 + GLUT_KEY_DOWN: return ImGuiKey_DownArrow; - case 256 + GLUT_KEY_PAGE_UP: return ImGuiKey_PageUp; - case 256 + GLUT_KEY_PAGE_DOWN: return ImGuiKey_PageDown; - case 256 + GLUT_KEY_HOME: return ImGuiKey_Home; - case 256 + GLUT_KEY_END: return ImGuiKey_End; - case 256 + GLUT_KEY_INSERT: return ImGuiKey_Insert; - case 127: return ImGuiKey_Delete; - case 8: return ImGuiKey_Backspace; - case ' ': return ImGuiKey_Space; - case 13: return ImGuiKey_Enter; - case 27: return ImGuiKey_Escape; - case 39: return ImGuiKey_Apostrophe; - case 44: return ImGuiKey_Comma; - case 45: return ImGuiKey_Minus; - case 46: return ImGuiKey_Period; - case 47: return ImGuiKey_Slash; - case 59: return ImGuiKey_Semicolon; - case 61: return ImGuiKey_Equal; - case 91: return ImGuiKey_LeftBracket; - case 92: return ImGuiKey_Backslash; - case 93: return ImGuiKey_RightBracket; - case 96: return ImGuiKey_GraveAccent; - //case 0: return ImGuiKey_CapsLock; - //case 0: return ImGuiKey_ScrollLock; - case 256 + 0x006D: return ImGuiKey_NumLock; - //case 0: return ImGuiKey_PrintScreen; - //case 0: return ImGuiKey_Pause; - //case '0': return ImGuiKey_Keypad0; - //case '1': return ImGuiKey_Keypad1; - //case '2': return ImGuiKey_Keypad2; - //case '3': return ImGuiKey_Keypad3; - //case '4': return ImGuiKey_Keypad4; - //case '5': return ImGuiKey_Keypad5; - //case '6': return ImGuiKey_Keypad6; - //case '7': return ImGuiKey_Keypad7; - //case '8': return ImGuiKey_Keypad8; - //case '9': return ImGuiKey_Keypad9; - //case 46: return ImGuiKey_KeypadDecimal; - //case 47: return ImGuiKey_KeypadDivide; - case 42: return ImGuiKey_KeypadMultiply; - //case 45: return ImGuiKey_KeypadSubtract; - case 43: return ImGuiKey_KeypadAdd; - //case 13: return ImGuiKey_KeypadEnter; - //case 0: return ImGuiKey_KeypadEqual; - case 256 + 0x0072: return ImGuiKey_LeftCtrl; - case 256 + 0x0070: return ImGuiKey_LeftShift; - case 256 + 0x0074: return ImGuiKey_LeftAlt; - //case 0: return ImGuiKey_LeftSuper; - case 256 + 0x0073: return ImGuiKey_RightCtrl; - case 256 + 0x0071: return ImGuiKey_RightShift; - case 256 + 0x0075: return ImGuiKey_RightAlt; - //case 0: return ImGuiKey_RightSuper; - //case 0: return ImGuiKey_Menu; - case '0': return ImGuiKey_0; - case '1': return ImGuiKey_1; - case '2': return ImGuiKey_2; - case '3': return ImGuiKey_3; - case '4': return ImGuiKey_4; - case '5': return ImGuiKey_5; - case '6': return ImGuiKey_6; - case '7': return ImGuiKey_7; - case '8': return ImGuiKey_8; - case '9': return ImGuiKey_9; - case 'A': case 'a': return ImGuiKey_A; - case 'B': case 'b': return ImGuiKey_B; - case 'C': case 'c': return ImGuiKey_C; - case 'D': case 'd': return ImGuiKey_D; - case 'E': case 'e': return ImGuiKey_E; - case 'F': case 'f': return ImGuiKey_F; - case 'G': case 'g': return ImGuiKey_G; - case 'H': case 'h': return ImGuiKey_H; - case 'I': case 'i': return ImGuiKey_I; - case 'J': case 'j': return ImGuiKey_J; - case 'K': case 'k': return ImGuiKey_K; - case 'L': case 'l': return ImGuiKey_L; - case 'M': case 'm': return ImGuiKey_M; - case 'N': case 'n': return ImGuiKey_N; - case 'O': case 'o': return ImGuiKey_O; - case 'P': case 'p': return ImGuiKey_P; - case 'Q': case 'q': return ImGuiKey_Q; - case 'R': case 'r': return ImGuiKey_R; - case 'S': case 's': return ImGuiKey_S; - case 'T': case 't': return ImGuiKey_T; - case 'U': case 'u': return ImGuiKey_U; - case 'V': case 'v': return ImGuiKey_V; - case 'W': case 'w': return ImGuiKey_W; - case 'X': case 'x': return ImGuiKey_X; - case 'Y': case 'y': return ImGuiKey_Y; - case 'Z': case 'z': return ImGuiKey_Z; - case 256 + GLUT_KEY_F1: return ImGuiKey_F1; - case 256 + GLUT_KEY_F2: return ImGuiKey_F2; - case 256 + GLUT_KEY_F3: return ImGuiKey_F3; - case 256 + GLUT_KEY_F4: return ImGuiKey_F4; - case 256 + GLUT_KEY_F5: return ImGuiKey_F5; - case 256 + GLUT_KEY_F6: return ImGuiKey_F6; - case 256 + GLUT_KEY_F7: return ImGuiKey_F7; - case 256 + GLUT_KEY_F8: return ImGuiKey_F8; - case 256 + GLUT_KEY_F9: return ImGuiKey_F9; - case 256 + GLUT_KEY_F10: return ImGuiKey_F10; - case 256 + GLUT_KEY_F11: return ImGuiKey_F11; - case 256 + GLUT_KEY_F12: return ImGuiKey_F12; - default: return ImGuiKey_None; - } -} - -bool ImGui_ImplGLUT_Init() -{ - ImGuiIO& io = ImGui::GetIO(); - -#ifdef FREEGLUT - io.BackendPlatformName = "imgui_impl_glut (freeglut)"; -#else - io.BackendPlatformName = "imgui_impl_glut"; -#endif - g_Time = 0; - - return true; -} - -void ImGui_ImplGLUT_InstallFuncs() -{ - glutReshapeFunc(ImGui_ImplGLUT_ReshapeFunc); - glutMotionFunc(ImGui_ImplGLUT_MotionFunc); - glutPassiveMotionFunc(ImGui_ImplGLUT_MotionFunc); - glutMouseFunc(ImGui_ImplGLUT_MouseFunc); -#ifdef __FREEGLUT_EXT_H__ - glutMouseWheelFunc(ImGui_ImplGLUT_MouseWheelFunc); -#endif - glutKeyboardFunc(ImGui_ImplGLUT_KeyboardFunc); - glutKeyboardUpFunc(ImGui_ImplGLUT_KeyboardUpFunc); - glutSpecialFunc(ImGui_ImplGLUT_SpecialFunc); - glutSpecialUpFunc(ImGui_ImplGLUT_SpecialUpFunc); -} - -void ImGui_ImplGLUT_Shutdown() -{ - ImGuiIO& io = ImGui::GetIO(); - io.BackendPlatformName = nullptr; -} - -void ImGui_ImplGLUT_NewFrame() -{ - // Setup time step - ImGuiIO& io = ImGui::GetIO(); - int current_time = glutGet(GLUT_ELAPSED_TIME); - int delta_time_ms = (current_time - g_Time); - if (delta_time_ms <= 0) - delta_time_ms = 1; - io.DeltaTime = delta_time_ms / 1000.0f; - g_Time = current_time; -} - -static void ImGui_ImplGLUT_UpdateKeyModifiers() -{ - ImGuiIO& io = ImGui::GetIO(); - int glut_key_mods = glutGetModifiers(); - io.AddKeyEvent(ImGuiMod_Ctrl, (glut_key_mods & GLUT_ACTIVE_CTRL) != 0); - io.AddKeyEvent(ImGuiMod_Shift, (glut_key_mods & GLUT_ACTIVE_SHIFT) != 0); - io.AddKeyEvent(ImGuiMod_Alt, (glut_key_mods & GLUT_ACTIVE_ALT) != 0); -} - -static void ImGui_ImplGLUT_AddKeyEvent(ImGuiKey key, bool down, int native_keycode) -{ - ImGuiIO& io = ImGui::GetIO(); - io.AddKeyEvent(key, down); - io.SetKeyEventNativeData(key, native_keycode, -1); // To support legacy indexing (<1.87 user code) -} - -void ImGui_ImplGLUT_KeyboardFunc(unsigned char c, int x, int y) -{ - // Send character to imgui - //printf("char_down_func %d '%c'\n", c, c); - ImGuiIO& io = ImGui::GetIO(); - if (c >= 32) - io.AddInputCharacter((unsigned int)c); - - ImGuiKey key = ImGui_ImplGLUT_KeyToImGuiKey(c); - ImGui_ImplGLUT_AddKeyEvent(key, true, c); - ImGui_ImplGLUT_UpdateKeyModifiers(); - (void)x; (void)y; // Unused -} - -void ImGui_ImplGLUT_KeyboardUpFunc(unsigned char c, int x, int y) -{ - //printf("char_up_func %d '%c'\n", c, c); - ImGuiKey key = ImGui_ImplGLUT_KeyToImGuiKey(c); - ImGui_ImplGLUT_AddKeyEvent(key, false, c); - ImGui_ImplGLUT_UpdateKeyModifiers(); - (void)x; (void)y; // Unused -} - -void ImGui_ImplGLUT_SpecialFunc(int key, int x, int y) -{ - //printf("key_down_func %d\n", key); - ImGuiKey imgui_key = ImGui_ImplGLUT_KeyToImGuiKey(key + 256); - ImGui_ImplGLUT_AddKeyEvent(imgui_key, true, key + 256); - ImGui_ImplGLUT_UpdateKeyModifiers(); - (void)x; (void)y; // Unused -} - -void ImGui_ImplGLUT_SpecialUpFunc(int key, int x, int y) -{ - //printf("key_up_func %d\n", key); - ImGuiKey imgui_key = ImGui_ImplGLUT_KeyToImGuiKey(key + 256); - ImGui_ImplGLUT_AddKeyEvent(imgui_key, false, key + 256); - ImGui_ImplGLUT_UpdateKeyModifiers(); - (void)x; (void)y; // Unused -} - -void ImGui_ImplGLUT_MouseFunc(int glut_button, int state, int x, int y) -{ - ImGuiIO& io = ImGui::GetIO(); - io.AddMousePosEvent((float)x, (float)y); - int button = -1; - if (glut_button == GLUT_LEFT_BUTTON) button = 0; - if (glut_button == GLUT_RIGHT_BUTTON) button = 1; - if (glut_button == GLUT_MIDDLE_BUTTON) button = 2; - if (button != -1 && (state == GLUT_DOWN || state == GLUT_UP)) - io.AddMouseButtonEvent(button, state == GLUT_DOWN); -} - -#ifdef __FREEGLUT_EXT_H__ -void ImGui_ImplGLUT_MouseWheelFunc(int button, int dir, int x, int y) -{ - ImGuiIO& io = ImGui::GetIO(); - io.AddMousePosEvent((float)x, (float)y); - if (dir != 0) - io.AddMouseWheelEvent(0.0f, dir > 0 ? 1.0f : -1.0f); - (void)button; // Unused -} -#endif - -void ImGui_ImplGLUT_ReshapeFunc(int w, int h) -{ - ImGuiIO& io = ImGui::GetIO(); - io.DisplaySize = ImVec2((float)w, (float)h); -} - -void ImGui_ImplGLUT_MotionFunc(int x, int y) -{ - ImGuiIO& io = ImGui::GetIO(); - io.AddMousePosEvent((float)x, (float)y); -} - -//----------------------------------------------------------------------------- - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_glut.h b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_glut.h deleted file mode 100644 index 0067192..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_glut.h +++ /dev/null @@ -1,46 +0,0 @@ -// dear imgui: Platform Backend for GLUT/FreeGLUT -// This needs to be used along with a Renderer (e.g. OpenGL2) - -// !!! GLUT/FreeGLUT IS OBSOLETE PREHISTORIC SOFTWARE. Using GLUT is not recommended unless you really miss the 90's. !!! -// !!! If someone or something is teaching you GLUT today, you are being abused. Please show some resistance. !!! -// !!! Nowadays, prefer using GLFW or SDL instead! - -// Implemented features: -// [X] Platform: Partial keyboard support. Since 1.87 we are using the io.AddKeyEvent() function. Pass ImGuiKey values to all key functions e.g. ImGui::IsKeyPressed(ImGuiKey_Space). [Legacy GLUT values will also be supported unless IMGUI_DISABLE_OBSOLETE_KEYIO is set] -// Missing features: -// [ ] Platform: GLUT is unable to distinguish e.g. Backspace from CTRL+H or TAB from CTRL+I -// [ ] Platform: Missing horizontal mouse wheel support. -// [ ] Platform: Missing mouse cursor shape/visibility support. -// [ ] Platform: Missing clipboard support (not supported by Glut). -// [ ] Platform: Missing gamepad support. - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#pragma once -#ifndef IMGUI_DISABLE -#include "imgui.h" // IMGUI_IMPL_API - -IMGUI_IMPL_API bool ImGui_ImplGLUT_Init(); -IMGUI_IMPL_API void ImGui_ImplGLUT_InstallFuncs(); -IMGUI_IMPL_API void ImGui_ImplGLUT_Shutdown(); -IMGUI_IMPL_API void ImGui_ImplGLUT_NewFrame(); - -// You can call ImGui_ImplGLUT_InstallFuncs() to get all those functions installed automatically, -// or call them yourself from your own GLUT handlers. We are using the same weird names as GLUT for consistency.. -//------------------------------------ GLUT name ---------------------------------------------- Decent Name --------- -IMGUI_IMPL_API void ImGui_ImplGLUT_ReshapeFunc(int w, int h); // ~ ResizeFunc -IMGUI_IMPL_API void ImGui_ImplGLUT_MotionFunc(int x, int y); // ~ MouseMoveFunc -IMGUI_IMPL_API void ImGui_ImplGLUT_MouseFunc(int button, int state, int x, int y); // ~ MouseButtonFunc -IMGUI_IMPL_API void ImGui_ImplGLUT_MouseWheelFunc(int button, int dir, int x, int y); // ~ MouseWheelFunc -IMGUI_IMPL_API void ImGui_ImplGLUT_KeyboardFunc(unsigned char c, int x, int y); // ~ CharPressedFunc -IMGUI_IMPL_API void ImGui_ImplGLUT_KeyboardUpFunc(unsigned char c, int x, int y); // ~ CharReleasedFunc -IMGUI_IMPL_API void ImGui_ImplGLUT_SpecialFunc(int key, int x, int y); // ~ KeyPressedFunc -IMGUI_IMPL_API void ImGui_ImplGLUT_SpecialUpFunc(int key, int x, int y); // ~ KeyReleasedFunc - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_metal.h b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_metal.h deleted file mode 100644 index d9540fb..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_metal.h +++ /dev/null @@ -1,73 +0,0 @@ -// dear imgui: Renderer Backend for Metal -// This needs to be used along with a Platform Backend (e.g. OSX) - -// Implemented features: -// [X] Renderer: User texture binding. Use 'MTLTexture' as ImTextureID. Read the FAQ about ImTextureID! -// [X] Renderer: Large meshes support (64k+ vertices) with 16-bit indices. -// [X] Renderer: Multi-viewport support (multiple windows). Enable with 'io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable'. - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#include "imgui.h" // IMGUI_IMPL_API -#ifndef IMGUI_DISABLE - -//----------------------------------------------------------------------------- -// ObjC API -//----------------------------------------------------------------------------- - -#ifdef __OBJC__ - -@class MTLRenderPassDescriptor; -@protocol MTLDevice, MTLCommandBuffer, MTLRenderCommandEncoder; - -IMGUI_IMPL_API bool ImGui_ImplMetal_Init(id device); -IMGUI_IMPL_API void ImGui_ImplMetal_Shutdown(); -IMGUI_IMPL_API void ImGui_ImplMetal_NewFrame(MTLRenderPassDescriptor* renderPassDescriptor); -IMGUI_IMPL_API void ImGui_ImplMetal_RenderDrawData(ImDrawData* drawData, - id commandBuffer, - id commandEncoder); - -// Called by Init/NewFrame/Shutdown -IMGUI_IMPL_API bool ImGui_ImplMetal_CreateFontsTexture(id device); -IMGUI_IMPL_API void ImGui_ImplMetal_DestroyFontsTexture(); -IMGUI_IMPL_API bool ImGui_ImplMetal_CreateDeviceObjects(id device); -IMGUI_IMPL_API void ImGui_ImplMetal_DestroyDeviceObjects(); - -#endif - -//----------------------------------------------------------------------------- -// C++ API -//----------------------------------------------------------------------------- - -// Enable Metal C++ binding support with '#define IMGUI_IMPL_METAL_CPP' in your imconfig.h file -// More info about using Metal from C++: https://developer.apple.com/metal/cpp/ - -#ifdef IMGUI_IMPL_METAL_CPP -#include -#ifndef __OBJC__ - -IMGUI_IMPL_API bool ImGui_ImplMetal_Init(MTL::Device* device); -IMGUI_IMPL_API void ImGui_ImplMetal_Shutdown(); -IMGUI_IMPL_API void ImGui_ImplMetal_NewFrame(MTL::RenderPassDescriptor* renderPassDescriptor); -IMGUI_IMPL_API void ImGui_ImplMetal_RenderDrawData(ImDrawData* draw_data, - MTL::CommandBuffer* commandBuffer, - MTL::RenderCommandEncoder* commandEncoder); - -// Called by Init/NewFrame/Shutdown -IMGUI_IMPL_API bool ImGui_ImplMetal_CreateFontsTexture(MTL::Device* device); -IMGUI_IMPL_API void ImGui_ImplMetal_DestroyFontsTexture(); -IMGUI_IMPL_API bool ImGui_ImplMetal_CreateDeviceObjects(MTL::Device* device); -IMGUI_IMPL_API void ImGui_ImplMetal_DestroyDeviceObjects(); - -#endif -#endif - -//----------------------------------------------------------------------------- - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_metal.mm b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_metal.mm deleted file mode 100644 index 55af1b1..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_metal.mm +++ /dev/null @@ -1,750 +0,0 @@ -// dear imgui: Renderer Backend for Metal -// This needs to be used along with a Platform Backend (e.g. OSX) - -// Implemented features: -// [X] Renderer: User texture binding. Use 'MTLTexture' as ImTextureID. Read the FAQ about ImTextureID! -// [X] Renderer: Large meshes support (64k+ vertices) with 16-bit indices. -// [X] Renderer: Multi-viewport support (multiple windows). Enable with 'io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable'. - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -// CHANGELOG -// (minor and older changes stripped away, please see git history for details) -// 2023-XX-XX: Metal: Added support for multiple windows via the ImGuiPlatformIO interface. -// 2022-08-23: Metal: Update deprecated property 'sampleCount'->'rasterSampleCount'. -// 2022-07-05: Metal: Add dispatch synchronization. -// 2022-06-30: Metal: Use __bridge for ARC based systems. -// 2022-06-01: Metal: Fixed null dereference on exit inside command buffer completion handler. -// 2022-04-27: Misc: Store backend data in a per-context struct, allowing to use this backend with multiple contexts. -// 2022-01-03: Metal: Ignore ImDrawCmd where ElemCount == 0 (very rare but can technically be manufactured by user code). -// 2021-12-30: Metal: Added Metal C++ support. Enable with '#define IMGUI_IMPL_METAL_CPP' in your imconfig.h file. -// 2021-08-24: Metal: Fixed a crash when clipping rect larger than framebuffer is submitted. (#4464) -// 2021-05-19: Metal: Replaced direct access to ImDrawCmd::TextureId with a call to ImDrawCmd::GetTexID(). (will become a requirement) -// 2021-02-18: Metal: Change blending equation to preserve alpha in output buffer. -// 2021-01-25: Metal: Fixed texture storage mode when building on Mac Catalyst. -// 2019-05-29: Metal: Added support for large mesh (64K+ vertices), enable ImGuiBackendFlags_RendererHasVtxOffset flag. -// 2019-04-30: Metal: Added support for special ImDrawCallback_ResetRenderState callback to reset render state. -// 2019-02-11: Metal: Projecting clipping rectangles correctly using draw_data->FramebufferScale to allow multi-viewports for retina display. -// 2018-11-30: Misc: Setting up io.BackendRendererName so it can be displayed in the About Window. -// 2018-07-05: Metal: Added new Metal backend implementation. - -#include "imgui.h" -#ifndef IMGUI_DISABLE -#include "imgui_impl_metal.h" -#import -#import - -// Forward Declarations -static void ImGui_ImplMetal_InitPlatformInterface(); -static void ImGui_ImplMetal_ShutdownPlatformInterface(); -static void ImGui_ImplMetal_CreateDeviceObjectsForPlatformWindows(); -static void ImGui_ImplMetal_InvalidateDeviceObjectsForPlatformWindows(); - -#pragma mark - Support classes - -// A wrapper around a MTLBuffer object that knows the last time it was reused -@interface MetalBuffer : NSObject -@property (nonatomic, strong) id buffer; -@property (nonatomic, assign) double lastReuseTime; -- (instancetype)initWithBuffer:(id)buffer; -@end - -// An object that encapsulates the data necessary to uniquely identify a -// render pipeline state. These are used as cache keys. -@interface FramebufferDescriptor : NSObject -@property (nonatomic, assign) unsigned long sampleCount; -@property (nonatomic, assign) MTLPixelFormat colorPixelFormat; -@property (nonatomic, assign) MTLPixelFormat depthPixelFormat; -@property (nonatomic, assign) MTLPixelFormat stencilPixelFormat; -- (instancetype)initWithRenderPassDescriptor:(MTLRenderPassDescriptor*)renderPassDescriptor; -@end - -// A singleton that stores long-lived objects that are needed by the Metal -// renderer backend. Stores the render pipeline state cache and the default -// font texture, and manages the reusable buffer cache. -@interface MetalContext : NSObject -@property (nonatomic, strong) id device; -@property (nonatomic, strong) id depthStencilState; -@property (nonatomic, strong) FramebufferDescriptor* framebufferDescriptor; // framebuffer descriptor for current frame; transient -@property (nonatomic, strong) NSMutableDictionary* renderPipelineStateCache; // pipeline cache; keyed on framebuffer descriptors -@property (nonatomic, strong, nullable) id fontTexture; -@property (nonatomic, strong) NSMutableArray* bufferCache; -@property (nonatomic, assign) double lastBufferCachePurge; -- (MetalBuffer*)dequeueReusableBufferOfLength:(NSUInteger)length device:(id)device; -- (id)renderPipelineStateForFramebufferDescriptor:(FramebufferDescriptor*)descriptor device:(id)device; -@end - -struct ImGui_ImplMetal_Data -{ - MetalContext* SharedMetalContext; - - ImGui_ImplMetal_Data() { memset(this, 0, sizeof(*this)); } -}; - -static ImGui_ImplMetal_Data* ImGui_ImplMetal_CreateBackendData() { return IM_NEW(ImGui_ImplMetal_Data)(); } -static ImGui_ImplMetal_Data* ImGui_ImplMetal_GetBackendData() { return ImGui::GetCurrentContext() ? (ImGui_ImplMetal_Data*)ImGui::GetIO().BackendRendererUserData : nullptr; } -static void ImGui_ImplMetal_DestroyBackendData(){ IM_DELETE(ImGui_ImplMetal_GetBackendData()); } - -static inline CFTimeInterval GetMachAbsoluteTimeInSeconds() { return (CFTimeInterval)(double)(clock_gettime_nsec_np(CLOCK_UPTIME_RAW) / 1e9); } - -#ifdef IMGUI_IMPL_METAL_CPP - -#pragma mark - Dear ImGui Metal C++ Backend API - -bool ImGui_ImplMetal_Init(MTL::Device* device) -{ - return ImGui_ImplMetal_Init((__bridge id)(device)); -} - -void ImGui_ImplMetal_NewFrame(MTL::RenderPassDescriptor* renderPassDescriptor) -{ - ImGui_ImplMetal_NewFrame((__bridge MTLRenderPassDescriptor*)(renderPassDescriptor)); -} - -void ImGui_ImplMetal_RenderDrawData(ImDrawData* draw_data, - MTL::CommandBuffer* commandBuffer, - MTL::RenderCommandEncoder* commandEncoder) -{ - ImGui_ImplMetal_RenderDrawData(draw_data, - (__bridge id)(commandBuffer), - (__bridge id)(commandEncoder)); - -} - -bool ImGui_ImplMetal_CreateFontsTexture(MTL::Device* device) -{ - return ImGui_ImplMetal_CreateFontsTexture((__bridge id)(device)); -} - -bool ImGui_ImplMetal_CreateDeviceObjects(MTL::Device* device) -{ - return ImGui_ImplMetal_CreateDeviceObjects((__bridge id)(device)); -} - -#endif // #ifdef IMGUI_IMPL_METAL_CPP - -#pragma mark - Dear ImGui Metal Backend API - -bool ImGui_ImplMetal_Init(id device) -{ - ImGui_ImplMetal_Data* bd = ImGui_ImplMetal_CreateBackendData(); - ImGuiIO& io = ImGui::GetIO(); - io.BackendRendererUserData = (void*)bd; - io.BackendRendererName = "imgui_impl_metal"; - io.BackendFlags |= ImGuiBackendFlags_RendererHasVtxOffset; // We can honor the ImDrawCmd::VtxOffset field, allowing for large meshes. - io.BackendFlags |= ImGuiBackendFlags_RendererHasViewports; // We can create multi-viewports on the Renderer side (optional) - - bd->SharedMetalContext = [[MetalContext alloc] init]; - bd->SharedMetalContext.device = device; - - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - ImGui_ImplMetal_InitPlatformInterface(); - - return true; -} - -void ImGui_ImplMetal_Shutdown() -{ - ImGui_ImplMetal_Data* bd = ImGui_ImplMetal_GetBackendData(); - IM_ASSERT(bd != nullptr && "No renderer backend to shutdown, or already shutdown?"); - ImGui_ImplMetal_ShutdownPlatformInterface(); - ImGui_ImplMetal_DestroyDeviceObjects(); - ImGui_ImplMetal_DestroyBackendData(); - - ImGuiIO& io = ImGui::GetIO(); - io.BackendRendererName = nullptr; - io.BackendRendererUserData = nullptr; - io.BackendFlags &= ~(ImGuiBackendFlags_RendererHasVtxOffset | ImGuiBackendFlags_RendererHasViewports); -} - -void ImGui_ImplMetal_NewFrame(MTLRenderPassDescriptor* renderPassDescriptor) -{ - ImGui_ImplMetal_Data* bd = ImGui_ImplMetal_GetBackendData(); - IM_ASSERT(bd->SharedMetalContext != nil && "No Metal context. Did you call ImGui_ImplMetal_Init() ?"); - bd->SharedMetalContext.framebufferDescriptor = [[FramebufferDescriptor alloc] initWithRenderPassDescriptor:renderPassDescriptor]; - - if (bd->SharedMetalContext.depthStencilState == nil) - ImGui_ImplMetal_CreateDeviceObjects(bd->SharedMetalContext.device); -} - -static void ImGui_ImplMetal_SetupRenderState(ImDrawData* drawData, id commandBuffer, - id commandEncoder, id renderPipelineState, - MetalBuffer* vertexBuffer, size_t vertexBufferOffset) -{ - IM_UNUSED(commandBuffer); - ImGui_ImplMetal_Data* bd = ImGui_ImplMetal_GetBackendData(); - [commandEncoder setCullMode:MTLCullModeNone]; - [commandEncoder setDepthStencilState:bd->SharedMetalContext.depthStencilState]; - - // Setup viewport, orthographic projection matrix - // Our visible imgui space lies from draw_data->DisplayPos (top left) to - // draw_data->DisplayPos+data_data->DisplaySize (bottom right). DisplayMin is typically (0,0) for single viewport apps. - MTLViewport viewport = - { - .originX = 0.0, - .originY = 0.0, - .width = (double)(drawData->DisplaySize.x * drawData->FramebufferScale.x), - .height = (double)(drawData->DisplaySize.y * drawData->FramebufferScale.y), - .znear = 0.0, - .zfar = 1.0 - }; - [commandEncoder setViewport:viewport]; - - float L = drawData->DisplayPos.x; - float R = drawData->DisplayPos.x + drawData->DisplaySize.x; - float T = drawData->DisplayPos.y; - float B = drawData->DisplayPos.y + drawData->DisplaySize.y; - float N = (float)viewport.znear; - float F = (float)viewport.zfar; - const float ortho_projection[4][4] = - { - { 2.0f/(R-L), 0.0f, 0.0f, 0.0f }, - { 0.0f, 2.0f/(T-B), 0.0f, 0.0f }, - { 0.0f, 0.0f, 1/(F-N), 0.0f }, - { (R+L)/(L-R), (T+B)/(B-T), N/(F-N), 1.0f }, - }; - [commandEncoder setVertexBytes:&ortho_projection length:sizeof(ortho_projection) atIndex:1]; - - [commandEncoder setRenderPipelineState:renderPipelineState]; - - [commandEncoder setVertexBuffer:vertexBuffer.buffer offset:0 atIndex:0]; - [commandEncoder setVertexBufferOffset:vertexBufferOffset atIndex:0]; -} - -// Metal Render function. -void ImGui_ImplMetal_RenderDrawData(ImDrawData* drawData, id commandBuffer, id commandEncoder) -{ - ImGui_ImplMetal_Data* bd = ImGui_ImplMetal_GetBackendData(); - MetalContext* ctx = bd->SharedMetalContext; - - // Avoid rendering when minimized, scale coordinates for retina displays (screen coordinates != framebuffer coordinates) - int fb_width = (int)(drawData->DisplaySize.x * drawData->FramebufferScale.x); - int fb_height = (int)(drawData->DisplaySize.y * drawData->FramebufferScale.y); - if (fb_width <= 0 || fb_height <= 0 || drawData->CmdListsCount == 0) - return; - - // Try to retrieve a render pipeline state that is compatible with the framebuffer config for this frame - // The hit rate for this cache should be very near 100%. - id renderPipelineState = ctx.renderPipelineStateCache[ctx.framebufferDescriptor]; - if (renderPipelineState == nil) - { - // No luck; make a new render pipeline state - renderPipelineState = [ctx renderPipelineStateForFramebufferDescriptor:ctx.framebufferDescriptor device:commandBuffer.device]; - - // Cache render pipeline state for later reuse - ctx.renderPipelineStateCache[ctx.framebufferDescriptor] = renderPipelineState; - } - - size_t vertexBufferLength = (size_t)drawData->TotalVtxCount * sizeof(ImDrawVert); - size_t indexBufferLength = (size_t)drawData->TotalIdxCount * sizeof(ImDrawIdx); - MetalBuffer* vertexBuffer = [ctx dequeueReusableBufferOfLength:vertexBufferLength device:commandBuffer.device]; - MetalBuffer* indexBuffer = [ctx dequeueReusableBufferOfLength:indexBufferLength device:commandBuffer.device]; - - ImGui_ImplMetal_SetupRenderState(drawData, commandBuffer, commandEncoder, renderPipelineState, vertexBuffer, 0); - - // Will project scissor/clipping rectangles into framebuffer space - ImVec2 clip_off = drawData->DisplayPos; // (0,0) unless using multi-viewports - ImVec2 clip_scale = drawData->FramebufferScale; // (1,1) unless using retina display which are often (2,2) - - // Render command lists - size_t vertexBufferOffset = 0; - size_t indexBufferOffset = 0; - for (int n = 0; n < drawData->CmdListsCount; n++) - { - const ImDrawList* cmd_list = drawData->CmdLists[n]; - - memcpy((char*)vertexBuffer.buffer.contents + vertexBufferOffset, cmd_list->VtxBuffer.Data, (size_t)cmd_list->VtxBuffer.Size * sizeof(ImDrawVert)); - memcpy((char*)indexBuffer.buffer.contents + indexBufferOffset, cmd_list->IdxBuffer.Data, (size_t)cmd_list->IdxBuffer.Size * sizeof(ImDrawIdx)); - - for (int cmd_i = 0; cmd_i < cmd_list->CmdBuffer.Size; cmd_i++) - { - const ImDrawCmd* pcmd = &cmd_list->CmdBuffer[cmd_i]; - if (pcmd->UserCallback) - { - // User callback, registered via ImDrawList::AddCallback() - // (ImDrawCallback_ResetRenderState is a special callback value used by the user to request the renderer to reset render state.) - if (pcmd->UserCallback == ImDrawCallback_ResetRenderState) - ImGui_ImplMetal_SetupRenderState(drawData, commandBuffer, commandEncoder, renderPipelineState, vertexBuffer, vertexBufferOffset); - else - pcmd->UserCallback(cmd_list, pcmd); - } - else - { - // Project scissor/clipping rectangles into framebuffer space - ImVec2 clip_min((pcmd->ClipRect.x - clip_off.x) * clip_scale.x, (pcmd->ClipRect.y - clip_off.y) * clip_scale.y); - ImVec2 clip_max((pcmd->ClipRect.z - clip_off.x) * clip_scale.x, (pcmd->ClipRect.w - clip_off.y) * clip_scale.y); - - // Clamp to viewport as setScissorRect() won't accept values that are off bounds - if (clip_min.x < 0.0f) { clip_min.x = 0.0f; } - if (clip_min.y < 0.0f) { clip_min.y = 0.0f; } - if (clip_max.x > fb_width) { clip_max.x = (float)fb_width; } - if (clip_max.y > fb_height) { clip_max.y = (float)fb_height; } - if (clip_max.x <= clip_min.x || clip_max.y <= clip_min.y) - continue; - if (pcmd->ElemCount == 0) // drawIndexedPrimitives() validation doesn't accept this - continue; - - // Apply scissor/clipping rectangle - MTLScissorRect scissorRect = - { - .x = NSUInteger(clip_min.x), - .y = NSUInteger(clip_min.y), - .width = NSUInteger(clip_max.x - clip_min.x), - .height = NSUInteger(clip_max.y - clip_min.y) - }; - [commandEncoder setScissorRect:scissorRect]; - - // Bind texture, Draw - if (ImTextureID tex_id = pcmd->GetTexID()) - [commandEncoder setFragmentTexture:(__bridge id)(tex_id) atIndex:0]; - - [commandEncoder setVertexBufferOffset:(vertexBufferOffset + pcmd->VtxOffset * sizeof(ImDrawVert)) atIndex:0]; - [commandEncoder drawIndexedPrimitives:MTLPrimitiveTypeTriangle - indexCount:pcmd->ElemCount - indexType:sizeof(ImDrawIdx) == 2 ? MTLIndexTypeUInt16 : MTLIndexTypeUInt32 - indexBuffer:indexBuffer.buffer - indexBufferOffset:indexBufferOffset + pcmd->IdxOffset * sizeof(ImDrawIdx)]; - } - } - - vertexBufferOffset += (size_t)cmd_list->VtxBuffer.Size * sizeof(ImDrawVert); - indexBufferOffset += (size_t)cmd_list->IdxBuffer.Size * sizeof(ImDrawIdx); - } - - [commandBuffer addCompletedHandler:^(id) - { - dispatch_async(dispatch_get_main_queue(), ^{ - ImGui_ImplMetal_Data* bd = ImGui_ImplMetal_GetBackendData(); - if (bd != nullptr) - { - @synchronized(bd->SharedMetalContext.bufferCache) - { - [bd->SharedMetalContext.bufferCache addObject:vertexBuffer]; - [bd->SharedMetalContext.bufferCache addObject:indexBuffer]; - } - } - }); - }]; -} - -bool ImGui_ImplMetal_CreateFontsTexture(id device) -{ - ImGui_ImplMetal_Data* bd = ImGui_ImplMetal_GetBackendData(); - ImGuiIO& io = ImGui::GetIO(); - - // We are retrieving and uploading the font atlas as a 4-channels RGBA texture here. - // In theory we could call GetTexDataAsAlpha8() and upload a 1-channel texture to save on memory access bandwidth. - // However, using a shader designed for 1-channel texture would make it less obvious to use the ImTextureID facility to render users own textures. - // You can make that change in your implementation. - unsigned char* pixels; - int width, height; - io.Fonts->GetTexDataAsRGBA32(&pixels, &width, &height); - MTLTextureDescriptor* textureDescriptor = [MTLTextureDescriptor texture2DDescriptorWithPixelFormat:MTLPixelFormatRGBA8Unorm - width:(NSUInteger)width - height:(NSUInteger)height - mipmapped:NO]; - textureDescriptor.usage = MTLTextureUsageShaderRead; -#if TARGET_OS_OSX || TARGET_OS_MACCATALYST - textureDescriptor.storageMode = MTLStorageModeManaged; -#else - textureDescriptor.storageMode = MTLStorageModeShared; -#endif - id texture = [device newTextureWithDescriptor:textureDescriptor]; - [texture replaceRegion:MTLRegionMake2D(0, 0, (NSUInteger)width, (NSUInteger)height) mipmapLevel:0 withBytes:pixels bytesPerRow:(NSUInteger)width * 4]; - bd->SharedMetalContext.fontTexture = texture; - io.Fonts->SetTexID((__bridge void*)bd->SharedMetalContext.fontTexture); // ImTextureID == void* - - return (bd->SharedMetalContext.fontTexture != nil); -} - -void ImGui_ImplMetal_DestroyFontsTexture() -{ - ImGui_ImplMetal_Data* bd = ImGui_ImplMetal_GetBackendData(); - ImGuiIO& io = ImGui::GetIO(); - bd->SharedMetalContext.fontTexture = nil; - io.Fonts->SetTexID(0); -} - -bool ImGui_ImplMetal_CreateDeviceObjects(id device) -{ - ImGui_ImplMetal_Data* bd = ImGui_ImplMetal_GetBackendData(); - MTLDepthStencilDescriptor* depthStencilDescriptor = [[MTLDepthStencilDescriptor alloc] init]; - depthStencilDescriptor.depthWriteEnabled = NO; - depthStencilDescriptor.depthCompareFunction = MTLCompareFunctionAlways; - bd->SharedMetalContext.depthStencilState = [device newDepthStencilStateWithDescriptor:depthStencilDescriptor]; - ImGui_ImplMetal_CreateDeviceObjectsForPlatformWindows(); - ImGui_ImplMetal_CreateFontsTexture(device); - - return true; -} - -void ImGui_ImplMetal_DestroyDeviceObjects() -{ - ImGui_ImplMetal_Data* bd = ImGui_ImplMetal_GetBackendData(); - ImGui_ImplMetal_DestroyFontsTexture(); - ImGui_ImplMetal_InvalidateDeviceObjectsForPlatformWindows(); - [bd->SharedMetalContext.renderPipelineStateCache removeAllObjects]; -} - -#pragma mark - Multi-viewport support - -#import - -#if TARGET_OS_OSX -#import -#endif - -//-------------------------------------------------------------------------------------------------------- -// MULTI-VIEWPORT / PLATFORM INTERFACE SUPPORT -// This is an _advanced_ and _optional_ feature, allowing the back-end to create and handle multiple viewports simultaneously. -// If you are new to dear imgui or creating a new binding for dear imgui, it is recommended that you completely ignore this section first.. -//-------------------------------------------------------------------------------------------------------- - -struct ImGuiViewportDataMetal -{ - CAMetalLayer* MetalLayer; - id CommandQueue; - MTLRenderPassDescriptor* RenderPassDescriptor; - void* Handle = nullptr; - bool FirstFrame = true; -}; - -static void ImGui_ImplMetal_CreateWindow(ImGuiViewport* viewport) -{ - ImGui_ImplMetal_Data* bd = ImGui_ImplMetal_GetBackendData(); - ImGuiViewportDataMetal* data = IM_NEW(ImGuiViewportDataMetal)(); - viewport->RendererUserData = data; - - // PlatformHandleRaw should always be a NSWindow*, whereas PlatformHandle might be a higher-level handle (e.g. GLFWWindow*, SDL_Window*). - // Some back-ends will leave PlatformHandleRaw == 0, in which case we assume PlatformHandle will contain the NSWindow*. - void* handle = viewport->PlatformHandleRaw ? viewport->PlatformHandleRaw : viewport->PlatformHandle; - IM_ASSERT(handle != nullptr); - - id device = bd->SharedMetalContext.device; - CAMetalLayer* layer = [CAMetalLayer layer]; - layer.device = device; - layer.framebufferOnly = YES; - layer.pixelFormat = bd->SharedMetalContext.framebufferDescriptor.colorPixelFormat; -#if TARGET_OS_OSX - NSWindow* window = (__bridge NSWindow*)handle; - NSView* view = window.contentView; - view.layer = layer; - view.wantsLayer = YES; -#endif - data->MetalLayer = layer; - data->CommandQueue = [device newCommandQueue]; - data->RenderPassDescriptor = [[MTLRenderPassDescriptor alloc] init]; - data->Handle = handle; -} - -static void ImGui_ImplMetal_DestroyWindow(ImGuiViewport* viewport) -{ - // The main viewport (owned by the application) will always have RendererUserData == 0 since we didn't create the data for it. - if (ImGuiViewportDataMetal* data = (ImGuiViewportDataMetal*)viewport->RendererUserData) - IM_DELETE(data); - viewport->RendererUserData = nullptr; -} - -inline static CGSize MakeScaledSize(CGSize size, CGFloat scale) -{ - return CGSizeMake(size.width * scale, size.height * scale); -} - -static void ImGui_ImplMetal_SetWindowSize(ImGuiViewport* viewport, ImVec2 size) -{ - ImGuiViewportDataMetal* data = (ImGuiViewportDataMetal*)viewport->RendererUserData; - data->MetalLayer.drawableSize = MakeScaledSize(CGSizeMake(size.x, size.y), viewport->DpiScale); -} - -static void ImGui_ImplMetal_RenderWindow(ImGuiViewport* viewport, void*) -{ - ImGuiViewportDataMetal* data = (ImGuiViewportDataMetal*)viewport->RendererUserData; - -#if TARGET_OS_OSX - void* handle = viewport->PlatformHandleRaw ? viewport->PlatformHandleRaw : viewport->PlatformHandle; - NSWindow* window = (__bridge NSWindow*)handle; - - // Always render the first frame, regardless of occlusionState, to avoid an initial flicker - if ((window.occlusionState & NSWindowOcclusionStateVisible) == 0 && !data->FirstFrame) - { - // Do not render windows which are completely occluded. Calling -[CAMetalLayer nextDrawable] will hang for - // approximately 1 second if the Metal layer is completely occluded. - return; - } - data->FirstFrame = false; - - viewport->DpiScale = (float)window.backingScaleFactor; - if (data->MetalLayer.contentsScale != viewport->DpiScale) - { - data->MetalLayer.contentsScale = viewport->DpiScale; - data->MetalLayer.drawableSize = MakeScaledSize(window.frame.size, viewport->DpiScale); - } - viewport->DrawData->FramebufferScale = ImVec2(viewport->DpiScale, viewport->DpiScale); -#endif - - id drawable = [data->MetalLayer nextDrawable]; - if (drawable == nil) - return; - - MTLRenderPassDescriptor* renderPassDescriptor = data->RenderPassDescriptor; - renderPassDescriptor.colorAttachments[0].texture = drawable.texture; - renderPassDescriptor.colorAttachments[0].clearColor = MTLClearColorMake(0, 0, 0, 0); - if ((viewport->Flags & ImGuiViewportFlags_NoRendererClear) == 0) - renderPassDescriptor.colorAttachments[0].loadAction = MTLLoadActionClear; - - id commandBuffer = [data->CommandQueue commandBuffer]; - id renderEncoder = [commandBuffer renderCommandEncoderWithDescriptor:renderPassDescriptor]; - ImGui_ImplMetal_RenderDrawData(viewport->DrawData, commandBuffer, renderEncoder); - [renderEncoder endEncoding]; - - [commandBuffer presentDrawable:drawable]; - [commandBuffer commit]; -} - -static void ImGui_ImplMetal_InitPlatformInterface() -{ - ImGuiPlatformIO& platform_io = ImGui::GetPlatformIO(); - platform_io.Renderer_CreateWindow = ImGui_ImplMetal_CreateWindow; - platform_io.Renderer_DestroyWindow = ImGui_ImplMetal_DestroyWindow; - platform_io.Renderer_SetWindowSize = ImGui_ImplMetal_SetWindowSize; - platform_io.Renderer_RenderWindow = ImGui_ImplMetal_RenderWindow; -} - -static void ImGui_ImplMetal_ShutdownPlatformInterface() -{ - ImGui::DestroyPlatformWindows(); -} - -static void ImGui_ImplMetal_CreateDeviceObjectsForPlatformWindows() -{ - ImGuiPlatformIO& platform_io = ImGui::GetPlatformIO(); - for (int i = 1; i < platform_io.Viewports.Size; i++) - if (!platform_io.Viewports[i]->RendererUserData) - ImGui_ImplMetal_CreateWindow(platform_io.Viewports[i]); -} - -static void ImGui_ImplMetal_InvalidateDeviceObjectsForPlatformWindows() -{ - ImGuiPlatformIO& platform_io = ImGui::GetPlatformIO(); - for (int i = 1; i < platform_io.Viewports.Size; i++) - if (platform_io.Viewports[i]->RendererUserData) - ImGui_ImplMetal_DestroyWindow(platform_io.Viewports[i]); -} - -#pragma mark - MetalBuffer implementation - -@implementation MetalBuffer -- (instancetype)initWithBuffer:(id)buffer -{ - if ((self = [super init])) - { - _buffer = buffer; - _lastReuseTime = GetMachAbsoluteTimeInSeconds(); - } - return self; -} -@end - -#pragma mark - FramebufferDescriptor implementation - -@implementation FramebufferDescriptor -- (instancetype)initWithRenderPassDescriptor:(MTLRenderPassDescriptor*)renderPassDescriptor -{ - if ((self = [super init])) - { - _sampleCount = renderPassDescriptor.colorAttachments[0].texture.sampleCount; - _colorPixelFormat = renderPassDescriptor.colorAttachments[0].texture.pixelFormat; - _depthPixelFormat = renderPassDescriptor.depthAttachment.texture.pixelFormat; - _stencilPixelFormat = renderPassDescriptor.stencilAttachment.texture.pixelFormat; - } - return self; -} - -- (nonnull id)copyWithZone:(nullable NSZone*)zone -{ - FramebufferDescriptor* copy = [[FramebufferDescriptor allocWithZone:zone] init]; - copy.sampleCount = self.sampleCount; - copy.colorPixelFormat = self.colorPixelFormat; - copy.depthPixelFormat = self.depthPixelFormat; - copy.stencilPixelFormat = self.stencilPixelFormat; - return copy; -} - -- (NSUInteger)hash -{ - NSUInteger sc = _sampleCount & 0x3; - NSUInteger cf = _colorPixelFormat & 0x3FF; - NSUInteger df = _depthPixelFormat & 0x3FF; - NSUInteger sf = _stencilPixelFormat & 0x3FF; - NSUInteger hash = (sf << 22) | (df << 12) | (cf << 2) | sc; - return hash; -} - -- (BOOL)isEqual:(id)object -{ - FramebufferDescriptor* other = object; - if (![other isKindOfClass:[FramebufferDescriptor class]]) - return NO; - return other.sampleCount == self.sampleCount && - other.colorPixelFormat == self.colorPixelFormat && - other.depthPixelFormat == self.depthPixelFormat && - other.stencilPixelFormat == self.stencilPixelFormat; -} - -@end - -#pragma mark - MetalContext implementation - -@implementation MetalContext -- (instancetype)init -{ - if ((self = [super init])) - { - self.renderPipelineStateCache = [NSMutableDictionary dictionary]; - self.bufferCache = [NSMutableArray array]; - _lastBufferCachePurge = GetMachAbsoluteTimeInSeconds(); - } - return self; -} - -- (MetalBuffer*)dequeueReusableBufferOfLength:(NSUInteger)length device:(id)device -{ - uint64_t now = GetMachAbsoluteTimeInSeconds(); - - @synchronized(self.bufferCache) - { - // Purge old buffers that haven't been useful for a while - if (now - self.lastBufferCachePurge > 1.0) - { - NSMutableArray* survivors = [NSMutableArray array]; - for (MetalBuffer* candidate in self.bufferCache) - if (candidate.lastReuseTime > self.lastBufferCachePurge) - [survivors addObject:candidate]; - self.bufferCache = [survivors mutableCopy]; - self.lastBufferCachePurge = now; - } - - // See if we have a buffer we can reuse - MetalBuffer* bestCandidate = nil; - for (MetalBuffer* candidate in self.bufferCache) - if (candidate.buffer.length >= length && (bestCandidate == nil || bestCandidate.lastReuseTime > candidate.lastReuseTime)) - bestCandidate = candidate; - - if (bestCandidate != nil) - { - [self.bufferCache removeObject:bestCandidate]; - bestCandidate.lastReuseTime = now; - return bestCandidate; - } - } - - // No luck; make a new buffer - id backing = [device newBufferWithLength:length options:MTLResourceStorageModeShared]; - return [[MetalBuffer alloc] initWithBuffer:backing]; -} - -// Bilinear sampling is required by default. Set 'io.Fonts->Flags |= ImFontAtlasFlags_NoBakedLines' or 'style.AntiAliasedLinesUseTex = false' to allow point/nearest sampling. -- (id)renderPipelineStateForFramebufferDescriptor:(FramebufferDescriptor*)descriptor device:(id)device -{ - NSError* error = nil; - - NSString* shaderSource = @"" - "#include \n" - "using namespace metal;\n" - "\n" - "struct Uniforms {\n" - " float4x4 projectionMatrix;\n" - "};\n" - "\n" - "struct VertexIn {\n" - " float2 position [[attribute(0)]];\n" - " float2 texCoords [[attribute(1)]];\n" - " uchar4 color [[attribute(2)]];\n" - "};\n" - "\n" - "struct VertexOut {\n" - " float4 position [[position]];\n" - " float2 texCoords;\n" - " float4 color;\n" - "};\n" - "\n" - "vertex VertexOut vertex_main(VertexIn in [[stage_in]],\n" - " constant Uniforms &uniforms [[buffer(1)]]) {\n" - " VertexOut out;\n" - " out.position = uniforms.projectionMatrix * float4(in.position, 0, 1);\n" - " out.texCoords = in.texCoords;\n" - " out.color = float4(in.color) / float4(255.0);\n" - " return out;\n" - "}\n" - "\n" - "fragment half4 fragment_main(VertexOut in [[stage_in]],\n" - " texture2d texture [[texture(0)]]) {\n" - " constexpr sampler linearSampler(coord::normalized, min_filter::linear, mag_filter::linear, mip_filter::linear);\n" - " half4 texColor = texture.sample(linearSampler, in.texCoords);\n" - " return half4(in.color) * texColor;\n" - "}\n"; - - id library = [device newLibraryWithSource:shaderSource options:nil error:&error]; - if (library == nil) - { - NSLog(@"Error: failed to create Metal library: %@", error); - return nil; - } - - id vertexFunction = [library newFunctionWithName:@"vertex_main"]; - id fragmentFunction = [library newFunctionWithName:@"fragment_main"]; - - if (vertexFunction == nil || fragmentFunction == nil) - { - NSLog(@"Error: failed to find Metal shader functions in library: %@", error); - return nil; - } - - MTLVertexDescriptor* vertexDescriptor = [MTLVertexDescriptor vertexDescriptor]; - vertexDescriptor.attributes[0].offset = IM_OFFSETOF(ImDrawVert, pos); - vertexDescriptor.attributes[0].format = MTLVertexFormatFloat2; // position - vertexDescriptor.attributes[0].bufferIndex = 0; - vertexDescriptor.attributes[1].offset = IM_OFFSETOF(ImDrawVert, uv); - vertexDescriptor.attributes[1].format = MTLVertexFormatFloat2; // texCoords - vertexDescriptor.attributes[1].bufferIndex = 0; - vertexDescriptor.attributes[2].offset = IM_OFFSETOF(ImDrawVert, col); - vertexDescriptor.attributes[2].format = MTLVertexFormatUChar4; // color - vertexDescriptor.attributes[2].bufferIndex = 0; - vertexDescriptor.layouts[0].stepRate = 1; - vertexDescriptor.layouts[0].stepFunction = MTLVertexStepFunctionPerVertex; - vertexDescriptor.layouts[0].stride = sizeof(ImDrawVert); - - MTLRenderPipelineDescriptor* pipelineDescriptor = [[MTLRenderPipelineDescriptor alloc] init]; - pipelineDescriptor.vertexFunction = vertexFunction; - pipelineDescriptor.fragmentFunction = fragmentFunction; - pipelineDescriptor.vertexDescriptor = vertexDescriptor; - pipelineDescriptor.rasterSampleCount = self.framebufferDescriptor.sampleCount; - pipelineDescriptor.colorAttachments[0].pixelFormat = self.framebufferDescriptor.colorPixelFormat; - pipelineDescriptor.colorAttachments[0].blendingEnabled = YES; - pipelineDescriptor.colorAttachments[0].rgbBlendOperation = MTLBlendOperationAdd; - pipelineDescriptor.colorAttachments[0].sourceRGBBlendFactor = MTLBlendFactorSourceAlpha; - pipelineDescriptor.colorAttachments[0].destinationRGBBlendFactor = MTLBlendFactorOneMinusSourceAlpha; - pipelineDescriptor.colorAttachments[0].alphaBlendOperation = MTLBlendOperationAdd; - pipelineDescriptor.colorAttachments[0].sourceAlphaBlendFactor = MTLBlendFactorOne; - pipelineDescriptor.colorAttachments[0].destinationAlphaBlendFactor = MTLBlendFactorOneMinusSourceAlpha; - pipelineDescriptor.depthAttachmentPixelFormat = self.framebufferDescriptor.depthPixelFormat; - pipelineDescriptor.stencilAttachmentPixelFormat = self.framebufferDescriptor.stencilPixelFormat; - - id renderPipelineState = [device newRenderPipelineStateWithDescriptor:pipelineDescriptor error:&error]; - if (error != nil) - NSLog(@"Error: failed to create Metal pipeline state: %@", error); - - return renderPipelineState; -} - -@end - -//----------------------------------------------------------------------------- - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_opengl2.cpp b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_opengl2.cpp deleted file mode 100644 index 8defd84..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_opengl2.cpp +++ /dev/null @@ -1,343 +0,0 @@ -// dear imgui: Renderer Backend for OpenGL2 (legacy OpenGL, fixed pipeline) -// This needs to be used along with a Platform Backend (e.g. GLFW, SDL, Win32, custom..) - -// Implemented features: -// [X] Renderer: User texture binding. Use 'GLuint' OpenGL texture identifier as void*/ImTextureID. Read the FAQ about ImTextureID! -// [X] Renderer: Multi-viewport support (multiple windows). Enable with 'io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable'. - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -// **DO NOT USE THIS CODE IF YOUR CODE/ENGINE IS USING MODERN OPENGL (SHADERS, VBO, VAO, etc.)** -// **Prefer using the code in imgui_impl_opengl3.cpp** -// This code is mostly provided as a reference to learn how ImGui integration works, because it is shorter to read. -// If your code is using GL3+ context or any semi modern OpenGL calls, using this is likely to make everything more -// complicated, will require your code to reset every single OpenGL attributes to their initial state, and might -// confuse your GPU driver. -// The GL2 code is unable to reset attributes or even call e.g. "glUseProgram(0)" because they don't exist in that API. - -// CHANGELOG -// (minor and older changes stripped away, please see git history for details) -// 2023-XX-XX: Platform: Added support for multiple windows via the ImGuiPlatformIO interface. -// 2022-10-11: Using 'nullptr' instead of 'NULL' as per our switch to C++11. -// 2021-12-08: OpenGL: Fixed mishandling of the the ImDrawCmd::IdxOffset field! This is an old bug but it never had an effect until some internal rendering changes in 1.86. -// 2021-06-29: Reorganized backend to pull data from a single structure to facilitate usage with multiple-contexts (all g_XXXX access changed to bd->XXXX). -// 2021-05-19: OpenGL: Replaced direct access to ImDrawCmd::TextureId with a call to ImDrawCmd::GetTexID(). (will become a requirement) -// 2021-01-03: OpenGL: Backup, setup and restore GL_SHADE_MODEL state, disable GL_STENCIL_TEST and disable GL_NORMAL_ARRAY client state to increase compatibility with legacy OpenGL applications. -// 2020-01-23: OpenGL: Backup, setup and restore GL_TEXTURE_ENV to increase compatibility with legacy OpenGL applications. -// 2019-04-30: OpenGL: Added support for special ImDrawCallback_ResetRenderState callback to reset render state. -// 2019-02-11: OpenGL: Projecting clipping rectangles correctly using draw_data->FramebufferScale to allow multi-viewports for retina display. -// 2018-11-30: Misc: Setting up io.BackendRendererName so it can be displayed in the About Window. -// 2018-08-03: OpenGL: Disabling/restoring GL_LIGHTING and GL_COLOR_MATERIAL to increase compatibility with legacy OpenGL applications. -// 2018-06-08: Misc: Extracted imgui_impl_opengl2.cpp/.h away from the old combined GLFW/SDL+OpenGL2 examples. -// 2018-06-08: OpenGL: Use draw_data->DisplayPos and draw_data->DisplaySize to setup projection matrix and clipping rectangle. -// 2018-02-16: Misc: Obsoleted the io.RenderDrawListsFn callback and exposed ImGui_ImplOpenGL2_RenderDrawData() in the .h file so you can call it yourself. -// 2017-09-01: OpenGL: Save and restore current polygon mode. -// 2016-09-10: OpenGL: Uploading font texture as RGBA32 to increase compatibility with users shaders (not ideal). -// 2016-09-05: OpenGL: Fixed save and restore of current scissor rectangle. - -#include "imgui.h" -#ifndef IMGUI_DISABLE -#include "imgui_impl_opengl2.h" -#include // intptr_t - -// Clang/GCC warnings with -Weverything -#if defined(__clang__) -#pragma clang diagnostic push -#pragma clang diagnostic ignored "-Wunused-macros" // warning: macro is not used -#pragma clang diagnostic ignored "-Wnonportable-system-include-path" -#endif - -// Include OpenGL header (without an OpenGL loader) requires a bit of fiddling -#if defined(_WIN32) && !defined(APIENTRY) -#define APIENTRY __stdcall // It is customary to use APIENTRY for OpenGL function pointer declarations on all platforms. Additionally, the Windows OpenGL header needs APIENTRY. -#endif -#if defined(_WIN32) && !defined(WINGDIAPI) -#define WINGDIAPI __declspec(dllimport) // Some Windows OpenGL headers need this -#endif -#if defined(__APPLE__) -#define GL_SILENCE_DEPRECATION -#include -#else -#include -#endif - -struct ImGui_ImplOpenGL2_Data -{ - GLuint FontTexture; - - ImGui_ImplOpenGL2_Data() { memset((void*)this, 0, sizeof(*this)); } -}; - -// Backend data stored in io.BackendRendererUserData to allow support for multiple Dear ImGui contexts -// It is STRONGLY preferred that you use docking branch with multi-viewports (== single Dear ImGui context + multiple windows) instead of multiple Dear ImGui contexts. -static ImGui_ImplOpenGL2_Data* ImGui_ImplOpenGL2_GetBackendData() -{ - return ImGui::GetCurrentContext() ? (ImGui_ImplOpenGL2_Data*)ImGui::GetIO().BackendRendererUserData : nullptr; -} - -// Forward Declarations -static void ImGui_ImplOpenGL2_InitPlatformInterface(); -static void ImGui_ImplOpenGL2_ShutdownPlatformInterface(); - -// Functions -bool ImGui_ImplOpenGL2_Init() -{ - ImGuiIO& io = ImGui::GetIO(); - IM_ASSERT(io.BackendRendererUserData == nullptr && "Already initialized a renderer backend!"); - - // Setup backend capabilities flags - ImGui_ImplOpenGL2_Data* bd = IM_NEW(ImGui_ImplOpenGL2_Data)(); - io.BackendRendererUserData = (void*)bd; - io.BackendRendererName = "imgui_impl_opengl2"; - io.BackendFlags |= ImGuiBackendFlags_RendererHasViewports; // We can create multi-viewports on the Renderer side (optional) - - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - ImGui_ImplOpenGL2_InitPlatformInterface(); - - return true; -} - -void ImGui_ImplOpenGL2_Shutdown() -{ - ImGui_ImplOpenGL2_Data* bd = ImGui_ImplOpenGL2_GetBackendData(); - IM_ASSERT(bd != nullptr && "No renderer backend to shutdown, or already shutdown?"); - ImGuiIO& io = ImGui::GetIO(); - - ImGui_ImplOpenGL2_ShutdownPlatformInterface(); - ImGui_ImplOpenGL2_DestroyDeviceObjects(); - io.BackendRendererName = nullptr; - io.BackendRendererUserData = nullptr; - io.BackendFlags &= ~ImGuiBackendFlags_RendererHasViewports; - IM_DELETE(bd); -} - -void ImGui_ImplOpenGL2_NewFrame() -{ - ImGui_ImplOpenGL2_Data* bd = ImGui_ImplOpenGL2_GetBackendData(); - IM_ASSERT(bd != nullptr && "Did you call ImGui_ImplOpenGL2_Init()?"); - - if (!bd->FontTexture) - ImGui_ImplOpenGL2_CreateDeviceObjects(); -} - -static void ImGui_ImplOpenGL2_SetupRenderState(ImDrawData* draw_data, int fb_width, int fb_height) -{ - // Setup render state: alpha-blending enabled, no face culling, no depth testing, scissor enabled, vertex/texcoord/color pointers, polygon fill. - glEnable(GL_BLEND); - glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); - //glBlendFuncSeparate(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA, GL_ONE, GL_ONE_MINUS_SRC_ALPHA); // In order to composite our output buffer we need to preserve alpha - glDisable(GL_CULL_FACE); - glDisable(GL_DEPTH_TEST); - glDisable(GL_STENCIL_TEST); - glDisable(GL_LIGHTING); - glDisable(GL_COLOR_MATERIAL); - glEnable(GL_SCISSOR_TEST); - glEnableClientState(GL_VERTEX_ARRAY); - glEnableClientState(GL_TEXTURE_COORD_ARRAY); - glEnableClientState(GL_COLOR_ARRAY); - glDisableClientState(GL_NORMAL_ARRAY); - glEnable(GL_TEXTURE_2D); - glPolygonMode(GL_FRONT_AND_BACK, GL_FILL); - glShadeModel(GL_SMOOTH); - glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); - - // If you are using this code with non-legacy OpenGL header/contexts (which you should not, prefer using imgui_impl_opengl3.cpp!!), - // you may need to backup/reset/restore other state, e.g. for current shader using the commented lines below. - // (DO NOT MODIFY THIS FILE! Add the code in your calling function) - // GLint last_program; - // glGetIntegerv(GL_CURRENT_PROGRAM, &last_program); - // glUseProgram(0); - // ImGui_ImplOpenGL2_RenderDrawData(...); - // glUseProgram(last_program) - // There are potentially many more states you could need to clear/setup that we can't access from default headers. - // e.g. glBindBuffer(GL_ARRAY_BUFFER, 0), glDisable(GL_TEXTURE_CUBE_MAP). - - // Setup viewport, orthographic projection matrix - // Our visible imgui space lies from draw_data->DisplayPos (top left) to draw_data->DisplayPos+data_data->DisplaySize (bottom right). DisplayPos is (0,0) for single viewport apps. - glViewport(0, 0, (GLsizei)fb_width, (GLsizei)fb_height); - glMatrixMode(GL_PROJECTION); - glPushMatrix(); - glLoadIdentity(); - glOrtho(draw_data->DisplayPos.x, draw_data->DisplayPos.x + draw_data->DisplaySize.x, draw_data->DisplayPos.y + draw_data->DisplaySize.y, draw_data->DisplayPos.y, -1.0f, +1.0f); - glMatrixMode(GL_MODELVIEW); - glPushMatrix(); - glLoadIdentity(); -} - -// OpenGL2 Render function. -// Note that this implementation is little overcomplicated because we are saving/setting up/restoring every OpenGL state explicitly. -// This is in order to be able to run within an OpenGL engine that doesn't do so. -void ImGui_ImplOpenGL2_RenderDrawData(ImDrawData* draw_data) -{ - // Avoid rendering when minimized, scale coordinates for retina displays (screen coordinates != framebuffer coordinates) - int fb_width = (int)(draw_data->DisplaySize.x * draw_data->FramebufferScale.x); - int fb_height = (int)(draw_data->DisplaySize.y * draw_data->FramebufferScale.y); - if (fb_width == 0 || fb_height == 0) - return; - - // Backup GL state - GLint last_texture; glGetIntegerv(GL_TEXTURE_BINDING_2D, &last_texture); - GLint last_polygon_mode[2]; glGetIntegerv(GL_POLYGON_MODE, last_polygon_mode); - GLint last_viewport[4]; glGetIntegerv(GL_VIEWPORT, last_viewport); - GLint last_scissor_box[4]; glGetIntegerv(GL_SCISSOR_BOX, last_scissor_box); - GLint last_shade_model; glGetIntegerv(GL_SHADE_MODEL, &last_shade_model); - GLint last_tex_env_mode; glGetTexEnviv(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, &last_tex_env_mode); - glPushAttrib(GL_ENABLE_BIT | GL_COLOR_BUFFER_BIT | GL_TRANSFORM_BIT); - - // Setup desired GL state - ImGui_ImplOpenGL2_SetupRenderState(draw_data, fb_width, fb_height); - - // Will project scissor/clipping rectangles into framebuffer space - ImVec2 clip_off = draw_data->DisplayPos; // (0,0) unless using multi-viewports - ImVec2 clip_scale = draw_data->FramebufferScale; // (1,1) unless using retina display which are often (2,2) - - // Render command lists - for (int n = 0; n < draw_data->CmdListsCount; n++) - { - const ImDrawList* cmd_list = draw_data->CmdLists[n]; - const ImDrawVert* vtx_buffer = cmd_list->VtxBuffer.Data; - const ImDrawIdx* idx_buffer = cmd_list->IdxBuffer.Data; - glVertexPointer(2, GL_FLOAT, sizeof(ImDrawVert), (const GLvoid*)((const char*)vtx_buffer + IM_OFFSETOF(ImDrawVert, pos))); - glTexCoordPointer(2, GL_FLOAT, sizeof(ImDrawVert), (const GLvoid*)((const char*)vtx_buffer + IM_OFFSETOF(ImDrawVert, uv))); - glColorPointer(4, GL_UNSIGNED_BYTE, sizeof(ImDrawVert), (const GLvoid*)((const char*)vtx_buffer + IM_OFFSETOF(ImDrawVert, col))); - - for (int cmd_i = 0; cmd_i < cmd_list->CmdBuffer.Size; cmd_i++) - { - const ImDrawCmd* pcmd = &cmd_list->CmdBuffer[cmd_i]; - if (pcmd->UserCallback) - { - // User callback, registered via ImDrawList::AddCallback() - // (ImDrawCallback_ResetRenderState is a special callback value used by the user to request the renderer to reset render state.) - if (pcmd->UserCallback == ImDrawCallback_ResetRenderState) - ImGui_ImplOpenGL2_SetupRenderState(draw_data, fb_width, fb_height); - else - pcmd->UserCallback(cmd_list, pcmd); - } - else - { - // Project scissor/clipping rectangles into framebuffer space - ImVec2 clip_min((pcmd->ClipRect.x - clip_off.x) * clip_scale.x, (pcmd->ClipRect.y - clip_off.y) * clip_scale.y); - ImVec2 clip_max((pcmd->ClipRect.z - clip_off.x) * clip_scale.x, (pcmd->ClipRect.w - clip_off.y) * clip_scale.y); - if (clip_max.x <= clip_min.x || clip_max.y <= clip_min.y) - continue; - - // Apply scissor/clipping rectangle (Y is inverted in OpenGL) - glScissor((int)clip_min.x, (int)((float)fb_height - clip_max.y), (int)(clip_max.x - clip_min.x), (int)(clip_max.y - clip_min.y)); - - // Bind texture, Draw - glBindTexture(GL_TEXTURE_2D, (GLuint)(intptr_t)pcmd->GetTexID()); - glDrawElements(GL_TRIANGLES, (GLsizei)pcmd->ElemCount, sizeof(ImDrawIdx) == 2 ? GL_UNSIGNED_SHORT : GL_UNSIGNED_INT, idx_buffer + pcmd->IdxOffset); - } - } - } - - // Restore modified GL state - glDisableClientState(GL_COLOR_ARRAY); - glDisableClientState(GL_TEXTURE_COORD_ARRAY); - glDisableClientState(GL_VERTEX_ARRAY); - glBindTexture(GL_TEXTURE_2D, (GLuint)last_texture); - glMatrixMode(GL_MODELVIEW); - glPopMatrix(); - glMatrixMode(GL_PROJECTION); - glPopMatrix(); - glPopAttrib(); - glPolygonMode(GL_FRONT, (GLenum)last_polygon_mode[0]); glPolygonMode(GL_BACK, (GLenum)last_polygon_mode[1]); - glViewport(last_viewport[0], last_viewport[1], (GLsizei)last_viewport[2], (GLsizei)last_viewport[3]); - glScissor(last_scissor_box[0], last_scissor_box[1], (GLsizei)last_scissor_box[2], (GLsizei)last_scissor_box[3]); - glShadeModel(last_shade_model); - glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, last_tex_env_mode); -} - -bool ImGui_ImplOpenGL2_CreateFontsTexture() -{ - // Build texture atlas - ImGuiIO& io = ImGui::GetIO(); - ImGui_ImplOpenGL2_Data* bd = ImGui_ImplOpenGL2_GetBackendData(); - unsigned char* pixels; - int width, height; - io.Fonts->GetTexDataAsRGBA32(&pixels, &width, &height); // Load as RGBA 32-bit (75% of the memory is wasted, but default font is so small) because it is more likely to be compatible with user's existing shaders. If your ImTextureId represent a higher-level concept than just a GL texture id, consider calling GetTexDataAsAlpha8() instead to save on GPU memory. - - // Upload texture to graphics system - // (Bilinear sampling is required by default. Set 'io.Fonts->Flags |= ImFontAtlasFlags_NoBakedLines' or 'style.AntiAliasedLinesUseTex = false' to allow point/nearest sampling) - GLint last_texture; - glGetIntegerv(GL_TEXTURE_BINDING_2D, &last_texture); - glGenTextures(1, &bd->FontTexture); - glBindTexture(GL_TEXTURE_2D, bd->FontTexture); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); - glPixelStorei(GL_UNPACK_ROW_LENGTH, 0); - glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, width, height, 0, GL_RGBA, GL_UNSIGNED_BYTE, pixels); - - // Store our identifier - io.Fonts->SetTexID((ImTextureID)(intptr_t)bd->FontTexture); - - // Restore state - glBindTexture(GL_TEXTURE_2D, last_texture); - - return true; -} - -void ImGui_ImplOpenGL2_DestroyFontsTexture() -{ - ImGuiIO& io = ImGui::GetIO(); - ImGui_ImplOpenGL2_Data* bd = ImGui_ImplOpenGL2_GetBackendData(); - if (bd->FontTexture) - { - glDeleteTextures(1, &bd->FontTexture); - io.Fonts->SetTexID(0); - bd->FontTexture = 0; - } -} - -bool ImGui_ImplOpenGL2_CreateDeviceObjects() -{ - return ImGui_ImplOpenGL2_CreateFontsTexture(); -} - -void ImGui_ImplOpenGL2_DestroyDeviceObjects() -{ - ImGui_ImplOpenGL2_DestroyFontsTexture(); -} - - -//-------------------------------------------------------------------------------------------------------- -// MULTI-VIEWPORT / PLATFORM INTERFACE SUPPORT -// This is an _advanced_ and _optional_ feature, allowing the backend to create and handle multiple viewports simultaneously. -// If you are new to dear imgui or creating a new binding for dear imgui, it is recommended that you completely ignore this section first.. -//-------------------------------------------------------------------------------------------------------- - -static void ImGui_ImplOpenGL2_RenderWindow(ImGuiViewport* viewport, void*) -{ - if (!(viewport->Flags & ImGuiViewportFlags_NoRendererClear)) - { - ImVec4 clear_color = ImVec4(0.0f, 0.0f, 0.0f, 1.0f); - glClearColor(clear_color.x, clear_color.y, clear_color.z, clear_color.w); - glClear(GL_COLOR_BUFFER_BIT); - } - ImGui_ImplOpenGL2_RenderDrawData(viewport->DrawData); -} - -static void ImGui_ImplOpenGL2_InitPlatformInterface() -{ - ImGuiPlatformIO& platform_io = ImGui::GetPlatformIO(); - platform_io.Renderer_RenderWindow = ImGui_ImplOpenGL2_RenderWindow; -} - -static void ImGui_ImplOpenGL2_ShutdownPlatformInterface() -{ - ImGui::DestroyPlatformWindows(); -} - -//----------------------------------------------------------------------------- - -#if defined(__clang__) -#pragma clang diagnostic pop -#endif - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_opengl2.h b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_opengl2.h deleted file mode 100644 index be8fb6c..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_opengl2.h +++ /dev/null @@ -1,39 +0,0 @@ -// dear imgui: Renderer Backend for OpenGL2 (legacy OpenGL, fixed pipeline) -// This needs to be used along with a Platform Backend (e.g. GLFW, SDL, Win32, custom..) - -// Implemented features: -// [X] Renderer: User texture binding. Use 'GLuint' OpenGL texture identifier as void*/ImTextureID. Read the FAQ about ImTextureID! -// [X] Renderer: Multi-viewport support (multiple windows). Enable with 'io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable'. - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -// **DO NOT USE THIS CODE IF YOUR CODE/ENGINE IS USING MODERN OPENGL (SHADERS, VBO, VAO, etc.)** -// **Prefer using the code in imgui_impl_opengl3.cpp** -// This code is mostly provided as a reference to learn how ImGui integration works, because it is shorter to read. -// If your code is using GL3+ context or any semi modern OpenGL calls, using this is likely to make everything more -// complicated, will require your code to reset every single OpenGL attributes to their initial state, and might -// confuse your GPU driver. -// The GL2 code is unable to reset attributes or even call e.g. "glUseProgram(0)" because they don't exist in that API. - -#pragma once -#include "imgui.h" // IMGUI_IMPL_API -#ifndef IMGUI_DISABLE - -IMGUI_IMPL_API bool ImGui_ImplOpenGL2_Init(); -IMGUI_IMPL_API void ImGui_ImplOpenGL2_Shutdown(); -IMGUI_IMPL_API void ImGui_ImplOpenGL2_NewFrame(); -IMGUI_IMPL_API void ImGui_ImplOpenGL2_RenderDrawData(ImDrawData* draw_data); - -// Called by Init/NewFrame/Shutdown -IMGUI_IMPL_API bool ImGui_ImplOpenGL2_CreateFontsTexture(); -IMGUI_IMPL_API void ImGui_ImplOpenGL2_DestroyFontsTexture(); -IMGUI_IMPL_API bool ImGui_ImplOpenGL2_CreateDeviceObjects(); -IMGUI_IMPL_API void ImGui_ImplOpenGL2_DestroyDeviceObjects(); - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_opengl3.cpp b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_opengl3.cpp deleted file mode 100644 index 6aa49ea..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_opengl3.cpp +++ /dev/null @@ -1,985 +0,0 @@ -// dear imgui: Renderer Backend for modern OpenGL with shaders / programmatic pipeline -// - Desktop GL: 2.x 3.x 4.x -// - Embedded GL: ES 2.0 (WebGL 1.0), ES 3.0 (WebGL 2.0) -// This needs to be used along with a Platform Backend (e.g. GLFW, SDL, Win32, custom..) - -// Implemented features: -// [X] Renderer: User texture binding. Use 'GLuint' OpenGL texture identifier as void*/ImTextureID. Read the FAQ about ImTextureID! -// [X] Renderer: Large meshes support (64k+ vertices) with 16-bit indices (Desktop OpenGL only). -// [X] Renderer: Multi-viewport support (multiple windows). Enable with 'io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable'. - -// About WebGL/ES: -// - You need to '#define IMGUI_IMPL_OPENGL_ES2' or '#define IMGUI_IMPL_OPENGL_ES3' to use WebGL or OpenGL ES. -// - This is done automatically on iOS, Android and Emscripten targets. -// - For other targets, the define needs to be visible from the imgui_impl_opengl3.cpp compilation unit. If unsure, define globally or in imconfig.h. - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -// CHANGELOG -// (minor and older changes stripped away, please see git history for details) -// 2023-XX-XX: Platform: Added support for multiple windows via the ImGuiPlatformIO interface. -// 2023-10-05: OpenGL: Rename symbols in our internal loader so that LTO compilation with another copy of gl3w is possible. (#6875, #6668, #4445) -// 2023-06-20: OpenGL: Fixed erroneous use glGetIntegerv(GL_CONTEXT_PROFILE_MASK) on contexts lower than 3.2. (#6539, #6333) -// 2023-05-09: OpenGL: Support for glBindSampler() backup/restore on ES3. (#6375) -// 2023-04-18: OpenGL: Restore front and back polygon mode separately when supported by context. (#6333) -// 2023-03-23: OpenGL: Properly restoring "no shader program bound" if it was the case prior to running the rendering function. (#6267, #6220, #6224) -// 2023-03-15: OpenGL: Fixed GL loader crash when GL_VERSION returns NULL. (#6154, #4445, #3530) -// 2023-03-06: OpenGL: Fixed restoration of a potentially deleted OpenGL program, by calling glIsProgram(). (#6220, #6224) -// 2022-11-09: OpenGL: Reverted use of glBufferSubData(), too many corruptions issues + old issues seemingly can't be reproed with Intel drivers nowadays (revert 2021-12-15 and 2022-05-23 changes). -// 2022-10-11: Using 'nullptr' instead of 'NULL' as per our switch to C++11. -// 2022-09-27: OpenGL: Added ability to '#define IMGUI_IMPL_OPENGL_DEBUG'. -// 2022-05-23: OpenGL: Reworking 2021-12-15 "Using buffer orphaning" so it only happens on Intel GPU, seems to cause problems otherwise. (#4468, #4825, #4832, #5127). -// 2022-05-13: OpenGL: Fixed state corruption on OpenGL ES 2.0 due to not preserving GL_ELEMENT_ARRAY_BUFFER_BINDING and vertex attribute states. -// 2021-12-15: OpenGL: Using buffer orphaning + glBufferSubData(), seems to fix leaks with multi-viewports with some Intel HD drivers. -// 2021-08-23: OpenGL: Fixed ES 3.0 shader ("#version 300 es") use normal precision floats to avoid wobbly rendering at HD resolutions. -// 2021-08-19: OpenGL: Embed and use our own minimal GL loader (imgui_impl_opengl3_loader.h), removing requirement and support for third-party loader. -// 2021-06-29: Reorganized backend to pull data from a single structure to facilitate usage with multiple-contexts (all g_XXXX access changed to bd->XXXX). -// 2021-06-25: OpenGL: Use OES_vertex_array extension on Emscripten + backup/restore current state. -// 2021-06-21: OpenGL: Destroy individual vertex/fragment shader objects right after they are linked into the main shader. -// 2021-05-24: OpenGL: Access GL_CLIP_ORIGIN when "GL_ARB_clip_control" extension is detected, inside of just OpenGL 4.5 version. -// 2021-05-19: OpenGL: Replaced direct access to ImDrawCmd::TextureId with a call to ImDrawCmd::GetTexID(). (will become a requirement) -// 2021-04-06: OpenGL: Don't try to read GL_CLIP_ORIGIN unless we're OpenGL 4.5 or greater. -// 2021-02-18: OpenGL: Change blending equation to preserve alpha in output buffer. -// 2021-01-03: OpenGL: Backup, setup and restore GL_STENCIL_TEST state. -// 2020-10-23: OpenGL: Backup, setup and restore GL_PRIMITIVE_RESTART state. -// 2020-10-15: OpenGL: Use glGetString(GL_VERSION) instead of glGetIntegerv(GL_MAJOR_VERSION, ...) when the later returns zero (e.g. Desktop GL 2.x) -// 2020-09-17: OpenGL: Fix to avoid compiling/calling glBindSampler() on ES or pre 3.3 context which have the defines set by a loader. -// 2020-07-10: OpenGL: Added support for glad2 OpenGL loader. -// 2020-05-08: OpenGL: Made default GLSL version 150 (instead of 130) on OSX. -// 2020-04-21: OpenGL: Fixed handling of glClipControl(GL_UPPER_LEFT) by inverting projection matrix. -// 2020-04-12: OpenGL: Fixed context version check mistakenly testing for 4.0+ instead of 3.2+ to enable ImGuiBackendFlags_RendererHasVtxOffset. -// 2020-03-24: OpenGL: Added support for glbinding 2.x OpenGL loader. -// 2020-01-07: OpenGL: Added support for glbinding 3.x OpenGL loader. -// 2019-10-25: OpenGL: Using a combination of GL define and runtime GL version to decide whether to use glDrawElementsBaseVertex(). Fix building with pre-3.2 GL loaders. -// 2019-09-22: OpenGL: Detect default GL loader using __has_include compiler facility. -// 2019-09-16: OpenGL: Tweak initialization code to allow application calling ImGui_ImplOpenGL3_CreateFontsTexture() before the first NewFrame() call. -// 2019-05-29: OpenGL: Desktop GL only: Added support for large mesh (64K+ vertices), enable ImGuiBackendFlags_RendererHasVtxOffset flag. -// 2019-04-30: OpenGL: Added support for special ImDrawCallback_ResetRenderState callback to reset render state. -// 2019-03-29: OpenGL: Not calling glBindBuffer more than necessary in the render loop. -// 2019-03-15: OpenGL: Added a GL call + comments in ImGui_ImplOpenGL3_Init() to detect uninitialized GL function loaders early. -// 2019-03-03: OpenGL: Fix support for ES 2.0 (WebGL 1.0). -// 2019-02-20: OpenGL: Fix for OSX not supporting OpenGL 4.5, we don't try to read GL_CLIP_ORIGIN even if defined by the headers/loader. -// 2019-02-11: OpenGL: Projecting clipping rectangles correctly using draw_data->FramebufferScale to allow multi-viewports for retina display. -// 2019-02-01: OpenGL: Using GLSL 410 shaders for any version over 410 (e.g. 430, 450). -// 2018-11-30: Misc: Setting up io.BackendRendererName so it can be displayed in the About Window. -// 2018-11-13: OpenGL: Support for GL 4.5's glClipControl(GL_UPPER_LEFT) / GL_CLIP_ORIGIN. -// 2018-08-29: OpenGL: Added support for more OpenGL loaders: glew and glad, with comments indicative that any loader can be used. -// 2018-08-09: OpenGL: Default to OpenGL ES 3 on iOS and Android. GLSL version default to "#version 300 ES". -// 2018-07-30: OpenGL: Support for GLSL 300 ES and 410 core. Fixes for Emscripten compilation. -// 2018-07-10: OpenGL: Support for more GLSL versions (based on the GLSL version string). Added error output when shaders fail to compile/link. -// 2018-06-08: Misc: Extracted imgui_impl_opengl3.cpp/.h away from the old combined GLFW/SDL+OpenGL3 examples. -// 2018-06-08: OpenGL: Use draw_data->DisplayPos and draw_data->DisplaySize to setup projection matrix and clipping rectangle. -// 2018-05-25: OpenGL: Removed unnecessary backup/restore of GL_ELEMENT_ARRAY_BUFFER_BINDING since this is part of the VAO state. -// 2018-05-14: OpenGL: Making the call to glBindSampler() optional so 3.2 context won't fail if the function is a nullptr pointer. -// 2018-03-06: OpenGL: Added const char* glsl_version parameter to ImGui_ImplOpenGL3_Init() so user can override the GLSL version e.g. "#version 150". -// 2018-02-23: OpenGL: Create the VAO in the render function so the setup can more easily be used with multiple shared GL context. -// 2018-02-16: Misc: Obsoleted the io.RenderDrawListsFn callback and exposed ImGui_ImplSdlGL3_RenderDrawData() in the .h file so you can call it yourself. -// 2018-01-07: OpenGL: Changed GLSL shader version from 330 to 150. -// 2017-09-01: OpenGL: Save and restore current bound sampler. Save and restore current polygon mode. -// 2017-05-01: OpenGL: Fixed save and restore of current blend func state. -// 2017-05-01: OpenGL: Fixed save and restore of current GL_ACTIVE_TEXTURE. -// 2016-09-05: OpenGL: Fixed save and restore of current scissor rectangle. -// 2016-07-29: OpenGL: Explicitly setting GL_UNPACK_ROW_LENGTH to reduce issues because SDL changes it. (#752) - -//---------------------------------------- -// OpenGL GLSL GLSL -// version version string -//---------------------------------------- -// 2.0 110 "#version 110" -// 2.1 120 "#version 120" -// 3.0 130 "#version 130" -// 3.1 140 "#version 140" -// 3.2 150 "#version 150" -// 3.3 330 "#version 330 core" -// 4.0 400 "#version 400 core" -// 4.1 410 "#version 410 core" -// 4.2 420 "#version 410 core" -// 4.3 430 "#version 430 core" -// ES 2.0 100 "#version 100" = WebGL 1.0 -// ES 3.0 300 "#version 300 es" = WebGL 2.0 -//---------------------------------------- - -#if defined(_MSC_VER) && !defined(_CRT_SECURE_NO_WARNINGS) -#define _CRT_SECURE_NO_WARNINGS -#endif - -#include "imgui.h" -#ifndef IMGUI_DISABLE -#include "imgui_impl_opengl3.h" -#include -#include // intptr_t -#if defined(__APPLE__) -#include -#endif - -// Clang/GCC warnings with -Weverything -#if defined(__clang__) -#pragma clang diagnostic push -#pragma clang diagnostic ignored "-Wold-style-cast" // warning: use of old-style cast -#pragma clang diagnostic ignored "-Wsign-conversion" // warning: implicit conversion changes signedness -#pragma clang diagnostic ignored "-Wunused-macros" // warning: macro is not used -#pragma clang diagnostic ignored "-Wnonportable-system-include-path" -#pragma clang diagnostic ignored "-Wcast-function-type" // warning: cast between incompatible function types (for loader) -#endif -#if defined(__GNUC__) -#pragma GCC diagnostic push -#pragma GCC diagnostic ignored "-Wpragmas" // warning: unknown option after '#pragma GCC diagnostic' kind -#pragma GCC diagnostic ignored "-Wunknown-warning-option" // warning: unknown warning group 'xxx' -#pragma GCC diagnostic ignored "-Wcast-function-type" // warning: cast between incompatible function types (for loader) -#endif - -// GL includes -#if defined(IMGUI_IMPL_OPENGL_ES2) -#if (defined(__APPLE__) && (TARGET_OS_IOS || TARGET_OS_TV)) -#include // Use GL ES 2 -#else -#include // Use GL ES 2 -#endif -#if defined(__EMSCRIPTEN__) -#ifndef GL_GLEXT_PROTOTYPES -#define GL_GLEXT_PROTOTYPES -#endif -#include -#endif -#elif defined(IMGUI_IMPL_OPENGL_ES3) -#if (defined(__APPLE__) && (TARGET_OS_IOS || TARGET_OS_TV)) -#include // Use GL ES 3 -#else -#include // Use GL ES 3 -#endif -#elif !defined(IMGUI_IMPL_OPENGL_LOADER_CUSTOM) -// Modern desktop OpenGL doesn't have a standard portable header file to load OpenGL function pointers. -// Helper libraries are often used for this purpose! Here we are using our own minimal custom loader based on gl3w. -// In the rest of your app/engine, you can use another loader of your choice (gl3w, glew, glad, glbinding, glext, glLoadGen, etc.). -// If you happen to be developing a new feature for this backend (imgui_impl_opengl3.cpp): -// - You may need to regenerate imgui_impl_opengl3_loader.h to add new symbols. See https://github.com/dearimgui/gl3w_stripped -// - You can temporarily use an unstripped version. See https://github.com/dearimgui/gl3w_stripped/releases -// Changes to this backend using new APIs should be accompanied by a regenerated stripped loader version. -#define IMGL3W_IMPL -#include "imgui_impl_opengl3_loader.h" -#endif - -// Vertex arrays are not supported on ES2/WebGL1 unless Emscripten which uses an extension -#ifndef IMGUI_IMPL_OPENGL_ES2 -#define IMGUI_IMPL_OPENGL_USE_VERTEX_ARRAY -#elif defined(__EMSCRIPTEN__) -#define IMGUI_IMPL_OPENGL_USE_VERTEX_ARRAY -#define glBindVertexArray glBindVertexArrayOES -#define glGenVertexArrays glGenVertexArraysOES -#define glDeleteVertexArrays glDeleteVertexArraysOES -#define GL_VERTEX_ARRAY_BINDING GL_VERTEX_ARRAY_BINDING_OES -#endif - -// Desktop GL 2.0+ has glPolygonMode() which GL ES and WebGL don't have. -#ifdef GL_POLYGON_MODE -#define IMGUI_IMPL_HAS_POLYGON_MODE -#endif - -// Desktop GL 3.2+ has glDrawElementsBaseVertex() which GL ES and WebGL don't have. -#if !defined(IMGUI_IMPL_OPENGL_ES2) && !defined(IMGUI_IMPL_OPENGL_ES3) && defined(GL_VERSION_3_2) -#define IMGUI_IMPL_OPENGL_MAY_HAVE_VTX_OFFSET -#endif - -// Desktop GL 3.3+ and GL ES 3.0+ have glBindSampler() -#if !defined(IMGUI_IMPL_OPENGL_ES2) && (defined(IMGUI_IMPL_OPENGL_ES3) || defined(GL_VERSION_3_3)) -#define IMGUI_IMPL_OPENGL_MAY_HAVE_BIND_SAMPLER -#endif - -// Desktop GL 3.1+ has GL_PRIMITIVE_RESTART state -#if !defined(IMGUI_IMPL_OPENGL_ES2) && !defined(IMGUI_IMPL_OPENGL_ES3) && defined(GL_VERSION_3_1) -#define IMGUI_IMPL_OPENGL_MAY_HAVE_PRIMITIVE_RESTART -#endif - -// Desktop GL use extension detection -#if !defined(IMGUI_IMPL_OPENGL_ES2) && !defined(IMGUI_IMPL_OPENGL_ES3) -#define IMGUI_IMPL_OPENGL_MAY_HAVE_EXTENSIONS -#endif - -// [Debugging] -//#define IMGUI_IMPL_OPENGL_DEBUG -#ifdef IMGUI_IMPL_OPENGL_DEBUG -#include -#define GL_CALL(_CALL) do { _CALL; GLenum gl_err = glGetError(); if (gl_err != 0) fprintf(stderr, "GL error 0x%x returned from '%s'.\n", gl_err, #_CALL); } while (0) // Call with error check -#else -#define GL_CALL(_CALL) _CALL // Call without error check -#endif - -// OpenGL Data -struct ImGui_ImplOpenGL3_Data -{ - GLuint GlVersion; // Extracted at runtime using GL_MAJOR_VERSION, GL_MINOR_VERSION queries (e.g. 320 for GL 3.2) - char GlslVersionString[32]; // Specified by user or detected based on compile time GL settings. - bool GlProfileIsES2; - bool GlProfileIsES3; - bool GlProfileIsCompat; - GLint GlProfileMask; - GLuint FontTexture; - GLuint ShaderHandle; - GLint AttribLocationTex; // Uniforms location - GLint AttribLocationProjMtx; - GLuint AttribLocationVtxPos; // Vertex attributes location - GLuint AttribLocationVtxUV; - GLuint AttribLocationVtxColor; - unsigned int VboHandle, ElementsHandle; - GLsizeiptr VertexBufferSize; - GLsizeiptr IndexBufferSize; - bool HasClipOrigin; - bool UseBufferSubData; - - ImGui_ImplOpenGL3_Data() { memset((void*)this, 0, sizeof(*this)); } -}; - -// Backend data stored in io.BackendRendererUserData to allow support for multiple Dear ImGui contexts -// It is STRONGLY preferred that you use docking branch with multi-viewports (== single Dear ImGui context + multiple windows) instead of multiple Dear ImGui contexts. -static ImGui_ImplOpenGL3_Data* ImGui_ImplOpenGL3_GetBackendData() -{ - return ImGui::GetCurrentContext() ? (ImGui_ImplOpenGL3_Data*)ImGui::GetIO().BackendRendererUserData : nullptr; -} - -// Forward Declarations -static void ImGui_ImplOpenGL3_InitPlatformInterface(); -static void ImGui_ImplOpenGL3_ShutdownPlatformInterface(); - -// OpenGL vertex attribute state (for ES 1.0 and ES 2.0 only) -#ifndef IMGUI_IMPL_OPENGL_USE_VERTEX_ARRAY -struct ImGui_ImplOpenGL3_VtxAttribState -{ - GLint Enabled, Size, Type, Normalized, Stride; - GLvoid* Ptr; - - void GetState(GLint index) - { - glGetVertexAttribiv(index, GL_VERTEX_ATTRIB_ARRAY_ENABLED, &Enabled); - glGetVertexAttribiv(index, GL_VERTEX_ATTRIB_ARRAY_SIZE, &Size); - glGetVertexAttribiv(index, GL_VERTEX_ATTRIB_ARRAY_TYPE, &Type); - glGetVertexAttribiv(index, GL_VERTEX_ATTRIB_ARRAY_NORMALIZED, &Normalized); - glGetVertexAttribiv(index, GL_VERTEX_ATTRIB_ARRAY_STRIDE, &Stride); - glGetVertexAttribPointerv(index, GL_VERTEX_ATTRIB_ARRAY_POINTER, &Ptr); - } - void SetState(GLint index) - { - glVertexAttribPointer(index, Size, Type, (GLboolean)Normalized, Stride, Ptr); - if (Enabled) glEnableVertexAttribArray(index); else glDisableVertexAttribArray(index); - } -}; -#endif - -// Functions -bool ImGui_ImplOpenGL3_Init(const char* glsl_version) -{ - ImGuiIO& io = ImGui::GetIO(); - IM_ASSERT(io.BackendRendererUserData == nullptr && "Already initialized a renderer backend!"); - - // Initialize our loader -#if !defined(IMGUI_IMPL_OPENGL_ES2) && !defined(IMGUI_IMPL_OPENGL_ES3) && !defined(IMGUI_IMPL_OPENGL_LOADER_CUSTOM) - if (imgl3wInit() != 0) - { - fprintf(stderr, "Failed to initialize OpenGL loader!\n"); - return false; - } -#endif - - // Setup backend capabilities flags - ImGui_ImplOpenGL3_Data* bd = IM_NEW(ImGui_ImplOpenGL3_Data)(); - io.BackendRendererUserData = (void*)bd; - io.BackendRendererName = "imgui_impl_opengl3"; - - // Query for GL version (e.g. 320 for GL 3.2) -#if defined(IMGUI_IMPL_OPENGL_ES2) - // GLES 2 - bd->GlVersion = 200; - bd->GlProfileIsES2 = true; -#else - // Desktop or GLES 3 - GLint major = 0; - GLint minor = 0; - glGetIntegerv(GL_MAJOR_VERSION, &major); - glGetIntegerv(GL_MINOR_VERSION, &minor); - if (major == 0 && minor == 0) - { - // Query GL_VERSION in desktop GL 2.x, the string will start with "." - const char* gl_version = (const char*)glGetString(GL_VERSION); - sscanf(gl_version, "%d.%d", &major, &minor); - } - bd->GlVersion = (GLuint)(major * 100 + minor * 10); -#if defined(GL_CONTEXT_PROFILE_MASK) - if (bd->GlVersion >= 320) - glGetIntegerv(GL_CONTEXT_PROFILE_MASK, &bd->GlProfileMask); - bd->GlProfileIsCompat = (bd->GlProfileMask & GL_CONTEXT_COMPATIBILITY_PROFILE_BIT) != 0; -#endif - -#if defined(IMGUI_IMPL_OPENGL_ES3) - bd->GlProfileIsES3 = true; -#endif - - bd->UseBufferSubData = false; - /* - // Query vendor to enable glBufferSubData kludge -#ifdef _WIN32 - if (const char* vendor = (const char*)glGetString(GL_VENDOR)) - if (strncmp(vendor, "Intel", 5) == 0) - bd->UseBufferSubData = true; -#endif - */ -#endif - -#ifdef IMGUI_IMPL_OPENGL_DEBUG - printf("GlVersion = %d\nGlProfileIsCompat = %d\nGlProfileMask = 0x%X\nGlProfileIsES2 = %d, GlProfileIsES3 = %d\nGL_VENDOR = '%s'\nGL_RENDERER = '%s'\n", bd->GlVersion, bd->GlProfileIsCompat, bd->GlProfileMask, bd->GlProfileIsES2, bd->GlProfileIsES3, (const char*)glGetString(GL_VENDOR), (const char*)glGetString(GL_RENDERER)); // [DEBUG] -#endif - -#ifdef IMGUI_IMPL_OPENGL_MAY_HAVE_VTX_OFFSET - if (bd->GlVersion >= 320) - io.BackendFlags |= ImGuiBackendFlags_RendererHasVtxOffset; // We can honor the ImDrawCmd::VtxOffset field, allowing for large meshes. -#endif - io.BackendFlags |= ImGuiBackendFlags_RendererHasViewports; // We can create multi-viewports on the Renderer side (optional) - - // Store GLSL version string so we can refer to it later in case we recreate shaders. - // Note: GLSL version is NOT the same as GL version. Leave this to nullptr if unsure. - if (glsl_version == nullptr) - { -#if defined(IMGUI_IMPL_OPENGL_ES2) - glsl_version = "#version 100"; -#elif defined(IMGUI_IMPL_OPENGL_ES3) - glsl_version = "#version 300 es"; -#elif defined(__APPLE__) - glsl_version = "#version 150"; -#else - glsl_version = "#version 130"; -#endif - } - IM_ASSERT((int)strlen(glsl_version) + 2 < IM_ARRAYSIZE(bd->GlslVersionString)); - strcpy(bd->GlslVersionString, glsl_version); - strcat(bd->GlslVersionString, "\n"); - - // Make an arbitrary GL call (we don't actually need the result) - // IF YOU GET A CRASH HERE: it probably means the OpenGL function loader didn't do its job. Let us know! - GLint current_texture; - glGetIntegerv(GL_TEXTURE_BINDING_2D, ¤t_texture); - - // Detect extensions we support - bd->HasClipOrigin = (bd->GlVersion >= 450); -#ifdef IMGUI_IMPL_OPENGL_MAY_HAVE_EXTENSIONS - GLint num_extensions = 0; - glGetIntegerv(GL_NUM_EXTENSIONS, &num_extensions); - for (GLint i = 0; i < num_extensions; i++) - { - const char* extension = (const char*)glGetStringi(GL_EXTENSIONS, i); - if (extension != nullptr && strcmp(extension, "GL_ARB_clip_control") == 0) - bd->HasClipOrigin = true; - } -#endif - - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - ImGui_ImplOpenGL3_InitPlatformInterface(); - - return true; -} - -void ImGui_ImplOpenGL3_Shutdown() -{ - ImGui_ImplOpenGL3_Data* bd = ImGui_ImplOpenGL3_GetBackendData(); - IM_ASSERT(bd != nullptr && "No renderer backend to shutdown, or already shutdown?"); - ImGuiIO& io = ImGui::GetIO(); - - ImGui_ImplOpenGL3_ShutdownPlatformInterface(); - ImGui_ImplOpenGL3_DestroyDeviceObjects(); - io.BackendRendererName = nullptr; - io.BackendRendererUserData = nullptr; - io.BackendFlags &= ~(ImGuiBackendFlags_RendererHasVtxOffset | ImGuiBackendFlags_RendererHasViewports); - IM_DELETE(bd); -} - -void ImGui_ImplOpenGL3_NewFrame() -{ - ImGui_ImplOpenGL3_Data* bd = ImGui_ImplOpenGL3_GetBackendData(); - IM_ASSERT(bd != nullptr && "Did you call ImGui_ImplOpenGL3_Init()?"); - - if (!bd->ShaderHandle) - ImGui_ImplOpenGL3_CreateDeviceObjects(); -} - -static void ImGui_ImplOpenGL3_SetupRenderState(ImDrawData* draw_data, int fb_width, int fb_height, GLuint vertex_array_object) -{ - ImGui_ImplOpenGL3_Data* bd = ImGui_ImplOpenGL3_GetBackendData(); - - // Setup render state: alpha-blending enabled, no face culling, no depth testing, scissor enabled, polygon fill - glEnable(GL_BLEND); - glBlendEquation(GL_FUNC_ADD); - glBlendFuncSeparate(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA, GL_ONE, GL_ONE_MINUS_SRC_ALPHA); - glDisable(GL_CULL_FACE); - glDisable(GL_DEPTH_TEST); - glDisable(GL_STENCIL_TEST); - glEnable(GL_SCISSOR_TEST); -#ifdef IMGUI_IMPL_OPENGL_MAY_HAVE_PRIMITIVE_RESTART - if (bd->GlVersion >= 310) - glDisable(GL_PRIMITIVE_RESTART); -#endif -#ifdef IMGUI_IMPL_HAS_POLYGON_MODE - glPolygonMode(GL_FRONT_AND_BACK, GL_FILL); -#endif - - // Support for GL 4.5 rarely used glClipControl(GL_UPPER_LEFT) -#if defined(GL_CLIP_ORIGIN) - bool clip_origin_lower_left = true; - if (bd->HasClipOrigin) - { - GLenum current_clip_origin = 0; glGetIntegerv(GL_CLIP_ORIGIN, (GLint*)¤t_clip_origin); - if (current_clip_origin == GL_UPPER_LEFT) - clip_origin_lower_left = false; - } -#endif - - // Setup viewport, orthographic projection matrix - // Our visible imgui space lies from draw_data->DisplayPos (top left) to draw_data->DisplayPos+data_data->DisplaySize (bottom right). DisplayPos is (0,0) for single viewport apps. - GL_CALL(glViewport(0, 0, (GLsizei)fb_width, (GLsizei)fb_height)); - float L = draw_data->DisplayPos.x; - float R = draw_data->DisplayPos.x + draw_data->DisplaySize.x; - float T = draw_data->DisplayPos.y; - float B = draw_data->DisplayPos.y + draw_data->DisplaySize.y; -#if defined(GL_CLIP_ORIGIN) - if (!clip_origin_lower_left) { float tmp = T; T = B; B = tmp; } // Swap top and bottom if origin is upper left -#endif - const float ortho_projection[4][4] = - { - { 2.0f/(R-L), 0.0f, 0.0f, 0.0f }, - { 0.0f, 2.0f/(T-B), 0.0f, 0.0f }, - { 0.0f, 0.0f, -1.0f, 0.0f }, - { (R+L)/(L-R), (T+B)/(B-T), 0.0f, 1.0f }, - }; - glUseProgram(bd->ShaderHandle); - glUniform1i(bd->AttribLocationTex, 0); - glUniformMatrix4fv(bd->AttribLocationProjMtx, 1, GL_FALSE, &ortho_projection[0][0]); - -#ifdef IMGUI_IMPL_OPENGL_MAY_HAVE_BIND_SAMPLER - if (bd->GlVersion >= 330 || bd->GlProfileIsES3) - glBindSampler(0, 0); // We use combined texture/sampler state. Applications using GL 3.3 and GL ES 3.0 may set that otherwise. -#endif - - (void)vertex_array_object; -#ifdef IMGUI_IMPL_OPENGL_USE_VERTEX_ARRAY - glBindVertexArray(vertex_array_object); -#endif - - // Bind vertex/index buffers and setup attributes for ImDrawVert - GL_CALL(glBindBuffer(GL_ARRAY_BUFFER, bd->VboHandle)); - GL_CALL(glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, bd->ElementsHandle)); - GL_CALL(glEnableVertexAttribArray(bd->AttribLocationVtxPos)); - GL_CALL(glEnableVertexAttribArray(bd->AttribLocationVtxUV)); - GL_CALL(glEnableVertexAttribArray(bd->AttribLocationVtxColor)); - GL_CALL(glVertexAttribPointer(bd->AttribLocationVtxPos, 2, GL_FLOAT, GL_FALSE, sizeof(ImDrawVert), (GLvoid*)IM_OFFSETOF(ImDrawVert, pos))); - GL_CALL(glVertexAttribPointer(bd->AttribLocationVtxUV, 2, GL_FLOAT, GL_FALSE, sizeof(ImDrawVert), (GLvoid*)IM_OFFSETOF(ImDrawVert, uv))); - GL_CALL(glVertexAttribPointer(bd->AttribLocationVtxColor, 4, GL_UNSIGNED_BYTE, GL_TRUE, sizeof(ImDrawVert), (GLvoid*)IM_OFFSETOF(ImDrawVert, col))); -} - -// OpenGL3 Render function. -// Note that this implementation is little overcomplicated because we are saving/setting up/restoring every OpenGL state explicitly. -// This is in order to be able to run within an OpenGL engine that doesn't do so. -void ImGui_ImplOpenGL3_RenderDrawData(ImDrawData* draw_data) -{ - // Avoid rendering when minimized, scale coordinates for retina displays (screen coordinates != framebuffer coordinates) - int fb_width = (int)(draw_data->DisplaySize.x * draw_data->FramebufferScale.x); - int fb_height = (int)(draw_data->DisplaySize.y * draw_data->FramebufferScale.y); - if (fb_width <= 0 || fb_height <= 0) - return; - - ImGui_ImplOpenGL3_Data* bd = ImGui_ImplOpenGL3_GetBackendData(); - - // Backup GL state - GLenum last_active_texture; glGetIntegerv(GL_ACTIVE_TEXTURE, (GLint*)&last_active_texture); - glActiveTexture(GL_TEXTURE0); - GLuint last_program; glGetIntegerv(GL_CURRENT_PROGRAM, (GLint*)&last_program); - GLuint last_texture; glGetIntegerv(GL_TEXTURE_BINDING_2D, (GLint*)&last_texture); -#ifdef IMGUI_IMPL_OPENGL_MAY_HAVE_BIND_SAMPLER - GLuint last_sampler; if (bd->GlVersion >= 330 || bd->GlProfileIsES3) { glGetIntegerv(GL_SAMPLER_BINDING, (GLint*)&last_sampler); } else { last_sampler = 0; } -#endif - GLuint last_array_buffer; glGetIntegerv(GL_ARRAY_BUFFER_BINDING, (GLint*)&last_array_buffer); -#ifndef IMGUI_IMPL_OPENGL_USE_VERTEX_ARRAY - // This is part of VAO on OpenGL 3.0+ and OpenGL ES 3.0+. - GLint last_element_array_buffer; glGetIntegerv(GL_ELEMENT_ARRAY_BUFFER_BINDING, &last_element_array_buffer); - ImGui_ImplOpenGL3_VtxAttribState last_vtx_attrib_state_pos; last_vtx_attrib_state_pos.GetState(bd->AttribLocationVtxPos); - ImGui_ImplOpenGL3_VtxAttribState last_vtx_attrib_state_uv; last_vtx_attrib_state_uv.GetState(bd->AttribLocationVtxUV); - ImGui_ImplOpenGL3_VtxAttribState last_vtx_attrib_state_color; last_vtx_attrib_state_color.GetState(bd->AttribLocationVtxColor); -#endif -#ifdef IMGUI_IMPL_OPENGL_USE_VERTEX_ARRAY - GLuint last_vertex_array_object; glGetIntegerv(GL_VERTEX_ARRAY_BINDING, (GLint*)&last_vertex_array_object); -#endif -#ifdef IMGUI_IMPL_HAS_POLYGON_MODE - GLint last_polygon_mode[2]; glGetIntegerv(GL_POLYGON_MODE, last_polygon_mode); -#endif - GLint last_viewport[4]; glGetIntegerv(GL_VIEWPORT, last_viewport); - GLint last_scissor_box[4]; glGetIntegerv(GL_SCISSOR_BOX, last_scissor_box); - GLenum last_blend_src_rgb; glGetIntegerv(GL_BLEND_SRC_RGB, (GLint*)&last_blend_src_rgb); - GLenum last_blend_dst_rgb; glGetIntegerv(GL_BLEND_DST_RGB, (GLint*)&last_blend_dst_rgb); - GLenum last_blend_src_alpha; glGetIntegerv(GL_BLEND_SRC_ALPHA, (GLint*)&last_blend_src_alpha); - GLenum last_blend_dst_alpha; glGetIntegerv(GL_BLEND_DST_ALPHA, (GLint*)&last_blend_dst_alpha); - GLenum last_blend_equation_rgb; glGetIntegerv(GL_BLEND_EQUATION_RGB, (GLint*)&last_blend_equation_rgb); - GLenum last_blend_equation_alpha; glGetIntegerv(GL_BLEND_EQUATION_ALPHA, (GLint*)&last_blend_equation_alpha); - GLboolean last_enable_blend = glIsEnabled(GL_BLEND); - GLboolean last_enable_cull_face = glIsEnabled(GL_CULL_FACE); - GLboolean last_enable_depth_test = glIsEnabled(GL_DEPTH_TEST); - GLboolean last_enable_stencil_test = glIsEnabled(GL_STENCIL_TEST); - GLboolean last_enable_scissor_test = glIsEnabled(GL_SCISSOR_TEST); -#ifdef IMGUI_IMPL_OPENGL_MAY_HAVE_PRIMITIVE_RESTART - GLboolean last_enable_primitive_restart = (bd->GlVersion >= 310) ? glIsEnabled(GL_PRIMITIVE_RESTART) : GL_FALSE; -#endif - - // Setup desired GL state - // Recreate the VAO every time (this is to easily allow multiple GL contexts to be rendered to. VAO are not shared among GL contexts) - // The renderer would actually work without any VAO bound, but then our VertexAttrib calls would overwrite the default one currently bound. - GLuint vertex_array_object = 0; -#ifdef IMGUI_IMPL_OPENGL_USE_VERTEX_ARRAY - GL_CALL(glGenVertexArrays(1, &vertex_array_object)); -#endif - ImGui_ImplOpenGL3_SetupRenderState(draw_data, fb_width, fb_height, vertex_array_object); - - // Will project scissor/clipping rectangles into framebuffer space - ImVec2 clip_off = draw_data->DisplayPos; // (0,0) unless using multi-viewports - ImVec2 clip_scale = draw_data->FramebufferScale; // (1,1) unless using retina display which are often (2,2) - - // Render command lists - for (int n = 0; n < draw_data->CmdListsCount; n++) - { - const ImDrawList* cmd_list = draw_data->CmdLists[n]; - - // Upload vertex/index buffers - // - OpenGL drivers are in a very sorry state nowadays.... - // During 2021 we attempted to switch from glBufferData() to orphaning+glBufferSubData() following reports - // of leaks on Intel GPU when using multi-viewports on Windows. - // - After this we kept hearing of various display corruptions issues. We started disabling on non-Intel GPU, but issues still got reported on Intel. - // - We are now back to using exclusively glBufferData(). So bd->UseBufferSubData IS ALWAYS FALSE in this code. - // We are keeping the old code path for a while in case people finding new issues may want to test the bd->UseBufferSubData path. - // - See https://github.com/ocornut/imgui/issues/4468 and please report any corruption issues. - const GLsizeiptr vtx_buffer_size = (GLsizeiptr)cmd_list->VtxBuffer.Size * (int)sizeof(ImDrawVert); - const GLsizeiptr idx_buffer_size = (GLsizeiptr)cmd_list->IdxBuffer.Size * (int)sizeof(ImDrawIdx); - if (bd->UseBufferSubData) - { - if (bd->VertexBufferSize < vtx_buffer_size) - { - bd->VertexBufferSize = vtx_buffer_size; - GL_CALL(glBufferData(GL_ARRAY_BUFFER, bd->VertexBufferSize, nullptr, GL_STREAM_DRAW)); - } - if (bd->IndexBufferSize < idx_buffer_size) - { - bd->IndexBufferSize = idx_buffer_size; - GL_CALL(glBufferData(GL_ELEMENT_ARRAY_BUFFER, bd->IndexBufferSize, nullptr, GL_STREAM_DRAW)); - } - GL_CALL(glBufferSubData(GL_ARRAY_BUFFER, 0, vtx_buffer_size, (const GLvoid*)cmd_list->VtxBuffer.Data)); - GL_CALL(glBufferSubData(GL_ELEMENT_ARRAY_BUFFER, 0, idx_buffer_size, (const GLvoid*)cmd_list->IdxBuffer.Data)); - } - else - { - GL_CALL(glBufferData(GL_ARRAY_BUFFER, vtx_buffer_size, (const GLvoid*)cmd_list->VtxBuffer.Data, GL_STREAM_DRAW)); - GL_CALL(glBufferData(GL_ELEMENT_ARRAY_BUFFER, idx_buffer_size, (const GLvoid*)cmd_list->IdxBuffer.Data, GL_STREAM_DRAW)); - } - - for (int cmd_i = 0; cmd_i < cmd_list->CmdBuffer.Size; cmd_i++) - { - const ImDrawCmd* pcmd = &cmd_list->CmdBuffer[cmd_i]; - if (pcmd->UserCallback != nullptr) - { - // User callback, registered via ImDrawList::AddCallback() - // (ImDrawCallback_ResetRenderState is a special callback value used by the user to request the renderer to reset render state.) - if (pcmd->UserCallback == ImDrawCallback_ResetRenderState) - ImGui_ImplOpenGL3_SetupRenderState(draw_data, fb_width, fb_height, vertex_array_object); - else - pcmd->UserCallback(cmd_list, pcmd); - } - else - { - // Project scissor/clipping rectangles into framebuffer space - ImVec2 clip_min((pcmd->ClipRect.x - clip_off.x) * clip_scale.x, (pcmd->ClipRect.y - clip_off.y) * clip_scale.y); - ImVec2 clip_max((pcmd->ClipRect.z - clip_off.x) * clip_scale.x, (pcmd->ClipRect.w - clip_off.y) * clip_scale.y); - if (clip_max.x <= clip_min.x || clip_max.y <= clip_min.y) - continue; - - // Apply scissor/clipping rectangle (Y is inverted in OpenGL) - GL_CALL(glScissor((int)clip_min.x, (int)((float)fb_height - clip_max.y), (int)(clip_max.x - clip_min.x), (int)(clip_max.y - clip_min.y))); - - // Bind texture, Draw - GL_CALL(glBindTexture(GL_TEXTURE_2D, (GLuint)(intptr_t)pcmd->GetTexID())); -#ifdef IMGUI_IMPL_OPENGL_MAY_HAVE_VTX_OFFSET - if (bd->GlVersion >= 320) - GL_CALL(glDrawElementsBaseVertex(GL_TRIANGLES, (GLsizei)pcmd->ElemCount, sizeof(ImDrawIdx) == 2 ? GL_UNSIGNED_SHORT : GL_UNSIGNED_INT, (void*)(intptr_t)(pcmd->IdxOffset * sizeof(ImDrawIdx)), (GLint)pcmd->VtxOffset)); - else -#endif - GL_CALL(glDrawElements(GL_TRIANGLES, (GLsizei)pcmd->ElemCount, sizeof(ImDrawIdx) == 2 ? GL_UNSIGNED_SHORT : GL_UNSIGNED_INT, (void*)(intptr_t)(pcmd->IdxOffset * sizeof(ImDrawIdx)))); - } - } - } - - // Destroy the temporary VAO -#ifdef IMGUI_IMPL_OPENGL_USE_VERTEX_ARRAY - GL_CALL(glDeleteVertexArrays(1, &vertex_array_object)); -#endif - - // Restore modified GL state - // This "glIsProgram()" check is required because if the program is "pending deletion" at the time of binding backup, it will have been deleted by now and will cause an OpenGL error. See #6220. - if (last_program == 0 || glIsProgram(last_program)) glUseProgram(last_program); - glBindTexture(GL_TEXTURE_2D, last_texture); -#ifdef IMGUI_IMPL_OPENGL_MAY_HAVE_BIND_SAMPLER - if (bd->GlVersion >= 330 || bd->GlProfileIsES3) - glBindSampler(0, last_sampler); -#endif - glActiveTexture(last_active_texture); -#ifdef IMGUI_IMPL_OPENGL_USE_VERTEX_ARRAY - glBindVertexArray(last_vertex_array_object); -#endif - glBindBuffer(GL_ARRAY_BUFFER, last_array_buffer); -#ifndef IMGUI_IMPL_OPENGL_USE_VERTEX_ARRAY - glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, last_element_array_buffer); - last_vtx_attrib_state_pos.SetState(bd->AttribLocationVtxPos); - last_vtx_attrib_state_uv.SetState(bd->AttribLocationVtxUV); - last_vtx_attrib_state_color.SetState(bd->AttribLocationVtxColor); -#endif - glBlendEquationSeparate(last_blend_equation_rgb, last_blend_equation_alpha); - glBlendFuncSeparate(last_blend_src_rgb, last_blend_dst_rgb, last_blend_src_alpha, last_blend_dst_alpha); - if (last_enable_blend) glEnable(GL_BLEND); else glDisable(GL_BLEND); - if (last_enable_cull_face) glEnable(GL_CULL_FACE); else glDisable(GL_CULL_FACE); - if (last_enable_depth_test) glEnable(GL_DEPTH_TEST); else glDisable(GL_DEPTH_TEST); - if (last_enable_stencil_test) glEnable(GL_STENCIL_TEST); else glDisable(GL_STENCIL_TEST); - if (last_enable_scissor_test) glEnable(GL_SCISSOR_TEST); else glDisable(GL_SCISSOR_TEST); -#ifdef IMGUI_IMPL_OPENGL_MAY_HAVE_PRIMITIVE_RESTART - if (bd->GlVersion >= 310) { if (last_enable_primitive_restart) glEnable(GL_PRIMITIVE_RESTART); else glDisable(GL_PRIMITIVE_RESTART); } -#endif - -#ifdef IMGUI_IMPL_HAS_POLYGON_MODE - // Desktop OpenGL 3.0 and OpenGL 3.1 had separate polygon draw modes for front-facing and back-facing faces of polygons - if (bd->GlVersion <= 310 || bd->GlProfileIsCompat) - { - glPolygonMode(GL_FRONT, (GLenum)last_polygon_mode[0]); - glPolygonMode(GL_BACK, (GLenum)last_polygon_mode[1]); - } - else - { - glPolygonMode(GL_FRONT_AND_BACK, (GLenum)last_polygon_mode[0]); - } -#endif // IMGUI_IMPL_HAS_POLYGON_MODE - - glViewport(last_viewport[0], last_viewport[1], (GLsizei)last_viewport[2], (GLsizei)last_viewport[3]); - glScissor(last_scissor_box[0], last_scissor_box[1], (GLsizei)last_scissor_box[2], (GLsizei)last_scissor_box[3]); - (void)bd; // Not all compilation paths use this -} - -bool ImGui_ImplOpenGL3_CreateFontsTexture() -{ - ImGuiIO& io = ImGui::GetIO(); - ImGui_ImplOpenGL3_Data* bd = ImGui_ImplOpenGL3_GetBackendData(); - - // Build texture atlas - unsigned char* pixels; - int width, height; - io.Fonts->GetTexDataAsRGBA32(&pixels, &width, &height); // Load as RGBA 32-bit (75% of the memory is wasted, but default font is so small) because it is more likely to be compatible with user's existing shaders. If your ImTextureId represent a higher-level concept than just a GL texture id, consider calling GetTexDataAsAlpha8() instead to save on GPU memory. - - // Upload texture to graphics system - // (Bilinear sampling is required by default. Set 'io.Fonts->Flags |= ImFontAtlasFlags_NoBakedLines' or 'style.AntiAliasedLinesUseTex = false' to allow point/nearest sampling) - GLint last_texture; - GL_CALL(glGetIntegerv(GL_TEXTURE_BINDING_2D, &last_texture)); - GL_CALL(glGenTextures(1, &bd->FontTexture)); - GL_CALL(glBindTexture(GL_TEXTURE_2D, bd->FontTexture)); - GL_CALL(glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR)); - GL_CALL(glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR)); -#ifdef GL_UNPACK_ROW_LENGTH // Not on WebGL/ES - GL_CALL(glPixelStorei(GL_UNPACK_ROW_LENGTH, 0)); -#endif - GL_CALL(glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, width, height, 0, GL_RGBA, GL_UNSIGNED_BYTE, pixels)); - - // Store our identifier - io.Fonts->SetTexID((ImTextureID)(intptr_t)bd->FontTexture); - - // Restore state - GL_CALL(glBindTexture(GL_TEXTURE_2D, last_texture)); - - return true; -} - -void ImGui_ImplOpenGL3_DestroyFontsTexture() -{ - ImGuiIO& io = ImGui::GetIO(); - ImGui_ImplOpenGL3_Data* bd = ImGui_ImplOpenGL3_GetBackendData(); - if (bd->FontTexture) - { - glDeleteTextures(1, &bd->FontTexture); - io.Fonts->SetTexID(0); - bd->FontTexture = 0; - } -} - -// If you get an error please report on github. You may try different GL context version or GLSL version. See GL<>GLSL version table at the top of this file. -static bool CheckShader(GLuint handle, const char* desc) -{ - ImGui_ImplOpenGL3_Data* bd = ImGui_ImplOpenGL3_GetBackendData(); - GLint status = 0, log_length = 0; - glGetShaderiv(handle, GL_COMPILE_STATUS, &status); - glGetShaderiv(handle, GL_INFO_LOG_LENGTH, &log_length); - if ((GLboolean)status == GL_FALSE) - fprintf(stderr, "ERROR: ImGui_ImplOpenGL3_CreateDeviceObjects: failed to compile %s! With GLSL: %s\n", desc, bd->GlslVersionString); - if (log_length > 1) - { - ImVector buf; - buf.resize((int)(log_length + 1)); - glGetShaderInfoLog(handle, log_length, nullptr, (GLchar*)buf.begin()); - fprintf(stderr, "%s\n", buf.begin()); - } - return (GLboolean)status == GL_TRUE; -} - -// If you get an error please report on GitHub. You may try different GL context version or GLSL version. -static bool CheckProgram(GLuint handle, const char* desc) -{ - ImGui_ImplOpenGL3_Data* bd = ImGui_ImplOpenGL3_GetBackendData(); - GLint status = 0, log_length = 0; - glGetProgramiv(handle, GL_LINK_STATUS, &status); - glGetProgramiv(handle, GL_INFO_LOG_LENGTH, &log_length); - if ((GLboolean)status == GL_FALSE) - fprintf(stderr, "ERROR: ImGui_ImplOpenGL3_CreateDeviceObjects: failed to link %s! With GLSL %s\n", desc, bd->GlslVersionString); - if (log_length > 1) - { - ImVector buf; - buf.resize((int)(log_length + 1)); - glGetProgramInfoLog(handle, log_length, nullptr, (GLchar*)buf.begin()); - fprintf(stderr, "%s\n", buf.begin()); - } - return (GLboolean)status == GL_TRUE; -} - -bool ImGui_ImplOpenGL3_CreateDeviceObjects() -{ - ImGui_ImplOpenGL3_Data* bd = ImGui_ImplOpenGL3_GetBackendData(); - - // Backup GL state - GLint last_texture, last_array_buffer; - glGetIntegerv(GL_TEXTURE_BINDING_2D, &last_texture); - glGetIntegerv(GL_ARRAY_BUFFER_BINDING, &last_array_buffer); -#ifdef IMGUI_IMPL_OPENGL_USE_VERTEX_ARRAY - GLint last_vertex_array; - glGetIntegerv(GL_VERTEX_ARRAY_BINDING, &last_vertex_array); -#endif - - // Parse GLSL version string - int glsl_version = 130; - sscanf(bd->GlslVersionString, "#version %d", &glsl_version); - - const GLchar* vertex_shader_glsl_120 = - "uniform mat4 ProjMtx;\n" - "attribute vec2 Position;\n" - "attribute vec2 UV;\n" - "attribute vec4 Color;\n" - "varying vec2 Frag_UV;\n" - "varying vec4 Frag_Color;\n" - "void main()\n" - "{\n" - " Frag_UV = UV;\n" - " Frag_Color = Color;\n" - " gl_Position = ProjMtx * vec4(Position.xy,0,1);\n" - "}\n"; - - const GLchar* vertex_shader_glsl_130 = - "uniform mat4 ProjMtx;\n" - "in vec2 Position;\n" - "in vec2 UV;\n" - "in vec4 Color;\n" - "out vec2 Frag_UV;\n" - "out vec4 Frag_Color;\n" - "void main()\n" - "{\n" - " Frag_UV = UV;\n" - " Frag_Color = Color;\n" - " gl_Position = ProjMtx * vec4(Position.xy,0,1);\n" - "}\n"; - - const GLchar* vertex_shader_glsl_300_es = - "precision highp float;\n" - "layout (location = 0) in vec2 Position;\n" - "layout (location = 1) in vec2 UV;\n" - "layout (location = 2) in vec4 Color;\n" - "uniform mat4 ProjMtx;\n" - "out vec2 Frag_UV;\n" - "out vec4 Frag_Color;\n" - "void main()\n" - "{\n" - " Frag_UV = UV;\n" - " Frag_Color = Color;\n" - " gl_Position = ProjMtx * vec4(Position.xy,0,1);\n" - "}\n"; - - const GLchar* vertex_shader_glsl_410_core = - "layout (location = 0) in vec2 Position;\n" - "layout (location = 1) in vec2 UV;\n" - "layout (location = 2) in vec4 Color;\n" - "uniform mat4 ProjMtx;\n" - "out vec2 Frag_UV;\n" - "out vec4 Frag_Color;\n" - "void main()\n" - "{\n" - " Frag_UV = UV;\n" - " Frag_Color = Color;\n" - " gl_Position = ProjMtx * vec4(Position.xy,0,1);\n" - "}\n"; - - const GLchar* fragment_shader_glsl_120 = - "#ifdef GL_ES\n" - " precision mediump float;\n" - "#endif\n" - "uniform sampler2D Texture;\n" - "varying vec2 Frag_UV;\n" - "varying vec4 Frag_Color;\n" - "void main()\n" - "{\n" - " gl_FragColor = Frag_Color * texture2D(Texture, Frag_UV.st);\n" - "}\n"; - - const GLchar* fragment_shader_glsl_130 = - "uniform sampler2D Texture;\n" - "in vec2 Frag_UV;\n" - "in vec4 Frag_Color;\n" - "out vec4 Out_Color;\n" - "void main()\n" - "{\n" - " Out_Color = Frag_Color * texture(Texture, Frag_UV.st);\n" - "}\n"; - - const GLchar* fragment_shader_glsl_300_es = - "precision mediump float;\n" - "uniform sampler2D Texture;\n" - "in vec2 Frag_UV;\n" - "in vec4 Frag_Color;\n" - "layout (location = 0) out vec4 Out_Color;\n" - "void main()\n" - "{\n" - " Out_Color = Frag_Color * texture(Texture, Frag_UV.st);\n" - "}\n"; - - const GLchar* fragment_shader_glsl_410_core = - "in vec2 Frag_UV;\n" - "in vec4 Frag_Color;\n" - "uniform sampler2D Texture;\n" - "layout (location = 0) out vec4 Out_Color;\n" - "void main()\n" - "{\n" - " Out_Color = Frag_Color * texture(Texture, Frag_UV.st);\n" - "}\n"; - - // Select shaders matching our GLSL versions - const GLchar* vertex_shader = nullptr; - const GLchar* fragment_shader = nullptr; - if (glsl_version < 130) - { - vertex_shader = vertex_shader_glsl_120; - fragment_shader = fragment_shader_glsl_120; - } - else if (glsl_version >= 410) - { - vertex_shader = vertex_shader_glsl_410_core; - fragment_shader = fragment_shader_glsl_410_core; - } - else if (glsl_version == 300) - { - vertex_shader = vertex_shader_glsl_300_es; - fragment_shader = fragment_shader_glsl_300_es; - } - else - { - vertex_shader = vertex_shader_glsl_130; - fragment_shader = fragment_shader_glsl_130; - } - - // Create shaders - const GLchar* vertex_shader_with_version[2] = { bd->GlslVersionString, vertex_shader }; - GLuint vert_handle = glCreateShader(GL_VERTEX_SHADER); - glShaderSource(vert_handle, 2, vertex_shader_with_version, nullptr); - glCompileShader(vert_handle); - CheckShader(vert_handle, "vertex shader"); - - const GLchar* fragment_shader_with_version[2] = { bd->GlslVersionString, fragment_shader }; - GLuint frag_handle = glCreateShader(GL_FRAGMENT_SHADER); - glShaderSource(frag_handle, 2, fragment_shader_with_version, nullptr); - glCompileShader(frag_handle); - CheckShader(frag_handle, "fragment shader"); - - // Link - bd->ShaderHandle = glCreateProgram(); - glAttachShader(bd->ShaderHandle, vert_handle); - glAttachShader(bd->ShaderHandle, frag_handle); - glLinkProgram(bd->ShaderHandle); - CheckProgram(bd->ShaderHandle, "shader program"); - - glDetachShader(bd->ShaderHandle, vert_handle); - glDetachShader(bd->ShaderHandle, frag_handle); - glDeleteShader(vert_handle); - glDeleteShader(frag_handle); - - bd->AttribLocationTex = glGetUniformLocation(bd->ShaderHandle, "Texture"); - bd->AttribLocationProjMtx = glGetUniformLocation(bd->ShaderHandle, "ProjMtx"); - bd->AttribLocationVtxPos = (GLuint)glGetAttribLocation(bd->ShaderHandle, "Position"); - bd->AttribLocationVtxUV = (GLuint)glGetAttribLocation(bd->ShaderHandle, "UV"); - bd->AttribLocationVtxColor = (GLuint)glGetAttribLocation(bd->ShaderHandle, "Color"); - - // Create buffers - glGenBuffers(1, &bd->VboHandle); - glGenBuffers(1, &bd->ElementsHandle); - - ImGui_ImplOpenGL3_CreateFontsTexture(); - - // Restore modified GL state - glBindTexture(GL_TEXTURE_2D, last_texture); - glBindBuffer(GL_ARRAY_BUFFER, last_array_buffer); -#ifdef IMGUI_IMPL_OPENGL_USE_VERTEX_ARRAY - glBindVertexArray(last_vertex_array); -#endif - - return true; -} - -void ImGui_ImplOpenGL3_DestroyDeviceObjects() -{ - ImGui_ImplOpenGL3_Data* bd = ImGui_ImplOpenGL3_GetBackendData(); - if (bd->VboHandle) { glDeleteBuffers(1, &bd->VboHandle); bd->VboHandle = 0; } - if (bd->ElementsHandle) { glDeleteBuffers(1, &bd->ElementsHandle); bd->ElementsHandle = 0; } - if (bd->ShaderHandle) { glDeleteProgram(bd->ShaderHandle); bd->ShaderHandle = 0; } - ImGui_ImplOpenGL3_DestroyFontsTexture(); -} - -//-------------------------------------------------------------------------------------------------------- -// MULTI-VIEWPORT / PLATFORM INTERFACE SUPPORT -// This is an _advanced_ and _optional_ feature, allowing the backend to create and handle multiple viewports simultaneously. -// If you are new to dear imgui or creating a new binding for dear imgui, it is recommended that you completely ignore this section first.. -//-------------------------------------------------------------------------------------------------------- - -static void ImGui_ImplOpenGL3_RenderWindow(ImGuiViewport* viewport, void*) -{ - if (!(viewport->Flags & ImGuiViewportFlags_NoRendererClear)) - { - ImVec4 clear_color = ImVec4(0.0f, 0.0f, 0.0f, 1.0f); - glClearColor(clear_color.x, clear_color.y, clear_color.z, clear_color.w); - glClear(GL_COLOR_BUFFER_BIT); - } - ImGui_ImplOpenGL3_RenderDrawData(viewport->DrawData); -} - -static void ImGui_ImplOpenGL3_InitPlatformInterface() -{ - ImGuiPlatformIO& platform_io = ImGui::GetPlatformIO(); - platform_io.Renderer_RenderWindow = ImGui_ImplOpenGL3_RenderWindow; -} - -static void ImGui_ImplOpenGL3_ShutdownPlatformInterface() -{ - ImGui::DestroyPlatformWindows(); -} - -//----------------------------------------------------------------------------- - -#if defined(__GNUC__) -#pragma GCC diagnostic pop -#endif -#if defined(__clang__) -#pragma clang diagnostic pop -#endif - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_opengl3.h b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_opengl3.h deleted file mode 100644 index ab779e0..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_opengl3.h +++ /dev/null @@ -1,67 +0,0 @@ -// dear imgui: Renderer Backend for modern OpenGL with shaders / programmatic pipeline -// - Desktop GL: 2.x 3.x 4.x -// - Embedded GL: ES 2.0 (WebGL 1.0), ES 3.0 (WebGL 2.0) -// This needs to be used along with a Platform Backend (e.g. GLFW, SDL, Win32, custom..) - -// Implemented features: -// [X] Renderer: User texture binding. Use 'GLuint' OpenGL texture identifier as void*/ImTextureID. Read the FAQ about ImTextureID! -// [X] Renderer: Large meshes support (64k+ vertices) with 16-bit indices (Desktop OpenGL only). -// [X] Renderer: Multi-viewport support (multiple windows). Enable with 'io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable'. - -// About WebGL/ES: -// - You need to '#define IMGUI_IMPL_OPENGL_ES2' or '#define IMGUI_IMPL_OPENGL_ES3' to use WebGL or OpenGL ES. -// - This is done automatically on iOS, Android and Emscripten targets. -// - For other targets, the define needs to be visible from the imgui_impl_opengl3.cpp compilation unit. If unsure, define globally or in imconfig.h. - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -// About GLSL version: -// The 'glsl_version' initialization parameter should be nullptr (default) or a "#version XXX" string. -// On computer platform the GLSL version default to "#version 130". On OpenGL ES 3 platform it defaults to "#version 300 es" -// Only override if your GL version doesn't handle this GLSL version. See GLSL version table at the top of imgui_impl_opengl3.cpp. - -#pragma once -#include "imgui.h" // IMGUI_IMPL_API -#ifndef IMGUI_DISABLE - -// Backend API -IMGUI_IMPL_API bool ImGui_ImplOpenGL3_Init(const char* glsl_version = nullptr); -IMGUI_IMPL_API void ImGui_ImplOpenGL3_Shutdown(); -IMGUI_IMPL_API void ImGui_ImplOpenGL3_NewFrame(); -IMGUI_IMPL_API void ImGui_ImplOpenGL3_RenderDrawData(ImDrawData* draw_data); - -// (Optional) Called by Init/NewFrame/Shutdown -IMGUI_IMPL_API bool ImGui_ImplOpenGL3_CreateFontsTexture(); -IMGUI_IMPL_API void ImGui_ImplOpenGL3_DestroyFontsTexture(); -IMGUI_IMPL_API bool ImGui_ImplOpenGL3_CreateDeviceObjects(); -IMGUI_IMPL_API void ImGui_ImplOpenGL3_DestroyDeviceObjects(); - -// Specific OpenGL ES versions -//#define IMGUI_IMPL_OPENGL_ES2 // Auto-detected on Emscripten -//#define IMGUI_IMPL_OPENGL_ES3 // Auto-detected on iOS/Android - -// You can explicitly select GLES2 or GLES3 API by using one of the '#define IMGUI_IMPL_OPENGL_LOADER_XXX' in imconfig.h or compiler command-line. -#if !defined(IMGUI_IMPL_OPENGL_ES2) \ - && !defined(IMGUI_IMPL_OPENGL_ES3) - -// Try to detect GLES on matching platforms -#if defined(__APPLE__) -#include -#endif -#if (defined(__APPLE__) && (TARGET_OS_IOS || TARGET_OS_TV)) || (defined(__ANDROID__)) -#define IMGUI_IMPL_OPENGL_ES3 // iOS, Android -> GL ES 3, "#version 300 es" -#elif defined(__EMSCRIPTEN__) || defined(__amigaos4__) -#define IMGUI_IMPL_OPENGL_ES2 // Emscripten -> GL ES 2, "#version 100" -#else -// Otherwise imgui_impl_opengl3_loader.h will be used. -#endif - -#endif - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_opengl3_loader.h b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_opengl3_loader.h deleted file mode 100644 index a077751..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_opengl3_loader.h +++ /dev/null @@ -1,809 +0,0 @@ -//----------------------------------------------------------------------------- -// About imgui_impl_opengl3_loader.h: -// -// We embed our own OpenGL loader to not require user to provide their own or to have to use ours, -// which proved to be endless problems for users. -// Our loader is custom-generated, based on gl3w but automatically filtered to only include -// enums/functions that we use in our imgui_impl_opengl3.cpp source file in order to be small. -// -// YOU SHOULD NOT NEED TO INCLUDE/USE THIS DIRECTLY. THIS IS USED BY imgui_impl_opengl3.cpp ONLY. -// THE REST OF YOUR APP SHOULD USE A DIFFERENT GL LOADER: ANY GL LOADER OF YOUR CHOICE. -// -// IF YOU GET BUILD ERRORS IN THIS FILE (commonly macro redefinitions or function redefinitions): -// IT LIKELY MEANS THAT YOU ARE BUILDING 'imgui_impl_opengl3.cpp' OR INCUDING 'imgui_impl_opengl3_loader.h' -// IN THE SAME COMPILATION UNIT AS ONE OF YOUR FILE WHICH IS USING A THIRD-PARTY OPENGL LOADER. -// (e.g. COULD HAPPEN IF YOU ARE DOING A UNITY/JUMBO BUILD, OR INCLUDING .CPP FILES FROM OTHERS) -// YOU SHOULD NOT BUILD BOTH IN THE SAME COMPILATION UNIT. -// BUT IF YOU REALLY WANT TO, you can '#define IMGUI_IMPL_OPENGL_LOADER_CUSTOM' and imgui_impl_opengl3.cpp -// WILL NOT BE USING OUR LOADER, AND INSTEAD EXPECT ANOTHER/YOUR LOADER TO BE AVAILABLE IN THE COMPILATION UNIT. -// -// Regenerate with: -// python gl3w_gen.py --output ../imgui/backends/imgui_impl_opengl3_loader.h --ref ../imgui/backends/imgui_impl_opengl3.cpp ./extra_symbols.txt -// -// More info: -// https://github.com/dearimgui/gl3w_stripped -// https://github.com/ocornut/imgui/issues/4445 -//----------------------------------------------------------------------------- - -/* - * This file was generated with gl3w_gen.py, part of imgl3w - * (hosted at https://github.com/dearimgui/gl3w_stripped) - * - * This is free and unencumbered software released into the public domain. - * - * Anyone is free to copy, modify, publish, use, compile, sell, or - * distribute this software, either in source code form or as a compiled - * binary, for any purpose, commercial or non-commercial, and by any - * means. - * - * In jurisdictions that recognize copyright laws, the author or authors - * of this software dedicate any and all copyright interest in the - * software to the public domain. We make this dedication for the benefit - * of the public at large and to the detriment of our heirs and - * successors. We intend this dedication to be an overt act of - * relinquishment in perpetuity of all present and future rights to this - * software under copyright law. - * - * 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 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 __gl3w_h_ -#define __gl3w_h_ - -// Adapted from KHR/khrplatform.h to avoid including entire file. -#ifndef __khrplatform_h_ -typedef float khronos_float_t; -typedef signed char khronos_int8_t; -typedef unsigned char khronos_uint8_t; -typedef signed short int khronos_int16_t; -typedef unsigned short int khronos_uint16_t; -#ifdef _WIN64 -typedef signed long long int khronos_intptr_t; -typedef signed long long int khronos_ssize_t; -#else -typedef signed long int khronos_intptr_t; -typedef signed long int khronos_ssize_t; -#endif - -#if defined(_MSC_VER) && !defined(__clang__) -typedef signed __int64 khronos_int64_t; -typedef unsigned __int64 khronos_uint64_t; -#elif (defined(__clang__) || defined(__GNUC__)) && (__cplusplus < 201100) -#include -typedef int64_t khronos_int64_t; -typedef uint64_t khronos_uint64_t; -#else -typedef signed long long khronos_int64_t; -typedef unsigned long long khronos_uint64_t; -#endif -#endif // __khrplatform_h_ - -#ifndef __gl_glcorearb_h_ -#define __gl_glcorearb_h_ 1 -#ifdef __cplusplus -extern "C" { -#endif -/* -** Copyright 2013-2020 The Khronos Group Inc. -** SPDX-License-Identifier: MIT -** -** This header is generated from the Khronos OpenGL / OpenGL ES XML -** API Registry. The current version of the Registry, generator scripts -** used to make the header, and the header can be found at -** https://github.com/KhronosGroup/OpenGL-Registry -*/ -#if defined(_WIN32) && !defined(APIENTRY) && !defined(__CYGWIN__) && !defined(__SCITECH_SNAP__) -#ifndef WIN32_LEAN_AND_MEAN -#define WIN32_LEAN_AND_MEAN 1 -#endif -#include -#endif -#ifndef APIENTRY -#define APIENTRY -#endif -#ifndef APIENTRYP -#define APIENTRYP APIENTRY * -#endif -#ifndef GLAPI -#define GLAPI extern -#endif -/* glcorearb.h is for use with OpenGL core profile implementations. -** It should should be placed in the same directory as gl.h and -** included as . -** -** glcorearb.h includes only APIs in the latest OpenGL core profile -** implementation together with APIs in newer ARB extensions which -** can be supported by the core profile. It does not, and never will -** include functionality removed from the core profile, such as -** fixed-function vertex and fragment processing. -** -** Do not #include both and either of or -** in the same source file. -*/ -/* Generated C header for: - * API: gl - * Profile: core - * Versions considered: .* - * Versions emitted: .* - * Default extensions included: glcore - * Additional extensions included: _nomatch_^ - * Extensions removed: _nomatch_^ - */ -#ifndef GL_VERSION_1_0 -typedef void GLvoid; -typedef unsigned int GLenum; - -typedef khronos_float_t GLfloat; -typedef int GLint; -typedef int GLsizei; -typedef unsigned int GLbitfield; -typedef double GLdouble; -typedef unsigned int GLuint; -typedef unsigned char GLboolean; -typedef khronos_uint8_t GLubyte; -#define GL_COLOR_BUFFER_BIT 0x00004000 -#define GL_FALSE 0 -#define GL_TRUE 1 -#define GL_TRIANGLES 0x0004 -#define GL_ONE 1 -#define GL_SRC_ALPHA 0x0302 -#define GL_ONE_MINUS_SRC_ALPHA 0x0303 -#define GL_FRONT 0x0404 -#define GL_BACK 0x0405 -#define GL_FRONT_AND_BACK 0x0408 -#define GL_POLYGON_MODE 0x0B40 -#define GL_CULL_FACE 0x0B44 -#define GL_DEPTH_TEST 0x0B71 -#define GL_STENCIL_TEST 0x0B90 -#define GL_VIEWPORT 0x0BA2 -#define GL_BLEND 0x0BE2 -#define GL_SCISSOR_BOX 0x0C10 -#define GL_SCISSOR_TEST 0x0C11 -#define GL_UNPACK_ROW_LENGTH 0x0CF2 -#define GL_PACK_ALIGNMENT 0x0D05 -#define GL_TEXTURE_2D 0x0DE1 -#define GL_UNSIGNED_BYTE 0x1401 -#define GL_UNSIGNED_SHORT 0x1403 -#define GL_UNSIGNED_INT 0x1405 -#define GL_FLOAT 0x1406 -#define GL_RGBA 0x1908 -#define GL_FILL 0x1B02 -#define GL_VENDOR 0x1F00 -#define GL_RENDERER 0x1F01 -#define GL_VERSION 0x1F02 -#define GL_EXTENSIONS 0x1F03 -#define GL_LINEAR 0x2601 -#define GL_TEXTURE_MAG_FILTER 0x2800 -#define GL_TEXTURE_MIN_FILTER 0x2801 -typedef void (APIENTRYP PFNGLPOLYGONMODEPROC) (GLenum face, GLenum mode); -typedef void (APIENTRYP PFNGLSCISSORPROC) (GLint x, GLint y, GLsizei width, GLsizei height); -typedef void (APIENTRYP PFNGLTEXPARAMETERIPROC) (GLenum target, GLenum pname, GLint param); -typedef void (APIENTRYP PFNGLTEXIMAGE2DPROC) (GLenum target, GLint level, GLint internalformat, GLsizei width, GLsizei height, GLint border, GLenum format, GLenum type, const void *pixels); -typedef void (APIENTRYP PFNGLCLEARPROC) (GLbitfield mask); -typedef void (APIENTRYP PFNGLCLEARCOLORPROC) (GLfloat red, GLfloat green, GLfloat blue, GLfloat alpha); -typedef void (APIENTRYP PFNGLDISABLEPROC) (GLenum cap); -typedef void (APIENTRYP PFNGLENABLEPROC) (GLenum cap); -typedef void (APIENTRYP PFNGLFLUSHPROC) (void); -typedef void (APIENTRYP PFNGLPIXELSTOREIPROC) (GLenum pname, GLint param); -typedef void (APIENTRYP PFNGLREADPIXELSPROC) (GLint x, GLint y, GLsizei width, GLsizei height, GLenum format, GLenum type, void *pixels); -typedef GLenum (APIENTRYP PFNGLGETERRORPROC) (void); -typedef void (APIENTRYP PFNGLGETINTEGERVPROC) (GLenum pname, GLint *data); -typedef const GLubyte *(APIENTRYP PFNGLGETSTRINGPROC) (GLenum name); -typedef GLboolean (APIENTRYP PFNGLISENABLEDPROC) (GLenum cap); -typedef void (APIENTRYP PFNGLVIEWPORTPROC) (GLint x, GLint y, GLsizei width, GLsizei height); -#ifdef GL_GLEXT_PROTOTYPES -GLAPI void APIENTRY glPolygonMode (GLenum face, GLenum mode); -GLAPI void APIENTRY glScissor (GLint x, GLint y, GLsizei width, GLsizei height); -GLAPI void APIENTRY glTexParameteri (GLenum target, GLenum pname, GLint param); -GLAPI void APIENTRY glTexImage2D (GLenum target, GLint level, GLint internalformat, GLsizei width, GLsizei height, GLint border, GLenum format, GLenum type, const void *pixels); -GLAPI void APIENTRY glClear (GLbitfield mask); -GLAPI void APIENTRY glClearColor (GLfloat red, GLfloat green, GLfloat blue, GLfloat alpha); -GLAPI void APIENTRY glDisable (GLenum cap); -GLAPI void APIENTRY glEnable (GLenum cap); -GLAPI void APIENTRY glFlush (void); -GLAPI void APIENTRY glPixelStorei (GLenum pname, GLint param); -GLAPI void APIENTRY glReadPixels (GLint x, GLint y, GLsizei width, GLsizei height, GLenum format, GLenum type, void *pixels); -GLAPI GLenum APIENTRY glGetError (void); -GLAPI void APIENTRY glGetIntegerv (GLenum pname, GLint *data); -GLAPI const GLubyte *APIENTRY glGetString (GLenum name); -GLAPI GLboolean APIENTRY glIsEnabled (GLenum cap); -GLAPI void APIENTRY glViewport (GLint x, GLint y, GLsizei width, GLsizei height); -#endif -#endif /* GL_VERSION_1_0 */ -#ifndef GL_VERSION_1_1 -typedef khronos_float_t GLclampf; -typedef double GLclampd; -#define GL_TEXTURE_BINDING_2D 0x8069 -typedef void (APIENTRYP PFNGLDRAWELEMENTSPROC) (GLenum mode, GLsizei count, GLenum type, const void *indices); -typedef void (APIENTRYP PFNGLBINDTEXTUREPROC) (GLenum target, GLuint texture); -typedef void (APIENTRYP PFNGLDELETETEXTURESPROC) (GLsizei n, const GLuint *textures); -typedef void (APIENTRYP PFNGLGENTEXTURESPROC) (GLsizei n, GLuint *textures); -#ifdef GL_GLEXT_PROTOTYPES -GLAPI void APIENTRY glDrawElements (GLenum mode, GLsizei count, GLenum type, const void *indices); -GLAPI void APIENTRY glBindTexture (GLenum target, GLuint texture); -GLAPI void APIENTRY glDeleteTextures (GLsizei n, const GLuint *textures); -GLAPI void APIENTRY glGenTextures (GLsizei n, GLuint *textures); -#endif -#endif /* GL_VERSION_1_1 */ -#ifndef GL_VERSION_1_3 -#define GL_TEXTURE0 0x84C0 -#define GL_ACTIVE_TEXTURE 0x84E0 -typedef void (APIENTRYP PFNGLACTIVETEXTUREPROC) (GLenum texture); -#ifdef GL_GLEXT_PROTOTYPES -GLAPI void APIENTRY glActiveTexture (GLenum texture); -#endif -#endif /* GL_VERSION_1_3 */ -#ifndef GL_VERSION_1_4 -#define GL_BLEND_DST_RGB 0x80C8 -#define GL_BLEND_SRC_RGB 0x80C9 -#define GL_BLEND_DST_ALPHA 0x80CA -#define GL_BLEND_SRC_ALPHA 0x80CB -#define GL_FUNC_ADD 0x8006 -typedef void (APIENTRYP PFNGLBLENDFUNCSEPARATEPROC) (GLenum sfactorRGB, GLenum dfactorRGB, GLenum sfactorAlpha, GLenum dfactorAlpha); -typedef void (APIENTRYP PFNGLBLENDEQUATIONPROC) (GLenum mode); -#ifdef GL_GLEXT_PROTOTYPES -GLAPI void APIENTRY glBlendFuncSeparate (GLenum sfactorRGB, GLenum dfactorRGB, GLenum sfactorAlpha, GLenum dfactorAlpha); -GLAPI void APIENTRY glBlendEquation (GLenum mode); -#endif -#endif /* GL_VERSION_1_4 */ -#ifndef GL_VERSION_1_5 -typedef khronos_ssize_t GLsizeiptr; -typedef khronos_intptr_t GLintptr; -#define GL_ARRAY_BUFFER 0x8892 -#define GL_ELEMENT_ARRAY_BUFFER 0x8893 -#define GL_ARRAY_BUFFER_BINDING 0x8894 -#define GL_ELEMENT_ARRAY_BUFFER_BINDING 0x8895 -#define GL_STREAM_DRAW 0x88E0 -typedef void (APIENTRYP PFNGLBINDBUFFERPROC) (GLenum target, GLuint buffer); -typedef void (APIENTRYP PFNGLDELETEBUFFERSPROC) (GLsizei n, const GLuint *buffers); -typedef void (APIENTRYP PFNGLGENBUFFERSPROC) (GLsizei n, GLuint *buffers); -typedef void (APIENTRYP PFNGLBUFFERDATAPROC) (GLenum target, GLsizeiptr size, const void *data, GLenum usage); -typedef void (APIENTRYP PFNGLBUFFERSUBDATAPROC) (GLenum target, GLintptr offset, GLsizeiptr size, const void *data); -#ifdef GL_GLEXT_PROTOTYPES -GLAPI void APIENTRY glBindBuffer (GLenum target, GLuint buffer); -GLAPI void APIENTRY glDeleteBuffers (GLsizei n, const GLuint *buffers); -GLAPI void APIENTRY glGenBuffers (GLsizei n, GLuint *buffers); -GLAPI void APIENTRY glBufferData (GLenum target, GLsizeiptr size, const void *data, GLenum usage); -GLAPI void APIENTRY glBufferSubData (GLenum target, GLintptr offset, GLsizeiptr size, const void *data); -#endif -#endif /* GL_VERSION_1_5 */ -#ifndef GL_VERSION_2_0 -typedef char GLchar; -typedef khronos_int16_t GLshort; -typedef khronos_int8_t GLbyte; -typedef khronos_uint16_t GLushort; -#define GL_BLEND_EQUATION_RGB 0x8009 -#define GL_VERTEX_ATTRIB_ARRAY_ENABLED 0x8622 -#define GL_VERTEX_ATTRIB_ARRAY_SIZE 0x8623 -#define GL_VERTEX_ATTRIB_ARRAY_STRIDE 0x8624 -#define GL_VERTEX_ATTRIB_ARRAY_TYPE 0x8625 -#define GL_VERTEX_ATTRIB_ARRAY_POINTER 0x8645 -#define GL_BLEND_EQUATION_ALPHA 0x883D -#define GL_VERTEX_ATTRIB_ARRAY_NORMALIZED 0x886A -#define GL_FRAGMENT_SHADER 0x8B30 -#define GL_VERTEX_SHADER 0x8B31 -#define GL_COMPILE_STATUS 0x8B81 -#define GL_LINK_STATUS 0x8B82 -#define GL_INFO_LOG_LENGTH 0x8B84 -#define GL_CURRENT_PROGRAM 0x8B8D -#define GL_UPPER_LEFT 0x8CA2 -typedef void (APIENTRYP PFNGLBLENDEQUATIONSEPARATEPROC) (GLenum modeRGB, GLenum modeAlpha); -typedef void (APIENTRYP PFNGLATTACHSHADERPROC) (GLuint program, GLuint shader); -typedef void (APIENTRYP PFNGLCOMPILESHADERPROC) (GLuint shader); -typedef GLuint (APIENTRYP PFNGLCREATEPROGRAMPROC) (void); -typedef GLuint (APIENTRYP PFNGLCREATESHADERPROC) (GLenum type); -typedef void (APIENTRYP PFNGLDELETEPROGRAMPROC) (GLuint program); -typedef void (APIENTRYP PFNGLDELETESHADERPROC) (GLuint shader); -typedef void (APIENTRYP PFNGLDETACHSHADERPROC) (GLuint program, GLuint shader); -typedef void (APIENTRYP PFNGLDISABLEVERTEXATTRIBARRAYPROC) (GLuint index); -typedef void (APIENTRYP PFNGLENABLEVERTEXATTRIBARRAYPROC) (GLuint index); -typedef GLint (APIENTRYP PFNGLGETATTRIBLOCATIONPROC) (GLuint program, const GLchar *name); -typedef void (APIENTRYP PFNGLGETPROGRAMIVPROC) (GLuint program, GLenum pname, GLint *params); -typedef void (APIENTRYP PFNGLGETPROGRAMINFOLOGPROC) (GLuint program, GLsizei bufSize, GLsizei *length, GLchar *infoLog); -typedef void (APIENTRYP PFNGLGETSHADERIVPROC) (GLuint shader, GLenum pname, GLint *params); -typedef void (APIENTRYP PFNGLGETSHADERINFOLOGPROC) (GLuint shader, GLsizei bufSize, GLsizei *length, GLchar *infoLog); -typedef GLint (APIENTRYP PFNGLGETUNIFORMLOCATIONPROC) (GLuint program, const GLchar *name); -typedef void (APIENTRYP PFNGLGETVERTEXATTRIBIVPROC) (GLuint index, GLenum pname, GLint *params); -typedef void (APIENTRYP PFNGLGETVERTEXATTRIBPOINTERVPROC) (GLuint index, GLenum pname, void **pointer); -typedef GLboolean (APIENTRYP PFNGLISPROGRAMPROC) (GLuint program); -typedef void (APIENTRYP PFNGLLINKPROGRAMPROC) (GLuint program); -typedef void (APIENTRYP PFNGLSHADERSOURCEPROC) (GLuint shader, GLsizei count, const GLchar *const*string, const GLint *length); -typedef void (APIENTRYP PFNGLUSEPROGRAMPROC) (GLuint program); -typedef void (APIENTRYP PFNGLUNIFORM1IPROC) (GLint location, GLint v0); -typedef void (APIENTRYP PFNGLUNIFORMMATRIX4FVPROC) (GLint location, GLsizei count, GLboolean transpose, const GLfloat *value); -typedef void (APIENTRYP PFNGLVERTEXATTRIBPOINTERPROC) (GLuint index, GLint size, GLenum type, GLboolean normalized, GLsizei stride, const void *pointer); -#ifdef GL_GLEXT_PROTOTYPES -GLAPI void APIENTRY glBlendEquationSeparate (GLenum modeRGB, GLenum modeAlpha); -GLAPI void APIENTRY glAttachShader (GLuint program, GLuint shader); -GLAPI void APIENTRY glCompileShader (GLuint shader); -GLAPI GLuint APIENTRY glCreateProgram (void); -GLAPI GLuint APIENTRY glCreateShader (GLenum type); -GLAPI void APIENTRY glDeleteProgram (GLuint program); -GLAPI void APIENTRY glDeleteShader (GLuint shader); -GLAPI void APIENTRY glDetachShader (GLuint program, GLuint shader); -GLAPI void APIENTRY glDisableVertexAttribArray (GLuint index); -GLAPI void APIENTRY glEnableVertexAttribArray (GLuint index); -GLAPI GLint APIENTRY glGetAttribLocation (GLuint program, const GLchar *name); -GLAPI void APIENTRY glGetProgramiv (GLuint program, GLenum pname, GLint *params); -GLAPI void APIENTRY glGetProgramInfoLog (GLuint program, GLsizei bufSize, GLsizei *length, GLchar *infoLog); -GLAPI void APIENTRY glGetShaderiv (GLuint shader, GLenum pname, GLint *params); -GLAPI void APIENTRY glGetShaderInfoLog (GLuint shader, GLsizei bufSize, GLsizei *length, GLchar *infoLog); -GLAPI GLint APIENTRY glGetUniformLocation (GLuint program, const GLchar *name); -GLAPI void APIENTRY glGetVertexAttribiv (GLuint index, GLenum pname, GLint *params); -GLAPI void APIENTRY glGetVertexAttribPointerv (GLuint index, GLenum pname, void **pointer); -GLAPI GLboolean APIENTRY glIsProgram (GLuint program); -GLAPI void APIENTRY glLinkProgram (GLuint program); -GLAPI void APIENTRY glShaderSource (GLuint shader, GLsizei count, const GLchar *const*string, const GLint *length); -GLAPI void APIENTRY glUseProgram (GLuint program); -GLAPI void APIENTRY glUniform1i (GLint location, GLint v0); -GLAPI void APIENTRY glUniformMatrix4fv (GLint location, GLsizei count, GLboolean transpose, const GLfloat *value); -GLAPI void APIENTRY glVertexAttribPointer (GLuint index, GLint size, GLenum type, GLboolean normalized, GLsizei stride, const void *pointer); -#endif -#endif /* GL_VERSION_2_0 */ -#ifndef GL_VERSION_3_0 -typedef khronos_uint16_t GLhalf; -#define GL_MAJOR_VERSION 0x821B -#define GL_MINOR_VERSION 0x821C -#define GL_NUM_EXTENSIONS 0x821D -#define GL_FRAMEBUFFER_SRGB 0x8DB9 -#define GL_VERTEX_ARRAY_BINDING 0x85B5 -typedef void (APIENTRYP PFNGLGETBOOLEANI_VPROC) (GLenum target, GLuint index, GLboolean *data); -typedef void (APIENTRYP PFNGLGETINTEGERI_VPROC) (GLenum target, GLuint index, GLint *data); -typedef const GLubyte *(APIENTRYP PFNGLGETSTRINGIPROC) (GLenum name, GLuint index); -typedef void (APIENTRYP PFNGLBINDVERTEXARRAYPROC) (GLuint array); -typedef void (APIENTRYP PFNGLDELETEVERTEXARRAYSPROC) (GLsizei n, const GLuint *arrays); -typedef void (APIENTRYP PFNGLGENVERTEXARRAYSPROC) (GLsizei n, GLuint *arrays); -#ifdef GL_GLEXT_PROTOTYPES -GLAPI const GLubyte *APIENTRY glGetStringi (GLenum name, GLuint index); -GLAPI void APIENTRY glBindVertexArray (GLuint array); -GLAPI void APIENTRY glDeleteVertexArrays (GLsizei n, const GLuint *arrays); -GLAPI void APIENTRY glGenVertexArrays (GLsizei n, GLuint *arrays); -#endif -#endif /* GL_VERSION_3_0 */ -#ifndef GL_VERSION_3_1 -#define GL_VERSION_3_1 1 -#define GL_PRIMITIVE_RESTART 0x8F9D -#endif /* GL_VERSION_3_1 */ -#ifndef GL_VERSION_3_2 -#define GL_VERSION_3_2 1 -typedef struct __GLsync *GLsync; -typedef khronos_uint64_t GLuint64; -typedef khronos_int64_t GLint64; -#define GL_CONTEXT_COMPATIBILITY_PROFILE_BIT 0x00000002 -#define GL_CONTEXT_PROFILE_MASK 0x9126 -typedef void (APIENTRYP PFNGLDRAWELEMENTSBASEVERTEXPROC) (GLenum mode, GLsizei count, GLenum type, const void *indices, GLint basevertex); -typedef void (APIENTRYP PFNGLGETINTEGER64I_VPROC) (GLenum target, GLuint index, GLint64 *data); -#ifdef GL_GLEXT_PROTOTYPES -GLAPI void APIENTRY glDrawElementsBaseVertex (GLenum mode, GLsizei count, GLenum type, const void *indices, GLint basevertex); -#endif -#endif /* GL_VERSION_3_2 */ -#ifndef GL_VERSION_3_3 -#define GL_VERSION_3_3 1 -#define GL_SAMPLER_BINDING 0x8919 -typedef void (APIENTRYP PFNGLBINDSAMPLERPROC) (GLuint unit, GLuint sampler); -#ifdef GL_GLEXT_PROTOTYPES -GLAPI void APIENTRY glBindSampler (GLuint unit, GLuint sampler); -#endif -#endif /* GL_VERSION_3_3 */ -#ifndef GL_VERSION_4_1 -typedef void (APIENTRYP PFNGLGETFLOATI_VPROC) (GLenum target, GLuint index, GLfloat *data); -typedef void (APIENTRYP PFNGLGETDOUBLEI_VPROC) (GLenum target, GLuint index, GLdouble *data); -#endif /* GL_VERSION_4_1 */ -#ifndef GL_VERSION_4_3 -typedef void (APIENTRY *GLDEBUGPROC)(GLenum source,GLenum type,GLuint id,GLenum severity,GLsizei length,const GLchar *message,const void *userParam); -#endif /* GL_VERSION_4_3 */ -#ifndef GL_VERSION_4_5 -#define GL_CLIP_ORIGIN 0x935C -typedef void (APIENTRYP PFNGLGETTRANSFORMFEEDBACKI_VPROC) (GLuint xfb, GLenum pname, GLuint index, GLint *param); -typedef void (APIENTRYP PFNGLGETTRANSFORMFEEDBACKI64_VPROC) (GLuint xfb, GLenum pname, GLuint index, GLint64 *param); -#endif /* GL_VERSION_4_5 */ -#ifndef GL_ARB_bindless_texture -typedef khronos_uint64_t GLuint64EXT; -#endif /* GL_ARB_bindless_texture */ -#ifndef GL_ARB_cl_event -struct _cl_context; -struct _cl_event; -#endif /* GL_ARB_cl_event */ -#ifndef GL_ARB_clip_control -#define GL_ARB_clip_control 1 -#endif /* GL_ARB_clip_control */ -#ifndef GL_ARB_debug_output -typedef void (APIENTRY *GLDEBUGPROCARB)(GLenum source,GLenum type,GLuint id,GLenum severity,GLsizei length,const GLchar *message,const void *userParam); -#endif /* GL_ARB_debug_output */ -#ifndef GL_EXT_EGL_image_storage -typedef void *GLeglImageOES; -#endif /* GL_EXT_EGL_image_storage */ -#ifndef GL_EXT_direct_state_access -typedef void (APIENTRYP PFNGLGETFLOATI_VEXTPROC) (GLenum pname, GLuint index, GLfloat *params); -typedef void (APIENTRYP PFNGLGETDOUBLEI_VEXTPROC) (GLenum pname, GLuint index, GLdouble *params); -typedef void (APIENTRYP PFNGLGETPOINTERI_VEXTPROC) (GLenum pname, GLuint index, void **params); -typedef void (APIENTRYP PFNGLGETVERTEXARRAYINTEGERI_VEXTPROC) (GLuint vaobj, GLuint index, GLenum pname, GLint *param); -typedef void (APIENTRYP PFNGLGETVERTEXARRAYPOINTERI_VEXTPROC) (GLuint vaobj, GLuint index, GLenum pname, void **param); -#endif /* GL_EXT_direct_state_access */ -#ifndef GL_NV_draw_vulkan_image -typedef void (APIENTRY *GLVULKANPROCNV)(void); -#endif /* GL_NV_draw_vulkan_image */ -#ifndef GL_NV_gpu_shader5 -typedef khronos_int64_t GLint64EXT; -#endif /* GL_NV_gpu_shader5 */ -#ifndef GL_NV_vertex_buffer_unified_memory -typedef void (APIENTRYP PFNGLGETINTEGERUI64I_VNVPROC) (GLenum value, GLuint index, GLuint64EXT *result); -#endif /* GL_NV_vertex_buffer_unified_memory */ -#ifdef __cplusplus -} -#endif -#endif - -#ifndef GL3W_API -#define GL3W_API -#endif - -#ifndef __gl_h_ -#define __gl_h_ -#endif - -#ifdef __cplusplus -extern "C" { -#endif - -#define GL3W_OK 0 -#define GL3W_ERROR_INIT -1 -#define GL3W_ERROR_LIBRARY_OPEN -2 -#define GL3W_ERROR_OPENGL_VERSION -3 - -typedef void (*GL3WglProc)(void); -typedef GL3WglProc (*GL3WGetProcAddressProc)(const char *proc); - -/* gl3w api */ -GL3W_API int imgl3wInit(void); -GL3W_API int imgl3wInit2(GL3WGetProcAddressProc proc); -GL3W_API int imgl3wIsSupported(int major, int minor); -GL3W_API GL3WglProc imgl3wGetProcAddress(const char *proc); - -/* gl3w internal state */ -union ImGL3WProcs { - GL3WglProc ptr[59]; - struct { - PFNGLACTIVETEXTUREPROC ActiveTexture; - PFNGLATTACHSHADERPROC AttachShader; - PFNGLBINDBUFFERPROC BindBuffer; - PFNGLBINDSAMPLERPROC BindSampler; - PFNGLBINDTEXTUREPROC BindTexture; - PFNGLBINDVERTEXARRAYPROC BindVertexArray; - PFNGLBLENDEQUATIONPROC BlendEquation; - PFNGLBLENDEQUATIONSEPARATEPROC BlendEquationSeparate; - PFNGLBLENDFUNCSEPARATEPROC BlendFuncSeparate; - PFNGLBUFFERDATAPROC BufferData; - PFNGLBUFFERSUBDATAPROC BufferSubData; - PFNGLCLEARPROC Clear; - PFNGLCLEARCOLORPROC ClearColor; - PFNGLCOMPILESHADERPROC CompileShader; - PFNGLCREATEPROGRAMPROC CreateProgram; - PFNGLCREATESHADERPROC CreateShader; - PFNGLDELETEBUFFERSPROC DeleteBuffers; - PFNGLDELETEPROGRAMPROC DeleteProgram; - PFNGLDELETESHADERPROC DeleteShader; - PFNGLDELETETEXTURESPROC DeleteTextures; - PFNGLDELETEVERTEXARRAYSPROC DeleteVertexArrays; - PFNGLDETACHSHADERPROC DetachShader; - PFNGLDISABLEPROC Disable; - PFNGLDISABLEVERTEXATTRIBARRAYPROC DisableVertexAttribArray; - PFNGLDRAWELEMENTSPROC DrawElements; - PFNGLDRAWELEMENTSBASEVERTEXPROC DrawElementsBaseVertex; - PFNGLENABLEPROC Enable; - PFNGLENABLEVERTEXATTRIBARRAYPROC EnableVertexAttribArray; - PFNGLFLUSHPROC Flush; - PFNGLGENBUFFERSPROC GenBuffers; - PFNGLGENTEXTURESPROC GenTextures; - PFNGLGENVERTEXARRAYSPROC GenVertexArrays; - PFNGLGETATTRIBLOCATIONPROC GetAttribLocation; - PFNGLGETERRORPROC GetError; - PFNGLGETINTEGERVPROC GetIntegerv; - PFNGLGETPROGRAMINFOLOGPROC GetProgramInfoLog; - PFNGLGETPROGRAMIVPROC GetProgramiv; - PFNGLGETSHADERINFOLOGPROC GetShaderInfoLog; - PFNGLGETSHADERIVPROC GetShaderiv; - PFNGLGETSTRINGPROC GetString; - PFNGLGETSTRINGIPROC GetStringi; - PFNGLGETUNIFORMLOCATIONPROC GetUniformLocation; - PFNGLGETVERTEXATTRIBPOINTERVPROC GetVertexAttribPointerv; - PFNGLGETVERTEXATTRIBIVPROC GetVertexAttribiv; - PFNGLISENABLEDPROC IsEnabled; - PFNGLISPROGRAMPROC IsProgram; - PFNGLLINKPROGRAMPROC LinkProgram; - PFNGLPIXELSTOREIPROC PixelStorei; - PFNGLPOLYGONMODEPROC PolygonMode; - PFNGLREADPIXELSPROC ReadPixels; - PFNGLSCISSORPROC Scissor; - PFNGLSHADERSOURCEPROC ShaderSource; - PFNGLTEXIMAGE2DPROC TexImage2D; - PFNGLTEXPARAMETERIPROC TexParameteri; - PFNGLUNIFORM1IPROC Uniform1i; - PFNGLUNIFORMMATRIX4FVPROC UniformMatrix4fv; - PFNGLUSEPROGRAMPROC UseProgram; - PFNGLVERTEXATTRIBPOINTERPROC VertexAttribPointer; - PFNGLVIEWPORTPROC Viewport; - } gl; -}; - -GL3W_API extern union ImGL3WProcs imgl3wProcs; - -/* OpenGL functions */ -#define glActiveTexture imgl3wProcs.gl.ActiveTexture -#define glAttachShader imgl3wProcs.gl.AttachShader -#define glBindBuffer imgl3wProcs.gl.BindBuffer -#define glBindSampler imgl3wProcs.gl.BindSampler -#define glBindTexture imgl3wProcs.gl.BindTexture -#define glBindVertexArray imgl3wProcs.gl.BindVertexArray -#define glBlendEquation imgl3wProcs.gl.BlendEquation -#define glBlendEquationSeparate imgl3wProcs.gl.BlendEquationSeparate -#define glBlendFuncSeparate imgl3wProcs.gl.BlendFuncSeparate -#define glBufferData imgl3wProcs.gl.BufferData -#define glBufferSubData imgl3wProcs.gl.BufferSubData -#define glClear imgl3wProcs.gl.Clear -#define glClearColor imgl3wProcs.gl.ClearColor -#define glCompileShader imgl3wProcs.gl.CompileShader -#define glCreateProgram imgl3wProcs.gl.CreateProgram -#define glCreateShader imgl3wProcs.gl.CreateShader -#define glDeleteBuffers imgl3wProcs.gl.DeleteBuffers -#define glDeleteProgram imgl3wProcs.gl.DeleteProgram -#define glDeleteShader imgl3wProcs.gl.DeleteShader -#define glDeleteTextures imgl3wProcs.gl.DeleteTextures -#define glDeleteVertexArrays imgl3wProcs.gl.DeleteVertexArrays -#define glDetachShader imgl3wProcs.gl.DetachShader -#define glDisable imgl3wProcs.gl.Disable -#define glDisableVertexAttribArray imgl3wProcs.gl.DisableVertexAttribArray -#define glDrawElements imgl3wProcs.gl.DrawElements -#define glDrawElementsBaseVertex imgl3wProcs.gl.DrawElementsBaseVertex -#define glEnable imgl3wProcs.gl.Enable -#define glEnableVertexAttribArray imgl3wProcs.gl.EnableVertexAttribArray -#define glFlush imgl3wProcs.gl.Flush -#define glGenBuffers imgl3wProcs.gl.GenBuffers -#define glGenTextures imgl3wProcs.gl.GenTextures -#define glGenVertexArrays imgl3wProcs.gl.GenVertexArrays -#define glGetAttribLocation imgl3wProcs.gl.GetAttribLocation -#define glGetError imgl3wProcs.gl.GetError -#define glGetIntegerv imgl3wProcs.gl.GetIntegerv -#define glGetProgramInfoLog imgl3wProcs.gl.GetProgramInfoLog -#define glGetProgramiv imgl3wProcs.gl.GetProgramiv -#define glGetShaderInfoLog imgl3wProcs.gl.GetShaderInfoLog -#define glGetShaderiv imgl3wProcs.gl.GetShaderiv -#define glGetString imgl3wProcs.gl.GetString -#define glGetStringi imgl3wProcs.gl.GetStringi -#define glGetUniformLocation imgl3wProcs.gl.GetUniformLocation -#define glGetVertexAttribPointerv imgl3wProcs.gl.GetVertexAttribPointerv -#define glGetVertexAttribiv imgl3wProcs.gl.GetVertexAttribiv -#define glIsEnabled imgl3wProcs.gl.IsEnabled -#define glIsProgram imgl3wProcs.gl.IsProgram -#define glLinkProgram imgl3wProcs.gl.LinkProgram -#define glPixelStorei imgl3wProcs.gl.PixelStorei -#define glPolygonMode imgl3wProcs.gl.PolygonMode -#define glReadPixels imgl3wProcs.gl.ReadPixels -#define glScissor imgl3wProcs.gl.Scissor -#define glShaderSource imgl3wProcs.gl.ShaderSource -#define glTexImage2D imgl3wProcs.gl.TexImage2D -#define glTexParameteri imgl3wProcs.gl.TexParameteri -#define glUniform1i imgl3wProcs.gl.Uniform1i -#define glUniformMatrix4fv imgl3wProcs.gl.UniformMatrix4fv -#define glUseProgram imgl3wProcs.gl.UseProgram -#define glVertexAttribPointer imgl3wProcs.gl.VertexAttribPointer -#define glViewport imgl3wProcs.gl.Viewport - -#ifdef __cplusplus -} -#endif - -#endif - -#ifdef IMGL3W_IMPL -#ifdef __cplusplus -extern "C" { -#endif - -#include - -#define ARRAY_SIZE(x) (sizeof(x) / sizeof((x)[0])) - -#if defined(_WIN32) -#ifndef WIN32_LEAN_AND_MEAN -#define WIN32_LEAN_AND_MEAN 1 -#endif -#include - -static HMODULE libgl; -typedef PROC(__stdcall* GL3WglGetProcAddr)(LPCSTR); -static GL3WglGetProcAddr wgl_get_proc_address; - -static int open_libgl(void) -{ - libgl = LoadLibraryA("opengl32.dll"); - if (!libgl) - return GL3W_ERROR_LIBRARY_OPEN; - wgl_get_proc_address = (GL3WglGetProcAddr)GetProcAddress(libgl, "wglGetProcAddress"); - return GL3W_OK; -} - -static void close_libgl(void) { FreeLibrary(libgl); } -static GL3WglProc get_proc(const char *proc) -{ - GL3WglProc res; - res = (GL3WglProc)wgl_get_proc_address(proc); - if (!res) - res = (GL3WglProc)GetProcAddress(libgl, proc); - return res; -} -#elif defined(__APPLE__) -#include - -static void *libgl; -static int open_libgl(void) -{ - libgl = dlopen("/System/Library/Frameworks/OpenGL.framework/OpenGL", RTLD_LAZY | RTLD_LOCAL); - if (!libgl) - return GL3W_ERROR_LIBRARY_OPEN; - return GL3W_OK; -} - -static void close_libgl(void) { dlclose(libgl); } - -static GL3WglProc get_proc(const char *proc) -{ - GL3WglProc res; - *(void **)(&res) = dlsym(libgl, proc); - return res; -} -#else -#include - -static void *libgl; -static GL3WglProc (*glx_get_proc_address)(const GLubyte *); - -static int open_libgl(void) -{ - libgl = dlopen("libGL.so.1", RTLD_LAZY | RTLD_LOCAL); - if (!libgl) - return GL3W_ERROR_LIBRARY_OPEN; - *(void **)(&glx_get_proc_address) = dlsym(libgl, "glXGetProcAddressARB"); - return GL3W_OK; -} - -static void close_libgl(void) { dlclose(libgl); } - -static GL3WglProc get_proc(const char *proc) -{ - GL3WglProc res; - res = glx_get_proc_address((const GLubyte *)proc); - if (!res) - *(void **)(&res) = dlsym(libgl, proc); - return res; -} -#endif - -static struct { int major, minor; } version; - -static int parse_version(void) -{ - if (!glGetIntegerv) - return GL3W_ERROR_INIT; - glGetIntegerv(GL_MAJOR_VERSION, &version.major); - glGetIntegerv(GL_MINOR_VERSION, &version.minor); - if (version.major == 0 && version.minor == 0) - { - // Query GL_VERSION in desktop GL 2.x, the string will start with "." - if (const char* gl_version = (const char*)glGetString(GL_VERSION)) - sscanf(gl_version, "%d.%d", &version.major, &version.minor); - } - if (version.major < 2) - return GL3W_ERROR_OPENGL_VERSION; - return GL3W_OK; -} - -static void load_procs(GL3WGetProcAddressProc proc); - -int imgl3wInit(void) -{ - int res = open_libgl(); - if (res) - return res; - atexit(close_libgl); - return imgl3wInit2(get_proc); -} - -int imgl3wInit2(GL3WGetProcAddressProc proc) -{ - load_procs(proc); - return parse_version(); -} - -int imgl3wIsSupported(int major, int minor) -{ - if (major < 2) - return 0; - if (version.major == major) - return version.minor >= minor; - return version.major >= major; -} - -GL3WglProc imgl3wGetProcAddress(const char *proc) { return get_proc(proc); } - -static const char *proc_names[] = { - "glActiveTexture", - "glAttachShader", - "glBindBuffer", - "glBindSampler", - "glBindTexture", - "glBindVertexArray", - "glBlendEquation", - "glBlendEquationSeparate", - "glBlendFuncSeparate", - "glBufferData", - "glBufferSubData", - "glClear", - "glClearColor", - "glCompileShader", - "glCreateProgram", - "glCreateShader", - "glDeleteBuffers", - "glDeleteProgram", - "glDeleteShader", - "glDeleteTextures", - "glDeleteVertexArrays", - "glDetachShader", - "glDisable", - "glDisableVertexAttribArray", - "glDrawElements", - "glDrawElementsBaseVertex", - "glEnable", - "glEnableVertexAttribArray", - "glFlush", - "glGenBuffers", - "glGenTextures", - "glGenVertexArrays", - "glGetAttribLocation", - "glGetError", - "glGetIntegerv", - "glGetProgramInfoLog", - "glGetProgramiv", - "glGetShaderInfoLog", - "glGetShaderiv", - "glGetString", - "glGetStringi", - "glGetUniformLocation", - "glGetVertexAttribPointerv", - "glGetVertexAttribiv", - "glIsEnabled", - "glIsProgram", - "glLinkProgram", - "glPixelStorei", - "glPolygonMode", - "glReadPixels", - "glScissor", - "glShaderSource", - "glTexImage2D", - "glTexParameteri", - "glUniform1i", - "glUniformMatrix4fv", - "glUseProgram", - "glVertexAttribPointer", - "glViewport", -}; - -GL3W_API union ImGL3WProcs imgl3wProcs; - -static void load_procs(GL3WGetProcAddressProc proc) -{ - size_t i; - for (i = 0; i < ARRAY_SIZE(proc_names); i++) - imgl3wProcs.ptr[i] = proc(proc_names[i]); -} - -#ifdef __cplusplus -} -#endif -#endif diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_osx.h b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_osx.h deleted file mode 100644 index 360317f..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_osx.h +++ /dev/null @@ -1,52 +0,0 @@ -// dear imgui: Platform Backend for OSX / Cocoa -// This needs to be used along with a Renderer (e.g. OpenGL2, OpenGL3, Vulkan, Metal..) -// - Not well tested. If you want a portable application, prefer using the GLFW or SDL platform Backends on Mac. -// - Requires linking with the GameController framework ("-framework GameController"). - -// Implemented features: -// [X] Platform: Mouse cursor shape and visibility. Disable with 'io.ConfigFlags |= ImGuiConfigFlags_NoMouseCursorChange'. -// [X] Platform: Mouse support. Can discriminate Mouse/Pen. -// [X] Platform: Keyboard support. Since 1.87 we are using the io.AddKeyEvent() function. Pass ImGuiKey values to all key functions e.g. ImGui::IsKeyPressed(ImGuiKey_Space). [Legacy kVK_* values will also be supported unless IMGUI_DISABLE_OBSOLETE_KEYIO is set] -// [X] Platform: OSX clipboard is supported within core Dear ImGui (no specific code in this backend). -// [X] Platform: Gamepad support. Enabled with 'io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad'. -// [X] Platform: IME support. -// [X] Platform: Multi-viewport / platform windows. - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#include "imgui.h" // IMGUI_IMPL_API -#ifndef IMGUI_DISABLE - -#ifdef __OBJC__ - -@class NSEvent; -@class NSView; - -IMGUI_IMPL_API bool ImGui_ImplOSX_Init(NSView* _Nonnull view); -IMGUI_IMPL_API void ImGui_ImplOSX_Shutdown(); -IMGUI_IMPL_API void ImGui_ImplOSX_NewFrame(NSView* _Nullable view); - -#endif - -//----------------------------------------------------------------------------- -// C++ API -//----------------------------------------------------------------------------- - -#ifdef IMGUI_IMPL_METAL_CPP_EXTENSIONS -// #include -#ifndef __OBJC__ - -IMGUI_IMPL_API bool ImGui_ImplOSX_Init(void* _Nonnull view); -IMGUI_IMPL_API void ImGui_ImplOSX_Shutdown(); -IMGUI_IMPL_API void ImGui_ImplOSX_NewFrame(void* _Nullable view); - -#endif -#endif - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_osx.mm b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_osx.mm deleted file mode 100644 index 56de6c1..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_osx.mm +++ /dev/null @@ -1,1120 +0,0 @@ -// dear imgui: Platform Backend for OSX / Cocoa -// This needs to be used along with a Renderer (e.g. OpenGL2, OpenGL3, Vulkan, Metal..) -// - Not well tested. If you want a portable application, prefer using the GLFW or SDL platform Backends on Mac. -// - Requires linking with the GameController framework ("-framework GameController"). - -// Implemented features: -// [X] Platform: Mouse cursor shape and visibility. Disable with 'io.ConfigFlags |= ImGuiConfigFlags_NoMouseCursorChange'. -// [X] Platform: Mouse support. Can discriminate Mouse/Pen. -// [X] Platform: Keyboard support. Since 1.87 we are using the io.AddKeyEvent() function. Pass ImGuiKey values to all key functions e.g. ImGui::IsKeyPressed(ImGuiKey_Space). [Legacy kVK_* values will also be supported unless IMGUI_DISABLE_OBSOLETE_KEYIO is set] -// [X] Platform: OSX clipboard is supported within core Dear ImGui (no specific code in this backend). -// [X] Platform: Gamepad support. Enabled with 'io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad'. -// [X] Platform: IME support. -// [X] Platform: Multi-viewport / platform windows. - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#import "imgui.h" -#ifndef IMGUI_DISABLE -#import "imgui_impl_osx.h" -#import -#import -#import -#import - -// CHANGELOG -// (minor and older changes stripped away, please see git history for details) -// 2023-XX-XX: Added support for multiple windows via the ImGuiPlatformIO interface. -// 2023-10-05: Inputs: Added support for extra ImGuiKey values: F13 to F20 function keys. Stopped mapping F13 into PrintScreen. -// 2023-04-09: Inputs: Added support for io.AddMouseSourceEvent() to discriminate ImGuiMouseSource_Mouse/ImGuiMouseSource_Pen. -// 2023-02-01: Fixed scroll wheel scaling for devices emitting events with hasPreciseScrollingDeltas==false (e.g. non-Apple mices). -// 2022-11-02: Fixed mouse coordinates before clicking the host window. -// 2022-10-06: Fixed mouse inputs on flipped views. -// 2022-09-26: Inputs: Renamed ImGuiKey_ModXXX introduced in 1.87 to ImGuiMod_XXX (old names still supported). -// 2022-05-03: Inputs: Removed ImGui_ImplOSX_HandleEvent() from backend API in favor of backend automatically handling event capture. -// 2022-04-27: Misc: Store backend data in a per-context struct, allowing to use this backend with multiple contexts. -// 2022-03-22: Inputs: Monitor NSKeyUp events to catch missing keyUp for key when user press Cmd + key -// 2022-02-07: Inputs: Forward keyDown/keyUp events to OS when unused by dear imgui. -// 2022-01-31: Fixed building with old Xcode versions that are missing gamepad features. -// 2022-01-26: Inputs: replaced short-lived io.AddKeyModsEvent() (added two weeks ago) with io.AddKeyEvent() using ImGuiKey_ModXXX flags. Sorry for the confusion. -// 2021-01-20: Inputs: calling new io.AddKeyAnalogEvent() for gamepad support, instead of writing directly to io.NavInputs[]. -// 2022-01-17: Inputs: calling new io.AddMousePosEvent(), io.AddMouseButtonEvent(), io.AddMouseWheelEvent() API (1.87+). -// 2022-01-12: Inputs: Added basic Platform IME support, hooking the io.SetPlatformImeDataFn() function. -// 2022-01-10: Inputs: calling new io.AddKeyEvent(), io.AddKeyModsEvent() + io.SetKeyEventNativeData() API (1.87+). Support for full ImGuiKey range. -// 2021-12-13: *BREAKING CHANGE* Add NSView parameter to ImGui_ImplOSX_Init(). Generally fix keyboard support. Using kVK_* codes for keyboard keys. -// 2021-12-13: Add game controller support. -// 2021-09-21: Use mach_absolute_time as CFAbsoluteTimeGetCurrent can jump backwards. -// 2021-08-17: Calling io.AddFocusEvent() on NSApplicationDidBecomeActiveNotification/NSApplicationDidResignActiveNotification events. -// 2021-06-23: Inputs: Added a fix for shortcuts using CTRL key instead of CMD key. -// 2021-04-19: Inputs: Added a fix for keys remaining stuck in pressed state when CMD-tabbing into different application. -// 2021-01-27: Inputs: Added a fix for mouse position not being reported when mouse buttons other than left one are down. -// 2020-10-28: Inputs: Added a fix for handling keypad-enter key. -// 2020-05-25: Inputs: Added a fix for missing trackpad clicks when done with "soft tap". -// 2019-12-05: Inputs: Added support for ImGuiMouseCursor_NotAllowed mouse cursor. -// 2019-10-11: Inputs: Fix using Backspace key. -// 2019-07-21: Re-added clipboard handlers as they are not enabled by default in core imgui.cpp (reverted 2019-05-18 change). -// 2019-05-28: Inputs: Added mouse cursor shape and visibility support. -// 2019-05-18: Misc: Removed clipboard handlers as they are now supported by core imgui.cpp. -// 2019-05-11: Inputs: Don't filter character values before calling AddInputCharacter() apart from 0xF700..0xFFFF range. -// 2018-11-30: Misc: Setting up io.BackendPlatformName so it can be displayed in the About Window. -// 2018-07-07: Initial version. - -#define APPLE_HAS_BUTTON_OPTIONS (__IPHONE_OS_VERSION_MIN_REQUIRED >= 130000 || __MAC_OS_X_VERSION_MIN_REQUIRED >= 101500 || __TV_OS_VERSION_MIN_REQUIRED >= 130000) -#define APPLE_HAS_CONTROLLER (__IPHONE_OS_VERSION_MIN_REQUIRED >= 140000 || __MAC_OS_X_VERSION_MIN_REQUIRED >= 110000 || __TV_OS_VERSION_MIN_REQUIRED >= 140000) -#define APPLE_HAS_THUMBSTICKS (__IPHONE_OS_VERSION_MIN_REQUIRED >= 120100 || __MAC_OS_X_VERSION_MIN_REQUIRED >= 101401 || __TV_OS_VERSION_MIN_REQUIRED >= 120100) - -@class ImGuiObserver; -@class KeyEventResponder; - -// Data -struct ImGui_ImplOSX_Data -{ - CFTimeInterval Time; - NSCursor* MouseCursors[ImGuiMouseCursor_COUNT]; - bool MouseCursorHidden; - ImGuiObserver* Observer; - KeyEventResponder* KeyEventResponder; - NSTextInputContext* InputContext; - id Monitor; - NSWindow* Window; - - ImGui_ImplOSX_Data() { memset(this, 0, sizeof(*this)); } -}; - -static ImGui_ImplOSX_Data* ImGui_ImplOSX_CreateBackendData() { return IM_NEW(ImGui_ImplOSX_Data)(); } -static ImGui_ImplOSX_Data* ImGui_ImplOSX_GetBackendData() { return (ImGui_ImplOSX_Data*)ImGui::GetIO().BackendPlatformUserData; } -static void ImGui_ImplOSX_DestroyBackendData() { IM_DELETE(ImGui_ImplOSX_GetBackendData()); } - -static inline CFTimeInterval GetMachAbsoluteTimeInSeconds() { return (CFTimeInterval)(double)(clock_gettime_nsec_np(CLOCK_UPTIME_RAW) / 1e9); } - -// Forward Declarations -static void ImGui_ImplOSX_InitPlatformInterface(); -static void ImGui_ImplOSX_ShutdownPlatformInterface(); -static void ImGui_ImplOSX_UpdateMonitors(); -static void ImGui_ImplOSX_AddTrackingArea(NSView* _Nonnull view); -static bool ImGui_ImplOSX_HandleEvent(NSEvent* event, NSView* view); - -// Undocumented methods for creating cursors. -@interface NSCursor() -+ (id)_windowResizeNorthWestSouthEastCursor; -+ (id)_windowResizeNorthEastSouthWestCursor; -+ (id)_windowResizeNorthSouthCursor; -+ (id)_windowResizeEastWestCursor; -@end - -/** - KeyEventResponder implements the NSTextInputClient protocol as is required by the macOS text input manager. - - The macOS text input manager is invoked by calling the interpretKeyEvents method from the keyDown method. - Keyboard events are then evaluated by the macOS input manager and valid text input is passed back via the - insertText:replacementRange method. - - This is the same approach employed by other cross-platform libraries such as SDL2: - https://github.com/spurious/SDL-mirror/blob/e17aacbd09e65a4fd1e166621e011e581fb017a8/src/video/cocoa/SDL_cocoakeyboard.m#L53 - and GLFW: - https://github.com/glfw/glfw/blob/b55a517ae0c7b5127dffa79a64f5406021bf9076/src/cocoa_window.m#L722-L723 - */ -@interface KeyEventResponder: NSView -@end - -@implementation KeyEventResponder -{ - float _posX; - float _posY; - NSRect _imeRect; -} - -#pragma mark - Public - -- (void)setImePosX:(float)posX imePosY:(float)posY -{ - _posX = posX; - _posY = posY; -} - -- (void)updateImePosWithView:(NSView *)view -{ - NSWindow *window = view.window; - if (!window) - return; - NSRect contentRect = [window contentRectForFrameRect:window.frame]; - NSRect rect = NSMakeRect(_posX, contentRect.size.height - _posY, 0, 0); - _imeRect = [window convertRectToScreen:rect]; -} - -- (void)viewDidMoveToWindow -{ - // Ensure self is a first responder to receive the input events. - [self.window makeFirstResponder:self]; -} - -- (void)keyDown:(NSEvent*)event -{ - if (!ImGui_ImplOSX_HandleEvent(event, self)) - [super keyDown:event]; - - // Call to the macOS input manager system. - [self interpretKeyEvents:@[event]]; -} - -- (void)keyUp:(NSEvent*)event -{ - if (!ImGui_ImplOSX_HandleEvent(event, self)) - [super keyUp:event]; -} - -- (void)insertText:(id)aString replacementRange:(NSRange)replacementRange -{ - ImGuiIO& io = ImGui::GetIO(); - - NSString* characters; - if ([aString isKindOfClass:[NSAttributedString class]]) - characters = [aString string]; - else - characters = (NSString*)aString; - - io.AddInputCharactersUTF8(characters.UTF8String); -} - -- (BOOL)acceptsFirstResponder -{ - return YES; -} - -- (void)doCommandBySelector:(SEL)myselector -{ -} - -- (nullable NSAttributedString*)attributedSubstringForProposedRange:(NSRange)range actualRange:(nullable NSRangePointer)actualRange -{ - return nil; -} - -- (NSUInteger)characterIndexForPoint:(NSPoint)point -{ - return 0; -} - -- (NSRect)firstRectForCharacterRange:(NSRange)range actualRange:(nullable NSRangePointer)actualRange -{ - return _imeRect; -} - -- (BOOL)hasMarkedText -{ - return NO; -} - -- (NSRange)markedRange -{ - return NSMakeRange(NSNotFound, 0); -} - -- (NSRange)selectedRange -{ - return NSMakeRange(NSNotFound, 0); -} - -- (void)setMarkedText:(nonnull id)string selectedRange:(NSRange)selectedRange replacementRange:(NSRange)replacementRange -{ -} - -- (void)unmarkText -{ -} - -- (nonnull NSArray*)validAttributesForMarkedText -{ - return @[]; -} - -@end - -@interface ImGuiObserver : NSObject - -- (void)onApplicationBecomeActive:(NSNotification*)aNotification; -- (void)onApplicationBecomeInactive:(NSNotification*)aNotification; -- (void)displaysDidChange:(NSNotification*)aNotification; - -@end - -@implementation ImGuiObserver - -- (void)onApplicationBecomeActive:(NSNotification*)aNotification -{ - ImGuiIO& io = ImGui::GetIO(); - io.AddFocusEvent(true); -} - -- (void)onApplicationBecomeInactive:(NSNotification*)aNotification -{ - ImGuiIO& io = ImGui::GetIO(); - io.AddFocusEvent(false); -} - -- (void)displaysDidChange:(NSNotification*)aNotification -{ - ImGui_ImplOSX_UpdateMonitors(); -} - -@end - -// Functions -static ImGuiKey ImGui_ImplOSX_KeyCodeToImGuiKey(int key_code) -{ - switch (key_code) - { - case kVK_ANSI_A: return ImGuiKey_A; - case kVK_ANSI_S: return ImGuiKey_S; - case kVK_ANSI_D: return ImGuiKey_D; - case kVK_ANSI_F: return ImGuiKey_F; - case kVK_ANSI_H: return ImGuiKey_H; - case kVK_ANSI_G: return ImGuiKey_G; - case kVK_ANSI_Z: return ImGuiKey_Z; - case kVK_ANSI_X: return ImGuiKey_X; - case kVK_ANSI_C: return ImGuiKey_C; - case kVK_ANSI_V: return ImGuiKey_V; - case kVK_ANSI_B: return ImGuiKey_B; - case kVK_ANSI_Q: return ImGuiKey_Q; - case kVK_ANSI_W: return ImGuiKey_W; - case kVK_ANSI_E: return ImGuiKey_E; - case kVK_ANSI_R: return ImGuiKey_R; - case kVK_ANSI_Y: return ImGuiKey_Y; - case kVK_ANSI_T: return ImGuiKey_T; - case kVK_ANSI_1: return ImGuiKey_1; - case kVK_ANSI_2: return ImGuiKey_2; - case kVK_ANSI_3: return ImGuiKey_3; - case kVK_ANSI_4: return ImGuiKey_4; - case kVK_ANSI_6: return ImGuiKey_6; - case kVK_ANSI_5: return ImGuiKey_5; - case kVK_ANSI_Equal: return ImGuiKey_Equal; - case kVK_ANSI_9: return ImGuiKey_9; - case kVK_ANSI_7: return ImGuiKey_7; - case kVK_ANSI_Minus: return ImGuiKey_Minus; - case kVK_ANSI_8: return ImGuiKey_8; - case kVK_ANSI_0: return ImGuiKey_0; - case kVK_ANSI_RightBracket: return ImGuiKey_RightBracket; - case kVK_ANSI_O: return ImGuiKey_O; - case kVK_ANSI_U: return ImGuiKey_U; - case kVK_ANSI_LeftBracket: return ImGuiKey_LeftBracket; - case kVK_ANSI_I: return ImGuiKey_I; - case kVK_ANSI_P: return ImGuiKey_P; - case kVK_ANSI_L: return ImGuiKey_L; - case kVK_ANSI_J: return ImGuiKey_J; - case kVK_ANSI_Quote: return ImGuiKey_Apostrophe; - case kVK_ANSI_K: return ImGuiKey_K; - case kVK_ANSI_Semicolon: return ImGuiKey_Semicolon; - case kVK_ANSI_Backslash: return ImGuiKey_Backslash; - case kVK_ANSI_Comma: return ImGuiKey_Comma; - case kVK_ANSI_Slash: return ImGuiKey_Slash; - case kVK_ANSI_N: return ImGuiKey_N; - case kVK_ANSI_M: return ImGuiKey_M; - case kVK_ANSI_Period: return ImGuiKey_Period; - case kVK_ANSI_Grave: return ImGuiKey_GraveAccent; - case kVK_ANSI_KeypadDecimal: return ImGuiKey_KeypadDecimal; - case kVK_ANSI_KeypadMultiply: return ImGuiKey_KeypadMultiply; - case kVK_ANSI_KeypadPlus: return ImGuiKey_KeypadAdd; - case kVK_ANSI_KeypadClear: return ImGuiKey_NumLock; - case kVK_ANSI_KeypadDivide: return ImGuiKey_KeypadDivide; - case kVK_ANSI_KeypadEnter: return ImGuiKey_KeypadEnter; - case kVK_ANSI_KeypadMinus: return ImGuiKey_KeypadSubtract; - case kVK_ANSI_KeypadEquals: return ImGuiKey_KeypadEqual; - case kVK_ANSI_Keypad0: return ImGuiKey_Keypad0; - case kVK_ANSI_Keypad1: return ImGuiKey_Keypad1; - case kVK_ANSI_Keypad2: return ImGuiKey_Keypad2; - case kVK_ANSI_Keypad3: return ImGuiKey_Keypad3; - case kVK_ANSI_Keypad4: return ImGuiKey_Keypad4; - case kVK_ANSI_Keypad5: return ImGuiKey_Keypad5; - case kVK_ANSI_Keypad6: return ImGuiKey_Keypad6; - case kVK_ANSI_Keypad7: return ImGuiKey_Keypad7; - case kVK_ANSI_Keypad8: return ImGuiKey_Keypad8; - case kVK_ANSI_Keypad9: return ImGuiKey_Keypad9; - case kVK_Return: return ImGuiKey_Enter; - case kVK_Tab: return ImGuiKey_Tab; - case kVK_Space: return ImGuiKey_Space; - case kVK_Delete: return ImGuiKey_Backspace; - case kVK_Escape: return ImGuiKey_Escape; - case kVK_CapsLock: return ImGuiKey_CapsLock; - case kVK_Control: return ImGuiKey_LeftCtrl; - case kVK_Shift: return ImGuiKey_LeftShift; - case kVK_Option: return ImGuiKey_LeftAlt; - case kVK_Command: return ImGuiKey_LeftSuper; - case kVK_RightControl: return ImGuiKey_RightCtrl; - case kVK_RightShift: return ImGuiKey_RightShift; - case kVK_RightOption: return ImGuiKey_RightAlt; - case kVK_RightCommand: return ImGuiKey_RightSuper; -// case kVK_Function: return ImGuiKey_; -// case kVK_VolumeUp: return ImGuiKey_; -// case kVK_VolumeDown: return ImGuiKey_; -// case kVK_Mute: return ImGuiKey_; - case kVK_F1: return ImGuiKey_F1; - case kVK_F2: return ImGuiKey_F2; - case kVK_F3: return ImGuiKey_F3; - case kVK_F4: return ImGuiKey_F4; - case kVK_F5: return ImGuiKey_F5; - case kVK_F6: return ImGuiKey_F6; - case kVK_F7: return ImGuiKey_F7; - case kVK_F8: return ImGuiKey_F8; - case kVK_F9: return ImGuiKey_F9; - case kVK_F10: return ImGuiKey_F10; - case kVK_F11: return ImGuiKey_F11; - case kVK_F12: return ImGuiKey_F12; - case kVK_F13: return ImGuiKey_F13; - case kVK_F14: return ImGuiKey_F14; - case kVK_F15: return ImGuiKey_F15; - case kVK_F16: return ImGuiKey_F16; - case kVK_F17: return ImGuiKey_F17; - case kVK_F18: return ImGuiKey_F18; - case kVK_F19: return ImGuiKey_F19; - case kVK_F20: return ImGuiKey_F20; - case 0x6E: return ImGuiKey_Menu; - case kVK_Help: return ImGuiKey_Insert; - case kVK_Home: return ImGuiKey_Home; - case kVK_PageUp: return ImGuiKey_PageUp; - case kVK_ForwardDelete: return ImGuiKey_Delete; - case kVK_End: return ImGuiKey_End; - case kVK_PageDown: return ImGuiKey_PageDown; - case kVK_LeftArrow: return ImGuiKey_LeftArrow; - case kVK_RightArrow: return ImGuiKey_RightArrow; - case kVK_DownArrow: return ImGuiKey_DownArrow; - case kVK_UpArrow: return ImGuiKey_UpArrow; - default: return ImGuiKey_None; - } -} - -#ifdef IMGUI_IMPL_METAL_CPP_EXTENSIONS - -IMGUI_IMPL_API bool ImGui_ImplOSX_Init(void* _Nonnull view) { - return ImGui_ImplOSX_Init((__bridge NSView*)(view)); -} - -IMGUI_IMPL_API void ImGui_ImplOSX_NewFrame(void* _Nullable view) { - return ImGui_ImplOSX_NewFrame((__bridge NSView*)(view)); -} - -#endif - - -bool ImGui_ImplOSX_Init(NSView* view) -{ - ImGuiIO& io = ImGui::GetIO(); - ImGui_ImplOSX_Data* bd = ImGui_ImplOSX_CreateBackendData(); - io.BackendPlatformUserData = (void*)bd; - - // Setup backend capabilities flags - io.BackendFlags |= ImGuiBackendFlags_HasMouseCursors; // We can honor GetMouseCursor() values (optional) - //io.BackendFlags |= ImGuiBackendFlags_HasSetMousePos; // We can honor io.WantSetMousePos requests (optional, rarely used) - io.BackendFlags |= ImGuiBackendFlags_PlatformHasViewports; // We can create multi-viewports on the Platform side (optional) - //io.BackendFlags |= ImGuiBackendFlags_HasMouseHoveredViewport; // We can call io.AddMouseViewportEvent() with correct data (optional) - io.BackendPlatformName = "imgui_impl_osx"; - - bd->Observer = [ImGuiObserver new]; - bd->Window = view.window ?: NSApp.orderedWindows.firstObject; - ImGuiViewport* main_viewport = ImGui::GetMainViewport(); - main_viewport->PlatformHandle = main_viewport->PlatformHandleRaw = (__bridge_retained void*)bd->Window; - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - ImGui_ImplOSX_InitPlatformInterface(); - - // Load cursors. Some of them are undocumented. - bd->MouseCursorHidden = false; - bd->MouseCursors[ImGuiMouseCursor_Arrow] = [NSCursor arrowCursor]; - bd->MouseCursors[ImGuiMouseCursor_TextInput] = [NSCursor IBeamCursor]; - bd->MouseCursors[ImGuiMouseCursor_ResizeAll] = [NSCursor closedHandCursor]; - bd->MouseCursors[ImGuiMouseCursor_Hand] = [NSCursor pointingHandCursor]; - bd->MouseCursors[ImGuiMouseCursor_NotAllowed] = [NSCursor operationNotAllowedCursor]; - bd->MouseCursors[ImGuiMouseCursor_ResizeNS] = [NSCursor respondsToSelector:@selector(_windowResizeNorthSouthCursor)] ? [NSCursor _windowResizeNorthSouthCursor] : [NSCursor resizeUpDownCursor]; - bd->MouseCursors[ImGuiMouseCursor_ResizeEW] = [NSCursor respondsToSelector:@selector(_windowResizeEastWestCursor)] ? [NSCursor _windowResizeEastWestCursor] : [NSCursor resizeLeftRightCursor]; - bd->MouseCursors[ImGuiMouseCursor_ResizeNESW] = [NSCursor respondsToSelector:@selector(_windowResizeNorthEastSouthWestCursor)] ? [NSCursor _windowResizeNorthEastSouthWestCursor] : [NSCursor closedHandCursor]; - bd->MouseCursors[ImGuiMouseCursor_ResizeNWSE] = [NSCursor respondsToSelector:@selector(_windowResizeNorthWestSouthEastCursor)] ? [NSCursor _windowResizeNorthWestSouthEastCursor] : [NSCursor closedHandCursor]; - - // Note that imgui.cpp also include default OSX clipboard handlers which can be enabled - // by adding '#define IMGUI_ENABLE_OSX_DEFAULT_CLIPBOARD_FUNCTIONS' in imconfig.h and adding '-framework ApplicationServices' to your linker command-line. - // Since we are already in ObjC land here, it is easy for us to add a clipboard handler using the NSPasteboard api. - io.SetClipboardTextFn = [](void*, const char* str) -> void - { - NSPasteboard* pasteboard = [NSPasteboard generalPasteboard]; - [pasteboard declareTypes:[NSArray arrayWithObject:NSPasteboardTypeString] owner:nil]; - [pasteboard setString:[NSString stringWithUTF8String:str] forType:NSPasteboardTypeString]; - }; - - io.GetClipboardTextFn = [](void*) -> const char* - { - NSPasteboard* pasteboard = [NSPasteboard generalPasteboard]; - NSString* available = [pasteboard availableTypeFromArray: [NSArray arrayWithObject:NSPasteboardTypeString]]; - if (![available isEqualToString:NSPasteboardTypeString]) - return nullptr; - - NSString* string = [pasteboard stringForType:NSPasteboardTypeString]; - if (string == nil) - return nullptr; - - const char* string_c = (const char*)[string UTF8String]; - size_t string_len = strlen(string_c); - static ImVector s_clipboard; - s_clipboard.resize((int)string_len + 1); - strcpy(s_clipboard.Data, string_c); - return s_clipboard.Data; - }; - - [[NSNotificationCenter defaultCenter] addObserver:bd->Observer - selector:@selector(onApplicationBecomeActive:) - name:NSApplicationDidBecomeActiveNotification - object:nil]; - [[NSNotificationCenter defaultCenter] addObserver:bd->Observer - selector:@selector(onApplicationBecomeInactive:) - name:NSApplicationDidResignActiveNotification - object:nil]; - - // Add the NSTextInputClient to the view hierarchy, - // to receive keyboard events and translate them to input text. - bd->KeyEventResponder = [[KeyEventResponder alloc] initWithFrame:NSZeroRect]; - bd->InputContext = [[NSTextInputContext alloc] initWithClient:bd->KeyEventResponder]; - [view addSubview:bd->KeyEventResponder]; - ImGui_ImplOSX_AddTrackingArea(view); - - io.SetPlatformImeDataFn = [](ImGuiViewport* viewport, ImGuiPlatformImeData* data) -> void - { - ImGui_ImplOSX_Data* bd = ImGui_ImplOSX_GetBackendData(); - if (data->WantVisible) - { - [bd->InputContext activate]; - } - else - { - [bd->InputContext discardMarkedText]; - [bd->InputContext invalidateCharacterCoordinates]; - [bd->InputContext deactivate]; - } - [bd->KeyEventResponder setImePosX:data->InputPos.x imePosY:data->InputPos.y + data->InputLineHeight]; - }; - - return true; -} - -void ImGui_ImplOSX_Shutdown() -{ - ImGui_ImplOSX_Data* bd = ImGui_ImplOSX_GetBackendData(); - IM_ASSERT(bd != nullptr && "No platform backend to shutdown, or already shutdown?"); - - bd->Observer = nullptr; - if (bd->Monitor != nullptr) - { - [NSEvent removeMonitor:bd->Monitor]; - bd->Monitor = nullptr; - } - - ImGui_ImplOSX_ShutdownPlatformInterface(); - ImGui_ImplOSX_DestroyBackendData(); - ImGuiIO& io = ImGui::GetIO(); - io.BackendPlatformName = nullptr; - io.BackendPlatformUserData = nullptr; - io.BackendFlags &= ~(ImGuiBackendFlags_HasMouseCursors | ImGuiBackendFlags_HasGamepad | ImGuiBackendFlags_PlatformHasViewports); -} - -static void ImGui_ImplOSX_UpdateMouseCursor() -{ - ImGui_ImplOSX_Data* bd = ImGui_ImplOSX_GetBackendData(); - ImGuiIO& io = ImGui::GetIO(); - if (io.ConfigFlags & ImGuiConfigFlags_NoMouseCursorChange) - return; - - ImGuiMouseCursor imgui_cursor = ImGui::GetMouseCursor(); - if (io.MouseDrawCursor || imgui_cursor == ImGuiMouseCursor_None) - { - // Hide OS mouse cursor if imgui is drawing it or if it wants no cursor - if (!bd->MouseCursorHidden) - { - bd->MouseCursorHidden = true; - [NSCursor hide]; - } - } - else - { - NSCursor* desired = bd->MouseCursors[imgui_cursor] ?: bd->MouseCursors[ImGuiMouseCursor_Arrow]; - // -[NSCursor set] generates measureable overhead if called unconditionally. - if (desired != NSCursor.currentCursor) - { - [desired set]; - } - if (bd->MouseCursorHidden) - { - bd->MouseCursorHidden = false; - [NSCursor unhide]; - } - } -} - -static void ImGui_ImplOSX_UpdateGamepads() -{ - ImGuiIO& io = ImGui::GetIO(); - memset(io.NavInputs, 0, sizeof(io.NavInputs)); - if ((io.ConfigFlags & ImGuiConfigFlags_NavEnableGamepad) == 0) // FIXME: Technically feeding gamepad shouldn't depend on this now that they are regular inputs. - return; - -#if APPLE_HAS_CONTROLLER - GCController* controller = GCController.current; -#else - GCController* controller = GCController.controllers.firstObject; -#endif - if (controller == nil || controller.extendedGamepad == nil) - { - io.BackendFlags &= ~ImGuiBackendFlags_HasGamepad; - return; - } - - GCExtendedGamepad* gp = controller.extendedGamepad; - - // Update gamepad inputs - #define IM_SATURATE(V) (V < 0.0f ? 0.0f : V > 1.0f ? 1.0f : V) - #define MAP_BUTTON(KEY_NO, BUTTON_NAME) { io.AddKeyEvent(KEY_NO, gp.BUTTON_NAME.isPressed); } - #define MAP_ANALOG(KEY_NO, AXIS_NAME, V0, V1) { float vn = (float)(gp.AXIS_NAME.value - V0) / (float)(V1 - V0); vn = IM_SATURATE(vn); io.AddKeyAnalogEvent(KEY_NO, vn > 0.1f, vn); } - const float thumb_dead_zone = 0.0f; - -#if APPLE_HAS_BUTTON_OPTIONS - MAP_BUTTON(ImGuiKey_GamepadBack, buttonOptions); -#endif - MAP_BUTTON(ImGuiKey_GamepadFaceLeft, buttonX); // Xbox X, PS Square - MAP_BUTTON(ImGuiKey_GamepadFaceRight, buttonB); // Xbox B, PS Circle - MAP_BUTTON(ImGuiKey_GamepadFaceUp, buttonY); // Xbox Y, PS Triangle - MAP_BUTTON(ImGuiKey_GamepadFaceDown, buttonA); // Xbox A, PS Cross - MAP_BUTTON(ImGuiKey_GamepadDpadLeft, dpad.left); - MAP_BUTTON(ImGuiKey_GamepadDpadRight, dpad.right); - MAP_BUTTON(ImGuiKey_GamepadDpadUp, dpad.up); - MAP_BUTTON(ImGuiKey_GamepadDpadDown, dpad.down); - MAP_ANALOG(ImGuiKey_GamepadL1, leftShoulder, 0.0f, 1.0f); - MAP_ANALOG(ImGuiKey_GamepadR1, rightShoulder, 0.0f, 1.0f); - MAP_ANALOG(ImGuiKey_GamepadL2, leftTrigger, 0.0f, 1.0f); - MAP_ANALOG(ImGuiKey_GamepadR2, rightTrigger, 0.0f, 1.0f); -#if APPLE_HAS_THUMBSTICKS - MAP_BUTTON(ImGuiKey_GamepadL3, leftThumbstickButton); - MAP_BUTTON(ImGuiKey_GamepadR3, rightThumbstickButton); -#endif - MAP_ANALOG(ImGuiKey_GamepadLStickLeft, leftThumbstick.xAxis, -thumb_dead_zone, -1.0f); - MAP_ANALOG(ImGuiKey_GamepadLStickRight, leftThumbstick.xAxis, +thumb_dead_zone, +1.0f); - MAP_ANALOG(ImGuiKey_GamepadLStickUp, leftThumbstick.yAxis, +thumb_dead_zone, +1.0f); - MAP_ANALOG(ImGuiKey_GamepadLStickDown, leftThumbstick.yAxis, -thumb_dead_zone, -1.0f); - MAP_ANALOG(ImGuiKey_GamepadRStickLeft, rightThumbstick.xAxis, -thumb_dead_zone, -1.0f); - MAP_ANALOG(ImGuiKey_GamepadRStickRight, rightThumbstick.xAxis, +thumb_dead_zone, +1.0f); - MAP_ANALOG(ImGuiKey_GamepadRStickUp, rightThumbstick.yAxis, +thumb_dead_zone, +1.0f); - MAP_ANALOG(ImGuiKey_GamepadRStickDown, rightThumbstick.yAxis, -thumb_dead_zone, -1.0f); - #undef MAP_BUTTON - #undef MAP_ANALOG - - io.BackendFlags |= ImGuiBackendFlags_HasGamepad; -} - -static void ImGui_ImplOSX_UpdateImePosWithView(NSView* view) -{ - ImGui_ImplOSX_Data* bd = ImGui_ImplOSX_GetBackendData(); - ImGuiIO& io = ImGui::GetIO(); - if (io.WantTextInput) - [bd->KeyEventResponder updateImePosWithView:view]; -} - -void ImGui_ImplOSX_NewFrame(NSView* view) -{ - ImGui_ImplOSX_Data* bd = ImGui_ImplOSX_GetBackendData(); - ImGuiIO& io = ImGui::GetIO(); - - // Setup display size - if (view) - { - const float dpi = (float)[view.window backingScaleFactor]; - io.DisplaySize = ImVec2((float)view.bounds.size.width, (float)view.bounds.size.height); - io.DisplayFramebufferScale = ImVec2(dpi, dpi); - } - - // Setup time step - if (bd->Time == 0.0) - bd->Time = GetMachAbsoluteTimeInSeconds(); - - double current_time = GetMachAbsoluteTimeInSeconds(); - io.DeltaTime = (float)(current_time - bd->Time); - bd->Time = current_time; - - ImGui_ImplOSX_UpdateMouseCursor(); - ImGui_ImplOSX_UpdateGamepads(); - ImGui_ImplOSX_UpdateImePosWithView(view); -} - -// Must only be called for a mouse event, otherwise an exception occurs -// (Note that NSEventTypeScrollWheel is considered "other input". Oddly enough an exception does not occur with it, but the value will sometimes be wrong!) -static ImGuiMouseSource GetMouseSource(NSEvent* event) -{ - switch (event.subtype) - { - case NSEventSubtypeTabletPoint: - return ImGuiMouseSource_Pen; - // macOS considers input from relative touch devices (like the trackpad or Apple Magic Mouse) to be touch input. - // This doesn't really make sense for Dear ImGui, which expects absolute touch devices only. - // There does not seem to be a simple way to disambiguate things here so we consider NSEventSubtypeTouch events to always come from mice. - // See https://developer.apple.com/library/archive/documentation/Cocoa/Conceptual/EventOverview/HandlingTouchEvents/HandlingTouchEvents.html#//apple_ref/doc/uid/10000060i-CH13-SW24 - //case NSEventSubtypeTouch: - // return ImGuiMouseSource_TouchScreen; - case NSEventSubtypeMouseEvent: - default: - return ImGuiMouseSource_Mouse; - } -} - -static bool ImGui_ImplOSX_HandleEvent(NSEvent* event, NSView* view) -{ - ImGuiIO& io = ImGui::GetIO(); - - if (event.type == NSEventTypeLeftMouseDown || event.type == NSEventTypeRightMouseDown || event.type == NSEventTypeOtherMouseDown) - { - int button = (int)[event buttonNumber]; - if (button >= 0 && button < ImGuiMouseButton_COUNT) - { - io.AddMouseSourceEvent(GetMouseSource(event)); - io.AddMouseButtonEvent(button, true); - } - return io.WantCaptureMouse; - } - - if (event.type == NSEventTypeLeftMouseUp || event.type == NSEventTypeRightMouseUp || event.type == NSEventTypeOtherMouseUp) - { - int button = (int)[event buttonNumber]; - if (button >= 0 && button < ImGuiMouseButton_COUNT) - { - io.AddMouseSourceEvent(GetMouseSource(event)); - io.AddMouseButtonEvent(button, false); - } - return io.WantCaptureMouse; - } - - if (event.type == NSEventTypeMouseMoved || event.type == NSEventTypeLeftMouseDragged || event.type == NSEventTypeRightMouseDragged || event.type == NSEventTypeOtherMouseDragged) - { - NSPoint mousePoint; - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - mousePoint = NSEvent.mouseLocation; - mousePoint.y = CGDisplayPixelsHigh(kCGDirectMainDisplay) - mousePoint.y; // Normalize y coordinate to top-left of main display. - } - else - { - mousePoint = event.locationInWindow; - if (event.window == nil) - mousePoint = [[view window] convertPointFromScreen:mousePoint]; - mousePoint = [view convertPoint:mousePoint fromView:nil]; // Convert to local coordinates of view - if ([view isFlipped]) - mousePoint = NSMakePoint(mousePoint.x, mousePoint.y); - else - mousePoint = NSMakePoint(mousePoint.x, view.bounds.size.height - mousePoint.y); - } - io.AddMouseSourceEvent(GetMouseSource(event)); - io.AddMousePosEvent((float)mousePoint.x, (float)mousePoint.y); - return io.WantCaptureMouse; - } - - if (event.type == NSEventTypeScrollWheel) - { - // Ignore canceled events. - // - // From macOS 12.1, scrolling with two fingers and then decelerating - // by tapping two fingers results in two events appearing: - // - // 1. A scroll wheel NSEvent, with a phase == NSEventPhaseMayBegin, when the user taps - // two fingers to decelerate or stop the scroll events. - // - // 2. A scroll wheel NSEvent, with a phase == NSEventPhaseCancelled, when the user releases the - // two-finger tap. It is this event that sometimes contains large values for scrollingDeltaX and - // scrollingDeltaY. When these are added to the current x and y positions of the scrolling view, - // it appears to jump up or down. It can be observed in Preview, various JetBrains IDEs and here. - if (event.phase == NSEventPhaseCancelled) - return false; - - double wheel_dx = 0.0; - double wheel_dy = 0.0; - - #if MAC_OS_X_VERSION_MAX_ALLOWED >= 1070 - if (floor(NSAppKitVersionNumber) > NSAppKitVersionNumber10_6) - { - wheel_dx = [event scrollingDeltaX]; - wheel_dy = [event scrollingDeltaY]; - if ([event hasPreciseScrollingDeltas]) - { - wheel_dx *= 0.01; - wheel_dy *= 0.01; - } - } - else - #endif // MAC_OS_X_VERSION_MAX_ALLOWED - { - wheel_dx = [event deltaX] * 0.1; - wheel_dy = [event deltaY] * 0.1; - } - if (wheel_dx != 0.0 || wheel_dy != 0.0) - io.AddMouseWheelEvent((float)wheel_dx, (float)wheel_dy); - - return io.WantCaptureMouse; - } - - if (event.type == NSEventTypeKeyDown || event.type == NSEventTypeKeyUp) - { - if ([event isARepeat]) - return io.WantCaptureKeyboard; - - int key_code = (int)[event keyCode]; - ImGuiKey key = ImGui_ImplOSX_KeyCodeToImGuiKey(key_code); - io.AddKeyEvent(key, event.type == NSEventTypeKeyDown); - io.SetKeyEventNativeData(key, key_code, -1); // To support legacy indexing (<1.87 user code) - - return io.WantCaptureKeyboard; - } - - if (event.type == NSEventTypeFlagsChanged) - { - unsigned short key_code = [event keyCode]; - NSEventModifierFlags modifier_flags = [event modifierFlags]; - - io.AddKeyEvent(ImGuiMod_Shift, (modifier_flags & NSEventModifierFlagShift) != 0); - io.AddKeyEvent(ImGuiMod_Ctrl, (modifier_flags & NSEventModifierFlagControl) != 0); - io.AddKeyEvent(ImGuiMod_Alt, (modifier_flags & NSEventModifierFlagOption) != 0); - io.AddKeyEvent(ImGuiMod_Super, (modifier_flags & NSEventModifierFlagCommand) != 0); - - ImGuiKey key = ImGui_ImplOSX_KeyCodeToImGuiKey(key_code); - if (key != ImGuiKey_None) - { - // macOS does not generate down/up event for modifiers. We're trying - // to use hardware dependent masks to extract that information. - // 'imgui_mask' is left as a fallback. - NSEventModifierFlags mask = 0; - switch (key) - { - case ImGuiKey_LeftCtrl: mask = 0x0001; break; - case ImGuiKey_RightCtrl: mask = 0x2000; break; - case ImGuiKey_LeftShift: mask = 0x0002; break; - case ImGuiKey_RightShift: mask = 0x0004; break; - case ImGuiKey_LeftSuper: mask = 0x0008; break; - case ImGuiKey_RightSuper: mask = 0x0010; break; - case ImGuiKey_LeftAlt: mask = 0x0020; break; - case ImGuiKey_RightAlt: mask = 0x0040; break; - default: - return io.WantCaptureKeyboard; - } - - NSEventModifierFlags modifier_flags = [event modifierFlags]; - io.AddKeyEvent(key, (modifier_flags & mask) != 0); - io.SetKeyEventNativeData(key, key_code, -1); // To support legacy indexing (<1.87 user code) - } - - return io.WantCaptureKeyboard; - } - - return false; -} - -static void ImGui_ImplOSX_AddTrackingArea(NSView* _Nonnull view) -{ - // If we want to receive key events, we either need to be in the responder chain of the key view, - // or else we can install a local monitor. The consequence of this heavy-handed approach is that - // we receive events for all controls, not just Dear ImGui widgets. If we had native controls in our - // window, we'd want to be much more careful than just ingesting the complete event stream. - // To match the behavior of other backends, we pass every event down to the OS. - ImGui_ImplOSX_Data* bd = ImGui_ImplOSX_GetBackendData(); - if (bd->Monitor) - return; - NSEventMask eventMask = 0; - eventMask |= NSEventMaskMouseMoved | NSEventMaskScrollWheel; - eventMask |= NSEventMaskLeftMouseDown | NSEventMaskLeftMouseUp | NSEventMaskLeftMouseDragged; - eventMask |= NSEventMaskRightMouseDown | NSEventMaskRightMouseUp | NSEventMaskRightMouseDragged; - eventMask |= NSEventMaskOtherMouseDown | NSEventMaskOtherMouseUp | NSEventMaskOtherMouseDragged; - eventMask |= NSEventMaskKeyDown | NSEventMaskKeyUp | NSEventMaskFlagsChanged; - bd->Monitor = [NSEvent addLocalMonitorForEventsMatchingMask:eventMask - handler:^NSEvent* _Nullable(NSEvent* event) - { - ImGui_ImplOSX_HandleEvent(event, view); - return event; - }]; -} - -//-------------------------------------------------------------------------------------------------------- -// MULTI-VIEWPORT / PLATFORM INTERFACE SUPPORT -// This is an _advanced_ and _optional_ feature, allowing the back-end to create and handle multiple viewports simultaneously. -// If you are new to dear imgui or creating a new binding for dear imgui, it is recommended that you completely ignore this section first.. -//-------------------------------------------------------------------------------------------------------- - -struct ImGuiViewportDataOSX -{ - NSWindow* Window; - bool WindowOwned; - - ImGuiViewportDataOSX() { WindowOwned = false; } - ~ImGuiViewportDataOSX() { IM_ASSERT(Window == nil); } -}; - -@interface ImGui_ImplOSX_Window: NSWindow -@end - -@implementation ImGui_ImplOSX_Window - -- (BOOL)canBecomeKeyWindow -{ - return YES; -} - -@end - -static void ConvertNSRect(NSScreen* screen, NSRect* r) -{ - r->origin.y = screen.frame.size.height - r->origin.y - r->size.height; -} - -static void ImGui_ImplOSX_CreateWindow(ImGuiViewport* viewport) -{ - ImGui_ImplOSX_Data* bd = ImGui_ImplOSX_GetBackendData(); - ImGuiViewportDataOSX* data = IM_NEW(ImGuiViewportDataOSX)(); - viewport->PlatformUserData = data; - - NSScreen* screen = bd->Window.screen; - NSRect rect = NSMakeRect(viewport->Pos.x, viewport->Pos.y, viewport->Size.x, viewport->Size.y); - ConvertNSRect(screen, &rect); - - NSWindowStyleMask styleMask = 0; - if (viewport->Flags & ImGuiViewportFlags_NoDecoration) - styleMask |= NSWindowStyleMaskBorderless; - else - styleMask |= NSWindowStyleMaskTitled | NSWindowStyleMaskResizable | NSWindowStyleMaskClosable | NSWindowStyleMaskMiniaturizable; - - NSWindow* window = [[ImGui_ImplOSX_Window alloc] initWithContentRect:rect - styleMask:styleMask - backing:NSBackingStoreBuffered - defer:YES - screen:screen]; - if (viewport->Flags & ImGuiViewportFlags_TopMost) - [window setLevel:NSFloatingWindowLevel]; - - window.title = @"Untitled"; - window.opaque = YES; - - KeyEventResponder* view = [[KeyEventResponder alloc] initWithFrame:rect]; - if (floor(NSAppKitVersionNumber) > NSAppKitVersionNumber10_6) - [view setWantsBestResolutionOpenGLSurface:YES]; - - window.contentView = view; - - data->Window = window; - data->WindowOwned = true; - viewport->PlatformRequestResize = false; - viewport->PlatformHandle = viewport->PlatformHandleRaw = (__bridge_retained void*)window; -} - -static void ImGui_ImplOSX_DestroyWindow(ImGuiViewport* viewport) -{ - NSWindow* window = (__bridge_transfer NSWindow*)viewport->PlatformHandleRaw; - window = nil; - - if (ImGuiViewportDataOSX* data = (ImGuiViewportDataOSX*)viewport->PlatformUserData) - { - NSWindow* window = data->Window; - if (window != nil && data->WindowOwned) - { - window.contentView = nil; - window.contentViewController = nil; - [window orderOut:nil]; - } - data->Window = nil; - IM_DELETE(data); - } - viewport->PlatformUserData = viewport->PlatformHandle = viewport->PlatformHandleRaw = nullptr; -} - -static void ImGui_ImplOSX_ShowWindow(ImGuiViewport* viewport) -{ - ImGuiViewportDataOSX* data = (ImGuiViewportDataOSX*)viewport->PlatformUserData; - IM_ASSERT(data->Window != 0); - - if (viewport->Flags & ImGuiViewportFlags_NoFocusOnAppearing) - [data->Window orderFront:nil]; - else - [data->Window makeKeyAndOrderFront:nil]; - - [data->Window setIsVisible:YES]; -} - -static ImVec2 ImGui_ImplOSX_GetWindowPos(ImGuiViewport* viewport) -{ - ImGuiViewportDataOSX* data = (ImGuiViewportDataOSX*)viewport->PlatformUserData; - IM_ASSERT(data->Window != 0); - - NSWindow* window = data->Window; - NSScreen* screen = window.screen; - NSSize size = screen.frame.size; - NSRect frame = window.frame; - NSRect rect = window.contentLayoutRect; - return ImVec2(frame.origin.x, size.height - frame.origin.y - rect.size.height); -} - -static void ImGui_ImplOSX_SetWindowPos(ImGuiViewport* viewport, ImVec2 pos) -{ - ImGuiViewportDataOSX* data = (ImGuiViewportDataOSX*)viewport->PlatformUserData; - IM_ASSERT(data->Window != 0); - - NSWindow* window = data->Window; - NSSize size = window.frame.size; - - NSRect r = NSMakeRect(pos.x, pos.y, size.width, size.height); - ConvertNSRect(window.screen, &r); - [window setFrameOrigin:r.origin]; -} - -static ImVec2 ImGui_ImplOSX_GetWindowSize(ImGuiViewport* viewport) -{ - ImGuiViewportDataOSX* data = (ImGuiViewportDataOSX*)viewport->PlatformUserData; - IM_ASSERT(data->Window != 0); - - NSWindow* window = data->Window; - NSSize size = window.contentLayoutRect.size; - return ImVec2(size.width, size.height); -} - -static void ImGui_ImplOSX_SetWindowSize(ImGuiViewport* viewport, ImVec2 size) -{ - ImGuiViewportDataOSX* data = (ImGuiViewportDataOSX*)viewport->PlatformUserData; - IM_ASSERT(data->Window != 0); - - NSWindow* window = data->Window; - NSRect rect = window.frame; - rect.origin.y -= (size.y - rect.size.height); - rect.size.width = size.x; - rect.size.height = size.y; - [window setFrame:rect display:YES]; -} - -static void ImGui_ImplOSX_SetWindowFocus(ImGuiViewport* viewport) -{ - ImGui_ImplOSX_Data* bd = ImGui_ImplOSX_GetBackendData(); - ImGuiViewportDataOSX* data = (ImGuiViewportDataOSX*)viewport->PlatformUserData; - IM_ASSERT(data->Window != 0); - [data->Window makeKeyAndOrderFront:bd->Window]; -} - -static bool ImGui_ImplOSX_GetWindowFocus(ImGuiViewport* viewport) -{ - ImGuiViewportDataOSX* data = (ImGuiViewportDataOSX*)viewport->PlatformUserData; - IM_ASSERT(data->Window != 0); - - return data->Window.isKeyWindow; -} - -static bool ImGui_ImplOSX_GetWindowMinimized(ImGuiViewport* viewport) -{ - ImGuiViewportDataOSX* data = (ImGuiViewportDataOSX*)viewport->PlatformUserData; - IM_ASSERT(data->Window != 0); - - return data->Window.isMiniaturized; -} - -static void ImGui_ImplOSX_SetWindowTitle(ImGuiViewport* viewport, const char* title) -{ - ImGuiViewportDataOSX* data = (ImGuiViewportDataOSX*)viewport->PlatformUserData; - IM_ASSERT(data->Window != 0); - - data->Window.title = [NSString stringWithUTF8String:title]; -} - -static void ImGui_ImplOSX_SetWindowAlpha(ImGuiViewport* viewport, float alpha) -{ - ImGuiViewportDataOSX* data = (ImGuiViewportDataOSX*)viewport->PlatformUserData; - IM_ASSERT(data->Window != 0); - IM_ASSERT(alpha >= 0.0f && alpha <= 1.0f); - - data->Window.alphaValue = alpha; -} - -static float ImGui_ImplOSX_GetWindowDpiScale(ImGuiViewport* viewport) -{ - ImGuiViewportDataOSX* data = (ImGuiViewportDataOSX*)viewport->PlatformUserData; - IM_ASSERT(data->Window != 0); - - return data->Window.backingScaleFactor; -} - -static void ImGui_ImplOSX_UpdateMonitors() -{ - ImGuiPlatformIO& platform_io = ImGui::GetPlatformIO(); - platform_io.Monitors.resize(0); - - for (NSScreen* screen in NSScreen.screens) - { - NSRect frame = screen.frame; - NSRect visibleFrame = screen.visibleFrame; - - ImGuiPlatformMonitor imgui_monitor; - imgui_monitor.MainPos = ImVec2(frame.origin.x, frame.origin.y); - imgui_monitor.MainSize = ImVec2(frame.size.width, frame.size.height); - imgui_monitor.WorkPos = ImVec2(visibleFrame.origin.x, visibleFrame.origin.y); - imgui_monitor.WorkSize = ImVec2(visibleFrame.size.width, visibleFrame.size.height); - imgui_monitor.DpiScale = screen.backingScaleFactor; - imgui_monitor.PlatformHandle = (__bridge_retained void*)screen; - - platform_io.Monitors.push_back(imgui_monitor); - } -} - -static void ImGui_ImplOSX_InitPlatformInterface() -{ - ImGui_ImplOSX_Data* bd = ImGui_ImplOSX_GetBackendData(); - ImGui_ImplOSX_UpdateMonitors(); - - // Register platform interface (will be coupled with a renderer interface) - ImGuiPlatformIO& platform_io = ImGui::GetPlatformIO(); - platform_io.Platform_CreateWindow = ImGui_ImplOSX_CreateWindow; - platform_io.Platform_DestroyWindow = ImGui_ImplOSX_DestroyWindow; - platform_io.Platform_ShowWindow = ImGui_ImplOSX_ShowWindow; - platform_io.Platform_SetWindowPos = ImGui_ImplOSX_SetWindowPos; - platform_io.Platform_GetWindowPos = ImGui_ImplOSX_GetWindowPos; - platform_io.Platform_SetWindowSize = ImGui_ImplOSX_SetWindowSize; - platform_io.Platform_GetWindowSize = ImGui_ImplOSX_GetWindowSize; - platform_io.Platform_SetWindowFocus = ImGui_ImplOSX_SetWindowFocus; - platform_io.Platform_GetWindowFocus = ImGui_ImplOSX_GetWindowFocus; - platform_io.Platform_GetWindowMinimized = ImGui_ImplOSX_GetWindowMinimized; - platform_io.Platform_SetWindowTitle = ImGui_ImplOSX_SetWindowTitle; - platform_io.Platform_SetWindowAlpha = ImGui_ImplOSX_SetWindowAlpha; - platform_io.Platform_GetWindowDpiScale = ImGui_ImplOSX_GetWindowDpiScale; // FIXME-DPI - - // Register main window handle (which is owned by the main application, not by us) - ImGuiViewport* main_viewport = ImGui::GetMainViewport(); - ImGuiViewportDataOSX* data = IM_NEW(ImGuiViewportDataOSX)(); - data->Window = bd->Window; - data->WindowOwned = false; - main_viewport->PlatformUserData = data; - main_viewport->PlatformHandle = (__bridge void*)bd->Window; - - [NSNotificationCenter.defaultCenter addObserver:bd->Observer - selector:@selector(displaysDidChange:) - name:NSApplicationDidChangeScreenParametersNotification - object:nil]; -} - -static void ImGui_ImplOSX_ShutdownPlatformInterface() -{ - ImGui_ImplOSX_Data* bd = ImGui_ImplOSX_GetBackendData(); - [NSNotificationCenter.defaultCenter removeObserver:bd->Observer - name:NSApplicationDidChangeScreenParametersNotification - object:nil]; - bd->Observer = nullptr; - bd->Window = nullptr; - if (bd->Monitor != nullptr) - { - [NSEvent removeMonitor:bd->Monitor]; - bd->Monitor = nullptr; - } - - ImGuiViewport* main_viewport = ImGui::GetMainViewport(); - ImGuiViewportDataOSX* data = (ImGuiViewportDataOSX*)main_viewport->PlatformUserData; - IM_DELETE(data); - main_viewport->PlatformUserData = nullptr; - ImGui::DestroyPlatformWindows(); -} - -//----------------------------------------------------------------------------- - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_sdl2.cpp b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_sdl2.cpp deleted file mode 100644 index 8baebd8..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_sdl2.cpp +++ /dev/null @@ -1,1070 +0,0 @@ -// dear imgui: Platform Backend for SDL2 -// This needs to be used along with a Renderer (e.g. DirectX11, OpenGL3, Vulkan..) -// (Info: SDL2 is a cross-platform general purpose library for handling windows, inputs, graphics context creation, etc.) -// (Prefer SDL 2.0.5+ for full feature support.) - -// Implemented features: -// [X] Platform: Clipboard support. -// [X] Platform: Mouse support. Can discriminate Mouse/TouchScreen. -// [X] Platform: Keyboard support. Since 1.87 we are using the io.AddKeyEvent() function. Pass ImGuiKey values to all key functions e.g. ImGui::IsKeyPressed(ImGuiKey_Space). [Legacy SDL_SCANCODE_* values will also be supported unless IMGUI_DISABLE_OBSOLETE_KEYIO is set] -// [X] Platform: Gamepad support. Enabled with 'io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad'. -// [X] Platform: Mouse cursor shape and visibility. Disable with 'io.ConfigFlags |= ImGuiConfigFlags_NoMouseCursorChange'. -// [X] Platform: Multi-viewport support (multiple windows). Enable with 'io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable'. -// Missing features: -// [ ] Platform: Multi-viewport + Minimized windows seems to break mouse wheel events (at least under Windows). -// [x] Platform: Basic IME support. App needs to call 'SDL_SetHint(SDL_HINT_IME_SHOW_UI, "1");' before SDL_CreateWindow()!. - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -// CHANGELOG -// (minor and older changes stripped away, please see git history for details) -// 2023-XX-XX: Platform: Added support for multiple windows via the ImGuiPlatformIO interface. -// 2023-10-05: Inputs: Added support for extra ImGuiKey values: F13 to F24 function keys, app back/forward keys. -// 2023-04-06: Inputs: Avoid calling SDL_StartTextInput()/SDL_StopTextInput() as they don't only pertain to IME. It's unclear exactly what their relation is to IME. (#6306) -// 2023-04-04: Inputs: Added support for io.AddMouseSourceEvent() to discriminate ImGuiMouseSource_Mouse/ImGuiMouseSource_TouchScreen. (#2702) -// 2023-02-23: Accept SDL_GetPerformanceCounter() not returning a monotonically increasing value. (#6189, #6114, #3644) -// 2023-02-07: Implement IME handler (io.SetPlatformImeDataFn will call SDL_SetTextInputRect()/SDL_StartTextInput()). -// 2023-02-07: *BREAKING CHANGE* Renamed this backend file from imgui_impl_sdl.cpp/.h to imgui_impl_sdl2.cpp/.h in prevision for the future release of SDL3. -// 2023-02-02: Avoid calling SDL_SetCursor() when cursor has not changed, as the function is surprisingly costly on Mac with latest SDL (may be fixed in next SDL version). -// 2023-02-02: Added support for SDL 2.0.18+ preciseX/preciseY mouse wheel data for smooth scrolling + Scaling X value on Emscripten (bug?). (#4019, #6096) -// 2023-02-02: Removed SDL_MOUSEWHEEL value clamping, as values seem correct in latest Emscripten. (#4019) -// 2023-02-01: Flipping SDL_MOUSEWHEEL 'wheel.x' value to match other backends and offer consistent horizontal scrolling direction. (#4019, #6096, #1463) -// 2022-10-11: Using 'nullptr' instead of 'NULL' as per our switch to C++11. -// 2022-09-26: Inputs: Disable SDL 2.0.22 new "auto capture" (SDL_HINT_MOUSE_AUTO_CAPTURE) which prevents drag and drop across windows for multi-viewport support + don't capture when drag and dropping. (#5710) -// 2022-09-26: Inputs: Renamed ImGuiKey_ModXXX introduced in 1.87 to ImGuiMod_XXX (old names still supported). -// 2022-03-22: Inputs: Fix mouse position issues when dragging outside of boundaries. SDL_CaptureMouse() erroneously still gives out LEAVE events when hovering OS decorations. -// 2022-03-22: Inputs: Added support for extra mouse buttons (SDL_BUTTON_X1/SDL_BUTTON_X2). -// 2022-02-04: Added SDL_Renderer* parameter to ImGui_ImplSDL2_InitForSDLRenderer(), so we can use SDL_GetRendererOutputSize() instead of SDL_GL_GetDrawableSize() when bound to a SDL_Renderer. -// 2022-01-26: Inputs: replaced short-lived io.AddKeyModsEvent() (added two weeks ago) with io.AddKeyEvent() using ImGuiKey_ModXXX flags. Sorry for the confusion. -// 2021-01-20: Inputs: calling new io.AddKeyAnalogEvent() for gamepad support, instead of writing directly to io.NavInputs[]. -// 2022-01-17: Inputs: calling new io.AddMousePosEvent(), io.AddMouseButtonEvent(), io.AddMouseWheelEvent() API (1.87+). -// 2022-01-17: Inputs: always update key mods next and before key event (not in NewFrame) to fix input queue with very low framerates. -// 2022-01-12: Update mouse inputs using SDL_MOUSEMOTION/SDL_WINDOWEVENT_LEAVE + fallback to provide it when focused but not hovered/captured. More standard and will allow us to pass it to future input queue API. -// 2022-01-12: Maintain our own copy of MouseButtonsDown mask instead of using ImGui::IsAnyMouseDown() which will be obsoleted. -// 2022-01-10: Inputs: calling new io.AddKeyEvent(), io.AddKeyModsEvent() + io.SetKeyEventNativeData() API (1.87+). Support for full ImGuiKey range. -// 2021-08-17: Calling io.AddFocusEvent() on SDL_WINDOWEVENT_FOCUS_GAINED/SDL_WINDOWEVENT_FOCUS_LOST. -// 2021-07-29: Inputs: MousePos is correctly reported when the host platform window is hovered but not focused (using SDL_GetMouseFocus() + SDL_HINT_MOUSE_FOCUS_CLICKTHROUGH, requires SDL 2.0.5+) -// 2021-06:29: *BREAKING CHANGE* Removed 'SDL_Window* window' parameter to ImGui_ImplSDL2_NewFrame() which was unnecessary. -// 2021-06-29: Reorganized backend to pull data from a single structure to facilitate usage with multiple-contexts (all g_XXXX access changed to bd->XXXX). -// 2021-03-22: Rework global mouse pos availability check listing supported platforms explicitly, effectively fixing mouse access on Raspberry Pi. (#2837, #3950) -// 2020-05-25: Misc: Report a zero display-size when window is minimized, to be consistent with other backends. -// 2020-02-20: Inputs: Fixed mapping for ImGuiKey_KeyPadEnter (using SDL_SCANCODE_KP_ENTER instead of SDL_SCANCODE_RETURN2). -// 2019-12-17: Inputs: On Wayland, use SDL_GetMouseState (because there is no global mouse state). -// 2019-12-05: Inputs: Added support for ImGuiMouseCursor_NotAllowed mouse cursor. -// 2019-07-21: Inputs: Added mapping for ImGuiKey_KeyPadEnter. -// 2019-04-23: Inputs: Added support for SDL_GameController (if ImGuiConfigFlags_NavEnableGamepad is set by user application). -// 2019-03-12: Misc: Preserve DisplayFramebufferScale when main window is minimized. -// 2018-12-21: Inputs: Workaround for Android/iOS which don't seem to handle focus related calls. -// 2018-11-30: Misc: Setting up io.BackendPlatformName so it can be displayed in the About Window. -// 2018-11-14: Changed the signature of ImGui_ImplSDL2_ProcessEvent() to take a 'const SDL_Event*'. -// 2018-08-01: Inputs: Workaround for Emscripten which doesn't seem to handle focus related calls. -// 2018-06-29: Inputs: Added support for the ImGuiMouseCursor_Hand cursor. -// 2018-06-08: Misc: Extracted imgui_impl_sdl.cpp/.h away from the old combined SDL2+OpenGL/Vulkan examples. -// 2018-06-08: Misc: ImGui_ImplSDL2_InitForOpenGL() now takes a SDL_GLContext parameter. -// 2018-05-09: Misc: Fixed clipboard paste memory leak (we didn't call SDL_FreeMemory on the data returned by SDL_GetClipboardText). -// 2018-03-20: Misc: Setup io.BackendFlags ImGuiBackendFlags_HasMouseCursors flag + honor ImGuiConfigFlags_NoMouseCursorChange flag. -// 2018-02-16: Inputs: Added support for mouse cursors, honoring ImGui::GetMouseCursor() value. -// 2018-02-06: Misc: Removed call to ImGui::Shutdown() which is not available from 1.60 WIP, user needs to call CreateContext/DestroyContext themselves. -// 2018-02-06: Inputs: Added mapping for ImGuiKey_Space. -// 2018-02-05: Misc: Using SDL_GetPerformanceCounter() instead of SDL_GetTicks() to be able to handle very high framerate (1000+ FPS). -// 2018-02-05: Inputs: Keyboard mapping is using scancodes everywhere instead of a confusing mixture of keycodes and scancodes. -// 2018-01-20: Inputs: Added Horizontal Mouse Wheel support. -// 2018-01-19: Inputs: When available (SDL 2.0.4+) using SDL_CaptureMouse() to retrieve coordinates outside of client area when dragging. Otherwise (SDL 2.0.3 and before) testing for SDL_WINDOW_INPUT_FOCUS instead of SDL_WINDOW_MOUSE_FOCUS. -// 2018-01-18: Inputs: Added mapping for ImGuiKey_Insert. -// 2017-08-25: Inputs: MousePos set to -FLT_MAX,-FLT_MAX when mouse is unavailable/missing (instead of -1,-1). -// 2016-10-15: Misc: Added a void* user_data parameter to Clipboard function handlers. - -#include "imgui.h" -#ifndef IMGUI_DISABLE -#include "imgui_impl_sdl2.h" - -// Clang warnings with -Weverything -#if defined(__clang__) -#pragma clang diagnostic push -#pragma clang diagnostic ignored "-Wimplicit-int-float-conversion" // warning: implicit conversion from 'xxx' to 'float' may lose precision -#endif - -// SDL -// (the multi-viewports feature requires SDL features supported from SDL 2.0.4+. SDL 2.0.5+ is highly recommended) -#include -#include -#if defined(__APPLE__) -#include -#endif - -#if SDL_VERSION_ATLEAST(2,0,4) && !defined(__EMSCRIPTEN__) && !defined(__ANDROID__) && !(defined(__APPLE__) && TARGET_OS_IOS) && !defined(__amigaos4__) -#define SDL_HAS_CAPTURE_AND_GLOBAL_MOUSE 1 -#else -#define SDL_HAS_CAPTURE_AND_GLOBAL_MOUSE 0 -#endif -#define SDL_HAS_WINDOW_ALPHA SDL_VERSION_ATLEAST(2,0,5) -#define SDL_HAS_ALWAYS_ON_TOP SDL_VERSION_ATLEAST(2,0,5) -#define SDL_HAS_USABLE_DISPLAY_BOUNDS SDL_VERSION_ATLEAST(2,0,5) -#define SDL_HAS_PER_MONITOR_DPI SDL_VERSION_ATLEAST(2,0,4) -#define SDL_HAS_VULKAN SDL_VERSION_ATLEAST(2,0,6) -#define SDL_HAS_DISPLAY_EVENT SDL_VERSION_ATLEAST(2,0,9) -#if !SDL_HAS_VULKAN -static const Uint32 SDL_WINDOW_VULKAN = 0x10000000; -#endif - -// SDL Data -struct ImGui_ImplSDL2_Data -{ - SDL_Window* Window; - SDL_Renderer* Renderer; - Uint64 Time; - Uint32 MouseWindowID; - int MouseButtonsDown; - SDL_Cursor* MouseCursors[ImGuiMouseCursor_COUNT]; - SDL_Cursor* LastMouseCursor; - int PendingMouseLeaveFrame; - char* ClipboardTextData; - bool MouseCanUseGlobalState; - bool MouseCanReportHoveredViewport; // This is hard to use/unreliable on SDL so we'll set ImGuiBackendFlags_HasMouseHoveredViewport dynamically based on state. - bool UseVulkan; - bool WantUpdateMonitors; - - ImGui_ImplSDL2_Data() { memset((void*)this, 0, sizeof(*this)); } -}; - -// Backend data stored in io.BackendPlatformUserData to allow support for multiple Dear ImGui contexts -// It is STRONGLY preferred that you use docking branch with multi-viewports (== single Dear ImGui context + multiple windows) instead of multiple Dear ImGui contexts. -// FIXME: multi-context support is not well tested and probably dysfunctional in this backend. -// FIXME: some shared resources (mouse cursor shape, gamepad) are mishandled when using multi-context. -static ImGui_ImplSDL2_Data* ImGui_ImplSDL2_GetBackendData() -{ - return ImGui::GetCurrentContext() ? (ImGui_ImplSDL2_Data*)ImGui::GetIO().BackendPlatformUserData : nullptr; -} - -// Forward Declarations -static void ImGui_ImplSDL2_UpdateMonitors(); -static void ImGui_ImplSDL2_InitPlatformInterface(SDL_Window* window, void* sdl_gl_context); -static void ImGui_ImplSDL2_ShutdownPlatformInterface(); - -// Functions -static const char* ImGui_ImplSDL2_GetClipboardText(void*) -{ - ImGui_ImplSDL2_Data* bd = ImGui_ImplSDL2_GetBackendData(); - if (bd->ClipboardTextData) - SDL_free(bd->ClipboardTextData); - bd->ClipboardTextData = SDL_GetClipboardText(); - return bd->ClipboardTextData; -} - -static void ImGui_ImplSDL2_SetClipboardText(void*, const char* text) -{ - SDL_SetClipboardText(text); -} - -// Note: native IME will only display if user calls SDL_SetHint(SDL_HINT_IME_SHOW_UI, "1") _before_ SDL_CreateWindow(). -static void ImGui_ImplSDL2_SetPlatformImeData(ImGuiViewport* viewport, ImGuiPlatformImeData* data) -{ - if (data->WantVisible) - { - SDL_Rect r; - r.x = (int)(data->InputPos.x - viewport->Pos.x); - r.y = (int)(data->InputPos.y - viewport->Pos.y + data->InputLineHeight); - r.w = 1; - r.h = (int)data->InputLineHeight; - SDL_SetTextInputRect(&r); - } -} - -static ImGuiKey ImGui_ImplSDL2_KeycodeToImGuiKey(int keycode) -{ - switch (keycode) - { - case SDLK_TAB: return ImGuiKey_Tab; - case SDLK_LEFT: return ImGuiKey_LeftArrow; - case SDLK_RIGHT: return ImGuiKey_RightArrow; - case SDLK_UP: return ImGuiKey_UpArrow; - case SDLK_DOWN: return ImGuiKey_DownArrow; - case SDLK_PAGEUP: return ImGuiKey_PageUp; - case SDLK_PAGEDOWN: return ImGuiKey_PageDown; - case SDLK_HOME: return ImGuiKey_Home; - case SDLK_END: return ImGuiKey_End; - case SDLK_INSERT: return ImGuiKey_Insert; - case SDLK_DELETE: return ImGuiKey_Delete; - case SDLK_BACKSPACE: return ImGuiKey_Backspace; - case SDLK_SPACE: return ImGuiKey_Space; - case SDLK_RETURN: return ImGuiKey_Enter; - case SDLK_ESCAPE: return ImGuiKey_Escape; - case SDLK_QUOTE: return ImGuiKey_Apostrophe; - case SDLK_COMMA: return ImGuiKey_Comma; - case SDLK_MINUS: return ImGuiKey_Minus; - case SDLK_PERIOD: return ImGuiKey_Period; - case SDLK_SLASH: return ImGuiKey_Slash; - case SDLK_SEMICOLON: return ImGuiKey_Semicolon; - case SDLK_EQUALS: return ImGuiKey_Equal; - case SDLK_LEFTBRACKET: return ImGuiKey_LeftBracket; - case SDLK_BACKSLASH: return ImGuiKey_Backslash; - case SDLK_RIGHTBRACKET: return ImGuiKey_RightBracket; - case SDLK_BACKQUOTE: return ImGuiKey_GraveAccent; - case SDLK_CAPSLOCK: return ImGuiKey_CapsLock; - case SDLK_SCROLLLOCK: return ImGuiKey_ScrollLock; - case SDLK_NUMLOCKCLEAR: return ImGuiKey_NumLock; - case SDLK_PRINTSCREEN: return ImGuiKey_PrintScreen; - case SDLK_PAUSE: return ImGuiKey_Pause; - case SDLK_KP_0: return ImGuiKey_Keypad0; - case SDLK_KP_1: return ImGuiKey_Keypad1; - case SDLK_KP_2: return ImGuiKey_Keypad2; - case SDLK_KP_3: return ImGuiKey_Keypad3; - case SDLK_KP_4: return ImGuiKey_Keypad4; - case SDLK_KP_5: return ImGuiKey_Keypad5; - case SDLK_KP_6: return ImGuiKey_Keypad6; - case SDLK_KP_7: return ImGuiKey_Keypad7; - case SDLK_KP_8: return ImGuiKey_Keypad8; - case SDLK_KP_9: return ImGuiKey_Keypad9; - case SDLK_KP_PERIOD: return ImGuiKey_KeypadDecimal; - case SDLK_KP_DIVIDE: return ImGuiKey_KeypadDivide; - case SDLK_KP_MULTIPLY: return ImGuiKey_KeypadMultiply; - case SDLK_KP_MINUS: return ImGuiKey_KeypadSubtract; - case SDLK_KP_PLUS: return ImGuiKey_KeypadAdd; - case SDLK_KP_ENTER: return ImGuiKey_KeypadEnter; - case SDLK_KP_EQUALS: return ImGuiKey_KeypadEqual; - case SDLK_LCTRL: return ImGuiKey_LeftCtrl; - case SDLK_LSHIFT: return ImGuiKey_LeftShift; - case SDLK_LALT: return ImGuiKey_LeftAlt; - case SDLK_LGUI: return ImGuiKey_LeftSuper; - case SDLK_RCTRL: return ImGuiKey_RightCtrl; - case SDLK_RSHIFT: return ImGuiKey_RightShift; - case SDLK_RALT: return ImGuiKey_RightAlt; - case SDLK_RGUI: return ImGuiKey_RightSuper; - case SDLK_APPLICATION: return ImGuiKey_Menu; - case SDLK_0: return ImGuiKey_0; - case SDLK_1: return ImGuiKey_1; - case SDLK_2: return ImGuiKey_2; - case SDLK_3: return ImGuiKey_3; - case SDLK_4: return ImGuiKey_4; - case SDLK_5: return ImGuiKey_5; - case SDLK_6: return ImGuiKey_6; - case SDLK_7: return ImGuiKey_7; - case SDLK_8: return ImGuiKey_8; - case SDLK_9: return ImGuiKey_9; - case SDLK_a: return ImGuiKey_A; - case SDLK_b: return ImGuiKey_B; - case SDLK_c: return ImGuiKey_C; - case SDLK_d: return ImGuiKey_D; - case SDLK_e: return ImGuiKey_E; - case SDLK_f: return ImGuiKey_F; - case SDLK_g: return ImGuiKey_G; - case SDLK_h: return ImGuiKey_H; - case SDLK_i: return ImGuiKey_I; - case SDLK_j: return ImGuiKey_J; - case SDLK_k: return ImGuiKey_K; - case SDLK_l: return ImGuiKey_L; - case SDLK_m: return ImGuiKey_M; - case SDLK_n: return ImGuiKey_N; - case SDLK_o: return ImGuiKey_O; - case SDLK_p: return ImGuiKey_P; - case SDLK_q: return ImGuiKey_Q; - case SDLK_r: return ImGuiKey_R; - case SDLK_s: return ImGuiKey_S; - case SDLK_t: return ImGuiKey_T; - case SDLK_u: return ImGuiKey_U; - case SDLK_v: return ImGuiKey_V; - case SDLK_w: return ImGuiKey_W; - case SDLK_x: return ImGuiKey_X; - case SDLK_y: return ImGuiKey_Y; - case SDLK_z: return ImGuiKey_Z; - case SDLK_F1: return ImGuiKey_F1; - case SDLK_F2: return ImGuiKey_F2; - case SDLK_F3: return ImGuiKey_F3; - case SDLK_F4: return ImGuiKey_F4; - case SDLK_F5: return ImGuiKey_F5; - case SDLK_F6: return ImGuiKey_F6; - case SDLK_F7: return ImGuiKey_F7; - case SDLK_F8: return ImGuiKey_F8; - case SDLK_F9: return ImGuiKey_F9; - case SDLK_F10: return ImGuiKey_F10; - case SDLK_F11: return ImGuiKey_F11; - case SDLK_F12: return ImGuiKey_F12; - case SDLK_F13: return ImGuiKey_F13; - case SDLK_F14: return ImGuiKey_F14; - case SDLK_F15: return ImGuiKey_F15; - case SDLK_F16: return ImGuiKey_F16; - case SDLK_F17: return ImGuiKey_F17; - case SDLK_F18: return ImGuiKey_F18; - case SDLK_F19: return ImGuiKey_F19; - case SDLK_F20: return ImGuiKey_F20; - case SDLK_F21: return ImGuiKey_F21; - case SDLK_F22: return ImGuiKey_F22; - case SDLK_F23: return ImGuiKey_F23; - case SDLK_F24: return ImGuiKey_F24; - case SDLK_AC_BACK: return ImGuiKey_AppBack; - case SDLK_AC_FORWARD: return ImGuiKey_AppForward; - } - return ImGuiKey_None; -} - -static void ImGui_ImplSDL2_UpdateKeyModifiers(SDL_Keymod sdl_key_mods) -{ - ImGuiIO& io = ImGui::GetIO(); - io.AddKeyEvent(ImGuiMod_Ctrl, (sdl_key_mods & KMOD_CTRL) != 0); - io.AddKeyEvent(ImGuiMod_Shift, (sdl_key_mods & KMOD_SHIFT) != 0); - io.AddKeyEvent(ImGuiMod_Alt, (sdl_key_mods & KMOD_ALT) != 0); - io.AddKeyEvent(ImGuiMod_Super, (sdl_key_mods & KMOD_GUI) != 0); -} - -// You can read the io.WantCaptureMouse, io.WantCaptureKeyboard flags to tell if dear imgui wants to use your inputs. -// - When io.WantCaptureMouse is true, do not dispatch mouse input data to your main application, or clear/overwrite your copy of the mouse data. -// - When io.WantCaptureKeyboard is true, do not dispatch keyboard input data to your main application, or clear/overwrite your copy of the keyboard data. -// Generally you may always pass all inputs to dear imgui, and hide them from your application based on those two flags. -// If you have multiple SDL events and some of them are not meant to be used by dear imgui, you may need to filter events based on their windowID field. -bool ImGui_ImplSDL2_ProcessEvent(const SDL_Event* event) -{ - ImGuiIO& io = ImGui::GetIO(); - ImGui_ImplSDL2_Data* bd = ImGui_ImplSDL2_GetBackendData(); - - switch (event->type) - { - case SDL_MOUSEMOTION: - { - ImVec2 mouse_pos((float)event->motion.x, (float)event->motion.y); - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - int window_x, window_y; - SDL_GetWindowPosition(SDL_GetWindowFromID(event->motion.windowID), &window_x, &window_y); - mouse_pos.x += window_x; - mouse_pos.y += window_y; - } - io.AddMouseSourceEvent(event->motion.which == SDL_TOUCH_MOUSEID ? ImGuiMouseSource_TouchScreen : ImGuiMouseSource_Mouse); - io.AddMousePosEvent(mouse_pos.x, mouse_pos.y); - return true; - } - case SDL_MOUSEWHEEL: - { - //IMGUI_DEBUG_LOG("wheel %.2f %.2f, precise %.2f %.2f\n", (float)event->wheel.x, (float)event->wheel.y, event->wheel.preciseX, event->wheel.preciseY); -#if SDL_VERSION_ATLEAST(2,0,18) // If this fails to compile on Emscripten: update to latest Emscripten! - float wheel_x = -event->wheel.preciseX; - float wheel_y = event->wheel.preciseY; -#else - float wheel_x = -(float)event->wheel.x; - float wheel_y = (float)event->wheel.y; -#endif -#ifdef __EMSCRIPTEN__ - wheel_x /= 100.0f; -#endif - io.AddMouseSourceEvent(event->wheel.which == SDL_TOUCH_MOUSEID ? ImGuiMouseSource_TouchScreen : ImGuiMouseSource_Mouse); - io.AddMouseWheelEvent(wheel_x, wheel_y); - return true; - } - case SDL_MOUSEBUTTONDOWN: - case SDL_MOUSEBUTTONUP: - { - int mouse_button = -1; - if (event->button.button == SDL_BUTTON_LEFT) { mouse_button = 0; } - if (event->button.button == SDL_BUTTON_RIGHT) { mouse_button = 1; } - if (event->button.button == SDL_BUTTON_MIDDLE) { mouse_button = 2; } - if (event->button.button == SDL_BUTTON_X1) { mouse_button = 3; } - if (event->button.button == SDL_BUTTON_X2) { mouse_button = 4; } - if (mouse_button == -1) - break; - io.AddMouseSourceEvent(event->button.which == SDL_TOUCH_MOUSEID ? ImGuiMouseSource_TouchScreen : ImGuiMouseSource_Mouse); - io.AddMouseButtonEvent(mouse_button, (event->type == SDL_MOUSEBUTTONDOWN)); - bd->MouseButtonsDown = (event->type == SDL_MOUSEBUTTONDOWN) ? (bd->MouseButtonsDown | (1 << mouse_button)) : (bd->MouseButtonsDown & ~(1 << mouse_button)); - return true; - } - case SDL_TEXTINPUT: - { - io.AddInputCharactersUTF8(event->text.text); - return true; - } - case SDL_KEYDOWN: - case SDL_KEYUP: - { - ImGui_ImplSDL2_UpdateKeyModifiers((SDL_Keymod)event->key.keysym.mod); - ImGuiKey key = ImGui_ImplSDL2_KeycodeToImGuiKey(event->key.keysym.sym); - io.AddKeyEvent(key, (event->type == SDL_KEYDOWN)); - io.SetKeyEventNativeData(key, event->key.keysym.sym, event->key.keysym.scancode, event->key.keysym.scancode); // To support legacy indexing (<1.87 user code). Legacy backend uses SDLK_*** as indices to IsKeyXXX() functions. - return true; - } -#if SDL_HAS_DISPLAY_EVENT - case SDL_DISPLAYEVENT: - { - // 2.0.26 has SDL_DISPLAYEVENT_CONNECTED/SDL_DISPLAYEVENT_DISCONNECTED/SDL_DISPLAYEVENT_ORIENTATION, - // so change of DPI/Scaling are not reflected in this event. (SDL3 has it) - bd->WantUpdateMonitors = true; - return true; - } -#endif - case SDL_WINDOWEVENT: - { - // - When capturing mouse, SDL will send a bunch of conflicting LEAVE/ENTER event on every mouse move, but the final ENTER tends to be right. - // - However we won't get a correct LEAVE event for a captured window. - // - In some cases, when detaching a window from main viewport SDL may send SDL_WINDOWEVENT_ENTER one frame too late, - // causing SDL_WINDOWEVENT_LEAVE on previous frame to interrupt drag operation by clear mouse position. This is why - // we delay process the SDL_WINDOWEVENT_LEAVE events by one frame. See issue #5012 for details. - Uint8 window_event = event->window.event; - if (window_event == SDL_WINDOWEVENT_ENTER) - { - bd->MouseWindowID = event->window.windowID; - bd->PendingMouseLeaveFrame = 0; - } - if (window_event == SDL_WINDOWEVENT_LEAVE) - bd->PendingMouseLeaveFrame = ImGui::GetFrameCount() + 1; - if (window_event == SDL_WINDOWEVENT_FOCUS_GAINED) - io.AddFocusEvent(true); - else if (window_event == SDL_WINDOWEVENT_FOCUS_LOST) - io.AddFocusEvent(false); - if (window_event == SDL_WINDOWEVENT_CLOSE || window_event == SDL_WINDOWEVENT_MOVED || window_event == SDL_WINDOWEVENT_RESIZED) - if (ImGuiViewport* viewport = ImGui::FindViewportByPlatformHandle((void*)SDL_GetWindowFromID(event->window.windowID))) - { - if (window_event == SDL_WINDOWEVENT_CLOSE) - viewport->PlatformRequestClose = true; - if (window_event == SDL_WINDOWEVENT_MOVED) - viewport->PlatformRequestMove = true; - if (window_event == SDL_WINDOWEVENT_RESIZED) - viewport->PlatformRequestResize = true; - return true; - } - return true; - } - } - return false; -} - -static bool ImGui_ImplSDL2_Init(SDL_Window* window, SDL_Renderer* renderer, void* sdl_gl_context) -{ - ImGuiIO& io = ImGui::GetIO(); - IM_ASSERT(io.BackendPlatformUserData == nullptr && "Already initialized a platform backend!"); - - // Check and store if we are on a SDL backend that supports global mouse position - // ("wayland" and "rpi" don't support it, but we chose to use a white-list instead of a black-list) - bool mouse_can_use_global_state = false; -#if SDL_HAS_CAPTURE_AND_GLOBAL_MOUSE - const char* sdl_backend = SDL_GetCurrentVideoDriver(); - const char* global_mouse_whitelist[] = { "windows", "cocoa", "x11", "DIVE", "VMAN" }; - for (int n = 0; n < IM_ARRAYSIZE(global_mouse_whitelist); n++) - if (strncmp(sdl_backend, global_mouse_whitelist[n], strlen(global_mouse_whitelist[n])) == 0) - mouse_can_use_global_state = true; -#endif - - // Setup backend capabilities flags - ImGui_ImplSDL2_Data* bd = IM_NEW(ImGui_ImplSDL2_Data)(); - io.BackendPlatformUserData = (void*)bd; - io.BackendPlatformName = "imgui_impl_sdl2"; - io.BackendFlags |= ImGuiBackendFlags_HasMouseCursors; // We can honor GetMouseCursor() values (optional) - io.BackendFlags |= ImGuiBackendFlags_HasSetMousePos; // We can honor io.WantSetMousePos requests (optional, rarely used) - if (mouse_can_use_global_state) - io.BackendFlags |= ImGuiBackendFlags_PlatformHasViewports; // We can create multi-viewports on the Platform side (optional) - - bd->Window = window; - bd->Renderer = renderer; - - // SDL on Linux/OSX doesn't report events for unfocused windows (see https://github.com/ocornut/imgui/issues/4960) - // We will use 'MouseCanReportHoveredViewport' to set 'ImGuiBackendFlags_HasMouseHoveredViewport' dynamically each frame. - bd->MouseCanUseGlobalState = mouse_can_use_global_state; -#ifndef __APPLE__ - bd->MouseCanReportHoveredViewport = bd->MouseCanUseGlobalState; -#else - bd->MouseCanReportHoveredViewport = false; -#endif - bd->WantUpdateMonitors = true; - - io.SetClipboardTextFn = ImGui_ImplSDL2_SetClipboardText; - io.GetClipboardTextFn = ImGui_ImplSDL2_GetClipboardText; - io.ClipboardUserData = nullptr; - io.SetPlatformImeDataFn = ImGui_ImplSDL2_SetPlatformImeData; - - // Load mouse cursors - bd->MouseCursors[ImGuiMouseCursor_Arrow] = SDL_CreateSystemCursor(SDL_SYSTEM_CURSOR_ARROW); - bd->MouseCursors[ImGuiMouseCursor_TextInput] = SDL_CreateSystemCursor(SDL_SYSTEM_CURSOR_IBEAM); - bd->MouseCursors[ImGuiMouseCursor_ResizeAll] = SDL_CreateSystemCursor(SDL_SYSTEM_CURSOR_SIZEALL); - bd->MouseCursors[ImGuiMouseCursor_ResizeNS] = SDL_CreateSystemCursor(SDL_SYSTEM_CURSOR_SIZENS); - bd->MouseCursors[ImGuiMouseCursor_ResizeEW] = SDL_CreateSystemCursor(SDL_SYSTEM_CURSOR_SIZEWE); - bd->MouseCursors[ImGuiMouseCursor_ResizeNESW] = SDL_CreateSystemCursor(SDL_SYSTEM_CURSOR_SIZENESW); - bd->MouseCursors[ImGuiMouseCursor_ResizeNWSE] = SDL_CreateSystemCursor(SDL_SYSTEM_CURSOR_SIZENWSE); - bd->MouseCursors[ImGuiMouseCursor_Hand] = SDL_CreateSystemCursor(SDL_SYSTEM_CURSOR_HAND); - bd->MouseCursors[ImGuiMouseCursor_NotAllowed] = SDL_CreateSystemCursor(SDL_SYSTEM_CURSOR_NO); - - // Set platform dependent data in viewport - // Our mouse update function expect PlatformHandle to be filled for the main viewport - ImGuiViewport* main_viewport = ImGui::GetMainViewport(); - main_viewport->PlatformHandle = (void*)window; - main_viewport->PlatformHandleRaw = nullptr; - SDL_SysWMinfo info; - SDL_VERSION(&info.version); - if (SDL_GetWindowWMInfo(window, &info)) - { -#if defined(SDL_VIDEO_DRIVER_WINDOWS) - main_viewport->PlatformHandleRaw = (void*)info.info.win.window; -#elif defined(__APPLE__) && defined(SDL_VIDEO_DRIVER_COCOA) - main_viewport->PlatformHandleRaw = (void*)info.info.cocoa.window; -#endif - } - - // From 2.0.5: Set SDL hint to receive mouse click events on window focus, otherwise SDL doesn't emit the event. - // Without this, when clicking to gain focus, our widgets wouldn't activate even though they showed as hovered. - // (This is unfortunately a global SDL setting, so enabling it might have a side-effect on your application. - // It is unlikely to make a difference, but if your app absolutely needs to ignore the initial on-focus click: - // you can ignore SDL_MOUSEBUTTONDOWN events coming right after a SDL_WINDOWEVENT_FOCUS_GAINED) -#ifdef SDL_HINT_MOUSE_FOCUS_CLICKTHROUGH - SDL_SetHint(SDL_HINT_MOUSE_FOCUS_CLICKTHROUGH, "1"); -#endif - - // From 2.0.18: Enable native IME. - // IMPORTANT: This is used at the time of SDL_CreateWindow() so this will only affects secondary windows, if any. - // For the main window to be affected, your application needs to call this manually before calling SDL_CreateWindow(). -#ifdef SDL_HINT_IME_SHOW_UI - SDL_SetHint(SDL_HINT_IME_SHOW_UI, "1"); -#endif - - // From 2.0.22: Disable auto-capture, this is preventing drag and drop across multiple windows (see #5710) -#ifdef SDL_HINT_MOUSE_AUTO_CAPTURE - SDL_SetHint(SDL_HINT_MOUSE_AUTO_CAPTURE, "0"); -#endif - - // We need SDL_CaptureMouse(), SDL_GetGlobalMouseState() from SDL 2.0.4+ to support multiple viewports. - // We left the call to ImGui_ImplSDL2_InitPlatformInterface() outside of #ifdef to avoid unused-function warnings. - if ((io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) && (io.BackendFlags & ImGuiBackendFlags_PlatformHasViewports)) - ImGui_ImplSDL2_InitPlatformInterface(window, sdl_gl_context); - - return true; -} - -bool ImGui_ImplSDL2_InitForOpenGL(SDL_Window* window, void* sdl_gl_context) -{ - return ImGui_ImplSDL2_Init(window, nullptr, sdl_gl_context); -} - -bool ImGui_ImplSDL2_InitForVulkan(SDL_Window* window) -{ -#if !SDL_HAS_VULKAN - IM_ASSERT(0 && "Unsupported"); -#endif - if (!ImGui_ImplSDL2_Init(window, nullptr, nullptr)) - return false; - ImGui_ImplSDL2_Data* bd = ImGui_ImplSDL2_GetBackendData(); - bd->UseVulkan = true; - return true; -} - -bool ImGui_ImplSDL2_InitForD3D(SDL_Window* window) -{ -#if !defined(_WIN32) - IM_ASSERT(0 && "Unsupported"); -#endif - return ImGui_ImplSDL2_Init(window, nullptr, nullptr); -} - -bool ImGui_ImplSDL2_InitForMetal(SDL_Window* window) -{ - return ImGui_ImplSDL2_Init(window, nullptr, nullptr); -} - -bool ImGui_ImplSDL2_InitForSDLRenderer(SDL_Window* window, SDL_Renderer* renderer) -{ - return ImGui_ImplSDL2_Init(window, renderer, nullptr); -} - -bool ImGui_ImplSDL2_InitForOther(SDL_Window* window) -{ - return ImGui_ImplSDL2_Init(window, nullptr, nullptr); -} - -void ImGui_ImplSDL2_Shutdown() -{ - ImGui_ImplSDL2_Data* bd = ImGui_ImplSDL2_GetBackendData(); - IM_ASSERT(bd != nullptr && "No platform backend to shutdown, or already shutdown?"); - ImGuiIO& io = ImGui::GetIO(); - - ImGui_ImplSDL2_ShutdownPlatformInterface(); - - if (bd->ClipboardTextData) - SDL_free(bd->ClipboardTextData); - for (ImGuiMouseCursor cursor_n = 0; cursor_n < ImGuiMouseCursor_COUNT; cursor_n++) - SDL_FreeCursor(bd->MouseCursors[cursor_n]); - bd->LastMouseCursor = nullptr; - - io.BackendPlatformName = nullptr; - io.BackendPlatformUserData = nullptr; - io.BackendFlags &= ~(ImGuiBackendFlags_HasMouseCursors | ImGuiBackendFlags_HasSetMousePos | ImGuiBackendFlags_HasGamepad | ImGuiBackendFlags_PlatformHasViewports | ImGuiBackendFlags_HasMouseHoveredViewport); - IM_DELETE(bd); -} - -// This code is incredibly messy because some of the functions we need for full viewport support are not available in SDL < 2.0.4. -static void ImGui_ImplSDL2_UpdateMouseData() -{ - ImGui_ImplSDL2_Data* bd = ImGui_ImplSDL2_GetBackendData(); - ImGuiIO& io = ImGui::GetIO(); - - // We forward mouse input when hovered or captured (via SDL_MOUSEMOTION) or when focused (below) -#if SDL_HAS_CAPTURE_AND_GLOBAL_MOUSE - // SDL_CaptureMouse() let the OS know e.g. that our imgui drag outside the SDL window boundaries shouldn't e.g. trigger other operations outside - SDL_CaptureMouse((bd->MouseButtonsDown != 0) ? SDL_TRUE : SDL_FALSE); - SDL_Window* focused_window = SDL_GetKeyboardFocus(); - const bool is_app_focused = (focused_window && (bd->Window == focused_window || ImGui::FindViewportByPlatformHandle((void*)focused_window))); -#else - SDL_Window* focused_window = bd->Window; - const bool is_app_focused = (SDL_GetWindowFlags(bd->Window) & SDL_WINDOW_INPUT_FOCUS) != 0; // SDL 2.0.3 and non-windowed systems: single-viewport only -#endif - - if (is_app_focused) - { - // (Optional) Set OS mouse position from Dear ImGui if requested (rarely used, only when ImGuiConfigFlags_NavEnableSetMousePos is enabled by user) - if (io.WantSetMousePos) - { -#if SDL_HAS_CAPTURE_AND_GLOBAL_MOUSE - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - SDL_WarpMouseGlobal((int)io.MousePos.x, (int)io.MousePos.y); - else -#endif - SDL_WarpMouseInWindow(bd->Window, (int)io.MousePos.x, (int)io.MousePos.y); - } - - // (Optional) Fallback to provide mouse position when focused (SDL_MOUSEMOTION already provides this when hovered or captured) - if (bd->MouseCanUseGlobalState && bd->MouseButtonsDown == 0) - { - // Single-viewport mode: mouse position in client window coordinates (io.MousePos is (0,0) when the mouse is on the upper-left corner of the app window) - // Multi-viewport mode: mouse position in OS absolute coordinates (io.MousePos is (0,0) when the mouse is on the upper-left of the primary monitor) - int mouse_x, mouse_y, window_x, window_y; - SDL_GetGlobalMouseState(&mouse_x, &mouse_y); - if (!(io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable)) - { - SDL_GetWindowPosition(focused_window, &window_x, &window_y); - mouse_x -= window_x; - mouse_y -= window_y; - } - io.AddMousePosEvent((float)mouse_x, (float)mouse_y); - } - } - - // (Optional) When using multiple viewports: call io.AddMouseViewportEvent() with the viewport the OS mouse cursor is hovering. - // If ImGuiBackendFlags_HasMouseHoveredViewport is not set by the backend, Dear imGui will ignore this field and infer the information using its flawed heuristic. - // - [!] SDL backend does NOT correctly ignore viewports with the _NoInputs flag. - // Some backend are not able to handle that correctly. If a backend report an hovered viewport that has the _NoInputs flag (e.g. when dragging a window - // for docking, the viewport has the _NoInputs flag in order to allow us to find the viewport under), then Dear ImGui is forced to ignore the value reported - // by the backend, and use its flawed heuristic to guess the viewport behind. - // - [X] SDL backend correctly reports this regardless of another viewport behind focused and dragged from (we need this to find a useful drag and drop target). - if (io.BackendFlags & ImGuiBackendFlags_HasMouseHoveredViewport) - { - ImGuiID mouse_viewport_id = 0; - if (SDL_Window* sdl_mouse_window = SDL_GetWindowFromID(bd->MouseWindowID)) - if (ImGuiViewport* mouse_viewport = ImGui::FindViewportByPlatformHandle((void*)sdl_mouse_window)) - mouse_viewport_id = mouse_viewport->ID; - io.AddMouseViewportEvent(mouse_viewport_id); - } -} - -static void ImGui_ImplSDL2_UpdateMouseCursor() -{ - ImGuiIO& io = ImGui::GetIO(); - if (io.ConfigFlags & ImGuiConfigFlags_NoMouseCursorChange) - return; - ImGui_ImplSDL2_Data* bd = ImGui_ImplSDL2_GetBackendData(); - - ImGuiMouseCursor imgui_cursor = ImGui::GetMouseCursor(); - if (io.MouseDrawCursor || imgui_cursor == ImGuiMouseCursor_None) - { - // Hide OS mouse cursor if imgui is drawing it or if it wants no cursor - SDL_ShowCursor(SDL_FALSE); - } - else - { - // Show OS mouse cursor - SDL_Cursor* expected_cursor = bd->MouseCursors[imgui_cursor] ? bd->MouseCursors[imgui_cursor] : bd->MouseCursors[ImGuiMouseCursor_Arrow]; - if (bd->LastMouseCursor != expected_cursor) - { - SDL_SetCursor(expected_cursor); // SDL function doesn't have an early out (see #6113) - bd->LastMouseCursor = expected_cursor; - } - SDL_ShowCursor(SDL_TRUE); - } -} - -static void ImGui_ImplSDL2_UpdateGamepads() -{ - ImGuiIO& io = ImGui::GetIO(); - - //When this is uncommented I'm getting double inputs. - //if ((io.ConfigFlags & ImGuiConfigFlags_NavEnableGamepad) == 0) // FIXME: Technically feeding gamepad shouldn't depend on this now that they are regular inputs. - // return; - - // Get gamepad - io.BackendFlags &= ~ImGuiBackendFlags_HasGamepad; - SDL_GameController* game_controller = SDL_GameControllerOpen(0); - if (!game_controller) - return; - io.BackendFlags |= ImGuiBackendFlags_HasGamepad; - - // Update gamepad inputs - #define IM_SATURATE(V) (V < 0.0f ? 0.0f : V > 1.0f ? 1.0f : V) - #define MAP_BUTTON(KEY_NO, BUTTON_NO) { io.AddKeyEvent(KEY_NO, SDL_GameControllerGetButton(game_controller, BUTTON_NO) != 0); } - #define MAP_ANALOG(KEY_NO, AXIS_NO, V0, V1) { float vn = (float)(SDL_GameControllerGetAxis(game_controller, AXIS_NO) - V0) / (float)(V1 - V0); vn = IM_SATURATE(vn); io.AddKeyAnalogEvent(KEY_NO, vn > 0.1f, vn); } - const int thumb_dead_zone = 8000; // SDL_gamecontroller.h suggests using this value. - MAP_BUTTON(ImGuiKey_GamepadStart, SDL_CONTROLLER_BUTTON_START); - MAP_BUTTON(ImGuiKey_GamepadBack, SDL_CONTROLLER_BUTTON_BACK); - MAP_BUTTON(ImGuiKey_GamepadFaceLeft, SDL_CONTROLLER_BUTTON_X); // Xbox X, PS Square - MAP_BUTTON(ImGuiKey_GamepadFaceRight, SDL_CONTROLLER_BUTTON_B); // Xbox B, PS Circle - MAP_BUTTON(ImGuiKey_GamepadFaceUp, SDL_CONTROLLER_BUTTON_Y); // Xbox Y, PS Triangle - MAP_BUTTON(ImGuiKey_GamepadFaceDown, SDL_CONTROLLER_BUTTON_A); // Xbox A, PS Cross - MAP_BUTTON(ImGuiKey_GamepadDpadLeft, SDL_CONTROLLER_BUTTON_DPAD_LEFT); - MAP_BUTTON(ImGuiKey_GamepadDpadRight, SDL_CONTROLLER_BUTTON_DPAD_RIGHT); - MAP_BUTTON(ImGuiKey_GamepadDpadUp, SDL_CONTROLLER_BUTTON_DPAD_UP); - MAP_BUTTON(ImGuiKey_GamepadDpadDown, SDL_CONTROLLER_BUTTON_DPAD_DOWN); - MAP_BUTTON(ImGuiKey_GamepadL1, SDL_CONTROLLER_BUTTON_LEFTSHOULDER); - MAP_BUTTON(ImGuiKey_GamepadR1, SDL_CONTROLLER_BUTTON_RIGHTSHOULDER); - MAP_ANALOG(ImGuiKey_GamepadL2, SDL_CONTROLLER_AXIS_TRIGGERLEFT, 0.0f, 32767); - MAP_ANALOG(ImGuiKey_GamepadR2, SDL_CONTROLLER_AXIS_TRIGGERRIGHT, 0.0f, 32767); - MAP_BUTTON(ImGuiKey_GamepadL3, SDL_CONTROLLER_BUTTON_LEFTSTICK); - MAP_BUTTON(ImGuiKey_GamepadR3, SDL_CONTROLLER_BUTTON_RIGHTSTICK); - MAP_ANALOG(ImGuiKey_GamepadLStickLeft, SDL_CONTROLLER_AXIS_LEFTX, -thumb_dead_zone, -32768); - MAP_ANALOG(ImGuiKey_GamepadLStickRight, SDL_CONTROLLER_AXIS_LEFTX, +thumb_dead_zone, +32767); - MAP_ANALOG(ImGuiKey_GamepadLStickUp, SDL_CONTROLLER_AXIS_LEFTY, -thumb_dead_zone, -32768); - MAP_ANALOG(ImGuiKey_GamepadLStickDown, SDL_CONTROLLER_AXIS_LEFTY, +thumb_dead_zone, +32767); - MAP_ANALOG(ImGuiKey_GamepadRStickLeft, SDL_CONTROLLER_AXIS_RIGHTX, -thumb_dead_zone, -32768); - MAP_ANALOG(ImGuiKey_GamepadRStickRight, SDL_CONTROLLER_AXIS_RIGHTX, +thumb_dead_zone, +32767); - MAP_ANALOG(ImGuiKey_GamepadRStickUp, SDL_CONTROLLER_AXIS_RIGHTY, -thumb_dead_zone, -32768); - MAP_ANALOG(ImGuiKey_GamepadRStickDown, SDL_CONTROLLER_AXIS_RIGHTY, +thumb_dead_zone, +32767); - #undef MAP_BUTTON - #undef MAP_ANALOG -} - -// FIXME: Note that doesn't update with DPI/Scaling change only as SDL2 doesn't have an event for it (SDL3 has). -static void ImGui_ImplSDL2_UpdateMonitors() -{ - ImGui_ImplSDL2_Data* bd = ImGui_ImplSDL2_GetBackendData(); - ImGuiPlatformIO& platform_io = ImGui::GetPlatformIO(); - platform_io.Monitors.resize(0); - bd->WantUpdateMonitors = false; - int display_count = SDL_GetNumVideoDisplays(); - for (int n = 0; n < display_count; n++) - { - // Warning: the validity of monitor DPI information on Windows depends on the application DPI awareness settings, which generally needs to be set in the manifest or at runtime. - ImGuiPlatformMonitor monitor; - SDL_Rect r; - SDL_GetDisplayBounds(n, &r); - monitor.MainPos = monitor.WorkPos = ImVec2((float)r.x, (float)r.y); - monitor.MainSize = monitor.WorkSize = ImVec2((float)r.w, (float)r.h); -#if SDL_HAS_USABLE_DISPLAY_BOUNDS - SDL_GetDisplayUsableBounds(n, &r); - monitor.WorkPos = ImVec2((float)r.x, (float)r.y); - monitor.WorkSize = ImVec2((float)r.w, (float)r.h); -#endif -#if SDL_HAS_PER_MONITOR_DPI - // FIXME-VIEWPORT: On MacOS SDL reports actual monitor DPI scale, ignoring OS configuration. We may want to set - // DpiScale to cocoa_window.backingScaleFactor here. - float dpi = 0.0f; - if (!SDL_GetDisplayDPI(n, &dpi, nullptr, nullptr)) - monitor.DpiScale = dpi / 96.0f; -#endif - monitor.PlatformHandle = (void*)(intptr_t)n; - platform_io.Monitors.push_back(monitor); - } -} - -void ImGui_ImplSDL2_NewFrame() -{ - ImGui_ImplSDL2_Data* bd = ImGui_ImplSDL2_GetBackendData(); - IM_ASSERT(bd != nullptr && "Did you call ImGui_ImplSDL2_Init()?"); - ImGuiIO& io = ImGui::GetIO(); - - // Setup display size (every frame to accommodate for window resizing) - int w, h; - int display_w, display_h; - SDL_GetWindowSize(bd->Window, &w, &h); - if (SDL_GetWindowFlags(bd->Window) & SDL_WINDOW_MINIMIZED) - w = h = 0; - if (bd->Renderer != nullptr) - SDL_GetRendererOutputSize(bd->Renderer, &display_w, &display_h); - else - SDL_GL_GetDrawableSize(bd->Window, &display_w, &display_h); - io.DisplaySize = ImVec2((float)w, (float)h); - if (w > 0 && h > 0) - io.DisplayFramebufferScale = ImVec2((float)display_w / w, (float)display_h / h); - - // Update monitors - if (bd->WantUpdateMonitors) - ImGui_ImplSDL2_UpdateMonitors(); - - // Setup time step (we don't use SDL_GetTicks() because it is using millisecond resolution) - // (Accept SDL_GetPerformanceCounter() not returning a monotonically increasing value. Happens in VMs and Emscripten, see #6189, #6114, #3644) - static Uint64 frequency = SDL_GetPerformanceFrequency(); - Uint64 current_time = SDL_GetPerformanceCounter(); - if (current_time <= bd->Time) - current_time = bd->Time + 1; - io.DeltaTime = bd->Time > 0 ? (float)((double)(current_time - bd->Time) / frequency) : (float)(1.0f / 60.0f); - bd->Time = current_time; - - if (bd->PendingMouseLeaveFrame && bd->PendingMouseLeaveFrame >= ImGui::GetFrameCount() && bd->MouseButtonsDown == 0) - { - bd->MouseWindowID = 0; - bd->PendingMouseLeaveFrame = 0; - io.AddMousePosEvent(-FLT_MAX, -FLT_MAX); - } - - // Our io.AddMouseViewportEvent() calls will only be valid when not capturing. - // Technically speaking testing for 'bd->MouseButtonsDown == 0' would be more rygorous, but testing for payload reduces noise and potential side-effects. - if (bd->MouseCanReportHoveredViewport && ImGui::GetDragDropPayload() == nullptr) - io.BackendFlags |= ImGuiBackendFlags_HasMouseHoveredViewport; - else - io.BackendFlags &= ~ImGuiBackendFlags_HasMouseHoveredViewport; - - ImGui_ImplSDL2_UpdateMouseData(); - ImGui_ImplSDL2_UpdateMouseCursor(); - - // Update game controllers (if enabled and available) - ImGui_ImplSDL2_UpdateGamepads(); -} - -//-------------------------------------------------------------------------------------------------------- -// MULTI-VIEWPORT / PLATFORM INTERFACE SUPPORT -// This is an _advanced_ and _optional_ feature, allowing the backend to create and handle multiple viewports simultaneously. -// If you are new to dear imgui or creating a new binding for dear imgui, it is recommended that you completely ignore this section first.. -//-------------------------------------------------------------------------------------------------------- - -// Helper structure we store in the void* RendererUserData field of each ImGuiViewport to easily retrieve our backend data. -struct ImGui_ImplSDL2_ViewportData -{ - SDL_Window* Window; - Uint32 WindowID; - bool WindowOwned; - SDL_GLContext GLContext; - - ImGui_ImplSDL2_ViewportData() { Window = nullptr; WindowID = 0; WindowOwned = false; GLContext = nullptr; } - ~ImGui_ImplSDL2_ViewportData() { IM_ASSERT(Window == nullptr && GLContext == nullptr); } -}; - -static void ImGui_ImplSDL2_CreateWindow(ImGuiViewport* viewport) -{ - ImGui_ImplSDL2_Data* bd = ImGui_ImplSDL2_GetBackendData(); - ImGui_ImplSDL2_ViewportData* vd = IM_NEW(ImGui_ImplSDL2_ViewportData)(); - viewport->PlatformUserData = vd; - - ImGuiViewport* main_viewport = ImGui::GetMainViewport(); - ImGui_ImplSDL2_ViewportData* main_viewport_data = (ImGui_ImplSDL2_ViewportData*)main_viewport->PlatformUserData; - - // Share GL resources with main context - bool use_opengl = (main_viewport_data->GLContext != nullptr); - SDL_GLContext backup_context = nullptr; - if (use_opengl) - { - backup_context = SDL_GL_GetCurrentContext(); - SDL_GL_SetAttribute(SDL_GL_SHARE_WITH_CURRENT_CONTEXT, 1); - SDL_GL_MakeCurrent(main_viewport_data->Window, main_viewport_data->GLContext); - } - - Uint32 sdl_flags = 0; - sdl_flags |= use_opengl ? SDL_WINDOW_OPENGL : (bd->UseVulkan ? SDL_WINDOW_VULKAN : 0); - sdl_flags |= SDL_GetWindowFlags(bd->Window) & SDL_WINDOW_ALLOW_HIGHDPI; - sdl_flags |= SDL_WINDOW_HIDDEN; - sdl_flags |= (viewport->Flags & ImGuiViewportFlags_NoDecoration) ? SDL_WINDOW_BORDERLESS : 0; - sdl_flags |= (viewport->Flags & ImGuiViewportFlags_NoDecoration) ? 0 : SDL_WINDOW_RESIZABLE; -#if !defined(_WIN32) - // See SDL hack in ImGui_ImplSDL2_ShowWindow(). - sdl_flags |= (viewport->Flags & ImGuiViewportFlags_NoTaskBarIcon) ? SDL_WINDOW_SKIP_TASKBAR : 0; -#endif -#if SDL_HAS_ALWAYS_ON_TOP - sdl_flags |= (viewport->Flags & ImGuiViewportFlags_TopMost) ? SDL_WINDOW_ALWAYS_ON_TOP : 0; -#endif - vd->Window = SDL_CreateWindow("No Title Yet", (int)viewport->Pos.x, (int)viewport->Pos.y, (int)viewport->Size.x, (int)viewport->Size.y, sdl_flags); - vd->WindowOwned = true; - if (use_opengl) - { - vd->GLContext = SDL_GL_CreateContext(vd->Window); - SDL_GL_SetSwapInterval(0); - } - if (use_opengl && backup_context) - SDL_GL_MakeCurrent(vd->Window, backup_context); - - viewport->PlatformHandle = (void*)vd->Window; - viewport->PlatformHandleRaw = nullptr; - SDL_SysWMinfo info; - SDL_VERSION(&info.version); - if (SDL_GetWindowWMInfo(vd->Window, &info)) - { -#if defined(SDL_VIDEO_DRIVER_WINDOWS) - viewport->PlatformHandleRaw = info.info.win.window; -#elif defined(__APPLE__) && defined(SDL_VIDEO_DRIVER_COCOA) - viewport->PlatformHandleRaw = (void*)info.info.cocoa.window; -#endif - } -} - -static void ImGui_ImplSDL2_DestroyWindow(ImGuiViewport* viewport) -{ - if (ImGui_ImplSDL2_ViewportData* vd = (ImGui_ImplSDL2_ViewportData*)viewport->PlatformUserData) - { - if (vd->GLContext && vd->WindowOwned) - SDL_GL_DeleteContext(vd->GLContext); - if (vd->Window && vd->WindowOwned) - SDL_DestroyWindow(vd->Window); - vd->GLContext = nullptr; - vd->Window = nullptr; - IM_DELETE(vd); - } - viewport->PlatformUserData = viewport->PlatformHandle = nullptr; -} - -static void ImGui_ImplSDL2_ShowWindow(ImGuiViewport* viewport) -{ - ImGui_ImplSDL2_ViewportData* vd = (ImGui_ImplSDL2_ViewportData*)viewport->PlatformUserData; -#if defined(_WIN32) - HWND hwnd = (HWND)viewport->PlatformHandleRaw; - - // SDL hack: Hide icon from task bar - // Note: SDL 2.0.6+ has a SDL_WINDOW_SKIP_TASKBAR flag which is supported under Windows but the way it create the window breaks our seamless transition. - if (viewport->Flags & ImGuiViewportFlags_NoTaskBarIcon) - { - LONG ex_style = ::GetWindowLong(hwnd, GWL_EXSTYLE); - ex_style &= ~WS_EX_APPWINDOW; - ex_style |= WS_EX_TOOLWINDOW; - ::SetWindowLong(hwnd, GWL_EXSTYLE, ex_style); - } - - // SDL hack: SDL always activate/focus windows :/ - if (viewport->Flags & ImGuiViewportFlags_NoFocusOnAppearing) - { - ::ShowWindow(hwnd, SW_SHOWNA); - return; - } -#endif - - SDL_ShowWindow(vd->Window); -} - -static ImVec2 ImGui_ImplSDL2_GetWindowPos(ImGuiViewport* viewport) -{ - ImGui_ImplSDL2_ViewportData* vd = (ImGui_ImplSDL2_ViewportData*)viewport->PlatformUserData; - int x = 0, y = 0; - SDL_GetWindowPosition(vd->Window, &x, &y); - return ImVec2((float)x, (float)y); -} - -static void ImGui_ImplSDL2_SetWindowPos(ImGuiViewport* viewport, ImVec2 pos) -{ - ImGui_ImplSDL2_ViewportData* vd = (ImGui_ImplSDL2_ViewportData*)viewport->PlatformUserData; - SDL_SetWindowPosition(vd->Window, (int)pos.x, (int)pos.y); -} - -static ImVec2 ImGui_ImplSDL2_GetWindowSize(ImGuiViewport* viewport) -{ - ImGui_ImplSDL2_ViewportData* vd = (ImGui_ImplSDL2_ViewportData*)viewport->PlatformUserData; - int w = 0, h = 0; - SDL_GetWindowSize(vd->Window, &w, &h); - return ImVec2((float)w, (float)h); -} - -static void ImGui_ImplSDL2_SetWindowSize(ImGuiViewport* viewport, ImVec2 size) -{ - ImGui_ImplSDL2_ViewportData* vd = (ImGui_ImplSDL2_ViewportData*)viewport->PlatformUserData; - SDL_SetWindowSize(vd->Window, (int)size.x, (int)size.y); -} - -static void ImGui_ImplSDL2_SetWindowTitle(ImGuiViewport* viewport, const char* title) -{ - ImGui_ImplSDL2_ViewportData* vd = (ImGui_ImplSDL2_ViewportData*)viewport->PlatformUserData; - SDL_SetWindowTitle(vd->Window, title); -} - -#if SDL_HAS_WINDOW_ALPHA -static void ImGui_ImplSDL2_SetWindowAlpha(ImGuiViewport* viewport, float alpha) -{ - ImGui_ImplSDL2_ViewportData* vd = (ImGui_ImplSDL2_ViewportData*)viewport->PlatformUserData; - SDL_SetWindowOpacity(vd->Window, alpha); -} -#endif - -static void ImGui_ImplSDL2_SetWindowFocus(ImGuiViewport* viewport) -{ - ImGui_ImplSDL2_ViewportData* vd = (ImGui_ImplSDL2_ViewportData*)viewport->PlatformUserData; - SDL_RaiseWindow(vd->Window); -} - -static bool ImGui_ImplSDL2_GetWindowFocus(ImGuiViewport* viewport) -{ - ImGui_ImplSDL2_ViewportData* vd = (ImGui_ImplSDL2_ViewportData*)viewport->PlatformUserData; - return (SDL_GetWindowFlags(vd->Window) & SDL_WINDOW_INPUT_FOCUS) != 0; -} - -static bool ImGui_ImplSDL2_GetWindowMinimized(ImGuiViewport* viewport) -{ - ImGui_ImplSDL2_ViewportData* vd = (ImGui_ImplSDL2_ViewportData*)viewport->PlatformUserData; - return (SDL_GetWindowFlags(vd->Window) & SDL_WINDOW_MINIMIZED) != 0; -} - -static void ImGui_ImplSDL2_RenderWindow(ImGuiViewport* viewport, void*) -{ - ImGui_ImplSDL2_ViewportData* vd = (ImGui_ImplSDL2_ViewportData*)viewport->PlatformUserData; - if (vd->GLContext) - SDL_GL_MakeCurrent(vd->Window, vd->GLContext); -} - -static void ImGui_ImplSDL2_SwapBuffers(ImGuiViewport* viewport, void*) -{ - ImGui_ImplSDL2_ViewportData* vd = (ImGui_ImplSDL2_ViewportData*)viewport->PlatformUserData; - if (vd->GLContext) - { - SDL_GL_MakeCurrent(vd->Window, vd->GLContext); - SDL_GL_SwapWindow(vd->Window); - } -} - -// Vulkan support (the Vulkan renderer needs to call a platform-side support function to create the surface) -// SDL is graceful enough to _not_ need so we can safely include this. -#if SDL_HAS_VULKAN -#include -static int ImGui_ImplSDL2_CreateVkSurface(ImGuiViewport* viewport, ImU64 vk_instance, const void* vk_allocator, ImU64* out_vk_surface) -{ - ImGui_ImplSDL2_ViewportData* vd = (ImGui_ImplSDL2_ViewportData*)viewport->PlatformUserData; - (void)vk_allocator; - SDL_bool ret = SDL_Vulkan_CreateSurface(vd->Window, (VkInstance)vk_instance, (VkSurfaceKHR*)out_vk_surface); - return ret ? 0 : 1; // ret ? VK_SUCCESS : VK_NOT_READY -} -#endif // SDL_HAS_VULKAN - -static void ImGui_ImplSDL2_InitPlatformInterface(SDL_Window* window, void* sdl_gl_context) -{ - // Register platform interface (will be coupled with a renderer interface) - ImGuiPlatformIO& platform_io = ImGui::GetPlatformIO(); - platform_io.Platform_CreateWindow = ImGui_ImplSDL2_CreateWindow; - platform_io.Platform_DestroyWindow = ImGui_ImplSDL2_DestroyWindow; - platform_io.Platform_ShowWindow = ImGui_ImplSDL2_ShowWindow; - platform_io.Platform_SetWindowPos = ImGui_ImplSDL2_SetWindowPos; - platform_io.Platform_GetWindowPos = ImGui_ImplSDL2_GetWindowPos; - platform_io.Platform_SetWindowSize = ImGui_ImplSDL2_SetWindowSize; - platform_io.Platform_GetWindowSize = ImGui_ImplSDL2_GetWindowSize; - platform_io.Platform_SetWindowFocus = ImGui_ImplSDL2_SetWindowFocus; - platform_io.Platform_GetWindowFocus = ImGui_ImplSDL2_GetWindowFocus; - platform_io.Platform_GetWindowMinimized = ImGui_ImplSDL2_GetWindowMinimized; - platform_io.Platform_SetWindowTitle = ImGui_ImplSDL2_SetWindowTitle; - platform_io.Platform_RenderWindow = ImGui_ImplSDL2_RenderWindow; - platform_io.Platform_SwapBuffers = ImGui_ImplSDL2_SwapBuffers; -#if SDL_HAS_WINDOW_ALPHA - platform_io.Platform_SetWindowAlpha = ImGui_ImplSDL2_SetWindowAlpha; -#endif -#if SDL_HAS_VULKAN - platform_io.Platform_CreateVkSurface = ImGui_ImplSDL2_CreateVkSurface; -#endif - - // Register main window handle (which is owned by the main application, not by us) - // This is mostly for simplicity and consistency, so that our code (e.g. mouse handling etc.) can use same logic for main and secondary viewports. - ImGuiViewport* main_viewport = ImGui::GetMainViewport(); - ImGui_ImplSDL2_ViewportData* vd = IM_NEW(ImGui_ImplSDL2_ViewportData)(); - vd->Window = window; - vd->WindowID = SDL_GetWindowID(window); - vd->WindowOwned = false; - vd->GLContext = sdl_gl_context; - main_viewport->PlatformUserData = vd; - main_viewport->PlatformHandle = vd->Window; -} - -static void ImGui_ImplSDL2_ShutdownPlatformInterface() -{ - ImGui::DestroyPlatformWindows(); -} - -//----------------------------------------------------------------------------- - -#if defined(__clang__) -#pragma clang diagnostic pop -#endif - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_sdl2.h b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_sdl2.h deleted file mode 100644 index dee37fb..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_sdl2.h +++ /dev/null @@ -1,46 +0,0 @@ -// dear imgui: Platform Backend for SDL2 -// This needs to be used along with a Renderer (e.g. DirectX11, OpenGL3, Vulkan..) -// (Info: SDL2 is a cross-platform general purpose library for handling windows, inputs, graphics context creation, etc.) - -// Implemented features: -// [X] Platform: Clipboard support. -// [X] Platform: Mouse support. Can discriminate Mouse/TouchScreen. -// [X] Platform: Keyboard support. Since 1.87 we are using the io.AddKeyEvent() function. Pass ImGuiKey values to all key functions e.g. ImGui::IsKeyPressed(ImGuiKey_Space). [Legacy SDL_SCANCODE_* values will also be supported unless IMGUI_DISABLE_OBSOLETE_KEYIO is set] -// [X] Platform: Gamepad support. Enabled with 'io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad'. -// [X] Platform: Mouse cursor shape and visibility. Disable with 'io.ConfigFlags |= ImGuiConfigFlags_NoMouseCursorChange'. -// [X] Platform: Multi-viewport support (multiple windows). Enable with 'io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable'. -// Missing features: -// [ ] Platform: Multi-viewport + Minimized windows seems to break mouse wheel events (at least under Windows). -// [x] Platform: Basic IME support. App needs to call 'SDL_SetHint(SDL_HINT_IME_SHOW_UI, "1");' before SDL_CreateWindow()!. - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#pragma once -#include "imgui.h" // IMGUI_IMPL_API -#ifndef IMGUI_DISABLE - -struct SDL_Window; -struct SDL_Renderer; -typedef union SDL_Event SDL_Event; - -IMGUI_IMPL_API bool ImGui_ImplSDL2_InitForOpenGL(SDL_Window* window, void* sdl_gl_context); -IMGUI_IMPL_API bool ImGui_ImplSDL2_InitForVulkan(SDL_Window* window); -IMGUI_IMPL_API bool ImGui_ImplSDL2_InitForD3D(SDL_Window* window); -IMGUI_IMPL_API bool ImGui_ImplSDL2_InitForMetal(SDL_Window* window); -IMGUI_IMPL_API bool ImGui_ImplSDL2_InitForSDLRenderer(SDL_Window* window, SDL_Renderer* renderer); -IMGUI_IMPL_API bool ImGui_ImplSDL2_InitForOther(SDL_Window* window); -IMGUI_IMPL_API void ImGui_ImplSDL2_Shutdown(); -IMGUI_IMPL_API void ImGui_ImplSDL2_NewFrame(); -IMGUI_IMPL_API bool ImGui_ImplSDL2_ProcessEvent(const SDL_Event* event); - -#ifndef IMGUI_DISABLE_OBSOLETE_FUNCTIONS -static inline void ImGui_ImplSDL2_NewFrame(SDL_Window*) { ImGui_ImplSDL2_NewFrame(); } // 1.84: removed unnecessary parameter -#endif - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_sdl3.cpp b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_sdl3.cpp deleted file mode 100644 index 0e91cc7..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_sdl3.cpp +++ /dev/null @@ -1,977 +0,0 @@ -// dear imgui: Platform Backend for SDL3 (*EXPERIMENTAL*) -// This needs to be used along with a Renderer (e.g. DirectX11, OpenGL3, Vulkan..) -// (Info: SDL3 is a cross-platform general purpose library for handling windows, inputs, graphics context creation, etc.) -// (IMPORTANT: SDL 3.0.0 is NOT YET RELEASED. IT IS POSSIBLE THAT ITS SPECS/API WILL CHANGE BEFORE RELEASE) - -// Implemented features: -// [X] Platform: Clipboard support. -// [X] Platform: Mouse support. Can discriminate Mouse/TouchScreen. -// [X] Platform: Keyboard support. Since 1.87 we are using the io.AddKeyEvent() function. Pass ImGuiKey values to all key functions e.g. ImGui::IsKeyPressed(ImGuiKey_Space). [Legacy SDL_SCANCODE_* values will also be supported unless IMGUI_DISABLE_OBSOLETE_KEYIO is set] -// [X] Platform: Gamepad support. Enabled with 'io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad'. -// [X] Platform: Mouse cursor shape and visibility. Disable with 'io.ConfigFlags |= ImGuiConfigFlags_NoMouseCursorChange'. -// [x] Platform: Multi-viewport support (multiple windows). Enable with 'io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable' -> the OS animation effect when window gets created/destroyed is problematic. SDL2 backend doesn't have issue. -// Missing features: -// [ ] Platform: Multi-viewport + Minimized windows seems to break mouse wheel events (at least under Windows). -// [x] Platform: Basic IME support. Position somehow broken in SDL3 + app needs to call 'SDL_SetHint(SDL_HINT_IME_SHOW_UI, "1");' before SDL_CreateWindow()!. - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -// CHANGELOG -// (minor and older changes stripped away, please see git history for details) -// 2023-XX-XX: Platform: Added support for multiple windows via the ImGuiPlatformIO interface. -// 2023-10-05: Inputs: Added support for extra ImGuiKey values: F13 to F24 function keys, app back/forward keys. -// 2023-05-04: Fixed build on Emscripten/iOS/Android. (#6391) -// 2023-04-06: Inputs: Avoid calling SDL_StartTextInput()/SDL_StopTextInput() as they don't only pertain to IME. It's unclear exactly what their relation is to IME. (#6306) -// 2023-04-04: Inputs: Added support for io.AddMouseSourceEvent() to discriminate ImGuiMouseSource_Mouse/ImGuiMouseSource_TouchScreen. (#2702) -// 2023-02-23: Accept SDL_GetPerformanceCounter() not returning a monotonically increasing value. (#6189, #6114, #3644) -// 2023-02-07: Forked "imgui_impl_sdl2" into "imgui_impl_sdl3". Removed version checks for old feature. Refer to imgui_impl_sdl2.cpp for older changelog. - -#include "imgui.h" -#ifndef IMGUI_DISABLE -#include "imgui_impl_sdl3.h" - -// Clang warnings with -Weverything -#if defined(__clang__) -#pragma clang diagnostic push -#pragma clang diagnostic ignored "-Wimplicit-int-float-conversion" // warning: implicit conversion from 'xxx' to 'float' may lose precision -#endif - -// SDL -#include -#include -#if defined(__APPLE__) -#include -#endif - -#if !defined(__EMSCRIPTEN__) && !defined(__ANDROID__) && !(defined(__APPLE__) && TARGET_OS_IOS) && !defined(__amigaos4__) -#define SDL_HAS_CAPTURE_AND_GLOBAL_MOUSE 1 -#else -#define SDL_HAS_CAPTURE_AND_GLOBAL_MOUSE 0 -#endif - -// SDL Data -struct ImGui_ImplSDL3_Data -{ - SDL_Window* Window; - SDL_Renderer* Renderer; - Uint64 Time; - Uint32 MouseWindowID; - int MouseButtonsDown; - SDL_Cursor* MouseCursors[ImGuiMouseCursor_COUNT]; - SDL_Cursor* LastMouseCursor; - int PendingMouseLeaveFrame; - char* ClipboardTextData; - bool MouseCanUseGlobalState; - bool MouseCanReportHoveredViewport; // This is hard to use/unreliable on SDL so we'll set ImGuiBackendFlags_HasMouseHoveredViewport dynamically based on state. - bool UseVulkan; - bool WantUpdateMonitors; - - ImGui_ImplSDL3_Data() { memset((void*)this, 0, sizeof(*this)); } -}; - -// Backend data stored in io.BackendPlatformUserData to allow support for multiple Dear ImGui contexts -// It is STRONGLY preferred that you use docking branch with multi-viewports (== single Dear ImGui context + multiple windows) instead of multiple Dear ImGui contexts. -// FIXME: multi-context support is not well tested and probably dysfunctional in this backend. -// FIXME: some shared resources (mouse cursor shape, gamepad) are mishandled when using multi-context. -static ImGui_ImplSDL3_Data* ImGui_ImplSDL3_GetBackendData() -{ - return ImGui::GetCurrentContext() ? (ImGui_ImplSDL3_Data*)ImGui::GetIO().BackendPlatformUserData : nullptr; -} - -// Forward Declarations -static void ImGui_ImplSDL3_UpdateMonitors(); -static void ImGui_ImplSDL3_InitPlatformInterface(SDL_Window* window, void* sdl_gl_context); -static void ImGui_ImplSDL3_ShutdownPlatformInterface(); - -// Functions -static const char* ImGui_ImplSDL3_GetClipboardText(void*) -{ - ImGui_ImplSDL3_Data* bd = ImGui_ImplSDL3_GetBackendData(); - if (bd->ClipboardTextData) - SDL_free(bd->ClipboardTextData); - bd->ClipboardTextData = SDL_GetClipboardText(); - return bd->ClipboardTextData; -} - -static void ImGui_ImplSDL3_SetClipboardText(void*, const char* text) -{ - SDL_SetClipboardText(text); -} - -static void ImGui_ImplSDL3_SetPlatformImeData(ImGuiViewport* viewport, ImGuiPlatformImeData* data) -{ - if (data->WantVisible) - { - SDL_Rect r; - r.x = (int)(data->InputPos.x - viewport->Pos.x); - r.y = (int)(data->InputPos.y - viewport->Pos.y + data->InputLineHeight); - r.w = 1; - r.h = (int)data->InputLineHeight; - SDL_SetTextInputRect(&r); - } -} - -static ImGuiKey ImGui_ImplSDL3_KeycodeToImGuiKey(int keycode) -{ - switch (keycode) - { - case SDLK_TAB: return ImGuiKey_Tab; - case SDLK_LEFT: return ImGuiKey_LeftArrow; - case SDLK_RIGHT: return ImGuiKey_RightArrow; - case SDLK_UP: return ImGuiKey_UpArrow; - case SDLK_DOWN: return ImGuiKey_DownArrow; - case SDLK_PAGEUP: return ImGuiKey_PageUp; - case SDLK_PAGEDOWN: return ImGuiKey_PageDown; - case SDLK_HOME: return ImGuiKey_Home; - case SDLK_END: return ImGuiKey_End; - case SDLK_INSERT: return ImGuiKey_Insert; - case SDLK_DELETE: return ImGuiKey_Delete; - case SDLK_BACKSPACE: return ImGuiKey_Backspace; - case SDLK_SPACE: return ImGuiKey_Space; - case SDLK_RETURN: return ImGuiKey_Enter; - case SDLK_ESCAPE: return ImGuiKey_Escape; - case SDLK_QUOTE: return ImGuiKey_Apostrophe; - case SDLK_COMMA: return ImGuiKey_Comma; - case SDLK_MINUS: return ImGuiKey_Minus; - case SDLK_PERIOD: return ImGuiKey_Period; - case SDLK_SLASH: return ImGuiKey_Slash; - case SDLK_SEMICOLON: return ImGuiKey_Semicolon; - case SDLK_EQUALS: return ImGuiKey_Equal; - case SDLK_LEFTBRACKET: return ImGuiKey_LeftBracket; - case SDLK_BACKSLASH: return ImGuiKey_Backslash; - case SDLK_RIGHTBRACKET: return ImGuiKey_RightBracket; - case SDLK_BACKQUOTE: return ImGuiKey_GraveAccent; - case SDLK_CAPSLOCK: return ImGuiKey_CapsLock; - case SDLK_SCROLLLOCK: return ImGuiKey_ScrollLock; - case SDLK_NUMLOCKCLEAR: return ImGuiKey_NumLock; - case SDLK_PRINTSCREEN: return ImGuiKey_PrintScreen; - case SDLK_PAUSE: return ImGuiKey_Pause; - case SDLK_KP_0: return ImGuiKey_Keypad0; - case SDLK_KP_1: return ImGuiKey_Keypad1; - case SDLK_KP_2: return ImGuiKey_Keypad2; - case SDLK_KP_3: return ImGuiKey_Keypad3; - case SDLK_KP_4: return ImGuiKey_Keypad4; - case SDLK_KP_5: return ImGuiKey_Keypad5; - case SDLK_KP_6: return ImGuiKey_Keypad6; - case SDLK_KP_7: return ImGuiKey_Keypad7; - case SDLK_KP_8: return ImGuiKey_Keypad8; - case SDLK_KP_9: return ImGuiKey_Keypad9; - case SDLK_KP_PERIOD: return ImGuiKey_KeypadDecimal; - case SDLK_KP_DIVIDE: return ImGuiKey_KeypadDivide; - case SDLK_KP_MULTIPLY: return ImGuiKey_KeypadMultiply; - case SDLK_KP_MINUS: return ImGuiKey_KeypadSubtract; - case SDLK_KP_PLUS: return ImGuiKey_KeypadAdd; - case SDLK_KP_ENTER: return ImGuiKey_KeypadEnter; - case SDLK_KP_EQUALS: return ImGuiKey_KeypadEqual; - case SDLK_LCTRL: return ImGuiKey_LeftCtrl; - case SDLK_LSHIFT: return ImGuiKey_LeftShift; - case SDLK_LALT: return ImGuiKey_LeftAlt; - case SDLK_LGUI: return ImGuiKey_LeftSuper; - case SDLK_RCTRL: return ImGuiKey_RightCtrl; - case SDLK_RSHIFT: return ImGuiKey_RightShift; - case SDLK_RALT: return ImGuiKey_RightAlt; - case SDLK_RGUI: return ImGuiKey_RightSuper; - case SDLK_APPLICATION: return ImGuiKey_Menu; - case SDLK_0: return ImGuiKey_0; - case SDLK_1: return ImGuiKey_1; - case SDLK_2: return ImGuiKey_2; - case SDLK_3: return ImGuiKey_3; - case SDLK_4: return ImGuiKey_4; - case SDLK_5: return ImGuiKey_5; - case SDLK_6: return ImGuiKey_6; - case SDLK_7: return ImGuiKey_7; - case SDLK_8: return ImGuiKey_8; - case SDLK_9: return ImGuiKey_9; - case SDLK_a: return ImGuiKey_A; - case SDLK_b: return ImGuiKey_B; - case SDLK_c: return ImGuiKey_C; - case SDLK_d: return ImGuiKey_D; - case SDLK_e: return ImGuiKey_E; - case SDLK_f: return ImGuiKey_F; - case SDLK_g: return ImGuiKey_G; - case SDLK_h: return ImGuiKey_H; - case SDLK_i: return ImGuiKey_I; - case SDLK_j: return ImGuiKey_J; - case SDLK_k: return ImGuiKey_K; - case SDLK_l: return ImGuiKey_L; - case SDLK_m: return ImGuiKey_M; - case SDLK_n: return ImGuiKey_N; - case SDLK_o: return ImGuiKey_O; - case SDLK_p: return ImGuiKey_P; - case SDLK_q: return ImGuiKey_Q; - case SDLK_r: return ImGuiKey_R; - case SDLK_s: return ImGuiKey_S; - case SDLK_t: return ImGuiKey_T; - case SDLK_u: return ImGuiKey_U; - case SDLK_v: return ImGuiKey_V; - case SDLK_w: return ImGuiKey_W; - case SDLK_x: return ImGuiKey_X; - case SDLK_y: return ImGuiKey_Y; - case SDLK_z: return ImGuiKey_Z; - case SDLK_F1: return ImGuiKey_F1; - case SDLK_F2: return ImGuiKey_F2; - case SDLK_F3: return ImGuiKey_F3; - case SDLK_F4: return ImGuiKey_F4; - case SDLK_F5: return ImGuiKey_F5; - case SDLK_F6: return ImGuiKey_F6; - case SDLK_F7: return ImGuiKey_F7; - case SDLK_F8: return ImGuiKey_F8; - case SDLK_F9: return ImGuiKey_F9; - case SDLK_F10: return ImGuiKey_F10; - case SDLK_F11: return ImGuiKey_F11; - case SDLK_F12: return ImGuiKey_F12; - case SDLK_F13: return ImGuiKey_F13; - case SDLK_F14: return ImGuiKey_F14; - case SDLK_F15: return ImGuiKey_F15; - case SDLK_F16: return ImGuiKey_F16; - case SDLK_F17: return ImGuiKey_F17; - case SDLK_F18: return ImGuiKey_F18; - case SDLK_F19: return ImGuiKey_F19; - case SDLK_F20: return ImGuiKey_F20; - case SDLK_F21: return ImGuiKey_F21; - case SDLK_F22: return ImGuiKey_F22; - case SDLK_F23: return ImGuiKey_F23; - case SDLK_F24: return ImGuiKey_F24; - case SDLK_AC_BACK: return ImGuiKey_AppBack; - case SDLK_AC_FORWARD: return ImGuiKey_AppForward; - } - return ImGuiKey_None; -} - -static void ImGui_ImplSDL3_UpdateKeyModifiers(SDL_Keymod sdl_key_mods) -{ - ImGuiIO& io = ImGui::GetIO(); - io.AddKeyEvent(ImGuiMod_Ctrl, (sdl_key_mods & SDL_KMOD_CTRL) != 0); - io.AddKeyEvent(ImGuiMod_Shift, (sdl_key_mods & SDL_KMOD_SHIFT) != 0); - io.AddKeyEvent(ImGuiMod_Alt, (sdl_key_mods & SDL_KMOD_ALT) != 0); - io.AddKeyEvent(ImGuiMod_Super, (sdl_key_mods & SDL_KMOD_GUI) != 0); -} - -// You can read the io.WantCaptureMouse, io.WantCaptureKeyboard flags to tell if dear imgui wants to use your inputs. -// - When io.WantCaptureMouse is true, do not dispatch mouse input data to your main application, or clear/overwrite your copy of the mouse data. -// - When io.WantCaptureKeyboard is true, do not dispatch keyboard input data to your main application, or clear/overwrite your copy of the keyboard data. -// Generally you may always pass all inputs to dear imgui, and hide them from your application based on those two flags. -// If you have multiple SDL events and some of them are not meant to be used by dear imgui, you may need to filter events based on their windowID field. -bool ImGui_ImplSDL3_ProcessEvent(const SDL_Event* event) -{ - ImGuiIO& io = ImGui::GetIO(); - ImGui_ImplSDL3_Data* bd = ImGui_ImplSDL3_GetBackendData(); - - switch (event->type) - { - case SDL_EVENT_MOUSE_MOTION: - { - ImVec2 mouse_pos((float)event->motion.x, (float)event->motion.y); - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - int window_x, window_y; - SDL_GetWindowPosition(SDL_GetWindowFromID(event->motion.windowID), &window_x, &window_y); - mouse_pos.x += window_x; - mouse_pos.y += window_y; - } - io.AddMouseSourceEvent(event->motion.which == SDL_TOUCH_MOUSEID ? ImGuiMouseSource_TouchScreen : ImGuiMouseSource_Mouse); - io.AddMousePosEvent(mouse_pos.x, mouse_pos.y); - return true; - } - case SDL_EVENT_MOUSE_WHEEL: - { - //IMGUI_DEBUG_LOG("wheel %.2f %.2f, precise %.2f %.2f\n", (float)event->wheel.x, (float)event->wheel.y, event->wheel.preciseX, event->wheel.preciseY); - float wheel_x = -event->wheel.x; - float wheel_y = event->wheel.y; - #ifdef __EMSCRIPTEN__ - wheel_x /= 100.0f; - #endif - io.AddMouseSourceEvent(event->wheel.which == SDL_TOUCH_MOUSEID ? ImGuiMouseSource_TouchScreen : ImGuiMouseSource_Mouse); - io.AddMouseWheelEvent(wheel_x, wheel_y); - return true; - } - case SDL_EVENT_MOUSE_BUTTON_DOWN: - case SDL_EVENT_MOUSE_BUTTON_UP: - { - int mouse_button = -1; - if (event->button.button == SDL_BUTTON_LEFT) { mouse_button = 0; } - if (event->button.button == SDL_BUTTON_RIGHT) { mouse_button = 1; } - if (event->button.button == SDL_BUTTON_MIDDLE) { mouse_button = 2; } - if (event->button.button == SDL_BUTTON_X1) { mouse_button = 3; } - if (event->button.button == SDL_BUTTON_X2) { mouse_button = 4; } - if (mouse_button == -1) - break; - io.AddMouseSourceEvent(event->button.which == SDL_TOUCH_MOUSEID ? ImGuiMouseSource_TouchScreen : ImGuiMouseSource_Mouse); - io.AddMouseButtonEvent(mouse_button, (event->type == SDL_EVENT_MOUSE_BUTTON_DOWN)); - bd->MouseButtonsDown = (event->type == SDL_EVENT_MOUSE_BUTTON_DOWN) ? (bd->MouseButtonsDown | (1 << mouse_button)) : (bd->MouseButtonsDown & ~(1 << mouse_button)); - return true; - } - case SDL_EVENT_TEXT_INPUT: - { - io.AddInputCharactersUTF8(event->text.text); - return true; - } - case SDL_EVENT_KEY_DOWN: - case SDL_EVENT_KEY_UP: - { - ImGui_ImplSDL3_UpdateKeyModifiers((SDL_Keymod)event->key.keysym.mod); - ImGuiKey key = ImGui_ImplSDL3_KeycodeToImGuiKey(event->key.keysym.sym); - io.AddKeyEvent(key, (event->type == SDL_EVENT_KEY_DOWN)); - io.SetKeyEventNativeData(key, event->key.keysym.sym, event->key.keysym.scancode, event->key.keysym.scancode); // To support legacy indexing (<1.87 user code). Legacy backend uses SDLK_*** as indices to IsKeyXXX() functions. - return true; - } - case SDL_EVENT_DISPLAY_ORIENTATION: - case SDL_EVENT_DISPLAY_CONNECTED: - case SDL_EVENT_DISPLAY_DISCONNECTED: - case SDL_EVENT_DISPLAY_MOVED: - case SDL_EVENT_DISPLAY_CONTENT_SCALE_CHANGED: - { - bd->WantUpdateMonitors = true; - return true; - } - case SDL_EVENT_WINDOW_MOUSE_ENTER: - { - bd->MouseWindowID = event->window.windowID; - bd->PendingMouseLeaveFrame = 0; - return true; - } - // - In some cases, when detaching a window from main viewport SDL may send SDL_WINDOWEVENT_ENTER one frame too late, - // causing SDL_WINDOWEVENT_LEAVE on previous frame to interrupt drag operation by clear mouse position. This is why - // we delay process the SDL_WINDOWEVENT_LEAVE events by one frame. See issue #5012 for details. - // FIXME: Unconfirmed whether this is still needed with SDL3. - case SDL_EVENT_WINDOW_MOUSE_LEAVE: - { - bd->PendingMouseLeaveFrame = ImGui::GetFrameCount() + 1; - return true; - } - case SDL_EVENT_WINDOW_FOCUS_GAINED: - io.AddFocusEvent(true); - return true; - case SDL_EVENT_WINDOW_FOCUS_LOST: - io.AddFocusEvent(false); - return true; - case SDL_EVENT_WINDOW_CLOSE_REQUESTED: - case SDL_EVENT_WINDOW_MOVED: - case SDL_EVENT_WINDOW_RESIZED: - if (ImGuiViewport* viewport = ImGui::FindViewportByPlatformHandle((void*)SDL_GetWindowFromID(event->window.windowID))) - { - if (event->type == SDL_EVENT_WINDOW_CLOSE_REQUESTED) - viewport->PlatformRequestClose = true; - if (event->type == SDL_EVENT_WINDOW_MOVED) - viewport->PlatformRequestMove = true; - if (event->type == SDL_EVENT_WINDOW_RESIZED) - viewport->PlatformRequestResize = true; - return true; - } - return true; - } - return false; -} - -static bool ImGui_ImplSDL3_Init(SDL_Window* window, SDL_Renderer* renderer, void* sdl_gl_context) -{ - ImGuiIO& io = ImGui::GetIO(); - IM_ASSERT(io.BackendPlatformUserData == nullptr && "Already initialized a platform backend!"); - - // Check and store if we are on a SDL backend that supports global mouse position - // ("wayland" and "rpi" don't support it, but we chose to use a white-list instead of a black-list) - bool mouse_can_use_global_state = false; -#if SDL_HAS_CAPTURE_AND_GLOBAL_MOUSE - const char* sdl_backend = SDL_GetCurrentVideoDriver(); - const char* global_mouse_whitelist[] = { "windows", "cocoa", "x11", "DIVE", "VMAN" }; - for (int n = 0; n < IM_ARRAYSIZE(global_mouse_whitelist); n++) - if (strncmp(sdl_backend, global_mouse_whitelist[n], strlen(global_mouse_whitelist[n])) == 0) - mouse_can_use_global_state = true; -#endif - - // Setup backend capabilities flags - ImGui_ImplSDL3_Data* bd = IM_NEW(ImGui_ImplSDL3_Data)(); - io.BackendPlatformUserData = (void*)bd; - io.BackendPlatformName = "imgui_impl_sdl3"; - io.BackendFlags |= ImGuiBackendFlags_HasMouseCursors; // We can honor GetMouseCursor() values (optional) - io.BackendFlags |= ImGuiBackendFlags_HasSetMousePos; // We can honor io.WantSetMousePos requests (optional, rarely used) - if (mouse_can_use_global_state) - io.BackendFlags |= ImGuiBackendFlags_PlatformHasViewports; // We can create multi-viewports on the Platform side (optional) - - bd->Window = window; - bd->Renderer = renderer; - - // SDL on Linux/OSX doesn't report events for unfocused windows (see https://github.com/ocornut/imgui/issues/4960) - // We will use 'MouseCanReportHoveredViewport' to set 'ImGuiBackendFlags_HasMouseHoveredViewport' dynamically each frame. - bd->MouseCanUseGlobalState = mouse_can_use_global_state; -#ifndef __APPLE__ - bd->MouseCanReportHoveredViewport = bd->MouseCanUseGlobalState; -#else - bd->MouseCanReportHoveredViewport = false; -#endif - bd->WantUpdateMonitors = true; - - io.SetClipboardTextFn = ImGui_ImplSDL3_SetClipboardText; - io.GetClipboardTextFn = ImGui_ImplSDL3_GetClipboardText; - io.ClipboardUserData = nullptr; - io.SetPlatformImeDataFn = ImGui_ImplSDL3_SetPlatformImeData; - - // Load mouse cursors - bd->MouseCursors[ImGuiMouseCursor_Arrow] = SDL_CreateSystemCursor(SDL_SYSTEM_CURSOR_ARROW); - bd->MouseCursors[ImGuiMouseCursor_TextInput] = SDL_CreateSystemCursor(SDL_SYSTEM_CURSOR_IBEAM); - bd->MouseCursors[ImGuiMouseCursor_ResizeAll] = SDL_CreateSystemCursor(SDL_SYSTEM_CURSOR_SIZEALL); - bd->MouseCursors[ImGuiMouseCursor_ResizeNS] = SDL_CreateSystemCursor(SDL_SYSTEM_CURSOR_SIZENS); - bd->MouseCursors[ImGuiMouseCursor_ResizeEW] = SDL_CreateSystemCursor(SDL_SYSTEM_CURSOR_SIZEWE); - bd->MouseCursors[ImGuiMouseCursor_ResizeNESW] = SDL_CreateSystemCursor(SDL_SYSTEM_CURSOR_SIZENESW); - bd->MouseCursors[ImGuiMouseCursor_ResizeNWSE] = SDL_CreateSystemCursor(SDL_SYSTEM_CURSOR_SIZENWSE); - bd->MouseCursors[ImGuiMouseCursor_Hand] = SDL_CreateSystemCursor(SDL_SYSTEM_CURSOR_HAND); - bd->MouseCursors[ImGuiMouseCursor_NotAllowed] = SDL_CreateSystemCursor(SDL_SYSTEM_CURSOR_NO); - - // Set platform dependent data in viewport - // Our mouse update function expect PlatformHandle to be filled for the main viewport - ImGuiViewport* main_viewport = ImGui::GetMainViewport(); - main_viewport->PlatformHandle = (void*)window; - main_viewport->PlatformHandleRaw = nullptr; - SDL_SysWMinfo info; - if (SDL_GetWindowWMInfo(window, &info, SDL_SYSWM_CURRENT_VERSION) == 0) - { -#if defined(SDL_ENABLE_SYSWM_WINDOWS) - main_viewport->PlatformHandleRaw = (void*)info.info.win.window; -#elif defined(__APPLE__) && defined(SDL_ENABLE_SYSWM_COCOA) - main_viewport->PlatformHandleRaw = (void*)info.info.cocoa.window; -#endif - } - - // From 2.0.5: Set SDL hint to receive mouse click events on window focus, otherwise SDL doesn't emit the event. - // Without this, when clicking to gain focus, our widgets wouldn't activate even though they showed as hovered. - // (This is unfortunately a global SDL setting, so enabling it might have a side-effect on your application. - // It is unlikely to make a difference, but if your app absolutely needs to ignore the initial on-focus click: - // you can ignore SDL_EVENT_MOUSE_BUTTON_DOWN events coming right after a SDL_WINDOWEVENT_FOCUS_GAINED) - SDL_SetHint(SDL_HINT_MOUSE_FOCUS_CLICKTHROUGH, "1"); - - // From 2.0.22: Disable auto-capture, this is preventing drag and drop across multiple windows (see #5710) - SDL_SetHint(SDL_HINT_MOUSE_AUTO_CAPTURE, "0"); - - // SDL 3.x : see https://github.com/libsdl-org/SDL/issues/6659 - SDL_SetHint("SDL_BORDERLESS_WINDOWED_STYLE", "0"); - - // We need SDL_CaptureMouse(), SDL_GetGlobalMouseState() from SDL 2.0.4+ to support multiple viewports. - // We left the call to ImGui_ImplSDL3_InitPlatformInterface() outside of #ifdef to avoid unused-function warnings. - if ((io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) && (io.BackendFlags & ImGuiBackendFlags_PlatformHasViewports)) - ImGui_ImplSDL3_InitPlatformInterface(window, sdl_gl_context); - - return true; -} - -bool ImGui_ImplSDL3_InitForOpenGL(SDL_Window* window, void* sdl_gl_context) -{ - return ImGui_ImplSDL3_Init(window, nullptr, sdl_gl_context); -} - -bool ImGui_ImplSDL3_InitForVulkan(SDL_Window* window) -{ - if (!ImGui_ImplSDL3_Init(window, nullptr, nullptr)) - return false; - ImGui_ImplSDL3_Data* bd = ImGui_ImplSDL3_GetBackendData(); - bd->UseVulkan = true; - return true; -} - -bool ImGui_ImplSDL3_InitForD3D(SDL_Window* window) -{ -#if !defined(_WIN32) - IM_ASSERT(0 && "Unsupported"); -#endif - return ImGui_ImplSDL3_Init(window, nullptr, nullptr); -} - -bool ImGui_ImplSDL3_InitForMetal(SDL_Window* window) -{ - return ImGui_ImplSDL3_Init(window, nullptr, nullptr); -} - -bool ImGui_ImplSDL3_InitForSDLRenderer(SDL_Window* window, SDL_Renderer* renderer) -{ - return ImGui_ImplSDL3_Init(window, renderer, nullptr); -} - -bool ImGui_ImplSDL3_InitForOther(SDL_Window* window) -{ - return ImGui_ImplSDL3_Init(window, nullptr, nullptr); -} - -void ImGui_ImplSDL3_Shutdown() -{ - ImGui_ImplSDL3_Data* bd = ImGui_ImplSDL3_GetBackendData(); - IM_ASSERT(bd != nullptr && "No platform backend to shutdown, or already shutdown?"); - ImGuiIO& io = ImGui::GetIO(); - - ImGui_ImplSDL3_ShutdownPlatformInterface(); - - if (bd->ClipboardTextData) - SDL_free(bd->ClipboardTextData); - for (ImGuiMouseCursor cursor_n = 0; cursor_n < ImGuiMouseCursor_COUNT; cursor_n++) - SDL_DestroyCursor(bd->MouseCursors[cursor_n]); - bd->LastMouseCursor = nullptr; - - io.BackendPlatformName = nullptr; - io.BackendPlatformUserData = nullptr; - io.BackendFlags &= ~(ImGuiBackendFlags_HasMouseCursors | ImGuiBackendFlags_HasSetMousePos | ImGuiBackendFlags_HasGamepad | ImGuiBackendFlags_PlatformHasViewports | ImGuiBackendFlags_HasMouseHoveredViewport); - IM_DELETE(bd); -} - -// This code is incredibly messy because some of the functions we need for full viewport support are not available in SDL < 2.0.4. -static void ImGui_ImplSDL3_UpdateMouseData() -{ - ImGui_ImplSDL3_Data* bd = ImGui_ImplSDL3_GetBackendData(); - ImGuiIO& io = ImGui::GetIO(); - - // We forward mouse input when hovered or captured (via SDL_EVENT_MOUSE_MOTION) or when focused (below) -#if SDL_HAS_CAPTURE_AND_GLOBAL_MOUSE - // SDL_CaptureMouse() let the OS know e.g. that our imgui drag outside the SDL window boundaries shouldn't e.g. trigger other operations outside - SDL_CaptureMouse((bd->MouseButtonsDown != 0) ? SDL_TRUE : SDL_FALSE); - SDL_Window* focused_window = SDL_GetKeyboardFocus(); - const bool is_app_focused = (focused_window && (bd->Window == focused_window || ImGui::FindViewportByPlatformHandle((void*)focused_window))); -#else - SDL_Window* focused_window = bd->Window; - const bool is_app_focused = (SDL_GetWindowFlags(bd->Window) & SDL_WINDOW_INPUT_FOCUS) != 0; // SDL 2.0.3 and non-windowed systems: single-viewport only -#endif - if (is_app_focused) - { - // (Optional) Set OS mouse position from Dear ImGui if requested (rarely used, only when ImGuiConfigFlags_NavEnableSetMousePos is enabled by user) - if (io.WantSetMousePos) - { -#if SDL_HAS_CAPTURE_AND_GLOBAL_MOUSE - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - SDL_WarpMouseGlobal(io.MousePos.x, io.MousePos.y); - else -#endif - SDL_WarpMouseInWindow(bd->Window, io.MousePos.x, io.MousePos.y); - } - - // (Optional) Fallback to provide mouse position when focused (SDL_EVENT_MOUSE_MOTION already provides this when hovered or captured) - if (bd->MouseCanUseGlobalState && bd->MouseButtonsDown == 0) - { - // Single-viewport mode: mouse position in client window coordinates (io.MousePos is (0,0) when the mouse is on the upper-left corner of the app window) - // Multi-viewport mode: mouse position in OS absolute coordinates (io.MousePos is (0,0) when the mouse is on the upper-left of the primary monitor) - float mouse_x, mouse_y; - int window_x, window_y; - SDL_GetGlobalMouseState(&mouse_x, &mouse_y); - if (!(io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable)) - { - SDL_GetWindowPosition(focused_window, &window_x, &window_y); - mouse_x -= window_x; - mouse_y -= window_y; - } - io.AddMousePosEvent((float)mouse_x, (float)mouse_y); - } - } - - // (Optional) When using multiple viewports: call io.AddMouseViewportEvent() with the viewport the OS mouse cursor is hovering. - // If ImGuiBackendFlags_HasMouseHoveredViewport is not set by the backend, Dear imGui will ignore this field and infer the information using its flawed heuristic. - // - [!] SDL backend does NOT correctly ignore viewports with the _NoInputs flag. - // Some backend are not able to handle that correctly. If a backend report an hovered viewport that has the _NoInputs flag (e.g. when dragging a window - // for docking, the viewport has the _NoInputs flag in order to allow us to find the viewport under), then Dear ImGui is forced to ignore the value reported - // by the backend, and use its flawed heuristic to guess the viewport behind. - // - [X] SDL backend correctly reports this regardless of another viewport behind focused and dragged from (we need this to find a useful drag and drop target). - if (io.BackendFlags & ImGuiBackendFlags_HasMouseHoveredViewport) - { - ImGuiID mouse_viewport_id = 0; - if (SDL_Window* sdl_mouse_window = SDL_GetWindowFromID(bd->MouseWindowID)) - if (ImGuiViewport* mouse_viewport = ImGui::FindViewportByPlatformHandle((void*)sdl_mouse_window)) - mouse_viewport_id = mouse_viewport->ID; - io.AddMouseViewportEvent(mouse_viewport_id); - } -} - -static void ImGui_ImplSDL3_UpdateMouseCursor() -{ - ImGuiIO& io = ImGui::GetIO(); - if (io.ConfigFlags & ImGuiConfigFlags_NoMouseCursorChange) - return; - ImGui_ImplSDL3_Data* bd = ImGui_ImplSDL3_GetBackendData(); - - ImGuiMouseCursor imgui_cursor = ImGui::GetMouseCursor(); - if (io.MouseDrawCursor || imgui_cursor == ImGuiMouseCursor_None) - { - // Hide OS mouse cursor if imgui is drawing it or if it wants no cursor - SDL_HideCursor(); - } - else - { - // Show OS mouse cursor - SDL_Cursor* expected_cursor = bd->MouseCursors[imgui_cursor] ? bd->MouseCursors[imgui_cursor] : bd->MouseCursors[ImGuiMouseCursor_Arrow]; - if (bd->LastMouseCursor != expected_cursor) - { - SDL_SetCursor(expected_cursor); // SDL function doesn't have an early out (see #6113) - bd->LastMouseCursor = expected_cursor; - } - SDL_ShowCursor(); - } -} - -static void ImGui_ImplSDL3_UpdateGamepads() -{ - ImGuiIO& io = ImGui::GetIO(); - if ((io.ConfigFlags & ImGuiConfigFlags_NavEnableGamepad) == 0) // FIXME: Technically feeding gamepad shouldn't depend on this now that they are regular inputs. - return; - - // Get gamepad - io.BackendFlags &= ~ImGuiBackendFlags_HasGamepad; - SDL_Gamepad* gamepad = SDL_OpenGamepad(0); - if (!gamepad) - return; - io.BackendFlags |= ImGuiBackendFlags_HasGamepad; - - // Update gamepad inputs - #define IM_SATURATE(V) (V < 0.0f ? 0.0f : V > 1.0f ? 1.0f : V) - #define MAP_BUTTON(KEY_NO, BUTTON_NO) { io.AddKeyEvent(KEY_NO, SDL_GetGamepadButton(gamepad, BUTTON_NO) != 0); } - #define MAP_ANALOG(KEY_NO, AXIS_NO, V0, V1) { float vn = (float)(SDL_GetGamepadAxis(gamepad, AXIS_NO) - V0) / (float)(V1 - V0); vn = IM_SATURATE(vn); io.AddKeyAnalogEvent(KEY_NO, vn > 0.1f, vn); } - const int thumb_dead_zone = 8000; // SDL_gamecontroller.h suggests using this value. - MAP_BUTTON(ImGuiKey_GamepadStart, SDL_GAMEPAD_BUTTON_START); - MAP_BUTTON(ImGuiKey_GamepadBack, SDL_GAMEPAD_BUTTON_BACK); - MAP_BUTTON(ImGuiKey_GamepadFaceLeft, SDL_GAMEPAD_BUTTON_X); // Xbox X, PS Square - MAP_BUTTON(ImGuiKey_GamepadFaceRight, SDL_GAMEPAD_BUTTON_B); // Xbox B, PS Circle - MAP_BUTTON(ImGuiKey_GamepadFaceUp, SDL_GAMEPAD_BUTTON_Y); // Xbox Y, PS Triangle - MAP_BUTTON(ImGuiKey_GamepadFaceDown, SDL_GAMEPAD_BUTTON_A); // Xbox A, PS Cross - MAP_BUTTON(ImGuiKey_GamepadDpadLeft, SDL_GAMEPAD_BUTTON_DPAD_LEFT); - MAP_BUTTON(ImGuiKey_GamepadDpadRight, SDL_GAMEPAD_BUTTON_DPAD_RIGHT); - MAP_BUTTON(ImGuiKey_GamepadDpadUp, SDL_GAMEPAD_BUTTON_DPAD_UP); - MAP_BUTTON(ImGuiKey_GamepadDpadDown, SDL_GAMEPAD_BUTTON_DPAD_DOWN); - MAP_BUTTON(ImGuiKey_GamepadL1, SDL_GAMEPAD_BUTTON_LEFT_SHOULDER); - MAP_BUTTON(ImGuiKey_GamepadR1, SDL_GAMEPAD_BUTTON_RIGHT_SHOULDER); - MAP_ANALOG(ImGuiKey_GamepadL2, SDL_GAMEPAD_AXIS_LEFT_TRIGGER, 0.0f, 32767); - MAP_ANALOG(ImGuiKey_GamepadR2, SDL_GAMEPAD_AXIS_RIGHT_TRIGGER, 0.0f, 32767); - MAP_BUTTON(ImGuiKey_GamepadL3, SDL_GAMEPAD_BUTTON_LEFT_STICK); - MAP_BUTTON(ImGuiKey_GamepadR3, SDL_GAMEPAD_BUTTON_RIGHT_STICK); - MAP_ANALOG(ImGuiKey_GamepadLStickLeft, SDL_GAMEPAD_AXIS_LEFTX, -thumb_dead_zone, -32768); - MAP_ANALOG(ImGuiKey_GamepadLStickRight, SDL_GAMEPAD_AXIS_LEFTX, +thumb_dead_zone, +32767); - MAP_ANALOG(ImGuiKey_GamepadLStickUp, SDL_GAMEPAD_AXIS_LEFTY, -thumb_dead_zone, -32768); - MAP_ANALOG(ImGuiKey_GamepadLStickDown, SDL_GAMEPAD_AXIS_LEFTY, +thumb_dead_zone, +32767); - MAP_ANALOG(ImGuiKey_GamepadRStickLeft, SDL_GAMEPAD_AXIS_RIGHTX, -thumb_dead_zone, -32768); - MAP_ANALOG(ImGuiKey_GamepadRStickRight, SDL_GAMEPAD_AXIS_RIGHTX, +thumb_dead_zone, +32767); - MAP_ANALOG(ImGuiKey_GamepadRStickUp, SDL_GAMEPAD_AXIS_RIGHTY, -thumb_dead_zone, -32768); - MAP_ANALOG(ImGuiKey_GamepadRStickDown, SDL_GAMEPAD_AXIS_RIGHTY, +thumb_dead_zone, +32767); - #undef MAP_BUTTON - #undef MAP_ANALOG -} - -static void ImGui_ImplSDL3_UpdateMonitors() -{ - ImGui_ImplSDL3_Data* bd = ImGui_ImplSDL3_GetBackendData(); - ImGuiPlatformIO& platform_io = ImGui::GetPlatformIO(); - platform_io.Monitors.resize(0); - bd->WantUpdateMonitors = false; - - int display_count; - SDL_DisplayID* displays = SDL_GetDisplays(&display_count); - for (int n = 0; n < display_count; n++) - { - // Warning: the validity of monitor DPI information on Windows depends on the application DPI awareness settings, which generally needs to be set in the manifest or at runtime. - SDL_DisplayID display_id = displays[n]; - ImGuiPlatformMonitor monitor; - SDL_Rect r; - SDL_GetDisplayBounds(display_id, &r); - monitor.MainPos = monitor.WorkPos = ImVec2((float)r.x, (float)r.y); - monitor.MainSize = monitor.WorkSize = ImVec2((float)r.w, (float)r.h); - SDL_GetDisplayUsableBounds(display_id, &r); - monitor.WorkPos = ImVec2((float)r.x, (float)r.y); - monitor.WorkSize = ImVec2((float)r.w, (float)r.h); - // FIXME-VIEWPORT: On MacOS SDL reports actual monitor DPI scale, ignoring OS configuration. We may want to set - // DpiScale to cocoa_window.backingScaleFactor here. - monitor.DpiScale = SDL_GetDisplayContentScale(display_id); - monitor.PlatformHandle = (void*)(intptr_t)n; - platform_io.Monitors.push_back(monitor); - } -} - -void ImGui_ImplSDL3_NewFrame() -{ - ImGui_ImplSDL3_Data* bd = ImGui_ImplSDL3_GetBackendData(); - IM_ASSERT(bd != nullptr && "Did you call ImGui_ImplSDL3_Init()?"); - ImGuiIO& io = ImGui::GetIO(); - - // Setup display size (every frame to accommodate for window resizing) - int w, h; - int display_w, display_h; - SDL_GetWindowSize(bd->Window, &w, &h); - if (SDL_GetWindowFlags(bd->Window) & SDL_WINDOW_MINIMIZED) - w = h = 0; - SDL_GetWindowSizeInPixels(bd->Window, &display_w, &display_h); - io.DisplaySize = ImVec2((float)w, (float)h); - if (w > 0 && h > 0) - io.DisplayFramebufferScale = ImVec2((float)display_w / w, (float)display_h / h); - - // Update monitors - if (bd->WantUpdateMonitors) - ImGui_ImplSDL3_UpdateMonitors(); - - // Setup time step (we don't use SDL_GetTicks() because it is using millisecond resolution) - // (Accept SDL_GetPerformanceCounter() not returning a monotonically increasing value. Happens in VMs and Emscripten, see #6189, #6114, #3644) - static Uint64 frequency = SDL_GetPerformanceFrequency(); - Uint64 current_time = SDL_GetPerformanceCounter(); - if (current_time <= bd->Time) - current_time = bd->Time + 1; - io.DeltaTime = bd->Time > 0 ? (float)((double)(current_time - bd->Time) / frequency) : (float)(1.0f / 60.0f); - bd->Time = current_time; - - if (bd->PendingMouseLeaveFrame && bd->PendingMouseLeaveFrame >= ImGui::GetFrameCount() && bd->MouseButtonsDown == 0) - { - bd->MouseWindowID = 0; - bd->PendingMouseLeaveFrame = 0; - io.AddMousePosEvent(-FLT_MAX, -FLT_MAX); - } - - // Our io.AddMouseViewportEvent() calls will only be valid when not capturing. - // Technically speaking testing for 'bd->MouseButtonsDown == 0' would be more rygorous, but testing for payload reduces noise and potential side-effects. - if (bd->MouseCanReportHoveredViewport && ImGui::GetDragDropPayload() == nullptr) - io.BackendFlags |= ImGuiBackendFlags_HasMouseHoveredViewport; - else - io.BackendFlags &= ~ImGuiBackendFlags_HasMouseHoveredViewport; - - ImGui_ImplSDL3_UpdateMouseData(); - ImGui_ImplSDL3_UpdateMouseCursor(); - - // Update game controllers (if enabled and available) - ImGui_ImplSDL3_UpdateGamepads(); -} - -//-------------------------------------------------------------------------------------------------------- -// MULTI-VIEWPORT / PLATFORM INTERFACE SUPPORT -// This is an _advanced_ and _optional_ feature, allowing the backend to create and handle multiple viewports simultaneously. -// If you are new to dear imgui or creating a new binding for dear imgui, it is recommended that you completely ignore this section first.. -//-------------------------------------------------------------------------------------------------------- - -// Helper structure we store in the void* RendererUserData field of each ImGuiViewport to easily retrieve our backend data. -struct ImGui_ImplSDL3_ViewportData -{ - SDL_Window* Window; - Uint32 WindowID; - bool WindowOwned; - SDL_GLContext GLContext; - - ImGui_ImplSDL3_ViewportData() { Window = nullptr; WindowID = 0; WindowOwned = false; GLContext = nullptr; } - ~ImGui_ImplSDL3_ViewportData() { IM_ASSERT(Window == nullptr && GLContext == nullptr); } -}; - -static void ImGui_ImplSDL3_CreateWindow(ImGuiViewport* viewport) -{ - ImGui_ImplSDL3_Data* bd = ImGui_ImplSDL3_GetBackendData(); - ImGui_ImplSDL3_ViewportData* vd = IM_NEW(ImGui_ImplSDL3_ViewportData)(); - viewport->PlatformUserData = vd; - - ImGuiViewport* main_viewport = ImGui::GetMainViewport(); - ImGui_ImplSDL3_ViewportData* main_viewport_data = (ImGui_ImplSDL3_ViewportData*)main_viewport->PlatformUserData; - - // Share GL resources with main context - bool use_opengl = (main_viewport_data->GLContext != nullptr); - SDL_GLContext backup_context = nullptr; - if (use_opengl) - { - backup_context = SDL_GL_GetCurrentContext(); - SDL_GL_SetAttribute(SDL_GL_SHARE_WITH_CURRENT_CONTEXT, 1); - SDL_GL_MakeCurrent(main_viewport_data->Window, main_viewport_data->GLContext); - } - - Uint32 sdl_flags = 0; - sdl_flags |= use_opengl ? SDL_WINDOW_OPENGL : (bd->UseVulkan ? SDL_WINDOW_VULKAN : 0); - sdl_flags |= SDL_GetWindowFlags(bd->Window); - sdl_flags |= (viewport->Flags & ImGuiViewportFlags_NoDecoration) ? SDL_WINDOW_BORDERLESS : 0; - sdl_flags |= (viewport->Flags & ImGuiViewportFlags_NoDecoration) ? 0 : SDL_WINDOW_RESIZABLE; -#if !defined(_WIN32) - // See SDL hack in ImGui_ImplSDL3_ShowWindow(). - sdl_flags |= (viewport->Flags & ImGuiViewportFlags_NoTaskBarIcon) ? SDL_WINDOW_UTILITY : 0; -#endif - sdl_flags |= (viewport->Flags & ImGuiViewportFlags_TopMost) ? SDL_WINDOW_ALWAYS_ON_TOP : 0; - vd->Window = SDL_CreateWindow("No Title Yet", (int)viewport->Size.x, (int)viewport->Size.y, sdl_flags); - SDL_SetWindowPosition(vd->Window, (int)viewport->Pos.x, (int)viewport->Pos.y); - vd->WindowOwned = true; - if (use_opengl) - { - vd->GLContext = SDL_GL_CreateContext(vd->Window); - SDL_GL_SetSwapInterval(0); - } - if (use_opengl && backup_context) - SDL_GL_MakeCurrent(vd->Window, backup_context); - - viewport->PlatformHandle = (void*)vd->Window; - viewport->PlatformHandleRaw = nullptr; - SDL_SysWMinfo info; - if (SDL_GetWindowWMInfo(vd->Window, &info, SDL_SYSWM_CURRENT_VERSION)) - { -#if defined(SDL_VIDEO_DRIVER_WINDOWS) - viewport->PlatformHandleRaw = info.info.win.window; -#elif defined(__APPLE__) && defined(SDL_VIDEO_DRIVER_COCOA) - viewport->PlatformHandleRaw = (void*)info.info.cocoa.window; -#endif - } -} - -static void ImGui_ImplSDL3_DestroyWindow(ImGuiViewport* viewport) -{ - if (ImGui_ImplSDL3_ViewportData* vd = (ImGui_ImplSDL3_ViewportData*)viewport->PlatformUserData) - { - if (vd->GLContext && vd->WindowOwned) - SDL_GL_DeleteContext(vd->GLContext); - if (vd->Window && vd->WindowOwned) - SDL_DestroyWindow(vd->Window); - vd->GLContext = nullptr; - vd->Window = nullptr; - IM_DELETE(vd); - } - viewport->PlatformUserData = viewport->PlatformHandle = nullptr; -} - -static void ImGui_ImplSDL3_ShowWindow(ImGuiViewport* viewport) -{ - ImGui_ImplSDL3_ViewportData* vd = (ImGui_ImplSDL3_ViewportData*)viewport->PlatformUserData; -#if defined(_WIN32) - HWND hwnd = (HWND)viewport->PlatformHandleRaw; - - // SDL hack: Hide icon from task bar - // Note: SDL 3.0.0+ has a SDL_WINDOW_UTILITY flag which is supported under Windows but the way it create the window breaks our seamless transition. - if (viewport->Flags & ImGuiViewportFlags_NoTaskBarIcon) - { - LONG ex_style = ::GetWindowLong(hwnd, GWL_EXSTYLE); - ex_style &= ~WS_EX_APPWINDOW; - ex_style |= WS_EX_TOOLWINDOW; - ::SetWindowLong(hwnd, GWL_EXSTYLE, ex_style); - } - - // SDL hack: SDL always activate/focus windows :/ - if (viewport->Flags & ImGuiViewportFlags_NoFocusOnAppearing) - { - ::ShowWindow(hwnd, SW_SHOWNA); - return; - } -#endif - - SDL_ShowWindow(vd->Window); -} - -static ImVec2 ImGui_ImplSDL3_GetWindowPos(ImGuiViewport* viewport) -{ - ImGui_ImplSDL3_ViewportData* vd = (ImGui_ImplSDL3_ViewportData*)viewport->PlatformUserData; - int x = 0, y = 0; - SDL_GetWindowPosition(vd->Window, &x, &y); - return ImVec2((float)x, (float)y); -} - -static void ImGui_ImplSDL3_SetWindowPos(ImGuiViewport* viewport, ImVec2 pos) -{ - ImGui_ImplSDL3_ViewportData* vd = (ImGui_ImplSDL3_ViewportData*)viewport->PlatformUserData; - SDL_SetWindowPosition(vd->Window, (int)pos.x, (int)pos.y); -} - -static ImVec2 ImGui_ImplSDL3_GetWindowSize(ImGuiViewport* viewport) -{ - ImGui_ImplSDL3_ViewportData* vd = (ImGui_ImplSDL3_ViewportData*)viewport->PlatformUserData; - int w = 0, h = 0; - SDL_GetWindowSize(vd->Window, &w, &h); - return ImVec2((float)w, (float)h); -} - -static void ImGui_ImplSDL3_SetWindowSize(ImGuiViewport* viewport, ImVec2 size) -{ - ImGui_ImplSDL3_ViewportData* vd = (ImGui_ImplSDL3_ViewportData*)viewport->PlatformUserData; - SDL_SetWindowSize(vd->Window, (int)size.x, (int)size.y); -} - -static void ImGui_ImplSDL3_SetWindowTitle(ImGuiViewport* viewport, const char* title) -{ - ImGui_ImplSDL3_ViewportData* vd = (ImGui_ImplSDL3_ViewportData*)viewport->PlatformUserData; - SDL_SetWindowTitle(vd->Window, title); -} - -static void ImGui_ImplSDL3_SetWindowAlpha(ImGuiViewport* viewport, float alpha) -{ - ImGui_ImplSDL3_ViewportData* vd = (ImGui_ImplSDL3_ViewportData*)viewport->PlatformUserData; - SDL_SetWindowOpacity(vd->Window, alpha); -} - -static void ImGui_ImplSDL3_SetWindowFocus(ImGuiViewport* viewport) -{ - ImGui_ImplSDL3_ViewportData* vd = (ImGui_ImplSDL3_ViewportData*)viewport->PlatformUserData; - SDL_RaiseWindow(vd->Window); -} - -static bool ImGui_ImplSDL3_GetWindowFocus(ImGuiViewport* viewport) -{ - ImGui_ImplSDL3_ViewportData* vd = (ImGui_ImplSDL3_ViewportData*)viewport->PlatformUserData; - return (SDL_GetWindowFlags(vd->Window) & SDL_WINDOW_INPUT_FOCUS) != 0; -} - -static bool ImGui_ImplSDL3_GetWindowMinimized(ImGuiViewport* viewport) -{ - ImGui_ImplSDL3_ViewportData* vd = (ImGui_ImplSDL3_ViewportData*)viewport->PlatformUserData; - return (SDL_GetWindowFlags(vd->Window) & SDL_WINDOW_MINIMIZED) != 0; -} - -static void ImGui_ImplSDL3_RenderWindow(ImGuiViewport* viewport, void*) -{ - ImGui_ImplSDL3_ViewportData* vd = (ImGui_ImplSDL3_ViewportData*)viewport->PlatformUserData; - if (vd->GLContext) - SDL_GL_MakeCurrent(vd->Window, vd->GLContext); -} - -static void ImGui_ImplSDL3_SwapBuffers(ImGuiViewport* viewport, void*) -{ - ImGui_ImplSDL3_ViewportData* vd = (ImGui_ImplSDL3_ViewportData*)viewport->PlatformUserData; - if (vd->GLContext) - { - SDL_GL_MakeCurrent(vd->Window, vd->GLContext); - SDL_GL_SwapWindow(vd->Window); - } -} - -// Vulkan support (the Vulkan renderer needs to call a platform-side support function to create the surface) -// SDL is graceful enough to _not_ need so we can safely include this. -#include -static int ImGui_ImplSDL3_CreateVkSurface(ImGuiViewport* viewport, ImU64 vk_instance, const void* vk_allocator, ImU64* out_vk_surface) -{ - ImGui_ImplSDL3_ViewportData* vd = (ImGui_ImplSDL3_ViewportData*)viewport->PlatformUserData; - (void)vk_allocator; - SDL_bool ret = SDL_Vulkan_CreateSurface(vd->Window, (VkInstance)vk_instance, (VkSurfaceKHR*)out_vk_surface); - return ret ? 0 : 1; // ret ? VK_SUCCESS : VK_NOT_READY -} - -static void ImGui_ImplSDL3_InitPlatformInterface(SDL_Window* window, void* sdl_gl_context) -{ - // Register platform interface (will be coupled with a renderer interface) - ImGuiPlatformIO& platform_io = ImGui::GetPlatformIO(); - platform_io.Platform_CreateWindow = ImGui_ImplSDL3_CreateWindow; - platform_io.Platform_DestroyWindow = ImGui_ImplSDL3_DestroyWindow; - platform_io.Platform_ShowWindow = ImGui_ImplSDL3_ShowWindow; - platform_io.Platform_SetWindowPos = ImGui_ImplSDL3_SetWindowPos; - platform_io.Platform_GetWindowPos = ImGui_ImplSDL3_GetWindowPos; - platform_io.Platform_SetWindowSize = ImGui_ImplSDL3_SetWindowSize; - platform_io.Platform_GetWindowSize = ImGui_ImplSDL3_GetWindowSize; - platform_io.Platform_SetWindowFocus = ImGui_ImplSDL3_SetWindowFocus; - platform_io.Platform_GetWindowFocus = ImGui_ImplSDL3_GetWindowFocus; - platform_io.Platform_GetWindowMinimized = ImGui_ImplSDL3_GetWindowMinimized; - platform_io.Platform_SetWindowTitle = ImGui_ImplSDL3_SetWindowTitle; - platform_io.Platform_RenderWindow = ImGui_ImplSDL3_RenderWindow; - platform_io.Platform_SwapBuffers = ImGui_ImplSDL3_SwapBuffers; - platform_io.Platform_SetWindowAlpha = ImGui_ImplSDL3_SetWindowAlpha; - platform_io.Platform_CreateVkSurface = ImGui_ImplSDL3_CreateVkSurface; - - // Register main window handle (which is owned by the main application, not by us) - // This is mostly for simplicity and consistency, so that our code (e.g. mouse handling etc.) can use same logic for main and secondary viewports. - ImGuiViewport* main_viewport = ImGui::GetMainViewport(); - ImGui_ImplSDL3_ViewportData* vd = IM_NEW(ImGui_ImplSDL3_ViewportData)(); - vd->Window = window; - vd->WindowID = SDL_GetWindowID(window); - vd->WindowOwned = false; - vd->GLContext = sdl_gl_context; - main_viewport->PlatformUserData = vd; - main_viewport->PlatformHandle = vd->Window; -} - -static void ImGui_ImplSDL3_ShutdownPlatformInterface() -{ - ImGui::DestroyPlatformWindows(); -} - -//----------------------------------------------------------------------------- - -#if defined(__clang__) -#pragma clang diagnostic pop -#endif - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_sdl3.h b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_sdl3.h deleted file mode 100644 index 1a4b317..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_sdl3.h +++ /dev/null @@ -1,43 +0,0 @@ -// dear imgui: Platform Backend for SDL3 (*EXPERIMENTAL*) -// This needs to be used along with a Renderer (e.g. DirectX11, OpenGL3, Vulkan..) -// (Info: SDL3 is a cross-platform general purpose library for handling windows, inputs, graphics context creation, etc.) -// (IMPORTANT: SDL 3.0.0 is NOT YET RELEASED. IT IS POSSIBLE THAT ITS SPECS/API WILL CHANGE BEFORE RELEASE) - -// Implemented features: -// [X] Platform: Clipboard support. -// [X] Platform: Mouse support. Can discriminate Mouse/TouchScreen. -// [X] Platform: Keyboard support. Since 1.87 we are using the io.AddKeyEvent() function. Pass ImGuiKey values to all key functions e.g. ImGui::IsKeyPressed(ImGuiKey_Space). [Legacy SDL_SCANCODE_* values will also be supported unless IMGUI_DISABLE_OBSOLETE_KEYIO is set] -// [X] Platform: Gamepad support. Enabled with 'io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad'. -// [X] Platform: Mouse cursor shape and visibility. Disable with 'io.ConfigFlags |= ImGuiConfigFlags_NoMouseCursorChange'. -// [x] Platform: Multi-viewport support (multiple windows). Enable with 'io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable' -> the OS animation effect when window gets created/destroyed is problematic. SDL2 backend doesn't have issue. -// Missing features: -// [ ] Platform: Multi-viewport + Minimized windows seems to break mouse wheel events (at least under Windows). -// [x] Platform: Basic IME support. Position somehow broken in SDL3 + app needs to call 'SDL_SetHint(SDL_HINT_IME_SHOW_UI, "1");' before SDL_CreateWindow()!. - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#pragma once -#include "imgui.h" // IMGUI_IMPL_API -#ifndef IMGUI_DISABLE - -struct SDL_Window; -struct SDL_Renderer; -typedef union SDL_Event SDL_Event; - -IMGUI_IMPL_API bool ImGui_ImplSDL3_InitForOpenGL(SDL_Window* window, void* sdl_gl_context); -IMGUI_IMPL_API bool ImGui_ImplSDL3_InitForVulkan(SDL_Window* window); -IMGUI_IMPL_API bool ImGui_ImplSDL3_InitForD3D(SDL_Window* window); -IMGUI_IMPL_API bool ImGui_ImplSDL3_InitForMetal(SDL_Window* window); -IMGUI_IMPL_API bool ImGui_ImplSDL3_InitForSDLRenderer(SDL_Window* window, SDL_Renderer* renderer); -IMGUI_IMPL_API bool ImGui_ImplSDL3_InitForOther(SDL_Window* window); -IMGUI_IMPL_API void ImGui_ImplSDL3_Shutdown(); -IMGUI_IMPL_API void ImGui_ImplSDL3_NewFrame(); -IMGUI_IMPL_API bool ImGui_ImplSDL3_ProcessEvent(const SDL_Event* event); - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_sdlrenderer2.cpp b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_sdlrenderer2.cpp deleted file mode 100644 index affa139..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_sdlrenderer2.cpp +++ /dev/null @@ -1,268 +0,0 @@ -// dear imgui: Renderer Backend for SDL_Renderer for SDL2 -// (Requires: SDL 2.0.17+) - -// Note how SDL_Renderer is an _optional_ component of SDL2. -// For a multi-platform app consider using e.g. SDL+DirectX on Windows and SDL+OpenGL on Linux/OSX. -// If your application will want to render any non trivial amount of graphics other than UI, -// please be aware that SDL_Renderer currently offers a limited graphic API to the end-user and -// it might be difficult to step out of those boundaries. - -// Implemented features: -// [X] Renderer: User texture binding. Use 'SDL_Texture*' as ImTextureID. Read the FAQ about ImTextureID! -// [X] Renderer: Large meshes support (64k+ vertices) with 16-bit indices. -// Missing features: -// [ ] Renderer: Multi-viewport support (multiple windows). - -// You can copy and use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -// CHANGELOG -// 2023-05-30: Renamed imgui_impl_sdlrenderer.h/.cpp to imgui_impl_sdlrenderer2.h/.cpp to accommodate for upcoming SDL3. -// 2022-10-11: Using 'nullptr' instead of 'NULL' as per our switch to C++11. -// 2021-12-21: Update SDL_RenderGeometryRaw() format to work with SDL 2.0.19. -// 2021-12-03: Added support for large mesh (64K+ vertices), enable ImGuiBackendFlags_RendererHasVtxOffset flag. -// 2021-10-06: Backup and restore modified ClipRect/Viewport. -// 2021-09-21: Initial version. - -#include "imgui.h" -#ifndef IMGUI_DISABLE -#include "imgui_impl_sdlrenderer2.h" -#include // intptr_t - -// Clang warnings with -Weverything -#if defined(__clang__) -#pragma clang diagnostic push -#pragma clang diagnostic ignored "-Wsign-conversion" // warning: implicit conversion changes signedness -#endif - -// SDL -#include -#if !SDL_VERSION_ATLEAST(2,0,17) -#error This backend requires SDL 2.0.17+ because of SDL_RenderGeometry() function -#endif - -// SDL_Renderer data -struct ImGui_ImplSDLRenderer2_Data -{ - SDL_Renderer* SDLRenderer; - SDL_Texture* FontTexture; - ImGui_ImplSDLRenderer2_Data() { memset((void*)this, 0, sizeof(*this)); } -}; - -// Backend data stored in io.BackendRendererUserData to allow support for multiple Dear ImGui contexts -// It is STRONGLY preferred that you use docking branch with multi-viewports (== single Dear ImGui context + multiple windows) instead of multiple Dear ImGui contexts. -static ImGui_ImplSDLRenderer2_Data* ImGui_ImplSDLRenderer2_GetBackendData() -{ - return ImGui::GetCurrentContext() ? (ImGui_ImplSDLRenderer2_Data*)ImGui::GetIO().BackendRendererUserData : nullptr; -} - -// Functions -bool ImGui_ImplSDLRenderer2_Init(SDL_Renderer* renderer) -{ - ImGuiIO& io = ImGui::GetIO(); - IM_ASSERT(io.BackendRendererUserData == nullptr && "Already initialized a renderer backend!"); - IM_ASSERT(renderer != nullptr && "SDL_Renderer not initialized!"); - - // Setup backend capabilities flags - ImGui_ImplSDLRenderer2_Data* bd = IM_NEW(ImGui_ImplSDLRenderer2_Data)(); - io.BackendRendererUserData = (void*)bd; - io.BackendRendererName = "imgui_impl_sdlrenderer2"; - io.BackendFlags |= ImGuiBackendFlags_RendererHasVtxOffset; // We can honor the ImDrawCmd::VtxOffset field, allowing for large meshes. - - bd->SDLRenderer = renderer; - - return true; -} - -void ImGui_ImplSDLRenderer2_Shutdown() -{ - ImGui_ImplSDLRenderer2_Data* bd = ImGui_ImplSDLRenderer2_GetBackendData(); - IM_ASSERT(bd != nullptr && "No renderer backend to shutdown, or already shutdown?"); - ImGuiIO& io = ImGui::GetIO(); - - ImGui_ImplSDLRenderer2_DestroyDeviceObjects(); - - io.BackendRendererName = nullptr; - io.BackendRendererUserData = nullptr; - io.BackendFlags &= ~ImGuiBackendFlags_RendererHasVtxOffset; - IM_DELETE(bd); -} - -static void ImGui_ImplSDLRenderer2_SetupRenderState() -{ - ImGui_ImplSDLRenderer2_Data* bd = ImGui_ImplSDLRenderer2_GetBackendData(); - - // Clear out any viewports and cliprect set by the user - // FIXME: Technically speaking there are lots of other things we could backup/setup/restore during our render process. - SDL_RenderSetViewport(bd->SDLRenderer, nullptr); - SDL_RenderSetClipRect(bd->SDLRenderer, nullptr); -} - -void ImGui_ImplSDLRenderer2_NewFrame() -{ - ImGui_ImplSDLRenderer2_Data* bd = ImGui_ImplSDLRenderer2_GetBackendData(); - IM_ASSERT(bd != nullptr && "Did you call ImGui_ImplSDLRenderer2_Init()?"); - - if (!bd->FontTexture) - ImGui_ImplSDLRenderer2_CreateDeviceObjects(); -} - -void ImGui_ImplSDLRenderer2_RenderDrawData(ImDrawData* draw_data) -{ - ImGui_ImplSDLRenderer2_Data* bd = ImGui_ImplSDLRenderer2_GetBackendData(); - - // If there's a scale factor set by the user, use that instead - // If the user has specified a scale factor to SDL_Renderer already via SDL_RenderSetScale(), SDL will scale whatever we pass - // to SDL_RenderGeometryRaw() by that scale factor. In that case we don't want to be also scaling it ourselves here. - float rsx = 1.0f; - float rsy = 1.0f; - SDL_RenderGetScale(bd->SDLRenderer, &rsx, &rsy); - ImVec2 render_scale; - render_scale.x = (rsx == 1.0f) ? draw_data->FramebufferScale.x : 1.0f; - render_scale.y = (rsy == 1.0f) ? draw_data->FramebufferScale.y : 1.0f; - - // Avoid rendering when minimized, scale coordinates for retina displays (screen coordinates != framebuffer coordinates) - int fb_width = (int)(draw_data->DisplaySize.x * render_scale.x); - int fb_height = (int)(draw_data->DisplaySize.y * render_scale.y); - if (fb_width == 0 || fb_height == 0) - return; - - // Backup SDL_Renderer state that will be modified to restore it afterwards - struct BackupSDLRendererState - { - SDL_Rect Viewport; - bool ClipEnabled; - SDL_Rect ClipRect; - }; - BackupSDLRendererState old = {}; - old.ClipEnabled = SDL_RenderIsClipEnabled(bd->SDLRenderer) == SDL_TRUE; - SDL_RenderGetViewport(bd->SDLRenderer, &old.Viewport); - SDL_RenderGetClipRect(bd->SDLRenderer, &old.ClipRect); - - // Will project scissor/clipping rectangles into framebuffer space - ImVec2 clip_off = draw_data->DisplayPos; // (0,0) unless using multi-viewports - ImVec2 clip_scale = render_scale; - - // Render command lists - ImGui_ImplSDLRenderer2_SetupRenderState(); - for (int n = 0; n < draw_data->CmdListsCount; n++) - { - const ImDrawList* cmd_list = draw_data->CmdLists[n]; - const ImDrawVert* vtx_buffer = cmd_list->VtxBuffer.Data; - const ImDrawIdx* idx_buffer = cmd_list->IdxBuffer.Data; - - for (int cmd_i = 0; cmd_i < cmd_list->CmdBuffer.Size; cmd_i++) - { - const ImDrawCmd* pcmd = &cmd_list->CmdBuffer[cmd_i]; - if (pcmd->UserCallback) - { - // User callback, registered via ImDrawList::AddCallback() - // (ImDrawCallback_ResetRenderState is a special callback value used by the user to request the renderer to reset render state.) - if (pcmd->UserCallback == ImDrawCallback_ResetRenderState) - ImGui_ImplSDLRenderer2_SetupRenderState(); - else - pcmd->UserCallback(cmd_list, pcmd); - } - else - { - // Project scissor/clipping rectangles into framebuffer space - ImVec2 clip_min((pcmd->ClipRect.x - clip_off.x) * clip_scale.x, (pcmd->ClipRect.y - clip_off.y) * clip_scale.y); - ImVec2 clip_max((pcmd->ClipRect.z - clip_off.x) * clip_scale.x, (pcmd->ClipRect.w - clip_off.y) * clip_scale.y); - if (clip_min.x < 0.0f) { clip_min.x = 0.0f; } - if (clip_min.y < 0.0f) { clip_min.y = 0.0f; } - if (clip_max.x > (float)fb_width) { clip_max.x = (float)fb_width; } - if (clip_max.y > (float)fb_height) { clip_max.y = (float)fb_height; } - if (clip_max.x <= clip_min.x || clip_max.y <= clip_min.y) - continue; - - SDL_Rect r = { (int)(clip_min.x), (int)(clip_min.y), (int)(clip_max.x - clip_min.x), (int)(clip_max.y - clip_min.y) }; - SDL_RenderSetClipRect(bd->SDLRenderer, &r); - - const float* xy = (const float*)(const void*)((const char*)(vtx_buffer + pcmd->VtxOffset) + IM_OFFSETOF(ImDrawVert, pos)); - const float* uv = (const float*)(const void*)((const char*)(vtx_buffer + pcmd->VtxOffset) + IM_OFFSETOF(ImDrawVert, uv)); -#if SDL_VERSION_ATLEAST(2,0,19) - const SDL_Color* color = (const SDL_Color*)(const void*)((const char*)(vtx_buffer + pcmd->VtxOffset) + IM_OFFSETOF(ImDrawVert, col)); // SDL 2.0.19+ -#else - const int* color = (const int*)(const void*)((const char*)(vtx_buffer + pcmd->VtxOffset) + IM_OFFSETOF(ImDrawVert, col)); // SDL 2.0.17 and 2.0.18 -#endif - - // Bind texture, Draw - SDL_Texture* tex = (SDL_Texture*)pcmd->GetTexID(); - SDL_RenderGeometryRaw(bd->SDLRenderer, tex, - xy, (int)sizeof(ImDrawVert), - color, (int)sizeof(ImDrawVert), - uv, (int)sizeof(ImDrawVert), - cmd_list->VtxBuffer.Size - pcmd->VtxOffset, - idx_buffer + pcmd->IdxOffset, pcmd->ElemCount, sizeof(ImDrawIdx)); - } - } - } - - // Restore modified SDL_Renderer state - SDL_RenderSetViewport(bd->SDLRenderer, &old.Viewport); - SDL_RenderSetClipRect(bd->SDLRenderer, old.ClipEnabled ? &old.ClipRect : nullptr); -} - -// Called by Init/NewFrame/Shutdown -bool ImGui_ImplSDLRenderer2_CreateFontsTexture() -{ - ImGuiIO& io = ImGui::GetIO(); - ImGui_ImplSDLRenderer2_Data* bd = ImGui_ImplSDLRenderer2_GetBackendData(); - - // Build texture atlas - unsigned char* pixels; - int width, height; - io.Fonts->GetTexDataAsRGBA32(&pixels, &width, &height); // Load as RGBA 32-bit (75% of the memory is wasted, but default font is so small) because it is more likely to be compatible with user's existing shaders. If your ImTextureId represent a higher-level concept than just a GL texture id, consider calling GetTexDataAsAlpha8() instead to save on GPU memory. - - // Upload texture to graphics system - // (Bilinear sampling is required by default. Set 'io.Fonts->Flags |= ImFontAtlasFlags_NoBakedLines' or 'style.AntiAliasedLinesUseTex = false' to allow point/nearest sampling) - bd->FontTexture = SDL_CreateTexture(bd->SDLRenderer, SDL_PIXELFORMAT_ABGR8888, SDL_TEXTUREACCESS_STATIC, width, height); - if (bd->FontTexture == nullptr) - { - SDL_Log("error creating texture"); - return false; - } - SDL_UpdateTexture(bd->FontTexture, nullptr, pixels, 4 * width); - SDL_SetTextureBlendMode(bd->FontTexture, SDL_BLENDMODE_BLEND); - SDL_SetTextureScaleMode(bd->FontTexture, SDL_ScaleModeLinear); - - // Store our identifier - io.Fonts->SetTexID((ImTextureID)(intptr_t)bd->FontTexture); - - return true; -} - -void ImGui_ImplSDLRenderer2_DestroyFontsTexture() -{ - ImGuiIO& io = ImGui::GetIO(); - ImGui_ImplSDLRenderer2_Data* bd = ImGui_ImplSDLRenderer2_GetBackendData(); - if (bd->FontTexture) - { - io.Fonts->SetTexID(0); - SDL_DestroyTexture(bd->FontTexture); - bd->FontTexture = nullptr; - } -} - -bool ImGui_ImplSDLRenderer2_CreateDeviceObjects() -{ - return ImGui_ImplSDLRenderer2_CreateFontsTexture(); -} - -void ImGui_ImplSDLRenderer2_DestroyDeviceObjects() -{ - ImGui_ImplSDLRenderer2_DestroyFontsTexture(); -} - -//----------------------------------------------------------------------------- - -#if defined(__clang__) -#pragma clang diagnostic pop -#endif - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_sdlrenderer2.h b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_sdlrenderer2.h deleted file mode 100644 index 1b02c74..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_sdlrenderer2.h +++ /dev/null @@ -1,41 +0,0 @@ -// dear imgui: Renderer Backend for SDL_Renderer for SDL2 -// (Requires: SDL 2.0.17+) - -// Note how SDL_Renderer is an _optional_ component of SDL2. -// For a multi-platform app consider using e.g. SDL+DirectX on Windows and SDL+OpenGL on Linux/OSX. -// If your application will want to render any non trivial amount of graphics other than UI, -// please be aware that SDL_Renderer currently offers a limited graphic API to the end-user and -// it might be difficult to step out of those boundaries. - -// Implemented features: -// [X] Renderer: User texture binding. Use 'SDL_Texture*' as ImTextureID. Read the FAQ about ImTextureID! -// [X] Renderer: Large meshes support (64k+ vertices) with 16-bit indices. -// Missing features: -// [ ] Renderer: Multi-viewport support (multiple windows). - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#pragma once -#ifndef IMGUI_DISABLE -#include "imgui.h" // IMGUI_IMPL_API - -struct SDL_Renderer; - -IMGUI_IMPL_API bool ImGui_ImplSDLRenderer2_Init(SDL_Renderer* renderer); -IMGUI_IMPL_API void ImGui_ImplSDLRenderer2_Shutdown(); -IMGUI_IMPL_API void ImGui_ImplSDLRenderer2_NewFrame(); -IMGUI_IMPL_API void ImGui_ImplSDLRenderer2_RenderDrawData(ImDrawData* draw_data); - -// Called by Init/NewFrame/Shutdown -IMGUI_IMPL_API bool ImGui_ImplSDLRenderer2_CreateFontsTexture(); -IMGUI_IMPL_API void ImGui_ImplSDLRenderer2_DestroyFontsTexture(); -IMGUI_IMPL_API bool ImGui_ImplSDLRenderer2_CreateDeviceObjects(); -IMGUI_IMPL_API void ImGui_ImplSDLRenderer2_DestroyDeviceObjects(); - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_sdlrenderer3.cpp b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_sdlrenderer3.cpp deleted file mode 100644 index 2deb607..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_sdlrenderer3.cpp +++ /dev/null @@ -1,263 +0,0 @@ -// dear imgui: Renderer Backend for SDL_Renderer for SDL3 -// (Requires: SDL 3.0.0+) - -// Note how SDL_Renderer is an _optional_ component of SDL3. -// For a multi-platform app consider using e.g. SDL+DirectX on Windows and SDL+OpenGL on Linux/OSX. -// If your application will want to render any non trivial amount of graphics other than UI, -// please be aware that SDL_Renderer currently offers a limited graphic API to the end-user and -// it might be difficult to step out of those boundaries. - -// Implemented features: -// [X] Renderer: User texture binding. Use 'SDL_Texture*' as ImTextureID. Read the FAQ about ImTextureID! -// [X] Renderer: Large meshes support (64k+ vertices) with 16-bit indices. -// Missing features: -// [ ] Renderer: Multi-viewport support (multiple windows). - -// You can copy and use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -// CHANGELOG -// 2023-05-30: Initial version. - -#include "imgui.h" -#ifndef IMGUI_DISABLE -#include "imgui_impl_sdlrenderer3.h" -#include // intptr_t - -// Clang warnings with -Weverything -#if defined(__clang__) -#pragma clang diagnostic push -#pragma clang diagnostic ignored "-Wsign-conversion" // warning: implicit conversion changes signedness -#endif - -// SDL -#include -#if !SDL_VERSION_ATLEAST(3,0,0) -#error This backend requires SDL 3.0.0+ -#endif - -// SDL_Renderer data -struct ImGui_ImplSDLRenderer3_Data -{ - SDL_Renderer* SDLRenderer; - SDL_Texture* FontTexture; - ImGui_ImplSDLRenderer3_Data() { memset((void*)this, 0, sizeof(*this)); } -}; - -// Backend data stored in io.BackendRendererUserData to allow support for multiple Dear ImGui contexts -// It is STRONGLY preferred that you use docking branch with multi-viewports (== single Dear ImGui context + multiple windows) instead of multiple Dear ImGui contexts. -static ImGui_ImplSDLRenderer3_Data* ImGui_ImplSDLRenderer3_GetBackendData() -{ - return ImGui::GetCurrentContext() ? (ImGui_ImplSDLRenderer3_Data*)ImGui::GetIO().BackendRendererUserData : nullptr; -} - -// Functions -bool ImGui_ImplSDLRenderer3_Init(SDL_Renderer* renderer) -{ - ImGuiIO& io = ImGui::GetIO(); - IM_ASSERT(io.BackendRendererUserData == nullptr && "Already initialized a renderer backend!"); - IM_ASSERT(renderer != nullptr && "SDL_Renderer not initialized!"); - - // Setup backend capabilities flags - ImGui_ImplSDLRenderer3_Data* bd = IM_NEW(ImGui_ImplSDLRenderer3_Data)(); - io.BackendRendererUserData = (void*)bd; - io.BackendRendererName = "imgui_impl_sdlrenderer3"; - io.BackendFlags |= ImGuiBackendFlags_RendererHasVtxOffset; // We can honor the ImDrawCmd::VtxOffset field, allowing for large meshes. - - bd->SDLRenderer = renderer; - - return true; -} - -void ImGui_ImplSDLRenderer3_Shutdown() -{ - ImGui_ImplSDLRenderer3_Data* bd = ImGui_ImplSDLRenderer3_GetBackendData(); - IM_ASSERT(bd != nullptr && "No renderer backend to shutdown, or already shutdown?"); - ImGuiIO& io = ImGui::GetIO(); - - ImGui_ImplSDLRenderer3_DestroyDeviceObjects(); - - io.BackendRendererName = nullptr; - io.BackendRendererUserData = nullptr; - io.BackendFlags &= ~ImGuiBackendFlags_RendererHasVtxOffset; - IM_DELETE(bd); -} - -static void ImGui_ImplSDLRenderer3_SetupRenderState() -{ - ImGui_ImplSDLRenderer3_Data* bd = ImGui_ImplSDLRenderer3_GetBackendData(); - - // Clear out any viewports and cliprect set by the user - // FIXME: Technically speaking there are lots of other things we could backup/setup/restore during our render process. - SDL_SetRenderViewport(bd->SDLRenderer, nullptr); - SDL_SetRenderClipRect(bd->SDLRenderer, nullptr); -} - -void ImGui_ImplSDLRenderer3_NewFrame() -{ - ImGui_ImplSDLRenderer3_Data* bd = ImGui_ImplSDLRenderer3_GetBackendData(); - IM_ASSERT(bd != nullptr && "Did you call ImGui_ImplSDLRenderer3_Init()?"); - - if (!bd->FontTexture) - ImGui_ImplSDLRenderer3_CreateDeviceObjects(); -} - -void ImGui_ImplSDLRenderer3_RenderDrawData(ImDrawData* draw_data) -{ - ImGui_ImplSDLRenderer3_Data* bd = ImGui_ImplSDLRenderer3_GetBackendData(); - - // If there's a scale factor set by the user, use that instead - // If the user has specified a scale factor to SDL_Renderer already via SDL_RenderSetScale(), SDL will scale whatever we pass - // to SDL_RenderGeometryRaw() by that scale factor. In that case we don't want to be also scaling it ourselves here. - float rsx = 1.0f; - float rsy = 1.0f; - SDL_GetRenderScale(bd->SDLRenderer, &rsx, &rsy); - ImVec2 render_scale; - render_scale.x = (rsx == 1.0f) ? draw_data->FramebufferScale.x : 1.0f; - render_scale.y = (rsy == 1.0f) ? draw_data->FramebufferScale.y : 1.0f; - - // Avoid rendering when minimized, scale coordinates for retina displays (screen coordinates != framebuffer coordinates) - int fb_width = (int)(draw_data->DisplaySize.x * render_scale.x); - int fb_height = (int)(draw_data->DisplaySize.y * render_scale.y); - if (fb_width == 0 || fb_height == 0) - return; - - // Backup SDL_Renderer state that will be modified to restore it afterwards - struct BackupSDLRendererState - { - SDL_Rect Viewport; - bool ClipEnabled; - SDL_Rect ClipRect; - }; - BackupSDLRendererState old = {}; - old.ClipEnabled = SDL_RenderClipEnabled(bd->SDLRenderer) == SDL_TRUE; - SDL_GetRenderViewport(bd->SDLRenderer, &old.Viewport); - SDL_GetRenderClipRect(bd->SDLRenderer, &old.ClipRect); - - // Will project scissor/clipping rectangles into framebuffer space - ImVec2 clip_off = draw_data->DisplayPos; // (0,0) unless using multi-viewports - ImVec2 clip_scale = render_scale; - - // Render command lists - ImGui_ImplSDLRenderer3_SetupRenderState(); - for (int n = 0; n < draw_data->CmdListsCount; n++) - { - const ImDrawList* cmd_list = draw_data->CmdLists[n]; - const ImDrawVert* vtx_buffer = cmd_list->VtxBuffer.Data; - const ImDrawIdx* idx_buffer = cmd_list->IdxBuffer.Data; - - for (int cmd_i = 0; cmd_i < cmd_list->CmdBuffer.Size; cmd_i++) - { - const ImDrawCmd* pcmd = &cmd_list->CmdBuffer[cmd_i]; - if (pcmd->UserCallback) - { - // User callback, registered via ImDrawList::AddCallback() - // (ImDrawCallback_ResetRenderState is a special callback value used by the user to request the renderer to reset render state.) - if (pcmd->UserCallback == ImDrawCallback_ResetRenderState) - ImGui_ImplSDLRenderer3_SetupRenderState(); - else - pcmd->UserCallback(cmd_list, pcmd); - } - else - { - // Project scissor/clipping rectangles into framebuffer space - ImVec2 clip_min((pcmd->ClipRect.x - clip_off.x) * clip_scale.x, (pcmd->ClipRect.y - clip_off.y) * clip_scale.y); - ImVec2 clip_max((pcmd->ClipRect.z - clip_off.x) * clip_scale.x, (pcmd->ClipRect.w - clip_off.y) * clip_scale.y); - if (clip_min.x < 0.0f) { clip_min.x = 0.0f; } - if (clip_min.y < 0.0f) { clip_min.y = 0.0f; } - if (clip_max.x > (float)fb_width) { clip_max.x = (float)fb_width; } - if (clip_max.y > (float)fb_height) { clip_max.y = (float)fb_height; } - if (clip_max.x <= clip_min.x || clip_max.y <= clip_min.y) - continue; - - SDL_Rect r = { (int)(clip_min.x), (int)(clip_min.y), (int)(clip_max.x - clip_min.x), (int)(clip_max.y - clip_min.y) }; - SDL_SetRenderClipRect(bd->SDLRenderer, &r); - - const float* xy = (const float*)(const void*)((const char*)(vtx_buffer + pcmd->VtxOffset) + IM_OFFSETOF(ImDrawVert, pos)); - const float* uv = (const float*)(const void*)((const char*)(vtx_buffer + pcmd->VtxOffset) + IM_OFFSETOF(ImDrawVert, uv)); -#if SDL_VERSION_ATLEAST(2,0,19) - const SDL_Color* color = (const SDL_Color*)(const void*)((const char*)(vtx_buffer + pcmd->VtxOffset) + IM_OFFSETOF(ImDrawVert, col)); // SDL 2.0.19+ -#else - const int* color = (const int*)(const void*)((const char*)(vtx_buffer + pcmd->VtxOffset) + IM_OFFSETOF(ImDrawVert, col)); // SDL 2.0.17 and 2.0.18 -#endif - - // Bind texture, Draw - SDL_Texture* tex = (SDL_Texture*)pcmd->GetTexID(); - SDL_RenderGeometryRaw(bd->SDLRenderer, tex, - xy, (int)sizeof(ImDrawVert), - color, (int)sizeof(ImDrawVert), - uv, (int)sizeof(ImDrawVert), - cmd_list->VtxBuffer.Size - pcmd->VtxOffset, - idx_buffer + pcmd->IdxOffset, pcmd->ElemCount, sizeof(ImDrawIdx)); - } - } - } - - // Restore modified SDL_Renderer state - SDL_SetRenderViewport(bd->SDLRenderer, &old.Viewport); - SDL_SetRenderClipRect(bd->SDLRenderer, old.ClipEnabled ? &old.ClipRect : nullptr); -} - -// Called by Init/NewFrame/Shutdown -bool ImGui_ImplSDLRenderer3_CreateFontsTexture() -{ - ImGuiIO& io = ImGui::GetIO(); - ImGui_ImplSDLRenderer3_Data* bd = ImGui_ImplSDLRenderer3_GetBackendData(); - - // Build texture atlas - unsigned char* pixels; - int width, height; - io.Fonts->GetTexDataAsRGBA32(&pixels, &width, &height); // Load as RGBA 32-bit (75% of the memory is wasted, but default font is so small) because it is more likely to be compatible with user's existing shaders. If your ImTextureId represent a higher-level concept than just a GL texture id, consider calling GetTexDataAsAlpha8() instead to save on GPU memory. - - // Upload texture to graphics system - // (Bilinear sampling is required by default. Set 'io.Fonts->Flags |= ImFontAtlasFlags_NoBakedLines' or 'style.AntiAliasedLinesUseTex = false' to allow point/nearest sampling) - bd->FontTexture = SDL_CreateTexture(bd->SDLRenderer, SDL_PIXELFORMAT_ABGR8888, SDL_TEXTUREACCESS_STATIC, width, height); - if (bd->FontTexture == nullptr) - { - SDL_Log("error creating texture"); - return false; - } - SDL_UpdateTexture(bd->FontTexture, nullptr, pixels, 4 * width); - SDL_SetTextureBlendMode(bd->FontTexture, SDL_BLENDMODE_BLEND); - SDL_SetTextureScaleMode(bd->FontTexture, SDL_SCALEMODE_LINEAR); - - // Store our identifier - io.Fonts->SetTexID((ImTextureID)(intptr_t)bd->FontTexture); - - return true; -} - -void ImGui_ImplSDLRenderer3_DestroyFontsTexture() -{ - ImGuiIO& io = ImGui::GetIO(); - ImGui_ImplSDLRenderer3_Data* bd = ImGui_ImplSDLRenderer3_GetBackendData(); - if (bd->FontTexture) - { - io.Fonts->SetTexID(0); - SDL_DestroyTexture(bd->FontTexture); - bd->FontTexture = nullptr; - } -} - -bool ImGui_ImplSDLRenderer3_CreateDeviceObjects() -{ - return ImGui_ImplSDLRenderer3_CreateFontsTexture(); -} - -void ImGui_ImplSDLRenderer3_DestroyDeviceObjects() -{ - ImGui_ImplSDLRenderer3_DestroyFontsTexture(); -} - -//----------------------------------------------------------------------------- - -#if defined(__clang__) -#pragma clang diagnostic pop -#endif - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_sdlrenderer3.h b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_sdlrenderer3.h deleted file mode 100644 index fd3cc17..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_sdlrenderer3.h +++ /dev/null @@ -1,41 +0,0 @@ -// dear imgui: Renderer Backend for SDL_Renderer for SDL3 -// (Requires: SDL 3.0.0+) - -// Note how SDL_Renderer is an _optional_ component of SDL3. -// For a multi-platform app consider using e.g. SDL+DirectX on Windows and SDL+OpenGL on Linux/OSX. -// If your application will want to render any non trivial amount of graphics other than UI, -// please be aware that SDL_Renderer currently offers a limited graphic API to the end-user and -// it might be difficult to step out of those boundaries. - -// Implemented features: -// [X] Renderer: User texture binding. Use 'SDL_Texture*' as ImTextureID. Read the FAQ about ImTextureID! -// [X] Renderer: Large meshes support (64k+ vertices) with 16-bit indices. -// Missing features: -// [ ] Renderer: Multi-viewport support (multiple windows). - -// You can copy and use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#pragma once -#include "imgui.h" // IMGUI_IMPL_API -#ifndef IMGUI_DISABLE - -struct SDL_Renderer; - -IMGUI_IMPL_API bool ImGui_ImplSDLRenderer3_Init(SDL_Renderer* renderer); -IMGUI_IMPL_API void ImGui_ImplSDLRenderer3_Shutdown(); -IMGUI_IMPL_API void ImGui_ImplSDLRenderer3_NewFrame(); -IMGUI_IMPL_API void ImGui_ImplSDLRenderer3_RenderDrawData(ImDrawData* draw_data); - -// Called by Init/NewFrame/Shutdown -IMGUI_IMPL_API bool ImGui_ImplSDLRenderer3_CreateFontsTexture(); -IMGUI_IMPL_API void ImGui_ImplSDLRenderer3_DestroyFontsTexture(); -IMGUI_IMPL_API bool ImGui_ImplSDLRenderer3_CreateDeviceObjects(); -IMGUI_IMPL_API void ImGui_ImplSDLRenderer3_DestroyDeviceObjects(); - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_vulkan.cpp b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_vulkan.cpp deleted file mode 100644 index c75ceb3..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_vulkan.cpp +++ /dev/null @@ -1,1816 +0,0 @@ -// dear imgui: Renderer Backend for Vulkan -// This needs to be used along with a Platform Backend (e.g. GLFW, SDL, Win32, custom..) - -// Implemented features: -// [x] Renderer: User texture binding. Use 'VkDescriptorSet' as ImTextureID. Read the FAQ about ImTextureID! See https://github.com/ocornut/imgui/pull/914 for discussions. -// [X] Renderer: Large meshes support (64k+ vertices) with 16-bit indices. -// [x] Renderer: Multi-viewport / platform windows. With issues (flickering when creating a new viewport). - -// Important: on 32-bit systems, user texture binding is only supported if your imconfig file has '#define ImTextureID ImU64'. -// This is because we need ImTextureID to carry a 64-bit value and by default ImTextureID is defined as void*. -// To build this on 32-bit systems and support texture changes: -// - [Solution 1] IDE/msbuild: in "Properties/C++/Preprocessor Definitions" add 'ImTextureID=ImU64' (this is what we do in our .vcxproj files) -// - [Solution 2] IDE/msbuild: in "Properties/C++/Preprocessor Definitions" add 'IMGUI_USER_CONFIG="my_imgui_config.h"' and inside 'my_imgui_config.h' add '#define ImTextureID ImU64' and as many other options as you like. -// - [Solution 3] IDE/msbuild: edit imconfig.h and add '#define ImTextureID ImU64' (prefer solution 2 to create your own config file!) -// - [Solution 4] command-line: add '/D ImTextureID=ImU64' to your cl.exe command-line (this is what we do in our batch files) - -// The aim of imgui_impl_vulkan.h/.cpp is to be usable in your engine without any modification. -// IF YOU FEEL YOU NEED TO MAKE ANY CHANGE TO THIS CODE, please share them and your feedback at https://github.com/ocornut/imgui/ - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -// Important note to the reader who wish to integrate imgui_impl_vulkan.cpp/.h in their own engine/app. -// - Common ImGui_ImplVulkan_XXX functions and structures are used to interface with imgui_impl_vulkan.cpp/.h. -// You will use those if you want to use this rendering backend in your engine/app. -// - Helper ImGui_ImplVulkanH_XXX functions and structures are only used by this example (main.cpp) and by -// the backend itself (imgui_impl_vulkan.cpp), but should PROBABLY NOT be used by your own engine/app code. -// Read comments in imgui_impl_vulkan.h. - -// CHANGELOG -// (minor and older changes stripped away, please see git history for details) -// 2023-XX-XX: Platform: Added support for multiple windows via the ImGuiPlatformIO interface. -// 2023-07-04: Vulkan: Added optional support for VK_KHR_dynamic_rendering. User needs to set init_info->UseDynamicRendering = true and init_info->ColorAttachmentFormat. -// 2023-01-02: Vulkan: Fixed sampler passed to ImGui_ImplVulkan_AddTexture() not being honored + removed a bunch of duplicate code. -// 2022-10-11: Using 'nullptr' instead of 'NULL' as per our switch to C++11. -// 2022-10-04: Vulkan: Added experimental ImGui_ImplVulkan_RemoveTexture() for api symetry. (#914, #5738). -// 2022-01-20: Vulkan: Added support for ImTextureID as VkDescriptorSet. User need to call ImGui_ImplVulkan_AddTexture(). Building for 32-bit targets requires '#define ImTextureID ImU64'. (#914). -// 2021-10-15: Vulkan: Call vkCmdSetScissor() at the end of render a full-viewport to reduce likehood of issues with people using VK_DYNAMIC_STATE_SCISSOR in their app without calling vkCmdSetScissor() explicitly every frame. -// 2021-06-29: Reorganized backend to pull data from a single structure to facilitate usage with multiple-contexts (all g_XXXX access changed to bd->XXXX). -// 2021-03-22: Vulkan: Fix mapped memory validation error when buffer sizes are not multiple of VkPhysicalDeviceLimits::nonCoherentAtomSize. -// 2021-02-18: Vulkan: Change blending equation to preserve alpha in output buffer. -// 2021-01-27: Vulkan: Added support for custom function load and IMGUI_IMPL_VULKAN_NO_PROTOTYPES by using ImGui_ImplVulkan_LoadFunctions(). -// 2020-11-11: Vulkan: Added support for specifying which subpass to reference during VkPipeline creation. -// 2020-09-07: Vulkan: Added VkPipeline parameter to ImGui_ImplVulkan_RenderDrawData (default to one passed to ImGui_ImplVulkan_Init). -// 2020-05-04: Vulkan: Fixed crash if initial frame has no vertices. -// 2020-04-26: Vulkan: Fixed edge case where render callbacks wouldn't be called if the ImDrawData didn't have vertices. -// 2019-08-01: Vulkan: Added support for specifying multisample count. Set ImGui_ImplVulkan_InitInfo::MSAASamples to one of the VkSampleCountFlagBits values to use, default is non-multisampled as before. -// 2019-05-29: Vulkan: Added support for large mesh (64K+ vertices), enable ImGuiBackendFlags_RendererHasVtxOffset flag. -// 2019-04-30: Vulkan: Added support for special ImDrawCallback_ResetRenderState callback to reset render state. -// 2019-04-04: *BREAKING CHANGE*: Vulkan: Added ImageCount/MinImageCount fields in ImGui_ImplVulkan_InitInfo, required for initialization (was previously a hard #define IMGUI_VK_QUEUED_FRAMES 2). Added ImGui_ImplVulkan_SetMinImageCount(). -// 2019-04-04: Vulkan: Added VkInstance argument to ImGui_ImplVulkanH_CreateWindow() optional helper. -// 2019-04-04: Vulkan: Avoid passing negative coordinates to vkCmdSetScissor, which debug validation layers do not like. -// 2019-04-01: Vulkan: Support for 32-bit index buffer (#define ImDrawIdx unsigned int). -// 2019-02-16: Vulkan: Viewport and clipping rectangles correctly using draw_data->FramebufferScale to allow retina display. -// 2018-11-30: Misc: Setting up io.BackendRendererName so it can be displayed in the About Window. -// 2018-08-25: Vulkan: Fixed mishandled VkSurfaceCapabilitiesKHR::maxImageCount=0 case. -// 2018-06-22: Inverted the parameters to ImGui_ImplVulkan_RenderDrawData() to be consistent with other backends. -// 2018-06-08: Misc: Extracted imgui_impl_vulkan.cpp/.h away from the old combined GLFW+Vulkan example. -// 2018-06-08: Vulkan: Use draw_data->DisplayPos and draw_data->DisplaySize to setup projection matrix and clipping rectangle. -// 2018-03-03: Vulkan: Various refactor, created a couple of ImGui_ImplVulkanH_XXX helper that the example can use and that viewport support will use. -// 2018-03-01: Vulkan: Renamed ImGui_ImplVulkan_Init_Info to ImGui_ImplVulkan_InitInfo and fields to match more closely Vulkan terminology. -// 2018-02-16: Misc: Obsoleted the io.RenderDrawListsFn callback, ImGui_ImplVulkan_Render() calls ImGui_ImplVulkan_RenderDrawData() itself. -// 2018-02-06: Misc: Removed call to ImGui::Shutdown() which is not available from 1.60 WIP, user needs to call CreateContext/DestroyContext themselves. -// 2017-05-15: Vulkan: Fix scissor offset being negative. Fix new Vulkan validation warnings. Set required depth member for buffer image copy. -// 2016-11-13: Vulkan: Fix validation layer warnings and errors and redeclare gl_PerVertex. -// 2016-10-18: Vulkan: Add location decorators & change to use structs as in/out in glsl, update embedded spv (produced with glslangValidator -x). Null the released resources. -// 2016-08-27: Vulkan: Fix Vulkan example for use when a depth buffer is active. - -#include "imgui.h" -#ifndef IMGUI_DISABLE -#include "imgui_impl_vulkan.h" -#include - -// Visual Studio warnings -#ifdef _MSC_VER -#pragma warning (disable: 4127) // condition expression is constant -#endif - -// Reusable buffers used for rendering 1 current in-flight frame, for ImGui_ImplVulkan_RenderDrawData() -// [Please zero-clear before use!] -struct ImGui_ImplVulkanH_FrameRenderBuffers -{ - VkDeviceMemory VertexBufferMemory; - VkDeviceMemory IndexBufferMemory; - VkDeviceSize VertexBufferSize; - VkDeviceSize IndexBufferSize; - VkBuffer VertexBuffer; - VkBuffer IndexBuffer; -}; - -// Each viewport will hold 1 ImGui_ImplVulkanH_WindowRenderBuffers -// [Please zero-clear before use!] -struct ImGui_ImplVulkanH_WindowRenderBuffers -{ - uint32_t Index; - uint32_t Count; - ImGui_ImplVulkanH_FrameRenderBuffers* FrameRenderBuffers; -}; - -// For multi-viewport support: -// Helper structure we store in the void* RendererUserData field of each ImGuiViewport to easily retrieve our backend data. -struct ImGui_ImplVulkan_ViewportData -{ - bool WindowOwned; - ImGui_ImplVulkanH_Window Window; // Used by secondary viewports only - ImGui_ImplVulkanH_WindowRenderBuffers RenderBuffers; // Used by all viewports - - ImGui_ImplVulkan_ViewportData() { WindowOwned = false; memset(&RenderBuffers, 0, sizeof(RenderBuffers)); } - ~ImGui_ImplVulkan_ViewportData() { } -}; - -// Vulkan data -struct ImGui_ImplVulkan_Data -{ - ImGui_ImplVulkan_InitInfo VulkanInitInfo; - VkRenderPass RenderPass; - VkDeviceSize BufferMemoryAlignment; - VkPipelineCreateFlags PipelineCreateFlags; - VkDescriptorSetLayout DescriptorSetLayout; - VkPipelineLayout PipelineLayout; - VkPipeline Pipeline; - uint32_t Subpass; - VkShaderModule ShaderModuleVert; - VkShaderModule ShaderModuleFrag; - - // Font data - VkSampler FontSampler; - VkDeviceMemory FontMemory; - VkImage FontImage; - VkImageView FontView; - VkDescriptorSet FontDescriptorSet; - VkDeviceMemory UploadBufferMemory; - VkBuffer UploadBuffer; - - // Render buffers for main window - ImGui_ImplVulkanH_WindowRenderBuffers MainWindowRenderBuffers; - - ImGui_ImplVulkan_Data() - { - memset((void*)this, 0, sizeof(*this)); - BufferMemoryAlignment = 256; - } -}; - -// Forward Declarations -bool ImGui_ImplVulkan_CreateDeviceObjects(); -void ImGui_ImplVulkan_DestroyDeviceObjects(); -void ImGui_ImplVulkanH_DestroyFrame(VkDevice device, ImGui_ImplVulkanH_Frame* fd, const VkAllocationCallbacks* allocator); -void ImGui_ImplVulkanH_DestroyFrameSemaphores(VkDevice device, ImGui_ImplVulkanH_FrameSemaphores* fsd, const VkAllocationCallbacks* allocator); -void ImGui_ImplVulkanH_DestroyFrameRenderBuffers(VkDevice device, ImGui_ImplVulkanH_FrameRenderBuffers* buffers, const VkAllocationCallbacks* allocator); -void ImGui_ImplVulkanH_DestroyWindowRenderBuffers(VkDevice device, ImGui_ImplVulkanH_WindowRenderBuffers* buffers, const VkAllocationCallbacks* allocator); -void ImGui_ImplVulkanH_DestroyAllViewportsRenderBuffers(VkDevice device, const VkAllocationCallbacks* allocator); -void ImGui_ImplVulkanH_CreateWindowSwapChain(VkPhysicalDevice physical_device, VkDevice device, ImGui_ImplVulkanH_Window* wd, const VkAllocationCallbacks* allocator, int w, int h, uint32_t min_image_count); -void ImGui_ImplVulkanH_CreateWindowCommandBuffers(VkPhysicalDevice physical_device, VkDevice device, ImGui_ImplVulkanH_Window* wd, uint32_t queue_family, const VkAllocationCallbacks* allocator); - -// Vulkan prototypes for use with custom loaders -// (see description of IMGUI_IMPL_VULKAN_NO_PROTOTYPES in imgui_impl_vulkan.h -#ifdef VK_NO_PROTOTYPES -static bool g_FunctionsLoaded = false; -#else -static bool g_FunctionsLoaded = true; -#endif -#ifdef VK_NO_PROTOTYPES -#define IMGUI_VULKAN_FUNC_MAP(IMGUI_VULKAN_FUNC_MAP_MACRO) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkAllocateCommandBuffers) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkAllocateDescriptorSets) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkAllocateMemory) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkBindBufferMemory) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkBindImageMemory) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkCmdBindDescriptorSets) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkCmdBindIndexBuffer) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkCmdBindPipeline) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkCmdBindVertexBuffers) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkCmdCopyBufferToImage) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkCmdDrawIndexed) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkCmdPipelineBarrier) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkCmdPushConstants) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkCmdSetScissor) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkCmdSetViewport) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkCreateBuffer) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkCreateCommandPool) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkCreateDescriptorSetLayout) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkCreateFence) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkCreateFramebuffer) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkCreateGraphicsPipelines) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkCreateImage) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkCreateImageView) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkCreatePipelineLayout) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkCreateRenderPass) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkCreateSampler) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkCreateSemaphore) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkCreateShaderModule) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkCreateSwapchainKHR) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkDestroyBuffer) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkDestroyCommandPool) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkDestroyDescriptorSetLayout) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkDestroyFence) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkDestroyFramebuffer) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkDestroyImage) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkDestroyImageView) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkDestroyPipeline) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkDestroyPipelineLayout) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkDestroyRenderPass) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkDestroySampler) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkDestroySemaphore) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkDestroyShaderModule) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkDestroySurfaceKHR) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkDestroySwapchainKHR) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkDeviceWaitIdle) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkFlushMappedMemoryRanges) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkFreeCommandBuffers) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkFreeDescriptorSets) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkFreeMemory) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkGetBufferMemoryRequirements) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkGetImageMemoryRequirements) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkGetPhysicalDeviceMemoryProperties) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkGetPhysicalDeviceSurfaceCapabilitiesKHR) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkGetPhysicalDeviceSurfaceFormatsKHR) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkGetPhysicalDeviceSurfacePresentModesKHR) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkGetSwapchainImagesKHR) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkMapMemory) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkUnmapMemory) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkUpdateDescriptorSets) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkGetPhysicalDeviceSurfaceSupportKHR) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkWaitForFences) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkCmdBeginRenderPass) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkCmdEndRenderPass) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkQueuePresentKHR) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkBeginCommandBuffer) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkEndCommandBuffer) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkResetFences) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkQueueSubmit) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkResetCommandPool) \ - IMGUI_VULKAN_FUNC_MAP_MACRO(vkAcquireNextImageKHR) - -// Define function pointers -#define IMGUI_VULKAN_FUNC_DEF(func) static PFN_##func func; -IMGUI_VULKAN_FUNC_MAP(IMGUI_VULKAN_FUNC_DEF) -#undef IMGUI_VULKAN_FUNC_DEF -#endif // VK_NO_PROTOTYPES - -#if defined(VK_VERSION_1_3) || defined(VK_KHR_dynamic_rendering) -#define IMGUI_IMPL_VULKAN_HAS_DYNAMIC_RENDERING -static PFN_vkCmdBeginRenderingKHR ImGuiImplVulkanFuncs_vkCmdBeginRenderingKHR; -static PFN_vkCmdEndRenderingKHR ImGuiImplVulkanFuncs_vkCmdEndRenderingKHR; -#endif - -//----------------------------------------------------------------------------- -// SHADERS -//----------------------------------------------------------------------------- - -// Forward Declarations -static void ImGui_ImplVulkan_InitPlatformInterface(); -static void ImGui_ImplVulkan_ShutdownPlatformInterface(); - -// glsl_shader.vert, compiled with: -// # glslangValidator -V -x -o glsl_shader.vert.u32 glsl_shader.vert -/* -#version 450 core -layout(location = 0) in vec2 aPos; -layout(location = 1) in vec2 aUV; -layout(location = 2) in vec4 aColor; -layout(push_constant) uniform uPushConstant { vec2 uScale; vec2 uTranslate; } pc; - -out gl_PerVertex { vec4 gl_Position; }; -layout(location = 0) out struct { vec4 Color; vec2 UV; } Out; - -void main() -{ - Out.Color = aColor; - Out.UV = aUV; - gl_Position = vec4(aPos * pc.uScale + pc.uTranslate, 0, 1); -} -*/ -static uint32_t __glsl_shader_vert_spv[] = -{ - 0x07230203,0x00010000,0x00080001,0x0000002e,0x00000000,0x00020011,0x00000001,0x0006000b, - 0x00000001,0x4c534c47,0x6474732e,0x3035342e,0x00000000,0x0003000e,0x00000000,0x00000001, - 0x000a000f,0x00000000,0x00000004,0x6e69616d,0x00000000,0x0000000b,0x0000000f,0x00000015, - 0x0000001b,0x0000001c,0x00030003,0x00000002,0x000001c2,0x00040005,0x00000004,0x6e69616d, - 0x00000000,0x00030005,0x00000009,0x00000000,0x00050006,0x00000009,0x00000000,0x6f6c6f43, - 0x00000072,0x00040006,0x00000009,0x00000001,0x00005655,0x00030005,0x0000000b,0x0074754f, - 0x00040005,0x0000000f,0x6c6f4361,0x0000726f,0x00030005,0x00000015,0x00565561,0x00060005, - 0x00000019,0x505f6c67,0x65567265,0x78657472,0x00000000,0x00060006,0x00000019,0x00000000, - 0x505f6c67,0x7469736f,0x006e6f69,0x00030005,0x0000001b,0x00000000,0x00040005,0x0000001c, - 0x736f5061,0x00000000,0x00060005,0x0000001e,0x73755075,0x6e6f4368,0x6e617473,0x00000074, - 0x00050006,0x0000001e,0x00000000,0x61635375,0x0000656c,0x00060006,0x0000001e,0x00000001, - 0x61725475,0x616c736e,0x00006574,0x00030005,0x00000020,0x00006370,0x00040047,0x0000000b, - 0x0000001e,0x00000000,0x00040047,0x0000000f,0x0000001e,0x00000002,0x00040047,0x00000015, - 0x0000001e,0x00000001,0x00050048,0x00000019,0x00000000,0x0000000b,0x00000000,0x00030047, - 0x00000019,0x00000002,0x00040047,0x0000001c,0x0000001e,0x00000000,0x00050048,0x0000001e, - 0x00000000,0x00000023,0x00000000,0x00050048,0x0000001e,0x00000001,0x00000023,0x00000008, - 0x00030047,0x0000001e,0x00000002,0x00020013,0x00000002,0x00030021,0x00000003,0x00000002, - 0x00030016,0x00000006,0x00000020,0x00040017,0x00000007,0x00000006,0x00000004,0x00040017, - 0x00000008,0x00000006,0x00000002,0x0004001e,0x00000009,0x00000007,0x00000008,0x00040020, - 0x0000000a,0x00000003,0x00000009,0x0004003b,0x0000000a,0x0000000b,0x00000003,0x00040015, - 0x0000000c,0x00000020,0x00000001,0x0004002b,0x0000000c,0x0000000d,0x00000000,0x00040020, - 0x0000000e,0x00000001,0x00000007,0x0004003b,0x0000000e,0x0000000f,0x00000001,0x00040020, - 0x00000011,0x00000003,0x00000007,0x0004002b,0x0000000c,0x00000013,0x00000001,0x00040020, - 0x00000014,0x00000001,0x00000008,0x0004003b,0x00000014,0x00000015,0x00000001,0x00040020, - 0x00000017,0x00000003,0x00000008,0x0003001e,0x00000019,0x00000007,0x00040020,0x0000001a, - 0x00000003,0x00000019,0x0004003b,0x0000001a,0x0000001b,0x00000003,0x0004003b,0x00000014, - 0x0000001c,0x00000001,0x0004001e,0x0000001e,0x00000008,0x00000008,0x00040020,0x0000001f, - 0x00000009,0x0000001e,0x0004003b,0x0000001f,0x00000020,0x00000009,0x00040020,0x00000021, - 0x00000009,0x00000008,0x0004002b,0x00000006,0x00000028,0x00000000,0x0004002b,0x00000006, - 0x00000029,0x3f800000,0x00050036,0x00000002,0x00000004,0x00000000,0x00000003,0x000200f8, - 0x00000005,0x0004003d,0x00000007,0x00000010,0x0000000f,0x00050041,0x00000011,0x00000012, - 0x0000000b,0x0000000d,0x0003003e,0x00000012,0x00000010,0x0004003d,0x00000008,0x00000016, - 0x00000015,0x00050041,0x00000017,0x00000018,0x0000000b,0x00000013,0x0003003e,0x00000018, - 0x00000016,0x0004003d,0x00000008,0x0000001d,0x0000001c,0x00050041,0x00000021,0x00000022, - 0x00000020,0x0000000d,0x0004003d,0x00000008,0x00000023,0x00000022,0x00050085,0x00000008, - 0x00000024,0x0000001d,0x00000023,0x00050041,0x00000021,0x00000025,0x00000020,0x00000013, - 0x0004003d,0x00000008,0x00000026,0x00000025,0x00050081,0x00000008,0x00000027,0x00000024, - 0x00000026,0x00050051,0x00000006,0x0000002a,0x00000027,0x00000000,0x00050051,0x00000006, - 0x0000002b,0x00000027,0x00000001,0x00070050,0x00000007,0x0000002c,0x0000002a,0x0000002b, - 0x00000028,0x00000029,0x00050041,0x00000011,0x0000002d,0x0000001b,0x0000000d,0x0003003e, - 0x0000002d,0x0000002c,0x000100fd,0x00010038 -}; - -// glsl_shader.frag, compiled with: -// # glslangValidator -V -x -o glsl_shader.frag.u32 glsl_shader.frag -/* -#version 450 core -layout(location = 0) out vec4 fColor; -layout(set=0, binding=0) uniform sampler2D sTexture; -layout(location = 0) in struct { vec4 Color; vec2 UV; } In; -void main() -{ - fColor = In.Color * texture(sTexture, In.UV.st); -} -*/ -static uint32_t __glsl_shader_frag_spv[] = -{ - 0x07230203,0x00010000,0x00080001,0x0000001e,0x00000000,0x00020011,0x00000001,0x0006000b, - 0x00000001,0x4c534c47,0x6474732e,0x3035342e,0x00000000,0x0003000e,0x00000000,0x00000001, - 0x0007000f,0x00000004,0x00000004,0x6e69616d,0x00000000,0x00000009,0x0000000d,0x00030010, - 0x00000004,0x00000007,0x00030003,0x00000002,0x000001c2,0x00040005,0x00000004,0x6e69616d, - 0x00000000,0x00040005,0x00000009,0x6c6f4366,0x0000726f,0x00030005,0x0000000b,0x00000000, - 0x00050006,0x0000000b,0x00000000,0x6f6c6f43,0x00000072,0x00040006,0x0000000b,0x00000001, - 0x00005655,0x00030005,0x0000000d,0x00006e49,0x00050005,0x00000016,0x78655473,0x65727574, - 0x00000000,0x00040047,0x00000009,0x0000001e,0x00000000,0x00040047,0x0000000d,0x0000001e, - 0x00000000,0x00040047,0x00000016,0x00000022,0x00000000,0x00040047,0x00000016,0x00000021, - 0x00000000,0x00020013,0x00000002,0x00030021,0x00000003,0x00000002,0x00030016,0x00000006, - 0x00000020,0x00040017,0x00000007,0x00000006,0x00000004,0x00040020,0x00000008,0x00000003, - 0x00000007,0x0004003b,0x00000008,0x00000009,0x00000003,0x00040017,0x0000000a,0x00000006, - 0x00000002,0x0004001e,0x0000000b,0x00000007,0x0000000a,0x00040020,0x0000000c,0x00000001, - 0x0000000b,0x0004003b,0x0000000c,0x0000000d,0x00000001,0x00040015,0x0000000e,0x00000020, - 0x00000001,0x0004002b,0x0000000e,0x0000000f,0x00000000,0x00040020,0x00000010,0x00000001, - 0x00000007,0x00090019,0x00000013,0x00000006,0x00000001,0x00000000,0x00000000,0x00000000, - 0x00000001,0x00000000,0x0003001b,0x00000014,0x00000013,0x00040020,0x00000015,0x00000000, - 0x00000014,0x0004003b,0x00000015,0x00000016,0x00000000,0x0004002b,0x0000000e,0x00000018, - 0x00000001,0x00040020,0x00000019,0x00000001,0x0000000a,0x00050036,0x00000002,0x00000004, - 0x00000000,0x00000003,0x000200f8,0x00000005,0x00050041,0x00000010,0x00000011,0x0000000d, - 0x0000000f,0x0004003d,0x00000007,0x00000012,0x00000011,0x0004003d,0x00000014,0x00000017, - 0x00000016,0x00050041,0x00000019,0x0000001a,0x0000000d,0x00000018,0x0004003d,0x0000000a, - 0x0000001b,0x0000001a,0x00050057,0x00000007,0x0000001c,0x00000017,0x0000001b,0x00050085, - 0x00000007,0x0000001d,0x00000012,0x0000001c,0x0003003e,0x00000009,0x0000001d,0x000100fd, - 0x00010038 -}; - -//----------------------------------------------------------------------------- -// FUNCTIONS -//----------------------------------------------------------------------------- - -// Backend data stored in io.BackendRendererUserData to allow support for multiple Dear ImGui contexts -// It is STRONGLY preferred that you use docking branch with multi-viewports (== single Dear ImGui context + multiple windows) instead of multiple Dear ImGui contexts. -// FIXME: multi-context support is not tested and probably dysfunctional in this backend. -static ImGui_ImplVulkan_Data* ImGui_ImplVulkan_GetBackendData() -{ - return ImGui::GetCurrentContext() ? (ImGui_ImplVulkan_Data*)ImGui::GetIO().BackendRendererUserData : nullptr; -} - -static uint32_t ImGui_ImplVulkan_MemoryType(VkMemoryPropertyFlags properties, uint32_t type_bits) -{ - ImGui_ImplVulkan_Data* bd = ImGui_ImplVulkan_GetBackendData(); - ImGui_ImplVulkan_InitInfo* v = &bd->VulkanInitInfo; - VkPhysicalDeviceMemoryProperties prop; - vkGetPhysicalDeviceMemoryProperties(v->PhysicalDevice, &prop); - for (uint32_t i = 0; i < prop.memoryTypeCount; i++) - if ((prop.memoryTypes[i].propertyFlags & properties) == properties && type_bits & (1 << i)) - return i; - return 0xFFFFFFFF; // Unable to find memoryType -} - -static void check_vk_result(VkResult err) -{ - ImGui_ImplVulkan_Data* bd = ImGui_ImplVulkan_GetBackendData(); - if (!bd) - return; - ImGui_ImplVulkan_InitInfo* v = &bd->VulkanInitInfo; - if (v->CheckVkResultFn) - v->CheckVkResultFn(err); -} - -static void CreateOrResizeBuffer(VkBuffer& buffer, VkDeviceMemory& buffer_memory, VkDeviceSize& p_buffer_size, size_t new_size, VkBufferUsageFlagBits usage) -{ - ImGui_ImplVulkan_Data* bd = ImGui_ImplVulkan_GetBackendData(); - ImGui_ImplVulkan_InitInfo* v = &bd->VulkanInitInfo; - VkResult err; - if (buffer != VK_NULL_HANDLE) - vkDestroyBuffer(v->Device, buffer, v->Allocator); - if (buffer_memory != VK_NULL_HANDLE) - vkFreeMemory(v->Device, buffer_memory, v->Allocator); - - VkDeviceSize vertex_buffer_size_aligned = ((new_size - 1) / bd->BufferMemoryAlignment + 1) * bd->BufferMemoryAlignment; - VkBufferCreateInfo buffer_info = {}; - buffer_info.sType = VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO; - buffer_info.size = vertex_buffer_size_aligned; - buffer_info.usage = usage; - buffer_info.sharingMode = VK_SHARING_MODE_EXCLUSIVE; - err = vkCreateBuffer(v->Device, &buffer_info, v->Allocator, &buffer); - check_vk_result(err); - - VkMemoryRequirements req; - vkGetBufferMemoryRequirements(v->Device, buffer, &req); - bd->BufferMemoryAlignment = (bd->BufferMemoryAlignment > req.alignment) ? bd->BufferMemoryAlignment : req.alignment; - VkMemoryAllocateInfo alloc_info = {}; - alloc_info.sType = VK_STRUCTURE_TYPE_MEMORY_ALLOCATE_INFO; - alloc_info.allocationSize = req.size; - alloc_info.memoryTypeIndex = ImGui_ImplVulkan_MemoryType(VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT, req.memoryTypeBits); - err = vkAllocateMemory(v->Device, &alloc_info, v->Allocator, &buffer_memory); - check_vk_result(err); - - err = vkBindBufferMemory(v->Device, buffer, buffer_memory, 0); - check_vk_result(err); - p_buffer_size = req.size; -} - -static void ImGui_ImplVulkan_SetupRenderState(ImDrawData* draw_data, VkPipeline pipeline, VkCommandBuffer command_buffer, ImGui_ImplVulkanH_FrameRenderBuffers* rb, int fb_width, int fb_height) -{ - ImGui_ImplVulkan_Data* bd = ImGui_ImplVulkan_GetBackendData(); - - // Bind pipeline: - { - vkCmdBindPipeline(command_buffer, VK_PIPELINE_BIND_POINT_GRAPHICS, pipeline); - } - - // Bind Vertex And Index Buffer: - if (draw_data->TotalVtxCount > 0) - { - VkBuffer vertex_buffers[1] = { rb->VertexBuffer }; - VkDeviceSize vertex_offset[1] = { 0 }; - vkCmdBindVertexBuffers(command_buffer, 0, 1, vertex_buffers, vertex_offset); - vkCmdBindIndexBuffer(command_buffer, rb->IndexBuffer, 0, sizeof(ImDrawIdx) == 2 ? VK_INDEX_TYPE_UINT16 : VK_INDEX_TYPE_UINT32); - } - - // Setup viewport: - { - VkViewport viewport; - viewport.x = 0; - viewport.y = 0; - viewport.width = (float)fb_width; - viewport.height = (float)fb_height; - viewport.minDepth = 0.0f; - viewport.maxDepth = 1.0f; - vkCmdSetViewport(command_buffer, 0, 1, &viewport); - } - - // Setup scale and translation: - // Our visible imgui space lies from draw_data->DisplayPps (top left) to draw_data->DisplayPos+data_data->DisplaySize (bottom right). DisplayPos is (0,0) for single viewport apps. - { - float scale[2]; - scale[0] = 2.0f / draw_data->DisplaySize.x; - scale[1] = 2.0f / draw_data->DisplaySize.y; - float translate[2]; - translate[0] = -1.0f - draw_data->DisplayPos.x * scale[0]; - translate[1] = -1.0f - draw_data->DisplayPos.y * scale[1]; - vkCmdPushConstants(command_buffer, bd->PipelineLayout, VK_SHADER_STAGE_VERTEX_BIT, sizeof(float) * 0, sizeof(float) * 2, scale); - vkCmdPushConstants(command_buffer, bd->PipelineLayout, VK_SHADER_STAGE_VERTEX_BIT, sizeof(float) * 2, sizeof(float) * 2, translate); - } -} - -// Render function -void ImGui_ImplVulkan_RenderDrawData(ImDrawData* draw_data, VkCommandBuffer command_buffer, VkPipeline pipeline) -{ - // Avoid rendering when minimized, scale coordinates for retina displays (screen coordinates != framebuffer coordinates) - int fb_width = (int)(draw_data->DisplaySize.x * draw_data->FramebufferScale.x); - int fb_height = (int)(draw_data->DisplaySize.y * draw_data->FramebufferScale.y); - if (fb_width <= 0 || fb_height <= 0) - return; - - ImGui_ImplVulkan_Data* bd = ImGui_ImplVulkan_GetBackendData(); - ImGui_ImplVulkan_InitInfo* v = &bd->VulkanInitInfo; - if (pipeline == VK_NULL_HANDLE) - pipeline = bd->Pipeline; - - // Allocate array to store enough vertex/index buffers. Each unique viewport gets its own storage. - ImGui_ImplVulkan_ViewportData* viewport_renderer_data = (ImGui_ImplVulkan_ViewportData*)draw_data->OwnerViewport->RendererUserData; - IM_ASSERT(viewport_renderer_data != nullptr); - ImGui_ImplVulkanH_WindowRenderBuffers* wrb = &viewport_renderer_data->RenderBuffers; - if (wrb->FrameRenderBuffers == nullptr) - { - wrb->Index = 0; - wrb->Count = v->ImageCount; - wrb->FrameRenderBuffers = (ImGui_ImplVulkanH_FrameRenderBuffers*)IM_ALLOC(sizeof(ImGui_ImplVulkanH_FrameRenderBuffers) * wrb->Count); - memset(wrb->FrameRenderBuffers, 0, sizeof(ImGui_ImplVulkanH_FrameRenderBuffers) * wrb->Count); - } - IM_ASSERT(wrb->Count == v->ImageCount); - wrb->Index = (wrb->Index + 1) % wrb->Count; - ImGui_ImplVulkanH_FrameRenderBuffers* rb = &wrb->FrameRenderBuffers[wrb->Index]; - - if (draw_data->TotalVtxCount > 0) - { - // Create or resize the vertex/index buffers - size_t vertex_size = draw_data->TotalVtxCount * sizeof(ImDrawVert); - size_t index_size = draw_data->TotalIdxCount * sizeof(ImDrawIdx); - if (rb->VertexBuffer == VK_NULL_HANDLE || rb->VertexBufferSize < vertex_size) - CreateOrResizeBuffer(rb->VertexBuffer, rb->VertexBufferMemory, rb->VertexBufferSize, vertex_size, VK_BUFFER_USAGE_VERTEX_BUFFER_BIT); - if (rb->IndexBuffer == VK_NULL_HANDLE || rb->IndexBufferSize < index_size) - CreateOrResizeBuffer(rb->IndexBuffer, rb->IndexBufferMemory, rb->IndexBufferSize, index_size, VK_BUFFER_USAGE_INDEX_BUFFER_BIT); - - // Upload vertex/index data into a single contiguous GPU buffer - ImDrawVert* vtx_dst = nullptr; - ImDrawIdx* idx_dst = nullptr; - VkResult err = vkMapMemory(v->Device, rb->VertexBufferMemory, 0, rb->VertexBufferSize, 0, (void**)(&vtx_dst)); - check_vk_result(err); - err = vkMapMemory(v->Device, rb->IndexBufferMemory, 0, rb->IndexBufferSize, 0, (void**)(&idx_dst)); - check_vk_result(err); - for (int n = 0; n < draw_data->CmdListsCount; n++) - { - const ImDrawList* cmd_list = draw_data->CmdLists[n]; - memcpy(vtx_dst, cmd_list->VtxBuffer.Data, cmd_list->VtxBuffer.Size * sizeof(ImDrawVert)); - memcpy(idx_dst, cmd_list->IdxBuffer.Data, cmd_list->IdxBuffer.Size * sizeof(ImDrawIdx)); - vtx_dst += cmd_list->VtxBuffer.Size; - idx_dst += cmd_list->IdxBuffer.Size; - } - VkMappedMemoryRange range[2] = {}; - range[0].sType = VK_STRUCTURE_TYPE_MAPPED_MEMORY_RANGE; - range[0].memory = rb->VertexBufferMemory; - range[0].size = VK_WHOLE_SIZE; - range[1].sType = VK_STRUCTURE_TYPE_MAPPED_MEMORY_RANGE; - range[1].memory = rb->IndexBufferMemory; - range[1].size = VK_WHOLE_SIZE; - err = vkFlushMappedMemoryRanges(v->Device, 2, range); - check_vk_result(err); - vkUnmapMemory(v->Device, rb->VertexBufferMemory); - vkUnmapMemory(v->Device, rb->IndexBufferMemory); - } - - // Setup desired Vulkan state - ImGui_ImplVulkan_SetupRenderState(draw_data, pipeline, command_buffer, rb, fb_width, fb_height); - - // Will project scissor/clipping rectangles into framebuffer space - ImVec2 clip_off = draw_data->DisplayPos; // (0,0) unless using multi-viewports - ImVec2 clip_scale = draw_data->FramebufferScale; // (1,1) unless using retina display which are often (2,2) - - // Render command lists - // (Because we merged all buffers into a single one, we maintain our own offset into them) - int global_vtx_offset = 0; - int global_idx_offset = 0; - for (int n = 0; n < draw_data->CmdListsCount; n++) - { - const ImDrawList* cmd_list = draw_data->CmdLists[n]; - for (int cmd_i = 0; cmd_i < cmd_list->CmdBuffer.Size; cmd_i++) - { - const ImDrawCmd* pcmd = &cmd_list->CmdBuffer[cmd_i]; - if (pcmd->UserCallback != nullptr) - { - // User callback, registered via ImDrawList::AddCallback() - // (ImDrawCallback_ResetRenderState is a special callback value used by the user to request the renderer to reset render state.) - if (pcmd->UserCallback == ImDrawCallback_ResetRenderState) - ImGui_ImplVulkan_SetupRenderState(draw_data, pipeline, command_buffer, rb, fb_width, fb_height); - else - pcmd->UserCallback(cmd_list, pcmd); - } - else - { - // Project scissor/clipping rectangles into framebuffer space - ImVec2 clip_min((pcmd->ClipRect.x - clip_off.x) * clip_scale.x, (pcmd->ClipRect.y - clip_off.y) * clip_scale.y); - ImVec2 clip_max((pcmd->ClipRect.z - clip_off.x) * clip_scale.x, (pcmd->ClipRect.w - clip_off.y) * clip_scale.y); - - // Clamp to viewport as vkCmdSetScissor() won't accept values that are off bounds - if (clip_min.x < 0.0f) { clip_min.x = 0.0f; } - if (clip_min.y < 0.0f) { clip_min.y = 0.0f; } - if (clip_max.x > fb_width) { clip_max.x = (float)fb_width; } - if (clip_max.y > fb_height) { clip_max.y = (float)fb_height; } - if (clip_max.x <= clip_min.x || clip_max.y <= clip_min.y) - continue; - - // Apply scissor/clipping rectangle - VkRect2D scissor; - scissor.offset.x = (int32_t)(clip_min.x); - scissor.offset.y = (int32_t)(clip_min.y); - scissor.extent.width = (uint32_t)(clip_max.x - clip_min.x); - scissor.extent.height = (uint32_t)(clip_max.y - clip_min.y); - vkCmdSetScissor(command_buffer, 0, 1, &scissor); - - // Bind DescriptorSet with font or user texture - VkDescriptorSet desc_set[1] = { (VkDescriptorSet)pcmd->TextureId }; - if (sizeof(ImTextureID) < sizeof(ImU64)) - { - // We don't support texture switches if ImTextureID hasn't been redefined to be 64-bit. Do a flaky check that other textures haven't been used. - IM_ASSERT(pcmd->TextureId == (ImTextureID)bd->FontDescriptorSet); - desc_set[0] = bd->FontDescriptorSet; - } - vkCmdBindDescriptorSets(command_buffer, VK_PIPELINE_BIND_POINT_GRAPHICS, bd->PipelineLayout, 0, 1, desc_set, 0, nullptr); - - // Draw - vkCmdDrawIndexed(command_buffer, pcmd->ElemCount, 1, pcmd->IdxOffset + global_idx_offset, pcmd->VtxOffset + global_vtx_offset, 0); - } - } - global_idx_offset += cmd_list->IdxBuffer.Size; - global_vtx_offset += cmd_list->VtxBuffer.Size; - } - - // Note: at this point both vkCmdSetViewport() and vkCmdSetScissor() have been called. - // Our last values will leak into user/application rendering IF: - // - Your app uses a pipeline with VK_DYNAMIC_STATE_VIEWPORT or VK_DYNAMIC_STATE_SCISSOR dynamic state - // - And you forgot to call vkCmdSetViewport() and vkCmdSetScissor() yourself to explicitly set that state. - // If you use VK_DYNAMIC_STATE_VIEWPORT or VK_DYNAMIC_STATE_SCISSOR you are responsible for setting the values before rendering. - // In theory we should aim to backup/restore those values but I am not sure this is possible. - // We perform a call to vkCmdSetScissor() to set back a full viewport which is likely to fix things for 99% users but technically this is not perfect. (See github #4644) - VkRect2D scissor = { { 0, 0 }, { (uint32_t)fb_width, (uint32_t)fb_height } }; - vkCmdSetScissor(command_buffer, 0, 1, &scissor); -} - -bool ImGui_ImplVulkan_CreateFontsTexture(VkCommandBuffer command_buffer) -{ - ImGuiIO& io = ImGui::GetIO(); - ImGui_ImplVulkan_Data* bd = ImGui_ImplVulkan_GetBackendData(); - ImGui_ImplVulkan_InitInfo* v = &bd->VulkanInitInfo; - - unsigned char* pixels; - int width, height; - io.Fonts->GetTexDataAsRGBA32(&pixels, &width, &height); - size_t upload_size = width * height * 4 * sizeof(char); - - VkResult err; - - // Create the Image: - { - VkImageCreateInfo info = {}; - info.sType = VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO; - info.imageType = VK_IMAGE_TYPE_2D; - info.format = VK_FORMAT_R8G8B8A8_UNORM; - info.extent.width = width; - info.extent.height = height; - info.extent.depth = 1; - info.mipLevels = 1; - info.arrayLayers = 1; - info.samples = VK_SAMPLE_COUNT_1_BIT; - info.tiling = VK_IMAGE_TILING_OPTIMAL; - info.usage = VK_IMAGE_USAGE_SAMPLED_BIT | VK_IMAGE_USAGE_TRANSFER_DST_BIT; - info.sharingMode = VK_SHARING_MODE_EXCLUSIVE; - info.initialLayout = VK_IMAGE_LAYOUT_UNDEFINED; - err = vkCreateImage(v->Device, &info, v->Allocator, &bd->FontImage); - check_vk_result(err); - VkMemoryRequirements req; - vkGetImageMemoryRequirements(v->Device, bd->FontImage, &req); - VkMemoryAllocateInfo alloc_info = {}; - alloc_info.sType = VK_STRUCTURE_TYPE_MEMORY_ALLOCATE_INFO; - alloc_info.allocationSize = req.size; - alloc_info.memoryTypeIndex = ImGui_ImplVulkan_MemoryType(VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT, req.memoryTypeBits); - err = vkAllocateMemory(v->Device, &alloc_info, v->Allocator, &bd->FontMemory); - check_vk_result(err); - err = vkBindImageMemory(v->Device, bd->FontImage, bd->FontMemory, 0); - check_vk_result(err); - } - - // Create the Image View: - { - VkImageViewCreateInfo info = {}; - info.sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO; - info.image = bd->FontImage; - info.viewType = VK_IMAGE_VIEW_TYPE_2D; - info.format = VK_FORMAT_R8G8B8A8_UNORM; - info.subresourceRange.aspectMask = VK_IMAGE_ASPECT_COLOR_BIT; - info.subresourceRange.levelCount = 1; - info.subresourceRange.layerCount = 1; - err = vkCreateImageView(v->Device, &info, v->Allocator, &bd->FontView); - check_vk_result(err); - } - - // Create the Descriptor Set: - bd->FontDescriptorSet = (VkDescriptorSet)ImGui_ImplVulkan_AddTexture(bd->FontSampler, bd->FontView, VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL); - - // Create the Upload Buffer: - { - VkBufferCreateInfo buffer_info = {}; - buffer_info.sType = VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO; - buffer_info.size = upload_size; - buffer_info.usage = VK_BUFFER_USAGE_TRANSFER_SRC_BIT; - buffer_info.sharingMode = VK_SHARING_MODE_EXCLUSIVE; - err = vkCreateBuffer(v->Device, &buffer_info, v->Allocator, &bd->UploadBuffer); - check_vk_result(err); - VkMemoryRequirements req; - vkGetBufferMemoryRequirements(v->Device, bd->UploadBuffer, &req); - bd->BufferMemoryAlignment = (bd->BufferMemoryAlignment > req.alignment) ? bd->BufferMemoryAlignment : req.alignment; - VkMemoryAllocateInfo alloc_info = {}; - alloc_info.sType = VK_STRUCTURE_TYPE_MEMORY_ALLOCATE_INFO; - alloc_info.allocationSize = req.size; - alloc_info.memoryTypeIndex = ImGui_ImplVulkan_MemoryType(VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT, req.memoryTypeBits); - err = vkAllocateMemory(v->Device, &alloc_info, v->Allocator, &bd->UploadBufferMemory); - check_vk_result(err); - err = vkBindBufferMemory(v->Device, bd->UploadBuffer, bd->UploadBufferMemory, 0); - check_vk_result(err); - } - - // Upload to Buffer: - { - char* map = nullptr; - err = vkMapMemory(v->Device, bd->UploadBufferMemory, 0, upload_size, 0, (void**)(&map)); - check_vk_result(err); - memcpy(map, pixels, upload_size); - VkMappedMemoryRange range[1] = {}; - range[0].sType = VK_STRUCTURE_TYPE_MAPPED_MEMORY_RANGE; - range[0].memory = bd->UploadBufferMemory; - range[0].size = upload_size; - err = vkFlushMappedMemoryRanges(v->Device, 1, range); - check_vk_result(err); - vkUnmapMemory(v->Device, bd->UploadBufferMemory); - } - - // Copy to Image: - { - VkImageMemoryBarrier copy_barrier[1] = {}; - copy_barrier[0].sType = VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER; - copy_barrier[0].dstAccessMask = VK_ACCESS_TRANSFER_WRITE_BIT; - copy_barrier[0].oldLayout = VK_IMAGE_LAYOUT_UNDEFINED; - copy_barrier[0].newLayout = VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL; - copy_barrier[0].srcQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED; - copy_barrier[0].dstQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED; - copy_barrier[0].image = bd->FontImage; - copy_barrier[0].subresourceRange.aspectMask = VK_IMAGE_ASPECT_COLOR_BIT; - copy_barrier[0].subresourceRange.levelCount = 1; - copy_barrier[0].subresourceRange.layerCount = 1; - vkCmdPipelineBarrier(command_buffer, VK_PIPELINE_STAGE_HOST_BIT, VK_PIPELINE_STAGE_TRANSFER_BIT, 0, 0, nullptr, 0, nullptr, 1, copy_barrier); - - VkBufferImageCopy region = {}; - region.imageSubresource.aspectMask = VK_IMAGE_ASPECT_COLOR_BIT; - region.imageSubresource.layerCount = 1; - region.imageExtent.width = width; - region.imageExtent.height = height; - region.imageExtent.depth = 1; - vkCmdCopyBufferToImage(command_buffer, bd->UploadBuffer, bd->FontImage, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, 1, ®ion); - - VkImageMemoryBarrier use_barrier[1] = {}; - use_barrier[0].sType = VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER; - use_barrier[0].srcAccessMask = VK_ACCESS_TRANSFER_WRITE_BIT; - use_barrier[0].dstAccessMask = VK_ACCESS_SHADER_READ_BIT; - use_barrier[0].oldLayout = VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL; - use_barrier[0].newLayout = VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL; - use_barrier[0].srcQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED; - use_barrier[0].dstQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED; - use_barrier[0].image = bd->FontImage; - use_barrier[0].subresourceRange.aspectMask = VK_IMAGE_ASPECT_COLOR_BIT; - use_barrier[0].subresourceRange.levelCount = 1; - use_barrier[0].subresourceRange.layerCount = 1; - vkCmdPipelineBarrier(command_buffer, VK_PIPELINE_STAGE_TRANSFER_BIT, VK_PIPELINE_STAGE_FRAGMENT_SHADER_BIT, 0, 0, nullptr, 0, nullptr, 1, use_barrier); - } - - // Store our identifier - io.Fonts->SetTexID((ImTextureID)bd->FontDescriptorSet); - - return true; -} - -static void ImGui_ImplVulkan_CreateShaderModules(VkDevice device, const VkAllocationCallbacks* allocator) -{ - // Create the shader modules - ImGui_ImplVulkan_Data* bd = ImGui_ImplVulkan_GetBackendData(); - if (bd->ShaderModuleVert == VK_NULL_HANDLE) - { - VkShaderModuleCreateInfo vert_info = {}; - vert_info.sType = VK_STRUCTURE_TYPE_SHADER_MODULE_CREATE_INFO; - vert_info.codeSize = sizeof(__glsl_shader_vert_spv); - vert_info.pCode = (uint32_t*)__glsl_shader_vert_spv; - VkResult err = vkCreateShaderModule(device, &vert_info, allocator, &bd->ShaderModuleVert); - check_vk_result(err); - } - if (bd->ShaderModuleFrag == VK_NULL_HANDLE) - { - VkShaderModuleCreateInfo frag_info = {}; - frag_info.sType = VK_STRUCTURE_TYPE_SHADER_MODULE_CREATE_INFO; - frag_info.codeSize = sizeof(__glsl_shader_frag_spv); - frag_info.pCode = (uint32_t*)__glsl_shader_frag_spv; - VkResult err = vkCreateShaderModule(device, &frag_info, allocator, &bd->ShaderModuleFrag); - check_vk_result(err); - } -} - -static void ImGui_ImplVulkan_CreatePipeline(VkDevice device, const VkAllocationCallbacks* allocator, VkPipelineCache pipelineCache, VkRenderPass renderPass, VkSampleCountFlagBits MSAASamples, VkPipeline* pipeline, uint32_t subpass) -{ - ImGui_ImplVulkan_Data* bd = ImGui_ImplVulkan_GetBackendData(); - ImGui_ImplVulkan_CreateShaderModules(device, allocator); - - VkPipelineShaderStageCreateInfo stage[2] = {}; - stage[0].sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO; - stage[0].stage = VK_SHADER_STAGE_VERTEX_BIT; - stage[0].module = bd->ShaderModuleVert; - stage[0].pName = "main"; - stage[1].sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO; - stage[1].stage = VK_SHADER_STAGE_FRAGMENT_BIT; - stage[1].module = bd->ShaderModuleFrag; - stage[1].pName = "main"; - - VkVertexInputBindingDescription binding_desc[1] = {}; - binding_desc[0].stride = sizeof(ImDrawVert); - binding_desc[0].inputRate = VK_VERTEX_INPUT_RATE_VERTEX; - - VkVertexInputAttributeDescription attribute_desc[3] = {}; - attribute_desc[0].location = 0; - attribute_desc[0].binding = binding_desc[0].binding; - attribute_desc[0].format = VK_FORMAT_R32G32_SFLOAT; - attribute_desc[0].offset = IM_OFFSETOF(ImDrawVert, pos); - attribute_desc[1].location = 1; - attribute_desc[1].binding = binding_desc[0].binding; - attribute_desc[1].format = VK_FORMAT_R32G32_SFLOAT; - attribute_desc[1].offset = IM_OFFSETOF(ImDrawVert, uv); - attribute_desc[2].location = 2; - attribute_desc[2].binding = binding_desc[0].binding; - attribute_desc[2].format = VK_FORMAT_R8G8B8A8_UNORM; - attribute_desc[2].offset = IM_OFFSETOF(ImDrawVert, col); - - VkPipelineVertexInputStateCreateInfo vertex_info = {}; - vertex_info.sType = VK_STRUCTURE_TYPE_PIPELINE_VERTEX_INPUT_STATE_CREATE_INFO; - vertex_info.vertexBindingDescriptionCount = 1; - vertex_info.pVertexBindingDescriptions = binding_desc; - vertex_info.vertexAttributeDescriptionCount = 3; - vertex_info.pVertexAttributeDescriptions = attribute_desc; - - VkPipelineInputAssemblyStateCreateInfo ia_info = {}; - ia_info.sType = VK_STRUCTURE_TYPE_PIPELINE_INPUT_ASSEMBLY_STATE_CREATE_INFO; - ia_info.topology = VK_PRIMITIVE_TOPOLOGY_TRIANGLE_LIST; - - VkPipelineViewportStateCreateInfo viewport_info = {}; - viewport_info.sType = VK_STRUCTURE_TYPE_PIPELINE_VIEWPORT_STATE_CREATE_INFO; - viewport_info.viewportCount = 1; - viewport_info.scissorCount = 1; - - VkPipelineRasterizationStateCreateInfo raster_info = {}; - raster_info.sType = VK_STRUCTURE_TYPE_PIPELINE_RASTERIZATION_STATE_CREATE_INFO; - raster_info.polygonMode = VK_POLYGON_MODE_FILL; - raster_info.cullMode = VK_CULL_MODE_NONE; - raster_info.frontFace = VK_FRONT_FACE_COUNTER_CLOCKWISE; - raster_info.lineWidth = 1.0f; - - VkPipelineMultisampleStateCreateInfo ms_info = {}; - ms_info.sType = VK_STRUCTURE_TYPE_PIPELINE_MULTISAMPLE_STATE_CREATE_INFO; - ms_info.rasterizationSamples = (MSAASamples != 0) ? MSAASamples : VK_SAMPLE_COUNT_1_BIT; - - VkPipelineColorBlendAttachmentState color_attachment[1] = {}; - color_attachment[0].blendEnable = VK_TRUE; - color_attachment[0].srcColorBlendFactor = VK_BLEND_FACTOR_SRC_ALPHA; - color_attachment[0].dstColorBlendFactor = VK_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA; - color_attachment[0].colorBlendOp = VK_BLEND_OP_ADD; - color_attachment[0].srcAlphaBlendFactor = VK_BLEND_FACTOR_ONE; - color_attachment[0].dstAlphaBlendFactor = VK_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA; - color_attachment[0].alphaBlendOp = VK_BLEND_OP_ADD; - color_attachment[0].colorWriteMask = VK_COLOR_COMPONENT_R_BIT | VK_COLOR_COMPONENT_G_BIT | VK_COLOR_COMPONENT_B_BIT | VK_COLOR_COMPONENT_A_BIT; - - VkPipelineDepthStencilStateCreateInfo depth_info = {}; - depth_info.sType = VK_STRUCTURE_TYPE_PIPELINE_DEPTH_STENCIL_STATE_CREATE_INFO; - - VkPipelineColorBlendStateCreateInfo blend_info = {}; - blend_info.sType = VK_STRUCTURE_TYPE_PIPELINE_COLOR_BLEND_STATE_CREATE_INFO; - blend_info.attachmentCount = 1; - blend_info.pAttachments = color_attachment; - - VkDynamicState dynamic_states[2] = { VK_DYNAMIC_STATE_VIEWPORT, VK_DYNAMIC_STATE_SCISSOR }; - VkPipelineDynamicStateCreateInfo dynamic_state = {}; - dynamic_state.sType = VK_STRUCTURE_TYPE_PIPELINE_DYNAMIC_STATE_CREATE_INFO; - dynamic_state.dynamicStateCount = (uint32_t)IM_ARRAYSIZE(dynamic_states); - dynamic_state.pDynamicStates = dynamic_states; - - VkGraphicsPipelineCreateInfo info = {}; - info.sType = VK_STRUCTURE_TYPE_GRAPHICS_PIPELINE_CREATE_INFO; - info.flags = bd->PipelineCreateFlags; - info.stageCount = 2; - info.pStages = stage; - info.pVertexInputState = &vertex_info; - info.pInputAssemblyState = &ia_info; - info.pViewportState = &viewport_info; - info.pRasterizationState = &raster_info; - info.pMultisampleState = &ms_info; - info.pDepthStencilState = &depth_info; - info.pColorBlendState = &blend_info; - info.pDynamicState = &dynamic_state; - info.layout = bd->PipelineLayout; - info.renderPass = renderPass; - info.subpass = subpass; - -#ifdef IMGUI_IMPL_VULKAN_HAS_DYNAMIC_RENDERING - VkPipelineRenderingCreateInfoKHR pipelineRenderingCreateInfo = {}; - pipelineRenderingCreateInfo.sType = VK_STRUCTURE_TYPE_PIPELINE_RENDERING_CREATE_INFO_KHR; - pipelineRenderingCreateInfo.colorAttachmentCount = 1; - pipelineRenderingCreateInfo.pColorAttachmentFormats = &bd->VulkanInitInfo.ColorAttachmentFormat; - if (bd->VulkanInitInfo.UseDynamicRendering) - { - info.pNext = &pipelineRenderingCreateInfo; - info.renderPass = VK_NULL_HANDLE; // Just make sure it's actually nullptr. - } -#endif - - VkResult err = vkCreateGraphicsPipelines(device, pipelineCache, 1, &info, allocator, pipeline); - check_vk_result(err); -} - -bool ImGui_ImplVulkan_CreateDeviceObjects() -{ - ImGui_ImplVulkan_Data* bd = ImGui_ImplVulkan_GetBackendData(); - ImGui_ImplVulkan_InitInfo* v = &bd->VulkanInitInfo; - VkResult err; - - if (!bd->FontSampler) - { - // Bilinear sampling is required by default. Set 'io.Fonts->Flags |= ImFontAtlasFlags_NoBakedLines' or 'style.AntiAliasedLinesUseTex = false' to allow point/nearest sampling. - VkSamplerCreateInfo info = {}; - info.sType = VK_STRUCTURE_TYPE_SAMPLER_CREATE_INFO; - info.magFilter = VK_FILTER_LINEAR; - info.minFilter = VK_FILTER_LINEAR; - info.mipmapMode = VK_SAMPLER_MIPMAP_MODE_LINEAR; - info.addressModeU = VK_SAMPLER_ADDRESS_MODE_REPEAT; - info.addressModeV = VK_SAMPLER_ADDRESS_MODE_REPEAT; - info.addressModeW = VK_SAMPLER_ADDRESS_MODE_REPEAT; - info.minLod = -1000; - info.maxLod = 1000; - info.maxAnisotropy = 1.0f; - err = vkCreateSampler(v->Device, &info, v->Allocator, &bd->FontSampler); - check_vk_result(err); - } - - if (!bd->DescriptorSetLayout) - { - VkDescriptorSetLayoutBinding binding[1] = {}; - binding[0].descriptorType = VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER; - binding[0].descriptorCount = 1; - binding[0].stageFlags = VK_SHADER_STAGE_FRAGMENT_BIT; - VkDescriptorSetLayoutCreateInfo info = {}; - info.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_CREATE_INFO; - info.bindingCount = 1; - info.pBindings = binding; - err = vkCreateDescriptorSetLayout(v->Device, &info, v->Allocator, &bd->DescriptorSetLayout); - check_vk_result(err); - } - - if (!bd->PipelineLayout) - { - // Constants: we are using 'vec2 offset' and 'vec2 scale' instead of a full 3d projection matrix - VkPushConstantRange push_constants[1] = {}; - push_constants[0].stageFlags = VK_SHADER_STAGE_VERTEX_BIT; - push_constants[0].offset = sizeof(float) * 0; - push_constants[0].size = sizeof(float) * 4; - VkDescriptorSetLayout set_layout[1] = { bd->DescriptorSetLayout }; - VkPipelineLayoutCreateInfo layout_info = {}; - layout_info.sType = VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO; - layout_info.setLayoutCount = 1; - layout_info.pSetLayouts = set_layout; - layout_info.pushConstantRangeCount = 1; - layout_info.pPushConstantRanges = push_constants; - err = vkCreatePipelineLayout(v->Device, &layout_info, v->Allocator, &bd->PipelineLayout); - check_vk_result(err); - } - - ImGui_ImplVulkan_CreatePipeline(v->Device, v->Allocator, v->PipelineCache, bd->RenderPass, v->MSAASamples, &bd->Pipeline, bd->Subpass); - - return true; -} - -void ImGui_ImplVulkan_DestroyFontUploadObjects() -{ - ImGui_ImplVulkan_Data* bd = ImGui_ImplVulkan_GetBackendData(); - ImGui_ImplVulkan_InitInfo* v = &bd->VulkanInitInfo; - if (bd->UploadBuffer) - { - vkDestroyBuffer(v->Device, bd->UploadBuffer, v->Allocator); - bd->UploadBuffer = VK_NULL_HANDLE; - } - if (bd->UploadBufferMemory) - { - vkFreeMemory(v->Device, bd->UploadBufferMemory, v->Allocator); - bd->UploadBufferMemory = VK_NULL_HANDLE; - } -} - -void ImGui_ImplVulkan_DestroyDeviceObjects() -{ - ImGui_ImplVulkan_Data* bd = ImGui_ImplVulkan_GetBackendData(); - ImGui_ImplVulkan_InitInfo* v = &bd->VulkanInitInfo; - ImGui_ImplVulkanH_DestroyAllViewportsRenderBuffers(v->Device, v->Allocator); - ImGui_ImplVulkan_DestroyFontUploadObjects(); - - if (bd->ShaderModuleVert) { vkDestroyShaderModule(v->Device, bd->ShaderModuleVert, v->Allocator); bd->ShaderModuleVert = VK_NULL_HANDLE; } - if (bd->ShaderModuleFrag) { vkDestroyShaderModule(v->Device, bd->ShaderModuleFrag, v->Allocator); bd->ShaderModuleFrag = VK_NULL_HANDLE; } - if (bd->FontView) { vkDestroyImageView(v->Device, bd->FontView, v->Allocator); bd->FontView = VK_NULL_HANDLE; } - if (bd->FontImage) { vkDestroyImage(v->Device, bd->FontImage, v->Allocator); bd->FontImage = VK_NULL_HANDLE; } - if (bd->FontMemory) { vkFreeMemory(v->Device, bd->FontMemory, v->Allocator); bd->FontMemory = VK_NULL_HANDLE; } - if (bd->FontSampler) { vkDestroySampler(v->Device, bd->FontSampler, v->Allocator); bd->FontSampler = VK_NULL_HANDLE; } - if (bd->DescriptorSetLayout) { vkDestroyDescriptorSetLayout(v->Device, bd->DescriptorSetLayout, v->Allocator); bd->DescriptorSetLayout = VK_NULL_HANDLE; } - if (bd->PipelineLayout) { vkDestroyPipelineLayout(v->Device, bd->PipelineLayout, v->Allocator); bd->PipelineLayout = VK_NULL_HANDLE; } - if (bd->Pipeline) { vkDestroyPipeline(v->Device, bd->Pipeline, v->Allocator); bd->Pipeline = VK_NULL_HANDLE; } -} - -bool ImGui_ImplVulkan_LoadFunctions(PFN_vkVoidFunction(*loader_func)(const char* function_name, void* user_data), void* user_data) -{ - // Load function pointers - // You can use the default Vulkan loader using: - // ImGui_ImplVulkan_LoadFunctions([](const char* function_name, void*) { return vkGetInstanceProcAddr(your_vk_isntance, function_name); }); - // But this would be equivalent to not setting VK_NO_PROTOTYPES. -#ifdef VK_NO_PROTOTYPES -#define IMGUI_VULKAN_FUNC_LOAD(func) \ - func = reinterpret_cast(loader_func(#func, user_data)); \ - if (func == nullptr) \ - return false; - IMGUI_VULKAN_FUNC_MAP(IMGUI_VULKAN_FUNC_LOAD) -#undef IMGUI_VULKAN_FUNC_LOAD - -#ifdef IMGUI_IMPL_VULKAN_HAS_DYNAMIC_RENDERING - // Manually load those two (see #5446) - ImGuiImplVulkanFuncs_vkCmdBeginRenderingKHR = reinterpret_cast(loader_func("vkCmdBeginRenderingKHR", user_data)); - ImGuiImplVulkanFuncs_vkCmdEndRenderingKHR = reinterpret_cast(loader_func("vkCmdEndRenderingKHR", user_data)); -#endif -#else - IM_UNUSED(loader_func); - IM_UNUSED(user_data); -#endif - - g_FunctionsLoaded = true; - return true; -} - -bool ImGui_ImplVulkan_Init(ImGui_ImplVulkan_InitInfo* info, VkRenderPass render_pass) -{ - IM_ASSERT(g_FunctionsLoaded && "Need to call ImGui_ImplVulkan_LoadFunctions() if IMGUI_IMPL_VULKAN_NO_PROTOTYPES or VK_NO_PROTOTYPES are set!"); - - if (info->UseDynamicRendering) - { -#ifdef IMGUI_IMPL_VULKAN_HAS_DYNAMIC_RENDERING -#ifndef VK_NO_PROTOTYPES - ImGuiImplVulkanFuncs_vkCmdBeginRenderingKHR = reinterpret_cast(vkGetInstanceProcAddr(info->Instance, "vkCmdBeginRenderingKHR")); - ImGuiImplVulkanFuncs_vkCmdEndRenderingKHR = reinterpret_cast(vkGetInstanceProcAddr(info->Instance, "vkCmdEndRenderingKHR")); -#endif - IM_ASSERT(ImGuiImplVulkanFuncs_vkCmdBeginRenderingKHR != nullptr); - IM_ASSERT(ImGuiImplVulkanFuncs_vkCmdEndRenderingKHR != nullptr); -#else - IM_ASSERT(0 && "Can't use dynamic rendering when neither VK_VERSION_1_3 or VK_KHR_dynamic_rendering is defined."); -#endif - } - - ImGuiIO& io = ImGui::GetIO(); - IM_ASSERT(io.BackendRendererUserData == nullptr && "Already initialized a renderer backend!"); - - // Setup backend capabilities flags - ImGui_ImplVulkan_Data* bd = IM_NEW(ImGui_ImplVulkan_Data)(); - io.BackendRendererUserData = (void*)bd; - io.BackendRendererName = "imgui_impl_vulkan"; - io.BackendFlags |= ImGuiBackendFlags_RendererHasVtxOffset; // We can honor the ImDrawCmd::VtxOffset field, allowing for large meshes. - io.BackendFlags |= ImGuiBackendFlags_RendererHasViewports; // We can create multi-viewports on the Renderer side (optional) - - IM_ASSERT(info->Instance != VK_NULL_HANDLE); - IM_ASSERT(info->PhysicalDevice != VK_NULL_HANDLE); - IM_ASSERT(info->Device != VK_NULL_HANDLE); - IM_ASSERT(info->Queue != VK_NULL_HANDLE); - IM_ASSERT(info->DescriptorPool != VK_NULL_HANDLE); - IM_ASSERT(info->MinImageCount >= 2); - IM_ASSERT(info->ImageCount >= info->MinImageCount); - if (info->UseDynamicRendering == false) - IM_ASSERT(render_pass != VK_NULL_HANDLE); - - bd->VulkanInitInfo = *info; - bd->RenderPass = render_pass; - bd->Subpass = info->Subpass; - - ImGui_ImplVulkan_CreateDeviceObjects(); - - // Our render function expect RendererUserData to be storing the window render buffer we need (for the main viewport we won't use ->Window) - ImGuiViewport* main_viewport = ImGui::GetMainViewport(); - main_viewport->RendererUserData = IM_NEW(ImGui_ImplVulkan_ViewportData)(); - - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - ImGui_ImplVulkan_InitPlatformInterface(); - - return true; -} - -void ImGui_ImplVulkan_Shutdown() -{ - ImGui_ImplVulkan_Data* bd = ImGui_ImplVulkan_GetBackendData(); - IM_ASSERT(bd != nullptr && "No renderer backend to shutdown, or already shutdown?"); - ImGuiIO& io = ImGui::GetIO(); - - // First destroy objects in all viewports - ImGui_ImplVulkan_DestroyDeviceObjects(); - - // Manually delete main viewport render data in-case we haven't initialized for viewports - ImGuiViewport* main_viewport = ImGui::GetMainViewport(); - if (ImGui_ImplVulkan_ViewportData* vd = (ImGui_ImplVulkan_ViewportData*)main_viewport->RendererUserData) - IM_DELETE(vd); - main_viewport->RendererUserData = nullptr; - - // Clean up windows - ImGui_ImplVulkan_ShutdownPlatformInterface(); - - io.BackendRendererName = nullptr; - io.BackendRendererUserData = nullptr; - io.BackendFlags &= ~(ImGuiBackendFlags_RendererHasVtxOffset | ImGuiBackendFlags_RendererHasViewports); - IM_DELETE(bd); -} - -void ImGui_ImplVulkan_NewFrame() -{ - ImGui_ImplVulkan_Data* bd = ImGui_ImplVulkan_GetBackendData(); - IM_ASSERT(bd != nullptr && "Did you call ImGui_ImplVulkan_Init()?"); - IM_UNUSED(bd); -} - -void ImGui_ImplVulkan_SetMinImageCount(uint32_t min_image_count) -{ - ImGui_ImplVulkan_Data* bd = ImGui_ImplVulkan_GetBackendData(); - IM_ASSERT(min_image_count >= 2); - if (bd->VulkanInitInfo.MinImageCount == min_image_count) - return; - - IM_ASSERT(0); // FIXME-VIEWPORT: Unsupported. Need to recreate all swap chains! - ImGui_ImplVulkan_InitInfo* v = &bd->VulkanInitInfo; - VkResult err = vkDeviceWaitIdle(v->Device); - check_vk_result(err); - ImGui_ImplVulkanH_DestroyAllViewportsRenderBuffers(v->Device, v->Allocator); - - bd->VulkanInitInfo.MinImageCount = min_image_count; -} - -// Register a texture -// FIXME: This is experimental in the sense that we are unsure how to best design/tackle this problem, please post to https://github.com/ocornut/imgui/pull/914 if you have suggestions. -VkDescriptorSet ImGui_ImplVulkan_AddTexture(VkSampler sampler, VkImageView image_view, VkImageLayout image_layout) -{ - ImGui_ImplVulkan_Data* bd = ImGui_ImplVulkan_GetBackendData(); - ImGui_ImplVulkan_InitInfo* v = &bd->VulkanInitInfo; - - // Create Descriptor Set: - VkDescriptorSet descriptor_set; - { - VkDescriptorSetAllocateInfo alloc_info = {}; - alloc_info.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_SET_ALLOCATE_INFO; - alloc_info.descriptorPool = v->DescriptorPool; - alloc_info.descriptorSetCount = 1; - alloc_info.pSetLayouts = &bd->DescriptorSetLayout; - VkResult err = vkAllocateDescriptorSets(v->Device, &alloc_info, &descriptor_set); - check_vk_result(err); - } - - // Update the Descriptor Set: - { - VkDescriptorImageInfo desc_image[1] = {}; - desc_image[0].sampler = sampler; - desc_image[0].imageView = image_view; - desc_image[0].imageLayout = image_layout; - VkWriteDescriptorSet write_desc[1] = {}; - write_desc[0].sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET; - write_desc[0].dstSet = descriptor_set; - write_desc[0].descriptorCount = 1; - write_desc[0].descriptorType = VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER; - write_desc[0].pImageInfo = desc_image; - vkUpdateDescriptorSets(v->Device, 1, write_desc, 0, nullptr); - } - return descriptor_set; -} - -void ImGui_ImplVulkan_RemoveTexture(VkDescriptorSet descriptor_set) -{ - ImGui_ImplVulkan_Data* bd = ImGui_ImplVulkan_GetBackendData(); - ImGui_ImplVulkan_InitInfo* v = &bd->VulkanInitInfo; - vkFreeDescriptorSets(v->Device, v->DescriptorPool, 1, &descriptor_set); -} - -//------------------------------------------------------------------------- -// Internal / Miscellaneous Vulkan Helpers -// (Used by example's main.cpp. Used by multi-viewport features. PROBABLY NOT used by your own app.) -//------------------------------------------------------------------------- -// You probably do NOT need to use or care about those functions. -// Those functions only exist because: -// 1) they facilitate the readability and maintenance of the multiple main.cpp examples files. -// 2) the upcoming multi-viewport feature will need them internally. -// Generally we avoid exposing any kind of superfluous high-level helpers in the backends, -// but it is too much code to duplicate everywhere so we exceptionally expose them. -// -// Your engine/app will likely _already_ have code to setup all that stuff (swap chain, render pass, frame buffers, etc.). -// You may read this code to learn about Vulkan, but it is recommended you use you own custom tailored code to do equivalent work. -// (The ImGui_ImplVulkanH_XXX functions do not interact with any of the state used by the regular ImGui_ImplVulkan_XXX functions) -//------------------------------------------------------------------------- - -VkSurfaceFormatKHR ImGui_ImplVulkanH_SelectSurfaceFormat(VkPhysicalDevice physical_device, VkSurfaceKHR surface, const VkFormat* request_formats, int request_formats_count, VkColorSpaceKHR request_color_space) -{ - IM_ASSERT(g_FunctionsLoaded && "Need to call ImGui_ImplVulkan_LoadFunctions() if IMGUI_IMPL_VULKAN_NO_PROTOTYPES or VK_NO_PROTOTYPES are set!"); - IM_ASSERT(request_formats != nullptr); - IM_ASSERT(request_formats_count > 0); - - // Per Spec Format and View Format are expected to be the same unless VK_IMAGE_CREATE_MUTABLE_BIT was set at image creation - // Assuming that the default behavior is without setting this bit, there is no need for separate Swapchain image and image view format - // Additionally several new color spaces were introduced with Vulkan Spec v1.0.40, - // hence we must make sure that a format with the mostly available color space, VK_COLOR_SPACE_SRGB_NONLINEAR_KHR, is found and used. - uint32_t avail_count; - vkGetPhysicalDeviceSurfaceFormatsKHR(physical_device, surface, &avail_count, nullptr); - ImVector avail_format; - avail_format.resize((int)avail_count); - vkGetPhysicalDeviceSurfaceFormatsKHR(physical_device, surface, &avail_count, avail_format.Data); - - // First check if only one format, VK_FORMAT_UNDEFINED, is available, which would imply that any format is available - if (avail_count == 1) - { - if (avail_format[0].format == VK_FORMAT_UNDEFINED) - { - VkSurfaceFormatKHR ret; - ret.format = request_formats[0]; - ret.colorSpace = request_color_space; - return ret; - } - else - { - // No point in searching another format - return avail_format[0]; - } - } - else - { - // Request several formats, the first found will be used - for (int request_i = 0; request_i < request_formats_count; request_i++) - for (uint32_t avail_i = 0; avail_i < avail_count; avail_i++) - if (avail_format[avail_i].format == request_formats[request_i] && avail_format[avail_i].colorSpace == request_color_space) - return avail_format[avail_i]; - - // If none of the requested image formats could be found, use the first available - return avail_format[0]; - } -} - -VkPresentModeKHR ImGui_ImplVulkanH_SelectPresentMode(VkPhysicalDevice physical_device, VkSurfaceKHR surface, const VkPresentModeKHR* request_modes, int request_modes_count) -{ - IM_ASSERT(g_FunctionsLoaded && "Need to call ImGui_ImplVulkan_LoadFunctions() if IMGUI_IMPL_VULKAN_NO_PROTOTYPES or VK_NO_PROTOTYPES are set!"); - IM_ASSERT(request_modes != nullptr); - IM_ASSERT(request_modes_count > 0); - - // Request a certain mode and confirm that it is available. If not use VK_PRESENT_MODE_FIFO_KHR which is mandatory - uint32_t avail_count = 0; - vkGetPhysicalDeviceSurfacePresentModesKHR(physical_device, surface, &avail_count, nullptr); - ImVector avail_modes; - avail_modes.resize((int)avail_count); - vkGetPhysicalDeviceSurfacePresentModesKHR(physical_device, surface, &avail_count, avail_modes.Data); - //for (uint32_t avail_i = 0; avail_i < avail_count; avail_i++) - // printf("[vulkan] avail_modes[%d] = %d\n", avail_i, avail_modes[avail_i]); - - for (int request_i = 0; request_i < request_modes_count; request_i++) - for (uint32_t avail_i = 0; avail_i < avail_count; avail_i++) - if (request_modes[request_i] == avail_modes[avail_i]) - return request_modes[request_i]; - - return VK_PRESENT_MODE_FIFO_KHR; // Always available -} - -void ImGui_ImplVulkanH_CreateWindowCommandBuffers(VkPhysicalDevice physical_device, VkDevice device, ImGui_ImplVulkanH_Window* wd, uint32_t queue_family, const VkAllocationCallbacks* allocator) -{ - IM_ASSERT(physical_device != VK_NULL_HANDLE && device != VK_NULL_HANDLE); - (void)physical_device; - (void)allocator; - - // Create Command Buffers - VkResult err; - for (uint32_t i = 0; i < wd->ImageCount; i++) - { - ImGui_ImplVulkanH_Frame* fd = &wd->Frames[i]; - ImGui_ImplVulkanH_FrameSemaphores* fsd = &wd->FrameSemaphores[i]; - { - VkCommandPoolCreateInfo info = {}; - info.sType = VK_STRUCTURE_TYPE_COMMAND_POOL_CREATE_INFO; - info.flags = VK_COMMAND_POOL_CREATE_RESET_COMMAND_BUFFER_BIT; - info.queueFamilyIndex = queue_family; - err = vkCreateCommandPool(device, &info, allocator, &fd->CommandPool); - check_vk_result(err); - } - { - VkCommandBufferAllocateInfo info = {}; - info.sType = VK_STRUCTURE_TYPE_COMMAND_BUFFER_ALLOCATE_INFO; - info.commandPool = fd->CommandPool; - info.level = VK_COMMAND_BUFFER_LEVEL_PRIMARY; - info.commandBufferCount = 1; - err = vkAllocateCommandBuffers(device, &info, &fd->CommandBuffer); - check_vk_result(err); - } - { - VkFenceCreateInfo info = {}; - info.sType = VK_STRUCTURE_TYPE_FENCE_CREATE_INFO; - info.flags = VK_FENCE_CREATE_SIGNALED_BIT; - err = vkCreateFence(device, &info, allocator, &fd->Fence); - check_vk_result(err); - } - { - VkSemaphoreCreateInfo info = {}; - info.sType = VK_STRUCTURE_TYPE_SEMAPHORE_CREATE_INFO; - err = vkCreateSemaphore(device, &info, allocator, &fsd->ImageAcquiredSemaphore); - check_vk_result(err); - err = vkCreateSemaphore(device, &info, allocator, &fsd->RenderCompleteSemaphore); - check_vk_result(err); - } - } -} - -int ImGui_ImplVulkanH_GetMinImageCountFromPresentMode(VkPresentModeKHR present_mode) -{ - if (present_mode == VK_PRESENT_MODE_MAILBOX_KHR) - return 3; - if (present_mode == VK_PRESENT_MODE_FIFO_KHR || present_mode == VK_PRESENT_MODE_FIFO_RELAXED_KHR) - return 2; - if (present_mode == VK_PRESENT_MODE_IMMEDIATE_KHR) - return 1; - IM_ASSERT(0); - return 1; -} - -// Also destroy old swap chain and in-flight frames data, if any. -void ImGui_ImplVulkanH_CreateWindowSwapChain(VkPhysicalDevice physical_device, VkDevice device, ImGui_ImplVulkanH_Window* wd, const VkAllocationCallbacks* allocator, int w, int h, uint32_t min_image_count) -{ - VkResult err; - VkSwapchainKHR old_swapchain = wd->Swapchain; - wd->Swapchain = VK_NULL_HANDLE; - err = vkDeviceWaitIdle(device); - check_vk_result(err); - - // We don't use ImGui_ImplVulkanH_DestroyWindow() because we want to preserve the old swapchain to create the new one. - // Destroy old Framebuffer - for (uint32_t i = 0; i < wd->ImageCount; i++) - { - ImGui_ImplVulkanH_DestroyFrame(device, &wd->Frames[i], allocator); - ImGui_ImplVulkanH_DestroyFrameSemaphores(device, &wd->FrameSemaphores[i], allocator); - } - IM_FREE(wd->Frames); - IM_FREE(wd->FrameSemaphores); - wd->Frames = nullptr; - wd->FrameSemaphores = nullptr; - wd->ImageCount = 0; - if (wd->RenderPass) - vkDestroyRenderPass(device, wd->RenderPass, allocator); - if (wd->Pipeline) - vkDestroyPipeline(device, wd->Pipeline, allocator); - - // If min image count was not specified, request different count of images dependent on selected present mode - if (min_image_count == 0) - min_image_count = ImGui_ImplVulkanH_GetMinImageCountFromPresentMode(wd->PresentMode); - - // Create Swapchain - { - VkSwapchainCreateInfoKHR info = {}; - info.sType = VK_STRUCTURE_TYPE_SWAPCHAIN_CREATE_INFO_KHR; - info.surface = wd->Surface; - info.minImageCount = min_image_count; - info.imageFormat = wd->SurfaceFormat.format; - info.imageColorSpace = wd->SurfaceFormat.colorSpace; - info.imageArrayLayers = 1; - info.imageUsage = VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT; - info.imageSharingMode = VK_SHARING_MODE_EXCLUSIVE; // Assume that graphics family == present family - info.preTransform = VK_SURFACE_TRANSFORM_IDENTITY_BIT_KHR; - info.compositeAlpha = VK_COMPOSITE_ALPHA_OPAQUE_BIT_KHR; - info.presentMode = wd->PresentMode; - info.clipped = VK_TRUE; - info.oldSwapchain = old_swapchain; - VkSurfaceCapabilitiesKHR cap; - err = vkGetPhysicalDeviceSurfaceCapabilitiesKHR(physical_device, wd->Surface, &cap); - check_vk_result(err); - if (info.minImageCount < cap.minImageCount) - info.minImageCount = cap.minImageCount; - else if (cap.maxImageCount != 0 && info.minImageCount > cap.maxImageCount) - info.minImageCount = cap.maxImageCount; - - if (cap.currentExtent.width == 0xffffffff) - { - info.imageExtent.width = wd->Width = w; - info.imageExtent.height = wd->Height = h; - } - else - { - info.imageExtent.width = wd->Width = cap.currentExtent.width; - info.imageExtent.height = wd->Height = cap.currentExtent.height; - } - err = vkCreateSwapchainKHR(device, &info, allocator, &wd->Swapchain); - check_vk_result(err); - err = vkGetSwapchainImagesKHR(device, wd->Swapchain, &wd->ImageCount, nullptr); - check_vk_result(err); - VkImage backbuffers[16] = {}; - IM_ASSERT(wd->ImageCount >= min_image_count); - IM_ASSERT(wd->ImageCount < IM_ARRAYSIZE(backbuffers)); - err = vkGetSwapchainImagesKHR(device, wd->Swapchain, &wd->ImageCount, backbuffers); - check_vk_result(err); - - IM_ASSERT(wd->Frames == nullptr); - wd->Frames = (ImGui_ImplVulkanH_Frame*)IM_ALLOC(sizeof(ImGui_ImplVulkanH_Frame) * wd->ImageCount); - wd->FrameSemaphores = (ImGui_ImplVulkanH_FrameSemaphores*)IM_ALLOC(sizeof(ImGui_ImplVulkanH_FrameSemaphores) * wd->ImageCount); - memset(wd->Frames, 0, sizeof(wd->Frames[0]) * wd->ImageCount); - memset(wd->FrameSemaphores, 0, sizeof(wd->FrameSemaphores[0]) * wd->ImageCount); - for (uint32_t i = 0; i < wd->ImageCount; i++) - wd->Frames[i].Backbuffer = backbuffers[i]; - } - if (old_swapchain) - vkDestroySwapchainKHR(device, old_swapchain, allocator); - - // Create the Render Pass - if (wd->UseDynamicRendering == false) - { - VkAttachmentDescription attachment = {}; - attachment.format = wd->SurfaceFormat.format; - attachment.samples = VK_SAMPLE_COUNT_1_BIT; - attachment.loadOp = wd->ClearEnable ? VK_ATTACHMENT_LOAD_OP_CLEAR : VK_ATTACHMENT_LOAD_OP_DONT_CARE; - attachment.storeOp = VK_ATTACHMENT_STORE_OP_STORE; - attachment.stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE; - attachment.stencilStoreOp = VK_ATTACHMENT_STORE_OP_DONT_CARE; - attachment.initialLayout = VK_IMAGE_LAYOUT_UNDEFINED; - attachment.finalLayout = VK_IMAGE_LAYOUT_PRESENT_SRC_KHR; - VkAttachmentReference color_attachment = {}; - color_attachment.attachment = 0; - color_attachment.layout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL; - VkSubpassDescription subpass = {}; - subpass.pipelineBindPoint = VK_PIPELINE_BIND_POINT_GRAPHICS; - subpass.colorAttachmentCount = 1; - subpass.pColorAttachments = &color_attachment; - VkSubpassDependency dependency = {}; - dependency.srcSubpass = VK_SUBPASS_EXTERNAL; - dependency.dstSubpass = 0; - dependency.srcStageMask = VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT; - dependency.dstStageMask = VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT; - dependency.srcAccessMask = 0; - dependency.dstAccessMask = VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT; - VkRenderPassCreateInfo info = {}; - info.sType = VK_STRUCTURE_TYPE_RENDER_PASS_CREATE_INFO; - info.attachmentCount = 1; - info.pAttachments = &attachment; - info.subpassCount = 1; - info.pSubpasses = &subpass; - info.dependencyCount = 1; - info.pDependencies = &dependency; - err = vkCreateRenderPass(device, &info, allocator, &wd->RenderPass); - check_vk_result(err); - - // We do not create a pipeline by default as this is also used by examples' main.cpp, - // but secondary viewport in multi-viewport mode may want to create one with: - //ImGui_ImplVulkan_CreatePipeline(device, allocator, VK_NULL_HANDLE, wd->RenderPass, VK_SAMPLE_COUNT_1_BIT, &wd->Pipeline, bd->Subpass); - } - - // Create The Image Views - { - VkImageViewCreateInfo info = {}; - info.sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO; - info.viewType = VK_IMAGE_VIEW_TYPE_2D; - info.format = wd->SurfaceFormat.format; - info.components.r = VK_COMPONENT_SWIZZLE_R; - info.components.g = VK_COMPONENT_SWIZZLE_G; - info.components.b = VK_COMPONENT_SWIZZLE_B; - info.components.a = VK_COMPONENT_SWIZZLE_A; - VkImageSubresourceRange image_range = { VK_IMAGE_ASPECT_COLOR_BIT, 0, 1, 0, 1 }; - info.subresourceRange = image_range; - for (uint32_t i = 0; i < wd->ImageCount; i++) - { - ImGui_ImplVulkanH_Frame* fd = &wd->Frames[i]; - info.image = fd->Backbuffer; - err = vkCreateImageView(device, &info, allocator, &fd->BackbufferView); - check_vk_result(err); - } - } - - // Create Framebuffer - if (wd->UseDynamicRendering == false) - { - VkImageView attachment[1]; - VkFramebufferCreateInfo info = {}; - info.sType = VK_STRUCTURE_TYPE_FRAMEBUFFER_CREATE_INFO; - info.renderPass = wd->RenderPass; - info.attachmentCount = 1; - info.pAttachments = attachment; - info.width = wd->Width; - info.height = wd->Height; - info.layers = 1; - for (uint32_t i = 0; i < wd->ImageCount; i++) - { - ImGui_ImplVulkanH_Frame* fd = &wd->Frames[i]; - attachment[0] = fd->BackbufferView; - err = vkCreateFramebuffer(device, &info, allocator, &fd->Framebuffer); - check_vk_result(err); - } - } -} - -// Create or resize window -void ImGui_ImplVulkanH_CreateOrResizeWindow(VkInstance instance, VkPhysicalDevice physical_device, VkDevice device, ImGui_ImplVulkanH_Window* wd, uint32_t queue_family, const VkAllocationCallbacks* allocator, int width, int height, uint32_t min_image_count) -{ - IM_ASSERT(g_FunctionsLoaded && "Need to call ImGui_ImplVulkan_LoadFunctions() if IMGUI_IMPL_VULKAN_NO_PROTOTYPES or VK_NO_PROTOTYPES are set!"); - (void)instance; - ImGui_ImplVulkanH_CreateWindowSwapChain(physical_device, device, wd, allocator, width, height, min_image_count); - //ImGui_ImplVulkan_CreatePipeline(device, allocator, VK_NULL_HANDLE, wd->RenderPass, VK_SAMPLE_COUNT_1_BIT, &wd->Pipeline, g_VulkanInitInfo.Subpass); - ImGui_ImplVulkanH_CreateWindowCommandBuffers(physical_device, device, wd, queue_family, allocator); -} - -void ImGui_ImplVulkanH_DestroyWindow(VkInstance instance, VkDevice device, ImGui_ImplVulkanH_Window* wd, const VkAllocationCallbacks* allocator) -{ - vkDeviceWaitIdle(device); // FIXME: We could wait on the Queue if we had the queue in wd-> (otherwise VulkanH functions can't use globals) - //vkQueueWaitIdle(bd->Queue); - - for (uint32_t i = 0; i < wd->ImageCount; i++) - { - ImGui_ImplVulkanH_DestroyFrame(device, &wd->Frames[i], allocator); - ImGui_ImplVulkanH_DestroyFrameSemaphores(device, &wd->FrameSemaphores[i], allocator); - } - IM_FREE(wd->Frames); - IM_FREE(wd->FrameSemaphores); - wd->Frames = nullptr; - wd->FrameSemaphores = nullptr; - vkDestroyPipeline(device, wd->Pipeline, allocator); - vkDestroyRenderPass(device, wd->RenderPass, allocator); - vkDestroySwapchainKHR(device, wd->Swapchain, allocator); - vkDestroySurfaceKHR(instance, wd->Surface, allocator); - - *wd = ImGui_ImplVulkanH_Window(); -} - -void ImGui_ImplVulkanH_DestroyFrame(VkDevice device, ImGui_ImplVulkanH_Frame* fd, const VkAllocationCallbacks* allocator) -{ - vkDestroyFence(device, fd->Fence, allocator); - vkFreeCommandBuffers(device, fd->CommandPool, 1, &fd->CommandBuffer); - vkDestroyCommandPool(device, fd->CommandPool, allocator); - fd->Fence = VK_NULL_HANDLE; - fd->CommandBuffer = VK_NULL_HANDLE; - fd->CommandPool = VK_NULL_HANDLE; - - vkDestroyImageView(device, fd->BackbufferView, allocator); - vkDestroyFramebuffer(device, fd->Framebuffer, allocator); -} - -void ImGui_ImplVulkanH_DestroyFrameSemaphores(VkDevice device, ImGui_ImplVulkanH_FrameSemaphores* fsd, const VkAllocationCallbacks* allocator) -{ - vkDestroySemaphore(device, fsd->ImageAcquiredSemaphore, allocator); - vkDestroySemaphore(device, fsd->RenderCompleteSemaphore, allocator); - fsd->ImageAcquiredSemaphore = fsd->RenderCompleteSemaphore = VK_NULL_HANDLE; -} - -void ImGui_ImplVulkanH_DestroyFrameRenderBuffers(VkDevice device, ImGui_ImplVulkanH_FrameRenderBuffers* buffers, const VkAllocationCallbacks* allocator) -{ - if (buffers->VertexBuffer) { vkDestroyBuffer(device, buffers->VertexBuffer, allocator); buffers->VertexBuffer = VK_NULL_HANDLE; } - if (buffers->VertexBufferMemory) { vkFreeMemory(device, buffers->VertexBufferMemory, allocator); buffers->VertexBufferMemory = VK_NULL_HANDLE; } - if (buffers->IndexBuffer) { vkDestroyBuffer(device, buffers->IndexBuffer, allocator); buffers->IndexBuffer = VK_NULL_HANDLE; } - if (buffers->IndexBufferMemory) { vkFreeMemory(device, buffers->IndexBufferMemory, allocator); buffers->IndexBufferMemory = VK_NULL_HANDLE; } - buffers->VertexBufferSize = 0; - buffers->IndexBufferSize = 0; -} - -void ImGui_ImplVulkanH_DestroyWindowRenderBuffers(VkDevice device, ImGui_ImplVulkanH_WindowRenderBuffers* buffers, const VkAllocationCallbacks* allocator) -{ - for (uint32_t n = 0; n < buffers->Count; n++) - ImGui_ImplVulkanH_DestroyFrameRenderBuffers(device, &buffers->FrameRenderBuffers[n], allocator); - IM_FREE(buffers->FrameRenderBuffers); - buffers->FrameRenderBuffers = nullptr; - buffers->Index = 0; - buffers->Count = 0; -} - -void ImGui_ImplVulkanH_DestroyAllViewportsRenderBuffers(VkDevice device, const VkAllocationCallbacks* allocator) -{ - ImGuiPlatformIO& platform_io = ImGui::GetPlatformIO(); - for (int n = 0; n < platform_io.Viewports.Size; n++) - if (ImGui_ImplVulkan_ViewportData* vd = (ImGui_ImplVulkan_ViewportData*)platform_io.Viewports[n]->RendererUserData) - ImGui_ImplVulkanH_DestroyWindowRenderBuffers(device, &vd->RenderBuffers, allocator); -} - -//-------------------------------------------------------------------------------------------------------- -// MULTI-VIEWPORT / PLATFORM INTERFACE SUPPORT -// This is an _advanced_ and _optional_ feature, allowing the backend to create and handle multiple viewports simultaneously. -// If you are new to dear imgui or creating a new binding for dear imgui, it is recommended that you completely ignore this section first.. -//-------------------------------------------------------------------------------------------------------- - -static void ImGui_ImplVulkan_CreateWindow(ImGuiViewport* viewport) -{ - ImGui_ImplVulkan_Data* bd = ImGui_ImplVulkan_GetBackendData(); - ImGui_ImplVulkan_ViewportData* vd = IM_NEW(ImGui_ImplVulkan_ViewportData)(); - viewport->RendererUserData = vd; - ImGui_ImplVulkanH_Window* wd = &vd->Window; - ImGui_ImplVulkan_InitInfo* v = &bd->VulkanInitInfo; - - // Create surface - ImGuiPlatformIO& platform_io = ImGui::GetPlatformIO(); - VkResult err = (VkResult)platform_io.Platform_CreateVkSurface(viewport, (ImU64)v->Instance, (const void*)v->Allocator, (ImU64*)&wd->Surface); - check_vk_result(err); - - // Check for WSI support - VkBool32 res; - vkGetPhysicalDeviceSurfaceSupportKHR(v->PhysicalDevice, v->QueueFamily, wd->Surface, &res); - if (res != VK_TRUE) - { - IM_ASSERT(0); // Error: no WSI support on physical device - return; - } - - // Select Surface Format - const VkFormat requestSurfaceImageFormat[] = { VK_FORMAT_B8G8R8A8_UNORM, VK_FORMAT_R8G8B8A8_UNORM, VK_FORMAT_B8G8R8_UNORM, VK_FORMAT_R8G8B8_UNORM }; - const VkColorSpaceKHR requestSurfaceColorSpace = VK_COLORSPACE_SRGB_NONLINEAR_KHR; - wd->SurfaceFormat = ImGui_ImplVulkanH_SelectSurfaceFormat(v->PhysicalDevice, wd->Surface, requestSurfaceImageFormat, (size_t)IM_ARRAYSIZE(requestSurfaceImageFormat), requestSurfaceColorSpace); - - // Select Present Mode - // FIXME-VULKAN: Even thought mailbox seems to get us maximum framerate with a single window, it halves framerate with a second window etc. (w/ Nvidia and SDK 1.82.1) - VkPresentModeKHR present_modes[] = { VK_PRESENT_MODE_MAILBOX_KHR, VK_PRESENT_MODE_IMMEDIATE_KHR, VK_PRESENT_MODE_FIFO_KHR }; - wd->PresentMode = ImGui_ImplVulkanH_SelectPresentMode(v->PhysicalDevice, wd->Surface, &present_modes[0], IM_ARRAYSIZE(present_modes)); - //printf("[vulkan] Secondary window selected PresentMode = %d\n", wd->PresentMode); - - // Create SwapChain, RenderPass, Framebuffer, etc. - wd->ClearEnable = (viewport->Flags & ImGuiViewportFlags_NoRendererClear) ? false : true; - wd->UseDynamicRendering = v->UseDynamicRendering; - ImGui_ImplVulkanH_CreateOrResizeWindow(v->Instance, v->PhysicalDevice, v->Device, wd, v->QueueFamily, v->Allocator, (int)viewport->Size.x, (int)viewport->Size.y, v->MinImageCount); - vd->WindowOwned = true; -} - -static void ImGui_ImplVulkan_DestroyWindow(ImGuiViewport* viewport) -{ - // The main viewport (owned by the application) will always have RendererUserData == 0 since we didn't create the data for it. - ImGui_ImplVulkan_Data* bd = ImGui_ImplVulkan_GetBackendData(); - if (ImGui_ImplVulkan_ViewportData* vd = (ImGui_ImplVulkan_ViewportData*)viewport->RendererUserData) - { - ImGui_ImplVulkan_InitInfo* v = &bd->VulkanInitInfo; - if (vd->WindowOwned) - ImGui_ImplVulkanH_DestroyWindow(v->Instance, v->Device, &vd->Window, v->Allocator); - ImGui_ImplVulkanH_DestroyWindowRenderBuffers(v->Device, &vd->RenderBuffers, v->Allocator); - IM_DELETE(vd); - } - viewport->RendererUserData = nullptr; -} - -static void ImGui_ImplVulkan_SetWindowSize(ImGuiViewport* viewport, ImVec2 size) -{ - ImGui_ImplVulkan_Data* bd = ImGui_ImplVulkan_GetBackendData(); - ImGui_ImplVulkan_ViewportData* vd = (ImGui_ImplVulkan_ViewportData*)viewport->RendererUserData; - if (vd == nullptr) // This is nullptr for the main viewport (which is left to the user/app to handle) - return; - ImGui_ImplVulkan_InitInfo* v = &bd->VulkanInitInfo; - vd->Window.ClearEnable = (viewport->Flags & ImGuiViewportFlags_NoRendererClear) ? false : true; - ImGui_ImplVulkanH_CreateOrResizeWindow(v->Instance, v->PhysicalDevice, v->Device, &vd->Window, v->QueueFamily, v->Allocator, (int)size.x, (int)size.y, v->MinImageCount); -} - -static void ImGui_ImplVulkan_RenderWindow(ImGuiViewport* viewport, void*) -{ - ImGui_ImplVulkan_Data* bd = ImGui_ImplVulkan_GetBackendData(); - ImGui_ImplVulkan_ViewportData* vd = (ImGui_ImplVulkan_ViewportData*)viewport->RendererUserData; - ImGui_ImplVulkanH_Window* wd = &vd->Window; - ImGui_ImplVulkan_InitInfo* v = &bd->VulkanInitInfo; - VkResult err; - - ImGui_ImplVulkanH_Frame* fd = &wd->Frames[wd->FrameIndex]; - ImGui_ImplVulkanH_FrameSemaphores* fsd = &wd->FrameSemaphores[wd->SemaphoreIndex]; - { - { - err = vkAcquireNextImageKHR(v->Device, wd->Swapchain, UINT64_MAX, fsd->ImageAcquiredSemaphore, VK_NULL_HANDLE, &wd->FrameIndex); - check_vk_result(err); - fd = &wd->Frames[wd->FrameIndex]; - } - for (;;) - { - err = vkWaitForFences(v->Device, 1, &fd->Fence, VK_TRUE, 100); - if (err == VK_SUCCESS) break; - if (err == VK_TIMEOUT) continue; - check_vk_result(err); - } - { - err = vkResetCommandPool(v->Device, fd->CommandPool, 0); - check_vk_result(err); - VkCommandBufferBeginInfo info = {}; - info.sType = VK_STRUCTURE_TYPE_COMMAND_BUFFER_BEGIN_INFO; - info.flags |= VK_COMMAND_BUFFER_USAGE_ONE_TIME_SUBMIT_BIT; - err = vkBeginCommandBuffer(fd->CommandBuffer, &info); - check_vk_result(err); - } - { - ImVec4 clear_color = ImVec4(0.0f, 0.0f, 0.0f, 1.0f); - memcpy(&wd->ClearValue.color.float32[0], &clear_color, 4 * sizeof(float)); - } -#ifdef IMGUI_IMPL_VULKAN_HAS_DYNAMIC_RENDERING - if (v->UseDynamicRendering) - { - // Transition swapchain image to a layout suitable for drawing. - VkImageMemoryBarrier barrier = {}; - barrier.sType = VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER; - barrier.dstAccessMask = VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT; - barrier.oldLayout = VK_IMAGE_LAYOUT_UNDEFINED; - barrier.newLayout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL; - barrier.image = fd->Backbuffer; - barrier.subresourceRange.aspectMask = VK_IMAGE_ASPECT_COLOR_BIT; - barrier.subresourceRange.levelCount = 1; - barrier.subresourceRange.layerCount = 1; - vkCmdPipelineBarrier(fd->CommandBuffer, VK_PIPELINE_STAGE_TOP_OF_PIPE_BIT, VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT, 0, 0, nullptr, 0, nullptr, 1, &barrier); - - VkRenderingAttachmentInfo attachmentInfo = {}; - attachmentInfo.sType = VK_STRUCTURE_TYPE_RENDERING_ATTACHMENT_INFO_KHR; - attachmentInfo.imageView = fd->BackbufferView; - attachmentInfo.imageLayout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL; - attachmentInfo.resolveMode = VK_RESOLVE_MODE_NONE; - attachmentInfo.loadOp = VK_ATTACHMENT_LOAD_OP_CLEAR; - attachmentInfo.storeOp = VK_ATTACHMENT_STORE_OP_STORE; - attachmentInfo.clearValue = wd->ClearValue; - - VkRenderingInfo renderingInfo = {}; - renderingInfo.sType = VK_STRUCTURE_TYPE_RENDERING_INFO_KHR; - renderingInfo.renderArea.extent.width = wd->Width; - renderingInfo.renderArea.extent.height = wd->Height; - renderingInfo.layerCount = 1; - renderingInfo.viewMask = 0; - renderingInfo.colorAttachmentCount = 1; - renderingInfo.pColorAttachments = &attachmentInfo; - - ImGuiImplVulkanFuncs_vkCmdBeginRenderingKHR(fd->CommandBuffer, &renderingInfo); - } - else -#endif - { - VkRenderPassBeginInfo info = {}; - info.sType = VK_STRUCTURE_TYPE_RENDER_PASS_BEGIN_INFO; - info.renderPass = wd->RenderPass; - info.framebuffer = fd->Framebuffer; - info.renderArea.extent.width = wd->Width; - info.renderArea.extent.height = wd->Height; - info.clearValueCount = (viewport->Flags & ImGuiViewportFlags_NoRendererClear) ? 0 : 1; - info.pClearValues = (viewport->Flags & ImGuiViewportFlags_NoRendererClear) ? nullptr : &wd->ClearValue; - vkCmdBeginRenderPass(fd->CommandBuffer, &info, VK_SUBPASS_CONTENTS_INLINE); - } - } - - ImGui_ImplVulkan_RenderDrawData(viewport->DrawData, fd->CommandBuffer, wd->Pipeline); - - { -#ifdef IMGUI_IMPL_VULKAN_HAS_DYNAMIC_RENDERING - if (v->UseDynamicRendering) - { - ImGuiImplVulkanFuncs_vkCmdEndRenderingKHR(fd->CommandBuffer); - - // Transition image to a layout suitable for presentation - VkImageMemoryBarrier barrier = {}; - barrier.sType = VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER; - barrier.srcAccessMask = VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT; - barrier.oldLayout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL; - barrier.newLayout = VK_IMAGE_LAYOUT_PRESENT_SRC_KHR; - barrier.image = fd->Backbuffer; - barrier.subresourceRange.aspectMask = VK_IMAGE_ASPECT_COLOR_BIT; - barrier.subresourceRange.levelCount = 1; - barrier.subresourceRange.layerCount = 1; - vkCmdPipelineBarrier(fd->CommandBuffer, VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT, VK_PIPELINE_STAGE_BOTTOM_OF_PIPE_BIT, 0, 0, nullptr, 0, nullptr, 1, &barrier); - } - else -#endif - { - vkCmdEndRenderPass(fd->CommandBuffer); - } - { - VkPipelineStageFlags wait_stage = VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT; - VkSubmitInfo info = {}; - info.sType = VK_STRUCTURE_TYPE_SUBMIT_INFO; - info.waitSemaphoreCount = 1; - info.pWaitSemaphores = &fsd->ImageAcquiredSemaphore; - info.pWaitDstStageMask = &wait_stage; - info.commandBufferCount = 1; - info.pCommandBuffers = &fd->CommandBuffer; - info.signalSemaphoreCount = 1; - info.pSignalSemaphores = &fsd->RenderCompleteSemaphore; - - err = vkEndCommandBuffer(fd->CommandBuffer); - check_vk_result(err); - err = vkResetFences(v->Device, 1, &fd->Fence); - check_vk_result(err); - err = vkQueueSubmit(v->Queue, 1, &info, fd->Fence); - check_vk_result(err); - } - } -} - -static void ImGui_ImplVulkan_SwapBuffers(ImGuiViewport* viewport, void*) -{ - ImGui_ImplVulkan_Data* bd = ImGui_ImplVulkan_GetBackendData(); - ImGui_ImplVulkan_ViewportData* vd = (ImGui_ImplVulkan_ViewportData*)viewport->RendererUserData; - ImGui_ImplVulkanH_Window* wd = &vd->Window; - ImGui_ImplVulkan_InitInfo* v = &bd->VulkanInitInfo; - - VkResult err; - uint32_t present_index = wd->FrameIndex; - - ImGui_ImplVulkanH_FrameSemaphores* fsd = &wd->FrameSemaphores[wd->SemaphoreIndex]; - VkPresentInfoKHR info = {}; - info.sType = VK_STRUCTURE_TYPE_PRESENT_INFO_KHR; - info.waitSemaphoreCount = 1; - info.pWaitSemaphores = &fsd->RenderCompleteSemaphore; - info.swapchainCount = 1; - info.pSwapchains = &wd->Swapchain; - info.pImageIndices = &present_index; - err = vkQueuePresentKHR(v->Queue, &info); - if (err == VK_ERROR_OUT_OF_DATE_KHR || err == VK_SUBOPTIMAL_KHR) - ImGui_ImplVulkanH_CreateOrResizeWindow(v->Instance, v->PhysicalDevice, v->Device, &vd->Window, v->QueueFamily, v->Allocator, (int)viewport->Size.x, (int)viewport->Size.y, v->MinImageCount); - else - check_vk_result(err); - - wd->FrameIndex = (wd->FrameIndex + 1) % wd->ImageCount; // This is for the next vkWaitForFences() - wd->SemaphoreIndex = (wd->SemaphoreIndex + 1) % wd->ImageCount; // Now we can use the next set of semaphores -} - -void ImGui_ImplVulkan_InitPlatformInterface() -{ - ImGuiPlatformIO& platform_io = ImGui::GetPlatformIO(); - if (ImGui::GetIO().ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - IM_ASSERT(platform_io.Platform_CreateVkSurface != nullptr && "Platform needs to setup the CreateVkSurface handler."); - platform_io.Renderer_CreateWindow = ImGui_ImplVulkan_CreateWindow; - platform_io.Renderer_DestroyWindow = ImGui_ImplVulkan_DestroyWindow; - platform_io.Renderer_SetWindowSize = ImGui_ImplVulkan_SetWindowSize; - platform_io.Renderer_RenderWindow = ImGui_ImplVulkan_RenderWindow; - platform_io.Renderer_SwapBuffers = ImGui_ImplVulkan_SwapBuffers; -} - -void ImGui_ImplVulkan_ShutdownPlatformInterface() -{ - ImGui::DestroyPlatformWindows(); -} - -//----------------------------------------------------------------------------- - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_vulkan.h b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_vulkan.h deleted file mode 100644 index 53388c8..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_vulkan.h +++ /dev/null @@ -1,170 +0,0 @@ -// dear imgui: Renderer Backend for Vulkan -// This needs to be used along with a Platform Backend (e.g. GLFW, SDL, Win32, custom..) - -// Implemented features: -// [x] Renderer: User texture binding. Use 'VkDescriptorSet' as ImTextureID. Read the FAQ about ImTextureID! See https://github.com/ocornut/imgui/pull/914 for discussions. -// [X] Renderer: Large meshes support (64k+ vertices) with 16-bit indices. -// [x] Renderer: Multi-viewport / platform windows. With issues (flickering when creating a new viewport). - -// Important: on 32-bit systems, user texture binding is only supported if your imconfig file has '#define ImTextureID ImU64'. -// See imgui_impl_vulkan.cpp file for details. - -// The aim of imgui_impl_vulkan.h/.cpp is to be usable in your engine without any modification. -// IF YOU FEEL YOU NEED TO MAKE ANY CHANGE TO THIS CODE, please share them and your feedback at https://github.com/ocornut/imgui/ - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -// Important note to the reader who wish to integrate imgui_impl_vulkan.cpp/.h in their own engine/app. -// - Common ImGui_ImplVulkan_XXX functions and structures are used to interface with imgui_impl_vulkan.cpp/.h. -// You will use those if you want to use this rendering backend in your engine/app. -// - Helper ImGui_ImplVulkanH_XXX functions and structures are only used by this example (main.cpp) and by -// the backend itself (imgui_impl_vulkan.cpp), but should PROBABLY NOT be used by your own engine/app code. -// Read comments in imgui_impl_vulkan.h. - -#pragma once -#ifndef IMGUI_DISABLE -#include "imgui.h" // IMGUI_IMPL_API - -// [Configuration] in order to use a custom Vulkan function loader: -// (1) You'll need to disable default Vulkan function prototypes. -// We provide a '#define IMGUI_IMPL_VULKAN_NO_PROTOTYPES' convenience configuration flag. -// In order to make sure this is visible from the imgui_impl_vulkan.cpp compilation unit: -// - Add '#define IMGUI_IMPL_VULKAN_NO_PROTOTYPES' in your imconfig.h file -// - Or as a compilation flag in your build system -// - Or uncomment here (not recommended because you'd be modifying imgui sources!) -// - Do not simply add it in a .cpp file! -// (2) Call ImGui_ImplVulkan_LoadFunctions() before ImGui_ImplVulkan_Init() with your custom function. -// If you have no idea what this is, leave it alone! -//#define IMGUI_IMPL_VULKAN_NO_PROTOTYPES - -// Vulkan includes -#if defined(IMGUI_IMPL_VULKAN_NO_PROTOTYPES) && !defined(VK_NO_PROTOTYPES) -#define VK_NO_PROTOTYPES -#endif -#include - -// Initialization data, for ImGui_ImplVulkan_Init() -// [Please zero-clear before use!] -struct ImGui_ImplVulkan_InitInfo -{ - VkInstance Instance; - VkPhysicalDevice PhysicalDevice; - VkDevice Device; - uint32_t QueueFamily; - VkQueue Queue; - VkPipelineCache PipelineCache; - VkDescriptorPool DescriptorPool; - uint32_t Subpass; - uint32_t MinImageCount; // >= 2 - uint32_t ImageCount; // >= MinImageCount - VkSampleCountFlagBits MSAASamples; // >= VK_SAMPLE_COUNT_1_BIT (0 -> default to VK_SAMPLE_COUNT_1_BIT) - - // Dynamic Rendering (Optional) - bool UseDynamicRendering; // Need to explicitly enable VK_KHR_dynamic_rendering extension to use this, even for Vulkan 1.3. - VkFormat ColorAttachmentFormat; // Required for dynamic rendering - - // Allocation, Debugging - const VkAllocationCallbacks* Allocator; - void (*CheckVkResultFn)(VkResult err); -}; - -// Called by user code -IMGUI_IMPL_API bool ImGui_ImplVulkan_Init(ImGui_ImplVulkan_InitInfo* info, VkRenderPass render_pass); -IMGUI_IMPL_API void ImGui_ImplVulkan_Shutdown(); -IMGUI_IMPL_API void ImGui_ImplVulkan_NewFrame(); -IMGUI_IMPL_API void ImGui_ImplVulkan_RenderDrawData(ImDrawData* draw_data, VkCommandBuffer command_buffer, VkPipeline pipeline = VK_NULL_HANDLE); -IMGUI_IMPL_API bool ImGui_ImplVulkan_CreateFontsTexture(VkCommandBuffer command_buffer); -IMGUI_IMPL_API void ImGui_ImplVulkan_DestroyFontUploadObjects(); -IMGUI_IMPL_API void ImGui_ImplVulkan_SetMinImageCount(uint32_t min_image_count); // To override MinImageCount after initialization (e.g. if swap chain is recreated) - -// Register a texture (VkDescriptorSet == ImTextureID) -// FIXME: This is experimental in the sense that we are unsure how to best design/tackle this problem -// Please post to https://github.com/ocornut/imgui/pull/914 if you have suggestions. -IMGUI_IMPL_API VkDescriptorSet ImGui_ImplVulkan_AddTexture(VkSampler sampler, VkImageView image_view, VkImageLayout image_layout); -IMGUI_IMPL_API void ImGui_ImplVulkan_RemoveTexture(VkDescriptorSet descriptor_set); - -// Optional: load Vulkan functions with a custom function loader -// This is only useful with IMGUI_IMPL_VULKAN_NO_PROTOTYPES / VK_NO_PROTOTYPES -IMGUI_IMPL_API bool ImGui_ImplVulkan_LoadFunctions(PFN_vkVoidFunction(*loader_func)(const char* function_name, void* user_data), void* user_data = nullptr); - -//------------------------------------------------------------------------- -// Internal / Miscellaneous Vulkan Helpers -// (Used by example's main.cpp. Used by multi-viewport features. PROBABLY NOT used by your own engine/app.) -//------------------------------------------------------------------------- -// You probably do NOT need to use or care about those functions. -// Those functions only exist because: -// 1) they facilitate the readability and maintenance of the multiple main.cpp examples files. -// 2) the multi-viewport / platform window implementation needs them internally. -// Generally we avoid exposing any kind of superfluous high-level helpers in the bindings, -// but it is too much code to duplicate everywhere so we exceptionally expose them. -// -// Your engine/app will likely _already_ have code to setup all that stuff (swap chain, render pass, frame buffers, etc.). -// You may read this code to learn about Vulkan, but it is recommended you use you own custom tailored code to do equivalent work. -// (The ImGui_ImplVulkanH_XXX functions do not interact with any of the state used by the regular ImGui_ImplVulkan_XXX functions) -//------------------------------------------------------------------------- - -struct ImGui_ImplVulkanH_Frame; -struct ImGui_ImplVulkanH_Window; - -// Helpers -IMGUI_IMPL_API void ImGui_ImplVulkanH_CreateOrResizeWindow(VkInstance instance, VkPhysicalDevice physical_device, VkDevice device, ImGui_ImplVulkanH_Window* wnd, uint32_t queue_family, const VkAllocationCallbacks* allocator, int w, int h, uint32_t min_image_count); -IMGUI_IMPL_API void ImGui_ImplVulkanH_DestroyWindow(VkInstance instance, VkDevice device, ImGui_ImplVulkanH_Window* wnd, const VkAllocationCallbacks* allocator); -IMGUI_IMPL_API VkSurfaceFormatKHR ImGui_ImplVulkanH_SelectSurfaceFormat(VkPhysicalDevice physical_device, VkSurfaceKHR surface, const VkFormat* request_formats, int request_formats_count, VkColorSpaceKHR request_color_space); -IMGUI_IMPL_API VkPresentModeKHR ImGui_ImplVulkanH_SelectPresentMode(VkPhysicalDevice physical_device, VkSurfaceKHR surface, const VkPresentModeKHR* request_modes, int request_modes_count); -IMGUI_IMPL_API int ImGui_ImplVulkanH_GetMinImageCountFromPresentMode(VkPresentModeKHR present_mode); - -// Helper structure to hold the data needed by one rendering frame -// (Used by example's main.cpp. Used by multi-viewport features. Probably NOT used by your own engine/app.) -// [Please zero-clear before use!] -struct ImGui_ImplVulkanH_Frame -{ - VkCommandPool CommandPool; - VkCommandBuffer CommandBuffer; - VkFence Fence; - VkImage Backbuffer; - VkImageView BackbufferView; - VkFramebuffer Framebuffer; -}; - -struct ImGui_ImplVulkanH_FrameSemaphores -{ - VkSemaphore ImageAcquiredSemaphore; - VkSemaphore RenderCompleteSemaphore; -}; - -// Helper structure to hold the data needed by one rendering context into one OS window -// (Used by example's main.cpp. Used by multi-viewport features. Probably NOT used by your own engine/app.) -struct ImGui_ImplVulkanH_Window -{ - int Width; - int Height; - VkSwapchainKHR Swapchain; - VkSurfaceKHR Surface; - VkSurfaceFormatKHR SurfaceFormat; - VkPresentModeKHR PresentMode; - VkRenderPass RenderPass; - VkPipeline Pipeline; // The window pipeline may uses a different VkRenderPass than the one passed in ImGui_ImplVulkan_InitInfo - bool UseDynamicRendering; - bool ClearEnable; - VkClearValue ClearValue; - uint32_t FrameIndex; // Current frame being rendered to (0 <= FrameIndex < FrameInFlightCount) - uint32_t ImageCount; // Number of simultaneous in-flight frames (returned by vkGetSwapchainImagesKHR, usually derived from min_image_count) - uint32_t SemaphoreIndex; // Current set of swapchain wait semaphores we're using (needs to be distinct from per frame data) - ImGui_ImplVulkanH_Frame* Frames; - ImGui_ImplVulkanH_FrameSemaphores* FrameSemaphores; - - ImGui_ImplVulkanH_Window() - { - memset((void*)this, 0, sizeof(*this)); - PresentMode = (VkPresentModeKHR)~0; // Ensure we get an error if user doesn't set this. - ClearEnable = true; - } -}; - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_wgpu.cpp b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_wgpu.cpp deleted file mode 100644 index d6f886b..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_wgpu.cpp +++ /dev/null @@ -1,774 +0,0 @@ -// dear imgui: Renderer for WebGPU -// This needs to be used along with a Platform Binding (e.g. GLFW) -// (Please note that WebGPU is currently experimental, will not run on non-beta browsers, and may break.) - -// Implemented features: -// [X] Renderer: User texture binding. Use 'WGPUTextureView' as ImTextureID. Read the FAQ about ImTextureID! -// [X] Renderer: Large meshes support (64k+ vertices) with 16-bit indices. -// Missing features: -// [ ] Renderer: Multi-viewport support (multiple windows). Not meaningful on the web. - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -// CHANGELOG -// (minor and older changes stripped away, please see git history for details) -// 2023-07-13: Use WGPUShaderModuleWGSLDescriptor's code instead of source. use WGPUMipmapFilterMode_Linear instead of WGPUFilterMode_Linear. (#6602) -// 2023-04-11: Align buffer sizes. Use WGSL shaders instead of precompiled SPIR-V. -// 2023-04-11: Reorganized backend to pull data from a single structure to facilitate usage with multiple-contexts (all g_XXXX access changed to bd->XXXX). -// 2023-01-25: Revert automatic pipeline layout generation (see https://github.com/gpuweb/gpuweb/issues/2470) -// 2022-11-24: Fixed validation error with default depth buffer settings. -// 2022-11-10: Fixed rendering when a depth buffer is enabled. Added 'WGPUTextureFormat depth_format' parameter to ImGui_ImplWGPU_Init(). -// 2022-10-11: Using 'nullptr' instead of 'NULL' as per our switch to C++11. -// 2021-11-29: Passing explicit buffer sizes to wgpuRenderPassEncoderSetVertexBuffer()/wgpuRenderPassEncoderSetIndexBuffer(). -// 2021-08-24: Fixed for latest specs. -// 2021-05-24: Add support for draw_data->FramebufferScale. -// 2021-05-19: Replaced direct access to ImDrawCmd::TextureId with a call to ImDrawCmd::GetTexID(). (will become a requirement) -// 2021-05-16: Update to latest WebGPU specs (compatible with Emscripten 2.0.20 and Chrome Canary 92). -// 2021-02-18: Change blending equation to preserve alpha in output buffer. -// 2021-01-28: Initial version. - -#include "imgui.h" -#ifndef IMGUI_DISABLE -#include "imgui_impl_wgpu.h" -#include -#include - -// Dear ImGui prototypes from imgui_internal.h -extern ImGuiID ImHashData(const void* data_p, size_t data_size, ImU32 seed = 0); -#define MEMALIGN(_SIZE,_ALIGN) (((_SIZE) + ((_ALIGN) - 1)) & ~((_ALIGN) - 1)) // Memory align (copied from IM_ALIGN() macro). - -// WebGPU data -struct RenderResources -{ - WGPUTexture FontTexture = nullptr; // Font texture - WGPUTextureView FontTextureView = nullptr; // Texture view for font texture - WGPUSampler Sampler = nullptr; // Sampler for the font texture - WGPUBuffer Uniforms = nullptr; // Shader uniforms - WGPUBindGroup CommonBindGroup = nullptr; // Resources bind-group to bind the common resources to pipeline - ImGuiStorage ImageBindGroups; // Resources bind-group to bind the font/image resources to pipeline (this is a key->value map) - WGPUBindGroup ImageBindGroup = nullptr; // Default font-resource of Dear ImGui - WGPUBindGroupLayout ImageBindGroupLayout = nullptr; // Cache layout used for the image bind group. Avoids allocating unnecessary JS objects when working with WebASM -}; - -struct FrameResources -{ - WGPUBuffer IndexBuffer; - WGPUBuffer VertexBuffer; - ImDrawIdx* IndexBufferHost; - ImDrawVert* VertexBufferHost; - int IndexBufferSize; - int VertexBufferSize; -}; - -struct Uniforms -{ - float MVP[4][4]; - float Gamma; -}; - -struct ImGui_ImplWGPU_Data -{ - WGPUDevice wgpuDevice = nullptr; - WGPUQueue defaultQueue = nullptr; - WGPUTextureFormat renderTargetFormat = WGPUTextureFormat_Undefined; - WGPUTextureFormat depthStencilFormat = WGPUTextureFormat_Undefined; - WGPURenderPipeline pipelineState = nullptr; - - RenderResources renderResources; - FrameResources* pFrameResources = nullptr; - unsigned int numFramesInFlight = 0; - unsigned int frameIndex = UINT_MAX; -}; - -// Backend data stored in io.BackendRendererUserData to allow support for multiple Dear ImGui contexts -// It is STRONGLY preferred that you use docking branch with multi-viewports (== single Dear ImGui context + multiple windows) instead of multiple Dear ImGui contexts. -static ImGui_ImplWGPU_Data* ImGui_ImplWGPU_GetBackendData() -{ - return ImGui::GetCurrentContext() ? (ImGui_ImplWGPU_Data*)ImGui::GetIO().BackendRendererUserData : nullptr; -} - -//----------------------------------------------------------------------------- -// SHADERS -//----------------------------------------------------------------------------- - -static const char __shader_vert_wgsl[] = R"( -struct VertexInput { - @location(0) position: vec2, - @location(1) uv: vec2, - @location(2) color: vec4, -}; - -struct VertexOutput { - @builtin(position) position: vec4, - @location(0) color: vec4, - @location(1) uv: vec2, -}; - -struct Uniforms { - mvp: mat4x4, - gamma: f32, -}; - -@group(0) @binding(0) var uniforms: Uniforms; - -@vertex -fn main(in: VertexInput) -> VertexOutput { - var out: VertexOutput; - out.position = uniforms.mvp * vec4(in.position, 0.0, 1.0); - out.color = in.color; - out.uv = in.uv; - return out; -} -)"; - -static const char __shader_frag_wgsl[] = R"( -struct VertexOutput { - @builtin(position) position: vec4, - @location(0) color: vec4, - @location(1) uv: vec2, -}; - -struct Uniforms { - mvp: mat4x4, - gamma: f32, -}; - -@group(0) @binding(0) var uniforms: Uniforms; -@group(0) @binding(1) var s: sampler; -@group(1) @binding(0) var t: texture_2d; - -@fragment -fn main(in: VertexOutput) -> @location(0) vec4 { - let color = in.color * textureSample(t, s, in.uv); - let corrected_color = pow(color.rgb, vec3(uniforms.gamma)); - return vec4(corrected_color, color.a); -} -)"; - -static void SafeRelease(ImDrawIdx*& res) -{ - if (res) - delete[] res; - res = nullptr; -} -static void SafeRelease(ImDrawVert*& res) -{ - if (res) - delete[] res; - res = nullptr; -} -static void SafeRelease(WGPUBindGroupLayout& res) -{ - if (res) - wgpuBindGroupLayoutRelease(res); - res = nullptr; -} -static void SafeRelease(WGPUBindGroup& res) -{ - if (res) - wgpuBindGroupRelease(res); - res = nullptr; -} -static void SafeRelease(WGPUBuffer& res) -{ - if (res) - wgpuBufferRelease(res); - res = nullptr; -} -static void SafeRelease(WGPURenderPipeline& res) -{ - if (res) - wgpuRenderPipelineRelease(res); - res = nullptr; -} -static void SafeRelease(WGPUSampler& res) -{ - if (res) - wgpuSamplerRelease(res); - res = nullptr; -} -static void SafeRelease(WGPUShaderModule& res) -{ - if (res) - wgpuShaderModuleRelease(res); - res = nullptr; -} -static void SafeRelease(WGPUTextureView& res) -{ - if (res) - wgpuTextureViewRelease(res); - res = nullptr; -} -static void SafeRelease(WGPUTexture& res) -{ - if (res) - wgpuTextureRelease(res); - res = nullptr; -} - -static void SafeRelease(RenderResources& res) -{ - SafeRelease(res.FontTexture); - SafeRelease(res.FontTextureView); - SafeRelease(res.Sampler); - SafeRelease(res.Uniforms); - SafeRelease(res.CommonBindGroup); - SafeRelease(res.ImageBindGroup); - SafeRelease(res.ImageBindGroupLayout); -}; - -static void SafeRelease(FrameResources& res) -{ - SafeRelease(res.IndexBuffer); - SafeRelease(res.VertexBuffer); - SafeRelease(res.IndexBufferHost); - SafeRelease(res.VertexBufferHost); -} - -static WGPUProgrammableStageDescriptor ImGui_ImplWGPU_CreateShaderModule(const char* wgsl_source) -{ - ImGui_ImplWGPU_Data* bd = ImGui_ImplWGPU_GetBackendData(); - - WGPUShaderModuleWGSLDescriptor wgsl_desc = {}; - wgsl_desc.chain.sType = WGPUSType_ShaderModuleWGSLDescriptor; - wgsl_desc.code = wgsl_source; - - WGPUShaderModuleDescriptor desc = {}; - desc.nextInChain = reinterpret_cast(&wgsl_desc); - - WGPUProgrammableStageDescriptor stage_desc = {}; - stage_desc.module = wgpuDeviceCreateShaderModule(bd->wgpuDevice, &desc); - stage_desc.entryPoint = "main"; - return stage_desc; -} - -static WGPUBindGroup ImGui_ImplWGPU_CreateImageBindGroup(WGPUBindGroupLayout layout, WGPUTextureView texture) -{ - ImGui_ImplWGPU_Data* bd = ImGui_ImplWGPU_GetBackendData(); - WGPUBindGroupEntry image_bg_entries[] = { { nullptr, 0, 0, 0, 0, 0, texture } }; - - WGPUBindGroupDescriptor image_bg_descriptor = {}; - image_bg_descriptor.layout = layout; - image_bg_descriptor.entryCount = sizeof(image_bg_entries) / sizeof(WGPUBindGroupEntry); - image_bg_descriptor.entries = image_bg_entries; - return wgpuDeviceCreateBindGroup(bd->wgpuDevice, &image_bg_descriptor); -} - -static void ImGui_ImplWGPU_SetupRenderState(ImDrawData* draw_data, WGPURenderPassEncoder ctx, FrameResources* fr) -{ - ImGui_ImplWGPU_Data* bd = ImGui_ImplWGPU_GetBackendData(); - - // Setup orthographic projection matrix into our constant buffer - // Our visible imgui space lies from draw_data->DisplayPos (top left) to draw_data->DisplayPos+data_data->DisplaySize (bottom right). - { - float L = draw_data->DisplayPos.x; - float R = draw_data->DisplayPos.x + draw_data->DisplaySize.x; - float T = draw_data->DisplayPos.y; - float B = draw_data->DisplayPos.y + draw_data->DisplaySize.y; - float mvp[4][4] = - { - { 2.0f/(R-L), 0.0f, 0.0f, 0.0f }, - { 0.0f, 2.0f/(T-B), 0.0f, 0.0f }, - { 0.0f, 0.0f, 0.5f, 0.0f }, - { (R+L)/(L-R), (T+B)/(B-T), 0.5f, 1.0f }, - }; - wgpuQueueWriteBuffer(bd->defaultQueue, bd->renderResources.Uniforms, offsetof(Uniforms, MVP), mvp, sizeof(Uniforms::MVP)); - float gamma; - switch (bd->renderTargetFormat) - { - case WGPUTextureFormat_ASTC10x10UnormSrgb: - case WGPUTextureFormat_ASTC10x5UnormSrgb: - case WGPUTextureFormat_ASTC10x6UnormSrgb: - case WGPUTextureFormat_ASTC10x8UnormSrgb: - case WGPUTextureFormat_ASTC12x10UnormSrgb: - case WGPUTextureFormat_ASTC12x12UnormSrgb: - case WGPUTextureFormat_ASTC4x4UnormSrgb: - case WGPUTextureFormat_ASTC5x5UnormSrgb: - case WGPUTextureFormat_ASTC6x5UnormSrgb: - case WGPUTextureFormat_ASTC6x6UnormSrgb: - case WGPUTextureFormat_ASTC8x5UnormSrgb: - case WGPUTextureFormat_ASTC8x6UnormSrgb: - case WGPUTextureFormat_ASTC8x8UnormSrgb: - case WGPUTextureFormat_BC1RGBAUnormSrgb: - case WGPUTextureFormat_BC2RGBAUnormSrgb: - case WGPUTextureFormat_BC3RGBAUnormSrgb: - case WGPUTextureFormat_BC7RGBAUnormSrgb: - case WGPUTextureFormat_BGRA8UnormSrgb: - case WGPUTextureFormat_ETC2RGB8A1UnormSrgb: - case WGPUTextureFormat_ETC2RGB8UnormSrgb: - case WGPUTextureFormat_ETC2RGBA8UnormSrgb: - case WGPUTextureFormat_RGBA8UnormSrgb: - gamma = 2.2f; - break; - default: - gamma = 1.0f; - } - wgpuQueueWriteBuffer(bd->defaultQueue, bd->renderResources.Uniforms, offsetof(Uniforms, Gamma), &gamma, sizeof(Uniforms::Gamma)); - } - - // Setup viewport - wgpuRenderPassEncoderSetViewport(ctx, 0, 0, draw_data->FramebufferScale.x * draw_data->DisplaySize.x, draw_data->FramebufferScale.y * draw_data->DisplaySize.y, 0, 1); - - // Bind shader and vertex buffers - wgpuRenderPassEncoderSetVertexBuffer(ctx, 0, fr->VertexBuffer, 0, fr->VertexBufferSize * sizeof(ImDrawVert)); - wgpuRenderPassEncoderSetIndexBuffer(ctx, fr->IndexBuffer, sizeof(ImDrawIdx) == 2 ? WGPUIndexFormat_Uint16 : WGPUIndexFormat_Uint32, 0, fr->IndexBufferSize * sizeof(ImDrawIdx)); - wgpuRenderPassEncoderSetPipeline(ctx, bd->pipelineState); - wgpuRenderPassEncoderSetBindGroup(ctx, 0, bd->renderResources.CommonBindGroup, 0, nullptr); - - // Setup blend factor - WGPUColor blend_color = { 0.f, 0.f, 0.f, 0.f }; - wgpuRenderPassEncoderSetBlendConstant(ctx, &blend_color); -} - -// Render function -// (this used to be set in io.RenderDrawListsFn and called by ImGui::Render(), but you can now call this directly from your main loop) -void ImGui_ImplWGPU_RenderDrawData(ImDrawData* draw_data, WGPURenderPassEncoder pass_encoder) -{ - // Avoid rendering when minimized - if (draw_data->DisplaySize.x <= 0.0f || draw_data->DisplaySize.y <= 0.0f) - return; - - // FIXME: Assuming that this only gets called once per frame! - // If not, we can't just re-allocate the IB or VB, we'll have to do a proper allocator. - ImGui_ImplWGPU_Data* bd = ImGui_ImplWGPU_GetBackendData(); - bd->frameIndex = bd->frameIndex + 1; - FrameResources* fr = &bd->pFrameResources[bd->frameIndex % bd->numFramesInFlight]; - - // Create and grow vertex/index buffers if needed - if (fr->VertexBuffer == nullptr || fr->VertexBufferSize < draw_data->TotalVtxCount) - { - if (fr->VertexBuffer) - { - wgpuBufferDestroy(fr->VertexBuffer); - wgpuBufferRelease(fr->VertexBuffer); - } - SafeRelease(fr->VertexBufferHost); - fr->VertexBufferSize = draw_data->TotalVtxCount + 5000; - - WGPUBufferDescriptor vb_desc = - { - nullptr, - "Dear ImGui Vertex buffer", - WGPUBufferUsage_CopyDst | WGPUBufferUsage_Vertex, - MEMALIGN(fr->VertexBufferSize * sizeof(ImDrawVert), 4), - false - }; - fr->VertexBuffer = wgpuDeviceCreateBuffer(bd->wgpuDevice, &vb_desc); - if (!fr->VertexBuffer) - return; - - fr->VertexBufferHost = new ImDrawVert[fr->VertexBufferSize]; - } - if (fr->IndexBuffer == nullptr || fr->IndexBufferSize < draw_data->TotalIdxCount) - { - if (fr->IndexBuffer) - { - wgpuBufferDestroy(fr->IndexBuffer); - wgpuBufferRelease(fr->IndexBuffer); - } - SafeRelease(fr->IndexBufferHost); - fr->IndexBufferSize = draw_data->TotalIdxCount + 10000; - - WGPUBufferDescriptor ib_desc = - { - nullptr, - "Dear ImGui Index buffer", - WGPUBufferUsage_CopyDst | WGPUBufferUsage_Index, - MEMALIGN(fr->IndexBufferSize * sizeof(ImDrawIdx), 4), - false - }; - fr->IndexBuffer = wgpuDeviceCreateBuffer(bd->wgpuDevice, &ib_desc); - if (!fr->IndexBuffer) - return; - - fr->IndexBufferHost = new ImDrawIdx[fr->IndexBufferSize]; - } - - // Upload vertex/index data into a single contiguous GPU buffer - ImDrawVert* vtx_dst = (ImDrawVert*)fr->VertexBufferHost; - ImDrawIdx* idx_dst = (ImDrawIdx*)fr->IndexBufferHost; - for (int n = 0; n < draw_data->CmdListsCount; n++) - { - const ImDrawList* cmd_list = draw_data->CmdLists[n]; - memcpy(vtx_dst, cmd_list->VtxBuffer.Data, cmd_list->VtxBuffer.Size * sizeof(ImDrawVert)); - memcpy(idx_dst, cmd_list->IdxBuffer.Data, cmd_list->IdxBuffer.Size * sizeof(ImDrawIdx)); - vtx_dst += cmd_list->VtxBuffer.Size; - idx_dst += cmd_list->IdxBuffer.Size; - } - int64_t vb_write_size = MEMALIGN((char*)vtx_dst - (char*)fr->VertexBufferHost, 4); - int64_t ib_write_size = MEMALIGN((char*)idx_dst - (char*)fr->IndexBufferHost, 4); - wgpuQueueWriteBuffer(bd->defaultQueue, fr->VertexBuffer, 0, fr->VertexBufferHost, vb_write_size); - wgpuQueueWriteBuffer(bd->defaultQueue, fr->IndexBuffer, 0, fr->IndexBufferHost, ib_write_size); - - // Setup desired render state - ImGui_ImplWGPU_SetupRenderState(draw_data, pass_encoder, fr); - - // Render command lists - // (Because we merged all buffers into a single one, we maintain our own offset into them) - int global_vtx_offset = 0; - int global_idx_offset = 0; - ImVec2 clip_scale = draw_data->FramebufferScale; - ImVec2 clip_off = draw_data->DisplayPos; - for (int n = 0; n < draw_data->CmdListsCount; n++) - { - const ImDrawList* cmd_list = draw_data->CmdLists[n]; - for (int cmd_i = 0; cmd_i < cmd_list->CmdBuffer.Size; cmd_i++) - { - const ImDrawCmd* pcmd = &cmd_list->CmdBuffer[cmd_i]; - if (pcmd->UserCallback != nullptr) - { - // User callback, registered via ImDrawList::AddCallback() - // (ImDrawCallback_ResetRenderState is a special callback value used by the user to request the renderer to reset render state.) - if (pcmd->UserCallback == ImDrawCallback_ResetRenderState) - ImGui_ImplWGPU_SetupRenderState(draw_data, pass_encoder, fr); - else - pcmd->UserCallback(cmd_list, pcmd); - } - else - { - // Bind custom texture - ImTextureID tex_id = pcmd->GetTexID(); - ImGuiID tex_id_hash = ImHashData(&tex_id, sizeof(tex_id)); - auto bind_group = bd->renderResources.ImageBindGroups.GetVoidPtr(tex_id_hash); - if (bind_group) - { - wgpuRenderPassEncoderSetBindGroup(pass_encoder, 1, (WGPUBindGroup)bind_group, 0, nullptr); - } - else - { - WGPUBindGroup image_bind_group = ImGui_ImplWGPU_CreateImageBindGroup(bd->renderResources.ImageBindGroupLayout, (WGPUTextureView)tex_id); - bd->renderResources.ImageBindGroups.SetVoidPtr(tex_id_hash, image_bind_group); - wgpuRenderPassEncoderSetBindGroup(pass_encoder, 1, image_bind_group, 0, nullptr); - } - - // Project scissor/clipping rectangles into framebuffer space - ImVec2 clip_min((pcmd->ClipRect.x - clip_off.x) * clip_scale.x, (pcmd->ClipRect.y - clip_off.y) * clip_scale.y); - ImVec2 clip_max((pcmd->ClipRect.z - clip_off.x) * clip_scale.x, (pcmd->ClipRect.w - clip_off.y) * clip_scale.y); - if (clip_max.x <= clip_min.x || clip_max.y <= clip_min.y) - continue; - - // Apply scissor/clipping rectangle, Draw - wgpuRenderPassEncoderSetScissorRect(pass_encoder, (uint32_t)clip_min.x, (uint32_t)clip_min.y, (uint32_t)(clip_max.x - clip_min.x), (uint32_t)(clip_max.y - clip_min.y)); - wgpuRenderPassEncoderDrawIndexed(pass_encoder, pcmd->ElemCount, 1, pcmd->IdxOffset + global_idx_offset, pcmd->VtxOffset + global_vtx_offset, 0); - } - } - global_idx_offset += cmd_list->IdxBuffer.Size; - global_vtx_offset += cmd_list->VtxBuffer.Size; - } -} - -static void ImGui_ImplWGPU_CreateFontsTexture() -{ - // Build texture atlas - ImGui_ImplWGPU_Data* bd = ImGui_ImplWGPU_GetBackendData(); - ImGuiIO& io = ImGui::GetIO(); - unsigned char* pixels; - int width, height, size_pp; - io.Fonts->GetTexDataAsRGBA32(&pixels, &width, &height, &size_pp); - - // Upload texture to graphics system - { - WGPUTextureDescriptor tex_desc = {}; - tex_desc.label = "Dear ImGui Font Texture"; - tex_desc.dimension = WGPUTextureDimension_2D; - tex_desc.size.width = width; - tex_desc.size.height = height; - tex_desc.size.depthOrArrayLayers = 1; - tex_desc.sampleCount = 1; - tex_desc.format = WGPUTextureFormat_RGBA8Unorm; - tex_desc.mipLevelCount = 1; - tex_desc.usage = WGPUTextureUsage_CopyDst | WGPUTextureUsage_TextureBinding; - bd->renderResources.FontTexture = wgpuDeviceCreateTexture(bd->wgpuDevice, &tex_desc); - - WGPUTextureViewDescriptor tex_view_desc = {}; - tex_view_desc.format = WGPUTextureFormat_RGBA8Unorm; - tex_view_desc.dimension = WGPUTextureViewDimension_2D; - tex_view_desc.baseMipLevel = 0; - tex_view_desc.mipLevelCount = 1; - tex_view_desc.baseArrayLayer = 0; - tex_view_desc.arrayLayerCount = 1; - tex_view_desc.aspect = WGPUTextureAspect_All; - bd->renderResources.FontTextureView = wgpuTextureCreateView(bd->renderResources.FontTexture, &tex_view_desc); - } - - // Upload texture data - { - WGPUImageCopyTexture dst_view = {}; - dst_view.texture = bd->renderResources.FontTexture; - dst_view.mipLevel = 0; - dst_view.origin = { 0, 0, 0 }; - dst_view.aspect = WGPUTextureAspect_All; - WGPUTextureDataLayout layout = {}; - layout.offset = 0; - layout.bytesPerRow = width * size_pp; - layout.rowsPerImage = height; - WGPUExtent3D size = { (uint32_t)width, (uint32_t)height, 1 }; - wgpuQueueWriteTexture(bd->defaultQueue, &dst_view, pixels, (uint32_t)(width * size_pp * height), &layout, &size); - } - - // Create the associated sampler - // (Bilinear sampling is required by default. Set 'io.Fonts->Flags |= ImFontAtlasFlags_NoBakedLines' or 'style.AntiAliasedLinesUseTex = false' to allow point/nearest sampling) - { - WGPUSamplerDescriptor sampler_desc = {}; - sampler_desc.minFilter = WGPUFilterMode_Linear; - sampler_desc.magFilter = WGPUFilterMode_Linear; - sampler_desc.mipmapFilter = WGPUMipmapFilterMode_Linear; - sampler_desc.addressModeU = WGPUAddressMode_Repeat; - sampler_desc.addressModeV = WGPUAddressMode_Repeat; - sampler_desc.addressModeW = WGPUAddressMode_Repeat; - sampler_desc.maxAnisotropy = 1; - bd->renderResources.Sampler = wgpuDeviceCreateSampler(bd->wgpuDevice, &sampler_desc); - } - - // Store our identifier - static_assert(sizeof(ImTextureID) >= sizeof(bd->renderResources.FontTexture), "Can't pack descriptor handle into TexID, 32-bit not supported yet."); - io.Fonts->SetTexID((ImTextureID)bd->renderResources.FontTextureView); -} - -static void ImGui_ImplWGPU_CreateUniformBuffer() -{ - ImGui_ImplWGPU_Data* bd = ImGui_ImplWGPU_GetBackendData(); - WGPUBufferDescriptor ub_desc = - { - nullptr, - "Dear ImGui Uniform buffer", - WGPUBufferUsage_CopyDst | WGPUBufferUsage_Uniform, - MEMALIGN(sizeof(Uniforms), 16), - false - }; - bd->renderResources.Uniforms = wgpuDeviceCreateBuffer(bd->wgpuDevice, &ub_desc); -} - -bool ImGui_ImplWGPU_CreateDeviceObjects() -{ - ImGui_ImplWGPU_Data* bd = ImGui_ImplWGPU_GetBackendData(); - if (!bd->wgpuDevice) - return false; - if (bd->pipelineState) - ImGui_ImplWGPU_InvalidateDeviceObjects(); - - // Create render pipeline - WGPURenderPipelineDescriptor graphics_pipeline_desc = {}; - graphics_pipeline_desc.primitive.topology = WGPUPrimitiveTopology_TriangleList; - graphics_pipeline_desc.primitive.stripIndexFormat = WGPUIndexFormat_Undefined; - graphics_pipeline_desc.primitive.frontFace = WGPUFrontFace_CW; - graphics_pipeline_desc.primitive.cullMode = WGPUCullMode_None; - graphics_pipeline_desc.multisample.count = 1; - graphics_pipeline_desc.multisample.mask = UINT_MAX; - graphics_pipeline_desc.multisample.alphaToCoverageEnabled = false; - - // Bind group layouts - WGPUBindGroupLayoutEntry common_bg_layout_entries[2] = {}; - common_bg_layout_entries[0].binding = 0; - common_bg_layout_entries[0].visibility = WGPUShaderStage_Vertex | WGPUShaderStage_Fragment; - common_bg_layout_entries[0].buffer.type = WGPUBufferBindingType_Uniform; - common_bg_layout_entries[1].binding = 1; - common_bg_layout_entries[1].visibility = WGPUShaderStage_Fragment; - common_bg_layout_entries[1].sampler.type = WGPUSamplerBindingType_Filtering; - - WGPUBindGroupLayoutEntry image_bg_layout_entries[1] = {}; - image_bg_layout_entries[0].binding = 0; - image_bg_layout_entries[0].visibility = WGPUShaderStage_Fragment; - image_bg_layout_entries[0].texture.sampleType = WGPUTextureSampleType_Float; - image_bg_layout_entries[0].texture.viewDimension = WGPUTextureViewDimension_2D; - - WGPUBindGroupLayoutDescriptor common_bg_layout_desc = {}; - common_bg_layout_desc.entryCount = 2; - common_bg_layout_desc.entries = common_bg_layout_entries; - - WGPUBindGroupLayoutDescriptor image_bg_layout_desc = {}; - image_bg_layout_desc.entryCount = 1; - image_bg_layout_desc.entries = image_bg_layout_entries; - - WGPUBindGroupLayout bg_layouts[2]; - bg_layouts[0] = wgpuDeviceCreateBindGroupLayout(bd->wgpuDevice, &common_bg_layout_desc); - bg_layouts[1] = wgpuDeviceCreateBindGroupLayout(bd->wgpuDevice, &image_bg_layout_desc); - - WGPUPipelineLayoutDescriptor layout_desc = {}; - layout_desc.bindGroupLayoutCount = 2; - layout_desc.bindGroupLayouts = bg_layouts; - graphics_pipeline_desc.layout = wgpuDeviceCreatePipelineLayout(bd->wgpuDevice, &layout_desc); - - // Create the vertex shader - WGPUProgrammableStageDescriptor vertex_shader_desc = ImGui_ImplWGPU_CreateShaderModule(__shader_vert_wgsl); - graphics_pipeline_desc.vertex.module = vertex_shader_desc.module; - graphics_pipeline_desc.vertex.entryPoint = vertex_shader_desc.entryPoint; - - // Vertex input configuration - WGPUVertexAttribute attribute_desc[] = - { - { WGPUVertexFormat_Float32x2, (uint64_t)IM_OFFSETOF(ImDrawVert, pos), 0 }, - { WGPUVertexFormat_Float32x2, (uint64_t)IM_OFFSETOF(ImDrawVert, uv), 1 }, - { WGPUVertexFormat_Unorm8x4, (uint64_t)IM_OFFSETOF(ImDrawVert, col), 2 }, - }; - - WGPUVertexBufferLayout buffer_layouts[1]; - buffer_layouts[0].arrayStride = sizeof(ImDrawVert); - buffer_layouts[0].stepMode = WGPUVertexStepMode_Vertex; - buffer_layouts[0].attributeCount = 3; - buffer_layouts[0].attributes = attribute_desc; - - graphics_pipeline_desc.vertex.bufferCount = 1; - graphics_pipeline_desc.vertex.buffers = buffer_layouts; - - // Create the pixel shader - WGPUProgrammableStageDescriptor pixel_shader_desc = ImGui_ImplWGPU_CreateShaderModule(__shader_frag_wgsl); - - // Create the blending setup - WGPUBlendState blend_state = {}; - blend_state.alpha.operation = WGPUBlendOperation_Add; - blend_state.alpha.srcFactor = WGPUBlendFactor_One; - blend_state.alpha.dstFactor = WGPUBlendFactor_OneMinusSrcAlpha; - blend_state.color.operation = WGPUBlendOperation_Add; - blend_state.color.srcFactor = WGPUBlendFactor_SrcAlpha; - blend_state.color.dstFactor = WGPUBlendFactor_OneMinusSrcAlpha; - - WGPUColorTargetState color_state = {}; - color_state.format = bd->renderTargetFormat; - color_state.blend = &blend_state; - color_state.writeMask = WGPUColorWriteMask_All; - - WGPUFragmentState fragment_state = {}; - fragment_state.module = pixel_shader_desc.module; - fragment_state.entryPoint = pixel_shader_desc.entryPoint; - fragment_state.targetCount = 1; - fragment_state.targets = &color_state; - - graphics_pipeline_desc.fragment = &fragment_state; - - // Create depth-stencil State - WGPUDepthStencilState depth_stencil_state = {}; - depth_stencil_state.format = bd->depthStencilFormat; - depth_stencil_state.depthWriteEnabled = false; - depth_stencil_state.depthCompare = WGPUCompareFunction_Always; - depth_stencil_state.stencilFront.compare = WGPUCompareFunction_Always; - depth_stencil_state.stencilBack.compare = WGPUCompareFunction_Always; - - // Configure disabled depth-stencil state - graphics_pipeline_desc.depthStencil = (bd->depthStencilFormat == WGPUTextureFormat_Undefined) ? nullptr : &depth_stencil_state; - - bd->pipelineState = wgpuDeviceCreateRenderPipeline(bd->wgpuDevice, &graphics_pipeline_desc); - - ImGui_ImplWGPU_CreateFontsTexture(); - ImGui_ImplWGPU_CreateUniformBuffer(); - - // Create resource bind group - WGPUBindGroupEntry common_bg_entries[] = - { - { nullptr, 0, bd->renderResources.Uniforms, 0, MEMALIGN(sizeof(Uniforms), 16), 0, 0 }, - { nullptr, 1, 0, 0, 0, bd->renderResources.Sampler, 0 }, - }; - - WGPUBindGroupDescriptor common_bg_descriptor = {}; - common_bg_descriptor.layout = bg_layouts[0]; - common_bg_descriptor.entryCount = sizeof(common_bg_entries) / sizeof(WGPUBindGroupEntry); - common_bg_descriptor.entries = common_bg_entries; - bd->renderResources.CommonBindGroup = wgpuDeviceCreateBindGroup(bd->wgpuDevice, &common_bg_descriptor); - - WGPUBindGroup image_bind_group = ImGui_ImplWGPU_CreateImageBindGroup(bg_layouts[1], bd->renderResources.FontTextureView); - bd->renderResources.ImageBindGroup = image_bind_group; - bd->renderResources.ImageBindGroupLayout = bg_layouts[1]; - bd->renderResources.ImageBindGroups.SetVoidPtr(ImHashData(&bd->renderResources.FontTextureView, sizeof(ImTextureID)), image_bind_group); - - SafeRelease(vertex_shader_desc.module); - SafeRelease(pixel_shader_desc.module); - SafeRelease(bg_layouts[0]); - - return true; -} - -void ImGui_ImplWGPU_InvalidateDeviceObjects() -{ - ImGui_ImplWGPU_Data* bd = ImGui_ImplWGPU_GetBackendData(); - if (!bd->wgpuDevice) - return; - - SafeRelease(bd->pipelineState); - SafeRelease(bd->renderResources); - - ImGuiIO& io = ImGui::GetIO(); - io.Fonts->SetTexID(0); // We copied g_pFontTextureView to io.Fonts->TexID so let's clear that as well. - - for (unsigned int i = 0; i < bd->numFramesInFlight; i++) - SafeRelease(bd->pFrameResources[i]); -} - -bool ImGui_ImplWGPU_Init(WGPUDevice device, int num_frames_in_flight, WGPUTextureFormat rt_format, WGPUTextureFormat depth_format) -{ - ImGuiIO& io = ImGui::GetIO(); - IM_ASSERT(io.BackendRendererUserData == nullptr && "Already initialized a renderer backend!"); - - // Setup backend capabilities flags - ImGui_ImplWGPU_Data* bd = IM_NEW(ImGui_ImplWGPU_Data)(); - io.BackendRendererUserData = (void*)bd; - io.BackendRendererName = "imgui_impl_webgpu"; - io.BackendFlags |= ImGuiBackendFlags_RendererHasVtxOffset; // We can honor the ImDrawCmd::VtxOffset field, allowing for large meshes. - - bd->wgpuDevice = device; - bd->defaultQueue = wgpuDeviceGetQueue(bd->wgpuDevice); - bd->renderTargetFormat = rt_format; - bd->depthStencilFormat = depth_format; - bd->numFramesInFlight = num_frames_in_flight; - bd->frameIndex = UINT_MAX; - - bd->renderResources.FontTexture = nullptr; - bd->renderResources.FontTextureView = nullptr; - bd->renderResources.Sampler = nullptr; - bd->renderResources.Uniforms = nullptr; - bd->renderResources.CommonBindGroup = nullptr; - bd->renderResources.ImageBindGroups.Data.reserve(100); - bd->renderResources.ImageBindGroup = nullptr; - bd->renderResources.ImageBindGroupLayout = nullptr; - - // Create buffers with a default size (they will later be grown as needed) - bd->pFrameResources = new FrameResources[num_frames_in_flight]; - for (int i = 0; i < num_frames_in_flight; i++) - { - FrameResources* fr = &bd->pFrameResources[i]; - fr->IndexBuffer = nullptr; - fr->VertexBuffer = nullptr; - fr->IndexBufferHost = nullptr; - fr->VertexBufferHost = nullptr; - fr->IndexBufferSize = 10000; - fr->VertexBufferSize = 5000; - } - - return true; -} - -void ImGui_ImplWGPU_Shutdown() -{ - ImGui_ImplWGPU_Data* bd = ImGui_ImplWGPU_GetBackendData(); - IM_ASSERT(bd != nullptr && "No renderer backend to shutdown, or already shutdown?"); - ImGuiIO& io = ImGui::GetIO(); - - ImGui_ImplWGPU_InvalidateDeviceObjects(); - delete[] bd->pFrameResources; - bd->pFrameResources = nullptr; - wgpuQueueRelease(bd->defaultQueue); - bd->wgpuDevice = nullptr; - bd->numFramesInFlight = 0; - bd->frameIndex = UINT_MAX; - - io.BackendRendererName = nullptr; - io.BackendRendererUserData = nullptr; - io.BackendFlags &= ~ImGuiBackendFlags_RendererHasVtxOffset; - IM_DELETE(bd); -} - -void ImGui_ImplWGPU_NewFrame() -{ - ImGui_ImplWGPU_Data* bd = ImGui_ImplWGPU_GetBackendData(); - if (!bd->pipelineState) - ImGui_ImplWGPU_CreateDeviceObjects(); -} - -//----------------------------------------------------------------------------- - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_wgpu.h b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_wgpu.h deleted file mode 100644 index b83ef0e..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_wgpu.h +++ /dev/null @@ -1,34 +0,0 @@ -// dear imgui: Renderer for WebGPU -// This needs to be used along with a Platform Binding (e.g. GLFW) -// (Please note that WebGPU is currently experimental, will not run on non-beta browsers, and may break.) - -// Implemented features: -// [X] Renderer: User texture binding. Use 'WGPUTextureView' as ImTextureID. Read the FAQ about ImTextureID! -// [X] Renderer: Large meshes support (64k+ vertices) with 16-bit indices. -// Missing features: -// [ ] Renderer: Multi-viewport support (multiple windows). Not meaningful on the web. - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#pragma once -#include "imgui.h" // IMGUI_IMPL_API -#ifndef IMGUI_DISABLE - -#include - -IMGUI_IMPL_API bool ImGui_ImplWGPU_Init(WGPUDevice device, int num_frames_in_flight, WGPUTextureFormat rt_format, WGPUTextureFormat depth_format = WGPUTextureFormat_Undefined); -IMGUI_IMPL_API void ImGui_ImplWGPU_Shutdown(); -IMGUI_IMPL_API void ImGui_ImplWGPU_NewFrame(); -IMGUI_IMPL_API void ImGui_ImplWGPU_RenderDrawData(ImDrawData* draw_data, WGPURenderPassEncoder pass_encoder); - -// Use if you want to reset your rendering device without losing Dear ImGui state. -IMGUI_IMPL_API void ImGui_ImplWGPU_InvalidateDeviceObjects(); -IMGUI_IMPL_API bool ImGui_ImplWGPU_CreateDeviceObjects(); - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_win32.cpp b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_win32.cpp deleted file mode 100644 index 924f2f1..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_win32.cpp +++ /dev/null @@ -1,1327 +0,0 @@ -// dear imgui: Platform Backend for Windows (standard windows API for 32-bits AND 64-bits applications) -// This needs to be used along with a Renderer (e.g. DirectX11, OpenGL3, Vulkan..) - -// Implemented features: -// [X] Platform: Clipboard support (for Win32 this is actually part of core dear imgui) -// [X] Platform: Mouse support. Can discriminate Mouse/TouchScreen/Pen. -// [X] Platform: Keyboard support. Since 1.87 we are using the io.AddKeyEvent() function. Pass ImGuiKey values to all key functions e.g. ImGui::IsKeyPressed(ImGuiKey_Space). [Legacy VK_* values will also be supported unless IMGUI_DISABLE_OBSOLETE_KEYIO is set] -// [X] Platform: Gamepad support. Enabled with 'io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad'. -// [X] Platform: Mouse cursor shape and visibility. Disable with 'io.ConfigFlags |= ImGuiConfigFlags_NoMouseCursorChange'. -// [X] Platform: Multi-viewport support (multiple windows). Enable with 'io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable'. - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#include "imgui.h" -#ifndef IMGUI_DISABLE -#include "imgui_impl_win32.h" -#ifndef WIN32_LEAN_AND_MEAN -#define WIN32_LEAN_AND_MEAN -#endif -#include -#include // GET_X_LPARAM(), GET_Y_LPARAM() -#include -#include - -// Configuration flags to add in your imconfig.h file: -//#define IMGUI_IMPL_WIN32_DISABLE_GAMEPAD // Disable gamepad support. This was meaningful before <1.81 but we now load XInput dynamically so the option is now less relevant. - -// Using XInput for gamepad (will load DLL dynamically) -#ifndef IMGUI_IMPL_WIN32_DISABLE_GAMEPAD -#include -typedef DWORD (WINAPI *PFN_XInputGetCapabilities)(DWORD, DWORD, XINPUT_CAPABILITIES*); -typedef DWORD (WINAPI *PFN_XInputGetState)(DWORD, XINPUT_STATE*); -#endif - -// CHANGELOG -// (minor and older changes stripped away, please see git history for details) -// 2023-XX-XX: Platform: Added support for multiple windows via the ImGuiPlatformIO interface. -// 2023-10-05: Inputs: Added support for extra ImGuiKey values: F13 to F24 function keys, app back/forward keys. -// 2023-09-25: Inputs: Synthesize key-down event on key-up for VK_SNAPSHOT / ImGuiKey_PrintScreen as Windows doesn't emit it (same behavior as GLFW/SDL). -// 2023-09-07: Inputs: Added support for keyboard codepage conversion for when application is compiled in MBCS mode and using a non-Unicode window. -// 2023-04-19: Added ImGui_ImplWin32_InitForOpenGL() to facilitate combining raw Win32/Winapi with OpenGL. (#3218) -// 2023-04-04: Inputs: Added support for io.AddMouseSourceEvent() to discriminate ImGuiMouseSource_Mouse/ImGuiMouseSource_TouchScreen/ImGuiMouseSource_Pen. (#2702) -// 2023-02-15: Inputs: Use WM_NCMOUSEMOVE / WM_NCMOUSELEAVE to track mouse position over non-client area (e.g. OS decorations) when app is not focused. (#6045, #6162) -// 2023-02-02: Inputs: Flipping WM_MOUSEHWHEEL (horizontal mouse-wheel) value to match other backends and offer consistent horizontal scrolling direction. (#4019, #6096, #1463) -// 2022-10-11: Using 'nullptr' instead of 'NULL' as per our switch to C++11. -// 2022-09-28: Inputs: Convert WM_CHAR values with MultiByteToWideChar() when window class was registered as MBCS (not Unicode). -// 2022-09-26: Inputs: Renamed ImGuiKey_ModXXX introduced in 1.87 to ImGuiMod_XXX (old names still supported). -// 2022-01-26: Inputs: replaced short-lived io.AddKeyModsEvent() (added two weeks ago) with io.AddKeyEvent() using ImGuiKey_ModXXX flags. Sorry for the confusion. -// 2021-01-20: Inputs: calling new io.AddKeyAnalogEvent() for gamepad support, instead of writing directly to io.NavInputs[]. -// 2022-01-17: Inputs: calling new io.AddMousePosEvent(), io.AddMouseButtonEvent(), io.AddMouseWheelEvent() API (1.87+). -// 2022-01-17: Inputs: always update key mods next and before a key event (not in NewFrame) to fix input queue with very low framerates. -// 2022-01-12: Inputs: Update mouse inputs using WM_MOUSEMOVE/WM_MOUSELEAVE + fallback to provide it when focused but not hovered/captured. More standard and will allow us to pass it to future input queue API. -// 2022-01-12: Inputs: Maintain our own copy of MouseButtonsDown mask instead of using ImGui::IsAnyMouseDown() which will be obsoleted. -// 2022-01-10: Inputs: calling new io.AddKeyEvent(), io.AddKeyModsEvent() + io.SetKeyEventNativeData() API (1.87+). Support for full ImGuiKey range. -// 2021-12-16: Inputs: Fill VK_LCONTROL/VK_RCONTROL/VK_LSHIFT/VK_RSHIFT/VK_LMENU/VK_RMENU for completeness. -// 2021-08-17: Calling io.AddFocusEvent() on WM_SETFOCUS/WM_KILLFOCUS messages. -// 2021-08-02: Inputs: Fixed keyboard modifiers being reported when host window doesn't have focus. -// 2021-07-29: Inputs: MousePos is correctly reported when the host platform window is hovered but not focused (using TrackMouseEvent() to receive WM_MOUSELEAVE events). -// 2021-06-29: Reorganized backend to pull data from a single structure to facilitate usage with multiple-contexts (all g_XXXX access changed to bd->XXXX). -// 2021-06-08: Fixed ImGui_ImplWin32_EnableDpiAwareness() and ImGui_ImplWin32_GetDpiScaleForMonitor() to handle Windows 8.1/10 features without a manifest (per-monitor DPI, and properly calls SetProcessDpiAwareness() on 8.1). -// 2021-03-23: Inputs: Clearing keyboard down array when losing focus (WM_KILLFOCUS). -// 2021-02-18: Added ImGui_ImplWin32_EnableAlphaCompositing(). Non Visual Studio users will need to link with dwmapi.lib (MinGW/gcc: use -ldwmapi). -// 2021-02-17: Fixed ImGui_ImplWin32_EnableDpiAwareness() attempting to get SetProcessDpiAwareness from shcore.dll on Windows 8 whereas it is only supported on Windows 8.1. -// 2021-01-25: Inputs: Dynamically loading XInput DLL. -// 2020-12-04: Misc: Fixed setting of io.DisplaySize to invalid/uninitialized data when after hwnd has been closed. -// 2020-03-03: Inputs: Calling AddInputCharacterUTF16() to support surrogate pairs leading to codepoint >= 0x10000 (for more complete CJK inputs) -// 2020-02-17: Added ImGui_ImplWin32_EnableDpiAwareness(), ImGui_ImplWin32_GetDpiScaleForHwnd(), ImGui_ImplWin32_GetDpiScaleForMonitor() helper functions. -// 2020-01-14: Inputs: Added support for #define IMGUI_IMPL_WIN32_DISABLE_GAMEPAD/IMGUI_IMPL_WIN32_DISABLE_LINKING_XINPUT. -// 2019-12-05: Inputs: Added support for ImGuiMouseCursor_NotAllowed mouse cursor. -// 2019-05-11: Inputs: Don't filter value from WM_CHAR before calling AddInputCharacter(). -// 2019-01-17: Misc: Using GetForegroundWindow()+IsChild() instead of GetActiveWindow() to be compatible with windows created in a different thread or parent. -// 2019-01-17: Inputs: Added support for mouse buttons 4 and 5 via WM_XBUTTON* messages. -// 2019-01-15: Inputs: Added support for XInput gamepads (if ImGuiConfigFlags_NavEnableGamepad is set by user application). -// 2018-11-30: Misc: Setting up io.BackendPlatformName so it can be displayed in the About Window. -// 2018-06-29: Inputs: Added support for the ImGuiMouseCursor_Hand cursor. -// 2018-06-10: Inputs: Fixed handling of mouse wheel messages to support fine position messages (typically sent by track-pads). -// 2018-06-08: Misc: Extracted imgui_impl_win32.cpp/.h away from the old combined DX9/DX10/DX11/DX12 examples. -// 2018-03-20: Misc: Setup io.BackendFlags ImGuiBackendFlags_HasMouseCursors and ImGuiBackendFlags_HasSetMousePos flags + honor ImGuiConfigFlags_NoMouseCursorChange flag. -// 2018-02-20: Inputs: Added support for mouse cursors (ImGui::GetMouseCursor() value and WM_SETCURSOR message handling). -// 2018-02-06: Inputs: Added mapping for ImGuiKey_Space. -// 2018-02-06: Inputs: Honoring the io.WantSetMousePos by repositioning the mouse (when using navigation and ImGuiConfigFlags_NavMoveMouse is set). -// 2018-02-06: Misc: Removed call to ImGui::Shutdown() which is not available from 1.60 WIP, user needs to call CreateContext/DestroyContext themselves. -// 2018-01-20: Inputs: Added Horizontal Mouse Wheel support. -// 2018-01-08: Inputs: Added mapping for ImGuiKey_Insert. -// 2018-01-05: Inputs: Added WM_LBUTTONDBLCLK double-click handlers for window classes with the CS_DBLCLKS flag. -// 2017-10-23: Inputs: Added WM_SYSKEYDOWN / WM_SYSKEYUP handlers so e.g. the VK_MENU key can be read. -// 2017-10-23: Inputs: Using Win32 ::SetCapture/::GetCapture() to retrieve mouse positions outside the client area when dragging. -// 2016-11-12: Inputs: Only call Win32 ::SetCursor(nullptr) when io.MouseDrawCursor is set. - -// Forward Declarations -static void ImGui_ImplWin32_InitPlatformInterface(bool platformHasOwnDC); -static void ImGui_ImplWin32_ShutdownPlatformInterface(); -static void ImGui_ImplWin32_UpdateMonitors(); - -struct ImGui_ImplWin32_Data -{ - HWND hWnd; - HWND MouseHwnd; - int MouseTrackedArea; // 0: not tracked, 1: client are, 2: non-client area - int MouseButtonsDown; - INT64 Time; - INT64 TicksPerSecond; - ImGuiMouseCursor LastMouseCursor; - UINT32 KeyboardCodePage; - bool WantUpdateMonitors; - -#ifndef IMGUI_IMPL_WIN32_DISABLE_GAMEPAD - bool HasGamepad; - bool WantUpdateHasGamepad; - HMODULE XInputDLL; - PFN_XInputGetCapabilities XInputGetCapabilities; - PFN_XInputGetState XInputGetState; -#endif - - ImGui_ImplWin32_Data() { memset((void*)this, 0, sizeof(*this)); } -}; - -// Backend data stored in io.BackendPlatformUserData to allow support for multiple Dear ImGui contexts -// It is STRONGLY preferred that you use docking branch with multi-viewports (== single Dear ImGui context + multiple windows) instead of multiple Dear ImGui contexts. -// FIXME: multi-context support is not well tested and probably dysfunctional in this backend. -// FIXME: some shared resources (mouse cursor shape, gamepad) are mishandled when using multi-context. -static ImGui_ImplWin32_Data* ImGui_ImplWin32_GetBackendData() -{ - return ImGui::GetCurrentContext() ? (ImGui_ImplWin32_Data*)ImGui::GetIO().BackendPlatformUserData : nullptr; -} - -// Functions -static void ImGui_ImplWin32_UpdateKeyboardCodePage() -{ - // Retrieve keyboard code page, required for handling of non-Unicode Windows. - ImGui_ImplWin32_Data* bd = ImGui_ImplWin32_GetBackendData(); - HKL keyboard_layout = ::GetKeyboardLayout(0); - LCID keyboard_lcid = MAKELCID(HIWORD(keyboard_layout), SORT_DEFAULT); - if (::GetLocaleInfoA(keyboard_lcid, (LOCALE_RETURN_NUMBER | LOCALE_IDEFAULTANSICODEPAGE), (LPSTR)&bd->KeyboardCodePage, sizeof(bd->KeyboardCodePage)) == 0) - bd->KeyboardCodePage = CP_ACP; // Fallback to default ANSI code page when fails. -} - -static bool ImGui_ImplWin32_InitEx(void* hwnd, bool platform_has_own_dc) -{ - ImGuiIO& io = ImGui::GetIO(); - IM_ASSERT(io.BackendPlatformUserData == nullptr && "Already initialized a platform backend!"); - - INT64 perf_frequency, perf_counter; - if (!::QueryPerformanceFrequency((LARGE_INTEGER*)&perf_frequency)) - return false; - if (!::QueryPerformanceCounter((LARGE_INTEGER*)&perf_counter)) - return false; - - // Setup backend capabilities flags - ImGui_ImplWin32_Data* bd = IM_NEW(ImGui_ImplWin32_Data)(); - io.BackendPlatformUserData = (void*)bd; - io.BackendPlatformName = "imgui_impl_win32"; - io.BackendFlags |= ImGuiBackendFlags_HasMouseCursors; // We can honor GetMouseCursor() values (optional) - io.BackendFlags |= ImGuiBackendFlags_HasSetMousePos; // We can honor io.WantSetMousePos requests (optional, rarely used) - io.BackendFlags |= ImGuiBackendFlags_PlatformHasViewports; // We can create multi-viewports on the Platform side (optional) - io.BackendFlags |= ImGuiBackendFlags_HasMouseHoveredViewport; // We can call io.AddMouseViewportEvent() with correct data (optional) - - bd->hWnd = (HWND)hwnd; - bd->WantUpdateMonitors = true; - bd->TicksPerSecond = perf_frequency; - bd->Time = perf_counter; - bd->LastMouseCursor = ImGuiMouseCursor_COUNT; - ImGui_ImplWin32_UpdateKeyboardCodePage(); - - // Our mouse update function expect PlatformHandle to be filled for the main viewport - ImGuiViewport* main_viewport = ImGui::GetMainViewport(); - main_viewport->PlatformHandle = main_viewport->PlatformHandleRaw = (void*)bd->hWnd; - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - ImGui_ImplWin32_InitPlatformInterface(platform_has_own_dc); - - // Dynamically load XInput library -#ifndef IMGUI_IMPL_WIN32_DISABLE_GAMEPAD - bd->WantUpdateHasGamepad = true; - const char* xinput_dll_names[] = - { - "xinput1_4.dll", // Windows 8+ - "xinput1_3.dll", // DirectX SDK - "xinput9_1_0.dll", // Windows Vista, Windows 7 - "xinput1_2.dll", // DirectX SDK - "xinput1_1.dll" // DirectX SDK - }; - for (int n = 0; n < IM_ARRAYSIZE(xinput_dll_names); n++) - if (HMODULE dll = ::LoadLibraryA(xinput_dll_names[n])) - { - bd->XInputDLL = dll; - bd->XInputGetCapabilities = (PFN_XInputGetCapabilities)::GetProcAddress(dll, "XInputGetCapabilities"); - bd->XInputGetState = (PFN_XInputGetState)::GetProcAddress(dll, "XInputGetState"); - break; - } -#endif // IMGUI_IMPL_WIN32_DISABLE_GAMEPAD - - return true; -} - -IMGUI_IMPL_API bool ImGui_ImplWin32_Init(void* hwnd) -{ - return ImGui_ImplWin32_InitEx(hwnd, false); -} - -IMGUI_IMPL_API bool ImGui_ImplWin32_InitForOpenGL(void* hwnd) -{ - // OpenGL needs CS_OWNDC - return ImGui_ImplWin32_InitEx(hwnd, true); -} - -void ImGui_ImplWin32_Shutdown() -{ - ImGui_ImplWin32_Data* bd = ImGui_ImplWin32_GetBackendData(); - IM_ASSERT(bd != nullptr && "No platform backend to shutdown, or already shutdown?"); - ImGuiIO& io = ImGui::GetIO(); - - ImGui_ImplWin32_ShutdownPlatformInterface(); - - // Unload XInput library -#ifndef IMGUI_IMPL_WIN32_DISABLE_GAMEPAD - if (bd->XInputDLL) - ::FreeLibrary(bd->XInputDLL); -#endif // IMGUI_IMPL_WIN32_DISABLE_GAMEPAD - - io.BackendPlatformName = nullptr; - io.BackendPlatformUserData = nullptr; - io.BackendFlags &= ~(ImGuiBackendFlags_HasMouseCursors | ImGuiBackendFlags_HasSetMousePos | ImGuiBackendFlags_HasGamepad | ImGuiBackendFlags_PlatformHasViewports | ImGuiBackendFlags_HasMouseHoveredViewport); - IM_DELETE(bd); -} - -static bool ImGui_ImplWin32_UpdateMouseCursor() -{ - ImGuiIO& io = ImGui::GetIO(); - if (io.ConfigFlags & ImGuiConfigFlags_NoMouseCursorChange) - return false; - - ImGuiMouseCursor imgui_cursor = ImGui::GetMouseCursor(); - if (imgui_cursor == ImGuiMouseCursor_None || io.MouseDrawCursor) - { - // Hide OS mouse cursor if imgui is drawing it or if it wants no cursor - ::SetCursor(nullptr); - } - else - { - // Show OS mouse cursor - LPTSTR win32_cursor = IDC_ARROW; - switch (imgui_cursor) - { - case ImGuiMouseCursor_Arrow: win32_cursor = IDC_ARROW; break; - case ImGuiMouseCursor_TextInput: win32_cursor = IDC_IBEAM; break; - case ImGuiMouseCursor_ResizeAll: win32_cursor = IDC_SIZEALL; break; - case ImGuiMouseCursor_ResizeEW: win32_cursor = IDC_SIZEWE; break; - case ImGuiMouseCursor_ResizeNS: win32_cursor = IDC_SIZENS; break; - case ImGuiMouseCursor_ResizeNESW: win32_cursor = IDC_SIZENESW; break; - case ImGuiMouseCursor_ResizeNWSE: win32_cursor = IDC_SIZENWSE; break; - case ImGuiMouseCursor_Hand: win32_cursor = IDC_HAND; break; - case ImGuiMouseCursor_NotAllowed: win32_cursor = IDC_NO; break; - } - ::SetCursor(::LoadCursor(nullptr, win32_cursor)); - } - return true; -} - -static bool IsVkDown(int vk) -{ - return (::GetKeyState(vk) & 0x8000) != 0; -} - -static void ImGui_ImplWin32_AddKeyEvent(ImGuiKey key, bool down, int native_keycode, int native_scancode = -1) -{ - ImGuiIO& io = ImGui::GetIO(); - io.AddKeyEvent(key, down); - io.SetKeyEventNativeData(key, native_keycode, native_scancode); // To support legacy indexing (<1.87 user code) - IM_UNUSED(native_scancode); -} - -static void ImGui_ImplWin32_ProcessKeyEventsWorkarounds() -{ - // Left & right Shift keys: when both are pressed together, Windows tend to not generate the WM_KEYUP event for the first released one. - if (ImGui::IsKeyDown(ImGuiKey_LeftShift) && !IsVkDown(VK_LSHIFT)) - ImGui_ImplWin32_AddKeyEvent(ImGuiKey_LeftShift, false, VK_LSHIFT); - if (ImGui::IsKeyDown(ImGuiKey_RightShift) && !IsVkDown(VK_RSHIFT)) - ImGui_ImplWin32_AddKeyEvent(ImGuiKey_RightShift, false, VK_RSHIFT); - - // Sometimes WM_KEYUP for Win key is not passed down to the app (e.g. for Win+V on some setups, according to GLFW). - if (ImGui::IsKeyDown(ImGuiKey_LeftSuper) && !IsVkDown(VK_LWIN)) - ImGui_ImplWin32_AddKeyEvent(ImGuiKey_LeftSuper, false, VK_LWIN); - if (ImGui::IsKeyDown(ImGuiKey_RightSuper) && !IsVkDown(VK_RWIN)) - ImGui_ImplWin32_AddKeyEvent(ImGuiKey_RightSuper, false, VK_RWIN); -} - -static void ImGui_ImplWin32_UpdateKeyModifiers() -{ - ImGuiIO& io = ImGui::GetIO(); - io.AddKeyEvent(ImGuiMod_Ctrl, IsVkDown(VK_CONTROL)); - io.AddKeyEvent(ImGuiMod_Shift, IsVkDown(VK_SHIFT)); - io.AddKeyEvent(ImGuiMod_Alt, IsVkDown(VK_MENU)); - io.AddKeyEvent(ImGuiMod_Super, IsVkDown(VK_APPS)); -} - -// This code supports multi-viewports (multiple OS Windows mapped into different Dear ImGui viewports) -// Because of that, it is a little more complicated than your typical single-viewport binding code! -static void ImGui_ImplWin32_UpdateMouseData() -{ - ImGui_ImplWin32_Data* bd = ImGui_ImplWin32_GetBackendData(); - ImGuiIO& io = ImGui::GetIO(); - IM_ASSERT(bd->hWnd != 0); - - POINT mouse_screen_pos; - bool has_mouse_screen_pos = ::GetCursorPos(&mouse_screen_pos) != 0; - - HWND focused_window = ::GetForegroundWindow(); - const bool is_app_focused = (focused_window && (focused_window == bd->hWnd || ::IsChild(focused_window, bd->hWnd) || ImGui::FindViewportByPlatformHandle((void*)focused_window))); - if (is_app_focused) - { - // (Optional) Set OS mouse position from Dear ImGui if requested (rarely used, only when ImGuiConfigFlags_NavEnableSetMousePos is enabled by user) - // When multi-viewports are enabled, all Dear ImGui positions are same as OS positions. - if (io.WantSetMousePos) - { - POINT pos = { (int)io.MousePos.x, (int)io.MousePos.y }; - if ((io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) == 0) - ::ClientToScreen(focused_window, &pos); - ::SetCursorPos(pos.x, pos.y); - } - - // (Optional) Fallback to provide mouse position when focused (WM_MOUSEMOVE already provides this when hovered or captured) - // This also fills a short gap when clicking non-client area: WM_NCMOUSELEAVE -> modal OS move -> gap -> WM_NCMOUSEMOVE - if (!io.WantSetMousePos && bd->MouseTrackedArea == 0 && has_mouse_screen_pos) - { - // Single viewport mode: mouse position in client window coordinates (io.MousePos is (0,0) when the mouse is on the upper-left corner of the app window) - // (This is the position you can get with ::GetCursorPos() + ::ScreenToClient() or WM_MOUSEMOVE.) - // Multi-viewport mode: mouse position in OS absolute coordinates (io.MousePos is (0,0) when the mouse is on the upper-left of the primary monitor) - // (This is the position you can get with ::GetCursorPos() or WM_MOUSEMOVE + ::ClientToScreen(). In theory adding viewport->Pos to a client position would also be the same.) - POINT mouse_pos = mouse_screen_pos; - if (!(io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable)) - ::ScreenToClient(bd->hWnd, &mouse_pos); - io.AddMousePosEvent((float)mouse_pos.x, (float)mouse_pos.y); - } - } - - // (Optional) When using multiple viewports: call io.AddMouseViewportEvent() with the viewport the OS mouse cursor is hovering. - // If ImGuiBackendFlags_HasMouseHoveredViewport is not set by the backend, Dear imGui will ignore this field and infer the information using its flawed heuristic. - // - [X] Win32 backend correctly ignore viewports with the _NoInputs flag (here using ::WindowFromPoint with WM_NCHITTEST + HTTRANSPARENT in WndProc does that) - // Some backend are not able to handle that correctly. If a backend report an hovered viewport that has the _NoInputs flag (e.g. when dragging a window - // for docking, the viewport has the _NoInputs flag in order to allow us to find the viewport under), then Dear ImGui is forced to ignore the value reported - // by the backend, and use its flawed heuristic to guess the viewport behind. - // - [X] Win32 backend correctly reports this regardless of another viewport behind focused and dragged from (we need this to find a useful drag and drop target). - ImGuiID mouse_viewport_id = 0; - if (has_mouse_screen_pos) - if (HWND hovered_hwnd = ::WindowFromPoint(mouse_screen_pos)) - if (ImGuiViewport* viewport = ImGui::FindViewportByPlatformHandle((void*)hovered_hwnd)) - mouse_viewport_id = viewport->ID; - io.AddMouseViewportEvent(mouse_viewport_id); -} - -// Gamepad navigation mapping -static void ImGui_ImplWin32_UpdateGamepads() -{ -#ifndef IMGUI_IMPL_WIN32_DISABLE_GAMEPAD - ImGuiIO& io = ImGui::GetIO(); - ImGui_ImplWin32_Data* bd = ImGui_ImplWin32_GetBackendData(); - //if ((io.ConfigFlags & ImGuiConfigFlags_NavEnableGamepad) == 0) // FIXME: Technically feeding gamepad shouldn't depend on this now that they are regular inputs. - // return; - - // Calling XInputGetState() every frame on disconnected gamepads is unfortunately too slow. - // Instead we refresh gamepad availability by calling XInputGetCapabilities() _only_ after receiving WM_DEVICECHANGE. - if (bd->WantUpdateHasGamepad) - { - XINPUT_CAPABILITIES caps = {}; - bd->HasGamepad = bd->XInputGetCapabilities ? (bd->XInputGetCapabilities(0, XINPUT_FLAG_GAMEPAD, &caps) == ERROR_SUCCESS) : false; - bd->WantUpdateHasGamepad = false; - } - - io.BackendFlags &= ~ImGuiBackendFlags_HasGamepad; - XINPUT_STATE xinput_state; - XINPUT_GAMEPAD& gamepad = xinput_state.Gamepad; - if (!bd->HasGamepad || bd->XInputGetState == nullptr || bd->XInputGetState(0, &xinput_state) != ERROR_SUCCESS) - return; - io.BackendFlags |= ImGuiBackendFlags_HasGamepad; - - #define IM_SATURATE(V) (V < 0.0f ? 0.0f : V > 1.0f ? 1.0f : V) - #define MAP_BUTTON(KEY_NO, BUTTON_ENUM) { io.AddKeyEvent(KEY_NO, (gamepad.wButtons & BUTTON_ENUM) != 0); } - #define MAP_ANALOG(KEY_NO, VALUE, V0, V1) { float vn = (float)(VALUE - V0) / (float)(V1 - V0); io.AddKeyAnalogEvent(KEY_NO, vn > 0.10f, IM_SATURATE(vn)); } - MAP_BUTTON(ImGuiKey_GamepadStart, XINPUT_GAMEPAD_START); - MAP_BUTTON(ImGuiKey_GamepadBack, XINPUT_GAMEPAD_BACK); - MAP_BUTTON(ImGuiKey_GamepadFaceLeft, XINPUT_GAMEPAD_X); - MAP_BUTTON(ImGuiKey_GamepadFaceRight, XINPUT_GAMEPAD_B); - MAP_BUTTON(ImGuiKey_GamepadFaceUp, XINPUT_GAMEPAD_Y); - MAP_BUTTON(ImGuiKey_GamepadFaceDown, XINPUT_GAMEPAD_A); - MAP_BUTTON(ImGuiKey_GamepadDpadLeft, XINPUT_GAMEPAD_DPAD_LEFT); - MAP_BUTTON(ImGuiKey_GamepadDpadRight, XINPUT_GAMEPAD_DPAD_RIGHT); - MAP_BUTTON(ImGuiKey_GamepadDpadUp, XINPUT_GAMEPAD_DPAD_UP); - MAP_BUTTON(ImGuiKey_GamepadDpadDown, XINPUT_GAMEPAD_DPAD_DOWN); - MAP_BUTTON(ImGuiKey_GamepadL1, XINPUT_GAMEPAD_LEFT_SHOULDER); - MAP_BUTTON(ImGuiKey_GamepadR1, XINPUT_GAMEPAD_RIGHT_SHOULDER); - MAP_ANALOG(ImGuiKey_GamepadL2, gamepad.bLeftTrigger, XINPUT_GAMEPAD_TRIGGER_THRESHOLD, 255); - MAP_ANALOG(ImGuiKey_GamepadR2, gamepad.bRightTrigger, XINPUT_GAMEPAD_TRIGGER_THRESHOLD, 255); - MAP_BUTTON(ImGuiKey_GamepadL3, XINPUT_GAMEPAD_LEFT_THUMB); - MAP_BUTTON(ImGuiKey_GamepadR3, XINPUT_GAMEPAD_RIGHT_THUMB); - MAP_ANALOG(ImGuiKey_GamepadLStickLeft, gamepad.sThumbLX, -XINPUT_GAMEPAD_LEFT_THUMB_DEADZONE, -32768); - MAP_ANALOG(ImGuiKey_GamepadLStickRight, gamepad.sThumbLX, +XINPUT_GAMEPAD_LEFT_THUMB_DEADZONE, +32767); - MAP_ANALOG(ImGuiKey_GamepadLStickUp, gamepad.sThumbLY, +XINPUT_GAMEPAD_LEFT_THUMB_DEADZONE, +32767); - MAP_ANALOG(ImGuiKey_GamepadLStickDown, gamepad.sThumbLY, -XINPUT_GAMEPAD_LEFT_THUMB_DEADZONE, -32768); - MAP_ANALOG(ImGuiKey_GamepadRStickLeft, gamepad.sThumbRX, -XINPUT_GAMEPAD_LEFT_THUMB_DEADZONE, -32768); - MAP_ANALOG(ImGuiKey_GamepadRStickRight, gamepad.sThumbRX, +XINPUT_GAMEPAD_LEFT_THUMB_DEADZONE, +32767); - MAP_ANALOG(ImGuiKey_GamepadRStickUp, gamepad.sThumbRY, +XINPUT_GAMEPAD_LEFT_THUMB_DEADZONE, +32767); - MAP_ANALOG(ImGuiKey_GamepadRStickDown, gamepad.sThumbRY, -XINPUT_GAMEPAD_LEFT_THUMB_DEADZONE, -32768); - #undef MAP_BUTTON - #undef MAP_ANALOG -#endif // #ifndef IMGUI_IMPL_WIN32_DISABLE_GAMEPAD -} - -static BOOL CALLBACK ImGui_ImplWin32_UpdateMonitors_EnumFunc(HMONITOR monitor, HDC, LPRECT, LPARAM) -{ - MONITORINFO info = {}; - info.cbSize = sizeof(MONITORINFO); - if (!::GetMonitorInfo(monitor, &info)) - return TRUE; - ImGuiPlatformMonitor imgui_monitor; - imgui_monitor.MainPos = ImVec2((float)info.rcMonitor.left, (float)info.rcMonitor.top); - imgui_monitor.MainSize = ImVec2((float)(info.rcMonitor.right - info.rcMonitor.left), (float)(info.rcMonitor.bottom - info.rcMonitor.top)); - imgui_monitor.WorkPos = ImVec2((float)info.rcWork.left, (float)info.rcWork.top); - imgui_monitor.WorkSize = ImVec2((float)(info.rcWork.right - info.rcWork.left), (float)(info.rcWork.bottom - info.rcWork.top)); - imgui_monitor.DpiScale = ImGui_ImplWin32_GetDpiScaleForMonitor(monitor); - imgui_monitor.PlatformHandle = (void*)monitor; - ImGuiPlatformIO& io = ImGui::GetPlatformIO(); - if (info.dwFlags & MONITORINFOF_PRIMARY) - io.Monitors.push_front(imgui_monitor); - else - io.Monitors.push_back(imgui_monitor); - return TRUE; -} - -static void ImGui_ImplWin32_UpdateMonitors() -{ - ImGui_ImplWin32_Data* bd = ImGui_ImplWin32_GetBackendData(); - ImGui::GetPlatformIO().Monitors.resize(0); - ::EnumDisplayMonitors(nullptr, nullptr, ImGui_ImplWin32_UpdateMonitors_EnumFunc, 0); - bd->WantUpdateMonitors = false; -} - -void ImGui_ImplWin32_NewFrame() -{ - ImGuiIO& io = ImGui::GetIO(); - ImGui_ImplWin32_Data* bd = ImGui_ImplWin32_GetBackendData(); - IM_ASSERT(bd != nullptr && "Did you call ImGui_ImplWin32_Init()?"); - - // Setup display size (every frame to accommodate for window resizing) - RECT rect = { 0, 0, 0, 0 }; - ::GetClientRect(bd->hWnd, &rect); - io.DisplaySize = ImVec2((float)(rect.right - rect.left), (float)(rect.bottom - rect.top)); - if (bd->WantUpdateMonitors) - ImGui_ImplWin32_UpdateMonitors(); - - // Setup time step - INT64 current_time = 0; - ::QueryPerformanceCounter((LARGE_INTEGER*)¤t_time); - io.DeltaTime = (float)(current_time - bd->Time) / bd->TicksPerSecond; - bd->Time = current_time; - - // Update OS mouse position - ImGui_ImplWin32_UpdateMouseData(); - - // Process workarounds for known Windows key handling issues - ImGui_ImplWin32_ProcessKeyEventsWorkarounds(); - - // Update OS mouse cursor with the cursor requested by imgui - ImGuiMouseCursor mouse_cursor = io.MouseDrawCursor ? ImGuiMouseCursor_None : ImGui::GetMouseCursor(); - if (bd->LastMouseCursor != mouse_cursor) - { - bd->LastMouseCursor = mouse_cursor; - ImGui_ImplWin32_UpdateMouseCursor(); - } - - // Update game controllers (if enabled and available) - ImGui_ImplWin32_UpdateGamepads(); -} - -// There is no distinct VK_xxx for keypad enter, instead it is VK_RETURN + KF_EXTENDED, we assign it an arbitrary value to make code more readable (VK_ codes go up to 255) -#define IM_VK_KEYPAD_ENTER (VK_RETURN + 256) - -// Map VK_xxx to ImGuiKey_xxx. -static ImGuiKey ImGui_ImplWin32_VirtualKeyToImGuiKey(WPARAM wParam) -{ - switch (wParam) - { - case VK_TAB: return ImGuiKey_Tab; - case VK_LEFT: return ImGuiKey_LeftArrow; - case VK_RIGHT: return ImGuiKey_RightArrow; - case VK_UP: return ImGuiKey_UpArrow; - case VK_DOWN: return ImGuiKey_DownArrow; - case VK_PRIOR: return ImGuiKey_PageUp; - case VK_NEXT: return ImGuiKey_PageDown; - case VK_HOME: return ImGuiKey_Home; - case VK_END: return ImGuiKey_End; - case VK_INSERT: return ImGuiKey_Insert; - case VK_DELETE: return ImGuiKey_Delete; - case VK_BACK: return ImGuiKey_Backspace; - case VK_SPACE: return ImGuiKey_Space; - case VK_RETURN: return ImGuiKey_Enter; - case VK_ESCAPE: return ImGuiKey_Escape; - case VK_OEM_7: return ImGuiKey_Apostrophe; - case VK_OEM_COMMA: return ImGuiKey_Comma; - case VK_OEM_MINUS: return ImGuiKey_Minus; - case VK_OEM_PERIOD: return ImGuiKey_Period; - case VK_OEM_2: return ImGuiKey_Slash; - case VK_OEM_1: return ImGuiKey_Semicolon; - case VK_OEM_PLUS: return ImGuiKey_Equal; - case VK_OEM_4: return ImGuiKey_LeftBracket; - case VK_OEM_5: return ImGuiKey_Backslash; - case VK_OEM_6: return ImGuiKey_RightBracket; - case VK_OEM_3: return ImGuiKey_GraveAccent; - case VK_CAPITAL: return ImGuiKey_CapsLock; - case VK_SCROLL: return ImGuiKey_ScrollLock; - case VK_NUMLOCK: return ImGuiKey_NumLock; - case VK_SNAPSHOT: return ImGuiKey_PrintScreen; - case VK_PAUSE: return ImGuiKey_Pause; - case VK_NUMPAD0: return ImGuiKey_Keypad0; - case VK_NUMPAD1: return ImGuiKey_Keypad1; - case VK_NUMPAD2: return ImGuiKey_Keypad2; - case VK_NUMPAD3: return ImGuiKey_Keypad3; - case VK_NUMPAD4: return ImGuiKey_Keypad4; - case VK_NUMPAD5: return ImGuiKey_Keypad5; - case VK_NUMPAD6: return ImGuiKey_Keypad6; - case VK_NUMPAD7: return ImGuiKey_Keypad7; - case VK_NUMPAD8: return ImGuiKey_Keypad8; - case VK_NUMPAD9: return ImGuiKey_Keypad9; - case VK_DECIMAL: return ImGuiKey_KeypadDecimal; - case VK_DIVIDE: return ImGuiKey_KeypadDivide; - case VK_MULTIPLY: return ImGuiKey_KeypadMultiply; - case VK_SUBTRACT: return ImGuiKey_KeypadSubtract; - case VK_ADD: return ImGuiKey_KeypadAdd; - case IM_VK_KEYPAD_ENTER: return ImGuiKey_KeypadEnter; - case VK_LSHIFT: return ImGuiKey_LeftShift; - case VK_LCONTROL: return ImGuiKey_LeftCtrl; - case VK_LMENU: return ImGuiKey_LeftAlt; - case VK_LWIN: return ImGuiKey_LeftSuper; - case VK_RSHIFT: return ImGuiKey_RightShift; - case VK_RCONTROL: return ImGuiKey_RightCtrl; - case VK_RMENU: return ImGuiKey_RightAlt; - case VK_RWIN: return ImGuiKey_RightSuper; - case VK_APPS: return ImGuiKey_Menu; - case '0': return ImGuiKey_0; - case '1': return ImGuiKey_1; - case '2': return ImGuiKey_2; - case '3': return ImGuiKey_3; - case '4': return ImGuiKey_4; - case '5': return ImGuiKey_5; - case '6': return ImGuiKey_6; - case '7': return ImGuiKey_7; - case '8': return ImGuiKey_8; - case '9': return ImGuiKey_9; - case 'A': return ImGuiKey_A; - case 'B': return ImGuiKey_B; - case 'C': return ImGuiKey_C; - case 'D': return ImGuiKey_D; - case 'E': return ImGuiKey_E; - case 'F': return ImGuiKey_F; - case 'G': return ImGuiKey_G; - case 'H': return ImGuiKey_H; - case 'I': return ImGuiKey_I; - case 'J': return ImGuiKey_J; - case 'K': return ImGuiKey_K; - case 'L': return ImGuiKey_L; - case 'M': return ImGuiKey_M; - case 'N': return ImGuiKey_N; - case 'O': return ImGuiKey_O; - case 'P': return ImGuiKey_P; - case 'Q': return ImGuiKey_Q; - case 'R': return ImGuiKey_R; - case 'S': return ImGuiKey_S; - case 'T': return ImGuiKey_T; - case 'U': return ImGuiKey_U; - case 'V': return ImGuiKey_V; - case 'W': return ImGuiKey_W; - case 'X': return ImGuiKey_X; - case 'Y': return ImGuiKey_Y; - case 'Z': return ImGuiKey_Z; - case VK_F1: return ImGuiKey_F1; - case VK_F2: return ImGuiKey_F2; - case VK_F3: return ImGuiKey_F3; - case VK_F4: return ImGuiKey_F4; - case VK_F5: return ImGuiKey_F5; - case VK_F6: return ImGuiKey_F6; - case VK_F7: return ImGuiKey_F7; - case VK_F8: return ImGuiKey_F8; - case VK_F9: return ImGuiKey_F9; - case VK_F10: return ImGuiKey_F10; - case VK_F11: return ImGuiKey_F11; - case VK_F12: return ImGuiKey_F12; - case VK_F13: return ImGuiKey_F13; - case VK_F14: return ImGuiKey_F14; - case VK_F15: return ImGuiKey_F15; - case VK_F16: return ImGuiKey_F16; - case VK_F17: return ImGuiKey_F17; - case VK_F18: return ImGuiKey_F18; - case VK_F19: return ImGuiKey_F19; - case VK_F20: return ImGuiKey_F20; - case VK_F21: return ImGuiKey_F21; - case VK_F22: return ImGuiKey_F22; - case VK_F23: return ImGuiKey_F23; - case VK_F24: return ImGuiKey_F24; - case VK_BROWSER_BACK: return ImGuiKey_AppBack; - case VK_BROWSER_FORWARD: return ImGuiKey_AppForward; - default: return ImGuiKey_None; - } -} - -// Allow compilation with old Windows SDK. MinGW doesn't have default _WIN32_WINNT/WINVER versions. -#ifndef WM_MOUSEHWHEEL -#define WM_MOUSEHWHEEL 0x020E -#endif -#ifndef DBT_DEVNODES_CHANGED -#define DBT_DEVNODES_CHANGED 0x0007 -#endif - -// Win32 message handler (process Win32 mouse/keyboard inputs, etc.) -// Call from your application's message handler. Keep calling your message handler unless this function returns TRUE. -// When implementing your own backend, you can read the io.WantCaptureMouse, io.WantCaptureKeyboard flags to tell if Dear ImGui wants to use your inputs. -// - When io.WantCaptureMouse is true, do not dispatch mouse input data to your main application, or clear/overwrite your copy of the mouse data. -// - When io.WantCaptureKeyboard is true, do not dispatch keyboard input data to your main application, or clear/overwrite your copy of the keyboard data. -// Generally you may always pass all inputs to Dear ImGui, and hide them from your application based on those two flags. -// PS: In this Win32 handler, we use the capture API (GetCapture/SetCapture/ReleaseCapture) to be able to read mouse coordinates when dragging mouse outside of our window bounds. -// PS: We treat DBLCLK messages as regular mouse down messages, so this code will work on windows classes that have the CS_DBLCLKS flag set. Our own example app code doesn't set this flag. -#if 0 -// Copy this line into your .cpp file to forward declare the function. -extern IMGUI_IMPL_API LRESULT ImGui_ImplWin32_WndProcHandler(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam); -#endif - -// See https://learn.microsoft.com/en-us/windows/win32/tablet/system-events-and-mouse-messages -// Prefer to call this at the top of the message handler to avoid the possibility of other Win32 calls interfering with this. -static ImGuiMouseSource GetMouseSourceFromMessageExtraInfo() -{ - LPARAM extra_info = ::GetMessageExtraInfo(); - if ((extra_info & 0xFFFFFF80) == 0xFF515700) - return ImGuiMouseSource_Pen; - if ((extra_info & 0xFFFFFF80) == 0xFF515780) - return ImGuiMouseSource_TouchScreen; - return ImGuiMouseSource_Mouse; -} - -IMGUI_IMPL_API LRESULT ImGui_ImplWin32_WndProcHandler(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam) -{ - if (ImGui::GetCurrentContext() == nullptr) - return 0; - - ImGuiIO& io = ImGui::GetIO(); - ImGui_ImplWin32_Data* bd = ImGui_ImplWin32_GetBackendData(); - - switch (msg) - { - case WM_MOUSEMOVE: - case WM_NCMOUSEMOVE: - { - // We need to call TrackMouseEvent in order to receive WM_MOUSELEAVE events - ImGuiMouseSource mouse_source = GetMouseSourceFromMessageExtraInfo(); - const int area = (msg == WM_MOUSEMOVE) ? 1 : 2; - bd->MouseHwnd = hwnd; - if (bd->MouseTrackedArea != area) - { - TRACKMOUSEEVENT tme_cancel = { sizeof(tme_cancel), TME_CANCEL, hwnd, 0 }; - TRACKMOUSEEVENT tme_track = { sizeof(tme_track), (DWORD)((area == 2) ? (TME_LEAVE | TME_NONCLIENT) : TME_LEAVE), hwnd, 0 }; - if (bd->MouseTrackedArea != 0) - ::TrackMouseEvent(&tme_cancel); - ::TrackMouseEvent(&tme_track); - bd->MouseTrackedArea = area; - } - POINT mouse_pos = { (LONG)GET_X_LPARAM(lParam), (LONG)GET_Y_LPARAM(lParam) }; - bool want_absolute_pos = (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) != 0; - if (msg == WM_MOUSEMOVE && want_absolute_pos) // WM_MOUSEMOVE are client-relative coordinates. - ::ClientToScreen(hwnd, &mouse_pos); - if (msg == WM_NCMOUSEMOVE && !want_absolute_pos) // WM_NCMOUSEMOVE are absolute coordinates. - ::ScreenToClient(hwnd, &mouse_pos); - io.AddMouseSourceEvent(mouse_source); - io.AddMousePosEvent((float)mouse_pos.x, (float)mouse_pos.y); - break; - } - case WM_MOUSELEAVE: - case WM_NCMOUSELEAVE: - { - const int area = (msg == WM_MOUSELEAVE) ? 1 : 2; - if (bd->MouseTrackedArea == area) - { - if (bd->MouseHwnd == hwnd) - bd->MouseHwnd = nullptr; - bd->MouseTrackedArea = 0; - io.AddMousePosEvent(-FLT_MAX, -FLT_MAX); - } - break; - } - case WM_LBUTTONDOWN: case WM_LBUTTONDBLCLK: - case WM_RBUTTONDOWN: case WM_RBUTTONDBLCLK: - case WM_MBUTTONDOWN: case WM_MBUTTONDBLCLK: - case WM_XBUTTONDOWN: case WM_XBUTTONDBLCLK: - { - ImGuiMouseSource mouse_source = GetMouseSourceFromMessageExtraInfo(); - int button = 0; - if (msg == WM_LBUTTONDOWN || msg == WM_LBUTTONDBLCLK) { button = 0; } - if (msg == WM_RBUTTONDOWN || msg == WM_RBUTTONDBLCLK) { button = 1; } - if (msg == WM_MBUTTONDOWN || msg == WM_MBUTTONDBLCLK) { button = 2; } - if (msg == WM_XBUTTONDOWN || msg == WM_XBUTTONDBLCLK) { button = (GET_XBUTTON_WPARAM(wParam) == XBUTTON1) ? 3 : 4; } - if (bd->MouseButtonsDown == 0 && ::GetCapture() == nullptr) - ::SetCapture(hwnd); - bd->MouseButtonsDown |= 1 << button; - io.AddMouseSourceEvent(mouse_source); - io.AddMouseButtonEvent(button, true); - return 0; - } - case WM_LBUTTONUP: - case WM_RBUTTONUP: - case WM_MBUTTONUP: - case WM_XBUTTONUP: - { - ImGuiMouseSource mouse_source = GetMouseSourceFromMessageExtraInfo(); - int button = 0; - if (msg == WM_LBUTTONUP) { button = 0; } - if (msg == WM_RBUTTONUP) { button = 1; } - if (msg == WM_MBUTTONUP) { button = 2; } - if (msg == WM_XBUTTONUP) { button = (GET_XBUTTON_WPARAM(wParam) == XBUTTON1) ? 3 : 4; } - bd->MouseButtonsDown &= ~(1 << button); - if (bd->MouseButtonsDown == 0 && ::GetCapture() == hwnd) - ::ReleaseCapture(); - io.AddMouseSourceEvent(mouse_source); - io.AddMouseButtonEvent(button, false); - return 0; - } - case WM_MOUSEWHEEL: - io.AddMouseWheelEvent(0.0f, (float)GET_WHEEL_DELTA_WPARAM(wParam) / (float)WHEEL_DELTA); - return 0; - case WM_MOUSEHWHEEL: - io.AddMouseWheelEvent(-(float)GET_WHEEL_DELTA_WPARAM(wParam) / (float)WHEEL_DELTA, 0.0f); - return 0; - case WM_KEYDOWN: - case WM_KEYUP: - case WM_SYSKEYDOWN: - case WM_SYSKEYUP: - { - const bool is_key_down = (msg == WM_KEYDOWN || msg == WM_SYSKEYDOWN); - if (wParam < 256) - { - // Submit modifiers - ImGui_ImplWin32_UpdateKeyModifiers(); - - // Obtain virtual key code - // (keypad enter doesn't have its own... VK_RETURN with KF_EXTENDED flag means keypad enter, see IM_VK_KEYPAD_ENTER definition for details, it is mapped to ImGuiKey_KeyPadEnter.) - int vk = (int)wParam; - if ((wParam == VK_RETURN) && (HIWORD(lParam) & KF_EXTENDED)) - vk = IM_VK_KEYPAD_ENTER; - const ImGuiKey key = ImGui_ImplWin32_VirtualKeyToImGuiKey(vk); - const int scancode = (int)LOBYTE(HIWORD(lParam)); - - // Special behavior for VK_SNAPSHOT / ImGuiKey_PrintScreen as Windows doesn't emit the key down event. - if (key == ImGuiKey_PrintScreen && !is_key_down) - ImGui_ImplWin32_AddKeyEvent(key, true, vk, scancode); - - // Submit key event - if (key != ImGuiKey_None) - ImGui_ImplWin32_AddKeyEvent(key, is_key_down, vk, scancode); - - // Submit individual left/right modifier events - if (vk == VK_SHIFT) - { - // Important: Shift keys tend to get stuck when pressed together, missing key-up events are corrected in ImGui_ImplWin32_ProcessKeyEventsWorkarounds() - if (IsVkDown(VK_LSHIFT) == is_key_down) { ImGui_ImplWin32_AddKeyEvent(ImGuiKey_LeftShift, is_key_down, VK_LSHIFT, scancode); } - if (IsVkDown(VK_RSHIFT) == is_key_down) { ImGui_ImplWin32_AddKeyEvent(ImGuiKey_RightShift, is_key_down, VK_RSHIFT, scancode); } - } - else if (vk == VK_CONTROL) - { - if (IsVkDown(VK_LCONTROL) == is_key_down) { ImGui_ImplWin32_AddKeyEvent(ImGuiKey_LeftCtrl, is_key_down, VK_LCONTROL, scancode); } - if (IsVkDown(VK_RCONTROL) == is_key_down) { ImGui_ImplWin32_AddKeyEvent(ImGuiKey_RightCtrl, is_key_down, VK_RCONTROL, scancode); } - } - else if (vk == VK_MENU) - { - if (IsVkDown(VK_LMENU) == is_key_down) { ImGui_ImplWin32_AddKeyEvent(ImGuiKey_LeftAlt, is_key_down, VK_LMENU, scancode); } - if (IsVkDown(VK_RMENU) == is_key_down) { ImGui_ImplWin32_AddKeyEvent(ImGuiKey_RightAlt, is_key_down, VK_RMENU, scancode); } - } - } - return 0; - } - case WM_SETFOCUS: - case WM_KILLFOCUS: - io.AddFocusEvent(msg == WM_SETFOCUS); - return 0; - case WM_INPUTLANGCHANGE: - ImGui_ImplWin32_UpdateKeyboardCodePage(); - return 0; - case WM_CHAR: - if (::IsWindowUnicode(hwnd)) - { - // You can also use ToAscii()+GetKeyboardState() to retrieve characters. - if (wParam > 0 && wParam < 0x10000) - io.AddInputCharacterUTF16((unsigned short)wParam); - } - else - { - wchar_t wch = 0; - ::MultiByteToWideChar(bd->KeyboardCodePage, MB_PRECOMPOSED, (char*)&wParam, 1, &wch, 1); - io.AddInputCharacter(wch); - } - return 0; - case WM_SETCURSOR: - // This is required to restore cursor when transitioning from e.g resize borders to client area. - if (LOWORD(lParam) == HTCLIENT && ImGui_ImplWin32_UpdateMouseCursor()) - return 1; - return 0; - case WM_DEVICECHANGE: -#ifndef IMGUI_IMPL_WIN32_DISABLE_GAMEPAD - if ((UINT)wParam == DBT_DEVNODES_CHANGED) - bd->WantUpdateHasGamepad = true; -#endif - return 0; - case WM_DISPLAYCHANGE: - bd->WantUpdateMonitors = true; - return 0; - } - return 0; -} - - -//-------------------------------------------------------------------------------------------------------- -// DPI-related helpers (optional) -//-------------------------------------------------------------------------------------------------------- -// - Use to enable DPI awareness without having to create an application manifest. -// - Your own app may already do this via a manifest or explicit calls. This is mostly useful for our examples/ apps. -// - In theory we could call simple functions from Windows SDK such as SetProcessDPIAware(), SetProcessDpiAwareness(), etc. -// but most of the functions provided by Microsoft require Windows 8.1/10+ SDK at compile time and Windows 8/10+ at runtime, -// neither we want to require the user to have. So we dynamically select and load those functions to avoid dependencies. -//--------------------------------------------------------------------------------------------------------- -// This is the scheme successfully used by GLFW (from which we borrowed some of the code) and other apps aiming to be highly portable. -// ImGui_ImplWin32_EnableDpiAwareness() is just a helper called by main.cpp, we don't call it automatically. -// If you are trying to implement your own backend for your own engine, you may ignore that noise. -//--------------------------------------------------------------------------------------------------------- - -// Perform our own check with RtlVerifyVersionInfo() instead of using functions from as they -// require a manifest to be functional for checks above 8.1. See https://github.com/ocornut/imgui/issues/4200 -static BOOL _IsWindowsVersionOrGreater(WORD major, WORD minor, WORD) -{ - typedef LONG(WINAPI* PFN_RtlVerifyVersionInfo)(OSVERSIONINFOEXW*, ULONG, ULONGLONG); - static PFN_RtlVerifyVersionInfo RtlVerifyVersionInfoFn = nullptr; - if (RtlVerifyVersionInfoFn == nullptr) - if (HMODULE ntdllModule = ::GetModuleHandleA("ntdll.dll")) - RtlVerifyVersionInfoFn = (PFN_RtlVerifyVersionInfo)GetProcAddress(ntdllModule, "RtlVerifyVersionInfo"); - if (RtlVerifyVersionInfoFn == nullptr) - return FALSE; - - RTL_OSVERSIONINFOEXW versionInfo = { }; - ULONGLONG conditionMask = 0; - versionInfo.dwOSVersionInfoSize = sizeof(RTL_OSVERSIONINFOEXW); - versionInfo.dwMajorVersion = major; - versionInfo.dwMinorVersion = minor; - VER_SET_CONDITION(conditionMask, VER_MAJORVERSION, VER_GREATER_EQUAL); - VER_SET_CONDITION(conditionMask, VER_MINORVERSION, VER_GREATER_EQUAL); - return (RtlVerifyVersionInfoFn(&versionInfo, VER_MAJORVERSION | VER_MINORVERSION, conditionMask) == 0) ? TRUE : FALSE; -} - -#define _IsWindowsVistaOrGreater() _IsWindowsVersionOrGreater(HIBYTE(0x0600), LOBYTE(0x0600), 0) // _WIN32_WINNT_VISTA -#define _IsWindows8OrGreater() _IsWindowsVersionOrGreater(HIBYTE(0x0602), LOBYTE(0x0602), 0) // _WIN32_WINNT_WIN8 -#define _IsWindows8Point1OrGreater() _IsWindowsVersionOrGreater(HIBYTE(0x0603), LOBYTE(0x0603), 0) // _WIN32_WINNT_WINBLUE -#define _IsWindows10OrGreater() _IsWindowsVersionOrGreater(HIBYTE(0x0A00), LOBYTE(0x0A00), 0) // _WIN32_WINNT_WINTHRESHOLD / _WIN32_WINNT_WIN10 - -#ifndef DPI_ENUMS_DECLARED -typedef enum { PROCESS_DPI_UNAWARE = 0, PROCESS_SYSTEM_DPI_AWARE = 1, PROCESS_PER_MONITOR_DPI_AWARE = 2 } PROCESS_DPI_AWARENESS; -typedef enum { MDT_EFFECTIVE_DPI = 0, MDT_ANGULAR_DPI = 1, MDT_RAW_DPI = 2, MDT_DEFAULT = MDT_EFFECTIVE_DPI } MONITOR_DPI_TYPE; -#endif -#ifndef _DPI_AWARENESS_CONTEXTS_ -DECLARE_HANDLE(DPI_AWARENESS_CONTEXT); -#define DPI_AWARENESS_CONTEXT_PER_MONITOR_AWARE (DPI_AWARENESS_CONTEXT)-3 -#endif -#ifndef DPI_AWARENESS_CONTEXT_PER_MONITOR_AWARE_V2 -#define DPI_AWARENESS_CONTEXT_PER_MONITOR_AWARE_V2 (DPI_AWARENESS_CONTEXT)-4 -#endif -typedef HRESULT(WINAPI* PFN_SetProcessDpiAwareness)(PROCESS_DPI_AWARENESS); // Shcore.lib + dll, Windows 8.1+ -typedef HRESULT(WINAPI* PFN_GetDpiForMonitor)(HMONITOR, MONITOR_DPI_TYPE, UINT*, UINT*); // Shcore.lib + dll, Windows 8.1+ -typedef DPI_AWARENESS_CONTEXT(WINAPI* PFN_SetThreadDpiAwarenessContext)(DPI_AWARENESS_CONTEXT); // User32.lib + dll, Windows 10 v1607+ (Creators Update) - -// Helper function to enable DPI awareness without setting up a manifest -void ImGui_ImplWin32_EnableDpiAwareness() -{ - // Make sure monitors will be updated with latest correct scaling - if (ImGui_ImplWin32_Data* bd = ImGui_ImplWin32_GetBackendData()) - bd->WantUpdateMonitors = true; - - if (_IsWindows10OrGreater()) - { - static HINSTANCE user32_dll = ::LoadLibraryA("user32.dll"); // Reference counted per-process - if (PFN_SetThreadDpiAwarenessContext SetThreadDpiAwarenessContextFn = (PFN_SetThreadDpiAwarenessContext)::GetProcAddress(user32_dll, "SetThreadDpiAwarenessContext")) - { - SetThreadDpiAwarenessContextFn(DPI_AWARENESS_CONTEXT_PER_MONITOR_AWARE_V2); - return; - } - } - if (_IsWindows8Point1OrGreater()) - { - static HINSTANCE shcore_dll = ::LoadLibraryA("shcore.dll"); // Reference counted per-process - if (PFN_SetProcessDpiAwareness SetProcessDpiAwarenessFn = (PFN_SetProcessDpiAwareness)::GetProcAddress(shcore_dll, "SetProcessDpiAwareness")) - { - SetProcessDpiAwarenessFn(PROCESS_PER_MONITOR_DPI_AWARE); - return; - } - } -#if _WIN32_WINNT >= 0x0600 - ::SetProcessDPIAware(); -#endif -} - -#if defined(_MSC_VER) && !defined(NOGDI) -#pragma comment(lib, "gdi32") // Link with gdi32.lib for GetDeviceCaps(). MinGW will require linking with '-lgdi32' -#endif - -float ImGui_ImplWin32_GetDpiScaleForMonitor(void* monitor) -{ - UINT xdpi = 96, ydpi = 96; - if (_IsWindows8Point1OrGreater()) - { - static HINSTANCE shcore_dll = ::LoadLibraryA("shcore.dll"); // Reference counted per-process - static PFN_GetDpiForMonitor GetDpiForMonitorFn = nullptr; - if (GetDpiForMonitorFn == nullptr && shcore_dll != nullptr) - GetDpiForMonitorFn = (PFN_GetDpiForMonitor)::GetProcAddress(shcore_dll, "GetDpiForMonitor"); - if (GetDpiForMonitorFn != nullptr) - { - GetDpiForMonitorFn((HMONITOR)monitor, MDT_EFFECTIVE_DPI, &xdpi, &ydpi); - IM_ASSERT(xdpi == ydpi); // Please contact me if you hit this assert! - return xdpi / 96.0f; - } - } -#ifndef NOGDI - const HDC dc = ::GetDC(nullptr); - xdpi = ::GetDeviceCaps(dc, LOGPIXELSX); - ydpi = ::GetDeviceCaps(dc, LOGPIXELSY); - IM_ASSERT(xdpi == ydpi); // Please contact me if you hit this assert! - ::ReleaseDC(nullptr, dc); -#endif - return xdpi / 96.0f; -} - -float ImGui_ImplWin32_GetDpiScaleForHwnd(void* hwnd) -{ - HMONITOR monitor = ::MonitorFromWindow((HWND)hwnd, MONITOR_DEFAULTTONEAREST); - return ImGui_ImplWin32_GetDpiScaleForMonitor(monitor); -} - -//--------------------------------------------------------------------------------------------------------- -// Transparency related helpers (optional) -//-------------------------------------------------------------------------------------------------------- - -#if defined(_MSC_VER) -#pragma comment(lib, "dwmapi") // Link with dwmapi.lib. MinGW will require linking with '-ldwmapi' -#endif - -// [experimental] -// Borrowed from GLFW's function updateFramebufferTransparency() in src/win32_window.c -// (the Dwm* functions are Vista era functions but we are borrowing logic from GLFW) -void ImGui_ImplWin32_EnableAlphaCompositing(void* hwnd) -{ - if (!_IsWindowsVistaOrGreater()) - return; - - BOOL composition; - if (FAILED(::DwmIsCompositionEnabled(&composition)) || !composition) - return; - - BOOL opaque; - DWORD color; - if (_IsWindows8OrGreater() || (SUCCEEDED(::DwmGetColorizationColor(&color, &opaque)) && !opaque)) - { - HRGN region = ::CreateRectRgn(0, 0, -1, -1); - DWM_BLURBEHIND bb = {}; - bb.dwFlags = DWM_BB_ENABLE | DWM_BB_BLURREGION; - bb.hRgnBlur = region; - bb.fEnable = TRUE; - ::DwmEnableBlurBehindWindow((HWND)hwnd, &bb); - ::DeleteObject(region); - } - else - { - DWM_BLURBEHIND bb = {}; - bb.dwFlags = DWM_BB_ENABLE; - ::DwmEnableBlurBehindWindow((HWND)hwnd, &bb); - } -} - -//--------------------------------------------------------------------------------------------------------- -// MULTI-VIEWPORT / PLATFORM INTERFACE SUPPORT -// This is an _advanced_ and _optional_ feature, allowing the backend to create and handle multiple viewports simultaneously. -// If you are new to dear imgui or creating a new binding for dear imgui, it is recommended that you completely ignore this section first.. -//-------------------------------------------------------------------------------------------------------- - -// Helper structure we store in the void* RendererUserData field of each ImGuiViewport to easily retrieve our backend data. -struct ImGui_ImplWin32_ViewportData -{ - HWND Hwnd; - HWND HwndParent; - bool HwndOwned; - DWORD DwStyle; - DWORD DwExStyle; - - ImGui_ImplWin32_ViewportData() { Hwnd = HwndParent = nullptr; HwndOwned = false; DwStyle = DwExStyle = 0; } - ~ImGui_ImplWin32_ViewportData() { IM_ASSERT(Hwnd == nullptr); } -}; - -static void ImGui_ImplWin32_GetWin32StyleFromViewportFlags(ImGuiViewportFlags flags, DWORD* out_style, DWORD* out_ex_style) -{ - if (flags & ImGuiViewportFlags_NoDecoration) - *out_style = WS_POPUP; - else - *out_style = WS_OVERLAPPEDWINDOW; - - if (flags & ImGuiViewportFlags_NoTaskBarIcon) - *out_ex_style = WS_EX_TOOLWINDOW; - else - *out_ex_style = WS_EX_APPWINDOW; - - if (flags & ImGuiViewportFlags_TopMost) - *out_ex_style |= WS_EX_TOPMOST; -} - -static HWND ImGui_ImplWin32_GetHwndFromViewportID(ImGuiID viewport_id) -{ - if (viewport_id != 0) - if (ImGuiViewport* viewport = ImGui::FindViewportByID(viewport_id)) - return (HWND)viewport->PlatformHandle; - return nullptr; -} - -static void ImGui_ImplWin32_CreateWindow(ImGuiViewport* viewport) -{ - ImGui_ImplWin32_ViewportData* vd = IM_NEW(ImGui_ImplWin32_ViewportData)(); - viewport->PlatformUserData = vd; - - // Select style and parent window - ImGui_ImplWin32_GetWin32StyleFromViewportFlags(viewport->Flags, &vd->DwStyle, &vd->DwExStyle); - vd->HwndParent = ImGui_ImplWin32_GetHwndFromViewportID(viewport->ParentViewportId); - - // Create window - RECT rect = { (LONG)viewport->Pos.x, (LONG)viewport->Pos.y, (LONG)(viewport->Pos.x + viewport->Size.x), (LONG)(viewport->Pos.y + viewport->Size.y) }; - ::AdjustWindowRectEx(&rect, vd->DwStyle, FALSE, vd->DwExStyle); - vd->Hwnd = ::CreateWindowEx( - vd->DwExStyle, _T("ImGui Platform"), _T("Untitled"), vd->DwStyle, // Style, class name, window name - rect.left, rect.top, rect.right - rect.left, rect.bottom - rect.top, // Window area - vd->HwndParent, nullptr, ::GetModuleHandle(nullptr), nullptr); // Owner window, Menu, Instance, Param - vd->HwndOwned = true; - viewport->PlatformRequestResize = false; - viewport->PlatformHandle = viewport->PlatformHandleRaw = vd->Hwnd; -} - -static void ImGui_ImplWin32_DestroyWindow(ImGuiViewport* viewport) -{ - ImGui_ImplWin32_Data* bd = ImGui_ImplWin32_GetBackendData(); - if (ImGui_ImplWin32_ViewportData* vd = (ImGui_ImplWin32_ViewportData*)viewport->PlatformUserData) - { - if (::GetCapture() == vd->Hwnd) - { - // Transfer capture so if we started dragging from a window that later disappears, we'll still receive the MOUSEUP event. - ::ReleaseCapture(); - ::SetCapture(bd->hWnd); - } - if (vd->Hwnd && vd->HwndOwned) - ::DestroyWindow(vd->Hwnd); - vd->Hwnd = nullptr; - IM_DELETE(vd); - } - viewport->PlatformUserData = viewport->PlatformHandle = nullptr; -} - -static void ImGui_ImplWin32_ShowWindow(ImGuiViewport* viewport) -{ - ImGui_ImplWin32_ViewportData* vd = (ImGui_ImplWin32_ViewportData*)viewport->PlatformUserData; - IM_ASSERT(vd->Hwnd != 0); - if (viewport->Flags & ImGuiViewportFlags_NoFocusOnAppearing) - ::ShowWindow(vd->Hwnd, SW_SHOWNA); - else - ::ShowWindow(vd->Hwnd, SW_SHOW); -} - -static void ImGui_ImplWin32_UpdateWindow(ImGuiViewport* viewport) -{ - ImGui_ImplWin32_ViewportData* vd = (ImGui_ImplWin32_ViewportData*)viewport->PlatformUserData; - IM_ASSERT(vd->Hwnd != 0); - - // Update Win32 parent if it changed _after_ creation - // Unlike style settings derived from configuration flags, this is more likely to change for advanced apps that are manipulating ParentViewportID manually. - HWND new_parent = ImGui_ImplWin32_GetHwndFromViewportID(viewport->ParentViewportId); - if (new_parent != vd->HwndParent) - { - // Win32 windows can either have a "Parent" (for WS_CHILD window) or an "Owner" (which among other thing keeps window above its owner). - // Our Dear Imgui-side concept of parenting only mostly care about what Win32 call "Owner". - // The parent parameter of CreateWindowEx() sets up Parent OR Owner depending on WS_CHILD flag. In our case an Owner as we never use WS_CHILD. - // Calling ::SetParent() here would be incorrect: it will create a full child relation, alter coordinate system and clipping. - // Calling ::SetWindowLongPtr() with GWLP_HWNDPARENT seems correct although poorly documented. - // https://devblogs.microsoft.com/oldnewthing/20100315-00/?p=14613 - vd->HwndParent = new_parent; - ::SetWindowLongPtr(vd->Hwnd, GWLP_HWNDPARENT, (LONG_PTR)vd->HwndParent); - } - - // (Optional) Update Win32 style if it changed _after_ creation. - // Generally they won't change unless configuration flags are changed, but advanced uses (such as manually rewriting viewport flags) make this useful. - DWORD new_style; - DWORD new_ex_style; - ImGui_ImplWin32_GetWin32StyleFromViewportFlags(viewport->Flags, &new_style, &new_ex_style); - - // Only reapply the flags that have been changed from our point of view (as other flags are being modified by Windows) - if (vd->DwStyle != new_style || vd->DwExStyle != new_ex_style) - { - // (Optional) Update TopMost state if it changed _after_ creation - bool top_most_changed = (vd->DwExStyle & WS_EX_TOPMOST) != (new_ex_style & WS_EX_TOPMOST); - HWND insert_after = top_most_changed ? ((viewport->Flags & ImGuiViewportFlags_TopMost) ? HWND_TOPMOST : HWND_NOTOPMOST) : 0; - UINT swp_flag = top_most_changed ? 0 : SWP_NOZORDER; - - // Apply flags and position (since it is affected by flags) - vd->DwStyle = new_style; - vd->DwExStyle = new_ex_style; - ::SetWindowLong(vd->Hwnd, GWL_STYLE, vd->DwStyle); - ::SetWindowLong(vd->Hwnd, GWL_EXSTYLE, vd->DwExStyle); - RECT rect = { (LONG)viewport->Pos.x, (LONG)viewport->Pos.y, (LONG)(viewport->Pos.x + viewport->Size.x), (LONG)(viewport->Pos.y + viewport->Size.y) }; - ::AdjustWindowRectEx(&rect, vd->DwStyle, FALSE, vd->DwExStyle); // Client to Screen - ::SetWindowPos(vd->Hwnd, insert_after, rect.left, rect.top, rect.right - rect.left, rect.bottom - rect.top, swp_flag | SWP_NOACTIVATE | SWP_FRAMECHANGED); - ::ShowWindow(vd->Hwnd, SW_SHOWNA); // This is necessary when we alter the style - viewport->PlatformRequestMove = viewport->PlatformRequestResize = true; - } -} - -static ImVec2 ImGui_ImplWin32_GetWindowPos(ImGuiViewport* viewport) -{ - ImGui_ImplWin32_ViewportData* vd = (ImGui_ImplWin32_ViewportData*)viewport->PlatformUserData; - IM_ASSERT(vd->Hwnd != 0); - POINT pos = { 0, 0 }; - ::ClientToScreen(vd->Hwnd, &pos); - return ImVec2((float)pos.x, (float)pos.y); -} - -static void ImGui_ImplWin32_SetWindowPos(ImGuiViewport* viewport, ImVec2 pos) -{ - ImGui_ImplWin32_ViewportData* vd = (ImGui_ImplWin32_ViewportData*)viewport->PlatformUserData; - IM_ASSERT(vd->Hwnd != 0); - RECT rect = { (LONG)pos.x, (LONG)pos.y, (LONG)pos.x, (LONG)pos.y }; - ::AdjustWindowRectEx(&rect, vd->DwStyle, FALSE, vd->DwExStyle); - ::SetWindowPos(vd->Hwnd, nullptr, rect.left, rect.top, 0, 0, SWP_NOZORDER | SWP_NOSIZE | SWP_NOACTIVATE); -} - -static ImVec2 ImGui_ImplWin32_GetWindowSize(ImGuiViewport* viewport) -{ - ImGui_ImplWin32_ViewportData* vd = (ImGui_ImplWin32_ViewportData*)viewport->PlatformUserData; - IM_ASSERT(vd->Hwnd != 0); - RECT rect; - ::GetClientRect(vd->Hwnd, &rect); - return ImVec2(float(rect.right - rect.left), float(rect.bottom - rect.top)); -} - -static void ImGui_ImplWin32_SetWindowSize(ImGuiViewport* viewport, ImVec2 size) -{ - ImGui_ImplWin32_ViewportData* vd = (ImGui_ImplWin32_ViewportData*)viewport->PlatformUserData; - IM_ASSERT(vd->Hwnd != 0); - RECT rect = { 0, 0, (LONG)size.x, (LONG)size.y }; - ::AdjustWindowRectEx(&rect, vd->DwStyle, FALSE, vd->DwExStyle); // Client to Screen - ::SetWindowPos(vd->Hwnd, nullptr, 0, 0, rect.right - rect.left, rect.bottom - rect.top, SWP_NOZORDER | SWP_NOMOVE | SWP_NOACTIVATE); -} - -static void ImGui_ImplWin32_SetWindowFocus(ImGuiViewport* viewport) -{ - ImGui_ImplWin32_ViewportData* vd = (ImGui_ImplWin32_ViewportData*)viewport->PlatformUserData; - IM_ASSERT(vd->Hwnd != 0); - ::BringWindowToTop(vd->Hwnd); - ::SetForegroundWindow(vd->Hwnd); - ::SetFocus(vd->Hwnd); -} - -static bool ImGui_ImplWin32_GetWindowFocus(ImGuiViewport* viewport) -{ - ImGui_ImplWin32_ViewportData* vd = (ImGui_ImplWin32_ViewportData*)viewport->PlatformUserData; - IM_ASSERT(vd->Hwnd != 0); - return ::GetForegroundWindow() == vd->Hwnd; -} - -static bool ImGui_ImplWin32_GetWindowMinimized(ImGuiViewport* viewport) -{ - ImGui_ImplWin32_ViewportData* vd = (ImGui_ImplWin32_ViewportData*)viewport->PlatformUserData; - IM_ASSERT(vd->Hwnd != 0); - return ::IsIconic(vd->Hwnd) != 0; -} - -static void ImGui_ImplWin32_SetWindowTitle(ImGuiViewport* viewport, const char* title) -{ - // ::SetWindowTextA() doesn't properly handle UTF-8 so we explicitely convert our string. - ImGui_ImplWin32_ViewportData* vd = (ImGui_ImplWin32_ViewportData*)viewport->PlatformUserData; - IM_ASSERT(vd->Hwnd != 0); - int n = ::MultiByteToWideChar(CP_UTF8, 0, title, -1, nullptr, 0); - ImVector title_w; - title_w.resize(n); - ::MultiByteToWideChar(CP_UTF8, 0, title, -1, title_w.Data, n); - ::SetWindowTextW(vd->Hwnd, title_w.Data); -} - -static void ImGui_ImplWin32_SetWindowAlpha(ImGuiViewport* viewport, float alpha) -{ - ImGui_ImplWin32_ViewportData* vd = (ImGui_ImplWin32_ViewportData*)viewport->PlatformUserData; - IM_ASSERT(vd->Hwnd != 0); - IM_ASSERT(alpha >= 0.0f && alpha <= 1.0f); - if (alpha < 1.0f) - { - DWORD style = ::GetWindowLongW(vd->Hwnd, GWL_EXSTYLE) | WS_EX_LAYERED; - ::SetWindowLongW(vd->Hwnd, GWL_EXSTYLE, style); - ::SetLayeredWindowAttributes(vd->Hwnd, 0, (BYTE)(255 * alpha), LWA_ALPHA); - } - else - { - DWORD style = ::GetWindowLongW(vd->Hwnd, GWL_EXSTYLE) & ~WS_EX_LAYERED; - ::SetWindowLongW(vd->Hwnd, GWL_EXSTYLE, style); - } -} - -static float ImGui_ImplWin32_GetWindowDpiScale(ImGuiViewport* viewport) -{ - ImGui_ImplWin32_ViewportData* vd = (ImGui_ImplWin32_ViewportData*)viewport->PlatformUserData; - IM_ASSERT(vd->Hwnd != 0); - return ImGui_ImplWin32_GetDpiScaleForHwnd(vd->Hwnd); -} - -// FIXME-DPI: Testing DPI related ideas -static void ImGui_ImplWin32_OnChangedViewport(ImGuiViewport* viewport) -{ - (void)viewport; -#if 0 - ImGuiStyle default_style; - //default_style.WindowPadding = ImVec2(0, 0); - //default_style.WindowBorderSize = 0.0f; - //default_style.ItemSpacing.y = 3.0f; - //default_style.FramePadding = ImVec2(0, 0); - default_style.ScaleAllSizes(viewport->DpiScale); - ImGuiStyle& style = ImGui::GetStyle(); - style = default_style; -#endif -} - -static LRESULT CALLBACK ImGui_ImplWin32_WndProcHandler_PlatformWindow(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam) -{ - if (ImGui_ImplWin32_WndProcHandler(hWnd, msg, wParam, lParam)) - return true; - - if (ImGuiViewport* viewport = ImGui::FindViewportByPlatformHandle((void*)hWnd)) - { - switch (msg) - { - case WM_CLOSE: - viewport->PlatformRequestClose = true; - return 0; - case WM_MOVE: - viewport->PlatformRequestMove = true; - break; - case WM_SIZE: - viewport->PlatformRequestResize = true; - break; - case WM_MOUSEACTIVATE: - if (viewport->Flags & ImGuiViewportFlags_NoFocusOnClick) - return MA_NOACTIVATE; - break; - case WM_NCHITTEST: - // Let mouse pass-through the window. This will allow the backend to call io.AddMouseViewportEvent() correctly. (which is optional). - // The ImGuiViewportFlags_NoInputs flag is set while dragging a viewport, as want to detect the window behind the one we are dragging. - // If you cannot easily access those viewport flags from your windowing/event code: you may manually synchronize its state e.g. in - // your main loop after calling UpdatePlatformWindows(). Iterate all viewports/platform windows and pass the flag to your windowing system. - if (viewport->Flags & ImGuiViewportFlags_NoInputs) - return HTTRANSPARENT; - break; - } - } - - return DefWindowProc(hWnd, msg, wParam, lParam); -} - -static void ImGui_ImplWin32_InitPlatformInterface(bool platform_has_own_dc) -{ - WNDCLASSEX wcex; - wcex.cbSize = sizeof(WNDCLASSEX); - wcex.style = CS_HREDRAW | CS_VREDRAW | (platform_has_own_dc ? CS_OWNDC : 0); - wcex.lpfnWndProc = ImGui_ImplWin32_WndProcHandler_PlatformWindow; - wcex.cbClsExtra = 0; - wcex.cbWndExtra = 0; - wcex.hInstance = ::GetModuleHandle(nullptr); - wcex.hIcon = nullptr; - wcex.hCursor = nullptr; - wcex.hbrBackground = (HBRUSH)(COLOR_BACKGROUND + 1); - wcex.lpszMenuName = nullptr; - wcex.lpszClassName = _T("ImGui Platform"); - wcex.hIconSm = nullptr; - ::RegisterClassEx(&wcex); - - ImGui_ImplWin32_UpdateMonitors(); - - // Register platform interface (will be coupled with a renderer interface) - ImGuiPlatformIO& platform_io = ImGui::GetPlatformIO(); - platform_io.Platform_CreateWindow = ImGui_ImplWin32_CreateWindow; - platform_io.Platform_DestroyWindow = ImGui_ImplWin32_DestroyWindow; - platform_io.Platform_ShowWindow = ImGui_ImplWin32_ShowWindow; - platform_io.Platform_SetWindowPos = ImGui_ImplWin32_SetWindowPos; - platform_io.Platform_GetWindowPos = ImGui_ImplWin32_GetWindowPos; - platform_io.Platform_SetWindowSize = ImGui_ImplWin32_SetWindowSize; - platform_io.Platform_GetWindowSize = ImGui_ImplWin32_GetWindowSize; - platform_io.Platform_SetWindowFocus = ImGui_ImplWin32_SetWindowFocus; - platform_io.Platform_GetWindowFocus = ImGui_ImplWin32_GetWindowFocus; - platform_io.Platform_GetWindowMinimized = ImGui_ImplWin32_GetWindowMinimized; - platform_io.Platform_SetWindowTitle = ImGui_ImplWin32_SetWindowTitle; - platform_io.Platform_SetWindowAlpha = ImGui_ImplWin32_SetWindowAlpha; - platform_io.Platform_UpdateWindow = ImGui_ImplWin32_UpdateWindow; - platform_io.Platform_GetWindowDpiScale = ImGui_ImplWin32_GetWindowDpiScale; // FIXME-DPI - platform_io.Platform_OnChangedViewport = ImGui_ImplWin32_OnChangedViewport; // FIXME-DPI - - // Register main window handle (which is owned by the main application, not by us) - // This is mostly for simplicity and consistency, so that our code (e.g. mouse handling etc.) can use same logic for main and secondary viewports. - ImGuiViewport* main_viewport = ImGui::GetMainViewport(); - ImGui_ImplWin32_Data* bd = ImGui_ImplWin32_GetBackendData(); - ImGui_ImplWin32_ViewportData* vd = IM_NEW(ImGui_ImplWin32_ViewportData)(); - vd->Hwnd = bd->hWnd; - vd->HwndOwned = false; - main_viewport->PlatformUserData = vd; - main_viewport->PlatformHandle = (void*)bd->hWnd; -} - -static void ImGui_ImplWin32_ShutdownPlatformInterface() -{ - ::UnregisterClass(_T("ImGui Platform"), ::GetModuleHandle(nullptr)); - ImGui::DestroyPlatformWindows(); -} - -//--------------------------------------------------------------------------------------------------------- - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_win32.h b/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_win32.h deleted file mode 100644 index cebe661..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/imgui_impl_win32.h +++ /dev/null @@ -1,53 +0,0 @@ -// dear imgui: Platform Backend for Windows (standard windows API for 32-bits AND 64-bits applications) -// This needs to be used along with a Renderer (e.g. DirectX11, OpenGL3, Vulkan..) - -// Implemented features: -// [X] Platform: Clipboard support (for Win32 this is actually part of core dear imgui) -// [X] Platform: Mouse support. Can discriminate Mouse/TouchScreen/Pen. -// [X] Platform: Keyboard support. Since 1.87 we are using the io.AddKeyEvent() function. Pass ImGuiKey values to all key functions e.g. ImGui::IsKeyPressed(ImGuiKey_Space). [Legacy VK_* values will also be supported unless IMGUI_DISABLE_OBSOLETE_KEYIO is set] -// [X] Platform: Gamepad support. Enabled with 'io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad'. -// [X] Platform: Mouse cursor shape and visibility. Disable with 'io.ConfigFlags |= ImGuiConfigFlags_NoMouseCursorChange'. -// [X] Platform: Multi-viewport support (multiple windows). Enable with 'io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable'. - -// You can use unmodified imgui_impl_* files in your project. See examples/ folder for examples of using this. -// Prefer including the entire imgui/ repository into your project (either as a copy or as a submodule), and only build the backends you need. -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#pragma once -#include "imgui.h" // IMGUI_IMPL_API -#ifndef IMGUI_DISABLE - -IMGUI_IMPL_API bool ImGui_ImplWin32_Init(void* hwnd); -IMGUI_IMPL_API bool ImGui_ImplWin32_InitForOpenGL(void* hwnd); -IMGUI_IMPL_API void ImGui_ImplWin32_Shutdown(); -IMGUI_IMPL_API void ImGui_ImplWin32_NewFrame(); - -// Win32 message handler your application need to call. -// - Intentionally commented out in a '#if 0' block to avoid dragging dependencies on from this helper. -// - You should COPY the line below into your .cpp code to forward declare the function and then you can call it. -// - Call from your application's message handler. Keep calling your message handler unless this function returns TRUE. - -#if 0 -extern IMGUI_IMPL_API LRESULT ImGui_ImplWin32_WndProcHandler(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam); -#endif - -// DPI-related helpers (optional) -// - Use to enable DPI awareness without having to create an application manifest. -// - Your own app may already do this via a manifest or explicit calls. This is mostly useful for our examples/ apps. -// - In theory we could call simple functions from Windows SDK such as SetProcessDPIAware(), SetProcessDpiAwareness(), etc. -// but most of the functions provided by Microsoft require Windows 8.1/10+ SDK at compile time and Windows 8/10+ at runtime, -// neither we want to require the user to have. So we dynamically select and load those functions to avoid dependencies. -IMGUI_IMPL_API void ImGui_ImplWin32_EnableDpiAwareness(); -IMGUI_IMPL_API float ImGui_ImplWin32_GetDpiScaleForHwnd(void* hwnd); // HWND hwnd -IMGUI_IMPL_API float ImGui_ImplWin32_GetDpiScaleForMonitor(void* monitor); // HMONITOR monitor - -// Transparency related helpers (optional) [experimental] -// - Use to enable alpha compositing transparency with the desktop. -// - Use together with e.g. clearing your framebuffer with zero-alpha. -IMGUI_IMPL_API void ImGui_ImplWin32_EnableAlphaCompositing(void* hwnd); // HWND hwnd - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/backends/vulkan/generate_spv.sh b/app/jni/src/libultraship/extern/ImGui/backends/vulkan/generate_spv.sh deleted file mode 100755 index 948ef77..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/vulkan/generate_spv.sh +++ /dev/null @@ -1,6 +0,0 @@ -#!/bin/bash -## -V: create SPIR-V binary -## -x: save binary output as text-based 32-bit hexadecimal numbers -## -o: output file -glslangValidator -V -x -o glsl_shader.frag.u32 glsl_shader.frag -glslangValidator -V -x -o glsl_shader.vert.u32 glsl_shader.vert diff --git a/app/jni/src/libultraship/extern/ImGui/backends/vulkan/glsl_shader.frag b/app/jni/src/libultraship/extern/ImGui/backends/vulkan/glsl_shader.frag deleted file mode 100644 index ce7e6f7..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/vulkan/glsl_shader.frag +++ /dev/null @@ -1,14 +0,0 @@ -#version 450 core -layout(location = 0) out vec4 fColor; - -layout(set=0, binding=0) uniform sampler2D sTexture; - -layout(location = 0) in struct { - vec4 Color; - vec2 UV; -} In; - -void main() -{ - fColor = In.Color * texture(sTexture, In.UV.st); -} diff --git a/app/jni/src/libultraship/extern/ImGui/backends/vulkan/glsl_shader.vert b/app/jni/src/libultraship/extern/ImGui/backends/vulkan/glsl_shader.vert deleted file mode 100644 index 9425365..0000000 --- a/app/jni/src/libultraship/extern/ImGui/backends/vulkan/glsl_shader.vert +++ /dev/null @@ -1,25 +0,0 @@ -#version 450 core -layout(location = 0) in vec2 aPos; -layout(location = 1) in vec2 aUV; -layout(location = 2) in vec4 aColor; - -layout(push_constant) uniform uPushConstant { - vec2 uScale; - vec2 uTranslate; -} pc; - -out gl_PerVertex { - vec4 gl_Position; -}; - -layout(location = 0) out struct { - vec4 Color; - vec2 UV; -} Out; - -void main() -{ - Out.Color = aColor; - Out.UV = aUV; - gl_Position = vec4(aPos * pc.uScale + pc.uTranslate, 0, 1); -} diff --git a/app/jni/src/libultraship/extern/ImGui/docs/BACKENDS.md b/app/jni/src/libultraship/extern/ImGui/docs/BACKENDS.md deleted file mode 100644 index e5aa79b..0000000 --- a/app/jni/src/libultraship/extern/ImGui/docs/BACKENDS.md +++ /dev/null @@ -1,146 +0,0 @@ -_(You may browse this at https://github.com/ocornut/imgui/blob/master/docs/BACKENDS.md or view this file with any Markdown viewer)_ - -## Dear ImGui: Backends - -**The backends/ folder contains backends for popular platforms/graphics API, which you can use in -your application or engine to easily integrate Dear ImGui.** Each backend is typically self-contained in a pair of files: imgui_impl_XXXX.cpp + imgui_impl_XXXX.h. - -- The 'Platform' backends are in charge of: mouse/keyboard/gamepad inputs, cursor shape, timing, and windowing.
- e.g. Windows ([imgui_impl_win32.cpp](https://github.com/ocornut/imgui/blob/master/backends/imgui_impl_win32.cpp)), GLFW ([imgui_impl_glfw.cpp](https://github.com/ocornut/imgui/blob/master/backends/imgui_impl_glfw.cpp)), SDL2 ([imgui_impl_sdl2.cpp](https://github.com/ocornut/imgui/blob/master/backends/imgui_impl_sdl2.cpp)), etc. - -- The 'Renderer' backends are in charge of: creating atlas texture, and rendering imgui draw data.
- e.g. DirectX11 ([imgui_impl_dx11.cpp](https://github.com/ocornut/imgui/blob/master/backends/imgui_impl_dx11.cpp)), OpenGL/WebGL ([imgui_impl_opengl3.cpp](https://github.com/ocornut/imgui/blob/master/backends/imgui_impl_opengl3.cpp)), Vulkan ([imgui_impl_vulkan.cpp](https://github.com/ocornut/imgui/blob/master/backends/imgui_impl_vulkan.cpp)), etc. - -- For some high-level frameworks, a single backend usually handles both 'Platform' and 'Renderer' parts.
- e.g. Allegro 5 ([imgui_impl_allegro5.cpp](https://github.com/ocornut/imgui/blob/master/backends/imgui_impl_allegro5.cpp)). If you end up creating a custom backend for your engine, you may want to do the same. - -An application usually combines one Platform backend + one Renderer backend + main Dear ImGui sources. -For example, the [example_win32_directx11](https://github.com/ocornut/imgui/tree/master/examples/example_win32_directx11) application combines imgui_impl_win32.cpp + imgui_impl_dx11.cpp. There are 20+ examples in the [examples/](https://github.com/ocornut/imgui/blob/master/examples/) folder. See [EXAMPLES.MD](https://github.com/ocornut/imgui/blob/master/docs/EXAMPLES.md) for details. - -**Once Dear ImGui is setup and running, run and refer to `ImGui::ShowDemoWindow()` in imgui_demo.cpp for usage of the end-user API.** - - -### What are backends? - -Dear ImGui is highly portable and only requires a few things to run and render, typically: - - - Required: providing mouse/keyboard inputs (fed into the `ImGuiIO` structure). - - Required: uploading the font atlas texture into graphics memory. - - Required: rendering indexed textured triangles with a clipping rectangle. - - Extra features are opt-in, our backends try to support as many as possible: - - - Optional: custom texture binding support. - - Optional: clipboard support. - - Optional: gamepad support. - - Optional: mouse cursor shape support. - - Optional: IME support. - - Optional: multi-viewports support. - etc. - -This is essentially what each backend is doing + obligatory portability cruft. Using default backends ensure you can get all those features including the ones that would be harder to implement on your side (e.g. multi-viewports support). - -It is important to understand the difference between the core Dear ImGui library (files in the root folder) -and the backends which we are describing here (backends/ folder). - -- Some issues may only be backend or platform specific. -- You should be able to write backends for pretty much any platform and any 3D graphics API. - e.g. you can get creative and use software rendering or render remotely on a different machine. - - -### Integrating a backend - -See "Getting Started" section of [EXAMPLES.MD](https://github.com/ocornut/imgui/blob/master/docs/EXAMPLES.md) for more details. - - -### List of backends - -In the [backends/](https://github.com/ocornut/imgui/blob/master/backends) folder: - -List of Platforms Backends: - - imgui_impl_android.cpp ; Android native app API - imgui_impl_glfw.cpp ; GLFW (Windows, macOS, Linux, etc.) http://www.glfw.org/ - imgui_impl_osx.mm ; macOS native API (not as feature complete as glfw/sdl backends) - imgui_impl_sdl2.cpp ; SDL2 (Windows, macOS, Linux, iOS, Android) https://www.libsdl.org - imgui_impl_sdl3.cpp ; SDL3 (Windows, macOS, Linux, iOS, Android) https://www.libsdl.org (*EXPERIMENTAL UNTIL SDL3 IS RELEASED*) - imgui_impl_win32.cpp ; Win32 native API (Windows) - imgui_impl_glut.cpp ; GLUT/FreeGLUT (this is prehistoric software and absolutely not recommended today!) - -List of Renderer Backends: - - imgui_impl_dx9.cpp ; DirectX9 - imgui_impl_dx10.cpp ; DirectX10 - imgui_impl_dx11.cpp ; DirectX11 - imgui_impl_dx12.cpp ; DirectX12 - imgui_impl_metal.mm ; Metal (with ObjC) - imgui_impl_opengl2.cpp ; OpenGL 2 (legacy, fixed pipeline <- don't use with modern OpenGL context) - imgui_impl_opengl3.cpp ; OpenGL 3/4, OpenGL ES 2, OpenGL ES 3 (modern programmable pipeline) - imgui_impl_sdlrenderer2.cpp ; SDL_Renderer (optional component of SDL2 available from SDL 2.0.18+) - imgui_impl_sdlrenderer3.cpp ; SDL_Renderer (optional component of SDL3 available from SDL 3.0.0+) - imgui_impl_vulkan.cpp ; Vulkan - imgui_impl_wgpu.cpp ; WebGPU - -List of high-level Frameworks Backends (combining Platform + Renderer): - - imgui_impl_allegro5.cpp - -Emscripten is also supported! -The SDL+GL, GLFW+GL and SDL+WebGPU examples are all ready to build and run with Emscripten. - -### Backends for third-party frameworks, graphics API or other languages - -See https://github.com/ocornut/imgui/wiki/Bindings for the full list (e.g. Adventure Game Studio, Cinder, Cocos2d-x, Game Maker Studio2, Godot, LÖVE+LUA, Magnum, Monogame, Ogre, openFrameworks, OpenSceneGraph, SFML, Sokol, Unity, Unreal Engine and many others). - -### Recommended Backends - -If you are not sure which backend to use, the recommended platform/frameworks for portable applications: - -|Library |Website |Backend |Note | -|--------|--------|--------|-----| -| GLFW | https://github.com/glfw/glfw | imgui_impl_glfw.cpp | | -| SDL2 | https://www.libsdl.org | imgui_impl_sdl2.cpp | | -| Sokol | https://github.com/floooh/sokol | [util/sokol_imgui.h](https://github.com/floooh/sokol/blob/master/util/sokol_imgui.h) | Lower-level than GLFW/SDL | - - -### Using a custom engine? - -You will likely be tempted to start by rewrite your own backend using your own custom/high-level facilities...
-Think twice! - -If you are new to Dear ImGui, first try using the existing backends as-is. -You will save lots of time integrating the library. -You can LATER decide to rewrite yourself a custom backend if you really need to. -In most situations, custom backends have fewer features and more bugs than the standard backends we provide. -If you want portability, you can use multiple backends and choose between them either at compile time -or at runtime. - -**Example A**: your engine is built over Windows + DirectX11 but you have your own high-level rendering -system layered over DirectX11.
-Suggestion: try using imgui_impl_win32.cpp + imgui_impl_dx11.cpp first. -Once it works, if you really need it, you can replace the imgui_impl_dx11.cpp code with a -custom renderer using your own rendering functions, and keep using the standard Win32 code etc. - -**Example B**: your engine runs on Windows, Mac, Linux and uses DirectX11, Metal, and Vulkan respectively.
-Suggestion: use multiple generic backends! -Once it works, if you really need it, you can replace parts of backends with your own abstractions. - -**Example C**: your engine runs on platforms we can't provide public backends for (e.g. PS4/PS5, Switch), -and you have high-level systems everywhere.
-Suggestion: try using a non-portable backend first (e.g. win32 + underlying graphics API) to get -your desktop builds working first. This will get you running faster and get your acquainted with -how Dear ImGui works and is setup. You can then rewrite a custom backend using your own engine API... - -Generally: -It is unlikely you will add value to your project by creating your own backend. - -Also: -The [multi-viewports feature](https://github.com/ocornut/imgui/issues/1542) of the 'docking' branch allows -Dear ImGui windows to be seamlessly detached from the main application window. This is achieved using an -extra layer to the Platform and Renderer backends, which allows Dear ImGui to communicate platform-specific -requests such as: "create an additional OS window", "create a render context", "get the OS position of this -window" etc. See 'ImGuiPlatformIO' for details. -Supporting the multi-viewports feature correctly using 100% of your own abstractions is more difficult -than supporting single-viewport. -If you decide to use unmodified imgui_impl_XXXX.cpp files, you can automatically benefit from -improvements and fixes related to viewports and platform windows without extra work on your side. diff --git a/app/jni/src/libultraship/extern/ImGui/docs/CHANGELOG.txt b/app/jni/src/libultraship/extern/ImGui/docs/CHANGELOG.txt deleted file mode 100644 index f7f564c..0000000 --- a/app/jni/src/libultraship/extern/ImGui/docs/CHANGELOG.txt +++ /dev/null @@ -1,5633 +0,0 @@ -dear imgui -CHANGELOG - -This document holds the user-facing changelog that we also use in release notes. -We generally fold multiple commits pertaining to the same topic as a single entry. -Changes to backends are also included within the individual .cpp files of each backend. - -FAQ https://www.dearimgui.com/faq/ -RELEASE NOTES: https://github.com/ocornut/imgui/releases -WIKI https://github.com/ocornut/imgui/wiki -GETTING STARTED https://github.com/ocornut/imgui/wiki/Getting-Started -GLOSSARY https://github.com/ocornut/imgui/wiki/Glossary -ISSUES & SUPPORT https://github.com/ocornut/imgui/issues - -WHEN TO UPDATE? - -- Keeping your copy of Dear ImGui updated regularly is recommended. -- It is generally safe and recommended to sync to the latest commit in 'master' or 'docking' - branches. The library is fairly stable and regressions tends to be fixed fast when reported. - -HOW TO UPDATE? - -- Update submodule or copy/overwrite every file. -- About imconfig.h: - - You may modify your copy of imconfig.h, in this case don't overwrite it. - - or you may locally branch to modify imconfig.h and merge/rebase latest. - - or you may '#define IMGUI_USER_CONFIG "my_config_file.h"' globally from your build system to - specify a custom path for your imconfig.h file and instead not have to modify the default one. -- Read the `Breaking Changes` section (in imgui.cpp or here in the Changelog). -- If you have a problem with a missing function/symbols, search for its name in the code, there will likely be a comment about it. -- If you are copying this repository in your codebase, please leave the demo and documentations files in there, they will be useful. -- You may diff your previous Changelog with the one you just copied and read that diff. -- You may enable `IMGUI_DISABLE_OBSOLETE_FUNCTIONS` in imconfig.h to forcefully disable legacy names and symbols. - Doing it every once in a while is a good way to make sure you are not using obsolete symbols. Dear ImGui is in active development, - and API updates have been a little more frequent lately. They are documented below and in imgui.cpp and should not affect all users. -- Please report any issue! - - ------------------------------------------------------------------------ - VERSION 1.90 WIP (In Progress) ------------------------------------------------------------------------ - -Breaking changes: - - - Debug Tools: Renamed ShowStackToolWindow() ("Stack Tool") to ShowIDStackToolWindow() ("ID Stack Tool"), - as earlier name was misleading. Kept inline redirection function. (#4631) - - IO: Removed io.MetricsActiveAllocations introduced in 1.63, was displayed in Metrics and unlikely to - be accessed by end-user. Value still visible in the UI and easily to recompute from a delta. - - ListBox, Combo: Changed signature of "name getter" callback in old one-liner ListBox()/Combo() apis. - Before: - getter type: bool (*getter)(void* user_data, int idx, const char** out_text) - function: bool Combo(const char* label, int* current_item, bool (*getter)(void* user_data, int idx, const char** out_text), ...); - function: bool ListBox(const char* label, int* current_item, bool (*getting)(void* user_data, int idx, const char** out_text), ...); - After: - getter type: const char* (*getter)(void* user_data, int idx) - function: bool Combo(const char* label, int* current_item, const char* (*getter)(void* user_data, int idx), ...); - function: bool ListBox(const char* label, int* current_item, const char* (*getter)(void* user_data, int idx), ...); - Old type was unnecessarily complex and harder to wrap in e.g. a lambda. Kept inline redirection function (will obsolete). - - Commented out obsolete redirecting enums/functions that were marked obsolete two years ago: - - GetWindowContentRegionWidth() -> use GetWindowContentRegionMax().x - GetWindowContentRegionMin().x. - Consider that generally 'GetContentRegionAvail().x' is more useful. - - ImDrawCornerFlags_XXX -> use ImDrawFlags_RoundCornersXXX names. - Read 1.82 changelog for details + grep commented names in sources + . - - Commented out runtime support for hardcoded ~0 or 0x01..0x0F rounding flags values for - AddRect()/AddRectFilled()/PathRect()/AddImageRounded(). -> Use ImDrawFlags_RoundCornersXXX flags. - Read 1.82 Changelog for details. - -Other changes: - -- Tooltips: made using SetItemTooltip()/IsItemHovered(ImGuiHoveredFlags_ForTooltip) defaults to - activate tooltips on disabled items. This is done by adding ImGuiHoveredFlags_AllowWhenDisabled - to the default value of style.HoverFlagsForTooltipMouse/HoverFlagsForTooltipNav. (#1485) -- Nav: Tabbing always enable nav highlight when ImGuiConfigFlags_NavEnableKeyboard is set. - Previously was inconsistent and only enabled when stepping through a non-input item. - (#6802, #3092, #5759, #787) -- Separator(): Altered end-points to use more standard boundaries. (#205, #4787, #1643) - - Left position is always current cursor X position. - - Right position is always work-rect rightmost edge. - - Effectively means that: - - A separator in the root of a window will end up a little more distant from edges - than previously (essentially following WindowPadding instead of clipping edges). - - A separator inside a table cell end up a little distance from edges instead of - touching them (essentially following CellPadding instead of clipping edges). - - Matches tree indentation (was not the case before). - - Matches SeparatorText(). (#1643) - - Makes things correct inside groups without specific/hard-coded handling. (#205) - - Mostly legacy behavior when used inside old Columns(), as we favored that idiom back then, - only different is left position follows indentation level, to match calling a Separator() - inside or outside Columns(). -- Popups: clarified meaning of 'p_open != NULL' in BeginPopupModal() + set back user value - to false when popup is closed in ways other than clicking the close button. (#6900) -- Drag and Drop: Rework drop target highlight: reduce rectangle to its visible portion, and - then expand slightly. A full rectangle is always visible and it may protrude slightly. (#4281, #3272) -- Drag and Drop: Fixed submitting a tooltip from drop target location when using AcceptDragDropPayload() - with ImGuiDragDropFlags_AcceptNoPreviewTooltip and submitting a tooltip manually. -- TreeNode: Added ImGuiTreeNodeFlags_SpanAllColumns for use in tables. (#3151, #3565, #2451, #2438) -- Tables: - - Added angled headers support. You need to set ImGuiTableColumnFlags_AngledHeader on selected - columns and call TableAngledHeadersRow(). Added style.TableAngledHeadersAngle style option. - - Added ImGuiTableFlags_HighlightHoveredColumn flag, currently highlighting column header. - - Fixed an edge-case when no columns are visible + table scrollbar is visible + user - code is always testing return value of TableSetColumnIndex() to coarse clip. With an active - clipper it would have asserted. Without a clipper, the scrollbar range would be wrong. - - Request user to submit contents when outer host-window is requesting auto-resize, - so a scrolling table can contribute to initial window size. (#6510) - - Fixed subtle drawing overlap between borders in some situations. - - Fixed bottom-most and right-most outer border offset by one. (#6765, #3752) [@v-ein] - - Fixed top-most outer border being drawn with both TableBorderLight and TableBorderStrong - in some situations, causing the earlier to be visible underneath when alpha is not 1.0f. - - fixed right-clicking right-most section (past right-most column) from highlighting a column. -- TabBar: Fixed position of unsaved document marker (ImGuiTabItemFlags_UnsavedDocument) which was - accidentally offset in 1.89.9. (#6862) [@alektron] -- Fonts: 'float size_pixels' passed to AddFontXXX() functions is now rounded to lowest integer. - This is because our layout/font system currently doesn't fully support non-integer sizes. Until - it does, this has been a common pitfall leading to more or less subtle issues. (#3164, #3309, #6800) -- Fonts: Better assert during load when passing truncated font data or wrong data size. (#6822) -- Fonts: Ensure calling AddFontXXX function doesn't invalidates ImFont's ConfigData pointers - prior to building again. (#6825) -- Fonts, imgui_freetype: Fixed a warning and leak in IMGUI_ENABLE_FREETYPE_LUNASVG support. (#6842, #6591) -- InputTextMultiline: Fixed a crash pressing Down on last empty line of a multiline buffer. - (regression from 1.89.2, only happened in some states). (#6783, #6000) -- InputTextMultiline: Fixed Tabbing cycle leading to a situation where Enter key wouldn't - be accepted by the widget when navigation highlight is visible. (#6802, #3092, #5759, #787) -- BeginGroup(): Fixed a bug pushing line lower extent too far down when called after a call - to SameLine() followed by manual cursor manipulation. -- BeginCombo(): Added ImGuiComboFlags_WidthFitPreview flag. (#6881) [@mpv-enjoyer] -- BeginListBox(): Fixed not consuming SetNextWindowXXX data when returning false. -- Menus: Fixed a bug where activating an item in a child-menu and dragging mouse over the - parent-menu would erroneously close the child-menu. (Regression from 1.88). (#6869) -- MenuBar: Fixed an issue where layouting an item in the menu-bar would erroneously - register contents size in a way that would affect the scrolling layer. - Was most often noticable when using an horizontal scrollbar. (#6789) -- Misc: Most text functions also treat "%.*s" (along with "%s") specially to avoid formatting. (#3466, #6846) -- IO: Add extra keys to ImGuiKey enum: ImGuiKey_F13 to ImGuiKey_F24. (#6891, #4921) -- IO: Add extra keys to ImGuiKey enum: ImGuiKey_AppBack, ImGuiKey_AppForward. (#4921) -- IO: Setting io.WantSetMousePos ignores incoming MousePos events. (#6837, #228) [@bertaye] -- Debug Tools: Metrics: Added log of recent alloc/free calls. -- Debug Tools: Metrics: Added "Show groups rectangles" in tools. -- ImDrawList: Added AddEllipse(), AddEllipseFilled(), PathEllipticalArcTo(). (#2743) [@Doohl] -- ImVector: Added find_index() helper. -- Demo: Added "Drag and Drop -> Tooltip at target location" demo. -- Backends: GLFW: Clear emscripten's MouseWheel callback before shutdown. (#6790, #6096, #4019) [@halx99] -- Backends: GLFW: Added support for F13 to F24 function keys. (#6891) -- Backends: SDL2, SDL3: Added support for F13 to F24 function keys, AppBack, AppForward. (#6891) -- Backends: Win32: Added support for F13 to F24 function keys, AppBack, AppForward. (#6891) -- Backends: Win32: Added support for keyboard codepage conversion for when application - is compiled in MBCS mode and using a non-Unicode window. (#6785, #6782, #5725, #5961) [@sneakyevil] -- Backends: Win32: Synthesize key-down event on key-up for VK_SNAPSHOT / ImGuiKey_PrintScreen as Windows - doesn't emit it (same behavior as GLFW/SDL). (#6859) [@thedmd, @SuperWangKai] -- Backends: OpenGL3: rename symbols in our internal loader so that LTO compilation with another - copy of gl3w becomes possible. (#6875, #6668, #4445) [@nicolasnoble] -- Backends: OSX: Added support for F13 to F20 function keys. Support mapping F13 to PrintScreen. (#6891) -- Internals: Renamed ImFloor() to ImTrunc(). Renamed ImFloorSigned() to ImFloor(). (#6861) - -Docking+Viewports Branch: - -- Viewports: Fixed window inner clipping rectangle off by one when window is located on a monitor - with negative coordinates. While it is expected that other small issues with arise from this - situation, at the moment we are fixing the most noticeable one. (#6861, #2884) [@Vuhdo, @alektron] -- Docking: Fixed an issue leading to incorrect restoration of selected tab in dock nodes that - don't carry the currently focused window. (#2304) -- Docking: added ImGuiDockNodeFlags_NoUndocking. (#2999, #6823, #6780, #3492) -- Docking: renamed ImGuiDockNodeFlags_NoSplit to ImGuiDockNodeFlags_NoDockingSplit. -- Docking: renamed ImGuiDockNodeFlags_NoDockingInCentralNode to ImGuiDockNodeFlags_NoDockingOverCentralNode. -- Docking: Internals: renamed ImGuiDockNodeFlags_NoDockingSplitMe to ImGuiDockNodeFlags_NoDockingSplit. -- Docking: Fixed a bug where ClassId compare tests (when using SetNextWindowClass) on success would - prevent further filter from running, namely the one that prevent docking over a popup. -- Backends: GLFW: Fixed an assertion in situation where the WndProc handler is different between - main and secondary viewport (may happen due to third-party hooks). (#6889) -- Backends: DX9: Fixed incorrect assert triggering on reopening session with minimized windows. (#3424) - - ------------------------------------------------------------------------ - VERSION 1.89.9 (Released 2023-09-04) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.89.9 - -Breaking changes: - -- Clipper: Renamed IncludeRangeByIndices(), also called ForceDisplayRangeByIndices() - before 1.89.6, to IncludeItemsByIndex(). Kept inline redirection function. (#6424, #3841) - -Other changes: - -- Tables: Made it possible to use SameLine(0,0) after TableNextColumn() or - TableSetColumnIndex() in order to reuse line pos/height from previous cell. (#3740) -- Tables: Made it possible to change style.CellPadding.y between rows. (#3740) -- Nav, TreeNode: Pressing Left with ImGuiTreeNodeFlags_NavLeftJumpsBackHere now goes - through proper navigation logic: honor scrolling and selection. (#1079, #1131) -- Sliders: Fixed an integer overflow and div-by-zero in SliderInt() when - v_max=INT_MAX (#6675, #6679) [@jbarthelmes] -- Windows: Layout of Close/Collapse buttons uses style.ItemInnerSpacing.x between items, - stopped incorrectly using FramePadding in a way where hit-boxes could overlap when - setting large values. (#6749) -- TabBar, Style: added style.TabBarBorderSize and associated ImGuiStyleVar_TabBarBorderSize. - Tweaked rendering of that separator to allow thicker values. (#6820, #4859, #5022, #5239) -- InputFloat, SliderFloat, DragFloat: always turn both '.' and ',' into the current decimal - point character when using Decimal/Scientific character filter. (#6719, #2278) [@adamsepp] -- ColorEdit, ColorPicker: Manipulating options popup don't mark item as edited. (#6722) - (Note that they may still be marked as Active/Hovered.) -- Clipper: Added IncludeItemByIndex() helper to include a single item. (#6424, #3841) -- Clipper: Fixed a bug if attempt to force-include a range which matches an already - included range, clipper would end earlier. (#3841) -- ImDrawData: Fixed an issue where TotalVtxCount/TotalIdxCount does not match the sum - of individual ImDrawList's buffer sizes when a dimming/modal background is rendered. (#6716) -- ImDrawList: Automatically calling ChannelsMerge() if not done after a split. -- ImDrawList: Fixed OOB access in _CalcCircleAutoSegmentCount when passing excessively - large radius to AddCircle(). (#6657, #5317) [@EggsyCRO, @jdpatdiscord] -- IO: Exposed io.PlatformLocaleDecimalPoint to configure decimal point ('.' or ',') for - languages needing it. Should ideally be set to the value of '*localeconv()->decimal_point' - but our backends don't do it yet. (#6719, #2278) -- IO: Fixed io.AddMousePosEvent() and io.AddMouseButtonEvent() writing MouseSource to - wrong union section. Was semantically incorrect and accidentally had no side-effects - with default compiler alignment settings. (#6727) [@RickHuang2001] -- Misc: Made multiple calls to Render() during the same frame early out faster. -- Debug Tools: Metrics: Fixed "Drawlists" section and per-viewport equivalent - appearing empty (regression in 1.89.8). -- Demo: Reorganized "Examples" menu. -- Demo: Tables: Demonstrate using SameLine() between cells. (#3740) -- Demo: Tables: Demonstrate altering CellPadding.y between rows. (#3740) -- Demo: Custom Rendering: Demonstrate out-of-order rendering using ImDrawListSplitter. -- Backends: SDL2,SDL3: added ImGui_ImplSDL2_InitForOther()/ImGui_ImplSDL3_InitForOther() - for consistency (matching GLFW backend) and as most initialization paths don't actually - need to care about rendering backend. -- Examples: Emscripten+WebGPU: Fixed WGPUInstance creation process + use preferred - framebuffer format. (#6640, #6748) [@smileorigin] - -Docking+Viewports Branch: - -- Docking: when io.ConfigDockingWithShift is enabled, staying stationary while moving - a window displays an help tooltip to increase affordance. (#6709, #4643) - - ------------------------------------------------------------------------ - VERSION 1.89.8 (Released 2023-08-01) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.89.8 - -Breaking changes: - -- IO: Obsoleted io.ClearInputCharacters() (added in 1.47) as it now ambiguous - and often incorrect/misleading considering the existence of a higher-level - input queue. This is automatically cleared by io.ClearInputsKeys(). (#4921) -- ImDrawData: CmdLists[] array is now owned, changed from 'ImDrawList**' to - 'ImVector'. Majority of users shouldn't be affected, but you - cannot compare to NULL nor reassign manually anymore. - Instead use AddDrawList(). Allocation count are identical. (#6406, #4879, #1878) - -Other changes: - -- Fonts: ImFontConfig::OversampleH now defaults to 2 instead of 3, since the - quality increase is largely minimal. -- Fonts, imgui_freetype: Added support to render OpenType SVG fonts using lunasvg. - Requires enabling IMGUI_ENABLE_FREETYPE_LUNASVG along with IMGUI_ENABLE_FREETYPE, - and providing headers/libraries for lunasvg. (#6591, #6607) [@sakiodre] -- ImDrawData: CmdLists[] array is now an ImVector<> owned by ImDrawData rather - than a pointer to internal state. - - This makes it easier for user to create their own or append to an existing draw data. - Added a ImDrawData::AddDrawList() helper function to do that. (#6406, #4879, #1878) - - This makes it easier to perform a deep-swap instead of a deep-copy, as array - ownership is now clear. (#6597, #6475, #6167, #5776, #5109, #4763, #3515, #1860) - - Syntax and allocation count are otherwise identical. -- Fixed CTRL+Tab dimming background assert when target window has a callback - in the last ImDrawCmd. (#4857, #5937) -- IsItemHovered: Fixed ImGuiHoveredFlags_ForTooltip for Keyboard/Gamepad navigation, - got broken prior to 1.89.7 due to an unrelated change making flags conflict. (#6622, #1485) -- InputText: Fixed a case where deactivation frame would write to underlying - buffer or call CallbackResize although unnecessary, in a frame where the - return value was false. -- Tables: fixed GetContentRegionAvail().y report not taking account of lower cell - padding or of using ImGuiTableFlags_NoHostExtendY. Not taking it into account - would make the idiom of creating vertically bottom-aligned content (e.g. a child - window) inside a table make the parent window erroneously have a scrollbar. (#6619) -- Tables: fixed calculation of multi-instance shared decoration/scrollbar width of - scrolling tables, to avoid flickering width variation when resizing down a table - hosting a child window. (#5920, #6619) -- Scrollbar: layout needs to take account of window border size, so a border size - will slightly reduce scrollbar size. Generally we tried to make it that window - border size has no incidence on layout but this can't work with thick borders. (#2522) -- IO: Added io.ClearEventsQueue() to clear incoming inputs events. (#4921) - May be useful in conjunction with io.ClearInputsKeys() if you need to clear - both current inputs state and queued events (e.g. when using blocking native - dialogs such as Windows's ::MessageBox() or ::GetOpenFileName()). -- IO: Changed io.ClearInputsKeys() specs to also clear current frame character buffer - (what now obsoleted io.ClearInputCharacters() did), as this is effectively the - desirable behavior. -- Misc: Added IMGUI_DISABLE_STB_SPRINTF_IMPLEMENTATION config macro to disable - stb_sprintf implementation when using IMGUI_USE_STB_SPRINTF. (#6626) [@septag] -- Misc: Avoid stb_textedit.h reincluding string.h while in a namespace, which - messes up with building with Clang Modules. (#6653, #4791) [@JohelEGP] -- Demo: Better showcase use of SetNextItemAllowOverlap(). (#6574, #6512, #3909, #517) -- Demo: Showcase a few more InputText() flags. -- Backends: Made all backends sources files support global IMGUI_DISABLE. (#6601) -- Backends: GLFW: Revert ignoring mouse data on GLFW_CURSOR_DISABLED as it can be used - differently. User may set ImGuiConfigFlags_NoMouse if desired. (#5625, #6609) [@scorpion-26] -- Backends: WebGPU: Update for changes in Dawn. (#6602, #6188) [@williamhCode] -- Examples: Vulkan: Creating minimal descriptor pools to fit only what is needed by - example. (#6642) [@SaschaWillem] - -Docking+Viewports Branch: - -- Docking, Style: resizing separators use same colors as window borders (ImGuiCol_Border) - for consistency. With default styles it doesn't make a big difference. (#2522) [@rmitton] - In the future if we promote using thick value for inner/outer docking padding we may - need to introduce new colors for it. -- Docking: added style.DockingSeparatorSize, ImGuiStyleVar_DockingSeparatorSize. Now - also scaled by style.ScaleAllSizes(). (#3481, #4721, #2522) [@PossiblyAShrub, @wobbier] -- Docking: fixed rendering of docked-window scrollbar above outer border. (#2522) - - ------------------------------------------------------------------------ - VERSION 1.89.7 (Released 2023-07-04) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.89.7 - -Breaking changes: - -- Moved io.HoverDelayShort/io.HoverDelayNormal to style.HoverDelayShort/style.HoverDelayNormal. - As the fields were added in 1.89 and expected to be left unchanged by most users, or only - tweaked once during app initialisation, we are exceptionally accepting the breakage. - Majority of users should not even notice. -- Overlapping items: (#6512, #3909, #517) - - Added 'SetNextItemAllowOverlap()' (called before an item) as a replacement for using - 'SetItemAllowOverlap()' (called after an item). This is roughly equivalent to using the - legacy 'SetItemAllowOverlap()' call (public API) + ImGuiButtonFlags_AllowOverlap (internal). - - Obsoleted 'SetItemAllowOverlap()': it didn't and couldn't work reliably since 1.89 (2022-11-15), - and relied on ambiguously defined design. Use 'SetNextItemAllowOverlap()' before item instead. - - Selectable, TreeNode: When using ImGuiSelectableFlags_AllowOverlap/ImGuiTreeNodeFlags_AllowOverlap - and holding item held, overlapping widgets won't appear as hovered. (#6512, #3909) - While this fixes a common small visual issue, it also means that calling IsItemHovered() - after a non-reactive elements - e.g. Text() - overlapping an active one may fail if you don't - use IsItemHovered(ImGuiHoveredFlags_AllowWhenBlockedByActiveItem). (#6610) - - Renamed 'ImGuiTreeNodeFlags_AllowItemOverlap' to 'ImGuiTreeNodeFlags_AllowOverlap'. - - Renamed 'ImGuiSelectableFlags_AllowItemOverlap' to 'ImGuiSelectableFlags_AllowOverlap' - - Kept redirecting enums (will obsolete). - -Other changes: - -- Tooltips/IsItemHovered() related changes: - - Tooltips: Added SetItemTooltip() and BeginItemTooltip() functions. - They are shortcuts for the common idiom of using IsItemHovered(). - - SetItemTooltip("Hello") == if (IsItemHovered(ImGuiHoveredFlags_Tooltip)) { SetTooltip("Hello"); } - - BeginItemTooltip() == IsItemHovered(ImGuiHoveredFlags_Tooltip) && BeginTooltip() - The newly added ImGuiHoveredFlags_Tooltip is meant to facilitate standardizing - mouse hovering delays and rules for a given application. - The previously common idiom of using 'if (IsItemHovered()) { SetTooltip(...); }' - won't use delay or stationary test. - - IsItemHovered: Added ImGuiHoveredFlags_Stationary to require mouse being - stationary when hovering a new item. Added style.HoverStationaryDelay (~0.15 sec). - Once the mouse has been stationary once the state is preserved for same item. (#1485) - - IsItemHovered: Added ImGuiHoveredFlags_ForTooltip as a shortcut for pulling flags - from style.HoverFlagsForTooltipMouse or style.HoverFlagsForTooltipNav depending - on active inputs (#1485) - - style.HoverFlagsForTooltipMouse defaults to 'ImGuiHoveredFlags_Stationary | ImGuiHoveredFlags_DelayShort' - - style.HoverFlagsForTooltipNav defaults to 'ImGuiHoveredFlags_NoSharedDelay | ImGuiHoveredFlags_DelayNormal'. - - Tooltips: Tweak default offset for non-drag and drop tooltips so underlying items - isn't covered as much. (Match offset for drag and drop tooltips) - - IsItemHovered: Tweaked default value of style.HoverDelayNormal from 0.30 to 0.40, - Tweaked default value of style.HoverDelayShort from 0.10 to 0.15. (#1485) - - IsItemHovered: Added ImGuiHoveredFlags_AllowWhenOverlappedByWindow to ignore window-overlap only. - Option ImGuiHoveredFlags_AllowWhenOverlapped now expand into a combination of both - _AllowWhenOverlappedByWindow + _AllowWhenOverlappedByItem, matching old behavior. -- Overlapping items: (#6512, #3909, #517) - - Most item types should now work with SetNextItemAllowOverlap(). (#6512, #3909, #517) - - Fixed first frame of an overlap highlighting underlying item if previous frame didn't hover anything. - - IsItemHovered: Changed to return false when querying an item using AllowOverlap mode which - is being overlapped. Added ImGuiHoveredFlags_AllowWhenOverlappedByItem to opt-out. (#6512, #3909, #517) -- IsWindowHovered: Added support for ImGuiHoveredFlags_Stationary. -- IsWindowHovered, IsItemHovered: Assert when passed any unsupported flags. -- Tables: Fixed a regression in 1.89.6 leading to the first column of tables with either - ScrollX or ScrollY flags from being impossible to resize. (#6503) -- CollapsingHeader/TreeNode: Fixed text padding when using _Framed+_Leaf flags. (#6549) [@BobbyAnguelov] -- InputText: Fixed not returning true when buffer is cleared while using the - ImGuiInputTextFlags_EscapeClearsAll flag. (#5688, #2620) -- InputText: Fixed a crash on deactivating a ReadOnly buffer. (#6570, #6292, #4714) -- InputText: ImGuiInputTextCallbackData::InsertChars() accept (NULL,NULL) range, in order to conform - to common idioms (e.g. passing .data(), .data() + .size() from a null string). (#6565, #6566, #3615) -- Combo: Made simple/legacy Combo() function not returns true when picking already selected item. - This is consistent with other widgets. If you need something else, you can use BeginCombo(). (#1182) -- Clipper: Rework inner logic to allow functioning with a zero-clear constructor. - This is order to facilitate usage for language bindings (e.g cimgui or dear_binding) - where user may not be calling a constructor manually. (#5856) -- Drag and Drop: Apply default behavior of drag source not reporting itself as hovered - at lower-level, so DragXXX, SliderXXX, InputXXX, Plot widgets are fulfilling it. - (Behavior doesn't apply when ImGuiDragDropFlags_SourceNoDisableHover is set). -- Modals: In the case of nested modal, made sure that focused or appearing windows are - moved below the lowest blocking modal (rather than the highest one). (#4317) -- GetKeyName(): Fixed assert with ImGuiMod_XXX values when IMGUI_DISABLE_OBSOLETE_KEYIO is set. -- Debug Tools: Added 'io.ConfigDebugIniSettings' option to save .ini data with extra - comments. Currently mainly for inspecting Docking .ini data, but makes saving slower. -- Demo: Added more developed "Widgets->Tooltips" section. (#1485) -- Backends: OpenGL3: Fixed support for glBindSampler() backup/restore on ES3. (#6375, #6508) [@jsm174] -- Backends: OpenGL3: Fixed erroneous use glGetIntegerv(GL_CONTEXT_PROFILE_MASK) on contexts - lower than 3.2. (#6539, #6333) [@krumelmonster] -- Backends: Vulkan: Added optional support for VK_KHR_dynamic_rendering (Vulkan 1.3+) in the - backend for applications using it. User needs to set 'init_info->UseDynamicRendering = true' - and 'init_info->ColorAttachmentFormat'. RenderPass becomes unused. (#5446, #5037) [@spnda, @cmarcelo] -- Backends: GLFW: Accept glfwGetTime() not returning a monotonically increasing value. - This seems to happens on some Windows setup when peripherals disconnect, and is likely - to also happen on browser+Emscripten. Matches similar 1.89.4 fix in SDL backend. (#6491) -- Examples: Win32+OpenGL3: Changed DefWindowProc() to DefWindowProcW() to match other examples - and support the example app being compiled without UNICODE. (#6516, #5725, #5961, #5975) [@yenixing] - -Docking+Viewports Branch: - -- Viewports+Docking: Fixed extraneous viewport+platform-window recreation in various - combination of showing or hiding windows, docking with/without split, undocking. - While with some backends and without OS decorations, some extraneous window recreation - were visibly not noticeable, they would typically become noticeable when enabling - OS decorations on those windows (e.g. Windows title bar fade-in/animation). -- Viewports: Closing a viewport via OS/platform means (e.g. OS close button or task-bar menu), - mark all windows in this viewport as closed. -- Docking: Fixed one-frame flickering on reappearing windows binding to a dock node - where a later-submitted window was already bound. -- Docking: Fixed dragging from title-bar empty space (regression from 1.88 related to - keeping ID alive when calling low-level ButtonBehavior() directly). (#5181, #2645) -- Docking: [Internal] DockBuilderDockWindow() API calls don't clear docking order - if the target node is same as existing one. -- Backends: Win32: Added support for changing ParentViewportID after viewport creation. - - ------------------------------------------------------------------------ - VERSION 1.89.6 (Released 2023-05-31) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.89.6 - -Breaking changes: - -- Clipper: Commented out obsolete redirection constructor which was marked obsolete in 1.79: - 'ImGuiListClipper(int items_count, float items_height)' --> Use 'ImGuiListClipper() + clipper.Begin()'. -- Clipper: Renamed ForceDisplayRangeByIndices() to IncludeRangeByIndices(), kept - inline redirection function (introduced in 1.86 and rarely used). (#6424, #3841) -- Commented out obsolete/redirecting functions that were marked obsolete more than two years ago: - - ListBoxHeader() -> use BeginListBox() - - ListBoxFooter() -> use EndListBox() - - Note how two variants of ListBoxHeader() existed. Check commented versions in imgui.h for refeence. -- Backends: SDL_Renderer: Renamed 'imgui_impl_sdlrenderer.h/cpp' to 'imgui_impl_sdlrenderer2.h/cpp', - in order to accomodate for upcoming SDL3 and change in its SDL_Renderer API. (#6286) -- Backends: GLUT: Removed call to ImGui::NewFrame() from ImGui_ImplGLUT_NewFrame(). - It needs to be called from the main app loop, like with every other backends. (#6337) [@GereonV] - -Other changes: - -- Window: Fixed resizing from upper border when io.ConfigWindowsMoveFromTitleBarOnly is set. (#6390) -- Tables: Fixed a small miscalculation in TableHeader() leading to an empty tooltip - showing when a sorting column has no visible name. (#6342) [@lukaasm] -- Tables: Fixed command merging when compiling with VS2013 (one array on stack was not - initialized on VS2013. Unsure if due to a bug or UB/standard conformance). (#6377) -- InputText: Avoid setting io.WantTextInputNextFrame during the deactivation frame. - (#6341) [@lukaasm] -- Drag, Sliders: if the format string doesn't contain any %, CTRL+Click to input text will - use the default format specifier for the type. Allow display/input of raw value when using - "enums" patterns (display label instead of value) + allow using when value is hidden. (#6405) -- Nav: Record/restore preferred position on each given axis after a movement on that axis, - then score movement on the other axis using this as a bias. This allows going up and down - between e.g. a large header spanning horizontal space and three-ways-columns, landing - on the same column as before. -- Nav: Fixed navigation within tables/columns where item boundaries goes beyond columns limits, - unclipped bounding boxes would interfere with other columns. (#2221) [@zzzyap, @ocornut] -- Nav: Fixed CTRL+Tab into a root window with only childs with _NavFlattened flags - erroneously initializing default nav layer to menu layer. -- Menus: Fixed an issue when opening a menu hierarchy in a given menu-bar would allow - opening another via simple hovering. (#3496, #4797) -- Fonts: Fixed crash when merging fonts and the first font has no valid glyph. (#6446) [@JaedanC] -- Fonts: Fixed crash when manually specifying an EllipsisChar that doesn't exist. (#6480) -- Misc: Added ImVec2 unary minus operator. (#6368) [@Koostosh] -- Debug Tools: Debug Log: Fixed not parsing 0xXXXXXXXX values for geo-locating on mouse - hover hover when the identifier is at the end of the line. (#5855) -- Debug Tools: Added 'io.ConfigDebugIgnoreFocusLoss' option to disable 'io.AddFocusEvent(false)' - handling. May facilitate interactions with a debugger when focus loss leads to clearing - inputs data. (#4388, #4921) -- Backends: Clear bits sets io.BackendFlags on backend Shutdown(). (#6334, #6335] [@GereonV] - Potentially this would facilitate switching runtime backend mid-session. -- Backends: Win32: Added ImGui_ImplWin32_InitForOpenGL() to facilitate combining raw - Win32/Winapi with OpenGL. (#3218) -- Backends: OpenGL3: Restore front and back polygon mode separately when supported - by context (Desktop 3.0, 3.1, or 3.2+ with compat bit). (#6333) [@GereonV] -- Backends: OpenGL3: Support for glBindSampler() backup/restore on ES3. (#6375) [@jsm174] -- Backends: SDL3: Fixed build on Emscripten/iOS/Android. (#6391) [@jo-codegirl] -- Backends: SDLRenderer3: Added SDL_Renderer for SDL3 backend. (#6286) [@Carcons, @ocornut] -- Examples: Added native Win32+OpenGL3 example. We don't recommend using this setup but we - provide it for completeness. (#3218, #5170, #6086, #2772, #2600, #2359, #2022, #1553) [@learn-more] -- Examples: Vulkan: Use integrated GPU if nothing else is available. (#6359) [@kimidaisuki22] -- Examples: DX9, DX10, DX11: Queue framebuffer resize instead of processing in WM_SIZE, - as some drivers tends to only cleanup after existing the native resize modal loop. (#6374) -- Examples: Added SDL3+SDL_Renderer example. (#6286) -- Examples: Updated all Visual Studio projects and batches to use /utf-8 argument. - -Docking+Viewports Branch: - -- Viewports: Fixed platform-side focus (e.g. Alt+Tab) from leading to accidental - closure of Modal windows. Regression from 1.89.5. (#6357, #6299) -- Viewports: Fixed loss of imgui-side focus when dragging a secondary viewport back in - main viewport, due to platform-side handling changes. Regression from 1.89.5 (#6299) -- Viewports: Avoid applying imgui-side focus when focus change is due to a viewport - destruction. Fixes erroneous popup closure on closing a previous popup. (#6462, #6299) -- Viewports: Added void* ImGuiPlatformMonitor::PlatformHandle field (backend-dependant), - for usage by user code. -- Backends: GLFW: Preserve monitor list when there are no monitor, may briefly - happen when recovering from macOS sleeping mode. (#5683) [@Guistac] -- Backends: SDL2: Update monitor list when receiving a display event. (#6348) - Note however that SDL2 currently doesn't have an event for a DPI/Scaling change, - so monitor data won't be updated in this situation. -- Backends: SDL3: Update monitor list when receiving a display event. (#6348) - - ------------------------------------------------------------------------ - VERSION 1.89.5 (Released 2023-04-13) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.89.5 - -Other changes: - -- InputText: Reworked prev/next-word behavior to more closely match Visual Studio - text editor. Include '.' as a delimiter and alter varying subtle behavior with how - blanks and separators are treated when skipping words. (#6067) [@ajweeks] -- InputText: Fixed a tricky edge case, ensuring value is always written back on the - frame where IsItemDeactivated() returns true, in order to allow usage without user - retaining underlying data. While we don't really want to encourage user not retaining - underlying data, in the absence of a "late commit" behavior/flag we understand it may - be desirable to take advantage of this trick. (#4714) -- Drag, Sliders: Fixed parsing of text input when '+' or '#' format flags are used - in the format string. (#6259) [@idbrii] -- Nav: Made Ctrl+Tab/Ctrl+Shift+Tab windowing register ownership to held modifier so - it doesn't interfere with other code when remapping those actions. (#4828, #3255, #5641) -- Nav: Made PageUp/PageDown/Home/End navigation also scroll parent windows when - necessary to make the target location fully visible (same as e.g. arrow keys). -- ColorEdit: Fixed shading of S/V triangle in Hue Wheel mode. (#5200, #6254) [@jamesthomasgriffin] -- TabBar: Tab-bars with ImGuiTabBarFlags_FittingPolicyScroll can be scrolled with - horizontal mouse-wheel (or Shift + WheelY). (#2702) -- Rendering: Using adaptive tessellation for RadioButton, ColorEdit preview circles, - Windows Close and Collapse Buttons. -- ButtonBehavior: Fixed an edge case where changing widget type/behavior while active - and using same id could lead to an assert. (#6304) -- Misc: Fixed ImVec2 operator[] violating aliasing rules causing issue with Intel C++ - compiler. (#6272) [@BayesBug] -- IO: Input queue trickling adjustment for touch screens. (#2702, #4921) - This fixes single-tapping to move simulated mouse and immediately click on a widget - that is using the ImGuiButtonFlags_AllowItemOverlap policy. - - This only works if the backend can distinguish TouchScreen vs Mouse. - See 'Demo->Tools->Metrics->Inputs->Mouse Source' to verify. - - Fixed tapping on BeginTabItem() on a touch-screen. (#2702) - - Fixed tapping on CollapsingHeader() with a close button on a touch-screen. - - Fixed tapping on TreeNode() using ImGuiTreeNodeFlags_AllowItemOverlap on a touch-screen. - - Fixed tapping on Selectable() using ImGuiSelectableFlags_AllowItemOverlap on a touch-screen. - - Fixed tapping on TableHeader() on a touch-screen. -- IO: Added io.AddMouseSourceEvent() and ImGuiMouseSource enum. This is to allow backend to - specify actual event source between Mouse/TouchScreen/Pen. (#2702, #2334, #2372, #3453, #5693) -- IO: Fixed support for calling io.AddXXXX functions from inactive context (wrongly - advertised as supported in 1.89.4). (#6199, #6256, #5856) [@cfillion] -- Backends: OpenGL3: Fixed GL loader crash when GL_VERSION returns NULL. (#6154, #4445, #3530) -- Backends: OpenGL3: Properly restoring "no shader program bound" if it was the case prior to - running the rendering function. (#6267, #6220, #6224) [@BrunoLevy] -- Backends: Win32: Added support for io.AddMouseSourceEvent() to discriminate Mouse/TouchScreen/Pen. (#2334, #2702) -- Backends: SDL2/SDL3: Added support for io.AddMouseSourceEvent() to discriminate Mouse/TouchScreen. - This is relying on SDL passing SDL_TOUCH_MOUSEID in the event's 'which' field. (#2334, #2702) -- Backends: SDL2/SDL3: Avoid calling SDL_StartTextInput()/SDL_StopTextInput() as they actually - block text input input and don't only pertain to IME. It's unclear exactly what their relation - is to other IME function such as SDL_SetTextInputRect(). (#6306, #6071, #1953) -- Backends: GLFW: Added support on Win32 only for io.AddMouseSourceEvent() to discriminate - Mouse/TouchScreen/Pen. (#2334, #2702) -- Backends: Android: Added support for io.AddMouseSourceEvent() to discriminate Mouse/TouchScreen/Pen. - (#6315) [@PathogenDavid] -- Backends: OSX: Added support for io.AddMouseSourceEvent() to discriminate Mouse/Pen. - (#6314) [@PathogenDavid] -- Backends: WebGPU: Align buffers. Use WGSL shaders instead of SPIR-V. Add gamma uniform. (#6188) [@eliemichel] -- Backends: WebGPU: Reorganized to store data in io.BackendRendererUserData like other backends. -- Examples: Vulkan: Fixed validation errors with newer VulkanSDK by explicitly querying and enabling - "VK_KHR_get_physical_device_properties2", "VK_KHR_portability_enumeration", and - VK_INSTANCE_CREATE_ENUMERATE_PORTABILITY_BIT_KHR. (#6109, #6172, #6101) -- Examples: Windows: Added 'misc/debuggers/imgui.natstepfilter' file to all Visual Studio projects, - now that VS 2022 17.6 Preview 2 support adding Debug Step Filter spec files into projects. -- Examples: SDL3: Updated for latest WIP SDL3 branch. (#6243) -- TestSuite: Added variety of new regression tests and improved/amended existing ones - in imgui_test_engine/ repo. [@PathogenDavid, @ocornut] - -Docking+Viewports Branch: - -- Viewports: Setting focus from Platform/OS (e.g. via decoration, or Alt-Tab) sets corresponding - focus at Dear ImGui level (generally last focused window in the viewport). (#6299) -- Docking: Fixed using GetItemXXX() or IsItemXXX() functions after a DockSpace(). (#6217) -- Backends: GLFW: Fixed key modifiers handling on secondary viewports. (#6248, #6034) [@aiekick] -- Backends: GLFW: Fixed Emscripten erroneously enabling multi-viewport support, leading to assert. (#5683) -- Backends: SDL2/SDL3: Fixed IME text input rectangle position with viewports. (#6071, #1953) -- Backends: SDL3: Fixed for compilation with multi-viewports. (#6255) [@P3RK4N] - - ------------------------------------------------------------------------ - VERSION 1.89.4 (Released 2023-03-14) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.89.4 - -Breaking Changes: - -- Renamed PushAllowKeyboardFocus()/PopAllowKeyboardFocus() to PushTabStop()/PopTabStop(). - Kept inline redirection functions (will obsolete). -- Moved the optional "courtesy maths operators" implementation from imgui_internal.h in imgui.h. - Even though we encourage using your own maths types and operators by setting up IM_VEC2_CLASS_EXTRA, - it has been frequently requested by people to use our own. We had an opt-in define which was - previously fulfilled by imgui_internal.h. It is now fulfilled by imgui.h. (#6164, #6137, #5966, #2832) - OK: #define IMGUI_DEFINE_MATH_OPERATORS / #include "imgui.h" / #include "imgui_internal.h" - Error: #include "imgui.h" / #define IMGUI_DEFINE_MATH_OPERATORS / #include "imgui_internal.h" - Added a dedicated compile-time check message to help diagnose this. -- Tooltips: Added 'bool' return value to BeginTooltip() for API consistency. - Please only submit contents and call EndTooltip() if BeginTooltip() returns true. - In reality the function will _currently_ always return true, but further changes down the - line may change this, best to clarify API sooner. Updated demo code accordingly. -- Commented out redirecting enums/functions names that were marked obsolete two years ago: - - ImGuiSliderFlags_ClampOnInput -> use ImGuiSliderFlags_AlwaysClamp - - ImGuiInputTextFlags_AlwaysInsertMode -> use ImGuiInputTextFlags_AlwaysOverwrite - - ImDrawList::AddBezierCurve() -> use ImDrawList::AddBezierCubic() - - ImDrawList::PathBezierCurveTo() -> use ImDrawList::PathBezierCubicCurveTo() - -Other changes: - -- Nav: Tabbing now cycles through all items when ImGuiConfigFlags_NavEnableKeyboard is set. - (#3092, #5759, #787) - While this was generally desired and requested by many, note that its addition means - that some types of UI may become more fastidious to use TAB key with, if the navigation - cursor cycles through too many items. You can mark items items as not tab-spottable: - - Public API: PushTabStop(false) / PopTabStop() - - Internal: PushItemFlag(ImGuiItemFlags_NoTabStop, true); - - Internal: Directly pass ImGuiItemFlags_NoTabStop to ItemAdd() for custom widgets. -- Nav: Tabbing/Shift-Tabbing can more reliably be used to step out of an item that is not - tab-stoppable. (#3092, #5759, #787) -- Nav: Made Enter key submit the same type of Activation event as Space key, - allowing to press buttons with Enter. (#5606) - (Enter emulates a "prefer text input" activation vs. - Space emulates a "prefer tweak" activation which is to closer to gamepad controls). -- Nav: Fixed an issue with Gamepad navigation when the movement lead to a scroll and - frame time > repeat rate. Triggering a new move request on the same frame as a move - result lead to an incorrect calculation and loss of navigation id. (#6171) -- Nav: Fixed SetItemDefaultFocus() from not scrolling when item is partially visible. - (#2814, #2812) [@DomGries] -- Tables: Fixed an issue where user's Y cursor movement within a hidden column would - have side-effects. -- IO: Lifted constraint to call io.AddEventXXX functions from current context. (#4921, #5856, #6199) -- InputText: Fixed not being able to use CTRL+Tab while an InputText() using Tab - for completion or text data is active (regression from 1.89). -- Drag and Drop: Fixed handling of overlapping targets when smaller one is submitted - before and can accept the same data type. (#6183). -- Drag and Drop: Clear drag and drop state as soon as delivery is accepted in order to - avoid interferences. (#5817, #6183) [@DimaKoltun] -- Debug Tools: Added io.ConfigDebugBeginReturnValueOnce / io.ConfigDebugBeginReturnValueLoop - options to simulate Begin/BeginChild returning false to facilitate debugging user behavior. -- Demo: Updated to test return value of BeginTooltip(). -- Backends: OpenGL3: Fixed restoration of a potentially deleted OpenGL program. If an active - program was pending deletion, attempting to restore it would error. (#6220, #6224) [@Cyphall] -- Backends: Win32: Use WM_NCMOUSEMOVE / WM_NCMOUSELEAVE to track mouse positions over - non-client area (e.g. OS decorations) when app is not focused. (#6045, #6162) -- Backends: SDL2, SDL3: Accept SDL_GetPerformanceCounter() not returning a monotonically - increasing value. (#6189, #6114, #3644) [@adamkewley] -- Backends: GLFW: Avoid using glfwGetError() and glfwGetGamepadState() on Emscripten, which - recently updated its GLFW emulation layer to GLFW 3.3 without supporting those. (#6240) -- Examples: Android: Fixed example build for Gradle 8. (#6229, #6227) [@duddel] -- Examples: Updated all examples application to enable ImGuiConfigFlags_NavEnableKeyboard - and ImGuiConfigFlags_NavEnableGamepad by default. (#787) -- Internals: Misc tweaks to facilitate applying an explicit-context patch. (#5856) [@Dragnalith] - ------------------------------------------------------------------------ - VERSION 1.89.3 (Released 2023-02-14) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.89.3 - -Breaking Changes: - -- Backends+Examples: SDL2: renamed all unnumbered references to "sdl" to "sdl2". - This is in prevision for the future release of SDL3 and its associated backend. (#6146) - - imgui_impl_sdl.cpp -> imgui_impl_sdl2.cpp - - imgui_impl_sdl.h -> imgui_impl_sdl2.h - - example_sdl_xxxx/ -> example_sdl2_xxxx/ (folders and projects) - -Other changes: - -- SeparatorText(): Added SeparatorText() widget. (#1643) [@phed, @ocornut] - - Added to style: float SeparatorTextBorderSize. - - Added to style: ImVec2 SeparatorTextAlign, SeparatorTextPadding. -- Tables: Raised max Columns count from 64 to 512. (#6094, #5305, #4876, #3572) - The previous limit was due to using 64-bit integers but we moved to bits-array - and tweaked the system enough to ensure no performance loss. -- Tables: Solved an ID conflict issue with multiple-instances of a same table, - due to how unique table instance id was generated. (#6140) [@ocornut, @rodrigorc] -- Inputs, Scrolling: Made horizontal scroll wheel and horizontal scroll direction consistent - across backends/os. (#4019, #6096, #1463) [@PathogenDavid, @ocornut, @rokups] - - Clarified that 'wheel_y > 0.0f' scrolls Up, 'wheel_y > 0.0f' scrolls Down. - Clarified that 'wheel_x > 0.0f' scrolls Left, 'wheel_x > 0.0f' scrolls Right. - - Backends: Fixed horizontal scroll direction for Win32 and SDL backends. (#4019) - - Shift+WheelY support on non-OSX machines was already correct. (#2424, #1463) - (whereas on OSX machines Shift+WheelY turns into WheelX at the OS level). - - If you use a custom backend, you should verify horizontal wheel direction. - - Axises are flipped by OSX for mouse & touch-pad when 'Natural Scrolling' is on. - - Axises are flipped by Windows for touch-pad when 'Settings->Touchpad->Down motion scrolls up' is on. - - You can use 'Demo->Tools->Debug Log->IO" to visualize values submitted to Dear ImGui. - - Known issues remaining with Emscripten: - - The magnitude of wheeling values on Emscripten was improved but isn't perfect. (#6096) - - When running the Emscripten app on a Mac with a mouse, SHIFT+WheelY doesn't turn into WheelX. - This is because we don't know that we are running on Mac and apply our own Shift+swapping - on top of OSX' own swapping, so wheel axises are swapped twice. Emscripten apps may need - to find a way to detect this and set io.ConfigMacOSXBehaviors manually (if you know a way - let us know!), or offer the "OSX-style behavior" option to their user. -- Window: Avoid rendering shapes for hidden resize grips. -- Text: Fixed layouting of wrapped-text block skipping successive empty lines, - regression from the fix in 1.89.2. (#5720, #5919) -- Text: Fixed clipping of single-character "..." ellipsis (U+2026 or U+0085) when font - is scaled. Scaling wasn't taken into account, leading to ellipsis character straying - slightly out of its expected boundaries. (#2775) -- Text: Tweaked rendering of three-dots "..." ellipsis variant. (#2775, #4269) -- InputText: Added support for Ctrl+Delete to delete up to end-of-word. (#6067) [@ajweeks] - (Not adding Super+Delete to delete to up to end-of-line on OSX, as OSX doesn't have it) -- InputText: On OSX, inhibit usage of Alt key to toggle menu when active (used for work skip). -- Menus: Fixed layout of MenuItem()/BeginMenu() when label contains a '\n'. (#6116) [@imkcy9] -- ColorEdit, ColorPicker: Fixed hue/saturation preservation logic from interfering with - the displayed value (but not stored value) of others widgets instances. (#6155) -- PlotHistogram, PlotLines: Passing negative sizes honor alignment like other widgets. -- Combo: Allow SetNextWindowSize() to alter combo popup size. (#6130) -- Fonts: Assert that in each GlyphRanges[] pairs first is <= second. -- ImDrawList: Added missing early-out in AddPolyline() and AddConvexPolyFilled() when - color alpha is zero. -- Misc: Most text functions treat "%s" as a shortcut to no-formatting. (#3466) -- Misc: Tolerate zero delta-time under Emscripten as backends are imprecise in their - values for io.DeltaTime, and browser features such as "privacy.resistFingerprinting=true" - can exacerbate that. (#6114, #3644) -- Backends: OSX: Fixed scroll/wheel scaling for devices emitting events with - hasPreciseScrollingDeltas==false (e.g. non-Apple mices). -- Backends: Win32: flipping WM_MOUSEHWHEEL horizontal value to match other backends and - offer consistent horizontal scrolling direction. (#4019) -- Backends: SDL2: flipping SDL_MOUSEWHEEL horizontal value to match other backends and - offer consistent horizontal scrolling direction. (#4019) -- Backends: SDL2: Removed SDL_MOUSEWHEEL value clamping. (#4019, #6096, #6081) -- Backends: SDL2: Added support for SDL 2.0.18+ preciseX/preciseY mouse wheel data - for smooth scrolling as reported by SDL. (#4019, #6096) -- Backends: SDL2: Avoid calling SDL_SetCursor() when cursor has not changed, as the function - is surprisingly costly on Mac with latest SDL (already fixed in SDL latest trunk). (#6113) -- Backends: SDL2: Implement IME handler to call SDL_SetTextInputRect()/SDL_StartTextInput(). - It will only works with SDL 2.0.18+ if your code calls 'SDL_SetHint(SDL_HINT_IME_SHOW_UI, "1")' - prior to calling SDL_CreateWindow(). Updated all examples accordingly. (#6071, #1953) -- Backends: SDL3: Added experimental imgui_impl_sdl3.cpp backend. (#6146) [@dovker, @ocornut] - SDL 3.0.0 has not yet been released, so it is possible that its specs/api will change before - release. This backend is provided as a convenience for early adopters etc. We don't recommend - switching to SDL3 before it is released. -- Backends: GLFW: Registering custom low-level mouse wheel handler to get more accurate - scrolling impulses on Emscripten. (#4019, #6096) [@ocornut, @wolfpld, @tolopolarity] -- Backends: GLFW: Added ImGui_ImplGlfw_SetCallbacksChainForAllWindows() to instruct backend - to chain callbacks even for secondary viewports/windows. User callbacks may need to test - the 'window' parameter. (#6142) -- Backends: OpenGL3: Fixed GL loader compatibility with 2.x profiles. (#6154, #4445, #3530) [@grauw] -- Backends: WebGPU: Fixed building for latest WebGPU specs (remove implicit layout generation). - (#6117, #4116, #3632) [@tonygrue, @bfierz] -- Examples: refactored SDL2+GL and GLFW+GL examples to compile with Emscripten. - (#2492, #2494, #3699, #3705) [@ocornut, @nicolasnoble] - The dedicated example_emscripten_opengl3/ has been removed. -- Examples: Added SDL3+GL experimental example. (#6146) -- Examples: Win32: Fixed examples using RegisterClassW() since 1.89 to also call - DefWindowProcW() instead of DefWindowProc() so that title text are correctly converted - when application is compiled without /DUNICODE. (#5725, #5961, #5975) [@markreidvfx] -- Examples: SDL2+SDL_Renderer: Added call to SDL_RenderSetScale() to fix display on a - Retina display (albeit lower-res as our other unmodified examples). (#6121, #6065, #5931). - -Docking+Viewports Branch: - -- Backends: GLFW: Handle unsupported glfwGetVideoMode() for Emscripten. (#6096) - - ------------------------------------------------------------------------ - VERSION 1.89.2 (Released 2023-01-05) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.89.2 - -All changes: - -- Tables, Nav, Scrolling: fixed scrolling functions and focus tracking with frozen rows and - frozen columns. Windows now have a better understanding of outer/inner decoration sizes, - which should later lead us toward more flexible uses of menu/status bars. (#5143, #3692) -- Tables, Nav: frozen columns are not part of menu layer and can be crossed over. (#5143, #3692) -- Tables, Columns: fixed cases where empty columns may lead to empty ImDrawCmd. (#4857, #5937) -- Tables: fixed matching width of synchronized tables (multiple tables with same id) when only - some instances have a vertical scrollbar and not all. (#5920) -- Fixed cases where CTRL+Tab or Modal can occasionally lead to the creation of ImDrawCmd with - zero triangles, which would makes the render loop of some backends assert (e.g. Metal with - debugging, Allegro). (#4857, #5937) -- Inputs, IO: reworked ImGuiMod_Shortcut to redirect to Ctrl/Super at runtime instead of - compile-time, being consistent with our support for io.ConfigMacOSXBehaviors and making it - easier for bindings generators to process that value. (#5923, #456) -- Inputs, Scrolling: better selection of scrolling window when hovering nested windows - and when backend/OS is emitting dual-axis wheeling inputs (typically touch pads on macOS). - We now select a primary axis based on recent events, and select a target window based on it. - We expect this behavior to be further improved/tweaked. (#3795, #4559) [@ocornut, @folays] -- InputText: fixed cursor navigation when pressing Up Arrow on the last character of a - multiline buffer which doesn't end with a carriage return. (#6000) -- Text: fixed layouting of wrapped-text block when the last source line is above the - clipping region. Regression added in 1.89. (#5720, #5919) -- Misc: added GetItemID() in public API. It is not often expected that you would use this, - but it is useful for Shortcut() and upcoming owner-aware input functions which wants to - be implemented with public API. -- Fonts: imgui_freetype: fixed a packing issue which in some occurrences would prevent large - amount of glyphs from being packed correctly. (#5788, #5829) -- Fonts: added a 'void* UserData' field in ImFontAtlas, as a convenience for use by - applications using multiple font atlases. -- Demo: simplified "Inputs" section, moved contents to Metrics->Inputs. -- Debug Tools: Metrics: added "Inputs" section, moved from Demo for consistency. -- Misc: fixed parameters to IMGUI_DEBUG_LOG() not being dead-stripped when building - with IMGUI_DISABLE_DEBUG_TOOLS is used. (#5901) [@Teselka] -- Misc: fixed compile-time detection of SSE features on MSVC 32-bits builds. (#5943) [@TheMostDiligent] -- Examples: DirectX10, DirectX11: try WARP software driver if hardware driver is not available. (#5924, #5562) -- Backends: GLFW: Fixed mods state on Linux when using Alt-GR text input (e.g. German keyboard layout), which - could lead to broken text input. Revert a 2022/01/17 change were we resumed using mods provided by GLFW, - turns out they are faulty in this specific situation. (#6034) -- Backends: Allegro5: restoring using al_draw_indexed_prim() when Allegro version is >= 5.2.5. (#5937) [@Espyo] -- Backends: Vulkan: Fixed sampler passed to ImGui_ImplVulkan_AddTexture() not being honored as we were using - an immutable sampler. (#5502, #6001, #914) [@martin-ejdestig, @rytisss] - -Docking+Viewports Branch: - -- Docking: Internals: fixed DockBuilderCopyDockSpace() crashing when windows not in the - remapping list are docked on the left or top side of a split. (#6035) -- Docking: fixed DockSpace() with ImGuiDockNodeFlags_KeepAliveOnly marking current window - as written to, even if it doesn't technically submit an item. This allow using KeepAliveOnly - from any window location. (#6037) -- Backends: OSX: fixed typo in ImGui_ImplOSX_GetWindowSize that would cause issues when resiing - from OS decorations, if they are enabled on secondary viewports. (#6009) [@sivu] -- Backends: Metal: fixed secondary viewport rendering. (#6015) [@dmirty-kuzmenko] - - ------------------------------------------------------------------------ - VERSION 1.89.1 (Released 2022-11-24) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.89.1 - -Other changes: - -- Scrolling, Focus: fixed SetKeyboardFocusHere()/SetItemDefaultFocus() during a window-appearing - frame (and associated lower-level functions e.g. ScrollToRectEx()) from not centering item. (#5902) -- Inputs: fixed moving a window or drag and dropping from preventing input-owner-unaware code - from accessing keys. (#5888, #4921, #456) -- Inputs: fixed moving a window or drag and dropping from capturing mods. (#5888, #4921, #456) -- Layout: fixed End()/EndChild() incorrectly asserting if users manipulates cursor position - inside a collapsed/culled window and IMGUI_DISABLE_OBSOLETE_FUNCTIONS is enabled. (#5548, #5911) -- Combo: fixed selected item (marked with SetItemDefaultFocus()) from not being centered when - the combo window initially appears. (#5902). -- ColorEdit: fixed label overlapping when using style.ColorButtonPosition == ImGuiDir_Left to - move the color button on the left side (regression introduced in 1.88 WIP 2022/02/28). (#5912) -- Drag and Drop: fixed GetDragDropPayload() returning a non-NULL value if a drag source is - active but a payload hasn't been submitted yet. This is convenient to detect new payload - from within a drag source handler. (#5910, #143) -- Backends: GLFW: cancel out errors emitted by glfwGetKeyName() when a name is missing. (#5908) -- Backends: WebGPU: fixed validation error with default depth buffer settings. (#5869, #5914) [@kdchambers] - -Docking+Viewports Branch: - -- Viewports: Fixed collapsed windows setting ImGuiViewportFlags_NoRendererClear without - making title bar color opaque, leading to potential texture/fb garbage being visible. - Right now as we don't fully support transparent viewports (#2766), so we turn that - 'TitleBgCollapsed' color opaque just lke we do for 'WindowBG' on uncollapsed windows. - - ------------------------------------------------------------------------ - VERSION 1.89 (Released 2022-11-15) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.89 - -Breaking changes: - -- Layout: Obsoleted using SetCursorPos()/SetCursorScreenPos() to extend parent window/cell boundaries. (#5548) - This relates to when moving the cursor position beyond current boundaries WITHOUT submitting an item. - - Previously this would make the window content size ~200x200: - Begin(...) + SetCursorScreenPos(GetCursorScreenPos() + ImVec2(200,200)) + End(); - - Instead, please submit an item: - Begin(...) + SetCursorScreenPos(GetCursorScreenPos() + ImVec2(200,200)) + Dummy(ImVec2(0,0)) + End(); - - Alternative: - Begin(...) + Dummy(ImVec2(200,200)) + End(); - Content size is now only extended when submitting an item. - With '#define IMGUI_DISABLE_OBSOLETE_FUNCTIONS' this will now be detected and assert. - Without '#define IMGUI_DISABLE_OBSOLETE_FUNCTIONS' this will silently be fixed until we obsolete it. - (This incorrect pattern has been mentioned or suggested in: #4510, #3355, #1760, #1490, #4152, #150, - threads have been amended to refer to this issue). -- Inputs: ImGuiKey is now a typed enum, allowing ImGuiKey_XXX symbols to be named in debuggers. (#4921) - This will require uses of legacy backend-dependent indices to be casted, e.g. - - with imgui_impl_glfw: IsKeyPressed(GLFW_KEY_A) -> IsKeyPressed((ImGuiKey)GLFW_KEY_A); - - with imgui_impl_win32: IsKeyPressed('A') -> IsKeyPressed((ImGuiKey)'A') - - etc. however if you are upgrading code you might as well use the backend-agnostic IsKeyPressed(ImGuiKey_A) now. -- Renamed and merged keyboard modifiers key enums and flags into a same set: (#4921, #456) - - ImGuiKey_ModCtrl and ImGuiModFlags_Ctrl -> ImGuiMod_Ctrl - - ImGuiKey_ModShift and ImGuiModFlags_Shift -> ImGuiMod_Shift - - ImGuiKey_ModAlt and ImGuiModFlags_Alt -> ImGuiMod_Alt - - ImGuiKey_ModSuper and ImGuiModFlags_Super -> ImGuiMod_Super - Kept inline redirection enums (will obsolete). - This change simplifies a few things, reduces confusion, and will facilitate upcoming - shortcut/input ownership apis. - - The ImGuiKey_ModXXX were introduced in 1.87 and mostly used by backends. - - The ImGuiModFlags_XXX have been exposed in imgui.h but not really used by any public api, - only by third-party extensions. They were however subject to a recent rename - (ImGuiKeyModFlags_XXX -> ImGuiModFlags_XXX) and we are exceptionally commenting out - the older ImGuiKeyModFlags_XXX names ahead of obsolescence schedule to reduce confusion - and because they were not meant to be used anyway. -- Removed io.NavInputs[] and ImGuiNavInput enum that were used to feed gamepad inputs. - Basically 1.87 already obsoleted them from the backend's point of view, but internally - our navigation code still used this array and enum, so they were still present. - Not anymore! (#4921, #4858, #787, #1599, #323) - Transition guide: - - Official backends from 1.87+ -> no issue. - - Official backends from 1.60 to 1.86 -> will build and convert gamepad inputs, unless IMGUI_DISABLE_OBSOLETE_KEYIO is defined. Need updating! - - Custom backends not writing to io.NavInputs[] -> no issue. - - Custom backends writing to io.NavInputs[] -> will build and convert gamepad inputs, unless IMGUI_DISABLE_OBSOLETE_KEYIO is defined. Need fixing! - - TL;DR: Backends should call io.AddKeyEvent()/io.AddKeyAnalogEvent() with ImGuiKey_GamepadXXX values instead of filling io.NavInput[]. - The ImGuiNavInput enum was essentially 1.60's attempt to combine keyboard and gamepad inputs with named - semantic, but the additional indirection and copy added complexity and got in the way of other - incoming work. User's code (other than backends) should not be affected, unless you have custom - widgets intercepting navigation events via the named enums (in which case you can upgrade your code). -- DragInt()/SliderInt(): Removed runtime patching of invalid "%f"/"%.0f" types of format strings. - This was obsoleted in 1.61 (May 2018). See 1.61 changelog for details. -- Changed signature of ImageButton() function: (#5533, #4471, #2464, #1390) - - Added 'const char* str_id' parameter + removed 'int frame_padding = -1' parameter. - - Old signature: bool ImageButton(ImTextureID tex_id, ImVec2 size, ImVec2 uv0 = ImVec2(0,0), ImVec2 uv1 = ImVec2(1,1), int frame_padding = -1, ImVec4 bg_col = ImVec4(0,0,0,0), ImVec4 tint_col = ImVec4(1,1,1,1)); - - used the ImTextureID value to create an ID. This was inconsistent with other functions, led to ID conflicts, and caused problems with engines using transient ImTextureID values. - - had a FramePadding override which was inconsistent with other functions and made the already-long signature even longer. - - New signature: bool ImageButton(const char* str_id, ImTextureID tex_id, ImVec2 size, ImVec2 uv0 = ImVec2(0,0), ImVec2 uv1 = ImVec2(1,1), ImVec4 bg_col = ImVec4(0,0,0,0), ImVec4 tint_col = ImVec4(1,1,1,1)); - - requires an explicit identifier. You may still use e.g. PushID() calls and then pass an empty identifier. - - always uses style.FramePadding for padding, to be consistent with other buttons. You may use PushStyleVar() to alter this. - - As always we are keeping a redirection function available (will obsolete later). -- Removed the bizarre legacy default argument for 'TreePush(const void* ptr = NULL)'. (#1057) - Must always pass a pointer value explicitly, NULL/nullptr is ok but require cast, e.g. TreePush((void*)nullptr); - If you used TreePush() replace with TreePush((void*)NULL); -- Removed support for 1.42-era IMGUI_DISABLE_INCLUDE_IMCONFIG_H / IMGUI_INCLUDE_IMCONFIG_H. (#255) - They only made sense before we could use IMGUI_USER_CONFIG. - -Other Changes: - -- Popups & Modals: fixed nested Begin() inside a popup being erroneously input-inhibited. - While it is unusual, you can nest a Begin() inside a popup or modal, it is occasionally - useful to achieve certain things (e.g. to implement suggestion popups #718, #4461). -- Inputs: Standard widgets now claim for key/button ownership and test for them. - - Fixes scenario where e.g. a Popup with a Selectable() reacting on mouse down - (e.g. double click) closes, and behind it is another window with an item reacting - on mouse up. Previously this would lead to both items reacting, now the item in the - window behind won't react on the mouse up since the mouse button ownership has already - been claimed earlier. - - Internals: There are MANY more aspects to this changes. Added experimental/internal APIs - to allow handling input/shorting routing and key ownership. Things will be moved into - public APIs over time. For now this release is a way to test the solidity of underlying - systems while letting early adopters adopters toy with internals. - (#456, #2637, #2620, #2891, #3370, #3724, #4828, #5108, #5242, #5641) -- Scrolling: Tweak mouse-wheel locked window timer so it is shorter but also gets reset - whenever scrolling again. Modulate for small (sub-pixel) amounts. (#2604) -- Scrolling: Mitigated issue where multi-axis mouse-wheel inputs (usually from touch pad - events) are incorrectly locking scrolling in a parent window. (#4559, #3795, #2604) -- Scrolling: Exposed SetNextWindowScroll() in public API. Useful to remove a scrolling - delay in some situations where e.g. windows need to be synched. (#1526) -- InputText: added experimental io.ConfigInputTextEnterKeepActive feature to make pressing - Enter keep the input active and select all text. -- InputText: numerical fields automatically accept full-width characters (U+FF01..U+FF5E) - by converting them to half-width (U+0021..U+007E). -- InputText: added ImGuiInputTextFlags_EscapeClearsAll flag: first press on Escape clears - text if any, second press deactivate the InputText(). (#5688, #2620) -- InputText: added support for shift+click style selection. (#5619) [@procedural] -- InputText: clarified that callbacks cannot modify buffer when using the ReadOnly flag. -- InputText: fixed minor one-frame selection glitch when reverting with Escape. -- ColorEdit3: fixed id collision leading to an assertion. (#5707) -- IsItemHovered: Added ImGuiHoveredFlags_DelayNormal and ImGuiHoveredFlags_DelayShort flags, - allowing to introduce a shared delay for tooltip idioms. The delays are respectively - io.HoverDelayNormal (default to 0.30f) and io.HoverDelayShort (default to 0.10f). (#1485) -- IsItemHovered: Added ImGuiHoveredFlags_NoSharedDelay to disable sharing delays between items, - so moving from one item to a nearby one will requires delay to elapse again. (#1485) -- Tables: activating an ID (e.g. clicking button inside) column doesn't prevent columns - output flags from having ImGuiTableColumnFlags_IsHovered set. (#2957) -- Tables,Columns: fixed a layout issue where SameLine() prior to a row change would set the - next row in such state where subsequent SameLine() would move back to previous row. -- Tabs: Fixed a crash when closing multiple windows (possible with docking only) with an - appended TabItemButton(). (#5515, #3291) [@rokups] -- Tabs: Fixed shrinking policy leading to infinite loops when fed unrounded tab widths. (#5652) -- Tabs: Fixed shrinking policy sometimes erroneously making right-most tabs stray a little out - bar boundaries (bug in 1.88). (#5652). -- Tabs: Enforcing minimum size of 1.0f, fixed asserting on zero-tab widths. (#5572) -- Window: Fixed a potential crash when appending to a child window. (#5515, #3496, #4797) [@rokups] -- Window: Fixed an issue where uncollapsed a window would show a scrollbar for a frame. -- Window: Auto-fit size takes account of work rectangle (menu bars eating from viewport). (#5843) -- Window: Fixed position not being clamped while auto-resizing (fixes appearing windows without - .ini data from moving for a frame when using io.ConfigWindowsMoveFromTitleBarOnly). (#5843) -- IO: Added ImGuiMod_Shortcut which is ImGuiMod_Super on Mac and ImGuiMod_Ctrl otherwise. (#456) -- IO: Added ImGuiKey_MouseXXX aliases for mouse buttons/wheel so all operations done on ImGuiKey - can apply to mouse data as well. (#4921) -- IO: Filter duplicate input events during the AddXXX() calls. (#5599, #4921) -- IO: Fixed AddFocusEvent(false) to also clear MouseDown[] state. (#4921) -- Menus: Fixed incorrect sub-menu parent association when opening a menu by closing another. - Among other things, it would accidentally break part of the closing heuristic logic when moving - towards a sub-menu. (#2517, #5614). [@rokups] -- Menus: Fixed gaps in closing logic which would make child-menu erroneously close when crossing - the gap between a menu item inside a window and a child-menu in a secondary viewport. (#5614) -- Menus: Fixed using IsItemHovered()/IsItemClicked() on BeginMenu(). (#5775) -- Menus, Popups: Experimental fix for issue where clicking on an open BeginMenu() item called from - a window which is neither a popup neither a menu used to incorrectly close and reopen the menu - (the fix may have side-effect and is labelld as experimental as we may need to revert). (#5775) -- Menus, Nav: Fixed keyboard/gamepad navigation occasionally erroneously landing on menu-item - in parent window when the parent is not a popup. (#5730) -- Menus, Nav: Fixed not being able to close a menu with Left arrow when parent is not a popup. (#5730) -- Menus, Nav: Fixed using left/right navigation when appending to an existing menu (multiple - BeginMenu() call with same names). (#1207) -- Menus: Fixed a one-frame issue where SetNextWindowXXX data are not consumed by a BeginMenu() - returning false. -- Nav: Fixed moving/resizing window with gamepad or keyboard when running at very high framerate. -- Nav: Pressing Space/GamepadFaceDown on a repeating button uses the same repeating rate as a mouse hold. -- Nav: Fixed an issue opening a menu with Right key from a non-menu window. -- Text: Fixed wrapped-text not doing a fast-forward on lines above the clipping region, - which would result in an abnormal number of vertices created (was slower and more likely to - asserts with 16-bits ImDrawVtx). (#5720) -- Fonts: Added GetGlyphRangesGreek() helper for Greek & Coptic glyph range. (#5676, #5727) [@azonenberg] -- ImDrawList: Not using alloca() anymore, lift single polygon size limits. (#5704, #1811) - - Note: now using a temporary buffer stored in ImDrawListSharedData. - This change made it more visible than you cannot append to multiple ImDrawList from multiple - threads if they share the same ImDrawListSharedData. Previously it was a little more likely - for this to "accidentally" work, but was already incorrect. (#6167) -- Platform IME: [Windows] Removed call to ImmAssociateContextEx() leading to freeze on some setups. - (#2589, #5535, #5264, #4972) -- Misc: better error reporting for PopStyleColor()/PopStyleVar() + easier to recover. (#1651) -- Misc: io.Framerate moving average now converge in 60 frames instead of 120. (#5236, #4138) -- Debug Tools: Debug Log: Visually locate items when hovering a 0xXXXXXXXX value. (#5855) -- Debug Tools: Debug Log: Added 'IO' and 'Clipper' events logging. (#5855) -- Debug Tools: Metrics: Visually locate items when hovering a 0xXXXXXXXX value (in most places). -- Debug Tools: Item Picker: Mouse button can be changed by holding Ctrl+Shift, making it easier - to use the Item Picker in e.g. menus. (#2673) -- Docs: Fixed various typos in comments and documentations. (#5649, #5675, #5679) [@tocic, @lessigsx] -- Demo: Improved "Constrained-resizing window" example, more clearly showcase aspect-ratio. (#5627) -- Demo: Added more explicit "Center window" mode to "Overlay example". (#5618) -- Demo: Fixed Log & Console from losing scrolling position with Auto-Scroll when child is clipped. (#5721) -- Examples: Added all SDL examples to default VS solution. -- Examples: Win32: Always use RegisterClassW() to ensure windows are Unicode. (#5725) -- Examples: Android: Enable .ini file loading/saving into application internal data folder. (#5836) [@rewtio] -- Backends: GLFW: Honor GLFW_CURSOR_DISABLED by not setting mouse position. (#5625) [@scorpion-26] -- Backends: GLFW: Add glfwGetError() call on GLFW 3.3 to inhibit missing mouse cursor errors. (#5785) [@mitchellh] -- Backends: SDL: Disable SDL 2.0.22 new "auto capture" which prevents drag and drop across windows - (e.g. for multi-viewport support) and don't capture mouse when drag and dropping. (#5710) -- Backends: Win32: Convert WM_CHAR values with MultiByteToWideChar() when window class was - registered as MBCS (not Unicode). (#5725, #1807, #471, #2815, #1060) [@or75, @ocornut] -- Backends: OSX: Fixed mouse inputs on flipped views. (#5756) [@Nemirtingas] -- Backends: OSX: Fixed mouse coordinate before clicking on the host window. (#5842) [@maezawa-akira] -- Backends: OSX: Fixes to support full app creation in C++. (#5403) [@stack] -- Backends: OpenGL3: Reverted use of glBufferSubData(), too many corruptions issues were reported, - and old leaks issues seemingly can't be reproed with Intel drivers nowadays (revert earlier changes). - (#4468, #4504, #3381, #2981, #4825, #4832, #5127). -- Backends: Metal: Use __bridge for ARC based systems. (#5403) [@stack] -- Backends: Metal: Add dispatch synchronization. (#5447) [@luigifcruz] -- Backends: Metal: Update deprecated property 'sampleCount'->'rasterSampleCount'. (#5603) [@dcvz] -- Backends: Vulkan: Added experimental ImGui_ImplVulkan_RemoveTexture() for api symetry. (#914, #5738). -- Backends: WebGPU: fixed rendering when a depth buffer is enabled. (#5869) [@brainlag] - -Docking+Viewports Branch: - -- Docking: Fixed incorrect focus highlight on docking node when focusing a menu. (#5702) -- Docking, Nav: Fixed using gamepad/keyboard navigation not being able enter menu layer when - it only contained the standard Collapse/Close buttons and no actual menu. (#5463, #4792) -- Docking: Fixed regression introduced in v1.87 when docked window content not rendered - while switching between with CTRL+Tab. [@rokups] -- Docking: Fixed amending into an existing tab bar from rendering invisible items. (#5515) -- Docking: Made spacing between dock nodes not a dropping gap. When hovering it only - outer-docking drop markers are visible. -- Docking+Viewports: Fixed undocking window node causing parent viewports to become unresponsive - in certain situation (e.g. hidden tab bar). (#5503) [@rokups] -- Backends: SDL: Fixed building backend under non-OSX Apple targets (e.g. iPhone). (#5665) -- Backends: SDL: Fixed drag'n drop crossing a viewport border losing mouse coordinates. (#5710, #5012) -- Backends: GLFW: Fixed leftover static variable preventing from changing or - reinitializing backend while application is running. (#4616, #5434) [@rtoumazet] - - ------------------------------------------------------------------------ - VERSION 1.88 (Released 2022-06-21) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.88 - -Breaking changes: - -- Renamed IMGUI_DISABLE_METRICS_WINDOW to IMGUI_DISABLE_DEBUG_TOOLS for correctness. - Kept support for old define (will obsolete). -- Renamed CaptureMouseFromApp() and CaptureKeyboardFromApp() to SetNextFrameWantCaptureMouse() - and SetNextFrameWantCaptureKeyboard() to clarify purpose, old name was too misleading. - Kept inline redirection functions (will obsolete). -- Renamed ImGuiKeyModFlags to ImGuiModFlags. Kept inline redirection enums (will obsolete). - (This was never used in public API functions but technically present in imgui.h and ImGuiIO). -- Backends: OSX: Removed ImGui_ImplOSX_HandleEvent() from backend API in favor of backend - automatically handling event capture. Examples that are using the OSX backend have removed - all the now-unnecessary calls to ImGui_ImplOSX_HandleEvent(), applications can do as well. - [@stuartcarnie] (#4821) -- Internals: calling ButtonBehavior() without calling ItemAdd() now requires a KeepAliveID() - call. This is because the KeepAliveID() call was moved from GetID() to ItemAdd(). (#5181) - -Other Changes: - -- IO: Fixed backward-compatibility regression introduced in 1.87: (#4921, #4858) - - Direct accesses to io.KeysDown[] with legacy indices didn't work (with new backends). - - Direct accesses to io.KeysDown[GetKeyIndex(XXX)] would access invalid data (with old/new backends). - - Calling IsKeyDown() didn't have those problems, and is recommended as io.KeysDown[] is obsolete. -- IO: Fixed input queue trickling of interleaved keys/chars events (which are frequent especially - when holding down a key as OS submits chars repeat events) delaying key presses and mouse movements. - In particular, using the input system for fast game-like actions (e.g. WASD camera move) would - typically have been impacted, as well as holding a key while dragging mouse. Constraints have - been lifted and are now only happening when e.g. an InputText() widget is active. (#4921, #4858) - Note that even thought you shouldn't need to disable io.ConfigInputTrickleEventQueue, you can - technically dynamically change its setting based on the context (e.g. disable only when hovering - or interacting with a game/3D view). -- IO: Fixed input queue trickling of mouse wheel events: multiple wheel events are merged, while - a mouse pos followed by a mouse wheel are now trickled. (#4921, #4821) -- IO: Added io.SetAppAcceptingEvents() to set a master flag for accepting key/mouse/characters - events (default to true). Useful if you have native dialog boxes that are interrupting your - application loop/refresh, and you want to disable events being queued while your app is frozen. -- Windows: Fixed first-time windows appearing in negative coordinates from being initialized - with a wrong size. This would most often be noticeable in multi-viewport mode (docking branch) - when spawning a window in a monitor with negative coordinates. (#5215, #3414) [@DimaKoltun] -- Clipper: Fixed a regression in 1.86 when not calling clipper.End() and late destructing the - clipper instance. High-level languages (Lua,Rust etc.) would typically be affected. (#4822) -- Layout: Fixed mixing up SameLine() and SetCursorPos() together from creating situations where line - height would be emitted from the wrong location (e.g. 'ItemA+SameLine()+SetCursorPos()+ItemB' would - emit ItemA worth of height from the position of ItemB, which is not necessarily aligned with ItemA). -- Sliders: An initial click within the knob/grab doesn't shift its position. (#1946, #5328) -- Sliders, Drags: Fixed dragging when using hexadecimal display format string. (#5165, #3133) -- Sliders, Drags: Fixed manual input when using hexadecimal display format string. (#5165, #3133) -- InputScalar: Fixed manual input when using %03d style width in display format string. (#5165, #3133) -- InputScalar: Automatically allow hexadecimal input when format is %X (without extra flag). -- InputScalar: Automatically allow scientific input when format is float/double (without extra flag). -- Nav: Fixed nav movement in a scope with only one disabled item from focusing the disabled item. (#5189) -- Nav: Fixed issues with nav request being transferred to another window when calling SetKeyboardFocusHere() - and simultaneous changing window focus. (#4449) -- Nav: Changed SetKeyboardFocusHere() to not behave if a drag or window moving is in progress. -- Nav: Fixed inability to cancel nav in modal popups. (#5400) [@rokups] -- IsItemHovered(): added ImGuiHoveredFlags_NoNavOverride to disable the behavior where the - return value is overridden by focus when gamepad/keyboard navigation is active. -- InputText: Fixed pressing Tab emitting two tabs characters because of dual Keys/Chars events being - trickled with the new input queue (happened on some backends only). (#2467, #1336) -- InputText: Fixed a one-frame display glitch where pressing Escape to revert after a deletion - would lead to small garbage being displayed for one frame. Curiously a rather old bug! (#3008) -- InputText: Fixed an undo-state corruption issue when editing main buffer before reactivating item. (#4947) -- InputText: Fixed an undo-state corruption issue when editing in-flight buffer in user callback. - (#4947, #4949] [@JoshuaWebb] -- Tables: Fixed incorrect border height used for logic when resizing one of several synchronized - instance of a same table ID, when instances have a different height. (#3955). -- Tables: Fixed incorrect auto-fit of parent windows when using non-resizable weighted columns. (#5276) -- Tables: Fixed draw-call merging of last column. Depending on some unrelated settings (e.g. BorderH) - merging draw-call of the last column didn't always work (regression since 1.87). (#4843, #4844) [@rokups] -- Inputs: Fixed IsMouseClicked() repeat mode rate being half of keyboard repeat rate. -- ColorEdit: Fixed text baseline alignment after a SameLine() after a ColorEdit() with visible label. -- Tabs: BeginTabItem() now reacts to SetNextItemWidth(). (#5262) -- Tabs: Tweak shrinking policy so that while resizing tabs that don't need shrinking keep their - initial width more precisely (without the occasional +1 worth of width). -- Menus: Adjusted BeginMenu() closing logic so hovering void or non-MenuItem() in parent window - always lead to menu closure. Fixes using items that are not MenuItem() or BeginItem() at the root - level of a popup with a child menu opened. -- Menus: Menus emitted from the main/scrolling layer are not part of the same menu-set as menus emitted - from the menu-bar, avoiding accidental hovering from one to the other. (#3496, #4797) [@rokups] -- Style: Adjust default value of GrabMinSize from 10.0f to 12.0f. -- Stack Tool: Added option to copy item path to clipboard. (#4631) -- Settings: Fixed out-of-bounds read when .ini file on disk is empty. (#5351) [@quantum5] -- Settings: Fixed some SetNextWindowPos/SetNextWindowSize API calls not marking settings as dirty. -- DrawList: Fixed PathArcTo() emitting terminating vertices too close to arc vertices. (#4993) [@thedmd] -- DrawList: Fixed texture-based anti-aliasing path with RGBA textures (#5132, #3245) [@cfillion] -- DrawList: Fixed divide-by-zero or glitches with Radius/Rounding values close to zero. (#5249, #5293, #3491) -- DrawList: Circle with a radius smaller than 0.5f won't appear, to be consistent with other primitives. [@thedmd] -- Debug Tools: Debug Log: Added ShowDebugLogWindow() showing an opt-in synthetic log of principal events - (focus, popup, active id changes) helping to diagnose issues. -- Debug Tools: Added DebugTextEncoding() function to facilitate diagnosing issues when not sure about - whether you have a UTF-8 text encoding issue or a font loading issue. [@LaMarche05, @ocornut] -- Demo: Add better demo of how to use SetNextFrameWantCaptureMouse()/SetNextFrameWantCaptureKeyboard(). -- Metrics: Added a "UTF-8 Encoding Viewer" section using the aforementioned DebugTextEncoding() function. -- Metrics: Added "InputText" section to visualize internal state (#4947, #4949). -- Misc: Fixed calling GetID("label") _before_ a widget emitting this item inside a group (such as InputInt()) - from causing an assertion when closing the group. (#5181). -- Misc: Fixed IsAnyItemHovered() returning false when using navigation. -- Misc: Allow redefining IM_COL32_XXX layout macros to facilitate use on big-endian systems. (#5190, #767, #844) -- Misc: Added IMGUI_STB_SPRINTF_FILENAME to support custom path to stb_sprintf. (#5068, #2954) [@jakubtomsu] -- Misc: Added constexpr to ImVec2/ImVec4 inline constructors. (#4995) [@Myriachan] -- Misc: Updated stb_truetype.h from 1.20 to 1.26 (many fixes). (#5075) -- Misc: Updated stb_textedit.h from 1.13 to 1.14 (our changes so this effectively is a no-op). (#5075) -- Misc: Updated stb_rect_pack.h from 1.00 to 1.01 (minor). (#5075) -- Misc: binary_to_compressed_c tool: Added -nostatic option. (#5021) [@podsvirov] -- ImVector: Fixed erase() with empty range. (#5009) [@thedmd] -- Backends: Vulkan: Don't use VK_PRESENT_MODE_MAX_ENUM_KHR as specs state it isn't part of the API. (#5254) -- Backends: GLFW: Fixed a regression in 1.87 which resulted in keyboard modifiers events being - reported incorrectly on Linux/X11, due to a bug in GLFW. [@rokups] -- Backends: GLFW: Fixed untranslated keys when pressing lower case letters on OSX (#5260, #5261) [@cpichard] -- Backends: SDL: Fixed dragging out viewport broken on some SDL setups. (#5012) [@rokups] -- Backends: SDL: Added support for extra mouse buttons (SDL_BUTTON_X1/SDL_BUTTON_X2). (#5125) [@sgiurgiu] -- Backends: SDL, OpenGL3: Fixes to facilitate building on AmigaOS4. (#5190) [@afxgroup] -- Backends: OSX: Monitor NSKeyUp events to catch missing keyUp for key when user press Cmd + key (#5128) [@thedmd] -- Backends: OSX, Metal: Store backend data in a per-context struct, allowing to use these backends with - multiple contexts. (#5203, #5221, #4141) [@noisewuwei] -- Backends: Metal: Fixed null dereference on exit inside command buffer completion handler. (#5363, #5365) [@warrenm] -- Backends: OpenGL3: Partially revert 1.86 change of using glBufferSubData(): now only done on Windows and - Intel GPU, based on querying glGetString(GL_VENDOR). Essentially we got report of accumulating leaks on Intel - with multi-viewports when using simple glBufferData() without orphaning, and report of corruptions on other - GPUs with multi-viewports when using orphaning and glBufferSubData(), so currently switching technique based - on GPU vendor, which unfortunately reinforce the cargo-cult nature of dealing with OpenGL drivers. - Navigating the space of mysterious OpenGL drivers is particularly difficult as they are known to rely on - application specific whitelisting. (#4468, #3381, #2981, #4825, #4832, #5127). -- Backends: OpenGL3: Fix state corruption on OpenGL ES 2.0 due to not preserving GL_ELEMENT_ARRAY_BUFFER_BINDING - and vertex attribute states. [@rokups] -- Examples: Emscripten+WebGPU: Fix building for latest WebGPU specs. (#3632) -- Examples: OSX+Metal, OSX+OpenGL: Removed now-unnecessary calls to ImGui_ImplOSX_HandleEvent(). (#4821) - -Docking+Viewports Branch: - -- Docking: Fixed floating docked nodes not being clamped into viewport workrect to stay reachable - when io.ConfigWindowsMoveFromTitleBarOnly is true and multi-viewports are disabled. (#5044) -- Docking: Fixed a regression where moving window would be interrupted after undocking a tab - when io.ConfigDockingAlwaysTabBar is true. (#5324) [@rokups] -- Docking: Fixed incorrect focus highlight on docking node when focusing empty central node - or a child window which was manually injected into a dockspace window. -- Docking, Modal: Fixed a crash when opening popup from a parent which is being docked on the same frame. (#5401) -- Viewports: Fixed an issue where MouseViewport was lagging by a frame when using 1.87 Input Queue. - A common side-effect would be that when releasing a window drag the underlying window would highlight - for a frame. (#5837, #4921) [@cfillion] -- Viewports: Fixed translating a host viewport from briefly altering the size of AlwaysAutoResize windows. (#5057) -- Viewports: Fixed main viewport size not matching ImDrawData::DisplaySize for one frame during resize - when multi-viewports are disabled. (#4900) -- Backends: SDL: Fixed dragging out main viewport broken on some SDL setups. (#5012) [@rokups] -- Backends: OSX: Added support for multi-viewports. [@stuartcarnie, @metarutaiga] (#4821, #2778) -- Backends: Metal: Added support for multi-viewports. [@stuartcarnie, @metarutaiga] (#4821, #2778) -- Examples: OSX+Metal, SDL+Metal, GLFW+Metal: Added support for multi-viewports. [@rokups] - - ------------------------------------------------------------------------ - VERSION 1.87 (Released 2022-02-07) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.87 - -Breaking Changes: - -- Removed support for pre-C++11 compilers. We'll stop supporting VS2010. (#4537) -- Reworked IO mouse input API: (#4921, #4858) [@thedmd, @ocornut] - - Added io.AddMousePosEvent(), io.AddMouseButtonEvent(), io.AddMouseWheelEvent() functions, - obsoleting writing directly to io.MousePos, io.MouseDown[], io.MouseWheel, etc. - - This enable input queue trickling to support low framerates. (#2787, #1992, #3383, #2525, #1320) - - For all calls to IO new functions, the Dear ImGui context should be bound/current. -- Reworked IO keyboard input API: (#4921, #2625, #3724) [@thedmd, @ocornut] - - Added io.AddKeyEvent() function, obsoleting writing directly to io.KeyMap[], io.KeysDown[] arrays. - - For keyboard modifiers, you can call io.AddKeyEvent() with ImGuiKey_ModXXX values, - obsoleting writing directly to io.KeyCtrl, io.KeyShift etc. - - Added io.SetKeyEventNativeData() function (optional) to pass native and old legacy indices. - - Added full range of key enums in ImGuiKey (e.g. ImGuiKey_F1). - - Added GetKeyName() helper function. - - Obsoleted GetKeyIndex(): it is now unnecessary and will now return the same value. - - All keyboard related functions taking 'int user_key_index' now take 'ImGuiKey key': - - IsKeyDown(), IsKeyPressed(), IsKeyReleased(), GetKeyPressedAmount(). - - Added io.ConfigInputTrickleEventQueue (defaulting to true) to disable input queue trickling. - - Backward compatibility: - - All backends updated to use new functions. - - Old backends populating those arrays should still work! - - Calling e.g. IsKeyPressed(MY_NATIVE_KEY_XXX) will still work! (for a while) - - Those legacy arrays will only be disabled if '#define IMGUI_DISABLE_OBSOLETE_KEYIO' is set in your imconfig. - In a few versions, IMGUI_DISABLE_OBSOLETE_FUNCTIONS will automatically enable IMGUI_DISABLE_OBSOLETE_KEYIO, - so this will be moved into the regular obsolescence path. - - BREAKING: If your custom backend used ImGuiKey as mock native indices (e.g. "io.KeyMap[ImGuiKey_A] = ImGuiKey_A") - this is a use case that will now assert and be breaking for your old backend. - - Transition guide: - - IsKeyPressed(MY_NATIVE_KEY_XXX) -> use IsKeyPressed(ImGuiKey_XXX) - - IsKeyPressed(GetKeyIndex(ImGuiKey_XXX)) -> use IsKeyPressed(ImGuiKey_XXX) - - Backend writing to io.KeyMap[],KeysDown[] -> backend should call io.AddKeyEvent(), if legacy indexing is desired, call io.SetKeyEventNativeData() - - Basically the trick we took advantage of is that we previously only supported native keycode from 0 to 511, - so ImGuiKey values can still express a legacy native keycode, and new named keys are all >= 512. - - This will enable a few things in the future: - - Access to portable keys allows for backend-agnostic keyboard input code. Until now it was difficult - to share code using keyboard across project because of this gap. (#2625, #3724) - - Access to full key ranges will allow us to develop a proper keyboard shortcut system. (#456) - - io.SetKeyEventNativeData() include native keycode/scancode which may later be exposed. (#3141, #2959) -- Reworked IO nav/gamepad input API and unifying inputs sources: (#4921, #4858, #787) - - Added full range of ImGuiKey_GamepadXXXX enums (e.g. ImGuiKey_GamepadDpadUp, ImGuiKey_GamepadR2) to use with - io.AddKeyEvent(), io.AddKeyAnalogEvent(). - - Added io.AddKeyAnalogEvent() function, obsoleting writing directly to io.NavInputs[] arrays. -- Renamed ImGuiKey_KeyPadEnter to ImGuiKey_KeypadEnter to align with new symbols. Kept redirection enum. (#2625) -- Removed support for legacy arithmetic operators (+,+-,*,/) when inputing text into a slider/drag. (#4917, #3184) - This doesn't break any api/code but a feature that was accessible by end-users (which seemingly no one used). - (Instead you may implement custom expression evaluators to provide a better version of this). -- Backends: GLFW: backend now uses glfwSetCursorPosCallback(). - - If calling ImGui_ImplGlfw_InitXXX with install_callbacks=true: nothing to do. is already done for you. - - If calling ImGui_ImplGlfw_InitXXX with install_callbacks=false: you WILL NEED to register the GLFW callback - using glfwSetCursorPosCallback() and forward it to the backend function ImGui_ImplGlfw_CursorPosCallback(). -- Backends: SDL: Added SDL_Renderer* parameter to ImGui_ImplSDL2_InitForSDLRenderer(), so backend can call - SDL_GetRendererOutputSize() to obtain framebuffer size valid for hi-dpi. (#4927) [@Clownacy] -- Commented out redirecting functions/enums names that were marked obsolete in 1.69, 1.70, 1.71, 1.72 (March-July 2019) - - ImGui::SetNextTreeNodeOpen() -> use ImGui::SetNextItemOpen() - - ImGui::GetContentRegionAvailWidth() -> use ImGui::GetContentRegionAvail().x - - ImGui::TreeAdvanceToLabelPos() -> use ImGui::SetCursorPosX(ImGui::GetCursorPosX() + ImGui::GetTreeNodeToLabelSpacing()); - - ImFontAtlas::CustomRect -> use ImFontAtlasCustomRect - - ImGuiColorEditFlags_RGB/HSV/HEX -> use ImGuiColorEditFlags_DisplayRGB/HSV/Hex -- Removed io.ImeSetInputScreenPosFn() in favor of more flexible io.SetPlatformImeDataFn() for IME support. - Because this field was mostly only ever used by Dear ImGui internally, not by backends nor the vast majority - of user code, this should only affect a very small fraction for users who are already very IME-aware. -- Obsoleted 'void* io.ImeWindowHandle' in favor of writing to 'void* ImGuiViewport::PlatformHandleRaw'. - This removes an incompatibility between 'master' and 'multi-viewports' backends and toward enabling - better support for IME. Updated backends accordingly. Because the old field is set by existing backends, - we are keeping it (marked as obsolete). - -Other Changes: - -- IO: Added event based input queue API, which now trickles events to support low framerates. [@thedmd, @ocornut] - Previously the most common issue case (button presses in low framerates) was handled by backend. This is now - handled by core automatically for all kind of inputs. (#4858, #2787, #1992, #3383, #2525, #1320) - - New IO functions for keyboard/gamepad: AddKeyEvent(), AddKeyAnalogEvent(). - - New IO functions for mouse: AddMousePosEvent(), AddMouseButtonEvent(), AddMouseWheelEvent(). -- IO: Unified key enums allow using key functions on key mods and gamepad values. -- Fixed CTRL+Tab into an empty window causing artifacts on the highlight rectangle due to bad reordering on ImDrawCmd. -- Fixed a situation where CTRL+Tab or Modal can occasionally lead to the creation of ImDrawCmd with zero triangles, - which would makes the draw operation of some backends assert (e.g. Metal with debugging). (#4857) -- Popups: Fixed a regression crash when a new window is created after a modal on the same frame. (#4920) [@rokups] -- Popups: Fixed an issue when reopening a same popup multiple times would offset them by 1 pixel on the right. (#4936) -- Tables, ImDrawListSplitter: Fixed erroneously stripping trailing ImDrawList::AddCallback() when submitted in - last column or last channel and when there are no other drawing operation. (#4843, #4844) [@hoffstadt] -- Tables: Fixed positioning of Sort icon on right-most column with some settings (not resizable + no borders). (#4918). -- Nav: Fixed gamepad navigation in wrapping popups not wrapping all the way. (#4365) -- Sliders, Drags: Fixed text input of values with a leading sign, common when using a format enforcing sign. (#4917) -- Demo: draw a section of keyboard in "Inputs > Keyboard, Gamepad & Navigation state" to visualize keys. [@thedmd] -- Platform IME: changed io.ImeSetInputScreenPosFn() to io.SetPlatformImeDataFn() API, - now taking a ImGuiPlatformImeData structure which we can more easily extend in the future. -- Platform IME: moved io.ImeWindowHandle to GetMainViewport()->PlatformHandleRaw. -- Platform IME: add ImGuiPlatformImeData::WantVisible, hide IME composition window when not used. (#2589) [@actboy168] -- Platform IME: add ImGuiPlatformImeData::InputLineHeight. (#3113) [@liuliu] -- Platform IME: [windows] call ImmSetCandidateWindow() to position candidate window. -- Backends: GLFW: Pass localized keys (matching keyboard layout). Fix e.g. CTRL+A, CTRL+Z, CTRL+Y shortcuts. - We are now converting GLFW untranslated keycodes back to translated keycodes in order to match the behavior of - other backend, and facilitate the use of GLFW with lettered-shortcuts API. (#456, #2625) -- Backends: GLFW: Submit keys and key mods using io.AddKeyEvent(). (#2625, #4921) -- Backends: GLFW: Submit mouse data using io.AddMousePosEvent(), io.AddMouseButtonEvent(), io.AddMouseWheelEvent() functions. (#4921) -- Backends: GLFW: Retrieve mouse position using glfwSetCursorPosCallback() + fallback when focused but not hovered/captured. -- Backends: GLFW: Submit gamepad data using io.AddKeyEvent/AddKeyAnalogEvent() functions, stopped writing to io.NavInputs[]. (#4921) -- Backends: GLFW: Added ImGui_ImplGlfw_InstallCallbacks()/ImGui_ImplGlfw_RestoreCallbacks() helpers to facilitate user installing - callbacks after iniitializing backend. (#4981) -- Backends: Win32: Submit keys and key mods using io.AddKeyEvent(). (#2625, #4921) -- Backends: Win32: Retrieve mouse position using WM_MOUSEMOVE/WM_MOUSELEAVE + fallback when focused but not hovered/captured. -- Backends: Win32: Submit mouse data using io.AddMousePosEvent(), AddMouseButtonEvent(), AddMouseWheelEvent() functions. (#4921) -- Backends: Win32: Maintain a MouseButtonsDown mask instead of using ImGui::IsAnyMouseDown() which will be obsoleted. -- Backends: Win32: Submit gamepad data using io.AddKeyEvent/AddKeyAnalogEvent() functions, stopped writing to io.NavInputs[]. (#4921) -- Backends: SDL: Pass localized keys (matching keyboard layout). Fix e.g. CTRL+A, CTRL+Z, CTRL+Y shortcuts. (#456, #2625) -- Backends: SDL: Submit key data using io.AddKeyEvent(). Submit keymods using io.AddKeyModsEvent() at the same time. (#2625) -- Backends: SDL: Retrieve mouse position using SDL_MOUSEMOTION/SDL_WINDOWEVENT_LEAVE + fallback when focused but not hovered/captured. -- Backends: SDL: Submit mouse data using io.AddMousePosEvent(), AddMouseButtonEvent(), AddMouseWheelEvent() functions. (#4921) -- Backends: SDL: Maintain a MouseButtonsDown mask instead of using ImGui::IsAnyMouseDown() which will be obsoleted. -- Backends: SDL: Submit gamepad data using io.AddKeyEvent/AddKeyAnalogEvent() functions, stopped writing to io.NavInputs[]. (#4921) -- Backends: Allegro5: Submit keys using io.AddKeyEvent(). Submit keymods using io.AddKeyModsEvent() at the same time. (#2625) -- Backends: Allegro5: Submit mouse data using io.AddMousePosEvent(), AddMouseButtonEvent(), AddMouseWheelEvent() functions. (#4921) -- Backends: OSX: Submit keys using io.AddKeyEvent(). Submit keymods using io.AddKeyModsEvent() at the same time. (#2625) -- Backends: OSX: Submit mouse data using io.AddMousePosEvent(), AddMouseButtonEvent(), AddMouseWheelEvent() functions. (#4921) -- Backends: OSX: Submit gamepad data using io.AddKeyEvent/AddKeyAnalogEvent() functions, stopped writing to io.NavInputs[]. (#4921) -- Backends: OSX: Added basic Platform IME support. (#3108, #2598) [@liuliu] -- Backends: OSX: Fix Game Controller nav mapping to use shoulder for both focusing and tweak speed. (#4759) -- Backends: OSX: Fix building with old Xcode versions that are missing gamepad features. [@rokups] -- Backends: OSX: Forward keyDown/keyUp events to OS when unused by Dear ImGui. -- Backends: Android, GLUT: Submit keys using io.AddKeyEvent(). Submit keymods using io.AddKeyModsEvent() at the same time. (#2625) -- Backends: Android, GLUT: Submit mouse data using io.AddMousePosEvent(), AddMouseButtonEvent(), AddMouseWheelEvent() functions. (#4858) -- Backends: OpenGL3: Fixed a buffer overflow in imgui_impl_opengl3_loader.h init (added in 1.86). (#4468, #4830) [@dymk] - It would generally not have noticeable side-effect at runtime but would be detected by runtime checkers. -- Backends: OpenGL3: Fix OpenGL ES2 includes on Apple systems. [@rokups] -- Backends: Metal: Added Apple Metal C++ API support. (#4824, #4746) [@luigifcruz] - Enable with '#define IMGUI_IMPL_METAL_CPP' in your imconfig.h file. -- Backends: Metal: Ignore ImDrawCmd where ElemCount == 0, which are normally not emitted by the library but - can theoretically be created by user code manipulating a ImDrawList. (#4857) -- Backends: Vulkan: Added support for ImTextureID as VkDescriptorSet, add ImGui_ImplVulkan_AddTexture(). (#914) [@martty] -- Backends: SDL_Renderer: Fix texture atlas format on big-endian hardware (#4927) [@Clownacy] -- Backends: WebGPU: Fixed incorrect size parameters in wgpuRenderPassEncoderSetIndexBuffer() and - wgpuRenderPassEncoderSetVertexBuffer() calls. (#4891) [@FeepsDev] - -Docking+Viewports Branch: - -- Docking: Fixed a CTRL+TAB crash when aiming at an empty docked window. (#4792) -- Docking: Tabs use their own identifier instead of the Window identifier. - (This will invalidate some stored .ini data such as last selected tab, sorry!) -- Docking: Fixed size constraints not working on single window holding on a dock id (still doesn't work on docked windows). -- Docking: Fixed CTRL+TAB back into a docked window not selecting menu layer when no item are on main layer. -- Viewports, IO: Added io.AddMouseViewportEvent() function to queue hovered viewport change (when known by backend). -- Viewports: Relaxed specs for backend supporting ImGuiBackendFlags_HasMouseHoveredViewport: it is now _optional_ - for the backend to have to ignore viewports with the _NoInputs flag when call io.AddMouseViewportEvent(). It is - much better if they can (Win32 and GLFW 3.3+ backends can, SDL and GLFW 3.2 backends cannot, they are lacking data). - A concrete example is: when dragging a viewport for docking, the viewport is marked with _NoInputs to allow us - to pick the target viewports for docking. If the backend reports a viewport with _NoInputs when calling the - io.AddMouseViewportEvent() function, then Dear ImGui will revert to its flawed heuristic to find the viewport under. - By lowering those specs, we allow the SDL and more backend to support this, only relying on the heuristic in a few - drag and drop situations rather that relying on it everywhere. -- Viewports: Fixed a CTRL+TAB crash with viewports enabled when the window list needs to appears in - its own viewport (regression from 1.86). (#4023, #787) -- Viewports: Fixed active InputText() from preventing viewports to merge. (#4212) -- Backends: SDL: Added support for ImGuiBackendFlags_HasMouseHoveredViewport now that its specs have been lowered. -- (Breaking) Removed ImGuiPlatformIO::Platform_SetImeInputPos() in favor of newly standardized - io.SetPlatformImeDataFn() function. Should not affect more than default backends. - - ------------------------------------------------------------------------ - VERSION 1.86 (Released 2021-12-22) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.86 - -Breaking Changes: - -- Removed CalcListClipping() function. Prefer using ImGuiListClipper which can return non-contiguous ranges. - Please open an issue if you think you really need this function. (#3841) -- Backends: OSX: Added NSView* parameter to ImGui_ImplOSX_Init(). (#4759) [@stuartcarnie] -- Backends: Marmalade: Removed obsolete Marmalade backend (imgui_impl_marmalade.cpp) + example app. (#368, #375) - Find last supported version at https://github.com/ocornut/imgui/wiki/Bindings - -Other Changes: - -- Added an assertion for the common user mistake of using "" as an identifier at the root level of a window - instead of using "##something". Empty identifiers are valid and useful in a very small amount of cases, - but 99.9% of the time if you need an empty label you should use "##something". (#1414, #2562, #2807, #4008, - #4158, #4375, #4548, #4657, #4796). READ THE FAQ ABOUT HOW THE ID STACK WORKS -> https://dearimgui.com/faq -- Added GetMouseClickedCount() function, returning the number of successive clicks. (#3229) [@kudaba] - (so IsMouseDoubleClicked(ImGuiMouseButton_Left) is same as GetMouseClickedCount(ImGuiMouseButton_Left) == 2, - but it allows testing for triple clicks and more). -- Modals: fixed issue hovering popups inside a child windows inside a modal. (#4676, #4527) -- Modals, Popups, Windows: changes how appearing windows are interrupting popups and modals. (#4317) [@rokups] - - appearing windows created from within the begin stack of a popup/modal will no longer close it. - - appearing windows created not within the begin stack of a modal will no longer close the modal, - and automatically appear behind it. -- Fixed IsWindowFocused()/IsWindowHovered() issues with child windows inside popups. (#4676) -- Nav: Ctrl+tabbing to cycle through windows is now enabled regardless of using the _NavEnableKeyboard - configuration flag. This is part of an effort to generalize the use of keyboard inputs. (#4023, #787). - Note that while this is active you can also moving windows (with arrow) and resize (shift+arrows). -- Nav: tabbing now cycles through clipped items and scroll accordingly. (#4449) -- Nav: pressing PageUp/PageDown/Home/End when in Menu layer automatically moves back to Main layer. -- Nav: fixed resizing window from borders setting navigation to Menu layer. -- Nav: prevent child from clipping items when using _NavFlattened and parent has a pending request. -- Nav: pressing Esc to exit a child window reactivates the Nav highlight if it was disabled by mouse. -- Nav: with ImGuiConfigFlags_NavEnableSetMousePos enabled: Fixed absolute mouse position when using - Home/End leads to scrolling. Fixed not setting mouse position when a failed move request (e.g. when - already at edge) reactivates the navigation highlight. -- Menus: fixed closing a menu inside a popup/modal by clicking on the popup/modal. (#3496, #4797) -- Menus: fixed closing a menu by clicking on its menu-bar item when inside a popup. (#3496, #4797) [@xndcn] -- Menus: fixed menu inside a popup/modal not inhibiting hovering of items in the popup/modal. (#3496, #4797) -- Menus: fixed sub-menu items inside a popups from closing the popup. -- Menus: fixed top-level menu from not consistently using style.PopupRounding. (#4788) -- InputText, Nav: fixed repeated calls to SetKeyboardFocusHere() preventing to use InputText(). (#4682) -- Inputtext, Nav: fixed using SetKeyboardFocusHere() on InputTextMultiline(). (#4761) -- InputText: made double-click select word, triple-line select line. Word delimitation logic differs - slightly from the one used by CTRL+arrows. (#2244) -- InputText: fixed ReadOnly flag preventing callbacks from receiving the text buffer. (#4762) [@actondev] -- InputText: fixed Shift+Delete from not cutting into clipboard. (#4818, #1541) [@corporateshark] -- InputTextMultiline: fixed incorrect padding when FrameBorder > 0. (#3781, #4794) -- InputTextMultiline: fixed vertical tracking with large values of FramePadding.y. (#3781, #4794) -- Separator: fixed cover all columns while called inside a table. (#4787) -- Clipper: currently focused item is automatically included in clipper range. - Fixes issue where e.g. drag and dropping an item and scrolling ensure the item source location is - still submitted. (#3841, #1725) [@GamingMinds-DanielC, @ocornut] -- Clipper: added ForceDisplayRangeByIndices() to force a given item (or several) to be stepped out - during a clipping operation. (#3841) [@GamingMinds-DanielC] -- Clipper: rework so gamepad/keyboard navigation doesn't create spikes in number of items requested - by the clipper to display. (#3841) -- Clipper: fixed content height declaration slightly mismatching the value of when not using a clipper. - (an additional ItemSpacing.y was declared, affecting scrollbar range). -- Clipper: various and incomplete changes to tame down scrolling and precision issues on very large ranges. - Passing an explicit height to the clipper now allows larger ranges. (#3609, #3962). -- Clipper: fixed invalid state when number of frozen table row is smaller than ItemCount. -- Drag and Drop: BeginDragDropSource() with ImGuiDragDropFlags_SourceAllowNullID doesn't lose - tooltip when scrolling. (#143) -- Fonts: fixed infinite loop in ImFontGlyphRangesBuilder::AddRanges() when passing UINT16_MAX or UINT32_MAX - without the IMGUI_USE_WCHAR32 compile-time option. (#4802) [@SlavicPotato] -- Metrics: Added a node showing windows in submission order and showing the Begin() stack. -- Misc: Added missing ImGuiMouseCursor_NotAllowed cursor for software rendering (when the - io.MouseDrawCursor flag is enabled). (#4713) [@nobody-special666] -- Misc: Fixed software mouse cursor being rendered multiple times if Render() is called more than once. -- Misc: Fix MinGW DLL build issue (when IMGUI_API is defined). [@rokups] -- CI: Add MinGW DLL build to test suite. [@rokups] -- Backends: Vulkan: Call vkCmdSetScissor() at the end of render with a full-viewport to reduce - likehood of issues with people using VK_DYNAMIC_STATE_SCISSOR in their app without calling - vkCmdSetScissor() explicitly every frame. (#4644) -- Backends: OpenGL3: Using buffer orphaning + glBufferSubData(), seems to fix leaks with multi-viewports - with some Intel HD drivers, and perhaps improve performances. (#4468, #4504, #2981, #3381) [@parbo] -- Backends: OpenGL2, Allegro5, Marmalade: Fixed mishandling of the ImDrawCmd::IdxOffset field. - This is an old bug, but due to the way we created drawlists, it never had any visible side-effect before. - The new code for handling Modal and CTRL+Tab dimming/whitening recently made the bug surface. (#4790) -- Backends: Win32: Store left/right variants of Ctrl/Shift/Alt mods in KeysDown[] array. (#2625) [@thedmd] -- Backends: DX12: Fixed DRAW_EMPTY_SCISSOR_RECTANGLE warnings. (#4775) -- Backends: SDL_Renderer: Added support for large meshes (64k+ vertices) with 16-bit indices, - enabling 'ImGuiBackendFlags_RendererHasVtxOffset' in the backend. (#3926) [@rokups] -- Backends: SDL_Renderer: Fix for SDL 2.0.19+ RenderGeometryRaw() API signature change. (#4819) [@sridenour] -- Backends: OSX: Generally fix keyboard support. Keyboard arrays indexed using kVK_* codes, e.g. - ImGui::IsKeyPressed(kVK_Space). Don't set mouse cursor shape unconditionally. Handle two fingers scroll - cancel event. (#4759, #4253, #1873) [@stuartcarnie] -- Backends: OSX: Add Game Controller support (need linking GameController framework) (#4759) [@stuartcarnie] -- Backends: WebGPU: Passing explicit buffer sizes to wgpuRenderPassEncoderSetVertexBuffer() and - wgpuRenderPassEncoderSetIndexBuffer() functions as validation layers appears to not do what the - in-flux specs says. (#4766) [@meshula] - -Docking+Viewports Branch: - -- Docking: Revert removal of io.ConfigDockingWithShift config option (removed in 1.83). (#4643) -- Docking: Fixed a bug undocking windows docked into a non-visible or _KeepAliveOnly dockspace - when unrelated windows submitted before the dockspace have dynamic visibility. (#4757) -- Docking, Style: Docked windows honor ImGuiCol_WindowBg. (#2700, #2539) -- Docking, Style: Docked windows honor display their border properly. (#2522) -- Docking: Fixed incorrectly rounded tab bars for dock node that are not at the top of their dock tree. -- Docking: Fixed single-frame node pos/size inconsistencies when window stop or start being submitted. -- Docking: Prevent docking any window created above a popup/modal. (#4317) -- Viewports: Made it possible to explicitly assign ImGuiWindowClass::ParentViewportId to 0 in order - to ensure a window is not parented. Previously this would use the global default (which might be 0, - but not always as it would depend on io.ConfigViewportsNoDefaultParent). (#3152, #2871) -- Viewports: Fixed tooltip in own viewport over modal from being incorrectly dimmed. (#4729) -- Viewports: Fixed CTRL+TAB highlight outline on docked windows not always fitting in host viewport. -- Backends: Made it possible to shutdown default Platform Backends before the Renderer backends. (#4656) -- Disabled: Fixed nested BeginDisabled()/EndDisabled() bug in Docking branch due to bad merge. (#4655, #4452, #4453, #4462) - - ------------------------------------------------------------------------ - VERSION 1.85 (Released 2021-10-12) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.85 - -This is the last release officially supporting C++03 and Visual Studio 2008/2010. (#4537) -We expect that the next release will require a subset of the C++11 language (VS 2012~, GCC 4.8.1, Clang 3.3). -We may use some C++11 language features but we will not use any C++ library headers. -If you are stuck on ancient compiler you may need to stay at this version onward. - -Breaking Changes: - -- Removed GetWindowContentRegionWidth() function. Kept inline redirection helper. - Can use 'GetWindowContentRegionMax().x - GetWindowContentRegionMin().x' instead but it's not - very useful in practice, and the only use of it in the demo was illfit. - Using 'GetContentRegionAvail().x' is generally a better choice. -- (Docking branch) IsWindowFocused() and IsWindowHovered() with only the _ChildWindows flag - and without the _RootWindow flag used to leak docking hierarchy, so a docked window would - return as the child of the window hosting the dockspace. This was inconsistent and incorrect - with other behaviors so we fixed it. Added a new _DockHierarchy flag to opt-in this behavior. - -Other Changes: - -- Debug: Stack Tool: Added "Stack Tool" available in "Demo->Tools->Stack Tool", "Metrics->Tools", - or by calling the ShowStackToolWindow() function. The tool run queries on hovered id to display - details about individual components that were hashed to create an ID. It helps understanding - the ID stack system and debugging potential ID collisions. (#4631) [@ocornut, @rokups] -- Windows: Fixed background order of overlapping childs submitted sequentially. (#4493) -- IsWindowFocused: Added ImGuiFocusedFlags_NoPopupHierarchy flag allowing to exclude child popups - from the tested windows when combined with _ChildWindows. -- IsWindowHovered: Added ImGuiHoveredFlags_NoPopupHierarchy flag allowing to exclude child popups - from the tested windows when combined with _ChildWindows. -- InputTextMultiline: Fixed label size not being included into window contents rect unless - the whole widget is clipped. -- InputText: Allow activating/cancelling/validating input with gamepad nav events. (#2321, #4552) -- InputText: Fixed selection rectangle appearing one frame late when selecting all. -- TextUnformatted: Accept null ranges including (NULL,NULL) without asserting, in order to conform - to common idioms (e.g. passing .data(), .data() + .size() from a null string). (#3615) -- Disabled: Added assert guard for mismatching BeginDisabled()/EndDisabled() blocks. (#211) -- Nav: Fixed using SetKeyboardFocusHere() on non-visible/clipped items. It now works and will scroll - toward the item. When called during a frame where the parent window is appearing, scrolling will - aim to center the item in the window. When calling during a frame where the parent window is already - visible, scrolling will aim to scroll as little as possible to make the item visible. We will later - expose scroll functions and flags in public API to select those behaviors. (#343, #4079, #2352) -- Nav: Fixed using SetKeyboardFocusHere() from activating a different item on the next frame if - submitted items have changed during that frame. (#432) -- Nav: Fixed toggling menu layer with Alt or exiting menu layer with Esc not moving mouse when - the ImGuiConfigFlags_NavEnableSetMousePos config flag is set. -- Nav: Fixed a few widgets from not setting reference keyboard/gamepad navigation ID when - activated with mouse. More specifically: BeginTabItem(), the scrolling arrows of BeginTabBar(), - the arrow section of TreeNode(), the +/- buttons of InputInt()/InputFloat(), Selectable() with - ImGuiSelectableFlags_SelectOnRelease. More generally: any direct use of ButtonBehavior() with - the PressedOnClick/PressedOnDoubleClick/PressedOnRelease button policy. -- Nav: Fixed an issue with losing focus on docked windows when pressing Alt while keyboard navigation - is disabled. (#4547, #4439) [@PathogenDavid] -- Nav: Fixed vertical scoring offset when wrapping on Y in a decorated window. -- Nav: Improve scrolling behavior when navigating to an item larger than view. -- TreePush(): removed unnecessary/inconsistent legacy behavior where passing a NULL value to - the TreePush(const char*) and TreePush(const void*) functions would use an hard-coded replacement. - The only situation where that change would make a meaningful difference is TreePush((const char*)NULL) - (_explicitly_ casting a null pointer to const char*), which is unlikely and will now crash. - You may replace it with anything else. -- ColorEdit4: Fixed not being able to change hue when saturation is 0. (#4014) [@rokups] -- ColorEdit4: Fixed hue resetting to 0 when it is set to 255. [@rokups] -- ColorEdit4: Fixed hue value jitter when source color is stored as RGB in 32-bit integer and perform - RGB<>HSV round trips every frames. [@rokups] -- ColorPicker4: Fixed picker being unable to select exact 1.0f color when dragging toward the edges - of the SV square (previously picked 0.999989986f). (#3517) [@rokups] -- Menus: Fixed vertical alignments of MenuItem() calls within a menu bar (broken in 1.84). (#4538) -- Menus: Improve closing logic when moving diagonally in empty between between parent and child menus to - accommodate for varying font size and dpi. -- Menus: Fixed crash when navigating left inside a child window inside a sub-menu. (#4510). -- Menus: Fixed an assertion happening in some situations when closing nested menus (broken in 1.83). (#4640) -- Drag and Drop: Fixed using BeginDragDropSource() inside a BeginChild() that returned false. (#4515) -- PlotHistogram: Fixed zero-line position when manually specifying min<0 and max>0. (#4349) [@filippocrocchini] -- Misc: Added asserts for missing PopItemFlag() calls. -- Misc: Fixed printf-style format checks on Clang+MinGW. (#4626, #4183, #3592) [@guusw] -- IO: Added 'io.WantCaptureMouseUnlessPopupClose' alternative to `io.WantCaptureMouse'. (#4480) - This allows apps to receive the click on void when that click is used to close popup (by default, - clicking on a void when a popup is open will close the popup but not release io.WantCaptureMouse). -- Fonts: imgui_freetype: Fixed crash when FT_Render_Glyph() fails to render a glyph and returns NULL - (which apparently happens with Freetype 2.11). (#4394, #4145?). -- Fonts: Fixed ImFontAtlas::ClearInputData() marking atlas as not built. (#4455, #3487) -- Backends: Added more implicit asserts to detect invalid/redundant calls to Shutdown functions. (#4562) -- Backends: OpenGL3: Fixed our custom GL loader conflicting with user using GL3W. (#4445) [@rokups] -- Backends: WebGPU: Fixed for latest specs. (#4472, #4512) [@Kangz, @bfierz] -- Backends: SDL_Renderer: Added SDL_Renderer backend compatible with upcoming SDL 2.0.18. (#3926) [@1bsyl] -- Backends: Metal: Fixed a crash when clipping rect larger than framebuffer is submitted via - a direct unclipped PushClipRect() call. (#4464) -- Backends: OSX: Use mach_absolute_time as CFAbsoluteTimeGetCurrent can jump backwards. (#4557, #4563) [@lfnoise] -- Backends: All renderers: Normalize clipping rect handling across backends. (#4464) -- Examples: Added SDL + SDL_Renderer example in "examples/example_sdl_sdlrenderer/" folder. (#3926) [@1bsyl] - -Docking+Viewports Branch: - -- IsWindowFocused: Fixed using ImGuiFocusedFlags_ChildWindows (without _RootWindow) from leaking the - docking hierarchy. Added ImGuiFocusedFlags_DockHierarchy flag to consider docking hierarchy in the test. -- IsWindowHovered: Fixed using ImGuiHoveredFlags_ChildWindows (without _RootWindow) from leaking the - docking hierarchy. Added ImGuiHoveredFlags_DockHierarchy flag to consider docking hierarchy in the test. -- Nav: Fixed an issue with losing focus on docked windows when pressing Alt while keyboard navigation - is disabled. (#4547, #4439) [@PathogenDavid] -- Docking: Fixed IsItemHovered() and functions depending on it (e.g. BeginPopupContextItem()) when - called after Begin() on a docked window (broken 2021/03/04). (#3851) -- Docking: Improved resizing system so that non-central zone are better at keeping their fixed size. - The algorithm is still not handling the allocation of size ideally for nested sibling, but it got better. -- Docking: Fixed settings load issue when mouse wheeling. (#4310) -- Docking: Fixed manually created floating node with a central node from not hiding when windows are gone. -- Docking + Drag and Drop: Fixed using BeginDragDropSource() or BeginDragDropTarget() inside a Begin() - that returned false because the window is docked. (#4515) -- Viewports: Fixed a crash while a window owning its viewport disappear while being dragged. - It would manifest when e.g. reconfiguring dock nodes while dragging. -- Viewports: Fixed unnecessary creation of temporary viewports when multiple docked windows - got reassigned to a new node (created mid-frame) which already has a HostWindow. -- Viewports: Fixed window with viewport ini data immediately merged into a host viewport from - leaving a temporary viewport alive for a frame (would leak into backend). - - ------------------------------------------------------------------------ - VERSION 1.84.2 (Released 2021-08-23) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.84.2 - -- Disabled: Fixed nested BeginDisabled()/EndDisabled() calls. (#211, #4452, #4453, #4462) [@Legulysse] -- Backends: OpenGL3: OpenGL: Fixed ES 3.0 shader ("#version 300 es") to use normal precision - floats. Avoid wobbly rendering at HD resolutions. (#4463) [@nicolasnoble] - - ------------------------------------------------------------------------ - VERSION 1.84.1 (Released 2021-08-20) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.84.1 - -- Disabled: Fixed BeginDisabled(false) - BeginDisabled(true) was working. (#211, #4452, #4453) - - ------------------------------------------------------------------------ - VERSION 1.84 (Released 2021-08-20) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.84 - -Breaking Changes: - -- Commented out redirecting functions/enums names that were marked obsolete in 1.67 and 1.69 (March 2019): - - ImGui::GetOverlayDrawList() -> use ImGui::GetForegroundDrawList() - - ImFont::GlyphRangesBuilder -> use ImFontGlyphRangesBuilder -- Backends: OpenGL3: added a third source file "imgui_impl_opengl3_loader.h". (#4445) [@rokups] -- Backends: GLFW: backend now uses glfwSetCursorEnterCallback(). (#3751, #4377, #2445) -- Backends: GLFW: backend now uses glfwSetWindowFocusCallback(). (#4388) [@thedmd] - - If calling ImGui_ImplGlfw_InitXXX with install_callbacks=true: this is already done for you. - - If calling ImGui_ImplGlfw_InitXXX with install_callbacks=false: you WILL NEED to register the GLFW callbacks - and forward them to the backend: - - Register glfwSetCursorEnterCallback, forward events to ImGui_ImplGlfw_CursorEnterCallback(). - - Register glfwSetWindowFocusCallback, forward events to ImGui_ImplGlfw_WindowFocusCallback(). -- Backends: SDL2: removed unnecessary SDL_Window* parameter from ImGui_ImplSDL2_NewFrame(). (#3244) [@funchal] - Kept inline redirection function (will obsolete). -- Backends: SDL2: backend needs to set 'SDL_SetHint(SDL_HINT_MOUSE_FOCUS_CLICKTHROUGH, "1")' in order to - receive mouse clicks events on window focus, otherwise SDL doesn't emit the event. (#3751, #4377, #2445) - This is unfortunately a global SDL setting, so enabling it _might_ have a side-effect on your application. - It is unlikely to make a difference, but if your app absolutely needs to ignore the initial on-focus click: - you can ignore SDL_MOUSEBUTTONDOWN events coming right after a SDL_WINDOWEVENT_FOCUS_GAINED event). -- Internals: (for custom widgets): because disabled items now sets HoveredId, if you want custom widgets to - not react as hovered when disabled, in the majority of use cases it is preferable to check the "hovered" - return value of ButtonBehavior() rather than (HoveredId == id). - -Other Changes: - -- IO: Added io.AddFocusEvent() api for backend to tell when host window has gained/lost focus. (#4388) [@thedmd] - If you use a custom backend, consider adding support for this! -- Disabled: added BeginDisabled()/EndDisabled() api to create a scope where interactions are disabled. (#211) - - Added style.DisabledAlpha (default to 0.60f) and ImGuiStyleVar_DisabledAlpha. (#211) - - Unlike the internal-and-undocumented-but-somehow-known PushItemFlag(ImGuiItemFlags_Disabled), this also alters - visuals. Currently this is done by lowering alpha of all widgets. Future styling system may do that differently. - - Disabled items set HoveredId, allowing e.g. HoveredIdTimer to run. (#211, #3419) [@rokups] - - Disabled items more consistently release ActiveId if the active item got disabled. (#211) - - Nav: Fixed disabled items from being candidate for default focus. (#211, #787) - - Fixed Selectable() selection not showing when disabled. (#211) - - Fixed IsItemHovered() returning true on disabled item when navigated to. (#211) - - Fixed IsItemHovered() when popping disabled state after item, or when using Selectable_Disabled. (#211) -- Windows: ImGuiWindowFlags_UnsavedDocument/ImGuiTabItemFlags_UnsavedDocument displays a dot instead of a '*' so it - is independent from font style. When in a tab, the dot is displayed at the same position as the close button. - Added extra comments to clarify the purpose of this flag in the context of docked windows. -- Tables: Added ImGuiTableColumnFlags_Disabled acting a master disable over (hidden from user/context menu). (#3935) -- Tables: Clarified that TableSetColumnEnabled() requires the table to use the ImGuiTableFlags_Hideable flag, - because it manipulates the user-accessible show/hide state. (#3935) -- Tables: Added ImGuiTableColumnFlags_NoHeaderLabel to request TableHeadersRow() to not submit label for a column. - Convenient for some small columns. Name will still appear in context menu. (#4206). -- Tables: Fixed columns order on TableSetupScrollFreeze() if previous data got frozen columns out of their section. -- Tables: Fixed invalid data in TableGetSortSpecs() when SpecsDirty flag is unset. (#4233) -- Tabs: Fixed using more than 32 KB-worth of tab names. (#4176) -- InputInt/InputFloat: When used with Steps values and _ReadOnly flag, the step button look disabled. (#211) -- InputText: Fixed named filtering flags disabling newline or tabs in multiline inputs (#4409, #4410) [@kfsone] -- Drag and Drop: drop target highlight doesn't try to bypass host clipping rectangle. (#4281, #3272) -- Drag and Drop: Fixed using AcceptDragDropPayload() with ImGuiDragDropFlags_AcceptNoPreviewTooltip. [@JeffM2501] -- Menus: MenuItem() and BeginMenu() are not affected/overlapping when style.SelectableTextAlign is altered. -- Menus: Fixed hovering a disabled menu or menu item not closing other menus. (#211) -- Popups: Fixed BeginPopup/OpenPopup sequence failing when there are no focused windows. (#4308) [@rokups] -- Nav: Alt doesn't toggle menu layer if other modifiers are held. (#4439) -- Fixed printf-style format checks on non-MinGW flavors. (#4183, #3592) -- Fonts: Functions with a 'float size_pixels' parameter can accept zero if it is set in ImFontSize::SizePixels. -- Fonts: Prefer using U+FFFD character for fallback instead of '?', if available. (#4269) -- Fonts: Use U+FF0E dot character to construct an ellipsis if U+002E '.' is not available. (#4269) -- Fonts: Added U+FFFD ("replacement character") to default asian glyphs ranges. (#4269) -- Fonts: Fixed calling ClearTexData() (clearing CPU side font data) triggering an assert in NewFrame(). (#3487) -- DrawList: Fixed AddCircle/AddCircleFilled() with auto-tesselation not using accelerated paths for small circles. - Fixed AddCircle/AddCircleFilled() with 12 segments which had a broken edge. (#4419, #4421) [@thedmd] -- Demo: Fixed requirement in 1.83 to link with imgui_demo.cpp if IMGUI_DISABLE_METRICS_WINDOW is not set. (#4171) - Normally the right way to disable compiling the demo is to set IMGUI_DISABLE_DEMO_WINDOWS, but we want to avoid - implying that the file is required. -- Metrics: Fixed a crash when inspecting the individual draw command of a foreground drawlist. [@rokups] -- Backends: Reorganized most backends (Win32, SDL, GLFW, OpenGL2/3, DX9/10/11/12, Vulkan, Allegro) to pull their - data from a single structure stored inside the main Dear ImGui context. This facilitate/allow usage of standard - backends with multiple-contexts BUT is only partially tested and not well supported. It is generally advised to - instead use the multi-viewports feature of docking branch where a single Dear ImGui context can be used across - multiple windows. (#586, #1851, #2004, #3012, #3934, #4141) -- Backends: Win32: Rework to handle certain Windows 8.1/10 features without a manifest. (#4200, #4191) - - ImGui_ImplWin32_GetDpiScaleForMonitor() will handle per-monitor DPI on Windows 10 without a manifest. - - ImGui_ImplWin32_EnableDpiAwareness() will call SetProcessDpiAwareness() fallback on Windows 8.1 without a manifest. -- Backends: Win32: IME functions are disabled by default for non-Visual Studio compilers (MinGW etc.). Enable with - '#define IMGUI_ENABLE_WIN32_DEFAULT_IME_FUNCTIONS' for those compilers. Undo change from 1.82. (#2590, #738, #4185, #4301) -- Backends: Win32: Mouse position is correctly reported when the host window is hovered but not focused. (#2445, #2696, #3751, #4377) -- Backends: Win32, SDL2, GLFW, OSX, Allegro: now calling io.AddFocusEvent() on focus gain/loss. (#4388) [@thedmd] - This allow us to ignore certain inputs on focus loss (previously relied on mouse loss but backends are now - reporting mouse even when host window is unfocused, as per #2445, #2696, #3751, #4377) -- Backends: Fixed keyboard modifiers being reported when host window doesn't have focus. (#2622) -- Backends: GLFW: Mouse position is correctly reported when the host window is hovered but not focused. (#3751, #4377, #2445) - (backend now uses glfwSetCursorEnterCallback(). If you called ImGui_ImplGlfw_InitXXX with install_callbacks=false, you will - need to install this callback and forward the data to the backend via ImGui_ImplGlfw_CursorEnterCallback). -- Backends: SDL2: Mouse position is correctly reported when the host window is hovered but not focused. (#3751, #4377, #2445) - (enabled with SDL 2.0.5+ as SDL_GetMouseFocus() is only usable with SDL_HINT_MOUSE_FOCUS_CLICKTHROUGH). -- Backends: DX9: Explicitly disable texture state stages after >= 1. (#4268) [@NZJenkins] -- Backends: DX12: Fix texture casting crash on 32-bit systems (introduced on 2021/05/19 and v1.83) + added comments - about building on 32-bit systems. (#4225) [@kingofthebongo2008] -- Backends: OpenGL3: Embed our own minimal GL headers/loader (imgui_impl_opengl3_loader.h) based on gl3w. - Reduces the frequent issues and confusion coming from having to support multiple loaders and requiring users to use and - initialize the same loader as the backend. (#4445) [@rokups] - Removed support for gl3w, glew, glad, glad2, glbinding2, glbinding3 (all now unnecessary). -- Backends: OpenGL3: Handle GL_CLIP_ORIGIN on <4.5 contexts if "GL_ARB_clip_control" extension is detected. (#4170, #3998) -- Backends: OpenGL3: Destroy vertex/fragment shader objects right after they are linked into main shader. (#4244) [@Crowbarous] -- Backends: OpenGL3: Use OES_vertex_array extension on Emscripten + backup/restore current state. (#4266, #4267) [@harry75369] -- Backends: GLFW: Installing and exposed ImGui_ImplGlfw_MonitorCallback() for forward compatibility with docking branch. -- Backends: OSX: Added a fix for shortcuts using CTRL key instead of CMD key. (#4253) [@rokups] -- Examples: DX12: Fixed handling of Alt+Enter in example app (using swapchain's ResizeBuffers). (#4346) [@PathogenDavid] -- Examples: DX12: Removed unnecessary recreation of backend-owned device objects when window is resized. (#4347) [@PathogenDavid] -- Examples: OpenGL3+GLFW,SDL: Remove include cruft to support variety of GL loaders (no longer necessary). [@rokups] -- Examples: OSX+OpenGL2: Fix event forwarding (fix key remaining stuck when using shortcuts with Cmd/Super key). - Other OSX examples were not affected. (#4253, #1873) [@rokups] -- Examples: Updated all .vcxproj to VS2015 (toolset v140) to facilitate usage with vcpkg. -- Examples: SDL2: Accommodate for vcpkg install having headers in SDL2/SDL.h vs SDL.h. - -Docking+Viewports Branch: - -- Docking: Clicking on the right-most close button of a docking node closes all windows. (#4186) -- Docking: Fix IsWindowAppearing() and ImGuiCond_Appearing on docked windows. (#4177, #3982, #1497, #1061) -- Docking: Fix crash using DockBuilderRemoveNode() in some situations. (#3111, #3179, #3203, #4295) [@hsimyu] -- Docking: Fix crash when a dock node gets re-qualified as dockspace>floating>dockspace, which tends to happen - when incorrectly calling DockBuilderAddNode() without ImGuiDockNodeFlags_Dockspace and using it as a Dockspace - on the next frame after the floating window hosting the node has been automatically created. (#3203, #4295) -- Docking: Reworked node flags saving/inheritance so that flags enforced by docked windows via the - DockNodeFlagsOverrideSet mechanism are are not left in empty dockspace nodes once the windows gets undocked. - (#4292, #3834, #3633, #3521, #3492, #3335, #2999, #2648) -- Docking: (Internal/Experimental) Removed DockNodeFlagsOverrideClear flags from ImGuiWindowClass as - it is ambiguous how to apply them and we haven't got a use out of them yet. -- Docking: Fixed ImGuiWindowFlags_UnsavedDocument clipping label in docked windows when there are - no close button. (#5745) -- Viewports: Fix popup/tooltip created without a parent window from being given a ParentViewportId value - from the implicit/fallback window. (#4236, #2409) -- Backends: Vulkan: Fix the use of the incorrect fence for secondary viewports. (#4208) [@FunMiles] - - ------------------------------------------------------------------------ - VERSION 1.83 (Released 2021-05-24) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.83 - -Breaking Changes: - -- Backends: Obsoleted direct access to ImDrawCmd::TextureId in favor of calling ImDrawCmd::GetTexID(). (#3761) [@thedmd] - - If you are using official backends from the source tree: you have nothing to do. - - If you copied old backend code or using your own: change access to draw_cmd->TextureId to draw_cmd->GetTexID(). - Why are we doing this? - - This change will be required in the future when adding support for incremental texture atlas updates. - - Please note this won't break soon, but we are making the change ahead of time. - -Other Changes: - -- Scrolling: Fix scroll tracking with e.g. SetScrollHereX/Y() when WindowPadding < ItemSpacing. -- Scrolling: Fix scroll snapping on edge of scroll region when both scrollbars are enabled. -- Scrolling: Fix mouse wheel axis swap when using SHIFT on macOS (system already does it). (#4010) -- Window: Fix IsWindowAppearing() from returning true twice in most cases. (#3982, #1497, #1061) -- Nav: Fixed toggling menu layer while an InputText() is active not stealing active id. (#787) -- Nav: Fixed pressing Escape to leave menu layer while in a popup or child window. (#787) -- Nav, InputText: Fixed accidental menu toggling while typing non-ascii characters using AltGR. [@rokups] (#370) -- Nav: Fixed using SetItemDefaultFocus() on windows with _NavFlattened flag. (#787) -- Nav: Fixed Tabbing initial activation from skipping the first item if it is tabbable through. (#787) -- Nav: Fixed fast CTRL+Tab (where keys are only held for one single frame) from properly enabling the - menu layer of target window if it doesn't have other active layers. -- Tables: Expose TableSetColumnEnabled() in public api. (#3935) -- Tables: Better preserve widths when columns count changes. (#4046) -- Tables: Sharing more memory buffers between tables, reducing general memory footprints. (#3740) -- Tabs: Fixed mouse reordering with very fast movements (e.g. crossing multiple tabs in a single - frame and then immediately standing still (would only affect automation/bots). [@rokups] -- Menus: made MenuItem() in a menu bar reflect the 'selected' argument with a highlight. (#4128) [@mattelegende] -- Drags, Sliders, Inputs: Specifying a NULL format to Float functions default them to "%.3f" to be - consistent with the compile-time default. (#3922) -- DragScalar: Add default value for v_speed argument to match higher-level functions. (#3922) [@eliasdaler] -- ColorEdit4: Alpha default to 255 (instead of 0) when omitted in hex input. (#3973) [@squadack] -- InputText: Fix handling of paste failure (buffer full) which in some cases could corrupt the undo stack. (#4038) - (fix submitted to https://github.com/nothings/stb/pull/1158) [@Unit2Ed, @ocornut] -- InputText: Do not filter private unicode codepoints (e.g. icons) when pasted from clipboard. (#4005) [@dougbinks] -- InputText: Align caret/cursor to pixel coordinates. (#4080) [@elvissteinjr] -- InputText: Fixed CTRL+Arrow or OSX double-click leaking the presence of spaces when ImGuiInputTextFlags_Password - is used. (#4155, #4156) [@michael-swan] -- LabelText: Fixed clipping of multi-line value text when label is single-line. (#4004) -- LabelText: Fixed vertical alignment of single-line value text when label is multi-line. (#4004) -- Combos: Changed the combo popup to use a different id to also using a context menu with the default item id. - Fixed using BeginPopupContextItem() with no parameter after a combo. (#4167) -- Popups: Added 'OpenPopup(ImGuiID id)' overload to facilitate calling from nested stacks. (#3993, #331) [@zlash] -- Tweak computation of io.Framerate so it is less biased toward high-values in the first 120 frames. (#4138) -- Optimization: Disabling some of MSVC most aggressive Debug runtime checks for some simple/low-level functions - (e.g. ImVec2, ImVector) leading to a 10-20% increase of performances with MSVC "default" Debug settings. -- ImDrawList: Add and use SSE-enabled ImRsqrt() in place of 1.0f / ImSqrt(). (#4091) [@wolfpld] -- ImDrawList: Fixed/improved thickness of thick strokes with sharp angles. (#4053, #3366, #2964, #2868, #2518, #2183) - Effectively introduced a regression in 1.67 (Jan 2019), and a fix in 1.70 (Apr 2019) but the fix wasn't actually on - par with original version. Now incorporating the correct revert. -- ImDrawList: Fixed PathArcTo() regression from 1.82 preventing use of counter-clockwise angles. (#4030, #3491) [@thedmd] -- Demo: Improved popups demo and comments. -- Metrics: Added "Fonts" section with same information as available in "Style Editor">"Fonts". -- Backends: SDL2: Rework global mouse pos availability check listing supported platforms explicitly, - effectively fixing mouse access on Raspberry Pi. (#2837, #3950) [@lethal-guitar, @hinxx] -- Backends: Win32: Clearing keyboard down array when losing focus (WM_KILLFOCUS). (#2062, #3532, #3961) - [@1025798851] -- Backends: OSX: Fix keys remaining stuck when CMD-tabbing to a different application. (#3832) [@rokups] -- Backends: DirectX9: calling IDirect3DStateBlock9::Capture() after CreateStateBlock() which appears to - workaround/fix state restoring issues. Unknown exactly why so, bit of a cargo-cult fix. (#3857) -- Backends: DirectX9: explicitly setting up more graphics states to increase compatibility with unusual - non-default states. (#4063) -- Backends: DirectX10, DirectX11: fixed a crash when backing/restoring state if nothing is bound when - entering the rendering function. (#4045) [@Nemirtingas] -- Backends: GLFW: Adding bound check in KeyCallback because GLFW appears to send -1 on some setups. [#4124] -- Backends: Vulkan: Fix mapped memory Vulkan validation error when buffer sizes are not multiple of - VkPhysicalDeviceLimits::nonCoherentAtomSize. (#3957) [@AgentX1994] -- Backends: WebGPU: Update to latest specs (Chrome Canary 92 and Emscripten 2.0.20). (#4116, #3632) [@bfierz, @Kangz] -- Backends: OpenGL3: Don't try to read GL_CLIP_ORIGIN unless we're OpenGL 4.5. (#3998, #2366, #2186) [@s7jones] -- Examples: OpenGL: Add OpenGL ES 2.0 support to modern GL examples. (#2837, #3951) [@lethal-guitar, @hinxx] -- Examples: Vulkan: Rebuild swapchain on VK_SUBOPTIMAL_KHR. (#3881) -- Examples: Vulkan: Prefer using discrete GPU if there are more than one available. (#4012) [@rokups] -- Examples: SDL2: Link with shell32.lib required by SDL2main.lib since SDL 2.0.12. [#3988] -- Examples: Android: Make Android example build compatible with Gradle 7.0. (#3446) -- Docs: Improvements to description of using colored glyphs/emojis. (#4169, #3369) -- Docs: Improvements to minor mistakes in documentation comments (#3923) [@ANF-Studios] - -Docking+Viewports Branch: - -- [Breaking] Removed io.ConfigDockingWithShift config option. Behavior always equivalent to having the - option set to false (dock/undock by default, hold shift to avoid docking). (#2109) -- Docking: DockSpace() returns its node ID. -- Docking: Dockspace() never draws a background. (#3924) -- Docking: Undocking nodes/windows covering most of the monitor max their size down to 90% to ease manipulations. -- Docking: Docking node tab bar honors ItemInnerSpacing.x before first tab. (#4130) -- Docking: Tweak rendering and alignment of dock node menu marker. (#4130) -- Docking: Fixed restoring of tab order within a dockspace or a split node. -- Docking: Fixed reappearing docked windows with no close button showing a tab with extraneous space for one frame. -- Docking: Fixed multiple simultaneously reappearing window from appearing undocked for one frame. -- Viewports: Hotfix for crash in monitor array access, caused by 4b9bc4902. (#3967) -- Backends, Viewports: GLFW: Add a workaround for stuck keys after closing a GLFW window (#3837). -- Backends, Viewports: Vulkan: Rebuild swapchain on VK_SUBOPTIMAL_KHR. (#3881) - - ------------------------------------------------------------------------ - VERSION 1.82 (Released 2021-02-15) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.82 - -Breaking Changes: - -- Removed redirecting functions/enums names that were marked obsolete in 1.66 (September 2018): - - ImGui::SetScrollHere() --> use ImGui::SetScrollHereY() -- ImDrawList: upgraded AddPolyline()/PathStroke()'s "bool closed" parameter to use "ImDrawFlags flags". - - bool closed = false --> use ImDrawFlags_None, or 0 - - bool closed = true --> use ImDrawFlags_Closed - The matching ImDrawFlags_Closed value is guaranteed to always stay == 1 in the future. - Difference may not be noticeable for most but zealous type-checking tools may report a need to change. -- ImDrawList: upgraded AddRect(), AddRectFilled(), PathRect() to use ImDrawFlags instead of ImDrawCornersFlags. - - ImDrawCornerFlags_TopLeft --> use ImDrawFlags_RoundCornersTopLeft - - ImDrawCornerFlags_BotRight --> use ImDrawFlags_RoundCornersBottomRight - - ImDrawCornerFlags_None --> use ImDrawFlags_RoundCornersNone etc. - Flags now sanely defaults to 0 instead of 0x0F, consistent with all other flags in the API. - IMPORTANT: The default with rounding > 0.0f is now "round all corners" vs old implicit "round no corners": - - rounding == 0.0f + flags == 0 --> meant no rounding --> unchanged (common use) - - rounding > 0.0f + flags != 0 --> meant rounding --> unchanged (common use) - - rounding == 0.0f + flags != 0 --> meant no rounding --> unchanged (unlikely use) - - rounding > 0.0f + flags == 0 --> meant no rounding --> BREAKING (unlikely use)! - - this ONLY matters for hardcoded use of 0 with rounding > 0.0f. - - fix by using named ImDrawFlags_RoundCornersNone or rounding == 0.0f! - - this is technically the only real breaking change which we can't solve automatically (it's also uncommon). - The old ImDrawCornersFlags used awkward default values of ~0 or 0xF (4 lower bits set) to signify "round all corners" - and we sometimes encouraged using them as shortcuts. As a result the legacy path still support use of hardcoded ~0 - or any value from 0x1 or 0xF. They will behave the same with legacy paths enabled (will assert otherwise). - Courtesy of legacy untangling commity: [@rokups, @ocornut, @thedmd] -- ImDrawList: clarified that PathArcTo()/PathArcToFast() won't render with radius < 0.0f. Previously it sorts - of accidentally worked but would lead to counter-clockwise paths which and have an effect on anti-aliasing. -- InputText: renamed ImGuiInputTextFlags_AlwaysInsertMode to ImGuiInputTextFlags_AlwaysOverwrite, old name was an - incorrect description of behavior. Was ostly used by memory editor. Kept inline redirection function. (#2863) -- Moved 'misc/natvis/imgui.natvis' to 'misc/debuggers/imgui.natvis' as we will provide scripts for other debuggers. -- Style: renamed rarely used style.CircleSegmentMaxError (old default = 1.60f) - to style.CircleTessellationMaxError (new default = 0.30f) as its meaning changed. (#3808) [@thedmd] -- Win32+MinGW: Re-enabled IME functions by default even under MinGW. In July 2016, issue #738 had me incorrectly - disable those default functions for MinGW. MinGW users should: either link with -limm32, either set their - imconfig file with '#define IMGUI_DISABLE_WIN32_DEFAULT_IME_FUNCTIONS'. (#2590, #738) [@actboy168] - *EDIT* Undid in 1.84. -- Backends: Win32: Pragma linking with dwmapi.lib (Vista-era, ~9 kb). MinGW users will need to link with -ldwmapi. - -Other Changes: - -- Window, Nav: Fixed crash when calling SetWindowFocus(NULL) at the time a new window appears. (#3865) [@nem0] -- Window: Shrink close button hit-testing region when it covers an abnormally high portion of the window visible - area (e.g. when window is collapsed + moved in a corner) to facilitate moving the window away. (#3825) -- Nav: Various fixes for losing gamepad/keyboard navigation reference point when a window reappears or - when it appears while gamepad/keyboard are not being used. (#787) -- Drags: Fixed crash when using DragScalar() directly (not via common wrapper like DragFloat() etc.) - with ImGuiSliderFlags_AlwaysClamp + only one of either p_min or p_max set. (#3824) [@harry75369] -- Drags, Sliders: Fixed a bug where editing value would use wrong number if there were digits right after - format specifier (e.g. using "%f123" as a format string). [@rokups] -- Drags, Sliders: Fixed a bug where using custom formatting flags (',$,_) supported by stb_sprintf.h - would cause incorrect value to be displayed. (#3604) [@rokups] -- Drags, Sliders: Support ImGuiSliderFlags_Logarithmic flag with integers. Because why not? (#3786) -- Tables: Fixed unaligned accesses when using TableSetBgColor(ImGuiTableBgTarget_CellBg). (#3872) -- IsItemHovered(): fixed return value false positive when used after EndChild(), EndGroup() or widgets using - either of them, when the hovered location is located within a child window, e.g. InputTextMultiline(). - This is intended to have no side effects, but brace yourself for the possible comeback.. (#3851, #1370) -- Drag and Drop: can use BeginDragDropSource() for other than the left mouse button as long as the item - has an ID (for ID-less items will add new functionalities later). (#1637, #3885) -- ImFontAtlas: Added 'bool TexPixelsUseColors' output to help backend decide of underlying texture format. (#3369) - This can currently only ever be set by the Freetype renderer. -- imgui_freetype: Added ImGuiFreeTypeBuilderFlags_Bitmap flag to request Freetype loading bitmap data. - This may have an effect on size and must be called with correct size values. (#3879) [@metarutaiga] -- ImDrawList: PathArcTo() now supports "int num_segments = 0" (new default) and adaptively tessellate. - The adaptive tessellation uses look up tables, tends to be faster than old PathArcTo() while maintaining - quality for large arcs (tessellation quality derived from "style.CircleTessellationMaxError") (#3491) [@thedmd] -- ImDrawList: PathArcToFast() also adaptively tessellate efficiently. This means that large rounded corners - in e.g. hi-dpi settings will generally look better. (#3491) [@thedmd] -- ImDrawList: AddCircle, AddCircleFilled(): Tweaked default segment count calculation to honor MaxError - with more accuracy. Made default segment count always even for better looking result. (#3808) [@thedmd] -- Misc: Added GetAllocatorFunctions() to facilitate sharing allocators across DLL boundaries. (#3836) -- Misc: Added 'debuggers/imgui.gdb' and 'debuggers/imgui.natstepfilter' (along with existing 'imgui.natvis') - scripts to configure popular debuggers into skipping trivial functions when using StepInto. [@rokups] -- Backends: Android: Added native Android backend. (#3446) [@duddel] -- Backends: Win32: Added ImGui_ImplWin32_EnableAlphaCompositing() to facilitate experimenting with - alpha compositing and transparent windows. (#2766, #3447 etc.). -- Backends: OpenGL, Vulkan, DX9, DX10, DX11, DX12, Metal, WebGPU, Allegro: Rework blending equation to - preserve alpha in output buffer (using SrcBlendAlpha = ONE, DstBlendAlpha = ONE_MINUS_SRC_ALPHA consistently - accross all backends), facilitating compositing of the output buffer with another buffer. - (#2693, #2764, #2766, #2873, #3447, #3813, #3816) [@ocornut, @thedmd, @ShawnM427, @Ubpa, @aiekick] -- Backends: DX9: Fix to support IMGUI_USE_BGRA_PACKED_COLOR. (#3844) [@Xiliusha] -- Backends: DX9: Fix to support colored glyphs, using newly introduced 'TexPixelsUseColors' info. (#3844) -- Examples: Android: Added Android + GL ES3 example. (#3446) [@duddel] -- Examples: Reworked setup of clear color to be compatible with transparent values. -- CI: Use a dedicated "scheduled" workflow to trigger scheduled builds. Forks may disable this workflow if - scheduled builds builds are not required. [@rokups] -- Log/Capture: Added LogTextV, a va_list variant of LogText. [@PathogenDavid] - -Docking+Viewports Branch: - -- Viewports: Fix setting of ImGuiViewportFlags_NoRendererClear. (#3213) -- Viewports: Added GetViewportPlatformMonitor() with a safety net to keep code portable. -- Viewports, Backends: SDL: Fix missing ImGuiBackendFlags_HasSetMousePos flag in docking branch. -- Viewports, Backends: GLFW: Fix application of WantSetMousePos. (#1542, #787) - - ------------------------------------------------------------------------ - VERSION 1.81 (Released 2021-02-10) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.81 - -Breaking Changes: - -- ListBox helpers: - - Renamed ListBoxHeader(const char* label, ImVec2 size) to BeginListBox(). - - Renamed ListBoxFooter() to EndListBox(). - - Removed ListBoxHeader(const char* label, int items_count, int height_in_items = -1) in favor of specifying size. - In the redirection function, made vertical padding consistent regardless of (items_count <= height_in_items) or not. - - Kept inline redirection function for all threes (will obsolete). -- imgui_freetype: - - Removed ImGuiFreeType::BuildFontAtlas(). Kept inline redirection function. - Prefer using '#define IMGUI_ENABLE_FREETYPE', but there's a runtime selection path available too. - - The shared extra flags parameters (very rarely used) are now stored in ImFontAtlas::FontBuilderFlags. - - Renamed ImFontConfig::RasterizerFlags (used by FreeType) to ImFontConfig::FontBuilderFlags. - - Renamed ImGuiFreeType::XXX flags to ImGuiFreeTypeBuilderFlags_XXX for consistency with other API. - -Other Changes: - -- Viewports Added ImGui::GetMainViewport() as a way to get the bounds and work area of the host display. (#3789, #1542) - - In 'master' branch or without multi-viewports feature enabled: - - GetMainViewport()->Pos is always == (0,0) - - GetMainViewport()->Size is always == io.DisplaySize - - In 'docking' branch and with the multi-viewports feature enabled: - - GetMainViewport() will return information from your host Platform Window. - - In the future, we will support a "no main viewport" mode and this may return bounds of your main monitor. - - For forward compatibility with multi-viewports/multi-monitors: - - Code using (0,0) as a way to signify "upper-left of the host window" should use GetMainViewport()->Pos. - - Code using io.DisplaySize as a way to signify "size of the host window" should use GetMainViewport()->Size. - - We are also exposing a work area in ImGuiViewport ('WorkPos', 'WorkSize' vs 'Pos', 'Size' for full area): - - For a Platform Window, the work area is generally the full area minus space used by menu-bars. - - For a Platform Monitor, the work area is generally the full area minus space used by task-bars. - - All of this has been the case in 'docking' branch for a long time. What we've done is merely merging - a small chunk of the multi-viewport logic into 'master' to standardize some concepts ahead of time. -- Tables: Fixed PopItemWidth() or multi-components items not restoring per-colum ItemWidth correctly. (#3760) -- Window: Fixed minor title bar text clipping issue when FramePadding is small/zero and there are no - close button in the window. (#3731) -- SliderInt: Fixed click/drag when v_min==v_max from setting the value to zero. (#3774) [@erwincoumans] - Would also repro with DragFloat() when using ImGuiSliderFlags_Logarithmic with v_min==v_max. -- Menus: Fixed an issue with child-menu auto sizing (issue introduced in 1.80 on 2021/01/25) (#3779) -- InputText: Fixed slightly off ScrollX tracking, noticeable with large values of FramePadding.x. (#3781) -- InputText: Multiline: Fixed padding/cliprect not precisely matching single-line version. (#3781) -- InputText: Multiline: Fixed FramePadding.y worth of vertical offset when aiming with mouse. -- ListBox: Tweaked default height calculation. -- Fonts: imgui_freetype: Facilitated using FreeType integration: [@Xipiryon, @ocornut] - - Use '#define IMGUI_ENABLE_FREETYPE' in imconfig.h should make it work with no other modifications - other than compiling misc/freetype/imgui_freetype.cpp and linking with FreeType. - - Use '#define IMGUI_ENABLE_STB_TRUETYPE' if you somehow need the stb_truetype rasterizer to be - compiled in along with the FreeType one, otherwise it is enabled by default. -- Fonts: imgui_freetype: Added support for colored glyphs as supported by Freetype 2.10+ (for .ttf using CPAL/COLR - tables only). Enable the ImGuiFreeTypeBuilderFlags_LoadColor on a given font. Atlas always output directly - as RGBA8 in this situation. Likely to make sense with IMGUI_USE_WCHAR32. (#3369) [@pshurgal] -- Fonts: Fixed CalcTextSize() width rounding so it behaves more like a ceil. This is in order for text wrapping - to have enough space when provided width precisely calculated with CalcTextSize().x. (#3776) - Note that the rounding of either positions and widths are technically undesirable (e.g. #3437, #791) but - variety of code is currently on it so we are first fixing current behavior before we'll eventually change it. -- Log/Capture: Fix various new line/spacing issue when logging widgets. [@Xipiryon, @ocornut] -- Log/Capture: Improved the ASCII look of various widgets, making large dumps more easily human readable. -- ImDrawList: Fixed AddCircle()/AddCircleFilled() with (rad > 0.0f && rad < 1.0f && num_segments == 0). (#3738) - Would lead to a buffer read overflow. -- ImDrawList: Clarified PathArcTo() need for a_min <= a_max with an assert. -- ImDrawList: Fixed PathArcToFast() handling of a_min > a_max. -- Metrics: Back-ported "Viewports" debug visualizer from 'docking' branch. -- Demo: Added 'Examples->Fullscreen Window' demo using GetMainViewport() values. (#3789) -- Demo: 'Simple Overlay' demo now moves under main menu-bar (if any) using GetMainViewport()'s work area. -- Backends: Win32: Dynamically loading XInput DLL instead of linking with it, facilitate compiling with - old WindowSDK versions or running on Windows 7. (#3646, #3645, #3248, #2716) [@Demonese] -- Backends: Vulkan: Add support for custom Vulkan function loader and VK_NO_PROTOTYPES. (#3759, #3227) [@Hossein-Noroozpour] - User needs to call ImGui_ImplVulkan_LoadFunctions() with their custom loader prior to other functions. -- Backends: Metal: Fixed texture storage mode when building on Mac Catalyst. (#3748) [@Belinsky-L-V] -- Backends: OSX: Fixed mouse position not being reported when mouse buttons other than left one are down. (#3762) [@rokups] -- Backends: WebGPU: Added enderer backend for WebGPU support (imgui_impl_wgpu.cpp) (#3632) [@bfierz] - Please note that WebGPU is currently experimental, will not run on non-beta browsers, and may break. -- Examples: WebGPU: Added Emscripten+WebGPU example. (#3632) [@bfierz] -- Backends: GLFW: Added ImGui_ImplGlfw_InitForOther() initialization call to use with non OpenGL API. (#3632) - -Docking+Viewports Branch: - -- Docking: Fix losing docking information on closed windows for which the hosting node was split. (#3716) [@GamingMinds-DanielC] -- Docking: Fix gap in hit test hole when using ImGuiDockNodeFlags_PassthruCentralNode touching the edge of a viewport. (#3733) -- Viewports: (Breaking) removed ImGuiPlatformIO::MainViewport which is now pretty much unused and duplicate - (and misleading as we will evolve the concept). -- Viewports: (Breaking) turned ImGuiViewport::GetWorkPos(), ImGuiViewport::GetWorkSize() into regular fields - (WorkPos, WorkSize) before exposing in master branch. -- Viewports: Fix issue inferring viewport z-order when new popups gets created. (#3734) + Metrics updates. -- Viewports, Backends: Vulkan: handle VK_ERROR_OUT_OF_DATE_KHR when resizing secondary viewport (#3766, #3758) - - ------------------------------------------------------------------------ - VERSION 1.80 (Released 2021-01-21) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.80 - -Breaking Changes: - -- Added imgui_tables.cpp file! Manually constructed project files will need the new file added! (#3740) -- Backends: moved all backends files (imgui_impl_XXXX.cpp, imgui_impl_XXXX.h) from examples/ to backends/. (#3513) -- Renamed ImDrawList::AddBezierCurve() to ImDrawList::AddBezierCubic(). Kept inline redirection function (will obsolete). -- Renamed ImDrawList::PathBezierCurveTo() to ImDrawList::PathBezierCubicCurveTo(). Kept inline redirection function (will obsolete). -- Removed redirecting functions/enums names that were marked obsolete in 1.60 (April 2018): - - io.RenderDrawListsFn pointer -> use ImGui::GetDrawData() value and call the render function of your backend - - ImGui::IsAnyWindowFocused() -> use ImGui::IsWindowFocused(ImGuiFocusedFlags_AnyWindow) - - ImGui::IsAnyWindowHovered() -> use ImGui::IsWindowHovered(ImGuiHoveredFlags_AnyWindow) - - ImGuiStyleVar_Count_ -> use ImGuiStyleVar_COUNT - - ImGuiMouseCursor_Count_ -> use ImGuiMouseCursor_COUNT -- Removed redirecting functions/enums names that were marked obsolete in 1.61 (May 2018): - - InputFloat (... int decimal_precision ...) -> use InputFloat (... const char* format ...) with format = "%.Xf" where X was value for decimal_precision. - - same for InputFloat2()/InputFloat3()/InputFloat4() variants taking a `int decimal_precision` parameter. -- Removed redirecting functions/enums names that were marked obsolete in 1.63 (August 2018): - - ImGui::IsItemDeactivatedAfterChange() -> use ImGui::IsItemDeactivatedAfterEdit(). - - ImGuiCol_ModalWindowDarkening -> use ImGuiCol_ModalWindowDimBg - - ImGuiInputTextCallback -> use ImGuiTextEditCallback - - ImGuiInputTextCallbackData -> use ImGuiTextEditCallbackData -- If you were still using the old names, while you are cleaning up, considering enabling - IMGUI_DISABLE_OBSOLETE_FUNCTIONS in imconfig.h even temporarily to have a pass at finding - and removing up old API calls, if any remaining. -- Internals: Columns: renamed undocumented/internals ImGuiColumnsFlags_* to ImGuiOldColumnFlags_* to reduce - confusion with Tables API. Keep redirection enums (will obsolete). (#125, #513, #913, #1204, #1444, #2142, #2707) -- Renamed io.ConfigWindowsMemoryCompactTimer to io.ConfigMemoryCompactTimer as the feature now applies - to other data structures. (#2636) - -Other Changes: - -- Tables: added new Tables Beta API as a replacement for old Columns. (#3740, #2957, #125) - Check out 'Demo->Tables' for many demos. - Read API comments in imgui.h for details. Read extra commentary in imgui_tables.cpp. - - Added 16 functions: - - BeginTable(), EndTable() - - TableNextRow(), TableNextColumn(), TableSetColumnIndex() - - TableSetupColumn(), TableSetupScrollFreeze() - - TableHeadersRow(), TableHeader() - - TableGetRowIndex(), TableGetColumnCount(), TableGetColumnIndex(), TableGetColumnName(), TableGetColumnFlags() - - TableGetSortSpecs(), TableSetBgColor() - - Added 3 flags sets: - - ImGuiTableFlags (29 flags for: features, decorations, sizing policies, padding, clipping, scrolling, sorting etc.) - - ImGuiTableColumnFlags (24 flags for: width policies, default settings, sorting options, indentation options etc.) - - ImGuiTableRowFlags (1 flag for: header row) - - Added 2 structures: ImGuiTableSortSpecs, ImGuiTableColumnSortSpecs - - Added 2 enums: ImGuiSortDirection, ImGuiTableBgTarget - - Added 1 style variable: ImGuiStyleVar_CellPadding - - Added 5 style colors: ImGuiCol_TableHeaderBg, ImGuiCol_TableBorderStrong, ImGuiCol_TableBorderLight, ImGuiCol_TableRowBg, ImGuiCol_TableRowBgAlt. -- Tabs: Made it possible to append to an existing tab bar by calling BeginTabBar()/EndTabBar() again. -- Tabs: Fixed using more than 128 tabs in a tab bar (scrolling policy recommended). -- Tabs: Do not display a tooltip if the name already fits over a given tab. (#3521) -- Tabs: Fixed minor/unlikely bug skipping over a button when scrolling left with arrows. -- Tabs: Requested ideal content size (for auto-fit) doesn't affect horizontal scrolling. (#3414) -- Drag and Drop: Fix losing drop source ActiveID (and often source tooltip) when opening a TreeNode() - or CollapsingHeader() while dragging. (#1738) -- Drag and Drop: Fix drag and drop to tie same-size drop targets by chosen the later one. Fixes dragging - into a full-window-sized dockspace inside a zero-padded window. (#3519, #2717) [@Black-Cat] -- Checkbox: Added CheckboxFlags() helper with int* type (internals have a template version, not exposed). -- Clipper: Fixed incorrect end-list positioning when using ImGuiListClipper with 1 item (bug in 1.79). (#3663) [@nyorain] -- InputText: Fixed updating cursor/selection position when a callback altered the buffer in a way - where the byte count is unchanged but the decoded character count changes. (#3587) [@gqw] -- InputText: Fixed switching from single to multi-line while preserving same ID. -- Combo: Fixed using IsItemEdited() after Combo() not matching the return value from Combo(). (#2034) -- DragFloat, DragInt: very slightly increased mouse drag threshold + expressing it as a factor of default value. -- DragFloat, DragInt: added experimental io.ConfigDragClickToInputText feature to enable turning DragXXX widgets - into text input with a simple mouse click-release (without moving). (#3737) -- Nav: Fixed IsItemFocused() from returning false when Nav highlight is hidden because mouse has moved. - It's essentially been always the case but it doesn't make much sense. Instead we will aim at exposing - feedback and control of keyboard/gamepad navigation highlight and mouse hover disable flag. (#787, #2048) -- Metrics: Fixed mishandling of ImDrawCmd::VtxOffset in wireframe mesh renderer. -- Metrics: Rebranded as "Dear ImGui Metrics/Debugger" to clarify its purpose. -- ImDrawList: Added ImDrawList::AddQuadBezierCurve(), ImDrawList::PathQuadBezierCurveTo() quadratic bezier - helpers. (#3127, #3664, #3665) [@aiekick] -- Fonts: Updated GetGlyphRangesJapanese() to include a larger 2999 ideograms selection of Joyo/Jinmeiyo - kanjis, from the previous 1946 ideograms selection. This will consume a some more memory but be generally - much more fitting for Japanese display, until we switch to a more dynamic atlas. (#3627) [@vaiorabbit] -- Log/Capture: fix capture to work on clipped child windows. -- Misc: Made the ItemFlags stack shared, so effectively the ButtonRepeat/AllowKeyboardFocus states - (and others exposed in internals such as PushItemFlag) are inherited by stacked Begin/End pairs, - vs previously a non-child stacked Begin() would reset those flags back to zero for the stacked window. -- Misc: Replaced UTF-8 decoder with one based on branchless one by Christopher Wellons. [@rokups] - Super minor fix handling incomplete UTF-8 contents: if input does not contain enough bytes, decoder - returns IM_UNICODE_CODEPOINT_INVALID and consume remaining bytes (vs old decoded consumed only 1 byte). -- Misc: Fix format warnings when using gnu printf extensions in a setup that supports them (gcc/mingw). (#3592) -- Misc: Made EndFrame() assertion for key modifiers being unchanged during the frame (added in 1.76) more - lenient, allowing full mid-frame releases. This is to accommodate the use of mid-frame modal native - windows calls, which leads backends such as GLFW to send key clearing events on focus loss. (#3575) -- Style: Changed default style.WindowRounding value to 0.0f (matches default for multi-viewports). -- Style: Reduced the size of the resizing grip, made alpha less prominent. -- Style: Classic: Increase the default alpha value of WindowBg to be closer to other styles. -- Demo: Clarify usage of right-aligned items in Demo>Layout>Widgets Width. -- Backends: OpenGL3: Use glGetString(GL_VERSION) query instead of glGetIntegerv(GL_MAJOR_VERSION, ...) - when the later returns zero (e.g. Desktop GL 2.x). (#3530) [@xndcn] -- Backends: OpenGL2: Backup and restore GL_SHADE_MODEL and disable GL_NORMAL_ARRAY state to increase - compatibility with legacy code. (#3671) -- Backends: OpenGL3: Backup and restore GL_PRIMITIVE_RESTART state. (#3544) [@Xipiryon] -- Backends: OpenGL2, OpenGL3: Backup and restore GL_STENCIL_TEST enable state. (#3668) -- Backends: Vulkan: Added support for specifying which sub-pass to reference during VkPipeline creation. (@3579) [@bdero] -- Backends: DX12: Improve Windows 7 compatibility (for D3D12On7) by loading d3d12.dll dynamically. (#3696) [@Mattiwatti] -- Backends: Win32: Fix setting of io.DisplaySize to invalid/uninitialized data after hwnd has been closed. -- Backends: OSX: Fix keypad-enter key not working on MacOS. (#3554) [@rokups, @lfnoise] -- Examples: Apple+Metal: Consolidated/simplified to get closer to other examples. (#3543) [@warrenm] -- Examples: Apple+Metal: Forward events down so OS key combination like Cmd+Q can work. (#3554) [@rokups] -- Examples: Emscripten: Renamed example_emscripten/ to example_emscripten_opengl3/. (#3632) -- Examples: Emscripten: Added 'make serve' helper to spawn a web-server on localhost. (#3705) [@Horki] -- Examples: DirectX12: Move ImGui::Render() call above the first barrier to clarify its lack of effect on the graphics pipe. -- CI: Fix testing for Windows DLL builds. (#3603, #3601) [@iboB] -- Docs: Improved the wiki and added a https://github.com/ocornut/imgui/wiki/Useful-Widgets page. [@Xipiryon] - [2021/05/20: moved to https://github.com/ocornut/imgui/wiki/Useful-Extensions] -- Docs: Split examples/README.txt into docs/BACKENDS.md and docs/EXAMPLES.md, and improved them. -- Docs: Consistently renamed all occurrences of "binding" and "back-end" to "backend" in comments and docs. - -Docking+Viewports Branch: - -- Docking: Docked windows honor change of tab and text colors. (#2771) -- Docking: Support for appending into existing tab-bar made to work with Docking + internal helper DockNodeBeginAmendTabBar(). -- Docking: Added experimental TabItemFlagsOverrideSet to ImGuiWindowClass. -- Viewports: Fixed incorrect whitening of popups above a modal if both use their own viewport. -- Viewports: Backends: Vulkan: Fixed build, removed extraneous pipeline creation. (#3459, #3579) - - ------------------------------------------------------------------------ - VERSION 1.79 (Released 2020-10-08) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.79 - -Breaking Changes: - -- Fonts: Removed ImFont::DisplayOffset in favor of ImFontConfig::GlyphOffset. DisplayOffset was applied - after scaling and not very meaningful/useful outside of being needed by the default ProggyClean font. - It was also getting in the way of better font scaling, so let's get rid of it now! - If you used DisplayOffset it was probably in association to rasterizing a font at a specific size, - in which case the corresponding offset may be reported into GlyphOffset. (#1619) - If you scaled this value after calling AddFontDefault(), this is now done automatically. -- ImGuiListClipper: Renamed constructor parameters which created an ambiguous alternative to using - the ImGuiListClipper::Begin() function, with misleading edge cases. Always use ImGuiListClipper::Begin()! - Kept inline redirection function (will obsolete). - (note: imgui_memory_editor <0.40 from imgui_club/ used this old clipper API. Update your copy if needed). -- Style: Renamed style.TabMinWidthForUnselectedCloseButton to style.TabMinWidthForCloseButton. -- Renamed ImGuiSliderFlags_ClampOnInput to ImGuiSliderFlags_AlwaysClamp. Kept redirection enum (will obsolete). -- Renamed OpenPopupContextItem() back to OpenPopupOnItemClick(), REVERTED CHANGE FROM 1.77. - For variety of reason this is more self-explanatory and less error-prone. Kept inline redirection function. -- Removed return value from OpenPopupOnItemClick() - returned true on mouse release on an item - because it - is inconsistent with other popups API and makes others misleading. It's also and unnecessary: you can - use IsWindowAppearing() after BeginPopup() for a similar result. - -Other Changes: - -- Window: Fixed using non-zero pivot in SetNextWindowPos() when the window is collapsed. (#3433) -- Nav: Fixed navigation resuming on first visible item when using gamepad. [@rokups] -- Nav: Fixed using Alt to toggle the Menu layer when inside a Modal window. (#787) -- Scrolling: Fixed SetScrollHere(0) functions edge snapping when called during a frame where - ContentSize is changing (issue introduced in 1.78). (#3452). -- InputText: Added support for Page Up/Down in InputTextMultiline(). (#3430) [@Xipiryon] -- InputText: Added selection helpers in ImGuiInputTextCallbackData(). -- InputText: Added ImGuiInputTextFlags_CallbackEdit to modify internally owned buffer after an edit. - (note that InputText() already returns true on edit, the callback is useful mainly to manipulate the - underlying buffer while focus is active). -- InputText: Fixed using ImGuiInputTextFlags_Password with InputTextMultiline(). (#3427, #3428) - It is a rather unusual or useless combination of features but no reason it shouldn't work! -- InputText: Fixed minor scrolling glitch when erasing trailing lines in InputTextMultiline(). -- InputText: Fixed cursor being partially covered after using Ctrl+End key. -- InputText: Fixed callback's helper DeleteChars() function when cursor is inside the deleted block. (#3454) -- InputText: Made pressing Down arrow on the last line when it doesn't have a carriage return not move to - the end of the line (so it is consistent with Up arrow, and behave same as Notepad and Visual Studio. - Note that some other text editors instead would move the cursor to the end of the line). [@Xipiryon] -- DragFloat, DragScalar: Fixed ImGuiSliderFlags_ClampOnInput not being honored in the special case - where v_min == v_max. (#3361) -- SliderInt, SliderScalar: Fixed reaching of maximum value with inverted integer min/max ranges, both - with signed and unsigned types. Added reverse Sliders to Demo. (#3432, #3449) [@rokups] -- Text: Bypass unnecessary formatting when using the TextColored()/TextWrapped()/TextDisabled() helpers - with a "%s" format string. (#3466) -- CheckboxFlags: Display mixed-value/tristate marker when passed flags that have multiple bits set and - stored value matches neither zero neither the full set. -- BeginMenuBar: Fixed minor bug where CursorPosMax gets pushed to CursorPos prior to calling BeginMenuBar(), - so e.g. calling the function at the end of a window would often add +ItemSpacing.y to scrolling range. -- TreeNode, CollapsingHeader: Made clicking on arrow toggle toggle the open state on the Mouse Down event - rather than the Mouse Down+Up sequence, even if the _OpenOnArrow flag isn't set. This is standard behavior - and amends the change done in 1.76 which only affected cases were _OpenOnArrow flag was set. - (This is also necessary to support full multi/range-select/drag and drop operations.) -- Tabs: Added TabItemButton() to submit tab that behave like a button. (#3291) [@Xipiryon] -- Tabs: Added ImGuiTabItemFlags_Leading and ImGuiTabItemFlags_Trailing flags to position tabs or button - at either end of the tab bar. Those tabs won't be part of the scrolling region, and when reordering cannot - be moving outside of their section. Most often used with TabItemButton(). (#3291) [@Xipiryon] -- Tabs: Added ImGuiTabItemFlags_NoReorder flag to disable reordering a given tab. -- Tabs: Keep tab item close button visible while dragging a tab (independent of hovering state). -- Tabs: Fixed a small bug where closing a tab that is not selected would leave a tab hole for a frame. -- Tabs: Fixed a small bug where scrolling buttons (with ImGuiTabBarFlags_FittingPolicyScroll) would - generate an unnecessary extra draw call. -- Tabs: Fixed a small bug where toggling a tab bar from Reorderable to not Reorderable would leave - tabs reordered in the tab list popup. [@Xipiryon] -- Columns: Fix inverted ClipRect being passed to renderer when using certain primitives inside of - a fully clipped column. (#3475) [@szreder] -- Popups, Tooltips: Fix edge cases issues with positioning popups and tooltips when they are larger than - viewport on either or both axises. [@Rokups] -- Fonts: AddFontDefault() adjust its vertical offset based on floor(size/13) instead of always +1. - Was previously done by altering DisplayOffset.y but wouldn't work for DPI scaled font. -- Metrics: Various tweaks, listing windows front-to-back, greying inactive items when possible. -- Demo: Add simple InputText() callbacks demo (aside from the more elaborate ones in 'Examples->Console'). -- Backends: OpenGL3: Fix to avoid compiling/calling glBindSampler() on ES or pre 3.3 contexts which have - the defines set by a loader. (#3467, #1985) [@jjwebb] -- Backends: Vulkan: Some internal refactor aimed at allowing multi-viewport feature to create their - own render pass. (#3455, #3459) [@FunMiles] -- Backends: DX12: Clarified that imgui_impl_dx12 can be compiled on 32-bit systems by redefining - the ImTextureID to be 64-bit (e.g. '#define ImTextureID ImU64' in imconfig.h). (#301) -- Backends: DX12: Fix debug layer warning when scissor rect is zero-sized. (#3472, #3462) [@StoneWolf] -- Examples: Vulkan: Reworked buffer resize handling, fix for Linux/X11. (#3390, #2626) [@RoryO] -- Examples: Vulkan: Switch validation layer to use "VK_LAYER_KHRONOS_validation" instead of - "VK_LAYER_LUNARG_standard_validation" which is deprecated (#3459) [@FunMiles] -- Examples: DX12: Enable breaking on any warning/error when debug interface is enabled. -- Examples: DX12: Added '#define ImTextureID ImU64' in project and build files to also allow building - on 32-bit systems. Added project to default Visual Studio solution file. (#301) - -Docking+Viewports Branch: - -- Docking: DockSpace() emits ItemSize() properly (useful when not filling all space). -- Docking: Fixed docking while hovering a child window. (#3420) broken by 85a661d. Improve metrics debugging. -- Docking: Fix honoring payload filter with overlapping nodes (we incorrectly over-relied on g.HoveredDockNode - when making change for #3398). -- Docking: Fix handling of WindowMenuButtonPosition == ImGuiDir_None in Docking Nodes. (#3499) -- Viewports: Fixed a rare edge-case if the window targeted by CTRL+Tab stops being rendered. -- Viewports, Backends: DX12: Make secondary viewport format match main viewport one (#3462) {@BeastLe9enD] -- Viewports: Backends: Vulkan: Removed unused shader code. Fix leaks. Avoid unnecessary pipeline creation for main - viewport. (#3459) + Add ImGui_ImplVulkanH_CreateWindowSwapChain in ImGui_ImplVulkanH_CreateOrResizeWindow(). -- Viewports: Backends: DirectX9: Recover from D3DERR_DEVICELOST on secondary viewports. (#3424) -- Viewports, Backends: Win32: Fix toggling of ImGuiViewportFlags_TopMost (#3477) [@Kodokuna] -- Viewports: Backends: GLFW: Workaround for cases where glfwGetMonitorWorkarea fails (#3457) [@dougbinks] - - ------------------------------------------------------------------------ - VERSION 1.78 (Released 2020-08-18) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.78 - -Breaking Changes: - -- Obsoleted use of the trailing 'float power=1.0f' parameter for those functions: [@Shironekoben, @ocornut] - - DragFloat(), DragFloat2(), DragFloat3(), DragFloat4(), DragFloatRange2(), DragScalar(), DragScalarN() - - SliderFloat(), SliderFloat2(), SliderFloat3(), SliderFloat4(), SliderScalar(), SliderScalarN() - - VSliderFloat(), VSliderScalar() - Replaced the final 'float power=1.0f' argument with ImGuiSliderFlags defaulting to 0 (as with all our flags). - Worked out a backward-compatibility scheme so hopefully most C++ codebase should not be affected. - In short, when calling those functions: - - If you omitted the 'power' parameter (likely!), you are not affected. - - If you set the 'power' parameter to 1.0f (same as previous default value): - - Your compiler may warn on float>int conversion. - - Everything else will work (but will assert if IMGUI_DISABLE_OBSOLETE_FUNCTIONS is defined). - - You can replace the 1.0f value with 0 to fix the warning, and be technically correct. - - If you set the 'power' parameter to >1.0f (to enable non-linear editing): - - Your compiler may warn on float>int conversion. - - Code will assert at runtime for IM_ASSERT(power == 1.0f) with the following assert description: - "Call Drag function with ImGuiSliderFlags_Logarithmic instead of using the old 'float power' function!". - - In case asserts are disabled, the code will not crash and enable the _Logarithmic flag. - - You can replace the >1.0f value with ImGuiSliderFlags_Logarithmic to fix the warning/assert - and get a _similar_ effect as previous uses of power >1.0f. - See https://github.com/ocornut/imgui/issues/3361 for all details. - For shared code, you can version check at compile-time with `#if IMGUI_VERSION_NUM >= 17704`. - Kept inline redirection functions (will obsolete) apart for: DragFloatRange2(), VSliderFloat(), VSliderScalar(). - For those three the 'float power=1.0f' version was removed directly as they were most unlikely ever used. -- DragInt, DragFloat, DragScalar: Obsoleted use of v_min > v_max to lock edits (introduced in 1.73, this was not - demoed nor documented much, will be replaced a more generic ReadOnly feature). - -Other Changes: - -- Nav: Fixed clicking on void (behind any windows) from not clearing the focused window. - This would be problematic e.g. in situation where the application relies on io.WantCaptureKeyboard - flag being cleared accordingly. (bug introduced in 1.77 WIP on 2020/06/16) (#3344, #2880) -- Window: Fixed clicking over an item which hovering has been disabled (e.g inhibited by a popup) - from marking the window as moved. -- Drag, Slider: Added ImGuiSliderFlags parameters. - - For float functions they replace the old trailing 'float power=1.0' parameter. - (See #3361 and the "Breaking Changes" block above for all details). - - Added ImGuiSliderFlags_Logarithmic flag to enable logarithmic editing - (generally more precision around zero), as a replacement to the old 'float power' parameter - which was obsoleted. (#1823, #1316, #642) [@Shironekoben, @AndrewBelt] - - Added ImGuiSliderFlags_ClampOnInput flag to force clamping value when using - CTRL+Click to type in a value manually. (#1829, #3209, #946, #413). - [note: RENAMED to ImGuiSliderFlags_AlwaysClamp in 1.79]. - - Added ImGuiSliderFlags_NoRoundToFormat flag to disable rounding underlying - value to match precision of the display format string. (#642) - - Added ImGuiSliderFlags_NoInput flag to disable turning widget into a text input - with CTRL+Click or Nav Enter. -- Nav, Slider: Fix using keyboard/gamepad controls with certain logarithmic sliders where - pushing a direction near zero values would be cancelled out. [@Shironekoben] -- DragFloatRange2, DragIntRange2: Fixed an issue allowing to drag out of bounds when both - min and max value are on the same value. (#1441) -- InputText, ImDrawList: Fixed assert triggering when drawing single line of text with more - than ~16 KB characters. (Note that current code is going to show corrupted display if after - clipping, more than 16 KB characters are visible in the same low-level ImDrawList::RenderText() - call. ImGui-level functions such as TextUnformatted() are not affected. This is quite rare - but it will be addressed later). (#3349) -- Selectable: Fixed highlight/hit extent when used with horizontal scrolling (in or outside columns). - Also fixed related text clipping when used in a column after the first one. (#3187, #3386) -- Scrolling: Avoid SetScroll, SetScrollFromPos functions from snapping on the edge of scroll - limits when close-enough by (WindowPadding - ItemPadding), which was a tweak with too many - side-effects. The behavior is still present in SetScrollHere functions as they are more explicitly - aiming at making widgets visible. May later be moved to a flag. -- Tabs: Allow calling SetTabItemClosed() after a tab has been submitted (will process next frame). -- InvisibleButton: Made public a small selection of ImGuiButtonFlags (previously in imgui_internal.h) - and allowed to pass them to InvisibleButton(): ImGuiButtonFlags_MouseButtonLeft/Right/Middle. - This is a small but rather important change because lots of multi-button behaviors could previously - only be achieved using lower-level/internal API. Now also available via high-level InvisibleButton() - with is a de-facto versatile building block to creating custom widgets with the public API. -- Fonts: Fixed ImFontConfig::GlyphExtraSpacing and ImFontConfig::PixelSnapH settings being pulled - from the merged/target font settings when merging fonts, instead of being pulled from the source - font settings. -- ImDrawList: Thick anti-aliased strokes (> 1.0f) with integer thickness now use a texture-based - path, reducing the amount of vertices/indices and CPU/GPU usage. (#3245) [@Shironekoben] - - This change will facilitate the wider use of thick borders in future style changes. - - Requires an extra bit of texture space (~64x64 by default), relies on GPU bilinear filtering. - - Set `io.AntiAliasedLinesUseTex = false` to disable rendering using this method. - - Clear `ImFontAtlasFlags_NoBakedLines` in ImFontAtlas::Flags to disable baking data in texture. -- ImDrawList: changed AddCircle(), AddCircleFilled() default num_segments from 12 to 0, effectively - enabling auto-tessellation by default. Tweak tessellation in Style Editor->Rendering section, or - by modifying the 'style.CircleSegmentMaxError' value. [@ShironekoBen] -- ImDrawList: Fixed minor bug introduced in 1.75 where AddCircle() with 12 segments would generate - an extra vertex. (This bug was mistakenly marked as fixed in earlier 1.77 release). [@ShironekoBen] -- Demo: Improved "Custom Rendering"->"Canvas" demo with a grid, scrolling and context menu. - Also showcase using InvisibleButton() with multiple mouse buttons flags. -- Demo: Improved "Layout & Scrolling" -> "Clipping" section. -- Demo: Improved "Layout & Scrolling" -> "Child Windows" section. -- Style Editor: Added preview of circle auto-tessellation when editing the corresponding value. -- Backends: OpenGL3: Added support for glad2 loader. (#3330) [@moritz-h] -- Backends: Allegro 5: Fixed horizontal scrolling direction with mouse wheel / touch pads (it seems - like Allegro 5 reports it differently from GLFW and SDL). (#3394, #2424, #1463) [@nobody-special666] -- Examples: Vulkan: Fixed GLFW+Vulkan and SDL+Vulkan clear color not being set. (#3390) [@RoryO] -- CI: Emscripten has stopped their support for their fastcomp backend, switching to latest sdk [@Xipiryon] - -Docking+Viewports Branch: - -- Docking: Made DockBuilderAddNode() automatically call DockBuilderRemoveNode(). (#3399, #2109) -- Docking: Storing HoveredDockNode in context which can be useful for easily detecting e.g. hovering an - empty node. (#3398) -- Docking: Fixed docking overlay bits appearing at (0,0), because of 43bd80a. Most typically noticeable - when disabling multi-viewport. -- Docking: Workaround recovery for node created without the _DockSpace flags later becoming a DockSpace. (#3340) -- Docking: Rework size allocations to recover when there's no enough room for nodes + do not hold on - _WantLockSizeOnce forever. (#3328) -- Docking: Rework size allocation to allow user code to override node sizes. Not all edge cases will be - properly handled but this is a step toward toolbar emitting size constraints. -- Docking: Added experimental flags to perform more docking filtering and disable resize per axis. - Designed for toolbar patterns. -- Viewports, Backends, GLFW: Use GLFW_MOUSE_PASSTHROUGH when available. -- Viewports, Backends: DX12: Fixed issue on shutdown when viewports are disabled. (#3347) - - ------------------------------------------------------------------------ - VERSION 1.77 (Released 2020-06-29) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.77 - -Breaking Changes: - -- Removed unnecessary ID (first arg) of ImFontAtlas::AddCustomRectRegular() function. Please - note that this is a Beta api and will likely be reworked in order to support multi-DPI across - multiple monitors. -- Renamed OpenPopupOnItemClick() to OpenPopupContextItem(). Kept inline redirection function (will obsolete). - [NOTE: THIS WAS REVERTED IN 1.79] -- Removed BeginPopupContextWindow(const char*, int mouse_button, bool also_over_items) in favor - of BeginPopupContextWindow(const char*, ImGuiPopupFlags flags) with ImGuiPopupFlags_NoOverItems. - Kept inline redirection function (will obsolete). -- Removed obsoleted CalcItemRectClosestPoint() entry point (has been asserting since December 2017). - -Other Changes: - -- TreeNode: Fixed bug where BeginDragDropSource() failed when the _OpenOnDoubleClick flag is - enabled (bug introduced in 1.76, but pre-1.76 it would also fail unless the _OpenOnArrow - flag was also set, and _OpenOnArrow is frequently set along with _OpenOnDoubleClick). -- TreeNode: Fixed bug where dragging a payload over a TreeNode() with either _OpenOnDoubleClick - or _OpenOnArrow would open the node. (#143) -- Windows: Fix unintended feedback loops when resizing windows close to main viewport edges. [@rokups] -- Tabs: Added style.TabMinWidthForUnselectedCloseButton settings: - - Set to 0.0f (default) to always make a close button appear on hover (same as Chrome, VS). - - Set to FLT_MAX to only display a close button when selected (merely hovering is not enough). - - Set to an intermediary value to toggle behavior based on width (same as Firefox). -- Tabs: Added a ImGuiTabItemFlags_NoTooltip flag to disable the tooltip for individual tab item - (vs ImGuiTabBarFlags_NoTooltip for entire tab bar). [@Xipiryon] -- Popups: All functions capable of opening popups (OpenPopup*, BeginPopupContext*) now take a new - ImGuiPopupFlags sets of flags instead of a mouse button index. The API is automatically backward - compatible as ImGuiPopupFlags is guaranteed to hold mouse button index in the lower bits. -- Popups: Added ImGuiPopupFlags_NoOpenOverExistingPopup for OpenPopup*/BeginPopupContext* functions - to first test for the presence of another popup at the same level. -- Popups: Added ImGuiPopupFlags_NoOpenOverItems for BeginPopupContextWindow() - similar to testing - for !IsAnyItemHovered() prior to doing an OpenPopup(). -- Popups: Added ImGuiPopupFlags_AnyPopupId and ImGuiPopupFlags_AnyPopupLevel flags for IsPopupOpen(), - allowing to check if any popup is open at the current level, if a given popup is open at any popup - level, if any popup is open at all. -- Popups: Fix an edge case where programmatically closing a popup while clicking on its empty space - would attempt to focus it and close other popups. (#2880) -- Popups: Fix BeginPopupContextVoid() when clicking over the area made unavailable by a modal. (#1636) -- Popups: Clarified some of the comments and function prototypes. -- Modals: BeginPopupModal() doesn't set the ImGuiWindowFlags_NoSavedSettings flag anymore, and will - not always be auto-centered. Note that modals are more similar to regular windows than they are to - popups, so api and behavior may evolve further toward embracing this. (#915, #3091) - Enforce centering using e.g. SetNextWindowPos(io.DisplaySize * 0.5f, ImGuiCond_Appearing, ImVec2(0.5f,0.5f)). -- Metrics: Added a "Settings" section with some details about persistent ini settings. -- Nav, Menus: Fix vertical wrap-around in menus or popups created with multiple appending calls to - BeginMenu()/EndMenu() or BeginPopup(0/EndPopup(). (#3223, #1207) [@rokups] -- Drag and Drop: Fixed unintended fallback "..." tooltip display during drag operation when - drag source uses _SourceNoPreviewTooltip flags. (#3160) [@rokups] -- Columns: Lower overhead on column switches and switching to background channel. - Benefits Columns but was primarily made with Tables in mind! -- Fonts: Fix GetGlyphRangesKorean() end-range to end at 0xD7A3 (instead of 0xD79D). (#348, #3217) [@marukrap] -- ImDrawList: Fixed an issue where draw command merging or primitive unreserve while crossing the - VtxOffset boundary would lead to draw commands with wrong VtxOffset. (#3129, #3163, #3232, #2591) - [@thedmd, @Shironekoben, @sergeyn, @ocornut] -- ImDrawList, ImDrawListSplitter, Columns: Fixed an issue where changing channels with different - TextureId, VtxOffset would incorrectly apply new settings to draw channels. (#3129, #3163) - [@ocornut, @thedmd, @Shironekoben] -- ImDrawList, ImDrawListSplitter, Columns: Fixed an issue where starting a split when current - VtxOffset was not zero would lead to draw commands with wrong VtxOffset. (#2591) -- ImDrawList, ImDrawListSplitter, Columns: Fixed an issue where starting a split right after - a callback draw command would incorrectly override the callback draw command. -- Misc, Freetype: Fix for rare case where FT_Get_Char_Index() succeeds but FT_Load_Glyph() fails. -- Docs: Improved and moved font documentation to docs/FONTS.md so it can be readable on the web. - Updated various links/wiki accordingly. Added FAQ entry about DPI. (#2861) [@ButternCream, @ocornut] -- CI: Added CI test to verify we're never accidentally dragging libstdc++ (on some compiler setups, - static constructors for non-pod data seems to drag in libstdc++ due to thread-safety concerns). - Fixed a static constructor which led to this dependency on some compiler setups. [@rokups] -- Backends: Win32: Support for #define NOGDI, won't try to call GetDeviceCaps(). (#3137, #2327) -- Backends: Win32: Fix _WIN32_WINNT < 0x0600 (MinGW defaults to 0x502 == Windows 2003). (#3183) -- Backends: SDL: Report a zero display-size when window is minimized, consistent with other backends, - making more render/clipping code use an early out path. -- Backends: OpenGL: Fixed handling of GL 4.5+ glClipControl(GL_UPPER_LEFT) by inverting the - projection matrix top and bottom values. (#3143, #3146) [@u3shit] -- Backends: OpenGL: On OSX, if unspecified by app, made default GLSL version 150. (#3199) [@albertvaka] -- Backends: OpenGL: Fixed loader auto-detection to not interfere with ES2/ES3 defines. (#3246) [@funchal] -- Backends: Vulkan: Fixed error in if initial frame has no vertices. (#3177) -- Backends: Vulkan: Fixed edge case where render callbacks wouldn't be called if the ImDrawData - structure didn't have any vertices. (#2697) [@kudaba] -- Backends: OSX: Added workaround to avoid fast mouse clicks. (#3261, #1992, #2525) [@nburrus] -- Examples: GLFW+Vulkan, SDL+Vulkan: Fix for handling of minimized windows. (#3259) -- Examples: Apple: Fixed example_apple_metal and example_apple_opengl2 using imgui_impl_osx.mm - not forwarding right and center mouse clicks. (#3260) [@nburrus] - -Docking+Viewports Branch: - -- Viewports: Don't set ImGuiViewportFlags_NoRendererClear when ImGuiWindowFlags_NoBackground is set. (#3213) -- Viewports: Report minimized viewports as zero DisplaySize to be consistent with main branch. (#1542) -- Docking, Settings: Allow reload of settings data at runtime. (#2573) -- Backends, GLFW: Fix windows resizing incorrectly on Linux due to GLFW firing window positioning - callbacks on next frame after window is resized manually. (#2117) -- Backends: DX12: Fix OBJECT_DELETED_WHILE_STILL_IN_USE on viewport resizing. (#3210) -- Backends: DX12: Fix for crash caused by early resource release. (#3121) -- Backends, Win32: Request monitor update when DPI awareness is enabled to make sure they have the correct DPI settings. - - ------------------------------------------------------------------------ - VERSION 1.76 (Released 2020-04-12) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.76 - -Other Changes: - -- Drag and Drop, Nav: Disabling navigation arrow keys when drag and drop is active. In the docking - branch pressing arrow keys while dragging a window from a tab could trigger an assert. (#3025) -- BeginMenu: Using same ID multiple times appends content to a menu. (#1207) [@rokups] -- BeginMenu: Fixed a bug where SetNextWindowXXX data before a BeginMenu() would not be cleared - when the menu is not open. (#3030) -- InputText: Fixed password fields displaying ASCII spaces as blanks instead of using the '*' - glyph. (#2149, #515) -- Selectable: Fixed honoring style.SelectableTextAlign with unspecified size. (#2347, #2601) -- Selectable: Allow using ImGuiSelectableFlags_SpanAllColumns in other columns than first. (#125) -- TreeNode: Made clicking on arrow with _OpenOnArrow toggle the open state on the Mouse Down - event rather than the Mouse Down+Up sequence (this is rather standard behavior). -- ColorButton: Added ImGuiColorEditFlags_NoBorder flag to remove the border normally enforced - by default for standalone ColorButton. -- Nav: Fixed interactions with ImGuiListClipper, so e.g. Home/End result would not clip the - landing item on the landing frame. (#787) -- Nav: Fixed currently focused item from ever being clipped by ItemAdd(). (#787) -- Scrolling: Fixed scrolling centering API leading to non-integer scrolling values and initial - cursor position. This would often get fixed after the fix item submission, but using the - ImGuiListClipper as the first thing after Begin() could largely break size calculations. (#3073) -- Added optional support for Unicode plane 1-16 (#2538, #2541, #2815) [@cloudwu, @samhocevar] - - Compile-time enable with '#define IMGUI_USE_WCHAR32' in imconfig.h. - - More onsistent handling of unsupported code points (0xFFFD). - - Surrogate pairs are supported when submitting UTF-16 data via io.AddInputCharacterUTF16(), - allowing for more complete CJK input. - - sizeof(ImWchar) goes from 2 to 4. IM_UNICODE_CODEPOINT_MAX goes from 0xFFFF to 0x10FFFF. - - Various structures such as ImFont, ImFontGlyphRangesBuilder will use more memory, this - is currently not particularly efficient. -- Columns: undid the change in 1.75 were Columns()/BeginColumns() were preemptively limited - to 64 columns with an assert. (#3037, #125) -- Window: Fixed a bug with child window inheriting ItemFlags from their parent when the child - window also manipulate the ItemFlags stack. (#3024) [@Stanbroek] -- Font: Fixed non-ASCII space occasionally creating unnecessary empty looking polygons. -- Misc: Added an explicit compile-time test for non-scoped IM_ASSERT() macros to redirect users - to a solution rather than encourage people to add braces in the codebase. -- Misc: Added additional checks in EndFrame() to verify that io.KeyXXX values have not been - tampered with between NewFrame() and EndFrame(). -- Misc: Made default clipboard handlers for Win32 and OSX use a buffer inside the main context - instead of a static buffer, so it can be freed properly on Shutdown. (#3110) -- Misc, Freetype: Fixed support for IMGUI_STB_RECT_PACK_FILENAME compile time directive - in imgui_freetype.cpp (matching support in the regular code path). (#3062) [@DonKult] -- Metrics: Made Tools section more prominent. Showing wire-frame mesh directly hovering the ImDrawCmd - instead of requiring to open it. Added options to disable bounding box and mesh display. - Added notes on inactive/gc-ed windows. -- Demo: Added black and white and color gradients to Demo>Examples>Custom Rendering. -- CI: Added more tests on the continuous-integration server: extra warnings for Clang/GCC, building - SDL+Metal example, building imgui_freetype.cpp, more compile-time imconfig.h settings: disabling - obsolete functions, enabling 32-bit ImDrawIdx, enabling 32-bit ImWchar, disabling demo. [@rokups] -- Backends: OpenGL3: Fixed version check mistakenly testing for GL 4.0+ instead of 3.2+ to enable - ImGuiBackendFlags_RendererHasVtxOffset, leaving 3.2 contexts without it. (#3119, #2866) [@wolfpld] -- Backends: OpenGL3: Added include support for older glbinding 2.x loader. (#3061) [@DonKult] -- Backends: Win32: Added ImGui_ImplWin32_EnableDpiAwareness(), ImGui_ImplWin32_GetDpiScaleForHwnd(), - ImGui_ImplWin32_GetDpiScaleForMonitor() helpers functions (backported from the docking branch). - Those functions makes it easier for example apps to support hi-dpi features without setting up - a manifest. -- Backends: Win32: Calling AddInputCharacterUTF16() from WM_CHAR message handler in order to support - high-plane surrogate pairs. (#2815) [@cloudwu, @samhocevar] -- Backends: SDL: Added ImGui_ImplSDL2_InitForMetal() for API consistency (even though the function - currently does nothing). -- Backends: SDL: Fixed mapping for ImGuiKey_KeyPadEnter. (#3031) [@Davido71] -- Examples: Win32+DX12: Fixed resizing main window, enabled debug layer. (#3087, #3115) [@sergeyn] -- Examples: SDL+DX11: Fixed resizing main window. (#3057) [@joeslay] -- Examples: Added SDL+Metal example application. (#3017) [@coding-jackalope] - -Docking+Viewports Branch: - -- Docking: Fixed assert preventing dockspace from being created instead a hidden tab. (#3101) -- Viewports: Fixed secondary viewports accidentally merging into a minimized host viewport. (#3118) -- Viewports, Docking: Added per-viewport work area system for e.g. menu-bars. Fixed DockspaceOverViewport() - and demo code (overlay etc) accordingly. (#3035, #2889, #2474, #1542, #2109) -- Viewports: Improve menu positioning in multi-monitor setups. [@rokups] -- Viewports: Software mouse cursor is also scaled by current DpiScale. (amend #939) -- Viewports: Avoid manually clipping resize grips and borders, which messes up with automation ability - to locate those items. Also simpler and more standard. -- Viewports: Fix for UWP in the imgui_impl_win32.cpp IME handler. (#2895, #2892). -- Viewports: Bunch of extra of comments to facilitate setting up multi-viewports. -- Viewports, GLFW: Avoid using window positioning workaround for GLFW 3.3+ versions that have it fixed. - - ------------------------------------------------------------------------ - VERSION 1.75 (Released 2020-02-10) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.75 - -Breaking Changes: - -- Removed redirecting functions/enums names that were marked obsolete in 1.53 (December 2017): - - ShowTestWindow() -> use ShowDemoWindow() - - IsRootWindowFocused() -> use IsWindowFocused(ImGuiFocusedFlags_RootWindow) - - IsRootWindowOrAnyChildFocused() -> use IsWindowFocused(ImGuiFocusedFlags_RootAndChildWindows) - - SetNextWindowContentWidth(w) -> use SetNextWindowContentSize(ImVec2(w, 0.0f) - - GetItemsLineHeightWithSpacing() -> use GetFrameHeightWithSpacing() - - ImGuiCol_ChildWindowBg -> use ImGuiCol_ChildBg - - ImGuiStyleVar_ChildWindowRounding -> use ImGuiStyleVar_ChildRounding - - ImGuiTreeNodeFlags_AllowOverlapMode -> use ImGuiTreeNodeFlags_AllowItemOverlap - - IMGUI_DISABLE_TEST_WINDOWS -> use IMGUI_DISABLE_DEMO_WINDOWS - If you were still using the old names, while you are cleaning up, considering enabling - IMGUI_DISABLE_OBSOLETE_FUNCTIONS in imconfig.h even temporarily to have a pass at finding - and removing up old API calls, if any remaining. -- Removed implicit default parameter to IsMouseDragging(int button = 0) to be consistent - with other mouse functions (none of the other functions have it). -- Obsoleted calling ImDrawList::PrimReserve() with a negative count (which was vaguely - documented and rarely if ever used). Instead we added an explicit PrimUnreserve() API - which can be implemented faster. Also clarified pre-existing constraints which weren't - documented (can only unreserve from the last reserve call). If you suspect you ever - used that feature before (very unlikely, but grep for call to PrimReserve in your code), - you can #define IMGUI_DEBUG_PARANOID in imconfig.h to catch existing calls. [@ShironekoBen] -- ImDrawList::AddCircle()/AddCircleFilled() functions don't accept negative radius. -- Limiting Columns()/BeginColumns() api to 64 columns with an assert. While the current code - technically supports it, future code may not so we're putting the restriction ahead. - [Undid that change in 1.76] -- imgui_internal.h: changed ImRect() default constructor initializes all fields to 0.0f instead - of (FLT_MAX,FLT_MAX,-FLT_MAX,-FLT_MAX). If you used ImRect::Add() to create bounding boxes by - adding points into it without explicit initialization, you may need to fix your initial value. - -Other Changes: - -- Inputs: Added ImGuiMouseButton enum for convenience (e.g. ImGuiMouseButton_Right=1). - We forever guarantee that the existing value will not changes so existing code is free to use 0/1/2. -- Nav: Fixed a bug where the initial CTRL-Tab press while in a child window sometimes selected - the current root window instead of always selecting the previous root window. (#787) -- ColorEdit: Fix label alignment when using ImGuiColorEditFlags_NoInputs. (#2955) [@rokups] -- ColorEdit: In HSV display of a RGB stored value, attempt to locally preserve Saturation - when Value==0.0 (similar to changes done in 1.73 for Hue). Removed Hue editing lock since - those improvements in 1.73 makes them unnecessary. (#2722, #2770). [@rokups] -- ColorEdit: "Copy As" context-menu tool shows hex values with a '#' prefix instead of '0x'. -- ColorEdit: "Copy As" content-menu tool shows hex values both with/without alpha when available. -- InputText: Fix corruption or crash when executing undo after clearing input with ESC, as a - byproduct we are allowing to later undo the revert with a CTRL+Z. (#3008). -- InputText: Fix using a combination of _CallbackResize (e.g. for std::string binding), along with the - _EnterReturnsTrue flag along with the rarely used property of using an InputText without persisting - user-side storage. Previously if you had e.g. a local unsaved std::string and reading result back - from the widget, the user string object wouldn't be resized when Enter key was pressed. (#3009) -- MenuBar: Fix minor clipping issue where occasionally a menu text can overlap the right-most border. -- Window: Fix SetNextWindowBgAlpha(1.0f) failing to override alpha component. (#3007) [@Albog] -- Window: When testing for the presence of the ImGuiWindowFlags_NoBringToFrontOnFocus flag we - test both the focused/clicked window (which could be a child window) and the root window. -- ImDrawList: AddCircle(), AddCircleFilled() API can now auto-tessellate when provided a segment - count of zero. Alter tessellation quality with 'style.CircleSegmentMaxError'. [@ShironekoBen] -- ImDrawList: Add AddNgon(), AddNgonFilled() API with a guarantee on the explicit segment count. - In the current branch they are essentially the same as AddCircle(), AddCircleFilled() but as - we will rework the circle rendering functions to use textures and automatic segment count - selection, those new api can fill a gap. [@ShironekoBen] -- Columns: ImDrawList::Channels* functions now work inside columns. Added extra comments to - suggest using user-owned ImDrawListSplitter instead of ImDrawList functions. [@rokups] -- Misc: Added ImGuiMouseCursor_NotAllowed enum so it can be used by more shared widgets. [@rokups] -- Misc: Added IMGUI_DISABLE compile-time definition to make all headers and sources empty. -- Misc: Disable format checks when using stb_printf, to allow using extra formats. - Made IMGUI_USE_STB_SPRINTF a properly documented imconfig.h flag. (#2954) [@loicmolinari] -- Misc: Added misc/single_file/imgui_single_file.h, We use this to validate compiling all *.cpp - files in a same compilation unit. Actual users of that technique (also called "Unity builds") - can generally provide this themselves, so we don't really recommend you use this. [@rokups] -- CI: Added PVS-Studio static analysis on the continuous-integration server. [@rokups] -- Backends: GLFW, SDL, Win32, OSX, Allegro: Added support for ImGuiMouseCursor_NotAllowed. [@rokups] -- Backends: GLFW: Added support for the missing mouse cursors newly added in GLFW 3.4+. [@rokups] -- Backends: SDL: Wayland: use SDL_GetMouseState (because there is no global mouse state available - on Wayland). (#2800, #2802) [@NeroBurner] -- Backends: GLFW, SDL: report Windows key (io.KeySuper) as always released. Neither GLFW nor SDL can - correctly report the key release in every cases (e.g. when using Win+V) causing problems with some - widgets. The next release of GLFW (3.4+) will have a fix for it. However since it is both difficult - and discouraged to make use of this key for Windows application anyway, we just hide it. (#2976) -- Backends: Win32: Added support for #define IMGUI_IMPL_WIN32_DISABLE_GAMEPAD to disable all - XInput using code, and IMGUI_IMPL_WIN32_DISABLE_LINKING_XINPUT to disable linking with XInput, - the later may be problematic if compiling with recent Windows SDK and you want your app to run - on Windows 7. You can instead try linking with Xinput9_1_0.lib instead. (#2716) -- Backends: Glut: Improved FreeGLUT support for MinGW. (#3004) [@podsvirov] -- Backends: Emscripten: Avoid forcefully setting IMGUI_DISABLE_FILE_FUNCTIONS. (#3005) [@podsvirov] -- Examples: OpenGL: Explicitly adding -DIMGUI_IMPL_OPENGL_LOADER_GL3W to Makefile to match linking - settings (otherwise if another loader such as Glew is accessible, the OpenGL3 backend might - automatically use it). (#2919, #2798) -- Examples: OpenGL: Added support for glbinding OpenGL loader. (#2870) [@rokups] -- Examples: Emscripten: Demonstrating embedding fonts in Makefile and code. (#2953) [@Oipo] -- Examples: Metal: Wrapped main loop in @autoreleasepool block to ensure allocations get freed - even if underlying system event loop gets paused due to app nap. (#2910, #2917) [@bear24rw] - -Docking+Viewports Branch: - -- Docking + Nav: Fixed messed up Ctrl+Tab order with docked windows. -- Docking + Nav: Fixed failing to restore NavId when refocusing a child within a docked window. -- Docking + Nav: Fixed failing to restore NavId when refocusing due to missing nav window (when - it stops being submitted). -- Docking: Fixed a bug where the tab bar of a hidden dockspace would keep requesting focus. (#2960) -- Docking: Added experimental DockNodeFlagsOverrideSet/DockNodeFlagsOverrideClear flags in ImGuiWindowClass - (currently experimenting with toolbar idioms). -- Viewports: Fix resizing viewport-owning windows when mouse pos is outside the InnerClipRect - (can happen with OS decoration enabled). -- Viewports: Preserve last known size for minimized main viewport to be consistent with secondary viewports. -- Backends: SDL: Honor NoTaskBarIcon flag under non Win32 OS. (#2117) -- Backends: GLFW, SDL: Platform monitors declared properly even if multi-viewport is not enabled. - - ------------------------------------------------------------------------ - VERSION 1.74 (Released 2019-11-25) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.74 - -Breaking Changes: - -- Removed redirecting functions/enums names that were marked obsolete in 1.52 (October 2017): - - Begin() [old 5 args version] -> use Begin() [3 args], use SetNextWindowSize() SetNextWindowBgAlpha() if needed - - IsRootWindowOrAnyChildHovered() -> use IsWindowHovered(ImGuiHoveredFlags_RootAndChildWindows) - - AlignFirstTextHeightToWidgets() -> use AlignTextToFramePadding() - - SetNextWindowPosCenter() -> use SetNextWindowPos() with a pivot of (0.5f, 0.5f) - - ImFont::Glyph -> use ImFontGlyph - If you were still using the old names, read "API Breaking Changes" section of imgui.cpp to find out - the new names or equivalent features, or see how they were implemented until 1.73. -- Inputs: Fixed a miscalculation in the keyboard/mouse "typematic" repeat delay/rate calculation, used - by keys and e.g. repeating mouse buttons as well as the GetKeyPressedAmount() function. - If you were using a non-default value for io.KeyRepeatRate (previous default was 0.250), you can - add +io.KeyRepeatDelay to it to compensate for the fix. - The function was triggering on: 0.0 and (delay+rate*N) where (N>=1). Fixed formula responds to (N>=0). - Effectively it made io.KeyRepeatRate behave like it was set to (io.KeyRepeatRate + io.KeyRepeatDelay). - Fixed the code and altered default io.KeyRepeatRate,Delay from 0.250,0.050 to 0.300,0.050 to compensate. - If you never altered io.KeyRepeatRate nor used GetKeyPressedAmount() this won't affect you. -- Misc: Renamed IMGUI_DISABLE_FORMAT_STRING_FUNCTIONS to IMGUI_DISABLE_DEFAULT_FORMAT_FUNCTIONS. (#1038) -- Misc: Renamed IMGUI_DISABLE_MATH_FUNCTIONS to IMGUI_DISABLE_DEFAULT_MATH_FUNCTIONS. -- Fonts: ImFontAtlas::AddCustomRectRegular() now requires an ID larger than 0x110000 (instead of 0x10000) to - conform with supporting Unicode planes 1-16 in a future update. ID below 0x110000 will now assert. -- Backends: DX12: Added extra ID3D12DescriptorHeap parameter to ImGui_ImplDX12_Init() function. - The value is unused in master branch but will be used by the multi-viewport feature. (#2851) [@obfuscate] - -Other Changes: - -- InputText, Nav: Fixed Home/End key broken when activating Keyboard Navigation. (#787) -- InputText: Filter out ASCII 127 (DEL) emitted by low-level OSX layer, as we are using the Key value. (#2578) -- Layout: Fixed a couple of subtle bounding box vertical positioning issues relating to the handling of text - baseline alignment. The issue would generally manifest when laying out multiple items on a same line, - with varying heights and text baseline offsets. - Some specific examples, e.g. a button with regular frame padding followed by another item with a - multi-line label and no frame padding, such as: multi-line text, small button, tree node item, etc. - The second item was correctly offset to match text baseline, and would interact/display correctly, - but it wouldn't push the contents area boundary low enough. -- Scrollbar: Fixed an issue where scrollbars wouldn't display on the frame following a frame where - all child window contents would be culled. -- ColorPicker: Fixed SV triangle gradient to block (broken in 1.73). (#2864, #2711). [@lewa-j] -- TreeNode: Fixed combination of ImGuiTreeNodeFlags_SpanFullWidth and ImGuiTreeNodeFlags_OpenOnArrow - incorrectly locating the arrow hit position to the left of the frame. (#2451, #2438, #1897) -- TreeNode: The collapsing arrow accepts click even if modifier keys are being held, facilitating - interactions with custom multi-selections patterns. (#2886, #1896, #1861) -- TreeNode: Added IsItemToggledOpen() to explicitly query if item was just open/closed, facilitating - interactions with custom multi-selections patterns. (#1896, #1861) -- DragScalar, SliderScalar, InputScalar: Added p_ prefix to parameter that are pointers to the data - to clarify how they are used, and more comments redirecting to the demo code. (#2844) -- Error handling: Assert if user mistakenly calls End() instead of EndChild() on a child window. (#1651) -- Misc: Optimized storage of window settings data (reducing allocation count). -- Misc: Windows: Do not use _wfopen() if IMGUI_DISABLE_WIN32_FUNCTIONS is defined. (#2815) -- Misc: Windows: Disabled win32 function by default when building with UWP. (#2892, #2895) -- Misc: Using static_assert() when using C++11, instead of our own construct (avoid zealous Clang warnings). -- Misc: Added IMGUI_DISABLE_FILE_FUNCTIONS/IMGUI_DISABLE_DEFAULT_FILE_FUNCTION to nullify or disable - default implementation of ImFileXXX functions linking with fopen/fclose/fread/fwrite. (#2734) -- Docs: Improved and moved FAQ to docs/FAQ.md so it can be readable on the web. [@ButternCream, @ocornut] -- Docs: Moved misc/fonts/README.txt to docs/FONTS.txt. -- Docs: Added permanent redirect from https://www.dearimgui.com/faq to FAQ page. -- Demo: Added simple item reordering demo in Widgets -> Drag and Drop section. (#2823, #143) [@rokups] -- Metrics: Show wire-frame mesh and approximate surface area when hovering ImDrawCmd. [@ShironekoBen] -- Metrics: Expose basic details of each window key/value state storage. -- Examples: DX12: Using IDXGIDebug1::ReportLiveObjects() when DX12_ENABLE_DEBUG_LAYER is enabled. -- Examples: Emscripten: Removed BINARYEN_TRAP_MODE=clamp from Makefile which was removed in Emscripten 1.39.0 - but required prior to 1.39.0, making life easier for absolutely no-one. (#2877, #2878) [@podsvirov] -- Backends: OpenGL2: Explicitly backup, setup and restore GL_TEXTURE_ENV to increase compatibility with - legacy OpenGL applications. (#3000) -- Backends: OpenGL3: Fix building with pre-3.2 GL loaders which do not expose glDrawElementsBaseVertex(), - using runtime GL version to decide if we set ImGuiBackendFlags_RendererHasVtxOffset. (#2866, #2852) [@dpilawa] -- Backends: OSX: Fix using Backspace key. (#2578, #2817, #2818) [@DiligentGraphics] -- Backends: GLFW: Previously installed user callbacks are now restored on shutdown. (#2836) [@malte-v] -- CI: Set up a bunch of continuous-integration tests using GitHub Actions. We now compile many of the example - applications on Windows, Linux, MacOS, iOS, Emscripten. Removed Travis integration. (#2865) [@rokups] - -Docking+Viewports Branch: - -- Docking: Can undock from the small triangle button. (#2109,. #2645) -- Docking: Fixed node->HasCloseButton not honoring ImGuiDockNodeFlags_NoCloseButton in a floating node, - leading to empty space at the right of tab-bars with those flags. (#2109) -- Docking: Made docked windows not use style.ChildRounding. -- Multi-viewports: Added multi-viewport support in the DX12 back-end. (#2851) [@obfuscate] - - ------------------------------------------------------------------------ - VERSION 1.73 (Released 2019-09-24) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.73 - -Other Changes: - -- Nav, Scrolling: Added support for Home/End key. (#787) -- ColorEdit: Disable Hue edit when Saturation==0 instead of letting Hue values jump around. -- ColorEdit, ColorPicker: In HSV display of a RGB stored value, attempt to locally preserve Hue - when Saturation==0, which reduces accidentally lossy interactions. (#2722, #2770) [@rokups] -- ColorPicker: Made rendering aware of global style alpha of the picker can be faded out. (#2711) - Note that some elements won't accurately fade down with the same intensity, and the color wheel - when enabled will have small overlap glitches with (style.Alpha < 1.0). -- Tabs: Fixed single-tab not shrinking their width down. -- Tabs: Fixed clicking on a tab larger than tab-bar width creating a bouncing feedback loop. -- Tabs: Feed desired width (sum of unclipped tabs width) into layout system to allow for auto-resize. (#2768) - (before 1.71 tab bars fed the sum of current width which created feedback loops in certain situations). -- Tabs: Improved shrinking for large number of tabs to avoid leaving extraneous space on the right side. - Individuals tabs are given integer-rounded width and remainder is spread between tabs left-to-right. -- Columns, Separator: Fixed a bug where non-visible separators within columns would alter the next row position - differently than visible ones. -- SliderScalar: Improved assert when using U32 or U64 types with a large v_max value. (#2765) [@loicmouton] -- DragInt, DragFloat, DragScalar: Using (v_min > v_max) allows locking any edits to the value. -- DragScalar: Fixed dragging of unsigned values on ARM cpu (float to uint cast is undefined). (#2780) [@dBagrat] -- TreeNode: Added ImGuiTreeNodeFlags_SpanAvailWidth flag. (#2451, #2438, #1897) [@Melix19, @PathogenDavid] - This extends the hit-box to the right-most edge, even if the node is not framed. - (Note: this is not the default in order to allow adding other items on the same line. In the future we will - aim toward refactoring the hit-system to be front-to-back, allowing more natural overlapping of items, - and then we will be able to make this the default.) -- TreeNode: Added ImGuiTreeNodeFlags_SpanFullWidth flag. This extends the hit-box to both the left-most and - right-most edge of the working area, bypassing indentation. -- CollapsingHeader: Added support for ImGuiTreeNodeFlags_Bullet and ImGuiTreeNodeFlags_Leaf on framed nodes, - mostly for consistency. (#2159, #2160) [@goran-w] -- Selectable: Added ImGuiSelectableFlags_AllowItemOverlap flag in public api (was previously internal only). -- Style: Allow style.WindowMenuButtonPosition to be set to ImGuiDir_None to hide the collapse button. (#2634, #2639) -- Font: Better ellipsis ("...") drawing implementation. Instead of drawing three pixel-ey dots (which was glaringly - unfitting with many types of fonts) we first attempt to find a standard ellipsis glyphs within the loaded set. - Otherwise we render ellipsis using '.' from the font from where we trim excessive spacing to make it as narrow - as possible. (#2775) [@rokups] -- ImDrawList: Clarified the name of many parameters so reading the code is a little easier. (#2740) -- ImDrawListSplitter: Fixed merging channels if the last submitted draw command used a different texture. (#2506) -- Using offsetof() when available in C++11. Avoids Clang sanitizer complaining about old-style macros. (#94) -- ImVector: Added find(), find_erase(), find_erase_unsorted() helpers. -- Added a mechanism to compact/free the larger allocations of unused windows (buffers are compacted when - a window is unused for 60 seconds, as per io.ConfigWindowsMemoryCompactTimer = 60.0f). Note that memory - usage has never been reported as a problem, so this is merely a touch of overzealous luxury. (#2636) -- Documentation: Various tweaks and improvements to the README page. [@ker0chan] -- Backends: OpenGL3: Tweaked initialization code allow application calling ImGui_ImplOpenGL3_CreateFontsTexture() - before ImGui_ImplOpenGL3_NewFrame(), which sometimes can be convenient. -- Backends: OpenGL3: Attempt to automatically detect default GL loader by using __has_include. (#2798) [@o-micron] -- Backends: DX11: Fixed GSGetShader() call not passing an initialized instance count, which would - generally make the DX11 debug layer complain (bug added in 1.72). -- Backends: Vulkan: Added support for specifying multisample count. Set 'ImGui_ImplVulkan_InitInfo::MSAASamples' to - one of the VkSampleCountFlagBits values to use, default is non-multisampled as before. (#2705, #2706) [@vilya] -- Examples: OSX: Fix example_apple_opengl2/main.mm not forwarding mouse clicks and drags correctly. (#1961, #2710) - [@intonarumori, @ElectricMagic] -- Misc: Updated stb_rect_pack.h from 0.99 to 1.00 (fixes by @rygorous: off-by-1 bug in best-fit heuristic, - fix handling of rectangles too large to fit inside texture). (#2762) [@tido64] - -Docking+Viewports Branch: - -- Docking: Fix BeginDocked() path that creates node so that SetNextWindowDockID() doesn't immediately discard the node. (#2109) -- Docking: Fix for node created at the same time as windows that are still resizing (typically with - io.ConfigDockingAlwaysTabBar) to not be zero/min sized. (#2109). The fix delays their visibility by one frame, - which is not ideal but not very problematic as the .ini data gets populated after that. -- Docking: Fix a crash that could occur with a malformed ini file (DockNode Parent value pointing to a missing node). -- Viewport: Fix modal/popup window being stuck in unowned hidden viewport associated to fallback window without stealing - it back. Fix modal reference viewport when opened outside of another window. (#1542) -- Viewport: Modals don't need to set ImGuiViewportFlags_NoFocusOnClick, this also mitigate the issue described by #2445, - which becomes particularly bad with unfocused modal. (#1542) -- Viewport: better case case where host window gets moved and resized simultaneous (toggling maximized state). - There's no perfect solution there, than using io.ConfigViewportsNoAutoMerge = false. (#1542) -- Viewport, Docking: Fixed incorrect assignment of IsFallbackWindow which would tag dock node host windows created - in NewFrame() as such, messing with popup viewport inheritance. -- Viewport: Fixed issue where resize grip would display as hovered while mouse is still off the OS bounds so a click - would miss it and focus the OS window behind expected one. (#1542) -- Viewport: Fix to allow multiple shutdown / calls to DestroyPlatformWindows(). (#2769) -- Viewport: Backends: GLFW: Fix setting window size on macOS (#2767, #2117) [@rokups] -- Viewport: Backends: GLFW+Linux: Fix window having incorrect size after uncollapse. (#2756, #2117) [@rokups] -- Viewport: Backends: DirectX9: Workaround for windows not refreshing when main viewport has no draw call. (#2560) - - ------------------------------------------------------------------------ - VERSION 1.72b (Released 2019-07-31) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.72b - -Other Changes: - -- Nav, Scrolling: Fixed programmatic scroll leading to a slightly incorrect scroll offset when - the window has decorations or a menu-bar (broken in 1.71). This was mostly noticeable when - a keyboard/gamepad movement led to scrolling the view, or using e.g. SetScrollHereY() function. -- Nav: Made hovering non-MenuItem Selectable not re-assign the source item for keyboard navigation. -- Nav: Fixed an issue with NavFlattened window flag (beta) where widgets not entirely fitting - in child window (often selectables because of their protruding sides) would be not considered - as entry points to to navigate toward the child window. (#787) - - ------------------------------------------------------------------------ - VERSION 1.72 (Released 2019-07-27) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.72 - -Breaking Changes: - -- Removed redirecting functions/enums names that were marked obsolete in 1.51 (June 2017): - - ImGuiCol_Column*, ImGuiSetCond_* enums. - - IsItemHoveredRect(), IsPosHoveringAnyWindow(), IsMouseHoveringAnyWindow(), IsMouseHoveringWindow() functions. - - IMGUI_ONCE_UPON_A_FRAME macro. - If you were still using the old names, read "API Breaking Changes" section of imgui.cpp to find out - the new names or equivalent features. -- Renamed ImFontAtlas::CustomRect to ImFontAtlasCustomRect. Kept redirection typedef (will obsolete). -- Removed TreeAdvanceToLabelPos() which is rarely used and only does SetCursorPosX(GetCursorPosX() + GetTreeNodeToLabelSpacing()). - Kept redirection function (will obsolete). (#581, #324) - -Other Changes: - -- Scrolling: Made mouse-wheel scrolling lock the underlying window until the mouse is moved again or - until a short delay expires (~2 seconds). This allow uninterrupted scroll even if child windows are - passing under the mouse cursor. (#2604) -- Scrolling: Made it possible for mouse wheel and navigation-triggered scrolling to override a call to - SetScrollX()/SetScrollY(), making it possible to use a simpler stateless pattern for auto-scrolling: - // (Submit items..) - if (ImGui::GetScrollY() >= ImGui::GetScrollMaxY()) // If scrolling at the already at the bottom.. - ImGui::SetScrollHereY(1.0f); // ..make last item fully visible -- Scrolling: Added SetScrollHereX(), SetScrollFromPosX() for completeness. (#1580) [@kevreco] -- Scrolling: Mouse wheel scrolling while hovering a child window is automatically forwarded to parent window - if ScrollMax is zero on the scrolling axis. - Also still the case if ImGuiWindowFlags_NoScrollWithMouse is set (not new), but previously the forwarding - would be disabled if ImGuiWindowFlags_NoScrollbar was set on the child window, which is not the case - any more. Forwarding can still be disabled by setting ImGuiWindowFlags_NoInputs. (amend #1502, #1380). -- Window: Fixed InnerClipRect right-most coordinates using wrong padding setting (introduced in 1.71). -- Window: Fixed old SetWindowFontScale() api value from not being inherited by child window. Added - comments about the right way to scale your UI (load a font at the right side, rebuild atlas, scale style). -- Scrollbar: Avoid overlapping the opposite side when window (often a child window) is forcibly too small. -- Combo: Hide arrow when there's not enough space even for the square button. -- InputText: Testing for newly added ImGuiKey_KeyPadEnter key. (#2677, #2005) [@amc522] -- Tabs: Fixed unfocused tab bar separator color (was using ImGuiCol_Tab, should use ImGuiCol_TabUnfocusedActive). -- Columns: Fixed a regression from 1.71 where the right-side of the contents rectangle within each column - would wrongly use a WindowPadding.x instead of ItemSpacing.x like it always did. (#125, #2666) -- Columns: Made the right-most edge reaches up to the clipping rectangle (removing half of WindowPadding.x - worth of asymmetrical/extraneous padding, note that there's another half that conservatively has to offset - the right-most column, otherwise it's clipping width won't match the other columns). (#125, #2666) -- Columns: Improved honoring alignment with various values of ItemSpacing.x and WindowPadding.x. (#125, #2666) -- Columns: Made GetColumnOffset() and GetColumnWidth() behave when there's no column set, consistently with - other column functions. (#2683) -- InputTextMultiline: Fixed vertical scrolling tracking glitch. -- Word-wrapping: Fixed overzealous word-wrapping when glyph edge lands exactly on the limit. Because - of this, auto-fitting exactly unwrapped text would make it wrap. (fixes initial 1.15 commit, 78645a7d). -- Style: Attenuated default opacity of ImGuiCol_Separator in Classic and Light styles. -- Style: Added style.ColorButtonPosition (left/right, defaults to ImGuiDir_Right) to move the color button - of ColorEdit3/ColorEdit4 functions to either side of the inputs. -- IO: Added ImGuiKey_KeyPadEnter and support in various backends (previously backends would need to - specifically redirect key-pad keys to their regular counterpart). This is a temporary attenuating measure - until we actually refactor and add whole sets of keys into the ImGuiKey enum. (#2677, #2005) [@amc522] -- Misc: Made Button(), ColorButton() not trigger an "edited" event leading to IsItemDeactivatedAfterEdit() - returning true. This also effectively make ColorEdit4() not incorrect trigger IsItemDeactivatedAfterEdit() - when clicking the color button to open the picker popup. (#1875) -- Misc: Added IMGUI_DISABLE_METRICS_WINDOW imconfig.h setting to explicitly compile out ShowMetricsWindow(). -- Debug Tools: Added "Metrics->Tools->Item Picker" tool which allow clicking on a widget to break in the - debugger within the item code. The tool calls IM_DEBUG_BREAK() which can be redefined in imconfig.h. -- ImDrawList: Fixed CloneOutput() helper crashing. (#1860) [@gviot] -- ImDrawList::ChannelsSplit(), ImDrawListSplitter: Fixed an issue with merging draw commands between - channel 0 and 1. (#2624) -- ImDrawListSplitter: Fixed memory leak when using low-level split api (was not affecting ImDrawList api, - also this type was added in 1.71 and not advertised as a public-facing feature). -- Fonts: binary_to_compressed_c.cpp: Display an error message if failing to open/read the input font file. -- Demo: Log, Console: Using a simpler stateless pattern for auto-scrolling. -- Demo: Widgets: Showing how to use the format parameter of Slider/Drag functions to display the name - of an enum value instead of the underlying integer value. -- Demo: Renamed the "Help" menu to "Tools" (more accurate). -- Backends: DX10/DX11: Backup, clear and restore Geometry Shader is any is bound when calling renderer. -- Backends: DX11: Clear Hull Shader, Domain Shader, Compute Shader before rendering. Not backing/restoring them. -- Backends: OSX: Disabled default native Mac clipboard copy/paste implementation in core library (added in 1.71), - because it needs application to be linked with '-framework ApplicationServices'. It can be explicitly - enabled back by using '#define IMGUI_ENABLE_OSX_DEFAULT_CLIPBOARD_FUNCTIONS' in imconfig.h. Re-added - equivalent using NSPasteboard api in the imgui_impl_osx.mm experimental backend. (#2546) -- Backends: SDL2: Added ImGui_ImplSDL2_InitForD3D() function to make D3D support more visible. - (#2482, #2632) [@josiahmanson] -- Examples: Added SDL2+DirectX11 example application. (#2632, #2612, #2482) [@vincenthamm] - -Docking+Viewports Branch: - -- Docking: Making it possible to undock a node by clicking on the tab bar / title bar for the node. (#2645). -- Docking: Explicitly inhibit constraint when docked for now. Fix clipping issue related to constraints. (#2690). -- Docking: Fixed dragging/resizing from OS decoration not marking settings as dirty. -- Docking: Renamed io.ConfigDockingTabBarOnSingleWindows to io.ConfigDockingAlwaysTabBar. - Added ImGuiWindowClass::DockingAlwaysTabBar to set on individual windows. -- Docking: Perform simple check: assert if Docking or Viewport are enabled exactly on frame 1 (instead of frame 0 - or later), which is a common user error leading to loss of .ini data on load. -- Docking: Fix so that an appearing window making a dock node reappear won't have a zero-size on its first frame. -- Docking: Fixed using ImGuiDockNodeFlags_AutoHideTabBar with io.ConfigDockingTabBarOnSingleWindows. -- Docking: Added ImGuiDockNode to .natvis file. -- Docking: Fixed support for large meshes in GetBackgroundDrawList(), GetForegroundDrawList(). (#2638) -- Viewport: Fix monitor dpi info not being copied to main viewport when multi-viewports are not enabled. (#2621, #1676) -- Viewport: Refactored ImGuiWindowClass's ViewportFlagsOverrideMask + ViewportFlagsOverrideValue into - ViewportFlagsOverrideSet + ViewportFlagsOverrideClear which appears easier to grasp. (#1542) -- Viewport: Added ImGuiViewportFlags_NoAutoMerge to prevent merging into host viewport in a per-window basis - via the ImGuiWindowClass override mechanism. (#1542) - - ------------------------------------------------------------------------ - VERSION 1.71 (Released 2019-06-12) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.71 - -Breaking Changes: - -- IO: changed AddInputCharacter(unsigned short c) signature to AddInputCharacter(unsigned int c). -- Renamed SetNextTreeNodeOpen() to SetNextItemOpen(). Kept inline redirection function (will obsolete). -- Window: rendering of child windows outer decorations (e.g. bg color, border, scrollbars) is now - performed as part of their parent window, avoiding the creation of an extraneous draw commands. - If you have overlapping child windows with decorations, and relied on their relative z-order to be - mapped to submission their order, this will affect your rendering. The optimization is disabled - if the parent window has no visual output because it appears to be the most common situation leading - to the creation of overlapping child windows. Please reach out if you are affected by this change! - -Other Changes: - -- Window: clarified behavior of SetNextWindowContentSize(). Content size is defined as the size available - after removal of WindowPadding on each sides. So SetNextWindowContentSize(ImVec2(100,100)) + auto-resize - will always allow submitting a 100x100 item without creating a scrollbar, regarding of WindowPadding. - The exact meaning of ContentSize for decorated windows was previously ill-defined. -- Window: Fixed auto-resize with AlwaysVerticalScrollbar or AlwaysHorizontalScrollbar flags. -- Window: Fixed one case where auto-resize by double-clicking the resize grip would make either scrollbar - appear for a single frame after the resize. -- Separator: Revert 1.70 "Declare its thickness (1.0f) to the layout" change. It's not incorrect - but it breaks existing some layout patterns. Will return back to it when we expose Separator flags. -- Fixed InputScalar, InputScalarN, SliderScalarN, DragScalarN with non-visible label from inserting - style.ItemInnerSpacing.x worth of trailing spacing. -- Fixed InputFloatX, SliderFloatX, DragFloatX functions erroneously reporting IsItemEdited() multiple - times when the text input doesn't match the formatted output value (e.g. input "1" shows "1.000"). - It wasn't much of a problem because we typically use the return value instead of IsItemEdited() here. -- Fixed uses of IsItemDeactivated(), IsItemDeactivatedAfterEdit() on multi-components widgets and - after EndGroup(). (#2550, #1875) -- Fixed crash when appending with BeginMainMenuBar() more than once and no other window are showing. (#2567) -- ColorEdit: Fixed the color picker popup only displaying inputs as HSV instead of showing multiple - options. (#2587, broken in 1.69 by #2384). -- CollapsingHeader: Better clipping when a close button is enabled and it overlaps the label. (#600) -- Scrollbar: Minor bounding box adjustment to cope with various border size. -- Scrollbar, Style: Changed default style.ScrollbarSize from 16 to 14. -- Combo: Fixed rounding not applying with the ImGuiComboFlags_NoArrowButton flag. (#2607) [@DucaRii] -- Nav: Fixed gamepad/keyboard moving of window affecting contents size incorrectly, sometimes leading - to scrollbars appearing during the movement. -- Nav: Fixed rare crash when e.g. releasing Alt-key while focusing a window with a menu at the same - frame as clearing the focus. This was in most noticeable in backends such as Glfw and SDL which - emits key release events when focusing another viewport, leading to Alt+clicking on void on another - viewport triggering the issue. (#2609) -- TreeNode, CollapsingHeader: Fixed highlight frame not covering horizontal area fully when using - horizontal scrolling. (#2211, #2579) -- Tabs: Fixed BeginTabBar() within a window with horizontal scrolling from creating a feedback - loop with the horizontal contents size. -- Columns: Fixed Columns() within a window with horizontal scrolling from not covering the full - horizontal area (previously only worked with an explicit contents size). (#125) -- Columns: Fixed Separator from creating an extraneous draw command. (#125) -- Columns: Fixed Selectable with SpanAllColumns flag from creating an extraneous draw command. (#125) -- Style: Added style.WindowMenuButtonPosition (left/right, defaults to ImGuiDir_Left) to move the - collapsing/docking button to the other side of the title bar. -- Style: Made window close button cross slightly smaller. -- Log/Capture: Fixed BeginTabItem() label not being included in a text log/capture. -- ImDrawList: Added ImDrawCmd::VtxOffset value to support large meshes (64k+ vertices) using 16-bit indices. - The renderer backend needs to set 'io.BackendFlags |= ImGuiBackendFlags_RendererHasVtxOffset' to enable - this, and honor the ImDrawCmd::VtxOffset field. Otherwise the value will always be zero. (#2591) - This has the advantage of preserving smaller index buffers and allowing to execute on hardware that do not - support 32-bit indices. Most examples backends have been modified to support the VtxOffset field. -- ImDrawList: Added ImDrawCmd::IdxOffset value, equivalent to summing element count for each draw command. - This is provided for convenience and consistency with VtxOffset. (#2591) -- ImDrawCallback: Allow to override the signature of ImDrawCallback by #define-ing it. This is meant to - facilitate custom rendering backends passing local render-specific data to the draw callback. -- ImFontAtlas: FreeType: Added RasterizerFlags::Monochrome flag to disable font anti-aliasing. Combine - with RasterizerFlags::MonoHinting for best results. (#2545) [@HolyBlackCat] -- ImFontGlyphRangesBuilder: Fixed unnecessarily over-sized buffer, which incidentally was also not - fully cleared. Fixed edge-case overflow when adding character 0xFFFF. (#2568). [@NIKE3500] -- Demo: Added full "Dear ImGui" prefix to the title of "Dear ImGui Demo" and "Dear ImGui Metrics" windows. -- Backends: Add native Mac clipboard copy/paste default implementation in core library to match what we are - dealing with Win32, and to facilitate integration in custom engines. (#2546) [@andrewwillmott] -- Backends: OSX: imgui_impl_osx: Added mouse cursor support. (#2585, #1873) [@actboy168] -- Examples/Backends: DirectX9/10/11/12, Metal, Vulkan, OpenGL3 (Desktop GL only): Added support for large meshes - (64k+ vertices) with 16-bit indices, enable 'ImGuiBackendFlags_RendererHasVtxOffset' in those backends. (#2591) -- Examples/Backends: Don't filter characters under 0x10000 before calling io.AddInputCharacter(), - the filtering is done in io.AddInputCharacter() itself. This is in prevision for fuller Unicode - support. (#2538, #2541) - - ------------------------------------------------------------------------ - VERSION 1.70 (Released 2019-05-06) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.70 - -Breaking Changes: - -- ImDrawList: Improved algorithm for mitre joints on thick lines, preserving correct thickness - up to 90 degrees angles (e.g. rectangles). If you have custom rendering using thick lines, - they will appear a little thicker now. (#2518) [@rmitton] -- Obsoleted GetContentRegionAvailWidth(), use GetContentRegionAvail().x instead. - Kept inline redirection function. -- Examples: Vulkan: Added MinImageCount/ImageCount fields in ImGui_ImplVulkan_InitInfo, required - during initialization to specify the number of in-flight image requested by swap chains. - (was previously a hard #define IMGUI_VK_QUEUED_FRAMES 2). (#2071, #1677) [@nathanvoglsam] -- Examples: Vulkan: Tidying up the demo/internals helpers (most engine/app should not rely - on them but it is possible you have!). - -Other Changes: - -- ImDrawList: Added ImDrawCallback_ResetRenderState, a special ImDrawList::AddCallback() value - to request the renderer backend to reset its render state. (#2037, #1639, #2452) - Examples: Added support for ImDrawCallback_ResetRenderState in all renderer backends. Each - renderer code setting up initial render state has been moved to a function so it could be - called at the start of rendering and when a ResetRenderState is requested. [@ocornut, @bear24rw] -- InputText: Fixed selection background rendering one frame after the cursor movement when - first transitioning from no-selection to has-selection. (Bug in 1.69) (#2436) [@Nazg-Gul] -- InputText: Work-around for buggy standard libraries where isprint('\t') returns true. (#2467, #1336) -- InputText: Fixed ImGuiInputTextFlags_AllowTabInput leading to two tabs characters being inserted - if the backend provided both Key and Character input. (#2467, #1336) -- Layout: Added SetNextItemWidth() helper to avoid using PushItemWidth/PopItemWidth() for single items. - Note that SetNextItemWidth() currently only affect the same subset of items as PushItemWidth(), - generally referred to as the large framed+labeled items. Because the new SetNextItemWidth() - function is explicit we may later extend its effect to more items. -- Layout: Fixed PushItemWidth(-width) for right-side alignment laying out some items (button, listbox, etc.) - with negative sizes if the 'width' argument was smaller than the available width at the time of item - submission. -- Window: Fixed window with the AlwaysAutoResize flag unnecessarily extending their hovering boundaries - by a few pixels (this is used to facilitate resizing from borders when available for a given window). - One of the noticeable minor side effect was that navigating menus would have had a tendency to disable - highlight from parent menu items earlier than necessary while approaching the child menu. -- Window: Close button is horizontally aligned with style.FramePadding.x. -- Window: Fixed contents region being off by WindowBorderSize amount on the right when scrollbar is active. -- Window: Fixed SetNextWindowSizeConstraints() with non-rounded positions making windows drift. (#2067, #2530) -- Popups: Closing a popup restores the focused/nav window in place at the time of the popup opening, - instead of restoring the window that was in the window stack at the time of the OpenPopup call. (#2517) - Among other things, this allows opening a popup while no window are focused, and pressing Escape to - clear the focus again. -- Popups: Fixed right-click from closing all popups instead of aiming at the hovered popup level - (regression in 1.67). -- Selectable: With ImGuiSelectableFlags_AllowDoubleClick doesn't return true on the mouse button release - following the double-click. Only first mouse release + second mouse down (double-click) returns true. - Likewise for internal ButtonBehavior() with both _PressedOnClickRelease | _PressedOnDoubleClick. (#2503) -- GetMouseDragDelta(): also returns the delta on the mouse button released frame. (#2419) -- GetMouseDragDelta(): verify that mouse positions are valid otherwise returns zero. -- Inputs: Also add support for horizontal scroll with Shift+Mouse Wheel. (#2424, #1463) [@LucaRood] -- PlotLines, PlotHistogram: Ignore NaN values when calculating min/max bounds. (#2485) -- Columns: Fixed boundary of clipping being off by 1 pixel within the left column. (#125) -- Separator: Declare its thickness (1.0f) to the layout, making items around separator more symmetrical. -- Combo, Slider, Scrollbar: Improve rendering in situation when there's only a few pixels available (<3 pixels). -- Nav: Fixed Drag/Slider functions going into text input mode when keyboard CTRL is held while pressing NavActivate. -- Drag and Drop: Fixed drag source with ImGuiDragDropFlags_SourceAllowNullID and null ID from receiving click - regardless of being covered by another window (it didn't honor correct hovering rules). (#2521) -- ImDrawList: Improved algorithm for mitre joints on thick lines, preserving correct thickness up to 90 degrees - angles, also faster to output. (#2518) [@rmitton] -- Misc: Added IM_MALLOC/IM_FREE macros mimicking IM_NEW/IM_DELETE so user doesn't need to revert - to using the ImGui::MemAlloc()/MemFree() calls directly. -- Misc: Made IMGUI_CHECKVERSION() macro also check for matching size of ImDrawIdx. -- Metrics: Added "Show windows rectangles" tool to visualize the different rectangles. -- Demo: Improved trees in columns demo. -- Examples: OpenGL: Added a test GL call + comments in ImGui_ImplOpenGL3_Init() to detect uninitialized - GL function loaders early, and help users understand what they are missing. (#2421) -- Examples: SDL: Added support for SDL_GameController gamepads (enable with ImGuiConfigFlags_NavEnableGamepad). (#2509) [@DJLink] -- Examples: Emscripten: Added Emscripten+SDL+GLES2 example. (#2494, #2492, #2351, #336) [@nicolasnoble, @redblobgames] -- Examples: Metal: Added Glfw+Metal example. (#2527) [@bear24rw] -- Examples: OpenGL3: Minor tweaks + not calling glBindBuffer more than necessary in the render loop. -- Examples: Vulkan: Fixed in-flight buffers issues when using multi-viewports. (#2461, #2348, #2378, #2097) -- Examples: Vulkan: Added missing support for 32-bit indices (#define ImDrawIdx unsigned int). -- Examples: Vulkan: Avoid passing negative coordinates to vkCmdSetScissor, which debug validation layers do not like. -- Examples: Vulkan: Added ImGui_ImplVulkan_SetMinImageCount() to change min image count at runtime. (#2071) [@nathanvoglsam] -- Examples: DirectX9: Fixed erroneous assert in ImGui_ImplDX9_InvalidateDeviceObjects(). (#2454) -- Examples: DirectX10/11/12, Allegro, Marmalade: Render functions early out when display size is zero (minimized). (#2496) -- Examples: GLUT: Fixed existing FreeGLUT example to work with regular GLUT. (#2465) [@andrewwillmott] -- Examples: GLUT: Renamed imgui_impl_freeglut.cpp/.h to imgui_impl_glut.cpp/.h. (#2465) [@andrewwillmott] -- Examples: GLUT: Made io.DeltaTime always > 0. (#2430) -- Examples: Visual Studio: Updated default platform toolset+sdk in vcproj files from v100+sdk7 (vs2010) - to v110+sdk8 (vs2012). This is mostly so we can remove reliance on DXSDK_DIR for the DX10/DX11 example, - which if existing and when switching to recent SDK ends up conflicting and creating warnings. - - ------------------------------------------------------------------------ - VERSION 1.69 (Released 2019-03-13) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.69 - -Breaking Changes: - -- Renamed ColorEdit/ColorPicker's ImGuiColorEditFlags_RGB/_HSV/_HEX flags to respectively - ImGuiColorEditFlags_DisplayRGB/_DisplayHSV/_DisplayHex. This is because the addition of - new flag ImGuiColorEditFlags_InputHSV makes the earlier one ambiguous. - Kept redirection enum values (will obsolete). (#2384) [@haldean] -- Renamed GetOverlayDrawList() to GetForegroundDrawList(). Kept redirection function (will obsolete). (#2391) - -Other Changes: - -- Added GetBackgroundDrawList() helper to quickly get access to a ImDrawList that will be rendered - behind every other windows. (#2391, #545) -- DragScalar, InputScalar, SliderScalar: Added support for u8/s8/u16/s16 data types (ImGuiDataType_S8, etc.) - We are reusing function instances of larger types to reduce code size. (#643, #320, #708, #1011) -- Added InputTextWithHint() to display a description/hint in the text box when no text - has been entered. (#2400) [@Organic-Code, @ocornut] -- Nav: Fixed a tap on AltGR (e.g. German keyboard) from navigating to the menu layer. -- Nav: Fixed Ctrl+Tab keeping active InputText() of a previous window active after the switch. (#2380) -- Fixed IsItemDeactivated()/IsItemDeactivatedAfterEdit() from not correctly returning true - when tabbing out of a focusable widget (Input/Slider/Drag) in most situations. (#2215, #1875) -- InputInt, InputFloat, InputScalar: Fix to keep the label of the +/- buttons centered when - style.FramePadding.x is abnormally larger than style.FramePadding.y. Since the buttons are - meant to be square (to align with e.g. color button) we always use FramePadding.y. (#2367) -- InputInt, InputScalar: +/- buttons now respects the natural type limits instead of - overflowing or underflowing the value. -- InputText: Fixed an edge case crash that would happen if another widget sharing the same ID - is being swapped with an InputText that has yet to be activated. -- InputText: Fixed various display corruption related to swapping the underlying buffer while - a input widget is active (both for writable and read-only paths). Often they would manifest - when manipulating the scrollbar of a multi-line input text. -- ColorEdit, ColorPicker, ColorButton: Added ImGuiColorEditFlags_InputHSV to manipulate color - values encoded as HSV (in order to avoid HSV<>RGB round trips and associated singularities). - (#2383, #2384) [@haldean] -- ColorPicker: Fixed a bug/assertion when displaying a color picker in a collapsed window - while dragging its title bar. (#2389) -- ColorEdit: Fixed tooltip not honoring the ImGuiColorEditFlags_NoAlpha contract of never - reading the 4th float in the array (value was read and discarded). (#2384) [@haldean] -- MenuItem, Selectable: Fixed disabled widget interfering with navigation (fix c2db7f63 in 1.67). -- Tabs: Fixed a crash when using many BeginTabBar() recursively (didn't affect docking). (#2371) -- Tabs: Added extra mis-usage error recovery. Past the assert, common mis-usage don't lead to - hard crashes any more, facilitating integration with scripting languages. (#1651) -- Tabs: Fixed ImGuiTabItemFlags_SetSelected being ignored if the tab is not visible (with - scrolling policy enabled) or if is currently appearing. -- Tabs: Fixed Tab tooltip code making drag and drop tooltip disappear during the frame where - the drag payload activate a tab. -- Tabs: Reworked scrolling policy (when ImGuiTabBarFlags_FittingPolicyScroll is set) to - teleport the view when aiming at a tab far away the visible section, and otherwise accelerate - the scrolling speed to cap the scrolling time to 0.3 seconds. -- Text: Fixed large Text/TextUnformatted calls not feeding their size into layout when starting - below the lower point of the current clipping rectangle. This bug has been there since v1.0! - It was hardly noticeable but would affect the scrolling range, which in turn would affect - some scrolling request functions when called during the appearing frame of a window. -- Plot: Fixed divide-by-zero in PlotLines() when passing a count of 1. (#2387) [@Lectem] -- Log/Capture: Fixed LogXXX functions emitting extraneous leading carriage return. -- Log/Capture: Fixed an issue when empty string on a new line would not emit a carriage return. -- Log/Capture: Fixed LogXXX functions 'auto_open_depth' parameter being treated as an absolute - tree depth instead of a relative one. -- Log/Capture: Fixed CollapsingHeader trailing ascii representation being "#" instead of "##". -- ImFont: Added GetGlyphRangesVietnamese() helper. (#2403) -- Misc: Asserting in NewFrame() if style.WindowMinSize is zero or smaller than (1.0f,1.0f). -- Demo: Using GetBackgroundDrawList() and GetForegroundDrawList() in "Custom Rendering" demo. -- Demo: InputText: Demonstrating use of ImGuiInputTextFlags_CallbackResize. (#2006, #1443, #1008). -- Examples: GLFW, SDL: Preserve DisplayFramebufferScale when main viewport is minimized. - (This is particularly useful for the viewport branch because we are not supporting per-viewport - frame-buffer scale. It fixes windows not refreshing when main viewport is minimized.) (#2416) -- Examples: OpenGL: Fix to be able to run on ES 2.0 / WebGL 1.0. [@rmitton, @gabrielcuvillier] -- Examples: OpenGL: Fix for OSX not supporting OpenGL 4.5, we don't try to read GL_CLIP_ORIGIN - even if the OpenGL headers/loader happens to define the value. (#2366, #2186) -- Examples: Allegro: Added support for touch events (emulating mouse). (#2219) [@dos1] -- Examples: DirectX9: Minor changes to match the other DirectX examples more closely. (#2394) - - ------------------------------------------------------------------------ - VERSION 1.68 (Released 2019-02-19) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.68 - -Breaking Changes: - -- Removed io.DisplayVisibleMin/DisplayVisibleMax (which were marked obsolete and removed from viewport/docking branch already). -- Made it illegal/assert when io.DisplayTime == 0.0f (with an exception for the first frame). - If for some reason your time step calculation gives you a zero value, replace it with a arbitrarily small value! - -Other Changes: - -- Added .editorconfig file for text editors to standardize using spaces. (#2038) [@kudaba] -- ImDrawData: Added FramebufferScale field (currently a copy of the value from io.DisplayFramebufferScale). - This is to allow render functions being written without pulling any data from ImGuiIO, allowing incoming - multi-viewport feature to behave on Retina display and with multiple displays. - If you are not using a custom backend, please update your render function code ahead of time, - and use draw_data->FramebufferScale instead of io.DisplayFramebufferScale. (#2306, #1676) -- Added IsItemActivated() as an extension to the IsItemDeactivated/IsItemDeactivatedAfterEdit functions - which are useful to implement variety of undo patterns. (#820, #956, #1875) -- InputText: Fixed a bug where ESCAPE would not restore the initial value in all situations. (#2321) [@relick] -- InputText: Fixed a bug where ESCAPE would be first captured by the Keyboard Navigation code. (#2321, #787) -- InputText: Fixed redo buffer exhaustion handling (rare) which could corrupt the undo character buffer. (#2333) - The way the redo/undo buffers work would have made it generally unnoticeable to the user. -- Fixed range-version of PushID() and GetID() not honoring the ### operator to restart from the seed value. -- Fixed CloseCurrentPopup() on a child-menu of a modal incorrectly closing the modal. (#2308) -- Tabs: Added ImGuiTabBarFlags_TabListPopupButton flag to show a popup button on manual tab bars. (#261, #351) -- Tabs: Removed ImGuiTabBarFlags_NoTabListPopupButton which was available in 1.67 but actually had zero use. -- Tabs: Fixed a minor clipping glitch when changing style's FramePadding from frame to frame. -- Tabs: Fixed border (when enabled) so it is aligned correctly mid-pixel and appears as bright as other borders. -- Style, Selectable: Added ImGuiStyle::SelectableTextAlign and ImGuiStyleVar_SelectableTextAlign. (#2347) [@haldean] -- Menus: Tweaked horizontal overlap between parent and child menu (to help convey relative depth) - from using style.ItemSpacing.x to style.ItemInnerSpacing.x, the later being expected to be smaller. (#1086) -- RadioButton: Fixed label horizontal alignment to precisely match Checkbox(). -- Window: When resizing from an edge, the border is more visible and better follow the rounded corners. -- Window: Fixed initial width of collapsed windows not taking account of contents width (broken in 1.67). (#2336, #176) -- Scrollbar: Fade out and disable interaction when too small, in order to facilitate using the resize grab on very - small window, as well as reducing visual noise/overlap. -- ListBox: Better optimized when clipped / non-visible. -- InputTextMultiline: Better optimized when clipped / non-visible. -- Font: Fixed high-level ImGui::CalcTextSize() used by most widgets from erroneously subtracting 1.0f*scale to - calculated text width. Among noticeable side-effects, it would make sequences of repeated Text/SameLine calls - not align the same as a single call, and create mismatch between high-level size calculation and those performed - with the lower-level ImDrawList api. (#792) [@SlNPacifist] -- Font: Fixed building atlas when specifying duplicate/overlapping ranges within a same font. (#2353, #2233) -- ImDrawList: Fixed AddCircle(), AddCircleFilled() angle step being off, which was visible when drawing a "circle" - with a small number of segments (e.g. an hexagon). (#2287) [@baktery] -- ImGuiTextBuffer: Added append() function (unformatted). -- ImFontAtlas: Added 0x2000-0x206F general punctuation range to default ChineseFull/ChineseSimplifiedCommon ranges. (#2093) -- ImFontAtlas: FreeType: Added support for imgui allocators + custom FreeType only SetAllocatorFunctions. (#2285) [@Vuhdo] -- ImFontAtlas: FreeType: Fixed using imgui_freetype.cpp in unity builds. (#2302) -- Demo: Fixed "Log" demo not initializing properly, leading to the first line not showing before a Clear. (#2318) [@bluescan] -- Demo: Added "Auto-scroll" option in Log/Console demos. (#2300) [@nicolasnoble, @ocornut] -- Examples: Metal, OpenGL2, OpenGL3, Vulkan: Fixed offsetting of clipping rectangle with ImDrawData::DisplayPos != (0,0) - when the display frame-buffer scale scale is not (1,1). While this doesn't make a difference when using master branch, - this is effectively fixing support for multi-viewport with Mac Retina Displays on those examples. (#2306) [@rasky, @ocornut] - Also using ImDrawData::FramebufferScale instead of io.DisplayFramebufferScale. -- Examples: Clarified the use the ImDrawData::DisplayPos to offset clipping rectangles. -- Examples: Win32: Using GetForegroundWindow()+IsChild() instead of GetActiveWindow() to be compatible with windows created - in a different thread or parent. (#1951, #2087, #2156, #2232) [many people] -- Examples: SDL: Using the SDL_WINDOW_ALLOW_HIGHDPI flag. (#2306, #1676) [@rasky] -- Examples: Win32: Added support for XInput gamepads (if ImGuiConfigFlags_NavEnableGamepad is enabled). -- Examples: Win32: Added support for mouse buttons 4 and 5 via WM_XBUTTON* messages. (#2264) -- Examples: DirectX9: Explicitly disable fog (D3DRS_FOGENABLE) before drawing in case user state has it set. (#2288, #2230) -- Examples: OpenGL2: Added #define GL_SILENCE_DEPRECATION to cope with newer XCode warnings. -- Examples: OpenGL3: Using GLSL 4.10 shaders for any GLSL version over 410 (e.g. 430, 450). (#2329) [@BrutPitt] - - ------------------------------------------------------------------------ - VERSION 1.67 (Released 2019-01-14) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.67 - -Breaking Changes: - -- Made it illegal to call Begin("") with an empty string. This somehow half-worked before but had various undesirable - side-effect because the window would have ID zero. In particular it is causing problems in viewport/docking branches. -- Renamed io.ConfigResizeWindowsFromEdges to io.ConfigWindowsResizeFromEdges and removed its [Beta] mark. - The addition of new configuration options in the Docking branch is pushing for a little reorganization of those names. -- Renamed ImFontAtlas::GlyphRangesBuilder to ImFontGlyphRangesBuilder. Kept redirection typedef (will obsolete). - -Other Changes: - -- Added BETA api for Tab Bar/Tabs widgets: (#261, #351) - - Added BeginTabBar(), EndTabBar(), BeginTabItem(), EndTabItem(), SetTabItemClosed() API. - - Added ImGuiTabBarFlags flags for BeginTabBar(). - - Added ImGuiTabItemFlags flags for BeginTabItem(). - - Style: Added ImGuiCol_Tab, ImGuiCol_TabHovered, ImGuiCol_TabActive, ImGuiCol_TabUnfocused, ImGuiCol_TabUnfocusedActive colors. - - Demo: Added Layout->Tabs demo code. - - Demo: Added "Documents" example app showcasing possible use for tabs. - This feature was merged from the Docking branch in order to allow the use of regular tabs in your code. - (It does not provide the docking/splitting/merging of windows available in the Docking branch) -- Added ImGuiWindowFlags_UnsavedDocument window flag to append '*' to title without altering the ID, as a convenience - to avoid using the ### operator. In the Docking branch this also has an effect on tab closing behavior. -- Window, Focus, Popup: Fixed an issue where closing a popup by clicking another window with the _NoMove flag would refocus - the parent window of the popup instead of the newly clicked window. -- Window: Contents size is preserved while a window collapsed. Fix auto-resizing window losing their size for one frame when uncollapsed. -- Window: Contents size is preserved while a window contents is hidden (unless it is hidden for resizing purpose). -- Window: Resizing windows from edge is now enabled by default (io.ConfigWindowsResizeFromEdges=true). Note that - it only works _if_ the backend sets ImGuiBackendFlags_HasMouseCursors, which the standard backends do. -- Window: Added io.ConfigWindowsMoveFromTitleBarOnly option. This is ignored by window with no title bars (often popups). - This affects clamping window within the visible area: with this option enabled title bars need to be visible. (#899) -- Window: Fixed using SetNextWindowPos() on a child window (which wasn't really documented) position the cursor as expected - in the parent window, so there is no mismatch between the layout in parent and the position of the child window. -- InputFloat: When using ImGuiInputTextFlags_ReadOnly the step buttons are disabled. (#2257) -- DragFloat: Fixed broken mouse direction change with power!=1.0. (#2174, #2206) [@Joshhua5] -- Nav: Fixed an keyboard issue where holding Activate/Space for longer than two frames on a button would unnecessary - keep the focus on the parent window, which could steal it from newly appearing windows. (#787) -- Nav: Fixed animated window titles from being updated when displayed in the CTRL+Tab list. (#787) -- Error recovery: Extraneous/undesired calls to End() are now being caught by an assert in the End() function closer - to the user call site (instead of being reported in EndFrame). Past the assert, they don't lead to crashes any more. (#1651) - Missing calls to End(), past the assert, should not lead to crashes or to the fallback Debug window appearing on screen. - Those changes makes it easier to integrate dear imgui with a scripting language allowing, given asserts are redirected - into e.g. an error log and stopping the script execution. -- ImFontAtlas: Stb and FreeType: Atlas width is now properly based on total surface rather than glyph count (unless overridden with TexDesiredWidth). -- ImFontAtlas: Stb and FreeType: Fixed atlas builder so missing glyphs won't influence the atlas texture width. (#2233) -- ImFontAtlas: Stb and FreeType: Fixed atlas builder so duplicate glyphs (when merging fonts) won't be included in the rasterized atlas. -- ImFontAtlas: FreeType: Fixed abnormally high atlas height. -- ImFontAtlas: FreeType: Fixed support for any values of TexGlyphPadding (not just only 1). -- ImDrawList: Optimized some of the functions for performance of debug builds where non-inline function call cost are non-negligible. - (Our test UI scene on VS2015 Debug Win64 with /RTC1 went ~5.9 ms -> ~4.9 ms. In Release same scene stays at ~0.3 ms.) -- IO: Added BackendPlatformUserData, BackendRendererUserData, BackendLanguageUserData void* for storage use by backends. -- IO: Renamed InputCharacters[], marked internal as was always intended. Please don't access directly, and use AddInputCharacter() instead! -- IO: AddInputCharacter() goes into a queue which can receive as many characters as needed during the frame. This is useful - for automation to not have an upper limit on typing speed. Will later transition key/mouse to use the event queue later. -- Style: Tweaked default value of style.DisplayWindowPadding from (20,20) to (19,19) so the default style as a value - which is the same as the title bar height. -- Demo: "Simple Layout" and "Style Editor" are now using tabs. -- Demo: Added a few more things under "Child windows" (changing ImGuiCol_ChildBg, positioning child, using IsItemHovered after a child). -- Examples: DirectX10/11/12: Made imgui_impl_dx10/dx11/dx12.cpp link d3dcompiler.lib from the .cpp file to ease integration. -- Examples: Allegro 5: Properly destroy globals on shutdown to allow for restart. (#2262) [@DomRe] - - ------------------------------------------------------------------------ - VERSION 1.66b (Released 2018-12-01) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.66b - -Other Changes: - -- Fixed a text rendering/clipping bug introduced in 1.66 (on 2018-10-12, commit ede3a3b9) that affect single ImDrawList::AddText() - calls with single strings larger than 10k. Text/TextUnformatted() calls were not affected, but e.g. InputText() was. [@pdoane] -- When the focused window become inactive don't restore focus to a window with the ImGuiWindowFlags_NoInputs flag. (#2213) [@zzzyap] -- Separator: Fixed Separator() outputting an extraneous empty line when captured into clipboard/text/file. -- Demo: Added ShowAboutWindow() call, previously was only accessible from the demo window. -- Demo: ShowAboutWindow() now display various Build/Config Information (compiler, os, etc.) that can easily be copied into bug reports. -- Fixed build issue with osxcross and macOS. (#2218) [@dos1] -- Examples: Setting up 'io.BackendPlatformName'/'io.BackendRendererName' fields to the current backend can be displayed in the About window. -- Examples: SDL: changed the signature of ImGui_ImplSDL2_ProcessEvent() to use a const SDL_Event*. (#2187) - - ------------------------------------------------------------------------ - VERSION 1.66 (Released 2018-11-22) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.66 - -Breaking Changes: - -- Renamed SetScrollHere() to SetScrollHereY(). Kept redirection function (will obsolete). -- Renamed misc/stl/imgui_stl.* to misc/cpp/imgui_stdlib.* in prevision for other C++ helper files. (#2035, #2096) - -Other Changes: - -- Fixed calling SetNextWindowSize()/SetWindowSize() with non-integer values leading to - accidental alteration of window position. We now round the provided size. (#2067) -- Fixed calling DestroyContext() always saving .ini data with the current context instead - of the supplied context pointer. (#2066) -- Nav, Focus: Fixed ImGuiWindowFlags_NoBringToFrontOnFocus windows not being restoring focus - properly after the main menu bar or last focused window is deactivated. -- Nav: Fixed an assert in certain circumstance (mostly when using popups) when mouse positions stop being valid. (#2168) -- Nav: Fixed explicit directional input not re-highlighting current nav item if there is a single item in the window - and highlight has been previously disabled by the mouse. (#787) -- DragFloat: Fixed a situation where dragging with value rounding enabled or with a power curve - erroneously wrapped the value to one of the min/max edge. (#2024, #708, #320, #2075). -- DragFloat: Disabled using power curve when one edge is FLT_MAX (broken in 1.61). (#2024) -- DragFloat: Disabled setting a default drag speed when one edge is FLT_MAX. (#2024) -- SliderAngle: Added optional format argument to alter precision or localize the string. (#2150) [@podsvirov] -- Window: Resizing from edges (with io.ConfigResizeWindowsFromEdges Beta flag) extends the hit region - of root floating windows outside the window, making it easier to resize windows. Resize grips are also - extended accordingly so there are no discontinuity when hovering between borders and corners. (#1495, #822) -- Window: Added ImGuiWindowFlags_NoBackground flag to avoid rendering window background. This is mostly to allow - the creation of new flag combinations, as we could already use SetNextWindowBgAlpha(0.0f). (#1660) [@biojppm, @ocornut] -- Window: Added ImGuiWindowFlags_NoDecoration helper flag which is essentially NoTitleBar+NoResize+NoScrollbar+NoCollapse. -- Window: Added ImGuiWindowFlags_NoMouseInputs which is basically the old ImGuiWindowFlags_NoInputs (essentially - we have renamed ImGuiWindowFlags_NoInputs to ImGuiWindowFlags_NoMouseInputs). Made the new ImGuiWindowFlags_NoInputs - encompass both NoMouseInputs+NoNav, which is consistent with its description. (#1660, #787) -- Window, Inputs: Fixed resizing from edges when io.MousePos is not pixel-rounded by rounding mouse position input. (#2110) -- BeginChild(): Fixed BeginChild(const char*, ...) variation erroneously not applying the ID stack - to the provided string to uniquely identify the child window. This was undoing an intentional change - introduced in 1.50 and broken in 1.60. (#1698, #894, #713). -- TextUnformatted(): Fixed a case where large-text path would read bytes past the text_end marker depending - on the position of new lines in the buffer (it wasn't affecting the output but still not the right thing to do!) -- ListBox(): Fixed frame sizing when items_count==1 unnecessarily showing a scrollbar. (#2173) [@luk1337, @ocornut] -- ListBox(): Tweaked frame sizing so list boxes will look more consistent when FramePadding is far from ItemSpacing. -- RenderText(): Some optimization for very large text buffers, useful for non-optimized builds. -- BeginMenu(): Fixed menu popup horizontal offset being off the item in the menu bar when WindowPadding=0.0f. -- ArrowButton(): Fixed arrow shape being horizontally misaligned by (FramePadding.y-FramePadding.x) if they are different. -- Demo: Split the contents of ShowDemoWindow() into smaller functions as it appears to speed up link time with VS. (#2152) -- Drag and Drop: Added GetDragDropPayload() to peek directly into the payload (if any) from anywhere. (#143) -- ImGuiTextBuffer: Avoid heap allocation when empty. -- ImDrawList: Fixed AddConvexPolyFilled() undefined behavior when passing points_count smaller than 3, - in particular, points_count==0 could lead to a memory stomp if the draw list was previously empty. -- Examples: DirectX10, DirectX11: Removed seemingly unnecessary calls to invalidate and recreate device objects - in the WM_SIZE handler. (#2088) [@ice1000] -- Examples: GLFW: User previously installed GLFW callbacks are now saved and chain-called by the default callbacks. (#1759) -- Examples: OpenGL3: Added support for GL 4.5's glClipControl(GL_UPPER_LEFT). (#2186) -- Examples: OpenGL3+GLFW: Fixed error condition when using the GLAD loader. (#2157) [@blackball] -- Examples: OpenGL3+GLFW/SDL: Made main.cpp compile with IMGUI_IMPL_OPENGL_LOADER_CUSTOM (may be missing init). (#2178) [@doug-moen] -- Examples: SDL2+Vulkan: Fixed application shutdown which could deadlock on Linux + Xorg. (#2181) [@eRabbit0] - - ------------------------------------------------------------------------ - VERSION 1.65 (Released 2018-09-06) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.65 - -Breaking Changes: - -- Renamed stb_truetype.h to imstb_truetype.h, stb_textedit.h to imstb_textedit.h, and - stb_rect_pack.h to imstb_rectpack.h. If you were conveniently using the imgui copy of those - STB headers in your project, you will have to update your include paths. (#1718, #2036) - The reason for this change is to avoid conflicts for projects that may also be importing - their own copy of the STB libraries. Note that imgui's copy of stb_textedit.h is modified. -- Renamed io.ConfigCursorBlink to io.ConfigInputTextCursorBlink. (#1427) - -Other Changes: - -- This is a minor release following the 1.64 refactor, with a little more shuffling of code. -- Clarified and improved the source code sectioning in all files (easier to search or browse sections). -- Nav: Removed the [Beta] tag from various descriptions of the gamepad/keyboard navigation system. - Although it is not perfect and will keep being improved, it is fairly functional and used by many. (#787) -- Fixed a build issue with non-Cygwin GCC under Windows. -- Demo: Added a "Configuration" block to make io.ConfigFlags/io.BackendFlags more prominent. -- Examples: OpenGL3+SDL2: Fixed error condition when using the GLAD loader. (#2059, #2002) [@jiri] - - ------------------------------------------------------------------------ - VERSION 1.64 (Released 2018-08-31) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.64 - -Changes: - -- Moved README, CHANGELOG and TODO files to the docs/ folder. - If you are updating dear imgui by copying files, take the chance to delete the old files. -- Added imgui_widgets.cpp file, extracted and moved widgets code out of imgui.cpp into imgui_widgets.cpp. - Re-ordered some of the code remaining in imgui.cpp. - NONE OF THE FUNCTIONS HAVE CHANGED. THE CODE IS SEMANTICALLY 100% IDENTICAL, BUT _EVERY_ FUNCTIONS HAS BEEN MOVED. - Because of this, any local modifications to imgui.cpp will likely conflict when you update. - If you have any modifications to imgui.cpp, it is suggested that you first update to 1.63, then - isolate your patches. You can peak at imgui_widgets.cpp from 1.64 to get a sense of what is included in it, - then separate your changes into several patches that can more easily be applied to 1.64 on a per-file basis. - What I found worked nicely for me, was to open the diff of the old patches in an interactive merge/diff tool, - search for the corresponding function in the new code and apply the chunks manually. -- As a reminder, if you have any change to imgui.cpp it is a good habit to discuss them on the github, - so a solution applicable on the Master branch can be found. If your company has changes that you cannot - disclose you may also contact me privately. - - ------------------------------------------------------------------------ - VERSION 1.63 (Released 2018-08-29) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.63 - -Breaking Changes: - -- Style: Renamed ImGuiCol_ModalWindowDarkening to ImGuiCol_ModalWindowDimBg for consistency with other features. - Kept redirection enum (will obsolete). -- Changed ImGui::GetTime() return value from float to double to avoid accumulating floating point imprecision over time. -- Removed per-window ImGuiWindowFlags_ResizeFromAnySide Beta flag in favor `io.ConfigResizeWindowsFromEdges=true` to - enable the feature globally. (#1495) - The feature is not currently enabled by default because it is not satisfying enough, but will eventually be. -- InputText: Renamed ImGuiTextEditCallback to ImGuiInputTextCallback, ImGuiTextEditCallbackData to ImGuiInputTextCallbackData - for consistency. Kept redirection types (will obsolete). -- InputText: Removed ImGuiTextEditCallbackData::ReadOnly because it is a duplication of (::Flags & ImGuiInputTextFlags_ReadOnly). -- Renamed IsItemDeactivatedAfterChange() to IsItemDeactivatedAfterEdit() for consistency with new IsItemEdited() API. - Kept redirection function (will obsolete soonish as IsItemDeactivatedAfterChange() is very recent). -- Renamed io.OptCursorBlink to io.ConfigCursorBlink [-> io.ConfigInputTextCursorBlink in 1.65], io.OptMacOSXBehaviors to - io.ConfigMacOSXBehaviors for consistency. (#1427, #473) -- Removed obsolete redirection functions: CollapsingHeader() variation with 2 bools - marked obsolete in v1.49, May 2016. - -Other Changes: - -- ArrowButton: Fixed to honor PushButtonRepeat() setting (and internals' ImGuiItemFlags_ButtonRepeat). -- ArrowButton: Setup current line text baseline so that ArrowButton() + SameLine() + Text() are aligned properly. -- Nav: Added a CTRL+TAB window list and changed the highlight system accordingly. The change is motivated by upcoming - Docking features. (#787) -- Nav: Made CTRL+TAB skip menus + skip the current navigation window if is has the ImGuiWindow_NoNavFocus set. (#787) - While it was previously possible, you won't be able to CTRL-TAB out and immediately back in a window with the - ImGuiWindow_NoNavFocus flag. -- Window: Allow menu and popups windows from ignoring the style.WindowMinSize values so short menus/popups are not padded. (#1909) -- Window: Added global io.ConfigResizeWindowsFromEdges option to enable resizing windows from their edges and from - the lower-left corner. (#1495) -- Window: Collapse button shows hovering highlight + clicking and dragging on it allows to drag the window as well. -- Added IsItemEdited() to query if the last item modified its value (or was pressed). This is equivalent to the bool - returned by most widgets. - It is useful in some situation e.g. using InputText() with ImGuiInputTextFlags_EnterReturnsTrue. (#2034) -- InputText: Added support for buffer size/capacity changes via the ImGuiInputTextFlags_CallbackResize flag. (#2006, #1443, #1008). -- InputText: Fixed not tracking the cursor horizontally when modifying the text buffer through a callback. -- InputText: Fixed minor off-by-one issue when submitting a buffer size smaller than the initial zero-terminated buffer contents. -- InputText: Fixed a few pathological crash cases on single-line InputText widget with multiple millions characters worth of contents. - Because the current text drawing function reserve for a worst-case amount of vertices and how we handle horizontal clipping, - we currently just avoid displaying those single-line widgets when they are over a threshold of 2 millions characters, - until a better solution is found. -- Drag and Drop: Fixed an incorrect assert when dropping a source that is submitted after the target (bug introduced with 1.62 changes - related to the addition of IsItemDeactivated()). (#1875, #143) -- Drag and Drop: Fixed ImGuiDragDropFlags_SourceNoDisableHover to affect hovering state prior to calling IsItemHovered() + fixed description. (#143) -- Drag and Drop: Calling BeginTooltip() between a BeginDragSource()/EndDragSource() or BeginDropTarget()/EndDropTarget() uses adjusted tooltip - settings matching the one created when calling BeginDragSource() without the ImGuiDragDropFlags_SourceNoPreviewTooltip flag. (#143) -- Drag and Drop: Payload stays available and under the mouse if the source stops being submitted, however the tooltip is replaced by "...". (#1725) -- Drag and Drop: Added ImGuiDragDropFlags_SourceAutoExpirePayload flag to force payload to expire if the source stops being submitted. (#1725, #143). -- IsItemHovered(): Added ImGuiHoveredFlags_AllowWhenDisabled flag to query hovered status on disabled items. (#1940, #211) -- Selectable: Added ImGuiSelectableFlags_Disabled flag in the public API. (#211) -- ColorEdit4: Fixed a bug when text input or drag and drop leading to unsaturated HSV values would erroneously alter the resulting color. (#2050) -- Misc: Added optional misc/stl/imgui_stl.h wrapper to use with STL types (e.g. InputText with std::string). (#2006, #1443, #1008) - [*EDIT* renamed to misc/std/imgui_stdlib.h in 1.66] -- Misc: Added IMGUI_VERSION_NUM for easy compile-time testing. (#2025) -- Misc: Added ImGuiMouseCursor_Hand cursor enum + corresponding software cursor. (#1913, 1914) [@aiekick, @ocornut] -- Misc: Tweaked software mouse cursor offset to match the offset of the corresponding Windows 10 cursors. -- Made assertion more clear when trying to call Begin() outside of the NewFrame()..EndFrame() scope. (#1987) -- Fixed assertion when transitioning from an active ID to another within a group, affecting ColorPicker (broken in 1.62). (#2023, #820, #956, #1875). -- Fixed PushID() from keeping alive the new ID Stack top value (if a previously active widget shared the ID it would be erroneously kept alive). -- Fixed horizontal mouse wheel not forwarding the request to the parent window if ImGuiWindowFlags_NoScrollWithMouse is set. (#1463, #1380, #1502) -- Fixed a include build issue for Cygwin in non-POSIX (Win32) mode. (#1917, #1319, #276) -- ImDrawList: Improved handling for worst-case vertices reservation policy when large amount of text (e.g. 1+ million character strings) - are being submitted in a single call. It would typically have crashed InputTextMultiline(). (#200) -- OS/Windows: Fixed missing ImmReleaseContext() call in the default Win32 IME handler. (#1932) [@vby] -- Metrics: Changed io.MetricsActiveWindows to reflect the number of active windows (!= from visible windows), which is useful - for lazy/idle render mechanisms as new windows are typically not visible for one frame. -- Metrics: Added io.MetricsRenderWindow to reflect the number of visible windows. -- Metrics: Added io.MetricsActiveAllocations, moving away from the cross-context global counters than we previously used. (#1565, #1599, #586) -- Demo: Added basic Drag and Drop demo. (#143) -- Demo: Modified the Console example to use InsertChars() in the input text callback instead of poking directly into the buffer. - Although this won't make a difference in the example itself, using InsertChars() will honor the resizing callback properly. (#2006, #1443, #1008). -- Demo: Clarified the use of IsItemHovered()/IsItemActive() right after being in the "Active, Focused, Hovered & Focused Tests" section. -- Examples: Tweaked the main.cpp of each example. -- Examples: Metal: Added Metal rendering backend. (#1929, #1873) [@warrenm] -- Examples: OSX: Added early raw OSX platform backend. (#1873) [@pagghiu, @itamago, @ocornut] -- Examples: Added mac OSX & iOS + Metal example in example_apple_metal/. (#1929, #1873) [@warrenm] -- Examples: Added mac OSX + OpenGL2 example in example_apple_opengl2/. (#1873) -- Examples: OpenGL3: Added shaders more versions of GLSL. (#1938, #1941, #1900, #1513, #1466, etc.) -- Examples: OpenGL3: Tweaked the imgui_impl_opengl3.cpp to work as-is with Emscripten + WebGL 2.0. (#1941). [@o-micron] -- Examples: OpenGL3: Made the example app default to GL 3.0 + GLSL 130 (instead of GL 3.2 + GLSL 150) unless on Mac. -- Examples: OpenGL3: Added error output when shaders fail to compile/link. -- Examples: OpenGL3: Added support for glew and glad OpenGL loaders out of the box. (#2001, #2002) [@jdumas] -- Examples: OpenGL2: Disabling/restoring GL_LIGHTING and GL_COLOR_MATERIAL to increase compatibility with legacy OpenGL applications. (#1996) -- Examples: DirectX10, DirectX11: Fixed unreleased resources in Init and Shutdown functions. (#1944) -- Examples: DirectX11: Querying for IDXGIFactory instead of IDXGIFactory1 to increase compatibility. (#1989) [@matt77hias] -- Examples: Vulkan: Fixed handling of VkSurfaceCapabilitiesKHR::maxImageCount = 0 case. Tweaked present mode selections. -- Examples: Win32, Glfw, SDL: Added support for the ImGuiMouseCursor_Hand cursor. - - ------------------------------------------------------------------------ - VERSION 1.62 (Released 2018-06-22) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.62 - -Breaking Changes: - -- TreeNodeEx(): The helper ImGuiTreeNodeFlags_CollapsingHeader flag now include ImGuiTreeNodeFlags_NoTreePushOnOpen. - The flag was already set by CollapsingHeader(). - The only difference is if you were using TreeNodeEx() manually with ImGuiTreeNodeFlags_CollapsingHeader and without - ImGuiTreeNodeFlags_NoTreePushOnOpen. In this case you can remove the ImGuiTreeNodeFlags_NoTreePushOnOpen flag from - your call (ImGuiTreeNodeFlags_CollapsingHeader & ~ImGuiTreeNodeFlags_NoTreePushOnOpen). (#1864) - This also apply if you were using internal's TreeNodeBehavior() with the ImGuiTreeNodeFlags_CollapsingHeader flag directly. -- ImFontAtlas: Renamed GetGlyphRangesChinese() to GetGlyphRangesChineseFull() to distinguish new smaller variants and - discourage using the full set. (#1859) - -Other Changes: - -- Examples backends have been refactored to separate the platform code (e.g. Win32, Glfw, SDL2) from the renderer code (e.g. DirectX11, OpenGL3, Vulkan). - The "Platform" backends are in charge of: mouse/keyboard/gamepad inputs, cursor shape, timing, etc. - The "Renderer" backends are in charge of: creating the main font texture, rendering imgui draw data. - before: imgui_impl_dx11.cpp --> after: imgui_impl_win32.cpp + imgui_impl_dx11.cpp - before: imgui_impl_dx12.cpp --> after: imgui_impl_win32.cpp + imgui_impl_dx12.cpp - before: imgui_impl_glfw_gl3.cpp --> after: imgui_impl_glfw.cpp + imgui_impl_opengl2.cpp - before: imgui_impl_glfw_vulkan.cpp --> after: imgui_impl_glfw.cpp + imgui_impl_vulkan.cpp - before: imgui_impl_sdl_gl3.cpp --> after: imgui_impl_sdl2.cpp + imgui_impl_opengl2.cpp - before: imgui_impl_sdl_gl3.cpp --> after: imgui_impl_sdl2.cpp + imgui_impl_opengl3.cpp etc. - - The idea is what we can now easily combine and maintain backends and reduce code redundancy. Individual files are - smaller and more reusable. Integration of imgui into a new/custom engine may also be easier as there is less overlap - between "windowing / inputs" and "rendering" code, so you may study or grab one half of the code and not the other. - - This change was motivated by the fact that adding support for the upcoming multi-viewport feature requires more work - from the Platform and Renderer backends, and the amount of redundancy across files was becoming too difficult to - maintain. If you use default backends, you'll benefit from an easy update path to support multi-viewports later - (for future ImGui 1.7x). - - This is not strictly a breaking change if you keep your old backends, but when you'll want to fully update your backends, - expect to have to reshuffle a few things. - - Each example still has its own main.cpp which you may refer you to understand how to initialize and glue everything together. - - Some frameworks (such as the Allegro, Marmalade) handle both the "platform" and "rendering" part, and your custom engine may as well. - - Read examples/README.txt for details. -- Added IsItemDeactivated() to query if the last item was active previously and isn't anymore. Useful for Undo/Redo patterns. (#820, #956, #1875) -- Added IsItemDeactivatedAfterChange() [*EDIT* renamed to IsItemDeactivatedAfterEdit() in 1.63] if the last item was active previously, - is not anymore, and during its active state modified a value. Note that you may still get false positive (e.g. drag value and while - holding return on the same value). (#820, #956, #1875) -- Nav: Added support for PageUp/PageDown (explorer-style: first aim at bottom/top most item, when scroll a page worth of contents). (#787) -- Nav: To keep the navigated item in view we also attempt to scroll the parent window as well as the current window. (#787) -- ColorEdit3, ColorEdit4, ColorButton: Added ImGuiColorEditFlags_NoDragDrop flag to disable ColorEditX as drag target and ColorButton as drag source. (#1826) -- BeginDragDropSource(): Offset tooltip position so it is off the mouse cursor, but also closer to it than regular tooltips, - and not clamped by viewport. (#1739) -- BeginDragDropTarget(): Added ImGuiDragDropFlags_AcceptNoPreviewTooltip flag to request hiding the drag source tooltip - from the target site. (#143) -- BeginCombo(), BeginMainMenuBar(), BeginChildFrame(): Temporary style modification are restored at the end of BeginXXX - instead of EndXXX, to not affect tooltips and child windows. -- Popup: Improved handling of (erroneously) repeating calls to OpenPopup() to not close the popup's child popups. (#1497, #1533, #1865). -- InputTextMultiline(): Fixed double navigation highlight when scrollbar is active. (#787) -- InputText(): Fixed Undo corruption after pasting large amount of text (Redo will still fail when undo buffers are exhausted, - but text won't be corrupted). -- SliderFloat(): When using keyboard/gamepad and a zero precision format string (e.g. "%.0f"), always step in integer units. (#1866) -- ImFontConfig: Added GlyphMinAdvanceX/GlyphMaxAdvanceX settings useful to make a font appears monospaced, particularly useful - for icon fonts. (#1869) -- ImFontAtlas: Added GetGlyphRangesChineseSimplifiedCommon() helper that returns a list of ~2500 most common Simplified Chinese - characters. (#1859) [@JX-Master, @ocornut] -- Examples: OSX: Added imgui_impl_osx.mm backend to be used along with e.g. imgui_impl_opengl2.cpp. (#281, #1870) [@pagghiu, @itamago, @ocornut] -- Examples: GLFW: Made it possible to Shutdown/Init the backend again (by resetting the time storage properly). (#1827) [@ice1000] -- Examples: Win32: Fixed handling of mouse wheel messages to support sub-unit scrolling messages (typically sent by track-pads). (#1874) [@zx64] -- Examples: SDL+Vulkan: Added SDL+Vulkan example. -- Examples: Allegro5: Added support for ImGuiConfigFlags_NoMouseCursorChange flag. Added clipboard support. -- Examples: Allegro5: Unindexing buffers ourselves as Allegro indexed drawing primitives are buggy in the DirectX9 backend - (will be fixed in Allegro 5.2.5+). -- Examples: DirectX12: Moved the ID3D12GraphicsCommandList* parameter from ImGui_ImplDX12_NewFrame() to ImGui_ImplDX12_RenderDrawData() which makes a lots more sense. (#301) -- Examples: Vulkan: Reordered parameters ImGui_ImplVulkan_RenderDrawData() to be consistent with other backends, - a good occasion since we refactored the code. -- Examples: FreeGLUT: Added FreeGLUT backends. Added FreeGLUT+OpenGL2 example. (#801) -- Examples: The functions in imgui_impl_xxx.cpp are prefixed with IMGUI_IMPL_API (which defaults to IMGUI_API) to facilitate - some uses. (#1888) -- Examples: Fixed backends to use ImGuiMouseCursor_COUNT instead of old name ImGuiMouseCursor_Count_ so they can compile - with IMGUI_DISABLE_OBSOLETE_FUNCTIONS. (#1887) -- Misc: Updated stb_textedit from 1.09 + patches to 1.12 + minor patches. -- Internals: PushItemFlag() flags are inherited by BeginChild(). - - ------------------------------------------------------------------------ - VERSION 1.61 (Released 2018-05-14) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.61 - -Breaking Changes: - -- DragInt(): The default compile-time format string has been changed from "%.0f" to "%d", as we are not using integers internally - any more. If you used DragInt() with custom format strings, make sure you change them to use %d or an integer-compatible format. - To honor backward-compatibility, the DragInt() code will currently parse and modify format strings to replace %*f with %d, - giving time to users to upgrade their code. - If you have IMGUI_DISABLE_OBSOLETE_FUNCTIONS enabled, the code will instead assert! You may run a reg-exp search on your - codebase for e.g. "DragInt.*%f" to you find them. -- InputFloat(): Obsoleted InputFloat() functions taking an optional "int decimal_precision" in favor of an equivalent and more - flexible "const char* format", consistent with other functions. Kept redirection functions (will obsolete). -- Misc: IM_DELETE() helper function added in 1.60 doesn't set the input pointer to NULL, more consistent with standard - expectation and allows passing r-values. - -Other Changes: - -- Added DragScalar, DragScalarN: supports signed/unsigned, 32/64 bits, float/double data types. (#643, #320, #708, #1011) -- Added InputScalar, InputScalarN: supports signed/unsigned, 32/64 bits, float/double data types. (#643, #320, #708, #1011) -- Added SliderScalar, SliderScalarN: supports signed/unsigned, 32/64 bits, float/double data types. (#643, #320, #708, #1011) -- Window: Fixed pop-ups/tooltips/menus not honoring style.DisplaySafeAreaPadding as well as it should have (part of menus - displayed outside the safe area, etc.). -- Window: Fixed windows using the ImGuiWindowFlags_NoSavedSettings flag from not using the same default position as other windows. (#1760) -- Window: Relaxed the internal stack size checker to allow Push/Begin/Pop/.../End patterns to be used with PushStyleColor, PushStyleVar, PushFont without causing a false positive assert. (#1767) -- Window: Fixed the default proportional item width lagging by one frame on resize. -- Columns: Fixed a bug introduced in 1.51 where columns would affect the contents size of their container, often creating - feedback loops when ImGuiWindowFlags_AlwaysAutoResize was used. (#1760) -- Settings: Fixed saving an empty .ini file if CreateContext/DestroyContext are called without a single call to NewFrame(). (#1741) -- Settings: Added LoadIniSettingsFromDisk(), LoadIniSettingsFromMemory(), SaveIniSettingsToDisk(), SaveIniSettingsToMemory() - to manually load/save .ini settings. (#923, #993) -- Settings: Added io.WantSaveIniSettings flag, which is set to notify the application that e.g. SaveIniSettingsToMemory() - should be called. (#923, #993) -- Scrolling: Fixed a case where using SetScrollHere(1.0f) at the bottom of a window on the same frame the window height - has been growing would have the scroll clamped using the previous height. (#1804) -- MenuBar: Made BeginMainMenuBar() honor style.DisplaySafeAreaPadding so the text can be made visible on TV settings that - don't display all pixels. (#1439) [@dougbinks] -- InputText: On Mac OS X, filter out characters when the CMD modifier is held. (#1747) [@sivu] -- InputText: On Mac OS X, support CMD+SHIFT+Z for Redo. CMD+Y is also supported as major apps seems to default to support both. (#1765) [@lfnoise] -- InputText: Fixed returning true when edition is cancelled with ESC and the current buffer matches the initial value. -- InputFloat,InputFloat2,InputFloat3,InputFloat4: Added variations taking a more flexible and consistent optional - "const char* format" parameter instead of "int decimal_precision". This allow using custom formats to display values - in scientific notation, and is generally more consistent with other API. - Obsoleted functions using the optional "int decimal_precision" parameter. (#648, #712) -- DragFloat, DragInt: Cancel mouse tweak when current value is initially past the min/max boundaries and mouse is pushing - in the same direction (keyboard/gamepad version already did this). -- DragFloat, DragInt: Honor natural type limits (e.g. INT_MAX, FLT_MAX) instead of wrapping around. (#708, #320) -- DragFloat, SliderFloat: Fixes to allow input of scientific notation numbers when using CTRL+Click to input the value. (~#648, #1011) -- DragFloat, SliderFloat: Rounding-on-write uses the provided format string instead of parsing the precision from the string, - which allows for finer uses of %e %g etc. (#648, #642) -- DragFloat: Improved computation when using the power curve. Improved lost of input precision with very small steps. - Added an assert than power-curve requires a min/max range. (~#642) -- DragFloat: The 'power' parameter is only honored if the min/max parameter are also setup. -- DragInt, SliderInt: Fixed handling of large integers (we previously passed data around internally as float, which reduced - the range of valid integers). -- ColorEdit: Fixed not being able to pass the ImGuiColorEditFlags_NoAlpha or ImGuiColorEditFlags_HDR flags to SetColorEditOptions(). -- Nav: Fixed hovering a Selectable() with the mouse so that it update the navigation cursor (as it happened in the pre-1.60 navigation branch). (#787) -- Style: Changed default style.DisplaySafeAreaPadding values from (4,4) to (3,3) so it is smaller than FramePadding and has no effect on main menu bar on a computer. (#1439) -- Fonts: When building font atlas, glyphs that are missing in the fonts are not using the glyph slot to render the default glyph. Saves space and allow merging fonts with - overlapping font ranges such as FontAwesome5 which split out the Brands separately from the Solid fonts. (#1703, #1671) -- Misc: Added IMGUI_CHECKVERSION() macro to compare version string and data structure sizes in order to catch issues with mismatching compilation unit settings. (#1695, #1769) -- Misc: Added IMGUI_DISABLE_MATH_FUNCTIONS in imconfig.h to make it easier to redefine wrappers for std/crt math functions. -- Misc: Fix to allow compiling in unity builds where stb_rectpack/stb_truetype may be already included in the same compilation unit. -- Demo: Simple Overlay: Added a context menu item to enable freely moving the window. -- Demo: Added demo for DragScalar(), InputScalar(), SliderScalar(). (#643) -- Examples: Calling IMGUI_CHECKVERSION() in the main.cpp of every example application. -- Examples: Allegro 5: Added support for 32-bit indices setup via defining ImDrawIdx, to avoid an unnecessary conversion (Allegro 5 doesn't support 16-bit indices). -- Examples: Allegro 5: Renamed backend from imgui_impl_a5.cpp to imgui_impl_allegro5.cpp. -- Examples: DirectX 9: Saving/restoring Transform because they don't seem to be included in the StateBlock. Setting shading mode to Gouraud. (#1790, #1687) [@sr-tream] -- Examples: SDL: Fixed clipboard paste memory leak in the SDL backend code. (#1803) [@eliasdaler] -- Various minor fixes, tweaks, refactoring, comments. - - ------------------------------------------------------------------------ - VERSION 1.60 (Released 2018-04-07) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.60 - -The gamepad/keyboard navigation branch (which has been in the work since July 2016) has been merged. -Gamepad/keyboard navigation is still marked as Beta and has to be enabled explicitly. -Various internal refactoring have also been done, as part of the navigation work and as part of the upcoming viewport/docking work. - -Breaking Changes: - -- Obsoleted the io.RenderDrawListsFn callback, you can call your graphics engine render function after ImGui::Render(). - e.g. with example backends, call ImDrawData* draw_data = ImGui::GetDrawData(); ImGui_ImplXXXX_RenderDrawData(draw_data). -- Reorganized context handling to be more explicit: (#1599) - - YOU NOW NEED TO CALL ImGui::CreateContext() AT THE BEGINNING OF YOUR APP, AND CALL ImGui::DestroyContext() AT THE END. - - removed Shutdown() function, as DestroyContext() serve this purpose. If you are using an old backend from the examples/ folder, remove the line that calls Shutdown(). - - you may pass a ImFontAtlas* pointer to CreateContext() to share a font atlas between contexts. Otherwise CreateContext() will create its own font atlas instance. - - removed allocator parameters from CreateContext(), they are now setup with SetAllocatorFunctions(), and shared by all contexts. - - removed the default global context and font atlas instance, which were confusing for users of DLL reloading and users of multiple contexts. -- Renamed ImGuiStyleVar_Count_ to ImGuiStyleVar_COUNT and ImGuiMouseCursor_Count_ to ImGuiMouseCursor_COUNT for consistency with other public enums. -- Fonts: Moved sample TTF files from extra_fonts/ to misc/fonts/. If you loaded files directly from the imgui repo you may need to update your paths. -- Fonts: Changed ImFont::DisplayOffset.y to defaults to 0 instead of +1. Fixed vertical rounding of Ascent/Descent to match TrueType renderer. - If you were adding or subtracting (not assigning) to ImFont::DisplayOffset check if your fonts are correctly aligned vertically. (#1619) -- BeginDragDropSource(): temporarily removed the optional mouse_button=0 parameter because it is not really usable in many situations at the moment. -- Obsoleted IsAnyWindowHovered() in favor of IsWindowHovered(ImGuiHoveredFlags_AnyWindow). Kept redirection function (will obsolete). -- Obsoleted IsAnyWindowFocused() in favor of IsWindowFocused(ImGuiFocusedFlags_AnyWindow). Kept redirection function (will obsolete). -- Renamed io.WantMoveMouse to io.WantSetMousePos for consistency and ease of understanding (was added in 1.52, not used by core, and honored by some backend ahead of merging the Nav branch). -- Removed ImGuiCol_CloseButton, ImGuiCol_CloseButtonActive, ImGuiCol_CloseButtonHovered style colors as the closing cross uses regular button colors now. -- Renamed ImGuiSizeConstraintCallback to ImGuiSizeCallback, ImGuiSizeConstraintCallbackData to ImGuiSizeCallbackData. -- Removed CalcItemRectClosestPoint() which was weird and not really used by anyone except demo code. If you need it should be easy to replicate on your side (you can find the code in 1.53). -- [EDITED] Window: BeginChild() with an explicit name doesn't include the hash within the internal window name. (#1698) - This change was erroneously introduced, undoing the change done for #894, #713, and not documented properly in the original - 1.60 release Changelog. It was fixed on 2018-09-28 (1.66) and I wrote this paragraph the same day. - -Other Changes: - -- Doc: Added a Changelog file in the repository to ease comparing versions (it goes back to dear imgui 1.48), until now it was only on GitHub. -- Navigation: merged in the gamepad/keyboard navigation (about a million changes!). (#787, #323) - The initial focus was to support game controllers, but keyboard is becoming increasingly and decently usable. -- To use Gamepad Navigation: - - Set io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad to enable. - - Backend: Set io.BackendFlags |= ImGuiBackendFlags_HasGamepad + fill the io.NavInputs[] fields before calling NewFrame(). Read imgui.cpp for more details. - - See https://github.com/ocornut/imgui/issues/1599 for recommended gamepad mapping or download PNG/PSD at http://goo.gl/9LgVZW - - See 'enum ImGuiNavInput_' in imgui.h for a description of inputs. Read imgui.cpp for more details. -- To use Keyboard Navigation: - - Set io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard to enable. NewFrame() will automatically fill io.NavInputs[] based on your io.KeysDown[] + io.KeyMap[] arrays. - - Basic controls: arrows to navigate, Alt to enter menus, Space to activate item, Enter to edit text, Escape to cancel/close, Ctrl-Tab to focus windows, etc. - - When keyboard navigation is active (io.NavActive + ImGuiConfigFlags_NavEnableKeyboard), the io.WantCaptureKeyboard flag will be set. - For more advanced uses, you may want to read from io.NavActive or io.NavVisible. Read imgui.cpp for more details. -- Navigation: SetItemDefaultFocus() sets the navigation position in addition to scrolling. (#787) -- Navigation: Added IsItemFocused(), added IsAnyItemFocused(). (#787) -- Navigation: Added window flags: ImGuiWindowFlags_NoNav (== ImGuiWindowFlags_NoNavInputs | ImGuiWindowFlags_NoNavFocus). -- Navigation: Style: Added ImGuiCol_NavHighlight, ImGuiCol_NavWindowingHighlight colors. (#787) -- Navigation: TreeNode: Added ImGuiTreeNodeFlags_NavLeftJumpsBackHere flag to allow Nav Left direction to jump back to parent tree node from any of its child. (#1079) -- Navigation: IO: Added io.ConfigFlags (input), io.NavActive (output), io.NavVisible (output). (#787) -- Context: Removed the default global context and font atlas instances, which caused various problems to users of multiple contexts and DLL users. (#1565, #1599) - YOU NOW NEED TO CALL ImGui::CreateContext() AT THE BEGINNING OF YOUR APP, AND CALL ImGui::DestroyContext() AT THE END. Existing apps will assert/crash without it. -- Context: Added SetAllocatorFunctions() to rewire memory allocators (as a replacement to previous parameters to CreateContext()). Allocators are shared by all contexts and imgui helpers. (#1565, #586, #992, #1007, #1558) -- Context: You may pass a ImFontAtlas to CreateContext() to specify a font atlas to share. Shared font atlas are not owned by the context and not destroyed along with it. (#1599) -- Context: Added IMGUI_DISABLE_DEFAULT_ALLOCATORS to disable linking with malloc/free. (#1565, #586, #992, #1007, #1558) -- IO: Added io.ConfigFlags for user application to store settings for imgui and for the backend: - - ImGuiConfigFlags_NavEnableKeyboard: Enable keyboard navigation. - - ImGuiConfigFlags_NavEnableGamepad: Enable gamepad navigation (provided ImGuiBackendFlags_HasGamepad is also set by backend). - - ImGuiConfigFlags_NavEnableSetMousePos: Instruct navigation to move the mouse cursor. May be useful on TV/console systems where moving a virtual mouse is awkward. - - ImGuiConfigFlags_NoMouseCursorChange: Instruct backend to not alter mouse cursor shape and visibility (by default the example backend use mouse cursor API of the platform when available) - - ImGuiConfigFlags_NoMouse: Instruct imgui to clear mouse position/buttons in NewFrame(). This allows ignoring the mouse information passed by the backend. - - ImGuiConfigFlags_IsSRGB, ImGuiConfigFlags_IsTouchScreen: Flags for general application use. -- IO: Added io.BackendFlags for backend to store its capabilities (currently: _HasGamepad, _HasMouseCursors, _HasSetMousePos). This will be used more in the next version. -- IO: Added ImGuiKey_Insert, ImGuiKey_Space keys. Setup in all example backends. (#1541) -- IO: Added Horizontal Mouse Wheel support for horizontal scrolling. (#1463) [@tseeker] -- IO: Added IsAnyMouseDown() helper which is helpful for backends to handle mouse capturing. -- Window: Clicking on a window with the ImGuiWIndowFlags_NoMove flags takes an ActiveId so we can't hover something else when dragging afterwards. (#1381, #1337) -- Window: IsWindowHovered(): Added ImGuiHoveredFlags_AnyWindow, ImGuiFocusedFlags_AnyWindow flags (See Breaking Changes). Added to demo. (#1382) -- Window: Added SetNextWindowBgAlpha() helper. Particularly helpful since the legacy 5-parameters version of Begin() has been marked as obsolete in 1.53. (#1567) -- Window: Fixed SetNextWindowContentSize() with 0.0f on Y axis (or SetNextWindowContentWidth()) overwriting the contents size. Got broken on Dec 10 (1.53). (#1363) -- ArrowButton: Added ArrowButton() given a cardinal direction (e.g. ImGuiDir_Left). -- InputText: Added alternative clipboard shortcuts: Shift+Delete (cut), CTRL+Insert (copy), Shift+Insert (paste). (#1541) -- InputText: Fixed losing Cursor X position when clicking outside on an item that's submitted after the InputText(). It was only noticeable when restoring focus programmatically. (#1418, #1554) -- InputText: Added ImGuiInputTextFlags_CharsScientific flag to also allow 'e'/'E' for input of values using scientific notation. Automatically used by InputFloat. -- Style: Default style is now StyleColorsDark(), instead of the old StyleColorsClassic(). (#707) -- Style: Enable window border by default. (#707) -- Style: Exposed ImGuiStyleVar_WindowTitleAlign, ImGuiStyleVar_ScrollbarSize, ImGuiStyleVar_ScrollbarRounding, ImGuiStyleVar_GrabRounding + added an assert to reduce accidental breakage. (#1181) -- Style: Added style.MouseCursorScale help when using the software mouse cursor facility. (#939). -- Style: Close button nows display a cross before hovering. Fixed cross positioning being a little off. Uses button colors for highlight when hovering. (#707) -- Popup: OpenPopup() Always reopen existing pop-ups. (Removed imgui_internal.h's OpenPopupEx() which was used for this.) (#1497, #1533). -- Popup: BeginPopupContextItem(), BeginPopupContextWindow(), BeginPopupContextVoid(), OpenPopupOnItemClick() all react on mouse release instead of mouse press. (~#439) -- Popup: Better handling of user mistakenly calling OpenPopup() every frame (with reopen_existing option). The error will now be more visible and easier to understand. (#1497) -- Popup: BeginPopup(): Exposed extra_flags parameter that are passed through to Begin(). (#1533) -- Popup: BeginPopupModal: fixed the conditional test for SetNextWindowPos() which was polling the wrong window, which in practice made the test succeed all the time. -- Tooltip: BeginTooltip() sets ImGuiWindowFlags_NoInputs flag. -- Scrollbar: Fixed ScrollbarY enable test after ScrollbarX has been enabled being a little off (small regression from Nov 2017). (#1574) -- Scrollbar: Fixed ScrollbarX enable test subtracting WindowPadding.x (this has been there since the addition of horizontal scroll bar!). -- Columns: Clear offsets data when columns count changed. (#1525) -- Columns: Fixed a memory leak of ImGuiColumnsSet's Columns vector. (#1529) [@unprompted] -- Columns: Fixed resizing a window very small breaking some columns positioning (broken in 1.53). -- Columns: The available column extent takes consideration of the right-most clipped pixel, so the right-most column may look a little wider but will contain the same amount of visible contents. -- MenuBar: Fixed menu bar pushing a clipping rect outside of its allocated bound (usually unnoticeable). -- TreeNode: nodes with the ImGuiTreeNodeFlags_Leaf flag correctly disable highlight when DragDrop is active. (#143, #581) -- Drag and Drop: Increased payload type string to 32 characters instead of 8. (#143) -- Drag and Drop: TreeNode as drop target displays rectangle over full frame. (#1597, #143) -- DragFloat: Fix/workaround for backends which do not preserve a valid mouse position when dragged out of bounds. (#1559) -- InputFloat: Allow inputing value using scientific notation e.g. "1e+10". -- InputDouble: Added InputDouble() function. We use a format string instead of a decimal_precision parameter to also for "%e" and variants. (#1011) -- Slider, Combo: Use ImGuiCol_FrameBgHovered color when hovered. (#1456) [@stfx] -- Combo: BeginCombo(): Added ImGuiComboFlags_NoArrowButton to disable the arrow button and only display the wide value preview box. -- Combo: BeginCombo(): Added ImGuiComboFlags_NoPreview to disable the preview and only display a square arrow button. -- Combo: Arrow button isn't displayed over frame background so its blended color matches other buttons. Left side of the button isn't rounded. -- PlotLines: plot a flat line if scale_min==scale_max. (#1621) -- Fonts: Changed DisplayOffset.y to defaults to 0 instead of +1. Fixed rounding of Ascent/Descent to match TrueType renderer. - If you were adding or subtracting (not assigning) to ImFont::DisplayOffset check if your fonts are correctly aligned vertically. (#1619) -- Fonts: Updated stb_truetype from 1.14 to stb_truetype 1.19. (w/ include fix from some platforms #1622) -- Fonts: Added optional FreeType rasterizer in misc/freetype. Moved from imgui_club repo. (#618) [@Vuhdo, @mikesart, @ocornut] -- Fonts: Moved extra_fonts/ to misc/fonts/. -- ImFontAtlas: Fixed cfg.MergeMode not reusing existing glyphs if available (always overwrote). -- ImFontAtlas: Handle stb_truetype stbtt_InitFont() and stbtt_PackBegin() possible failures more gracefully, GetTexDataAsRGBA32() won't crash during conversion. (#1527) -- ImFontAtlas: Moved mouse cursor data out of ImGuiContext, fix drawing them with multiple contexts. Also remove the last remaining undesirable dependency on ImGui in imgui_draw.cpp. (#939) -- ImFontAtlas: Added ImFontAtlasFlags_NoPowerOfTwoHeight flag to disable padding font height to nearest power of two. (#1613) -- ImFontAtlas: Added ImFontAtlasFlags_NoMouseCursors flag to disable baking software mouse cursors, mostly to save texture memory on very low end hardware. (#1613) -- ImDrawList: Fixed AddRect() with anti-aliasing disabled (lower-right corner pixel was often missing, rounding looks a little better.) (#1646) -- ImDrawList: Added CloneOutput() helper to facilitate the cloning of ImDrawData or ImDrawList for multi-threaded rendering. -- Misc: Functions passed to libc qsort are explicitly marked cdecl to support compiling with vectorcall as the default calling convention. (#1230, #1611) [@RandyGaul] -- Misc: ImVec2: added [] operator. This is becoming desirable for some code working of either axes independently. Better adding it sooner than later. -- Misc: NewFrame(): Added an assert to detect incorrect filling of the io.KeyMap[] array earlier. (#1555) -- Misc: Added IM_OFFSETOF() helper in imgui.h (previously was in imgui_internal.h) -- Misc: Added IM_NEW(), IM_DELETE() helpers in imgui.h (previously were in imgui_internal.h) -- Misc: Added obsolete redirection function GetItemsLineHeightWithSpacing() (which redirects to GetFrameHeightWithSpacing()), as intended and stated in docs of 1.53. -- Misc: Added misc/natvis/imgui.natvis for visual studio debugger users to easily visualize imgui internal types. Added to examples projects. -- Misc: Added IMGUI_USER_CONFIG to define a custom configuration filename. (#255, #1573, #1144, #41) -- Misc: Added IMGUI_STB_TRUETYPE_FILENAME and IMGUI_STB_RECT_PACK_FILENAME compile time directives to use another version of the stb_ files. -- Misc: Updated stb_rect_pack from 0.10 to 0.11 (minor changes). - (Those flags are not used by ImGui itself, they only exists to make it easy for the engine/backend to pass information to the application in a standard manner.) -- Metrics: Added display of Columns state. -- Demo: Improved Selectable() examples. (#1528) -- Demo: Tweaked the Child demos, added a menu bar to the second child to test some navigation functions. -- Demo: Console: Using ImGuiCol_Text to be more friendly to color changes. -- Demo: Using IM_COL32() instead of ImColor() in ImDrawList centric contexts. Trying to phase out use of the ImColor helper whenever possible. -- Examples: Files in examples/ now include their own changelog so it is easier to occasionally update your backends if needed. -- Examples: Using Dark theme by default. (#707). Tweaked demo code. -- Examples: Added support for horizontal mouse wheel for API that allows it. (#1463) [@tseeker] -- Examples: All examples now setup the io.BackendFlags to signify they can honor mouse cursors, gamepad, etc. -- Examples: DirectX10: Fixed erroneous call to io.Fonts->ClearInputData() + ClearTexData() that was left in DX10 example but removed in 1.47 (Nov 2015) in every other backends. (#1733) -- Examples: DirectX12: Added DirectX 12 example. (#301) [@jdm3] -- Examples: OpenGL3+GLFW,SDL: Changed GLSL shader version from 330 to 150. (#1466, #1504) -- Examples: OpenGL3+GLFW,SDL: Added a way to override the GLSL version string in the Init function. (#1466, #1504). -- Examples: OpenGL3+GLFW,SDL: Creating VAO in the render function so it can be more easily used by multiple shared OpenGL contexts. (#1217) -- Examples: OpenGL3+GLFW: Using 3.2 context instead of 3.3. (#1466) -- Examples: OpenGL: Setting up glPixelStorei() explicitly before uploading texture. -- Examples: OpenGL: Calls to glPolygonMode() are casting parameters as GLEnum to not fail with more strict backends. (#1628) [@ilia-glushchenko] -- Examples: Win32 (DirectX9,10,11,12): Added support for mouse cursor shapes. (#1495) -- Examples: Win32 (DirectX9,10,11,12: Support for windows using the CS_DBLCLKS class flag by handling the double-click messages (WM_LBUTTONDBLCLK etc.). (#1538, #754) [@ndandoulakis] -- Examples: Win32 (DirectX9,10,11,12): Made the Win32 proc handlers not assert if there is no active context yet, to be more flexible with creation order. (#1565) -- Examples: GLFW: Added support for mouse cursor shapes (the diagonal resize cursors are unfortunately not supported by GLFW at the moment. (#1495) -- Examples: GLFW: Don't attempt to change the mouse cursor input mode if it is set to GLFW_CURSOR_DISABLED by the application. (#1202) [@PhilCK] -- Examples: SDL: Added support for mouse cursor shapes. (#1626) [@olls] -- Examples: SDL: Using SDL_CaptureMouse() to retrieve coordinates outside of client area when dragging (SDL 2.0.4+ only, otherwise using SDL_WINDOW_INPUT_FOCUS instead of previously SDL_WINDOW_MOUSE_FOCUS). (#1559) -- Examples: SDL: Enabled vsync by default so people don't come at us when the examples are running at 2000 FPS and burning a CPU core. -- Examples: SDL: Using SDL_GetPerformanceCounter() / SDL_GetPerformanceFrequency() to handle frame-rate over 1000 FPS properly. (#996) -- Examples: SDL: Using scan-code exclusively instead of a confusing mixture of scan-codes and key-codes. -- Examples: SDL: Visual Studio: Added .vcxproj file. Using %SDL2_DIR% in the default .vcxproj and build files instead of %SDL_DIR%, the earlier being more standard. -- Examples: Vulkan: Visual Studio: Added .vcxproj file. -- Examples: Apple: Fixed filenames in OSX xcode project. Various other Mac friendly fixes. [@gerryhernandez etc.] -- Examples: Visual Studio: Disabled extraneous function-level check in Release build. -- Various fixes, tweaks, internal refactoring, optimizations, comments. - - ------------------------------------------------------------------------ - VERSION 1.53 (Released 2017-12-25) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.53 - -Breaking Changes: - -- Renamed the emblematic `ShowTestWindow()` function to `ShowDemoWindow()`. Kept redirection function (will obsolete). -- Renamed `GetItemsLineHeightWithSpacing()` to `GetFrameHeightWithSpacing()` for consistency. Kept redirection function (will obsolete). -- Renamed `ImGuiTreeNodeFlags_AllowOverlapMode` flag to `ImGuiTreeNodeFlags_AllowItemOverlap`. Kept redirection enum (will obsolete). -- Obsoleted `IsRootWindowFocused()` in favor of using `IsWindowFocused(ImGuiFocusedFlags_RootWindow)`. Kept redirection function (will obsolete). (#1382) -- Obsoleted `IsRootWindowOrAnyChildFocused()` in favor of using `IsWindowFocused(ImGuiFocusedFlags_RootAndChildWindows)`. Kept redirection function (will obsolete). (#1382) -- Obsoleted `IsRootWindowOrAnyChildHovered()` in favor of using `IsWindowHovered(ImGuiHoveredFlags_RootAndChildWindows)`. Kept redirection function (will obsolete). (#1382) -- Obsoleted `SetNextWindowContentWidth() in favor of using `SetNextWindowContentSize()`. Kept redirection function (will obsolete). -- Renamed `ImGuiTextBuffer::append()` helper to `appendf()`, and `appendv()` to `appendfv()` for consistency. If you copied the 'Log' demo in your code, it uses appendv() so that needs to be renamed. -- ImDrawList: Removed 'bool anti_aliased = true' final parameter of `ImDrawList::AddPolyline()` and `ImDrawList::AddConvexPolyFilled()`. Prefer manipulating ImDrawList::Flags if you need to toggle them during the frame. -- Style, ImDrawList: Renamed `style.AntiAliasedShapes` to `style.AntiAliasedFill` for consistency and as a way to explicitly break code that manipulate those flag at runtime. You can now manipulate ImDrawList::Flags. -- Style, Begin: Removed `ImGuiWindowFlags_ShowBorders` window flag. Borders are now fully set up in the ImGuiStyle structure (see e.g. `style.FrameBorderSize`, `style.WindowBorderSize`, `style.PopupBorderSize`). - Use `ImGui::ShowStyleEditor()` to look them up. - Please note that the style system will keep evolving (hopefully stabilizing in Q1 2018), and so custom styles will probably subtly break over time. - It is recommended that you use the `StyleColorsClassic()`, `StyleColorsDark()`, `StyleColorsLight()` functions. Also see `ShowStyleSelector()`. -- Style: Removed `ImGuiCol_ComboBg` in favor of combo boxes using `ImGuiCol_PopupBg` for consistency. Combo are normal pop-ups. -- Style: Renamed `ImGuiCol_ChildWindowBg` to `ImGuiCol_ChildBg`. -- Style: Renamed `style.ChildWindowRounding` to `style.ChildRounding`, `ImGuiStyleVar_ChildWindowRounding` to `ImGuiStyleVar_ChildRounding`. -- Removed obsolete redirection functions: SetScrollPosHere() - marked obsolete in v1.42, July 2015. -- Removed obsolete redirection functions: GetWindowFont(), GetWindowFontSize() - marked obsolete in v1.48, March 2016. - -Other Changes: - -- Added `io.OptCursorBlink` option to allow disabling cursor blinking. (#1427) [renamed to io.ConfigCursorBlink in 1.63] -- Added `GetOverlayDrawList()` helper to quickly get access to a ImDrawList that will be rendered in front of every windows. -- Added `GetFrameHeight()` helper which returns `(FontSize + style.FramePadding.y * 2)`. -- Drag and Drop: Added Beta API to easily use drag and drop patterns between imgui widgets. - - Setup a source on a widget with `BeginDragDropSource()`, `SetDragDropPayload()`, `EndDragDropSource()` functions. - - Receive data with `BeginDragDropTarget()`, `AcceptDragDropPayload()`, `EndDragDropTarget()`. - - See ImGuiDragDropFlags for various options. - - The ColorEdit4() and ColorButton() widgets now support Drag and Drop. - - The API is tagged as Beta as it still may be subject to small changes. -- Drag and Drop: When drag and drop is active, tree nodes and collapsing header can be opened by hovering on them for 0.7 seconds. -- Renamed io.OSXBehaviors to io.OptMacOSXBehaviors. Should not affect users as the compile-time default is usually enough. (#473, #650) -- Style: Added StyleColorsDark() style. (#707) [@dougbinks] -- Style: Added StyleColorsLight() style. Best used with frame borders + thicker font than the default font. (#707) -- Style: Added style.PopupRounding setting. (#1112) -- Style: Added style.FrameBorderSize, style.WindowBorderSize, style.PopupBorderSize. Removed ImGuiWindowFlags_ShowBorders window flag! - Borders are now fully set up in the ImGuiStyle structure. Use ImGui::ShowStyleEditor() to look them up. (#707, fix #819, #1031) -- Style: Various small changes to the classic style (most noticeably, buttons are now using blue shades). (#707) -- Style: Renamed ImGuiCol_ChildWindowBg to ImGuiCol_ChildBg. -- Style: Renamed style.ChildWindowRounding to style.ChildRounding, ImGuiStyleVar_ChildWindowRounding to ImGuiStyleVar_ChildRounding. -- Style: Removed ImGuiCol_ComboBg in favor of combo boxes using ImGuiCol_PopupBg for consistency. (#707) -- Style: Made the ScaleAllSizes() helper rounds down every values so they are aligned on integers. -- Focus: Added SetItemDefaultFocus(), which in the current (master) branch behave the same as doing `if (IsWindowAppearing()) SetScrollHere()`. - In the navigation branch this will also set the default focus. Prefer using this when creating combo boxes with `BeginCombo()` so your code will be forward-compatible with gamepad/keyboard navigation features. (#787) -- Combo: Pop-up grows horizontally to accommodate for contents that is larger then the parent combo button. -- Combo: Added BeginCombo()/EndCombo() API which allows use to submit content of any form and manage your selection state without relying on indices. -- Combo: Added ImGuiComboFlags_PopupAlignLeft flag to BeginCombo() to prioritize keeping the pop-up on the left side (for small-button-looking combos). -- Combo: Added ImGuiComboFlags_HeightSmall, ImGuiComboFlags_HeightLarge, ImGuiComboFlags_HeightLargest to easily provide desired pop-up height. -- Combo: You can use SetNextWindowSizeConstraints() before BeginCombo() to specify specific pop-up width/height constraints. -- Combo: Offset popup position by border size so that a double border isn't so visible. (#707) -- Combo: Recycling windows by using a stack number instead of a unique id, wasting less memory (like menus do). -- InputText: Added ImGuiInputTextFlags_NoUndoRedo flag. (#1506, #1508) [@ibachar] -- Window: Fixed auto-resize allocating too much space for scrollbar when SizeContents is bigger than maximum window size (fixes c0547d3). (#1417) -- Window: Child windows with MenuBar use regular WindowPadding.y so layout look consistent as child or as a regular window. -- Window: Begin(): Fixed appending into a child window with a second Begin() from a different window stack querying the wrong window for the window->Collapsed test. -- Window: Calling IsItemActive(), IsItemHovered() etc. after a call to Begin() provides item data for the title bar, so you can easily test if the title bar is being hovered, etc. (#823) -- Window: Made it possible to use SetNextWindowPos() on a child window. -- Window: Fixed a one frame glitch. When an appearing window claimed the focus themselves, the title bar wouldn't use the focused color for one frame. -- Window: Added ImGuiWindowFlags_ResizeFromAnySide flag to resize from any borders or from the lower-left corner of a window. This requires your backend to honor GetMouseCursor() requests for full usability. (#822) -- Window: Sizing fixes when using SetNextWindowSize() on individual axises. -- Window: Hide new window for one frame until they calculate their size. Also fixes SetNextWindowPos() given a non-zero pivot. (#1694) -- Window: Made mouse wheel scrolling accommodate better to windows that are smaller than the scroll step. -- Window: SetNextWindowContentSize() adjust for the size of decorations (title bar/menu bar), but _not_ for borders are we consistently make borders not affect layout. - If you need a non-child window of an exact size with border enabled but zero window padding, you'll need to accommodate for the border size yourself. -- Window: Using the ImGuiWindowFlags_NoScrollWithMouse flag on a child window forwards the mouse wheel event to the parent window, unless either ImGuiWindowFlags_NoInputs or ImGuiWindowFlags_NoScrollbar are also set. (#1380, #1502) -- Window: Active Modal window always set the WantCaptureKeyboard flag. (#744) -- Window: Moving window doesn't use accumulating MouseDelta so straying out of imgui boundaries keeps moved imgui window at the same cursor-relative position. -- IsWindowFocused(): Added ImGuiFocusedFlags_ChildWindows flag to include child windows in the focused test. (#1382). -- IsWindowFocused(): Added ImGuiFocusedFlags_RootWindow flag to start focused test from the root (top-most) window. Obsolete IsRootWindowFocused(). (#1382) -- IsWindowHovered(): Added ImGuiHoveredFlags_ChildWindows flag to include child windows in the hovered test. (#1382). -- IsWindowHovered(): Added ImGuiHoveredFlags_RootWindow flag to start hovered test from the root (top-most) window. The combination of both flags obsoletes IsRootWindowOrAnyChildHovered(). (#1382) -- IsWindowHovered(): Fixed return value when an item is active to use the same logic as IsItemHovered(). (#1382, #1404) -- IsWindowHovered(): Always return true when current window is being moved. (#1382) -- Scrollbar: Fixed issues with vertical scrollbar flickering/appearing, typically when manually resizing and using a pattern of filling available height (e.g. full sized BeginChild). -- Scrollbar: Minor graphical fix for when scrollbar don't have enough visible space to display the full grab. -- Scrolling: Fixed padding and scrolling asymmetry where lower/right sides of a window wouldn't use WindowPadding properly + causing minor scrolling glitches. -- Tree: TreePush with zero arguments was ambiguous. Resolved by making it call TreePush(const void*). [@JasonWilkins] -- Tree: Renamed ImGuiTreeNodeFlags_AllowOverlapMode to ImGuiTreeNodeFlags_AllowItemOverlap. (#600, #1330) -- MenuBar: Fixed minor rendering issues on the right size when resizing a window very small and using rounded window corners. -- MenuBar: better software clipping to handle small windows, in particular child window don't have minimum constraints so we need to render clipped menus better. -- BeginMenu(): Tweaked the Arrow/Triangle displayed on child menu items. -- Columns: Clipping columns borders on Y axis on CPU because some Linux GPU drivers appears to be unhappy with triangle spanning large regions. (#125) -- Columns: Added ImGuiColumnsFlags_GrowParentContentsSize to internal API to restore old content sizes behavior (may be obsolete). (#1444, #125) -- Columns: Columns width is no longer lost when dragging a column to the right side of the window, until releasing the mouse button you have a chance to save them. (#1499, #125). [@ggtucker] -- Columns: Fixed dragging when using a same of columns multiple times in the frame. (#125) -- Indent(), Unindent(): Allow passing negative values. -- ColorEdit4(): Made IsItemActive() return true when picker pop-up is active. (#1489) -- ColorEdit4(): Tweaked tooltip so that the color button aligns more correctly with text. -- ColorEdit4(): Support drag and drop. Color buttons can be used as drag sources, and ColorEdit widgets as drag targets. (#143) -- ColorPicker4(): Fixed continuously returning true when holding mouse button on the sat/value/alpha locations. We only return true on value change. (#1489) -- NewFrame(): using literal strings in the most-frequently firing IM_ASSERT expressions to increase the odd of programmers seeing them (especially those who don't use a debugger). -- NewFrame() now asserts if neither Render or EndFrame have been called. Exposed EndFrame(). Made it legal to call EndFrame() more than one. (#1423) -- ImGuiStorage: Added BuildSortByKey() helper to rebuild storage from scratch. -- ImFont: Added GetDebugName() helper. -- ImFontAtlas: Added missing Thai punctuation in the GetGlyphRangesThai() ranges. (#1396) [@nProtect] -- ImDrawList: Removed 'bool anti_aliased = true' final parameter of ImDrawList::AddPolyline() and ImDrawList::AddConvexPolyFilled(). Anti-aliasing is controlled via the regular style.AntiAliased flags. -- ImDrawList: Added ImDrawList::AddImageRounded() helper. (#845) [@thedmd] -- ImDrawList: Refactored to make ImDrawList independent of ImGui. Removed static variable in PathArcToFast() which caused linking issues to some. -- ImDrawList: Exposed ImDrawCornerFlags, replaced occurrences of ~0 with an explicit ImDrawCornerFlags_All. NB: Inversed BotLeft (prev 1<<3, now 1<<2) and BotRight (prev 1<<2, now 1<<3). -- ImVector: Added ImVector::push_front() helper. -- ImVector: Added ImVector::contains() helper. -- ImVector: insert() uses grow_capacity() instead of using grow policy inconsistent with push_back(). -- Internals: Remove requirement to define IMGUI_DEFINE_PLACEMENT_NEW to use the IM_PLACEMENT_NEW macro. (#1103) -- Internals: ButtonBehavior: Fixed ImGuiButtonFlags_NoHoldingActiveID flag from incorrectly setting the ActiveIdClickOffset field. - This had no known effect within imgui code but could have affected custom drag and drop patterns. And it is more correct this way! (#1418) -- Internals: ButtonBehavior: Fixed ImGuiButtonFlags_AllowOverlapMode to avoid temporarily activating widgets on click before they have been correctly double-hovered. (#319, #600) -- Internals: Added SplitterBehavior() helper. (#319) -- Internals: Added IM_NEW(), IM_DELETE() helpers. (#484, #504, #1517) -- Internals: Basic refactor of the settings API which now allows external elements to be loaded/saved. -- Demo: Added ShowFontSelector() showing loaded fonts. -- Demo: Added ShowStyleSelector() to select among default styles. (#707) -- Demo: Renamed the emblematic ShowTestWindow() function to ShowDemoWindow(). -- Demo: Style Editor: Added a "Simplified settings" sections with check-boxes for border size and frame rounding. (#707, #1019) -- Demo: Style Editor: Added combo box to select stock styles and select current font when multiple are loaded. (#707) -- Demo: Style Editor: Using local storage so Save/Revert button makes more sense without code passing its storage. Added horizontal scroll bar. Fixed Save/Revert button to be always accessible. (#1211) -- Demo: Console: Fixed context menu issue. (#1404) -- Demo: Console: Fixed incorrect positioning which was hidden by a minor scroll issue (this would affect people who copied the Console code as is). -- Demo: Constrained Resize: Added more test cases. (#1417) -- Demo: Custom Rendering: Fixed clipping rectangle extruding out of parent window. -- Demo: Layout: Removed unnecessary and misleading BeginChild/EndChild calls. -- Demo: The "Color Picker with Palette" demo supports drag and drop. (#143) -- Demo: Display better mouse cursor info for debugging backends. -- Demo: Stopped using rand() function in demo code. -- Examples: Added a handful of extra comments (about fonts, third-party libraries used in the examples, etc.). -- Examples: DirectX9: Handle loss of D3D9 device (D3DERR_DEVICELOST). (#1464) -- Examples: Added null_example/ which is helpful for quick testing on multiple compilers/settings without relying on graphics library. -- Fix for using alloca() in "Clang with Microsoft Codechain" mode. -- Various fixes, optimizations, comments. - - ------------------------------------------------------------------------ - VERSION 1.52 (2017-10-27) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.52 - -Breaking Changes: - -- IO: `io.MousePos` needs to be set to ImVec2(-FLT_MAX,-FLT_MAX) when mouse is unavailable/missing, instead of ImVec2(-1,-1) as previously) This is needed so we can clear `io.MouseDelta` field when the mouse is made available again. -- Renamed `AlignFirstTextHeightToWidgets()` to `AlignTextToFramePadding()`. Kept inline redirection function (will obsolete). -- Obsoleted the legacy 5 parameters version of Begin(). Please avoid using it. If you need a transparent window background, uses `PushStyleColor()`. The old size parameter there was also misleading and equivalent to calling `SetNextWindowSize(size, ImGuiCond_FirstTimeEver)`. Kept inline redirection function (will obsolete). -- Obsoleted `IsItemHoveredRect()`, `IsMouseHoveringWindow()` in favor of using the newly introduced flags of `IsItemHovered()` and `IsWindowHovered()`. Kept inline redirection function (will obsolete). (#1382) -- Obsoleted 'SetNextWindowPosCenter()' in favor of using 1SetNextWindowPos()` with a pivot value which allows to do the same and more. Keep inline redirection function. -- Removed `IsItemRectHovered()`, `IsWindowRectHovered()` recently introduced in 1.51 which were merely the more consistent/correct names for the above functions which are now obsolete anyway. (#1382) -- Changed `IsWindowHovered()` default parameters behavior to return false if an item is active in another window (e.g. click-dragging item from another window to this window). You can use the newly introduced IsWindowHovered() flags to requests this specific behavior if you need it. (#1382) -- Renamed imconfig.h's `IMGUI_DISABLE_WIN32_DEFAULT_CLIPBOARD_FUNCS`/`IMGUI_DISABLE_WIN32_DEFAULT_IME_FUNCS` to `IMGUI_DISABLE_WIN32_DEFAULT_CLIPBOARD_FUNCTIONS`/`IMGUI_DISABLE_WIN32_DEFAULT_IME_FUNCTIONS` for consistency. -- Renamed ImFont::Glyph to ImFontGlyph. Kept redirection typedef (will obsolete). - -Other Changes: - -- ProgressBar: fixed rendering when straddling rounded area. (#1296) -- SliderFloat, DragFloat: Using scientific notation e.g. "%.1e" in the displayed format string doesn't mistakenly trigger rounding of the value. [@MomentsInGraphics] -- Combo, InputFloat, InputInt: Made the small button on the right side align properly with the equivalent colored button of ColorEdit4(). -- IO: Tweaked logic for `io.WantCaptureMouse` so it now outputs false when e.g. hovering over void while an InputText() is active. (#621) [@pdoane] -- IO: Fixed `io.WantTextInput` from mistakenly outputting true when an activated Drag or Slider was previously turned into an InputText(). (#1317) -- Misc: Added flags to `IsItemHovered()`, `IsWindowHovered()` to access advanced hovering-test behavior. Generally useful for pop-ups and drag and drop behaviors: (relates to ~#439, #1013, #143, #925) - - `ImGuiHoveredFlags_AllowWhenBlockedByPopup` - - `ImGuiHoveredFlags_AllowWhenBlockedByActiveItem` - - `ImGuiHoveredFlags_AllowWhenOverlapped` - - `ImGuiHoveredFlags_RectOnly` -- Input: Added `IsMousePosValid()` helper. -- Input: Added `GetKeyPressedAmount()` to easily measure press count when the repeat rate is faster than the frame rate. -- Input/Focus: Disabled TAB and Shift+TAB when CTRL key is held. -- CheckBox: Now rendering a tick mark instead of a full square. -- ColorEdit4: Added "Copy as..." option in context menu. (#346) -- ColorPicker: Improved ColorPicker hue wheel color interpolation. (#1313) [@thevaber] -- ColorButton: Reduced bordering artifact that would be particularly visible with an opaque Col_FrameBg and FrameRounding enabled. -- ColorButton: Fixed rendering color button with a checkerboard if the transparency comes from the global style.Alpha and not from the actual source color. -- TreeNode: Added `ImGuiTreeNodeFlags_FramePadding` flag to conveniently create a tree node with full padding at the beginning of a line, without having to call `AlignTextToFramePadding()`. -- Trees: Fixed calling `SetNextTreeNodeOpen()` on a collapsed window leaking to the first tree node item of the next frame. -- Layout: Horizontal layout is automatically enforced in a menu bar, so you can use non-MenuItem elements without calling SameLine(). -- Separator: Output a vertical separator when used inside a menu bar (or in general when horizontal layout is active, but that isn't exposed yet!). -- Window: Added `IsWindowAppearing()` helper (helpful e.g. as a condition before initializing some of your own things.). -- Window: Added pivot parameter to `SetNextWindowPos()`, making it possible to center or right align a window. Obsoleted `SetNextWindowPosCenter()`. -- Window: Fixed title bar color of top-most window under a modal window. -- Window: Fixed not being able to move a window by clicking on one of its child window. (#1337, #635) -- Window: Fixed `Begin()` auto-fit calculation code that predict the presence of a scrollbar so it works better when window size constraints are used. -- Window: Fixed calling `Begin()` more than once per frame setting `window_just_activated_by_user` which in turn would set enable the Appearing condition for that frame. -- Window: The implicit "Debug" window now uses a "Debug##Default" identifier instead of "Debug" to allow user creating a window called "Debug" without losing their custom flags. -- Window: Made the `ImGuiWindowFlags_NoMove` flag properly inherited from parent to child. In a setup with ParentWindow (no flag) -> Child (NoMove) -> SubChild (no flag), the user won't be able to move the parent window by clicking on SubChild. (#1381) -- Popups: Pop-ups can be closed with a right-click anywhere, without altering focus under the pop-up. (~#439) -- Popups: `BeginPopupContextItem()`, `BeginPopupContextWindow()` are now setup to allow reopening a context menu by right-clicking again. (~#439) -- Popups: `BeginPopupContextItem()` now supports a NULL string identifier and uses the last item ID if available. -- Popups: Added `OpenPopupOnItemClick()` helper which mimic `BeginPopupContextItem()` but doesn't do the BeginPopup(). -- MenuItem: Only activating on mouse release. [@Urmeli0815] (was already fixed in nav branch). -- MenuItem: Made tick mark thicker (thick mark?). -- MenuItem: Tweaks to be usable inside a menu bar (nb: it looks like a regular menu and thus is misleading, prefer using Button() and regular widgets in menu bar if you need to). (#1387) -- ImDrawList: Fixed a rare draw call merging bug which could lead to undisplayed triangles. (#1172, #1368) -- ImDrawList: Fixed a rare bug in `ChannelsMerge()` when all contents has been clipped, leading to an extraneous draw call being created. (#1172, #1368) -- ImFont: Added `AddGlyph()` building helper for use by custom atlas builders. -- ImFontAtlas: Added support for CustomRect API to submit custom rectangles to be packed into the atlas. You can map them as font glyphs, or use them for custom purposes. - After the atlas is built you can query the position of your rectangles in the texture and then copy your data there. You can use this features to create e.g. full color font-mapped icons. -- ImFontAtlas: Fixed fall-back handling when merging fonts, if a glyph was missing from the second font input it could have used a glyph from the first one. (#1349) [@inolen] -- ImFontAtlas: Fixed memory leak on build failure case when stbtt_InitFont failed (generally due to incorrect or supported font type). (#1391) (@Moka42) -- ImFontConfig: Added `RasterizerMultiply` option to alter the brightness of individual fonts at rasterization time, which may help increasing readability for some. -- ImFontConfig: Added `RasterizerFlags` to pass options to custom rasterizer (e.g. the [imgui_freetype](https://github.com/ocornut/imgui_club/tree/master/imgui_freetype) rasterizer in imgui_club has such options). -- ImVector: added resize() variant with initialization value. -- Misc: Changed the internal name formatting of child windows identifier to use slashes (instead of dots) as separator, more readable. -- Misc: Fixed compilation with `IMGUI_DISABLE_OBSOLETE_FUNCTIONS` defined. -- Misc: Marked all format+va_list functions with format attribute so GCC/Clang can warn about misuses. -- Misc: Fixed compilation on NetBSD due to missing alloca.h (#1319) [@RyuKojiro] -- Misc: Improved warnings compilation for newer versions of Clang. (#1324) (@waywardmonkeys) -- Misc: Added `io.WantMoveMouse flags` (from Nav branch) and honored in Examples applications. Currently unused but trying to spread Examples applications code that supports it. -- Misc: Added `IMGUI_DISABLE_FORMAT_STRING_FUNCTIONS` support in imconfig.h to allow user reimplementing the `ImFormatString()` functions e.g. to use stb_printf(). (#1038) -- Misc: [Windows] Fixed default Win32 `SetClipboardText()` handler leaving the Win32 clipboard handler unclosed on failure. [@pdoane] -- Style: Added `ImGuiStyle::ScaleAllSizes(float)` helper to make it easier to have application transition e.g. from low to high DPI with a matching style. -- Metrics: Draw window bounding boxes when hovering Pos/Size; List all draw layers; Trimming empty commands like Render() does. -- Examples: OpenGL3: Save and restore sampler state. (#1145) [@nlguillemot] -- Examples: OpenGL2, OpenGL3: Save and restore polygon mode. (#1307) [@JJscott] -- Examples: DirectX11: Allow creating device with feature level 10 since we don't really need much for that example. (#1333) -- Examples: DirectX9/10/12: Using the Win32 SetCapture/ReleaseCapture API to read mouse coordinates when they are out of bounds. (#1375) [@Gargaj, @ocornut] -- Tools: Fixed binary_to_compressed_c tool to return 0 when successful. (#1350) [@benvanik] -- Internals: Exposed more helpers and unfinished features in imgui_internal.h. (use at your own risk!). -- Internals: A bunch of internal refactoring, hopefully haven't broken anything! Merged a bunch of internal changes from the upcoming Navigation branch. -- Various tweaks, fixes and documentation changes. - -Beta Navigation Branch: -(Lots of work has been done toward merging the Beta Gamepad/Keyboard Navigation branch (#787) in master.) -(Please note that this branch is always kept up to date with master. If you are using the navigation branch, some of the changes include:) -- Nav: Added `#define IMGUI_HAS_NAV` in imgui.h to ease sharing code between both branches. (#787) -- Nav: MainMenuBar now releases focus when user gets out of the menu layer. (#787) -- Nav: When applying focus to a window with only menus, the menu layer is automatically activated. (#787) -- Nav: Added `ImGuiNavInput_KeyMenu` (~Alt key) aside from ImGuiNavInput_PadMenu input as it is one differentiator of pad vs keyboard that was detrimental to the keyboard experience. Although isn't officially supported, it makes the current experience better. (#787) -- Nav: Move requests now wrap vertically inside Menus and Pop-ups. (#787) -- Nav: Allow to collapse tree nodes with NavLeft and open them with NavRight. (#787, #1079). -- Nav: It's now possible to navigate sibling of a menu-bar while navigating inside one of their child. If a Left<>Right navigation request fails to find a match we forward the request to the root menu. (#787, #126) -- Nav: Fixed `SetItemDefaultFocus` from stealing default focus when we are initializing default focus for a menu bar layer. (#787) -- Nav: Support for fall-back horizontal scrolling with PadLeft/PadRight (nb: fall-back scrolling is only used to navigate windows that have no interactive items). (#787) -- Nav: Fixed tool-tip from being selectable in the window selection list. (#787) -- Nav: `CollapsingHeader(bool*)` variant: fixed for `IsItemHovered()` not working properly in the nav branch. (#600, #787) -- Nav: InputText: Fixed using Up/Down history callback feature when Nav is enabled. (#787) -- Nav: InputTextMultiline: Fixed navigation/selection. Disabled selecting all when activating a multi-line text editor. (#787) -- Nav: More consistently drawing a (thin) navigation rectangle hover filled frames such as tree nodes, collapsing header, menus. (#787) -- Nav: Various internal refactoring. - - ------------------------------------------------------------------------ - VERSION 1.51 (2017-08-24) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.51 - -Breaking Changes: - -Work on dear imgui has been gradually resuming. It means that fixes and new features should be tackled at a faster rate than last year. However, in order to move forward with the library and get rid of some cruft, I have taken the liberty to be a little bit more aggressive than usual with API breaking changes. Read the details below and search for those names in your code! In the grand scheme of things, those changes are small and should not affect everyone, but this is technically our most aggressive release so far in term of API breakage. If you want to be extra forward-facing, you can enable `#define IMGUI_DISABLE_OBSOLETE_FUNCTIONS` in your imconfig.h to disable the obsolete names/redirection. - -- Renamed `IsItemHoveredRect()` to `IsItemRectHovered()`. Kept inline redirection function (will obsolete). -- Renamed `IsMouseHoveringWindow()` to `IsWindowRectHovered()` for consistency. Kept inline redirection function (will obsolete). -- Renamed `IsMouseHoveringAnyWindow()` to `IsAnyWindowHovered()` for consistency. Kept inline redirection function (will obsolete). -- Renamed `ImGuiCol_Columns***` enums to `ImGuiCol_Separator***`. Kept redirection enums (will obsolete). -- Renamed `ImGuiSetCond***` types and enums to `ImGuiCond***`. Kept redirection enums (will obsolete). -- Renamed `GetStyleColName()` to `GetStyleColorName()` for consistency. Unlikely to be used by end-user! -- Added `PushStyleColor(ImGuiCol idx, ImU32 col)` overload, which _might_ cause an "ambiguous call" compilation error if you are using ImColor() with implicit cast. Cast to ImU32 or ImVec4 explicitly to fix. -- Marked the weird `IMGUI_ONCE_UPON_A_FRAME` helper macro as obsolete. Prefer using the more explicit `ImGuiOnceUponAFrame`. -- Changed `ColorEdit4(const char* label, float col[4], bool show_alpha = true)` signature to `ColorEdit4(const char* label, float col[4], ImGuiColorEditFlags flags = 0)`, where flags 0x01 is a safe no-op (hello dodgy backward compatibility!). The new `ColorEdit4`/`ColorPicker4` functions have lots of available flags! Check and run the demo window, under "Color/Picker Widgets", to understand the various new options. -- Changed signature of `ColorButton(ImVec4 col, bool small_height = false, bool outline_border = true)` to `ColorButton(const char* desc_id, ImVec4 col, ImGuiColorEditFlags flags = 0, ImVec2 size = ImVec2(0,0))`. This function was rarely used and was very dodgy (no explicit ID!). -- Changed `BeginPopupContextWindow(bool also_over_items=true, const char* str_id=NULL, int mouse_button=1)` signature to `(const char* str_id=NULL, int mouse_button=1, bool also_over_items=true)`. This is perhaps the most aggressive change in this update, but note that the majority of users relied on default parameters completely, so this will affect only a fraction of users of this already rarely used function. -- Removed `IsPosHoveringAnyWindow()`, which was partly broken and misleading. In the vast majority of cases, people using that function wanted to use `io.WantCaptureMouse` flag. Replaced with IM_ASSERT + comment redirecting user to `io.WantCaptureMouse`. (#1237) -- Removed the old `ValueColor()` helpers, they are equivalent to calling `Text(label)` + `SameLine()` + `ColorButton()`. -- Removed `ColorEditMode()` and `ImGuiColorEditMode` type in favor of `ImGuiColorEditFlags` and parameters to the various Color*() functions. The `SetColorEditOptions()` function allows to initialize default but the user can still change them with right-click context menu. Commenting out your old call to `ColorEditMode()` may just be fine! - -Other Changes: - -- Added flags to `ColorEdit3()`, `ColorEdit4()`. The color edit widget now has a context-menu and access to the color picker. (#346) -- Added flags to `ColorButton()`. (#346) -- Added `ColorPicker3()`, `ColorPicker4()`. The API along with those of the updated `ColorEdit4()` was designed so you may use them in various situation and hopefully compose your own picker if required. There are a bunch of available flags, check the Demo window and comment for `ImGuiColorEditFlags_`. Some of the options it supports are: two color picker types (hue bar + sat/val rectangle, hue wheel + rotating sat/val triangle), display as u8 or float, lifting 0.0..1.0 constraints (currently rgba only), context menus, alpha bar, background checkerboard options, preview tooltip, basic revert. For simple use, calling the existing `ColorEdit4()` function as you did before will be enough, as you can now open the color picker from there. (#346) [@r-lyeh, @nem0, @thennequin, @dariomanesku and @ocornut] -- Added `SetColorEditOptions()` to set default color options (e.g. if you want HSV over RGBA, float over u8, select a default picker mode etc. at startup time without a user intervention. Note that the user can still change options with the context menu unless disabled with `ImGuiColorFlags_NoOptions` or explicitly enforcing a display type/picker mode etc.). -- Added user-facing `IsPopupOpen()` function. (#891) [@mkeeter] -- Added `GetColorU32(u32)` variant that perform the style alpha multiply without a floating-point round trip, and helps makes code more consistent when using ImDrawList APIs. -- Added `PushStyleColor(ImGuiCol idx, ImU32 col)` overload. -- Added `GetStyleColorVec4(ImGuiCol idx)` which is equivalent to accessing `ImGui::GetStyle().Colors[idx]` (aka return the raw style color without alpha alteration). -- ImFontAtlas: Added `GlyphRangesBuilder` helper class, which makes it easier to build custom glyph ranges from your app/game localization data, or add into existing glyph ranges. -- ImFontAtlas: Added `TexGlyphPadding` option. (#1282) [@jadwallis] -- ImFontAtlas: Made it possible to override size of AddFontDefault() (even if it isn't really recommended!). -- ImDrawList: Added `GetClipRectMin()`, `GetClipRectMax()` helpers. -- Fixed Ini saving crash if the ImGuiWindowFlags_NoSavedSettings gets removed from a window after its creation (unlikely!). (#1000) -- Fixed `PushID()`/`PopID()` from marking parent window as Accessed (which needlessly woke up the root "Debug" window when used outside of a regular window). (#747) -- Fixed an assert when calling `CloseCurrentPopup()` twice in a row. [@nem0] -- Window size can be loaded from .ini data even if ImGuiWindowFlags_NoResize flag is set. (#1048, #1056) -- Columns: Added `SetColumnWidth()`. (#913) [@ggtucker] -- Columns: Dragging a column preserve its width by default. (#913) [@ggtucker] -- Columns: Fixed first column appearing wider than others. (#1266) -- Columns: Fixed allocating space on the right-most side with the assumption of a vertical scrollbar. The space is only allocated when needed. (#125, #913, #893, #1138) -- Columns: Fixed the right-most column from registering its content width to the parent window, which led to various issues when using auto-resizing window or e.g. horizontal scrolling. (#519, #125, #913) -- Columns: Refactored some of the columns code internally toward a better API (not yet exposed) + minor optimizations. (#913) [@ggtucker, @ocornut] -- Popups: Most pop-ups windows can be moved by the user after appearing (if they don't have explicit positions provided by caller, or e.g. sub-menu pop-up). The previous restriction was totally arbitrary. (#1252) -- Tooltip: `SetTooltip()` is expanded immediately into a window, honoring current font / styling setting. Add internal mechanism to override tooltips. (#862) -- PlotHistogram: bars are drawn based on zero-line, so negative values are going under. (#828) -- Scrolling: Fixed return values of `GetScrollMaxX()`, `GetScrollMaxY()` when both scrollbars were enabled. Tweak demo to display more data. (#1271) [@degracode] -- Scrolling: Fixes for Vertical Scrollbar not automatically getting enabled if enabled Horizontal Scrollbar straddle the vertical limit. (#1271, #246) -- Scrolling: `SetScrollHere()`, `SetScrollFromPosY()`: Fixed Y scroll aiming when Horizontal Scrollbar is enabled. (#665). -- [Windows] Clipboard: Fixed not closing Win32 clipboard on early open failure path. (#1264) -- Removed an unnecessary dependency on int64_t which failed on some older compilers. -- Demo: Rearranged everything under Widgets in a more consistent way. -- Demo: Columns: Added Horizontal Scrolling demo. Tweaked another Columns demo. (#519, #125, #913) -- Examples: OpenGL: Various makefiles for MINGW, Linux. (#1209, #1229, #1209) [@fr500, @acda] -- Examples: Enabled vsync by default in example applications, so it doesn't confuse people that the sample run at 2000+ fps and waste an entire CPU. (#1213, #1151). -- Various other small fixes, tweaks, comments, optimizations. - - ------------------------------------------------------------------------ - VERSION 1.50 (2017-06-02) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.50 - -Breaking Changes: - -- Added a void* user_data parameter to Clipboard function handlers. (#875) -- SameLine(x) with x>0.0f is now relative to left of column/group if any, and not always to left of window. This was sort of always the intent and hopefully breakage should be minimal. -- Renamed ImDrawList::PathFill() - rarely used directly - to ImDrawList::PathFillConvex() for clarity and consistency. -- Removed ImFontConfig::MergeGlyphCenterV in favor of a more multipurpose ImFontConfig::GlyphOffset. -- Style: style.WindowTitleAlign is now a ImVec2 (ImGuiAlign enum was removed). set to (0.5f,0.5f) for horizontal+vertical centering, (0.0f,0.0f) for upper-left, etc. -- BeginChild(const char*) now applies the stack id to the provided label, consistently with other functions as it should always have been. It shouldn't affect you unless (extremely unlikely) you were appending multiple times to a same child from different locations of the stack id. If that's the case, generate an id with GetId() and use it instead of passing string to BeginChild(). - -Other Changes: - -- InputText(): Added support for CTRL+Backspace (delete word). -- InputText(): OSX uses Super+Arrows for home/end. Add Shortcut+Backspace support. (#650) [@michaelbartnett] -- InputText(): Got rid of individual OSX-specific options in ImGuiIO, added a single io.OSXBehaviors flag. (#473, #650) -- InputText(): Fixed pressing home key on last character when it isn't a trailing \n (#588, #815) -- InputText(): Fixed state corruption/crash bug in stb_textedit.h redo logic when exhausting undo/redo char buffer. (#715. #681) -- InputTextMultiline(): Fixed CTRL+DownArrow moving scrolling out of bounds. -- InputTextMultiline(): Scrollbar fix for when input and latched internal buffers differs in a way that affects vertical scrollbar existence. (#725) -- ImFormatString(): Fixed an overflow handling bug with implementation of vsnprintf() that do not return -1. (#793) -- BeginChild(const char*) now applies stack id to provided label, consistent with other widgets. (#894, #713) -- SameLine() with explicit X position is relative to left of group/columns. (ref #746, #125, #630) -- SliderInt(), SliderFloat() supports reverse direction (where v_min > v_max). (#854) -- SliderInt(), SliderFloat() better support for when v_min==v_max. (#919) -- SliderInt(), SliderFloat() enforces writing back value when interacting, to be consistent with other widgets. (#919) -- SliderInt, SliderFloat(): Fixed edge case where style.GrabMinSize being bigger than slider width can lead to a division by zero. (#919) -- Added IsRectVisible() variation with explicit start-end positions. (#768) [@thedmd] -- Fixed TextUnformatted() clipping bug in the large-text path when horizontal scroll has been applied. (#692, #246) -- Fixed minor text clipping issue in window title when using font straying above usual line. (#699) -- Fixed SetCursorScreenPos() fixed not adjusting CursorMaxPos as well. -- Fixed scrolling offset when using SetScrollY(), SetScrollFromPosY(), SetScrollHere() with menu bar. -- Fixed using IsItemActive() after EndGroup() or any widget using groups. (#840, #479) -- Fixed IsItemActive() lagging by one frame on initial widget activation. (#840) -- Fixed Separator() zero-height bounding box resulting in clipping when laying exactly on top line of clipping rectangle (#860) -- Fixed PlotLines() PlotHistogram() calling with values_count == 0. -- Fixed clicking on a window's void while staying still overzealously marking .ini settings as dirty. (#923) -- Fixed assert triggering when a window has zero rendering but has a callback. (#810) -- Scrollbar: Fixed rendering when sizes are negative to reduce glitches (which can happen with certain style settings and zero WindowMinSize). -- EndGroup(): Made IsItemHovered() work when an item was activated within the group. (#849) -- BulletText(): Fixed stopping to display formatted string after the '##' mark. -- Closing the focused window restore focus to the first active root window in descending z-order .(part of #727) -- Word-wrapping: Fixed a bug where we never wrapped after a 1 character word. [@sronsse] -- Word-wrapping: Fixed TextWrapped() overriding wrap position if one is already set. (#690) -- Word-wrapping: Fixed incorrect testing for negative wrap coordinates, they are perfectly legal. (#706) -- ImGuiListClipper: Fixed automatic-height calc path dumbly having user display element 0 twice. (#661, #716) -- ImGuiListClipper: Fix to behave within column. (#661, #662, #716) -- ImDrawList: Renamed ImDrawList::PathFill() to ImDrawList::PathFillConvex() for clarity. (BREAKING API) -- Columns: End() avoid calling Columns(1) if no columns set is open, not sure why it wasn't the case already (pros: faster, cons: exercise less code). -- ColorButton(): Fix ColorButton showing wrong hex value for alpha. (#1068) [@codecat] -- ColorEdit4(): better preserve inputting value out of 0..255 range, display then clamped in Hexadecimal form. -- Shutdown() clear out some remaining pointers for sanity. (#836) -- Added IMGUI_USE_BGRA_PACKED_COLOR option in imconfig.h (#767, #844) [@thedmd] -- Style: Removed the inconsistent shadow under RenderCollapseTriangle() (~#707) -- Style: Added ButtonTextAlign, ImGuiStyleVar_ButtonTextAlign. (#842) -- ImFont: Allowing to use up to 0xFFFE glyphs in same font (increased from previous 0x8000). -- ImFont: Added GetGlyphRangesThai() helper. [@nProtect] -- ImFont: CalcWordWrapPositionA() fixed font scaling with fallback character. -- ImFont: Calculate and store the approximate texture surface to get an idea of how costly each source font is. -- ImFontConfig: Added GlyphOffset to explicitly offset glyphs at font build time, useful for merged fonts. Removed MergeGlyphCenterV. (BREAKING API) -- Clarified asserts in CheckStacksSize() when there is a stack mismatch. -- Context: Support for #define-ing GImGui and IMGUI_SET_CURRENT_CONTEXT_FUNC to enable custom thread-based hackery (#586) -- Updated stb_truetype.h to 1.14 (added OTF support, removed warnings). (#883, #976) -- Updated stb_rect_pack.h to 0.10 (removed warnings). (#883) -- Added ImGuiMouseCursor_None enum value for convenient usage by app/backends. -- Clipboard: Added a void* user_data parameter to Clipboard function handlers. (#875) (BREAKING API) -- Internals: Refactor internal text alignment options to use ImVec2, removed ImGuiAlign. (#842, #222) -- Internals: Renamed ImLoadFileToMemory to ImFileLoadToMemory to be consistent with ImFileOpen + fix mismatching .h name. (#917) -- OS/Windows: Fixed Windows default clipboard handler leaving its buffer unfreed on application's exit. (#714) -- OS/Windows: No default IME handler when compiling for Windows using GCC. (#738) -- OS/Windows: Now using _wfopen() instead of fopen() to allow passing in paths/filenames with UTF-8 characters. (#917) -- Tools: binary_to_compressed_c: Avoid ?? trigraphs sequences in string outputs which break some older compilers. (#839) -- Demo: Added an extra 3-way columns demo. -- Demo: ShowStyleEditor: show font character map / grid in more details. -- Demo: Console: Fixed a completion bug when multiple candidates are equals and match until the end. -- Demo: Fixed 1-byte off overflow in the ShowStyleEditor() combo usage. (#783) [@bear24rw] -- Examples: Accessing ImVector fields directly, feel less stl-ey. (#810) -- Examples: OpenGL*: Saving/restoring existing scissor rectangle for completeness. (#807) -- Examples: OpenGL*: Saving/restoring active texture number (the value modified by glActiveTexture). (#1087, #1088, #1116) -- Examples: OpenGL*: Saving/restoring separate color/alpha blend functions correctly. (#1120) [@greggman] -- Examples: OpenGL2: Uploading font texture as RGBA32 to increase compatibility with users shaders for beginners. (#824) -- Examples: Vulkan: Countless fixes and improvements. (#785, #804, #910, #1017, #1039, #1041, #1042, #1043, #1080) [@martty, @Loftilus, @ParticlePeter, @SaschaWillems] -- Examples: DirectX9/10/10: Only call SetCursor(NULL) is io.MouseDrawCursor is set. (#585, #909) -- Examples: DirectX9: Explicitly setting viewport to match that other examples are doing. (#937) -- Examples: GLFW+OpenGL3: Fixed Shutdown() calling GL functions with NULL parameters if NewFrame was never called. (#800) -- Examples: GLFW+OpenGL2: Renaming opengl_example/ to opengl2_example/ for clarity. -- Examples: SDL+OpenGL: explicitly setting GL_UNPACK_ROW_LENGTH to reduce issues because SDL changes it. (#752) -- Examples: SDL2: Added build .bat files for Win32. -- Added various links to language/engine bindings. -- Various other minor fixes, tweaks, comments, optimizations. - - ------------------------------------------------------------------------ - VERSION 1.49 (2016-05-09) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.49 - -Breaking Changes: - -- Renamed `SetNextTreeNodeOpened()` to `SetNextTreeNodeOpen()` for consistency, no redirection. -- Removed confusing set of `GetInternalState()`, `GetInternalStateSize()`, `SetInternalState()` functions. Now using `CreateContext()`, `DestroyContext()`, `GetCurrentContext()`, `SetCurrentContext()`. If you were using multiple contexts the change should be obvious and trivial. -- Obsoleted old signature of `CollapsingHeader(const char* label, const char* str_id = NULL, bool display_frame = true, bool default_open = false)`, as extra parameters were badly designed and rarely used. Most uses were using 1 parameter and shouldn't affect you. You can replace the "default_open = true" flag in new API with `CollapsingHeader(label, ImGuiTreeNodeFlags_DefaultOpen)`. -- Changed `ImDrawList::PushClipRect(ImVec4 rect)` to `ImDraw::PushClipRect(ImVec2 min,ImVec2 max,bool intersect_with_current_clip_rect=false)`. Note that higher-level `ImGui::PushClipRect()` is preferable because it will clip at logic/widget level, whereas `ImDrawList::PushClipRect()` only affect your renderer. -- Title bar (using ImGuiCol_TitleBg/ImGuiCol_TitleBgActive colors) isn't rendered over a window background (ImGuiCol_WindowBg color) anymore (see #655). If your TitleBg/TitleBgActive alpha was 1.0f or you are using the default theme it will not affect you. However if your TitleBg/TitleBgActive alpha was <1.0f you need to tweak your custom theme to readjust for the fact that we don't draw a WindowBg background behind the title bar. - This helper function will convert an old TitleBg/TitleBgActive color into a new one with the same visual output, given the OLD color and the OLD WindowBg color. (Or If this is confusing, just pick the RGB value from title bar from an old screenshot and apply this as TitleBg/TitleBgActive. Or you may just create TitleBgActive from a tweaked TitleBg color.) - - ImVec4 ConvertTitleBgCol(const ImVec4& win_bg_col, const ImVec4& title_bg_col) - { - float new_a = 1.0f - ((1.0f - win_bg_col.w) * (1.0f - title_bg_col.w)); - float k = title_bg_col.w / new_a; - return ImVec4((win_bg_col.x * win_bg_col.w + title_bg_col.x) * k, (win_bg_col.y * win_bg_col.w + title_bg_col.y) * k, (win_bg_col.z * win_bg_col.w + title_bg_col.z) * k, new_a); - } - -Other changes: - -- New version of ImGuiListClipper helper calculates item height automatically. See comments and demo code. (#662, #661, #660) -- Added SetNextWindowSizeConstraints() to enable basic min/max and programmatic size constraints on window. Added demo. (#668) -- Added PushClipRect()/PopClipRect() (previously part of imgui_internal.h). Changed ImDrawList::PushClipRect() prototype. (#610) -- Added IsRootWindowOrAnyChildHovered() helper. (#615) -- Added TreeNodeEx() functions. (#581, #600, #190) -- Added ImGuiTreeNodeFlags_Selected flag to display TreeNode as "selected". (#581, #190) -- Added ImGuiTreeNodeFlags_AllowOverlapMode flag. (#600) -- Added ImGuiTreeNodeFlags_NoTreePushOnOpen flag (#590). -- Added ImGuiTreeNodeFlags_NoAutoOpenOnLog flag (previously private). -- Added ImGuiTreeNodeFlags_DefaultOpen flag (previously private). -- Added ImGuiTreeNodeFlags_OpenOnDoubleClick flag. -- Added ImGuiTreeNodeFlags_OpenOnArrow flag. -- Added ImGuiTreeNodeFlags_Leaf flag, always opened, no arrow, for convenience. For simple use case prefer using TreeAdvanceToLabelPos()+Text(). -- Added ImGuiTreeNodeFlags_Bullet flag, to add a bullet to Leaf node or replace Arrow with a bullet. -- Added TreeAdvanceToLabelPos(), GetTreeNodeToLabelSpacing() helpers. (#581, #324) -- Added CreateContext()/DestroyContext()/GetCurrentContext()/SetCurrentContext(). Obsoleted nearly identical GetInternalState()/SetInternalState() functions. (#586, #269) -- Added NewLine() to undo a SameLine() and as a shy reminder that horizontal layout support hasn't been implemented yet. -- Added IsItemClicked() helper. (#581) -- Added CollapsingHeader() variant with close button. (#600) -- Fixed MenuBar missing lower border when borders are enabled. -- InputText(): Fixed clipping of cursor rendering in case it gets out of the box (which can be forced w/ ImGuiInputTextFlags_NoHorizontalScroll. (#601) -- Style: Changed default IndentSpacing from 22 to 21. (#581, #324) -- Style: Fixed TitleBg/TitleBgActive color being rendered above WindowBg color, which was inconsistent and causing visual artifact. (#655) - This broke the meaning of TitleBg and TitleBgActive. Only affect values where Alpha<1.0f. Fixed default theme. Read comments in "API BREAKING CHANGES" section to convert. -- Relative rendering of order of Child windows creation is preserved, to allow more control with overlapping children. (#595) -- Fixed GetWindowContentRegionMax() being off by ScrollbarSize amount when explicit SizeContents is set. -- Indent(), Unindent(): optional non-default indenting width. (#324, #581) -- Bullet(), BulletText(): Slightly bigger. Less polygons. -- ButtonBehavior(): fixed subtle old bug when a repeating button would also return true on mouse release (barely noticeable unless RepeatRate is set to be very slow). (#656) -- BeginMenu(): a menu that becomes disabled while open gets closed down, facilitate user's code. (#126) -- BeginGroup(): fixed using within Columns set. (#630) -- Fixed a lag in reading the currently hovered window when dragging a window. (#635) -- Obsoleted 4 parameters version of CollapsingHeader(). Refactored code into TreeNodeBehavior. (#600, #579) -- Scrollbar: minor fix for top-right rounding of scrollbar background when window has menu bar but no title bar. -- MenuItem(): the check mark renders in disabled color when menu item is disabled. -- Fixed clipping rectangle floating point representation to ensure renderer-side float point operations yield correct results in typical DirectX/GL settings. (#582, 597) -- Fixed GetFrontMostModalRootWindow(), fixing missing fade-out when a combo pop was used stacked over a modal window. (#604) -- ImDrawList: Added AddQuad(), AddQuadFilled() helpers. -- ImDrawList: AddText() refactor, moving some code to ImFont, reserving less unused vertices when large vertical clipping occurs. -- ImFont: Added RenderChar() helper. -- ImFont: Added AddRemapChar() helper. (#609) -- ImFontConfig: Clarified persistence requirement of GlyphRanges array. (#651) -- ImGuiStorage: Added bool helper functions for completeness. -- AddFontFromMemoryCompressedTTF(): Fix ImFontConfig propagation. (#587) -- Renamed majority of use of the word "opened" to "open" for clarity. Renamed SetNextTreeNodeOpened() to SetNextTreeNodeOpen(). (#625, #579) -- Examples: OpenGL3: Saving/restoring glActiveTexture() state. (#602) -- Examples: DirectX9: save/restore all device state. -- Examples: DirectX9: Removed dependency on d3dx9.h, d3dx9.lib, dxguid.lib so it can be used in a DirectXMath.h only environment. (#611) -- Examples: DirectX10/X11: Apply depth-stencil state (no use of depth buffer). (#640, #636) -- Examples: DirectX11/X11: Added comments on removing dependency on D3DCompiler. (#638) -- Examples: SDL: Initialize video+timer subsystem only. -- Examples: Apple/iOS: lowered XCode project deployment target from 10.7 to 10.11. (#598, #575) - - ------------------------------------------------------------------------ - VERSION 1.48 (2016-04-09) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.48 - -Breaking Changes: - -- Consistently honoring exact width passed to PushItemWidth() (when positive), previously it would add extra FramePadding.x*2 over that width. Some hand-tuned layout may be affected slightly. (#346) -- Style: removed `style.WindowFillAlphaDefault` which was confusing and redundant, baked alpha into `ImGuiCol_WindowBg` color. If you had a custom WindowBg color but didn't change WindowFillAlphaDefault, multiply WindowBg alpha component by 0.7. Renamed `ImGuiCol_TooltipBg` to `ImGuiCol_PopupBG`, applies to other types of pop-ups. `bg_alpha` parameter of 5-parameters version of Begin() is an override. (#337) -- InputText(): Added BufTextLen field in ImGuiTextEditCallbackData. Requesting user to update it if the buffer is modified in the callback. Added a temporary length-check assert to minimize panic for the 3 people using the callback. (#541) -- Renamed GetWindowFont() to GetFont(), GetWindowFontSize() to GetFontSize(). Kept inline redirection function (will obsolete). (#340) - -Other Changes: - -- Consistently honoring exact width passed to PushItemWidth(), previously it would add extra FramePadding.x*2 over that width. Some hand-tuned layout may be affected slightly. (#346) -- Fixed clipping of child windows within parent not taking account of child outer clipping boundaries (including scrollbar, etc.). (#506) -- TextUnformatted(): Fixed rare crash bug with large blurb of text (2k+) not finished with a '\n' and fully above the clipping Y line. (#535) -- IO: Added 'KeySuper' field to hold CMD keyboard modifiers for OS X. Updated all examples accordingly. (#473) -- Added ImGuiWindowFlags_ForceVerticalScrollbar, ImGuiWindowFlags_ForceHorizontalScrollbar flags. (#476) -- Added IM_COL32 macros to generate a U32 packed color, convenient for direct use of ImDrawList api. (#346) -- Added GetFontTexUvWhitePixel() helper, convenient for direct use of ImDrawList api. -- Selectable(): Added ImGuiSelectableFlags_AllowDoubleClick flag to allow user reacting on double-click. (@zapolnov) (#516) -- Begin(): made the close button explicitly set the boolean to false instead of toggling it. (#499) -- BeginChild()/EndChild(): fixed incorrect layout to allow widgets submitted after an auto-fitted child window. (#540) -- BeginChild(): Added ImGuiWindowFlags_AlwaysUseWindowPadding flag to ensure non-bordered child window uses window padding. (#462) -- Fixed InputTextMultiLine(), ListBox(), BeginChildFrame(), ProgressBar(): outer frame not honoring bordering. (#462, #503) -- Fixed Image(), ImageButtion() rendering a rectangle 1 px too large on each axis. (#457) -- SetItemAllowOverlap(): Promoted from imgui_internal.h to public imgui.h api. (#517) -- Combo(): Right-most button stays highlighted when pop-up is open. -- Combo(): Display pop-up above if there's isn't enough space below / or select largest side. (#505) -- DragFloat(), SliderFloat(), InputFloat(): fixed cases of erroneously returning true repeatedly after a text input modification (e.g. "0.0" --> "0.000" would keep returning true). (#564) -- DragFloat(): Always apply value when mouse is held/widget active, so that an always-resetting variable (e.g. non saved local) can be passed. -- InputText(): OS X friendly behaviors: Word movement uses ALT key; Shortcuts uses CMD key; Double-clicking text select a single word; Jumping to next word sets cursor to end of current word instead of beginning of current word. (@zhiayang), (#473) -- InputText(): Added BufTextLen in ImGuiTextEditCallbackData. Requesting user to maintain it if buffer is modified. Zero-ing structure properly before use. (#541) -- CheckboxFlags(): Added support for testing/setting multiple flags at the same time. (@DMartinek) (#555) -- TreeNode(), CollapsingHeader() fixed not being able to use "##" sequence in a formatted label. -- ColorEdit4(): Empty label doesn't add InnerSpacing.x, matching behavior of other widgets. (#346) -- ColorEdit4(): Removed unnecessary calls to scanf() when idle in hexadecimal edit mode. -- BeginPopupContextItem(), BeginPopupContextWindow(): added early out optimization. -- CaptureKeyboardFromApp() / CaptureMouseFromApp(): added argument to allow clearing the capture flag. (#533) -- ImDrawList: Fixed index-overflow check broken by AddText() casting current index back to ImDrawIdx. (#514) -- ImDrawList: Fixed incorrect removal of trailing draw command if it is a callback command. -- ImDrawList: Allow windows with only a callback only to be functional. (#524) -- ImDrawList: Fixed ImDrawList::AddRect() which used to render a rectangle 1 px too large on each axis. (#457) -- ImDrawList: Fixed ImDrawList::AddCircle() to fit precisely within bounding box like AddCircleFilled() and AddRectFilled(). (#457) -- ImDrawList: AddCircle(), AddRect() takes optional thickness parameter. -- ImDrawList: Added AddTriangle(). -- ImDrawList: Added PrimQuadUV() helper to ease custom rendering of textured quads (require primitive reserve). -- ImDrawList: Allow AddText(ImFont\* font, float font_size, ...) variant to take NULL/0.0f as default. -- ImFontAtlas: heuristic increase default texture width up for large number of glyphs. (#491) -- ImTextBuffer: Fixed empty() helper which was utterly broken. -- Metrics: allow to inspect individual triangles in draw calls. -- Demo: added more draw primitives in the Custom Rendering example. (#457) -- Demo: extra comments and example for PushItemWidth(-1) patterns. -- Demo: InputText password demo filters out blanks. (#515) -- Demo: Fixed malloc/free mismatch and leak when destructing demo console, if it has been used. (@fungos) (#536) -- Demo: plot code doesn't use ImVector to avoid heap allocation and be more friendly to custom allocator users. (#538) -- Fixed compilation on DragonFly BSD (@mneumann) (#563) -- Examples: Vulkan: Added a Vulkan example (@Loftilus) (#549) -- Examples: DX10, DX11: Saving/restoring most device state so dropping render function in your codebase shouldn't have DX device side-effects. (#570) -- Examples: DX10, DX11: Fixed ImGui_ImplDX??_NewFrame() from recreating device objects if render isn't called (g_pVB not set). -- Examples: OpenGL3: Fix BindVertexArray/BindBuffer order. (@nlguillemot) (#527) -- Examples: OpenGL: skip rendering and calling glViewport() if we have zero-fixed buffer. (#486) -- Examples: SDL2+OpenGL3: Fix context creation options. Made ImGui_ImplSdlGL3_NewFrame() signature match GL2 one. (#468, #463) -- Examples: SDL2+OpenGL2/3: Fix for high-dpi displays. (@nickgravelyn) -- Various extra comments and clarification in the code. -- Various other fixes and optimizations. - - ------------------------------------------------------------------------ - VERSION 1.47 (2015-12-25) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.47 - -Changes: - -- Rebranding "ImGui" -> "dear imgui" as an optional first name to reduce ambiguity with IMGUI term. (#21) -- Added ProgressBar(). (#333) -- InputText(): Added ImGuiInputTextFlags_Password mode: hide display, disable logging/copying to clipboard. (#237, #363, #374) -- Added GetColorU32() helper to retrieve color given enum with global alpha and extra applied. -- Added ImGuiIO::ClearInputCharacters() superfluous helper. -- Fixed ImDrawList draw command merging bug where using PopClipRect() along with PushTextureID()/PopTextureID() functions - would occasionally restore an incorrect clipping rectangle. -- Fixed ImDrawList draw command merging so PushTextureID(XXX)/PopTextureID()/PushTextureID(XXX) sequence are now properly merged. -- Fixed large popups positioning issues when their contents on either axis is larger than DisplaySize, - and WindowPadding < DisplaySafeAreaPadding. -- Fixed border rendering in various situations when using non-pixel aligned glyphs. -- Fixed border rendering of windows to always contain the border within the window. -- Fixed Shutdown() leaking font atlas data if NewFrame() was never called. (#396, #303) -- Fixed int>void\* warnings for 64-bit architectures with fancy warnings enabled. -- Renamed the dubious Color() helpers to ValueColor() - dangerously named, rarely used and probably to be made obsolete. -- InputText(): Fixed and better handling of using keyboard while mouse button if being held and dragging. (#429) -- InputText(): Replace OS IME (Input Method Editor) cursor on top-left when we are not text editing. -- TreeNode(), CollapsingHeader(), Bullet(), BulletText(): various sizing and layout fixes to better support laying out - multiple item with different height on same line. (#414, #282) -- Begin(): Initial window creation with ImGuiWindowFlags_NoBringToFrontOnFocus flag pushes it at the front of global window list. -- BeginPopupContextWindow() and BeginPopupContextVoid() reopen window on subsequent click. (#439) -- ColorEdit4(): Fixed broken tooltip on hovering the color button. (actually fixes #373, #380) -- ImageButton(): uses FrameRounding up to a maximum of available framing size. (#394) -- Columns: Fixed bug with indentation within columns, also making code a bit shorter/faster. (#414, #125) -- Columns: Columns set with no implicit id include the columns count within the id to reduce collisions. (#125) -- Columns: Removed one unnecessary allocation when columns are not used by a window. (#125) -- ImFontAtlas: Tweaked GetGlyphRangesJapanese() so it is easier to modify. -- ImFontAtlas: Updated stb_rect_pack.h to 0.08. -- Metrics: Fixed computing ImDrawCmd bounding box when the draw buffer have been unindexed. -- Demo: Added a simple "Property Editor" demo applet. (#125, #414) -- Demo: Fixed assertion in "Custom Rendering" demo when holding both mouse buttons. (#393) -- Demo: Lots of extra comments, fixes. -- Demo: Tweaks to Style Editor. -- Examples: Not clearing input data/tex data in atlas (will be required for dynamic atlas anyway). -- Examples: Added /Zi (output debug information) to Win32 batch files. -- Examples: Various fixes for resizing window and recreating graphic context. -- Examples: OpenGL2/3: Save/restore viewport as part of default render function. (#392, #441). -- Examples; OpenGL3: Fixed gl3w.c for Linux when compiled with a C++ compiler. (#411) -- Examples: DirectX: Removed assumption about Unicode build in example main.cpp. (#399) -- Examples: DirectX10: Added DirectX10 example. (#424) -- Examples: DirectX11: Downgraded requirement from shader model 5.0 to 4.0. (#420) -- Examples: DirectX11: Removed Debug flag from graphics context. (#415) -- Examples: Added SDL+OpenGL3 example. (#356) - - ------------------------------------------------------------------------ - VERSION 1.46 (2015-10-18) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.46 - -Changes: - -- Begin*(): added ImGuiWindowFlags_NoFocusOnAppearing flag. (#314) -- Begin*(): added ImGuiWindowFlags_NoBringToFrontOnFocus flag. -- Added GetDrawData() alternative to setting a Render function pointer in ImGuiIO structure. -- Added SetClipboardText(), GetClipboardText() helper shortcuts that user code can call directly without reading - from the ImGuiIO structure (to match MemAlloc/MemFree) -- Fixed handling of malformed UTF-8 at the end of a non-zero terminated string range. -- Fixed mouse click detection when passing DeltaTime 0.0. (#338) -- Fixed IsKeyReleased() and IsMouseReleased() returning true on the first frame. -- Fixed using SetNextWindow\* functions on Modal windows with a ImGuiSetCond_Appearing condition. (#377) -- IsMouseHoveringRect(): Added 'bool clip' parameter to disable clipping provided rectangle. (#316) -- InputText(): added ImGuiInputTextFlags_ReadOnly flag. (#211) -- InputText(): lose cursor/undo-stack when reactivating focus is buffer has changed size. -- InputText(): fixed ignoring text inputs when ALT or ALTGR are pressed. (#334) -- InputText(): fixed mouse-dragging not tracking the cursor when text doesn't fit. (#339) -- InputText(): fixed cursor pixel-perfect alignment when horizontally scrolling. -- InputText(): fixed crash when passing a buf_size==0 (which can be of use for read-only selectable text boxes). (#360) -- InputFloat() fixed explicit precision modifier, both display and input were broken. -- PlotHistogram(): improved rendering of histogram with a lot of values. -- Dummy(): creates an item so functions such as IsItemHovered() can be used. -- BeginChildFrame() helper: added the extra_flags parameter. -- Scrollbar: fixed rounding of background + child window consistenly have ChildWindowBg color under ScrollbarBg fill. (#355). -- Scrollbar: background color less translucent in default style so it works better when changing background color. -- Scrollbar: fixed minor rendering offset when borders are enabled. (#365) -- ImDrawList: fixed 1 leak per ImDrawList using the ChannelsSplit() API (via Columns). (#318) -- ImDrawList: fixed rectangle rendering glitches with width/height <= 1/2 and rounding enabled. -- ImDrawList: AddImage() uv parameters default to (0,0) and (1,1). -- ImFontAtlas: Added TexDesiredWidth and tweaked default cheapo best-width choice. (#327) -- ImFontAtlas: Added GetGlyphRangesKorean() helper to retrieve unicode ranges for Korean. (#348) -- ImGuiTextFilter::Draw() helper return bool and build when filter is modified. -- ImGuiTextBuffer: added c_str() helper. -- ColorEdit4(): fixed hovering the color button always showing 1.0 alpha. (#373) -- ColorConvertFloat4ToU32() round the floats instead of truncating them. -- Window: Fixed window lower-right clipping limit so it plays more friendly with both OpenGL and DirectX coordinates. -- Internal: Extracted a EndFrame() function out of Render() but kept it internal/private + clarified some asserts. (#335) -- Internal: Added missing IMGUI_API definitions in imgui_internal.h (#326) -- Internal: ImLoadFileToMemory() return void\* instead of taking void*\* + allow optional int\* file_size. -- Demo: Horizontal scrollbar demo allows to enable simultanaeous scrollbars on both axises. -- Tools: binary_to_compressed_c.cpp: added -nocompress option. -- Examples: Added example for the Marmalade platform. -- Examples: Added batch files to build Windows examples with VS. -- Examples: OpenGL3: Saving/restoring more GL state correctly. (#347) -- Examples: OpenGL2/3: Added msys2/mingw64 target to Makefiles. - - ------------------------------------------------------------------------ - VERSION 1.45 (2015-09-01) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.45 - -Breaking Changes: - -- With the addition of better horizontal scrolling primitives I had to make some consistency fixes. - `GetCursorPos()` `SetCursorPos()` `GetContentRegionMax()` `GetWindowContentRegionMin()` `GetWindowContentRegionMax()` - are now incorporating the scrolling amount. They were incorrectly not incorporating this amount previously. - It PROBABLY shouldn't break anything, but that depends on how you used them. Namely: - - If you always used SetCursorPos() with values relative to GetCursorPos() there shouldn't be a problem. - However if you used absolute coordinates, note that SetCursorPosY(100.0f) will put you at +100 from the initial Y position (which may be scrolled out of the view), NOT at +100 from the window top border. Since there wasn't any official scrolling value on X axis (past just manually moving the cursor) this can only affect you if you used to set absolute coordinates on the Y axis which is hopefully rare/unlikely, and trivial to fix. - - The value of GetWindowContentRegionMax() isn't necessarily close to GetWindowWidth() if horizontally scrolling. - Previously they were roughly interchangeable (roughly because the content region exclude window padding). - -Other Changes: - -- Added Horizontal Scrollbar via ImGuiWindowFlags_HorizontalScroll (#246). -- Added GetScrollX(), GetScrollX(), GetScrollMaxX() apis (#246). -- Added SetNextWindowContentSize(), SetNextWindowContentWidth() to explicitly set the content size of a window, which - define the range of scrollbar. When set explicitly it also define the base value from which widget width are derived. -- Added IO.WantTextInput telling when ImGui is expecting text input, so that e.g. OS on-screen keyboard can be enabled. -- Added printf attribute to printf-like text formatting functions (Clang/GCC). -- Added GetMousePosOnOpeningCurrentPopup() helper. -- Added GetContentRegionAvailWidth() helper. -- Malformed UTF-8 data don't terminate string, output 0xFFFD instead (#307). -- ImDrawList: Added AddBezierCurve(), PathBezierCurveTo() API for cubic bezier curves (#311). -- ImDrawList: Allow to override ImDrawIdx type (#292). -- ImDrawList: Added an assert on overflowing index value (#292). -- ImDrawList: Fixed issues with channels split/merge. Now functional without manually adding a draw cmd. Added comments. -- ImDrawData: Added ScaleClipRects() helper useful when rendering scaled. (#287). -- Fixed Bullet() inconsistent layout behaviour when clipped. -- Fixed IsWindowHovered() not taking account of window hoverability (may be disabled because of a popup). -- Fixed InvisibleButton() not honoring negative size consistently with other widgets that do so. -- Fixed OpenPopup() accessing current window, effectively opening "Debug" when called from an empty window stack. -- TreeNode(): Fixed IsItemHovered() result being inconsistent with interaction visuals (#282). -- TreeNode(): Fixed mouse interaction padding past the node label being accounted for in layout (#282). -- BeginChild(): Passing a ImGuiWindowFlags_NoMove inhibits moving parent window from this child. -- BeginChild() fixed missing rounding for child sizes which leaked into layout and have items misaligned. -- Begin(): Removed default name = "Debug" parameter. We already have a "Debug" window pushed to the stack in the first place so it's not really a useful default. -- Begin(): Minor fixes with windows main clipping rectangle (e.g. child window with border). -- Begin(): Window flags are only read on the first call of the frame. Subsequent calls ignore flags, which allows appending to a window without worryin about flags. -- InputText(): ignore character input when ctrl/alt are held. (Normally those text input are ignored by most wrappers.) (#279). -- Demo: Fixed incorrectly formed string passed to Combo (#298). -- Demo: Added simple Log demo. -- Demo: Added horizontal scrolling example + enabled in console, log and child examples (#246). -- Style: made scrollbars rounded by default. Because nice. Minor menu bar background alpha tweak. (#246) -- Metrics: display indices along with triangles count (#299) and some internal state. -- ImGuiTextFilter::PassFilter() supports string range. Added [] helper to ImGuiTextBuffer. -- ImGuiTextFilter::Draw() default parameter width=0.0f for no override, allow override with negative values. -- Examples: OpenGL2/OpenGL3: fix for retina displays. Default font current lack crispness. -- Examples: OpenGL2/OpenGL3: save/restore more GL state correctly. -- Examples: DirectX9/DirectX11: resizing buffers dynamically (#299). -- Examples: DirectX9/DirectX11: added missing middle mouse button to Windows event handler. -- Examples: DirectX11: fix for Visual Studio 2015 presumably shipping with an updated version of DX11. -- Examples: iOS: fixed missing files in project. - - ------------------------------------------------------------------------ - VERSION 1.44 (2015-08-08) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.44 - -Breaking Changes: - -- imgui.cpp has been split intro extra files: imgui_demo.cpp, imgui_draw.cpp, imgui_internal.h. - Add the two extra .cpp to your project or #include them from another .cpp file. (#219) - -Other Changes: - -- Internal data structure and several useful functions are now exposed in imgui_internal.h. This should make it easier - and more natural to extend ImGui. However please note that none of the content in imgui_internal.h is guaranteed - for forward-compatibility and code using those types/functions may occasionally break. (#219) -- All sample code is in imgui_demo.cpp. Please keep this file in your project and consider allowing your code to call - the ShowTestWindow() function as de-facto guide to ImGui features. It will be stripped out by the linker when unused. -- Added GetContentRegionAvail() helper (basically GetContentRegionMax() - GetCursorPos()). -- Added ImGuiWindowFlags_NoInputs for totally input-passthru window. -- Button(): honor negative size consistently with other widgets that do so (width -100 to align the button 100 pixels - before the right-most position of the contents region). -- InputTextMultiline(): honor negative size consistently with other widgets that do so. -- Combo() clamp popup to lower edge of visible area. -- InputInt(): value doesn't pass through an int>float>int casting chain, fix handling lost of precision with "large" integer. -- InputInt() allow hexadecimal input (awkwardly via ImGuiInputTextFlags_CharsHexadecimal but we will allow format - string in InputInt* later). -- Checkbox(), RadioButton(): fixed scaling of checkbox and radio button for the filling of "active" visual. -- Columns: never assume horizontal space for scrollbar if NoScrollbar flag is explicitly set. -- Slider: fixed using FramePadding between frame and grab visual. Scaling that spacing would look odd. -- Fixed lower-right resize grip hit box not scaling along with its rendered size (#287) -- ImDrawList: Fixed angles in ImDrawList::PathArcTo(), PathArcToFast() (v1.43) being off by an extra PI for no reason. -- ImDrawList: Added ImDrawList::AddText() shorthand helper. -- ImDrawList: Add missing support for anti-aliased thick-lines (#133, also ref #288) -- ImFontAtlas: Added AddFontFromMemoryCompressedBase85TTF() to load base85 encoded font string. Default font encoded - as base85 saves ~100 lines / 26 KB of source code. Added base85 output to the binary_to_compressed_c tool. -- Build fix for MinGW (#276). -- Examples: OpenGL3: Fixed running on script core profiles for OSX (#277). -- Examples: OpenGL3: Simplified code using glBufferData for vertices as well (#277, #278) -- Examples: DirectX11: Clear font texture view to ensure Release() doesn't get called twice (#290). -- Updated to stb_truetype 1.07 (back to vanilla version as our minor changes are now in master & fix unlikely assert - with odd fonts (#280) - - ------------------------------------------------------------------------ - VERSION 1.43 (2015-07-17) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.43 - -Breaking Changes: - -- This is a rather important release and we unfortunately had to break the rendering API. - ImGui now requires you to render indexed vertices instead of non-indexed ones. The fix should be very easy. - Sorry for that! This change is saving a fair amount of CPU/GPU and enables us to get anti-aliasing for a marginal cost. - Each ImDrawList now contains both a vertex buffer and an index buffer. For each command, render ElemCount/3 triangles - using indices from the index buffer. -- If you are using a vanilla copy of one of the imgui_impl_XXXX.cpp provided in the example, you just need to update - your copy and you can ignore the rest. -- The signature of the io.RenderDrawListsFn handler has changed - From: ImGui_XXXX_RenderDrawLists(ImDrawList** const cmd_lists, int cmd_lists_count) - To: ImGui_XXXX_RenderDrawLists(ImDrawData* draw_data) - With: argument 'cmd_lists' -> 'draw_data->CmdLists' - argument 'cmd_lists_count' -> 'draw_data->CmdListsCount' - ImDrawList 'commands' -> 'CmdBuffer' - ImDrawList 'vtx_buffer' -> 'VtxBuffer' - ImDrawList n/a -> 'IdxBuffer' (new) - ImDrawCmd 'vtx_count' -> 'ElemCount' - ImDrawCmd 'clip_rect' -> 'ClipRect' - ImDrawCmd 'user_callback' -> 'UserCallback' - ImDrawCmd 'texture_id' -> 'TextureId' -- If you REALLY cannot render indexed primitives, you can call the draw_data->DeIndexAllBuffers() method to de-index - the buffers. This is slow and a waste of CPU/GPU. Prefer using indexed rendering! - Refer to code in the examples/ folder or ask on the GitHub if you are unsure of how to upgrade. Please upgrade! - -Other Changes: - -- Added anti-aliasing on lines and shapes based on primitives by @MikkoMononen (#133). - Between the use of indexed-rendering and the fact that the entire rendering codebase has been optimized and massaged - enough, with anti-aliasing enabled ImGui 1.43 is now running FASTER than 1.41. - Made some extra effort in making the code run faster in your typical Debug build. -- Anti-aliasing can be disabled in the ImGuiStyle structure via the AntiAliasedLines/AntiAliasedShapes fields for further gains. -- ImDrawList: Added AddPolyline(), AddConvexPolyFilled() with optional anti-aliasing. -- ImDrawList: Added stateful path building and stroking API. PathLineTo(), PathArcTo(), PathRect(), PathFill(), PathStroke() - with optional anti-aliasing. -- ImDrawList: Added AddRectFilledMultiColor() helper. -- ImDrawList: Added multi-channel rendering so out of order elements can be rendered in separate channels and then merged - back together (used by columns). -- ImDrawList: Fixed merging draw commands when equal clip rectangles are in the two first commands. -- ImDrawList: Fixed window draw lists not destructed properly on Shutdown(). -- ImDrawData: Added DeIndexAllBuffers() helper. -- Added lots of new font options ImFontAtlas::AddFont() and the new ImFontConfig structure. - - Added support for oversampling (ImFontConfig: OversampleH, OversampleV) and sub-pixel positioning (ImFontConfig: PixelSnapH). - Oversampling allows sub-pixel positioning but can also be used as a way to get some leeway with scaling fonts without re-rasterizing. - - Added GlyphExtraSpacing option to add extra horizontal spacing between characters (#242). - - Added MergeMode option to merge glyphs from different font inputs into a same font (#182, #232). - - Added FontDataOwnedByAtlas option to keep ownership from the TTF data buffer and request the atlas to make a copy (#220). -- Updated to stb_truetype 1.06 (+ minor mods) with better font rasterization. -- InputText: Added ImGuiInputTextFlags_NoHorizontalScroll flag. -- InputText: Added ImGuiInputTextFlags_AlwaysInsertMode flag. -- InputText: Added HasSelection() helper in ImGuiTextEditCallbackData as a clarification. -- InputText: Fix for using END key on a multi-line text editor (#275) -- Columns: Dispatch render of each column in a sub-draw list and merge on closure, saving a lot of draw calls! (#125) -- Popups: Fixed Combo boxes inside menus. (#272) -- Style: Added GrabRounding setting to make the sliders etc. grabs rounded. -- Changed SameLine() parameters from int to float. -- Fixed incorrect assert triggering when code stole ActiveID from user moving a window by calling e.g. SetKeyboardFocusHere(). -- Fixed CollapsingHeader() label rendering outside its frame in columns context where ClipRect max isn't aligned with the - right-side of the header. -- Metrics window: calculate bounding box of actual vertices when hovering a draw list. -- Examples: Showing more information in the Fonts section. -- Examples: Added a gratuitous About window. -- Examples: Updated all examples code (OpenGL/DX9/DX11/SDL/Allegro/iOS) to use indexed rendering. -- Examples: Fixed the SDL2 example to support Unicode text input (#274). - - ------------------------------------------------------------------------ - VERSION 1.42 (2015-07-08) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.42 - -Breaking Changes: - -- Renamed SetScrollPosHere() to SetScrollHere(). Kept inline redirection function (will obsolete). -- Renamed GetScrollPosY() to GetScrollY(). Necessary to reduce confusion and make scrolling API consistent, - because positions (e.g. cursor position) are not equivalent to scrolling amount. -- Removed obsolete GetDefaultFontData() function that would assert anyway. - If you are updating from <1.30 you'll get a compile error instead of an assertion. (obsoleted 2015/01/11) - -Other Changes: - -- Added SDL2 example application (courtesy of @CedricGuillemet) -- Added iOS example application (courtesy of @joeld42) -- Added Allegro 5 example application (courtesy of @bggd) -- Added TitleBgActive color in style so focused window is made visible. (#253) -- Added CaptureKeyboardFromApp() / CaptureMouseFromApp() to manually enforce inputs capturing. -- Added DragFloatRange2() DragIntRange2() helpers. (#76) -- Added a Y centering ratio to SetScrollFromCursorPos() which can be used to aim the top or bottom of the window. (#150) -- Added SetScrollY(), SetScrollFromPos(), GetCursorStartPos() for manual scrolling manipulations. (#150). -- Added GetKeyIndex() helper for converting from ImGuiKey_\* enum to user's keycodes. Basically pulls from io.KeysMap[]. -- Added missing ImGuiKey_PageUp, ImGuiKey_PageDown so more UI code can be written without referring to implementation-side keycodes. -- MenuItem() can be activated on release. (#245) -- Allowing NewFrame() with DeltaTime==0.0f to not assert. -- Fixed IsMouseDragging(). (#260) -- Fixed PlotLines(), PlotHistogram() using incorrect hovering test so they would show their tooltip even when there is - a popup between mouse and the graph. -- Fixed window padding being reported incorrectly for child windows with borders when parent have no borders. -- Fixed a bug with TextUnformatted() clipping of long text blob when clipping y1 line sits on the first line of text. (#257) -- Fixed text baseline alignment of small button (no padding) after regular buttons. -- Fixed ListBoxHeader() not honoring negative sizes the same way as BeginChild() or BeginChildFrame(). (#263) -- Fixed warnings for more pedantic compiler settings (#258). -- ImVector<> cannot be re-defined anymore, cannot be replaced with std::vector<>. Allowed us to clean up and optimize - lots of code. Yeah! (#262) -- ImDrawList: store pointer to their owner name for easier auditing/debugging. -- Examples: added scroll tracking example with SetScrollFromCursorPos(). -- Examples: metrics windows render clip rectangle when hovering over a draw call. -- Lots of small optimization (particularly to run faster on unoptimized builds) and tidying up. -- Added font links in extra_fonts/ + instructions for using compressed fonts in C array. - - ------------------------------------------------------------------------ - VERSION 1.41 (2015-06-26) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.41 - -Breaking Changes: - -- Changed ImageButton() default bg_col parameter from (0,0,0,1) (black) to (0,0,0,0) (transparent). - Only makes a difference when texture have transparency. -- Changed Selectable() API from (label, selected, size) to (label, selected, flags, size). - Size override should be used very rarely so hopefully it doesn't affect many people. Sorry! - -Other Changes: - -- Added InputTextMultiline() multi-line text editor, vertical scrolling, selection, optimized enough to handle rather - big chunks of text in stateless context (thousands of lines are ok), option for allowing Tab to be input, option - for validating with Return or Ctrl+Return (#200). -- Added modal window API, BeginPopupModal(), follows the popup api scheme. Modal windows can be closed by clicking - outside. By default the rest of the screen is dimmed (using ImGuiCol_ModalWindowDarkening). Modal windows can be stacked. -- Added GetGlyphRangesCyrillic() helper (#237). -- Added SetNextWindowPosCenter() to center a window prior to knowing its size. (#249) -- Added IsWindowHovered() helper. -- Added IsMouseReleased(), IsKeyReleased() helpers to allow to user to avoid tracking them. (#248) -- Allow Set*WindowSize() calls to be used with popups. -- Window: AutoFit can be triggered on each axis separately via SetNextWindowSize(), etc. -- Window: fixed scrolling with mouse wheel while window was collapsed. -- Window: fixed mouse wheel scroll issues. -- DragFloat(), SliderFloat(): Fixed rounding of negative numbers which sometime made the negative lower bound unreachable. -- InputText(): lifted character count limit. -- InputText(): fixes in case of using per-window font scaling. -- Selectable(), MenuItem(): do not use frame rounding for hovering/selection. -- Selectable(): Added flag ImGuiSelectableFlags_DontClosePopups. -- Selectable(): Added flag ImGuiSelectableFlags_SpanAllColumns (#125). -- Combo(): Fixed issue with activating a Combo() not taking active id (#241). -- ColorButton(), ColorEdit4(): fix to ensure that the colored square stays square when non-default padding settings are used. -- BeginChildFrame(): returns bool like BeginChild() for clipping. -- SetScrollPosHere(): takes account of item height + more accurate centering + fixed precision issue. -- ImFont: ignoring '\r'. -- ImFont: added GetCharAdvance() helper. Exposed font Ascent and font Descent. -- ImFont: additional rendering optimizations. -- Metrics windows display storage size. - - ------------------------------------------------------------------------ - VERSION 1.40 (2015-05-31) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.40 - -Breaking Changes: - -- The BeginPopup() API (introduced in 1.37) had to be changed to allow for stacked popups and menus. - Use OpenPopup() to toggle the opened state and BeginPopup() to append.** -- The third parameter of Button(), 'repeat_if_held' has been removed. While it's been very rarely used, - some code will possibly break if you didn't rely on the default parameter. - Use PushButtonRepeat()/PopButtonRepeat() to configure repeat. -- Renamed IsRectClipped() to !IsRectVisible() for consistency (opposite return value!). Kept inline redirection function (will obsolete) -- Renamed GetWindowCollapsed() to IsWindowCollapsed() for consistency. Kept inline indirection function (will obsolete). - -Other Changes: - -- Menus: Added a menu system! Menus are typically populated with menu items and sub-menus, but you can add any sort of - widgets in them (buttons, text inputs, sliders, etc.). (#126) -- Menus: Added MenuItem() to append a menu item. Optional shortcut display, acts a button & toggle with checked/unchecked state, - disabled mode. Menu items can be used in any window. -- Menus: Added BeginMenu() to append a sub-menu. Note that you generally want to add sub-menu inside a popup or a menu-bar. - They will work inside a normal window but it will be a bit unusual. -- Menus: Added BeginMenuBar() to append to window menu-bar (set ImGuiWindowFlags_MenuBar to enable). -- Menus: Added BeginMainMenuBar() helper to append to a fullscreen main menu-bar. -- Popups: Support for stacked popups. Each popup level inhibit inputs to lower levels. The menus system is based on this. (#126). -- Popups: Added BeginPopupContextItem(), BeginPopupContextWindow(), BeginPopupContextVoid() to create a popup window on mouse-click. -- Popups: Popups have borders by default (#197), attenuated border alpha in default theme. -- Popups & Tooltip: Fit within display. Handling various positioning/sizing/scrolling edge cases. Better hysteresis when moving - in corners. Tooltip always tries to stay away from mouse-cursor. -- Added ImGuiStorage::GetVoidPtrRef() for manipulating stored void*. -- Added IsKeyDown() IsMouseDown() as convenience and for consistency with existing functions (instead of reading them from IO structures). -- Added Dummy() helper to advance layout by a given size. Unlike InvisibleButton() this doesn't catch any click. -- Added configurable io.KeyRepeatDelay, io.KeyRepeatRate keyboard and mouse repeat rate. -- Added PushButtonRepeat() / PopButtonRepeat() to enable hold-button-to-repeat press on any button. -- Removed the third 'repeat' parameter of Button(). -- Added IsAnyItemHovered() helper. -- Added GetItemsLineHeightWithSpacing() helper. -- Added ImGuiListClipper helper for clipping large list of evenly sized items, to avoid using CalcListClipping() directly. -- Separator: within group start on group horizontal offset. (#205) -- InputText: Fixed incorrect edit state after text buffer is appended to by user via the callback. (#206) -- InputText: CTRL+letter-key shortcuts (e.g. CTRL+C/V/X) makes sure only CTRL is pressed. (#214) -- InputText: Fixed cursor generating a zero-width wire-frame rectangle turning into a division by zero (would go unnoticed - unless you trapped exceptions). -- InputFloatN/InputIntN: Flags parameter added to match scalar versions. (#218) -- Selectable: Horizontal filling not declared to ItemSize() so Selectable(),SameLine() works and we can better auto-fit the window. -- Selectable: Handling text baseline alignment for line that aren't of text height. -- Combo: Empty label doesn't add ItemInnerSpacing alignment, matching other widgets. -- EndGroup: Carries the text base offset from the last line of the group (sort of incorrect but better than nothing, - should use the first line of the group, will implement in the future). -- Columns: distinguish columns-set ID from other widgets as a convenience, added asserts and sailors. -- ListBox: ListBox() function only use public API to encourage creating custom versions. ListBoxHeader() can return false. -- ListBox: Uses ImGuiListClipper and assume items of matching height, so large lists can be handled. -- Plot: overlay label clipped within frame when not fitting. -- Window: Added ImGuiSetCond_Appearing to test the hidden->visible transition in SetWindow***/SetNextWindow*** functions. -- Window: Auto-fitting cancel out one worth of vertical spacing for vertical symmetry (like what group and tooltip do). -- Window: Default item width for auto-resizing windows expressed as a factor of font height, scales better with different font. -- Window: Fixed auto-fit calculation mismatch of whether a scrollbar will be added by maximum height clamping. Also honor NoScrollBar in the case of height clamping, not adding extra horizontal space. -- Window: Hovering require to hover same child window. Reverted 860cf57 (December 3). Might break something if you have - child overlapping items in parent window. -- Window: Fixed appending multiple times to an existing child via multiple BeginChild/EndChild calls to same child name. - Allows a simple form of out-of-order appending. -- Window: Fixed auto-filling child window using WindowMinSize at their minimum size, irrelevant. -- Metrics: Added io.MetricsActiveWindows counter. (#213. -- Metrics: Added io.MetricsAllocs counter (number of active memory allocations). -- Metrics: ShowMetricsWindow() shows popups stack, allocations. -- Style: Added style.DisplayWindowPadding to prevent windows from reaching edges of display (similar to style.DisplaySafeAreaPadding which is still in effect and also affect popups/tooltips). -- Style: Removed style.AutoFitPadding, using style.WindowPadding makes more sense (the default values were already the same). -- Style: Added style.ScrollbarRounding. (#212) -- Style: Added ImGuiCol_TextDisabled for disabled text. Added TextDisabled() helper. -- Style: Added style.WindowTitleAlign alignment options, to e.g. center title on windows. (#222) -- ImVector: tweak growth strategy, matches vector from VS2010. -- ImFontAtlas: Added ClearFonts(), making the different clear funcs more explicit. (#224) -- ImFontAtlas: Fixed appending new fonts without clearing existing fonts. Clearing input data left to application. (#224) -- ImDrawList: Merge draw command better, cases of multiple Begin/End gets merged properly. -- Store common stacked settings contiguously in memory to avoid heap allocation for unused features, and reduce cache misses. -- Shutdown() tests for g.IO.Fonts not being NULL to ease use of multiple ImGui contexts. (#207) -- Added IMGUI_DISABLE_OBSOLETE_FUNCTIONS define to disable the functions that are meant to be removed. -- Examples: Added ? marks with tooltips next to various widgets. Added more comments in the demo window. -- Examples: Added Menu-bar example. -- Examples: Added Simple Layout example. -- Examples: AutoResize demo doesn't use TextWrapped(). -- Examples: Console example uses standard malloc/free, makes more sense as a copy & pastable example. -- Examples: DirectX9/11: Fixed key mapping for down arrow. -- Examples: DirectX9/11: hide OS cursor if ImGui is drawing it. (#155) -- Examples: DirectX11: explicitly set rasterizer state. -- Examples: OpenGL3: Add conditional compilation of forward compat as required by glfw on OSX. (#229) -- Fixed build with Visual Studio 2008 (possibly earlier versions as well). -- Other fixes, comments, tweaks. - - ------------------------------------------------------------------------ - VERSION 1.38 (2015-04-20) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.38 - -Breaking Changes: - -- Renamed IsClipped() to IsRectClipped(). Kept inline redirection function (will obsolete). -- Renamed ImDrawList::AddArc() to ImDrawList::AddArcFast(). - -Other Changes: - -- Added DragFloat(), DragInt() widget, click and drag to adjust value with given step. - Hold SHIFT/ALT to speed-up/slow-down. Double-click or CTRL+click to input text. - Passing min >= max makes the widget unbounded. -- Added DragFloat2(), DragFloat3(), DragFloat4(), DragInt2(), DragInt3(), DragInt4() helper variants. -- Added ShowMetricsWindow() which is mainly useful to debug ImGui internals. Added IO.MetricsRenderVertices counter. -- Added ResetMouseDragDelta() for iterative dragging operations. -- Added ImFontAtlas::AddFontFromCompressedTTF() helper + binary_to_compressed_c.cpp tool to compress a file and create a .c array from it. -- Added PushId() GetId() variants that takes string range to avoid user making unnecessary copies. -- Added IsItemVisible(). -- Fixed IsRectClipped() incorrectly returning false when log is enabled. -- Slider: visual fix in the unlikely that style.GrabMinSize is larger than a slider. -- SliderFloat: removed support for unbound slider (using FLT_MAX), caused various inconsistency. Use InputFloat()/DragFloat(). -- ColorEdit4: hide components prefix if there's no space for them. -- Combo: adding frame padding inside the combo box. -- Columns: mouse dragging uses absolute mouse coordinates.Fixed dragging left-most column of an auto-resizable window. #125 -- Selectable: render highlight into AutoFitPadding region but do not extend it, fixing visual gap. -- Focus: Allow SetWindowFocus(NULL) to remove focus. -- Focus: Clicking on void (outside an ImGui windows) loses keyboard-focus so application can use TAB. -- Popup: Fixed hovering over a popup's child (popups disable hovering on other windows but not their childs) #197 -- Fixed active widget not releasing its active state while being clipped. -- Fixed user-facing version of IsItemHovered() ignoring overlapping windows. -- Fixed label vertical alignment for InputInt2(), InputInt3(), InputInt4(). -- Fixed new collapsed auto-resizing window with saved .ini settings not calculating their initial width #176 -- Fixed Begin() returning true on collapsed windows that had loaded settings #176 -- Fixed style.DisplaySafeAreaPadding handling from being applied on window prior to them auto-fitting. -- ShowTestWindow(): added examples for DragFloat, DragInt and only custom label embedded in format strings. -- ShowTestWindow(): fixed "manipulating titles" example not doing the right thing, broken in ff35d24 -- Examples: OpenGL/GLFW: Fixed modifier key state setting in GLFW callbacks. -- Examples: OpenGL/GLFW: Added glBindTexture(0) in OpenGL fixed pipeline examples. Save restore current program and texture in the OpenGL3 example. -- Examples: DirectX11: Removed unnecessary vertices conversion and CUSTOMVERTEX types. -- Comments, fixes, tweaks. - - ------------------------------------------------------------------------ - VERSION 1.37 (2015-03-26) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.37 - -Other Changes: - -- Added a more convenient three parameters version of Begin() which covers the common uses better. -- Added mouse cursor types handling (resize, move, text input cursors, etc.) that user can query with GetMouseCursor(). Added demo and instructions in ShowTestWindow(). -- Added embedded mouse cursor data for MouseDrawCursor software cursor rendering, for consoles/tablets/etc. (#155). -- Added first version of BeginPopup/EndPopup() helper API to create popup menus. Popups automatically lock their position to the mouse cursor when first appearing. They close automatically when clicking outside, and inhibit hovering items from other windows when active (to allow for clicking outside). (#126) -- Added thickness parameter to ImDrawList::AddLine(). -- Added ImDrawList::PushClipRectFullScreen() helper. -- Added style.DisplaySafeAreaPadding which was previously hard-coded (useful if you can't see the edges of your display, e.g. TV screens). -- Added CalcItemRectClosestPoint() helper. -- Added GetMouseDragDelta(), IsMouseDragging() helpers, given a mouse button and an optional "unlock" threshold. Added io.MouseDragThreshold setting. (#167) -- IsItemHovered() return false if another widget is active, aka we can't use what we are hovering now. -- Added IsItemHoveredRect() if old behavior of IsItemHovered() is needed (e.g. for implementing the drop side of a drag'n drop operation). -- IsItemhovered() include space taken by label and behave consistently for all widgets (#145) -- Auto-filling child window feed their content size to parent (#170) -- InputText() removed the odd ~ characters when clipping. -- InputText() update its width in case of resize initiated programmatically while the widget is active. -- InputText() last active preserve scrolling position. Reset scroll if widget size becomes bigger than contents. -- Selectable(): not specifying a width defaults to using max of label width and remaining width. -- Selectable(const char*, bool) version has bool defaulting to false. -- Selectable(): fixed misusage of GetContentRegionMax().x leaking into auto-fitting. -- Windows starting Collapsed runs initial auto-fit to retrieve a width for their title bar (#175) -- Fixed new window from having an incorrect content size on their first frame, if queried by user. Fixed SetWindowPos/SetNextWindowPos having a side-effect size computation (#175) -- InputFloat(): fixed label alignment if total widget width forcefully bigger than space available. -- Auto contents size aware of enforced vertical scrollbar if window is larger than display size. -- Fixed new windows auto-fitting bigger than their .ini saved size. This was a bug but it may be a desirable effect sometimes, may reconsider it. -- Fixed negative clipping rectangle when collapsing windows that could affect manual submission to ImDrawList and end-user rendering function if unhandled (#177) -- Fixed bounding measurement of empty groups (fix #162) -- Fixed assignment order in Begin() making auto-fit size effectively lag by one frame. Also disabling "clamp into view" while windows are auto-fitting so that auto-fitting window in corners don't get pushed away. -- Fixed MouseClickedPos not updated on double-click update (#167) -- Fixed MouseDrawCursor feature submitting an empty trailing command in the draw list. Fixed unmerged draw calls for software mouse cursor. -- Fixed double-clicking on resize grip keeping the grip active if mouse button is kept held. -- Bounding box tests exclude higher bound, so touching items (zero spacing) don't report double hover when cursor is on edge. -- Setting io.LogFilename to NULL disable default LogToFile() (part of #175) -- Tweak stb_textedit integration to be lenient if another piece of code are leaking their STB_TEXTEDIT definitions/symbols. -- Shutdown() freeing a few extra vectors so they don't have to freed by destruction (#169) -- Examples: OpenGL2/3 examples automatically hide the OS mouse cursor if software cursor rendering is used. -- ShowTestWindow: Added Widgets Alignment demo under Layout section -- ShowTestWindow: Added simple dragging widget example. -- ShowTestWindow: Graph has checkbox under the label, also demo using BeginGroup/EndGroup(). -- ShowTestWindow: Using SetNextWindowSize() in examples to encourage its use. -- Fixes, tweaks, comments. - - ------------------------------------------------------------------------ - VERSION 1.36 (2015-03-18) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.36 - -Other Changes: - -- Added ImGui::GetVersion(), IMGUI_VERSION (#127) -- Added BeginGroup()/EndGroup() layout tools (#160). -- Added Indent() / Unindent(). -- Added InputInt2(), InputInt3(), InputInt4() for completeness. -- Added GetItemRectSize(). -- Added VSliderFloat(), VSliderInt(), vertical sliders. -- Added IsRootWindowFocused(), IsRootWindowOrAnyChildFocused(). -- Added io.KeyAlt + support in examples apps, in prevision for future usage of Alt modifier (was missing). -- Added ImGuiStyleVar_GrabMinSize enum value for PushStyleVar(). -- Various fixes related to vertical alignment of text after widget of varied sizes. Allow for multiple blocks of multiple lines text on the same "line". Added demos. -- Explicit size passed to Plot*(), Button() includes the frame padding. -- Style: Changed default Border and Column border colors to be most subtle. -- Renamed style.TreeNodeSpacing to style.IndentSpacing, ImGuiStyleVar_TreeNodeSpacing to ImGuiStyleVar_IndentSpacing. -- Renamed GetWindowIsFocused() to IsWindowFocused(), kept inline redirection with old name (will obsolete). -- Renamed GetItemRectMin()/GetItemRectMax() to GetItemRectMin()/GetItemRectMax(), kept inline redirection with old name (will obsolete). -- Sliders: Fast-path when power=1.0f, also makes code easier to read. -- Sliders: Fixed parsing of decimal precision back from format string when using %%. -- Sliders: Fixed hovering bounding test excluding padding between outer frame and grab (there was a few pixels dead-zone). -- Separator() logs itself as text when passing through text log. -- Optimisation: TreeNodeV() early out if SkipItems is set without formatting. -- Moved various static buffers into state. Increase the formatted string buffer from 1K to 3K. -- Examples: Example console keeps focus on input box at all times. -- Examples: Updated to GLFW 3.1. Moved to examples/libs/ folder. -- Examples: Added 64-bit projects for MSVC. -- Examples: Increase warning level from /W3 to /W4 for MSVC. -- Examples: DirectX9: fixed duplicate creation of vertex buffer. -- Renamed internal type ImGuiAabb to ImRect. Changed mentions of 'box' or 'aabb' to say 'rect'. -- Tweaks, minor fixes and comments. - - ------------------------------------------------------------------------ - VERSION 1.35 (2015-03-09) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.35 - -Other Changes: - -- Examples: refactored all examples application to make it easier to isolate and grab the code you need for OpenGL 2/3, DirectX 9/11, and toward a more sensible format for samples. -- Scrollbar grab have a minimum size (style.GrabSizeMin), always visible even with huge scroll amount. (#150). -- Scrollbar: Clicking inside the grab box doesn't modify scroll value. Subsequent movement always relative. -- Added "###" labelling syntax to pass a label that isn't part of the hashed ID (#107), e.g. ("%d###static_id",rand()). -- Added GetColumnIndex(), GetColumnsCount() (#154) -- Added GetScrollPosY(), GetScrollMaxY(). -- Fixed the Chinese/Japanese glyph ranges; include missing punctuations (#156) -- Fixed Combo() and ListBox() labels not included in declared size, for use with SameLine(), etc. (fix #149, #151). -- Fixed ListBoxHeader() incorrect handling of SkipItems early out when window is collapsed. -- Fixed using IsItemHovered() after EndChild() (#151) -- Fixed malformed UTF-8 decoding errors leading to infinite loops (#158) -- InputText() handles buffer limit correctly for multi-byte UTF-8 characters, won't insert an incomplete UTF-8 character when reaching buffer limit (fix #158) -- Handle double-width space (0x3000) in various places the same as single-width spaces, for Chinese/Japanese users. -- Collapse triangle uses text color (not border color). -- Fixed font fallback glyph width. -- Renamed style.ScrollBarWidth to style.ScrollbarWidth to be consistent with other casing. -- Windows: setup a default handler for ImeSetInputScreenPosFn so the IME dialog (for Japanese/Chinese, etc.) is positioned correctly as you input text. -- Windows: default clipboard handlers for Windows handle UTF-8. -- Examples: Fixed DirectX 9/11 examples applications handling of Microsoft IME. -- Examples: Allow DirectX 9/11 examples applications to resize the window. -- ShowTestWindow: Fixed "undo" button of custom rendering applet. -- ShowTestWindow: Added "Manipulating Window Title" example. - - ------------------------------------------------------------------------ - VERSION 1.34 (2015-03-02) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.34 - -Other Changes: - -- Added Bullet() helper - equivalent to BulletText(""), SameLine(). -- Added SetWindowFocus(), SetWindowFocus(const char*), SetNextWindowFocus() (#146) -- Added SetWindowPos(), SetWindowSize(), SetWindowCollaposed() given a window name. -- Added SetNextTreeNodeOpened() with optional condition flag in replacement of OpenNextNode() and consistent with other API. -- Renamed ImGuiSetCondition_* to ImGuiSetCond_* and ImGuiCondition_FirstUseThisSession to ImGuiCond_Once. -- Added missing definition for ImGui::GetWindowCollapsed(). -- Fixed GetGlyphRangesJapanese() actually missing katakana ranges and a few useful extensions. -- Fixed clicking on a widget in a child window not focusing the parent window (#147). -- Fixed clicking on empty space of child window not setting keyboard focus for the child window (#147). -- Fixed IsItemHovered() behaving differently on Combo() (#145) -- Fixed ColumnOffsets storage not honoring SetStateStorage() (not very useful but consistent). -- Examples: Removed dependency on Glew for OpenGL examples. Removed Glew binaries for Windows. -- Examples: Fixed link warning for OpenGL windows examples. -- Comments, tweaks. - ------------------------------------------------------------------------ - VERSION 1.33b (2015-02-23) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.33b - -Other Changes: - -- Fixed resizing columns. - - ------------------------------------------------------------------------ - VERSION 1.33 (2015-02-22) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.33 - -Other Changes: - -- InputText: having a InputText widget active doesn't steal mouse inputs from clicking on a button before losing focus (relate to #134) -- InputText: cursor/selection/undo stack persist when using other widgets and getting back to same (#134). -- InputText: fix effective buffer size being smaller than necessary by 1 byte (so if you give 3 bytes you can input 2 ascii chars + zero terminator, which is correct). -- Added IsAnyItemActive(). -- Child window explicitly inherit collapse state from parent (so if user keeps submitting items even thought Begin has returned 'false' the child items will be clipped faster). -- BeginChild() return a bool the same way Begin() does. if true you can skip submitting content. -- Removed extraneous (1,1) padding on child window (pointed out in #125) -- Columns: doesn't bail out when SkipItems is set (fix #136) -- Columns: Separator() within column correctly vertical offset all cells (pointed out in #125) -- GetColumnOffset() / SetColumnOffset() handles padding values more correctly so matching columns can be lined up between a parent and a child window (cf. #125) -- Fix ImFont::BuildLookupTable() potential dangling pointer dereference (fix #131) -- Fix hovering of child window extending past their parent not taking account of parent clipping rectangle (fix #137) -- Sliders: value text is clipped inside the frame when resizing sliders to be small. -- ImGuITextFilter::Draw() use regular width call rather than computing its own arbitrary width. -- ImGuiTextFilter: can take a default filter string during construction. - - ------------------------------------------------------------------------ - VERSION 1.32 (2015-02-11) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.32 - -Other Changes: - -- Added Selectable() building block for various list boxes, combo boxes, etc. -- Added ListBox() (#129). -- Added ListBoxHeader(), ListBoxFooter() for customized list traversal and creating multi-selection boxes. -- Fixed title bar text clipping issue (fix #128). -- InputText: added ImGuiInputTextFlags_CallbackCharFilter system for filtering/replacement (#130). Callback now passed an "EventFlag" parameter. -- InputText: Added ImGuiInputTextFlags_CharsUppercase and ImGuiInputTextFlags_CharsNoBlank stock filters. -- PushItemWidth() can take negative value to right-align items. -- Optimisation: Columns offsets cached to avoid unnecessary binary search. -- Optimisation: Optimized CalcTextSize() function by about 25% (they are often the bottleneck when submitting thousands of clipped items). -- Added ImGuiCol_ChildWindowBg, ImGuiStyleVar_ChildWindowRounding for completeness and flexibility. -- Added BeginChild() variant that takes an ImGuiID. -- Tweak default ImGuiCol_HeaderActive color to be less bright. -- Calculate framerate for the user (IO.Framerate), as a purely luxurious feature and to reduce sample code size a little. - - ------------------------------------------------------------------------ - VERSION 1.31 (2015-02-08) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.31 - -Other Changes: - -- Added ImGuiWindowFlags_NoCollapse flag. -- Added a way to replace the internal state pointer so that we can optionally share it between modules (e.g. multiple DLLs). -- Added tint_col parameter to ImageButton(). -- Added CalcListClipping() helper to perform faster/coarse clipping on user side (when manipulating lists with thousands of items). -- Added GetCursorPosX() / GetCursorPosY() shortcuts. -- Renamed GetTextLineSpacing() to GetTextLineHeightWithSpacing(). -- Combo box always appears above other child windows of a same parent. -- Combo/Label: label is properly clipped inside the frame (#23). -- Added cpu-side text clipping functions which are used in some instances to avoid extra draw calls. -- InputText: Filtering private Unicode range 0xE000-0xF8FF. -- Fixed holding button over scrollbar creating a small feedback loop with calculation of contents size. -- Calling SetCursorPos() automatically extends the contents size. -- Track ownership of mouse clicks. Avoid requesting IO.WantCaptureMouse if initial click was outside of ImGui. -- Removed the dependency on realloc(). -- Other fixes, tweaks and comments. - - ------------------------------------------------------------------------ - VERSION 1.30 (2015-02-01) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.30 - -Breaking Changes: - -- Big update! Initialisation had to be changed. You don't need to load PNG data anymore. The new system gives you uncompressed texture data. - - This sequence: - const void* png_data; - unsigned int png_size; - ImGui::GetDefaultFontData(NULL, NULL, &png_data, &png_size); - // - - Became: - unsigned char* pixels; - int width, height; - // io.Fonts->AddFontFromFileTTF("myfontfile.ttf", 24.0f); // Optionally load another font - io.Fonts->GetTexDataAsRGBA32(&pixels, &width, &height); - // - io.Fonts->TexID = (your_texture_identifier); - - PixelCenterOffset has been removed and isn't a necessary setting anymore. Offset your projection matrix by 0.5 if you have rendering problems. - -Other Changes: - -- Loading TTF files with stb_truetype.h. -- We still embed a compressed pixel-perfect TTF version of ProggyClean for convenience. -- Runtime font rendering is a little faster than previously. -- You can load multiple fonts with multiple size inside the font atlas. Rendering with multiple fonts are still merged into a single draw call whenever possible. -- The system handles UTF-8 and provide ranges to easily load e.g. characters for Japanese display. -- Added PushFont() / PopFont(). -- Added Image() and ImageButton() to display your own texture data. -- Added callback system in command-list. This can be used if you want to do your own rendering (e.g. render a 3D scene) inside ImGui widgets. -- Added IsItemActive() to tell if last widget is being held / modified (as opposed to just being hovered). Useful for custom dragging behaviors. -- Style: Added FrameRounding setting for a more rounded look (default to 0 for now). -- Window: Fixed using multiple Begin/End pair on the same wnidow. -- Window: Fixed style.WindowMinSize not being honored properly. -- Window: Added SetCursorScreenPos() helper (WindowPos+CursorPos = ScreenPos). -- ColorEdit3: clicking on color square change the edition. The toggle button is hidden by default. -- Clipboard: Fixed logging to clipboard on architectures where va_list are passed by reference to vsnprintf. -- Clipboard: Improve memory reserve policy for Clipboard / ImGuiTextBuffer. -- Tooltip: Always auto-resize. -- Tooltip: Fixed TooltigBg color not being honored properly. -- Tooltip: Allow SetNextWindowPos() to be used on tooltips. -- Added io.DisplayVisibleMin / io.DisplayVisibleMax to ease integration of virtual / scrolling display. -- Added Set/GetVoidPtr in ImGuiStorage. -- Added ColorConvertHSVtoRGB, ColorConvertRGBtoHSV, ColorConvertFloat4ToU32 helpers. -- Added ImColor() inline helper to easily convert colors to packed 4x1 byte or 4x1 float formats. -- Added io.MouseDrawCursor option to draw a mouse cursor for now (on systems that don't have one) -- Examples: Added custom drawing app example for using ImDrawList api. -- Lots of others fixes, tweaks and comments! - - ------------------------------------------------------------------------ - VERSION 1.20 (2015-01-07) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.20 - -- Fixed InputInt() InputFloat() label not declaring their width, breaking usage of SameLine(). -- Fixed hovering of combo boxes that extend beyond the parent window limits. -- Fixed text input of Unicode character in the 128-255 range. -- Fixed clipboard pasting into an InputText box not filtering the characters according to contents semantic. -- Dragging outside area of a widget while it is active doesn't trigger hover on other widgets. -- Activating widget bring parent window to front if not already. -- Checkbox and Radio buttons activate on click-release to be consistent with other widgets and most UI. -- InputText() nows consume input characters immediately so they cannot be reused if ImGui::Update is called again with a call to ImGui::Render(). (fixes #105) -- Examples: Console: added support for History callbacks + some cleanup. -- Various small optimisations. -- Cleanup and other fixes. - - ------------------------------------------------------------------------ - VERSION 1.19 (2014-12-30) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.19 - -- Tightening default style a little. -- Added ImGuiStyleVar_WindowRounding enum for PushStyleVar() API. -- Added SliderInt2(), SliderInt3(), SliderInt4() for consistency. -- Widgets more consistently handle empty labels (starting with ## mark) for their size calculation. -- Fixed crashing with zero sized frame-buffer. -- Fixed ImGui::Combo() not registering its size properly when clipped out of screen. -- Renamed second parameter to Begin() to 'bool* p_opened' to be a little more self-explanatory. Added more comments on the use of Begin(). -- Logging: Added LogText() to pass text straight to the log output (tty/clipboard/file) without rendering it. -- Logging: Added LogFinish() to stop logging at an arbitrary point. -- Logging: Log depth padding relative to start depth. -- Logging: Tree nodes and headers looking better when logged to text. -- Logging: Log outputs \r\n under Windows to play it nicely with \n unaware tools such as Notepad. -- Style editor: added a button to output colors to clipboard/tty. -- OpenGL3 example: fix growing of VBO. -- Cleanup and other minor fixes. - - ------------------------------------------------------------------------ - VERSION 1.18 (2014-12-11) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.18 - -- Added ImGuiWindowFlags_NoScrollWithMouse, disable mouse wheel scrolling on a window. -- Added ImGuiWindowFlags_NoSavedSettings, disable loading/saving window state to .ini file. -- Added SetNextWindowPos(), SetNextWindowSize(), SetNextWindowCollapsed() API along with SetWindowPos(), SetWindowSize(), SetWindowCollapsed(). All functions include an optional second parameter to easily set current value vs session default value vs persistent default value. -- Removed rarely useful SetNewWindowDefaultPos() in favor of new API. -- Fixed hovering of lower-right resize grip when it is above a child window. -- Fixed InputInt() writing to output when it doesn't need to. -- Added IMGUI_INCLUDE_IMGUI_USER_H define to include user file at the bottom of imgui.h without modifying the vanilla distribution. -- ImGuiStorage helper can store float + added helpers to get pointer to stored data. -- Setup Travis CI integration. Builds the OpenGL examples on Linux with GCC and Clang. -- Examples: Added a "Fixed overlay" example in ShowTestWindow(). -- Examples: Re-added OpenGL 3 programmable-pipeline example (along with the existing fixed pipeline example). -- Examples: OpenGL examples can now resize the application window. -- Other minor fixes and comments. - - ------------------------------------------------------------------------ - VERSION 1.17 (2014-12-03) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.17 - -- Added ImGuiWindowFlags_AlwaysAutoResize + example app. -- Calling ImGui::SetWindowSize(0,0) force an autofit without zero-sizing first. -- ImGui::InputText() support for completion/history/custom callback + added fancy completion example in the console demo app. -- Not word-wrapping on apostrophes. -- Increased visibility of check box and radio button with smaller size. -- Smooth mouse scrolling on OSX (uses floating point scroll/wheel input). -- New version of IMGUI_ONCE_UPON_A_FRAME helper macro that works with all compilers. -- Moved IO.Font*** options to inside the IO.Font-> structure.. Added IO.FontGlobalScale setting (in addition to Font->Scale per individual font). -- Fixed more Clang -Weverything warnings. -- Examples: Added DirectX11 example application. -- Examples: Created single .sln solution for all example projects. -- Examples: Fixed DirectX9 example window initially showing an hourglass cursor. -- Examples: Removed Microsoft IME handler in examples, too niche/confusing. Moved equivalent code to imgui.cpp instruction block. - - ------------------------------------------------------------------------ - VERSION 1.16b (2014-11-21) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.16b - -- Fix broken PopStyleVar() crashing. - - ------------------------------------------------------------------------ - VERSION 1.16 (2014-11-21) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.16 - -- General fixing of Columns API to allow filling a cell with multiple widgets before switching to the next column. -- Added documentation INDEX to top of imgui.cpp. -- Fixed unaligned memory access for Emscripten compatibility. -- Various pedantic warning fixes (now testing with Clang). -- Added extra asserts to catch incorrect usage. -- PushStyleColor() / PushStyleVar() can be used outside the scope of a window (namely to change variables that are used within the Begin() call). -- PushTextWrapPos() defaults to 0.0 (right-end of current drawing region). -- Fixed compatibility with std::vector if user decide to #define ImVector. -- MouseWheel input is now normalized. -- Added IMGUI_OVERRIDE_DRAWVERT_STRUCT_LAYOUT compile-time option to redefine the vertex layout. -- Style editor: colors listed inside a scrolling region. -- Examples: tweaks and fixes. - - ------------------------------------------------------------------------ - VERSION 1.15 (2014-11-07) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.15 - -- Renamed IsHovered() to IsItemHovered(). -- Added word-wrapping API: TextWrapped(), PushTextWrapPos(), PopTextWrapPos(). -- Added IsItemFocused() to tell if last widget is being focused for keyboard input. -- Added overloads of ImGui::PlotLines() and ImGui::PlotHistogram() taking a function pointer to get values. -- Added SetWindowSize(). -- Added GetContentRegionMax() supporting columns. Some bug fixes with using columns. -- Added PushStyleVar(),PopStyleVar() helpers to modify style from user code. -- Added dummy IMGUI_API definition in front of all entry-points for silly DLL action. -- Allowing BeginChild() allows to specify negative sizes to specify "use remaining minus xx". -- Windows with the NoResize flag can still use auto-fitting. -- Added a simple example console into the demo window. -- Comments and fixes. - - ------------------------------------------------------------------------ - VERSION 1.14 (2014-10-25) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.14 - -- Comments and fixes. -- Added SetKeyboardFocusHere() to set input focus from code. -- Added GetWindowFont(), GetWindowFontSize() for users of the low-level ImDrawList API. -- Added a UserData void *pointer so that the callback functions can access user state "Just in case a project has adverse reactions to adding globals or statics in their own code." -- Renamed IMGUI_INCLUDE_IMGUI_USER_CPP to IMGUI_INCLUDE_IMGUI_USER_INL - - ----------------------------------------------------------------------- - VERSION 1.13 (2014-09-30) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.13 - -- Added support for UTF-8 for international text display and text edition/input (if the font supports it). -- Added sample "M+ font" by Coji Morishita in extra_fonts/ to display Japanese text. -- Added IO.ImeSetInputScreenPosFn callback for positioning OS IME input. -- Added IO.FontFallbackGlyph (default to '?'). -- OpenGL example: added commented code to load custom font from file-system. -- OpenGL example: shared makefile for Linux and MacOSX. - - ----------------------------------------------------------------------- - VERSION 1.12 (2014-09-24) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.12 - -- Added IO.FontBaseScale value for easy scaling of all windows. -- Added IsMouseHoveringWindow(), IsMouseHoveringAnyWindow(), IsPosHoveringAnyWindow() helpers. -- Added va_list variations of all functions taking ellipsis (...) parameters. -- Added section in documentation to explicitly document cases of API breaking changes (e.g. renamed IM_MALLOC below). -- Moved IM_MALLOC / IM_FREE defines. to IO structure members that can be set at runtime (also allowing precompiled ImGui to cover more use cases). -- Fixed OpenGL samples for Retina display. -- Comments and minor fixes. - - ----------------------------------------------------------------------- - VERSION 1.11 (2014-09-10) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.11 - -- Added more comments in the code. -- Made radio buttons render ascii when logged into tty/file/clipboard. -- Added ImGuiInputTextFlags_EnterReturnsTrue flag to InputText() and variants. -- Added #define IMGUI_INCLUDE_IMGUI_USER_CPP to optionally include imgui_user.cpp from the end of imgui.cpp -- Fixed file-descriptor leak if ImBitmapFont::LoadFromFile() calls to fseek/ftell fails. - - ----------------------------------------------------------------------- - VERSION 1.10 (2014-08-31) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.10 - -- User can override memory allocators by #define-ing IM_MALLOC, IM_FREE, IM_REALLOC, -- Added SetCursorPosX(), SetCursorPosY() shortcuts. -- Checkbox() returns true when pressed. -- Added optional external fonts data in extra_fonts/ for reference. -- Removed the need to setup IO.FontHeight when using a custom font. -- Added comments on external fonts usage. - - ----------------------------------------------------------------------- - VERSION 1.09 (2014-08-28) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.09 - -Breaking Changes: - -- The behaviour of PixelCenterOffset changed! You may need to change your value if you had set it to non-default in your code and/or offset your projection matrix by 0.5 pixels. It is likely that the default PixelCenterOffset value of 0.0 is now suitable unless your rendering uses some form of multisampling. - -Other Changes: - -- Various minor render tweaks and fixes. Better support for renderers using multisampling. -- Moved IMGUI_FONT_TEX_UV_FOR_WHITE #define to a variable in the IO structure so font can be changed at runtime. -- Minor other fixes, tweaks, comments. - - ----------------------------------------------------------------------- - VERSION 1.08 (2014-08-25) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.09 - -- Fixed ImGuiTextFilter trimming of leading/trailing blanks. -- Fixed file descriptor leak on LoadSettings() failure. -- Fix type conversion compiler warnings. -- Added basic sizes edition in the style editor. -- Added CalcTextSize(), GetCursorScreenPos() functions. -- Disable client state in OpenGL example after rendering. -- Converted all Tabs to Spaces in sources. - - ----------------------------------------------------------------------- - VERSION 1.07 (2014-08-18) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.07 - -- Added InputFloat4(), SliderFloat4() helpers. -- Added global Alpha in ImGuiStyle structure. When Alpha=0.0, ImGui skips most of logic and all rendering processing. -- Fix clipping of title bar text. -- Fix to allow the user to call NewFrame() multiple times without calling Render(). -- Reduce inner window clipping to take account for the extend of CollapsingHeader() - share same clipping rectangle. -- Fix for child windows with inverted clip rectangles (when scrolled and out of screen, Etc.). -- Minor fixes, tweaks, comments. - - ----------------------------------------------------------------------- - VERSION 1.06 (2014-08-15) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.06 - -- Added BeginTooltip()/EndTooltip() helpers to create tooltips with custom contents. -- Added TextColored() helper. -- Added a 'stride' parameter to PlotLines() / PlotHistogram(). -- Fixed PlotLines() / PlotHistogram() from occasionally wrapping back to the most-left value. -- TreeNode() / CollapsingHeader() ignore clicks when CTRL or SHIFT are held. -- Slowed down mouse wheel scrolling inside combo boxes. -- Minor tweaks. -- Fixed trailing '\n' in text strings reporting extra line height. -- Fixed tooltip position needlessly leaking into .ini file. -- Fixed invalid .ini file data persistently being saved back into the file. - - ----------------------------------------------------------------------- - VERSION 1.05 (2014-08-14) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.05 - -- Added default clipboard functions for Windows + "private" clipboard on other systems (user can still override). -- Fixed logarithmic sliders and HSV conversions on Mac/Linux. -- Tidying up example applications so it looks easier to just grab code. -- Added GetItemBoxMin(), GetItemBoxMax(). -- Tweaks, more consistent #define names. -- Fix for doing multiple Begin()/End() during the same frame. - - ----------------------------------------------------------------------- - VERSION 1.04 (2014-08-13) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.04 - -- Fixes (v1.03 introduced a bug with combo box & scissoring bug OpenGL sample). -- Added ImGui::InputFloat2() and ImGui::SliderFloat2() functions. - - ----------------------------------------------------------------------- - VERSION 1.03 (2014-08-13) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.03 - -- OpenGL example now use the fixed function-pipeline + cleanups, down by 150 lines. -- Added quick & dirty Makefiles for MacOSX and Linux. -- Simplified the DrawList system, ImDrawCmd include the clipping rectangle + some optimisations. -- Fixed warnings for more stringent compilation settings. - - ----------------------------------------------------------------------- - VERSION 1.02 (2014-08-12) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.02 - -- Comments. -- Portability fixes. -- Fixing and tidying up sample applications. -- Checkboxes and radio buttons can be clicked on their labels as well as their icon. -- Checkboxes and radio buttons display in a different color when hovered. - - ----------------------------------------------------------------------- - VERSION 1.01 (2014-08-11) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.01 - -- Added PixelCenterOffset for OpenGL/DirectX compatibility. -- Commented and tweaked samples. -- Added Git ignore list. - - ----------------------------------------------------------------------- - VERSION 1.00 (2014-08-10) ------------------------------------------------------------------------ - -Decorated log and release notes: https://github.com/ocornut/imgui/releases/tag/v1.00 - -- Initial release. - diff --git a/app/jni/src/libultraship/extern/ImGui/docs/CONTRIBUTING.md b/app/jni/src/libultraship/extern/ImGui/docs/CONTRIBUTING.md deleted file mode 100644 index 7d6738d..0000000 --- a/app/jni/src/libultraship/extern/ImGui/docs/CONTRIBUTING.md +++ /dev/null @@ -1,81 +0,0 @@ -# Contributing Guidelines - -## Index - -- [Getting Started & General Advice](#getting-started--general-advice) -- [Issues vs Discussions](#issues-vs-discussions) -- [How to open an Issue](#how-to-open-an-issue) -- [How to open a Pull Request](#how-to-open-a-pull-request) -- [Copyright / Contributor License Agreement](#copyright--contributor-license-agreement) - -## Getting Started & General Advice - -- Article: [How To Ask Good Questions](https://bit.ly/3nwRnx1). -- Please browse the [Wiki](https://github.com/ocornut/imgui/wiki) to find code snippets, links and other resources (e.g. [Getting Started](https://github.com/ocornut/imgui/wiki/Getting-Started), [Useful extensions](https://github.com/ocornut/imgui/wiki/Useful-Extensions)). -- Please read [Getting Started](https://github.com/ocornut/imgui/wiki/Getting-Started) if your question relates to setting up Dear ImGui. -- Please read [docs/FAQ.md](https://github.com/ocornut/imgui/blob/master/docs/FAQ.md). -- Please read [docs/FONTS.md](https://github.com/ocornut/imgui/blob/master/docs/FONTS.md) if your question relates to fonts or text. -- Please run `ImGui::ShowDemoWindow()` to explore the demo and its sources. -- Please use the search function of your IDE to search for symbols and comments related to your situation. -- Please use the search function of GitHub to look for similar topics (always include 'Closed' issues/pr in your search). -- You may [browse issues by Labels](https://github.com/ocornut/imgui/labels). -- Please use a web search engine to look for similar issues. -- If you get a crash or assert, use a debugger to locate the line triggering it and read the comments around. -- Please don't be a [Help Vampire](https://slash7.com/2006/12/22/vampires/). - -## 'Issues' vs 'Discussions' - -We are happy to use 'Issues' for many type of open-ended questions. We are encouraging 'Issues' becoming an enormous, centralized and cross-referenced database of Dear ImGui contents. - -Only if you: -- Cannot BUILD or LINK examples. -- Cannot BUILD, or LINK, or RUN Dear ImGui in your application or custom engine. -- Cannot LOAD a font. - -Then please [use the Discussions forums](https://github.com/ocornut/imgui/discussions) instead of opening an issue. - -If Dear ImGui is successfully showing in your app and you have used Dear ImGui before, you can open an Issue. Any form of discussions is welcome as a new issue. - -## How to open an issue - -You may use the Issue Tracker to submit bug reports, feature requests or suggestions. You may ask for help or advice as well. But **PLEASE CAREFULLY READ THIS WALL OF TEXT. ISSUES IGNORING THOSE GUIDELINES MAY BE CLOSED. USERS IGNORING THOSE GUIDELINES MIGHT BE BLOCKED.** - -Please do your best to clarify your request. The amount of incomplete or ambiguous requests due to people not following those guidelines is often overwhelming. Issues created without the requested information may be closed prematurely. Exceptionally entitled, impolite, or lazy requests may lead to bans. - -**PLEASE UNDERSTAND THAT OPEN-SOURCE SOFTWARE LIVES OR DIES BY THE AMOUNT OF ENERGY MAINTAINERS CAN SPARE. WE HAVE LOTS OF STUFF TO DO. THIS IS AN ATTENTION ECONOMY AND MANY LAZY OR MINOR ISSUES ARE HOGGING OUR ATTENTION AND DRAINING ENERGY, TAKING US AWAY FROM MORE IMPORTANT WORK.** - -Steps: - -- Article: [How To Ask Good Questions](https://bit.ly/3nwRnx1). -- **PLEASE DO FILL THE REQUESTED NEW ISSUE TEMPLATE.** Including Dear ImGui version number, branch name, platform/renderer back-ends (imgui_impl_XXX files), operating system. -- **Try to be explicit with your GOALS, your EXPECTATIONS and what you have tried**. Be mindful of [The XY Problem](http://xyproblem.info/). What you have in mind or in your code is not obvious to other people. People frequently discuss problems and suggest incorrect solutions without first clarifying their goals. When requesting a new feature, please describe the usage context (how you intend to use it, why you need it, etc.). If you tried something and it failed, show us what you tried. -- **Please INCLUDE CODE. Provide a Minimal, Complete, and Verifiable Example ([MCVE](https://stackoverflow.com/help/mcve)) to demonstrate your problem**. An ideal submission includes a small piece of code that anyone can paste into one of the examples applications (examples/../main.cpp) or demo (imgui_demo.cpp) to understand and reproduce it. **Narrowing your problem to its shortest and purest form is the easiest way to understand it, explain it and fix it**. Please test your shortened code to ensure it exhibits the problem. **Often while creating the MCVE you will solve the problem!** Many questions that are missing a standalone verifiable example are missing the actual cause of their issue in the description, which ends up wasting everyone's time. -- **Attach screenshots (or GIF/video) to clarify the context**. They often convey useful information that is omitted by the description. You can drag pictures/files in the message edit box. Avoid using 3rd party image hosting services, prefer the long-term longevity of GitHub attachments (you can drag pictures into your post). On Windows, you can use [ScreenToGif](https://www.screentogif.com/) to easily capture .gif files. -- **If you are discussing an assert or a crash, please provide a debugger callstack**. Never state "it crashes" without additional information. If you don't know how to use a debugger and retrieve a callstack, learning about it will be useful. -- **Please make sure that your project has asserts enabled.** Calls to IM_ASSERT() are scattered in the code to help catch common issues. When an assert is triggered read the comments around it. By default IM_ASSERT() calls the standard assert() function. To verify that your asserts are enabled, add the line `IM_ASSERT(false);` in your main() function. Your application should display an error message and abort. If your application doesn't report an error, your asserts are disabled. -- Please state if you have made substantial modifications to your copy of Dear ImGui or the back-end. -- If you are not calling Dear ImGui directly from C++, please provide information about your Language and the wrapper/binding you are using. -- Be mindful that messages are being sent to the mailbox of "Watching" users. Try to proofread your messages before sending them. Edits are not seen by those users unless they browse the site. - -**Some unfortunate words of warning** -- If you are involved in cheating schemes (e.g. DLL injection) for competitive online multiplayer games, please don't post here. We won't answer and you will be blocked. It doesn't matter if your question relates to said project. We've had too many of you and need to project our time and sanity. -- Due to frequent abuse of this service from the aforementioned users, if your GitHub account is anonymous and was created five minutes ago please understand that your post will receive more scrutiny and incomplete questions will be harshly dismissed. - -If you have been using Dear ImGui for a while or have been using C/C++ for several years or have demonstrated good behavior here, it is ok to not fulfill every item to the letter. Those are guidelines and experienced users or members of the community will know which information is useful in a given context. - -## How to open a Pull Request - -- **Please understand that by submitting a PR you are also submitting a request for the maintainer to review your code and then take over its maintenance.** PR should be crafted both in the interest of the end-users and also to ease the maintainer into understanding and accepting it. -- Many PRs are useful to demonstrate a need and a possible solution but aren't adequate for merging (causing other issues, not seeing other aspects of the big picture, etc.). In doubt, don't hesitate to push a PR because that is always the first step toward pointing toward a problem, and finding the mergeable solution! Even if a PR stays unmerged for a long time, its presence can be useful for other users and helps toward finding a general solution. -- **When adding a feature,** please describe the usage context (how you intend to use it, why you need it, etc.). Be mindful of [The XY Problem](http://xyproblem.info/). -- **When fixing a warning or compilation problem,** please post the compiler log and specify the compiler version and platform you are using. -- **Attach screenshots (or GIF/video) to clarify the context and demonstrate the feature at a glance.** You can drag pictures/files in the message edit box. Prefer the long-term longevity of GitHub attachments over 3rd party hosting (you can drag pictures into your post). -- **Make sure your code follows the coding style already used in the codebase:** 4 spaces indentations (no tabs), `local_variable`, `FunctionName()`, `MemberName`, `// Text Comment`, `//CodeComment();`, C-style casts, etc.. We don't use modern C++ idioms and tend to use only a minimum of C++11 features. The applications under examples/ are generally less consistent because they sometimes try to mimic the coding style often adopted by a certain ecosystem (e.g. DirectX-related code tend to use the style of their sample). -- **Make sure you create a branch dedicated to the pull request**. In Git, 1 PR is associated to 1 branch. If you keep pushing to the same branch after you submitted the PR, your new commits will appear in the PR (we can still cherry-pick individual commits). - -## Copyright / Contributor License Agreement - -Any code you submit will become part of the repository and be distributed under the [Dear ImGui license](https://github.com/ocornut/imgui/blob/master/LICENSE.txt). By submitting code to the project you agree that the code is your work and that you can give it to the project. - -You also agree by submitting your code that you grant all transferrable rights to the code to the project maintainer, including for example re-licensing the code, modifying the code, and distributing it in source or binary forms. Specifically, this includes a requirement that you assign copyright to the project maintainer. For this reason, do not modify any copyright statements in files in any PRs. - diff --git a/app/jni/src/libultraship/extern/ImGui/docs/EXAMPLES.md b/app/jni/src/libultraship/extern/ImGui/docs/EXAMPLES.md deleted file mode 100644 index edaddb0..0000000 --- a/app/jni/src/libultraship/extern/ImGui/docs/EXAMPLES.md +++ /dev/null @@ -1,245 +0,0 @@ -_(You may browse this at https://github.com/ocornut/imgui/blob/master/docs/EXAMPLES.md or view this file with any Markdown viewer)_ - -## Dear ImGui: Examples - -**The [examples/](https://github.com/ocornut/imgui/blob/master/examples) folder example applications (standalone, ready-to-build) for variety of -platforms and graphics APIs.** They all use standard backends from the [backends/](https://github.com/ocornut/imgui/blob/master/backends) folder (see [BACKENDS.md](https://github.com/ocornut/imgui/blob/master/docs/BACKENDS.md)). - -The purpose of Examples is to showcase integration with backends, let you try Dear ImGui, and guide you toward -integrating Dear ImGui in your own application/game/engine. -**Once Dear ImGui is setup and running, run and refer to `ImGui::ShowDemoWindow()` in imgui_demo.cpp for usage of the end-user API.** - -You can find Windows binaries for some of those example applications at: - https://www.dearimgui.com/binaries - - -### Getting Started - -Integration in a typical existing application, should take <20 lines when using standard backends. - -```cpp -At initialization: - call ImGui::CreateContext() - call ImGui_ImplXXXX_Init() for each backend. - -At the beginning of your frame: - call ImGui_ImplXXXX_NewFrame() for each backend. - call ImGui::NewFrame() - -At the end of your frame: - call ImGui::Render() - call ImGui_ImplXXXX_RenderDrawData() for your Renderer backend. - -At shutdown: - call ImGui_ImplXXXX_Shutdown() for each backend. - call ImGui::DestroyContext() -``` - -Example (using [backends/imgui_impl_win32.cpp](https://github.com/ocornut/imgui/blob/master/backends/imgui_impl_win32.cpp) + [backends/imgui_impl_dx11.cpp](https://github.com/ocornut/imgui/blob/master/backends/imgui_impl_dx11.cpp)): - -```cpp -// Create a Dear ImGui context, setup some options -ImGui::CreateContext(); -ImGuiIO& io = ImGui::GetIO(); -io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard; // Enable some options - -// Initialize Platform + Renderer backends (here: using imgui_impl_win32.cpp + imgui_impl_dx11.cpp) -ImGui_ImplWin32_Init(my_hwnd); -ImGui_ImplDX11_Init(my_d3d_device, my_d3d_device_context); - -// Application main loop -while (true) -{ - // Beginning of frame: update Renderer + Platform backend, start Dear ImGui frame - ImGui_ImplDX11_NewFrame(); - ImGui_ImplWin32_NewFrame(); - ImGui::NewFrame(); - - // Any application code here - ImGui::Text("Hello, world!"); - - // End of frame: render Dear ImGui - ImGui::Render(); - ImGui_ImplDX11_RenderDrawData(ImGui::GetDrawData()); - - // Swap - g_pSwapChain->Present(1, 0); -} - -// Shutdown -ImGui_ImplDX11_Shutdown(); -ImGui_ImplWin32_Shutdown(); -ImGui::DestroyContext(); -``` - -Please read 'PROGRAMMER GUIDE' in imgui.cpp for notes on how to setup Dear ImGui in your codebase. -Please read the comments and instruction at the top of each file. -Please read FAQ at https://www.dearimgui.com/faq - -If you are using any of the backends provided here, you can add the backends/imgui_impl_xxxx(.cpp,.h) -files to your project and use as-in. Each imgui_impl_xxxx.cpp file comes with its own individual -Changelog, so if you want to update them later it will be easier to catch up with what changed. - - -### Examples Applications - -[example_allegro5/](https://github.com/ocornut/imgui/blob/master/examples/example_allegro5/)
-Allegro 5 example.
-= main.cpp + imgui_impl_allegro5.cpp - -[example_android_opengl3/](https://github.com/ocornut/imgui/blob/master/examples/example_android_opengl3/)
-Android + OpenGL3 (ES) example.
-= main.cpp + imgui_impl_android.cpp + imgui_impl_opengl3.cpp - -[example_apple_metal/](https://github.com/ocornut/imgui/blob/master/examples/example_metal/)
-OSX & iOS + Metal example.
-= main.m + imgui_impl_osx.mm + imgui_impl_metal.mm
-It is based on the "cross-platform" game template provided with Xcode as of Xcode 9. -(NB: imgui_impl_osx.mm is currently not as feature complete as other platforms backends. -You may prefer to use the GLFW Or SDL backends, which will also support Windows and Linux.) - -[example_apple_opengl2/](https://github.com/ocornut/imgui/blob/master/examples/example_apple_opengl2/)
-OSX + OpenGL2 example.
-= main.mm + imgui_impl_osx.mm + imgui_impl_opengl2.cpp
-(NB: imgui_impl_osx.mm is currently not as feature complete as other platforms backends. - You may prefer to use the GLFW Or SDL backends, which will also support Windows and Linux.) - -[example_emscripten_wgpu/](https://github.com/ocornut/imgui/blob/master/examples/example_emscripten_wgpu/)
-Emcripten + GLFW + WebGPU example.
-= main.cpp + imgui_impl_glfw.cpp + imgui_impl_wgpu.cpp -Note that the 'example_glfw_opengl3' and 'example_sdl2_opengl3' examples also supports Emscripten! - -[example_glfw_metal/](https://github.com/ocornut/imgui/blob/master/examples/example_glfw_metal/)
-GLFW (Mac) + Metal example.
-= main.mm + imgui_impl_glfw.cpp + imgui_impl_metal.mm - -[example_glfw_opengl2/](https://github.com/ocornut/imgui/blob/master/examples/example_glfw_opengl2/)
-GLFW + OpenGL2 example (legacy, fixed pipeline).
-= main.cpp + imgui_impl_glfw.cpp + imgui_impl_opengl2.cpp
-**DO NOT USE THIS IF YOUR CODE/ENGINE IS USING MODERN GL or WEBGL (SHADERS, VBO, VAO, etc.)**
-This code is mostly provided as a reference to learn about Dear ImGui integration, because it is shorter. -If your code is using GL3+ context or any semi modern GL calls, using this renderer is likely to -make things more complicated, will require your code to reset many GL attributes to their initial -state, and might confuse your GPU driver. One star, not recommended. - -[example_glfw_opengl3/](https://github.com/ocornut/imgui/blob/master/examples/example_glfw_opengl3/)
-GLFW (Win32, Mac, Linux) + OpenGL3+/ES2/ES3 example (modern, programmable pipeline).
-= main.cpp + imgui_impl_glfw.cpp + imgui_impl_opengl3.cpp
-This uses more modern GL calls and custom shaders.
-This support building with Emscripten and targetting WebGL.
-Prefer using that if you are using modern GL or WebGL in your application. - -[example_glfw_vulkan/](https://github.com/ocornut/imgui/blob/master/examples/example_glfw_vulkan/)
-GLFW (Win32, Mac, Linux) + Vulkan example.
-= main.cpp + imgui_impl_glfw.cpp + imgui_impl_vulkan.cpp
-This is quite long and tedious, because: Vulkan. -For this example, the main.cpp file exceptionally use helpers function from imgui_impl_vulkan.h/cpp. - -[example_glut_opengl2/](https://github.com/ocornut/imgui/blob/master/examples/example_glut_opengl2/)
-GLUT (e.g., FreeGLUT on Linux/Windows, GLUT framework on OSX) + OpenGL2 example.
-= main.cpp + imgui_impl_glut.cpp + imgui_impl_opengl2.cpp
-Note that GLUT/FreeGLUT is largely obsolete software, prefer using GLFW or SDL. - -[example_null/](https://github.com/ocornut/imgui/blob/master/examples/example_null/)
-Null example, compile and link imgui, create context, run headless with no inputs and no graphics output.
-= main.cpp
-This is used to quickly test compilation of core imgui files in as many setups as possible. -Because this application doesn't create a window nor a graphic context, there's no graphics output. - -[example_sdl2_directx11/](https://github.com/ocornut/imgui/blob/master/examples/example_sdl2_directx11/)
-SDL2 + DirectX11 example, Windows only.
-= main.cpp + imgui_impl_sdl2.cpp + imgui_impl_dx11.cpp
-This to demonstrate usage of DirectX with SDL2. - -[example_sdl2_metal/](https://github.com/ocornut/imgui/blob/master/examples/example_sdl2_metal/)
-SDL2 + Metal example, Mac only.
-= main.mm + imgui_impl_sdl2.cpp + imgui_impl_metal.mm - -[example_sdl2_opengl2/](https://github.com/ocornut/imgui/blob/master/examples/example_sdl2_opengl2/)
-SDL2 (Win32, Mac, Linux etc.) + OpenGL example (legacy, fixed pipeline).
-= main.cpp + imgui_impl_sdl2.cpp + imgui_impl_opengl2.cpp
-**DO NOT USE OPENGL2 CODE IF YOUR CODE/ENGINE IS USING GL OR WEBGL (SHADERS, VBO, VAO, etc.)**
-This code is mostly provided as a reference to learn about Dear ImGui integration, because it is shorter. -If your code is using GL3+ context or any semi modern GL calls, using this renderer is likely to -make things more complicated, will require your code to reset many GL attributes to their initial -state, and might confuse your GPU driver. One star, not recommended. - -[example_sdl2_opengl3/](https://github.com/ocornut/imgui/blob/master/examples/example_sdl2_opengl3/)
-SDL2 (Win32, Mac, Linux, etc.) + OpenGL3+/ES2/ES3 example.
-= main.cpp + imgui_impl_sdl2.cpp + imgui_impl_opengl3.cpp
-This uses more modern GL calls and custom shaders.
-This support building with Emscripten and targetting WebGL.
-Prefer using that if you are using modern GL or WebGL in your application. - -[example_sdl2_sdlrenderer2/](https://github.com/ocornut/imgui/blob/master/examples/example_sdl2_sdlrenderer2/)
-SDL2 (Win32, Mac, Linux, etc.) + SDL_Renderer for SDL2 (most graphics backends are supported underneath)
-= main.cpp + imgui_impl_sdl2.cpp + imgui_impl_sdlrenderer.cpp
-This requires SDL 2.0.18+ (released November 2021)
- -[example_sdl2_vulkan/](https://github.com/ocornut/imgui/blob/master/examples/example_sdl2_vulkan/)
-SDL2 (Win32, Mac, Linux, etc.) + Vulkan example.
-= main.cpp + imgui_impl_sdl2.cpp + imgui_impl_vulkan.cpp
-This is quite long and tedious, because: Vulkan.
-For this example, the main.cpp file exceptionally use helpers function from imgui_impl_vulkan.h/cpp. - -[example_win32_directx9/](https://github.com/ocornut/imgui/blob/master/examples/example_win32_directx9/)
-DirectX9 example, Windows only.
-= main.cpp + imgui_impl_win32.cpp + imgui_impl_dx9.cpp - -[example_win32_directx10/](https://github.com/ocornut/imgui/blob/master/examples/example_win32_directx10/)
-DirectX10 example, Windows only.
-= main.cpp + imgui_impl_win32.cpp + imgui_impl_dx10.cpp - -[example_win32_directx11/](https://github.com/ocornut/imgui/blob/master/examples/example_win32_directx11/)
-DirectX11 example, Windows only.
-= main.cpp + imgui_impl_win32.cpp + imgui_impl_dx11.cpp - -[example_win32_directx12/](https://github.com/ocornut/imgui/blob/master/examples/example_win32_directx12/)
-DirectX12 example, Windows only.
-= main.cpp + imgui_impl_win32.cpp + imgui_impl_dx12.cpp
-This is quite long and tedious, because: DirectX12. - -[example_win32_opengl3/](https://github.com/ocornut/imgui/blob/master/examples/example_win32_opengl3/)
-Raw Windows + OpenGL3 + example (modern, programmable pipeline)
-= main.cpp + imgui_impl_win32.cpp + imgui_impl_opengl3.cpp
- - -### Miscellaneous - -**Building** - -Unfortunately nowadays it is still tedious to create and maintain portable build files using external -libraries (the kind we're using here to create a window and render 3D triangles) without relying on -third party software and build systems. For most examples here we choose to provide: - - Makefiles for Linux/OSX - - Batch files for Visual Studio 2008+ - - A .sln project file for Visual Studio 2012+ - - Xcode project files for the Apple examples -Please let us know if they don't work with your setup! -You can probably just import the imgui_impl_xxx.cpp/.h files into your own codebase or compile those -directly with a command-line compiler. - -If you are interested in using Cmake to build and links examples, see: - https://github.com/ocornut/imgui/pull/1713 and https://github.com/ocornut/imgui/pull/3027 - -**About mouse cursor latency** - -Dear ImGui has no particular extra lag for most behaviors, -e.g. the last value passed to 'io.AddMousePosEvent()' before NewFrame() will result in windows being moved -to the right spot at the time of EndFrame()/Render(). At 60 FPS your experience should be pleasant. - -However, consider that OS mouse cursors are typically drawn through a very specific hardware accelerated -path and will feel smoother than the majority of contents rendered via regular graphics API (including, -but not limited to Dear ImGui windows). Because UI rendering and interaction happens on the same plane -as the mouse, that disconnect may be jarring to particularly sensitive users. -You may experiment with enabling the io.MouseDrawCursor flag to request Dear ImGui to draw a mouse cursor -using the regular graphics API, to help you visualize the difference between a "hardware" cursor and a -regularly rendered software cursor. -However, rendering a mouse cursor at 60 FPS will feel sluggish so you likely won't want to enable that at -all times. It might be beneficial for the user experience to switch to a software rendered cursor _only_ -when an interactive drag is in progress. - -Note that some setup or GPU drivers are likely to be causing extra display lag depending on their settings. -If you feel that dragging windows feels laggy and you are not sure what the cause is: try to build a simple -drawing a flat 2D shape directly under the mouse cursor! - diff --git a/app/jni/src/libultraship/extern/ImGui/docs/FAQ.md b/app/jni/src/libultraship/extern/ImGui/docs/FAQ.md deleted file mode 100644 index be79376..0000000 --- a/app/jni/src/libultraship/extern/ImGui/docs/FAQ.md +++ /dev/null @@ -1,680 +0,0 @@ -# FAQ (Frequently Asked Questions) - -You may link to this document using short form: - https://www.dearimgui.com/faq -or its real address: - https://github.com/ocornut/imgui/blob/master/docs/FAQ.md -or view this file with any Markdown viewer. - - -## Index - -| **Q&A: Basics** | -:---------------------------------------------------------- | -| [Where is the documentation?](#q-where-is-the-documentation) | -| [What is this library called?](#q-what-is-this-library-called) | -| [Which version should I get?](#q-which-version-should-i-get) | -| **Q&A: Integration** | -| **[How to get started?](#q-how-to-get-started)** | -| **[How can I tell whether to dispatch mouse/keyboard to Dear ImGui or my application?](#q-how-can-i-tell-whether-to-dispatch-mousekeyboard-to-dear-imgui-or-my-application)** | -| [How can I enable keyboard or gamepad controls?](#q-how-can-i-enable-keyboard-or-gamepad-controls) | -| [How can I use this on a machine without mouse, keyboard or screen? (input share, remote display)](#q-how-can-i-use-this-on-a-machine-without-mouse-keyboard-or-screen-input-share-remote-display) | -| [I integrated Dear ImGui in my engine and little squares are showing instead of text...](#q-i-integrated-dear-imgui-in-my-engine-and-little-squares-are-showing-instead-of-text) | -| [I integrated Dear ImGui in my engine and some elements are clipping or disappearing when I move windows around...](#q-i-integrated-dear-imgui-in-my-engine-and-some-elements-are-clipping-or-disappearing-when-i-move-windows-around) | -| [I integrated Dear ImGui in my engine and some elements are displaying outside their expected windows boundaries...](#q-i-integrated-dear-imgui-in-my-engine-and-some-elements-are-displaying-outside-their-expected-windows-boundaries) | -| **Q&A: Usage** | -| **[About the ID Stack system..
Why is my widget not reacting when I click on it?
How can I have widgets with an empty label?
How can I have multiple widgets with the same label?
How can I have multiple windows with the same label?](#q-about-the-id-stack-system)** | -| [How can I display an image? What is ImTextureID, how does it work?](#q-how-can-i-display-an-image-what-is-imtextureid-how-does-it-work)| -| [How can I use maths operators with ImVec2?](#q-how-can-i-use-maths-operators-with-imvec2) | -| [How can I use my own maths types instead of ImVec2/ImVec4?](#q-how-can-i-use-my-own-maths-types-instead-of-imvec2imvec4) | -| [How can I interact with standard C++ types (such as std::string and std::vector)?](#q-how-can-i-interact-with-standard-c-types-such-as-stdstring-and-stdvector) | -| [How can I display custom shapes? (using low-level ImDrawList API)](#q-how-can-i-display-custom-shapes-using-low-level-imdrawlist-api) | -| **Q&A: Fonts, Text** | -| [How should I handle DPI in my application?](#q-how-should-i-handle-dpi-in-my-application) | -| [How can I load a different font than the default?](#q-how-can-i-load-a-different-font-than-the-default) | -| [How can I easily use icons in my application?](#q-how-can-i-easily-use-icons-in-my-application) | -| [How can I load multiple fonts?](#q-how-can-i-load-multiple-fonts) | -| [How can I display and input non-Latin characters such as Chinese, Japanese, Korean, Cyrillic?](#q-how-can-i-display-and-input-non-latin-characters-such-as-chinese-japanese-korean-cyrillic) | -| **Q&A: Concerns** | -| [Who uses Dear ImGui?](#q-who-uses-dear-imgui) | -| [Can you create elaborate/serious tools with Dear ImGui?](#q-can-you-create-elaborateserious-tools-with-dear-imgui) | -| [Can you reskin the look of Dear ImGui?](#q-can-you-reskin-the-look-of-dear-imgui) | -| [Why using C++ (as opposed to C)?](#q-why-using-c-as-opposed-to-c) | -| **Q&A: Community** | -| [How can I help?](#q-how-can-i-help) | - - -# Q&A: Basics - -### Q: Where is the documentation? - -**This library is poorly documented at the moment and expects the user to be acquainted with C/C++.** -- The [Wiki](https://github.com/ocornut/imgui/wiki) is a hub to many resources and links. -- Handy [Getting Started](https://github.com/ocornut/imgui/wiki/Getting-Started) guide to integrate Dear ImGui in an existing application. -- 20+ standalone example applications using e.g. OpenGL/DirectX are provided in the [examples/](https://github.com/ocornut/imgui/blob/master/examples/) folder to explain how to integrate Dear ImGui with your own engine/application. You can run those applications and explore them. -- See demo code in [imgui_demo.cpp](https://github.com/ocornut/imgui/blob/master/imgui_demo.cpp) and particularly the `ImGui::ShowDemoWindow()` function. The demo covers most features of Dear ImGui, so you can read the code and see its output. -- See documentation: [Backends](https://github.com/ocornut/imgui/blob/master/docs/BACKENDS.md), [Examples](https://github.com/ocornut/imgui/blob/master/docs/EXAMPLES.md), [Fonts](https://github.com/ocornut/imgui/blob/master/docs/FONTS.md). -- See documentation and comments at the top of [imgui.cpp](https://github.com/ocornut/imgui/blob/master/imgui.cpp) + general API comments in [imgui.h](https://github.com/ocornut/imgui/blob/master/imgui.h). -- The [Glossary](https://github.com/ocornut/imgui/wiki/Glossary) page may be useful. -- The [Issues](https://github.com/ocornut/imgui/issues) and [Discussions](https://github.com/ocornut/imgui/discussions) sections can be searched for past questions and issues. -- Your programming IDE is your friend, find the type or function declaration to find comments associated with it. -- The `ImGui::ShowMetricsWindow()` function exposes lots of internal information and tools. Although it is primarily designed as a debugging tool, having access to that information tends to help understands concepts. - -##### [Return to Index](#index) - ---- - -### Q. What is this library called? - -**This library is called Dear ImGui**. Please refer to it as Dear ImGui (not ImGui, not IMGUI). - -(The library misleadingly started its life in 2014 as "ImGui" due to the fact that I didn't give it a proper name when I released 1.0, and had no particular expectation that it would take off. However, the term IMGUI (immediate-mode graphical user interface) was coined before and is being used in variety of other situations e.g. Unity uses it own implementation of the IMGUI paradigm. To reduce the ambiguity without affecting existing code bases, I have decided in December 2015 a fully qualified name "Dear ImGui" for this library. - -##### [Return to Index](#index) - ---- - -### Q: Which version should I get? -I occasionally tag [Releases](https://github.com/ocornut/imgui/releases) but it is generally safe and recommended to sync to master/latest. The library is fairly stable and regressions tend to be fixed fast when reported. - -You may use the [docking](https://github.com/ocornut/imgui/tree/docking) branch which includes: -- [Docking features](https://github.com/ocornut/imgui/issues/2109) -- [Multi-viewport features](https://github.com/ocornut/imgui/issues/1542) - -Many projects are using this branch and it is kept in sync with master regularly. - -##### [Return to Index](#index) - ----- - -# Q&A: Integration - -### Q: How to get started? - -Read [Getting Started](https://github.com/ocornut/imgui/wiki/Getting-Started).
-Read [EXAMPLES.md](https://github.com/ocornut/imgui/blob/master/docs/EXAMPLES.md).
-Read [BACKENDS.md](https://github.com/ocornut/imgui/blob/master/docs/BACKENDS.md).
-Read `PROGRAMMER GUIDE` section of [imgui.cpp](https://github.com/ocornut/imgui/blob/master/imgui.cpp).
-The [Wiki](https://github.com/ocornut/imgui/wiki) is a hub to many resources and links. - -For first-time users having issues compiling/linking/running or issues loading fonts, please use [GitHub Discussions](https://github.com/ocornut/imgui/discussions). - -##### [Return to Index](#index) - ---- - -### Q: How can I tell whether to dispatch mouse/keyboard to Dear ImGui or my application? - -You can read the `io.WantCaptureMouse`, `io.WantCaptureKeyboard` and `io.WantTextInput` flags from the ImGuiIO structure. -- When `io.WantCaptureMouse` is set, you need to discard/hide the mouse inputs from your underlying application. -- When `io.WantCaptureKeyboard` is set, you need to discard/hide the keyboard inputs from your underlying application. -- When `io.WantTextInput` is set, you can notify your OS/engine to popup an on-screen keyboard, if available (e.g. on a mobile phone, or console OS). - -Important: you should always pass your mouse/keyboard inputs to Dear ImGui, regardless of the value `io.WantCaptureMouse`/`io.WantCaptureKeyboard`. This is because e.g. we need to detect that you clicked in the void to unfocus its own windows, and other reasons. - -```cpp -void MyLowLevelMouseButtonHandler(int button, bool down) -{ - // (1) ALWAYS forward mouse data to ImGui! This is automatic with default backends. With your own backend: - ImGuiIO& io = ImGui::GetIO(); - io.AddMouseButtonEvent(button, down); - - // (2) ONLY forward mouse data to your underlying app/game. - if (!io.WantCaptureMouse) - my_game->HandleMouseData(...); -} -``` - - -**Note:** The `io.WantCaptureMouse` is more correct that any manual attempt to "check if the mouse is hovering a window" (don't do that!). It handles mouse dragging correctly (both dragging that started over your application or over a Dear ImGui window) and handle e.g. popup and modal windows blocking inputs. - -**Note:** Those flags are updated by `ImGui::NewFrame()`. However it is generally more correct and easier that you poll flags from the previous frame, then submit your inputs, then call `NewFrame()`. If you attempt to do the opposite (which is generally harder) you are likely going to submit your inputs after `NewFrame()`, and therefore too late. - -**Note:** If you are using a touch device, you may find use for an early call to `UpdateHoveredWindowAndCaptureFlags()` to correctly dispatch your initial touch. We will work on better out-of-the-box touch support in the future. - -**Note:** Text input widget releases focus on the "KeyDown" event of the Return key, so the subsequent "KeyUp" event that your application receive will typically have `io.WantCaptureKeyboard == false`. Depending on your application logic it may or not be inconvenient to receive that KeyUp event. You might want to track which key-downs were targeted for Dear ImGui, e.g. with an array of bool, and filter out the corresponding key-ups.) - -##### [Return to Index](#index) - ---- - -### Q: How can I enable keyboard or gamepad controls? -- The gamepad/keyboard navigation is fairly functional and keeps being improved. The initial focus was to support game controllers, but keyboard is becoming increasingly and decently usable. Gamepad support is particularly useful to use Dear ImGui on a game console (e.g. PS4, Switch, XB1) without a mouse connected! -- Keyboard: set `io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard` to enable. -- Gamepad: set `io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad` to enable (with a supporting backend). -- See [Control Sheets for Gamepads](https://www.dearimgui.com/controls_sheets) (reference PNG/PSD for PS4, XB1, Switch gamepads). -- See `USING GAMEPAD/KEYBOARD NAVIGATION CONTROLS` section of [imgui.cpp](https://github.com/ocornut/imgui/blob/master/imgui.cpp) for more details. - -##### [Return to Index](#index) - ---- - -### Q: How can I use this on a machine without mouse, keyboard or screen? (input share, remote display) -- You can share your computer mouse seamlessly with your console/tablet/phone using solutions such as [Synergy](https://symless.com/synergy) -This is the preferred solution for developer productivity. -In particular, the [micro-synergy-client repository](https://github.com/symless/micro-synergy-client) has simple -and portable source code (uSynergy.c/.h) for a small embeddable client that you can use on any platform to connect -to your host computer, based on the Synergy 1.x protocol. Make sure you download the Synergy 1 server on your computer. -Console SDK also sometimes provide equivalent tooling or wrapper for Synergy-like protocols. -- Game console users: consider emulating a mouse cursor with DualShock4 touch pad or a spare analog stick as a mouse-emulation fallback. -- You may also use a third party solution such as [netImgui](https://github.com/sammyfreg/netImgui), [Remote ImGui](https://github.com/JordiRos/remoteimgui) or [imgui-ws](https://github.com/ggerganov/imgui-ws) which sends the vertices to render over the local network, allowing you to use Dear ImGui even on a screen-less machine. See [Wiki](https://github.com/ocornut/imgui/wiki) index for most details. -- For touch inputs, you can increase the hit box of widgets (via the `style.TouchPadding` setting) to accommodate for the lack of precision of touch inputs, but it is recommended you use a mouse or gamepad to allow optimizing for screen real-estate and precision. - -##### [Return to Index](#index) - ---- - -### Q: I integrated Dear ImGui in my engine and little squares are showing instead of text... -Your renderer backend is not using the font texture correctly or it hasn't been uploaded to the GPU. -- If this happens using the standard backends: A) have you modified the font atlas after `ImGui_ImplXXX_NewFrame()`? B) maybe the texture failed to upload, which **can if your texture atlas is too big**. Also see [docs/FONTS.md](https://github.com/ocornut/imgui/blob/master/docs/FONTS.md). -- If this happens with a custom backend: make sure you have uploaded the font texture to the GPU, that all shaders are rendering states are setup properly (e.g. texture is bound). Compare your code to existing backends and use a graphics debugger such as [RenderDoc](https://renderdoc.org) to debug your rendering states. - -##### [Return to Index](#index) - ---- - -### Q: I integrated Dear ImGui in my engine and some elements are clipping or disappearing when I move windows around... -### Q: I integrated Dear ImGui in my engine and some elements are displaying outside their expected windows boundaries... -You are probably mishandling the clipping rectangles in your render function. -Each draw command needs the triangle rendered using the clipping rectangle provided in the ImDrawCmd structure (`ImDrawCmd->CllipRect`). -Rectangles provided by Dear ImGui are defined as -`(x1=left,y1=top,x2=right,y2=bottom)` -and **NOT** as -`(x1,y1,width,height)`. -Refer to rendering backends in the [backends/](https://github.com/ocornut/imgui/tree/master/backends) folder for references of how to handle the `ClipRect` field. -For example, the [DirectX11 backend](https://github.com/ocornut/imgui/blob/master/backends/imgui_impl_dx11.cpp) does this: -```cpp -// Project scissor/clipping rectangles into framebuffer space -ImVec2 clip_off = draw_data->DisplayPos; -ImVec2 clip_min(pcmd->ClipRect.x - clip_off.x, pcmd->ClipRect.y - clip_off.y); -ImVec2 clip_max(pcmd->ClipRect.z - clip_off.x, pcmd->ClipRect.w - clip_off.y); -if (clip_max.x <= clip_min.x || clip_max.y <= clip_min.y) - continue; - -// Apply scissor/clipping rectangle -const D3D11_RECT r = { (LONG)clip_min.x, (LONG)clip_min.y, (LONG)clip_max.x, (LONG)clip_max.y }; -ctx->RSSetScissorRects(1, &r); -``` - -##### [Return to Index](#index) - ---- - -# Q&A: Usage - -### Q: About the ID Stack system... -### Q: Why is my widget not reacting when I click on it? -### Q: How can I have widgets with an empty label? -### Q: How can I have multiple widgets with the same label? -### Q: How can I have multiple windows with the same label? - -A primer on labels and the ID Stack... - -Dear ImGui internally needs to uniquely identify UI elements. -Elements that are typically not clickable (such as calls to the Text functions) don't need an ID. -Interactive widgets (such as calls to Button buttons) need a unique ID. - -**Unique IDs are used internally to track active widgets and occasionally associate state to widgets.
-Unique IDs are implicitly built from the hash of multiple elements that identify the "path" to the UI element.** - -Since Dear ImGui 1.85, you can use `Demo>Tools>ID Stack Tool` or call `ImGui::ShowIDStackToolWindow()`. The tool display intermediate values leading to the creation of a unique ID, making things easier to debug and understand. - -![Stack tool](https://user-images.githubusercontent.com/8225057/136235657-a0ea5665-dcd1-423f-9be6-dc3f8ced8f12.png) - -- Unique ID are often derived from a string label and at minimum scoped within their host window: -```cpp -Begin("MyWindow"); -Button("OK"); // Label = "OK", ID = hash of ("MyWindow", "OK") -Button("Cancel"); // Label = "Cancel", ID = hash of ("MyWindow", "Cancel") -End(); -``` -- Other elements such as tree nodes, etc. also pushes to the ID stack: -```cpp -Begin("MyWindow"); -if (TreeNode("MyTreeNode")) -{ - Button("OK"); // Label = "OK", ID = hash of ("MyWindow", "MyTreeNode", "OK") - TreePop(); -} -End(); -``` -- Two items labeled "OK" in different windows or different tree locations won't collide: -```cpp -Begin("MyFirstWindow"); -Button("OK"); // Label = "OK", ID = hash of ("MyFirstWindow", "OK") -End(); -Begin("MyOtherWindow"); -Button("OK"); // Label = "OK", ID = hash of ("MyOtherWindow", "OK") -End(); -``` - -- If you have a same ID twice in the same location, you'll have a conflict: -```cpp -Begin("MyWindow"); -Button("OK"); -Button("OK"); // ERROR: ID collision with the first button! Interacting with either button will trigger the first one. -Button(""); // ERROR: ID collision with Begin("MyWindow")! -End(); -``` -Fear not! This is easy to solve and there are many ways to solve it! - -- Solving ID conflict in a simple/local context: -When passing a label you can optionally specify extra ID information within the string itself. -Use "##" to pass a complement to the ID that won't be visible to the end-user. -This helps solve the simple collision cases when you know e.g. at compilation time which items -are going to be created: -```cpp -Begin("MyWindow"); -Button("Play"); // Label = "Play", ID = hash of ("MyWindow", "Play") -Button("Play##foo1"); // Label = "Play", ID = hash of ("MyWindow", "Play##foo1") // Different from other buttons -Button("Play##foo2"); // Label = "Play", ID = hash of ("MyWindow", "Play##foo2") // Different from other buttons -Button("##foo"); // Label = "", ID = hash of ("MyWindow", "##foo") // Different from window -End(); -``` -- If you want to completely hide the label, but still need an ID: -```cpp -Checkbox("##On", &b); // Label = "", ID = hash of (..., "##On") // No visible label, just a checkbox! -``` -- Occasionally/rarely you might want to change a label while preserving a constant ID. This allows -you to animate labels. For example, you may want to include varying information in a window title bar, -but windows are uniquely identified by their ID. Use "###" to pass a label that isn't part of ID: -```cpp -Button("Hello###ID"); // Label = "Hello", ID = hash of (..., "###ID") -Button("World###ID"); // Label = "World", ID = hash of (..., "###ID") // Same ID, different label - -sprintf(buf, "My game (%f FPS)###MyGame", fps); -Begin(buf); // Variable title, ID = hash of "MyGame" -``` -- Solving ID conflict in a more general manner: -Use `PushID()` / `PopID()` to create scopes and manipulate the ID stack, as to avoid ID conflicts -within the same window. This is the most convenient way of distinguishing ID when iterating and -creating many UI elements programmatically. -You can push a pointer, a string, or an integer value into the ID stack. -Remember that IDs are formed from the concatenation of _everything_ pushed into the ID stack. -At each level of the stack, we store the seed used for items at this level of the ID stack. -```cpp -Begin("Window"); -for (int i = 0; i < 100; i++) -{ - PushID(i); // Push i to the id tack - Button("Click"); // Label = "Click", ID = hash of ("Window", i, "Click") - PopID(); -} -for (int i = 0; i < 100; i++) -{ - MyObject* obj = Objects[i]; - PushID(obj); - Button("Click"); // Label = "Click", ID = hash of ("Window", obj pointer, "Click") - PopID(); -} -for (int i = 0; i < 100; i++) -{ - MyObject* obj = Objects[i]; - PushID(obj->Name); - Button("Click"); // Label = "Click", ID = hash of ("Window", obj->Name, "Click") - PopID(); -} -End(); -``` -- You can stack multiple prefixes into the ID stack: -```cpp -Button("Click"); // Label = "Click", ID = hash of (..., "Click") -PushID("node"); - Button("Click"); // Label = "Click", ID = hash of (..., "node", "Click") - PushID(my_ptr); - Button("Click"); // Label = "Click", ID = hash of (..., "node", my_ptr, "Click") - PopID(); -PopID(); -``` -- Tree nodes implicitly create a scope for you by calling `PushID()`: -```cpp -Button("Click"); // Label = "Click", ID = hash of (..., "Click") -if (TreeNode("node")) // <-- this function call will do a PushID() for you (unless instructed not to, with a special flag) -{ - Button("Click"); // Label = "Click", ID = hash of (..., "node", "Click") - TreePop(); -} -``` - -When working with trees, IDs are used to preserve the open/close state of each tree node. -Depending on your use cases you may want to use strings, indices, or pointers as ID. -- e.g. when following a single pointer that may change over time, using a static string as ID -will preserve your node open/closed state when the targeted object change. -- e.g. when displaying a list of objects, using indices or pointers as ID will preserve the -node open/closed state differently. See what makes more sense in your situation! - -##### [Return to Index](#index) - ---- - -### Q: How can I display an image? What is ImTextureID, how does it work? - -Short explanation: -- Refer to [Image Loading and Displaying Examples](https://github.com/ocornut/imgui/wiki/Image-Loading-and-Displaying-Examples) on the [Wiki](https://github.com/ocornut/imgui/wiki). -- You may use functions such as `ImGui::Image()`, `ImGui::ImageButton()` or lower-level `ImDrawList::AddImage()` to emit draw calls that will use your own textures. -- Actual textures are identified in a way that is up to the user/engine. Those identifiers are stored and passed as ImTextureID (void*) value. -- Loading image files from the disk and turning them into a texture is not within the scope of Dear ImGui (for a good reason). - -**Please read documentations or tutorials on your graphics API to understand how to display textures on the screen before moving onward.** - -Long explanation: -- Dear ImGui's job is to create "meshes", defined in a renderer-agnostic format made of draw commands and vertices. At the end of the frame, those meshes (ImDrawList) will be displayed by your rendering function. They are made up of textured polygons and the code to render them is generally fairly short (a few dozen lines). In the examples/ folder, we provide functions for popular graphics APIs (OpenGL, DirectX, etc.). -- Each rendering function decides on a data type to represent "textures". The concept of what is a "texture" is entirely tied to your underlying engine/graphics API. - We carry the information to identify a "texture" in the ImTextureID type. -ImTextureID is nothing more than a void*, aka 4/8 bytes worth of data: just enough to store one pointer or integer of your choice. -Dear ImGui doesn't know or understand what you are storing in ImTextureID, it merely passes ImTextureID values until they reach your rendering function. -- In the [examples/](https://github.com/ocornut/imgui/tree/master/examples) backends, for each graphics API we decided on a type that is likely to be a good representation for specifying an image from the end-user perspective. This is what the _examples_ rendering functions are using: -```cpp -OpenGL: -- ImTextureID = GLuint -- See ImGui_ImplOpenGL3_RenderDrawData() function in imgui_impl_opengl3.cpp -``` -```cpp -DirectX9: -- ImTextureID = LPDIRECT3DTEXTURE9 -- See ImGui_ImplDX9_RenderDrawData() function in imgui_impl_dx9.cpp -``` -```cpp -DirectX11: -- ImTextureID = ID3D11ShaderResourceView* -- See ImGui_ImplDX11_RenderDrawData() function in imgui_impl_dx11.cpp -``` -```cpp -DirectX12: -- ImTextureID = D3D12_GPU_DESCRIPTOR_HANDLE -- See ImGui_ImplDX12_RenderDrawData() function in imgui_impl_dx12.cpp -``` -For example, in the OpenGL example backend we store raw OpenGL texture identifier (GLuint) inside ImTextureID. -Whereas in the DirectX11 example backend we store a pointer to ID3D11ShaderResourceView inside ImTextureID, which is a higher-level structure tying together both the texture and information about its format and how to read it. - -- If you have a custom engine built over e.g. OpenGL, instead of passing GLuint around you may decide to use a high-level data type to carry information about the texture as well as how to display it (shaders, etc.). The decision of what to use as ImTextureID can always be made better by knowing how your codebase is designed. If your engine has high-level data types for "textures" and "material" then you may want to use them. -If you are starting with OpenGL or DirectX or Vulkan and haven't built much of a rendering engine over them, keeping the default ImTextureID representation suggested by the example backends is probably the best choice. -(Advanced users may also decide to keep a low-level type in ImTextureID, use ImDrawList callback and pass information to their renderer) - -User code may do: -```cpp -// Cast our texture type to ImTextureID / void* -MyTexture* texture = g_CoffeeTableTexture; -ImGui::Image((void*)texture, ImVec2(texture->Width, texture->Height)); -``` -The renderer function called after ImGui::Render() will receive that same value that the user code passed: -```cpp -// Cast ImTextureID / void* stored in the draw command as our texture type -MyTexture* texture = (MyTexture*)pcmd->GetTexID(); -MyEngineBindTexture2D(texture); -``` -Once you understand this design, you will understand that loading image files and turning them into displayable textures is not within the scope of Dear ImGui. -This is by design and is a good thing because it means your code has full control over your data types and how you display them. -If you want to display an image file (e.g. PNG file) on the screen, please refer to documentation and tutorials for the graphics API you are using. - -Refer to [Image Loading and Displaying Examples](https://github.com/ocornut/imgui/wiki/Image-Loading-and-Displaying-Examples) on the [Wiki](https://github.com/ocornut/imgui/wiki) to find simplified examples for loading textures with OpenGL, DirectX9 and DirectX11. - -C/C++ tip: a void* is pointer-sized storage. You may safely store any pointer or integer into it by casting your value to ImTextureID / void*, and vice-versa. -Because both end-points (user code and rendering function) are under your control, you know exactly what is stored inside the ImTextureID / void*. -Here are some examples: -```cpp -GLuint my_tex = XXX; -void* my_void_ptr; -my_void_ptr = (void*)(intptr_t)my_tex; // cast a GLuint into a void* (we don't take its address! we literally store the value inside the pointer) -my_tex = (GLuint)(intptr_t)my_void_ptr; // cast a void* into a GLuint - -ID3D11ShaderResourceView* my_dx11_srv = XXX; -void* my_void_ptr; -my_void_ptr = (void*)my_dx11_srv; // cast a ID3D11ShaderResourceView* into an opaque void* -my_dx11_srv = (ID3D11ShaderResourceView*)my_void_ptr; // cast a void* into a ID3D11ShaderResourceView* -``` -Finally, you may call `ImGui::ShowMetricsWindow()` to explore/visualize/understand how the ImDrawList are generated. - -##### [Return to Index](#index) - ---- - -### Q: How can I use maths operators with ImVec2? - -We do not export maths operators by default in imgui.h in order to not conflict with the use of your own maths types and maths operators. As a convenience, you may use `#defne IMGUI_DEFINE_MATH_OPERATORS` + `#include "imgui.h"` to access our basic maths operators. - -##### [Return to Index](#index) - ---- - -### Q: How can I use my own maths types instead of ImVec2/ImVec4? - -You can setup your [imconfig.h](https://github.com/ocornut/imgui/blob/master/imconfig.h) file with `IM_VEC2_CLASS_EXTRA`/`IM_VEC4_CLASS_EXTRA` macros to add implicit type conversions to our own maths types. -This way you will be able to use your own types everywhere, e.g. passing `MyVector2` or `glm::vec2` to ImGui functions instead of `ImVec2`. - -##### [Return to Index](#index) - ---- - -### Q: How can I interact with standard C++ types (such as std::string and std::vector)? -- Being highly portable (backends/bindings for several languages, frameworks, programming styles, obscure or older platforms/compilers), and aiming for compatibility & performance suitable for every modern real-time game engine, Dear ImGui does not use any of std C++ types. We use raw types (e.g. char* instead of std::string) because they adapt to more use cases. -- To use ImGui::InputText() with a std::string or any resizable string class, see [misc/cpp/imgui_stdlib.h](https://github.com/ocornut/imgui/blob/master/misc/cpp/imgui_stdlib.h). -- To use combo boxes and list boxes with `std::vector` or any other data structure: the `BeginCombo()/EndCombo()` API -lets you iterate and submit items yourself, so does the `ListBoxHeader()/ListBoxFooter()` API. -Prefer using them over the old and awkward `Combo()/ListBox()` api. -- Generally for most high-level types you should be able to access the underlying data type. -You may write your own one-liner wrappers to facilitate user code (tip: add new functions in ImGui:: namespace from your code). -- Dear ImGui applications often need to make intensive use of strings. It is expected that many of the strings you will pass -to the API are raw literals (free in C/C++) or allocated in a manner that won't incur a large cost on your application. -Please bear in mind that using `std::string` on applications with a large amount of UI may incur unsatisfactory performances. -Modern implementations of `std::string` often include small-string optimization (which is often a local buffer) but those -are not configurable and not the same across implementations. -- If you are finding your UI traversal cost to be too large, make sure your string usage is not leading to an excessive amount -of heap allocations. Consider using literals, statically sized buffers, and your own helper functions. A common pattern -is that you will need to build lots of strings on the fly, and their maximum length can be easily scoped ahead. -One possible implementation of a helper to facilitate printf-style building of strings: https://github.com/ocornut/Str -This is a small helper where you can instance strings with configurable local buffers length. Many game engines will -provide similar or better string helpers. - -##### [Return to Index](#index) - ---- - -### Q: How can I display custom shapes? (using low-level ImDrawList API) - -- You can use the low-level `ImDrawList` api to render shapes within a window. -```cpp -ImGui::Begin("My shapes"); - -ImDrawList* draw_list = ImGui::GetWindowDrawList(); - -// Get the current ImGui cursor position -ImVec2 p = ImGui::GetCursorScreenPos(); - -// Draw a red circle -draw_list->AddCircleFilled(ImVec2(p.x + 50, p.y + 50), 30.0f, IM_COL32(255, 0, 0, 255)); - -// Draw a 3 pixel thick yellow line -draw_list->AddLine(ImVec2(p.x, p.y), ImVec2(p.x + 100.0f, p.y + 100.0f), IM_COL32(255, 255, 0, 255), 3.0f); - -// Advance the ImGui cursor to claim space in the window (otherwise the window will appear small and needs to be resized) -ImGui::Dummy(ImVec2(200, 200)); - -ImGui::End(); -``` -![ImDrawList usage](https://raw.githubusercontent.com/wiki/ocornut/imgui/tutorials/CustomRendering01.png) - -- Refer to "Demo > Examples > Custom Rendering" in the demo window and read the code of `ShowExampleAppCustomRendering()` in `imgui_demo.cpp` from more examples. -- To generate colors: you can use the macro `IM_COL32(255,255,255,255)` to generate them at compile time, or use `ImGui::GetColorU32(IM_COL32(255,255,255,255))` or `ImGui::GetColorU32(ImVec4(1.0f,1.0f,1.0f,1.0f))` to generate a color that is multiplied by the current value of `style.Alpha`. -- Math operators: if you have setup `IM_VEC2_CLASS_EXTRA` in `imconfig.h` to bind your own math types, you can use your own math types and their natural operators instead of ImVec2. ImVec2 by default doesn't export any math operators in the public API. You may use `#define IMGUI_DEFINE_MATH_OPERATORS` `#include "imgui.h"` to use our math operators, but instead prefer using your own math library and set it up in `imconfig.h`. -- You can use `ImGui::GetBackgroundDrawList()` or `ImGui::GetForegroundDrawList()` to access draw lists which will be displayed behind and over every other Dear ImGui window (one bg/fg drawlist per viewport). This is very convenient if you need to quickly display something on the screen that is not associated with a Dear ImGui window. -- You can also create your own empty window and draw inside it. Call Begin() with the NoBackground | NoDecoration | NoSavedSettings | NoInputs flags (The `ImGuiWindowFlags_NoDecoration` flag itself is a shortcut for NoTitleBar | NoResize | NoScrollbar | NoCollapse). Then you can retrieve the ImDrawList* via `GetWindowDrawList()` and draw to it in any way you like. -- You can create your own ImDrawList instance. You'll need to initialize them with `ImGui::GetDrawListSharedData()`, or create your own instancing `ImDrawListSharedData`, and then call your renderer function with your own ImDrawList or ImDrawData data. -- Looking for fun? The [ImDrawList coding party 2020](https://github.com/ocornut/imgui/issues/3606) thread is full of "don't do this at home" extreme uses of the ImDrawList API. - -##### [Return to Index](#index) - ---- - -# Q&A: Fonts, Text - -### Q: How should I handle DPI in my application? - -The short answer is: obtain the desired DPI scale, load your fonts resized with that scale (always round down fonts size to the nearest integer), and scale your Style structure accordingly using `style.ScaleAllSizes()`. - -Your application may want to detect DPI change and reload the fonts and reset style between frames. - -Your ui code should avoid using hardcoded constants for size and positioning. Prefer to express values as multiple of reference values such as `ImGui::GetFontSize()` or `ImGui::GetFrameHeight()`. So e.g. instead of seeing a hardcoded height of 500 for a given item/window, you may want to use `30*ImGui::GetFontSize()` instead. - -Down the line Dear ImGui will provide a variety of standardized reference values to facilitate using this. - -Applications in the `examples/` folder are not DPI aware partly because they are unable to load a custom font from the file-system (may change that in the future). - -The reason DPI is not auto-magically solved in stock examples is that we don't yet have a satisfying solution for the "multi-dpi" problem (using the `docking` branch: when multiple viewport windows are over multiple monitors using different DPI scales). The current way to handle this on the application side is: -- Create and maintain one font atlas per active DPI scale (e.g. by iterating `platform_io.Monitors[]` before `NewFrame()`). -- Hook `platform_io.OnChangedViewport()` to detect when a `Begin()` call makes a Dear ImGui window change monitor (and therefore DPI). -- In the hook: swap atlas, swap style with correctly sized one, and remap the current font from one atlas to the other (you may need to maintain a remapping table of your fonts at varying DPI scales). - -This approach is relatively easy and functional but comes with two issues: -- It's not possibly to reliably size or position a window ahead of `Begin()` without knowing on which monitor it'll land. -- Style override may be lost during the `Begin()` call crossing monitor boundaries. You may need to do some custom scaling mumbo-jumbo if you want your `OnChangedViewport()` handler to preserve style overrides. - -Please note that if you are not using multi-viewports with multi-monitors using different DPI scales, you can ignore that and use the simpler technique recommended at the top. - -On Windows, in addition to scaling the font size (make sure to round to an integer) and using `style.ScaleAllSizes()`, you will need to inform Windows that your application is DPI aware. If this is not done, Windows will scale the application window and the UI text will be blurry. Potential solutions to indicate DPI awareness on Windows are: - -- For SDL: the flag `SDL_WINDOW_ALLOW_HIGHDPI` needs to be passed to `SDL_CreateWindow()``. -- For GLFW: this is done automatically. -- For other Windows projects with other backends, or wrapper projects: - - We provide a `ImGui_ImplWin32_EnableDpiAwareness()` helper method in the Win32 backend. - - Use an [application manifest file](https://learn.microsoft.com/en-us/windows/win32/hidpi/setting-the-default-dpi-awareness-for-a-process) to set the `` property. - -### Q: How can I load a different font than the default? -Use the font atlas to load the TTF/OTF file you want: - -```cpp -ImGuiIO& io = ImGui::GetIO(); -io.Fonts->AddFontFromFileTTF("myfontfile.ttf", size_in_pixels); -io.Fonts->GetTexDataAsRGBA32() or GetTexDataAsAlpha8() -``` - -Default is ProggyClean.ttf, monospace, rendered at size 13, embedded in dear imgui's source code. - -(Tip: monospace fonts are convenient because they allow to facilitate horizontal alignment directly at the string level.) - -(Read the [docs/FONTS.md](https://github.com/ocornut/imgui/blob/master/docs/FONTS.md) file for more details about font loading.) - -New programmers: remember that in C/C++ and most programming languages if you want to use a -backslash \ within a string literal, you need to write it double backslash "\\": - -```cpp -io.Fonts->AddFontFromFileTTF("MyFolder\MyFont.ttf", size); // WRONG (you are escaping the M here!) -io.Fonts->AddFontFromFileTTF("MyFolder\\MyFont.ttf", size); // CORRECT (Windows only) -io.Fonts->AddFontFromFileTTF("MyFolder/MyFont.ttf", size); // ALSO CORRECT -``` - -##### [Return to Index](#index) - ---- - -### Q: How can I easily use icons in my application? -The most convenient and practical way is to merge an icon font such as FontAwesome inside your -main font. Then you can refer to icons within your strings. -Read the [docs/FONTS.md](https://github.com/ocornut/imgui/blob/master/docs/FONTS.md) file for more details about icons font loading. - -##### [Return to Index](#index) - ---- - -### Q: How can I load multiple fonts? - -Use the font atlas to pack them into a single texture. Read [docs/FONTS.md](https://github.com/ocornut/imgui/blob/master/docs/FONTS.md) for more details. - -##### [Return to Index](#index) - ---- - -### Q: How can I display and input non-Latin characters such as Chinese, Japanese, Korean, Cyrillic? -When loading a font, pass custom Unicode ranges to specify the glyphs to load. - -```cpp -// Add default Japanese ranges -io.Fonts->AddFontFromFileTTF("myfontfile.ttf", size_in_pixels, nullptr, io.Fonts->GetGlyphRangesJapanese()); - -// Or create your own custom ranges (e.g. for a game you can feed your entire game script and only build the characters the game need) -ImVector ranges; -ImFontGlyphRangesBuilder builder; -builder.AddText("Hello world"); // Add a string (here "Hello world" contains 7 unique characters) -builder.AddChar(0x7262); // Add a specific character -builder.AddRanges(io.Fonts->GetGlyphRangesJapanese()); // Add one of the default ranges -builder.BuildRanges(&ranges); // Build the final result (ordered ranges with all the unique characters submitted) -io.Fonts->AddFontFromFileTTF("myfontfile.ttf", 16.0f, nullptr, ranges.Data); -``` - -All your strings need to use UTF-8 encoding. -You need to tell your compiler to use UTF-8, or in C++11 you can encode a string literal in UTF-8 by using the u8"hello" syntax. -Specifying literal in your source code using a local code page (such as CP-923 for Japanese or CP-1251 for Cyrillic) will NOT work! -See [About UTF-8 Encoding](https://github.com/ocornut/imgui/blob/master/docs/FONTS.md#about-utf-8-encoding) section -of [FONTS.md](https://github.com/ocornut/imgui/blob/master/docs/FONTS.md) for details about UTF-8 Encoding. - -Text input: it is up to your application to pass the right character code by calling `io.AddInputCharacter()`. -The applications in examples/ are doing that. -Windows: you can use the WM_CHAR or WM_UNICHAR or WM_IME_CHAR message (depending if your app is built using Unicode or MultiByte mode). -You may also use `MultiByteToWideChar()` or `ToUnicode()` to retrieve Unicode codepoints from MultiByte characters or keyboard state. -Windows: if your language is relying on an Input Method Editor (IME), you can write your HWND to ImGui::GetMainViewport()->PlatformHandleRaw -for the default implementation of io.SetPlatformImeDataFn() to set your Microsoft IME position correctly. - -##### [Return to Index](#index) - ---- - -# Q&A: Concerns - -### Q: Who uses Dear ImGui? - -You may take a look at: - -- [Quotes](https://github.com/ocornut/imgui/wiki/Quotes) -- [Software using Dear ImGui](https://github.com/ocornut/imgui/wiki/Software-using-dear-imgui) -- [Sponsors](https://github.com/ocornut/imgui/wiki/Sponsors) -- [Gallery](https://github.com/ocornut/imgui/issues/6897) - -##### [Return to Index](#index) - ---- - -### Q: Can you create elaborate/serious tools with Dear ImGui? - -Yes. People have written game editors, data browsers, debuggers, profilers, and all sorts of non-trivial tools with the library. In my experience, the simplicity of the API is very empowering. Your UI runs close to your live data. Make the tools always-on and everybody in the team will be inclined to create new tools (as opposed to more "offline" UI toolkits where only a fraction of your team effectively creates tools). The list of sponsors below is also an indicator that serious game teams have been using the library. - -Dear ImGui is very programmer centric and the immediate-mode GUI paradigm might require you to readjust some habits before you can realize its full potential. Dear ImGui is about making things that are simple, efficient, and powerful. - -Dear ImGui is built to be efficient and scalable toward the needs for AAA-quality applications running all day. The IMGUI paradigm offers different opportunities for optimization than the more typical RMGUI paradigm. - -##### [Return to Index](#index) - ---- - -### Q: Can you reskin the look of Dear ImGui? - -Somewhat. You can alter the look of the interface to some degree: changing colors, sizes, padding, rounding, and fonts. However, as Dear ImGui is designed and optimized to create debug tools, the amount of skinning you can apply is limited. There is only so much you can stray away from the default look and feel of the interface. Dear ImGui is NOT designed to create a user interface for games, although with ingenious use of the low-level API you can do it. - -A reasonably skinned application may look like (screenshot from [#2529](https://github.com/ocornut/imgui/issues/2529#issuecomment-524281119)): -![minipars](https://user-images.githubusercontent.com/314805/63589441-d9794f00-c5b1-11e9-8d96-cfc1b93702f7.png) - -##### [Return to Index](#index) - ---- - -### Q: Why using C++ (as opposed to C)? - -Dear ImGui takes advantage of a few C++ language features for convenience but nothing anywhere Boost insanity/quagmire. Dear ImGui doesn't use any C++ header file. Dear ImGui uses a very small subset of C++11 features. In particular, function overloading and default parameters are used to make the API easier to use and code terser. Doing so I believe the API is sitting on a sweet spot and giving up on those features would make the API more cumbersome. Other features such as namespace, constructors, and templates (in the case of the ImVector<> class) are also relied on as a convenience. - -There is an auto-generated [c-api for Dear ImGui (cimgui)](https://github.com/cimgui/cimgui) by Sonoro1234 and Stephan Dilly. It is designed for creating bindings to other languages. If possible, I would suggest using your target language functionalities to try replicating the function overloading and default parameters used in C++ else the API may be harder to use. Also see [Bindings](https://github.com/ocornut/imgui/wiki/Bindings) for various third-party bindings. - -##### [Return to Index](#index) - ---- - -# Q&A: Community - -### Q: How can I help? -- Businesses: please reach out to `omar AT dearimgui.com` if you work in a place using Dear ImGui! We can discuss ways for your company to fund development via invoiced technical support, maintenance, or sponsoring contacts. This is among the most useful thing you can do for Dear ImGui. With increased funding, we can hire more people to work on this project. -- Individuals: you can support continued maintenance and development via PayPal donations. See [README](https://github.com/ocornut/imgui/blob/master/docs/README.md). -- If you are experienced with Dear ImGui and C++, look at [GitHub Issues](https://github.com/ocornut/imgui/issues), [GitHub Discussions](https://github.com/ocornut/imgui/discussions), the [Wiki](https://github.com/ocornut/imgui/wiki), read [docs/TODO.txt](https://github.com/ocornut/imgui/blob/master/docs/TODO.txt), and see how you want to help and can help! -- Disclose your usage of Dear ImGui via a dev blog post, a tweet, a screenshot, a mention somewhere, etc. -You may post screenshots or links in the [gallery threads](https://github.com/ocornut/imgui/issues/6897). Visuals are ideal as they inspire other programmers. Disclosing your use of Dear ImGui helps the library grow credibility, and helps other teams and programmers with taking decisions. -- If you have issues or if you need to hack into the library, even if you don't expect any support it is useful that you share your issues or sometimes incomplete PR. - -##### [Return to Index](#index) - diff --git a/app/jni/src/libultraship/extern/ImGui/docs/FONTS.md b/app/jni/src/libultraship/extern/ImGui/docs/FONTS.md deleted file mode 100644 index b0876a3..0000000 --- a/app/jni/src/libultraship/extern/ImGui/docs/FONTS.md +++ /dev/null @@ -1,502 +0,0 @@ -_(You may browse this at https://github.com/ocornut/imgui/blob/master/docs/FONTS.md or view this file with any Markdown viewer)_ - -## Dear ImGui: Using Fonts - -The code in imgui.cpp embeds a copy of 'ProggyClean.ttf' (by Tristan Grimmer), -a 13 pixels high, pixel-perfect font used by default. We embed it in the source code so you can use Dear ImGui without any file system access. ProggyClean does not scale smoothly, therefore it is recommended that you load your own file when using Dear ImGui in an application aiming to look nice and wanting to support multiple resolutions. - -You may also load external .TTF/.OTF files. -In the [misc/fonts/](https://github.com/ocornut/imgui/tree/master/misc/fonts) folder you can find a few suggested fonts, provided as a convenience. - -**Also read the FAQ:** https://www.dearimgui.com/faq (there is a Fonts section!) - -## Index -- [Troubleshooting](#troubleshooting) -- [How should I handle DPI in my application?](#how-should-i-handle-dpi-in-my-application) -- [Fonts Loading Instructions](#fonts-loading-instructions) -- [Loading Font Data from Memory](#loading-font-data-from-memory) -- [Loading Font Data Embedded In Source Code](#loading-font-data-embedded-in-source-code) -- [Using Icon Fonts](#using-icon-fonts) -- [Using FreeType Rasterizer (imgui_freetype)](#using-freetype-rasterizer-imgui_freetype) -- [Using Colorful Glyphs/Emojis](#using-colorful-glyphsemojis) -- [Using Custom Glyph Ranges](#using-custom-glyph-ranges) -- [Using Custom Colorful Icons](#using-custom-colorful-icons) -- [About Filenames](#about-filenames) -- [About UTF-8 Encoding](#about-utf-8-encoding) -- [Debug Tools](#debug-tools) -- [Credits/Licenses For Fonts Included In Repository](#creditslicenses-for-fonts-included-in-repository) -- [Font Links](#font-links) - ---------------------------------------- - -## Troubleshooting - -**A vast majority of font and text related issues encountered comes from 4 things:** - -### (1) Invalid filename due to use of `\` or unexpected working directory. - -See [About Filenames](#about-filenames). AddFontXXX functions should assert if the filename is incorrect. - -### (2) Invalid UTF-8 encoding of your non-ASCII strings. - -See [About UTF-8 Encoding](#about-utf-8-encoding). Use the encoding viewer to confirm encoding of string literal in your source code is correct. - -### (3) Missing glyph ranges. - -You need to load a font with explicit glyph ranges if you want to use non-ASCII characters. See [Fonts Loading Instructions](#fonts-loading-instructions). Use [Debug Tools](#debug-tools) confirm loaded fonts and loaded glyph ranges. - -This is a current constraint of Dear ImGui (which we will lift in the future): when loading a font you need to specify which characters glyphs to load. -All loaded fonts glyphs are rendered into a single texture atlas ahead of time. Calling either of `io.Fonts->GetTexDataAsAlpha8()`, `io.Fonts->GetTexDataAsRGBA32()` or `io.Fonts->Build()` will build the atlas. This is generally called by the Renderer backend, e.g. `ImGui_ImplDX11_NewFrame()` calls it. **If you use custom glyphs ranges, make sure the array is persistent** and available during the calls to `GetTexDataAsAlpha8()/GetTexDataAsRGBA32()/Build()`. - -### (4) Font atlas texture fails to upload to GPU. - -This is often of byproduct of point 3. If you have large number of glyphs or multiple fonts, the texture may become too big for your graphics API. **The typical result of failing to upload a texture is if every glyph or everything appears as empty black or white rectangle.** Mind the fact that some graphics drivers have texture size limitation. If you are building a PC application, mind the fact that your users may use hardware with lower limitations than yours. - -Some solutions: -- You may reduce oversampling, e.g. `font_config.OversampleH = 1`, this will half your texture size for a quality looss. - Note that while OversampleH = 2 looks visibly very close to 3 in most situations, with OversampleH = 1 the quality drop will be noticeable. Read about oversampling [here](https://github.com/nothings/stb/blob/master/tests/oversample). -- Reduce glyphs ranges by calculating them from source localization data. - You can use the `ImFontGlyphRangesBuilder` for this purpose and rebuilding your atlas between frames when new characters are needed. This will be the biggest win! -- Set `io.Fonts.Flags |= ImFontAtlasFlags_NoPowerOfTwoHeight;` to disable rounding the texture height to the next power of two. -- Set `io.Fonts.TexDesiredWidth` to specify a texture width to reduce maximum texture height (see comment in `ImFontAtlas::Build()` function). - -##### [Return to Index](#index) - ---------------------------------------- - -## How should I handle DPI in my application? - -See [FAQ entry](https://github.com/ocornut/imgui/blob/master/docs/FAQ.md#q-how-should-i-handle-dpi-in-my-application). - -##### [Return to Index](#index) - ---------------------------------------- - -## Fonts Loading Instructions - -**Load default font:** -```cpp -ImGuiIO& io = ImGui::GetIO(); -io.Fonts->AddFontDefault(); -``` - -**Load .TTF/.OTF file with:** -```cpp -ImGuiIO& io = ImGui::GetIO(); -io.Fonts->AddFontFromFileTTF("font.ttf", size_pixels); -``` -If you get an assert stating "Could not load font file!", your font filename is likely incorrect. Read [About filenames](#about-filenames) carefully. - -**Load multiple fonts:** -```cpp -// Init -ImGuiIO& io = ImGui::GetIO(); -ImFont* font1 = io.Fonts->AddFontFromFileTTF("font.ttf", size_pixels); -ImFont* font2 = io.Fonts->AddFontFromFileTTF("anotherfont.otf", size_pixels); -``` - -In your application loop, select which font to use: -```cpp -ImGui::Text("Hello"); // use the default font (which is the first loaded font) -ImGui::PushFont(font2); -ImGui::Text("Hello with another font"); -ImGui::PopFont(); -``` - -**For advanced options create a ImFontConfig structure and pass it to the AddFont() function (it will be copied internally):** -```cpp -ImFontConfig config; -config.OversampleH = 2; -config.OversampleV = 1; -config.GlyphExtraSpacing.x = 1.0f; -ImFont* font = io.Fonts->AddFontFromFileTTF("font.ttf", size_pixels, &config); -``` - -**Combine multiple fonts into one:** -```cpp -// Load a first font -ImFont* font = io.Fonts->AddFontDefault(); - -// Add character ranges and merge into the previous font -// The ranges array is not copied by the AddFont* functions and is used lazily -// so ensure it is available at the time of building or calling GetTexDataAsRGBA32(). -static const ImWchar icons_ranges[] = { 0xf000, 0xf3ff, 0 }; // Will not be copied by AddFont* so keep in scope. -ImFontConfig config; -config.MergeMode = true; -io.Fonts->AddFontFromFileTTF("DroidSans.ttf", 18.0f, &config, io.Fonts->GetGlyphRangesJapanese()); // Merge into first font -io.Fonts->AddFontFromFileTTF("fontawesome-webfont.ttf", 18.0f, &config, icons_ranges); // Merge into first font -io.Fonts->Build(); -``` - -**Add a fourth parameter to bake specific font ranges only:** - -```cpp -// Basic Latin, Extended Latin -io.Fonts->AddFontFromFileTTF("font.ttf", size_pixels, nullptr, io.Fonts->GetGlyphRangesDefault()); - -// Default + Selection of 2500 Ideographs used by Simplified Chinese -io.Fonts->AddFontFromFileTTF("font.ttf", size_pixels, nullptr, io.Fonts->GetGlyphRangesChineseSimplifiedCommon()); - -// Default + Hiragana, Katakana, Half-Width, Selection of 1946 Ideographs -io.Fonts->AddFontFromFileTTF("font.ttf", size_pixels, nullptr, io.Fonts->GetGlyphRangesJapanese()); -``` -See [Using Custom Glyph Ranges](#using-custom-glyph-ranges) section to create your own ranges. - -**Example loading and using a Japanese font:** - -```cpp -ImGuiIO& io = ImGui::GetIO(); -io.Fonts->AddFontFromFileTTF("NotoSansCJKjp-Medium.otf", 20.0f, nullptr, io.Fonts->GetGlyphRangesJapanese()); -``` -```cpp -ImGui::Text(u8"こんにちは!テスト %d", 123); -if (ImGui::Button(u8"ロード")) -{ - // do stuff -} -ImGui::InputText("string", buf, IM_ARRAYSIZE(buf)); -ImGui::SliderFloat("float", &f, 0.0f, 1.0f); -``` - -![sample code output](https://raw.githubusercontent.com/wiki/ocornut/imgui/web/v160/code_sample_02_jp.png) -
_(settings: Dark style (left), Light style (right) / Font: NotoSansCJKjp-Medium, 20px / Rounding: 5)_ - -##### [Return to Index](#index) - ---------------------------------------- - -## Loading Font Data from Memory - -```cpp -ImFont* font = io.Fonts->AddFontFromMemoryTTF(data, data_size, size_pixels, ...); -``` - -IMPORTANT: `AddFontFromMemoryTTF()` by default transfer ownership of the data buffer to the font atlas, which will attempt to free it on destruction. -This was to avoid an unnecessary copy, and is perhaps not a good API (a future version will redesign it). -If you want to keep ownership of the data and free it yourself, you need to clear the `FontDataOwnedByAtlas` field: - -```cpp -ImFontConfig font_cfg; -font_cfg.FontDataOwnedByAtlas = false; -ImFont* font = io.Fonts->AddFontFromMemoryTTF(data, data_size, size_pixels, &font_cfg); -``` - -##### [Return to Index](#index) - ---------------------------------------- - -## Loading Font Data Embedded In Source Code - -- Compile and use [binary_to_compressed_c.cpp](https://github.com/ocornut/imgui/blob/master/misc/fonts/binary_to_compressed_c.cpp) to create a compressed C style array that you can embed in source code. -- See the documentation in [binary_to_compressed_c.cpp](https://github.com/ocornut/imgui/blob/master/misc/fonts/binary_to_compressed_c.cpp) for instructions on how to use the tool. -- You may find a precompiled version binary_to_compressed_c.exe for Windows inside the demo binaries package (see [README](https://github.com/ocornut/imgui/blob/master/docs/README.md)). -- The tool can optionally output Base85 encoding to reduce the size of _source code_ but the read-only arrays in the actual binary will be about 20% bigger. - -Then load the font with: -```cpp -ImFont* font = io.Fonts->AddFontFromMemoryCompressedTTF(compressed_data, compressed_data_size, size_pixels, ...); -``` -or -```cpp -ImFont* font = io.Fonts->AddFontFromMemoryCompressedBase85TTF(compressed_data_base85, size_pixels, ...); -``` - -##### [Return to Index](#index) - ---------------------------------------- - -## Using Icon Fonts - -Using an icon font (such as [FontAwesome](http://fontawesome.io) or [OpenFontIcons](https://github.com/traverseda/OpenFontIcons)) is an easy and practical way to use icons in your Dear ImGui application. -A common pattern is to merge the icon font within your main font, so you can embed icons directly from your strings without having to change fonts back and forth. - -To refer to the icon UTF-8 codepoints from your C++ code, you may use those headers files created by Juliette Foucaut: https://github.com/juliettef/IconFontCppHeaders. - -So you can use `ICON_FA_SEARCH` as a string that will render as a "Search" icon. - -Example Setup: -```cpp -// Merge icons into default tool font -#include "IconsFontAwesome.h" -ImGuiIO& io = ImGui::GetIO(); -io.Fonts->AddFontDefault(); - -ImFontConfig config; -config.MergeMode = true; -config.GlyphMinAdvanceX = 13.0f; // Use if you want to make the icon monospaced -static const ImWchar icon_ranges[] = { ICON_MIN_FA, ICON_MAX_FA, 0 }; -io.Fonts->AddFontFromFileTTF("fonts/fontawesome-webfont.ttf", 13.0f, &config, icon_ranges); -``` -Example Usage: -```cpp -// Usage, e.g. -ImGui::Text("%s among %d items", ICON_FA_SEARCH, count); -ImGui::Button(ICON_FA_SEARCH " Search"); -// C string _literals_ can be concatenated at compilation time, e.g. "hello" " world" -// ICON_FA_SEARCH is defined as a string literal so this is the same as "A" "B" becoming "AB" -``` -See Links below for other icons fonts and related tools. - -**Monospace Icons?** - -To make your icon look more monospace and facilitate alignment, you may want to set the ImFontConfig::GlyphMinAdvanceX value when loading an icon font. - -**Screenshot** - -Here's an application using icons ("Avoyd", https://www.avoyd.com): -![avoyd](https://user-images.githubusercontent.com/8225057/81696852-c15d9e80-9464-11ea-9cab-2a4d4fc84396.jpg) - -##### [Return to Index](#index) - ---------------------------------------- - -## Using FreeType Rasterizer (imgui_freetype) - -- Dear ImGui uses imstb\_truetype.h to rasterize fonts (with optional oversampling). This technique and its implementation are not ideal for fonts rendered at small sizes, which may appear a little blurry or hard to read. -- There is an implementation of the ImFontAtlas builder using FreeType that you can use in the [misc/freetype/](https://github.com/ocornut/imgui/tree/master/misc/freetype) folder. -- FreeType supports auto-hinting which tends to improve the readability of small fonts. -- Read documentation in the [misc/freetype/](https://github.com/ocornut/imgui/tree/master/misc/freetype) folder. -- Correct sRGB space blending will have an important effect on your font rendering quality. - -##### [Return to Index](#index) - ---------------------------------------- - -## Using Colorful Glyphs/Emojis - -- Rendering of colored emojis is supported by imgui_freetype with FreeType 2.10+. -- You will need to load fonts with the `ImGuiFreeTypeBuilderFlags_LoadColor` flag. -- Emojis are frequently encoded in upper Unicode layers (character codes >0x10000) and will need dear imgui compiled with `IMGUI_USE_WCHAR32`. -- Not all types of color fonts are supported by FreeType at the moment. -- Stateful Unicode features such as skin tone modifiers are not supported by the text renderer. - -![colored glyphs](https://user-images.githubusercontent.com/8225057/106171241-9dc4ba80-6191-11eb-8a69-ca1467b206d1.png) - -```cpp -io.Fonts->AddFontFromFileTTF("../../../imgui_dev/data/fonts/NotoSans-Regular.ttf", 16.0f); -static ImWchar ranges[] = { 0x1, 0x1FFFF, 0 }; -static ImFontConfig cfg; -cfg.OversampleH = cfg.OversampleV = 1; -cfg.MergeMode = true; -cfg.FontBuilderFlags |= ImGuiFreeTypeBuilderFlags_LoadColor; -io.Fonts->AddFontFromFileTTF("C:\\Windows\\Fonts\\seguiemj.ttf", 16.0f, &cfg, ranges); -``` - -##### [Return to Index](#index) - ---------------------------------------- - -## Using Custom Glyph Ranges - -You can use the `ImFontGlyphRangesBuilder` helper to create glyph ranges based on text input. For example: for a game where your script is known, if you can feed your entire script to it and only build the characters the game needs. -```cpp -ImVector ranges; -ImFontGlyphRangesBuilder builder; -builder.AddText("Hello world"); // Add a string (here "Hello world" contains 7 unique characters) -builder.AddChar(0x7262); // Add a specific character -builder.AddRanges(io.Fonts->GetGlyphRangesJapanese()); // Add one of the default ranges -builder.BuildRanges(&ranges); // Build the final result (ordered ranges with all the unique characters submitted) - -io.Fonts->AddFontFromFileTTF("myfontfile.ttf", size_in_pixels, nullptr, ranges.Data); -io.Fonts->Build(); // Build the atlas while 'ranges' is still in scope and not deleted. -``` - -##### [Return to Index](#index) - ---------------------------------------- - -## Using Custom Colorful Icons - -As an alternative to rendering colorful glyphs using imgui_freetype with `ImGuiFreeTypeBuilderFlags_LoadColor`, you may allocate your own space in the texture atlas and write yourself into it. **(This is a BETA api, use if you are familiar with dear imgui and with your rendering backend)** - -- You can use the `ImFontAtlas::AddCustomRect()` and `ImFontAtlas::AddCustomRectFontGlyph()` api to register rectangles that will be packed into the font atlas texture. Register them before building the atlas, then call Build()`. -- You can then use `ImFontAtlas::GetCustomRectByIndex(int)` to query the position/size of your rectangle within the texture, and blit/copy any graphics data of your choice into those rectangles. -- This API is beta because it is likely to change in order to support multi-dpi (multiple viewports on multiple monitors with varying DPI scale). - -#### Pseudo-code: -```cpp -// Add font, then register two custom 13x13 rectangles mapped to glyph 'a' and 'b' of this font -ImFont* font = io.Fonts->AddFontDefault(); -int rect_ids[2]; -rect_ids[0] = io.Fonts->AddCustomRectFontGlyph(font, 'a', 13, 13, 13+1); -rect_ids[1] = io.Fonts->AddCustomRectFontGlyph(font, 'b', 13, 13, 13+1); - -// Build atlas -io.Fonts->Build(); - -// Retrieve texture in RGBA format -unsigned char* tex_pixels = nullptr; -int tex_width, tex_height; -io.Fonts->GetTexDataAsRGBA32(&tex_pixels, &tex_width, &tex_height); - -for (int rect_n = 0; rect_n < IM_ARRAYSIZE(rect_ids); rect_n++) -{ - int rect_id = rect_ids[rect_n]; - if (const ImFontAtlasCustomRect* rect = io.Fonts->GetCustomRectByIndex(rect_id)) - { - // Fill the custom rectangle with red pixels (in reality you would draw/copy your bitmap data here!) - for (int y = 0; y < rect->Height; y++) - { - ImU32* p = (ImU32*)tex_pixels + (rect->Y + y) * tex_width + (rect->X); - for (int x = rect->Width; x > 0; x--) - *p++ = IM_COL32(255, 0, 0, 255); - } - } -} -``` - -##### [Return to Index](#index) - ---------------------------------------- - -## About Filenames - -**Please note that many new C/C++ users have issues loading their files _because the filename they provide is wrong_ due to incorrect assumption of what is the current directory.** - -Two things to watch for: - -(1) In C/C++ and most programming languages if you want to use a backslash `\` within a string literal, you need to write it double backslash `\\`. At it happens, Windows uses backslashes as a path separator, so be mindful. -```cpp -io.Fonts->AddFontFromFileTTF("MyFiles\MyImage01.jpg", ...); // This is INCORRECT!! -io.Fonts->AddFontFromFileTTF("MyFiles\\MyImage01.jpg", ...); // This is CORRECT -``` -In some situations, you may also use `/` path separator under Windows. - -(2) Make sure your IDE/debugger settings starts your executable from the right working (current) directory. In Visual Studio you can change your working directory in project `Properties > General > Debugging > Working Directory`. People assume that their execution will start from the root folder of the project, where by default it often starts from the folder where object or executable files are stored. -```cpp -io.Fonts->AddFontFromFileTTF("MyImage01.jpg", ...); // Relative filename depends on your Working Directory when running your program! -io.Fonts->AddFontFromFileTTF("../MyImage01.jpg", ...); // Load from the parent folder of your Working Directory -``` -##### [Return to Index](#index) - ---------------------------------------- - -## About UTF-8 Encoding - -**For non-ASCII characters display, a common user issue is not passing correctly UTF-8 encoded strings.** - -(1) We provide a function `ImGui::DebugTextEncoding(const char* text)` which you can call to verify the content of your UTF-8 strings. -This is a convenient way to confirm that your encoding is correct. - -```cpp -ImGui::SeparatorText("CORRECT"); -ImGui::DebugTextEncoding(u8"こんにちは"); - -ImGui::SeparatorText("INCORRECT"); -ImGui::DebugTextEncoding("こんにちは"); -``` -![UTF-8 Encoding viewer](https://github.com/ocornut/imgui/assets/8225057/61c1696a-9a94-46c5-9627-cf91211111f0) - -You can also find this tool under `Metrics/Debuggers->Tools->UTF-8 Encoding viewer` if you want to paste from clipboard, but this won't validate the UTF-8 encoding done by your compiler. - -(2) To encode in UTF-8: - -There are also compiler-specific ways to enforce UTF-8 encoding by default: - -- Visual Studio compiler: `/utf-8` command-line flag. -- Visual Studio compiler: `#pragma execution_character_set("utf-8")` inside your code. -- Since May 2023 we have changed the Visual Studio projects of all our examples to use `/utf-8` ([see commit](https://github.com/ocornut/imgui/commit/513af1efc9080857bbd10000d98f98f2a0c96803)). - -Or, since C++11, you can use the `u8"my text"` syntax to encode literal strings as UTF-8. e.g.: -```cpp -ImGui::Text(u8"hello"); -ImGui::Text(u8"こんにちは"); // this will always be encoded as UTF-8 -ImGui::Text("こんにちは"); // the encoding of this is depending on compiler settings/flags and may be incorrect. -``` - -Since C++20, because the C++ committee hate its users, they decided to change the `u8""` syntax to not return `const char*` but a new type `const char_t*` which doesn't cast to `const char*`. -Because of type usage of `u8""` in C++20 is a little more tedious: -```cpp -ImGui::Text((const char*)u8"こんにちは"); -``` -We suggest using a macro in your codebase: -```cpp -#define U8(_S) (const char*)u8##_S -ImGui::Text(U8("こんにちは")); -``` -##### [Return to Index](#index) - ---------------------------------------- - -## Debug Tools - -#### Metrics/Debugger->Fonts -You can use the `Metrics/Debugger` window (available in `Demo>Tools`) to browse your fonts and understand what's going on if you have an issue. You can also reach it in `Demo->Tools->Style Editor->Fonts`. The same information are also available in the Style Editor under Fonts. - -![Fonts debugging](https://user-images.githubusercontent.com/8225057/135429892-0e41ef8d-33c5-4991-bcf6-f997a0bcfd6b.png) - -#### UTF-8 Encoding Viewer** -You can use the `UTF-8 Encoding viewer` in `Metrics/Debugger` to verify the content of your UTF-8 strings. From C/C++ code, you can call `ImGui::DebugTextEncoding("my string");` function to verify that your UTF-8 encoding is correct. - -![UTF-8 Encoding viewer](https://user-images.githubusercontent.com/8225057/166505963-8a0d7899-8ee8-4558-abb2-1ae523dc02f9.png) - -##### [Return to Index](#index) - ---------------------------------------- - -## Credits/Licenses For Fonts Included In Repository - -Some fonts files are available in the `misc/fonts/` folder: - -**Roboto-Medium.ttf**, by Christian Robetson -
Apache License 2.0 -
https://fonts.google.com/specimen/Roboto - -**Cousine-Regular.ttf**, by Steve Matteson -
Digitized data copyright (c) 2010 Google Corporation. -
Licensed under the SIL Open Font License, Version 1.1 -
https://fonts.google.com/specimen/Cousine - -**DroidSans.ttf**, by Steve Matteson -
Apache License 2.0 -
https://www.fontsquirrel.com/fonts/droid-sans - -**ProggyClean.ttf**, by Tristan Grimmer -
MIT License -
(recommended loading setting: Size = 13.0, GlyphOffset.y = +1) -
http://www.proggyfonts.net/ - -**ProggyTiny.ttf**, by Tristan Grimmer -
MIT License -
(recommended loading setting: Size = 10.0, GlyphOffset.y = +1) -
http://www.proggyfonts.net/ - -**Karla-Regular.ttf**, by Jonathan Pinhorn -
SIL OPEN FONT LICENSE Version 1.1 - -##### [Return to Index](#index) - -## Font Links - -#### ICON FONTS - -- C/C++ header for icon fonts (#define with code points to use in source code string literals) https://github.com/juliettef/IconFontCppHeaders -- FontAwesome https://fortawesome.github.io/Font-Awesome -- OpenFontIcons https://github.com/traverseda/OpenFontIcons -- Google Icon Fonts https://design.google.com/icons/ -- Kenney Icon Font (Game Controller Icons) https://github.com/nicodinh/kenney-icon-font -- IcoMoon - Custom Icon font builder https://icomoon.io/app - -#### REGULAR FONTS - -- Google Noto Fonts (worldwide languages) https://www.google.com/get/noto/ -- Open Sans Fonts https://fonts.google.com/specimen/Open+Sans -- (Japanese) M+ fonts by Coji Morishita http://mplus-fonts.sourceforge.jp/mplus-outline-fonts/index-en.html - -#### MONOSPACE FONTS - -Pixel Perfect: -- Proggy Fonts, by Tristan Grimmer http://www.proggyfonts.net or http://upperbounds.net -- Sweet16, Sweet16 Mono, by Martin Sedlak (Latin + Supplemental + Extended A) https://github.com/kmar/Sweet16Font (also include an .inl file to use directly in dear imgui.) - -Regular: -- Google Noto Mono Fonts https://www.google.com/get/noto/ -- Typefaces for source code beautification https://github.com/chrissimpkins/codeface -- Programmation fonts http://s9w.github.io/font_compare/ -- Inconsolata http://www.levien.com/type/myfonts/inconsolata.html -- Adobe Source Code Pro: Monospaced font family for ui & coding environments https://github.com/adobe-fonts/source-code-pro -- Monospace/Fixed Width Programmer's Fonts http://www.lowing.org/fonts/ - -Or use Arial Unicode or other Unicode fonts provided with Windows for full characters coverage (not sure of their licensing). - -##### [Return to Index](#index) diff --git a/app/jni/src/libultraship/extern/ImGui/docs/README.md b/app/jni/src/libultraship/extern/ImGui/docs/README.md deleted file mode 100644 index bd7ee8d..0000000 --- a/app/jni/src/libultraship/extern/ImGui/docs/README.md +++ /dev/null @@ -1,218 +0,0 @@ -Dear ImGui -===== - -
"Give someone state and they'll have a bug one day, but teach them how to represent state in two separate locations that have to be kept in sync and they'll have bugs for a lifetime."
-ryg - ----- - -[![Build Status](https://github.com/ocornut/imgui/workflows/build/badge.svg)](https://github.com/ocornut/imgui/actions?workflow=build) [![Static Analysis Status](https://github.com/ocornut/imgui/workflows/static-analysis/badge.svg)](https://github.com/ocornut/imgui/actions?workflow=static-analysis) [![Tests Status](https://github.com/ocornut/imgui_test_engine/workflows/tests/badge.svg)](https://github.com/ocornut/imgui_test_engine/actions?workflow=tests) - -(This library is available under a free and permissive license, but needs financial support to sustain its continued improvements. In addition to maintenance and stability there are many desirable features yet to be added. If your company is using Dear ImGui, please consider reaching out.) - -Businesses: support continued development and maintenance via invoiced sponsoring/support contracts: -
  _E-mail: contact @ dearimgui dot com_ -
Individuals: support continued development and maintenance [here](https://www.paypal.com/cgi-bin/webscr?cmd=_s-xclick&hosted_button_id=WGHNC6MBFLZ2S). Also see [Sponsors](https://github.com/ocornut/imgui/wiki/Sponsors) page. - -| [The Pitch](#the-pitch) - [Usage](#usage) - [How it works](#how-it-works) - [Releases & Changelogs](#releases--changelogs) - [Demo](#demo) - [Integration](#integration) | -:----------------------------------------------------------: | -| [Gallery](#gallery) - [Support, FAQ](#support-frequently-asked-questions-faq) - [How to help](#how-to-help) - [Sponsors](https://github.com/ocornut/imgui/wiki/Sponsors) - [Credits](#credits) - [License](#license) | -| [Wiki](https://github.com/ocornut/imgui/wiki) - [Languages & frameworks backends/bindings](https://github.com/ocornut/imgui/wiki/Bindings) - [Software using Dear ImGui](https://github.com/ocornut/imgui/wiki/Software-using-dear-imgui) - [User quotes](https://github.com/ocornut/imgui/wiki/Quotes) | - -### The Pitch - -Dear ImGui is a **bloat-free graphical user interface library for C++**. It outputs optimized vertex buffers that you can render anytime in your 3D-pipeline-enabled application. It is fast, portable, renderer agnostic, and self-contained (no external dependencies). - -Dear ImGui is designed to **enable fast iterations** and to **empower programmers** to create **content creation tools and visualization / debug tools** (as opposed to UI for the average end-user). It favors simplicity and productivity toward this goal and lacks certain features commonly found in more high-level libraries. - -Dear ImGui is particularly suited to integration in game engines (for tooling), real-time 3D applications, fullscreen applications, embedded applications, or any applications on console platforms where operating system features are non-standard. - - - Minimize state synchronization. - - Minimize state storage on user side. - - Minimize setup and maintenance. - - Easy to use to create dynamic UI which are the reflection of a dynamic data set. - - Easy to use to create code-driven and data-driven tools. - - Easy to use to create ad hoc short-lived tools and long-lived, more elaborate tools. - - Easy to hack and improve. - - Portable, minimize dependencies, run on target (consoles, phones, etc.). - - Efficient runtime and memory consumption. - - Battle-tested, used by [many major actors in the game industry](https://github.com/ocornut/imgui/wiki/Software-using-dear-imgui). - -### Usage - -**The core of Dear ImGui is self-contained within a few platform-agnostic files** which you can easily compile in your application/engine. They are all the files in the root folder of the repository (imgui*.cpp, imgui*.h). **No specific build process is required**. You can add the .cpp files into your existing project. - -**Backends for a variety of graphics API and rendering platforms** are provided in the [backends/](https://github.com/ocornut/imgui/tree/master/backends) folder, along with example applications in the [examples/](https://github.com/ocornut/imgui/tree/master/examples) folder. You may also create your own backend. Anywhere where you can render textured triangles, you can render Dear ImGui. - -See the [Getting Started](https://github.com/ocornut/imgui/wiki/Getting-Started) guide and [Integration](#integration) section of this document for more details. - -After Dear ImGui is set up in your application, you can use it from \_anywhere\_ in your program loop: -```cpp -ImGui::Text("Hello, world %d", 123); -if (ImGui::Button("Save")) - MySaveFunction(); -ImGui::InputText("string", buf, IM_ARRAYSIZE(buf)); -ImGui::SliderFloat("float", &f, 0.0f, 1.0f); -``` -![sample code output (dark, segoeui font, freetype)](https://user-images.githubusercontent.com/8225057/191050833-b7ecf528-bfae-4a9f-ac1b-f3d83437a2f4.png) -![sample code output (light, segoeui font, freetype)](https://user-images.githubusercontent.com/8225057/191050838-8742efd4-504d-4334-a9a2-e756d15bc2ab.png) - -```cpp -// Create a window called "My First Tool", with a menu bar. -ImGui::Begin("My First Tool", &my_tool_active, ImGuiWindowFlags_MenuBar); -if (ImGui::BeginMenuBar()) -{ - if (ImGui::BeginMenu("File")) - { - if (ImGui::MenuItem("Open..", "Ctrl+O")) { /* Do stuff */ } - if (ImGui::MenuItem("Save", "Ctrl+S")) { /* Do stuff */ } - if (ImGui::MenuItem("Close", "Ctrl+W")) { my_tool_active = false; } - ImGui::EndMenu(); - } - ImGui::EndMenuBar(); -} - -// Edit a color stored as 4 floats -ImGui::ColorEdit4("Color", my_color); - -// Generate samples and plot them -float samples[100]; -for (int n = 0; n < 100; n++) - samples[n] = sinf(n * 0.2f + ImGui::GetTime() * 1.5f); -ImGui::PlotLines("Samples", samples, 100); - -// Display contents in a scrolling region -ImGui::TextColored(ImVec4(1,1,0,1), "Important Stuff"); -ImGui::BeginChild("Scrolling"); -for (int n = 0; n < 50; n++) - ImGui::Text("%04d: Some text", n); -ImGui::EndChild(); -ImGui::End(); -``` -![my_first_tool_v188](https://user-images.githubusercontent.com/8225057/191055698-690a5651-458f-4856-b5a9-e8cc95c543e2.gif) - -Dear ImGui allows you to **create elaborate tools** as well as very short-lived ones. On the extreme side of short-livedness: using the Edit&Continue (hot code reload) feature of modern compilers you can add a few widgets to tweak variables while your application is running, and remove the code a minute later! Dear ImGui is not just for tweaking values. You can use it to trace a running algorithm by just emitting text commands. You can use it along with your own reflection data to browse your dataset live. You can use it to expose the internals of a subsystem in your engine, to create a logger, an inspection tool, a profiler, a debugger, an entire game-making editor/framework, etc. - -### How it works - -The IMGUI paradigm through its API tries to minimize superfluous state duplication, state synchronization, and state retention from the user's point of view. It is less error-prone (less code and fewer bugs) than traditional retained-mode interfaces, and lends itself to creating dynamic user interfaces. Check out the Wiki's [About the IMGUI paradigm](https://github.com/ocornut/imgui/wiki#about-the-imgui-paradigm) section for more details. - -Dear ImGui outputs vertex buffers and command lists that you can easily render in your application. The number of draw calls and state changes required to render them is fairly small. Because Dear ImGui doesn't know or touch graphics state directly, you can call its functions anywhere in your code (e.g. in the middle of a running algorithm, or in the middle of your own rendering process). Refer to the sample applications in the examples/ folder for instructions on how to integrate Dear ImGui with your existing codebase. - -_A common misunderstanding is to mistake immediate mode GUI for immediate mode rendering, which usually implies hammering your driver/GPU with a bunch of inefficient draw calls and state changes as the GUI functions are called. This is NOT what Dear ImGui does. Dear ImGui outputs vertex buffers and a small list of draw calls batches. It never touches your GPU directly. The draw call batches are decently optimal and you can render them later, in your app or even remotely._ - -### Releases & Changelogs - -See [Releases](https://github.com/ocornut/imgui/releases) page for decorated Changelogs. -Reading the changelogs is a good way to keep up to date with the things Dear ImGui has to offer, and maybe will give you ideas of some features that you've been ignoring until now! - -### Demo - -Calling the `ImGui::ShowDemoWindow()` function will create a demo window showcasing a variety of features and examples. The code is always available for reference in `imgui_demo.cpp`. [Here's how the demo looks](https://raw.githubusercontent.com/wiki/ocornut/imgui/web/v167/v167-misc.png). - -You should be able to build the examples from sources. If you don't, let us know! If you want to have a quick look at some Dear ImGui features, you can download Windows binaries of the demo app here: -- [imgui-demo-binaries-20230704.zip](https://www.dearimgui.com/binaries/imgui-demo-binaries-20230704.zip) (Windows, 1.89.7, built 2023/07/04, master) or [older binaries](https://www.dearimgui.com/binaries). - -The demo applications are not DPI aware so expect some blurriness on a 4K screen. For DPI awareness in your application, you can load/reload your font at a different scale and scale your style with `style.ScaleAllSizes()` (see [FAQ](https://www.dearimgui.com/faq)). - -### Integration - -See the [Getting Started](https://github.com/ocornut/imgui/wiki/Getting-Started) guide for details. - -On most platforms and when using C++, **you should be able to use a combination of the [imgui_impl_xxxx](https://github.com/ocornut/imgui/tree/master/backends) backends without modification** (e.g. `imgui_impl_win32.cpp` + `imgui_impl_dx11.cpp`). If your engine supports multiple platforms, consider using more imgui_impl_xxxx files instead of rewriting them: this will be less work for you, and you can get Dear ImGui running immediately. You can _later_ decide to rewrite a custom backend using your custom engine functions if you wish so. - -Integrating Dear ImGui within your custom engine is a matter of 1) wiring mouse/keyboard/gamepad inputs 2) uploading a texture to your GPU/render engine 3) providing a render function that can bind textures and render textured triangles, which is essentially what Backends are doing. The [examples/](https://github.com/ocornut/imgui/tree/master/examples) folder is populated with applications doing just that: setting up a window and using backends. If you follow the [Getting Started](https://github.com/ocornut/imgui/wiki/Getting-Started) guide it should in theory takes you less than an hour to integrate Dear ImGui. **Make sure to spend time reading the [FAQ](https://www.dearimgui.com/faq), comments, and the examples applications!** - -Officially maintained backends/bindings (in repository): -- Renderers: DirectX9, DirectX10, DirectX11, DirectX12, Metal, OpenGL/ES/ES2, SDL_Renderer, Vulkan, WebGPU. -- Platforms: GLFW, SDL2/SDL3, Win32, Glut, OSX, Android. -- Frameworks: Allegro5, Emscripten. - -[Third-party backends/bindings](https://github.com/ocornut/imgui/wiki/Bindings) wiki page: -- Languages: C, C# and: Beef, ChaiScript, Crystal, D, Go, Haskell, Haxe/hxcpp, Java, JavaScript, Julia, Kotlin, Lobster, Lua, Odin, Pascal, PureBasic, Python, Ruby, Rust, Swift... -- Frameworks: AGS/Adventure Game Studio, Amethyst, Blender, bsf, Cinder, Cocos2d-x, Diligent Engine, Flexium, GML/Game Maker Studio2, GLEQ, Godot, GTK3+OpenGL3, Irrlicht Engine, LÖVE+LUA, Magnum, Monogame, NanoRT, nCine, Nim Game Lib, Nintendo 3DS & Switch (homebrew), Ogre, openFrameworks, OSG/OpenSceneGraph, Orx, Photoshop, px_render, Qt/QtDirect3D, SDL_Renderer, SFML, Sokol, Unity, Unreal Engine 4, vtk, VulkanHpp, VulkanSceneGraph, Win32 GDI, WxWidgets. -- Many bindings are auto-generated (by good old [cimgui](https://github.com/cimgui/cimgui) or newer/experimental [dear_bindings](https://github.com/dearimgui/dear_bindings)), you can use their metadata output to generate bindings for other languages. - -[Useful Extensions/Widgets](https://github.com/ocornut/imgui/wiki/Useful-Extensions) wiki page: -- Automation/testing, Text editors, node editors, timeline editors, plotting, software renderers, remote network access, memory editors, gizmos, etc. One of the most notable and well supported extension is [ImPlot](https://github.com/epezent/implot). - -Also see [Wiki](https://github.com/ocornut/imgui/wiki) for more links and ideas. - -### Gallery - -For more user-submitted screenshots of projects using Dear ImGui, check out the [Gallery Threads](https://github.com/ocornut/imgui/issues/6897)! - -For a list of third-party widgets and extensions, check out the [Useful Extensions/Widgets](https://github.com/ocornut/imgui/wiki/Useful-Extensions) wiki page. - -| | | -|--|--| -| Custom engine [erhe](https://github.com/tksuoran/erhe) (docking branch)
[![erhe](https://user-images.githubusercontent.com/8225057/190203358-6988b846-0686-480e-8663-1311fbd18abd.jpg)](https://user-images.githubusercontent.com/994606/147875067-a848991e-2ad2-4fd3-bf71-4aeb8a547bcf.png) | Custom engine for [Wonder Boy: The Dragon's Trap](http://www.TheDragonsTrap.com) (2017)
[![the dragon's trap](https://user-images.githubusercontent.com/8225057/190203379-57fcb80e-4aec-4fec-959e-17ddd3cd71e5.jpg)](https://cloud.githubusercontent.com/assets/8225057/20628927/33e14cac-b329-11e6-80f6-9524e93b048a.png) | -| Custom engine (untitled)
[![editor white](https://user-images.githubusercontent.com/8225057/190203393-c5ac9f22-b900-4d1e-bfeb-6027c63e3d92.jpg)](https://raw.githubusercontent.com/wiki/ocornut/imgui/web/v160/editor_white.png) | Tracy Profiler ([github](https://github.com/wolfpld/tracy))
[![tracy profiler](https://user-images.githubusercontent.com/8225057/190203401-7b595f6e-607c-44d3-97ea-4c2673244dfb.jpg)](https://raw.githubusercontent.com/wiki/ocornut/imgui/web/v176/tracy_profiler.png) | - -### Support, Frequently Asked Questions (FAQ) - -See: [Frequently Asked Questions (FAQ)](https://github.com/ocornut/imgui/blob/master/docs/FAQ.md) where common questions are answered. - -See: [Getting Started](https://github.com/ocornut/imgui/wiki/Getting-Started) and [Wiki](https://github.com/ocornut/imgui/wiki) for many links, references, articles. - -See: [Articles about the IMGUI paradigm](https://github.com/ocornut/imgui/wiki#about-the-imgui-paradigm) to read/learn about the Immediate Mode GUI paradigm. - -See: [Upcoming Changes](https://github.com/ocornut/imgui/wiki/Upcoming-Changes). - -See: [Dear ImGui Test Engine + Test Suite](https://github.com/ocornut/imgui_test_engine) for Automation & Testing. - -Getting started? For first-time users having issues compiling/linking/running or issues loading fonts, please use [GitHub Discussions](https://github.com/ocornut/imgui/discussions). For other questions, bug reports, requests, feedback, you may post on [GitHub Issues](https://github.com/ocornut/imgui/issues). Please read and fill the New Issue template carefully. - -Private support is available for paying business customers (E-mail: _contact @ dearimgui dot com_). - -**Which version should I get?** - -We occasionally tag [Releases](https://github.com/ocornut/imgui/releases) (with nice releases notes) but it is generally safe and recommended to sync to latest `master` or `docking` branch. The library is fairly stable and regressions tend to be fixed fast when reported. Advanced users may want to use the `docking` branch with [Multi-Viewport](https://github.com/ocornut/imgui/issues/1542) and [Docking](https://github.com/ocornut/imgui/issues/2109) features. This branch is kept in sync with master regularly. - -**Who uses Dear ImGui?** - -See the [Quotes](https://github.com/ocornut/imgui/wiki/Quotes), [Sponsors](https://github.com/ocornut/imgui/wiki/Sponsors), and [Software using Dear ImGui](https://github.com/ocornut/imgui/wiki/Software-using-dear-imgui) Wiki pages for an idea of who is using Dear ImGui. Please add your game/software if you can! Also, see the [Gallery Threads](https://github.com/ocornut/imgui/issues/6897)! - -How to help ------------ - -**How can I help?** - -- See [GitHub Forum/Issues](https://github.com/ocornut/imgui/issues) and [GitHub Discussions](https://github.com/ocornut/imgui/discussions). -- You may help with development and submit pull requests! Please understand that by submitting a PR you are also submitting a request for the maintainer to review your code and then take over its maintenance forever. PR should be crafted both in the interest of the end-users and also to ease the maintainer into understanding and accepting it. -- See [Help wanted](https://github.com/ocornut/imgui/wiki/Help-Wanted) on the [Wiki](https://github.com/ocornut/imgui/wiki/) for some more ideas. -- Have your company financially support this project with invoiced sponsoring/support contracts or by buying a license for [Dear ImGui Test Engine](https://github.com/ocornut/imgui_test_engine) (please reach out: omar AT dearimgui DOT com). - -Sponsors --------- - -Ongoing Dear ImGui development is and has been financially supported by users and private sponsors. -
Please see the **[detailed list of current and past Dear ImGui supporters](https://github.com/ocornut/imgui/wiki/Sponsors)** for details. -
From November 2014 to December 2019, ongoing development has also been financially supported by its users on Patreon and through individual donations. - -**THANK YOU to all past and present supporters for helping to keep this project alive and thriving!** - -Dear ImGui is using software and services provided free of charge for open source projects: -- [PVS-Studio](https://www.viva64.com/en/b/0570/) for static analysis. -- [GitHub actions](https://github.com/features/actions) for continuous integration systems. -- [OpenCppCoverage](https://github.com/OpenCppCoverage/OpenCppCoverage) for code coverage analysis. - -Credits -------- - -Developed by [Omar Cornut](https://www.miracleworld.net) and every direct or indirect [contributors](https://github.com/ocornut/imgui/graphs/contributors) to the GitHub. The early version of this library was developed with the support of [Media Molecule](https://www.mediamolecule.com) and first used internally on the game [Tearaway](https://tearaway.mediamolecule.com) (PS Vita). - -Recurring contributors (2022): Omar Cornut [@ocornut](https://github.com/ocornut), Rokas Kupstys [@rokups](https://github.com/rokups) (a good portion of work on automation system and regression tests now available in [Dear ImGui Test Engine](https://github.com/ocornut/imgui_test_engine)). - -Sponsoring, support contracts and other B2B transactions are hosted and handled by [Disco Hello](https://www.discohello.com). - -Omar: "I first discovered the IMGUI paradigm at [Q-Games](https://www.q-games.com) where Atman Binstock had dropped his own simple implementation in the codebase, which I spent quite some time improving and thinking about. It turned out that Atman was exposed to the concept directly by working with Casey. When I moved to Media Molecule I rewrote a new library trying to overcome the flaws and limitations of the first one I've worked with. It became this library and since then I have spent an unreasonable amount of time iterating and improving it." - -Embeds [ProggyClean.ttf](http://upperbounds.net) font by Tristan Grimmer (MIT license). -
Embeds [stb_textedit.h, stb_truetype.h, stb_rect_pack.h](https://github.com/nothings/stb/) by Sean Barrett (public domain). - -Inspiration, feedback, and testing for early versions: Casey Muratori, Atman Binstock, Mikko Mononen, Emmanuel Briney, Stefan Kamoda, Anton Mikhailov, Matt Willis. Also thank you to everyone posting feedback, questions and patches on GitHub. - -License -------- - -Dear ImGui is licensed under the MIT License, see [LICENSE.txt](https://github.com/ocornut/imgui/blob/master/LICENSE.txt) for more information. diff --git a/app/jni/src/libultraship/extern/ImGui/docs/TODO.txt b/app/jni/src/libultraship/extern/ImGui/docs/TODO.txt deleted file mode 100644 index 4df57e5..0000000 --- a/app/jni/src/libultraship/extern/ImGui/docs/TODO.txt +++ /dev/null @@ -1,388 +0,0 @@ -dear imgui -ISSUES & TODO LIST - -Issue numbers (#) refer to GitHub issues listed at https://github.com/ocornut/imgui/issues/XXXX -THIS LIST IS NOT WELL MAINTAINED. MOST OF THE WORK HAPPENS ON GITHUB NOWADAYS. -The list below consist mostly of ideas noted down before they are requested/discussed by users (at which point they usually exist on the github issue tracker). -It's mostly a bunch of personal notes, probably incomplete. Feel free to query if you have any questions. - - - doc: add a proper documentation system (maybe relying on automation? #435) - - doc: checklist app to verify backends/integration of imgui (test inputs, rendering, callback, etc.). - - doc/tips: tips of the day: website? applet in imgui_club? - - doc/wiki: work on the wiki https://github.com/ocornut/imgui/wiki - - - window: preserve/restore relative focus ordering (persistent or not), and e.g. of multiple reappearing windows (#2304) -> also see docking reference to same #. - - window: calling SetNextWindowSize() every frame with <= 0 doesn't do anything, may be useful to allow (particularly when used for a single axis). (#690) - - window: add a way for very transient windows (non-saved, temporary overlay over hundreds of objects) to "clean" up from the global window list. perhaps a lightweight explicit cleanup pass. - - window: auto-fit feedback loop when user relies on any dynamic layout (window width multiplier, column) appears weird to end-user. clarify. - - window: begin with *p_open == false could return false. - - window: get size/pos helpers given names (see discussion in #249) - - window: when window is very small, prioritize resize button over close button. - - window: double-clicking on title bar to minimize isn't consistent interaction, perhaps move to single-click on left-most collapse icon? - - window: expose contents size. (#1045) - - window: using SetWindowPos() inside Begin() and moving the window with the mouse reacts a very ugly glitch. We should just defer the SetWindowPos() call. - - window: GetWindowSize() returns (0,0) when not calculated? (#1045) - - window: investigate better auto-positioning for new windows. - - window: top most window flag? more z-order contrl? (#2574) - - window/size: manually triggered auto-fit (double-click on grip) shouldn't resize window down to viewport size? - - window/size: how to allow to e.g. auto-size vertically to fit contents, but be horizontally resizable? Assuming SetNextWindowSize() is modified to treat -1.0f on each axis as "keep as-is" (would be good but might break erroneous code): Problem is UpdateWindowManualResize() and lots of code treat (window->AutoFitFramesX > 0 || window->AutoFitFramesY > 0) together. - - window/opt: freeze window flag: if not focused/hovered, return false, render with previous ImDrawList. and/or reduce refresh rate. -> this may require enforcing that it is illegal to submit contents if Begin returns false. - - window/child: background options for child windows, border option (disable rounding). - - window/child: allow resizing of child windows (possibly given min/max for each axis?.) - - window/child: allow SetNextWindowContentSize() to work on child windows. - - window/clipping: some form of clipping when DisplaySize (or corresponding viewport) is zero. - - window/tabbing: add a way to signify that a window or docked window requires attention (e.g. blinking title bar, trying to click behind a modal). - - window/id_stack: add e.g. window->GetIDFromPath() with support for leading / and ../ (#1390, #331) -> model from test engine. - ! scrolling: exposing horizontal scrolling with Shift+Wheel even when scrollbar is disabled expose lots of issues (#2424, #1463) - - scrolling: while holding down a scrollbar, try to keep the same contents visible (at least while not moving mouse) - - scrolling: allow immediately effective change of scroll after Begin() if we haven't appended items yet. - - scrolling: forward mouse wheel scrolling to parent window when at the edge of scrolling limits? (useful for listbox,tables?) - - scrolling/style: shadows on scrollable areas to denote that there is more contents (see e.g. DaVinci Resolve ui) - - - drawdata: make it easy to deep-copy (or swap?) a full ImDrawData so user can easily save that data if they use threaded rendering. (e.g. #2646) - ! drawlist: add CalcTextSize() func to facilitate consistent code from user pov (currently need to use ImGui or ImFont alternatives!) - - drawlist: maintaining bounding box per command would allow to merge draw command when clipping isn't relied on (typical non-scrolling window or non-overflowing column would merge with previous command). (WIP branch) - - drawlist: make it easier to toggle AA per primitive, so we can use e.g. non-AA fill + AA borders more naturally - - drawlist: non-AA strokes have gaps between points (#593, #288), glitch especially on RenderCheckmark() and ColorPicker4(). - - drawlist: callback: add an extra void* in ImDrawCallback to allow passing render-local data to the callback (would break API). - - drawlist: AddRect vs AddLine position confusing (#2441) - - drawlist/opt: store rounded corners in texture to use 1 quad per corner (filled and wireframe) to lower the cost of rounding. (#1962) - - drawlist/opt: AddRect() axis aligned pixel aligned (no-aa) could use 8 triangles instead of 16 and no normal calculation. - - drawlist/opt: thick AA line could be doable in same number of triangles as 1.0 AA line by storing gradient+full color in atlas. - - - items: IsItemHovered() info stored in a stack? so that 'if TreeNode() { Text; TreePop; } if IsHovered' return the hover state of the TreeNode? - - - widgets: display mode: widget-label, label-widget (aligned on column or using fixed size), label-newline-tab-widget etc. (#395) - - widgets: clean up widgets internal toward exposing everything and stabilizing imgui_internals.h. - - widgets: add always-allow-overlap mode. This should perhaps be the default? one problem is that highlight after mouse-wheel scrolling gets deferred, makes scrolling more flickery. - - widgets: start exposing PushItemFlag() and ImGuiItemFlags - - widgets: alignment options in style (e.g. center Selectable, Right-Align within Button, etc.) #1260 - - widgets: activate by identifier (trigger button, focus given id) - - widgets: custom glyph/shapes replacements for stock sapes. (also #6090 #2431 #2235 #6517) - - widgets: coloredit: keep reporting as active when picker is on? - - widgets: group/scalarn functions: expose more per-component information. e.g. store NextItemData.ComponentIdx set by scalarn function, groups can expose them back somehow. - - selectable: using (size.x == 0.0f) and (SelectableTextAlign.x > 0.0f) followed by SameLine() is currently not supported. - - selectable: generic BeginSelectable()/EndSelectable() mechanism. (work out alongside range-select branch) - - selectable: a way to visualize partial/mixed selection (e.g. parent tree node has children with mixed selection) - - - input text: clean up the mess caused by converting UTF-8 <> wchar. the code is rather inefficient right now and super fragile. (WIP branch) - - input text: preserve scrolling when unfocused? - - input text: reorganize event handling, allow CharFilter to modify buffers, allow multiple events? (#541) - - input text: expose CursorPos in char filter event (#816) - - input text: try usage idiom of using InputText with data only exposed through get/set accessors, without extraneous copy/alloc. (#3009) - - input text: access public fields via a non-callback API e.g. InputTextGetState("xxx") that may return nullptr if not active (available in internals) - - input text: flag to disable live update of the user buffer (also applies to float/int text input) (#701) - - input text: hover tooltip could show unclamped text - - input text: support for INSERT key to toggle overwrite mode. currently disabled because stb_textedit behavior is unsatisfactory on multi-line. (#2863) - - input text: option to Tab after an Enter validation. - - input text: add ImGuiInputTextFlags_EnterToApply? (off #218) - - input text: easier ways to update buffer (from source char*) while owned. preserve some sort of cursor position for multi-line text. - - input text: add discard flag (e.g. ImGuiInputTextFlags_DiscardActiveBuffer) or make it easier to clear active focus for text replacement during edition (#725) - - input text: display bug when clicking a drag/slider after an input text in a different window has all-selected text (order dependent). actually a very old bug but no one appears to have noticed it. - - input text: allow centering/positioning text so that ctrl+clicking Drag or Slider keeps the textual value at the same pixel position. - - input text: decorrelate display layout from inputs with custom template - e.g. what's the easiest way to implement a nice IP/Mac address input editor? - - input text: global callback system so user can plug in an expression evaluator easily. (#1691) - - input text: force scroll to end or scroll to a given line/contents (so user can implement a log or a search feature) - - input text: a way to preview completion (e.g. disabled text completing from the cursor) - - input text: a side bar that could e.g. preview where errors are. probably left to the user to draw but we'd need to give them the info there. - - input text: a way for the user to provide syntax coloring. - - input text: Shift+TAB with ImGuiInputTextFlags_AllowTabInput could eat preceding blanks, up to tab_count. - - input text multi-line: don't directly call AddText() which does an unnecessary vertex reserve for character count prior to clipping. and/or more line-based clipping to AddText(). and/or reorganize TextUnformatted/RenderText for more efficiency for large text (e.g TextUnformatted could clip and log separately, etc). - - input text multi-line: support for copy/cut without selection (copy/cut current line?) - - input text multi-line: line numbers? status bar? (follow up on #200) - - input text multi-line: behave better when user changes input buffer while editing is active (even though it is illegal behavior). namely, the change of buffer can create a scrollbar glitch (#725) - - input text multi-line: better horizontal scrolling support (#383, #1224) - - input text multi-line: single call to AddText() should be coarse clipped on InputTextEx() end. - - input number: optional range min/max for Input*() functions - - input number: holding [-]/[+] buttons could increase the step speed non-linearly (or user-controlled) - - input number: use mouse wheel to step up/down - - - layout: helper or a way to express ImGui::SameLine(ImGui::GetCursorStartPos().x + ImGui::CalcItemWidth() + ImGui::GetStyle().ItemInnerSpacing.x); in a simpler manner. - - layout, font: horizontal tab support, A) text mode: forward only tabs (e.g. every 4 characters/N pixels from pos x1), B) manual mode: explicit tab stops acting as mini columns, no clipping (for menu items, many kind of uses, also vaguely relate to #267, #395) - - layout: horizontal layout helper (#97) - - layout: horizontal flow until no space left (#404) - - layout: more generic alignment state (left/right/centered) for single items? - - layout: clean up the InputFloatN/SliderFloatN/ColorEdit4 layout code. item width should include frame padding. - - layout: vertical alignment of mixed height items (e.g. buttons) within a same line (#1284) - - layout: null layout mode were items are not rendered but user can query GetItemRectMin()/Max/Size. - - layout: (R&D) local multi-pass layout mode. - - layout: (R&D) bind authored layout data (created by an off-line tool), items fetch their pos/size at submission, self-optimize data structures to stable linear access. - - - tables: see https://github.com/ocornut/imgui/issues/2957#issuecomment-569726095 - - - group: BeginGroup() needs a border option. (~#1496) - - group: IsItemHovered() after EndGroup() covers whole AABB rather than the intersection of individual items. Is that desirable? - - group: merge deactivation/activation within same group (fwd WasEdited flag). (#2550) - -!- color: the color conversion helpers/types are a mess and needs sorting out. - - color: (api breaking) ImGui::ColorConvertXXX functions should be loose ImColorConvertXX to match imgui_internals.h - - - plot: full featured plot/graph api w/ scrolling, zooming etc. --> ImPlot - - (plot: deleted all other todo lines on 2023-06-28) - - - clipper: ability to disable the clipping through a simple flag/bool. - - clipper: ability to run without knowing full count in advance. - - clipper: horizontal clipping support. (#2580) - - - separator: expose flags (#759) - - separator: take indent into consideration (optional) - - separator: width, thickness, centering (#1643, #2657) - - splitter: formalize the splitter idiom into an official api (we want to handle n-way split) (#319) - - - docking: B: ordering currently held in tab bar should be implicitly held by windows themselves (also see #2304) - - docking: B- tab bar: the order/focus restoring code could be part of TabBar and not DockNode? (#8) - - docking: B~ rework code to be able to lazily create tab bar instance in a single place. The _Unsorted tab flag could be replacing a trailing-counter in DockNode? - - docking: B~ fully track windows/settings reference in dock nodes. perhaps find a representation that allows facilitate use of dock builder functions. - - docking: B~ Unreal style document system (requires low-level controls of dockspace serialization fork/copy/delete). this is mostly working but the DockBuilderXXX api are not exposed/finished. - - docking: B: when docking outer, perform size locking on neighbors nodes the same way we do it with splitters, so other nodes are not resized. - - docking: B~ central node resizing behavior incorrect. - - docking: B: changing title font/style per-window is not supported as dock nodes are created in NewFrame. - - docking: B- dock node inside its own viewports creates 1 temporary viewport per window on startup before ditching them (doesn't affect the user nor request platform windows to be created, but unnecessary) - - docking: B- resize sibling locking behavior may be less desirable if we merged same-axis sibling in a same node level? - - docking: B- single visible node part of a hidden split hierarchy (OnlyNodeWithWindows != NULL) should show a normal title bar (not a tab bar) - - docking: B~ SetNextWindowDock() calls (with conditional) -> defer everything to DockContextUpdate (repro: Documents->[X]Windows->Dock 1 elsewhere->Click Redock All - - docking: B~ tidy up tab list popup buttons features (available with manual tab-bar, see ImGuiTabBarFlags_NoTabListPopupButton code, not used by docking nodes) - - docking: B- SetNextWindowDockId(0) with a second Begin() in the frame will asserts - - docking: B: resize grip drawn in host window typically appears under scrollbar. - - docking: B: resize grip auto-resize on multiple node hierarchy doesn't make much sense or should be improved? - - docking: B- SetNextWindowFocus() doesn't seem to apply if the window is hidden this frame, need repro (#4) - - docking: B- resizing a dock tree small currently has glitches (overlapping collapse and close button, etc.) - - docking: B- dpi: look at interaction with the hi-dpi and multi-dpi stuff. - - docking: B- tab bar: appearing on first frame with a dumb layout would do less harm that not appearing? (when behind dynamic branch) or store titles + render in EndTabBar() - - docking: B- tab bar: make selected tab always shows its full title? - - docking: B- hide close button on single tab bar? - - docking: B- nav: design interactions so nav controls can dock/undock - - docking: B- dockspace: flag to lock the dock tree and/or sizes (ImGuiDockNodeFlags_Locked?) - - docking: B- reintroduce collapsing a floating dock node. also collapsing a docked dock node! - - docking: B- allow dragging a non-floating dock node by clicking on the title-bar-looking section (not just the collapse/menu button) - - docking: B- option to remember undocked window size? (instead of keeping their docked size) (relate to #2104) - - docking: C- nav: CTRL+TAB highlighting tabs shows the mismatch between focus-stack and tab-order (not visible in VS because it doesn't highlight the tabs) - - docking: C- after a dock/undock, the Scrollbar Status update in Begin() should use an updated e.g. size_y_for_scrollbars to avoid a 1 frame scrollbar flicker. - - - tabs: "there is currently a problem because TabItem() will try to submit their own tooltip after 0.50 second, and this will have the effect of making your tooltip flicker once." -> tooltip priority work (WIP branch) - - tabs: make EndTabBar fail if users doesn't respect BeginTabBar return value, for consistency/future-proofing. - - tabs: persistent order/focus in BeginTabBar() api (#261, #351) - - tabs: explicit api (even if internal) to cleanly manipulate tab order. - - - image/image button: misalignment on padded/bordered button? - - image/image button: parameters are confusing, image() has tint_col,border_col whereas imagebutton() has bg_col/tint_col. Even thou they are different parameters ordering could be more consistent. can we fix that? - - slider: allow using the [-]/[+] buttons used by InputFloat()/InputInt() - - slider: add dragging-based widgets to edit values with mouse (on 2 axises), saving screen real-estate. - - slider: tint background based on value (e.g. v_min -> v_max, or use 0.0f either side of the sign) - - slider: relative dragging? + precision dragging - - slider: step option (#1183) - - slider: style: fill % of the bar instead of positioning a drag. - - knob: rotating knob widget (#942) - - drag float: support for reversed drags (min > max) (removed is_locked, also see fdc526e) - - drag float: up/down axis - - drag float: power != 0.0f with current value being outside the range keeps the value stuck. - - drag float: added leeway on edge (e.g. a few invisible steps past the clamp limits) - - - combo: use clipper. - - combo: a way/helper to customize the combo preview (#1658) -> experimental BeginComboPreview() - - combo/listbox: keyboard control. need InputText-like non-active focus + key handling. considering keyboard for custom listbox (pr #203) - - listbox: multiple selection (WIP range-select branch) - - listbox: unselect option (#1208) - - listbox: make it easier/more natural to implement range-select (need some sort of info/ref about the last clicked/focused item that user can translate to an index?) (WIP range-select branch) - - listbox: user may want to initial scroll to focus on the one selected value? - - listbox: disable capturing mouse wheel if the listbox has no scrolling. (#1681) - - listbox: scrolling should track modified selection. - - listbox: future api should allow to enable horizontal scrolling (#2510) - -!- popups/menus: clarify usage of popups id, how MenuItem/Selectable closing parent popups affects the ID, etc. this is quite fishy needs improvement! (#331, #402) - - modals: make modal title bar blink when trying to click outside the modal - - modals: technically speaking, we could make Begin() with ImGuiWindowFlags_Modal work without involving popup. May help untangle a few things, as modals are more like regular windows than popups. - - popups: if the popup functions took explicit ImGuiID it would allow the user to manage the scope of those ID. (#331) - - popups: clicking outside (to close popup) and holding shouldn't drag window below. - - popups: add variant using global identifier similar to Begin/End (#402) - - popups: border options. richer api like BeginChild() perhaps? (#197) - - popups/modals: although it is sometimes convenient that popups/modals lifetime is owned by imgui, we could also a bool-owned-by-user api as long as Begin() return value testing is enforced. - - - tooltip: drag and drop with tooltip near monitor edges lose/changes its last direction instead of locking one. The drag and drop tooltip should always follow without changing direction. - - tooltip: allow to set the width of a tooltip to allow TextWrapped() etc. while keeping the height automatic. - - tooltip: drag tooltip hovering over source widget with IsItemHovered/SetTooltip flickers (WIP branch) - - - status-bar: add a per-window status bar helper similar to what menu-bar does. generalize concept of layer0 rect in window (can make _MenuBar window flag obsolete too). - - shortcuts: local-style shortcut api, e.g. parse "&Save" - - shortcuts,menus: global-style shortcut api e.g. "Save (CTRL+S)" -> explicit flag for recursing into closed menu - - shortcuts: programmatically access shortcuts "Focus("&Save")) - - menus: menu-bar: main menu-bar could affect clamping of windows position (~ akin to modifying DisplayMin) - - menus: hovering from menu to menu on a menu-bar has 1 frame without any menu, which is a little annoying. ideally either 0 either longer. - - menus: would be nice if the Selectable() supported horizontal alignment (must be given the equivalent of WorkRect.Max.x matching the position of the shortcut column) - - - tree node: add treenode/treepush int variants? not there because (void*) cast from int warns on some platforms/settings? - - tree node: try to apply scrolling at time of TreePop() if node was just opened and end of node is past scrolling limits? - - tree node / selectable render mismatch which is visible if you use them both next to each other (e.g. cf. property viewer) - - tree node: tweak color scheme to distinguish headers from selected tree node (#581) - - tree node: leaf/non-leaf highlight mismatch. - - tree node/opt: could avoid formatting when clipped (flag assuming we don't care about width/height, assume single line height? format only %s/%c to be able to count height?) - - - settings: write more decent code to allow saving/loading new fields: columns, selected tree nodes? - - settings: api for per-tool simple persistent data (bool,int,float,columns sizes,etc.) in .ini file (#437) - - settings/persistence: helpers to make TreeNodeBehavior persist (even during dev!) - may need to store some semantic and/or data type in ImGuiStoragePair - - - style: better default styles. (#707) - - style: PushStyleVar: allow direct access to individual float X/Y elements. - - style: add a highlighted text color (for headers, etc.) - - style: border types: out-screen, in-screen, etc. (#447) - - style: add window shadow (fading away from the window. Paint-style calculation of vertices alpha after drawlist would be easier) - - style: a concept of "compact style" that the end-user can easily rely on (e.g. PushStyleCompact()?) that maps to other settings? avoid implementing duplicate helpers such as SmallCheckbox(), etc. - - style: try to make PushStyleVar() more robust to incorrect parameters (to be more friendly to edit & continues situation). - - style: global scale setting. - - style: FramePadding could be different for up vs down (#584) - - style: WindowPadding needs to be EVEN as the 0.5 multiplier used on this value probably have a subtle effect on clip rectangle - - style: have a more global HSV setter (e.g. alter hue on all elements). consider replacing active/hovered by offset in HSV space? (#438, #707, #1223) - - style: gradients fill (#1223) ~ 2 bg colors for each fill? tricky with rounded shapes and using textures for corners. - - style editor: color child window height expressed in multiple of line height. - - - log: improve logging of ArrowButton, ListBox, TabItem - - log: carry on indent / tree depth when opening a child window - - log: enabling log ends up pushing and growing vertices buffers because we don't distinguish layout vs render clipping - - log: have more control over the log scope (e.g. stop logging when leaving current tree node scope) - - log: be able to log anything (e.g. right-click on a window/tree-node, shows context menu? log into tty/file/clipboard) - - log: let user copy any window content to clipboard easily (CTRL+C on windows? while moving it? context menu?). code is commented because it fails with multiple Begin/End pairs. - - log: obsolete LogButtons().... (was: LogButtons() options for specifying depth and/or hiding depth slider) - - - filters: set a current filter that certains items (e.g. tree node) can automatically query to hide themselves - - filters: handle wild-cards (with implicit leading/trailing *), reg-exprs - - filters: fuzzy matches (may use code at blog.forrestthewoods.com/4cffeed33fdb) - - - drag and drop: focus drag target window on hold (even without open) - - drag and drop: releasing a drop shows the "..." tooltip for one frame - since e13e598 (#1725) - - drag and drop: drag source on a group object (would need e.g. an invisible button covering group in EndGroup) https://twitter.com/paniq/status/1121446364909535233 - - drag and drop: have some way to know when a drag begin from BeginDragDropSource() pov. (see 2018/01/11 post in #143) - - drag and drop: allow preview tooltip to be submitted from a different place than the drag source. (#1725) - - drag and drop: make it easier and provide a demo to have tooltip both are source and target site, with a more detailed one on target site (tooltip ordering problem) - - drag and drop: demo with reordering nodes (in a list, or a tree node). (#143) - - drag and drop: test integrating with os drag and drop (make it easy to do a naive WM_DROPFILE integration) - - drag and drop: allow for multiple payload types. (#143) - - drag and drop: make payload optional? payload promise? (see 2018/01/11 post in #143) - - drag and drop: (#143) "both an in-process pointer and a promise to generate a serialized version, for whether the drag ends inside or outside the same process" - - drag and drop: feedback when hovering a region blocked by modal (mouse cursor "NO"?) - - - markup: simple markup language for color change? (#902, #3130) - - - text: selectable text (for copy) as a generic feature (ItemFlags?) - - text: proper alignment options in imgui_internal.h - - text: provided a framed text helper, e.g. https://pastebin.com/1Laxy8bT - - text: refactor TextUnformatted (or underlying function) to more explicitly request if we need width measurement or not - - text/layout/tabs: \t pulling position from base pos + step, or offset array (e.g. could be used in text edit, menus for simple icon+text alignment, etc.) - - text link/url button: underlined. should api expose an ID or use text contents as ID? which colors enum to use? - - text/wrapped: should be a more first-class citizen, e.g. wrapped text within a Selectable with known width. - - text/wrapped: custom separator for text wrapping. (#3002) - - text/wrapped: figure out better way to use TextWrapped() in an always auto-resize context (tooltip, etc.) (#249) - - - font: arbitrary line spacing. (#2945) - - font: MergeMode: flags to select overwriting or not (this is now very easy with refactored ImFontAtlasBuildWithStbTruetype) - - font: free the Alpha buffer if user only requested RGBA. -!- font: better CalcTextSizeA() API, at least for simple use cases. current one is horrible (perhaps have simple vs extended versions). - - font: for the purpose of RenderTextEllipsis(), it might be useful that CalcTextSizeA() can ignore the trailing padding? - - font: a CalcTextHeight() helper could run faster than CalcTextSize().y - - font: enforce monospace through ImFontConfig (for icons?) + create dual ImFont output from same input, reusing rasterized data but with different glyphs/AdvanceX - - font: finish CustomRectRegister() to allow mapping Unicode codepoint to custom texture data - - font: remove ID from CustomRect registration, it seems unnecessary! - - font: make it easier to submit own bitmap font (same texture, another texture?). (#2127, #2575) - - font: PushFontSize API (#1018) - - font: MemoryTTF taking ownership confusing/not obvious, maybe default should be opposite? - - font: storing MinAdvanceX per font would allow us to skip calculating line width (under a threshold of character count) in loops looking for block width - - font/demo: add tools to show glyphs used by a text blob, display U16 value, list missing glyphs. - - font/demo: demonstrate use of ImFontGlyphRangesBuilder. - - font/atlas: add a missing Glyphs.reserve() - - font/atlas: incremental updates - - font/atlas: dynamic font atlas to avoid baking huge ranges into bitmap and make scaling easier. - - font/draw: vertical and/or rotated text renderer (#705) - vertical is easier clipping wise - - font/draw: need to be able to specify wrap start position. - - font/draw: better reserve policy for large horizontal block of text (shouldn't reserve for all clipped lines). also see #3349. - - font/draw: fix for drawing 16k+ visible characters in same call. - - font/draw: underline, squiggle line rendering helpers. - - font: optimization: for monospace font (like the default one) we can trim IndexXAdvance as long as trailing value is == FallbackXAdvance (need to make sure TAB is still correct), would save on cache line. - - font: add support for kerning, probably optional. A) perhaps default to (32..128)^2 matrix ~ 9K entries = 36KB, then hash for non-ascii?. B) or sparse lookup into per-char list? - - font: add a simpler CalcTextSizeA() api? current one ok but not welcome if user needs to call it directly (without going through ImGui::CalcTextSize) - - font: fix AddRemapChar() to work before atlas has been built. - - font: (api breaking) remove "TTF" from symbol names. also because it now supports OTF. - - font/opt: Considering storing standalone AdvanceX table as 16-bit fixed point integer? - - font/opt: Glyph currently 40 bytes (2+9*4). Consider storing UV as 16-bits integer? (->32 bytes). X0/Y0/X1/Y1 as 16 fixed-point integers? Or X0/Y0 as float and X1/Y1 as fixed8_8? - - - nav: visual feedback on button press. - - nav: some features such as PageUp/Down/Home/End should probably work without ImGuiConfigFlags_NavEnableKeyboard? (where do we draw the line? how about CTRL+Tab) - ! nav: never clear NavId on some setup (e.g. gamepad centric) - - nav: there's currently no way to completely clear focus with the keyboard. depending on patterns used by the application to dispatch inputs, it may be desirable. - - nav: Home/End behavior when navigable item is not fully visible at the edge of scrolling? should be backtrack to keep item into view? - - nav: NavScrollToBringItemIntoView() with item bigger than view should focus top-right? Repro: using Nav in "About Window" - - nav: wrap around logic to allow e.g. grid based layout (pressing NavRight on the right-most element would go to the next row, etc.). see internal's NavMoveRequestTryWrapping(). - - nav: patterns to make it possible for arrows key to update selection (see JustMovedTo in range_select branch) - - nav: restore/find nearest NavId when current one disappear (e.g. pressed a button that disappear, or perhaps auto restoring when current button change name) - - nav: SetItemDefaultFocus() level of priority, so widget like Selectable when inside a popup could claim a low-priority default focus on the first selected iem - - nav: NavFlattened: init requests don't work properly on flattened siblings. - - nav: NavFlattened: pageup/pagedown/home/end don't work properly on flattened siblings. - - nav: NavFlattened: ESC on a flattened child should select something. - - nav: NavFlattened: broken: in typical usage scenario, the items of a fully clipped child are currently not considered to enter into a NavFlattened child. - - nav: NavFlattened: cannot access menu-bar of a flattened child window with Alt/menu key (not a very common use case..). - - nav: simulate right-click or context activation? (SHIFT+F10, keyboard Menu key?) - - nav/popup: esc/enter default behavior for popups, e.g. be able to mark an "ok" or "cancel" button that would get triggered by those keys, default validation button, etc. - - nav/treenode: left within a tree node block as a fallback (ImGuiTreeNodeFlags_NavLeftJumpsBackHere by default?) - - nav/menus: pressing left-right on a vertically clipped menu bar tends to jump to the collapse/close buttons. - - nav/menus: allow pressing Menu to leave a sub-menu. - - nav/menus: a way to access the main menu bar with Alt? (currently needs CTRL+TAB) or last focused window menu bar? - - nav/menus: when using the main menu bar, even though we restore focus after, the underlying window loses its title bar highlight during menu manipulation. could we prevent it? - - nav/menus: main menu bar currently cannot restore a nullptr focus. Could save NavWindow at the time of being focused, similarly to what popup do? - - nav/menus: Alt,Up could open the first menu (e.g. "File") currently it tends to nav into the window/collapse menu. Do do that we would need custom transition? - - nav/windowing: when CTRL+Tab/windowing is active, the HoveredWindow detection doesn't take account of the window display re-ordering. - - nav/windowing: Resizing window will currently fail with certain types of resizing constraints/callback applied - - focus: preserve ActiveId/focus stack state, e.g. when opening a menu and close it, previously selected InputText() focus gets restored (#622) - - - viewport: make it possible to have no main/hosting viewport - - viewport: We set ImGuiViewportFlags_NoFocusOnAppearing in a way that is required for GLFW/SDL binding, but could be handled better without - on a custom e.g. Win32 bindings. It prevents newly dragged-out viewports from taking the focus, which makes ALT+F4 more ambiguous. - - viewport: not focusing newly undocked viewport means clicking back on previous one doesn't bring OS window to front. - - viewport: with platform decoration enabled, platform may force constraint (e.g. minimum size) - - viewport: use getfocus/setfocus api to synchronize imgui<>platform focus better (e.g imgui-side ctrl-tab can focus os window, OS initial setup and alt-tab can focus imgui window etc.) - - viewport: store per-viewport/monitor DPI in .ini file so an application reload or main window changing DPI on reload can be properly patched for. - - viewport: implicit/fallback Debug window can hog a zombie viewport (harmless, noisy?) > could at least clear out the reference on a per session basis? - - viewport: need to clarify how to use GetMousePos() from a user point of view. - - platform: glfw: no support for ImGuiBackendFlags_HasMouseHoveredViewport. - - platform: sdl: no support for ImGuiBackendFlags_HasMouseHoveredViewport. maybe we could use SDL_GetMouseFocus() / SDL_WINDOW_MOUSE_FOCUS if imgui could fallback on its heuristic when NoInputs is set - - platform: sdl: no refresh of monitor/display (SDL doesn't seem to have an event for it). - - platform: sdl: multi-viewport + minimized window seems to break mouse wheel events (at least under Win32). - - - inputs: support track pad style scrolling & slider edit. - - inputs/io: backspace and arrows in the context of a text input could use system repeat rate. - - inputs/io: clarify/standardize/expose repeat rate and repeat delays (#1808) - - inputs/scrolling: support for smooth scrolling (#2462, #2569) - - - misc: idle: expose "woken up" boolean (set by inputs) and/or animation time (for cursor blink) for backend to be able stop refreshing easily. - - misc: idle: if cursor blink if the _only_ visible animation, core imgui could rewrite vertex alpha to avoid CPU pass on ImGui:: calls. - - misc: idle: if cursor blink if the _only_ visible animation, could even expose a dirty rectangle that optionally can be leverage by some app to render in a smaller viewport, getting rid of much pixel shading cost. - - misc: no way to run a root-most GetID() with ImGui:: api since there's always a Debug window in the stack. (mentioned in #2960) - - misc: make the ImGuiCond values linear (non-power-of-two). internal storage for ImGuiWindow can use integers to combine into flags (Why?) - - misc: PushItemFlag(): add a flag to disable keyboard capture when used with mouse? (#1682) - - misc: use more size_t in public api? - - misc: possible compile-time support for string view/range instead of char* would e.g. facilitate usage with Rust (#683, #3038, WIP string_view branch) - - misc: possible compile-time support for wchar_t instead of char*? - - - demo: demonstrate using PushStyleVar() in more details. - - demo: add vertical separator demo - - demo: add virtual scrolling example? - - demo: demonstrate Plot offset - - demo: window size constraint: square demo is broken when resizing from edges (#1975), would need to rework the callback system to solve this - - - examples: window minimize, maximize (#583) - - examples: provide a zero frame-rate/idle example. - - examples: dx11/dx12: try to use new swapchain blit models (#2970) - - backends: report it better when not able to create texture? - - backends: glfw: could go idle when minimized? if (glfwGetWindowAttrib(window, GLFW_ICONIFIED)) { glfwWaitEvents(); continue; } // issue: DeltaTime will be super high on resume, perhaps provide a way to let impl know (#440) - - backends: opengl: rename imgui_impl_opengl2 to impl_opengl_legacy and imgui_impl_opengl3 to imgui_impl_opengl? (#1900) - - backends: opengl: could use a single vertex buffer and glBufferSubData for uploads? - - backends: opengl: explicitly disable GL_STENCIL_TEST in bindings. - - backends: vulkan: viewport: support for synchronized swapping of multiple swap chains. - - backends: bgfx: https://gist.github.com/RichardGale/6e2b74bc42b3005e08397236e4be0fd0 - - backends: emscriptem: with refactored examples, we could provide a direct imgui_impl_emscripten platform layer (see eg. https://github.com/floooh/sokol-samples/blob/master/html5/imgui-emsc.cc#L42) - - - bindings: ways to use clang ast dump to generate bindings or helpers for bindings? (e.g. clang++ -Xclang -ast-dump=json imgui.h) (WIP project "dear-bindings" still private) - - - optimization: replace vsnprintf with stb_printf? using IMGUI_USE_STB_SPRINTF. (#1038 + needed for string_view) - - optimization: add clipping for multi-component widgets (SliderFloatX, ColorEditX, etc.). one problem is that nav branch can't easily clip parent group when there is a move request. - - optimization: add a flag to disable most of rendering, for the case where the user expect to skip it (#335) - - optimization: fully covered window (covered by another with non-translucent bg + WindowRounding worth of padding) may want to clip rendering. - - optimization: use another hash function than crc32, e.g. FNV1a - - optimization: turn some the various stack vectors into statically-sized arrays diff --git a/app/jni/src/libultraship/extern/ImGui/examples/README.txt b/app/jni/src/libultraship/extern/ImGui/examples/README.txt deleted file mode 100644 index 6db2f3c..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/README.txt +++ /dev/null @@ -1,9 +0,0 @@ -See BACKENDS and EXAMPLES files in the docs/ folder, or on the web at: https://github.com/ocornut/imgui/tree/master/docs - -Backends = Helper code to facilitate integration with platforms/graphics api (used by Examples + should be used by your app). -Examples = Standalone applications showcasing integration with platforms/graphics api. - -Some Examples have extra README files in their respective directory, please check them too! - -Once Dear ImGui is running (in either examples or your own application/game/engine), -run and refer to ImGui::ShowDemoWindow() in imgui_demo.cpp for the end-user API. diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_allegro5/README.md b/app/jni/src/libultraship/extern/ImGui/examples/example_allegro5/README.md deleted file mode 100644 index 4af31f6..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_allegro5/README.md +++ /dev/null @@ -1,36 +0,0 @@ - -# Configuration - -Dear ImGui outputs 16-bit vertex indices by default. -Allegro doesn't support them natively, so we have two solutions: convert the indices manually in imgui_impl_allegro5.cpp, or compile dear imgui with 32-bit indices. -You can either modify imconfig.h that comes with Dear ImGui (easier), or set a C++ preprocessor option IMGUI_USER_CONFIG to find to a filename. -We are providing `imconfig_allegro5.h` that enables 32-bit indices. -Note that the backend supports _BOTH_ 16-bit and 32-bit indices, but 32-bit indices will be slightly faster as they won't require a manual conversion. - -# How to Build - -### On Ubuntu 14.04+ and macOS - -```bash -g++ -DIMGUI_USER_CONFIG=\"examples/example_allegro5/imconfig_allegro5.h\" -I .. -I ../.. -I ../../backends main.cpp ../../backends/imgui_impl_allegro5.cpp ../../imgui*.cpp -lallegro -lallegro_main -lallegro_primitives -o allegro5_example -``` - -On macOS, install Allegro with homebrew: `brew install allegro`. - -### On Windows with Visual Studio's CLI - -You may install Allegro using vcpkg: -``` -git clone https://github.com/Microsoft/vcpkg -cd vcpkg -bootstrap-vcpkg.bat -vcpkg install allegro5 --triplet=x86-windows ; for win32 -vcpkg install allegro5 --triplet=x64-windows ; for win64 -vcpkg integrate install ; register include / libs in Visual Studio -``` - -Build: -``` -set ALLEGRODIR=path_to_your_allegro5_folder -cl /Zi /MD /utf-8 /I %ALLEGRODIR%\include /DIMGUI_USER_CONFIG=\"examples/example_allegro5/imconfig_allegro5.h\" /I .. /I ..\.. /I ..\..\backends main.cpp ..\..\backends\imgui_impl_allegro5.cpp ..\..\imgui*.cpp /link /LIBPATH:%ALLEGRODIR%\lib allegro-5.0.10-monolith-md.lib user32.lib -``` diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_allegro5/example_allegro5.vcxproj b/app/jni/src/libultraship/extern/ImGui/examples/example_allegro5/example_allegro5.vcxproj deleted file mode 100644 index 02f6a47..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_allegro5/example_allegro5.vcxproj +++ /dev/null @@ -1,185 +0,0 @@ - - - - - Debug - Win32 - - - Debug - x64 - - - Release - Win32 - - - Release - x64 - - - - {73F235B5-7D31-4FC6-8682-DDC5A097B9C1} - example_allegro5 - 8.1 - - - - Application - true - MultiByte - v140 - - - Application - true - MultiByte - v140 - - - Application - false - true - MultiByte - v140 - - - Application - false - true - MultiByte - v140 - - - - - - - - - - - - - - - - - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - - Level4 - Disabled - ..\..;..\..\backends;%(AdditionalIncludeDirectories) - /utf-8 %(AdditionalOptions) - - - true - %(AdditionalLibraryDirectories) - opengl32.lib;%(AdditionalDependencies) - Console - msvcrt.lib - - - - - Level4 - Disabled - ..\..;..\..\backends;%(AdditionalIncludeDirectories) - /utf-8 %(AdditionalOptions) - - - true - %(AdditionalLibraryDirectories) - opengl32.lib;%(AdditionalDependencies) - Console - msvcrt.lib - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends;%(AdditionalIncludeDirectories) - false - /utf-8 %(AdditionalOptions) - - - true - true - true - %(AdditionalLibraryDirectories) - opengl32.lib;%(AdditionalDependencies) - Console - - - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends;%(AdditionalIncludeDirectories) - false - /utf-8 %(AdditionalOptions) - - - true - true - true - %(AdditionalLibraryDirectories) - opengl32.lib;%(AdditionalDependencies) - Console - - - - - - - - - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_allegro5/example_allegro5.vcxproj.filters b/app/jni/src/libultraship/extern/ImGui/examples/example_allegro5/example_allegro5.vcxproj.filters deleted file mode 100644 index 84881d3..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_allegro5/example_allegro5.vcxproj.filters +++ /dev/null @@ -1,61 +0,0 @@ - - - - - {20b90ce4-7fcb-4731-b9a0-075f875de82d} - - - {f18ab499-84e1-499f-8eff-9754361e0e52} - cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx - - - - - imgui - - - imgui - - - imgui - - - sources - - - sources - - - sources - - - imgui - - - imgui - - - - - imgui - - - imgui - - - imgui - - - sources - - - - - - imgui - - - imgui - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_allegro5/imconfig_allegro5.h b/app/jni/src/libultraship/extern/ImGui/examples/example_allegro5/imconfig_allegro5.h deleted file mode 100644 index 35afa67..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_allegro5/imconfig_allegro5.h +++ /dev/null @@ -1,11 +0,0 @@ -//----------------------------------------------------------------------------- -// COMPILE-TIME OPTIONS FOR DEAR IMGUI ALLEGRO 5 EXAMPLE -// See imconfig.h for the full template -// Because Allegro doesn't support 16-bit vertex indices, we enable the compile-time option of imgui to use 32-bit indices -//----------------------------------------------------------------------------- - -#pragma once - -// Use 32-bit vertex indices because Allegro doesn't support 16-bit ones -// This allows us to avoid converting vertices format at runtime -#define ImDrawIdx int diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_allegro5/main.cpp b/app/jni/src/libultraship/extern/ImGui/examples/example_allegro5/main.cpp deleted file mode 100644 index 298c845..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_allegro5/main.cpp +++ /dev/null @@ -1,150 +0,0 @@ -// Dear ImGui: standalone example application for Allegro 5 - -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -// On Windows, you can install Allegro5 using vcpkg: -// git clone https://github.com/Microsoft/vcpkg -// cd vcpkg -// bootstrap - vcpkg.bat -// vcpkg install allegro5 --triplet=x86-windows ; for win32 -// vcpkg install allegro5 --triplet=x64-windows ; for win64 -// vcpkg integrate install ; register include and libs in Visual Studio - -#include -#include -#include -#include "imgui.h" -#include "imgui_impl_allegro5.h" - -int main(int, char**) -{ - // Setup Allegro - al_init(); - al_install_keyboard(); - al_install_mouse(); - al_init_primitives_addon(); - al_set_new_display_flags(ALLEGRO_RESIZABLE); - ALLEGRO_DISPLAY* display = al_create_display(1280, 720); - al_set_window_title(display, "Dear ImGui Allegro 5 example"); - ALLEGRO_EVENT_QUEUE* queue = al_create_event_queue(); - al_register_event_source(queue, al_get_display_event_source(display)); - al_register_event_source(queue, al_get_keyboard_event_source()); - al_register_event_source(queue, al_get_mouse_event_source()); - - // Setup Dear ImGui context - IMGUI_CHECKVERSION(); - ImGui::CreateContext(); - ImGuiIO& io = ImGui::GetIO(); (void)io; - io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard; // Enable Keyboard Controls - io.ConfigFlags |= ImGuiConfigFlags_DockingEnable; // Enable Docking - - // Setup Dear ImGui style - ImGui::StyleColorsDark(); - //ImGui::StyleColorsLight(); - - // Setup Platform/Renderer backends - ImGui_ImplAllegro5_Init(display); - - // Load Fonts - // - If no fonts are loaded, dear imgui will use the default font. You can also load multiple fonts and use ImGui::PushFont()/PopFont() to select them. - // - AddFontFromFileTTF() will return the ImFont* so you can store it if you need to select the font among multiple. - // - If the file cannot be loaded, the function will return a nullptr. Please handle those errors in your application (e.g. use an assertion, or display an error and quit). - // - The fonts will be rasterized at a given size (w/ oversampling) and stored into a texture when calling ImFontAtlas::Build()/GetTexDataAsXXXX(), which ImGui_ImplXXXX_NewFrame below will call. - // - Use '#define IMGUI_ENABLE_FREETYPE' in your imconfig file to use Freetype for higher quality font rendering. - // - Read 'docs/FONTS.md' for more instructions and details. - // - Remember that in C/C++ if you want to include a backslash \ in a string literal you need to write a double backslash \\ ! - //io.Fonts->AddFontDefault(); - //io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\segoeui.ttf", 18.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/DroidSans.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Roboto-Medium.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Cousine-Regular.ttf", 15.0f); - //ImFont* font = io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\ArialUni.ttf", 18.0f, nullptr, io.Fonts->GetGlyphRangesJapanese()); - //IM_ASSERT(font != nullptr); - - bool show_demo_window = true; - bool show_another_window = false; - ImVec4 clear_color = ImVec4(0.45f, 0.55f, 0.60f, 1.00f); - - // Main loop - bool running = true; - while (running) - { - // Poll and handle events (inputs, window resize, etc.) - // You can read the io.WantCaptureMouse, io.WantCaptureKeyboard flags to tell if dear imgui wants to use your inputs. - // - When io.WantCaptureMouse is true, do not dispatch mouse input data to your main application, or clear/overwrite your copy of the mouse data. - // - When io.WantCaptureKeyboard is true, do not dispatch keyboard input data to your main application, or clear/overwrite your copy of the keyboard data. - // Generally you may always pass all inputs to dear imgui, and hide them from your application based on those two flags. - ALLEGRO_EVENT ev; - while (al_get_next_event(queue, &ev)) - { - ImGui_ImplAllegro5_ProcessEvent(&ev); - if (ev.type == ALLEGRO_EVENT_DISPLAY_CLOSE) - running = false; - if (ev.type == ALLEGRO_EVENT_DISPLAY_RESIZE) - { - ImGui_ImplAllegro5_InvalidateDeviceObjects(); - al_acknowledge_resize(display); - ImGui_ImplAllegro5_CreateDeviceObjects(); - } - } - - // Start the Dear ImGui frame - ImGui_ImplAllegro5_NewFrame(); - ImGui::NewFrame(); - - // 1. Show the big demo window (Most of the sample code is in ImGui::ShowDemoWindow()! You can browse its code to learn more about Dear ImGui!). - if (show_demo_window) - ImGui::ShowDemoWindow(&show_demo_window); - - // 2. Show a simple window that we create ourselves. We use a Begin/End pair to create a named window. - { - static float f = 0.0f; - static int counter = 0; - - ImGui::Begin("Hello, world!"); // Create a window called "Hello, world!" and append into it. - - ImGui::Text("This is some useful text."); // Display some text (you can use a format strings too) - ImGui::Checkbox("Demo Window", &show_demo_window); // Edit bools storing our window open/close state - ImGui::Checkbox("Another Window", &show_another_window); - - ImGui::SliderFloat("float", &f, 0.0f, 1.0f); // Edit 1 float using a slider from 0.0f to 1.0f - ImGui::ColorEdit3("clear color", (float*)&clear_color); // Edit 3 floats representing a color - - if (ImGui::Button("Button")) // Buttons return true when clicked (most widgets return true when edited/activated) - counter++; - ImGui::SameLine(); - ImGui::Text("counter = %d", counter); - - ImGui::Text("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / io.Framerate, io.Framerate); - ImGui::End(); - } - - // 3. Show another simple window. - if (show_another_window) - { - ImGui::Begin("Another Window", &show_another_window); // Pass a pointer to our bool variable (the window will have a closing button that will clear the bool when clicked) - ImGui::Text("Hello from another window!"); - if (ImGui::Button("Close Me")) - show_another_window = false; - ImGui::End(); - } - - // Rendering - ImGui::Render(); - al_clear_to_color(al_map_rgba_f(clear_color.x * clear_color.w, clear_color.y * clear_color.w, clear_color.z * clear_color.w, clear_color.w)); - ImGui_ImplAllegro5_RenderDrawData(ImGui::GetDrawData()); - al_flip_display(); - } - - // Cleanup - ImGui_ImplAllegro5_Shutdown(); - ImGui::DestroyContext(); - al_destroy_event_queue(queue); - al_destroy_display(display); - - return 0; -} diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_android_opengl3/CMakeLists.txt b/app/jni/src/libultraship/extern/ImGui/examples/example_android_opengl3/CMakeLists.txt deleted file mode 100644 index 63531f4..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_android_opengl3/CMakeLists.txt +++ /dev/null @@ -1,40 +0,0 @@ -cmake_minimum_required(VERSION 3.6) - -project(ImGuiExample) - -set(CMAKE_CXX_STANDARD 11) -set(CMAKE_CXX_STANDARD_REQUIRED ON) -set(CMAKE_CXX_EXTENSIONS OFF) - -add_library(${CMAKE_PROJECT_NAME} SHARED - ${CMAKE_CURRENT_SOURCE_DIR}/main.cpp - ${CMAKE_CURRENT_SOURCE_DIR}/../../imgui.cpp - ${CMAKE_CURRENT_SOURCE_DIR}/../../imgui_demo.cpp - ${CMAKE_CURRENT_SOURCE_DIR}/../../imgui_draw.cpp - ${CMAKE_CURRENT_SOURCE_DIR}/../../imgui_tables.cpp - ${CMAKE_CURRENT_SOURCE_DIR}/../../imgui_widgets.cpp - ${CMAKE_CURRENT_SOURCE_DIR}/../../backends/imgui_impl_android.cpp - ${CMAKE_CURRENT_SOURCE_DIR}/../../backends/imgui_impl_opengl3.cpp - ${ANDROID_NDK}/sources/android/native_app_glue/android_native_app_glue.c -) - -set(CMAKE_SHARED_LINKER_FLAGS - "${CMAKE_SHARED_LINKER_FLAGS} -u ANativeActivity_onCreate" -) - -target_compile_definitions(${CMAKE_PROJECT_NAME} PRIVATE - IMGUI_IMPL_OPENGL_ES3 -) - -target_include_directories(${CMAKE_PROJECT_NAME} PRIVATE - ${CMAKE_CURRENT_SOURCE_DIR}/../.. - ${CMAKE_CURRENT_SOURCE_DIR}/../../backends - ${ANDROID_NDK}/sources/android/native_app_glue -) - -target_link_libraries(${CMAKE_PROJECT_NAME} PRIVATE - android - EGL - GLESv3 - log -) diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_android_opengl3/android/.gitignore b/app/jni/src/libultraship/extern/ImGui/examples/example_android_opengl3/android/.gitignore deleted file mode 100644 index 3c7a619..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_android_opengl3/android/.gitignore +++ /dev/null @@ -1,12 +0,0 @@ -.cxx -.externalNativeBuild -build/ -*.iml - -.idea -.gradle -local.properties - -# Android Studio puts a Gradle wrapper here, that we don't want: -gradle/ -gradlew* diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_android_opengl3/android/app/build.gradle b/app/jni/src/libultraship/extern/ImGui/examples/example_android_opengl3/android/app/build.gradle deleted file mode 100644 index 53181ba..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_android_opengl3/android/app/build.gradle +++ /dev/null @@ -1,46 +0,0 @@ -apply plugin: 'com.android.application' -apply plugin: 'kotlin-android' - -android { - compileSdkVersion 33 - buildToolsVersion "33.0.2" - ndkVersion "25.2.9519653" - - defaultConfig { - applicationId "imgui.example.android" - namespace "imgui.example.android" - minSdkVersion 24 - targetSdkVersion 33 - versionCode 1 - versionName "1.0" - } - - buildTypes { - release { - minifyEnabled false - proguardFiles getDefaultProguardFile('proguard-android-optimize.txt') - } - } - - compileOptions { - sourceCompatibility JavaVersion.VERSION_11 - targetCompatibility JavaVersion.VERSION_11 - } - - kotlinOptions { - jvmTarget="11" - } - - externalNativeBuild { - cmake { - path "../../CMakeLists.txt" - version '3.22.1' - } - } -} -repositories { - mavenCentral() -} -dependencies { - implementation "org.jetbrains.kotlin:kotlin-stdlib-jdk7:$kotlin_version" -} diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_android_opengl3/android/app/src/main/AndroidManifest.xml b/app/jni/src/libultraship/extern/ImGui/examples/example_android_opengl3/android/app/src/main/AndroidManifest.xml deleted file mode 100644 index a87b95b..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_android_opengl3/android/app/src/main/AndroidManifest.xml +++ /dev/null @@ -1,24 +0,0 @@ - - - - - - - - - - - - - - - diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_android_opengl3/android/app/src/main/java/MainActivity.kt b/app/jni/src/libultraship/extern/ImGui/examples/example_android_opengl3/android/app/src/main/java/MainActivity.kt deleted file mode 100644 index 896a88c..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_android_opengl3/android/app/src/main/java/MainActivity.kt +++ /dev/null @@ -1,40 +0,0 @@ -package imgui.example.android - -import android.app.NativeActivity -import android.os.Bundle -import android.content.Context -import android.view.inputmethod.InputMethodManager -import android.view.KeyEvent -import java.util.concurrent.LinkedBlockingQueue - -class MainActivity : NativeActivity() { - public override fun onCreate(savedInstanceState: Bundle?) { - super.onCreate(savedInstanceState) - } - - fun showSoftInput() { - val inputMethodManager = getSystemService(Context.INPUT_METHOD_SERVICE) as InputMethodManager - inputMethodManager.showSoftInput(this.window.decorView, 0) - } - - fun hideSoftInput() { - val inputMethodManager = getSystemService(Context.INPUT_METHOD_SERVICE) as InputMethodManager - inputMethodManager.hideSoftInputFromWindow(this.window.decorView.windowToken, 0) - } - - // Queue for the Unicode characters to be polled from native code (via pollUnicodeChar()) - private var unicodeCharacterQueue: LinkedBlockingQueue = LinkedBlockingQueue() - - // We assume dispatchKeyEvent() of the NativeActivity is actually called for every - // KeyEvent and not consumed by any View before it reaches here - override fun dispatchKeyEvent(event: KeyEvent): Boolean { - if (event.action == KeyEvent.ACTION_DOWN) { - unicodeCharacterQueue.offer(event.getUnicodeChar(event.metaState)) - } - return super.dispatchKeyEvent(event) - } - - fun pollUnicodeChar(): Int { - return unicodeCharacterQueue.poll() ?: 0 - } -} diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_android_opengl3/android/build.gradle b/app/jni/src/libultraship/extern/ImGui/examples/example_android_opengl3/android/build.gradle deleted file mode 100644 index ccd2185..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_android_opengl3/android/build.gradle +++ /dev/null @@ -1,24 +0,0 @@ -buildscript { - ext.kotlin_version = '1.8.0' - repositories { - google() - mavenCentral() - - } - dependencies { - classpath 'com.android.tools.build:gradle:7.4.1' - classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlin_version" - - } -} - -allprojects { - repositories { - google() - mavenCentral() - } -} - -task clean(type: Delete) { - delete rootProject.buildDir -} diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_android_opengl3/android/settings.gradle b/app/jni/src/libultraship/extern/ImGui/examples/example_android_opengl3/android/settings.gradle deleted file mode 100644 index e7b4def..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_android_opengl3/android/settings.gradle +++ /dev/null @@ -1 +0,0 @@ -include ':app' diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_android_opengl3/main.cpp b/app/jni/src/libultraship/extern/ImGui/examples/example_android_opengl3/main.cpp deleted file mode 100644 index 2316ce6..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_android_opengl3/main.cpp +++ /dev/null @@ -1,383 +0,0 @@ -// dear imgui: standalone example application for Android + OpenGL ES 3 - -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#include "imgui.h" -#include "imgui_impl_android.h" -#include "imgui_impl_opengl3.h" -#include -#include -#include -#include -#include -#include - -// Data -static EGLDisplay g_EglDisplay = EGL_NO_DISPLAY; -static EGLSurface g_EglSurface = EGL_NO_SURFACE; -static EGLContext g_EglContext = EGL_NO_CONTEXT; -static struct android_app* g_App = nullptr; -static bool g_Initialized = false; -static char g_LogTag[] = "ImGuiExample"; -static std::string g_IniFilename = ""; - -// Forward declarations of helper functions -static void Init(struct android_app* app); -static void Shutdown(); -static void MainLoopStep(); -static int ShowSoftKeyboardInput(); -static int PollUnicodeChars(); -static int GetAssetData(const char* filename, void** out_data); - -// Main code -static void handleAppCmd(struct android_app* app, int32_t appCmd) -{ - switch (appCmd) - { - case APP_CMD_SAVE_STATE: - break; - case APP_CMD_INIT_WINDOW: - Init(app); - break; - case APP_CMD_TERM_WINDOW: - Shutdown(); - break; - case APP_CMD_GAINED_FOCUS: - case APP_CMD_LOST_FOCUS: - break; - } -} - -static int32_t handleInputEvent(struct android_app* app, AInputEvent* inputEvent) -{ - return ImGui_ImplAndroid_HandleInputEvent(inputEvent); -} - -void android_main(struct android_app* app) -{ - app->onAppCmd = handleAppCmd; - app->onInputEvent = handleInputEvent; - - while (true) - { - int out_events; - struct android_poll_source* out_data; - - // Poll all events. If the app is not visible, this loop blocks until g_Initialized == true. - while (ALooper_pollAll(g_Initialized ? 0 : -1, nullptr, &out_events, (void**)&out_data) >= 0) - { - // Process one event - if (out_data != nullptr) - out_data->process(app, out_data); - - // Exit the app by returning from within the infinite loop - if (app->destroyRequested != 0) - { - // shutdown() should have been called already while processing the - // app command APP_CMD_TERM_WINDOW. But we play save here - if (!g_Initialized) - Shutdown(); - - return; - } - } - - // Initiate a new frame - MainLoopStep(); - } -} - -void Init(struct android_app* app) -{ - if (g_Initialized) - return; - - g_App = app; - ANativeWindow_acquire(g_App->window); - - // Initialize EGL - // This is mostly boilerplate code for EGL... - { - g_EglDisplay = eglGetDisplay(EGL_DEFAULT_DISPLAY); - if (g_EglDisplay == EGL_NO_DISPLAY) - __android_log_print(ANDROID_LOG_ERROR, g_LogTag, "%s", "eglGetDisplay(EGL_DEFAULT_DISPLAY) returned EGL_NO_DISPLAY"); - - if (eglInitialize(g_EglDisplay, 0, 0) != EGL_TRUE) - __android_log_print(ANDROID_LOG_ERROR, g_LogTag, "%s", "eglInitialize() returned with an error"); - - const EGLint egl_attributes[] = { EGL_BLUE_SIZE, 8, EGL_GREEN_SIZE, 8, EGL_RED_SIZE, 8, EGL_DEPTH_SIZE, 24, EGL_SURFACE_TYPE, EGL_WINDOW_BIT, EGL_NONE }; - EGLint num_configs = 0; - if (eglChooseConfig(g_EglDisplay, egl_attributes, nullptr, 0, &num_configs) != EGL_TRUE) - __android_log_print(ANDROID_LOG_ERROR, g_LogTag, "%s", "eglChooseConfig() returned with an error"); - if (num_configs == 0) - __android_log_print(ANDROID_LOG_ERROR, g_LogTag, "%s", "eglChooseConfig() returned 0 matching config"); - - // Get the first matching config - EGLConfig egl_config; - eglChooseConfig(g_EglDisplay, egl_attributes, &egl_config, 1, &num_configs); - EGLint egl_format; - eglGetConfigAttrib(g_EglDisplay, egl_config, EGL_NATIVE_VISUAL_ID, &egl_format); - ANativeWindow_setBuffersGeometry(g_App->window, 0, 0, egl_format); - - const EGLint egl_context_attributes[] = { EGL_CONTEXT_CLIENT_VERSION, 3, EGL_NONE }; - g_EglContext = eglCreateContext(g_EglDisplay, egl_config, EGL_NO_CONTEXT, egl_context_attributes); - - if (g_EglContext == EGL_NO_CONTEXT) - __android_log_print(ANDROID_LOG_ERROR, g_LogTag, "%s", "eglCreateContext() returned EGL_NO_CONTEXT"); - - g_EglSurface = eglCreateWindowSurface(g_EglDisplay, egl_config, g_App->window, nullptr); - eglMakeCurrent(g_EglDisplay, g_EglSurface, g_EglSurface, g_EglContext); - } - - // Setup Dear ImGui context - IMGUI_CHECKVERSION(); - ImGui::CreateContext(); - ImGuiIO& io = ImGui::GetIO(); - - // Redirect loading/saving of .ini file to our location. - // Make sure 'g_IniFilename' persists while we use Dear ImGui. - g_IniFilename = std::string(app->activity->internalDataPath) + "/imgui.ini"; - io.IniFilename = g_IniFilename.c_str();; - - // Setup Dear ImGui style - ImGui::StyleColorsDark(); - //ImGui::StyleColorsLight(); - - // Setup Platform/Renderer backends - ImGui_ImplAndroid_Init(g_App->window); - ImGui_ImplOpenGL3_Init("#version 300 es"); - - // Load Fonts - // - If no fonts are loaded, dear imgui will use the default font. You can also load multiple fonts and use ImGui::PushFont()/PopFont() to select them. - // - If the file cannot be loaded, the function will return a nullptr. Please handle those errors in your application (e.g. use an assertion, or display an error and quit). - // - The fonts will be rasterized at a given size (w/ oversampling) and stored into a texture when calling ImFontAtlas::Build()/GetTexDataAsXXXX(), which ImGui_ImplXXXX_NewFrame below will call. - // - Read 'docs/FONTS.md' for more instructions and details. - // - Remember that in C/C++ if you want to include a backslash \ in a string literal you need to write a double backslash \\ ! - // - Android: The TTF files have to be placed into the assets/ directory (android/app/src/main/assets), we use our GetAssetData() helper to retrieve them. - - // We load the default font with increased size to improve readability on many devices with "high" DPI. - // FIXME: Put some effort into DPI awareness. - // Important: when calling AddFontFromMemoryTTF(), ownership of font_data is transfered by Dear ImGui by default (deleted is handled by Dear ImGui), unless we set FontDataOwnedByAtlas=false in ImFontConfig - ImFontConfig font_cfg; - font_cfg.SizePixels = 22.0f; - io.Fonts->AddFontDefault(&font_cfg); - //void* font_data; - //int font_data_size; - //ImFont* font; - //font_data_size = GetAssetData("segoeui.ttf", &font_data); - //font = io.Fonts->AddFontFromMemoryTTF(font_data, font_data_size, 16.0f); - //IM_ASSERT(font != nullptr); - //font_data_size = GetAssetData("DroidSans.ttf", &font_data); - //font = io.Fonts->AddFontFromMemoryTTF(font_data, font_data_size, 16.0f); - //IM_ASSERT(font != nullptr); - //font_data_size = GetAssetData("Roboto-Medium.ttf", &font_data); - //font = io.Fonts->AddFontFromMemoryTTF(font_data, font_data_size, 16.0f); - //IM_ASSERT(font != nullptr); - //font_data_size = GetAssetData("Cousine-Regular.ttf", &font_data); - //font = io.Fonts->AddFontFromMemoryTTF(font_data, font_data_size, 15.0f); - //IM_ASSERT(font != nullptr); - //font_data_size = GetAssetData("ArialUni.ttf", &font_data); - //font = io.Fonts->AddFontFromMemoryTTF(font_data, font_data_size, 18.0f, nullptr, io.Fonts->GetGlyphRangesJapanese()); - //IM_ASSERT(font != nullptr); - - // Arbitrary scale-up - // FIXME: Put some effort into DPI awareness - ImGui::GetStyle().ScaleAllSizes(3.0f); - - g_Initialized = true; -} - -void MainLoopStep() -{ - ImGuiIO& io = ImGui::GetIO(); - if (g_EglDisplay == EGL_NO_DISPLAY) - return; - - // Our state - // (we use static, which essentially makes the variable globals, as a convenience to keep the example code easy to follow) - static bool show_demo_window = true; - static bool show_another_window = false; - static ImVec4 clear_color = ImVec4(0.45f, 0.55f, 0.60f, 1.00f); - - // Poll Unicode characters via JNI - // FIXME: do not call this every frame because of JNI overhead - PollUnicodeChars(); - - // Open on-screen (soft) input if requested by Dear ImGui - static bool WantTextInputLast = false; - if (io.WantTextInput && !WantTextInputLast) - ShowSoftKeyboardInput(); - WantTextInputLast = io.WantTextInput; - - // Start the Dear ImGui frame - ImGui_ImplOpenGL3_NewFrame(); - ImGui_ImplAndroid_NewFrame(); - ImGui::NewFrame(); - - // 1. Show the big demo window (Most of the sample code is in ImGui::ShowDemoWindow()! You can browse its code to learn more about Dear ImGui!). - if (show_demo_window) - ImGui::ShowDemoWindow(&show_demo_window); - - // 2. Show a simple window that we create ourselves. We use a Begin/End pair to create a named window. - { - static float f = 0.0f; - static int counter = 0; - - ImGui::Begin("Hello, world!"); // Create a window called "Hello, world!" and append into it. - - ImGui::Text("This is some useful text."); // Display some text (you can use a format strings too) - ImGui::Checkbox("Demo Window", &show_demo_window); // Edit bools storing our window open/close state - ImGui::Checkbox("Another Window", &show_another_window); - - ImGui::SliderFloat("float", &f, 0.0f, 1.0f); // Edit 1 float using a slider from 0.0f to 1.0f - ImGui::ColorEdit3("clear color", (float*)&clear_color); // Edit 3 floats representing a color - - if (ImGui::Button("Button")) // Buttons return true when clicked (most widgets return true when edited/activated) - counter++; - ImGui::SameLine(); - ImGui::Text("counter = %d", counter); - - ImGui::Text("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / io.Framerate, io.Framerate); - ImGui::End(); - } - - // 3. Show another simple window. - if (show_another_window) - { - ImGui::Begin("Another Window", &show_another_window); // Pass a pointer to our bool variable (the window will have a closing button that will clear the bool when clicked) - ImGui::Text("Hello from another window!"); - if (ImGui::Button("Close Me")) - show_another_window = false; - ImGui::End(); - } - - // Rendering - ImGui::Render(); - glViewport(0, 0, (int)io.DisplaySize.x, (int)io.DisplaySize.y); - glClearColor(clear_color.x * clear_color.w, clear_color.y * clear_color.w, clear_color.z * clear_color.w, clear_color.w); - glClear(GL_COLOR_BUFFER_BIT); - ImGui_ImplOpenGL3_RenderDrawData(ImGui::GetDrawData()); - eglSwapBuffers(g_EglDisplay, g_EglSurface); -} - -void Shutdown() -{ - if (!g_Initialized) - return; - - // Cleanup - ImGui_ImplOpenGL3_Shutdown(); - ImGui_ImplAndroid_Shutdown(); - ImGui::DestroyContext(); - - if (g_EglDisplay != EGL_NO_DISPLAY) - { - eglMakeCurrent(g_EglDisplay, EGL_NO_SURFACE, EGL_NO_SURFACE, EGL_NO_CONTEXT); - - if (g_EglContext != EGL_NO_CONTEXT) - eglDestroyContext(g_EglDisplay, g_EglContext); - - if (g_EglSurface != EGL_NO_SURFACE) - eglDestroySurface(g_EglDisplay, g_EglSurface); - - eglTerminate(g_EglDisplay); - } - - g_EglDisplay = EGL_NO_DISPLAY; - g_EglContext = EGL_NO_CONTEXT; - g_EglSurface = EGL_NO_SURFACE; - ANativeWindow_release(g_App->window); - - g_Initialized = false; -} - -// Helper functions - -// Unfortunately, there is no way to show the on-screen input from native code. -// Therefore, we call ShowSoftKeyboardInput() of the main activity implemented in MainActivity.kt via JNI. -static int ShowSoftKeyboardInput() -{ - JavaVM* java_vm = g_App->activity->vm; - JNIEnv* java_env = nullptr; - - jint jni_return = java_vm->GetEnv((void**)&java_env, JNI_VERSION_1_6); - if (jni_return == JNI_ERR) - return -1; - - jni_return = java_vm->AttachCurrentThread(&java_env, nullptr); - if (jni_return != JNI_OK) - return -2; - - jclass native_activity_clazz = java_env->GetObjectClass(g_App->activity->clazz); - if (native_activity_clazz == nullptr) - return -3; - - jmethodID method_id = java_env->GetMethodID(native_activity_clazz, "showSoftInput", "()V"); - if (method_id == nullptr) - return -4; - - java_env->CallVoidMethod(g_App->activity->clazz, method_id); - - jni_return = java_vm->DetachCurrentThread(); - if (jni_return != JNI_OK) - return -5; - - return 0; -} - -// Unfortunately, the native KeyEvent implementation has no getUnicodeChar() function. -// Therefore, we implement the processing of KeyEvents in MainActivity.kt and poll -// the resulting Unicode characters here via JNI and send them to Dear ImGui. -static int PollUnicodeChars() -{ - JavaVM* java_vm = g_App->activity->vm; - JNIEnv* java_env = nullptr; - - jint jni_return = java_vm->GetEnv((void**)&java_env, JNI_VERSION_1_6); - if (jni_return == JNI_ERR) - return -1; - - jni_return = java_vm->AttachCurrentThread(&java_env, nullptr); - if (jni_return != JNI_OK) - return -2; - - jclass native_activity_clazz = java_env->GetObjectClass(g_App->activity->clazz); - if (native_activity_clazz == nullptr) - return -3; - - jmethodID method_id = java_env->GetMethodID(native_activity_clazz, "pollUnicodeChar", "()I"); - if (method_id == nullptr) - return -4; - - // Send the actual characters to Dear ImGui - ImGuiIO& io = ImGui::GetIO(); - jint unicode_character; - while ((unicode_character = java_env->CallIntMethod(g_App->activity->clazz, method_id)) != 0) - io.AddInputCharacter(unicode_character); - - jni_return = java_vm->DetachCurrentThread(); - if (jni_return != JNI_OK) - return -5; - - return 0; -} - -// Helper to retrieve data placed into the assets/ directory (android/app/src/main/assets) -static int GetAssetData(const char* filename, void** outData) -{ - int num_bytes = 0; - AAsset* asset_descriptor = AAssetManager_open(g_App->activity->assetManager, filename, AASSET_MODE_BUFFER); - if (asset_descriptor) - { - num_bytes = AAsset_getLength(asset_descriptor); - *outData = IM_ALLOC(num_bytes); - int64_t num_bytes_read = AAsset_read(asset_descriptor, *outData, num_bytes); - AAsset_close(asset_descriptor); - IM_ASSERT(num_bytes_read == num_bytes); - } - return num_bytes; -} diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_apple_metal/README.md b/app/jni/src/libultraship/extern/ImGui/examples/example_apple_metal/README.md deleted file mode 100644 index 48a2b57..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_apple_metal/README.md +++ /dev/null @@ -1,10 +0,0 @@ -# iOS / OSX Metal example - -## Introduction - -This example shows how to integrate Dear ImGui with Metal. It is based on the "cross-platform" game template provided with Xcode as of Xcode 9. - -Consider basing your work off the example_glfw_metal/ or example_sdl2_metal/ examples. They are better supported and will be portable unlike this one. - - - diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_apple_metal/example_apple_metal.xcodeproj/project.pbxproj b/app/jni/src/libultraship/extern/ImGui/examples/example_apple_metal/example_apple_metal.xcodeproj/project.pbxproj deleted file mode 100644 index 3ebf9cc..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_apple_metal/example_apple_metal.xcodeproj/project.pbxproj +++ /dev/null @@ -1,516 +0,0 @@ -// !$*UTF8*$! -{ - archiveVersion = 1; - classes = { - }; - objectVersion = 48; - objects = { - -/* Begin PBXBuildFile section */ - 050450AB2768052600AB6805 /* imgui_tables.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 5079822D257677DB0038A28D /* imgui_tables.cpp */; }; - 050450AD276863B000AB6805 /* QuartzCore.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 050450AC276863B000AB6805 /* QuartzCore.framework */; }; - 05318E0F274C397200A8DE2E /* GameController.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 05318E0E274C397200A8DE2E /* GameController.framework */; }; - 05A275442773BEA20084EF39 /* QuartzCore.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 05A275432773BEA20084EF39 /* QuartzCore.framework */; }; - 07A82ED82139413D0078D120 /* imgui_widgets.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 07A82ED72139413C0078D120 /* imgui_widgets.cpp */; }; - 07A82ED92139418F0078D120 /* imgui_widgets.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 07A82ED72139413C0078D120 /* imgui_widgets.cpp */; }; - 5079822E257677DB0038A28D /* imgui_tables.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 5079822D257677DB0038A28D /* imgui_tables.cpp */; }; - 8309BD8F253CCAAA0045E2A1 /* UIKit.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 8309BD8E253CCAAA0045E2A1 /* UIKit.framework */; }; - 8309BDA5253CCC070045E2A1 /* main.mm in Sources */ = {isa = PBXBuildFile; fileRef = 8309BDA0253CCBC10045E2A1 /* main.mm */; }; - 8309BDA8253CCC080045E2A1 /* main.mm in Sources */ = {isa = PBXBuildFile; fileRef = 8309BDA0253CCBC10045E2A1 /* main.mm */; }; - 8309BDBB253CCCAD0045E2A1 /* imgui_impl_metal.mm in Sources */ = {isa = PBXBuildFile; fileRef = 8309BDB5253CCC9D0045E2A1 /* imgui_impl_metal.mm */; }; - 8309BDBE253CCCB60045E2A1 /* imgui_impl_metal.mm in Sources */ = {isa = PBXBuildFile; fileRef = 8309BDB5253CCC9D0045E2A1 /* imgui_impl_metal.mm */; }; - 8309BDBF253CCCB60045E2A1 /* imgui_impl_osx.mm in Sources */ = {isa = PBXBuildFile; fileRef = 8309BDB6253CCC9D0045E2A1 /* imgui_impl_osx.mm */; }; - 8309BDC6253CCCFE0045E2A1 /* AppKit.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 8309BDC5253CCCFE0045E2A1 /* AppKit.framework */; }; - 8309BDFC253CDAB30045E2A1 /* LaunchScreen.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = 8309BDF7253CDAAE0045E2A1 /* LaunchScreen.storyboard */; }; - 8309BE04253CDAB60045E2A1 /* MainMenu.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = 8309BDFA253CDAAE0045E2A1 /* MainMenu.storyboard */; }; - 83BBE9E520EB46B900295997 /* Metal.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 83BBE9E420EB46B900295997 /* Metal.framework */; }; - 83BBE9E720EB46BD00295997 /* MetalKit.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 83BBE9E620EB46BD00295997 /* MetalKit.framework */; }; - 83BBE9EC20EB471700295997 /* MetalKit.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 83BBE9EA20EB471700295997 /* MetalKit.framework */; }; - 83BBE9ED20EB471700295997 /* Metal.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 83BBE9EB20EB471700295997 /* Metal.framework */; }; - 83BBEA0520EB54E700295997 /* imgui_draw.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 83BBEA0120EB54E700295997 /* imgui_draw.cpp */; }; - 83BBEA0620EB54E700295997 /* imgui_draw.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 83BBEA0120EB54E700295997 /* imgui_draw.cpp */; }; - 83BBEA0720EB54E700295997 /* imgui_demo.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 83BBEA0220EB54E700295997 /* imgui_demo.cpp */; }; - 83BBEA0820EB54E700295997 /* imgui_demo.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 83BBEA0220EB54E700295997 /* imgui_demo.cpp */; }; - 83BBEA0920EB54E700295997 /* imgui.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 83BBEA0320EB54E700295997 /* imgui.cpp */; }; - 83BBEA0A20EB54E700295997 /* imgui.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 83BBEA0320EB54E700295997 /* imgui.cpp */; }; -/* End PBXBuildFile section */ - -/* Begin PBXFileReference section */ - 050450AC276863B000AB6805 /* QuartzCore.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = QuartzCore.framework; path = System/Library/Frameworks/QuartzCore.framework; sourceTree = SDKROOT; }; - 05318E0E274C397200A8DE2E /* GameController.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = GameController.framework; path = System/Library/Frameworks/GameController.framework; sourceTree = SDKROOT; }; - 05A2754027728F5B0084EF39 /* imgui_impl_metal.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = imgui_impl_metal.h; path = ../../backends/imgui_impl_metal.h; sourceTree = ""; }; - 05A2754127728F5B0084EF39 /* imgui_impl_osx.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = imgui_impl_osx.h; path = ../../backends/imgui_impl_osx.h; sourceTree = ""; }; - 05A275432773BEA20084EF39 /* QuartzCore.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = QuartzCore.framework; path = Platforms/iPhoneOS.platform/Developer/SDKs/iPhoneOS15.2.sdk/System/Library/Frameworks/QuartzCore.framework; sourceTree = DEVELOPER_DIR; }; - 07A82ED62139413C0078D120 /* imgui_internal.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = imgui_internal.h; path = ../../imgui_internal.h; sourceTree = ""; }; - 07A82ED72139413C0078D120 /* imgui_widgets.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = imgui_widgets.cpp; path = ../../imgui_widgets.cpp; sourceTree = ""; }; - 5079822D257677DB0038A28D /* imgui_tables.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = imgui_tables.cpp; path = ../../imgui_tables.cpp; sourceTree = ""; }; - 8307E7C420E9F9C900473790 /* example_apple_metal.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = example_apple_metal.app; sourceTree = BUILT_PRODUCTS_DIR; }; - 8307E7DA20E9F9C900473790 /* example_apple_metal.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = example_apple_metal.app; sourceTree = BUILT_PRODUCTS_DIR; }; - 8309BD8E253CCAAA0045E2A1 /* UIKit.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = UIKit.framework; path = Platforms/iPhoneOS.platform/Developer/SDKs/iPhoneOS14.0.sdk/System/Library/Frameworks/UIKit.framework; sourceTree = DEVELOPER_DIR; }; - 8309BDA0253CCBC10045E2A1 /* main.mm */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.objcpp; path = main.mm; sourceTree = ""; }; - 8309BDB5253CCC9D0045E2A1 /* imgui_impl_metal.mm */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.objcpp; name = imgui_impl_metal.mm; path = ../../backends/imgui_impl_metal.mm; sourceTree = ""; }; - 8309BDB6253CCC9D0045E2A1 /* imgui_impl_osx.mm */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.objcpp; name = imgui_impl_osx.mm; path = ../../backends/imgui_impl_osx.mm; sourceTree = ""; }; - 8309BDC5253CCCFE0045E2A1 /* AppKit.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = AppKit.framework; path = System/Library/Frameworks/AppKit.framework; sourceTree = SDKROOT; }; - 8309BDF7253CDAAE0045E2A1 /* LaunchScreen.storyboard */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; path = LaunchScreen.storyboard; sourceTree = ""; }; - 8309BDF8253CDAAE0045E2A1 /* Info-iOS.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = "Info-iOS.plist"; sourceTree = ""; }; - 8309BDFA253CDAAE0045E2A1 /* MainMenu.storyboard */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; path = MainMenu.storyboard; sourceTree = ""; }; - 8309BDFB253CDAAE0045E2A1 /* Info-macOS.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = "Info-macOS.plist"; sourceTree = ""; }; - 83BBE9E420EB46B900295997 /* Metal.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = Metal.framework; path = Platforms/iPhoneOS.platform/Developer/SDKs/iPhoneOS11.4.sdk/System/Library/Frameworks/Metal.framework; sourceTree = DEVELOPER_DIR; }; - 83BBE9E620EB46BD00295997 /* MetalKit.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = MetalKit.framework; path = Platforms/iPhoneOS.platform/Developer/SDKs/iPhoneOS11.4.sdk/System/Library/Frameworks/MetalKit.framework; sourceTree = DEVELOPER_DIR; }; - 83BBE9E820EB46C100295997 /* ModelIO.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = ModelIO.framework; path = Platforms/iPhoneOS.platform/Developer/SDKs/iPhoneOS11.4.sdk/System/Library/Frameworks/ModelIO.framework; sourceTree = DEVELOPER_DIR; }; - 83BBE9EA20EB471700295997 /* MetalKit.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = MetalKit.framework; path = System/Library/Frameworks/MetalKit.framework; sourceTree = SDKROOT; }; - 83BBE9EB20EB471700295997 /* Metal.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = Metal.framework; path = System/Library/Frameworks/Metal.framework; sourceTree = SDKROOT; }; - 83BBE9EE20EB471C00295997 /* ModelIO.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = ModelIO.framework; path = System/Library/Frameworks/ModelIO.framework; sourceTree = SDKROOT; }; - 83BBEA0020EB54E700295997 /* imgui.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = imgui.h; path = ../../imgui.h; sourceTree = ""; }; - 83BBEA0120EB54E700295997 /* imgui_draw.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = imgui_draw.cpp; path = ../../imgui_draw.cpp; sourceTree = ""; }; - 83BBEA0220EB54E700295997 /* imgui_demo.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = imgui_demo.cpp; path = ../../imgui_demo.cpp; sourceTree = ""; }; - 83BBEA0320EB54E700295997 /* imgui.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = imgui.cpp; path = ../../imgui.cpp; sourceTree = ""; }; - 83BBEA0420EB54E700295997 /* imconfig.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = imconfig.h; path = ../../imconfig.h; sourceTree = ""; }; -/* End PBXFileReference section */ - -/* Begin PBXFrameworksBuildPhase section */ - 8307E7C120E9F9C900473790 /* Frameworks */ = { - isa = PBXFrameworksBuildPhase; - buildActionMask = 2147483647; - files = ( - 05A275442773BEA20084EF39 /* QuartzCore.framework in Frameworks */, - 8309BD8F253CCAAA0045E2A1 /* UIKit.framework in Frameworks */, - 83BBE9E720EB46BD00295997 /* MetalKit.framework in Frameworks */, - 83BBE9E520EB46B900295997 /* Metal.framework in Frameworks */, - ); - runOnlyForDeploymentPostprocessing = 0; - }; - 8307E7D720E9F9C900473790 /* Frameworks */ = { - isa = PBXFrameworksBuildPhase; - buildActionMask = 2147483647; - files = ( - 050450AD276863B000AB6805 /* QuartzCore.framework in Frameworks */, - 8309BDC6253CCCFE0045E2A1 /* AppKit.framework in Frameworks */, - 83BBE9EC20EB471700295997 /* MetalKit.framework in Frameworks */, - 05318E0F274C397200A8DE2E /* GameController.framework in Frameworks */, - 83BBE9ED20EB471700295997 /* Metal.framework in Frameworks */, - ); - runOnlyForDeploymentPostprocessing = 0; - }; -/* End PBXFrameworksBuildPhase section */ - -/* Begin PBXGroup section */ - 8307E7B520E9F9C700473790 = { - isa = PBXGroup; - children = ( - 83BBE9F020EB544400295997 /* imgui */, - 8309BD9E253CCBA70045E2A1 /* example */, - 8307E7C520E9F9C900473790 /* Products */, - 83BBE9E320EB46B800295997 /* Frameworks */, - ); - sourceTree = ""; - }; - 8307E7C520E9F9C900473790 /* Products */ = { - isa = PBXGroup; - children = ( - 8307E7C420E9F9C900473790 /* example_apple_metal.app */, - 8307E7DA20E9F9C900473790 /* example_apple_metal.app */, - ); - name = Products; - sourceTree = ""; - }; - 8309BD9E253CCBA70045E2A1 /* example */ = { - isa = PBXGroup; - children = ( - 8309BDF6253CDAAE0045E2A1 /* iOS */, - 8309BDF9253CDAAE0045E2A1 /* macOS */, - 8309BDA0253CCBC10045E2A1 /* main.mm */, - ); - name = example; - sourceTree = ""; - }; - 8309BDF6253CDAAE0045E2A1 /* iOS */ = { - isa = PBXGroup; - children = ( - 8309BDF7253CDAAE0045E2A1 /* LaunchScreen.storyboard */, - 8309BDF8253CDAAE0045E2A1 /* Info-iOS.plist */, - ); - path = iOS; - sourceTree = ""; - }; - 8309BDF9253CDAAE0045E2A1 /* macOS */ = { - isa = PBXGroup; - children = ( - 8309BDFA253CDAAE0045E2A1 /* MainMenu.storyboard */, - 8309BDFB253CDAAE0045E2A1 /* Info-macOS.plist */, - ); - path = macOS; - sourceTree = ""; - }; - 83BBE9E320EB46B800295997 /* Frameworks */ = { - isa = PBXGroup; - children = ( - 050450AC276863B000AB6805 /* QuartzCore.framework */, - 05A275432773BEA20084EF39 /* QuartzCore.framework */, - 05318E0E274C397200A8DE2E /* GameController.framework */, - 8309BDC5253CCCFE0045E2A1 /* AppKit.framework */, - 8309BD8E253CCAAA0045E2A1 /* UIKit.framework */, - 83BBE9EE20EB471C00295997 /* ModelIO.framework */, - 83BBE9EB20EB471700295997 /* Metal.framework */, - 83BBE9EA20EB471700295997 /* MetalKit.framework */, - 83BBE9E820EB46C100295997 /* ModelIO.framework */, - 83BBE9E620EB46BD00295997 /* MetalKit.framework */, - 83BBE9E420EB46B900295997 /* Metal.framework */, - ); - name = Frameworks; - sourceTree = ""; - }; - 83BBE9F020EB544400295997 /* imgui */ = { - isa = PBXGroup; - children = ( - 5079822D257677DB0038A28D /* imgui_tables.cpp */, - 05A2754027728F5B0084EF39 /* imgui_impl_metal.h */, - 8309BDB5253CCC9D0045E2A1 /* imgui_impl_metal.mm */, - 05A2754127728F5B0084EF39 /* imgui_impl_osx.h */, - 8309BDB6253CCC9D0045E2A1 /* imgui_impl_osx.mm */, - 83BBEA0420EB54E700295997 /* imconfig.h */, - 83BBEA0320EB54E700295997 /* imgui.cpp */, - 83BBEA0020EB54E700295997 /* imgui.h */, - 83BBEA0220EB54E700295997 /* imgui_demo.cpp */, - 83BBEA0120EB54E700295997 /* imgui_draw.cpp */, - 07A82ED62139413C0078D120 /* imgui_internal.h */, - 07A82ED72139413C0078D120 /* imgui_widgets.cpp */, - ); - name = imgui; - sourceTree = ""; - }; -/* End PBXGroup section */ - -/* Begin PBXNativeTarget section */ - 8307E7C320E9F9C900473790 /* example_apple_metal_ios */ = { - isa = PBXNativeTarget; - buildConfigurationList = 8307E7F020E9F9C900473790 /* Build configuration list for PBXNativeTarget "example_apple_metal_ios" */; - buildPhases = ( - 8307E7C020E9F9C900473790 /* Sources */, - 8307E7C120E9F9C900473790 /* Frameworks */, - 8307E7C220E9F9C900473790 /* Resources */, - ); - buildRules = ( - ); - dependencies = ( - ); - name = example_apple_metal_ios; - productName = "imguiex iOS"; - productReference = 8307E7C420E9F9C900473790 /* example_apple_metal.app */; - productType = "com.apple.product-type.application"; - }; - 8307E7D920E9F9C900473790 /* example_apple_metal_macos */ = { - isa = PBXNativeTarget; - buildConfigurationList = 8307E7F320E9F9C900473790 /* Build configuration list for PBXNativeTarget "example_apple_metal_macos" */; - buildPhases = ( - 8307E7D620E9F9C900473790 /* Sources */, - 8307E7D720E9F9C900473790 /* Frameworks */, - 8307E7D820E9F9C900473790 /* Resources */, - ); - buildRules = ( - ); - dependencies = ( - ); - name = example_apple_metal_macos; - productName = "imguiex macOS"; - productReference = 8307E7DA20E9F9C900473790 /* example_apple_metal.app */; - productType = "com.apple.product-type.application"; - }; -/* End PBXNativeTarget section */ - -/* Begin PBXProject section */ - 8307E7B620E9F9C700473790 /* Project object */ = { - isa = PBXProject; - attributes = { - LastUpgradeCheck = 1200; - ORGANIZATIONNAME = "Warren Moore"; - TargetAttributes = { - 8307E7C320E9F9C900473790 = { - CreatedOnToolsVersion = 9.4.1; - ProvisioningStyle = Automatic; - }; - 8307E7D920E9F9C900473790 = { - CreatedOnToolsVersion = 9.4.1; - ProvisioningStyle = Automatic; - }; - }; - }; - buildConfigurationList = 8307E7B920E9F9C700473790 /* Build configuration list for PBXProject "example_apple_metal" */; - compatibilityVersion = "Xcode 8.0"; - developmentRegion = en; - hasScannedForEncodings = 0; - knownRegions = ( - en, - Base, - ); - mainGroup = 8307E7B520E9F9C700473790; - productRefGroup = 8307E7C520E9F9C900473790 /* Products */; - projectDirPath = ""; - projectRoot = ""; - targets = ( - 8307E7C320E9F9C900473790 /* example_apple_metal_ios */, - 8307E7D920E9F9C900473790 /* example_apple_metal_macos */, - ); - }; -/* End PBXProject section */ - -/* Begin PBXResourcesBuildPhase section */ - 8307E7C220E9F9C900473790 /* Resources */ = { - isa = PBXResourcesBuildPhase; - buildActionMask = 2147483647; - files = ( - 8309BDFC253CDAB30045E2A1 /* LaunchScreen.storyboard in Resources */, - ); - runOnlyForDeploymentPostprocessing = 0; - }; - 8307E7D820E9F9C900473790 /* Resources */ = { - isa = PBXResourcesBuildPhase; - buildActionMask = 2147483647; - files = ( - 8309BE04253CDAB60045E2A1 /* MainMenu.storyboard in Resources */, - ); - runOnlyForDeploymentPostprocessing = 0; - }; -/* End PBXResourcesBuildPhase section */ - -/* Begin PBXSourcesBuildPhase section */ - 8307E7C020E9F9C900473790 /* Sources */ = { - isa = PBXSourcesBuildPhase; - buildActionMask = 2147483647; - files = ( - 8309BDBB253CCCAD0045E2A1 /* imgui_impl_metal.mm in Sources */, - 83BBEA0920EB54E700295997 /* imgui.cpp in Sources */, - 83BBEA0720EB54E700295997 /* imgui_demo.cpp in Sources */, - 83BBEA0520EB54E700295997 /* imgui_draw.cpp in Sources */, - 5079822E257677DB0038A28D /* imgui_tables.cpp in Sources */, - 07A82ED82139413D0078D120 /* imgui_widgets.cpp in Sources */, - 8309BDA5253CCC070045E2A1 /* main.mm in Sources */, - ); - runOnlyForDeploymentPostprocessing = 0; - }; - 8307E7D620E9F9C900473790 /* Sources */ = { - isa = PBXSourcesBuildPhase; - buildActionMask = 2147483647; - files = ( - 8309BDBE253CCCB60045E2A1 /* imgui_impl_metal.mm in Sources */, - 8309BDBF253CCCB60045E2A1 /* imgui_impl_osx.mm in Sources */, - 83BBEA0A20EB54E700295997 /* imgui.cpp in Sources */, - 83BBEA0820EB54E700295997 /* imgui_demo.cpp in Sources */, - 83BBEA0620EB54E700295997 /* imgui_draw.cpp in Sources */, - 050450AB2768052600AB6805 /* imgui_tables.cpp in Sources */, - 07A82ED92139418F0078D120 /* imgui_widgets.cpp in Sources */, - 8309BDA8253CCC080045E2A1 /* main.mm in Sources */, - ); - runOnlyForDeploymentPostprocessing = 0; - }; -/* End PBXSourcesBuildPhase section */ - -/* Begin XCBuildConfiguration section */ - 8307E7EE20E9F9C900473790 /* Debug */ = { - isa = XCBuildConfiguration; - buildSettings = { - ALWAYS_SEARCH_USER_PATHS = NO; - CLANG_ANALYZER_NONNULL = YES; - CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE; - CLANG_CXX_LANGUAGE_STANDARD = "gnu++14"; - CLANG_CXX_LIBRARY = "libc++"; - CLANG_ENABLE_MODULES = YES; - CLANG_ENABLE_OBJC_ARC = YES; - CLANG_ENABLE_OBJC_WEAK = YES; - CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES; - CLANG_WARN_BOOL_CONVERSION = YES; - CLANG_WARN_COMMA = YES; - CLANG_WARN_CONSTANT_CONVERSION = YES; - CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES; - CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; - CLANG_WARN_DOCUMENTATION_COMMENTS = YES; - CLANG_WARN_EMPTY_BODY = YES; - CLANG_WARN_ENUM_CONVERSION = YES; - CLANG_WARN_INFINITE_RECURSION = YES; - CLANG_WARN_INT_CONVERSION = YES; - CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES; - CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES; - CLANG_WARN_OBJC_LITERAL_CONVERSION = YES; - CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; - CLANG_WARN_QUOTED_INCLUDE_IN_FRAMEWORK_HEADER = YES; - CLANG_WARN_RANGE_LOOP_ANALYSIS = YES; - CLANG_WARN_STRICT_PROTOTYPES = YES; - CLANG_WARN_SUSPICIOUS_MOVE = YES; - CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE; - CLANG_WARN_UNREACHABLE_CODE = YES; - CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; - COPY_PHASE_STRIP = NO; - DEBUG_INFORMATION_FORMAT = dwarf; - ENABLE_STRICT_OBJC_MSGSEND = YES; - ENABLE_TESTABILITY = YES; - GCC_C_LANGUAGE_STANDARD = gnu11; - GCC_DYNAMIC_NO_PIC = NO; - GCC_NO_COMMON_BLOCKS = YES; - GCC_OPTIMIZATION_LEVEL = 0; - GCC_PREPROCESSOR_DEFINITIONS = ( - "DEBUG=1", - "$(inherited)", - ); - GCC_WARN_64_TO_32_BIT_CONVERSION = YES; - GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; - GCC_WARN_UNDECLARED_SELECTOR = YES; - GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; - GCC_WARN_UNUSED_FUNCTION = YES; - GCC_WARN_UNUSED_VARIABLE = YES; - MTL_ENABLE_DEBUG_INFO = YES; - ONLY_ACTIVE_ARCH = YES; - }; - name = Debug; - }; - 8307E7EF20E9F9C900473790 /* Release */ = { - isa = XCBuildConfiguration; - buildSettings = { - ALWAYS_SEARCH_USER_PATHS = NO; - CLANG_ANALYZER_NONNULL = YES; - CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE; - CLANG_CXX_LANGUAGE_STANDARD = "gnu++14"; - CLANG_CXX_LIBRARY = "libc++"; - CLANG_ENABLE_MODULES = YES; - CLANG_ENABLE_OBJC_ARC = YES; - CLANG_ENABLE_OBJC_WEAK = YES; - CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES; - CLANG_WARN_BOOL_CONVERSION = YES; - CLANG_WARN_COMMA = YES; - CLANG_WARN_CONSTANT_CONVERSION = YES; - CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES; - CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; - CLANG_WARN_DOCUMENTATION_COMMENTS = YES; - CLANG_WARN_EMPTY_BODY = YES; - CLANG_WARN_ENUM_CONVERSION = YES; - CLANG_WARN_INFINITE_RECURSION = YES; - CLANG_WARN_INT_CONVERSION = YES; - CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES; - CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES; - CLANG_WARN_OBJC_LITERAL_CONVERSION = YES; - CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; - CLANG_WARN_QUOTED_INCLUDE_IN_FRAMEWORK_HEADER = YES; - CLANG_WARN_RANGE_LOOP_ANALYSIS = YES; - CLANG_WARN_STRICT_PROTOTYPES = YES; - CLANG_WARN_SUSPICIOUS_MOVE = YES; - CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE; - CLANG_WARN_UNREACHABLE_CODE = YES; - CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; - COPY_PHASE_STRIP = NO; - DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym"; - ENABLE_NS_ASSERTIONS = NO; - ENABLE_STRICT_OBJC_MSGSEND = YES; - GCC_C_LANGUAGE_STANDARD = gnu11; - GCC_NO_COMMON_BLOCKS = YES; - GCC_WARN_64_TO_32_BIT_CONVERSION = YES; - GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; - GCC_WARN_UNDECLARED_SELECTOR = YES; - GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; - GCC_WARN_UNUSED_FUNCTION = YES; - GCC_WARN_UNUSED_VARIABLE = YES; - MTL_ENABLE_DEBUG_INFO = NO; - }; - name = Release; - }; - 8307E7F120E9F9C900473790 /* Debug */ = { - isa = XCBuildConfiguration; - buildSettings = { - CODE_SIGN_IDENTITY = "iPhone Developer"; - CODE_SIGN_STYLE = Automatic; - DEVELOPMENT_TEAM = ""; - INFOPLIST_FILE = "$(SRCROOT)/iOS/Info-iOS.plist"; - IPHONEOS_DEPLOYMENT_TARGET = 10.0; - LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks"; - PRODUCT_BUNDLE_IDENTIFIER = "org.imgui.example.apple-metal-ios"; - PRODUCT_NAME = example_apple_metal; - SDKROOT = iphoneos; - TARGETED_DEVICE_FAMILY = "1,2"; - USER_HEADER_SEARCH_PATHS = "$(SRCROOT)/../../**"; - }; - name = Debug; - }; - 8307E7F220E9F9C900473790 /* Release */ = { - isa = XCBuildConfiguration; - buildSettings = { - CODE_SIGN_IDENTITY = "iPhone Developer"; - CODE_SIGN_STYLE = Automatic; - DEVELOPMENT_TEAM = ""; - INFOPLIST_FILE = "$(SRCROOT)/iOS/Info-iOS.plist"; - IPHONEOS_DEPLOYMENT_TARGET = 10.0; - LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks"; - PRODUCT_BUNDLE_IDENTIFIER = "org.imgui.example.apple-metal-ios"; - PRODUCT_NAME = example_apple_metal; - SDKROOT = iphoneos; - TARGETED_DEVICE_FAMILY = "1,2"; - USER_HEADER_SEARCH_PATHS = "$(SRCROOT)/../../**"; - VALIDATE_PRODUCT = YES; - }; - name = Release; - }; - 8307E7F420E9F9C900473790 /* Debug */ = { - isa = XCBuildConfiguration; - buildSettings = { - CODE_SIGN_IDENTITY = "-"; - CODE_SIGN_STYLE = Automatic; - COMBINE_HIDPI_IMAGES = YES; - DEVELOPMENT_TEAM = ""; - INFOPLIST_FILE = "$(SRCROOT)/macOS/Info-macOS.plist"; - LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/../Frameworks"; - MACOSX_DEPLOYMENT_TARGET = 10.12; - PRODUCT_BUNDLE_IDENTIFIER = "org.imgui.example.apple-metal-macos"; - PRODUCT_NAME = example_apple_metal; - SDKROOT = macosx; - USER_HEADER_SEARCH_PATHS = "$(SRCROOT)/../../**"; - }; - name = Debug; - }; - 8307E7F520E9F9C900473790 /* Release */ = { - isa = XCBuildConfiguration; - buildSettings = { - CODE_SIGN_IDENTITY = "-"; - CODE_SIGN_STYLE = Automatic; - COMBINE_HIDPI_IMAGES = YES; - DEVELOPMENT_TEAM = ""; - INFOPLIST_FILE = "$(SRCROOT)/macOS/Info-macOS.plist"; - LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/../Frameworks"; - MACOSX_DEPLOYMENT_TARGET = 10.12; - PRODUCT_BUNDLE_IDENTIFIER = "org.imgui.example.apple-metal-macos"; - PRODUCT_NAME = example_apple_metal; - SDKROOT = macosx; - USER_HEADER_SEARCH_PATHS = "$(SRCROOT)/../../**"; - }; - name = Release; - }; -/* End XCBuildConfiguration section */ - -/* Begin XCConfigurationList section */ - 8307E7B920E9F9C700473790 /* Build configuration list for PBXProject "example_apple_metal" */ = { - isa = XCConfigurationList; - buildConfigurations = ( - 8307E7EE20E9F9C900473790 /* Debug */, - 8307E7EF20E9F9C900473790 /* Release */, - ); - defaultConfigurationIsVisible = 0; - defaultConfigurationName = Release; - }; - 8307E7F020E9F9C900473790 /* Build configuration list for PBXNativeTarget "example_apple_metal_ios" */ = { - isa = XCConfigurationList; - buildConfigurations = ( - 8307E7F120E9F9C900473790 /* Debug */, - 8307E7F220E9F9C900473790 /* Release */, - ); - defaultConfigurationIsVisible = 0; - defaultConfigurationName = Release; - }; - 8307E7F320E9F9C900473790 /* Build configuration list for PBXNativeTarget "example_apple_metal_macos" */ = { - isa = XCConfigurationList; - buildConfigurations = ( - 8307E7F420E9F9C900473790 /* Debug */, - 8307E7F520E9F9C900473790 /* Release */, - ); - defaultConfigurationIsVisible = 0; - defaultConfigurationName = Release; - }; -/* End XCConfigurationList section */ - }; - rootObject = 8307E7B620E9F9C700473790 /* Project object */; -} diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_apple_metal/iOS/Info-iOS.plist b/app/jni/src/libultraship/extern/ImGui/examples/example_apple_metal/iOS/Info-iOS.plist deleted file mode 100644 index 93ef078..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_apple_metal/iOS/Info-iOS.plist +++ /dev/null @@ -1,49 +0,0 @@ - - - - - CFBundleDevelopmentRegion - $(DEVELOPMENT_LANGUAGE) - CFBundleExecutable - $(EXECUTABLE_NAME) - CFBundleIdentifier - $(PRODUCT_BUNDLE_IDENTIFIER) - CFBundleInfoDictionaryVersion - 6.0 - CFBundleName - imgui - CFBundlePackageType - APPL - CFBundleShortVersionString - 1.0 - CFBundleVersion - 1 - LSRequiresIPhoneOS - - UILaunchStoryboardName - LaunchScreen - UIRequiredDeviceCapabilities - - armv7 - metal - - UIRequiresFullScreen - - UIStatusBarHidden - - UISupportedInterfaceOrientations - - UIInterfaceOrientationPortrait - UIInterfaceOrientationLandscapeLeft - UIInterfaceOrientationLandscapeRight - UIInterfaceOrientationPortraitUpsideDown - - UISupportedInterfaceOrientations~ipad - - UIInterfaceOrientationPortrait - UIInterfaceOrientationPortraitUpsideDown - UIInterfaceOrientationLandscapeLeft - UIInterfaceOrientationLandscapeRight - - - diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_apple_metal/iOS/LaunchScreen.storyboard b/app/jni/src/libultraship/extern/ImGui/examples/example_apple_metal/iOS/LaunchScreen.storyboard deleted file mode 100644 index 12c52cf..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_apple_metal/iOS/LaunchScreen.storyboard +++ /dev/null @@ -1,27 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_apple_metal/macOS/Info-macOS.plist b/app/jni/src/libultraship/extern/ImGui/examples/example_apple_metal/macOS/Info-macOS.plist deleted file mode 100644 index 6f4a2b2..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_apple_metal/macOS/Info-macOS.plist +++ /dev/null @@ -1,30 +0,0 @@ - - - - - CFBundleDevelopmentRegion - $(DEVELOPMENT_LANGUAGE) - CFBundleExecutable - $(EXECUTABLE_NAME) - CFBundleIconFile - - CFBundleIdentifier - $(PRODUCT_BUNDLE_IDENTIFIER) - CFBundleInfoDictionaryVersion - 6.0 - CFBundleName - imgui - CFBundlePackageType - APPL - CFBundleShortVersionString - 1.0 - CFBundleVersion - 1 - LSMinimumSystemVersion - $(MACOSX_DEPLOYMENT_TARGET) - NSMainStoryboardFile - MainMenu - NSPrincipalClass - NSApplication - - diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_apple_metal/macOS/MainMenu.storyboard b/app/jni/src/libultraship/extern/ImGui/examples/example_apple_metal/macOS/MainMenu.storyboard deleted file mode 100644 index 38ad432..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_apple_metal/macOS/MainMenu.storyboard +++ /dev/null @@ -1,93 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_apple_metal/main.mm b/app/jni/src/libultraship/extern/ImGui/examples/example_apple_metal/main.mm deleted file mode 100644 index d184dd6..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_apple_metal/main.mm +++ /dev/null @@ -1,354 +0,0 @@ -// Dear ImGui: standalone example application for OSX + Metal. - -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#import - -#if TARGET_OS_OSX -#import -#else -#import -#endif - -#import -#import - -#include "imgui.h" -#include "imgui_impl_metal.h" -#if TARGET_OS_OSX -#include "imgui_impl_osx.h" -@interface AppViewController : NSViewController -@end -#else -@interface AppViewController : UIViewController -@end -#endif - -@interface AppViewController () -@property (nonatomic, readonly) MTKView *mtkView; -@property (nonatomic, strong) id device; -@property (nonatomic, strong) id commandQueue; -@end - -//----------------------------------------------------------------------------------- -// AppViewController -//----------------------------------------------------------------------------------- - -@implementation AppViewController - --(instancetype)initWithNibName:(nullable NSString *)nibNameOrNil bundle:(nullable NSBundle *)nibBundleOrNil -{ - self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil]; - - _device = MTLCreateSystemDefaultDevice(); - _commandQueue = [_device newCommandQueue]; - - if (!self.device) - { - NSLog(@"Metal is not supported"); - abort(); - } - - // Setup Dear ImGui context - // FIXME: This example doesn't have proper cleanup... - IMGUI_CHECKVERSION(); - ImGui::CreateContext(); - ImGuiIO& io = ImGui::GetIO(); (void)io; - io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard; // Enable Keyboard Controls - io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad; // Enable Gamepad Controls - io.ConfigFlags |= ImGuiConfigFlags_DockingEnable; // Enable Docking - io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable; // Enable Multi-Viewport / Platform Windows - - // Setup Dear ImGui style - ImGui::StyleColorsDark(); - //ImGui::StyleColorsLight(); - - // When viewports are enabled we tweak WindowRounding/WindowBg so platform windows can look identical to regular ones. - ImGuiStyle& style = ImGui::GetStyle(); - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - style.WindowRounding = 0.0f; - style.Colors[ImGuiCol_WindowBg].w = 1.0f; - } - - // Setup Renderer backend - ImGui_ImplMetal_Init(_device); - - // Load Fonts - // - If no fonts are loaded, dear imgui will use the default font. You can also load multiple fonts and use ImGui::PushFont()/PopFont() to select them. - // - AddFontFromFileTTF() will return the ImFont* so you can store it if you need to select the font among multiple. - // - If the file cannot be loaded, the function will return a nullptr. Please handle those errors in your application (e.g. use an assertion, or display an error and quit). - // - The fonts will be rasterized at a given size (w/ oversampling) and stored into a texture when calling ImFontAtlas::Build()/GetTexDataAsXXXX(), which ImGui_ImplXXXX_NewFrame below will call. - // - Use '#define IMGUI_ENABLE_FREETYPE' in your imconfig file to use Freetype for higher quality font rendering. - // - Read 'docs/FONTS.md' for more instructions and details. - // - Remember that in C/C++ if you want to include a backslash \ in a string literal you need to write a double backslash \\ ! - //io.Fonts->AddFontDefault(); - //io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\segoeui.ttf", 18.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/DroidSans.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Roboto-Medium.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Cousine-Regular.ttf", 15.0f); - //ImFont* font = io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\ArialUni.ttf", 18.0f, nullptr, io.Fonts->GetGlyphRangesJapanese()); - //IM_ASSERT(font != nullptr); - - return self; -} - --(MTKView *)mtkView -{ - return (MTKView *)self.view; -} - --(void)loadView -{ - self.view = [[MTKView alloc] initWithFrame:CGRectMake(0, 0, 1200, 720)]; -} - --(void)viewDidLoad -{ - [super viewDidLoad]; - - self.mtkView.device = self.device; - self.mtkView.delegate = self; - -#if TARGET_OS_OSX - ImGui_ImplOSX_Init(self.view); - [NSApp activateIgnoringOtherApps:YES]; -#endif -} - --(void)drawInMTKView:(MTKView*)view -{ - ImGuiIO& io = ImGui::GetIO(); - io.DisplaySize.x = view.bounds.size.width; - io.DisplaySize.y = view.bounds.size.height; - -#if TARGET_OS_OSX - CGFloat framebufferScale = view.window.screen.backingScaleFactor ?: NSScreen.mainScreen.backingScaleFactor; -#else - CGFloat framebufferScale = view.window.screen.scale ?: UIScreen.mainScreen.scale; -#endif - io.DisplayFramebufferScale = ImVec2(framebufferScale, framebufferScale); - - id commandBuffer = [self.commandQueue commandBuffer]; - - MTLRenderPassDescriptor* renderPassDescriptor = view.currentRenderPassDescriptor; - if (renderPassDescriptor == nil) - { - [commandBuffer commit]; - return; - } - - // Start the Dear ImGui frame - ImGui_ImplMetal_NewFrame(renderPassDescriptor); -#if TARGET_OS_OSX - ImGui_ImplOSX_NewFrame(view); -#endif - ImGui::NewFrame(); - - // Our state (make them static = more or less global) as a convenience to keep the example terse. - static bool show_demo_window = true; - static bool show_another_window = false; - static ImVec4 clear_color = ImVec4(0.45f, 0.55f, 0.60f, 1.00f); - - // 1. Show the big demo window (Most of the sample code is in ImGui::ShowDemoWindow()! You can browse its code to learn more about Dear ImGui!). - if (show_demo_window) - ImGui::ShowDemoWindow(&show_demo_window); - - // 2. Show a simple window that we create ourselves. We use a Begin/End pair to create a named window. - { - static float f = 0.0f; - static int counter = 0; - - ImGui::Begin("Hello, world!"); // Create a window called "Hello, world!" and append into it. - - ImGui::Text("This is some useful text."); // Display some text (you can use a format strings too) - ImGui::Checkbox("Demo Window", &show_demo_window); // Edit bools storing our window open/close state - ImGui::Checkbox("Another Window", &show_another_window); - - ImGui::SliderFloat("float", &f, 0.0f, 1.0f); // Edit 1 float using a slider from 0.0f to 1.0f - ImGui::ColorEdit3("clear color", (float*)&clear_color); // Edit 3 floats representing a color - - if (ImGui::Button("Button")) // Buttons return true when clicked (most widgets return true when edited/activated) - counter++; - ImGui::SameLine(); - ImGui::Text("counter = %d", counter); - - ImGui::Text("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / io.Framerate, io.Framerate); - ImGui::End(); - } - - // 3. Show another simple window. - if (show_another_window) - { - ImGui::Begin("Another Window", &show_another_window); // Pass a pointer to our bool variable (the window will have a closing button that will clear the bool when clicked) - ImGui::Text("Hello from another window!"); - if (ImGui::Button("Close Me")) - show_another_window = false; - ImGui::End(); - } - - // Rendering - ImGui::Render(); - ImDrawData* draw_data = ImGui::GetDrawData(); - - renderPassDescriptor.colorAttachments[0].clearColor = MTLClearColorMake(clear_color.x * clear_color.w, clear_color.y * clear_color.w, clear_color.z * clear_color.w, clear_color.w); - id renderEncoder = [commandBuffer renderCommandEncoderWithDescriptor:renderPassDescriptor]; - [renderEncoder pushDebugGroup:@"Dear ImGui rendering"]; - ImGui_ImplMetal_RenderDrawData(draw_data, commandBuffer, renderEncoder); - [renderEncoder popDebugGroup]; - [renderEncoder endEncoding]; - - // Present - [commandBuffer presentDrawable:view.currentDrawable]; - [commandBuffer commit]; - - // Update and Render additional Platform Windows - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - ImGui::UpdatePlatformWindows(); - ImGui::RenderPlatformWindowsDefault(); - } -} - --(void)mtkView:(MTKView*)view drawableSizeWillChange:(CGSize)size -{ -} - -//----------------------------------------------------------------------------------- -// Input processing -//----------------------------------------------------------------------------------- - -#if TARGET_OS_OSX - -- (void)viewWillAppear -{ - [super viewWillAppear]; - self.view.window.delegate = self; -} - -- (void)windowWillClose:(NSNotification *)notification -{ - ImGui_ImplMetal_Shutdown(); - ImGui_ImplOSX_Shutdown(); - ImGui::DestroyContext(); -} - -#else - -// This touch mapping is super cheesy/hacky. We treat any touch on the screen -// as if it were a depressed left mouse button, and we don't bother handling -// multitouch correctly at all. This causes the "cursor" to behave very erratically -// when there are multiple active touches. But for demo purposes, single-touch -// interaction actually works surprisingly well. --(void)updateIOWithTouchEvent:(UIEvent *)event -{ - UITouch *anyTouch = event.allTouches.anyObject; - CGPoint touchLocation = [anyTouch locationInView:self.view]; - ImGuiIO &io = ImGui::GetIO(); - io.AddMouseSourceEvent(ImGuiMouseSource_TouchScreen); - io.AddMousePosEvent(touchLocation.x, touchLocation.y); - - BOOL hasActiveTouch = NO; - for (UITouch *touch in event.allTouches) - { - if (touch.phase != UITouchPhaseEnded && touch.phase != UITouchPhaseCancelled) - { - hasActiveTouch = YES; - break; - } - } - io.AddMouseButtonEvent(0, hasActiveTouch); -} - --(void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event { [self updateIOWithTouchEvent:event]; } --(void)touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event { [self updateIOWithTouchEvent:event]; } --(void)touchesCancelled:(NSSet *)touches withEvent:(UIEvent *)event { [self updateIOWithTouchEvent:event]; } --(void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event { [self updateIOWithTouchEvent:event]; } - -#endif - -@end - -//----------------------------------------------------------------------------------- -// AppDelegate -//----------------------------------------------------------------------------------- - -#if TARGET_OS_OSX - -@interface AppDelegate : NSObject -@property (nonatomic, strong) NSWindow *window; -@end - -@implementation AppDelegate - --(BOOL)applicationShouldTerminateAfterLastWindowClosed:(NSApplication *)sender -{ - return YES; -} - --(instancetype)init -{ - if (self = [super init]) - { - NSViewController *rootViewController = [[AppViewController alloc] initWithNibName:nil bundle:nil]; - self.window = [[NSWindow alloc] initWithContentRect:NSZeroRect - styleMask:NSWindowStyleMaskTitled | NSWindowStyleMaskClosable | NSWindowStyleMaskResizable | NSWindowStyleMaskMiniaturizable - backing:NSBackingStoreBuffered - defer:NO]; - self.window.contentViewController = rootViewController; - [self.window center]; - [self.window makeKeyAndOrderFront:self]; - } - return self; -} - -@end - -#else - -@interface AppDelegate : UIResponder -@property (strong, nonatomic) UIWindow *window; -@end - -@implementation AppDelegate - --(BOOL)application:(UIApplication *)application - didFinishLaunchingWithOptions:(NSDictionary *)launchOptions -{ - UIViewController *rootViewController = [[AppViewController alloc] init]; - self.window = [[UIWindow alloc] initWithFrame:UIScreen.mainScreen.bounds]; - self.window.rootViewController = rootViewController; - [self.window makeKeyAndVisible]; - return YES; -} - -@end - -#endif - -//----------------------------------------------------------------------------------- -// Application main() function -//----------------------------------------------------------------------------------- - -#if TARGET_OS_OSX - -int main(int argc, const char * argv[]) -{ - return NSApplicationMain(argc, argv); -} - -#else - -int main(int argc, char * argv[]) -{ - @autoreleasepool - { - return UIApplicationMain(argc, argv, nil, NSStringFromClass([AppDelegate class])); - } -} - -#endif diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_apple_opengl2/example_apple_opengl2.xcodeproj/project.pbxproj b/app/jni/src/libultraship/extern/ImGui/examples/example_apple_opengl2/example_apple_opengl2.xcodeproj/project.pbxproj deleted file mode 100644 index a168373..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_apple_opengl2/example_apple_opengl2.xcodeproj/project.pbxproj +++ /dev/null @@ -1,332 +0,0 @@ -// !$*UTF8*$! -{ - archiveVersion = 1; - classes = { - }; - objectVersion = 48; - objects = { - -/* Begin PBXBuildFile section */ - 05E31B59274EF0700083FCB6 /* GameController.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 05E31B57274EF0360083FCB6 /* GameController.framework */; }; - 07A82EDB213941D00078D120 /* imgui_widgets.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 07A82EDA213941D00078D120 /* imgui_widgets.cpp */; }; - 4080A99820B02D340036BA46 /* main.mm in Sources */ = {isa = PBXBuildFile; fileRef = 4080A98A20B02CD90036BA46 /* main.mm */; }; - 4080A9A220B034280036BA46 /* imgui_impl_opengl2.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4080A99E20B034280036BA46 /* imgui_impl_opengl2.cpp */; }; - 4080A9AD20B0343C0036BA46 /* imgui_demo.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4080A9A620B0343C0036BA46 /* imgui_demo.cpp */; }; - 4080A9AE20B0343C0036BA46 /* imgui.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4080A9A720B0343C0036BA46 /* imgui.cpp */; }; - 4080A9AF20B0343C0036BA46 /* imgui_draw.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4080A9AA20B0343C0036BA46 /* imgui_draw.cpp */; }; - 4080A9B020B0347A0036BA46 /* imgui_impl_osx.mm in Sources */ = {isa = PBXBuildFile; fileRef = 4080A99F20B034280036BA46 /* imgui_impl_osx.mm */; }; - 4080A9B320B034E40036BA46 /* Cocoa.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 4080A9B220B034E40036BA46 /* Cocoa.framework */; }; - 4080A9B520B034EA0036BA46 /* OpenGL.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 4080A9B420B034EA0036BA46 /* OpenGL.framework */; }; - 50798230257677FD0038A28D /* imgui_tables.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 5079822F257677FC0038A28D /* imgui_tables.cpp */; }; -/* End PBXBuildFile section */ - -/* Begin PBXCopyFilesBuildPhase section */ - 4080A96920B029B00036BA46 /* CopyFiles */ = { - isa = PBXCopyFilesBuildPhase; - buildActionMask = 2147483647; - dstPath = /usr/share/man/man1/; - dstSubfolderSpec = 0; - files = ( - ); - runOnlyForDeploymentPostprocessing = 1; - }; -/* End PBXCopyFilesBuildPhase section */ - -/* Begin PBXFileReference section */ - 05E31B57274EF0360083FCB6 /* GameController.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = GameController.framework; path = System/Library/Frameworks/GameController.framework; sourceTree = SDKROOT; }; - 07A82EDA213941D00078D120 /* imgui_widgets.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = imgui_widgets.cpp; path = ../../imgui_widgets.cpp; sourceTree = ""; }; - 4080A96B20B029B00036BA46 /* example_osx_opengl2 */ = {isa = PBXFileReference; explicitFileType = "compiled.mach-o.executable"; includeInIndex = 0; path = example_osx_opengl2; sourceTree = BUILT_PRODUCTS_DIR; }; - 4080A98A20B02CD90036BA46 /* main.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = main.mm; sourceTree = SOURCE_ROOT; }; - 4080A99E20B034280036BA46 /* imgui_impl_opengl2.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = imgui_impl_opengl2.cpp; path = ../../backends/imgui_impl_opengl2.cpp; sourceTree = ""; }; - 4080A99F20B034280036BA46 /* imgui_impl_osx.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; name = imgui_impl_osx.mm; path = ../../backends/imgui_impl_osx.mm; sourceTree = ""; }; - 4080A9A020B034280036BA46 /* imgui_impl_opengl2.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = imgui_impl_opengl2.h; path = ../../backends/imgui_impl_opengl2.h; sourceTree = ""; }; - 4080A9A120B034280036BA46 /* imgui_impl_osx.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = imgui_impl_osx.h; path = ../../backends/imgui_impl_osx.h; sourceTree = ""; }; - 4080A9A520B0343C0036BA46 /* imgui_internal.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = imgui_internal.h; path = ../../imgui_internal.h; sourceTree = ""; }; - 4080A9A620B0343C0036BA46 /* imgui_demo.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = imgui_demo.cpp; path = ../../imgui_demo.cpp; sourceTree = ""; }; - 4080A9A720B0343C0036BA46 /* imgui.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = imgui.cpp; path = ../../imgui.cpp; sourceTree = ""; }; - 4080A9A820B0343C0036BA46 /* imgui.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = imgui.h; path = ../../imgui.h; sourceTree = ""; }; - 4080A9AA20B0343C0036BA46 /* imgui_draw.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = imgui_draw.cpp; path = ../../imgui_draw.cpp; sourceTree = ""; }; - 4080A9AC20B0343C0036BA46 /* imconfig.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = imconfig.h; path = ../../imconfig.h; sourceTree = ""; }; - 4080A9B220B034E40036BA46 /* Cocoa.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = Cocoa.framework; path = System/Library/Frameworks/Cocoa.framework; sourceTree = SDKROOT; }; - 4080A9B420B034EA0036BA46 /* OpenGL.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = OpenGL.framework; path = System/Library/Frameworks/OpenGL.framework; sourceTree = SDKROOT; }; - 5079822F257677FC0038A28D /* imgui_tables.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = imgui_tables.cpp; path = ../../imgui_tables.cpp; sourceTree = ""; }; -/* End PBXFileReference section */ - -/* Begin PBXFrameworksBuildPhase section */ - 4080A96820B029B00036BA46 /* Frameworks */ = { - isa = PBXFrameworksBuildPhase; - buildActionMask = 2147483647; - files = ( - 4080A9B520B034EA0036BA46 /* OpenGL.framework in Frameworks */, - 4080A9B320B034E40036BA46 /* Cocoa.framework in Frameworks */, - 05E31B59274EF0700083FCB6 /* GameController.framework in Frameworks */, - ); - runOnlyForDeploymentPostprocessing = 0; - }; -/* End PBXFrameworksBuildPhase section */ - -/* Begin PBXGroup section */ - 4080A96220B029B00036BA46 = { - isa = PBXGroup; - children = ( - 5079822F257677FC0038A28D /* imgui_tables.cpp */, - 4080A9AC20B0343C0036BA46 /* imconfig.h */, - 4080A9A720B0343C0036BA46 /* imgui.cpp */, - 4080A9A820B0343C0036BA46 /* imgui.h */, - 07A82EDA213941D00078D120 /* imgui_widgets.cpp */, - 4080A9A620B0343C0036BA46 /* imgui_demo.cpp */, - 4080A9AA20B0343C0036BA46 /* imgui_draw.cpp */, - 4080A9A520B0343C0036BA46 /* imgui_internal.h */, - 4080A99E20B034280036BA46 /* imgui_impl_opengl2.cpp */, - 4080A9A020B034280036BA46 /* imgui_impl_opengl2.h */, - 4080A9A120B034280036BA46 /* imgui_impl_osx.h */, - 4080A99F20B034280036BA46 /* imgui_impl_osx.mm */, - 4080A98A20B02CD90036BA46 /* main.mm */, - 4080A96C20B029B00036BA46 /* Products */, - 4080A9B120B034E40036BA46 /* Frameworks */, - ); - sourceTree = ""; - }; - 4080A96C20B029B00036BA46 /* Products */ = { - isa = PBXGroup; - children = ( - 4080A96B20B029B00036BA46 /* example_osx_opengl2 */, - ); - name = Products; - sourceTree = ""; - }; - 4080A9B120B034E40036BA46 /* Frameworks */ = { - isa = PBXGroup; - children = ( - 05E31B57274EF0360083FCB6 /* GameController.framework */, - 4080A9B420B034EA0036BA46 /* OpenGL.framework */, - 4080A9B220B034E40036BA46 /* Cocoa.framework */, - ); - name = Frameworks; - sourceTree = ""; - }; -/* End PBXGroup section */ - -/* Begin PBXNativeTarget section */ - 4080A96A20B029B00036BA46 /* example_osx_opengl2 */ = { - isa = PBXNativeTarget; - buildConfigurationList = 4080A97220B029B00036BA46 /* Build configuration list for PBXNativeTarget "example_osx_opengl2" */; - buildPhases = ( - 4080A96720B029B00036BA46 /* Sources */, - 4080A96820B029B00036BA46 /* Frameworks */, - 4080A96920B029B00036BA46 /* CopyFiles */, - ); - buildRules = ( - ); - dependencies = ( - ); - name = example_osx_opengl2; - productName = example_osx_opengl2; - productReference = 4080A96B20B029B00036BA46 /* example_osx_opengl2 */; - productType = "com.apple.product-type.tool"; - }; -/* End PBXNativeTarget section */ - -/* Begin PBXProject section */ - 4080A96320B029B00036BA46 /* Project object */ = { - isa = PBXProject; - attributes = { - LastUpgradeCheck = 0930; - ORGANIZATIONNAME = ImGui; - TargetAttributes = { - 4080A96A20B029B00036BA46 = { - CreatedOnToolsVersion = 9.3.1; - ProvisioningStyle = Automatic; - }; - }; - }; - buildConfigurationList = 4080A96620B029B00036BA46 /* Build configuration list for PBXProject "example_apple_opengl2" */; - compatibilityVersion = "Xcode 8.0"; - developmentRegion = en; - hasScannedForEncodings = 0; - knownRegions = ( - en, - ); - mainGroup = 4080A96220B029B00036BA46; - productRefGroup = 4080A96C20B029B00036BA46 /* Products */; - projectDirPath = ""; - projectRoot = ""; - targets = ( - 4080A96A20B029B00036BA46 /* example_osx_opengl2 */, - ); - }; -/* End PBXProject section */ - -/* Begin PBXSourcesBuildPhase section */ - 4080A96720B029B00036BA46 /* Sources */ = { - isa = PBXSourcesBuildPhase; - buildActionMask = 2147483647; - files = ( - 4080A99820B02D340036BA46 /* main.mm in Sources */, - 4080A9AD20B0343C0036BA46 /* imgui_demo.cpp in Sources */, - 4080A9AF20B0343C0036BA46 /* imgui_draw.cpp in Sources */, - 4080A9A220B034280036BA46 /* imgui_impl_opengl2.cpp in Sources */, - 4080A9B020B0347A0036BA46 /* imgui_impl_osx.mm in Sources */, - 4080A9AE20B0343C0036BA46 /* imgui.cpp in Sources */, - 50798230257677FD0038A28D /* imgui_tables.cpp in Sources */, - 07A82EDB213941D00078D120 /* imgui_widgets.cpp in Sources */, - ); - runOnlyForDeploymentPostprocessing = 0; - }; -/* End PBXSourcesBuildPhase section */ - -/* Begin XCBuildConfiguration section */ - 4080A97020B029B00036BA46 /* Debug */ = { - isa = XCBuildConfiguration; - buildSettings = { - ALWAYS_SEARCH_USER_PATHS = NO; - CLANG_ANALYZER_NONNULL = YES; - CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE; - CLANG_CXX_LANGUAGE_STANDARD = "gnu++14"; - CLANG_CXX_LIBRARY = "libc++"; - CLANG_ENABLE_MODULES = YES; - CLANG_ENABLE_OBJC_ARC = YES; - CLANG_ENABLE_OBJC_WEAK = YES; - CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES; - CLANG_WARN_BOOL_CONVERSION = YES; - CLANG_WARN_COMMA = YES; - CLANG_WARN_CONSTANT_CONVERSION = YES; - CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES; - CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; - CLANG_WARN_DOCUMENTATION_COMMENTS = YES; - CLANG_WARN_EMPTY_BODY = YES; - CLANG_WARN_ENUM_CONVERSION = YES; - CLANG_WARN_INFINITE_RECURSION = YES; - CLANG_WARN_INT_CONVERSION = YES; - CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES; - CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES; - CLANG_WARN_OBJC_LITERAL_CONVERSION = YES; - CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; - CLANG_WARN_RANGE_LOOP_ANALYSIS = YES; - CLANG_WARN_STRICT_PROTOTYPES = YES; - CLANG_WARN_SUSPICIOUS_MOVE = YES; - CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE; - CLANG_WARN_UNREACHABLE_CODE = YES; - CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; - CODE_SIGN_IDENTITY = "-"; - COPY_PHASE_STRIP = NO; - DEBUG_INFORMATION_FORMAT = dwarf; - ENABLE_STRICT_OBJC_MSGSEND = YES; - ENABLE_TESTABILITY = YES; - GCC_C_LANGUAGE_STANDARD = gnu11; - GCC_DYNAMIC_NO_PIC = NO; - GCC_NO_COMMON_BLOCKS = YES; - GCC_OPTIMIZATION_LEVEL = 0; - GCC_PREPROCESSOR_DEFINITIONS = ( - "DEBUG=1", - "$(inherited)", - ); - GCC_WARN_64_TO_32_BIT_CONVERSION = YES; - GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; - GCC_WARN_UNDECLARED_SELECTOR = YES; - GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; - GCC_WARN_UNUSED_FUNCTION = YES; - GCC_WARN_UNUSED_VARIABLE = YES; - MACOSX_DEPLOYMENT_TARGET = 10.13; - MTL_ENABLE_DEBUG_INFO = YES; - ONLY_ACTIVE_ARCH = YES; - SDKROOT = macosx; - }; - name = Debug; - }; - 4080A97120B029B00036BA46 /* Release */ = { - isa = XCBuildConfiguration; - buildSettings = { - ALWAYS_SEARCH_USER_PATHS = NO; - CLANG_ANALYZER_NONNULL = YES; - CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE; - CLANG_CXX_LANGUAGE_STANDARD = "gnu++14"; - CLANG_CXX_LIBRARY = "libc++"; - CLANG_ENABLE_MODULES = YES; - CLANG_ENABLE_OBJC_ARC = YES; - CLANG_ENABLE_OBJC_WEAK = YES; - CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES; - CLANG_WARN_BOOL_CONVERSION = YES; - CLANG_WARN_COMMA = YES; - CLANG_WARN_CONSTANT_CONVERSION = YES; - CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES; - CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; - CLANG_WARN_DOCUMENTATION_COMMENTS = YES; - CLANG_WARN_EMPTY_BODY = YES; - CLANG_WARN_ENUM_CONVERSION = YES; - CLANG_WARN_INFINITE_RECURSION = YES; - CLANG_WARN_INT_CONVERSION = YES; - CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES; - CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES; - CLANG_WARN_OBJC_LITERAL_CONVERSION = YES; - CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; - CLANG_WARN_RANGE_LOOP_ANALYSIS = YES; - CLANG_WARN_STRICT_PROTOTYPES = YES; - CLANG_WARN_SUSPICIOUS_MOVE = YES; - CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE; - CLANG_WARN_UNREACHABLE_CODE = YES; - CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; - CODE_SIGN_IDENTITY = "-"; - COPY_PHASE_STRIP = NO; - DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym"; - ENABLE_NS_ASSERTIONS = NO; - ENABLE_STRICT_OBJC_MSGSEND = YES; - GCC_C_LANGUAGE_STANDARD = gnu11; - GCC_NO_COMMON_BLOCKS = YES; - GCC_WARN_64_TO_32_BIT_CONVERSION = YES; - GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; - GCC_WARN_UNDECLARED_SELECTOR = YES; - GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; - GCC_WARN_UNUSED_FUNCTION = YES; - GCC_WARN_UNUSED_VARIABLE = YES; - MACOSX_DEPLOYMENT_TARGET = 10.13; - MTL_ENABLE_DEBUG_INFO = NO; - SDKROOT = macosx; - }; - name = Release; - }; - 4080A97320B029B00036BA46 /* Debug */ = { - isa = XCBuildConfiguration; - buildSettings = { - CODE_SIGN_STYLE = Automatic; - MACOSX_DEPLOYMENT_TARGET = 10.12; - PRODUCT_NAME = "$(TARGET_NAME)"; - USER_HEADER_SEARCH_PATHS = ../..; - }; - name = Debug; - }; - 4080A97420B029B00036BA46 /* Release */ = { - isa = XCBuildConfiguration; - buildSettings = { - CODE_SIGN_STYLE = Automatic; - MACOSX_DEPLOYMENT_TARGET = 10.12; - PRODUCT_NAME = "$(TARGET_NAME)"; - USER_HEADER_SEARCH_PATHS = ../..; - }; - name = Release; - }; -/* End XCBuildConfiguration section */ - -/* Begin XCConfigurationList section */ - 4080A96620B029B00036BA46 /* Build configuration list for PBXProject "example_apple_opengl2" */ = { - isa = XCConfigurationList; - buildConfigurations = ( - 4080A97020B029B00036BA46 /* Debug */, - 4080A97120B029B00036BA46 /* Release */, - ); - defaultConfigurationIsVisible = 0; - defaultConfigurationName = Release; - }; - 4080A97220B029B00036BA46 /* Build configuration list for PBXNativeTarget "example_osx_opengl2" */ = { - isa = XCConfigurationList; - buildConfigurations = ( - 4080A97320B029B00036BA46 /* Debug */, - 4080A97420B029B00036BA46 /* Release */, - ); - defaultConfigurationIsVisible = 0; - defaultConfigurationName = Release; - }; -/* End XCConfigurationList section */ - }; - rootObject = 4080A96320B029B00036BA46 /* Project object */; -} diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_apple_opengl2/main.mm b/app/jni/src/libultraship/extern/ImGui/examples/example_apple_opengl2/main.mm deleted file mode 100644 index 11829a8..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_apple_opengl2/main.mm +++ /dev/null @@ -1,273 +0,0 @@ -// Dear ImGui: standalone example application for OSX + OpenGL2, using legacy fixed pipeline - -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#import -#import -#import - -#include "imgui.h" -#include "imgui_impl_opengl2.h" -#include "imgui_impl_osx.h" - -//----------------------------------------------------------------------------------- -// AppView -//----------------------------------------------------------------------------------- - -@interface AppView : NSOpenGLView -{ - NSTimer* animationTimer; -} -@end - -@implementation AppView - --(void)prepareOpenGL -{ - [super prepareOpenGL]; - -#ifndef DEBUG - GLint swapInterval = 1; - [[self openGLContext] setValues:&swapInterval forParameter:NSOpenGLCPSwapInterval]; - if (swapInterval == 0) - NSLog(@"Error: Cannot set swap interval."); -#endif -} - --(void)initialize -{ - // Setup Dear ImGui context - // FIXME: This example doesn't have proper cleanup... - IMGUI_CHECKVERSION(); - ImGui::CreateContext(); - ImGuiIO& io = ImGui::GetIO(); (void)io; - io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard; // Enable Keyboard Controls - io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad; // Enable Gamepad Controls - io.ConfigFlags |= ImGuiConfigFlags_DockingEnable; // Enable Docking - io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable; // Enable Multi-Viewport / Platform Windows - - // Setup Dear ImGui style - ImGui::StyleColorsDark(); - //ImGui::StyleColorsLight(); - - // When viewports are enabled we tweak WindowRounding/WindowBg so platform windows can look identical to regular ones. - ImGuiStyle& style = ImGui::GetStyle(); - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - style.WindowRounding = 0.0f; - style.Colors[ImGuiCol_WindowBg].w = 1.0f; - } - - // Setup Platform/Renderer backends - ImGui_ImplOSX_Init(self); - ImGui_ImplOpenGL2_Init(); - - // Load Fonts - // - If no fonts are loaded, dear imgui will use the default font. You can also load multiple fonts and use ImGui::PushFont()/PopFont() to select them. - // - AddFontFromFileTTF() will return the ImFont* so you can store it if you need to select the font among multiple. - // - If the file cannot be loaded, the function will return a nullptr. Please handle those errors in your application (e.g. use an assertion, or display an error and quit). - // - The fonts will be rasterized at a given size (w/ oversampling) and stored into a texture when calling ImFontAtlas::Build()/GetTexDataAsXXXX(), which ImGui_ImplXXXX_NewFrame below will call. - // - Use '#define IMGUI_ENABLE_FREETYPE' in your imconfig file to use Freetype for higher quality font rendering. - // - Read 'docs/FONTS.md' for more instructions and details. - // - Remember that in C/C++ if you want to include a backslash \ in a string literal you need to write a double backslash \\ ! - //io.Fonts->AddFontDefault(); - //io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\segoeui.ttf", 18.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/DroidSans.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Roboto-Medium.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Cousine-Regular.ttf", 15.0f); - //ImFont* font = io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\ArialUni.ttf", 18.0f, nullptr, io.Fonts->GetGlyphRangesJapanese()); - //IM_ASSERT(font != nullptr); -} - --(void)updateAndDrawDemoView -{ - // Start the Dear ImGui frame - ImGuiIO& io = ImGui::GetIO(); - ImGui_ImplOpenGL2_NewFrame(); - ImGui_ImplOSX_NewFrame(self); - ImGui::NewFrame(); - - // Our state (make them static = more or less global) as a convenience to keep the example terse. - static bool show_demo_window = true; - static bool show_another_window = false; - static ImVec4 clear_color = ImVec4(0.45f, 0.55f, 0.60f, 1.00f); - - // 1. Show the big demo window (Most of the sample code is in ImGui::ShowDemoWindow()! You can browse its code to learn more about Dear ImGui!). - if (show_demo_window) - ImGui::ShowDemoWindow(&show_demo_window); - - // 2. Show a simple window that we create ourselves. We use a Begin/End pair to create a named window. - { - static float f = 0.0f; - static int counter = 0; - - ImGui::Begin("Hello, world!"); // Create a window called "Hello, world!" and append into it. - - ImGui::Text("This is some useful text."); // Display some text (you can use a format strings too) - ImGui::Checkbox("Demo Window", &show_demo_window); // Edit bools storing our window open/close state - ImGui::Checkbox("Another Window", &show_another_window); - - ImGui::SliderFloat("float", &f, 0.0f, 1.0f); // Edit 1 float using a slider from 0.0f to 1.0f - ImGui::ColorEdit3("clear color", (float*)&clear_color); // Edit 3 floats representing a color - - if (ImGui::Button("Button")) // Buttons return true when clicked (most widgets return true when edited/activated) - counter++; - ImGui::SameLine(); - ImGui::Text("counter = %d", counter); - - ImGui::Text("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / io.Framerate, io.Framerate); - ImGui::End(); - } - - // 3. Show another simple window. - if (show_another_window) - { - ImGui::Begin("Another Window", &show_another_window); // Pass a pointer to our bool variable (the window will have a closing button that will clear the bool when clicked) - ImGui::Text("Hello from another window!"); - if (ImGui::Button("Close Me")) - show_another_window = false; - ImGui::End(); - } - - // Rendering - ImGui::Render(); - ImDrawData* draw_data = ImGui::GetDrawData(); - - [[self openGLContext] makeCurrentContext]; - GLsizei width = (GLsizei)(draw_data->DisplaySize.x * draw_data->FramebufferScale.x); - GLsizei height = (GLsizei)(draw_data->DisplaySize.y * draw_data->FramebufferScale.y); - glViewport(0, 0, width, height); - glClearColor(clear_color.x * clear_color.w, clear_color.y * clear_color.w, clear_color.z * clear_color.w, clear_color.w); - glClear(GL_COLOR_BUFFER_BIT); - - ImGui_ImplOpenGL2_RenderDrawData(draw_data); - - // Update and Render additional Platform Windows - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - ImGui::UpdatePlatformWindows(); - ImGui::RenderPlatformWindowsDefault(); - } - - // Present - [[self openGLContext] flushBuffer]; - - if (!animationTimer) - animationTimer = [NSTimer scheduledTimerWithTimeInterval:0.017 target:self selector:@selector(animationTimerFired:) userInfo:nil repeats:YES]; -} - --(void)reshape { [super reshape]; [[self openGLContext] update]; [self updateAndDrawDemoView]; } --(void)drawRect:(NSRect)bounds { [self updateAndDrawDemoView]; } --(void)animationTimerFired:(NSTimer*)timer { [self setNeedsDisplay:YES]; } --(void)dealloc { animationTimer = nil; } - -@end - -//----------------------------------------------------------------------------------- -// AppDelegate -//----------------------------------------------------------------------------------- - -@interface AppDelegate : NSObject -@property (nonatomic, readonly) NSWindow* window; -@end - -@implementation AppDelegate -@synthesize window = _window; - --(BOOL)applicationShouldTerminateAfterLastWindowClosed:(NSApplication *)theApplication -{ - return YES; -} - --(NSWindow*)window -{ - if (_window != nil) - return (_window); - - NSRect viewRect = NSMakeRect(100.0, 100.0, 100.0 + 1280.0, 100 + 720.0); - - _window = [[NSWindow alloc] initWithContentRect:viewRect styleMask:NSWindowStyleMaskTitled|NSWindowStyleMaskMiniaturizable|NSWindowStyleMaskResizable|NSWindowStyleMaskClosable backing:NSBackingStoreBuffered defer:YES]; - [_window setTitle:@"Dear ImGui OSX+OpenGL2 Example"]; - [_window setAcceptsMouseMovedEvents:YES]; - [_window setOpaque:YES]; - [_window makeKeyAndOrderFront:NSApp]; - - return (_window); -} - --(void)setupMenu -{ - NSMenu* mainMenuBar = [[NSMenu alloc] init]; - NSMenu* appMenu; - NSMenuItem* menuItem; - - appMenu = [[NSMenu alloc] initWithTitle:@"Dear ImGui OSX+OpenGL2 Example"]; - menuItem = [appMenu addItemWithTitle:@"Quit Dear ImGui OSX+OpenGL2 Example" action:@selector(terminate:) keyEquivalent:@"q"]; - [menuItem setKeyEquivalentModifierMask:NSEventModifierFlagCommand]; - - menuItem = [[NSMenuItem alloc] init]; - [menuItem setSubmenu:appMenu]; - - [mainMenuBar addItem:menuItem]; - - appMenu = nil; - [NSApp setMainMenu:mainMenuBar]; -} - --(void)dealloc -{ - _window = nil; -} - --(void)applicationDidFinishLaunching:(NSNotification *)aNotification -{ - // Make the application a foreground application (else it won't receive keyboard events) - ProcessSerialNumber psn = {0, kCurrentProcess}; - TransformProcessType(&psn, kProcessTransformToForegroundApplication); - - // Menu - [self setupMenu]; - - NSOpenGLPixelFormatAttribute attrs[] = - { - NSOpenGLPFADoubleBuffer, - NSOpenGLPFADepthSize, 32, - 0 - }; - - NSOpenGLPixelFormat* format = [[NSOpenGLPixelFormat alloc] initWithAttributes:attrs]; - AppView* view = [[AppView alloc] initWithFrame:self.window.frame pixelFormat:format]; - format = nil; -#if MAC_OS_X_VERSION_MAX_ALLOWED >= 1070 - if (floor(NSAppKitVersionNumber) > NSAppKitVersionNumber10_6) - [view setWantsBestResolutionOpenGLSurface:YES]; -#endif // MAC_OS_X_VERSION_MAX_ALLOWED >= 1070 - [self.window setContentView:view]; - - if ([view openGLContext] == nil) - NSLog(@"No OpenGL Context!"); - - [view initialize]; -} - -@end - -//----------------------------------------------------------------------------------- -// Application main() function -//----------------------------------------------------------------------------------- - -int main(int argc, const char* argv[]) -{ - @autoreleasepool - { - NSApp = [NSApplication sharedApplication]; - AppDelegate* delegate = [[AppDelegate alloc] init]; - [[NSApplication sharedApplication] setDelegate:delegate]; - [NSApp run]; - } - return NSApplicationMain(argc, argv); -} diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_emscripten_wgpu/Makefile b/app/jni/src/libultraship/extern/ImGui/examples/example_emscripten_wgpu/Makefile deleted file mode 100644 index 5c79f0c..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_emscripten_wgpu/Makefile +++ /dev/null @@ -1,88 +0,0 @@ -# -# Makefile to use with emscripten -# See https://emscripten.org/docs/getting_started/downloads.html -# for installation instructions. -# -# This Makefile assumes you have loaded emscripten's environment. -# (On Windows, you may need to execute emsdk_env.bat or encmdprompt.bat ahead) -# -# Running `make` will produce three files: -# - web/index.html (current stored in the repository) -# - web/index.js -# - web/index.wasm -# -# All three are needed to run the demo. - -CC = emcc -CXX = em++ -WEB_DIR = web -EXE = $(WEB_DIR)/index.js -IMGUI_DIR = ../.. -SOURCES = main.cpp -SOURCES += $(IMGUI_DIR)/imgui.cpp $(IMGUI_DIR)/imgui_demo.cpp $(IMGUI_DIR)/imgui_draw.cpp $(IMGUI_DIR)/imgui_tables.cpp $(IMGUI_DIR)/imgui_widgets.cpp -SOURCES += $(IMGUI_DIR)/backends/imgui_impl_glfw.cpp $(IMGUI_DIR)/backends/imgui_impl_wgpu.cpp -OBJS = $(addsuffix .o, $(basename $(notdir $(SOURCES)))) -UNAME_S := $(shell uname -s) -CPPFLAGS = -LDFLAGS = -EMS = - -##--------------------------------------------------------------------- -## EMSCRIPTEN OPTIONS -##--------------------------------------------------------------------- - -# ("EMS" options gets added to both CPPFLAGS and LDFLAGS, whereas some options are for linker only) -EMS += -s DISABLE_EXCEPTION_CATCHING=1 -LDFLAGS += -s USE_GLFW=3 -s USE_WEBGPU=1 -LDFLAGS += -s WASM=1 -s ALLOW_MEMORY_GROWTH=1 -s NO_EXIT_RUNTIME=0 -s ASSERTIONS=1 - -# Emscripten allows preloading a file or folder to be accessible at runtime. -# The Makefile for this example project suggests embedding the misc/fonts/ folder into our application, it will then be accessible as "/fonts" -# See documentation for more details: https://emscripten.org/docs/porting/files/packaging_files.html -# (Default value is 0. Set to 1 to enable file-system and include the misc/fonts/ folder as part of the build.) -USE_FILE_SYSTEM ?= 0 -ifeq ($(USE_FILE_SYSTEM), 0) -LDFLAGS += -s NO_FILESYSTEM=1 -CPPFLAGS += -DIMGUI_DISABLE_FILE_FUNCTIONS -endif -ifeq ($(USE_FILE_SYSTEM), 1) -LDFLAGS += --no-heap-copy --preload-file ../../misc/fonts@/fonts -endif - -##--------------------------------------------------------------------- -## FINAL BUILD FLAGS -##--------------------------------------------------------------------- - -CPPFLAGS += -I$(IMGUI_DIR) -I$(IMGUI_DIR)/backends -#CPPFLAGS += -g -CPPFLAGS += -Wall -Wformat -Os $(EMS) -#LDFLAGS += --shell-file shell_minimal.html -LDFLAGS += $(EMS) - -##--------------------------------------------------------------------- -## BUILD RULES -##--------------------------------------------------------------------- - -%.o:%.cpp - $(CXX) $(CPPFLAGS) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/%.cpp - $(CXX) $(CPPFLAGS) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/backends/%.cpp - $(CXX) $(CPPFLAGS) $(CXXFLAGS) -c -o $@ $< - -all: $(EXE) - @echo Build complete for $(EXE) - -$(WEB_DIR): - mkdir $@ - -serve: all - python3 -m http.server -d $(WEB_DIR) - -$(EXE): $(OBJS) $(WEB_DIR) - $(CXX) -o $@ $(OBJS) $(LDFLAGS) - -clean: - rm -f $(EXE) $(OBJS) $(WEB_DIR)/*.js $(WEB_DIR)/*.wasm $(WEB_DIR)/*.wasm.pre diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_emscripten_wgpu/README.md b/app/jni/src/libultraship/extern/ImGui/examples/example_emscripten_wgpu/README.md deleted file mode 100644 index c4c4dec..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_emscripten_wgpu/README.md +++ /dev/null @@ -1,24 +0,0 @@ -## How to Build - -- You need to install Emscripten from https://emscripten.org/docs/getting_started/downloads.html, and have the environment variables set, as described in https://emscripten.org/docs/getting_started/downloads.html#installation-instructions - -- Depending on your configuration, in Windows you may need to run `emsdk/emsdk_env.bat` in your console to access the Emscripten command-line tools. - -- You may also refer to our [Continuous Integration setup](https://github.com/ocornut/imgui/tree/master/.github/workflows) for Emscripten setup. - -- Then build using `make` while in the `example_emscripten_wgpu/` directory. - -- Requires recent Emscripten as WGPU is still a work-in-progress API. - -## How to Run - -To run on a local machine: -- Make sure your browse supports WGPU and it is enabled. WGPU is still WIP not enabled by default in most browser. -- `make serve` will use Python3 to spawn a local webserver, you can then browse http://localhost:8000 to access your build. -- Otherwise, generally you will need a local webserver: - - Quoting [https://emscripten.org/docs/getting_started](https://emscripten.org/docs/getting_started/Tutorial.html#generating-html):
-_"Unfortunately several browsers (including Chrome, Safari, and Internet Explorer) do not support file:// [XHR](https://emscripten.org/docs/site/glossary.html#term-xhr) requests, and can’t load extra files needed by the HTML (like a .wasm file, or packaged file data as mentioned lower down). For these browsers you’ll need to serve the files using a [local webserver](https://emscripten.org/docs/getting_started/FAQ.html#faq-local-webserver) and then open http://localhost:8000/hello.html."_ - - Emscripten SDK has a handy `emrun` command: `emrun web/example_emscripten_opengl3.html --browser firefox` which will spawn a temporary local webserver (in Firefox). See https://emscripten.org/docs/compiling/Running-html-files-with-emrun.html for details. - - You may use Python 3 builtin webserver: `python -m http.server -d web` (this is what `make serve` uses). - - You may use Python 2 builtin webserver: `cd web && python -m SimpleHTTPServer`. - - If you are accessing the files over a network, certain browsers, such as Firefox, will restrict Gamepad API access to secure contexts only (e.g. https only). diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_emscripten_wgpu/main.cpp b/app/jni/src/libultraship/extern/ImGui/examples/example_emscripten_wgpu/main.cpp deleted file mode 100644 index a2126bc..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_emscripten_wgpu/main.cpp +++ /dev/null @@ -1,253 +0,0 @@ -// Dear ImGui: standalone example application for Emscripten, using GLFW + WebGPU -// (Emscripten is a C++-to-javascript compiler, used to publish executables for the web. See https://emscripten.org/) - -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#include "imgui.h" -#include "imgui_impl_glfw.h" -#include "imgui_impl_wgpu.h" -#include -#include -#include -#include -#include -#include -#include - -// Global WebGPU required states -static WGPUDevice wgpu_device = nullptr; -static WGPUSurface wgpu_surface = nullptr; -static WGPUTextureFormat wgpu_preferred_fmt = WGPUTextureFormat_RGBA8Unorm; -static WGPUSwapChain wgpu_swap_chain = nullptr; -static int wgpu_swap_chain_width = 0; -static int wgpu_swap_chain_height = 0; - -// Forward declarations -static void MainLoopStep(void* window); -static bool InitWGPU(); -static void print_glfw_error(int error, const char* description); -static void print_wgpu_error(WGPUErrorType error_type, const char* message, void*); - -// Main code -int main(int, char**) -{ - glfwSetErrorCallback(print_glfw_error); - if (!glfwInit()) - return 1; - - // Make sure GLFW does not initialize any graphics context. - // This needs to be done explicitly later. - glfwWindowHint(GLFW_CLIENT_API, GLFW_NO_API); - GLFWwindow* window = glfwCreateWindow(1280, 720, "Dear ImGui GLFW+WebGPU example", nullptr, nullptr); - if (!window) - { - glfwTerminate(); - return 1; - } - - // Initialize the WebGPU environment - if (!InitWGPU()) - { - if (window) - glfwDestroyWindow(window); - glfwTerminate(); - return 1; - } - glfwShowWindow(window); - - // Setup Dear ImGui context - IMGUI_CHECKVERSION(); - ImGui::CreateContext(); - ImGuiIO& io = ImGui::GetIO(); (void)io; - io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard; // Enable Keyboard Controls - io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad; // Enable Gamepad Controls - - // For an Emscripten build we are disabling file-system access, so let's not attempt to do a fopen() of the imgui.ini file. - // You may manually call LoadIniSettingsFromMemory() to load settings from your own storage. - io.IniFilename = nullptr; - - // Setup Dear ImGui style - ImGui::StyleColorsDark(); - //ImGui::StyleColorsLight(); - - // Setup Platform/Renderer backends - ImGui_ImplGlfw_InitForOther(window, true); - ImGui_ImplWGPU_Init(wgpu_device, 3, wgpu_preferred_fmt, WGPUTextureFormat_Undefined); - - // Load Fonts - // - If no fonts are loaded, dear imgui will use the default font. You can also load multiple fonts and use ImGui::PushFont()/PopFont() to select them. - // - AddFontFromFileTTF() will return the ImFont* so you can store it if you need to select the font among multiple. - // - If the file cannot be loaded, the function will return a nullptr. Please handle those errors in your application (e.g. use an assertion, or display an error and quit). - // - The fonts will be rasterized at a given size (w/ oversampling) and stored into a texture when calling ImFontAtlas::Build()/GetTexDataAsXXXX(), which ImGui_ImplXXXX_NewFrame below will call. - // - Use '#define IMGUI_ENABLE_FREETYPE' in your imconfig file to use Freetype for higher quality font rendering. - // - Read 'docs/FONTS.md' for more instructions and details. - // - Remember that in C/C++ if you want to include a backslash \ in a string literal you need to write a double backslash \\ ! - // - Emscripten allows preloading a file or folder to be accessible at runtime. See Makefile for details. - //io.Fonts->AddFontDefault(); -#ifndef IMGUI_DISABLE_FILE_FUNCTIONS - //io.Fonts->AddFontFromFileTTF("fonts/segoeui.ttf", 18.0f); - io.Fonts->AddFontFromFileTTF("fonts/DroidSans.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("fonts/Roboto-Medium.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("fonts/Cousine-Regular.ttf", 15.0f); - //io.Fonts->AddFontFromFileTTF("fonts/ProggyTiny.ttf", 10.0f); - //ImFont* font = io.Fonts->AddFontFromFileTTF("fonts/ArialUni.ttf", 18.0f, nullptr, io.Fonts->GetGlyphRangesJapanese()); - //IM_ASSERT(font != nullptr); -#endif - - // This function will directly return and exit the main function. - // Make sure that no required objects get cleaned up. - // This way we can use the browsers 'requestAnimationFrame' to control the rendering. - emscripten_set_main_loop_arg(MainLoopStep, window, 0, false); - - return 0; -} - -static bool InitWGPU() -{ - wgpu_device = emscripten_webgpu_get_device(); - if (!wgpu_device) - return false; - - wgpuDeviceSetUncapturedErrorCallback(wgpu_device, print_wgpu_error, nullptr); - - // Use C++ wrapper due to misbehavior in Emscripten. - // Some offset computation for wgpuInstanceCreateSurface in JavaScript - // seem to be inline with struct alignments in the C++ structure - wgpu::SurfaceDescriptorFromCanvasHTMLSelector html_surface_desc = {}; - html_surface_desc.selector = "#canvas"; - - wgpu::SurfaceDescriptor surface_desc = {}; - surface_desc.nextInChain = &html_surface_desc; - - wgpu::Instance instance = wgpuCreateInstance(nullptr); - wgpu::Surface surface = instance.CreateSurface(&surface_desc); - wgpu::Adapter adapter = {}; - wgpu_preferred_fmt = (WGPUTextureFormat)surface.GetPreferredFormat(adapter); - wgpu_surface = surface.Release(); - - return true; -} - -static void MainLoopStep(void* window) -{ - ImGuiIO& io = ImGui::GetIO(); - - glfwPollEvents(); - - int width, height; - glfwGetFramebufferSize((GLFWwindow*)window, &width, &height); - - // React to changes in screen size - if (width != wgpu_swap_chain_width && height != wgpu_swap_chain_height) - { - ImGui_ImplWGPU_InvalidateDeviceObjects(); - if (wgpu_swap_chain) - wgpuSwapChainRelease(wgpu_swap_chain); - wgpu_swap_chain_width = width; - wgpu_swap_chain_height = height; - WGPUSwapChainDescriptor swap_chain_desc = {}; - swap_chain_desc.usage = WGPUTextureUsage_RenderAttachment; - swap_chain_desc.format = wgpu_preferred_fmt; - swap_chain_desc.width = width; - swap_chain_desc.height = height; - swap_chain_desc.presentMode = WGPUPresentMode_Fifo; - wgpu_swap_chain = wgpuDeviceCreateSwapChain(wgpu_device, wgpu_surface, &swap_chain_desc); - ImGui_ImplWGPU_CreateDeviceObjects(); - } - - // Start the Dear ImGui frame - ImGui_ImplWGPU_NewFrame(); - ImGui_ImplGlfw_NewFrame(); - ImGui::NewFrame(); - - // Our state - // (we use static, which essentially makes the variable globals, as a convenience to keep the example code easy to follow) - static bool show_demo_window = true; - static bool show_another_window = false; - static ImVec4 clear_color = ImVec4(0.45f, 0.55f, 0.60f, 1.00f); - - // 1. Show the big demo window (Most of the sample code is in ImGui::ShowDemoWindow()! You can browse its code to learn more about Dear ImGui!). - if (show_demo_window) - ImGui::ShowDemoWindow(&show_demo_window); - - // 2. Show a simple window that we create ourselves. We use a Begin/End pair to create a named window. - { - static float f = 0.0f; - static int counter = 0; - - ImGui::Begin("Hello, world!"); // Create a window called "Hello, world!" and append into it. - - ImGui::Text("This is some useful text."); // Display some text (you can use a format strings too) - ImGui::Checkbox("Demo Window", &show_demo_window); // Edit bools storing our window open/close state - ImGui::Checkbox("Another Window", &show_another_window); - - ImGui::SliderFloat("float", &f, 0.0f, 1.0f); // Edit 1 float using a slider from 0.0f to 1.0f - ImGui::ColorEdit3("clear color", (float*)&clear_color); // Edit 3 floats representing a color - - if (ImGui::Button("Button")) // Buttons return true when clicked (most widgets return true when edited/activated) - counter++; - ImGui::SameLine(); - ImGui::Text("counter = %d", counter); - - ImGui::Text("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / io.Framerate, io.Framerate); - ImGui::End(); - } - - // 3. Show another simple window. - if (show_another_window) - { - ImGui::Begin("Another Window", &show_another_window); // Pass a pointer to our bool variable (the window will have a closing button that will clear the bool when clicked) - ImGui::Text("Hello from another window!"); - if (ImGui::Button("Close Me")) - show_another_window = false; - ImGui::End(); - } - - // Rendering - ImGui::Render(); - - WGPURenderPassColorAttachment color_attachments = {}; - color_attachments.loadOp = WGPULoadOp_Clear; - color_attachments.storeOp = WGPUStoreOp_Store; - color_attachments.clearValue = { clear_color.x * clear_color.w, clear_color.y * clear_color.w, clear_color.z * clear_color.w, clear_color.w }; - color_attachments.view = wgpuSwapChainGetCurrentTextureView(wgpu_swap_chain); - WGPURenderPassDescriptor render_pass_desc = {}; - render_pass_desc.colorAttachmentCount = 1; - render_pass_desc.colorAttachments = &color_attachments; - render_pass_desc.depthStencilAttachment = nullptr; - - WGPUCommandEncoderDescriptor enc_desc = {}; - WGPUCommandEncoder encoder = wgpuDeviceCreateCommandEncoder(wgpu_device, &enc_desc); - - WGPURenderPassEncoder pass = wgpuCommandEncoderBeginRenderPass(encoder, &render_pass_desc); - ImGui_ImplWGPU_RenderDrawData(ImGui::GetDrawData(), pass); - wgpuRenderPassEncoderEnd(pass); - - WGPUCommandBufferDescriptor cmd_buffer_desc = {}; - WGPUCommandBuffer cmd_buffer = wgpuCommandEncoderFinish(encoder, &cmd_buffer_desc); - WGPUQueue queue = wgpuDeviceGetQueue(wgpu_device); - wgpuQueueSubmit(queue, 1, &cmd_buffer); -} - -static void print_glfw_error(int error, const char* description) -{ - printf("GLFW Error %d: %s\n", error, description); -} - -static void print_wgpu_error(WGPUErrorType error_type, const char* message, void*) -{ - const char* error_type_lbl = ""; - switch (error_type) - { - case WGPUErrorType_Validation: error_type_lbl = "Validation"; break; - case WGPUErrorType_OutOfMemory: error_type_lbl = "Out of memory"; break; - case WGPUErrorType_Unknown: error_type_lbl = "Unknown"; break; - case WGPUErrorType_DeviceLost: error_type_lbl = "Device lost"; break; - default: error_type_lbl = "Unknown"; - } - printf("%s error: %s\n", error_type_lbl, message); -} diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_metal/Makefile b/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_metal/Makefile deleted file mode 100644 index 82d5ac9..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_metal/Makefile +++ /dev/null @@ -1,46 +0,0 @@ -# -# You will need GLFW (http://www.glfw.org): -# brew install glfw -# - -#CXX = g++ -#CXX = clang++ - -EXE = example_glfw_metal -IMGUI_DIR = ../.. -SOURCES = main.mm -SOURCES += $(IMGUI_DIR)/imgui.cpp $(IMGUI_DIR)/imgui_demo.cpp $(IMGUI_DIR)/imgui_draw.cpp $(IMGUI_DIR)/imgui_tables.cpp $(IMGUI_DIR)/imgui_widgets.cpp -SOURCES += $(IMGUI_DIR)/backends/imgui_impl_glfw.cpp $(IMGUI_DIR)/backends/imgui_impl_metal.mm -OBJS = $(addsuffix .o, $(basename $(notdir $(SOURCES)))) - -LIBS = -framework Metal -framework MetalKit -framework Cocoa -framework IOKit -framework CoreVideo -framework QuartzCore -LIBS += -L/usr/local/lib -L/opt/homebrew/lib -LIBS += -lglfw - -CXXFLAGS = -std=c++11 -I$(IMGUI_DIR) -I$(IMGUI_DIR)/backends -I/usr/local/include -I/opt/homebrew/include -CXXFLAGS += -Wall -Wformat -CFLAGS = $(CXXFLAGS) - -%.o:%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/backends/%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -%.o:%.mm - $(CXX) $(CXXFLAGS) -ObjC++ -fobjc-weak -fobjc-arc -c -o $@ $< - -%.o:$(IMGUI_DIR)/backends/%.mm - $(CXX) $(CXXFLAGS) -ObjC++ -fobjc-weak -fobjc-arc -c -o $@ $< - -all: $(EXE) - @echo Build complete - -$(EXE): $(OBJS) - $(CXX) -o $@ $^ $(CXXFLAGS) $(LIBS) - -clean: - rm -f $(EXE) $(OBJS) diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_metal/main.mm b/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_metal/main.mm deleted file mode 100644 index 2f346ff..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_metal/main.mm +++ /dev/null @@ -1,194 +0,0 @@ -// Dear ImGui: standalone example application for GLFW + Metal, using programmable pipeline -// (GLFW is a cross-platform general purpose library for handling windows, inputs, OpenGL/Vulkan/Metal graphics context creation, etc.) - -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#include "imgui.h" -#include "imgui_impl_glfw.h" -#include "imgui_impl_metal.h" -#include - -#define GLFW_INCLUDE_NONE -#define GLFW_EXPOSE_NATIVE_COCOA -#include -#include - -#import -#import - -static void glfw_error_callback(int error, const char* description) -{ - fprintf(stderr, "Glfw Error %d: %s\n", error, description); -} - -int main(int, char**) -{ - // Setup Dear ImGui context - IMGUI_CHECKVERSION(); - ImGui::CreateContext(); - ImGuiIO& io = ImGui::GetIO(); (void)io; - io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard; // Enable Keyboard Controls - io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad; // Enable Gamepad Controls - io.ConfigFlags |= ImGuiConfigFlags_DockingEnable; // Enable Docking - io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable; // Enable Multi-Viewport / Platform Windows - - // Setup style - ImGui::StyleColorsDark(); - //ImGui::StyleColorsLight(); - - // When viewports are enabled we tweak WindowRounding/WindowBg so platform windows can look identical to regular ones. - ImGuiStyle& style = ImGui::GetStyle(); - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - style.WindowRounding = 0.0f; - style.Colors[ImGuiCol_WindowBg].w = 1.0f; - } - - // Load Fonts - // - If no fonts are loaded, dear imgui will use the default font. You can also load multiple fonts and use ImGui::PushFont()/PopFont() to select them. - // - AddFontFromFileTTF() will return the ImFont* so you can store it if you need to select the font among multiple. - // - If the file cannot be loaded, the function will return a nullptr. Please handle those errors in your application (e.g. use an assertion, or display an error and quit). - // - The fonts will be rasterized at a given size (w/ oversampling) and stored into a texture when calling ImFontAtlas::Build()/GetTexDataAsXXXX(), which ImGui_ImplXXXX_NewFrame below will call. - // - Use '#define IMGUI_ENABLE_FREETYPE' in your imconfig file to use Freetype for higher quality font rendering. - // - Read 'docs/FONTS.md' for more instructions and details. - // - Remember that in C/C++ if you want to include a backslash \ in a string literal you need to write a double backslash \\ ! - //io.Fonts->AddFontDefault(); - //io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\segoeui.ttf", 18.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/DroidSans.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Roboto-Medium.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Cousine-Regular.ttf", 15.0f); - //ImFont* font = io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\ArialUni.ttf", 18.0f, nullptr, io.Fonts->GetGlyphRangesJapanese()); - //IM_ASSERT(font != nullptr); - - // Setup window - glfwSetErrorCallback(glfw_error_callback); - if (!glfwInit()) - return 1; - - // Create window with graphics context - glfwWindowHint(GLFW_CLIENT_API, GLFW_NO_API); - GLFWwindow* window = glfwCreateWindow(1280, 720, "Dear ImGui GLFW+Metal example", nullptr, nullptr); - if (window == nullptr) - return 1; - - id device = MTLCreateSystemDefaultDevice(); - id commandQueue = [device newCommandQueue]; - - // Setup Platform/Renderer backends - ImGui_ImplGlfw_InitForOther(window, true); - ImGui_ImplMetal_Init(device); - - NSWindow *nswin = glfwGetCocoaWindow(window); - CAMetalLayer *layer = [CAMetalLayer layer]; - layer.device = device; - layer.pixelFormat = MTLPixelFormatBGRA8Unorm; - nswin.contentView.layer = layer; - nswin.contentView.wantsLayer = YES; - - MTLRenderPassDescriptor *renderPassDescriptor = [MTLRenderPassDescriptor new]; - - // Our state - bool show_demo_window = true; - bool show_another_window = false; - float clear_color[4] = {0.45f, 0.55f, 0.60f, 1.00f}; - - // Main loop - while (!glfwWindowShouldClose(window)) - { - @autoreleasepool - { - // Poll and handle events (inputs, window resize, etc.) - // You can read the io.WantCaptureMouse, io.WantCaptureKeyboard flags to tell if dear imgui wants to use your inputs. - // - When io.WantCaptureMouse is true, do not dispatch mouse input data to your main application, or clear/overwrite your copy of the mouse data. - // - When io.WantCaptureKeyboard is true, do not dispatch keyboard input data to your main application, or clear/overwrite your copy of the keyboard data. - // Generally you may always pass all inputs to dear imgui, and hide them from your application based on those two flags. - glfwPollEvents(); - - int width, height; - glfwGetFramebufferSize(window, &width, &height); - layer.drawableSize = CGSizeMake(width, height); - id drawable = [layer nextDrawable]; - - id commandBuffer = [commandQueue commandBuffer]; - renderPassDescriptor.colorAttachments[0].clearColor = MTLClearColorMake(clear_color[0] * clear_color[3], clear_color[1] * clear_color[3], clear_color[2] * clear_color[3], clear_color[3]); - renderPassDescriptor.colorAttachments[0].texture = drawable.texture; - renderPassDescriptor.colorAttachments[0].loadAction = MTLLoadActionClear; - renderPassDescriptor.colorAttachments[0].storeAction = MTLStoreActionStore; - id renderEncoder = [commandBuffer renderCommandEncoderWithDescriptor:renderPassDescriptor]; - [renderEncoder pushDebugGroup:@"ImGui demo"]; - - // Start the Dear ImGui frame - ImGui_ImplMetal_NewFrame(renderPassDescriptor); - ImGui_ImplGlfw_NewFrame(); - ImGui::NewFrame(); - - // 1. Show the big demo window (Most of the sample code is in ImGui::ShowDemoWindow()! You can browse its code to learn more about Dear ImGui!). - if (show_demo_window) - ImGui::ShowDemoWindow(&show_demo_window); - - // 2. Show a simple window that we create ourselves. We use a Begin/End pair to create a named window. - { - static float f = 0.0f; - static int counter = 0; - - ImGui::Begin("Hello, world!"); // Create a window called "Hello, world!" and append into it. - - ImGui::Text("This is some useful text."); // Display some text (you can use a format strings too) - ImGui::Checkbox("Demo Window", &show_demo_window); // Edit bools storing our window open/close state - ImGui::Checkbox("Another Window", &show_another_window); - - ImGui::SliderFloat("float", &f, 0.0f, 1.0f); // Edit 1 float using a slider from 0.0f to 1.0f - ImGui::ColorEdit3("clear color", (float*)&clear_color); // Edit 3 floats representing a color - - if (ImGui::Button("Button")) // Buttons return true when clicked (most widgets return true when edited/activated) - counter++; - ImGui::SameLine(); - ImGui::Text("counter = %d", counter); - - ImGui::Text("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / io.Framerate, io.Framerate); - ImGui::End(); - } - - // 3. Show another simple window. - if (show_another_window) - { - ImGui::Begin("Another Window", &show_another_window); // Pass a pointer to our bool variable (the window will have a closing button that will clear the bool when clicked) - ImGui::Text("Hello from another window!"); - if (ImGui::Button("Close Me")) - show_another_window = false; - ImGui::End(); - } - - // Rendering - ImGui::Render(); - ImGui_ImplMetal_RenderDrawData(ImGui::GetDrawData(), commandBuffer, renderEncoder); - - // Update and Render additional Platform Windows - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - ImGui::UpdatePlatformWindows(); - ImGui::RenderPlatformWindowsDefault(); - } - - [renderEncoder popDebugGroup]; - [renderEncoder endEncoding]; - - [commandBuffer presentDrawable:drawable]; - [commandBuffer commit]; - } - } - - // Cleanup - ImGui_ImplMetal_Shutdown(); - ImGui_ImplGlfw_Shutdown(); - ImGui::DestroyContext(); - - glfwDestroyWindow(window); - glfwTerminate(); - - return 0; -} diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl2/Makefile b/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl2/Makefile deleted file mode 100644 index 1f15c15..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl2/Makefile +++ /dev/null @@ -1,81 +0,0 @@ -# -# Cross Platform Makefile -# Compatible with MSYS2/MINGW, Ubuntu 14.04.1 and Mac OS X -# -# You will need GLFW (http://www.glfw.org): -# Linux: -# apt-get install libglfw-dev -# Mac OS X: -# brew install glfw -# MSYS2: -# pacman -S --noconfirm --needed mingw-w64-x86_64-toolchain mingw-w64-x86_64-glfw -# - -#CXX = g++ -#CXX = clang++ - -EXE = example_glfw_opengl2 -IMGUI_DIR = ../.. -SOURCES = main.cpp -SOURCES += $(IMGUI_DIR)/imgui.cpp $(IMGUI_DIR)/imgui_demo.cpp $(IMGUI_DIR)/imgui_draw.cpp $(IMGUI_DIR)/imgui_tables.cpp $(IMGUI_DIR)/imgui_widgets.cpp -SOURCES += $(IMGUI_DIR)/backends/imgui_impl_glfw.cpp $(IMGUI_DIR)/backends/imgui_impl_opengl2.cpp -OBJS = $(addsuffix .o, $(basename $(notdir $(SOURCES)))) -UNAME_S := $(shell uname -s) - -CXXFLAGS = -std=c++11 -I$(IMGUI_DIR) -I$(IMGUI_DIR)/backends -CXXFLAGS += -g -Wall -Wformat -LIBS = - -##--------------------------------------------------------------------- -## BUILD FLAGS PER PLATFORM -##--------------------------------------------------------------------- - -ifeq ($(UNAME_S), Linux) #LINUX - ECHO_MESSAGE = "Linux" - LIBS += -lGL `pkg-config --static --libs glfw3` - - CXXFLAGS += `pkg-config --cflags glfw3` - CFLAGS = $(CXXFLAGS) -endif - -ifeq ($(UNAME_S), Darwin) #APPLE - ECHO_MESSAGE = "Mac OS X" - LIBS += -framework OpenGL -framework Cocoa -framework IOKit -framework CoreVideo - LIBS += -L/usr/local/lib -L/opt/local/lib -L/opt/homebrew/lib - #LIBS += -lglfw3 - LIBS += -lglfw - - CXXFLAGS += -I/usr/local/include -I/opt/local/include -I/opt/homebrew/include - CFLAGS = $(CXXFLAGS) -endif - -ifeq ($(OS), Windows_NT) - ECHO_MESSAGE = "MinGW" - LIBS += -lglfw3 -lgdi32 -lopengl32 -limm32 - - CXXFLAGS += `pkg-config --cflags glfw3` - CFLAGS = $(CXXFLAGS) -endif - -##--------------------------------------------------------------------- -## BUILD RULES -##--------------------------------------------------------------------- - -%.o:%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/backends/%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -all: $(EXE) - @echo Build complete for $(ECHO_MESSAGE) - -$(EXE): $(OBJS) - $(CXX) -o $@ $^ $(CXXFLAGS) $(LIBS) - -clean: - rm -f $(EXE) $(OBJS) - diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl2/build_win32.bat b/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl2/build_win32.bat deleted file mode 100644 index 24c0e08..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl2/build_win32.bat +++ /dev/null @@ -1,8 +0,0 @@ -@REM Build for Visual Studio compiler. Run your copy of vcvars32.bat or vcvarsall.bat to setup command-line compiler. -@set OUT_DIR=Debug -@set OUT_EXE=example_glfw_opengl2 -@set INCLUDES=/I..\.. /I..\..\backends /I..\libs\glfw\include -@set SOURCES=main.cpp ..\..\backends\imgui_impl_opengl2.cpp ..\..\backends\imgui_impl_glfw.cpp ..\..\imgui*.cpp -@set LIBS=/LIBPATH:..\libs\glfw\lib-vc2010-32 glfw3.lib opengl32.lib gdi32.lib shell32.lib -mkdir %OUT_DIR% -cl /nologo /Zi /MD /utf-8 %INCLUDES% %SOURCES% /Fe%OUT_DIR%/%OUT_EXE%.exe /Fo%OUT_DIR%/ /link %LIBS% diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl2/example_glfw_opengl2.vcxproj b/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl2/example_glfw_opengl2.vcxproj deleted file mode 100644 index 2aa2550..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl2/example_glfw_opengl2.vcxproj +++ /dev/null @@ -1,186 +0,0 @@ - - - - - Debug - Win32 - - - Debug - x64 - - - Release - Win32 - - - Release - x64 - - - - {9CDA7840-B7A5-496D-A527-E95571496D18} - example_glfw_opengl2 - 8.1 - - - - Application - true - MultiByte - v140 - - - Application - true - MultiByte - v140 - - - Application - false - true - MultiByte - v140 - - - Application - false - true - MultiByte - v140 - - - - - - - - - - - - - - - - - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - - Level4 - Disabled - ..\..;..\..\backends;..\libs\glfw\include;%(AdditionalIncludeDirectories) - /utf-8 %(AdditionalOptions) - - - true - ..\libs\glfw\lib-vc2010-32;%(AdditionalLibraryDirectories) - opengl32.lib;glfw3.lib;%(AdditionalDependencies) - Console - msvcrt.lib - - - - - Level4 - Disabled - ..\..;..\..\backends;..\libs\glfw\include;%(AdditionalIncludeDirectories) - /utf-8 %(AdditionalOptions) - - - true - ..\libs\glfw\lib-vc2010-64;%(AdditionalLibraryDirectories) - opengl32.lib;glfw3.lib;%(AdditionalDependencies) - Console - msvcrt.lib - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends;..\libs\glfw\include;%(AdditionalIncludeDirectories) - false - /utf-8 %(AdditionalOptions) - - - true - true - true - ..\libs\glfw\lib-vc2010-32;%(AdditionalLibraryDirectories) - opengl32.lib;glfw3.lib;%(AdditionalDependencies) - Console - - - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends;..\libs\glfw\include;%(AdditionalIncludeDirectories) - false - /utf-8 %(AdditionalOptions) - - - true - true - true - ..\libs\glfw\lib-vc2010-64;%(AdditionalLibraryDirectories) - opengl32.lib;glfw3.lib;%(AdditionalDependencies) - Console - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl2/example_glfw_opengl2.vcxproj.filters b/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl2/example_glfw_opengl2.vcxproj.filters deleted file mode 100644 index 049b0b1..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl2/example_glfw_opengl2.vcxproj.filters +++ /dev/null @@ -1,64 +0,0 @@ - - - - - {c336cfe3-f0c4-464c-9ef0-a9e17a7ff222} - - - {4FC737F1-C7A5-4376-A066-2A32D752A2FF} - cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx - - - - - sources - - - imgui - - - imgui - - - imgui - - - imgui - - - imgui - - - sources - - - sources - - - - - imgui - - - imgui - - - imgui - - - sources - - - sources - - - - - - imgui - - - imgui - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl2/main.cpp b/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl2/main.cpp deleted file mode 100644 index 1ed2083..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl2/main.cpp +++ /dev/null @@ -1,189 +0,0 @@ -// Dear ImGui: standalone example application for GLFW + OpenGL2, using legacy fixed pipeline -// (GLFW is a cross-platform general purpose library for handling windows, inputs, OpenGL/Vulkan/Metal graphics context creation, etc.) - -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -// **DO NOT USE THIS CODE IF YOUR CODE/ENGINE IS USING MODERN OPENGL (SHADERS, VBO, VAO, etc.)** -// **Prefer using the code in the example_glfw_opengl2/ folder** -// See imgui_impl_glfw.cpp for details. - -#include "imgui.h" -#include "imgui_impl_glfw.h" -#include "imgui_impl_opengl2.h" -#include -#ifdef __APPLE__ -#define GL_SILENCE_DEPRECATION -#endif -#include - -// [Win32] Our example includes a copy of glfw3.lib pre-compiled with VS2010 to maximize ease of testing and compatibility with old VS compilers. -// To link with VS2010-era libraries, VS2015+ requires linking with legacy_stdio_definitions.lib, which we do using this pragma. -// Your own project should not be affected, as you are likely to link with a newer binary of GLFW that is adequate for your version of Visual Studio. -#if defined(_MSC_VER) && (_MSC_VER >= 1900) && !defined(IMGUI_DISABLE_WIN32_FUNCTIONS) -#pragma comment(lib, "legacy_stdio_definitions") -#endif - -static void glfw_error_callback(int error, const char* description) -{ - fprintf(stderr, "GLFW Error %d: %s\n", error, description); -} - -// Main code -int main(int, char**) -{ - glfwSetErrorCallback(glfw_error_callback); - if (!glfwInit()) - return 1; - - // Create window with graphics context - GLFWwindow* window = glfwCreateWindow(1280, 720, "Dear ImGui GLFW+OpenGL2 example", nullptr, nullptr); - if (window == nullptr) - return 1; - glfwMakeContextCurrent(window); - glfwSwapInterval(1); // Enable vsync - - // Setup Dear ImGui context - IMGUI_CHECKVERSION(); - ImGui::CreateContext(); - ImGuiIO& io = ImGui::GetIO(); (void)io; - io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard; // Enable Keyboard Controls - io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad; // Enable Gamepad Controls - io.ConfigFlags |= ImGuiConfigFlags_DockingEnable; // Enable Docking - io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable; // Enable Multi-Viewport / Platform Windows - //io.ConfigViewportsNoAutoMerge = true; - //io.ConfigViewportsNoTaskBarIcon = true; - - // Setup Dear ImGui style - ImGui::StyleColorsDark(); - //ImGui::StyleColorsLight(); - - // When viewports are enabled we tweak WindowRounding/WindowBg so platform windows can look identical to regular ones. - ImGuiStyle& style = ImGui::GetStyle(); - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - style.WindowRounding = 0.0f; - style.Colors[ImGuiCol_WindowBg].w = 1.0f; - } - - // Setup Platform/Renderer backends - ImGui_ImplGlfw_InitForOpenGL(window, true); - ImGui_ImplOpenGL2_Init(); - - // Load Fonts - // - If no fonts are loaded, dear imgui will use the default font. You can also load multiple fonts and use ImGui::PushFont()/PopFont() to select them. - // - AddFontFromFileTTF() will return the ImFont* so you can store it if you need to select the font among multiple. - // - If the file cannot be loaded, the function will return a nullptr. Please handle those errors in your application (e.g. use an assertion, or display an error and quit). - // - The fonts will be rasterized at a given size (w/ oversampling) and stored into a texture when calling ImFontAtlas::Build()/GetTexDataAsXXXX(), which ImGui_ImplXXXX_NewFrame below will call. - // - Use '#define IMGUI_ENABLE_FREETYPE' in your imconfig file to use Freetype for higher quality font rendering. - // - Read 'docs/FONTS.md' for more instructions and details. - // - Remember that in C/C++ if you want to include a backslash \ in a string literal you need to write a double backslash \\ ! - //io.Fonts->AddFontDefault(); - //io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\segoeui.ttf", 18.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/DroidSans.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Roboto-Medium.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Cousine-Regular.ttf", 15.0f); - //ImFont* font = io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\ArialUni.ttf", 18.0f, nullptr, io.Fonts->GetGlyphRangesJapanese()); - //IM_ASSERT(font != nullptr); - - // Our state - bool show_demo_window = true; - bool show_another_window = false; - ImVec4 clear_color = ImVec4(0.45f, 0.55f, 0.60f, 1.00f); - - // Main loop - while (!glfwWindowShouldClose(window)) - { - // Poll and handle events (inputs, window resize, etc.) - // You can read the io.WantCaptureMouse, io.WantCaptureKeyboard flags to tell if dear imgui wants to use your inputs. - // - When io.WantCaptureMouse is true, do not dispatch mouse input data to your main application, or clear/overwrite your copy of the mouse data. - // - When io.WantCaptureKeyboard is true, do not dispatch keyboard input data to your main application, or clear/overwrite your copy of the keyboard data. - // Generally you may always pass all inputs to dear imgui, and hide them from your application based on those two flags. - glfwPollEvents(); - - // Start the Dear ImGui frame - ImGui_ImplOpenGL2_NewFrame(); - ImGui_ImplGlfw_NewFrame(); - ImGui::NewFrame(); - - // 1. Show the big demo window (Most of the sample code is in ImGui::ShowDemoWindow()! You can browse its code to learn more about Dear ImGui!). - if (show_demo_window) - ImGui::ShowDemoWindow(&show_demo_window); - - // 2. Show a simple window that we create ourselves. We use a Begin/End pair to create a named window. - { - static float f = 0.0f; - static int counter = 0; - - ImGui::Begin("Hello, world!"); // Create a window called "Hello, world!" and append into it. - - ImGui::Text("This is some useful text."); // Display some text (you can use a format strings too) - ImGui::Checkbox("Demo Window", &show_demo_window); // Edit bools storing our window open/close state - ImGui::Checkbox("Another Window", &show_another_window); - - ImGui::SliderFloat("float", &f, 0.0f, 1.0f); // Edit 1 float using a slider from 0.0f to 1.0f - ImGui::ColorEdit3("clear color", (float*)&clear_color); // Edit 3 floats representing a color - - if (ImGui::Button("Button")) // Buttons return true when clicked (most widgets return true when edited/activated) - counter++; - ImGui::SameLine(); - ImGui::Text("counter = %d", counter); - - ImGui::Text("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / io.Framerate, io.Framerate); - ImGui::End(); - } - - // 3. Show another simple window. - if (show_another_window) - { - ImGui::Begin("Another Window", &show_another_window); // Pass a pointer to our bool variable (the window will have a closing button that will clear the bool when clicked) - ImGui::Text("Hello from another window!"); - if (ImGui::Button("Close Me")) - show_another_window = false; - ImGui::End(); - } - - // Rendering - ImGui::Render(); - int display_w, display_h; - glfwGetFramebufferSize(window, &display_w, &display_h); - glViewport(0, 0, display_w, display_h); - glClearColor(clear_color.x * clear_color.w, clear_color.y * clear_color.w, clear_color.z * clear_color.w, clear_color.w); - glClear(GL_COLOR_BUFFER_BIT); - - // If you are using this code with non-legacy OpenGL header/contexts (which you should not, prefer using imgui_impl_opengl3.cpp!!), - // you may need to backup/reset/restore other state, e.g. for current shader using the commented lines below. - //GLint last_program; - //glGetIntegerv(GL_CURRENT_PROGRAM, &last_program); - //glUseProgram(0); - ImGui_ImplOpenGL2_RenderDrawData(ImGui::GetDrawData()); - //glUseProgram(last_program); - - // Update and Render additional Platform Windows - // (Platform functions may change the current OpenGL context, so we save/restore it to make it easier to paste this code elsewhere. - // For this specific demo app we could also call glfwMakeContextCurrent(window) directly) - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - GLFWwindow* backup_current_context = glfwGetCurrentContext(); - ImGui::UpdatePlatformWindows(); - ImGui::RenderPlatformWindowsDefault(); - glfwMakeContextCurrent(backup_current_context); - } - - glfwMakeContextCurrent(window); - glfwSwapBuffers(window); - } - - // Cleanup - ImGui_ImplOpenGL2_Shutdown(); - ImGui_ImplGlfw_Shutdown(); - ImGui::DestroyContext(); - - glfwDestroyWindow(window); - glfwTerminate(); - - return 0; -} diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl3/Makefile b/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl3/Makefile deleted file mode 100644 index 252ce57..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl3/Makefile +++ /dev/null @@ -1,89 +0,0 @@ -# -# Cross Platform Makefile -# Compatible with MSYS2/MINGW, Ubuntu 14.04.1 and Mac OS X -# -# You will need GLFW (http://www.glfw.org): -# Linux: -# apt-get install libglfw-dev -# Mac OS X: -# brew install glfw -# MSYS2: -# pacman -S --noconfirm --needed mingw-w64-x86_64-toolchain mingw-w64-x86_64-glfw -# - -#CXX = g++ -#CXX = clang++ - -EXE = example_glfw_opengl3 -IMGUI_DIR = ../.. -SOURCES = main.cpp -SOURCES += $(IMGUI_DIR)/imgui.cpp $(IMGUI_DIR)/imgui_demo.cpp $(IMGUI_DIR)/imgui_draw.cpp $(IMGUI_DIR)/imgui_tables.cpp $(IMGUI_DIR)/imgui_widgets.cpp -SOURCES += $(IMGUI_DIR)/backends/imgui_impl_glfw.cpp $(IMGUI_DIR)/backends/imgui_impl_opengl3.cpp -OBJS = $(addsuffix .o, $(basename $(notdir $(SOURCES)))) -UNAME_S := $(shell uname -s) -LINUX_GL_LIBS = -lGL - -CXXFLAGS = -std=c++11 -I$(IMGUI_DIR) -I$(IMGUI_DIR)/backends -CXXFLAGS += -g -Wall -Wformat -LIBS = - -##--------------------------------------------------------------------- -## OPENGL ES -##--------------------------------------------------------------------- - -## This assumes a GL ES library available in the system, e.g. libGLESv2.so -# CXXFLAGS += -DIMGUI_IMPL_OPENGL_ES2 -# LINUX_GL_LIBS = -lGLESv2 - -##--------------------------------------------------------------------- -## BUILD FLAGS PER PLATFORM -##--------------------------------------------------------------------- - -ifeq ($(UNAME_S), Linux) #LINUX - ECHO_MESSAGE = "Linux" - LIBS += $(LINUX_GL_LIBS) `pkg-config --static --libs glfw3` - - CXXFLAGS += `pkg-config --cflags glfw3` - CFLAGS = $(CXXFLAGS) -endif - -ifeq ($(UNAME_S), Darwin) #APPLE - ECHO_MESSAGE = "Mac OS X" - LIBS += -framework OpenGL -framework Cocoa -framework IOKit -framework CoreVideo - LIBS += -L/usr/local/lib -L/opt/local/lib -L/opt/homebrew/lib - #LIBS += -lglfw3 - LIBS += -lglfw - - CXXFLAGS += -I/usr/local/include -I/opt/local/include -I/opt/homebrew/include - CFLAGS = $(CXXFLAGS) -endif - -ifeq ($(OS), Windows_NT) - ECHO_MESSAGE = "MinGW" - LIBS += -lglfw3 -lgdi32 -lopengl32 -limm32 - - CXXFLAGS += `pkg-config --cflags glfw3` - CFLAGS = $(CXXFLAGS) -endif - -##--------------------------------------------------------------------- -## BUILD RULES -##--------------------------------------------------------------------- - -%.o:%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/backends/%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -all: $(EXE) - @echo Build complete for $(ECHO_MESSAGE) - -$(EXE): $(OBJS) - $(CXX) -o $@ $^ $(CXXFLAGS) $(LIBS) - -clean: - rm -f $(EXE) $(OBJS) diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl3/Makefile.emscripten b/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl3/Makefile.emscripten deleted file mode 100644 index 8ea4eac..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl3/Makefile.emscripten +++ /dev/null @@ -1,91 +0,0 @@ -# -# Makefile to use with GLFW+emscripten -# See https://emscripten.org/docs/getting_started/downloads.html -# for installation instructions. -# -# This Makefile assumes you have loaded emscripten's environment. -# (On Windows, you may need to execute emsdk_env.bat or encmdprompt.bat ahead) -# -# Running `make -f Makefile.emscripten` will produce three files: -# - web/index.html -# - web/index.js -# - web/index.wasm -# -# All three are needed to run the demo. - -CC = emcc -CXX = em++ -WEB_DIR = web -EXE = $(WEB_DIR)/index.html -IMGUI_DIR = ../.. -SOURCES = main.cpp -SOURCES += $(IMGUI_DIR)/imgui.cpp $(IMGUI_DIR)/imgui_demo.cpp $(IMGUI_DIR)/imgui_draw.cpp $(IMGUI_DIR)/imgui_tables.cpp $(IMGUI_DIR)/imgui_widgets.cpp -SOURCES += $(IMGUI_DIR)/backends/imgui_impl_glfw.cpp $(IMGUI_DIR)/backends/imgui_impl_opengl3.cpp -OBJS = $(addsuffix .o, $(basename $(notdir $(SOURCES)))) -UNAME_S := $(shell uname -s) -CPPFLAGS = -LDFLAGS = -EMS = - -##--------------------------------------------------------------------- -## EMSCRIPTEN OPTIONS -##--------------------------------------------------------------------- - -# ("EMS" options gets added to both CPPFLAGS and LDFLAGS, whereas some options are for linker only) -EMS += -s DISABLE_EXCEPTION_CATCHING=1 -LDFLAGS += -s USE_GLFW=3 -s WASM=1 -s ALLOW_MEMORY_GROWTH=1 -s NO_EXIT_RUNTIME=0 -s ASSERTIONS=1 - -# Uncomment next line to fix possible rendering bugs with Emscripten version older then 1.39.0 (https://github.com/ocornut/imgui/issues/2877) -#EMS += -s BINARYEN_TRAP_MODE=clamp -#EMS += -s SAFE_HEAP=1 ## Adds overhead - -# Emscripten allows preloading a file or folder to be accessible at runtime. -# The Makefile for this example project suggests embedding the misc/fonts/ folder into our application, it will then be accessible as "/fonts" -# See documentation for more details: https://emscripten.org/docs/porting/files/packaging_files.html -# (Default value is 0. Set to 1 to enable file-system and include the misc/fonts/ folder as part of the build.) -USE_FILE_SYSTEM ?= 0 -ifeq ($(USE_FILE_SYSTEM), 0) -LDFLAGS += -s NO_FILESYSTEM=1 -CPPFLAGS += -DIMGUI_DISABLE_FILE_FUNCTIONS -endif -ifeq ($(USE_FILE_SYSTEM), 1) -LDFLAGS += --no-heap-copy --preload-file ../../misc/fonts@/fonts -endif - -##--------------------------------------------------------------------- -## FINAL BUILD FLAGS -##--------------------------------------------------------------------- - -CPPFLAGS += -I$(IMGUI_DIR) -I$(IMGUI_DIR)/backends -#CPPFLAGS += -g -CPPFLAGS += -Wall -Wformat -Os $(EMS) -# LDFLAGS += --shell-file ../libs/emscripten/shell_minimal.html -LDFLAGS += $(EMS) - -##--------------------------------------------------------------------- -## BUILD RULES -##--------------------------------------------------------------------- - -%.o:%.cpp - $(CXX) $(CPPFLAGS) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/%.cpp - $(CXX) $(CPPFLAGS) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/backends/%.cpp - $(CXX) $(CPPFLAGS) $(CXXFLAGS) -c -o $@ $< - -all: $(EXE) - @echo Build complete for $(EXE) - -$(WEB_DIR): - mkdir $@ - -serve: all - python3 -m http.server -d $(WEB_DIR) - -$(EXE): $(OBJS) $(WEB_DIR) - $(CXX) -o $@ $(OBJS) $(LDFLAGS) - -clean: - rm -rf $(OBJS) $(WEB_DIR) diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl3/build_win32.bat b/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl3/build_win32.bat deleted file mode 100644 index b5979ad..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl3/build_win32.bat +++ /dev/null @@ -1,8 +0,0 @@ -@REM Build for Visual Studio compiler. Run your copy of vcvars32.bat or vcvarsall.bat to setup command-line compiler. -@set OUT_DIR=Debug -@set OUT_EXE=example_glfw_opengl3 -@set INCLUDES=/I..\.. /I..\..\backends /I..\libs\glfw\include -@set SOURCES=main.cpp ..\..\backends\imgui_impl_glfw.cpp ..\..\backends\imgui_impl_opengl3.cpp ..\..\imgui*.cpp -@set LIBS=/LIBPATH:..\libs\glfw\lib-vc2010-32 glfw3.lib opengl32.lib gdi32.lib shell32.lib -mkdir %OUT_DIR% -cl /nologo /Zi /MD /utf-8 %INCLUDES% %SOURCES% /Fe%OUT_DIR%/%OUT_EXE%.exe /Fo%OUT_DIR%/ /link %LIBS% diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl3/example_glfw_opengl3.vcxproj b/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl3/example_glfw_opengl3.vcxproj deleted file mode 100644 index 4bd503a..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl3/example_glfw_opengl3.vcxproj +++ /dev/null @@ -1,187 +0,0 @@ - - - - - Debug - Win32 - - - Debug - x64 - - - Release - Win32 - - - Release - x64 - - - - {4a1fb5ea-22f5-42a8-ab92-1d2df5d47fb9} - example_glfw_opengl3 - 8.1 - - - - Application - true - MultiByte - v140 - - - Application - true - MultiByte - v140 - - - Application - false - true - MultiByte - v140 - - - Application - false - true - MultiByte - v140 - - - - - - - - - - - - - - - - - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - - Level4 - Disabled - ..\..;..\..\backends;..\libs\glfw\include;%(AdditionalIncludeDirectories) - /utf-8 %(AdditionalOptions) - - - true - ..\libs\glfw\lib-vc2010-32;%(AdditionalLibraryDirectories) - opengl32.lib;glfw3.lib;%(AdditionalDependencies) - Console - msvcrt.lib - - - - - Level4 - Disabled - ..\..;..\..\backends;..\libs\glfw\include;%(AdditionalIncludeDirectories) - /utf-8 %(AdditionalOptions) - - - true - ..\libs\glfw\lib-vc2010-64;%(AdditionalLibraryDirectories) - opengl32.lib;glfw3.lib;%(AdditionalDependencies) - Console - msvcrt.lib - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends;..\libs\glfw\include;%(AdditionalIncludeDirectories) - false - /utf-8 %(AdditionalOptions) - - - true - true - true - ..\libs\glfw\lib-vc2010-32;%(AdditionalLibraryDirectories) - opengl32.lib;glfw3.lib;%(AdditionalDependencies) - Console - - - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends;..\libs\glfw\include;%(AdditionalIncludeDirectories) - false - /utf-8 %(AdditionalOptions) - - - true - true - true - ..\libs\glfw\lib-vc2010-64;%(AdditionalLibraryDirectories) - opengl32.lib;glfw3.lib;%(AdditionalDependencies) - Console - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl3/example_glfw_opengl3.vcxproj.filters b/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl3/example_glfw_opengl3.vcxproj.filters deleted file mode 100644 index bc79bb1..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl3/example_glfw_opengl3.vcxproj.filters +++ /dev/null @@ -1,67 +0,0 @@ - - - - - {20b90ce4-7fcb-4731-b9a0-075f875de82d} - - - {f18ab499-84e1-499f-8eff-9754361e0e52} - cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx - - - - - sources - - - imgui - - - imgui - - - imgui - - - imgui - - - imgui - - - sources - - - sources - - - - - imgui - - - imgui - - - imgui - - - sources - - - sources - - - sources - - - - - - imgui - - - imgui - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl3/main.cpp b/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl3/main.cpp deleted file mode 100644 index 2e369fb..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_opengl3/main.cpp +++ /dev/null @@ -1,217 +0,0 @@ -// Dear ImGui: standalone example application for GLFW + OpenGL 3, using programmable pipeline -// (GLFW is a cross-platform general purpose library for handling windows, inputs, OpenGL/Vulkan/Metal graphics context creation, etc.) - -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#include "imgui.h" -#include "imgui_impl_glfw.h" -#include "imgui_impl_opengl3.h" -#include -#define GL_SILENCE_DEPRECATION -#if defined(IMGUI_IMPL_OPENGL_ES2) -#include -#endif -#include // Will drag system OpenGL headers - -// [Win32] Our example includes a copy of glfw3.lib pre-compiled with VS2010 to maximize ease of testing and compatibility with old VS compilers. -// To link with VS2010-era libraries, VS2015+ requires linking with legacy_stdio_definitions.lib, which we do using this pragma. -// Your own project should not be affected, as you are likely to link with a newer binary of GLFW that is adequate for your version of Visual Studio. -#if defined(_MSC_VER) && (_MSC_VER >= 1900) && !defined(IMGUI_DISABLE_WIN32_FUNCTIONS) -#pragma comment(lib, "legacy_stdio_definitions") -#endif - -// This example can also compile and run with Emscripten! See 'Makefile.emscripten' for details. -#ifdef __EMSCRIPTEN__ -#include "../libs/emscripten/emscripten_mainloop_stub.h" -#endif - -static void glfw_error_callback(int error, const char* description) -{ - fprintf(stderr, "GLFW Error %d: %s\n", error, description); -} - -// Main code -int main(int, char**) -{ - glfwSetErrorCallback(glfw_error_callback); - if (!glfwInit()) - return 1; - - // Decide GL+GLSL versions -#if defined(IMGUI_IMPL_OPENGL_ES2) - // GL ES 2.0 + GLSL 100 - const char* glsl_version = "#version 100"; - glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 2); - glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 0); - glfwWindowHint(GLFW_CLIENT_API, GLFW_OPENGL_ES_API); -#elif defined(__APPLE__) - // GL 3.2 + GLSL 150 - const char* glsl_version = "#version 150"; - glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3); - glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 2); - glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE); // 3.2+ only - glfwWindowHint(GLFW_OPENGL_FORWARD_COMPAT, GL_TRUE); // Required on Mac -#else - // GL 3.0 + GLSL 130 - const char* glsl_version = "#version 130"; - glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3); - glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 0); - //glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE); // 3.2+ only - //glfwWindowHint(GLFW_OPENGL_FORWARD_COMPAT, GL_TRUE); // 3.0+ only -#endif - - // Create window with graphics context - GLFWwindow* window = glfwCreateWindow(1280, 720, "Dear ImGui GLFW+OpenGL3 example", nullptr, nullptr); - if (window == nullptr) - return 1; - glfwMakeContextCurrent(window); - glfwSwapInterval(1); // Enable vsync - - // Setup Dear ImGui context - IMGUI_CHECKVERSION(); - ImGui::CreateContext(); - ImGuiIO& io = ImGui::GetIO(); (void)io; - io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard; // Enable Keyboard Controls - io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad; // Enable Gamepad Controls - io.ConfigFlags |= ImGuiConfigFlags_DockingEnable; // Enable Docking - io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable; // Enable Multi-Viewport / Platform Windows - //io.ConfigViewportsNoAutoMerge = true; - //io.ConfigViewportsNoTaskBarIcon = true; - - // Setup Dear ImGui style - ImGui::StyleColorsDark(); - //ImGui::StyleColorsLight(); - - // When viewports are enabled we tweak WindowRounding/WindowBg so platform windows can look identical to regular ones. - ImGuiStyle& style = ImGui::GetStyle(); - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - style.WindowRounding = 0.0f; - style.Colors[ImGuiCol_WindowBg].w = 1.0f; - } - - // Setup Platform/Renderer backends - ImGui_ImplGlfw_InitForOpenGL(window, true); - ImGui_ImplOpenGL3_Init(glsl_version); - - // Load Fonts - // - If no fonts are loaded, dear imgui will use the default font. You can also load multiple fonts and use ImGui::PushFont()/PopFont() to select them. - // - AddFontFromFileTTF() will return the ImFont* so you can store it if you need to select the font among multiple. - // - If the file cannot be loaded, the function will return a nullptr. Please handle those errors in your application (e.g. use an assertion, or display an error and quit). - // - The fonts will be rasterized at a given size (w/ oversampling) and stored into a texture when calling ImFontAtlas::Build()/GetTexDataAsXXXX(), which ImGui_ImplXXXX_NewFrame below will call. - // - Use '#define IMGUI_ENABLE_FREETYPE' in your imconfig file to use Freetype for higher quality font rendering. - // - Read 'docs/FONTS.md' for more instructions and details. - // - Remember that in C/C++ if you want to include a backslash \ in a string literal you need to write a double backslash \\ ! - // - Our Emscripten build process allows embedding fonts to be accessible at runtime from the "fonts/" folder. See Makefile.emscripten for details. - //io.Fonts->AddFontDefault(); - //io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\segoeui.ttf", 18.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/DroidSans.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Roboto-Medium.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Cousine-Regular.ttf", 15.0f); - //ImFont* font = io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\ArialUni.ttf", 18.0f, nullptr, io.Fonts->GetGlyphRangesJapanese()); - //IM_ASSERT(font != nullptr); - - // Our state - bool show_demo_window = true; - bool show_another_window = false; - ImVec4 clear_color = ImVec4(0.45f, 0.55f, 0.60f, 1.00f); - - // Main loop -#ifdef __EMSCRIPTEN__ - // For an Emscripten build we are disabling file-system access, so let's not attempt to do a fopen() of the imgui.ini file. - // You may manually call LoadIniSettingsFromMemory() to load settings from your own storage. - io.IniFilename = nullptr; - EMSCRIPTEN_MAINLOOP_BEGIN -#else - while (!glfwWindowShouldClose(window)) -#endif - { - // Poll and handle events (inputs, window resize, etc.) - // You can read the io.WantCaptureMouse, io.WantCaptureKeyboard flags to tell if dear imgui wants to use your inputs. - // - When io.WantCaptureMouse is true, do not dispatch mouse input data to your main application, or clear/overwrite your copy of the mouse data. - // - When io.WantCaptureKeyboard is true, do not dispatch keyboard input data to your main application, or clear/overwrite your copy of the keyboard data. - // Generally you may always pass all inputs to dear imgui, and hide them from your application based on those two flags. - glfwPollEvents(); - - // Start the Dear ImGui frame - ImGui_ImplOpenGL3_NewFrame(); - ImGui_ImplGlfw_NewFrame(); - ImGui::NewFrame(); - - // 1. Show the big demo window (Most of the sample code is in ImGui::ShowDemoWindow()! You can browse its code to learn more about Dear ImGui!). - if (show_demo_window) - ImGui::ShowDemoWindow(&show_demo_window); - - // 2. Show a simple window that we create ourselves. We use a Begin/End pair to create a named window. - { - static float f = 0.0f; - static int counter = 0; - - ImGui::Begin("Hello, world!"); // Create a window called "Hello, world!" and append into it. - - ImGui::Text("This is some useful text."); // Display some text (you can use a format strings too) - ImGui::Checkbox("Demo Window", &show_demo_window); // Edit bools storing our window open/close state - ImGui::Checkbox("Another Window", &show_another_window); - - ImGui::SliderFloat("float", &f, 0.0f, 1.0f); // Edit 1 float using a slider from 0.0f to 1.0f - ImGui::ColorEdit3("clear color", (float*)&clear_color); // Edit 3 floats representing a color - - if (ImGui::Button("Button")) // Buttons return true when clicked (most widgets return true when edited/activated) - counter++; - ImGui::SameLine(); - ImGui::Text("counter = %d", counter); - - ImGui::Text("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / io.Framerate, io.Framerate); - ImGui::End(); - } - - // 3. Show another simple window. - if (show_another_window) - { - ImGui::Begin("Another Window", &show_another_window); // Pass a pointer to our bool variable (the window will have a closing button that will clear the bool when clicked) - ImGui::Text("Hello from another window!"); - if (ImGui::Button("Close Me")) - show_another_window = false; - ImGui::End(); - } - - // Rendering - ImGui::Render(); - int display_w, display_h; - glfwGetFramebufferSize(window, &display_w, &display_h); - glViewport(0, 0, display_w, display_h); - glClearColor(clear_color.x * clear_color.w, clear_color.y * clear_color.w, clear_color.z * clear_color.w, clear_color.w); - glClear(GL_COLOR_BUFFER_BIT); - ImGui_ImplOpenGL3_RenderDrawData(ImGui::GetDrawData()); - - // Update and Render additional Platform Windows - // (Platform functions may change the current OpenGL context, so we save/restore it to make it easier to paste this code elsewhere. - // For this specific demo app we could also call glfwMakeContextCurrent(window) directly) - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - GLFWwindow* backup_current_context = glfwGetCurrentContext(); - ImGui::UpdatePlatformWindows(); - ImGui::RenderPlatformWindowsDefault(); - glfwMakeContextCurrent(backup_current_context); - } - - glfwSwapBuffers(window); - } -#ifdef __EMSCRIPTEN__ - EMSCRIPTEN_MAINLOOP_END; -#endif - - // Cleanup - ImGui_ImplOpenGL3_Shutdown(); - ImGui_ImplGlfw_Shutdown(); - ImGui::DestroyContext(); - - glfwDestroyWindow(window); - glfwTerminate(); - - return 0; -} diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_vulkan/CMakeLists.txt b/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_vulkan/CMakeLists.txt deleted file mode 100644 index a6e5bf9..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_vulkan/CMakeLists.txt +++ /dev/null @@ -1,45 +0,0 @@ -# Example usage: -# mkdir build -# cd build -# cmake -g "Visual Studio 14 2015" .. - -cmake_minimum_required(VERSION 2.8) -project(imgui_example_glfw_vulkan C CXX) - -if(NOT CMAKE_BUILD_TYPE) - set(CMAKE_BUILD_TYPE Debug CACHE STRING "" FORCE) -endif() - -set(CMAKE_CXX_STANDARD 11) -set (CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -DVK_PROTOTYPES") -set (CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -DVK_PROTOTYPES") - -# GLFW -set(GLFW_DIR ../../../glfw) # Set this to point to an up-to-date GLFW repo -option(GLFW_BUILD_EXAMPLES "Build the GLFW example programs" OFF) -option(GLFW_BUILD_TESTS "Build the GLFW test programs" OFF) -option(GLFW_BUILD_DOCS "Build the GLFW documentation" OFF) -option(GLFW_INSTALL "Generate installation target" OFF) -option(GLFW_DOCUMENT_INTERNALS "Include internals in documentation" OFF) -add_subdirectory(${GLFW_DIR} binary_dir EXCLUDE_FROM_ALL) -include_directories(${GLFW_DIR}/include) - -# Dear ImGui -set(IMGUI_DIR ../../) -include_directories(${IMGUI_DIR} ${IMGUI_DIR}/backends ..) - -# Libraries -find_package(Vulkan REQUIRED) -#find_library(VULKAN_LIBRARY - #NAMES vulkan vulkan-1) -#set(LIBRARIES "glfw;${VULKAN_LIBRARY}") -set(LIBRARIES "glfw;Vulkan::Vulkan") - -# Use vulkan headers from glfw: -include_directories(${GLFW_DIR}/deps) - -file(GLOB sources *.cpp) - -add_executable(example_glfw_vulkan ${sources} ${IMGUI_DIR}/backends/imgui_impl_glfw.cpp ${IMGUI_DIR}/backends/imgui_impl_vulkan.cpp ${IMGUI_DIR}/imgui.cpp ${IMGUI_DIR}/imgui_draw.cpp ${IMGUI_DIR}/imgui_demo.cpp ${IMGUI_DIR}/imgui_tables.cpp ${IMGUI_DIR}/imgui_widgets.cpp) -target_link_libraries(example_glfw_vulkan ${LIBRARIES}) -target_compile_definitions(example_glfw_vulkan PUBLIC -DImTextureID=ImU64) diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_vulkan/build_win32.bat b/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_vulkan/build_win32.bat deleted file mode 100644 index be92398..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_vulkan/build_win32.bat +++ /dev/null @@ -1,14 +0,0 @@ -@REM Build for Visual Studio compiler. Run your copy of vcvars32.bat or vcvarsall.bat to setup command-line compiler. - -@set OUT_EXE=example_glfw_vulkan -@set INCLUDES=/I..\.. /I..\..\backends /I..\libs\glfw\include /I %VULKAN_SDK%\include -@set SOURCES=main.cpp ..\..\backends\imgui_impl_vulkan.cpp ..\..\backends\imgui_impl_glfw.cpp ..\..\imgui*.cpp -@set LIBS=/LIBPATH:..\libs\glfw\lib-vc2010-32 /libpath:%VULKAN_SDK%\lib32 glfw3.lib opengl32.lib gdi32.lib shell32.lib vulkan-1.lib - -@set OUT_DIR=Debug -mkdir %OUT_DIR% -cl /nologo /Zi /MD /utf-8 %INCLUDES% /D ImTextureID=ImU64 %SOURCES% /Fe%OUT_DIR%/%OUT_EXE%.exe /Fo%OUT_DIR%/ /link %LIBS% - -@set OUT_DIR=Release -mkdir %OUT_DIR% -cl /nologo /Zi /MD /utf-8 /Ox /Oi %INCLUDES% /D ImTextureID=ImU64 %SOURCES% /Fe%OUT_DIR%/%OUT_EXE%.exe /Fo%OUT_DIR%/ /link %LIBS% diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_vulkan/build_win64.bat b/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_vulkan/build_win64.bat deleted file mode 100644 index c60b027..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_vulkan/build_win64.bat +++ /dev/null @@ -1,13 +0,0 @@ -@REM Build for Visual Studio compiler. Run your copy of amd64/vcvars32.bat to setup 64-bit command-line compiler. - -@set INCLUDES=/I..\.. /I..\..\backends /I..\libs\glfw\include /I %VULKAN_SDK%\include -@set SOURCES=main.cpp ..\..\backends\imgui_impl_vulkan.cpp ..\..\backends\imgui_impl_glfw.cpp ..\..\imgui*.cpp -@set LIBS=/LIBPATH:..\libs\glfw\lib-vc2010-64 /libpath:%VULKAN_SDK%\lib glfw3.lib opengl32.lib gdi32.lib shell32.lib vulkan-1.lib - -@set OUT_DIR=Debug -mkdir %OUT_DIR% -cl /nologo /Zi /MD /utf-8 %INCLUDES% /D ImTextureID=ImU64 %SOURCES% /Fe%OUT_DIR%/%OUT_EXE%.exe /Fo%OUT_DIR%/ /link %LIBS% - -@set OUT_DIR=Release -mkdir %OUT_DIR% -cl /nologo /Zi /MD /utf-8 /Ox /Oi %INCLUDES% /D ImTextureID=ImU64 %SOURCES% /Fe%OUT_DIR%/%OUT_EXE%.exe /Fo%OUT_DIR%/ /link %LIBS% diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_vulkan/example_glfw_vulkan.vcxproj b/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_vulkan/example_glfw_vulkan.vcxproj deleted file mode 100644 index d0d1c5f..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_vulkan/example_glfw_vulkan.vcxproj +++ /dev/null @@ -1,190 +0,0 @@ - - - - - Debug - Win32 - - - Debug - x64 - - - Release - Win32 - - - Release - x64 - - - - {57E2DF5A-6FC8-45BB-99DD-91A18C646E80} - example_glfw_vulkan - 8.1 - - - - Application - true - MultiByte - v140 - - - Application - true - MultiByte - v140 - - - Application - false - true - MultiByte - v140 - - - Application - false - true - MultiByte - v140 - - - - - - - - - - - - - - - - - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - - Level4 - Disabled - ..\..;..\..\backends;%VULKAN_SDK%\include;..\libs\glfw\include;%(AdditionalIncludeDirectories) - ImTextureID=ImU64;_MBCS;%(PreprocessorDefinitions) - /utf-8 %(AdditionalOptions) - - - true - %VULKAN_SDK%\lib32;..\libs\glfw\lib-vc2010-32;%(AdditionalLibraryDirectories) - vulkan-1.lib;glfw3.lib;%(AdditionalDependencies) - Console - msvcrt.lib - - - - - Level4 - Disabled - ..\..;..\..\backends;%VULKAN_SDK%\include;..\libs\glfw\include;%(AdditionalIncludeDirectories) - ImTextureID=ImU64;_MBCS;%(PreprocessorDefinitions) - /utf-8 %(AdditionalOptions) - - - true - %VULKAN_SDK%\lib;..\libs\glfw\lib-vc2010-64;%(AdditionalLibraryDirectories) - vulkan-1.lib;glfw3.lib;%(AdditionalDependencies) - Console - msvcrt.lib - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends;%VULKAN_SDK%\include;..\libs\glfw\include;%(AdditionalIncludeDirectories) - false - ImTextureID=ImU64;_MBCS;%(PreprocessorDefinitions) - /utf-8 %(AdditionalOptions) - - - true - true - true - %VULKAN_SDK%\lib32;..\libs\glfw\lib-vc2010-32;%(AdditionalLibraryDirectories) - vulkan-1.lib;glfw3.lib;%(AdditionalDependencies) - Console - - - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends;%VULKAN_SDK%\include;..\libs\glfw\include;%(AdditionalIncludeDirectories) - false - ImTextureID=ImU64;_MBCS;%(PreprocessorDefinitions) - /utf-8 %(AdditionalOptions) - - - true - true - true - %VULKAN_SDK%\lib;..\libs\glfw\lib-vc2010-64;%(AdditionalLibraryDirectories) - vulkan-1.lib;glfw3.lib;%(AdditionalDependencies) - Console - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_vulkan/example_glfw_vulkan.vcxproj.filters b/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_vulkan/example_glfw_vulkan.vcxproj.filters deleted file mode 100644 index 510fc85..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_vulkan/example_glfw_vulkan.vcxproj.filters +++ /dev/null @@ -1,64 +0,0 @@ - - - - - {20b90ce4-7fcb-4731-b9a0-075f875de82d} - - - {f18ab499-84e1-499f-8eff-9754361e0e52} - cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx - - - - - sources - - - imgui - - - imgui - - - imgui - - - imgui - - - imgui - - - sources - - - sources - - - - - imgui - - - imgui - - - imgui - - - sources - - - sources - - - - - - imgui - - - imgui - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_vulkan/main.cpp b/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_vulkan/main.cpp deleted file mode 100644 index 7d0a05f..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_glfw_vulkan/main.cpp +++ /dev/null @@ -1,611 +0,0 @@ -// Dear ImGui: standalone example application for Glfw + Vulkan - -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -// Important note to the reader who wish to integrate imgui_impl_vulkan.cpp/.h in their own engine/app. -// - Common ImGui_ImplVulkan_XXX functions and structures are used to interface with imgui_impl_vulkan.cpp/.h. -// You will use those if you want to use this rendering backend in your engine/app. -// - Helper ImGui_ImplVulkanH_XXX functions and structures are only used by this example (main.cpp) and by -// the backend itself (imgui_impl_vulkan.cpp), but should PROBABLY NOT be used by your own engine/app code. -// Read comments in imgui_impl_vulkan.h. - -#include "imgui.h" -#include "imgui_impl_glfw.h" -#include "imgui_impl_vulkan.h" -#include // printf, fprintf -#include // abort -#define GLFW_INCLUDE_NONE -#define GLFW_INCLUDE_VULKAN -#include -#include -//#include - -// [Win32] Our example includes a copy of glfw3.lib pre-compiled with VS2010 to maximize ease of testing and compatibility with old VS compilers. -// To link with VS2010-era libraries, VS2015+ requires linking with legacy_stdio_definitions.lib, which we do using this pragma. -// Your own project should not be affected, as you are likely to link with a newer binary of GLFW that is adequate for your version of Visual Studio. -#if defined(_MSC_VER) && (_MSC_VER >= 1900) && !defined(IMGUI_DISABLE_WIN32_FUNCTIONS) -#pragma comment(lib, "legacy_stdio_definitions") -#endif - -//#define IMGUI_UNLIMITED_FRAME_RATE -#ifdef _DEBUG -#define IMGUI_VULKAN_DEBUG_REPORT -#endif - -// Data -static VkAllocationCallbacks* g_Allocator = nullptr; -static VkInstance g_Instance = VK_NULL_HANDLE; -static VkPhysicalDevice g_PhysicalDevice = VK_NULL_HANDLE; -static VkDevice g_Device = VK_NULL_HANDLE; -static uint32_t g_QueueFamily = (uint32_t)-1; -static VkQueue g_Queue = VK_NULL_HANDLE; -static VkDebugReportCallbackEXT g_DebugReport = VK_NULL_HANDLE; -static VkPipelineCache g_PipelineCache = VK_NULL_HANDLE; -static VkDescriptorPool g_DescriptorPool = VK_NULL_HANDLE; - -static ImGui_ImplVulkanH_Window g_MainWindowData; -static int g_MinImageCount = 2; -static bool g_SwapChainRebuild = false; - -static void glfw_error_callback(int error, const char* description) -{ - fprintf(stderr, "GLFW Error %d: %s\n", error, description); -} -static void check_vk_result(VkResult err) -{ - if (err == 0) - return; - fprintf(stderr, "[vulkan] Error: VkResult = %d\n", err); - if (err < 0) - abort(); -} - -#ifdef IMGUI_VULKAN_DEBUG_REPORT -static VKAPI_ATTR VkBool32 VKAPI_CALL debug_report(VkDebugReportFlagsEXT flags, VkDebugReportObjectTypeEXT objectType, uint64_t object, size_t location, int32_t messageCode, const char* pLayerPrefix, const char* pMessage, void* pUserData) -{ - (void)flags; (void)object; (void)location; (void)messageCode; (void)pUserData; (void)pLayerPrefix; // Unused arguments - fprintf(stderr, "[vulkan] Debug report from ObjectType: %i\nMessage: %s\n\n", objectType, pMessage); - return VK_FALSE; -} -#endif // IMGUI_VULKAN_DEBUG_REPORT - -static bool IsExtensionAvailable(const ImVector& properties, const char* extension) -{ - for (const VkExtensionProperties& p : properties) - if (strcmp(p.extensionName, extension) == 0) - return true; - return false; -} - -static VkPhysicalDevice SetupVulkan_SelectPhysicalDevice() -{ - uint32_t gpu_count; - VkResult err = vkEnumeratePhysicalDevices(g_Instance, &gpu_count, nullptr); - check_vk_result(err); - IM_ASSERT(gpu_count > 0); - - ImVector gpus; - gpus.resize(gpu_count); - err = vkEnumeratePhysicalDevices(g_Instance, &gpu_count, gpus.Data); - check_vk_result(err); - - // If a number >1 of GPUs got reported, find discrete GPU if present, or use first one available. This covers - // most common cases (multi-gpu/integrated+dedicated graphics). Handling more complicated setups (multiple - // dedicated GPUs) is out of scope of this sample. - for (VkPhysicalDevice& device : gpus) - { - VkPhysicalDeviceProperties properties; - vkGetPhysicalDeviceProperties(device, &properties); - if (properties.deviceType == VK_PHYSICAL_DEVICE_TYPE_DISCRETE_GPU) - return device; - } - - // Use first GPU (Integrated) is a Discrete one is not available. - if (gpu_count > 0) - return gpus[0]; - return VK_NULL_HANDLE; -} - -static void SetupVulkan(ImVector instance_extensions) -{ - VkResult err; - - // Create Vulkan Instance - { - VkInstanceCreateInfo create_info = {}; - create_info.sType = VK_STRUCTURE_TYPE_INSTANCE_CREATE_INFO; - - // Enumerate available extensions - uint32_t properties_count; - ImVector properties; - vkEnumerateInstanceExtensionProperties(nullptr, &properties_count, nullptr); - properties.resize(properties_count); - err = vkEnumerateInstanceExtensionProperties(nullptr, &properties_count, properties.Data); - check_vk_result(err); - - // Enable required extensions - if (IsExtensionAvailable(properties, VK_KHR_GET_PHYSICAL_DEVICE_PROPERTIES_2_EXTENSION_NAME)) - instance_extensions.push_back(VK_KHR_GET_PHYSICAL_DEVICE_PROPERTIES_2_EXTENSION_NAME); -#ifdef VK_KHR_PORTABILITY_ENUMERATION_EXTENSION_NAME - if (IsExtensionAvailable(properties, VK_KHR_PORTABILITY_ENUMERATION_EXTENSION_NAME)) - { - instance_extensions.push_back(VK_KHR_PORTABILITY_ENUMERATION_EXTENSION_NAME); - create_info.flags |= VK_INSTANCE_CREATE_ENUMERATE_PORTABILITY_BIT_KHR; - } -#endif - - // Enabling validation layers -#ifdef IMGUI_VULKAN_DEBUG_REPORT - const char* layers[] = { "VK_LAYER_KHRONOS_validation" }; - create_info.enabledLayerCount = 1; - create_info.ppEnabledLayerNames = layers; - instance_extensions.push_back("VK_EXT_debug_report"); -#endif - - // Create Vulkan Instance - create_info.enabledExtensionCount = (uint32_t)instance_extensions.Size; - create_info.ppEnabledExtensionNames = instance_extensions.Data; - err = vkCreateInstance(&create_info, g_Allocator, &g_Instance); - check_vk_result(err); - - // Setup the debug report callback -#ifdef IMGUI_VULKAN_DEBUG_REPORT - auto vkCreateDebugReportCallbackEXT = (PFN_vkCreateDebugReportCallbackEXT)vkGetInstanceProcAddr(g_Instance, "vkCreateDebugReportCallbackEXT"); - IM_ASSERT(vkCreateDebugReportCallbackEXT != nullptr); - VkDebugReportCallbackCreateInfoEXT debug_report_ci = {}; - debug_report_ci.sType = VK_STRUCTURE_TYPE_DEBUG_REPORT_CALLBACK_CREATE_INFO_EXT; - debug_report_ci.flags = VK_DEBUG_REPORT_ERROR_BIT_EXT | VK_DEBUG_REPORT_WARNING_BIT_EXT | VK_DEBUG_REPORT_PERFORMANCE_WARNING_BIT_EXT; - debug_report_ci.pfnCallback = debug_report; - debug_report_ci.pUserData = nullptr; - err = vkCreateDebugReportCallbackEXT(g_Instance, &debug_report_ci, g_Allocator, &g_DebugReport); - check_vk_result(err); -#endif - } - - // Select Physical Device (GPU) - g_PhysicalDevice = SetupVulkan_SelectPhysicalDevice(); - - // Select graphics queue family - { - uint32_t count; - vkGetPhysicalDeviceQueueFamilyProperties(g_PhysicalDevice, &count, nullptr); - VkQueueFamilyProperties* queues = (VkQueueFamilyProperties*)malloc(sizeof(VkQueueFamilyProperties) * count); - vkGetPhysicalDeviceQueueFamilyProperties(g_PhysicalDevice, &count, queues); - for (uint32_t i = 0; i < count; i++) - if (queues[i].queueFlags & VK_QUEUE_GRAPHICS_BIT) - { - g_QueueFamily = i; - break; - } - free(queues); - IM_ASSERT(g_QueueFamily != (uint32_t)-1); - } - - // Create Logical Device (with 1 queue) - { - ImVector device_extensions; - device_extensions.push_back("VK_KHR_swapchain"); - - // Enumerate physical device extension - uint32_t properties_count; - ImVector properties; - vkEnumerateDeviceExtensionProperties(g_PhysicalDevice, nullptr, &properties_count, nullptr); - properties.resize(properties_count); - vkEnumerateDeviceExtensionProperties(g_PhysicalDevice, nullptr, &properties_count, properties.Data); -#ifdef VK_KHR_PORTABILITY_SUBSET_EXTENSION_NAME - if (IsExtensionAvailable(properties, VK_KHR_PORTABILITY_SUBSET_EXTENSION_NAME)) - device_extensions.push_back(VK_KHR_PORTABILITY_SUBSET_EXTENSION_NAME); -#endif - - const float queue_priority[] = { 1.0f }; - VkDeviceQueueCreateInfo queue_info[1] = {}; - queue_info[0].sType = VK_STRUCTURE_TYPE_DEVICE_QUEUE_CREATE_INFO; - queue_info[0].queueFamilyIndex = g_QueueFamily; - queue_info[0].queueCount = 1; - queue_info[0].pQueuePriorities = queue_priority; - VkDeviceCreateInfo create_info = {}; - create_info.sType = VK_STRUCTURE_TYPE_DEVICE_CREATE_INFO; - create_info.queueCreateInfoCount = sizeof(queue_info) / sizeof(queue_info[0]); - create_info.pQueueCreateInfos = queue_info; - create_info.enabledExtensionCount = (uint32_t)device_extensions.Size; - create_info.ppEnabledExtensionNames = device_extensions.Data; - err = vkCreateDevice(g_PhysicalDevice, &create_info, g_Allocator, &g_Device); - check_vk_result(err); - vkGetDeviceQueue(g_Device, g_QueueFamily, 0, &g_Queue); - } - - // Create Descriptor Pool - // The example only requires a single combined image sampler descriptor for the font image and only uses one descriptor set (for that) - // If you wish to load e.g. additional textures you may need to alter pools sizes. - { - VkDescriptorPoolSize pool_sizes[] = - { - { VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER, 1 }, - }; - VkDescriptorPoolCreateInfo pool_info = {}; - pool_info.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_POOL_CREATE_INFO; - pool_info.flags = VK_DESCRIPTOR_POOL_CREATE_FREE_DESCRIPTOR_SET_BIT; - pool_info.maxSets = 1; - pool_info.poolSizeCount = (uint32_t)IM_ARRAYSIZE(pool_sizes); - pool_info.pPoolSizes = pool_sizes; - err = vkCreateDescriptorPool(g_Device, &pool_info, g_Allocator, &g_DescriptorPool); - check_vk_result(err); - } -} - -// All the ImGui_ImplVulkanH_XXX structures/functions are optional helpers used by the demo. -// Your real engine/app may not use them. -static void SetupVulkanWindow(ImGui_ImplVulkanH_Window* wd, VkSurfaceKHR surface, int width, int height) -{ - wd->Surface = surface; - - // Check for WSI support - VkBool32 res; - vkGetPhysicalDeviceSurfaceSupportKHR(g_PhysicalDevice, g_QueueFamily, wd->Surface, &res); - if (res != VK_TRUE) - { - fprintf(stderr, "Error no WSI support on physical device 0\n"); - exit(-1); - } - - // Select Surface Format - const VkFormat requestSurfaceImageFormat[] = { VK_FORMAT_B8G8R8A8_UNORM, VK_FORMAT_R8G8B8A8_UNORM, VK_FORMAT_B8G8R8_UNORM, VK_FORMAT_R8G8B8_UNORM }; - const VkColorSpaceKHR requestSurfaceColorSpace = VK_COLORSPACE_SRGB_NONLINEAR_KHR; - wd->SurfaceFormat = ImGui_ImplVulkanH_SelectSurfaceFormat(g_PhysicalDevice, wd->Surface, requestSurfaceImageFormat, (size_t)IM_ARRAYSIZE(requestSurfaceImageFormat), requestSurfaceColorSpace); - - // Select Present Mode -#ifdef IMGUI_UNLIMITED_FRAME_RATE - VkPresentModeKHR present_modes[] = { VK_PRESENT_MODE_MAILBOX_KHR, VK_PRESENT_MODE_IMMEDIATE_KHR, VK_PRESENT_MODE_FIFO_KHR }; -#else - VkPresentModeKHR present_modes[] = { VK_PRESENT_MODE_FIFO_KHR }; -#endif - wd->PresentMode = ImGui_ImplVulkanH_SelectPresentMode(g_PhysicalDevice, wd->Surface, &present_modes[0], IM_ARRAYSIZE(present_modes)); - //printf("[vulkan] Selected PresentMode = %d\n", wd->PresentMode); - - // Create SwapChain, RenderPass, Framebuffer, etc. - IM_ASSERT(g_MinImageCount >= 2); - ImGui_ImplVulkanH_CreateOrResizeWindow(g_Instance, g_PhysicalDevice, g_Device, wd, g_QueueFamily, g_Allocator, width, height, g_MinImageCount); -} - -static void CleanupVulkan() -{ - vkDestroyDescriptorPool(g_Device, g_DescriptorPool, g_Allocator); - -#ifdef IMGUI_VULKAN_DEBUG_REPORT - // Remove the debug report callback - auto vkDestroyDebugReportCallbackEXT = (PFN_vkDestroyDebugReportCallbackEXT)vkGetInstanceProcAddr(g_Instance, "vkDestroyDebugReportCallbackEXT"); - vkDestroyDebugReportCallbackEXT(g_Instance, g_DebugReport, g_Allocator); -#endif // IMGUI_VULKAN_DEBUG_REPORT - - vkDestroyDevice(g_Device, g_Allocator); - vkDestroyInstance(g_Instance, g_Allocator); -} - -static void CleanupVulkanWindow() -{ - ImGui_ImplVulkanH_DestroyWindow(g_Instance, g_Device, &g_MainWindowData, g_Allocator); -} - -static void FrameRender(ImGui_ImplVulkanH_Window* wd, ImDrawData* draw_data) -{ - VkResult err; - - VkSemaphore image_acquired_semaphore = wd->FrameSemaphores[wd->SemaphoreIndex].ImageAcquiredSemaphore; - VkSemaphore render_complete_semaphore = wd->FrameSemaphores[wd->SemaphoreIndex].RenderCompleteSemaphore; - err = vkAcquireNextImageKHR(g_Device, wd->Swapchain, UINT64_MAX, image_acquired_semaphore, VK_NULL_HANDLE, &wd->FrameIndex); - if (err == VK_ERROR_OUT_OF_DATE_KHR || err == VK_SUBOPTIMAL_KHR) - { - g_SwapChainRebuild = true; - return; - } - check_vk_result(err); - - ImGui_ImplVulkanH_Frame* fd = &wd->Frames[wd->FrameIndex]; - { - err = vkWaitForFences(g_Device, 1, &fd->Fence, VK_TRUE, UINT64_MAX); // wait indefinitely instead of periodically checking - check_vk_result(err); - - err = vkResetFences(g_Device, 1, &fd->Fence); - check_vk_result(err); - } - { - err = vkResetCommandPool(g_Device, fd->CommandPool, 0); - check_vk_result(err); - VkCommandBufferBeginInfo info = {}; - info.sType = VK_STRUCTURE_TYPE_COMMAND_BUFFER_BEGIN_INFO; - info.flags |= VK_COMMAND_BUFFER_USAGE_ONE_TIME_SUBMIT_BIT; - err = vkBeginCommandBuffer(fd->CommandBuffer, &info); - check_vk_result(err); - } - { - VkRenderPassBeginInfo info = {}; - info.sType = VK_STRUCTURE_TYPE_RENDER_PASS_BEGIN_INFO; - info.renderPass = wd->RenderPass; - info.framebuffer = fd->Framebuffer; - info.renderArea.extent.width = wd->Width; - info.renderArea.extent.height = wd->Height; - info.clearValueCount = 1; - info.pClearValues = &wd->ClearValue; - vkCmdBeginRenderPass(fd->CommandBuffer, &info, VK_SUBPASS_CONTENTS_INLINE); - } - - // Record dear imgui primitives into command buffer - ImGui_ImplVulkan_RenderDrawData(draw_data, fd->CommandBuffer); - - // Submit command buffer - vkCmdEndRenderPass(fd->CommandBuffer); - { - VkPipelineStageFlags wait_stage = VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT; - VkSubmitInfo info = {}; - info.sType = VK_STRUCTURE_TYPE_SUBMIT_INFO; - info.waitSemaphoreCount = 1; - info.pWaitSemaphores = &image_acquired_semaphore; - info.pWaitDstStageMask = &wait_stage; - info.commandBufferCount = 1; - info.pCommandBuffers = &fd->CommandBuffer; - info.signalSemaphoreCount = 1; - info.pSignalSemaphores = &render_complete_semaphore; - - err = vkEndCommandBuffer(fd->CommandBuffer); - check_vk_result(err); - err = vkQueueSubmit(g_Queue, 1, &info, fd->Fence); - check_vk_result(err); - } -} - -static void FramePresent(ImGui_ImplVulkanH_Window* wd) -{ - if (g_SwapChainRebuild) - return; - VkSemaphore render_complete_semaphore = wd->FrameSemaphores[wd->SemaphoreIndex].RenderCompleteSemaphore; - VkPresentInfoKHR info = {}; - info.sType = VK_STRUCTURE_TYPE_PRESENT_INFO_KHR; - info.waitSemaphoreCount = 1; - info.pWaitSemaphores = &render_complete_semaphore; - info.swapchainCount = 1; - info.pSwapchains = &wd->Swapchain; - info.pImageIndices = &wd->FrameIndex; - VkResult err = vkQueuePresentKHR(g_Queue, &info); - if (err == VK_ERROR_OUT_OF_DATE_KHR || err == VK_SUBOPTIMAL_KHR) - { - g_SwapChainRebuild = true; - return; - } - check_vk_result(err); - wd->SemaphoreIndex = (wd->SemaphoreIndex + 1) % wd->ImageCount; // Now we can use the next set of semaphores -} - -// Main code -int main(int, char**) -{ - glfwSetErrorCallback(glfw_error_callback); - if (!glfwInit()) - return 1; - - // Create window with Vulkan context - glfwWindowHint(GLFW_CLIENT_API, GLFW_NO_API); - GLFWwindow* window = glfwCreateWindow(1280, 720, "Dear ImGui GLFW+Vulkan example", nullptr, nullptr); - if (!glfwVulkanSupported()) - { - printf("GLFW: Vulkan Not Supported\n"); - return 1; - } - - ImVector extensions; - uint32_t extensions_count = 0; - const char** glfw_extensions = glfwGetRequiredInstanceExtensions(&extensions_count); - for (uint32_t i = 0; i < extensions_count; i++) - extensions.push_back(glfw_extensions[i]); - SetupVulkan(extensions); - - // Create Window Surface - VkSurfaceKHR surface; - VkResult err = glfwCreateWindowSurface(g_Instance, window, g_Allocator, &surface); - check_vk_result(err); - - // Create Framebuffers - int w, h; - glfwGetFramebufferSize(window, &w, &h); - ImGui_ImplVulkanH_Window* wd = &g_MainWindowData; - SetupVulkanWindow(wd, surface, w, h); - - // Setup Dear ImGui context - IMGUI_CHECKVERSION(); - ImGui::CreateContext(); - ImGuiIO& io = ImGui::GetIO(); (void)io; - io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard; // Enable Keyboard Controls - io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad; // Enable Gamepad Controls - io.ConfigFlags |= ImGuiConfigFlags_DockingEnable; // Enable Docking - io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable; // Enable Multi-Viewport / Platform Windows - //io.ConfigViewportsNoAutoMerge = true; - //io.ConfigViewportsNoTaskBarIcon = true; - - // Setup Dear ImGui style - ImGui::StyleColorsDark(); - //ImGui::StyleColorsLight(); - - // When viewports are enabled we tweak WindowRounding/WindowBg so platform windows can look identical to regular ones. - ImGuiStyle& style = ImGui::GetStyle(); - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - style.WindowRounding = 0.0f; - style.Colors[ImGuiCol_WindowBg].w = 1.0f; - } - - // Setup Platform/Renderer backends - ImGui_ImplGlfw_InitForVulkan(window, true); - ImGui_ImplVulkan_InitInfo init_info = {}; - init_info.Instance = g_Instance; - init_info.PhysicalDevice = g_PhysicalDevice; - init_info.Device = g_Device; - init_info.QueueFamily = g_QueueFamily; - init_info.Queue = g_Queue; - init_info.PipelineCache = g_PipelineCache; - init_info.DescriptorPool = g_DescriptorPool; - init_info.Subpass = 0; - init_info.MinImageCount = g_MinImageCount; - init_info.ImageCount = wd->ImageCount; - init_info.MSAASamples = VK_SAMPLE_COUNT_1_BIT; - init_info.Allocator = g_Allocator; - init_info.CheckVkResultFn = check_vk_result; - ImGui_ImplVulkan_Init(&init_info, wd->RenderPass); - - // Load Fonts - // - If no fonts are loaded, dear imgui will use the default font. You can also load multiple fonts and use ImGui::PushFont()/PopFont() to select them. - // - AddFontFromFileTTF() will return the ImFont* so you can store it if you need to select the font among multiple. - // - If the file cannot be loaded, the function will return a nullptr. Please handle those errors in your application (e.g. use an assertion, or display an error and quit). - // - The fonts will be rasterized at a given size (w/ oversampling) and stored into a texture when calling ImFontAtlas::Build()/GetTexDataAsXXXX(), which ImGui_ImplXXXX_NewFrame below will call. - // - Use '#define IMGUI_ENABLE_FREETYPE' in your imconfig file to use Freetype for higher quality font rendering. - // - Read 'docs/FONTS.md' for more instructions and details. - // - Remember that in C/C++ if you want to include a backslash \ in a string literal you need to write a double backslash \\ ! - //io.Fonts->AddFontDefault(); - //io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\segoeui.ttf", 18.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/DroidSans.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Roboto-Medium.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Cousine-Regular.ttf", 15.0f); - //ImFont* font = io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\ArialUni.ttf", 18.0f, nullptr, io.Fonts->GetGlyphRangesJapanese()); - //IM_ASSERT(font != nullptr); - - // Upload Fonts - { - // Use any command queue - VkCommandPool command_pool = wd->Frames[wd->FrameIndex].CommandPool; - VkCommandBuffer command_buffer = wd->Frames[wd->FrameIndex].CommandBuffer; - - err = vkResetCommandPool(g_Device, command_pool, 0); - check_vk_result(err); - VkCommandBufferBeginInfo begin_info = {}; - begin_info.sType = VK_STRUCTURE_TYPE_COMMAND_BUFFER_BEGIN_INFO; - begin_info.flags |= VK_COMMAND_BUFFER_USAGE_ONE_TIME_SUBMIT_BIT; - err = vkBeginCommandBuffer(command_buffer, &begin_info); - check_vk_result(err); - - ImGui_ImplVulkan_CreateFontsTexture(command_buffer); - - VkSubmitInfo end_info = {}; - end_info.sType = VK_STRUCTURE_TYPE_SUBMIT_INFO; - end_info.commandBufferCount = 1; - end_info.pCommandBuffers = &command_buffer; - err = vkEndCommandBuffer(command_buffer); - check_vk_result(err); - err = vkQueueSubmit(g_Queue, 1, &end_info, VK_NULL_HANDLE); - check_vk_result(err); - - err = vkDeviceWaitIdle(g_Device); - check_vk_result(err); - ImGui_ImplVulkan_DestroyFontUploadObjects(); - } - - // Our state - bool show_demo_window = true; - bool show_another_window = false; - ImVec4 clear_color = ImVec4(0.45f, 0.55f, 0.60f, 1.00f); - - // Main loop - while (!glfwWindowShouldClose(window)) - { - // Poll and handle events (inputs, window resize, etc.) - // You can read the io.WantCaptureMouse, io.WantCaptureKeyboard flags to tell if dear imgui wants to use your inputs. - // - When io.WantCaptureMouse is true, do not dispatch mouse input data to your main application, or clear/overwrite your copy of the mouse data. - // - When io.WantCaptureKeyboard is true, do not dispatch keyboard input data to your main application, or clear/overwrite your copy of the keyboard data. - // Generally you may always pass all inputs to dear imgui, and hide them from your application based on those two flags. - glfwPollEvents(); - - // Resize swap chain? - if (g_SwapChainRebuild) - { - int width, height; - glfwGetFramebufferSize(window, &width, &height); - if (width > 0 && height > 0) - { - ImGui_ImplVulkan_SetMinImageCount(g_MinImageCount); - ImGui_ImplVulkanH_CreateOrResizeWindow(g_Instance, g_PhysicalDevice, g_Device, &g_MainWindowData, g_QueueFamily, g_Allocator, width, height, g_MinImageCount); - g_MainWindowData.FrameIndex = 0; - g_SwapChainRebuild = false; - } - } - - // Start the Dear ImGui frame - ImGui_ImplVulkan_NewFrame(); - ImGui_ImplGlfw_NewFrame(); - ImGui::NewFrame(); - - // 1. Show the big demo window (Most of the sample code is in ImGui::ShowDemoWindow()! You can browse its code to learn more about Dear ImGui!). - if (show_demo_window) - ImGui::ShowDemoWindow(&show_demo_window); - - // 2. Show a simple window that we create ourselves. We use a Begin/End pair to create a named window. - { - static float f = 0.0f; - static int counter = 0; - - ImGui::Begin("Hello, world!"); // Create a window called "Hello, world!" and append into it. - - ImGui::Text("This is some useful text."); // Display some text (you can use a format strings too) - ImGui::Checkbox("Demo Window", &show_demo_window); // Edit bools storing our window open/close state - ImGui::Checkbox("Another Window", &show_another_window); - - ImGui::SliderFloat("float", &f, 0.0f, 1.0f); // Edit 1 float using a slider from 0.0f to 1.0f - ImGui::ColorEdit3("clear color", (float*)&clear_color); // Edit 3 floats representing a color - - if (ImGui::Button("Button")) // Buttons return true when clicked (most widgets return true when edited/activated) - counter++; - ImGui::SameLine(); - ImGui::Text("counter = %d", counter); - - ImGui::Text("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / io.Framerate, io.Framerate); - ImGui::End(); - } - - // 3. Show another simple window. - if (show_another_window) - { - ImGui::Begin("Another Window", &show_another_window); // Pass a pointer to our bool variable (the window will have a closing button that will clear the bool when clicked) - ImGui::Text("Hello from another window!"); - if (ImGui::Button("Close Me")) - show_another_window = false; - ImGui::End(); - } - - // Rendering - ImGui::Render(); - ImDrawData* main_draw_data = ImGui::GetDrawData(); - const bool main_is_minimized = (main_draw_data->DisplaySize.x <= 0.0f || main_draw_data->DisplaySize.y <= 0.0f); - wd->ClearValue.color.float32[0] = clear_color.x * clear_color.w; - wd->ClearValue.color.float32[1] = clear_color.y * clear_color.w; - wd->ClearValue.color.float32[2] = clear_color.z * clear_color.w; - wd->ClearValue.color.float32[3] = clear_color.w; - if (!main_is_minimized) - FrameRender(wd, main_draw_data); - - // Update and Render additional Platform Windows - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - ImGui::UpdatePlatformWindows(); - ImGui::RenderPlatformWindowsDefault(); - } - - // Present Main Platform Window - if (!main_is_minimized) - FramePresent(wd); - } - - // Cleanup - err = vkDeviceWaitIdle(g_Device); - check_vk_result(err); - ImGui_ImplVulkan_Shutdown(); - ImGui_ImplGlfw_Shutdown(); - ImGui::DestroyContext(); - - CleanupVulkanWindow(); - CleanupVulkan(); - - glfwDestroyWindow(window); - glfwTerminate(); - - return 0; -} diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_glut_opengl2/Makefile b/app/jni/src/libultraship/extern/ImGui/examples/example_glut_opengl2/Makefile deleted file mode 100644 index 7af289d..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_glut_opengl2/Makefile +++ /dev/null @@ -1,75 +0,0 @@ -# -# Cross Platform Makefile -# Compatible with MSYS2/MINGW, Ubuntu 14.04.1 and Mac OS X -# -# Linux: -# apt-get install freeglut3-dev -# - -#CXX = g++ -#CXX = clang++ - -EXE = example_glut_opengl2 -IMGUI_DIR = ../.. -SOURCES = main.cpp -SOURCES += $(IMGUI_DIR)/imgui.cpp $(IMGUI_DIR)/imgui_demo.cpp $(IMGUI_DIR)/imgui_draw.cpp $(IMGUI_DIR)/imgui_tables.cpp $(IMGUI_DIR)/imgui_widgets.cpp -SOURCES += $(IMGUI_DIR)/backends/imgui_impl_glut.cpp $(IMGUI_DIR)/backends/imgui_impl_opengl2.cpp -OBJS = $(addsuffix .o, $(basename $(notdir $(SOURCES)))) -UNAME_S := $(shell uname -s) - -CXXFLAGS = -std=c++11 -I$(IMGUI_DIR) -I$(IMGUI_DIR)/backends -CXXFLAGS += -g -Wall -Wformat -LIBS = - -##--------------------------------------------------------------------- -## BUILD FLAGS PER PLATFORM -##--------------------------------------------------------------------- - -ifeq ($(UNAME_S), Linux) #LINUX - ECHO_MESSAGE = "Linux" - LIBS += -lGL -lglut - CFLAGS = $(CXXFLAGS) -endif - -ifeq ($(UNAME_S), Darwin) #APPLE - ECHO_MESSAGE = "Mac OS X" - LIBS += -framework OpenGL -framework GLUT - LIBS += -L/usr/local/lib -L/opt/local/lib - - CXXFLAGS += -I/usr/local/include -I/opt/local/include - CFLAGS = $(CXXFLAGS) -endif - -ifeq ($(OS), Windows_NT) - ECHO_MESSAGE = "MinGW" - LIBS += -lgdi32 -lopengl32 -limm32 -ifeq ($(shell pkg-config freeglut --exists 2> /dev/null && echo yes || echo no),yes) - CXXFLAGS += $(shell pkg-config freeglut --cflags) - LIBS += $(shell pkg-config freeglut --libs) -else - LIBS += -lglut -endif - CFLAGS = $(CXXFLAGS) -endif - -##--------------------------------------------------------------------- -## BUILD RULES -##--------------------------------------------------------------------- - -%.o:%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/backends/%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -all: $(EXE) - @echo Build complete for $(ECHO_MESSAGE) - -$(EXE): $(OBJS) - $(CXX) -o $@ $^ $(CXXFLAGS) $(LIBS) - -clean: - rm -f $(EXE) $(OBJS) diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_glut_opengl2/example_glut_opengl2.vcxproj b/app/jni/src/libultraship/extern/ImGui/examples/example_glut_opengl2/example_glut_opengl2.vcxproj deleted file mode 100644 index c56452b..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_glut_opengl2/example_glut_opengl2.vcxproj +++ /dev/null @@ -1,186 +0,0 @@ - - - - - Debug - Win32 - - - Debug - x64 - - - Release - Win32 - - - Release - x64 - - - - {F90D0333-5FB1-440D-918D-DD39A1B5187E} - example_glut_opengl2 - 8.1 - - - - Application - true - MultiByte - v140 - - - Application - true - MultiByte - v140 - - - Application - false - true - MultiByte - v140 - - - Application - false - true - MultiByte - v140 - - - - - - - - - - - - - - - - - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - - Level4 - Disabled - $(GLUT_INCLUDE_DIR);..\..;..\..\backends;%(AdditionalIncludeDirectories) - /utf-8 %(AdditionalOptions) - - - true - $(GLUT_ROOT_PATH)/lib;%(AdditionalLibraryDirectories) - opengl32.lib;freeglut.lib;%(AdditionalDependencies) - Console - msvcrt.lib - - - - - Level4 - Disabled - $(GLUT_INCLUDE_DIR);..\..;..\..\backends;%(AdditionalIncludeDirectories) - /utf-8 %(AdditionalOptions) - - - true - $(GLUT_ROOT_PATH)/lib/x64;%(AdditionalLibraryDirectories) - opengl32.lib;freeglut.lib;%(AdditionalDependencies) - Console - msvcrt.lib - - - - - Level4 - MaxSpeed - true - true - $(GLUT_INCLUDE_DIR);..\..;..\..\backends;%(AdditionalIncludeDirectories) - false - /utf-8 %(AdditionalOptions) - - - true - true - true - $(GLUT_ROOT_PATH)/lib;%(AdditionalLibraryDirectories) - opengl32.lib;freeglut.lib;%(AdditionalDependencies) - Console - - - - - - - Level4 - MaxSpeed - true - true - $(GLUT_INCLUDE_DIR);..\..;..\..\backends;%(AdditionalIncludeDirectories) - false - /utf-8 %(AdditionalOptions) - - - true - true - true - $(GLUT_ROOT_PATH)/lib/x64;%(AdditionalLibraryDirectories) - opengl32.lib;freeglut.lib;%(AdditionalDependencies) - Console - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_glut_opengl2/example_glut_opengl2.vcxproj.filters b/app/jni/src/libultraship/extern/ImGui/examples/example_glut_opengl2/example_glut_opengl2.vcxproj.filters deleted file mode 100644 index 0ac4a0b..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_glut_opengl2/example_glut_opengl2.vcxproj.filters +++ /dev/null @@ -1,64 +0,0 @@ - - - - - {c336cfe3-f0c4-464c-9ef0-a9e17a7ff222} - - - {4FC737F1-C7A5-4376-A066-2A32D752A2FF} - cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx - - - - - sources - - - imgui - - - imgui - - - imgui - - - imgui - - - imgui - - - sources - - - sources - - - - - imgui - - - imgui - - - imgui - - - sources - - - sources - - - - - - imgui - - - imgui - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_glut_opengl2/main.cpp b/app/jni/src/libultraship/extern/ImGui/examples/example_glut_opengl2/main.cpp deleted file mode 100644 index 4edae6f..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_glut_opengl2/main.cpp +++ /dev/null @@ -1,164 +0,0 @@ -// Dear ImGui: standalone example application for GLUT/FreeGLUT + OpenGL2, using legacy fixed pipeline - -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -// !!! GLUT/FreeGLUT IS OBSOLETE PREHISTORIC SOFTWARE. Using GLUT is not recommended unless you really miss the 90's. !!! -// !!! If someone or something is teaching you GLUT today, you are being abused. Please show some resistance. !!! -// !!! Nowadays, prefer using GLFW or SDL instead! - -// On Windows, you can install Freeglut using vcpkg: -// git clone https://github.com/Microsoft/vcpkg -// cd vcpkg -// bootstrap - vcpkg.bat -// vcpkg install freeglut --triplet=x86-windows ; for win32 -// vcpkg install freeglut --triplet=x64-windows ; for win64 -// vcpkg integrate install ; register include and libs in Visual Studio - -#include "imgui.h" -#include "imgui_impl_glut.h" -#include "imgui_impl_opengl2.h" -#define GL_SILENCE_DEPRECATION -#ifdef __APPLE__ -#include -#else -#include -#endif - -#ifdef _MSC_VER -#pragma warning (disable: 4505) // unreferenced local function has been removed -#endif - -// Forward declarations of helper functions -void MainLoopStep(); - -// Our state -static bool show_demo_window = true; -static bool show_another_window = false; -static ImVec4 clear_color = ImVec4(0.45f, 0.55f, 0.60f, 1.00f); - -int main(int argc, char** argv) -{ - // Create GLUT window - glutInit(&argc, argv); -#ifdef __FREEGLUT_EXT_H__ - glutSetOption(GLUT_ACTION_ON_WINDOW_CLOSE, GLUT_ACTION_GLUTMAINLOOP_RETURNS); -#endif - glutInitDisplayMode(GLUT_RGBA | GLUT_DOUBLE | GLUT_MULTISAMPLE); - glutInitWindowSize(1280, 720); - glutCreateWindow("Dear ImGui GLUT+OpenGL2 Example"); - - // Setup GLUT display function - // We will also call ImGui_ImplGLUT_InstallFuncs() to get all the other functions installed for us, - // otherwise it is possible to install our own functions and call the imgui_impl_glut.h functions ourselves. - glutDisplayFunc(MainLoopStep); - - // Setup Dear ImGui context - IMGUI_CHECKVERSION(); - ImGui::CreateContext(); - ImGuiIO& io = ImGui::GetIO(); (void)io; - io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard; // Enable Keyboard Controls - io.ConfigFlags |= ImGuiConfigFlags_DockingEnable; // Enable Docking - - // Setup Dear ImGui style - ImGui::StyleColorsDark(); - //ImGui::StyleColorsLight(); - - // Setup Platform/Renderer backends - // FIXME: Consider reworking this example to install our own GLUT funcs + forward calls ImGui_ImplGLUT_XXX ones, instead of using ImGui_ImplGLUT_InstallFuncs(). - ImGui_ImplGLUT_Init(); - ImGui_ImplOpenGL2_Init(); - - // Install GLUT handlers (glutReshapeFunc(), glutMotionFunc(), glutPassiveMotionFunc(), glutMouseFunc(), glutKeyboardFunc() etc.) - // You can read the io.WantCaptureMouse, io.WantCaptureKeyboard flags to tell if dear imgui wants to use your inputs. - // - When io.WantCaptureMouse is true, do not dispatch mouse input data to your main application, or clear/overwrite your copy of the mouse data. - // - When io.WantCaptureKeyboard is true, do not dispatch keyboard input data to your main application, or clear/overwrite your copy of the keyboard data. - // Generally you may always pass all inputs to dear imgui, and hide them from your application based on those two flags. - ImGui_ImplGLUT_InstallFuncs(); - - // Load Fonts - // - If no fonts are loaded, dear imgui will use the default font. You can also load multiple fonts and use ImGui::PushFont()/PopFont() to select them. - // - AddFontFromFileTTF() will return the ImFont* so you can store it if you need to select the font among multiple. - // - If the file cannot be loaded, the function will return a nullptr. Please handle those errors in your application (e.g. use an assertion, or display an error and quit). - // - The fonts will be rasterized at a given size (w/ oversampling) and stored into a texture when calling ImFontAtlas::Build()/GetTexDataAsXXXX(), which ImGui_ImplXXXX_NewFrame below will call. - // - Use '#define IMGUI_ENABLE_FREETYPE' in your imconfig file to use Freetype for higher quality font rendering. - // - Read 'docs/FONTS.md' for more instructions and details. - // - Remember that in C/C++ if you want to include a backslash \ in a string literal you need to write a double backslash \\ ! - //io.Fonts->AddFontDefault(); - //io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\segoeui.ttf", 18.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/DroidSans.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Roboto-Medium.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Cousine-Regular.ttf", 15.0f); - //ImFont* font = io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\ArialUni.ttf", 18.0f, nullptr, io.Fonts->GetGlyphRangesJapanese()); - //IM_ASSERT(font != nullptr); - - // Main loop - glutMainLoop(); - - // Cleanup - ImGui_ImplOpenGL2_Shutdown(); - ImGui_ImplGLUT_Shutdown(); - ImGui::DestroyContext(); - - return 0; -} - -void MainLoopStep() -{ - // Start the Dear ImGui frame - ImGui_ImplOpenGL2_NewFrame(); - ImGui_ImplGLUT_NewFrame(); - ImGui::NewFrame(); - ImGuiIO& io = ImGui::GetIO(); - - // 1. Show the big demo window (Most of the sample code is in ImGui::ShowDemoWindow()! You can browse its code to learn more about Dear ImGui!). - if (show_demo_window) - ImGui::ShowDemoWindow(&show_demo_window); - - // 2. Show a simple window that we create ourselves. We use a Begin/End pair to create a named window. - { - static float f = 0.0f; - static int counter = 0; - - ImGui::Begin("Hello, world!"); // Create a window called "Hello, world!" and append into it. - - ImGui::Text("This is some useful text."); // Display some text (you can use a format strings too) - ImGui::Checkbox("Demo Window", &show_demo_window); // Edit bools storing our window open/close state - ImGui::Checkbox("Another Window", &show_another_window); - - ImGui::SliderFloat("float", &f, 0.0f, 1.0f); // Edit 1 float using a slider from 0.0f to 1.0f - ImGui::ColorEdit3("clear color", (float*)&clear_color); // Edit 3 floats representing a color - - if (ImGui::Button("Button")) // Buttons return true when clicked (most widgets return true when edited/activated) - counter++; - ImGui::SameLine(); - ImGui::Text("counter = %d", counter); - - ImGui::Text("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / io.Framerate, io.Framerate); - ImGui::End(); - } - - // 3. Show another simple window. - if (show_another_window) - { - ImGui::Begin("Another Window", &show_another_window); // Pass a pointer to our bool variable (the window will have a closing button that will clear the bool when clicked) - ImGui::Text("Hello from another window!"); - if (ImGui::Button("Close Me")) - show_another_window = false; - ImGui::End(); - } - - // Rendering - ImGui::Render(); - glViewport(0, 0, (GLsizei)io.DisplaySize.x, (GLsizei)io.DisplaySize.y); - glClearColor(clear_color.x * clear_color.w, clear_color.y * clear_color.w, clear_color.z * clear_color.w, clear_color.w); - glClear(GL_COLOR_BUFFER_BIT); - //glUseProgram(0); // You may want this if using this code in an OpenGL 3+ context where shaders may be bound, but prefer using the GL3+ code. - ImGui_ImplOpenGL2_RenderDrawData(ImGui::GetDrawData()); - - glutSwapBuffers(); - glutPostRedisplay(); -} diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_null/Makefile b/app/jni/src/libultraship/extern/ImGui/examples/example_null/Makefile deleted file mode 100644 index 9ceb353..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_null/Makefile +++ /dev/null @@ -1,92 +0,0 @@ -# -# Cross Platform Makefile -# Compatible with MSYS2/MINGW, Ubuntu 14.04.1 and Mac OS X -# -# Important: This is a "null backend" application, with no visible output or interaction! -# This is used for testing purpose and continuous integration, and has little use for end-user. -# - -# Options -WITH_EXTRA_WARNINGS ?= 0 -WITH_FREETYPE ?= 0 - -EXE = example_null -IMGUI_DIR = ../.. -SOURCES = main.cpp -SOURCES += $(IMGUI_DIR)/imgui.cpp $(IMGUI_DIR)/imgui_demo.cpp $(IMGUI_DIR)/imgui_draw.cpp $(IMGUI_DIR)/imgui_tables.cpp $(IMGUI_DIR)/imgui_widgets.cpp -OBJS = $(addsuffix .o, $(basename $(notdir $(SOURCES)))) -UNAME_S := $(shell uname -s) - -CXXFLAGS += -std=c++11 -I$(IMGUI_DIR) -CXXFLAGS += -g -Wall -Wformat -LIBS = - -# We use the WITH_EXTRA_WARNINGS flag on our CI setup to eagerly catch zealous warnings -ifeq ($(WITH_EXTRA_WARNINGS), 1) - CXXFLAGS += -Wno-zero-as-null-pointer-constant -Wno-double-promotion -Wno-variadic-macros -endif - -# We use the WITH_FREETYPE flag on our CI setup to test compiling misc/freetype/imgui_freetype.cpp -# (only supported on Linux, and note that the imgui_freetype code currently won't be executed) -ifeq ($(WITH_FREETYPE), 1) - SOURCES += $(IMGUI_DIR)/misc/freetype/imgui_freetype.cpp - CXXFLAGS += $(shell pkg-config --cflags freetype2) - LIBS += $(shell pkg-config --libs freetype2) -endif - -##--------------------------------------------------------------------- -## BUILD FLAGS PER PLATFORM -##--------------------------------------------------------------------- - -ifeq ($(UNAME_S), Linux) #LINUX - ECHO_MESSAGE = "Linux" - ifeq ($(WITH_EXTRA_WARNINGS), 1) - CXXFLAGS += -Wextra -Wpedantic - ifeq ($(shell $(CXX) -v 2>&1 | grep -c "clang version"), 1) - CXXFLAGS += -Wshadow -Wsign-conversion - endif - endif - CFLAGS = $(CXXFLAGS) -endif - -ifeq ($(UNAME_S), Darwin) #APPLE - ECHO_MESSAGE = "Mac OS X" - ifeq ($(WITH_EXTRA_WARNINGS), 1) - CXXFLAGS += -Weverything -Wno-reserved-id-macro -Wno-c++98-compat-pedantic -Wno-padded -Wno-poison-system-directories - endif - CFLAGS = $(CXXFLAGS) -endif - -ifeq ($(OS), Windows_NT) - ECHO_MESSAGE = "MinGW" - ifeq ($(WITH_EXTRA_WARNINGS), 1) - CXXFLAGS += -Wextra -Wpedantic - endif - LIBS += -limm32 - CFLAGS = $(CXXFLAGS) -endif - -##--------------------------------------------------------------------- -## BUILD RULES -##--------------------------------------------------------------------- - -%.o:%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/backends/%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/misc/freetype/%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -all: $(EXE) - @echo Build complete for $(ECHO_MESSAGE) - -$(EXE): $(OBJS) - $(CXX) -o $@ $^ $(CXXFLAGS) $(LIBS) - -clean: - rm -f $(EXE) $(OBJS) diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_null/build_win32.bat b/app/jni/src/libultraship/extern/ImGui/examples/example_null/build_win32.bat deleted file mode 100644 index be81d80..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_null/build_win32.bat +++ /dev/null @@ -1,3 +0,0 @@ -@REM Build for Visual Studio compiler. Run your copy of vcvars32.bat or vcvarsall.bat to setup command-line compiler. -mkdir Debug -cl /nologo /Zi /MD /utf-8 /I ..\.. %* *.cpp ..\..\*.cpp /FeDebug/example_null.exe /FoDebug/ /link gdi32.lib shell32.lib imm32.lib diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_null/main.cpp b/app/jni/src/libultraship/extern/ImGui/examples/example_null/main.cpp deleted file mode 100644 index f7153cc..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_null/main.cpp +++ /dev/null @@ -1,37 +0,0 @@ -// dear imgui: "null" example application -// (compile and link imgui, create context, run headless with NO INPUTS, NO GRAPHICS OUTPUT) -// This is useful to test building, but you cannot interact with anything here! -#include "imgui.h" -#include - -int main(int, char**) -{ - IMGUI_CHECKVERSION(); - ImGui::CreateContext(); - ImGuiIO& io = ImGui::GetIO(); - - // Build atlas - unsigned char* tex_pixels = nullptr; - int tex_w, tex_h; - io.Fonts->GetTexDataAsRGBA32(&tex_pixels, &tex_w, &tex_h); - - for (int n = 0; n < 20; n++) - { - printf("NewFrame() %d\n", n); - io.DisplaySize = ImVec2(1920, 1080); - io.DeltaTime = 1.0f / 60.0f; - ImGui::NewFrame(); - - static float f = 0.0f; - ImGui::Text("Hello, world!"); - ImGui::SliderFloat("float", &f, 0.0f, 1.0f); - ImGui::Text("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / io.Framerate, io.Framerate); - ImGui::ShowDemoWindow(nullptr); - - ImGui::Render(); - } - - printf("DestroyContext()\n"); - ImGui::DestroyContext(); - return 0; -} diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_directx11/build_win32.bat b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_directx11/build_win32.bat deleted file mode 100644 index f0b485c..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_directx11/build_win32.bat +++ /dev/null @@ -1,8 +0,0 @@ -@REM Build for Visual Studio compiler. Run your copy of vcvars32.bat or vcvarsall.bat to setup command-line compiler. -@set OUT_DIR=Debug -@set OUT_EXE=example_sdl2_directx11 -@set INCLUDES=/I..\.. /I..\..\backends /I%SDL2_DIR%\include /I "%WindowsSdkDir%Include\um" /I "%WindowsSdkDir%Include\shared" /I "%DXSDK_DIR%Include" -@set SOURCES=main.cpp ..\..\backends\imgui_impl_sdl2.cpp ..\..\backends\imgui_impl_dx11.cpp ..\..\imgui*.cpp -@set LIBS=/LIBPATH:%SDL2_DIR%\lib\x86 SDL2.lib SDL2main.lib /LIBPATH:"%DXSDK_DIR%/Lib/x86" d3d11.lib d3dcompiler.lib shell32.lib -mkdir %OUT_DIR% -cl /nologo /Zi /MD /utf-8 %INCLUDES% %SOURCES% /Fe%OUT_DIR%/%OUT_EXE%.exe /Fo%OUT_DIR%/ /link %LIBS% /subsystem:console diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_directx11/example_sdl2_directx11.vcxproj b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_directx11/example_sdl2_directx11.vcxproj deleted file mode 100644 index c23800c..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_directx11/example_sdl2_directx11.vcxproj +++ /dev/null @@ -1,187 +0,0 @@ - - - - - Debug - Win32 - - - Debug - x64 - - - Release - Win32 - - - Release - x64 - - - - {9E1987E3-1F19-45CA-B9C9-D31E791836D8} - example_sdl2_directx11 - 8.1 - example_sdl2_directx11 - - - - Application - true - MultiByte - v140 - - - Application - true - MultiByte - v140 - - - Application - false - true - MultiByte - v140 - - - Application - false - true - MultiByte - v140 - - - - - - - - - - - - - - - - - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - - Level4 - Disabled - ..\..;..\..\backends;%SDL2_DIR%\include;$(VcpkgCurrentInstalledDir)include\SDL2;%(AdditionalIncludeDirectories) - /utf-8 %(AdditionalOptions) - - - true - %SDL2_DIR%\lib\x86;$(DXSDK_DIR)/Lib/x86;%(AdditionalLibraryDirectories) - SDL2.lib;SDL2main.lib;d3d11.lib;d3dcompiler.lib;dxgi.lib;%(AdditionalDependencies) - Console - msvcrt.lib - - - - - Level4 - Disabled - ..\..;..\..\backends;%SDL2_DIR%\include;$(VcpkgCurrentInstalledDir)include\SDL2;%(AdditionalIncludeDirectories) - /utf-8 %(AdditionalOptions) - - - true - %SDL2_DIR%\lib\x64;$(DXSDK_DIR)/Lib/x64;%(AdditionalLibraryDirectories) - SDL2.lib;SDL2main.lib;d3d11.lib;d3dcompiler.lib;dxgi.lib;%(AdditionalDependencies) - Console - msvcrt.lib - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends;%SDL2_DIR%\include;$(VcpkgCurrentInstalledDir)include\SDL2;%(AdditionalIncludeDirectories) - false - /utf-8 %(AdditionalOptions) - - - true - true - true - %SDL2_DIR%\lib\x86;$(DXSDK_DIR)/Lib/x86;%(AdditionalLibraryDirectories) - SDL2.lib;SDL2main.lib;d3d11.lib;d3dcompiler.lib;dxgi.lib;%(AdditionalDependencies) - Console - - - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends;%SDL2_DIR%\include;$(VcpkgCurrentInstalledDir)include\SDL2;%(AdditionalIncludeDirectories) - false - /utf-8 %(AdditionalOptions) - - - true - true - true - %SDL2_DIR%\lib\x64;$(DXSDK_DIR)/Lib/x64;%(AdditionalLibraryDirectories) - SDL2.lib;SDL2main.lib;d3d11.lib;d3dcompiler.lib;dxgi.lib;%(AdditionalDependencies) - Console - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_directx11/example_sdl2_directx11.vcxproj.filters b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_directx11/example_sdl2_directx11.vcxproj.filters deleted file mode 100644 index 92d11f8..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_directx11/example_sdl2_directx11.vcxproj.filters +++ /dev/null @@ -1,63 +0,0 @@ - - - - - {0587d7a3-f2ce-4d56-b84f-a0005d3bfce6} - - - {08e36723-ce4f-4cff-9662-c40801cf1acf} - - - - - imgui - - - imgui - - - imgui - - - sources - - - sources - - - - - imgui - - - sources - - - imgui - - - imgui - - - imgui - - - imgui - - - sources - - - sources - - - - - - imgui - - - imgui - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_directx11/main.cpp b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_directx11/main.cpp deleted file mode 100644 index 69d4da1..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_directx11/main.cpp +++ /dev/null @@ -1,258 +0,0 @@ -// Dear ImGui: standalone example application for SDL2 + DirectX 11 -// (SDL is a cross-platform general purpose library for handling windows, inputs, OpenGL/Vulkan/Metal graphics context creation, etc.) - -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#include "imgui.h" -#include "imgui_impl_sdl2.h" -#include "imgui_impl_dx11.h" -#include -#include -#include -#include - -// Data -static ID3D11Device* g_pd3dDevice = nullptr; -static ID3D11DeviceContext* g_pd3dDeviceContext = nullptr; -static IDXGISwapChain* g_pSwapChain = nullptr; -static ID3D11RenderTargetView* g_mainRenderTargetView = nullptr; - -// Forward declarations of helper functions -bool CreateDeviceD3D(HWND hWnd); -void CleanupDeviceD3D(); -void CreateRenderTarget(); -void CleanupRenderTarget(); - -// Main code -int main(int, char**) -{ - // Setup SDL - // (Some versions of SDL before <2.0.10 appears to have performance/stalling issues on a minority of Windows systems, - // depending on whether SDL_INIT_GAMECONTROLLER is enabled or disabled.. updating to the latest version of SDL is recommended!) - if (SDL_Init(SDL_INIT_VIDEO | SDL_INIT_TIMER | SDL_INIT_GAMECONTROLLER) != 0) - { - printf("Error: %s\n", SDL_GetError()); - return -1; - } - - // From 2.0.18: Enable native IME. -#ifdef SDL_HINT_IME_SHOW_UI - SDL_SetHint(SDL_HINT_IME_SHOW_UI, "1"); -#endif - - // Setup window - SDL_WindowFlags window_flags = (SDL_WindowFlags)(SDL_WINDOW_RESIZABLE | SDL_WINDOW_ALLOW_HIGHDPI); - SDL_Window* window = SDL_CreateWindow("Dear ImGui SDL2+DirectX11 example", SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED, 1280, 720, window_flags); - SDL_SysWMinfo wmInfo; - SDL_VERSION(&wmInfo.version); - SDL_GetWindowWMInfo(window, &wmInfo); - HWND hwnd = (HWND)wmInfo.info.win.window; - - // Initialize Direct3D - if (!CreateDeviceD3D(hwnd)) - { - CleanupDeviceD3D(); - return 1; - } - - // Setup Dear ImGui context - IMGUI_CHECKVERSION(); - ImGui::CreateContext(); - ImGuiIO& io = ImGui::GetIO(); (void)io; - io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard; // Enable Keyboard Controls - io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad; // Enable Gamepad Controls - io.ConfigFlags |= ImGuiConfigFlags_DockingEnable; // Enable Docking - io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable; // Enable Multi-Viewport / Platform Windows - //io.ConfigViewportsNoAutoMerge = true; - //io.ConfigViewportsNoTaskBarIcon = true; - - // Setup Dear ImGui style - ImGui::StyleColorsDark(); - //ImGui::StyleColorsLight(); - - // When viewports are enabled we tweak WindowRounding/WindowBg so platform windows can look identical to regular ones. - ImGuiStyle& style = ImGui::GetStyle(); - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - style.WindowRounding = 0.0f; - style.Colors[ImGuiCol_WindowBg].w = 1.0f; - } - - // Setup Platform/Renderer backends - ImGui_ImplSDL2_InitForD3D(window); - ImGui_ImplDX11_Init(g_pd3dDevice, g_pd3dDeviceContext); - - // Load Fonts - // - If no fonts are loaded, dear imgui will use the default font. You can also load multiple fonts and use ImGui::PushFont()/PopFont() to select them. - // - AddFontFromFileTTF() will return the ImFont* so you can store it if you need to select the font among multiple. - // - If the file cannot be loaded, the function will return a nullptr. Please handle those errors in your application (e.g. use an assertion, or display an error and quit). - // - The fonts will be rasterized at a given size (w/ oversampling) and stored into a texture when calling ImFontAtlas::Build()/GetTexDataAsXXXX(), which ImGui_ImplXXXX_NewFrame below will call. - // - Use '#define IMGUI_ENABLE_FREETYPE' in your imconfig file to use Freetype for higher quality font rendering. - // - Read 'docs/FONTS.md' for more instructions and details. - // - Remember that in C/C++ if you want to include a backslash \ in a string literal you need to write a double backslash \\ ! - //io.Fonts->AddFontDefault(); - //io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\segoeui.ttf", 18.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/DroidSans.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Roboto-Medium.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Cousine-Regular.ttf", 15.0f); - //ImFont* font = io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\ArialUni.ttf", 18.0f, nullptr, io.Fonts->GetGlyphRangesJapanese()); - //IM_ASSERT(font != nullptr); - - // Our state - bool show_demo_window = true; - bool show_another_window = false; - ImVec4 clear_color = ImVec4(0.45f, 0.55f, 0.60f, 1.00f); - - // Main loop - bool done = false; - while (!done) - { - // Poll and handle events (inputs, window resize, etc.) - // You can read the io.WantCaptureMouse, io.WantCaptureKeyboard flags to tell if dear imgui wants to use your inputs. - // - When io.WantCaptureMouse is true, do not dispatch mouse input data to your main application, or clear/overwrite your copy of the mouse data. - // - When io.WantCaptureKeyboard is true, do not dispatch keyboard input data to your main application, or clear/overwrite your copy of the keyboard data. - // Generally you may always pass all inputs to dear imgui, and hide them from your application based on those two flags. - SDL_Event event; - while (SDL_PollEvent(&event)) - { - ImGui_ImplSDL2_ProcessEvent(&event); - if (event.type == SDL_QUIT) - done = true; - if (event.type == SDL_WINDOWEVENT && event.window.event == SDL_WINDOWEVENT_CLOSE && event.window.windowID == SDL_GetWindowID(window)) - done = true; - if (event.type == SDL_WINDOWEVENT && event.window.event == SDL_WINDOWEVENT_RESIZED && event.window.windowID == SDL_GetWindowID(window)) - { - // Release all outstanding references to the swap chain's buffers before resizing. - CleanupRenderTarget(); - g_pSwapChain->ResizeBuffers(0, 0, 0, DXGI_FORMAT_UNKNOWN, 0); - CreateRenderTarget(); - } - } - - // Start the Dear ImGui frame - ImGui_ImplDX11_NewFrame(); - ImGui_ImplSDL2_NewFrame(); - ImGui::NewFrame(); - - // 1. Show the big demo window (Most of the sample code is in ImGui::ShowDemoWindow()! You can browse its code to learn more about Dear ImGui!). - if (show_demo_window) - ImGui::ShowDemoWindow(&show_demo_window); - - // 2. Show a simple window that we create ourselves. We use a Begin/End pair to create a named window. - { - static float f = 0.0f; - static int counter = 0; - - ImGui::Begin("Hello, world!"); // Create a window called "Hello, world!" and append into it. - - ImGui::Text("This is some useful text."); // Display some text (you can use a format strings too) - ImGui::Checkbox("Demo Window", &show_demo_window); // Edit bools storing our window open/close state - ImGui::Checkbox("Another Window", &show_another_window); - - ImGui::SliderFloat("float", &f, 0.0f, 1.0f); // Edit 1 float using a slider from 0.0f to 1.0f - ImGui::ColorEdit3("clear color", (float*)&clear_color); // Edit 3 floats representing a color - - if (ImGui::Button("Button")) // Buttons return true when clicked (most widgets return true when edited/activated) - counter++; - ImGui::SameLine(); - ImGui::Text("counter = %d", counter); - - ImGui::Text("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / io.Framerate, io.Framerate); - ImGui::End(); - } - - // 3. Show another simple window. - if (show_another_window) - { - ImGui::Begin("Another Window", &show_another_window); // Pass a pointer to our bool variable (the window will have a closing button that will clear the bool when clicked) - ImGui::Text("Hello from another window!"); - if (ImGui::Button("Close Me")) - show_another_window = false; - ImGui::End(); - } - - // Rendering - ImGui::Render(); - const float clear_color_with_alpha[4] = { clear_color.x * clear_color.w, clear_color.y * clear_color.w, clear_color.z * clear_color.w, clear_color.w }; - g_pd3dDeviceContext->OMSetRenderTargets(1, &g_mainRenderTargetView, nullptr); - g_pd3dDeviceContext->ClearRenderTargetView(g_mainRenderTargetView, clear_color_with_alpha); - ImGui_ImplDX11_RenderDrawData(ImGui::GetDrawData()); - - // Update and Render additional Platform Windows - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - ImGui::UpdatePlatformWindows(); - ImGui::RenderPlatformWindowsDefault(); - } - - g_pSwapChain->Present(1, 0); // Present with vsync - //g_pSwapChain->Present(0, 0); // Present without vsync - } - - // Cleanup - ImGui_ImplDX11_Shutdown(); - ImGui_ImplSDL2_Shutdown(); - ImGui::DestroyContext(); - - CleanupDeviceD3D(); - SDL_DestroyWindow(window); - SDL_Quit(); - - return 0; -} - -// Helper functions to use DirectX11 -bool CreateDeviceD3D(HWND hWnd) -{ - // Setup swap chain - DXGI_SWAP_CHAIN_DESC sd; - ZeroMemory(&sd, sizeof(sd)); - sd.BufferCount = 2; - sd.BufferDesc.Width = 0; - sd.BufferDesc.Height = 0; - sd.BufferDesc.Format = DXGI_FORMAT_R8G8B8A8_UNORM; - sd.BufferDesc.RefreshRate.Numerator = 60; - sd.BufferDesc.RefreshRate.Denominator = 1; - sd.Flags = DXGI_SWAP_CHAIN_FLAG_ALLOW_MODE_SWITCH; - sd.BufferUsage = DXGI_USAGE_RENDER_TARGET_OUTPUT; - sd.OutputWindow = hWnd; - sd.SampleDesc.Count = 1; - sd.SampleDesc.Quality = 0; - sd.Windowed = TRUE; - sd.SwapEffect = DXGI_SWAP_EFFECT_DISCARD; - - UINT createDeviceFlags = 0; - //createDeviceFlags |= D3D11_CREATE_DEVICE_DEBUG; - D3D_FEATURE_LEVEL featureLevel; - const D3D_FEATURE_LEVEL featureLevelArray[2] = { D3D_FEATURE_LEVEL_11_0, D3D_FEATURE_LEVEL_10_0, }; - if (D3D11CreateDeviceAndSwapChain(nullptr, D3D_DRIVER_TYPE_HARDWARE, nullptr, createDeviceFlags, featureLevelArray, 2, D3D11_SDK_VERSION, &sd, &g_pSwapChain, &g_pd3dDevice, &featureLevel, &g_pd3dDeviceContext) != S_OK) - return false; - - CreateRenderTarget(); - return true; -} - -void CleanupDeviceD3D() -{ - CleanupRenderTarget(); - if (g_pSwapChain) { g_pSwapChain->Release(); g_pSwapChain = nullptr; } - if (g_pd3dDeviceContext) { g_pd3dDeviceContext->Release(); g_pd3dDeviceContext = nullptr; } - if (g_pd3dDevice) { g_pd3dDevice->Release(); g_pd3dDevice = nullptr; } -} - -void CreateRenderTarget() -{ - ID3D11Texture2D* pBackBuffer; - g_pSwapChain->GetBuffer(0, IID_PPV_ARGS(&pBackBuffer)); - g_pd3dDevice->CreateRenderTargetView(pBackBuffer, nullptr, &g_mainRenderTargetView); - pBackBuffer->Release(); -} - -void CleanupRenderTarget() -{ - if (g_mainRenderTargetView) { g_mainRenderTargetView->Release(); g_mainRenderTargetView = nullptr; } -} diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_metal/Makefile b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_metal/Makefile deleted file mode 100644 index 53c5f75..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_metal/Makefile +++ /dev/null @@ -1,47 +0,0 @@ -# -# You will need SDL2 (http://www.libsdl.org): -# brew install sdl2 -# - -#CXX = g++ -#CXX = clang++ - -EXE = example_sdl2_metal -IMGUI_DIR = ../.. -SOURCES = main.mm -SOURCES += $(IMGUI_DIR)/imgui.cpp $(IMGUI_DIR)/imgui_demo.cpp $(IMGUI_DIR)/imgui_draw.cpp $(IMGUI_DIR)/imgui_tables.cpp $(IMGUI_DIR)/imgui_widgets.cpp -SOURCES += $(IMGUI_DIR)/backends/imgui_impl_sdl2.cpp $(IMGUI_DIR)/backends/imgui_impl_metal.mm -OBJS = $(addsuffix .o, $(basename $(notdir $(SOURCES)))) - -LIBS = -framework Metal -framework MetalKit -framework Cocoa -framework IOKit -framework CoreVideo -framework QuartzCore -LIBS += `sdl2-config --libs` -LIBS += -L/usr/local/lib - -CXXFLAGS = -std=c++11 -I$(IMGUI_DIR) -I$(IMGUI_DIR)/backends -I/usr/local/include -CXXFLAGS += `sdl2-config --cflags` -CXXFLAGS += -Wall -Wformat -CFLAGS = $(CXXFLAGS) - -%.o:%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/backends/%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -%.o:%.mm - $(CXX) $(CXXFLAGS) -ObjC++ -fobjc-weak -fobjc-arc -c -o $@ $< - -%.o:$(IMGUI_DIR)/backends/%.mm - $(CXX) $(CXXFLAGS) -ObjC++ -fobjc-weak -fobjc-arc -c -o $@ $< - -all: $(EXE) - @echo Build complete - -$(EXE): $(OBJS) - $(CXX) -o $@ $^ $(CXXFLAGS) $(LIBS) - -clean: - rm -f $(EXE) $(OBJS) diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_metal/main.mm b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_metal/main.mm deleted file mode 100644 index 5cd7043..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_metal/main.mm +++ /dev/null @@ -1,206 +0,0 @@ -// Dear ImGui: standalone example application for SDL2 + Metal -// (SDL is a cross-platform general purpose library for handling windows, inputs, OpenGL/Vulkan/Metal graphics context creation, etc.) - -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#include "imgui.h" -#include "imgui_impl_sdl2.h" -#include "imgui_impl_metal.h" -#include -#include - -#import -#import - -int main(int, char**) -{ - // Setup Dear ImGui context - IMGUI_CHECKVERSION(); - ImGui::CreateContext(); - ImGuiIO& io = ImGui::GetIO(); (void)io; - io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard; // Enable Keyboard Controls - io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad; // Enable Gamepad Controls - io.ConfigFlags |= ImGuiConfigFlags_DockingEnable; // Enable Docking - io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable; // Enable Multi-Viewport / Platform Windows - - // Setup style - ImGui::StyleColorsDark(); - //ImGui::StyleColorsLight(); - - // When viewports are enabled we tweak WindowRounding/WindowBg so platform windows can look identical to regular ones. - ImGuiStyle& style = ImGui::GetStyle(); - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - style.WindowRounding = 0.0f; - style.Colors[ImGuiCol_WindowBg].w = 1.0f; - } - - // Load Fonts - // - If no fonts are loaded, dear imgui will use the default font. You can also load multiple fonts and use ImGui::PushFont()/PopFont() to select them. - // - AddFontFromFileTTF() will return the ImFont* so you can store it if you need to select the font among multiple. - // - If the file cannot be loaded, the function will return a nullptr. Please handle those errors in your application (e.g. use an assertion, or display an error and quit). - // - The fonts will be rasterized at a given size (w/ oversampling) and stored into a texture when calling ImFontAtlas::Build()/GetTexDataAsXXXX(), which ImGui_ImplXXXX_NewFrame below will call. - // - Use '#define IMGUI_ENABLE_FREETYPE' in your imconfig file to use Freetype for higher quality font rendering. - // - Read 'docs/FONTS.md' for more instructions and details. - // - Remember that in C/C++ if you want to include a backslash \ in a string literal you need to write a double backslash \\ ! - //io.Fonts->AddFontDefault(); - //io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\segoeui.ttf", 18.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/DroidSans.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Roboto-Medium.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Cousine-Regular.ttf", 15.0f); - //ImFont* font = io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\ArialUni.ttf", 18.0f, nullptr, io.Fonts->GetGlyphRangesJapanese()); - //IM_ASSERT(font != nullptr); - - // Setup SDL - // (Some versions of SDL before <2.0.10 appears to have performance/stalling issues on a minority of Windows systems, - // depending on whether SDL_INIT_GAMECONTROLLER is enabled or disabled.. updating to latest version of SDL is recommended!) - if (SDL_Init(SDL_INIT_VIDEO | SDL_INIT_TIMER | SDL_INIT_GAMECONTROLLER) != 0) - { - printf("Error: %s\n", SDL_GetError()); - return -1; - } - - // Inform SDL that we will be using metal for rendering. Without this hint initialization of metal renderer may fail. - SDL_SetHint(SDL_HINT_RENDER_DRIVER, "metal"); - - // Enable native IME. - SDL_SetHint(SDL_HINT_IME_SHOW_UI, "1"); - - SDL_Window* window = SDL_CreateWindow("Dear ImGui SDL+Metal example", SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED, 1280, 720, SDL_WINDOW_RESIZABLE | SDL_WINDOW_ALLOW_HIGHDPI); - if (window == nullptr) - { - printf("Error creating window: %s\n", SDL_GetError()); - return -2; - } - - SDL_Renderer* renderer = SDL_CreateRenderer(window, -1, SDL_RENDERER_ACCELERATED | SDL_RENDERER_PRESENTVSYNC); - if (renderer == nullptr) - { - printf("Error creating renderer: %s\n", SDL_GetError()); - return -3; - } - - // Setup Platform/Renderer backends - CAMetalLayer* layer = (__bridge CAMetalLayer*)SDL_RenderGetMetalLayer(renderer); - layer.pixelFormat = MTLPixelFormatBGRA8Unorm; - ImGui_ImplMetal_Init(layer.device); - ImGui_ImplSDL2_InitForMetal(window); - - id commandQueue = [layer.device newCommandQueue]; - MTLRenderPassDescriptor* renderPassDescriptor = [MTLRenderPassDescriptor new]; - - // Our state - bool show_demo_window = true; - bool show_another_window = false; - float clear_color[4] = {0.45f, 0.55f, 0.60f, 1.00f}; - - // Main loop - bool done = false; - while (!done) - { - @autoreleasepool - { - // Poll and handle events (inputs, window resize, etc.) - // You can read the io.WantCaptureMouse, io.WantCaptureKeyboard flags to tell if dear imgui wants to use your inputs. - // - When io.WantCaptureMouse is true, do not dispatch mouse input data to your main application, or clear/overwrite your copy of the mouse data. - // - When io.WantCaptureKeyboard is true, do not dispatch keyboard input data to your main application, or clear/overwrite your copy of the keyboard data. - // Generally you may always pass all inputs to dear imgui, and hide them from your application based on those two flags. - SDL_Event event; - while (SDL_PollEvent(&event)) - { - ImGui_ImplSDL2_ProcessEvent(&event); - if (event.type == SDL_QUIT) - done = true; - if (event.type == SDL_WINDOWEVENT && event.window.event == SDL_WINDOWEVENT_CLOSE && event.window.windowID == SDL_GetWindowID(window)) - done = true; - } - - int width, height; - SDL_GetRendererOutputSize(renderer, &width, &height); - layer.drawableSize = CGSizeMake(width, height); - id drawable = [layer nextDrawable]; - - id commandBuffer = [commandQueue commandBuffer]; - renderPassDescriptor.colorAttachments[0].clearColor = MTLClearColorMake(clear_color[0] * clear_color[3], clear_color[1] * clear_color[3], clear_color[2] * clear_color[3], clear_color[3]); - renderPassDescriptor.colorAttachments[0].texture = drawable.texture; - renderPassDescriptor.colorAttachments[0].loadAction = MTLLoadActionClear; - renderPassDescriptor.colorAttachments[0].storeAction = MTLStoreActionStore; - id renderEncoder = [commandBuffer renderCommandEncoderWithDescriptor:renderPassDescriptor]; - [renderEncoder pushDebugGroup:@"ImGui demo"]; - - // Start the Dear ImGui frame - ImGui_ImplMetal_NewFrame(renderPassDescriptor); - ImGui_ImplSDL2_NewFrame(); - ImGui::NewFrame(); - - // 1. Show the big demo window (Most of the sample code is in ImGui::ShowDemoWindow()! You can browse its code to learn more about Dear ImGui!). - if (show_demo_window) - ImGui::ShowDemoWindow(&show_demo_window); - - // 2. Show a simple window that we create ourselves. We use a Begin/End pair to create a named window. - { - static float f = 0.0f; - static int counter = 0; - - ImGui::Begin("Hello, world!"); // Create a window called "Hello, world!" and append into it. - - ImGui::Text("This is some useful text."); // Display some text (you can use a format strings too) - ImGui::Checkbox("Demo Window", &show_demo_window); // Edit bools storing our window open/close state - ImGui::Checkbox("Another Window", &show_another_window); - - ImGui::SliderFloat("float", &f, 0.0f, 1.0f); // Edit 1 float using a slider from 0.0f to 1.0f - ImGui::ColorEdit3("clear color", (float*)&clear_color); // Edit 3 floats representing a color - - if (ImGui::Button("Button")) // Buttons return true when clicked (most widgets return true when edited/activated) - counter++; - ImGui::SameLine(); - ImGui::Text("counter = %d", counter); - - ImGui::Text("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / io.Framerate, io.Framerate); - ImGui::End(); - } - - // 3. Show another simple window. - if (show_another_window) - { - ImGui::Begin("Another Window", &show_another_window); // Pass a pointer to our bool variable (the window will have a closing button that will clear the bool when clicked) - ImGui::Text("Hello from another window!"); - if (ImGui::Button("Close Me")) - show_another_window = false; - ImGui::End(); - } - - // Rendering - ImGui::Render(); - ImGui_ImplMetal_RenderDrawData(ImGui::GetDrawData(), commandBuffer, renderEncoder); - - // Update and Render additional Platform Windows - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - ImGui::UpdatePlatformWindows(); - ImGui::RenderPlatformWindowsDefault(); - } - - [renderEncoder popDebugGroup]; - [renderEncoder endEncoding]; - - [commandBuffer presentDrawable:drawable]; - [commandBuffer commit]; - } - } - - // Cleanup - ImGui_ImplMetal_Shutdown(); - ImGui_ImplSDL2_Shutdown(); - ImGui::DestroyContext(); - - SDL_DestroyRenderer(renderer); - SDL_DestroyWindow(window); - SDL_Quit(); - - return 0; -} diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl2/Makefile b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl2/Makefile deleted file mode 100644 index a85ced0..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl2/Makefile +++ /dev/null @@ -1,79 +0,0 @@ -# -# Cross Platform Makefile -# Compatible with MSYS2/MINGW, Ubuntu 14.04.1 and Mac OS X -# -# You will need SDL2 (http://www.libsdl.org): -# Linux: -# apt-get install libsdl2-dev -# Mac OS X: -# brew install sdl2 -# MSYS2: -# pacman -S mingw-w64-i686-SDL2 -# - -#CXX = g++ -#CXX = clang++ - -EXE = example_sdl2_opengl2 -IMGUI_DIR = ../.. -SOURCES = main.cpp -SOURCES += $(IMGUI_DIR)/imgui.cpp $(IMGUI_DIR)/imgui_demo.cpp $(IMGUI_DIR)/imgui_draw.cpp $(IMGUI_DIR)/imgui_tables.cpp $(IMGUI_DIR)/imgui_widgets.cpp -SOURCES += $(IMGUI_DIR)/backends/imgui_impl_sdl2.cpp $(IMGUI_DIR)/backends/imgui_impl_opengl2.cpp -OBJS = $(addsuffix .o, $(basename $(notdir $(SOURCES)))) -UNAME_S := $(shell uname -s) - -CXXFLAGS = -std=c++11 -I$(IMGUI_DIR) -I$(IMGUI_DIR)/backends -CXXFLAGS += -g -Wall -Wformat -LIBS = - -##--------------------------------------------------------------------- -## BUILD FLAGS PER PLATFORM -##--------------------------------------------------------------------- - -ifeq ($(UNAME_S), Linux) #LINUX - ECHO_MESSAGE = "Linux" - LIBS += -lGL -ldl `sdl2-config --libs` - - CXXFLAGS += `sdl2-config --cflags` - CFLAGS = $(CXXFLAGS) -endif - -ifeq ($(UNAME_S), Darwin) #APPLE - ECHO_MESSAGE = "Mac OS X" - LIBS += -framework OpenGL -framework Cocoa -framework IOKit -framework CoreVideo `sdl2-config --libs` - LIBS += -L/usr/local/lib -L/opt/local/lib - - CXXFLAGS += `sdl2-config --cflags` - CXXFLAGS += -I/usr/local/include -I/opt/local/include - CFLAGS = $(CXXFLAGS) -endif - -ifeq ($(OS), Windows_NT) - ECHO_MESSAGE = "MinGW" - LIBS += -lgdi32 -lopengl32 -limm32 `pkg-config --static --libs sdl2` - - CXXFLAGS += `pkg-config --cflags sdl2` - CFLAGS = $(CXXFLAGS) -endif - -##--------------------------------------------------------------------- -## BUILD RULES -##--------------------------------------------------------------------- - -%.o:%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/backends/%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -all: $(EXE) - @echo Build complete for $(ECHO_MESSAGE) - -$(EXE): $(OBJS) - $(CXX) -o $@ $^ $(CXXFLAGS) $(LIBS) - -clean: - rm -f $(EXE) $(OBJS) diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl2/README.md b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl2/README.md deleted file mode 100644 index 40a49e6..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl2/README.md +++ /dev/null @@ -1,29 +0,0 @@ - -# How to Build - -- On Windows with Visual Studio's IDE - -Use the provided project file (.vcxproj). Add to solution (imgui_examples.sln) if necessary. - -- On Windows with Visual Studio's CLI - -``` -set SDL2_DIR=path_to_your_sdl2_folder -cl /Zi /MD /I.. /I..\.. /I%SDL2_DIR%\include main.cpp ..\..\backends\imgui_impl_sdl2.cpp ..\..\backends\imgui_impl_opengl2.cpp ..\..\imgui*.cpp /FeDebug/example_sdl2_opengl2.exe /FoDebug/ /link /libpath:%SDL2_DIR%\lib\x86 SDL2.lib SDL2main.lib opengl32.lib /subsystem:console -# ^^ include paths ^^ source files ^^ output exe ^^ output dir ^^ libraries -# or for 64-bit: -cl /Zi /MD /I.. /I..\.. /I%SDL2_DIR%\include main.cpp ..\..\backends\imgui_impl_sdl2.cpp ..\..\backends\imgui_impl_opengl2.cpp ..\..\imgui*.cpp /FeDebug/example_sdl2_opengl2.exe /FoDebug/ /link /libpath:%SDL2_DIR%\lib\x64 SDL2.lib SDL2main.lib opengl32.lib /subsystem:console -``` - -- On Linux and similar Unixes - -``` -c++ `sdl2-config --cflags` -I .. -I ../.. -I ../../backends main.cpp ../../backends/imgui_impl_sdl2.cpp ../../backends/imgui_impl_opengl2.cpp ../../imgui*.cpp `sdl2-config --libs` -lGL -``` - -- On Mac OS X - -``` -brew install sdl2 -c++ `sdl2-config --cflags` -I .. -I ../.. -I ../../backends main.cpp ../../backends/imgui_impl_sdl2.cpp ../../backends/imgui_impl_opengl2.cpp ../../imgui*.cpp `sdl2-config --libs` -framework OpenGl -``` diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl2/build_win32.bat b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl2/build_win32.bat deleted file mode 100644 index 7543eda..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl2/build_win32.bat +++ /dev/null @@ -1,8 +0,0 @@ -@REM Build for Visual Studio compiler. Run your copy of vcvars32.bat or vcvarsall.bat to setup command-line compiler. -@set OUT_DIR=Debug -@set OUT_EXE=example_sdl2_opengl2 -@set INCLUDES=/I..\.. /I..\..\backends /I%SDL2_DIR%\include -@set SOURCES=main.cpp ..\..\backends\imgui_impl_sdl2.cpp ..\..\backends\imgui_impl_opengl2.cpp ..\..\imgui*.cpp -@set LIBS=/LIBPATH:%SDL2_DIR%\lib\x86 SDL2.lib SDL2main.lib opengl32.lib shell32.lib -mkdir %OUT_DIR% -cl /nologo /Zi /MD /utf-8 %INCLUDES% %SOURCES% /Fe%OUT_DIR%/%OUT_EXE%.exe /Fo%OUT_DIR%/ /link %LIBS% /subsystem:console diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl2/example_sdl2_opengl2.vcxproj b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl2/example_sdl2_opengl2.vcxproj deleted file mode 100644 index 036463f..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl2/example_sdl2_opengl2.vcxproj +++ /dev/null @@ -1,186 +0,0 @@ - - - - - Debug - Win32 - - - Debug - x64 - - - Release - Win32 - - - Release - x64 - - - - {2AE17FDE-F7F3-4CAC-ADAB-0710EDA4F741} - example_sdl2_opengl2 - 8.1 - - - - Application - true - MultiByte - v140 - - - Application - true - MultiByte - v140 - - - Application - false - true - MultiByte - v140 - - - Application - false - true - MultiByte - v140 - - - - - - - - - - - - - - - - - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - - Level4 - Disabled - ..\..;..\..\backends;%SDL2_DIR%\include;$(VcpkgCurrentInstalledDir)include\SDL2;%(AdditionalIncludeDirectories) - /utf-8 %(AdditionalOptions) - - - true - %SDL2_DIR%\lib\x86;%(AdditionalLibraryDirectories) - opengl32.lib;SDL2.lib;SDL2main.lib;%(AdditionalDependencies) - Console - msvcrt.lib - - - - - Level4 - Disabled - ..\..;..\..\backends;%SDL2_DIR%\include;$(VcpkgCurrentInstalledDir)include\SDL2;%(AdditionalIncludeDirectories) - /utf-8 %(AdditionalOptions) - - - true - %SDL2_DIR%\lib\x64;%(AdditionalLibraryDirectories) - opengl32.lib;SDL2.lib;SDL2main.lib;%(AdditionalDependencies) - Console - msvcrt.lib - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends;%SDL2_DIR%\include;$(VcpkgCurrentInstalledDir)include\SDL2;%(AdditionalIncludeDirectories) - false - /utf-8 %(AdditionalOptions) - - - true - true - true - %SDL2_DIR%\lib\x86;%(AdditionalLibraryDirectories) - opengl32.lib;SDL2.lib;SDL2main.lib;%(AdditionalDependencies) - Console - - - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends;%SDL2_DIR%\include;$(VcpkgCurrentInstalledDir)include\SDL2;%(AdditionalIncludeDirectories) - false - /utf-8 %(AdditionalOptions) - - - true - true - true - %SDL2_DIR%\lib\x64;%(AdditionalLibraryDirectories) - opengl32.lib;SDL2.lib;SDL2main.lib;%(AdditionalDependencies) - Console - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl2/example_sdl2_opengl2.vcxproj.filters b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl2/example_sdl2_opengl2.vcxproj.filters deleted file mode 100644 index 752a196..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl2/example_sdl2_opengl2.vcxproj.filters +++ /dev/null @@ -1,64 +0,0 @@ - - - - - {20b90ce4-7fcb-4731-b9a0-075f875de82d} - - - {f18ab499-84e1-499f-8eff-9754361e0e52} - cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx - - - - - imgui - - - imgui - - - imgui - - - sources - - - imgui - - - imgui - - - sources - - - sources - - - - - imgui - - - imgui - - - imgui - - - sources - - - sources - - - - - - imgui - - - imgui - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl2/main.cpp b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl2/main.cpp deleted file mode 100644 index f4f1f21..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl2/main.cpp +++ /dev/null @@ -1,190 +0,0 @@ -// Dear ImGui: standalone example application for SDL2 + OpenGL -// (SDL is a cross-platform general purpose library for handling windows, inputs, OpenGL/Vulkan/Metal graphics context creation, etc.) - -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -// **DO NOT USE THIS CODE IF YOUR CODE/ENGINE IS USING MODERN OPENGL (SHADERS, VBO, VAO, etc.)** -// **Prefer using the code in the example_sdl2_opengl3/ folder** -// See imgui_impl_sdl2.cpp for details. - -#include "imgui.h" -#include "imgui_impl_sdl2.h" -#include "imgui_impl_opengl2.h" -#include -#include -#include - -// Main code -int main(int, char**) -{ - // Setup SDL - if (SDL_Init(SDL_INIT_VIDEO | SDL_INIT_TIMER | SDL_INIT_GAMECONTROLLER) != 0) - { - printf("Error: %s\n", SDL_GetError()); - return -1; - } - - // From 2.0.18: Enable native IME. -#ifdef SDL_HINT_IME_SHOW_UI - SDL_SetHint(SDL_HINT_IME_SHOW_UI, "1"); -#endif - - // Setup window - SDL_GL_SetAttribute(SDL_GL_DOUBLEBUFFER, 1); - SDL_GL_SetAttribute(SDL_GL_DEPTH_SIZE, 24); - SDL_GL_SetAttribute(SDL_GL_STENCIL_SIZE, 8); - SDL_GL_SetAttribute(SDL_GL_CONTEXT_MAJOR_VERSION, 2); - SDL_GL_SetAttribute(SDL_GL_CONTEXT_MINOR_VERSION, 2); - SDL_WindowFlags window_flags = (SDL_WindowFlags)(SDL_WINDOW_OPENGL | SDL_WINDOW_RESIZABLE | SDL_WINDOW_ALLOW_HIGHDPI); - SDL_Window* window = SDL_CreateWindow("Dear ImGui SDL2+OpenGL example", SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED, 1280, 720, window_flags); - SDL_GLContext gl_context = SDL_GL_CreateContext(window); - SDL_GL_MakeCurrent(window, gl_context); - SDL_GL_SetSwapInterval(1); // Enable vsync - - // Setup Dear ImGui context - IMGUI_CHECKVERSION(); - ImGui::CreateContext(); - ImGuiIO& io = ImGui::GetIO(); (void)io; - io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard; // Enable Keyboard Controls - io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad; // Enable Gamepad Controls - io.ConfigFlags |= ImGuiConfigFlags_DockingEnable; // Enable Docking - io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable; // Enable Multi-Viewport / Platform Windows - //io.ConfigViewportsNoAutoMerge = true; - //io.ConfigViewportsNoTaskBarIcon = true; - - // Setup Dear ImGui style - ImGui::StyleColorsDark(); - //ImGui::StyleColorsLight(); - - // When viewports are enabled we tweak WindowRounding/WindowBg so platform windows can look identical to regular ones. - ImGuiStyle& style = ImGui::GetStyle(); - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - style.WindowRounding = 0.0f; - style.Colors[ImGuiCol_WindowBg].w = 1.0f; - } - - // Setup Platform/Renderer backends - ImGui_ImplSDL2_InitForOpenGL(window, gl_context); - ImGui_ImplOpenGL2_Init(); - - // Load Fonts - // - If no fonts are loaded, dear imgui will use the default font. You can also load multiple fonts and use ImGui::PushFont()/PopFont() to select them. - // - AddFontFromFileTTF() will return the ImFont* so you can store it if you need to select the font among multiple. - // - If the file cannot be loaded, the function will return a nullptr. Please handle those errors in your application (e.g. use an assertion, or display an error and quit). - // - The fonts will be rasterized at a given size (w/ oversampling) and stored into a texture when calling ImFontAtlas::Build()/GetTexDataAsXXXX(), which ImGui_ImplXXXX_NewFrame below will call. - // - Use '#define IMGUI_ENABLE_FREETYPE' in your imconfig file to use Freetype for higher quality font rendering. - // - Read 'docs/FONTS.md' for more instructions and details. - // - Remember that in C/C++ if you want to include a backslash \ in a string literal you need to write a double backslash \\ ! - //io.Fonts->AddFontDefault(); - //io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\segoeui.ttf", 18.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/DroidSans.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Roboto-Medium.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Cousine-Regular.ttf", 15.0f); - //ImFont* font = io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\ArialUni.ttf", 18.0f, nullptr, io.Fonts->GetGlyphRangesJapanese()); - //IM_ASSERT(font != nullptr); - - // Our state - bool show_demo_window = true; - bool show_another_window = false; - ImVec4 clear_color = ImVec4(0.45f, 0.55f, 0.60f, 1.00f); - - // Main loop - bool done = false; - while (!done) - { - // Poll and handle events (inputs, window resize, etc.) - // You can read the io.WantCaptureMouse, io.WantCaptureKeyboard flags to tell if dear imgui wants to use your inputs. - // - When io.WantCaptureMouse is true, do not dispatch mouse input data to your main application, or clear/overwrite your copy of the mouse data. - // - When io.WantCaptureKeyboard is true, do not dispatch keyboard input data to your main application, or clear/overwrite your copy of the keyboard data. - // Generally you may always pass all inputs to dear imgui, and hide them from your application based on those two flags. - SDL_Event event; - while (SDL_PollEvent(&event)) - { - ImGui_ImplSDL2_ProcessEvent(&event); - if (event.type == SDL_QUIT) - done = true; - if (event.type == SDL_WINDOWEVENT && event.window.event == SDL_WINDOWEVENT_CLOSE && event.window.windowID == SDL_GetWindowID(window)) - done = true; - } - - // Start the Dear ImGui frame - ImGui_ImplOpenGL2_NewFrame(); - ImGui_ImplSDL2_NewFrame(); - ImGui::NewFrame(); - - // 1. Show the big demo window (Most of the sample code is in ImGui::ShowDemoWindow()! You can browse its code to learn more about Dear ImGui!). - if (show_demo_window) - ImGui::ShowDemoWindow(&show_demo_window); - - // 2. Show a simple window that we create ourselves. We use a Begin/End pair to create a named window. - { - static float f = 0.0f; - static int counter = 0; - - ImGui::Begin("Hello, world!"); // Create a window called "Hello, world!" and append into it. - - ImGui::Text("This is some useful text."); // Display some text (you can use a format strings too) - ImGui::Checkbox("Demo Window", &show_demo_window); // Edit bools storing our window open/close state - ImGui::Checkbox("Another Window", &show_another_window); - - ImGui::SliderFloat("float", &f, 0.0f, 1.0f); // Edit 1 float using a slider from 0.0f to 1.0f - ImGui::ColorEdit3("clear color", (float*)&clear_color); // Edit 3 floats representing a color - - if (ImGui::Button("Button")) // Buttons return true when clicked (most widgets return true when edited/activated) - counter++; - ImGui::SameLine(); - ImGui::Text("counter = %d", counter); - - ImGui::Text("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / io.Framerate, io.Framerate); - ImGui::End(); - } - - // 3. Show another simple window. - if (show_another_window) - { - ImGui::Begin("Another Window", &show_another_window); // Pass a pointer to our bool variable (the window will have a closing button that will clear the bool when clicked) - ImGui::Text("Hello from another window!"); - if (ImGui::Button("Close Me")) - show_another_window = false; - ImGui::End(); - } - - // Rendering - ImGui::Render(); - glViewport(0, 0, (int)io.DisplaySize.x, (int)io.DisplaySize.y); - glClearColor(clear_color.x * clear_color.w, clear_color.y * clear_color.w, clear_color.z * clear_color.w, clear_color.w); - glClear(GL_COLOR_BUFFER_BIT); - //glUseProgram(0); // You may want this if using this code in an OpenGL 3+ context where shaders may be bound - ImGui_ImplOpenGL2_RenderDrawData(ImGui::GetDrawData()); - - // Update and Render additional Platform Windows - // (Platform functions may change the current OpenGL context, so we save/restore it to make it easier to paste this code elsewhere. - // For this specific demo app we could also call SDL_GL_MakeCurrent(window, gl_context) directly) - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - SDL_Window* backup_current_window = SDL_GL_GetCurrentWindow(); - SDL_GLContext backup_current_context = SDL_GL_GetCurrentContext(); - ImGui::UpdatePlatformWindows(); - ImGui::RenderPlatformWindowsDefault(); - SDL_GL_MakeCurrent(backup_current_window, backup_current_context); - } - - SDL_GL_SwapWindow(window); - } - - // Cleanup - ImGui_ImplOpenGL2_Shutdown(); - ImGui_ImplSDL2_Shutdown(); - ImGui::DestroyContext(); - - SDL_GL_DeleteContext(gl_context); - SDL_DestroyWindow(window); - SDL_Quit(); - - return 0; -} diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl3/Makefile b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl3/Makefile deleted file mode 100644 index 5b4f941..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl3/Makefile +++ /dev/null @@ -1,91 +0,0 @@ -# -# Cross Platform Makefile -# Compatible with MSYS2/MINGW, Ubuntu 14.04.1 and Mac OS X -# -# You will need SDL2 (http://www.libsdl.org): -# Linux: -# apt-get install libsdl2-dev -# Mac OS X: -# brew install sdl2 -# MSYS2: -# pacman -S mingw-w64-i686-SDL2 -# - -#CXX = g++ -#CXX = clang++ - -EXE = example_sdl2_opengl3 -IMGUI_DIR = ../.. -SOURCES = main.cpp -SOURCES += $(IMGUI_DIR)/imgui.cpp $(IMGUI_DIR)/imgui_demo.cpp $(IMGUI_DIR)/imgui_draw.cpp $(IMGUI_DIR)/imgui_tables.cpp $(IMGUI_DIR)/imgui_widgets.cpp -SOURCES += $(IMGUI_DIR)/backends/imgui_impl_sdl2.cpp $(IMGUI_DIR)/backends/imgui_impl_opengl3.cpp -OBJS = $(addsuffix .o, $(basename $(notdir $(SOURCES)))) -UNAME_S := $(shell uname -s) -LINUX_GL_LIBS = -lGL - -CXXFLAGS = -std=c++11 -I$(IMGUI_DIR) -I$(IMGUI_DIR)/backends -CXXFLAGS += -g -Wall -Wformat -LIBS = - -##--------------------------------------------------------------------- -## OPENGL ES -##--------------------------------------------------------------------- - -## This assumes a GL ES library available in the system, e.g. libGLESv2.so -# CXXFLAGS += -DIMGUI_IMPL_OPENGL_ES2 -# LINUX_GL_LIBS = -lGLESv2 -## If you're on a Raspberry Pi and want to use the legacy drivers, -## use the following instead: -# LINUX_GL_LIBS = -L/opt/vc/lib -lbrcmGLESv2 - -##--------------------------------------------------------------------- -## BUILD FLAGS PER PLATFORM -##--------------------------------------------------------------------- - -ifeq ($(UNAME_S), Linux) #LINUX - ECHO_MESSAGE = "Linux" - LIBS += $(LINUX_GL_LIBS) -ldl `sdl2-config --libs` - - CXXFLAGS += `sdl2-config --cflags` - CFLAGS = $(CXXFLAGS) -endif - -ifeq ($(UNAME_S), Darwin) #APPLE - ECHO_MESSAGE = "Mac OS X" - LIBS += -framework OpenGL -framework Cocoa -framework IOKit -framework CoreVideo `sdl2-config --libs` - LIBS += -L/usr/local/lib -L/opt/local/lib - - CXXFLAGS += `sdl2-config --cflags` - CXXFLAGS += -I/usr/local/include -I/opt/local/include - CFLAGS = $(CXXFLAGS) -endif - -ifeq ($(OS), Windows_NT) - ECHO_MESSAGE = "MinGW" - LIBS += -lgdi32 -lopengl32 -limm32 `pkg-config --static --libs sdl2` - - CXXFLAGS += `pkg-config --cflags sdl2` - CFLAGS = $(CXXFLAGS) -endif - -##--------------------------------------------------------------------- -## BUILD RULES -##--------------------------------------------------------------------- - -%.o:%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/backends/%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -all: $(EXE) - @echo Build complete for $(ECHO_MESSAGE) - -$(EXE): $(OBJS) - $(CXX) -o $@ $^ $(CXXFLAGS) $(LIBS) - -clean: - rm -f $(EXE) $(OBJS) diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl3/Makefile.emscripten b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl3/Makefile.emscripten deleted file mode 100644 index da03484..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl3/Makefile.emscripten +++ /dev/null @@ -1,92 +0,0 @@ -# -# Makefile to use with SDL+emscripten -# See https://emscripten.org/docs/getting_started/downloads.html -# for installation instructions. -# -# This Makefile assumes you have loaded emscripten's environment. -# (On Windows, you may need to execute emsdk_env.bat or encmdprompt.bat ahead) -# -# Running `make -f Makefile.emscripten` will produce three files: -# - web/index.html -# - web/index.js -# - web/index.wasm -# -# All three are needed to run the demo. - -CC = emcc -CXX = em++ -WEB_DIR = web -EXE = $(WEB_DIR)/index.html -IMGUI_DIR = ../.. -SOURCES = main.cpp -SOURCES += $(IMGUI_DIR)/imgui.cpp $(IMGUI_DIR)/imgui_demo.cpp $(IMGUI_DIR)/imgui_draw.cpp $(IMGUI_DIR)/imgui_tables.cpp $(IMGUI_DIR)/imgui_widgets.cpp -SOURCES += $(IMGUI_DIR)/backends/imgui_impl_sdl2.cpp $(IMGUI_DIR)/backends/imgui_impl_opengl3.cpp -OBJS = $(addsuffix .o, $(basename $(notdir $(SOURCES)))) -UNAME_S := $(shell uname -s) -CPPFLAGS = -LDFLAGS = -EMS = - -##--------------------------------------------------------------------- -## EMSCRIPTEN OPTIONS -##--------------------------------------------------------------------- - -# ("EMS" options gets added to both CPPFLAGS and LDFLAGS, whereas some options are for linker only) -EMS += -s USE_SDL=2 -EMS += -s DISABLE_EXCEPTION_CATCHING=1 -LDFLAGS += -s WASM=1 -s ALLOW_MEMORY_GROWTH=1 -s NO_EXIT_RUNTIME=0 -s ASSERTIONS=1 - -# Uncomment next line to fix possible rendering bugs with Emscripten version older then 1.39.0 (https://github.com/ocornut/imgui/issues/2877) -#EMS += -s BINARYEN_TRAP_MODE=clamp -#EMS += -s SAFE_HEAP=1 ## Adds overhead - -# Emscripten allows preloading a file or folder to be accessible at runtime. -# The Makefile for this example project suggests embedding the misc/fonts/ folder into our application, it will then be accessible as "/fonts" -# See documentation for more details: https://emscripten.org/docs/porting/files/packaging_files.html -# (Default value is 0. Set to 1 to enable file-system and include the misc/fonts/ folder as part of the build.) -USE_FILE_SYSTEM ?= 0 -ifeq ($(USE_FILE_SYSTEM), 0) -LDFLAGS += -s NO_FILESYSTEM=1 -CPPFLAGS += -DIMGUI_DISABLE_FILE_FUNCTIONS -endif -ifeq ($(USE_FILE_SYSTEM), 1) -LDFLAGS += --no-heap-copy --preload-file ../../misc/fonts@/fonts -endif - -##--------------------------------------------------------------------- -## FINAL BUILD FLAGS -##--------------------------------------------------------------------- - -CPPFLAGS += -I$(IMGUI_DIR) -I$(IMGUI_DIR)/backends -#CPPFLAGS += -g -CPPFLAGS += -Wall -Wformat -Os $(EMS) -LDFLAGS += --shell-file ../libs/emscripten/shell_minimal.html -LDFLAGS += $(EMS) - -##--------------------------------------------------------------------- -## BUILD RULES -##--------------------------------------------------------------------- - -%.o:%.cpp - $(CXX) $(CPPFLAGS) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/%.cpp - $(CXX) $(CPPFLAGS) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/backends/%.cpp - $(CXX) $(CPPFLAGS) $(CXXFLAGS) -c -o $@ $< - -all: $(EXE) - @echo Build complete for $(EXE) - -$(WEB_DIR): - mkdir $@ - -serve: all - python3 -m http.server -d $(WEB_DIR) - -$(EXE): $(OBJS) $(WEB_DIR) - $(CXX) -o $@ $(OBJS) $(LDFLAGS) - -clean: - rm -rf $(OBJS) $(WEB_DIR) diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl3/README.md b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl3/README.md deleted file mode 100644 index 81fd9fe..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl3/README.md +++ /dev/null @@ -1,57 +0,0 @@ - -# How to Build - -## Windows with Visual Studio's IDE - -Use the provided project file (.vcxproj). Add to solution (imgui_examples.sln) if necessary. - -## Windows with Visual Studio's CLI - -Use build_win32.bat or directly: -``` -set SDL2_DIR=path_to_your_sdl2_folder -cl /Zi /MD /utf-8 /I.. /I..\.. /I%SDL2_DIR%\include main.cpp ..\..\backends\imgui_impl_sdl2.cpp ..\..\backends\imgui_impl_opengl3.cpp ..\..\imgui*.cpp /FeDebug/example_sdl2_opengl3.exe /FoDebug/ /link /libpath:%SDL2_DIR%\lib\x86 SDL2.lib SDL2main.lib opengl32.lib /subsystem:console -# ^^ include paths ^^ source files ^^ output exe ^^ output dir ^^ libraries -# or for 64-bit: -cl /Zi /MD /utf-8 /I.. /I..\.. /I%SDL2_DIR%\include main.cpp ..\..\backends\imgui_impl_sdl2.cpp ..\..\backends\imgui_impl_opengl3.cpp ..\..\imgui*.cpp /FeDebug/example_sdl2_opengl3.exe /FoDebug/ /link /libpath:%SDL2_DIR%\lib\x64 SDL2.lib SDL2main.lib opengl32.lib /subsystem:console -``` - -## Linux and similar Unixes - -Use our Makefile or directly: -``` -c++ `sdl2-config --cflags` -I .. -I ../.. -I ../../backends - main.cpp ../../backends/imgui_impl_sdl2.cpp ../../backends/imgui_impl_opengl3.cpp ../../imgui*.cpp - `sdl2-config --libs` -lGL -ldl -``` - -## macOS - -Use our Makefile or directly: -``` -brew install sdl2 -c++ `sdl2-config --cflags` -I .. -I ../.. -I ../../backends - main.cpp ../../backends/imgui_impl_sdl2.cpp ../../backends/imgui_impl_opengl3.cpp ../../imgui*.cpp - `sdl2-config --libs` -framework OpenGl -framework CoreFoundation -``` - -## Emscripten - -**Building** - -You need to install Emscripten from https://emscripten.org/docs/getting_started/downloads.html, and have the environment variables set, as described in https://emscripten.org/docs/getting_started/downloads.html#installation-instructions - -- Depending on your configuration, in Windows you may need to run `emsdk/emsdk_env.bat` in your console to access the Emscripten command-line tools. -- You may also refer to our [Continuous Integration setup](https://github.com/ocornut/imgui/tree/master/.github/workflows) for Emscripten setup. -- Then build using `make -f Makefile.emscripten` while in the current directory. - -**Running an Emscripten project** - -To run on a local machine: -- `make -f Makefile.emscripten serve` will use Python3 to spawn a local webserver, you can then browse http://localhost:8000 to access your build. -- Otherwise, generally you will need a local webserver. Quoting [https://emscripten.org/docs/getting_started](https://emscripten.org/docs/getting_started/Tutorial.html#generating-html):
-_"Unfortunately several browsers (including Chrome, Safari, and Internet Explorer) do not support file:// [XHR](https://emscripten.org/docs/site/glossary.html#term-xhr) requests, and can’t load extra files needed by the HTML (like a .wasm file, or packaged file data as mentioned lower down). For these browsers you’ll need to serve the files using a [local webserver](https://emscripten.org/docs/getting_started/FAQ.html#faq-local-webserver) and then open http://localhost:8000/hello.html."_ -- Emscripten SDK has a handy `emrun` command: `emrun web/index.html --browser firefox` which will spawn a temporary local webserver (in Firefox). See https://emscripten.org/docs/compiling/Running-html-files-with-emrun.html for details. -- You may use Python 3 builtin webserver: `python -m http.server -d web` (this is what `make serve` uses). -- You may use Python 2 builtin webserver: `cd web && python -m SimpleHTTPServer`. -- If you are accessing the files over a network, certain browsers, such as Firefox, will restrict Gamepad API access to secure contexts only (e.g. https only). diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl3/build_win32.bat b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl3/build_win32.bat deleted file mode 100644 index 7b2fac9..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl3/build_win32.bat +++ /dev/null @@ -1,8 +0,0 @@ -@REM Build for Visual Studio compiler. Run your copy of vcvars32.bat or vcvarsall.bat to setup command-line compiler. -@set OUT_DIR=Debug -@set OUT_EXE=example_sdl2_opengl3 -@set INCLUDES=/I..\.. /I..\..\backends /I%SDL2_DIR%\include -@set SOURCES=main.cpp ..\..\backends\imgui_impl_sdl2.cpp ..\..\backends\imgui_impl_opengl3.cpp ..\..\imgui*.cpp -@set LIBS=/LIBPATH:%SDL2_DIR%\lib\x86 SDL2.lib SDL2main.lib opengl32.lib shell32.lib -mkdir %OUT_DIR% -cl /nologo /Zi /MD /utf-8 %INCLUDES% %SOURCES% /Fe%OUT_DIR%/%OUT_EXE%.exe /Fo%OUT_DIR%/ /link %LIBS% /subsystem:console diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl3/example_sdl2_opengl3.vcxproj b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl3/example_sdl2_opengl3.vcxproj deleted file mode 100644 index 6a81c67..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl3/example_sdl2_opengl3.vcxproj +++ /dev/null @@ -1,187 +0,0 @@ - - - - - Debug - Win32 - - - Debug - x64 - - - Release - Win32 - - - Release - x64 - - - - {BBAEB705-1669-40F3-8567-04CF6A991F4C} - example_sdl2_opengl3 - 8.1 - - - - Application - true - MultiByte - v140 - - - Application - true - MultiByte - v140 - - - Application - false - true - MultiByte - v140 - - - Application - false - true - MultiByte - v140 - - - - - - - - - - - - - - - - - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - - Level4 - Disabled - ..\..;..\..\backends;%SDL2_DIR%\include;$(VcpkgCurrentInstalledDir)include\SDL2;%(AdditionalIncludeDirectories) - /utf-8 %(AdditionalOptions) - - - true - %SDL2_DIR%\lib\x86;%(AdditionalLibraryDirectories) - opengl32.lib;SDL2.lib;SDL2main.lib;%(AdditionalDependencies) - Console - msvcrt.lib - - - - - Level4 - Disabled - ..\..;..\..\backends;%SDL2_DIR%\include;$(VcpkgCurrentInstalledDir)include\SDL2;%(AdditionalIncludeDirectories) - /utf-8 %(AdditionalOptions) - - - true - %SDL2_DIR%\lib\x64;%(AdditionalLibraryDirectories) - opengl32.lib;SDL2.lib;SDL2main.lib;%(AdditionalDependencies) - Console - msvcrt.lib - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends;%SDL2_DIR%\include;$(VcpkgCurrentInstalledDir)include\SDL2;%(AdditionalIncludeDirectories) - false - /utf-8 %(AdditionalOptions) - - - true - true - true - %SDL2_DIR%\lib\x86;%(AdditionalLibraryDirectories) - opengl32.lib;SDL2.lib;SDL2main.lib;%(AdditionalDependencies) - Console - - - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends;%SDL2_DIR%\include;$(VcpkgCurrentInstalledDir)include\SDL2;%(AdditionalIncludeDirectories) - false - /utf-8 %(AdditionalOptions) - - - true - true - true - %SDL2_DIR%\lib\x64;%(AdditionalLibraryDirectories) - opengl32.lib;SDL2.lib;SDL2main.lib;%(AdditionalDependencies) - Console - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl3/example_sdl2_opengl3.vcxproj.filters b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl3/example_sdl2_opengl3.vcxproj.filters deleted file mode 100644 index 846d557..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl3/example_sdl2_opengl3.vcxproj.filters +++ /dev/null @@ -1,67 +0,0 @@ - - - - - {20b90ce4-7fcb-4731-b9a0-075f875de82d} - - - {f18ab499-84e1-499f-8eff-9754361e0e52} - cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx - - - - - imgui - - - imgui - - - imgui - - - sources - - - sources - - - sources - - - imgui - - - imgui - - - - - imgui - - - imgui - - - imgui - - - sources - - - sources - - - sources - - - - - - imgui - - - imgui - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl3/main.cpp b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl3/main.cpp deleted file mode 100644 index e298e0a..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_opengl3/main.cpp +++ /dev/null @@ -1,227 +0,0 @@ -// Dear ImGui: standalone example application for SDL2 + OpenGL -// (SDL is a cross-platform general purpose library for handling windows, inputs, OpenGL/Vulkan/Metal graphics context creation, etc.) - -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#include "imgui.h" -#include "imgui_impl_sdl2.h" -#include "imgui_impl_opengl3.h" -#include -#include -#if defined(IMGUI_IMPL_OPENGL_ES2) -#include -#else -#include -#endif - -// This example can also compile and run with Emscripten! See 'Makefile.emscripten' for details. -#ifdef __EMSCRIPTEN__ -#include "../libs/emscripten/emscripten_mainloop_stub.h" -#endif - -// Main code -int main(int, char**) -{ - // Setup SDL - if (SDL_Init(SDL_INIT_VIDEO | SDL_INIT_TIMER | SDL_INIT_GAMECONTROLLER) != 0) - { - printf("Error: %s\n", SDL_GetError()); - return -1; - } - - // Decide GL+GLSL versions -#if defined(IMGUI_IMPL_OPENGL_ES2) - // GL ES 2.0 + GLSL 100 - const char* glsl_version = "#version 100"; - SDL_GL_SetAttribute(SDL_GL_CONTEXT_FLAGS, 0); - SDL_GL_SetAttribute(SDL_GL_CONTEXT_PROFILE_MASK, SDL_GL_CONTEXT_PROFILE_ES); - SDL_GL_SetAttribute(SDL_GL_CONTEXT_MAJOR_VERSION, 2); - SDL_GL_SetAttribute(SDL_GL_CONTEXT_MINOR_VERSION, 0); -#elif defined(__APPLE__) - // GL 3.2 Core + GLSL 150 - const char* glsl_version = "#version 150"; - SDL_GL_SetAttribute(SDL_GL_CONTEXT_FLAGS, SDL_GL_CONTEXT_FORWARD_COMPATIBLE_FLAG); // Always required on Mac - SDL_GL_SetAttribute(SDL_GL_CONTEXT_PROFILE_MASK, SDL_GL_CONTEXT_PROFILE_CORE); - SDL_GL_SetAttribute(SDL_GL_CONTEXT_MAJOR_VERSION, 3); - SDL_GL_SetAttribute(SDL_GL_CONTEXT_MINOR_VERSION, 2); -#else - // GL 3.0 + GLSL 130 - const char* glsl_version = "#version 130"; - SDL_GL_SetAttribute(SDL_GL_CONTEXT_FLAGS, 0); - SDL_GL_SetAttribute(SDL_GL_CONTEXT_PROFILE_MASK, SDL_GL_CONTEXT_PROFILE_CORE); - SDL_GL_SetAttribute(SDL_GL_CONTEXT_MAJOR_VERSION, 3); - SDL_GL_SetAttribute(SDL_GL_CONTEXT_MINOR_VERSION, 0); -#endif - - // From 2.0.18: Enable native IME. -#ifdef SDL_HINT_IME_SHOW_UI - SDL_SetHint(SDL_HINT_IME_SHOW_UI, "1"); -#endif - - // Create window with graphics context - SDL_GL_SetAttribute(SDL_GL_DOUBLEBUFFER, 1); - SDL_GL_SetAttribute(SDL_GL_DEPTH_SIZE, 24); - SDL_GL_SetAttribute(SDL_GL_STENCIL_SIZE, 8); - SDL_WindowFlags window_flags = (SDL_WindowFlags)(SDL_WINDOW_OPENGL | SDL_WINDOW_RESIZABLE | SDL_WINDOW_ALLOW_HIGHDPI); - SDL_Window* window = SDL_CreateWindow("Dear ImGui SDL2+OpenGL3 example", SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED, 1280, 720, window_flags); - SDL_GLContext gl_context = SDL_GL_CreateContext(window); - SDL_GL_MakeCurrent(window, gl_context); - SDL_GL_SetSwapInterval(1); // Enable vsync - - // Setup Dear ImGui context - IMGUI_CHECKVERSION(); - ImGui::CreateContext(); - ImGuiIO& io = ImGui::GetIO(); (void)io; - io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard; // Enable Keyboard Controls - io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad; // Enable Gamepad Controls - io.ConfigFlags |= ImGuiConfigFlags_DockingEnable; // Enable Docking - io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable; // Enable Multi-Viewport / Platform Windows - //io.ConfigViewportsNoAutoMerge = true; - //io.ConfigViewportsNoTaskBarIcon = true; - - // Setup Dear ImGui style - ImGui::StyleColorsDark(); - //ImGui::StyleColorsLight(); - - // When viewports are enabled we tweak WindowRounding/WindowBg so platform windows can look identical to regular ones. - ImGuiStyle& style = ImGui::GetStyle(); - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - style.WindowRounding = 0.0f; - style.Colors[ImGuiCol_WindowBg].w = 1.0f; - } - - // Setup Platform/Renderer backends - ImGui_ImplSDL2_InitForOpenGL(window, gl_context); - ImGui_ImplOpenGL3_Init(glsl_version); - - // Load Fonts - // - If no fonts are loaded, dear imgui will use the default font. You can also load multiple fonts and use ImGui::PushFont()/PopFont() to select them. - // - AddFontFromFileTTF() will return the ImFont* so you can store it if you need to select the font among multiple. - // - If the file cannot be loaded, the function will return a nullptr. Please handle those errors in your application (e.g. use an assertion, or display an error and quit). - // - The fonts will be rasterized at a given size (w/ oversampling) and stored into a texture when calling ImFontAtlas::Build()/GetTexDataAsXXXX(), which ImGui_ImplXXXX_NewFrame below will call. - // - Use '#define IMGUI_ENABLE_FREETYPE' in your imconfig file to use Freetype for higher quality font rendering. - // - Read 'docs/FONTS.md' for more instructions and details. - // - Remember that in C/C++ if you want to include a backslash \ in a string literal you need to write a double backslash \\ ! - // - Our Emscripten build process allows embedding fonts to be accessible at runtime from the "fonts/" folder. See Makefile.emscripten for details. - //io.Fonts->AddFontDefault(); - //io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\segoeui.ttf", 18.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/DroidSans.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Roboto-Medium.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Cousine-Regular.ttf", 15.0f); - //ImFont* font = io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\ArialUni.ttf", 18.0f, nullptr, io.Fonts->GetGlyphRangesJapanese()); - //IM_ASSERT(font != nullptr); - - // Our state - bool show_demo_window = true; - bool show_another_window = false; - ImVec4 clear_color = ImVec4(0.45f, 0.55f, 0.60f, 1.00f); - - // Main loop - bool done = false; -#ifdef __EMSCRIPTEN__ - // For an Emscripten build we are disabling file-system access, so let's not attempt to do a fopen() of the imgui.ini file. - // You may manually call LoadIniSettingsFromMemory() to load settings from your own storage. - io.IniFilename = nullptr; - EMSCRIPTEN_MAINLOOP_BEGIN -#else - while (!done) -#endif - { - // Poll and handle events (inputs, window resize, etc.) - // You can read the io.WantCaptureMouse, io.WantCaptureKeyboard flags to tell if dear imgui wants to use your inputs. - // - When io.WantCaptureMouse is true, do not dispatch mouse input data to your main application, or clear/overwrite your copy of the mouse data. - // - When io.WantCaptureKeyboard is true, do not dispatch keyboard input data to your main application, or clear/overwrite your copy of the keyboard data. - // Generally you may always pass all inputs to dear imgui, and hide them from your application based on those two flags. - SDL_Event event; - while (SDL_PollEvent(&event)) - { - ImGui_ImplSDL2_ProcessEvent(&event); - if (event.type == SDL_QUIT) - done = true; - if (event.type == SDL_WINDOWEVENT && event.window.event == SDL_WINDOWEVENT_CLOSE && event.window.windowID == SDL_GetWindowID(window)) - done = true; - } - - // Start the Dear ImGui frame - ImGui_ImplOpenGL3_NewFrame(); - ImGui_ImplSDL2_NewFrame(); - ImGui::NewFrame(); - - // 1. Show the big demo window (Most of the sample code is in ImGui::ShowDemoWindow()! You can browse its code to learn more about Dear ImGui!). - if (show_demo_window) - ImGui::ShowDemoWindow(&show_demo_window); - - // 2. Show a simple window that we create ourselves. We use a Begin/End pair to create a named window. - { - static float f = 0.0f; - static int counter = 0; - - ImGui::Begin("Hello, world!"); // Create a window called "Hello, world!" and append into it. - - ImGui::Text("This is some useful text."); // Display some text (you can use a format strings too) - ImGui::Checkbox("Demo Window", &show_demo_window); // Edit bools storing our window open/close state - ImGui::Checkbox("Another Window", &show_another_window); - - ImGui::SliderFloat("float", &f, 0.0f, 1.0f); // Edit 1 float using a slider from 0.0f to 1.0f - ImGui::ColorEdit3("clear color", (float*)&clear_color); // Edit 3 floats representing a color - - if (ImGui::Button("Button")) // Buttons return true when clicked (most widgets return true when edited/activated) - counter++; - ImGui::SameLine(); - ImGui::Text("counter = %d", counter); - - ImGui::Text("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / io.Framerate, io.Framerate); - ImGui::End(); - } - - // 3. Show another simple window. - if (show_another_window) - { - ImGui::Begin("Another Window", &show_another_window); // Pass a pointer to our bool variable (the window will have a closing button that will clear the bool when clicked) - ImGui::Text("Hello from another window!"); - if (ImGui::Button("Close Me")) - show_another_window = false; - ImGui::End(); - } - - // Rendering - ImGui::Render(); - glViewport(0, 0, (int)io.DisplaySize.x, (int)io.DisplaySize.y); - glClearColor(clear_color.x * clear_color.w, clear_color.y * clear_color.w, clear_color.z * clear_color.w, clear_color.w); - glClear(GL_COLOR_BUFFER_BIT); - ImGui_ImplOpenGL3_RenderDrawData(ImGui::GetDrawData()); - - // Update and Render additional Platform Windows - // (Platform functions may change the current OpenGL context, so we save/restore it to make it easier to paste this code elsewhere. - // For this specific demo app we could also call SDL_GL_MakeCurrent(window, gl_context) directly) - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - SDL_Window* backup_current_window = SDL_GL_GetCurrentWindow(); - SDL_GLContext backup_current_context = SDL_GL_GetCurrentContext(); - ImGui::UpdatePlatformWindows(); - ImGui::RenderPlatformWindowsDefault(); - SDL_GL_MakeCurrent(backup_current_window, backup_current_context); - } - - SDL_GL_SwapWindow(window); - } -#ifdef __EMSCRIPTEN__ - EMSCRIPTEN_MAINLOOP_END; -#endif - - // Cleanup - ImGui_ImplOpenGL3_Shutdown(); - ImGui_ImplSDL2_Shutdown(); - ImGui::DestroyContext(); - - SDL_GL_DeleteContext(gl_context); - SDL_DestroyWindow(window); - SDL_Quit(); - - return 0; -} diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_sdlrenderer2/Makefile b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_sdlrenderer2/Makefile deleted file mode 100644 index 5820d9b..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_sdlrenderer2/Makefile +++ /dev/null @@ -1,79 +0,0 @@ -# -# Cross Platform Makefile -# Compatible with MSYS2/MINGW, Ubuntu 14.04.1 and Mac OS X -# -# You will need SDL2 (http://www.libsdl.org): -# Linux: -# apt-get install libsdl2-dev -# Mac OS X: -# brew install sdl2 -# MSYS2: -# pacman -S mingw-w64-i686-SDL2 -# - -#CXX = g++ -#CXX = clang++ - -EXE = example_sdl2_sdlrenderer2 -IMGUI_DIR = ../.. -SOURCES = main.cpp -SOURCES += $(IMGUI_DIR)/imgui.cpp $(IMGUI_DIR)/imgui_demo.cpp $(IMGUI_DIR)/imgui_draw.cpp $(IMGUI_DIR)/imgui_tables.cpp $(IMGUI_DIR)/imgui_widgets.cpp -SOURCES += $(IMGUI_DIR)/backends/imgui_impl_sdl2.cpp $(IMGUI_DIR)/backends/imgui_impl_sdlrenderer2.cpp -OBJS = $(addsuffix .o, $(basename $(notdir $(SOURCES)))) -UNAME_S := $(shell uname -s) - -CXXFLAGS = -std=c++11 -I$(IMGUI_DIR) -I$(IMGUI_DIR)/backends -CXXFLAGS += -g -Wall -Wformat -LIBS = - -##--------------------------------------------------------------------- -## BUILD FLAGS PER PLATFORM -##--------------------------------------------------------------------- - -ifeq ($(UNAME_S), Linux) #LINUX - ECHO_MESSAGE = "Linux" - LIBS += -lGL -ldl `sdl2-config --libs` - - CXXFLAGS += `sdl2-config --cflags` - CFLAGS = $(CXXFLAGS) -endif - -ifeq ($(UNAME_S), Darwin) #APPLE - ECHO_MESSAGE = "Mac OS X" - LIBS += -framework OpenGL -framework Cocoa -framework IOKit -framework CoreVideo `sdl2-config --libs` - LIBS += -L/usr/local/lib -L/opt/local/lib - - CXXFLAGS += `sdl2-config --cflags` - CXXFLAGS += -I/usr/local/include -I/opt/local/include - CFLAGS = $(CXXFLAGS) -endif - -ifeq ($(OS), Windows_NT) - ECHO_MESSAGE = "MinGW" - LIBS += -lgdi32 -lopengl32 -limm32 `pkg-config --static --libs sdl2` - - CXXFLAGS += `pkg-config --cflags sdl2` - CFLAGS = $(CXXFLAGS) -endif - -##--------------------------------------------------------------------- -## BUILD RULES -##--------------------------------------------------------------------- - -%.o:%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/backends/%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -all: $(EXE) - @echo Build complete for $(ECHO_MESSAGE) - -$(EXE): $(OBJS) - $(CXX) -o $@ $^ $(CXXFLAGS) $(LIBS) - -clean: - rm -f $(EXE) $(OBJS) diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_sdlrenderer2/README.md b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_sdlrenderer2/README.md deleted file mode 100644 index ef6fe85..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_sdlrenderer2/README.md +++ /dev/null @@ -1,25 +0,0 @@ - -# How to Build - -- On Windows with Visual Studio's CLI - -``` -set SDL2_DIR=path_to_your_sdl2_folder -cl /Zi /MD /utf-8 /I.. /I..\.. /I%SDL2_DIR%\include main.cpp ..\..\backends\imgui_impl_sdl2.cpp ..\..\backends\imgui_impl_sdlrenderer2.cpp ..\..\imgui*.cpp /FeDebug/example_sdl2_sdlrenderer.exe /FoDebug/ /link /libpath:%SDL2_DIR%\lib\x86 SDL2.lib SDL2main.lib /subsystem:console -# ^^ include paths ^^ source files ^^ output exe ^^ output dir ^^ libraries -# or for 64-bit: -cl /Zi /MD /utf-8 /I.. /I..\.. /I%SDL2_DIR%\include main.cpp ..\..\backends\imgui_impl_sdl2.cpp ..\..\backends\imgui_impl_sdlrenderer2.cpp ..\..\imgui*.cpp /FeDebug/example_sdl2_sdlrenderer.exe /FoDebug/ /link /libpath:%SDL2_DIR%\lib\x64 SDL2.lib SDL2main.lib /subsystem:console -``` - -- On Linux and similar Unixes - -``` -c++ `sdl2-config --cflags` -I .. -I ../.. main.cpp ../../backends/imgui_impl_sdl2.cpp ../../backends/imgui_impl_sdlrenderer2.cpp ../../imgui*.cpp `sdl2-config --libs` -lGL -``` - -- On Mac OS X - -``` -brew install sdl2 -c++ `sdl2-config --cflags` -I .. -I ../.. main.cpp ../../backends/imgui_impl_sdl2.cpp ../../backends/imgui_impl_sdlrenderer2.cpp ../../imgui*.cpp `sdl2-config --libs` -framework OpenGl -``` diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_sdlrenderer2/build_win32.bat b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_sdlrenderer2/build_win32.bat deleted file mode 100644 index e311bfc..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_sdlrenderer2/build_win32.bat +++ /dev/null @@ -1,8 +0,0 @@ -@REM Build for Visual Studio compiler. Run your copy of vcvars32.bat or vcvarsall.bat to setup command-line compiler. -@set OUT_DIR=Debug -@set OUT_EXE=example_sdl2_sdlrenderer_ -@set INCLUDES=/I..\.. /I..\..\backends /I%SDL2_DIR%\include -@set SOURCES=main.cpp ..\..\backends\imgui_impl_sdl2.cpp ..\..\backends\imgui_impl_sdlrenderer2.cpp ..\..\imgui*.cpp -@set LIBS=/LIBPATH:%SDL2_DIR%\lib\x86 SDL2.lib SDL2main.lib -mkdir %OUT_DIR% -cl /nologo /Zi /MD /utf-8 %INCLUDES% %SOURCES% /Fe%OUT_DIR%/%OUT_EXE%.exe /Fo%OUT_DIR%/ /link %LIBS% /subsystem:console diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_sdlrenderer2/example_sdl2_sdlrenderer2.vcxproj b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_sdlrenderer2/example_sdl2_sdlrenderer2.vcxproj deleted file mode 100644 index cf2c890..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_sdlrenderer2/example_sdl2_sdlrenderer2.vcxproj +++ /dev/null @@ -1,187 +0,0 @@ - - - - - Debug - Win32 - - - Debug - x64 - - - Release - Win32 - - - Release - x64 - - - - {0C0B2BEA-311F-473C-9652-87923EF639E3} - example_sdl2_sdlrenderer2 - 8.1 - example_sdl2_sdlrenderer2 - - - - Application - true - MultiByte - v140 - - - Application - true - MultiByte - v140 - - - Application - false - true - MultiByte - v140 - - - Application - false - true - MultiByte - v140 - - - - - - - - - - - - - - - - - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - - Level4 - Disabled - ..\..;..\..\backends;%SDL2_DIR%\include;%(AdditionalIncludeDirectories) - /utf-8 %(AdditionalOptions) - - - true - %SDL2_DIR%\lib\x86;%(AdditionalLibraryDirectories) - SDL2.lib;SDL2main.lib;%(AdditionalDependencies) - Console - msvcrt.lib - - - - - Level4 - Disabled - ..\..;..\..\backends;%SDL2_DIR%\include;%(AdditionalIncludeDirectories) - /utf-8 %(AdditionalOptions) - - - true - %SDL2_DIR%\lib\x64;%(AdditionalLibraryDirectories) - SDL2.lib;SDL2main.lib;%(AdditionalDependencies) - Console - msvcrt.lib - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends;%SDL2_DIR%\include;%(AdditionalIncludeDirectories) - false - /utf-8 %(AdditionalOptions) - - - true - true - true - %SDL2_DIR%\lib\x86;%(AdditionalLibraryDirectories) - SDL2.lib;SDL2main.lib;%(AdditionalDependencies) - Console - - - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends;%SDL2_DIR%\include;%(AdditionalIncludeDirectories) - false - /utf-8 %(AdditionalOptions) - - - true - true - true - %SDL2_DIR%\lib\x64;%(AdditionalLibraryDirectories) - SDL2.lib;SDL2main.lib;%(AdditionalDependencies) - Console - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_sdlrenderer2/example_sdl2_sdlrenderer2.vcxproj.filters b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_sdlrenderer2/example_sdl2_sdlrenderer2.vcxproj.filters deleted file mode 100644 index 5c6da42..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_sdlrenderer2/example_sdl2_sdlrenderer2.vcxproj.filters +++ /dev/null @@ -1,64 +0,0 @@ - - - - - {20b90ce4-7fcb-4731-b9a0-075f875de82d} - - - {f18ab499-84e1-499f-8eff-9754361e0e52} - cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx - - - - - imgui - - - imgui - - - imgui - - - sources - - - imgui - - - imgui - - - sources - - - sources - - - - - imgui - - - imgui - - - imgui - - - sources - - - sources - - - - - - imgui - - - imgui - - - diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_sdlrenderer2/main.cpp b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_sdlrenderer2/main.cpp deleted file mode 100644 index bc7603e..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_sdlrenderer2/main.cpp +++ /dev/null @@ -1,167 +0,0 @@ -// Dear ImGui: standalone example application for SDL2 + SDL_Renderer -// (SDL is a cross-platform general purpose library for handling windows, inputs, OpenGL/Vulkan/Metal graphics context creation, etc.) - -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -// Important to understand: SDL_Renderer is an _optional_ component of SDL2. -// For a multi-platform app consider using e.g. SDL+DirectX on Windows and SDL+OpenGL on Linux/OSX. - -#include "imgui.h" -#include "imgui_impl_sdl2.h" -#include "imgui_impl_sdlrenderer2.h" -#include -#include - -#if !SDL_VERSION_ATLEAST(2,0,17) -#error This backend requires SDL 2.0.17+ because of SDL_RenderGeometry() function -#endif - -// Main code -int main(int, char**) -{ - // Setup SDL - if (SDL_Init(SDL_INIT_VIDEO | SDL_INIT_TIMER | SDL_INIT_GAMECONTROLLER) != 0) - { - printf("Error: %s\n", SDL_GetError()); - return -1; - } - - // From 2.0.18: Enable native IME. -#ifdef SDL_HINT_IME_SHOW_UI - SDL_SetHint(SDL_HINT_IME_SHOW_UI, "1"); -#endif - - // Create window with SDL_Renderer graphics context - SDL_WindowFlags window_flags = (SDL_WindowFlags)(SDL_WINDOW_RESIZABLE | SDL_WINDOW_ALLOW_HIGHDPI); - SDL_Window* window = SDL_CreateWindow("Dear ImGui SDL2+SDL_Renderer example", SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED, 1280, 720, window_flags); - SDL_Renderer* renderer = SDL_CreateRenderer(window, -1, SDL_RENDERER_PRESENTVSYNC | SDL_RENDERER_ACCELERATED); - if (renderer == nullptr) - { - SDL_Log("Error creating SDL_Renderer!"); - return 0; - } - //SDL_RendererInfo info; - //SDL_GetRendererInfo(renderer, &info); - //SDL_Log("Current SDL_Renderer: %s", info.name); - - // Setup Dear ImGui context - IMGUI_CHECKVERSION(); - ImGui::CreateContext(); - ImGuiIO& io = ImGui::GetIO(); (void)io; - io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard; // Enable Keyboard Controls - io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad; // Enable Gamepad Controls - - // Setup Dear ImGui style - ImGui::StyleColorsDark(); - //ImGui::StyleColorsLight(); - - // Setup Platform/Renderer backends - ImGui_ImplSDL2_InitForSDLRenderer(window, renderer); - ImGui_ImplSDLRenderer2_Init(renderer); - - // Load Fonts - // - If no fonts are loaded, dear imgui will use the default font. You can also load multiple fonts and use ImGui::PushFont()/PopFont() to select them. - // - AddFontFromFileTTF() will return the ImFont* so you can store it if you need to select the font among multiple. - // - If the file cannot be loaded, the function will return a nullptr. Please handle those errors in your application (e.g. use an assertion, or display an error and quit). - // - The fonts will be rasterized at a given size (w/ oversampling) and stored into a texture when calling ImFontAtlas::Build()/GetTexDataAsXXXX(), which ImGui_ImplXXXX_NewFrame below will call. - // - Use '#define IMGUI_ENABLE_FREETYPE' in your imconfig file to use Freetype for higher quality font rendering. - // - Read 'docs/FONTS.md' for more instructions and details. - // - Remember that in C/C++ if you want to include a backslash \ in a string literal you need to write a double backslash \\ ! - //io.Fonts->AddFontDefault(); - //io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\segoeui.ttf", 18.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/DroidSans.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Roboto-Medium.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Cousine-Regular.ttf", 15.0f); - //ImFont* font = io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\ArialUni.ttf", 18.0f, nullptr, io.Fonts->GetGlyphRangesJapanese()); - //IM_ASSERT(font != nullptr); - - // Our state - bool show_demo_window = true; - bool show_another_window = false; - ImVec4 clear_color = ImVec4(0.45f, 0.55f, 0.60f, 1.00f); - - // Main loop - bool done = false; - while (!done) - { - // Poll and handle events (inputs, window resize, etc.) - // You can read the io.WantCaptureMouse, io.WantCaptureKeyboard flags to tell if dear imgui wants to use your inputs. - // - When io.WantCaptureMouse is true, do not dispatch mouse input data to your main application, or clear/overwrite your copy of the mouse data. - // - When io.WantCaptureKeyboard is true, do not dispatch keyboard input data to your main application, or clear/overwrite your copy of the keyboard data. - // Generally you may always pass all inputs to dear imgui, and hide them from your application based on those two flags. - SDL_Event event; - while (SDL_PollEvent(&event)) - { - ImGui_ImplSDL2_ProcessEvent(&event); - if (event.type == SDL_QUIT) - done = true; - if (event.type == SDL_WINDOWEVENT && event.window.event == SDL_WINDOWEVENT_CLOSE && event.window.windowID == SDL_GetWindowID(window)) - done = true; - } - - // Start the Dear ImGui frame - ImGui_ImplSDLRenderer2_NewFrame(); - ImGui_ImplSDL2_NewFrame(); - ImGui::NewFrame(); - - // 1. Show the big demo window (Most of the sample code is in ImGui::ShowDemoWindow()! You can browse its code to learn more about Dear ImGui!). - if (show_demo_window) - ImGui::ShowDemoWindow(&show_demo_window); - - // 2. Show a simple window that we create ourselves. We use a Begin/End pair to create a named window. - { - static float f = 0.0f; - static int counter = 0; - - ImGui::Begin("Hello, world!"); // Create a window called "Hello, world!" and append into it. - - ImGui::Text("This is some useful text."); // Display some text (you can use a format strings too) - ImGui::Checkbox("Demo Window", &show_demo_window); // Edit bools storing our window open/close state - ImGui::Checkbox("Another Window", &show_another_window); - - ImGui::SliderFloat("float", &f, 0.0f, 1.0f); // Edit 1 float using a slider from 0.0f to 1.0f - ImGui::ColorEdit3("clear color", (float*)&clear_color); // Edit 3 floats representing a color - - if (ImGui::Button("Button")) // Buttons return true when clicked (most widgets return true when edited/activated) - counter++; - ImGui::SameLine(); - ImGui::Text("counter = %d", counter); - - ImGui::Text("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / io.Framerate, io.Framerate); - ImGui::End(); - } - - // 3. Show another simple window. - if (show_another_window) - { - ImGui::Begin("Another Window", &show_another_window); // Pass a pointer to our bool variable (the window will have a closing button that will clear the bool when clicked) - ImGui::Text("Hello from another window!"); - if (ImGui::Button("Close Me")) - show_another_window = false; - ImGui::End(); - } - - // Rendering - ImGui::Render(); - SDL_RenderSetScale(renderer, io.DisplayFramebufferScale.x, io.DisplayFramebufferScale.y); - SDL_SetRenderDrawColor(renderer, (Uint8)(clear_color.x * 255), (Uint8)(clear_color.y * 255), (Uint8)(clear_color.z * 255), (Uint8)(clear_color.w * 255)); - SDL_RenderClear(renderer); - ImGui_ImplSDLRenderer2_RenderDrawData(ImGui::GetDrawData()); - SDL_RenderPresent(renderer); - } - - // Cleanup - ImGui_ImplSDLRenderer2_Shutdown(); - ImGui_ImplSDL2_Shutdown(); - ImGui::DestroyContext(); - - SDL_DestroyRenderer(renderer); - SDL_DestroyWindow(window); - SDL_Quit(); - - return 0; -} diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_vulkan/build_win32.bat b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_vulkan/build_win32.bat deleted file mode 100644 index 8a4aefc..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_vulkan/build_win32.bat +++ /dev/null @@ -1,10 +0,0 @@ -@REM Build for Visual Studio compiler. Run your copy of vcvars32.bat or vcvarsall.bat to setup command-line compiler. - -@set OUT_EXE=example_sdl2_vulkan -@set INCLUDES=/I..\.. /I..\..\backends /I%SDL2_DIR%\include /I %VULKAN_SDK%\include -@set SOURCES=main.cpp ..\..\backends\imgui_impl_sdl2.cpp ..\..\backends\imgui_impl_vulkan.cpp ..\..\imgui*.cpp -@set LIBS=/LIBPATH:%SDL2_DIR%\lib\x86 /libpath:%VULKAN_SDK%\lib32 SDL2.lib SDL2main.lib shell32.lib vulkan-1.lib - -@set OUT_DIR=Debug -mkdir %OUT_DIR% -cl /nologo /Zi /MD /utf-8 %INCLUDES% /D ImTextureID=ImU64 %SOURCES% /Fe%OUT_DIR%/%OUT_EXE%.exe /Fo%OUT_DIR%/ /link %LIBS% /subsystem:console diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_vulkan/example_sdl2_vulkan.vcxproj b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_vulkan/example_sdl2_vulkan.vcxproj deleted file mode 100644 index ba6afaf..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_vulkan/example_sdl2_vulkan.vcxproj +++ /dev/null @@ -1,190 +0,0 @@ - - - - - Debug - Win32 - - - Debug - x64 - - - Release - Win32 - - - Release - x64 - - - - {BAE3D0B5-9695-4EB1-AD0F-75890EB4A3B3} - example_sdl2_vulkan - 8.1 - - - - Application - true - MultiByte - v140 - - - Application - true - MultiByte - v140 - - - Application - false - true - MultiByte - v140 - - - Application - false - true - MultiByte - v140 - - - - - - - - - - - - - - - - - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - - Level4 - Disabled - ..\..;..\..\backends;%VULKAN_SDK%\include;%SDL2_DIR%\include;$(VcpkgCurrentInstalledDir)include\SDL2;%(AdditionalIncludeDirectories) - ImTextureID=ImU64;_MBCS;%(PreprocessorDefinitions) - /utf-8 %(AdditionalOptions) - - - true - %VULKAN_SDK%\lib32;%SDL2_DIR%\lib\x86;%(AdditionalLibraryDirectories) - vulkan-1.lib;SDL2.lib;SDL2main.lib;%(AdditionalDependencies) - Console - msvcrt.lib - - - - - Level4 - Disabled - ..\..;..\..\backends;%VULKAN_SDK%\include;%SDL2_DIR%\include;$(VcpkgCurrentInstalledDir)include\SDL2;%(AdditionalIncludeDirectories) - ImTextureID=ImU64;_MBCS;%(PreprocessorDefinitions) - /utf-8 %(AdditionalOptions) - - - true - %VULKAN_SDK%\lib;%SDL2_DIR%\lib\x64;%(AdditionalLibraryDirectories) - vulkan-1.lib;SDL2.lib;SDL2main.lib;%(AdditionalDependencies) - Console - msvcrt.lib - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends;%VULKAN_SDK%\include;%SDL2_DIR%\include;$(VcpkgCurrentInstalledDir)include\SDL2;%(AdditionalIncludeDirectories) - false - ImTextureID=ImU64;_MBCS;%(PreprocessorDefinitions) - /utf-8 %(AdditionalOptions) - - - true - true - true - %VULKAN_SDK%\lib32;%SDL2_DIR%\lib\x86;%(AdditionalLibraryDirectories) - vulkan-1.lib;SDL2.lib;SDL2main.lib;%(AdditionalDependencies) - Console - - - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends;%VULKAN_SDK%\include;%SDL2_DIR%\include;$(VcpkgCurrentInstalledDir)include\SDL2;%(AdditionalIncludeDirectories) - false - ImTextureID=ImU64;_MBCS;%(PreprocessorDefinitions) - /utf-8 %(AdditionalOptions) - - - true - true - true - %VULKAN_SDK%\lib;%SDL2_DIR%\lib\x64;%(AdditionalLibraryDirectories) - vulkan-1.lib;SDL2.lib;SDL2main.lib;%(AdditionalDependencies) - Console - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_vulkan/example_sdl2_vulkan.vcxproj.filters b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_vulkan/example_sdl2_vulkan.vcxproj.filters deleted file mode 100644 index ab42485..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_vulkan/example_sdl2_vulkan.vcxproj.filters +++ /dev/null @@ -1,64 +0,0 @@ - - - - - {20b90ce4-7fcb-4731-b9a0-075f875de82d} - - - {f18ab499-84e1-499f-8eff-9754361e0e52} - cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx - - - - - imgui - - - imgui - - - imgui - - - sources - - - sources - - - sources - - - imgui - - - imgui - - - - - imgui - - - imgui - - - imgui - - - sources - - - sources - - - - - - imgui - - - imgui - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_vulkan/main.cpp b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_vulkan/main.cpp deleted file mode 100644 index 7d353d4..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl2_vulkan/main.cpp +++ /dev/null @@ -1,615 +0,0 @@ -// Dear ImGui: standalone example application for SDL2 + Vulkan - -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -// Important note to the reader who wish to integrate imgui_impl_vulkan.cpp/.h in their own engine/app. -// - Common ImGui_ImplVulkan_XXX functions and structures are used to interface with imgui_impl_vulkan.cpp/.h. -// You will use those if you want to use this rendering backend in your engine/app. -// - Helper ImGui_ImplVulkanH_XXX functions and structures are only used by this example (main.cpp) and by -// the backend itself (imgui_impl_vulkan.cpp), but should PROBABLY NOT be used by your own engine/app code. -// Read comments in imgui_impl_vulkan.h. - -#include "imgui.h" -#include "imgui_impl_sdl2.h" -#include "imgui_impl_vulkan.h" -#include // printf, fprintf -#include // abort -#include -#include -#include -//#include - -//#define IMGUI_UNLIMITED_FRAME_RATE -#ifdef _DEBUG -#define IMGUI_VULKAN_DEBUG_REPORT -#endif - -// Data -static VkAllocationCallbacks* g_Allocator = nullptr; -static VkInstance g_Instance = VK_NULL_HANDLE; -static VkPhysicalDevice g_PhysicalDevice = VK_NULL_HANDLE; -static VkDevice g_Device = VK_NULL_HANDLE; -static uint32_t g_QueueFamily = (uint32_t)-1; -static VkQueue g_Queue = VK_NULL_HANDLE; -static VkDebugReportCallbackEXT g_DebugReport = VK_NULL_HANDLE; -static VkPipelineCache g_PipelineCache = VK_NULL_HANDLE; -static VkDescriptorPool g_DescriptorPool = VK_NULL_HANDLE; - -static ImGui_ImplVulkanH_Window g_MainWindowData; -static uint32_t g_MinImageCount = 2; -static bool g_SwapChainRebuild = false; - -static void check_vk_result(VkResult err) -{ - if (err == 0) - return; - fprintf(stderr, "[vulkan] Error: VkResult = %d\n", err); - if (err < 0) - abort(); -} - -#ifdef IMGUI_VULKAN_DEBUG_REPORT -static VKAPI_ATTR VkBool32 VKAPI_CALL debug_report(VkDebugReportFlagsEXT flags, VkDebugReportObjectTypeEXT objectType, uint64_t object, size_t location, int32_t messageCode, const char* pLayerPrefix, const char* pMessage, void* pUserData) -{ - (void)flags; (void)object; (void)location; (void)messageCode; (void)pUserData; (void)pLayerPrefix; // Unused arguments - fprintf(stderr, "[vulkan] Debug report from ObjectType: %i\nMessage: %s\n\n", objectType, pMessage); - return VK_FALSE; -} -#endif // IMGUI_VULKAN_DEBUG_REPORT - -static bool IsExtensionAvailable(const ImVector& properties, const char* extension) -{ - for (const VkExtensionProperties& p : properties) - if (strcmp(p.extensionName, extension) == 0) - return true; - return false; -} - -static VkPhysicalDevice SetupVulkan_SelectPhysicalDevice() -{ - uint32_t gpu_count; - VkResult err = vkEnumeratePhysicalDevices(g_Instance, &gpu_count, nullptr); - check_vk_result(err); - IM_ASSERT(gpu_count > 0); - - ImVector gpus; - gpus.resize(gpu_count); - err = vkEnumeratePhysicalDevices(g_Instance, &gpu_count, gpus.Data); - check_vk_result(err); - - // If a number >1 of GPUs got reported, find discrete GPU if present, or use first one available. This covers - // most common cases (multi-gpu/integrated+dedicated graphics). Handling more complicated setups (multiple - // dedicated GPUs) is out of scope of this sample. - for (VkPhysicalDevice& device : gpus) - { - VkPhysicalDeviceProperties properties; - vkGetPhysicalDeviceProperties(device, &properties); - if (properties.deviceType == VK_PHYSICAL_DEVICE_TYPE_DISCRETE_GPU) - return device; - } - - // Use first GPU (Integrated) is a Discrete one is not available. - if (gpu_count > 0) - return gpus[0]; - return VK_NULL_HANDLE; -} - -static void SetupVulkan(ImVector instance_extensions) -{ - VkResult err; - - // Create Vulkan Instance - { - VkInstanceCreateInfo create_info = {}; - create_info.sType = VK_STRUCTURE_TYPE_INSTANCE_CREATE_INFO; - - // Enumerate available extensions - uint32_t properties_count; - ImVector properties; - vkEnumerateInstanceExtensionProperties(nullptr, &properties_count, nullptr); - properties.resize(properties_count); - err = vkEnumerateInstanceExtensionProperties(nullptr, &properties_count, properties.Data); - check_vk_result(err); - - // Enable required extensions - if (IsExtensionAvailable(properties, VK_KHR_GET_PHYSICAL_DEVICE_PROPERTIES_2_EXTENSION_NAME)) - instance_extensions.push_back(VK_KHR_GET_PHYSICAL_DEVICE_PROPERTIES_2_EXTENSION_NAME); -#ifdef VK_KHR_PORTABILITY_ENUMERATION_EXTENSION_NAME - if (IsExtensionAvailable(properties, VK_KHR_PORTABILITY_ENUMERATION_EXTENSION_NAME)) - { - instance_extensions.push_back(VK_KHR_PORTABILITY_ENUMERATION_EXTENSION_NAME); - create_info.flags |= VK_INSTANCE_CREATE_ENUMERATE_PORTABILITY_BIT_KHR; - } -#endif - - // Enabling validation layers -#ifdef IMGUI_VULKAN_DEBUG_REPORT - const char* layers[] = { "VK_LAYER_KHRONOS_validation" }; - create_info.enabledLayerCount = 1; - create_info.ppEnabledLayerNames = layers; - instance_extensions.push_back("VK_EXT_debug_report"); -#endif - - // Create Vulkan Instance - create_info.enabledExtensionCount = (uint32_t)instance_extensions.Size; - create_info.ppEnabledExtensionNames = instance_extensions.Data; - err = vkCreateInstance(&create_info, g_Allocator, &g_Instance); - check_vk_result(err); - - // Setup the debug report callback -#ifdef IMGUI_VULKAN_DEBUG_REPORT - auto vkCreateDebugReportCallbackEXT = (PFN_vkCreateDebugReportCallbackEXT)vkGetInstanceProcAddr(g_Instance, "vkCreateDebugReportCallbackEXT"); - IM_ASSERT(vkCreateDebugReportCallbackEXT != nullptr); - VkDebugReportCallbackCreateInfoEXT debug_report_ci = {}; - debug_report_ci.sType = VK_STRUCTURE_TYPE_DEBUG_REPORT_CALLBACK_CREATE_INFO_EXT; - debug_report_ci.flags = VK_DEBUG_REPORT_ERROR_BIT_EXT | VK_DEBUG_REPORT_WARNING_BIT_EXT | VK_DEBUG_REPORT_PERFORMANCE_WARNING_BIT_EXT; - debug_report_ci.pfnCallback = debug_report; - debug_report_ci.pUserData = nullptr; - err = vkCreateDebugReportCallbackEXT(g_Instance, &debug_report_ci, g_Allocator, &g_DebugReport); - check_vk_result(err); -#endif - } - - // Select Physical Device (GPU) - g_PhysicalDevice = SetupVulkan_SelectPhysicalDevice(); - - // Select graphics queue family - { - uint32_t count; - vkGetPhysicalDeviceQueueFamilyProperties(g_PhysicalDevice, &count, nullptr); - VkQueueFamilyProperties* queues = (VkQueueFamilyProperties*)malloc(sizeof(VkQueueFamilyProperties) * count); - vkGetPhysicalDeviceQueueFamilyProperties(g_PhysicalDevice, &count, queues); - for (uint32_t i = 0; i < count; i++) - if (queues[i].queueFlags & VK_QUEUE_GRAPHICS_BIT) - { - g_QueueFamily = i; - break; - } - free(queues); - IM_ASSERT(g_QueueFamily != (uint32_t)-1); - } - - // Create Logical Device (with 1 queue) - { - ImVector device_extensions; - device_extensions.push_back("VK_KHR_swapchain"); - - // Enumerate physical device extension - uint32_t properties_count; - ImVector properties; - vkEnumerateDeviceExtensionProperties(g_PhysicalDevice, nullptr, &properties_count, nullptr); - properties.resize(properties_count); - vkEnumerateDeviceExtensionProperties(g_PhysicalDevice, nullptr, &properties_count, properties.Data); -#ifdef VK_KHR_PORTABILITY_SUBSET_EXTENSION_NAME - if (IsExtensionAvailable(properties, VK_KHR_PORTABILITY_SUBSET_EXTENSION_NAME)) - device_extensions.push_back(VK_KHR_PORTABILITY_SUBSET_EXTENSION_NAME); -#endif - - const float queue_priority[] = { 1.0f }; - VkDeviceQueueCreateInfo queue_info[1] = {}; - queue_info[0].sType = VK_STRUCTURE_TYPE_DEVICE_QUEUE_CREATE_INFO; - queue_info[0].queueFamilyIndex = g_QueueFamily; - queue_info[0].queueCount = 1; - queue_info[0].pQueuePriorities = queue_priority; - VkDeviceCreateInfo create_info = {}; - create_info.sType = VK_STRUCTURE_TYPE_DEVICE_CREATE_INFO; - create_info.queueCreateInfoCount = sizeof(queue_info) / sizeof(queue_info[0]); - create_info.pQueueCreateInfos = queue_info; - create_info.enabledExtensionCount = (uint32_t)device_extensions.Size; - create_info.ppEnabledExtensionNames = device_extensions.Data; - err = vkCreateDevice(g_PhysicalDevice, &create_info, g_Allocator, &g_Device); - check_vk_result(err); - vkGetDeviceQueue(g_Device, g_QueueFamily, 0, &g_Queue); - } - - // Create Descriptor Pool - // The example only requires a single combined image sampler descriptor for the font image and only uses one descriptor set (for that) - // If you wish to load e.g. additional textures you may need to alter pools sizes. - { - VkDescriptorPoolSize pool_sizes[] = - { - { VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER, 1 }, - }; - VkDescriptorPoolCreateInfo pool_info = {}; - pool_info.sType = VK_STRUCTURE_TYPE_DESCRIPTOR_POOL_CREATE_INFO; - pool_info.flags = VK_DESCRIPTOR_POOL_CREATE_FREE_DESCRIPTOR_SET_BIT; - pool_info.maxSets = 1; - pool_info.poolSizeCount = (uint32_t)IM_ARRAYSIZE(pool_sizes); - pool_info.pPoolSizes = pool_sizes; - err = vkCreateDescriptorPool(g_Device, &pool_info, g_Allocator, &g_DescriptorPool); - check_vk_result(err); - } -} - -// All the ImGui_ImplVulkanH_XXX structures/functions are optional helpers used by the demo. -// Your real engine/app may not use them. -static void SetupVulkanWindow(ImGui_ImplVulkanH_Window* wd, VkSurfaceKHR surface, int width, int height) -{ - wd->Surface = surface; - - // Check for WSI support - VkBool32 res; - vkGetPhysicalDeviceSurfaceSupportKHR(g_PhysicalDevice, g_QueueFamily, wd->Surface, &res); - if (res != VK_TRUE) - { - fprintf(stderr, "Error no WSI support on physical device 0\n"); - exit(-1); - } - - // Select Surface Format - const VkFormat requestSurfaceImageFormat[] = { VK_FORMAT_B8G8R8A8_UNORM, VK_FORMAT_R8G8B8A8_UNORM, VK_FORMAT_B8G8R8_UNORM, VK_FORMAT_R8G8B8_UNORM }; - const VkColorSpaceKHR requestSurfaceColorSpace = VK_COLORSPACE_SRGB_NONLINEAR_KHR; - wd->SurfaceFormat = ImGui_ImplVulkanH_SelectSurfaceFormat(g_PhysicalDevice, wd->Surface, requestSurfaceImageFormat, (size_t)IM_ARRAYSIZE(requestSurfaceImageFormat), requestSurfaceColorSpace); - - // Select Present Mode -#ifdef IMGUI_UNLIMITED_FRAME_RATE - VkPresentModeKHR present_modes[] = { VK_PRESENT_MODE_MAILBOX_KHR, VK_PRESENT_MODE_IMMEDIATE_KHR, VK_PRESENT_MODE_FIFO_KHR }; -#else - VkPresentModeKHR present_modes[] = { VK_PRESENT_MODE_FIFO_KHR }; -#endif - wd->PresentMode = ImGui_ImplVulkanH_SelectPresentMode(g_PhysicalDevice, wd->Surface, &present_modes[0], IM_ARRAYSIZE(present_modes)); - //printf("[vulkan] Selected PresentMode = %d\n", wd->PresentMode); - - // Create SwapChain, RenderPass, Framebuffer, etc. - IM_ASSERT(g_MinImageCount >= 2); - ImGui_ImplVulkanH_CreateOrResizeWindow(g_Instance, g_PhysicalDevice, g_Device, wd, g_QueueFamily, g_Allocator, width, height, g_MinImageCount); -} - -static void CleanupVulkan() -{ - vkDestroyDescriptorPool(g_Device, g_DescriptorPool, g_Allocator); - -#ifdef IMGUI_VULKAN_DEBUG_REPORT - // Remove the debug report callback - auto vkDestroyDebugReportCallbackEXT = (PFN_vkDestroyDebugReportCallbackEXT)vkGetInstanceProcAddr(g_Instance, "vkDestroyDebugReportCallbackEXT"); - vkDestroyDebugReportCallbackEXT(g_Instance, g_DebugReport, g_Allocator); -#endif // IMGUI_VULKAN_DEBUG_REPORT - - vkDestroyDevice(g_Device, g_Allocator); - vkDestroyInstance(g_Instance, g_Allocator); -} - -static void CleanupVulkanWindow() -{ - ImGui_ImplVulkanH_DestroyWindow(g_Instance, g_Device, &g_MainWindowData, g_Allocator); -} - -static void FrameRender(ImGui_ImplVulkanH_Window* wd, ImDrawData* draw_data) -{ - VkResult err; - - VkSemaphore image_acquired_semaphore = wd->FrameSemaphores[wd->SemaphoreIndex].ImageAcquiredSemaphore; - VkSemaphore render_complete_semaphore = wd->FrameSemaphores[wd->SemaphoreIndex].RenderCompleteSemaphore; - err = vkAcquireNextImageKHR(g_Device, wd->Swapchain, UINT64_MAX, image_acquired_semaphore, VK_NULL_HANDLE, &wd->FrameIndex); - if (err == VK_ERROR_OUT_OF_DATE_KHR || err == VK_SUBOPTIMAL_KHR) - { - g_SwapChainRebuild = true; - return; - } - check_vk_result(err); - - ImGui_ImplVulkanH_Frame* fd = &wd->Frames[wd->FrameIndex]; - { - err = vkWaitForFences(g_Device, 1, &fd->Fence, VK_TRUE, UINT64_MAX); // wait indefinitely instead of periodically checking - check_vk_result(err); - - err = vkResetFences(g_Device, 1, &fd->Fence); - check_vk_result(err); - } - { - err = vkResetCommandPool(g_Device, fd->CommandPool, 0); - check_vk_result(err); - VkCommandBufferBeginInfo info = {}; - info.sType = VK_STRUCTURE_TYPE_COMMAND_BUFFER_BEGIN_INFO; - info.flags |= VK_COMMAND_BUFFER_USAGE_ONE_TIME_SUBMIT_BIT; - err = vkBeginCommandBuffer(fd->CommandBuffer, &info); - check_vk_result(err); - } - { - VkRenderPassBeginInfo info = {}; - info.sType = VK_STRUCTURE_TYPE_RENDER_PASS_BEGIN_INFO; - info.renderPass = wd->RenderPass; - info.framebuffer = fd->Framebuffer; - info.renderArea.extent.width = wd->Width; - info.renderArea.extent.height = wd->Height; - info.clearValueCount = 1; - info.pClearValues = &wd->ClearValue; - vkCmdBeginRenderPass(fd->CommandBuffer, &info, VK_SUBPASS_CONTENTS_INLINE); - } - - // Record dear imgui primitives into command buffer - ImGui_ImplVulkan_RenderDrawData(draw_data, fd->CommandBuffer); - - // Submit command buffer - vkCmdEndRenderPass(fd->CommandBuffer); - { - VkPipelineStageFlags wait_stage = VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT; - VkSubmitInfo info = {}; - info.sType = VK_STRUCTURE_TYPE_SUBMIT_INFO; - info.waitSemaphoreCount = 1; - info.pWaitSemaphores = &image_acquired_semaphore; - info.pWaitDstStageMask = &wait_stage; - info.commandBufferCount = 1; - info.pCommandBuffers = &fd->CommandBuffer; - info.signalSemaphoreCount = 1; - info.pSignalSemaphores = &render_complete_semaphore; - - err = vkEndCommandBuffer(fd->CommandBuffer); - check_vk_result(err); - err = vkQueueSubmit(g_Queue, 1, &info, fd->Fence); - check_vk_result(err); - } -} - -static void FramePresent(ImGui_ImplVulkanH_Window* wd) -{ - if (g_SwapChainRebuild) - return; - VkSemaphore render_complete_semaphore = wd->FrameSemaphores[wd->SemaphoreIndex].RenderCompleteSemaphore; - VkPresentInfoKHR info = {}; - info.sType = VK_STRUCTURE_TYPE_PRESENT_INFO_KHR; - info.waitSemaphoreCount = 1; - info.pWaitSemaphores = &render_complete_semaphore; - info.swapchainCount = 1; - info.pSwapchains = &wd->Swapchain; - info.pImageIndices = &wd->FrameIndex; - VkResult err = vkQueuePresentKHR(g_Queue, &info); - if (err == VK_ERROR_OUT_OF_DATE_KHR || err == VK_SUBOPTIMAL_KHR) - { - g_SwapChainRebuild = true; - return; - } - check_vk_result(err); - wd->SemaphoreIndex = (wd->SemaphoreIndex + 1) % wd->ImageCount; // Now we can use the next set of semaphores -} - -// Main code -int main(int, char**) -{ - // Setup SDL - if (SDL_Init(SDL_INIT_VIDEO | SDL_INIT_TIMER | SDL_INIT_GAMECONTROLLER) != 0) - { - printf("Error: %s\n", SDL_GetError()); - return -1; - } - - // From 2.0.18: Enable native IME. -#ifdef SDL_HINT_IME_SHOW_UI - SDL_SetHint(SDL_HINT_IME_SHOW_UI, "1"); -#endif - - // Create window with Vulkan graphics context - SDL_WindowFlags window_flags = (SDL_WindowFlags)(SDL_WINDOW_VULKAN | SDL_WINDOW_RESIZABLE | SDL_WINDOW_ALLOW_HIGHDPI); - SDL_Window* window = SDL_CreateWindow("Dear ImGui SDL2+Vulkan example", SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED, 1280, 720, window_flags); - - ImVector extensions; - uint32_t extensions_count = 0; - SDL_Vulkan_GetInstanceExtensions(window, &extensions_count, nullptr); - extensions.resize(extensions_count); - SDL_Vulkan_GetInstanceExtensions(window, &extensions_count, extensions.Data); - SetupVulkan(extensions); - - // Create Window Surface - VkSurfaceKHR surface; - VkResult err; - if (SDL_Vulkan_CreateSurface(window, g_Instance, &surface) == 0) - { - printf("Failed to create Vulkan surface.\n"); - return 1; - } - - // Create Framebuffers - int w, h; - SDL_GetWindowSize(window, &w, &h); - ImGui_ImplVulkanH_Window* wd = &g_MainWindowData; - SetupVulkanWindow(wd, surface, w, h); - - // Setup Dear ImGui context - IMGUI_CHECKVERSION(); - ImGui::CreateContext(); - ImGuiIO& io = ImGui::GetIO(); (void)io; - io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard; // Enable Keyboard Controls - io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad; // Enable Gamepad Controls - io.ConfigFlags |= ImGuiConfigFlags_DockingEnable; // Enable Docking - io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable; // Enable Multi-Viewport / Platform Windows - //io.ConfigFlags |= ImGuiConfigFlags_ViewportsNoTaskBarIcons; - //io.ConfigFlags |= ImGuiConfigFlags_ViewportsNoMerge; - - // Setup Dear ImGui style - ImGui::StyleColorsDark(); - //ImGui::StyleColorsLight(); - - // When viewports are enabled we tweak WindowRounding/WindowBg so platform windows can look identical to regular ones. - ImGuiStyle& style = ImGui::GetStyle(); - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - style.WindowRounding = 0.0f; - style.Colors[ImGuiCol_WindowBg].w = 1.0f; - } - - // Setup Platform/Renderer backends - ImGui_ImplSDL2_InitForVulkan(window); - ImGui_ImplVulkan_InitInfo init_info = {}; - init_info.Instance = g_Instance; - init_info.PhysicalDevice = g_PhysicalDevice; - init_info.Device = g_Device; - init_info.QueueFamily = g_QueueFamily; - init_info.Queue = g_Queue; - init_info.PipelineCache = g_PipelineCache; - init_info.DescriptorPool = g_DescriptorPool; - init_info.Subpass = 0; - init_info.MinImageCount = g_MinImageCount; - init_info.ImageCount = wd->ImageCount; - init_info.MSAASamples = VK_SAMPLE_COUNT_1_BIT; - init_info.Allocator = g_Allocator; - init_info.CheckVkResultFn = check_vk_result; - ImGui_ImplVulkan_Init(&init_info, wd->RenderPass); - - // Load Fonts - // - If no fonts are loaded, dear imgui will use the default font. You can also load multiple fonts and use ImGui::PushFont()/PopFont() to select them. - // - AddFontFromFileTTF() will return the ImFont* so you can store it if you need to select the font among multiple. - // - If the file cannot be loaded, the function will return a nullptr. Please handle those errors in your application (e.g. use an assertion, or display an error and quit). - // - The fonts will be rasterized at a given size (w/ oversampling) and stored into a texture when calling ImFontAtlas::Build()/GetTexDataAsXXXX(), which ImGui_ImplXXXX_NewFrame below will call. - // - Use '#define IMGUI_ENABLE_FREETYPE' in your imconfig file to use Freetype for higher quality font rendering. - // - Read 'docs/FONTS.md' for more instructions and details. - // - Remember that in C/C++ if you want to include a backslash \ in a string literal you need to write a double backslash \\ ! - //io.Fonts->AddFontDefault(); - //io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\segoeui.ttf", 18.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/DroidSans.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Roboto-Medium.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Cousine-Regular.ttf", 15.0f); - //ImFont* font = io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\ArialUni.ttf", 18.0f, nullptr, io.Fonts->GetGlyphRangesJapanese()); - //IM_ASSERT(font != nullptr); - - // Upload Fonts - { - // Use any command queue - VkCommandPool command_pool = wd->Frames[wd->FrameIndex].CommandPool; - VkCommandBuffer command_buffer = wd->Frames[wd->FrameIndex].CommandBuffer; - - err = vkResetCommandPool(g_Device, command_pool, 0); - check_vk_result(err); - VkCommandBufferBeginInfo begin_info = {}; - begin_info.sType = VK_STRUCTURE_TYPE_COMMAND_BUFFER_BEGIN_INFO; - begin_info.flags |= VK_COMMAND_BUFFER_USAGE_ONE_TIME_SUBMIT_BIT; - err = vkBeginCommandBuffer(command_buffer, &begin_info); - check_vk_result(err); - - ImGui_ImplVulkan_CreateFontsTexture(command_buffer); - - VkSubmitInfo end_info = {}; - end_info.sType = VK_STRUCTURE_TYPE_SUBMIT_INFO; - end_info.commandBufferCount = 1; - end_info.pCommandBuffers = &command_buffer; - err = vkEndCommandBuffer(command_buffer); - check_vk_result(err); - err = vkQueueSubmit(g_Queue, 1, &end_info, VK_NULL_HANDLE); - check_vk_result(err); - - err = vkDeviceWaitIdle(g_Device); - check_vk_result(err); - ImGui_ImplVulkan_DestroyFontUploadObjects(); - } - - // Our state - bool show_demo_window = true; - bool show_another_window = false; - ImVec4 clear_color = ImVec4(0.45f, 0.55f, 0.60f, 1.00f); - - // Main loop - bool done = false; - while (!done) - { - // Poll and handle events (inputs, window resize, etc.) - // You can read the io.WantCaptureMouse, io.WantCaptureKeyboard flags to tell if dear imgui wants to use your inputs. - // - When io.WantCaptureMouse is true, do not dispatch mouse input data to your main application, or clear/overwrite your copy of the mouse data. - // - When io.WantCaptureKeyboard is true, do not dispatch keyboard input data to your main application, or clear/overwrite your copy of the keyboard data. - // Generally you may always pass all inputs to dear imgui, and hide them from your application based on those two flags. - SDL_Event event; - while (SDL_PollEvent(&event)) - { - ImGui_ImplSDL2_ProcessEvent(&event); - if (event.type == SDL_QUIT) - done = true; - if (event.type == SDL_WINDOWEVENT && event.window.event == SDL_WINDOWEVENT_CLOSE && event.window.windowID == SDL_GetWindowID(window)) - done = true; - } - - // Resize swap chain? - if (g_SwapChainRebuild) - { - int width, height; - SDL_GetWindowSize(window, &width, &height); - if (width > 0 && height > 0) - { - ImGui_ImplVulkan_SetMinImageCount(g_MinImageCount); - ImGui_ImplVulkanH_CreateOrResizeWindow(g_Instance, g_PhysicalDevice, g_Device, &g_MainWindowData, g_QueueFamily, g_Allocator, width, height, g_MinImageCount); - g_MainWindowData.FrameIndex = 0; - g_SwapChainRebuild = false; - } - } - - // Start the Dear ImGui frame - ImGui_ImplVulkan_NewFrame(); - ImGui_ImplSDL2_NewFrame(); - ImGui::NewFrame(); - - // 1. Show the big demo window (Most of the sample code is in ImGui::ShowDemoWindow()! You can browse its code to learn more about Dear ImGui!). - if (show_demo_window) - ImGui::ShowDemoWindow(&show_demo_window); - - // 2. Show a simple window that we create ourselves. We use a Begin/End pair to create a named window. - { - static float f = 0.0f; - static int counter = 0; - - ImGui::Begin("Hello, world!"); // Create a window called "Hello, world!" and append into it. - - ImGui::Text("This is some useful text."); // Display some text (you can use a format strings too) - ImGui::Checkbox("Demo Window", &show_demo_window); // Edit bools storing our window open/close state - ImGui::Checkbox("Another Window", &show_another_window); - - ImGui::SliderFloat("float", &f, 0.0f, 1.0f); // Edit 1 float using a slider from 0.0f to 1.0f - ImGui::ColorEdit3("clear color", (float*)&clear_color); // Edit 3 floats representing a color - - if (ImGui::Button("Button")) // Buttons return true when clicked (most widgets return true when edited/activated) - counter++; - ImGui::SameLine(); - ImGui::Text("counter = %d", counter); - - ImGui::Text("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / io.Framerate, io.Framerate); - ImGui::End(); - } - - // 3. Show another simple window. - if (show_another_window) - { - ImGui::Begin("Another Window", &show_another_window); // Pass a pointer to our bool variable (the window will have a closing button that will clear the bool when clicked) - ImGui::Text("Hello from another window!"); - if (ImGui::Button("Close Me")) - show_another_window = false; - ImGui::End(); - } - - // Rendering - ImGui::Render(); - ImDrawData* main_draw_data = ImGui::GetDrawData(); - const bool main_is_minimized = (main_draw_data->DisplaySize.x <= 0.0f || main_draw_data->DisplaySize.y <= 0.0f); - wd->ClearValue.color.float32[0] = clear_color.x * clear_color.w; - wd->ClearValue.color.float32[1] = clear_color.y * clear_color.w; - wd->ClearValue.color.float32[2] = clear_color.z * clear_color.w; - wd->ClearValue.color.float32[3] = clear_color.w; - if (!main_is_minimized) - FrameRender(wd, main_draw_data); - - // Update and Render additional Platform Windows - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - ImGui::UpdatePlatformWindows(); - ImGui::RenderPlatformWindowsDefault(); - } - - // Present Main Platform Window - if (!main_is_minimized) - FramePresent(wd); - } - - // Cleanup - err = vkDeviceWaitIdle(g_Device); - check_vk_result(err); - ImGui_ImplVulkan_Shutdown(); - ImGui_ImplSDL2_Shutdown(); - ImGui::DestroyContext(); - - CleanupVulkanWindow(); - CleanupVulkan(); - - SDL_DestroyWindow(window); - SDL_Quit(); - - return 0; -} diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_opengl3/Makefile b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_opengl3/Makefile deleted file mode 100644 index 3a00a31..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_opengl3/Makefile +++ /dev/null @@ -1,84 +0,0 @@ -# -# Cross Platform Makefile -# Compatible with MSYS2/MINGW, Ubuntu 14.04.1 and Mac OS X -# -# You will need SDL3 (http://www.libsdl.org) which is still unreleased/unpackaged. - -#CXX = g++ -#CXX = clang++ - -EXE = example_sdl3_opengl3 -IMGUI_DIR = ../.. -SOURCES = main.cpp -SOURCES += $(IMGUI_DIR)/imgui.cpp $(IMGUI_DIR)/imgui_demo.cpp $(IMGUI_DIR)/imgui_draw.cpp $(IMGUI_DIR)/imgui_tables.cpp $(IMGUI_DIR)/imgui_widgets.cpp -SOURCES += $(IMGUI_DIR)/backends/imgui_impl_sdl3.cpp $(IMGUI_DIR)/backends/imgui_impl_opengl3.cpp -OBJS = $(addsuffix .o, $(basename $(notdir $(SOURCES)))) -UNAME_S := $(shell uname -s) -LINUX_GL_LIBS = -lGL - -CXXFLAGS = -std=c++11 -I$(IMGUI_DIR) -I$(IMGUI_DIR)/backends -CXXFLAGS += -g -Wall -Wformat -LIBS = - -##--------------------------------------------------------------------- -## OPENGL ES -##--------------------------------------------------------------------- - -## This assumes a GL ES library available in the system, e.g. libGLESv2.so -# CXXFLAGS += -DIMGUI_IMPL_OPENGL_ES2 -# LINUX_GL_LIBS = -lGLESv2 -## If you're on a Raspberry Pi and want to use the legacy drivers, -## use the following instead: -# LINUX_GL_LIBS = -L/opt/vc/lib -lbrcmGLESv2 - -##--------------------------------------------------------------------- -## BUILD FLAGS PER PLATFORM -##--------------------------------------------------------------------- - -ifeq ($(UNAME_S), Linux) #LINUX - ECHO_MESSAGE = "Linux" - LIBS += $(LINUX_GL_LIBS) -ldl `sdl3-config --libs` - - CXXFLAGS += `sdl3-config --cflags` - CFLAGS = $(CXXFLAGS) -endif - -ifeq ($(UNAME_S), Darwin) #APPLE - ECHO_MESSAGE = "Mac OS X" - LIBS += -framework OpenGL -framework Cocoa -framework IOKit -framework CoreVideo `sdl3-config --libs` - LIBS += -L/usr/local/lib -L/opt/local/lib - - CXXFLAGS += `sdl3-config --cflags` - CXXFLAGS += -I/usr/local/include -I/opt/local/include - CFLAGS = $(CXXFLAGS) -endif - -ifeq ($(OS), Windows_NT) - ECHO_MESSAGE = "MinGW" - LIBS += -lgdi32 -lopengl32 -limm32 `pkg-config --static --libs sdl3` - - CXXFLAGS += `pkg-config --cflags sdl3` - CFLAGS = $(CXXFLAGS) -endif - -##--------------------------------------------------------------------- -## BUILD RULES -##--------------------------------------------------------------------- - -%.o:%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/backends/%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -all: $(EXE) - @echo Build complete for $(ECHO_MESSAGE) - -$(EXE): $(OBJS) - $(CXX) -o $@ $^ $(CXXFLAGS) $(LIBS) - -clean: - rm -f $(EXE) $(OBJS) diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_opengl3/Makefile.emscripten b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_opengl3/Makefile.emscripten deleted file mode 100644 index 9e9ffd6..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_opengl3/Makefile.emscripten +++ /dev/null @@ -1,96 +0,0 @@ - -# IMPORTANT: SDL3 IS IN DEVELOPMENT, AS OF 2023-05-30, EMSCRIPTEN DOESN'T SUPPORT SDL3 YET. -# WE ARE LEAVING THIS MAKEFILE AROUND FOR THE DAY IT WILL SUPPORT IT. - -# -# Makefile to use with SDL+emscripten -# See https://emscripten.org/docs/getting_started/downloads.html -# for installation instructions. -# -# This Makefile assumes you have loaded emscripten's environment. -# (On Windows, you may need to execute emsdk_env.bat or encmdprompt.bat ahead) -# -# Running `make -f Makefile.emscripten` will produce three files: -# - web/index.html -# - web/index.js -# - web/index.wasm -# -# All three are needed to run the demo. - -CC = emcc -CXX = em++ -WEB_DIR = web -EXE = $(WEB_DIR)/index.html -IMGUI_DIR = ../.. -SOURCES = main.cpp -SOURCES += $(IMGUI_DIR)/imgui.cpp $(IMGUI_DIR)/imgui_demo.cpp $(IMGUI_DIR)/imgui_draw.cpp $(IMGUI_DIR)/imgui_tables.cpp $(IMGUI_DIR)/imgui_widgets.cpp -SOURCES += $(IMGUI_DIR)/backends/imgui_impl_sdl3.cpp $(IMGUI_DIR)/backends/imgui_impl_opengl3.cpp -OBJS = $(addsuffix .o, $(basename $(notdir $(SOURCES)))) -UNAME_S := $(shell uname -s) -CPPFLAGS = -LDFLAGS = -EMS = - -##--------------------------------------------------------------------- -## EMSCRIPTEN OPTIONS -##--------------------------------------------------------------------- - -# ("EMS" options gets added to both CPPFLAGS and LDFLAGS, whereas some options are for linker only) -EMS += -s USE_SDL=2 -EMS += -s DISABLE_EXCEPTION_CATCHING=1 -LDFLAGS += -s WASM=1 -s ALLOW_MEMORY_GROWTH=1 -s NO_EXIT_RUNTIME=0 -s ASSERTIONS=1 - -# Uncomment next line to fix possible rendering bugs with Emscripten version older then 1.39.0 (https://github.com/ocornut/imgui/issues/2877) -#EMS += -s BINARYEN_TRAP_MODE=clamp -#EMS += -s SAFE_HEAP=1 ## Adds overhead - -# Emscripten allows preloading a file or folder to be accessible at runtime. -# The Makefile for this example project suggests embedding the misc/fonts/ folder into our application, it will then be accessible as "/fonts" -# See documentation for more details: https://emscripten.org/docs/porting/files/packaging_files.html -# (Default value is 0. Set to 1 to enable file-system and include the misc/fonts/ folder as part of the build.) -USE_FILE_SYSTEM ?= 0 -ifeq ($(USE_FILE_SYSTEM), 0) -LDFLAGS += -s NO_FILESYSTEM=1 -CPPFLAGS += -DIMGUI_DISABLE_FILE_FUNCTIONS -endif -ifeq ($(USE_FILE_SYSTEM), 1) -LDFLAGS += --no-heap-copy --preload-file ../../misc/fonts@/fonts -endif - -##--------------------------------------------------------------------- -## FINAL BUILD FLAGS -##--------------------------------------------------------------------- - -CPPFLAGS += -I$(IMGUI_DIR) -I$(IMGUI_DIR)/backends -#CPPFLAGS += -g -CPPFLAGS += -Wall -Wformat -Os $(EMS) -LDFLAGS += --shell-file ../libs/emscripten/shell_minimal.html -LDFLAGS += $(EMS) - -##--------------------------------------------------------------------- -## BUILD RULES -##--------------------------------------------------------------------- - -%.o:%.cpp - $(CXX) $(CPPFLAGS) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/%.cpp - $(CXX) $(CPPFLAGS) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/backends/%.cpp - $(CXX) $(CPPFLAGS) $(CXXFLAGS) -c -o $@ $< - -all: $(EXE) - @echo Build complete for $(EXE) - -$(WEB_DIR): - mkdir $@ - -serve: all - python3 -m http.server -d $(WEB_DIR) - -$(EXE): $(OBJS) $(WEB_DIR) - $(CXX) -o $@ $(OBJS) $(LDFLAGS) - -clean: - rm -rf $(OBJS) $(WEB_DIR) diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_opengl3/README.md b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_opengl3/README.md deleted file mode 100644 index 5828e4b..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_opengl3/README.md +++ /dev/null @@ -1,40 +0,0 @@ - -# How to Build - -## Windows with Visual Studio's IDE - -Use the provided project file (.vcxproj). Add to solution (imgui_examples.sln) if necessary. - -## Windows with Visual Studio's CLI - -Use build_win32.bat or directly: -``` -set SDL2_DIR=path_to_your_sdl3_folder -cl /Zi /MD /utf-8 /I.. /I..\.. /I%SDL2_DIR%\include main.cpp ..\..\backends\imgui_impl_sdl3.cpp ..\..\backends\imgui_impl_opengl3.cpp ..\..\imgui*.cpp /FeDebug/example_sdl3_opengl3.exe /FoDebug/ /link /libpath:%SDL2_DIR%\lib\x86 SDL3.lib opengl32.lib /subsystem:console -# ^^ include paths ^^ source files ^^ output exe ^^ output dir ^^ libraries -# or for 64-bit: -cl /Zi /MD /utf-8 /I.. /I..\.. /I%SDL2_DIR%\include main.cpp ..\..\backends\imgui_impl_sdl3.cpp ..\..\backends\imgui_impl_opengl3.cpp ..\..\imgui*.cpp /FeDebug/example_sdl3_opengl3.exe /FoDebug/ /link /libpath:%SDL2_DIR%\lib\x64 SDL3.lib SDL2mainopengl32.lib /subsystem:console -``` - -## Linux and similar Unixes - -Use our Makefile or directly: -``` -c++ `sdl3-config --cflags` -I .. -I ../.. -I ../../backends - main.cpp ../../backends/imgui_impl_sdl3.cpp ../../backends/imgui_impl_opengl3.cpp ../../imgui*.cpp - `sdl3-config --libs` -lGL -ldl -``` - -## macOS - -Use our Makefile or directly: -``` -brew install sdl3 -c++ `sdl3-config --cflags` -I .. -I ../.. -I ../../backends - main.cpp ../../backends/imgui_impl_sdl3.cpp ../../backends/imgui_impl_opengl3.cpp ../../imgui*.cpp - `sdl3-config --libs` -framework OpenGl -framework CoreFoundation -``` - -## Emscripten - -As of 2023-05-30 Emscripten doesn't support SDL3 yet. diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_opengl3/build_win32.bat b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_opengl3/build_win32.bat deleted file mode 100644 index 5b8d5f8..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_opengl3/build_win32.bat +++ /dev/null @@ -1,8 +0,0 @@ -@REM Build for Visual Studio compiler. Run your copy of vcvars32.bat or vcvarsall.bat to setup command-line compiler. -@set OUT_DIR=Debug -@set OUT_EXE=example_sdl3_opengl3 -@set INCLUDES=/I..\.. /I..\..\backends /I%SDL3_DIR%\include -@set SOURCES=main.cpp ..\..\backends\imgui_impl_sdl3.cpp ..\..\backends\imgui_impl_opengl3.cpp ..\..\imgui*.cpp -@set LIBS=/LIBPATH:%SDL3_DIR%\lib\x86 SDL3.lib opengl32.lib shell32.lib -mkdir %OUT_DIR% -cl /nologo /Zi /MD /utf-8 %INCLUDES% %SOURCES% /Fe%OUT_DIR%/%OUT_EXE%.exe /Fo%OUT_DIR%/ /link %LIBS% /subsystem:console diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_opengl3/example_sdl3_opengl3.vcxproj b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_opengl3/example_sdl3_opengl3.vcxproj deleted file mode 100644 index 051f87d..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_opengl3/example_sdl3_opengl3.vcxproj +++ /dev/null @@ -1,187 +0,0 @@ - - - - - Debug - Win32 - - - Debug - x64 - - - Release - Win32 - - - Release - x64 - - - - {84AAA301-84FE-428B-9E3E-817BC8123C0C} - example_sdl3_opengl3 - 8.1 - - - - Application - true - MultiByte - v140 - - - Application - true - MultiByte - v140 - - - Application - false - true - MultiByte - v140 - - - Application - false - true - MultiByte - v140 - - - - - - - - - - - - - - - - - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - - Level4 - Disabled - ..\..;..\..\backends;%SDL3_DIR%\include;$(VcpkgCurrentInstalledDir)include\SDL3;%(AdditionalIncludeDirectories) - /utf-8 %(AdditionalOptions) - - - true - %SDL3_DIR%\lib\x86;%(AdditionalLibraryDirectories) - opengl32.lib;SDL3.lib;%(AdditionalDependencies) - Console - msvcrt.lib - - - - - Level4 - Disabled - ..\..;..\..\backends;%SDL3_DIR%\include;$(VcpkgCurrentInstalledDir)include\SDL3;%(AdditionalIncludeDirectories) - /utf-8 %(AdditionalOptions) - - - true - %SDL3_DIR%\lib\x64;%(AdditionalLibraryDirectories) - opengl32.lib;SDL3.lib;%(AdditionalDependencies) - Console - msvcrt.lib - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends;%SDL3_DIR%\include;$(VcpkgCurrentInstalledDir)include\SDL3;%(AdditionalIncludeDirectories) - false - /utf-8 %(AdditionalOptions) - - - true - true - true - %SDL3_DIR%\lib\x86;%(AdditionalLibraryDirectories) - opengl32.lib;SDL3.lib;%(AdditionalDependencies) - Console - - - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends;%SDL3_DIR%\include;$(VcpkgCurrentInstalledDir)include\SDL3;%(AdditionalIncludeDirectories) - false - /utf-8 %(AdditionalOptions) - - - true - true - true - %SDL3_DIR%\lib\x64;%(AdditionalLibraryDirectories) - opengl32.lib;SDL3.lib;%(AdditionalDependencies) - Console - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_opengl3/example_sdl3_opengl3.vcxproj.filters b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_opengl3/example_sdl3_opengl3.vcxproj.filters deleted file mode 100644 index f365473..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_opengl3/example_sdl3_opengl3.vcxproj.filters +++ /dev/null @@ -1,67 +0,0 @@ - - - - - {20b90ce4-7fcb-4731-b9a0-075f875de82d} - - - {f18ab499-84e1-499f-8eff-9754361e0e52} - cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx - - - - - imgui - - - imgui - - - imgui - - - sources - - - sources - - - sources - - - imgui - - - imgui - - - - - imgui - - - imgui - - - imgui - - - sources - - - sources - - - sources - - - - - - imgui - - - imgui - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_opengl3/main.cpp b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_opengl3/main.cpp deleted file mode 100644 index 8d1ff95..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_opengl3/main.cpp +++ /dev/null @@ -1,232 +0,0 @@ -// Dear ImGui: standalone example application for SDL3 + OpenGL -// (SDL is a cross-platform general purpose library for handling windows, inputs, OpenGL/Vulkan/Metal graphics context creation, etc.) - -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#include "imgui.h" -#include "imgui_impl_sdl3.h" -#include "imgui_impl_opengl3.h" -#include -#include -#if defined(IMGUI_IMPL_OPENGL_ES2) -#include -#else -#include -#endif - -// This example doesn't compile with Emscripten yet! Awaiting SDL3 support. -#ifdef __EMSCRIPTEN__ -#include "../libs/emscripten/emscripten_mainloop_stub.h" -#endif - -// Main code -int main(int, char**) -{ - // Setup SDL - if (SDL_Init(SDL_INIT_VIDEO | SDL_INIT_TIMER | SDL_INIT_GAMEPAD) != 0) - { - printf("Error: SDL_Init(): %s\n", SDL_GetError()); - return -1; - } - - // Decide GL+GLSL versions -#if defined(IMGUI_IMPL_OPENGL_ES2) - // GL ES 2.0 + GLSL 100 - const char* glsl_version = "#version 100"; - SDL_GL_SetAttribute(SDL_GL_CONTEXT_FLAGS, 0); - SDL_GL_SetAttribute(SDL_GL_CONTEXT_PROFILE_MASK, SDL_GL_CONTEXT_PROFILE_ES); - SDL_GL_SetAttribute(SDL_GL_CONTEXT_MAJOR_VERSION, 2); - SDL_GL_SetAttribute(SDL_GL_CONTEXT_MINOR_VERSION, 0); -#elif defined(__APPLE__) - // GL 3.2 Core + GLSL 150 - const char* glsl_version = "#version 150"; - SDL_GL_SetAttribute(SDL_GL_CONTEXT_FLAGS, SDL_GL_CONTEXT_FORWARD_COMPATIBLE_FLAG); // Always required on Mac - SDL_GL_SetAttribute(SDL_GL_CONTEXT_PROFILE_MASK, SDL_GL_CONTEXT_PROFILE_CORE); - SDL_GL_SetAttribute(SDL_GL_CONTEXT_MAJOR_VERSION, 3); - SDL_GL_SetAttribute(SDL_GL_CONTEXT_MINOR_VERSION, 2); -#else - // GL 3.0 + GLSL 130 - const char* glsl_version = "#version 130"; - SDL_GL_SetAttribute(SDL_GL_CONTEXT_FLAGS, 0); - SDL_GL_SetAttribute(SDL_GL_CONTEXT_PROFILE_MASK, SDL_GL_CONTEXT_PROFILE_CORE); - SDL_GL_SetAttribute(SDL_GL_CONTEXT_MAJOR_VERSION, 3); - SDL_GL_SetAttribute(SDL_GL_CONTEXT_MINOR_VERSION, 0); -#endif - - // Enable native IME. - SDL_SetHint(SDL_HINT_IME_SHOW_UI, "1"); - - // Create window with graphics context - SDL_GL_SetAttribute(SDL_GL_DOUBLEBUFFER, 1); - SDL_GL_SetAttribute(SDL_GL_DEPTH_SIZE, 24); - SDL_GL_SetAttribute(SDL_GL_STENCIL_SIZE, 8); - SDL_WindowFlags window_flags = (SDL_WindowFlags)(SDL_WINDOW_OPENGL | SDL_WINDOW_RESIZABLE | SDL_WINDOW_HIDDEN); - SDL_Window* window = SDL_CreateWindow("Dear ImGui SDL3+OpenGL3 example", 1280, 720, window_flags); - if (window == nullptr) - { - printf("Error: SDL_CreateWindow(): %s\n", SDL_GetError()); - return -1; - } - SDL_SetWindowPosition(window, SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED); - SDL_GLContext gl_context = SDL_GL_CreateContext(window); - SDL_GL_MakeCurrent(window, gl_context); - SDL_GL_SetSwapInterval(1); // Enable vsync - SDL_ShowWindow(window); - - // Setup Dear ImGui context - IMGUI_CHECKVERSION(); - ImGui::CreateContext(); - ImGuiIO& io = ImGui::GetIO(); (void)io; - io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard; // Enable Keyboard Controls - io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad; // Enable Gamepad Controls - io.ConfigFlags |= ImGuiConfigFlags_DockingEnable; // Enable Docking - io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable; // Enable Multi-Viewport / Platform Windows - //io.ConfigViewportsNoAutoMerge = true; - //io.ConfigViewportsNoTaskBarIcon = true; - - // Setup Dear ImGui style - ImGui::StyleColorsDark(); - //ImGui::StyleColorsLight(); - - // When viewports are enabled we tweak WindowRounding/WindowBg so platform windows can look identical to regular ones. - ImGuiStyle& style = ImGui::GetStyle(); - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - style.WindowRounding = 0.0f; - style.Colors[ImGuiCol_WindowBg].w = 1.0f; - } - - // Setup Platform/Renderer backends - ImGui_ImplSDL3_InitForOpenGL(window, gl_context); - ImGui_ImplOpenGL3_Init(glsl_version); - - // Load Fonts - // - If no fonts are loaded, dear imgui will use the default font. You can also load multiple fonts and use ImGui::PushFont()/PopFont() to select them. - // - AddFontFromFileTTF() will return the ImFont* so you can store it if you need to select the font among multiple. - // - If the file cannot be loaded, the function will return a nullptr. Please handle those errors in your application (e.g. use an assertion, or display an error and quit). - // - The fonts will be rasterized at a given size (w/ oversampling) and stored into a texture when calling ImFontAtlas::Build()/GetTexDataAsXXXX(), which ImGui_ImplXXXX_NewFrame below will call. - // - Use '#define IMGUI_ENABLE_FREETYPE' in your imconfig file to use Freetype for higher quality font rendering. - // - Read 'docs/FONTS.md' for more instructions and details. - // - Remember that in C/C++ if you want to include a backslash \ in a string literal you need to write a double backslash \\ ! - // - Our Emscripten build process allows embedding fonts to be accessible at runtime from the "fonts/" folder. See Makefile.emscripten for details. - //io.Fonts->AddFontDefault(); - //io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\segoeui.ttf", 18.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/DroidSans.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Roboto-Medium.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Cousine-Regular.ttf", 15.0f); - //ImFont* font = io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\ArialUni.ttf", 18.0f, nullptr, io.Fonts->GetGlyphRangesJapanese()); - //IM_ASSERT(font != nullptr); - - // Our state - bool show_demo_window = true; - bool show_another_window = false; - ImVec4 clear_color = ImVec4(0.45f, 0.55f, 0.60f, 1.00f); - - // Main loop - bool done = false; -#ifdef __EMSCRIPTEN__ - // For an Emscripten build we are disabling file-system access, so let's not attempt to do a fopen() of the imgui.ini file. - // You may manually call LoadIniSettingsFromMemory() to load settings from your own storage. - io.IniFilename = nullptr; - EMSCRIPTEN_MAINLOOP_BEGIN -#else - while (!done) -#endif - { - // Poll and handle events (inputs, window resize, etc.) - // You can read the io.WantCaptureMouse, io.WantCaptureKeyboard flags to tell if dear imgui wants to use your inputs. - // - When io.WantCaptureMouse is true, do not dispatch mouse input data to your main application, or clear/overwrite your copy of the mouse data. - // - When io.WantCaptureKeyboard is true, do not dispatch keyboard input data to your main application, or clear/overwrite your copy of the keyboard data. - // Generally you may always pass all inputs to dear imgui, and hide them from your application based on those two flags. - SDL_Event event; - while (SDL_PollEvent(&event)) - { - ImGui_ImplSDL3_ProcessEvent(&event); - if (event.type == SDL_EVENT_QUIT) - done = true; - if (event.type == SDL_EVENT_WINDOW_CLOSE_REQUESTED && event.window.windowID == SDL_GetWindowID(window)) - done = true; - } - - // Start the Dear ImGui frame - ImGui_ImplOpenGL3_NewFrame(); - ImGui_ImplSDL3_NewFrame(); - ImGui::NewFrame(); - - // 1. Show the big demo window (Most of the sample code is in ImGui::ShowDemoWindow()! You can browse its code to learn more about Dear ImGui!). - if (show_demo_window) - ImGui::ShowDemoWindow(&show_demo_window); - - // 2. Show a simple window that we create ourselves. We use a Begin/End pair to create a named window. - { - static float f = 0.0f; - static int counter = 0; - - ImGui::Begin("Hello, world!"); // Create a window called "Hello, world!" and append into it. - - ImGui::Text("This is some useful text."); // Display some text (you can use a format strings too) - ImGui::Checkbox("Demo Window", &show_demo_window); // Edit bools storing our window open/close state - ImGui::Checkbox("Another Window", &show_another_window); - - ImGui::SliderFloat("float", &f, 0.0f, 1.0f); // Edit 1 float using a slider from 0.0f to 1.0f - ImGui::ColorEdit3("clear color", (float*)&clear_color); // Edit 3 floats representing a color - - if (ImGui::Button("Button")) // Buttons return true when clicked (most widgets return true when edited/activated) - counter++; - ImGui::SameLine(); - ImGui::Text("counter = %d", counter); - - ImGui::Text("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / io.Framerate, io.Framerate); - ImGui::End(); - } - - // 3. Show another simple window. - if (show_another_window) - { - ImGui::Begin("Another Window", &show_another_window); // Pass a pointer to our bool variable (the window will have a closing button that will clear the bool when clicked) - ImGui::Text("Hello from another window!"); - if (ImGui::Button("Close Me")) - show_another_window = false; - ImGui::End(); - } - - // Rendering - ImGui::Render(); - glViewport(0, 0, (int)io.DisplaySize.x, (int)io.DisplaySize.y); - glClearColor(clear_color.x * clear_color.w, clear_color.y * clear_color.w, clear_color.z * clear_color.w, clear_color.w); - glClear(GL_COLOR_BUFFER_BIT); - ImGui_ImplOpenGL3_RenderDrawData(ImGui::GetDrawData()); - - // Update and Render additional Platform Windows - // (Platform functions may change the current OpenGL context, so we save/restore it to make it easier to paste this code elsewhere. - // For this specific demo app we could also call SDL_GL_MakeCurrent(window, gl_context) directly) - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - SDL_Window* backup_current_window = SDL_GL_GetCurrentWindow(); - SDL_GLContext backup_current_context = SDL_GL_GetCurrentContext(); - ImGui::UpdatePlatformWindows(); - ImGui::RenderPlatformWindowsDefault(); - SDL_GL_MakeCurrent(backup_current_window, backup_current_context); - } - - SDL_GL_SwapWindow(window); - } -#ifdef __EMSCRIPTEN__ - EMSCRIPTEN_MAINLOOP_END; -#endif - - // Cleanup - ImGui_ImplOpenGL3_Shutdown(); - ImGui_ImplSDL3_Shutdown(); - ImGui::DestroyContext(); - - SDL_GL_DeleteContext(gl_context); - SDL_DestroyWindow(window); - SDL_Quit(); - - return 0; -} diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_sdlrenderer3/Makefile b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_sdlrenderer3/Makefile deleted file mode 100644 index d0a73bf..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_sdlrenderer3/Makefile +++ /dev/null @@ -1,73 +0,0 @@ -# -# Cross Platform Makefile -# Compatible with MSYS2/MINGW, Ubuntu 14.04.1 and Mac OS X -# -# You will need SDL3 (http://www.libsdl.org) which is still unreleased/unpackaged. - -#CXX = g++ -#CXX = clang++ - -EXE = example_sdl3_sdlrenderer3 -IMGUI_DIR = ../.. -SOURCES = main.cpp -SOURCES += $(IMGUI_DIR)/imgui.cpp $(IMGUI_DIR)/imgui_demo.cpp $(IMGUI_DIR)/imgui_draw.cpp $(IMGUI_DIR)/imgui_tables.cpp $(IMGUI_DIR)/imgui_widgets.cpp -SOURCES += $(IMGUI_DIR)/backends/imgui_impl_sdl3.cpp $(IMGUI_DIR)/backends/imgui_impl_sdlrenderer3.cpp -OBJS = $(addsuffix .o, $(basename $(notdir $(SOURCES)))) -UNAME_S := $(shell uname -s) -LINUX_GL_LIBS = -lGL - -CXXFLAGS = -std=c++11 -I$(IMGUI_DIR) -I$(IMGUI_DIR)/backends -CXXFLAGS += -g -Wall -Wformat -LIBS = - -##--------------------------------------------------------------------- -## BUILD FLAGS PER PLATFORM -##--------------------------------------------------------------------- - -ifeq ($(UNAME_S), Linux) #LINUX - ECHO_MESSAGE = "Linux" - LIBS += -ldl `sdl3-config --libs` - - CXXFLAGS += `sdl3-config --cflags` - CFLAGS = $(CXXFLAGS) -endif - -ifeq ($(UNAME_S), Darwin) #APPLE - ECHO_MESSAGE = "Mac OS X" - LIBS += -framework OpenGL -framework Cocoa -framework IOKit -framework CoreVideo `sdl3-config --libs` - LIBS += -L/usr/local/lib -L/opt/local/lib - - CXXFLAGS += `sdl3-config --cflags` - CXXFLAGS += -I/usr/local/include -I/opt/local/include - CFLAGS = $(CXXFLAGS) -endif - -ifeq ($(OS), Windows_NT) - ECHO_MESSAGE = "MinGW" - LIBS += -lgdi32 -lopengl32 -limm32 `pkg-config --static --libs sdl3` - - CXXFLAGS += `pkg-config --cflags sdl3` - CFLAGS = $(CXXFLAGS) -endif - -##--------------------------------------------------------------------- -## BUILD RULES -##--------------------------------------------------------------------- - -%.o:%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -%.o:$(IMGUI_DIR)/backends/%.cpp - $(CXX) $(CXXFLAGS) -c -o $@ $< - -all: $(EXE) - @echo Build complete for $(ECHO_MESSAGE) - -$(EXE): $(OBJS) - $(CXX) -o $@ $^ $(CXXFLAGS) $(LIBS) - -clean: - rm -f $(EXE) $(OBJS) diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_sdlrenderer3/build_win32.bat b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_sdlrenderer3/build_win32.bat deleted file mode 100644 index 7bc131a..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_sdlrenderer3/build_win32.bat +++ /dev/null @@ -1,8 +0,0 @@ -@REM Build for Visual Studio compiler. Run your copy of vcvars32.bat or vcvarsall.bat to setup command-line compiler. -@set OUT_DIR=Debug -@set OUT_EXE=example_sdl3_sdlrenderer3 -@set INCLUDES=/I..\.. /I..\..\backends /I%SDL3_DIR%\include -@set SOURCES=main.cpp ..\..\backends\imgui_impl_sdl3.cpp ..\..\backends\imgui_impl_sdlrenderer3.cpp ..\..\imgui*.cpp -@set LIBS=/LIBPATH:%SDL3_DIR%\lib\x86 SDL3.lib -mkdir %OUT_DIR% -cl /nologo /Zi /MD /utf-8 %INCLUDES% %SOURCES% /Fe%OUT_DIR%/%OUT_EXE%.exe /Fo%OUT_DIR%/ /link %LIBS% /subsystem:console diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_sdlrenderer3/example_sdl3_sdlrenderer3.vcxproj b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_sdlrenderer3/example_sdl3_sdlrenderer3.vcxproj deleted file mode 100644 index 8b71324..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_sdlrenderer3/example_sdl3_sdlrenderer3.vcxproj +++ /dev/null @@ -1,186 +0,0 @@ - - - - - Debug - Win32 - - - Debug - x64 - - - Release - Win32 - - - Release - x64 - - - - {C0290D21-3AD2-4A35-ABBC-A2F5F48326DA} - example_sdl3_opengl3 - 8.1 - - - - Application - true - MultiByte - v140 - - - Application - true - MultiByte - v140 - - - Application - false - true - MultiByte - v140 - - - Application - false - true - MultiByte - v140 - - - - - - - - - - - - - - - - - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - $(IncludePath) - - - - Level4 - Disabled - ..\..;..\..\backends;%SDL3_DIR%\include;$(VcpkgCurrentInstalledDir)include\SDL3;%(AdditionalIncludeDirectories) - /utf-8 %(AdditionalOptions) - - - true - %SDL3_DIR%\lib\x86;%(AdditionalLibraryDirectories) - opengl32.lib;SDL3.lib;%(AdditionalDependencies) - Console - msvcrt.lib - - - - - Level4 - Disabled - ..\..;..\..\backends;%SDL3_DIR%\include;$(VcpkgCurrentInstalledDir)include\SDL3;%(AdditionalIncludeDirectories) - /utf-8 %(AdditionalOptions) - - - true - %SDL3_DIR%\lib\x64;%(AdditionalLibraryDirectories) - opengl32.lib;SDL3.lib;%(AdditionalDependencies) - Console - msvcrt.lib - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends;%SDL3_DIR%\include;$(VcpkgCurrentInstalledDir)include\SDL3;%(AdditionalIncludeDirectories) - false - /utf-8 %(AdditionalOptions) - - - true - true - true - %SDL3_DIR%\lib\x86;%(AdditionalLibraryDirectories) - opengl32.lib;SDL3.lib;%(AdditionalDependencies) - Console - - - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends;%SDL3_DIR%\include;$(VcpkgCurrentInstalledDir)include\SDL3;%(AdditionalIncludeDirectories) - false - /utf-8 %(AdditionalOptions) - - - true - true - true - %SDL3_DIR%\lib\x64;%(AdditionalLibraryDirectories) - opengl32.lib;SDL3.lib;%(AdditionalDependencies) - Console - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_sdlrenderer3/example_sdl3_sdlrenderer3.vcxproj.filters b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_sdlrenderer3/example_sdl3_sdlrenderer3.vcxproj.filters deleted file mode 100644 index c41210d..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_sdlrenderer3/example_sdl3_sdlrenderer3.vcxproj.filters +++ /dev/null @@ -1,64 +0,0 @@ - - - - - {20b90ce4-7fcb-4731-b9a0-075f875de82d} - - - {f18ab499-84e1-499f-8eff-9754361e0e52} - cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx - - - - - imgui - - - imgui - - - imgui - - - sources - - - sources - - - imgui - - - imgui - - - sources - - - - - imgui - - - imgui - - - imgui - - - sources - - - sources - - - - - - imgui - - - imgui - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_sdlrenderer3/main.cpp b/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_sdlrenderer3/main.cpp deleted file mode 100644 index 3b8e789..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_sdl3_sdlrenderer3/main.cpp +++ /dev/null @@ -1,178 +0,0 @@ -// Dear ImGui: standalone example application for SDL3 + SDL_Renderer -// (SDL is a cross-platform general purpose library for handling windows, inputs, OpenGL/Vulkan/Metal graphics context creation, etc.) - -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -// Important to understand: SDL_Renderer is an _optional_ component of SDL3. -// For a multi-platform app consider using e.g. SDL+DirectX on Windows and SDL+OpenGL on Linux/OSX. - -#include "imgui.h" -#include "imgui_impl_sdl3.h" -#include "imgui_impl_sdlrenderer3.h" -#include -#include -#if defined(IMGUI_IMPL_OPENGL_ES2) -#include -#else -#include -#endif - -// Main code -int main(int, char**) -{ - // Setup SDL - if (SDL_Init(SDL_INIT_VIDEO | SDL_INIT_TIMER | SDL_INIT_GAMEPAD) != 0) - { - printf("Error: SDL_Init(): %s\n", SDL_GetError()); - return -1; - } - - // Enable native IME. - SDL_SetHint(SDL_HINT_IME_SHOW_UI, "1"); - - // Create window with SDL_Renderer graphics context - SDL_WindowFlags window_flags = (SDL_WindowFlags)(SDL_WINDOW_OPENGL | SDL_WINDOW_RESIZABLE | SDL_WINDOW_HIDDEN); - SDL_Window* window = SDL_CreateWindow("Dear ImGui SDL3+SDL_Renderer example", 1280, 720, window_flags); - if (window == nullptr) - { - printf("Error: SDL_CreateWindow(): %s\n", SDL_GetError()); - return -1; - } - SDL_Renderer* renderer = SDL_CreateRenderer(window, NULL, SDL_RENDERER_PRESENTVSYNC | SDL_RENDERER_ACCELERATED); - if (renderer == nullptr) - { - SDL_Log("Error: SDL_CreateRenderer(): %s\n", SDL_GetError()); - return -1; -} - SDL_SetWindowPosition(window, SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED); - SDL_ShowWindow(window); - - // Setup Dear ImGui context - IMGUI_CHECKVERSION(); - ImGui::CreateContext(); - ImGuiIO& io = ImGui::GetIO(); (void)io; - io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard; // Enable Keyboard Controls - io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad; // Enable Gamepad Controls - - // Setup Dear ImGui style - ImGui::StyleColorsDark(); - //ImGui::StyleColorsLight(); - - // Setup Platform/Renderer backends - ImGui_ImplSDL3_InitForSDLRenderer(window, renderer); - ImGui_ImplSDLRenderer3_Init(renderer); - - // Load Fonts - // - If no fonts are loaded, dear imgui will use the default font. You can also load multiple fonts and use ImGui::PushFont()/PopFont() to select them. - // - AddFontFromFileTTF() will return the ImFont* so you can store it if you need to select the font among multiple. - // - If the file cannot be loaded, the function will return a nullptr. Please handle those errors in your application (e.g. use an assertion, or display an error and quit). - // - The fonts will be rasterized at a given size (w/ oversampling) and stored into a texture when calling ImFontAtlas::Build()/GetTexDataAsXXXX(), which ImGui_ImplXXXX_NewFrame below will call. - // - Use '#define IMGUI_ENABLE_FREETYPE' in your imconfig file to use Freetype for higher quality font rendering. - // - Read 'docs/FONTS.md' for more instructions and details. - // - Remember that in C/C++ if you want to include a backslash \ in a string literal you need to write a double backslash \\ ! - // - Our Emscripten build process allows embedding fonts to be accessible at runtime from the "fonts/" folder. See Makefile.emscripten for details. - //io.Fonts->AddFontDefault(); - //io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\segoeui.ttf", 18.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/DroidSans.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Roboto-Medium.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Cousine-Regular.ttf", 15.0f); - //ImFont* font = io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\ArialUni.ttf", 18.0f, nullptr, io.Fonts->GetGlyphRangesJapanese()); - //IM_ASSERT(font != nullptr); - - // Our state - bool show_demo_window = true; - bool show_another_window = false; - ImVec4 clear_color = ImVec4(0.45f, 0.55f, 0.60f, 1.00f); - - // Main loop - bool done = false; -#ifdef __EMSCRIPTEN__ - // For an Emscripten build we are disabling file-system access, so let's not attempt to do a fopen() of the imgui.ini file. - // You may manually call LoadIniSettingsFromMemory() to load settings from your own storage. - io.IniFilename = nullptr; - EMSCRIPTEN_MAINLOOP_BEGIN -#else - while (!done) -#endif - { - // Poll and handle events (inputs, window resize, etc.) - // You can read the io.WantCaptureMouse, io.WantCaptureKeyboard flags to tell if dear imgui wants to use your inputs. - // - When io.WantCaptureMouse is true, do not dispatch mouse input data to your main application, or clear/overwrite your copy of the mouse data. - // - When io.WantCaptureKeyboard is true, do not dispatch keyboard input data to your main application, or clear/overwrite your copy of the keyboard data. - // Generally you may always pass all inputs to dear imgui, and hide them from your application based on those two flags. - SDL_Event event; - while (SDL_PollEvent(&event)) - { - ImGui_ImplSDL3_ProcessEvent(&event); - if (event.type == SDL_EVENT_QUIT) - done = true; - if (event.type == SDL_EVENT_WINDOW_CLOSE_REQUESTED && event.window.windowID == SDL_GetWindowID(window)) - done = true; - } - - // Start the Dear ImGui frame - ImGui_ImplSDLRenderer3_NewFrame(); - ImGui_ImplSDL3_NewFrame(); - ImGui::NewFrame(); - - // 1. Show the big demo window (Most of the sample code is in ImGui::ShowDemoWindow()! You can browse its code to learn more about Dear ImGui!). - if (show_demo_window) - ImGui::ShowDemoWindow(&show_demo_window); - - // 2. Show a simple window that we create ourselves. We use a Begin/End pair to create a named window. - { - static float f = 0.0f; - static int counter = 0; - - ImGui::Begin("Hello, world!"); // Create a window called "Hello, world!" and append into it. - - ImGui::Text("This is some useful text."); // Display some text (you can use a format strings too) - ImGui::Checkbox("Demo Window", &show_demo_window); // Edit bools storing our window open/close state - ImGui::Checkbox("Another Window", &show_another_window); - - ImGui::SliderFloat("float", &f, 0.0f, 1.0f); // Edit 1 float using a slider from 0.0f to 1.0f - ImGui::ColorEdit3("clear color", (float*)&clear_color); // Edit 3 floats representing a color - - if (ImGui::Button("Button")) // Buttons return true when clicked (most widgets return true when edited/activated) - counter++; - ImGui::SameLine(); - ImGui::Text("counter = %d", counter); - - ImGui::Text("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / io.Framerate, io.Framerate); - ImGui::End(); - } - - // 3. Show another simple window. - if (show_another_window) - { - ImGui::Begin("Another Window", &show_another_window); // Pass a pointer to our bool variable (the window will have a closing button that will clear the bool when clicked) - ImGui::Text("Hello from another window!"); - if (ImGui::Button("Close Me")) - show_another_window = false; - ImGui::End(); - } - - // Rendering - ImGui::Render(); - //SDL_RenderSetScale(renderer, io.DisplayFramebufferScale.x, io.DisplayFramebufferScale.y); - SDL_SetRenderDrawColor(renderer, (Uint8)(clear_color.x * 255), (Uint8)(clear_color.y * 255), (Uint8)(clear_color.z * 255), (Uint8)(clear_color.w * 255)); - SDL_RenderClear(renderer); - ImGui_ImplSDLRenderer3_RenderDrawData(ImGui::GetDrawData()); - SDL_RenderPresent(renderer); - } - - // Cleanup - ImGui_ImplSDLRenderer3_Shutdown(); - ImGui_ImplSDL3_Shutdown(); - ImGui::DestroyContext(); - - SDL_DestroyRenderer(renderer); - SDL_DestroyWindow(window); - SDL_Quit(); - - return 0; -} diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx10/build_win32.bat b/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx10/build_win32.bat deleted file mode 100644 index 78a6e37..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx10/build_win32.bat +++ /dev/null @@ -1,8 +0,0 @@ -@REM Build for Visual Studio compiler. Run your copy of vcvars32.bat or vcvarsall.bat to setup command-line compiler. -@set OUT_DIR=Debug -@set OUT_EXE=example_win32_directx10 -@set INCLUDES=/I..\.. /I..\..\backends /I "%WindowsSdkDir%Include\um" /I "%WindowsSdkDir%Include\shared" /I "%DXSDK_DIR%Include" -@set SOURCES=main.cpp ..\..\backends\imgui_impl_win32.cpp ..\..\backends\imgui_impl_dx10.cpp ..\..\imgui*.cpp -@set LIBS=/LIBPATH:"%DXSDK_DIR%/Lib/x86" d3d10.lib d3dcompiler.lib -mkdir %OUT_DIR% -cl /nologo /Zi /MD /utf-8 %INCLUDES% /D UNICODE /D _UNICODE %SOURCES% /Fe%OUT_DIR%/%OUT_EXE%.exe /Fo%OUT_DIR%/ /link %LIBS% diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx10/example_win32_directx10.vcxproj b/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx10/example_win32_directx10.vcxproj deleted file mode 100644 index d11aed8..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx10/example_win32_directx10.vcxproj +++ /dev/null @@ -1,176 +0,0 @@ - - - - - Debug - Win32 - - - Debug - x64 - - - Release - Win32 - - - Release - x64 - - - - {345A953E-A004-4648-B442-DC5F9F11068C} - example_win32_directx10 - 8.1 - - - - Application - true - Unicode - v140 - - - Application - true - Unicode - v140 - - - Application - false - true - Unicode - v140 - - - Application - false - true - Unicode - v140 - - - - - - - - - - - - - - - - - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - - - - Level4 - Disabled - ..\..;..\..\backends;%(AdditionalIncludeDirectories); - /utf-8 %(AdditionalOptions) - - - true - d3d10.lib;d3dcompiler.lib;dxgi.lib;%(AdditionalDependencies) - $(DXSDK_DIR)/Lib/x86;%(AdditionalLibraryDirectories) - Console - - - - - Level4 - Disabled - ..\..;..\..\backends;%(AdditionalIncludeDirectories); - /utf-8 %(AdditionalOptions) - - - true - d3d10.lib;d3dcompiler.lib;dxgi.lib;%(AdditionalDependencies) - $(DXSDK_DIR)/Lib/x64;%(AdditionalLibraryDirectories) - Console - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends;%(AdditionalIncludeDirectories); - false - /utf-8 %(AdditionalOptions) - - - true - true - true - d3d10.lib;d3dcompiler.lib;dxgi.lib;%(AdditionalDependencies) - $(DXSDK_DIR)/Lib/x86;%(AdditionalLibraryDirectories) - Console - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends;%(AdditionalIncludeDirectories); - false - /utf-8 %(AdditionalOptions) - - - true - true - true - d3d10.lib;d3dcompiler.lib;dxgi.lib;%(AdditionalDependencies) - $(DXSDK_DIR)/Lib/x64;%(AdditionalLibraryDirectories) - Console - - - - - - - - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx10/example_win32_directx10.vcxproj.filters b/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx10/example_win32_directx10.vcxproj.filters deleted file mode 100644 index 33ab99b..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx10/example_win32_directx10.vcxproj.filters +++ /dev/null @@ -1,63 +0,0 @@ - - - - - {0587d7a3-f2ce-4d56-b84f-a0005d3bfce6} - - - {08e36723-ce4f-4cff-9662-c40801cf1acf} - - - - - imgui - - - imgui - - - imgui - - - sources - - - sources - - - - - imgui - - - sources - - - imgui - - - imgui - - - sources - - - sources - - - imgui - - - imgui - - - - - - imgui - - - imgui - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx10/main.cpp b/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx10/main.cpp deleted file mode 100644 index dc1b72b..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx10/main.cpp +++ /dev/null @@ -1,277 +0,0 @@ -// Dear ImGui: standalone example application for DirectX 10 - -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#include "imgui.h" -#include "imgui_impl_win32.h" -#include "imgui_impl_dx10.h" -#include -#include -#include - -// Data -static ID3D10Device* g_pd3dDevice = nullptr; -static IDXGISwapChain* g_pSwapChain = nullptr; -static UINT g_ResizeWidth = 0, g_ResizeHeight = 0; -static ID3D10RenderTargetView* g_mainRenderTargetView = nullptr; - -// Forward declarations of helper functions -bool CreateDeviceD3D(HWND hWnd); -void CleanupDeviceD3D(); -void CreateRenderTarget(); -void CleanupRenderTarget(); -LRESULT WINAPI WndProc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam); - -// Main code -int main(int, char**) -{ - // Create application window - //ImGui_ImplWin32_EnableDpiAwareness(); - WNDCLASSEXW wc = { sizeof(wc), CS_CLASSDC, WndProc, 0L, 0L, GetModuleHandle(nullptr), nullptr, nullptr, nullptr, nullptr, L"ImGui Example", nullptr }; - ::RegisterClassExW(&wc); - HWND hwnd = ::CreateWindowW(wc.lpszClassName, L"Dear ImGui DirectX10 Example", WS_OVERLAPPEDWINDOW, 100, 100, 1280, 800, nullptr, nullptr, wc.hInstance, nullptr); - - // Initialize Direct3D - if (!CreateDeviceD3D(hwnd)) - { - CleanupDeviceD3D(); - ::UnregisterClassW(wc.lpszClassName, wc.hInstance); - return 1; - } - - // Show the window - ::ShowWindow(hwnd, SW_SHOWDEFAULT); - ::UpdateWindow(hwnd); - - // Setup Dear ImGui context - IMGUI_CHECKVERSION(); - ImGui::CreateContext(); - ImGuiIO& io = ImGui::GetIO(); (void)io; - io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard; // Enable Keyboard Controls - io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad; // Enable Gamepad Controls - io.ConfigFlags |= ImGuiConfigFlags_DockingEnable; // Enable Docking - io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable; // Enable Multi-Viewport / Platform Windows - //io.ConfigViewportsNoAutoMerge = true; - //io.ConfigViewportsNoTaskBarIcon = true; - - // Setup Dear ImGui style - ImGui::StyleColorsDark(); - //ImGui::StyleColorsLight(); - - // When viewports are enabled we tweak WindowRounding/WindowBg so platform windows can look identical to regular ones. - ImGuiStyle& style = ImGui::GetStyle(); - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - style.WindowRounding = 0.0f; - style.Colors[ImGuiCol_WindowBg].w = 1.0f; - } - - // Setup Platform/Renderer backends - ImGui_ImplWin32_Init(hwnd); - ImGui_ImplDX10_Init(g_pd3dDevice); - - // Load Fonts - // - If no fonts are loaded, dear imgui will use the default font. You can also load multiple fonts and use ImGui::PushFont()/PopFont() to select them. - // - AddFontFromFileTTF() will return the ImFont* so you can store it if you need to select the font among multiple. - // - If the file cannot be loaded, the function will return a nullptr. Please handle those errors in your application (e.g. use an assertion, or display an error and quit). - // - The fonts will be rasterized at a given size (w/ oversampling) and stored into a texture when calling ImFontAtlas::Build()/GetTexDataAsXXXX(), which ImGui_ImplXXXX_NewFrame below will call. - // - Use '#define IMGUI_ENABLE_FREETYPE' in your imconfig file to use Freetype for higher quality font rendering. - // - Read 'docs/FONTS.md' for more instructions and details. - // - Remember that in C/C++ if you want to include a backslash \ in a string literal you need to write a double backslash \\ ! - //io.Fonts->AddFontDefault(); - //io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\segoeui.ttf", 18.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/DroidSans.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Roboto-Medium.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Cousine-Regular.ttf", 15.0f); - //ImFont* font = io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\ArialUni.ttf", 18.0f, nullptr, io.Fonts->GetGlyphRangesJapanese()); - //IM_ASSERT(font != nullptr); - - // Our state - bool show_demo_window = true; - bool show_another_window = false; - ImVec4 clear_color = ImVec4(0.45f, 0.55f, 0.60f, 1.00f); - - // Main loop - bool done = false; - while (!done) - { - // Poll and handle messages (inputs, window resize, etc.) - // See the WndProc() function below for our to dispatch events to the Win32 backend. - MSG msg; - while (::PeekMessage(&msg, nullptr, 0U, 0U, PM_REMOVE)) - { - ::TranslateMessage(&msg); - ::DispatchMessage(&msg); - if (msg.message == WM_QUIT) - done = true; - } - if (done) - break; - - // Handle window resize (we don't resize directly in the WM_SIZE handler) - if (g_ResizeWidth != 0 && g_ResizeHeight != 0) - { - CleanupRenderTarget(); - g_pSwapChain->ResizeBuffers(0, g_ResizeWidth, g_ResizeHeight, DXGI_FORMAT_UNKNOWN, 0); - g_ResizeWidth = g_ResizeHeight = 0; - CreateRenderTarget(); - } - - // Start the Dear ImGui frame - ImGui_ImplDX10_NewFrame(); - ImGui_ImplWin32_NewFrame(); - ImGui::NewFrame(); - - // 1. Show the big demo window (Most of the sample code is in ImGui::ShowDemoWindow()! You can browse its code to learn more about Dear ImGui!). - if (show_demo_window) - ImGui::ShowDemoWindow(&show_demo_window); - - // 2. Show a simple window that we create ourselves. We use a Begin/End pair to create a named window. - { - static float f = 0.0f; - static int counter = 0; - - ImGui::Begin("Hello, world!"); // Create a window called "Hello, world!" and append into it. - - ImGui::Text("This is some useful text."); // Display some text (you can use a format strings too) - ImGui::Checkbox("Demo Window", &show_demo_window); // Edit bools storing our window open/close state - ImGui::Checkbox("Another Window", &show_another_window); - - ImGui::SliderFloat("float", &f, 0.0f, 1.0f); // Edit 1 float using a slider from 0.0f to 1.0f - ImGui::ColorEdit3("clear color", (float*)&clear_color); // Edit 3 floats representing a color - - if (ImGui::Button("Button")) // Buttons return true when clicked (most widgets return true when edited/activated) - counter++; - ImGui::SameLine(); - ImGui::Text("counter = %d", counter); - - ImGui::Text("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / io.Framerate, io.Framerate); - ImGui::End(); - } - - // 3. Show another simple window. - if (show_another_window) - { - ImGui::Begin("Another Window", &show_another_window); // Pass a pointer to our bool variable (the window will have a closing button that will clear the bool when clicked) - ImGui::Text("Hello from another window!"); - if (ImGui::Button("Close Me")) - show_another_window = false; - ImGui::End(); - } - - // Rendering - ImGui::Render(); - const float clear_color_with_alpha[4] = { clear_color.x * clear_color.w, clear_color.y * clear_color.w, clear_color.z * clear_color.w, clear_color.w }; - g_pd3dDevice->OMSetRenderTargets(1, &g_mainRenderTargetView, nullptr); - g_pd3dDevice->ClearRenderTargetView(g_mainRenderTargetView, clear_color_with_alpha); - ImGui_ImplDX10_RenderDrawData(ImGui::GetDrawData()); - - // Update and Render additional Platform Windows - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - ImGui::UpdatePlatformWindows(); - ImGui::RenderPlatformWindowsDefault(); - } - - g_pSwapChain->Present(1, 0); // Present with vsync - //g_pSwapChain->Present(0, 0); // Present without vsync - } - - ImGui_ImplDX10_Shutdown(); - ImGui_ImplWin32_Shutdown(); - ImGui::DestroyContext(); - - CleanupDeviceD3D(); - ::DestroyWindow(hwnd); - ::UnregisterClassW(wc.lpszClassName, wc.hInstance); - - return 0; -} - -// Helper functions -bool CreateDeviceD3D(HWND hWnd) -{ - // Setup swap chain - DXGI_SWAP_CHAIN_DESC sd; - ZeroMemory(&sd, sizeof(sd)); - sd.BufferCount = 2; - sd.BufferDesc.Width = 0; - sd.BufferDesc.Height = 0; - sd.BufferDesc.Format = DXGI_FORMAT_R8G8B8A8_UNORM; - sd.BufferDesc.RefreshRate.Numerator = 60; - sd.BufferDesc.RefreshRate.Denominator = 1; - sd.Flags = DXGI_SWAP_CHAIN_FLAG_ALLOW_MODE_SWITCH; - sd.BufferUsage = DXGI_USAGE_RENDER_TARGET_OUTPUT; - sd.OutputWindow = hWnd; - sd.SampleDesc.Count = 1; - sd.SampleDesc.Quality = 0; - sd.Windowed = TRUE; - sd.SwapEffect = DXGI_SWAP_EFFECT_DISCARD; - - UINT createDeviceFlags = 0; - //createDeviceFlags |= D3D10_CREATE_DEVICE_DEBUG; - HRESULT res = D3D10CreateDeviceAndSwapChain(nullptr, D3D10_DRIVER_TYPE_HARDWARE, nullptr, createDeviceFlags, D3D10_SDK_VERSION, &sd, &g_pSwapChain, &g_pd3dDevice); - if (res == DXGI_ERROR_UNSUPPORTED) // Try high-performance WARP software driver if hardware is not available. - res = D3D10CreateDeviceAndSwapChain(nullptr, D3D10_DRIVER_TYPE_WARP, nullptr, createDeviceFlags, D3D10_SDK_VERSION, &sd, &g_pSwapChain, &g_pd3dDevice); - if (res != S_OK) - return false; - - CreateRenderTarget(); - return true; -} - -void CleanupDeviceD3D() -{ - CleanupRenderTarget(); - if (g_pSwapChain) { g_pSwapChain->Release(); g_pSwapChain = nullptr; } - if (g_pd3dDevice) { g_pd3dDevice->Release(); g_pd3dDevice = nullptr; } -} - -void CreateRenderTarget() -{ - ID3D10Texture2D* pBackBuffer; - g_pSwapChain->GetBuffer(0, IID_PPV_ARGS(&pBackBuffer)); - g_pd3dDevice->CreateRenderTargetView(pBackBuffer, nullptr, &g_mainRenderTargetView); - pBackBuffer->Release(); -} - -void CleanupRenderTarget() -{ - if (g_mainRenderTargetView) { g_mainRenderTargetView->Release(); g_mainRenderTargetView = nullptr; } -} - -// Forward declare message handler from imgui_impl_win32.cpp -extern IMGUI_IMPL_API LRESULT ImGui_ImplWin32_WndProcHandler(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam); - -// Win32 message handler -// You can read the io.WantCaptureMouse, io.WantCaptureKeyboard flags to tell if dear imgui wants to use your inputs. -// - When io.WantCaptureMouse is true, do not dispatch mouse input data to your main application, or clear/overwrite your copy of the mouse data. -// - When io.WantCaptureKeyboard is true, do not dispatch keyboard input data to your main application, or clear/overwrite your copy of the keyboard data. -// Generally you may always pass all inputs to dear imgui, and hide them from your application based on those two flags. -LRESULT WINAPI WndProc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam) -{ - if (ImGui_ImplWin32_WndProcHandler(hWnd, msg, wParam, lParam)) - return true; - - switch (msg) - { - case WM_SIZE: - if (wParam == SIZE_MINIMIZED) - return 0; - g_ResizeWidth = (UINT)LOWORD(lParam); // Queue resize - g_ResizeHeight = (UINT)HIWORD(lParam); - return 0; - case WM_SYSCOMMAND: - if ((wParam & 0xfff0) == SC_KEYMENU) // Disable ALT application menu - return 0; - break; - case WM_DESTROY: - ::PostQuitMessage(0); - return 0; - } - return ::DefWindowProcW(hWnd, msg, wParam, lParam); -} diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx11/build_win32.bat b/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx11/build_win32.bat deleted file mode 100644 index c9a717c..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx11/build_win32.bat +++ /dev/null @@ -1,9 +0,0 @@ -@REM Build for Visual Studio compiler. Run your copy of vcvars32.bat or vcvarsall.bat to setup command-line compiler. -@set OUT_DIR=Debug -@set OUT_EXE=example_win32_directx11 -@set INCLUDES=/I..\.. /I..\..\backends /I "%WindowsSdkDir%Include\um" /I "%WindowsSdkDir%Include\shared" /I "%DXSDK_DIR%Include" -@set SOURCES=main.cpp ..\..\backends\imgui_impl_dx11.cpp ..\..\backends\imgui_impl_win32.cpp ..\..\imgui*.cpp -@set LIBS=/LIBPATH:"%DXSDK_DIR%/Lib/x86" d3d11.lib d3dcompiler.lib -mkdir %OUT_DIR% -cl /nologo /Zi /MD /utf-8 %INCLUDES% /D UNICODE /D _UNICODE %SOURCES% /Fe%OUT_DIR%/%OUT_EXE%.exe /Fo%OUT_DIR%/ /link %LIBS% - diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx11/example_win32_directx11.vcxproj b/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx11/example_win32_directx11.vcxproj deleted file mode 100644 index bace6a2..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx11/example_win32_directx11.vcxproj +++ /dev/null @@ -1,175 +0,0 @@ - - - - - Debug - Win32 - - - Debug - x64 - - - Release - Win32 - - - Release - x64 - - - - {9F316E83-5AE5-4939-A723-305A94F48005} - example_win32_directx11 - - - - Application - true - Unicode - v140 - - - Application - true - Unicode - v140 - - - Application - false - true - Unicode - v140 - - - Application - false - true - Unicode - v140 - - - - - - - - - - - - - - - - - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - - - - Level4 - Disabled - ..\..;..\..\backends;%(AdditionalIncludeDirectories); - /utf-8 %(AdditionalOptions) - - - true - d3d11.lib;d3dcompiler.lib;dxgi.lib;%(AdditionalDependencies) - $(DXSDK_DIR)/Lib/x86;%(AdditionalLibraryDirectories) - Console - - - - - Level4 - Disabled - ..\..;..\..\backends;%(AdditionalIncludeDirectories); - /utf-8 %(AdditionalOptions) - - - true - d3d11.lib;d3dcompiler.lib;dxgi.lib;%(AdditionalDependencies) - $(DXSDK_DIR)/Lib/x64;%(AdditionalLibraryDirectories) - Console - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends;%(AdditionalIncludeDirectories); - false - /utf-8 %(AdditionalOptions) - - - true - true - true - d3d11.lib;d3dcompiler.lib;dxgi.lib;%(AdditionalDependencies) - $(DXSDK_DIR)/Lib/x86;%(AdditionalLibraryDirectories) - Console - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends;%(AdditionalIncludeDirectories); - false - /utf-8 %(AdditionalOptions) - - - true - true - true - d3d11.lib;d3dcompiler.lib;dxgi.lib;%(AdditionalDependencies) - $(DXSDK_DIR)/Lib/x64;%(AdditionalLibraryDirectories) - Console - - - - - - - - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx11/example_win32_directx11.vcxproj.filters b/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx11/example_win32_directx11.vcxproj.filters deleted file mode 100644 index 63032a6..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx11/example_win32_directx11.vcxproj.filters +++ /dev/null @@ -1,63 +0,0 @@ - - - - - {0587d7a3-f2ce-4d56-b84f-a0005d3bfce6} - - - {08e36723-ce4f-4cff-9662-c40801cf1acf} - - - - - imgui - - - imgui - - - imgui - - - sources - - - sources - - - - - imgui - - - sources - - - imgui - - - imgui - - - imgui - - - sources - - - sources - - - imgui - - - - - - imgui - - - imgui - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx11/main.cpp b/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx11/main.cpp deleted file mode 100644 index e9e907b..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx11/main.cpp +++ /dev/null @@ -1,299 +0,0 @@ -// Dear ImGui: standalone example application for DirectX 11 - -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#include "imgui.h" -#include "imgui_impl_win32.h" -#include "imgui_impl_dx11.h" -#include -#include - -// Data -static ID3D11Device* g_pd3dDevice = nullptr; -static ID3D11DeviceContext* g_pd3dDeviceContext = nullptr; -static IDXGISwapChain* g_pSwapChain = nullptr; -static UINT g_ResizeWidth = 0, g_ResizeHeight = 0; -static ID3D11RenderTargetView* g_mainRenderTargetView = nullptr; - -// Forward declarations of helper functions -bool CreateDeviceD3D(HWND hWnd); -void CleanupDeviceD3D(); -void CreateRenderTarget(); -void CleanupRenderTarget(); -LRESULT WINAPI WndProc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam); - -// Main code -int main(int, char**) -{ - // Create application window - //ImGui_ImplWin32_EnableDpiAwareness(); - WNDCLASSEXW wc = { sizeof(wc), CS_CLASSDC, WndProc, 0L, 0L, GetModuleHandle(nullptr), nullptr, nullptr, nullptr, nullptr, L"ImGui Example", nullptr }; - ::RegisterClassExW(&wc); - HWND hwnd = ::CreateWindowW(wc.lpszClassName, L"Dear ImGui DirectX11 Example", WS_OVERLAPPEDWINDOW, 100, 100, 1280, 800, nullptr, nullptr, wc.hInstance, nullptr); - - // Initialize Direct3D - if (!CreateDeviceD3D(hwnd)) - { - CleanupDeviceD3D(); - ::UnregisterClassW(wc.lpszClassName, wc.hInstance); - return 1; - } - - // Show the window - ::ShowWindow(hwnd, SW_SHOWDEFAULT); - ::UpdateWindow(hwnd); - - // Setup Dear ImGui context - IMGUI_CHECKVERSION(); - ImGui::CreateContext(); - ImGuiIO& io = ImGui::GetIO(); (void)io; - io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard; // Enable Keyboard Controls - io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad; // Enable Gamepad Controls - io.ConfigFlags |= ImGuiConfigFlags_DockingEnable; // Enable Docking - io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable; // Enable Multi-Viewport / Platform Windows - //io.ConfigViewportsNoAutoMerge = true; - //io.ConfigViewportsNoTaskBarIcon = true; - //io.ConfigViewportsNoDefaultParent = true; - //io.ConfigDockingAlwaysTabBar = true; - //io.ConfigDockingTransparentPayload = true; - //io.ConfigFlags |= ImGuiConfigFlags_DpiEnableScaleFonts; // FIXME-DPI: Experimental. THIS CURRENTLY DOESN'T WORK AS EXPECTED. DON'T USE IN USER APP! - //io.ConfigFlags |= ImGuiConfigFlags_DpiEnableScaleViewports; // FIXME-DPI: Experimental. - - // Setup Dear ImGui style - ImGui::StyleColorsDark(); - //ImGui::StyleColorsLight(); - - // When viewports are enabled we tweak WindowRounding/WindowBg so platform windows can look identical to regular ones. - ImGuiStyle& style = ImGui::GetStyle(); - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - style.WindowRounding = 0.0f; - style.Colors[ImGuiCol_WindowBg].w = 1.0f; - } - - // Setup Platform/Renderer backends - ImGui_ImplWin32_Init(hwnd); - ImGui_ImplDX11_Init(g_pd3dDevice, g_pd3dDeviceContext); - - // Load Fonts - // - If no fonts are loaded, dear imgui will use the default font. You can also load multiple fonts and use ImGui::PushFont()/PopFont() to select them. - // - AddFontFromFileTTF() will return the ImFont* so you can store it if you need to select the font among multiple. - // - If the file cannot be loaded, the function will return a nullptr. Please handle those errors in your application (e.g. use an assertion, or display an error and quit). - // - The fonts will be rasterized at a given size (w/ oversampling) and stored into a texture when calling ImFontAtlas::Build()/GetTexDataAsXXXX(), which ImGui_ImplXXXX_NewFrame below will call. - // - Use '#define IMGUI_ENABLE_FREETYPE' in your imconfig file to use Freetype for higher quality font rendering. - // - Read 'docs/FONTS.md' for more instructions and details. - // - Remember that in C/C++ if you want to include a backslash \ in a string literal you need to write a double backslash \\ ! - //io.Fonts->AddFontDefault(); - //io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\segoeui.ttf", 18.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/DroidSans.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Roboto-Medium.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Cousine-Regular.ttf", 15.0f); - //ImFont* font = io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\ArialUni.ttf", 18.0f, nullptr, io.Fonts->GetGlyphRangesJapanese()); - //IM_ASSERT(font != nullptr); - - // Our state - bool show_demo_window = true; - bool show_another_window = false; - ImVec4 clear_color = ImVec4(0.45f, 0.55f, 0.60f, 1.00f); - - // Main loop - bool done = false; - while (!done) - { - // Poll and handle messages (inputs, window resize, etc.) - // See the WndProc() function below for our to dispatch events to the Win32 backend. - MSG msg; - while (::PeekMessage(&msg, nullptr, 0U, 0U, PM_REMOVE)) - { - ::TranslateMessage(&msg); - ::DispatchMessage(&msg); - if (msg.message == WM_QUIT) - done = true; - } - if (done) - break; - - // Handle window resize (we don't resize directly in the WM_SIZE handler) - if (g_ResizeWidth != 0 && g_ResizeHeight != 0) - { - CleanupRenderTarget(); - g_pSwapChain->ResizeBuffers(0, g_ResizeWidth, g_ResizeHeight, DXGI_FORMAT_UNKNOWN, 0); - g_ResizeWidth = g_ResizeHeight = 0; - CreateRenderTarget(); - } - - // Start the Dear ImGui frame - ImGui_ImplDX11_NewFrame(); - ImGui_ImplWin32_NewFrame(); - ImGui::NewFrame(); - - // 1. Show the big demo window (Most of the sample code is in ImGui::ShowDemoWindow()! You can browse its code to learn more about Dear ImGui!). - if (show_demo_window) - ImGui::ShowDemoWindow(&show_demo_window); - - // 2. Show a simple window that we create ourselves. We use a Begin/End pair to create a named window. - { - static float f = 0.0f; - static int counter = 0; - - ImGui::Begin("Hello, world!"); // Create a window called "Hello, world!" and append into it. - - ImGui::Text("This is some useful text."); // Display some text (you can use a format strings too) - ImGui::Checkbox("Demo Window", &show_demo_window); // Edit bools storing our window open/close state - ImGui::Checkbox("Another Window", &show_another_window); - - ImGui::SliderFloat("float", &f, 0.0f, 1.0f); // Edit 1 float using a slider from 0.0f to 1.0f - ImGui::ColorEdit3("clear color", (float*)&clear_color); // Edit 3 floats representing a color - - if (ImGui::Button("Button")) // Buttons return true when clicked (most widgets return true when edited/activated) - counter++; - ImGui::SameLine(); - ImGui::Text("counter = %d", counter); - - ImGui::Text("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / io.Framerate, io.Framerate); - ImGui::End(); - } - - // 3. Show another simple window. - if (show_another_window) - { - ImGui::Begin("Another Window", &show_another_window); // Pass a pointer to our bool variable (the window will have a closing button that will clear the bool when clicked) - ImGui::Text("Hello from another window!"); - if (ImGui::Button("Close Me")) - show_another_window = false; - ImGui::End(); - } - - // Rendering - ImGui::Render(); - const float clear_color_with_alpha[4] = { clear_color.x * clear_color.w, clear_color.y * clear_color.w, clear_color.z * clear_color.w, clear_color.w }; - g_pd3dDeviceContext->OMSetRenderTargets(1, &g_mainRenderTargetView, nullptr); - g_pd3dDeviceContext->ClearRenderTargetView(g_mainRenderTargetView, clear_color_with_alpha); - ImGui_ImplDX11_RenderDrawData(ImGui::GetDrawData()); - - // Update and Render additional Platform Windows - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - ImGui::UpdatePlatformWindows(); - ImGui::RenderPlatformWindowsDefault(); - } - - g_pSwapChain->Present(1, 0); // Present with vsync - //g_pSwapChain->Present(0, 0); // Present without vsync - } - - // Cleanup - ImGui_ImplDX11_Shutdown(); - ImGui_ImplWin32_Shutdown(); - ImGui::DestroyContext(); - - CleanupDeviceD3D(); - ::DestroyWindow(hwnd); - ::UnregisterClassW(wc.lpszClassName, wc.hInstance); - - return 0; -} - -// Helper functions -bool CreateDeviceD3D(HWND hWnd) -{ - // Setup swap chain - DXGI_SWAP_CHAIN_DESC sd; - ZeroMemory(&sd, sizeof(sd)); - sd.BufferCount = 2; - sd.BufferDesc.Width = 0; - sd.BufferDesc.Height = 0; - sd.BufferDesc.Format = DXGI_FORMAT_R8G8B8A8_UNORM; - sd.BufferDesc.RefreshRate.Numerator = 60; - sd.BufferDesc.RefreshRate.Denominator = 1; - sd.Flags = DXGI_SWAP_CHAIN_FLAG_ALLOW_MODE_SWITCH; - sd.BufferUsage = DXGI_USAGE_RENDER_TARGET_OUTPUT; - sd.OutputWindow = hWnd; - sd.SampleDesc.Count = 1; - sd.SampleDesc.Quality = 0; - sd.Windowed = TRUE; - sd.SwapEffect = DXGI_SWAP_EFFECT_DISCARD; - - UINT createDeviceFlags = 0; - //createDeviceFlags |= D3D11_CREATE_DEVICE_DEBUG; - D3D_FEATURE_LEVEL featureLevel; - const D3D_FEATURE_LEVEL featureLevelArray[2] = { D3D_FEATURE_LEVEL_11_0, D3D_FEATURE_LEVEL_10_0, }; - HRESULT res = D3D11CreateDeviceAndSwapChain(nullptr, D3D_DRIVER_TYPE_HARDWARE, nullptr, createDeviceFlags, featureLevelArray, 2, D3D11_SDK_VERSION, &sd, &g_pSwapChain, &g_pd3dDevice, &featureLevel, &g_pd3dDeviceContext); - if (res == DXGI_ERROR_UNSUPPORTED) // Try high-performance WARP software driver if hardware is not available. - res = D3D11CreateDeviceAndSwapChain(nullptr, D3D_DRIVER_TYPE_WARP, nullptr, createDeviceFlags, featureLevelArray, 2, D3D11_SDK_VERSION, &sd, &g_pSwapChain, &g_pd3dDevice, &featureLevel, &g_pd3dDeviceContext); - if (res != S_OK) - return false; - - CreateRenderTarget(); - return true; -} - -void CleanupDeviceD3D() -{ - CleanupRenderTarget(); - if (g_pSwapChain) { g_pSwapChain->Release(); g_pSwapChain = nullptr; } - if (g_pd3dDeviceContext) { g_pd3dDeviceContext->Release(); g_pd3dDeviceContext = nullptr; } - if (g_pd3dDevice) { g_pd3dDevice->Release(); g_pd3dDevice = nullptr; } -} - -void CreateRenderTarget() -{ - ID3D11Texture2D* pBackBuffer; - g_pSwapChain->GetBuffer(0, IID_PPV_ARGS(&pBackBuffer)); - g_pd3dDevice->CreateRenderTargetView(pBackBuffer, nullptr, &g_mainRenderTargetView); - pBackBuffer->Release(); -} - -void CleanupRenderTarget() -{ - if (g_mainRenderTargetView) { g_mainRenderTargetView->Release(); g_mainRenderTargetView = nullptr; } -} - -#ifndef WM_DPICHANGED -#define WM_DPICHANGED 0x02E0 // From Windows SDK 8.1+ headers -#endif - -// Forward declare message handler from imgui_impl_win32.cpp -extern IMGUI_IMPL_API LRESULT ImGui_ImplWin32_WndProcHandler(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam); - -// Win32 message handler -// You can read the io.WantCaptureMouse, io.WantCaptureKeyboard flags to tell if dear imgui wants to use your inputs. -// - When io.WantCaptureMouse is true, do not dispatch mouse input data to your main application, or clear/overwrite your copy of the mouse data. -// - When io.WantCaptureKeyboard is true, do not dispatch keyboard input data to your main application, or clear/overwrite your copy of the keyboard data. -// Generally you may always pass all inputs to dear imgui, and hide them from your application based on those two flags. -LRESULT WINAPI WndProc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam) -{ - if (ImGui_ImplWin32_WndProcHandler(hWnd, msg, wParam, lParam)) - return true; - - switch (msg) - { - case WM_SIZE: - if (wParam == SIZE_MINIMIZED) - return 0; - g_ResizeWidth = (UINT)LOWORD(lParam); // Queue resize - g_ResizeHeight = (UINT)HIWORD(lParam); - return 0; - case WM_SYSCOMMAND: - if ((wParam & 0xfff0) == SC_KEYMENU) // Disable ALT application menu - return 0; - break; - case WM_DESTROY: - ::PostQuitMessage(0); - return 0; - case WM_DPICHANGED: - if (ImGui::GetIO().ConfigFlags & ImGuiConfigFlags_DpiEnableScaleViewports) - { - //const int dpi = HIWORD(wParam); - //printf("WM_DPICHANGED to %d (%.0f%%)\n", dpi, (float)dpi / 96.0f * 100.0f); - const RECT* suggested_rect = (RECT*)lParam; - ::SetWindowPos(hWnd, nullptr, suggested_rect->left, suggested_rect->top, suggested_rect->right - suggested_rect->left, suggested_rect->bottom - suggested_rect->top, SWP_NOZORDER | SWP_NOACTIVATE); - } - break; - } - return ::DefWindowProcW(hWnd, msg, wParam, lParam); -} diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx12/build_win32.bat b/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx12/build_win32.bat deleted file mode 100644 index 68e3c92..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx12/build_win32.bat +++ /dev/null @@ -1,9 +0,0 @@ -@REM Build for Visual Studio compiler. Run your copy of vcvars32.bat or vcvarsall.bat to setup command-line compiler. -@REM Important: to build on 32-bit systems, the DX12 backends needs '#define ImTextureID ImU64', so we pass it here. -@set OUT_DIR=Debug -@set OUT_EXE=example_win32_directx12 -@set INCLUDES=/I..\.. /I..\..\backends /I "%WindowsSdkDir%Include\um" /I "%WindowsSdkDir%Include\shared" -@set SOURCES=main.cpp ..\..\backends\imgui_impl_dx12.cpp ..\..\backends\imgui_impl_win32.cpp ..\..\imgui*.cpp -@set LIBS=d3d12.lib d3dcompiler.lib dxgi.lib -mkdir Debug -cl /nologo /Zi /MD /utf-8 %INCLUDES% /D ImTextureID=ImU64 /D UNICODE /D _UNICODE %SOURCES% /Fe%OUT_DIR%/%OUT_EXE%.exe /Fo%OUT_DIR%/ /link %LIBS% diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx12/example_win32_directx12.vcxproj b/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx12/example_win32_directx12.vcxproj deleted file mode 100644 index 7b64371..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx12/example_win32_directx12.vcxproj +++ /dev/null @@ -1,180 +0,0 @@ - - - - - Debug - Win32 - - - Debug - x64 - - - Release - Win32 - - - Release - x64 - - - - {b4cf9797-519d-4afe-a8f4-5141a6b521d3} - example_win32_directx12 - 10.0.18362.0 - - - - Application - true - Unicode - v140 - - - Application - true - Unicode - v140 - - - Application - false - true - Unicode - v140 - - - Application - false - true - Unicode - v140 - - - - - - - - - - - - - - - - - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - - - - Level4 - Disabled - ..\..;..\..\backends;%(AdditionalIncludeDirectories) - ImTextureID=ImU64;_UNICODE;UNICODE;%(PreprocessorDefinitions) - /utf-8 %(AdditionalOptions) - - - true - d3d12.lib;d3dcompiler.lib;dxgi.lib;%(AdditionalDependencies) - %(AdditionalLibraryDirectories) - Console - - - - - Level4 - Disabled - ..\..;..\..\backends;%(AdditionalIncludeDirectories) - ImTextureID=ImU64;_UNICODE;UNICODE;%(PreprocessorDefinitions) - /utf-8 %(AdditionalOptions) - - - true - d3d12.lib;d3dcompiler.lib;dxgi.lib;%(AdditionalDependencies) - %(AdditionalLibraryDirectories) - Console - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends;%(AdditionalIncludeDirectories) - ImTextureID=ImU64;_UNICODE;UNICODE;%(PreprocessorDefinitions) - /utf-8 %(AdditionalOptions) - - - true - true - true - d3d12.lib;d3dcompiler.lib;dxgi.lib;%(AdditionalDependencies) - %(AdditionalLibraryDirectories) - Console - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends;%(AdditionalIncludeDirectories) - ImTextureID=ImU64;_UNICODE;UNICODE;%(PreprocessorDefinitions) - /utf-8 %(AdditionalOptions) - - - true - true - true - d3d12.lib;d3dcompiler.lib;dxgi.lib;%(AdditionalDependencies) - %(AdditionalLibraryDirectories) - Console - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx12/example_win32_directx12.vcxproj.filters b/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx12/example_win32_directx12.vcxproj.filters deleted file mode 100644 index 23a9952..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx12/example_win32_directx12.vcxproj.filters +++ /dev/null @@ -1,65 +0,0 @@ - - - - - {fb3d294f-51ec-478e-a627-25831c80fefd} - - - {4f33ddea-9910-456d-b868-4267eb3c2b19} - - - - - imgui - - - imgui - - - imgui - - - sources - - - sources - - - - - imgui - - - sources - - - imgui - - - imgui - - - sources - - - sources - - - imgui - - - imgui - - - - - - imgui - - - - - imgui - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx12/main.cpp b/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx12/main.cpp deleted file mode 100644 index 1ef5ae8..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx12/main.cpp +++ /dev/null @@ -1,488 +0,0 @@ -// Dear ImGui: standalone example application for DirectX 12 - -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -// Important: to compile on 32-bit systems, the DirectX12 backend requires code to be compiled with '#define ImTextureID ImU64'. -// This is because we need ImTextureID to carry a 64-bit value and by default ImTextureID is defined as void*. -// This define is set in the example .vcxproj file and need to be replicated in your app or by adding it to your imconfig.h file. - -#include "imgui.h" -#include "imgui_impl_win32.h" -#include "imgui_impl_dx12.h" -#include -#include -#include - -#ifdef _DEBUG -#define DX12_ENABLE_DEBUG_LAYER -#endif - -#ifdef DX12_ENABLE_DEBUG_LAYER -#include -#pragma comment(lib, "dxguid.lib") -#endif - -struct FrameContext -{ - ID3D12CommandAllocator* CommandAllocator; - UINT64 FenceValue; -}; - -// Data -static int const NUM_FRAMES_IN_FLIGHT = 3; -static FrameContext g_frameContext[NUM_FRAMES_IN_FLIGHT] = {}; -static UINT g_frameIndex = 0; - -static int const NUM_BACK_BUFFERS = 3; -static ID3D12Device* g_pd3dDevice = nullptr; -static ID3D12DescriptorHeap* g_pd3dRtvDescHeap = nullptr; -static ID3D12DescriptorHeap* g_pd3dSrvDescHeap = nullptr; -static ID3D12CommandQueue* g_pd3dCommandQueue = nullptr; -static ID3D12GraphicsCommandList* g_pd3dCommandList = nullptr; -static ID3D12Fence* g_fence = nullptr; -static HANDLE g_fenceEvent = nullptr; -static UINT64 g_fenceLastSignaledValue = 0; -static IDXGISwapChain3* g_pSwapChain = nullptr; -static HANDLE g_hSwapChainWaitableObject = nullptr; -static ID3D12Resource* g_mainRenderTargetResource[NUM_BACK_BUFFERS] = {}; -static D3D12_CPU_DESCRIPTOR_HANDLE g_mainRenderTargetDescriptor[NUM_BACK_BUFFERS] = {}; - -// Forward declarations of helper functions -bool CreateDeviceD3D(HWND hWnd); -void CleanupDeviceD3D(); -void CreateRenderTarget(); -void CleanupRenderTarget(); -void WaitForLastSubmittedFrame(); -FrameContext* WaitForNextFrameResources(); -LRESULT WINAPI WndProc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam); - -// Main code -int main(int, char**) -{ - // Create application window - //ImGui_ImplWin32_EnableDpiAwareness(); - WNDCLASSEXW wc = { sizeof(wc), CS_CLASSDC, WndProc, 0L, 0L, GetModuleHandle(nullptr), nullptr, nullptr, nullptr, nullptr, L"ImGui Example", nullptr }; - ::RegisterClassExW(&wc); - HWND hwnd = ::CreateWindowW(wc.lpszClassName, L"Dear ImGui DirectX12 Example", WS_OVERLAPPEDWINDOW, 100, 100, 1280, 800, nullptr, nullptr, wc.hInstance, nullptr); - - // Initialize Direct3D - if (!CreateDeviceD3D(hwnd)) - { - CleanupDeviceD3D(); - ::UnregisterClassW(wc.lpszClassName, wc.hInstance); - return 1; - } - - // Show the window - ::ShowWindow(hwnd, SW_SHOWDEFAULT); - ::UpdateWindow(hwnd); - - // Setup Dear ImGui context - IMGUI_CHECKVERSION(); - ImGui::CreateContext(); - ImGuiIO& io = ImGui::GetIO(); (void)io; - io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard; // Enable Keyboard Controls - io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad; // Enable Gamepad Controls - io.ConfigFlags |= ImGuiConfigFlags_DockingEnable; // Enable Docking - io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable; // Enable Multi-Viewport / Platform Windows - //io.ConfigViewportsNoAutoMerge = true; - //io.ConfigViewportsNoTaskBarIcon = true; - - // Setup Dear ImGui style - ImGui::StyleColorsDark(); - //ImGui::StyleColorsLight(); - - // When viewports are enabled we tweak WindowRounding/WindowBg so platform windows can look identical to regular ones. - ImGuiStyle& style = ImGui::GetStyle(); - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - style.WindowRounding = 0.0f; - style.Colors[ImGuiCol_WindowBg].w = 1.0f; - } - - // Setup Platform/Renderer backends - ImGui_ImplWin32_Init(hwnd); - ImGui_ImplDX12_Init(g_pd3dDevice, NUM_FRAMES_IN_FLIGHT, - DXGI_FORMAT_R8G8B8A8_UNORM, g_pd3dSrvDescHeap, - g_pd3dSrvDescHeap->GetCPUDescriptorHandleForHeapStart(), - g_pd3dSrvDescHeap->GetGPUDescriptorHandleForHeapStart()); - - // Load Fonts - // - If no fonts are loaded, dear imgui will use the default font. You can also load multiple fonts and use ImGui::PushFont()/PopFont() to select them. - // - AddFontFromFileTTF() will return the ImFont* so you can store it if you need to select the font among multiple. - // - If the file cannot be loaded, the function will return a nullptr. Please handle those errors in your application (e.g. use an assertion, or display an error and quit). - // - The fonts will be rasterized at a given size (w/ oversampling) and stored into a texture when calling ImFontAtlas::Build()/GetTexDataAsXXXX(), which ImGui_ImplXXXX_NewFrame below will call. - // - Use '#define IMGUI_ENABLE_FREETYPE' in your imconfig file to use Freetype for higher quality font rendering. - // - Read 'docs/FONTS.md' for more instructions and details. - // - Remember that in C/C++ if you want to include a backslash \ in a string literal you need to write a double backslash \\ ! - //io.Fonts->AddFontDefault(); - //io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\segoeui.ttf", 18.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/DroidSans.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Roboto-Medium.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Cousine-Regular.ttf", 15.0f); - //ImFont* font = io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\ArialUni.ttf", 18.0f, nullptr, io.Fonts->GetGlyphRangesJapanese()); - //IM_ASSERT(font != nullptr); - - // Our state - bool show_demo_window = true; - bool show_another_window = false; - ImVec4 clear_color = ImVec4(0.45f, 0.55f, 0.60f, 1.00f); - - // Main loop - bool done = false; - while (!done) - { - // Poll and handle messages (inputs, window resize, etc.) - // See the WndProc() function below for our to dispatch events to the Win32 backend. - MSG msg; - while (::PeekMessage(&msg, nullptr, 0U, 0U, PM_REMOVE)) - { - ::TranslateMessage(&msg); - ::DispatchMessage(&msg); - if (msg.message == WM_QUIT) - done = true; - } - if (done) - break; - - // Start the Dear ImGui frame - ImGui_ImplDX12_NewFrame(); - ImGui_ImplWin32_NewFrame(); - ImGui::NewFrame(); - - // 1. Show the big demo window (Most of the sample code is in ImGui::ShowDemoWindow()! You can browse its code to learn more about Dear ImGui!). - if (show_demo_window) - ImGui::ShowDemoWindow(&show_demo_window); - - // 2. Show a simple window that we create ourselves. We use a Begin/End pair to create a named window. - { - static float f = 0.0f; - static int counter = 0; - - ImGui::Begin("Hello, world!"); // Create a window called "Hello, world!" and append into it. - - ImGui::Text("This is some useful text."); // Display some text (you can use a format strings too) - ImGui::Checkbox("Demo Window", &show_demo_window); // Edit bools storing our window open/close state - ImGui::Checkbox("Another Window", &show_another_window); - - ImGui::SliderFloat("float", &f, 0.0f, 1.0f); // Edit 1 float using a slider from 0.0f to 1.0f - ImGui::ColorEdit3("clear color", (float*)&clear_color); // Edit 3 floats representing a color - - if (ImGui::Button("Button")) // Buttons return true when clicked (most widgets return true when edited/activated) - counter++; - ImGui::SameLine(); - ImGui::Text("counter = %d", counter); - - ImGui::Text("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / io.Framerate, io.Framerate); - ImGui::End(); - } - - // 3. Show another simple window. - if (show_another_window) - { - ImGui::Begin("Another Window", &show_another_window); // Pass a pointer to our bool variable (the window will have a closing button that will clear the bool when clicked) - ImGui::Text("Hello from another window!"); - if (ImGui::Button("Close Me")) - show_another_window = false; - ImGui::End(); - } - - // Rendering - ImGui::Render(); - - FrameContext* frameCtx = WaitForNextFrameResources(); - UINT backBufferIdx = g_pSwapChain->GetCurrentBackBufferIndex(); - frameCtx->CommandAllocator->Reset(); - - D3D12_RESOURCE_BARRIER barrier = {}; - barrier.Type = D3D12_RESOURCE_BARRIER_TYPE_TRANSITION; - barrier.Flags = D3D12_RESOURCE_BARRIER_FLAG_NONE; - barrier.Transition.pResource = g_mainRenderTargetResource[backBufferIdx]; - barrier.Transition.Subresource = D3D12_RESOURCE_BARRIER_ALL_SUBRESOURCES; - barrier.Transition.StateBefore = D3D12_RESOURCE_STATE_PRESENT; - barrier.Transition.StateAfter = D3D12_RESOURCE_STATE_RENDER_TARGET; - g_pd3dCommandList->Reset(frameCtx->CommandAllocator, nullptr); - g_pd3dCommandList->ResourceBarrier(1, &barrier); - - // Render Dear ImGui graphics - const float clear_color_with_alpha[4] = { clear_color.x * clear_color.w, clear_color.y * clear_color.w, clear_color.z * clear_color.w, clear_color.w }; - g_pd3dCommandList->ClearRenderTargetView(g_mainRenderTargetDescriptor[backBufferIdx], clear_color_with_alpha, 0, nullptr); - g_pd3dCommandList->OMSetRenderTargets(1, &g_mainRenderTargetDescriptor[backBufferIdx], FALSE, nullptr); - g_pd3dCommandList->SetDescriptorHeaps(1, &g_pd3dSrvDescHeap); - ImGui_ImplDX12_RenderDrawData(ImGui::GetDrawData(), g_pd3dCommandList); - barrier.Transition.StateBefore = D3D12_RESOURCE_STATE_RENDER_TARGET; - barrier.Transition.StateAfter = D3D12_RESOURCE_STATE_PRESENT; - g_pd3dCommandList->ResourceBarrier(1, &barrier); - g_pd3dCommandList->Close(); - - g_pd3dCommandQueue->ExecuteCommandLists(1, (ID3D12CommandList* const*)&g_pd3dCommandList); - - // Update and Render additional Platform Windows - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - ImGui::UpdatePlatformWindows(); - ImGui::RenderPlatformWindowsDefault(nullptr, (void*)g_pd3dCommandList); - } - - g_pSwapChain->Present(1, 0); // Present with vsync - //g_pSwapChain->Present(0, 0); // Present without vsync - - UINT64 fenceValue = g_fenceLastSignaledValue + 1; - g_pd3dCommandQueue->Signal(g_fence, fenceValue); - g_fenceLastSignaledValue = fenceValue; - frameCtx->FenceValue = fenceValue; - } - - WaitForLastSubmittedFrame(); - - // Cleanup - ImGui_ImplDX12_Shutdown(); - ImGui_ImplWin32_Shutdown(); - ImGui::DestroyContext(); - - CleanupDeviceD3D(); - ::DestroyWindow(hwnd); - ::UnregisterClassW(wc.lpszClassName, wc.hInstance); - - return 0; -} - -// Helper functions -bool CreateDeviceD3D(HWND hWnd) -{ - // Setup swap chain - DXGI_SWAP_CHAIN_DESC1 sd; - { - ZeroMemory(&sd, sizeof(sd)); - sd.BufferCount = NUM_BACK_BUFFERS; - sd.Width = 0; - sd.Height = 0; - sd.Format = DXGI_FORMAT_R8G8B8A8_UNORM; - sd.Flags = DXGI_SWAP_CHAIN_FLAG_FRAME_LATENCY_WAITABLE_OBJECT; - sd.BufferUsage = DXGI_USAGE_RENDER_TARGET_OUTPUT; - sd.SampleDesc.Count = 1; - sd.SampleDesc.Quality = 0; - sd.SwapEffect = DXGI_SWAP_EFFECT_FLIP_DISCARD; - sd.AlphaMode = DXGI_ALPHA_MODE_UNSPECIFIED; - sd.Scaling = DXGI_SCALING_STRETCH; - sd.Stereo = FALSE; - } - - // [DEBUG] Enable debug interface -#ifdef DX12_ENABLE_DEBUG_LAYER - ID3D12Debug* pdx12Debug = nullptr; - if (SUCCEEDED(D3D12GetDebugInterface(IID_PPV_ARGS(&pdx12Debug)))) - pdx12Debug->EnableDebugLayer(); -#endif - - // Create device - D3D_FEATURE_LEVEL featureLevel = D3D_FEATURE_LEVEL_11_0; - if (D3D12CreateDevice(nullptr, featureLevel, IID_PPV_ARGS(&g_pd3dDevice)) != S_OK) - return false; - - // [DEBUG] Setup debug interface to break on any warnings/errors -#ifdef DX12_ENABLE_DEBUG_LAYER - if (pdx12Debug != nullptr) - { - ID3D12InfoQueue* pInfoQueue = nullptr; - g_pd3dDevice->QueryInterface(IID_PPV_ARGS(&pInfoQueue)); - pInfoQueue->SetBreakOnSeverity(D3D12_MESSAGE_SEVERITY_ERROR, true); - pInfoQueue->SetBreakOnSeverity(D3D12_MESSAGE_SEVERITY_CORRUPTION, true); - pInfoQueue->SetBreakOnSeverity(D3D12_MESSAGE_SEVERITY_WARNING, true); - pInfoQueue->Release(); - pdx12Debug->Release(); - } -#endif - - { - D3D12_DESCRIPTOR_HEAP_DESC desc = {}; - desc.Type = D3D12_DESCRIPTOR_HEAP_TYPE_RTV; - desc.NumDescriptors = NUM_BACK_BUFFERS; - desc.Flags = D3D12_DESCRIPTOR_HEAP_FLAG_NONE; - desc.NodeMask = 1; - if (g_pd3dDevice->CreateDescriptorHeap(&desc, IID_PPV_ARGS(&g_pd3dRtvDescHeap)) != S_OK) - return false; - - SIZE_T rtvDescriptorSize = g_pd3dDevice->GetDescriptorHandleIncrementSize(D3D12_DESCRIPTOR_HEAP_TYPE_RTV); - D3D12_CPU_DESCRIPTOR_HANDLE rtvHandle = g_pd3dRtvDescHeap->GetCPUDescriptorHandleForHeapStart(); - for (UINT i = 0; i < NUM_BACK_BUFFERS; i++) - { - g_mainRenderTargetDescriptor[i] = rtvHandle; - rtvHandle.ptr += rtvDescriptorSize; - } - } - - { - D3D12_DESCRIPTOR_HEAP_DESC desc = {}; - desc.Type = D3D12_DESCRIPTOR_HEAP_TYPE_CBV_SRV_UAV; - desc.NumDescriptors = 1; - desc.Flags = D3D12_DESCRIPTOR_HEAP_FLAG_SHADER_VISIBLE; - if (g_pd3dDevice->CreateDescriptorHeap(&desc, IID_PPV_ARGS(&g_pd3dSrvDescHeap)) != S_OK) - return false; - } - - { - D3D12_COMMAND_QUEUE_DESC desc = {}; - desc.Type = D3D12_COMMAND_LIST_TYPE_DIRECT; - desc.Flags = D3D12_COMMAND_QUEUE_FLAG_NONE; - desc.NodeMask = 1; - if (g_pd3dDevice->CreateCommandQueue(&desc, IID_PPV_ARGS(&g_pd3dCommandQueue)) != S_OK) - return false; - } - - for (UINT i = 0; i < NUM_FRAMES_IN_FLIGHT; i++) - if (g_pd3dDevice->CreateCommandAllocator(D3D12_COMMAND_LIST_TYPE_DIRECT, IID_PPV_ARGS(&g_frameContext[i].CommandAllocator)) != S_OK) - return false; - - if (g_pd3dDevice->CreateCommandList(0, D3D12_COMMAND_LIST_TYPE_DIRECT, g_frameContext[0].CommandAllocator, nullptr, IID_PPV_ARGS(&g_pd3dCommandList)) != S_OK || - g_pd3dCommandList->Close() != S_OK) - return false; - - if (g_pd3dDevice->CreateFence(0, D3D12_FENCE_FLAG_NONE, IID_PPV_ARGS(&g_fence)) != S_OK) - return false; - - g_fenceEvent = CreateEvent(nullptr, FALSE, FALSE, nullptr); - if (g_fenceEvent == nullptr) - return false; - - { - IDXGIFactory4* dxgiFactory = nullptr; - IDXGISwapChain1* swapChain1 = nullptr; - if (CreateDXGIFactory1(IID_PPV_ARGS(&dxgiFactory)) != S_OK) - return false; - if (dxgiFactory->CreateSwapChainForHwnd(g_pd3dCommandQueue, hWnd, &sd, nullptr, nullptr, &swapChain1) != S_OK) - return false; - if (swapChain1->QueryInterface(IID_PPV_ARGS(&g_pSwapChain)) != S_OK) - return false; - swapChain1->Release(); - dxgiFactory->Release(); - g_pSwapChain->SetMaximumFrameLatency(NUM_BACK_BUFFERS); - g_hSwapChainWaitableObject = g_pSwapChain->GetFrameLatencyWaitableObject(); - } - - CreateRenderTarget(); - return true; -} - -void CleanupDeviceD3D() -{ - CleanupRenderTarget(); - if (g_pSwapChain) { g_pSwapChain->SetFullscreenState(false, nullptr); g_pSwapChain->Release(); g_pSwapChain = nullptr; } - if (g_hSwapChainWaitableObject != nullptr) { CloseHandle(g_hSwapChainWaitableObject); } - for (UINT i = 0; i < NUM_FRAMES_IN_FLIGHT; i++) - if (g_frameContext[i].CommandAllocator) { g_frameContext[i].CommandAllocator->Release(); g_frameContext[i].CommandAllocator = nullptr; } - if (g_pd3dCommandQueue) { g_pd3dCommandQueue->Release(); g_pd3dCommandQueue = nullptr; } - if (g_pd3dCommandList) { g_pd3dCommandList->Release(); g_pd3dCommandList = nullptr; } - if (g_pd3dRtvDescHeap) { g_pd3dRtvDescHeap->Release(); g_pd3dRtvDescHeap = nullptr; } - if (g_pd3dSrvDescHeap) { g_pd3dSrvDescHeap->Release(); g_pd3dSrvDescHeap = nullptr; } - if (g_fence) { g_fence->Release(); g_fence = nullptr; } - if (g_fenceEvent) { CloseHandle(g_fenceEvent); g_fenceEvent = nullptr; } - if (g_pd3dDevice) { g_pd3dDevice->Release(); g_pd3dDevice = nullptr; } - -#ifdef DX12_ENABLE_DEBUG_LAYER - IDXGIDebug1* pDebug = nullptr; - if (SUCCEEDED(DXGIGetDebugInterface1(0, IID_PPV_ARGS(&pDebug)))) - { - pDebug->ReportLiveObjects(DXGI_DEBUG_ALL, DXGI_DEBUG_RLO_SUMMARY); - pDebug->Release(); - } -#endif -} - -void CreateRenderTarget() -{ - for (UINT i = 0; i < NUM_BACK_BUFFERS; i++) - { - ID3D12Resource* pBackBuffer = nullptr; - g_pSwapChain->GetBuffer(i, IID_PPV_ARGS(&pBackBuffer)); - g_pd3dDevice->CreateRenderTargetView(pBackBuffer, nullptr, g_mainRenderTargetDescriptor[i]); - g_mainRenderTargetResource[i] = pBackBuffer; - } -} - -void CleanupRenderTarget() -{ - WaitForLastSubmittedFrame(); - - for (UINT i = 0; i < NUM_BACK_BUFFERS; i++) - if (g_mainRenderTargetResource[i]) { g_mainRenderTargetResource[i]->Release(); g_mainRenderTargetResource[i] = nullptr; } -} - -void WaitForLastSubmittedFrame() -{ - FrameContext* frameCtx = &g_frameContext[g_frameIndex % NUM_FRAMES_IN_FLIGHT]; - - UINT64 fenceValue = frameCtx->FenceValue; - if (fenceValue == 0) - return; // No fence was signaled - - frameCtx->FenceValue = 0; - if (g_fence->GetCompletedValue() >= fenceValue) - return; - - g_fence->SetEventOnCompletion(fenceValue, g_fenceEvent); - WaitForSingleObject(g_fenceEvent, INFINITE); -} - -FrameContext* WaitForNextFrameResources() -{ - UINT nextFrameIndex = g_frameIndex + 1; - g_frameIndex = nextFrameIndex; - - HANDLE waitableObjects[] = { g_hSwapChainWaitableObject, nullptr }; - DWORD numWaitableObjects = 1; - - FrameContext* frameCtx = &g_frameContext[nextFrameIndex % NUM_FRAMES_IN_FLIGHT]; - UINT64 fenceValue = frameCtx->FenceValue; - if (fenceValue != 0) // means no fence was signaled - { - frameCtx->FenceValue = 0; - g_fence->SetEventOnCompletion(fenceValue, g_fenceEvent); - waitableObjects[1] = g_fenceEvent; - numWaitableObjects = 2; - } - - WaitForMultipleObjects(numWaitableObjects, waitableObjects, TRUE, INFINITE); - - return frameCtx; -} - -// Forward declare message handler from imgui_impl_win32.cpp -extern IMGUI_IMPL_API LRESULT ImGui_ImplWin32_WndProcHandler(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam); - -// Win32 message handler -// You can read the io.WantCaptureMouse, io.WantCaptureKeyboard flags to tell if dear imgui wants to use your inputs. -// - When io.WantCaptureMouse is true, do not dispatch mouse input data to your main application, or clear/overwrite your copy of the mouse data. -// - When io.WantCaptureKeyboard is true, do not dispatch keyboard input data to your main application, or clear/overwrite your copy of the keyboard data. -// Generally you may always pass all inputs to dear imgui, and hide them from your application based on those two flags. -LRESULT WINAPI WndProc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam) -{ - if (ImGui_ImplWin32_WndProcHandler(hWnd, msg, wParam, lParam)) - return true; - - switch (msg) - { - case WM_SIZE: - if (g_pd3dDevice != nullptr && wParam != SIZE_MINIMIZED) - { - WaitForLastSubmittedFrame(); - CleanupRenderTarget(); - HRESULT result = g_pSwapChain->ResizeBuffers(0, (UINT)LOWORD(lParam), (UINT)HIWORD(lParam), DXGI_FORMAT_UNKNOWN, DXGI_SWAP_CHAIN_FLAG_FRAME_LATENCY_WAITABLE_OBJECT); - assert(SUCCEEDED(result) && "Failed to resize swapchain."); - CreateRenderTarget(); - } - return 0; - case WM_SYSCOMMAND: - if ((wParam & 0xfff0) == SC_KEYMENU) // Disable ALT application menu - return 0; - break; - case WM_DESTROY: - ::PostQuitMessage(0); - return 0; - } - return ::DefWindowProcW(hWnd, msg, wParam, lParam); -} diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx9/build_win32.bat b/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx9/build_win32.bat deleted file mode 100644 index ece5ea1..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx9/build_win32.bat +++ /dev/null @@ -1,8 +0,0 @@ -@REM Build for Visual Studio compiler. Run your copy of vcvars32.bat or vcvarsall.bat to setup command-line compiler. -@set OUT_DIR=Debug -@set OUT_EXE=example_win32_directx9 -@set INCLUDES=/I..\.. /I..\..\backends /I "%DXSDK_DIR%/Include" -@set SOURCES=main.cpp ..\..\backends\imgui_impl_dx9.cpp ..\..\backends\imgui_impl_win32.cpp ..\..\imgui*.cpp -@set LIBS=/LIBPATH:"%DXSDK_DIR%/Lib/x86" d3d9.lib -mkdir %OUT_DIR% -cl /nologo /Zi /MD /utf-8 %INCLUDES% /D UNICODE /D _UNICODE %SOURCES% /Fe%OUT_DIR%/%OUT_EXE%.exe /Fo%OUT_DIR%/ /link %LIBS% diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx9/example_win32_directx9.vcxproj b/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx9/example_win32_directx9.vcxproj deleted file mode 100644 index 8c3f995..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx9/example_win32_directx9.vcxproj +++ /dev/null @@ -1,176 +0,0 @@ - - - - - Debug - Win32 - - - Debug - x64 - - - Release - Win32 - - - Release - x64 - - - - {4165A294-21F2-44CA-9B38-E3F935ABADF5} - example_win32_directx9 - 8.1 - - - - Application - true - Unicode - v140 - - - Application - true - Unicode - v140 - - - Application - false - true - Unicode - v140 - - - Application - false - true - Unicode - v140 - - - - - - - - - - - - - - - - - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - - - - Level4 - Disabled - ..\..;..\..\backends;%(AdditionalIncludeDirectories);$(DXSDK_DIR)Include; - /utf-8 %(AdditionalOptions) - - - true - $(DXSDK_DIR)/Lib/x86;%(AdditionalLibraryDirectories) - d3d9.lib;%(AdditionalDependencies) - Console - - - - - Level4 - Disabled - ..\..;..\..\backends;%(AdditionalIncludeDirectories);$(DXSDK_DIR)Include; - /utf-8 %(AdditionalOptions) - - - true - $(DXSDK_DIR)/Lib/x64;%(AdditionalLibraryDirectories) - d3d9.lib;%(AdditionalDependencies) - Console - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends;%(AdditionalIncludeDirectories);$(DXSDK_DIR)Include; - false - /utf-8 %(AdditionalOptions) - - - true - true - true - $(DXSDK_DIR)/Lib/x86;%(AdditionalLibraryDirectories) - d3d9.lib;%(AdditionalDependencies) - Console - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends;%(AdditionalIncludeDirectories);$(DXSDK_DIR)Include; - false - /utf-8 %(AdditionalOptions) - - - true - true - true - $(DXSDK_DIR)/Lib/x64;%(AdditionalLibraryDirectories) - d3d9.lib;%(AdditionalDependencies) - Console - - - - - - - - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx9/example_win32_directx9.vcxproj.filters b/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx9/example_win32_directx9.vcxproj.filters deleted file mode 100644 index 5ed89d6..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx9/example_win32_directx9.vcxproj.filters +++ /dev/null @@ -1,64 +0,0 @@ - - - - - {4FC737F1-C7A5-4376-A066-2A32D752A2FF} - cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx - - - {a82cba23-9de0-45c2-b1e3-2eb1666702de} - - - - - sources - - - imgui - - - imgui - - - imgui - - - sources - - - sources - - - imgui - - - imgui - - - - - imgui - - - imgui - - - imgui - - - sources - - - sources - - - - - - imgui - - - imgui - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx9/main.cpp b/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx9/main.cpp deleted file mode 100644 index 89190b0..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_directx9/main.cpp +++ /dev/null @@ -1,282 +0,0 @@ -// Dear ImGui: standalone example application for DirectX 9 - -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -#include "imgui.h" -#include "imgui_impl_dx9.h" -#include "imgui_impl_win32.h" -#include -#include - -// Data -static LPDIRECT3D9 g_pD3D = nullptr; -static LPDIRECT3DDEVICE9 g_pd3dDevice = nullptr; -static UINT g_ResizeWidth = 0, g_ResizeHeight = 0; -static D3DPRESENT_PARAMETERS g_d3dpp = {}; - -// Forward declarations of helper functions -bool CreateDeviceD3D(HWND hWnd); -void CleanupDeviceD3D(); -void ResetDevice(); -LRESULT WINAPI WndProc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam); - -// Main code -int main(int, char**) -{ - // Create application window - //ImGui_ImplWin32_EnableDpiAwareness(); - WNDCLASSEXW wc = { sizeof(wc), CS_CLASSDC, WndProc, 0L, 0L, GetModuleHandle(nullptr), nullptr, nullptr, nullptr, nullptr, L"ImGui Example", nullptr }; - ::RegisterClassExW(&wc); - HWND hwnd = ::CreateWindowW(wc.lpszClassName, L"Dear ImGui DirectX9 Example", WS_OVERLAPPEDWINDOW, 100, 100, 1280, 800, nullptr, nullptr, wc.hInstance, nullptr); - - // Initialize Direct3D - if (!CreateDeviceD3D(hwnd)) - { - CleanupDeviceD3D(); - ::UnregisterClassW(wc.lpszClassName, wc.hInstance); - return 1; - } - - // Show the window - ::ShowWindow(hwnd, SW_SHOWDEFAULT); - ::UpdateWindow(hwnd); - - // Setup Dear ImGui context - IMGUI_CHECKVERSION(); - ImGui::CreateContext(); - ImGuiIO& io = ImGui::GetIO(); (void)io; - io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard; // Enable Keyboard Controls - io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad; // Enable Gamepad Controls - io.ConfigFlags |= ImGuiConfigFlags_DockingEnable; // Enable Docking - io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable; // Enable Multi-Viewport / Platform Windows - //io.ConfigViewportsNoAutoMerge = true; - //io.ConfigViewportsNoTaskBarIcon = true; - - // Setup Dear ImGui style - ImGui::StyleColorsDark(); - //ImGui::StyleColorsLight(); - - // When viewports are enabled we tweak WindowRounding/WindowBg so platform windows can look identical to regular ones. - ImGuiStyle& style = ImGui::GetStyle(); - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - style.WindowRounding = 0.0f; - style.Colors[ImGuiCol_WindowBg].w = 1.0f; - } - - // Setup Platform/Renderer backends - ImGui_ImplWin32_Init(hwnd); - ImGui_ImplDX9_Init(g_pd3dDevice); - - // Load Fonts - // - If no fonts are loaded, dear imgui will use the default font. You can also load multiple fonts and use ImGui::PushFont()/PopFont() to select them. - // - AddFontFromFileTTF() will return the ImFont* so you can store it if you need to select the font among multiple. - // - If the file cannot be loaded, the function will return a nullptr. Please handle those errors in your application (e.g. use an assertion, or display an error and quit). - // - The fonts will be rasterized at a given size (w/ oversampling) and stored into a texture when calling ImFontAtlas::Build()/GetTexDataAsXXXX(), which ImGui_ImplXXXX_NewFrame below will call. - // - Use '#define IMGUI_ENABLE_FREETYPE' in your imconfig file to use Freetype for higher quality font rendering. - // - Read 'docs/FONTS.md' for more instructions and details. - // - Remember that in C/C++ if you want to include a backslash \ in a string literal you need to write a double backslash \\ ! - //io.Fonts->AddFontDefault(); - //io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\segoeui.ttf", 18.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/DroidSans.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Roboto-Medium.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Cousine-Regular.ttf", 15.0f); - //ImFont* font = io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\ArialUni.ttf", 18.0f, nullptr, io.Fonts->GetGlyphRangesJapanese()); - //IM_ASSERT(font != nullptr); - - // Our state - bool show_demo_window = true; - bool show_another_window = false; - ImVec4 clear_color = ImVec4(0.45f, 0.55f, 0.60f, 1.00f); - - // Main loop - bool done = false; - while (!done) - { - // Poll and handle messages (inputs, window resize, etc.) - // See the WndProc() function below for our to dispatch events to the Win32 backend. - MSG msg; - while (::PeekMessage(&msg, nullptr, 0U, 0U, PM_REMOVE)) - { - ::TranslateMessage(&msg); - ::DispatchMessage(&msg); - if (msg.message == WM_QUIT) - done = true; - } - if (done) - break; - - // Handle window resize (we don't resize directly in the WM_SIZE handler) - if (g_ResizeWidth != 0 && g_ResizeHeight != 0) - { - g_d3dpp.BackBufferWidth = g_ResizeWidth; - g_d3dpp.BackBufferHeight = g_ResizeHeight; - g_ResizeWidth = g_ResizeHeight = 0; - ResetDevice(); - } - - // Start the Dear ImGui frame - ImGui_ImplDX9_NewFrame(); - ImGui_ImplWin32_NewFrame(); - ImGui::NewFrame(); - - // 1. Show the big demo window (Most of the sample code is in ImGui::ShowDemoWindow()! You can browse its code to learn more about Dear ImGui!). - if (show_demo_window) - ImGui::ShowDemoWindow(&show_demo_window); - - // 2. Show a simple window that we create ourselves. We use a Begin/End pair to create a named window. - { - static float f = 0.0f; - static int counter = 0; - - ImGui::Begin("Hello, world!"); // Create a window called "Hello, world!" and append into it. - - ImGui::Text("This is some useful text."); // Display some text (you can use a format strings too) - ImGui::Checkbox("Demo Window", &show_demo_window); // Edit bools storing our window open/close state - ImGui::Checkbox("Another Window", &show_another_window); - - ImGui::SliderFloat("float", &f, 0.0f, 1.0f); // Edit 1 float using a slider from 0.0f to 1.0f - ImGui::ColorEdit3("clear color", (float*)&clear_color); // Edit 3 floats representing a color - - if (ImGui::Button("Button")) // Buttons return true when clicked (most widgets return true when edited/activated) - counter++; - ImGui::SameLine(); - ImGui::Text("counter = %d", counter); - - ImGui::Text("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / io.Framerate, io.Framerate); - ImGui::End(); - } - - // 3. Show another simple window. - if (show_another_window) - { - ImGui::Begin("Another Window", &show_another_window); // Pass a pointer to our bool variable (the window will have a closing button that will clear the bool when clicked) - ImGui::Text("Hello from another window!"); - if (ImGui::Button("Close Me")) - show_another_window = false; - ImGui::End(); - } - - // Rendering - ImGui::EndFrame(); - g_pd3dDevice->SetRenderState(D3DRS_ZENABLE, FALSE); - g_pd3dDevice->SetRenderState(D3DRS_ALPHABLENDENABLE, FALSE); - g_pd3dDevice->SetRenderState(D3DRS_SCISSORTESTENABLE, FALSE); - D3DCOLOR clear_col_dx = D3DCOLOR_RGBA((int)(clear_color.x*clear_color.w*255.0f), (int)(clear_color.y*clear_color.w*255.0f), (int)(clear_color.z*clear_color.w*255.0f), (int)(clear_color.w*255.0f)); - g_pd3dDevice->Clear(0, nullptr, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, clear_col_dx, 1.0f, 0); - if (g_pd3dDevice->BeginScene() >= 0) - { - ImGui::Render(); - ImGui_ImplDX9_RenderDrawData(ImGui::GetDrawData()); - g_pd3dDevice->EndScene(); - } - - // Update and Render additional Platform Windows - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - ImGui::UpdatePlatformWindows(); - ImGui::RenderPlatformWindowsDefault(); - } - - HRESULT result = g_pd3dDevice->Present(nullptr, nullptr, nullptr, nullptr); - - // Handle loss of D3D9 device - if (result == D3DERR_DEVICELOST && g_pd3dDevice->TestCooperativeLevel() == D3DERR_DEVICENOTRESET) - ResetDevice(); - } - - ImGui_ImplDX9_Shutdown(); - ImGui_ImplWin32_Shutdown(); - ImGui::DestroyContext(); - - CleanupDeviceD3D(); - ::DestroyWindow(hwnd); - ::UnregisterClassW(wc.lpszClassName, wc.hInstance); - - return 0; -} - -// Helper functions -bool CreateDeviceD3D(HWND hWnd) -{ - if ((g_pD3D = Direct3DCreate9(D3D_SDK_VERSION)) == nullptr) - return false; - - // Create the D3DDevice - ZeroMemory(&g_d3dpp, sizeof(g_d3dpp)); - g_d3dpp.Windowed = TRUE; - g_d3dpp.SwapEffect = D3DSWAPEFFECT_DISCARD; - g_d3dpp.BackBufferFormat = D3DFMT_UNKNOWN; // Need to use an explicit format with alpha if needing per-pixel alpha composition. - g_d3dpp.EnableAutoDepthStencil = TRUE; - g_d3dpp.AutoDepthStencilFormat = D3DFMT_D16; - g_d3dpp.PresentationInterval = D3DPRESENT_INTERVAL_ONE; // Present with vsync - //g_d3dpp.PresentationInterval = D3DPRESENT_INTERVAL_IMMEDIATE; // Present without vsync, maximum unthrottled framerate - if (g_pD3D->CreateDevice(D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, hWnd, D3DCREATE_HARDWARE_VERTEXPROCESSING, &g_d3dpp, &g_pd3dDevice) < 0) - return false; - - return true; -} - -void CleanupDeviceD3D() -{ - if (g_pd3dDevice) { g_pd3dDevice->Release(); g_pd3dDevice = nullptr; } - if (g_pD3D) { g_pD3D->Release(); g_pD3D = nullptr; } -} - -void ResetDevice() -{ - ImGui_ImplDX9_InvalidateDeviceObjects(); - HRESULT hr = g_pd3dDevice->Reset(&g_d3dpp); - if (hr == D3DERR_INVALIDCALL) - IM_ASSERT(0); - ImGui_ImplDX9_CreateDeviceObjects(); -} - -#ifndef WM_DPICHANGED -#define WM_DPICHANGED 0x02E0 // From Windows SDK 8.1+ headers -#endif - -// Forward declare message handler from imgui_impl_win32.cpp -extern IMGUI_IMPL_API LRESULT ImGui_ImplWin32_WndProcHandler(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam); - -// Win32 message handler -// You can read the io.WantCaptureMouse, io.WantCaptureKeyboard flags to tell if dear imgui wants to use your inputs. -// - When io.WantCaptureMouse is true, do not dispatch mouse input data to your main application, or clear/overwrite your copy of the mouse data. -// - When io.WantCaptureKeyboard is true, do not dispatch keyboard input data to your main application, or clear/overwrite your copy of the keyboard data. -// Generally you may always pass all inputs to dear imgui, and hide them from your application based on those two flags. -LRESULT WINAPI WndProc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam) -{ - if (ImGui_ImplWin32_WndProcHandler(hWnd, msg, wParam, lParam)) - return true; - - switch (msg) - { - case WM_SIZE: - if (wParam == SIZE_MINIMIZED) - return 0; - g_ResizeWidth = (UINT)LOWORD(lParam); // Queue resize - g_ResizeHeight = (UINT)HIWORD(lParam); - return 0; - case WM_SYSCOMMAND: - if ((wParam & 0xfff0) == SC_KEYMENU) // Disable ALT application menu - return 0; - break; - case WM_DESTROY: - ::PostQuitMessage(0); - return 0; - case WM_DPICHANGED: - if (ImGui::GetIO().ConfigFlags & ImGuiConfigFlags_DpiEnableScaleViewports) - { - //const int dpi = HIWORD(wParam); - //printf("WM_DPICHANGED to %d (%.0f%%)\n", dpi, (float)dpi / 96.0f * 100.0f); - const RECT* suggested_rect = (RECT*)lParam; - ::SetWindowPos(hWnd, nullptr, suggested_rect->left, suggested_rect->top, suggested_rect->right - suggested_rect->left, suggested_rect->bottom - suggested_rect->top, SWP_NOZORDER | SWP_NOACTIVATE); - } - break; - } - return ::DefWindowProcW(hWnd, msg, wParam, lParam); -} diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_opengl3/build_win32.bat b/app/jni/src/libultraship/extern/ImGui/examples/example_win32_opengl3/build_win32.bat deleted file mode 100644 index 48df080..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_opengl3/build_win32.bat +++ /dev/null @@ -1,8 +0,0 @@ -@REM Build for Visual Studio compiler. Run your copy of vcvars32.bat or vcvarsall.bat to setup command-line compiler. -@set OUT_DIR=Debug -@set OUT_EXE=example_win32_opengl3 -@set INCLUDES=/I..\.. /I..\..\backends -@set SOURCES=main.cpp ..\..\backends\imgui_impl_opengl3.cpp ..\..\backends\imgui_impl_win32.cpp ..\..\imgui*.cpp -@set LIBS=opengl32.lib -mkdir %OUT_DIR% -cl /nologo /Zi /MD /utf-8 %INCLUDES% /D UNICODE /D _UNICODE %SOURCES% /Fe%OUT_DIR%/%OUT_EXE%.exe /Fo%OUT_DIR%/ /link %LIBS% diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_opengl3/example_win32_opengl3.vcxproj b/app/jni/src/libultraship/extern/ImGui/examples/example_win32_opengl3/example_win32_opengl3.vcxproj deleted file mode 100644 index 98fc38f..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_opengl3/example_win32_opengl3.vcxproj +++ /dev/null @@ -1,176 +0,0 @@ - - - - - Debug - Win32 - - - Debug - x64 - - - Release - Win32 - - - Release - x64 - - - - {C624E5FF-D4FE-4D35-9164-B8A91864F98E} - example_win32_opengl2 - 8.1 - - - - Application - true - Unicode - v140 - - - Application - true - Unicode - v140 - - - Application - false - true - Unicode - v140 - - - Application - false - true - Unicode - v140 - - - - - - - - - - - - - - - - - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - - - $(ProjectDir)$(Configuration)\ - $(ProjectDir)$(Configuration)\ - - - - Level4 - Disabled - ..\..;..\..\backends; - /utf-8 %(AdditionalOptions) - - - true - %(AdditionalLibraryDirectories) - opengl32.lib;%(AdditionalDependencies) - Console - - - - - Level4 - Disabled - ..\..;..\..\backends; - /utf-8 %(AdditionalOptions) - - - true - %(AdditionalLibraryDirectories) - opengl32.lib;%(AdditionalDependencies) - Console - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends; - false - /utf-8 %(AdditionalOptions) - - - true - true - true - %(AdditionalLibraryDirectories) - opengl32.lib;%(AdditionalDependencies) - Console - - - - - Level4 - MaxSpeed - true - true - ..\..;..\..\backends; - false - /utf-8 %(AdditionalOptions) - - - true - true - true - %(AdditionalLibraryDirectories) - opengl32.lib;%(AdditionalDependencies) - Console - - - - - - - - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_opengl3/example_win32_opengl3.vcxproj.filters b/app/jni/src/libultraship/extern/ImGui/examples/example_win32_opengl3/example_win32_opengl3.vcxproj.filters deleted file mode 100644 index 47ed299..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_opengl3/example_win32_opengl3.vcxproj.filters +++ /dev/null @@ -1,64 +0,0 @@ - - - - - {4FC737F1-C7A5-4376-A066-2A32D752A2FF} - cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx - - - {a82cba23-9de0-45c2-b1e3-2eb1666702de} - - - - - sources - - - imgui - - - imgui - - - imgui - - - imgui - - - sources - - - imgui - - - sources - - - - - imgui - - - imgui - - - imgui - - - sources - - - sources - - - sources - - - - - - sources - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_opengl3/main.cpp b/app/jni/src/libultraship/extern/ImGui/examples/example_win32_opengl3/main.cpp deleted file mode 100644 index 3dc71de..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/example_win32_opengl3/main.cpp +++ /dev/null @@ -1,308 +0,0 @@ -// Dear ImGui: standalone example application for Win32 + OpenGL 3 - -// Learn about Dear ImGui: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Documentation https://dearimgui.com/docs (same as your local docs/ folder). -// - Introduction, links and more at the top of imgui.cpp - -// This is provided for completeness, however it is strongly recommended you use OpenGL with SDL or GLFW. - -#include "imgui.h" -#include "imgui_impl_opengl3.h" -#include "imgui_impl_win32.h" -#ifndef WIN32_LEAN_AND_MEAN -#define WIN32_LEAN_AND_MEAN -#endif -#include -#include -#include - -// Data stored per platform window -struct WGL_WindowData { HDC hDC; }; - -// Data -static HGLRC g_hRC; -static WGL_WindowData g_MainWindow; -static int g_Width; -static int g_Height; - -// Forward declarations of helper functions -bool CreateDeviceWGL(HWND hWnd, WGL_WindowData* data); -void CleanupDeviceWGL(HWND hWnd, WGL_WindowData* data); -void ResetDeviceWGL(); -LRESULT WINAPI WndProc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam); - -// Support function for multi-viewports -// Unlike most other backend combination, we need specific hooks to combine Win32+OpenGL. -// We could in theory decide to support Win32-specific code in OpenGL backend via e.g. an hypothetical ImGui_ImplOpenGL3_InitForRawWin32(). -static void Hook_Renderer_CreateWindow(ImGuiViewport* viewport) -{ - assert(viewport->RendererUserData == NULL); - - WGL_WindowData* data = IM_NEW(WGL_WindowData); - CreateDeviceWGL((HWND)viewport->PlatformHandle, data); - viewport->RendererUserData = data; -} - -static void Hook_Renderer_DestroyWindow(ImGuiViewport* viewport) -{ - if (viewport->RendererUserData != NULL) - { - WGL_WindowData* data = (WGL_WindowData*)viewport->RendererUserData; - CleanupDeviceWGL((HWND)viewport->PlatformHandle, data); - IM_DELETE(data); - viewport->RendererUserData = NULL; - } -} - -static void Hook_Platform_RenderWindow(ImGuiViewport* viewport, void*) -{ - // Activate the platform window DC in the OpenGL rendering context - if (WGL_WindowData* data = (WGL_WindowData*)viewport->RendererUserData) - wglMakeCurrent(data->hDC, g_hRC); -} - -static void Hook_Renderer_SwapBuffers(ImGuiViewport* viewport, void*) -{ - if (WGL_WindowData* data = (WGL_WindowData*)viewport->RendererUserData) - ::SwapBuffers(data->hDC); -} - -// Main code -int main(int, char**) -{ - // Create application window - //ImGui_ImplWin32_EnableDpiAwareness(); - WNDCLASSEXW wc = { sizeof(wc), CS_OWNDC, WndProc, 0L, 0L, GetModuleHandle(NULL), NULL, NULL, NULL, NULL, L"ImGui Example", NULL }; - ::RegisterClassExW(&wc); - HWND hwnd = ::CreateWindowW(wc.lpszClassName, L"Dear ImGui Win32+OpenGL3 Example", WS_OVERLAPPEDWINDOW, 100, 100, 1280, 800, NULL, NULL, wc.hInstance, NULL); - - // Initialize OpenGL - if (!CreateDeviceWGL(hwnd, &g_MainWindow)) - { - CleanupDeviceWGL(hwnd, &g_MainWindow); - ::DestroyWindow(hwnd); - ::UnregisterClassW(wc.lpszClassName, wc.hInstance); - return 1; - } - wglMakeCurrent(g_MainWindow.hDC, g_hRC); - - // Show the window - ::ShowWindow(hwnd, SW_SHOWDEFAULT); - ::UpdateWindow(hwnd); - - // Setup Dear ImGui context - IMGUI_CHECKVERSION(); - ImGui::CreateContext(); - ImGuiIO& io = ImGui::GetIO(); (void)io; - io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard; // Enable Keyboard Controls - io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad; // Enable Gamepad Controls - io.ConfigFlags |= ImGuiConfigFlags_DockingEnable; // Enable Docking - io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable; // Enable Multi-Viewport / Platform Windows - - // Setup Dear ImGui style - ImGui::StyleColorsDark(); - //ImGui::StyleColorsClassic(); - - // When viewports are enabled we tweak WindowRounding/WindowBg so platform windows can look identical to regular ones. - ImGuiStyle& style = ImGui::GetStyle(); - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - style.WindowRounding = 0.0f; - style.Colors[ImGuiCol_WindowBg].w = 1.0f; - } - - // Setup Platform/Renderer backends - ImGui_ImplWin32_InitForOpenGL(hwnd); - ImGui_ImplOpenGL3_Init(); - - // Win32+GL needs specific hooks for viewport, as there are specific things needed to tie Win32 and GL api. - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - ImGuiPlatformIO& platform_io = ImGui::GetPlatformIO(); - IM_ASSERT(platform_io.Renderer_CreateWindow == NULL); - IM_ASSERT(platform_io.Renderer_DestroyWindow == NULL); - IM_ASSERT(platform_io.Renderer_SwapBuffers == NULL); - IM_ASSERT(platform_io.Platform_RenderWindow == NULL); - platform_io.Renderer_CreateWindow = Hook_Renderer_CreateWindow; - platform_io.Renderer_DestroyWindow = Hook_Renderer_DestroyWindow; - platform_io.Renderer_SwapBuffers = Hook_Renderer_SwapBuffers; - platform_io.Platform_RenderWindow = Hook_Platform_RenderWindow; - } - - // Load Fonts - // - If no fonts are loaded, dear imgui will use the default font. You can also load multiple fonts and use ImGui::PushFont()/PopFont() to select them. - // - AddFontFromFileTTF() will return the ImFont* so you can store it if you need to select the font among multiple. - // - If the file cannot be loaded, the function will return NULL. Please handle those errors in your application (e.g. use an assertion, or display an error and quit). - // - The fonts will be rasterized at a given size (w/ oversampling) and stored into a texture when calling ImFontAtlas::Build()/GetTexDataAsXXXX(), which ImGui_ImplXXXX_NewFrame below will call. - // - Use '#define IMGUI_ENABLE_FREETYPE' in your imconfig file to use Freetype for higher quality font rendering. - // - Read 'docs/FONTS.md' for more instructions and details. - // - Remember that in C/C++ if you want to include a backslash \ in a string literal you need to write a double backslash \\ ! - //io.Fonts->AddFontDefault(); - //io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\segoeui.ttf", 18.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/DroidSans.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Roboto-Medium.ttf", 16.0f); - //io.Fonts->AddFontFromFileTTF("../../misc/fonts/Cousine-Regular.ttf", 15.0f); - //ImFont* font = io.Fonts->AddFontFromFileTTF("c:\\Windows\\Fonts\\ArialUni.ttf", 18.0f, NULL, io.Fonts->GetGlyphRangesJapanese()); - //IM_ASSERT(font != NULL); - - // Our state - bool show_demo_window = true; - bool show_another_window = false; - ImVec4 clear_color = ImVec4(0.45f, 0.55f, 0.60f, 1.00f); - - // Main loop - bool done = false; - while (!done) - { - // Poll and handle messages (inputs, window resize, etc.) - // See the WndProc() function below for our to dispatch events to the Win32 backend. - MSG msg; - while (::PeekMessage(&msg, NULL, 0U, 0U, PM_REMOVE)) - { - ::TranslateMessage(&msg); - ::DispatchMessage(&msg); - if (msg.message == WM_QUIT) - done = true; - } - if (done) - break; - - // Start the Dear ImGui frame - ImGui_ImplOpenGL3_NewFrame(); - ImGui_ImplWin32_NewFrame(); - ImGui::NewFrame(); - - // 1. Show the big demo window (Most of the sample code is in ImGui::ShowDemoWindow()! You can browse its code to learn more about Dear ImGui!). - if (show_demo_window) - ImGui::ShowDemoWindow(&show_demo_window); - - // 2. Show a simple window that we create ourselves. We use a Begin/End pair to create a named window. - { - static float f = 0.0f; - static int counter = 0; - - ImGui::Begin("Hello, world!"); // Create a window called "Hello, world!" and append into it. - - ImGui::Text("This is some useful text."); // Display some text (you can use a format strings too) - ImGui::Checkbox("Demo Window", &show_demo_window); // Edit bools storing our window open/close state - ImGui::Checkbox("Another Window", &show_another_window); - - ImGui::SliderFloat("float", &f, 0.0f, 1.0f); // Edit 1 float using a slider from 0.0f to 1.0f - ImGui::ColorEdit3("clear color", (float*)&clear_color); // Edit 3 floats representing a color - - if (ImGui::Button("Button")) // Buttons return true when clicked (most widgets return true when edited/activated) - counter++; - ImGui::SameLine(); - ImGui::Text("counter = %d", counter); - - ImGui::Text("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / io.Framerate, io.Framerate); - ImGui::End(); - } - - // 3. Show another simple window. - if (show_another_window) - { - ImGui::Begin("Another Window", &show_another_window); // Pass a pointer to our bool variable (the window will have a closing button that will clear the bool when clicked) - ImGui::Text("Hello from another window!"); - if (ImGui::Button("Close Me")) - show_another_window = false; - ImGui::End(); - } - - // Rendering - ImGui::Render(); - glViewport(0, 0, g_Width, g_Height); - glClearColor(clear_color.x, clear_color.y, clear_color.z, clear_color.w); - glClear(GL_COLOR_BUFFER_BIT); - ImGui_ImplOpenGL3_RenderDrawData(ImGui::GetDrawData()); - - // Update and Render additional Platform Windows - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - ImGui::UpdatePlatformWindows(); - ImGui::RenderPlatformWindowsDefault(); - - // Restore the OpenGL rendering context to the main window DC, since platform windows might have changed it. - wglMakeCurrent(g_MainWindow.hDC, g_hRC); - } - - // Present - ::SwapBuffers(g_MainWindow.hDC); - } - - ImGui_ImplOpenGL3_Shutdown(); - ImGui_ImplWin32_Shutdown(); - ImGui::DestroyContext(); - - CleanupDeviceWGL(hwnd, &g_MainWindow); - wglDeleteContext(g_hRC); - ::DestroyWindow(hwnd); - ::UnregisterClassW(wc.lpszClassName, wc.hInstance); - - return 0; -} - -// Helper functions -bool CreateDeviceWGL(HWND hWnd, WGL_WindowData* data) -{ - HDC hDc = ::GetDC(hWnd); - PIXELFORMATDESCRIPTOR pfd = { 0 }; - pfd.nSize = sizeof(pfd); - pfd.nVersion = 1; - pfd.dwFlags = PFD_DRAW_TO_WINDOW | PFD_SUPPORT_OPENGL | PFD_DOUBLEBUFFER; - pfd.iPixelType = PFD_TYPE_RGBA; - pfd.cColorBits = 32; - - const int pf = ::ChoosePixelFormat(hDc, &pfd); - if (pf == 0) - return false; - if (::SetPixelFormat(hDc, pf, &pfd) == FALSE) - return false; - ::ReleaseDC(hWnd, hDc); - - data->hDC = ::GetDC(hWnd); - if (!g_hRC) - g_hRC = wglCreateContext(data->hDC); - return true; -} - -void CleanupDeviceWGL(HWND hWnd, WGL_WindowData* data) -{ - wglMakeCurrent(NULL, NULL); - ::ReleaseDC(hWnd, data->hDC); -} - -// Forward declare message handler from imgui_impl_win32.cpp -extern IMGUI_IMPL_API LRESULT ImGui_ImplWin32_WndProcHandler(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam); - -// Win32 message handler -// You can read the io.WantCaptureMouse, io.WantCaptureKeyboard flags to tell if dear imgui wants to use your inputs. -// - When io.WantCaptureMouse is true, do not dispatch mouse input data to your main application, or clear/overwrite your copy of the mouse data. -// - When io.WantCaptureKeyboard is true, do not dispatch keyboard input data to your main application, or clear/overwrite your copy of the keyboard data. -// Generally you may always pass all inputs to dear imgui, and hide them from your application based on those two flags. -LRESULT WINAPI WndProc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam) -{ - if (ImGui_ImplWin32_WndProcHandler(hWnd, msg, wParam, lParam)) - return true; - - switch (msg) - { - case WM_SIZE: - if (wParam != SIZE_MINIMIZED) - { - g_Width = LOWORD(lParam); - g_Height = HIWORD(lParam); - } - return 0; - case WM_SYSCOMMAND: - if ((wParam & 0xfff0) == SC_KEYMENU) // Disable ALT application menu - return 0; - break; - case WM_DESTROY: - ::PostQuitMessage(0); - return 0; - } - return ::DefWindowProcW(hWnd, msg, wParam, lParam); -} diff --git a/app/jni/src/libultraship/extern/ImGui/examples/imgui_examples.sln b/app/jni/src/libultraship/extern/ImGui/examples/imgui_examples.sln deleted file mode 100644 index 071bcbd..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/imgui_examples.sln +++ /dev/null @@ -1,151 +0,0 @@ - -Microsoft Visual Studio Solution File, Format Version 12.00 -# Visual Studio Version 17 -VisualStudioVersion = 17.2.32616.157 -MinimumVisualStudioVersion = 10.0.40219.1 -Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "example_win32_directx9", "example_win32_directx9\example_win32_directx9.vcxproj", "{4165A294-21F2-44CA-9B38-E3F935ABADF5}" -EndProject -Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "example_win32_directx10", "example_win32_directx10\example_win32_directx10.vcxproj", "{345A953E-A004-4648-B442-DC5F9F11068C}" -EndProject -Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "example_win32_directx11", "example_win32_directx11\example_win32_directx11.vcxproj", "{9F316E83-5AE5-4939-A723-305A94F48005}" -EndProject -Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "example_win32_directx12", "example_win32_directx12\example_win32_directx12.vcxproj", "{B4CF9797-519D-4AFE-A8F4-5141A6B521D3}" -EndProject -Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "example_glfw_opengl2", "example_glfw_opengl2\example_glfw_opengl2.vcxproj", "{9CDA7840-B7A5-496D-A527-E95571496D18}" -EndProject -Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "example_glfw_opengl3", "example_glfw_opengl3\example_glfw_opengl3.vcxproj", "{4A1FB5EA-22F5-42A8-AB92-1D2DF5D47FB9}" -EndProject -Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "example_glfw_vulkan", "example_glfw_vulkan\example_glfw_vulkan.vcxproj", "{57E2DF5A-6FC8-45BB-99DD-91A18C646E80}" -EndProject -Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "example_sdl2_directx11", "example_sdl2_directx11\example_sdl2_directx11.vcxproj", "{9E1987E3-1F19-45CA-B9C9-D31E791836D8}" -EndProject -Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "example_sdl2_opengl2", "example_sdl2_opengl2\example_sdl2_opengl2.vcxproj", "{2AE17FDE-F7F3-4CAC-ADAB-0710EDA4F741}" -EndProject -Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "example_sdl2_opengl3", "example_sdl2_opengl3\example_sdl2_opengl3.vcxproj", "{BBAEB705-1669-40F3-8567-04CF6A991F4C}" -EndProject -Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "example_sdl2_vulkan", "example_sdl2_vulkan\example_sdl2_vulkan.vcxproj", "{BAE3D0B5-9695-4EB1-AD0F-75890EB4A3B3}" -EndProject -Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "example_win32_opengl3", "example_win32_opengl3\example_win32_opengl3.vcxproj", "{C624E5FF-D4FE-4D35-9164-B8A91864F98E}" -EndProject -Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "example_sdl2_sdlrenderer2", "example_sdl2_sdlrenderer2\example_sdl2_sdlrenderer2.vcxproj", "{0C0B2BEA-311F-473C-9652-87923EF639E3}" -EndProject -Global - GlobalSection(SolutionConfigurationPlatforms) = preSolution - Debug|Win32 = Debug|Win32 - Debug|x64 = Debug|x64 - Release|Win32 = Release|Win32 - Release|x64 = Release|x64 - EndGlobalSection - GlobalSection(ProjectConfigurationPlatforms) = postSolution - {4165A294-21F2-44CA-9B38-E3F935ABADF5}.Debug|Win32.ActiveCfg = Debug|Win32 - {4165A294-21F2-44CA-9B38-E3F935ABADF5}.Debug|Win32.Build.0 = Debug|Win32 - {4165A294-21F2-44CA-9B38-E3F935ABADF5}.Debug|x64.ActiveCfg = Debug|x64 - {4165A294-21F2-44CA-9B38-E3F935ABADF5}.Debug|x64.Build.0 = Debug|x64 - {4165A294-21F2-44CA-9B38-E3F935ABADF5}.Release|Win32.ActiveCfg = Release|Win32 - {4165A294-21F2-44CA-9B38-E3F935ABADF5}.Release|Win32.Build.0 = Release|Win32 - {4165A294-21F2-44CA-9B38-E3F935ABADF5}.Release|x64.ActiveCfg = Release|x64 - {4165A294-21F2-44CA-9B38-E3F935ABADF5}.Release|x64.Build.0 = Release|x64 - {345A953E-A004-4648-B442-DC5F9F11068C}.Debug|Win32.ActiveCfg = Debug|Win32 - {345A953E-A004-4648-B442-DC5F9F11068C}.Debug|Win32.Build.0 = Debug|Win32 - {345A953E-A004-4648-B442-DC5F9F11068C}.Debug|x64.ActiveCfg = Debug|x64 - {345A953E-A004-4648-B442-DC5F9F11068C}.Debug|x64.Build.0 = Debug|x64 - {345A953E-A004-4648-B442-DC5F9F11068C}.Release|Win32.ActiveCfg = Release|Win32 - {345A953E-A004-4648-B442-DC5F9F11068C}.Release|Win32.Build.0 = Release|Win32 - {345A953E-A004-4648-B442-DC5F9F11068C}.Release|x64.ActiveCfg = Release|x64 - {345A953E-A004-4648-B442-DC5F9F11068C}.Release|x64.Build.0 = Release|x64 - {9F316E83-5AE5-4939-A723-305A94F48005}.Debug|Win32.ActiveCfg = Debug|Win32 - {9F316E83-5AE5-4939-A723-305A94F48005}.Debug|Win32.Build.0 = Debug|Win32 - {9F316E83-5AE5-4939-A723-305A94F48005}.Debug|x64.ActiveCfg = Debug|x64 - {9F316E83-5AE5-4939-A723-305A94F48005}.Debug|x64.Build.0 = Debug|x64 - {9F316E83-5AE5-4939-A723-305A94F48005}.Release|Win32.ActiveCfg = Release|Win32 - {9F316E83-5AE5-4939-A723-305A94F48005}.Release|Win32.Build.0 = Release|Win32 - {9F316E83-5AE5-4939-A723-305A94F48005}.Release|x64.ActiveCfg = Release|x64 - {9F316E83-5AE5-4939-A723-305A94F48005}.Release|x64.Build.0 = Release|x64 - {B4CF9797-519D-4AFE-A8F4-5141A6B521D3}.Debug|Win32.ActiveCfg = Debug|Win32 - {B4CF9797-519D-4AFE-A8F4-5141A6B521D3}.Debug|Win32.Build.0 = Debug|Win32 - {B4CF9797-519D-4AFE-A8F4-5141A6B521D3}.Debug|x64.ActiveCfg = Debug|x64 - {B4CF9797-519D-4AFE-A8F4-5141A6B521D3}.Debug|x64.Build.0 = Debug|x64 - {B4CF9797-519D-4AFE-A8F4-5141A6B521D3}.Release|Win32.ActiveCfg = Release|Win32 - {B4CF9797-519D-4AFE-A8F4-5141A6B521D3}.Release|Win32.Build.0 = Release|Win32 - {B4CF9797-519D-4AFE-A8F4-5141A6B521D3}.Release|x64.ActiveCfg = Release|x64 - {B4CF9797-519D-4AFE-A8F4-5141A6B521D3}.Release|x64.Build.0 = Release|x64 - {9CDA7840-B7A5-496D-A527-E95571496D18}.Debug|Win32.ActiveCfg = Debug|Win32 - {9CDA7840-B7A5-496D-A527-E95571496D18}.Debug|Win32.Build.0 = Debug|Win32 - {9CDA7840-B7A5-496D-A527-E95571496D18}.Debug|x64.ActiveCfg = Debug|x64 - {9CDA7840-B7A5-496D-A527-E95571496D18}.Debug|x64.Build.0 = Debug|x64 - {9CDA7840-B7A5-496D-A527-E95571496D18}.Release|Win32.ActiveCfg = Release|Win32 - {9CDA7840-B7A5-496D-A527-E95571496D18}.Release|Win32.Build.0 = Release|Win32 - {9CDA7840-B7A5-496D-A527-E95571496D18}.Release|x64.ActiveCfg = Release|x64 - {9CDA7840-B7A5-496D-A527-E95571496D18}.Release|x64.Build.0 = Release|x64 - {4A1FB5EA-22F5-42A8-AB92-1D2DF5D47FB9}.Debug|Win32.ActiveCfg = Debug|Win32 - {4A1FB5EA-22F5-42A8-AB92-1D2DF5D47FB9}.Debug|Win32.Build.0 = Debug|Win32 - {4A1FB5EA-22F5-42A8-AB92-1D2DF5D47FB9}.Debug|x64.ActiveCfg = Debug|x64 - {4A1FB5EA-22F5-42A8-AB92-1D2DF5D47FB9}.Debug|x64.Build.0 = Debug|x64 - {4A1FB5EA-22F5-42A8-AB92-1D2DF5D47FB9}.Release|Win32.ActiveCfg = Release|Win32 - {4A1FB5EA-22F5-42A8-AB92-1D2DF5D47FB9}.Release|Win32.Build.0 = Release|Win32 - {4A1FB5EA-22F5-42A8-AB92-1D2DF5D47FB9}.Release|x64.ActiveCfg = Release|x64 - {4A1FB5EA-22F5-42A8-AB92-1D2DF5D47FB9}.Release|x64.Build.0 = Release|x64 - {57E2DF5A-6FC8-45BB-99DD-91A18C646E80}.Debug|Win32.ActiveCfg = Debug|Win32 - {57E2DF5A-6FC8-45BB-99DD-91A18C646E80}.Debug|Win32.Build.0 = Debug|Win32 - {57E2DF5A-6FC8-45BB-99DD-91A18C646E80}.Debug|x64.ActiveCfg = Debug|x64 - {57E2DF5A-6FC8-45BB-99DD-91A18C646E80}.Debug|x64.Build.0 = Debug|x64 - {57E2DF5A-6FC8-45BB-99DD-91A18C646E80}.Release|Win32.ActiveCfg = Release|Win32 - {57E2DF5A-6FC8-45BB-99DD-91A18C646E80}.Release|Win32.Build.0 = Release|Win32 - {57E2DF5A-6FC8-45BB-99DD-91A18C646E80}.Release|x64.ActiveCfg = Release|x64 - {57E2DF5A-6FC8-45BB-99DD-91A18C646E80}.Release|x64.Build.0 = Release|x64 - {9E1987E3-1F19-45CA-B9C9-D31E791836D8}.Debug|Win32.ActiveCfg = Debug|Win32 - {9E1987E3-1F19-45CA-B9C9-D31E791836D8}.Debug|Win32.Build.0 = Debug|Win32 - {9E1987E3-1F19-45CA-B9C9-D31E791836D8}.Debug|x64.ActiveCfg = Debug|x64 - {9E1987E3-1F19-45CA-B9C9-D31E791836D8}.Debug|x64.Build.0 = Debug|x64 - {9E1987E3-1F19-45CA-B9C9-D31E791836D8}.Release|Win32.ActiveCfg = Release|Win32 - {9E1987E3-1F19-45CA-B9C9-D31E791836D8}.Release|Win32.Build.0 = Release|Win32 - {9E1987E3-1F19-45CA-B9C9-D31E791836D8}.Release|x64.ActiveCfg = Release|x64 - {9E1987E3-1F19-45CA-B9C9-D31E791836D8}.Release|x64.Build.0 = Release|x64 - {2AE17FDE-F7F3-4CAC-ADAB-0710EDA4F741}.Debug|Win32.ActiveCfg = Debug|Win32 - {2AE17FDE-F7F3-4CAC-ADAB-0710EDA4F741}.Debug|Win32.Build.0 = Debug|Win32 - {2AE17FDE-F7F3-4CAC-ADAB-0710EDA4F741}.Debug|x64.ActiveCfg = Debug|x64 - {2AE17FDE-F7F3-4CAC-ADAB-0710EDA4F741}.Debug|x64.Build.0 = Debug|x64 - {2AE17FDE-F7F3-4CAC-ADAB-0710EDA4F741}.Release|Win32.ActiveCfg = Release|Win32 - {2AE17FDE-F7F3-4CAC-ADAB-0710EDA4F741}.Release|Win32.Build.0 = Release|Win32 - {2AE17FDE-F7F3-4CAC-ADAB-0710EDA4F741}.Release|x64.ActiveCfg = Release|x64 - {2AE17FDE-F7F3-4CAC-ADAB-0710EDA4F741}.Release|x64.Build.0 = Release|x64 - {BBAEB705-1669-40F3-8567-04CF6A991F4C}.Debug|Win32.ActiveCfg = Debug|Win32 - {BBAEB705-1669-40F3-8567-04CF6A991F4C}.Debug|Win32.Build.0 = Debug|Win32 - {BBAEB705-1669-40F3-8567-04CF6A991F4C}.Debug|x64.ActiveCfg = Debug|x64 - {BBAEB705-1669-40F3-8567-04CF6A991F4C}.Debug|x64.Build.0 = Debug|x64 - {BBAEB705-1669-40F3-8567-04CF6A991F4C}.Release|Win32.ActiveCfg = Release|Win32 - {BBAEB705-1669-40F3-8567-04CF6A991F4C}.Release|Win32.Build.0 = Release|Win32 - {BBAEB705-1669-40F3-8567-04CF6A991F4C}.Release|x64.ActiveCfg = Release|x64 - {BBAEB705-1669-40F3-8567-04CF6A991F4C}.Release|x64.Build.0 = Release|x64 - {BAE3D0B5-9695-4EB1-AD0F-75890EB4A3B3}.Debug|Win32.ActiveCfg = Debug|Win32 - {BAE3D0B5-9695-4EB1-AD0F-75890EB4A3B3}.Debug|Win32.Build.0 = Debug|Win32 - {BAE3D0B5-9695-4EB1-AD0F-75890EB4A3B3}.Debug|x64.ActiveCfg = Debug|x64 - {BAE3D0B5-9695-4EB1-AD0F-75890EB4A3B3}.Debug|x64.Build.0 = Debug|x64 - {BAE3D0B5-9695-4EB1-AD0F-75890EB4A3B3}.Release|Win32.ActiveCfg = Release|Win32 - {BAE3D0B5-9695-4EB1-AD0F-75890EB4A3B3}.Release|Win32.Build.0 = Release|Win32 - {BAE3D0B5-9695-4EB1-AD0F-75890EB4A3B3}.Release|x64.ActiveCfg = Release|x64 - {BAE3D0B5-9695-4EB1-AD0F-75890EB4A3B3}.Release|x64.Build.0 = Release|x64 - {C624E5FF-D4FE-4D35-9164-B8A91864F98E}.Debug|Win32.ActiveCfg = Debug|Win32 - {C624E5FF-D4FE-4D35-9164-B8A91864F98E}.Debug|Win32.Build.0 = Debug|Win32 - {C624E5FF-D4FE-4D35-9164-B8A91864F98E}.Debug|x64.ActiveCfg = Debug|x64 - {C624E5FF-D4FE-4D35-9164-B8A91864F98E}.Debug|x64.Build.0 = Debug|x64 - {C624E5FF-D4FE-4D35-9164-B8A91864F98E}.Release|Win32.ActiveCfg = Release|Win32 - {C624E5FF-D4FE-4D35-9164-B8A91864F98E}.Release|Win32.Build.0 = Release|Win32 - {C624E5FF-D4FE-4D35-9164-B8A91864F98E}.Release|x64.ActiveCfg = Release|x64 - {C624E5FF-D4FE-4D35-9164-B8A91864F98E}.Release|x64.Build.0 = Release|x64 - {0C0B2BEA-311F-473C-9652-87923EF639E3}.Debug|Win32.ActiveCfg = Debug|Win32 - {0C0B2BEA-311F-473C-9652-87923EF639E3}.Debug|Win32.Build.0 = Debug|Win32 - {0C0B2BEA-311F-473C-9652-87923EF639E3}.Debug|x64.ActiveCfg = Debug|x64 - {0C0B2BEA-311F-473C-9652-87923EF639E3}.Debug|x64.Build.0 = Debug|x64 - {0C0B2BEA-311F-473C-9652-87923EF639E3}.Release|Win32.ActiveCfg = Release|Win32 - {0C0B2BEA-311F-473C-9652-87923EF639E3}.Release|Win32.Build.0 = Release|Win32 - {0C0B2BEA-311F-473C-9652-87923EF639E3}.Release|x64.ActiveCfg = Release|x64 - {0C0B2BEA-311F-473C-9652-87923EF639E3}.Release|x64.Build.0 = Release|x64 - EndGlobalSection - GlobalSection(SolutionProperties) = preSolution - HideSolutionNode = FALSE - EndGlobalSection - GlobalSection(ExtensibilityGlobals) = postSolution - SolutionGuid = {B1ACFD20-A0A9-4A4C-ADBA-E7608F0E2BEE} - EndGlobalSection -EndGlobal diff --git a/app/jni/src/libultraship/extern/ImGui/examples/libs/emscripten/emscripten_mainloop_stub.h b/app/jni/src/libultraship/extern/ImGui/examples/libs/emscripten/emscripten_mainloop_stub.h deleted file mode 100644 index 05cf60f..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/libs/emscripten/emscripten_mainloop_stub.h +++ /dev/null @@ -1,37 +0,0 @@ -// What does this file solves? -// - Since Dear ImGui 1.00 we took pride that most of our examples applications had their entire -// main-loop inside the main() function. That's because: -// - It makes the examples easier to read, keeping the code sequential. -// - It permit the use of local variables, making it easier to try things and perform quick -// changes when someone needs to quickly test something (vs having to structure the example -// in order to pass data around). This is very important because people use those examples -// to craft easy-to-past repro when they want to discuss features or report issues. -// - It conveys at a glance that this is a no-BS framework, it won't take your main loop away from you. -// - It is generally nice and elegant. -// - However, comes Emscripten... it is a wonderful and magical tech but it requires a "main loop" function. -// - Only some of our examples would run on Emscripten. Typically the ones rendering with GL or WGPU ones. -// - I tried to refactor those examples but felt it was problematic that other examples didn't follow the -// same layout. Why would the SDL+GL example be structured one way and the SGL+DX11 be structured differently? -// Especially as we are trying hard to convey that using a Dear ImGui backend in an *existing application* -// should requires only a few dozens lines of code, and this should be consistent and symmetrical for all backends. -// - So the next logical step was to refactor all examples to follow that layout of using a "main loop" function. -// This worked, but it made us lose all the nice things we had... - -// Since only about 3 examples really need to run with Emscripten, here's our solution: -// - Use some weird macros and capturing lambda to turn a loop in main() into a function. -// - Hide all that crap in this file so it doesn't make our examples unusually ugly. -// As a stance and principle of Dear ImGui development we don't use C++ headers and we don't -// want to suggest to the newcomer that we would ever use C++ headers as this would affect -// the initial judgment of many of our target audience. -// - Technique is based on this idea: https://github.com/ocornut/imgui/pull/2492/ -#ifdef __EMSCRIPTEN__ -#include -#include -static std::function MainLoopForEmscriptenP; -static void MainLoopForEmscripten() { MainLoopForEmscriptenP(); } -#define EMSCRIPTEN_MAINLOOP_BEGIN MainLoopForEmscriptenP = [&]() -#define EMSCRIPTEN_MAINLOOP_END ; emscripten_set_main_loop(MainLoopForEmscripten, 0, true) -#else -#define EMSCRIPTEN_MAINLOOP_BEGIN -#define EMSCRIPTEN_MAINLOOP_END -#endif diff --git a/app/jni/src/libultraship/extern/ImGui/examples/libs/emscripten/shell_minimal.html b/app/jni/src/libultraship/extern/ImGui/examples/libs/emscripten/shell_minimal.html deleted file mode 100644 index bcf6262..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/libs/emscripten/shell_minimal.html +++ /dev/null @@ -1,65 +0,0 @@ - - - - - - Dear ImGui Emscripten example - - - - - - {{{ SCRIPT }}} - - diff --git a/app/jni/src/libultraship/extern/ImGui/examples/libs/glfw/COPYING.txt b/app/jni/src/libultraship/extern/ImGui/examples/libs/glfw/COPYING.txt deleted file mode 100644 index b30c701..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/libs/glfw/COPYING.txt +++ /dev/null @@ -1,22 +0,0 @@ -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. - diff --git a/app/jni/src/libultraship/extern/ImGui/examples/libs/glfw/include/GLFW/glfw3.h b/app/jni/src/libultraship/extern/ImGui/examples/libs/glfw/include/GLFW/glfw3.h deleted file mode 100644 index f8ca3d6..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/libs/glfw/include/GLFW/glfw3.h +++ /dev/null @@ -1,4227 +0,0 @@ -/************************************************************************* - * GLFW 3.2 - www.glfw.org - * A library for OpenGL, window and input - *------------------------------------------------------------------------ - * 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 _glfw3_h_ -#define _glfw3_h_ - -#ifdef __cplusplus -extern "C" { -#endif - - -/************************************************************************* - * Doxygen documentation - *************************************************************************/ - -/*! @file glfw3.h - * @brief The header of the GLFW 3 API. - * - * This is the header file of the GLFW 3 API. It defines all its types and - * declares all its functions. - * - * For more information about how to use this file, see @ref build_include. - */ -/*! @defgroup context Context reference - * - * This is the reference documentation for OpenGL and OpenGL ES context related - * functions. For more task-oriented information, see the @ref context_guide. - */ -/*! @defgroup vulkan Vulkan reference - * - * This is the reference documentation for Vulkan related functions and types. - * For more task-oriented information, see the @ref vulkan_guide. - */ -/*! @defgroup init Initialization, version and error reference - * - * This is the reference documentation for initialization and termination of - * the library, version management and error handling. For more task-oriented - * information, see the @ref intro_guide. - */ -/*! @defgroup input Input reference - * - * This is the reference documentation for input related functions and types. - * For more task-oriented information, see the @ref input_guide. - */ -/*! @defgroup monitor Monitor reference - * - * This is the reference documentation for monitor related functions and types. - * For more task-oriented information, see the @ref monitor_guide. - */ -/*! @defgroup window Window reference - * - * This is the reference documentation for window related functions and types, - * including creation, deletion and event polling. For more task-oriented - * information, see the @ref window_guide. - */ - - -/************************************************************************* - * Compiler- and platform-specific preprocessor work - *************************************************************************/ - -/* If we are we on Windows, we want a single define for it. - */ -#if !defined(_WIN32) && (defined(__WIN32__) || defined(WIN32) || defined(__MINGW32__)) - #define _WIN32 -#endif /* _WIN32 */ - -/* It is customary to use APIENTRY for OpenGL function pointer declarations on - * all platforms. Additionally, the Windows OpenGL header needs APIENTRY. - */ -#ifndef APIENTRY - #ifdef _WIN32 - #define APIENTRY __stdcall - #else - #define APIENTRY - #endif -#endif /* APIENTRY */ - -/* Some Windows OpenGL headers need this. - */ -#if !defined(WINGDIAPI) && defined(_WIN32) - #define WINGDIAPI __declspec(dllimport) - #define GLFW_WINGDIAPI_DEFINED -#endif /* WINGDIAPI */ - -/* Some Windows GLU headers need this. - */ -#if !defined(CALLBACK) && defined(_WIN32) - #define CALLBACK __stdcall - #define GLFW_CALLBACK_DEFINED -#endif /* CALLBACK */ - -/* Most Windows GLU headers need wchar_t. - * The OS X OpenGL header blocks the definition of ptrdiff_t by glext.h. - * Include it unconditionally to avoid surprising side-effects. - */ -#include -#include - -/* Include the chosen client API headers. - */ -#if defined(__APPLE__) - #if defined(GLFW_INCLUDE_GLCOREARB) - #include - #if defined(GLFW_INCLUDE_GLEXT) - #include - #endif - #elif !defined(GLFW_INCLUDE_NONE) - #if !defined(GLFW_INCLUDE_GLEXT) - #define GL_GLEXT_LEGACY - #endif - #include - #endif - #if defined(GLFW_INCLUDE_GLU) - #include - #endif -#else - #if defined(GLFW_INCLUDE_GLCOREARB) - #include - #elif defined(GLFW_INCLUDE_ES1) - #include - #if defined(GLFW_INCLUDE_GLEXT) - #include - #endif - #elif defined(GLFW_INCLUDE_ES2) - #include - #if defined(GLFW_INCLUDE_GLEXT) - #include - #endif - #elif defined(GLFW_INCLUDE_ES3) - #include - #if defined(GLFW_INCLUDE_GLEXT) - #include - #endif - #elif defined(GLFW_INCLUDE_ES31) - #include - #if defined(GLFW_INCLUDE_GLEXT) - #include - #endif - #elif defined(GLFW_INCLUDE_VULKAN) - #include - #elif !defined(GLFW_INCLUDE_NONE) - #include - #if defined(GLFW_INCLUDE_GLEXT) - #include - #endif - #endif - #if defined(GLFW_INCLUDE_GLU) - #include - #endif -#endif - -#if defined(GLFW_DLL) && defined(_GLFW_BUILD_DLL) - /* GLFW_DLL must be defined by applications that are linking against the DLL - * version of the GLFW library. _GLFW_BUILD_DLL is defined by the GLFW - * configuration header when compiling the DLL version of the library. - */ - #error "You must not have both GLFW_DLL and _GLFW_BUILD_DLL defined" -#endif - -/* GLFWAPI is used to declare public API functions for export - * from the DLL / shared library / dynamic library. - */ -#if defined(_WIN32) && defined(_GLFW_BUILD_DLL) - /* We are building GLFW as a Win32 DLL */ - #define GLFWAPI __declspec(dllexport) -#elif defined(_WIN32) && defined(GLFW_DLL) - /* We are calling GLFW as a Win32 DLL */ - #define GLFWAPI __declspec(dllimport) -#elif defined(__GNUC__) && defined(_GLFW_BUILD_DLL) - /* We are building GLFW as a shared / dynamic library */ - #define GLFWAPI __attribute__((visibility("default"))) -#else - /* We are building or calling GLFW as a static library */ - #define GLFWAPI -#endif - - -/************************************************************************* - * GLFW API tokens - *************************************************************************/ - -/*! @name GLFW version macros - * @{ */ -/*! @brief The major version number of the GLFW library. - * - * This is incremented when the API is changed in non-compatible ways. - * @ingroup init - */ -#define GLFW_VERSION_MAJOR 3 -/*! @brief The minor version number of the GLFW library. - * - * This is incremented when features are added to the API but it remains - * backward-compatible. - * @ingroup init - */ -#define GLFW_VERSION_MINOR 2 -/*! @brief The revision number of the GLFW library. - * - * This is incremented when a bug fix release is made that does not contain any - * API changes. - * @ingroup init - */ -#define GLFW_VERSION_REVISION 0 -/*! @} */ - -/*! @name Boolean values - * @{ */ -/*! @brief One. - * - * One. Seriously. You don't _need_ to use this symbol in your code. It's - * just semantic sugar for the number 1. You can use `1` or `true` or `_True` - * or `GL_TRUE` or whatever you want. - */ -#define GLFW_TRUE 1 -/*! @brief Zero. - * - * Zero. Seriously. You don't _need_ to use this symbol in your code. It's - * just just semantic sugar for the number 0. You can use `0` or `false` or - * `_False` or `GL_FALSE` or whatever you want. - */ -#define GLFW_FALSE 0 -/*! @} */ - -/*! @name Key and button actions - * @{ */ -/*! @brief The key or mouse button was released. - * - * The key or mouse button was released. - * - * @ingroup input - */ -#define GLFW_RELEASE 0 -/*! @brief The key or mouse button was pressed. - * - * The key or mouse button was pressed. - * - * @ingroup input - */ -#define GLFW_PRESS 1 -/*! @brief The key was held down until it repeated. - * - * The key was held down until it repeated. - * - * @ingroup input - */ -#define GLFW_REPEAT 2 -/*! @} */ - -/*! @defgroup keys Keyboard keys - * - * See [key input](@ref input_key) for how these are used. - * - * These key codes are inspired by the _USB HID Usage Tables v1.12_ (p. 53-60), - * but re-arranged to map to 7-bit ASCII for printable keys (function keys are - * put in the 256+ range). - * - * The naming of the key codes follow these rules: - * - The US keyboard layout is used - * - Names of printable alpha-numeric characters are used (e.g. "A", "R", - * "3", etc.) - * - For non-alphanumeric characters, Unicode:ish names are used (e.g. - * "COMMA", "LEFT_SQUARE_BRACKET", etc.). Note that some names do not - * correspond to the Unicode standard (usually for brevity) - * - Keys that lack a clear US mapping are named "WORLD_x" - * - For non-printable keys, custom names are used (e.g. "F4", - * "BACKSPACE", etc.) - * - * @ingroup input - * @{ - */ - -/* The unknown key */ -#define GLFW_KEY_UNKNOWN -1 - -/* Printable keys */ -#define GLFW_KEY_SPACE 32 -#define GLFW_KEY_APOSTROPHE 39 /* ' */ -#define GLFW_KEY_COMMA 44 /* , */ -#define GLFW_KEY_MINUS 45 /* - */ -#define GLFW_KEY_PERIOD 46 /* . */ -#define GLFW_KEY_SLASH 47 /* / */ -#define GLFW_KEY_0 48 -#define GLFW_KEY_1 49 -#define GLFW_KEY_2 50 -#define GLFW_KEY_3 51 -#define GLFW_KEY_4 52 -#define GLFW_KEY_5 53 -#define GLFW_KEY_6 54 -#define GLFW_KEY_7 55 -#define GLFW_KEY_8 56 -#define GLFW_KEY_9 57 -#define GLFW_KEY_SEMICOLON 59 /* ; */ -#define GLFW_KEY_EQUAL 61 /* = */ -#define GLFW_KEY_A 65 -#define GLFW_KEY_B 66 -#define GLFW_KEY_C 67 -#define GLFW_KEY_D 68 -#define GLFW_KEY_E 69 -#define GLFW_KEY_F 70 -#define GLFW_KEY_G 71 -#define GLFW_KEY_H 72 -#define GLFW_KEY_I 73 -#define GLFW_KEY_J 74 -#define GLFW_KEY_K 75 -#define GLFW_KEY_L 76 -#define GLFW_KEY_M 77 -#define GLFW_KEY_N 78 -#define GLFW_KEY_O 79 -#define GLFW_KEY_P 80 -#define GLFW_KEY_Q 81 -#define GLFW_KEY_R 82 -#define GLFW_KEY_S 83 -#define GLFW_KEY_T 84 -#define GLFW_KEY_U 85 -#define GLFW_KEY_V 86 -#define GLFW_KEY_W 87 -#define GLFW_KEY_X 88 -#define GLFW_KEY_Y 89 -#define GLFW_KEY_Z 90 -#define GLFW_KEY_LEFT_BRACKET 91 /* [ */ -#define GLFW_KEY_BACKSLASH 92 /* \ */ -#define GLFW_KEY_RIGHT_BRACKET 93 /* ] */ -#define GLFW_KEY_GRAVE_ACCENT 96 /* ` */ -#define GLFW_KEY_WORLD_1 161 /* non-US #1 */ -#define GLFW_KEY_WORLD_2 162 /* non-US #2 */ - -/* Function keys */ -#define GLFW_KEY_ESCAPE 256 -#define GLFW_KEY_ENTER 257 -#define GLFW_KEY_TAB 258 -#define GLFW_KEY_BACKSPACE 259 -#define GLFW_KEY_INSERT 260 -#define GLFW_KEY_DELETE 261 -#define GLFW_KEY_RIGHT 262 -#define GLFW_KEY_LEFT 263 -#define GLFW_KEY_DOWN 264 -#define GLFW_KEY_UP 265 -#define GLFW_KEY_PAGE_UP 266 -#define GLFW_KEY_PAGE_DOWN 267 -#define GLFW_KEY_HOME 268 -#define GLFW_KEY_END 269 -#define GLFW_KEY_CAPS_LOCK 280 -#define GLFW_KEY_SCROLL_LOCK 281 -#define GLFW_KEY_NUM_LOCK 282 -#define GLFW_KEY_PRINT_SCREEN 283 -#define GLFW_KEY_PAUSE 284 -#define GLFW_KEY_F1 290 -#define GLFW_KEY_F2 291 -#define GLFW_KEY_F3 292 -#define GLFW_KEY_F4 293 -#define GLFW_KEY_F5 294 -#define GLFW_KEY_F6 295 -#define GLFW_KEY_F7 296 -#define GLFW_KEY_F8 297 -#define GLFW_KEY_F9 298 -#define GLFW_KEY_F10 299 -#define GLFW_KEY_F11 300 -#define GLFW_KEY_F12 301 -#define GLFW_KEY_F13 302 -#define GLFW_KEY_F14 303 -#define GLFW_KEY_F15 304 -#define GLFW_KEY_F16 305 -#define GLFW_KEY_F17 306 -#define GLFW_KEY_F18 307 -#define GLFW_KEY_F19 308 -#define GLFW_KEY_F20 309 -#define GLFW_KEY_F21 310 -#define GLFW_KEY_F22 311 -#define GLFW_KEY_F23 312 -#define GLFW_KEY_F24 313 -#define GLFW_KEY_F25 314 -#define GLFW_KEY_KP_0 320 -#define GLFW_KEY_KP_1 321 -#define GLFW_KEY_KP_2 322 -#define GLFW_KEY_KP_3 323 -#define GLFW_KEY_KP_4 324 -#define GLFW_KEY_KP_5 325 -#define GLFW_KEY_KP_6 326 -#define GLFW_KEY_KP_7 327 -#define GLFW_KEY_KP_8 328 -#define GLFW_KEY_KP_9 329 -#define GLFW_KEY_KP_DECIMAL 330 -#define GLFW_KEY_KP_DIVIDE 331 -#define GLFW_KEY_KP_MULTIPLY 332 -#define GLFW_KEY_KP_SUBTRACT 333 -#define GLFW_KEY_KP_ADD 334 -#define GLFW_KEY_KP_ENTER 335 -#define GLFW_KEY_KP_EQUAL 336 -#define GLFW_KEY_LEFT_SHIFT 340 -#define GLFW_KEY_LEFT_CONTROL 341 -#define GLFW_KEY_LEFT_ALT 342 -#define GLFW_KEY_LEFT_SUPER 343 -#define GLFW_KEY_RIGHT_SHIFT 344 -#define GLFW_KEY_RIGHT_CONTROL 345 -#define GLFW_KEY_RIGHT_ALT 346 -#define GLFW_KEY_RIGHT_SUPER 347 -#define GLFW_KEY_MENU 348 - -#define GLFW_KEY_LAST GLFW_KEY_MENU - -/*! @} */ - -/*! @defgroup mods Modifier key flags - * - * See [key input](@ref input_key) for how these are used. - * - * @ingroup input - * @{ */ - -/*! @brief If this bit is set one or more Shift keys were held down. - */ -#define GLFW_MOD_SHIFT 0x0001 -/*! @brief If this bit is set one or more Control keys were held down. - */ -#define GLFW_MOD_CONTROL 0x0002 -/*! @brief If this bit is set one or more Alt keys were held down. - */ -#define GLFW_MOD_ALT 0x0004 -/*! @brief If this bit is set one or more Super keys were held down. - */ -#define GLFW_MOD_SUPER 0x0008 - -/*! @} */ - -/*! @defgroup buttons Mouse buttons - * - * See [mouse button input](@ref input_mouse_button) for how these are used. - * - * @ingroup input - * @{ */ -#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 -#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 -/*! @} */ - -/*! @defgroup joysticks Joysticks - * - * See [joystick input](@ref joystick) for how these are used. - * - * @ingroup input - * @{ */ -#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 -/*! @} */ - -/*! @defgroup errors Error codes - * - * See [error handling](@ref error_handling) for how these are used. - * - * @ingroup init - * @{ */ -/*! @brief GLFW has not been initialized. - * - * This occurs if a GLFW function was called that must not be called unless the - * library is [initialized](@ref intro_init). - * - * @analysis Application programmer error. Initialize GLFW before calling any - * function that requires initialization. - */ -#define GLFW_NOT_INITIALIZED 0x00010001 -/*! @brief No context is current for this thread. - * - * This occurs if a GLFW function was called that needs and operates on the - * current OpenGL or OpenGL ES context but no context is current on the calling - * thread. One such function is @ref glfwSwapInterval. - * - * @analysis Application programmer error. Ensure a context is current before - * calling functions that require a current context. - */ -#define GLFW_NO_CURRENT_CONTEXT 0x00010002 -/*! @brief One of the arguments to the function was an invalid enum value. - * - * One of the arguments to the function was an invalid enum value, for example - * requesting [GLFW_RED_BITS](@ref window_hints_fb) with @ref - * glfwGetWindowAttrib. - * - * @analysis Application programmer error. Fix the offending call. - */ -#define GLFW_INVALID_ENUM 0x00010003 -/*! @brief One of the arguments to the function was an invalid value. - * - * One of the arguments to the function was an invalid value, for example - * requesting a non-existent OpenGL or OpenGL ES version like 2.7. - * - * Requesting a valid but unavailable OpenGL or OpenGL ES version will instead - * result in a @ref GLFW_VERSION_UNAVAILABLE error. - * - * @analysis Application programmer error. Fix the offending call. - */ -#define GLFW_INVALID_VALUE 0x00010004 -/*! @brief A memory allocation failed. - * - * A memory allocation failed. - * - * @analysis A bug in GLFW or the underlying operating system. Report the bug - * to our [issue tracker](https://github.com/glfw/glfw/issues). - */ -#define GLFW_OUT_OF_MEMORY 0x00010005 -/*! @brief GLFW could not find support for the requested API on the system. - * - * GLFW could not find support for the requested API on the system. - * - * @analysis The installed graphics driver does not support the requested - * API, or does not support it via the chosen context creation backend. - * Below are a few examples. - * - * @par - * Some pre-installed Windows graphics drivers do not support OpenGL. AMD only - * supports OpenGL ES via EGL, while Nvidia and Intel only support it via - * a WGL or GLX extension. OS X does not provide OpenGL ES at all. The Mesa - * EGL, OpenGL and OpenGL ES libraries do not interface with the Nvidia binary - * driver. Older graphics drivers do not support Vulkan. - */ -#define GLFW_API_UNAVAILABLE 0x00010006 -/*! @brief The requested OpenGL or OpenGL ES version is not available. - * - * The requested OpenGL or OpenGL ES version (including any requested context - * or framebuffer hints) is not available on this machine. - * - * @analysis The machine does not support your requirements. If your - * application is sufficiently flexible, downgrade your requirements and try - * again. Otherwise, inform the user that their machine does not match your - * requirements. - * - * @par - * Future invalid OpenGL and OpenGL ES versions, for example OpenGL 4.8 if 5.0 - * comes out before the 4.x series gets that far, also fail with this error and - * not @ref GLFW_INVALID_VALUE, because GLFW cannot know what future versions - * will exist. - */ -#define GLFW_VERSION_UNAVAILABLE 0x00010007 -/*! @brief A platform-specific error occurred that does not match any of the - * more specific categories. - * - * A platform-specific error occurred that does not match any of the more - * specific categories. - * - * @analysis A bug or configuration error in GLFW, the underlying operating - * system or its drivers, or a lack of required resources. Report the issue to - * our [issue tracker](https://github.com/glfw/glfw/issues). - */ -#define GLFW_PLATFORM_ERROR 0x00010008 -/*! @brief The requested format is not supported or available. - * - * If emitted during window creation, the requested pixel format is not - * supported. - * - * If emitted when querying the clipboard, the contents of the clipboard could - * not be converted to the requested format. - * - * @analysis If emitted during window creation, one or more - * [hard constraints](@ref window_hints_hard) did not match any of the - * available pixel formats. If your application is sufficiently flexible, - * downgrade your requirements and try again. Otherwise, inform the user that - * their machine does not match your requirements. - * - * @par - * If emitted when querying the clipboard, ignore the error or report it to - * the user, as appropriate. - */ -#define GLFW_FORMAT_UNAVAILABLE 0x00010009 -/*! @brief The specified window does not have an OpenGL or OpenGL ES context. - * - * A window that does not have an OpenGL or OpenGL ES context was passed to - * a function that requires it to have one. - * - * @analysis Application programmer error. Fix the offending call. - */ -#define GLFW_NO_WINDOW_CONTEXT 0x0001000A -/*! @} */ - -#define GLFW_FOCUSED 0x00020001 -#define GLFW_ICONIFIED 0x00020002 -#define GLFW_RESIZABLE 0x00020003 -#define GLFW_VISIBLE 0x00020004 -#define GLFW_DECORATED 0x00020005 -#define GLFW_AUTO_ICONIFY 0x00020006 -#define GLFW_FLOATING 0x00020007 -#define GLFW_MAXIMIZED 0x00020008 - -#define GLFW_RED_BITS 0x00021001 -#define GLFW_GREEN_BITS 0x00021002 -#define GLFW_BLUE_BITS 0x00021003 -#define GLFW_ALPHA_BITS 0x00021004 -#define GLFW_DEPTH_BITS 0x00021005 -#define GLFW_STENCIL_BITS 0x00021006 -#define GLFW_ACCUM_RED_BITS 0x00021007 -#define GLFW_ACCUM_GREEN_BITS 0x00021008 -#define GLFW_ACCUM_BLUE_BITS 0x00021009 -#define GLFW_ACCUM_ALPHA_BITS 0x0002100A -#define GLFW_AUX_BUFFERS 0x0002100B -#define GLFW_STEREO 0x0002100C -#define GLFW_SAMPLES 0x0002100D -#define GLFW_SRGB_CAPABLE 0x0002100E -#define GLFW_REFRESH_RATE 0x0002100F -#define GLFW_DOUBLEBUFFER 0x00021010 - -#define GLFW_CLIENT_API 0x00022001 -#define GLFW_CONTEXT_VERSION_MAJOR 0x00022002 -#define GLFW_CONTEXT_VERSION_MINOR 0x00022003 -#define GLFW_CONTEXT_REVISION 0x00022004 -#define GLFW_CONTEXT_ROBUSTNESS 0x00022005 -#define GLFW_OPENGL_FORWARD_COMPAT 0x00022006 -#define GLFW_OPENGL_DEBUG_CONTEXT 0x00022007 -#define GLFW_OPENGL_PROFILE 0x00022008 -#define GLFW_CONTEXT_RELEASE_BEHAVIOR 0x00022009 -#define GLFW_CONTEXT_NO_ERROR 0x0002200A - -#define GLFW_NO_API 0 -#define GLFW_OPENGL_API 0x00030001 -#define GLFW_OPENGL_ES_API 0x00030002 - -#define GLFW_NO_ROBUSTNESS 0 -#define GLFW_NO_RESET_NOTIFICATION 0x00031001 -#define GLFW_LOSE_CONTEXT_ON_RESET 0x00031002 - -#define GLFW_OPENGL_ANY_PROFILE 0 -#define GLFW_OPENGL_CORE_PROFILE 0x00032001 -#define GLFW_OPENGL_COMPAT_PROFILE 0x00032002 - -#define GLFW_CURSOR 0x00033001 -#define GLFW_STICKY_KEYS 0x00033002 -#define GLFW_STICKY_MOUSE_BUTTONS 0x00033003 - -#define GLFW_CURSOR_NORMAL 0x00034001 -#define GLFW_CURSOR_HIDDEN 0x00034002 -#define GLFW_CURSOR_DISABLED 0x00034003 - -#define GLFW_ANY_RELEASE_BEHAVIOR 0 -#define GLFW_RELEASE_BEHAVIOR_FLUSH 0x00035001 -#define GLFW_RELEASE_BEHAVIOR_NONE 0x00035002 - -/*! @defgroup shapes Standard cursor shapes - * - * See [standard cursor creation](@ref cursor_standard) for how these are used. - * - * @ingroup input - * @{ */ - -/*! @brief The regular arrow cursor shape. - * - * The regular arrow cursor. - */ -#define GLFW_ARROW_CURSOR 0x00036001 -/*! @brief The text input I-beam cursor shape. - * - * The text input I-beam cursor shape. - */ -#define GLFW_IBEAM_CURSOR 0x00036002 -/*! @brief The crosshair shape. - * - * The crosshair shape. - */ -#define GLFW_CROSSHAIR_CURSOR 0x00036003 -/*! @brief The hand shape. - * - * The hand shape. - */ -#define GLFW_HAND_CURSOR 0x00036004 -/*! @brief The horizontal resize arrow shape. - * - * The horizontal resize arrow shape. - */ -#define GLFW_HRESIZE_CURSOR 0x00036005 -/*! @brief The vertical resize arrow shape. - * - * The vertical resize arrow shape. - */ -#define GLFW_VRESIZE_CURSOR 0x00036006 -/*! @} */ - -#define GLFW_CONNECTED 0x00040001 -#define GLFW_DISCONNECTED 0x00040002 - -#define GLFW_DONT_CARE -1 - - -/************************************************************************* - * GLFW API types - *************************************************************************/ - -/*! @brief Client API function pointer type. - * - * Generic function pointer used for returning client API function pointers - * without forcing a cast from a regular pointer. - * - * @sa @ref context_glext - * @sa glfwGetProcAddress - * - * @since Added in version 3.0. - - * @ingroup context - */ -typedef void (*GLFWglproc)(void); - -/*! @brief Vulkan API function pointer type. - * - * Generic function pointer used for returning Vulkan API function pointers - * without forcing a cast from a regular pointer. - * - * @sa @ref vulkan_proc - * @sa glfwGetInstanceProcAddress - * - * @since Added in version 3.2. - * - * @ingroup vulkan - */ -typedef void (*GLFWvkproc)(void); - -/*! @brief Opaque monitor object. - * - * Opaque monitor object. - * - * @see @ref monitor_object - * - * @since Added in version 3.0. - * - * @ingroup monitor - */ -typedef struct GLFWmonitor GLFWmonitor; - -/*! @brief Opaque window object. - * - * Opaque window object. - * - * @see @ref window_object - * - * @since Added in version 3.0. - * - * @ingroup window - */ -typedef struct GLFWwindow GLFWwindow; - -/*! @brief Opaque cursor object. - * - * Opaque cursor object. - * - * @see @ref cursor_object - * - * @since Added in version 3.1. - * - * @ingroup cursor - */ -typedef struct GLFWcursor GLFWcursor; - -/*! @brief The function signature for error callbacks. - * - * This is the function signature for error callback functions. - * - * @param[in] error An [error code](@ref errors). - * @param[in] description A UTF-8 encoded string describing the error. - * - * @sa @ref error_handling - * @sa glfwSetErrorCallback - * - * @since Added in version 3.0. - * - * @ingroup init - */ -typedef void (* GLFWerrorfun)(int,const char*); - -/*! @brief The function signature for window position callbacks. - * - * This is the function signature for window position callback functions. - * - * @param[in] window The window that was moved. - * @param[in] xpos The new x-coordinate, in screen coordinates, of the - * upper-left corner of the client area of the window. - * @param[in] ypos The new y-coordinate, in screen coordinates, of the - * upper-left corner of the client area of the window. - * - * @sa @ref window_pos - * @sa glfwSetWindowPosCallback - * - * @since Added in version 3.0. - * - * @ingroup window - */ -typedef void (* GLFWwindowposfun)(GLFWwindow*,int,int); - -/*! @brief The function signature for window resize callbacks. - * - * This is the function signature for window size callback functions. - * - * @param[in] window The window that was resized. - * @param[in] width The new width, in screen coordinates, of the window. - * @param[in] height The new height, in screen coordinates, of the window. - * - * @sa @ref window_size - * @sa glfwSetWindowSizeCallback - * - * @since Added in version 1.0. - * @glfw3 Added window handle parameter. - * - * @ingroup window - */ -typedef void (* GLFWwindowsizefun)(GLFWwindow*,int,int); - -/*! @brief The function signature for window close callbacks. - * - * This is the function signature for window close callback functions. - * - * @param[in] window The window that the user attempted to close. - * - * @sa @ref window_close - * @sa glfwSetWindowCloseCallback - * - * @since Added in version 2.5. - * @glfw3 Added window handle parameter. - * - * @ingroup window - */ -typedef void (* GLFWwindowclosefun)(GLFWwindow*); - -/*! @brief The function signature for window content refresh callbacks. - * - * This is the function signature for window refresh callback functions. - * - * @param[in] window The window whose content needs to be refreshed. - * - * @sa @ref window_refresh - * @sa glfwSetWindowRefreshCallback - * - * @since Added in version 2.5. - * @glfw3 Added window handle parameter. - * - * @ingroup window - */ -typedef void (* GLFWwindowrefreshfun)(GLFWwindow*); - -/*! @brief The function signature for window focus/defocus callbacks. - * - * This is the function signature for window focus callback functions. - * - * @param[in] window The window that gained or lost input focus. - * @param[in] focused `GLFW_TRUE` if the window was given input focus, or - * `GLFW_FALSE` if it lost it. - * - * @sa @ref window_focus - * @sa glfwSetWindowFocusCallback - * - * @since Added in version 3.0. - * - * @ingroup window - */ -typedef void (* GLFWwindowfocusfun)(GLFWwindow*,int); - -/*! @brief The function signature for window iconify/restore callbacks. - * - * This is the function signature for window iconify/restore callback - * functions. - * - * @param[in] window The window that was iconified or restored. - * @param[in] iconified `GLFW_TRUE` if the window was iconified, or - * `GLFW_FALSE` if it was restored. - * - * @sa @ref window_iconify - * @sa glfwSetWindowIconifyCallback - * - * @since Added in version 3.0. - * - * @ingroup window - */ -typedef void (* GLFWwindowiconifyfun)(GLFWwindow*,int); - -/*! @brief The function signature for framebuffer resize callbacks. - * - * This is the function signature for framebuffer resize callback - * functions. - * - * @param[in] window The window whose framebuffer was resized. - * @param[in] width The new width, in pixels, of the framebuffer. - * @param[in] height The new height, in pixels, of the framebuffer. - * - * @sa @ref window_fbsize - * @sa glfwSetFramebufferSizeCallback - * - * @since Added in version 3.0. - * - * @ingroup window - */ -typedef void (* GLFWframebuffersizefun)(GLFWwindow*,int,int); - -/*! @brief The function signature for mouse button callbacks. - * - * This is the function signature for mouse button callback functions. - * - * @param[in] window The window that received the event. - * @param[in] button The [mouse button](@ref buttons) that was pressed or - * released. - * @param[in] action One of `GLFW_PRESS` or `GLFW_RELEASE`. - * @param[in] mods Bit field describing which [modifier keys](@ref mods) were - * held down. - * - * @sa @ref input_mouse_button - * @sa glfwSetMouseButtonCallback - * - * @since Added in version 1.0. - * @glfw3 Added window handle and modifier mask parameters. - * - * @ingroup input - */ -typedef void (* GLFWmousebuttonfun)(GLFWwindow*,int,int,int); - -/*! @brief The function signature for cursor position callbacks. - * - * This is the function signature for cursor position callback functions. - * - * @param[in] window The window that received the event. - * @param[in] xpos The new cursor x-coordinate, relative to the left edge of - * the client area. - * @param[in] ypos The new cursor y-coordinate, relative to the top edge of the - * client area. - * - * @sa @ref cursor_pos - * @sa glfwSetCursorPosCallback - * - * @since Added in version 3.0. Replaces `GLFWmouseposfun`. - * - * @ingroup input - */ -typedef void (* GLFWcursorposfun)(GLFWwindow*,double,double); - -/*! @brief The function signature for cursor enter/leave callbacks. - * - * This is the function signature for cursor enter/leave callback functions. - * - * @param[in] window The window that received the event. - * @param[in] entered `GLFW_TRUE` if the cursor entered the window's client - * area, or `GLFW_FALSE` if it left it. - * - * @sa @ref cursor_enter - * @sa glfwSetCursorEnterCallback - * - * @since Added in version 3.0. - * - * @ingroup input - */ -typedef void (* GLFWcursorenterfun)(GLFWwindow*,int); - -/*! @brief The function signature for scroll callbacks. - * - * This is the function signature for scroll callback functions. - * - * @param[in] window The window that received the event. - * @param[in] xoffset The scroll offset along the x-axis. - * @param[in] yoffset The scroll offset along the y-axis. - * - * @sa @ref scrolling - * @sa glfwSetScrollCallback - * - * @since Added in version 3.0. Replaces `GLFWmousewheelfun`. - * - * @ingroup input - */ -typedef void (* GLFWscrollfun)(GLFWwindow*,double,double); - -/*! @brief The function signature for keyboard key callbacks. - * - * This is the function signature for keyboard key callback functions. - * - * @param[in] window The window that received the event. - * @param[in] key The [keyboard key](@ref keys) that was pressed or released. - * @param[in] scancode The system-specific scancode of the key. - * @param[in] action `GLFW_PRESS`, `GLFW_RELEASE` or `GLFW_REPEAT`. - * @param[in] mods Bit field describing which [modifier keys](@ref mods) were - * held down. - * - * @sa @ref input_key - * @sa glfwSetKeyCallback - * - * @since Added in version 1.0. - * @glfw3 Added window handle, scancode and modifier mask parameters. - * - * @ingroup input - */ -typedef void (* GLFWkeyfun)(GLFWwindow*,int,int,int,int); - -/*! @brief The function signature for Unicode character callbacks. - * - * This is the function signature for Unicode character callback functions. - * - * @param[in] window The window that received the event. - * @param[in] codepoint The Unicode code point of the character. - * - * @sa @ref input_char - * @sa glfwSetCharCallback - * - * @since Added in version 2.4. - * @glfw3 Added window handle parameter. - * - * @ingroup input - */ -typedef void (* GLFWcharfun)(GLFWwindow*,unsigned int); - -/*! @brief The function signature for Unicode character with modifiers - * callbacks. - * - * This is the function signature for Unicode character with modifiers callback - * functions. It is called for each input character, regardless of what - * modifier keys are held down. - * - * @param[in] window The window that received the event. - * @param[in] codepoint The Unicode code point of the character. - * @param[in] mods Bit field describing which [modifier keys](@ref mods) were - * held down. - * - * @sa @ref input_char - * @sa glfwSetCharModsCallback - * - * @since Added in version 3.1. - * - * @ingroup input - */ -typedef void (* GLFWcharmodsfun)(GLFWwindow*,unsigned int,int); - -/*! @brief The function signature for file drop callbacks. - * - * This is the function signature for file drop callbacks. - * - * @param[in] window The window that received the event. - * @param[in] count The number of dropped files. - * @param[in] paths The UTF-8 encoded file and/or directory path names. - * - * @sa @ref path_drop - * @sa glfwSetDropCallback - * - * @since Added in version 3.1. - * - * @ingroup input - */ -typedef void (* GLFWdropfun)(GLFWwindow*,int,const char**); - -/*! @brief The function signature for monitor configuration callbacks. - * - * This is the function signature for monitor configuration callback functions. - * - * @param[in] monitor The monitor that was connected or disconnected. - * @param[in] event One of `GLFW_CONNECTED` or `GLFW_DISCONNECTED`. - * - * @sa @ref monitor_event - * @sa glfwSetMonitorCallback - * - * @since Added in version 3.0. - * - * @ingroup monitor - */ -typedef void (* GLFWmonitorfun)(GLFWmonitor*,int); - -/*! @brief The function signature for joystick configuration callbacks. - * - * This is the function signature for joystick configuration callback - * functions. - * - * @param[in] joy The joystick that was connected or disconnected. - * @param[in] event One of `GLFW_CONNECTED` or `GLFW_DISCONNECTED`. - * - * @sa @ref joystick_event - * @sa glfwSetJoystickCallback - * - * @since Added in version 3.2. - * - * @ingroup input - */ -typedef void (* GLFWjoystickfun)(int,int); - -/*! @brief Video mode type. - * - * This describes a single video mode. - * - * @sa @ref monitor_modes - * @sa glfwGetVideoMode glfwGetVideoModes - * - * @since Added in version 1.0. - * @glfw3 Added refresh rate member. - * - * @ingroup monitor - */ -typedef struct GLFWvidmode -{ - /*! The width, in screen coordinates, of the video mode. - */ - int width; - /*! The height, in screen coordinates, of the video mode. - */ - int height; - /*! The bit depth of the red channel of the video mode. - */ - int redBits; - /*! The bit depth of the green channel of the video mode. - */ - int greenBits; - /*! The bit depth of the blue channel of the video mode. - */ - int blueBits; - /*! The refresh rate, in Hz, of the video mode. - */ - int refreshRate; -} GLFWvidmode; - -/*! @brief Gamma ramp. - * - * This describes the gamma ramp for a monitor. - * - * @sa @ref monitor_gamma - * @sa glfwGetGammaRamp glfwSetGammaRamp - * - * @since Added in version 3.0. - * - * @ingroup monitor - */ -typedef struct GLFWgammaramp -{ - /*! An array of value describing the response of the red channel. - */ - unsigned short* red; - /*! An array of value describing the response of the green channel. - */ - unsigned short* green; - /*! An array of value describing the response of the blue channel. - */ - unsigned short* blue; - /*! The number of elements in each array. - */ - unsigned int size; -} GLFWgammaramp; - -/*! @brief Image data. - * - * @sa @ref cursor_custom - * - * @since Added in version 2.1. - * @glfw3 Removed format and bytes-per-pixel members. - */ -typedef struct GLFWimage -{ - /*! The width, in pixels, of this image. - */ - int width; - /*! The height, in pixels, of this image. - */ - int height; - /*! The pixel data of this image, arranged left-to-right, top-to-bottom. - */ - unsigned char* pixels; -} GLFWimage; - - -/************************************************************************* - * GLFW API functions - *************************************************************************/ - -/*! @brief Initializes the GLFW library. - * - * This function initializes the GLFW library. Before most GLFW functions can - * be used, GLFW must be initialized, and before an application terminates GLFW - * should be terminated in order to free any resources allocated during or - * after initialization. - * - * If this function fails, it calls @ref glfwTerminate before returning. If it - * succeeds, you should call @ref glfwTerminate before the application exits. - * - * Additional calls to this function after successful initialization but before - * termination will return `GLFW_TRUE` immediately. - * - * @return `GLFW_TRUE` if successful, or `GLFW_FALSE` if an - * [error](@ref error_handling) occurred. - * - * @errors Possible errors include @ref GLFW_PLATFORM_ERROR. - * - * @remark @osx This function will change the current directory of the - * application to the `Contents/Resources` subdirectory of the application's - * bundle, if present. This can be disabled with a - * [compile-time option](@ref compile_options_osx). - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref intro_init - * @sa glfwTerminate - * - * @since Added in version 1.0. - * - * @ingroup init - */ -GLFWAPI int glfwInit(void); - -/*! @brief Terminates the GLFW library. - * - * This function destroys all remaining windows and cursors, restores any - * modified gamma ramps and frees any other allocated resources. Once this - * function is called, you must again call @ref glfwInit successfully before - * you will be able to use most GLFW functions. - * - * If GLFW has been successfully initialized, this function should be called - * before the application exits. If initialization fails, there is no need to - * call this function, as it is called by @ref glfwInit before it returns - * failure. - * - * @errors Possible errors include @ref GLFW_PLATFORM_ERROR. - * - * @remark This function may be called before @ref glfwInit. - * - * @warning The contexts of any remaining windows must not be current on any - * other thread when this function is called. - * - * @reentrancy This function must not be called from a callback. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref intro_init - * @sa glfwInit - * - * @since Added in version 1.0. - * - * @ingroup init - */ -GLFWAPI void glfwTerminate(void); - -/*! @brief Retrieves the version of the GLFW library. - * - * This function retrieves the major, minor and revision numbers of the GLFW - * library. It is intended for when you are using GLFW as a shared library and - * want to ensure that you are using the minimum required version. - * - * Any or all of the version arguments may be `NULL`. - * - * @param[out] major Where to store the major version number, or `NULL`. - * @param[out] minor Where to store the minor version number, or `NULL`. - * @param[out] rev Where to store the revision number, or `NULL`. - * - * @errors None. - * - * @remark This function may be called before @ref glfwInit. - * - * @thread_safety This function may be called from any thread. - * - * @sa @ref intro_version - * @sa glfwGetVersionString - * - * @since Added in version 1.0. - * - * @ingroup init - */ -GLFWAPI void glfwGetVersion(int* major, int* minor, int* rev); - -/*! @brief Returns a string describing the compile-time configuration. - * - * This function returns the compile-time generated - * [version string](@ref intro_version_string) of the GLFW library binary. It - * describes the version, platform, compiler and any platform-specific - * compile-time options. It should not be confused with the OpenGL or OpenGL - * ES version string, queried with `glGetString`. - * - * __Do not use the version string__ to parse the GLFW library version. The - * @ref glfwGetVersion function provides the version of the running library - * binary in numerical format. - * - * @return The ASCII encoded GLFW version string. - * - * @errors None. - * - * @remark This function may be called before @ref glfwInit. - * - * @pointer_lifetime The returned string is static and compile-time generated. - * - * @thread_safety This function may be called from any thread. - * - * @sa @ref intro_version - * @sa glfwGetVersion - * - * @since Added in version 3.0. - * - * @ingroup init - */ -GLFWAPI const char* glfwGetVersionString(void); - -/*! @brief Sets the error callback. - * - * This function sets the error callback, which is called with an error code - * and a human-readable description each time a GLFW error occurs. - * - * The error callback is called on the thread where the error occurred. If you - * are using GLFW from multiple threads, your error callback needs to be - * written accordingly. - * - * Because the description string may have been generated specifically for that - * error, it is not guaranteed to be valid after the callback has returned. If - * you wish to use it after the callback returns, you need to make a copy. - * - * Once set, the error callback remains set even after the library has been - * terminated. - * - * @param[in] cbfun The new callback, or `NULL` to remove the currently set - * callback. - * @return The previously set callback, or `NULL` if no callback was set. - * - * @errors None. - * - * @remark This function may be called before @ref glfwInit. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref error_handling - * - * @since Added in version 3.0. - * - * @ingroup init - */ -GLFWAPI GLFWerrorfun glfwSetErrorCallback(GLFWerrorfun cbfun); - -/*! @brief Returns the currently connected monitors. - * - * This function returns an array of handles for all currently connected - * monitors. The primary monitor is always first in the returned array. If no - * monitors were found, this function returns `NULL`. - * - * @param[out] count Where to store the number of monitors in the returned - * array. This is set to zero if an error occurred. - * @return An array of monitor handles, or `NULL` if no monitors were found or - * if an [error](@ref error_handling) occurred. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @pointer_lifetime The returned array is allocated and freed by GLFW. You - * should not free it yourself. It is guaranteed to be valid only until the - * monitor configuration changes or the library is terminated. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref monitor_monitors - * @sa @ref monitor_event - * @sa glfwGetPrimaryMonitor - * - * @since Added in version 3.0. - * - * @ingroup monitor - */ -GLFWAPI GLFWmonitor** glfwGetMonitors(int* count); - -/*! @brief Returns the primary monitor. - * - * This function returns the primary monitor. This is usually the monitor - * where elements like the task bar or global menu bar are located. - * - * @return The primary monitor, or `NULL` if no monitors were found or if an - * [error](@ref error_handling) occurred. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @thread_safety This function must only be called from the main thread. - * - * @remark The primary monitor is always first in the array returned by @ref - * glfwGetMonitors. - * - * @sa @ref monitor_monitors - * @sa glfwGetMonitors - * - * @since Added in version 3.0. - * - * @ingroup monitor - */ -GLFWAPI GLFWmonitor* glfwGetPrimaryMonitor(void); - -/*! @brief Returns the position of the monitor's viewport on the virtual screen. - * - * This function returns the position, in screen coordinates, of the upper-left - * corner of the specified monitor. - * - * Any or all of the position arguments may be `NULL`. If an error occurs, all - * non-`NULL` position arguments will be set to zero. - * - * @param[in] monitor The monitor to query. - * @param[out] xpos Where to store the monitor x-coordinate, or `NULL`. - * @param[out] ypos Where to store the monitor y-coordinate, or `NULL`. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref monitor_properties - * - * @since Added in version 3.0. - * - * @ingroup monitor - */ -GLFWAPI void glfwGetMonitorPos(GLFWmonitor* monitor, int* xpos, int* ypos); - -/*! @brief Returns the physical size of the monitor. - * - * This function returns the size, in millimetres, of the display area of the - * specified monitor. - * - * Some systems do not provide accurate monitor size information, either - * because the monitor - * [EDID](https://en.wikipedia.org/wiki/Extended_display_identification_data) - * data is incorrect or because the driver does not report it accurately. - * - * Any or all of the size arguments may be `NULL`. If an error occurs, all - * non-`NULL` size arguments will be set to zero. - * - * @param[in] monitor The monitor to query. - * @param[out] widthMM Where to store the width, in millimetres, of the - * monitor's display area, or `NULL`. - * @param[out] heightMM Where to store the height, in millimetres, of the - * monitor's display area, or `NULL`. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @remark @win32 calculates the returned physical size from the - * current resolution and system DPI instead of querying the monitor EDID data. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref monitor_properties - * - * @since Added in version 3.0. - * - * @ingroup monitor - */ -GLFWAPI void glfwGetMonitorPhysicalSize(GLFWmonitor* monitor, int* widthMM, int* heightMM); - -/*! @brief Returns the name of the specified monitor. - * - * This function returns a human-readable name, encoded as UTF-8, of the - * specified monitor. The name typically reflects the make and model of the - * monitor and is not guaranteed to be unique among the connected monitors. - * - * @param[in] monitor The monitor to query. - * @return The UTF-8 encoded name of the monitor, or `NULL` if an - * [error](@ref error_handling) occurred. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @pointer_lifetime The returned string is allocated and freed by GLFW. You - * should not free it yourself. It is valid until the specified monitor is - * disconnected or the library is terminated. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref monitor_properties - * - * @since Added in version 3.0. - * - * @ingroup monitor - */ -GLFWAPI const char* glfwGetMonitorName(GLFWmonitor* monitor); - -/*! @brief Sets the monitor configuration callback. - * - * This function sets the monitor configuration callback, or removes the - * currently set callback. This is called when a monitor is connected to or - * disconnected from the system. - * - * @param[in] cbfun The new callback, or `NULL` to remove the currently set - * callback. - * @return The previously set callback, or `NULL` if no callback was set or the - * library had not been [initialized](@ref intro_init). - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref monitor_event - * - * @since Added in version 3.0. - * - * @ingroup monitor - */ -GLFWAPI GLFWmonitorfun glfwSetMonitorCallback(GLFWmonitorfun cbfun); - -/*! @brief Returns the available video modes for the specified monitor. - * - * This function returns an array of all video modes supported by the specified - * monitor. The returned array is sorted in ascending order, first by color - * bit depth (the sum of all channel depths) and then by resolution area (the - * product of width and height). - * - * @param[in] monitor The monitor to query. - * @param[out] count Where to store the number of video modes in the returned - * array. This is set to zero if an error occurred. - * @return An array of video modes, or `NULL` if an - * [error](@ref error_handling) occurred. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @pointer_lifetime The returned array is allocated and freed by GLFW. You - * should not free it yourself. It is valid until the specified monitor is - * disconnected, this function is called again for that monitor or the library - * is terminated. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref monitor_modes - * @sa glfwGetVideoMode - * - * @since Added in version 1.0. - * @glfw3 Changed to return an array of modes for a specific monitor. - * - * @ingroup monitor - */ -GLFWAPI const GLFWvidmode* glfwGetVideoModes(GLFWmonitor* monitor, int* count); - -/*! @brief Returns the current mode of the specified monitor. - * - * This function returns the current video mode of the specified monitor. If - * you have created a full screen window for that monitor, the return value - * will depend on whether that window is iconified. - * - * @param[in] monitor The monitor to query. - * @return The current mode of the monitor, or `NULL` if an - * [error](@ref error_handling) occurred. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @pointer_lifetime The returned array is allocated and freed by GLFW. You - * should not free it yourself. It is valid until the specified monitor is - * disconnected or the library is terminated. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref monitor_modes - * @sa glfwGetVideoModes - * - * @since Added in version 3.0. Replaces `glfwGetDesktopMode`. - * - * @ingroup monitor - */ -GLFWAPI const GLFWvidmode* glfwGetVideoMode(GLFWmonitor* monitor); - -/*! @brief Generates a gamma ramp and sets it for the specified monitor. - * - * This function generates a 256-element gamma ramp from the specified exponent - * and then calls @ref glfwSetGammaRamp with it. The value must be a finite - * number greater than zero. - * - * @param[in] monitor The monitor whose gamma ramp to set. - * @param[in] gamma The desired exponent. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED, @ref - * GLFW_INVALID_VALUE and @ref GLFW_PLATFORM_ERROR. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref monitor_gamma - * - * @since Added in version 3.0. - * - * @ingroup monitor - */ -GLFWAPI void glfwSetGamma(GLFWmonitor* monitor, float gamma); - -/*! @brief Returns the current gamma ramp for the specified monitor. - * - * This function returns the current gamma ramp of the specified monitor. - * - * @param[in] monitor The monitor to query. - * @return The current gamma ramp, or `NULL` if an - * [error](@ref error_handling) occurred. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @pointer_lifetime The returned structure and its arrays are allocated and - * freed by GLFW. You should not free them yourself. They are valid until the - * specified monitor is disconnected, this function is called again for that - * monitor or the library is terminated. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref monitor_gamma - * - * @since Added in version 3.0. - * - * @ingroup monitor - */ -GLFWAPI const GLFWgammaramp* glfwGetGammaRamp(GLFWmonitor* monitor); - -/*! @brief Sets the current gamma ramp for the specified monitor. - * - * This function sets the current gamma ramp for the specified monitor. The - * original gamma ramp for that monitor is saved by GLFW the first time this - * function is called and is restored by @ref glfwTerminate. - * - * @param[in] monitor The monitor whose gamma ramp to set. - * @param[in] ramp The gamma ramp to use. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @remark Gamma ramp sizes other than 256 are not supported by all platforms - * or graphics hardware. - * - * @remark @win32 The gamma ramp size must be 256. - * - * @pointer_lifetime The specified gamma ramp is copied before this function - * returns. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref monitor_gamma - * - * @since Added in version 3.0. - * - * @ingroup monitor - */ -GLFWAPI void glfwSetGammaRamp(GLFWmonitor* monitor, const GLFWgammaramp* ramp); - -/*! @brief Resets all window hints to their default values. - * - * This function resets all window hints to their - * [default values](@ref window_hints_values). - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref window_hints - * @sa glfwWindowHint - * - * @since Added in version 3.0. - * - * @ingroup window - */ -GLFWAPI void glfwDefaultWindowHints(void); - -/*! @brief Sets the specified window hint to the desired value. - * - * This function sets hints for the next call to @ref glfwCreateWindow. The - * hints, once set, retain their values until changed by a call to @ref - * glfwWindowHint or @ref glfwDefaultWindowHints, or until the library is - * terminated. - * - * This function does not check whether the specified hint values are valid. - * If you set hints to invalid values this will instead be reported by the next - * call to @ref glfwCreateWindow. - * - * @param[in] hint The [window hint](@ref window_hints) to set. - * @param[in] value The new value of the window hint. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_INVALID_ENUM. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref window_hints - * @sa glfwDefaultWindowHints - * - * @since Added in version 3.0. Replaces `glfwOpenWindowHint`. - * - * @ingroup window - */ -GLFWAPI void glfwWindowHint(int hint, int value); - -/*! @brief Creates a window and its associated context. - * - * This function creates a window and its associated OpenGL or OpenGL ES - * context. Most of the options controlling how the window and its context - * should be created are specified with [window hints](@ref window_hints). - * - * Successful creation does not change which context is current. Before you - * can use the newly created context, you need to - * [make it current](@ref context_current). For information about the `share` - * parameter, see @ref context_sharing. - * - * The created window, framebuffer and context may differ from what you - * requested, as not all parameters and hints are - * [hard constraints](@ref window_hints_hard). This includes the size of the - * window, especially for full screen windows. To query the actual attributes - * of the created window, framebuffer and context, see @ref - * glfwGetWindowAttrib, @ref glfwGetWindowSize and @ref glfwGetFramebufferSize. - * - * To create a full screen window, you need to specify the monitor the window - * will cover. If no monitor is specified, the window will be windowed mode. - * Unless you have a way for the user to choose a specific monitor, it is - * recommended that you pick the primary monitor. For more information on how - * to query connected monitors, see @ref monitor_monitors. - * - * For full screen windows, the specified size becomes the resolution of the - * window's _desired video mode_. As long as a full screen window is not - * iconified, the supported video mode most closely matching the desired video - * mode is set for the specified monitor. For more information about full - * screen windows, including the creation of so called _windowed full screen_ - * or _borderless full screen_ windows, see @ref window_windowed_full_screen. - * - * By default, newly created windows use the placement recommended by the - * window system. To create the window at a specific position, make it - * initially invisible using the [GLFW_VISIBLE](@ref window_hints_wnd) window - * hint, set its [position](@ref window_pos) and then [show](@ref window_hide) - * it. - * - * As long as at least one full screen window is not iconified, the screensaver - * is prohibited from starting. - * - * Window systems put limits on window sizes. Very large or very small window - * dimensions may be overridden by the window system on creation. Check the - * actual [size](@ref window_size) after creation. - * - * The [swap interval](@ref buffer_swap) is not set during window creation and - * the initial value may vary depending on driver settings and defaults. - * - * @param[in] width The desired width, in screen coordinates, of the window. - * This must be greater than zero. - * @param[in] height The desired height, in screen coordinates, of the window. - * This must be greater than zero. - * @param[in] title The initial, UTF-8 encoded window title. - * @param[in] monitor The monitor to use for full screen mode, or `NULL` for - * windowed mode. - * @param[in] share The window whose context to share resources with, or `NULL` - * to not share resources. - * @return The handle of the created window, or `NULL` if an - * [error](@ref error_handling) occurred. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED, @ref - * GLFW_INVALID_ENUM, @ref GLFW_INVALID_VALUE, @ref GLFW_API_UNAVAILABLE, @ref - * GLFW_VERSION_UNAVAILABLE, @ref GLFW_FORMAT_UNAVAILABLE and @ref - * GLFW_PLATFORM_ERROR. - * - * @remark @win32 Window creation will fail if the Microsoft GDI software - * OpenGL implementation is the only one available. - * - * @remark @win32 If the executable has an icon resource named `GLFW_ICON,` - * it will be set as the icon for the window. If no such icon is present, the - * `IDI_WINLOGO` icon will be used instead. - * - * @remark @win32 The context to share resources with must not be current on - * any other thread. - * - * @remark @osx The GLFW window has no icon, as it is not a document - * window, but the dock icon will be the same as the application bundle's icon. - * For more information on bundles, see the - * [Bundle Programming Guide](https://developer.apple.com/library/mac/documentation/CoreFoundation/Conceptual/CFBundles/) - * in the Mac Developer Library. - * - * @remark @osx The first time a window is created the menu bar is populated - * with common commands like Hide, Quit and About. The About entry opens - * a minimal about dialog with information from the application's bundle. The - * menu bar can be disabled with a - * [compile-time option](@ref compile_options_osx). - * - * @remark @osx On OS X 10.10 and later the window frame will not be rendered - * at full resolution on Retina displays unless the `NSHighResolutionCapable` - * key is enabled in the application bundle's `Info.plist`. For more - * information, see - * [High Resolution Guidelines for OS X](https://developer.apple.com/library/mac/documentation/GraphicsAnimation/Conceptual/HighResolutionOSX/Explained/Explained.html) - * in the Mac Developer Library. The GLFW test and example programs use - * a custom `Info.plist` template for this, which can be found as - * `CMake/MacOSXBundleInfo.plist.in` in the source tree. - * - * @remark @x11 There is no mechanism for setting the window icon yet. - * - * @remark @x11 Some window managers will not respect the placement of - * initially hidden windows. - * - * @remark @x11 Due to the asynchronous nature of X11, it may take a moment for - * a window to reach its requested state. This means you may not be able to - * query the final size, position or other attributes directly after window - * creation. - * - * @reentrancy This function must not be called from a callback. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref window_creation - * @sa glfwDestroyWindow - * - * @since Added in version 3.0. Replaces `glfwOpenWindow`. - * - * @ingroup window - */ -GLFWAPI GLFWwindow* glfwCreateWindow(int width, int height, const char* title, GLFWmonitor* monitor, GLFWwindow* share); - -/*! @brief Destroys the specified window and its context. - * - * This function destroys the specified window and its context. On calling - * this function, no further callbacks will be called for that window. - * - * If the context of the specified window is current on the main thread, it is - * detached before being destroyed. - * - * @param[in] window The window to destroy. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @note The context of the specified window must not be current on any other - * thread when this function is called. - * - * @reentrancy This function must not be called from a callback. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref window_creation - * @sa glfwCreateWindow - * - * @since Added in version 3.0. Replaces `glfwCloseWindow`. - * - * @ingroup window - */ -GLFWAPI void glfwDestroyWindow(GLFWwindow* window); - -/*! @brief Checks the close flag of the specified window. - * - * This function returns the value of the close flag of the specified window. - * - * @param[in] window The window to query. - * @return The value of the close flag. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @thread_safety This function may be called from any thread. Access is not - * synchronized. - * - * @sa @ref window_close - * - * @since Added in version 3.0. - * - * @ingroup window - */ -GLFWAPI int glfwWindowShouldClose(GLFWwindow* window); - -/*! @brief Sets the close flag of the specified window. - * - * This function sets the value of the close flag of the specified window. - * This can be used to override the user's attempt to close the window, or - * to signal that it should be closed. - * - * @param[in] window The window whose flag to change. - * @param[in] value The new value. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @thread_safety This function may be called from any thread. Access is not - * synchronized. - * - * @sa @ref window_close - * - * @since Added in version 3.0. - * - * @ingroup window - */ -GLFWAPI void glfwSetWindowShouldClose(GLFWwindow* window, int value); - -/*! @brief Sets the title of the specified window. - * - * This function sets the window title, encoded as UTF-8, of the specified - * window. - * - * @param[in] window The window whose title to change. - * @param[in] title The UTF-8 encoded window title. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @remark @osx The window title will not be updated until the next time you - * process events. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref window_title - * - * @since Added in version 1.0. - * @glfw3 Added window handle parameter. - * - * @ingroup window - */ -GLFWAPI void glfwSetWindowTitle(GLFWwindow* window, const char* title); - -/*! @brief Sets the icon for the specified window. - * - * This function sets the icon of the specified window. If passed an array of - * candidate images, those of or closest to the sizes desired by the system are - * selected. If no images are specified, the window reverts to its default - * icon. - * - * The desired image sizes varies depending on platform and system settings. - * The selected images will be rescaled as needed. Good sizes include 16x16, - * 32x32 and 48x48. - * - * @param[in] window The window whose icon to set. - * @param[in] count The number of images in the specified array, or zero to - * revert to the default window icon. - * @param[in] images The images to create the icon from. This is ignored if - * count is zero. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @pointer_lifetime The specified image data is copied before this function - * returns. - * - * @remark @osx The GLFW window has no icon, as it is not a document - * window, but the dock icon will be the same as the application bundle's icon. - * For more information on bundles, see the - * [Bundle Programming Guide](https://developer.apple.com/library/mac/documentation/CoreFoundation/Conceptual/CFBundles/) - * in the Mac Developer Library. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref window_icon - * - * @since Added in version 3.2. - * - * @ingroup window - */ -GLFWAPI void glfwSetWindowIcon(GLFWwindow* window, int count, const GLFWimage* images); - -/*! @brief Retrieves the position of the client area of the specified window. - * - * This function retrieves the position, in screen coordinates, of the - * upper-left corner of the client area of the specified window. - * - * Any or all of the position arguments may be `NULL`. If an error occurs, all - * non-`NULL` position arguments will be set to zero. - * - * @param[in] window The window to query. - * @param[out] xpos Where to store the x-coordinate of the upper-left corner of - * the client area, or `NULL`. - * @param[out] ypos Where to store the y-coordinate of the upper-left corner of - * the client area, or `NULL`. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref window_pos - * @sa glfwSetWindowPos - * - * @since Added in version 3.0. - * - * @ingroup window - */ -GLFWAPI void glfwGetWindowPos(GLFWwindow* window, int* xpos, int* ypos); - -/*! @brief Sets the position of the client area of the specified window. - * - * This function sets the position, in screen coordinates, of the upper-left - * corner of the client area of the specified windowed mode window. If the - * window is a full screen window, this function does nothing. - * - * __Do not use this function__ to move an already visible window unless you - * have very good reasons for doing so, as it will confuse and annoy the user. - * - * The window manager may put limits on what positions are allowed. GLFW - * cannot and should not override these limits. - * - * @param[in] window The window to query. - * @param[in] xpos The x-coordinate of the upper-left corner of the client area. - * @param[in] ypos The y-coordinate of the upper-left corner of the client area. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref window_pos - * @sa glfwGetWindowPos - * - * @since Added in version 1.0. - * @glfw3 Added window handle parameter. - * - * @ingroup window - */ -GLFWAPI void glfwSetWindowPos(GLFWwindow* window, int xpos, int ypos); - -/*! @brief Retrieves the size of the client area of the specified window. - * - * This function retrieves the size, in screen coordinates, of the client area - * of the specified window. If you wish to retrieve the size of the - * framebuffer of the window in pixels, see @ref glfwGetFramebufferSize. - * - * Any or all of the size arguments may be `NULL`. If an error occurs, all - * non-`NULL` size arguments will be set to zero. - * - * @param[in] window The window whose size to retrieve. - * @param[out] width Where to store the width, in screen coordinates, of the - * client area, or `NULL`. - * @param[out] height Where to store the height, in screen coordinates, of the - * client area, or `NULL`. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref window_size - * @sa glfwSetWindowSize - * - * @since Added in version 1.0. - * @glfw3 Added window handle parameter. - * - * @ingroup window - */ -GLFWAPI void glfwGetWindowSize(GLFWwindow* window, int* width, int* height); - -/*! @brief Sets the size limits of the specified window. - * - * This function sets the size limits of the client area of the specified - * window. If the window is full screen, the size limits only take effect if - * once it is made windowed. If the window is not resizable, this function - * does nothing. - * - * The size limits are applied immediately to a windowed mode window and may - * cause it to be resized. - * - * @param[in] window The window to set limits for. - * @param[in] minwidth The minimum width, in screen coordinates, of the client - * area, or `GLFW_DONT_CARE`. - * @param[in] minheight The minimum height, in screen coordinates, of the - * client area, or `GLFW_DONT_CARE`. - * @param[in] maxwidth The maximum width, in screen coordinates, of the client - * area, or `GLFW_DONT_CARE`. - * @param[in] maxheight The maximum height, in screen coordinates, of the - * client area, or `GLFW_DONT_CARE`. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @remark If you set size limits and an aspect ratio that conflict, the - * results are undefined. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref window_sizelimits - * @sa glfwSetWindowAspectRatio - * - * @since Added in version 3.2. - * - * @ingroup window - */ -GLFWAPI void glfwSetWindowSizeLimits(GLFWwindow* window, int minwidth, int minheight, int maxwidth, int maxheight); - -/*! @brief Sets the aspect ratio of the specified window. - * - * This function sets the required aspect ratio of the client area of the - * specified window. If the window is full screen, the aspect ratio only takes - * effect once it is made windowed. If the window is not resizable, this - * function does nothing. - * - * The aspect ratio is specified as a numerator and a denominator and both - * values must be greater than zero. For example, the common 16:9 aspect ratio - * is specified as 16 and 9, respectively. - * - * If the numerator and denominator is set to `GLFW_DONT_CARE` then the aspect - * ratio limit is disabled. - * - * The aspect ratio is applied immediately to a windowed mode window and may - * cause it to be resized. - * - * @param[in] window The window to set limits for. - * @param[in] numer The numerator of the desired aspect ratio, or - * `GLFW_DONT_CARE`. - * @param[in] denom The denominator of the desired aspect ratio, or - * `GLFW_DONT_CARE`. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED, @ref - * GLFW_INVALID_VALUE and @ref GLFW_PLATFORM_ERROR. - * - * @remark If you set size limits and an aspect ratio that conflict, the - * results are undefined. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref window_sizelimits - * @sa glfwSetWindowSizeLimits - * - * @since Added in version 3.2. - * - * @ingroup window - */ -GLFWAPI void glfwSetWindowAspectRatio(GLFWwindow* window, int numer, int denom); - -/*! @brief Sets the size of the client area of the specified window. - * - * This function sets the size, in screen coordinates, of the client area of - * the specified window. - * - * For full screen windows, this function updates the resolution of its desired - * video mode and switches to the video mode closest to it, without affecting - * the window's context. As the context is unaffected, the bit depths of the - * framebuffer remain unchanged. - * - * If you wish to update the refresh rate of the desired video mode in addition - * to its resolution, see @ref glfwSetWindowMonitor. - * - * The window manager may put limits on what sizes are allowed. GLFW cannot - * and should not override these limits. - * - * @param[in] window The window to resize. - * @param[in] width The desired width, in screen coordinates, of the window - * client area. - * @param[in] height The desired height, in screen coordinates, of the window - * client area. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref window_size - * @sa glfwGetWindowSize - * @sa glfwSetWindowMonitor - * - * @since Added in version 1.0. - * @glfw3 Added window handle parameter. - * - * @ingroup window - */ -GLFWAPI void glfwSetWindowSize(GLFWwindow* window, int width, int height); - -/*! @brief Retrieves the size of the framebuffer of the specified window. - * - * This function retrieves the size, in pixels, of the framebuffer of the - * specified window. If you wish to retrieve the size of the window in screen - * coordinates, see @ref glfwGetWindowSize. - * - * Any or all of the size arguments may be `NULL`. If an error occurs, all - * non-`NULL` size arguments will be set to zero. - * - * @param[in] window The window whose framebuffer to query. - * @param[out] width Where to store the width, in pixels, of the framebuffer, - * or `NULL`. - * @param[out] height Where to store the height, in pixels, of the framebuffer, - * or `NULL`. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref window_fbsize - * @sa glfwSetFramebufferSizeCallback - * - * @since Added in version 3.0. - * - * @ingroup window - */ -GLFWAPI void glfwGetFramebufferSize(GLFWwindow* window, int* width, int* height); - -/*! @brief Retrieves the size of the frame of the window. - * - * This function retrieves the size, in screen coordinates, of each edge of the - * frame of the specified window. This size includes the title bar, if the - * window has one. The size of the frame may vary depending on the - * [window-related hints](@ref window_hints_wnd) used to create it. - * - * Because this function retrieves the size of each window frame edge and not - * the offset along a particular coordinate axis, the retrieved values will - * always be zero or positive. - * - * Any or all of the size arguments may be `NULL`. If an error occurs, all - * non-`NULL` size arguments will be set to zero. - * - * @param[in] window The window whose frame size to query. - * @param[out] left Where to store the size, in screen coordinates, of the left - * edge of the window frame, or `NULL`. - * @param[out] top Where to store the size, in screen coordinates, of the top - * edge of the window frame, or `NULL`. - * @param[out] right Where to store the size, in screen coordinates, of the - * right edge of the window frame, or `NULL`. - * @param[out] bottom Where to store the size, in screen coordinates, of the - * bottom edge of the window frame, or `NULL`. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref window_size - * - * @since Added in version 3.1. - * - * @ingroup window - */ -GLFWAPI void glfwGetWindowFrameSize(GLFWwindow* window, int* left, int* top, int* right, int* bottom); - -/*! @brief Iconifies the specified window. - * - * This function iconifies (minimizes) the specified window if it was - * previously restored. If the window is already iconified, this function does - * nothing. - * - * If the specified window is a full screen window, the original monitor - * resolution is restored until the window is restored. - * - * @param[in] window The window to iconify. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref window_iconify - * @sa glfwRestoreWindow - * @sa glfwMaximizeWindow - * - * @since Added in version 2.1. - * @glfw3 Added window handle parameter. - * - * @ingroup window - */ -GLFWAPI void glfwIconifyWindow(GLFWwindow* window); - -/*! @brief Restores the specified window. - * - * This function restores the specified window if it was previously iconified - * (minimized) or maximized. If the window is already restored, this function - * does nothing. - * - * If the specified window is a full screen window, the resolution chosen for - * the window is restored on the selected monitor. - * - * @param[in] window The window to restore. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref window_iconify - * @sa glfwIconifyWindow - * @sa glfwMaximizeWindow - * - * @since Added in version 2.1. - * @glfw3 Added window handle parameter. - * - * @ingroup window - */ -GLFWAPI void glfwRestoreWindow(GLFWwindow* window); - -/*! @brief Maximizes the specified window. - * - * This function maximizes the specified window if it was previously not - * maximized. If the window is already maximized, this function does nothing. - * - * If the specified window is a full screen window, this function does nothing. - * - * @param[in] window The window to maximize. - * - * @par Thread Safety - * This function may only be called from the main thread. - * - * @sa @ref window_iconify - * @sa glfwIconifyWindow - * @sa glfwRestoreWindow - * - * @since Added in GLFW 3.2. - * - * @ingroup window - */ -GLFWAPI void glfwMaximizeWindow(GLFWwindow* window); - -/*! @brief Makes the specified window visible. - * - * This function makes the specified window visible if it was previously - * hidden. If the window is already visible or is in full screen mode, this - * function does nothing. - * - * @param[in] window The window to make visible. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref window_hide - * @sa glfwHideWindow - * - * @since Added in version 3.0. - * - * @ingroup window - */ -GLFWAPI void glfwShowWindow(GLFWwindow* window); - -/*! @brief Hides the specified window. - * - * This function hides the specified window if it was previously visible. If - * the window is already hidden or is in full screen mode, this function does - * nothing. - * - * @param[in] window The window to hide. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref window_hide - * @sa glfwShowWindow - * - * @since Added in version 3.0. - * - * @ingroup window - */ -GLFWAPI void glfwHideWindow(GLFWwindow* window); - -/*! @brief Brings the specified window to front and sets input focus. - * - * This function brings the specified window to front and sets input focus. - * The window should already be visible and not iconified. - * - * By default, both windowed and full screen mode windows are focused when - * initially created. Set the [GLFW_FOCUSED](@ref window_hints_wnd) to disable - * this behavior. - * - * __Do not use this function__ to steal focus from other applications unless - * you are certain that is what the user wants. Focus stealing can be - * extremely disruptive. - * - * @param[in] window The window to give input focus. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref window_focus - * - * @since Added in version 3.2. - * - * @ingroup window - */ -GLFWAPI void glfwFocusWindow(GLFWwindow* window); - -/*! @brief Returns the monitor that the window uses for full screen mode. - * - * This function returns the handle of the monitor that the specified window is - * in full screen on. - * - * @param[in] window The window to query. - * @return The monitor, or `NULL` if the window is in windowed mode or an error - * occurred. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref window_monitor - * @sa glfwSetWindowMonitor - * - * @since Added in version 3.0. - * - * @ingroup window - */ -GLFWAPI GLFWmonitor* glfwGetWindowMonitor(GLFWwindow* window); - -/*! @brief Sets the mode, monitor, video mode and placement of a window. - * - * This function sets the monitor that the window uses for full screen mode or, - * if the monitor is `NULL`, makes it windowed mode. - * - * When setting a monitor, this function updates the width, height and refresh - * rate of the desired video mode and switches to the video mode closest to it. - * The window position is ignored when setting a monitor. - * - * When the monitor is `NULL`, the position, width and height are used to - * place the window client area. The refresh rate is ignored when no monitor - * is specified. - * - * If you only wish to update the resolution of a full screen window or the - * size of a windowed mode window, see @ref glfwSetWindowSize. - * - * When a window transitions from full screen to windowed mode, this function - * restores any previous window settings such as whether it is decorated, - * floating, resizable, has size or aspect ratio limits, etc.. - * - * @param[in] window The window whose monitor, size or video mode to set. - * @param[in] monitor The desired monitor, or `NULL` to set windowed mode. - * @param[in] xpos The desired x-coordinate of the upper-left corner of the - * client area. - * @param[in] ypos The desired y-coordinate of the upper-left corner of the - * client area. - * @param[in] width The desired with, in screen coordinates, of the client area - * or video mode. - * @param[in] height The desired height, in screen coordinates, of the client - * area or video mode. - * @param[in] refreshRate The desired refresh rate, in Hz, of the video mode. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref window_monitor - * @sa @ref window_full_screen - * @sa glfwGetWindowMonitor - * @sa glfwSetWindowSize - * - * @since Added in version 3.2. - * - * @ingroup window - */ -GLFWAPI void glfwSetWindowMonitor(GLFWwindow* window, GLFWmonitor* monitor, int xpos, int ypos, int width, int height, int refreshRate); - -/*! @brief Returns an attribute of the specified window. - * - * This function returns the value of an attribute of the specified window or - * its OpenGL or OpenGL ES context. - * - * @param[in] window The window to query. - * @param[in] attrib The [window attribute](@ref window_attribs) whose value to - * return. - * @return The value of the attribute, or zero if an - * [error](@ref error_handling) occurred. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED, @ref - * GLFW_INVALID_ENUM and @ref GLFW_PLATFORM_ERROR. - * - * @remark Framebuffer related hints are not window attributes. See @ref - * window_attribs_fb for more information. - * - * @remark Zero is a valid value for many window and context related - * attributes so you cannot use a return value of zero as an indication of - * errors. However, this function should not fail as long as it is passed - * valid arguments and the library has been [initialized](@ref intro_init). - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref window_attribs - * - * @since Added in version 3.0. Replaces `glfwGetWindowParam` and - * `glfwGetGLVersion`. - * - * @ingroup window - */ -GLFWAPI int glfwGetWindowAttrib(GLFWwindow* window, int attrib); - -/*! @brief Sets the user pointer of the specified window. - * - * This function sets the user-defined pointer of the specified window. The - * current value is retained until the window is destroyed. The initial value - * is `NULL`. - * - * @param[in] window The window whose pointer to set. - * @param[in] pointer The new value. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @thread_safety This function may be called from any thread. Access is not - * synchronized. - * - * @sa @ref window_userptr - * @sa glfwGetWindowUserPointer - * - * @since Added in version 3.0. - * - * @ingroup window - */ -GLFWAPI void glfwSetWindowUserPointer(GLFWwindow* window, void* pointer); - -/*! @brief Returns the user pointer of the specified window. - * - * This function returns the current value of the user-defined pointer of the - * specified window. The initial value is `NULL`. - * - * @param[in] window The window whose pointer to return. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @thread_safety This function may be called from any thread. Access is not - * synchronized. - * - * @sa @ref window_userptr - * @sa glfwSetWindowUserPointer - * - * @since Added in version 3.0. - * - * @ingroup window - */ -GLFWAPI void* glfwGetWindowUserPointer(GLFWwindow* window); - -/*! @brief Sets the position callback for the specified window. - * - * This function sets the position callback of the specified window, which is - * called when the window is moved. The callback is provided with the screen - * position of the upper-left corner of the client area of the window. - * - * @param[in] window The window whose callback to set. - * @param[in] cbfun The new callback, or `NULL` to remove the currently set - * callback. - * @return The previously set callback, or `NULL` if no callback was set or the - * library had not been [initialized](@ref intro_init). - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref window_pos - * - * @since Added in version 3.0. - * - * @ingroup window - */ -GLFWAPI GLFWwindowposfun glfwSetWindowPosCallback(GLFWwindow* window, GLFWwindowposfun cbfun); - -/*! @brief Sets the size callback for the specified window. - * - * This function sets the size callback of the specified window, which is - * called when the window is resized. The callback is provided with the size, - * in screen coordinates, of the client area of the window. - * - * @param[in] window The window whose callback to set. - * @param[in] cbfun The new callback, or `NULL` to remove the currently set - * callback. - * @return The previously set callback, or `NULL` if no callback was set or the - * library had not been [initialized](@ref intro_init). - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref window_size - * - * @since Added in version 1.0. - * @glfw3 Added window handle parameter and return value. - * - * @ingroup window - */ -GLFWAPI GLFWwindowsizefun glfwSetWindowSizeCallback(GLFWwindow* window, GLFWwindowsizefun cbfun); - -/*! @brief Sets the close callback for the specified window. - * - * This function sets the close callback of the specified window, which is - * called when the user attempts to close the window, for example by clicking - * the close widget in the title bar. - * - * The close flag is set before this callback is called, but you can modify it - * at any time with @ref glfwSetWindowShouldClose. - * - * The close callback is not triggered by @ref glfwDestroyWindow. - * - * @param[in] window The window whose callback to set. - * @param[in] cbfun The new callback, or `NULL` to remove the currently set - * callback. - * @return The previously set callback, or `NULL` if no callback was set or the - * library had not been [initialized](@ref intro_init). - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @remark @osx Selecting Quit from the application menu will trigger the close - * callback for all windows. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref window_close - * - * @since Added in version 2.5. - * @glfw3 Added window handle parameter and return value. - * - * @ingroup window - */ -GLFWAPI GLFWwindowclosefun glfwSetWindowCloseCallback(GLFWwindow* window, GLFWwindowclosefun cbfun); - -/*! @brief Sets the refresh callback for the specified window. - * - * This function sets the refresh callback of the specified window, which is - * called when the client area of the window needs to be redrawn, for example - * if the window has been exposed after having been covered by another window. - * - * On compositing window systems such as Aero, Compiz or Aqua, where the window - * contents are saved off-screen, this callback may be called only very - * infrequently or never at all. - * - * @param[in] window The window whose callback to set. - * @param[in] cbfun The new callback, or `NULL` to remove the currently set - * callback. - * @return The previously set callback, or `NULL` if no callback was set or the - * library had not been [initialized](@ref intro_init). - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref window_refresh - * - * @since Added in version 2.5. - * @glfw3 Added window handle parameter and return value. - * - * @ingroup window - */ -GLFWAPI GLFWwindowrefreshfun glfwSetWindowRefreshCallback(GLFWwindow* window, GLFWwindowrefreshfun cbfun); - -/*! @brief Sets the focus callback for the specified window. - * - * This function sets the focus callback of the specified window, which is - * called when the window gains or loses input focus. - * - * After the focus callback is called for a window that lost input focus, - * synthetic key and mouse button release events will be generated for all such - * that had been pressed. For more information, see @ref glfwSetKeyCallback - * and @ref glfwSetMouseButtonCallback. - * - * @param[in] window The window whose callback to set. - * @param[in] cbfun The new callback, or `NULL` to remove the currently set - * callback. - * @return The previously set callback, or `NULL` if no callback was set or the - * library had not been [initialized](@ref intro_init). - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref window_focus - * - * @since Added in version 3.0. - * - * @ingroup window - */ -GLFWAPI GLFWwindowfocusfun glfwSetWindowFocusCallback(GLFWwindow* window, GLFWwindowfocusfun cbfun); - -/*! @brief Sets the iconify callback for the specified window. - * - * This function sets the iconification callback of the specified window, which - * is called when the window is iconified or restored. - * - * @param[in] window The window whose callback to set. - * @param[in] cbfun The new callback, or `NULL` to remove the currently set - * callback. - * @return The previously set callback, or `NULL` if no callback was set or the - * library had not been [initialized](@ref intro_init). - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref window_iconify - * - * @since Added in version 3.0. - * - * @ingroup window - */ -GLFWAPI GLFWwindowiconifyfun glfwSetWindowIconifyCallback(GLFWwindow* window, GLFWwindowiconifyfun cbfun); - -/*! @brief Sets the framebuffer resize callback for the specified window. - * - * This function sets the framebuffer resize callback of the specified window, - * which is called when the framebuffer of the specified window is resized. - * - * @param[in] window The window whose callback to set. - * @param[in] cbfun The new callback, or `NULL` to remove the currently set - * callback. - * @return The previously set callback, or `NULL` if no callback was set or the - * library had not been [initialized](@ref intro_init). - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref window_fbsize - * - * @since Added in version 3.0. - * - * @ingroup window - */ -GLFWAPI GLFWframebuffersizefun glfwSetFramebufferSizeCallback(GLFWwindow* window, GLFWframebuffersizefun cbfun); - -/*! @brief Processes all pending events. - * - * This function processes only those events that are already in the event - * queue and then returns immediately. Processing events will cause the window - * and input callbacks associated with those events to be called. - * - * On some platforms, a window move, resize or menu operation will cause event - * processing to block. This is due to how event processing is designed on - * those platforms. You can use the - * [window refresh callback](@ref window_refresh) to redraw the contents of - * your window when necessary during such operations. - * - * On some platforms, certain events are sent directly to the application - * without going through the event queue, causing callbacks to be called - * outside of a call to one of the event processing functions. - * - * Event processing is not required for joystick input to work. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @reentrancy This function must not be called from a callback. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref events - * @sa glfwWaitEvents - * @sa glfwWaitEventsTimeout - * - * @since Added in version 1.0. - * - * @ingroup window - */ -GLFWAPI void glfwPollEvents(void); - -/*! @brief Waits until events are queued and processes them. - * - * This function puts the calling thread to sleep until at least one event is - * available in the event queue. Once one or more events are available, - * it behaves exactly like @ref glfwPollEvents, i.e. the events in the queue - * are processed and the function then returns immediately. Processing events - * will cause the window and input callbacks associated with those events to be - * called. - * - * Since not all events are associated with callbacks, this function may return - * without a callback having been called even if you are monitoring all - * callbacks. - * - * On some platforms, a window move, resize or menu operation will cause event - * processing to block. This is due to how event processing is designed on - * those platforms. You can use the - * [window refresh callback](@ref window_refresh) to redraw the contents of - * your window when necessary during such operations. - * - * On some platforms, certain callbacks may be called outside of a call to one - * of the event processing functions. - * - * If no windows exist, this function returns immediately. For synchronization - * of threads in applications that do not create windows, use your threading - * library of choice. - * - * Event processing is not required for joystick input to work. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @reentrancy This function must not be called from a callback. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref events - * @sa glfwPollEvents - * @sa glfwWaitEventsTimeout - * - * @since Added in version 2.5. - * - * @ingroup window - */ -GLFWAPI void glfwWaitEvents(void); - -/*! @brief Waits with timeout until events are queued and processes them. - * - * This function puts the calling thread to sleep until at least one event is - * available in the event queue, or until the specified timeout is reached. If - * one or more events are available, it behaves exactly like @ref - * glfwPollEvents, i.e. the events in the queue are processed and the function - * then returns immediately. Processing events will cause the window and input - * callbacks associated with those events to be called. - * - * The timeout value must be a positive finite number. - * - * Since not all events are associated with callbacks, this function may return - * without a callback having been called even if you are monitoring all - * callbacks. - * - * On some platforms, a window move, resize or menu operation will cause event - * processing to block. This is due to how event processing is designed on - * those platforms. You can use the - * [window refresh callback](@ref window_refresh) to redraw the contents of - * your window when necessary during such operations. - * - * On some platforms, certain callbacks may be called outside of a call to one - * of the event processing functions. - * - * If no windows exist, this function returns immediately. For synchronization - * of threads in applications that do not create windows, use your threading - * library of choice. - * - * Event processing is not required for joystick input to work. - * - * @param[in] timeout The maximum amount of time, in seconds, to wait. - * - * @reentrancy This function must not be called from a callback. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref events - * @sa glfwPollEvents - * @sa glfwWaitEvents - * - * @since Added in version 3.2. - * - * @ingroup window - */ -GLFWAPI void glfwWaitEventsTimeout(double timeout); - -/*! @brief Posts an empty event to the event queue. - * - * This function posts an empty event from the current thread to the event - * queue, causing @ref glfwWaitEvents to return. - * - * If no windows exist, this function returns immediately. For synchronization - * of threads in applications that do not create windows, use your threading - * library of choice. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @thread_safety This function may be called from any thread. - * - * @sa @ref events - * @sa glfwWaitEvents - * - * @since Added in version 3.1. - * - * @ingroup window - */ -GLFWAPI void glfwPostEmptyEvent(void); - -/*! @brief Returns the value of an input option for the specified window. - * - * This function returns the value of an input option for the specified window. - * The mode must be one of `GLFW_CURSOR`, `GLFW_STICKY_KEYS` or - * `GLFW_STICKY_MOUSE_BUTTONS`. - * - * @param[in] window The window to query. - * @param[in] mode One of `GLFW_CURSOR`, `GLFW_STICKY_KEYS` or - * `GLFW_STICKY_MOUSE_BUTTONS`. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_INVALID_ENUM. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa glfwSetInputMode - * - * @since Added in version 3.0. - * - * @ingroup input - */ -GLFWAPI int glfwGetInputMode(GLFWwindow* window, int mode); - -/*! @brief Sets an input option for the specified window. - * - * This function sets an input mode option for the specified window. The mode - * must be one of `GLFW_CURSOR`, `GLFW_STICKY_KEYS` or - * `GLFW_STICKY_MOUSE_BUTTONS`. - * - * If the mode is `GLFW_CURSOR`, the value must be one of the following cursor - * modes: - * - `GLFW_CURSOR_NORMAL` makes the cursor visible and behaving normally. - * - `GLFW_CURSOR_HIDDEN` makes the cursor invisible when it is over the client - * area of the window but does not restrict the cursor from leaving. - * - `GLFW_CURSOR_DISABLED` hides and grabs the cursor, providing virtual - * and unlimited cursor movement. This is useful for implementing for - * example 3D camera controls. - * - * If the mode is `GLFW_STICKY_KEYS`, the value must be either `GLFW_TRUE` to - * enable sticky keys, or `GLFW_FALSE` to disable it. If sticky keys are - * enabled, a key press will ensure that @ref glfwGetKey returns `GLFW_PRESS` - * the next time it is called even if the key had been released before the - * call. This is useful when you are only interested in whether keys have been - * pressed but not when or in which order. - * - * If the mode is `GLFW_STICKY_MOUSE_BUTTONS`, the value must be either - * `GLFW_TRUE` to enable sticky mouse buttons, or `GLFW_FALSE` to disable it. - * If sticky mouse buttons are enabled, a mouse button press will ensure that - * @ref glfwGetMouseButton returns `GLFW_PRESS` the next time it is called even - * if the mouse button had been released before the call. This is useful when - * you are only interested in whether mouse buttons have been pressed but not - * when or in which order. - * - * @param[in] window The window whose input mode to set. - * @param[in] mode One of `GLFW_CURSOR`, `GLFW_STICKY_KEYS` or - * `GLFW_STICKY_MOUSE_BUTTONS`. - * @param[in] value The new value of the specified input mode. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED, @ref - * GLFW_INVALID_ENUM and @ref GLFW_PLATFORM_ERROR. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa glfwGetInputMode - * - * @since Added in version 3.0. Replaces `glfwEnable` and `glfwDisable`. - * - * @ingroup input - */ -GLFWAPI void glfwSetInputMode(GLFWwindow* window, int mode, int value); - -/*! @brief Returns the localized name of the specified printable key. - * - * This function returns the localized name of the specified printable key. - * This is intended for displaying key bindings to the user. - * - * If the key is `GLFW_KEY_UNKNOWN`, the scancode is used instead, otherwise - * the scancode is ignored. If a non-printable key or (if the key is - * `GLFW_KEY_UNKNOWN`) a scancode that maps to a non-printable key is - * specified, this function returns `NULL`. - * - * This behavior allows you to pass in the arguments passed to the - * [key callback](@ref input_key) without modification. - * - * The printable keys are: - * - `GLFW_KEY_APOSTROPHE` - * - `GLFW_KEY_COMMA` - * - `GLFW_KEY_MINUS` - * - `GLFW_KEY_PERIOD` - * - `GLFW_KEY_SLASH` - * - `GLFW_KEY_SEMICOLON` - * - `GLFW_KEY_EQUAL` - * - `GLFW_KEY_LEFT_BRACKET` - * - `GLFW_KEY_RIGHT_BRACKET` - * - `GLFW_KEY_BACKSLASH` - * - `GLFW_KEY_WORLD_1` - * - `GLFW_KEY_WORLD_2` - * - `GLFW_KEY_0` to `GLFW_KEY_9` - * - `GLFW_KEY_A` to `GLFW_KEY_Z` - * - `GLFW_KEY_KP_0` to `GLFW_KEY_KP_9` - * - `GLFW_KEY_KP_DECIMAL` - * - `GLFW_KEY_KP_DIVIDE` - * - `GLFW_KEY_KP_MULTIPLY` - * - `GLFW_KEY_KP_SUBTRACT` - * - `GLFW_KEY_KP_ADD` - * - `GLFW_KEY_KP_EQUAL` - * - * @param[in] key The key to query, or `GLFW_KEY_UNKNOWN`. - * @param[in] scancode The scancode of the key to query. - * @return The localized name of the key, or `NULL`. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @pointer_lifetime The returned string is allocated and freed by GLFW. You - * should not free it yourself. It is valid until the next call to @ref - * glfwGetKeyName, or until the library is terminated. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref input_key_name - * - * @since Added in version 3.2. - * - * @ingroup input - */ -GLFWAPI const char* glfwGetKeyName(int key, int scancode); - -/*! @brief Returns the last reported state of a keyboard key for the specified - * window. - * - * This function returns the last state reported for the specified key to the - * specified window. The returned state is one of `GLFW_PRESS` or - * `GLFW_RELEASE`. The higher-level action `GLFW_REPEAT` is only reported to - * the key callback. - * - * If the `GLFW_STICKY_KEYS` input mode is enabled, this function returns - * `GLFW_PRESS` the first time you call it for a key that was pressed, even if - * that key has already been released. - * - * The key functions deal with physical keys, with [key tokens](@ref keys) - * named after their use on the standard US keyboard layout. If you want to - * input text, use the Unicode character callback instead. - * - * The [modifier key bit masks](@ref mods) are not key tokens and cannot be - * used with this function. - * - * __Do not use this function__ to implement [text input](@ref input_char). - * - * @param[in] window The desired window. - * @param[in] key The desired [keyboard key](@ref keys). `GLFW_KEY_UNKNOWN` is - * not a valid key for this function. - * @return One of `GLFW_PRESS` or `GLFW_RELEASE`. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_INVALID_ENUM. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref input_key - * - * @since Added in version 1.0. - * @glfw3 Added window handle parameter. - * - * @ingroup input - */ -GLFWAPI int glfwGetKey(GLFWwindow* window, int key); - -/*! @brief Returns the last reported state of a mouse button for the specified - * window. - * - * This function returns the last state reported for the specified mouse button - * to the specified window. The returned state is one of `GLFW_PRESS` or - * `GLFW_RELEASE`. - * - * If the `GLFW_STICKY_MOUSE_BUTTONS` input mode is enabled, this function - * `GLFW_PRESS` the first time you call it for a mouse button that was pressed, - * even if that mouse button has already been released. - * - * @param[in] window The desired window. - * @param[in] button The desired [mouse button](@ref buttons). - * @return One of `GLFW_PRESS` or `GLFW_RELEASE`. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_INVALID_ENUM. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref input_mouse_button - * - * @since Added in version 1.0. - * @glfw3 Added window handle parameter. - * - * @ingroup input - */ -GLFWAPI int glfwGetMouseButton(GLFWwindow* window, int button); - -/*! @brief Retrieves the position of the cursor relative to the client area of - * the window. - * - * This function returns the position of the cursor, in screen coordinates, - * relative to the upper-left corner of the client area of the specified - * window. - * - * If the cursor is disabled (with `GLFW_CURSOR_DISABLED`) then the cursor - * position is unbounded and limited only by the minimum and maximum values of - * a `double`. - * - * The coordinate can be converted to their integer equivalents with the - * `floor` function. Casting directly to an integer type works for positive - * coordinates, but fails for negative ones. - * - * Any or all of the position arguments may be `NULL`. If an error occurs, all - * non-`NULL` position arguments will be set to zero. - * - * @param[in] window The desired window. - * @param[out] xpos Where to store the cursor x-coordinate, relative to the - * left edge of the client area, or `NULL`. - * @param[out] ypos Where to store the cursor y-coordinate, relative to the to - * top edge of the client area, or `NULL`. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref cursor_pos - * @sa glfwSetCursorPos - * - * @since Added in version 3.0. Replaces `glfwGetMousePos`. - * - * @ingroup input - */ -GLFWAPI void glfwGetCursorPos(GLFWwindow* window, double* xpos, double* ypos); - -/*! @brief Sets the position of the cursor, relative to the client area of the - * window. - * - * This function sets the position, in screen coordinates, of the cursor - * relative to the upper-left corner of the client area of the specified - * window. The window must have input focus. If the window does not have - * input focus when this function is called, it fails silently. - * - * __Do not use this function__ to implement things like camera controls. GLFW - * already provides the `GLFW_CURSOR_DISABLED` cursor mode that hides the - * cursor, transparently re-centers it and provides unconstrained cursor - * motion. See @ref glfwSetInputMode for more information. - * - * If the cursor mode is `GLFW_CURSOR_DISABLED` then the cursor position is - * unconstrained and limited only by the minimum and maximum values of - * a `double`. - * - * @param[in] window The desired window. - * @param[in] xpos The desired x-coordinate, relative to the left edge of the - * client area. - * @param[in] ypos The desired y-coordinate, relative to the top edge of the - * client area. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @remark @x11 Due to the asynchronous nature of X11, it may take a moment for - * the window focus event to arrive. This means you may not be able to set the - * cursor position directly after window creation. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref cursor_pos - * @sa glfwGetCursorPos - * - * @since Added in version 3.0. Replaces `glfwSetMousePos`. - * - * @ingroup input - */ -GLFWAPI void glfwSetCursorPos(GLFWwindow* window, double xpos, double ypos); - -/*! @brief Creates a custom cursor. - * - * Creates a new custom cursor image that can be set for a window with @ref - * glfwSetCursor. The cursor can be destroyed with @ref glfwDestroyCursor. - * Any remaining cursors are destroyed by @ref glfwTerminate. - * - * The pixels are 32-bit, little-endian, non-premultiplied RGBA, i.e. eight - * bits per channel. They are arranged canonically as packed sequential rows, - * starting from the top-left corner. - * - * The cursor hotspot is specified in pixels, relative to the upper-left corner - * of the cursor image. Like all other coordinate systems in GLFW, the X-axis - * points to the right and the Y-axis points down. - * - * @param[in] image The desired cursor image. - * @param[in] xhot The desired x-coordinate, in pixels, of the cursor hotspot. - * @param[in] yhot The desired y-coordinate, in pixels, of the cursor hotspot. - * @return The handle of the created cursor, or `NULL` if an - * [error](@ref error_handling) occurred. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @pointer_lifetime The specified image data is copied before this function - * returns. - * - * @reentrancy This function must not be called from a callback. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref cursor_object - * @sa glfwDestroyCursor - * @sa glfwCreateStandardCursor - * - * @since Added in version 3.1. - * - * @ingroup input - */ -GLFWAPI GLFWcursor* glfwCreateCursor(const GLFWimage* image, int xhot, int yhot); - -/*! @brief Creates a cursor with a standard shape. - * - * Returns a cursor with a [standard shape](@ref shapes), that can be set for - * a window with @ref glfwSetCursor. - * - * @param[in] shape One of the [standard shapes](@ref shapes). - * @return A new cursor ready to use or `NULL` if an - * [error](@ref error_handling) occurred. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED, @ref - * GLFW_INVALID_ENUM and @ref GLFW_PLATFORM_ERROR. - * - * @reentrancy This function must not be called from a callback. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref cursor_object - * @sa glfwCreateCursor - * - * @since Added in version 3.1. - * - * @ingroup input - */ -GLFWAPI GLFWcursor* glfwCreateStandardCursor(int shape); - -/*! @brief Destroys a cursor. - * - * This function destroys a cursor previously created with @ref - * glfwCreateCursor. Any remaining cursors will be destroyed by @ref - * glfwTerminate. - * - * @param[in] cursor The cursor object to destroy. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @reentrancy This function must not be called from a callback. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref cursor_object - * @sa glfwCreateCursor - * - * @since Added in version 3.1. - * - * @ingroup input - */ -GLFWAPI void glfwDestroyCursor(GLFWcursor* cursor); - -/*! @brief Sets the cursor for the window. - * - * This function sets the cursor image to be used when the cursor is over the - * client area of the specified window. The set cursor will only be visible - * when the [cursor mode](@ref cursor_mode) of the window is - * `GLFW_CURSOR_NORMAL`. - * - * On some platforms, the set cursor may not be visible unless the window also - * has input focus. - * - * @param[in] window The window to set the cursor for. - * @param[in] cursor The cursor to set, or `NULL` to switch back to the default - * arrow cursor. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref cursor_object - * - * @since Added in version 3.1. - * - * @ingroup input - */ -GLFWAPI void glfwSetCursor(GLFWwindow* window, GLFWcursor* cursor); - -/*! @brief Sets the key callback. - * - * This function sets the key callback of the specified window, which is called - * when a key is pressed, repeated or released. - * - * The key functions deal with physical keys, with layout independent - * [key tokens](@ref keys) named after their values in the standard US keyboard - * layout. If you want to input text, use the - * [character callback](@ref glfwSetCharCallback) instead. - * - * When a window loses input focus, it will generate synthetic key release - * events for all pressed keys. You can tell these events from user-generated - * events by the fact that the synthetic ones are generated after the focus - * loss event has been processed, i.e. after the - * [window focus callback](@ref glfwSetWindowFocusCallback) has been called. - * - * The scancode of a key is specific to that platform or sometimes even to that - * machine. Scancodes are intended to allow users to bind keys that don't have - * a GLFW key token. Such keys have `key` set to `GLFW_KEY_UNKNOWN`, their - * state is not saved and so it cannot be queried with @ref glfwGetKey. - * - * Sometimes GLFW needs to generate synthetic key events, in which case the - * scancode may be zero. - * - * @param[in] window The window whose callback to set. - * @param[in] cbfun The new key callback, or `NULL` to remove the currently - * set callback. - * @return The previously set callback, or `NULL` if no callback was set or the - * library had not been [initialized](@ref intro_init). - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref input_key - * - * @since Added in version 1.0. - * @glfw3 Added window handle parameter and return value. - * - * @ingroup input - */ -GLFWAPI GLFWkeyfun glfwSetKeyCallback(GLFWwindow* window, GLFWkeyfun cbfun); - -/*! @brief Sets the Unicode character callback. - * - * This function sets the character callback of the specified window, which is - * called when a Unicode character is input. - * - * The character callback is intended for Unicode text input. As it deals with - * characters, it is keyboard layout dependent, whereas the - * [key callback](@ref glfwSetKeyCallback) is not. Characters do not map 1:1 - * to physical keys, as a key may produce zero, one or more characters. If you - * want to know whether a specific physical key was pressed or released, see - * the key callback instead. - * - * The character callback behaves as system text input normally does and will - * not be called if modifier keys are held down that would prevent normal text - * input on that platform, for example a Super (Command) key on OS X or Alt key - * on Windows. There is a - * [character with modifiers callback](@ref glfwSetCharModsCallback) that - * receives these events. - * - * @param[in] window The window whose callback to set. - * @param[in] cbfun The new callback, or `NULL` to remove the currently set - * callback. - * @return The previously set callback, or `NULL` if no callback was set or the - * library had not been [initialized](@ref intro_init). - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref input_char - * - * @since Added in version 2.4. - * @glfw3 Added window handle parameter and return value. - * - * @ingroup input - */ -GLFWAPI GLFWcharfun glfwSetCharCallback(GLFWwindow* window, GLFWcharfun cbfun); - -/*! @brief Sets the Unicode character with modifiers callback. - * - * This function sets the character with modifiers callback of the specified - * window, which is called when a Unicode character is input regardless of what - * modifier keys are used. - * - * The character with modifiers callback is intended for implementing custom - * Unicode character input. For regular Unicode text input, see the - * [character callback](@ref glfwSetCharCallback). Like the character - * callback, the character with modifiers callback deals with characters and is - * keyboard layout dependent. Characters do not map 1:1 to physical keys, as - * a key may produce zero, one or more characters. If you want to know whether - * a specific physical key was pressed or released, see the - * [key callback](@ref glfwSetKeyCallback) instead. - * - * @param[in] window The window whose callback to set. - * @param[in] cbfun The new callback, or `NULL` to remove the currently set - * callback. - * @return The previously set callback, or `NULL` if no callback was set or an - * error occurred. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref input_char - * - * @since Added in version 3.1. - * - * @ingroup input - */ -GLFWAPI GLFWcharmodsfun glfwSetCharModsCallback(GLFWwindow* window, GLFWcharmodsfun cbfun); - -/*! @brief Sets the mouse button callback. - * - * This function sets the mouse button callback of the specified window, which - * is called when a mouse button is pressed or released. - * - * When a window loses input focus, it will generate synthetic mouse button - * release events for all pressed mouse buttons. You can tell these events - * from user-generated events by the fact that the synthetic ones are generated - * after the focus loss event has been processed, i.e. after the - * [window focus callback](@ref glfwSetWindowFocusCallback) has been called. - * - * @param[in] window The window whose callback to set. - * @param[in] cbfun The new callback, or `NULL` to remove the currently set - * callback. - * @return The previously set callback, or `NULL` if no callback was set or the - * library had not been [initialized](@ref intro_init). - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref input_mouse_button - * - * @since Added in version 1.0. - * @glfw3 Added window handle parameter and return value. - * - * @ingroup input - */ -GLFWAPI GLFWmousebuttonfun glfwSetMouseButtonCallback(GLFWwindow* window, GLFWmousebuttonfun cbfun); - -/*! @brief Sets the cursor position callback. - * - * This function sets the cursor position callback of the specified window, - * which is called when the cursor is moved. The callback is provided with the - * position, in screen coordinates, relative to the upper-left corner of the - * client area of the window. - * - * @param[in] window The window whose callback to set. - * @param[in] cbfun The new callback, or `NULL` to remove the currently set - * callback. - * @return The previously set callback, or `NULL` if no callback was set or the - * library had not been [initialized](@ref intro_init). - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref cursor_pos - * - * @since Added in version 3.0. Replaces `glfwSetMousePosCallback`. - * - * @ingroup input - */ -GLFWAPI GLFWcursorposfun glfwSetCursorPosCallback(GLFWwindow* window, GLFWcursorposfun cbfun); - -/*! @brief Sets the cursor enter/exit callback. - * - * This function sets the cursor boundary crossing callback of the specified - * window, which is called when the cursor enters or leaves the client area of - * the window. - * - * @param[in] window The window whose callback to set. - * @param[in] cbfun The new callback, or `NULL` to remove the currently set - * callback. - * @return The previously set callback, or `NULL` if no callback was set or the - * library had not been [initialized](@ref intro_init). - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref cursor_enter - * - * @since Added in version 3.0. - * - * @ingroup input - */ -GLFWAPI GLFWcursorenterfun glfwSetCursorEnterCallback(GLFWwindow* window, GLFWcursorenterfun cbfun); - -/*! @brief Sets the scroll callback. - * - * This function sets the scroll callback of the specified window, which is - * called when a scrolling device is used, such as a mouse wheel or scrolling - * area of a touchpad. - * - * The scroll callback receives all scrolling input, like that from a mouse - * wheel or a touchpad scrolling area. - * - * @param[in] window The window whose callback to set. - * @param[in] cbfun The new scroll callback, or `NULL` to remove the currently - * set callback. - * @return The previously set callback, or `NULL` if no callback was set or the - * library had not been [initialized](@ref intro_init). - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref scrolling - * - * @since Added in version 3.0. Replaces `glfwSetMouseWheelCallback`. - * - * @ingroup input - */ -GLFWAPI GLFWscrollfun glfwSetScrollCallback(GLFWwindow* window, GLFWscrollfun cbfun); - -/*! @brief Sets the file drop callback. - * - * This function sets the file drop callback of the specified window, which is - * called when one or more dragged files are dropped on the window. - * - * Because the path array and its strings may have been generated specifically - * for that event, they are not guaranteed to be valid after the callback has - * returned. If you wish to use them after the callback returns, you need to - * make a deep copy. - * - * @param[in] window The window whose callback to set. - * @param[in] cbfun The new file drop callback, or `NULL` to remove the - * currently set callback. - * @return The previously set callback, or `NULL` if no callback was set or the - * library had not been [initialized](@ref intro_init). - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref path_drop - * - * @since Added in version 3.1. - * - * @ingroup input - */ -GLFWAPI GLFWdropfun glfwSetDropCallback(GLFWwindow* window, GLFWdropfun cbfun); - -/*! @brief Returns whether the specified joystick is present. - * - * This function returns whether the specified joystick is present. - * - * @param[in] joy The [joystick](@ref joysticks) to query. - * @return `GLFW_TRUE` if the joystick is present, or `GLFW_FALSE` otherwise. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED, @ref - * GLFW_INVALID_ENUM and @ref GLFW_PLATFORM_ERROR. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref joystick - * - * @since Added in version 3.0. Replaces `glfwGetJoystickParam`. - * - * @ingroup input - */ -GLFWAPI int glfwJoystickPresent(int joy); - -/*! @brief Returns the values of all axes of the specified joystick. - * - * This function returns the values of all axes of the specified joystick. - * Each element in the array is a value between -1.0 and 1.0. - * - * Querying a joystick slot with no device present is not an error, but will - * cause this function to return `NULL`. Call @ref glfwJoystickPresent to - * check device presence. - * - * @param[in] joy The [joystick](@ref joysticks) to query. - * @param[out] count Where to store the number of axis values in the returned - * array. This is set to zero if an error occurred. - * @return An array of axis values, or `NULL` if the joystick is not present. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED, @ref - * GLFW_INVALID_ENUM and @ref GLFW_PLATFORM_ERROR. - * - * @pointer_lifetime The returned array is allocated and freed by GLFW. You - * should not free it yourself. It is valid until the specified joystick is - * disconnected, this function is called again for that joystick or the library - * is terminated. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref joystick_axis - * - * @since Added in version 3.0. Replaces `glfwGetJoystickPos`. - * - * @ingroup input - */ -GLFWAPI const float* glfwGetJoystickAxes(int joy, int* count); - -/*! @brief Returns the state of all buttons of the specified joystick. - * - * This function returns the state of all buttons of the specified joystick. - * Each element in the array is either `GLFW_PRESS` or `GLFW_RELEASE`. - * - * Querying a joystick slot with no device present is not an error, but will - * cause this function to return `NULL`. Call @ref glfwJoystickPresent to - * check device presence. - * - * @param[in] joy The [joystick](@ref joysticks) to query. - * @param[out] count Where to store the number of button states in the returned - * array. This is set to zero if an error occurred. - * @return An array of button states, or `NULL` if the joystick is not present. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED, @ref - * GLFW_INVALID_ENUM and @ref GLFW_PLATFORM_ERROR. - * - * @pointer_lifetime The returned array is allocated and freed by GLFW. You - * should not free it yourself. It is valid until the specified joystick is - * disconnected, this function is called again for that joystick or the library - * is terminated. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref joystick_button - * - * @since Added in version 2.2. - * @glfw3 Changed to return a dynamic array. - * - * @ingroup input - */ -GLFWAPI const unsigned char* glfwGetJoystickButtons(int joy, int* count); - -/*! @brief Returns the name of the specified joystick. - * - * This function returns the name, encoded as UTF-8, of the specified joystick. - * The returned string is allocated and freed by GLFW. You should not free it - * yourself. - * - * Querying a joystick slot with no device present is not an error, but will - * cause this function to return `NULL`. Call @ref glfwJoystickPresent to - * check device presence. - * - * @param[in] joy The [joystick](@ref joysticks) to query. - * @return The UTF-8 encoded name of the joystick, or `NULL` if the joystick - * is not present. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED, @ref - * GLFW_INVALID_ENUM and @ref GLFW_PLATFORM_ERROR. - * - * @pointer_lifetime The returned string is allocated and freed by GLFW. You - * should not free it yourself. It is valid until the specified joystick is - * disconnected, this function is called again for that joystick or the library - * is terminated. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref joystick_name - * - * @since Added in version 3.0. - * - * @ingroup input - */ -GLFWAPI const char* glfwGetJoystickName(int joy); - -/*! @brief Sets the joystick configuration callback. - * - * This function sets the joystick configuration callback, or removes the - * currently set callback. This is called when a joystick is connected to or - * disconnected from the system. - * - * @param[in] cbfun The new callback, or `NULL` to remove the currently set - * callback. - * @return The previously set callback, or `NULL` if no callback was set or the - * library had not been [initialized](@ref intro_init). - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref joystick_event - * - * @since Added in version 3.2. - * - * @ingroup input - */ -GLFWAPI GLFWjoystickfun glfwSetJoystickCallback(GLFWjoystickfun cbfun); - -/*! @brief Sets the clipboard to the specified string. - * - * This function sets the system clipboard to the specified, UTF-8 encoded - * string. - * - * @param[in] window The window that will own the clipboard contents. - * @param[in] string A UTF-8 encoded string. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @pointer_lifetime The specified string is copied before this function - * returns. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref clipboard - * @sa glfwGetClipboardString - * - * @since Added in version 3.0. - * - * @ingroup input - */ -GLFWAPI void glfwSetClipboardString(GLFWwindow* window, const char* string); - -/*! @brief Returns the contents of the clipboard as a string. - * - * This function returns the contents of the system clipboard, if it contains - * or is convertible to a UTF-8 encoded string. If the clipboard is empty or - * if its contents cannot be converted, `NULL` is returned and a @ref - * GLFW_FORMAT_UNAVAILABLE error is generated. - * - * @param[in] window The window that will request the clipboard contents. - * @return The contents of the clipboard as a UTF-8 encoded string, or `NULL` - * if an [error](@ref error_handling) occurred. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_PLATFORM_ERROR. - * - * @pointer_lifetime The returned string is allocated and freed by GLFW. You - * should not free it yourself. It is valid until the next call to @ref - * glfwGetClipboardString or @ref glfwSetClipboardString, or until the library - * is terminated. - * - * @thread_safety This function must only be called from the main thread. - * - * @sa @ref clipboard - * @sa glfwSetClipboardString - * - * @since Added in version 3.0. - * - * @ingroup input - */ -GLFWAPI const char* glfwGetClipboardString(GLFWwindow* window); - -/*! @brief Returns the value of the GLFW timer. - * - * This function returns the value of the GLFW timer. Unless the timer has - * been set using @ref glfwSetTime, the timer measures time elapsed since GLFW - * was initialized. - * - * The resolution of the timer is system dependent, but is usually on the order - * of a few micro- or nanoseconds. It uses the highest-resolution monotonic - * time source on each supported platform. - * - * @return The current value, in seconds, or zero if an - * [error](@ref error_handling) occurred. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @thread_safety This function may be called from any thread. Reading of the - * internal timer offset is not atomic. - * - * @sa @ref time - * - * @since Added in version 1.0. - * - * @ingroup input - */ -GLFWAPI double glfwGetTime(void); - -/*! @brief Sets the GLFW timer. - * - * This function sets the value of the GLFW timer. It then continues to count - * up from that value. The value must be a positive finite number less than - * or equal to 18446744073.0, which is approximately 584.5 years. - * - * @param[in] time The new value, in seconds. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_INVALID_VALUE. - * - * @remark The upper limit of the timer is calculated as - * floor((264 - 1) / 109) and is due to implementations - * storing nanoseconds in 64 bits. The limit may be increased in the future. - * - * @thread_safety This function may be called from any thread. Writing of the - * internal timer offset is not atomic. - * - * @sa @ref time - * - * @since Added in version 2.2. - * - * @ingroup input - */ -GLFWAPI void glfwSetTime(double time); - -/*! @brief Returns the current value of the raw timer. - * - * This function returns the current value of the raw timer, measured in - * 1 / frequency seconds. To get the frequency, call @ref - * glfwGetTimerFrequency. - * - * @return The value of the timer, or zero if an - * [error](@ref error_handling) occurred. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @thread_safety This function may be called from any thread. - * - * @sa @ref time - * @sa glfwGetTimerFrequency - * - * @since Added in version 3.2. - * - * @ingroup input - */ -GLFWAPI uint64_t glfwGetTimerValue(void); - -/*! @brief Returns the frequency, in Hz, of the raw timer. - * - * This function returns the frequency, in Hz, of the raw timer. - * - * @return The frequency of the timer, in Hz, or zero if an - * [error](@ref error_handling) occurred. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @thread_safety This function may be called from any thread. - * - * @sa @ref time - * @sa glfwGetTimerValue - * - * @since Added in version 3.2. - * - * @ingroup input - */ -GLFWAPI uint64_t glfwGetTimerFrequency(void); - -/*! @brief Makes the context of the specified window current for the calling - * thread. - * - * This function makes the OpenGL or OpenGL ES context of the specified window - * current on the calling thread. A context can only be made current on - * a single thread at a time and each thread can have only a single current - * context at a time. - * - * By default, making a context non-current implicitly forces a pipeline flush. - * On machines that support `GL_KHR_context_flush_control`, you can control - * whether a context performs this flush by setting the - * [GLFW_CONTEXT_RELEASE_BEHAVIOR](@ref window_hints_ctx) window hint. - * - * The specified window must have an OpenGL or OpenGL ES context. Specifying - * a window without a context will generate a @ref GLFW_NO_WINDOW_CONTEXT - * error. - * - * @param[in] window The window whose context to make current, or `NULL` to - * detach the current context. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED, @ref - * GLFW_NO_WINDOW_CONTEXT and @ref GLFW_PLATFORM_ERROR. - * - * @thread_safety This function may be called from any thread. - * - * @sa @ref context_current - * @sa glfwGetCurrentContext - * - * @since Added in version 3.0. - * - * @ingroup context - */ -GLFWAPI void glfwMakeContextCurrent(GLFWwindow* window); - -/*! @brief Returns the window whose context is current on the calling thread. - * - * This function returns the window whose OpenGL or OpenGL ES context is - * current on the calling thread. - * - * @return The window whose context is current, or `NULL` if no window's - * context is current. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @thread_safety This function may be called from any thread. - * - * @sa @ref context_current - * @sa glfwMakeContextCurrent - * - * @since Added in version 3.0. - * - * @ingroup context - */ -GLFWAPI GLFWwindow* glfwGetCurrentContext(void); - -/*! @brief Swaps the front and back buffers of the specified window. - * - * This function swaps the front and back buffers of the specified window when - * rendering with OpenGL or OpenGL ES. If the swap interval is greater than - * zero, the GPU driver waits the specified number of screen updates before - * swapping the buffers. - * - * The specified window must have an OpenGL or OpenGL ES context. Specifying - * a window without a context will generate a @ref GLFW_NO_WINDOW_CONTEXT - * error. - * - * This function does not apply to Vulkan. If you are rendering with Vulkan, - * see `vkQueuePresentKHR` instead. - * - * @param[in] window The window whose buffers to swap. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED, @ref - * GLFW_NO_WINDOW_CONTEXT and @ref GLFW_PLATFORM_ERROR. - * - * @remark __EGL:__ The context of the specified window must be current on the - * calling thread. - * - * @thread_safety This function may be called from any thread. - * - * @sa @ref buffer_swap - * @sa glfwSwapInterval - * - * @since Added in version 1.0. - * @glfw3 Added window handle parameter. - * - * @ingroup window - */ -GLFWAPI void glfwSwapBuffers(GLFWwindow* window); - -/*! @brief Sets the swap interval for the current context. - * - * This function sets the swap interval for the current OpenGL or OpenGL ES - * context, i.e. the number of screen updates to wait from the time @ref - * glfwSwapBuffers was called before swapping the buffers and returning. This - * is sometimes called _vertical synchronization_, _vertical retrace - * synchronization_ or just _vsync_. - * - * Contexts that support either of the `WGL_EXT_swap_control_tear` and - * `GLX_EXT_swap_control_tear` extensions also accept negative swap intervals, - * which allow the driver to swap even if a frame arrives a little bit late. - * You can check for the presence of these extensions using @ref - * glfwExtensionSupported. For more information about swap tearing, see the - * extension specifications. - * - * A context must be current on the calling thread. Calling this function - * without a current context will cause a @ref GLFW_NO_CURRENT_CONTEXT error. - * - * This function does not apply to Vulkan. If you are rendering with Vulkan, - * see the present mode of your swapchain instead. - * - * @param[in] interval The minimum number of screen updates to wait for - * until the buffers are swapped by @ref glfwSwapBuffers. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED, @ref - * GLFW_NO_CURRENT_CONTEXT and @ref GLFW_PLATFORM_ERROR. - * - * @remark This function is not called during context creation, leaving the - * swap interval set to whatever is the default on that platform. This is done - * because some swap interval extensions used by GLFW do not allow the swap - * interval to be reset to zero once it has been set to a non-zero value. - * - * @remark Some GPU drivers do not honor the requested swap interval, either - * because of a user setting that overrides the application's request or due to - * bugs in the driver. - * - * @thread_safety This function may be called from any thread. - * - * @sa @ref buffer_swap - * @sa glfwSwapBuffers - * - * @since Added in version 1.0. - * - * @ingroup context - */ -GLFWAPI void glfwSwapInterval(int interval); - -/*! @brief Returns whether the specified extension is available. - * - * This function returns whether the specified - * [API extension](@ref context_glext) is supported by the current OpenGL or - * OpenGL ES context. It searches both for client API extension and context - * creation API extensions. - * - * A context must be current on the calling thread. Calling this function - * without a current context will cause a @ref GLFW_NO_CURRENT_CONTEXT error. - * - * As this functions retrieves and searches one or more extension strings each - * call, it is recommended that you cache its results if it is going to be used - * frequently. The extension strings will not change during the lifetime of - * a context, so there is no danger in doing this. - * - * This function does not apply to Vulkan. If you are using Vulkan, see @ref - * glfwGetRequiredInstanceExtensions, `vkEnumerateInstanceExtensionProperties` - * and `vkEnumerateDeviceExtensionProperties` instead. - * - * @param[in] extension The ASCII encoded name of the extension. - * @return `GLFW_TRUE` if the extension is available, or `GLFW_FALSE` - * otherwise. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED, @ref - * GLFW_NO_CURRENT_CONTEXT, @ref GLFW_INVALID_VALUE and @ref - * GLFW_PLATFORM_ERROR. - * - * @thread_safety This function may be called from any thread. - * - * @sa @ref context_glext - * @sa glfwGetProcAddress - * - * @since Added in version 1.0. - * - * @ingroup context - */ -GLFWAPI int glfwExtensionSupported(const char* extension); - -/*! @brief Returns the address of the specified function for the current - * context. - * - * This function returns the address of the specified OpenGL or OpenGL ES - * [core or extension function](@ref context_glext), if it is supported - * by the current context. - * - * A context must be current on the calling thread. Calling this function - * without a current context will cause a @ref GLFW_NO_CURRENT_CONTEXT error. - * - * This function does not apply to Vulkan. If you are rendering with Vulkan, - * see @ref glfwGetInstanceProcAddress, `vkGetInstanceProcAddr` and - * `vkGetDeviceProcAddr` instead. - * - * @param[in] procname The ASCII encoded name of the function. - * @return The address of the function, or `NULL` if an - * [error](@ref error_handling) occurred. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED, @ref - * GLFW_NO_CURRENT_CONTEXT and @ref GLFW_PLATFORM_ERROR. - * - * @remark The address of a given function is not guaranteed to be the same - * between contexts. - * - * @remark This function may return a non-`NULL` address despite the - * associated version or extension not being available. Always check the - * context version or extension string first. - * - * @pointer_lifetime The returned function pointer is valid until the context - * is destroyed or the library is terminated. - * - * @thread_safety This function may be called from any thread. - * - * @sa @ref context_glext - * @sa glfwExtensionSupported - * - * @since Added in version 1.0. - * - * @ingroup context - */ -GLFWAPI GLFWglproc glfwGetProcAddress(const char* procname); - -/*! @brief Returns whether the Vulkan loader has been found. - * - * This function returns whether the Vulkan loader has been found. This check - * is performed by @ref glfwInit. - * - * The availability of a Vulkan loader does not by itself guarantee that window - * surface creation or even device creation is possible. Call @ref - * glfwGetRequiredInstanceExtensions to check whether the extensions necessary - * for Vulkan surface creation are available and @ref - * glfwGetPhysicalDevicePresentationSupport to check whether a queue family of - * a physical device supports image presentation. - * - * @return `GLFW_TRUE` if Vulkan is available, or `GLFW_FALSE` otherwise. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED. - * - * @thread_safety This function may be called from any thread. - * - * @sa @ref vulkan_support - * - * @since Added in version 3.2. - * - * @ingroup vulkan - */ -GLFWAPI int glfwVulkanSupported(void); - -/*! @brief Returns the Vulkan instance extensions required by GLFW. - * - * This function returns an array of names of Vulkan instance extensions required - * by GLFW for creating Vulkan surfaces for GLFW windows. If successful, the - * list will always contains `VK_KHR_surface`, so if you don't require any - * additional extensions you can pass this list directly to the - * `VkInstanceCreateInfo` struct. - * - * If Vulkan is not available on the machine, this function returns `NULL` and - * generates a @ref GLFW_API_UNAVAILABLE error. Call @ref glfwVulkanSupported - * to check whether Vulkan is available. - * - * If Vulkan is available but no set of extensions allowing window surface - * creation was found, this function returns `NULL`. You may still use Vulkan - * for off-screen rendering and compute work. - * - * @param[out] count Where to store the number of extensions in the returned - * array. This is set to zero if an error occurred. - * @return An array of ASCII encoded extension names, or `NULL` if an - * [error](@ref error_handling) occurred. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_API_UNAVAILABLE. - * - * @remarks Additional extensions may be required by future versions of GLFW. - * You should check if any extensions you wish to enable are already in the - * returned array, as it is an error to specify an extension more than once in - * the `VkInstanceCreateInfo` struct. - * - * @pointer_lifetime The returned array is allocated and freed by GLFW. You - * should not free it yourself. It is guaranteed to be valid only until the - * library is terminated. - * - * @thread_safety This function may be called from any thread. - * - * @sa @ref vulkan_ext - * @sa glfwCreateWindowSurface - * - * @since Added in version 3.2. - * - * @ingroup vulkan - */ -GLFWAPI const char** glfwGetRequiredInstanceExtensions(uint32_t* count); - -#if defined(VK_VERSION_1_0) - -/*! @brief Returns the address of the specified Vulkan instance function. - * - * This function returns the address of the specified Vulkan core or extension - * function for the specified instance. If instance is set to `NULL` it can - * return any function exported from the Vulkan loader, including at least the - * following functions: - * - * - `vkEnumerateInstanceExtensionProperties` - * - `vkEnumerateInstanceLayerProperties` - * - `vkCreateInstance` - * - `vkGetInstanceProcAddr` - * - * If Vulkan is not available on the machine, this function returns `NULL` and - * generates a @ref GLFW_API_UNAVAILABLE error. Call @ref glfwVulkanSupported - * to check whether Vulkan is available. - * - * This function is equivalent to calling `vkGetInstanceProcAddr` with - * a platform-specific query of the Vulkan loader as a fallback. - * - * @param[in] instance The Vulkan instance to query, or `NULL` to retrieve - * functions related to instance creation. - * @param[in] procname The ASCII encoded name of the function. - * @return The address of the function, or `NULL` if an - * [error](@ref error_handling) occurred. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED and @ref - * GLFW_API_UNAVAILABLE. - * - * @pointer_lifetime The returned function pointer is valid until the library - * is terminated. - * - * @thread_safety This function may be called from any thread. - * - * @sa @ref vulkan_proc - * - * @since Added in version 3.2. - * - * @ingroup vulkan - */ -GLFWAPI GLFWvkproc glfwGetInstanceProcAddress(VkInstance instance, const char* procname); - -/*! @brief Returns whether the specified queue family can present images. - * - * This function returns whether the specified queue family of the specified - * physical device supports presentation to the platform GLFW was built for. - * - * If Vulkan or the required window surface creation instance extensions are - * not available on the machine, or if the specified instance was not created - * with the required extensions, this function returns `GLFW_FALSE` and - * generates a @ref GLFW_API_UNAVAILABLE error. Call @ref glfwVulkanSupported - * to check whether Vulkan is available and @ref - * glfwGetRequiredInstanceExtensions to check what instance extensions are - * required. - * - * @param[in] instance The instance that the physical device belongs to. - * @param[in] device The physical device that the queue family belongs to. - * @param[in] queuefamily The index of the queue family to query. - * @return `GLFW_TRUE` if the queue family supports presentation, or - * `GLFW_FALSE` otherwise. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED, @ref - * GLFW_API_UNAVAILABLE and @ref GLFW_PLATFORM_ERROR. - * - * @thread_safety This function may be called from any thread. For - * synchronization details of Vulkan objects, see the Vulkan specification. - * - * @sa @ref vulkan_present - * - * @since Added in version 3.2. - * - * @ingroup vulkan - */ -GLFWAPI int glfwGetPhysicalDevicePresentationSupport(VkInstance instance, VkPhysicalDevice device, uint32_t queuefamily); - -/*! @brief Creates a Vulkan surface for the specified window. - * - * This function creates a Vulkan surface for the specified window. - * - * If the Vulkan loader was not found at initialization, this function returns - * `VK_ERROR_INITIALIZATION_FAILED` and generates a @ref GLFW_API_UNAVAILABLE - * error. Call @ref glfwVulkanSupported to check whether the Vulkan loader was - * found. - * - * If the required window surface creation instance extensions are not - * available or if the specified instance was not created with these extensions - * enabled, this function returns `VK_ERROR_EXTENSION_NOT_PRESENT` and - * generates a @ref GLFW_API_UNAVAILABLE error. Call @ref - * glfwGetRequiredInstanceExtensions to check what instance extensions are - * required. - * - * The window surface must be destroyed before the specified Vulkan instance. - * It is the responsibility of the caller to destroy the window surface. GLFW - * does not destroy it for you. Call `vkDestroySurfaceKHR` to destroy the - * surface. - * - * @param[in] instance The Vulkan instance to create the surface in. - * @param[in] window The window to create the surface for. - * @param[in] allocator The allocator to use, or `NULL` to use the default - * allocator. - * @param[out] surface Where to store the handle of the surface. This is set - * to `VK_NULL_HANDLE` if an error occurred. - * @return `VK_SUCCESS` if successful, or a Vulkan error code if an - * [error](@ref error_handling) occurred. - * - * @errors Possible errors include @ref GLFW_NOT_INITIALIZED, @ref - * GLFW_API_UNAVAILABLE and @ref GLFW_PLATFORM_ERROR. - * - * @remarks If an error occurs before the creation call is made, GLFW returns - * the Vulkan error code most appropriate for the error. Appropriate use of - * @ref glfwVulkanSupported and @ref glfwGetRequiredInstanceExtensions should - * eliminate almost all occurrences of these errors. - * - * @thread_safety This function may be called from any thread. For - * synchronization details of Vulkan objects, see the Vulkan specification. - * - * @sa @ref vulkan_surface - * @sa glfwGetRequiredInstanceExtensions - * - * @since Added in version 3.2. - * - * @ingroup vulkan - */ -GLFWAPI VkResult glfwCreateWindowSurface(VkInstance instance, GLFWwindow* window, const VkAllocationCallbacks* allocator, VkSurfaceKHR* surface); - -#endif /*VK_VERSION_1_0*/ - - -/************************************************************************* - * Global definition cleanup - *************************************************************************/ - -/* ------------------- BEGIN SYSTEM/COMPILER SPECIFIC -------------------- */ - -#ifdef GLFW_WINGDIAPI_DEFINED - #undef WINGDIAPI - #undef GLFW_WINGDIAPI_DEFINED -#endif - -#ifdef GLFW_CALLBACK_DEFINED - #undef CALLBACK - #undef GLFW_CALLBACK_DEFINED -#endif - -/* -------------------- END SYSTEM/COMPILER SPECIFIC --------------------- */ - - -#ifdef __cplusplus -} -#endif - -#endif /* _glfw3_h_ */ - diff --git a/app/jni/src/libultraship/extern/ImGui/examples/libs/glfw/include/GLFW/glfw3native.h b/app/jni/src/libultraship/extern/ImGui/examples/libs/glfw/include/GLFW/glfw3native.h deleted file mode 100644 index 9fa955e..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/libs/glfw/include/GLFW/glfw3native.h +++ /dev/null @@ -1,456 +0,0 @@ -/************************************************************************* - * GLFW 3.2 - www.glfw.org - * A library for OpenGL, window and input - *------------------------------------------------------------------------ - * 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 _glfw3_native_h_ -#define _glfw3_native_h_ - -#ifdef __cplusplus -extern "C" { -#endif - - -/************************************************************************* - * Doxygen documentation - *************************************************************************/ - -/*! @file glfw3native.h - * @brief The header of the native access functions. - * - * This is the header file of the native access functions. See @ref native for - * more information. - */ -/*! @defgroup native Native access - * - * **By using the native access functions you assert that you know what you're - * doing and how to fix problems caused by using them. If you don't, you - * shouldn't be using them.** - * - * Before the inclusion of @ref glfw3native.h, you may define exactly one - * window system API macro and zero or more context creation API macros. - * - * The chosen backends must match those the library was compiled for. Failure - * to do this will cause a link-time error. - * - * The available window API macros are: - * * `GLFW_EXPOSE_NATIVE_WIN32` - * * `GLFW_EXPOSE_NATIVE_COCOA` - * * `GLFW_EXPOSE_NATIVE_X11` - * * `GLFW_EXPOSE_NATIVE_WAYLAND` - * * `GLFW_EXPOSE_NATIVE_MIR` - * - * The available context API macros are: - * * `GLFW_EXPOSE_NATIVE_WGL` - * * `GLFW_EXPOSE_NATIVE_NSGL` - * * `GLFW_EXPOSE_NATIVE_GLX` - * * `GLFW_EXPOSE_NATIVE_EGL` - * - * These macros select which of the native access functions that are declared - * and which platform-specific headers to include. It is then up your (by - * definition platform-specific) code to handle which of these should be - * defined. - */ - - -/************************************************************************* - * System headers and types - *************************************************************************/ - -#if defined(GLFW_EXPOSE_NATIVE_WIN32) - // This is a workaround for the fact that glfw3.h needs to export APIENTRY (for - // example to allow applications to correctly declare a GL_ARB_debug_output - // callback) but windows.h assumes no one will define APIENTRY before it does - #undef APIENTRY - #include -#elif defined(GLFW_EXPOSE_NATIVE_COCOA) - #include - #if defined(__OBJC__) - #import - #else - typedef void* id; - #endif -#elif defined(GLFW_EXPOSE_NATIVE_X11) - #include - #include -#elif defined(GLFW_EXPOSE_NATIVE_WAYLAND) - #include -#elif defined(GLFW_EXPOSE_NATIVE_MIR) - #include -#endif - -#if defined(GLFW_EXPOSE_NATIVE_WGL) - /* WGL is declared by windows.h */ -#endif -#if defined(GLFW_EXPOSE_NATIVE_NSGL) - /* NSGL is declared by Cocoa.h */ -#endif -#if defined(GLFW_EXPOSE_NATIVE_GLX) - #include -#endif -#if defined(GLFW_EXPOSE_NATIVE_EGL) - #include -#endif - - -/************************************************************************* - * Functions - *************************************************************************/ - -#if defined(GLFW_EXPOSE_NATIVE_WIN32) -/*! @brief Returns the adapter device name of the specified monitor. - * - * @return The UTF-8 encoded adapter device name (for example `\\.\DISPLAY1`) - * of the specified monitor, or `NULL` if an [error](@ref error_handling) - * occurred. - * - * @thread_safety This function may be called from any thread. Access is not - * synchronized. - * - * @since Added in version 3.1. - * - * @ingroup native - */ -GLFWAPI const char* glfwGetWin32Adapter(GLFWmonitor* monitor); - -/*! @brief Returns the display device name of the specified monitor. - * - * @return The UTF-8 encoded display device name (for example - * `\\.\DISPLAY1\Monitor0`) of the specified monitor, or `NULL` if an - * [error](@ref error_handling) occurred. - * - * @thread_safety This function may be called from any thread. Access is not - * synchronized. - * - * @since Added in version 3.1. - * - * @ingroup native - */ -GLFWAPI const char* glfwGetWin32Monitor(GLFWmonitor* monitor); - -/*! @brief Returns the `HWND` of the specified window. - * - * @return The `HWND` of the specified window, or `NULL` if an - * [error](@ref error_handling) occurred. - * - * @thread_safety This function may be called from any thread. Access is not - * synchronized. - * - * @since Added in version 3.0. - * - * @ingroup native - */ -GLFWAPI HWND glfwGetWin32Window(GLFWwindow* window); -#endif - -#if defined(GLFW_EXPOSE_NATIVE_WGL) -/*! @brief Returns the `HGLRC` of the specified window. - * - * @return The `HGLRC` of the specified window, or `NULL` if an - * [error](@ref error_handling) occurred. - * - * @thread_safety This function may be called from any thread. Access is not - * synchronized. - * - * @since Added in version 3.0. - * - * @ingroup native - */ -GLFWAPI HGLRC glfwGetWGLContext(GLFWwindow* window); -#endif - -#if defined(GLFW_EXPOSE_NATIVE_COCOA) -/*! @brief Returns the `CGDirectDisplayID` of the specified monitor. - * - * @return The `CGDirectDisplayID` of the specified monitor, or - * `kCGNullDirectDisplay` if an [error](@ref error_handling) occurred. - * - * @thread_safety This function may be called from any thread. Access is not - * synchronized. - * - * @since Added in version 3.1. - * - * @ingroup native - */ -GLFWAPI CGDirectDisplayID glfwGetCocoaMonitor(GLFWmonitor* monitor); - -/*! @brief Returns the `NSWindow` of the specified window. - * - * @return The `NSWindow` of the specified window, or `nil` if an - * [error](@ref error_handling) occurred. - * - * @thread_safety This function may be called from any thread. Access is not - * synchronized. - * - * @since Added in version 3.0. - * - * @ingroup native - */ -GLFWAPI id glfwGetCocoaWindow(GLFWwindow* window); -#endif - -#if defined(GLFW_EXPOSE_NATIVE_NSGL) -/*! @brief Returns the `NSOpenGLContext` of the specified window. - * - * @return The `NSOpenGLContext` of the specified window, or `nil` if an - * [error](@ref error_handling) occurred. - * - * @thread_safety This function may be called from any thread. Access is not - * synchronized. - * - * @since Added in version 3.0. - * - * @ingroup native - */ -GLFWAPI id glfwGetNSGLContext(GLFWwindow* window); -#endif - -#if defined(GLFW_EXPOSE_NATIVE_X11) -/*! @brief Returns the `Display` used by GLFW. - * - * @return The `Display` used by GLFW, or `NULL` if an - * [error](@ref error_handling) occurred. - * - * @thread_safety This function may be called from any thread. Access is not - * synchronized. - * - * @since Added in version 3.0. - * - * @ingroup native - */ -GLFWAPI Display* glfwGetX11Display(void); - -/*! @brief Returns the `RRCrtc` of the specified monitor. - * - * @return The `RRCrtc` of the specified monitor, or `None` if an - * [error](@ref error_handling) occurred. - * - * @thread_safety This function may be called from any thread. Access is not - * synchronized. - * - * @since Added in version 3.1. - * - * @ingroup native - */ -GLFWAPI RRCrtc glfwGetX11Adapter(GLFWmonitor* monitor); - -/*! @brief Returns the `RROutput` of the specified monitor. - * - * @return The `RROutput` of the specified monitor, or `None` if an - * [error](@ref error_handling) occurred. - * - * @thread_safety This function may be called from any thread. Access is not - * synchronized. - * - * @since Added in version 3.1. - * - * @ingroup native - */ -GLFWAPI RROutput glfwGetX11Monitor(GLFWmonitor* monitor); - -/*! @brief Returns the `Window` of the specified window. - * - * @return The `Window` of the specified window, or `None` if an - * [error](@ref error_handling) occurred. - * - * @thread_safety This function may be called from any thread. Access is not - * synchronized. - * - * @since Added in version 3.0. - * - * @ingroup native - */ -GLFWAPI Window glfwGetX11Window(GLFWwindow* window); -#endif - -#if defined(GLFW_EXPOSE_NATIVE_GLX) -/*! @brief Returns the `GLXContext` of the specified window. - * - * @return The `GLXContext` of the specified window, or `NULL` if an - * [error](@ref error_handling) occurred. - * - * @thread_safety This function may be called from any thread. Access is not - * synchronized. - * - * @since Added in version 3.0. - * - * @ingroup native - */ -GLFWAPI GLXContext glfwGetGLXContext(GLFWwindow* window); - -/*! @brief Returns the `GLXWindow` of the specified window. - * - * @return The `GLXWindow` of the specified window, or `None` if an - * [error](@ref error_handling) occurred. - * - * @thread_safety This function may be called from any thread. Access is not - * synchronized. - * - * @since Added in version 3.2. - * - * @ingroup native - */ -GLFWAPI GLXWindow glfwGetGLXWindow(GLFWwindow* window); -#endif - -#if defined(GLFW_EXPOSE_NATIVE_WAYLAND) -/*! @brief Returns the `struct wl_display*` used by GLFW. - * - * @return The `struct wl_display*` used by GLFW, or `NULL` if an - * [error](@ref error_handling) occurred. - * - * @thread_safety This function may be called from any thread. Access is not - * synchronized. - * - * @since Added in version 3.2. - * - * @ingroup native - */ -GLFWAPI struct wl_display* glfwGetWaylandDisplay(void); - -/*! @brief Returns the `struct wl_output*` of the specified monitor. - * - * @return The `struct wl_output*` of the specified monitor, or `NULL` if an - * [error](@ref error_handling) occurred. - * - * @thread_safety This function may be called from any thread. Access is not - * synchronized. - * - * @since Added in version 3.2. - * - * @ingroup native - */ -GLFWAPI struct wl_output* glfwGetWaylandMonitor(GLFWmonitor* monitor); - -/*! @brief Returns the main `struct wl_surface*` of the specified window. - * - * @return The main `struct wl_surface*` of the specified window, or `NULL` if - * an [error](@ref error_handling) occurred. - * - * @thread_safety This function may be called from any thread. Access is not - * synchronized. - * - * @since Added in version 3.2. - * - * @ingroup native - */ -GLFWAPI struct wl_surface* glfwGetWaylandWindow(GLFWwindow* window); -#endif - -#if defined(GLFW_EXPOSE_NATIVE_MIR) -/*! @brief Returns the `MirConnection*` used by GLFW. - * - * @return The `MirConnection*` used by GLFW, or `NULL` if an - * [error](@ref error_handling) occurred. - * - * @thread_safety This function may be called from any thread. Access is not - * synchronized. - * - * @since Added in version 3.2. - * - * @ingroup native - */ -GLFWAPI MirConnection* glfwGetMirDisplay(void); - -/*! @brief Returns the Mir output ID of the specified monitor. - * - * @return The Mir output ID of the specified monitor, or zero if an - * [error](@ref error_handling) occurred. - * - * @thread_safety This function may be called from any thread. Access is not - * synchronized. - * - * @since Added in version 3.2. - * - * @ingroup native - */ -GLFWAPI int glfwGetMirMonitor(GLFWmonitor* monitor); - -/*! @brief Returns the `MirSurface*` of the specified window. - * - * @return The `MirSurface*` of the specified window, or `NULL` if an - * [error](@ref error_handling) occurred. - * - * @thread_safety This function may be called from any thread. Access is not - * synchronized. - * - * @since Added in version 3.2. - * - * @ingroup native - */ -GLFWAPI MirSurface* glfwGetMirWindow(GLFWwindow* window); -#endif - -#if defined(GLFW_EXPOSE_NATIVE_EGL) -/*! @brief Returns the `EGLDisplay` used by GLFW. - * - * @return The `EGLDisplay` used by GLFW, or `EGL_NO_DISPLAY` if an - * [error](@ref error_handling) occurred. - * - * @thread_safety This function may be called from any thread. Access is not - * synchronized. - * - * @since Added in version 3.0. - * - * @ingroup native - */ -GLFWAPI EGLDisplay glfwGetEGLDisplay(void); - -/*! @brief Returns the `EGLContext` of the specified window. - * - * @return The `EGLContext` of the specified window, or `EGL_NO_CONTEXT` if an - * [error](@ref error_handling) occurred. - * - * @thread_safety This function may be called from any thread. Access is not - * synchronized. - * - * @since Added in version 3.0. - * - * @ingroup native - */ -GLFWAPI EGLContext glfwGetEGLContext(GLFWwindow* window); - -/*! @brief Returns the `EGLSurface` of the specified window. - * - * @return The `EGLSurface` of the specified window, or `EGL_NO_SURFACE` if an - * [error](@ref error_handling) occurred. - * - * @thread_safety This function may be called from any thread. Access is not - * synchronized. - * - * @since Added in version 3.0. - * - * @ingroup native - */ -GLFWAPI EGLSurface glfwGetEGLSurface(GLFWwindow* window); -#endif - -#ifdef __cplusplus -} -#endif - -#endif /* _glfw3_native_h_ */ - diff --git a/app/jni/src/libultraship/extern/ImGui/examples/libs/glfw/lib-vc2010-32/glfw3.lib b/app/jni/src/libultraship/extern/ImGui/examples/libs/glfw/lib-vc2010-32/glfw3.lib deleted file mode 100644 index 348abec..0000000 Binary files a/app/jni/src/libultraship/extern/ImGui/examples/libs/glfw/lib-vc2010-32/glfw3.lib and /dev/null differ diff --git a/app/jni/src/libultraship/extern/ImGui/examples/libs/glfw/lib-vc2010-64/glfw3.lib b/app/jni/src/libultraship/extern/ImGui/examples/libs/glfw/lib-vc2010-64/glfw3.lib deleted file mode 100644 index 768f308..0000000 Binary files a/app/jni/src/libultraship/extern/ImGui/examples/libs/glfw/lib-vc2010-64/glfw3.lib and /dev/null differ diff --git a/app/jni/src/libultraship/extern/ImGui/examples/libs/usynergy/README.txt b/app/jni/src/libultraship/extern/ImGui/examples/libs/usynergy/README.txt deleted file mode 100644 index c86b909..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/libs/usynergy/README.txt +++ /dev/null @@ -1,8 +0,0 @@ - -uSynergy client -- Implementation for the embedded Synergy client library -version 1.0.0, July 7th, 2012 -Copyright (c) 2012 Alex Evans - -This is a copy of the files once found at: - https://github.com/symless/synergy-core/tree/790d108a56ada9caad8e56ff777d444485a69da9/src/micro - diff --git a/app/jni/src/libultraship/extern/ImGui/examples/libs/usynergy/uSynergy.c b/app/jni/src/libultraship/extern/ImGui/examples/libs/usynergy/uSynergy.c deleted file mode 100644 index 8dce47b..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/libs/usynergy/uSynergy.c +++ /dev/null @@ -1,636 +0,0 @@ -/* -uSynergy client -- Implementation for the embedded Synergy client library - version 1.0.0, July 7th, 2012 - -Copyright (c) 2012 Alex Evans - -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 "uSynergy.h" -#include -#include - - - -//--------------------------------------------------------------------------------------------------------------------- -// Internal helpers -//--------------------------------------------------------------------------------------------------------------------- - - - -/** -@brief Read 16 bit integer in network byte order and convert to native byte order -**/ -static int16_t sNetToNative16(const unsigned char *value) -{ -#ifdef USYNERGY_LITTLE_ENDIAN - return value[1] | (value[0] << 8); -#else - return value[0] | (value[1] << 8); -#endif -} - - - -/** -@brief Read 32 bit integer in network byte order and convert to native byte order -**/ -static int32_t sNetToNative32(const unsigned char *value) -{ -#ifdef USYNERGY_LITTLE_ENDIAN - return value[3] | (value[2] << 8) | (value[1] << 16) | (value[0] << 24); -#else - return value[0] | (value[1] << 8) | (value[2] << 16) | (value[3] << 24); -#endif -} - - - -/** -@brief Trace text to client -**/ -static void sTrace(uSynergyContext *context, const char* text) -{ - // Don't trace if we don't have a trace function - if (context->m_traceFunc != 0L) - context->m_traceFunc(context->m_cookie, text); -} - - - -/** -@brief Add string to reply packet -**/ -static void sAddString(uSynergyContext *context, const char *string) -{ - size_t len = strlen(string); - memcpy(context->m_replyCur, string, len); - context->m_replyCur += len; -} - - - -/** -@brief Add uint8 to reply packet -**/ -static void sAddUInt8(uSynergyContext *context, uint8_t value) -{ - *context->m_replyCur++ = value; -} - - - -/** -@brief Add uint16 to reply packet -**/ -static void sAddUInt16(uSynergyContext *context, uint16_t value) -{ - uint8_t *reply = context->m_replyCur; - *reply++ = (uint8_t)(value >> 8); - *reply++ = (uint8_t)value; - context->m_replyCur = reply; -} - - - -/** -@brief Add uint32 to reply packet -**/ -static void sAddUInt32(uSynergyContext *context, uint32_t value) -{ - uint8_t *reply = context->m_replyCur; - *reply++ = (uint8_t)(value >> 24); - *reply++ = (uint8_t)(value >> 16); - *reply++ = (uint8_t)(value >> 8); - *reply++ = (uint8_t)value; - context->m_replyCur = reply; -} - - - -/** -@brief Send reply packet -**/ -static uSynergyBool sSendReply(uSynergyContext *context) -{ - // Set header size - uint8_t *reply_buf = context->m_replyBuffer; - uint32_t reply_len = (uint32_t)(context->m_replyCur - reply_buf); /* Total size of reply */ - uint32_t body_len = reply_len - 4; /* Size of body */ - uSynergyBool ret; - reply_buf[0] = (uint8_t)(body_len >> 24); - reply_buf[1] = (uint8_t)(body_len >> 16); - reply_buf[2] = (uint8_t)(body_len >> 8); - reply_buf[3] = (uint8_t)body_len; - - // Send reply - ret = context->m_sendFunc(context->m_cookie, context->m_replyBuffer, reply_len); - - // Reset reply buffer write pointer - context->m_replyCur = context->m_replyBuffer+4; - return ret; -} - - - -/** -@brief Call mouse callback after a mouse event -**/ -static void sSendMouseCallback(uSynergyContext *context) -{ - // Skip if no callback is installed - if (context->m_mouseCallback == 0L) - return; - - // Send callback - context->m_mouseCallback(context->m_cookie, context->m_mouseX, context->m_mouseY, context->m_mouseWheelX, - context->m_mouseWheelY, context->m_mouseButtonLeft, context->m_mouseButtonRight, context->m_mouseButtonMiddle); -} - - - -/** -@brief Send keyboard callback when a key has been pressed or released -**/ -static void sSendKeyboardCallback(uSynergyContext *context, uint16_t key, uint16_t modifiers, uSynergyBool down, uSynergyBool repeat) -{ - // Skip if no callback is installed - if (context->m_keyboardCallback == 0L) - return; - - // Send callback - context->m_keyboardCallback(context->m_cookie, key, modifiers, down, repeat); -} - - - -/** -@brief Send joystick callback -**/ -static void sSendJoystickCallback(uSynergyContext *context, uint8_t joyNum) -{ - int8_t *sticks; - - // Skip if no callback is installed - if (context->m_joystickCallback == 0L) - return; - - // Send callback - sticks = context->m_joystickSticks[joyNum]; - context->m_joystickCallback(context->m_cookie, joyNum, context->m_joystickButtons[joyNum], sticks[0], sticks[1], sticks[2], sticks[3]); -} - - - -/** -@brief Parse a single client message, update state, send callbacks and send replies -**/ -#define USYNERGY_IS_PACKET(pkt_id) memcmp(message+4, pkt_id, 4)==0 -static void sProcessMessage(uSynergyContext *context, const uint8_t *message) -{ - // We have a packet! - if (memcmp(message+4, "Synergy", 7)==0) - { - // Welcome message - // kMsgHello = "Synergy%2i%2i" - // kMsgHelloBack = "Synergy%2i%2i%s" - sAddString(context, "Synergy"); - sAddUInt16(context, USYNERGY_PROTOCOL_MAJOR); - sAddUInt16(context, USYNERGY_PROTOCOL_MINOR); - sAddUInt32(context, (uint32_t)strlen(context->m_clientName)); - sAddString(context, context->m_clientName); - if (!sSendReply(context)) - { - // Send reply failed, let's try to reconnect - sTrace(context, "SendReply failed, trying to reconnect in a second"); - context->m_connected = USYNERGY_FALSE; - context->m_sleepFunc(context->m_cookie, 1000); - } - else - { - // Let's assume we're connected - char buffer[256+1]; - sprintf(buffer, "Connected as client \"%s\"", context->m_clientName); - sTrace(context, buffer); - context->m_hasReceivedHello = USYNERGY_TRUE; - } - return; - } - else if (USYNERGY_IS_PACKET("QINF")) - { - // Screen info. Reply with DINF - // kMsgQInfo = "QINF" - // kMsgDInfo = "DINF%2i%2i%2i%2i%2i%2i%2i" - uint16_t x = 0, y = 0, warp = 0; - sAddString(context, "DINF"); - sAddUInt16(context, x); - sAddUInt16(context, y); - sAddUInt16(context, context->m_clientWidth); - sAddUInt16(context, context->m_clientHeight); - sAddUInt16(context, warp); - sAddUInt16(context, 0); // mx? - sAddUInt16(context, 0); // my? - sSendReply(context); - return; - } - else if (USYNERGY_IS_PACKET("CIAK")) - { - // Do nothing? - // kMsgCInfoAck = "CIAK" - return; - } - else if (USYNERGY_IS_PACKET("CROP")) - { - // Do nothing? - // kMsgCResetOptions = "CROP" - return; - } - else if (USYNERGY_IS_PACKET("CINN")) - { - // Screen enter. Reply with CNOP - // kMsgCEnter = "CINN%2i%2i%4i%2i" - - // Obtain the Synergy sequence number - context->m_sequenceNumber = sNetToNative32(message + 12); - context->m_isCaptured = USYNERGY_TRUE; - - // Call callback - if (context->m_screenActiveCallback != 0L) - context->m_screenActiveCallback(context->m_cookie, USYNERGY_TRUE); - } - else if (USYNERGY_IS_PACKET("COUT")) - { - // Screen leave - // kMsgCLeave = "COUT" - context->m_isCaptured = USYNERGY_FALSE; - - // Call callback - if (context->m_screenActiveCallback != 0L) - context->m_screenActiveCallback(context->m_cookie, USYNERGY_FALSE); - } - else if (USYNERGY_IS_PACKET("DMDN")) - { - // Mouse down - // kMsgDMouseDown = "DMDN%1i" - char btn = message[8]-1; - if (btn==2) - context->m_mouseButtonRight = USYNERGY_TRUE; - else if (btn==1) - context->m_mouseButtonMiddle = USYNERGY_TRUE; - else - context->m_mouseButtonLeft = USYNERGY_TRUE; - sSendMouseCallback(context); - } - else if (USYNERGY_IS_PACKET("DMUP")) - { - // Mouse up - // kMsgDMouseUp = "DMUP%1i" - char btn = message[8]-1; - if (btn==2) - context->m_mouseButtonRight = USYNERGY_FALSE; - else if (btn==1) - context->m_mouseButtonMiddle = USYNERGY_FALSE; - else - context->m_mouseButtonLeft = USYNERGY_FALSE; - sSendMouseCallback(context); - } - else if (USYNERGY_IS_PACKET("DMMV")) - { - // Mouse move. Reply with CNOP - // kMsgDMouseMove = "DMMV%2i%2i" - context->m_mouseX = sNetToNative16(message+8); - context->m_mouseY = sNetToNative16(message+10); - sSendMouseCallback(context); - } - else if (USYNERGY_IS_PACKET("DMWM")) - { - // Mouse wheel - // kMsgDMouseWheel = "DMWM%2i%2i" - // kMsgDMouseWheel1_0 = "DMWM%2i" - context->m_mouseWheelX += sNetToNative16(message+8); - context->m_mouseWheelY += sNetToNative16(message+10); - sSendMouseCallback(context); - } - else if (USYNERGY_IS_PACKET("DKDN")) - { - // Key down - // kMsgDKeyDown = "DKDN%2i%2i%2i" - // kMsgDKeyDown1_0 = "DKDN%2i%2i" - //uint16_t id = sNetToNative16(message+8); - uint16_t mod = sNetToNative16(message+10); - uint16_t key = sNetToNative16(message+12); - sSendKeyboardCallback(context, key, mod, USYNERGY_TRUE, USYNERGY_FALSE); - } - else if (USYNERGY_IS_PACKET("DKRP")) - { - // Key repeat - // kMsgDKeyRepeat = "DKRP%2i%2i%2i%2i" - // kMsgDKeyRepeat1_0 = "DKRP%2i%2i%2i" - uint16_t mod = sNetToNative16(message+10); -// uint16_t count = sNetToNative16(message+12); - uint16_t key = sNetToNative16(message+14); - sSendKeyboardCallback(context, key, mod, USYNERGY_TRUE, USYNERGY_TRUE); - } - else if (USYNERGY_IS_PACKET("DKUP")) - { - // Key up - // kMsgDKeyUp = "DKUP%2i%2i%2i" - // kMsgDKeyUp1_0 = "DKUP%2i%2i" - //uint16 id=Endian::sNetToNative(sbuf[4]); - uint16_t mod = sNetToNative16(message+10); - uint16_t key = sNetToNative16(message+12); - sSendKeyboardCallback(context, key, mod, USYNERGY_FALSE, USYNERGY_FALSE); - } - else if (USYNERGY_IS_PACKET("DGBT")) - { - // Joystick buttons - // kMsgDGameButtons = "DGBT%1i%2i"; - uint8_t joy_num = message[8]; - if (joy_numm_joystickButtons[joy_num] = (message[9] << 8) | message[10]; - sSendJoystickCallback(context, joy_num); - } - } - else if (USYNERGY_IS_PACKET("DGST")) - { - // Joystick sticks - // kMsgDGameSticks = "DGST%1i%1i%1i%1i%1i"; - uint8_t joy_num = message[8]; - if (joy_numm_joystickSticks[joy_num], message+9, 4); - sSendJoystickCallback(context, joy_num); - } - } - else if (USYNERGY_IS_PACKET("DSOP")) - { - // Set options - // kMsgDSetOptions = "DSOP%4I" - } - else if (USYNERGY_IS_PACKET("CALV")) - { - // Keepalive, reply with CALV and then CNOP - // kMsgCKeepAlive = "CALV" - sAddString(context, "CALV"); - sSendReply(context); - // now reply with CNOP - } - else if (USYNERGY_IS_PACKET("DCLP")) - { - // Clipboard message - // kMsgDClipboard = "DCLP%1i%4i%s" - // - // The clipboard message contains: - // 1 uint32: The size of the message - // 4 chars: The identifier ("DCLP") - // 1 uint8: The clipboard index - // 1 uint32: The sequence number. It's zero, because this message is always coming from the server? - // 1 uint32: The total size of the remaining 'string' (as per the Synergy %s string format (which is 1 uint32 for size followed by a char buffer (not necessarily null terminated)). - // 1 uint32: The number of formats present in the message - // And then 'number of formats' times the following: - // 1 uint32: The format of the clipboard data - // 1 uint32: The size n of the clipboard data - // n uint8: The clipboard data - const uint8_t * parse_msg = message+17; - uint32_t num_formats = sNetToNative32(parse_msg); - parse_msg += 4; - for (; num_formats; num_formats--) - { - // Parse clipboard format header - uint32_t format = sNetToNative32(parse_msg); - uint32_t size = sNetToNative32(parse_msg+4); - parse_msg += 8; - - // Call callback - if (context->m_clipboardCallback) - context->m_clipboardCallback(context->m_cookie, format, parse_msg, size); - - parse_msg += size; - } - } - else - { - // Unknown packet, could be any of these - // kMsgCNoop = "CNOP" - // kMsgCClose = "CBYE" - // kMsgCClipboard = "CCLP%1i%4i" - // kMsgCScreenSaver = "CSEC%1i" - // kMsgDKeyRepeat = "DKRP%2i%2i%2i%2i" - // kMsgDKeyRepeat1_0 = "DKRP%2i%2i%2i" - // kMsgDMouseRelMove = "DMRM%2i%2i" - // kMsgEIncompatible = "EICV%2i%2i" - // kMsgEBusy = "EBSY" - // kMsgEUnknown = "EUNK" - // kMsgEBad = "EBAD" - char buffer[64]; - sprintf(buffer, "Unknown packet '%c%c%c%c'", message[4], message[5], message[6], message[7]); - sTrace(context, buffer); - return; - } - - // Reply with CNOP maybe? - sAddString(context, "CNOP"); - sSendReply(context); -} -#undef USYNERGY_IS_PACKET - - - -/** -@brief Mark context as being disconnected -**/ -static void sSetDisconnected(uSynergyContext *context) -{ - context->m_connected = USYNERGY_FALSE; - context->m_hasReceivedHello = USYNERGY_FALSE; - context->m_isCaptured = USYNERGY_FALSE; - context->m_replyCur = context->m_replyBuffer + 4; - context->m_sequenceNumber = 0; -} - - - -/** -@brief Update a connected context -**/ -static void sUpdateContext(uSynergyContext *context) -{ - /* Receive data (blocking) */ - int receive_size = USYNERGY_RECEIVE_BUFFER_SIZE - context->m_receiveOfs; - int num_received = 0; - int packlen = 0; - if (context->m_receiveFunc(context->m_cookie, context->m_receiveBuffer + context->m_receiveOfs, receive_size, &num_received) == USYNERGY_FALSE) - { - /* Receive failed, let's try to reconnect */ - char buffer[128]; - sprintf(buffer, "Receive failed (%d bytes asked, %d bytes received), trying to reconnect in a second", receive_size, num_received); - sTrace(context, buffer); - sSetDisconnected(context); - context->m_sleepFunc(context->m_cookie, 1000); - return; - } - context->m_receiveOfs += num_received; - - /* If we didn't receive any data then we're probably still polling to get connected and - therefore not getting any data back. To avoid overloading the system with a Synergy - thread that would hammer on polling, we let it rest for a bit if there's no data. */ - if (num_received == 0) - context->m_sleepFunc(context->m_cookie, 500); - - /* Check for timeouts */ - if (context->m_hasReceivedHello) - { - uint32_t cur_time = context->m_getTimeFunc(); - if (num_received == 0) - { - /* Timeout after 2 secs of inactivity (we received no CALV) */ - if ((cur_time - context->m_lastMessageTime) > USYNERGY_IDLE_TIMEOUT) - sSetDisconnected(context); - } - else - context->m_lastMessageTime = cur_time; - } - - /* Eat packets */ - for (;;) - { - /* Grab packet length and bail out if the packet goes beyond the end of the buffer */ - packlen = sNetToNative32(context->m_receiveBuffer); - if (packlen+4 > context->m_receiveOfs) - break; - - /* Process message */ - sProcessMessage(context, context->m_receiveBuffer); - - /* Move packet to front of buffer */ - memmove(context->m_receiveBuffer, context->m_receiveBuffer+packlen+4, context->m_receiveOfs-packlen-4); - context->m_receiveOfs -= packlen+4; - } - - /* Throw away over-sized packets */ - if (packlen > USYNERGY_RECEIVE_BUFFER_SIZE) - { - /* Oversized packet, ditch tail end */ - char buffer[128]; - sprintf(buffer, "Oversized packet: '%c%c%c%c' (length %d)", context->m_receiveBuffer[4], context->m_receiveBuffer[5], context->m_receiveBuffer[6], context->m_receiveBuffer[7], packlen); - sTrace(context, buffer); - num_received = context->m_receiveOfs-4; // 4 bytes for the size field - while (num_received != packlen) - { - int buffer_left = packlen - num_received; - int to_receive = buffer_left < USYNERGY_RECEIVE_BUFFER_SIZE ? buffer_left : USYNERGY_RECEIVE_BUFFER_SIZE; - int ditch_received = 0; - if (context->m_receiveFunc(context->m_cookie, context->m_receiveBuffer, to_receive, &ditch_received) == USYNERGY_FALSE) - { - /* Receive failed, let's try to reconnect */ - sTrace(context, "Receive failed, trying to reconnect in a second"); - sSetDisconnected(context); - context->m_sleepFunc(context->m_cookie, 1000); - break; - } - else - { - num_received += ditch_received; - } - } - context->m_receiveOfs = 0; - } -} - - -//--------------------------------------------------------------------------------------------------------------------- -// Public interface -//--------------------------------------------------------------------------------------------------------------------- - - - -/** -@brief Initialize uSynergy context -**/ -void uSynergyInit(uSynergyContext *context) -{ - /* Zero memory */ - memset(context, 0, sizeof(uSynergyContext)); - - /* Initialize to default state */ - sSetDisconnected(context); -} - - -/** -@brief Update uSynergy -**/ -void uSynergyUpdate(uSynergyContext *context) -{ - if (context->m_connected) - { - /* Update context, receive data, call callbacks */ - sUpdateContext(context); - } - else - { - /* Try to connect */ - if (context->m_connectFunc(context->m_cookie)) - context->m_connected = USYNERGY_TRUE; - } -} - - - -/** -@brief Send clipboard data -**/ -void uSynergySendClipboard(uSynergyContext *context, const char *text) -{ - // Calculate maximum size that will fit in a reply packet - uint32_t overhead_size = 4 + /* Message size */ - 4 + /* Message ID */ - 1 + /* Clipboard index */ - 4 + /* Sequence number */ - 4 + /* Rest of message size (because it's a Synergy string from here on) */ - 4 + /* Number of clipboard formats */ - 4 + /* Clipboard format */ - 4; /* Clipboard data length */ - uint32_t max_length = USYNERGY_REPLY_BUFFER_SIZE - overhead_size; - - // Clip text to max length - uint32_t text_length = (uint32_t)strlen(text); - if (text_length > max_length) - { - char buffer[128]; - sprintf(buffer, "Clipboard buffer too small, clipboard truncated at %d characters", max_length); - sTrace(context, buffer); - text_length = max_length; - } - - // Assemble packet - sAddString(context, "DCLP"); - sAddUInt8(context, 0); /* Clipboard index */ - sAddUInt32(context, context->m_sequenceNumber); - sAddUInt32(context, 4+4+4+text_length); /* Rest of message size: numFormats, format, length, data */ - sAddUInt32(context, 1); /* Number of formats (only text for now) */ - sAddUInt32(context, USYNERGY_CLIPBOARD_FORMAT_TEXT); - sAddUInt32(context, text_length); - sAddString(context, text); - sSendReply(context); -} diff --git a/app/jni/src/libultraship/extern/ImGui/examples/libs/usynergy/uSynergy.h b/app/jni/src/libultraship/extern/ImGui/examples/libs/usynergy/uSynergy.h deleted file mode 100644 index cedc387..0000000 --- a/app/jni/src/libultraship/extern/ImGui/examples/libs/usynergy/uSynergy.h +++ /dev/null @@ -1,420 +0,0 @@ -/* -uSynergy client -- Interface for the embedded Synergy client library - version 1.0.0, July 7th, 2012 - -Copyright (C) 2012 Synergy Si Ltd. -Copyright (c) 2012 Alex Evans - -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 - -#ifdef __cplusplus -extern "C" { -#endif - - - -//--------------------------------------------------------------------------------------------------------------------- -// Configuration -//--------------------------------------------------------------------------------------------------------------------- - - - -/** -@brief Determine endianness -**/ -#if defined(USYNERGY_LITTLE_ENDIAN) && defined(USYNERGY_BIG_ENDIAN) - /* Ambiguous: both endians specified */ - #error "Can't define both USYNERGY_LITTLE_ENDIAN and USYNERGY_BIG_ENDIAN" -#elif !defined(USYNERGY_LITTLE_ENDIAN) && !defined(USYNERGY_BIG_ENDIAN) - /* Attempt to auto detect */ - #if defined(__LITTLE_ENDIAN__) || defined(LITTLE_ENDIAN) || (_BYTE_ORDER == _LITTLE_ENDIAN) - #define USYNERGY_LITTLE_ENDIAN - #elif defined(__BIG_ENDIAN__) || defined(BIG_ENDIAN) || (_BYTE_ORDER == _BIG_ENDIAN) - #define USYNERGY_BIG_ENDIAN - #else - #error "Can't detect endian-nes, please defined either USYNERGY_LITTLE_ENDIAN or USYNERGY_BIG_ENDIAN"; - #endif -#else - /* User-specified endian-nes, nothing to do for us */ -#endif - - - -//--------------------------------------------------------------------------------------------------------------------- -// Types and Constants -//--------------------------------------------------------------------------------------------------------------------- - - - -/** -@brief Boolean type -**/ -typedef int uSynergyBool; -#define USYNERGY_FALSE 0 /* False value */ -#define USYNERGY_TRUE 1 /* True value */ - - -/** -@brief User context type - -The uSynergyCookie type is an opaque type that is used by uSynergy to communicate to the client. It is passed along to -callback functions as context. -**/ -typedef struct { int ignored; } * uSynergyCookie; - - - -/** -@brief Clipboard types -**/ -enum uSynergyClipboardFormat -{ - USYNERGY_CLIPBOARD_FORMAT_TEXT = 0, /* Text format, UTF-8, newline is LF */ - USYNERGY_CLIPBOARD_FORMAT_BITMAP = 1, /* Bitmap format, BMP 24/32bpp, BI_RGB */ - USYNERGY_CLIPBOARD_FORMAT_HTML = 2, /* HTML format, HTML fragment, UTF-8, newline is LF */ -}; - - - -/** -@brief Constants and limits -**/ -#define USYNERGY_NUM_JOYSTICKS 4 /* Maximum number of supported joysticks */ - -#define USYNERGY_PROTOCOL_MAJOR 1 /* Major protocol version */ -#define USYNERGY_PROTOCOL_MINOR 4 /* Minor protocol version */ - -#define USYNERGY_IDLE_TIMEOUT 2000 /* Timeout in milliseconds before reconnecting */ - -#define USYNERGY_TRACE_BUFFER_SIZE 1024 /* Maximum length of traced message */ -#define USYNERGY_REPLY_BUFFER_SIZE 1024 /* Maximum size of a reply packet */ -#define USYNERGY_RECEIVE_BUFFER_SIZE 4096 /* Maximum size of an incoming packet */ - - - -/** -@brief Keyboard constants -**/ -#define USYNERGY_MODIFIER_SHIFT 0x0001 /* Shift key modifier */ -#define USYNERGY_MODIFIER_CTRL 0x0002 /* Ctrl key modifier */ -#define USYNERGY_MODIFIER_ALT 0x0004 /* Alt key modifier */ -#define USYNERGY_MODIFIER_META 0x0008 /* Meta key modifier */ -#define USYNERGY_MODIFIER_WIN 0x0010 /* Windows key modifier */ -#define USYNERGY_MODIFIER_ALT_GR 0x0020 /* AltGr key modifier */ -#define USYNERGY_MODIFIER_LEVEL5LOCK 0x0040 /* Level5Lock key modifier */ -#define USYNERGY_MODIFIER_CAPSLOCK 0x1000 /* CapsLock key modifier */ -#define USYNERGY_MODIFIER_NUMLOCK 0x2000 /* NumLock key modifier */ -#define USYNERGY_MODIFIER_SCROLLOCK 0x4000 /* ScrollLock key modifier */ - - - - -//--------------------------------------------------------------------------------------------------------------------- -// Functions and Callbacks -//--------------------------------------------------------------------------------------------------------------------- - - - -/** -@brief Connect function - -This function is called when uSynergy needs to connect to the host. It doesn't imply a network implementation or -destination address, that must all be handled on the user side. The function should return USYNERGY_TRUE if a -connection was established or USYNERGY_FALSE if it could not connect. - -When network errors occur (e.g. uSynergySend or uSynergyReceive fail) then the connect call will be called again -so the implementation of the function must close any old connections and clean up resources before retrying. - -@param cookie Cookie supplied in the Synergy context -**/ -typedef uSynergyBool (*uSynergyConnectFunc)(uSynergyCookie cookie); - - - -/** -@brief Send function - -This function is called when uSynergy needs to send something over the default connection. It should return -USYNERGY_TRUE if sending succeeded and USYNERGY_FALSE otherwise. This function should block until the send -operation is completed. - -@param cookie Cookie supplied in the Synergy context -@param buffer Address of buffer to send -@param length Length of buffer to send -**/ -typedef uSynergyBool (*uSynergySendFunc)(uSynergyCookie cookie, const uint8_t *buffer, int length); - - - -/** -@brief Receive function - -This function is called when uSynergy needs to receive data from the default connection. It should return -USYNERGY_TRUE if receiving data succeeded and USYNERGY_FALSE otherwise. This function should block until data -has been received and wait for data to become available. If @a outLength is set to 0 upon completion it is -assumed that the connection is alive, but still in a connecting state and needs time to settle. - -@param cookie Cookie supplied in the Synergy context -@param buffer Address of buffer to receive data into -@param maxLength Maximum amount of bytes to write into the receive buffer -@param outLength Address of integer that receives the actual amount of bytes written into @a buffer -**/ -typedef uSynergyBool (*uSynergyReceiveFunc)(uSynergyCookie cookie, uint8_t *buffer, int maxLength, int* outLength); - - - -/** -@brief Thread sleep function - -This function is called when uSynergy wants to suspend operation for a while before retrying an operation. It -is mostly used when a socket times out or disconnect occurs to prevent uSynergy from continuously hammering a -network connection in case the network is down. - -@param cookie Cookie supplied in the Synergy context -@param timeMs Time to sleep the current thread (in milliseconds) -**/ -typedef void (*uSynergySleepFunc)(uSynergyCookie cookie, int timeMs); - - - -/** -@brief Get time function - -This function is called when uSynergy needs to know the current time. This is used to determine when timeouts -have occured. The time base should be a cyclic millisecond time value. - -@returns Time value in milliseconds -**/ -typedef uint32_t (*uSynergyGetTimeFunc)(); - - - -/** -@brief Trace function - -This function is called when uSynergy wants to trace something. It is optional to show these messages, but they -are often useful when debugging. uSynergy only traces major events like connecting and disconnecting. Usually -only a single trace is shown when the connection is established and no more trace are called. - -@param cookie Cookie supplied in the Synergy context -@param text Text to be traced -**/ -typedef void (*uSynergyTraceFunc)(uSynergyCookie cookie, const char *text); - - - -/** -@brief Screen active callback - -This callback is called when Synergy makes the screen active or inactive. This -callback is usually sent when the mouse enters or leaves the screen. - -@param cookie Cookie supplied in the Synergy context -@param active Activation flag, 1 if the screen has become active, 0 if the screen has become inactive -**/ -typedef void (*uSynergyScreenActiveCallback)(uSynergyCookie cookie, uSynergyBool active); - - - -/** -@brief Mouse callback - -This callback is called when a mouse events happens. The mouse X and Y position, -wheel and button state is communicated in the message. It's up to the user to -interpret if this is a mouse up, down, double-click or other message. - -@param cookie Cookie supplied in the Synergy context -@param x Mouse X position -@param y Mouse Y position -@param wheelX Mouse wheel X position -@param wheelY Mouse wheel Y position -@param buttonLeft Left button pressed status, 0 for released, 1 for pressed -@param buttonMiddle Middle button pressed status, 0 for released, 1 for pressed -@param buttonRight Right button pressed status, 0 for released, 1 for pressed -**/ -typedef void (*uSynergyMouseCallback)(uSynergyCookie cookie, uint16_t x, uint16_t y, int16_t wheelX, int16_t wheelY, uSynergyBool buttonLeft, uSynergyBool buttonRight, uSynergyBool buttonMiddle); - - - -/** -@brief Key event callback - -This callback is called when a key is pressed or released. - -@param cookie Cookie supplied in the Synergy context -@param key Key code of key that was pressed or released -@param modifiers Status of modifier keys (alt, shift, etc.) -@param down Down or up status, 1 is key is pressed down, 0 if key is released (up) -@param repeat Repeat flag, 1 if the key is down because the key is repeating, 0 if the key is initially pressed by the user -**/ -typedef void (*uSynergyKeyboardCallback)(uSynergyCookie cookie, uint16_t key, uint16_t modifiers, uSynergyBool down, uSynergyBool repeat); - - - -/** -@brief Joystick event callback - -This callback is called when a joystick stick or button changes. It is possible that multiple callbacks are -fired when different sticks or buttons change as these are individual messages in the packet stream. Each -callback will contain all the valid state for the different axes and buttons. The last callback received will -represent the most current joystick state. - -@param cookie Cookie supplied in the Synergy context -@param joyNum Joystick number, always in the range [0 ... USYNERGY_NUM_JOYSTICKS> -@param buttons Button pressed mask -@param leftStickX Left stick X position, in range [-127 ... 127] -@param leftStickY Left stick Y position, in range [-127 ... 127] -@param rightStickX Right stick X position, in range [-127 ... 127] -@param rightStickY Right stick Y position, in range [-127 ... 127] -**/ -typedef void (*uSynergyJoystickCallback)(uSynergyCookie cookie, uint8_t joyNum, uint16_t buttons, int8_t leftStickX, int8_t leftStickY, int8_t rightStickX, int8_t rightStickY); - - - -/** -@brief Clipboard event callback - -This callback is called when something is placed on the clipboard. Multiple callbacks may be fired for -multiple clipboard formats if they are supported. The data provided is read-only and may not be modified -by the application. - -@param cookie Cookie supplied in the Synergy context -@param format Clipboard format -@param data Memory area containing the clipboard raw data -@param size Size of clipboard data -**/ -typedef void (*uSynergyClipboardCallback)(uSynergyCookie cookie, enum uSynergyClipboardFormat format, const uint8_t *data, uint32_t size); - - - -//--------------------------------------------------------------------------------------------------------------------- -// Context -//--------------------------------------------------------------------------------------------------------------------- - - - -/** -@brief uSynergy context -**/ -typedef struct -{ - /* Mandatory configuration data, filled in by client */ - uSynergyConnectFunc m_connectFunc; /* Connect function */ - uSynergySendFunc m_sendFunc; /* Send data function */ - uSynergyReceiveFunc m_receiveFunc; /* Receive data function */ - uSynergySleepFunc m_sleepFunc; /* Thread sleep function */ - uSynergyGetTimeFunc m_getTimeFunc; /* Get current time function */ - const char* m_clientName; /* Name of Synergy Screen / Client */ - uint16_t m_clientWidth; /* Width of screen */ - uint16_t m_clientHeight; /* Height of screen */ - - /* Optional configuration data, filled in by client */ - uSynergyCookie m_cookie; /* Cookie pointer passed to callback functions (can be NULL) */ - uSynergyTraceFunc m_traceFunc; /* Function for tracing status (can be NULL) */ - uSynergyScreenActiveCallback m_screenActiveCallback; /* Callback for entering and leaving screen */ - uSynergyMouseCallback m_mouseCallback; /* Callback for mouse events */ - uSynergyKeyboardCallback m_keyboardCallback; /* Callback for keyboard events */ - uSynergyJoystickCallback m_joystickCallback; /* Callback for joystick events */ - uSynergyClipboardCallback m_clipboardCallback; /* Callback for clipboard events */ - - /* State data, used internall by client, initialized by uSynergyInit() */ - uSynergyBool m_connected; /* Is our socket connected? */ - uSynergyBool m_hasReceivedHello; /* Have we received a 'Hello' from the server? */ - uSynergyBool m_isCaptured; /* Is Synergy active (i.e. this client is receiving input messages?) */ - uint32_t m_lastMessageTime; /* Time at which last message was received */ - uint32_t m_sequenceNumber; /* Packet sequence number */ - uint8_t m_receiveBuffer[USYNERGY_RECEIVE_BUFFER_SIZE]; /* Receive buffer */ - int m_receiveOfs; /* Receive buffer offset */ - uint8_t m_replyBuffer[USYNERGY_REPLY_BUFFER_SIZE]; /* Reply buffer */ - uint8_t* m_replyCur; /* Write offset into reply buffer */ - uint16_t m_mouseX; /* Mouse X position */ - uint16_t m_mouseY; /* Mouse Y position */ - int16_t m_mouseWheelX; /* Mouse wheel X position */ - int16_t m_mouseWheelY; /* Mouse wheel Y position */ - uSynergyBool m_mouseButtonLeft; /* Mouse left button */ - uSynergyBool m_mouseButtonRight; /* Mouse right button */ - uSynergyBool m_mouseButtonMiddle; /* Mouse middle button */ - int8_t m_joystickSticks[USYNERGY_NUM_JOYSTICKS][4]; /* Joystick stick position in 2 axes for 2 sticks */ - uint16_t m_joystickButtons[USYNERGY_NUM_JOYSTICKS]; /* Joystick button state */ -} uSynergyContext; - - - -//--------------------------------------------------------------------------------------------------------------------- -// Interface -//--------------------------------------------------------------------------------------------------------------------- - - - -/** -@brief Initialize uSynergy context - -This function initializes @a context for use. Call this function directly after -creating the context, before filling in any configuration data in it. Not calling -this function will cause undefined behavior. - -@param context Context to be initialized -**/ -extern void uSynergyInit(uSynergyContext *context); - - - -/** -@brief Update uSynergy - -This function updates uSynergy and does the bulk of the work. It does connection management, -receiving data, reconnecting after errors or timeouts and so on. It assumes that networking -operations are blocking and it can suspend the current thread if it needs to wait. It is -best practice to call uSynergyUpdate from a background thread so it is responsive. - -Because uSynergy relies mostly on blocking calls it will mostly stay in thread sleep state -waiting for system mutexes and won't eat much memory. - -uSynergyUpdate doesn't do any memory allocations or have any side effects beyond those of -the callbacks it calls. - -@param context Context to be updated -**/ -extern void uSynergyUpdate(uSynergyContext *context); - - - -/** -@brief Send clipboard data - -This function sets new clipboard data and sends it to the server. Use this function if -your client cuts or copies data onto the clipboard that it needs to share with the -server. - -Currently there is only support for plaintext, but HTML and image data could be -supported with some effort. - -@param context Context to send clipboard data to -@param text Text to set to the clipboard -**/ -extern void uSynergySendClipboard(uSynergyContext *context, const char *text); - - - -#ifdef __cplusplus -}; -#endif diff --git a/app/jni/src/libultraship/extern/ImGui/imconfig.h b/app/jni/src/libultraship/extern/ImGui/imconfig.h deleted file mode 100644 index bac7661..0000000 --- a/app/jni/src/libultraship/extern/ImGui/imconfig.h +++ /dev/null @@ -1,129 +0,0 @@ -//----------------------------------------------------------------------------- -// DEAR IMGUI COMPILE-TIME OPTIONS -// Runtime options (clipboard callbacks, enabling various features, etc.) can generally be set via the ImGuiIO structure. -// You can use ImGui::SetAllocatorFunctions() before calling ImGui::CreateContext() to rewire memory allocation functions. -//----------------------------------------------------------------------------- -// A) You may edit imconfig.h (and not overwrite it when updating Dear ImGui, or maintain a patch/rebased branch with your modifications to it) -// B) or '#define IMGUI_USER_CONFIG "my_imgui_config.h"' in your project and then add directives in your own file without touching this template. -//----------------------------------------------------------------------------- -// You need to make sure that configuration settings are defined consistently _everywhere_ Dear ImGui is used, which include the imgui*.cpp -// files but also _any_ of your code that uses Dear ImGui. This is because some compile-time options have an affect on data structures. -// Defining those options in imconfig.h will ensure every compilation unit gets to see the same data structure layouts. -// Call IMGUI_CHECKVERSION() from your .cpp file to verify that the data structures your files are using are matching the ones imgui.cpp is using. -//----------------------------------------------------------------------------- - -#pragma once - -//---- Define assertion handler. Defaults to calling assert(). -// If your macro uses multiple statements, make sure is enclosed in a 'do { .. } while (0)' block so it can be used as a single statement. -//#define IM_ASSERT(_EXPR) MyAssert(_EXPR) -//#define IM_ASSERT(_EXPR) ((void)(_EXPR)) // Disable asserts - -//---- Define attributes of all API symbols declarations, e.g. for DLL under Windows -// Using Dear ImGui via a shared library is not recommended, because of function call overhead and because we don't guarantee backward nor forward ABI compatibility. -// DLL users: heaps and globals are not shared across DLL boundaries! You will need to call SetCurrentContext() + SetAllocatorFunctions() -// for each static/DLL boundary you are calling from. Read "Context and Memory Allocators" section of imgui.cpp for more details. -//#define IMGUI_API __declspec( dllexport ) -//#define IMGUI_API __declspec( dllimport ) - -//---- Don't define obsolete functions/enums/behaviors. Consider enabling from time to time after updating to clean your code of obsolete function/names. -//#define IMGUI_DISABLE_OBSOLETE_FUNCTIONS -//#define IMGUI_DISABLE_OBSOLETE_KEYIO // 1.87: disable legacy io.KeyMap[]+io.KeysDown[] in favor io.AddKeyEvent(). This will be folded into IMGUI_DISABLE_OBSOLETE_FUNCTIONS in a few versions. - -//---- Disable all of Dear ImGui or don't implement standard windows/tools. -// It is very strongly recommended to NOT disable the demo windows and debug tool during development. They are extremely useful in day to day work. Please read comments in imgui_demo.cpp. -//#define IMGUI_DISABLE // Disable everything: all headers and source files will be empty. -//#define IMGUI_DISABLE_DEMO_WINDOWS // Disable demo windows: ShowDemoWindow()/ShowStyleEditor() will be empty. -//#define IMGUI_DISABLE_DEBUG_TOOLS // Disable metrics/debugger and other debug tools: ShowMetricsWindow(), ShowDebugLogWindow() and ShowIDStackToolWindow() will be empty. - -//---- Don't implement some functions to reduce linkage requirements. -//#define IMGUI_DISABLE_WIN32_DEFAULT_CLIPBOARD_FUNCTIONS // [Win32] Don't implement default clipboard handler. Won't use and link with OpenClipboard/GetClipboardData/CloseClipboard etc. (user32.lib/.a, kernel32.lib/.a) -//#define IMGUI_ENABLE_WIN32_DEFAULT_IME_FUNCTIONS // [Win32] [Default with Visual Studio] Implement default IME handler (require imm32.lib/.a, auto-link for Visual Studio, -limm32 on command-line for MinGW) -//#define IMGUI_DISABLE_WIN32_DEFAULT_IME_FUNCTIONS // [Win32] [Default with non-Visual Studio compilers] Don't implement default IME handler (won't require imm32.lib/.a) -//#define IMGUI_DISABLE_WIN32_FUNCTIONS // [Win32] Won't use and link with any Win32 function (clipboard, IME). -//#define IMGUI_ENABLE_OSX_DEFAULT_CLIPBOARD_FUNCTIONS // [OSX] Implement default OSX clipboard handler (need to link with '-framework ApplicationServices', this is why this is not the default). -//#define IMGUI_DISABLE_DEFAULT_FORMAT_FUNCTIONS // Don't implement ImFormatString/ImFormatStringV so you can implement them yourself (e.g. if you don't want to link with vsnprintf) -//#define IMGUI_DISABLE_DEFAULT_MATH_FUNCTIONS // Don't implement ImFabs/ImSqrt/ImPow/ImFmod/ImCos/ImSin/ImAcos/ImAtan2 so you can implement them yourself. -//#define IMGUI_DISABLE_FILE_FUNCTIONS // Don't implement ImFileOpen/ImFileClose/ImFileRead/ImFileWrite and ImFileHandle at all (replace them with dummies) -//#define IMGUI_DISABLE_DEFAULT_FILE_FUNCTIONS // Don't implement ImFileOpen/ImFileClose/ImFileRead/ImFileWrite and ImFileHandle so you can implement them yourself if you don't want to link with fopen/fclose/fread/fwrite. This will also disable the LogToTTY() function. -//#define IMGUI_DISABLE_DEFAULT_ALLOCATORS // Don't implement default allocators calling malloc()/free() to avoid linking with them. You will need to call ImGui::SetAllocatorFunctions(). -//#define IMGUI_DISABLE_SSE // Disable use of SSE intrinsics even if available - -//---- Include imgui_user.h at the end of imgui.h as a convenience -//#define IMGUI_INCLUDE_IMGUI_USER_H - -//---- Pack colors to BGRA8 instead of RGBA8 (to avoid converting from one to another) -//#define IMGUI_USE_BGRA_PACKED_COLOR - -//---- Use 32-bit for ImWchar (default is 16-bit) to support unicode planes 1-16. (e.g. point beyond 0xFFFF like emoticons, dingbats, symbols, shapes, ancient languages, etc...) -//#define IMGUI_USE_WCHAR32 - -//---- Avoid multiple STB libraries implementations, or redefine path/filenames to prioritize another version -// By default the embedded implementations are declared static and not available outside of Dear ImGui sources files. -//#define IMGUI_STB_TRUETYPE_FILENAME "my_folder/stb_truetype.h" -//#define IMGUI_STB_RECT_PACK_FILENAME "my_folder/stb_rect_pack.h" -//#define IMGUI_STB_SPRINTF_FILENAME "my_folder/stb_sprintf.h" // only used if IMGUI_USE_STB_SPRINTF is defined. -//#define IMGUI_DISABLE_STB_TRUETYPE_IMPLEMENTATION -//#define IMGUI_DISABLE_STB_RECT_PACK_IMPLEMENTATION -//#define IMGUI_DISABLE_STB_SPRINTF_IMPLEMENTATION // only disabled if IMGUI_USE_STB_SPRINTF is defined. - -//---- Use stb_sprintf.h for a faster implementation of vsnprintf instead of the one from libc (unless IMGUI_DISABLE_DEFAULT_FORMAT_FUNCTIONS is defined) -// Compatibility checks of arguments and formats done by clang and GCC will be disabled in order to support the extra formats provided by stb_sprintf.h. -//#define IMGUI_USE_STB_SPRINTF - -//---- Use FreeType to build and rasterize the font atlas (instead of stb_truetype which is embedded by default in Dear ImGui) -// Requires FreeType headers to be available in the include path. Requires program to be compiled with 'misc/freetype/imgui_freetype.cpp' (in this repository) + the FreeType library (not provided). -// On Windows you may use vcpkg with 'vcpkg install freetype --triplet=x64-windows' + 'vcpkg integrate install'. -//#define IMGUI_ENABLE_FREETYPE - -//---- Use FreeType+lunasvg library to render OpenType SVG fonts (SVGinOT) -// Requires lunasvg headers to be available in the include path + program to be linked with the lunasvg library (not provided). -// Only works in combination with IMGUI_ENABLE_FREETYPE. -// (implementation is based on Freetype's rsvg-port.c which is licensed under CeCILL-C Free Software License Agreement) -//#define IMGUI_ENABLE_FREETYPE_LUNASVG - -//---- Use stb_truetype to build and rasterize the font atlas (default) -// The only purpose of this define is if you want force compilation of the stb_truetype backend ALONG with the FreeType backend. -//#define IMGUI_ENABLE_STB_TRUETYPE - -//---- Define constructor and implicit cast operators to convert back<>forth between your math types and ImVec2/ImVec4. -// This will be inlined as part of ImVec2 and ImVec4 class declarations. -/* -#define IM_VEC2_CLASS_EXTRA \ - constexpr ImVec2(const MyVec2& f) : x(f.x), y(f.y) {} \ - operator MyVec2() const { return MyVec2(x,y); } - -#define IM_VEC4_CLASS_EXTRA \ - constexpr ImVec4(const MyVec4& f) : x(f.x), y(f.y), z(f.z), w(f.w) {} \ - operator MyVec4() const { return MyVec4(x,y,z,w); } -*/ -//---- ...Or use Dear ImGui's own very basic math operators. -//#define IMGUI_DEFINE_MATH_OPERATORS - -//---- Use 32-bit vertex indices (default is 16-bit) is one way to allow large meshes with more than 64K vertices. -// Your renderer backend will need to support it (most example renderer backends support both 16/32-bit indices). -// Another way to allow large meshes while keeping 16-bit indices is to handle ImDrawCmd::VtxOffset in your renderer. -// Read about ImGuiBackendFlags_RendererHasVtxOffset for details. -//#define ImDrawIdx unsigned int - -//---- Override ImDrawCallback signature (will need to modify renderer backends accordingly) -//struct ImDrawList; -//struct ImDrawCmd; -//typedef void (*MyImDrawCallback)(const ImDrawList* draw_list, const ImDrawCmd* cmd, void* my_renderer_user_data); -//#define ImDrawCallback MyImDrawCallback - -//---- Debug Tools: Macro to break in Debugger (we provide a default implementation of this in the codebase) -// (use 'Metrics->Tools->Item Picker' to pick widgets with the mouse and break into them for easy debugging.) -//#define IM_DEBUG_BREAK IM_ASSERT(0) -//#define IM_DEBUG_BREAK __debugbreak() - -//---- Debug Tools: Enable slower asserts -//#define IMGUI_DEBUG_PARANOID - -//---- Tip: You can add extra functions within the ImGui:: namespace from anywhere (e.g. your own sources/header files) -/* -namespace ImGui -{ - void MyFunction(const char* name, MyMatrix44* mtx); -} -*/ diff --git a/app/jni/src/libultraship/extern/ImGui/imgui.cpp b/app/jni/src/libultraship/extern/ImGui/imgui.cpp deleted file mode 100644 index f495ff4..0000000 --- a/app/jni/src/libultraship/extern/ImGui/imgui.cpp +++ /dev/null @@ -1,20905 +0,0 @@ -// dear imgui, v1.90 WIP -// (main code and documentation) - -// Help: -// - See links below. -// - Call and read ImGui::ShowDemoWindow() in imgui_demo.cpp. All applications in examples/ are doing that. -// - Read top of imgui.cpp for more details, links and comments. - -// Resources: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Homepage https://github.com/ocornut/imgui -// - Releases & changelog https://github.com/ocornut/imgui/releases -// - Gallery https://github.com/ocornut/imgui/issues/6897 (please post your screenshots/video there!) -// - Wiki https://github.com/ocornut/imgui/wiki (lots of good stuff there) -// - Glossary https://github.com/ocornut/imgui/wiki/Glossary -// - Issues & support https://github.com/ocornut/imgui/issues -// - Tests & Automation https://github.com/ocornut/imgui_test_engine - -// For first-time users having issues compiling/linking/running/loading fonts: -// please post in https://github.com/ocornut/imgui/discussions if you cannot find a solution in resources above. -// Everything else should be asked in 'Issues'! We are building a database of cross-linked knowledge there. - -// Copyright (c) 2014-2023 Omar Cornut -// Developed by Omar Cornut and every direct or indirect contributors to the GitHub. -// See LICENSE.txt for copyright and licensing details (standard MIT License). -// This library is free but needs your support to sustain development and maintenance. -// Businesses: you can support continued development via B2B invoiced technical support, maintenance and sponsoring contracts. -// PLEASE reach out at omar AT dearimgui DOT com. See https://github.com/ocornut/imgui/wiki/Sponsors -// Businesses: you can also purchase licenses for the Dear ImGui Automation/Test Engine. - -// It is recommended that you don't modify imgui.cpp! It will become difficult for you to update the library. -// Note that 'ImGui::' being a namespace, you can add functions into the namespace from your own source files, without -// modifying imgui.h or imgui.cpp. You may include imgui_internal.h to access internal data structures, but it doesn't -// come with any guarantee of forward compatibility. Discussing your changes on the GitHub Issue Tracker may lead you -// to a better solution or official support for them. - -/* - -Index of this file: - -DOCUMENTATION - -- MISSION STATEMENT -- CONTROLS GUIDE -- PROGRAMMER GUIDE - - READ FIRST - - HOW TO UPDATE TO A NEWER VERSION OF DEAR IMGUI - - GETTING STARTED WITH INTEGRATING DEAR IMGUI IN YOUR CODE/ENGINE - - HOW A SIMPLE APPLICATION MAY LOOK LIKE - - HOW A SIMPLE RENDERING FUNCTION MAY LOOK LIKE -- API BREAKING CHANGES (read me when you update!) -- FREQUENTLY ASKED QUESTIONS (FAQ) - - Read all answers online: https://www.dearimgui.com/faq, or in docs/FAQ.md (with a Markdown viewer) - -CODE -(search for "[SECTION]" in the code to find them) - -// [SECTION] INCLUDES -// [SECTION] FORWARD DECLARATIONS -// [SECTION] CONTEXT AND MEMORY ALLOCATORS -// [SECTION] USER FACING STRUCTURES (ImGuiStyle, ImGuiIO) -// [SECTION] MISC HELPERS/UTILITIES (Geometry functions) -// [SECTION] MISC HELPERS/UTILITIES (String, Format, Hash functions) -// [SECTION] MISC HELPERS/UTILITIES (File functions) -// [SECTION] MISC HELPERS/UTILITIES (ImText* functions) -// [SECTION] MISC HELPERS/UTILITIES (Color functions) -// [SECTION] ImGuiStorage -// [SECTION] ImGuiTextFilter -// [SECTION] ImGuiTextBuffer, ImGuiTextIndex -// [SECTION] ImGuiListClipper -// [SECTION] STYLING -// [SECTION] RENDER HELPERS -// [SECTION] INITIALIZATION, SHUTDOWN -// [SECTION] MAIN CODE (most of the code! lots of stuff, needs tidying up!) -// [SECTION] INPUTS -// [SECTION] ERROR CHECKING -// [SECTION] LAYOUT -// [SECTION] SCROLLING -// [SECTION] TOOLTIPS -// [SECTION] POPUPS -// [SECTION] KEYBOARD/GAMEPAD NAVIGATION -// [SECTION] DRAG AND DROP -// [SECTION] LOGGING/CAPTURING -// [SECTION] SETTINGS -// [SECTION] LOCALIZATION -// [SECTION] VIEWPORTS, PLATFORM WINDOWS -// [SECTION] DOCKING -// [SECTION] PLATFORM DEPENDENT HELPERS -// [SECTION] METRICS/DEBUGGER WINDOW -// [SECTION] DEBUG LOG WINDOW -// [SECTION] OTHER DEBUG TOOLS (ITEM PICKER, ID STACK TOOL) - -*/ - -//----------------------------------------------------------------------------- -// DOCUMENTATION -//----------------------------------------------------------------------------- - -/* - - MISSION STATEMENT - ================= - - - Easy to use to create code-driven and data-driven tools. - - Easy to use to create ad hoc short-lived tools and long-lived, more elaborate tools. - - Easy to hack and improve. - - Minimize setup and maintenance. - - Minimize state storage on user side. - - Minimize state synchronization. - - Portable, minimize dependencies, run on target (consoles, phones, etc.). - - Efficient runtime and memory consumption. - - Designed primarily for developers and content-creators, not the typical end-user! - Some of the current weaknesses (which we aim to address in the future) includes: - - - Doesn't look fancy. - - Limited layout features, intricate layouts are typically crafted in code. - - - CONTROLS GUIDE - ============== - - - MOUSE CONTROLS - - Mouse wheel: Scroll vertically. - - SHIFT+Mouse wheel: Scroll horizontally. - - Click [X]: Close a window, available when 'bool* p_open' is passed to ImGui::Begin(). - - Click ^, Double-Click title: Collapse window. - - Drag on corner/border: Resize window (double-click to auto fit window to its contents). - - Drag on any empty space: Move window (unless io.ConfigWindowsMoveFromTitleBarOnly = true). - - Left-click outside popup: Close popup stack (right-click over underlying popup: Partially close popup stack). - - - TEXT EDITOR - - Hold SHIFT or Drag Mouse: Select text. - - CTRL+Left/Right: Word jump. - - CTRL+Shift+Left/Right: Select words. - - CTRL+A or Double-Click: Select All. - - CTRL+X, CTRL+C, CTRL+V: Use OS clipboard. - - CTRL+Z, CTRL+Y: Undo, Redo. - - ESCAPE: Revert text to its original value. - - On OSX, controls are automatically adjusted to match standard OSX text editing shortcuts and behaviors. - - - KEYBOARD CONTROLS - - Basic: - - Tab, SHIFT+Tab Cycle through text editable fields. - - CTRL+Tab, CTRL+Shift+Tab Cycle through windows. - - CTRL+Click Input text into a Slider or Drag widget. - - Extended features with `io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard`: - - Tab, SHIFT+Tab: Cycle through every items. - - Arrow keys Move through items using directional navigation. Tweak value. - - Arrow keys + Alt, Shift Tweak slower, tweak faster (when using arrow keys). - - Enter Activate item (prefer text input when possible). - - Space Activate item (prefer tweaking with arrows when possible). - - Escape Deactivate item, leave child window, close popup. - - Page Up, Page Down Previous page, next page. - - Home, End Scroll to top, scroll to bottom. - - Alt Toggle between scrolling layer and menu layer. - - CTRL+Tab then Ctrl+Arrows Move window. Hold SHIFT to resize instead of moving. - - Output when ImGuiConfigFlags_NavEnableKeyboard set, - - io.WantCaptureKeyboard flag is set when keyboard is claimed. - - io.NavActive: true when a window is focused and it doesn't have the ImGuiWindowFlags_NoNavInputs flag set. - - io.NavVisible: true when the navigation cursor is visible (usually goes to back false when mouse is used). - - - GAMEPAD CONTROLS - - Enable with 'io.ConfigFlags |= ImGuiConfigFlags_NavEnableGamepad'. - - Particularly useful to use Dear ImGui on a console system (e.g. PlayStation, Switch, Xbox) without a mouse! - - Download controller mapping PNG/PSD at http://dearimgui.com/controls_sheets - - Backend support: backend needs to: - - Set 'io.BackendFlags |= ImGuiBackendFlags_HasGamepad' + call io.AddKeyEvent/AddKeyAnalogEvent() with ImGuiKey_Gamepad_XXX keys. - - For analog values (0.0f to 1.0f), backend is responsible to handling a dead-zone and rescaling inputs accordingly. - Backend code will probably need to transform your raw inputs (such as e.g. remapping your 0.2..0.9 raw input range to 0.0..1.0 imgui range, etc.). - - BEFORE 1.87, BACKENDS USED TO WRITE TO io.NavInputs[]. This is now obsolete. Please call io functions instead! - - If you need to share inputs between your game and the Dear ImGui interface, the easiest approach is to go all-or-nothing, - with a buttons combo to toggle the target. Please reach out if you think the game vs navigation input sharing could be improved. - - - REMOTE INPUTS SHARING & MOUSE EMULATION - - PS4/PS5 users: Consider emulating a mouse cursor with DualShock touch pad or a spare analog stick as a mouse-emulation fallback. - - Consoles/Tablet/Phone users: Consider using a Synergy 1.x server (on your PC) + run examples/libs/synergy/uSynergy.c (on your console/tablet/phone app) - in order to share your PC mouse/keyboard. - - See https://github.com/ocornut/imgui/wiki/Useful-Extensions#remoting for other remoting solutions. - - On a TV/console system where readability may be lower or mouse inputs may be awkward, you may want to set the ImGuiConfigFlags_NavEnableSetMousePos flag. - Enabling ImGuiConfigFlags_NavEnableSetMousePos + ImGuiBackendFlags_HasSetMousePos instructs Dear ImGui to move your mouse cursor along with navigation movements. - When enabled, the NewFrame() function may alter 'io.MousePos' and set 'io.WantSetMousePos' to notify you that it wants the mouse cursor to be moved. - When that happens your backend NEEDS to move the OS or underlying mouse cursor on the next frame. Some of the backends in examples/ do that. - (If you set the NavEnableSetMousePos flag but don't honor 'io.WantSetMousePos' properly, Dear ImGui will misbehave as it will see your mouse moving back & forth!) - (In a setup when you may not have easy control over the mouse cursor, e.g. uSynergy.c doesn't expose moving remote mouse cursor, you may want - to set a boolean to ignore your other external mouse positions until the external source is moved again.) - - - PROGRAMMER GUIDE - ================ - - READ FIRST - ---------- - - Remember to check the wonderful Wiki (https://github.com/ocornut/imgui/wiki) - - Your code creates the UI every frame of your application loop, if your code doesn't run the UI is gone! - The UI can be highly dynamic, there are no construction or destruction steps, less superfluous - data retention on your side, less state duplication, less state synchronization, fewer bugs. - - Call and read ImGui::ShowDemoWindow() for demo code demonstrating most features. - Or browse https://pthom.github.io/imgui_manual_online/manual/imgui_manual.html for interactive web version. - - The library is designed to be built from sources. Avoid pre-compiled binaries and packaged versions. See imconfig.h to configure your build. - - Dear ImGui is an implementation of the IMGUI paradigm (immediate-mode graphical user interface, a term coined by Casey Muratori). - You can learn about IMGUI principles at http://www.johno.se/book/imgui.html, http://mollyrocket.com/861 & more links in Wiki. - - Dear ImGui is a "single pass" rasterizing implementation of the IMGUI paradigm, aimed at ease of use and high-performances. - For every application frame, your UI code will be called only once. This is in contrast to e.g. Unity's implementation of an IMGUI, - where the UI code is called multiple times ("multiple passes") from a single entry point. There are pros and cons to both approaches. - - Our origin is on the top-left. In axis aligned bounding boxes, Min = top-left, Max = bottom-right. - - Please make sure you have asserts enabled (IM_ASSERT redirects to assert() by default, but can be redirected). - If you get an assert, read the messages and comments around the assert. - - This codebase aims to be highly optimized: - - A typical idle frame should never call malloc/free. - - We rely on a maximum of constant-time or O(N) algorithms. Limiting searches/scans as much as possible. - - We put particular energy in making sure performances are decent with typical "Debug" build settings as well. - Which mean we tend to avoid over-relying on "zero-cost abstraction" as they aren't zero-cost at all. - - This codebase aims to be both highly opinionated and highly flexible: - - This code works because of the things it choose to solve or not solve. - - C++: this is a pragmatic C-ish codebase: we don't use fancy C++ features, we don't include C++ headers, - and ImGui:: is a namespace. We rarely use member functions (and when we did, I am mostly regretting it now). - This is to increase compatibility, increase maintainability and facilitate use from other languages. - - C++: ImVec2/ImVec4 do not expose math operators by default, because it is expected that you use your own math types. - See FAQ "How can I use my own math types instead of ImVec2/ImVec4?" for details about setting up imconfig.h for that. - We can can optionally export math operators for ImVec2/ImVec4 using IMGUI_DEFINE_MATH_OPERATORS, which we use internally. - - C++: pay attention that ImVector<> manipulates plain-old-data and does not honor construction/destruction - (so don't use ImVector in your code or at our own risk!). - - Building: We don't use nor mandate a build system for the main library. - This is in an effort to ensure that it works in the real world aka with any esoteric build setup. - This is also because providing a build system for the main library would be of little-value. - The build problems are almost never coming from the main library but from specific backends. - - - HOW TO UPDATE TO A NEWER VERSION OF DEAR IMGUI - ---------------------------------------------- - - Update submodule or copy/overwrite every file. - - About imconfig.h: - - You may modify your copy of imconfig.h, in this case don't overwrite it. - - or you may locally branch to modify imconfig.h and merge/rebase latest. - - or you may '#define IMGUI_USER_CONFIG "my_config_file.h"' globally from your build system to - specify a custom path for your imconfig.h file and instead not have to modify the default one. - - - Overwrite all the sources files except for imconfig.h (if you have modified your copy of imconfig.h) - - Or maintain your own branch where you have imconfig.h modified as a top-most commit which you can regularly rebase over "master". - - You can also use '#define IMGUI_USER_CONFIG "my_config_file.h" to redirect configuration to your own file. - - Read the "API BREAKING CHANGES" section (below). This is where we list occasional API breaking changes. - If a function/type has been renamed / or marked obsolete, try to fix the name in your code before it is permanently removed - from the public API. If you have a problem with a missing function/symbols, search for its name in the code, there will - likely be a comment about it. Please report any issue to the GitHub page! - - To find out usage of old API, you can add '#define IMGUI_DISABLE_OBSOLETE_FUNCTIONS' in your configuration file. - - Try to keep your copy of Dear ImGui reasonably up to date! - - - GETTING STARTED WITH INTEGRATING DEAR IMGUI IN YOUR CODE/ENGINE - --------------------------------------------------------------- - - See https://github.com/ocornut/imgui/wiki/Getting-Started. - - Run and study the examples and demo in imgui_demo.cpp to get acquainted with the library. - - In the majority of cases you should be able to use unmodified backends files available in the backends/ folder. - - Add the Dear ImGui source files + selected backend source files to your projects or using your preferred build system. - It is recommended you build and statically link the .cpp files as part of your project and NOT as a shared library (DLL). - - You can later customize the imconfig.h file to tweak some compile-time behavior, such as integrating Dear ImGui types with your own maths types. - - When using Dear ImGui, your programming IDE is your friend: follow the declaration of variables, functions and types to find comments about them. - - Dear ImGui never touches or knows about your GPU state. The only function that knows about GPU is the draw function that you provide. - Effectively it means you can create widgets at any time in your code, regardless of considerations of being in "update" vs "render" - phases of your own application. All rendering information is stored into command-lists that you will retrieve after calling ImGui::Render(). - - Refer to the backends and demo applications in the examples/ folder for instruction on how to setup your code. - - If you are running over a standard OS with a common graphics API, you should be able to use unmodified imgui_impl_*** files from the examples/ folder. - - - HOW A SIMPLE APPLICATION MAY LOOK LIKE - -------------------------------------- - EXHIBIT 1: USING THE EXAMPLE BACKENDS (= imgui_impl_XXX.cpp files from the backends/ folder). - The sub-folders in examples/ contain examples applications following this structure. - - // Application init: create a dear imgui context, setup some options, load fonts - ImGui::CreateContext(); - ImGuiIO& io = ImGui::GetIO(); - // TODO: Set optional io.ConfigFlags values, e.g. 'io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard' to enable keyboard controls. - // TODO: Fill optional fields of the io structure later. - // TODO: Load TTF/OTF fonts if you don't want to use the default font. - - // Initialize helper Platform and Renderer backends (here we are using imgui_impl_win32.cpp and imgui_impl_dx11.cpp) - ImGui_ImplWin32_Init(hwnd); - ImGui_ImplDX11_Init(g_pd3dDevice, g_pd3dDeviceContext); - - // Application main loop - while (true) - { - // Feed inputs to dear imgui, start new frame - ImGui_ImplDX11_NewFrame(); - ImGui_ImplWin32_NewFrame(); - ImGui::NewFrame(); - - // Any application code here - ImGui::Text("Hello, world!"); - - // Render dear imgui into screen - ImGui::Render(); - ImGui_ImplDX11_RenderDrawData(ImGui::GetDrawData()); - g_pSwapChain->Present(1, 0); - } - - // Shutdown - ImGui_ImplDX11_Shutdown(); - ImGui_ImplWin32_Shutdown(); - ImGui::DestroyContext(); - - EXHIBIT 2: IMPLEMENTING CUSTOM BACKEND / CUSTOM ENGINE - - // Application init: create a dear imgui context, setup some options, load fonts - ImGui::CreateContext(); - ImGuiIO& io = ImGui::GetIO(); - // TODO: Set optional io.ConfigFlags values, e.g. 'io.ConfigFlags |= ImGuiConfigFlags_NavEnableKeyboard' to enable keyboard controls. - // TODO: Fill optional fields of the io structure later. - // TODO: Load TTF/OTF fonts if you don't want to use the default font. - - // Build and load the texture atlas into a texture - // (In the examples/ app this is usually done within the ImGui_ImplXXX_Init() function from one of the demo Renderer) - int width, height; - unsigned char* pixels = nullptr; - io.Fonts->GetTexDataAsRGBA32(&pixels, &width, &height); - - // At this point you've got the texture data and you need to upload that to your graphic system: - // After we have created the texture, store its pointer/identifier (_in whichever format your engine uses_) in 'io.Fonts->TexID'. - // This will be passed back to your via the renderer. Basically ImTextureID == void*. Read FAQ for details about ImTextureID. - MyTexture* texture = MyEngine::CreateTextureFromMemoryPixels(pixels, width, height, TEXTURE_TYPE_RGBA32) - io.Fonts->SetTexID((void*)texture); - - // Application main loop - while (true) - { - // Setup low-level inputs, e.g. on Win32: calling GetKeyboardState(), or write to those fields from your Windows message handlers, etc. - // (In the examples/ app this is usually done within the ImGui_ImplXXX_NewFrame() function from one of the demo Platform Backends) - io.DeltaTime = 1.0f/60.0f; // set the time elapsed since the previous frame (in seconds) - io.DisplaySize.x = 1920.0f; // set the current display width - io.DisplaySize.y = 1280.0f; // set the current display height here - io.AddMousePosEvent(mouse_x, mouse_y); // update mouse position - io.AddMouseButtonEvent(0, mouse_b[0]); // update mouse button states - io.AddMouseButtonEvent(1, mouse_b[1]); // update mouse button states - - // Call NewFrame(), after this point you can use ImGui::* functions anytime - // (So you want to try calling NewFrame() as early as you can in your main loop to be able to use Dear ImGui everywhere) - ImGui::NewFrame(); - - // Most of your application code here - ImGui::Text("Hello, world!"); - MyGameUpdate(); // may use any Dear ImGui functions, e.g. ImGui::Begin("My window"); ImGui::Text("Hello, world!"); ImGui::End(); - MyGameRender(); // may use any Dear ImGui functions as well! - - // Render dear imgui, swap buffers - // (You want to try calling EndFrame/Render as late as you can, to be able to use Dear ImGui in your own game rendering code) - ImGui::EndFrame(); - ImGui::Render(); - ImDrawData* draw_data = ImGui::GetDrawData(); - MyImGuiRenderFunction(draw_data); - SwapBuffers(); - } - - // Shutdown - ImGui::DestroyContext(); - - To decide whether to dispatch mouse/keyboard inputs to Dear ImGui to the rest of your application, - you should read the 'io.WantCaptureMouse', 'io.WantCaptureKeyboard' and 'io.WantTextInput' flags! - Please read the FAQ and example applications for details about this! - - - HOW A SIMPLE RENDERING FUNCTION MAY LOOK LIKE - --------------------------------------------- - The backends in impl_impl_XXX.cpp files contain many working implementations of a rendering function. - - void MyImGuiRenderFunction(ImDrawData* draw_data) - { - // TODO: Setup render state: alpha-blending enabled, no face culling, no depth testing, scissor enabled - // TODO: Setup texture sampling state: sample with bilinear filtering (NOT point/nearest filtering). Use 'io.Fonts->Flags |= ImFontAtlasFlags_NoBakedLines;' to allow point/nearest filtering. - // TODO: Setup viewport covering draw_data->DisplayPos to draw_data->DisplayPos + draw_data->DisplaySize - // TODO: Setup orthographic projection matrix cover draw_data->DisplayPos to draw_data->DisplayPos + draw_data->DisplaySize - // TODO: Setup shader: vertex { float2 pos, float2 uv, u32 color }, fragment shader sample color from 1 texture, multiply by vertex color. - ImVec2 clip_off = draw_data->DisplayPos; - for (int n = 0; n < draw_data->CmdListsCount; n++) - { - const ImDrawList* cmd_list = draw_data->CmdLists[n]; - const ImDrawVert* vtx_buffer = cmd_list->VtxBuffer.Data; // vertex buffer generated by Dear ImGui - const ImDrawIdx* idx_buffer = cmd_list->IdxBuffer.Data; // index buffer generated by Dear ImGui - for (int cmd_i = 0; cmd_i < cmd_list->CmdBuffer.Size; cmd_i++) - { - const ImDrawCmd* pcmd = &cmd_list->CmdBuffer[cmd_i]; - if (pcmd->UserCallback) - { - pcmd->UserCallback(cmd_list, pcmd); - } - else - { - // Project scissor/clipping rectangles into framebuffer space - ImVec2 clip_min(pcmd->ClipRect.x - clip_off.x, pcmd->ClipRect.y - clip_off.y); - ImVec2 clip_max(pcmd->ClipRect.z - clip_off.x, pcmd->ClipRect.w - clip_off.y); - if (clip_max.x <= clip_min.x || clip_max.y <= clip_min.y) - continue; - - // We are using scissoring to clip some objects. All low-level graphics API should support it. - // - If your engine doesn't support scissoring yet, you may ignore this at first. You will get some small glitches - // (some elements visible outside their bounds) but you can fix that once everything else works! - // - Clipping coordinates are provided in imgui coordinates space: - // - For a given viewport, draw_data->DisplayPos == viewport->Pos and draw_data->DisplaySize == viewport->Size - // - In a single viewport application, draw_data->DisplayPos == (0,0) and draw_data->DisplaySize == io.DisplaySize, but always use GetMainViewport()->Pos/Size instead of hardcoding those values. - // - In the interest of supporting multi-viewport applications (see 'docking' branch on github), - // always subtract draw_data->DisplayPos from clipping bounds to convert them to your viewport space. - // - Note that pcmd->ClipRect contains Min+Max bounds. Some graphics API may use Min+Max, other may use Min+Size (size being Max-Min) - MyEngineSetScissor(clip_min.x, clip_min.y, clip_max.x, clip_max.y); - - // The texture for the draw call is specified by pcmd->GetTexID(). - // The vast majority of draw calls will use the Dear ImGui texture atlas, which value you have set yourself during initialization. - MyEngineBindTexture((MyTexture*)pcmd->GetTexID()); - - // Render 'pcmd->ElemCount/3' indexed triangles. - // By default the indices ImDrawIdx are 16-bit, you can change them to 32-bit in imconfig.h if your engine doesn't support 16-bit indices. - MyEngineDrawIndexedTriangles(pcmd->ElemCount, sizeof(ImDrawIdx) == 2 ? GL_UNSIGNED_SHORT : GL_UNSIGNED_INT, idx_buffer + pcmd->IdxOffset, vtx_buffer, pcmd->VtxOffset); - } - } - } - } - - - API BREAKING CHANGES - ==================== - - Occasionally introducing changes that are breaking the API. We try to make the breakage minor and easy to fix. - Below is a change-log of API breaking changes only. If you are using one of the functions listed, expect to have to fix some code. - When you are not sure about an old symbol or function name, try using the Search/Find function of your IDE to look for comments or references in all imgui files. - You can read releases logs https://github.com/ocornut/imgui/releases for more details. - -(Docking/Viewport Branch) - - 2023/XX/XX (1.XXXX) - when multi-viewports are enabled, all positions will be in your natural OS coordinates space. It means that: - - reference to hard-coded positions such as in SetNextWindowPos(ImVec2(0,0)) are probably not what you want anymore. - you may use GetMainViewport()->Pos to offset hard-coded positions, e.g. SetNextWindowPos(GetMainViewport()->Pos) - - likewise io.MousePos and GetMousePos() will use OS coordinates. - If you query mouse positions to interact with non-imgui coordinates you will need to offset them, e.g. subtract GetWindowViewport()->Pos. - - - 2023/09/27 (1.90.0) - io: removed io.MetricsActiveAllocations introduced in 1.63. Same as 'g.DebugMemAllocCount - g.DebugMemFreeCount' (still displayed in Metrics, unlikely to be accessed by end-user). - - 2023/09/26 (1.90.0) - debug tools: Renamed ShowStackToolWindow() ("Stack Tool") to ShowIDStackToolWindow() ("ID Stack Tool"), as earlier name was misleading. Kept inline redirection function. (#4631) - - 2023/09/15 (1.90.0) - ListBox, Combo: changed signature of "name getter" callback in old one-liner ListBox()/Combo() apis. kept inline redirection function (will obsolete). - - old: bool Combo(const char* label, int* current_item, bool (*getter)(void* user_data, int idx, const char** out_text), ...) - - new: bool Combo(const char* label, int* current_item, const char* (*getter)(void* user_data, int idx), ...); - - old: bool ListBox(const char* label, int* current_item, bool (*getting)(void* user_data, int idx, const char** out_text), ...); - - new: bool ListBox(const char* label, int* current_item, const char* (*getter)(void* user_data, int idx), ...); - - 2023/09/08 (1.90.0) - commented out obsolete redirecting functions: - - GetWindowContentRegionWidth() -> use GetWindowContentRegionMax().x - GetWindowContentRegionMin().x. Consider that generally 'GetContentRegionAvail().x' is more useful. - - ImDrawCornerFlags_XXX -> use ImDrawFlags_RoundCornersXXX flags. Read 1.82 Changelog for details + grep commented names in sources. - - commented out runtime support for hardcoded ~0 or 0x01..0x0F rounding flags values for AddRect()/AddRectFilled()/PathRect()/AddImageRounded() -> use ImDrawFlags_RoundCornersXXX flags. Read 1.82 Changelog for details - - 2023/08/25 (1.89.9) - clipper: Renamed IncludeRangeByIndices() (also called ForceDisplayRangeByIndices() before 1.89.6) to IncludeItemsByIndex(). Kept inline redirection function. Sorry! - - 2023/07/12 (1.89.8) - ImDrawData: CmdLists now owned, changed from ImDrawList** to ImVector. Majority of users shouldn't be affected, but you cannot compare to NULL nor reassign manually anymore. Instead use AddDrawList(). (#6406, #4879, #1878) - - 2023/06/28 (1.89.7) - overlapping items: obsoleted 'SetItemAllowOverlap()' (called after item) in favor of calling 'SetNextItemAllowOverlap()' (called before item). 'SetItemAllowOverlap()' didn't and couldn't work reliably since 1.89 (2022-11-15). - - 2023/06/28 (1.89.7) - overlapping items: renamed 'ImGuiTreeNodeFlags_AllowItemOverlap' to 'ImGuiTreeNodeFlags_AllowOverlap', 'ImGuiSelectableFlags_AllowItemOverlap' to 'ImGuiSelectableFlags_AllowOverlap'. Kept redirecting enums (will obsolete). - - 2023/06/28 (1.89.7) - overlapping items: IsItemHovered() now by default return false when querying an item using AllowOverlap mode which is being overlapped. Use ImGuiHoveredFlags_AllowWhenOverlappedByItem to revert to old behavior. - - 2023/06/28 (1.89.7) - overlapping items: Selectable and TreeNode don't allow overlap when active so overlapping widgets won't appear as hovered. While this fixes a common small visual issue, it also means that calling IsItemHovered() after a non-reactive elements - e.g. Text() - overlapping an active one may fail if you don't use IsItemHovered(ImGuiHoveredFlags_AllowWhenBlockedByActiveItem). (#6610) - - 2023/06/20 (1.89.7) - moved io.HoverDelayShort/io.HoverDelayNormal to style.HoverDelayShort/style.HoverDelayNormal. As the fields were added in 1.89 and expected to be left unchanged by most users, or only tweaked once during app initialization, we are exceptionally accepting the breakage. - - 2023/05/30 (1.89.6) - backends: renamed "imgui_impl_sdlrenderer.cpp" to "imgui_impl_sdlrenderer2.cpp" and "imgui_impl_sdlrenderer.h" to "imgui_impl_sdlrenderer2.h". This is in prevision for the future release of SDL3. - - 2023/05/22 (1.89.6) - listbox: commented out obsolete/redirecting functions that were marked obsolete more than two years ago: - - ListBoxHeader() -> use BeginListBox() (note how two variants of ListBoxHeader() existed. Check commented versions in imgui.h for reference) - - ListBoxFooter() -> use EndListBox() - - 2023/05/15 (1.89.6) - clipper: commented out obsolete redirection constructor 'ImGuiListClipper(int items_count, float items_height = -1.0f)' that was marked obsolete in 1.79. Use default constructor + clipper.Begin(). - - 2023/05/15 (1.89.6) - clipper: renamed ImGuiListClipper::ForceDisplayRangeByIndices() to ImGuiListClipper::IncludeRangeByIndices(). - - 2023/03/14 (1.89.4) - commented out redirecting enums/functions names that were marked obsolete two years ago: - - ImGuiSliderFlags_ClampOnInput -> use ImGuiSliderFlags_AlwaysClamp - - ImGuiInputTextFlags_AlwaysInsertMode -> use ImGuiInputTextFlags_AlwaysOverwrite - - ImDrawList::AddBezierCurve() -> use ImDrawList::AddBezierCubic() - - ImDrawList::PathBezierCurveTo() -> use ImDrawList::PathBezierCubicCurveTo() - - 2023/03/09 (1.89.4) - renamed PushAllowKeyboardFocus()/PopAllowKeyboardFocus() to PushTabStop()/PopTabStop(). Kept inline redirection functions (will obsolete). - - 2023/03/09 (1.89.4) - tooltips: Added 'bool' return value to BeginTooltip() for API consistency. Please only submit contents and call EndTooltip() if BeginTooltip() returns true. In reality the function will _currently_ always return true, but further changes down the line may change this, best to clarify API sooner. - - 2023/02/15 (1.89.4) - moved the optional "courtesy maths operators" implementation from imgui_internal.h in imgui.h. - Even though we encourage using your own maths types and operators by setting up IM_VEC2_CLASS_EXTRA, - it has been frequently requested by people to use our own. We had an opt-in define which was - previously fulfilled in imgui_internal.h. It is now fulfilled in imgui.h. (#6164) - - OK: #define IMGUI_DEFINE_MATH_OPERATORS / #include "imgui.h" / #include "imgui_internal.h" - - Error: #include "imgui.h" / #define IMGUI_DEFINE_MATH_OPERATORS / #include "imgui_internal.h" - - 2023/02/07 (1.89.3) - backends: renamed "imgui_impl_sdl.cpp" to "imgui_impl_sdl2.cpp" and "imgui_impl_sdl.h" to "imgui_impl_sdl2.h". (#6146) This is in prevision for the future release of SDL3. - - 2022/10/26 (1.89) - commented out redirecting OpenPopupContextItem() which was briefly the name of OpenPopupOnItemClick() from 1.77 to 1.79. - - 2022/10/12 (1.89) - removed runtime patching of invalid "%f"/"%0.f" format strings for DragInt()/SliderInt(). This was obsoleted in 1.61 (May 2018). See 1.61 changelog for details. - - 2022/09/26 (1.89) - renamed and merged keyboard modifiers key enums and flags into a same set. Kept inline redirection enums (will obsolete). - - ImGuiKey_ModCtrl and ImGuiModFlags_Ctrl -> ImGuiMod_Ctrl - - ImGuiKey_ModShift and ImGuiModFlags_Shift -> ImGuiMod_Shift - - ImGuiKey_ModAlt and ImGuiModFlags_Alt -> ImGuiMod_Alt - - ImGuiKey_ModSuper and ImGuiModFlags_Super -> ImGuiMod_Super - the ImGuiKey_ModXXX were introduced in 1.87 and mostly used by backends. - the ImGuiModFlags_XXX have been exposed in imgui.h but not really used by any public api only by third-party extensions. - exceptionally commenting out the older ImGuiKeyModFlags_XXX names ahead of obsolescence schedule to reduce confusion and because they were not meant to be used anyway. - - 2022/09/20 (1.89) - ImGuiKey is now a typed enum, allowing ImGuiKey_XXX symbols to be named in debuggers. - this will require uses of legacy backend-dependent indices to be casted, e.g. - - with imgui_impl_glfw: IsKeyPressed(GLFW_KEY_A) -> IsKeyPressed((ImGuiKey)GLFW_KEY_A); - - with imgui_impl_win32: IsKeyPressed('A') -> IsKeyPressed((ImGuiKey)'A') - - etc. However if you are upgrading code you might well use the better, backend-agnostic IsKeyPressed(ImGuiKey_A) now! - - 2022/09/12 (1.89) - removed the bizarre legacy default argument for 'TreePush(const void* ptr = NULL)', always pass a pointer value explicitly. NULL/nullptr is ok but require cast, e.g. TreePush((void*)nullptr); - - 2022/09/05 (1.89) - commented out redirecting functions/enums names that were marked obsolete in 1.77 and 1.78 (June 2020): - - DragScalar(), DragScalarN(), DragFloat(), DragFloat2(), DragFloat3(), DragFloat4(): For old signatures ending with (..., const char* format, float power = 1.0f) -> use (..., format ImGuiSliderFlags_Logarithmic) if power != 1.0f. - - SliderScalar(), SliderScalarN(), SliderFloat(), SliderFloat2(), SliderFloat3(), SliderFloat4(): For old signatures ending with (..., const char* format, float power = 1.0f) -> use (..., format ImGuiSliderFlags_Logarithmic) if power != 1.0f. - - BeginPopupContextWindow(const char*, ImGuiMouseButton, bool) -> use BeginPopupContextWindow(const char*, ImGuiPopupFlags) - - 2022/09/02 (1.89) - obsoleted using SetCursorPos()/SetCursorScreenPos() to extend parent window/cell boundaries. - this relates to when moving the cursor position beyond current boundaries WITHOUT submitting an item. - - previously this would make the window content size ~200x200: - Begin(...) + SetCursorScreenPos(GetCursorScreenPos() + ImVec2(200,200)) + End(); - - instead, please submit an item: - Begin(...) + SetCursorScreenPos(GetCursorScreenPos() + ImVec2(200,200)) + Dummy(ImVec2(0,0)) + End(); - - alternative: - Begin(...) + Dummy(ImVec2(200,200)) + End(); - - content size is now only extended when submitting an item! - - with '#define IMGUI_DISABLE_OBSOLETE_FUNCTIONS' this will now be detected and assert. - - without '#define IMGUI_DISABLE_OBSOLETE_FUNCTIONS' this will silently be fixed until we obsolete it. - - 2022/08/03 (1.89) - changed signature of ImageButton() function. Kept redirection function (will obsolete). - - added 'const char* str_id' parameter + removed 'int frame_padding = -1' parameter. - - old signature: bool ImageButton(ImTextureID tex_id, ImVec2 size, ImVec2 uv0 = ImVec2(0,0), ImVec2 uv1 = ImVec2(1,1), int frame_padding = -1, ImVec4 bg_col = ImVec4(0,0,0,0), ImVec4 tint_col = ImVec4(1,1,1,1)); - - used the ImTextureID value to create an ID. This was inconsistent with other functions, led to ID conflicts, and caused problems with engines using transient ImTextureID values. - - had a FramePadding override which was inconsistent with other functions and made the already-long signature even longer. - - new signature: bool ImageButton(const char* str_id, ImTextureID tex_id, ImVec2 size, ImVec2 uv0 = ImVec2(0,0), ImVec2 uv1 = ImVec2(1,1), ImVec4 bg_col = ImVec4(0,0,0,0), ImVec4 tint_col = ImVec4(1,1,1,1)); - - requires an explicit identifier. You may still use e.g. PushID() calls and then pass an empty identifier. - - always uses style.FramePadding for padding, to be consistent with other buttons. You may use PushStyleVar() to alter this. - - 2022/07/08 (1.89) - inputs: removed io.NavInputs[] and ImGuiNavInput enum (following 1.87 changes). - - Official backends from 1.87+ -> no issue. - - Official backends from 1.60 to 1.86 -> will build and convert gamepad inputs, unless IMGUI_DISABLE_OBSOLETE_KEYIO is defined. Need updating! - - Custom backends not writing to io.NavInputs[] -> no issue. - - Custom backends writing to io.NavInputs[] -> will build and convert gamepad inputs, unless IMGUI_DISABLE_OBSOLETE_KEYIO is defined. Need fixing! - - TL;DR: Backends should call io.AddKeyEvent()/io.AddKeyAnalogEvent() with ImGuiKey_GamepadXXX values instead of filling io.NavInput[]. - - 2022/06/15 (1.88) - renamed IMGUI_DISABLE_METRICS_WINDOW to IMGUI_DISABLE_DEBUG_TOOLS for correctness. kept support for old define (will obsolete). - - 2022/05/03 (1.88) - backends: osx: removed ImGui_ImplOSX_HandleEvent() from backend API in favor of backend automatically handling event capture. All ImGui_ImplOSX_HandleEvent() calls should be removed as they are now unnecessary. - - 2022/04/05 (1.88) - inputs: renamed ImGuiKeyModFlags to ImGuiModFlags. Kept inline redirection enums (will obsolete). This was never used in public API functions but technically present in imgui.h and ImGuiIO. - - 2022/01/20 (1.87) - inputs: reworded gamepad IO. - - Backend writing to io.NavInputs[] -> backend should call io.AddKeyEvent()/io.AddKeyAnalogEvent() with ImGuiKey_GamepadXXX values. - - 2022/01/19 (1.87) - sliders, drags: removed support for legacy arithmetic operators (+,+-,*,/) when inputing text. This doesn't break any api/code but a feature that used to be accessible by end-users (which seemingly no one used). - - 2022/01/17 (1.87) - inputs: reworked mouse IO. - - Backend writing to io.MousePos -> backend should call io.AddMousePosEvent() - - Backend writing to io.MouseDown[] -> backend should call io.AddMouseButtonEvent() - - Backend writing to io.MouseWheel -> backend should call io.AddMouseWheelEvent() - - Backend writing to io.MouseHoveredViewport -> backend should call io.AddMouseViewportEvent() [Docking branch w/ multi-viewports only] - note: for all calls to IO new functions, the Dear ImGui context should be bound/current. - read https://github.com/ocornut/imgui/issues/4921 for details. - - 2022/01/10 (1.87) - inputs: reworked keyboard IO. Removed io.KeyMap[], io.KeysDown[] in favor of calling io.AddKeyEvent(). Removed GetKeyIndex(), now unecessary. All IsKeyXXX() functions now take ImGuiKey values. All features are still functional until IMGUI_DISABLE_OBSOLETE_KEYIO is defined. Read Changelog and Release Notes for details. - - IsKeyPressed(MY_NATIVE_KEY_XXX) -> use IsKeyPressed(ImGuiKey_XXX) - - IsKeyPressed(GetKeyIndex(ImGuiKey_XXX)) -> use IsKeyPressed(ImGuiKey_XXX) - - Backend writing to io.KeyMap[],io.KeysDown[] -> backend should call io.AddKeyEvent() (+ call io.SetKeyEventNativeData() if you want legacy user code to stil function with legacy key codes). - - Backend writing to io.KeyCtrl, io.KeyShift.. -> backend should call io.AddKeyEvent() with ImGuiMod_XXX values. *IF YOU PULLED CODE BETWEEN 2021/01/10 and 2021/01/27: We used to have a io.AddKeyModsEvent() function which was now replaced by io.AddKeyEvent() with ImGuiMod_XXX values.* - - one case won't work with backward compatibility: if your custom backend used ImGuiKey as mock native indices (e.g. "io.KeyMap[ImGuiKey_A] = ImGuiKey_A") because those values are now larger than the legacy KeyDown[] array. Will assert. - - inputs: added ImGuiKey_ModCtrl/ImGuiKey_ModShift/ImGuiKey_ModAlt/ImGuiKey_ModSuper values to submit keyboard modifiers using io.AddKeyEvent(), instead of writing directly to io.KeyCtrl, io.KeyShift, io.KeyAlt, io.KeySuper. - - 2022/01/05 (1.87) - inputs: renamed ImGuiKey_KeyPadEnter to ImGuiKey_KeypadEnter to align with new symbols. Kept redirection enum. - - 2022/01/05 (1.87) - removed io.ImeSetInputScreenPosFn() in favor of more flexible io.SetPlatformImeDataFn(). Removed 'void* io.ImeWindowHandle' in favor of writing to 'void* ImGuiViewport::PlatformHandleRaw'. - - 2022/01/01 (1.87) - commented out redirecting functions/enums names that were marked obsolete in 1.69, 1.70, 1.71, 1.72 (March-July 2019) - - ImGui::SetNextTreeNodeOpen() -> use ImGui::SetNextItemOpen() - - ImGui::GetContentRegionAvailWidth() -> use ImGui::GetContentRegionAvail().x - - ImGui::TreeAdvanceToLabelPos() -> use ImGui::SetCursorPosX(ImGui::GetCursorPosX() + ImGui::GetTreeNodeToLabelSpacing()); - - ImFontAtlas::CustomRect -> use ImFontAtlasCustomRect - - ImGuiColorEditFlags_RGB/HSV/HEX -> use ImGuiColorEditFlags_DisplayRGB/HSV/Hex - - 2021/12/20 (1.86) - backends: removed obsolete Marmalade backend (imgui_impl_marmalade.cpp) + example. Find last supported version at https://github.com/ocornut/imgui/wiki/Bindings - - 2021/11/04 (1.86) - removed CalcListClipping() function. Prefer using ImGuiListClipper which can return non-contiguous ranges. Please open an issue if you think you really need this function. - - 2021/08/23 (1.85) - removed GetWindowContentRegionWidth() function. keep inline redirection helper. can use 'GetWindowContentRegionMax().x - GetWindowContentRegionMin().x' instead for generally 'GetContentRegionAvail().x' is more useful. - - 2021/07/26 (1.84) - commented out redirecting functions/enums names that were marked obsolete in 1.67 and 1.69 (March 2019): - - ImGui::GetOverlayDrawList() -> use ImGui::GetForegroundDrawList() - - ImFont::GlyphRangesBuilder -> use ImFontGlyphRangesBuilder - - 2021/05/19 (1.83) - backends: obsoleted direct access to ImDrawCmd::TextureId in favor of calling ImDrawCmd::GetTexID(). - - if you are using official backends from the source tree: you have nothing to do. - - if you have copied old backend code or using your own: change access to draw_cmd->TextureId to draw_cmd->GetTexID(). - - 2021/03/12 (1.82) - upgraded ImDrawList::AddRect(), AddRectFilled(), PathRect() to use ImDrawFlags instead of ImDrawCornersFlags. - - ImDrawCornerFlags_TopLeft -> use ImDrawFlags_RoundCornersTopLeft - - ImDrawCornerFlags_BotRight -> use ImDrawFlags_RoundCornersBottomRight - - ImDrawCornerFlags_None -> use ImDrawFlags_RoundCornersNone etc. - flags now sanely defaults to 0 instead of 0x0F, consistent with all other flags in the API. - breaking: the default with rounding > 0.0f is now "round all corners" vs old implicit "round no corners": - - rounding == 0.0f + flags == 0 --> meant no rounding --> unchanged (common use) - - rounding > 0.0f + flags != 0 --> meant rounding --> unchanged (common use) - - rounding == 0.0f + flags != 0 --> meant no rounding --> unchanged (unlikely use) - - rounding > 0.0f + flags == 0 --> meant no rounding --> BREAKING (unlikely use): will now round all corners --> use ImDrawFlags_RoundCornersNone or rounding == 0.0f. - this ONLY matters for hard coded use of 0 + rounding > 0.0f. Use of named ImDrawFlags_RoundCornersNone (new) or ImDrawCornerFlags_None (old) are ok. - the old ImDrawCornersFlags used awkward default values of ~0 or 0xF (4 lower bits set) to signify "round all corners" and we sometimes encouraged using them as shortcuts. - legacy path still support use of hard coded ~0 or any value from 0x1 or 0xF. They will behave the same with legacy paths enabled (will assert otherwise). - - 2021/03/11 (1.82) - removed redirecting functions/enums names that were marked obsolete in 1.66 (September 2018): - - ImGui::SetScrollHere() -> use ImGui::SetScrollHereY() - - 2021/03/11 (1.82) - clarified that ImDrawList::PathArcTo(), ImDrawList::PathArcToFast() won't render with radius < 0.0f. Previously it sorts of accidentally worked but would generally lead to counter-clockwise paths and have an effect on anti-aliasing. - - 2021/03/10 (1.82) - upgraded ImDrawList::AddPolyline() and PathStroke() "bool closed" parameter to "ImDrawFlags flags". The matching ImDrawFlags_Closed value is guaranteed to always stay == 1 in the future. - - 2021/02/22 (1.82) - (*undone in 1.84*) win32+mingw: Re-enabled IME functions by default even under MinGW. In July 2016, issue #738 had me incorrectly disable those default functions for MinGW. MinGW users should: either link with -limm32, either set their imconfig file with '#define IMGUI_DISABLE_WIN32_DEFAULT_IME_FUNCTIONS'. - - 2021/02/17 (1.82) - renamed rarely used style.CircleSegmentMaxError (old default = 1.60f) to style.CircleTessellationMaxError (new default = 0.30f) as the meaning of the value changed. - - 2021/02/03 (1.81) - renamed ListBoxHeader(const char* label, ImVec2 size) to BeginListBox(). Kept inline redirection function (will obsolete). - - removed ListBoxHeader(const char* label, int items_count, int height_in_items = -1) in favor of specifying size. Kept inline redirection function (will obsolete). - - renamed ListBoxFooter() to EndListBox(). Kept inline redirection function (will obsolete). - - 2021/01/26 (1.81) - removed ImGuiFreeType::BuildFontAtlas(). Kept inline redirection function. Prefer using '#define IMGUI_ENABLE_FREETYPE', but there's a runtime selection path available too. The shared extra flags parameters (very rarely used) are now stored in ImFontAtlas::FontBuilderFlags. - - renamed ImFontConfig::RasterizerFlags (used by FreeType) to ImFontConfig::FontBuilderFlags. - - renamed ImGuiFreeType::XXX flags to ImGuiFreeTypeBuilderFlags_XXX for consistency with other API. - - 2020/10/12 (1.80) - removed redirecting functions/enums that were marked obsolete in 1.63 (August 2018): - - ImGui::IsItemDeactivatedAfterChange() -> use ImGui::IsItemDeactivatedAfterEdit(). - - ImGuiCol_ModalWindowDarkening -> use ImGuiCol_ModalWindowDimBg - - ImGuiInputTextCallback -> use ImGuiTextEditCallback - - ImGuiInputTextCallbackData -> use ImGuiTextEditCallbackData - - 2020/12/21 (1.80) - renamed ImDrawList::AddBezierCurve() to AddBezierCubic(), and PathBezierCurveTo() to PathBezierCubicCurveTo(). Kept inline redirection function (will obsolete). - - 2020/12/04 (1.80) - added imgui_tables.cpp file! Manually constructed project files will need the new file added! - - 2020/11/18 (1.80) - renamed undocumented/internals ImGuiColumnsFlags_* to ImGuiOldColumnFlags_* in prevision of incoming Tables API. - - 2020/11/03 (1.80) - renamed io.ConfigWindowsMemoryCompactTimer to io.ConfigMemoryCompactTimer as the feature will apply to other data structures - - 2020/10/14 (1.80) - backends: moved all backends files (imgui_impl_XXXX.cpp, imgui_impl_XXXX.h) from examples/ to backends/. - - 2020/10/12 (1.80) - removed redirecting functions/enums that were marked obsolete in 1.60 (April 2018): - - io.RenderDrawListsFn pointer -> use ImGui::GetDrawData() value and call the render function of your backend - - ImGui::IsAnyWindowFocused() -> use ImGui::IsWindowFocused(ImGuiFocusedFlags_AnyWindow) - - ImGui::IsAnyWindowHovered() -> use ImGui::IsWindowHovered(ImGuiHoveredFlags_AnyWindow) - - ImGuiStyleVar_Count_ -> use ImGuiStyleVar_COUNT - - ImGuiMouseCursor_Count_ -> use ImGuiMouseCursor_COUNT - - removed redirecting functions names that were marked obsolete in 1.61 (May 2018): - - InputFloat (... int decimal_precision ...) -> use InputFloat (... const char* format ...) with format = "%.Xf" where X is your value for decimal_precision. - - same for InputFloat2()/InputFloat3()/InputFloat4() variants taking a `int decimal_precision` parameter. - - 2020/10/05 (1.79) - removed ImGuiListClipper: Renamed constructor parameters which created an ambiguous alternative to using the ImGuiListClipper::Begin() function, with misleading edge cases (note: imgui_memory_editor <0.40 from imgui_club/ used this old clipper API. Update your copy if needed). - - 2020/09/25 (1.79) - renamed ImGuiSliderFlags_ClampOnInput to ImGuiSliderFlags_AlwaysClamp. Kept redirection enum (will obsolete sooner because previous name was added recently). - - 2020/09/25 (1.79) - renamed style.TabMinWidthForUnselectedCloseButton to style.TabMinWidthForCloseButton. - - 2020/09/21 (1.79) - renamed OpenPopupContextItem() back to OpenPopupOnItemClick(), reverting the change from 1.77. For varieties of reason this is more self-explanatory. - - 2020/09/21 (1.79) - removed return value from OpenPopupOnItemClick() - returned true on mouse release on an item - because it is inconsistent with other popup APIs and makes others misleading. It's also and unnecessary: you can use IsWindowAppearing() after BeginPopup() for a similar result. - - 2020/09/17 (1.79) - removed ImFont::DisplayOffset in favor of ImFontConfig::GlyphOffset. DisplayOffset was applied after scaling and not very meaningful/useful outside of being needed by the default ProggyClean font. If you scaled this value after calling AddFontDefault(), this is now done automatically. It was also getting in the way of better font scaling, so let's get rid of it now! - - 2020/08/17 (1.78) - obsoleted use of the trailing 'float power=1.0f' parameter for DragFloat(), DragFloat2(), DragFloat3(), DragFloat4(), DragFloatRange2(), DragScalar(), DragScalarN(), SliderFloat(), SliderFloat2(), SliderFloat3(), SliderFloat4(), SliderScalar(), SliderScalarN(), VSliderFloat() and VSliderScalar(). - replaced the 'float power=1.0f' argument with integer-based flags defaulting to 0 (as with all our flags). - worked out a backward-compatibility scheme so hopefully most C++ codebase should not be affected. in short, when calling those functions: - - if you omitted the 'power' parameter (likely!), you are not affected. - - if you set the 'power' parameter to 1.0f (same as previous default value): 1/ your compiler may warn on float>int conversion, 2/ everything else will work. 3/ you can replace the 1.0f value with 0 to fix the warning, and be technically correct. - - if you set the 'power' parameter to >1.0f (to enable non-linear editing): 1/ your compiler may warn on float>int conversion, 2/ code will assert at runtime, 3/ in case asserts are disabled, the code will not crash and enable the _Logarithmic flag. 4/ you can replace the >1.0f value with ImGuiSliderFlags_Logarithmic to fix the warning/assert and get a _similar_ effect as previous uses of power >1.0f. - see https://github.com/ocornut/imgui/issues/3361 for all details. - kept inline redirection functions (will obsolete) apart for: DragFloatRange2(), VSliderFloat(), VSliderScalar(). For those three the 'float power=1.0f' version was removed directly as they were most unlikely ever used. - for shared code, you can version check at compile-time with `#if IMGUI_VERSION_NUM >= 17704`. - - obsoleted use of v_min > v_max in DragInt, DragFloat, DragScalar to lock edits (introduced in 1.73, was not demoed nor documented very), will be replaced by a more generic ReadOnly feature. You may use the ImGuiSliderFlags_ReadOnly internal flag in the meantime. - - 2020/06/23 (1.77) - removed BeginPopupContextWindow(const char*, int mouse_button, bool also_over_items) in favor of BeginPopupContextWindow(const char*, ImGuiPopupFlags flags) with ImGuiPopupFlags_NoOverItems. - - 2020/06/15 (1.77) - renamed OpenPopupOnItemClick() to OpenPopupContextItem(). Kept inline redirection function (will obsolete). [NOTE: THIS WAS REVERTED IN 1.79] - - 2020/06/15 (1.77) - removed CalcItemRectClosestPoint() entry point which was made obsolete and asserting in December 2017. - - 2020/04/23 (1.77) - removed unnecessary ID (first arg) of ImFontAtlas::AddCustomRectRegular(). - - 2020/01/22 (1.75) - ImDrawList::AddCircle()/AddCircleFilled() functions don't accept negative radius any more. - - 2019/12/17 (1.75) - [undid this change in 1.76] made Columns() limited to 64 columns by asserting above that limit. While the current code technically supports it, future code may not so we're putting the restriction ahead. - - 2019/12/13 (1.75) - [imgui_internal.h] changed ImRect() default constructor initializes all fields to 0.0f instead of (FLT_MAX,FLT_MAX,-FLT_MAX,-FLT_MAX). If you used ImRect::Add() to create bounding boxes by adding multiple points into it, you may need to fix your initial value. - - 2019/12/08 (1.75) - removed redirecting functions/enums that were marked obsolete in 1.53 (December 2017): - - ShowTestWindow() -> use ShowDemoWindow() - - IsRootWindowFocused() -> use IsWindowFocused(ImGuiFocusedFlags_RootWindow) - - IsRootWindowOrAnyChildFocused() -> use IsWindowFocused(ImGuiFocusedFlags_RootAndChildWindows) - - SetNextWindowContentWidth(w) -> use SetNextWindowContentSize(ImVec2(w, 0.0f) - - GetItemsLineHeightWithSpacing() -> use GetFrameHeightWithSpacing() - - ImGuiCol_ChildWindowBg -> use ImGuiCol_ChildBg - - ImGuiStyleVar_ChildWindowRounding -> use ImGuiStyleVar_ChildRounding - - ImGuiTreeNodeFlags_AllowOverlapMode -> use ImGuiTreeNodeFlags_AllowItemOverlap - - IMGUI_DISABLE_TEST_WINDOWS -> use IMGUI_DISABLE_DEMO_WINDOWS - - 2019/12/08 (1.75) - obsoleted calling ImDrawList::PrimReserve() with a negative count (which was vaguely documented and rarely if ever used). Instead, we added an explicit PrimUnreserve() API. - - 2019/12/06 (1.75) - removed implicit default parameter to IsMouseDragging(int button = 0) to be consistent with other mouse functions (none of the other functions have it). - - 2019/11/21 (1.74) - ImFontAtlas::AddCustomRectRegular() now requires an ID larger than 0x110000 (instead of 0x10000) to conform with supporting Unicode planes 1-16 in a future update. ID below 0x110000 will now assert. - - 2019/11/19 (1.74) - renamed IMGUI_DISABLE_FORMAT_STRING_FUNCTIONS to IMGUI_DISABLE_DEFAULT_FORMAT_FUNCTIONS for consistency. - - 2019/11/19 (1.74) - renamed IMGUI_DISABLE_MATH_FUNCTIONS to IMGUI_DISABLE_DEFAULT_MATH_FUNCTIONS for consistency. - - 2019/10/22 (1.74) - removed redirecting functions/enums that were marked obsolete in 1.52 (October 2017): - - Begin() [old 5 args version] -> use Begin() [3 args], use SetNextWindowSize() SetNextWindowBgAlpha() if needed - - IsRootWindowOrAnyChildHovered() -> use IsWindowHovered(ImGuiHoveredFlags_RootAndChildWindows) - - AlignFirstTextHeightToWidgets() -> use AlignTextToFramePadding() - - SetNextWindowPosCenter() -> use SetNextWindowPos() with a pivot of (0.5f, 0.5f) - - ImFont::Glyph -> use ImFontGlyph - - 2019/10/14 (1.74) - inputs: Fixed a miscalculation in the keyboard/mouse "typematic" repeat delay/rate calculation, used by keys and e.g. repeating mouse buttons as well as the GetKeyPressedAmount() function. - if you were using a non-default value for io.KeyRepeatRate (previous default was 0.250), you can add +io.KeyRepeatDelay to it to compensate for the fix. - The function was triggering on: 0.0 and (delay+rate*N) where (N>=1). Fixed formula responds to (N>=0). Effectively it made io.KeyRepeatRate behave like it was set to (io.KeyRepeatRate + io.KeyRepeatDelay). - If you never altered io.KeyRepeatRate nor used GetKeyPressedAmount() this won't affect you. - - 2019/07/15 (1.72) - removed TreeAdvanceToLabelPos() which is rarely used and only does SetCursorPosX(GetCursorPosX() + GetTreeNodeToLabelSpacing()). Kept redirection function (will obsolete). - - 2019/07/12 (1.72) - renamed ImFontAtlas::CustomRect to ImFontAtlasCustomRect. Kept redirection typedef (will obsolete). - - 2019/06/14 (1.72) - removed redirecting functions/enums names that were marked obsolete in 1.51 (June 2017): ImGuiCol_Column*, ImGuiSetCond_*, IsItemHoveredRect(), IsPosHoveringAnyWindow(), IsMouseHoveringAnyWindow(), IsMouseHoveringWindow(), IMGUI_ONCE_UPON_A_FRAME. Grep this log for details and new names, or see how they were implemented until 1.71. - - 2019/06/07 (1.71) - rendering of child window outer decorations (bg color, border, scrollbars) is now performed as part of the parent window. If you have - overlapping child windows in a same parent, and relied on their relative z-order to be mapped to their submission order, this will affect your rendering. - This optimization is disabled if the parent window has no visual output, because it appears to be the most common situation leading to the creation of overlapping child windows. - Please reach out if you are affected. - - 2019/05/13 (1.71) - renamed SetNextTreeNodeOpen() to SetNextItemOpen(). Kept inline redirection function (will obsolete). - - 2019/05/11 (1.71) - changed io.AddInputCharacter(unsigned short c) signature to io.AddInputCharacter(unsigned int c). - - 2019/04/29 (1.70) - improved ImDrawList thick strokes (>1.0f) preserving correct thickness up to 90 degrees angles (e.g. rectangles). If you have custom rendering using thick lines, they will appear thicker now. - - 2019/04/29 (1.70) - removed GetContentRegionAvailWidth(), use GetContentRegionAvail().x instead. Kept inline redirection function (will obsolete). - - 2019/03/04 (1.69) - renamed GetOverlayDrawList() to GetForegroundDrawList(). Kept redirection function (will obsolete). - - 2019/02/26 (1.69) - renamed ImGuiColorEditFlags_RGB/ImGuiColorEditFlags_HSV/ImGuiColorEditFlags_HEX to ImGuiColorEditFlags_DisplayRGB/ImGuiColorEditFlags_DisplayHSV/ImGuiColorEditFlags_DisplayHex. Kept redirection enums (will obsolete). - - 2019/02/14 (1.68) - made it illegal/assert when io.DisplayTime == 0.0f (with an exception for the first frame). If for some reason your time step calculation gives you a zero value, replace it with an arbitrarily small value! - - 2019/02/01 (1.68) - removed io.DisplayVisibleMin/DisplayVisibleMax (which were marked obsolete and removed from viewport/docking branch already). - - 2019/01/06 (1.67) - renamed io.InputCharacters[], marked internal as was always intended. Please don't access directly, and use AddInputCharacter() instead! - - 2019/01/06 (1.67) - renamed ImFontAtlas::GlyphRangesBuilder to ImFontGlyphRangesBuilder. Kept redirection typedef (will obsolete). - - 2018/12/20 (1.67) - made it illegal to call Begin("") with an empty string. This somehow half-worked before but had various undesirable side-effects. - - 2018/12/10 (1.67) - renamed io.ConfigResizeWindowsFromEdges to io.ConfigWindowsResizeFromEdges as we are doing a large pass on configuration flags. - - 2018/10/12 (1.66) - renamed misc/stl/imgui_stl.* to misc/cpp/imgui_stdlib.* in prevision for other C++ helper files. - - 2018/09/28 (1.66) - renamed SetScrollHere() to SetScrollHereY(). Kept redirection function (will obsolete). - - 2018/09/06 (1.65) - renamed stb_truetype.h to imstb_truetype.h, stb_textedit.h to imstb_textedit.h, and stb_rect_pack.h to imstb_rectpack.h. - If you were conveniently using the imgui copy of those STB headers in your project you will have to update your include paths. - - 2018/09/05 (1.65) - renamed io.OptCursorBlink/io.ConfigCursorBlink to io.ConfigInputTextCursorBlink. (#1427) - - 2018/08/31 (1.64) - added imgui_widgets.cpp file, extracted and moved widgets code out of imgui.cpp into imgui_widgets.cpp. Re-ordered some of the code remaining in imgui.cpp. - NONE OF THE FUNCTIONS HAVE CHANGED. THE CODE IS SEMANTICALLY 100% IDENTICAL, BUT _EVERY_ FUNCTION HAS BEEN MOVED. - Because of this, any local modifications to imgui.cpp will likely conflict when you update. Read docs/CHANGELOG.txt for suggestions. - - 2018/08/22 (1.63) - renamed IsItemDeactivatedAfterChange() to IsItemDeactivatedAfterEdit() for consistency with new IsItemEdited() API. Kept redirection function (will obsolete soonish as IsItemDeactivatedAfterChange() is very recent). - - 2018/08/21 (1.63) - renamed ImGuiTextEditCallback to ImGuiInputTextCallback, ImGuiTextEditCallbackData to ImGuiInputTextCallbackData for consistency. Kept redirection types (will obsolete). - - 2018/08/21 (1.63) - removed ImGuiInputTextCallbackData::ReadOnly since it is a duplication of (ImGuiInputTextCallbackData::Flags & ImGuiInputTextFlags_ReadOnly). - - 2018/08/01 (1.63) - removed per-window ImGuiWindowFlags_ResizeFromAnySide beta flag in favor of a global io.ConfigResizeWindowsFromEdges [update 1.67 renamed to ConfigWindowsResizeFromEdges] to enable the feature. - - 2018/08/01 (1.63) - renamed io.OptCursorBlink to io.ConfigCursorBlink [-> io.ConfigInputTextCursorBlink in 1.65], io.OptMacOSXBehaviors to ConfigMacOSXBehaviors for consistency. - - 2018/07/22 (1.63) - changed ImGui::GetTime() return value from float to double to avoid accumulating floating point imprecisions over time. - - 2018/07/08 (1.63) - style: renamed ImGuiCol_ModalWindowDarkening to ImGuiCol_ModalWindowDimBg for consistency with other features. Kept redirection enum (will obsolete). - - 2018/06/08 (1.62) - examples: the imgui_impl_XXX files have been split to separate platform (Win32, GLFW, SDL2, etc.) from renderer (DX11, OpenGL, Vulkan, etc.). - old backends will still work as is, however prefer using the separated backends as they will be updated to support multi-viewports. - when adopting new backends follow the main.cpp code of your preferred examples/ folder to know which functions to call. - in particular, note that old backends called ImGui::NewFrame() at the end of their ImGui_ImplXXXX_NewFrame() function. - - 2018/06/06 (1.62) - renamed GetGlyphRangesChinese() to GetGlyphRangesChineseFull() to distinguish other variants and discourage using the full set. - - 2018/06/06 (1.62) - TreeNodeEx()/TreeNodeBehavior(): the ImGuiTreeNodeFlags_CollapsingHeader helper now include the ImGuiTreeNodeFlags_NoTreePushOnOpen flag. See Changelog for details. - - 2018/05/03 (1.61) - DragInt(): the default compile-time format string has been changed from "%.0f" to "%d", as we are not using integers internally any more. - If you used DragInt() with custom format strings, make sure you change them to use %d or an integer-compatible format. - To honor backward-compatibility, the DragInt() code will currently parse and modify format strings to replace %*f with %d, giving time to users to upgrade their code. - If you have IMGUI_DISABLE_OBSOLETE_FUNCTIONS enabled, the code will instead assert! You may run a reg-exp search on your codebase for e.g. "DragInt.*%f" to help you find them. - - 2018/04/28 (1.61) - obsoleted InputFloat() functions taking an optional "int decimal_precision" in favor of an equivalent and more flexible "const char* format", - consistent with other functions. Kept redirection functions (will obsolete). - - 2018/04/09 (1.61) - IM_DELETE() helper function added in 1.60 doesn't clear the input _pointer_ reference, more consistent with expectation and allows passing r-value. - - 2018/03/20 (1.60) - renamed io.WantMoveMouse to io.WantSetMousePos for consistency and ease of understanding (was added in 1.52, _not_ used by core and only honored by some backend ahead of merging the Nav branch). - - 2018/03/12 (1.60) - removed ImGuiCol_CloseButton, ImGuiCol_CloseButtonActive, ImGuiCol_CloseButtonHovered as the closing cross uses regular button colors now. - - 2018/03/08 (1.60) - changed ImFont::DisplayOffset.y to default to 0 instead of +1. Fixed rounding of Ascent/Descent to match TrueType renderer. If you were adding or subtracting to ImFont::DisplayOffset check if your fonts are correctly aligned vertically. - - 2018/03/03 (1.60) - renamed ImGuiStyleVar_Count_ to ImGuiStyleVar_COUNT and ImGuiMouseCursor_Count_ to ImGuiMouseCursor_COUNT for consistency with other public enums. - - 2018/02/18 (1.60) - BeginDragDropSource(): temporarily removed the optional mouse_button=0 parameter because it is not really usable in many situations at the moment. - - 2018/02/16 (1.60) - obsoleted the io.RenderDrawListsFn callback, you can call your graphics engine render function after ImGui::Render(). Use ImGui::GetDrawData() to retrieve the ImDrawData* to display. - - 2018/02/07 (1.60) - reorganized context handling to be more explicit, - - YOU NOW NEED TO CALL ImGui::CreateContext() AT THE BEGINNING OF YOUR APP, AND CALL ImGui::DestroyContext() AT THE END. - - removed Shutdown() function, as DestroyContext() serve this purpose. - - you may pass a ImFontAtlas* pointer to CreateContext() to share a font atlas between contexts. Otherwise CreateContext() will create its own font atlas instance. - - removed allocator parameters from CreateContext(), they are now setup with SetAllocatorFunctions(), and shared by all contexts. - - removed the default global context and font atlas instance, which were confusing for users of DLL reloading and users of multiple contexts. - - 2018/01/31 (1.60) - moved sample TTF files from extra_fonts/ to misc/fonts/. If you loaded files directly from the imgui repo you may need to update your paths. - - 2018/01/11 (1.60) - obsoleted IsAnyWindowHovered() in favor of IsWindowHovered(ImGuiHoveredFlags_AnyWindow). Kept redirection function (will obsolete). - - 2018/01/11 (1.60) - obsoleted IsAnyWindowFocused() in favor of IsWindowFocused(ImGuiFocusedFlags_AnyWindow). Kept redirection function (will obsolete). - - 2018/01/03 (1.60) - renamed ImGuiSizeConstraintCallback to ImGuiSizeCallback, ImGuiSizeConstraintCallbackData to ImGuiSizeCallbackData. - - 2017/12/29 (1.60) - removed CalcItemRectClosestPoint() which was weird and not really used by anyone except demo code. If you need it it's easy to replicate on your side. - - 2017/12/24 (1.53) - renamed the emblematic ShowTestWindow() function to ShowDemoWindow(). Kept redirection function (will obsolete). - - 2017/12/21 (1.53) - ImDrawList: renamed style.AntiAliasedShapes to style.AntiAliasedFill for consistency and as a way to explicitly break code that manipulate those flag at runtime. You can now manipulate ImDrawList::Flags - - 2017/12/21 (1.53) - ImDrawList: removed 'bool anti_aliased = true' final parameter of ImDrawList::AddPolyline() and ImDrawList::AddConvexPolyFilled(). Prefer manipulating ImDrawList::Flags if you need to toggle them during the frame. - - 2017/12/14 (1.53) - using the ImGuiWindowFlags_NoScrollWithMouse flag on a child window forwards the mouse wheel event to the parent window, unless either ImGuiWindowFlags_NoInputs or ImGuiWindowFlags_NoScrollbar are also set. - - 2017/12/13 (1.53) - renamed GetItemsLineHeightWithSpacing() to GetFrameHeightWithSpacing(). Kept redirection function (will obsolete). - - 2017/12/13 (1.53) - obsoleted IsRootWindowFocused() in favor of using IsWindowFocused(ImGuiFocusedFlags_RootWindow). Kept redirection function (will obsolete). - - obsoleted IsRootWindowOrAnyChildFocused() in favor of using IsWindowFocused(ImGuiFocusedFlags_RootAndChildWindows). Kept redirection function (will obsolete). - - 2017/12/12 (1.53) - renamed ImGuiTreeNodeFlags_AllowOverlapMode to ImGuiTreeNodeFlags_AllowItemOverlap. Kept redirection enum (will obsolete). - - 2017/12/10 (1.53) - removed SetNextWindowContentWidth(), prefer using SetNextWindowContentSize(). Kept redirection function (will obsolete). - - 2017/11/27 (1.53) - renamed ImGuiTextBuffer::append() helper to appendf(), appendv() to appendfv(). If you copied the 'Log' demo in your code, it uses appendv() so that needs to be renamed. - - 2017/11/18 (1.53) - Style, Begin: removed ImGuiWindowFlags_ShowBorders window flag. Borders are now fully set up in the ImGuiStyle structure (see e.g. style.FrameBorderSize, style.WindowBorderSize). Use ImGui::ShowStyleEditor() to look them up. - Please note that the style system will keep evolving (hopefully stabilizing in Q1 2018), and so custom styles will probably subtly break over time. It is recommended you use the StyleColorsClassic(), StyleColorsDark(), StyleColorsLight() functions. - - 2017/11/18 (1.53) - Style: removed ImGuiCol_ComboBg in favor of combo boxes using ImGuiCol_PopupBg for consistency. - - 2017/11/18 (1.53) - Style: renamed ImGuiCol_ChildWindowBg to ImGuiCol_ChildBg. - - 2017/11/18 (1.53) - Style: renamed style.ChildWindowRounding to style.ChildRounding, ImGuiStyleVar_ChildWindowRounding to ImGuiStyleVar_ChildRounding. - - 2017/11/02 (1.53) - obsoleted IsRootWindowOrAnyChildHovered() in favor of using IsWindowHovered(ImGuiHoveredFlags_RootAndChildWindows); - - 2017/10/24 (1.52) - renamed IMGUI_DISABLE_WIN32_DEFAULT_CLIPBOARD_FUNCS/IMGUI_DISABLE_WIN32_DEFAULT_IME_FUNCS to IMGUI_DISABLE_WIN32_DEFAULT_CLIPBOARD_FUNCTIONS/IMGUI_DISABLE_WIN32_DEFAULT_IME_FUNCTIONS for consistency. - - 2017/10/20 (1.52) - changed IsWindowHovered() default parameters behavior to return false if an item is active in another window (e.g. click-dragging item from another window to this window). You can use the newly introduced IsWindowHovered() flags to requests this specific behavior if you need it. - - 2017/10/20 (1.52) - marked IsItemHoveredRect()/IsMouseHoveringWindow() as obsolete, in favor of using the newly introduced flags for IsItemHovered() and IsWindowHovered(). See https://github.com/ocornut/imgui/issues/1382 for details. - removed the IsItemRectHovered()/IsWindowRectHovered() names introduced in 1.51 since they were merely more consistent names for the two functions we are now obsoleting. - IsItemHoveredRect() --> IsItemHovered(ImGuiHoveredFlags_RectOnly) - IsMouseHoveringAnyWindow() --> IsWindowHovered(ImGuiHoveredFlags_AnyWindow) - IsMouseHoveringWindow() --> IsWindowHovered(ImGuiHoveredFlags_AllowWhenBlockedByPopup | ImGuiHoveredFlags_AllowWhenBlockedByActiveItem) [weird, old behavior] - - 2017/10/17 (1.52) - marked the old 5-parameters version of Begin() as obsolete (still available). Use SetNextWindowSize()+Begin() instead! - - 2017/10/11 (1.52) - renamed AlignFirstTextHeightToWidgets() to AlignTextToFramePadding(). Kept inline redirection function (will obsolete). - - 2017/09/26 (1.52) - renamed ImFont::Glyph to ImFontGlyph. Kept redirection typedef (will obsolete). - - 2017/09/25 (1.52) - removed SetNextWindowPosCenter() because SetNextWindowPos() now has the optional pivot information to do the same and more. Kept redirection function (will obsolete). - - 2017/08/25 (1.52) - io.MousePos needs to be set to ImVec2(-FLT_MAX,-FLT_MAX) when mouse is unavailable/missing. Previously ImVec2(-1,-1) was enough but we now accept negative mouse coordinates. In your backend if you need to support unavailable mouse, make sure to replace "io.MousePos = ImVec2(-1,-1)" with "io.MousePos = ImVec2(-FLT_MAX,-FLT_MAX)". - - 2017/08/22 (1.51) - renamed IsItemHoveredRect() to IsItemRectHovered(). Kept inline redirection function (will obsolete). -> (1.52) use IsItemHovered(ImGuiHoveredFlags_RectOnly)! - - renamed IsMouseHoveringAnyWindow() to IsAnyWindowHovered() for consistency. Kept inline redirection function (will obsolete). - - renamed IsMouseHoveringWindow() to IsWindowRectHovered() for consistency. Kept inline redirection function (will obsolete). - - 2017/08/20 (1.51) - renamed GetStyleColName() to GetStyleColorName() for consistency. - - 2017/08/20 (1.51) - added PushStyleColor(ImGuiCol idx, ImU32 col) overload, which _might_ cause an "ambiguous call" compilation error if you are using ImColor() with implicit cast. Cast to ImU32 or ImVec4 explicily to fix. - - 2017/08/15 (1.51) - marked the weird IMGUI_ONCE_UPON_A_FRAME helper macro as obsolete. prefer using the more explicit ImGuiOnceUponAFrame type. - - 2017/08/15 (1.51) - changed parameter order for BeginPopupContextWindow() from (const char*,int buttons,bool also_over_items) to (const char*,int buttons,bool also_over_items). Note that most calls relied on default parameters completely. - - 2017/08/13 (1.51) - renamed ImGuiCol_Column to ImGuiCol_Separator, ImGuiCol_ColumnHovered to ImGuiCol_SeparatorHovered, ImGuiCol_ColumnActive to ImGuiCol_SeparatorActive. Kept redirection enums (will obsolete). - - 2017/08/11 (1.51) - renamed ImGuiSetCond_Always to ImGuiCond_Always, ImGuiSetCond_Once to ImGuiCond_Once, ImGuiSetCond_FirstUseEver to ImGuiCond_FirstUseEver, ImGuiSetCond_Appearing to ImGuiCond_Appearing. Kept redirection enums (will obsolete). - - 2017/08/09 (1.51) - removed ValueColor() helpers, they are equivalent to calling Text(label) + SameLine() + ColorButton(). - - 2017/08/08 (1.51) - removed ColorEditMode() and ImGuiColorEditMode in favor of ImGuiColorEditFlags and parameters to the various Color*() functions. The SetColorEditOptions() allows to initialize default but the user can still change them with right-click context menu. - - changed prototype of 'ColorEdit4(const char* label, float col[4], bool show_alpha = true)' to 'ColorEdit4(const char* label, float col[4], ImGuiColorEditFlags flags = 0)', where passing flags = 0x01 is a safe no-op (hello dodgy backward compatibility!). - check and run the demo window, under "Color/Picker Widgets", to understand the various new options. - - changed prototype of rarely used 'ColorButton(ImVec4 col, bool small_height = false, bool outline_border = true)' to 'ColorButton(const char* desc_id, ImVec4 col, ImGuiColorEditFlags flags = 0, ImVec2 size = ImVec2(0, 0))' - - 2017/07/20 (1.51) - removed IsPosHoveringAnyWindow(ImVec2), which was partly broken and misleading. ASSERT + redirect user to io.WantCaptureMouse - - 2017/05/26 (1.50) - removed ImFontConfig::MergeGlyphCenterV in favor of a more multipurpose ImFontConfig::GlyphOffset. - - 2017/05/01 (1.50) - renamed ImDrawList::PathFill() (rarely used directly) to ImDrawList::PathFillConvex() for clarity. - - 2016/11/06 (1.50) - BeginChild(const char*) now applies the stack id to the provided label, consistently with other functions as it should always have been. It shouldn't affect you unless (extremely unlikely) you were appending multiple times to a same child from different locations of the stack id. If that's the case, generate an id with GetID() and use it instead of passing string to BeginChild(). - - 2016/10/15 (1.50) - avoid 'void* user_data' parameter to io.SetClipboardTextFn/io.GetClipboardTextFn pointers. We pass io.ClipboardUserData to it. - - 2016/09/25 (1.50) - style.WindowTitleAlign is now a ImVec2 (ImGuiAlign enum was removed). set to (0.5f,0.5f) for horizontal+vertical centering, (0.0f,0.0f) for upper-left, etc. - - 2016/07/30 (1.50) - SameLine(x) with x>0.0f is now relative to left of column/group if any, and not always to left of window. This was sort of always the intent and hopefully, breakage should be minimal. - - 2016/05/12 (1.49) - title bar (using ImGuiCol_TitleBg/ImGuiCol_TitleBgActive colors) isn't rendered over a window background (ImGuiCol_WindowBg color) anymore. - If your TitleBg/TitleBgActive alpha was 1.0f or you are using the default theme it will not affect you, otherwise if <1.0f you need to tweak your custom theme to readjust for the fact that we don't draw a WindowBg background behind the title bar. - This helper function will convert an old TitleBg/TitleBgActive color into a new one with the same visual output, given the OLD color and the OLD WindowBg color: - ImVec4 ConvertTitleBgCol(const ImVec4& win_bg_col, const ImVec4& title_bg_col) { float new_a = 1.0f - ((1.0f - win_bg_col.w) * (1.0f - title_bg_col.w)), k = title_bg_col.w / new_a; return ImVec4((win_bg_col.x * win_bg_col.w + title_bg_col.x) * k, (win_bg_col.y * win_bg_col.w + title_bg_col.y) * k, (win_bg_col.z * win_bg_col.w + title_bg_col.z) * k, new_a); } - If this is confusing, pick the RGB value from title bar from an old screenshot and apply this as TitleBg/TitleBgActive. Or you may just create TitleBgActive from a tweaked TitleBg color. - - 2016/05/07 (1.49) - removed confusing set of GetInternalState(), GetInternalStateSize(), SetInternalState() functions. Now using CreateContext(), DestroyContext(), GetCurrentContext(), SetCurrentContext(). - - 2016/05/02 (1.49) - renamed SetNextTreeNodeOpened() to SetNextTreeNodeOpen(), no redirection. - - 2016/05/01 (1.49) - obsoleted old signature of CollapsingHeader(const char* label, const char* str_id = NULL, bool display_frame = true, bool default_open = false) as extra parameters were badly designed and rarely used. You can replace the "default_open = true" flag in new API with CollapsingHeader(label, ImGuiTreeNodeFlags_DefaultOpen). - - 2016/04/26 (1.49) - changed ImDrawList::PushClipRect(ImVec4 rect) to ImDrawList::PushClipRect(Imvec2 min,ImVec2 max,bool intersect_with_current_clip_rect=false). Note that higher-level ImGui::PushClipRect() is preferable because it will clip at logic/widget level, whereas ImDrawList::PushClipRect() only affect your renderer. - - 2016/04/03 (1.48) - removed style.WindowFillAlphaDefault setting which was redundant. Bake default BG alpha inside style.Colors[ImGuiCol_WindowBg] and all other Bg color values. (ref GitHub issue #337). - - 2016/04/03 (1.48) - renamed ImGuiCol_TooltipBg to ImGuiCol_PopupBg, used by popups/menus and tooltips. popups/menus were previously using ImGuiCol_WindowBg. (ref github issue #337) - - 2016/03/21 (1.48) - renamed GetWindowFont() to GetFont(), GetWindowFontSize() to GetFontSize(). Kept inline redirection function (will obsolete). - - 2016/03/02 (1.48) - InputText() completion/history/always callbacks: if you modify the text buffer manually (without using DeleteChars()/InsertChars() helper) you need to maintain the BufTextLen field. added an assert. - - 2016/01/23 (1.48) - fixed not honoring exact width passed to PushItemWidth(), previously it would add extra FramePadding.x*2 over that width. if you had manual pixel-perfect alignment in place it might affect you. - - 2015/12/27 (1.48) - fixed ImDrawList::AddRect() which used to render a rectangle 1 px too large on each axis. - - 2015/12/04 (1.47) - renamed Color() helpers to ValueColor() - dangerously named, rarely used and probably to be made obsolete. - - 2015/08/29 (1.45) - with the addition of horizontal scrollbar we made various fixes to inconsistencies with dealing with cursor position. - GetCursorPos()/SetCursorPos() functions now include the scrolled amount. It shouldn't affect the majority of users, but take note that SetCursorPosX(100.0f) puts you at +100 from the starting x position which may include scrolling, not at +100 from the window left side. - GetContentRegionMax()/GetWindowContentRegionMin()/GetWindowContentRegionMax() functions allow include the scrolled amount. Typically those were used in cases where no scrolling would happen so it may not be a problem, but watch out! - - 2015/08/29 (1.45) - renamed style.ScrollbarWidth to style.ScrollbarSize - - 2015/08/05 (1.44) - split imgui.cpp into extra files: imgui_demo.cpp imgui_draw.cpp imgui_internal.h that you need to add to your project. - - 2015/07/18 (1.44) - fixed angles in ImDrawList::PathArcTo(), PathArcToFast() (introduced in 1.43) being off by an extra PI for no justifiable reason - - 2015/07/14 (1.43) - add new ImFontAtlas::AddFont() API. For the old AddFont***, moved the 'font_no' parameter of ImFontAtlas::AddFont** functions to the ImFontConfig structure. - you need to render your textured triangles with bilinear filtering to benefit from sub-pixel positioning of text. - - 2015/07/08 (1.43) - switched rendering data to use indexed rendering. this is saving a fair amount of CPU/GPU and enables us to get anti-aliasing for a marginal cost. - this necessary change will break your rendering function! the fix should be very easy. sorry for that :( - - if you are using a vanilla copy of one of the imgui_impl_XXX.cpp provided in the example, you just need to update your copy and you can ignore the rest. - - the signature of the io.RenderDrawListsFn handler has changed! - old: ImGui_XXXX_RenderDrawLists(ImDrawList** const cmd_lists, int cmd_lists_count) - new: ImGui_XXXX_RenderDrawLists(ImDrawData* draw_data). - parameters: 'cmd_lists' becomes 'draw_data->CmdLists', 'cmd_lists_count' becomes 'draw_data->CmdListsCount' - ImDrawList: 'commands' becomes 'CmdBuffer', 'vtx_buffer' becomes 'VtxBuffer', 'IdxBuffer' is new. - ImDrawCmd: 'vtx_count' becomes 'ElemCount', 'clip_rect' becomes 'ClipRect', 'user_callback' becomes 'UserCallback', 'texture_id' becomes 'TextureId'. - - each ImDrawList now contains both a vertex buffer and an index buffer. For each command, render ElemCount/3 triangles using indices from the index buffer. - - if you REALLY cannot render indexed primitives, you can call the draw_data->DeIndexAllBuffers() method to de-index the buffers. This is slow and a waste of CPU/GPU. Prefer using indexed rendering! - - refer to code in the examples/ folder or ask on the GitHub if you are unsure of how to upgrade. please upgrade! - - 2015/07/10 (1.43) - changed SameLine() parameters from int to float. - - 2015/07/02 (1.42) - renamed SetScrollPosHere() to SetScrollFromCursorPos(). Kept inline redirection function (will obsolete). - - 2015/07/02 (1.42) - renamed GetScrollPosY() to GetScrollY(). Necessary to reduce confusion along with other scrolling functions, because positions (e.g. cursor position) are not equivalent to scrolling amount. - - 2015/06/14 (1.41) - changed ImageButton() default bg_col parameter from (0,0,0,1) (black) to (0,0,0,0) (transparent) - makes a difference when texture have transparence - - 2015/06/14 (1.41) - changed Selectable() API from (label, selected, size) to (label, selected, flags, size). Size override should have been rarely used. Sorry! - - 2015/05/31 (1.40) - renamed GetWindowCollapsed() to IsWindowCollapsed() for consistency. Kept inline redirection function (will obsolete). - - 2015/05/31 (1.40) - renamed IsRectClipped() to IsRectVisible() for consistency. Note that return value is opposite! Kept inline redirection function (will obsolete). - - 2015/05/27 (1.40) - removed the third 'repeat_if_held' parameter from Button() - sorry! it was rarely used and inconsistent. Use PushButtonRepeat(true) / PopButtonRepeat() to enable repeat on desired buttons. - - 2015/05/11 (1.40) - changed BeginPopup() API, takes a string identifier instead of a bool. ImGui needs to manage the open/closed state of popups. Call OpenPopup() to actually set the "open" state of a popup. BeginPopup() returns true if the popup is opened. - - 2015/05/03 (1.40) - removed style.AutoFitPadding, using style.WindowPadding makes more sense (the default values were already the same). - - 2015/04/13 (1.38) - renamed IsClipped() to IsRectClipped(). Kept inline redirection function until 1.50. - - 2015/04/09 (1.38) - renamed ImDrawList::AddArc() to ImDrawList::AddArcFast() for compatibility with future API - - 2015/04/03 (1.38) - removed ImGuiCol_CheckHovered, ImGuiCol_CheckActive, replaced with the more general ImGuiCol_FrameBgHovered, ImGuiCol_FrameBgActive. - - 2014/04/03 (1.38) - removed support for passing -FLT_MAX..+FLT_MAX as the range for a SliderFloat(). Use DragFloat() or Inputfloat() instead. - - 2015/03/17 (1.36) - renamed GetItemBoxMin()/GetItemBoxMax()/IsMouseHoveringBox() to GetItemRectMin()/GetItemRectMax()/IsMouseHoveringRect(). Kept inline redirection function until 1.50. - - 2015/03/15 (1.36) - renamed style.TreeNodeSpacing to style.IndentSpacing, ImGuiStyleVar_TreeNodeSpacing to ImGuiStyleVar_IndentSpacing - - 2015/03/13 (1.36) - renamed GetWindowIsFocused() to IsWindowFocused(). Kept inline redirection function until 1.50. - - 2015/03/08 (1.35) - renamed style.ScrollBarWidth to style.ScrollbarWidth (casing) - - 2015/02/27 (1.34) - renamed OpenNextNode(bool) to SetNextTreeNodeOpened(bool, ImGuiSetCond). Kept inline redirection function until 1.50. - - 2015/02/27 (1.34) - renamed ImGuiSetCondition_*** to ImGuiSetCond_***, and _FirstUseThisSession becomes _Once. - - 2015/02/11 (1.32) - changed text input callback ImGuiTextEditCallback return type from void-->int. reserved for future use, return 0 for now. - - 2015/02/10 (1.32) - renamed GetItemWidth() to CalcItemWidth() to clarify its evolving behavior - - 2015/02/08 (1.31) - renamed GetTextLineSpacing() to GetTextLineHeightWithSpacing() - - 2015/02/01 (1.31) - removed IO.MemReallocFn (unused) - - 2015/01/19 (1.30) - renamed ImGuiStorage::GetIntPtr()/GetFloatPtr() to GetIntRef()/GetIntRef() because Ptr was conflicting with actual pointer storage functions. - - 2015/01/11 (1.30) - big font/image API change! now loads TTF file. allow for multiple fonts. no need for a PNG loader. - - 2015/01/11 (1.30) - removed GetDefaultFontData(). uses io.Fonts->GetTextureData*() API to retrieve uncompressed pixels. - - old: const void* png_data; unsigned int png_size; ImGui::GetDefaultFontData(NULL, NULL, &png_data, &png_size); [..Upload texture to GPU..]; - - new: unsigned char* pixels; int width, height; io.Fonts->GetTexDataAsRGBA32(&pixels, &width, &height); [..Upload texture to GPU..]; io.Fonts->SetTexID(YourTexIdentifier); - you now have more flexibility to load multiple TTF fonts and manage the texture buffer for internal needs. It is now recommended that you sample the font texture with bilinear interpolation. - - 2015/01/11 (1.30) - added texture identifier in ImDrawCmd passed to your render function (we can now render images). make sure to call io.Fonts->SetTexID() - - 2015/01/11 (1.30) - removed IO.PixelCenterOffset (unnecessary, can be handled in user projection matrix) - - 2015/01/11 (1.30) - removed ImGui::IsItemFocused() in favor of ImGui::IsItemActive() which handles all widgets - - 2014/12/10 (1.18) - removed SetNewWindowDefaultPos() in favor of new generic API SetNextWindowPos(pos, ImGuiSetCondition_FirstUseEver) - - 2014/11/28 (1.17) - moved IO.Font*** options to inside the IO.Font-> structure (FontYOffset, FontTexUvForWhite, FontBaseScale, FontFallbackGlyph) - - 2014/11/26 (1.17) - reworked syntax of IMGUI_ONCE_UPON_A_FRAME helper macro to increase compiler compatibility - - 2014/11/07 (1.15) - renamed IsHovered() to IsItemHovered() - - 2014/10/02 (1.14) - renamed IMGUI_INCLUDE_IMGUI_USER_CPP to IMGUI_INCLUDE_IMGUI_USER_INL and imgui_user.cpp to imgui_user.inl (more IDE friendly) - - 2014/09/25 (1.13) - removed 'text_end' parameter from IO.SetClipboardTextFn (the string is now always zero-terminated for simplicity) - - 2014/09/24 (1.12) - renamed SetFontScale() to SetWindowFontScale() - - 2014/09/24 (1.12) - moved IM_MALLOC/IM_REALLOC/IM_FREE preprocessor defines to IO.MemAllocFn/IO.MemReallocFn/IO.MemFreeFn - - 2014/08/30 (1.09) - removed IO.FontHeight (now computed automatically) - - 2014/08/30 (1.09) - moved IMGUI_FONT_TEX_UV_FOR_WHITE preprocessor define to IO.FontTexUvForWhite - - 2014/08/28 (1.09) - changed the behavior of IO.PixelCenterOffset following various rendering fixes - - - FREQUENTLY ASKED QUESTIONS (FAQ) - ================================ - - Read all answers online: - https://www.dearimgui.com/faq or https://github.com/ocornut/imgui/blob/master/docs/FAQ.md (same url) - Read all answers locally (with a text editor or ideally a Markdown viewer): - docs/FAQ.md - Some answers are copied down here to facilitate searching in code. - - Q&A: Basics - =========== - - Q: Where is the documentation? - A: This library is poorly documented at the moment and expects the user to be acquainted with C/C++. - - Run the examples/ applications and explore them. - - Read Getting Started (https://github.com/ocornut/imgui/wiki/Getting-Started) guide. - - See demo code in imgui_demo.cpp and particularly the ImGui::ShowDemoWindow() function. - - The demo covers most features of Dear ImGui, so you can read the code and see its output. - - See documentation and comments at the top of imgui.cpp + effectively imgui.h. - - 20+ standalone example applications using e.g. OpenGL/DirectX are provided in the - examples/ folder to explain how to integrate Dear ImGui with your own engine/application. - - The Wiki (https://github.com/ocornut/imgui/wiki) has many resources and links. - - The Glossary (https://github.com/ocornut/imgui/wiki/Glossary) page also may be useful. - - Your programming IDE is your friend, find the type or function declaration to find comments - associated with it. - - Q: What is this library called? - Q: Which version should I get? - >> This library is called "Dear ImGui", please don't call it "ImGui" :) - >> See https://www.dearimgui.com/faq for details. - - Q&A: Integration - ================ - - Q: How to get started? - A: Read https://github.com/ocornut/imgui/wiki/Getting-Started. Read 'PROGRAMMER GUIDE' above. Read examples/README.txt. - - Q: How can I tell whether to dispatch mouse/keyboard to Dear ImGui or my application? - A: You should read the 'io.WantCaptureMouse', 'io.WantCaptureKeyboard' and 'io.WantTextInput' flags! - >> See https://www.dearimgui.com/faq for a fully detailed answer. You really want to read this. - - Q. How can I enable keyboard or gamepad controls? - Q: How can I use this on a machine without mouse, keyboard or screen? (input share, remote display) - Q: I integrated Dear ImGui in my engine and little squares are showing instead of text... - Q: I integrated Dear ImGui in my engine and some elements are clipping or disappearing when I move windows around... - Q: I integrated Dear ImGui in my engine and some elements are displaying outside their expected windows boundaries... - >> See https://www.dearimgui.com/faq - - Q&A: Usage - ---------- - - Q: About the ID Stack system.. - - Why is my widget not reacting when I click on it? - - How can I have widgets with an empty label? - - How can I have multiple widgets with the same label? - - How can I have multiple windows with the same label? - Q: How can I display an image? What is ImTextureID, how does it work? - Q: How can I use my own math types instead of ImVec2? - Q: How can I interact with standard C++ types (such as std::string and std::vector)? - Q: How can I display custom shapes? (using low-level ImDrawList API) - >> See https://www.dearimgui.com/faq - - Q&A: Fonts, Text - ================ - - Q: How should I handle DPI in my application? - Q: How can I load a different font than the default? - Q: How can I easily use icons in my application? - Q: How can I load multiple fonts? - Q: How can I display and input non-Latin characters such as Chinese, Japanese, Korean, Cyrillic? - >> See https://www.dearimgui.com/faq and https://github.com/ocornut/imgui/edit/master/docs/FONTS.md - - Q&A: Concerns - ============= - - Q: Who uses Dear ImGui? - Q: Can you create elaborate/serious tools with Dear ImGui? - Q: Can you reskin the look of Dear ImGui? - Q: Why using C++ (as opposed to C)? - >> See https://www.dearimgui.com/faq - - Q&A: Community - ============== - - Q: How can I help? - A: - Businesses: please reach out to "omar AT dearimgui DOT com" if you work in a place using Dear ImGui! - We can discuss ways for your company to fund development via invoiced technical support, maintenance or sponsoring contacts. - This is among the most useful thing you can do for Dear ImGui. With increased funding, we sustain and grow work on this project. - Also see https://github.com/ocornut/imgui/wiki/Sponsors - - Businesses: you can also purchase licenses for the Dear ImGui Automation/Test Engine. - - If you are experienced with Dear ImGui and C++, look at the GitHub issues, look at the Wiki, and see how you want to help and can help! - - Disclose your usage of Dear ImGui via a dev blog post, a tweet, a screenshot, a mention somewhere etc. - You may post screenshot or links in the gallery threads. Visuals are ideal as they inspire other programmers. - But even without visuals, disclosing your use of dear imgui helps the library grow credibility, and help other teams and programmers with taking decisions. - - If you have issues or if you need to hack into the library, even if you don't expect any support it is useful that you share your issues (on GitHub or privately). - -*/ - -//------------------------------------------------------------------------- -// [SECTION] INCLUDES -//------------------------------------------------------------------------- - -#if defined(_MSC_VER) && !defined(_CRT_SECURE_NO_WARNINGS) -#define _CRT_SECURE_NO_WARNINGS -#endif - -#ifndef IMGUI_DEFINE_MATH_OPERATORS -#define IMGUI_DEFINE_MATH_OPERATORS -#endif - -#include "imgui.h" -#ifndef IMGUI_DISABLE -#include "imgui_internal.h" - -// System includes -#include // vsnprintf, sscanf, printf -#include // intptr_t - -// [Windows] On non-Visual Studio compilers, we default to IMGUI_DISABLE_WIN32_DEFAULT_IME_FUNCTIONS unless explicitly enabled -#if defined(_WIN32) && !defined(_MSC_VER) && !defined(IMGUI_ENABLE_WIN32_DEFAULT_IME_FUNCTIONS) && !defined(IMGUI_DISABLE_WIN32_DEFAULT_IME_FUNCTIONS) -#define IMGUI_DISABLE_WIN32_DEFAULT_IME_FUNCTIONS -#endif - -// [Windows] OS specific includes (optional) -#if defined(_WIN32) && defined(IMGUI_DISABLE_DEFAULT_FILE_FUNCTIONS) && defined(IMGUI_DISABLE_WIN32_DEFAULT_CLIPBOARD_FUNCTIONS) && defined(IMGUI_DISABLE_WIN32_DEFAULT_IME_FUNCTIONS) && !defined(IMGUI_DISABLE_WIN32_FUNCTIONS) -#define IMGUI_DISABLE_WIN32_FUNCTIONS -#endif -#if defined(_WIN32) && !defined(IMGUI_DISABLE_WIN32_FUNCTIONS) -#ifndef WIN32_LEAN_AND_MEAN -#define WIN32_LEAN_AND_MEAN -#endif -#ifndef NOMINMAX -#define NOMINMAX -#endif -#ifndef __MINGW32__ -#include // _wfopen, OpenClipboard -#else -#include -#endif -#if defined(WINAPI_FAMILY) && (WINAPI_FAMILY == WINAPI_FAMILY_APP) // UWP doesn't have all Win32 functions -#define IMGUI_DISABLE_WIN32_DEFAULT_CLIPBOARD_FUNCTIONS -#define IMGUI_DISABLE_WIN32_DEFAULT_IME_FUNCTIONS -#endif -#endif - -// [Apple] OS specific includes -#if defined(__APPLE__) -#include -#endif - -// Visual Studio warnings -#ifdef _MSC_VER -#pragma warning (disable: 4127) // condition expression is constant -#pragma warning (disable: 4996) // 'This function or variable may be unsafe': strcpy, strdup, sprintf, vsnprintf, sscanf, fopen -#if defined(_MSC_VER) && _MSC_VER >= 1922 // MSVC 2019 16.2 or later -#pragma warning (disable: 5054) // operator '|': deprecated between enumerations of different types -#endif -#pragma warning (disable: 26451) // [Static Analyzer] Arithmetic overflow : Using operator 'xxx' on a 4 byte value and then casting the result to an 8 byte value. Cast the value to the wider type before calling operator 'xxx' to avoid overflow(io.2). -#pragma warning (disable: 26495) // [Static Analyzer] Variable 'XXX' is uninitialized. Always initialize a member variable (type.6). -#pragma warning (disable: 26812) // [Static Analyzer] The enum type 'xxx' is unscoped. Prefer 'enum class' over 'enum' (Enum.3). -#endif - -// Clang/GCC warnings with -Weverything -#if defined(__clang__) -#if __has_warning("-Wunknown-warning-option") -#pragma clang diagnostic ignored "-Wunknown-warning-option" // warning: unknown warning group 'xxx' // not all warnings are known by all Clang versions and they tend to be rename-happy.. so ignoring warnings triggers new warnings on some configuration. Great! -#endif -#pragma clang diagnostic ignored "-Wunknown-pragmas" // warning: unknown warning group 'xxx' -#pragma clang diagnostic ignored "-Wold-style-cast" // warning: use of old-style cast // yes, they are more terse. -#pragma clang diagnostic ignored "-Wfloat-equal" // warning: comparing floating point with == or != is unsafe // storing and comparing against same constants (typically 0.0f) is ok. -#pragma clang diagnostic ignored "-Wformat-nonliteral" // warning: format string is not a string literal // passing non-literal to vsnformat(). yes, user passing incorrect format strings can crash the code. -#pragma clang diagnostic ignored "-Wexit-time-destructors" // warning: declaration requires an exit-time destructor // exit-time destruction order is undefined. if MemFree() leads to users code that has been disabled before exit it might cause problems. ImGui coding style welcomes static/globals. -#pragma clang diagnostic ignored "-Wglobal-constructors" // warning: declaration requires a global destructor // similar to above, not sure what the exact difference is. -#pragma clang diagnostic ignored "-Wsign-conversion" // warning: implicit conversion changes signedness -#pragma clang diagnostic ignored "-Wformat-pedantic" // warning: format specifies type 'void *' but the argument has type 'xxxx *' // unreasonable, would lead to casting every %p arg to void*. probably enabled by -pedantic. -#pragma clang diagnostic ignored "-Wint-to-void-pointer-cast" // warning: cast to 'void *' from smaller integer type 'int' -#pragma clang diagnostic ignored "-Wzero-as-null-pointer-constant" // warning: zero as null pointer constant // some standard header variations use #define NULL 0 -#pragma clang diagnostic ignored "-Wdouble-promotion" // warning: implicit conversion from 'float' to 'double' when passing argument to function // using printf() is a misery with this as C++ va_arg ellipsis changes float to double. -#pragma clang diagnostic ignored "-Wimplicit-int-float-conversion" // warning: implicit conversion from 'xxx' to 'float' may lose precision -#elif defined(__GNUC__) -// We disable -Wpragmas because GCC doesn't provide a has_warning equivalent and some forks/patches may not follow the warning/version association. -#pragma GCC diagnostic ignored "-Wpragmas" // warning: unknown option after '#pragma GCC diagnostic' kind -#pragma GCC diagnostic ignored "-Wunused-function" // warning: 'xxxx' defined but not used -#pragma GCC diagnostic ignored "-Wint-to-pointer-cast" // warning: cast to pointer from integer of different size -#pragma GCC diagnostic ignored "-Wformat" // warning: format '%p' expects argument of type 'void*', but argument 6 has type 'ImGuiWindow*' -#pragma GCC diagnostic ignored "-Wdouble-promotion" // warning: implicit conversion from 'float' to 'double' when passing argument to function -#pragma GCC diagnostic ignored "-Wconversion" // warning: conversion to 'xxxx' from 'xxxx' may alter its value -#pragma GCC diagnostic ignored "-Wformat-nonliteral" // warning: format not a string literal, format string not checked -#pragma GCC diagnostic ignored "-Wstrict-overflow" // warning: assuming signed overflow does not occur when assuming that (X - c) > X is always false -#pragma GCC diagnostic ignored "-Wclass-memaccess" // [__GNUC__ >= 8] warning: 'memset/memcpy' clearing/writing an object of type 'xxxx' with no trivial copy-assignment; use assignment or value-initialization instead -#endif - -// Debug options -#define IMGUI_DEBUG_NAV_SCORING 0 // Display navigation scoring preview when hovering items. Display last moving direction matches when holding CTRL -#define IMGUI_DEBUG_NAV_RECTS 0 // Display the reference navigation rectangle for each window - -// When using CTRL+TAB (or Gamepad Square+L/R) we delay the visual a little in order to reduce visual noise doing a fast switch. -static const float NAV_WINDOWING_HIGHLIGHT_DELAY = 0.20f; // Time before the highlight and screen dimming starts fading in -static const float NAV_WINDOWING_LIST_APPEAR_DELAY = 0.15f; // Time before the window list starts to appear - -// Window resizing from edges (when io.ConfigWindowsResizeFromEdges = true and ImGuiBackendFlags_HasMouseCursors is set in io.BackendFlags by backend) -static const float WINDOWS_HOVER_PADDING = 4.0f; // Extend outside window for hovering/resizing (maxxed with TouchPadding) and inside windows for borders. Affect FindHoveredWindow(). -static const float WINDOWS_RESIZE_FROM_EDGES_FEEDBACK_TIMER = 0.04f; // Reduce visual noise by only highlighting the border after a certain time. -static const float WINDOWS_MOUSE_WHEEL_SCROLL_LOCK_TIMER = 0.70f; // Lock scrolled window (so it doesn't pick child windows that are scrolling through) for a certain time, unless mouse moved. - -// Tooltip offset -static const ImVec2 TOOLTIP_DEFAULT_OFFSET = ImVec2(16, 10); // Multiplied by g.Style.MouseCursorScale - -// Docking -static const float DOCKING_TRANSPARENT_PAYLOAD_ALPHA = 0.50f; // For use with io.ConfigDockingTransparentPayload. Apply to Viewport _or_ WindowBg in host viewport. - -//------------------------------------------------------------------------- -// [SECTION] FORWARD DECLARATIONS -//------------------------------------------------------------------------- - -static void SetCurrentWindow(ImGuiWindow* window); -static void FindHoveredWindow(); -static ImGuiWindow* CreateNewWindow(const char* name, ImGuiWindowFlags flags); -static ImVec2 CalcNextScrollFromScrollTargetAndClamp(ImGuiWindow* window); - -static void AddWindowToSortBuffer(ImVector* out_sorted_windows, ImGuiWindow* window); - -// Settings -static void WindowSettingsHandler_ClearAll(ImGuiContext*, ImGuiSettingsHandler*); -static void* WindowSettingsHandler_ReadOpen(ImGuiContext*, ImGuiSettingsHandler*, const char* name); -static void WindowSettingsHandler_ReadLine(ImGuiContext*, ImGuiSettingsHandler*, void* entry, const char* line); -static void WindowSettingsHandler_ApplyAll(ImGuiContext*, ImGuiSettingsHandler*); -static void WindowSettingsHandler_WriteAll(ImGuiContext*, ImGuiSettingsHandler*, ImGuiTextBuffer* buf); - -// Platform Dependents default implementation for IO functions -static const char* GetClipboardTextFn_DefaultImpl(void* user_data_ctx); -static void SetClipboardTextFn_DefaultImpl(void* user_data_ctx, const char* text); -static void SetPlatformImeDataFn_DefaultImpl(ImGuiViewport* viewport, ImGuiPlatformImeData* data); - -namespace ImGui -{ -// Navigation -static void NavUpdate(); -static void NavUpdateWindowing(); -static void NavUpdateWindowingOverlay(); -static void NavUpdateCancelRequest(); -static void NavUpdateCreateMoveRequest(); -static void NavUpdateCreateTabbingRequest(); -static float NavUpdatePageUpPageDown(); -static inline void NavUpdateAnyRequestFlag(); -static void NavUpdateCreateWrappingRequest(); -static void NavEndFrame(); -static bool NavScoreItem(ImGuiNavItemData* result); -static void NavApplyItemToResult(ImGuiNavItemData* result); -static void NavProcessItem(); -static void NavProcessItemForTabbingRequest(ImGuiID id, ImGuiItemFlags item_flags, ImGuiNavMoveFlags move_flags); -static ImVec2 NavCalcPreferredRefPos(); -static void NavSaveLastChildNavWindowIntoParent(ImGuiWindow* nav_window); -static ImGuiWindow* NavRestoreLastChildNavWindow(ImGuiWindow* window); -static void NavRestoreLayer(ImGuiNavLayer layer); -static int FindWindowFocusIndex(ImGuiWindow* window); - -// Error Checking and Debug Tools -static void ErrorCheckNewFrameSanityChecks(); -static void ErrorCheckEndFrameSanityChecks(); -static void UpdateDebugToolItemPicker(); -static void UpdateDebugToolStackQueries(); - -// Inputs -static void UpdateKeyboardInputs(); -static void UpdateMouseInputs(); -static void UpdateMouseWheel(); -static void UpdateKeyRoutingTable(ImGuiKeyRoutingTable* rt); - -// Misc -static void UpdateSettings(); -static bool UpdateWindowManualResize(ImGuiWindow* window, const ImVec2& size_auto_fit, int* border_held, int resize_grip_count, ImU32 resize_grip_col[4], const ImRect& visibility_rect); -static void RenderWindowOuterBorders(ImGuiWindow* window); -static void RenderWindowDecorations(ImGuiWindow* window, const ImRect& title_bar_rect, bool title_bar_is_highlight, bool handle_borders_and_resize_grips, int resize_grip_count, const ImU32 resize_grip_col[4], float resize_grip_draw_size); -static void RenderWindowTitleBarContents(ImGuiWindow* window, const ImRect& title_bar_rect, const char* name, bool* p_open); -static void RenderDimmedBackgroundBehindWindow(ImGuiWindow* window, ImU32 col); -static void RenderDimmedBackgrounds(); - -// Viewports -const ImGuiID IMGUI_VIEWPORT_DEFAULT_ID = 0x11111111; // Using an arbitrary constant instead of e.g. ImHashStr("ViewportDefault", 0); so it's easier to spot in the debugger. The exact value doesn't matter. -static ImGuiViewportP* AddUpdateViewport(ImGuiWindow* window, ImGuiID id, const ImVec2& platform_pos, const ImVec2& size, ImGuiViewportFlags flags); -static void DestroyViewport(ImGuiViewportP* viewport); -static void UpdateViewportsNewFrame(); -static void UpdateViewportsEndFrame(); -static void WindowSelectViewport(ImGuiWindow* window); -static void WindowSyncOwnedViewport(ImGuiWindow* window, ImGuiWindow* parent_window_in_stack); -static bool UpdateTryMergeWindowIntoHostViewport(ImGuiWindow* window, ImGuiViewportP* host_viewport); -static bool UpdateTryMergeWindowIntoHostViewports(ImGuiWindow* window); -static bool GetWindowAlwaysWantOwnViewport(ImGuiWindow* window); -static int FindPlatformMonitorForPos(const ImVec2& pos); -static int FindPlatformMonitorForRect(const ImRect& r); -static void UpdateViewportPlatformMonitor(ImGuiViewportP* viewport); - -} - -//----------------------------------------------------------------------------- -// [SECTION] CONTEXT AND MEMORY ALLOCATORS -//----------------------------------------------------------------------------- - -// DLL users: -// - Heaps and globals are not shared across DLL boundaries! -// - You will need to call SetCurrentContext() + SetAllocatorFunctions() for each static/DLL boundary you are calling from. -// - Same applies for hot-reloading mechanisms that are reliant on reloading DLL (note that many hot-reloading mechanisms work without DLL). -// - Using Dear ImGui via a shared library is not recommended, because of function call overhead and because we don't guarantee backward nor forward ABI compatibility. -// - Confused? In a debugger: add GImGui to your watch window and notice how its value changes depending on your current location (which DLL boundary you are in). - -// Current context pointer. Implicitly used by all Dear ImGui functions. Always assumed to be != NULL. -// - ImGui::CreateContext() will automatically set this pointer if it is NULL. -// Change to a different context by calling ImGui::SetCurrentContext(). -// - Important: Dear ImGui functions are not thread-safe because of this pointer. -// If you want thread-safety to allow N threads to access N different contexts: -// - Change this variable to use thread local storage so each thread can refer to a different context, in your imconfig.h: -// struct ImGuiContext; -// extern thread_local ImGuiContext* MyImGuiTLS; -// #define GImGui MyImGuiTLS -// And then define MyImGuiTLS in one of your cpp files. Note that thread_local is a C++11 keyword, earlier C++ uses compiler-specific keyword. -// - Future development aims to make this context pointer explicit to all calls. Also read https://github.com/ocornut/imgui/issues/586 -// - If you need a finite number of contexts, you may compile and use multiple instances of the ImGui code from a different namespace. -// - DLL users: read comments above. -#ifndef GImGui -ImGuiContext* GImGui = NULL; -#endif - -// Memory Allocator functions. Use SetAllocatorFunctions() to change them. -// - You probably don't want to modify that mid-program, and if you use global/static e.g. ImVector<> instances you may need to keep them accessible during program destruction. -// - DLL users: read comments above. -#ifndef IMGUI_DISABLE_DEFAULT_ALLOCATORS -static void* MallocWrapper(size_t size, void* user_data) { IM_UNUSED(user_data); return malloc(size); } -static void FreeWrapper(void* ptr, void* user_data) { IM_UNUSED(user_data); free(ptr); } -#else -static void* MallocWrapper(size_t size, void* user_data) { IM_UNUSED(user_data); IM_UNUSED(size); IM_ASSERT(0); return NULL; } -static void FreeWrapper(void* ptr, void* user_data) { IM_UNUSED(user_data); IM_UNUSED(ptr); IM_ASSERT(0); } -#endif -static ImGuiMemAllocFunc GImAllocatorAllocFunc = MallocWrapper; -static ImGuiMemFreeFunc GImAllocatorFreeFunc = FreeWrapper; -static void* GImAllocatorUserData = NULL; - -//----------------------------------------------------------------------------- -// [SECTION] USER FACING STRUCTURES (ImGuiStyle, ImGuiIO) -//----------------------------------------------------------------------------- - -ImGuiStyle::ImGuiStyle() -{ - Alpha = 1.0f; // Global alpha applies to everything in Dear ImGui. - DisabledAlpha = 0.60f; // Additional alpha multiplier applied by BeginDisabled(). Multiply over current value of Alpha. - WindowPadding = ImVec2(8,8); // Padding within a window - WindowRounding = 0.0f; // Radius of window corners rounding. Set to 0.0f to have rectangular windows. Large values tend to lead to variety of artifacts and are not recommended. - WindowBorderSize = 1.0f; // Thickness of border around windows. Generally set to 0.0f or 1.0f. Other values not well tested. - WindowMinSize = ImVec2(32,32); // Minimum window size - WindowTitleAlign = ImVec2(0.0f,0.5f);// Alignment for title bar text - WindowMenuButtonPosition= ImGuiDir_Left; // Position of the collapsing/docking button in the title bar (left/right). Defaults to ImGuiDir_Left. - ChildRounding = 0.0f; // Radius of child window corners rounding. Set to 0.0f to have rectangular child windows - ChildBorderSize = 1.0f; // Thickness of border around child windows. Generally set to 0.0f or 1.0f. Other values not well tested. - PopupRounding = 0.0f; // Radius of popup window corners rounding. Set to 0.0f to have rectangular child windows - PopupBorderSize = 1.0f; // Thickness of border around popup or tooltip windows. Generally set to 0.0f or 1.0f. Other values not well tested. - FramePadding = ImVec2(4,3); // Padding within a framed rectangle (used by most widgets) - FrameRounding = 0.0f; // Radius of frame corners rounding. Set to 0.0f to have rectangular frames (used by most widgets). - FrameBorderSize = 0.0f; // Thickness of border around frames. Generally set to 0.0f or 1.0f. Other values not well tested. - ItemSpacing = ImVec2(8,4); // Horizontal and vertical spacing between widgets/lines - ItemInnerSpacing = ImVec2(4,4); // Horizontal and vertical spacing between within elements of a composed widget (e.g. a slider and its label) - CellPadding = ImVec2(4,2); // Padding within a table cell. CellPadding.y may be altered between different rows. - TouchExtraPadding = ImVec2(0,0); // Expand reactive bounding box for touch-based system where touch position is not accurate enough. Unfortunately we don't sort widgets so priority on overlap will always be given to the first widget. So don't grow this too much! - IndentSpacing = 21.0f; // Horizontal spacing when e.g. entering a tree node. Generally == (FontSize + FramePadding.x*2). - ColumnsMinSpacing = 6.0f; // Minimum horizontal spacing between two columns. Preferably > (FramePadding.x + 1). - ScrollbarSize = 14.0f; // Width of the vertical scrollbar, Height of the horizontal scrollbar - ScrollbarRounding = 9.0f; // Radius of grab corners rounding for scrollbar - GrabMinSize = 12.0f; // Minimum width/height of a grab box for slider/scrollbar - GrabRounding = 0.0f; // Radius of grabs corners rounding. Set to 0.0f to have rectangular slider grabs. - LogSliderDeadzone = 4.0f; // The size in pixels of the dead-zone around zero on logarithmic sliders that cross zero. - TabRounding = 4.0f; // Radius of upper corners of a tab. Set to 0.0f to have rectangular tabs. - TabBorderSize = 0.0f; // Thickness of border around tabs. - TabMinWidthForCloseButton = 0.0f; // Minimum width for close button to appear on an unselected tab when hovered. Set to 0.0f to always show when hovering, set to FLT_MAX to never show close button unless selected. - TabBarBorderSize = 1.0f; // Thickness of tab-bar separator, which takes on the tab active color to denote focus. - TableAngledHeadersAngle = 35.0f * (IM_PI / 180.0f); // Angle of angled headers (supported values range from -50 degrees to +50 degrees). - ColorButtonPosition = ImGuiDir_Right; // Side of the color button in the ColorEdit4 widget (left/right). Defaults to ImGuiDir_Right. - ButtonTextAlign = ImVec2(0.5f,0.5f);// Alignment of button text when button is larger than text. - SelectableTextAlign = ImVec2(0.0f,0.0f);// Alignment of selectable text. Defaults to (0.0f, 0.0f) (top-left aligned). It's generally important to keep this left-aligned if you want to lay multiple items on a same line. - SeparatorTextBorderSize = 3.0f; // Thickkness of border in SeparatorText() - SeparatorTextAlign = ImVec2(0.0f,0.5f);// Alignment of text within the separator. Defaults to (0.0f, 0.5f) (left aligned, center). - SeparatorTextPadding = ImVec2(20.0f,3.f);// Horizontal offset of text from each edge of the separator + spacing on other axis. Generally small values. .y is recommended to be == FramePadding.y. - DisplayWindowPadding = ImVec2(19,19); // Window position are clamped to be visible within the display area or monitors by at least this amount. Only applies to regular windows. - DisplaySafeAreaPadding = ImVec2(3,3); // If you cannot see the edge of your screen (e.g. on a TV) increase the safe area padding. Covers popups/tooltips as well regular windows. - DockingSeparatorSize = 2.0f; // Thickness of resizing border between docked windows - MouseCursorScale = 1.0f; // Scale software rendered mouse cursor (when io.MouseDrawCursor is enabled). May be removed later. - AntiAliasedLines = true; // Enable anti-aliased lines/borders. Disable if you are really tight on CPU/GPU. - AntiAliasedLinesUseTex = true; // Enable anti-aliased lines/borders using textures where possible. Require backend to render with bilinear filtering (NOT point/nearest filtering). - AntiAliasedFill = true; // Enable anti-aliased filled shapes (rounded rectangles, circles, etc.). - CurveTessellationTol = 1.25f; // Tessellation tolerance when using PathBezierCurveTo() without a specific number of segments. Decrease for highly tessellated curves (higher quality, more polygons), increase to reduce quality. - CircleTessellationMaxError = 0.30f; // Maximum error (in pixels) allowed when using AddCircle()/AddCircleFilled() or drawing rounded corner rectangles with no explicit segment count specified. Decrease for higher quality but more geometry. - - // Behaviors - HoverStationaryDelay = 0.15f; // Delay for IsItemHovered(ImGuiHoveredFlags_Stationary). Time required to consider mouse stationary. - HoverDelayShort = 0.15f; // Delay for IsItemHovered(ImGuiHoveredFlags_DelayShort). Usually used along with HoverStationaryDelay. - HoverDelayNormal = 0.40f; // Delay for IsItemHovered(ImGuiHoveredFlags_DelayNormal). " - HoverFlagsForTooltipMouse = ImGuiHoveredFlags_Stationary | ImGuiHoveredFlags_DelayShort | ImGuiHoveredFlags_AllowWhenDisabled; // Default flags when using IsItemHovered(ImGuiHoveredFlags_ForTooltip) or BeginItemTooltip()/SetItemTooltip() while using mouse. - HoverFlagsForTooltipNav = ImGuiHoveredFlags_NoSharedDelay | ImGuiHoveredFlags_DelayNormal | ImGuiHoveredFlags_AllowWhenDisabled; // Default flags when using IsItemHovered(ImGuiHoveredFlags_ForTooltip) or BeginItemTooltip()/SetItemTooltip() while using keyboard/gamepad. - - // Default theme - ImGui::StyleColorsDark(this); -} - -// To scale your entire UI (e.g. if you want your app to use High DPI or generally be DPI aware) you may use this helper function. Scaling the fonts is done separately and is up to you. -// Important: This operation is lossy because we round all sizes to integer. If you need to change your scale multiples, call this over a freshly initialized ImGuiStyle structure rather than scaling multiple times. -void ImGuiStyle::ScaleAllSizes(float scale_factor) -{ - WindowPadding = ImTrunc(WindowPadding * scale_factor); - WindowRounding = ImTrunc(WindowRounding * scale_factor); - WindowMinSize = ImTrunc(WindowMinSize * scale_factor); - ChildRounding = ImTrunc(ChildRounding * scale_factor); - PopupRounding = ImTrunc(PopupRounding * scale_factor); - FramePadding = ImTrunc(FramePadding * scale_factor); - FrameRounding = ImTrunc(FrameRounding * scale_factor); - ItemSpacing = ImTrunc(ItemSpacing * scale_factor); - ItemInnerSpacing = ImTrunc(ItemInnerSpacing * scale_factor); - CellPadding = ImTrunc(CellPadding * scale_factor); - TouchExtraPadding = ImTrunc(TouchExtraPadding * scale_factor); - IndentSpacing = ImTrunc(IndentSpacing * scale_factor); - ColumnsMinSpacing = ImTrunc(ColumnsMinSpacing * scale_factor); - ScrollbarSize = ImTrunc(ScrollbarSize * scale_factor); - ScrollbarRounding = ImTrunc(ScrollbarRounding * scale_factor); - GrabMinSize = ImTrunc(GrabMinSize * scale_factor); - GrabRounding = ImTrunc(GrabRounding * scale_factor); - LogSliderDeadzone = ImTrunc(LogSliderDeadzone * scale_factor); - TabRounding = ImTrunc(TabRounding * scale_factor); - TabMinWidthForCloseButton = (TabMinWidthForCloseButton != FLT_MAX) ? ImTrunc(TabMinWidthForCloseButton * scale_factor) : FLT_MAX; - SeparatorTextPadding = ImTrunc(SeparatorTextPadding * scale_factor); - DockingSeparatorSize = ImTrunc(DockingSeparatorSize * scale_factor); - DisplayWindowPadding = ImTrunc(DisplayWindowPadding * scale_factor); - DisplaySafeAreaPadding = ImTrunc(DisplaySafeAreaPadding * scale_factor); - MouseCursorScale = ImTrunc(MouseCursorScale * scale_factor); -} - -ImGuiIO::ImGuiIO() -{ - // Most fields are initialized with zero - memset(this, 0, sizeof(*this)); - IM_STATIC_ASSERT(IM_ARRAYSIZE(ImGuiIO::MouseDown) == ImGuiMouseButton_COUNT && IM_ARRAYSIZE(ImGuiIO::MouseClicked) == ImGuiMouseButton_COUNT); - - // Settings - ConfigFlags = ImGuiConfigFlags_None; - BackendFlags = ImGuiBackendFlags_None; - DisplaySize = ImVec2(-1.0f, -1.0f); - DeltaTime = 1.0f / 60.0f; - IniSavingRate = 5.0f; - IniFilename = "imgui.ini"; // Important: "imgui.ini" is relative to current working dir, most apps will want to lock this to an absolute path (e.g. same path as executables). - LogFilename = "imgui_log.txt"; -#ifndef IMGUI_DISABLE_OBSOLETE_KEYIO - for (int i = 0; i < ImGuiKey_COUNT; i++) - KeyMap[i] = -1; -#endif - UserData = NULL; - - Fonts = NULL; - FontGlobalScale = 1.0f; - FontDefault = NULL; - FontAllowUserScaling = false; - DisplayFramebufferScale = ImVec2(1.0f, 1.0f); - - // Docking options (when ImGuiConfigFlags_DockingEnable is set) - ConfigDockingNoSplit = false; - ConfigDockingWithShift = false; - ConfigDockingAlwaysTabBar = false; - ConfigDockingTransparentPayload = false; - - // Viewport options (when ImGuiConfigFlags_ViewportsEnable is set) - ConfigViewportsNoAutoMerge = false; - ConfigViewportsNoTaskBarIcon = false; - ConfigViewportsNoDecoration = true; - ConfigViewportsNoDefaultParent = false; - - // Miscellaneous options - MouseDrawCursor = false; -#ifdef __APPLE__ - ConfigMacOSXBehaviors = true; // Set Mac OS X style defaults based on __APPLE__ compile time flag -#else - ConfigMacOSXBehaviors = false; -#endif - ConfigInputTrickleEventQueue = true; - ConfigInputTextCursorBlink = true; - ConfigInputTextEnterKeepActive = false; - ConfigDragClickToInputText = false; - ConfigWindowsResizeFromEdges = true; - ConfigWindowsMoveFromTitleBarOnly = false; - ConfigMemoryCompactTimer = 60.0f; - ConfigDebugBeginReturnValueOnce = false; - ConfigDebugBeginReturnValueLoop = false; - - // Inputs Behaviors - MouseDoubleClickTime = 0.30f; - MouseDoubleClickMaxDist = 6.0f; - MouseDragThreshold = 6.0f; - KeyRepeatDelay = 0.275f; - KeyRepeatRate = 0.050f; - - // Platform Functions - // Note: Initialize() will setup default clipboard/ime handlers. - BackendPlatformName = BackendRendererName = NULL; - BackendPlatformUserData = BackendRendererUserData = BackendLanguageUserData = NULL; - PlatformLocaleDecimalPoint = '.'; - - // Input (NB: we already have memset zero the entire structure!) - MousePos = ImVec2(-FLT_MAX, -FLT_MAX); - MousePosPrev = ImVec2(-FLT_MAX, -FLT_MAX); - MouseSource = ImGuiMouseSource_Mouse; - for (int i = 0; i < IM_ARRAYSIZE(MouseDownDuration); i++) MouseDownDuration[i] = MouseDownDurationPrev[i] = -1.0f; - for (int i = 0; i < IM_ARRAYSIZE(KeysData); i++) { KeysData[i].DownDuration = KeysData[i].DownDurationPrev = -1.0f; } - AppAcceptingEvents = true; - BackendUsingLegacyKeyArrays = (ImS8)-1; - BackendUsingLegacyNavInputArray = true; // assume using legacy array until proven wrong -} - -// Pass in translated ASCII characters for text input. -// - with glfw you can get those from the callback set in glfwSetCharCallback() -// - on Windows you can get those using ToAscii+keyboard state, or via the WM_CHAR message -// FIXME: Should in theory be called "AddCharacterEvent()" to be consistent with new API -void ImGuiIO::AddInputCharacter(unsigned int c) -{ - IM_ASSERT(Ctx != NULL); - ImGuiContext& g = *Ctx; - if (c == 0 || !AppAcceptingEvents) - return; - - ImGuiInputEvent e; - e.Type = ImGuiInputEventType_Text; - e.Source = ImGuiInputSource_Keyboard; - e.EventId = g.InputEventsNextEventId++; - e.Text.Char = c; - g.InputEventsQueue.push_back(e); -} - -// UTF16 strings use surrogate pairs to encode codepoints >= 0x10000, so -// we should save the high surrogate. -void ImGuiIO::AddInputCharacterUTF16(ImWchar16 c) -{ - if ((c == 0 && InputQueueSurrogate == 0) || !AppAcceptingEvents) - return; - - if ((c & 0xFC00) == 0xD800) // High surrogate, must save - { - if (InputQueueSurrogate != 0) - AddInputCharacter(IM_UNICODE_CODEPOINT_INVALID); - InputQueueSurrogate = c; - return; - } - - ImWchar cp = c; - if (InputQueueSurrogate != 0) - { - if ((c & 0xFC00) != 0xDC00) // Invalid low surrogate - { - AddInputCharacter(IM_UNICODE_CODEPOINT_INVALID); - } - else - { -#if IM_UNICODE_CODEPOINT_MAX == 0xFFFF - cp = IM_UNICODE_CODEPOINT_INVALID; // Codepoint will not fit in ImWchar -#else - cp = (ImWchar)(((InputQueueSurrogate - 0xD800) << 10) + (c - 0xDC00) + 0x10000); -#endif - } - - InputQueueSurrogate = 0; - } - AddInputCharacter((unsigned)cp); -} - -void ImGuiIO::AddInputCharactersUTF8(const char* utf8_chars) -{ - if (!AppAcceptingEvents) - return; - while (*utf8_chars != 0) - { - unsigned int c = 0; - utf8_chars += ImTextCharFromUtf8(&c, utf8_chars, NULL); - AddInputCharacter(c); - } -} - -// Clear all incoming events. -void ImGuiIO::ClearEventsQueue() -{ - IM_ASSERT(Ctx != NULL); - ImGuiContext& g = *Ctx; - g.InputEventsQueue.clear(); -} - -// Clear current keyboard/mouse/gamepad state + current frame text input buffer. Equivalent to releasing all keys/buttons. -void ImGuiIO::ClearInputKeys() -{ -#ifndef IMGUI_DISABLE_OBSOLETE_KEYIO - memset(KeysDown, 0, sizeof(KeysDown)); -#endif - for (int n = 0; n < IM_ARRAYSIZE(KeysData); n++) - { - KeysData[n].Down = false; - KeysData[n].DownDuration = -1.0f; - KeysData[n].DownDurationPrev = -1.0f; - } - KeyCtrl = KeyShift = KeyAlt = KeySuper = false; - KeyMods = ImGuiMod_None; - MousePos = ImVec2(-FLT_MAX, -FLT_MAX); - for (int n = 0; n < IM_ARRAYSIZE(MouseDown); n++) - { - MouseDown[n] = false; - MouseDownDuration[n] = MouseDownDurationPrev[n] = -1.0f; - } - MouseWheel = MouseWheelH = 0.0f; - InputQueueCharacters.resize(0); // Behavior of old ClearInputCharacters(). -} - -// Removed this as it is ambiguous/misleading and generally incorrect to use with the existence of a higher-level input queue. -// Current frame character buffer is now also cleared by ClearInputKeys(). -#ifndef IMGUI_DISABLE_OBSOLETE_FUNCTIONS -void ImGuiIO::ClearInputCharacters() -{ - InputQueueCharacters.resize(0); -} -#endif - -static ImGuiInputEvent* FindLatestInputEvent(ImGuiContext* ctx, ImGuiInputEventType type, int arg = -1) -{ - ImGuiContext& g = *ctx; - for (int n = g.InputEventsQueue.Size - 1; n >= 0; n--) - { - ImGuiInputEvent* e = &g.InputEventsQueue[n]; - if (e->Type != type) - continue; - if (type == ImGuiInputEventType_Key && e->Key.Key != arg) - continue; - if (type == ImGuiInputEventType_MouseButton && e->MouseButton.Button != arg) - continue; - return e; - } - return NULL; -} - -// Queue a new key down/up event. -// - ImGuiKey key: Translated key (as in, generally ImGuiKey_A matches the key end-user would use to emit an 'A' character) -// - bool down: Is the key down? use false to signify a key release. -// - float analog_value: 0.0f..1.0f -// IMPORTANT: THIS FUNCTION AND OTHER "ADD" GRABS THE CONTEXT FROM OUR INSTANCE. -// WE NEED TO ENSURE THAT ALL FUNCTION CALLS ARE FULLFILLING THIS, WHICH IS WHY GetKeyData() HAS AN EXPLICIT CONTEXT. -void ImGuiIO::AddKeyAnalogEvent(ImGuiKey key, bool down, float analog_value) -{ - //if (e->Down) { IMGUI_DEBUG_LOG_IO("AddKeyEvent() Key='%s' %d, NativeKeycode = %d, NativeScancode = %d\n", ImGui::GetKeyName(e->Key), e->Down, e->NativeKeycode, e->NativeScancode); } - IM_ASSERT(Ctx != NULL); - if (key == ImGuiKey_None || !AppAcceptingEvents) - return; - ImGuiContext& g = *Ctx; - IM_ASSERT(ImGui::IsNamedKeyOrModKey(key)); // Backend needs to pass a valid ImGuiKey_ constant. 0..511 values are legacy native key codes which are not accepted by this API. - IM_ASSERT(ImGui::IsAliasKey(key) == false); // Backend cannot submit ImGuiKey_MouseXXX values they are automatically inferred from AddMouseXXX() events. - IM_ASSERT(key != ImGuiMod_Shortcut); // We could easily support the translation here but it seems saner to not accept it (TestEngine perform a translation itself) - - // Verify that backend isn't mixing up using new io.AddKeyEvent() api and old io.KeysDown[] + io.KeyMap[] data. -#ifndef IMGUI_DISABLE_OBSOLETE_KEYIO - IM_ASSERT((BackendUsingLegacyKeyArrays == -1 || BackendUsingLegacyKeyArrays == 0) && "Backend needs to either only use io.AddKeyEvent(), either only fill legacy io.KeysDown[] + io.KeyMap[]. Not both!"); - if (BackendUsingLegacyKeyArrays == -1) - for (int n = ImGuiKey_NamedKey_BEGIN; n < ImGuiKey_NamedKey_END; n++) - IM_ASSERT(KeyMap[n] == -1 && "Backend needs to either only use io.AddKeyEvent(), either only fill legacy io.KeysDown[] + io.KeyMap[]. Not both!"); - BackendUsingLegacyKeyArrays = 0; -#endif - if (ImGui::IsGamepadKey(key)) - BackendUsingLegacyNavInputArray = false; - - // Filter duplicate (in particular: key mods and gamepad analog values are commonly spammed) - const ImGuiInputEvent* latest_event = FindLatestInputEvent(&g, ImGuiInputEventType_Key, (int)key); - const ImGuiKeyData* key_data = ImGui::GetKeyData(&g, key); - const bool latest_key_down = latest_event ? latest_event->Key.Down : key_data->Down; - const float latest_key_analog = latest_event ? latest_event->Key.AnalogValue : key_data->AnalogValue; - if (latest_key_down == down && latest_key_analog == analog_value) - return; - - // Add event - ImGuiInputEvent e; - e.Type = ImGuiInputEventType_Key; - e.Source = ImGui::IsGamepadKey(key) ? ImGuiInputSource_Gamepad : ImGuiInputSource_Keyboard; - e.EventId = g.InputEventsNextEventId++; - e.Key.Key = key; - e.Key.Down = down; - e.Key.AnalogValue = analog_value; - g.InputEventsQueue.push_back(e); -} - -void ImGuiIO::AddKeyEvent(ImGuiKey key, bool down) -{ - if (!AppAcceptingEvents) - return; - AddKeyAnalogEvent(key, down, down ? 1.0f : 0.0f); -} - -// [Optional] Call after AddKeyEvent(). -// Specify native keycode, scancode + Specify index for legacy <1.87 IsKeyXXX() functions with native indices. -// If you are writing a backend in 2022 or don't use IsKeyXXX() with native values that are not ImGuiKey values, you can avoid calling this. -void ImGuiIO::SetKeyEventNativeData(ImGuiKey key, int native_keycode, int native_scancode, int native_legacy_index) -{ - if (key == ImGuiKey_None) - return; - IM_ASSERT(ImGui::IsNamedKey(key)); // >= 512 - IM_ASSERT(native_legacy_index == -1 || ImGui::IsLegacyKey((ImGuiKey)native_legacy_index)); // >= 0 && <= 511 - IM_UNUSED(native_keycode); // Yet unused - IM_UNUSED(native_scancode); // Yet unused - - // Build native->imgui map so old user code can still call key functions with native 0..511 values. -#ifndef IMGUI_DISABLE_OBSOLETE_KEYIO - const int legacy_key = (native_legacy_index != -1) ? native_legacy_index : native_keycode; - if (!ImGui::IsLegacyKey((ImGuiKey)legacy_key)) - return; - KeyMap[legacy_key] = key; - KeyMap[key] = legacy_key; -#else - IM_UNUSED(key); - IM_UNUSED(native_legacy_index); -#endif -} - -// Set master flag for accepting key/mouse/text events (default to true). Useful if you have native dialog boxes that are interrupting your application loop/refresh, and you want to disable events being queued while your app is frozen. -void ImGuiIO::SetAppAcceptingEvents(bool accepting_events) -{ - AppAcceptingEvents = accepting_events; -} - -// Queue a mouse move event -void ImGuiIO::AddMousePosEvent(float x, float y) -{ - IM_ASSERT(Ctx != NULL); - ImGuiContext& g = *Ctx; - if (!AppAcceptingEvents) - return; - - // Apply same flooring as UpdateMouseInputs() - ImVec2 pos((x > -FLT_MAX) ? ImFloor(x) : x, (y > -FLT_MAX) ? ImFloor(y) : y); - - // Filter duplicate - const ImGuiInputEvent* latest_event = FindLatestInputEvent(&g, ImGuiInputEventType_MousePos); - const ImVec2 latest_pos = latest_event ? ImVec2(latest_event->MousePos.PosX, latest_event->MousePos.PosY) : g.IO.MousePos; - if (latest_pos.x == pos.x && latest_pos.y == pos.y) - return; - - ImGuiInputEvent e; - e.Type = ImGuiInputEventType_MousePos; - e.Source = ImGuiInputSource_Mouse; - e.EventId = g.InputEventsNextEventId++; - e.MousePos.PosX = pos.x; - e.MousePos.PosY = pos.y; - e.MousePos.MouseSource = g.InputEventsNextMouseSource; - g.InputEventsQueue.push_back(e); -} - -void ImGuiIO::AddMouseButtonEvent(int mouse_button, bool down) -{ - IM_ASSERT(Ctx != NULL); - ImGuiContext& g = *Ctx; - IM_ASSERT(mouse_button >= 0 && mouse_button < ImGuiMouseButton_COUNT); - if (!AppAcceptingEvents) - return; - - // Filter duplicate - const ImGuiInputEvent* latest_event = FindLatestInputEvent(&g, ImGuiInputEventType_MouseButton, (int)mouse_button); - const bool latest_button_down = latest_event ? latest_event->MouseButton.Down : g.IO.MouseDown[mouse_button]; - if (latest_button_down == down) - return; - - ImGuiInputEvent e; - e.Type = ImGuiInputEventType_MouseButton; - e.Source = ImGuiInputSource_Mouse; - e.EventId = g.InputEventsNextEventId++; - e.MouseButton.Button = mouse_button; - e.MouseButton.Down = down; - e.MouseButton.MouseSource = g.InputEventsNextMouseSource; - g.InputEventsQueue.push_back(e); -} - -// Queue a mouse wheel event (some mouse/API may only have a Y component) -void ImGuiIO::AddMouseWheelEvent(float wheel_x, float wheel_y) -{ - IM_ASSERT(Ctx != NULL); - ImGuiContext& g = *Ctx; - - // Filter duplicate (unlike most events, wheel values are relative and easy to filter) - if (!AppAcceptingEvents || (wheel_x == 0.0f && wheel_y == 0.0f)) - return; - - ImGuiInputEvent e; - e.Type = ImGuiInputEventType_MouseWheel; - e.Source = ImGuiInputSource_Mouse; - e.EventId = g.InputEventsNextEventId++; - e.MouseWheel.WheelX = wheel_x; - e.MouseWheel.WheelY = wheel_y; - e.MouseWheel.MouseSource = g.InputEventsNextMouseSource; - g.InputEventsQueue.push_back(e); -} - -// This is not a real event, the data is latched in order to be stored in actual Mouse events. -// This is so that duplicate events (e.g. Windows sending extraneous WM_MOUSEMOVE) gets filtered and are not leading to actual source changes. -void ImGuiIO::AddMouseSourceEvent(ImGuiMouseSource source) -{ - IM_ASSERT(Ctx != NULL); - ImGuiContext& g = *Ctx; - g.InputEventsNextMouseSource = source; -} - -void ImGuiIO::AddMouseViewportEvent(ImGuiID viewport_id) -{ - IM_ASSERT(Ctx != NULL); - ImGuiContext& g = *Ctx; - //IM_ASSERT(g.IO.BackendFlags & ImGuiBackendFlags_HasMouseHoveredViewport); - if (!AppAcceptingEvents) - return; - - // Filter duplicate - const ImGuiInputEvent* latest_event = FindLatestInputEvent(&g, ImGuiInputEventType_MouseViewport); - const ImGuiID latest_viewport_id = latest_event ? latest_event->MouseViewport.HoveredViewportID : g.IO.MouseHoveredViewport; - if (latest_viewport_id == viewport_id) - return; - - ImGuiInputEvent e; - e.Type = ImGuiInputEventType_MouseViewport; - e.Source = ImGuiInputSource_Mouse; - e.MouseViewport.HoveredViewportID = viewport_id; - g.InputEventsQueue.push_back(e); -} - -void ImGuiIO::AddFocusEvent(bool focused) -{ - IM_ASSERT(Ctx != NULL); - ImGuiContext& g = *Ctx; - - // Filter duplicate - const ImGuiInputEvent* latest_event = FindLatestInputEvent(&g, ImGuiInputEventType_Focus); - const bool latest_focused = latest_event ? latest_event->AppFocused.Focused : !g.IO.AppFocusLost; - if (latest_focused == focused || (ConfigDebugIgnoreFocusLoss && !focused)) - return; - - ImGuiInputEvent e; - e.Type = ImGuiInputEventType_Focus; - e.EventId = g.InputEventsNextEventId++; - e.AppFocused.Focused = focused; - g.InputEventsQueue.push_back(e); -} - -//----------------------------------------------------------------------------- -// [SECTION] MISC HELPERS/UTILITIES (Geometry functions) -//----------------------------------------------------------------------------- - -ImVec2 ImBezierCubicClosestPoint(const ImVec2& p1, const ImVec2& p2, const ImVec2& p3, const ImVec2& p4, const ImVec2& p, int num_segments) -{ - IM_ASSERT(num_segments > 0); // Use ImBezierCubicClosestPointCasteljau() - ImVec2 p_last = p1; - ImVec2 p_closest; - float p_closest_dist2 = FLT_MAX; - float t_step = 1.0f / (float)num_segments; - for (int i_step = 1; i_step <= num_segments; i_step++) - { - ImVec2 p_current = ImBezierCubicCalc(p1, p2, p3, p4, t_step * i_step); - ImVec2 p_line = ImLineClosestPoint(p_last, p_current, p); - float dist2 = ImLengthSqr(p - p_line); - if (dist2 < p_closest_dist2) - { - p_closest = p_line; - p_closest_dist2 = dist2; - } - p_last = p_current; - } - return p_closest; -} - -// Closely mimics PathBezierToCasteljau() in imgui_draw.cpp -static void ImBezierCubicClosestPointCasteljauStep(const ImVec2& p, ImVec2& p_closest, ImVec2& p_last, float& p_closest_dist2, float x1, float y1, float x2, float y2, float x3, float y3, float x4, float y4, float tess_tol, int level) -{ - float dx = x4 - x1; - float dy = y4 - y1; - float d2 = ((x2 - x4) * dy - (y2 - y4) * dx); - float d3 = ((x3 - x4) * dy - (y3 - y4) * dx); - d2 = (d2 >= 0) ? d2 : -d2; - d3 = (d3 >= 0) ? d3 : -d3; - if ((d2 + d3) * (d2 + d3) < tess_tol * (dx * dx + dy * dy)) - { - ImVec2 p_current(x4, y4); - ImVec2 p_line = ImLineClosestPoint(p_last, p_current, p); - float dist2 = ImLengthSqr(p - p_line); - if (dist2 < p_closest_dist2) - { - p_closest = p_line; - p_closest_dist2 = dist2; - } - p_last = p_current; - } - else if (level < 10) - { - float x12 = (x1 + x2)*0.5f, y12 = (y1 + y2)*0.5f; - float x23 = (x2 + x3)*0.5f, y23 = (y2 + y3)*0.5f; - float x34 = (x3 + x4)*0.5f, y34 = (y3 + y4)*0.5f; - float x123 = (x12 + x23)*0.5f, y123 = (y12 + y23)*0.5f; - float x234 = (x23 + x34)*0.5f, y234 = (y23 + y34)*0.5f; - float x1234 = (x123 + x234)*0.5f, y1234 = (y123 + y234)*0.5f; - ImBezierCubicClosestPointCasteljauStep(p, p_closest, p_last, p_closest_dist2, x1, y1, x12, y12, x123, y123, x1234, y1234, tess_tol, level + 1); - ImBezierCubicClosestPointCasteljauStep(p, p_closest, p_last, p_closest_dist2, x1234, y1234, x234, y234, x34, y34, x4, y4, tess_tol, level + 1); - } -} - -// tess_tol is generally the same value you would find in ImGui::GetStyle().CurveTessellationTol -// Because those ImXXX functions are lower-level than ImGui:: we cannot access this value automatically. -ImVec2 ImBezierCubicClosestPointCasteljau(const ImVec2& p1, const ImVec2& p2, const ImVec2& p3, const ImVec2& p4, const ImVec2& p, float tess_tol) -{ - IM_ASSERT(tess_tol > 0.0f); - ImVec2 p_last = p1; - ImVec2 p_closest; - float p_closest_dist2 = FLT_MAX; - ImBezierCubicClosestPointCasteljauStep(p, p_closest, p_last, p_closest_dist2, p1.x, p1.y, p2.x, p2.y, p3.x, p3.y, p4.x, p4.y, tess_tol, 0); - return p_closest; -} - -ImVec2 ImLineClosestPoint(const ImVec2& a, const ImVec2& b, const ImVec2& p) -{ - ImVec2 ap = p - a; - ImVec2 ab_dir = b - a; - float dot = ap.x * ab_dir.x + ap.y * ab_dir.y; - if (dot < 0.0f) - return a; - float ab_len_sqr = ab_dir.x * ab_dir.x + ab_dir.y * ab_dir.y; - if (dot > ab_len_sqr) - return b; - return a + ab_dir * dot / ab_len_sqr; -} - -bool ImTriangleContainsPoint(const ImVec2& a, const ImVec2& b, const ImVec2& c, const ImVec2& p) -{ - bool b1 = ((p.x - b.x) * (a.y - b.y) - (p.y - b.y) * (a.x - b.x)) < 0.0f; - bool b2 = ((p.x - c.x) * (b.y - c.y) - (p.y - c.y) * (b.x - c.x)) < 0.0f; - bool b3 = ((p.x - a.x) * (c.y - a.y) - (p.y - a.y) * (c.x - a.x)) < 0.0f; - return ((b1 == b2) && (b2 == b3)); -} - -void ImTriangleBarycentricCoords(const ImVec2& a, const ImVec2& b, const ImVec2& c, const ImVec2& p, float& out_u, float& out_v, float& out_w) -{ - ImVec2 v0 = b - a; - ImVec2 v1 = c - a; - ImVec2 v2 = p - a; - const float denom = v0.x * v1.y - v1.x * v0.y; - out_v = (v2.x * v1.y - v1.x * v2.y) / denom; - out_w = (v0.x * v2.y - v2.x * v0.y) / denom; - out_u = 1.0f - out_v - out_w; -} - -ImVec2 ImTriangleClosestPoint(const ImVec2& a, const ImVec2& b, const ImVec2& c, const ImVec2& p) -{ - ImVec2 proj_ab = ImLineClosestPoint(a, b, p); - ImVec2 proj_bc = ImLineClosestPoint(b, c, p); - ImVec2 proj_ca = ImLineClosestPoint(c, a, p); - float dist2_ab = ImLengthSqr(p - proj_ab); - float dist2_bc = ImLengthSqr(p - proj_bc); - float dist2_ca = ImLengthSqr(p - proj_ca); - float m = ImMin(dist2_ab, ImMin(dist2_bc, dist2_ca)); - if (m == dist2_ab) - return proj_ab; - if (m == dist2_bc) - return proj_bc; - return proj_ca; -} - -//----------------------------------------------------------------------------- -// [SECTION] MISC HELPERS/UTILITIES (String, Format, Hash functions) -//----------------------------------------------------------------------------- - -// Consider using _stricmp/_strnicmp under Windows or strcasecmp/strncasecmp. We don't actually use either ImStricmp/ImStrnicmp in the codebase any more. -int ImStricmp(const char* str1, const char* str2) -{ - int d; - while ((d = ImToUpper(*str2) - ImToUpper(*str1)) == 0 && *str1) { str1++; str2++; } - return d; -} - -int ImStrnicmp(const char* str1, const char* str2, size_t count) -{ - int d = 0; - while (count > 0 && (d = ImToUpper(*str2) - ImToUpper(*str1)) == 0 && *str1) { str1++; str2++; count--; } - return d; -} - -void ImStrncpy(char* dst, const char* src, size_t count) -{ - if (count < 1) - return; - if (count > 1) - strncpy(dst, src, count - 1); - dst[count - 1] = 0; -} - -char* ImStrdup(const char* str) -{ - size_t len = strlen(str); - void* buf = IM_ALLOC(len + 1); - return (char*)memcpy(buf, (const void*)str, len + 1); -} - -char* ImStrdupcpy(char* dst, size_t* p_dst_size, const char* src) -{ - size_t dst_buf_size = p_dst_size ? *p_dst_size : strlen(dst) + 1; - size_t src_size = strlen(src) + 1; - if (dst_buf_size < src_size) - { - IM_FREE(dst); - dst = (char*)IM_ALLOC(src_size); - if (p_dst_size) - *p_dst_size = src_size; - } - return (char*)memcpy(dst, (const void*)src, src_size); -} - -const char* ImStrchrRange(const char* str, const char* str_end, char c) -{ - const char* p = (const char*)memchr(str, (int)c, str_end - str); - return p; -} - -int ImStrlenW(const ImWchar* str) -{ - //return (int)wcslen((const wchar_t*)str); // FIXME-OPT: Could use this when wchar_t are 16-bit - int n = 0; - while (*str++) n++; - return n; -} - -// Find end-of-line. Return pointer will point to either first \n, either str_end. -const char* ImStreolRange(const char* str, const char* str_end) -{ - const char* p = (const char*)memchr(str, '\n', str_end - str); - return p ? p : str_end; -} - -const ImWchar* ImStrbolW(const ImWchar* buf_mid_line, const ImWchar* buf_begin) // find beginning-of-line -{ - while (buf_mid_line > buf_begin && buf_mid_line[-1] != '\n') - buf_mid_line--; - return buf_mid_line; -} - -const char* ImStristr(const char* haystack, const char* haystack_end, const char* needle, const char* needle_end) -{ - if (!needle_end) - needle_end = needle + strlen(needle); - - const char un0 = (char)ImToUpper(*needle); - while ((!haystack_end && *haystack) || (haystack_end && haystack < haystack_end)) - { - if (ImToUpper(*haystack) == un0) - { - const char* b = needle + 1; - for (const char* a = haystack + 1; b < needle_end; a++, b++) - if (ImToUpper(*a) != ImToUpper(*b)) - break; - if (b == needle_end) - return haystack; - } - haystack++; - } - return NULL; -} - -// Trim str by offsetting contents when there's leading data + writing a \0 at the trailing position. We use this in situation where the cost is negligible. -void ImStrTrimBlanks(char* buf) -{ - char* p = buf; - while (p[0] == ' ' || p[0] == '\t') // Leading blanks - p++; - char* p_start = p; - while (*p != 0) // Find end of string - p++; - while (p > p_start && (p[-1] == ' ' || p[-1] == '\t')) // Trailing blanks - p--; - if (p_start != buf) // Copy memory if we had leading blanks - memmove(buf, p_start, p - p_start); - buf[p - p_start] = 0; // Zero terminate -} - -const char* ImStrSkipBlank(const char* str) -{ - while (str[0] == ' ' || str[0] == '\t') - str++; - return str; -} - -// A) MSVC version appears to return -1 on overflow, whereas glibc appears to return total count (which may be >= buf_size). -// Ideally we would test for only one of those limits at runtime depending on the behavior the vsnprintf(), but trying to deduct it at compile time sounds like a pandora can of worm. -// B) When buf==NULL vsnprintf() will return the output size. -#ifndef IMGUI_DISABLE_DEFAULT_FORMAT_FUNCTIONS - -// We support stb_sprintf which is much faster (see: https://github.com/nothings/stb/blob/master/stb_sprintf.h) -// You may set IMGUI_USE_STB_SPRINTF to use our default wrapper, or set IMGUI_DISABLE_DEFAULT_FORMAT_FUNCTIONS -// and setup the wrapper yourself. (FIXME-OPT: Some of our high-level operations such as ImGuiTextBuffer::appendfv() are -// designed using two-passes worst case, which probably could be improved using the stbsp_vsprintfcb() function.) -#ifdef IMGUI_USE_STB_SPRINTF -#ifndef IMGUI_DISABLE_STB_SPRINTF_IMPLEMENTATION -#define STB_SPRINTF_IMPLEMENTATION -#endif -#ifdef IMGUI_STB_SPRINTF_FILENAME -#include IMGUI_STB_SPRINTF_FILENAME -#else -#include "stb_sprintf.h" -#endif -#endif // #ifdef IMGUI_USE_STB_SPRINTF - -#if defined(_MSC_VER) && !defined(vsnprintf) -#define vsnprintf _vsnprintf -#endif - -int ImFormatString(char* buf, size_t buf_size, const char* fmt, ...) -{ - va_list args; - va_start(args, fmt); -#ifdef IMGUI_USE_STB_SPRINTF - int w = stbsp_vsnprintf(buf, (int)buf_size, fmt, args); -#else - int w = vsnprintf(buf, buf_size, fmt, args); -#endif - va_end(args); - if (buf == NULL) - return w; - if (w == -1 || w >= (int)buf_size) - w = (int)buf_size - 1; - buf[w] = 0; - return w; -} - -int ImFormatStringV(char* buf, size_t buf_size, const char* fmt, va_list args) -{ -#ifdef IMGUI_USE_STB_SPRINTF - int w = stbsp_vsnprintf(buf, (int)buf_size, fmt, args); -#else - int w = vsnprintf(buf, buf_size, fmt, args); -#endif - if (buf == NULL) - return w; - if (w == -1 || w >= (int)buf_size) - w = (int)buf_size - 1; - buf[w] = 0; - return w; -} -#endif // #ifdef IMGUI_DISABLE_DEFAULT_FORMAT_FUNCTIONS - -void ImFormatStringToTempBuffer(const char** out_buf, const char** out_buf_end, const char* fmt, ...) -{ - va_list args; - va_start(args, fmt); - ImFormatStringToTempBufferV(out_buf, out_buf_end, fmt, args); - va_end(args); -} - -void ImFormatStringToTempBufferV(const char** out_buf, const char** out_buf_end, const char* fmt, va_list args) -{ - ImGuiContext& g = *GImGui; - if (fmt[0] == '%' && fmt[1] == 's' && fmt[2] == 0) - { - const char* buf = va_arg(args, const char*); // Skip formatting when using "%s" - *out_buf = buf; - if (out_buf_end) { *out_buf_end = buf + strlen(buf); } - } - else if (fmt[0] == '%' && fmt[1] == '.' && fmt[2] == '*' && fmt[3] == 's' && fmt[4] == 0) - { - int buf_len = va_arg(args, int); // Skip formatting when using "%.*s" - const char* buf = va_arg(args, const char*); - *out_buf = buf; - *out_buf_end = buf + buf_len; // Disallow not passing 'out_buf_end' here. User is expected to use it. - } - else - { - int buf_len = ImFormatStringV(g.TempBuffer.Data, g.TempBuffer.Size, fmt, args); - *out_buf = g.TempBuffer.Data; - if (out_buf_end) { *out_buf_end = g.TempBuffer.Data + buf_len; } - } -} - -// CRC32 needs a 1KB lookup table (not cache friendly) -// Although the code to generate the table is simple and shorter than the table itself, using a const table allows us to easily: -// - avoid an unnecessary branch/memory tap, - keep the ImHashXXX functions usable by static constructors, - make it thread-safe. -static const ImU32 GCrc32LookupTable[256] = -{ - 0x00000000,0x77073096,0xEE0E612C,0x990951BA,0x076DC419,0x706AF48F,0xE963A535,0x9E6495A3,0x0EDB8832,0x79DCB8A4,0xE0D5E91E,0x97D2D988,0x09B64C2B,0x7EB17CBD,0xE7B82D07,0x90BF1D91, - 0x1DB71064,0x6AB020F2,0xF3B97148,0x84BE41DE,0x1ADAD47D,0x6DDDE4EB,0xF4D4B551,0x83D385C7,0x136C9856,0x646BA8C0,0xFD62F97A,0x8A65C9EC,0x14015C4F,0x63066CD9,0xFA0F3D63,0x8D080DF5, - 0x3B6E20C8,0x4C69105E,0xD56041E4,0xA2677172,0x3C03E4D1,0x4B04D447,0xD20D85FD,0xA50AB56B,0x35B5A8FA,0x42B2986C,0xDBBBC9D6,0xACBCF940,0x32D86CE3,0x45DF5C75,0xDCD60DCF,0xABD13D59, - 0x26D930AC,0x51DE003A,0xC8D75180,0xBFD06116,0x21B4F4B5,0x56B3C423,0xCFBA9599,0xB8BDA50F,0x2802B89E,0x5F058808,0xC60CD9B2,0xB10BE924,0x2F6F7C87,0x58684C11,0xC1611DAB,0xB6662D3D, - 0x76DC4190,0x01DB7106,0x98D220BC,0xEFD5102A,0x71B18589,0x06B6B51F,0x9FBFE4A5,0xE8B8D433,0x7807C9A2,0x0F00F934,0x9609A88E,0xE10E9818,0x7F6A0DBB,0x086D3D2D,0x91646C97,0xE6635C01, - 0x6B6B51F4,0x1C6C6162,0x856530D8,0xF262004E,0x6C0695ED,0x1B01A57B,0x8208F4C1,0xF50FC457,0x65B0D9C6,0x12B7E950,0x8BBEB8EA,0xFCB9887C,0x62DD1DDF,0x15DA2D49,0x8CD37CF3,0xFBD44C65, - 0x4DB26158,0x3AB551CE,0xA3BC0074,0xD4BB30E2,0x4ADFA541,0x3DD895D7,0xA4D1C46D,0xD3D6F4FB,0x4369E96A,0x346ED9FC,0xAD678846,0xDA60B8D0,0x44042D73,0x33031DE5,0xAA0A4C5F,0xDD0D7CC9, - 0x5005713C,0x270241AA,0xBE0B1010,0xC90C2086,0x5768B525,0x206F85B3,0xB966D409,0xCE61E49F,0x5EDEF90E,0x29D9C998,0xB0D09822,0xC7D7A8B4,0x59B33D17,0x2EB40D81,0xB7BD5C3B,0xC0BA6CAD, - 0xEDB88320,0x9ABFB3B6,0x03B6E20C,0x74B1D29A,0xEAD54739,0x9DD277AF,0x04DB2615,0x73DC1683,0xE3630B12,0x94643B84,0x0D6D6A3E,0x7A6A5AA8,0xE40ECF0B,0x9309FF9D,0x0A00AE27,0x7D079EB1, - 0xF00F9344,0x8708A3D2,0x1E01F268,0x6906C2FE,0xF762575D,0x806567CB,0x196C3671,0x6E6B06E7,0xFED41B76,0x89D32BE0,0x10DA7A5A,0x67DD4ACC,0xF9B9DF6F,0x8EBEEFF9,0x17B7BE43,0x60B08ED5, - 0xD6D6A3E8,0xA1D1937E,0x38D8C2C4,0x4FDFF252,0xD1BB67F1,0xA6BC5767,0x3FB506DD,0x48B2364B,0xD80D2BDA,0xAF0A1B4C,0x36034AF6,0x41047A60,0xDF60EFC3,0xA867DF55,0x316E8EEF,0x4669BE79, - 0xCB61B38C,0xBC66831A,0x256FD2A0,0x5268E236,0xCC0C7795,0xBB0B4703,0x220216B9,0x5505262F,0xC5BA3BBE,0xB2BD0B28,0x2BB45A92,0x5CB36A04,0xC2D7FFA7,0xB5D0CF31,0x2CD99E8B,0x5BDEAE1D, - 0x9B64C2B0,0xEC63F226,0x756AA39C,0x026D930A,0x9C0906A9,0xEB0E363F,0x72076785,0x05005713,0x95BF4A82,0xE2B87A14,0x7BB12BAE,0x0CB61B38,0x92D28E9B,0xE5D5BE0D,0x7CDCEFB7,0x0BDBDF21, - 0x86D3D2D4,0xF1D4E242,0x68DDB3F8,0x1FDA836E,0x81BE16CD,0xF6B9265B,0x6FB077E1,0x18B74777,0x88085AE6,0xFF0F6A70,0x66063BCA,0x11010B5C,0x8F659EFF,0xF862AE69,0x616BFFD3,0x166CCF45, - 0xA00AE278,0xD70DD2EE,0x4E048354,0x3903B3C2,0xA7672661,0xD06016F7,0x4969474D,0x3E6E77DB,0xAED16A4A,0xD9D65ADC,0x40DF0B66,0x37D83BF0,0xA9BCAE53,0xDEBB9EC5,0x47B2CF7F,0x30B5FFE9, - 0xBDBDF21C,0xCABAC28A,0x53B39330,0x24B4A3A6,0xBAD03605,0xCDD70693,0x54DE5729,0x23D967BF,0xB3667A2E,0xC4614AB8,0x5D681B02,0x2A6F2B94,0xB40BBE37,0xC30C8EA1,0x5A05DF1B,0x2D02EF8D, -}; - -// Known size hash -// It is ok to call ImHashData on a string with known length but the ### operator won't be supported. -// FIXME-OPT: Replace with e.g. FNV1a hash? CRC32 pretty much randomly access 1KB. Need to do proper measurements. -ImGuiID ImHashData(const void* data_p, size_t data_size, ImGuiID seed) -{ - ImU32 crc = ~seed; - const unsigned char* data = (const unsigned char*)data_p; - const ImU32* crc32_lut = GCrc32LookupTable; - while (data_size-- != 0) - crc = (crc >> 8) ^ crc32_lut[(crc & 0xFF) ^ *data++]; - return ~crc; -} - -// Zero-terminated string hash, with support for ### to reset back to seed value -// We support a syntax of "label###id" where only "###id" is included in the hash, and only "label" gets displayed. -// Because this syntax is rarely used we are optimizing for the common case. -// - If we reach ### in the string we discard the hash so far and reset to the seed. -// - We don't do 'current += 2; continue;' after handling ### to keep the code smaller/faster (measured ~10% diff in Debug build) -// FIXME-OPT: Replace with e.g. FNV1a hash? CRC32 pretty much randomly access 1KB. Need to do proper measurements. -ImGuiID ImHashStr(const char* data_p, size_t data_size, ImGuiID seed) -{ - seed = ~seed; - ImU32 crc = seed; - const unsigned char* data = (const unsigned char*)data_p; - const ImU32* crc32_lut = GCrc32LookupTable; - if (data_size != 0) - { - while (data_size-- != 0) - { - unsigned char c = *data++; - if (c == '#' && data_size >= 2 && data[0] == '#' && data[1] == '#') - crc = seed; - crc = (crc >> 8) ^ crc32_lut[(crc & 0xFF) ^ c]; - } - } - else - { - while (unsigned char c = *data++) - { - if (c == '#' && data[0] == '#' && data[1] == '#') - crc = seed; - crc = (crc >> 8) ^ crc32_lut[(crc & 0xFF) ^ c]; - } - } - return ~crc; -} - -//----------------------------------------------------------------------------- -// [SECTION] MISC HELPERS/UTILITIES (File functions) -//----------------------------------------------------------------------------- - -// Default file functions -#ifndef IMGUI_DISABLE_DEFAULT_FILE_FUNCTIONS - -ImFileHandle ImFileOpen(const char* filename, const char* mode) -{ -#if defined(_WIN32) && !defined(IMGUI_DISABLE_WIN32_FUNCTIONS) && !defined(__CYGWIN__) && !defined(__GNUC__) - // We need a fopen() wrapper because MSVC/Windows fopen doesn't handle UTF-8 filenames. - // Previously we used ImTextCountCharsFromUtf8/ImTextStrFromUtf8 here but we now need to support ImWchar16 and ImWchar32! - const int filename_wsize = ::MultiByteToWideChar(CP_UTF8, 0, filename, -1, NULL, 0); - const int mode_wsize = ::MultiByteToWideChar(CP_UTF8, 0, mode, -1, NULL, 0); - ImGuiContext& g = *GImGui; - g.TempBuffer.reserve((filename_wsize + mode_wsize) * sizeof(wchar_t)); - wchar_t* buf = (wchar_t*)(void*)g.TempBuffer.Data; - ::MultiByteToWideChar(CP_UTF8, 0, filename, -1, (wchar_t*)&buf[0], filename_wsize); - ::MultiByteToWideChar(CP_UTF8, 0, mode, -1, (wchar_t*)&buf[filename_wsize], mode_wsize); - return ::_wfopen((const wchar_t*)&buf[0], (const wchar_t*)&buf[filename_wsize]); -#else - return fopen(filename, mode); -#endif -} - -// We should in theory be using fseeko()/ftello() with off_t and _fseeki64()/_ftelli64() with __int64, waiting for the PR that does that in a very portable pre-C++11 zero-warnings way. -bool ImFileClose(ImFileHandle f) { return fclose(f) == 0; } -ImU64 ImFileGetSize(ImFileHandle f) { long off = 0, sz = 0; return ((off = ftell(f)) != -1 && !fseek(f, 0, SEEK_END) && (sz = ftell(f)) != -1 && !fseek(f, off, SEEK_SET)) ? (ImU64)sz : (ImU64)-1; } -ImU64 ImFileRead(void* data, ImU64 sz, ImU64 count, ImFileHandle f) { return fread(data, (size_t)sz, (size_t)count, f); } -ImU64 ImFileWrite(const void* data, ImU64 sz, ImU64 count, ImFileHandle f) { return fwrite(data, (size_t)sz, (size_t)count, f); } -#endif // #ifndef IMGUI_DISABLE_DEFAULT_FILE_FUNCTIONS - -// Helper: Load file content into memory -// Memory allocated with IM_ALLOC(), must be freed by user using IM_FREE() == ImGui::MemFree() -// This can't really be used with "rt" because fseek size won't match read size. -void* ImFileLoadToMemory(const char* filename, const char* mode, size_t* out_file_size, int padding_bytes) -{ - IM_ASSERT(filename && mode); - if (out_file_size) - *out_file_size = 0; - - ImFileHandle f; - if ((f = ImFileOpen(filename, mode)) == NULL) - return NULL; - - size_t file_size = (size_t)ImFileGetSize(f); - if (file_size == (size_t)-1) - { - ImFileClose(f); - return NULL; - } - - void* file_data = IM_ALLOC(file_size + padding_bytes); - if (file_data == NULL) - { - ImFileClose(f); - return NULL; - } - if (ImFileRead(file_data, 1, file_size, f) != file_size) - { - ImFileClose(f); - IM_FREE(file_data); - return NULL; - } - if (padding_bytes > 0) - memset((void*)(((char*)file_data) + file_size), 0, (size_t)padding_bytes); - - ImFileClose(f); - if (out_file_size) - *out_file_size = file_size; - - return file_data; -} - -//----------------------------------------------------------------------------- -// [SECTION] MISC HELPERS/UTILITIES (ImText* functions) -//----------------------------------------------------------------------------- - -IM_MSVC_RUNTIME_CHECKS_OFF - -// Convert UTF-8 to 32-bit character, process single character input. -// A nearly-branchless UTF-8 decoder, based on work of Christopher Wellons (https://github.com/skeeto/branchless-utf8). -// We handle UTF-8 decoding error by skipping forward. -int ImTextCharFromUtf8(unsigned int* out_char, const char* in_text, const char* in_text_end) -{ - static const char lengths[32] = { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 2, 2, 2, 2, 3, 3, 4, 0 }; - static const int masks[] = { 0x00, 0x7f, 0x1f, 0x0f, 0x07 }; - static const uint32_t mins[] = { 0x400000, 0, 0x80, 0x800, 0x10000 }; - static const int shiftc[] = { 0, 18, 12, 6, 0 }; - static const int shifte[] = { 0, 6, 4, 2, 0 }; - int len = lengths[*(const unsigned char*)in_text >> 3]; - int wanted = len + (len ? 0 : 1); - - if (in_text_end == NULL) - in_text_end = in_text + wanted; // Max length, nulls will be taken into account. - - // Copy at most 'len' bytes, stop copying at 0 or past in_text_end. Branch predictor does a good job here, - // so it is fast even with excessive branching. - unsigned char s[4]; - s[0] = in_text + 0 < in_text_end ? in_text[0] : 0; - s[1] = in_text + 1 < in_text_end ? in_text[1] : 0; - s[2] = in_text + 2 < in_text_end ? in_text[2] : 0; - s[3] = in_text + 3 < in_text_end ? in_text[3] : 0; - - // Assume a four-byte character and load four bytes. Unused bits are shifted out. - *out_char = (uint32_t)(s[0] & masks[len]) << 18; - *out_char |= (uint32_t)(s[1] & 0x3f) << 12; - *out_char |= (uint32_t)(s[2] & 0x3f) << 6; - *out_char |= (uint32_t)(s[3] & 0x3f) << 0; - *out_char >>= shiftc[len]; - - // Accumulate the various error conditions. - int e = 0; - e = (*out_char < mins[len]) << 6; // non-canonical encoding - e |= ((*out_char >> 11) == 0x1b) << 7; // surrogate half? - e |= (*out_char > IM_UNICODE_CODEPOINT_MAX) << 8; // out of range? - e |= (s[1] & 0xc0) >> 2; - e |= (s[2] & 0xc0) >> 4; - e |= (s[3] ) >> 6; - e ^= 0x2a; // top two bits of each tail byte correct? - e >>= shifte[len]; - - if (e) - { - // No bytes are consumed when *in_text == 0 || in_text == in_text_end. - // One byte is consumed in case of invalid first byte of in_text. - // All available bytes (at most `len` bytes) are consumed on incomplete/invalid second to last bytes. - // Invalid or incomplete input may consume less bytes than wanted, therefore every byte has to be inspected in s. - wanted = ImMin(wanted, !!s[0] + !!s[1] + !!s[2] + !!s[3]); - *out_char = IM_UNICODE_CODEPOINT_INVALID; - } - - return wanted; -} - -int ImTextStrFromUtf8(ImWchar* buf, int buf_size, const char* in_text, const char* in_text_end, const char** in_text_remaining) -{ - ImWchar* buf_out = buf; - ImWchar* buf_end = buf + buf_size; - while (buf_out < buf_end - 1 && (!in_text_end || in_text < in_text_end) && *in_text) - { - unsigned int c; - in_text += ImTextCharFromUtf8(&c, in_text, in_text_end); - *buf_out++ = (ImWchar)c; - } - *buf_out = 0; - if (in_text_remaining) - *in_text_remaining = in_text; - return (int)(buf_out - buf); -} - -int ImTextCountCharsFromUtf8(const char* in_text, const char* in_text_end) -{ - int char_count = 0; - while ((!in_text_end || in_text < in_text_end) && *in_text) - { - unsigned int c; - in_text += ImTextCharFromUtf8(&c, in_text, in_text_end); - char_count++; - } - return char_count; -} - -// Based on stb_to_utf8() from github.com/nothings/stb/ -static inline int ImTextCharToUtf8_inline(char* buf, int buf_size, unsigned int c) -{ - if (c < 0x80) - { - buf[0] = (char)c; - return 1; - } - if (c < 0x800) - { - if (buf_size < 2) return 0; - buf[0] = (char)(0xc0 + (c >> 6)); - buf[1] = (char)(0x80 + (c & 0x3f)); - return 2; - } - if (c < 0x10000) - { - if (buf_size < 3) return 0; - buf[0] = (char)(0xe0 + (c >> 12)); - buf[1] = (char)(0x80 + ((c >> 6) & 0x3f)); - buf[2] = (char)(0x80 + ((c ) & 0x3f)); - return 3; - } - if (c <= 0x10FFFF) - { - if (buf_size < 4) return 0; - buf[0] = (char)(0xf0 + (c >> 18)); - buf[1] = (char)(0x80 + ((c >> 12) & 0x3f)); - buf[2] = (char)(0x80 + ((c >> 6) & 0x3f)); - buf[3] = (char)(0x80 + ((c ) & 0x3f)); - return 4; - } - // Invalid code point, the max unicode is 0x10FFFF - return 0; -} - -const char* ImTextCharToUtf8(char out_buf[5], unsigned int c) -{ - int count = ImTextCharToUtf8_inline(out_buf, 5, c); - out_buf[count] = 0; - return out_buf; -} - -// Not optimal but we very rarely use this function. -int ImTextCountUtf8BytesFromChar(const char* in_text, const char* in_text_end) -{ - unsigned int unused = 0; - return ImTextCharFromUtf8(&unused, in_text, in_text_end); -} - -static inline int ImTextCountUtf8BytesFromChar(unsigned int c) -{ - if (c < 0x80) return 1; - if (c < 0x800) return 2; - if (c < 0x10000) return 3; - if (c <= 0x10FFFF) return 4; - return 3; -} - -int ImTextStrToUtf8(char* out_buf, int out_buf_size, const ImWchar* in_text, const ImWchar* in_text_end) -{ - char* buf_p = out_buf; - const char* buf_end = out_buf + out_buf_size; - while (buf_p < buf_end - 1 && (!in_text_end || in_text < in_text_end) && *in_text) - { - unsigned int c = (unsigned int)(*in_text++); - if (c < 0x80) - *buf_p++ = (char)c; - else - buf_p += ImTextCharToUtf8_inline(buf_p, (int)(buf_end - buf_p - 1), c); - } - *buf_p = 0; - return (int)(buf_p - out_buf); -} - -int ImTextCountUtf8BytesFromStr(const ImWchar* in_text, const ImWchar* in_text_end) -{ - int bytes_count = 0; - while ((!in_text_end || in_text < in_text_end) && *in_text) - { - unsigned int c = (unsigned int)(*in_text++); - if (c < 0x80) - bytes_count++; - else - bytes_count += ImTextCountUtf8BytesFromChar(c); - } - return bytes_count; -} - -const char* ImTextFindPreviousUtf8Codepoint(const char* in_text_start, const char* in_text_curr) -{ - while (in_text_curr > in_text_start) - { - in_text_curr--; - if ((*in_text_curr & 0xC0) != 0x80) - return in_text_curr; - } - return in_text_start; -} - -IM_MSVC_RUNTIME_CHECKS_RESTORE - -//----------------------------------------------------------------------------- -// [SECTION] MISC HELPERS/UTILITIES (Color functions) -// Note: The Convert functions are early design which are not consistent with other API. -//----------------------------------------------------------------------------- - -IMGUI_API ImU32 ImAlphaBlendColors(ImU32 col_a, ImU32 col_b) -{ - float t = ((col_b >> IM_COL32_A_SHIFT) & 0xFF) / 255.f; - int r = ImLerp((int)(col_a >> IM_COL32_R_SHIFT) & 0xFF, (int)(col_b >> IM_COL32_R_SHIFT) & 0xFF, t); - int g = ImLerp((int)(col_a >> IM_COL32_G_SHIFT) & 0xFF, (int)(col_b >> IM_COL32_G_SHIFT) & 0xFF, t); - int b = ImLerp((int)(col_a >> IM_COL32_B_SHIFT) & 0xFF, (int)(col_b >> IM_COL32_B_SHIFT) & 0xFF, t); - return IM_COL32(r, g, b, 0xFF); -} - -ImVec4 ImGui::ColorConvertU32ToFloat4(ImU32 in) -{ - float s = 1.0f / 255.0f; - return ImVec4( - ((in >> IM_COL32_R_SHIFT) & 0xFF) * s, - ((in >> IM_COL32_G_SHIFT) & 0xFF) * s, - ((in >> IM_COL32_B_SHIFT) & 0xFF) * s, - ((in >> IM_COL32_A_SHIFT) & 0xFF) * s); -} - -ImU32 ImGui::ColorConvertFloat4ToU32(const ImVec4& in) -{ - ImU32 out; - out = ((ImU32)IM_F32_TO_INT8_SAT(in.x)) << IM_COL32_R_SHIFT; - out |= ((ImU32)IM_F32_TO_INT8_SAT(in.y)) << IM_COL32_G_SHIFT; - out |= ((ImU32)IM_F32_TO_INT8_SAT(in.z)) << IM_COL32_B_SHIFT; - out |= ((ImU32)IM_F32_TO_INT8_SAT(in.w)) << IM_COL32_A_SHIFT; - return out; -} - -// Convert rgb floats ([0-1],[0-1],[0-1]) to hsv floats ([0-1],[0-1],[0-1]), from Foley & van Dam p592 -// Optimized http://lolengine.net/blog/2013/01/13/fast-rgb-to-hsv -void ImGui::ColorConvertRGBtoHSV(float r, float g, float b, float& out_h, float& out_s, float& out_v) -{ - float K = 0.f; - if (g < b) - { - ImSwap(g, b); - K = -1.f; - } - if (r < g) - { - ImSwap(r, g); - K = -2.f / 6.f - K; - } - - const float chroma = r - (g < b ? g : b); - out_h = ImFabs(K + (g - b) / (6.f * chroma + 1e-20f)); - out_s = chroma / (r + 1e-20f); - out_v = r; -} - -// Convert hsv floats ([0-1],[0-1],[0-1]) to rgb floats ([0-1],[0-1],[0-1]), from Foley & van Dam p593 -// also http://en.wikipedia.org/wiki/HSL_and_HSV -void ImGui::ColorConvertHSVtoRGB(float h, float s, float v, float& out_r, float& out_g, float& out_b) -{ - if (s == 0.0f) - { - // gray - out_r = out_g = out_b = v; - return; - } - - h = ImFmod(h, 1.0f) / (60.0f / 360.0f); - int i = (int)h; - float f = h - (float)i; - float p = v * (1.0f - s); - float q = v * (1.0f - s * f); - float t = v * (1.0f - s * (1.0f - f)); - - switch (i) - { - case 0: out_r = v; out_g = t; out_b = p; break; - case 1: out_r = q; out_g = v; out_b = p; break; - case 2: out_r = p; out_g = v; out_b = t; break; - case 3: out_r = p; out_g = q; out_b = v; break; - case 4: out_r = t; out_g = p; out_b = v; break; - case 5: default: out_r = v; out_g = p; out_b = q; break; - } -} - -//----------------------------------------------------------------------------- -// [SECTION] ImGuiStorage -// Helper: Key->value storage -//----------------------------------------------------------------------------- - -// std::lower_bound but without the bullshit -static ImGuiStorage::ImGuiStoragePair* LowerBound(ImVector& data, ImGuiID key) -{ - ImGuiStorage::ImGuiStoragePair* first = data.Data; - ImGuiStorage::ImGuiStoragePair* last = data.Data + data.Size; - size_t count = (size_t)(last - first); - while (count > 0) - { - size_t count2 = count >> 1; - ImGuiStorage::ImGuiStoragePair* mid = first + count2; - if (mid->key < key) - { - first = ++mid; - count -= count2 + 1; - } - else - { - count = count2; - } - } - return first; -} - -// For quicker full rebuild of a storage (instead of an incremental one), you may add all your contents and then sort once. -void ImGuiStorage::BuildSortByKey() -{ - struct StaticFunc - { - static int IMGUI_CDECL PairComparerByID(const void* lhs, const void* rhs) - { - // We can't just do a subtraction because qsort uses signed integers and subtracting our ID doesn't play well with that. - if (((const ImGuiStoragePair*)lhs)->key > ((const ImGuiStoragePair*)rhs)->key) return +1; - if (((const ImGuiStoragePair*)lhs)->key < ((const ImGuiStoragePair*)rhs)->key) return -1; - return 0; - } - }; - ImQsort(Data.Data, (size_t)Data.Size, sizeof(ImGuiStoragePair), StaticFunc::PairComparerByID); -} - -int ImGuiStorage::GetInt(ImGuiID key, int default_val) const -{ - ImGuiStoragePair* it = LowerBound(const_cast&>(Data), key); - if (it == Data.end() || it->key != key) - return default_val; - return it->val_i; -} - -bool ImGuiStorage::GetBool(ImGuiID key, bool default_val) const -{ - return GetInt(key, default_val ? 1 : 0) != 0; -} - -float ImGuiStorage::GetFloat(ImGuiID key, float default_val) const -{ - ImGuiStoragePair* it = LowerBound(const_cast&>(Data), key); - if (it == Data.end() || it->key != key) - return default_val; - return it->val_f; -} - -void* ImGuiStorage::GetVoidPtr(ImGuiID key) const -{ - ImGuiStoragePair* it = LowerBound(const_cast&>(Data), key); - if (it == Data.end() || it->key != key) - return NULL; - return it->val_p; -} - -// References are only valid until a new value is added to the storage. Calling a Set***() function or a Get***Ref() function invalidates the pointer. -int* ImGuiStorage::GetIntRef(ImGuiID key, int default_val) -{ - ImGuiStoragePair* it = LowerBound(Data, key); - if (it == Data.end() || it->key != key) - it = Data.insert(it, ImGuiStoragePair(key, default_val)); - return &it->val_i; -} - -bool* ImGuiStorage::GetBoolRef(ImGuiID key, bool default_val) -{ - return (bool*)GetIntRef(key, default_val ? 1 : 0); -} - -float* ImGuiStorage::GetFloatRef(ImGuiID key, float default_val) -{ - ImGuiStoragePair* it = LowerBound(Data, key); - if (it == Data.end() || it->key != key) - it = Data.insert(it, ImGuiStoragePair(key, default_val)); - return &it->val_f; -} - -void** ImGuiStorage::GetVoidPtrRef(ImGuiID key, void* default_val) -{ - ImGuiStoragePair* it = LowerBound(Data, key); - if (it == Data.end() || it->key != key) - it = Data.insert(it, ImGuiStoragePair(key, default_val)); - return &it->val_p; -} - -// FIXME-OPT: Need a way to reuse the result of lower_bound when doing GetInt()/SetInt() - not too bad because it only happens on explicit interaction (maximum one a frame) -void ImGuiStorage::SetInt(ImGuiID key, int val) -{ - ImGuiStoragePair* it = LowerBound(Data, key); - if (it == Data.end() || it->key != key) - { - Data.insert(it, ImGuiStoragePair(key, val)); - return; - } - it->val_i = val; -} - -void ImGuiStorage::SetBool(ImGuiID key, bool val) -{ - SetInt(key, val ? 1 : 0); -} - -void ImGuiStorage::SetFloat(ImGuiID key, float val) -{ - ImGuiStoragePair* it = LowerBound(Data, key); - if (it == Data.end() || it->key != key) - { - Data.insert(it, ImGuiStoragePair(key, val)); - return; - } - it->val_f = val; -} - -void ImGuiStorage::SetVoidPtr(ImGuiID key, void* val) -{ - ImGuiStoragePair* it = LowerBound(Data, key); - if (it == Data.end() || it->key != key) - { - Data.insert(it, ImGuiStoragePair(key, val)); - return; - } - it->val_p = val; -} - -void ImGuiStorage::SetAllInt(int v) -{ - for (int i = 0; i < Data.Size; i++) - Data[i].val_i = v; -} - -//----------------------------------------------------------------------------- -// [SECTION] ImGuiTextFilter -//----------------------------------------------------------------------------- - -// Helper: Parse and apply text filters. In format "aaaaa[,bbbb][,ccccc]" -ImGuiTextFilter::ImGuiTextFilter(const char* default_filter) //-V1077 -{ - InputBuf[0] = 0; - CountGrep = 0; - if (default_filter) - { - ImStrncpy(InputBuf, default_filter, IM_ARRAYSIZE(InputBuf)); - Build(); - } -} - -bool ImGuiTextFilter::Draw(const char* label, float width) -{ - if (width != 0.0f) - ImGui::SetNextItemWidth(width); - bool value_changed = ImGui::InputText(label, InputBuf, IM_ARRAYSIZE(InputBuf)); - if (value_changed) - Build(); - return value_changed; -} - -void ImGuiTextFilter::ImGuiTextRange::split(char separator, ImVector* out) const -{ - out->resize(0); - const char* wb = b; - const char* we = wb; - while (we < e) - { - if (*we == separator) - { - out->push_back(ImGuiTextRange(wb, we)); - wb = we + 1; - } - we++; - } - if (wb != we) - out->push_back(ImGuiTextRange(wb, we)); -} - -void ImGuiTextFilter::Build() -{ - Filters.resize(0); - ImGuiTextRange input_range(InputBuf, InputBuf + strlen(InputBuf)); - input_range.split(',', &Filters); - - CountGrep = 0; - for (ImGuiTextRange& f : Filters) - { - while (f.b < f.e && ImCharIsBlankA(f.b[0])) - f.b++; - while (f.e > f.b && ImCharIsBlankA(f.e[-1])) - f.e--; - if (f.empty()) - continue; - if (f.b[0] != '-') - CountGrep += 1; - } -} - -bool ImGuiTextFilter::PassFilter(const char* text, const char* text_end) const -{ - if (Filters.empty()) - return true; - - if (text == NULL) - text = ""; - - for (const ImGuiTextRange& f : Filters) - { - if (f.empty()) - continue; - if (f.b[0] == '-') - { - // Subtract - if (ImStristr(text, text_end, f.b + 1, f.e) != NULL) - return false; - } - else - { - // Grep - if (ImStristr(text, text_end, f.b, f.e) != NULL) - return true; - } - } - - // Implicit * grep - if (CountGrep == 0) - return true; - - return false; -} - -//----------------------------------------------------------------------------- -// [SECTION] ImGuiTextBuffer, ImGuiTextIndex -//----------------------------------------------------------------------------- - -// On some platform vsnprintf() takes va_list by reference and modifies it. -// va_copy is the 'correct' way to copy a va_list but Visual Studio prior to 2013 doesn't have it. -#ifndef va_copy -#if defined(__GNUC__) || defined(__clang__) -#define va_copy(dest, src) __builtin_va_copy(dest, src) -#else -#define va_copy(dest, src) (dest = src) -#endif -#endif - -char ImGuiTextBuffer::EmptyString[1] = { 0 }; - -void ImGuiTextBuffer::append(const char* str, const char* str_end) -{ - int len = str_end ? (int)(str_end - str) : (int)strlen(str); - - // Add zero-terminator the first time - const int write_off = (Buf.Size != 0) ? Buf.Size : 1; - const int needed_sz = write_off + len; - if (write_off + len >= Buf.Capacity) - { - int new_capacity = Buf.Capacity * 2; - Buf.reserve(needed_sz > new_capacity ? needed_sz : new_capacity); - } - - Buf.resize(needed_sz); - memcpy(&Buf[write_off - 1], str, (size_t)len); - Buf[write_off - 1 + len] = 0; -} - -void ImGuiTextBuffer::appendf(const char* fmt, ...) -{ - va_list args; - va_start(args, fmt); - appendfv(fmt, args); - va_end(args); -} - -// Helper: Text buffer for logging/accumulating text -void ImGuiTextBuffer::appendfv(const char* fmt, va_list args) -{ - va_list args_copy; - va_copy(args_copy, args); - - int len = ImFormatStringV(NULL, 0, fmt, args); // FIXME-OPT: could do a first pass write attempt, likely successful on first pass. - if (len <= 0) - { - va_end(args_copy); - return; - } - - // Add zero-terminator the first time - const int write_off = (Buf.Size != 0) ? Buf.Size : 1; - const int needed_sz = write_off + len; - if (write_off + len >= Buf.Capacity) - { - int new_capacity = Buf.Capacity * 2; - Buf.reserve(needed_sz > new_capacity ? needed_sz : new_capacity); - } - - Buf.resize(needed_sz); - ImFormatStringV(&Buf[write_off - 1], (size_t)len + 1, fmt, args_copy); - va_end(args_copy); -} - -void ImGuiTextIndex::append(const char* base, int old_size, int new_size) -{ - IM_ASSERT(old_size >= 0 && new_size >= old_size && new_size >= EndOffset); - if (old_size == new_size) - return; - if (EndOffset == 0 || base[EndOffset - 1] == '\n') - LineOffsets.push_back(EndOffset); - const char* base_end = base + new_size; - for (const char* p = base + old_size; (p = (const char*)memchr(p, '\n', base_end - p)) != 0; ) - if (++p < base_end) // Don't push a trailing offset on last \n - LineOffsets.push_back((int)(intptr_t)(p - base)); - EndOffset = ImMax(EndOffset, new_size); -} - -//----------------------------------------------------------------------------- -// [SECTION] ImGuiListClipper -//----------------------------------------------------------------------------- - -// FIXME-TABLE: This prevents us from using ImGuiListClipper _inside_ a table cell. -// The problem we have is that without a Begin/End scheme for rows using the clipper is ambiguous. -static bool GetSkipItemForListClipping() -{ - ImGuiContext& g = *GImGui; - return (g.CurrentTable ? g.CurrentTable->HostSkipItems : g.CurrentWindow->SkipItems); -} - -#ifndef IMGUI_DISABLE_OBSOLETE_FUNCTIONS -// Legacy helper to calculate coarse clipping of large list of evenly sized items. -// This legacy API is not ideal because it assumes we will return a single contiguous rectangle. -// Prefer using ImGuiListClipper which can returns non-contiguous ranges. -void ImGui::CalcListClipping(int items_count, float items_height, int* out_items_display_start, int* out_items_display_end) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - if (g.LogEnabled) - { - // If logging is active, do not perform any clipping - *out_items_display_start = 0; - *out_items_display_end = items_count; - return; - } - if (GetSkipItemForListClipping()) - { - *out_items_display_start = *out_items_display_end = 0; - return; - } - - // We create the union of the ClipRect and the scoring rect which at worst should be 1 page away from ClipRect - // We don't include g.NavId's rectangle in there (unless g.NavJustMovedToId is set) because the rectangle enlargement can get costly. - ImRect rect = window->ClipRect; - if (g.NavMoveScoringItems) - rect.Add(g.NavScoringNoClipRect); - if (g.NavJustMovedToId && window->NavLastIds[0] == g.NavJustMovedToId) - rect.Add(WindowRectRelToAbs(window, window->NavRectRel[0])); // Could store and use NavJustMovedToRectRel - - const ImVec2 pos = window->DC.CursorPos; - int start = (int)((rect.Min.y - pos.y) / items_height); - int end = (int)((rect.Max.y - pos.y) / items_height); - - // When performing a navigation request, ensure we have one item extra in the direction we are moving to - // FIXME: Verify this works with tabbing - const bool is_nav_request = (g.NavMoveScoringItems && g.NavWindow && g.NavWindow->RootWindowForNav == window->RootWindowForNav); - if (is_nav_request && g.NavMoveClipDir == ImGuiDir_Up) - start--; - if (is_nav_request && g.NavMoveClipDir == ImGuiDir_Down) - end++; - - start = ImClamp(start, 0, items_count); - end = ImClamp(end + 1, start, items_count); - *out_items_display_start = start; - *out_items_display_end = end; -} -#endif - -static void ImGuiListClipper_SortAndFuseRanges(ImVector& ranges, int offset = 0) -{ - if (ranges.Size - offset <= 1) - return; - - // Helper to order ranges and fuse them together if possible (bubble sort is fine as we are only sorting 2-3 entries) - for (int sort_end = ranges.Size - offset - 1; sort_end > 0; --sort_end) - for (int i = offset; i < sort_end + offset; ++i) - if (ranges[i].Min > ranges[i + 1].Min) - ImSwap(ranges[i], ranges[i + 1]); - - // Now fuse ranges together as much as possible. - for (int i = 1 + offset; i < ranges.Size; i++) - { - IM_ASSERT(!ranges[i].PosToIndexConvert && !ranges[i - 1].PosToIndexConvert); - if (ranges[i - 1].Max < ranges[i].Min) - continue; - ranges[i - 1].Min = ImMin(ranges[i - 1].Min, ranges[i].Min); - ranges[i - 1].Max = ImMax(ranges[i - 1].Max, ranges[i].Max); - ranges.erase(ranges.Data + i); - i--; - } -} - -static void ImGuiListClipper_SeekCursorAndSetupPrevLine(float pos_y, float line_height) -{ - // Set cursor position and a few other things so that SetScrollHereY() and Columns() can work when seeking cursor. - // FIXME: It is problematic that we have to do that here, because custom/equivalent end-user code would stumble on the same issue. - // The clipper should probably have a final step to display the last item in a regular manner, maybe with an opt-out flag for data sets which may have costly seek? - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - float off_y = pos_y - window->DC.CursorPos.y; - window->DC.CursorPos.y = pos_y; - window->DC.CursorMaxPos.y = ImMax(window->DC.CursorMaxPos.y, pos_y - g.Style.ItemSpacing.y); - window->DC.CursorPosPrevLine.y = window->DC.CursorPos.y - line_height; // Setting those fields so that SetScrollHereY() can properly function after the end of our clipper usage. - window->DC.PrevLineSize.y = (line_height - g.Style.ItemSpacing.y); // If we end up needing more accurate data (to e.g. use SameLine) we may as well make the clipper have a fourth step to let user process and display the last item in their list. - if (ImGuiOldColumns* columns = window->DC.CurrentColumns) - columns->LineMinY = window->DC.CursorPos.y; // Setting this so that cell Y position are set properly - if (ImGuiTable* table = g.CurrentTable) - { - if (table->IsInsideRow) - ImGui::TableEndRow(table); - table->RowPosY2 = window->DC.CursorPos.y; - const int row_increase = (int)((off_y / line_height) + 0.5f); - //table->CurrentRow += row_increase; // Can't do without fixing TableEndRow() - table->RowBgColorCounter += row_increase; - } -} - -static void ImGuiListClipper_SeekCursorForItem(ImGuiListClipper* clipper, int item_n) -{ - // StartPosY starts from ItemsFrozen hence the subtraction - // Perform the add and multiply with double to allow seeking through larger ranges - ImGuiListClipperData* data = (ImGuiListClipperData*)clipper->TempData; - float pos_y = (float)((double)clipper->StartPosY + data->LossynessOffset + (double)(item_n - data->ItemsFrozen) * clipper->ItemsHeight); - ImGuiListClipper_SeekCursorAndSetupPrevLine(pos_y, clipper->ItemsHeight); -} - -ImGuiListClipper::ImGuiListClipper() -{ - memset(this, 0, sizeof(*this)); -} - -ImGuiListClipper::~ImGuiListClipper() -{ - End(); -} - -void ImGuiListClipper::Begin(int items_count, float items_height) -{ - if (Ctx == NULL) - Ctx = ImGui::GetCurrentContext(); - - ImGuiContext& g = *Ctx; - ImGuiWindow* window = g.CurrentWindow; - IMGUI_DEBUG_LOG_CLIPPER("Clipper: Begin(%d,%.2f) in '%s'\n", items_count, items_height, window->Name); - - if (ImGuiTable* table = g.CurrentTable) - if (table->IsInsideRow) - ImGui::TableEndRow(table); - - StartPosY = window->DC.CursorPos.y; - ItemsHeight = items_height; - ItemsCount = items_count; - DisplayStart = -1; - DisplayEnd = 0; - - // Acquire temporary buffer - if (++g.ClipperTempDataStacked > g.ClipperTempData.Size) - g.ClipperTempData.resize(g.ClipperTempDataStacked, ImGuiListClipperData()); - ImGuiListClipperData* data = &g.ClipperTempData[g.ClipperTempDataStacked - 1]; - data->Reset(this); - data->LossynessOffset = window->DC.CursorStartPosLossyness.y; - TempData = data; -} - -void ImGuiListClipper::End() -{ - if (ImGuiListClipperData* data = (ImGuiListClipperData*)TempData) - { - // In theory here we should assert that we are already at the right position, but it seems saner to just seek at the end and not assert/crash the user. - ImGuiContext& g = *Ctx; - IMGUI_DEBUG_LOG_CLIPPER("Clipper: End() in '%s'\n", g.CurrentWindow->Name); - if (ItemsCount >= 0 && ItemsCount < INT_MAX && DisplayStart >= 0) - ImGuiListClipper_SeekCursorForItem(this, ItemsCount); - - // Restore temporary buffer and fix back pointers which may be invalidated when nesting - IM_ASSERT(data->ListClipper == this); - data->StepNo = data->Ranges.Size; - if (--g.ClipperTempDataStacked > 0) - { - data = &g.ClipperTempData[g.ClipperTempDataStacked - 1]; - data->ListClipper->TempData = data; - } - TempData = NULL; - } - ItemsCount = -1; -} - -void ImGuiListClipper::IncludeItemsByIndex(int item_begin, int item_end) -{ - ImGuiListClipperData* data = (ImGuiListClipperData*)TempData; - IM_ASSERT(DisplayStart < 0); // Only allowed after Begin() and if there has not been a specified range yet. - IM_ASSERT(item_begin <= item_end); - if (item_begin < item_end) - data->Ranges.push_back(ImGuiListClipperRange::FromIndices(item_begin, item_end)); -} - -static bool ImGuiListClipper_StepInternal(ImGuiListClipper* clipper) -{ - ImGuiContext& g = *clipper->Ctx; - ImGuiWindow* window = g.CurrentWindow; - ImGuiListClipperData* data = (ImGuiListClipperData*)clipper->TempData; - IM_ASSERT(data != NULL && "Called ImGuiListClipper::Step() too many times, or before ImGuiListClipper::Begin() ?"); - - ImGuiTable* table = g.CurrentTable; - if (table && table->IsInsideRow) - ImGui::TableEndRow(table); - - // No items - if (clipper->ItemsCount == 0 || GetSkipItemForListClipping()) - return false; - - // While we are in frozen row state, keep displaying items one by one, unclipped - // FIXME: Could be stored as a table-agnostic state. - if (data->StepNo == 0 && table != NULL && !table->IsUnfrozenRows) - { - clipper->DisplayStart = data->ItemsFrozen; - clipper->DisplayEnd = ImMin(data->ItemsFrozen + 1, clipper->ItemsCount); - if (clipper->DisplayStart < clipper->DisplayEnd) - data->ItemsFrozen++; - return true; - } - - // Step 0: Let you process the first element (regardless of it being visible or not, so we can measure the element height) - bool calc_clipping = false; - if (data->StepNo == 0) - { - clipper->StartPosY = window->DC.CursorPos.y; - if (clipper->ItemsHeight <= 0.0f) - { - // Submit the first item (or range) so we can measure its height (generally the first range is 0..1) - data->Ranges.push_front(ImGuiListClipperRange::FromIndices(data->ItemsFrozen, data->ItemsFrozen + 1)); - clipper->DisplayStart = ImMax(data->Ranges[0].Min, data->ItemsFrozen); - clipper->DisplayEnd = ImMin(data->Ranges[0].Max, clipper->ItemsCount); - data->StepNo = 1; - return true; - } - calc_clipping = true; // If on the first step with known item height, calculate clipping. - } - - // Step 1: Let the clipper infer height from first range - if (clipper->ItemsHeight <= 0.0f) - { - IM_ASSERT(data->StepNo == 1); - if (table) - IM_ASSERT(table->RowPosY1 == clipper->StartPosY && table->RowPosY2 == window->DC.CursorPos.y); - - clipper->ItemsHeight = (window->DC.CursorPos.y - clipper->StartPosY) / (float)(clipper->DisplayEnd - clipper->DisplayStart); - bool affected_by_floating_point_precision = ImIsFloatAboveGuaranteedIntegerPrecision(clipper->StartPosY) || ImIsFloatAboveGuaranteedIntegerPrecision(window->DC.CursorPos.y); - if (affected_by_floating_point_precision) - clipper->ItemsHeight = window->DC.PrevLineSize.y + g.Style.ItemSpacing.y; // FIXME: Technically wouldn't allow multi-line entries. - - IM_ASSERT(clipper->ItemsHeight > 0.0f && "Unable to calculate item height! First item hasn't moved the cursor vertically!"); - calc_clipping = true; // If item height had to be calculated, calculate clipping afterwards. - } - - // Step 0 or 1: Calculate the actual ranges of visible elements. - const int already_submitted = clipper->DisplayEnd; - if (calc_clipping) - { - if (g.LogEnabled) - { - // If logging is active, do not perform any clipping - data->Ranges.push_back(ImGuiListClipperRange::FromIndices(0, clipper->ItemsCount)); - } - else - { - // Add range selected to be included for navigation - const bool is_nav_request = (g.NavMoveScoringItems && g.NavWindow && g.NavWindow->RootWindowForNav == window->RootWindowForNav); - if (is_nav_request) - data->Ranges.push_back(ImGuiListClipperRange::FromPositions(g.NavScoringNoClipRect.Min.y, g.NavScoringNoClipRect.Max.y, 0, 0)); - if (is_nav_request && (g.NavMoveFlags & ImGuiNavMoveFlags_IsTabbing) && g.NavTabbingDir == -1) - data->Ranges.push_back(ImGuiListClipperRange::FromIndices(clipper->ItemsCount - 1, clipper->ItemsCount)); - - // Add focused/active item - ImRect nav_rect_abs = ImGui::WindowRectRelToAbs(window, window->NavRectRel[0]); - if (g.NavId != 0 && window->NavLastIds[0] == g.NavId) - data->Ranges.push_back(ImGuiListClipperRange::FromPositions(nav_rect_abs.Min.y, nav_rect_abs.Max.y, 0, 0)); - - // Add visible range - const int off_min = (is_nav_request && g.NavMoveClipDir == ImGuiDir_Up) ? -1 : 0; - const int off_max = (is_nav_request && g.NavMoveClipDir == ImGuiDir_Down) ? 1 : 0; - data->Ranges.push_back(ImGuiListClipperRange::FromPositions(window->ClipRect.Min.y, window->ClipRect.Max.y, off_min, off_max)); - } - - // Convert position ranges to item index ranges - // - Very important: when a starting position is after our maximum item, we set Min to (ItemsCount - 1). This allows us to handle most forms of wrapping. - // - Due to how Selectable extra padding they tend to be "unaligned" with exact unit in the item list, - // which with the flooring/ceiling tend to lead to 2 items instead of one being submitted. - for (ImGuiListClipperRange& range : data->Ranges) - if (range.PosToIndexConvert) - { - int m1 = (int)(((double)range.Min - window->DC.CursorPos.y - data->LossynessOffset) / clipper->ItemsHeight); - int m2 = (int)((((double)range.Max - window->DC.CursorPos.y - data->LossynessOffset) / clipper->ItemsHeight) + 0.999999f); - range.Min = ImClamp(already_submitted + m1 + range.PosToIndexOffsetMin, already_submitted, clipper->ItemsCount - 1); - range.Max = ImClamp(already_submitted + m2 + range.PosToIndexOffsetMax, range.Min + 1, clipper->ItemsCount); - range.PosToIndexConvert = false; - } - ImGuiListClipper_SortAndFuseRanges(data->Ranges, data->StepNo); - } - - // Step 0+ (if item height is given in advance) or 1+: Display the next range in line. - while (data->StepNo < data->Ranges.Size) - { - clipper->DisplayStart = ImMax(data->Ranges[data->StepNo].Min, already_submitted); - clipper->DisplayEnd = ImMin(data->Ranges[data->StepNo].Max, clipper->ItemsCount); - if (clipper->DisplayStart > already_submitted) //-V1051 - ImGuiListClipper_SeekCursorForItem(clipper, clipper->DisplayStart); - data->StepNo++; - if (clipper->DisplayStart == clipper->DisplayEnd && data->StepNo < data->Ranges.Size) - continue; - return true; - } - - // After the last step: Let the clipper validate that we have reached the expected Y position (corresponding to element DisplayEnd), - // Advance the cursor to the end of the list and then returns 'false' to end the loop. - if (clipper->ItemsCount < INT_MAX) - ImGuiListClipper_SeekCursorForItem(clipper, clipper->ItemsCount); - - return false; -} - -bool ImGuiListClipper::Step() -{ - ImGuiContext& g = *Ctx; - bool need_items_height = (ItemsHeight <= 0.0f); - bool ret = ImGuiListClipper_StepInternal(this); - if (ret && (DisplayStart == DisplayEnd)) - ret = false; - if (g.CurrentTable && g.CurrentTable->IsUnfrozenRows == false) - IMGUI_DEBUG_LOG_CLIPPER("Clipper: Step(): inside frozen table row.\n"); - if (need_items_height && ItemsHeight > 0.0f) - IMGUI_DEBUG_LOG_CLIPPER("Clipper: Step(): computed ItemsHeight: %.2f.\n", ItemsHeight); - if (ret) - { - IMGUI_DEBUG_LOG_CLIPPER("Clipper: Step(): display %d to %d.\n", DisplayStart, DisplayEnd); - } - else - { - IMGUI_DEBUG_LOG_CLIPPER("Clipper: Step(): End.\n"); - End(); - } - return ret; -} - -//----------------------------------------------------------------------------- -// [SECTION] STYLING -//----------------------------------------------------------------------------- - -ImGuiStyle& ImGui::GetStyle() -{ - IM_ASSERT(GImGui != NULL && "No current context. Did you call ImGui::CreateContext() and ImGui::SetCurrentContext() ?"); - return GImGui->Style; -} - -ImU32 ImGui::GetColorU32(ImGuiCol idx, float alpha_mul) -{ - ImGuiStyle& style = GImGui->Style; - ImVec4 c = style.Colors[idx]; - c.w *= style.Alpha * alpha_mul; - return ColorConvertFloat4ToU32(c); -} - -ImU32 ImGui::GetColorU32(const ImVec4& col) -{ - ImGuiStyle& style = GImGui->Style; - ImVec4 c = col; - c.w *= style.Alpha; - return ColorConvertFloat4ToU32(c); -} - -const ImVec4& ImGui::GetStyleColorVec4(ImGuiCol idx) -{ - ImGuiStyle& style = GImGui->Style; - return style.Colors[idx]; -} - -ImU32 ImGui::GetColorU32(ImU32 col) -{ - ImGuiStyle& style = GImGui->Style; - if (style.Alpha >= 1.0f) - return col; - ImU32 a = (col & IM_COL32_A_MASK) >> IM_COL32_A_SHIFT; - a = (ImU32)(a * style.Alpha); // We don't need to clamp 0..255 because Style.Alpha is in 0..1 range. - return (col & ~IM_COL32_A_MASK) | (a << IM_COL32_A_SHIFT); -} - -// FIXME: This may incur a round-trip (if the end user got their data from a float4) but eventually we aim to store the in-flight colors as ImU32 -void ImGui::PushStyleColor(ImGuiCol idx, ImU32 col) -{ - ImGuiContext& g = *GImGui; - ImGuiColorMod backup; - backup.Col = idx; - backup.BackupValue = g.Style.Colors[idx]; - g.ColorStack.push_back(backup); - g.Style.Colors[idx] = ColorConvertU32ToFloat4(col); -} - -void ImGui::PushStyleColor(ImGuiCol idx, const ImVec4& col) -{ - ImGuiContext& g = *GImGui; - ImGuiColorMod backup; - backup.Col = idx; - backup.BackupValue = g.Style.Colors[idx]; - g.ColorStack.push_back(backup); - g.Style.Colors[idx] = col; -} - -void ImGui::PopStyleColor(int count) -{ - ImGuiContext& g = *GImGui; - if (g.ColorStack.Size < count) - { - IM_ASSERT_USER_ERROR(g.ColorStack.Size > count, "Calling PopStyleColor() too many times: stack underflow."); - count = g.ColorStack.Size; - } - while (count > 0) - { - ImGuiColorMod& backup = g.ColorStack.back(); - g.Style.Colors[backup.Col] = backup.BackupValue; - g.ColorStack.pop_back(); - count--; - } -} - -static const ImGuiCol GWindowDockStyleColors[ImGuiWindowDockStyleCol_COUNT] = -{ - ImGuiCol_Text, ImGuiCol_Tab, ImGuiCol_TabHovered, ImGuiCol_TabActive, ImGuiCol_TabUnfocused, ImGuiCol_TabUnfocusedActive -}; - -static const ImGuiDataVarInfo GStyleVarInfo[] = -{ - { ImGuiDataType_Float, 1, (ImU32)IM_OFFSETOF(ImGuiStyle, Alpha) }, // ImGuiStyleVar_Alpha - { ImGuiDataType_Float, 1, (ImU32)IM_OFFSETOF(ImGuiStyle, DisabledAlpha) }, // ImGuiStyleVar_DisabledAlpha - { ImGuiDataType_Float, 2, (ImU32)IM_OFFSETOF(ImGuiStyle, WindowPadding) }, // ImGuiStyleVar_WindowPadding - { ImGuiDataType_Float, 1, (ImU32)IM_OFFSETOF(ImGuiStyle, WindowRounding) }, // ImGuiStyleVar_WindowRounding - { ImGuiDataType_Float, 1, (ImU32)IM_OFFSETOF(ImGuiStyle, WindowBorderSize) }, // ImGuiStyleVar_WindowBorderSize - { ImGuiDataType_Float, 2, (ImU32)IM_OFFSETOF(ImGuiStyle, WindowMinSize) }, // ImGuiStyleVar_WindowMinSize - { ImGuiDataType_Float, 2, (ImU32)IM_OFFSETOF(ImGuiStyle, WindowTitleAlign) }, // ImGuiStyleVar_WindowTitleAlign - { ImGuiDataType_Float, 1, (ImU32)IM_OFFSETOF(ImGuiStyle, ChildRounding) }, // ImGuiStyleVar_ChildRounding - { ImGuiDataType_Float, 1, (ImU32)IM_OFFSETOF(ImGuiStyle, ChildBorderSize) }, // ImGuiStyleVar_ChildBorderSize - { ImGuiDataType_Float, 1, (ImU32)IM_OFFSETOF(ImGuiStyle, PopupRounding) }, // ImGuiStyleVar_PopupRounding - { ImGuiDataType_Float, 1, (ImU32)IM_OFFSETOF(ImGuiStyle, PopupBorderSize) }, // ImGuiStyleVar_PopupBorderSize - { ImGuiDataType_Float, 2, (ImU32)IM_OFFSETOF(ImGuiStyle, FramePadding) }, // ImGuiStyleVar_FramePadding - { ImGuiDataType_Float, 1, (ImU32)IM_OFFSETOF(ImGuiStyle, FrameRounding) }, // ImGuiStyleVar_FrameRounding - { ImGuiDataType_Float, 1, (ImU32)IM_OFFSETOF(ImGuiStyle, FrameBorderSize) }, // ImGuiStyleVar_FrameBorderSize - { ImGuiDataType_Float, 2, (ImU32)IM_OFFSETOF(ImGuiStyle, ItemSpacing) }, // ImGuiStyleVar_ItemSpacing - { ImGuiDataType_Float, 2, (ImU32)IM_OFFSETOF(ImGuiStyle, ItemInnerSpacing) }, // ImGuiStyleVar_ItemInnerSpacing - { ImGuiDataType_Float, 1, (ImU32)IM_OFFSETOF(ImGuiStyle, IndentSpacing) }, // ImGuiStyleVar_IndentSpacing - { ImGuiDataType_Float, 2, (ImU32)IM_OFFSETOF(ImGuiStyle, CellPadding) }, // ImGuiStyleVar_CellPadding - { ImGuiDataType_Float, 1, (ImU32)IM_OFFSETOF(ImGuiStyle, ScrollbarSize) }, // ImGuiStyleVar_ScrollbarSize - { ImGuiDataType_Float, 1, (ImU32)IM_OFFSETOF(ImGuiStyle, ScrollbarRounding) }, // ImGuiStyleVar_ScrollbarRounding - { ImGuiDataType_Float, 1, (ImU32)IM_OFFSETOF(ImGuiStyle, GrabMinSize) }, // ImGuiStyleVar_GrabMinSize - { ImGuiDataType_Float, 1, (ImU32)IM_OFFSETOF(ImGuiStyle, GrabRounding) }, // ImGuiStyleVar_GrabRounding - { ImGuiDataType_Float, 1, (ImU32)IM_OFFSETOF(ImGuiStyle, TabRounding) }, // ImGuiStyleVar_TabRounding - { ImGuiDataType_Float, 1, (ImU32)IM_OFFSETOF(ImGuiStyle, TabBarBorderSize) }, // ImGuiStyleVar_TabBarBorderSize - { ImGuiDataType_Float, 2, (ImU32)IM_OFFSETOF(ImGuiStyle, ButtonTextAlign) }, // ImGuiStyleVar_ButtonTextAlign - { ImGuiDataType_Float, 2, (ImU32)IM_OFFSETOF(ImGuiStyle, SelectableTextAlign) }, // ImGuiStyleVar_SelectableTextAlign - { ImGuiDataType_Float, 1, (ImU32)IM_OFFSETOF(ImGuiStyle, SeparatorTextBorderSize) },// ImGuiStyleVar_SeparatorTextBorderSize - { ImGuiDataType_Float, 2, (ImU32)IM_OFFSETOF(ImGuiStyle, SeparatorTextAlign) }, // ImGuiStyleVar_SeparatorTextAlign - { ImGuiDataType_Float, 2, (ImU32)IM_OFFSETOF(ImGuiStyle, SeparatorTextPadding) }, // ImGuiStyleVar_SeparatorTextPadding - { ImGuiDataType_Float, 1, (ImU32)IM_OFFSETOF(ImGuiStyle, DockingSeparatorSize) }, // ImGuiStyleVar_DockingSeparatorSize -}; - -const ImGuiDataVarInfo* ImGui::GetStyleVarInfo(ImGuiStyleVar idx) -{ - IM_ASSERT(idx >= 0 && idx < ImGuiStyleVar_COUNT); - IM_STATIC_ASSERT(IM_ARRAYSIZE(GStyleVarInfo) == ImGuiStyleVar_COUNT); - return &GStyleVarInfo[idx]; -} - -void ImGui::PushStyleVar(ImGuiStyleVar idx, float val) -{ - ImGuiContext& g = *GImGui; - const ImGuiDataVarInfo* var_info = GetStyleVarInfo(idx); - if (var_info->Type == ImGuiDataType_Float && var_info->Count == 1) - { - float* pvar = (float*)var_info->GetVarPtr(&g.Style); - g.StyleVarStack.push_back(ImGuiStyleMod(idx, *pvar)); - *pvar = val; - return; - } - IM_ASSERT_USER_ERROR(0, "Called PushStyleVar() variant with wrong type!"); -} - -void ImGui::PushStyleVar(ImGuiStyleVar idx, const ImVec2& val) -{ - ImGuiContext& g = *GImGui; - const ImGuiDataVarInfo* var_info = GetStyleVarInfo(idx); - if (var_info->Type == ImGuiDataType_Float && var_info->Count == 2) - { - ImVec2* pvar = (ImVec2*)var_info->GetVarPtr(&g.Style); - g.StyleVarStack.push_back(ImGuiStyleMod(idx, *pvar)); - *pvar = val; - return; - } - IM_ASSERT_USER_ERROR(0, "Called PushStyleVar() variant with wrong type!"); -} - -void ImGui::PopStyleVar(int count) -{ - ImGuiContext& g = *GImGui; - if (g.StyleVarStack.Size < count) - { - IM_ASSERT_USER_ERROR(g.StyleVarStack.Size > count, "Calling PopStyleVar() too many times: stack underflow."); - count = g.StyleVarStack.Size; - } - while (count > 0) - { - // We avoid a generic memcpy(data, &backup.Backup.., GDataTypeSize[info->Type] * info->Count), the overhead in Debug is not worth it. - ImGuiStyleMod& backup = g.StyleVarStack.back(); - const ImGuiDataVarInfo* info = GetStyleVarInfo(backup.VarIdx); - void* data = info->GetVarPtr(&g.Style); - if (info->Type == ImGuiDataType_Float && info->Count == 1) { ((float*)data)[0] = backup.BackupFloat[0]; } - else if (info->Type == ImGuiDataType_Float && info->Count == 2) { ((float*)data)[0] = backup.BackupFloat[0]; ((float*)data)[1] = backup.BackupFloat[1]; } - g.StyleVarStack.pop_back(); - count--; - } -} - -const char* ImGui::GetStyleColorName(ImGuiCol idx) -{ - // Create switch-case from enum with regexp: ImGuiCol_{.*}, --> case ImGuiCol_\1: return "\1"; - switch (idx) - { - case ImGuiCol_Text: return "Text"; - case ImGuiCol_TextDisabled: return "TextDisabled"; - case ImGuiCol_WindowBg: return "WindowBg"; - case ImGuiCol_ChildBg: return "ChildBg"; - case ImGuiCol_PopupBg: return "PopupBg"; - case ImGuiCol_Border: return "Border"; - case ImGuiCol_BorderShadow: return "BorderShadow"; - case ImGuiCol_FrameBg: return "FrameBg"; - case ImGuiCol_FrameBgHovered: return "FrameBgHovered"; - case ImGuiCol_FrameBgActive: return "FrameBgActive"; - case ImGuiCol_TitleBg: return "TitleBg"; - case ImGuiCol_TitleBgActive: return "TitleBgActive"; - case ImGuiCol_TitleBgCollapsed: return "TitleBgCollapsed"; - case ImGuiCol_MenuBarBg: return "MenuBarBg"; - case ImGuiCol_ScrollbarBg: return "ScrollbarBg"; - case ImGuiCol_ScrollbarGrab: return "ScrollbarGrab"; - case ImGuiCol_ScrollbarGrabHovered: return "ScrollbarGrabHovered"; - case ImGuiCol_ScrollbarGrabActive: return "ScrollbarGrabActive"; - case ImGuiCol_CheckMark: return "CheckMark"; - case ImGuiCol_SliderGrab: return "SliderGrab"; - case ImGuiCol_SliderGrabActive: return "SliderGrabActive"; - case ImGuiCol_Button: return "Button"; - case ImGuiCol_ButtonHovered: return "ButtonHovered"; - case ImGuiCol_ButtonActive: return "ButtonActive"; - case ImGuiCol_Header: return "Header"; - case ImGuiCol_HeaderHovered: return "HeaderHovered"; - case ImGuiCol_HeaderActive: return "HeaderActive"; - case ImGuiCol_Separator: return "Separator"; - case ImGuiCol_SeparatorHovered: return "SeparatorHovered"; - case ImGuiCol_SeparatorActive: return "SeparatorActive"; - case ImGuiCol_ResizeGrip: return "ResizeGrip"; - case ImGuiCol_ResizeGripHovered: return "ResizeGripHovered"; - case ImGuiCol_ResizeGripActive: return "ResizeGripActive"; - case ImGuiCol_Tab: return "Tab"; - case ImGuiCol_TabHovered: return "TabHovered"; - case ImGuiCol_TabActive: return "TabActive"; - case ImGuiCol_TabUnfocused: return "TabUnfocused"; - case ImGuiCol_TabUnfocusedActive: return "TabUnfocusedActive"; - case ImGuiCol_DockingPreview: return "DockingPreview"; - case ImGuiCol_DockingEmptyBg: return "DockingEmptyBg"; - case ImGuiCol_PlotLines: return "PlotLines"; - case ImGuiCol_PlotLinesHovered: return "PlotLinesHovered"; - case ImGuiCol_PlotHistogram: return "PlotHistogram"; - case ImGuiCol_PlotHistogramHovered: return "PlotHistogramHovered"; - case ImGuiCol_TableHeaderBg: return "TableHeaderBg"; - case ImGuiCol_TableBorderStrong: return "TableBorderStrong"; - case ImGuiCol_TableBorderLight: return "TableBorderLight"; - case ImGuiCol_TableRowBg: return "TableRowBg"; - case ImGuiCol_TableRowBgAlt: return "TableRowBgAlt"; - case ImGuiCol_TextSelectedBg: return "TextSelectedBg"; - case ImGuiCol_DragDropTarget: return "DragDropTarget"; - case ImGuiCol_NavHighlight: return "NavHighlight"; - case ImGuiCol_NavWindowingHighlight: return "NavWindowingHighlight"; - case ImGuiCol_NavWindowingDimBg: return "NavWindowingDimBg"; - case ImGuiCol_ModalWindowDimBg: return "ModalWindowDimBg"; - } - IM_ASSERT(0); - return "Unknown"; -} - - -//----------------------------------------------------------------------------- -// [SECTION] RENDER HELPERS -// Some of those (internal) functions are currently quite a legacy mess - their signature and behavior will change, -// we need a nicer separation between low-level functions and high-level functions relying on the ImGui context. -// Also see imgui_draw.cpp for some more which have been reworked to not rely on ImGui:: context. -//----------------------------------------------------------------------------- - -const char* ImGui::FindRenderedTextEnd(const char* text, const char* text_end) -{ - const char* text_display_end = text; - if (!text_end) - text_end = (const char*)-1; - - while (text_display_end < text_end && *text_display_end != '\0' && (text_display_end[0] != '#' || text_display_end[1] != '#')) - text_display_end++; - return text_display_end; -} - -// Internal ImGui functions to render text -// RenderText***() functions calls ImDrawList::AddText() calls ImBitmapFont::RenderText() -void ImGui::RenderText(ImVec2 pos, const char* text, const char* text_end, bool hide_text_after_hash) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - - // Hide anything after a '##' string - const char* text_display_end; - if (hide_text_after_hash) - { - text_display_end = FindRenderedTextEnd(text, text_end); - } - else - { - if (!text_end) - text_end = text + strlen(text); // FIXME-OPT - text_display_end = text_end; - } - - if (text != text_display_end) - { - window->DrawList->AddText(g.Font, g.FontSize, pos, GetColorU32(ImGuiCol_Text), text, text_display_end); - if (g.LogEnabled) - LogRenderedText(&pos, text, text_display_end); - } -} - -void ImGui::RenderTextWrapped(ImVec2 pos, const char* text, const char* text_end, float wrap_width) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - - if (!text_end) - text_end = text + strlen(text); // FIXME-OPT - - if (text != text_end) - { - window->DrawList->AddText(g.Font, g.FontSize, pos, GetColorU32(ImGuiCol_Text), text, text_end, wrap_width); - if (g.LogEnabled) - LogRenderedText(&pos, text, text_end); - } -} - -// Default clip_rect uses (pos_min,pos_max) -// Handle clipping on CPU immediately (vs typically let the GPU clip the triangles that are overlapping the clipping rectangle edges) -// FIXME-OPT: Since we have or calculate text_size we could coarse clip whole block immediately, especally for text above draw_list->DrawList. -// Effectively as this is called from widget doing their own coarse clipping it's not very valuable presently. Next time function will take -// better advantage of the render function taking size into account for coarse clipping. -void ImGui::RenderTextClippedEx(ImDrawList* draw_list, const ImVec2& pos_min, const ImVec2& pos_max, const char* text, const char* text_display_end, const ImVec2* text_size_if_known, const ImVec2& align, const ImRect* clip_rect) -{ - // Perform CPU side clipping for single clipped element to avoid using scissor state - ImVec2 pos = pos_min; - const ImVec2 text_size = text_size_if_known ? *text_size_if_known : CalcTextSize(text, text_display_end, false, 0.0f); - - const ImVec2* clip_min = clip_rect ? &clip_rect->Min : &pos_min; - const ImVec2* clip_max = clip_rect ? &clip_rect->Max : &pos_max; - bool need_clipping = (pos.x + text_size.x >= clip_max->x) || (pos.y + text_size.y >= clip_max->y); - if (clip_rect) // If we had no explicit clipping rectangle then pos==clip_min - need_clipping |= (pos.x < clip_min->x) || (pos.y < clip_min->y); - - // Align whole block. We should defer that to the better rendering function when we'll have support for individual line alignment. - if (align.x > 0.0f) pos.x = ImMax(pos.x, pos.x + (pos_max.x - pos.x - text_size.x) * align.x); - if (align.y > 0.0f) pos.y = ImMax(pos.y, pos.y + (pos_max.y - pos.y - text_size.y) * align.y); - - // Render - if (need_clipping) - { - ImVec4 fine_clip_rect(clip_min->x, clip_min->y, clip_max->x, clip_max->y); - draw_list->AddText(NULL, 0.0f, pos, GetColorU32(ImGuiCol_Text), text, text_display_end, 0.0f, &fine_clip_rect); - } - else - { - draw_list->AddText(NULL, 0.0f, pos, GetColorU32(ImGuiCol_Text), text, text_display_end, 0.0f, NULL); - } -} - -void ImGui::RenderTextClipped(const ImVec2& pos_min, const ImVec2& pos_max, const char* text, const char* text_end, const ImVec2* text_size_if_known, const ImVec2& align, const ImRect* clip_rect) -{ - // Hide anything after a '##' string - const char* text_display_end = FindRenderedTextEnd(text, text_end); - const int text_len = (int)(text_display_end - text); - if (text_len == 0) - return; - - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - RenderTextClippedEx(window->DrawList, pos_min, pos_max, text, text_display_end, text_size_if_known, align, clip_rect); - if (g.LogEnabled) - LogRenderedText(&pos_min, text, text_display_end); -} - -// Another overly complex function until we reorganize everything into a nice all-in-one helper. -// This is made more complex because we have dissociated the layout rectangle (pos_min..pos_max) which define _where_ the ellipsis is, from actual clipping of text and limit of the ellipsis display. -// This is because in the context of tabs we selectively hide part of the text when the Close Button appears, but we don't want the ellipsis to move. -void ImGui::RenderTextEllipsis(ImDrawList* draw_list, const ImVec2& pos_min, const ImVec2& pos_max, float clip_max_x, float ellipsis_max_x, const char* text, const char* text_end_full, const ImVec2* text_size_if_known) -{ - ImGuiContext& g = *GImGui; - if (text_end_full == NULL) - text_end_full = FindRenderedTextEnd(text); - const ImVec2 text_size = text_size_if_known ? *text_size_if_known : CalcTextSize(text, text_end_full, false, 0.0f); - - //draw_list->AddLine(ImVec2(pos_max.x, pos_min.y - 4), ImVec2(pos_max.x, pos_max.y + 4), IM_COL32(0, 0, 255, 255)); - //draw_list->AddLine(ImVec2(ellipsis_max_x, pos_min.y-2), ImVec2(ellipsis_max_x, pos_max.y+2), IM_COL32(0, 255, 0, 255)); - //draw_list->AddLine(ImVec2(clip_max_x, pos_min.y), ImVec2(clip_max_x, pos_max.y), IM_COL32(255, 0, 0, 255)); - // FIXME: We could technically remove (last_glyph->AdvanceX - last_glyph->X1) from text_size.x here and save a few pixels. - if (text_size.x > pos_max.x - pos_min.x) - { - // Hello wo... - // | | | - // min max ellipsis_max - // <-> this is generally some padding value - - const ImFont* font = draw_list->_Data->Font; - const float font_size = draw_list->_Data->FontSize; - const float font_scale = font_size / font->FontSize; - const char* text_end_ellipsis = NULL; - const float ellipsis_width = font->EllipsisWidth * font_scale; - - // We can now claim the space between pos_max.x and ellipsis_max.x - const float text_avail_width = ImMax((ImMax(pos_max.x, ellipsis_max_x) - ellipsis_width) - pos_min.x, 1.0f); - float text_size_clipped_x = font->CalcTextSizeA(font_size, text_avail_width, 0.0f, text, text_end_full, &text_end_ellipsis).x; - if (text == text_end_ellipsis && text_end_ellipsis < text_end_full) - { - // Always display at least 1 character if there's no room for character + ellipsis - text_end_ellipsis = text + ImTextCountUtf8BytesFromChar(text, text_end_full); - text_size_clipped_x = font->CalcTextSizeA(font_size, FLT_MAX, 0.0f, text, text_end_ellipsis).x; - } - while (text_end_ellipsis > text && ImCharIsBlankA(text_end_ellipsis[-1])) - { - // Trim trailing space before ellipsis (FIXME: Supporting non-ascii blanks would be nice, for this we need a function to backtrack in UTF-8 text) - text_end_ellipsis--; - text_size_clipped_x -= font->CalcTextSizeA(font_size, FLT_MAX, 0.0f, text_end_ellipsis, text_end_ellipsis + 1).x; // Ascii blanks are always 1 byte - } - - // Render text, render ellipsis - RenderTextClippedEx(draw_list, pos_min, ImVec2(clip_max_x, pos_max.y), text, text_end_ellipsis, &text_size, ImVec2(0.0f, 0.0f)); - ImVec2 ellipsis_pos = ImTrunc(ImVec2(pos_min.x + text_size_clipped_x, pos_min.y)); - if (ellipsis_pos.x + ellipsis_width <= ellipsis_max_x) - for (int i = 0; i < font->EllipsisCharCount; i++, ellipsis_pos.x += font->EllipsisCharStep * font_scale) - font->RenderChar(draw_list, font_size, ellipsis_pos, GetColorU32(ImGuiCol_Text), font->EllipsisChar); - } - else - { - RenderTextClippedEx(draw_list, pos_min, ImVec2(clip_max_x, pos_max.y), text, text_end_full, &text_size, ImVec2(0.0f, 0.0f)); - } - - if (g.LogEnabled) - LogRenderedText(&pos_min, text, text_end_full); -} - -// Render a rectangle shaped with optional rounding and borders -void ImGui::RenderFrame(ImVec2 p_min, ImVec2 p_max, ImU32 fill_col, bool border, float rounding) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - window->DrawList->AddRectFilled(p_min, p_max, fill_col, rounding); - const float border_size = g.Style.FrameBorderSize; - if (border && border_size > 0.0f) - { - window->DrawList->AddRect(p_min + ImVec2(1, 1), p_max + ImVec2(1, 1), GetColorU32(ImGuiCol_BorderShadow), rounding, 0, border_size); - window->DrawList->AddRect(p_min, p_max, GetColorU32(ImGuiCol_Border), rounding, 0, border_size); - } -} - -void ImGui::RenderFrameBorder(ImVec2 p_min, ImVec2 p_max, float rounding) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - const float border_size = g.Style.FrameBorderSize; - if (border_size > 0.0f) - { - window->DrawList->AddRect(p_min + ImVec2(1, 1), p_max + ImVec2(1, 1), GetColorU32(ImGuiCol_BorderShadow), rounding, 0, border_size); - window->DrawList->AddRect(p_min, p_max, GetColorU32(ImGuiCol_Border), rounding, 0, border_size); - } -} - -void ImGui::RenderNavHighlight(const ImRect& bb, ImGuiID id, ImGuiNavHighlightFlags flags) -{ - ImGuiContext& g = *GImGui; - if (id != g.NavId) - return; - if (g.NavDisableHighlight && !(flags & ImGuiNavHighlightFlags_AlwaysDraw)) - return; - ImGuiWindow* window = g.CurrentWindow; - if (window->DC.NavHideHighlightOneFrame) - return; - - float rounding = (flags & ImGuiNavHighlightFlags_NoRounding) ? 0.0f : g.Style.FrameRounding; - ImRect display_rect = bb; - display_rect.ClipWith(window->ClipRect); - if (flags & ImGuiNavHighlightFlags_TypeDefault) - { - const float THICKNESS = 2.0f; - const float DISTANCE = 3.0f + THICKNESS * 0.5f; - display_rect.Expand(ImVec2(DISTANCE, DISTANCE)); - bool fully_visible = window->ClipRect.Contains(display_rect); - if (!fully_visible) - window->DrawList->PushClipRect(display_rect.Min, display_rect.Max); - window->DrawList->AddRect(display_rect.Min + ImVec2(THICKNESS * 0.5f, THICKNESS * 0.5f), display_rect.Max - ImVec2(THICKNESS * 0.5f, THICKNESS * 0.5f), GetColorU32(ImGuiCol_NavHighlight), rounding, 0, THICKNESS); - if (!fully_visible) - window->DrawList->PopClipRect(); - } - if (flags & ImGuiNavHighlightFlags_TypeThin) - { - window->DrawList->AddRect(display_rect.Min, display_rect.Max, GetColorU32(ImGuiCol_NavHighlight), rounding, 0, 1.0f); - } -} - -void ImGui::RenderMouseCursor(ImVec2 base_pos, float base_scale, ImGuiMouseCursor mouse_cursor, ImU32 col_fill, ImU32 col_border, ImU32 col_shadow) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(mouse_cursor > ImGuiMouseCursor_None && mouse_cursor < ImGuiMouseCursor_COUNT); - ImFontAtlas* font_atlas = g.DrawListSharedData.Font->ContainerAtlas; - for (ImGuiViewportP* viewport : g.Viewports) - { - // We scale cursor with current viewport/monitor, however Windows 10 for its own hardware cursor seems to be using a different scale factor. - ImVec2 offset, size, uv[4]; - if (!font_atlas->GetMouseCursorTexData(mouse_cursor, &offset, &size, &uv[0], &uv[2])) - continue; - const ImVec2 pos = base_pos - offset; - const float scale = base_scale * viewport->DpiScale; - if (!viewport->GetMainRect().Overlaps(ImRect(pos, pos + ImVec2(size.x + 2, size.y + 2) * scale))) - continue; - ImDrawList* draw_list = GetForegroundDrawList(viewport); - ImTextureID tex_id = font_atlas->TexID; - draw_list->PushTextureID(tex_id); - draw_list->AddImage(tex_id, pos + ImVec2(1, 0) * scale, pos + (ImVec2(1, 0) + size) * scale, uv[2], uv[3], col_shadow); - draw_list->AddImage(tex_id, pos + ImVec2(2, 0) * scale, pos + (ImVec2(2, 0) + size) * scale, uv[2], uv[3], col_shadow); - draw_list->AddImage(tex_id, pos, pos + size * scale, uv[2], uv[3], col_border); - draw_list->AddImage(tex_id, pos, pos + size * scale, uv[0], uv[1], col_fill); - draw_list->PopTextureID(); - } -} - -//----------------------------------------------------------------------------- -// [SECTION] INITIALIZATION, SHUTDOWN -//----------------------------------------------------------------------------- - -// Internal state access - if you want to share Dear ImGui state between modules (e.g. DLL) or allocate it yourself -// Note that we still point to some static data and members (such as GFontAtlas), so the state instance you end up using will point to the static data within its module -ImGuiContext* ImGui::GetCurrentContext() -{ - return GImGui; -} - -void ImGui::SetCurrentContext(ImGuiContext* ctx) -{ -#ifdef IMGUI_SET_CURRENT_CONTEXT_FUNC - IMGUI_SET_CURRENT_CONTEXT_FUNC(ctx); // For custom thread-based hackery you may want to have control over this. -#else - GImGui = ctx; -#endif -} - -void ImGui::SetAllocatorFunctions(ImGuiMemAllocFunc alloc_func, ImGuiMemFreeFunc free_func, void* user_data) -{ - GImAllocatorAllocFunc = alloc_func; - GImAllocatorFreeFunc = free_func; - GImAllocatorUserData = user_data; -} - -// This is provided to facilitate copying allocators from one static/DLL boundary to another (e.g. retrieve default allocator of your executable address space) -void ImGui::GetAllocatorFunctions(ImGuiMemAllocFunc* p_alloc_func, ImGuiMemFreeFunc* p_free_func, void** p_user_data) -{ - *p_alloc_func = GImAllocatorAllocFunc; - *p_free_func = GImAllocatorFreeFunc; - *p_user_data = GImAllocatorUserData; -} - -ImGuiContext* ImGui::CreateContext(ImFontAtlas* shared_font_atlas) -{ - ImGuiContext* prev_ctx = GetCurrentContext(); - ImGuiContext* ctx = IM_NEW(ImGuiContext)(shared_font_atlas); - SetCurrentContext(ctx); - Initialize(); - if (prev_ctx != NULL) - SetCurrentContext(prev_ctx); // Restore previous context if any, else keep new one. - return ctx; -} - -void ImGui::DestroyContext(ImGuiContext* ctx) -{ - ImGuiContext* prev_ctx = GetCurrentContext(); - if (ctx == NULL) //-V1051 - ctx = prev_ctx; - SetCurrentContext(ctx); - Shutdown(); - SetCurrentContext((prev_ctx != ctx) ? prev_ctx : NULL); - IM_DELETE(ctx); -} - -// IMPORTANT: ###xxx suffixes must be same in ALL languages -static const ImGuiLocEntry GLocalizationEntriesEnUS[] = -{ - { ImGuiLocKey_VersionStr, "Dear ImGui " IMGUI_VERSION " (" IM_STRINGIFY(IMGUI_VERSION_NUM) ")" }, - { ImGuiLocKey_TableSizeOne, "Size column to fit###SizeOne" }, - { ImGuiLocKey_TableSizeAllFit, "Size all columns to fit###SizeAll" }, - { ImGuiLocKey_TableSizeAllDefault, "Size all columns to default###SizeAll" }, - { ImGuiLocKey_TableResetOrder, "Reset order###ResetOrder" }, - { ImGuiLocKey_WindowingMainMenuBar, "(Main menu bar)" }, - { ImGuiLocKey_WindowingPopup, "(Popup)" }, - { ImGuiLocKey_WindowingUntitled, "(Untitled)" }, - { ImGuiLocKey_DockingHideTabBar, "Hide tab bar###HideTabBar" }, - { ImGuiLocKey_DockingHoldShiftToDock, "Hold SHIFT to enable Docking window."}, -}; - -void ImGui::Initialize() -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(!g.Initialized && !g.SettingsLoaded); - - // Add .ini handle for ImGuiWindow and ImGuiTable types - { - ImGuiSettingsHandler ini_handler; - ini_handler.TypeName = "Window"; - ini_handler.TypeHash = ImHashStr("Window"); - ini_handler.ClearAllFn = WindowSettingsHandler_ClearAll; - ini_handler.ReadOpenFn = WindowSettingsHandler_ReadOpen; - ini_handler.ReadLineFn = WindowSettingsHandler_ReadLine; - ini_handler.ApplyAllFn = WindowSettingsHandler_ApplyAll; - ini_handler.WriteAllFn = WindowSettingsHandler_WriteAll; - AddSettingsHandler(&ini_handler); - } - TableSettingsAddSettingsHandler(); - - // Setup default localization table - LocalizeRegisterEntries(GLocalizationEntriesEnUS, IM_ARRAYSIZE(GLocalizationEntriesEnUS)); - - // Setup default platform clipboard/IME handlers. - g.IO.GetClipboardTextFn = GetClipboardTextFn_DefaultImpl; // Platform dependent default implementations - g.IO.SetClipboardTextFn = SetClipboardTextFn_DefaultImpl; - g.IO.ClipboardUserData = (void*)&g; // Default implementation use the ImGuiContext as user data (ideally those would be arguments to the function) - g.IO.SetPlatformImeDataFn = SetPlatformImeDataFn_DefaultImpl; - - // Create default viewport - ImGuiViewportP* viewport = IM_NEW(ImGuiViewportP)(); - viewport->ID = IMGUI_VIEWPORT_DEFAULT_ID; - viewport->Idx = 0; - viewport->PlatformWindowCreated = true; - viewport->Flags = ImGuiViewportFlags_OwnedByApp; - g.Viewports.push_back(viewport); - g.TempBuffer.resize(1024 * 3 + 1, 0); - g.ViewportCreatedCount++; - g.PlatformIO.Viewports.push_back(g.Viewports[0]); - -#ifdef IMGUI_HAS_DOCK - // Initialize Docking - DockContextInitialize(&g); -#endif - - g.Initialized = true; -} - -// This function is merely here to free heap allocations. -void ImGui::Shutdown() -{ - // The fonts atlas can be used prior to calling NewFrame(), so we clear it even if g.Initialized is FALSE (which would happen if we never called NewFrame) - ImGuiContext& g = *GImGui; - if (g.IO.Fonts && g.FontAtlasOwnedByContext) - { - g.IO.Fonts->Locked = false; - IM_DELETE(g.IO.Fonts); - } - g.IO.Fonts = NULL; - g.DrawListSharedData.TempBuffer.clear(); - - // Cleanup of other data are conditional on actually having initialized Dear ImGui. - if (!g.Initialized) - return; - - // Save settings (unless we haven't attempted to load them: CreateContext/DestroyContext without a call to NewFrame shouldn't save an empty file) - if (g.SettingsLoaded && g.IO.IniFilename != NULL) - SaveIniSettingsToDisk(g.IO.IniFilename); - - // Destroy platform windows - DestroyPlatformWindows(); - - // Shutdown extensions - DockContextShutdown(&g); - - CallContextHooks(&g, ImGuiContextHookType_Shutdown); - - // Clear everything else - g.Windows.clear_delete(); - g.WindowsFocusOrder.clear(); - g.WindowsTempSortBuffer.clear(); - g.CurrentWindow = NULL; - g.CurrentWindowStack.clear(); - g.WindowsById.Clear(); - g.NavWindow = NULL; - g.HoveredWindow = g.HoveredWindowUnderMovingWindow = NULL; - g.ActiveIdWindow = g.ActiveIdPreviousFrameWindow = NULL; - g.MovingWindow = NULL; - - g.KeysRoutingTable.Clear(); - - g.ColorStack.clear(); - g.StyleVarStack.clear(); - g.FontStack.clear(); - g.OpenPopupStack.clear(); - g.BeginPopupStack.clear(); - g.NavTreeNodeStack.clear(); - - g.CurrentViewport = g.MouseViewport = g.MouseLastHoveredViewport = NULL; - g.Viewports.clear_delete(); - - g.TabBars.Clear(); - g.CurrentTabBarStack.clear(); - g.ShrinkWidthBuffer.clear(); - - g.ClipperTempData.clear_destruct(); - - g.Tables.Clear(); - g.TablesTempData.clear_destruct(); - g.DrawChannelsTempMergeBuffer.clear(); - - g.ClipboardHandlerData.clear(); - g.MenusIdSubmittedThisFrame.clear(); - g.InputTextState.ClearFreeMemory(); - g.InputTextDeactivatedState.ClearFreeMemory(); - - g.SettingsWindows.clear(); - g.SettingsHandlers.clear(); - - if (g.LogFile) - { -#ifndef IMGUI_DISABLE_TTY_FUNCTIONS - if (g.LogFile != stdout) -#endif - ImFileClose(g.LogFile); - g.LogFile = NULL; - } - g.LogBuffer.clear(); - g.DebugLogBuf.clear(); - g.DebugLogIndex.clear(); - - g.Initialized = false; -} - -// No specific ordering/dependency support, will see as needed -ImGuiID ImGui::AddContextHook(ImGuiContext* ctx, const ImGuiContextHook* hook) -{ - ImGuiContext& g = *ctx; - IM_ASSERT(hook->Callback != NULL && hook->HookId == 0 && hook->Type != ImGuiContextHookType_PendingRemoval_); - g.Hooks.push_back(*hook); - g.Hooks.back().HookId = ++g.HookIdNext; - return g.HookIdNext; -} - -// Deferred removal, avoiding issue with changing vector while iterating it -void ImGui::RemoveContextHook(ImGuiContext* ctx, ImGuiID hook_id) -{ - ImGuiContext& g = *ctx; - IM_ASSERT(hook_id != 0); - for (ImGuiContextHook& hook : g.Hooks) - if (hook.HookId == hook_id) - hook.Type = ImGuiContextHookType_PendingRemoval_; -} - -// Call context hooks (used by e.g. test engine) -// We assume a small number of hooks so all stored in same array -void ImGui::CallContextHooks(ImGuiContext* ctx, ImGuiContextHookType hook_type) -{ - ImGuiContext& g = *ctx; - for (ImGuiContextHook& hook : g.Hooks) - if (hook.Type == hook_type) - hook.Callback(&g, &hook); -} - - -//----------------------------------------------------------------------------- -// [SECTION] MAIN CODE (most of the code! lots of stuff, needs tidying up!) -//----------------------------------------------------------------------------- - -// ImGuiWindow is mostly a dumb struct. It merely has a constructor and a few helper methods -ImGuiWindow::ImGuiWindow(ImGuiContext* ctx, const char* name) : DrawListInst(NULL) -{ - memset(this, 0, sizeof(*this)); - Ctx = ctx; - Name = ImStrdup(name); - NameBufLen = (int)strlen(name) + 1; - ID = ImHashStr(name); - IDStack.push_back(ID); - ViewportAllowPlatformMonitorExtend = -1; - ViewportPos = ImVec2(FLT_MAX, FLT_MAX); - MoveId = GetID("#MOVE"); - TabId = GetID("#TAB"); - ScrollTarget = ImVec2(FLT_MAX, FLT_MAX); - ScrollTargetCenterRatio = ImVec2(0.5f, 0.5f); - AutoFitFramesX = AutoFitFramesY = -1; - AutoPosLastDirection = ImGuiDir_None; - SetWindowPosAllowFlags = SetWindowSizeAllowFlags = SetWindowCollapsedAllowFlags = SetWindowDockAllowFlags = 0; - SetWindowPosVal = SetWindowPosPivot = ImVec2(FLT_MAX, FLT_MAX); - LastFrameActive = -1; - LastFrameJustFocused = -1; - LastTimeActive = -1.0f; - FontWindowScale = FontDpiScale = 1.0f; - SettingsOffset = -1; - DockOrder = -1; - DrawList = &DrawListInst; - DrawList->_Data = &Ctx->DrawListSharedData; - DrawList->_OwnerName = Name; - NavPreferredScoringPosRel[0] = NavPreferredScoringPosRel[1] = ImVec2(FLT_MAX, FLT_MAX); - IM_PLACEMENT_NEW(&WindowClass) ImGuiWindowClass(); -} - -ImGuiWindow::~ImGuiWindow() -{ - IM_ASSERT(DrawList == &DrawListInst); - IM_DELETE(Name); - ColumnsStorage.clear_destruct(); -} - -ImGuiID ImGuiWindow::GetID(const char* str, const char* str_end) -{ - ImGuiID seed = IDStack.back(); - ImGuiID id = ImHashStr(str, str_end ? (str_end - str) : 0, seed); - ImGuiContext& g = *Ctx; - if (g.DebugHookIdInfo == id) - ImGui::DebugHookIdInfo(id, ImGuiDataType_String, str, str_end); - return id; -} - -ImGuiID ImGuiWindow::GetID(const void* ptr) -{ - ImGuiID seed = IDStack.back(); - ImGuiID id = ImHashData(&ptr, sizeof(void*), seed); - ImGuiContext& g = *Ctx; - if (g.DebugHookIdInfo == id) - ImGui::DebugHookIdInfo(id, ImGuiDataType_Pointer, ptr, NULL); - return id; -} - -ImGuiID ImGuiWindow::GetID(int n) -{ - ImGuiID seed = IDStack.back(); - ImGuiID id = ImHashData(&n, sizeof(n), seed); - ImGuiContext& g = *Ctx; - if (g.DebugHookIdInfo == id) - ImGui::DebugHookIdInfo(id, ImGuiDataType_S32, (void*)(intptr_t)n, NULL); - return id; -} - -// This is only used in rare/specific situations to manufacture an ID out of nowhere. -ImGuiID ImGuiWindow::GetIDFromRectangle(const ImRect& r_abs) -{ - ImGuiID seed = IDStack.back(); - ImRect r_rel = ImGui::WindowRectAbsToRel(this, r_abs); - ImGuiID id = ImHashData(&r_rel, sizeof(r_rel), seed); - return id; -} - -static void SetCurrentWindow(ImGuiWindow* window) -{ - ImGuiContext& g = *GImGui; - g.CurrentWindow = window; - g.CurrentTable = window && window->DC.CurrentTableIdx != -1 ? g.Tables.GetByIndex(window->DC.CurrentTableIdx) : NULL; - if (window) - { - g.FontSize = g.DrawListSharedData.FontSize = window->CalcFontSize(); - ImGui::NavUpdateCurrentWindowIsScrollPushableX(); - } -} - -void ImGui::GcCompactTransientMiscBuffers() -{ - ImGuiContext& g = *GImGui; - g.ItemFlagsStack.clear(); - g.GroupStack.clear(); - TableGcCompactSettings(); -} - -// Free up/compact internal window buffers, we can use this when a window becomes unused. -// Not freed: -// - ImGuiWindow, ImGuiWindowSettings, Name, StateStorage, ColumnsStorage (may hold useful data) -// This should have no noticeable visual effect. When the window reappear however, expect new allocation/buffer growth/copy cost. -void ImGui::GcCompactTransientWindowBuffers(ImGuiWindow* window) -{ - window->MemoryCompacted = true; - window->MemoryDrawListIdxCapacity = window->DrawList->IdxBuffer.Capacity; - window->MemoryDrawListVtxCapacity = window->DrawList->VtxBuffer.Capacity; - window->IDStack.clear(); - window->DrawList->_ClearFreeMemory(); - window->DC.ChildWindows.clear(); - window->DC.ItemWidthStack.clear(); - window->DC.TextWrapPosStack.clear(); -} - -void ImGui::GcAwakeTransientWindowBuffers(ImGuiWindow* window) -{ - // We stored capacity of the ImDrawList buffer to reduce growth-caused allocation/copy when awakening. - // The other buffers tends to amortize much faster. - window->MemoryCompacted = false; - window->DrawList->IdxBuffer.reserve(window->MemoryDrawListIdxCapacity); - window->DrawList->VtxBuffer.reserve(window->MemoryDrawListVtxCapacity); - window->MemoryDrawListIdxCapacity = window->MemoryDrawListVtxCapacity = 0; -} - -void ImGui::SetActiveID(ImGuiID id, ImGuiWindow* window) -{ - ImGuiContext& g = *GImGui; - - // Clear previous active id - if (g.ActiveId != 0) - { - // While most behaved code would make an effort to not steal active id during window move/drag operations, - // we at least need to be resilient to it. Canceling the move is rather aggressive and users of 'master' branch - // may prefer the weird ill-defined half working situation ('docking' did assert), so may need to rework that. - if (g.MovingWindow != NULL && g.ActiveId == g.MovingWindow->MoveId) - { - IMGUI_DEBUG_LOG_ACTIVEID("SetActiveID() cancel MovingWindow\n"); - g.MovingWindow = NULL; - } - - // This could be written in a more general way (e.g associate a hook to ActiveId), - // but since this is currently quite an exception we'll leave it as is. - // One common scenario leading to this is: pressing Key ->NavMoveRequestApplyResult() -> ClearActiveId() - if (g.InputTextState.ID == g.ActiveId) - InputTextDeactivateHook(g.ActiveId); - } - - // Set active id - g.ActiveIdIsJustActivated = (g.ActiveId != id); - if (g.ActiveIdIsJustActivated) - { - IMGUI_DEBUG_LOG_ACTIVEID("SetActiveID() old:0x%08X (window \"%s\") -> new:0x%08X (window \"%s\")\n", g.ActiveId, g.ActiveIdWindow ? g.ActiveIdWindow->Name : "", id, window ? window->Name : ""); - g.ActiveIdTimer = 0.0f; - g.ActiveIdHasBeenPressedBefore = false; - g.ActiveIdHasBeenEditedBefore = false; - g.ActiveIdMouseButton = -1; - if (id != 0) - { - g.LastActiveId = id; - g.LastActiveIdTimer = 0.0f; - } - } - g.ActiveId = id; - g.ActiveIdAllowOverlap = false; - g.ActiveIdNoClearOnFocusLoss = false; - g.ActiveIdWindow = window; - g.ActiveIdHasBeenEditedThisFrame = false; - if (id) - { - g.ActiveIdIsAlive = id; - g.ActiveIdSource = (g.NavActivateId == id || g.NavJustMovedToId == id) ? g.NavInputSource : ImGuiInputSource_Mouse; - IM_ASSERT(g.ActiveIdSource != ImGuiInputSource_None); - } - - // Clear declaration of inputs claimed by the widget - // (Please note that this is WIP and not all keys/inputs are thoroughly declared by all widgets yet) - g.ActiveIdUsingNavDirMask = 0x00; - g.ActiveIdUsingAllKeyboardKeys = false; -#ifndef IMGUI_DISABLE_OBSOLETE_KEYIO - g.ActiveIdUsingNavInputMask = 0x00; -#endif -} - -void ImGui::ClearActiveID() -{ - SetActiveID(0, NULL); // g.ActiveId = 0; -} - -void ImGui::SetHoveredID(ImGuiID id) -{ - ImGuiContext& g = *GImGui; - g.HoveredId = id; - g.HoveredIdAllowOverlap = false; - if (id != 0 && g.HoveredIdPreviousFrame != id) - g.HoveredIdTimer = g.HoveredIdNotActiveTimer = 0.0f; -} - -ImGuiID ImGui::GetHoveredID() -{ - ImGuiContext& g = *GImGui; - return g.HoveredId ? g.HoveredId : g.HoveredIdPreviousFrame; -} - -// This is called by ItemAdd(). -// Code not using ItemAdd() may need to call this manually otherwise ActiveId will be cleared. In IMGUI_VERSION_NUM < 18717 this was called by GetID(). -void ImGui::KeepAliveID(ImGuiID id) -{ - ImGuiContext& g = *GImGui; - if (g.ActiveId == id) - g.ActiveIdIsAlive = id; - if (g.ActiveIdPreviousFrame == id) - g.ActiveIdPreviousFrameIsAlive = true; -} - -void ImGui::MarkItemEdited(ImGuiID id) -{ - // This marking is solely to be able to provide info for IsItemDeactivatedAfterEdit(). - // ActiveId might have been released by the time we call this (as in the typical press/release button behavior) but still need to fill the data. - ImGuiContext& g = *GImGui; - if (g.LockMarkEdited > 0) - return; - if (g.ActiveId == id || g.ActiveId == 0) - { - g.ActiveIdHasBeenEditedThisFrame = true; - g.ActiveIdHasBeenEditedBefore = true; - } - - // We accept a MarkItemEdited() on drag and drop targets (see https://github.com/ocornut/imgui/issues/1875#issuecomment-978243343) - // We accept 'ActiveIdPreviousFrame == id' for InputText() returning an edit after it has been taken ActiveId away (#4714) - IM_ASSERT(g.DragDropActive || g.ActiveId == id || g.ActiveId == 0 || g.ActiveIdPreviousFrame == id); - - //IM_ASSERT(g.CurrentWindow->DC.LastItemId == id); - g.LastItemData.StatusFlags |= ImGuiItemStatusFlags_Edited; -} - -bool ImGui::IsWindowContentHoverable(ImGuiWindow* window, ImGuiHoveredFlags flags) -{ - // An active popup disable hovering on other windows (apart from its own children) - // FIXME-OPT: This could be cached/stored within the window. - ImGuiContext& g = *GImGui; - if (g.NavWindow) - if (ImGuiWindow* focused_root_window = g.NavWindow->RootWindowDockTree) - if (focused_root_window->WasActive && focused_root_window != window->RootWindowDockTree) - { - // For the purpose of those flags we differentiate "standard popup" from "modal popup" - // NB: The 'else' is important because Modal windows are also Popups. - bool want_inhibit = false; - if (focused_root_window->Flags & ImGuiWindowFlags_Modal) - want_inhibit = true; - else if ((focused_root_window->Flags & ImGuiWindowFlags_Popup) && !(flags & ImGuiHoveredFlags_AllowWhenBlockedByPopup)) - want_inhibit = true; - - // Inhibit hover unless the window is within the stack of our modal/popup - if (want_inhibit) - if (!IsWindowWithinBeginStackOf(window->RootWindow, focused_root_window)) - return false; - } - - // Filter by viewport - if (window->Viewport != g.MouseViewport) - if (g.MovingWindow == NULL || window->RootWindowDockTree != g.MovingWindow->RootWindowDockTree) - return false; - - return true; -} - -static inline float CalcDelayFromHoveredFlags(ImGuiHoveredFlags flags) -{ - ImGuiContext& g = *GImGui; - if (flags & ImGuiHoveredFlags_DelayShort) - return g.Style.HoverDelayShort; - if (flags & ImGuiHoveredFlags_DelayNormal) - return g.Style.HoverDelayNormal; - return 0.0f; -} - -// This is roughly matching the behavior of internal-facing ItemHoverable() -// - we allow hovering to be true when ActiveId==window->MoveID, so that clicking on non-interactive items such as a Text() item still returns true with IsItemHovered() -// - this should work even for non-interactive items that have no ID, so we cannot use LastItemId -bool ImGui::IsItemHovered(ImGuiHoveredFlags flags) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - IM_ASSERT((flags & ~ImGuiHoveredFlags_AllowedMaskForIsItemHovered) == 0 && "Invalid flags for IsItemHovered()!"); - - if (g.NavDisableMouseHover && !g.NavDisableHighlight && !(flags & ImGuiHoveredFlags_NoNavOverride)) - { - if ((g.LastItemData.InFlags & ImGuiItemFlags_Disabled) && !(flags & ImGuiHoveredFlags_AllowWhenDisabled)) - return false; - if (!IsItemFocused()) - return false; - - if (flags & ImGuiHoveredFlags_ForTooltip) - flags |= g.Style.HoverFlagsForTooltipNav; - } - else - { - // Test for bounding box overlap, as updated as ItemAdd() - ImGuiItemStatusFlags status_flags = g.LastItemData.StatusFlags; - if (!(status_flags & ImGuiItemStatusFlags_HoveredRect)) - return false; - - if (flags & ImGuiHoveredFlags_ForTooltip) - flags |= g.Style.HoverFlagsForTooltipMouse; - - IM_ASSERT((flags & (ImGuiHoveredFlags_AnyWindow | ImGuiHoveredFlags_RootWindow | ImGuiHoveredFlags_ChildWindows | ImGuiHoveredFlags_NoPopupHierarchy | ImGuiHoveredFlags_DockHierarchy)) == 0); // Flags not supported by this function - - // Done with rectangle culling so we can perform heavier checks now - // Test if we are hovering the right window (our window could be behind another window) - // [2021/03/02] Reworked / reverted the revert, finally. Note we want e.g. BeginGroup/ItemAdd/EndGroup to work as well. (#3851) - // [2017/10/16] Reverted commit 344d48be3 and testing RootWindow instead. I believe it is correct to NOT test for RootWindow but this leaves us unable - // to use IsItemHovered() after EndChild() itself. Until a solution is found I believe reverting to the test from 2017/09/27 is safe since this was - // the test that has been running for a long while. - if (g.HoveredWindow != window && (status_flags & ImGuiItemStatusFlags_HoveredWindow) == 0) - if ((flags & ImGuiHoveredFlags_AllowWhenOverlappedByWindow) == 0) - return false; - - // Test if another item is active (e.g. being dragged) - const ImGuiID id = g.LastItemData.ID; - if ((flags & ImGuiHoveredFlags_AllowWhenBlockedByActiveItem) == 0) - if (g.ActiveId != 0 && g.ActiveId != id && !g.ActiveIdAllowOverlap) - if (g.ActiveId != window->MoveId && g.ActiveId != window->TabId) - return false; - - // Test if interactions on this window are blocked by an active popup or modal. - // The ImGuiHoveredFlags_AllowWhenBlockedByPopup flag will be tested here. - if (!IsWindowContentHoverable(window, flags) && !(g.LastItemData.InFlags & ImGuiItemFlags_NoWindowHoverableCheck)) - return false; - - // Test if the item is disabled - if ((g.LastItemData.InFlags & ImGuiItemFlags_Disabled) && !(flags & ImGuiHoveredFlags_AllowWhenDisabled)) - return false; - - // Special handling for calling after Begin() which represent the title bar or tab. - // When the window is skipped/collapsed (SkipItems==true) that last item (always ->MoveId submitted by Begin) - // will never be overwritten so we need to detect the case. - if (id == window->MoveId && window->WriteAccessed) - return false; - - // Test if using AllowOverlap and overlapped - if ((g.LastItemData.InFlags & ImGuiItemFlags_AllowOverlap) && id != 0) - if ((flags & ImGuiHoveredFlags_AllowWhenOverlappedByItem) == 0) - if (g.HoveredIdPreviousFrame != g.LastItemData.ID) - return false; - } - - // Handle hover delay - // (some ideas: https://www.nngroup.com/articles/timing-exposing-content) - const float delay = CalcDelayFromHoveredFlags(flags); - if (delay > 0.0f || (flags & ImGuiHoveredFlags_Stationary)) - { - ImGuiID hover_delay_id = (g.LastItemData.ID != 0) ? g.LastItemData.ID : window->GetIDFromRectangle(g.LastItemData.Rect); - if ((flags & ImGuiHoveredFlags_NoSharedDelay) && (g.HoverItemDelayIdPreviousFrame != hover_delay_id)) - g.HoverItemDelayTimer = 0.0f; - g.HoverItemDelayId = hover_delay_id; - - // When changing hovered item we requires a bit of stationary delay before activating hover timer, - // but once unlocked on a given item we also moving. - //if (g.HoverDelayTimer >= delay && (g.HoverDelayTimer - g.IO.DeltaTime < delay || g.MouseStationaryTimer - g.IO.DeltaTime < g.Style.HoverStationaryDelay)) { IMGUI_DEBUG_LOG("HoverDelayTimer = %f/%f, MouseStationaryTimer = %f\n", g.HoverDelayTimer, delay, g.MouseStationaryTimer); } - if ((flags & ImGuiHoveredFlags_Stationary) != 0 && g.HoverItemUnlockedStationaryId != hover_delay_id) - return false; - - if (g.HoverItemDelayTimer < delay) - return false; - } - - return true; -} - -// Internal facing ItemHoverable() used when submitting widgets. Differs slightly from IsItemHovered(). -// (this does not rely on LastItemData it can be called from a ButtonBehavior() call not following an ItemAdd() call) -// FIXME-LEGACY: the 'ImGuiItemFlags item_flags' parameter was added on 2023-06-28. -// If you used this in your legacy/custom widgets code: -// - Commonly: if your ItemHoverable() call comes after an ItemAdd() call: pass 'item_flags = g.LastItemData.InFlags'. -// - Rare: otherwise you may pass 'item_flags = 0' (ImGuiItemFlags_None) unless you want to benefit from special behavior handled by ItemHoverable. -bool ImGui::ItemHoverable(const ImRect& bb, ImGuiID id, ImGuiItemFlags item_flags) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - if (g.HoveredWindow != window) - return false; - if (!IsMouseHoveringRect(bb.Min, bb.Max)) - return false; - - if (g.HoveredId != 0 && g.HoveredId != id && !g.HoveredIdAllowOverlap) - return false; - if (g.ActiveId != 0 && g.ActiveId != id && !g.ActiveIdAllowOverlap) - return false; - - // Done with rectangle culling so we can perform heavier checks now. - if (!(item_flags & ImGuiItemFlags_NoWindowHoverableCheck) && !IsWindowContentHoverable(window, ImGuiHoveredFlags_None)) - { - g.HoveredIdDisabled = true; - return false; - } - - // We exceptionally allow this function to be called with id==0 to allow using it for easy high-level - // hover test in widgets code. We could also decide to split this function is two. - if (id != 0) - { - // Drag source doesn't report as hovered - if (g.DragDropActive && g.DragDropPayload.SourceId == id && !(g.DragDropSourceFlags & ImGuiDragDropFlags_SourceNoDisableHover)) - return false; - - SetHoveredID(id); - - // AllowOverlap mode (rarely used) requires previous frame HoveredId to be null or to match. - // This allows using patterns where a later submitted widget overlaps a previous one. Generally perceived as a front-to-back hit-test. - if (item_flags & ImGuiItemFlags_AllowOverlap) - { - g.HoveredIdAllowOverlap = true; - if (g.HoveredIdPreviousFrame != id) - return false; - } - } - - // When disabled we'll return false but still set HoveredId - if (item_flags & ImGuiItemFlags_Disabled) - { - // Release active id if turning disabled - if (g.ActiveId == id && id != 0) - ClearActiveID(); - g.HoveredIdDisabled = true; - return false; - } - - if (id != 0) - { - // [DEBUG] Item Picker tool! - // We perform the check here because SetHoveredID() is not frequently called (1~ time a frame), making - // the cost of this tool near-zero. We can get slightly better call-stack and support picking non-hovered - // items if we performed the test in ItemAdd(), but that would incur a small runtime cost. - if (g.DebugItemPickerActive && g.HoveredIdPreviousFrame == id) - GetForegroundDrawList()->AddRect(bb.Min, bb.Max, IM_COL32(255, 255, 0, 255)); - if (g.DebugItemPickerBreakId == id) - IM_DEBUG_BREAK(); - } - - if (g.NavDisableMouseHover) - return false; - - return true; -} - -// FIXME: This is inlined/duplicated in ItemAdd() -bool ImGui::IsClippedEx(const ImRect& bb, ImGuiID id) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - if (!bb.Overlaps(window->ClipRect)) - if (id == 0 || (id != g.ActiveId && id != g.NavId)) - if (!g.LogEnabled) - return true; - return false; -} - -// This is also inlined in ItemAdd() -// Note: if ImGuiItemStatusFlags_HasDisplayRect is set, user needs to set g.LastItemData.DisplayRect. -void ImGui::SetLastItemData(ImGuiID item_id, ImGuiItemFlags in_flags, ImGuiItemStatusFlags item_flags, const ImRect& item_rect) -{ - ImGuiContext& g = *GImGui; - g.LastItemData.ID = item_id; - g.LastItemData.InFlags = in_flags; - g.LastItemData.StatusFlags = item_flags; - g.LastItemData.Rect = g.LastItemData.NavRect = item_rect; -} - -float ImGui::CalcWrapWidthForPos(const ImVec2& pos, float wrap_pos_x) -{ - if (wrap_pos_x < 0.0f) - return 0.0f; - - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - if (wrap_pos_x == 0.0f) - { - // We could decide to setup a default wrapping max point for auto-resizing windows, - // or have auto-wrap (with unspecified wrapping pos) behave as a ContentSize extending function? - //if (window->Hidden && (window->Flags & ImGuiWindowFlags_AlwaysAutoResize)) - // wrap_pos_x = ImMax(window->WorkRect.Min.x + g.FontSize * 10.0f, window->WorkRect.Max.x); - //else - wrap_pos_x = window->WorkRect.Max.x; - } - else if (wrap_pos_x > 0.0f) - { - wrap_pos_x += window->Pos.x - window->Scroll.x; // wrap_pos_x is provided is window local space - } - - return ImMax(wrap_pos_x - pos.x, 1.0f); -} - -// IM_ALLOC() == ImGui::MemAlloc() -void* ImGui::MemAlloc(size_t size) -{ - void* ptr = (*GImAllocatorAllocFunc)(size, GImAllocatorUserData); -#ifndef IMGUI_DISABLE_DEBUG_TOOLS - if (ImGuiContext* ctx = GImGui) - DebugAllocHook(&ctx->DebugAllocInfo, ctx->FrameCount, ptr, size); -#endif - return ptr; -} - -// IM_FREE() == ImGui::MemFree() -void ImGui::MemFree(void* ptr) -{ -#ifndef IMGUI_DISABLE_DEBUG_TOOLS - if (ptr != NULL) - if (ImGuiContext* ctx = GImGui) - DebugAllocHook(&ctx->DebugAllocInfo, ctx->FrameCount, ptr, (size_t)-1); -#endif - return (*GImAllocatorFreeFunc)(ptr, GImAllocatorUserData); -} - -// We record the number of allocation in recent frames, as a way to audit/sanitize our guiding principles of "no allocations on idle/repeating frames" -void ImGui::DebugAllocHook(ImGuiDebugAllocInfo* info, int frame_count, void* ptr, size_t size) -{ - ImGuiDebugAllocEntry* entry = &info->LastEntriesBuf[info->LastEntriesIdx]; - IM_UNUSED(ptr); - if (entry->FrameCount != frame_count) - { - info->LastEntriesIdx = (info->LastEntriesIdx + 1) % IM_ARRAYSIZE(info->LastEntriesBuf); - entry = &info->LastEntriesBuf[info->LastEntriesIdx]; - entry->FrameCount = frame_count; - entry->AllocCount = entry->FreeCount = 0; - } - if (size != (size_t)-1) - { - entry->AllocCount++; - info->TotalAllocCount++; - //printf("[%05d] MemAlloc(%d) -> 0x%p\n", frame_count, size, ptr); - } - else - { - entry->FreeCount++; - info->TotalFreeCount++; - //printf("[%05d] MemFree(0x%p)\n", frame_count, ptr); - } -} - -const char* ImGui::GetClipboardText() -{ - ImGuiContext& g = *GImGui; - return g.IO.GetClipboardTextFn ? g.IO.GetClipboardTextFn(g.IO.ClipboardUserData) : ""; -} - -void ImGui::SetClipboardText(const char* text) -{ - ImGuiContext& g = *GImGui; - if (g.IO.SetClipboardTextFn) - g.IO.SetClipboardTextFn(g.IO.ClipboardUserData, text); -} - -const char* ImGui::GetVersion() -{ - return IMGUI_VERSION; -} - -ImGuiIO& ImGui::GetIO() -{ - IM_ASSERT(GImGui != NULL && "No current context. Did you call ImGui::CreateContext() and ImGui::SetCurrentContext() ?"); - return GImGui->IO; -} - -ImGuiPlatformIO& ImGui::GetPlatformIO() -{ - IM_ASSERT(GImGui != NULL && "No current context. Did you call ImGui::CreateContext() or ImGui::SetCurrentContext()?"); - return GImGui->PlatformIO; -} - -// Pass this to your backend rendering function! Valid after Render() and until the next call to NewFrame() -ImDrawData* ImGui::GetDrawData() -{ - ImGuiContext& g = *GImGui; - ImGuiViewportP* viewport = g.Viewports[0]; - return viewport->DrawDataP.Valid ? &viewport->DrawDataP : NULL; -} - -double ImGui::GetTime() -{ - return GImGui->Time; -} - -int ImGui::GetFrameCount() -{ - return GImGui->FrameCount; -} - -static ImDrawList* GetViewportBgFgDrawList(ImGuiViewportP* viewport, size_t drawlist_no, const char* drawlist_name) -{ - // Create the draw list on demand, because they are not frequently used for all viewports - ImGuiContext& g = *GImGui; - IM_ASSERT(drawlist_no < IM_ARRAYSIZE(viewport->BgFgDrawLists)); - ImDrawList* draw_list = viewport->BgFgDrawLists[drawlist_no]; - if (draw_list == NULL) - { - draw_list = IM_NEW(ImDrawList)(&g.DrawListSharedData); - draw_list->_OwnerName = drawlist_name; - viewport->BgFgDrawLists[drawlist_no] = draw_list; - } - - // Our ImDrawList system requires that there is always a command - if (viewport->BgFgDrawListsLastFrame[drawlist_no] != g.FrameCount) - { - draw_list->_ResetForNewFrame(); - draw_list->PushTextureID(g.IO.Fonts->TexID); - draw_list->PushClipRect(viewport->Pos, viewport->Pos + viewport->Size, false); - viewport->BgFgDrawListsLastFrame[drawlist_no] = g.FrameCount; - } - return draw_list; -} - -ImDrawList* ImGui::GetBackgroundDrawList(ImGuiViewport* viewport) -{ - return GetViewportBgFgDrawList((ImGuiViewportP*)viewport, 0, "##Background"); -} - -ImDrawList* ImGui::GetBackgroundDrawList() -{ - ImGuiContext& g = *GImGui; - return GetBackgroundDrawList(g.CurrentWindow->Viewport); -} - -ImDrawList* ImGui::GetForegroundDrawList(ImGuiViewport* viewport) -{ - return GetViewportBgFgDrawList((ImGuiViewportP*)viewport, 1, "##Foreground"); -} - -ImDrawList* ImGui::GetForegroundDrawList() -{ - ImGuiContext& g = *GImGui; - return GetForegroundDrawList(g.CurrentWindow->Viewport); -} - -ImDrawListSharedData* ImGui::GetDrawListSharedData() -{ - return &GImGui->DrawListSharedData; -} - -void ImGui::StartMouseMovingWindow(ImGuiWindow* window) -{ - // Set ActiveId even if the _NoMove flag is set. Without it, dragging away from a window with _NoMove would activate hover on other windows. - // We _also_ call this when clicking in a window empty space when io.ConfigWindowsMoveFromTitleBarOnly is set, but clear g.MovingWindow afterward. - // This is because we want ActiveId to be set even when the window is not permitted to move. - ImGuiContext& g = *GImGui; - FocusWindow(window); - SetActiveID(window->MoveId, window); - g.NavDisableHighlight = true; - g.ActiveIdClickOffset = g.IO.MouseClickedPos[0] - window->RootWindowDockTree->Pos; - g.ActiveIdNoClearOnFocusLoss = true; - SetActiveIdUsingAllKeyboardKeys(); - - bool can_move_window = true; - if ((window->Flags & ImGuiWindowFlags_NoMove) || (window->RootWindowDockTree->Flags & ImGuiWindowFlags_NoMove)) - can_move_window = false; - if (ImGuiDockNode* node = window->DockNodeAsHost) - if (node->VisibleWindow && (node->VisibleWindow->Flags & ImGuiWindowFlags_NoMove)) - can_move_window = false; - if (can_move_window) - g.MovingWindow = window; -} - -// We use 'undock_floating_node == false' when dragging from title bar to allow moving groups of floating nodes without undocking them. -// - undock_floating_node == true: when dragging from a floating node within a hierarchy, always undock the node. -// - undock_floating_node == false: when dragging from a floating node within a hierarchy, move root window. -void ImGui::StartMouseMovingWindowOrNode(ImGuiWindow* window, ImGuiDockNode* node, bool undock_floating_node) -{ - ImGuiContext& g = *GImGui; - bool can_undock_node = false; - if (node != NULL && node->VisibleWindow && (node->VisibleWindow->Flags & ImGuiWindowFlags_NoMove) == 0 && (node->MergedFlags & ImGuiDockNodeFlags_NoUndocking) == 0) - { - // Can undock if: - // - part of a floating node hierarchy with more than one visible node (if only one is visible, we'll just move the whole hierarchy) - // - part of a dockspace node hierarchy (trivia: undocking from a fixed/central node will create a new node and copy windows) - ImGuiDockNode* root_node = DockNodeGetRootNode(node); - if (root_node->OnlyNodeWithWindows != node || root_node->CentralNode != NULL) // -V1051 PVS-Studio thinks node should be root_node and is wrong about that. - if (undock_floating_node || root_node->IsDockSpace()) - can_undock_node = true; - } - - const bool clicked = IsMouseClicked(0); - const bool dragging = IsMouseDragging(0, g.IO.MouseDragThreshold * 1.70f); - if (can_undock_node && dragging) - DockContextQueueUndockNode(&g, node); // Will lead to DockNodeStartMouseMovingWindow() -> StartMouseMovingWindow() being called next frame - else if (!can_undock_node && (clicked || dragging) && g.MovingWindow != window) - StartMouseMovingWindow(window); -} - -// Handle mouse moving window -// Note: moving window with the navigation keys (Square + d-pad / CTRL+TAB + Arrows) are processed in NavUpdateWindowing() -// FIXME: We don't have strong guarantee that g.MovingWindow stay synched with g.ActiveId == g.MovingWindow->MoveId. -// This is currently enforced by the fact that BeginDragDropSource() is setting all g.ActiveIdUsingXXXX flags to inhibit navigation inputs, -// but if we should more thoroughly test cases where g.ActiveId or g.MovingWindow gets changed and not the other. -void ImGui::UpdateMouseMovingWindowNewFrame() -{ - ImGuiContext& g = *GImGui; - if (g.MovingWindow != NULL) - { - // We actually want to move the root window. g.MovingWindow == window we clicked on (could be a child window). - // We track it to preserve Focus and so that generally ActiveIdWindow == MovingWindow and ActiveId == MovingWindow->MoveId for consistency. - KeepAliveID(g.ActiveId); - IM_ASSERT(g.MovingWindow && g.MovingWindow->RootWindowDockTree); - ImGuiWindow* moving_window = g.MovingWindow->RootWindowDockTree; - - // When a window stop being submitted while being dragged, it may will its viewport until next Begin() - const bool window_disappared = (!moving_window->WasActive && !moving_window->Active); - if (g.IO.MouseDown[0] && IsMousePosValid(&g.IO.MousePos) && !window_disappared) - { - ImVec2 pos = g.IO.MousePos - g.ActiveIdClickOffset; - if (moving_window->Pos.x != pos.x || moving_window->Pos.y != pos.y) - { - SetWindowPos(moving_window, pos, ImGuiCond_Always); - if (moving_window->Viewport && moving_window->ViewportOwned) // Synchronize viewport immediately because some overlays may relies on clipping rectangle before we Begin() into the window. - { - moving_window->Viewport->Pos = pos; - moving_window->Viewport->UpdateWorkRect(); - } - } - FocusWindow(g.MovingWindow); - } - else - { - if (!window_disappared) - { - // Try to merge the window back into the main viewport. - // This works because MouseViewport should be != MovingWindow->Viewport on release (as per code in UpdateViewports) - if (g.ConfigFlagsCurrFrame & ImGuiConfigFlags_ViewportsEnable) - UpdateTryMergeWindowIntoHostViewport(moving_window, g.MouseViewport); - - // Restore the mouse viewport so that we don't hover the viewport _under_ the moved window during the frame we released the mouse button. - if (moving_window->Viewport && !IsDragDropPayloadBeingAccepted()) - g.MouseViewport = moving_window->Viewport; - - // Clear the NoInput window flag set by the Viewport system - if (moving_window->Viewport) - moving_window->Viewport->Flags &= ~ImGuiViewportFlags_NoInputs; - } - - g.MovingWindow = NULL; - ClearActiveID(); - } - } - else - { - // When clicking/dragging from a window that has the _NoMove flag, we still set the ActiveId in order to prevent hovering others. - if (g.ActiveIdWindow && g.ActiveIdWindow->MoveId == g.ActiveId) - { - KeepAliveID(g.ActiveId); - if (!g.IO.MouseDown[0]) - ClearActiveID(); - } - } -} - -// Initiate moving window when clicking on empty space or title bar. -// Handle left-click and right-click focus. -void ImGui::UpdateMouseMovingWindowEndFrame() -{ - ImGuiContext& g = *GImGui; - if (g.ActiveId != 0 || g.HoveredId != 0) - return; - - // Unless we just made a window/popup appear - if (g.NavWindow && g.NavWindow->Appearing) - return; - - // Click on empty space to focus window and start moving - // (after we're done with all our widgets, so e.g. clicking on docking tab-bar which have set HoveredId already and not get us here!) - if (g.IO.MouseClicked[0]) - { - // Handle the edge case of a popup being closed while clicking in its empty space. - // If we try to focus it, FocusWindow() > ClosePopupsOverWindow() will accidentally close any parent popups because they are not linked together any more. - ImGuiWindow* root_window = g.HoveredWindow ? g.HoveredWindow->RootWindow : NULL; - const bool is_closed_popup = root_window && (root_window->Flags & ImGuiWindowFlags_Popup) && !IsPopupOpen(root_window->PopupId, ImGuiPopupFlags_AnyPopupLevel); - - if (root_window != NULL && !is_closed_popup) - { - StartMouseMovingWindow(g.HoveredWindow); //-V595 - - // Cancel moving if clicked outside of title bar - if (g.IO.ConfigWindowsMoveFromTitleBarOnly) - if (!(root_window->Flags & ImGuiWindowFlags_NoTitleBar) || root_window->DockIsActive) - if (!root_window->TitleBarRect().Contains(g.IO.MouseClickedPos[0])) - g.MovingWindow = NULL; - - // Cancel moving if clicked over an item which was disabled or inhibited by popups (note that we know HoveredId == 0 already) - if (g.HoveredIdDisabled) - g.MovingWindow = NULL; - } - else if (root_window == NULL && g.NavWindow != NULL) - { - // Clicking on void disable focus - FocusWindow(NULL, ImGuiFocusRequestFlags_UnlessBelowModal); - } - } - - // With right mouse button we close popups without changing focus based on where the mouse is aimed - // Instead, focus will be restored to the window under the bottom-most closed popup. - // (The left mouse button path calls FocusWindow on the hovered window, which will lead NewFrame->ClosePopupsOverWindow to trigger) - if (g.IO.MouseClicked[1]) - { - // Find the top-most window between HoveredWindow and the top-most Modal Window. - // This is where we can trim the popup stack. - ImGuiWindow* modal = GetTopMostPopupModal(); - bool hovered_window_above_modal = g.HoveredWindow && (modal == NULL || IsWindowAbove(g.HoveredWindow, modal)); - ClosePopupsOverWindow(hovered_window_above_modal ? g.HoveredWindow : modal, true); - } -} - -// This is called during NewFrame()->UpdateViewportsNewFrame() only. -// Need to keep in sync with SetWindowPos() -static void TranslateWindow(ImGuiWindow* window, const ImVec2& delta) -{ - window->Pos += delta; - window->ClipRect.Translate(delta); - window->OuterRectClipped.Translate(delta); - window->InnerRect.Translate(delta); - window->DC.CursorPos += delta; - window->DC.CursorStartPos += delta; - window->DC.CursorMaxPos += delta; - window->DC.IdealMaxPos += delta; -} - -static void ScaleWindow(ImGuiWindow* window, float scale) -{ - ImVec2 origin = window->Viewport->Pos; - window->Pos = ImFloor((window->Pos - origin) * scale + origin); - window->Size = ImTrunc(window->Size * scale); - window->SizeFull = ImTrunc(window->SizeFull * scale); - window->ContentSize = ImTrunc(window->ContentSize * scale); -} - -static bool IsWindowActiveAndVisible(ImGuiWindow* window) -{ - return (window->Active) && (!window->Hidden); -} - -// The reason this is exposed in imgui_internal.h is: on touch-based system that don't have hovering, we want to dispatch inputs to the right target (imgui vs imgui+app) -void ImGui::UpdateHoveredWindowAndCaptureFlags() -{ - ImGuiContext& g = *GImGui; - ImGuiIO& io = g.IO; - g.WindowsHoverPadding = ImMax(g.Style.TouchExtraPadding, ImVec2(WINDOWS_HOVER_PADDING, WINDOWS_HOVER_PADDING)); - - // Find the window hovered by mouse: - // - Child windows can extend beyond the limit of their parent so we need to derive HoveredRootWindow from HoveredWindow. - // - When moving a window we can skip the search, which also conveniently bypasses the fact that window->WindowRectClipped is lagging as this point of the frame. - // - We also support the moved window toggling the NoInputs flag after moving has started in order to be able to detect windows below it, which is useful for e.g. docking mechanisms. - bool clear_hovered_windows = false; - FindHoveredWindow(); - IM_ASSERT(g.HoveredWindow == NULL || g.HoveredWindow == g.MovingWindow || g.HoveredWindow->Viewport == g.MouseViewport); - - // Modal windows prevents mouse from hovering behind them. - ImGuiWindow* modal_window = GetTopMostPopupModal(); - if (modal_window && g.HoveredWindow && !IsWindowWithinBeginStackOf(g.HoveredWindow->RootWindow, modal_window)) // FIXME-MERGE: RootWindowDockTree ? - clear_hovered_windows = true; - - // Disabled mouse? - if (io.ConfigFlags & ImGuiConfigFlags_NoMouse) - clear_hovered_windows = true; - - // We track click ownership. When clicked outside of a window the click is owned by the application and - // won't report hovering nor request capture even while dragging over our windows afterward. - const bool has_open_popup = (g.OpenPopupStack.Size > 0); - const bool has_open_modal = (modal_window != NULL); - int mouse_earliest_down = -1; - bool mouse_any_down = false; - for (int i = 0; i < IM_ARRAYSIZE(io.MouseDown); i++) - { - if (io.MouseClicked[i]) - { - io.MouseDownOwned[i] = (g.HoveredWindow != NULL) || has_open_popup; - io.MouseDownOwnedUnlessPopupClose[i] = (g.HoveredWindow != NULL) || has_open_modal; - } - mouse_any_down |= io.MouseDown[i]; - if (io.MouseDown[i]) - if (mouse_earliest_down == -1 || io.MouseClickedTime[i] < io.MouseClickedTime[mouse_earliest_down]) - mouse_earliest_down = i; - } - const bool mouse_avail = (mouse_earliest_down == -1) || io.MouseDownOwned[mouse_earliest_down]; - const bool mouse_avail_unless_popup_close = (mouse_earliest_down == -1) || io.MouseDownOwnedUnlessPopupClose[mouse_earliest_down]; - - // If mouse was first clicked outside of ImGui bounds we also cancel out hovering. - // FIXME: For patterns of drag and drop across OS windows, we may need to rework/remove this test (first committed 311c0ca9 on 2015/02) - const bool mouse_dragging_extern_payload = g.DragDropActive && (g.DragDropSourceFlags & ImGuiDragDropFlags_SourceExtern) != 0; - if (!mouse_avail && !mouse_dragging_extern_payload) - clear_hovered_windows = true; - - if (clear_hovered_windows) - g.HoveredWindow = g.HoveredWindowUnderMovingWindow = NULL; - - // Update io.WantCaptureMouse for the user application (true = dispatch mouse info to Dear ImGui only, false = dispatch mouse to Dear ImGui + underlying app) - // Update io.WantCaptureMouseAllowPopupClose (experimental) to give a chance for app to react to popup closure with a drag - if (g.WantCaptureMouseNextFrame != -1) - { - io.WantCaptureMouse = io.WantCaptureMouseUnlessPopupClose = (g.WantCaptureMouseNextFrame != 0); - } - else - { - io.WantCaptureMouse = (mouse_avail && (g.HoveredWindow != NULL || mouse_any_down)) || has_open_popup; - io.WantCaptureMouseUnlessPopupClose = (mouse_avail_unless_popup_close && (g.HoveredWindow != NULL || mouse_any_down)) || has_open_modal; - } - - // Update io.WantCaptureKeyboard for the user application (true = dispatch keyboard info to Dear ImGui only, false = dispatch keyboard info to Dear ImGui + underlying app) - if (g.WantCaptureKeyboardNextFrame != -1) - io.WantCaptureKeyboard = (g.WantCaptureKeyboardNextFrame != 0); - else - io.WantCaptureKeyboard = (g.ActiveId != 0) || (modal_window != NULL); - if (io.NavActive && (io.ConfigFlags & ImGuiConfigFlags_NavEnableKeyboard) && !(io.ConfigFlags & ImGuiConfigFlags_NavNoCaptureKeyboard)) - io.WantCaptureKeyboard = true; - - // Update io.WantTextInput flag, this is to allow systems without a keyboard (e.g. mobile, hand-held) to show a software keyboard if possible - io.WantTextInput = (g.WantTextInputNextFrame != -1) ? (g.WantTextInputNextFrame != 0) : false; -} - -void ImGui::NewFrame() -{ - IM_ASSERT(GImGui != NULL && "No current context. Did you call ImGui::CreateContext() and ImGui::SetCurrentContext() ?"); - ImGuiContext& g = *GImGui; - - // Remove pending delete hooks before frame start. - // This deferred removal avoid issues of removal while iterating the hook vector - for (int n = g.Hooks.Size - 1; n >= 0; n--) - if (g.Hooks[n].Type == ImGuiContextHookType_PendingRemoval_) - g.Hooks.erase(&g.Hooks[n]); - - CallContextHooks(&g, ImGuiContextHookType_NewFramePre); - - // Check and assert for various common IO and Configuration mistakes - g.ConfigFlagsLastFrame = g.ConfigFlagsCurrFrame; - ErrorCheckNewFrameSanityChecks(); - g.ConfigFlagsCurrFrame = g.IO.ConfigFlags; - - // Load settings on first frame, save settings when modified (after a delay) - UpdateSettings(); - - g.Time += g.IO.DeltaTime; - g.WithinFrameScope = true; - g.FrameCount += 1; - g.TooltipOverrideCount = 0; - g.WindowsActiveCount = 0; - g.MenusIdSubmittedThisFrame.resize(0); - - // Calculate frame-rate for the user, as a purely luxurious feature - g.FramerateSecPerFrameAccum += g.IO.DeltaTime - g.FramerateSecPerFrame[g.FramerateSecPerFrameIdx]; - g.FramerateSecPerFrame[g.FramerateSecPerFrameIdx] = g.IO.DeltaTime; - g.FramerateSecPerFrameIdx = (g.FramerateSecPerFrameIdx + 1) % IM_ARRAYSIZE(g.FramerateSecPerFrame); - g.FramerateSecPerFrameCount = ImMin(g.FramerateSecPerFrameCount + 1, IM_ARRAYSIZE(g.FramerateSecPerFrame)); - g.IO.Framerate = (g.FramerateSecPerFrameAccum > 0.0f) ? (1.0f / (g.FramerateSecPerFrameAccum / (float)g.FramerateSecPerFrameCount)) : FLT_MAX; - - // Process input queue (trickle as many events as possible), turn events into writes to IO structure - g.InputEventsTrail.resize(0); - UpdateInputEvents(g.IO.ConfigInputTrickleEventQueue); - - // Update viewports (after processing input queue, so io.MouseHoveredViewport is set) - UpdateViewportsNewFrame(); - - // Setup current font and draw list shared data - // FIXME-VIEWPORT: the concept of a single ClipRectFullscreen is not ideal! - g.IO.Fonts->Locked = true; - SetCurrentFont(GetDefaultFont()); - IM_ASSERT(g.Font->IsLoaded()); - ImRect virtual_space(FLT_MAX, FLT_MAX, -FLT_MAX, -FLT_MAX); - for (ImGuiViewportP* viewport : g.Viewports) - virtual_space.Add(viewport->GetMainRect()); - g.DrawListSharedData.ClipRectFullscreen = virtual_space.ToVec4(); - g.DrawListSharedData.CurveTessellationTol = g.Style.CurveTessellationTol; - g.DrawListSharedData.SetCircleTessellationMaxError(g.Style.CircleTessellationMaxError); - g.DrawListSharedData.InitialFlags = ImDrawListFlags_None; - if (g.Style.AntiAliasedLines) - g.DrawListSharedData.InitialFlags |= ImDrawListFlags_AntiAliasedLines; - if (g.Style.AntiAliasedLinesUseTex && !(g.Font->ContainerAtlas->Flags & ImFontAtlasFlags_NoBakedLines)) - g.DrawListSharedData.InitialFlags |= ImDrawListFlags_AntiAliasedLinesUseTex; - if (g.Style.AntiAliasedFill) - g.DrawListSharedData.InitialFlags |= ImDrawListFlags_AntiAliasedFill; - if (g.IO.BackendFlags & ImGuiBackendFlags_RendererHasVtxOffset) - g.DrawListSharedData.InitialFlags |= ImDrawListFlags_AllowVtxOffset; - - // Mark rendering data as invalid to prevent user who may have a handle on it to use it. - for (ImGuiViewportP* viewport : g.Viewports) - { - viewport->DrawData = NULL; - viewport->DrawDataP.Valid = false; - } - - // Drag and drop keep the source ID alive so even if the source disappear our state is consistent - if (g.DragDropActive && g.DragDropPayload.SourceId == g.ActiveId) - KeepAliveID(g.DragDropPayload.SourceId); - - // Update HoveredId data - if (!g.HoveredIdPreviousFrame) - g.HoveredIdTimer = 0.0f; - if (!g.HoveredIdPreviousFrame || (g.HoveredId && g.ActiveId == g.HoveredId)) - g.HoveredIdNotActiveTimer = 0.0f; - if (g.HoveredId) - g.HoveredIdTimer += g.IO.DeltaTime; - if (g.HoveredId && g.ActiveId != g.HoveredId) - g.HoveredIdNotActiveTimer += g.IO.DeltaTime; - g.HoveredIdPreviousFrame = g.HoveredId; - g.HoveredId = 0; - g.HoveredIdAllowOverlap = false; - g.HoveredIdDisabled = false; - - // Clear ActiveID if the item is not alive anymore. - // In 1.87, the common most call to KeepAliveID() was moved from GetID() to ItemAdd(). - // As a result, custom widget using ButtonBehavior() _without_ ItemAdd() need to call KeepAliveID() themselves. - if (g.ActiveId != 0 && g.ActiveIdIsAlive != g.ActiveId && g.ActiveIdPreviousFrame == g.ActiveId) - { - IMGUI_DEBUG_LOG_ACTIVEID("NewFrame(): ClearActiveID() because it isn't marked alive anymore!\n"); - ClearActiveID(); - } - - // Update ActiveId data (clear reference to active widget if the widget isn't alive anymore) - if (g.ActiveId) - g.ActiveIdTimer += g.IO.DeltaTime; - g.LastActiveIdTimer += g.IO.DeltaTime; - g.ActiveIdPreviousFrame = g.ActiveId; - g.ActiveIdPreviousFrameWindow = g.ActiveIdWindow; - g.ActiveIdPreviousFrameHasBeenEditedBefore = g.ActiveIdHasBeenEditedBefore; - g.ActiveIdIsAlive = 0; - g.ActiveIdHasBeenEditedThisFrame = false; - g.ActiveIdPreviousFrameIsAlive = false; - g.ActiveIdIsJustActivated = false; - if (g.TempInputId != 0 && g.ActiveId != g.TempInputId) - g.TempInputId = 0; - if (g.ActiveId == 0) - { - g.ActiveIdUsingNavDirMask = 0x00; - g.ActiveIdUsingAllKeyboardKeys = false; -#ifndef IMGUI_DISABLE_OBSOLETE_KEYIO - g.ActiveIdUsingNavInputMask = 0x00; -#endif - } - -#ifndef IMGUI_DISABLE_OBSOLETE_KEYIO - if (g.ActiveId == 0) - g.ActiveIdUsingNavInputMask = 0; - else if (g.ActiveIdUsingNavInputMask != 0) - { - // If your custom widget code used: { g.ActiveIdUsingNavInputMask |= (1 << ImGuiNavInput_Cancel); } - // Since IMGUI_VERSION_NUM >= 18804 it should be: { SetKeyOwner(ImGuiKey_Escape, g.ActiveId); SetKeyOwner(ImGuiKey_NavGamepadCancel, g.ActiveId); } - if (g.ActiveIdUsingNavInputMask & (1 << ImGuiNavInput_Cancel)) - SetKeyOwner(ImGuiKey_Escape, g.ActiveId); - if (g.ActiveIdUsingNavInputMask & ~(1 << ImGuiNavInput_Cancel)) - IM_ASSERT(0); // Other values unsupported - } -#endif - - // Record when we have been stationary as this state is preserved while over same item. - // FIXME: The way this is expressed means user cannot alter HoverStationaryDelay during the frame to use varying values. - // To allow this we should store HoverItemMaxStationaryTime+ID and perform the >= check in IsItemHovered() function. - if (g.HoverItemDelayId != 0 && g.MouseStationaryTimer >= g.Style.HoverStationaryDelay) - g.HoverItemUnlockedStationaryId = g.HoverItemDelayId; - else if (g.HoverItemDelayId == 0) - g.HoverItemUnlockedStationaryId = 0; - if (g.HoveredWindow != NULL && g.MouseStationaryTimer >= g.Style.HoverStationaryDelay) - g.HoverWindowUnlockedStationaryId = g.HoveredWindow->ID; - else if (g.HoveredWindow == NULL) - g.HoverWindowUnlockedStationaryId = 0; - - // Update hover delay for IsItemHovered() with delays and tooltips - g.HoverItemDelayIdPreviousFrame = g.HoverItemDelayId; - if (g.HoverItemDelayId != 0) - { - g.HoverItemDelayTimer += g.IO.DeltaTime; - g.HoverItemDelayClearTimer = 0.0f; - g.HoverItemDelayId = 0; - } - else if (g.HoverItemDelayTimer > 0.0f) - { - // This gives a little bit of leeway before clearing the hover timer, allowing mouse to cross gaps - // We could expose 0.25f as style.HoverClearDelay but I am not sure of the logic yet, this is particularly subtle. - g.HoverItemDelayClearTimer += g.IO.DeltaTime; - if (g.HoverItemDelayClearTimer >= ImMax(0.25f, g.IO.DeltaTime * 2.0f)) // ~7 frames at 30 Hz + allow for low framerate - g.HoverItemDelayTimer = g.HoverItemDelayClearTimer = 0.0f; // May want a decaying timer, in which case need to clamp at max first, based on max of caller last requested timer. - } - - // Drag and drop - g.DragDropAcceptIdPrev = g.DragDropAcceptIdCurr; - g.DragDropAcceptIdCurr = 0; - g.DragDropAcceptIdCurrRectSurface = FLT_MAX; - g.DragDropWithinSource = false; - g.DragDropWithinTarget = false; - g.DragDropHoldJustPressedId = 0; - - // Close popups on focus lost (currently wip/opt-in) - //if (g.IO.AppFocusLost) - // ClosePopupsExceptModals(); - - // Update keyboard input state - UpdateKeyboardInputs(); - - //IM_ASSERT(g.IO.KeyCtrl == IsKeyDown(ImGuiKey_LeftCtrl) || IsKeyDown(ImGuiKey_RightCtrl)); - //IM_ASSERT(g.IO.KeyShift == IsKeyDown(ImGuiKey_LeftShift) || IsKeyDown(ImGuiKey_RightShift)); - //IM_ASSERT(g.IO.KeyAlt == IsKeyDown(ImGuiKey_LeftAlt) || IsKeyDown(ImGuiKey_RightAlt)); - //IM_ASSERT(g.IO.KeySuper == IsKeyDown(ImGuiKey_LeftSuper) || IsKeyDown(ImGuiKey_RightSuper)); - - // Update gamepad/keyboard navigation - NavUpdate(); - - // Update mouse input state - UpdateMouseInputs(); - - // Undocking - // (needs to be before UpdateMouseMovingWindowNewFrame so the window is already offset and following the mouse on the detaching frame) - DockContextNewFrameUpdateUndocking(&g); - - // Find hovered window - // (needs to be before UpdateMouseMovingWindowNewFrame so we fill g.HoveredWindowUnderMovingWindow on the mouse release frame) - UpdateHoveredWindowAndCaptureFlags(); - - // Handle user moving window with mouse (at the beginning of the frame to avoid input lag or sheering) - UpdateMouseMovingWindowNewFrame(); - - // Background darkening/whitening - if (GetTopMostPopupModal() != NULL || (g.NavWindowingTarget != NULL && g.NavWindowingHighlightAlpha > 0.0f)) - g.DimBgRatio = ImMin(g.DimBgRatio + g.IO.DeltaTime * 6.0f, 1.0f); - else - g.DimBgRatio = ImMax(g.DimBgRatio - g.IO.DeltaTime * 10.0f, 0.0f); - - g.MouseCursor = ImGuiMouseCursor_Arrow; - g.WantCaptureMouseNextFrame = g.WantCaptureKeyboardNextFrame = g.WantTextInputNextFrame = -1; - - // Platform IME data: reset for the frame - g.PlatformImeDataPrev = g.PlatformImeData; - g.PlatformImeData.WantVisible = false; - - // Mouse wheel scrolling, scale - UpdateMouseWheel(); - - // Mark all windows as not visible and compact unused memory. - IM_ASSERT(g.WindowsFocusOrder.Size <= g.Windows.Size); - const float memory_compact_start_time = (g.GcCompactAll || g.IO.ConfigMemoryCompactTimer < 0.0f) ? FLT_MAX : (float)g.Time - g.IO.ConfigMemoryCompactTimer; - for (ImGuiWindow* window : g.Windows) - { - window->WasActive = window->Active; - window->Active = false; - window->WriteAccessed = false; - window->BeginCountPreviousFrame = window->BeginCount; - window->BeginCount = 0; - - // Garbage collect transient buffers of recently unused windows - if (!window->WasActive && !window->MemoryCompacted && window->LastTimeActive < memory_compact_start_time) - GcCompactTransientWindowBuffers(window); - } - - // Garbage collect transient buffers of recently unused tables - for (int i = 0; i < g.TablesLastTimeActive.Size; i++) - if (g.TablesLastTimeActive[i] >= 0.0f && g.TablesLastTimeActive[i] < memory_compact_start_time) - TableGcCompactTransientBuffers(g.Tables.GetByIndex(i)); - for (ImGuiTableTempData& table_temp_data : g.TablesTempData) - if (table_temp_data.LastTimeActive >= 0.0f && table_temp_data.LastTimeActive < memory_compact_start_time) - TableGcCompactTransientBuffers(&table_temp_data); - if (g.GcCompactAll) - GcCompactTransientMiscBuffers(); - g.GcCompactAll = false; - - // Closing the focused window restore focus to the first active root window in descending z-order - if (g.NavWindow && !g.NavWindow->WasActive) - FocusTopMostWindowUnderOne(NULL, NULL, NULL, ImGuiFocusRequestFlags_RestoreFocusedChild); - - // No window should be open at the beginning of the frame. - // But in order to allow the user to call NewFrame() multiple times without calling Render(), we are doing an explicit clear. - g.CurrentWindowStack.resize(0); - g.BeginPopupStack.resize(0); - g.ItemFlagsStack.resize(0); - g.ItemFlagsStack.push_back(ImGuiItemFlags_None); - g.GroupStack.resize(0); - - // Docking - DockContextNewFrameUpdateDocking(&g); - - // [DEBUG] Update debug features - UpdateDebugToolItemPicker(); - UpdateDebugToolStackQueries(); - if (g.DebugLocateFrames > 0 && --g.DebugLocateFrames == 0) - g.DebugLocateId = 0; - if (g.DebugLogClipperAutoDisableFrames > 0 && --g.DebugLogClipperAutoDisableFrames == 0) - { - DebugLog("(Auto-disabled ImGuiDebugLogFlags_EventClipper to avoid spamming)\n"); - g.DebugLogFlags &= ~ImGuiDebugLogFlags_EventClipper; - } - - // Create implicit/fallback window - which we will only render it if the user has added something to it. - // We don't use "Debug" to avoid colliding with user trying to create a "Debug" window with custom flags. - // This fallback is particularly important as it prevents ImGui:: calls from crashing. - g.WithinFrameScopeWithImplicitWindow = true; - SetNextWindowSize(ImVec2(400, 400), ImGuiCond_FirstUseEver); - Begin("Debug##Default"); - IM_ASSERT(g.CurrentWindow->IsFallbackWindow == true); - - // [DEBUG] When io.ConfigDebugBeginReturnValue is set, we make Begin()/BeginChild() return false at different level of the window-stack, - // allowing to validate correct Begin/End behavior in user code. - if (g.IO.ConfigDebugBeginReturnValueLoop) - g.DebugBeginReturnValueCullDepth = (g.DebugBeginReturnValueCullDepth == -1) ? 0 : ((g.DebugBeginReturnValueCullDepth + ((g.FrameCount % 4) == 0 ? 1 : 0)) % 10); - else - g.DebugBeginReturnValueCullDepth = -1; - - CallContextHooks(&g, ImGuiContextHookType_NewFramePost); -} - -// FIXME: Add a more explicit sort order in the window structure. -static int IMGUI_CDECL ChildWindowComparer(const void* lhs, const void* rhs) -{ - const ImGuiWindow* const a = *(const ImGuiWindow* const *)lhs; - const ImGuiWindow* const b = *(const ImGuiWindow* const *)rhs; - if (int d = (a->Flags & ImGuiWindowFlags_Popup) - (b->Flags & ImGuiWindowFlags_Popup)) - return d; - if (int d = (a->Flags & ImGuiWindowFlags_Tooltip) - (b->Flags & ImGuiWindowFlags_Tooltip)) - return d; - return (a->BeginOrderWithinParent - b->BeginOrderWithinParent); -} - -static void AddWindowToSortBuffer(ImVector* out_sorted_windows, ImGuiWindow* window) -{ - out_sorted_windows->push_back(window); - if (window->Active) - { - int count = window->DC.ChildWindows.Size; - ImQsort(window->DC.ChildWindows.Data, (size_t)count, sizeof(ImGuiWindow*), ChildWindowComparer); - for (int i = 0; i < count; i++) - { - ImGuiWindow* child = window->DC.ChildWindows[i]; - if (child->Active) - AddWindowToSortBuffer(out_sorted_windows, child); - } - } -} - -static void AddWindowToDrawData(ImGuiWindow* window, int layer) -{ - ImGuiContext& g = *GImGui; - ImGuiViewportP* viewport = window->Viewport; - IM_ASSERT(viewport != NULL); - g.IO.MetricsRenderWindows++; - if (window->DrawList->_Splitter._Count > 1) - window->DrawList->ChannelsMerge(); // Merge if user forgot to merge back. Also required in Docking branch for ImGuiWindowFlags_DockNodeHost windows. - ImGui::AddDrawListToDrawDataEx(&viewport->DrawDataP, viewport->DrawDataBuilder.Layers[layer], window->DrawList); - for (ImGuiWindow* child : window->DC.ChildWindows) - if (IsWindowActiveAndVisible(child)) // Clipped children may have been marked not active - AddWindowToDrawData(child, layer); -} - -static inline int GetWindowDisplayLayer(ImGuiWindow* window) -{ - return (window->Flags & ImGuiWindowFlags_Tooltip) ? 1 : 0; -} - -// Layer is locked for the root window, however child windows may use a different viewport (e.g. extruding menu) -static inline void AddRootWindowToDrawData(ImGuiWindow* window) -{ - AddWindowToDrawData(window, GetWindowDisplayLayer(window)); -} - -static void FlattenDrawDataIntoSingleLayer(ImDrawDataBuilder* builder) -{ - int n = builder->Layers[0]->Size; - int full_size = n; - for (int i = 1; i < IM_ARRAYSIZE(builder->Layers); i++) - full_size += builder->Layers[i]->Size; - builder->Layers[0]->resize(full_size); - for (int layer_n = 1; layer_n < IM_ARRAYSIZE(builder->Layers); layer_n++) - { - ImVector* layer = builder->Layers[layer_n]; - if (layer->empty()) - continue; - memcpy(builder->Layers[0]->Data + n, layer->Data, layer->Size * sizeof(ImDrawList*)); - n += layer->Size; - layer->resize(0); - } -} - -static void InitViewportDrawData(ImGuiViewportP* viewport) -{ - ImGuiIO& io = ImGui::GetIO(); - ImDrawData* draw_data = &viewport->DrawDataP; - - viewport->DrawData = draw_data; // Make publicly accessible - viewport->DrawDataBuilder.Layers[0] = &draw_data->CmdLists; - viewport->DrawDataBuilder.Layers[1] = &viewport->DrawDataBuilder.LayerData1; - viewport->DrawDataBuilder.Layers[0]->resize(0); - viewport->DrawDataBuilder.Layers[1]->resize(0); - - // When minimized, we report draw_data->DisplaySize as zero to be consistent with non-viewport mode, - // and to allow applications/backends to easily skip rendering. - // FIXME: Note that we however do NOT attempt to report "zero drawlist / vertices" into the ImDrawData structure. - // This is because the work has been done already, and its wasted! We should fix that and add optimizations for - // it earlier in the pipeline, rather than pretend to hide the data at the end of the pipeline. - const bool is_minimized = (viewport->Flags & ImGuiViewportFlags_IsMinimized) != 0; - - draw_data->Valid = true; - draw_data->CmdListsCount = 0; - draw_data->TotalVtxCount = draw_data->TotalIdxCount = 0; - draw_data->DisplayPos = viewport->Pos; - draw_data->DisplaySize = is_minimized ? ImVec2(0.0f, 0.0f) : viewport->Size; - draw_data->FramebufferScale = io.DisplayFramebufferScale; // FIXME-VIEWPORT: This may vary on a per-monitor/viewport basis? - draw_data->OwnerViewport = viewport; -} - -// Push a clipping rectangle for both ImGui logic (hit-testing etc.) and low-level ImDrawList rendering. -// - When using this function it is sane to ensure that float are perfectly rounded to integer values, -// so that e.g. (int)(max.x-min.x) in user's render produce correct result. -// - If the code here changes, may need to update code of functions like NextColumn() and PushColumnClipRect(): -// some frequently called functions which to modify both channels and clipping simultaneously tend to use the -// more specialized SetWindowClipRectBeforeSetChannel() to avoid extraneous updates of underlying ImDrawCmds. -void ImGui::PushClipRect(const ImVec2& clip_rect_min, const ImVec2& clip_rect_max, bool intersect_with_current_clip_rect) -{ - ImGuiWindow* window = GetCurrentWindow(); - window->DrawList->PushClipRect(clip_rect_min, clip_rect_max, intersect_with_current_clip_rect); - window->ClipRect = window->DrawList->_ClipRectStack.back(); -} - -void ImGui::PopClipRect() -{ - ImGuiWindow* window = GetCurrentWindow(); - window->DrawList->PopClipRect(); - window->ClipRect = window->DrawList->_ClipRectStack.back(); -} - -static ImGuiWindow* FindFrontMostVisibleChildWindow(ImGuiWindow* window) -{ - for (int n = window->DC.ChildWindows.Size - 1; n >= 0; n--) - if (IsWindowActiveAndVisible(window->DC.ChildWindows[n])) - return FindFrontMostVisibleChildWindow(window->DC.ChildWindows[n]); - return window; -} - -static void ImGui::RenderDimmedBackgroundBehindWindow(ImGuiWindow* window, ImU32 col) -{ - if ((col & IM_COL32_A_MASK) == 0) - return; - - ImGuiViewportP* viewport = window->Viewport; - ImRect viewport_rect = viewport->GetMainRect(); - - // Draw behind window by moving the draw command at the FRONT of the draw list - { - // Draw list have been trimmed already, hence the explicit recreation of a draw command if missing. - // FIXME: This is creating complication, might be simpler if we could inject a drawlist in drawdata at a given position and not attempt to manipulate ImDrawCmd order. - ImDrawList* draw_list = window->RootWindowDockTree->DrawList; - draw_list->ChannelsMerge(); - if (draw_list->CmdBuffer.Size == 0) - draw_list->AddDrawCmd(); - draw_list->PushClipRect(viewport_rect.Min - ImVec2(1, 1), viewport_rect.Max + ImVec2(1, 1), false); // FIXME: Need to stricty ensure ImDrawCmd are not merged (ElemCount==6 checks below will verify that) - draw_list->AddRectFilled(viewport_rect.Min, viewport_rect.Max, col); - ImDrawCmd cmd = draw_list->CmdBuffer.back(); - IM_ASSERT(cmd.ElemCount == 6); - draw_list->CmdBuffer.pop_back(); - draw_list->CmdBuffer.push_front(cmd); - draw_list->AddDrawCmd(); // We need to create a command as CmdBuffer.back().IdxOffset won't be correct if we append to same command. - draw_list->PopClipRect(); - } - - // Draw over sibling docking nodes in a same docking tree - if (window->RootWindow->DockIsActive) - { - ImDrawList* draw_list = FindFrontMostVisibleChildWindow(window->RootWindowDockTree)->DrawList; - draw_list->ChannelsMerge(); - if (draw_list->CmdBuffer.Size == 0) - draw_list->AddDrawCmd(); - draw_list->PushClipRect(viewport_rect.Min, viewport_rect.Max, false); - RenderRectFilledWithHole(draw_list, window->RootWindowDockTree->Rect(), window->RootWindow->Rect(), col, 0.0f);// window->RootWindowDockTree->WindowRounding); - draw_list->PopClipRect(); - } -} - -ImGuiWindow* ImGui::FindBottomMostVisibleWindowWithinBeginStack(ImGuiWindow* parent_window) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* bottom_most_visible_window = parent_window; - for (int i = FindWindowDisplayIndex(parent_window); i >= 0; i--) - { - ImGuiWindow* window = g.Windows[i]; - if (window->Flags & ImGuiWindowFlags_ChildWindow) - continue; - if (!IsWindowWithinBeginStackOf(window, parent_window)) - break; - if (IsWindowActiveAndVisible(window) && GetWindowDisplayLayer(window) <= GetWindowDisplayLayer(parent_window)) - bottom_most_visible_window = window; - } - return bottom_most_visible_window; -} - -// Important: AddWindowToDrawData() has not been called yet, meaning DockNodeHost windows needs a DrawList->ChannelsMerge() before usage. -// We call ChannelsMerge() lazily here at it is faster that doing a full iteration of g.Windows[] prior to calling RenderDimmedBackgrounds(). -static void ImGui::RenderDimmedBackgrounds() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* modal_window = GetTopMostAndVisiblePopupModal(); - if (g.DimBgRatio <= 0.0f && g.NavWindowingHighlightAlpha <= 0.0f) - return; - const bool dim_bg_for_modal = (modal_window != NULL); - const bool dim_bg_for_window_list = (g.NavWindowingTargetAnim != NULL && g.NavWindowingTargetAnim->Active); - if (!dim_bg_for_modal && !dim_bg_for_window_list) - return; - - ImGuiViewport* viewports_already_dimmed[2] = { NULL, NULL }; - if (dim_bg_for_modal) - { - // Draw dimming behind modal or a begin stack child, whichever comes first in draw order. - ImGuiWindow* dim_behind_window = FindBottomMostVisibleWindowWithinBeginStack(modal_window); - RenderDimmedBackgroundBehindWindow(dim_behind_window, GetColorU32(ImGuiCol_ModalWindowDimBg, g.DimBgRatio)); - viewports_already_dimmed[0] = modal_window->Viewport; - } - else if (dim_bg_for_window_list) - { - // Draw dimming behind CTRL+Tab target window and behind CTRL+Tab UI window - RenderDimmedBackgroundBehindWindow(g.NavWindowingTargetAnim, GetColorU32(ImGuiCol_NavWindowingDimBg, g.DimBgRatio)); - if (g.NavWindowingListWindow != NULL && g.NavWindowingListWindow->Viewport && g.NavWindowingListWindow->Viewport != g.NavWindowingTargetAnim->Viewport) - RenderDimmedBackgroundBehindWindow(g.NavWindowingListWindow, GetColorU32(ImGuiCol_NavWindowingDimBg, g.DimBgRatio)); - viewports_already_dimmed[0] = g.NavWindowingTargetAnim->Viewport; - viewports_already_dimmed[1] = g.NavWindowingListWindow ? g.NavWindowingListWindow->Viewport : NULL; - - // Draw border around CTRL+Tab target window - ImGuiWindow* window = g.NavWindowingTargetAnim; - ImGuiViewport* viewport = window->Viewport; - float distance = g.FontSize; - ImRect bb = window->Rect(); - bb.Expand(distance); - if (bb.GetWidth() >= viewport->Size.x && bb.GetHeight() >= viewport->Size.y) - bb.Expand(-distance - 1.0f); // If a window fits the entire viewport, adjust its highlight inward - window->DrawList->ChannelsMerge(); - if (window->DrawList->CmdBuffer.Size == 0) - window->DrawList->AddDrawCmd(); - window->DrawList->PushClipRect(viewport->Pos, viewport->Pos + viewport->Size); - window->DrawList->AddRect(bb.Min, bb.Max, GetColorU32(ImGuiCol_NavWindowingHighlight, g.NavWindowingHighlightAlpha), window->WindowRounding, 0, 3.0f); - window->DrawList->PopClipRect(); - } - - // Draw dimming background on _other_ viewports than the ones our windows are in - for (ImGuiViewportP* viewport : g.Viewports) - { - if (viewport == viewports_already_dimmed[0] || viewport == viewports_already_dimmed[1]) - continue; - if (modal_window && viewport->Window && IsWindowAbove(viewport->Window, modal_window)) - continue; - ImDrawList* draw_list = GetForegroundDrawList(viewport); - const ImU32 dim_bg_col = GetColorU32(dim_bg_for_modal ? ImGuiCol_ModalWindowDimBg : ImGuiCol_NavWindowingDimBg, g.DimBgRatio); - draw_list->AddRectFilled(viewport->Pos, viewport->Pos + viewport->Size, dim_bg_col); - } -} - -// This is normally called by Render(). You may want to call it directly if you want to avoid calling Render() but the gain will be very minimal. -void ImGui::EndFrame() -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(g.Initialized); - - // Don't process EndFrame() multiple times. - if (g.FrameCountEnded == g.FrameCount) - return; - IM_ASSERT(g.WithinFrameScope && "Forgot to call ImGui::NewFrame()?"); - - CallContextHooks(&g, ImGuiContextHookType_EndFramePre); - - ErrorCheckEndFrameSanityChecks(); - - // Notify Platform/OS when our Input Method Editor cursor has moved (e.g. CJK inputs using Microsoft IME) - ImGuiPlatformImeData* ime_data = &g.PlatformImeData; - if (g.IO.SetPlatformImeDataFn && memcmp(ime_data, &g.PlatformImeDataPrev, sizeof(ImGuiPlatformImeData)) != 0) - { - ImGuiViewport* viewport = FindViewportByID(g.PlatformImeViewport); - IMGUI_DEBUG_LOG_IO("[io] Calling io.SetPlatformImeDataFn(): WantVisible: %d, InputPos (%.2f,%.2f)\n", ime_data->WantVisible, ime_data->InputPos.x, ime_data->InputPos.y); - if (viewport == NULL) - viewport = GetMainViewport(); -#ifndef IMGUI_DISABLE_OBSOLETE_FUNCTIONS - if (viewport->PlatformHandleRaw == NULL && g.IO.ImeWindowHandle != NULL) - { - viewport->PlatformHandleRaw = g.IO.ImeWindowHandle; - g.IO.SetPlatformImeDataFn(viewport, ime_data); - viewport->PlatformHandleRaw = NULL; - } - else -#endif - { - g.IO.SetPlatformImeDataFn(viewport, ime_data); - } - } - - // Hide implicit/fallback "Debug" window if it hasn't been used - g.WithinFrameScopeWithImplicitWindow = false; - if (g.CurrentWindow && !g.CurrentWindow->WriteAccessed) - g.CurrentWindow->Active = false; - End(); - - // Update navigation: CTRL+Tab, wrap-around requests - NavEndFrame(); - - // Update docking - DockContextEndFrame(&g); - - SetCurrentViewport(NULL, NULL); - - // Drag and Drop: Elapse payload (if delivered, or if source stops being submitted) - if (g.DragDropActive) - { - bool is_delivered = g.DragDropPayload.Delivery; - bool is_elapsed = (g.DragDropPayload.DataFrameCount + 1 < g.FrameCount) && ((g.DragDropSourceFlags & ImGuiDragDropFlags_SourceAutoExpirePayload) || !IsMouseDown(g.DragDropMouseButton)); - if (is_delivered || is_elapsed) - ClearDragDrop(); - } - - // Drag and Drop: Fallback for source tooltip. This is not ideal but better than nothing. - if (g.DragDropActive && g.DragDropSourceFrameCount < g.FrameCount && !(g.DragDropSourceFlags & ImGuiDragDropFlags_SourceNoPreviewTooltip)) - { - g.DragDropWithinSource = true; - SetTooltip("..."); - g.DragDropWithinSource = false; - } - - // End frame - g.WithinFrameScope = false; - g.FrameCountEnded = g.FrameCount; - - // Initiate moving window + handle left-click and right-click focus - UpdateMouseMovingWindowEndFrame(); - - // Update user-facing viewport list (g.Viewports -> g.PlatformIO.Viewports after filtering out some) - UpdateViewportsEndFrame(); - - // Sort the window list so that all child windows are after their parent - // We cannot do that on FocusWindow() because children may not exist yet - g.WindowsTempSortBuffer.resize(0); - g.WindowsTempSortBuffer.reserve(g.Windows.Size); - for (ImGuiWindow* window : g.Windows) - { - if (window->Active && (window->Flags & ImGuiWindowFlags_ChildWindow)) // if a child is active its parent will add it - continue; - AddWindowToSortBuffer(&g.WindowsTempSortBuffer, window); - } - - // This usually assert if there is a mismatch between the ImGuiWindowFlags_ChildWindow / ParentWindow values and DC.ChildWindows[] in parents, aka we've done something wrong. - IM_ASSERT(g.Windows.Size == g.WindowsTempSortBuffer.Size); - g.Windows.swap(g.WindowsTempSortBuffer); - g.IO.MetricsActiveWindows = g.WindowsActiveCount; - - // Unlock font atlas - g.IO.Fonts->Locked = false; - - // Clear Input data for next frame - g.IO.MousePosPrev = g.IO.MousePos; - g.IO.AppFocusLost = false; - g.IO.MouseWheel = g.IO.MouseWheelH = 0.0f; - g.IO.InputQueueCharacters.resize(0); - - CallContextHooks(&g, ImGuiContextHookType_EndFramePost); -} - -// Prepare the data for rendering so you can call GetDrawData() -// (As with anything within the ImGui:: namspace this doesn't touch your GPU or graphics API at all: -// it is the role of the ImGui_ImplXXXX_RenderDrawData() function provided by the renderer backend) -void ImGui::Render() -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(g.Initialized); - - if (g.FrameCountEnded != g.FrameCount) - EndFrame(); - if (g.FrameCountRendered == g.FrameCount) - return; - g.FrameCountRendered = g.FrameCount; - - g.IO.MetricsRenderWindows = 0; - CallContextHooks(&g, ImGuiContextHookType_RenderPre); - - // Add background ImDrawList (for each active viewport) - for (ImGuiViewportP* viewport : g.Viewports) - { - InitViewportDrawData(viewport); - if (viewport->BgFgDrawLists[0] != NULL) - AddDrawListToDrawDataEx(&viewport->DrawDataP, viewport->DrawDataBuilder.Layers[0], GetBackgroundDrawList(viewport)); - } - - // Draw modal/window whitening backgrounds - RenderDimmedBackgrounds(); - - // Add ImDrawList to render - ImGuiWindow* windows_to_render_top_most[2]; - windows_to_render_top_most[0] = (g.NavWindowingTarget && !(g.NavWindowingTarget->Flags & ImGuiWindowFlags_NoBringToFrontOnFocus)) ? g.NavWindowingTarget->RootWindowDockTree : NULL; - windows_to_render_top_most[1] = (g.NavWindowingTarget ? g.NavWindowingListWindow : NULL); - for (ImGuiWindow* window : g.Windows) - { - IM_MSVC_WARNING_SUPPRESS(6011); // Static Analysis false positive "warning C6011: Dereferencing NULL pointer 'window'" - if (IsWindowActiveAndVisible(window) && (window->Flags & ImGuiWindowFlags_ChildWindow) == 0 && window != windows_to_render_top_most[0] && window != windows_to_render_top_most[1]) - AddRootWindowToDrawData(window); - } - for (int n = 0; n < IM_ARRAYSIZE(windows_to_render_top_most); n++) - if (windows_to_render_top_most[n] && IsWindowActiveAndVisible(windows_to_render_top_most[n])) // NavWindowingTarget is always temporarily displayed as the top-most window - AddRootWindowToDrawData(windows_to_render_top_most[n]); - - // Draw software mouse cursor if requested by io.MouseDrawCursor flag - if (g.IO.MouseDrawCursor && g.MouseCursor != ImGuiMouseCursor_None) - RenderMouseCursor(g.IO.MousePos, g.Style.MouseCursorScale, g.MouseCursor, IM_COL32_WHITE, IM_COL32_BLACK, IM_COL32(0, 0, 0, 48)); - - // Setup ImDrawData structures for end-user - g.IO.MetricsRenderVertices = g.IO.MetricsRenderIndices = 0; - for (ImGuiViewportP* viewport : g.Viewports) - { - FlattenDrawDataIntoSingleLayer(&viewport->DrawDataBuilder); - - // Add foreground ImDrawList (for each active viewport) - if (viewport->BgFgDrawLists[1] != NULL) - AddDrawListToDrawDataEx(&viewport->DrawDataP, viewport->DrawDataBuilder.Layers[0], GetForegroundDrawList(viewport)); - - // We call _PopUnusedDrawCmd() last thing, as RenderDimmedBackgrounds() rely on a valid command being there (especially in docking branch). - ImDrawData* draw_data = &viewport->DrawDataP; - IM_ASSERT(draw_data->CmdLists.Size == draw_data->CmdListsCount); - for (ImDrawList* draw_list : draw_data->CmdLists) - draw_list->_PopUnusedDrawCmd(); - - g.IO.MetricsRenderVertices += draw_data->TotalVtxCount; - g.IO.MetricsRenderIndices += draw_data->TotalIdxCount; - } - - CallContextHooks(&g, ImGuiContextHookType_RenderPost); -} - -// Calculate text size. Text can be multi-line. Optionally ignore text after a ## marker. -// CalcTextSize("") should return ImVec2(0.0f, g.FontSize) -ImVec2 ImGui::CalcTextSize(const char* text, const char* text_end, bool hide_text_after_double_hash, float wrap_width) -{ - ImGuiContext& g = *GImGui; - - const char* text_display_end; - if (hide_text_after_double_hash) - text_display_end = FindRenderedTextEnd(text, text_end); // Hide anything after a '##' string - else - text_display_end = text_end; - - ImFont* font = g.Font; - const float font_size = g.FontSize; - if (text == text_display_end) - return ImVec2(0.0f, font_size); - ImVec2 text_size = font->CalcTextSizeA(font_size, FLT_MAX, wrap_width, text, text_display_end, NULL); - - // Round - // FIXME: This has been here since Dec 2015 (7b0bf230) but down the line we want this out. - // FIXME: Investigate using ceilf or e.g. - // - https://git.musl-libc.org/cgit/musl/tree/src/math/ceilf.c - // - https://embarkstudios.github.io/rust-gpu/api/src/libm/math/ceilf.rs.html - text_size.x = IM_TRUNC(text_size.x + 0.99999f); - - return text_size; -} - -// Find window given position, search front-to-back -// FIXME: Note that we have an inconsequential lag here: OuterRectClipped is updated in Begin(), so windows moved programmatically -// with SetWindowPos() and not SetNextWindowPos() will have that rectangle lagging by a frame at the time FindHoveredWindow() is -// called, aka before the next Begin(). Moving window isn't affected. -static void FindHoveredWindow() -{ - ImGuiContext& g = *GImGui; - - // Special handling for the window being moved: Ignore the mouse viewport check (because it may reset/lose its viewport during the undocking frame) - ImGuiViewportP* moving_window_viewport = g.MovingWindow ? g.MovingWindow->Viewport : NULL; - if (g.MovingWindow) - g.MovingWindow->Viewport = g.MouseViewport; - - ImGuiWindow* hovered_window = NULL; - ImGuiWindow* hovered_window_ignoring_moving_window = NULL; - if (g.MovingWindow && !(g.MovingWindow->Flags & ImGuiWindowFlags_NoMouseInputs)) - hovered_window = g.MovingWindow; - - ImVec2 padding_regular = g.Style.TouchExtraPadding; - ImVec2 padding_for_resize = g.IO.ConfigWindowsResizeFromEdges ? g.WindowsHoverPadding : padding_regular; - for (int i = g.Windows.Size - 1; i >= 0; i--) - { - ImGuiWindow* window = g.Windows[i]; - IM_MSVC_WARNING_SUPPRESS(28182); // [Static Analyzer] Dereferencing NULL pointer. - if (!window->Active || window->Hidden) - continue; - if (window->Flags & ImGuiWindowFlags_NoMouseInputs) - continue; - IM_ASSERT(window->Viewport); - if (window->Viewport != g.MouseViewport) - continue; - - // Using the clipped AABB, a child window will typically be clipped by its parent (not always) - ImVec2 hit_padding = (window->Flags & (ImGuiWindowFlags_ChildWindow | ImGuiWindowFlags_NoResize | ImGuiWindowFlags_AlwaysAutoResize)) ? padding_regular : padding_for_resize; - if (!window->OuterRectClipped.ContainsWithPad(g.IO.MousePos, hit_padding)) - continue; - - // Support for one rectangular hole in any given window - // FIXME: Consider generalizing hit-testing override (with more generic data, callback, etc.) (#1512) - if (window->HitTestHoleSize.x != 0) - { - ImVec2 hole_pos(window->Pos.x + (float)window->HitTestHoleOffset.x, window->Pos.y + (float)window->HitTestHoleOffset.y); - ImVec2 hole_size((float)window->HitTestHoleSize.x, (float)window->HitTestHoleSize.y); - if (ImRect(hole_pos, hole_pos + hole_size).Contains(g.IO.MousePos)) - continue; - } - - if (hovered_window == NULL) - hovered_window = window; - IM_MSVC_WARNING_SUPPRESS(28182); // [Static Analyzer] Dereferencing NULL pointer. - if (hovered_window_ignoring_moving_window == NULL && (!g.MovingWindow || window->RootWindowDockTree != g.MovingWindow->RootWindowDockTree)) - hovered_window_ignoring_moving_window = window; - if (hovered_window && hovered_window_ignoring_moving_window) - break; - } - - g.HoveredWindow = hovered_window; - g.HoveredWindowUnderMovingWindow = hovered_window_ignoring_moving_window; - - if (g.MovingWindow) - g.MovingWindow->Viewport = moving_window_viewport; -} - -bool ImGui::IsItemActive() -{ - ImGuiContext& g = *GImGui; - if (g.ActiveId) - return g.ActiveId == g.LastItemData.ID; - return false; -} - -bool ImGui::IsItemActivated() -{ - ImGuiContext& g = *GImGui; - if (g.ActiveId) - if (g.ActiveId == g.LastItemData.ID && g.ActiveIdPreviousFrame != g.LastItemData.ID) - return true; - return false; -} - -bool ImGui::IsItemDeactivated() -{ - ImGuiContext& g = *GImGui; - if (g.LastItemData.StatusFlags & ImGuiItemStatusFlags_HasDeactivated) - return (g.LastItemData.StatusFlags & ImGuiItemStatusFlags_Deactivated) != 0; - return (g.ActiveIdPreviousFrame == g.LastItemData.ID && g.ActiveIdPreviousFrame != 0 && g.ActiveId != g.LastItemData.ID); -} - -bool ImGui::IsItemDeactivatedAfterEdit() -{ - ImGuiContext& g = *GImGui; - return IsItemDeactivated() && (g.ActiveIdPreviousFrameHasBeenEditedBefore || (g.ActiveId == 0 && g.ActiveIdHasBeenEditedBefore)); -} - -// == GetItemID() == GetFocusID() -bool ImGui::IsItemFocused() -{ - ImGuiContext& g = *GImGui; - if (g.NavId != g.LastItemData.ID || g.NavId == 0) - return false; - - // Special handling for the dummy item after Begin() which represent the title bar or tab. - // When the window is collapsed (SkipItems==true) that last item will never be overwritten so we need to detect the case. - ImGuiWindow* window = g.CurrentWindow; - if (g.LastItemData.ID == window->ID && window->WriteAccessed) - return false; - - return true; -} - -// Important: this can be useful but it is NOT equivalent to the behavior of e.g.Button()! -// Most widgets have specific reactions based on mouse-up/down state, mouse position etc. -bool ImGui::IsItemClicked(ImGuiMouseButton mouse_button) -{ - return IsMouseClicked(mouse_button) && IsItemHovered(ImGuiHoveredFlags_None); -} - -bool ImGui::IsItemToggledOpen() -{ - ImGuiContext& g = *GImGui; - return (g.LastItemData.StatusFlags & ImGuiItemStatusFlags_ToggledOpen) ? true : false; -} - -bool ImGui::IsItemToggledSelection() -{ - ImGuiContext& g = *GImGui; - return (g.LastItemData.StatusFlags & ImGuiItemStatusFlags_ToggledSelection) ? true : false; -} - -bool ImGui::IsAnyItemHovered() -{ - ImGuiContext& g = *GImGui; - return g.HoveredId != 0 || g.HoveredIdPreviousFrame != 0; -} - -bool ImGui::IsAnyItemActive() -{ - ImGuiContext& g = *GImGui; - return g.ActiveId != 0; -} - -bool ImGui::IsAnyItemFocused() -{ - ImGuiContext& g = *GImGui; - return g.NavId != 0 && !g.NavDisableHighlight; -} - -bool ImGui::IsItemVisible() -{ - ImGuiContext& g = *GImGui; - return (g.LastItemData.StatusFlags & ImGuiItemStatusFlags_Visible) != 0; -} - -bool ImGui::IsItemEdited() -{ - ImGuiContext& g = *GImGui; - return (g.LastItemData.StatusFlags & ImGuiItemStatusFlags_Edited) != 0; -} - -// Allow next item to be overlapped by subsequent items. -// This works by requiring HoveredId to match for two subsequent frames, -// so if a following items overwrite it our interactions will naturally be disabled. -void ImGui::SetNextItemAllowOverlap() -{ - ImGuiContext& g = *GImGui; - g.NextItemData.ItemFlags |= ImGuiItemFlags_AllowOverlap; -} - -#ifndef IMGUI_DISABLE_OBSOLETE_FUNCTIONS -// Allow last item to be overlapped by a subsequent item. Both may be activated during the same frame before the later one takes priority. -// FIXME-LEGACY: Use SetNextItemAllowOverlap() *before* your item instead. -void ImGui::SetItemAllowOverlap() -{ - ImGuiContext& g = *GImGui; - ImGuiID id = g.LastItemData.ID; - if (g.HoveredId == id) - g.HoveredIdAllowOverlap = true; - if (g.ActiveId == id) // Before we made this obsolete, most calls to SetItemAllowOverlap() used to avoid this path by testing g.ActiveId != id. - g.ActiveIdAllowOverlap = true; -} -#endif - -// FIXME: It might be undesirable that this will likely disable KeyOwner-aware shortcuts systems. Consider a more fine-tuned version for the two users of this function. -void ImGui::SetActiveIdUsingAllKeyboardKeys() -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(g.ActiveId != 0); - g.ActiveIdUsingNavDirMask = (1 << ImGuiDir_COUNT) - 1; - g.ActiveIdUsingAllKeyboardKeys = true; - NavMoveRequestCancel(); -} - -ImGuiID ImGui::GetItemID() -{ - ImGuiContext& g = *GImGui; - return g.LastItemData.ID; -} - -ImVec2 ImGui::GetItemRectMin() -{ - ImGuiContext& g = *GImGui; - return g.LastItemData.Rect.Min; -} - -ImVec2 ImGui::GetItemRectMax() -{ - ImGuiContext& g = *GImGui; - return g.LastItemData.Rect.Max; -} - -ImVec2 ImGui::GetItemRectSize() -{ - ImGuiContext& g = *GImGui; - return g.LastItemData.Rect.GetSize(); -} - -bool ImGui::BeginChildEx(const char* name, ImGuiID id, const ImVec2& size_arg, bool border, ImGuiWindowFlags flags) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* parent_window = g.CurrentWindow; - - flags |= ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_NoResize | ImGuiWindowFlags_NoSavedSettings | ImGuiWindowFlags_ChildWindow | ImGuiWindowFlags_NoDocking; - flags |= (parent_window->Flags & ImGuiWindowFlags_NoMove); // Inherit the NoMove flag - - // Size - const ImVec2 content_avail = GetContentRegionAvail(); - ImVec2 size = ImTrunc(size_arg); - const int auto_fit_axises = ((size.x == 0.0f) ? (1 << ImGuiAxis_X) : 0x00) | ((size.y == 0.0f) ? (1 << ImGuiAxis_Y) : 0x00); - if (size.x <= 0.0f) - size.x = ImMax(content_avail.x + size.x, 4.0f); // Arbitrary minimum child size (0.0f causing too many issues) - if (size.y <= 0.0f) - size.y = ImMax(content_avail.y + size.y, 4.0f); - SetNextWindowSize(size); - - // Build up name. If you need to append to a same child from multiple location in the ID stack, use BeginChild(ImGuiID id) with a stable value. - const char* temp_window_name; - if (name) - ImFormatStringToTempBuffer(&temp_window_name, NULL, "%s/%s_%08X", parent_window->Name, name, id); - else - ImFormatStringToTempBuffer(&temp_window_name, NULL, "%s/%08X", parent_window->Name, id); - - const float backup_border_size = g.Style.ChildBorderSize; - if (!border) - g.Style.ChildBorderSize = 0.0f; - bool ret = Begin(temp_window_name, NULL, flags); - g.Style.ChildBorderSize = backup_border_size; - - ImGuiWindow* child_window = g.CurrentWindow; - child_window->ChildId = id; - child_window->AutoFitChildAxises = (ImS8)auto_fit_axises; - - // Set the cursor to handle case where the user called SetNextWindowPos()+BeginChild() manually. - // While this is not really documented/defined, it seems that the expected thing to do. - if (child_window->BeginCount == 1) - parent_window->DC.CursorPos = child_window->Pos; - - // Process navigation-in immediately so NavInit can run on first frame - // Can enter a child if (A) it has navigatable items or (B) it can be scrolled. - const ImGuiID temp_id_for_activation = ImHashStr("##Child", 0, id); - if (g.ActiveId == temp_id_for_activation) - ClearActiveID(); - if (g.NavActivateId == id && !(flags & ImGuiWindowFlags_NavFlattened) && (child_window->DC.NavLayersActiveMask != 0 || child_window->DC.NavWindowHasScrollY)) - { - FocusWindow(child_window); - NavInitWindow(child_window, false); - SetActiveID(temp_id_for_activation, child_window); // Steal ActiveId with another arbitrary id so that key-press won't activate child item - g.ActiveIdSource = g.NavInputSource; - } - return ret; -} - -bool ImGui::BeginChild(const char* str_id, const ImVec2& size_arg, bool border, ImGuiWindowFlags extra_flags) -{ - ImGuiWindow* window = GetCurrentWindow(); - return BeginChildEx(str_id, window->GetID(str_id), size_arg, border, extra_flags); -} - -bool ImGui::BeginChild(ImGuiID id, const ImVec2& size_arg, bool border, ImGuiWindowFlags extra_flags) -{ - IM_ASSERT(id != 0); - return BeginChildEx(NULL, id, size_arg, border, extra_flags); -} - -void ImGui::EndChild() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - - IM_ASSERT(g.WithinEndChild == false); - IM_ASSERT(window->Flags & ImGuiWindowFlags_ChildWindow); // Mismatched BeginChild()/EndChild() calls - - g.WithinEndChild = true; - if (window->BeginCount > 1) - { - End(); - } - else - { - ImVec2 sz = window->Size; - if (window->AutoFitChildAxises & (1 << ImGuiAxis_X)) // Arbitrary minimum zero-ish child size of 4.0f causes less trouble than a 0.0f - sz.x = ImMax(4.0f, sz.x); - if (window->AutoFitChildAxises & (1 << ImGuiAxis_Y)) - sz.y = ImMax(4.0f, sz.y); - End(); - - ImGuiWindow* parent_window = g.CurrentWindow; - ImRect bb(parent_window->DC.CursorPos, parent_window->DC.CursorPos + sz); - ItemSize(sz); - if ((window->DC.NavLayersActiveMask != 0 || window->DC.NavWindowHasScrollY) && !(window->Flags & ImGuiWindowFlags_NavFlattened)) - { - ItemAdd(bb, window->ChildId); - RenderNavHighlight(bb, window->ChildId); - - // When browsing a window that has no activable items (scroll only) we keep a highlight on the child (pass g.NavId to trick into always displaying) - if (window->DC.NavLayersActiveMask == 0 && window == g.NavWindow) - RenderNavHighlight(ImRect(bb.Min - ImVec2(2, 2), bb.Max + ImVec2(2, 2)), g.NavId, ImGuiNavHighlightFlags_TypeThin); - } - else - { - // Not navigable into - ItemAdd(bb, 0); - - // But when flattened we directly reach items, adjust active layer mask accordingly - if (window->Flags & ImGuiWindowFlags_NavFlattened) - parent_window->DC.NavLayersActiveMaskNext |= window->DC.NavLayersActiveMaskNext; - } - if (g.HoveredWindow == window) - g.LastItemData.StatusFlags |= ImGuiItemStatusFlags_HoveredWindow; - } - g.WithinEndChild = false; - g.LogLinePosY = -FLT_MAX; // To enforce a carriage return -} - -// Helper to create a child window / scrolling region that looks like a normal widget frame. -bool ImGui::BeginChildFrame(ImGuiID id, const ImVec2& size, ImGuiWindowFlags extra_flags) -{ - ImGuiContext& g = *GImGui; - const ImGuiStyle& style = g.Style; - PushStyleColor(ImGuiCol_ChildBg, style.Colors[ImGuiCol_FrameBg]); - PushStyleVar(ImGuiStyleVar_ChildRounding, style.FrameRounding); - PushStyleVar(ImGuiStyleVar_ChildBorderSize, style.FrameBorderSize); - PushStyleVar(ImGuiStyleVar_WindowPadding, style.FramePadding); - bool ret = BeginChild(id, size, true, ImGuiWindowFlags_NoMove | ImGuiWindowFlags_AlwaysUseWindowPadding | extra_flags); - PopStyleVar(3); - PopStyleColor(); - return ret; -} - -void ImGui::EndChildFrame() -{ - EndChild(); -} - -static void SetWindowConditionAllowFlags(ImGuiWindow* window, ImGuiCond flags, bool enabled) -{ - window->SetWindowPosAllowFlags = enabled ? (window->SetWindowPosAllowFlags | flags) : (window->SetWindowPosAllowFlags & ~flags); - window->SetWindowSizeAllowFlags = enabled ? (window->SetWindowSizeAllowFlags | flags) : (window->SetWindowSizeAllowFlags & ~flags); - window->SetWindowCollapsedAllowFlags = enabled ? (window->SetWindowCollapsedAllowFlags | flags) : (window->SetWindowCollapsedAllowFlags & ~flags); - window->SetWindowDockAllowFlags = enabled ? (window->SetWindowDockAllowFlags | flags) : (window->SetWindowDockAllowFlags & ~flags); -} - -ImGuiWindow* ImGui::FindWindowByID(ImGuiID id) -{ - ImGuiContext& g = *GImGui; - return (ImGuiWindow*)g.WindowsById.GetVoidPtr(id); -} - -ImGuiWindow* ImGui::FindWindowByName(const char* name) -{ - ImGuiID id = ImHashStr(name); - return FindWindowByID(id); -} - -static void ApplyWindowSettings(ImGuiWindow* window, ImGuiWindowSettings* settings) -{ - const ImGuiViewport* main_viewport = ImGui::GetMainViewport(); - window->ViewportPos = main_viewport->Pos; - if (settings->ViewportId) - { - window->ViewportId = settings->ViewportId; - window->ViewportPos = ImVec2(settings->ViewportPos.x, settings->ViewportPos.y); - } - window->Pos = ImTrunc(ImVec2(settings->Pos.x + window->ViewportPos.x, settings->Pos.y + window->ViewportPos.y)); - if (settings->Size.x > 0 && settings->Size.y > 0) - window->Size = window->SizeFull = ImTrunc(ImVec2(settings->Size.x, settings->Size.y)); - window->Collapsed = settings->Collapsed; - window->DockId = settings->DockId; - window->DockOrder = settings->DockOrder; -} - -static void UpdateWindowInFocusOrderList(ImGuiWindow* window, bool just_created, ImGuiWindowFlags new_flags) -{ - ImGuiContext& g = *GImGui; - - const bool new_is_explicit_child = (new_flags & ImGuiWindowFlags_ChildWindow) != 0 && ((new_flags & ImGuiWindowFlags_Popup) == 0 || (new_flags & ImGuiWindowFlags_ChildMenu) != 0); - const bool child_flag_changed = new_is_explicit_child != window->IsExplicitChild; - if ((just_created || child_flag_changed) && !new_is_explicit_child) - { - IM_ASSERT(!g.WindowsFocusOrder.contains(window)); - g.WindowsFocusOrder.push_back(window); - window->FocusOrder = (short)(g.WindowsFocusOrder.Size - 1); - } - else if (!just_created && child_flag_changed && new_is_explicit_child) - { - IM_ASSERT(g.WindowsFocusOrder[window->FocusOrder] == window); - for (int n = window->FocusOrder + 1; n < g.WindowsFocusOrder.Size; n++) - g.WindowsFocusOrder[n]->FocusOrder--; - g.WindowsFocusOrder.erase(g.WindowsFocusOrder.Data + window->FocusOrder); - window->FocusOrder = -1; - } - window->IsExplicitChild = new_is_explicit_child; -} - -static void InitOrLoadWindowSettings(ImGuiWindow* window, ImGuiWindowSettings* settings) -{ - // Initial window state with e.g. default/arbitrary window position - // Use SetNextWindowPos() with the appropriate condition flag to change the initial position of a window. - const ImGuiViewport* main_viewport = ImGui::GetMainViewport(); - window->Pos = main_viewport->Pos + ImVec2(60, 60); - window->Size = window->SizeFull = ImVec2(0, 0); - window->ViewportPos = main_viewport->Pos; - window->SetWindowPosAllowFlags = window->SetWindowSizeAllowFlags = window->SetWindowCollapsedAllowFlags = window->SetWindowDockAllowFlags = ImGuiCond_Always | ImGuiCond_Once | ImGuiCond_FirstUseEver | ImGuiCond_Appearing; - - if (settings != NULL) - { - SetWindowConditionAllowFlags(window, ImGuiCond_FirstUseEver, false); - ApplyWindowSettings(window, settings); - } - window->DC.CursorStartPos = window->DC.CursorMaxPos = window->DC.IdealMaxPos = window->Pos; // So first call to CalcWindowContentSizes() doesn't return crazy values - - if ((window->Flags & ImGuiWindowFlags_AlwaysAutoResize) != 0) - { - window->AutoFitFramesX = window->AutoFitFramesY = 2; - window->AutoFitOnlyGrows = false; - } - else - { - if (window->Size.x <= 0.0f) - window->AutoFitFramesX = 2; - if (window->Size.y <= 0.0f) - window->AutoFitFramesY = 2; - window->AutoFitOnlyGrows = (window->AutoFitFramesX > 0) || (window->AutoFitFramesY > 0); - } -} - -static ImGuiWindow* CreateNewWindow(const char* name, ImGuiWindowFlags flags) -{ - // Create window the first time - //IMGUI_DEBUG_LOG("CreateNewWindow '%s', flags = 0x%08X\n", name, flags); - ImGuiContext& g = *GImGui; - ImGuiWindow* window = IM_NEW(ImGuiWindow)(&g, name); - window->Flags = flags; - g.WindowsById.SetVoidPtr(window->ID, window); - - ImGuiWindowSettings* settings = NULL; - if (!(flags & ImGuiWindowFlags_NoSavedSettings)) - if ((settings = ImGui::FindWindowSettingsByWindow(window)) != 0) - window->SettingsOffset = g.SettingsWindows.offset_from_ptr(settings); - - InitOrLoadWindowSettings(window, settings); - - if (flags & ImGuiWindowFlags_NoBringToFrontOnFocus) - g.Windows.push_front(window); // Quite slow but rare and only once - else - g.Windows.push_back(window); - - return window; -} - -static ImGuiWindow* GetWindowForTitleDisplay(ImGuiWindow* window) -{ - return window->DockNodeAsHost ? window->DockNodeAsHost->VisibleWindow : window; -} - -static ImGuiWindow* GetWindowForTitleAndMenuHeight(ImGuiWindow* window) -{ - return (window->DockNodeAsHost && window->DockNodeAsHost->VisibleWindow) ? window->DockNodeAsHost->VisibleWindow : window; -} - -static ImVec2 CalcWindowSizeAfterConstraint(ImGuiWindow* window, const ImVec2& size_desired) -{ - ImGuiContext& g = *GImGui; - ImVec2 new_size = size_desired; - if (g.NextWindowData.Flags & ImGuiNextWindowDataFlags_HasSizeConstraint) - { - // Using -1,-1 on either X/Y axis to preserve the current size. - ImRect cr = g.NextWindowData.SizeConstraintRect; - new_size.x = (cr.Min.x >= 0 && cr.Max.x >= 0) ? ImClamp(new_size.x, cr.Min.x, cr.Max.x) : window->SizeFull.x; - new_size.y = (cr.Min.y >= 0 && cr.Max.y >= 0) ? ImClamp(new_size.y, cr.Min.y, cr.Max.y) : window->SizeFull.y; - if (g.NextWindowData.SizeCallback) - { - ImGuiSizeCallbackData data; - data.UserData = g.NextWindowData.SizeCallbackUserData; - data.Pos = window->Pos; - data.CurrentSize = window->SizeFull; - data.DesiredSize = new_size; - g.NextWindowData.SizeCallback(&data); - new_size = data.DesiredSize; - } - new_size.x = IM_TRUNC(new_size.x); - new_size.y = IM_TRUNC(new_size.y); - } - - // Minimum size - if (!(window->Flags & (ImGuiWindowFlags_ChildWindow | ImGuiWindowFlags_AlwaysAutoResize))) - { - ImGuiWindow* window_for_height = GetWindowForTitleAndMenuHeight(window); - new_size = ImMax(new_size, g.Style.WindowMinSize); - const float minimum_height = window_for_height->TitleBarHeight() + window_for_height->MenuBarHeight() + ImMax(0.0f, g.Style.WindowRounding - 1.0f); - new_size.y = ImMax(new_size.y, minimum_height); // Reduce artifacts with very small windows - } - return new_size; -} - -static void CalcWindowContentSizes(ImGuiWindow* window, ImVec2* content_size_current, ImVec2* content_size_ideal) -{ - bool preserve_old_content_sizes = false; - if (window->Collapsed && window->AutoFitFramesX <= 0 && window->AutoFitFramesY <= 0) - preserve_old_content_sizes = true; - else if (window->Hidden && window->HiddenFramesCannotSkipItems == 0 && window->HiddenFramesCanSkipItems > 0) - preserve_old_content_sizes = true; - if (preserve_old_content_sizes) - { - *content_size_current = window->ContentSize; - *content_size_ideal = window->ContentSizeIdeal; - return; - } - - content_size_current->x = (window->ContentSizeExplicit.x != 0.0f) ? window->ContentSizeExplicit.x : IM_TRUNC(window->DC.CursorMaxPos.x - window->DC.CursorStartPos.x); - content_size_current->y = (window->ContentSizeExplicit.y != 0.0f) ? window->ContentSizeExplicit.y : IM_TRUNC(window->DC.CursorMaxPos.y - window->DC.CursorStartPos.y); - content_size_ideal->x = (window->ContentSizeExplicit.x != 0.0f) ? window->ContentSizeExplicit.x : IM_TRUNC(ImMax(window->DC.CursorMaxPos.x, window->DC.IdealMaxPos.x) - window->DC.CursorStartPos.x); - content_size_ideal->y = (window->ContentSizeExplicit.y != 0.0f) ? window->ContentSizeExplicit.y : IM_TRUNC(ImMax(window->DC.CursorMaxPos.y, window->DC.IdealMaxPos.y) - window->DC.CursorStartPos.y); -} - -static ImVec2 CalcWindowAutoFitSize(ImGuiWindow* window, const ImVec2& size_contents) -{ - ImGuiContext& g = *GImGui; - ImGuiStyle& style = g.Style; - const float decoration_w_without_scrollbars = window->DecoOuterSizeX1 + window->DecoOuterSizeX2 - window->ScrollbarSizes.x; - const float decoration_h_without_scrollbars = window->DecoOuterSizeY1 + window->DecoOuterSizeY2 - window->ScrollbarSizes.y; - ImVec2 size_pad = window->WindowPadding * 2.0f; - ImVec2 size_desired = size_contents + size_pad + ImVec2(decoration_w_without_scrollbars, decoration_h_without_scrollbars); - if (window->Flags & ImGuiWindowFlags_Tooltip) - { - // Tooltip always resize - return size_desired; - } - else - { - // Maximum window size is determined by the viewport size or monitor size - const bool is_popup = (window->Flags & ImGuiWindowFlags_Popup) != 0; - const bool is_menu = (window->Flags & ImGuiWindowFlags_ChildMenu) != 0; - ImVec2 size_min = style.WindowMinSize; - if (is_popup || is_menu) // Popups and menus bypass style.WindowMinSize by default, but we give then a non-zero minimum size to facilitate understanding problematic cases (e.g. empty popups) - size_min = ImMin(size_min, ImVec2(4.0f, 4.0f)); - - ImVec2 avail_size = window->Viewport->WorkSize; - if (window->ViewportOwned) - avail_size = ImVec2(FLT_MAX, FLT_MAX); - const int monitor_idx = window->ViewportAllowPlatformMonitorExtend; - if (monitor_idx >= 0 && monitor_idx < g.PlatformIO.Monitors.Size) - avail_size = g.PlatformIO.Monitors[monitor_idx].WorkSize; - ImVec2 size_auto_fit = ImClamp(size_desired, size_min, ImMax(size_min, avail_size - style.DisplaySafeAreaPadding * 2.0f)); - - // When the window cannot fit all contents (either because of constraints, either because screen is too small), - // we are growing the size on the other axis to compensate for expected scrollbar. FIXME: Might turn bigger than ViewportSize-WindowPadding. - ImVec2 size_auto_fit_after_constraint = CalcWindowSizeAfterConstraint(window, size_auto_fit); - bool will_have_scrollbar_x = (size_auto_fit_after_constraint.x - size_pad.x - decoration_w_without_scrollbars < size_contents.x && !(window->Flags & ImGuiWindowFlags_NoScrollbar) && (window->Flags & ImGuiWindowFlags_HorizontalScrollbar)) || (window->Flags & ImGuiWindowFlags_AlwaysHorizontalScrollbar); - bool will_have_scrollbar_y = (size_auto_fit_after_constraint.y - size_pad.y - decoration_h_without_scrollbars < size_contents.y && !(window->Flags & ImGuiWindowFlags_NoScrollbar)) || (window->Flags & ImGuiWindowFlags_AlwaysVerticalScrollbar); - if (will_have_scrollbar_x) - size_auto_fit.y += style.ScrollbarSize; - if (will_have_scrollbar_y) - size_auto_fit.x += style.ScrollbarSize; - return size_auto_fit; - } -} - -ImVec2 ImGui::CalcWindowNextAutoFitSize(ImGuiWindow* window) -{ - ImVec2 size_contents_current; - ImVec2 size_contents_ideal; - CalcWindowContentSizes(window, &size_contents_current, &size_contents_ideal); - ImVec2 size_auto_fit = CalcWindowAutoFitSize(window, size_contents_ideal); - ImVec2 size_final = CalcWindowSizeAfterConstraint(window, size_auto_fit); - return size_final; -} - -static ImGuiCol GetWindowBgColorIdx(ImGuiWindow* window) -{ - if (window->Flags & (ImGuiWindowFlags_Tooltip | ImGuiWindowFlags_Popup)) - return ImGuiCol_PopupBg; - if ((window->Flags & ImGuiWindowFlags_ChildWindow) && !window->DockIsActive) - return ImGuiCol_ChildBg; - return ImGuiCol_WindowBg; -} - -static void CalcResizePosSizeFromAnyCorner(ImGuiWindow* window, const ImVec2& corner_target, const ImVec2& corner_norm, ImVec2* out_pos, ImVec2* out_size) -{ - ImVec2 pos_min = ImLerp(corner_target, window->Pos, corner_norm); // Expected window upper-left - ImVec2 pos_max = ImLerp(window->Pos + window->Size, corner_target, corner_norm); // Expected window lower-right - ImVec2 size_expected = pos_max - pos_min; - ImVec2 size_constrained = CalcWindowSizeAfterConstraint(window, size_expected); - *out_pos = pos_min; - if (corner_norm.x == 0.0f) - out_pos->x -= (size_constrained.x - size_expected.x); - if (corner_norm.y == 0.0f) - out_pos->y -= (size_constrained.y - size_expected.y); - *out_size = size_constrained; -} - -// Data for resizing from corner -struct ImGuiResizeGripDef -{ - ImVec2 CornerPosN; - ImVec2 InnerDir; - int AngleMin12, AngleMax12; -}; -static const ImGuiResizeGripDef resize_grip_def[4] = -{ - { ImVec2(1, 1), ImVec2(-1, -1), 0, 3 }, // Lower-right - { ImVec2(0, 1), ImVec2(+1, -1), 3, 6 }, // Lower-left - { ImVec2(0, 0), ImVec2(+1, +1), 6, 9 }, // Upper-left (Unused) - { ImVec2(1, 0), ImVec2(-1, +1), 9, 12 } // Upper-right (Unused) -}; - -// Data for resizing from borders -struct ImGuiResizeBorderDef -{ - ImVec2 InnerDir; - ImVec2 SegmentN1, SegmentN2; - float OuterAngle; -}; -static const ImGuiResizeBorderDef resize_border_def[4] = -{ - { ImVec2(+1, 0), ImVec2(0, 1), ImVec2(0, 0), IM_PI * 1.00f }, // Left - { ImVec2(-1, 0), ImVec2(1, 0), ImVec2(1, 1), IM_PI * 0.00f }, // Right - { ImVec2(0, +1), ImVec2(0, 0), ImVec2(1, 0), IM_PI * 1.50f }, // Up - { ImVec2(0, -1), ImVec2(1, 1), ImVec2(0, 1), IM_PI * 0.50f } // Down -}; - -static ImRect GetResizeBorderRect(ImGuiWindow* window, int border_n, float perp_padding, float thickness) -{ - ImRect rect = window->Rect(); - if (thickness == 0.0f) - rect.Max -= ImVec2(1, 1); - if (border_n == ImGuiDir_Left) { return ImRect(rect.Min.x - thickness, rect.Min.y + perp_padding, rect.Min.x + thickness, rect.Max.y - perp_padding); } - if (border_n == ImGuiDir_Right) { return ImRect(rect.Max.x - thickness, rect.Min.y + perp_padding, rect.Max.x + thickness, rect.Max.y - perp_padding); } - if (border_n == ImGuiDir_Up) { return ImRect(rect.Min.x + perp_padding, rect.Min.y - thickness, rect.Max.x - perp_padding, rect.Min.y + thickness); } - if (border_n == ImGuiDir_Down) { return ImRect(rect.Min.x + perp_padding, rect.Max.y - thickness, rect.Max.x - perp_padding, rect.Max.y + thickness); } - IM_ASSERT(0); - return ImRect(); -} - -// 0..3: corners (Lower-right, Lower-left, Unused, Unused) -ImGuiID ImGui::GetWindowResizeCornerID(ImGuiWindow* window, int n) -{ - IM_ASSERT(n >= 0 && n < 4); - ImGuiID id = window->DockIsActive ? window->DockNode->HostWindow->ID : window->ID; - id = ImHashStr("#RESIZE", 0, id); - id = ImHashData(&n, sizeof(int), id); - return id; -} - -// Borders (Left, Right, Up, Down) -ImGuiID ImGui::GetWindowResizeBorderID(ImGuiWindow* window, ImGuiDir dir) -{ - IM_ASSERT(dir >= 0 && dir < 4); - int n = (int)dir + 4; - ImGuiID id = window->DockIsActive ? window->DockNode->HostWindow->ID : window->ID; - id = ImHashStr("#RESIZE", 0, id); - id = ImHashData(&n, sizeof(int), id); - return id; -} - -// Handle resize for: Resize Grips, Borders, Gamepad -// Return true when using auto-fit (double-click on resize grip) -static bool ImGui::UpdateWindowManualResize(ImGuiWindow* window, const ImVec2& size_auto_fit, int* border_held, int resize_grip_count, ImU32 resize_grip_col[4], const ImRect& visibility_rect) -{ - ImGuiContext& g = *GImGui; - ImGuiWindowFlags flags = window->Flags; - - if ((flags & ImGuiWindowFlags_NoResize) || (flags & ImGuiWindowFlags_AlwaysAutoResize) || window->AutoFitFramesX > 0 || window->AutoFitFramesY > 0) - return false; - if (window->WasActive == false) // Early out to avoid running this code for e.g. a hidden implicit/fallback Debug window. - return false; - - bool ret_auto_fit = false; - const int resize_border_count = g.IO.ConfigWindowsResizeFromEdges ? 4 : 0; - const float grip_draw_size = IM_TRUNC(ImMax(g.FontSize * 1.35f, window->WindowRounding + 1.0f + g.FontSize * 0.2f)); - const float grip_hover_inner_size = IM_TRUNC(grip_draw_size * 0.75f); - const float grip_hover_outer_size = g.IO.ConfigWindowsResizeFromEdges ? WINDOWS_HOVER_PADDING : 0.0f; - - ImRect clamp_rect = visibility_rect; - const bool window_move_from_title_bar = g.IO.ConfigWindowsMoveFromTitleBarOnly && !(window->Flags & ImGuiWindowFlags_NoTitleBar); - if (window_move_from_title_bar) - clamp_rect.Min.y -= window->TitleBarHeight(); - - ImVec2 pos_target(FLT_MAX, FLT_MAX); - ImVec2 size_target(FLT_MAX, FLT_MAX); - - // Clip mouse interaction rectangles within the viewport rectangle (in practice the narrowing is going to happen most of the time). - // - Not narrowing would mostly benefit the situation where OS windows _without_ decoration have a threshold for hovering when outside their limits. - // This is however not the case with current backends under Win32, but a custom borderless window implementation would benefit from it. - // - When decoration are enabled we typically benefit from that distance, but then our resize elements would be conflicting with OS resize elements, so we also narrow. - // - Note that we are unable to tell if the platform setup allows hovering with a distance threshold (on Win32, decorated window have such threshold). - // We only clip interaction so we overwrite window->ClipRect, cannot call PushClipRect() yet as DrawList is not yet setup. - const bool clip_with_viewport_rect = !(g.IO.BackendFlags & ImGuiBackendFlags_HasMouseHoveredViewport) || (g.IO.MouseHoveredViewport != window->ViewportId) || !(window->Viewport->Flags & ImGuiViewportFlags_NoDecoration); - if (clip_with_viewport_rect) - window->ClipRect = window->Viewport->GetMainRect(); - - // Resize grips and borders are on layer 1 - window->DC.NavLayerCurrent = ImGuiNavLayer_Menu; - - // Manual resize grips - PushID("#RESIZE"); - for (int resize_grip_n = 0; resize_grip_n < resize_grip_count; resize_grip_n++) - { - const ImGuiResizeGripDef& def = resize_grip_def[resize_grip_n]; - const ImVec2 corner = ImLerp(window->Pos, window->Pos + window->Size, def.CornerPosN); - - // Using the FlattenChilds button flag we make the resize button accessible even if we are hovering over a child window - bool hovered, held; - ImRect resize_rect(corner - def.InnerDir * grip_hover_outer_size, corner + def.InnerDir * grip_hover_inner_size); - if (resize_rect.Min.x > resize_rect.Max.x) ImSwap(resize_rect.Min.x, resize_rect.Max.x); - if (resize_rect.Min.y > resize_rect.Max.y) ImSwap(resize_rect.Min.y, resize_rect.Max.y); - ImGuiID resize_grip_id = window->GetID(resize_grip_n); // == GetWindowResizeCornerID() - ItemAdd(resize_rect, resize_grip_id, NULL, ImGuiItemFlags_NoNav); - ButtonBehavior(resize_rect, resize_grip_id, &hovered, &held, ImGuiButtonFlags_FlattenChildren | ImGuiButtonFlags_NoNavFocus); - //GetForegroundDrawList(window)->AddRect(resize_rect.Min, resize_rect.Max, IM_COL32(255, 255, 0, 255)); - if (hovered || held) - g.MouseCursor = (resize_grip_n & 1) ? ImGuiMouseCursor_ResizeNESW : ImGuiMouseCursor_ResizeNWSE; - - if (held && g.IO.MouseClickedCount[0] == 2 && resize_grip_n == 0) - { - // Manual auto-fit when double-clicking - size_target = CalcWindowSizeAfterConstraint(window, size_auto_fit); - ret_auto_fit = true; - ClearActiveID(); - } - else if (held) - { - // Resize from any of the four corners - // We don't use an incremental MouseDelta but rather compute an absolute target size based on mouse position - ImVec2 clamp_min = ImVec2(def.CornerPosN.x == 1.0f ? clamp_rect.Min.x : -FLT_MAX, (def.CornerPosN.y == 1.0f || (def.CornerPosN.y == 0.0f && window_move_from_title_bar)) ? clamp_rect.Min.y : -FLT_MAX); - ImVec2 clamp_max = ImVec2(def.CornerPosN.x == 0.0f ? clamp_rect.Max.x : +FLT_MAX, def.CornerPosN.y == 0.0f ? clamp_rect.Max.y : +FLT_MAX); - ImVec2 corner_target = g.IO.MousePos - g.ActiveIdClickOffset + ImLerp(def.InnerDir * grip_hover_outer_size, def.InnerDir * -grip_hover_inner_size, def.CornerPosN); // Corner of the window corresponding to our corner grip - corner_target = ImClamp(corner_target, clamp_min, clamp_max); - CalcResizePosSizeFromAnyCorner(window, corner_target, def.CornerPosN, &pos_target, &size_target); - } - - // Only lower-left grip is visible before hovering/activating - if (resize_grip_n == 0 || held || hovered) - resize_grip_col[resize_grip_n] = GetColorU32(held ? ImGuiCol_ResizeGripActive : hovered ? ImGuiCol_ResizeGripHovered : ImGuiCol_ResizeGrip); - } - for (int border_n = 0; border_n < resize_border_count; border_n++) - { - const ImGuiResizeBorderDef& def = resize_border_def[border_n]; - const ImGuiAxis axis = (border_n == ImGuiDir_Left || border_n == ImGuiDir_Right) ? ImGuiAxis_X : ImGuiAxis_Y; - - bool hovered, held; - ImRect border_rect = GetResizeBorderRect(window, border_n, grip_hover_inner_size, WINDOWS_HOVER_PADDING); - ImGuiID border_id = window->GetID(border_n + 4); // == GetWindowResizeBorderID() - ItemAdd(border_rect, border_id, NULL, ImGuiItemFlags_NoNav); - ButtonBehavior(border_rect, border_id, &hovered, &held, ImGuiButtonFlags_FlattenChildren | ImGuiButtonFlags_NoNavFocus); - //GetForegroundDrawLists(window)->AddRect(border_rect.Min, border_rect.Max, IM_COL32(255, 255, 0, 255)); - if ((hovered && g.HoveredIdTimer > WINDOWS_RESIZE_FROM_EDGES_FEEDBACK_TIMER) || held) - { - g.MouseCursor = (axis == ImGuiAxis_X) ? ImGuiMouseCursor_ResizeEW : ImGuiMouseCursor_ResizeNS; - if (held) - *border_held = border_n; - } - if (held) - { - ImVec2 clamp_min(border_n == ImGuiDir_Right ? clamp_rect.Min.x : -FLT_MAX, border_n == ImGuiDir_Down || (border_n == ImGuiDir_Up && window_move_from_title_bar) ? clamp_rect.Min.y : -FLT_MAX); - ImVec2 clamp_max(border_n == ImGuiDir_Left ? clamp_rect.Max.x : +FLT_MAX, border_n == ImGuiDir_Up ? clamp_rect.Max.y : +FLT_MAX); - ImVec2 border_target = window->Pos; - border_target[axis] = g.IO.MousePos[axis] - g.ActiveIdClickOffset[axis] + WINDOWS_HOVER_PADDING; - border_target = ImClamp(border_target, clamp_min, clamp_max); - CalcResizePosSizeFromAnyCorner(window, border_target, ImMin(def.SegmentN1, def.SegmentN2), &pos_target, &size_target); - } - } - PopID(); - - // Restore nav layer - window->DC.NavLayerCurrent = ImGuiNavLayer_Main; - - // Navigation resize (keyboard/gamepad) - // FIXME: This cannot be moved to NavUpdateWindowing() because CalcWindowSizeAfterConstraint() need to callback into user. - // Not even sure the callback works here. - if (g.NavWindowingTarget && g.NavWindowingTarget->RootWindowDockTree == window) - { - ImVec2 nav_resize_dir; - if (g.NavInputSource == ImGuiInputSource_Keyboard && g.IO.KeyShift) - nav_resize_dir = GetKeyMagnitude2d(ImGuiKey_LeftArrow, ImGuiKey_RightArrow, ImGuiKey_UpArrow, ImGuiKey_DownArrow); - if (g.NavInputSource == ImGuiInputSource_Gamepad) - nav_resize_dir = GetKeyMagnitude2d(ImGuiKey_GamepadDpadLeft, ImGuiKey_GamepadDpadRight, ImGuiKey_GamepadDpadUp, ImGuiKey_GamepadDpadDown); - if (nav_resize_dir.x != 0.0f || nav_resize_dir.y != 0.0f) - { - const float NAV_RESIZE_SPEED = 600.0f; - const float resize_step = NAV_RESIZE_SPEED * g.IO.DeltaTime * ImMin(g.IO.DisplayFramebufferScale.x, g.IO.DisplayFramebufferScale.y); - g.NavWindowingAccumDeltaSize += nav_resize_dir * resize_step; - g.NavWindowingAccumDeltaSize = ImMax(g.NavWindowingAccumDeltaSize, clamp_rect.Min - window->Pos - window->Size); // We need Pos+Size >= clmap_rect.Min, so Size >= clmap_rect.Min - Pos, so size_delta >= clmap_rect.Min - window->Pos - window->Size - g.NavWindowingToggleLayer = false; - g.NavDisableMouseHover = true; - resize_grip_col[0] = GetColorU32(ImGuiCol_ResizeGripActive); - ImVec2 accum_floored = ImTrunc(g.NavWindowingAccumDeltaSize); - if (accum_floored.x != 0.0f || accum_floored.y != 0.0f) - { - // FIXME-NAV: Should store and accumulate into a separate size buffer to handle sizing constraints properly, right now a constraint will make us stuck. - size_target = CalcWindowSizeAfterConstraint(window, window->SizeFull + accum_floored); - g.NavWindowingAccumDeltaSize -= accum_floored; - } - } - } - - // Apply back modified position/size to window - if (size_target.x != FLT_MAX) - { - window->SizeFull = size_target; - MarkIniSettingsDirty(window); - } - if (pos_target.x != FLT_MAX) - { - window->Pos = ImTrunc(pos_target); - MarkIniSettingsDirty(window); - } - - window->Size = window->SizeFull; - return ret_auto_fit; -} - -static inline void ClampWindowPos(ImGuiWindow* window, const ImRect& visibility_rect) -{ - ImGuiContext& g = *GImGui; - ImVec2 size_for_clamping = window->Size; - if (g.IO.ConfigWindowsMoveFromTitleBarOnly && (!(window->Flags & ImGuiWindowFlags_NoTitleBar) || window->DockNodeAsHost)) - size_for_clamping.y = ImGui::GetFrameHeight(); // Not using window->TitleBarHeight() as DockNodeAsHost will report 0.0f here. - window->Pos = ImClamp(window->Pos, visibility_rect.Min - size_for_clamping, visibility_rect.Max); -} - -static void ImGui::RenderWindowOuterBorders(ImGuiWindow* window) -{ - ImGuiContext& g = *GImGui; - float rounding = window->WindowRounding; - float border_size = window->WindowBorderSize; - if (border_size > 0.0f && !(window->Flags & ImGuiWindowFlags_NoBackground)) - window->DrawList->AddRect(window->Pos, window->Pos + window->Size, GetColorU32(ImGuiCol_Border), rounding, 0, border_size); - - int border_held = window->ResizeBorderHeld; - if (border_held != -1) - { - const ImGuiResizeBorderDef& def = resize_border_def[border_held]; - ImRect border_r = GetResizeBorderRect(window, border_held, rounding, 0.0f); - window->DrawList->PathArcTo(ImLerp(border_r.Min, border_r.Max, def.SegmentN1) + ImVec2(0.5f, 0.5f) + def.InnerDir * rounding, rounding, def.OuterAngle - IM_PI * 0.25f, def.OuterAngle); - window->DrawList->PathArcTo(ImLerp(border_r.Min, border_r.Max, def.SegmentN2) + ImVec2(0.5f, 0.5f) + def.InnerDir * rounding, rounding, def.OuterAngle, def.OuterAngle + IM_PI * 0.25f); - window->DrawList->PathStroke(GetColorU32(ImGuiCol_SeparatorActive), 0, ImMax(2.0f, border_size)); // Thicker than usual - } - if (g.Style.FrameBorderSize > 0 && !(window->Flags & ImGuiWindowFlags_NoTitleBar) && !window->DockIsActive) - { - float y = window->Pos.y + window->TitleBarHeight() - 1; - window->DrawList->AddLine(ImVec2(window->Pos.x + border_size, y), ImVec2(window->Pos.x + window->Size.x - border_size, y), GetColorU32(ImGuiCol_Border), g.Style.FrameBorderSize); - } -} - -// Draw background and borders -// Draw and handle scrollbars -void ImGui::RenderWindowDecorations(ImGuiWindow* window, const ImRect& title_bar_rect, bool title_bar_is_highlight, bool handle_borders_and_resize_grips, int resize_grip_count, const ImU32 resize_grip_col[4], float resize_grip_draw_size) -{ - ImGuiContext& g = *GImGui; - ImGuiStyle& style = g.Style; - ImGuiWindowFlags flags = window->Flags; - - // Ensure that ScrollBar doesn't read last frame's SkipItems - IM_ASSERT(window->BeginCount == 0); - window->SkipItems = false; - - // Draw window + handle manual resize - // As we highlight the title bar when want_focus is set, multiple reappearing windows will have their title bar highlighted on their reappearing frame. - const float window_rounding = window->WindowRounding; - const float window_border_size = window->WindowBorderSize; - if (window->Collapsed) - { - // Title bar only - const float backup_border_size = style.FrameBorderSize; - g.Style.FrameBorderSize = window->WindowBorderSize; - ImU32 title_bar_col = GetColorU32((title_bar_is_highlight && !g.NavDisableHighlight) ? ImGuiCol_TitleBgActive : ImGuiCol_TitleBgCollapsed); - if (window->ViewportOwned) - title_bar_col |= IM_COL32_A_MASK; // No alpha (we don't support is_docking_transparent_payload here because simpler and less meaningful, but could with a bit of code shuffle/reuse) - RenderFrame(title_bar_rect.Min, title_bar_rect.Max, title_bar_col, true, window_rounding); - g.Style.FrameBorderSize = backup_border_size; - } - else - { - // Window background - if (!(flags & ImGuiWindowFlags_NoBackground)) - { - bool is_docking_transparent_payload = false; - if (g.DragDropActive && (g.FrameCount - g.DragDropAcceptFrameCount) <= 1 && g.IO.ConfigDockingTransparentPayload) - if (g.DragDropPayload.IsDataType(IMGUI_PAYLOAD_TYPE_WINDOW) && *(ImGuiWindow**)g.DragDropPayload.Data == window) - is_docking_transparent_payload = true; - - ImU32 bg_col = GetColorU32(GetWindowBgColorIdx(window)); - if (window->ViewportOwned) - { - bg_col |= IM_COL32_A_MASK; // No alpha - if (is_docking_transparent_payload) - window->Viewport->Alpha *= DOCKING_TRANSPARENT_PAYLOAD_ALPHA; - } - else - { - // Adjust alpha. For docking - bool override_alpha = false; - float alpha = 1.0f; - if (g.NextWindowData.Flags & ImGuiNextWindowDataFlags_HasBgAlpha) - { - alpha = g.NextWindowData.BgAlphaVal; - override_alpha = true; - } - if (is_docking_transparent_payload) - { - alpha *= DOCKING_TRANSPARENT_PAYLOAD_ALPHA; // FIXME-DOCK: Should that be an override? - override_alpha = true; - } - if (override_alpha) - bg_col = (bg_col & ~IM_COL32_A_MASK) | (IM_F32_TO_INT8_SAT(alpha) << IM_COL32_A_SHIFT); - } - - // Render, for docked windows and host windows we ensure bg goes before decorations - if (window->DockIsActive) - window->DockNode->LastBgColor = bg_col; - ImDrawList* bg_draw_list = window->DockIsActive ? window->DockNode->HostWindow->DrawList : window->DrawList; - if (window->DockIsActive || (flags & ImGuiWindowFlags_DockNodeHost)) - bg_draw_list->ChannelsSetCurrent(DOCKING_HOST_DRAW_CHANNEL_BG); - bg_draw_list->AddRectFilled(window->Pos + ImVec2(0, window->TitleBarHeight()), window->Pos + window->Size, bg_col, window_rounding, (flags & ImGuiWindowFlags_NoTitleBar) ? 0 : ImDrawFlags_RoundCornersBottom); - if (window->DockIsActive || (flags & ImGuiWindowFlags_DockNodeHost)) - bg_draw_list->ChannelsSetCurrent(DOCKING_HOST_DRAW_CHANNEL_FG); - } - if (window->DockIsActive) - window->DockNode->IsBgDrawnThisFrame = true; - - // Title bar - // (when docked, DockNode are drawing their own title bar. Individual windows however do NOT set the _NoTitleBar flag, - // in order for their pos/size to be matching their undocking state.) - if (!(flags & ImGuiWindowFlags_NoTitleBar) && !window->DockIsActive) - { - ImU32 title_bar_col = GetColorU32(title_bar_is_highlight ? ImGuiCol_TitleBgActive : ImGuiCol_TitleBg); - window->DrawList->AddRectFilled(title_bar_rect.Min, title_bar_rect.Max, title_bar_col, window_rounding, ImDrawFlags_RoundCornersTop); - } - - // Menu bar - if (flags & ImGuiWindowFlags_MenuBar) - { - ImRect menu_bar_rect = window->MenuBarRect(); - menu_bar_rect.ClipWith(window->Rect()); // Soft clipping, in particular child window don't have minimum size covering the menu bar so this is useful for them. - window->DrawList->AddRectFilled(menu_bar_rect.Min + ImVec2(window_border_size, 0), menu_bar_rect.Max - ImVec2(window_border_size, 0), GetColorU32(ImGuiCol_MenuBarBg), (flags & ImGuiWindowFlags_NoTitleBar) ? window_rounding : 0.0f, ImDrawFlags_RoundCornersTop); - if (style.FrameBorderSize > 0.0f && menu_bar_rect.Max.y < window->Pos.y + window->Size.y) - window->DrawList->AddLine(menu_bar_rect.GetBL(), menu_bar_rect.GetBR(), GetColorU32(ImGuiCol_Border), style.FrameBorderSize); - } - - // Docking: Unhide tab bar (small triangle in the corner), drag from small triangle to quickly undock - ImGuiDockNode* node = window->DockNode; - if (window->DockIsActive && node->IsHiddenTabBar() && !node->IsNoTabBar()) - { - float unhide_sz_draw = ImTrunc(g.FontSize * 0.70f); - float unhide_sz_hit = ImTrunc(g.FontSize * 0.55f); - ImVec2 p = node->Pos; - ImRect r(p, p + ImVec2(unhide_sz_hit, unhide_sz_hit)); - ImGuiID unhide_id = window->GetID("#UNHIDE"); - KeepAliveID(unhide_id); - bool hovered, held; - if (ButtonBehavior(r, unhide_id, &hovered, &held, ImGuiButtonFlags_FlattenChildren)) - node->WantHiddenTabBarToggle = true; - else if (held && IsMouseDragging(0)) - StartMouseMovingWindowOrNode(window, node, true); - - // FIXME-DOCK: Ideally we'd use ImGuiCol_TitleBgActive/ImGuiCol_TitleBg here, but neither is guaranteed to be visible enough at this sort of size.. - ImU32 col = GetColorU32(((held && hovered) || (node->IsFocused && !hovered)) ? ImGuiCol_ButtonActive : hovered ? ImGuiCol_ButtonHovered : ImGuiCol_Button); - window->DrawList->AddTriangleFilled(p, p + ImVec2(unhide_sz_draw, 0.0f), p + ImVec2(0.0f, unhide_sz_draw), col); - } - - // Scrollbars - if (window->ScrollbarX) - Scrollbar(ImGuiAxis_X); - if (window->ScrollbarY) - Scrollbar(ImGuiAxis_Y); - - // Render resize grips (after their input handling so we don't have a frame of latency) - if (handle_borders_and_resize_grips && !(flags & ImGuiWindowFlags_NoResize)) - { - for (int resize_grip_n = 0; resize_grip_n < resize_grip_count; resize_grip_n++) - { - const ImU32 col = resize_grip_col[resize_grip_n]; - if ((col & IM_COL32_A_MASK) == 0) - continue; - const ImGuiResizeGripDef& grip = resize_grip_def[resize_grip_n]; - const ImVec2 corner = ImLerp(window->Pos, window->Pos + window->Size, grip.CornerPosN); - window->DrawList->PathLineTo(corner + grip.InnerDir * ((resize_grip_n & 1) ? ImVec2(window_border_size, resize_grip_draw_size) : ImVec2(resize_grip_draw_size, window_border_size))); - window->DrawList->PathLineTo(corner + grip.InnerDir * ((resize_grip_n & 1) ? ImVec2(resize_grip_draw_size, window_border_size) : ImVec2(window_border_size, resize_grip_draw_size))); - window->DrawList->PathArcToFast(ImVec2(corner.x + grip.InnerDir.x * (window_rounding + window_border_size), corner.y + grip.InnerDir.y * (window_rounding + window_border_size)), window_rounding, grip.AngleMin12, grip.AngleMax12); - window->DrawList->PathFillConvex(col); - } - } - - // Borders (for dock node host they will be rendered over after the tab bar) - if (handle_borders_and_resize_grips && !window->DockNodeAsHost) - RenderWindowOuterBorders(window); - } -} - -// When inside a dock node, this is handled in DockNodeCalcTabBarLayout() instead. -// Render title text, collapse button, close button -void ImGui::RenderWindowTitleBarContents(ImGuiWindow* window, const ImRect& title_bar_rect, const char* name, bool* p_open) -{ - ImGuiContext& g = *GImGui; - ImGuiStyle& style = g.Style; - ImGuiWindowFlags flags = window->Flags; - - const bool has_close_button = (p_open != NULL); - const bool has_collapse_button = !(flags & ImGuiWindowFlags_NoCollapse) && (style.WindowMenuButtonPosition != ImGuiDir_None); - - // Close & Collapse button are on the Menu NavLayer and don't default focus (unless there's nothing else on that layer) - // FIXME-NAV: Might want (or not?) to set the equivalent of ImGuiButtonFlags_NoNavFocus so that mouse clicks on standard title bar items don't necessarily set nav/keyboard ref? - const ImGuiItemFlags item_flags_backup = g.CurrentItemFlags; - g.CurrentItemFlags |= ImGuiItemFlags_NoNavDefaultFocus; - window->DC.NavLayerCurrent = ImGuiNavLayer_Menu; - - // Layout buttons - // FIXME: Would be nice to generalize the subtleties expressed here into reusable code. - float pad_l = style.FramePadding.x; - float pad_r = style.FramePadding.x; - float button_sz = g.FontSize; - ImVec2 close_button_pos; - ImVec2 collapse_button_pos; - if (has_close_button) - { - close_button_pos = ImVec2(title_bar_rect.Max.x - pad_r - button_sz, title_bar_rect.Min.y + style.FramePadding.y); - pad_r += button_sz + style.ItemInnerSpacing.x; - } - if (has_collapse_button && style.WindowMenuButtonPosition == ImGuiDir_Right) - { - collapse_button_pos = ImVec2(title_bar_rect.Max.x - pad_r - button_sz, title_bar_rect.Min.y + style.FramePadding.y); - pad_r += button_sz + style.ItemInnerSpacing.x; - } - if (has_collapse_button && style.WindowMenuButtonPosition == ImGuiDir_Left) - { - collapse_button_pos = ImVec2(title_bar_rect.Min.x + pad_l, title_bar_rect.Min.y + style.FramePadding.y); - pad_l += button_sz + style.ItemInnerSpacing.x; - } - - // Collapse button (submitting first so it gets priority when choosing a navigation init fallback) - if (has_collapse_button) - if (CollapseButton(window->GetID("#COLLAPSE"), collapse_button_pos, NULL)) - window->WantCollapseToggle = true; // Defer actual collapsing to next frame as we are too far in the Begin() function - - // Close button - if (has_close_button) - if (CloseButton(window->GetID("#CLOSE"), close_button_pos)) - *p_open = false; - - window->DC.NavLayerCurrent = ImGuiNavLayer_Main; - g.CurrentItemFlags = item_flags_backup; - - // Title bar text (with: horizontal alignment, avoiding collapse/close button, optional "unsaved document" marker) - // FIXME: Refactor text alignment facilities along with RenderText helpers, this is WAY too much messy code.. - const float marker_size_x = (flags & ImGuiWindowFlags_UnsavedDocument) ? button_sz * 0.80f : 0.0f; - const ImVec2 text_size = CalcTextSize(name, NULL, true) + ImVec2(marker_size_x, 0.0f); - - // As a nice touch we try to ensure that centered title text doesn't get affected by visibility of Close/Collapse button, - // while uncentered title text will still reach edges correctly. - if (pad_l > style.FramePadding.x) - pad_l += g.Style.ItemInnerSpacing.x; - if (pad_r > style.FramePadding.x) - pad_r += g.Style.ItemInnerSpacing.x; - if (style.WindowTitleAlign.x > 0.0f && style.WindowTitleAlign.x < 1.0f) - { - float centerness = ImSaturate(1.0f - ImFabs(style.WindowTitleAlign.x - 0.5f) * 2.0f); // 0.0f on either edges, 1.0f on center - float pad_extend = ImMin(ImMax(pad_l, pad_r), title_bar_rect.GetWidth() - pad_l - pad_r - text_size.x); - pad_l = ImMax(pad_l, pad_extend * centerness); - pad_r = ImMax(pad_r, pad_extend * centerness); - } - - ImRect layout_r(title_bar_rect.Min.x + pad_l, title_bar_rect.Min.y, title_bar_rect.Max.x - pad_r, title_bar_rect.Max.y); - ImRect clip_r(layout_r.Min.x, layout_r.Min.y, ImMin(layout_r.Max.x + g.Style.ItemInnerSpacing.x, title_bar_rect.Max.x), layout_r.Max.y); - if (flags & ImGuiWindowFlags_UnsavedDocument) - { - ImVec2 marker_pos; - marker_pos.x = ImClamp(layout_r.Min.x + (layout_r.GetWidth() - text_size.x) * style.WindowTitleAlign.x + text_size.x, layout_r.Min.x, layout_r.Max.x); - marker_pos.y = (layout_r.Min.y + layout_r.Max.y) * 0.5f; - if (marker_pos.x > layout_r.Min.x) - { - RenderBullet(window->DrawList, marker_pos, GetColorU32(ImGuiCol_Text)); - clip_r.Max.x = ImMin(clip_r.Max.x, marker_pos.x - (int)(marker_size_x * 0.5f)); - } - } - //if (g.IO.KeyShift) window->DrawList->AddRect(layout_r.Min, layout_r.Max, IM_COL32(255, 128, 0, 255)); // [DEBUG] - //if (g.IO.KeyCtrl) window->DrawList->AddRect(clip_r.Min, clip_r.Max, IM_COL32(255, 128, 0, 255)); // [DEBUG] - RenderTextClipped(layout_r.Min, layout_r.Max, name, NULL, &text_size, style.WindowTitleAlign, &clip_r); -} - -void ImGui::UpdateWindowParentAndRootLinks(ImGuiWindow* window, ImGuiWindowFlags flags, ImGuiWindow* parent_window) -{ - window->ParentWindow = parent_window; - window->RootWindow = window->RootWindowPopupTree = window->RootWindowDockTree = window->RootWindowForTitleBarHighlight = window->RootWindowForNav = window; - if (parent_window && (flags & ImGuiWindowFlags_ChildWindow) && !(flags & ImGuiWindowFlags_Tooltip)) - { - window->RootWindowDockTree = parent_window->RootWindowDockTree; - if (!window->DockIsActive && !(parent_window->Flags & ImGuiWindowFlags_DockNodeHost)) - window->RootWindow = parent_window->RootWindow; - } - if (parent_window && (flags & ImGuiWindowFlags_Popup)) - window->RootWindowPopupTree = parent_window->RootWindowPopupTree; - if (parent_window && !(flags & ImGuiWindowFlags_Modal) && (flags & (ImGuiWindowFlags_ChildWindow | ImGuiWindowFlags_Popup))) // FIXME: simply use _NoTitleBar ? - window->RootWindowForTitleBarHighlight = parent_window->RootWindowForTitleBarHighlight; - while (window->RootWindowForNav->Flags & ImGuiWindowFlags_NavFlattened) - { - IM_ASSERT(window->RootWindowForNav->ParentWindow != NULL); - window->RootWindowForNav = window->RootWindowForNav->ParentWindow; - } -} - -// When a modal popup is open, newly created windows that want focus (i.e. are not popups and do not specify ImGuiWindowFlags_NoFocusOnAppearing) -// should be positioned behind that modal window, unless the window was created inside the modal begin-stack. -// In case of multiple stacked modals newly created window honors begin stack order and does not go below its own modal parent. -// - WindowA // FindBlockingModal() returns Modal1 -// - WindowB // .. returns Modal1 -// - Modal1 // .. returns Modal2 -// - WindowC // .. returns Modal2 -// - WindowD // .. returns Modal2 -// - Modal2 // .. returns Modal2 -// - WindowE // .. returns NULL -// Notes: -// - FindBlockingModal(NULL) == NULL is generally equivalent to GetTopMostPopupModal() == NULL. -// Only difference is here we check for ->Active/WasActive but it may be unecessary. -ImGuiWindow* ImGui::FindBlockingModal(ImGuiWindow* window) -{ - ImGuiContext& g = *GImGui; - if (g.OpenPopupStack.Size <= 0) - return NULL; - - // Find a modal that has common parent with specified window. Specified window should be positioned behind that modal. - for (ImGuiPopupData& popup_data : g.OpenPopupStack) - { - ImGuiWindow* popup_window = popup_data.Window; - if (popup_window == NULL || !(popup_window->Flags & ImGuiWindowFlags_Modal)) - continue; - if (!popup_window->Active && !popup_window->WasActive) // Check WasActive, because this code may run before popup renders on current frame, also check Active to handle newly created windows. - continue; - if (window == NULL) // FindBlockingModal(NULL) test for if FocusWindow(NULL) is naturally possible via a mouse click. - return popup_window; - if (IsWindowWithinBeginStackOf(window, popup_window)) // Window may be over modal - continue; - return popup_window; // Place window right below first block modal - } - return NULL; -} - -// Push a new Dear ImGui window to add widgets to. -// - A default window called "Debug" is automatically stacked at the beginning of every frame so you can use widgets without explicitly calling a Begin/End pair. -// - Begin/End can be called multiple times during the frame with the same window name to append content. -// - The window name is used as a unique identifier to preserve window information across frames (and save rudimentary information to the .ini file). -// You can use the "##" or "###" markers to use the same label with different id, or same id with different label. See documentation at the top of this file. -// - Return false when window is collapsed, so you can early out in your code. You always need to call ImGui::End() even if false is returned. -// - Passing 'bool* p_open' displays a Close button on the upper-right corner of the window, the pointed value will be set to false when the button is pressed. -bool ImGui::Begin(const char* name, bool* p_open, ImGuiWindowFlags flags) -{ - ImGuiContext& g = *GImGui; - const ImGuiStyle& style = g.Style; - IM_ASSERT(name != NULL && name[0] != '\0'); // Window name required - IM_ASSERT(g.WithinFrameScope); // Forgot to call ImGui::NewFrame() - IM_ASSERT(g.FrameCountEnded != g.FrameCount); // Called ImGui::Render() or ImGui::EndFrame() and haven't called ImGui::NewFrame() again yet - - // Find or create - ImGuiWindow* window = FindWindowByName(name); - const bool window_just_created = (window == NULL); - if (window_just_created) - window = CreateNewWindow(name, flags); - - // Automatically disable manual moving/resizing when NoInputs is set - if ((flags & ImGuiWindowFlags_NoInputs) == ImGuiWindowFlags_NoInputs) - flags |= ImGuiWindowFlags_NoMove | ImGuiWindowFlags_NoResize; - - if (flags & ImGuiWindowFlags_NavFlattened) - IM_ASSERT(flags & ImGuiWindowFlags_ChildWindow); - - const int current_frame = g.FrameCount; - const bool first_begin_of_the_frame = (window->LastFrameActive != current_frame); - window->IsFallbackWindow = (g.CurrentWindowStack.Size == 0 && g.WithinFrameScopeWithImplicitWindow); - - // Update the Appearing flag (note: the BeginDocked() path may also set this to true later) - bool window_just_activated_by_user = (window->LastFrameActive < current_frame - 1); // Not using !WasActive because the implicit "Debug" window would always toggle off->on - if (flags & ImGuiWindowFlags_Popup) - { - ImGuiPopupData& popup_ref = g.OpenPopupStack[g.BeginPopupStack.Size]; - window_just_activated_by_user |= (window->PopupId != popup_ref.PopupId); // We recycle popups so treat window as activated if popup id changed - window_just_activated_by_user |= (window != popup_ref.Window); - } - - // Update Flags, LastFrameActive, BeginOrderXXX fields - const bool window_was_appearing = window->Appearing; - if (first_begin_of_the_frame) - { - UpdateWindowInFocusOrderList(window, window_just_created, flags); - window->Appearing = window_just_activated_by_user; - if (window->Appearing) - SetWindowConditionAllowFlags(window, ImGuiCond_Appearing, true); - window->FlagsPreviousFrame = window->Flags; - window->Flags = (ImGuiWindowFlags)flags; - window->LastFrameActive = current_frame; - window->LastTimeActive = (float)g.Time; - window->BeginOrderWithinParent = 0; - window->BeginOrderWithinContext = (short)(g.WindowsActiveCount++); - } - else - { - flags = window->Flags; - } - - // Docking - // (NB: during the frame dock nodes are created, it is possible that (window->DockIsActive == false) even though (window->DockNode->Windows.Size > 1) - IM_ASSERT(window->DockNode == NULL || window->DockNodeAsHost == NULL); // Cannot be both - if (g.NextWindowData.Flags & ImGuiNextWindowDataFlags_HasDock) - SetWindowDock(window, g.NextWindowData.DockId, g.NextWindowData.DockCond); - if (first_begin_of_the_frame) - { - bool has_dock_node = (window->DockId != 0 || window->DockNode != NULL); - bool new_auto_dock_node = !has_dock_node && GetWindowAlwaysWantOwnTabBar(window); - bool dock_node_was_visible = window->DockNodeIsVisible; - bool dock_tab_was_visible = window->DockTabIsVisible; - if (has_dock_node || new_auto_dock_node) - { - BeginDocked(window, p_open); - flags = window->Flags; - if (window->DockIsActive) - { - IM_ASSERT(window->DockNode != NULL); - g.NextWindowData.Flags &= ~ImGuiNextWindowDataFlags_HasSizeConstraint; // Docking currently override constraints - } - - // Amend the Appearing flag - if (window->DockTabIsVisible && !dock_tab_was_visible && dock_node_was_visible && !window->Appearing && !window_was_appearing) - { - window->Appearing = true; - SetWindowConditionAllowFlags(window, ImGuiCond_Appearing, true); - } - } - else - { - window->DockIsActive = window->DockNodeIsVisible = window->DockTabIsVisible = false; - } - } - - // Parent window is latched only on the first call to Begin() of the frame, so further append-calls can be done from a different window stack - ImGuiWindow* parent_window_in_stack = (window->DockIsActive && window->DockNode->HostWindow) ? window->DockNode->HostWindow : g.CurrentWindowStack.empty() ? NULL : g.CurrentWindowStack.back().Window; - ImGuiWindow* parent_window = first_begin_of_the_frame ? ((flags & (ImGuiWindowFlags_ChildWindow | ImGuiWindowFlags_Popup)) ? parent_window_in_stack : NULL) : window->ParentWindow; - IM_ASSERT(parent_window != NULL || !(flags & ImGuiWindowFlags_ChildWindow)); - - // We allow window memory to be compacted so recreate the base stack when needed. - if (window->IDStack.Size == 0) - window->IDStack.push_back(window->ID); - - // Add to stack - // We intentionally set g.CurrentWindow to NULL to prevent usage until when the viewport is set, then will call SetCurrentWindow() - g.CurrentWindow = window; - ImGuiWindowStackData window_stack_data; - window_stack_data.Window = window; - window_stack_data.ParentLastItemDataBackup = g.LastItemData; - window_stack_data.StackSizesOnBegin.SetToContextState(&g); - g.CurrentWindowStack.push_back(window_stack_data); - if (flags & ImGuiWindowFlags_ChildMenu) - g.BeginMenuCount++; - - // Update ->RootWindow and others pointers (before any possible call to FocusWindow) - if (first_begin_of_the_frame) - { - UpdateWindowParentAndRootLinks(window, flags, parent_window); - window->ParentWindowInBeginStack = parent_window_in_stack; - } - - // Add to focus scope stack - PushFocusScope(window->ID); - window->NavRootFocusScopeId = g.CurrentFocusScopeId; - g.CurrentWindow = NULL; - - // Add to popup stack - if (flags & ImGuiWindowFlags_Popup) - { - ImGuiPopupData& popup_ref = g.OpenPopupStack[g.BeginPopupStack.Size]; - popup_ref.Window = window; - popup_ref.ParentNavLayer = parent_window_in_stack->DC.NavLayerCurrent; - g.BeginPopupStack.push_back(popup_ref); - window->PopupId = popup_ref.PopupId; - } - - // Process SetNextWindow***() calls - // (FIXME: Consider splitting the HasXXX flags into X/Y components - bool window_pos_set_by_api = false; - bool window_size_x_set_by_api = false, window_size_y_set_by_api = false; - if (g.NextWindowData.Flags & ImGuiNextWindowDataFlags_HasPos) - { - window_pos_set_by_api = (window->SetWindowPosAllowFlags & g.NextWindowData.PosCond) != 0; - if (window_pos_set_by_api && ImLengthSqr(g.NextWindowData.PosPivotVal) > 0.00001f) - { - // May be processed on the next frame if this is our first frame and we are measuring size - // FIXME: Look into removing the branch so everything can go through this same code path for consistency. - window->SetWindowPosVal = g.NextWindowData.PosVal; - window->SetWindowPosPivot = g.NextWindowData.PosPivotVal; - window->SetWindowPosAllowFlags &= ~(ImGuiCond_Once | ImGuiCond_FirstUseEver | ImGuiCond_Appearing); - } - else - { - SetWindowPos(window, g.NextWindowData.PosVal, g.NextWindowData.PosCond); - } - } - if (g.NextWindowData.Flags & ImGuiNextWindowDataFlags_HasSize) - { - window_size_x_set_by_api = (window->SetWindowSizeAllowFlags & g.NextWindowData.SizeCond) != 0 && (g.NextWindowData.SizeVal.x > 0.0f); - window_size_y_set_by_api = (window->SetWindowSizeAllowFlags & g.NextWindowData.SizeCond) != 0 && (g.NextWindowData.SizeVal.y > 0.0f); - SetWindowSize(window, g.NextWindowData.SizeVal, g.NextWindowData.SizeCond); - } - if (g.NextWindowData.Flags & ImGuiNextWindowDataFlags_HasScroll) - { - if (g.NextWindowData.ScrollVal.x >= 0.0f) - { - window->ScrollTarget.x = g.NextWindowData.ScrollVal.x; - window->ScrollTargetCenterRatio.x = 0.0f; - } - if (g.NextWindowData.ScrollVal.y >= 0.0f) - { - window->ScrollTarget.y = g.NextWindowData.ScrollVal.y; - window->ScrollTargetCenterRatio.y = 0.0f; - } - } - if (g.NextWindowData.Flags & ImGuiNextWindowDataFlags_HasContentSize) - window->ContentSizeExplicit = g.NextWindowData.ContentSizeVal; - else if (first_begin_of_the_frame) - window->ContentSizeExplicit = ImVec2(0.0f, 0.0f); - if (g.NextWindowData.Flags & ImGuiNextWindowDataFlags_HasWindowClass) - window->WindowClass = g.NextWindowData.WindowClass; - if (g.NextWindowData.Flags & ImGuiNextWindowDataFlags_HasCollapsed) - SetWindowCollapsed(window, g.NextWindowData.CollapsedVal, g.NextWindowData.CollapsedCond); - if (g.NextWindowData.Flags & ImGuiNextWindowDataFlags_HasFocus) - FocusWindow(window); - if (window->Appearing) - SetWindowConditionAllowFlags(window, ImGuiCond_Appearing, false); - - // When reusing window again multiple times a frame, just append content (don't need to setup again) - if (first_begin_of_the_frame) - { - // Initialize - const bool window_is_child_tooltip = (flags & ImGuiWindowFlags_ChildWindow) && (flags & ImGuiWindowFlags_Tooltip); // FIXME-WIP: Undocumented behavior of Child+Tooltip for pinned tooltip (#1345) - const bool window_just_appearing_after_hidden_for_resize = (window->HiddenFramesCannotSkipItems > 0); - window->Active = true; - window->HasCloseButton = (p_open != NULL); - window->ClipRect = ImVec4(-FLT_MAX, -FLT_MAX, +FLT_MAX, +FLT_MAX); - window->IDStack.resize(1); - window->DrawList->_ResetForNewFrame(); - window->DC.CurrentTableIdx = -1; - if (flags & ImGuiWindowFlags_DockNodeHost) - { - window->DrawList->ChannelsSplit(2); - window->DrawList->ChannelsSetCurrent(DOCKING_HOST_DRAW_CHANNEL_FG); // Render decorations on channel 1 as we will render the backgrounds manually later - } - - // Restore buffer capacity when woken from a compacted state, to avoid - if (window->MemoryCompacted) - GcAwakeTransientWindowBuffers(window); - - // Update stored window name when it changes (which can _only_ happen with the "###" operator, so the ID would stay unchanged). - // The title bar always display the 'name' parameter, so we only update the string storage if it needs to be visible to the end-user elsewhere. - bool window_title_visible_elsewhere = false; - if ((window->Viewport && window->Viewport->Window == window) || (window->DockIsActive)) - window_title_visible_elsewhere = true; - else if (g.NavWindowingListWindow != NULL && (window->Flags & ImGuiWindowFlags_NoNavFocus) == 0) // Window titles visible when using CTRL+TAB - window_title_visible_elsewhere = true; - if (window_title_visible_elsewhere && !window_just_created && strcmp(name, window->Name) != 0) - { - size_t buf_len = (size_t)window->NameBufLen; - window->Name = ImStrdupcpy(window->Name, &buf_len, name); - window->NameBufLen = (int)buf_len; - } - - // UPDATE CONTENTS SIZE, UPDATE HIDDEN STATUS - - // Update contents size from last frame for auto-fitting (or use explicit size) - CalcWindowContentSizes(window, &window->ContentSize, &window->ContentSizeIdeal); - - // FIXME: These flags are decremented before they are used. This means that in order to have these fields produce their intended behaviors - // for one frame we must set them to at least 2, which is counter-intuitive. HiddenFramesCannotSkipItems is a more complicated case because - // it has a single usage before this code block and may be set below before it is finally checked. - if (window->HiddenFramesCanSkipItems > 0) - window->HiddenFramesCanSkipItems--; - if (window->HiddenFramesCannotSkipItems > 0) - window->HiddenFramesCannotSkipItems--; - if (window->HiddenFramesForRenderOnly > 0) - window->HiddenFramesForRenderOnly--; - - // Hide new windows for one frame until they calculate their size - if (window_just_created && (!window_size_x_set_by_api || !window_size_y_set_by_api)) - window->HiddenFramesCannotSkipItems = 1; - - // Hide popup/tooltip window when re-opening while we measure size (because we recycle the windows) - // We reset Size/ContentSize for reappearing popups/tooltips early in this function, so further code won't be tempted to use the old size. - if (window_just_activated_by_user && (flags & (ImGuiWindowFlags_Popup | ImGuiWindowFlags_Tooltip)) != 0) - { - window->HiddenFramesCannotSkipItems = 1; - if (flags & ImGuiWindowFlags_AlwaysAutoResize) - { - if (!window_size_x_set_by_api) - window->Size.x = window->SizeFull.x = 0.f; - if (!window_size_y_set_by_api) - window->Size.y = window->SizeFull.y = 0.f; - window->ContentSize = window->ContentSizeIdeal = ImVec2(0.f, 0.f); - } - } - - // SELECT VIEWPORT - // We need to do this before using any style/font sizes, as viewport with a different DPI may affect font sizes. - - WindowSelectViewport(window); - SetCurrentViewport(window, window->Viewport); - window->FontDpiScale = (g.IO.ConfigFlags & ImGuiConfigFlags_DpiEnableScaleFonts) ? window->Viewport->DpiScale : 1.0f; - SetCurrentWindow(window); - flags = window->Flags; - - // LOCK BORDER SIZE AND PADDING FOR THE FRAME (so that altering them doesn't cause inconsistencies) - // We read Style data after the call to UpdateSelectWindowViewport() which might be swapping the style. - - if (!window->DockIsActive && (flags & ImGuiWindowFlags_ChildWindow)) - window->WindowBorderSize = style.ChildBorderSize; - else - window->WindowBorderSize = ((flags & (ImGuiWindowFlags_Popup | ImGuiWindowFlags_Tooltip)) && !(flags & ImGuiWindowFlags_Modal)) ? style.PopupBorderSize : style.WindowBorderSize; - if (!window->DockIsActive && (flags & ImGuiWindowFlags_ChildWindow) && !(flags & (ImGuiWindowFlags_AlwaysUseWindowPadding | ImGuiWindowFlags_Popup)) && window->WindowBorderSize == 0.0f) - window->WindowPadding = ImVec2(0.0f, (flags & ImGuiWindowFlags_MenuBar) ? style.WindowPadding.y : 0.0f); - else - window->WindowPadding = style.WindowPadding; - - // Lock menu offset so size calculation can use it as menu-bar windows need a minimum size. - window->DC.MenuBarOffset.x = ImMax(ImMax(window->WindowPadding.x, style.ItemSpacing.x), g.NextWindowData.MenuBarOffsetMinVal.x); - window->DC.MenuBarOffset.y = g.NextWindowData.MenuBarOffsetMinVal.y; - - bool use_current_size_for_scrollbar_x = window_just_created; - bool use_current_size_for_scrollbar_y = window_just_created; - - // Collapse window by double-clicking on title bar - // At this point we don't have a clipping rectangle setup yet, so we can use the title bar area for hit detection and drawing - if (!(flags & ImGuiWindowFlags_NoTitleBar) && !(flags & ImGuiWindowFlags_NoCollapse) && !window->DockIsActive) - { - // We don't use a regular button+id to test for double-click on title bar (mostly due to legacy reason, could be fixed), so verify that we don't have items over the title bar. - ImRect title_bar_rect = window->TitleBarRect(); - if (g.HoveredWindow == window && g.HoveredId == 0 && g.HoveredIdPreviousFrame == 0 && IsMouseHoveringRect(title_bar_rect.Min, title_bar_rect.Max) && g.IO.MouseClickedCount[0] == 2) - window->WantCollapseToggle = true; - if (window->WantCollapseToggle) - { - window->Collapsed = !window->Collapsed; - if (!window->Collapsed) - use_current_size_for_scrollbar_y = true; - MarkIniSettingsDirty(window); - } - } - else - { - window->Collapsed = false; - } - window->WantCollapseToggle = false; - - // SIZE - - // Outer Decoration Sizes - // (we need to clear ScrollbarSize immediatly as CalcWindowAutoFitSize() needs it and can be called from other locations). - const ImVec2 scrollbar_sizes_from_last_frame = window->ScrollbarSizes; - window->DecoOuterSizeX1 = 0.0f; - window->DecoOuterSizeX2 = 0.0f; - window->DecoOuterSizeY1 = window->TitleBarHeight() + window->MenuBarHeight(); - window->DecoOuterSizeY2 = 0.0f; - window->ScrollbarSizes = ImVec2(0.0f, 0.0f); - - // Calculate auto-fit size, handle automatic resize - const ImVec2 size_auto_fit = CalcWindowAutoFitSize(window, window->ContentSizeIdeal); - if ((flags & ImGuiWindowFlags_AlwaysAutoResize) && !window->Collapsed) - { - // Using SetNextWindowSize() overrides ImGuiWindowFlags_AlwaysAutoResize, so it can be used on tooltips/popups, etc. - if (!window_size_x_set_by_api) - { - window->SizeFull.x = size_auto_fit.x; - use_current_size_for_scrollbar_x = true; - } - if (!window_size_y_set_by_api) - { - window->SizeFull.y = size_auto_fit.y; - use_current_size_for_scrollbar_y = true; - } - } - else if (window->AutoFitFramesX > 0 || window->AutoFitFramesY > 0) - { - // Auto-fit may only grow window during the first few frames - // We still process initial auto-fit on collapsed windows to get a window width, but otherwise don't honor ImGuiWindowFlags_AlwaysAutoResize when collapsed. - if (!window_size_x_set_by_api && window->AutoFitFramesX > 0) - { - window->SizeFull.x = window->AutoFitOnlyGrows ? ImMax(window->SizeFull.x, size_auto_fit.x) : size_auto_fit.x; - use_current_size_for_scrollbar_x = true; - } - if (!window_size_y_set_by_api && window->AutoFitFramesY > 0) - { - window->SizeFull.y = window->AutoFitOnlyGrows ? ImMax(window->SizeFull.y, size_auto_fit.y) : size_auto_fit.y; - use_current_size_for_scrollbar_y = true; - } - if (!window->Collapsed) - MarkIniSettingsDirty(window); - } - - // Apply minimum/maximum window size constraints and final size - window->SizeFull = CalcWindowSizeAfterConstraint(window, window->SizeFull); - window->Size = window->Collapsed && !(flags & ImGuiWindowFlags_ChildWindow) ? window->TitleBarRect().GetSize() : window->SizeFull; - - // POSITION - - // Popup latch its initial position, will position itself when it appears next frame - if (window_just_activated_by_user) - { - window->AutoPosLastDirection = ImGuiDir_None; - if ((flags & ImGuiWindowFlags_Popup) != 0 && !(flags & ImGuiWindowFlags_Modal) && !window_pos_set_by_api) // FIXME: BeginPopup() could use SetNextWindowPos() - window->Pos = g.BeginPopupStack.back().OpenPopupPos; - } - - // Position child window - if (flags & ImGuiWindowFlags_ChildWindow) - { - IM_ASSERT(parent_window && parent_window->Active); - window->BeginOrderWithinParent = (short)parent_window->DC.ChildWindows.Size; - parent_window->DC.ChildWindows.push_back(window); - if (!(flags & ImGuiWindowFlags_Popup) && !window_pos_set_by_api && !window_is_child_tooltip) - window->Pos = parent_window->DC.CursorPos; - } - - const bool window_pos_with_pivot = (window->SetWindowPosVal.x != FLT_MAX && window->HiddenFramesCannotSkipItems == 0); - if (window_pos_with_pivot) - SetWindowPos(window, window->SetWindowPosVal - window->Size * window->SetWindowPosPivot, 0); // Position given a pivot (e.g. for centering) - else if ((flags & ImGuiWindowFlags_ChildMenu) != 0) - window->Pos = FindBestWindowPosForPopup(window); - else if ((flags & ImGuiWindowFlags_Popup) != 0 && !window_pos_set_by_api && window_just_appearing_after_hidden_for_resize) - window->Pos = FindBestWindowPosForPopup(window); - else if ((flags & ImGuiWindowFlags_Tooltip) != 0 && !window_pos_set_by_api && !window_is_child_tooltip) - window->Pos = FindBestWindowPosForPopup(window); - - // Late create viewport if we don't fit within our current host viewport. - if (window->ViewportAllowPlatformMonitorExtend >= 0 && !window->ViewportOwned && !(window->Viewport->Flags & ImGuiViewportFlags_IsMinimized)) - if (!window->Viewport->GetMainRect().Contains(window->Rect())) - { - // This is based on the assumption that the DPI will be known ahead (same as the DPI of the selection done in UpdateSelectWindowViewport) - //ImGuiViewport* old_viewport = window->Viewport; - window->Viewport = AddUpdateViewport(window, window->ID, window->Pos, window->Size, ImGuiViewportFlags_NoFocusOnAppearing); - - // FIXME-DPI - //IM_ASSERT(old_viewport->DpiScale == window->Viewport->DpiScale); // FIXME-DPI: Something went wrong - SetCurrentViewport(window, window->Viewport); - window->FontDpiScale = (g.IO.ConfigFlags & ImGuiConfigFlags_DpiEnableScaleFonts) ? window->Viewport->DpiScale : 1.0f; - SetCurrentWindow(window); - } - - if (window->ViewportOwned) - WindowSyncOwnedViewport(window, parent_window_in_stack); - - // Calculate the range of allowed position for that window (to be movable and visible past safe area padding) - // When clamping to stay visible, we will enforce that window->Pos stays inside of visibility_rect. - ImRect viewport_rect(window->Viewport->GetMainRect()); - ImRect viewport_work_rect(window->Viewport->GetWorkRect()); - ImVec2 visibility_padding = ImMax(style.DisplayWindowPadding, style.DisplaySafeAreaPadding); - ImRect visibility_rect(viewport_work_rect.Min + visibility_padding, viewport_work_rect.Max - visibility_padding); - - // Clamp position/size so window stays visible within its viewport or monitor - // Ignore zero-sized display explicitly to avoid losing positions if a window manager reports zero-sized window when initializing or minimizing. - // FIXME: Similar to code in GetWindowAllowedExtentRect() - if (!window_pos_set_by_api && !(flags & ImGuiWindowFlags_ChildWindow)) - { - if (!window->ViewportOwned && viewport_rect.GetWidth() > 0 && viewport_rect.GetHeight() > 0.0f) - { - ClampWindowPos(window, visibility_rect); - } - else if (window->ViewportOwned && g.PlatformIO.Monitors.Size > 0) - { - // Lost windows (e.g. a monitor disconnected) will naturally moved to the fallback/dummy monitor aka the main viewport. - const ImGuiPlatformMonitor* monitor = GetViewportPlatformMonitor(window->Viewport); - visibility_rect.Min = monitor->WorkPos + visibility_padding; - visibility_rect.Max = monitor->WorkPos + monitor->WorkSize - visibility_padding; - ClampWindowPos(window, visibility_rect); - } - } - window->Pos = ImTrunc(window->Pos); - - // Lock window rounding for the frame (so that altering them doesn't cause inconsistencies) - // Large values tend to lead to variety of artifacts and are not recommended. - if (window->ViewportOwned || window->DockIsActive) - window->WindowRounding = 0.0f; - else - window->WindowRounding = (flags & ImGuiWindowFlags_ChildWindow) ? style.ChildRounding : ((flags & ImGuiWindowFlags_Popup) && !(flags & ImGuiWindowFlags_Modal)) ? style.PopupRounding : style.WindowRounding; - - // For windows with title bar or menu bar, we clamp to FrameHeight(FontSize + FramePadding.y * 2.0f) to completely hide artifacts. - //if ((window->Flags & ImGuiWindowFlags_MenuBar) || !(window->Flags & ImGuiWindowFlags_NoTitleBar)) - // window->WindowRounding = ImMin(window->WindowRounding, g.FontSize + style.FramePadding.y * 2.0f); - - // Apply window focus (new and reactivated windows are moved to front) - bool want_focus = false; - if (window_just_activated_by_user && !(flags & ImGuiWindowFlags_NoFocusOnAppearing)) - { - if (flags & ImGuiWindowFlags_Popup) - want_focus = true; - else if ((window->DockIsActive || (flags & ImGuiWindowFlags_ChildWindow) == 0) && !(flags & ImGuiWindowFlags_Tooltip)) - want_focus = true; - } - - // [Test Engine] Register whole window in the item system (before submitting further decorations) -#ifdef IMGUI_ENABLE_TEST_ENGINE - if (g.TestEngineHookItems) - { - IM_ASSERT(window->IDStack.Size == 1); - window->IDStack.Size = 0; // As window->IDStack[0] == window->ID here, make sure TestEngine doesn't erroneously see window as parent of itself. - IMGUI_TEST_ENGINE_ITEM_ADD(window->ID, window->Rect(), NULL); - IMGUI_TEST_ENGINE_ITEM_INFO(window->ID, window->Name, (g.HoveredWindow == window) ? ImGuiItemStatusFlags_HoveredRect : 0); - window->IDStack.Size = 1; - } -#endif - - // Decide if we are going to handle borders and resize grips - const bool handle_borders_and_resize_grips = (window->DockNodeAsHost || !window->DockIsActive); - - // Handle manual resize: Resize Grips, Borders, Gamepad - int border_held = -1; - ImU32 resize_grip_col[4] = {}; - const int resize_grip_count = g.IO.ConfigWindowsResizeFromEdges ? 2 : 1; // Allow resize from lower-left if we have the mouse cursor feedback for it. - const float resize_grip_draw_size = IM_TRUNC(ImMax(g.FontSize * 1.10f, window->WindowRounding + 1.0f + g.FontSize * 0.2f)); - if (handle_borders_and_resize_grips && !window->Collapsed) - if (UpdateWindowManualResize(window, size_auto_fit, &border_held, resize_grip_count, &resize_grip_col[0], visibility_rect)) - use_current_size_for_scrollbar_x = use_current_size_for_scrollbar_y = true; - window->ResizeBorderHeld = (signed char)border_held; - - // Synchronize window --> viewport again and one last time (clamping and manual resize may have affected either) - if (window->ViewportOwned) - { - if (!window->Viewport->PlatformRequestMove) - window->Viewport->Pos = window->Pos; - if (!window->Viewport->PlatformRequestResize) - window->Viewport->Size = window->Size; - window->Viewport->UpdateWorkRect(); - viewport_rect = window->Viewport->GetMainRect(); - } - - // Save last known viewport position within the window itself (so it can be saved in .ini file and restored) - window->ViewportPos = window->Viewport->Pos; - - // SCROLLBAR VISIBILITY - - // Update scrollbar visibility (based on the Size that was effective during last frame or the auto-resized Size). - if (!window->Collapsed) - { - // When reading the current size we need to read it after size constraints have been applied. - // Intentionally use previous frame values for InnerRect and ScrollbarSizes. - // And when we use window->DecorationUp here it doesn't have ScrollbarSizes.y applied yet. - ImVec2 avail_size_from_current_frame = ImVec2(window->SizeFull.x, window->SizeFull.y - (window->DecoOuterSizeY1 + window->DecoOuterSizeY2)); - ImVec2 avail_size_from_last_frame = window->InnerRect.GetSize() + scrollbar_sizes_from_last_frame; - ImVec2 needed_size_from_last_frame = window_just_created ? ImVec2(0, 0) : window->ContentSize + window->WindowPadding * 2.0f; - float size_x_for_scrollbars = use_current_size_for_scrollbar_x ? avail_size_from_current_frame.x : avail_size_from_last_frame.x; - float size_y_for_scrollbars = use_current_size_for_scrollbar_y ? avail_size_from_current_frame.y : avail_size_from_last_frame.y; - //bool scrollbar_y_from_last_frame = window->ScrollbarY; // FIXME: May want to use that in the ScrollbarX expression? How many pros vs cons? - window->ScrollbarY = (flags & ImGuiWindowFlags_AlwaysVerticalScrollbar) || ((needed_size_from_last_frame.y > size_y_for_scrollbars) && !(flags & ImGuiWindowFlags_NoScrollbar)); - window->ScrollbarX = (flags & ImGuiWindowFlags_AlwaysHorizontalScrollbar) || ((needed_size_from_last_frame.x > size_x_for_scrollbars - (window->ScrollbarY ? style.ScrollbarSize : 0.0f)) && !(flags & ImGuiWindowFlags_NoScrollbar) && (flags & ImGuiWindowFlags_HorizontalScrollbar)); - if (window->ScrollbarX && !window->ScrollbarY) - window->ScrollbarY = (needed_size_from_last_frame.y > size_y_for_scrollbars) && !(flags & ImGuiWindowFlags_NoScrollbar); - window->ScrollbarSizes = ImVec2(window->ScrollbarY ? style.ScrollbarSize : 0.0f, window->ScrollbarX ? style.ScrollbarSize : 0.0f); - - // Amend the partially filled window->DecorationXXX values. - window->DecoOuterSizeX2 += window->ScrollbarSizes.x; - window->DecoOuterSizeY2 += window->ScrollbarSizes.y; - } - - // UPDATE RECTANGLES (1- THOSE NOT AFFECTED BY SCROLLING) - // Update various regions. Variables they depend on should be set above in this function. - // We set this up after processing the resize grip so that our rectangles doesn't lag by a frame. - - // Outer rectangle - // Not affected by window border size. Used by: - // - FindHoveredWindow() (w/ extra padding when border resize is enabled) - // - Begin() initial clipping rect for drawing window background and borders. - // - Begin() clipping whole child - const ImRect host_rect = ((flags & ImGuiWindowFlags_ChildWindow) && !(flags & ImGuiWindowFlags_Popup) && !window_is_child_tooltip) ? parent_window->ClipRect : viewport_rect; - const ImRect outer_rect = window->Rect(); - const ImRect title_bar_rect = window->TitleBarRect(); - window->OuterRectClipped = outer_rect; - if (window->DockIsActive) - window->OuterRectClipped.Min.y += window->TitleBarHeight(); - window->OuterRectClipped.ClipWith(host_rect); - - // Inner rectangle - // Not affected by window border size. Used by: - // - InnerClipRect - // - ScrollToRectEx() - // - NavUpdatePageUpPageDown() - // - Scrollbar() - window->InnerRect.Min.x = window->Pos.x + window->DecoOuterSizeX1; - window->InnerRect.Min.y = window->Pos.y + window->DecoOuterSizeY1; - window->InnerRect.Max.x = window->Pos.x + window->Size.x - window->DecoOuterSizeX2; - window->InnerRect.Max.y = window->Pos.y + window->Size.y - window->DecoOuterSizeY2; - - // Inner clipping rectangle. - // Will extend a little bit outside the normal work region. - // This is to allow e.g. Selectable or CollapsingHeader or some separators to cover that space. - // Force round operator last to ensure that e.g. (int)(max.x-min.x) in user's render code produce correct result. - // Note that if our window is collapsed we will end up with an inverted (~null) clipping rectangle which is the correct behavior. - // Affected by window/frame border size. Used by: - // - Begin() initial clip rect - float top_border_size = (((flags & ImGuiWindowFlags_MenuBar) || !(flags & ImGuiWindowFlags_NoTitleBar)) ? style.FrameBorderSize : window->WindowBorderSize); - window->InnerClipRect.Min.x = ImFloor(0.5f + window->InnerRect.Min.x + ImMax(ImTrunc(window->WindowPadding.x * 0.5f), window->WindowBorderSize)); - window->InnerClipRect.Min.y = ImFloor(0.5f + window->InnerRect.Min.y + top_border_size); - window->InnerClipRect.Max.x = ImFloor(0.5f + window->InnerRect.Max.x - ImMax(ImTrunc(window->WindowPadding.x * 0.5f), window->WindowBorderSize)); - window->InnerClipRect.Max.y = ImFloor(0.5f + window->InnerRect.Max.y - window->WindowBorderSize); - window->InnerClipRect.ClipWithFull(host_rect); - - // Default item width. Make it proportional to window size if window manually resizes - if (window->Size.x > 0.0f && !(flags & ImGuiWindowFlags_Tooltip) && !(flags & ImGuiWindowFlags_AlwaysAutoResize)) - window->ItemWidthDefault = ImTrunc(window->Size.x * 0.65f); - else - window->ItemWidthDefault = ImTrunc(g.FontSize * 16.0f); - - // SCROLLING - - // Lock down maximum scrolling - // The value of ScrollMax are ahead from ScrollbarX/ScrollbarY which is intentionally using InnerRect from previous rect in order to accommodate - // for right/bottom aligned items without creating a scrollbar. - window->ScrollMax.x = ImMax(0.0f, window->ContentSize.x + window->WindowPadding.x * 2.0f - window->InnerRect.GetWidth()); - window->ScrollMax.y = ImMax(0.0f, window->ContentSize.y + window->WindowPadding.y * 2.0f - window->InnerRect.GetHeight()); - - // Apply scrolling - window->Scroll = CalcNextScrollFromScrollTargetAndClamp(window); - window->ScrollTarget = ImVec2(FLT_MAX, FLT_MAX); - window->DecoInnerSizeX1 = window->DecoInnerSizeY1 = 0.0f; - - // DRAWING - - // Setup draw list and outer clipping rectangle - IM_ASSERT(window->DrawList->CmdBuffer.Size == 1 && window->DrawList->CmdBuffer[0].ElemCount == 0); - window->DrawList->PushTextureID(g.Font->ContainerAtlas->TexID); - PushClipRect(host_rect.Min, host_rect.Max, false); - - // Child windows can render their decoration (bg color, border, scrollbars, etc.) within their parent to save a draw call (since 1.71) - // When using overlapping child windows, this will break the assumption that child z-order is mapped to submission order. - // FIXME: User code may rely on explicit sorting of overlapping child window and would need to disable this somehow. Please get in contact if you are affected (github #4493) - const bool is_undocked_or_docked_visible = !window->DockIsActive || window->DockTabIsVisible; - if (is_undocked_or_docked_visible) - { - bool render_decorations_in_parent = false; - if ((flags & ImGuiWindowFlags_ChildWindow) && !(flags & ImGuiWindowFlags_Popup) && !window_is_child_tooltip) - { - // - We test overlap with the previous child window only (testing all would end up being O(log N) not a good investment here) - // - We disable this when the parent window has zero vertices, which is a common pattern leading to laying out multiple overlapping childs - ImGuiWindow* previous_child = parent_window->DC.ChildWindows.Size >= 2 ? parent_window->DC.ChildWindows[parent_window->DC.ChildWindows.Size - 2] : NULL; - bool previous_child_overlapping = previous_child ? previous_child->Rect().Overlaps(window->Rect()) : false; - bool parent_is_empty = (parent_window->DrawList->VtxBuffer.Size == 0); - if (window->DrawList->CmdBuffer.back().ElemCount == 0 && !parent_is_empty && !previous_child_overlapping) - render_decorations_in_parent = true; - } - if (render_decorations_in_parent) - window->DrawList = parent_window->DrawList; - - // Handle title bar, scrollbar, resize grips and resize borders - const ImGuiWindow* window_to_highlight = g.NavWindowingTarget ? g.NavWindowingTarget : g.NavWindow; - const bool title_bar_is_highlight = want_focus || (window_to_highlight && (window->RootWindowForTitleBarHighlight == window_to_highlight->RootWindowForTitleBarHighlight || (window->DockNode && window->DockNode == window_to_highlight->DockNode))); - RenderWindowDecorations(window, title_bar_rect, title_bar_is_highlight, handle_borders_and_resize_grips, resize_grip_count, resize_grip_col, resize_grip_draw_size); - - if (render_decorations_in_parent) - window->DrawList = &window->DrawListInst; - } - - // UPDATE RECTANGLES (2- THOSE AFFECTED BY SCROLLING) - - // Work rectangle. - // Affected by window padding and border size. Used by: - // - Columns() for right-most edge - // - TreeNode(), CollapsingHeader() for right-most edge - // - BeginTabBar() for right-most edge - const bool allow_scrollbar_x = !(flags & ImGuiWindowFlags_NoScrollbar) && (flags & ImGuiWindowFlags_HorizontalScrollbar); - const bool allow_scrollbar_y = !(flags & ImGuiWindowFlags_NoScrollbar); - const float work_rect_size_x = (window->ContentSizeExplicit.x != 0.0f ? window->ContentSizeExplicit.x : ImMax(allow_scrollbar_x ? window->ContentSize.x : 0.0f, window->Size.x - window->WindowPadding.x * 2.0f - (window->DecoOuterSizeX1 + window->DecoOuterSizeX2))); - const float work_rect_size_y = (window->ContentSizeExplicit.y != 0.0f ? window->ContentSizeExplicit.y : ImMax(allow_scrollbar_y ? window->ContentSize.y : 0.0f, window->Size.y - window->WindowPadding.y * 2.0f - (window->DecoOuterSizeY1 + window->DecoOuterSizeY2))); - window->WorkRect.Min.x = ImTrunc(window->InnerRect.Min.x - window->Scroll.x + ImMax(window->WindowPadding.x, window->WindowBorderSize)); - window->WorkRect.Min.y = ImTrunc(window->InnerRect.Min.y - window->Scroll.y + ImMax(window->WindowPadding.y, window->WindowBorderSize)); - window->WorkRect.Max.x = window->WorkRect.Min.x + work_rect_size_x; - window->WorkRect.Max.y = window->WorkRect.Min.y + work_rect_size_y; - window->ParentWorkRect = window->WorkRect; - - // [LEGACY] Content Region - // FIXME-OBSOLETE: window->ContentRegionRect.Max is currently very misleading / partly faulty, but some BeginChild() patterns relies on it. - // Unless explicit content size is specified by user, this currently represent the region leading to no scrolling. - // Used by: - // - Mouse wheel scrolling + many other things - window->ContentRegionRect.Min.x = window->Pos.x - window->Scroll.x + window->WindowPadding.x + window->DecoOuterSizeX1; - window->ContentRegionRect.Min.y = window->Pos.y - window->Scroll.y + window->WindowPadding.y + window->DecoOuterSizeY1; - window->ContentRegionRect.Max.x = window->ContentRegionRect.Min.x + (window->ContentSizeExplicit.x != 0.0f ? window->ContentSizeExplicit.x : (window->Size.x - window->WindowPadding.x * 2.0f - (window->DecoOuterSizeX1 + window->DecoOuterSizeX2))); - window->ContentRegionRect.Max.y = window->ContentRegionRect.Min.y + (window->ContentSizeExplicit.y != 0.0f ? window->ContentSizeExplicit.y : (window->Size.y - window->WindowPadding.y * 2.0f - (window->DecoOuterSizeY1 + window->DecoOuterSizeY2))); - - // Setup drawing context - // (NB: That term "drawing context / DC" lost its meaning a long time ago. Initially was meant to hold transient data only. Nowadays difference between window-> and window->DC-> is dubious.) - window->DC.Indent.x = window->DecoOuterSizeX1 + window->WindowPadding.x - window->Scroll.x; - window->DC.GroupOffset.x = 0.0f; - window->DC.ColumnsOffset.x = 0.0f; - - // Record the loss of precision of CursorStartPos which can happen due to really large scrolling amount. - // This is used by clipper to compensate and fix the most common use case of large scroll area. Easy and cheap, next best thing compared to switching everything to double or ImU64. - double start_pos_highp_x = (double)window->Pos.x + window->WindowPadding.x - (double)window->Scroll.x + window->DecoOuterSizeX1 + window->DC.ColumnsOffset.x; - double start_pos_highp_y = (double)window->Pos.y + window->WindowPadding.y - (double)window->Scroll.y + window->DecoOuterSizeY1; - window->DC.CursorStartPos = ImVec2((float)start_pos_highp_x, (float)start_pos_highp_y); - window->DC.CursorStartPosLossyness = ImVec2((float)(start_pos_highp_x - window->DC.CursorStartPos.x), (float)(start_pos_highp_y - window->DC.CursorStartPos.y)); - window->DC.CursorPos = window->DC.CursorStartPos; - window->DC.CursorPosPrevLine = window->DC.CursorPos; - window->DC.CursorMaxPos = window->DC.CursorStartPos; - window->DC.IdealMaxPos = window->DC.CursorStartPos; - window->DC.CurrLineSize = window->DC.PrevLineSize = ImVec2(0.0f, 0.0f); - window->DC.CurrLineTextBaseOffset = window->DC.PrevLineTextBaseOffset = 0.0f; - window->DC.IsSameLine = window->DC.IsSetPos = false; - - window->DC.NavLayerCurrent = ImGuiNavLayer_Main; - window->DC.NavLayersActiveMask = window->DC.NavLayersActiveMaskNext; - window->DC.NavLayersActiveMaskNext = 0x00; - window->DC.NavIsScrollPushableX = true; - window->DC.NavHideHighlightOneFrame = false; - window->DC.NavWindowHasScrollY = (window->ScrollMax.y > 0.0f); - - window->DC.MenuBarAppending = false; - window->DC.MenuColumns.Update(style.ItemSpacing.x, window_just_activated_by_user); - window->DC.TreeDepth = 0; - window->DC.TreeJumpToParentOnPopMask = 0x00; - window->DC.ChildWindows.resize(0); - window->DC.StateStorage = &window->StateStorage; - window->DC.CurrentColumns = NULL; - window->DC.LayoutType = ImGuiLayoutType_Vertical; - window->DC.ParentLayoutType = parent_window ? parent_window->DC.LayoutType : ImGuiLayoutType_Vertical; - - window->DC.ItemWidth = window->ItemWidthDefault; - window->DC.TextWrapPos = -1.0f; // disabled - window->DC.ItemWidthStack.resize(0); - window->DC.TextWrapPosStack.resize(0); - - if (window->AutoFitFramesX > 0) - window->AutoFitFramesX--; - if (window->AutoFitFramesY > 0) - window->AutoFitFramesY--; - - // Apply focus (we need to call FocusWindow() AFTER setting DC.CursorStartPos so our initial navigation reference rectangle can start around there) - // We ImGuiFocusRequestFlags_UnlessBelowModal to: - // - Avoid focusing a window that is created outside of a modal. This will prevent active modal from being closed. - // - Position window behind the modal that is not a begin-parent of this window. - if (want_focus) - FocusWindow(window, ImGuiFocusRequestFlags_UnlessBelowModal); - if (want_focus && window == g.NavWindow) - NavInitWindow(window, false); // <-- this is in the way for us to be able to defer and sort reappearing FocusWindow() calls - - // Close requested by platform window (apply to all windows in this viewport) - if (p_open != NULL && window->Viewport->PlatformRequestClose && window->Viewport != GetMainViewport()) - { - IMGUI_DEBUG_LOG_VIEWPORT("[viewport] Window '%s' closed by PlatformRequestClose\n", window->Name); - *p_open = false; - g.NavWindowingToggleLayer = false; // Assume user mapped PlatformRequestClose on ALT-F4 so we disable ALT for menu toggle. False positive not an issue. // FIXME-NAV: Try removing. - } - - // Title bar - if (!(flags & ImGuiWindowFlags_NoTitleBar) && !window->DockIsActive) - RenderWindowTitleBarContents(window, ImRect(title_bar_rect.Min.x + window->WindowBorderSize, title_bar_rect.Min.y, title_bar_rect.Max.x - window->WindowBorderSize, title_bar_rect.Max.y), name, p_open); - - // Clear hit test shape every frame - window->HitTestHoleSize.x = window->HitTestHoleSize.y = 0; - - // Pressing CTRL+C while holding on a window copy its content to the clipboard - // This works but 1. doesn't handle multiple Begin/End pairs, 2. recursing into another Begin/End pair - so we need to work that out and add better logging scope. - // Maybe we can support CTRL+C on every element? - /* - //if (g.NavWindow == window && g.ActiveId == 0) - if (g.ActiveId == window->MoveId) - if (g.IO.KeyCtrl && IsKeyPressed(ImGuiKey_C)) - LogToClipboard(); - */ - - if (g.IO.ConfigFlags & ImGuiConfigFlags_DockingEnable) - { - // Docking: Dragging a dockable window (or any of its child) turns it into a drag and drop source. - // We need to do this _before_ we overwrite window->DC.LastItemId below because BeginDockableDragDropSource() also overwrites it. - if (g.MovingWindow == window && (window->RootWindowDockTree->Flags & ImGuiWindowFlags_NoDocking) == 0) - BeginDockableDragDropSource(window); - - // Docking: Any dockable window can act as a target. For dock node hosts we call BeginDockableDragDropTarget() in DockNodeUpdate() instead. - if (g.DragDropActive && !(flags & ImGuiWindowFlags_NoDocking)) - if (g.MovingWindow == NULL || g.MovingWindow->RootWindowDockTree != window) - if ((window == window->RootWindowDockTree) && !(window->Flags & ImGuiWindowFlags_DockNodeHost)) - BeginDockableDragDropTarget(window); - } - - // We fill last item data based on Title Bar/Tab, in order for IsItemHovered() and IsItemActive() to be usable after Begin(). - // This is useful to allow creating context menus on title bar only, etc. - if (window->DockIsActive) - SetLastItemData(window->MoveId, g.CurrentItemFlags, window->DockTabItemStatusFlags, window->DockTabItemRect); - else - SetLastItemData(window->MoveId, g.CurrentItemFlags, IsMouseHoveringRect(title_bar_rect.Min, title_bar_rect.Max, false) ? ImGuiItemStatusFlags_HoveredRect : 0, title_bar_rect); - - // [DEBUG] -#ifndef IMGUI_DISABLE_DEBUG_TOOLS - if (g.DebugLocateId != 0 && (window->ID == g.DebugLocateId || window->MoveId == g.DebugLocateId)) - DebugLocateItemResolveWithLastItem(); -#endif - - // [Test Engine] Register title bar / tab with MoveId. -#ifdef IMGUI_ENABLE_TEST_ENGINE - if (!(window->Flags & ImGuiWindowFlags_NoTitleBar)) - IMGUI_TEST_ENGINE_ITEM_ADD(g.LastItemData.ID, g.LastItemData.Rect, &g.LastItemData); -#endif - } - else - { - // Append - SetCurrentViewport(window, window->Viewport); - SetCurrentWindow(window); - } - - if (!(flags & ImGuiWindowFlags_DockNodeHost)) - PushClipRect(window->InnerClipRect.Min, window->InnerClipRect.Max, true); - - // Clear 'accessed' flag last thing (After PushClipRect which will set the flag. We want the flag to stay false when the default "Debug" window is unused) - window->WriteAccessed = false; - window->BeginCount++; - g.NextWindowData.ClearFlags(); - - // Update visibility - if (first_begin_of_the_frame) - { - // When we are about to select this tab (which will only be visible on the _next frame_), flag it with a non-zero HiddenFramesCannotSkipItems. - // This will have the important effect of actually returning true in Begin() and not setting SkipItems, allowing an earlier submission of the window contents. - // This is analogous to regular windows being hidden from one frame. - // It is especially important as e.g. nested TabBars would otherwise generate flicker in the form of one empty frame, or focus requests won't be processed. - if (window->DockIsActive && !window->DockTabIsVisible) - { - if (window->LastFrameJustFocused == g.FrameCount) - window->HiddenFramesCannotSkipItems = 1; - else - window->HiddenFramesCanSkipItems = 1; - } - - if (flags & ImGuiWindowFlags_ChildWindow) - { - // Child window can be out of sight and have "negative" clip windows. - // Mark them as collapsed so commands are skipped earlier (we can't manually collapse them because they have no title bar). - IM_ASSERT((flags& ImGuiWindowFlags_NoTitleBar) != 0 || (window->DockIsActive)); - if (!(flags & ImGuiWindowFlags_AlwaysAutoResize) && window->AutoFitFramesX <= 0 && window->AutoFitFramesY <= 0) // FIXME: Doesn't make sense for ChildWindow?? - { - const bool nav_request = (flags & ImGuiWindowFlags_NavFlattened) && (g.NavAnyRequest && g.NavWindow && g.NavWindow->RootWindowForNav == window->RootWindowForNav); - if (!g.LogEnabled && !nav_request) - if (window->OuterRectClipped.Min.x >= window->OuterRectClipped.Max.x || window->OuterRectClipped.Min.y >= window->OuterRectClipped.Max.y) - window->HiddenFramesCanSkipItems = 1; - } - - // Hide along with parent or if parent is collapsed - if (parent_window && (parent_window->Collapsed || parent_window->HiddenFramesCanSkipItems > 0)) - window->HiddenFramesCanSkipItems = 1; - if (parent_window && (parent_window->Collapsed || parent_window->HiddenFramesCannotSkipItems > 0)) - window->HiddenFramesCannotSkipItems = 1; - } - - // Don't render if style alpha is 0.0 at the time of Begin(). This is arbitrary and inconsistent but has been there for a long while (may remove at some point) - if (style.Alpha <= 0.0f) - window->HiddenFramesCanSkipItems = 1; - - // Update the Hidden flag - bool hidden_regular = (window->HiddenFramesCanSkipItems > 0) || (window->HiddenFramesCannotSkipItems > 0); - window->Hidden = hidden_regular || (window->HiddenFramesForRenderOnly > 0); - - // Disable inputs for requested number of frames - if (window->DisableInputsFrames > 0) - { - window->DisableInputsFrames--; - window->Flags |= ImGuiWindowFlags_NoInputs; - } - - // Update the SkipItems flag, used to early out of all items functions (no layout required) - bool skip_items = false; - if (window->Collapsed || !window->Active || hidden_regular) - if (window->AutoFitFramesX <= 0 && window->AutoFitFramesY <= 0 && window->HiddenFramesCannotSkipItems <= 0) - skip_items = true; - window->SkipItems = skip_items; - - // Restore NavLayersActiveMaskNext to previous value when not visible, so a CTRL+Tab back can use a safe value. - if (window->SkipItems) - window->DC.NavLayersActiveMaskNext = window->DC.NavLayersActiveMask; - - // Sanity check: there are two spots which can set Appearing = true - // - when 'window_just_activated_by_user' is set -> HiddenFramesCannotSkipItems is set -> SkipItems always false - // - in BeginDocked() path when DockNodeIsVisible == DockTabIsVisible == true -> hidden _should_ be all zero // FIXME: Not formally proven, hence the assert. - if (window->SkipItems && !window->Appearing) - IM_ASSERT(window->Appearing == false); // Please report on GitHub if this triggers: https://github.com/ocornut/imgui/issues/4177 - } - - // [DEBUG] io.ConfigDebugBeginReturnValue override return value to test Begin/End and BeginChild/EndChild behaviors. - // (The implicit fallback window is NOT automatically ended allowing it to always be able to receive commands without crashing) - if (!window->IsFallbackWindow && ((g.IO.ConfigDebugBeginReturnValueOnce && window_just_created) || (g.IO.ConfigDebugBeginReturnValueLoop && g.DebugBeginReturnValueCullDepth == g.CurrentWindowStack.Size))) - { - if (window->AutoFitFramesX > 0) { window->AutoFitFramesX++; } - if (window->AutoFitFramesY > 0) { window->AutoFitFramesY++; } - return false; - } - - return !window->SkipItems; -} - -void ImGui::End() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - - // Error checking: verify that user hasn't called End() too many times! - if (g.CurrentWindowStack.Size <= 1 && g.WithinFrameScopeWithImplicitWindow) - { - IM_ASSERT_USER_ERROR(g.CurrentWindowStack.Size > 1, "Calling End() too many times!"); - return; - } - IM_ASSERT(g.CurrentWindowStack.Size > 0); - - // Error checking: verify that user doesn't directly call End() on a child window. - if ((window->Flags & ImGuiWindowFlags_ChildWindow) && !(window->Flags & ImGuiWindowFlags_DockNodeHost) && !window->DockIsActive) - IM_ASSERT_USER_ERROR(g.WithinEndChild, "Must call EndChild() and not End()!"); - - // Close anything that is open - if (window->DC.CurrentColumns) - EndColumns(); - if (!(window->Flags & ImGuiWindowFlags_DockNodeHost)) // Pop inner window clip rectangle - PopClipRect(); - PopFocusScope(); - - // Stop logging - if (!(window->Flags & ImGuiWindowFlags_ChildWindow)) // FIXME: add more options for scope of logging - LogFinish(); - - if (window->DC.IsSetPos) - ErrorCheckUsingSetCursorPosToExtendParentBoundaries(); - - // Docking: report contents sizes to parent to allow for auto-resize - if (window->DockNode && window->DockTabIsVisible) - if (ImGuiWindow* host_window = window->DockNode->HostWindow) // FIXME-DOCK - host_window->DC.CursorMaxPos = window->DC.CursorMaxPos + window->WindowPadding - host_window->WindowPadding; - - // Pop from window stack - g.LastItemData = g.CurrentWindowStack.back().ParentLastItemDataBackup; - if (window->Flags & ImGuiWindowFlags_ChildMenu) - g.BeginMenuCount--; - if (window->Flags & ImGuiWindowFlags_Popup) - g.BeginPopupStack.pop_back(); - g.CurrentWindowStack.back().StackSizesOnBegin.CompareWithContextState(&g); - g.CurrentWindowStack.pop_back(); - SetCurrentWindow(g.CurrentWindowStack.Size == 0 ? NULL : g.CurrentWindowStack.back().Window); - if (g.CurrentWindow) - SetCurrentViewport(g.CurrentWindow, g.CurrentWindow->Viewport); -} - -void ImGui::BringWindowToFocusFront(ImGuiWindow* window) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(window == window->RootWindow); - - const int cur_order = window->FocusOrder; - IM_ASSERT(g.WindowsFocusOrder[cur_order] == window); - if (g.WindowsFocusOrder.back() == window) - return; - - const int new_order = g.WindowsFocusOrder.Size - 1; - for (int n = cur_order; n < new_order; n++) - { - g.WindowsFocusOrder[n] = g.WindowsFocusOrder[n + 1]; - g.WindowsFocusOrder[n]->FocusOrder--; - IM_ASSERT(g.WindowsFocusOrder[n]->FocusOrder == n); - } - g.WindowsFocusOrder[new_order] = window; - window->FocusOrder = (short)new_order; -} - -void ImGui::BringWindowToDisplayFront(ImGuiWindow* window) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* current_front_window = g.Windows.back(); - if (current_front_window == window || current_front_window->RootWindowDockTree == window) // Cheap early out (could be better) - return; - for (int i = g.Windows.Size - 2; i >= 0; i--) // We can ignore the top-most window - if (g.Windows[i] == window) - { - memmove(&g.Windows[i], &g.Windows[i + 1], (size_t)(g.Windows.Size - i - 1) * sizeof(ImGuiWindow*)); - g.Windows[g.Windows.Size - 1] = window; - break; - } -} - -void ImGui::BringWindowToDisplayBack(ImGuiWindow* window) -{ - ImGuiContext& g = *GImGui; - if (g.Windows[0] == window) - return; - for (int i = 0; i < g.Windows.Size; i++) - if (g.Windows[i] == window) - { - memmove(&g.Windows[1], &g.Windows[0], (size_t)i * sizeof(ImGuiWindow*)); - g.Windows[0] = window; - break; - } -} - -void ImGui::BringWindowToDisplayBehind(ImGuiWindow* window, ImGuiWindow* behind_window) -{ - IM_ASSERT(window != NULL && behind_window != NULL); - ImGuiContext& g = *GImGui; - window = window->RootWindow; - behind_window = behind_window->RootWindow; - int pos_wnd = FindWindowDisplayIndex(window); - int pos_beh = FindWindowDisplayIndex(behind_window); - if (pos_wnd < pos_beh) - { - size_t copy_bytes = (pos_beh - pos_wnd - 1) * sizeof(ImGuiWindow*); - memmove(&g.Windows.Data[pos_wnd], &g.Windows.Data[pos_wnd + 1], copy_bytes); - g.Windows[pos_beh - 1] = window; - } - else - { - size_t copy_bytes = (pos_wnd - pos_beh) * sizeof(ImGuiWindow*); - memmove(&g.Windows.Data[pos_beh + 1], &g.Windows.Data[pos_beh], copy_bytes); - g.Windows[pos_beh] = window; - } -} - -int ImGui::FindWindowDisplayIndex(ImGuiWindow* window) -{ - ImGuiContext& g = *GImGui; - return g.Windows.index_from_ptr(g.Windows.find(window)); -} - -// Moving window to front of display and set focus (which happens to be back of our sorted list) -void ImGui::FocusWindow(ImGuiWindow* window, ImGuiFocusRequestFlags flags) -{ - ImGuiContext& g = *GImGui; - - // Modal check? - if ((flags & ImGuiFocusRequestFlags_UnlessBelowModal) && (g.NavWindow != window)) // Early out in common case. - if (ImGuiWindow* blocking_modal = FindBlockingModal(window)) - { - IMGUI_DEBUG_LOG_FOCUS("[focus] FocusWindow(\"%s\", UnlessBelowModal): prevented by \"%s\".\n", window ? window->Name : "", blocking_modal->Name); - if (window && window == window->RootWindow && (window->Flags & ImGuiWindowFlags_NoBringToFrontOnFocus) == 0) - BringWindowToDisplayBehind(window, blocking_modal); // Still bring to right below modal. - return; - } - - // Find last focused child (if any) and focus it instead. - if ((flags & ImGuiFocusRequestFlags_RestoreFocusedChild) && window != NULL) - window = NavRestoreLastChildNavWindow(window); - - // Apply focus - if (g.NavWindow != window) - { - SetNavWindow(window); - if (window && g.NavDisableMouseHover) - g.NavMousePosDirty = true; - g.NavId = window ? window->NavLastIds[0] : 0; // Restore NavId - g.NavLayer = ImGuiNavLayer_Main; - g.NavFocusScopeId = window ? window->NavRootFocusScopeId : 0; - g.NavIdIsAlive = false; - g.NavLastValidSelectionUserData = ImGuiSelectionUserData_Invalid; - - // Close popups if any - ClosePopupsOverWindow(window, false); - } - - // Move the root window to the top of the pile - IM_ASSERT(window == NULL || window->RootWindowDockTree != NULL); - ImGuiWindow* focus_front_window = window ? window->RootWindow : NULL; - ImGuiWindow* display_front_window = window ? window->RootWindowDockTree : NULL; - ImGuiDockNode* dock_node = window ? window->DockNode : NULL; - bool active_id_window_is_dock_node_host = (g.ActiveIdWindow && dock_node && dock_node->HostWindow == g.ActiveIdWindow); - - // Steal active widgets. Some of the cases it triggers includes: - // - Focus a window while an InputText in another window is active, if focus happens before the old InputText can run. - // - When using Nav to activate menu items (due to timing of activating on press->new window appears->losing ActiveId) - // - Using dock host items (tab, collapse button) can trigger this before we redirect the ActiveIdWindow toward the child window. - if (g.ActiveId != 0 && g.ActiveIdWindow && g.ActiveIdWindow->RootWindow != focus_front_window) - if (!g.ActiveIdNoClearOnFocusLoss && !active_id_window_is_dock_node_host) - ClearActiveID(); - - // Passing NULL allow to disable keyboard focus - if (!window) - return; - window->LastFrameJustFocused = g.FrameCount; - - // Select in dock node - // For #2304 we avoid applying focus immediately before the tabbar is visible. - //if (dock_node && dock_node->TabBar) - // dock_node->TabBar->SelectedTabId = dock_node->TabBar->NextSelectedTabId = window->TabId; - - // Bring to front - BringWindowToFocusFront(focus_front_window); - if (((window->Flags | focus_front_window->Flags | display_front_window->Flags) & ImGuiWindowFlags_NoBringToFrontOnFocus) == 0) - BringWindowToDisplayFront(display_front_window); -} - -void ImGui::FocusTopMostWindowUnderOne(ImGuiWindow* under_this_window, ImGuiWindow* ignore_window, ImGuiViewport* filter_viewport, ImGuiFocusRequestFlags flags) -{ - ImGuiContext& g = *GImGui; - int start_idx = g.WindowsFocusOrder.Size - 1; - if (under_this_window != NULL) - { - // Aim at root window behind us, if we are in a child window that's our own root (see #4640) - int offset = -1; - while (under_this_window->Flags & ImGuiWindowFlags_ChildWindow) - { - under_this_window = under_this_window->ParentWindow; - offset = 0; - } - start_idx = FindWindowFocusIndex(under_this_window) + offset; - } - for (int i = start_idx; i >= 0; i--) - { - // We may later decide to test for different NoXXXInputs based on the active navigation input (mouse vs nav) but that may feel more confusing to the user. - ImGuiWindow* window = g.WindowsFocusOrder[i]; - if (window == ignore_window || !window->WasActive) - continue; - if (filter_viewport != NULL && window->Viewport != filter_viewport) - continue; - if ((window->Flags & (ImGuiWindowFlags_NoMouseInputs | ImGuiWindowFlags_NoNavInputs)) != (ImGuiWindowFlags_NoMouseInputs | ImGuiWindowFlags_NoNavInputs)) - { - // FIXME-DOCK: When ImGuiFocusRequestFlags_RestoreFocusedChild is set... - // This is failing (lagging by one frame) for docked windows. - // If A and B are docked into window and B disappear, at the NewFrame() call site window->NavLastChildNavWindow will still point to B. - // We might leverage the tab order implicitly stored in window->DockNodeAsHost->TabBar (essentially the 'most_recently_selected_tab' code in tab bar will do that but on next update) - // to tell which is the "previous" window. Or we may leverage 'LastFrameFocused/LastFrameJustFocused' and have this function handle child window itself? - FocusWindow(window, flags); - return; - } - } - FocusWindow(NULL, flags); -} - -// Important: this alone doesn't alter current ImDrawList state. This is called by PushFont/PopFont only. -void ImGui::SetCurrentFont(ImFont* font) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(font && font->IsLoaded()); // Font Atlas not created. Did you call io.Fonts->GetTexDataAsRGBA32 / GetTexDataAsAlpha8 ? - IM_ASSERT(font->Scale > 0.0f); - g.Font = font; - g.FontBaseSize = ImMax(1.0f, g.IO.FontGlobalScale * g.Font->FontSize * g.Font->Scale); - g.FontSize = g.CurrentWindow ? g.CurrentWindow->CalcFontSize() : 0.0f; - - ImFontAtlas* atlas = g.Font->ContainerAtlas; - g.DrawListSharedData.TexUvWhitePixel = atlas->TexUvWhitePixel; - g.DrawListSharedData.TexUvLines = atlas->TexUvLines; - g.DrawListSharedData.Font = g.Font; - g.DrawListSharedData.FontSize = g.FontSize; -} - -void ImGui::PushFont(ImFont* font) -{ - ImGuiContext& g = *GImGui; - if (!font) - font = GetDefaultFont(); - SetCurrentFont(font); - g.FontStack.push_back(font); - g.CurrentWindow->DrawList->PushTextureID(font->ContainerAtlas->TexID); -} - -void ImGui::PopFont() -{ - ImGuiContext& g = *GImGui; - g.CurrentWindow->DrawList->PopTextureID(); - g.FontStack.pop_back(); - SetCurrentFont(g.FontStack.empty() ? GetDefaultFont() : g.FontStack.back()); -} - -void ImGui::PushItemFlag(ImGuiItemFlags option, bool enabled) -{ - ImGuiContext& g = *GImGui; - ImGuiItemFlags item_flags = g.CurrentItemFlags; - IM_ASSERT(item_flags == g.ItemFlagsStack.back()); - if (enabled) - item_flags |= option; - else - item_flags &= ~option; - g.CurrentItemFlags = item_flags; - g.ItemFlagsStack.push_back(item_flags); -} - -void ImGui::PopItemFlag() -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(g.ItemFlagsStack.Size > 1); // Too many calls to PopItemFlag() - we always leave a 0 at the bottom of the stack. - g.ItemFlagsStack.pop_back(); - g.CurrentItemFlags = g.ItemFlagsStack.back(); -} - -// BeginDisabled()/EndDisabled() -// - Those can be nested but it cannot be used to enable an already disabled section (a single BeginDisabled(true) in the stack is enough to keep everything disabled) -// - Visually this is currently altering alpha, but it is expected that in a future styling system this would work differently. -// - Feedback welcome at https://github.com/ocornut/imgui/issues/211 -// - BeginDisabled(false) essentially does nothing useful but is provided to facilitate use of boolean expressions. If you can avoid calling BeginDisabled(False)/EndDisabled() best to avoid it. -// - Optimized shortcuts instead of PushStyleVar() + PushItemFlag() -void ImGui::BeginDisabled(bool disabled) -{ - ImGuiContext& g = *GImGui; - bool was_disabled = (g.CurrentItemFlags & ImGuiItemFlags_Disabled) != 0; - if (!was_disabled && disabled) - { - g.DisabledAlphaBackup = g.Style.Alpha; - g.Style.Alpha *= g.Style.DisabledAlpha; // PushStyleVar(ImGuiStyleVar_Alpha, g.Style.Alpha * g.Style.DisabledAlpha); - } - if (was_disabled || disabled) - g.CurrentItemFlags |= ImGuiItemFlags_Disabled; - g.ItemFlagsStack.push_back(g.CurrentItemFlags); - g.DisabledStackSize++; -} - -void ImGui::EndDisabled() -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(g.DisabledStackSize > 0); - g.DisabledStackSize--; - bool was_disabled = (g.CurrentItemFlags & ImGuiItemFlags_Disabled) != 0; - //PopItemFlag(); - g.ItemFlagsStack.pop_back(); - g.CurrentItemFlags = g.ItemFlagsStack.back(); - if (was_disabled && (g.CurrentItemFlags & ImGuiItemFlags_Disabled) == 0) - g.Style.Alpha = g.DisabledAlphaBackup; //PopStyleVar(); -} - -void ImGui::PushTabStop(bool tab_stop) -{ - PushItemFlag(ImGuiItemFlags_NoTabStop, !tab_stop); -} - -void ImGui::PopTabStop() -{ - PopItemFlag(); -} - -void ImGui::PushButtonRepeat(bool repeat) -{ - PushItemFlag(ImGuiItemFlags_ButtonRepeat, repeat); -} - -void ImGui::PopButtonRepeat() -{ - PopItemFlag(); -} - -void ImGui::PushTextWrapPos(float wrap_pos_x) -{ - ImGuiWindow* window = GetCurrentWindow(); - window->DC.TextWrapPosStack.push_back(window->DC.TextWrapPos); - window->DC.TextWrapPos = wrap_pos_x; -} - -void ImGui::PopTextWrapPos() -{ - ImGuiWindow* window = GetCurrentWindow(); - window->DC.TextWrapPos = window->DC.TextWrapPosStack.back(); - window->DC.TextWrapPosStack.pop_back(); -} - -static ImGuiWindow* GetCombinedRootWindow(ImGuiWindow* window, bool popup_hierarchy, bool dock_hierarchy) -{ - ImGuiWindow* last_window = NULL; - while (last_window != window) - { - last_window = window; - window = window->RootWindow; - if (popup_hierarchy) - window = window->RootWindowPopupTree; - if (dock_hierarchy) - window = window->RootWindowDockTree; - } - return window; -} - -bool ImGui::IsWindowChildOf(ImGuiWindow* window, ImGuiWindow* potential_parent, bool popup_hierarchy, bool dock_hierarchy) -{ - ImGuiWindow* window_root = GetCombinedRootWindow(window, popup_hierarchy, dock_hierarchy); - if (window_root == potential_parent) - return true; - while (window != NULL) - { - if (window == potential_parent) - return true; - if (window == window_root) // end of chain - return false; - window = window->ParentWindow; - } - return false; -} - -bool ImGui::IsWindowWithinBeginStackOf(ImGuiWindow* window, ImGuiWindow* potential_parent) -{ - if (window->RootWindow == potential_parent) - return true; - while (window != NULL) - { - if (window == potential_parent) - return true; - window = window->ParentWindowInBeginStack; - } - return false; -} - -bool ImGui::IsWindowAbove(ImGuiWindow* potential_above, ImGuiWindow* potential_below) -{ - ImGuiContext& g = *GImGui; - - // It would be saner to ensure that display layer is always reflected in the g.Windows[] order, which would likely requires altering all manipulations of that array - const int display_layer_delta = GetWindowDisplayLayer(potential_above) - GetWindowDisplayLayer(potential_below); - if (display_layer_delta != 0) - return display_layer_delta > 0; - - for (int i = g.Windows.Size - 1; i >= 0; i--) - { - ImGuiWindow* candidate_window = g.Windows[i]; - if (candidate_window == potential_above) - return true; - if (candidate_window == potential_below) - return false; - } - return false; -} - -bool ImGui::IsWindowHovered(ImGuiHoveredFlags flags) -{ - IM_ASSERT((flags & ~ImGuiHoveredFlags_AllowedMaskForIsWindowHovered) == 0 && "Invalid flags for IsWindowHovered()!"); - - ImGuiContext& g = *GImGui; - ImGuiWindow* ref_window = g.HoveredWindow; - ImGuiWindow* cur_window = g.CurrentWindow; - if (ref_window == NULL) - return false; - - if ((flags & ImGuiHoveredFlags_AnyWindow) == 0) - { - IM_ASSERT(cur_window); // Not inside a Begin()/End() - const bool popup_hierarchy = (flags & ImGuiHoveredFlags_NoPopupHierarchy) == 0; - const bool dock_hierarchy = (flags & ImGuiHoveredFlags_DockHierarchy) != 0; - if (flags & ImGuiHoveredFlags_RootWindow) - cur_window = GetCombinedRootWindow(cur_window, popup_hierarchy, dock_hierarchy); - - bool result; - if (flags & ImGuiHoveredFlags_ChildWindows) - result = IsWindowChildOf(ref_window, cur_window, popup_hierarchy, dock_hierarchy); - else - result = (ref_window == cur_window); - if (!result) - return false; - } - - if (!IsWindowContentHoverable(ref_window, flags)) - return false; - if (!(flags & ImGuiHoveredFlags_AllowWhenBlockedByActiveItem)) - if (g.ActiveId != 0 && !g.ActiveIdAllowOverlap && g.ActiveId != ref_window->MoveId) - return false; - - // When changing hovered window we requires a bit of stationary delay before activating hover timer. - // FIXME: We don't support delay other than stationary one for now, other delay would need a way - // to fullfill the possibility that multiple IsWindowHovered() with varying flag could return true - // for different windows of the hierarchy. Possibly need a Hash(Current+Flags) ==> (Timer) cache. - // We can implement this for _Stationary because the data is linked to HoveredWindow rather than CurrentWindow. - if (flags & ImGuiHoveredFlags_ForTooltip) - flags |= g.Style.HoverFlagsForTooltipMouse; - if ((flags & ImGuiHoveredFlags_Stationary) != 0 && g.HoverWindowUnlockedStationaryId != ref_window->ID) - return false; - - return true; -} - -bool ImGui::IsWindowFocused(ImGuiFocusedFlags flags) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* ref_window = g.NavWindow; - ImGuiWindow* cur_window = g.CurrentWindow; - - if (ref_window == NULL) - return false; - if (flags & ImGuiFocusedFlags_AnyWindow) - return true; - - IM_ASSERT(cur_window); // Not inside a Begin()/End() - const bool popup_hierarchy = (flags & ImGuiFocusedFlags_NoPopupHierarchy) == 0; - const bool dock_hierarchy = (flags & ImGuiFocusedFlags_DockHierarchy) != 0; - if (flags & ImGuiHoveredFlags_RootWindow) - cur_window = GetCombinedRootWindow(cur_window, popup_hierarchy, dock_hierarchy); - - if (flags & ImGuiHoveredFlags_ChildWindows) - return IsWindowChildOf(ref_window, cur_window, popup_hierarchy, dock_hierarchy); - else - return (ref_window == cur_window); -} - -ImGuiID ImGui::GetWindowDockID() -{ - ImGuiContext& g = *GImGui; - return g.CurrentWindow->DockId; -} - -bool ImGui::IsWindowDocked() -{ - ImGuiContext& g = *GImGui; - return g.CurrentWindow->DockIsActive; -} - -// Can we focus this window with CTRL+TAB (or PadMenu + PadFocusPrev/PadFocusNext) -// Note that NoNavFocus makes the window not reachable with CTRL+TAB but it can still be focused with mouse or programmatically. -// If you want a window to never be focused, you may use the e.g. NoInputs flag. -bool ImGui::IsWindowNavFocusable(ImGuiWindow* window) -{ - return window->WasActive && window == window->RootWindow && !(window->Flags & ImGuiWindowFlags_NoNavFocus); -} - -float ImGui::GetWindowWidth() -{ - ImGuiWindow* window = GImGui->CurrentWindow; - return window->Size.x; -} - -float ImGui::GetWindowHeight() -{ - ImGuiWindow* window = GImGui->CurrentWindow; - return window->Size.y; -} - -ImVec2 ImGui::GetWindowPos() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - return window->Pos; -} - -void ImGui::SetWindowPos(ImGuiWindow* window, const ImVec2& pos, ImGuiCond cond) -{ - // Test condition (NB: bit 0 is always true) and clear flags for next time - if (cond && (window->SetWindowPosAllowFlags & cond) == 0) - return; - - IM_ASSERT(cond == 0 || ImIsPowerOfTwo(cond)); // Make sure the user doesn't attempt to combine multiple condition flags. - window->SetWindowPosAllowFlags &= ~(ImGuiCond_Once | ImGuiCond_FirstUseEver | ImGuiCond_Appearing); - window->SetWindowPosVal = ImVec2(FLT_MAX, FLT_MAX); - - // Set - const ImVec2 old_pos = window->Pos; - window->Pos = ImTrunc(pos); - ImVec2 offset = window->Pos - old_pos; - if (offset.x == 0.0f && offset.y == 0.0f) - return; - MarkIniSettingsDirty(window); - // FIXME: share code with TranslateWindow(), need to confirm whether the 3 rect modified by TranslateWindow() are desirable here. - window->DC.CursorPos += offset; // As we happen to move the window while it is being appended to (which is a bad idea - will smear) let's at least offset the cursor - window->DC.CursorMaxPos += offset; // And more importantly we need to offset CursorMaxPos/CursorStartPos this so ContentSize calculation doesn't get affected. - window->DC.IdealMaxPos += offset; - window->DC.CursorStartPos += offset; -} - -void ImGui::SetWindowPos(const ImVec2& pos, ImGuiCond cond) -{ - ImGuiWindow* window = GetCurrentWindowRead(); - SetWindowPos(window, pos, cond); -} - -void ImGui::SetWindowPos(const char* name, const ImVec2& pos, ImGuiCond cond) -{ - if (ImGuiWindow* window = FindWindowByName(name)) - SetWindowPos(window, pos, cond); -} - -ImVec2 ImGui::GetWindowSize() -{ - ImGuiWindow* window = GetCurrentWindowRead(); - return window->Size; -} - -void ImGui::SetWindowSize(ImGuiWindow* window, const ImVec2& size, ImGuiCond cond) -{ - // Test condition (NB: bit 0 is always true) and clear flags for next time - if (cond && (window->SetWindowSizeAllowFlags & cond) == 0) - return; - - IM_ASSERT(cond == 0 || ImIsPowerOfTwo(cond)); // Make sure the user doesn't attempt to combine multiple condition flags. - window->SetWindowSizeAllowFlags &= ~(ImGuiCond_Once | ImGuiCond_FirstUseEver | ImGuiCond_Appearing); - - // Set - ImVec2 old_size = window->SizeFull; - window->AutoFitFramesX = (size.x <= 0.0f) ? 2 : 0; - window->AutoFitFramesY = (size.y <= 0.0f) ? 2 : 0; - if (size.x <= 0.0f) - window->AutoFitOnlyGrows = false; - else - window->SizeFull.x = IM_TRUNC(size.x); - if (size.y <= 0.0f) - window->AutoFitOnlyGrows = false; - else - window->SizeFull.y = IM_TRUNC(size.y); - if (old_size.x != window->SizeFull.x || old_size.y != window->SizeFull.y) - MarkIniSettingsDirty(window); -} - -void ImGui::SetWindowSize(const ImVec2& size, ImGuiCond cond) -{ - SetWindowSize(GImGui->CurrentWindow, size, cond); -} - -void ImGui::SetWindowSize(const char* name, const ImVec2& size, ImGuiCond cond) -{ - if (ImGuiWindow* window = FindWindowByName(name)) - SetWindowSize(window, size, cond); -} - -void ImGui::SetWindowCollapsed(ImGuiWindow* window, bool collapsed, ImGuiCond cond) -{ - // Test condition (NB: bit 0 is always true) and clear flags for next time - if (cond && (window->SetWindowCollapsedAllowFlags & cond) == 0) - return; - window->SetWindowCollapsedAllowFlags &= ~(ImGuiCond_Once | ImGuiCond_FirstUseEver | ImGuiCond_Appearing); - - // Set - window->Collapsed = collapsed; -} - -void ImGui::SetWindowHitTestHole(ImGuiWindow* window, const ImVec2& pos, const ImVec2& size) -{ - IM_ASSERT(window->HitTestHoleSize.x == 0); // We don't support multiple holes/hit test filters - window->HitTestHoleSize = ImVec2ih(size); - window->HitTestHoleOffset = ImVec2ih(pos - window->Pos); -} - -void ImGui::SetWindowHiddendAndSkipItemsForCurrentFrame(ImGuiWindow* window) -{ - window->Hidden = window->SkipItems = true; - window->HiddenFramesCanSkipItems = 1; -} - -void ImGui::SetWindowCollapsed(bool collapsed, ImGuiCond cond) -{ - SetWindowCollapsed(GImGui->CurrentWindow, collapsed, cond); -} - -bool ImGui::IsWindowCollapsed() -{ - ImGuiWindow* window = GetCurrentWindowRead(); - return window->Collapsed; -} - -bool ImGui::IsWindowAppearing() -{ - ImGuiWindow* window = GetCurrentWindowRead(); - return window->Appearing; -} - -void ImGui::SetWindowCollapsed(const char* name, bool collapsed, ImGuiCond cond) -{ - if (ImGuiWindow* window = FindWindowByName(name)) - SetWindowCollapsed(window, collapsed, cond); -} - -void ImGui::SetWindowFocus() -{ - FocusWindow(GImGui->CurrentWindow); -} - -void ImGui::SetWindowFocus(const char* name) -{ - if (name) - { - if (ImGuiWindow* window = FindWindowByName(name)) - FocusWindow(window); - } - else - { - FocusWindow(NULL); - } -} - -void ImGui::SetNextWindowPos(const ImVec2& pos, ImGuiCond cond, const ImVec2& pivot) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(cond == 0 || ImIsPowerOfTwo(cond)); // Make sure the user doesn't attempt to combine multiple condition flags. - g.NextWindowData.Flags |= ImGuiNextWindowDataFlags_HasPos; - g.NextWindowData.PosVal = pos; - g.NextWindowData.PosPivotVal = pivot; - g.NextWindowData.PosCond = cond ? cond : ImGuiCond_Always; - g.NextWindowData.PosUndock = true; -} - -void ImGui::SetNextWindowSize(const ImVec2& size, ImGuiCond cond) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(cond == 0 || ImIsPowerOfTwo(cond)); // Make sure the user doesn't attempt to combine multiple condition flags. - g.NextWindowData.Flags |= ImGuiNextWindowDataFlags_HasSize; - g.NextWindowData.SizeVal = size; - g.NextWindowData.SizeCond = cond ? cond : ImGuiCond_Always; -} - -void ImGui::SetNextWindowSizeConstraints(const ImVec2& size_min, const ImVec2& size_max, ImGuiSizeCallback custom_callback, void* custom_callback_user_data) -{ - ImGuiContext& g = *GImGui; - g.NextWindowData.Flags |= ImGuiNextWindowDataFlags_HasSizeConstraint; - g.NextWindowData.SizeConstraintRect = ImRect(size_min, size_max); - g.NextWindowData.SizeCallback = custom_callback; - g.NextWindowData.SizeCallbackUserData = custom_callback_user_data; -} - -// Content size = inner scrollable rectangle, padded with WindowPadding. -// SetNextWindowContentSize(ImVec2(100,100) + ImGuiWindowFlags_AlwaysAutoResize will always allow submitting a 100x100 item. -void ImGui::SetNextWindowContentSize(const ImVec2& size) -{ - ImGuiContext& g = *GImGui; - g.NextWindowData.Flags |= ImGuiNextWindowDataFlags_HasContentSize; - g.NextWindowData.ContentSizeVal = ImTrunc(size); -} - -void ImGui::SetNextWindowScroll(const ImVec2& scroll) -{ - ImGuiContext& g = *GImGui; - g.NextWindowData.Flags |= ImGuiNextWindowDataFlags_HasScroll; - g.NextWindowData.ScrollVal = scroll; -} - -void ImGui::SetNextWindowCollapsed(bool collapsed, ImGuiCond cond) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(cond == 0 || ImIsPowerOfTwo(cond)); // Make sure the user doesn't attempt to combine multiple condition flags. - g.NextWindowData.Flags |= ImGuiNextWindowDataFlags_HasCollapsed; - g.NextWindowData.CollapsedVal = collapsed; - g.NextWindowData.CollapsedCond = cond ? cond : ImGuiCond_Always; -} - -void ImGui::SetNextWindowFocus() -{ - ImGuiContext& g = *GImGui; - g.NextWindowData.Flags |= ImGuiNextWindowDataFlags_HasFocus; -} - -void ImGui::SetNextWindowBgAlpha(float alpha) -{ - ImGuiContext& g = *GImGui; - g.NextWindowData.Flags |= ImGuiNextWindowDataFlags_HasBgAlpha; - g.NextWindowData.BgAlphaVal = alpha; -} - -void ImGui::SetNextWindowViewport(ImGuiID id) -{ - ImGuiContext& g = *GImGui; - g.NextWindowData.Flags |= ImGuiNextWindowDataFlags_HasViewport; - g.NextWindowData.ViewportId = id; -} - -void ImGui::SetNextWindowDockID(ImGuiID id, ImGuiCond cond) -{ - ImGuiContext& g = *GImGui; - g.NextWindowData.Flags |= ImGuiNextWindowDataFlags_HasDock; - g.NextWindowData.DockCond = cond ? cond : ImGuiCond_Always; - g.NextWindowData.DockId = id; -} - -void ImGui::SetNextWindowClass(const ImGuiWindowClass* window_class) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT((window_class->ViewportFlagsOverrideSet & window_class->ViewportFlagsOverrideClear) == 0); // Cannot set both set and clear for the same bit - g.NextWindowData.Flags |= ImGuiNextWindowDataFlags_HasWindowClass; - g.NextWindowData.WindowClass = *window_class; -} - -ImDrawList* ImGui::GetWindowDrawList() -{ - ImGuiWindow* window = GetCurrentWindow(); - return window->DrawList; -} - -float ImGui::GetWindowDpiScale() -{ - ImGuiContext& g = *GImGui; - return g.CurrentDpiScale; -} - -ImGuiViewport* ImGui::GetWindowViewport() -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(g.CurrentViewport != NULL && g.CurrentViewport == g.CurrentWindow->Viewport); - return g.CurrentViewport; -} - -ImFont* ImGui::GetFont() -{ - return GImGui->Font; -} - -float ImGui::GetFontSize() -{ - return GImGui->FontSize; -} - -ImVec2 ImGui::GetFontTexUvWhitePixel() -{ - return GImGui->DrawListSharedData.TexUvWhitePixel; -} - -void ImGui::SetWindowFontScale(float scale) -{ - IM_ASSERT(scale > 0.0f); - ImGuiContext& g = *GImGui; - ImGuiWindow* window = GetCurrentWindow(); - window->FontWindowScale = scale; - g.FontSize = g.DrawListSharedData.FontSize = window->CalcFontSize(); -} - -void ImGui::PushFocusScope(ImGuiID id) -{ - ImGuiContext& g = *GImGui; - g.FocusScopeStack.push_back(id); - g.CurrentFocusScopeId = id; -} - -void ImGui::PopFocusScope() -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(g.FocusScopeStack.Size > 0); // Too many PopFocusScope() ? - g.FocusScopeStack.pop_back(); - g.CurrentFocusScopeId = g.FocusScopeStack.Size ? g.FocusScopeStack.back() : 0; -} - -// Focus = move navigation cursor, set scrolling, set focus window. -void ImGui::FocusItem() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - IMGUI_DEBUG_LOG_FOCUS("FocusItem(0x%08x) in window \"%s\"\n", g.LastItemData.ID, window->Name); - if (g.DragDropActive || g.MovingWindow != NULL) // FIXME: Opt-in flags for this? - { - IMGUI_DEBUG_LOG_FOCUS("FocusItem() ignored while DragDropActive!\n"); - return; - } - - ImGuiNavMoveFlags move_flags = ImGuiNavMoveFlags_IsTabbing | ImGuiNavMoveFlags_FocusApi | ImGuiNavMoveFlags_NoSetNavHighlight | ImGuiNavMoveFlags_NoSelect; - ImGuiScrollFlags scroll_flags = window->Appearing ? ImGuiScrollFlags_KeepVisibleEdgeX | ImGuiScrollFlags_AlwaysCenterY : ImGuiScrollFlags_KeepVisibleEdgeX | ImGuiScrollFlags_KeepVisibleEdgeY; - SetNavWindow(window); - NavMoveRequestSubmit(ImGuiDir_None, ImGuiDir_Up, move_flags, scroll_flags); - NavMoveRequestResolveWithLastItem(&g.NavMoveResultLocal); -} - -void ImGui::ActivateItemByID(ImGuiID id) -{ - ImGuiContext& g = *GImGui; - g.NavNextActivateId = id; - g.NavNextActivateFlags = ImGuiActivateFlags_None; -} - -// Note: this will likely be called ActivateItem() once we rework our Focus/Activation system! -// But ActivateItem() should function without altering scroll/focus? -void ImGui::SetKeyboardFocusHere(int offset) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - IM_ASSERT(offset >= -1); // -1 is allowed but not below - IMGUI_DEBUG_LOG_FOCUS("SetKeyboardFocusHere(%d) in window \"%s\"\n", offset, window->Name); - - // It makes sense in the vast majority of cases to never interrupt a drag and drop. - // When we refactor this function into ActivateItem() we may want to make this an option. - // MovingWindow is protected from most user inputs using SetActiveIdUsingNavAndKeys(), but - // is also automatically dropped in the event g.ActiveId is stolen. - if (g.DragDropActive || g.MovingWindow != NULL) - { - IMGUI_DEBUG_LOG_FOCUS("SetKeyboardFocusHere() ignored while DragDropActive!\n"); - return; - } - - SetNavWindow(window); - - ImGuiNavMoveFlags move_flags = ImGuiNavMoveFlags_IsTabbing | ImGuiNavMoveFlags_Activate | ImGuiNavMoveFlags_FocusApi | ImGuiNavMoveFlags_NoSetNavHighlight; - ImGuiScrollFlags scroll_flags = window->Appearing ? ImGuiScrollFlags_KeepVisibleEdgeX | ImGuiScrollFlags_AlwaysCenterY : ImGuiScrollFlags_KeepVisibleEdgeX | ImGuiScrollFlags_KeepVisibleEdgeY; - NavMoveRequestSubmit(ImGuiDir_None, offset < 0 ? ImGuiDir_Up : ImGuiDir_Down, move_flags, scroll_flags); // FIXME-NAV: Once we refactor tabbing, add LegacyApi flag to not activate non-inputable. - if (offset == -1) - { - NavMoveRequestResolveWithLastItem(&g.NavMoveResultLocal); - } - else - { - g.NavTabbingDir = 1; - g.NavTabbingCounter = offset + 1; - } -} - -void ImGui::SetItemDefaultFocus() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - if (!window->Appearing) - return; - if (g.NavWindow != window->RootWindowForNav || (!g.NavInitRequest && g.NavInitResult.ID == 0) || g.NavLayer != window->DC.NavLayerCurrent) - return; - - g.NavInitRequest = false; - NavApplyItemToResult(&g.NavInitResult); - NavUpdateAnyRequestFlag(); - - // Scroll could be done in NavInitRequestApplyResult() via an opt-in flag (we however don't want regular init requests to scroll) - if (!window->ClipRect.Contains(g.LastItemData.Rect)) - ScrollToRectEx(window, g.LastItemData.Rect, ImGuiScrollFlags_None); -} - -void ImGui::SetStateStorage(ImGuiStorage* tree) -{ - ImGuiWindow* window = GImGui->CurrentWindow; - window->DC.StateStorage = tree ? tree : &window->StateStorage; -} - -ImGuiStorage* ImGui::GetStateStorage() -{ - ImGuiWindow* window = GImGui->CurrentWindow; - return window->DC.StateStorage; -} - -void ImGui::PushID(const char* str_id) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - ImGuiID id = window->GetID(str_id); - window->IDStack.push_back(id); -} - -void ImGui::PushID(const char* str_id_begin, const char* str_id_end) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - ImGuiID id = window->GetID(str_id_begin, str_id_end); - window->IDStack.push_back(id); -} - -void ImGui::PushID(const void* ptr_id) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - ImGuiID id = window->GetID(ptr_id); - window->IDStack.push_back(id); -} - -void ImGui::PushID(int int_id) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - ImGuiID id = window->GetID(int_id); - window->IDStack.push_back(id); -} - -// Push a given id value ignoring the ID stack as a seed. -void ImGui::PushOverrideID(ImGuiID id) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - if (g.DebugHookIdInfo == id) - DebugHookIdInfo(id, ImGuiDataType_ID, NULL, NULL); - window->IDStack.push_back(id); -} - -// Helper to avoid a common series of PushOverrideID -> GetID() -> PopID() call -// (note that when using this pattern, ID Stack Tool will tend to not display the intermediate stack level. -// for that to work we would need to do PushOverrideID() -> ItemAdd() -> PopID() which would alter widget code a little more) -ImGuiID ImGui::GetIDWithSeed(const char* str, const char* str_end, ImGuiID seed) -{ - ImGuiID id = ImHashStr(str, str_end ? (str_end - str) : 0, seed); - ImGuiContext& g = *GImGui; - if (g.DebugHookIdInfo == id) - DebugHookIdInfo(id, ImGuiDataType_String, str, str_end); - return id; -} - -ImGuiID ImGui::GetIDWithSeed(int n, ImGuiID seed) -{ - ImGuiID id = ImHashData(&n, sizeof(n), seed); - ImGuiContext& g = *GImGui; - if (g.DebugHookIdInfo == id) - DebugHookIdInfo(id, ImGuiDataType_S32, (void*)(intptr_t)n, NULL); - return id; -} - -void ImGui::PopID() -{ - ImGuiWindow* window = GImGui->CurrentWindow; - IM_ASSERT(window->IDStack.Size > 1); // Too many PopID(), or could be popping in a wrong/different window? - window->IDStack.pop_back(); -} - -ImGuiID ImGui::GetID(const char* str_id) -{ - ImGuiWindow* window = GImGui->CurrentWindow; - return window->GetID(str_id); -} - -ImGuiID ImGui::GetID(const char* str_id_begin, const char* str_id_end) -{ - ImGuiWindow* window = GImGui->CurrentWindow; - return window->GetID(str_id_begin, str_id_end); -} - -ImGuiID ImGui::GetID(const void* ptr_id) -{ - ImGuiWindow* window = GImGui->CurrentWindow; - return window->GetID(ptr_id); -} - -bool ImGui::IsRectVisible(const ImVec2& size) -{ - ImGuiWindow* window = GImGui->CurrentWindow; - return window->ClipRect.Overlaps(ImRect(window->DC.CursorPos, window->DC.CursorPos + size)); -} - -bool ImGui::IsRectVisible(const ImVec2& rect_min, const ImVec2& rect_max) -{ - ImGuiWindow* window = GImGui->CurrentWindow; - return window->ClipRect.Overlaps(ImRect(rect_min, rect_max)); -} - - -//----------------------------------------------------------------------------- -// [SECTION] INPUTS -//----------------------------------------------------------------------------- -// - GetKeyData() [Internal] -// - GetKeyIndex() [Internal] -// - GetKeyName() -// - GetKeyChordName() [Internal] -// - CalcTypematicRepeatAmount() [Internal] -// - GetTypematicRepeatRate() [Internal] -// - GetKeyPressedAmount() [Internal] -// - GetKeyMagnitude2d() [Internal] -//----------------------------------------------------------------------------- -// - UpdateKeyRoutingTable() [Internal] -// - GetRoutingIdFromOwnerId() [Internal] -// - GetShortcutRoutingData() [Internal] -// - CalcRoutingScore() [Internal] -// - SetShortcutRouting() [Internal] -// - TestShortcutRouting() [Internal] -//----------------------------------------------------------------------------- -// - IsKeyDown() -// - IsKeyPressed() -// - IsKeyReleased() -//----------------------------------------------------------------------------- -// - IsMouseDown() -// - IsMouseClicked() -// - IsMouseReleased() -// - IsMouseDoubleClicked() -// - GetMouseClickedCount() -// - IsMouseHoveringRect() [Internal] -// - IsMouseDragPastThreshold() [Internal] -// - IsMouseDragging() -// - GetMousePos() -// - SetMousePos() [Internal] -// - GetMousePosOnOpeningCurrentPopup() -// - IsMousePosValid() -// - IsAnyMouseDown() -// - GetMouseDragDelta() -// - ResetMouseDragDelta() -// - GetMouseCursor() -// - SetMouseCursor() -//----------------------------------------------------------------------------- -// - UpdateAliasKey() -// - GetMergedModsFromKeys() -// - UpdateKeyboardInputs() -// - UpdateMouseInputs() -//----------------------------------------------------------------------------- -// - LockWheelingWindow [Internal] -// - FindBestWheelingWindow [Internal] -// - UpdateMouseWheel() [Internal] -//----------------------------------------------------------------------------- -// - SetNextFrameWantCaptureKeyboard() -// - SetNextFrameWantCaptureMouse() -//----------------------------------------------------------------------------- -// - GetInputSourceName() [Internal] -// - DebugPrintInputEvent() [Internal] -// - UpdateInputEvents() [Internal] -//----------------------------------------------------------------------------- -// - GetKeyOwner() [Internal] -// - TestKeyOwner() [Internal] -// - SetKeyOwner() [Internal] -// - SetItemKeyOwner() [Internal] -// - Shortcut() [Internal] -//----------------------------------------------------------------------------- - -ImGuiKeyData* ImGui::GetKeyData(ImGuiContext* ctx, ImGuiKey key) -{ - ImGuiContext& g = *ctx; - - // Special storage location for mods - if (key & ImGuiMod_Mask_) - key = ConvertSingleModFlagToKey(ctx, key); - -#ifndef IMGUI_DISABLE_OBSOLETE_KEYIO - IM_ASSERT(key >= ImGuiKey_LegacyNativeKey_BEGIN && key < ImGuiKey_NamedKey_END); - if (IsLegacyKey(key) && g.IO.KeyMap[key] != -1) - key = (ImGuiKey)g.IO.KeyMap[key]; // Remap native->imgui or imgui->native -#else - IM_ASSERT(IsNamedKey(key) && "Support for user key indices was dropped in favor of ImGuiKey. Please update backend & user code."); -#endif - return &g.IO.KeysData[key - ImGuiKey_KeysData_OFFSET]; -} - -#ifndef IMGUI_DISABLE_OBSOLETE_KEYIO -ImGuiKey ImGui::GetKeyIndex(ImGuiKey key) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(IsNamedKey(key)); - const ImGuiKeyData* key_data = GetKeyData(key); - return (ImGuiKey)(key_data - g.IO.KeysData); -} -#endif - -// Those names a provided for debugging purpose and are not meant to be saved persistently not compared. -static const char* const GKeyNames[] = -{ - "Tab", "LeftArrow", "RightArrow", "UpArrow", "DownArrow", "PageUp", "PageDown", - "Home", "End", "Insert", "Delete", "Backspace", "Space", "Enter", "Escape", - "LeftCtrl", "LeftShift", "LeftAlt", "LeftSuper", "RightCtrl", "RightShift", "RightAlt", "RightSuper", "Menu", - "0", "1", "2", "3", "4", "5", "6", "7", "8", "9", "A", "B", "C", "D", "E", "F", "G", "H", - "I", "J", "K", "L", "M", "N", "O", "P", "Q", "R", "S", "T", "U", "V", "W", "X", "Y", "Z", - "F1", "F2", "F3", "F4", "F5", "F6", "F7", "F8", "F9", "F10", "F11", "F12", - "F13", "F14", "F15", "F16", "F17", "F18", "F19", "F20", "F21", "F22", "F23", "F24", - "Apostrophe", "Comma", "Minus", "Period", "Slash", "Semicolon", "Equal", "LeftBracket", - "Backslash", "RightBracket", "GraveAccent", "CapsLock", "ScrollLock", "NumLock", "PrintScreen", - "Pause", "Keypad0", "Keypad1", "Keypad2", "Keypad3", "Keypad4", "Keypad5", "Keypad6", - "Keypad7", "Keypad8", "Keypad9", "KeypadDecimal", "KeypadDivide", "KeypadMultiply", - "KeypadSubtract", "KeypadAdd", "KeypadEnter", "KeypadEqual", - "AppBack", "AppForward", - "GamepadStart", "GamepadBack", - "GamepadFaceLeft", "GamepadFaceRight", "GamepadFaceUp", "GamepadFaceDown", - "GamepadDpadLeft", "GamepadDpadRight", "GamepadDpadUp", "GamepadDpadDown", - "GamepadL1", "GamepadR1", "GamepadL2", "GamepadR2", "GamepadL3", "GamepadR3", - "GamepadLStickLeft", "GamepadLStickRight", "GamepadLStickUp", "GamepadLStickDown", - "GamepadRStickLeft", "GamepadRStickRight", "GamepadRStickUp", "GamepadRStickDown", - "MouseLeft", "MouseRight", "MouseMiddle", "MouseX1", "MouseX2", "MouseWheelX", "MouseWheelY", - "ModCtrl", "ModShift", "ModAlt", "ModSuper", // ReservedForModXXX are showing the ModXXX names. -}; -IM_STATIC_ASSERT(ImGuiKey_NamedKey_COUNT == IM_ARRAYSIZE(GKeyNames)); - -const char* ImGui::GetKeyName(ImGuiKey key) -{ - ImGuiContext& g = *GImGui; -#ifdef IMGUI_DISABLE_OBSOLETE_KEYIO - IM_ASSERT((IsNamedKeyOrModKey(key) || key == ImGuiKey_None) && "Support for user key indices was dropped in favor of ImGuiKey. Please update backend and user code."); -#else - if (IsLegacyKey(key)) - { - if (g.IO.KeyMap[key] == -1) - return "N/A"; - IM_ASSERT(IsNamedKey((ImGuiKey)g.IO.KeyMap[key])); - key = (ImGuiKey)g.IO.KeyMap[key]; - } -#endif - if (key == ImGuiKey_None) - return "None"; - if (key & ImGuiMod_Mask_) - key = ConvertSingleModFlagToKey(&g, key); - if (!IsNamedKey(key)) - return "Unknown"; - - return GKeyNames[key - ImGuiKey_NamedKey_BEGIN]; -} - -// ImGuiMod_Shortcut is translated to either Ctrl or Super. -void ImGui::GetKeyChordName(ImGuiKeyChord key_chord, char* out_buf, int out_buf_size) -{ - ImGuiContext& g = *GImGui; - if (key_chord & ImGuiMod_Shortcut) - key_chord = ConvertShortcutMod(key_chord); - ImFormatString(out_buf, (size_t)out_buf_size, "%s%s%s%s%s", - (key_chord & ImGuiMod_Ctrl) ? "Ctrl+" : "", - (key_chord & ImGuiMod_Shift) ? "Shift+" : "", - (key_chord & ImGuiMod_Alt) ? "Alt+" : "", - (key_chord & ImGuiMod_Super) ? (g.IO.ConfigMacOSXBehaviors ? "Cmd+" : "Super+") : "", - GetKeyName((ImGuiKey)(key_chord & ~ImGuiMod_Mask_))); -} - -// t0 = previous time (e.g.: g.Time - g.IO.DeltaTime) -// t1 = current time (e.g.: g.Time) -// An event is triggered at: -// t = 0.0f t = repeat_delay, t = repeat_delay + repeat_rate*N -int ImGui::CalcTypematicRepeatAmount(float t0, float t1, float repeat_delay, float repeat_rate) -{ - if (t1 == 0.0f) - return 1; - if (t0 >= t1) - return 0; - if (repeat_rate <= 0.0f) - return (t0 < repeat_delay) && (t1 >= repeat_delay); - const int count_t0 = (t0 < repeat_delay) ? -1 : (int)((t0 - repeat_delay) / repeat_rate); - const int count_t1 = (t1 < repeat_delay) ? -1 : (int)((t1 - repeat_delay) / repeat_rate); - const int count = count_t1 - count_t0; - return count; -} - -void ImGui::GetTypematicRepeatRate(ImGuiInputFlags flags, float* repeat_delay, float* repeat_rate) -{ - ImGuiContext& g = *GImGui; - switch (flags & ImGuiInputFlags_RepeatRateMask_) - { - case ImGuiInputFlags_RepeatRateNavMove: *repeat_delay = g.IO.KeyRepeatDelay * 0.72f; *repeat_rate = g.IO.KeyRepeatRate * 0.80f; return; - case ImGuiInputFlags_RepeatRateNavTweak: *repeat_delay = g.IO.KeyRepeatDelay * 0.72f; *repeat_rate = g.IO.KeyRepeatRate * 0.30f; return; - case ImGuiInputFlags_RepeatRateDefault: default: *repeat_delay = g.IO.KeyRepeatDelay * 1.00f; *repeat_rate = g.IO.KeyRepeatRate * 1.00f; return; - } -} - -// Return value representing the number of presses in the last time period, for the given repeat rate -// (most often returns 0 or 1. The result is generally only >1 when RepeatRate is smaller than DeltaTime, aka large DeltaTime or fast RepeatRate) -int ImGui::GetKeyPressedAmount(ImGuiKey key, float repeat_delay, float repeat_rate) -{ - ImGuiContext& g = *GImGui; - const ImGuiKeyData* key_data = GetKeyData(key); - if (!key_data->Down) // In theory this should already be encoded as (DownDuration < 0.0f), but testing this facilitates eating mechanism (until we finish work on key ownership) - return 0; - const float t = key_data->DownDuration; - return CalcTypematicRepeatAmount(t - g.IO.DeltaTime, t, repeat_delay, repeat_rate); -} - -// Return 2D vector representing the combination of four cardinal direction, with analog value support (for e.g. ImGuiKey_GamepadLStick* values). -ImVec2 ImGui::GetKeyMagnitude2d(ImGuiKey key_left, ImGuiKey key_right, ImGuiKey key_up, ImGuiKey key_down) -{ - return ImVec2( - GetKeyData(key_right)->AnalogValue - GetKeyData(key_left)->AnalogValue, - GetKeyData(key_down)->AnalogValue - GetKeyData(key_up)->AnalogValue); -} - -// Rewrite routing data buffers to strip old entries + sort by key to make queries not touch scattered data. -// Entries D,A,B,B,A,C,B --> A,A,B,B,B,C,D -// Index A:1 B:2 C:5 D:0 --> A:0 B:2 C:5 D:6 -// See 'Metrics->Key Owners & Shortcut Routing' to visualize the result of that operation. -static void ImGui::UpdateKeyRoutingTable(ImGuiKeyRoutingTable* rt) -{ - ImGuiContext& g = *GImGui; - rt->EntriesNext.resize(0); - for (ImGuiKey key = ImGuiKey_NamedKey_BEGIN; key < ImGuiKey_NamedKey_END; key = (ImGuiKey)(key + 1)) - { - const int new_routing_start_idx = rt->EntriesNext.Size; - ImGuiKeyRoutingData* routing_entry; - for (int old_routing_idx = rt->Index[key - ImGuiKey_NamedKey_BEGIN]; old_routing_idx != -1; old_routing_idx = routing_entry->NextEntryIndex) - { - routing_entry = &rt->Entries[old_routing_idx]; - routing_entry->RoutingCurr = routing_entry->RoutingNext; // Update entry - routing_entry->RoutingNext = ImGuiKeyOwner_None; - routing_entry->RoutingNextScore = 255; - if (routing_entry->RoutingCurr == ImGuiKeyOwner_None) - continue; - rt->EntriesNext.push_back(*routing_entry); // Write alive ones into new buffer - - // Apply routing to owner if there's no owner already (RoutingCurr == None at this point) - if (routing_entry->Mods == g.IO.KeyMods) - { - ImGuiKeyOwnerData* owner_data = GetKeyOwnerData(&g, key); - if (owner_data->OwnerCurr == ImGuiKeyOwner_None) - owner_data->OwnerCurr = routing_entry->RoutingCurr; - } - } - - // Rewrite linked-list - rt->Index[key - ImGuiKey_NamedKey_BEGIN] = (ImGuiKeyRoutingIndex)(new_routing_start_idx < rt->EntriesNext.Size ? new_routing_start_idx : -1); - for (int n = new_routing_start_idx; n < rt->EntriesNext.Size; n++) - rt->EntriesNext[n].NextEntryIndex = (ImGuiKeyRoutingIndex)((n + 1 < rt->EntriesNext.Size) ? n + 1 : -1); - } - rt->Entries.swap(rt->EntriesNext); // Swap new and old indexes -} - -// owner_id may be None/Any, but routing_id needs to be always be set, so we default to GetCurrentFocusScope(). -static inline ImGuiID GetRoutingIdFromOwnerId(ImGuiID owner_id) -{ - ImGuiContext& g = *GImGui; - return (owner_id != ImGuiKeyOwner_None && owner_id != ImGuiKeyOwner_Any) ? owner_id : g.CurrentFocusScopeId; -} - -ImGuiKeyRoutingData* ImGui::GetShortcutRoutingData(ImGuiKeyChord key_chord) -{ - // Majority of shortcuts will be Key + any number of Mods - // We accept _Single_ mod with ImGuiKey_None. - // - Shortcut(ImGuiKey_S | ImGuiMod_Ctrl); // Legal - // - Shortcut(ImGuiKey_S | ImGuiMod_Ctrl | ImGuiMod_Shift); // Legal - // - Shortcut(ImGuiMod_Ctrl); // Legal - // - Shortcut(ImGuiMod_Ctrl | ImGuiMod_Shift); // Not legal - ImGuiContext& g = *GImGui; - ImGuiKeyRoutingTable* rt = &g.KeysRoutingTable; - ImGuiKeyRoutingData* routing_data; - if (key_chord & ImGuiMod_Shortcut) - key_chord = ConvertShortcutMod(key_chord); - ImGuiKey key = (ImGuiKey)(key_chord & ~ImGuiMod_Mask_); - ImGuiKey mods = (ImGuiKey)(key_chord & ImGuiMod_Mask_); - if (key == ImGuiKey_None) - key = ConvertSingleModFlagToKey(&g, mods); - IM_ASSERT(IsNamedKey(key)); - - // Get (in the majority of case, the linked list will have one element so this should be 2 reads. - // Subsequent elements will be contiguous in memory as list is sorted/rebuilt in NewFrame). - for (ImGuiKeyRoutingIndex idx = rt->Index[key - ImGuiKey_NamedKey_BEGIN]; idx != -1; idx = routing_data->NextEntryIndex) - { - routing_data = &rt->Entries[idx]; - if (routing_data->Mods == mods) - return routing_data; - } - - // Add to linked-list - ImGuiKeyRoutingIndex routing_data_idx = (ImGuiKeyRoutingIndex)rt->Entries.Size; - rt->Entries.push_back(ImGuiKeyRoutingData()); - routing_data = &rt->Entries[routing_data_idx]; - routing_data->Mods = (ImU16)mods; - routing_data->NextEntryIndex = rt->Index[key - ImGuiKey_NamedKey_BEGIN]; // Setup linked list - rt->Index[key - ImGuiKey_NamedKey_BEGIN] = routing_data_idx; - return routing_data; -} - -// Current score encoding (lower is highest priority): -// - 0: ImGuiInputFlags_RouteGlobalHigh -// - 1: ImGuiInputFlags_RouteFocused (if item active) -// - 2: ImGuiInputFlags_RouteGlobal -// - 3+: ImGuiInputFlags_RouteFocused (if window in focus-stack) -// - 254: ImGuiInputFlags_RouteGlobalLow -// - 255: never route -// 'flags' should include an explicit routing policy -static int CalcRoutingScore(ImGuiWindow* location, ImGuiID owner_id, ImGuiInputFlags flags) -{ - if (flags & ImGuiInputFlags_RouteFocused) - { - ImGuiContext& g = *GImGui; - ImGuiWindow* focused = g.NavWindow; - - // ActiveID gets top priority - // (we don't check g.ActiveIdUsingAllKeys here. Routing is applied but if input ownership is tested later it may discard it) - if (owner_id != 0 && g.ActiveId == owner_id) - return 1; - - // Score based on distance to focused window (lower is better) - // Assuming both windows are submitting a routing request, - // - When Window....... is focused -> Window scores 3 (best), Window/ChildB scores 255 (no match) - // - When Window/ChildB is focused -> Window scores 4, Window/ChildB scores 3 (best) - // Assuming only WindowA is submitting a routing request, - // - When Window/ChildB is focused -> Window scores 4 (best), Window/ChildB doesn't have a score. - if (focused != NULL && focused->RootWindow == location->RootWindow) - for (int next_score = 3; focused != NULL; next_score++) - { - if (focused == location) - { - IM_ASSERT(next_score < 255); - return next_score; - } - focused = (focused->RootWindow != focused) ? focused->ParentWindow : NULL; // FIXME: This could be later abstracted as a focus path - } - return 255; - } - - // ImGuiInputFlags_RouteGlobalHigh is default, so calls without flags are not conditional - if (flags & ImGuiInputFlags_RouteGlobal) - return 2; - if (flags & ImGuiInputFlags_RouteGlobalLow) - return 254; - return 0; -} - -// Request a desired route for an input chord (key + mods). -// Return true if the route is available this frame. -// - Routes and key ownership are attributed at the beginning of next frame based on best score and mod state. -// (Conceptually this does a "Submit for next frame" + "Test for current frame". -// As such, it could be called TrySetXXX or SubmitXXX, or the Submit and Test operations should be separate.) -// - Using 'owner_id == ImGuiKeyOwner_Any/0': auto-assign an owner based on current focus scope (each window has its focus scope by default) -// - Using 'owner_id == ImGuiKeyOwner_None': allows disabling/locking a shortcut. -bool ImGui::SetShortcutRouting(ImGuiKeyChord key_chord, ImGuiID owner_id, ImGuiInputFlags flags) -{ - ImGuiContext& g = *GImGui; - if ((flags & ImGuiInputFlags_RouteMask_) == 0) - flags |= ImGuiInputFlags_RouteGlobalHigh; // IMPORTANT: This is the default for SetShortcutRouting() but NOT Shortcut() - else - IM_ASSERT(ImIsPowerOfTwo(flags & ImGuiInputFlags_RouteMask_)); // Check that only 1 routing flag is used - - if (flags & ImGuiInputFlags_RouteUnlessBgFocused) - if (g.NavWindow == NULL) - return false; - if (flags & ImGuiInputFlags_RouteAlways) - return true; - - const int score = CalcRoutingScore(g.CurrentWindow, owner_id, flags); - if (score == 255) - return false; - - // Submit routing for NEXT frame (assuming score is sufficient) - // FIXME: Could expose a way to use a "serve last" policy for same score resolution (using <= instead of <). - ImGuiKeyRoutingData* routing_data = GetShortcutRoutingData(key_chord); - const ImGuiID routing_id = GetRoutingIdFromOwnerId(owner_id); - //const bool set_route = (flags & ImGuiInputFlags_ServeLast) ? (score <= routing_data->RoutingNextScore) : (score < routing_data->RoutingNextScore); - if (score < routing_data->RoutingNextScore) - { - routing_data->RoutingNext = routing_id; - routing_data->RoutingNextScore = (ImU8)score; - } - - // Return routing state for CURRENT frame - return routing_data->RoutingCurr == routing_id; -} - -// Currently unused by core (but used by tests) -// Note: this cannot be turned into GetShortcutRouting() because we do the owner_id->routing_id translation, name would be more misleading. -bool ImGui::TestShortcutRouting(ImGuiKeyChord key_chord, ImGuiID owner_id) -{ - const ImGuiID routing_id = GetRoutingIdFromOwnerId(owner_id); - ImGuiKeyRoutingData* routing_data = GetShortcutRoutingData(key_chord); // FIXME: Could avoid creating entry. - return routing_data->RoutingCurr == routing_id; -} - -// Note that Dear ImGui doesn't know the meaning/semantic of ImGuiKey from 0..511: they are legacy native keycodes. -// Consider transitioning from 'IsKeyDown(MY_ENGINE_KEY_A)' (<1.87) to IsKeyDown(ImGuiKey_A) (>= 1.87) -bool ImGui::IsKeyDown(ImGuiKey key) -{ - return IsKeyDown(key, ImGuiKeyOwner_Any); -} - -bool ImGui::IsKeyDown(ImGuiKey key, ImGuiID owner_id) -{ - const ImGuiKeyData* key_data = GetKeyData(key); - if (!key_data->Down) - return false; - if (!TestKeyOwner(key, owner_id)) - return false; - return true; -} - -bool ImGui::IsKeyPressed(ImGuiKey key, bool repeat) -{ - return IsKeyPressed(key, ImGuiKeyOwner_Any, repeat ? ImGuiInputFlags_Repeat : ImGuiInputFlags_None); -} - -// Important: unless legacy IsKeyPressed(ImGuiKey, bool repeat=true) which DEFAULT to repeat, this requires EXPLICIT repeat. -bool ImGui::IsKeyPressed(ImGuiKey key, ImGuiID owner_id, ImGuiInputFlags flags) -{ - const ImGuiKeyData* key_data = GetKeyData(key); - if (!key_data->Down) // In theory this should already be encoded as (DownDuration < 0.0f), but testing this facilitates eating mechanism (until we finish work on key ownership) - return false; - const float t = key_data->DownDuration; - if (t < 0.0f) - return false; - IM_ASSERT((flags & ~ImGuiInputFlags_SupportedByIsKeyPressed) == 0); // Passing flags not supported by this function! - - bool pressed = (t == 0.0f); - if (!pressed && ((flags & ImGuiInputFlags_Repeat) != 0)) - { - float repeat_delay, repeat_rate; - GetTypematicRepeatRate(flags, &repeat_delay, &repeat_rate); - pressed = (t > repeat_delay) && GetKeyPressedAmount(key, repeat_delay, repeat_rate) > 0; - } - if (!pressed) - return false; - if (!TestKeyOwner(key, owner_id)) - return false; - return true; -} - -bool ImGui::IsKeyReleased(ImGuiKey key) -{ - return IsKeyReleased(key, ImGuiKeyOwner_Any); -} - -bool ImGui::IsKeyReleased(ImGuiKey key, ImGuiID owner_id) -{ - const ImGuiKeyData* key_data = GetKeyData(key); - if (key_data->DownDurationPrev < 0.0f || key_data->Down) - return false; - if (!TestKeyOwner(key, owner_id)) - return false; - return true; -} - -bool ImGui::IsMouseDown(ImGuiMouseButton button) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(button >= 0 && button < IM_ARRAYSIZE(g.IO.MouseDown)); - return g.IO.MouseDown[button] && TestKeyOwner(MouseButtonToKey(button), ImGuiKeyOwner_Any); // should be same as IsKeyDown(MouseButtonToKey(button), ImGuiKeyOwner_Any), but this allows legacy code hijacking the io.Mousedown[] array. -} - -bool ImGui::IsMouseDown(ImGuiMouseButton button, ImGuiID owner_id) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(button >= 0 && button < IM_ARRAYSIZE(g.IO.MouseDown)); - return g.IO.MouseDown[button] && TestKeyOwner(MouseButtonToKey(button), owner_id); // Should be same as IsKeyDown(MouseButtonToKey(button), owner_id), but this allows legacy code hijacking the io.Mousedown[] array. -} - -bool ImGui::IsMouseClicked(ImGuiMouseButton button, bool repeat) -{ - return IsMouseClicked(button, ImGuiKeyOwner_Any, repeat ? ImGuiInputFlags_Repeat : ImGuiInputFlags_None); -} - -bool ImGui::IsMouseClicked(ImGuiMouseButton button, ImGuiID owner_id, ImGuiInputFlags flags) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(button >= 0 && button < IM_ARRAYSIZE(g.IO.MouseDown)); - if (!g.IO.MouseDown[button]) // In theory this should already be encoded as (DownDuration < 0.0f), but testing this facilitates eating mechanism (until we finish work on key ownership) - return false; - const float t = g.IO.MouseDownDuration[button]; - if (t < 0.0f) - return false; - IM_ASSERT((flags & ~ImGuiInputFlags_SupportedByIsKeyPressed) == 0); // Passing flags not supported by this function! - - const bool repeat = (flags & ImGuiInputFlags_Repeat) != 0; - const bool pressed = (t == 0.0f) || (repeat && t > g.IO.KeyRepeatDelay && CalcTypematicRepeatAmount(t - g.IO.DeltaTime, t, g.IO.KeyRepeatDelay, g.IO.KeyRepeatRate) > 0); - if (!pressed) - return false; - - if (!TestKeyOwner(MouseButtonToKey(button), owner_id)) - return false; - - return true; -} - -bool ImGui::IsMouseReleased(ImGuiMouseButton button) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(button >= 0 && button < IM_ARRAYSIZE(g.IO.MouseDown)); - return g.IO.MouseReleased[button] && TestKeyOwner(MouseButtonToKey(button), ImGuiKeyOwner_Any); // Should be same as IsKeyReleased(MouseButtonToKey(button), ImGuiKeyOwner_Any) -} - -bool ImGui::IsMouseReleased(ImGuiMouseButton button, ImGuiID owner_id) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(button >= 0 && button < IM_ARRAYSIZE(g.IO.MouseDown)); - return g.IO.MouseReleased[button] && TestKeyOwner(MouseButtonToKey(button), owner_id); // Should be same as IsKeyReleased(MouseButtonToKey(button), owner_id) -} - -bool ImGui::IsMouseDoubleClicked(ImGuiMouseButton button) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(button >= 0 && button < IM_ARRAYSIZE(g.IO.MouseDown)); - return g.IO.MouseClickedCount[button] == 2 && TestKeyOwner(MouseButtonToKey(button), ImGuiKeyOwner_Any); -} - -int ImGui::GetMouseClickedCount(ImGuiMouseButton button) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(button >= 0 && button < IM_ARRAYSIZE(g.IO.MouseDown)); - return g.IO.MouseClickedCount[button]; -} - -// Test if mouse cursor is hovering given rectangle -// NB- Rectangle is clipped by our current clip setting -// NB- Expand the rectangle to be generous on imprecise inputs systems (g.Style.TouchExtraPadding) -bool ImGui::IsMouseHoveringRect(const ImVec2& r_min, const ImVec2& r_max, bool clip) -{ - ImGuiContext& g = *GImGui; - - // Clip - ImRect rect_clipped(r_min, r_max); - if (clip) - rect_clipped.ClipWith(g.CurrentWindow->ClipRect); - - // Hit testing, expanded for touch input - if (!rect_clipped.ContainsWithPad(g.IO.MousePos, g.Style.TouchExtraPadding)) - return false; - if (!g.MouseViewport->GetMainRect().Overlaps(rect_clipped)) - return false; - return true; -} - -// Return if a mouse click/drag went past the given threshold. Valid to call during the MouseReleased frame. -// [Internal] This doesn't test if the button is pressed -bool ImGui::IsMouseDragPastThreshold(ImGuiMouseButton button, float lock_threshold) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(button >= 0 && button < IM_ARRAYSIZE(g.IO.MouseDown)); - if (lock_threshold < 0.0f) - lock_threshold = g.IO.MouseDragThreshold; - return g.IO.MouseDragMaxDistanceSqr[button] >= lock_threshold * lock_threshold; -} - -bool ImGui::IsMouseDragging(ImGuiMouseButton button, float lock_threshold) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(button >= 0 && button < IM_ARRAYSIZE(g.IO.MouseDown)); - if (!g.IO.MouseDown[button]) - return false; - return IsMouseDragPastThreshold(button, lock_threshold); -} - -ImVec2 ImGui::GetMousePos() -{ - ImGuiContext& g = *GImGui; - return g.IO.MousePos; -} - -// This is called TeleportMousePos() and not SetMousePos() to emphasis that setting MousePosPrev will effectively clear mouse delta as well. -// It is expected you only call this if (io.BackendFlags & ImGuiBackendFlags_HasSetMousePos) is set and supported by backend. -void ImGui::TeleportMousePos(const ImVec2& pos) -{ - ImGuiContext& g = *GImGui; - g.IO.MousePos = g.IO.MousePosPrev = pos; - g.IO.MouseDelta = ImVec2(0.0f, 0.0f); - g.IO.WantSetMousePos = true; - //IMGUI_DEBUG_LOG_IO("TeleportMousePos: (%.1f,%.1f)\n", io.MousePos.x, io.MousePos.y); -} - -// NB: prefer to call right after BeginPopup(). At the time Selectable/MenuItem is activated, the popup is already closed! -ImVec2 ImGui::GetMousePosOnOpeningCurrentPopup() -{ - ImGuiContext& g = *GImGui; - if (g.BeginPopupStack.Size > 0) - return g.OpenPopupStack[g.BeginPopupStack.Size - 1].OpenMousePos; - return g.IO.MousePos; -} - -// We typically use ImVec2(-FLT_MAX,-FLT_MAX) to denote an invalid mouse position. -bool ImGui::IsMousePosValid(const ImVec2* mouse_pos) -{ - // The assert is only to silence a false-positive in XCode Static Analysis. - // Because GImGui is not dereferenced in every code path, the static analyzer assume that it may be NULL (which it doesn't for other functions). - IM_ASSERT(GImGui != NULL); - const float MOUSE_INVALID = -256000.0f; - ImVec2 p = mouse_pos ? *mouse_pos : GImGui->IO.MousePos; - return p.x >= MOUSE_INVALID && p.y >= MOUSE_INVALID; -} - -// [WILL OBSOLETE] This was designed for backends, but prefer having backend maintain a mask of held mouse buttons, because upcoming input queue system will make this invalid. -bool ImGui::IsAnyMouseDown() -{ - ImGuiContext& g = *GImGui; - for (int n = 0; n < IM_ARRAYSIZE(g.IO.MouseDown); n++) - if (g.IO.MouseDown[n]) - return true; - return false; -} - -// Return the delta from the initial clicking position while the mouse button is clicked or was just released. -// This is locked and return 0.0f until the mouse moves past a distance threshold at least once. -// NB: This is only valid if IsMousePosValid(). backends in theory should always keep mouse position valid when dragging even outside the client window. -ImVec2 ImGui::GetMouseDragDelta(ImGuiMouseButton button, float lock_threshold) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(button >= 0 && button < IM_ARRAYSIZE(g.IO.MouseDown)); - if (lock_threshold < 0.0f) - lock_threshold = g.IO.MouseDragThreshold; - if (g.IO.MouseDown[button] || g.IO.MouseReleased[button]) - if (g.IO.MouseDragMaxDistanceSqr[button] >= lock_threshold * lock_threshold) - if (IsMousePosValid(&g.IO.MousePos) && IsMousePosValid(&g.IO.MouseClickedPos[button])) - return g.IO.MousePos - g.IO.MouseClickedPos[button]; - return ImVec2(0.0f, 0.0f); -} - -void ImGui::ResetMouseDragDelta(ImGuiMouseButton button) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(button >= 0 && button < IM_ARRAYSIZE(g.IO.MouseDown)); - // NB: We don't need to reset g.IO.MouseDragMaxDistanceSqr - g.IO.MouseClickedPos[button] = g.IO.MousePos; -} - -// Get desired mouse cursor shape. -// Important: this is meant to be used by a platform backend, it is reset in ImGui::NewFrame(), -// updated during the frame, and locked in EndFrame()/Render(). -// If you use software rendering by setting io.MouseDrawCursor then Dear ImGui will render those for you -ImGuiMouseCursor ImGui::GetMouseCursor() -{ - ImGuiContext& g = *GImGui; - return g.MouseCursor; -} - -void ImGui::SetMouseCursor(ImGuiMouseCursor cursor_type) -{ - ImGuiContext& g = *GImGui; - g.MouseCursor = cursor_type; -} - -static void UpdateAliasKey(ImGuiKey key, bool v, float analog_value) -{ - IM_ASSERT(ImGui::IsAliasKey(key)); - ImGuiKeyData* key_data = ImGui::GetKeyData(key); - key_data->Down = v; - key_data->AnalogValue = analog_value; -} - -// [Internal] Do not use directly -static ImGuiKeyChord GetMergedModsFromKeys() -{ - ImGuiKeyChord mods = 0; - if (ImGui::IsKeyDown(ImGuiMod_Ctrl)) { mods |= ImGuiMod_Ctrl; } - if (ImGui::IsKeyDown(ImGuiMod_Shift)) { mods |= ImGuiMod_Shift; } - if (ImGui::IsKeyDown(ImGuiMod_Alt)) { mods |= ImGuiMod_Alt; } - if (ImGui::IsKeyDown(ImGuiMod_Super)) { mods |= ImGuiMod_Super; } - return mods; -} - -static void ImGui::UpdateKeyboardInputs() -{ - ImGuiContext& g = *GImGui; - ImGuiIO& io = g.IO; - - // Import legacy keys or verify they are not used -#ifndef IMGUI_DISABLE_OBSOLETE_KEYIO - if (io.BackendUsingLegacyKeyArrays == 0) - { - // Backend used new io.AddKeyEvent() API: Good! Verify that old arrays are never written to externally. - for (int n = 0; n < ImGuiKey_LegacyNativeKey_END; n++) - IM_ASSERT((io.KeysDown[n] == false || IsKeyDown((ImGuiKey)n)) && "Backend needs to either only use io.AddKeyEvent(), either only fill legacy io.KeysDown[] + io.KeyMap[]. Not both!"); - } - else - { - if (g.FrameCount == 0) - for (int n = ImGuiKey_LegacyNativeKey_BEGIN; n < ImGuiKey_LegacyNativeKey_END; n++) - IM_ASSERT(g.IO.KeyMap[n] == -1 && "Backend is not allowed to write to io.KeyMap[0..511]!"); - - // Build reverse KeyMap (Named -> Legacy) - for (int n = ImGuiKey_NamedKey_BEGIN; n < ImGuiKey_NamedKey_END; n++) - if (io.KeyMap[n] != -1) - { - IM_ASSERT(IsLegacyKey((ImGuiKey)io.KeyMap[n])); - io.KeyMap[io.KeyMap[n]] = n; - } - - // Import legacy keys into new ones - for (int n = ImGuiKey_LegacyNativeKey_BEGIN; n < ImGuiKey_LegacyNativeKey_END; n++) - if (io.KeysDown[n] || io.BackendUsingLegacyKeyArrays == 1) - { - const ImGuiKey key = (ImGuiKey)(io.KeyMap[n] != -1 ? io.KeyMap[n] : n); - IM_ASSERT(io.KeyMap[n] == -1 || IsNamedKey(key)); - io.KeysData[key].Down = io.KeysDown[n]; - if (key != n) - io.KeysDown[key] = io.KeysDown[n]; // Allow legacy code using io.KeysDown[GetKeyIndex()] with old backends - io.BackendUsingLegacyKeyArrays = 1; - } - if (io.BackendUsingLegacyKeyArrays == 1) - { - GetKeyData(ImGuiMod_Ctrl)->Down = io.KeyCtrl; - GetKeyData(ImGuiMod_Shift)->Down = io.KeyShift; - GetKeyData(ImGuiMod_Alt)->Down = io.KeyAlt; - GetKeyData(ImGuiMod_Super)->Down = io.KeySuper; - } - } - -#ifndef IMGUI_DISABLE_OBSOLETE_KEYIO - const bool nav_gamepad_active = (io.ConfigFlags & ImGuiConfigFlags_NavEnableGamepad) != 0 && (io.BackendFlags & ImGuiBackendFlags_HasGamepad) != 0; - if (io.BackendUsingLegacyNavInputArray && nav_gamepad_active) - { - #define MAP_LEGACY_NAV_INPUT_TO_KEY1(_KEY, _NAV1) do { io.KeysData[_KEY].Down = (io.NavInputs[_NAV1] > 0.0f); io.KeysData[_KEY].AnalogValue = io.NavInputs[_NAV1]; } while (0) - #define MAP_LEGACY_NAV_INPUT_TO_KEY2(_KEY, _NAV1, _NAV2) do { io.KeysData[_KEY].Down = (io.NavInputs[_NAV1] > 0.0f) || (io.NavInputs[_NAV2] > 0.0f); io.KeysData[_KEY].AnalogValue = ImMax(io.NavInputs[_NAV1], io.NavInputs[_NAV2]); } while (0) - MAP_LEGACY_NAV_INPUT_TO_KEY1(ImGuiKey_GamepadFaceDown, ImGuiNavInput_Activate); - MAP_LEGACY_NAV_INPUT_TO_KEY1(ImGuiKey_GamepadFaceRight, ImGuiNavInput_Cancel); - MAP_LEGACY_NAV_INPUT_TO_KEY1(ImGuiKey_GamepadFaceLeft, ImGuiNavInput_Menu); - MAP_LEGACY_NAV_INPUT_TO_KEY1(ImGuiKey_GamepadFaceUp, ImGuiNavInput_Input); - MAP_LEGACY_NAV_INPUT_TO_KEY1(ImGuiKey_GamepadDpadLeft, ImGuiNavInput_DpadLeft); - MAP_LEGACY_NAV_INPUT_TO_KEY1(ImGuiKey_GamepadDpadRight, ImGuiNavInput_DpadRight); - MAP_LEGACY_NAV_INPUT_TO_KEY1(ImGuiKey_GamepadDpadUp, ImGuiNavInput_DpadUp); - MAP_LEGACY_NAV_INPUT_TO_KEY1(ImGuiKey_GamepadDpadDown, ImGuiNavInput_DpadDown); - MAP_LEGACY_NAV_INPUT_TO_KEY2(ImGuiKey_GamepadL1, ImGuiNavInput_FocusPrev, ImGuiNavInput_TweakSlow); - MAP_LEGACY_NAV_INPUT_TO_KEY2(ImGuiKey_GamepadR1, ImGuiNavInput_FocusNext, ImGuiNavInput_TweakFast); - MAP_LEGACY_NAV_INPUT_TO_KEY1(ImGuiKey_GamepadLStickLeft, ImGuiNavInput_LStickLeft); - MAP_LEGACY_NAV_INPUT_TO_KEY1(ImGuiKey_GamepadLStickRight, ImGuiNavInput_LStickRight); - MAP_LEGACY_NAV_INPUT_TO_KEY1(ImGuiKey_GamepadLStickUp, ImGuiNavInput_LStickUp); - MAP_LEGACY_NAV_INPUT_TO_KEY1(ImGuiKey_GamepadLStickDown, ImGuiNavInput_LStickDown); - #undef NAV_MAP_KEY - } -#endif -#endif - - // Update aliases - for (int n = 0; n < ImGuiMouseButton_COUNT; n++) - UpdateAliasKey(MouseButtonToKey(n), io.MouseDown[n], io.MouseDown[n] ? 1.0f : 0.0f); - UpdateAliasKey(ImGuiKey_MouseWheelX, io.MouseWheelH != 0.0f, io.MouseWheelH); - UpdateAliasKey(ImGuiKey_MouseWheelY, io.MouseWheel != 0.0f, io.MouseWheel); - - // Synchronize io.KeyMods and io.KeyXXX values. - // - New backends (1.87+): send io.AddKeyEvent(ImGuiMod_XXX) -> -> (here) deriving io.KeyMods + io.KeyXXX from key array. - // - Legacy backends: set io.KeyXXX bools -> (above) set key array from io.KeyXXX -> (here) deriving io.KeyMods + io.KeyXXX from key array. - // So with legacy backends the 4 values will do a unnecessary back-and-forth but it makes the code simpler and future facing. - io.KeyMods = GetMergedModsFromKeys(); - io.KeyCtrl = (io.KeyMods & ImGuiMod_Ctrl) != 0; - io.KeyShift = (io.KeyMods & ImGuiMod_Shift) != 0; - io.KeyAlt = (io.KeyMods & ImGuiMod_Alt) != 0; - io.KeySuper = (io.KeyMods & ImGuiMod_Super) != 0; - - // Clear gamepad data if disabled - if ((io.BackendFlags & ImGuiBackendFlags_HasGamepad) == 0) - for (int i = ImGuiKey_Gamepad_BEGIN; i < ImGuiKey_Gamepad_END; i++) - { - io.KeysData[i - ImGuiKey_KeysData_OFFSET].Down = false; - io.KeysData[i - ImGuiKey_KeysData_OFFSET].AnalogValue = 0.0f; - } - - // Update keys - for (int i = 0; i < ImGuiKey_KeysData_SIZE; i++) - { - ImGuiKeyData* key_data = &io.KeysData[i]; - key_data->DownDurationPrev = key_data->DownDuration; - key_data->DownDuration = key_data->Down ? (key_data->DownDuration < 0.0f ? 0.0f : key_data->DownDuration + io.DeltaTime) : -1.0f; - } - - // Update keys/input owner (named keys only): one entry per key - for (ImGuiKey key = ImGuiKey_NamedKey_BEGIN; key < ImGuiKey_NamedKey_END; key = (ImGuiKey)(key + 1)) - { - ImGuiKeyData* key_data = &io.KeysData[key - ImGuiKey_KeysData_OFFSET]; - ImGuiKeyOwnerData* owner_data = &g.KeysOwnerData[key - ImGuiKey_NamedKey_BEGIN]; - owner_data->OwnerCurr = owner_data->OwnerNext; - if (!key_data->Down) // Important: ownership is released on the frame after a release. Ensure a 'MouseDown -> CloseWindow -> MouseUp' chain doesn't lead to someone else seeing the MouseUp. - owner_data->OwnerNext = ImGuiKeyOwner_None; - owner_data->LockThisFrame = owner_data->LockUntilRelease = owner_data->LockUntilRelease && key_data->Down; // Clear LockUntilRelease when key is not Down anymore - } - - UpdateKeyRoutingTable(&g.KeysRoutingTable); -} - -static void ImGui::UpdateMouseInputs() -{ - ImGuiContext& g = *GImGui; - ImGuiIO& io = g.IO; - - // Mouse Wheel swapping flag - // As a standard behavior holding SHIFT while using Vertical Mouse Wheel triggers Horizontal scroll instead - // - We avoid doing it on OSX as it the OS input layer handles this already. - // - FIXME: However this means when running on OSX over Emscripten, Shift+WheelY will incur two swapping (1 in OS, 1 here), canceling the feature. - // - FIXME: When we can distinguish e.g. touchpad scroll events from mouse ones, we'll set this accordingly based on input source. - io.MouseWheelRequestAxisSwap = io.KeyShift && !io.ConfigMacOSXBehaviors; - - // Round mouse position to avoid spreading non-rounded position (e.g. UpdateManualResize doesn't support them well) - if (IsMousePosValid(&io.MousePos)) - io.MousePos = g.MouseLastValidPos = ImFloor(io.MousePos); - - // If mouse just appeared or disappeared (usually denoted by -FLT_MAX components) we cancel out movement in MouseDelta - if (IsMousePosValid(&io.MousePos) && IsMousePosValid(&io.MousePosPrev)) - io.MouseDelta = io.MousePos - io.MousePosPrev; - else - io.MouseDelta = ImVec2(0.0f, 0.0f); - - // Update stationary timer. - // FIXME: May need to rework again to have some tolerance for occasional small movement, while being functional on high-framerates. - const float mouse_stationary_threshold = (io.MouseSource == ImGuiMouseSource_Mouse) ? 2.0f : 3.0f; // Slightly higher threshold for ImGuiMouseSource_TouchScreen/ImGuiMouseSource_Pen, may need rework. - const bool mouse_stationary = (ImLengthSqr(io.MouseDelta) <= mouse_stationary_threshold * mouse_stationary_threshold); - g.MouseStationaryTimer = mouse_stationary ? (g.MouseStationaryTimer + io.DeltaTime) : 0.0f; - //IMGUI_DEBUG_LOG("%.4f\n", g.MouseStationaryTimer); - - // If mouse moved we re-enable mouse hovering in case it was disabled by gamepad/keyboard. In theory should use a >0.0f threshold but would need to reset in everywhere we set this to true. - if (io.MouseDelta.x != 0.0f || io.MouseDelta.y != 0.0f) - g.NavDisableMouseHover = false; - - for (int i = 0; i < IM_ARRAYSIZE(io.MouseDown); i++) - { - io.MouseClicked[i] = io.MouseDown[i] && io.MouseDownDuration[i] < 0.0f; - io.MouseClickedCount[i] = 0; // Will be filled below - io.MouseReleased[i] = !io.MouseDown[i] && io.MouseDownDuration[i] >= 0.0f; - io.MouseDownDurationPrev[i] = io.MouseDownDuration[i]; - io.MouseDownDuration[i] = io.MouseDown[i] ? (io.MouseDownDuration[i] < 0.0f ? 0.0f : io.MouseDownDuration[i] + io.DeltaTime) : -1.0f; - if (io.MouseClicked[i]) - { - bool is_repeated_click = false; - if ((float)(g.Time - io.MouseClickedTime[i]) < io.MouseDoubleClickTime) - { - ImVec2 delta_from_click_pos = IsMousePosValid(&io.MousePos) ? (io.MousePos - io.MouseClickedPos[i]) : ImVec2(0.0f, 0.0f); - if (ImLengthSqr(delta_from_click_pos) < io.MouseDoubleClickMaxDist * io.MouseDoubleClickMaxDist) - is_repeated_click = true; - } - if (is_repeated_click) - io.MouseClickedLastCount[i]++; - else - io.MouseClickedLastCount[i] = 1; - io.MouseClickedTime[i] = g.Time; - io.MouseClickedPos[i] = io.MousePos; - io.MouseClickedCount[i] = io.MouseClickedLastCount[i]; - io.MouseDragMaxDistanceAbs[i] = ImVec2(0.0f, 0.0f); - io.MouseDragMaxDistanceSqr[i] = 0.0f; - } - else if (io.MouseDown[i]) - { - // Maintain the maximum distance we reaching from the initial click position, which is used with dragging threshold - ImVec2 delta_from_click_pos = IsMousePosValid(&io.MousePos) ? (io.MousePos - io.MouseClickedPos[i]) : ImVec2(0.0f, 0.0f); - io.MouseDragMaxDistanceSqr[i] = ImMax(io.MouseDragMaxDistanceSqr[i], ImLengthSqr(delta_from_click_pos)); - io.MouseDragMaxDistanceAbs[i].x = ImMax(io.MouseDragMaxDistanceAbs[i].x, delta_from_click_pos.x < 0.0f ? -delta_from_click_pos.x : delta_from_click_pos.x); - io.MouseDragMaxDistanceAbs[i].y = ImMax(io.MouseDragMaxDistanceAbs[i].y, delta_from_click_pos.y < 0.0f ? -delta_from_click_pos.y : delta_from_click_pos.y); - } - - // We provide io.MouseDoubleClicked[] as a legacy service - io.MouseDoubleClicked[i] = (io.MouseClickedCount[i] == 2); - - // Clicking any mouse button reactivate mouse hovering which may have been deactivated by gamepad/keyboard navigation - if (io.MouseClicked[i]) - g.NavDisableMouseHover = false; - } -} - -static void LockWheelingWindow(ImGuiWindow* window, float wheel_amount) -{ - ImGuiContext& g = *GImGui; - if (window) - g.WheelingWindowReleaseTimer = ImMin(g.WheelingWindowReleaseTimer + ImAbs(wheel_amount) * WINDOWS_MOUSE_WHEEL_SCROLL_LOCK_TIMER, WINDOWS_MOUSE_WHEEL_SCROLL_LOCK_TIMER); - else - g.WheelingWindowReleaseTimer = 0.0f; - if (g.WheelingWindow == window) - return; - IMGUI_DEBUG_LOG_IO("[io] LockWheelingWindow() \"%s\"\n", window ? window->Name : "NULL"); - g.WheelingWindow = window; - g.WheelingWindowRefMousePos = g.IO.MousePos; - if (window == NULL) - { - g.WheelingWindowStartFrame = -1; - g.WheelingAxisAvg = ImVec2(0.0f, 0.0f); - } -} - -static ImGuiWindow* FindBestWheelingWindow(const ImVec2& wheel) -{ - // For each axis, find window in the hierarchy that may want to use scrolling - ImGuiContext& g = *GImGui; - ImGuiWindow* windows[2] = { NULL, NULL }; - for (int axis = 0; axis < 2; axis++) - if (wheel[axis] != 0.0f) - for (ImGuiWindow* window = windows[axis] = g.HoveredWindow; window->Flags & ImGuiWindowFlags_ChildWindow; window = windows[axis] = window->ParentWindow) - { - // Bubble up into parent window if: - // - a child window doesn't allow any scrolling. - // - a child window has the ImGuiWindowFlags_NoScrollWithMouse flag. - //// - a child window doesn't need scrolling because it is already at the edge for the direction we are going in (FIXME-WIP) - const bool has_scrolling = (window->ScrollMax[axis] != 0.0f); - const bool inputs_disabled = (window->Flags & ImGuiWindowFlags_NoScrollWithMouse) && !(window->Flags & ImGuiWindowFlags_NoMouseInputs); - //const bool scrolling_past_limits = (wheel_v < 0.0f) ? (window->Scroll[axis] <= 0.0f) : (window->Scroll[axis] >= window->ScrollMax[axis]); - if (has_scrolling && !inputs_disabled) // && !scrolling_past_limits) - break; // select this window - } - if (windows[0] == NULL && windows[1] == NULL) - return NULL; - - // If there's only one window or only one axis then there's no ambiguity - if (windows[0] == windows[1] || windows[0] == NULL || windows[1] == NULL) - return windows[1] ? windows[1] : windows[0]; - - // If candidate are different windows we need to decide which one to prioritize - // - First frame: only find a winner if one axis is zero. - // - Subsequent frames: only find a winner when one is more than the other. - if (g.WheelingWindowStartFrame == -1) - g.WheelingWindowStartFrame = g.FrameCount; - if ((g.WheelingWindowStartFrame == g.FrameCount && wheel.x != 0.0f && wheel.y != 0.0f) || (g.WheelingAxisAvg.x == g.WheelingAxisAvg.y)) - { - g.WheelingWindowWheelRemainder = wheel; - return NULL; - } - return (g.WheelingAxisAvg.x > g.WheelingAxisAvg.y) ? windows[0] : windows[1]; -} - -// Called by NewFrame() -void ImGui::UpdateMouseWheel() -{ - // Reset the locked window if we move the mouse or after the timer elapses. - // FIXME: Ideally we could refactor to have one timer for "changing window w/ same axis" and a shorter timer for "changing window or axis w/ other axis" (#3795) - ImGuiContext& g = *GImGui; - if (g.WheelingWindow != NULL) - { - g.WheelingWindowReleaseTimer -= g.IO.DeltaTime; - if (IsMousePosValid() && ImLengthSqr(g.IO.MousePos - g.WheelingWindowRefMousePos) > g.IO.MouseDragThreshold * g.IO.MouseDragThreshold) - g.WheelingWindowReleaseTimer = 0.0f; - if (g.WheelingWindowReleaseTimer <= 0.0f) - LockWheelingWindow(NULL, 0.0f); - } - - ImVec2 wheel; - wheel.x = TestKeyOwner(ImGuiKey_MouseWheelX, ImGuiKeyOwner_None) ? g.IO.MouseWheelH : 0.0f; - wheel.y = TestKeyOwner(ImGuiKey_MouseWheelY, ImGuiKeyOwner_None) ? g.IO.MouseWheel : 0.0f; - - //IMGUI_DEBUG_LOG("MouseWheel X:%.3f Y:%.3f\n", wheel_x, wheel_y); - ImGuiWindow* mouse_window = g.WheelingWindow ? g.WheelingWindow : g.HoveredWindow; - if (!mouse_window || mouse_window->Collapsed) - return; - - // Zoom / Scale window - // FIXME-OBSOLETE: This is an old feature, it still works but pretty much nobody is using it and may be best redesigned. - if (wheel.y != 0.0f && g.IO.KeyCtrl && g.IO.FontAllowUserScaling) - { - LockWheelingWindow(mouse_window, wheel.y); - ImGuiWindow* window = mouse_window; - const float new_font_scale = ImClamp(window->FontWindowScale + g.IO.MouseWheel * 0.10f, 0.50f, 2.50f); - const float scale = new_font_scale / window->FontWindowScale; - window->FontWindowScale = new_font_scale; - if (window == window->RootWindow) - { - const ImVec2 offset = window->Size * (1.0f - scale) * (g.IO.MousePos - window->Pos) / window->Size; - SetWindowPos(window, window->Pos + offset, 0); - window->Size = ImTrunc(window->Size * scale); - window->SizeFull = ImTrunc(window->SizeFull * scale); - } - return; - } - if (g.IO.KeyCtrl) - return; - - // Mouse wheel scrolling - // Read about io.MouseWheelRequestAxisSwap and its issue on Mac+Emscripten in UpdateMouseInputs() - if (g.IO.MouseWheelRequestAxisSwap) - wheel = ImVec2(wheel.y, 0.0f); - - // Maintain a rough average of moving magnitude on both axises - // FIXME: should by based on wall clock time rather than frame-counter - g.WheelingAxisAvg.x = ImExponentialMovingAverage(g.WheelingAxisAvg.x, ImAbs(wheel.x), 30); - g.WheelingAxisAvg.y = ImExponentialMovingAverage(g.WheelingAxisAvg.y, ImAbs(wheel.y), 30); - - // In the rare situation where FindBestWheelingWindow() had to defer first frame of wheeling due to ambiguous main axis, reinject it now. - wheel += g.WheelingWindowWheelRemainder; - g.WheelingWindowWheelRemainder = ImVec2(0.0f, 0.0f); - if (wheel.x == 0.0f && wheel.y == 0.0f) - return; - - // Mouse wheel scrolling: find target and apply - // - don't renew lock if axis doesn't apply on the window. - // - select a main axis when both axises are being moved. - if (ImGuiWindow* window = (g.WheelingWindow ? g.WheelingWindow : FindBestWheelingWindow(wheel))) - if (!(window->Flags & ImGuiWindowFlags_NoScrollWithMouse) && !(window->Flags & ImGuiWindowFlags_NoMouseInputs)) - { - bool do_scroll[2] = { wheel.x != 0.0f && window->ScrollMax.x != 0.0f, wheel.y != 0.0f && window->ScrollMax.y != 0.0f }; - if (do_scroll[ImGuiAxis_X] && do_scroll[ImGuiAxis_Y]) - do_scroll[(g.WheelingAxisAvg.x > g.WheelingAxisAvg.y) ? ImGuiAxis_Y : ImGuiAxis_X] = false; - if (do_scroll[ImGuiAxis_X]) - { - LockWheelingWindow(window, wheel.x); - float max_step = window->InnerRect.GetWidth() * 0.67f; - float scroll_step = ImTrunc(ImMin(2 * window->CalcFontSize(), max_step)); - SetScrollX(window, window->Scroll.x - wheel.x * scroll_step); - } - if (do_scroll[ImGuiAxis_Y]) - { - LockWheelingWindow(window, wheel.y); - float max_step = window->InnerRect.GetHeight() * 0.67f; - float scroll_step = ImTrunc(ImMin(5 * window->CalcFontSize(), max_step)); - SetScrollY(window, window->Scroll.y - wheel.y * scroll_step); - } - } -} - -void ImGui::SetNextFrameWantCaptureKeyboard(bool want_capture_keyboard) -{ - ImGuiContext& g = *GImGui; - g.WantCaptureKeyboardNextFrame = want_capture_keyboard ? 1 : 0; -} - -void ImGui::SetNextFrameWantCaptureMouse(bool want_capture_mouse) -{ - ImGuiContext& g = *GImGui; - g.WantCaptureMouseNextFrame = want_capture_mouse ? 1 : 0; -} - -#ifndef IMGUI_DISABLE_DEBUG_TOOLS -static const char* GetInputSourceName(ImGuiInputSource source) -{ - const char* input_source_names[] = { "None", "Mouse", "Keyboard", "Gamepad", "Clipboard" }; - IM_ASSERT(IM_ARRAYSIZE(input_source_names) == ImGuiInputSource_COUNT && source >= 0 && source < ImGuiInputSource_COUNT); - return input_source_names[source]; -} -static const char* GetMouseSourceName(ImGuiMouseSource source) -{ - const char* mouse_source_names[] = { "Mouse", "TouchScreen", "Pen" }; - IM_ASSERT(IM_ARRAYSIZE(mouse_source_names) == ImGuiMouseSource_COUNT && source >= 0 && source < ImGuiMouseSource_COUNT); - return mouse_source_names[source]; -} -static void DebugPrintInputEvent(const char* prefix, const ImGuiInputEvent* e) -{ - ImGuiContext& g = *GImGui; - if (e->Type == ImGuiInputEventType_MousePos) { if (e->MousePos.PosX == -FLT_MAX && e->MousePos.PosY == -FLT_MAX) IMGUI_DEBUG_LOG_IO("[io] %s: MousePos (-FLT_MAX, -FLT_MAX)\n", prefix); else IMGUI_DEBUG_LOG_IO("[io] %s: MousePos (%.1f, %.1f) (%s)\n", prefix, e->MousePos.PosX, e->MousePos.PosY, GetMouseSourceName(e->MousePos.MouseSource)); return; } - if (e->Type == ImGuiInputEventType_MouseButton) { IMGUI_DEBUG_LOG_IO("[io] %s: MouseButton %d %s (%s)\n", prefix, e->MouseButton.Button, e->MouseButton.Down ? "Down" : "Up", GetMouseSourceName(e->MouseButton.MouseSource)); return; } - if (e->Type == ImGuiInputEventType_MouseWheel) { IMGUI_DEBUG_LOG_IO("[io] %s: MouseWheel (%.3f, %.3f) (%s)\n", prefix, e->MouseWheel.WheelX, e->MouseWheel.WheelY, GetMouseSourceName(e->MouseWheel.MouseSource)); return; } - if (e->Type == ImGuiInputEventType_MouseViewport){IMGUI_DEBUG_LOG_IO("[io] %s: MouseViewport (0x%08X)\n", prefix, e->MouseViewport.HoveredViewportID); return; } - if (e->Type == ImGuiInputEventType_Key) { IMGUI_DEBUG_LOG_IO("[io] %s: Key \"%s\" %s\n", prefix, ImGui::GetKeyName(e->Key.Key), e->Key.Down ? "Down" : "Up"); return; } - if (e->Type == ImGuiInputEventType_Text) { IMGUI_DEBUG_LOG_IO("[io] %s: Text: %c (U+%08X)\n", prefix, e->Text.Char, e->Text.Char); return; } - if (e->Type == ImGuiInputEventType_Focus) { IMGUI_DEBUG_LOG_IO("[io] %s: AppFocused %d\n", prefix, e->AppFocused.Focused); return; } -} -#endif - -// Process input queue -// We always call this with the value of 'bool g.IO.ConfigInputTrickleEventQueue'. -// - trickle_fast_inputs = false : process all events, turn into flattened input state (e.g. successive down/up/down/up will be lost) -// - trickle_fast_inputs = true : process as many events as possible (successive down/up/down/up will be trickled over several frames so nothing is lost) (new feature in 1.87) -void ImGui::UpdateInputEvents(bool trickle_fast_inputs) -{ - ImGuiContext& g = *GImGui; - ImGuiIO& io = g.IO; - - // Only trickle chars<>key when working with InputText() - // FIXME: InputText() could parse event trail? - // FIXME: Could specialize chars<>keys trickling rules for control keys (those not typically associated to characters) - const bool trickle_interleaved_keys_and_text = (trickle_fast_inputs && g.WantTextInputNextFrame == 1); - - bool mouse_moved = false, mouse_wheeled = false, key_changed = false, text_inputted = false; - int mouse_button_changed = 0x00; - ImBitArray key_changed_mask; - - int event_n = 0; - for (; event_n < g.InputEventsQueue.Size; event_n++) - { - ImGuiInputEvent* e = &g.InputEventsQueue[event_n]; - if (e->Type == ImGuiInputEventType_MousePos) - { - if (g.IO.WantSetMousePos) - continue; - // Trickling Rule: Stop processing queued events if we already handled a mouse button change - ImVec2 event_pos(e->MousePos.PosX, e->MousePos.PosY); - if (trickle_fast_inputs && (mouse_button_changed != 0 || mouse_wheeled || key_changed || text_inputted)) - break; - io.MousePos = event_pos; - io.MouseSource = e->MousePos.MouseSource; - mouse_moved = true; - } - else if (e->Type == ImGuiInputEventType_MouseButton) - { - // Trickling Rule: Stop processing queued events if we got multiple action on the same button - const ImGuiMouseButton button = e->MouseButton.Button; - IM_ASSERT(button >= 0 && button < ImGuiMouseButton_COUNT); - if (trickle_fast_inputs && ((mouse_button_changed & (1 << button)) || mouse_wheeled)) - break; - if (trickle_fast_inputs && e->MouseButton.MouseSource == ImGuiMouseSource_TouchScreen && mouse_moved) // #2702: TouchScreen have no initial hover. - break; - io.MouseDown[button] = e->MouseButton.Down; - io.MouseSource = e->MouseButton.MouseSource; - mouse_button_changed |= (1 << button); - } - else if (e->Type == ImGuiInputEventType_MouseWheel) - { - // Trickling Rule: Stop processing queued events if we got multiple action on the event - if (trickle_fast_inputs && (mouse_moved || mouse_button_changed != 0)) - break; - io.MouseWheelH += e->MouseWheel.WheelX; - io.MouseWheel += e->MouseWheel.WheelY; - io.MouseSource = e->MouseWheel.MouseSource; - mouse_wheeled = true; - } - else if (e->Type == ImGuiInputEventType_MouseViewport) - { - io.MouseHoveredViewport = e->MouseViewport.HoveredViewportID; - } - else if (e->Type == ImGuiInputEventType_Key) - { - // Trickling Rule: Stop processing queued events if we got multiple action on the same button - ImGuiKey key = e->Key.Key; - IM_ASSERT(key != ImGuiKey_None); - ImGuiKeyData* key_data = GetKeyData(key); - const int key_data_index = (int)(key_data - g.IO.KeysData); - if (trickle_fast_inputs && key_data->Down != e->Key.Down && (key_changed_mask.TestBit(key_data_index) || text_inputted || mouse_button_changed != 0)) - break; - key_data->Down = e->Key.Down; - key_data->AnalogValue = e->Key.AnalogValue; - key_changed = true; - key_changed_mask.SetBit(key_data_index); - - // Allow legacy code using io.KeysDown[GetKeyIndex()] with new backends -#ifndef IMGUI_DISABLE_OBSOLETE_KEYIO - io.KeysDown[key_data_index] = key_data->Down; - if (io.KeyMap[key_data_index] != -1) - io.KeysDown[io.KeyMap[key_data_index]] = key_data->Down; -#endif - } - else if (e->Type == ImGuiInputEventType_Text) - { - // Trickling Rule: Stop processing queued events if keys/mouse have been interacted with - if (trickle_fast_inputs && ((key_changed && trickle_interleaved_keys_and_text) || mouse_button_changed != 0 || mouse_moved || mouse_wheeled)) - break; - unsigned int c = e->Text.Char; - io.InputQueueCharacters.push_back(c <= IM_UNICODE_CODEPOINT_MAX ? (ImWchar)c : IM_UNICODE_CODEPOINT_INVALID); - if (trickle_interleaved_keys_and_text) - text_inputted = true; - } - else if (e->Type == ImGuiInputEventType_Focus) - { - // We intentionally overwrite this and process in NewFrame(), in order to give a chance - // to multi-viewports backends to queue AddFocusEvent(false) + AddFocusEvent(true) in same frame. - const bool focus_lost = !e->AppFocused.Focused; - io.AppFocusLost = focus_lost; - } - else - { - IM_ASSERT(0 && "Unknown event!"); - } - } - - // Record trail (for domain-specific applications wanting to access a precise trail) - //if (event_n != 0) IMGUI_DEBUG_LOG_IO("Processed: %d / Remaining: %d\n", event_n, g.InputEventsQueue.Size - event_n); - for (int n = 0; n < event_n; n++) - g.InputEventsTrail.push_back(g.InputEventsQueue[n]); - - // [DEBUG] -#ifndef IMGUI_DISABLE_DEBUG_TOOLS - if (event_n != 0 && (g.DebugLogFlags & ImGuiDebugLogFlags_EventIO)) - for (int n = 0; n < g.InputEventsQueue.Size; n++) - DebugPrintInputEvent(n < event_n ? "Processed" : "Remaining", &g.InputEventsQueue[n]); -#endif - - // Remaining events will be processed on the next frame - if (event_n == g.InputEventsQueue.Size) - g.InputEventsQueue.resize(0); - else - g.InputEventsQueue.erase(g.InputEventsQueue.Data, g.InputEventsQueue.Data + event_n); - - // Clear buttons state when focus is lost - // - this is useful so e.g. releasing Alt after focus loss on Alt-Tab doesn't trigger the Alt menu toggle. - // - we clear in EndFrame() and not now in order allow application/user code polling this flag - // (e.g. custom backend may want to clear additional data, custom widgets may want to react with a "canceling" event). - if (g.IO.AppFocusLost) - g.IO.ClearInputKeys(); -} - -ImGuiID ImGui::GetKeyOwner(ImGuiKey key) -{ - if (!IsNamedKeyOrModKey(key)) - return ImGuiKeyOwner_None; - - ImGuiContext& g = *GImGui; - ImGuiKeyOwnerData* owner_data = GetKeyOwnerData(&g, key); - ImGuiID owner_id = owner_data->OwnerCurr; - - if (g.ActiveIdUsingAllKeyboardKeys && owner_id != g.ActiveId && owner_id != ImGuiKeyOwner_Any) - if (key >= ImGuiKey_Keyboard_BEGIN && key < ImGuiKey_Keyboard_END) - return ImGuiKeyOwner_None; - - return owner_id; -} - -// TestKeyOwner(..., ID) : (owner == None || owner == ID) -// TestKeyOwner(..., None) : (owner == None) -// TestKeyOwner(..., Any) : no owner test -// All paths are also testing for key not being locked, for the rare cases that key have been locked with using ImGuiInputFlags_LockXXX flags. -bool ImGui::TestKeyOwner(ImGuiKey key, ImGuiID owner_id) -{ - if (!IsNamedKeyOrModKey(key)) - return true; - - ImGuiContext& g = *GImGui; - if (g.ActiveIdUsingAllKeyboardKeys && owner_id != g.ActiveId && owner_id != ImGuiKeyOwner_Any) - if (key >= ImGuiKey_Keyboard_BEGIN && key < ImGuiKey_Keyboard_END) - return false; - - ImGuiKeyOwnerData* owner_data = GetKeyOwnerData(&g, key); - if (owner_id == ImGuiKeyOwner_Any) - return (owner_data->LockThisFrame == false); - - // Note: SetKeyOwner() sets OwnerCurr. It is not strictly required for most mouse routing overlap (because of ActiveId/HoveredId - // are acting as filter before this has a chance to filter), but sane as soon as user tries to look into things. - // Setting OwnerCurr in SetKeyOwner() is more consistent than testing OwnerNext here: would be inconsistent with getter and other functions. - if (owner_data->OwnerCurr != owner_id) - { - if (owner_data->LockThisFrame) - return false; - if (owner_data->OwnerCurr != ImGuiKeyOwner_None) - return false; - } - - return true; -} - -// _LockXXX flags are useful to lock keys away from code which is not input-owner aware. -// When using _LockXXX flags, you can use ImGuiKeyOwner_Any to lock keys from everyone. -// - SetKeyOwner(..., None) : clears owner -// - SetKeyOwner(..., Any, !Lock) : illegal (assert) -// - SetKeyOwner(..., Any or None, Lock) : set lock -void ImGui::SetKeyOwner(ImGuiKey key, ImGuiID owner_id, ImGuiInputFlags flags) -{ - IM_ASSERT(IsNamedKeyOrModKey(key) && (owner_id != ImGuiKeyOwner_Any || (flags & (ImGuiInputFlags_LockThisFrame | ImGuiInputFlags_LockUntilRelease)))); // Can only use _Any with _LockXXX flags (to eat a key away without an ID to retrieve it) - IM_ASSERT((flags & ~ImGuiInputFlags_SupportedBySetKeyOwner) == 0); // Passing flags not supported by this function! - - ImGuiContext& g = *GImGui; - ImGuiKeyOwnerData* owner_data = GetKeyOwnerData(&g, key); - owner_data->OwnerCurr = owner_data->OwnerNext = owner_id; - - // We cannot lock by default as it would likely break lots of legacy code. - // In the case of using LockUntilRelease while key is not down we still lock during the frame (no key_data->Down test) - owner_data->LockUntilRelease = (flags & ImGuiInputFlags_LockUntilRelease) != 0; - owner_data->LockThisFrame = (flags & ImGuiInputFlags_LockThisFrame) != 0 || (owner_data->LockUntilRelease); -} - -// Rarely used helper -void ImGui::SetKeyOwnersForKeyChord(ImGuiKeyChord key_chord, ImGuiID owner_id, ImGuiInputFlags flags) -{ - if (key_chord & ImGuiMod_Ctrl) { SetKeyOwner(ImGuiMod_Ctrl, owner_id, flags); } - if (key_chord & ImGuiMod_Shift) { SetKeyOwner(ImGuiMod_Shift, owner_id, flags); } - if (key_chord & ImGuiMod_Alt) { SetKeyOwner(ImGuiMod_Alt, owner_id, flags); } - if (key_chord & ImGuiMod_Super) { SetKeyOwner(ImGuiMod_Super, owner_id, flags); } - if (key_chord & ImGuiMod_Shortcut) { SetKeyOwner(ImGuiMod_Shortcut, owner_id, flags); } - if (key_chord & ~ImGuiMod_Mask_) { SetKeyOwner((ImGuiKey)(key_chord & ~ImGuiMod_Mask_), owner_id, flags); } -} - -// This is more or less equivalent to: -// if (IsItemHovered() || IsItemActive()) -// SetKeyOwner(key, GetItemID()); -// Extensive uses of that (e.g. many calls for a single item) may want to manually perform the tests once and then call SetKeyOwner() multiple times. -// More advanced usage scenarios may want to call SetKeyOwner() manually based on different condition. -// Worth noting is that only one item can be hovered and only one item can be active, therefore this usage pattern doesn't need to bother with routing and priority. -void ImGui::SetItemKeyOwner(ImGuiKey key, ImGuiInputFlags flags) -{ - ImGuiContext& g = *GImGui; - ImGuiID id = g.LastItemData.ID; - if (id == 0 || (g.HoveredId != id && g.ActiveId != id)) - return; - if ((flags & ImGuiInputFlags_CondMask_) == 0) - flags |= ImGuiInputFlags_CondDefault_; - if ((g.HoveredId == id && (flags & ImGuiInputFlags_CondHovered)) || (g.ActiveId == id && (flags & ImGuiInputFlags_CondActive))) - { - IM_ASSERT((flags & ~ImGuiInputFlags_SupportedBySetItemKeyOwner) == 0); // Passing flags not supported by this function! - SetKeyOwner(key, id, flags & ~ImGuiInputFlags_CondMask_); - } -} - -bool ImGui::Shortcut(ImGuiKeyChord key_chord, ImGuiID owner_id, ImGuiInputFlags flags) -{ - ImGuiContext& g = *GImGui; - - // When using (owner_id == 0/Any): SetShortcutRouting() will use CurrentFocusScopeId and filter with this, so IsKeyPressed() is fine with he 0/Any. - if ((flags & ImGuiInputFlags_RouteMask_) == 0) - flags |= ImGuiInputFlags_RouteFocused; - if (!SetShortcutRouting(key_chord, owner_id, flags)) - return false; - - if (key_chord & ImGuiMod_Shortcut) - key_chord = ConvertShortcutMod(key_chord); - ImGuiKey mods = (ImGuiKey)(key_chord & ImGuiMod_Mask_); - if (g.IO.KeyMods != mods) - return false; - - // Special storage location for mods - ImGuiKey key = (ImGuiKey)(key_chord & ~ImGuiMod_Mask_); - if (key == ImGuiKey_None) - key = ConvertSingleModFlagToKey(&g, mods); - - if (!IsKeyPressed(key, owner_id, (flags & (ImGuiInputFlags_Repeat | (ImGuiInputFlags)ImGuiInputFlags_RepeatRateMask_)))) - return false; - IM_ASSERT((flags & ~ImGuiInputFlags_SupportedByShortcut) == 0); // Passing flags not supported by this function! - - return true; -} - - -//----------------------------------------------------------------------------- -// [SECTION] ERROR CHECKING -//----------------------------------------------------------------------------- - -// Helper function to verify ABI compatibility between caller code and compiled version of Dear ImGui. -// Verify that the type sizes are matching between the calling file's compilation unit and imgui.cpp's compilation unit -// If this triggers you have an issue: -// - Most commonly: mismatched headers and compiled code version. -// - Or: mismatched configuration #define, compilation settings, packing pragma etc. -// The configuration settings mentioned in imconfig.h must be set for all compilation units involved with Dear ImGui, -// which is way it is required you put them in your imconfig file (and not just before including imgui.h). -// Otherwise it is possible that different compilation units would see different structure layout -bool ImGui::DebugCheckVersionAndDataLayout(const char* version, size_t sz_io, size_t sz_style, size_t sz_vec2, size_t sz_vec4, size_t sz_vert, size_t sz_idx) -{ - bool error = false; - if (strcmp(version, IMGUI_VERSION) != 0) { error = true; IM_ASSERT(strcmp(version, IMGUI_VERSION) == 0 && "Mismatched version string!"); } - if (sz_io != sizeof(ImGuiIO)) { error = true; IM_ASSERT(sz_io == sizeof(ImGuiIO) && "Mismatched struct layout!"); } - if (sz_style != sizeof(ImGuiStyle)) { error = true; IM_ASSERT(sz_style == sizeof(ImGuiStyle) && "Mismatched struct layout!"); } - if (sz_vec2 != sizeof(ImVec2)) { error = true; IM_ASSERT(sz_vec2 == sizeof(ImVec2) && "Mismatched struct layout!"); } - if (sz_vec4 != sizeof(ImVec4)) { error = true; IM_ASSERT(sz_vec4 == sizeof(ImVec4) && "Mismatched struct layout!"); } - if (sz_vert != sizeof(ImDrawVert)) { error = true; IM_ASSERT(sz_vert == sizeof(ImDrawVert) && "Mismatched struct layout!"); } - if (sz_idx != sizeof(ImDrawIdx)) { error = true; IM_ASSERT(sz_idx == sizeof(ImDrawIdx) && "Mismatched struct layout!"); } - return !error; -} - -// Until 1.89 (IMGUI_VERSION_NUM < 18814) it was legal to use SetCursorPos() to extend the boundary of a parent (e.g. window or table cell) -// This is causing issues and ambiguity and we need to retire that. -// See https://github.com/ocornut/imgui/issues/5548 for more details. -// [Scenario 1] -// Previously this would make the window content size ~200x200: -// Begin(...) + SetCursorScreenPos(GetCursorScreenPos() + ImVec2(200,200)) + End(); // NOT OK -// Instead, please submit an item: -// Begin(...) + SetCursorScreenPos(GetCursorScreenPos() + ImVec2(200,200)) + Dummy(ImVec2(0,0)) + End(); // OK -// Alternative: -// Begin(...) + Dummy(ImVec2(200,200)) + End(); // OK -// [Scenario 2] -// For reference this is one of the issue what we aim to fix with this change: -// BeginGroup() + SomeItem("foobar") + SetCursorScreenPos(GetCursorScreenPos()) + EndGroup() -// The previous logic made SetCursorScreenPos(GetCursorScreenPos()) have a side-effect! It would erroneously incorporate ItemSpacing.y after the item into content size, making the group taller! -// While this code is a little twisted, no-one would expect SetXXX(GetXXX()) to have a side-effect. Using vertical alignment patterns could trigger this issue. -void ImGui::ErrorCheckUsingSetCursorPosToExtendParentBoundaries() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - IM_ASSERT(window->DC.IsSetPos); - window->DC.IsSetPos = false; -#ifdef IMGUI_DISABLE_OBSOLETE_FUNCTIONS - if (window->DC.CursorPos.x <= window->DC.CursorMaxPos.x && window->DC.CursorPos.y <= window->DC.CursorMaxPos.y) - return; - if (window->SkipItems) - return; - IM_ASSERT(0 && "Code uses SetCursorPos()/SetCursorScreenPos() to extend window/parent boundaries. Please submit an item e.g. Dummy() to validate extent."); -#else - window->DC.CursorMaxPos = ImMax(window->DC.CursorMaxPos, window->DC.CursorPos); -#endif -} - -static void ImGui::ErrorCheckNewFrameSanityChecks() -{ - ImGuiContext& g = *GImGui; - - // Check user IM_ASSERT macro - // (IF YOU GET A WARNING OR COMPILE ERROR HERE: it means your assert macro is incorrectly defined! - // If your macro uses multiple statements, it NEEDS to be surrounded by a 'do { ... } while (0)' block. - // This is a common C/C++ idiom to allow multiple statements macros to be used in control flow blocks.) - // #define IM_ASSERT(EXPR) if (SomeCode(EXPR)) SomeMoreCode(); // Wrong! - // #define IM_ASSERT(EXPR) do { if (SomeCode(EXPR)) SomeMoreCode(); } while (0) // Correct! - if (true) IM_ASSERT(1); else IM_ASSERT(0); - - // Emscripten backends are often imprecise in their submission of DeltaTime. (#6114, #3644) - // Ideally the Emscripten app/backend should aim to fix or smooth this value and avoid feeding zero, but we tolerate it. -#ifdef __EMSCRIPTEN__ - if (g.IO.DeltaTime <= 0.0f && g.FrameCount > 0) - g.IO.DeltaTime = 0.00001f; -#endif - - // Check user data - // (We pass an error message in the assert expression to make it visible to programmers who are not using a debugger, as most assert handlers display their argument) - IM_ASSERT(g.Initialized); - IM_ASSERT((g.IO.DeltaTime > 0.0f || g.FrameCount == 0) && "Need a positive DeltaTime!"); - IM_ASSERT((g.FrameCount == 0 || g.FrameCountEnded == g.FrameCount) && "Forgot to call Render() or EndFrame() at the end of the previous frame?"); - IM_ASSERT(g.IO.DisplaySize.x >= 0.0f && g.IO.DisplaySize.y >= 0.0f && "Invalid DisplaySize value!"); - IM_ASSERT(g.IO.Fonts->IsBuilt() && "Font Atlas not built! Make sure you called ImGui_ImplXXXX_NewFrame() function for renderer backend, which should call io.Fonts->GetTexDataAsRGBA32() / GetTexDataAsAlpha8()"); - IM_ASSERT(g.Style.CurveTessellationTol > 0.0f && "Invalid style setting!"); - IM_ASSERT(g.Style.CircleTessellationMaxError > 0.0f && "Invalid style setting!"); - IM_ASSERT(g.Style.Alpha >= 0.0f && g.Style.Alpha <= 1.0f && "Invalid style setting!"); // Allows us to avoid a few clamps in color computations - IM_ASSERT(g.Style.WindowMinSize.x >= 1.0f && g.Style.WindowMinSize.y >= 1.0f && "Invalid style setting."); - IM_ASSERT(g.Style.WindowMenuButtonPosition == ImGuiDir_None || g.Style.WindowMenuButtonPosition == ImGuiDir_Left || g.Style.WindowMenuButtonPosition == ImGuiDir_Right); - IM_ASSERT(g.Style.ColorButtonPosition == ImGuiDir_Left || g.Style.ColorButtonPosition == ImGuiDir_Right); -#ifndef IMGUI_DISABLE_OBSOLETE_KEYIO - for (int n = ImGuiKey_NamedKey_BEGIN; n < ImGuiKey_COUNT; n++) - IM_ASSERT(g.IO.KeyMap[n] >= -1 && g.IO.KeyMap[n] < ImGuiKey_LegacyNativeKey_END && "io.KeyMap[] contains an out of bound value (need to be 0..511, or -1 for unmapped key)"); - - // Check: required key mapping (we intentionally do NOT check all keys to not pressure user into setting up everything, but Space is required and was only added in 1.60 WIP) - if ((g.IO.ConfigFlags & ImGuiConfigFlags_NavEnableKeyboard) && g.IO.BackendUsingLegacyKeyArrays == 1) - IM_ASSERT(g.IO.KeyMap[ImGuiKey_Space] != -1 && "ImGuiKey_Space is not mapped, required for keyboard navigation."); -#endif - - // Check: the io.ConfigWindowsResizeFromEdges option requires backend to honor mouse cursor changes and set the ImGuiBackendFlags_HasMouseCursors flag accordingly. - if (g.IO.ConfigWindowsResizeFromEdges && !(g.IO.BackendFlags & ImGuiBackendFlags_HasMouseCursors)) - g.IO.ConfigWindowsResizeFromEdges = false; - - // Perform simple check: error if Docking or Viewport are enabled _exactly_ on frame 1 (instead of frame 0 or later), which is a common error leading to loss of .ini data. - if (g.FrameCount == 1 && (g.IO.ConfigFlags & ImGuiConfigFlags_DockingEnable) && (g.ConfigFlagsLastFrame & ImGuiConfigFlags_DockingEnable) == 0) - IM_ASSERT(0 && "Please set DockingEnable before the first call to NewFrame()! Otherwise you will lose your .ini settings!"); - if (g.FrameCount == 1 && (g.IO.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) && (g.ConfigFlagsLastFrame & ImGuiConfigFlags_ViewportsEnable) == 0) - IM_ASSERT(0 && "Please set ViewportsEnable before the first call to NewFrame()! Otherwise you will lose your .ini settings!"); - - // Perform simple checks: multi-viewport and platform windows support - if (g.IO.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - if ((g.IO.BackendFlags & ImGuiBackendFlags_PlatformHasViewports) && (g.IO.BackendFlags & ImGuiBackendFlags_RendererHasViewports)) - { - IM_ASSERT((g.FrameCount == 0 || g.FrameCount == g.FrameCountPlatformEnded) && "Forgot to call UpdatePlatformWindows() in main loop after EndFrame()? Check examples/ applications for reference."); - IM_ASSERT(g.PlatformIO.Platform_CreateWindow != NULL && "Platform init didn't install handlers?"); - IM_ASSERT(g.PlatformIO.Platform_DestroyWindow != NULL && "Platform init didn't install handlers?"); - IM_ASSERT(g.PlatformIO.Platform_GetWindowPos != NULL && "Platform init didn't install handlers?"); - IM_ASSERT(g.PlatformIO.Platform_SetWindowPos != NULL && "Platform init didn't install handlers?"); - IM_ASSERT(g.PlatformIO.Platform_GetWindowSize != NULL && "Platform init didn't install handlers?"); - IM_ASSERT(g.PlatformIO.Platform_SetWindowSize != NULL && "Platform init didn't install handlers?"); - IM_ASSERT(g.PlatformIO.Monitors.Size > 0 && "Platform init didn't setup Monitors list?"); - IM_ASSERT((g.Viewports[0]->PlatformUserData != NULL || g.Viewports[0]->PlatformHandle != NULL) && "Platform init didn't setup main viewport."); - if (g.IO.ConfigDockingTransparentPayload && (g.IO.ConfigFlags & ImGuiConfigFlags_DockingEnable)) - IM_ASSERT(g.PlatformIO.Platform_SetWindowAlpha != NULL && "Platform_SetWindowAlpha handler is required to use io.ConfigDockingTransparent!"); - } - else - { - // Disable feature, our backends do not support it - g.IO.ConfigFlags &= ~ImGuiConfigFlags_ViewportsEnable; - } - - // Perform simple checks on platform monitor data + compute a total bounding box for quick early outs - for (ImGuiPlatformMonitor& mon : g.PlatformIO.Monitors) - { - IM_UNUSED(mon); - IM_ASSERT(mon.MainSize.x > 0.0f && mon.MainSize.y > 0.0f && "Monitor main bounds not setup properly."); - IM_ASSERT(ImRect(mon.MainPos, mon.MainPos + mon.MainSize).Contains(ImRect(mon.WorkPos, mon.WorkPos + mon.WorkSize)) && "Monitor work bounds not setup properly. If you don't have work area information, just copy MainPos/MainSize into them."); - IM_ASSERT(mon.DpiScale != 0.0f); - } - } -} - -static void ImGui::ErrorCheckEndFrameSanityChecks() -{ - ImGuiContext& g = *GImGui; - - // Verify that io.KeyXXX fields haven't been tampered with. Key mods should not be modified between NewFrame() and EndFrame() - // One possible reason leading to this assert is that your backends update inputs _AFTER_ NewFrame(). - // It is known that when some modal native windows called mid-frame takes focus away, some backends such as GLFW will - // send key release events mid-frame. This would normally trigger this assertion and lead to sheared inputs. - // We silently accommodate for this case by ignoring the case where all io.KeyXXX modifiers were released (aka key_mod_flags == 0), - // while still correctly asserting on mid-frame key press events. - const ImGuiKeyChord key_mods = GetMergedModsFromKeys(); - IM_ASSERT((key_mods == 0 || g.IO.KeyMods == key_mods) && "Mismatching io.KeyCtrl/io.KeyShift/io.KeyAlt/io.KeySuper vs io.KeyMods"); - IM_UNUSED(key_mods); - - // [EXPERIMENTAL] Recover from errors: You may call this yourself before EndFrame(). - //ErrorCheckEndFrameRecover(); - - // Report when there is a mismatch of Begin/BeginChild vs End/EndChild calls. Important: Remember that the Begin/BeginChild API requires you - // to always call End/EndChild even if Begin/BeginChild returns false! (this is unfortunately inconsistent with most other Begin* API). - if (g.CurrentWindowStack.Size != 1) - { - if (g.CurrentWindowStack.Size > 1) - { - ImGuiWindow* window = g.CurrentWindowStack.back().Window; // <-- This window was not Ended! - IM_ASSERT_USER_ERROR(g.CurrentWindowStack.Size == 1, "Mismatched Begin/BeginChild vs End/EndChild calls: did you forget to call End/EndChild?"); - IM_UNUSED(window); - while (g.CurrentWindowStack.Size > 1) - End(); - } - else - { - IM_ASSERT_USER_ERROR(g.CurrentWindowStack.Size == 1, "Mismatched Begin/BeginChild vs End/EndChild calls: did you call End/EndChild too much?"); - } - } - - IM_ASSERT_USER_ERROR(g.GroupStack.Size == 0, "Missing EndGroup call!"); -} - -// Experimental recovery from incorrect usage of BeginXXX/EndXXX/PushXXX/PopXXX calls. -// Must be called during or before EndFrame(). -// This is generally flawed as we are not necessarily End/Popping things in the right order. -// FIXME: Can't recover from inside BeginTabItem/EndTabItem yet. -// FIXME: Can't recover from interleaved BeginTabBar/Begin -void ImGui::ErrorCheckEndFrameRecover(ImGuiErrorLogCallback log_callback, void* user_data) -{ - // PVS-Studio V1044 is "Loop break conditions do not depend on the number of iterations" - ImGuiContext& g = *GImGui; - while (g.CurrentWindowStack.Size > 0) //-V1044 - { - ErrorCheckEndWindowRecover(log_callback, user_data); - ImGuiWindow* window = g.CurrentWindow; - if (g.CurrentWindowStack.Size == 1) - { - IM_ASSERT(window->IsFallbackWindow); - break; - } - if (window->Flags & ImGuiWindowFlags_ChildWindow) - { - if (log_callback) log_callback(user_data, "Recovered from missing EndChild() for '%s'", window->Name); - EndChild(); - } - else - { - if (log_callback) log_callback(user_data, "Recovered from missing End() for '%s'", window->Name); - End(); - } - } -} - -// Must be called before End()/EndChild() -void ImGui::ErrorCheckEndWindowRecover(ImGuiErrorLogCallback log_callback, void* user_data) -{ - ImGuiContext& g = *GImGui; - while (g.CurrentTable && (g.CurrentTable->OuterWindow == g.CurrentWindow || g.CurrentTable->InnerWindow == g.CurrentWindow)) - { - if (log_callback) log_callback(user_data, "Recovered from missing EndTable() in '%s'", g.CurrentTable->OuterWindow->Name); - EndTable(); - } - - ImGuiWindow* window = g.CurrentWindow; - ImGuiStackSizes* stack_sizes = &g.CurrentWindowStack.back().StackSizesOnBegin; - IM_ASSERT(window != NULL); - while (g.CurrentTabBar != NULL) //-V1044 - { - if (log_callback) log_callback(user_data, "Recovered from missing EndTabBar() in '%s'", window->Name); - EndTabBar(); - } - while (window->DC.TreeDepth > 0) - { - if (log_callback) log_callback(user_data, "Recovered from missing TreePop() in '%s'", window->Name); - TreePop(); - } - while (g.GroupStack.Size > stack_sizes->SizeOfGroupStack) //-V1044 - { - if (log_callback) log_callback(user_data, "Recovered from missing EndGroup() in '%s'", window->Name); - EndGroup(); - } - while (window->IDStack.Size > 1) - { - if (log_callback) log_callback(user_data, "Recovered from missing PopID() in '%s'", window->Name); - PopID(); - } - while (g.DisabledStackSize > stack_sizes->SizeOfDisabledStack) //-V1044 - { - if (log_callback) log_callback(user_data, "Recovered from missing EndDisabled() in '%s'", window->Name); - EndDisabled(); - } - while (g.ColorStack.Size > stack_sizes->SizeOfColorStack) - { - if (log_callback) log_callback(user_data, "Recovered from missing PopStyleColor() in '%s' for ImGuiCol_%s", window->Name, GetStyleColorName(g.ColorStack.back().Col)); - PopStyleColor(); - } - while (g.ItemFlagsStack.Size > stack_sizes->SizeOfItemFlagsStack) //-V1044 - { - if (log_callback) log_callback(user_data, "Recovered from missing PopItemFlag() in '%s'", window->Name); - PopItemFlag(); - } - while (g.StyleVarStack.Size > stack_sizes->SizeOfStyleVarStack) //-V1044 - { - if (log_callback) log_callback(user_data, "Recovered from missing PopStyleVar() in '%s'", window->Name); - PopStyleVar(); - } - while (g.FontStack.Size > stack_sizes->SizeOfFontStack) //-V1044 - { - if (log_callback) log_callback(user_data, "Recovered from missing PopFont() in '%s'", window->Name); - PopFont(); - } - while (g.FocusScopeStack.Size > stack_sizes->SizeOfFocusScopeStack + 1) //-V1044 - { - if (log_callback) log_callback(user_data, "Recovered from missing PopFocusScope() in '%s'", window->Name); - PopFocusScope(); - } -} - -// Save current stack sizes for later compare -void ImGuiStackSizes::SetToContextState(ImGuiContext* ctx) -{ - ImGuiContext& g = *ctx; - ImGuiWindow* window = g.CurrentWindow; - SizeOfIDStack = (short)window->IDStack.Size; - SizeOfColorStack = (short)g.ColorStack.Size; - SizeOfStyleVarStack = (short)g.StyleVarStack.Size; - SizeOfFontStack = (short)g.FontStack.Size; - SizeOfFocusScopeStack = (short)g.FocusScopeStack.Size; - SizeOfGroupStack = (short)g.GroupStack.Size; - SizeOfItemFlagsStack = (short)g.ItemFlagsStack.Size; - SizeOfBeginPopupStack = (short)g.BeginPopupStack.Size; - SizeOfDisabledStack = (short)g.DisabledStackSize; -} - -// Compare to detect usage errors -void ImGuiStackSizes::CompareWithContextState(ImGuiContext* ctx) -{ - ImGuiContext& g = *ctx; - ImGuiWindow* window = g.CurrentWindow; - IM_UNUSED(window); - - // Window stacks - // NOT checking: DC.ItemWidth, DC.TextWrapPos (per window) to allow user to conveniently push once and not pop (they are cleared on Begin) - IM_ASSERT(SizeOfIDStack == window->IDStack.Size && "PushID/PopID or TreeNode/TreePop Mismatch!"); - - // Global stacks - // For color, style and font stacks there is an incentive to use Push/Begin/Pop/.../End patterns, so we relax our checks a little to allow them. - IM_ASSERT(SizeOfGroupStack == g.GroupStack.Size && "BeginGroup/EndGroup Mismatch!"); - IM_ASSERT(SizeOfBeginPopupStack == g.BeginPopupStack.Size && "BeginPopup/EndPopup or BeginMenu/EndMenu Mismatch!"); - IM_ASSERT(SizeOfDisabledStack == g.DisabledStackSize && "BeginDisabled/EndDisabled Mismatch!"); - IM_ASSERT(SizeOfItemFlagsStack >= g.ItemFlagsStack.Size && "PushItemFlag/PopItemFlag Mismatch!"); - IM_ASSERT(SizeOfColorStack >= g.ColorStack.Size && "PushStyleColor/PopStyleColor Mismatch!"); - IM_ASSERT(SizeOfStyleVarStack >= g.StyleVarStack.Size && "PushStyleVar/PopStyleVar Mismatch!"); - IM_ASSERT(SizeOfFontStack >= g.FontStack.Size && "PushFont/PopFont Mismatch!"); - IM_ASSERT(SizeOfFocusScopeStack == g.FocusScopeStack.Size && "PushFocusScope/PopFocusScope Mismatch!"); -} - - -//----------------------------------------------------------------------------- -// [SECTION] LAYOUT -//----------------------------------------------------------------------------- -// - ItemSize() -// - ItemAdd() -// - SameLine() -// - GetCursorScreenPos() -// - SetCursorScreenPos() -// - GetCursorPos(), GetCursorPosX(), GetCursorPosY() -// - SetCursorPos(), SetCursorPosX(), SetCursorPosY() -// - GetCursorStartPos() -// - Indent() -// - Unindent() -// - SetNextItemWidth() -// - PushItemWidth() -// - PushMultiItemsWidths() -// - PopItemWidth() -// - CalcItemWidth() -// - CalcItemSize() -// - GetTextLineHeight() -// - GetTextLineHeightWithSpacing() -// - GetFrameHeight() -// - GetFrameHeightWithSpacing() -// - GetContentRegionMax() -// - GetContentRegionMaxAbs() [Internal] -// - GetContentRegionAvail(), -// - GetWindowContentRegionMin(), GetWindowContentRegionMax() -// - BeginGroup() -// - EndGroup() -// Also see in imgui_widgets: tab bars, and in imgui_tables: tables, columns. -//----------------------------------------------------------------------------- - -// Advance cursor given item size for layout. -// Register minimum needed size so it can extend the bounding box used for auto-fit calculation. -// See comments in ItemAdd() about how/why the size provided to ItemSize() vs ItemAdd() may often different. -void ImGui::ItemSize(const ImVec2& size, float text_baseline_y) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - if (window->SkipItems) - return; - - // We increase the height in this function to accommodate for baseline offset. - // In theory we should be offsetting the starting position (window->DC.CursorPos), that will be the topic of a larger refactor, - // but since ItemSize() is not yet an API that moves the cursor (to handle e.g. wrapping) enlarging the height has the same effect. - const float offset_to_match_baseline_y = (text_baseline_y >= 0) ? ImMax(0.0f, window->DC.CurrLineTextBaseOffset - text_baseline_y) : 0.0f; - - const float line_y1 = window->DC.IsSameLine ? window->DC.CursorPosPrevLine.y : window->DC.CursorPos.y; - const float line_height = ImMax(window->DC.CurrLineSize.y, /*ImMax(*/window->DC.CursorPos.y - line_y1/*, 0.0f)*/ + size.y + offset_to_match_baseline_y); - - // Always align ourselves on pixel boundaries - //if (g.IO.KeyAlt) window->DrawList->AddRect(window->DC.CursorPos, window->DC.CursorPos + ImVec2(size.x, line_height), IM_COL32(255,0,0,200)); // [DEBUG] - window->DC.CursorPosPrevLine.x = window->DC.CursorPos.x + size.x; - window->DC.CursorPosPrevLine.y = line_y1; - window->DC.CursorPos.x = IM_TRUNC(window->Pos.x + window->DC.Indent.x + window->DC.ColumnsOffset.x); // Next line - window->DC.CursorPos.y = IM_TRUNC(line_y1 + line_height + g.Style.ItemSpacing.y); // Next line - window->DC.CursorMaxPos.x = ImMax(window->DC.CursorMaxPos.x, window->DC.CursorPosPrevLine.x); - window->DC.CursorMaxPos.y = ImMax(window->DC.CursorMaxPos.y, window->DC.CursorPos.y - g.Style.ItemSpacing.y); - //if (g.IO.KeyAlt) window->DrawList->AddCircle(window->DC.CursorMaxPos, 3.0f, IM_COL32(255,0,0,255), 4); // [DEBUG] - - window->DC.PrevLineSize.y = line_height; - window->DC.CurrLineSize.y = 0.0f; - window->DC.PrevLineTextBaseOffset = ImMax(window->DC.CurrLineTextBaseOffset, text_baseline_y); - window->DC.CurrLineTextBaseOffset = 0.0f; - window->DC.IsSameLine = window->DC.IsSetPos = false; - - // Horizontal layout mode - if (window->DC.LayoutType == ImGuiLayoutType_Horizontal) - SameLine(); -} - -// Declare item bounding box for clipping and interaction. -// Note that the size can be different than the one provided to ItemSize(). Typically, widgets that spread over available surface -// declare their minimum size requirement to ItemSize() and provide a larger region to ItemAdd() which is used drawing/interaction. -bool ImGui::ItemAdd(const ImRect& bb, ImGuiID id, const ImRect* nav_bb_arg, ImGuiItemFlags extra_flags) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - - // Set item data - // (DisplayRect is left untouched, made valid when ImGuiItemStatusFlags_HasDisplayRect is set) - g.LastItemData.ID = id; - g.LastItemData.Rect = bb; - g.LastItemData.NavRect = nav_bb_arg ? *nav_bb_arg : bb; - g.LastItemData.InFlags = g.CurrentItemFlags | g.NextItemData.ItemFlags | extra_flags; - g.LastItemData.StatusFlags = ImGuiItemStatusFlags_None; - // Note: we don't copy 'g.NextItemData.SelectionUserData' to an hypothetical g.LastItemData.SelectionUserData: since the former is not cleared. - - // Directional navigation processing - if (id != 0) - { - KeepAliveID(id); - - // Runs prior to clipping early-out - // (a) So that NavInitRequest can be honored, for newly opened windows to select a default widget - // (b) So that we can scroll up/down past clipped items. This adds a small O(N) cost to regular navigation requests - // unfortunately, but it is still limited to one window. It may not scale very well for windows with ten of - // thousands of item, but at least NavMoveRequest is only set on user interaction, aka maximum once a frame. - // We could early out with "if (is_clipped && !g.NavInitRequest) return false;" but when we wouldn't be able - // to reach unclipped widgets. This would work if user had explicit scrolling control (e.g. mapped on a stick). - // We intentionally don't check if g.NavWindow != NULL because g.NavAnyRequest should only be set when it is non null. - // If we crash on a NULL g.NavWindow we need to fix the bug elsewhere. - if (!(g.LastItemData.InFlags & ImGuiItemFlags_NoNav)) - { - window->DC.NavLayersActiveMaskNext |= (1 << window->DC.NavLayerCurrent); - if (g.NavId == id || g.NavAnyRequest) - if (g.NavWindow->RootWindowForNav == window->RootWindowForNav) - if (window == g.NavWindow || ((window->Flags | g.NavWindow->Flags) & ImGuiWindowFlags_NavFlattened)) - NavProcessItem(); - } - - // [DEBUG] People keep stumbling on this problem and using "" as identifier in the root of a window instead of "##something". - // Empty identifier are valid and useful in a small amount of cases, but 99.9% of the time you want to use "##something". - // READ THE FAQ: https://dearimgui.com/faq - IM_ASSERT(id != window->ID && "Cannot have an empty ID at the root of a window. If you need an empty label, use ## and read the FAQ about how the ID Stack works!"); - } - g.NextItemData.Flags = ImGuiNextItemDataFlags_None; - g.NextItemData.ItemFlags = ImGuiItemFlags_None; - -#ifdef IMGUI_ENABLE_TEST_ENGINE - if (id != 0) - IMGUI_TEST_ENGINE_ITEM_ADD(id, g.LastItemData.NavRect, &g.LastItemData); -#endif - - // Clipping test - // (FIXME: This is a modified copy of IsClippedEx() so we can reuse the is_rect_visible value) - //const bool is_clipped = IsClippedEx(bb, id); - //if (is_clipped) - // return false; - const bool is_rect_visible = bb.Overlaps(window->ClipRect); - if (!is_rect_visible) - if (id == 0 || (id != g.ActiveId && id != g.ActiveIdPreviousFrame && id != g.NavId)) - if (!g.LogEnabled) - return false; - - // [DEBUG] -#ifndef IMGUI_DISABLE_DEBUG_TOOLS - if (id != 0 && id == g.DebugLocateId) - DebugLocateItemResolveWithLastItem(); -#endif - //if (g.IO.KeyAlt) window->DrawList->AddRect(bb.Min, bb.Max, IM_COL32(255,255,0,120)); // [DEBUG] - //if ((g.LastItemData.InFlags & ImGuiItemFlags_NoNav) == 0) - // window->DrawList->AddRect(g.LastItemData.NavRect.Min, g.LastItemData.NavRect.Max, IM_COL32(255,255,0,255)); // [DEBUG] - - // We need to calculate this now to take account of the current clipping rectangle (as items like Selectable may change them) - if (is_rect_visible) - g.LastItemData.StatusFlags |= ImGuiItemStatusFlags_Visible; - if (IsMouseHoveringRect(bb.Min, bb.Max)) - g.LastItemData.StatusFlags |= ImGuiItemStatusFlags_HoveredRect; - return true; -} - -// Gets back to previous line and continue with horizontal layout -// offset_from_start_x == 0 : follow right after previous item -// offset_from_start_x != 0 : align to specified x position (relative to window/group left) -// spacing_w < 0 : use default spacing if offset_from_start_x == 0, no spacing if offset_from_start_x != 0 -// spacing_w >= 0 : enforce spacing amount -void ImGui::SameLine(float offset_from_start_x, float spacing_w) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - if (window->SkipItems) - return; - - if (offset_from_start_x != 0.0f) - { - if (spacing_w < 0.0f) - spacing_w = 0.0f; - window->DC.CursorPos.x = window->Pos.x - window->Scroll.x + offset_from_start_x + spacing_w + window->DC.GroupOffset.x + window->DC.ColumnsOffset.x; - window->DC.CursorPos.y = window->DC.CursorPosPrevLine.y; - } - else - { - if (spacing_w < 0.0f) - spacing_w = g.Style.ItemSpacing.x; - window->DC.CursorPos.x = window->DC.CursorPosPrevLine.x + spacing_w; - window->DC.CursorPos.y = window->DC.CursorPosPrevLine.y; - } - window->DC.CurrLineSize = window->DC.PrevLineSize; - window->DC.CurrLineTextBaseOffset = window->DC.PrevLineTextBaseOffset; - window->DC.IsSameLine = true; -} - -ImVec2 ImGui::GetCursorScreenPos() -{ - ImGuiWindow* window = GetCurrentWindowRead(); - return window->DC.CursorPos; -} - -void ImGui::SetCursorScreenPos(const ImVec2& pos) -{ - ImGuiWindow* window = GetCurrentWindow(); - window->DC.CursorPos = pos; - //window->DC.CursorMaxPos = ImMax(window->DC.CursorMaxPos, window->DC.CursorPos); - window->DC.IsSetPos = true; -} - -// User generally sees positions in window coordinates. Internally we store CursorPos in absolute screen coordinates because it is more convenient. -// Conversion happens as we pass the value to user, but it makes our naming convention confusing because GetCursorPos() == (DC.CursorPos - window.Pos). May want to rename 'DC.CursorPos'. -ImVec2 ImGui::GetCursorPos() -{ - ImGuiWindow* window = GetCurrentWindowRead(); - return window->DC.CursorPos - window->Pos + window->Scroll; -} - -float ImGui::GetCursorPosX() -{ - ImGuiWindow* window = GetCurrentWindowRead(); - return window->DC.CursorPos.x - window->Pos.x + window->Scroll.x; -} - -float ImGui::GetCursorPosY() -{ - ImGuiWindow* window = GetCurrentWindowRead(); - return window->DC.CursorPos.y - window->Pos.y + window->Scroll.y; -} - -void ImGui::SetCursorPos(const ImVec2& local_pos) -{ - ImGuiWindow* window = GetCurrentWindow(); - window->DC.CursorPos = window->Pos - window->Scroll + local_pos; - //window->DC.CursorMaxPos = ImMax(window->DC.CursorMaxPos, window->DC.CursorPos); - window->DC.IsSetPos = true; -} - -void ImGui::SetCursorPosX(float x) -{ - ImGuiWindow* window = GetCurrentWindow(); - window->DC.CursorPos.x = window->Pos.x - window->Scroll.x + x; - //window->DC.CursorMaxPos.x = ImMax(window->DC.CursorMaxPos.x, window->DC.CursorPos.x); - window->DC.IsSetPos = true; -} - -void ImGui::SetCursorPosY(float y) -{ - ImGuiWindow* window = GetCurrentWindow(); - window->DC.CursorPos.y = window->Pos.y - window->Scroll.y + y; - //window->DC.CursorMaxPos.y = ImMax(window->DC.CursorMaxPos.y, window->DC.CursorPos.y); - window->DC.IsSetPos = true; -} - -ImVec2 ImGui::GetCursorStartPos() -{ - ImGuiWindow* window = GetCurrentWindowRead(); - return window->DC.CursorStartPos - window->Pos; -} - -void ImGui::Indent(float indent_w) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = GetCurrentWindow(); - window->DC.Indent.x += (indent_w != 0.0f) ? indent_w : g.Style.IndentSpacing; - window->DC.CursorPos.x = window->Pos.x + window->DC.Indent.x + window->DC.ColumnsOffset.x; -} - -void ImGui::Unindent(float indent_w) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = GetCurrentWindow(); - window->DC.Indent.x -= (indent_w != 0.0f) ? indent_w : g.Style.IndentSpacing; - window->DC.CursorPos.x = window->Pos.x + window->DC.Indent.x + window->DC.ColumnsOffset.x; -} - -// Affect large frame+labels widgets only. -void ImGui::SetNextItemWidth(float item_width) -{ - ImGuiContext& g = *GImGui; - g.NextItemData.Flags |= ImGuiNextItemDataFlags_HasWidth; - g.NextItemData.Width = item_width; -} - -// FIXME: Remove the == 0.0f behavior? -void ImGui::PushItemWidth(float item_width) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - window->DC.ItemWidthStack.push_back(window->DC.ItemWidth); // Backup current width - window->DC.ItemWidth = (item_width == 0.0f ? window->ItemWidthDefault : item_width); - g.NextItemData.Flags &= ~ImGuiNextItemDataFlags_HasWidth; -} - -void ImGui::PushMultiItemsWidths(int components, float w_full) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - const ImGuiStyle& style = g.Style; - const float w_item_one = ImMax(1.0f, IM_TRUNC((w_full - (style.ItemInnerSpacing.x) * (components - 1)) / (float)components)); - const float w_item_last = ImMax(1.0f, IM_TRUNC(w_full - (w_item_one + style.ItemInnerSpacing.x) * (components - 1))); - window->DC.ItemWidthStack.push_back(window->DC.ItemWidth); // Backup current width - window->DC.ItemWidthStack.push_back(w_item_last); - for (int i = 0; i < components - 2; i++) - window->DC.ItemWidthStack.push_back(w_item_one); - window->DC.ItemWidth = (components == 1) ? w_item_last : w_item_one; - g.NextItemData.Flags &= ~ImGuiNextItemDataFlags_HasWidth; -} - -void ImGui::PopItemWidth() -{ - ImGuiWindow* window = GetCurrentWindow(); - window->DC.ItemWidth = window->DC.ItemWidthStack.back(); - window->DC.ItemWidthStack.pop_back(); -} - -// Calculate default item width given value passed to PushItemWidth() or SetNextItemWidth(). -// The SetNextItemWidth() data is generally cleared/consumed by ItemAdd() or NextItemData.ClearFlags() -float ImGui::CalcItemWidth() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - float w; - if (g.NextItemData.Flags & ImGuiNextItemDataFlags_HasWidth) - w = g.NextItemData.Width; - else - w = window->DC.ItemWidth; - if (w < 0.0f) - { - float region_max_x = GetContentRegionMaxAbs().x; - w = ImMax(1.0f, region_max_x - window->DC.CursorPos.x + w); - } - w = IM_TRUNC(w); - return w; -} - -// [Internal] Calculate full item size given user provided 'size' parameter and default width/height. Default width is often == CalcItemWidth(). -// Those two functions CalcItemWidth vs CalcItemSize are awkwardly named because they are not fully symmetrical. -// Note that only CalcItemWidth() is publicly exposed. -// The 4.0f here may be changed to match CalcItemWidth() and/or BeginChild() (right now we have a mismatch which is harmless but undesirable) -ImVec2 ImGui::CalcItemSize(ImVec2 size, float default_w, float default_h) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - - ImVec2 region_max; - if (size.x < 0.0f || size.y < 0.0f) - region_max = GetContentRegionMaxAbs(); - - if (size.x == 0.0f) - size.x = default_w; - else if (size.x < 0.0f) - size.x = ImMax(4.0f, region_max.x - window->DC.CursorPos.x + size.x); - - if (size.y == 0.0f) - size.y = default_h; - else if (size.y < 0.0f) - size.y = ImMax(4.0f, region_max.y - window->DC.CursorPos.y + size.y); - - return size; -} - -float ImGui::GetTextLineHeight() -{ - ImGuiContext& g = *GImGui; - return g.FontSize; -} - -float ImGui::GetTextLineHeightWithSpacing() -{ - ImGuiContext& g = *GImGui; - return g.FontSize + g.Style.ItemSpacing.y; -} - -float ImGui::GetFrameHeight() -{ - ImGuiContext& g = *GImGui; - return g.FontSize + g.Style.FramePadding.y * 2.0f; -} - -float ImGui::GetFrameHeightWithSpacing() -{ - ImGuiContext& g = *GImGui; - return g.FontSize + g.Style.FramePadding.y * 2.0f + g.Style.ItemSpacing.y; -} - -// FIXME: All the Contents Region function are messy or misleading. WE WILL AIM TO OBSOLETE ALL OF THEM WITH A NEW "WORK RECT" API. Thanks for your patience! - -// FIXME: This is in window space (not screen space!). -ImVec2 ImGui::GetContentRegionMax() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - ImVec2 mx = (window->DC.CurrentColumns || g.CurrentTable) ? window->WorkRect.Max : window->ContentRegionRect.Max; - return mx - window->Pos; -} - -// [Internal] Absolute coordinate. Saner. This is not exposed until we finishing refactoring work rect features. -ImVec2 ImGui::GetContentRegionMaxAbs() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - ImVec2 mx = (window->DC.CurrentColumns || g.CurrentTable) ? window->WorkRect.Max : window->ContentRegionRect.Max; - return mx; -} - -ImVec2 ImGui::GetContentRegionAvail() -{ - ImGuiWindow* window = GImGui->CurrentWindow; - return GetContentRegionMaxAbs() - window->DC.CursorPos; -} - -// In window space (not screen space!) -ImVec2 ImGui::GetWindowContentRegionMin() -{ - ImGuiWindow* window = GImGui->CurrentWindow; - return window->ContentRegionRect.Min - window->Pos; -} - -ImVec2 ImGui::GetWindowContentRegionMax() -{ - ImGuiWindow* window = GImGui->CurrentWindow; - return window->ContentRegionRect.Max - window->Pos; -} - -// Lock horizontal starting position + capture group bounding box into one "item" (so you can use IsItemHovered() or layout primitives such as SameLine() on whole group, etc.) -// Groups are currently a mishmash of functionalities which should perhaps be clarified and separated. -// FIXME-OPT: Could we safely early out on ->SkipItems? -void ImGui::BeginGroup() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - - g.GroupStack.resize(g.GroupStack.Size + 1); - ImGuiGroupData& group_data = g.GroupStack.back(); - group_data.WindowID = window->ID; - group_data.BackupCursorPos = window->DC.CursorPos; - group_data.BackupCursorPosPrevLine = window->DC.CursorPosPrevLine; - group_data.BackupCursorMaxPos = window->DC.CursorMaxPos; - group_data.BackupIndent = window->DC.Indent; - group_data.BackupGroupOffset = window->DC.GroupOffset; - group_data.BackupCurrLineSize = window->DC.CurrLineSize; - group_data.BackupCurrLineTextBaseOffset = window->DC.CurrLineTextBaseOffset; - group_data.BackupActiveIdIsAlive = g.ActiveIdIsAlive; - group_data.BackupHoveredIdIsAlive = g.HoveredId != 0; - group_data.BackupIsSameLine = window->DC.IsSameLine; - group_data.BackupActiveIdPreviousFrameIsAlive = g.ActiveIdPreviousFrameIsAlive; - group_data.EmitItem = true; - - window->DC.GroupOffset.x = window->DC.CursorPos.x - window->Pos.x - window->DC.ColumnsOffset.x; - window->DC.Indent = window->DC.GroupOffset; - window->DC.CursorMaxPos = window->DC.CursorPos; - window->DC.CurrLineSize = ImVec2(0.0f, 0.0f); - if (g.LogEnabled) - g.LogLinePosY = -FLT_MAX; // To enforce a carriage return -} - -void ImGui::EndGroup() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - IM_ASSERT(g.GroupStack.Size > 0); // Mismatched BeginGroup()/EndGroup() calls - - ImGuiGroupData& group_data = g.GroupStack.back(); - IM_ASSERT(group_data.WindowID == window->ID); // EndGroup() in wrong window? - - if (window->DC.IsSetPos) - ErrorCheckUsingSetCursorPosToExtendParentBoundaries(); - - ImRect group_bb(group_data.BackupCursorPos, ImMax(window->DC.CursorMaxPos, group_data.BackupCursorPos)); - - window->DC.CursorPos = group_data.BackupCursorPos; - window->DC.CursorPosPrevLine = group_data.BackupCursorPosPrevLine; - window->DC.CursorMaxPos = ImMax(group_data.BackupCursorMaxPos, window->DC.CursorMaxPos); - window->DC.Indent = group_data.BackupIndent; - window->DC.GroupOffset = group_data.BackupGroupOffset; - window->DC.CurrLineSize = group_data.BackupCurrLineSize; - window->DC.CurrLineTextBaseOffset = group_data.BackupCurrLineTextBaseOffset; - window->DC.IsSameLine = group_data.BackupIsSameLine; - if (g.LogEnabled) - g.LogLinePosY = -FLT_MAX; // To enforce a carriage return - - if (!group_data.EmitItem) - { - g.GroupStack.pop_back(); - return; - } - - window->DC.CurrLineTextBaseOffset = ImMax(window->DC.PrevLineTextBaseOffset, group_data.BackupCurrLineTextBaseOffset); // FIXME: Incorrect, we should grab the base offset from the *first line* of the group but it is hard to obtain now. - ItemSize(group_bb.GetSize()); - ItemAdd(group_bb, 0, NULL, ImGuiItemFlags_NoTabStop); - - // If the current ActiveId was declared within the boundary of our group, we copy it to LastItemId so IsItemActive(), IsItemDeactivated() etc. will be functional on the entire group. - // It would be neater if we replaced window.DC.LastItemId by e.g. 'bool LastItemIsActive', but would put a little more burden on individual widgets. - // Also if you grep for LastItemId you'll notice it is only used in that context. - // (The two tests not the same because ActiveIdIsAlive is an ID itself, in order to be able to handle ActiveId being overwritten during the frame.) - const bool group_contains_curr_active_id = (group_data.BackupActiveIdIsAlive != g.ActiveId) && (g.ActiveIdIsAlive == g.ActiveId) && g.ActiveId; - const bool group_contains_prev_active_id = (group_data.BackupActiveIdPreviousFrameIsAlive == false) && (g.ActiveIdPreviousFrameIsAlive == true); - if (group_contains_curr_active_id) - g.LastItemData.ID = g.ActiveId; - else if (group_contains_prev_active_id) - g.LastItemData.ID = g.ActiveIdPreviousFrame; - g.LastItemData.Rect = group_bb; - - // Forward Hovered flag - const bool group_contains_curr_hovered_id = (group_data.BackupHoveredIdIsAlive == false) && g.HoveredId != 0; - if (group_contains_curr_hovered_id) - g.LastItemData.StatusFlags |= ImGuiItemStatusFlags_HoveredWindow; - - // Forward Edited flag - if (group_contains_curr_active_id && g.ActiveIdHasBeenEditedThisFrame) - g.LastItemData.StatusFlags |= ImGuiItemStatusFlags_Edited; - - // Forward Deactivated flag - g.LastItemData.StatusFlags |= ImGuiItemStatusFlags_HasDeactivated; - if (group_contains_prev_active_id && g.ActiveId != g.ActiveIdPreviousFrame) - g.LastItemData.StatusFlags |= ImGuiItemStatusFlags_Deactivated; - - g.GroupStack.pop_back(); - if (g.DebugShowGroupRects) - window->DrawList->AddRect(group_bb.Min, group_bb.Max, IM_COL32(255,0,255,255)); // [Debug] -} - - -//----------------------------------------------------------------------------- -// [SECTION] SCROLLING -//----------------------------------------------------------------------------- - -// Helper to snap on edges when aiming at an item very close to the edge, -// So the difference between WindowPadding and ItemSpacing will be in the visible area after scrolling. -// When we refactor the scrolling API this may be configurable with a flag? -// Note that the effect for this won't be visible on X axis with default Style settings as WindowPadding.x == ItemSpacing.x by default. -static float CalcScrollEdgeSnap(float target, float snap_min, float snap_max, float snap_threshold, float center_ratio) -{ - if (target <= snap_min + snap_threshold) - return ImLerp(snap_min, target, center_ratio); - if (target >= snap_max - snap_threshold) - return ImLerp(target, snap_max, center_ratio); - return target; -} - -static ImVec2 CalcNextScrollFromScrollTargetAndClamp(ImGuiWindow* window) -{ - ImVec2 scroll = window->Scroll; - ImVec2 decoration_size(window->DecoOuterSizeX1 + window->DecoInnerSizeX1 + window->DecoOuterSizeX2, window->DecoOuterSizeY1 + window->DecoInnerSizeY1 + window->DecoOuterSizeY2); - for (int axis = 0; axis < 2; axis++) - { - if (window->ScrollTarget[axis] < FLT_MAX) - { - float center_ratio = window->ScrollTargetCenterRatio[axis]; - float scroll_target = window->ScrollTarget[axis]; - if (window->ScrollTargetEdgeSnapDist[axis] > 0.0f) - { - float snap_min = 0.0f; - float snap_max = window->ScrollMax[axis] + window->SizeFull[axis] - decoration_size[axis]; - scroll_target = CalcScrollEdgeSnap(scroll_target, snap_min, snap_max, window->ScrollTargetEdgeSnapDist[axis], center_ratio); - } - scroll[axis] = scroll_target - center_ratio * (window->SizeFull[axis] - decoration_size[axis]); - } - scroll[axis] = IM_TRUNC(ImMax(scroll[axis], 0.0f)); - if (!window->Collapsed && !window->SkipItems) - scroll[axis] = ImMin(scroll[axis], window->ScrollMax[axis]); - } - return scroll; -} - -void ImGui::ScrollToItem(ImGuiScrollFlags flags) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - ScrollToRectEx(window, g.LastItemData.NavRect, flags); -} - -void ImGui::ScrollToRect(ImGuiWindow* window, const ImRect& item_rect, ImGuiScrollFlags flags) -{ - ScrollToRectEx(window, item_rect, flags); -} - -// Scroll to keep newly navigated item fully into view -ImVec2 ImGui::ScrollToRectEx(ImGuiWindow* window, const ImRect& item_rect, ImGuiScrollFlags flags) -{ - ImGuiContext& g = *GImGui; - ImRect scroll_rect(window->InnerRect.Min - ImVec2(1, 1), window->InnerRect.Max + ImVec2(1, 1)); - scroll_rect.Min.x = ImMin(scroll_rect.Min.x + window->DecoInnerSizeX1, scroll_rect.Max.x); - scroll_rect.Min.y = ImMin(scroll_rect.Min.y + window->DecoInnerSizeY1, scroll_rect.Max.y); - //GetForegroundDrawList(window)->AddRect(item_rect.Min, item_rect.Max, IM_COL32(255,0,0,255), 0.0f, 0, 5.0f); // [DEBUG] - //GetForegroundDrawList(window)->AddRect(scroll_rect.Min, scroll_rect.Max, IM_COL32_WHITE); // [DEBUG] - - // Check that only one behavior is selected per axis - IM_ASSERT((flags & ImGuiScrollFlags_MaskX_) == 0 || ImIsPowerOfTwo(flags & ImGuiScrollFlags_MaskX_)); - IM_ASSERT((flags & ImGuiScrollFlags_MaskY_) == 0 || ImIsPowerOfTwo(flags & ImGuiScrollFlags_MaskY_)); - - // Defaults - ImGuiScrollFlags in_flags = flags; - if ((flags & ImGuiScrollFlags_MaskX_) == 0 && window->ScrollbarX) - flags |= ImGuiScrollFlags_KeepVisibleEdgeX; - if ((flags & ImGuiScrollFlags_MaskY_) == 0) - flags |= window->Appearing ? ImGuiScrollFlags_AlwaysCenterY : ImGuiScrollFlags_KeepVisibleEdgeY; - - const bool fully_visible_x = item_rect.Min.x >= scroll_rect.Min.x && item_rect.Max.x <= scroll_rect.Max.x; - const bool fully_visible_y = item_rect.Min.y >= scroll_rect.Min.y && item_rect.Max.y <= scroll_rect.Max.y; - const bool can_be_fully_visible_x = (item_rect.GetWidth() + g.Style.ItemSpacing.x * 2.0f) <= scroll_rect.GetWidth() || (window->AutoFitFramesX > 0) || (window->Flags & ImGuiWindowFlags_AlwaysAutoResize) != 0; - const bool can_be_fully_visible_y = (item_rect.GetHeight() + g.Style.ItemSpacing.y * 2.0f) <= scroll_rect.GetHeight() || (window->AutoFitFramesY > 0) || (window->Flags & ImGuiWindowFlags_AlwaysAutoResize) != 0; - - if ((flags & ImGuiScrollFlags_KeepVisibleEdgeX) && !fully_visible_x) - { - if (item_rect.Min.x < scroll_rect.Min.x || !can_be_fully_visible_x) - SetScrollFromPosX(window, item_rect.Min.x - g.Style.ItemSpacing.x - window->Pos.x, 0.0f); - else if (item_rect.Max.x >= scroll_rect.Max.x) - SetScrollFromPosX(window, item_rect.Max.x + g.Style.ItemSpacing.x - window->Pos.x, 1.0f); - } - else if (((flags & ImGuiScrollFlags_KeepVisibleCenterX) && !fully_visible_x) || (flags & ImGuiScrollFlags_AlwaysCenterX)) - { - if (can_be_fully_visible_x) - SetScrollFromPosX(window, ImTrunc((item_rect.Min.x + item_rect.Max.x) * 0.5f) - window->Pos.x, 0.5f); - else - SetScrollFromPosX(window, item_rect.Min.x - window->Pos.x, 0.0f); - } - - if ((flags & ImGuiScrollFlags_KeepVisibleEdgeY) && !fully_visible_y) - { - if (item_rect.Min.y < scroll_rect.Min.y || !can_be_fully_visible_y) - SetScrollFromPosY(window, item_rect.Min.y - g.Style.ItemSpacing.y - window->Pos.y, 0.0f); - else if (item_rect.Max.y >= scroll_rect.Max.y) - SetScrollFromPosY(window, item_rect.Max.y + g.Style.ItemSpacing.y - window->Pos.y, 1.0f); - } - else if (((flags & ImGuiScrollFlags_KeepVisibleCenterY) && !fully_visible_y) || (flags & ImGuiScrollFlags_AlwaysCenterY)) - { - if (can_be_fully_visible_y) - SetScrollFromPosY(window, ImTrunc((item_rect.Min.y + item_rect.Max.y) * 0.5f) - window->Pos.y, 0.5f); - else - SetScrollFromPosY(window, item_rect.Min.y - window->Pos.y, 0.0f); - } - - ImVec2 next_scroll = CalcNextScrollFromScrollTargetAndClamp(window); - ImVec2 delta_scroll = next_scroll - window->Scroll; - - // Also scroll parent window to keep us into view if necessary - if (!(flags & ImGuiScrollFlags_NoScrollParent) && (window->Flags & ImGuiWindowFlags_ChildWindow)) - { - // FIXME-SCROLL: May be an option? - if ((in_flags & (ImGuiScrollFlags_AlwaysCenterX | ImGuiScrollFlags_KeepVisibleCenterX)) != 0) - in_flags = (in_flags & ~ImGuiScrollFlags_MaskX_) | ImGuiScrollFlags_KeepVisibleEdgeX; - if ((in_flags & (ImGuiScrollFlags_AlwaysCenterY | ImGuiScrollFlags_KeepVisibleCenterY)) != 0) - in_flags = (in_flags & ~ImGuiScrollFlags_MaskY_) | ImGuiScrollFlags_KeepVisibleEdgeY; - delta_scroll += ScrollToRectEx(window->ParentWindow, ImRect(item_rect.Min - delta_scroll, item_rect.Max - delta_scroll), in_flags); - } - - return delta_scroll; -} - -float ImGui::GetScrollX() -{ - ImGuiWindow* window = GImGui->CurrentWindow; - return window->Scroll.x; -} - -float ImGui::GetScrollY() -{ - ImGuiWindow* window = GImGui->CurrentWindow; - return window->Scroll.y; -} - -float ImGui::GetScrollMaxX() -{ - ImGuiWindow* window = GImGui->CurrentWindow; - return window->ScrollMax.x; -} - -float ImGui::GetScrollMaxY() -{ - ImGuiWindow* window = GImGui->CurrentWindow; - return window->ScrollMax.y; -} - -void ImGui::SetScrollX(ImGuiWindow* window, float scroll_x) -{ - window->ScrollTarget.x = scroll_x; - window->ScrollTargetCenterRatio.x = 0.0f; - window->ScrollTargetEdgeSnapDist.x = 0.0f; -} - -void ImGui::SetScrollY(ImGuiWindow* window, float scroll_y) -{ - window->ScrollTarget.y = scroll_y; - window->ScrollTargetCenterRatio.y = 0.0f; - window->ScrollTargetEdgeSnapDist.y = 0.0f; -} - -void ImGui::SetScrollX(float scroll_x) -{ - ImGuiContext& g = *GImGui; - SetScrollX(g.CurrentWindow, scroll_x); -} - -void ImGui::SetScrollY(float scroll_y) -{ - ImGuiContext& g = *GImGui; - SetScrollY(g.CurrentWindow, scroll_y); -} - -// Note that a local position will vary depending on initial scroll value, -// This is a little bit confusing so bear with us: -// - local_pos = (absolution_pos - window->Pos) -// - So local_x/local_y are 0.0f for a position at the upper-left corner of a window, -// and generally local_x/local_y are >(padding+decoration) && <(size-padding-decoration) when in the visible area. -// - They mostly exist because of legacy API. -// Following the rules above, when trying to work with scrolling code, consider that: -// - SetScrollFromPosY(0.0f) == SetScrollY(0.0f + scroll.y) == has no effect! -// - SetScrollFromPosY(-scroll.y) == SetScrollY(-scroll.y + scroll.y) == SetScrollY(0.0f) == reset scroll. Of course writing SetScrollY(0.0f) directly then makes more sense -// We store a target position so centering and clamping can occur on the next frame when we are guaranteed to have a known window size -void ImGui::SetScrollFromPosX(ImGuiWindow* window, float local_x, float center_x_ratio) -{ - IM_ASSERT(center_x_ratio >= 0.0f && center_x_ratio <= 1.0f); - window->ScrollTarget.x = IM_TRUNC(local_x - window->DecoOuterSizeX1 - window->DecoInnerSizeX1 + window->Scroll.x); // Convert local position to scroll offset - window->ScrollTargetCenterRatio.x = center_x_ratio; - window->ScrollTargetEdgeSnapDist.x = 0.0f; -} - -void ImGui::SetScrollFromPosY(ImGuiWindow* window, float local_y, float center_y_ratio) -{ - IM_ASSERT(center_y_ratio >= 0.0f && center_y_ratio <= 1.0f); - window->ScrollTarget.y = IM_TRUNC(local_y - window->DecoOuterSizeY1 - window->DecoInnerSizeY1 + window->Scroll.y); // Convert local position to scroll offset - window->ScrollTargetCenterRatio.y = center_y_ratio; - window->ScrollTargetEdgeSnapDist.y = 0.0f; -} - -void ImGui::SetScrollFromPosX(float local_x, float center_x_ratio) -{ - ImGuiContext& g = *GImGui; - SetScrollFromPosX(g.CurrentWindow, local_x, center_x_ratio); -} - -void ImGui::SetScrollFromPosY(float local_y, float center_y_ratio) -{ - ImGuiContext& g = *GImGui; - SetScrollFromPosY(g.CurrentWindow, local_y, center_y_ratio); -} - -// center_x_ratio: 0.0f left of last item, 0.5f horizontal center of last item, 1.0f right of last item. -void ImGui::SetScrollHereX(float center_x_ratio) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - float spacing_x = ImMax(window->WindowPadding.x, g.Style.ItemSpacing.x); - float target_pos_x = ImLerp(g.LastItemData.Rect.Min.x - spacing_x, g.LastItemData.Rect.Max.x + spacing_x, center_x_ratio); - SetScrollFromPosX(window, target_pos_x - window->Pos.x, center_x_ratio); // Convert from absolute to local pos - - // Tweak: snap on edges when aiming at an item very close to the edge - window->ScrollTargetEdgeSnapDist.x = ImMax(0.0f, window->WindowPadding.x - spacing_x); -} - -// center_y_ratio: 0.0f top of last item, 0.5f vertical center of last item, 1.0f bottom of last item. -void ImGui::SetScrollHereY(float center_y_ratio) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - float spacing_y = ImMax(window->WindowPadding.y, g.Style.ItemSpacing.y); - float target_pos_y = ImLerp(window->DC.CursorPosPrevLine.y - spacing_y, window->DC.CursorPosPrevLine.y + window->DC.PrevLineSize.y + spacing_y, center_y_ratio); - SetScrollFromPosY(window, target_pos_y - window->Pos.y, center_y_ratio); // Convert from absolute to local pos - - // Tweak: snap on edges when aiming at an item very close to the edge - window->ScrollTargetEdgeSnapDist.y = ImMax(0.0f, window->WindowPadding.y - spacing_y); -} - -//----------------------------------------------------------------------------- -// [SECTION] TOOLTIPS -//----------------------------------------------------------------------------- - -bool ImGui::BeginTooltip() -{ - return BeginTooltipEx(ImGuiTooltipFlags_None, ImGuiWindowFlags_None); -} - -bool ImGui::BeginItemTooltip() -{ - if (!IsItemHovered(ImGuiHoveredFlags_ForTooltip)) - return false; - return BeginTooltipEx(ImGuiTooltipFlags_None, ImGuiWindowFlags_None); -} - -bool ImGui::BeginTooltipEx(ImGuiTooltipFlags tooltip_flags, ImGuiWindowFlags extra_window_flags) -{ - ImGuiContext& g = *GImGui; - - if (g.DragDropWithinSource || g.DragDropWithinTarget) - { - // Drag and Drop tooltips are positioning differently than other tooltips: - // - offset visibility to increase visibility around mouse. - // - never clamp within outer viewport boundary. - // We call SetNextWindowPos() to enforce position and disable clamping. - // See FindBestWindowPosForPopup() for positionning logic of other tooltips (not drag and drop ones). - //ImVec2 tooltip_pos = g.IO.MousePos - g.ActiveIdClickOffset - g.Style.WindowPadding; - ImVec2 tooltip_pos = g.IO.MousePos + TOOLTIP_DEFAULT_OFFSET * g.Style.MouseCursorScale; - SetNextWindowPos(tooltip_pos); - SetNextWindowBgAlpha(g.Style.Colors[ImGuiCol_PopupBg].w * 0.60f); - //PushStyleVar(ImGuiStyleVar_Alpha, g.Style.Alpha * 0.60f); // This would be nice but e.g ColorButton with checkboard has issue with transparent colors :( - tooltip_flags |= ImGuiTooltipFlags_OverridePrevious; - } - - char window_name[16]; - ImFormatString(window_name, IM_ARRAYSIZE(window_name), "##Tooltip_%02d", g.TooltipOverrideCount); - if (tooltip_flags & ImGuiTooltipFlags_OverridePrevious) - if (ImGuiWindow* window = FindWindowByName(window_name)) - if (window->Active) - { - // Hide previous tooltip from being displayed. We can't easily "reset" the content of a window so we create a new one. - SetWindowHiddendAndSkipItemsForCurrentFrame(window); - ImFormatString(window_name, IM_ARRAYSIZE(window_name), "##Tooltip_%02d", ++g.TooltipOverrideCount); - } - ImGuiWindowFlags flags = ImGuiWindowFlags_Tooltip | ImGuiWindowFlags_NoInputs | ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_NoMove | ImGuiWindowFlags_NoResize | ImGuiWindowFlags_NoSavedSettings | ImGuiWindowFlags_AlwaysAutoResize | ImGuiWindowFlags_NoDocking; - Begin(window_name, NULL, flags | extra_window_flags); - // 2023-03-09: Added bool return value to the API, but currently always returning true. - // If this ever returns false we need to update BeginDragDropSource() accordingly. - //if (!ret) - // End(); - //return ret; - return true; -} - -void ImGui::EndTooltip() -{ - IM_ASSERT(GetCurrentWindowRead()->Flags & ImGuiWindowFlags_Tooltip); // Mismatched BeginTooltip()/EndTooltip() calls - End(); -} - -void ImGui::SetTooltip(const char* fmt, ...) -{ - va_list args; - va_start(args, fmt); - SetTooltipV(fmt, args); - va_end(args); -} - -void ImGui::SetTooltipV(const char* fmt, va_list args) -{ - if (!BeginTooltipEx(ImGuiTooltipFlags_OverridePrevious, ImGuiWindowFlags_None)) - return; - TextV(fmt, args); - EndTooltip(); -} - -// Shortcut to use 'style.HoverFlagsForTooltipMouse' or 'style.HoverFlagsForTooltipNav'. -// Defaults to == ImGuiHoveredFlags_Stationary | ImGuiHoveredFlags_DelayShort when using the mouse. -void ImGui::SetItemTooltip(const char* fmt, ...) -{ - va_list args; - va_start(args, fmt); - if (IsItemHovered(ImGuiHoveredFlags_ForTooltip)) - SetTooltipV(fmt, args); - va_end(args); -} - -void ImGui::SetItemTooltipV(const char* fmt, va_list args) -{ - if (IsItemHovered(ImGuiHoveredFlags_ForTooltip)) - SetTooltipV(fmt, args); -} - - -//----------------------------------------------------------------------------- -// [SECTION] POPUPS -//----------------------------------------------------------------------------- - -// Supported flags: ImGuiPopupFlags_AnyPopupId, ImGuiPopupFlags_AnyPopupLevel -bool ImGui::IsPopupOpen(ImGuiID id, ImGuiPopupFlags popup_flags) -{ - ImGuiContext& g = *GImGui; - if (popup_flags & ImGuiPopupFlags_AnyPopupId) - { - // Return true if any popup is open at the current BeginPopup() level of the popup stack - // This may be used to e.g. test for another popups already opened to handle popups priorities at the same level. - IM_ASSERT(id == 0); - if (popup_flags & ImGuiPopupFlags_AnyPopupLevel) - return g.OpenPopupStack.Size > 0; - else - return g.OpenPopupStack.Size > g.BeginPopupStack.Size; - } - else - { - if (popup_flags & ImGuiPopupFlags_AnyPopupLevel) - { - // Return true if the popup is open anywhere in the popup stack - for (ImGuiPopupData& popup_data : g.OpenPopupStack) - if (popup_data.PopupId == id) - return true; - return false; - } - else - { - // Return true if the popup is open at the current BeginPopup() level of the popup stack (this is the most-common query) - return g.OpenPopupStack.Size > g.BeginPopupStack.Size && g.OpenPopupStack[g.BeginPopupStack.Size].PopupId == id; - } - } -} - -bool ImGui::IsPopupOpen(const char* str_id, ImGuiPopupFlags popup_flags) -{ - ImGuiContext& g = *GImGui; - ImGuiID id = (popup_flags & ImGuiPopupFlags_AnyPopupId) ? 0 : g.CurrentWindow->GetID(str_id); - if ((popup_flags & ImGuiPopupFlags_AnyPopupLevel) && id != 0) - IM_ASSERT(0 && "Cannot use IsPopupOpen() with a string id and ImGuiPopupFlags_AnyPopupLevel."); // But non-string version is legal and used internally - return IsPopupOpen(id, popup_flags); -} - -// Also see FindBlockingModal(NULL) -ImGuiWindow* ImGui::GetTopMostPopupModal() -{ - ImGuiContext& g = *GImGui; - for (int n = g.OpenPopupStack.Size - 1; n >= 0; n--) - if (ImGuiWindow* popup = g.OpenPopupStack.Data[n].Window) - if (popup->Flags & ImGuiWindowFlags_Modal) - return popup; - return NULL; -} - -// See Demo->Stacked Modal to confirm what this is for. -ImGuiWindow* ImGui::GetTopMostAndVisiblePopupModal() -{ - ImGuiContext& g = *GImGui; - for (int n = g.OpenPopupStack.Size - 1; n >= 0; n--) - if (ImGuiWindow* popup = g.OpenPopupStack.Data[n].Window) - if ((popup->Flags & ImGuiWindowFlags_Modal) && IsWindowActiveAndVisible(popup)) - return popup; - return NULL; -} - -void ImGui::OpenPopup(const char* str_id, ImGuiPopupFlags popup_flags) -{ - ImGuiContext& g = *GImGui; - ImGuiID id = g.CurrentWindow->GetID(str_id); - IMGUI_DEBUG_LOG_POPUP("[popup] OpenPopup(\"%s\" -> 0x%08X)\n", str_id, id); - OpenPopupEx(id, popup_flags); -} - -void ImGui::OpenPopup(ImGuiID id, ImGuiPopupFlags popup_flags) -{ - OpenPopupEx(id, popup_flags); -} - -// Mark popup as open (toggle toward open state). -// Popups are closed when user click outside, or activate a pressable item, or CloseCurrentPopup() is called within a BeginPopup()/EndPopup() block. -// Popup identifiers are relative to the current ID-stack (so OpenPopup and BeginPopup needs to be at the same level). -// One open popup per level of the popup hierarchy (NB: when assigning we reset the Window member of ImGuiPopupRef to NULL) -void ImGui::OpenPopupEx(ImGuiID id, ImGuiPopupFlags popup_flags) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* parent_window = g.CurrentWindow; - const int current_stack_size = g.BeginPopupStack.Size; - - if (popup_flags & ImGuiPopupFlags_NoOpenOverExistingPopup) - if (IsPopupOpen((ImGuiID)0, ImGuiPopupFlags_AnyPopupId)) - return; - - ImGuiPopupData popup_ref; // Tagged as new ref as Window will be set back to NULL if we write this into OpenPopupStack. - popup_ref.PopupId = id; - popup_ref.Window = NULL; - popup_ref.BackupNavWindow = g.NavWindow; // When popup closes focus may be restored to NavWindow (depend on window type). - popup_ref.OpenFrameCount = g.FrameCount; - popup_ref.OpenParentId = parent_window->IDStack.back(); - popup_ref.OpenPopupPos = NavCalcPreferredRefPos(); - popup_ref.OpenMousePos = IsMousePosValid(&g.IO.MousePos) ? g.IO.MousePos : popup_ref.OpenPopupPos; - - IMGUI_DEBUG_LOG_POPUP("[popup] OpenPopupEx(0x%08X)\n", id); - if (g.OpenPopupStack.Size < current_stack_size + 1) - { - g.OpenPopupStack.push_back(popup_ref); - } - else - { - // Gently handle the user mistakenly calling OpenPopup() every frame. It is a programming mistake! However, if we were to run the regular code path, the ui - // would become completely unusable because the popup will always be in hidden-while-calculating-size state _while_ claiming focus. Which would be a very confusing - // situation for the programmer. Instead, we silently allow the popup to proceed, it will keep reappearing and the programming error will be more obvious to understand. - if (g.OpenPopupStack[current_stack_size].PopupId == id && g.OpenPopupStack[current_stack_size].OpenFrameCount == g.FrameCount - 1) - { - g.OpenPopupStack[current_stack_size].OpenFrameCount = popup_ref.OpenFrameCount; - } - else - { - // Close child popups if any, then flag popup for open/reopen - ClosePopupToLevel(current_stack_size, false); - g.OpenPopupStack.push_back(popup_ref); - } - - // When reopening a popup we first refocus its parent, otherwise if its parent is itself a popup it would get closed by ClosePopupsOverWindow(). - // This is equivalent to what ClosePopupToLevel() does. - //if (g.OpenPopupStack[current_stack_size].PopupId == id) - // FocusWindow(parent_window); - } -} - -// When popups are stacked, clicking on a lower level popups puts focus back to it and close popups above it. -// This function closes any popups that are over 'ref_window'. -void ImGui::ClosePopupsOverWindow(ImGuiWindow* ref_window, bool restore_focus_to_window_under_popup) -{ - ImGuiContext& g = *GImGui; - if (g.OpenPopupStack.Size == 0) - return; - - // Don't close our own child popup windows. - int popup_count_to_keep = 0; - if (ref_window) - { - // Find the highest popup which is a descendant of the reference window (generally reference window = NavWindow) - for (; popup_count_to_keep < g.OpenPopupStack.Size; popup_count_to_keep++) - { - ImGuiPopupData& popup = g.OpenPopupStack[popup_count_to_keep]; - if (!popup.Window) - continue; - IM_ASSERT((popup.Window->Flags & ImGuiWindowFlags_Popup) != 0); - if (popup.Window->Flags & ImGuiWindowFlags_ChildWindow) - continue; - - // Trim the stack unless the popup is a direct parent of the reference window (the reference window is often the NavWindow) - // - With this stack of window, clicking/focusing Popup1 will close Popup2 and Popup3: - // Window -> Popup1 -> Popup2 -> Popup3 - // - Each popups may contain child windows, which is why we compare ->RootWindowDockTree! - // Window -> Popup1 -> Popup1_Child -> Popup2 -> Popup2_Child - bool ref_window_is_descendent_of_popup = false; - for (int n = popup_count_to_keep; n < g.OpenPopupStack.Size; n++) - if (ImGuiWindow* popup_window = g.OpenPopupStack[n].Window) - //if (popup_window->RootWindowDockTree == ref_window->RootWindowDockTree) // FIXME-MERGE - if (IsWindowWithinBeginStackOf(ref_window, popup_window)) - { - ref_window_is_descendent_of_popup = true; - break; - } - if (!ref_window_is_descendent_of_popup) - break; - } - } - if (popup_count_to_keep < g.OpenPopupStack.Size) // This test is not required but it allows to set a convenient breakpoint on the statement below - { - IMGUI_DEBUG_LOG_POPUP("[popup] ClosePopupsOverWindow(\"%s\")\n", ref_window ? ref_window->Name : ""); - ClosePopupToLevel(popup_count_to_keep, restore_focus_to_window_under_popup); - } -} - -void ImGui::ClosePopupsExceptModals() -{ - ImGuiContext& g = *GImGui; - - int popup_count_to_keep; - for (popup_count_to_keep = g.OpenPopupStack.Size; popup_count_to_keep > 0; popup_count_to_keep--) - { - ImGuiWindow* window = g.OpenPopupStack[popup_count_to_keep - 1].Window; - if (!window || (window->Flags & ImGuiWindowFlags_Modal)) - break; - } - if (popup_count_to_keep < g.OpenPopupStack.Size) // This test is not required but it allows to set a convenient breakpoint on the statement below - ClosePopupToLevel(popup_count_to_keep, true); -} - -void ImGui::ClosePopupToLevel(int remaining, bool restore_focus_to_window_under_popup) -{ - ImGuiContext& g = *GImGui; - IMGUI_DEBUG_LOG_POPUP("[popup] ClosePopupToLevel(%d), restore_focus_to_window_under_popup=%d\n", remaining, restore_focus_to_window_under_popup); - IM_ASSERT(remaining >= 0 && remaining < g.OpenPopupStack.Size); - - // Trim open popup stack - ImGuiWindow* popup_window = g.OpenPopupStack[remaining].Window; - ImGuiWindow* popup_backup_nav_window = g.OpenPopupStack[remaining].BackupNavWindow; - g.OpenPopupStack.resize(remaining); - - if (restore_focus_to_window_under_popup) - { - ImGuiWindow* focus_window = (popup_window && popup_window->Flags & ImGuiWindowFlags_ChildMenu) ? popup_window->ParentWindow : popup_backup_nav_window; - if (focus_window && !focus_window->WasActive && popup_window) - FocusTopMostWindowUnderOne(popup_window, NULL, NULL, ImGuiFocusRequestFlags_RestoreFocusedChild); // Fallback - else - FocusWindow(focus_window, (g.NavLayer == ImGuiNavLayer_Main) ? ImGuiFocusRequestFlags_RestoreFocusedChild : ImGuiFocusRequestFlags_None); - } -} - -// Close the popup we have begin-ed into. -void ImGui::CloseCurrentPopup() -{ - ImGuiContext& g = *GImGui; - int popup_idx = g.BeginPopupStack.Size - 1; - if (popup_idx < 0 || popup_idx >= g.OpenPopupStack.Size || g.BeginPopupStack[popup_idx].PopupId != g.OpenPopupStack[popup_idx].PopupId) - return; - - // Closing a menu closes its top-most parent popup (unless a modal) - while (popup_idx > 0) - { - ImGuiWindow* popup_window = g.OpenPopupStack[popup_idx].Window; - ImGuiWindow* parent_popup_window = g.OpenPopupStack[popup_idx - 1].Window; - bool close_parent = false; - if (popup_window && (popup_window->Flags & ImGuiWindowFlags_ChildMenu)) - if (parent_popup_window && !(parent_popup_window->Flags & ImGuiWindowFlags_MenuBar)) - close_parent = true; - if (!close_parent) - break; - popup_idx--; - } - IMGUI_DEBUG_LOG_POPUP("[popup] CloseCurrentPopup %d -> %d\n", g.BeginPopupStack.Size - 1, popup_idx); - ClosePopupToLevel(popup_idx, true); - - // A common pattern is to close a popup when selecting a menu item/selectable that will open another window. - // To improve this usage pattern, we avoid nav highlight for a single frame in the parent window. - // Similarly, we could avoid mouse hover highlight in this window but it is less visually problematic. - if (ImGuiWindow* window = g.NavWindow) - window->DC.NavHideHighlightOneFrame = true; -} - -// Attention! BeginPopup() adds default flags which BeginPopupEx()! -bool ImGui::BeginPopupEx(ImGuiID id, ImGuiWindowFlags flags) -{ - ImGuiContext& g = *GImGui; - if (!IsPopupOpen(id, ImGuiPopupFlags_None)) - { - g.NextWindowData.ClearFlags(); // We behave like Begin() and need to consume those values - return false; - } - - char name[20]; - if (flags & ImGuiWindowFlags_ChildMenu) - ImFormatString(name, IM_ARRAYSIZE(name), "##Menu_%02d", g.BeginMenuCount); // Recycle windows based on depth - else - ImFormatString(name, IM_ARRAYSIZE(name), "##Popup_%08x", id); // Not recycling, so we can close/open during the same frame - - flags |= ImGuiWindowFlags_Popup | ImGuiWindowFlags_NoDocking; - bool is_open = Begin(name, NULL, flags); - if (!is_open) // NB: Begin can return false when the popup is completely clipped (e.g. zero size display) - EndPopup(); - - return is_open; -} - -bool ImGui::BeginPopup(const char* str_id, ImGuiWindowFlags flags) -{ - ImGuiContext& g = *GImGui; - if (g.OpenPopupStack.Size <= g.BeginPopupStack.Size) // Early out for performance - { - g.NextWindowData.ClearFlags(); // We behave like Begin() and need to consume those values - return false; - } - flags |= ImGuiWindowFlags_AlwaysAutoResize | ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_NoSavedSettings; - ImGuiID id = g.CurrentWindow->GetID(str_id); - return BeginPopupEx(id, flags); -} - -// If 'p_open' is specified for a modal popup window, the popup will have a regular close button which will close the popup. -// Note that popup visibility status is owned by Dear ImGui (and manipulated with e.g. OpenPopup). -// - *p_open set back to false in BeginPopupModal() when popup is not open. -// - if you set *p_open to false before calling BeginPopupModal(), it will close the popup. -bool ImGui::BeginPopupModal(const char* name, bool* p_open, ImGuiWindowFlags flags) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - const ImGuiID id = window->GetID(name); - if (!IsPopupOpen(id, ImGuiPopupFlags_None)) - { - g.NextWindowData.ClearFlags(); // We behave like Begin() and need to consume those values - if (p_open && *p_open) - *p_open = false; - return false; - } - - // Center modal windows by default for increased visibility - // (this won't really last as settings will kick in, and is mostly for backward compatibility. user may do the same themselves) - // FIXME: Should test for (PosCond & window->SetWindowPosAllowFlags) with the upcoming window. - if ((g.NextWindowData.Flags & ImGuiNextWindowDataFlags_HasPos) == 0) - { - const ImGuiViewport* viewport = window->WasActive ? window->Viewport : GetMainViewport(); // FIXME-VIEWPORT: What may be our reference viewport? - SetNextWindowPos(viewport->GetCenter(), ImGuiCond_FirstUseEver, ImVec2(0.5f, 0.5f)); - } - - flags |= ImGuiWindowFlags_Popup | ImGuiWindowFlags_Modal | ImGuiWindowFlags_NoCollapse | ImGuiWindowFlags_NoDocking; - const bool is_open = Begin(name, p_open, flags); - if (!is_open || (p_open && !*p_open)) // NB: is_open can be 'false' when the popup is completely clipped (e.g. zero size display) - { - EndPopup(); - if (is_open) - ClosePopupToLevel(g.BeginPopupStack.Size, true); - return false; - } - return is_open; -} - -void ImGui::EndPopup() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - IM_ASSERT(window->Flags & ImGuiWindowFlags_Popup); // Mismatched BeginPopup()/EndPopup() calls - IM_ASSERT(g.BeginPopupStack.Size > 0); - - // Make all menus and popups wrap around for now, may need to expose that policy (e.g. focus scope could include wrap/loop policy flags used by new move requests) - if (g.NavWindow == window) - NavMoveRequestTryWrapping(window, ImGuiNavMoveFlags_LoopY); - - // Child-popups don't need to be laid out - IM_ASSERT(g.WithinEndChild == false); - if (window->Flags & ImGuiWindowFlags_ChildWindow) - g.WithinEndChild = true; - End(); - g.WithinEndChild = false; -} - -// Helper to open a popup if mouse button is released over the item -// - This is essentially the same as BeginPopupContextItem() but without the trailing BeginPopup() -void ImGui::OpenPopupOnItemClick(const char* str_id, ImGuiPopupFlags popup_flags) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - int mouse_button = (popup_flags & ImGuiPopupFlags_MouseButtonMask_); - if (IsMouseReleased(mouse_button) && IsItemHovered(ImGuiHoveredFlags_AllowWhenBlockedByPopup)) - { - ImGuiID id = str_id ? window->GetID(str_id) : g.LastItemData.ID; // If user hasn't passed an ID, we can use the LastItemID. Using LastItemID as a Popup ID won't conflict! - IM_ASSERT(id != 0); // You cannot pass a NULL str_id if the last item has no identifier (e.g. a Text() item) - OpenPopupEx(id, popup_flags); - } -} - -// This is a helper to handle the simplest case of associating one named popup to one given widget. -// - To create a popup associated to the last item, you generally want to pass a NULL value to str_id. -// - To create a popup with a specific identifier, pass it in str_id. -// - This is useful when using using BeginPopupContextItem() on an item which doesn't have an identifier, e.g. a Text() call. -// - This is useful when multiple code locations may want to manipulate/open the same popup, given an explicit id. -// - You may want to handle the whole on user side if you have specific needs (e.g. tweaking IsItemHovered() parameters). -// This is essentially the same as: -// id = str_id ? GetID(str_id) : GetItemID(); -// OpenPopupOnItemClick(str_id, ImGuiPopupFlags_MouseButtonRight); -// return BeginPopup(id); -// Which is essentially the same as: -// id = str_id ? GetID(str_id) : GetItemID(); -// if (IsItemHovered() && IsMouseReleased(ImGuiMouseButton_Right)) -// OpenPopup(id); -// return BeginPopup(id); -// The main difference being that this is tweaked to avoid computing the ID twice. -bool ImGui::BeginPopupContextItem(const char* str_id, ImGuiPopupFlags popup_flags) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - if (window->SkipItems) - return false; - ImGuiID id = str_id ? window->GetID(str_id) : g.LastItemData.ID; // If user hasn't passed an ID, we can use the LastItemID. Using LastItemID as a Popup ID won't conflict! - IM_ASSERT(id != 0); // You cannot pass a NULL str_id if the last item has no identifier (e.g. a Text() item) - int mouse_button = (popup_flags & ImGuiPopupFlags_MouseButtonMask_); - if (IsMouseReleased(mouse_button) && IsItemHovered(ImGuiHoveredFlags_AllowWhenBlockedByPopup)) - OpenPopupEx(id, popup_flags); - return BeginPopupEx(id, ImGuiWindowFlags_AlwaysAutoResize | ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_NoSavedSettings); -} - -bool ImGui::BeginPopupContextWindow(const char* str_id, ImGuiPopupFlags popup_flags) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - if (!str_id) - str_id = "window_context"; - ImGuiID id = window->GetID(str_id); - int mouse_button = (popup_flags & ImGuiPopupFlags_MouseButtonMask_); - if (IsMouseReleased(mouse_button) && IsWindowHovered(ImGuiHoveredFlags_AllowWhenBlockedByPopup)) - if (!(popup_flags & ImGuiPopupFlags_NoOpenOverItems) || !IsAnyItemHovered()) - OpenPopupEx(id, popup_flags); - return BeginPopupEx(id, ImGuiWindowFlags_AlwaysAutoResize | ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_NoSavedSettings); -} - -bool ImGui::BeginPopupContextVoid(const char* str_id, ImGuiPopupFlags popup_flags) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - if (!str_id) - str_id = "void_context"; - ImGuiID id = window->GetID(str_id); - int mouse_button = (popup_flags & ImGuiPopupFlags_MouseButtonMask_); - if (IsMouseReleased(mouse_button) && !IsWindowHovered(ImGuiHoveredFlags_AnyWindow)) - if (GetTopMostPopupModal() == NULL) - OpenPopupEx(id, popup_flags); - return BeginPopupEx(id, ImGuiWindowFlags_AlwaysAutoResize | ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_NoSavedSettings); -} - -// r_avoid = the rectangle to avoid (e.g. for tooltip it is a rectangle around the mouse cursor which we want to avoid. for popups it's a small point around the cursor.) -// r_outer = the visible area rectangle, minus safe area padding. If our popup size won't fit because of safe area padding we ignore it. -// (r_outer is usually equivalent to the viewport rectangle minus padding, but when multi-viewports are enabled and monitor -// information are available, it may represent the entire platform monitor from the frame of reference of the current viewport. -// this allows us to have tooltips/popups displayed out of the parent viewport.) -ImVec2 ImGui::FindBestWindowPosForPopupEx(const ImVec2& ref_pos, const ImVec2& size, ImGuiDir* last_dir, const ImRect& r_outer, const ImRect& r_avoid, ImGuiPopupPositionPolicy policy) -{ - ImVec2 base_pos_clamped = ImClamp(ref_pos, r_outer.Min, r_outer.Max - size); - //GetForegroundDrawList()->AddRect(r_avoid.Min, r_avoid.Max, IM_COL32(255,0,0,255)); - //GetForegroundDrawList()->AddRect(r_outer.Min, r_outer.Max, IM_COL32(0,255,0,255)); - - // Combo Box policy (we want a connecting edge) - if (policy == ImGuiPopupPositionPolicy_ComboBox) - { - const ImGuiDir dir_prefered_order[ImGuiDir_COUNT] = { ImGuiDir_Down, ImGuiDir_Right, ImGuiDir_Left, ImGuiDir_Up }; - for (int n = (*last_dir != ImGuiDir_None) ? -1 : 0; n < ImGuiDir_COUNT; n++) - { - const ImGuiDir dir = (n == -1) ? *last_dir : dir_prefered_order[n]; - if (n != -1 && dir == *last_dir) // Already tried this direction? - continue; - ImVec2 pos; - if (dir == ImGuiDir_Down) pos = ImVec2(r_avoid.Min.x, r_avoid.Max.y); // Below, Toward Right (default) - if (dir == ImGuiDir_Right) pos = ImVec2(r_avoid.Min.x, r_avoid.Min.y - size.y); // Above, Toward Right - if (dir == ImGuiDir_Left) pos = ImVec2(r_avoid.Max.x - size.x, r_avoid.Max.y); // Below, Toward Left - if (dir == ImGuiDir_Up) pos = ImVec2(r_avoid.Max.x - size.x, r_avoid.Min.y - size.y); // Above, Toward Left - if (!r_outer.Contains(ImRect(pos, pos + size))) - continue; - *last_dir = dir; - return pos; - } - } - - // Tooltip and Default popup policy - // (Always first try the direction we used on the last frame, if any) - if (policy == ImGuiPopupPositionPolicy_Tooltip || policy == ImGuiPopupPositionPolicy_Default) - { - const ImGuiDir dir_prefered_order[ImGuiDir_COUNT] = { ImGuiDir_Right, ImGuiDir_Down, ImGuiDir_Up, ImGuiDir_Left }; - for (int n = (*last_dir != ImGuiDir_None) ? -1 : 0; n < ImGuiDir_COUNT; n++) - { - const ImGuiDir dir = (n == -1) ? *last_dir : dir_prefered_order[n]; - if (n != -1 && dir == *last_dir) // Already tried this direction? - continue; - - const float avail_w = (dir == ImGuiDir_Left ? r_avoid.Min.x : r_outer.Max.x) - (dir == ImGuiDir_Right ? r_avoid.Max.x : r_outer.Min.x); - const float avail_h = (dir == ImGuiDir_Up ? r_avoid.Min.y : r_outer.Max.y) - (dir == ImGuiDir_Down ? r_avoid.Max.y : r_outer.Min.y); - - // If there's not enough room on one axis, there's no point in positioning on a side on this axis (e.g. when not enough width, use a top/bottom position to maximize available width) - if (avail_w < size.x && (dir == ImGuiDir_Left || dir == ImGuiDir_Right)) - continue; - if (avail_h < size.y && (dir == ImGuiDir_Up || dir == ImGuiDir_Down)) - continue; - - ImVec2 pos; - pos.x = (dir == ImGuiDir_Left) ? r_avoid.Min.x - size.x : (dir == ImGuiDir_Right) ? r_avoid.Max.x : base_pos_clamped.x; - pos.y = (dir == ImGuiDir_Up) ? r_avoid.Min.y - size.y : (dir == ImGuiDir_Down) ? r_avoid.Max.y : base_pos_clamped.y; - - // Clamp top-left corner of popup - pos.x = ImMax(pos.x, r_outer.Min.x); - pos.y = ImMax(pos.y, r_outer.Min.y); - - *last_dir = dir; - return pos; - } - } - - // Fallback when not enough room: - *last_dir = ImGuiDir_None; - - // For tooltip we prefer avoiding the cursor at all cost even if it means that part of the tooltip won't be visible. - if (policy == ImGuiPopupPositionPolicy_Tooltip) - return ref_pos + ImVec2(2, 2); - - // Otherwise try to keep within display - ImVec2 pos = ref_pos; - pos.x = ImMax(ImMin(pos.x + size.x, r_outer.Max.x) - size.x, r_outer.Min.x); - pos.y = ImMax(ImMin(pos.y + size.y, r_outer.Max.y) - size.y, r_outer.Min.y); - return pos; -} - -// Note that this is used for popups, which can overlap the non work-area of individual viewports. -ImRect ImGui::GetPopupAllowedExtentRect(ImGuiWindow* window) -{ - ImGuiContext& g = *GImGui; - ImRect r_screen; - if (window->ViewportAllowPlatformMonitorExtend >= 0) - { - // Extent with be in the frame of reference of the given viewport (so Min is likely to be negative here) - const ImGuiPlatformMonitor& monitor = g.PlatformIO.Monitors[window->ViewportAllowPlatformMonitorExtend]; - r_screen.Min = monitor.WorkPos; - r_screen.Max = monitor.WorkPos + monitor.WorkSize; - } - else - { - // Use the full viewport area (not work area) for popups - r_screen = window->Viewport->GetMainRect(); - } - ImVec2 padding = g.Style.DisplaySafeAreaPadding; - r_screen.Expand(ImVec2((r_screen.GetWidth() > padding.x * 2) ? -padding.x : 0.0f, (r_screen.GetHeight() > padding.y * 2) ? -padding.y : 0.0f)); - return r_screen; -} - -ImVec2 ImGui::FindBestWindowPosForPopup(ImGuiWindow* window) -{ - ImGuiContext& g = *GImGui; - - ImRect r_outer = GetPopupAllowedExtentRect(window); - if (window->Flags & ImGuiWindowFlags_ChildMenu) - { - // Child menus typically request _any_ position within the parent menu item, and then we move the new menu outside the parent bounds. - // This is how we end up with child menus appearing (most-commonly) on the right of the parent menu. - ImGuiWindow* parent_window = window->ParentWindow; - float horizontal_overlap = g.Style.ItemInnerSpacing.x; // We want some overlap to convey the relative depth of each menu (currently the amount of overlap is hard-coded to style.ItemSpacing.x). - ImRect r_avoid; - if (parent_window->DC.MenuBarAppending) - r_avoid = ImRect(-FLT_MAX, parent_window->ClipRect.Min.y, FLT_MAX, parent_window->ClipRect.Max.y); // Avoid parent menu-bar. If we wanted multi-line menu-bar, we may instead want to have the calling window setup e.g. a NextWindowData.PosConstraintAvoidRect field - else - r_avoid = ImRect(parent_window->Pos.x + horizontal_overlap, -FLT_MAX, parent_window->Pos.x + parent_window->Size.x - horizontal_overlap - parent_window->ScrollbarSizes.x, FLT_MAX); - return FindBestWindowPosForPopupEx(window->Pos, window->Size, &window->AutoPosLastDirection, r_outer, r_avoid, ImGuiPopupPositionPolicy_Default); - } - if (window->Flags & ImGuiWindowFlags_Popup) - { - return FindBestWindowPosForPopupEx(window->Pos, window->Size, &window->AutoPosLastDirection, r_outer, ImRect(window->Pos, window->Pos), ImGuiPopupPositionPolicy_Default); // Ideally we'd disable r_avoid here - } - if (window->Flags & ImGuiWindowFlags_Tooltip) - { - // Position tooltip (always follows mouse + clamp within outer boundaries) - // Note that drag and drop tooltips are NOT using this path: BeginTooltipEx() manually sets their position. - // In theory we could handle both cases in same location, but requires a bit of shuffling as drag and drop tooltips are calling SetWindowPos() leading to 'window_pos_set_by_api' being set in Begin() - IM_ASSERT(g.CurrentWindow == window); - const float scale = g.Style.MouseCursorScale; - const ImVec2 ref_pos = NavCalcPreferredRefPos(); - const ImVec2 tooltip_pos = ref_pos + TOOLTIP_DEFAULT_OFFSET * scale; - ImRect r_avoid; - if (!g.NavDisableHighlight && g.NavDisableMouseHover && !(g.IO.ConfigFlags & ImGuiConfigFlags_NavEnableSetMousePos)) - r_avoid = ImRect(ref_pos.x - 16, ref_pos.y - 8, ref_pos.x + 16, ref_pos.y + 8); - else - r_avoid = ImRect(ref_pos.x - 16, ref_pos.y - 8, ref_pos.x + 24 * scale, ref_pos.y + 24 * scale); // FIXME: Hard-coded based on mouse cursor shape expectation. Exact dimension not very important. - //GetForegroundDrawList()->AddRect(r_avoid.Min, r_avoid.Max, IM_COL32(255, 0, 255, 255)); - return FindBestWindowPosForPopupEx(tooltip_pos, window->Size, &window->AutoPosLastDirection, r_outer, r_avoid, ImGuiPopupPositionPolicy_Tooltip); - } - IM_ASSERT(0); - return window->Pos; -} - -//----------------------------------------------------------------------------- -// [SECTION] KEYBOARD/GAMEPAD NAVIGATION -//----------------------------------------------------------------------------- - -// FIXME-NAV: The existence of SetNavID vs SetFocusID vs FocusWindow() needs to be clarified/reworked. -// In our terminology those should be interchangeable, yet right now this is super confusing. -// Those two functions are merely a legacy artifact, so at minimum naming should be clarified. - -void ImGui::SetNavWindow(ImGuiWindow* window) -{ - ImGuiContext& g = *GImGui; - if (g.NavWindow != window) - { - IMGUI_DEBUG_LOG_FOCUS("[focus] SetNavWindow(\"%s\")\n", window ? window->Name : ""); - g.NavWindow = window; - g.NavLastValidSelectionUserData = ImGuiSelectionUserData_Invalid; - } - g.NavInitRequest = g.NavMoveSubmitted = g.NavMoveScoringItems = false; - NavUpdateAnyRequestFlag(); -} - -void ImGui::NavClearPreferredPosForAxis(ImGuiAxis axis) -{ - ImGuiContext& g = *GImGui; - g.NavWindow->RootWindowForNav->NavPreferredScoringPosRel[g.NavLayer][axis] = FLT_MAX; -} - -void ImGui::SetNavID(ImGuiID id, ImGuiNavLayer nav_layer, ImGuiID focus_scope_id, const ImRect& rect_rel) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(g.NavWindow != NULL); - IM_ASSERT(nav_layer == ImGuiNavLayer_Main || nav_layer == ImGuiNavLayer_Menu); - g.NavId = id; - g.NavLayer = nav_layer; - g.NavFocusScopeId = focus_scope_id; - g.NavWindow->NavLastIds[nav_layer] = id; - g.NavWindow->NavRectRel[nav_layer] = rect_rel; - - // Clear preferred scoring position (NavMoveRequestApplyResult() will tend to restore it) - NavClearPreferredPosForAxis(ImGuiAxis_X); - NavClearPreferredPosForAxis(ImGuiAxis_Y); -} - -void ImGui::SetFocusID(ImGuiID id, ImGuiWindow* window) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(id != 0); - - if (g.NavWindow != window) - SetNavWindow(window); - - // Assume that SetFocusID() is called in the context where its window->DC.NavLayerCurrent and g.CurrentFocusScopeId are valid. - // Note that window may be != g.CurrentWindow (e.g. SetFocusID call in InputTextEx for multi-line text) - const ImGuiNavLayer nav_layer = window->DC.NavLayerCurrent; - g.NavId = id; - g.NavLayer = nav_layer; - g.NavFocusScopeId = g.CurrentFocusScopeId; - window->NavLastIds[nav_layer] = id; - if (g.LastItemData.ID == id) - window->NavRectRel[nav_layer] = WindowRectAbsToRel(window, g.LastItemData.NavRect); - - if (g.ActiveIdSource == ImGuiInputSource_Keyboard || g.ActiveIdSource == ImGuiInputSource_Gamepad) - g.NavDisableMouseHover = true; - else - g.NavDisableHighlight = true; - - // Clear preferred scoring position (NavMoveRequestApplyResult() will tend to restore it) - NavClearPreferredPosForAxis(ImGuiAxis_X); - NavClearPreferredPosForAxis(ImGuiAxis_Y); -} - -static ImGuiDir ImGetDirQuadrantFromDelta(float dx, float dy) -{ - if (ImFabs(dx) > ImFabs(dy)) - return (dx > 0.0f) ? ImGuiDir_Right : ImGuiDir_Left; - return (dy > 0.0f) ? ImGuiDir_Down : ImGuiDir_Up; -} - -static float inline NavScoreItemDistInterval(float cand_min, float cand_max, float curr_min, float curr_max) -{ - if (cand_max < curr_min) - return cand_max - curr_min; - if (curr_max < cand_min) - return cand_min - curr_max; - return 0.0f; -} - -// Scoring function for gamepad/keyboard directional navigation. Based on https://gist.github.com/rygorous/6981057 -static bool ImGui::NavScoreItem(ImGuiNavItemData* result) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - if (g.NavLayer != window->DC.NavLayerCurrent) - return false; - - // FIXME: Those are not good variables names - ImRect cand = g.LastItemData.NavRect; // Current item nav rectangle - const ImRect curr = g.NavScoringRect; // Current modified source rect (NB: we've applied Max.x = Min.x in NavUpdate() to inhibit the effect of having varied item width) - g.NavScoringDebugCount++; - - // When entering through a NavFlattened border, we consider child window items as fully clipped for scoring - if (window->ParentWindow == g.NavWindow) - { - IM_ASSERT((window->Flags | g.NavWindow->Flags) & ImGuiWindowFlags_NavFlattened); - if (!window->ClipRect.Overlaps(cand)) - return false; - cand.ClipWithFull(window->ClipRect); // This allows the scored item to not overlap other candidates in the parent window - } - - // Compute distance between boxes - // FIXME-NAV: Introducing biases for vertical navigation, needs to be removed. - float dbx = NavScoreItemDistInterval(cand.Min.x, cand.Max.x, curr.Min.x, curr.Max.x); - float dby = NavScoreItemDistInterval(ImLerp(cand.Min.y, cand.Max.y, 0.2f), ImLerp(cand.Min.y, cand.Max.y, 0.8f), ImLerp(curr.Min.y, curr.Max.y, 0.2f), ImLerp(curr.Min.y, curr.Max.y, 0.8f)); // Scale down on Y to keep using box-distance for vertically touching items - if (dby != 0.0f && dbx != 0.0f) - dbx = (dbx / 1000.0f) + ((dbx > 0.0f) ? +1.0f : -1.0f); - float dist_box = ImFabs(dbx) + ImFabs(dby); - - // Compute distance between centers (this is off by a factor of 2, but we only compare center distances with each other so it doesn't matter) - float dcx = (cand.Min.x + cand.Max.x) - (curr.Min.x + curr.Max.x); - float dcy = (cand.Min.y + cand.Max.y) - (curr.Min.y + curr.Max.y); - float dist_center = ImFabs(dcx) + ImFabs(dcy); // L1 metric (need this for our connectedness guarantee) - - // Determine which quadrant of 'curr' our candidate item 'cand' lies in based on distance - ImGuiDir quadrant; - float dax = 0.0f, day = 0.0f, dist_axial = 0.0f; - if (dbx != 0.0f || dby != 0.0f) - { - // For non-overlapping boxes, use distance between boxes - dax = dbx; - day = dby; - dist_axial = dist_box; - quadrant = ImGetDirQuadrantFromDelta(dbx, dby); - } - else if (dcx != 0.0f || dcy != 0.0f) - { - // For overlapping boxes with different centers, use distance between centers - dax = dcx; - day = dcy; - dist_axial = dist_center; - quadrant = ImGetDirQuadrantFromDelta(dcx, dcy); - } - else - { - // Degenerate case: two overlapping buttons with same center, break ties arbitrarily (note that LastItemId here is really the _previous_ item order, but it doesn't matter) - quadrant = (g.LastItemData.ID < g.NavId) ? ImGuiDir_Left : ImGuiDir_Right; - } - - const ImGuiDir move_dir = g.NavMoveDir; -#if IMGUI_DEBUG_NAV_SCORING - char buf[200]; - if (g.IO.KeyCtrl) // Hold CTRL to preview score in matching quadrant. CTRL+Arrow to rotate. - { - if (quadrant == move_dir) - { - ImFormatString(buf, IM_ARRAYSIZE(buf), "%.0f/%.0f", dist_box, dist_center); - ImDrawList* draw_list = GetForegroundDrawList(window); - draw_list->AddRectFilled(cand.Min, cand.Max, IM_COL32(255, 0, 0, 80)); - draw_list->AddRectFilled(cand.Min, cand.Min + CalcTextSize(buf), IM_COL32(255, 0, 0, 200)); - draw_list->AddText(cand.Min, IM_COL32(255, 255, 255, 255), buf); - } - } - const bool debug_hovering = IsMouseHoveringRect(cand.Min, cand.Max); - const bool debug_tty = (g.IO.KeyCtrl && IsKeyPressed(ImGuiKey_Space)); - if (debug_hovering || debug_tty) - { - ImFormatString(buf, IM_ARRAYSIZE(buf), - "d-box (%7.3f,%7.3f) -> %7.3f\nd-center (%7.3f,%7.3f) -> %7.3f\nd-axial (%7.3f,%7.3f) -> %7.3f\nnav %c, quadrant %c", - dbx, dby, dist_box, dcx, dcy, dist_center, dax, day, dist_axial, "-WENS"[move_dir+1], "-WENS"[quadrant+1]); - if (debug_hovering) - { - ImDrawList* draw_list = GetForegroundDrawList(window); - draw_list->AddRect(curr.Min, curr.Max, IM_COL32(255, 200, 0, 100)); - draw_list->AddRect(cand.Min, cand.Max, IM_COL32(255, 255, 0, 200)); - draw_list->AddRectFilled(cand.Max - ImVec2(4, 4), cand.Max + CalcTextSize(buf) + ImVec2(4, 4), IM_COL32(40, 0, 0, 200)); - draw_list->AddText(cand.Max, ~0U, buf); - } - if (debug_tty) { IMGUI_DEBUG_LOG_NAV("id 0x%08X\n%s\n", g.LastItemData.ID, buf); } - } -#endif - - // Is it in the quadrant we're interested in moving to? - bool new_best = false; - if (quadrant == move_dir) - { - // Does it beat the current best candidate? - if (dist_box < result->DistBox) - { - result->DistBox = dist_box; - result->DistCenter = dist_center; - return true; - } - if (dist_box == result->DistBox) - { - // Try using distance between center points to break ties - if (dist_center < result->DistCenter) - { - result->DistCenter = dist_center; - new_best = true; - } - else if (dist_center == result->DistCenter) - { - // Still tied! we need to be extra-careful to make sure everything gets linked properly. We consistently break ties by symbolically moving "later" items - // (with higher index) to the right/downwards by an infinitesimal amount since we the current "best" button already (so it must have a lower index), - // this is fairly easy. This rule ensures that all buttons with dx==dy==0 will end up being linked in order of appearance along the x axis. - if (((move_dir == ImGuiDir_Up || move_dir == ImGuiDir_Down) ? dby : dbx) < 0.0f) // moving bj to the right/down decreases distance - new_best = true; - } - } - } - - // Axial check: if 'curr' has no link at all in some direction and 'cand' lies roughly in that direction, add a tentative link. This will only be kept if no "real" matches - // are found, so it only augments the graph produced by the above method using extra links. (important, since it doesn't guarantee strong connectedness) - // This is just to avoid buttons having no links in a particular direction when there's a suitable neighbor. you get good graphs without this too. - // 2017/09/29: FIXME: This now currently only enabled inside menu bars, ideally we'd disable it everywhere. Menus in particular need to catch failure. For general navigation it feels awkward. - // Disabling it may lead to disconnected graphs when nodes are very spaced out on different axis. Perhaps consider offering this as an option? - if (result->DistBox == FLT_MAX && dist_axial < result->DistAxial) // Check axial match - if (g.NavLayer == ImGuiNavLayer_Menu && !(g.NavWindow->Flags & ImGuiWindowFlags_ChildMenu)) - if ((move_dir == ImGuiDir_Left && dax < 0.0f) || (move_dir == ImGuiDir_Right && dax > 0.0f) || (move_dir == ImGuiDir_Up && day < 0.0f) || (move_dir == ImGuiDir_Down && day > 0.0f)) - { - result->DistAxial = dist_axial; - new_best = true; - } - - return new_best; -} - -static void ImGui::NavApplyItemToResult(ImGuiNavItemData* result) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - result->Window = window; - result->ID = g.LastItemData.ID; - result->FocusScopeId = g.CurrentFocusScopeId; - result->InFlags = g.LastItemData.InFlags; - result->RectRel = WindowRectAbsToRel(window, g.LastItemData.NavRect); - if (result->InFlags & ImGuiItemFlags_HasSelectionUserData) - { - IM_ASSERT(g.NextItemData.SelectionUserData != ImGuiSelectionUserData_Invalid); - result->SelectionUserData = g.NextItemData.SelectionUserData; // INTENTIONAL: At this point this field is not cleared in NextItemData. Avoid unnecessary copy to LastItemData. - } -} - -// True when current work location may be scrolled horizontally when moving left / right. -// This is generally always true UNLESS within a column. We don't have a vertical equivalent. -void ImGui::NavUpdateCurrentWindowIsScrollPushableX() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - window->DC.NavIsScrollPushableX = (g.CurrentTable == NULL && window->DC.CurrentColumns == NULL); -} - -// We get there when either NavId == id, or when g.NavAnyRequest is set (which is updated by NavUpdateAnyRequestFlag above) -// This is called after LastItemData is set, but NextItemData is also still valid. -static void ImGui::NavProcessItem() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - const ImGuiID id = g.LastItemData.ID; - const ImGuiItemFlags item_flags = g.LastItemData.InFlags; - - // When inside a container that isn't scrollable with Left<>Right, clip NavRect accordingly (#2221) - if (window->DC.NavIsScrollPushableX == false) - { - g.LastItemData.NavRect.Min.x = ImClamp(g.LastItemData.NavRect.Min.x, window->ClipRect.Min.x, window->ClipRect.Max.x); - g.LastItemData.NavRect.Max.x = ImClamp(g.LastItemData.NavRect.Max.x, window->ClipRect.Min.x, window->ClipRect.Max.x); - } - const ImRect nav_bb = g.LastItemData.NavRect; - - // Process Init Request - if (g.NavInitRequest && g.NavLayer == window->DC.NavLayerCurrent && (item_flags & ImGuiItemFlags_Disabled) == 0) - { - // Even if 'ImGuiItemFlags_NoNavDefaultFocus' is on (typically collapse/close button) we record the first ResultId so they can be used as a fallback - const bool candidate_for_nav_default_focus = (item_flags & ImGuiItemFlags_NoNavDefaultFocus) == 0; - if (candidate_for_nav_default_focus || g.NavInitResult.ID == 0) - { - NavApplyItemToResult(&g.NavInitResult); - } - if (candidate_for_nav_default_focus) - { - g.NavInitRequest = false; // Found a match, clear request - NavUpdateAnyRequestFlag(); - } - } - - // Process Move Request (scoring for navigation) - // FIXME-NAV: Consider policy for double scoring (scoring from NavScoringRect + scoring from a rect wrapped according to current wrapping policy) - if (g.NavMoveScoringItems && (item_flags & ImGuiItemFlags_Disabled) == 0) - { - const bool is_tabbing = (g.NavMoveFlags & ImGuiNavMoveFlags_IsTabbing) != 0; - if (is_tabbing) - { - NavProcessItemForTabbingRequest(id, item_flags, g.NavMoveFlags); - } - else if (g.NavId != id || (g.NavMoveFlags & ImGuiNavMoveFlags_AllowCurrentNavId)) - { - ImGuiNavItemData* result = (window == g.NavWindow) ? &g.NavMoveResultLocal : &g.NavMoveResultOther; - if (NavScoreItem(result)) - NavApplyItemToResult(result); - - // Features like PageUp/PageDown need to maintain a separate score for the visible set of items. - const float VISIBLE_RATIO = 0.70f; - if ((g.NavMoveFlags & ImGuiNavMoveFlags_AlsoScoreVisibleSet) && window->ClipRect.Overlaps(nav_bb)) - if (ImClamp(nav_bb.Max.y, window->ClipRect.Min.y, window->ClipRect.Max.y) - ImClamp(nav_bb.Min.y, window->ClipRect.Min.y, window->ClipRect.Max.y) >= (nav_bb.Max.y - nav_bb.Min.y) * VISIBLE_RATIO) - if (NavScoreItem(&g.NavMoveResultLocalVisible)) - NavApplyItemToResult(&g.NavMoveResultLocalVisible); - } - } - - // Update information for currently focused/navigated item - if (g.NavId == id) - { - if (g.NavWindow != window) - SetNavWindow(window); // Always refresh g.NavWindow, because some operations such as FocusItem() may not have a window. - g.NavLayer = window->DC.NavLayerCurrent; - g.NavFocusScopeId = g.CurrentFocusScopeId; - g.NavIdIsAlive = true; - if (g.LastItemData.InFlags & ImGuiItemFlags_HasSelectionUserData) - { - IM_ASSERT(g.NextItemData.SelectionUserData != ImGuiSelectionUserData_Invalid); - g.NavLastValidSelectionUserData = g.NextItemData.SelectionUserData; // INTENTIONAL: At this point this field is not cleared in NextItemData. Avoid unnecessary copy to LastItemData. - } - window->NavRectRel[window->DC.NavLayerCurrent] = WindowRectAbsToRel(window, nav_bb); // Store item bounding box (relative to window position) - } -} - -// Handle "scoring" of an item for a tabbing/focusing request initiated by NavUpdateCreateTabbingRequest(). -// Note that SetKeyboardFocusHere() API calls are considered tabbing requests! -// - Case 1: no nav/active id: set result to first eligible item, stop storing. -// - Case 2: tab forward: on ref id set counter, on counter elapse store result -// - Case 3: tab forward wrap: set result to first eligible item (preemptively), on ref id set counter, on next frame if counter hasn't elapsed store result. // FIXME-TABBING: Could be done as a next-frame forwarded request -// - Case 4: tab backward: store all results, on ref id pick prev, stop storing -// - Case 5: tab backward wrap: store all results, on ref id if no result keep storing until last // FIXME-TABBING: Could be done as next-frame forwarded requested -void ImGui::NavProcessItemForTabbingRequest(ImGuiID id, ImGuiItemFlags item_flags, ImGuiNavMoveFlags move_flags) -{ - ImGuiContext& g = *GImGui; - - if ((move_flags & ImGuiNavMoveFlags_FocusApi) == 0) - if (g.NavLayer != g.CurrentWindow->DC.NavLayerCurrent) - return; - - // - Can always land on an item when using API call. - // - Tabbing with _NavEnableKeyboard (space/enter/arrows): goes through every item. - // - Tabbing without _NavEnableKeyboard: goes through inputable items only. - bool can_stop; - if (move_flags & ImGuiNavMoveFlags_FocusApi) - can_stop = true; - else - can_stop = (item_flags & ImGuiItemFlags_NoTabStop) == 0 && ((g.IO.ConfigFlags & ImGuiConfigFlags_NavEnableKeyboard) || (item_flags & ImGuiItemFlags_Inputable)); - - // Always store in NavMoveResultLocal (unlike directional request which uses NavMoveResultOther on sibling/flattened windows) - ImGuiNavItemData* result = &g.NavMoveResultLocal; - if (g.NavTabbingDir == +1) - { - // Tab Forward or SetKeyboardFocusHere() with >= 0 - if (can_stop && g.NavTabbingResultFirst.ID == 0) - NavApplyItemToResult(&g.NavTabbingResultFirst); - if (can_stop && g.NavTabbingCounter > 0 && --g.NavTabbingCounter == 0) - NavMoveRequestResolveWithLastItem(result); - else if (g.NavId == id) - g.NavTabbingCounter = 1; - } - else if (g.NavTabbingDir == -1) - { - // Tab Backward - if (g.NavId == id) - { - if (result->ID) - { - g.NavMoveScoringItems = false; - NavUpdateAnyRequestFlag(); - } - } - else if (can_stop) - { - // Keep applying until reaching NavId - NavApplyItemToResult(result); - } - } - else if (g.NavTabbingDir == 0) - { - if (can_stop && g.NavId == id) - NavMoveRequestResolveWithLastItem(result); - if (can_stop && g.NavTabbingResultFirst.ID == 0) // Tab init - NavApplyItemToResult(&g.NavTabbingResultFirst); - } -} - -bool ImGui::NavMoveRequestButNoResultYet() -{ - ImGuiContext& g = *GImGui; - return g.NavMoveScoringItems && g.NavMoveResultLocal.ID == 0 && g.NavMoveResultOther.ID == 0; -} - -// FIXME: ScoringRect is not set -void ImGui::NavMoveRequestSubmit(ImGuiDir move_dir, ImGuiDir clip_dir, ImGuiNavMoveFlags move_flags, ImGuiScrollFlags scroll_flags) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(g.NavWindow != NULL); - - if (move_flags & ImGuiNavMoveFlags_IsTabbing) - move_flags |= ImGuiNavMoveFlags_AllowCurrentNavId; - - g.NavMoveSubmitted = g.NavMoveScoringItems = true; - g.NavMoveDir = move_dir; - g.NavMoveDirForDebug = move_dir; - g.NavMoveClipDir = clip_dir; - g.NavMoveFlags = move_flags; - g.NavMoveScrollFlags = scroll_flags; - g.NavMoveForwardToNextFrame = false; - g.NavMoveKeyMods = g.IO.KeyMods; - g.NavMoveResultLocal.Clear(); - g.NavMoveResultLocalVisible.Clear(); - g.NavMoveResultOther.Clear(); - g.NavTabbingCounter = 0; - g.NavTabbingResultFirst.Clear(); - NavUpdateAnyRequestFlag(); -} - -void ImGui::NavMoveRequestResolveWithLastItem(ImGuiNavItemData* result) -{ - ImGuiContext& g = *GImGui; - g.NavMoveScoringItems = false; // Ensure request doesn't need more processing - NavApplyItemToResult(result); - NavUpdateAnyRequestFlag(); -} - -// Called by TreePop() to implement ImGuiTreeNodeFlags_NavLeftJumpsBackHere -void ImGui::NavMoveRequestResolveWithPastTreeNode(ImGuiNavItemData* result, ImGuiNavTreeNodeData* tree_node_data) -{ - ImGuiContext& g = *GImGui; - g.NavMoveScoringItems = false; - g.LastItemData.ID = tree_node_data->ID; - g.LastItemData.InFlags = tree_node_data->InFlags & ~ImGuiItemFlags_HasSelectionUserData; // Losing SelectionUserData, recovered next-frame (cheaper). - g.LastItemData.NavRect = tree_node_data->NavRect; - NavApplyItemToResult(result); // Result this instead of implementing a NavApplyPastTreeNodeToResult() - NavClearPreferredPosForAxis(ImGuiAxis_Y); - NavUpdateAnyRequestFlag(); -} - -void ImGui::NavMoveRequestCancel() -{ - ImGuiContext& g = *GImGui; - g.NavMoveSubmitted = g.NavMoveScoringItems = false; - NavUpdateAnyRequestFlag(); -} - -// Forward will reuse the move request again on the next frame (generally with modifications done to it) -void ImGui::NavMoveRequestForward(ImGuiDir move_dir, ImGuiDir clip_dir, ImGuiNavMoveFlags move_flags, ImGuiScrollFlags scroll_flags) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(g.NavMoveForwardToNextFrame == false); - NavMoveRequestCancel(); - g.NavMoveForwardToNextFrame = true; - g.NavMoveDir = move_dir; - g.NavMoveClipDir = clip_dir; - g.NavMoveFlags = move_flags | ImGuiNavMoveFlags_Forwarded; - g.NavMoveScrollFlags = scroll_flags; -} - -// Navigation wrap-around logic is delayed to the end of the frame because this operation is only valid after entire -// popup is assembled and in case of appended popups it is not clear which EndPopup() call is final. -void ImGui::NavMoveRequestTryWrapping(ImGuiWindow* window, ImGuiNavMoveFlags wrap_flags) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT((wrap_flags & ImGuiNavMoveFlags_WrapMask_ ) != 0 && (wrap_flags & ~ImGuiNavMoveFlags_WrapMask_) == 0); // Call with _WrapX, _WrapY, _LoopX, _LoopY - - // In theory we should test for NavMoveRequestButNoResultYet() but there's no point doing it: - // as NavEndFrame() will do the same test. It will end up calling NavUpdateCreateWrappingRequest(). - if (g.NavWindow == window && g.NavMoveScoringItems && g.NavLayer == ImGuiNavLayer_Main) - g.NavMoveFlags = (g.NavMoveFlags & ~ImGuiNavMoveFlags_WrapMask_) | wrap_flags; -} - -// FIXME: This could be replaced by updating a frame number in each window when (window == NavWindow) and (NavLayer == 0). -// This way we could find the last focused window among our children. It would be much less confusing this way? -static void ImGui::NavSaveLastChildNavWindowIntoParent(ImGuiWindow* nav_window) -{ - ImGuiWindow* parent = nav_window; - while (parent && parent->RootWindow != parent && (parent->Flags & (ImGuiWindowFlags_Popup | ImGuiWindowFlags_ChildMenu)) == 0) - parent = parent->ParentWindow; - if (parent && parent != nav_window) - parent->NavLastChildNavWindow = nav_window; -} - -// Restore the last focused child. -// Call when we are expected to land on the Main Layer (0) after FocusWindow() -static ImGuiWindow* ImGui::NavRestoreLastChildNavWindow(ImGuiWindow* window) -{ - if (window->NavLastChildNavWindow && window->NavLastChildNavWindow->WasActive) - return window->NavLastChildNavWindow; - if (window->DockNodeAsHost && window->DockNodeAsHost->TabBar) - if (ImGuiTabItem* tab = TabBarFindMostRecentlySelectedTabForActiveWindow(window->DockNodeAsHost->TabBar)) - return tab->Window; - return window; -} - -void ImGui::NavRestoreLayer(ImGuiNavLayer layer) -{ - ImGuiContext& g = *GImGui; - if (layer == ImGuiNavLayer_Main) - { - ImGuiWindow* prev_nav_window = g.NavWindow; - g.NavWindow = NavRestoreLastChildNavWindow(g.NavWindow); // FIXME-NAV: Should clear ongoing nav requests? - g.NavLastValidSelectionUserData = ImGuiSelectionUserData_Invalid; - if (prev_nav_window) - IMGUI_DEBUG_LOG_FOCUS("[focus] NavRestoreLayer: from \"%s\" to SetNavWindow(\"%s\")\n", prev_nav_window->Name, g.NavWindow->Name); - } - ImGuiWindow* window = g.NavWindow; - if (window->NavLastIds[layer] != 0) - { - SetNavID(window->NavLastIds[layer], layer, 0, window->NavRectRel[layer]); - } - else - { - g.NavLayer = layer; - NavInitWindow(window, true); - } -} - -void ImGui::NavRestoreHighlightAfterMove() -{ - ImGuiContext& g = *GImGui; - g.NavDisableHighlight = false; - g.NavDisableMouseHover = g.NavMousePosDirty = true; -} - -static inline void ImGui::NavUpdateAnyRequestFlag() -{ - ImGuiContext& g = *GImGui; - g.NavAnyRequest = g.NavMoveScoringItems || g.NavInitRequest || (IMGUI_DEBUG_NAV_SCORING && g.NavWindow != NULL); - if (g.NavAnyRequest) - IM_ASSERT(g.NavWindow != NULL); -} - -// This needs to be called before we submit any widget (aka in or before Begin) -void ImGui::NavInitWindow(ImGuiWindow* window, bool force_reinit) -{ - // FIXME: ChildWindow test here is wrong for docking - ImGuiContext& g = *GImGui; - IM_ASSERT(window == g.NavWindow); - - if (window->Flags & ImGuiWindowFlags_NoNavInputs) - { - g.NavId = 0; - g.NavFocusScopeId = window->NavRootFocusScopeId; - return; - } - - bool init_for_nav = false; - if (window == window->RootWindow || (window->Flags & ImGuiWindowFlags_Popup) || (window->NavLastIds[0] == 0) || force_reinit) - init_for_nav = true; - IMGUI_DEBUG_LOG_NAV("[nav] NavInitRequest: from NavInitWindow(), init_for_nav=%d, window=\"%s\", layer=%d\n", init_for_nav, window->Name, g.NavLayer); - if (init_for_nav) - { - SetNavID(0, g.NavLayer, window->NavRootFocusScopeId, ImRect()); - g.NavInitRequest = true; - g.NavInitRequestFromMove = false; - g.NavInitResult.ID = 0; - NavUpdateAnyRequestFlag(); - } - else - { - g.NavId = window->NavLastIds[0]; - g.NavFocusScopeId = window->NavRootFocusScopeId; - } -} - -static ImVec2 ImGui::NavCalcPreferredRefPos() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.NavWindow; - if (g.NavDisableHighlight || !g.NavDisableMouseHover || !window) - { - // Mouse (we need a fallback in case the mouse becomes invalid after being used) - // The +1.0f offset when stored by OpenPopupEx() allows reopening this or another popup (same or another mouse button) while not moving the mouse, it is pretty standard. - // In theory we could move that +1.0f offset in OpenPopupEx() - ImVec2 p = IsMousePosValid(&g.IO.MousePos) ? g.IO.MousePos : g.MouseLastValidPos; - return ImVec2(p.x + 1.0f, p.y); - } - else - { - // When navigation is active and mouse is disabled, pick a position around the bottom left of the currently navigated item - // Take account of upcoming scrolling (maybe set mouse pos should be done in EndFrame?) - ImRect rect_rel = WindowRectRelToAbs(window, window->NavRectRel[g.NavLayer]); - if (window->LastFrameActive != g.FrameCount && (window->ScrollTarget.x != FLT_MAX || window->ScrollTarget.y != FLT_MAX)) - { - ImVec2 next_scroll = CalcNextScrollFromScrollTargetAndClamp(window); - rect_rel.Translate(window->Scroll - next_scroll); - } - ImVec2 pos = ImVec2(rect_rel.Min.x + ImMin(g.Style.FramePadding.x * 4, rect_rel.GetWidth()), rect_rel.Max.y - ImMin(g.Style.FramePadding.y, rect_rel.GetHeight())); - ImGuiViewport* viewport = window->Viewport; - return ImTrunc(ImClamp(pos, viewport->Pos, viewport->Pos + viewport->Size)); // ImTrunc() is important because non-integer mouse position application in backend might be lossy and result in undesirable non-zero delta. - } -} - -float ImGui::GetNavTweakPressedAmount(ImGuiAxis axis) -{ - ImGuiContext& g = *GImGui; - float repeat_delay, repeat_rate; - GetTypematicRepeatRate(ImGuiInputFlags_RepeatRateNavTweak, &repeat_delay, &repeat_rate); - - ImGuiKey key_less, key_more; - if (g.NavInputSource == ImGuiInputSource_Gamepad) - { - key_less = (axis == ImGuiAxis_X) ? ImGuiKey_GamepadDpadLeft : ImGuiKey_GamepadDpadUp; - key_more = (axis == ImGuiAxis_X) ? ImGuiKey_GamepadDpadRight : ImGuiKey_GamepadDpadDown; - } - else - { - key_less = (axis == ImGuiAxis_X) ? ImGuiKey_LeftArrow : ImGuiKey_UpArrow; - key_more = (axis == ImGuiAxis_X) ? ImGuiKey_RightArrow : ImGuiKey_DownArrow; - } - float amount = (float)GetKeyPressedAmount(key_more, repeat_delay, repeat_rate) - (float)GetKeyPressedAmount(key_less, repeat_delay, repeat_rate); - if (amount != 0.0f && IsKeyDown(key_less) && IsKeyDown(key_more)) // Cancel when opposite directions are held, regardless of repeat phase - amount = 0.0f; - return amount; -} - -static void ImGui::NavUpdate() -{ - ImGuiContext& g = *GImGui; - ImGuiIO& io = g.IO; - - io.WantSetMousePos = false; - //if (g.NavScoringDebugCount > 0) IMGUI_DEBUG_LOG_NAV("[nav] NavScoringDebugCount %d for '%s' layer %d (Init:%d, Move:%d)\n", g.NavScoringDebugCount, g.NavWindow ? g.NavWindow->Name : "NULL", g.NavLayer, g.NavInitRequest || g.NavInitResultId != 0, g.NavMoveRequest); - - // Set input source based on which keys are last pressed (as some features differs when used with Gamepad vs Keyboard) - // FIXME-NAV: Now that keys are separated maybe we can get rid of NavInputSource? - const bool nav_gamepad_active = (io.ConfigFlags & ImGuiConfigFlags_NavEnableGamepad) != 0 && (io.BackendFlags & ImGuiBackendFlags_HasGamepad) != 0; - const ImGuiKey nav_gamepad_keys_to_change_source[] = { ImGuiKey_GamepadFaceRight, ImGuiKey_GamepadFaceLeft, ImGuiKey_GamepadFaceUp, ImGuiKey_GamepadFaceDown, ImGuiKey_GamepadDpadRight, ImGuiKey_GamepadDpadLeft, ImGuiKey_GamepadDpadUp, ImGuiKey_GamepadDpadDown }; - if (nav_gamepad_active) - for (ImGuiKey key : nav_gamepad_keys_to_change_source) - if (IsKeyDown(key)) - g.NavInputSource = ImGuiInputSource_Gamepad; - const bool nav_keyboard_active = (io.ConfigFlags & ImGuiConfigFlags_NavEnableKeyboard) != 0; - const ImGuiKey nav_keyboard_keys_to_change_source[] = { ImGuiKey_Space, ImGuiKey_Enter, ImGuiKey_Escape, ImGuiKey_RightArrow, ImGuiKey_LeftArrow, ImGuiKey_UpArrow, ImGuiKey_DownArrow }; - if (nav_keyboard_active) - for (ImGuiKey key : nav_keyboard_keys_to_change_source) - if (IsKeyDown(key)) - g.NavInputSource = ImGuiInputSource_Keyboard; - - // Process navigation init request (select first/default focus) - g.NavJustMovedToId = 0; - if (g.NavInitResult.ID != 0) - NavInitRequestApplyResult(); - g.NavInitRequest = false; - g.NavInitRequestFromMove = false; - g.NavInitResult.ID = 0; - - // Process navigation move request - if (g.NavMoveSubmitted) - NavMoveRequestApplyResult(); - g.NavTabbingCounter = 0; - g.NavMoveSubmitted = g.NavMoveScoringItems = false; - - // Schedule mouse position update (will be done at the bottom of this function, after 1) processing all move requests and 2) updating scrolling) - bool set_mouse_pos = false; - if (g.NavMousePosDirty && g.NavIdIsAlive) - if (!g.NavDisableHighlight && g.NavDisableMouseHover && g.NavWindow) - set_mouse_pos = true; - g.NavMousePosDirty = false; - IM_ASSERT(g.NavLayer == ImGuiNavLayer_Main || g.NavLayer == ImGuiNavLayer_Menu); - - // Store our return window (for returning from Menu Layer to Main Layer) and clear it as soon as we step back in our own Layer 0 - if (g.NavWindow) - NavSaveLastChildNavWindowIntoParent(g.NavWindow); - if (g.NavWindow && g.NavWindow->NavLastChildNavWindow != NULL && g.NavLayer == ImGuiNavLayer_Main) - g.NavWindow->NavLastChildNavWindow = NULL; - - // Update CTRL+TAB and Windowing features (hold Square to move/resize/etc.) - NavUpdateWindowing(); - - // Set output flags for user application - io.NavActive = (nav_keyboard_active || nav_gamepad_active) && g.NavWindow && !(g.NavWindow->Flags & ImGuiWindowFlags_NoNavInputs); - io.NavVisible = (io.NavActive && g.NavId != 0 && !g.NavDisableHighlight) || (g.NavWindowingTarget != NULL); - - // Process NavCancel input (to close a popup, get back to parent, clear focus) - NavUpdateCancelRequest(); - - // Process manual activation request - g.NavActivateId = g.NavActivateDownId = g.NavActivatePressedId = 0; - g.NavActivateFlags = ImGuiActivateFlags_None; - if (g.NavId != 0 && !g.NavDisableHighlight && !g.NavWindowingTarget && g.NavWindow && !(g.NavWindow->Flags & ImGuiWindowFlags_NoNavInputs)) - { - const bool activate_down = (nav_keyboard_active && IsKeyDown(ImGuiKey_Space)) || (nav_gamepad_active && IsKeyDown(ImGuiKey_NavGamepadActivate)); - const bool activate_pressed = activate_down && ((nav_keyboard_active && IsKeyPressed(ImGuiKey_Space, false)) || (nav_gamepad_active && IsKeyPressed(ImGuiKey_NavGamepadActivate, false))); - const bool input_down = (nav_keyboard_active && IsKeyDown(ImGuiKey_Enter)) || (nav_gamepad_active && IsKeyDown(ImGuiKey_NavGamepadInput)); - const bool input_pressed = input_down && ((nav_keyboard_active && IsKeyPressed(ImGuiKey_Enter, false)) || (nav_gamepad_active && IsKeyPressed(ImGuiKey_NavGamepadInput, false))); - if (g.ActiveId == 0 && activate_pressed) - { - g.NavActivateId = g.NavId; - g.NavActivateFlags = ImGuiActivateFlags_PreferTweak; - } - if ((g.ActiveId == 0 || g.ActiveId == g.NavId) && input_pressed) - { - g.NavActivateId = g.NavId; - g.NavActivateFlags = ImGuiActivateFlags_PreferInput; - } - if ((g.ActiveId == 0 || g.ActiveId == g.NavId) && (activate_down || input_down)) - g.NavActivateDownId = g.NavId; - if ((g.ActiveId == 0 || g.ActiveId == g.NavId) && (activate_pressed || input_pressed)) - g.NavActivatePressedId = g.NavId; - } - if (g.NavWindow && (g.NavWindow->Flags & ImGuiWindowFlags_NoNavInputs)) - g.NavDisableHighlight = true; - if (g.NavActivateId != 0) - IM_ASSERT(g.NavActivateDownId == g.NavActivateId); - - // Process programmatic activation request - // FIXME-NAV: Those should eventually be queued (unlike focus they don't cancel each others) - if (g.NavNextActivateId != 0) - { - g.NavActivateId = g.NavActivateDownId = g.NavActivatePressedId = g.NavNextActivateId; - g.NavActivateFlags = g.NavNextActivateFlags; - } - g.NavNextActivateId = 0; - - // Process move requests - NavUpdateCreateMoveRequest(); - if (g.NavMoveDir == ImGuiDir_None) - NavUpdateCreateTabbingRequest(); - NavUpdateAnyRequestFlag(); - g.NavIdIsAlive = false; - - // Scrolling - if (g.NavWindow && !(g.NavWindow->Flags & ImGuiWindowFlags_NoNavInputs) && !g.NavWindowingTarget) - { - // *Fallback* manual-scroll with Nav directional keys when window has no navigable item - ImGuiWindow* window = g.NavWindow; - const float scroll_speed = IM_ROUND(window->CalcFontSize() * 100 * io.DeltaTime); // We need round the scrolling speed because sub-pixel scroll isn't reliably supported. - const ImGuiDir move_dir = g.NavMoveDir; - if (window->DC.NavLayersActiveMask == 0x00 && window->DC.NavWindowHasScrollY && move_dir != ImGuiDir_None) - { - if (move_dir == ImGuiDir_Left || move_dir == ImGuiDir_Right) - SetScrollX(window, ImTrunc(window->Scroll.x + ((move_dir == ImGuiDir_Left) ? -1.0f : +1.0f) * scroll_speed)); - if (move_dir == ImGuiDir_Up || move_dir == ImGuiDir_Down) - SetScrollY(window, ImTrunc(window->Scroll.y + ((move_dir == ImGuiDir_Up) ? -1.0f : +1.0f) * scroll_speed)); - } - - // *Normal* Manual scroll with LStick - // Next movement request will clamp the NavId reference rectangle to the visible area, so navigation will resume within those bounds. - if (nav_gamepad_active) - { - const ImVec2 scroll_dir = GetKeyMagnitude2d(ImGuiKey_GamepadLStickLeft, ImGuiKey_GamepadLStickRight, ImGuiKey_GamepadLStickUp, ImGuiKey_GamepadLStickDown); - const float tweak_factor = IsKeyDown(ImGuiKey_NavGamepadTweakSlow) ? 1.0f / 10.0f : IsKeyDown(ImGuiKey_NavGamepadTweakFast) ? 10.0f : 1.0f; - if (scroll_dir.x != 0.0f && window->ScrollbarX) - SetScrollX(window, ImTrunc(window->Scroll.x + scroll_dir.x * scroll_speed * tweak_factor)); - if (scroll_dir.y != 0.0f) - SetScrollY(window, ImTrunc(window->Scroll.y + scroll_dir.y * scroll_speed * tweak_factor)); - } - } - - // Always prioritize mouse highlight if navigation is disabled - if (!nav_keyboard_active && !nav_gamepad_active) - { - g.NavDisableHighlight = true; - g.NavDisableMouseHover = set_mouse_pos = false; - } - - // Update mouse position if requested - // (This will take into account the possibility that a Scroll was queued in the window to offset our absolute mouse position before scroll has been applied) - if (set_mouse_pos && (io.ConfigFlags & ImGuiConfigFlags_NavEnableSetMousePos) && (io.BackendFlags & ImGuiBackendFlags_HasSetMousePos)) - TeleportMousePos(NavCalcPreferredRefPos()); - - // [DEBUG] - g.NavScoringDebugCount = 0; -#if IMGUI_DEBUG_NAV_RECTS - if (ImGuiWindow* debug_window = g.NavWindow) - { - ImDrawList* draw_list = GetForegroundDrawList(debug_window); - int layer = g.NavLayer; /* for (int layer = 0; layer < 2; layer++)*/ { ImRect r = WindowRectRelToAbs(debug_window, debug_window->NavRectRel[layer]); draw_list->AddRect(r.Min, r.Max, IM_COL32(255, 200, 0, 255)); } - //if (1) { ImU32 col = (!debug_window->Hidden) ? IM_COL32(255,0,255,255) : IM_COL32(255,0,0,255); ImVec2 p = NavCalcPreferredRefPos(); char buf[32]; ImFormatString(buf, 32, "%d", g.NavLayer); draw_list->AddCircleFilled(p, 3.0f, col); draw_list->AddText(NULL, 13.0f, p + ImVec2(8,-4), col, buf); } - } -#endif -} - -void ImGui::NavInitRequestApplyResult() -{ - // In very rare cases g.NavWindow may be null (e.g. clearing focus after requesting an init request, which does happen when releasing Alt while clicking on void) - ImGuiContext& g = *GImGui; - if (!g.NavWindow) - return; - - ImGuiNavItemData* result = &g.NavInitResult; - if (g.NavId != result->ID) - { - g.NavJustMovedToId = result->ID; - g.NavJustMovedToFocusScopeId = result->FocusScopeId; - g.NavJustMovedToKeyMods = 0; - } - - // Apply result from previous navigation init request (will typically select the first item, unless SetItemDefaultFocus() has been called) - // FIXME-NAV: On _NavFlattened windows, g.NavWindow will only be updated during subsequent frame. Not a problem currently. - IMGUI_DEBUG_LOG_NAV("[nav] NavInitRequest: ApplyResult: NavID 0x%08X in Layer %d Window \"%s\"\n", result->ID, g.NavLayer, g.NavWindow->Name); - SetNavID(result->ID, g.NavLayer, result->FocusScopeId, result->RectRel); - g.NavIdIsAlive = true; // Mark as alive from previous frame as we got a result - if (result->SelectionUserData != ImGuiSelectionUserData_Invalid) - g.NavLastValidSelectionUserData = result->SelectionUserData; - if (g.NavInitRequestFromMove) - NavRestoreHighlightAfterMove(); -} - -// Bias scoring rect ahead of scoring + update preferred pos (if missing) using source position -static void NavBiasScoringRect(ImRect& r, ImVec2& preferred_pos_rel, ImGuiDir move_dir, ImGuiNavMoveFlags move_flags) -{ - // Bias initial rect - ImGuiContext& g = *GImGui; - const ImVec2 rel_to_abs_offset = g.NavWindow->DC.CursorStartPos; - - // Initialize bias on departure if we don't have any. So mouse-click + arrow will record bias. - // - We default to L/U bias, so moving down from a large source item into several columns will land on left-most column. - // - But each successful move sets new bias on one axis, only cleared when using mouse. - if ((move_flags & ImGuiNavMoveFlags_Forwarded) == 0) - { - if (preferred_pos_rel.x == FLT_MAX) - preferred_pos_rel.x = ImMin(r.Min.x + 1.0f, r.Max.x) - rel_to_abs_offset.x; - if (preferred_pos_rel.y == FLT_MAX) - preferred_pos_rel.y = r.GetCenter().y - rel_to_abs_offset.y; - } - - // Apply general bias on the other axis - if ((move_dir == ImGuiDir_Up || move_dir == ImGuiDir_Down) && preferred_pos_rel.x != FLT_MAX) - r.Min.x = r.Max.x = preferred_pos_rel.x + rel_to_abs_offset.x; - else if ((move_dir == ImGuiDir_Left || move_dir == ImGuiDir_Right) && preferred_pos_rel.y != FLT_MAX) - r.Min.y = r.Max.y = preferred_pos_rel.y + rel_to_abs_offset.y; -} - -void ImGui::NavUpdateCreateMoveRequest() -{ - ImGuiContext& g = *GImGui; - ImGuiIO& io = g.IO; - ImGuiWindow* window = g.NavWindow; - const bool nav_gamepad_active = (io.ConfigFlags & ImGuiConfigFlags_NavEnableGamepad) != 0 && (io.BackendFlags & ImGuiBackendFlags_HasGamepad) != 0; - const bool nav_keyboard_active = (io.ConfigFlags & ImGuiConfigFlags_NavEnableKeyboard) != 0; - - if (g.NavMoveForwardToNextFrame && window != NULL) - { - // Forwarding previous request (which has been modified, e.g. wrap around menus rewrite the requests with a starting rectangle at the other side of the window) - // (preserve most state, which were already set by the NavMoveRequestForward() function) - IM_ASSERT(g.NavMoveDir != ImGuiDir_None && g.NavMoveClipDir != ImGuiDir_None); - IM_ASSERT(g.NavMoveFlags & ImGuiNavMoveFlags_Forwarded); - IMGUI_DEBUG_LOG_NAV("[nav] NavMoveRequestForward %d\n", g.NavMoveDir); - } - else - { - // Initiate directional inputs request - g.NavMoveDir = ImGuiDir_None; - g.NavMoveFlags = ImGuiNavMoveFlags_None; - g.NavMoveScrollFlags = ImGuiScrollFlags_None; - if (window && !g.NavWindowingTarget && !(window->Flags & ImGuiWindowFlags_NoNavInputs)) - { - const ImGuiInputFlags repeat_mode = ImGuiInputFlags_Repeat | (ImGuiInputFlags)ImGuiInputFlags_RepeatRateNavMove; - if (!IsActiveIdUsingNavDir(ImGuiDir_Left) && ((nav_gamepad_active && IsKeyPressed(ImGuiKey_GamepadDpadLeft, ImGuiKeyOwner_None, repeat_mode)) || (nav_keyboard_active && IsKeyPressed(ImGuiKey_LeftArrow, ImGuiKeyOwner_None, repeat_mode)))) { g.NavMoveDir = ImGuiDir_Left; } - if (!IsActiveIdUsingNavDir(ImGuiDir_Right) && ((nav_gamepad_active && IsKeyPressed(ImGuiKey_GamepadDpadRight, ImGuiKeyOwner_None, repeat_mode)) || (nav_keyboard_active && IsKeyPressed(ImGuiKey_RightArrow, ImGuiKeyOwner_None, repeat_mode)))) { g.NavMoveDir = ImGuiDir_Right; } - if (!IsActiveIdUsingNavDir(ImGuiDir_Up) && ((nav_gamepad_active && IsKeyPressed(ImGuiKey_GamepadDpadUp, ImGuiKeyOwner_None, repeat_mode)) || (nav_keyboard_active && IsKeyPressed(ImGuiKey_UpArrow, ImGuiKeyOwner_None, repeat_mode)))) { g.NavMoveDir = ImGuiDir_Up; } - if (!IsActiveIdUsingNavDir(ImGuiDir_Down) && ((nav_gamepad_active && IsKeyPressed(ImGuiKey_GamepadDpadDown, ImGuiKeyOwner_None, repeat_mode)) || (nav_keyboard_active && IsKeyPressed(ImGuiKey_DownArrow, ImGuiKeyOwner_None, repeat_mode)))) { g.NavMoveDir = ImGuiDir_Down; } - } - g.NavMoveClipDir = g.NavMoveDir; - g.NavScoringNoClipRect = ImRect(+FLT_MAX, +FLT_MAX, -FLT_MAX, -FLT_MAX); - } - - // Update PageUp/PageDown/Home/End scroll - // FIXME-NAV: Consider enabling those keys even without the master ImGuiConfigFlags_NavEnableKeyboard flag? - float scoring_rect_offset_y = 0.0f; - if (window && g.NavMoveDir == ImGuiDir_None && nav_keyboard_active) - scoring_rect_offset_y = NavUpdatePageUpPageDown(); - if (scoring_rect_offset_y != 0.0f) - { - g.NavScoringNoClipRect = window->InnerRect; - g.NavScoringNoClipRect.TranslateY(scoring_rect_offset_y); - } - - // [DEBUG] Always send a request when holding CTRL. Hold CTRL + Arrow change the direction. -#if IMGUI_DEBUG_NAV_SCORING - //if (io.KeyCtrl && IsKeyPressed(ImGuiKey_C)) - // g.NavMoveDirForDebug = (ImGuiDir)((g.NavMoveDirForDebug + 1) & 3); - if (io.KeyCtrl) - { - if (g.NavMoveDir == ImGuiDir_None) - g.NavMoveDir = g.NavMoveDirForDebug; - g.NavMoveClipDir = g.NavMoveDir; - g.NavMoveFlags |= ImGuiNavMoveFlags_DebugNoResult; - } -#endif - - // Submit - g.NavMoveForwardToNextFrame = false; - if (g.NavMoveDir != ImGuiDir_None) - NavMoveRequestSubmit(g.NavMoveDir, g.NavMoveClipDir, g.NavMoveFlags, g.NavMoveScrollFlags); - - // Moving with no reference triggers an init request (will be used as a fallback if the direction fails to find a match) - if (g.NavMoveSubmitted && g.NavId == 0) - { - IMGUI_DEBUG_LOG_NAV("[nav] NavInitRequest: from move, window \"%s\", layer=%d\n", window ? window->Name : "", g.NavLayer); - g.NavInitRequest = g.NavInitRequestFromMove = true; - g.NavInitResult.ID = 0; - g.NavDisableHighlight = false; - } - - // When using gamepad, we project the reference nav bounding box into window visible area. - // This is to allow resuming navigation inside the visible area after doing a large amount of scrolling, - // since with gamepad all movements are relative (can't focus a visible object like we can with the mouse). - if (g.NavMoveSubmitted && g.NavInputSource == ImGuiInputSource_Gamepad && g.NavLayer == ImGuiNavLayer_Main && window != NULL)// && (g.NavMoveFlags & ImGuiNavMoveFlags_Forwarded)) - { - bool clamp_x = (g.NavMoveFlags & (ImGuiNavMoveFlags_LoopX | ImGuiNavMoveFlags_WrapX)) == 0; - bool clamp_y = (g.NavMoveFlags & (ImGuiNavMoveFlags_LoopY | ImGuiNavMoveFlags_WrapY)) == 0; - ImRect inner_rect_rel = WindowRectAbsToRel(window, ImRect(window->InnerRect.Min - ImVec2(1, 1), window->InnerRect.Max + ImVec2(1, 1))); - - // Take account of changing scroll to handle triggering a new move request on a scrolling frame. (#6171) - // Otherwise 'inner_rect_rel' would be off on the move result frame. - inner_rect_rel.Translate(CalcNextScrollFromScrollTargetAndClamp(window) - window->Scroll); - - if ((clamp_x || clamp_y) && !inner_rect_rel.Contains(window->NavRectRel[g.NavLayer])) - { - IMGUI_DEBUG_LOG_NAV("[nav] NavMoveRequest: clamp NavRectRel for gamepad move\n"); - float pad_x = ImMin(inner_rect_rel.GetWidth(), window->CalcFontSize() * 0.5f); - float pad_y = ImMin(inner_rect_rel.GetHeight(), window->CalcFontSize() * 0.5f); // Terrible approximation for the intent of starting navigation from first fully visible item - inner_rect_rel.Min.x = clamp_x ? (inner_rect_rel.Min.x + pad_x) : -FLT_MAX; - inner_rect_rel.Max.x = clamp_x ? (inner_rect_rel.Max.x - pad_x) : +FLT_MAX; - inner_rect_rel.Min.y = clamp_y ? (inner_rect_rel.Min.y + pad_y) : -FLT_MAX; - inner_rect_rel.Max.y = clamp_y ? (inner_rect_rel.Max.y - pad_y) : +FLT_MAX; - window->NavRectRel[g.NavLayer].ClipWithFull(inner_rect_rel); - g.NavId = 0; - } - } - - // For scoring we use a single segment on the left side our current item bounding box (not touching the edge to avoid box overlap with zero-spaced items) - ImRect scoring_rect; - if (window != NULL) - { - ImRect nav_rect_rel = !window->NavRectRel[g.NavLayer].IsInverted() ? window->NavRectRel[g.NavLayer] : ImRect(0, 0, 0, 0); - scoring_rect = WindowRectRelToAbs(window, nav_rect_rel); - scoring_rect.TranslateY(scoring_rect_offset_y); - if (g.NavMoveSubmitted) - NavBiasScoringRect(scoring_rect, window->RootWindowForNav->NavPreferredScoringPosRel[g.NavLayer], g.NavMoveDir, g.NavMoveFlags); - IM_ASSERT(!scoring_rect.IsInverted()); // Ensure we have a non-inverted bounding box here will allow us to remove extraneous ImFabs() calls in NavScoreItem(). - //GetForegroundDrawList()->AddRect(scoring_rect.Min, scoring_rect.Max, IM_COL32(255,200,0,255)); // [DEBUG] - //if (!g.NavScoringNoClipRect.IsInverted()) { GetForegroundDrawList()->AddRect(g.NavScoringNoClipRect.Min, g.NavScoringNoClipRect.Max, IM_COL32(255, 200, 0, 255)); } // [DEBUG] - } - g.NavScoringRect = scoring_rect; - g.NavScoringNoClipRect.Add(scoring_rect); -} - -void ImGui::NavUpdateCreateTabbingRequest() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.NavWindow; - IM_ASSERT(g.NavMoveDir == ImGuiDir_None); - if (window == NULL || g.NavWindowingTarget != NULL || (window->Flags & ImGuiWindowFlags_NoNavInputs)) - return; - - const bool tab_pressed = IsKeyPressed(ImGuiKey_Tab, ImGuiKeyOwner_None, ImGuiInputFlags_Repeat) && !g.IO.KeyCtrl && !g.IO.KeyAlt; - if (!tab_pressed) - return; - - // Initiate tabbing request - // (this is ALWAYS ENABLED, regardless of ImGuiConfigFlags_NavEnableKeyboard flag!) - // See NavProcessItemForTabbingRequest() for a description of the various forward/backward tabbing cases with and without wrapping. - const bool nav_keyboard_active = (g.IO.ConfigFlags & ImGuiConfigFlags_NavEnableKeyboard) != 0; - if (nav_keyboard_active) - g.NavTabbingDir = g.IO.KeyShift ? -1 : (g.NavDisableHighlight == true && g.ActiveId == 0) ? 0 : +1; - else - g.NavTabbingDir = g.IO.KeyShift ? -1 : (g.ActiveId == 0) ? 0 : +1; - ImGuiNavMoveFlags move_flags = ImGuiNavMoveFlags_IsTabbing | ImGuiNavMoveFlags_Activate; - ImGuiScrollFlags scroll_flags = window->Appearing ? ImGuiScrollFlags_KeepVisibleEdgeX | ImGuiScrollFlags_AlwaysCenterY : ImGuiScrollFlags_KeepVisibleEdgeX | ImGuiScrollFlags_KeepVisibleEdgeY; - ImGuiDir clip_dir = (g.NavTabbingDir < 0) ? ImGuiDir_Up : ImGuiDir_Down; - NavMoveRequestSubmit(ImGuiDir_None, clip_dir, move_flags, scroll_flags); // FIXME-NAV: Once we refactor tabbing, add LegacyApi flag to not activate non-inputable. - g.NavTabbingCounter = -1; -} - -// Apply result from previous frame navigation directional move request. Always called from NavUpdate() -void ImGui::NavMoveRequestApplyResult() -{ - ImGuiContext& g = *GImGui; -#if IMGUI_DEBUG_NAV_SCORING - if (g.NavMoveFlags & ImGuiNavMoveFlags_DebugNoResult) // [DEBUG] Scoring all items in NavWindow at all times - return; -#endif - - // Select which result to use - ImGuiNavItemData* result = (g.NavMoveResultLocal.ID != 0) ? &g.NavMoveResultLocal : (g.NavMoveResultOther.ID != 0) ? &g.NavMoveResultOther : NULL; - - // Tabbing forward wrap - if ((g.NavMoveFlags & ImGuiNavMoveFlags_IsTabbing) && result == NULL) - if ((g.NavTabbingCounter == 1 || g.NavTabbingDir == 0) && g.NavTabbingResultFirst.ID) - result = &g.NavTabbingResultFirst; - - // In a situation when there are no results but NavId != 0, re-enable the Navigation highlight (because g.NavId is not considered as a possible result) - const ImGuiAxis axis = (g.NavMoveDir == ImGuiDir_Up || g.NavMoveDir == ImGuiDir_Down) ? ImGuiAxis_Y : ImGuiAxis_X; - if (result == NULL) - { - if (g.NavMoveFlags & ImGuiNavMoveFlags_IsTabbing) - g.NavMoveFlags |= ImGuiNavMoveFlags_NoSetNavHighlight; - if (g.NavId != 0 && (g.NavMoveFlags & ImGuiNavMoveFlags_NoSetNavHighlight) == 0) - NavRestoreHighlightAfterMove(); - NavClearPreferredPosForAxis(axis); // On a failed move, clear preferred pos for this axis. - IMGUI_DEBUG_LOG_NAV("[nav] NavMoveSubmitted but not led to a result!\n"); - return; - } - - // PageUp/PageDown behavior first jumps to the bottom/top mostly visible item, _otherwise_ use the result from the previous/next page. - if (g.NavMoveFlags & ImGuiNavMoveFlags_AlsoScoreVisibleSet) - if (g.NavMoveResultLocalVisible.ID != 0 && g.NavMoveResultLocalVisible.ID != g.NavId) - result = &g.NavMoveResultLocalVisible; - - // Maybe entering a flattened child from the outside? In this case solve the tie using the regular scoring rules. - if (result != &g.NavMoveResultOther && g.NavMoveResultOther.ID != 0 && g.NavMoveResultOther.Window->ParentWindow == g.NavWindow) - if ((g.NavMoveResultOther.DistBox < result->DistBox) || (g.NavMoveResultOther.DistBox == result->DistBox && g.NavMoveResultOther.DistCenter < result->DistCenter)) - result = &g.NavMoveResultOther; - IM_ASSERT(g.NavWindow && result->Window); - - // Scroll to keep newly navigated item fully into view. - if (g.NavLayer == ImGuiNavLayer_Main) - { - ImRect rect_abs = WindowRectRelToAbs(result->Window, result->RectRel); - ScrollToRectEx(result->Window, rect_abs, g.NavMoveScrollFlags); - - if (g.NavMoveFlags & ImGuiNavMoveFlags_ScrollToEdgeY) - { - // FIXME: Should remove this? Or make more precise: use ScrollToRectEx() with edge? - float scroll_target = (g.NavMoveDir == ImGuiDir_Up) ? result->Window->ScrollMax.y : 0.0f; - SetScrollY(result->Window, scroll_target); - } - } - - if (g.NavWindow != result->Window) - { - IMGUI_DEBUG_LOG_FOCUS("[focus] NavMoveRequest: SetNavWindow(\"%s\")\n", result->Window->Name); - g.NavWindow = result->Window; - g.NavLastValidSelectionUserData = ImGuiSelectionUserData_Invalid; - } - if (g.ActiveId != result->ID) - ClearActiveID(); - - // Don't set NavJustMovedToId if just landed on the same spot (which may happen with ImGuiNavMoveFlags_AllowCurrentNavId) - // PageUp/PageDown however sets always set NavJustMovedTo (vs Home/End which doesn't) mimicking Windows behavior. - if ((g.NavId != result->ID || (g.NavMoveFlags & ImGuiNavMoveFlags_IsPageMove)) && (g.NavMoveFlags & ImGuiNavMoveFlags_NoSelect) == 0) - { - g.NavJustMovedToId = result->ID; - g.NavJustMovedToFocusScopeId = result->FocusScopeId; - g.NavJustMovedToKeyMods = g.NavMoveKeyMods; - } - - // Apply new NavID/Focus - IMGUI_DEBUG_LOG_NAV("[nav] NavMoveRequest: result NavID 0x%08X in Layer %d Window \"%s\"\n", result->ID, g.NavLayer, g.NavWindow->Name); - ImVec2 preferred_scoring_pos_rel = g.NavWindow->RootWindowForNav->NavPreferredScoringPosRel[g.NavLayer]; - SetNavID(result->ID, g.NavLayer, result->FocusScopeId, result->RectRel); - if (result->SelectionUserData != ImGuiSelectionUserData_Invalid) - g.NavLastValidSelectionUserData = result->SelectionUserData; - - // Restore last preferred position for current axis - // (storing in RootWindowForNav-> as the info is desirable at the beginning of a Move Request. In theory all storage should use RootWindowForNav..) - if ((g.NavMoveFlags & ImGuiNavMoveFlags_IsTabbing) == 0) - { - preferred_scoring_pos_rel[axis] = result->RectRel.GetCenter()[axis]; - g.NavWindow->RootWindowForNav->NavPreferredScoringPosRel[g.NavLayer] = preferred_scoring_pos_rel; - } - - // Tabbing: Activates Inputable, otherwise only Focus - if ((g.NavMoveFlags & ImGuiNavMoveFlags_IsTabbing) && (result->InFlags & ImGuiItemFlags_Inputable) == 0) - g.NavMoveFlags &= ~ImGuiNavMoveFlags_Activate; - - // Activate - if (g.NavMoveFlags & ImGuiNavMoveFlags_Activate) - { - g.NavNextActivateId = result->ID; - g.NavNextActivateFlags = ImGuiActivateFlags_None; - if (g.NavMoveFlags & ImGuiNavMoveFlags_IsTabbing) - g.NavNextActivateFlags |= ImGuiActivateFlags_PreferInput | ImGuiActivateFlags_TryToPreserveState; - } - - // Enable nav highlight - if ((g.NavMoveFlags & ImGuiNavMoveFlags_NoSetNavHighlight) == 0) - NavRestoreHighlightAfterMove(); -} - -// Process NavCancel input (to close a popup, get back to parent, clear focus) -// FIXME: In order to support e.g. Escape to clear a selection we'll need: -// - either to store the equivalent of ActiveIdUsingKeyInputMask for a FocusScope and test for it. -// - either to move most/all of those tests to the epilogue/end functions of the scope they are dealing with (e.g. exit child window in EndChild()) or in EndFrame(), to allow an earlier intercept -static void ImGui::NavUpdateCancelRequest() -{ - ImGuiContext& g = *GImGui; - const bool nav_gamepad_active = (g.IO.ConfigFlags & ImGuiConfigFlags_NavEnableGamepad) != 0 && (g.IO.BackendFlags & ImGuiBackendFlags_HasGamepad) != 0; - const bool nav_keyboard_active = (g.IO.ConfigFlags & ImGuiConfigFlags_NavEnableKeyboard) != 0; - if (!(nav_keyboard_active && IsKeyPressed(ImGuiKey_Escape, ImGuiKeyOwner_None)) && !(nav_gamepad_active && IsKeyPressed(ImGuiKey_NavGamepadCancel, ImGuiKeyOwner_None))) - return; - - IMGUI_DEBUG_LOG_NAV("[nav] NavUpdateCancelRequest()\n"); - if (g.ActiveId != 0) - { - ClearActiveID(); - } - else if (g.NavLayer != ImGuiNavLayer_Main) - { - // Leave the "menu" layer - NavRestoreLayer(ImGuiNavLayer_Main); - NavRestoreHighlightAfterMove(); - } - else if (g.NavWindow && g.NavWindow != g.NavWindow->RootWindow && !(g.NavWindow->Flags & ImGuiWindowFlags_Popup) && g.NavWindow->ParentWindow) - { - // Exit child window - ImGuiWindow* child_window = g.NavWindow; - ImGuiWindow* parent_window = g.NavWindow->ParentWindow; - IM_ASSERT(child_window->ChildId != 0); - ImRect child_rect = child_window->Rect(); - FocusWindow(parent_window); - SetNavID(child_window->ChildId, ImGuiNavLayer_Main, 0, WindowRectAbsToRel(parent_window, child_rect)); - NavRestoreHighlightAfterMove(); - } - else if (g.OpenPopupStack.Size > 0 && g.OpenPopupStack.back().Window != NULL && !(g.OpenPopupStack.back().Window->Flags & ImGuiWindowFlags_Modal)) - { - // Close open popup/menu - ClosePopupToLevel(g.OpenPopupStack.Size - 1, true); - } - else - { - // Clear NavLastId for popups but keep it for regular child window so we can leave one and come back where we were - if (g.NavWindow && ((g.NavWindow->Flags & ImGuiWindowFlags_Popup) || !(g.NavWindow->Flags & ImGuiWindowFlags_ChildWindow))) - g.NavWindow->NavLastIds[0] = 0; - g.NavId = 0; - } -} - -// Handle PageUp/PageDown/Home/End keys -// Called from NavUpdateCreateMoveRequest() which will use our output to create a move request -// FIXME-NAV: This doesn't work properly with NavFlattened siblings as we use NavWindow rectangle for reference -// FIXME-NAV: how to get Home/End to aim at the beginning/end of a 2D grid? -static float ImGui::NavUpdatePageUpPageDown() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.NavWindow; - if ((window->Flags & ImGuiWindowFlags_NoNavInputs) || g.NavWindowingTarget != NULL) - return 0.0f; - - const bool page_up_held = IsKeyDown(ImGuiKey_PageUp, ImGuiKeyOwner_None); - const bool page_down_held = IsKeyDown(ImGuiKey_PageDown, ImGuiKeyOwner_None); - const bool home_pressed = IsKeyPressed(ImGuiKey_Home, ImGuiKeyOwner_None, ImGuiInputFlags_Repeat); - const bool end_pressed = IsKeyPressed(ImGuiKey_End, ImGuiKeyOwner_None, ImGuiInputFlags_Repeat); - if (page_up_held == page_down_held && home_pressed == end_pressed) // Proceed if either (not both) are pressed, otherwise early out - return 0.0f; - - if (g.NavLayer != ImGuiNavLayer_Main) - NavRestoreLayer(ImGuiNavLayer_Main); - - if (window->DC.NavLayersActiveMask == 0x00 && window->DC.NavWindowHasScrollY) - { - // Fallback manual-scroll when window has no navigable item - if (IsKeyPressed(ImGuiKey_PageUp, ImGuiKeyOwner_None, ImGuiInputFlags_Repeat)) - SetScrollY(window, window->Scroll.y - window->InnerRect.GetHeight()); - else if (IsKeyPressed(ImGuiKey_PageDown, ImGuiKeyOwner_None, ImGuiInputFlags_Repeat)) - SetScrollY(window, window->Scroll.y + window->InnerRect.GetHeight()); - else if (home_pressed) - SetScrollY(window, 0.0f); - else if (end_pressed) - SetScrollY(window, window->ScrollMax.y); - } - else - { - ImRect& nav_rect_rel = window->NavRectRel[g.NavLayer]; - const float page_offset_y = ImMax(0.0f, window->InnerRect.GetHeight() - window->CalcFontSize() * 1.0f + nav_rect_rel.GetHeight()); - float nav_scoring_rect_offset_y = 0.0f; - if (IsKeyPressed(ImGuiKey_PageUp, true)) - { - nav_scoring_rect_offset_y = -page_offset_y; - g.NavMoveDir = ImGuiDir_Down; // Because our scoring rect is offset up, we request the down direction (so we can always land on the last item) - g.NavMoveClipDir = ImGuiDir_Up; - g.NavMoveFlags = ImGuiNavMoveFlags_AllowCurrentNavId | ImGuiNavMoveFlags_AlsoScoreVisibleSet | ImGuiNavMoveFlags_IsPageMove; - } - else if (IsKeyPressed(ImGuiKey_PageDown, true)) - { - nav_scoring_rect_offset_y = +page_offset_y; - g.NavMoveDir = ImGuiDir_Up; // Because our scoring rect is offset down, we request the up direction (so we can always land on the last item) - g.NavMoveClipDir = ImGuiDir_Down; - g.NavMoveFlags = ImGuiNavMoveFlags_AllowCurrentNavId | ImGuiNavMoveFlags_AlsoScoreVisibleSet | ImGuiNavMoveFlags_IsPageMove; - } - else if (home_pressed) - { - // FIXME-NAV: handling of Home/End is assuming that the top/bottom most item will be visible with Scroll.y == 0/ScrollMax.y - // Scrolling will be handled via the ImGuiNavMoveFlags_ScrollToEdgeY flag, we don't scroll immediately to avoid scrolling happening before nav result. - // Preserve current horizontal position if we have any. - nav_rect_rel.Min.y = nav_rect_rel.Max.y = 0.0f; - if (nav_rect_rel.IsInverted()) - nav_rect_rel.Min.x = nav_rect_rel.Max.x = 0.0f; - g.NavMoveDir = ImGuiDir_Down; - g.NavMoveFlags = ImGuiNavMoveFlags_AllowCurrentNavId | ImGuiNavMoveFlags_ScrollToEdgeY; - // FIXME-NAV: MoveClipDir left to _None, intentional? - } - else if (end_pressed) - { - nav_rect_rel.Min.y = nav_rect_rel.Max.y = window->ContentSize.y; - if (nav_rect_rel.IsInverted()) - nav_rect_rel.Min.x = nav_rect_rel.Max.x = 0.0f; - g.NavMoveDir = ImGuiDir_Up; - g.NavMoveFlags = ImGuiNavMoveFlags_AllowCurrentNavId | ImGuiNavMoveFlags_ScrollToEdgeY; - // FIXME-NAV: MoveClipDir left to _None, intentional? - } - return nav_scoring_rect_offset_y; - } - return 0.0f; -} - -static void ImGui::NavEndFrame() -{ - ImGuiContext& g = *GImGui; - - // Show CTRL+TAB list window - if (g.NavWindowingTarget != NULL) - NavUpdateWindowingOverlay(); - - // Perform wrap-around in menus - // FIXME-NAV: Wrap may need to apply a weight bias on the other axis. e.g. 4x4 grid with 2 last items missing on last item won't handle LoopY/WrapY correctly. - // FIXME-NAV: Wrap (not Loop) support could be handled by the scoring function and then WrapX would function without an extra frame. - if (g.NavWindow && NavMoveRequestButNoResultYet() && (g.NavMoveFlags & ImGuiNavMoveFlags_WrapMask_) && (g.NavMoveFlags & ImGuiNavMoveFlags_Forwarded) == 0) - NavUpdateCreateWrappingRequest(); -} - -static void ImGui::NavUpdateCreateWrappingRequest() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.NavWindow; - - bool do_forward = false; - ImRect bb_rel = window->NavRectRel[g.NavLayer]; - ImGuiDir clip_dir = g.NavMoveDir; - - const ImGuiNavMoveFlags move_flags = g.NavMoveFlags; - //const ImGuiAxis move_axis = (g.NavMoveDir == ImGuiDir_Up || g.NavMoveDir == ImGuiDir_Down) ? ImGuiAxis_Y : ImGuiAxis_X; - if (g.NavMoveDir == ImGuiDir_Left && (move_flags & (ImGuiNavMoveFlags_WrapX | ImGuiNavMoveFlags_LoopX))) - { - bb_rel.Min.x = bb_rel.Max.x = window->ContentSize.x + window->WindowPadding.x; - if (move_flags & ImGuiNavMoveFlags_WrapX) - { - bb_rel.TranslateY(-bb_rel.GetHeight()); // Previous row - clip_dir = ImGuiDir_Up; - } - do_forward = true; - } - if (g.NavMoveDir == ImGuiDir_Right && (move_flags & (ImGuiNavMoveFlags_WrapX | ImGuiNavMoveFlags_LoopX))) - { - bb_rel.Min.x = bb_rel.Max.x = -window->WindowPadding.x; - if (move_flags & ImGuiNavMoveFlags_WrapX) - { - bb_rel.TranslateY(+bb_rel.GetHeight()); // Next row - clip_dir = ImGuiDir_Down; - } - do_forward = true; - } - if (g.NavMoveDir == ImGuiDir_Up && (move_flags & (ImGuiNavMoveFlags_WrapY | ImGuiNavMoveFlags_LoopY))) - { - bb_rel.Min.y = bb_rel.Max.y = window->ContentSize.y + window->WindowPadding.y; - if (move_flags & ImGuiNavMoveFlags_WrapY) - { - bb_rel.TranslateX(-bb_rel.GetWidth()); // Previous column - clip_dir = ImGuiDir_Left; - } - do_forward = true; - } - if (g.NavMoveDir == ImGuiDir_Down && (move_flags & (ImGuiNavMoveFlags_WrapY | ImGuiNavMoveFlags_LoopY))) - { - bb_rel.Min.y = bb_rel.Max.y = -window->WindowPadding.y; - if (move_flags & ImGuiNavMoveFlags_WrapY) - { - bb_rel.TranslateX(+bb_rel.GetWidth()); // Next column - clip_dir = ImGuiDir_Right; - } - do_forward = true; - } - if (!do_forward) - return; - window->NavRectRel[g.NavLayer] = bb_rel; - NavClearPreferredPosForAxis(ImGuiAxis_X); - NavClearPreferredPosForAxis(ImGuiAxis_Y); - NavMoveRequestForward(g.NavMoveDir, clip_dir, move_flags, g.NavMoveScrollFlags); -} - -static int ImGui::FindWindowFocusIndex(ImGuiWindow* window) -{ - ImGuiContext& g = *GImGui; - IM_UNUSED(g); - int order = window->FocusOrder; - IM_ASSERT(window->RootWindow == window); // No child window (not testing _ChildWindow because of docking) - IM_ASSERT(g.WindowsFocusOrder[order] == window); - return order; -} - -static ImGuiWindow* FindWindowNavFocusable(int i_start, int i_stop, int dir) // FIXME-OPT O(N) -{ - ImGuiContext& g = *GImGui; - for (int i = i_start; i >= 0 && i < g.WindowsFocusOrder.Size && i != i_stop; i += dir) - if (ImGui::IsWindowNavFocusable(g.WindowsFocusOrder[i])) - return g.WindowsFocusOrder[i]; - return NULL; -} - -static void NavUpdateWindowingHighlightWindow(int focus_change_dir) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(g.NavWindowingTarget); - if (g.NavWindowingTarget->Flags & ImGuiWindowFlags_Modal) - return; - - const int i_current = ImGui::FindWindowFocusIndex(g.NavWindowingTarget); - ImGuiWindow* window_target = FindWindowNavFocusable(i_current + focus_change_dir, -INT_MAX, focus_change_dir); - if (!window_target) - window_target = FindWindowNavFocusable((focus_change_dir < 0) ? (g.WindowsFocusOrder.Size - 1) : 0, i_current, focus_change_dir); - if (window_target) // Don't reset windowing target if there's a single window in the list - { - g.NavWindowingTarget = g.NavWindowingTargetAnim = window_target; - g.NavWindowingAccumDeltaPos = g.NavWindowingAccumDeltaSize = ImVec2(0.0f, 0.0f); - } - g.NavWindowingToggleLayer = false; -} - -// Windowing management mode -// Keyboard: CTRL+Tab (change focus/move/resize), Alt (toggle menu layer) -// Gamepad: Hold Menu/Square (change focus/move/resize), Tap Menu/Square (toggle menu layer) -static void ImGui::NavUpdateWindowing() -{ - ImGuiContext& g = *GImGui; - ImGuiIO& io = g.IO; - - ImGuiWindow* apply_focus_window = NULL; - bool apply_toggle_layer = false; - - ImGuiWindow* modal_window = GetTopMostPopupModal(); - bool allow_windowing = (modal_window == NULL); // FIXME: This prevent CTRL+TAB from being usable with windows that are inside the Begin-stack of that modal. - if (!allow_windowing) - g.NavWindowingTarget = NULL; - - // Fade out - if (g.NavWindowingTargetAnim && g.NavWindowingTarget == NULL) - { - g.NavWindowingHighlightAlpha = ImMax(g.NavWindowingHighlightAlpha - io.DeltaTime * 10.0f, 0.0f); - if (g.DimBgRatio <= 0.0f && g.NavWindowingHighlightAlpha <= 0.0f) - g.NavWindowingTargetAnim = NULL; - } - - // Start CTRL+Tab or Square+L/R window selection - const ImGuiID owner_id = ImHashStr("###NavUpdateWindowing"); - const bool nav_gamepad_active = (io.ConfigFlags & ImGuiConfigFlags_NavEnableGamepad) != 0 && (io.BackendFlags & ImGuiBackendFlags_HasGamepad) != 0; - const bool nav_keyboard_active = (io.ConfigFlags & ImGuiConfigFlags_NavEnableKeyboard) != 0; - const bool keyboard_next_window = allow_windowing && g.ConfigNavWindowingKeyNext && Shortcut(g.ConfigNavWindowingKeyNext, owner_id, ImGuiInputFlags_Repeat | ImGuiInputFlags_RouteAlways); - const bool keyboard_prev_window = allow_windowing && g.ConfigNavWindowingKeyPrev && Shortcut(g.ConfigNavWindowingKeyPrev, owner_id, ImGuiInputFlags_Repeat | ImGuiInputFlags_RouteAlways); - const bool start_windowing_with_gamepad = allow_windowing && nav_gamepad_active && !g.NavWindowingTarget && IsKeyPressed(ImGuiKey_NavGamepadMenu, 0, ImGuiInputFlags_None); - const bool start_windowing_with_keyboard = allow_windowing && !g.NavWindowingTarget && (keyboard_next_window || keyboard_prev_window); // Note: enabled even without NavEnableKeyboard! - if (start_windowing_with_gamepad || start_windowing_with_keyboard) - if (ImGuiWindow* window = g.NavWindow ? g.NavWindow : FindWindowNavFocusable(g.WindowsFocusOrder.Size - 1, -INT_MAX, -1)) - { - g.NavWindowingTarget = g.NavWindowingTargetAnim = window->RootWindow; - g.NavWindowingTimer = g.NavWindowingHighlightAlpha = 0.0f; - g.NavWindowingAccumDeltaPos = g.NavWindowingAccumDeltaSize = ImVec2(0.0f, 0.0f); - g.NavWindowingToggleLayer = start_windowing_with_gamepad ? true : false; // Gamepad starts toggling layer - g.NavInputSource = start_windowing_with_keyboard ? ImGuiInputSource_Keyboard : ImGuiInputSource_Gamepad; - - // Register ownership of our mods. Using ImGuiInputFlags_RouteGlobalHigh in the Shortcut() calls instead would probably be correct but may have more side-effects. - if (keyboard_next_window || keyboard_prev_window) - SetKeyOwnersForKeyChord((g.ConfigNavWindowingKeyNext | g.ConfigNavWindowingKeyPrev) & ImGuiMod_Mask_, owner_id); - } - - // Gamepad update - g.NavWindowingTimer += io.DeltaTime; - if (g.NavWindowingTarget && g.NavInputSource == ImGuiInputSource_Gamepad) - { - // Highlight only appears after a brief time holding the button, so that a fast tap on PadMenu (to toggle NavLayer) doesn't add visual noise - g.NavWindowingHighlightAlpha = ImMax(g.NavWindowingHighlightAlpha, ImSaturate((g.NavWindowingTimer - NAV_WINDOWING_HIGHLIGHT_DELAY) / 0.05f)); - - // Select window to focus - const int focus_change_dir = (int)IsKeyPressed(ImGuiKey_GamepadL1) - (int)IsKeyPressed(ImGuiKey_GamepadR1); - if (focus_change_dir != 0) - { - NavUpdateWindowingHighlightWindow(focus_change_dir); - g.NavWindowingHighlightAlpha = 1.0f; - } - - // Single press toggles NavLayer, long press with L/R apply actual focus on release (until then the window was merely rendered top-most) - if (!IsKeyDown(ImGuiKey_NavGamepadMenu)) - { - g.NavWindowingToggleLayer &= (g.NavWindowingHighlightAlpha < 1.0f); // Once button was held long enough we don't consider it a tap-to-toggle-layer press anymore. - if (g.NavWindowingToggleLayer && g.NavWindow) - apply_toggle_layer = true; - else if (!g.NavWindowingToggleLayer) - apply_focus_window = g.NavWindowingTarget; - g.NavWindowingTarget = NULL; - } - } - - // Keyboard: Focus - if (g.NavWindowingTarget && g.NavInputSource == ImGuiInputSource_Keyboard) - { - // Visuals only appears after a brief time after pressing TAB the first time, so that a fast CTRL+TAB doesn't add visual noise - ImGuiKeyChord shared_mods = ((g.ConfigNavWindowingKeyNext ? g.ConfigNavWindowingKeyNext : ImGuiMod_Mask_) & (g.ConfigNavWindowingKeyPrev ? g.ConfigNavWindowingKeyPrev : ImGuiMod_Mask_)) & ImGuiMod_Mask_; - IM_ASSERT(shared_mods != 0); // Next/Prev shortcut currently needs a shared modifier to "hold", otherwise Prev actions would keep cycling between two windows. - g.NavWindowingHighlightAlpha = ImMax(g.NavWindowingHighlightAlpha, ImSaturate((g.NavWindowingTimer - NAV_WINDOWING_HIGHLIGHT_DELAY) / 0.05f)); // 1.0f - if (keyboard_next_window || keyboard_prev_window) - NavUpdateWindowingHighlightWindow(keyboard_next_window ? -1 : +1); - else if ((io.KeyMods & shared_mods) != shared_mods) - apply_focus_window = g.NavWindowingTarget; - } - - // Keyboard: Press and Release ALT to toggle menu layer - // - Testing that only Alt is tested prevents Alt+Shift or AltGR from toggling menu layer. - // - AltGR is normally Alt+Ctrl but we can't reliably detect it (not all backends/systems/layout emit it as Alt+Ctrl). But even on keyboards without AltGR we don't want Alt+Ctrl to open menu anyway. - if (nav_keyboard_active && IsKeyPressed(ImGuiMod_Alt, ImGuiKeyOwner_None)) - { - g.NavWindowingToggleLayer = true; - g.NavInputSource = ImGuiInputSource_Keyboard; - } - if (g.NavWindowingToggleLayer && g.NavInputSource == ImGuiInputSource_Keyboard) - { - // We cancel toggling nav layer when any text has been typed (generally while holding Alt). (See #370) - // We cancel toggling nav layer when other modifiers are pressed. (See #4439) - // We cancel toggling nav layer if an owner has claimed the key. - if (io.InputQueueCharacters.Size > 0 || io.KeyCtrl || io.KeyShift || io.KeySuper || TestKeyOwner(ImGuiMod_Alt, ImGuiKeyOwner_None) == false) - g.NavWindowingToggleLayer = false; - - // Apply layer toggle on release - // Important: as before version <18314 we lacked an explicit IO event for focus gain/loss, we also compare mouse validity to detect old backends clearing mouse pos on focus loss. - if (IsKeyReleased(ImGuiMod_Alt) && g.NavWindowingToggleLayer) - if (g.ActiveId == 0 || g.ActiveIdAllowOverlap) - if (IsMousePosValid(&io.MousePos) == IsMousePosValid(&io.MousePosPrev)) - apply_toggle_layer = true; - if (!IsKeyDown(ImGuiMod_Alt)) - g.NavWindowingToggleLayer = false; - } - - // Move window - if (g.NavWindowingTarget && !(g.NavWindowingTarget->Flags & ImGuiWindowFlags_NoMove)) - { - ImVec2 nav_move_dir; - if (g.NavInputSource == ImGuiInputSource_Keyboard && !io.KeyShift) - nav_move_dir = GetKeyMagnitude2d(ImGuiKey_LeftArrow, ImGuiKey_RightArrow, ImGuiKey_UpArrow, ImGuiKey_DownArrow); - if (g.NavInputSource == ImGuiInputSource_Gamepad) - nav_move_dir = GetKeyMagnitude2d(ImGuiKey_GamepadLStickLeft, ImGuiKey_GamepadLStickRight, ImGuiKey_GamepadLStickUp, ImGuiKey_GamepadLStickDown); - if (nav_move_dir.x != 0.0f || nav_move_dir.y != 0.0f) - { - const float NAV_MOVE_SPEED = 800.0f; - const float move_step = NAV_MOVE_SPEED * io.DeltaTime * ImMin(io.DisplayFramebufferScale.x, io.DisplayFramebufferScale.y); - g.NavWindowingAccumDeltaPos += nav_move_dir * move_step; - g.NavDisableMouseHover = true; - ImVec2 accum_floored = ImTrunc(g.NavWindowingAccumDeltaPos); - if (accum_floored.x != 0.0f || accum_floored.y != 0.0f) - { - ImGuiWindow* moving_window = g.NavWindowingTarget->RootWindowDockTree; - SetWindowPos(moving_window, moving_window->Pos + accum_floored, ImGuiCond_Always); - g.NavWindowingAccumDeltaPos -= accum_floored; - } - } - } - - // Apply final focus - if (apply_focus_window && (g.NavWindow == NULL || apply_focus_window != g.NavWindow->RootWindow)) - { - // FIXME: Many actions here could be part of a higher-level/reused function. Why aren't they in FocusWindow() - // Investigate for each of them: ClearActiveID(), NavRestoreHighlightAfterMove(), NavRestoreLastChildNavWindow(), ClosePopupsOverWindow(), NavInitWindow() - ImGuiViewport* previous_viewport = g.NavWindow ? g.NavWindow->Viewport : NULL; - ClearActiveID(); - NavRestoreHighlightAfterMove(); - ClosePopupsOverWindow(apply_focus_window, false); - FocusWindow(apply_focus_window, ImGuiFocusRequestFlags_RestoreFocusedChild); - apply_focus_window = g.NavWindow; - if (apply_focus_window->NavLastIds[0] == 0) - NavInitWindow(apply_focus_window, false); - - // If the window has ONLY a menu layer (no main layer), select it directly - // Use NavLayersActiveMaskNext since windows didn't have a chance to be Begin()-ed on this frame, - // so CTRL+Tab where the keys are only held for 1 frame will be able to use correct layers mask since - // the target window as already been previewed once. - // FIXME-NAV: This should be done in NavInit.. or in FocusWindow... However in both of those cases, - // we won't have a guarantee that windows has been visible before and therefore NavLayersActiveMask* - // won't be valid. - if (apply_focus_window->DC.NavLayersActiveMaskNext == (1 << ImGuiNavLayer_Menu)) - g.NavLayer = ImGuiNavLayer_Menu; - - // Request OS level focus - if (apply_focus_window->Viewport != previous_viewport && g.PlatformIO.Platform_SetWindowFocus) - g.PlatformIO.Platform_SetWindowFocus(apply_focus_window->Viewport); - } - if (apply_focus_window) - g.NavWindowingTarget = NULL; - - // Apply menu/layer toggle - if (apply_toggle_layer && g.NavWindow) - { - ClearActiveID(); - - // Move to parent menu if necessary - ImGuiWindow* new_nav_window = g.NavWindow; - while (new_nav_window->ParentWindow - && (new_nav_window->DC.NavLayersActiveMask & (1 << ImGuiNavLayer_Menu)) == 0 - && (new_nav_window->Flags & ImGuiWindowFlags_ChildWindow) != 0 - && (new_nav_window->Flags & (ImGuiWindowFlags_Popup | ImGuiWindowFlags_ChildMenu)) == 0) - new_nav_window = new_nav_window->ParentWindow; - if (new_nav_window != g.NavWindow) - { - ImGuiWindow* old_nav_window = g.NavWindow; - FocusWindow(new_nav_window); - new_nav_window->NavLastChildNavWindow = old_nav_window; - } - - // Toggle layer - const ImGuiNavLayer new_nav_layer = (g.NavWindow->DC.NavLayersActiveMask & (1 << ImGuiNavLayer_Menu)) ? (ImGuiNavLayer)((int)g.NavLayer ^ 1) : ImGuiNavLayer_Main; - if (new_nav_layer != g.NavLayer) - { - // Reinitialize navigation when entering menu bar with the Alt key (FIXME: could be a properly of the layer?) - const bool preserve_layer_1_nav_id = (new_nav_window->DockNodeAsHost != NULL); - if (new_nav_layer == ImGuiNavLayer_Menu && !preserve_layer_1_nav_id) - g.NavWindow->NavLastIds[new_nav_layer] = 0; - NavRestoreLayer(new_nav_layer); - NavRestoreHighlightAfterMove(); - } - } -} - -// Window has already passed the IsWindowNavFocusable() -static const char* GetFallbackWindowNameForWindowingList(ImGuiWindow* window) -{ - if (window->Flags & ImGuiWindowFlags_Popup) - return ImGui::LocalizeGetMsg(ImGuiLocKey_WindowingPopup); - if ((window->Flags & ImGuiWindowFlags_MenuBar) && strcmp(window->Name, "##MainMenuBar") == 0) - return ImGui::LocalizeGetMsg(ImGuiLocKey_WindowingMainMenuBar); - if (window->DockNodeAsHost) - return "(Dock node)"; // Not normally shown to user. - return ImGui::LocalizeGetMsg(ImGuiLocKey_WindowingUntitled); -} - -// Overlay displayed when using CTRL+TAB. Called by EndFrame(). -void ImGui::NavUpdateWindowingOverlay() -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(g.NavWindowingTarget != NULL); - - if (g.NavWindowingTimer < NAV_WINDOWING_LIST_APPEAR_DELAY) - return; - - if (g.NavWindowingListWindow == NULL) - g.NavWindowingListWindow = FindWindowByName("###NavWindowingList"); - const ImGuiViewport* viewport = /*g.NavWindow ? g.NavWindow->Viewport :*/ GetMainViewport(); - SetNextWindowSizeConstraints(ImVec2(viewport->Size.x * 0.20f, viewport->Size.y * 0.20f), ImVec2(FLT_MAX, FLT_MAX)); - SetNextWindowPos(viewport->GetCenter(), ImGuiCond_Always, ImVec2(0.5f, 0.5f)); - PushStyleVar(ImGuiStyleVar_WindowPadding, g.Style.WindowPadding * 2.0f); - Begin("###NavWindowingList", NULL, ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_NoFocusOnAppearing | ImGuiWindowFlags_NoResize | ImGuiWindowFlags_NoMove | ImGuiWindowFlags_NoInputs | ImGuiWindowFlags_AlwaysAutoResize | ImGuiWindowFlags_NoSavedSettings); - for (int n = g.WindowsFocusOrder.Size - 1; n >= 0; n--) - { - ImGuiWindow* window = g.WindowsFocusOrder[n]; - IM_ASSERT(window != NULL); // Fix static analyzers - if (!IsWindowNavFocusable(window)) - continue; - const char* label = window->Name; - if (label == FindRenderedTextEnd(label)) - label = GetFallbackWindowNameForWindowingList(window); - Selectable(label, g.NavWindowingTarget == window); - } - End(); - PopStyleVar(); -} - - -//----------------------------------------------------------------------------- -// [SECTION] DRAG AND DROP -//----------------------------------------------------------------------------- - -bool ImGui::IsDragDropActive() -{ - ImGuiContext& g = *GImGui; - return g.DragDropActive; -} - -void ImGui::ClearDragDrop() -{ - ImGuiContext& g = *GImGui; - g.DragDropActive = false; - g.DragDropPayload.Clear(); - g.DragDropAcceptFlags = ImGuiDragDropFlags_None; - g.DragDropAcceptIdCurr = g.DragDropAcceptIdPrev = 0; - g.DragDropAcceptIdCurrRectSurface = FLT_MAX; - g.DragDropAcceptFrameCount = -1; - - g.DragDropPayloadBufHeap.clear(); - memset(&g.DragDropPayloadBufLocal, 0, sizeof(g.DragDropPayloadBufLocal)); -} - -bool ImGui::BeginTooltipHidden() -{ - ImGuiContext& g = *GImGui; - bool ret = Begin("##Tooltip_Hidden", NULL, ImGuiWindowFlags_Tooltip | ImGuiWindowFlags_NoInputs | ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_NoMove | ImGuiWindowFlags_NoResize | ImGuiWindowFlags_NoSavedSettings | ImGuiWindowFlags_AlwaysAutoResize); - SetWindowHiddendAndSkipItemsForCurrentFrame(g.CurrentWindow); - return ret; -} - -// When this returns true you need to: a) call SetDragDropPayload() exactly once, b) you may render the payload visual/description, c) call EndDragDropSource() -// If the item has an identifier: -// - This assume/require the item to be activated (typically via ButtonBehavior). -// - Therefore if you want to use this with a mouse button other than left mouse button, it is up to the item itself to activate with another button. -// - We then pull and use the mouse button that was used to activate the item and use it to carry on the drag. -// If the item has no identifier: -// - Currently always assume left mouse button. -bool ImGui::BeginDragDropSource(ImGuiDragDropFlags flags) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - - // FIXME-DRAGDROP: While in the common-most "drag from non-zero active id" case we can tell the mouse button, - // in both SourceExtern and id==0 cases we may requires something else (explicit flags or some heuristic). - ImGuiMouseButton mouse_button = ImGuiMouseButton_Left; - - bool source_drag_active = false; - ImGuiID source_id = 0; - ImGuiID source_parent_id = 0; - if (!(flags & ImGuiDragDropFlags_SourceExtern)) - { - source_id = g.LastItemData.ID; - if (source_id != 0) - { - // Common path: items with ID - if (g.ActiveId != source_id) - return false; - if (g.ActiveIdMouseButton != -1) - mouse_button = g.ActiveIdMouseButton; - if (g.IO.MouseDown[mouse_button] == false || window->SkipItems) - return false; - g.ActiveIdAllowOverlap = false; - } - else - { - // Uncommon path: items without ID - if (g.IO.MouseDown[mouse_button] == false || window->SkipItems) - return false; - if ((g.LastItemData.StatusFlags & ImGuiItemStatusFlags_HoveredRect) == 0 && (g.ActiveId == 0 || g.ActiveIdWindow != window)) - return false; - - // If you want to use BeginDragDropSource() on an item with no unique identifier for interaction, such as Text() or Image(), you need to: - // A) Read the explanation below, B) Use the ImGuiDragDropFlags_SourceAllowNullID flag. - if (!(flags & ImGuiDragDropFlags_SourceAllowNullID)) - { - IM_ASSERT(0); - return false; - } - - // Magic fallback to handle items with no assigned ID, e.g. Text(), Image() - // We build a throwaway ID based on current ID stack + relative AABB of items in window. - // THE IDENTIFIER WON'T SURVIVE ANY REPOSITIONING/RESIZINGG OF THE WIDGET, so if your widget moves your dragging operation will be canceled. - // We don't need to maintain/call ClearActiveID() as releasing the button will early out this function and trigger !ActiveIdIsAlive. - // Rely on keeping other window->LastItemXXX fields intact. - source_id = g.LastItemData.ID = window->GetIDFromRectangle(g.LastItemData.Rect); - KeepAliveID(source_id); - bool is_hovered = ItemHoverable(g.LastItemData.Rect, source_id, g.LastItemData.InFlags); - if (is_hovered && g.IO.MouseClicked[mouse_button]) - { - SetActiveID(source_id, window); - FocusWindow(window); - } - if (g.ActiveId == source_id) // Allow the underlying widget to display/return hovered during the mouse release frame, else we would get a flicker. - g.ActiveIdAllowOverlap = is_hovered; - } - if (g.ActiveId != source_id) - return false; - source_parent_id = window->IDStack.back(); - source_drag_active = IsMouseDragging(mouse_button); - - // Disable navigation and key inputs while dragging + cancel existing request if any - SetActiveIdUsingAllKeyboardKeys(); - } - else - { - window = NULL; - source_id = ImHashStr("#SourceExtern"); - source_drag_active = true; - } - - if (source_drag_active) - { - if (!g.DragDropActive) - { - IM_ASSERT(source_id != 0); - ClearDragDrop(); - ImGuiPayload& payload = g.DragDropPayload; - payload.SourceId = source_id; - payload.SourceParentId = source_parent_id; - g.DragDropActive = true; - g.DragDropSourceFlags = flags; - g.DragDropMouseButton = mouse_button; - if (payload.SourceId == g.ActiveId) - g.ActiveIdNoClearOnFocusLoss = true; - } - g.DragDropSourceFrameCount = g.FrameCount; - g.DragDropWithinSource = true; - - if (!(flags & ImGuiDragDropFlags_SourceNoPreviewTooltip)) - { - // Target can request the Source to not display its tooltip (we use a dedicated flag to make this request explicit) - // We unfortunately can't just modify the source flags and skip the call to BeginTooltip, as caller may be emitting contents. - bool ret; - if (g.DragDropAcceptIdPrev && (g.DragDropAcceptFlags & ImGuiDragDropFlags_AcceptNoPreviewTooltip)) - ret = BeginTooltipHidden(); - else - ret = BeginTooltip(); - IM_ASSERT(ret); // FIXME-NEWBEGIN: If this ever becomes false, we need to Begin("##Hidden", NULL, ImGuiWindowFlags_NoSavedSettings) + SetWindowHiddendAndSkipItemsForCurrentFrame(). - IM_UNUSED(ret); - } - - if (!(flags & ImGuiDragDropFlags_SourceNoDisableHover) && !(flags & ImGuiDragDropFlags_SourceExtern)) - g.LastItemData.StatusFlags &= ~ImGuiItemStatusFlags_HoveredRect; - - return true; - } - return false; -} - -void ImGui::EndDragDropSource() -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(g.DragDropActive); - IM_ASSERT(g.DragDropWithinSource && "Not after a BeginDragDropSource()?"); - - if (!(g.DragDropSourceFlags & ImGuiDragDropFlags_SourceNoPreviewTooltip)) - EndTooltip(); - - // Discard the drag if have not called SetDragDropPayload() - if (g.DragDropPayload.DataFrameCount == -1) - ClearDragDrop(); - g.DragDropWithinSource = false; -} - -// Use 'cond' to choose to submit payload on drag start or every frame -bool ImGui::SetDragDropPayload(const char* type, const void* data, size_t data_size, ImGuiCond cond) -{ - ImGuiContext& g = *GImGui; - ImGuiPayload& payload = g.DragDropPayload; - if (cond == 0) - cond = ImGuiCond_Always; - - IM_ASSERT(type != NULL); - IM_ASSERT(strlen(type) < IM_ARRAYSIZE(payload.DataType) && "Payload type can be at most 32 characters long"); - IM_ASSERT((data != NULL && data_size > 0) || (data == NULL && data_size == 0)); - IM_ASSERT(cond == ImGuiCond_Always || cond == ImGuiCond_Once); - IM_ASSERT(payload.SourceId != 0); // Not called between BeginDragDropSource() and EndDragDropSource() - - if (cond == ImGuiCond_Always || payload.DataFrameCount == -1) - { - // Copy payload - ImStrncpy(payload.DataType, type, IM_ARRAYSIZE(payload.DataType)); - g.DragDropPayloadBufHeap.resize(0); - if (data_size > sizeof(g.DragDropPayloadBufLocal)) - { - // Store in heap - g.DragDropPayloadBufHeap.resize((int)data_size); - payload.Data = g.DragDropPayloadBufHeap.Data; - memcpy(payload.Data, data, data_size); - } - else if (data_size > 0) - { - // Store locally - memset(&g.DragDropPayloadBufLocal, 0, sizeof(g.DragDropPayloadBufLocal)); - payload.Data = g.DragDropPayloadBufLocal; - memcpy(payload.Data, data, data_size); - } - else - { - payload.Data = NULL; - } - payload.DataSize = (int)data_size; - } - payload.DataFrameCount = g.FrameCount; - - // Return whether the payload has been accepted - return (g.DragDropAcceptFrameCount == g.FrameCount) || (g.DragDropAcceptFrameCount == g.FrameCount - 1); -} - -bool ImGui::BeginDragDropTargetCustom(const ImRect& bb, ImGuiID id) -{ - ImGuiContext& g = *GImGui; - if (!g.DragDropActive) - return false; - - ImGuiWindow* window = g.CurrentWindow; - ImGuiWindow* hovered_window = g.HoveredWindowUnderMovingWindow; - if (hovered_window == NULL || window->RootWindowDockTree != hovered_window->RootWindowDockTree) - return false; - IM_ASSERT(id != 0); - if (!IsMouseHoveringRect(bb.Min, bb.Max) || (id == g.DragDropPayload.SourceId)) - return false; - if (window->SkipItems) - return false; - - IM_ASSERT(g.DragDropWithinTarget == false); - g.DragDropTargetRect = bb; - g.DragDropTargetId = id; - g.DragDropWithinTarget = true; - return true; -} - -// We don't use BeginDragDropTargetCustom() and duplicate its code because: -// 1) we use LastItemRectHoveredRect which handles items that push a temporarily clip rectangle in their code. Calling BeginDragDropTargetCustom(LastItemRect) would not handle them. -// 2) and it's faster. as this code may be very frequently called, we want to early out as fast as we can. -// Also note how the HoveredWindow test is positioned differently in both functions (in both functions we optimize for the cheapest early out case) -bool ImGui::BeginDragDropTarget() -{ - ImGuiContext& g = *GImGui; - if (!g.DragDropActive) - return false; - - ImGuiWindow* window = g.CurrentWindow; - if (!(g.LastItemData.StatusFlags & ImGuiItemStatusFlags_HoveredRect)) - return false; - ImGuiWindow* hovered_window = g.HoveredWindowUnderMovingWindow; - if (hovered_window == NULL || window->RootWindowDockTree != hovered_window->RootWindowDockTree || window->SkipItems) - return false; - - const ImRect& display_rect = (g.LastItemData.StatusFlags & ImGuiItemStatusFlags_HasDisplayRect) ? g.LastItemData.DisplayRect : g.LastItemData.Rect; - ImGuiID id = g.LastItemData.ID; - if (id == 0) - { - id = window->GetIDFromRectangle(display_rect); - KeepAliveID(id); - } - if (g.DragDropPayload.SourceId == id) - return false; - - IM_ASSERT(g.DragDropWithinTarget == false); - g.DragDropTargetRect = display_rect; - g.DragDropTargetId = id; - g.DragDropWithinTarget = true; - return true; -} - -bool ImGui::IsDragDropPayloadBeingAccepted() -{ - ImGuiContext& g = *GImGui; - return g.DragDropActive && g.DragDropAcceptIdPrev != 0; -} - -const ImGuiPayload* ImGui::AcceptDragDropPayload(const char* type, ImGuiDragDropFlags flags) -{ - ImGuiContext& g = *GImGui; - ImGuiPayload& payload = g.DragDropPayload; - IM_ASSERT(g.DragDropActive); // Not called between BeginDragDropTarget() and EndDragDropTarget() ? - IM_ASSERT(payload.DataFrameCount != -1); // Forgot to call EndDragDropTarget() ? - if (type != NULL && !payload.IsDataType(type)) - return NULL; - - // Accept smallest drag target bounding box, this allows us to nest drag targets conveniently without ordering constraints. - // NB: We currently accept NULL id as target. However, overlapping targets requires a unique ID to function! - const bool was_accepted_previously = (g.DragDropAcceptIdPrev == g.DragDropTargetId); - ImRect r = g.DragDropTargetRect; - float r_surface = r.GetWidth() * r.GetHeight(); - if (r_surface > g.DragDropAcceptIdCurrRectSurface) - return NULL; - - g.DragDropAcceptFlags = flags; - g.DragDropAcceptIdCurr = g.DragDropTargetId; - g.DragDropAcceptIdCurrRectSurface = r_surface; - //IMGUI_DEBUG_LOG("AcceptDragDropPayload(): %08X: accept\n", g.DragDropTargetId); - - // Render default drop visuals - payload.Preview = was_accepted_previously; - flags |= (g.DragDropSourceFlags & ImGuiDragDropFlags_AcceptNoDrawDefaultRect); // Source can also inhibit the preview (useful for external sources that live for 1 frame) - if (!(flags & ImGuiDragDropFlags_AcceptNoDrawDefaultRect) && payload.Preview) - RenderDragDropTargetRect(r); - - g.DragDropAcceptFrameCount = g.FrameCount; - payload.Delivery = was_accepted_previously && !IsMouseDown(g.DragDropMouseButton); // For extern drag sources affecting OS window focus, it's easier to just test !IsMouseDown() instead of IsMouseReleased() - if (!payload.Delivery && !(flags & ImGuiDragDropFlags_AcceptBeforeDelivery)) - return NULL; - - //IMGUI_DEBUG_LOG("AcceptDragDropPayload(): %08X: return payload\n", g.DragDropTargetId); - return &payload; -} - -// FIXME-STYLE FIXME-DRAGDROP: Settle on a proper default visuals for drop target. -void ImGui::RenderDragDropTargetRect(const ImRect& bb) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - ImRect bb_display = bb; - bb_display.ClipWith(window->ClipRect); // Clip THEN expand so we have a way to visualize that target is not entirely visible. - bb_display.Expand(3.5f); - bool push_clip_rect = !window->ClipRect.Contains(bb_display); - if (push_clip_rect) - window->DrawList->PushClipRectFullScreen(); - window->DrawList->AddRect(bb_display.Min, bb_display.Max, GetColorU32(ImGuiCol_DragDropTarget), 0.0f, 0, 2.0f); - if (push_clip_rect) - window->DrawList->PopClipRect(); -} - -const ImGuiPayload* ImGui::GetDragDropPayload() -{ - ImGuiContext& g = *GImGui; - return (g.DragDropActive && g.DragDropPayload.DataFrameCount != -1) ? &g.DragDropPayload : NULL; -} - -void ImGui::EndDragDropTarget() -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(g.DragDropActive); - IM_ASSERT(g.DragDropWithinTarget); - g.DragDropWithinTarget = false; - - // Clear drag and drop state payload right after delivery - if (g.DragDropPayload.Delivery) - ClearDragDrop(); -} - -//----------------------------------------------------------------------------- -// [SECTION] LOGGING/CAPTURING -//----------------------------------------------------------------------------- -// All text output from the interface can be captured into tty/file/clipboard. -// By default, tree nodes are automatically opened during logging. -//----------------------------------------------------------------------------- - -// Pass text data straight to log (without being displayed) -static inline void LogTextV(ImGuiContext& g, const char* fmt, va_list args) -{ - if (g.LogFile) - { - g.LogBuffer.Buf.resize(0); - g.LogBuffer.appendfv(fmt, args); - ImFileWrite(g.LogBuffer.c_str(), sizeof(char), (ImU64)g.LogBuffer.size(), g.LogFile); - } - else - { - g.LogBuffer.appendfv(fmt, args); - } -} - -void ImGui::LogText(const char* fmt, ...) -{ - ImGuiContext& g = *GImGui; - if (!g.LogEnabled) - return; - - va_list args; - va_start(args, fmt); - LogTextV(g, fmt, args); - va_end(args); -} - -void ImGui::LogTextV(const char* fmt, va_list args) -{ - ImGuiContext& g = *GImGui; - if (!g.LogEnabled) - return; - - LogTextV(g, fmt, args); -} - -// Internal version that takes a position to decide on newline placement and pad items according to their depth. -// We split text into individual lines to add current tree level padding -// FIXME: This code is a little complicated perhaps, considering simplifying the whole system. -void ImGui::LogRenderedText(const ImVec2* ref_pos, const char* text, const char* text_end) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - - const char* prefix = g.LogNextPrefix; - const char* suffix = g.LogNextSuffix; - g.LogNextPrefix = g.LogNextSuffix = NULL; - - if (!text_end) - text_end = FindRenderedTextEnd(text, text_end); - - const bool log_new_line = ref_pos && (ref_pos->y > g.LogLinePosY + g.Style.FramePadding.y + 1); - if (ref_pos) - g.LogLinePosY = ref_pos->y; - if (log_new_line) - { - LogText(IM_NEWLINE); - g.LogLineFirstItem = true; - } - - if (prefix) - LogRenderedText(ref_pos, prefix, prefix + strlen(prefix)); // Calculate end ourself to ensure "##" are included here. - - // Re-adjust padding if we have popped out of our starting depth - if (g.LogDepthRef > window->DC.TreeDepth) - g.LogDepthRef = window->DC.TreeDepth; - const int tree_depth = (window->DC.TreeDepth - g.LogDepthRef); - - const char* text_remaining = text; - for (;;) - { - // Split the string. Each new line (after a '\n') is followed by indentation corresponding to the current depth of our log entry. - // We don't add a trailing \n yet to allow a subsequent item on the same line to be captured. - const char* line_start = text_remaining; - const char* line_end = ImStreolRange(line_start, text_end); - const bool is_last_line = (line_end == text_end); - if (line_start != line_end || !is_last_line) - { - const int line_length = (int)(line_end - line_start); - const int indentation = g.LogLineFirstItem ? tree_depth * 4 : 1; - LogText("%*s%.*s", indentation, "", line_length, line_start); - g.LogLineFirstItem = false; - if (*line_end == '\n') - { - LogText(IM_NEWLINE); - g.LogLineFirstItem = true; - } - } - if (is_last_line) - break; - text_remaining = line_end + 1; - } - - if (suffix) - LogRenderedText(ref_pos, suffix, suffix + strlen(suffix)); -} - -// Start logging/capturing text output -void ImGui::LogBegin(ImGuiLogType type, int auto_open_depth) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - IM_ASSERT(g.LogEnabled == false); - IM_ASSERT(g.LogFile == NULL); - IM_ASSERT(g.LogBuffer.empty()); - g.LogEnabled = true; - g.LogType = type; - g.LogNextPrefix = g.LogNextSuffix = NULL; - g.LogDepthRef = window->DC.TreeDepth; - g.LogDepthToExpand = ((auto_open_depth >= 0) ? auto_open_depth : g.LogDepthToExpandDefault); - g.LogLinePosY = FLT_MAX; - g.LogLineFirstItem = true; -} - -// Important: doesn't copy underlying data, use carefully (prefix/suffix must be in scope at the time of the next LogRenderedText) -void ImGui::LogSetNextTextDecoration(const char* prefix, const char* suffix) -{ - ImGuiContext& g = *GImGui; - g.LogNextPrefix = prefix; - g.LogNextSuffix = suffix; -} - -void ImGui::LogToTTY(int auto_open_depth) -{ - ImGuiContext& g = *GImGui; - if (g.LogEnabled) - return; - IM_UNUSED(auto_open_depth); -#ifndef IMGUI_DISABLE_TTY_FUNCTIONS - LogBegin(ImGuiLogType_TTY, auto_open_depth); - g.LogFile = stdout; -#endif -} - -// Start logging/capturing text output to given file -void ImGui::LogToFile(int auto_open_depth, const char* filename) -{ - ImGuiContext& g = *GImGui; - if (g.LogEnabled) - return; - - // FIXME: We could probably open the file in text mode "at", however note that clipboard/buffer logging will still - // be subject to outputting OS-incompatible carriage return if within strings the user doesn't use IM_NEWLINE. - // By opening the file in binary mode "ab" we have consistent output everywhere. - if (!filename) - filename = g.IO.LogFilename; - if (!filename || !filename[0]) - return; - ImFileHandle f = ImFileOpen(filename, "ab"); - if (!f) - { - IM_ASSERT(0); - return; - } - - LogBegin(ImGuiLogType_File, auto_open_depth); - g.LogFile = f; -} - -// Start logging/capturing text output to clipboard -void ImGui::LogToClipboard(int auto_open_depth) -{ - ImGuiContext& g = *GImGui; - if (g.LogEnabled) - return; - LogBegin(ImGuiLogType_Clipboard, auto_open_depth); -} - -void ImGui::LogToBuffer(int auto_open_depth) -{ - ImGuiContext& g = *GImGui; - if (g.LogEnabled) - return; - LogBegin(ImGuiLogType_Buffer, auto_open_depth); -} - -void ImGui::LogFinish() -{ - ImGuiContext& g = *GImGui; - if (!g.LogEnabled) - return; - - LogText(IM_NEWLINE); - switch (g.LogType) - { - case ImGuiLogType_TTY: -#ifndef IMGUI_DISABLE_TTY_FUNCTIONS - fflush(g.LogFile); -#endif - break; - case ImGuiLogType_File: - ImFileClose(g.LogFile); - break; - case ImGuiLogType_Buffer: - break; - case ImGuiLogType_Clipboard: - if (!g.LogBuffer.empty()) - SetClipboardText(g.LogBuffer.begin()); - break; - case ImGuiLogType_None: - IM_ASSERT(0); - break; - } - - g.LogEnabled = false; - g.LogType = ImGuiLogType_None; - g.LogFile = NULL; - g.LogBuffer.clear(); -} - -// Helper to display logging buttons -// FIXME-OBSOLETE: We should probably obsolete this and let the user have their own helper (this is one of the oldest function alive!) -void ImGui::LogButtons() -{ - ImGuiContext& g = *GImGui; - - PushID("LogButtons"); -#ifndef IMGUI_DISABLE_TTY_FUNCTIONS - const bool log_to_tty = Button("Log To TTY"); SameLine(); -#else - const bool log_to_tty = false; -#endif - const bool log_to_file = Button("Log To File"); SameLine(); - const bool log_to_clipboard = Button("Log To Clipboard"); SameLine(); - PushTabStop(false); - SetNextItemWidth(80.0f); - SliderInt("Default Depth", &g.LogDepthToExpandDefault, 0, 9, NULL); - PopTabStop(); - PopID(); - - // Start logging at the end of the function so that the buttons don't appear in the log - if (log_to_tty) - LogToTTY(); - if (log_to_file) - LogToFile(); - if (log_to_clipboard) - LogToClipboard(); -} - - -//----------------------------------------------------------------------------- -// [SECTION] SETTINGS -//----------------------------------------------------------------------------- -// - UpdateSettings() [Internal] -// - MarkIniSettingsDirty() [Internal] -// - FindSettingsHandler() [Internal] -// - ClearIniSettings() [Internal] -// - LoadIniSettingsFromDisk() -// - LoadIniSettingsFromMemory() -// - SaveIniSettingsToDisk() -// - SaveIniSettingsToMemory() -//----------------------------------------------------------------------------- -// - CreateNewWindowSettings() [Internal] -// - FindWindowSettingsByID() [Internal] -// - FindWindowSettingsByWindow() [Internal] -// - ClearWindowSettings() [Internal] -// - WindowSettingsHandler_***() [Internal] -//----------------------------------------------------------------------------- - -// Called by NewFrame() -void ImGui::UpdateSettings() -{ - // Load settings on first frame (if not explicitly loaded manually before) - ImGuiContext& g = *GImGui; - if (!g.SettingsLoaded) - { - IM_ASSERT(g.SettingsWindows.empty()); - if (g.IO.IniFilename) - LoadIniSettingsFromDisk(g.IO.IniFilename); - g.SettingsLoaded = true; - } - - // Save settings (with a delay after the last modification, so we don't spam disk too much) - if (g.SettingsDirtyTimer > 0.0f) - { - g.SettingsDirtyTimer -= g.IO.DeltaTime; - if (g.SettingsDirtyTimer <= 0.0f) - { - if (g.IO.IniFilename != NULL) - SaveIniSettingsToDisk(g.IO.IniFilename); - else - g.IO.WantSaveIniSettings = true; // Let user know they can call SaveIniSettingsToMemory(). user will need to clear io.WantSaveIniSettings themselves. - g.SettingsDirtyTimer = 0.0f; - } - } -} - -void ImGui::MarkIniSettingsDirty() -{ - ImGuiContext& g = *GImGui; - if (g.SettingsDirtyTimer <= 0.0f) - g.SettingsDirtyTimer = g.IO.IniSavingRate; -} - -void ImGui::MarkIniSettingsDirty(ImGuiWindow* window) -{ - ImGuiContext& g = *GImGui; - if (!(window->Flags & ImGuiWindowFlags_NoSavedSettings)) - if (g.SettingsDirtyTimer <= 0.0f) - g.SettingsDirtyTimer = g.IO.IniSavingRate; -} - -void ImGui::AddSettingsHandler(const ImGuiSettingsHandler* handler) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(FindSettingsHandler(handler->TypeName) == NULL); - g.SettingsHandlers.push_back(*handler); -} - -void ImGui::RemoveSettingsHandler(const char* type_name) -{ - ImGuiContext& g = *GImGui; - if (ImGuiSettingsHandler* handler = FindSettingsHandler(type_name)) - g.SettingsHandlers.erase(handler); -} - -ImGuiSettingsHandler* ImGui::FindSettingsHandler(const char* type_name) -{ - ImGuiContext& g = *GImGui; - const ImGuiID type_hash = ImHashStr(type_name); - for (ImGuiSettingsHandler& handler : g.SettingsHandlers) - if (handler.TypeHash == type_hash) - return &handler; - return NULL; -} - -// Clear all settings (windows, tables, docking etc.) -void ImGui::ClearIniSettings() -{ - ImGuiContext& g = *GImGui; - g.SettingsIniData.clear(); - for (ImGuiSettingsHandler& handler : g.SettingsHandlers) - if (handler.ClearAllFn != NULL) - handler.ClearAllFn(&g, &handler); -} - -void ImGui::LoadIniSettingsFromDisk(const char* ini_filename) -{ - size_t file_data_size = 0; - char* file_data = (char*)ImFileLoadToMemory(ini_filename, "rb", &file_data_size); - if (!file_data) - return; - if (file_data_size > 0) - LoadIniSettingsFromMemory(file_data, (size_t)file_data_size); - IM_FREE(file_data); -} - -// Zero-tolerance, no error reporting, cheap .ini parsing -// Set ini_size==0 to let us use strlen(ini_data). Do not call this function with a 0 if your buffer is actually empty! -void ImGui::LoadIniSettingsFromMemory(const char* ini_data, size_t ini_size) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(g.Initialized); - //IM_ASSERT(!g.WithinFrameScope && "Cannot be called between NewFrame() and EndFrame()"); - //IM_ASSERT(g.SettingsLoaded == false && g.FrameCount == 0); - - // For user convenience, we allow passing a non zero-terminated string (hence the ini_size parameter). - // For our convenience and to make the code simpler, we'll also write zero-terminators within the buffer. So let's create a writable copy.. - if (ini_size == 0) - ini_size = strlen(ini_data); - g.SettingsIniData.Buf.resize((int)ini_size + 1); - char* const buf = g.SettingsIniData.Buf.Data; - char* const buf_end = buf + ini_size; - memcpy(buf, ini_data, ini_size); - buf_end[0] = 0; - - // Call pre-read handlers - // Some types will clear their data (e.g. dock information) some types will allow merge/override (window) - for (ImGuiSettingsHandler& handler : g.SettingsHandlers) - if (handler.ReadInitFn != NULL) - handler.ReadInitFn(&g, &handler); - - void* entry_data = NULL; - ImGuiSettingsHandler* entry_handler = NULL; - - char* line_end = NULL; - for (char* line = buf; line < buf_end; line = line_end + 1) - { - // Skip new lines markers, then find end of the line - while (*line == '\n' || *line == '\r') - line++; - line_end = line; - while (line_end < buf_end && *line_end != '\n' && *line_end != '\r') - line_end++; - line_end[0] = 0; - if (line[0] == ';') - continue; - if (line[0] == '[' && line_end > line && line_end[-1] == ']') - { - // Parse "[Type][Name]". Note that 'Name' can itself contains [] characters, which is acceptable with the current format and parsing code. - line_end[-1] = 0; - const char* name_end = line_end - 1; - const char* type_start = line + 1; - char* type_end = (char*)(void*)ImStrchrRange(type_start, name_end, ']'); - const char* name_start = type_end ? ImStrchrRange(type_end + 1, name_end, '[') : NULL; - if (!type_end || !name_start) - continue; - *type_end = 0; // Overwrite first ']' - name_start++; // Skip second '[' - entry_handler = FindSettingsHandler(type_start); - entry_data = entry_handler ? entry_handler->ReadOpenFn(&g, entry_handler, name_start) : NULL; - } - else if (entry_handler != NULL && entry_data != NULL) - { - // Let type handler parse the line - entry_handler->ReadLineFn(&g, entry_handler, entry_data, line); - } - } - g.SettingsLoaded = true; - - // [DEBUG] Restore untouched copy so it can be browsed in Metrics (not strictly necessary) - memcpy(buf, ini_data, ini_size); - - // Call post-read handlers - for (ImGuiSettingsHandler& handler : g.SettingsHandlers) - if (handler.ApplyAllFn != NULL) - handler.ApplyAllFn(&g, &handler); -} - -void ImGui::SaveIniSettingsToDisk(const char* ini_filename) -{ - ImGuiContext& g = *GImGui; - g.SettingsDirtyTimer = 0.0f; - if (!ini_filename) - return; - - size_t ini_data_size = 0; - const char* ini_data = SaveIniSettingsToMemory(&ini_data_size); - ImFileHandle f = ImFileOpen(ini_filename, "wt"); - if (!f) - return; - ImFileWrite(ini_data, sizeof(char), ini_data_size, f); - ImFileClose(f); -} - -// Call registered handlers (e.g. SettingsHandlerWindow_WriteAll() + custom handlers) to write their stuff into a text buffer -const char* ImGui::SaveIniSettingsToMemory(size_t* out_size) -{ - ImGuiContext& g = *GImGui; - g.SettingsDirtyTimer = 0.0f; - g.SettingsIniData.Buf.resize(0); - g.SettingsIniData.Buf.push_back(0); - for (ImGuiSettingsHandler& handler : g.SettingsHandlers) - handler.WriteAllFn(&g, &handler, &g.SettingsIniData); - if (out_size) - *out_size = (size_t)g.SettingsIniData.size(); - return g.SettingsIniData.c_str(); -} - -ImGuiWindowSettings* ImGui::CreateNewWindowSettings(const char* name) -{ - ImGuiContext& g = *GImGui; - - if (g.IO.ConfigDebugIniSettings == false) - { - // Skip to the "###" marker if any. We don't skip past to match the behavior of GetID() - // Preserve the full string when ConfigDebugVerboseIniSettings is set to make .ini inspection easier. - if (const char* p = strstr(name, "###")) - name = p; - } - const size_t name_len = strlen(name); - - // Allocate chunk - const size_t chunk_size = sizeof(ImGuiWindowSettings) + name_len + 1; - ImGuiWindowSettings* settings = g.SettingsWindows.alloc_chunk(chunk_size); - IM_PLACEMENT_NEW(settings) ImGuiWindowSettings(); - settings->ID = ImHashStr(name, name_len); - memcpy(settings->GetName(), name, name_len + 1); // Store with zero terminator - - return settings; -} - -// We don't provide a FindWindowSettingsByName() because Docking system doesn't always hold on names. -// This is called once per window .ini entry + once per newly instantiated window. -ImGuiWindowSettings* ImGui::FindWindowSettingsByID(ImGuiID id) -{ - ImGuiContext& g = *GImGui; - for (ImGuiWindowSettings* settings = g.SettingsWindows.begin(); settings != NULL; settings = g.SettingsWindows.next_chunk(settings)) - if (settings->ID == id && !settings->WantDelete) - return settings; - return NULL; -} - -// This is faster if you are holding on a Window already as we don't need to perform a search. -ImGuiWindowSettings* ImGui::FindWindowSettingsByWindow(ImGuiWindow* window) -{ - ImGuiContext& g = *GImGui; - if (window->SettingsOffset != -1) - return g.SettingsWindows.ptr_from_offset(window->SettingsOffset); - return FindWindowSettingsByID(window->ID); -} - -// This will revert window to its initial state, including enabling the ImGuiCond_FirstUseEver/ImGuiCond_Once conditions once more. -void ImGui::ClearWindowSettings(const char* name) -{ - //IMGUI_DEBUG_LOG("ClearWindowSettings('%s')\n", name); - ImGuiContext& g = *GImGui; - ImGuiWindow* window = FindWindowByName(name); - if (window != NULL) - { - window->Flags |= ImGuiWindowFlags_NoSavedSettings; - InitOrLoadWindowSettings(window, NULL); - if (window->DockId != 0) - DockContextProcessUndockWindow(&g, window, true); - } - if (ImGuiWindowSettings* settings = window ? FindWindowSettingsByWindow(window) : FindWindowSettingsByID(ImHashStr(name))) - settings->WantDelete = true; -} - -static void WindowSettingsHandler_ClearAll(ImGuiContext* ctx, ImGuiSettingsHandler*) -{ - ImGuiContext& g = *ctx; - for (ImGuiWindow* window : g.Windows) - window->SettingsOffset = -1; - g.SettingsWindows.clear(); -} - -static void* WindowSettingsHandler_ReadOpen(ImGuiContext*, ImGuiSettingsHandler*, const char* name) -{ - ImGuiID id = ImHashStr(name); - ImGuiWindowSettings* settings = ImGui::FindWindowSettingsByID(id); - if (settings) - *settings = ImGuiWindowSettings(); // Clear existing if recycling previous entry - else - settings = ImGui::CreateNewWindowSettings(name); - settings->ID = id; - settings->WantApply = true; - return (void*)settings; -} - -static void WindowSettingsHandler_ReadLine(ImGuiContext*, ImGuiSettingsHandler*, void* entry, const char* line) -{ - ImGuiWindowSettings* settings = (ImGuiWindowSettings*)entry; - int x, y; - int i; - ImU32 u1; - if (sscanf(line, "Pos=%i,%i", &x, &y) == 2) { settings->Pos = ImVec2ih((short)x, (short)y); } - else if (sscanf(line, "Size=%i,%i", &x, &y) == 2) { settings->Size = ImVec2ih((short)x, (short)y); } - else if (sscanf(line, "ViewportId=0x%08X", &u1) == 1) { settings->ViewportId = u1; } - else if (sscanf(line, "ViewportPos=%i,%i", &x, &y) == 2){ settings->ViewportPos = ImVec2ih((short)x, (short)y); } - else if (sscanf(line, "Collapsed=%d", &i) == 1) { settings->Collapsed = (i != 0); } - else if (sscanf(line, "DockId=0x%X,%d", &u1, &i) == 2) { settings->DockId = u1; settings->DockOrder = (short)i; } - else if (sscanf(line, "DockId=0x%X", &u1) == 1) { settings->DockId = u1; settings->DockOrder = -1; } - else if (sscanf(line, "ClassId=0x%X", &u1) == 1) { settings->ClassId = u1; } -} - -// Apply to existing windows (if any) -static void WindowSettingsHandler_ApplyAll(ImGuiContext* ctx, ImGuiSettingsHandler*) -{ - ImGuiContext& g = *ctx; - for (ImGuiWindowSettings* settings = g.SettingsWindows.begin(); settings != NULL; settings = g.SettingsWindows.next_chunk(settings)) - if (settings->WantApply) - { - if (ImGuiWindow* window = ImGui::FindWindowByID(settings->ID)) - ApplyWindowSettings(window, settings); - settings->WantApply = false; - } -} - -static void WindowSettingsHandler_WriteAll(ImGuiContext* ctx, ImGuiSettingsHandler* handler, ImGuiTextBuffer* buf) -{ - // Gather data from windows that were active during this session - // (if a window wasn't opened in this session we preserve its settings) - ImGuiContext& g = *ctx; - for (ImGuiWindow* window : g.Windows) - { - if (window->Flags & ImGuiWindowFlags_NoSavedSettings) - continue; - - ImGuiWindowSettings* settings = ImGui::FindWindowSettingsByWindow(window); - if (!settings) - { - settings = ImGui::CreateNewWindowSettings(window->Name); - window->SettingsOffset = g.SettingsWindows.offset_from_ptr(settings); - } - IM_ASSERT(settings->ID == window->ID); - settings->Pos = ImVec2ih(window->Pos - window->ViewportPos); - settings->Size = ImVec2ih(window->SizeFull); - settings->ViewportId = window->ViewportId; - settings->ViewportPos = ImVec2ih(window->ViewportPos); - IM_ASSERT(window->DockNode == NULL || window->DockNode->ID == window->DockId); - settings->DockId = window->DockId; - settings->ClassId = window->WindowClass.ClassId; - settings->DockOrder = window->DockOrder; - settings->Collapsed = window->Collapsed; - settings->WantDelete = false; - } - - // Write to text buffer - buf->reserve(buf->size() + g.SettingsWindows.size() * 6); // ballpark reserve - for (ImGuiWindowSettings* settings = g.SettingsWindows.begin(); settings != NULL; settings = g.SettingsWindows.next_chunk(settings)) - { - if (settings->WantDelete) - continue; - const char* settings_name = settings->GetName(); - buf->appendf("[%s][%s]\n", handler->TypeName, settings_name); - if (settings->ViewportId != 0 && settings->ViewportId != ImGui::IMGUI_VIEWPORT_DEFAULT_ID) - { - buf->appendf("ViewportPos=%d,%d\n", settings->ViewportPos.x, settings->ViewportPos.y); - buf->appendf("ViewportId=0x%08X\n", settings->ViewportId); - } - if (settings->Pos.x != 0 || settings->Pos.y != 0 || settings->ViewportId == ImGui::IMGUI_VIEWPORT_DEFAULT_ID) - buf->appendf("Pos=%d,%d\n", settings->Pos.x, settings->Pos.y); - if (settings->Size.x != 0 || settings->Size.y != 0) - buf->appendf("Size=%d,%d\n", settings->Size.x, settings->Size.y); - buf->appendf("Collapsed=%d\n", settings->Collapsed); - if (settings->DockId != 0) - { - //buf->appendf("TabId=0x%08X\n", ImHashStr("#TAB", 4, settings->ID)); // window->TabId: this is not read back but writing it makes "debugging" the .ini data easier. - if (settings->DockOrder == -1) - buf->appendf("DockId=0x%08X\n", settings->DockId); - else - buf->appendf("DockId=0x%08X,%d\n", settings->DockId, settings->DockOrder); - if (settings->ClassId != 0) - buf->appendf("ClassId=0x%08X\n", settings->ClassId); - } - buf->append("\n"); - } -} - - -//----------------------------------------------------------------------------- -// [SECTION] LOCALIZATION -//----------------------------------------------------------------------------- - -void ImGui::LocalizeRegisterEntries(const ImGuiLocEntry* entries, int count) -{ - ImGuiContext& g = *GImGui; - for (int n = 0; n < count; n++) - g.LocalizationTable[entries[n].Key] = entries[n].Text; -} - - -//----------------------------------------------------------------------------- -// [SECTION] VIEWPORTS, PLATFORM WINDOWS -//----------------------------------------------------------------------------- -// - GetMainViewport() -// - FindViewportByID() -// - FindViewportByPlatformHandle() -// - SetCurrentViewport() [Internal] -// - SetWindowViewport() [Internal] -// - GetWindowAlwaysWantOwnViewport() [Internal] -// - UpdateTryMergeWindowIntoHostViewport() [Internal] -// - UpdateTryMergeWindowIntoHostViewports() [Internal] -// - TranslateWindowsInViewport() [Internal] -// - ScaleWindowsInViewport() [Internal] -// - FindHoveredViewportFromPlatformWindowStack() [Internal] -// - UpdateViewportsNewFrame() [Internal] -// - UpdateViewportsEndFrame() [Internal] -// - AddUpdateViewport() [Internal] -// - WindowSelectViewport() [Internal] -// - WindowSyncOwnedViewport() [Internal] -// - UpdatePlatformWindows() -// - RenderPlatformWindowsDefault() -// - FindPlatformMonitorForPos() [Internal] -// - FindPlatformMonitorForRect() [Internal] -// - UpdateViewportPlatformMonitor() [Internal] -// - DestroyPlatformWindow() [Internal] -// - DestroyPlatformWindows() -//----------------------------------------------------------------------------- - -ImGuiViewport* ImGui::GetMainViewport() -{ - ImGuiContext& g = *GImGui; - return g.Viewports[0]; -} - -// FIXME: This leaks access to viewports not listed in PlatformIO.Viewports[]. Problematic? (#4236) -ImGuiViewport* ImGui::FindViewportByID(ImGuiID id) -{ - ImGuiContext& g = *GImGui; - for (ImGuiViewportP* viewport : g.Viewports) - if (viewport->ID == id) - return viewport; - return NULL; -} - -ImGuiViewport* ImGui::FindViewportByPlatformHandle(void* platform_handle) -{ - ImGuiContext& g = *GImGui; - for (ImGuiViewportP* viewport : g.Viewports) - if (viewport->PlatformHandle == platform_handle) - return viewport; - return NULL; -} - -void ImGui::SetCurrentViewport(ImGuiWindow* current_window, ImGuiViewportP* viewport) -{ - ImGuiContext& g = *GImGui; - (void)current_window; - - if (viewport) - viewport->LastFrameActive = g.FrameCount; - if (g.CurrentViewport == viewport) - return; - g.CurrentDpiScale = viewport ? viewport->DpiScale : 1.0f; - g.CurrentViewport = viewport; - //IMGUI_DEBUG_LOG_VIEWPORT("[viewport] SetCurrentViewport changed '%s' 0x%08X\n", current_window ? current_window->Name : NULL, viewport ? viewport->ID : 0); - - // Notify platform layer of viewport changes - // FIXME-DPI: This is only currently used for experimenting with handling of multiple DPI - if (g.CurrentViewport && g.PlatformIO.Platform_OnChangedViewport) - g.PlatformIO.Platform_OnChangedViewport(g.CurrentViewport); -} - -void ImGui::SetWindowViewport(ImGuiWindow* window, ImGuiViewportP* viewport) -{ - // Abandon viewport - if (window->ViewportOwned && window->Viewport->Window == window) - window->Viewport->Size = ImVec2(0.0f, 0.0f); - - window->Viewport = viewport; - window->ViewportId = viewport->ID; - window->ViewportOwned = (viewport->Window == window); -} - -static bool ImGui::GetWindowAlwaysWantOwnViewport(ImGuiWindow* window) -{ - // Tooltips and menus are not automatically forced into their own viewport when the NoMerge flag is set, however the multiplication of viewports makes them more likely to protrude and create their own. - ImGuiContext& g = *GImGui; - if (g.IO.ConfigViewportsNoAutoMerge || (window->WindowClass.ViewportFlagsOverrideSet & ImGuiViewportFlags_NoAutoMerge)) - if (g.ConfigFlagsCurrFrame & ImGuiConfigFlags_ViewportsEnable) - if (!window->DockIsActive) - if ((window->Flags & (ImGuiWindowFlags_ChildWindow | ImGuiWindowFlags_ChildMenu | ImGuiWindowFlags_Tooltip)) == 0) - if ((window->Flags & ImGuiWindowFlags_Popup) == 0 || (window->Flags & ImGuiWindowFlags_Modal) != 0) - return true; - return false; -} - -static bool ImGui::UpdateTryMergeWindowIntoHostViewport(ImGuiWindow* window, ImGuiViewportP* viewport) -{ - ImGuiContext& g = *GImGui; - if (window->Viewport == viewport) - return false; - if ((viewport->Flags & ImGuiViewportFlags_CanHostOtherWindows) == 0) - return false; - if ((viewport->Flags & ImGuiViewportFlags_IsMinimized) != 0) - return false; - if (!viewport->GetMainRect().Contains(window->Rect())) - return false; - if (GetWindowAlwaysWantOwnViewport(window)) - return false; - - // FIXME: Can't use g.WindowsFocusOrder[] for root windows only as we care about Z order. If we maintained a DisplayOrder along with FocusOrder we could.. - for (ImGuiWindow* window_behind : g.Windows) - { - if (window_behind == window) - break; - if (window_behind->WasActive && window_behind->ViewportOwned && !(window_behind->Flags & ImGuiWindowFlags_ChildWindow)) - if (window_behind->Viewport->GetMainRect().Overlaps(window->Rect())) - return false; - } - - // Move to the existing viewport, Move child/hosted windows as well (FIXME-OPT: iterate child) - ImGuiViewportP* old_viewport = window->Viewport; - if (window->ViewportOwned) - for (int n = 0; n < g.Windows.Size; n++) - if (g.Windows[n]->Viewport == old_viewport) - SetWindowViewport(g.Windows[n], viewport); - SetWindowViewport(window, viewport); - BringWindowToDisplayFront(window); - - return true; -} - -// FIXME: handle 0 to N host viewports -static bool ImGui::UpdateTryMergeWindowIntoHostViewports(ImGuiWindow* window) -{ - ImGuiContext& g = *GImGui; - return UpdateTryMergeWindowIntoHostViewport(window, g.Viewports[0]); -} - -// Translate Dear ImGui windows when a Host Viewport has been moved -// (This additionally keeps windows at the same place when ImGuiConfigFlags_ViewportsEnable is toggled!) -void ImGui::TranslateWindowsInViewport(ImGuiViewportP* viewport, const ImVec2& old_pos, const ImVec2& new_pos) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(viewport->Window == NULL && (viewport->Flags & ImGuiViewportFlags_CanHostOtherWindows)); - - // 1) We test if ImGuiConfigFlags_ViewportsEnable was just toggled, which allows us to conveniently - // translate imgui windows from OS-window-local to absolute coordinates or vice-versa. - // 2) If it's not going to fit into the new size, keep it at same absolute position. - // One problem with this is that most Win32 applications doesn't update their render while dragging, - // and so the window will appear to teleport when releasing the mouse. - const bool translate_all_windows = (g.ConfigFlagsCurrFrame & ImGuiConfigFlags_ViewportsEnable) != (g.ConfigFlagsLastFrame & ImGuiConfigFlags_ViewportsEnable); - ImRect test_still_fit_rect(old_pos, old_pos + viewport->Size); - ImVec2 delta_pos = new_pos - old_pos; - for (ImGuiWindow* window : g.Windows) // FIXME-OPT - if (translate_all_windows || (window->Viewport == viewport && test_still_fit_rect.Contains(window->Rect()))) - TranslateWindow(window, delta_pos); -} - -// Scale all windows (position, size). Use when e.g. changing DPI. (This is a lossy operation!) -void ImGui::ScaleWindowsInViewport(ImGuiViewportP* viewport, float scale) -{ - ImGuiContext& g = *GImGui; - if (viewport->Window) - { - ScaleWindow(viewport->Window, scale); - } - else - { - for (ImGuiWindow* window : g.Windows) - if (window->Viewport == viewport) - ScaleWindow(window, scale); - } -} - -// If the backend doesn't set MouseLastHoveredViewport or doesn't honor ImGuiViewportFlags_NoInputs, we do a search ourselves. -// A) It won't take account of the possibility that non-imgui windows may be in-between our dragged window and our target window. -// B) It requires Platform_GetWindowFocus to be implemented by backend. -ImGuiViewportP* ImGui::FindHoveredViewportFromPlatformWindowStack(const ImVec2& mouse_platform_pos) -{ - ImGuiContext& g = *GImGui; - ImGuiViewportP* best_candidate = NULL; - for (ImGuiViewportP* viewport : g.Viewports) - if (!(viewport->Flags & (ImGuiViewportFlags_NoInputs | ImGuiViewportFlags_IsMinimized)) && viewport->GetMainRect().Contains(mouse_platform_pos)) - if (best_candidate == NULL || best_candidate->LastFocusedStampCount < viewport->LastFocusedStampCount) - best_candidate = viewport; - return best_candidate; -} - -// Update viewports and monitor infos -// Note that this is running even if 'ImGuiConfigFlags_ViewportsEnable' is not set, in order to clear unused viewports (if any) and update monitor info. -static void ImGui::UpdateViewportsNewFrame() -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(g.PlatformIO.Viewports.Size <= g.Viewports.Size); - - // Update Minimized status (we need it first in order to decide if we'll apply Pos/Size of the main viewport) - // Update Focused status - const bool viewports_enabled = (g.ConfigFlagsCurrFrame & ImGuiConfigFlags_ViewportsEnable) != 0; - if (viewports_enabled) - { - ImGuiViewportP* focused_viewport = NULL; - for (ImGuiViewportP* viewport : g.Viewports) - { - const bool platform_funcs_available = viewport->PlatformWindowCreated; - if (g.PlatformIO.Platform_GetWindowMinimized && platform_funcs_available) - { - bool is_minimized = g.PlatformIO.Platform_GetWindowMinimized(viewport); - if (is_minimized) - viewport->Flags |= ImGuiViewportFlags_IsMinimized; - else - viewport->Flags &= ~ImGuiViewportFlags_IsMinimized; - } - - // Update our implicit z-order knowledge of platform windows, which is used when the backend cannot provide io.MouseHoveredViewport. - // When setting Platform_GetWindowFocus, it is expected that the platform backend can handle calls without crashing if it doesn't have data stored. - if (g.PlatformIO.Platform_GetWindowFocus && platform_funcs_available) - { - bool is_focused = g.PlatformIO.Platform_GetWindowFocus(viewport); - if (is_focused) - viewport->Flags |= ImGuiViewportFlags_IsFocused; - else - viewport->Flags &= ~ImGuiViewportFlags_IsFocused; - if (is_focused) - focused_viewport = viewport; - } - } - - // Focused viewport has changed? - if (focused_viewport && g.PlatformLastFocusedViewportId != focused_viewport->ID) - { - IMGUI_DEBUG_LOG_VIEWPORT("[viewport] Focused viewport changed %08X -> %08X, attempting to apply our focus.\n", g.PlatformLastFocusedViewportId, focused_viewport->ID); - const ImGuiViewport* prev_focused_viewport = FindViewportByID(g.PlatformLastFocusedViewportId); - const bool prev_focused_has_been_destroyed = (prev_focused_viewport == NULL) || (prev_focused_viewport->PlatformWindowCreated == false); - - // Store a tag so we can infer z-order easily from all our windows - // We compare PlatformLastFocusedViewportId so newly created viewports with _NoFocusOnAppearing flag - // will keep the front most stamp instead of losing it back to their parent viewport. - if (focused_viewport->LastFocusedStampCount != g.ViewportFocusedStampCount) - focused_viewport->LastFocusedStampCount = ++g.ViewportFocusedStampCount; - g.PlatformLastFocusedViewportId = focused_viewport->ID; - - // Focus associated dear imgui window - // - if focus didn't happen with a click within imgui boundaries, e.g. Clicking platform title bar. (#6299) - // - if focus didn't happen because we destroyed another window (#6462) - // FIXME: perhaps 'FocusTopMostWindowUnderOne()' can handle the 'focused_window->Window != NULL' case as well. - const bool apply_imgui_focus_on_focused_viewport = !IsAnyMouseDown() && !prev_focused_has_been_destroyed; - if (apply_imgui_focus_on_focused_viewport) - { - focused_viewport->LastFocusedHadNavWindow |= (g.NavWindow != NULL) && (g.NavWindow->Viewport == focused_viewport); // Update so a window changing viewport won't lose focus. - ImGuiFocusRequestFlags focus_request_flags = ImGuiFocusRequestFlags_UnlessBelowModal | ImGuiFocusRequestFlags_RestoreFocusedChild; - if (focused_viewport->Window != NULL) - FocusWindow(focused_viewport->Window, focus_request_flags); - else if (focused_viewport->LastFocusedHadNavWindow) - FocusTopMostWindowUnderOne(NULL, NULL, focused_viewport, focus_request_flags); // Focus top most in viewport - else - FocusWindow(NULL, focus_request_flags); // No window had focus last time viewport was focused - } - } - if (focused_viewport) - focused_viewport->LastFocusedHadNavWindow = (g.NavWindow != NULL) && (g.NavWindow->Viewport == focused_viewport); - } - - // Create/update main viewport with current platform position. - // FIXME-VIEWPORT: Size is driven by backend/user code for backward-compatibility but we should aim to make this more consistent. - ImGuiViewportP* main_viewport = g.Viewports[0]; - IM_ASSERT(main_viewport->ID == IMGUI_VIEWPORT_DEFAULT_ID); - IM_ASSERT(main_viewport->Window == NULL); - ImVec2 main_viewport_pos = viewports_enabled ? g.PlatformIO.Platform_GetWindowPos(main_viewport) : ImVec2(0.0f, 0.0f); - ImVec2 main_viewport_size = g.IO.DisplaySize; - if (viewports_enabled && (main_viewport->Flags & ImGuiViewportFlags_IsMinimized)) - { - main_viewport_pos = main_viewport->Pos; // Preserve last pos/size when minimized (FIXME: We don't do the same for Size outside of the viewport path) - main_viewport_size = main_viewport->Size; - } - AddUpdateViewport(NULL, IMGUI_VIEWPORT_DEFAULT_ID, main_viewport_pos, main_viewport_size, ImGuiViewportFlags_OwnedByApp | ImGuiViewportFlags_CanHostOtherWindows); - - g.CurrentDpiScale = 0.0f; - g.CurrentViewport = NULL; - g.MouseViewport = NULL; - for (int n = 0; n < g.Viewports.Size; n++) - { - ImGuiViewportP* viewport = g.Viewports[n]; - viewport->Idx = n; - - // Erase unused viewports - if (n > 0 && viewport->LastFrameActive < g.FrameCount - 2) - { - DestroyViewport(viewport); - n--; - continue; - } - - const bool platform_funcs_available = viewport->PlatformWindowCreated; - if (viewports_enabled) - { - // Update Position and Size (from Platform Window to ImGui) if requested. - // We do it early in the frame instead of waiting for UpdatePlatformWindows() to avoid a frame of lag when moving/resizing using OS facilities. - if (!(viewport->Flags & ImGuiViewportFlags_IsMinimized) && platform_funcs_available) - { - // Viewport->WorkPos and WorkSize will be updated below - if (viewport->PlatformRequestMove) - viewport->Pos = viewport->LastPlatformPos = g.PlatformIO.Platform_GetWindowPos(viewport); - if (viewport->PlatformRequestResize) - viewport->Size = viewport->LastPlatformSize = g.PlatformIO.Platform_GetWindowSize(viewport); - } - } - - // Update/copy monitor info - UpdateViewportPlatformMonitor(viewport); - - // Lock down space taken by menu bars and status bars, reset the offset for functions like BeginMainMenuBar() to alter them again. - viewport->WorkOffsetMin = viewport->BuildWorkOffsetMin; - viewport->WorkOffsetMax = viewport->BuildWorkOffsetMax; - viewport->BuildWorkOffsetMin = viewport->BuildWorkOffsetMax = ImVec2(0.0f, 0.0f); - viewport->UpdateWorkRect(); - - // Reset alpha every frame. Users of transparency (docking) needs to request a lower alpha back. - viewport->Alpha = 1.0f; - - // Translate Dear ImGui windows when a Host Viewport has been moved - // (This additionally keeps windows at the same place when ImGuiConfigFlags_ViewportsEnable is toggled!) - const ImVec2 viewport_delta_pos = viewport->Pos - viewport->LastPos; - if ((viewport->Flags & ImGuiViewportFlags_CanHostOtherWindows) && (viewport_delta_pos.x != 0.0f || viewport_delta_pos.y != 0.0f)) - TranslateWindowsInViewport(viewport, viewport->LastPos, viewport->Pos); - - // Update DPI scale - float new_dpi_scale; - if (g.PlatformIO.Platform_GetWindowDpiScale && platform_funcs_available) - new_dpi_scale = g.PlatformIO.Platform_GetWindowDpiScale(viewport); - else if (viewport->PlatformMonitor != -1) - new_dpi_scale = g.PlatformIO.Monitors[viewport->PlatformMonitor].DpiScale; - else - new_dpi_scale = (viewport->DpiScale != 0.0f) ? viewport->DpiScale : 1.0f; - if (viewport->DpiScale != 0.0f && new_dpi_scale != viewport->DpiScale) - { - float scale_factor = new_dpi_scale / viewport->DpiScale; - if (g.IO.ConfigFlags & ImGuiConfigFlags_DpiEnableScaleViewports) - ScaleWindowsInViewport(viewport, scale_factor); - //if (viewport == GetMainViewport()) - // g.PlatformInterface.SetWindowSize(viewport, viewport->Size * scale_factor); - - // Scale our window moving pivot so that the window will rescale roughly around the mouse position. - // FIXME-VIEWPORT: This currently creates a resizing feedback loop when a window is straddling a DPI transition border. - // (Minor: since our sizes do not perfectly linearly scale, deferring the click offset scale until we know the actual window scale ratio may get us slightly more precise mouse positioning.) - //if (g.MovingWindow != NULL && g.MovingWindow->Viewport == viewport) - // g.ActiveIdClickOffset = ImTrunc(g.ActiveIdClickOffset * scale_factor); - } - viewport->DpiScale = new_dpi_scale; - } - - // Update fallback monitor - if (g.PlatformIO.Monitors.Size == 0) - { - ImGuiPlatformMonitor* monitor = &g.FallbackMonitor; - monitor->MainPos = main_viewport->Pos; - monitor->MainSize = main_viewport->Size; - monitor->WorkPos = main_viewport->WorkPos; - monitor->WorkSize = main_viewport->WorkSize; - monitor->DpiScale = main_viewport->DpiScale; - } - - if (!viewports_enabled) - { - g.MouseViewport = main_viewport; - return; - } - - // Mouse handling: decide on the actual mouse viewport for this frame between the active/focused viewport and the hovered viewport. - // Note that 'viewport_hovered' should skip over any viewport that has the ImGuiViewportFlags_NoInputs flags set. - ImGuiViewportP* viewport_hovered = NULL; - if (g.IO.BackendFlags & ImGuiBackendFlags_HasMouseHoveredViewport) - { - viewport_hovered = g.IO.MouseHoveredViewport ? (ImGuiViewportP*)FindViewportByID(g.IO.MouseHoveredViewport) : NULL; - if (viewport_hovered && (viewport_hovered->Flags & ImGuiViewportFlags_NoInputs)) - viewport_hovered = FindHoveredViewportFromPlatformWindowStack(g.IO.MousePos); // Backend failed to handle _NoInputs viewport: revert to our fallback. - } - else - { - // If the backend doesn't know how to honor ImGuiViewportFlags_NoInputs, we do a search ourselves. Note that this search: - // A) won't take account of the possibility that non-imgui windows may be in-between our dragged window and our target window. - // B) won't take account of how the backend apply parent<>child relationship to secondary viewports, which affects their Z order. - // C) uses LastFrameAsRefViewport as a flawed replacement for the last time a window was focused (we could/should fix that by introducing Focus functions in PlatformIO) - viewport_hovered = FindHoveredViewportFromPlatformWindowStack(g.IO.MousePos); - } - if (viewport_hovered != NULL) - g.MouseLastHoveredViewport = viewport_hovered; - else if (g.MouseLastHoveredViewport == NULL) - g.MouseLastHoveredViewport = g.Viewports[0]; - - // Update mouse reference viewport - // (when moving a window we aim at its viewport, but this will be overwritten below if we go in drag and drop mode) - // (MovingViewport->Viewport will be NULL in the rare situation where the window disappared while moving, set UpdateMouseMovingWindowNewFrame() for details) - if (g.MovingWindow && g.MovingWindow->Viewport) - g.MouseViewport = g.MovingWindow->Viewport; - else - g.MouseViewport = g.MouseLastHoveredViewport; - - // When dragging something, always refer to the last hovered viewport. - // - when releasing a moving window we will revert to aiming behind (at viewport_hovered) - // - when we are between viewports, our dragged preview will tend to show in the last viewport _even_ if we don't have tooltips in their viewports (when lacking monitor info) - // - consider the case of holding on a menu item to browse child menus: even thou a mouse button is held, there's no active id because menu items only react on mouse release. - // FIXME-VIEWPORT: This is essentially broken, when ImGuiBackendFlags_HasMouseHoveredViewport is set we want to trust when viewport_hovered==NULL and use that. - const bool is_mouse_dragging_with_an_expected_destination = g.DragDropActive; - if (is_mouse_dragging_with_an_expected_destination && viewport_hovered == NULL) - viewport_hovered = g.MouseLastHoveredViewport; - if (is_mouse_dragging_with_an_expected_destination || g.ActiveId == 0 || !IsAnyMouseDown()) - if (viewport_hovered != NULL && viewport_hovered != g.MouseViewport && !(viewport_hovered->Flags & ImGuiViewportFlags_NoInputs)) - g.MouseViewport = viewport_hovered; - - IM_ASSERT(g.MouseViewport != NULL); -} - -// Update user-facing viewport list (g.Viewports -> g.PlatformIO.Viewports after filtering out some) -static void ImGui::UpdateViewportsEndFrame() -{ - ImGuiContext& g = *GImGui; - g.PlatformIO.Viewports.resize(0); - for (int i = 0; i < g.Viewports.Size; i++) - { - ImGuiViewportP* viewport = g.Viewports[i]; - viewport->LastPos = viewport->Pos; - if (viewport->LastFrameActive < g.FrameCount || viewport->Size.x <= 0.0f || viewport->Size.y <= 0.0f) - if (i > 0) // Always include main viewport in the list - continue; - if (viewport->Window && !IsWindowActiveAndVisible(viewport->Window)) - continue; - if (i > 0) - IM_ASSERT(viewport->Window != NULL); - g.PlatformIO.Viewports.push_back(viewport); - } - g.Viewports[0]->ClearRequestFlags(); // Clear main viewport flags because UpdatePlatformWindows() won't do it and may not even be called -} - -// FIXME: We should ideally refactor the system to call this every frame (we currently don't) -ImGuiViewportP* ImGui::AddUpdateViewport(ImGuiWindow* window, ImGuiID id, const ImVec2& pos, const ImVec2& size, ImGuiViewportFlags flags) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(id != 0); - - flags |= ImGuiViewportFlags_IsPlatformWindow; - if (window != NULL) - { - if (g.MovingWindow && g.MovingWindow->RootWindowDockTree == window) - flags |= ImGuiViewportFlags_NoInputs | ImGuiViewportFlags_NoFocusOnAppearing; - if ((window->Flags & ImGuiWindowFlags_NoMouseInputs) && (window->Flags & ImGuiWindowFlags_NoNavInputs)) - flags |= ImGuiViewportFlags_NoInputs; - if (window->Flags & ImGuiWindowFlags_NoFocusOnAppearing) - flags |= ImGuiViewportFlags_NoFocusOnAppearing; - } - - ImGuiViewportP* viewport = (ImGuiViewportP*)FindViewportByID(id); - if (viewport) - { - // Always update for main viewport as we are already pulling correct platform pos/size (see #4900) - if (!viewport->PlatformRequestMove || viewport->ID == IMGUI_VIEWPORT_DEFAULT_ID) - viewport->Pos = pos; - if (!viewport->PlatformRequestResize || viewport->ID == IMGUI_VIEWPORT_DEFAULT_ID) - viewport->Size = size; - viewport->Flags = flags | (viewport->Flags & (ImGuiViewportFlags_IsMinimized | ImGuiViewportFlags_IsFocused)); // Preserve existing flags - } - else - { - // New viewport - viewport = IM_NEW(ImGuiViewportP)(); - viewport->ID = id; - viewport->Idx = g.Viewports.Size; - viewport->Pos = viewport->LastPos = pos; - viewport->Size = size; - viewport->Flags = flags; - UpdateViewportPlatformMonitor(viewport); - g.Viewports.push_back(viewport); - g.ViewportCreatedCount++; - IMGUI_DEBUG_LOG_VIEWPORT("[viewport] Add Viewport %08X '%s'\n", id, window ? window->Name : ""); - - // We normally setup for all viewports in NewFrame() but here need to handle the mid-frame creation of a new viewport. - // We need to extend the fullscreen clip rect so the OverlayDrawList clip is correct for that the first frame - g.DrawListSharedData.ClipRectFullscreen.x = ImMin(g.DrawListSharedData.ClipRectFullscreen.x, viewport->Pos.x); - g.DrawListSharedData.ClipRectFullscreen.y = ImMin(g.DrawListSharedData.ClipRectFullscreen.y, viewport->Pos.y); - g.DrawListSharedData.ClipRectFullscreen.z = ImMax(g.DrawListSharedData.ClipRectFullscreen.z, viewport->Pos.x + viewport->Size.x); - g.DrawListSharedData.ClipRectFullscreen.w = ImMax(g.DrawListSharedData.ClipRectFullscreen.w, viewport->Pos.y + viewport->Size.y); - - // Store initial DpiScale before the OS platform window creation, based on expected monitor data. - // This is so we can select an appropriate font size on the first frame of our window lifetime - if (viewport->PlatformMonitor != -1) - viewport->DpiScale = g.PlatformIO.Monitors[viewport->PlatformMonitor].DpiScale; - } - - viewport->Window = window; - viewport->LastFrameActive = g.FrameCount; - viewport->UpdateWorkRect(); - IM_ASSERT(window == NULL || viewport->ID == window->ID); - - if (window != NULL) - window->ViewportOwned = true; - - return viewport; -} - -static void ImGui::DestroyViewport(ImGuiViewportP* viewport) -{ - // Clear references to this viewport in windows (window->ViewportId becomes the master data) - ImGuiContext& g = *GImGui; - for (ImGuiWindow* window : g.Windows) - { - if (window->Viewport != viewport) - continue; - window->Viewport = NULL; - window->ViewportOwned = false; - } - if (viewport == g.MouseLastHoveredViewport) - g.MouseLastHoveredViewport = NULL; - - // Destroy - IMGUI_DEBUG_LOG_VIEWPORT("[viewport] Delete Viewport %08X '%s'\n", viewport->ID, viewport->Window ? viewport->Window->Name : "n/a"); - DestroyPlatformWindow(viewport); // In most circumstances the platform window will already be destroyed here. - IM_ASSERT(g.PlatformIO.Viewports.contains(viewport) == false); - IM_ASSERT(g.Viewports[viewport->Idx] == viewport); - g.Viewports.erase(g.Viewports.Data + viewport->Idx); - IM_DELETE(viewport); -} - -// FIXME-VIEWPORT: This is all super messy and ought to be clarified or rewritten. -static void ImGui::WindowSelectViewport(ImGuiWindow* window) -{ - ImGuiContext& g = *GImGui; - ImGuiWindowFlags flags = window->Flags; - window->ViewportAllowPlatformMonitorExtend = -1; - - // Restore main viewport if multi-viewport is not supported by the backend - ImGuiViewportP* main_viewport = (ImGuiViewportP*)(void*)GetMainViewport(); - if (!(g.ConfigFlagsCurrFrame & ImGuiConfigFlags_ViewportsEnable)) - { - SetWindowViewport(window, main_viewport); - return; - } - window->ViewportOwned = false; - - // Appearing popups reset their viewport so they can inherit again - if ((flags & (ImGuiWindowFlags_Popup | ImGuiWindowFlags_Tooltip)) && window->Appearing) - { - window->Viewport = NULL; - window->ViewportId = 0; - } - - if ((g.NextWindowData.Flags & ImGuiNextWindowDataFlags_HasViewport) == 0) - { - // By default inherit from parent window - if (window->Viewport == NULL && window->ParentWindow && (!window->ParentWindow->IsFallbackWindow || window->ParentWindow->WasActive)) - window->Viewport = window->ParentWindow->Viewport; - - // Attempt to restore saved viewport id (= window that hasn't been activated yet), try to restore the viewport based on saved 'window->ViewportPos' restored from .ini file - if (window->Viewport == NULL && window->ViewportId != 0) - { - window->Viewport = (ImGuiViewportP*)FindViewportByID(window->ViewportId); - if (window->Viewport == NULL && window->ViewportPos.x != FLT_MAX && window->ViewportPos.y != FLT_MAX) - window->Viewport = AddUpdateViewport(window, window->ID, window->ViewportPos, window->Size, ImGuiViewportFlags_None); - } - } - - bool lock_viewport = false; - if (g.NextWindowData.Flags & ImGuiNextWindowDataFlags_HasViewport) - { - // Code explicitly request a viewport - window->Viewport = (ImGuiViewportP*)FindViewportByID(g.NextWindowData.ViewportId); - window->ViewportId = g.NextWindowData.ViewportId; // Store ID even if Viewport isn't resolved yet. - if (window->Viewport && (window->Flags & ImGuiWindowFlags_DockNodeHost) != 0 && window->Viewport->Window != NULL) - { - window->Viewport->Window = window; - window->Viewport->ID = window->ViewportId = window->ID; // Overwrite ID (always owned by node) - } - lock_viewport = true; - } - else if ((flags & ImGuiWindowFlags_ChildWindow) || (flags & ImGuiWindowFlags_ChildMenu)) - { - // Always inherit viewport from parent window - if (window->DockNode && window->DockNode->HostWindow) - IM_ASSERT(window->DockNode->HostWindow->Viewport == window->ParentWindow->Viewport); - window->Viewport = window->ParentWindow->Viewport; - } - else if (window->DockNode && window->DockNode->HostWindow) - { - // This covers the "always inherit viewport from parent window" case for when a window reattach to a node that was just created mid-frame - window->Viewport = window->DockNode->HostWindow->Viewport; - } - else if (flags & ImGuiWindowFlags_Tooltip) - { - window->Viewport = g.MouseViewport; - } - else if (GetWindowAlwaysWantOwnViewport(window)) - { - window->Viewport = AddUpdateViewport(window, window->ID, window->Pos, window->Size, ImGuiViewportFlags_None); - } - else if (g.MovingWindow && g.MovingWindow->RootWindowDockTree == window && IsMousePosValid()) - { - if (window->Viewport != NULL && window->Viewport->Window == window) - window->Viewport = AddUpdateViewport(window, window->ID, window->Pos, window->Size, ImGuiViewportFlags_None); - } - else - { - // Merge into host viewport? - // We cannot test window->ViewportOwned as it set lower in the function. - // Testing (g.ActiveId == 0 || g.ActiveIdAllowOverlap) to avoid merging during a short-term widget interaction. Main intent was to avoid during resize (see #4212) - bool try_to_merge_into_host_viewport = (window->Viewport && window == window->Viewport->Window && (g.ActiveId == 0 || g.ActiveIdAllowOverlap)); - if (try_to_merge_into_host_viewport) - UpdateTryMergeWindowIntoHostViewports(window); - } - - // Fallback: merge in default viewport if z-order matches, otherwise create a new viewport - if (window->Viewport == NULL) - if (!UpdateTryMergeWindowIntoHostViewport(window, main_viewport)) - window->Viewport = AddUpdateViewport(window, window->ID, window->Pos, window->Size, ImGuiViewportFlags_None); - - // Mark window as allowed to protrude outside of its viewport and into the current monitor - if (!lock_viewport) - { - if (flags & (ImGuiWindowFlags_Tooltip | ImGuiWindowFlags_Popup)) - { - // We need to take account of the possibility that mouse may become invalid. - // Popups/Tooltip always set ViewportAllowPlatformMonitorExtend so GetWindowAllowedExtentRect() will return full monitor bounds. - ImVec2 mouse_ref = (flags & ImGuiWindowFlags_Tooltip) ? g.IO.MousePos : g.BeginPopupStack.back().OpenMousePos; - bool use_mouse_ref = (g.NavDisableHighlight || !g.NavDisableMouseHover || !g.NavWindow); - bool mouse_valid = IsMousePosValid(&mouse_ref); - if ((window->Appearing || (flags & (ImGuiWindowFlags_Tooltip | ImGuiWindowFlags_ChildMenu))) && (!use_mouse_ref || mouse_valid)) - window->ViewportAllowPlatformMonitorExtend = FindPlatformMonitorForPos((use_mouse_ref && mouse_valid) ? mouse_ref : NavCalcPreferredRefPos()); - else - window->ViewportAllowPlatformMonitorExtend = window->Viewport->PlatformMonitor; - } - else if (window->Viewport && window != window->Viewport->Window && window->Viewport->Window && !(flags & ImGuiWindowFlags_ChildWindow) && window->DockNode == NULL) - { - // When called from Begin() we don't have access to a proper version of the Hidden flag yet, so we replicate this code. - const bool will_be_visible = (window->DockIsActive && !window->DockTabIsVisible) ? false : true; - if ((window->Flags & ImGuiWindowFlags_DockNodeHost) && window->Viewport->LastFrameActive < g.FrameCount && will_be_visible) - { - // Steal/transfer ownership - IMGUI_DEBUG_LOG_VIEWPORT("[viewport] Window '%s' steal Viewport %08X from Window '%s'\n", window->Name, window->Viewport->ID, window->Viewport->Window->Name); - window->Viewport->Window = window; - window->Viewport->ID = window->ID; - window->Viewport->LastNameHash = 0; - } - else if (!UpdateTryMergeWindowIntoHostViewports(window)) // Merge? - { - // New viewport - window->Viewport = AddUpdateViewport(window, window->ID, window->Pos, window->Size, ImGuiViewportFlags_NoFocusOnAppearing); - } - } - else if (window->ViewportAllowPlatformMonitorExtend < 0 && (flags & ImGuiWindowFlags_ChildWindow) == 0) - { - // Regular (non-child, non-popup) windows by default are also allowed to protrude - // Child windows are kept contained within their parent. - window->ViewportAllowPlatformMonitorExtend = window->Viewport->PlatformMonitor; - } - } - - // Update flags - window->ViewportOwned = (window == window->Viewport->Window); - window->ViewportId = window->Viewport->ID; - - // If the OS window has a title bar, hide our imgui title bar - //if (window->ViewportOwned && !(window->Viewport->Flags & ImGuiViewportFlags_NoDecoration)) - // window->Flags |= ImGuiWindowFlags_NoTitleBar; -} - -void ImGui::WindowSyncOwnedViewport(ImGuiWindow* window, ImGuiWindow* parent_window_in_stack) -{ - ImGuiContext& g = *GImGui; - - bool viewport_rect_changed = false; - - // Synchronize window --> viewport in most situations - // Synchronize viewport -> window in case the platform window has been moved or resized from the OS/WM - if (window->Viewport->PlatformRequestMove) - { - window->Pos = window->Viewport->Pos; - MarkIniSettingsDirty(window); - } - else if (memcmp(&window->Viewport->Pos, &window->Pos, sizeof(window->Pos)) != 0) - { - viewport_rect_changed = true; - window->Viewport->Pos = window->Pos; - } - - if (window->Viewport->PlatformRequestResize) - { - window->Size = window->SizeFull = window->Viewport->Size; - MarkIniSettingsDirty(window); - } - else if (memcmp(&window->Viewport->Size, &window->Size, sizeof(window->Size)) != 0) - { - viewport_rect_changed = true; - window->Viewport->Size = window->Size; - } - window->Viewport->UpdateWorkRect(); - - // The viewport may have changed monitor since the global update in UpdateViewportsNewFrame() - // Either a SetNextWindowPos() call in the current frame or a SetWindowPos() call in the previous frame may have this effect. - if (viewport_rect_changed) - UpdateViewportPlatformMonitor(window->Viewport); - - // Update common viewport flags - const ImGuiViewportFlags viewport_flags_to_clear = ImGuiViewportFlags_TopMost | ImGuiViewportFlags_NoTaskBarIcon | ImGuiViewportFlags_NoDecoration | ImGuiViewportFlags_NoRendererClear; - ImGuiViewportFlags viewport_flags = window->Viewport->Flags & ~viewport_flags_to_clear; - ImGuiWindowFlags window_flags = window->Flags; - const bool is_modal = (window_flags & ImGuiWindowFlags_Modal) != 0; - const bool is_short_lived_floating_window = (window_flags & (ImGuiWindowFlags_ChildMenu | ImGuiWindowFlags_Tooltip | ImGuiWindowFlags_Popup)) != 0; - if (window_flags & ImGuiWindowFlags_Tooltip) - viewport_flags |= ImGuiViewportFlags_TopMost; - if ((g.IO.ConfigViewportsNoTaskBarIcon || is_short_lived_floating_window) && !is_modal) - viewport_flags |= ImGuiViewportFlags_NoTaskBarIcon; - if (g.IO.ConfigViewportsNoDecoration || is_short_lived_floating_window) - viewport_flags |= ImGuiViewportFlags_NoDecoration; - - // Not correct to set modal as topmost because: - // - Because other popups can be stacked above a modal (e.g. combo box in a modal) - // - ImGuiViewportFlags_TopMost is currently handled different in backends: in Win32 it is "appear top most" whereas in GLFW and SDL it is "stay topmost" - //if (flags & ImGuiWindowFlags_Modal) - // viewport_flags |= ImGuiViewportFlags_TopMost; - - // For popups and menus that may be protruding out of their parent viewport, we enable _NoFocusOnClick so that clicking on them - // won't steal the OS focus away from their parent window (which may be reflected in OS the title bar decoration). - // Setting _NoFocusOnClick would technically prevent us from bringing back to front in case they are being covered by an OS window from a different app, - // but it shouldn't be much of a problem considering those are already popups that are closed when clicking elsewhere. - if (is_short_lived_floating_window && !is_modal) - viewport_flags |= ImGuiViewportFlags_NoFocusOnAppearing | ImGuiViewportFlags_NoFocusOnClick; - - // We can overwrite viewport flags using ImGuiWindowClass (advanced users) - if (window->WindowClass.ViewportFlagsOverrideSet) - viewport_flags |= window->WindowClass.ViewportFlagsOverrideSet; - if (window->WindowClass.ViewportFlagsOverrideClear) - viewport_flags &= ~window->WindowClass.ViewportFlagsOverrideClear; - - // We can also tell the backend that clearing the platform window won't be necessary, - // as our window background is filling the viewport and we have disabled BgAlpha. - // FIXME: Work on support for per-viewport transparency (#2766) - if (!(window_flags & ImGuiWindowFlags_NoBackground)) - viewport_flags |= ImGuiViewportFlags_NoRendererClear; - - window->Viewport->Flags = viewport_flags; - - // Update parent viewport ID - // (the !IsFallbackWindow test mimic the one done in WindowSelectViewport()) - if (window->WindowClass.ParentViewportId != (ImGuiID)-1) - window->Viewport->ParentViewportId = window->WindowClass.ParentViewportId; - else if ((window_flags & (ImGuiWindowFlags_Popup | ImGuiWindowFlags_Tooltip)) && parent_window_in_stack && (!parent_window_in_stack->IsFallbackWindow || parent_window_in_stack->WasActive)) - window->Viewport->ParentViewportId = parent_window_in_stack->Viewport->ID; - else - window->Viewport->ParentViewportId = g.IO.ConfigViewportsNoDefaultParent ? 0 : IMGUI_VIEWPORT_DEFAULT_ID; -} - -// Called by user at the end of the main loop, after EndFrame() -// This will handle the creation/update of all OS windows via function defined in the ImGuiPlatformIO api. -void ImGui::UpdatePlatformWindows() -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(g.FrameCountEnded == g.FrameCount && "Forgot to call Render() or EndFrame() before UpdatePlatformWindows()?"); - IM_ASSERT(g.FrameCountPlatformEnded < g.FrameCount); - g.FrameCountPlatformEnded = g.FrameCount; - if (!(g.ConfigFlagsCurrFrame & ImGuiConfigFlags_ViewportsEnable)) - return; - - // Create/resize/destroy platform windows to match each active viewport. - // Skip the main viewport (index 0), which is always fully handled by the application! - for (int i = 1; i < g.Viewports.Size; i++) - { - ImGuiViewportP* viewport = g.Viewports[i]; - - // Destroy platform window if the viewport hasn't been submitted or if it is hosting a hidden window - // (the implicit/fallback Debug##Default window will be registering its viewport then be disabled, causing a dummy DestroyPlatformWindow to be made each frame) - bool destroy_platform_window = false; - destroy_platform_window |= (viewport->LastFrameActive < g.FrameCount - 1); - destroy_platform_window |= (viewport->Window && !IsWindowActiveAndVisible(viewport->Window)); - if (destroy_platform_window) - { - DestroyPlatformWindow(viewport); - continue; - } - - // New windows that appears directly in a new viewport won't always have a size on their first frame - if (viewport->LastFrameActive < g.FrameCount || viewport->Size.x <= 0 || viewport->Size.y <= 0) - continue; - - // Create window - const bool is_new_platform_window = (viewport->PlatformWindowCreated == false); - if (is_new_platform_window) - { - IMGUI_DEBUG_LOG_VIEWPORT("[viewport] Create Platform Window %08X '%s'\n", viewport->ID, viewport->Window ? viewport->Window->Name : "n/a"); - g.PlatformIO.Platform_CreateWindow(viewport); - if (g.PlatformIO.Renderer_CreateWindow != NULL) - g.PlatformIO.Renderer_CreateWindow(viewport); - g.PlatformWindowsCreatedCount++; - viewport->LastNameHash = 0; - viewport->LastPlatformPos = viewport->LastPlatformSize = ImVec2(FLT_MAX, FLT_MAX); // By clearing those we'll enforce a call to Platform_SetWindowPos/Size below, before Platform_ShowWindow (FIXME: Is that necessary?) - viewport->LastRendererSize = viewport->Size; // We don't need to call Renderer_SetWindowSize() as it is expected Renderer_CreateWindow() already did it. - viewport->PlatformWindowCreated = true; - } - - // Apply Position and Size (from ImGui to Platform/Renderer backends) - if ((viewport->LastPlatformPos.x != viewport->Pos.x || viewport->LastPlatformPos.y != viewport->Pos.y) && !viewport->PlatformRequestMove) - g.PlatformIO.Platform_SetWindowPos(viewport, viewport->Pos); - if ((viewport->LastPlatformSize.x != viewport->Size.x || viewport->LastPlatformSize.y != viewport->Size.y) && !viewport->PlatformRequestResize) - g.PlatformIO.Platform_SetWindowSize(viewport, viewport->Size); - if ((viewport->LastRendererSize.x != viewport->Size.x || viewport->LastRendererSize.y != viewport->Size.y) && g.PlatformIO.Renderer_SetWindowSize) - g.PlatformIO.Renderer_SetWindowSize(viewport, viewport->Size); - viewport->LastPlatformPos = viewport->Pos; - viewport->LastPlatformSize = viewport->LastRendererSize = viewport->Size; - - // Update title bar (if it changed) - if (ImGuiWindow* window_for_title = GetWindowForTitleDisplay(viewport->Window)) - { - const char* title_begin = window_for_title->Name; - char* title_end = (char*)(intptr_t)FindRenderedTextEnd(title_begin); - const ImGuiID title_hash = ImHashStr(title_begin, title_end - title_begin); - if (viewport->LastNameHash != title_hash) - { - char title_end_backup_c = *title_end; - *title_end = 0; // Cut existing buffer short instead of doing an alloc/free, no small gain. - g.PlatformIO.Platform_SetWindowTitle(viewport, title_begin); - *title_end = title_end_backup_c; - viewport->LastNameHash = title_hash; - } - } - - // Update alpha (if it changed) - if (viewport->LastAlpha != viewport->Alpha && g.PlatformIO.Platform_SetWindowAlpha) - g.PlatformIO.Platform_SetWindowAlpha(viewport, viewport->Alpha); - viewport->LastAlpha = viewport->Alpha; - - // Optional, general purpose call to allow the backend to perform general book-keeping even if things haven't changed. - if (g.PlatformIO.Platform_UpdateWindow) - g.PlatformIO.Platform_UpdateWindow(viewport); - - if (is_new_platform_window) - { - // On startup ensure new platform window don't steal focus (give it a few frames, as nested contents may lead to viewport being created a few frames late) - if (g.FrameCount < 3) - viewport->Flags |= ImGuiViewportFlags_NoFocusOnAppearing; - - // Show window - g.PlatformIO.Platform_ShowWindow(viewport); - - // Even without focus, we assume the window becomes front-most. - // This is useful for our platform z-order heuristic when io.MouseHoveredViewport is not available. - if (viewport->LastFocusedStampCount != g.ViewportFocusedStampCount) - viewport->LastFocusedStampCount = ++g.ViewportFocusedStampCount; - } - - // Clear request flags - viewport->ClearRequestFlags(); - } -} - -// This is a default/basic function for performing the rendering/swap of multiple Platform Windows. -// Custom renderers may prefer to not call this function at all, and instead iterate the publicly exposed platform data and handle rendering/sync themselves. -// The Render/Swap functions stored in ImGuiPlatformIO are merely here to allow for this helper to exist, but you can do it yourself: -// -// ImGuiPlatformIO& platform_io = ImGui::GetPlatformIO(); -// for (int i = 1; i < platform_io.Viewports.Size; i++) -// if ((platform_io.Viewports[i]->Flags & ImGuiViewportFlags_Minimized) == 0) -// MyRenderFunction(platform_io.Viewports[i], my_args); -// for (int i = 1; i < platform_io.Viewports.Size; i++) -// if ((platform_io.Viewports[i]->Flags & ImGuiViewportFlags_Minimized) == 0) -// MySwapBufferFunction(platform_io.Viewports[i], my_args); -// -void ImGui::RenderPlatformWindowsDefault(void* platform_render_arg, void* renderer_render_arg) -{ - // Skip the main viewport (index 0), which is always fully handled by the application! - ImGuiPlatformIO& platform_io = ImGui::GetPlatformIO(); - for (int i = 1; i < platform_io.Viewports.Size; i++) - { - ImGuiViewport* viewport = platform_io.Viewports[i]; - if (viewport->Flags & ImGuiViewportFlags_IsMinimized) - continue; - if (platform_io.Platform_RenderWindow) platform_io.Platform_RenderWindow(viewport, platform_render_arg); - if (platform_io.Renderer_RenderWindow) platform_io.Renderer_RenderWindow(viewport, renderer_render_arg); - } - for (int i = 1; i < platform_io.Viewports.Size; i++) - { - ImGuiViewport* viewport = platform_io.Viewports[i]; - if (viewport->Flags & ImGuiViewportFlags_IsMinimized) - continue; - if (platform_io.Platform_SwapBuffers) platform_io.Platform_SwapBuffers(viewport, platform_render_arg); - if (platform_io.Renderer_SwapBuffers) platform_io.Renderer_SwapBuffers(viewport, renderer_render_arg); - } -} - -static int ImGui::FindPlatformMonitorForPos(const ImVec2& pos) -{ - ImGuiContext& g = *GImGui; - for (int monitor_n = 0; monitor_n < g.PlatformIO.Monitors.Size; monitor_n++) - { - const ImGuiPlatformMonitor& monitor = g.PlatformIO.Monitors[monitor_n]; - if (ImRect(monitor.MainPos, monitor.MainPos + monitor.MainSize).Contains(pos)) - return monitor_n; - } - return -1; -} - -// Search for the monitor with the largest intersection area with the given rectangle -// We generally try to avoid searching loops but the monitor count should be very small here -// FIXME-OPT: We could test the last monitor used for that viewport first, and early -static int ImGui::FindPlatformMonitorForRect(const ImRect& rect) -{ - ImGuiContext& g = *GImGui; - - const int monitor_count = g.PlatformIO.Monitors.Size; - if (monitor_count <= 1) - return monitor_count - 1; - - // Use a minimum threshold of 1.0f so a zero-sized rect won't false positive, and will still find the correct monitor given its position. - // This is necessary for tooltips which always resize down to zero at first. - const float surface_threshold = ImMax(rect.GetWidth() * rect.GetHeight() * 0.5f, 1.0f); - int best_monitor_n = -1; - float best_monitor_surface = 0.001f; - - for (int monitor_n = 0; monitor_n < g.PlatformIO.Monitors.Size && best_monitor_surface < surface_threshold; monitor_n++) - { - const ImGuiPlatformMonitor& monitor = g.PlatformIO.Monitors[monitor_n]; - const ImRect monitor_rect = ImRect(monitor.MainPos, monitor.MainPos + monitor.MainSize); - if (monitor_rect.Contains(rect)) - return monitor_n; - ImRect overlapping_rect = rect; - overlapping_rect.ClipWithFull(monitor_rect); - float overlapping_surface = overlapping_rect.GetWidth() * overlapping_rect.GetHeight(); - if (overlapping_surface < best_monitor_surface) - continue; - best_monitor_surface = overlapping_surface; - best_monitor_n = monitor_n; - } - return best_monitor_n; -} - -// Update monitor from viewport rectangle (we'll use this info to clamp windows and save windows lost in a removed monitor) -static void ImGui::UpdateViewportPlatformMonitor(ImGuiViewportP* viewport) -{ - viewport->PlatformMonitor = (short)FindPlatformMonitorForRect(viewport->GetMainRect()); -} - -// Return value is always != NULL, but don't hold on it across frames. -const ImGuiPlatformMonitor* ImGui::GetViewportPlatformMonitor(ImGuiViewport* viewport_p) -{ - ImGuiContext& g = *GImGui; - ImGuiViewportP* viewport = (ImGuiViewportP*)(void*)viewport_p; - int monitor_idx = viewport->PlatformMonitor; - if (monitor_idx >= 0 && monitor_idx < g.PlatformIO.Monitors.Size) - return &g.PlatformIO.Monitors[monitor_idx]; - return &g.FallbackMonitor; -} - -void ImGui::DestroyPlatformWindow(ImGuiViewportP* viewport) -{ - ImGuiContext& g = *GImGui; - if (viewport->PlatformWindowCreated) - { - IMGUI_DEBUG_LOG_VIEWPORT("[viewport] Destroy Platform Window %08X '%s'\n", viewport->ID, viewport->Window ? viewport->Window->Name : "n/a"); - if (g.PlatformIO.Renderer_DestroyWindow) - g.PlatformIO.Renderer_DestroyWindow(viewport); - if (g.PlatformIO.Platform_DestroyWindow) - g.PlatformIO.Platform_DestroyWindow(viewport); - IM_ASSERT(viewport->RendererUserData == NULL && viewport->PlatformUserData == NULL); - - // Don't clear PlatformWindowCreated for the main viewport, as we initially set that up to true in Initialize() - // The righter way may be to leave it to the backend to set this flag all-together, and made the flag public. - if (viewport->ID != IMGUI_VIEWPORT_DEFAULT_ID) - viewport->PlatformWindowCreated = false; - } - else - { - IM_ASSERT(viewport->RendererUserData == NULL && viewport->PlatformUserData == NULL && viewport->PlatformHandle == NULL); - } - viewport->RendererUserData = viewport->PlatformUserData = viewport->PlatformHandle = NULL; - viewport->ClearRequestFlags(); -} - -void ImGui::DestroyPlatformWindows() -{ - // We call the destroy window on every viewport (including the main viewport, index 0) to give a chance to the backend - // to clear any data they may have stored in e.g. PlatformUserData, RendererUserData. - // It is convenient for the platform backend code to store something in the main viewport, in order for e.g. the mouse handling - // code to operator a consistent manner. - // It is expected that the backend can handle calls to Renderer_DestroyWindow/Platform_DestroyWindow without - // crashing if it doesn't have data stored. - ImGuiContext& g = *GImGui; - for (ImGuiViewportP* viewport : g.Viewports) - DestroyPlatformWindow(viewport); -} - - -//----------------------------------------------------------------------------- -// [SECTION] DOCKING -//----------------------------------------------------------------------------- -// Docking: Internal Types -// Docking: Forward Declarations -// Docking: ImGuiDockContext -// Docking: ImGuiDockContext Docking/Undocking functions -// Docking: ImGuiDockNode -// Docking: ImGuiDockNode Tree manipulation functions -// Docking: Public Functions (SetWindowDock, DockSpace, DockSpaceOverViewport) -// Docking: Builder Functions -// Docking: Begin/End Support Functions (called from Begin/End) -// Docking: Settings -//----------------------------------------------------------------------------- - -//----------------------------------------------------------------------------- -// Typical Docking call flow: (root level is generally public API): -//----------------------------------------------------------------------------- -// - NewFrame() new dear imgui frame -// | DockContextNewFrameUpdateUndocking() - process queued undocking requests -// | - DockContextProcessUndockWindow() - process one window undocking request -// | - DockContextProcessUndockNode() - process one whole node undocking request -// | DockContextNewFrameUpdateUndocking() - process queue docking requests, create floating dock nodes -// | - update g.HoveredDockNode - [debug] update node hovered by mouse -// | - DockContextProcessDock() - process one docking request -// | - DockNodeUpdate() -// | - DockNodeUpdateForRootNode() -// | - DockNodeUpdateFlagsAndCollapse() -// | - DockNodeFindInfo() -// | - destroy unused node or tab bar -// | - create dock node host window -// | - Begin() etc. -// | - DockNodeStartMouseMovingWindow() -// | - DockNodeTreeUpdatePosSize() -// | - DockNodeTreeUpdateSplitter() -// | - draw node background -// | - DockNodeUpdateTabBar() - create/update tab bar for a docking node -// | - DockNodeAddTabBar() -// | - DockNodeWindowMenuUpdate() -// | - DockNodeCalcTabBarLayout() -// | - BeginTabBarEx() -// | - TabItemEx() calls -// | - EndTabBar() -// | - BeginDockableDragDropTarget() -// | - DockNodeUpdate() - recurse into child nodes... -//----------------------------------------------------------------------------- -// - DockSpace() user submit a dockspace into a window -// | Begin(Child) - create a child window -// | DockNodeUpdate() - call main dock node update function -// | End(Child) -// | ItemSize() -//----------------------------------------------------------------------------- -// - Begin() -// | BeginDocked() -// | BeginDockableDragDropSource() -// | BeginDockableDragDropTarget() -// | - DockNodePreviewDockRender() -//----------------------------------------------------------------------------- -// - EndFrame() -// | DockContextEndFrame() -//----------------------------------------------------------------------------- - -//----------------------------------------------------------------------------- -// Docking: Internal Types -//----------------------------------------------------------------------------- -// - ImGuiDockRequestType -// - ImGuiDockRequest -// - ImGuiDockPreviewData -// - ImGuiDockNodeSettings -// - ImGuiDockContext -//----------------------------------------------------------------------------- - -enum ImGuiDockRequestType -{ - ImGuiDockRequestType_None = 0, - ImGuiDockRequestType_Dock, - ImGuiDockRequestType_Undock, - ImGuiDockRequestType_Split // Split is the same as Dock but without a DockPayload -}; - -struct ImGuiDockRequest -{ - ImGuiDockRequestType Type; - ImGuiWindow* DockTargetWindow; // Destination/Target Window to dock into (may be a loose window or a DockNode, might be NULL in which case DockTargetNode cannot be NULL) - ImGuiDockNode* DockTargetNode; // Destination/Target Node to dock into - ImGuiWindow* DockPayload; // Source/Payload window to dock (may be a loose window or a DockNode), [Optional] - ImGuiDir DockSplitDir; - float DockSplitRatio; - bool DockSplitOuter; - ImGuiWindow* UndockTargetWindow; - ImGuiDockNode* UndockTargetNode; - - ImGuiDockRequest() - { - Type = ImGuiDockRequestType_None; - DockTargetWindow = DockPayload = UndockTargetWindow = NULL; - DockTargetNode = UndockTargetNode = NULL; - DockSplitDir = ImGuiDir_None; - DockSplitRatio = 0.5f; - DockSplitOuter = false; - } -}; - -struct ImGuiDockPreviewData -{ - ImGuiDockNode FutureNode; - bool IsDropAllowed; - bool IsCenterAvailable; - bool IsSidesAvailable; // Hold your breath, grammar freaks.. - bool IsSplitDirExplicit; // Set when hovered the drop rect (vs. implicit SplitDir==None when hovered the window) - ImGuiDockNode* SplitNode; - ImGuiDir SplitDir; - float SplitRatio; - ImRect DropRectsDraw[ImGuiDir_COUNT + 1]; // May be slightly different from hit-testing drop rects used in DockNodeCalcDropRects() - - ImGuiDockPreviewData() : FutureNode(0) { IsDropAllowed = IsCenterAvailable = IsSidesAvailable = IsSplitDirExplicit = false; SplitNode = NULL; SplitDir = ImGuiDir_None; SplitRatio = 0.f; for (int n = 0; n < IM_ARRAYSIZE(DropRectsDraw); n++) DropRectsDraw[n] = ImRect(+FLT_MAX, +FLT_MAX, -FLT_MAX, -FLT_MAX); } -}; - -// Persistent Settings data, stored contiguously in SettingsNodes (sizeof() ~32 bytes) -struct ImGuiDockNodeSettings -{ - ImGuiID ID; - ImGuiID ParentNodeId; - ImGuiID ParentWindowId; - ImGuiID SelectedTabId; - signed char SplitAxis; - char Depth; - ImGuiDockNodeFlags Flags; // NB: We save individual flags one by one in ascii format (ImGuiDockNodeFlags_SavedFlagsMask_) - ImVec2ih Pos; - ImVec2ih Size; - ImVec2ih SizeRef; - ImGuiDockNodeSettings() { memset(this, 0, sizeof(*this)); SplitAxis = ImGuiAxis_None; } -}; - -//----------------------------------------------------------------------------- -// Docking: Forward Declarations -//----------------------------------------------------------------------------- - -namespace ImGui -{ - // ImGuiDockContext - static ImGuiDockNode* DockContextAddNode(ImGuiContext* ctx, ImGuiID id); - static void DockContextRemoveNode(ImGuiContext* ctx, ImGuiDockNode* node, bool merge_sibling_into_parent_node); - static void DockContextQueueNotifyRemovedNode(ImGuiContext* ctx, ImGuiDockNode* node); - static void DockContextProcessDock(ImGuiContext* ctx, ImGuiDockRequest* req); - static void DockContextPruneUnusedSettingsNodes(ImGuiContext* ctx); - static ImGuiDockNode* DockContextBindNodeToWindow(ImGuiContext* ctx, ImGuiWindow* window); - static void DockContextBuildNodesFromSettings(ImGuiContext* ctx, ImGuiDockNodeSettings* node_settings_array, int node_settings_count); - static void DockContextBuildAddWindowsToNodes(ImGuiContext* ctx, ImGuiID root_id); // Use root_id==0 to add all - - // ImGuiDockNode - static void DockNodeAddWindow(ImGuiDockNode* node, ImGuiWindow* window, bool add_to_tab_bar); - static void DockNodeMoveWindows(ImGuiDockNode* dst_node, ImGuiDockNode* src_node); - static void DockNodeMoveChildNodes(ImGuiDockNode* dst_node, ImGuiDockNode* src_node); - static ImGuiWindow* DockNodeFindWindowByID(ImGuiDockNode* node, ImGuiID id); - static void DockNodeApplyPosSizeToWindows(ImGuiDockNode* node); - static void DockNodeRemoveWindow(ImGuiDockNode* node, ImGuiWindow* window, ImGuiID save_dock_id); - static void DockNodeHideHostWindow(ImGuiDockNode* node); - static void DockNodeUpdate(ImGuiDockNode* node); - static void DockNodeUpdateForRootNode(ImGuiDockNode* node); - static void DockNodeUpdateFlagsAndCollapse(ImGuiDockNode* node); - static void DockNodeUpdateHasCentralNodeChild(ImGuiDockNode* node); - static void DockNodeUpdateTabBar(ImGuiDockNode* node, ImGuiWindow* host_window); - static void DockNodeAddTabBar(ImGuiDockNode* node); - static void DockNodeRemoveTabBar(ImGuiDockNode* node); - static void DockNodeWindowMenuUpdate(ImGuiDockNode* node, ImGuiTabBar* tab_bar); - static void DockNodeUpdateVisibleFlag(ImGuiDockNode* node); - static void DockNodeStartMouseMovingWindow(ImGuiDockNode* node, ImGuiWindow* window); - static bool DockNodeIsDropAllowed(ImGuiWindow* host_window, ImGuiWindow* payload_window); - static void DockNodePreviewDockSetup(ImGuiWindow* host_window, ImGuiDockNode* host_node, ImGuiWindow* payload_window, ImGuiDockNode* payload_node, ImGuiDockPreviewData* preview_data, bool is_explicit_target, bool is_outer_docking); - static void DockNodePreviewDockRender(ImGuiWindow* host_window, ImGuiDockNode* host_node, ImGuiWindow* payload_window, const ImGuiDockPreviewData* preview_data); - static void DockNodeCalcTabBarLayout(const ImGuiDockNode* node, ImRect* out_title_rect, ImRect* out_tab_bar_rect, ImVec2* out_window_menu_button_pos, ImVec2* out_close_button_pos); - static void DockNodeCalcSplitRects(ImVec2& pos_old, ImVec2& size_old, ImVec2& pos_new, ImVec2& size_new, ImGuiDir dir, ImVec2 size_new_desired); - static bool DockNodeCalcDropRectsAndTestMousePos(const ImRect& parent, ImGuiDir dir, ImRect& out_draw, bool outer_docking, ImVec2* test_mouse_pos); - static const char* DockNodeGetHostWindowTitle(ImGuiDockNode* node, char* buf, int buf_size) { ImFormatString(buf, buf_size, "##DockNode_%02X", node->ID); return buf; } - static int DockNodeGetTabOrder(ImGuiWindow* window); - - // ImGuiDockNode tree manipulations - static void DockNodeTreeSplit(ImGuiContext* ctx, ImGuiDockNode* parent_node, ImGuiAxis split_axis, int split_first_child, float split_ratio, ImGuiDockNode* new_node); - static void DockNodeTreeMerge(ImGuiContext* ctx, ImGuiDockNode* parent_node, ImGuiDockNode* merge_lead_child); - static void DockNodeTreeUpdatePosSize(ImGuiDockNode* node, ImVec2 pos, ImVec2 size, ImGuiDockNode* only_write_to_single_node = NULL); - static void DockNodeTreeUpdateSplitter(ImGuiDockNode* node); - static ImGuiDockNode* DockNodeTreeFindVisibleNodeByPos(ImGuiDockNode* node, ImVec2 pos); - static ImGuiDockNode* DockNodeTreeFindFallbackLeafNode(ImGuiDockNode* node); - - // Settings - static void DockSettingsRenameNodeReferences(ImGuiID old_node_id, ImGuiID new_node_id); - static void DockSettingsRemoveNodeReferences(ImGuiID* node_ids, int node_ids_count); - static ImGuiDockNodeSettings* DockSettingsFindNodeSettings(ImGuiContext* ctx, ImGuiID node_id); - static void DockSettingsHandler_ClearAll(ImGuiContext*, ImGuiSettingsHandler*); - static void DockSettingsHandler_ApplyAll(ImGuiContext*, ImGuiSettingsHandler*); - static void* DockSettingsHandler_ReadOpen(ImGuiContext*, ImGuiSettingsHandler*, const char* name); - static void DockSettingsHandler_ReadLine(ImGuiContext*, ImGuiSettingsHandler*, void* entry, const char* line); - static void DockSettingsHandler_WriteAll(ImGuiContext* imgui_ctx, ImGuiSettingsHandler* handler, ImGuiTextBuffer* buf); -} - -//----------------------------------------------------------------------------- -// Docking: ImGuiDockContext -//----------------------------------------------------------------------------- -// The lifetime model is different from the one of regular windows: we always create a ImGuiDockNode for each ImGuiDockNodeSettings, -// or we always hold the entire docking node tree. Nodes are frequently hidden, e.g. if the window(s) or child nodes they host are not active. -// At boot time only, we run a simple GC to remove nodes that have no references. -// Because dock node settings (which are small, contiguous structures) are always mirrored by their corresponding dock nodes (more complete structures), -// we can also very easily recreate the nodes from scratch given the settings data (this is what DockContextRebuild() does). -// This is convenient as docking reconfiguration can be implemented by mostly poking at the simpler settings data. -//----------------------------------------------------------------------------- -// - DockContextInitialize() -// - DockContextShutdown() -// - DockContextClearNodes() -// - DockContextRebuildNodes() -// - DockContextNewFrameUpdateUndocking() -// - DockContextNewFrameUpdateDocking() -// - DockContextEndFrame() -// - DockContextFindNodeByID() -// - DockContextBindNodeToWindow() -// - DockContextGenNodeID() -// - DockContextAddNode() -// - DockContextRemoveNode() -// - ImGuiDockContextPruneNodeData -// - DockContextPruneUnusedSettingsNodes() -// - DockContextBuildNodesFromSettings() -// - DockContextBuildAddWindowsToNodes() -//----------------------------------------------------------------------------- - -void ImGui::DockContextInitialize(ImGuiContext* ctx) -{ - ImGuiContext& g = *ctx; - - // Add .ini handle for persistent docking data - ImGuiSettingsHandler ini_handler; - ini_handler.TypeName = "Docking"; - ini_handler.TypeHash = ImHashStr("Docking"); - ini_handler.ClearAllFn = DockSettingsHandler_ClearAll; - ini_handler.ReadInitFn = DockSettingsHandler_ClearAll; // Also clear on read - ini_handler.ReadOpenFn = DockSettingsHandler_ReadOpen; - ini_handler.ReadLineFn = DockSettingsHandler_ReadLine; - ini_handler.ApplyAllFn = DockSettingsHandler_ApplyAll; - ini_handler.WriteAllFn = DockSettingsHandler_WriteAll; - g.SettingsHandlers.push_back(ini_handler); - - g.DockNodeWindowMenuHandler = &DockNodeWindowMenuHandler_Default; -} - -void ImGui::DockContextShutdown(ImGuiContext* ctx) -{ - ImGuiDockContext* dc = &ctx->DockContext; - for (int n = 0; n < dc->Nodes.Data.Size; n++) - if (ImGuiDockNode* node = (ImGuiDockNode*)dc->Nodes.Data[n].val_p) - IM_DELETE(node); -} - -void ImGui::DockContextClearNodes(ImGuiContext* ctx, ImGuiID root_id, bool clear_settings_refs) -{ - IM_UNUSED(ctx); - IM_ASSERT(ctx == GImGui); - DockBuilderRemoveNodeDockedWindows(root_id, clear_settings_refs); - DockBuilderRemoveNodeChildNodes(root_id); -} - -// [DEBUG] This function also acts as a defacto test to make sure we can rebuild from scratch without a glitch -// (Different from DockSettingsHandler_ClearAll() + DockSettingsHandler_ApplyAll() because this reuses current settings!) -void ImGui::DockContextRebuildNodes(ImGuiContext* ctx) -{ - ImGuiContext& g = *ctx; - ImGuiDockContext* dc = &ctx->DockContext; - IMGUI_DEBUG_LOG_DOCKING("[docking] DockContextRebuildNodes\n"); - SaveIniSettingsToMemory(); - ImGuiID root_id = 0; // Rebuild all - DockContextClearNodes(ctx, root_id, false); - DockContextBuildNodesFromSettings(ctx, dc->NodesSettings.Data, dc->NodesSettings.Size); - DockContextBuildAddWindowsToNodes(ctx, root_id); -} - -// Docking context update function, called by NewFrame() -void ImGui::DockContextNewFrameUpdateUndocking(ImGuiContext* ctx) -{ - ImGuiContext& g = *ctx; - ImGuiDockContext* dc = &ctx->DockContext; - if (!(g.IO.ConfigFlags & ImGuiConfigFlags_DockingEnable)) - { - if (dc->Nodes.Data.Size > 0 || dc->Requests.Size > 0) - DockContextClearNodes(ctx, 0, true); - return; - } - - // Setting NoSplit at runtime merges all nodes - if (g.IO.ConfigDockingNoSplit) - for (int n = 0; n < dc->Nodes.Data.Size; n++) - if (ImGuiDockNode* node = (ImGuiDockNode*)dc->Nodes.Data[n].val_p) - if (node->IsRootNode() && node->IsSplitNode()) - { - DockBuilderRemoveNodeChildNodes(node->ID); - //dc->WantFullRebuild = true; - } - - // Process full rebuild -#if 0 - if (ImGui::IsKeyPressed(ImGui::GetKeyIndex(ImGuiKey_C))) - dc->WantFullRebuild = true; -#endif - if (dc->WantFullRebuild) - { - DockContextRebuildNodes(ctx); - dc->WantFullRebuild = false; - } - - // Process Undocking requests (we need to process them _before_ the UpdateMouseMovingWindowNewFrame call in NewFrame) - for (ImGuiDockRequest& req : dc->Requests) - { - if (req.Type == ImGuiDockRequestType_Undock && req.UndockTargetWindow) - DockContextProcessUndockWindow(ctx, req.UndockTargetWindow); - else if (req.Type == ImGuiDockRequestType_Undock && req.UndockTargetNode) - DockContextProcessUndockNode(ctx, req.UndockTargetNode); - } -} - -// Docking context update function, called by NewFrame() -void ImGui::DockContextNewFrameUpdateDocking(ImGuiContext* ctx) -{ - ImGuiContext& g = *ctx; - ImGuiDockContext* dc = &ctx->DockContext; - if (!(g.IO.ConfigFlags & ImGuiConfigFlags_DockingEnable)) - return; - - // [DEBUG] Store hovered dock node. - // We could in theory use DockNodeTreeFindVisibleNodeByPos() on the root host dock node, but using ->DockNode is a good shortcut. - // Note this is mostly a debug thing and isn't actually used for docking target, because docking involve more detailed filtering. - g.DebugHoveredDockNode = NULL; - if (ImGuiWindow* hovered_window = g.HoveredWindowUnderMovingWindow) - { - if (hovered_window->DockNodeAsHost) - g.DebugHoveredDockNode = DockNodeTreeFindVisibleNodeByPos(hovered_window->DockNodeAsHost, g.IO.MousePos); - else if (hovered_window->RootWindow->DockNode) - g.DebugHoveredDockNode = hovered_window->RootWindow->DockNode; - } - - // Process Docking requests - for (ImGuiDockRequest& req : dc->Requests) - if (req.Type == ImGuiDockRequestType_Dock) - DockContextProcessDock(ctx, &req); - dc->Requests.resize(0); - - // Create windows for each automatic docking nodes - // We can have NULL pointers when we delete nodes, but because ID are recycled this should amortize nicely (and our node count will never be very high) - for (int n = 0; n < dc->Nodes.Data.Size; n++) - if (ImGuiDockNode* node = (ImGuiDockNode*)dc->Nodes.Data[n].val_p) - if (node->IsFloatingNode()) - DockNodeUpdate(node); -} - -void ImGui::DockContextEndFrame(ImGuiContext* ctx) -{ - // Draw backgrounds of node missing their window - ImGuiContext& g = *ctx; - ImGuiDockContext* dc = &g.DockContext; - for (int n = 0; n < dc->Nodes.Data.Size; n++) - if (ImGuiDockNode* node = (ImGuiDockNode*)dc->Nodes.Data[n].val_p) - if (node->LastFrameActive == g.FrameCount && node->IsVisible && node->HostWindow && node->IsLeafNode() && !node->IsBgDrawnThisFrame) - { - ImRect bg_rect(node->Pos + ImVec2(0.0f, GetFrameHeight()), node->Pos + node->Size); - ImDrawFlags bg_rounding_flags = CalcRoundingFlagsForRectInRect(bg_rect, node->HostWindow->Rect(), g.Style.DockingSeparatorSize); - node->HostWindow->DrawList->ChannelsSetCurrent(DOCKING_HOST_DRAW_CHANNEL_BG); - node->HostWindow->DrawList->AddRectFilled(bg_rect.Min, bg_rect.Max, node->LastBgColor, node->HostWindow->WindowRounding, bg_rounding_flags); - } -} - -ImGuiDockNode* ImGui::DockContextFindNodeByID(ImGuiContext* ctx, ImGuiID id) -{ - return (ImGuiDockNode*)ctx->DockContext.Nodes.GetVoidPtr(id); -} - -ImGuiID ImGui::DockContextGenNodeID(ImGuiContext* ctx) -{ - // Generate an ID for new node (the exact ID value doesn't matter as long as it is not already used) - // FIXME-OPT FIXME-DOCK: This is suboptimal, even if the node count is small enough not to be a worry.0 - // We should poke in ctx->Nodes to find a suitable ID faster. Even more so trivial that ctx->Nodes lookup is already sorted. - ImGuiID id = 0x0001; - while (DockContextFindNodeByID(ctx, id) != NULL) - id++; - return id; -} - -static ImGuiDockNode* ImGui::DockContextAddNode(ImGuiContext* ctx, ImGuiID id) -{ - // Generate an ID for the new node (the exact ID value doesn't matter as long as it is not already used) and add the first window. - ImGuiContext& g = *ctx; - if (id == 0) - id = DockContextGenNodeID(ctx); - else - IM_ASSERT(DockContextFindNodeByID(ctx, id) == NULL); - - // We don't set node->LastFrameAlive on construction. Nodes are always created at all time to reflect .ini settings! - IMGUI_DEBUG_LOG_DOCKING("[docking] DockContextAddNode 0x%08X\n", id); - ImGuiDockNode* node = IM_NEW(ImGuiDockNode)(id); - ctx->DockContext.Nodes.SetVoidPtr(node->ID, node); - return node; -} - -static void ImGui::DockContextRemoveNode(ImGuiContext* ctx, ImGuiDockNode* node, bool merge_sibling_into_parent_node) -{ - ImGuiContext& g = *ctx; - ImGuiDockContext* dc = &ctx->DockContext; - - IMGUI_DEBUG_LOG_DOCKING("[docking] DockContextRemoveNode 0x%08X\n", node->ID); - IM_ASSERT(DockContextFindNodeByID(ctx, node->ID) == node); - IM_ASSERT(node->ChildNodes[0] == NULL && node->ChildNodes[1] == NULL); - IM_ASSERT(node->Windows.Size == 0); - - if (node->HostWindow) - node->HostWindow->DockNodeAsHost = NULL; - - ImGuiDockNode* parent_node = node->ParentNode; - const bool merge = (merge_sibling_into_parent_node && parent_node != NULL); - if (merge) - { - IM_ASSERT(parent_node->ChildNodes[0] == node || parent_node->ChildNodes[1] == node); - ImGuiDockNode* sibling_node = (parent_node->ChildNodes[0] == node ? parent_node->ChildNodes[1] : parent_node->ChildNodes[0]); - DockNodeTreeMerge(&g, parent_node, sibling_node); - } - else - { - for (int n = 0; parent_node && n < IM_ARRAYSIZE(parent_node->ChildNodes); n++) - if (parent_node->ChildNodes[n] == node) - node->ParentNode->ChildNodes[n] = NULL; - dc->Nodes.SetVoidPtr(node->ID, NULL); - IM_DELETE(node); - } -} - -static int IMGUI_CDECL DockNodeComparerDepthMostFirst(const void* lhs, const void* rhs) -{ - const ImGuiDockNode* a = *(const ImGuiDockNode* const*)lhs; - const ImGuiDockNode* b = *(const ImGuiDockNode* const*)rhs; - return ImGui::DockNodeGetDepth(b) - ImGui::DockNodeGetDepth(a); -} - -// Pre C++0x doesn't allow us to use a function-local type (without linkage) as template parameter, so we moved this here. -struct ImGuiDockContextPruneNodeData -{ - int CountWindows, CountChildWindows, CountChildNodes; - ImGuiID RootId; - ImGuiDockContextPruneNodeData() { CountWindows = CountChildWindows = CountChildNodes = 0; RootId = 0; } -}; - -// Garbage collect unused nodes (run once at init time) -static void ImGui::DockContextPruneUnusedSettingsNodes(ImGuiContext* ctx) -{ - ImGuiContext& g = *ctx; - ImGuiDockContext* dc = &ctx->DockContext; - IM_ASSERT(g.Windows.Size == 0); - - ImPool pool; - pool.Reserve(dc->NodesSettings.Size); - - // Count child nodes and compute RootID - for (int settings_n = 0; settings_n < dc->NodesSettings.Size; settings_n++) - { - ImGuiDockNodeSettings* settings = &dc->NodesSettings[settings_n]; - ImGuiDockContextPruneNodeData* parent_data = settings->ParentNodeId ? pool.GetByKey(settings->ParentNodeId) : 0; - pool.GetOrAddByKey(settings->ID)->RootId = parent_data ? parent_data->RootId : settings->ID; - if (settings->ParentNodeId) - pool.GetOrAddByKey(settings->ParentNodeId)->CountChildNodes++; - } - - // Count reference to dock ids from dockspaces - // We track the 'auto-DockNode <- manual-Window <- manual-DockSpace' in order to avoid 'auto-DockNode' being ditched by DockContextPruneUnusedSettingsNodes() - for (int settings_n = 0; settings_n < dc->NodesSettings.Size; settings_n++) - { - ImGuiDockNodeSettings* settings = &dc->NodesSettings[settings_n]; - if (settings->ParentWindowId != 0) - if (ImGuiWindowSettings* window_settings = FindWindowSettingsByID(settings->ParentWindowId)) - if (window_settings->DockId) - if (ImGuiDockContextPruneNodeData* data = pool.GetByKey(window_settings->DockId)) - data->CountChildNodes++; - } - - // Count reference to dock ids from window settings - // We guard against the possibility of an invalid .ini file (RootID may point to a missing node) - for (ImGuiWindowSettings* settings = g.SettingsWindows.begin(); settings != NULL; settings = g.SettingsWindows.next_chunk(settings)) - if (ImGuiID dock_id = settings->DockId) - if (ImGuiDockContextPruneNodeData* data = pool.GetByKey(dock_id)) - { - data->CountWindows++; - if (ImGuiDockContextPruneNodeData* data_root = (data->RootId == dock_id) ? data : pool.GetByKey(data->RootId)) - data_root->CountChildWindows++; - } - - // Prune - for (int settings_n = 0; settings_n < dc->NodesSettings.Size; settings_n++) - { - ImGuiDockNodeSettings* settings = &dc->NodesSettings[settings_n]; - ImGuiDockContextPruneNodeData* data = pool.GetByKey(settings->ID); - if (data->CountWindows > 1) - continue; - ImGuiDockContextPruneNodeData* data_root = (data->RootId == settings->ID) ? data : pool.GetByKey(data->RootId); - - bool remove = false; - remove |= (data->CountWindows == 1 && settings->ParentNodeId == 0 && data->CountChildNodes == 0 && !(settings->Flags & ImGuiDockNodeFlags_CentralNode)); // Floating root node with only 1 window - remove |= (data->CountWindows == 0 && settings->ParentNodeId == 0 && data->CountChildNodes == 0); // Leaf nodes with 0 window - remove |= (data_root->CountChildWindows == 0); - if (remove) - { - IMGUI_DEBUG_LOG_DOCKING("[docking] DockContextPruneUnusedSettingsNodes: Prune 0x%08X\n", settings->ID); - DockSettingsRemoveNodeReferences(&settings->ID, 1); - settings->ID = 0; - } - } -} - -static void ImGui::DockContextBuildNodesFromSettings(ImGuiContext* ctx, ImGuiDockNodeSettings* node_settings_array, int node_settings_count) -{ - // Build nodes - for (int node_n = 0; node_n < node_settings_count; node_n++) - { - ImGuiDockNodeSettings* settings = &node_settings_array[node_n]; - if (settings->ID == 0) - continue; - ImGuiDockNode* node = DockContextAddNode(ctx, settings->ID); - node->ParentNode = settings->ParentNodeId ? DockContextFindNodeByID(ctx, settings->ParentNodeId) : NULL; - node->Pos = ImVec2(settings->Pos.x, settings->Pos.y); - node->Size = ImVec2(settings->Size.x, settings->Size.y); - node->SizeRef = ImVec2(settings->SizeRef.x, settings->SizeRef.y); - node->AuthorityForPos = node->AuthorityForSize = node->AuthorityForViewport = ImGuiDataAuthority_DockNode; - if (node->ParentNode && node->ParentNode->ChildNodes[0] == NULL) - node->ParentNode->ChildNodes[0] = node; - else if (node->ParentNode && node->ParentNode->ChildNodes[1] == NULL) - node->ParentNode->ChildNodes[1] = node; - node->SelectedTabId = settings->SelectedTabId; - node->SplitAxis = (ImGuiAxis)settings->SplitAxis; - node->SetLocalFlags(settings->Flags & ImGuiDockNodeFlags_SavedFlagsMask_); - - // Bind host window immediately if it already exist (in case of a rebuild) - // This is useful as the RootWindowForTitleBarHighlight links necessary to highlight the currently focused node requires node->HostWindow to be set. - char host_window_title[20]; - ImGuiDockNode* root_node = DockNodeGetRootNode(node); - node->HostWindow = FindWindowByName(DockNodeGetHostWindowTitle(root_node, host_window_title, IM_ARRAYSIZE(host_window_title))); - } -} - -void ImGui::DockContextBuildAddWindowsToNodes(ImGuiContext* ctx, ImGuiID root_id) -{ - // Rebind all windows to nodes (they can also lazily rebind but we'll have a visible glitch during the first frame) - ImGuiContext& g = *ctx; - for (ImGuiWindow* window : g.Windows) - { - if (window->DockId == 0 || window->LastFrameActive < g.FrameCount - 1) - continue; - if (window->DockNode != NULL) - continue; - - ImGuiDockNode* node = DockContextFindNodeByID(ctx, window->DockId); - IM_ASSERT(node != NULL); // This should have been called after DockContextBuildNodesFromSettings() - if (root_id == 0 || DockNodeGetRootNode(node)->ID == root_id) - DockNodeAddWindow(node, window, true); - } -} - -//----------------------------------------------------------------------------- -// Docking: ImGuiDockContext Docking/Undocking functions -//----------------------------------------------------------------------------- -// - DockContextQueueDock() -// - DockContextQueueUndockWindow() -// - DockContextQueueUndockNode() -// - DockContextQueueNotifyRemovedNode() -// - DockContextProcessDock() -// - DockContextProcessUndockWindow() -// - DockContextProcessUndockNode() -// - DockContextCalcDropPosForDocking() -//----------------------------------------------------------------------------- - -void ImGui::DockContextQueueDock(ImGuiContext* ctx, ImGuiWindow* target, ImGuiDockNode* target_node, ImGuiWindow* payload, ImGuiDir split_dir, float split_ratio, bool split_outer) -{ - IM_ASSERT(target != payload); - ImGuiDockRequest req; - req.Type = ImGuiDockRequestType_Dock; - req.DockTargetWindow = target; - req.DockTargetNode = target_node; - req.DockPayload = payload; - req.DockSplitDir = split_dir; - req.DockSplitRatio = split_ratio; - req.DockSplitOuter = split_outer; - ctx->DockContext.Requests.push_back(req); -} - -void ImGui::DockContextQueueUndockWindow(ImGuiContext* ctx, ImGuiWindow* window) -{ - ImGuiDockRequest req; - req.Type = ImGuiDockRequestType_Undock; - req.UndockTargetWindow = window; - ctx->DockContext.Requests.push_back(req); -} - -void ImGui::DockContextQueueUndockNode(ImGuiContext* ctx, ImGuiDockNode* node) -{ - ImGuiDockRequest req; - req.Type = ImGuiDockRequestType_Undock; - req.UndockTargetNode = node; - ctx->DockContext.Requests.push_back(req); -} - -void ImGui::DockContextQueueNotifyRemovedNode(ImGuiContext* ctx, ImGuiDockNode* node) -{ - ImGuiDockContext* dc = &ctx->DockContext; - for (ImGuiDockRequest& req : dc->Requests) - if (req.DockTargetNode == node) - req.Type = ImGuiDockRequestType_None; -} - -void ImGui::DockContextProcessDock(ImGuiContext* ctx, ImGuiDockRequest* req) -{ - IM_ASSERT((req->Type == ImGuiDockRequestType_Dock && req->DockPayload != NULL) || (req->Type == ImGuiDockRequestType_Split && req->DockPayload == NULL)); - IM_ASSERT(req->DockTargetWindow != NULL || req->DockTargetNode != NULL); - - ImGuiContext& g = *ctx; - IM_UNUSED(g); - - ImGuiWindow* payload_window = req->DockPayload; // Optional - ImGuiWindow* target_window = req->DockTargetWindow; - ImGuiDockNode* node = req->DockTargetNode; - if (payload_window) - IMGUI_DEBUG_LOG_DOCKING("[docking] DockContextProcessDock node 0x%08X target '%s' dock window '%s', split_dir %d\n", node ? node->ID : 0, target_window ? target_window->Name : "NULL", payload_window->Name, req->DockSplitDir); - else - IMGUI_DEBUG_LOG_DOCKING("[docking] DockContextProcessDock node 0x%08X, split_dir %d\n", node ? node->ID : 0, req->DockSplitDir); - - // Decide which Tab will be selected at the end of the operation - ImGuiID next_selected_id = 0; - ImGuiDockNode* payload_node = NULL; - if (payload_window) - { - payload_node = payload_window->DockNodeAsHost; - payload_window->DockNodeAsHost = NULL; // Important to clear this as the node will have its life as a child which might be merged/deleted later. - if (payload_node && payload_node->IsLeafNode()) - next_selected_id = payload_node->TabBar->NextSelectedTabId ? payload_node->TabBar->NextSelectedTabId : payload_node->TabBar->SelectedTabId; - if (payload_node == NULL) - next_selected_id = payload_window->TabId; - } - - // FIXME-DOCK: When we are trying to dock an existing single-window node into a loose window, transfer Node ID as well - // When processing an interactive split, usually LastFrameAlive will be < g.FrameCount. But DockBuilder operations can make it ==. - if (node) - IM_ASSERT(node->LastFrameAlive <= g.FrameCount); - if (node && target_window && node == target_window->DockNodeAsHost) - IM_ASSERT(node->Windows.Size > 0 || node->IsSplitNode() || node->IsCentralNode()); - - // Create new node and add existing window to it - if (node == NULL) - { - node = DockContextAddNode(ctx, 0); - node->Pos = target_window->Pos; - node->Size = target_window->Size; - if (target_window->DockNodeAsHost == NULL) - { - DockNodeAddWindow(node, target_window, true); - node->TabBar->Tabs[0].Flags &= ~ImGuiTabItemFlags_Unsorted; - target_window->DockIsActive = true; - } - } - - ImGuiDir split_dir = req->DockSplitDir; - if (split_dir != ImGuiDir_None) - { - // Split into two, one side will be our payload node unless we are dropping a loose window - const ImGuiAxis split_axis = (split_dir == ImGuiDir_Left || split_dir == ImGuiDir_Right) ? ImGuiAxis_X : ImGuiAxis_Y; - const int split_inheritor_child_idx = (split_dir == ImGuiDir_Left || split_dir == ImGuiDir_Up) ? 1 : 0; // Current contents will be moved to the opposite side - const float split_ratio = req->DockSplitRatio; - DockNodeTreeSplit(ctx, node, split_axis, split_inheritor_child_idx, split_ratio, payload_node); // payload_node may be NULL here! - ImGuiDockNode* new_node = node->ChildNodes[split_inheritor_child_idx ^ 1]; - new_node->HostWindow = node->HostWindow; - node = new_node; - } - node->SetLocalFlags(node->LocalFlags & ~ImGuiDockNodeFlags_HiddenTabBar); - - if (node != payload_node) - { - // Create tab bar before we call DockNodeMoveWindows (which would attempt to move the old tab-bar, which would lead us to payload tabs wrongly appearing before target tabs!) - if (node->Windows.Size > 0 && node->TabBar == NULL) - { - DockNodeAddTabBar(node); - for (int n = 0; n < node->Windows.Size; n++) - TabBarAddTab(node->TabBar, ImGuiTabItemFlags_None, node->Windows[n]); - } - - if (payload_node != NULL) - { - // Transfer full payload node (with 1+ child windows or child nodes) - if (payload_node->IsSplitNode()) - { - if (node->Windows.Size > 0) - { - // We can dock a split payload into a node that already has windows _only_ if our payload is a node tree with a single visible node. - // In this situation, we move the windows of the target node into the currently visible node of the payload. - // This allows us to preserve some of the underlying dock tree settings nicely. - IM_ASSERT(payload_node->OnlyNodeWithWindows != NULL); // The docking should have been blocked by DockNodePreviewDockSetup() early on and never submitted. - ImGuiDockNode* visible_node = payload_node->OnlyNodeWithWindows; - if (visible_node->TabBar) - IM_ASSERT(visible_node->TabBar->Tabs.Size > 0); - DockNodeMoveWindows(node, visible_node); - DockNodeMoveWindows(visible_node, node); - DockSettingsRenameNodeReferences(node->ID, visible_node->ID); - } - if (node->IsCentralNode()) - { - // Central node property needs to be moved to a leaf node, pick the last focused one. - // FIXME-DOCK: If we had to transfer other flags here, what would the policy be? - ImGuiDockNode* last_focused_node = DockContextFindNodeByID(ctx, payload_node->LastFocusedNodeId); - IM_ASSERT(last_focused_node != NULL); - ImGuiDockNode* last_focused_root_node = DockNodeGetRootNode(last_focused_node); - IM_ASSERT(last_focused_root_node == DockNodeGetRootNode(payload_node)); - last_focused_node->SetLocalFlags(last_focused_node->LocalFlags | ImGuiDockNodeFlags_CentralNode); - node->SetLocalFlags(node->LocalFlags & ~ImGuiDockNodeFlags_CentralNode); - last_focused_root_node->CentralNode = last_focused_node; - } - - IM_ASSERT(node->Windows.Size == 0); - DockNodeMoveChildNodes(node, payload_node); - } - else - { - const ImGuiID payload_dock_id = payload_node->ID; - DockNodeMoveWindows(node, payload_node); - DockSettingsRenameNodeReferences(payload_dock_id, node->ID); - } - DockContextRemoveNode(ctx, payload_node, true); - } - else if (payload_window) - { - // Transfer single window - const ImGuiID payload_dock_id = payload_window->DockId; - node->VisibleWindow = payload_window; - DockNodeAddWindow(node, payload_window, true); - if (payload_dock_id != 0) - DockSettingsRenameNodeReferences(payload_dock_id, node->ID); - } - } - else - { - // When docking a floating single window node we want to reevaluate auto-hiding of the tab bar - node->WantHiddenTabBarUpdate = true; - } - - // Update selection immediately - if (ImGuiTabBar* tab_bar = node->TabBar) - tab_bar->NextSelectedTabId = next_selected_id; - MarkIniSettingsDirty(); -} - -// Problem: -// Undocking a large (~full screen) window would leave it so large that the bottom right sizing corner would more -// than likely be off the screen and the window would be hard to resize to fit on screen. This can be particularly problematic -// with 'ConfigWindowsMoveFromTitleBarOnly=true' and/or with 'ConfigWindowsResizeFromEdges=false' as well (the later can be -// due to missing ImGuiBackendFlags_HasMouseCursors backend flag). -// Solution: -// When undocking a window we currently force its maximum size to 90% of the host viewport or monitor. -// Reevaluate this when we implement preserving docked/undocked size ("docking_wip/undocked_size" branch). -static ImVec2 FixLargeWindowsWhenUndocking(const ImVec2& size, ImGuiViewport* ref_viewport) -{ - if (ref_viewport == NULL) - return size; - - ImGuiContext& g = *GImGui; - ImVec2 max_size = ImTrunc(ref_viewport->WorkSize * 0.90f); - if (g.ConfigFlagsCurrFrame & ImGuiConfigFlags_ViewportsEnable) - { - const ImGuiPlatformMonitor* monitor = ImGui::GetViewportPlatformMonitor(ref_viewport); - max_size = ImTrunc(monitor->WorkSize * 0.90f); - } - return ImMin(size, max_size); -} - -void ImGui::DockContextProcessUndockWindow(ImGuiContext* ctx, ImGuiWindow* window, bool clear_persistent_docking_ref) -{ - ImGuiContext& g = *ctx; - IMGUI_DEBUG_LOG_DOCKING("[docking] DockContextProcessUndockWindow window '%s', clear_persistent_docking_ref = %d\n", window->Name, clear_persistent_docking_ref); - if (window->DockNode) - DockNodeRemoveWindow(window->DockNode, window, clear_persistent_docking_ref ? 0 : window->DockId); - else - window->DockId = 0; - window->Collapsed = false; - window->DockIsActive = false; - window->DockNodeIsVisible = window->DockTabIsVisible = false; - window->Size = window->SizeFull = FixLargeWindowsWhenUndocking(window->SizeFull, window->Viewport); - - MarkIniSettingsDirty(); -} - -void ImGui::DockContextProcessUndockNode(ImGuiContext* ctx, ImGuiDockNode* node) -{ - ImGuiContext& g = *ctx; - IMGUI_DEBUG_LOG_DOCKING("[docking] DockContextProcessUndockNode node %08X\n", node->ID); - IM_ASSERT(node->IsLeafNode()); - IM_ASSERT(node->Windows.Size >= 1); - - if (node->IsRootNode() || node->IsCentralNode()) - { - // In the case of a root node or central node, the node will have to stay in place. Create a new node to receive the payload. - ImGuiDockNode* new_node = DockContextAddNode(ctx, 0); - new_node->Pos = node->Pos; - new_node->Size = node->Size; - new_node->SizeRef = node->SizeRef; - DockNodeMoveWindows(new_node, node); - DockSettingsRenameNodeReferences(node->ID, new_node->ID); - node = new_node; - } - else - { - // Otherwise extract our node and merge our sibling back into the parent node. - IM_ASSERT(node->ParentNode->ChildNodes[0] == node || node->ParentNode->ChildNodes[1] == node); - int index_in_parent = (node->ParentNode->ChildNodes[0] == node) ? 0 : 1; - node->ParentNode->ChildNodes[index_in_parent] = NULL; - DockNodeTreeMerge(ctx, node->ParentNode, node->ParentNode->ChildNodes[index_in_parent ^ 1]); - node->ParentNode->AuthorityForViewport = ImGuiDataAuthority_Window; // The node that stays in place keeps the viewport, so our newly dragged out node will create a new viewport - node->ParentNode = NULL; - } - for (ImGuiWindow* window : node->Windows) - { - window->Flags &= ~ImGuiWindowFlags_ChildWindow; - if (window->ParentWindow) - window->ParentWindow->DC.ChildWindows.find_erase(window); - UpdateWindowParentAndRootLinks(window, window->Flags, NULL); - } - node->AuthorityForPos = node->AuthorityForSize = ImGuiDataAuthority_DockNode; - node->Size = FixLargeWindowsWhenUndocking(node->Size, node->Windows[0]->Viewport); - node->WantMouseMove = true; - MarkIniSettingsDirty(); -} - -// This is mostly used for automation. -bool ImGui::DockContextCalcDropPosForDocking(ImGuiWindow* target, ImGuiDockNode* target_node, ImGuiWindow* payload_window, ImGuiDockNode* payload_node, ImGuiDir split_dir, bool split_outer, ImVec2* out_pos) -{ - if (target != NULL && target_node == NULL) - target_node = target->DockNode; - - // In DockNodePreviewDockSetup() for a root central node instead of showing both "inner" and "outer" drop rects - // (which would be functionally identical) we only show the outer one. Reflect this here. - if (target_node && target_node->ParentNode == NULL && target_node->IsCentralNode() && split_dir != ImGuiDir_None) - split_outer = true; - ImGuiDockPreviewData split_data; - DockNodePreviewDockSetup(target, target_node, payload_window, payload_node, &split_data, false, split_outer); - if (split_data.DropRectsDraw[split_dir+1].IsInverted()) - return false; - *out_pos = split_data.DropRectsDraw[split_dir+1].GetCenter(); - return true; -} - -//----------------------------------------------------------------------------- -// Docking: ImGuiDockNode -//----------------------------------------------------------------------------- -// - DockNodeGetTabOrder() -// - DockNodeAddWindow() -// - DockNodeRemoveWindow() -// - DockNodeMoveChildNodes() -// - DockNodeMoveWindows() -// - DockNodeApplyPosSizeToWindows() -// - DockNodeHideHostWindow() -// - ImGuiDockNodeFindInfoResults -// - DockNodeFindInfo() -// - DockNodeFindWindowByID() -// - DockNodeUpdateFlagsAndCollapse() -// - DockNodeUpdateHasCentralNodeFlag() -// - DockNodeUpdateVisibleFlag() -// - DockNodeStartMouseMovingWindow() -// - DockNodeUpdate() -// - DockNodeUpdateWindowMenu() -// - DockNodeBeginAmendTabBar() -// - DockNodeEndAmendTabBar() -// - DockNodeUpdateTabBar() -// - DockNodeAddTabBar() -// - DockNodeRemoveTabBar() -// - DockNodeIsDropAllowedOne() -// - DockNodeIsDropAllowed() -// - DockNodeCalcTabBarLayout() -// - DockNodeCalcSplitRects() -// - DockNodeCalcDropRectsAndTestMousePos() -// - DockNodePreviewDockSetup() -// - DockNodePreviewDockRender() -//----------------------------------------------------------------------------- - -ImGuiDockNode::ImGuiDockNode(ImGuiID id) -{ - ID = id; - SharedFlags = LocalFlags = LocalFlagsInWindows = MergedFlags = ImGuiDockNodeFlags_None; - ParentNode = ChildNodes[0] = ChildNodes[1] = NULL; - TabBar = NULL; - SplitAxis = ImGuiAxis_None; - - State = ImGuiDockNodeState_Unknown; - LastBgColor = IM_COL32_WHITE; - HostWindow = VisibleWindow = NULL; - CentralNode = OnlyNodeWithWindows = NULL; - CountNodeWithWindows = 0; - LastFrameAlive = LastFrameActive = LastFrameFocused = -1; - LastFocusedNodeId = 0; - SelectedTabId = 0; - WantCloseTabId = 0; - RefViewportId = 0; - AuthorityForPos = AuthorityForSize = ImGuiDataAuthority_DockNode; - AuthorityForViewport = ImGuiDataAuthority_Auto; - IsVisible = true; - IsFocused = HasCloseButton = HasWindowMenuButton = HasCentralNodeChild = false; - IsBgDrawnThisFrame = false; - WantCloseAll = WantLockSizeOnce = WantMouseMove = WantHiddenTabBarUpdate = WantHiddenTabBarToggle = false; -} - -ImGuiDockNode::~ImGuiDockNode() -{ - IM_DELETE(TabBar); - TabBar = NULL; - ChildNodes[0] = ChildNodes[1] = NULL; -} - -int ImGui::DockNodeGetTabOrder(ImGuiWindow* window) -{ - ImGuiTabBar* tab_bar = window->DockNode->TabBar; - if (tab_bar == NULL) - return -1; - ImGuiTabItem* tab = TabBarFindTabByID(tab_bar, window->TabId); - return tab ? TabBarGetTabOrder(tab_bar, tab) : -1; -} - -static void DockNodeHideWindowDuringHostWindowCreation(ImGuiWindow* window) -{ - window->Hidden = true; - window->HiddenFramesCanSkipItems = window->Active ? 1 : 2; -} - -static void ImGui::DockNodeAddWindow(ImGuiDockNode* node, ImGuiWindow* window, bool add_to_tab_bar) -{ - ImGuiContext& g = *GImGui; (void)g; - if (window->DockNode) - { - // Can overwrite an existing window->DockNode (e.g. pointing to a disabled DockSpace node) - IM_ASSERT(window->DockNode->ID != node->ID); - DockNodeRemoveWindow(window->DockNode, window, 0); - } - IM_ASSERT(window->DockNode == NULL || window->DockNodeAsHost == NULL); - IMGUI_DEBUG_LOG_DOCKING("[docking] DockNodeAddWindow node 0x%08X window '%s'\n", node->ID, window->Name); - - // If more than 2 windows appeared on the same frame leading to the creation of a new hosting window, - // we'll hide windows until the host window is ready. Hide the 1st window after its been output (so it is not visible for one frame). - // We will call DockNodeHideWindowDuringHostWindowCreation() on ourselves in Begin() - if (node->HostWindow == NULL && node->Windows.Size == 1 && node->Windows[0]->WasActive == false) - DockNodeHideWindowDuringHostWindowCreation(node->Windows[0]); - - node->Windows.push_back(window); - node->WantHiddenTabBarUpdate = true; - window->DockNode = node; - window->DockId = node->ID; - window->DockIsActive = (node->Windows.Size > 1); - window->DockTabWantClose = false; - - // When reactivating a node with one or two loose window, the window pos/size/viewport are authoritative over the node storage. - // In particular it is important we init the viewport from the first window so we don't create two viewports and drop one. - if (node->HostWindow == NULL && node->IsFloatingNode()) - { - if (node->AuthorityForPos == ImGuiDataAuthority_Auto) - node->AuthorityForPos = ImGuiDataAuthority_Window; - if (node->AuthorityForSize == ImGuiDataAuthority_Auto) - node->AuthorityForSize = ImGuiDataAuthority_Window; - if (node->AuthorityForViewport == ImGuiDataAuthority_Auto) - node->AuthorityForViewport = ImGuiDataAuthority_Window; - } - - // Add to tab bar if requested - if (add_to_tab_bar) - { - if (node->TabBar == NULL) - { - DockNodeAddTabBar(node); - node->TabBar->SelectedTabId = node->TabBar->NextSelectedTabId = node->SelectedTabId; - - // Add existing windows - for (int n = 0; n < node->Windows.Size - 1; n++) - TabBarAddTab(node->TabBar, ImGuiTabItemFlags_None, node->Windows[n]); - } - TabBarAddTab(node->TabBar, ImGuiTabItemFlags_Unsorted, window); - } - - DockNodeUpdateVisibleFlag(node); - - // Update this without waiting for the next time we Begin() in the window, so our host window will have the proper title bar color on its first frame. - if (node->HostWindow) - UpdateWindowParentAndRootLinks(window, window->Flags | ImGuiWindowFlags_ChildWindow, node->HostWindow); -} - -static void ImGui::DockNodeRemoveWindow(ImGuiDockNode* node, ImGuiWindow* window, ImGuiID save_dock_id) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(window->DockNode == node); - //IM_ASSERT(window->RootWindowDockTree == node->HostWindow); - //IM_ASSERT(window->LastFrameActive < g.FrameCount); // We may call this from Begin() - IM_ASSERT(save_dock_id == 0 || save_dock_id == node->ID); - IMGUI_DEBUG_LOG_DOCKING("[docking] DockNodeRemoveWindow node 0x%08X window '%s'\n", node->ID, window->Name); - - window->DockNode = NULL; - window->DockIsActive = window->DockTabWantClose = false; - window->DockId = save_dock_id; - window->Flags &= ~ImGuiWindowFlags_ChildWindow; - if (window->ParentWindow) - window->ParentWindow->DC.ChildWindows.find_erase(window); - UpdateWindowParentAndRootLinks(window, window->Flags, NULL); // Update immediately - - if (node->HostWindow && node->HostWindow->ViewportOwned) - { - // When undocking from a user interaction this will always run in NewFrame() and have not much effect. - // But mid-frame, if we clear viewport we need to mark window as hidden as well. - window->Viewport = NULL; - window->ViewportId = 0; - window->ViewportOwned = false; - window->Hidden = true; - } - - // Remove window - bool erased = false; - for (int n = 0; n < node->Windows.Size; n++) - if (node->Windows[n] == window) - { - node->Windows.erase(node->Windows.Data + n); - erased = true; - break; - } - if (!erased) - IM_ASSERT(erased); - if (node->VisibleWindow == window) - node->VisibleWindow = NULL; - - // Remove tab and possibly tab bar - node->WantHiddenTabBarUpdate = true; - if (node->TabBar) - { - TabBarRemoveTab(node->TabBar, window->TabId); - const int tab_count_threshold_for_tab_bar = node->IsCentralNode() ? 1 : 2; - if (node->Windows.Size < tab_count_threshold_for_tab_bar) - DockNodeRemoveTabBar(node); - } - - if (node->Windows.Size == 0 && !node->IsCentralNode() && !node->IsDockSpace() && window->DockId != node->ID) - { - // Automatic dock node delete themselves if they are not holding at least one tab - DockContextRemoveNode(&g, node, true); - return; - } - - if (node->Windows.Size == 1 && !node->IsCentralNode() && node->HostWindow) - { - ImGuiWindow* remaining_window = node->Windows[0]; - // Note: we used to transport viewport ownership here. - remaining_window->Collapsed = node->HostWindow->Collapsed; - } - - // Update visibility immediately is required so the DockNodeUpdateRemoveInactiveChilds() processing can reflect changes up the tree - DockNodeUpdateVisibleFlag(node); -} - -static void ImGui::DockNodeMoveChildNodes(ImGuiDockNode* dst_node, ImGuiDockNode* src_node) -{ - IM_ASSERT(dst_node->Windows.Size == 0); - dst_node->ChildNodes[0] = src_node->ChildNodes[0]; - dst_node->ChildNodes[1] = src_node->ChildNodes[1]; - if (dst_node->ChildNodes[0]) - dst_node->ChildNodes[0]->ParentNode = dst_node; - if (dst_node->ChildNodes[1]) - dst_node->ChildNodes[1]->ParentNode = dst_node; - dst_node->SplitAxis = src_node->SplitAxis; - dst_node->SizeRef = src_node->SizeRef; - src_node->ChildNodes[0] = src_node->ChildNodes[1] = NULL; -} - -static void ImGui::DockNodeMoveWindows(ImGuiDockNode* dst_node, ImGuiDockNode* src_node) -{ - // Insert tabs in the same orders as currently ordered (node->Windows isn't ordered) - IM_ASSERT(src_node && dst_node && dst_node != src_node); - ImGuiTabBar* src_tab_bar = src_node->TabBar; - if (src_tab_bar != NULL) - IM_ASSERT(src_node->Windows.Size <= src_node->TabBar->Tabs.Size); - - // If the dst_node is empty we can just move the entire tab bar (to preserve selection, scrolling, etc.) - bool move_tab_bar = (src_tab_bar != NULL) && (dst_node->TabBar == NULL); - if (move_tab_bar) - { - dst_node->TabBar = src_node->TabBar; - src_node->TabBar = NULL; - } - - // Tab order is not important here, it is preserved by sorting in DockNodeUpdateTabBar(). - for (ImGuiWindow* window : src_node->Windows) - { - window->DockNode = NULL; - window->DockIsActive = false; - DockNodeAddWindow(dst_node, window, !move_tab_bar); - } - src_node->Windows.clear(); - - if (!move_tab_bar && src_node->TabBar) - { - if (dst_node->TabBar) - dst_node->TabBar->SelectedTabId = src_node->TabBar->SelectedTabId; - DockNodeRemoveTabBar(src_node); - } -} - -static void ImGui::DockNodeApplyPosSizeToWindows(ImGuiDockNode* node) -{ - for (ImGuiWindow* window : node->Windows) - { - SetWindowPos(window, node->Pos, ImGuiCond_Always); // We don't assign directly to Pos because it can break the calculation of SizeContents on next frame - SetWindowSize(window, node->Size, ImGuiCond_Always); - } -} - -static void ImGui::DockNodeHideHostWindow(ImGuiDockNode* node) -{ - if (node->HostWindow) - { - if (node->HostWindow->DockNodeAsHost == node) - node->HostWindow->DockNodeAsHost = NULL; - node->HostWindow = NULL; - } - - if (node->Windows.Size == 1) - { - node->VisibleWindow = node->Windows[0]; - node->Windows[0]->DockIsActive = false; - } - - if (node->TabBar) - DockNodeRemoveTabBar(node); -} - -// Search function called once by root node in DockNodeUpdate() -struct ImGuiDockNodeTreeInfo -{ - ImGuiDockNode* CentralNode; - ImGuiDockNode* FirstNodeWithWindows; - int CountNodesWithWindows; - //ImGuiWindowClass WindowClassForMerges; - - ImGuiDockNodeTreeInfo() { memset(this, 0, sizeof(*this)); } -}; - -static void DockNodeFindInfo(ImGuiDockNode* node, ImGuiDockNodeTreeInfo* info) -{ - if (node->Windows.Size > 0) - { - if (info->FirstNodeWithWindows == NULL) - info->FirstNodeWithWindows = node; - info->CountNodesWithWindows++; - } - if (node->IsCentralNode()) - { - IM_ASSERT(info->CentralNode == NULL); // Should be only one - IM_ASSERT(node->IsLeafNode() && "If you get this assert: please submit .ini file + repro of actions leading to this."); - info->CentralNode = node; - } - if (info->CountNodesWithWindows > 1 && info->CentralNode != NULL) - return; - if (node->ChildNodes[0]) - DockNodeFindInfo(node->ChildNodes[0], info); - if (node->ChildNodes[1]) - DockNodeFindInfo(node->ChildNodes[1], info); -} - -static ImGuiWindow* ImGui::DockNodeFindWindowByID(ImGuiDockNode* node, ImGuiID id) -{ - IM_ASSERT(id != 0); - for (ImGuiWindow* window : node->Windows) - if (window->ID == id) - return window; - return NULL; -} - -// - Remove inactive windows/nodes. -// - Update visibility flag. -static void ImGui::DockNodeUpdateFlagsAndCollapse(ImGuiDockNode* node) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(node->ParentNode == NULL || node->ParentNode->ChildNodes[0] == node || node->ParentNode->ChildNodes[1] == node); - - // Inherit most flags - if (node->ParentNode) - node->SharedFlags = node->ParentNode->SharedFlags & ImGuiDockNodeFlags_SharedFlagsInheritMask_; - - // Recurse into children - // There is the possibility that one of our child becoming empty will delete itself and moving its sibling contents into 'node'. - // If 'node->ChildNode[0]' delete itself, then 'node->ChildNode[1]->Windows' will be moved into 'node' - // If 'node->ChildNode[1]' delete itself, then 'node->ChildNode[0]->Windows' will be moved into 'node' and the "remove inactive windows" loop will have run twice on those windows (harmless) - node->HasCentralNodeChild = false; - if (node->ChildNodes[0]) - DockNodeUpdateFlagsAndCollapse(node->ChildNodes[0]); - if (node->ChildNodes[1]) - DockNodeUpdateFlagsAndCollapse(node->ChildNodes[1]); - - // Remove inactive windows, collapse nodes - // Merge node flags overrides stored in windows - node->LocalFlagsInWindows = ImGuiDockNodeFlags_None; - for (int window_n = 0; window_n < node->Windows.Size; window_n++) - { - ImGuiWindow* window = node->Windows[window_n]; - IM_ASSERT(window->DockNode == node); - - bool node_was_active = (node->LastFrameActive + 1 == g.FrameCount); - bool remove = false; - remove |= node_was_active && (window->LastFrameActive + 1 < g.FrameCount); - remove |= node_was_active && (node->WantCloseAll || node->WantCloseTabId == window->TabId) && window->HasCloseButton && !(window->Flags & ImGuiWindowFlags_UnsavedDocument); // Submit all _expected_ closure from last frame - remove |= (window->DockTabWantClose); - if (remove) - { - window->DockTabWantClose = false; - if (node->Windows.Size == 1 && !node->IsCentralNode()) - { - DockNodeHideHostWindow(node); - node->State = ImGuiDockNodeState_HostWindowHiddenBecauseSingleWindow; - DockNodeRemoveWindow(node, window, node->ID); // Will delete the node so it'll be invalid on return - return; - } - DockNodeRemoveWindow(node, window, node->ID); - window_n--; - continue; - } - - // FIXME-DOCKING: Missing policies for conflict resolution, hence the "Experimental" tag on this. - //node->LocalFlagsInWindow &= ~window->WindowClass.DockNodeFlagsOverrideClear; - node->LocalFlagsInWindows |= window->WindowClass.DockNodeFlagsOverrideSet; - } - node->UpdateMergedFlags(); - - // Auto-hide tab bar option - ImGuiDockNodeFlags node_flags = node->MergedFlags; - if (node->WantHiddenTabBarUpdate && node->Windows.Size == 1 && (node_flags & ImGuiDockNodeFlags_AutoHideTabBar) && !node->IsHiddenTabBar()) - node->WantHiddenTabBarToggle = true; - node->WantHiddenTabBarUpdate = false; - - // Cancel toggling if we know our tab bar is enforced to be hidden at all times - if (node->WantHiddenTabBarToggle && node->VisibleWindow && (node->VisibleWindow->WindowClass.DockNodeFlagsOverrideSet & ImGuiDockNodeFlags_HiddenTabBar)) - node->WantHiddenTabBarToggle = false; - - // Apply toggles at a single point of the frame (here!) - if (node->Windows.Size > 1) - node->SetLocalFlags(node->LocalFlags & ~ImGuiDockNodeFlags_HiddenTabBar); - else if (node->WantHiddenTabBarToggle) - node->SetLocalFlags(node->LocalFlags ^ ImGuiDockNodeFlags_HiddenTabBar); - node->WantHiddenTabBarToggle = false; - - DockNodeUpdateVisibleFlag(node); -} - -// This is rarely called as DockNodeUpdateForRootNode() generally does it most frames. -static void ImGui::DockNodeUpdateHasCentralNodeChild(ImGuiDockNode* node) -{ - node->HasCentralNodeChild = false; - if (node->ChildNodes[0]) - DockNodeUpdateHasCentralNodeChild(node->ChildNodes[0]); - if (node->ChildNodes[1]) - DockNodeUpdateHasCentralNodeChild(node->ChildNodes[1]); - if (node->IsRootNode()) - { - ImGuiDockNode* mark_node = node->CentralNode; - while (mark_node) - { - mark_node->HasCentralNodeChild = true; - mark_node = mark_node->ParentNode; - } - } -} - -static void ImGui::DockNodeUpdateVisibleFlag(ImGuiDockNode* node) -{ - // Update visibility flag - bool is_visible = (node->ParentNode == NULL) ? node->IsDockSpace() : node->IsCentralNode(); - is_visible |= (node->Windows.Size > 0); - is_visible |= (node->ChildNodes[0] && node->ChildNodes[0]->IsVisible); - is_visible |= (node->ChildNodes[1] && node->ChildNodes[1]->IsVisible); - node->IsVisible = is_visible; -} - -static void ImGui::DockNodeStartMouseMovingWindow(ImGuiDockNode* node, ImGuiWindow* window) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(node->WantMouseMove == true); - StartMouseMovingWindow(window); - g.ActiveIdClickOffset = g.IO.MouseClickedPos[0] - node->Pos; - g.MovingWindow = window; // If we are docked into a non moveable root window, StartMouseMovingWindow() won't set g.MovingWindow. Override that decision. - node->WantMouseMove = false; -} - -// Update CentralNode, OnlyNodeWithWindows, LastFocusedNodeID. Copy window class. -static void ImGui::DockNodeUpdateForRootNode(ImGuiDockNode* node) -{ - DockNodeUpdateFlagsAndCollapse(node); - - // - Setup central node pointers - // - Find if there's only a single visible window in the hierarchy (in which case we need to display a regular title bar -> FIXME-DOCK: that last part is not done yet!) - // Cannot merge this with DockNodeUpdateFlagsAndCollapse() because FirstNodeWithWindows is found after window removal and child collapsing - ImGuiDockNodeTreeInfo info; - DockNodeFindInfo(node, &info); - node->CentralNode = info.CentralNode; - node->OnlyNodeWithWindows = (info.CountNodesWithWindows == 1) ? info.FirstNodeWithWindows : NULL; - node->CountNodeWithWindows = info.CountNodesWithWindows; - if (node->LastFocusedNodeId == 0 && info.FirstNodeWithWindows != NULL) - node->LastFocusedNodeId = info.FirstNodeWithWindows->ID; - - // Copy the window class from of our first window so it can be used for proper dock filtering. - // When node has mixed windows, prioritize the class with the most constraint (DockingAllowUnclassed = false) as the reference to copy. - // FIXME-DOCK: We don't recurse properly, this code could be reworked to work from DockNodeUpdateScanRec. - if (ImGuiDockNode* first_node_with_windows = info.FirstNodeWithWindows) - { - node->WindowClass = first_node_with_windows->Windows[0]->WindowClass; - for (int n = 1; n < first_node_with_windows->Windows.Size; n++) - if (first_node_with_windows->Windows[n]->WindowClass.DockingAllowUnclassed == false) - { - node->WindowClass = first_node_with_windows->Windows[n]->WindowClass; - break; - } - } - - ImGuiDockNode* mark_node = node->CentralNode; - while (mark_node) - { - mark_node->HasCentralNodeChild = true; - mark_node = mark_node->ParentNode; - } -} - -static void DockNodeSetupHostWindow(ImGuiDockNode* node, ImGuiWindow* host_window) -{ - // Remove ourselves from any previous different host window - // This can happen if a user mistakenly does (see #4295 for details): - // - N+0: DockBuilderAddNode(id, 0) // missing ImGuiDockNodeFlags_DockSpace - // - N+1: NewFrame() // will create floating host window for that node - // - N+1: DockSpace(id) // requalify node as dockspace, moving host window - if (node->HostWindow && node->HostWindow != host_window && node->HostWindow->DockNodeAsHost == node) - node->HostWindow->DockNodeAsHost = NULL; - - host_window->DockNodeAsHost = node; - node->HostWindow = host_window; -} - -static void ImGui::DockNodeUpdate(ImGuiDockNode* node) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(node->LastFrameActive != g.FrameCount); - node->LastFrameAlive = g.FrameCount; - node->IsBgDrawnThisFrame = false; - - node->CentralNode = node->OnlyNodeWithWindows = NULL; - if (node->IsRootNode()) - DockNodeUpdateForRootNode(node); - - // Remove tab bar if not needed - if (node->TabBar && node->IsNoTabBar()) - DockNodeRemoveTabBar(node); - - // Early out for hidden root dock nodes (when all DockId references are in inactive windows, or there is only 1 floating window holding on the DockId) - bool want_to_hide_host_window = false; - if (node->IsFloatingNode()) - { - if (node->Windows.Size <= 1 && node->IsLeafNode()) - if (!g.IO.ConfigDockingAlwaysTabBar && (node->Windows.Size == 0 || !node->Windows[0]->WindowClass.DockingAlwaysTabBar)) - want_to_hide_host_window = true; - if (node->CountNodeWithWindows == 0) - want_to_hide_host_window = true; - } - if (want_to_hide_host_window) - { - if (node->Windows.Size == 1) - { - // Floating window pos/size is authoritative - ImGuiWindow* single_window = node->Windows[0]; - node->Pos = single_window->Pos; - node->Size = single_window->SizeFull; - node->AuthorityForPos = node->AuthorityForSize = node->AuthorityForViewport = ImGuiDataAuthority_Window; - - // Transfer focus immediately so when we revert to a regular window it is immediately selected - if (node->HostWindow && g.NavWindow == node->HostWindow) - FocusWindow(single_window); - if (node->HostWindow) - { - IMGUI_DEBUG_LOG_VIEWPORT("[viewport] Node %08X transfer Viewport %08X->%08X to Window '%s'\n", node->ID, node->HostWindow->Viewport->ID, single_window->ID, single_window->Name); - single_window->Viewport = node->HostWindow->Viewport; - single_window->ViewportId = node->HostWindow->ViewportId; - if (node->HostWindow->ViewportOwned) - { - single_window->Viewport->ID = single_window->ID; - single_window->Viewport->Window = single_window; - single_window->ViewportOwned = true; - } - } - node->RefViewportId = single_window->ViewportId; - } - - DockNodeHideHostWindow(node); - node->State = ImGuiDockNodeState_HostWindowHiddenBecauseSingleWindow; - node->WantCloseAll = false; - node->WantCloseTabId = 0; - node->HasCloseButton = node->HasWindowMenuButton = false; - node->LastFrameActive = g.FrameCount; - - if (node->WantMouseMove && node->Windows.Size == 1) - DockNodeStartMouseMovingWindow(node, node->Windows[0]); - return; - } - - // In some circumstance we will defer creating the host window (so everything will be kept hidden), - // while the expected visible window is resizing itself. - // This is important for first-time (no ini settings restored) single window when io.ConfigDockingAlwaysTabBar is enabled, - // otherwise the node ends up using the minimum window size. Effectively those windows will take an extra frame to show up: - // N+0: Begin(): window created (with no known size), node is created - // N+1: DockNodeUpdate(): node skip creating host window / Begin(): window size applied, not visible - // N+2: DockNodeUpdate(): node can create host window / Begin(): window becomes visible - // We could remove this frame if we could reliably calculate the expected window size during node update, before the Begin() code. - // It would require a generalization of CalcWindowExpectedSize(), probably extracting code away from Begin(). - // In reality it isn't very important as user quickly ends up with size data in .ini file. - if (node->IsVisible && node->HostWindow == NULL && node->IsFloatingNode() && node->IsLeafNode()) - { - IM_ASSERT(node->Windows.Size > 0); - ImGuiWindow* ref_window = NULL; - if (node->SelectedTabId != 0) // Note that we prune single-window-node settings on .ini loading, so this is generally 0 for them! - ref_window = DockNodeFindWindowByID(node, node->SelectedTabId); - if (ref_window == NULL) - ref_window = node->Windows[0]; - if (ref_window->AutoFitFramesX > 0 || ref_window->AutoFitFramesY > 0) - { - node->State = ImGuiDockNodeState_HostWindowHiddenBecauseWindowsAreResizing; - return; - } - } - - const ImGuiDockNodeFlags node_flags = node->MergedFlags; - - // Decide if the node will have a close button and a window menu button - node->HasWindowMenuButton = (node->Windows.Size > 0) && (node_flags & ImGuiDockNodeFlags_NoWindowMenuButton) == 0; - node->HasCloseButton = false; - for (ImGuiWindow* window : node->Windows) - { - // FIXME-DOCK: Setting DockIsActive here means that for single active window in a leaf node, DockIsActive will be cleared until the next Begin() call. - node->HasCloseButton |= window->HasCloseButton; - window->DockIsActive = (node->Windows.Size > 1); - } - if (node_flags & ImGuiDockNodeFlags_NoCloseButton) - node->HasCloseButton = false; - - // Bind or create host window - ImGuiWindow* host_window = NULL; - bool beginned_into_host_window = false; - if (node->IsDockSpace()) - { - // [Explicit root dockspace node] - IM_ASSERT(node->HostWindow); - host_window = node->HostWindow; - } - else - { - // [Automatic root or child nodes] - if (node->IsRootNode() && node->IsVisible) - { - ImGuiWindow* ref_window = (node->Windows.Size > 0) ? node->Windows[0] : NULL; - - // Sync Pos - if (node->AuthorityForPos == ImGuiDataAuthority_Window && ref_window) - SetNextWindowPos(ref_window->Pos); - else if (node->AuthorityForPos == ImGuiDataAuthority_DockNode) - SetNextWindowPos(node->Pos); - - // Sync Size - if (node->AuthorityForSize == ImGuiDataAuthority_Window && ref_window) - SetNextWindowSize(ref_window->SizeFull); - else if (node->AuthorityForSize == ImGuiDataAuthority_DockNode) - SetNextWindowSize(node->Size); - - // Sync Collapsed - if (node->AuthorityForSize == ImGuiDataAuthority_Window && ref_window) - SetNextWindowCollapsed(ref_window->Collapsed); - - // Sync Viewport - if (node->AuthorityForViewport == ImGuiDataAuthority_Window && ref_window) - SetNextWindowViewport(ref_window->ViewportId); - else if (node->AuthorityForViewport == ImGuiDataAuthority_Window && node->RefViewportId != 0) - SetNextWindowViewport(node->RefViewportId); - - SetNextWindowClass(&node->WindowClass); - - // Begin into the host window - char window_label[20]; - DockNodeGetHostWindowTitle(node, window_label, IM_ARRAYSIZE(window_label)); - ImGuiWindowFlags window_flags = ImGuiWindowFlags_NoScrollbar | ImGuiWindowFlags_NoScrollWithMouse | ImGuiWindowFlags_DockNodeHost; - window_flags |= ImGuiWindowFlags_NoFocusOnAppearing; - window_flags |= ImGuiWindowFlags_NoSavedSettings | ImGuiWindowFlags_NoNavFocus | ImGuiWindowFlags_NoCollapse; - window_flags |= ImGuiWindowFlags_NoTitleBar; - - SetNextWindowBgAlpha(0.0f); // Don't set ImGuiWindowFlags_NoBackground because it disables borders - PushStyleVar(ImGuiStyleVar_WindowPadding, ImVec2(0, 0)); - Begin(window_label, NULL, window_flags); - PopStyleVar(); - beginned_into_host_window = true; - - host_window = g.CurrentWindow; - DockNodeSetupHostWindow(node, host_window); - host_window->DC.CursorPos = host_window->Pos; - node->Pos = host_window->Pos; - node->Size = host_window->Size; - - // We set ImGuiWindowFlags_NoFocusOnAppearing because we don't want the host window to take full focus (e.g. steal NavWindow) - // But we still it bring it to the front of display. There's no way to choose this precise behavior via window flags. - // One simple case to ponder if: window A has a toggle to create windows B/C/D. Dock B/C/D together, clear the toggle and enable it again. - // When reappearing B/C/D will request focus and be moved to the top of the display pile, but they are not linked to the dock host window - // during the frame they appear. The dock host window would keep its old display order, and the sorting in EndFrame would move B/C/D back - // after the dock host window, losing their top-most status. - if (node->HostWindow->Appearing) - BringWindowToDisplayFront(node->HostWindow); - - node->AuthorityForPos = node->AuthorityForSize = node->AuthorityForViewport = ImGuiDataAuthority_Auto; - } - else if (node->ParentNode) - { - node->HostWindow = host_window = node->ParentNode->HostWindow; - node->AuthorityForPos = node->AuthorityForSize = node->AuthorityForViewport = ImGuiDataAuthority_Auto; - } - if (node->WantMouseMove && node->HostWindow) - DockNodeStartMouseMovingWindow(node, node->HostWindow); - } - node->RefViewportId = 0; // Clear when we have a host window - - // Update focused node (the one whose title bar is highlight) within a node tree - if (node->IsSplitNode()) - IM_ASSERT(node->TabBar == NULL); - if (node->IsRootNode()) - if (ImGuiWindow* p_window = g.NavWindow ? g.NavWindow->RootWindow : NULL) - while (p_window != NULL && p_window->DockNode != NULL) - { - ImGuiDockNode* p_node = DockNodeGetRootNode(p_window->DockNode); - if (p_node == node) - { - node->LastFocusedNodeId = p_window->DockNode->ID; // Note: not using root node ID! - break; - } - p_window = p_node->HostWindow ? p_node->HostWindow->RootWindow : NULL; - } - - // Register a hit-test hole in the window unless we are currently dragging a window that is compatible with our dockspace - ImGuiDockNode* central_node = node->CentralNode; - const bool central_node_hole = node->IsRootNode() && host_window && (node_flags & ImGuiDockNodeFlags_PassthruCentralNode) != 0 && central_node != NULL && central_node->IsEmpty(); - bool central_node_hole_register_hit_test_hole = central_node_hole; - if (central_node_hole) - if (const ImGuiPayload* payload = ImGui::GetDragDropPayload()) - if (payload->IsDataType(IMGUI_PAYLOAD_TYPE_WINDOW) && DockNodeIsDropAllowed(host_window, *(ImGuiWindow**)payload->Data)) - central_node_hole_register_hit_test_hole = false; - if (central_node_hole_register_hit_test_hole) - { - // We add a little padding to match the "resize from edges" behavior and allow grabbing the splitter easily. - // (But we only add it if there's something else on the other side of the hole, otherwise for e.g. fullscreen - // covering passthru node we'd have a gap on the edge not covered by the hole) - IM_ASSERT(node->IsDockSpace()); // We cannot pass this flag without the DockSpace() api. Testing this because we also setup the hole in host_window->ParentNode - ImGuiDockNode* root_node = DockNodeGetRootNode(central_node); - ImRect root_rect(root_node->Pos, root_node->Pos + root_node->Size); - ImRect hole_rect(central_node->Pos, central_node->Pos + central_node->Size); - if (hole_rect.Min.x > root_rect.Min.x) { hole_rect.Min.x += WINDOWS_HOVER_PADDING; } - if (hole_rect.Max.x < root_rect.Max.x) { hole_rect.Max.x -= WINDOWS_HOVER_PADDING; } - if (hole_rect.Min.y > root_rect.Min.y) { hole_rect.Min.y += WINDOWS_HOVER_PADDING; } - if (hole_rect.Max.y < root_rect.Max.y) { hole_rect.Max.y -= WINDOWS_HOVER_PADDING; } - //GetForegroundDrawList()->AddRect(hole_rect.Min, hole_rect.Max, IM_COL32(255, 0, 0, 255)); - if (central_node_hole && !hole_rect.IsInverted()) - { - SetWindowHitTestHole(host_window, hole_rect.Min, hole_rect.Max - hole_rect.Min); - if (host_window->ParentWindow) - SetWindowHitTestHole(host_window->ParentWindow, hole_rect.Min, hole_rect.Max - hole_rect.Min); - } - } - - // Update position/size, process and draw resizing splitters - if (node->IsRootNode() && host_window) - { - DockNodeTreeUpdatePosSize(node, host_window->Pos, host_window->Size); - PushStyleColor(ImGuiCol_Separator, g.Style.Colors[ImGuiCol_Border]); - PushStyleColor(ImGuiCol_SeparatorActive, g.Style.Colors[ImGuiCol_ResizeGripActive]); - PushStyleColor(ImGuiCol_SeparatorHovered, g.Style.Colors[ImGuiCol_ResizeGripHovered]); - DockNodeTreeUpdateSplitter(node); - PopStyleColor(3); - } - - // Draw empty node background (currently can only be the Central Node) - if (host_window && node->IsEmpty() && node->IsVisible) - { - host_window->DrawList->ChannelsSetCurrent(DOCKING_HOST_DRAW_CHANNEL_BG); - node->LastBgColor = (node_flags & ImGuiDockNodeFlags_PassthruCentralNode) ? 0 : GetColorU32(ImGuiCol_DockingEmptyBg); - if (node->LastBgColor != 0) - host_window->DrawList->AddRectFilled(node->Pos, node->Pos + node->Size, node->LastBgColor); - node->IsBgDrawnThisFrame = true; - } - - // Draw whole dockspace background if ImGuiDockNodeFlags_PassthruCentralNode if set. - // We need to draw a background at the root level if requested by ImGuiDockNodeFlags_PassthruCentralNode, but we will only know the correct pos/size - // _after_ processing the resizing splitters. So we are using the DrawList channel splitting facility to submit drawing primitives out of order! - const bool render_dockspace_bg = node->IsRootNode() && host_window && (node_flags & ImGuiDockNodeFlags_PassthruCentralNode) != 0; - if (render_dockspace_bg && node->IsVisible) - { - host_window->DrawList->ChannelsSetCurrent(DOCKING_HOST_DRAW_CHANNEL_BG); - if (central_node_hole) - RenderRectFilledWithHole(host_window->DrawList, node->Rect(), central_node->Rect(), GetColorU32(ImGuiCol_WindowBg), 0.0f); - else - host_window->DrawList->AddRectFilled(node->Pos, node->Pos + node->Size, GetColorU32(ImGuiCol_WindowBg), 0.0f); - } - - // Draw and populate Tab Bar - if (host_window) - host_window->DrawList->ChannelsSetCurrent(DOCKING_HOST_DRAW_CHANNEL_FG); - if (host_window && node->Windows.Size > 0) - { - DockNodeUpdateTabBar(node, host_window); - } - else - { - node->WantCloseAll = false; - node->WantCloseTabId = 0; - node->IsFocused = false; - } - if (node->TabBar && node->TabBar->SelectedTabId) - node->SelectedTabId = node->TabBar->SelectedTabId; - else if (node->Windows.Size > 0) - node->SelectedTabId = node->Windows[0]->TabId; - - // Draw payload drop target - if (host_window && node->IsVisible) - if (node->IsRootNode() && (g.MovingWindow == NULL || g.MovingWindow->RootWindowDockTree != host_window)) - BeginDockableDragDropTarget(host_window); - - // We update this after DockNodeUpdateTabBar() - node->LastFrameActive = g.FrameCount; - - // Recurse into children - // FIXME-DOCK FIXME-OPT: Should not need to recurse into children - if (host_window) - { - if (node->ChildNodes[0]) - DockNodeUpdate(node->ChildNodes[0]); - if (node->ChildNodes[1]) - DockNodeUpdate(node->ChildNodes[1]); - - // Render outer borders last (after the tab bar) - if (node->IsRootNode()) - RenderWindowOuterBorders(host_window); - } - - // End host window - if (beginned_into_host_window) //-V1020 - End(); -} - -// Compare TabItem nodes given the last known DockOrder (will persist in .ini file as hint), used to sort tabs when multiple tabs are added on the same frame. -static int IMGUI_CDECL TabItemComparerByDockOrder(const void* lhs, const void* rhs) -{ - ImGuiWindow* a = ((const ImGuiTabItem*)lhs)->Window; - ImGuiWindow* b = ((const ImGuiTabItem*)rhs)->Window; - if (int d = ((a->DockOrder == -1) ? INT_MAX : a->DockOrder) - ((b->DockOrder == -1) ? INT_MAX : b->DockOrder)) - return d; - return (a->BeginOrderWithinContext - b->BeginOrderWithinContext); -} - -// Default handler for g.DockNodeWindowMenuHandler(): display the list of windows for a given dock-node. -// This is exceptionally stored in a function pointer to also user applications to tweak this menu (undocumented) -// Custom overrides may want to decorate, group, sort entries. -// Please note those are internal structures: if you copy this expect occasional breakage. -// (if you don't need to modify the "Tabs.Size == 1" behavior/path it is recommend you call this function in your handler) -void ImGui::DockNodeWindowMenuHandler_Default(ImGuiContext* ctx, ImGuiDockNode* node, ImGuiTabBar* tab_bar) -{ - IM_UNUSED(ctx); - if (tab_bar->Tabs.Size == 1) - { - // "Hide tab bar" option. Being one of our rare user-facing string we pull it from a table. - if (MenuItem(LocalizeGetMsg(ImGuiLocKey_DockingHideTabBar), NULL, node->IsHiddenTabBar())) - node->WantHiddenTabBarToggle = true; - } - else - { - // Display a selectable list of windows in this docking node - for (int tab_n = 0; tab_n < tab_bar->Tabs.Size; tab_n++) - { - ImGuiTabItem* tab = &tab_bar->Tabs[tab_n]; - if (tab->Flags & ImGuiTabItemFlags_Button) - continue; - if (Selectable(TabBarGetTabName(tab_bar, tab), tab->ID == tab_bar->SelectedTabId)) - TabBarQueueFocus(tab_bar, tab); - SameLine(); - Text(" "); - } - } -} - -static void ImGui::DockNodeWindowMenuUpdate(ImGuiDockNode* node, ImGuiTabBar* tab_bar) -{ - // Try to position the menu so it is more likely to stays within the same viewport - ImGuiContext& g = *GImGui; - if (g.Style.WindowMenuButtonPosition == ImGuiDir_Left) - SetNextWindowPos(ImVec2(node->Pos.x, node->Pos.y + GetFrameHeight()), ImGuiCond_Always, ImVec2(0.0f, 0.0f)); - else - SetNextWindowPos(ImVec2(node->Pos.x + node->Size.x, node->Pos.y + GetFrameHeight()), ImGuiCond_Always, ImVec2(1.0f, 0.0f)); - if (BeginPopup("#WindowMenu")) - { - node->IsFocused = true; - g.DockNodeWindowMenuHandler(&g, node, tab_bar); - EndPopup(); - } -} - -// User helper to append/amend into a dock node tab bar. Most commonly used to add e.g. a "+" button. -bool ImGui::DockNodeBeginAmendTabBar(ImGuiDockNode* node) -{ - if (node->TabBar == NULL || node->HostWindow == NULL) - return false; - if (node->MergedFlags & ImGuiDockNodeFlags_KeepAliveOnly) - return false; - Begin(node->HostWindow->Name); - PushOverrideID(node->ID); - bool ret = BeginTabBarEx(node->TabBar, node->TabBar->BarRect, node->TabBar->Flags); - IM_UNUSED(ret); - IM_ASSERT(ret); - return true; -} - -void ImGui::DockNodeEndAmendTabBar() -{ - EndTabBar(); - PopID(); - End(); -} - -static bool IsDockNodeTitleBarHighlighted(ImGuiDockNode* node, ImGuiDockNode* root_node) -{ - // CTRL+Tab highlight (only highlighting leaf node, not whole hierarchy) - ImGuiContext& g = *GImGui; - if (g.NavWindowingTarget) - return (g.NavWindowingTarget->DockNode == node); - - // FIXME-DOCKING: May want alternative to treat central node void differently? e.g. if (g.NavWindow == host_window) - if (g.NavWindow && root_node->LastFocusedNodeId == node->ID) - { - // FIXME: This could all be backed in RootWindowForTitleBarHighlight? Probably need to reorganize for both dock nodes + other RootWindowForTitleBarHighlight users (not-node) - ImGuiWindow* parent_window = g.NavWindow->RootWindow; - while (parent_window->Flags & ImGuiWindowFlags_ChildMenu) - parent_window = parent_window->ParentWindow->RootWindow; - ImGuiDockNode* start_parent_node = parent_window->DockNodeAsHost ? parent_window->DockNodeAsHost : parent_window->DockNode; - for (ImGuiDockNode* parent_node = start_parent_node; parent_node != NULL; parent_node = parent_node->HostWindow ? parent_node->HostWindow->RootWindow->DockNode : NULL) - if ((parent_node = ImGui::DockNodeGetRootNode(parent_node)) == root_node) - return true; - } - return false; -} - -// Submit the tab bar corresponding to a dock node and various housekeeping details. -static void ImGui::DockNodeUpdateTabBar(ImGuiDockNode* node, ImGuiWindow* host_window) -{ - ImGuiContext& g = *GImGui; - ImGuiStyle& style = g.Style; - - const bool node_was_active = (node->LastFrameActive + 1 == g.FrameCount); - const bool closed_all = node->WantCloseAll && node_was_active; - const ImGuiID closed_one = node->WantCloseTabId && node_was_active; - node->WantCloseAll = false; - node->WantCloseTabId = 0; - - // Decide if we should use a focused title bar color - bool is_focused = false; - ImGuiDockNode* root_node = DockNodeGetRootNode(node); - if (IsDockNodeTitleBarHighlighted(node, root_node)) - is_focused = true; - - // Hidden tab bar will show a triangle on the upper-left (in Begin) - if (node->IsHiddenTabBar() || node->IsNoTabBar()) - { - node->VisibleWindow = (node->Windows.Size > 0) ? node->Windows[0] : NULL; - node->IsFocused = is_focused; - if (is_focused) - node->LastFrameFocused = g.FrameCount; - if (node->VisibleWindow) - { - // Notify root of visible window (used to display title in OS task bar) - if (is_focused || root_node->VisibleWindow == NULL) - root_node->VisibleWindow = node->VisibleWindow; - if (node->TabBar) - node->TabBar->VisibleTabId = node->VisibleWindow->TabId; - } - return; - } - - // Move ourselves to the Menu layer (so we can be accessed by tapping Alt) + undo SkipItems flag in order to draw over the title bar even if the window is collapsed - bool backup_skip_item = host_window->SkipItems; - if (!node->IsDockSpace()) - { - host_window->SkipItems = false; - host_window->DC.NavLayerCurrent = ImGuiNavLayer_Menu; - } - - // Use PushOverrideID() instead of PushID() to use the node id _without_ the host window ID. - // This is to facilitate computing those ID from the outside, and will affect more or less only the ID of the collapse button, popup and tabs, - // as docked windows themselves will override the stack with their own root ID. - PushOverrideID(node->ID); - ImGuiTabBar* tab_bar = node->TabBar; - bool tab_bar_is_recreated = (tab_bar == NULL); // Tab bar are automatically destroyed when a node gets hidden - if (tab_bar == NULL) - { - DockNodeAddTabBar(node); - tab_bar = node->TabBar; - } - - ImGuiID focus_tab_id = 0; - node->IsFocused = is_focused; - - const ImGuiDockNodeFlags node_flags = node->MergedFlags; - const bool has_window_menu_button = (node_flags & ImGuiDockNodeFlags_NoWindowMenuButton) == 0 && (style.WindowMenuButtonPosition != ImGuiDir_None); - - // In a dock node, the Collapse Button turns into the Window Menu button. - // FIXME-DOCK FIXME-OPT: Could we recycle popups id across multiple dock nodes? - if (has_window_menu_button && IsPopupOpen("#WindowMenu")) - { - ImGuiID next_selected_tab_id = tab_bar->NextSelectedTabId; - DockNodeWindowMenuUpdate(node, tab_bar); - if (tab_bar->NextSelectedTabId != 0 && tab_bar->NextSelectedTabId != next_selected_tab_id) - focus_tab_id = tab_bar->NextSelectedTabId; - is_focused |= node->IsFocused; - } - - // Layout - ImRect title_bar_rect, tab_bar_rect; - ImVec2 window_menu_button_pos; - ImVec2 close_button_pos; - DockNodeCalcTabBarLayout(node, &title_bar_rect, &tab_bar_rect, &window_menu_button_pos, &close_button_pos); - - // Submit new tabs, they will be added as Unsorted and sorted below based on relative DockOrder value. - const int tabs_count_old = tab_bar->Tabs.Size; - for (int window_n = 0; window_n < node->Windows.Size; window_n++) - { - ImGuiWindow* window = node->Windows[window_n]; - if (TabBarFindTabByID(tab_bar, window->TabId) == NULL) - TabBarAddTab(tab_bar, ImGuiTabItemFlags_Unsorted, window); - } - - // Title bar - if (is_focused) - node->LastFrameFocused = g.FrameCount; - ImU32 title_bar_col = GetColorU32(host_window->Collapsed ? ImGuiCol_TitleBgCollapsed : is_focused ? ImGuiCol_TitleBgActive : ImGuiCol_TitleBg); - ImDrawFlags rounding_flags = CalcRoundingFlagsForRectInRect(title_bar_rect, host_window->Rect(), g.Style.DockingSeparatorSize); - host_window->DrawList->AddRectFilled(title_bar_rect.Min, title_bar_rect.Max, title_bar_col, host_window->WindowRounding, rounding_flags); - - // Docking/Collapse button - if (has_window_menu_button) - { - if (CollapseButton(host_window->GetID("#COLLAPSE"), window_menu_button_pos, node)) // == DockNodeGetWindowMenuButtonId(node) - OpenPopup("#WindowMenu"); - if (IsItemActive()) - focus_tab_id = tab_bar->SelectedTabId; - } - - // If multiple tabs are appearing on the same frame, sort them based on their persistent DockOrder value - int tabs_unsorted_start = tab_bar->Tabs.Size; - for (int tab_n = tab_bar->Tabs.Size - 1; tab_n >= 0 && (tab_bar->Tabs[tab_n].Flags & ImGuiTabItemFlags_Unsorted); tab_n--) - { - // FIXME-DOCK: Consider only clearing the flag after the tab has been alive for a few consecutive frames, allowing late comers to not break sorting? - tab_bar->Tabs[tab_n].Flags &= ~ImGuiTabItemFlags_Unsorted; - tabs_unsorted_start = tab_n; - } - if (tab_bar->Tabs.Size > tabs_unsorted_start) - { - IMGUI_DEBUG_LOG_DOCKING("[docking] In node 0x%08X: %d new appearing tabs:%s\n", node->ID, tab_bar->Tabs.Size - tabs_unsorted_start, (tab_bar->Tabs.Size > tabs_unsorted_start + 1) ? " (will sort)" : ""); - for (int tab_n = tabs_unsorted_start; tab_n < tab_bar->Tabs.Size; tab_n++) - { - ImGuiTabItem* tab = &tab_bar->Tabs[tab_n]; - IMGUI_DEBUG_LOG_DOCKING("[docking] - Tab 0x%08X '%s' Order %d\n", tab->ID, TabBarGetTabName(tab_bar, tab), tab->Window ? tab->Window->DockOrder : -1); - } - IMGUI_DEBUG_LOG_DOCKING("[docking] SelectedTabId = 0x%08X, NavWindow->TabId = 0x%08X\n", node->SelectedTabId, g.NavWindow ? g.NavWindow->TabId : -1); - if (tab_bar->Tabs.Size > tabs_unsorted_start + 1) - ImQsort(tab_bar->Tabs.Data + tabs_unsorted_start, tab_bar->Tabs.Size - tabs_unsorted_start, sizeof(ImGuiTabItem), TabItemComparerByDockOrder); - } - - // Apply NavWindow focus back to the tab bar - if (g.NavWindow && g.NavWindow->RootWindow->DockNode == node) - tab_bar->SelectedTabId = g.NavWindow->RootWindow->TabId; - - // Selected newly added tabs, or persistent tab ID if the tab bar was just recreated - if (tab_bar_is_recreated && TabBarFindTabByID(tab_bar, node->SelectedTabId) != NULL) - tab_bar->SelectedTabId = tab_bar->NextSelectedTabId = node->SelectedTabId; - else if (tab_bar->Tabs.Size > tabs_count_old) - tab_bar->SelectedTabId = tab_bar->NextSelectedTabId = tab_bar->Tabs.back().Window->TabId; - - // Begin tab bar - ImGuiTabBarFlags tab_bar_flags = ImGuiTabBarFlags_Reorderable | ImGuiTabBarFlags_AutoSelectNewTabs; // | ImGuiTabBarFlags_NoTabListScrollingButtons); - tab_bar_flags |= ImGuiTabBarFlags_SaveSettings | ImGuiTabBarFlags_DockNode;// | ImGuiTabBarFlags_FittingPolicyScroll; - if (!host_window->Collapsed && is_focused) - tab_bar_flags |= ImGuiTabBarFlags_IsFocused; - tab_bar->ID = GetID("#TabBar"); - tab_bar->SeparatorMinX = node->Pos.x + host_window->WindowBorderSize; // Separator cover the whole node width - tab_bar->SeparatorMaxX = node->Pos.x + node->Size.x - host_window->WindowBorderSize; - BeginTabBarEx(tab_bar, tab_bar_rect, tab_bar_flags); - //host_window->DrawList->AddRect(tab_bar_rect.Min, tab_bar_rect.Max, IM_COL32(255,0,255,255)); - - // Backup style colors - ImVec4 backup_style_cols[ImGuiWindowDockStyleCol_COUNT]; - for (int color_n = 0; color_n < ImGuiWindowDockStyleCol_COUNT; color_n++) - backup_style_cols[color_n] = g.Style.Colors[GWindowDockStyleColors[color_n]]; - - // Submit actual tabs - node->VisibleWindow = NULL; - for (int window_n = 0; window_n < node->Windows.Size; window_n++) - { - ImGuiWindow* window = node->Windows[window_n]; - if ((closed_all || closed_one == window->TabId) && window->HasCloseButton && !(window->Flags & ImGuiWindowFlags_UnsavedDocument)) - continue; - if (window->LastFrameActive + 1 >= g.FrameCount || !node_was_active) - { - ImGuiTabItemFlags tab_item_flags = 0; - tab_item_flags |= window->WindowClass.TabItemFlagsOverrideSet; - if (window->Flags & ImGuiWindowFlags_UnsavedDocument) - tab_item_flags |= ImGuiTabItemFlags_UnsavedDocument; - if (tab_bar->Flags & ImGuiTabBarFlags_NoCloseWithMiddleMouseButton) - tab_item_flags |= ImGuiTabItemFlags_NoCloseWithMiddleMouseButton; - - // Apply stored style overrides for the window - for (int color_n = 0; color_n < ImGuiWindowDockStyleCol_COUNT; color_n++) - g.Style.Colors[GWindowDockStyleColors[color_n]] = ColorConvertU32ToFloat4(window->DockStyle.Colors[color_n]); - - // Note that TabItemEx() calls TabBarCalcTabID() so our tab item ID will ignore the current ID stack (rightly so) - bool tab_open = true; - TabItemEx(tab_bar, window->Name, window->HasCloseButton ? &tab_open : NULL, tab_item_flags, window); - if (!tab_open) - node->WantCloseTabId = window->TabId; - if (tab_bar->VisibleTabId == window->TabId) - node->VisibleWindow = window; - - // Store last item data so it can be queried with IsItemXXX functions after the user Begin() call - window->DockTabItemStatusFlags = g.LastItemData.StatusFlags; - window->DockTabItemRect = g.LastItemData.Rect; - - // Update navigation ID on menu layer - if (g.NavWindow && g.NavWindow->RootWindow == window && (window->DC.NavLayersActiveMask & (1 << ImGuiNavLayer_Menu)) == 0) - host_window->NavLastIds[1] = window->TabId; - } - } - - // Restore style colors - for (int color_n = 0; color_n < ImGuiWindowDockStyleCol_COUNT; color_n++) - g.Style.Colors[GWindowDockStyleColors[color_n]] = backup_style_cols[color_n]; - - // Notify root of visible window (used to display title in OS task bar) - if (node->VisibleWindow) - if (is_focused || root_node->VisibleWindow == NULL) - root_node->VisibleWindow = node->VisibleWindow; - - // Close button (after VisibleWindow was updated) - // Note that VisibleWindow may have been overrided by CTRL+Tabbing, so VisibleWindow->TabId may be != from tab_bar->SelectedTabId - const bool close_button_is_enabled = node->HasCloseButton && node->VisibleWindow && node->VisibleWindow->HasCloseButton; - const bool close_button_is_visible = node->HasCloseButton; - //const bool close_button_is_visible = close_button_is_enabled; // Most people would expect this behavior of not even showing the button (leaving a hole since we can't claim that space as other windows in the tba bar have one) - if (close_button_is_visible) - { - if (!close_button_is_enabled) - { - PushItemFlag(ImGuiItemFlags_Disabled, true); - PushStyleColor(ImGuiCol_Text, style.Colors[ImGuiCol_Text] * ImVec4(1.0f,1.0f,1.0f,0.4f)); - } - if (CloseButton(host_window->GetID("#CLOSE"), close_button_pos)) - { - node->WantCloseAll = true; - for (int n = 0; n < tab_bar->Tabs.Size; n++) - TabBarCloseTab(tab_bar, &tab_bar->Tabs[n]); - } - //if (IsItemActive()) - // focus_tab_id = tab_bar->SelectedTabId; - if (!close_button_is_enabled) - { - PopStyleColor(); - PopItemFlag(); - } - } - - // When clicking on the title bar outside of tabs, we still focus the selected tab for that node - // FIXME: TabItems submitted earlier use AllowItemOverlap so we manually perform a more specific test for now (hovered || held) in order to not cover them. - ImGuiID title_bar_id = host_window->GetID("#TITLEBAR"); - if (g.HoveredId == 0 || g.HoveredId == title_bar_id || g.ActiveId == title_bar_id) - { - // AllowItem mode required for appending into dock node tab bar, - // otherwise dragging window will steal HoveredId and amended tabs cannot get them. - bool held; - KeepAliveID(title_bar_id); - ButtonBehavior(title_bar_rect, title_bar_id, NULL, &held, ImGuiButtonFlags_AllowOverlap); - if (g.HoveredId == title_bar_id) - { - g.LastItemData.ID = title_bar_id; - } - if (held) - { - if (IsMouseClicked(0)) - focus_tab_id = tab_bar->SelectedTabId; - - // Forward moving request to selected window - if (ImGuiTabItem* tab = TabBarFindTabByID(tab_bar, tab_bar->SelectedTabId)) - StartMouseMovingWindowOrNode(tab->Window ? tab->Window : node->HostWindow, node, false); - } - } - - // Forward focus from host node to selected window - //if (is_focused && g.NavWindow == host_window && !g.NavWindowingTarget) - // focus_tab_id = tab_bar->SelectedTabId; - - // When clicked on a tab we requested focus to the docked child - // This overrides the value set by "forward focus from host node to selected window". - if (tab_bar->NextSelectedTabId) - focus_tab_id = tab_bar->NextSelectedTabId; - - // Apply navigation focus - if (focus_tab_id != 0) - if (ImGuiTabItem* tab = TabBarFindTabByID(tab_bar, focus_tab_id)) - if (tab->Window) - { - FocusWindow(tab->Window); - NavInitWindow(tab->Window, false); - } - - EndTabBar(); - PopID(); - - // Restore SkipItems flag - if (!node->IsDockSpace()) - { - host_window->DC.NavLayerCurrent = ImGuiNavLayer_Main; - host_window->SkipItems = backup_skip_item; - } -} - -static void ImGui::DockNodeAddTabBar(ImGuiDockNode* node) -{ - IM_ASSERT(node->TabBar == NULL); - node->TabBar = IM_NEW(ImGuiTabBar); -} - -static void ImGui::DockNodeRemoveTabBar(ImGuiDockNode* node) -{ - if (node->TabBar == NULL) - return; - IM_DELETE(node->TabBar); - node->TabBar = NULL; -} - -static bool DockNodeIsDropAllowedOne(ImGuiWindow* payload, ImGuiWindow* host_window) -{ - if (host_window->DockNodeAsHost && host_window->DockNodeAsHost->IsDockSpace() && payload->BeginOrderWithinContext < host_window->BeginOrderWithinContext) - return false; - - ImGuiWindowClass* host_class = host_window->DockNodeAsHost ? &host_window->DockNodeAsHost->WindowClass : &host_window->WindowClass; - ImGuiWindowClass* payload_class = &payload->WindowClass; - if (host_class->ClassId != payload_class->ClassId) - { - bool pass = false; - if (host_class->ClassId != 0 && host_class->DockingAllowUnclassed && payload_class->ClassId == 0) - pass = true; - if (payload_class->ClassId != 0 && payload_class->DockingAllowUnclassed && host_class->ClassId == 0) - pass = true; - if (!pass) - return false; - } - - // Prevent docking any window created above a popup - // Technically we should support it (e.g. in the case of a long-lived modal window that had fancy docking features), - // by e.g. adding a 'if (!ImGui::IsWindowWithinBeginStackOf(host_window, popup_window))' test. - // But it would requires more work on our end because the dock host windows is technically created in NewFrame() - // and our ->ParentXXX and ->RootXXX pointers inside windows are currently mislading or lacking. - ImGuiContext& g = *GImGui; - for (int i = g.OpenPopupStack.Size - 1; i >= 0; i--) - if (ImGuiWindow* popup_window = g.OpenPopupStack[i].Window) - if (ImGui::IsWindowWithinBeginStackOf(payload, popup_window)) // Payload is created from within a popup begin stack. - return false; - - return true; -} - -static bool ImGui::DockNodeIsDropAllowed(ImGuiWindow* host_window, ImGuiWindow* root_payload) -{ - if (root_payload->DockNodeAsHost && root_payload->DockNodeAsHost->IsSplitNode()) // FIXME-DOCK: Missing filtering - return true; - - const int payload_count = root_payload->DockNodeAsHost ? root_payload->DockNodeAsHost->Windows.Size : 1; - for (int payload_n = 0; payload_n < payload_count; payload_n++) - { - ImGuiWindow* payload = root_payload->DockNodeAsHost ? root_payload->DockNodeAsHost->Windows[payload_n] : root_payload; - if (DockNodeIsDropAllowedOne(payload, host_window)) - return true; - } - return false; -} - -// window menu button == collapse button when not in a dock node. -// FIXME: This is similar to RenderWindowTitleBarContents(), may want to share code. -static void ImGui::DockNodeCalcTabBarLayout(const ImGuiDockNode* node, ImRect* out_title_rect, ImRect* out_tab_bar_rect, ImVec2* out_window_menu_button_pos, ImVec2* out_close_button_pos) -{ - ImGuiContext& g = *GImGui; - ImGuiStyle& style = g.Style; - - ImRect r = ImRect(node->Pos.x, node->Pos.y, node->Pos.x + node->Size.x, node->Pos.y + g.FontSize + g.Style.FramePadding.y * 2.0f); - if (out_title_rect) { *out_title_rect = r; } - - r.Min.x += style.WindowBorderSize; - r.Max.x -= style.WindowBorderSize; - - float button_sz = g.FontSize; - r.Min.x += style.FramePadding.x; - r.Max.x -= style.FramePadding.x; - ImVec2 window_menu_button_pos = ImVec2(r.Min.x, r.Min.y + style.FramePadding.y); - if (node->HasCloseButton) - { - if (out_close_button_pos) *out_close_button_pos = ImVec2(r.Max.x - button_sz, r.Min.y + style.FramePadding.y); - r.Max.x -= button_sz + style.ItemInnerSpacing.x; - } - if (node->HasWindowMenuButton && style.WindowMenuButtonPosition == ImGuiDir_Left) - { - r.Min.x += button_sz + style.ItemInnerSpacing.x; - } - else if (node->HasWindowMenuButton && style.WindowMenuButtonPosition == ImGuiDir_Right) - { - window_menu_button_pos = ImVec2(r.Max.x - button_sz, r.Min.y + style.FramePadding.y); - r.Max.x -= button_sz + style.ItemInnerSpacing.x; - } - if (out_tab_bar_rect) { *out_tab_bar_rect = r; } - if (out_window_menu_button_pos) { *out_window_menu_button_pos = window_menu_button_pos; } -} - -void ImGui::DockNodeCalcSplitRects(ImVec2& pos_old, ImVec2& size_old, ImVec2& pos_new, ImVec2& size_new, ImGuiDir dir, ImVec2 size_new_desired) -{ - ImGuiContext& g = *GImGui; - const float dock_spacing = g.Style.ItemInnerSpacing.x; - const ImGuiAxis axis = (dir == ImGuiDir_Left || dir == ImGuiDir_Right) ? ImGuiAxis_X : ImGuiAxis_Y; - pos_new[axis ^ 1] = pos_old[axis ^ 1]; - size_new[axis ^ 1] = size_old[axis ^ 1]; - - // Distribute size on given axis (with a desired size or equally) - const float w_avail = size_old[axis] - dock_spacing; - if (size_new_desired[axis] > 0.0f && size_new_desired[axis] <= w_avail * 0.5f) - { - size_new[axis] = size_new_desired[axis]; - size_old[axis] = IM_TRUNC(w_avail - size_new[axis]); - } - else - { - size_new[axis] = IM_TRUNC(w_avail * 0.5f); - size_old[axis] = IM_TRUNC(w_avail - size_new[axis]); - } - - // Position each node - if (dir == ImGuiDir_Right || dir == ImGuiDir_Down) - { - pos_new[axis] = pos_old[axis] + size_old[axis] + dock_spacing; - } - else if (dir == ImGuiDir_Left || dir == ImGuiDir_Up) - { - pos_new[axis] = pos_old[axis]; - pos_old[axis] = pos_new[axis] + size_new[axis] + dock_spacing; - } -} - -// Retrieve the drop rectangles for a given direction or for the center + perform hit testing. -bool ImGui::DockNodeCalcDropRectsAndTestMousePos(const ImRect& parent, ImGuiDir dir, ImRect& out_r, bool outer_docking, ImVec2* test_mouse_pos) -{ - ImGuiContext& g = *GImGui; - - const float parent_smaller_axis = ImMin(parent.GetWidth(), parent.GetHeight()); - const float hs_for_central_nodes = ImMin(g.FontSize * 1.5f, ImMax(g.FontSize * 0.5f, parent_smaller_axis / 8.0f)); - float hs_w; // Half-size, longer axis - float hs_h; // Half-size, smaller axis - ImVec2 off; // Distance from edge or center - if (outer_docking) - { - //hs_w = ImTrunc(ImClamp(parent_smaller_axis - hs_for_central_nodes * 4.0f, g.FontSize * 0.5f, g.FontSize * 8.0f)); - //hs_h = ImTrunc(hs_w * 0.15f); - //off = ImVec2(ImTrunc(parent.GetWidth() * 0.5f - GetFrameHeightWithSpacing() * 1.4f - hs_h), ImTrunc(parent.GetHeight() * 0.5f - GetFrameHeightWithSpacing() * 1.4f - hs_h)); - hs_w = ImTrunc(hs_for_central_nodes * 1.50f); - hs_h = ImTrunc(hs_for_central_nodes * 0.80f); - off = ImTrunc(ImVec2(parent.GetWidth() * 0.5f - hs_h, parent.GetHeight() * 0.5f - hs_h)); - } - else - { - hs_w = ImTrunc(hs_for_central_nodes); - hs_h = ImTrunc(hs_for_central_nodes * 0.90f); - off = ImTrunc(ImVec2(hs_w * 2.40f, hs_w * 2.40f)); - } - - ImVec2 c = ImTrunc(parent.GetCenter()); - if (dir == ImGuiDir_None) { out_r = ImRect(c.x - hs_w, c.y - hs_w, c.x + hs_w, c.y + hs_w); } - else if (dir == ImGuiDir_Up) { out_r = ImRect(c.x - hs_w, c.y - off.y - hs_h, c.x + hs_w, c.y - off.y + hs_h); } - else if (dir == ImGuiDir_Down) { out_r = ImRect(c.x - hs_w, c.y + off.y - hs_h, c.x + hs_w, c.y + off.y + hs_h); } - else if (dir == ImGuiDir_Left) { out_r = ImRect(c.x - off.x - hs_h, c.y - hs_w, c.x - off.x + hs_h, c.y + hs_w); } - else if (dir == ImGuiDir_Right) { out_r = ImRect(c.x + off.x - hs_h, c.y - hs_w, c.x + off.x + hs_h, c.y + hs_w); } - - if (test_mouse_pos == NULL) - return false; - - ImRect hit_r = out_r; - if (!outer_docking) - { - // Custom hit testing for the 5-way selection, designed to reduce flickering when moving diagonally between sides - hit_r.Expand(ImTrunc(hs_w * 0.30f)); - ImVec2 mouse_delta = (*test_mouse_pos - c); - float mouse_delta_len2 = ImLengthSqr(mouse_delta); - float r_threshold_center = hs_w * 1.4f; - float r_threshold_sides = hs_w * (1.4f + 1.2f); - if (mouse_delta_len2 < r_threshold_center * r_threshold_center) - return (dir == ImGuiDir_None); - if (mouse_delta_len2 < r_threshold_sides * r_threshold_sides) - return (dir == ImGetDirQuadrantFromDelta(mouse_delta.x, mouse_delta.y)); - } - return hit_r.Contains(*test_mouse_pos); -} - -// host_node may be NULL if the window doesn't have a DockNode already. -// FIXME-DOCK: This is misnamed since it's also doing the filtering. -static void ImGui::DockNodePreviewDockSetup(ImGuiWindow* host_window, ImGuiDockNode* host_node, ImGuiWindow* payload_window, ImGuiDockNode* payload_node, ImGuiDockPreviewData* data, bool is_explicit_target, bool is_outer_docking) -{ - ImGuiContext& g = *GImGui; - - // There is an edge case when docking into a dockspace which only has inactive nodes. - // In this case DockNodeTreeFindNodeByPos() will have selected a leaf node which is inactive. - // Because the inactive leaf node doesn't have proper pos/size yet, we'll use the root node as reference. - if (payload_node == NULL) - payload_node = payload_window->DockNodeAsHost; - ImGuiDockNode* ref_node_for_rect = (host_node && !host_node->IsVisible) ? DockNodeGetRootNode(host_node) : host_node; - if (ref_node_for_rect) - IM_ASSERT(ref_node_for_rect->IsVisible == true); - - // Filter, figure out where we are allowed to dock - ImGuiDockNodeFlags src_node_flags = payload_node ? payload_node->MergedFlags : payload_window->WindowClass.DockNodeFlagsOverrideSet; - ImGuiDockNodeFlags dst_node_flags = host_node ? host_node->MergedFlags : host_window->WindowClass.DockNodeFlagsOverrideSet; - data->IsCenterAvailable = true; - if (is_outer_docking) - data->IsCenterAvailable = false; - else if (dst_node_flags & ImGuiDockNodeFlags_NoDockingOverMe) - data->IsCenterAvailable = false; - else if (host_node && (dst_node_flags & ImGuiDockNodeFlags_NoDockingOverCentralNode) && host_node->IsCentralNode()) - data->IsCenterAvailable = false; - else if ((!host_node || !host_node->IsEmpty()) && payload_node && payload_node->IsSplitNode() && (payload_node->OnlyNodeWithWindows == NULL)) // Is _visibly_ split? - data->IsCenterAvailable = false; - else if ((src_node_flags & ImGuiDockNodeFlags_NoDockingOverOther) && (!host_node || !host_node->IsEmpty())) - data->IsCenterAvailable = false; - else if ((src_node_flags & ImGuiDockNodeFlags_NoDockingOverEmpty) && host_node && host_node->IsEmpty()) - data->IsCenterAvailable = false; - - data->IsSidesAvailable = true; - if ((dst_node_flags & ImGuiDockNodeFlags_NoDockingSplit) || g.IO.ConfigDockingNoSplit) - data->IsSidesAvailable = false; - else if (!is_outer_docking && host_node && host_node->ParentNode == NULL && host_node->IsCentralNode()) - data->IsSidesAvailable = false; - else if (src_node_flags & ImGuiDockNodeFlags_NoDockingSplitOther) - data->IsSidesAvailable = false; - - // Build a tentative future node (reuse same structure because it is practical. Shape will be readjusted when previewing a split) - data->FutureNode.HasCloseButton = (host_node ? host_node->HasCloseButton : host_window->HasCloseButton) || (payload_window->HasCloseButton); - data->FutureNode.HasWindowMenuButton = host_node ? true : ((host_window->Flags & ImGuiWindowFlags_NoCollapse) == 0); - data->FutureNode.Pos = ref_node_for_rect ? ref_node_for_rect->Pos : host_window->Pos; - data->FutureNode.Size = ref_node_for_rect ? ref_node_for_rect->Size : host_window->Size; - - // Calculate drop shapes geometry for allowed splitting directions - IM_ASSERT(ImGuiDir_None == -1); - data->SplitNode = host_node; - data->SplitDir = ImGuiDir_None; - data->IsSplitDirExplicit = false; - if (!host_window->Collapsed) - for (int dir = ImGuiDir_None; dir < ImGuiDir_COUNT; dir++) - { - if (dir == ImGuiDir_None && !data->IsCenterAvailable) - continue; - if (dir != ImGuiDir_None && !data->IsSidesAvailable) - continue; - if (DockNodeCalcDropRectsAndTestMousePos(data->FutureNode.Rect(), (ImGuiDir)dir, data->DropRectsDraw[dir+1], is_outer_docking, &g.IO.MousePos)) - { - data->SplitDir = (ImGuiDir)dir; - data->IsSplitDirExplicit = true; - } - } - - // When docking without holding Shift, we only allow and preview docking when hovering over a drop rect or over the title bar - data->IsDropAllowed = (data->SplitDir != ImGuiDir_None) || (data->IsCenterAvailable); - if (!is_explicit_target && !data->IsSplitDirExplicit && !g.IO.ConfigDockingWithShift) - data->IsDropAllowed = false; - - // Calculate split area - data->SplitRatio = 0.0f; - if (data->SplitDir != ImGuiDir_None) - { - ImGuiDir split_dir = data->SplitDir; - ImGuiAxis split_axis = (split_dir == ImGuiDir_Left || split_dir == ImGuiDir_Right) ? ImGuiAxis_X : ImGuiAxis_Y; - ImVec2 pos_new, pos_old = data->FutureNode.Pos; - ImVec2 size_new, size_old = data->FutureNode.Size; - DockNodeCalcSplitRects(pos_old, size_old, pos_new, size_new, split_dir, payload_window->Size); - - // Calculate split ratio so we can pass it down the docking request - float split_ratio = ImSaturate(size_new[split_axis] / data->FutureNode.Size[split_axis]); - data->FutureNode.Pos = pos_new; - data->FutureNode.Size = size_new; - data->SplitRatio = (split_dir == ImGuiDir_Right || split_dir == ImGuiDir_Down) ? (1.0f - split_ratio) : (split_ratio); - } -} - -static void ImGui::DockNodePreviewDockRender(ImGuiWindow* host_window, ImGuiDockNode* host_node, ImGuiWindow* root_payload, const ImGuiDockPreviewData* data) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(g.CurrentWindow == host_window); // Because we rely on font size to calculate tab sizes - - // With this option, we only display the preview on the target viewport, and the payload viewport is made transparent. - // To compensate for the single layer obstructed by the payload, we'll increase the alpha of the preview nodes. - const bool is_transparent_payload = g.IO.ConfigDockingTransparentPayload; - - // In case the two windows involved are on different viewports, we will draw the overlay on each of them. - int overlay_draw_lists_count = 0; - ImDrawList* overlay_draw_lists[2]; - overlay_draw_lists[overlay_draw_lists_count++] = GetForegroundDrawList(host_window->Viewport); - if (host_window->Viewport != root_payload->Viewport && !is_transparent_payload) - overlay_draw_lists[overlay_draw_lists_count++] = GetForegroundDrawList(root_payload->Viewport); - - // Draw main preview rectangle - const ImU32 overlay_col_main = GetColorU32(ImGuiCol_DockingPreview, is_transparent_payload ? 0.60f : 0.40f); - const ImU32 overlay_col_drop = GetColorU32(ImGuiCol_DockingPreview, is_transparent_payload ? 0.90f : 0.70f); - const ImU32 overlay_col_drop_hovered = GetColorU32(ImGuiCol_DockingPreview, is_transparent_payload ? 1.20f : 1.00f); - const ImU32 overlay_col_lines = GetColorU32(ImGuiCol_NavWindowingHighlight, is_transparent_payload ? 0.80f : 0.60f); - - // Display area preview - const bool can_preview_tabs = (root_payload->DockNodeAsHost == NULL || root_payload->DockNodeAsHost->Windows.Size > 0); - if (data->IsDropAllowed) - { - ImRect overlay_rect = data->FutureNode.Rect(); - if (data->SplitDir == ImGuiDir_None && can_preview_tabs) - overlay_rect.Min.y += GetFrameHeight(); - if (data->SplitDir != ImGuiDir_None || data->IsCenterAvailable) - for (int overlay_n = 0; overlay_n < overlay_draw_lists_count; overlay_n++) - overlay_draw_lists[overlay_n]->AddRectFilled(overlay_rect.Min, overlay_rect.Max, overlay_col_main, host_window->WindowRounding, CalcRoundingFlagsForRectInRect(overlay_rect, host_window->Rect(), g.Style.DockingSeparatorSize)); - } - - // Display tab shape/label preview unless we are splitting node (it generally makes the situation harder to read) - if (data->IsDropAllowed && can_preview_tabs && data->SplitDir == ImGuiDir_None && data->IsCenterAvailable) - { - // Compute target tab bar geometry so we can locate our preview tabs - ImRect tab_bar_rect; - DockNodeCalcTabBarLayout(&data->FutureNode, NULL, &tab_bar_rect, NULL, NULL); - ImVec2 tab_pos = tab_bar_rect.Min; - if (host_node && host_node->TabBar) - { - if (!host_node->IsHiddenTabBar() && !host_node->IsNoTabBar()) - tab_pos.x += host_node->TabBar->WidthAllTabs + g.Style.ItemInnerSpacing.x; // We don't use OffsetNewTab because when using non-persistent-order tab bar it is incremented with each Tab submission. - else - tab_pos.x += g.Style.ItemInnerSpacing.x + TabItemCalcSize(host_node->Windows[0]).x; - } - else if (!(host_window->Flags & ImGuiWindowFlags_DockNodeHost)) - { - tab_pos.x += g.Style.ItemInnerSpacing.x + TabItemCalcSize(host_window).x; // Account for slight offset which will be added when changing from title bar to tab bar - } - - // Draw tab shape/label preview (payload may be a loose window or a host window carrying multiple tabbed windows) - if (root_payload->DockNodeAsHost) - IM_ASSERT(root_payload->DockNodeAsHost->Windows.Size <= root_payload->DockNodeAsHost->TabBar->Tabs.Size); - ImGuiTabBar* tab_bar_with_payload = root_payload->DockNodeAsHost ? root_payload->DockNodeAsHost->TabBar : NULL; - const int payload_count = tab_bar_with_payload ? tab_bar_with_payload->Tabs.Size : 1; - for (int payload_n = 0; payload_n < payload_count; payload_n++) - { - // DockNode's TabBar may have non-window Tabs manually appended by user - ImGuiWindow* payload_window = tab_bar_with_payload ? tab_bar_with_payload->Tabs[payload_n].Window : root_payload; - if (tab_bar_with_payload && payload_window == NULL) - continue; - if (!DockNodeIsDropAllowedOne(payload_window, host_window)) - continue; - - // Calculate the tab bounding box for each payload window - ImVec2 tab_size = TabItemCalcSize(payload_window); - ImRect tab_bb(tab_pos.x, tab_pos.y, tab_pos.x + tab_size.x, tab_pos.y + tab_size.y); - tab_pos.x += tab_size.x + g.Style.ItemInnerSpacing.x; - const ImU32 overlay_col_text = GetColorU32(payload_window->DockStyle.Colors[ImGuiWindowDockStyleCol_Text]); - const ImU32 overlay_col_tabs = GetColorU32(payload_window->DockStyle.Colors[ImGuiWindowDockStyleCol_TabActive]); - PushStyleColor(ImGuiCol_Text, overlay_col_text); - for (int overlay_n = 0; overlay_n < overlay_draw_lists_count; overlay_n++) - { - ImGuiTabItemFlags tab_flags = (payload_window->Flags & ImGuiWindowFlags_UnsavedDocument) ? ImGuiTabItemFlags_UnsavedDocument : 0; - if (!tab_bar_rect.Contains(tab_bb)) - overlay_draw_lists[overlay_n]->PushClipRect(tab_bar_rect.Min, tab_bar_rect.Max); - TabItemBackground(overlay_draw_lists[overlay_n], tab_bb, tab_flags, overlay_col_tabs); - TabItemLabelAndCloseButton(overlay_draw_lists[overlay_n], tab_bb, tab_flags, g.Style.FramePadding, payload_window->Name, 0, 0, false, NULL, NULL); - if (!tab_bar_rect.Contains(tab_bb)) - overlay_draw_lists[overlay_n]->PopClipRect(); - } - PopStyleColor(); - } - } - - // Display drop boxes - const float overlay_rounding = ImMax(3.0f, g.Style.FrameRounding); - for (int dir = ImGuiDir_None; dir < ImGuiDir_COUNT; dir++) - { - if (!data->DropRectsDraw[dir + 1].IsInverted()) - { - ImRect draw_r = data->DropRectsDraw[dir + 1]; - ImRect draw_r_in = draw_r; - draw_r_in.Expand(-2.0f); - ImU32 overlay_col = (data->SplitDir == (ImGuiDir)dir && data->IsSplitDirExplicit) ? overlay_col_drop_hovered : overlay_col_drop; - for (int overlay_n = 0; overlay_n < overlay_draw_lists_count; overlay_n++) - { - ImVec2 center = ImFloor(draw_r_in.GetCenter()); - overlay_draw_lists[overlay_n]->AddRectFilled(draw_r.Min, draw_r.Max, overlay_col, overlay_rounding); - overlay_draw_lists[overlay_n]->AddRect(draw_r_in.Min, draw_r_in.Max, overlay_col_lines, overlay_rounding); - if (dir == ImGuiDir_Left || dir == ImGuiDir_Right) - overlay_draw_lists[overlay_n]->AddLine(ImVec2(center.x, draw_r_in.Min.y), ImVec2(center.x, draw_r_in.Max.y), overlay_col_lines); - if (dir == ImGuiDir_Up || dir == ImGuiDir_Down) - overlay_draw_lists[overlay_n]->AddLine(ImVec2(draw_r_in.Min.x, center.y), ImVec2(draw_r_in.Max.x, center.y), overlay_col_lines); - } - } - - // Stop after ImGuiDir_None - if ((host_node && (host_node->MergedFlags & ImGuiDockNodeFlags_NoDockingSplit)) || g.IO.ConfigDockingNoSplit) - return; - } -} - -//----------------------------------------------------------------------------- -// Docking: ImGuiDockNode Tree manipulation functions -//----------------------------------------------------------------------------- -// - DockNodeTreeSplit() -// - DockNodeTreeMerge() -// - DockNodeTreeUpdatePosSize() -// - DockNodeTreeUpdateSplitterFindTouchingNode() -// - DockNodeTreeUpdateSplitter() -// - DockNodeTreeFindFallbackLeafNode() -// - DockNodeTreeFindNodeByPos() -//----------------------------------------------------------------------------- - -void ImGui::DockNodeTreeSplit(ImGuiContext* ctx, ImGuiDockNode* parent_node, ImGuiAxis split_axis, int split_inheritor_child_idx, float split_ratio, ImGuiDockNode* new_node) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(split_axis != ImGuiAxis_None); - - ImGuiDockNode* child_0 = (new_node && split_inheritor_child_idx != 0) ? new_node : DockContextAddNode(ctx, 0); - child_0->ParentNode = parent_node; - - ImGuiDockNode* child_1 = (new_node && split_inheritor_child_idx != 1) ? new_node : DockContextAddNode(ctx, 0); - child_1->ParentNode = parent_node; - - ImGuiDockNode* child_inheritor = (split_inheritor_child_idx == 0) ? child_0 : child_1; - DockNodeMoveChildNodes(child_inheritor, parent_node); - parent_node->ChildNodes[0] = child_0; - parent_node->ChildNodes[1] = child_1; - parent_node->ChildNodes[split_inheritor_child_idx]->VisibleWindow = parent_node->VisibleWindow; - parent_node->SplitAxis = split_axis; - parent_node->VisibleWindow = NULL; - parent_node->AuthorityForPos = parent_node->AuthorityForSize = ImGuiDataAuthority_DockNode; - - float size_avail = (parent_node->Size[split_axis] - g.Style.DockingSeparatorSize); - size_avail = ImMax(size_avail, g.Style.WindowMinSize[split_axis] * 2.0f); - IM_ASSERT(size_avail > 0.0f); // If you created a node manually with DockBuilderAddNode(), you need to also call DockBuilderSetNodeSize() before splitting. - child_0->SizeRef = child_1->SizeRef = parent_node->Size; - child_0->SizeRef[split_axis] = ImTrunc(size_avail * split_ratio); - child_1->SizeRef[split_axis] = ImTrunc(size_avail - child_0->SizeRef[split_axis]); - - DockNodeMoveWindows(parent_node->ChildNodes[split_inheritor_child_idx], parent_node); - DockSettingsRenameNodeReferences(parent_node->ID, parent_node->ChildNodes[split_inheritor_child_idx]->ID); - DockNodeUpdateHasCentralNodeChild(DockNodeGetRootNode(parent_node)); - DockNodeTreeUpdatePosSize(parent_node, parent_node->Pos, parent_node->Size); - - // Flags transfer (e.g. this is where we transfer the ImGuiDockNodeFlags_CentralNode property) - child_0->SharedFlags = parent_node->SharedFlags & ImGuiDockNodeFlags_SharedFlagsInheritMask_; - child_1->SharedFlags = parent_node->SharedFlags & ImGuiDockNodeFlags_SharedFlagsInheritMask_; - child_inheritor->LocalFlags = parent_node->LocalFlags & ImGuiDockNodeFlags_LocalFlagsTransferMask_; - parent_node->LocalFlags &= ~ImGuiDockNodeFlags_LocalFlagsTransferMask_; - child_0->UpdateMergedFlags(); - child_1->UpdateMergedFlags(); - parent_node->UpdateMergedFlags(); - if (child_inheritor->IsCentralNode()) - DockNodeGetRootNode(parent_node)->CentralNode = child_inheritor; -} - -void ImGui::DockNodeTreeMerge(ImGuiContext* ctx, ImGuiDockNode* parent_node, ImGuiDockNode* merge_lead_child) -{ - // When called from DockContextProcessUndockNode() it is possible that one of the child is NULL. - ImGuiContext& g = *GImGui; - ImGuiDockNode* child_0 = parent_node->ChildNodes[0]; - ImGuiDockNode* child_1 = parent_node->ChildNodes[1]; - IM_ASSERT(child_0 || child_1); - IM_ASSERT(merge_lead_child == child_0 || merge_lead_child == child_1); - if ((child_0 && child_0->Windows.Size > 0) || (child_1 && child_1->Windows.Size > 0)) - { - IM_ASSERT(parent_node->TabBar == NULL); - IM_ASSERT(parent_node->Windows.Size == 0); - } - IMGUI_DEBUG_LOG_DOCKING("[docking] DockNodeTreeMerge: 0x%08X + 0x%08X back into parent 0x%08X\n", child_0 ? child_0->ID : 0, child_1 ? child_1->ID : 0, parent_node->ID); - - ImVec2 backup_last_explicit_size = parent_node->SizeRef; - DockNodeMoveChildNodes(parent_node, merge_lead_child); - if (child_0) - { - DockNodeMoveWindows(parent_node, child_0); // Generally only 1 of the 2 child node will have windows - DockSettingsRenameNodeReferences(child_0->ID, parent_node->ID); - } - if (child_1) - { - DockNodeMoveWindows(parent_node, child_1); - DockSettingsRenameNodeReferences(child_1->ID, parent_node->ID); - } - DockNodeApplyPosSizeToWindows(parent_node); - parent_node->AuthorityForPos = parent_node->AuthorityForSize = parent_node->AuthorityForViewport = ImGuiDataAuthority_Auto; - parent_node->VisibleWindow = merge_lead_child->VisibleWindow; - parent_node->SizeRef = backup_last_explicit_size; - - // Flags transfer - parent_node->LocalFlags &= ~ImGuiDockNodeFlags_LocalFlagsTransferMask_; // Preserve Dockspace flag - parent_node->LocalFlags |= (child_0 ? child_0->LocalFlags : 0) & ImGuiDockNodeFlags_LocalFlagsTransferMask_; - parent_node->LocalFlags |= (child_1 ? child_1->LocalFlags : 0) & ImGuiDockNodeFlags_LocalFlagsTransferMask_; - parent_node->LocalFlagsInWindows = (child_0 ? child_0->LocalFlagsInWindows : 0) | (child_1 ? child_1->LocalFlagsInWindows : 0); // FIXME: Would be more consistent to update from actual windows - parent_node->UpdateMergedFlags(); - - if (child_0) - { - ctx->DockContext.Nodes.SetVoidPtr(child_0->ID, NULL); - IM_DELETE(child_0); - } - if (child_1) - { - ctx->DockContext.Nodes.SetVoidPtr(child_1->ID, NULL); - IM_DELETE(child_1); - } -} - -// Update Pos/Size for a node hierarchy (don't affect child Windows yet) -// (Depth-first, Pre-Order) -void ImGui::DockNodeTreeUpdatePosSize(ImGuiDockNode* node, ImVec2 pos, ImVec2 size, ImGuiDockNode* only_write_to_single_node) -{ - // During the regular dock node update we write to all nodes. - // 'only_write_to_single_node' is only set when turning a node visible mid-frame and we need its size right-away. - ImGuiContext& g = *GImGui; - const bool write_to_node = only_write_to_single_node == NULL || only_write_to_single_node == node; - if (write_to_node) - { - node->Pos = pos; - node->Size = size; - } - - if (node->IsLeafNode()) - return; - - ImGuiDockNode* child_0 = node->ChildNodes[0]; - ImGuiDockNode* child_1 = node->ChildNodes[1]; - ImVec2 child_0_pos = pos, child_1_pos = pos; - ImVec2 child_0_size = size, child_1_size = size; - - const bool child_0_is_toward_single_node = (only_write_to_single_node != NULL && DockNodeIsInHierarchyOf(only_write_to_single_node, child_0)); - const bool child_1_is_toward_single_node = (only_write_to_single_node != NULL && DockNodeIsInHierarchyOf(only_write_to_single_node, child_1)); - const bool child_0_is_or_will_be_visible = child_0->IsVisible || child_0_is_toward_single_node; - const bool child_1_is_or_will_be_visible = child_1->IsVisible || child_1_is_toward_single_node; - - if (child_0_is_or_will_be_visible && child_1_is_or_will_be_visible) - { - const float spacing = g.Style.DockingSeparatorSize; - const ImGuiAxis axis = (ImGuiAxis)node->SplitAxis; - const float size_avail = ImMax(size[axis] - spacing, 0.0f); - - // Size allocation policy - // 1) The first 0..WindowMinSize[axis]*2 are allocated evenly to both windows. - const float size_min_each = ImTrunc(ImMin(size_avail, g.Style.WindowMinSize[axis] * 2.0f) * 0.5f); - - // FIXME: Blocks 2) and 3) are essentially doing nearly the same thing. - // Difference are: write-back to SizeRef; application of a minimum size; rounding before ImTrunc() - // Clarify and rework differences between Size & SizeRef and purpose of WantLockSizeOnce - - // 2) Process locked absolute size (during a splitter resize we preserve the child of nodes not touching the splitter edge) - if (child_0->WantLockSizeOnce && !child_1->WantLockSizeOnce) - { - child_0_size[axis] = child_0->SizeRef[axis] = ImMin(size_avail - 1.0f, child_0->Size[axis]); - child_1_size[axis] = child_1->SizeRef[axis] = (size_avail - child_0_size[axis]); - IM_ASSERT(child_0->SizeRef[axis] > 0.0f && child_1->SizeRef[axis] > 0.0f); - } - else if (child_1->WantLockSizeOnce && !child_0->WantLockSizeOnce) - { - child_1_size[axis] = child_1->SizeRef[axis] = ImMin(size_avail - 1.0f, child_1->Size[axis]); - child_0_size[axis] = child_0->SizeRef[axis] = (size_avail - child_1_size[axis]); - IM_ASSERT(child_0->SizeRef[axis] > 0.0f && child_1->SizeRef[axis] > 0.0f); - } - else if (child_0->WantLockSizeOnce && child_1->WantLockSizeOnce) - { - // FIXME-DOCK: We cannot honor the requested size, so apply ratio. - // Currently this path will only be taken if code programmatically sets WantLockSizeOnce - float split_ratio = child_0_size[axis] / (child_0_size[axis] + child_1_size[axis]); - child_0_size[axis] = child_0->SizeRef[axis] = ImTrunc(size_avail * split_ratio); - child_1_size[axis] = child_1->SizeRef[axis] = (size_avail - child_0_size[axis]); - IM_ASSERT(child_0->SizeRef[axis] > 0.0f && child_1->SizeRef[axis] > 0.0f); - } - - // 3) If one window is the central node (~ use remaining space, should be made explicit!), use explicit size from the other, and remainder for the central node - else if (child_0->SizeRef[axis] != 0.0f && child_1->HasCentralNodeChild) - { - child_0_size[axis] = ImMin(size_avail - size_min_each, child_0->SizeRef[axis]); - child_1_size[axis] = (size_avail - child_0_size[axis]); - } - else if (child_1->SizeRef[axis] != 0.0f && child_0->HasCentralNodeChild) - { - child_1_size[axis] = ImMin(size_avail - size_min_each, child_1->SizeRef[axis]); - child_0_size[axis] = (size_avail - child_1_size[axis]); - } - else - { - // 4) Otherwise distribute according to the relative ratio of each SizeRef value - float split_ratio = child_0->SizeRef[axis] / (child_0->SizeRef[axis] + child_1->SizeRef[axis]); - child_0_size[axis] = ImMax(size_min_each, ImTrunc(size_avail * split_ratio + 0.5f)); - child_1_size[axis] = (size_avail - child_0_size[axis]); - } - - child_1_pos[axis] += spacing + child_0_size[axis]; - } - - if (only_write_to_single_node == NULL) - child_0->WantLockSizeOnce = child_1->WantLockSizeOnce = false; - - const bool child_0_recurse = only_write_to_single_node ? child_0_is_toward_single_node : child_0->IsVisible; - const bool child_1_recurse = only_write_to_single_node ? child_1_is_toward_single_node : child_1->IsVisible; - if (child_0_recurse) - DockNodeTreeUpdatePosSize(child_0, child_0_pos, child_0_size); - if (child_1_recurse) - DockNodeTreeUpdatePosSize(child_1, child_1_pos, child_1_size); -} - -static void DockNodeTreeUpdateSplitterFindTouchingNode(ImGuiDockNode* node, ImGuiAxis axis, int side, ImVector* touching_nodes) -{ - if (node->IsLeafNode()) - { - touching_nodes->push_back(node); - return; - } - if (node->ChildNodes[0]->IsVisible) - if (node->SplitAxis != axis || side == 0 || !node->ChildNodes[1]->IsVisible) - DockNodeTreeUpdateSplitterFindTouchingNode(node->ChildNodes[0], axis, side, touching_nodes); - if (node->ChildNodes[1]->IsVisible) - if (node->SplitAxis != axis || side == 1 || !node->ChildNodes[0]->IsVisible) - DockNodeTreeUpdateSplitterFindTouchingNode(node->ChildNodes[1], axis, side, touching_nodes); -} - -// (Depth-First, Pre-Order) -void ImGui::DockNodeTreeUpdateSplitter(ImGuiDockNode* node) -{ - if (node->IsLeafNode()) - return; - - ImGuiContext& g = *GImGui; - - ImGuiDockNode* child_0 = node->ChildNodes[0]; - ImGuiDockNode* child_1 = node->ChildNodes[1]; - if (child_0->IsVisible && child_1->IsVisible) - { - // Bounding box of the splitter cover the space between both nodes (w = Spacing, h = Size[xy^1] for when splitting horizontally) - const ImGuiAxis axis = (ImGuiAxis)node->SplitAxis; - IM_ASSERT(axis != ImGuiAxis_None); - ImRect bb; - bb.Min = child_0->Pos; - bb.Max = child_1->Pos; - bb.Min[axis] += child_0->Size[axis]; - bb.Max[axis ^ 1] += child_1->Size[axis ^ 1]; - //if (g.IO.KeyCtrl) GetForegroundDrawList(g.CurrentWindow->Viewport)->AddRect(bb.Min, bb.Max, IM_COL32(255,0,255,255)); - - const ImGuiDockNodeFlags merged_flags = child_0->MergedFlags | child_1->MergedFlags; // Merged flags for BOTH childs - const ImGuiDockNodeFlags no_resize_axis_flag = (axis == ImGuiAxis_X) ? ImGuiDockNodeFlags_NoResizeX : ImGuiDockNodeFlags_NoResizeY; - if ((merged_flags & ImGuiDockNodeFlags_NoResize) || (merged_flags & no_resize_axis_flag)) - { - ImGuiWindow* window = g.CurrentWindow; - window->DrawList->AddRectFilled(bb.Min, bb.Max, GetColorU32(ImGuiCol_Separator), g.Style.FrameRounding); - } - else - { - //bb.Min[axis] += 1; // Display a little inward so highlight doesn't connect with nearby tabs on the neighbor node. - //bb.Max[axis] -= 1; - PushID(node->ID); - - // Find resizing limits by gathering list of nodes that are touching the splitter line. - ImVector touching_nodes[2]; - float min_size = g.Style.WindowMinSize[axis]; - float resize_limits[2]; - resize_limits[0] = node->ChildNodes[0]->Pos[axis] + min_size; - resize_limits[1] = node->ChildNodes[1]->Pos[axis] + node->ChildNodes[1]->Size[axis] - min_size; - - ImGuiID splitter_id = GetID("##Splitter"); - if (g.ActiveId == splitter_id) // Only process when splitter is active - { - DockNodeTreeUpdateSplitterFindTouchingNode(child_0, axis, 1, &touching_nodes[0]); - DockNodeTreeUpdateSplitterFindTouchingNode(child_1, axis, 0, &touching_nodes[1]); - for (int touching_node_n = 0; touching_node_n < touching_nodes[0].Size; touching_node_n++) - resize_limits[0] = ImMax(resize_limits[0], touching_nodes[0][touching_node_n]->Rect().Min[axis] + min_size); - for (int touching_node_n = 0; touching_node_n < touching_nodes[1].Size; touching_node_n++) - resize_limits[1] = ImMin(resize_limits[1], touching_nodes[1][touching_node_n]->Rect().Max[axis] - min_size); - - // [DEBUG] Render touching nodes & limits - /* - ImDrawList* draw_list = node->HostWindow ? GetForegroundDrawList(node->HostWindow) : GetForegroundDrawList(GetMainViewport()); - for (int n = 0; n < 2; n++) - { - for (int touching_node_n = 0; touching_node_n < touching_nodes[n].Size; touching_node_n++) - draw_list->AddRect(touching_nodes[n][touching_node_n]->Pos, touching_nodes[n][touching_node_n]->Pos + touching_nodes[n][touching_node_n]->Size, IM_COL32(0, 255, 0, 255)); - if (axis == ImGuiAxis_X) - draw_list->AddLine(ImVec2(resize_limits[n], node->ChildNodes[n]->Pos.y), ImVec2(resize_limits[n], node->ChildNodes[n]->Pos.y + node->ChildNodes[n]->Size.y), IM_COL32(255, 0, 255, 255), 3.0f); - else - draw_list->AddLine(ImVec2(node->ChildNodes[n]->Pos.x, resize_limits[n]), ImVec2(node->ChildNodes[n]->Pos.x + node->ChildNodes[n]->Size.x, resize_limits[n]), IM_COL32(255, 0, 255, 255), 3.0f); - } - */ - } - - // Use a short delay before highlighting the splitter (and changing the mouse cursor) in order for regular mouse movement to not highlight many splitters - float cur_size_0 = child_0->Size[axis]; - float cur_size_1 = child_1->Size[axis]; - float min_size_0 = resize_limits[0] - child_0->Pos[axis]; - float min_size_1 = child_1->Pos[axis] + child_1->Size[axis] - resize_limits[1]; - ImU32 bg_col = GetColorU32(ImGuiCol_WindowBg); - if (SplitterBehavior(bb, GetID("##Splitter"), axis, &cur_size_0, &cur_size_1, min_size_0, min_size_1, WINDOWS_HOVER_PADDING, WINDOWS_RESIZE_FROM_EDGES_FEEDBACK_TIMER, bg_col)) - { - if (touching_nodes[0].Size > 0 && touching_nodes[1].Size > 0) - { - child_0->Size[axis] = child_0->SizeRef[axis] = cur_size_0; - child_1->Pos[axis] -= cur_size_1 - child_1->Size[axis]; - child_1->Size[axis] = child_1->SizeRef[axis] = cur_size_1; - - // Lock the size of every node that is a sibling of the node we are touching - // This might be less desirable if we can merge sibling of a same axis into the same parental level. - for (int side_n = 0; side_n < 2; side_n++) - for (int touching_node_n = 0; touching_node_n < touching_nodes[side_n].Size; touching_node_n++) - { - ImGuiDockNode* touching_node = touching_nodes[side_n][touching_node_n]; - //ImDrawList* draw_list = node->HostWindow ? GetForegroundDrawList(node->HostWindow) : GetForegroundDrawList(GetMainViewport()); - //draw_list->AddRect(touching_node->Pos, touching_node->Pos + touching_node->Size, IM_COL32(255, 128, 0, 255)); - while (touching_node->ParentNode != node) - { - if (touching_node->ParentNode->SplitAxis == axis) - { - // Mark other node so its size will be preserved during the upcoming call to DockNodeTreeUpdatePosSize(). - ImGuiDockNode* node_to_preserve = touching_node->ParentNode->ChildNodes[side_n]; - node_to_preserve->WantLockSizeOnce = true; - //draw_list->AddRect(touching_node->Pos, touching_node->Rect().Max, IM_COL32(255, 0, 0, 255)); - //draw_list->AddRectFilled(node_to_preserve->Pos, node_to_preserve->Rect().Max, IM_COL32(0, 255, 0, 100)); - } - touching_node = touching_node->ParentNode; - } - } - - DockNodeTreeUpdatePosSize(child_0, child_0->Pos, child_0->Size); - DockNodeTreeUpdatePosSize(child_1, child_1->Pos, child_1->Size); - MarkIniSettingsDirty(); - } - } - PopID(); - } - } - - if (child_0->IsVisible) - DockNodeTreeUpdateSplitter(child_0); - if (child_1->IsVisible) - DockNodeTreeUpdateSplitter(child_1); -} - -ImGuiDockNode* ImGui::DockNodeTreeFindFallbackLeafNode(ImGuiDockNode* node) -{ - if (node->IsLeafNode()) - return node; - if (ImGuiDockNode* leaf_node = DockNodeTreeFindFallbackLeafNode(node->ChildNodes[0])) - return leaf_node; - if (ImGuiDockNode* leaf_node = DockNodeTreeFindFallbackLeafNode(node->ChildNodes[1])) - return leaf_node; - return NULL; -} - -ImGuiDockNode* ImGui::DockNodeTreeFindVisibleNodeByPos(ImGuiDockNode* node, ImVec2 pos) -{ - if (!node->IsVisible) - return NULL; - - const float dock_spacing = 0.0f;// g.Style.ItemInnerSpacing.x; // FIXME: Relation to DOCKING_SPLITTER_SIZE? - ImRect r(node->Pos, node->Pos + node->Size); - r.Expand(dock_spacing * 0.5f); - bool inside = r.Contains(pos); - if (!inside) - return NULL; - - if (node->IsLeafNode()) - return node; - if (ImGuiDockNode* hovered_node = DockNodeTreeFindVisibleNodeByPos(node->ChildNodes[0], pos)) - return hovered_node; - if (ImGuiDockNode* hovered_node = DockNodeTreeFindVisibleNodeByPos(node->ChildNodes[1], pos)) - return hovered_node; - - // This means we are hovering over the splitter/spacing of a parent node - return node; -} - -//----------------------------------------------------------------------------- -// Docking: Public Functions (SetWindowDock, DockSpace, DockSpaceOverViewport) -//----------------------------------------------------------------------------- -// - SetWindowDock() [Internal] -// - DockSpace() -// - DockSpaceOverViewport() -//----------------------------------------------------------------------------- - -// [Internal] Called via SetNextWindowDockID() -void ImGui::SetWindowDock(ImGuiWindow* window, ImGuiID dock_id, ImGuiCond cond) -{ - // Test condition (NB: bit 0 is always true) and clear flags for next time - if (cond && (window->SetWindowDockAllowFlags & cond) == 0) - return; - window->SetWindowDockAllowFlags &= ~(ImGuiCond_Once | ImGuiCond_FirstUseEver | ImGuiCond_Appearing); - - if (window->DockId == dock_id) - return; - - // If the user attempt to set a dock id that is a split node, we'll dig within to find a suitable docking spot - ImGuiContext* ctx = GImGui; - if (ImGuiDockNode* new_node = DockContextFindNodeByID(ctx, dock_id)) - if (new_node->IsSplitNode()) - { - // Policy: Find central node or latest focused node. We first move back to our root node. - new_node = DockNodeGetRootNode(new_node); - if (new_node->CentralNode) - { - IM_ASSERT(new_node->CentralNode->IsCentralNode()); - dock_id = new_node->CentralNode->ID; - } - else - { - dock_id = new_node->LastFocusedNodeId; - } - } - - if (window->DockId == dock_id) - return; - - if (window->DockNode) - DockNodeRemoveWindow(window->DockNode, window, 0); - window->DockId = dock_id; -} - -// Create an explicit dockspace node within an existing window. Also expose dock node flags and creates a CentralNode by default. -// The Central Node is always displayed even when empty and shrink/extend according to the requested size of its neighbors. -// DockSpace() needs to be submitted _before_ any window they can host. If you use a dockspace, submit it early in your app. -// When ImGuiDockNodeFlags_KeepAliveOnly is set, nothing is submitted in the current window (function may be called from any location). -ImGuiID ImGui::DockSpace(ImGuiID id, const ImVec2& size_arg, ImGuiDockNodeFlags flags, const ImGuiWindowClass* window_class) -{ - ImGuiContext* ctx = GImGui; - ImGuiContext& g = *ctx; - ImGuiWindow* window = GetCurrentWindowRead(); - if (!(g.IO.ConfigFlags & ImGuiConfigFlags_DockingEnable)) - return 0; - - // Early out if parent window is hidden/collapsed - // This is faster but also DockNodeUpdateTabBar() relies on TabBarLayout() running (which won't if SkipItems=true) to set NextSelectedTabId = 0). See #2960. - // If for whichever reason this is causing problem we would need to ensure that DockNodeUpdateTabBar() ends up clearing NextSelectedTabId even if SkipItems=true. - if (window->SkipItems) - flags |= ImGuiDockNodeFlags_KeepAliveOnly; - if ((flags & ImGuiDockNodeFlags_KeepAliveOnly) == 0) - window = GetCurrentWindow(); // call to set window->WriteAccessed = true; - - IM_ASSERT((flags & ImGuiDockNodeFlags_DockSpace) == 0); - IM_ASSERT(id != 0); - ImGuiDockNode* node = DockContextFindNodeByID(ctx, id); - if (!node) - { - IMGUI_DEBUG_LOG_DOCKING("[docking] DockSpace: dockspace node 0x%08X created\n", id); - node = DockContextAddNode(ctx, id); - node->SetLocalFlags(ImGuiDockNodeFlags_CentralNode); - } - if (window_class && window_class->ClassId != node->WindowClass.ClassId) - IMGUI_DEBUG_LOG_DOCKING("[docking] DockSpace: dockspace node 0x%08X: setup WindowClass 0x%08X -> 0x%08X\n", id, node->WindowClass.ClassId, window_class->ClassId); - node->SharedFlags = flags; - node->WindowClass = window_class ? *window_class : ImGuiWindowClass(); - - // When a DockSpace transitioned form implicit to explicit this may be called a second time - // It is possible that the node has already been claimed by a docked window which appeared before the DockSpace() node, so we overwrite IsDockSpace again. - if (node->LastFrameActive == g.FrameCount && !(flags & ImGuiDockNodeFlags_KeepAliveOnly)) - { - IM_ASSERT(node->IsDockSpace() == false && "Cannot call DockSpace() twice a frame with the same ID"); - node->SetLocalFlags(node->LocalFlags | ImGuiDockNodeFlags_DockSpace); - return id; - } - node->SetLocalFlags(node->LocalFlags | ImGuiDockNodeFlags_DockSpace); - - // Keep alive mode, this is allow windows docked into this node so stay docked even if they are not visible - if (flags & ImGuiDockNodeFlags_KeepAliveOnly) - { - node->LastFrameAlive = g.FrameCount; - return id; - } - - const ImVec2 content_avail = GetContentRegionAvail(); - ImVec2 size = ImTrunc(size_arg); - if (size.x <= 0.0f) - size.x = ImMax(content_avail.x + size.x, 4.0f); // Arbitrary minimum child size (0.0f causing too much issues) - if (size.y <= 0.0f) - size.y = ImMax(content_avail.y + size.y, 4.0f); - IM_ASSERT(size.x > 0.0f && size.y > 0.0f); - - node->Pos = window->DC.CursorPos; - node->Size = node->SizeRef = size; - SetNextWindowPos(node->Pos); - SetNextWindowSize(node->Size); - g.NextWindowData.PosUndock = false; - - // FIXME-DOCK: Why do we need a child window to host a dockspace, could we host it in the existing window? - // FIXME-DOCK: What is the reason for not simply calling BeginChild()? (OK to have a reason but should be commented) - ImGuiWindowFlags window_flags = ImGuiWindowFlags_ChildWindow | ImGuiWindowFlags_DockNodeHost; - window_flags |= ImGuiWindowFlags_NoSavedSettings | ImGuiWindowFlags_NoResize | ImGuiWindowFlags_NoCollapse | ImGuiWindowFlags_NoTitleBar; - window_flags |= ImGuiWindowFlags_NoScrollbar | ImGuiWindowFlags_NoScrollWithMouse; - window_flags |= ImGuiWindowFlags_NoBackground; - - char title[256]; - ImFormatString(title, IM_ARRAYSIZE(title), "%s/DockSpace_%08X", window->Name, id); - - PushStyleVar(ImGuiStyleVar_ChildBorderSize, 0.0f); - Begin(title, NULL, window_flags); - PopStyleVar(); - - ImGuiWindow* host_window = g.CurrentWindow; - DockNodeSetupHostWindow(node, host_window); - host_window->ChildId = window->GetID(title); - node->OnlyNodeWithWindows = NULL; - - IM_ASSERT(node->IsRootNode()); - - // We need to handle the rare case were a central node is missing. - // This can happen if the node was first created manually with DockBuilderAddNode() but _without_ the ImGuiDockNodeFlags_Dockspace. - // Doing it correctly would set the _CentralNode flags, which would then propagate according to subsequent split. - // It would also be ambiguous to attempt to assign a central node while there are split nodes, so we wait until there's a single node remaining. - // The specific sub-property of _CentralNode we are interested in recovering here is the "Don't delete when empty" property, - // as it doesn't make sense for an empty dockspace to not have this property. - if (node->IsLeafNode() && !node->IsCentralNode()) - node->SetLocalFlags(node->LocalFlags | ImGuiDockNodeFlags_CentralNode); - - // Update the node - DockNodeUpdate(node); - - End(); - - ImRect bb(node->Pos, node->Pos + size); - ItemSize(size); - ItemAdd(bb, id, NULL, ImGuiItemFlags_NoNav); // Not a nav point (could be, would need to draw the nav rect and replicate/refactor activation from BeginChild(), but seems like CTRL+Tab works better here?) - if ((g.LastItemData.StatusFlags & ImGuiItemStatusFlags_HoveredRect) && IsWindowChildOf(g.HoveredWindow, host_window, false, true)) // To fullfill IsItemHovered(), similar to EndChild() - g.LastItemData.StatusFlags |= ImGuiItemStatusFlags_HoveredWindow; - - return id; -} - -// Tips: Use with ImGuiDockNodeFlags_PassthruCentralNode! -// The limitation with this call is that your window won't have a menu bar. -// Even though we could pass window flags, it would also require the user to be able to call BeginMenuBar() somehow meaning we can't Begin/End in a single function. -// But you can also use BeginMainMenuBar(). If you really want a menu bar inside the same window as the one hosting the dockspace, you will need to copy this code somewhere and tweak it. -ImGuiID ImGui::DockSpaceOverViewport(const ImGuiViewport* viewport, ImGuiDockNodeFlags dockspace_flags, const ImGuiWindowClass* window_class) -{ - if (viewport == NULL) - viewport = GetMainViewport(); - - SetNextWindowPos(viewport->WorkPos); - SetNextWindowSize(viewport->WorkSize); - SetNextWindowViewport(viewport->ID); - - ImGuiWindowFlags host_window_flags = 0; - host_window_flags |= ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_NoCollapse | ImGuiWindowFlags_NoResize | ImGuiWindowFlags_NoMove | ImGuiWindowFlags_NoDocking; - host_window_flags |= ImGuiWindowFlags_NoBringToFrontOnFocus | ImGuiWindowFlags_NoNavFocus; - if (dockspace_flags & ImGuiDockNodeFlags_PassthruCentralNode) - host_window_flags |= ImGuiWindowFlags_NoBackground; - - char label[32]; - ImFormatString(label, IM_ARRAYSIZE(label), "DockSpaceViewport_%08X", viewport->ID); - - PushStyleVar(ImGuiStyleVar_WindowRounding, 0.0f); - PushStyleVar(ImGuiStyleVar_WindowBorderSize, 0.0f); - PushStyleVar(ImGuiStyleVar_WindowPadding, ImVec2(0.0f, 0.0f)); - Begin(label, NULL, host_window_flags); - PopStyleVar(3); - - ImGuiID dockspace_id = GetID("DockSpace"); - DockSpace(dockspace_id, ImVec2(0.0f, 0.0f), dockspace_flags, window_class); - End(); - - return dockspace_id; -} - -//----------------------------------------------------------------------------- -// Docking: Builder Functions -//----------------------------------------------------------------------------- -// Very early end-user API to manipulate dock nodes. -// Only available in imgui_internal.h. Expect this API to change/break! -// It is expected that those functions are all called _before_ the dockspace node submission. -//----------------------------------------------------------------------------- -// - DockBuilderDockWindow() -// - DockBuilderGetNode() -// - DockBuilderSetNodePos() -// - DockBuilderSetNodeSize() -// - DockBuilderAddNode() -// - DockBuilderRemoveNode() -// - DockBuilderRemoveNodeChildNodes() -// - DockBuilderRemoveNodeDockedWindows() -// - DockBuilderSplitNode() -// - DockBuilderCopyNodeRec() -// - DockBuilderCopyNode() -// - DockBuilderCopyWindowSettings() -// - DockBuilderCopyDockSpace() -// - DockBuilderFinish() -//----------------------------------------------------------------------------- - -void ImGui::DockBuilderDockWindow(const char* window_name, ImGuiID node_id) -{ - // We don't preserve relative order of multiple docked windows (by clearing DockOrder back to -1) - ImGuiContext& g = *GImGui; IM_UNUSED(g); - IMGUI_DEBUG_LOG_DOCKING("[docking] DockBuilderDockWindow '%s' to node 0x%08X\n", window_name, node_id); - ImGuiID window_id = ImHashStr(window_name); - if (ImGuiWindow* window = FindWindowByID(window_id)) - { - // Apply to created window - ImGuiID prev_node_id = window->DockId; - SetWindowDock(window, node_id, ImGuiCond_Always); - if (window->DockId != prev_node_id) - window->DockOrder = -1; - } - else - { - // Apply to settings - ImGuiWindowSettings* settings = FindWindowSettingsByID(window_id); - if (settings == NULL) - settings = CreateNewWindowSettings(window_name); - if (settings->DockId != node_id) - settings->DockOrder = -1; - settings->DockId = node_id; - } -} - -ImGuiDockNode* ImGui::DockBuilderGetNode(ImGuiID node_id) -{ - ImGuiContext* ctx = GImGui; - return DockContextFindNodeByID(ctx, node_id); -} - -void ImGui::DockBuilderSetNodePos(ImGuiID node_id, ImVec2 pos) -{ - ImGuiContext* ctx = GImGui; - ImGuiDockNode* node = DockContextFindNodeByID(ctx, node_id); - if (node == NULL) - return; - node->Pos = pos; - node->AuthorityForPos = ImGuiDataAuthority_DockNode; -} - -void ImGui::DockBuilderSetNodeSize(ImGuiID node_id, ImVec2 size) -{ - ImGuiContext* ctx = GImGui; - ImGuiDockNode* node = DockContextFindNodeByID(ctx, node_id); - if (node == NULL) - return; - IM_ASSERT(size.x > 0.0f && size.y > 0.0f); - node->Size = node->SizeRef = size; - node->AuthorityForSize = ImGuiDataAuthority_DockNode; -} - -// Make sure to use the ImGuiDockNodeFlags_DockSpace flag to create a dockspace node! Otherwise this will create a floating node! -// - Floating node: you can then call DockBuilderSetNodePos()/DockBuilderSetNodeSize() to position and size the floating node. -// - Dockspace node: calling DockBuilderSetNodePos() is unnecessary. -// - If you intend to split a node immediately after creation using DockBuilderSplitNode(), make sure to call DockBuilderSetNodeSize() beforehand! -// For various reason, the splitting code currently needs a base size otherwise space may not be allocated as precisely as you would expect. -// - Use (id == 0) to let the system allocate a node identifier. -// - Existing node with a same id will be removed. -ImGuiID ImGui::DockBuilderAddNode(ImGuiID node_id, ImGuiDockNodeFlags flags) -{ - ImGuiContext* ctx = GImGui; - ImGuiContext& g = *ctx; IM_UNUSED(g); - IMGUI_DEBUG_LOG_DOCKING("[docking] DockBuilderAddNode 0x%08X flags=%08X\n", node_id, flags); - - if (node_id != 0) - DockBuilderRemoveNode(node_id); - - ImGuiDockNode* node = NULL; - if (flags & ImGuiDockNodeFlags_DockSpace) - { - DockSpace(node_id, ImVec2(0, 0), (flags & ~ImGuiDockNodeFlags_DockSpace) | ImGuiDockNodeFlags_KeepAliveOnly); - node = DockContextFindNodeByID(ctx, node_id); - } - else - { - node = DockContextAddNode(ctx, node_id); - node->SetLocalFlags(flags); - } - node->LastFrameAlive = ctx->FrameCount; // Set this otherwise BeginDocked will undock during the same frame. - return node->ID; -} - -void ImGui::DockBuilderRemoveNode(ImGuiID node_id) -{ - ImGuiContext* ctx = GImGui; - ImGuiContext& g = *ctx; IM_UNUSED(g); - IMGUI_DEBUG_LOG_DOCKING("[docking] DockBuilderRemoveNode 0x%08X\n", node_id); - - ImGuiDockNode* node = DockContextFindNodeByID(ctx, node_id); - if (node == NULL) - return; - DockBuilderRemoveNodeDockedWindows(node_id, true); - DockBuilderRemoveNodeChildNodes(node_id); - // Node may have moved or deleted if e.g. any merge happened - node = DockContextFindNodeByID(ctx, node_id); - if (node == NULL) - return; - if (node->IsCentralNode() && node->ParentNode) - node->ParentNode->SetLocalFlags(node->ParentNode->LocalFlags | ImGuiDockNodeFlags_CentralNode); - DockContextRemoveNode(ctx, node, true); -} - -// root_id = 0 to remove all, root_id != 0 to remove child of given node. -void ImGui::DockBuilderRemoveNodeChildNodes(ImGuiID root_id) -{ - ImGuiContext* ctx = GImGui; - ImGuiDockContext* dc = &ctx->DockContext; - - ImGuiDockNode* root_node = root_id ? DockContextFindNodeByID(ctx, root_id) : NULL; - if (root_id && root_node == NULL) - return; - bool has_central_node = false; - - ImGuiDataAuthority backup_root_node_authority_for_pos = root_node ? root_node->AuthorityForPos : ImGuiDataAuthority_Auto; - ImGuiDataAuthority backup_root_node_authority_for_size = root_node ? root_node->AuthorityForSize : ImGuiDataAuthority_Auto; - - // Process active windows - ImVector nodes_to_remove; - for (int n = 0; n < dc->Nodes.Data.Size; n++) - if (ImGuiDockNode* node = (ImGuiDockNode*)dc->Nodes.Data[n].val_p) - { - bool want_removal = (root_id == 0) || (node->ID != root_id && DockNodeGetRootNode(node)->ID == root_id); - if (want_removal) - { - if (node->IsCentralNode()) - has_central_node = true; - if (root_id != 0) - DockContextQueueNotifyRemovedNode(ctx, node); - if (root_node) - { - DockNodeMoveWindows(root_node, node); - DockSettingsRenameNodeReferences(node->ID, root_node->ID); - } - nodes_to_remove.push_back(node); - } - } - - // DockNodeMoveWindows->DockNodeAddWindow will normally set those when reaching two windows (which is only adequate during interactive merge) - // Make sure we don't lose our current pos/size. (FIXME-DOCK: Consider tidying up that code in DockNodeAddWindow instead) - if (root_node) - { - root_node->AuthorityForPos = backup_root_node_authority_for_pos; - root_node->AuthorityForSize = backup_root_node_authority_for_size; - } - - // Apply to settings - for (ImGuiWindowSettings* settings = ctx->SettingsWindows.begin(); settings != NULL; settings = ctx->SettingsWindows.next_chunk(settings)) - if (ImGuiID window_settings_dock_id = settings->DockId) - for (int n = 0; n < nodes_to_remove.Size; n++) - if (nodes_to_remove[n]->ID == window_settings_dock_id) - { - settings->DockId = root_id; - break; - } - - // Not really efficient, but easier to destroy a whole hierarchy considering DockContextRemoveNode is attempting to merge nodes - if (nodes_to_remove.Size > 1) - ImQsort(nodes_to_remove.Data, nodes_to_remove.Size, sizeof(ImGuiDockNode*), DockNodeComparerDepthMostFirst); - for (int n = 0; n < nodes_to_remove.Size; n++) - DockContextRemoveNode(ctx, nodes_to_remove[n], false); - - if (root_id == 0) - { - dc->Nodes.Clear(); - dc->Requests.clear(); - } - else if (has_central_node) - { - root_node->CentralNode = root_node; - root_node->SetLocalFlags(root_node->LocalFlags | ImGuiDockNodeFlags_CentralNode); - } -} - -void ImGui::DockBuilderRemoveNodeDockedWindows(ImGuiID root_id, bool clear_settings_refs) -{ - // Clear references in settings - ImGuiContext* ctx = GImGui; - ImGuiContext& g = *ctx; - if (clear_settings_refs) - { - for (ImGuiWindowSettings* settings = g.SettingsWindows.begin(); settings != NULL; settings = g.SettingsWindows.next_chunk(settings)) - { - bool want_removal = (root_id == 0) || (settings->DockId == root_id); - if (!want_removal && settings->DockId != 0) - if (ImGuiDockNode* node = DockContextFindNodeByID(ctx, settings->DockId)) - if (DockNodeGetRootNode(node)->ID == root_id) - want_removal = true; - if (want_removal) - settings->DockId = 0; - } - } - - // Clear references in windows - for (int n = 0; n < g.Windows.Size; n++) - { - ImGuiWindow* window = g.Windows[n]; - bool want_removal = (root_id == 0) || (window->DockNode && DockNodeGetRootNode(window->DockNode)->ID == root_id) || (window->DockNodeAsHost && window->DockNodeAsHost->ID == root_id); - if (want_removal) - { - const ImGuiID backup_dock_id = window->DockId; - IM_UNUSED(backup_dock_id); - DockContextProcessUndockWindow(ctx, window, clear_settings_refs); - if (!clear_settings_refs) - IM_ASSERT(window->DockId == backup_dock_id); - } - } -} - -// If 'out_id_at_dir' or 'out_id_at_opposite_dir' are non NULL, the function will write out the ID of the two new nodes created. -// Return value is ID of the node at the specified direction, so same as (*out_id_at_dir) if that pointer is set. -// FIXME-DOCK: We are not exposing nor using split_outer. -ImGuiID ImGui::DockBuilderSplitNode(ImGuiID id, ImGuiDir split_dir, float size_ratio_for_node_at_dir, ImGuiID* out_id_at_dir, ImGuiID* out_id_at_opposite_dir) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(split_dir != ImGuiDir_None); - IMGUI_DEBUG_LOG_DOCKING("[docking] DockBuilderSplitNode: node 0x%08X, split_dir %d\n", id, split_dir); - - ImGuiDockNode* node = DockContextFindNodeByID(&g, id); - if (node == NULL) - { - IM_ASSERT(node != NULL); - return 0; - } - - IM_ASSERT(!node->IsSplitNode()); // Assert if already Split - - ImGuiDockRequest req; - req.Type = ImGuiDockRequestType_Split; - req.DockTargetWindow = NULL; - req.DockTargetNode = node; - req.DockPayload = NULL; - req.DockSplitDir = split_dir; - req.DockSplitRatio = ImSaturate((split_dir == ImGuiDir_Left || split_dir == ImGuiDir_Up) ? size_ratio_for_node_at_dir : 1.0f - size_ratio_for_node_at_dir); - req.DockSplitOuter = false; - DockContextProcessDock(&g, &req); - - ImGuiID id_at_dir = node->ChildNodes[(split_dir == ImGuiDir_Left || split_dir == ImGuiDir_Up) ? 0 : 1]->ID; - ImGuiID id_at_opposite_dir = node->ChildNodes[(split_dir == ImGuiDir_Left || split_dir == ImGuiDir_Up) ? 1 : 0]->ID; - if (out_id_at_dir) - *out_id_at_dir = id_at_dir; - if (out_id_at_opposite_dir) - *out_id_at_opposite_dir = id_at_opposite_dir; - return id_at_dir; -} - -static ImGuiDockNode* DockBuilderCopyNodeRec(ImGuiDockNode* src_node, ImGuiID dst_node_id_if_known, ImVector* out_node_remap_pairs) -{ - ImGuiContext& g = *GImGui; - ImGuiDockNode* dst_node = ImGui::DockContextAddNode(&g, dst_node_id_if_known); - dst_node->SharedFlags = src_node->SharedFlags; - dst_node->LocalFlags = src_node->LocalFlags; - dst_node->LocalFlagsInWindows = ImGuiDockNodeFlags_None; - dst_node->Pos = src_node->Pos; - dst_node->Size = src_node->Size; - dst_node->SizeRef = src_node->SizeRef; - dst_node->SplitAxis = src_node->SplitAxis; - dst_node->UpdateMergedFlags(); - - out_node_remap_pairs->push_back(src_node->ID); - out_node_remap_pairs->push_back(dst_node->ID); - - for (int child_n = 0; child_n < IM_ARRAYSIZE(src_node->ChildNodes); child_n++) - if (src_node->ChildNodes[child_n]) - { - dst_node->ChildNodes[child_n] = DockBuilderCopyNodeRec(src_node->ChildNodes[child_n], 0, out_node_remap_pairs); - dst_node->ChildNodes[child_n]->ParentNode = dst_node; - } - - IMGUI_DEBUG_LOG_DOCKING("[docking] Fork node %08X -> %08X (%d childs)\n", src_node->ID, dst_node->ID, dst_node->IsSplitNode() ? 2 : 0); - return dst_node; -} - -void ImGui::DockBuilderCopyNode(ImGuiID src_node_id, ImGuiID dst_node_id, ImVector* out_node_remap_pairs) -{ - ImGuiContext* ctx = GImGui; - IM_ASSERT(src_node_id != 0); - IM_ASSERT(dst_node_id != 0); - IM_ASSERT(out_node_remap_pairs != NULL); - - DockBuilderRemoveNode(dst_node_id); - - ImGuiDockNode* src_node = DockContextFindNodeByID(ctx, src_node_id); - IM_ASSERT(src_node != NULL); - - out_node_remap_pairs->clear(); - DockBuilderCopyNodeRec(src_node, dst_node_id, out_node_remap_pairs); - - IM_ASSERT((out_node_remap_pairs->Size % 2) == 0); -} - -void ImGui::DockBuilderCopyWindowSettings(const char* src_name, const char* dst_name) -{ - ImGuiWindow* src_window = FindWindowByName(src_name); - if (src_window == NULL) - return; - if (ImGuiWindow* dst_window = FindWindowByName(dst_name)) - { - dst_window->Pos = src_window->Pos; - dst_window->Size = src_window->Size; - dst_window->SizeFull = src_window->SizeFull; - dst_window->Collapsed = src_window->Collapsed; - } - else - { - ImGuiWindowSettings* dst_settings = FindWindowSettingsByID(ImHashStr(dst_name)); - if (!dst_settings) - dst_settings = CreateNewWindowSettings(dst_name); - ImVec2ih window_pos_2ih = ImVec2ih(src_window->Pos); - if (src_window->ViewportId != 0 && src_window->ViewportId != IMGUI_VIEWPORT_DEFAULT_ID) - { - dst_settings->ViewportPos = window_pos_2ih; - dst_settings->ViewportId = src_window->ViewportId; - dst_settings->Pos = ImVec2ih(0, 0); - } - else - { - dst_settings->Pos = window_pos_2ih; - } - dst_settings->Size = ImVec2ih(src_window->SizeFull); - dst_settings->Collapsed = src_window->Collapsed; - } -} - -// FIXME: Will probably want to change this signature, in particular how the window remapping pairs are passed. -void ImGui::DockBuilderCopyDockSpace(ImGuiID src_dockspace_id, ImGuiID dst_dockspace_id, ImVector* in_window_remap_pairs) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(src_dockspace_id != 0); - IM_ASSERT(dst_dockspace_id != 0); - IM_ASSERT(in_window_remap_pairs != NULL); - IM_ASSERT((in_window_remap_pairs->Size % 2) == 0); - - // Duplicate entire dock - // FIXME: When overwriting dst_dockspace_id, windows that aren't part of our dockspace window class but that are docked in a same node will be split apart, - // whereas we could attempt to at least keep them together in a new, same floating node. - ImVector node_remap_pairs; - DockBuilderCopyNode(src_dockspace_id, dst_dockspace_id, &node_remap_pairs); - - // Attempt to transition all the upcoming windows associated to dst_dockspace_id into the newly created hierarchy of dock nodes - // (The windows associated to src_dockspace_id are staying in place) - ImVector src_windows; - for (int remap_window_n = 0; remap_window_n < in_window_remap_pairs->Size; remap_window_n += 2) - { - const char* src_window_name = (*in_window_remap_pairs)[remap_window_n]; - const char* dst_window_name = (*in_window_remap_pairs)[remap_window_n + 1]; - ImGuiID src_window_id = ImHashStr(src_window_name); - src_windows.push_back(src_window_id); - - // Search in the remapping tables - ImGuiID src_dock_id = 0; - if (ImGuiWindow* src_window = FindWindowByID(src_window_id)) - src_dock_id = src_window->DockId; - else if (ImGuiWindowSettings* src_window_settings = FindWindowSettingsByID(src_window_id)) - src_dock_id = src_window_settings->DockId; - ImGuiID dst_dock_id = 0; - for (int dock_remap_n = 0; dock_remap_n < node_remap_pairs.Size; dock_remap_n += 2) - if (node_remap_pairs[dock_remap_n] == src_dock_id) - { - dst_dock_id = node_remap_pairs[dock_remap_n + 1]; - //node_remap_pairs[dock_remap_n] = node_remap_pairs[dock_remap_n + 1] = 0; // Clear - break; - } - - if (dst_dock_id != 0) - { - // Docked windows gets redocked into the new node hierarchy. - IMGUI_DEBUG_LOG_DOCKING("[docking] Remap live window '%s' 0x%08X -> '%s' 0x%08X\n", src_window_name, src_dock_id, dst_window_name, dst_dock_id); - DockBuilderDockWindow(dst_window_name, dst_dock_id); - } - else - { - // Floating windows gets their settings transferred (regardless of whether the new window already exist or not) - // When this is leading to a Copy and not a Move, we would get two overlapping floating windows. Could we possibly dock them together? - IMGUI_DEBUG_LOG_DOCKING("[docking] Remap window settings '%s' -> '%s'\n", src_window_name, dst_window_name); - DockBuilderCopyWindowSettings(src_window_name, dst_window_name); - } - } - - // Anything else in the source nodes of 'node_remap_pairs' are windows that are not included in the remapping list. - // Find those windows and move to them to the cloned dock node. This may be optional? - // Dock those are a second step as undocking would invalidate source dock nodes. - struct DockRemainingWindowTask { ImGuiWindow* Window; ImGuiID DockId; DockRemainingWindowTask(ImGuiWindow* window, ImGuiID dock_id) { Window = window; DockId = dock_id; } }; - ImVector dock_remaining_windows; - for (int dock_remap_n = 0; dock_remap_n < node_remap_pairs.Size; dock_remap_n += 2) - if (ImGuiID src_dock_id = node_remap_pairs[dock_remap_n]) - { - ImGuiID dst_dock_id = node_remap_pairs[dock_remap_n + 1]; - ImGuiDockNode* node = DockBuilderGetNode(src_dock_id); - for (int window_n = 0; window_n < node->Windows.Size; window_n++) - { - ImGuiWindow* window = node->Windows[window_n]; - if (src_windows.contains(window->ID)) - continue; - - // Docked windows gets redocked into the new node hierarchy. - IMGUI_DEBUG_LOG_DOCKING("[docking] Remap window '%s' %08X -> %08X\n", window->Name, src_dock_id, dst_dock_id); - dock_remaining_windows.push_back(DockRemainingWindowTask(window, dst_dock_id)); - } - } - for (const DockRemainingWindowTask& task : dock_remaining_windows) - DockBuilderDockWindow(task.Window->Name, task.DockId); -} - -// FIXME-DOCK: This is awkward because in series of split user is likely to loose access to its root node. -void ImGui::DockBuilderFinish(ImGuiID root_id) -{ - ImGuiContext* ctx = GImGui; - //DockContextRebuild(ctx); - DockContextBuildAddWindowsToNodes(ctx, root_id); -} - -//----------------------------------------------------------------------------- -// Docking: Begin/End Support Functions (called from Begin/End) -//----------------------------------------------------------------------------- -// - GetWindowAlwaysWantOwnTabBar() -// - DockContextBindNodeToWindow() -// - BeginDocked() -// - BeginDockableDragDropSource() -// - BeginDockableDragDropTarget() -//----------------------------------------------------------------------------- - -bool ImGui::GetWindowAlwaysWantOwnTabBar(ImGuiWindow* window) -{ - ImGuiContext& g = *GImGui; - if (g.IO.ConfigDockingAlwaysTabBar || window->WindowClass.DockingAlwaysTabBar) - if ((window->Flags & (ImGuiWindowFlags_ChildWindow | ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_NoDocking)) == 0) - if (!window->IsFallbackWindow) // We don't support AlwaysTabBar on the fallback/implicit window to avoid unused dock-node overhead/noise - return true; - return false; -} - -static ImGuiDockNode* ImGui::DockContextBindNodeToWindow(ImGuiContext* ctx, ImGuiWindow* window) -{ - ImGuiContext& g = *ctx; - ImGuiDockNode* node = DockContextFindNodeByID(ctx, window->DockId); - IM_ASSERT(window->DockNode == NULL); - - // We should not be docking into a split node (SetWindowDock should avoid this) - if (node && node->IsSplitNode()) - { - DockContextProcessUndockWindow(ctx, window); - return NULL; - } - - // Create node - if (node == NULL) - { - node = DockContextAddNode(ctx, window->DockId); - node->AuthorityForPos = node->AuthorityForSize = node->AuthorityForViewport = ImGuiDataAuthority_Window; - node->LastFrameAlive = g.FrameCount; - } - - // If the node just turned visible and is part of a hierarchy, it doesn't have a Size assigned by DockNodeTreeUpdatePosSize() yet, - // so we're forcing a Pos/Size update from the first ancestor that is already visible (often it will be the root node). - // If we don't do this, the window will be assigned a zero-size on its first frame, which won't ideally warm up the layout. - // This is a little wonky because we don't normally update the Pos/Size of visible node mid-frame. - if (!node->IsVisible) - { - ImGuiDockNode* ancestor_node = node; - while (!ancestor_node->IsVisible && ancestor_node->ParentNode) - ancestor_node = ancestor_node->ParentNode; - IM_ASSERT(ancestor_node->Size.x > 0.0f && ancestor_node->Size.y > 0.0f); - DockNodeUpdateHasCentralNodeChild(DockNodeGetRootNode(ancestor_node)); - DockNodeTreeUpdatePosSize(ancestor_node, ancestor_node->Pos, ancestor_node->Size, node); - } - - // Add window to node - bool node_was_visible = node->IsVisible; - DockNodeAddWindow(node, window, true); - node->IsVisible = node_was_visible; // Don't mark visible right away (so DockContextEndFrame() doesn't render it, maybe other side effects? will see) - IM_ASSERT(node == window->DockNode); - return node; -} - -void ImGui::BeginDocked(ImGuiWindow* window, bool* p_open) -{ - ImGuiContext* ctx = GImGui; - ImGuiContext& g = *ctx; - - // Clear fields ahead so most early-out paths don't have to do it - window->DockIsActive = window->DockNodeIsVisible = window->DockTabIsVisible = false; - - const bool auto_dock_node = GetWindowAlwaysWantOwnTabBar(window); - if (auto_dock_node) - { - if (window->DockId == 0) - { - IM_ASSERT(window->DockNode == NULL); - window->DockId = DockContextGenNodeID(ctx); - } - } - else - { - // Calling SetNextWindowPos() undock windows by default (by setting PosUndock) - bool want_undock = false; - want_undock |= (window->Flags & ImGuiWindowFlags_NoDocking) != 0; - want_undock |= (g.NextWindowData.Flags & ImGuiNextWindowDataFlags_HasPos) && (window->SetWindowPosAllowFlags & g.NextWindowData.PosCond) && g.NextWindowData.PosUndock; - if (want_undock) - { - DockContextProcessUndockWindow(ctx, window); - return; - } - } - - // Bind to our dock node - ImGuiDockNode* node = window->DockNode; - if (node != NULL) - IM_ASSERT(window->DockId == node->ID); - if (window->DockId != 0 && node == NULL) - { - node = DockContextBindNodeToWindow(ctx, window); - if (node == NULL) - return; - } - -#if 0 - // Undock if the ImGuiDockNodeFlags_NoDockingInCentralNode got set - if (node->IsCentralNode && (node->Flags & ImGuiDockNodeFlags_NoDockingInCentralNode)) - { - DockContextProcessUndockWindow(ctx, window); - return; - } -#endif - - // Undock if our dockspace node disappeared - // Note how we are testing for LastFrameAlive and NOT LastFrameActive. A DockSpace node can be maintained alive while being inactive with ImGuiDockNodeFlags_KeepAliveOnly. - if (node->LastFrameAlive < g.FrameCount) - { - // If the window has been orphaned, transition the docknode to an implicit node processed in DockContextNewFrameUpdateDocking() - ImGuiDockNode* root_node = DockNodeGetRootNode(node); - if (root_node->LastFrameAlive < g.FrameCount) - DockContextProcessUndockWindow(ctx, window); - else - window->DockIsActive = true; - return; - } - - // Store style overrides - for (int color_n = 0; color_n < ImGuiWindowDockStyleCol_COUNT; color_n++) - window->DockStyle.Colors[color_n] = ColorConvertFloat4ToU32(g.Style.Colors[GWindowDockStyleColors[color_n]]); - - // Fast path return. It is common for windows to hold on a persistent DockId but be the only visible window, - // and never create neither a host window neither a tab bar. - // FIXME-DOCK: replace ->HostWindow NULL compare with something more explicit (~was initially intended as a first frame test) - if (node->HostWindow == NULL) - { - if (node->State == ImGuiDockNodeState_HostWindowHiddenBecauseWindowsAreResizing) - window->DockIsActive = true; - if (node->Windows.Size > 1 && window->Appearing) // Only hide appearing window - DockNodeHideWindowDuringHostWindowCreation(window); - return; - } - - // We can have zero-sized nodes (e.g. children of a small-size dockspace) - IM_ASSERT(node->HostWindow); - IM_ASSERT(node->IsLeafNode()); - IM_ASSERT(node->Size.x >= 0.0f && node->Size.y >= 0.0f); - node->State = ImGuiDockNodeState_HostWindowVisible; - - // Undock if we are submitted earlier than the host window - if (!(node->MergedFlags & ImGuiDockNodeFlags_KeepAliveOnly) && window->BeginOrderWithinContext < node->HostWindow->BeginOrderWithinContext) - { - DockContextProcessUndockWindow(ctx, window); - return; - } - - // Position/Size window - SetNextWindowPos(node->Pos); - SetNextWindowSize(node->Size); - g.NextWindowData.PosUndock = false; // Cancel implicit undocking of SetNextWindowPos() - window->DockIsActive = true; - window->DockNodeIsVisible = true; - window->DockTabIsVisible = false; - if (node->MergedFlags & ImGuiDockNodeFlags_KeepAliveOnly) - return; - - // When the window is selected we mark it as visible. - if (node->VisibleWindow == window) - window->DockTabIsVisible = true; - - // Update window flag - IM_ASSERT((window->Flags & ImGuiWindowFlags_ChildWindow) == 0); - window->Flags |= ImGuiWindowFlags_ChildWindow | ImGuiWindowFlags_AlwaysUseWindowPadding | ImGuiWindowFlags_NoResize; - if (node->IsHiddenTabBar() || node->IsNoTabBar()) - window->Flags |= ImGuiWindowFlags_NoTitleBar; - else - window->Flags &= ~ImGuiWindowFlags_NoTitleBar; // Clear the NoTitleBar flag in case the user set it: confusingly enough we need a title bar height so we are correctly offset, but it won't be displayed! - - // Save new dock order only if the window has been visible once already - // This allows multiple windows to be created in the same frame and have their respective dock orders preserved. - if (node->TabBar && window->WasActive) - window->DockOrder = (short)DockNodeGetTabOrder(window); - - if ((node->WantCloseAll || node->WantCloseTabId == window->TabId) && p_open != NULL) - *p_open = false; - - // Update ChildId to allow returning from Child to Parent with Escape - ImGuiWindow* parent_window = window->DockNode->HostWindow; - window->ChildId = parent_window->GetID(window->Name); -} - -void ImGui::BeginDockableDragDropSource(ImGuiWindow* window) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(g.ActiveId == window->MoveId); - IM_ASSERT(g.MovingWindow == window); - IM_ASSERT(g.CurrentWindow == window); - - // 0: Hold SHIFT to disable docking, 1: Hold SHIFT to enable docking. - if (g.IO.ConfigDockingWithShift != g.IO.KeyShift) - { - // When ConfigDockingWithShift is set, display a tooltip to increase UI affordance. - // We cannot set for HoveredWindowUnderMovingWindow != NULL here, as it is only valid/useful when drag and drop is already active - // (because of the 'is_mouse_dragging_with_an_expected_destination' logic in UpdateViewportsNewFrame() function) - if (g.IO.ConfigDockingWithShift && g.MouseStationaryTimer >= 1.0f && g.ActiveId >= 1.0f) - SetTooltip("%s", LocalizeGetMsg(ImGuiLocKey_DockingHoldShiftToDock)); - return; - } - - g.LastItemData.ID = window->MoveId; - window = window->RootWindowDockTree; - IM_ASSERT((window->Flags & ImGuiWindowFlags_NoDocking) == 0); - bool is_drag_docking = (g.IO.ConfigDockingWithShift) || ImRect(0, 0, window->SizeFull.x, GetFrameHeight()).Contains(g.ActiveIdClickOffset); // FIXME-DOCKING: Need to make this stateful and explicit - if (is_drag_docking && BeginDragDropSource(ImGuiDragDropFlags_SourceNoPreviewTooltip | ImGuiDragDropFlags_SourceNoHoldToOpenOthers | ImGuiDragDropFlags_SourceAutoExpirePayload)) - { - SetDragDropPayload(IMGUI_PAYLOAD_TYPE_WINDOW, &window, sizeof(window)); - EndDragDropSource(); - - // Store style overrides - for (int color_n = 0; color_n < ImGuiWindowDockStyleCol_COUNT; color_n++) - window->DockStyle.Colors[color_n] = ColorConvertFloat4ToU32(g.Style.Colors[GWindowDockStyleColors[color_n]]); - } -} - -void ImGui::BeginDockableDragDropTarget(ImGuiWindow* window) -{ - ImGuiContext* ctx = GImGui; - ImGuiContext& g = *ctx; - - //IM_ASSERT(window->RootWindowDockTree == window); // May also be a DockSpace - IM_ASSERT((window->Flags & ImGuiWindowFlags_NoDocking) == 0); - if (!g.DragDropActive) - return; - //GetForegroundDrawList(window)->AddRect(window->Pos, window->Pos + window->Size, IM_COL32(255, 255, 0, 255)); - if (!BeginDragDropTargetCustom(window->Rect(), window->ID)) - return; - - // Peek into the payload before calling AcceptDragDropPayload() so we can handle overlapping dock nodes with filtering - // (this is a little unusual pattern, normally most code would call AcceptDragDropPayload directly) - const ImGuiPayload* payload = &g.DragDropPayload; - if (!payload->IsDataType(IMGUI_PAYLOAD_TYPE_WINDOW) || !DockNodeIsDropAllowed(window, *(ImGuiWindow**)payload->Data)) - { - EndDragDropTarget(); - return; - } - - ImGuiWindow* payload_window = *(ImGuiWindow**)payload->Data; - if (AcceptDragDropPayload(IMGUI_PAYLOAD_TYPE_WINDOW, ImGuiDragDropFlags_AcceptBeforeDelivery | ImGuiDragDropFlags_AcceptNoDrawDefaultRect)) - { - // Select target node - // (Important: we cannot use g.HoveredDockNode here! Because each of our target node have filters based on payload, each candidate drop target will do its own evaluation) - bool dock_into_floating_window = false; - ImGuiDockNode* node = NULL; - if (window->DockNodeAsHost) - { - // Cannot assume that node will != NULL even though we passed the rectangle test: it depends on padding/spacing handled by DockNodeTreeFindVisibleNodeByPos(). - node = DockNodeTreeFindVisibleNodeByPos(window->DockNodeAsHost, g.IO.MousePos); - - // There is an edge case when docking into a dockspace which only has _inactive_ nodes (because none of the windows are active) - // In this case we need to fallback into any leaf mode, possibly the central node. - // FIXME-20181220: We should not have to test for IsLeafNode() here but we have another bug to fix first. - if (node && node->IsDockSpace() && node->IsRootNode()) - node = (node->CentralNode && node->IsLeafNode()) ? node->CentralNode : DockNodeTreeFindFallbackLeafNode(node); - } - else - { - if (window->DockNode) - node = window->DockNode; - else - dock_into_floating_window = true; // Dock into a regular window - } - - const ImRect explicit_target_rect = (node && node->TabBar && !node->IsHiddenTabBar() && !node->IsNoTabBar()) ? node->TabBar->BarRect : ImRect(window->Pos, window->Pos + ImVec2(window->Size.x, GetFrameHeight())); - const bool is_explicit_target = g.IO.ConfigDockingWithShift || IsMouseHoveringRect(explicit_target_rect.Min, explicit_target_rect.Max); - - // Preview docking request and find out split direction/ratio - //const bool do_preview = true; // Ignore testing for payload->IsPreview() which removes one frame of delay, but breaks overlapping drop targets within the same window. - const bool do_preview = payload->IsPreview() || payload->IsDelivery(); - if (do_preview && (node != NULL || dock_into_floating_window)) - { - // If we have a non-leaf node it means we are hovering the border of a parent node, in which case only outer markers will appear. - ImGuiDockPreviewData split_inner; - ImGuiDockPreviewData split_outer; - ImGuiDockPreviewData* split_data = &split_inner; - if (node && (node->ParentNode || node->IsCentralNode() || !node->IsLeafNode())) - if (ImGuiDockNode* root_node = DockNodeGetRootNode(node)) - { - DockNodePreviewDockSetup(window, root_node, payload_window, NULL, &split_outer, is_explicit_target, true); - if (split_outer.IsSplitDirExplicit) - split_data = &split_outer; - } - if (!node || node->IsLeafNode()) - DockNodePreviewDockSetup(window, node, payload_window, NULL, &split_inner, is_explicit_target, false); - if (split_data == &split_outer) - split_inner.IsDropAllowed = false; - - // Draw inner then outer, so that previewed tab (in inner data) will be behind the outer drop boxes - DockNodePreviewDockRender(window, node, payload_window, &split_inner); - DockNodePreviewDockRender(window, node, payload_window, &split_outer); - - // Queue docking request - if (split_data->IsDropAllowed && payload->IsDelivery()) - DockContextQueueDock(ctx, window, split_data->SplitNode, payload_window, split_data->SplitDir, split_data->SplitRatio, split_data == &split_outer); - } - } - EndDragDropTarget(); -} - -//----------------------------------------------------------------------------- -// Docking: Settings -//----------------------------------------------------------------------------- -// - DockSettingsRenameNodeReferences() -// - DockSettingsRemoveNodeReferences() -// - DockSettingsFindNodeSettings() -// - DockSettingsHandler_ApplyAll() -// - DockSettingsHandler_ReadOpen() -// - DockSettingsHandler_ReadLine() -// - DockSettingsHandler_DockNodeToSettings() -// - DockSettingsHandler_WriteAll() -//----------------------------------------------------------------------------- - -static void ImGui::DockSettingsRenameNodeReferences(ImGuiID old_node_id, ImGuiID new_node_id) -{ - ImGuiContext& g = *GImGui; - IMGUI_DEBUG_LOG_DOCKING("[docking] DockSettingsRenameNodeReferences: from 0x%08X -> to 0x%08X\n", old_node_id, new_node_id); - for (int window_n = 0; window_n < g.Windows.Size; window_n++) - { - ImGuiWindow* window = g.Windows[window_n]; - if (window->DockId == old_node_id && window->DockNode == NULL) - window->DockId = new_node_id; - } - //// FIXME-OPT: We could remove this loop by storing the index in the map - for (ImGuiWindowSettings* settings = g.SettingsWindows.begin(); settings != NULL; settings = g.SettingsWindows.next_chunk(settings)) - if (settings->DockId == old_node_id) - settings->DockId = new_node_id; -} - -// Remove references stored in ImGuiWindowSettings to the given ImGuiDockNodeSettings -static void ImGui::DockSettingsRemoveNodeReferences(ImGuiID* node_ids, int node_ids_count) -{ - ImGuiContext& g = *GImGui; - int found = 0; - //// FIXME-OPT: We could remove this loop by storing the index in the map - for (ImGuiWindowSettings* settings = g.SettingsWindows.begin(); settings != NULL; settings = g.SettingsWindows.next_chunk(settings)) - for (int node_n = 0; node_n < node_ids_count; node_n++) - if (settings->DockId == node_ids[node_n]) - { - settings->DockId = 0; - settings->DockOrder = -1; - if (++found < node_ids_count) - break; - return; - } -} - -static ImGuiDockNodeSettings* ImGui::DockSettingsFindNodeSettings(ImGuiContext* ctx, ImGuiID id) -{ - // FIXME-OPT - ImGuiDockContext* dc = &ctx->DockContext; - for (int n = 0; n < dc->NodesSettings.Size; n++) - if (dc->NodesSettings[n].ID == id) - return &dc->NodesSettings[n]; - return NULL; -} - -// Clear settings data -static void ImGui::DockSettingsHandler_ClearAll(ImGuiContext* ctx, ImGuiSettingsHandler*) -{ - ImGuiDockContext* dc = &ctx->DockContext; - dc->NodesSettings.clear(); - DockContextClearNodes(ctx, 0, true); -} - -// Recreate nodes based on settings data -static void ImGui::DockSettingsHandler_ApplyAll(ImGuiContext* ctx, ImGuiSettingsHandler*) -{ - // Prune settings at boot time only - ImGuiDockContext* dc = &ctx->DockContext; - if (ctx->Windows.Size == 0) - DockContextPruneUnusedSettingsNodes(ctx); - DockContextBuildNodesFromSettings(ctx, dc->NodesSettings.Data, dc->NodesSettings.Size); - DockContextBuildAddWindowsToNodes(ctx, 0); -} - -static void* ImGui::DockSettingsHandler_ReadOpen(ImGuiContext*, ImGuiSettingsHandler*, const char* name) -{ - if (strcmp(name, "Data") != 0) - return NULL; - return (void*)1; -} - -static void ImGui::DockSettingsHandler_ReadLine(ImGuiContext* ctx, ImGuiSettingsHandler*, void*, const char* line) -{ - char c = 0; - int x = 0, y = 0; - int r = 0; - - // Parsing, e.g. - // " DockNode ID=0x00000001 Pos=383,193 Size=201,322 Split=Y,0.506 " - // " DockNode ID=0x00000002 Parent=0x00000001 " - // Important: this code expect currently fields in a fixed order. - ImGuiDockNodeSettings node; - line = ImStrSkipBlank(line); - if (strncmp(line, "DockNode", 8) == 0) { line = ImStrSkipBlank(line + strlen("DockNode")); } - else if (strncmp(line, "DockSpace", 9) == 0) { line = ImStrSkipBlank(line + strlen("DockSpace")); node.Flags |= ImGuiDockNodeFlags_DockSpace; } - else return; - if (sscanf(line, "ID=0x%08X%n", &node.ID, &r) == 1) { line += r; } else return; - if (sscanf(line, " Parent=0x%08X%n", &node.ParentNodeId, &r) == 1) { line += r; if (node.ParentNodeId == 0) return; } - if (sscanf(line, " Window=0x%08X%n", &node.ParentWindowId, &r) ==1) { line += r; if (node.ParentWindowId == 0) return; } - if (node.ParentNodeId == 0) - { - if (sscanf(line, " Pos=%i,%i%n", &x, &y, &r) == 2) { line += r; node.Pos = ImVec2ih((short)x, (short)y); } else return; - if (sscanf(line, " Size=%i,%i%n", &x, &y, &r) == 2) { line += r; node.Size = ImVec2ih((short)x, (short)y); } else return; - } - else - { - if (sscanf(line, " SizeRef=%i,%i%n", &x, &y, &r) == 2) { line += r; node.SizeRef = ImVec2ih((short)x, (short)y); } - } - if (sscanf(line, " Split=%c%n", &c, &r) == 1) { line += r; if (c == 'X') node.SplitAxis = ImGuiAxis_X; else if (c == 'Y') node.SplitAxis = ImGuiAxis_Y; } - if (sscanf(line, " NoResize=%d%n", &x, &r) == 1) { line += r; if (x != 0) node.Flags |= ImGuiDockNodeFlags_NoResize; } - if (sscanf(line, " CentralNode=%d%n", &x, &r) == 1) { line += r; if (x != 0) node.Flags |= ImGuiDockNodeFlags_CentralNode; } - if (sscanf(line, " NoTabBar=%d%n", &x, &r) == 1) { line += r; if (x != 0) node.Flags |= ImGuiDockNodeFlags_NoTabBar; } - if (sscanf(line, " HiddenTabBar=%d%n", &x, &r) == 1) { line += r; if (x != 0) node.Flags |= ImGuiDockNodeFlags_HiddenTabBar; } - if (sscanf(line, " NoWindowMenuButton=%d%n", &x, &r) == 1) { line += r; if (x != 0) node.Flags |= ImGuiDockNodeFlags_NoWindowMenuButton; } - if (sscanf(line, " NoCloseButton=%d%n", &x, &r) == 1) { line += r; if (x != 0) node.Flags |= ImGuiDockNodeFlags_NoCloseButton; } - if (sscanf(line, " Selected=0x%08X%n", &node.SelectedTabId,&r) == 1) { line += r; } - if (node.ParentNodeId != 0) - if (ImGuiDockNodeSettings* parent_settings = DockSettingsFindNodeSettings(ctx, node.ParentNodeId)) - node.Depth = parent_settings->Depth + 1; - ctx->DockContext.NodesSettings.push_back(node); -} - -static void DockSettingsHandler_DockNodeToSettings(ImGuiDockContext* dc, ImGuiDockNode* node, int depth) -{ - ImGuiDockNodeSettings node_settings; - IM_ASSERT(depth < (1 << (sizeof(node_settings.Depth) << 3))); - node_settings.ID = node->ID; - node_settings.ParentNodeId = node->ParentNode ? node->ParentNode->ID : 0; - node_settings.ParentWindowId = (node->IsDockSpace() && node->HostWindow && node->HostWindow->ParentWindow) ? node->HostWindow->ParentWindow->ID : 0; - node_settings.SelectedTabId = node->SelectedTabId; - node_settings.SplitAxis = (signed char)(node->IsSplitNode() ? node->SplitAxis : ImGuiAxis_None); - node_settings.Depth = (char)depth; - node_settings.Flags = (node->LocalFlags & ImGuiDockNodeFlags_SavedFlagsMask_); - node_settings.Pos = ImVec2ih(node->Pos); - node_settings.Size = ImVec2ih(node->Size); - node_settings.SizeRef = ImVec2ih(node->SizeRef); - dc->NodesSettings.push_back(node_settings); - if (node->ChildNodes[0]) - DockSettingsHandler_DockNodeToSettings(dc, node->ChildNodes[0], depth + 1); - if (node->ChildNodes[1]) - DockSettingsHandler_DockNodeToSettings(dc, node->ChildNodes[1], depth + 1); -} - -static void ImGui::DockSettingsHandler_WriteAll(ImGuiContext* ctx, ImGuiSettingsHandler* handler, ImGuiTextBuffer* buf) -{ - ImGuiContext& g = *ctx; - ImGuiDockContext* dc = &ctx->DockContext; - if (!(g.IO.ConfigFlags & ImGuiConfigFlags_DockingEnable)) - return; - - // Gather settings data - // (unlike our windows settings, because nodes are always built we can do a full rewrite of the SettingsNode buffer) - dc->NodesSettings.resize(0); - dc->NodesSettings.reserve(dc->Nodes.Data.Size); - for (int n = 0; n < dc->Nodes.Data.Size; n++) - if (ImGuiDockNode* node = (ImGuiDockNode*)dc->Nodes.Data[n].val_p) - if (node->IsRootNode()) - DockSettingsHandler_DockNodeToSettings(dc, node, 0); - - int max_depth = 0; - for (int node_n = 0; node_n < dc->NodesSettings.Size; node_n++) - max_depth = ImMax((int)dc->NodesSettings[node_n].Depth, max_depth); - - // Write to text buffer - buf->appendf("[%s][Data]\n", handler->TypeName); - for (int node_n = 0; node_n < dc->NodesSettings.Size; node_n++) - { - const int line_start_pos = buf->size(); (void)line_start_pos; - const ImGuiDockNodeSettings* node_settings = &dc->NodesSettings[node_n]; - buf->appendf("%*s%s%*s", node_settings->Depth * 2, "", (node_settings->Flags & ImGuiDockNodeFlags_DockSpace) ? "DockSpace" : "DockNode ", (max_depth - node_settings->Depth) * 2, ""); // Text align nodes to facilitate looking at .ini file - buf->appendf(" ID=0x%08X", node_settings->ID); - if (node_settings->ParentNodeId) - { - buf->appendf(" Parent=0x%08X SizeRef=%d,%d", node_settings->ParentNodeId, node_settings->SizeRef.x, node_settings->SizeRef.y); - } - else - { - if (node_settings->ParentWindowId) - buf->appendf(" Window=0x%08X", node_settings->ParentWindowId); - buf->appendf(" Pos=%d,%d Size=%d,%d", node_settings->Pos.x, node_settings->Pos.y, node_settings->Size.x, node_settings->Size.y); - } - if (node_settings->SplitAxis != ImGuiAxis_None) - buf->appendf(" Split=%c", (node_settings->SplitAxis == ImGuiAxis_X) ? 'X' : 'Y'); - if (node_settings->Flags & ImGuiDockNodeFlags_NoResize) - buf->appendf(" NoResize=1"); - if (node_settings->Flags & ImGuiDockNodeFlags_CentralNode) - buf->appendf(" CentralNode=1"); - if (node_settings->Flags & ImGuiDockNodeFlags_NoTabBar) - buf->appendf(" NoTabBar=1"); - if (node_settings->Flags & ImGuiDockNodeFlags_HiddenTabBar) - buf->appendf(" HiddenTabBar=1"); - if (node_settings->Flags & ImGuiDockNodeFlags_NoWindowMenuButton) - buf->appendf(" NoWindowMenuButton=1"); - if (node_settings->Flags & ImGuiDockNodeFlags_NoCloseButton) - buf->appendf(" NoCloseButton=1"); - if (node_settings->SelectedTabId) - buf->appendf(" Selected=0x%08X", node_settings->SelectedTabId); - - // [DEBUG] Include comments in the .ini file to ease debugging (this makes saving slower!) - if (g.IO.ConfigDebugIniSettings) - if (ImGuiDockNode* node = DockContextFindNodeByID(ctx, node_settings->ID)) - { - buf->appendf("%*s", ImMax(2, (line_start_pos + 92) - buf->size()), ""); // Align everything - if (node->IsDockSpace() && node->HostWindow && node->HostWindow->ParentWindow) - buf->appendf(" ; in '%s'", node->HostWindow->ParentWindow->Name); - // Iterate settings so we can give info about windows that didn't exist during the session. - int contains_window = 0; - for (ImGuiWindowSettings* settings = g.SettingsWindows.begin(); settings != NULL; settings = g.SettingsWindows.next_chunk(settings)) - if (settings->DockId == node_settings->ID) - { - if (contains_window++ == 0) - buf->appendf(" ; contains "); - buf->appendf("'%s' ", settings->GetName()); - } - } - - buf->appendf("\n"); - } - buf->appendf("\n"); -} - - -//----------------------------------------------------------------------------- -// [SECTION] PLATFORM DEPENDENT HELPERS -//----------------------------------------------------------------------------- - -#if defined(_WIN32) && !defined(IMGUI_DISABLE_WIN32_FUNCTIONS) && !defined(IMGUI_DISABLE_WIN32_DEFAULT_CLIPBOARD_FUNCTIONS) - -#ifdef _MSC_VER -#pragma comment(lib, "user32") -#pragma comment(lib, "kernel32") -#endif - -// Win32 clipboard implementation -// We use g.ClipboardHandlerData for temporary storage to ensure it is freed on Shutdown() -static const char* GetClipboardTextFn_DefaultImpl(void* user_data_ctx) -{ - ImGuiContext& g = *(ImGuiContext*)user_data_ctx; - g.ClipboardHandlerData.clear(); - if (!::OpenClipboard(NULL)) - return NULL; - HANDLE wbuf_handle = ::GetClipboardData(CF_UNICODETEXT); - if (wbuf_handle == NULL) - { - ::CloseClipboard(); - return NULL; - } - if (const WCHAR* wbuf_global = (const WCHAR*)::GlobalLock(wbuf_handle)) - { - int buf_len = ::WideCharToMultiByte(CP_UTF8, 0, wbuf_global, -1, NULL, 0, NULL, NULL); - g.ClipboardHandlerData.resize(buf_len); - ::WideCharToMultiByte(CP_UTF8, 0, wbuf_global, -1, g.ClipboardHandlerData.Data, buf_len, NULL, NULL); - } - ::GlobalUnlock(wbuf_handle); - ::CloseClipboard(); - return g.ClipboardHandlerData.Data; -} - -static void SetClipboardTextFn_DefaultImpl(void*, const char* text) -{ - if (!::OpenClipboard(NULL)) - return; - const int wbuf_length = ::MultiByteToWideChar(CP_UTF8, 0, text, -1, NULL, 0); - HGLOBAL wbuf_handle = ::GlobalAlloc(GMEM_MOVEABLE, (SIZE_T)wbuf_length * sizeof(WCHAR)); - if (wbuf_handle == NULL) - { - ::CloseClipboard(); - return; - } - WCHAR* wbuf_global = (WCHAR*)::GlobalLock(wbuf_handle); - ::MultiByteToWideChar(CP_UTF8, 0, text, -1, wbuf_global, wbuf_length); - ::GlobalUnlock(wbuf_handle); - ::EmptyClipboard(); - if (::SetClipboardData(CF_UNICODETEXT, wbuf_handle) == NULL) - ::GlobalFree(wbuf_handle); - ::CloseClipboard(); -} - -#elif defined(__APPLE__) && TARGET_OS_OSX && defined(IMGUI_ENABLE_OSX_DEFAULT_CLIPBOARD_FUNCTIONS) - -#include // Use old API to avoid need for separate .mm file -static PasteboardRef main_clipboard = 0; - -// OSX clipboard implementation -// If you enable this you will need to add '-framework ApplicationServices' to your linker command-line! -static void SetClipboardTextFn_DefaultImpl(void*, const char* text) -{ - if (!main_clipboard) - PasteboardCreate(kPasteboardClipboard, &main_clipboard); - PasteboardClear(main_clipboard); - CFDataRef cf_data = CFDataCreate(kCFAllocatorDefault, (const UInt8*)text, strlen(text)); - if (cf_data) - { - PasteboardPutItemFlavor(main_clipboard, (PasteboardItemID)1, CFSTR("public.utf8-plain-text"), cf_data, 0); - CFRelease(cf_data); - } -} - -static const char* GetClipboardTextFn_DefaultImpl(void* user_data_ctx) -{ - ImGuiContext& g = *(ImGuiContext*)user_data_ctx; - if (!main_clipboard) - PasteboardCreate(kPasteboardClipboard, &main_clipboard); - PasteboardSynchronize(main_clipboard); - - ItemCount item_count = 0; - PasteboardGetItemCount(main_clipboard, &item_count); - for (ItemCount i = 0; i < item_count; i++) - { - PasteboardItemID item_id = 0; - PasteboardGetItemIdentifier(main_clipboard, i + 1, &item_id); - CFArrayRef flavor_type_array = 0; - PasteboardCopyItemFlavors(main_clipboard, item_id, &flavor_type_array); - for (CFIndex j = 0, nj = CFArrayGetCount(flavor_type_array); j < nj; j++) - { - CFDataRef cf_data; - if (PasteboardCopyItemFlavorData(main_clipboard, item_id, CFSTR("public.utf8-plain-text"), &cf_data) == noErr) - { - g.ClipboardHandlerData.clear(); - int length = (int)CFDataGetLength(cf_data); - g.ClipboardHandlerData.resize(length + 1); - CFDataGetBytes(cf_data, CFRangeMake(0, length), (UInt8*)g.ClipboardHandlerData.Data); - g.ClipboardHandlerData[length] = 0; - CFRelease(cf_data); - return g.ClipboardHandlerData.Data; - } - } - } - return NULL; -} - -#else - -// Local Dear ImGui-only clipboard implementation, if user hasn't defined better clipboard handlers. -static const char* GetClipboardTextFn_DefaultImpl(void* user_data_ctx) -{ - ImGuiContext& g = *(ImGuiContext*)user_data_ctx; - return g.ClipboardHandlerData.empty() ? NULL : g.ClipboardHandlerData.begin(); -} - -static void SetClipboardTextFn_DefaultImpl(void* user_data_ctx, const char* text) -{ - ImGuiContext& g = *(ImGuiContext*)user_data_ctx; - g.ClipboardHandlerData.clear(); - const char* text_end = text + strlen(text); - g.ClipboardHandlerData.resize((int)(text_end - text) + 1); - memcpy(&g.ClipboardHandlerData[0], text, (size_t)(text_end - text)); - g.ClipboardHandlerData[(int)(text_end - text)] = 0; -} - -#endif - -// Win32 API IME support (for Asian languages, etc.) -#if defined(_WIN32) && !defined(IMGUI_DISABLE_WIN32_FUNCTIONS) && !defined(IMGUI_DISABLE_WIN32_DEFAULT_IME_FUNCTIONS) - -#include -#ifdef _MSC_VER -#pragma comment(lib, "imm32") -#endif - -static void SetPlatformImeDataFn_DefaultImpl(ImGuiViewport* viewport, ImGuiPlatformImeData* data) -{ - // Notify OS Input Method Editor of text input position - HWND hwnd = (HWND)viewport->PlatformHandleRaw; - if (hwnd == 0) - return; - - //::ImmAssociateContextEx(hwnd, NULL, data->WantVisible ? IACE_DEFAULT : 0); - if (HIMC himc = ::ImmGetContext(hwnd)) - { - COMPOSITIONFORM composition_form = {}; - composition_form.ptCurrentPos.x = (LONG)(data->InputPos.x - viewport->Pos.x); - composition_form.ptCurrentPos.y = (LONG)(data->InputPos.y - viewport->Pos.y); - composition_form.dwStyle = CFS_FORCE_POSITION; - ::ImmSetCompositionWindow(himc, &composition_form); - CANDIDATEFORM candidate_form = {}; - candidate_form.dwStyle = CFS_CANDIDATEPOS; - candidate_form.ptCurrentPos.x = (LONG)(data->InputPos.x - viewport->Pos.x); - candidate_form.ptCurrentPos.y = (LONG)(data->InputPos.y - viewport->Pos.y); - ::ImmSetCandidateWindow(himc, &candidate_form); - ::ImmReleaseContext(hwnd, himc); - } -} - -#else - -static void SetPlatformImeDataFn_DefaultImpl(ImGuiViewport*, ImGuiPlatformImeData*) {} - -#endif - -//----------------------------------------------------------------------------- -// [SECTION] METRICS/DEBUGGER WINDOW -//----------------------------------------------------------------------------- -// - RenderViewportThumbnail() [Internal] -// - RenderViewportsThumbnails() [Internal] -// - DebugTextEncoding() -// - MetricsHelpMarker() [Internal] -// - ShowFontAtlas() [Internal] -// - ShowMetricsWindow() -// - DebugNodeColumns() [Internal] -// - DebugNodeDockNode() [Internal] -// - DebugNodeDrawList() [Internal] -// - DebugNodeDrawCmdShowMeshAndBoundingBox() [Internal] -// - DebugNodeFont() [Internal] -// - DebugNodeFontGlyph() [Internal] -// - DebugNodeStorage() [Internal] -// - DebugNodeTabBar() [Internal] -// - DebugNodeViewport() [Internal] -// - DebugNodeWindow() [Internal] -// - DebugNodeWindowSettings() [Internal] -// - DebugNodeWindowsList() [Internal] -// - DebugNodeWindowsListByBeginStackParent() [Internal] -//----------------------------------------------------------------------------- - -#ifndef IMGUI_DISABLE_DEBUG_TOOLS - -void ImGui::DebugRenderViewportThumbnail(ImDrawList* draw_list, ImGuiViewportP* viewport, const ImRect& bb) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - - ImVec2 scale = bb.GetSize() / viewport->Size; - ImVec2 off = bb.Min - viewport->Pos * scale; - float alpha_mul = (viewport->Flags & ImGuiViewportFlags_IsMinimized) ? 0.30f : 1.00f; - window->DrawList->AddRectFilled(bb.Min, bb.Max, GetColorU32(ImGuiCol_Border, alpha_mul * 0.40f)); - for (ImGuiWindow* thumb_window : g.Windows) - { - if (!thumb_window->WasActive || (thumb_window->Flags & ImGuiWindowFlags_ChildWindow)) - continue; - if (thumb_window->Viewport != viewport) - continue; - - ImRect thumb_r = thumb_window->Rect(); - ImRect title_r = thumb_window->TitleBarRect(); - thumb_r = ImRect(ImTrunc(off + thumb_r.Min * scale), ImTrunc(off + thumb_r.Max * scale)); - title_r = ImRect(ImTrunc(off + title_r.Min * scale), ImTrunc(off + ImVec2(title_r.Max.x, title_r.Min.y) * scale) + ImVec2(0,5)); // Exaggerate title bar height - thumb_r.ClipWithFull(bb); - title_r.ClipWithFull(bb); - const bool window_is_focused = (g.NavWindow && thumb_window->RootWindowForTitleBarHighlight == g.NavWindow->RootWindowForTitleBarHighlight); - window->DrawList->AddRectFilled(thumb_r.Min, thumb_r.Max, GetColorU32(ImGuiCol_WindowBg, alpha_mul)); - window->DrawList->AddRectFilled(title_r.Min, title_r.Max, GetColorU32(window_is_focused ? ImGuiCol_TitleBgActive : ImGuiCol_TitleBg, alpha_mul)); - window->DrawList->AddRect(thumb_r.Min, thumb_r.Max, GetColorU32(ImGuiCol_Border, alpha_mul)); - window->DrawList->AddText(g.Font, g.FontSize * 1.0f, title_r.Min, GetColorU32(ImGuiCol_Text, alpha_mul), thumb_window->Name, FindRenderedTextEnd(thumb_window->Name)); - } - draw_list->AddRect(bb.Min, bb.Max, GetColorU32(ImGuiCol_Border, alpha_mul)); -} - -static void RenderViewportsThumbnails() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - - // We don't display full monitor bounds (we could, but it often looks awkward), instead we display just enough to cover all of our viewports. - float SCALE = 1.0f / 8.0f; - ImRect bb_full(FLT_MAX, FLT_MAX, -FLT_MAX, -FLT_MAX); - for (ImGuiViewportP* viewport : g.Viewports) - bb_full.Add(viewport->GetMainRect()); - ImVec2 p = window->DC.CursorPos; - ImVec2 off = p - bb_full.Min * SCALE; - for (ImGuiViewportP* viewport : g.Viewports) - { - ImRect viewport_draw_bb(off + (viewport->Pos) * SCALE, off + (viewport->Pos + viewport->Size) * SCALE); - ImGui::DebugRenderViewportThumbnail(window->DrawList, viewport, viewport_draw_bb); - } - ImGui::Dummy(bb_full.GetSize() * SCALE); -} - -static int IMGUI_CDECL ViewportComparerByLastFocusedStampCount(const void* lhs, const void* rhs) -{ - const ImGuiViewportP* a = *(const ImGuiViewportP* const*)lhs; - const ImGuiViewportP* b = *(const ImGuiViewportP* const*)rhs; - return b->LastFocusedStampCount - a->LastFocusedStampCount; -} - -// Draw an arbitrary US keyboard layout to visualize translated keys -void ImGui::DebugRenderKeyboardPreview(ImDrawList* draw_list) -{ - const ImVec2 key_size = ImVec2(35.0f, 35.0f); - const float key_rounding = 3.0f; - const ImVec2 key_face_size = ImVec2(25.0f, 25.0f); - const ImVec2 key_face_pos = ImVec2(5.0f, 3.0f); - const float key_face_rounding = 2.0f; - const ImVec2 key_label_pos = ImVec2(7.0f, 4.0f); - const ImVec2 key_step = ImVec2(key_size.x - 1.0f, key_size.y - 1.0f); - const float key_row_offset = 9.0f; - - ImVec2 board_min = GetCursorScreenPos(); - ImVec2 board_max = ImVec2(board_min.x + 3 * key_step.x + 2 * key_row_offset + 10.0f, board_min.y + 3 * key_step.y + 10.0f); - ImVec2 start_pos = ImVec2(board_min.x + 5.0f - key_step.x, board_min.y); - - struct KeyLayoutData { int Row, Col; const char* Label; ImGuiKey Key; }; - const KeyLayoutData keys_to_display[] = - { - { 0, 0, "", ImGuiKey_Tab }, { 0, 1, "Q", ImGuiKey_Q }, { 0, 2, "W", ImGuiKey_W }, { 0, 3, "E", ImGuiKey_E }, { 0, 4, "R", ImGuiKey_R }, - { 1, 0, "", ImGuiKey_CapsLock }, { 1, 1, "A", ImGuiKey_A }, { 1, 2, "S", ImGuiKey_S }, { 1, 3, "D", ImGuiKey_D }, { 1, 4, "F", ImGuiKey_F }, - { 2, 0, "", ImGuiKey_LeftShift },{ 2, 1, "Z", ImGuiKey_Z }, { 2, 2, "X", ImGuiKey_X }, { 2, 3, "C", ImGuiKey_C }, { 2, 4, "V", ImGuiKey_V } - }; - - // Elements rendered manually via ImDrawList API are not clipped automatically. - // While not strictly necessary, here IsItemVisible() is used to avoid rendering these shapes when they are out of view. - Dummy(board_max - board_min); - if (!IsItemVisible()) - return; - draw_list->PushClipRect(board_min, board_max, true); - for (int n = 0; n < IM_ARRAYSIZE(keys_to_display); n++) - { - const KeyLayoutData* key_data = &keys_to_display[n]; - ImVec2 key_min = ImVec2(start_pos.x + key_data->Col * key_step.x + key_data->Row * key_row_offset, start_pos.y + key_data->Row * key_step.y); - ImVec2 key_max = key_min + key_size; - draw_list->AddRectFilled(key_min, key_max, IM_COL32(204, 204, 204, 255), key_rounding); - draw_list->AddRect(key_min, key_max, IM_COL32(24, 24, 24, 255), key_rounding); - ImVec2 face_min = ImVec2(key_min.x + key_face_pos.x, key_min.y + key_face_pos.y); - ImVec2 face_max = ImVec2(face_min.x + key_face_size.x, face_min.y + key_face_size.y); - draw_list->AddRect(face_min, face_max, IM_COL32(193, 193, 193, 255), key_face_rounding, ImDrawFlags_None, 2.0f); - draw_list->AddRectFilled(face_min, face_max, IM_COL32(252, 252, 252, 255), key_face_rounding); - ImVec2 label_min = ImVec2(key_min.x + key_label_pos.x, key_min.y + key_label_pos.y); - draw_list->AddText(label_min, IM_COL32(64, 64, 64, 255), key_data->Label); - if (IsKeyDown(key_data->Key)) - draw_list->AddRectFilled(key_min, key_max, IM_COL32(255, 0, 0, 128), key_rounding); - } - draw_list->PopClipRect(); -} - -// Helper tool to diagnose between text encoding issues and font loading issues. Pass your UTF-8 string and verify that there are correct. -void ImGui::DebugTextEncoding(const char* str) -{ - Text("Text: \"%s\"", str); - if (!BeginTable("##DebugTextEncoding", 4, ImGuiTableFlags_Borders | ImGuiTableFlags_RowBg | ImGuiTableFlags_SizingFixedFit | ImGuiTableFlags_Resizable)) - return; - TableSetupColumn("Offset"); - TableSetupColumn("UTF-8"); - TableSetupColumn("Glyph"); - TableSetupColumn("Codepoint"); - TableHeadersRow(); - for (const char* p = str; *p != 0; ) - { - unsigned int c; - const int c_utf8_len = ImTextCharFromUtf8(&c, p, NULL); - TableNextColumn(); - Text("%d", (int)(p - str)); - TableNextColumn(); - for (int byte_index = 0; byte_index < c_utf8_len; byte_index++) - { - if (byte_index > 0) - SameLine(); - Text("0x%02X", (int)(unsigned char)p[byte_index]); - } - TableNextColumn(); - if (GetFont()->FindGlyphNoFallback((ImWchar)c)) - TextUnformatted(p, p + c_utf8_len); - else - TextUnformatted((c == IM_UNICODE_CODEPOINT_INVALID) ? "[invalid]" : "[missing]"); - TableNextColumn(); - Text("U+%04X", (int)c); - p += c_utf8_len; - } - EndTable(); -} - -// Avoid naming collision with imgui_demo.cpp's HelpMarker() for unity builds. -static void MetricsHelpMarker(const char* desc) -{ - ImGui::TextDisabled("(?)"); - if (ImGui::BeginItemTooltip()) - { - ImGui::PushTextWrapPos(ImGui::GetFontSize() * 35.0f); - ImGui::TextUnformatted(desc); - ImGui::PopTextWrapPos(); - ImGui::EndTooltip(); - } -} - -// [DEBUG] List fonts in a font atlas and display its texture -void ImGui::ShowFontAtlas(ImFontAtlas* atlas) -{ - for (ImFont* font : atlas->Fonts) - { - PushID(font); - DebugNodeFont(font); - PopID(); - } - if (TreeNode("Font Atlas", "Font Atlas (%dx%d pixels)", atlas->TexWidth, atlas->TexHeight)) - { - ImGuiContext& g = *GImGui; - ImGuiMetricsConfig* cfg = &g.DebugMetricsConfig; - Checkbox("Tint with Text Color", &cfg->ShowAtlasTintedWithTextColor); // Using text color ensure visibility of core atlas data, but will alter custom colored icons - ImVec4 tint_col = cfg->ShowAtlasTintedWithTextColor ? GetStyleColorVec4(ImGuiCol_Text) : ImVec4(1.0f, 1.0f, 1.0f, 1.0f); - ImVec4 border_col = GetStyleColorVec4(ImGuiCol_Border); - Image(atlas->TexID, ImVec2((float)atlas->TexWidth, (float)atlas->TexHeight), ImVec2(0.0f, 0.0f), ImVec2(1.0f, 1.0f), tint_col, border_col); - TreePop(); - } -} - -void ImGui::ShowMetricsWindow(bool* p_open) -{ - ImGuiContext& g = *GImGui; - ImGuiIO& io = g.IO; - ImGuiMetricsConfig* cfg = &g.DebugMetricsConfig; - if (cfg->ShowDebugLog) - ShowDebugLogWindow(&cfg->ShowDebugLog); - if (cfg->ShowIDStackTool) - ShowIDStackToolWindow(&cfg->ShowIDStackTool); - - if (!Begin("Dear ImGui Metrics/Debugger", p_open) || GetCurrentWindow()->BeginCount > 1) - { - End(); - return; - } - - // Basic info - Text("Dear ImGui %s", GetVersion()); - Text("Application average %.3f ms/frame (%.1f FPS)", 1000.0f / io.Framerate, io.Framerate); - Text("%d vertices, %d indices (%d triangles)", io.MetricsRenderVertices, io.MetricsRenderIndices, io.MetricsRenderIndices / 3); - Text("%d visible windows, %d current allocations", io.MetricsRenderWindows, g.DebugAllocInfo.TotalAllocCount - g.DebugAllocInfo.TotalFreeCount); - //SameLine(); if (SmallButton("GC")) { g.GcCompactAll = true; } - - Separator(); - - // Debugging enums - enum { WRT_OuterRect, WRT_OuterRectClipped, WRT_InnerRect, WRT_InnerClipRect, WRT_WorkRect, WRT_Content, WRT_ContentIdeal, WRT_ContentRegionRect, WRT_Count }; // Windows Rect Type - const char* wrt_rects_names[WRT_Count] = { "OuterRect", "OuterRectClipped", "InnerRect", "InnerClipRect", "WorkRect", "Content", "ContentIdeal", "ContentRegionRect" }; - enum { TRT_OuterRect, TRT_InnerRect, TRT_WorkRect, TRT_HostClipRect, TRT_InnerClipRect, TRT_BackgroundClipRect, TRT_ColumnsRect, TRT_ColumnsWorkRect, TRT_ColumnsClipRect, TRT_ColumnsContentHeadersUsed, TRT_ColumnsContentHeadersIdeal, TRT_ColumnsContentFrozen, TRT_ColumnsContentUnfrozen, TRT_Count }; // Tables Rect Type - const char* trt_rects_names[TRT_Count] = { "OuterRect", "InnerRect", "WorkRect", "HostClipRect", "InnerClipRect", "BackgroundClipRect", "ColumnsRect", "ColumnsWorkRect", "ColumnsClipRect", "ColumnsContentHeadersUsed", "ColumnsContentHeadersIdeal", "ColumnsContentFrozen", "ColumnsContentUnfrozen" }; - if (cfg->ShowWindowsRectsType < 0) - cfg->ShowWindowsRectsType = WRT_WorkRect; - if (cfg->ShowTablesRectsType < 0) - cfg->ShowTablesRectsType = TRT_WorkRect; - - struct Funcs - { - static ImRect GetTableRect(ImGuiTable* table, int rect_type, int n) - { - ImGuiTableInstanceData* table_instance = TableGetInstanceData(table, table->InstanceCurrent); // Always using last submitted instance - if (rect_type == TRT_OuterRect) { return table->OuterRect; } - else if (rect_type == TRT_InnerRect) { return table->InnerRect; } - else if (rect_type == TRT_WorkRect) { return table->WorkRect; } - else if (rect_type == TRT_HostClipRect) { return table->HostClipRect; } - else if (rect_type == TRT_InnerClipRect) { return table->InnerClipRect; } - else if (rect_type == TRT_BackgroundClipRect) { return table->BgClipRect; } - else if (rect_type == TRT_ColumnsRect) { ImGuiTableColumn* c = &table->Columns[n]; return ImRect(c->MinX, table->InnerClipRect.Min.y, c->MaxX, table->InnerClipRect.Min.y + table_instance->LastOuterHeight); } - else if (rect_type == TRT_ColumnsWorkRect) { ImGuiTableColumn* c = &table->Columns[n]; return ImRect(c->WorkMinX, table->WorkRect.Min.y, c->WorkMaxX, table->WorkRect.Max.y); } - else if (rect_type == TRT_ColumnsClipRect) { ImGuiTableColumn* c = &table->Columns[n]; return c->ClipRect; } - else if (rect_type == TRT_ColumnsContentHeadersUsed){ ImGuiTableColumn* c = &table->Columns[n]; return ImRect(c->WorkMinX, table->InnerClipRect.Min.y, c->ContentMaxXHeadersUsed, table->InnerClipRect.Min.y + table_instance->LastTopHeadersRowHeight); } // Note: y1/y2 not always accurate - else if (rect_type == TRT_ColumnsContentHeadersIdeal){ImGuiTableColumn* c = &table->Columns[n]; return ImRect(c->WorkMinX, table->InnerClipRect.Min.y, c->ContentMaxXHeadersIdeal, table->InnerClipRect.Min.y + table_instance->LastTopHeadersRowHeight); } - else if (rect_type == TRT_ColumnsContentFrozen) { ImGuiTableColumn* c = &table->Columns[n]; return ImRect(c->WorkMinX, table->InnerClipRect.Min.y, c->ContentMaxXFrozen, table->InnerClipRect.Min.y + table_instance->LastFrozenHeight); } - else if (rect_type == TRT_ColumnsContentUnfrozen) { ImGuiTableColumn* c = &table->Columns[n]; return ImRect(c->WorkMinX, table->InnerClipRect.Min.y + table_instance->LastFrozenHeight, c->ContentMaxXUnfrozen, table->InnerClipRect.Max.y); } - IM_ASSERT(0); - return ImRect(); - } - - static ImRect GetWindowRect(ImGuiWindow* window, int rect_type) - { - if (rect_type == WRT_OuterRect) { return window->Rect(); } - else if (rect_type == WRT_OuterRectClipped) { return window->OuterRectClipped; } - else if (rect_type == WRT_InnerRect) { return window->InnerRect; } - else if (rect_type == WRT_InnerClipRect) { return window->InnerClipRect; } - else if (rect_type == WRT_WorkRect) { return window->WorkRect; } - else if (rect_type == WRT_Content) { ImVec2 min = window->InnerRect.Min - window->Scroll + window->WindowPadding; return ImRect(min, min + window->ContentSize); } - else if (rect_type == WRT_ContentIdeal) { ImVec2 min = window->InnerRect.Min - window->Scroll + window->WindowPadding; return ImRect(min, min + window->ContentSizeIdeal); } - else if (rect_type == WRT_ContentRegionRect) { return window->ContentRegionRect; } - IM_ASSERT(0); - return ImRect(); - } - }; - - // Tools - if (TreeNode("Tools")) - { - bool show_encoding_viewer = TreeNode("UTF-8 Encoding viewer"); - SameLine(); - MetricsHelpMarker("You can also call ImGui::DebugTextEncoding() from your code with a given string to test that your UTF-8 encoding settings are correct."); - if (show_encoding_viewer) - { - static char buf[100] = ""; - SetNextItemWidth(-FLT_MIN); - InputText("##Text", buf, IM_ARRAYSIZE(buf)); - if (buf[0] != 0) - DebugTextEncoding(buf); - TreePop(); - } - - // The Item Picker tool is super useful to visually select an item and break into the call-stack of where it was submitted. - if (Checkbox("Show Item Picker", &g.DebugItemPickerActive) && g.DebugItemPickerActive) - DebugStartItemPicker(); - SameLine(); - MetricsHelpMarker("Will call the IM_DEBUG_BREAK() macro to break in debugger.\nWarning: If you don't have a debugger attached, this will probably crash."); - - Checkbox("Show Debug Log", &cfg->ShowDebugLog); - SameLine(); - MetricsHelpMarker("You can also call ImGui::ShowDebugLogWindow() from your code."); - - Checkbox("Show ID Stack Tool", &cfg->ShowIDStackTool); - SameLine(); - MetricsHelpMarker("You can also call ImGui::ShowIDStackToolWindow() from your code."); - - Checkbox("Show windows begin order", &cfg->ShowWindowsBeginOrder); - Checkbox("Show windows rectangles", &cfg->ShowWindowsRects); - SameLine(); - SetNextItemWidth(GetFontSize() * 12); - cfg->ShowWindowsRects |= Combo("##show_windows_rect_type", &cfg->ShowWindowsRectsType, wrt_rects_names, WRT_Count, WRT_Count); - if (cfg->ShowWindowsRects && g.NavWindow != NULL) - { - BulletText("'%s':", g.NavWindow->Name); - Indent(); - for (int rect_n = 0; rect_n < WRT_Count; rect_n++) - { - ImRect r = Funcs::GetWindowRect(g.NavWindow, rect_n); - Text("(%6.1f,%6.1f) (%6.1f,%6.1f) Size (%6.1f,%6.1f) %s", r.Min.x, r.Min.y, r.Max.x, r.Max.y, r.GetWidth(), r.GetHeight(), wrt_rects_names[rect_n]); - } - Unindent(); - } - - Checkbox("Show tables rectangles", &cfg->ShowTablesRects); - SameLine(); - SetNextItemWidth(GetFontSize() * 12); - cfg->ShowTablesRects |= Combo("##show_table_rects_type", &cfg->ShowTablesRectsType, trt_rects_names, TRT_Count, TRT_Count); - if (cfg->ShowTablesRects && g.NavWindow != NULL) - { - for (int table_n = 0; table_n < g.Tables.GetMapSize(); table_n++) - { - ImGuiTable* table = g.Tables.TryGetMapData(table_n); - if (table == NULL || table->LastFrameActive < g.FrameCount - 1 || (table->OuterWindow != g.NavWindow && table->InnerWindow != g.NavWindow)) - continue; - - BulletText("Table 0x%08X (%d columns, in '%s')", table->ID, table->ColumnsCount, table->OuterWindow->Name); - if (IsItemHovered()) - GetForegroundDrawList()->AddRect(table->OuterRect.Min - ImVec2(1, 1), table->OuterRect.Max + ImVec2(1, 1), IM_COL32(255, 255, 0, 255), 0.0f, 0, 2.0f); - Indent(); - char buf[128]; - for (int rect_n = 0; rect_n < TRT_Count; rect_n++) - { - if (rect_n >= TRT_ColumnsRect) - { - if (rect_n != TRT_ColumnsRect && rect_n != TRT_ColumnsClipRect) - continue; - for (int column_n = 0; column_n < table->ColumnsCount; column_n++) - { - ImRect r = Funcs::GetTableRect(table, rect_n, column_n); - ImFormatString(buf, IM_ARRAYSIZE(buf), "(%6.1f,%6.1f) (%6.1f,%6.1f) Size (%6.1f,%6.1f) Col %d %s", r.Min.x, r.Min.y, r.Max.x, r.Max.y, r.GetWidth(), r.GetHeight(), column_n, trt_rects_names[rect_n]); - Selectable(buf); - if (IsItemHovered()) - GetForegroundDrawList()->AddRect(r.Min - ImVec2(1, 1), r.Max + ImVec2(1, 1), IM_COL32(255, 255, 0, 255), 0.0f, 0, 2.0f); - } - } - else - { - ImRect r = Funcs::GetTableRect(table, rect_n, -1); - ImFormatString(buf, IM_ARRAYSIZE(buf), "(%6.1f,%6.1f) (%6.1f,%6.1f) Size (%6.1f,%6.1f) %s", r.Min.x, r.Min.y, r.Max.x, r.Max.y, r.GetWidth(), r.GetHeight(), trt_rects_names[rect_n]); - Selectable(buf); - if (IsItemHovered()) - GetForegroundDrawList()->AddRect(r.Min - ImVec2(1, 1), r.Max + ImVec2(1, 1), IM_COL32(255, 255, 0, 255), 0.0f, 0, 2.0f); - } - } - Unindent(); - } - } - Checkbox("Show groups rectangles", &g.DebugShowGroupRects); // Storing in context as this is used by group code and prefers to be in hot-data - - Checkbox("Debug Begin/BeginChild return value", &io.ConfigDebugBeginReturnValueLoop); - SameLine(); - MetricsHelpMarker("Some calls to Begin()/BeginChild() will return false.\n\nWill cycle through window depths then repeat. Windows should be flickering while running."); - - TreePop(); - } - - // Windows - if (TreeNode("Windows", "Windows (%d)", g.Windows.Size)) - { - //SetNextItemOpen(true, ImGuiCond_Once); - DebugNodeWindowsList(&g.Windows, "By display order"); - DebugNodeWindowsList(&g.WindowsFocusOrder, "By focus order (root windows)"); - if (TreeNode("By submission order (begin stack)")) - { - // Here we display windows in their submitted order/hierarchy, however note that the Begin stack doesn't constitute a Parent<>Child relationship! - ImVector& temp_buffer = g.WindowsTempSortBuffer; - temp_buffer.resize(0); - for (ImGuiWindow* window : g.Windows) - if (window->LastFrameActive + 1 >= g.FrameCount) - temp_buffer.push_back(window); - struct Func { static int IMGUI_CDECL WindowComparerByBeginOrder(const void* lhs, const void* rhs) { return ((int)(*(const ImGuiWindow* const *)lhs)->BeginOrderWithinContext - (*(const ImGuiWindow* const*)rhs)->BeginOrderWithinContext); } }; - ImQsort(temp_buffer.Data, (size_t)temp_buffer.Size, sizeof(ImGuiWindow*), Func::WindowComparerByBeginOrder); - DebugNodeWindowsListByBeginStackParent(temp_buffer.Data, temp_buffer.Size, NULL); - TreePop(); - } - - TreePop(); - } - - // DrawLists - int drawlist_count = 0; - for (ImGuiViewportP* viewport : g.Viewports) - drawlist_count += viewport->DrawDataP.CmdLists.Size; - if (TreeNode("DrawLists", "DrawLists (%d)", drawlist_count)) - { - Checkbox("Show ImDrawCmd mesh when hovering", &cfg->ShowDrawCmdMesh); - Checkbox("Show ImDrawCmd bounding boxes when hovering", &cfg->ShowDrawCmdBoundingBoxes); - for (ImGuiViewportP* viewport : g.Viewports) - { - bool viewport_has_drawlist = false; - for (ImDrawList* draw_list : viewport->DrawDataP.CmdLists) - { - if (!viewport_has_drawlist) - Text("Active DrawLists in Viewport #%d, ID: 0x%08X", viewport->Idx, viewport->ID); - viewport_has_drawlist = true; - DebugNodeDrawList(NULL, viewport, draw_list, "DrawList"); - } - } - TreePop(); - } - - // Viewports - if (TreeNode("Viewports", "Viewports (%d)", g.Viewports.Size)) - { - Indent(GetTreeNodeToLabelSpacing()); - RenderViewportsThumbnails(); - Unindent(GetTreeNodeToLabelSpacing()); - - bool open = TreeNode("Monitors", "Monitors (%d)", g.PlatformIO.Monitors.Size); - SameLine(); - MetricsHelpMarker("Dear ImGui uses monitor data:\n- to query DPI settings on a per monitor basis\n- to position popup/tooltips so they don't straddle monitors."); - if (open) - { - for (int i = 0; i < g.PlatformIO.Monitors.Size; i++) - { - const ImGuiPlatformMonitor& mon = g.PlatformIO.Monitors[i]; - BulletText("Monitor #%d: DPI %.0f%%\n MainMin (%.0f,%.0f), MainMax (%.0f,%.0f), MainSize (%.0f,%.0f)\n WorkMin (%.0f,%.0f), WorkMax (%.0f,%.0f), WorkSize (%.0f,%.0f)", - i, mon.DpiScale * 100.0f, - mon.MainPos.x, mon.MainPos.y, mon.MainPos.x + mon.MainSize.x, mon.MainPos.y + mon.MainSize.y, mon.MainSize.x, mon.MainSize.y, - mon.WorkPos.x, mon.WorkPos.y, mon.WorkPos.x + mon.WorkSize.x, mon.WorkPos.y + mon.WorkSize.y, mon.WorkSize.x, mon.WorkSize.y); - } - TreePop(); - } - - BulletText("MouseViewport: 0x%08X (UserHovered 0x%08X, LastHovered 0x%08X)", g.MouseViewport ? g.MouseViewport->ID : 0, g.IO.MouseHoveredViewport, g.MouseLastHoveredViewport ? g.MouseLastHoveredViewport->ID : 0); - if (TreeNode("Inferred Z order (front-to-back)")) - { - static ImVector viewports; - viewports.resize(g.Viewports.Size); - memcpy(viewports.Data, g.Viewports.Data, g.Viewports.size_in_bytes()); - if (viewports.Size > 1) - ImQsort(viewports.Data, viewports.Size, sizeof(ImGuiViewport*), ViewportComparerByLastFocusedStampCount); - for (ImGuiViewportP* viewport : viewports) - BulletText("Viewport #%d, ID: 0x%08X, LastFocused = %08d, PlatformFocused = %s, Window: \"%s\"", - viewport->Idx, viewport->ID, viewport->LastFocusedStampCount, - (g.PlatformIO.Platform_GetWindowFocus && viewport->PlatformWindowCreated) ? (g.PlatformIO.Platform_GetWindowFocus(viewport) ? "1" : "0") : "N/A", - viewport->Window ? viewport->Window->Name : "N/A"); - TreePop(); - } - for (ImGuiViewportP* viewport : g.Viewports) - DebugNodeViewport(viewport); - TreePop(); - } - - // Details for Popups - if (TreeNode("Popups", "Popups (%d)", g.OpenPopupStack.Size)) - { - for (const ImGuiPopupData& popup_data : g.OpenPopupStack) - { - // As it's difficult to interact with tree nodes while popups are open, we display everything inline. - ImGuiWindow* window = popup_data.Window; - BulletText("PopupID: %08x, Window: '%s' (%s%s), BackupNavWindow '%s', ParentWindow '%s'", - popup_data.PopupId, window ? window->Name : "NULL", window && (window->Flags & ImGuiWindowFlags_ChildWindow) ? "Child;" : "", window && (window->Flags & ImGuiWindowFlags_ChildMenu) ? "Menu;" : "", - popup_data.BackupNavWindow ? popup_data.BackupNavWindow->Name : "NULL", window && window->ParentWindow ? window->ParentWindow->Name : "NULL"); - } - TreePop(); - } - - // Details for TabBars - if (TreeNode("TabBars", "Tab Bars (%d)", g.TabBars.GetAliveCount())) - { - for (int n = 0; n < g.TabBars.GetMapSize(); n++) - if (ImGuiTabBar* tab_bar = g.TabBars.TryGetMapData(n)) - { - PushID(tab_bar); - DebugNodeTabBar(tab_bar, "TabBar"); - PopID(); - } - TreePop(); - } - - // Details for Tables - if (TreeNode("Tables", "Tables (%d)", g.Tables.GetAliveCount())) - { - for (int n = 0; n < g.Tables.GetMapSize(); n++) - if (ImGuiTable* table = g.Tables.TryGetMapData(n)) - DebugNodeTable(table); - TreePop(); - } - - // Details for Fonts - ImFontAtlas* atlas = g.IO.Fonts; - if (TreeNode("Fonts", "Fonts (%d)", atlas->Fonts.Size)) - { - ShowFontAtlas(atlas); - TreePop(); - } - - // Details for InputText - if (TreeNode("InputText")) - { - DebugNodeInputTextState(&g.InputTextState); - TreePop(); - } - - // Details for TypingSelect - if (TreeNode("TypingSelect", "TypingSelect (%d)", g.TypingSelectState.SearchBuffer[0] != 0 ? 1 : 0)) - { - DebugNodeTypingSelectState(&g.TypingSelectState); - TreePop(); - } - - // Details for Docking -#ifdef IMGUI_HAS_DOCK - if (TreeNode("Docking")) - { - static bool root_nodes_only = true; - ImGuiDockContext* dc = &g.DockContext; - Checkbox("List root nodes", &root_nodes_only); - Checkbox("Ctrl shows window dock info", &cfg->ShowDockingNodes); - if (SmallButton("Clear nodes")) { DockContextClearNodes(&g, 0, true); } - SameLine(); - if (SmallButton("Rebuild all")) { dc->WantFullRebuild = true; } - for (int n = 0; n < dc->Nodes.Data.Size; n++) - if (ImGuiDockNode* node = (ImGuiDockNode*)dc->Nodes.Data[n].val_p) - if (!root_nodes_only || node->IsRootNode()) - DebugNodeDockNode(node, "Node"); - TreePop(); - } -#endif // #ifdef IMGUI_HAS_DOCK - - // Settings - if (TreeNode("Settings")) - { - if (SmallButton("Clear")) - ClearIniSettings(); - SameLine(); - if (SmallButton("Save to memory")) - SaveIniSettingsToMemory(); - SameLine(); - if (SmallButton("Save to disk")) - SaveIniSettingsToDisk(g.IO.IniFilename); - SameLine(); - if (g.IO.IniFilename) - Text("\"%s\"", g.IO.IniFilename); - else - TextUnformatted(""); - Checkbox("io.ConfigDebugIniSettings", &io.ConfigDebugIniSettings); - Text("SettingsDirtyTimer %.2f", g.SettingsDirtyTimer); - if (TreeNode("SettingsHandlers", "Settings handlers: (%d)", g.SettingsHandlers.Size)) - { - for (ImGuiSettingsHandler& handler : g.SettingsHandlers) - BulletText("\"%s\"", handler.TypeName); - TreePop(); - } - if (TreeNode("SettingsWindows", "Settings packed data: Windows: %d bytes", g.SettingsWindows.size())) - { - for (ImGuiWindowSettings* settings = g.SettingsWindows.begin(); settings != NULL; settings = g.SettingsWindows.next_chunk(settings)) - DebugNodeWindowSettings(settings); - TreePop(); - } - - if (TreeNode("SettingsTables", "Settings packed data: Tables: %d bytes", g.SettingsTables.size())) - { - for (ImGuiTableSettings* settings = g.SettingsTables.begin(); settings != NULL; settings = g.SettingsTables.next_chunk(settings)) - DebugNodeTableSettings(settings); - TreePop(); - } - -#ifdef IMGUI_HAS_DOCK - if (TreeNode("SettingsDocking", "Settings packed data: Docking")) - { - ImGuiDockContext* dc = &g.DockContext; - Text("In SettingsWindows:"); - for (ImGuiWindowSettings* settings = g.SettingsWindows.begin(); settings != NULL; settings = g.SettingsWindows.next_chunk(settings)) - if (settings->DockId != 0) - BulletText("Window '%s' -> DockId %08X DockOrder=%d", settings->GetName(), settings->DockId, settings->DockOrder); - Text("In SettingsNodes:"); - for (int n = 0; n < dc->NodesSettings.Size; n++) - { - ImGuiDockNodeSettings* settings = &dc->NodesSettings[n]; - const char* selected_tab_name = NULL; - if (settings->SelectedTabId) - { - if (ImGuiWindow* window = FindWindowByID(settings->SelectedTabId)) - selected_tab_name = window->Name; - else if (ImGuiWindowSettings* window_settings = FindWindowSettingsByID(settings->SelectedTabId)) - selected_tab_name = window_settings->GetName(); - } - BulletText("Node %08X, Parent %08X, SelectedTab %08X ('%s')", settings->ID, settings->ParentNodeId, settings->SelectedTabId, selected_tab_name ? selected_tab_name : settings->SelectedTabId ? "N/A" : ""); - } - TreePop(); - } -#endif // #ifdef IMGUI_HAS_DOCK - - if (TreeNode("SettingsIniData", "Settings unpacked data (.ini): %d bytes", g.SettingsIniData.size())) - { - InputTextMultiline("##Ini", (char*)(void*)g.SettingsIniData.c_str(), g.SettingsIniData.Buf.Size, ImVec2(-FLT_MIN, GetTextLineHeight() * 20), ImGuiInputTextFlags_ReadOnly); - TreePop(); - } - TreePop(); - } - - // Settings - if (TreeNode("Memory allocations")) - { - ImGuiDebugAllocInfo* info = &g.DebugAllocInfo; - Text("%d current allocations", info->TotalAllocCount - info->TotalFreeCount); - Text("Recent frames with allocations:"); - int buf_size = IM_ARRAYSIZE(info->LastEntriesBuf); - for (int n = buf_size - 1; n >= 0; n--) - { - ImGuiDebugAllocEntry* entry = &info->LastEntriesBuf[(info->LastEntriesIdx - n + buf_size) % buf_size]; - BulletText("Frame %06d: %+3d ( %2d malloc, %2d free )%s", entry->FrameCount, entry->AllocCount - entry->FreeCount, entry->AllocCount, entry->FreeCount, (n == 0) ? " (most recent)" : ""); - } - TreePop(); - } - - if (TreeNode("Inputs")) - { - Text("KEYBOARD/GAMEPAD/MOUSE KEYS"); - { - // We iterate both legacy native range and named ImGuiKey ranges, which is a little odd but this allows displaying the data for old/new backends. - // User code should never have to go through such hoops! You can generally iterate between ImGuiKey_NamedKey_BEGIN and ImGuiKey_NamedKey_END. - Indent(); -#ifdef IMGUI_DISABLE_OBSOLETE_KEYIO - struct funcs { static bool IsLegacyNativeDupe(ImGuiKey) { return false; } }; -#else - struct funcs { static bool IsLegacyNativeDupe(ImGuiKey key) { return key < 512 && GetIO().KeyMap[key] != -1; } }; // Hide Native<>ImGuiKey duplicates when both exists in the array - //Text("Legacy raw:"); for (ImGuiKey key = ImGuiKey_KeysData_OFFSET; key < ImGuiKey_COUNT; key++) { if (io.KeysDown[key]) { SameLine(); Text("\"%s\" %d", GetKeyName(key), key); } } -#endif - Text("Keys down:"); for (ImGuiKey key = ImGuiKey_KeysData_OFFSET; key < ImGuiKey_COUNT; key = (ImGuiKey)(key + 1)) { if (funcs::IsLegacyNativeDupe(key) || !IsKeyDown(key)) continue; SameLine(); Text(IsNamedKey(key) ? "\"%s\"" : "\"%s\" %d", GetKeyName(key), key); SameLine(); Text("(%.02f)", GetKeyData(key)->DownDuration); } - Text("Keys pressed:"); for (ImGuiKey key = ImGuiKey_KeysData_OFFSET; key < ImGuiKey_COUNT; key = (ImGuiKey)(key + 1)) { if (funcs::IsLegacyNativeDupe(key) || !IsKeyPressed(key)) continue; SameLine(); Text(IsNamedKey(key) ? "\"%s\"" : "\"%s\" %d", GetKeyName(key), key); } - Text("Keys released:"); for (ImGuiKey key = ImGuiKey_KeysData_OFFSET; key < ImGuiKey_COUNT; key = (ImGuiKey)(key + 1)) { if (funcs::IsLegacyNativeDupe(key) || !IsKeyReleased(key)) continue; SameLine(); Text(IsNamedKey(key) ? "\"%s\"" : "\"%s\" %d", GetKeyName(key), key); } - Text("Keys mods: %s%s%s%s", io.KeyCtrl ? "CTRL " : "", io.KeyShift ? "SHIFT " : "", io.KeyAlt ? "ALT " : "", io.KeySuper ? "SUPER " : ""); - Text("Chars queue:"); for (int i = 0; i < io.InputQueueCharacters.Size; i++) { ImWchar c = io.InputQueueCharacters[i]; SameLine(); Text("\'%c\' (0x%04X)", (c > ' ' && c <= 255) ? (char)c : '?', c); } // FIXME: We should convert 'c' to UTF-8 here but the functions are not public. - DebugRenderKeyboardPreview(GetWindowDrawList()); - Unindent(); - } - - Text("MOUSE STATE"); - { - Indent(); - if (IsMousePosValid()) - Text("Mouse pos: (%g, %g)", io.MousePos.x, io.MousePos.y); - else - Text("Mouse pos: "); - Text("Mouse delta: (%g, %g)", io.MouseDelta.x, io.MouseDelta.y); - int count = IM_ARRAYSIZE(io.MouseDown); - Text("Mouse down:"); for (int i = 0; i < count; i++) if (IsMouseDown(i)) { SameLine(); Text("b%d (%.02f secs)", i, io.MouseDownDuration[i]); } - Text("Mouse clicked:"); for (int i = 0; i < count; i++) if (IsMouseClicked(i)) { SameLine(); Text("b%d (%d)", i, io.MouseClickedCount[i]); } - Text("Mouse released:"); for (int i = 0; i < count; i++) if (IsMouseReleased(i)) { SameLine(); Text("b%d", i); } - Text("Mouse wheel: %.1f", io.MouseWheel); - Text("MouseStationaryTimer: %.2f", g.MouseStationaryTimer); - Text("Mouse source: %s", GetMouseSourceName(io.MouseSource)); - Text("Pen Pressure: %.1f", io.PenPressure); // Note: currently unused - Unindent(); - } - - Text("MOUSE WHEELING"); - { - Indent(); - Text("WheelingWindow: '%s'", g.WheelingWindow ? g.WheelingWindow->Name : "NULL"); - Text("WheelingWindowReleaseTimer: %.2f", g.WheelingWindowReleaseTimer); - Text("WheelingAxisAvg[] = { %.3f, %.3f }, Main Axis: %s", g.WheelingAxisAvg.x, g.WheelingAxisAvg.y, (g.WheelingAxisAvg.x > g.WheelingAxisAvg.y) ? "X" : (g.WheelingAxisAvg.x < g.WheelingAxisAvg.y) ? "Y" : ""); - Unindent(); - } - - Text("KEY OWNERS"); - { - Indent(); - if (BeginListBox("##owners", ImVec2(-FLT_MIN, GetTextLineHeightWithSpacing() * 6))) - { - for (ImGuiKey key = ImGuiKey_NamedKey_BEGIN; key < ImGuiKey_NamedKey_END; key = (ImGuiKey)(key + 1)) - { - ImGuiKeyOwnerData* owner_data = GetKeyOwnerData(&g, key); - if (owner_data->OwnerCurr == ImGuiKeyOwner_None) - continue; - Text("%s: 0x%08X%s", GetKeyName(key), owner_data->OwnerCurr, - owner_data->LockUntilRelease ? " LockUntilRelease" : owner_data->LockThisFrame ? " LockThisFrame" : ""); - DebugLocateItemOnHover(owner_data->OwnerCurr); - } - EndListBox(); - } - Unindent(); - } - Text("SHORTCUT ROUTING"); - { - Indent(); - if (BeginListBox("##routes", ImVec2(-FLT_MIN, GetTextLineHeightWithSpacing() * 6))) - { - for (ImGuiKey key = ImGuiKey_NamedKey_BEGIN; key < ImGuiKey_NamedKey_END; key = (ImGuiKey)(key + 1)) - { - ImGuiKeyRoutingTable* rt = &g.KeysRoutingTable; - for (ImGuiKeyRoutingIndex idx = rt->Index[key - ImGuiKey_NamedKey_BEGIN]; idx != -1; ) - { - char key_chord_name[64]; - ImGuiKeyRoutingData* routing_data = &rt->Entries[idx]; - GetKeyChordName(key | routing_data->Mods, key_chord_name, IM_ARRAYSIZE(key_chord_name)); - Text("%s: 0x%08X", key_chord_name, routing_data->RoutingCurr); - DebugLocateItemOnHover(routing_data->RoutingCurr); - idx = routing_data->NextEntryIndex; - } - } - EndListBox(); - } - Text("(ActiveIdUsing: AllKeyboardKeys: %d, NavDirMask: 0x%X)", g.ActiveIdUsingAllKeyboardKeys, g.ActiveIdUsingNavDirMask); - Unindent(); - } - TreePop(); - } - - if (TreeNode("Internal state")) - { - Text("WINDOWING"); - Indent(); - Text("HoveredWindow: '%s'", g.HoveredWindow ? g.HoveredWindow->Name : "NULL"); - Text("HoveredWindow->Root: '%s'", g.HoveredWindow ? g.HoveredWindow->RootWindowDockTree->Name : "NULL"); - Text("HoveredWindowUnderMovingWindow: '%s'", g.HoveredWindowUnderMovingWindow ? g.HoveredWindowUnderMovingWindow->Name : "NULL"); - Text("HoveredDockNode: 0x%08X", g.DebugHoveredDockNode ? g.DebugHoveredDockNode->ID : 0); - Text("MovingWindow: '%s'", g.MovingWindow ? g.MovingWindow->Name : "NULL"); - Text("MouseViewport: 0x%08X (UserHovered 0x%08X, LastHovered 0x%08X)", g.MouseViewport->ID, g.IO.MouseHoveredViewport, g.MouseLastHoveredViewport ? g.MouseLastHoveredViewport->ID : 0); - Unindent(); - - Text("ITEMS"); - Indent(); - Text("ActiveId: 0x%08X/0x%08X (%.2f sec), AllowOverlap: %d, Source: %s", g.ActiveId, g.ActiveIdPreviousFrame, g.ActiveIdTimer, g.ActiveIdAllowOverlap, GetInputSourceName(g.ActiveIdSource)); - DebugLocateItemOnHover(g.ActiveId); - Text("ActiveIdWindow: '%s'", g.ActiveIdWindow ? g.ActiveIdWindow->Name : "NULL"); - Text("ActiveIdUsing: AllKeyboardKeys: %d, NavDirMask: %X", g.ActiveIdUsingAllKeyboardKeys, g.ActiveIdUsingNavDirMask); - Text("HoveredId: 0x%08X (%.2f sec), AllowOverlap: %d", g.HoveredIdPreviousFrame, g.HoveredIdTimer, g.HoveredIdAllowOverlap); // Not displaying g.HoveredId as it is update mid-frame - Text("HoverItemDelayId: 0x%08X, Timer: %.2f, ClearTimer: %.2f", g.HoverItemDelayId, g.HoverItemDelayTimer, g.HoverItemDelayClearTimer); - Text("DragDrop: %d, SourceId = 0x%08X, Payload \"%s\" (%d bytes)", g.DragDropActive, g.DragDropPayload.SourceId, g.DragDropPayload.DataType, g.DragDropPayload.DataSize); - DebugLocateItemOnHover(g.DragDropPayload.SourceId); - Unindent(); - - Text("NAV,FOCUS"); - Indent(); - Text("NavWindow: '%s'", g.NavWindow ? g.NavWindow->Name : "NULL"); - Text("NavId: 0x%08X, NavLayer: %d", g.NavId, g.NavLayer); - DebugLocateItemOnHover(g.NavId); - Text("NavInputSource: %s", GetInputSourceName(g.NavInputSource)); - Text("NavLastValidSelectionUserData = %" IM_PRId64 " (0x%" IM_PRIX64 ")", g.NavLastValidSelectionUserData, g.NavLastValidSelectionUserData); - Text("NavActive: %d, NavVisible: %d", g.IO.NavActive, g.IO.NavVisible); - Text("NavActivateId/DownId/PressedId: %08X/%08X/%08X", g.NavActivateId, g.NavActivateDownId, g.NavActivatePressedId); - Text("NavActivateFlags: %04X", g.NavActivateFlags); - Text("NavDisableHighlight: %d, NavDisableMouseHover: %d", g.NavDisableHighlight, g.NavDisableMouseHover); - Text("NavFocusScopeId = 0x%08X", g.NavFocusScopeId); - Text("NavWindowingTarget: '%s'", g.NavWindowingTarget ? g.NavWindowingTarget->Name : "NULL"); - Unindent(); - - TreePop(); - } - - // Overlay: Display windows Rectangles and Begin Order - if (cfg->ShowWindowsRects || cfg->ShowWindowsBeginOrder) - { - for (ImGuiWindow* window : g.Windows) - { - if (!window->WasActive) - continue; - ImDrawList* draw_list = GetForegroundDrawList(window); - if (cfg->ShowWindowsRects) - { - ImRect r = Funcs::GetWindowRect(window, cfg->ShowWindowsRectsType); - draw_list->AddRect(r.Min, r.Max, IM_COL32(255, 0, 128, 255)); - } - if (cfg->ShowWindowsBeginOrder && !(window->Flags & ImGuiWindowFlags_ChildWindow)) - { - char buf[32]; - ImFormatString(buf, IM_ARRAYSIZE(buf), "%d", window->BeginOrderWithinContext); - float font_size = GetFontSize(); - draw_list->AddRectFilled(window->Pos, window->Pos + ImVec2(font_size, font_size), IM_COL32(200, 100, 100, 255)); - draw_list->AddText(window->Pos, IM_COL32(255, 255, 255, 255), buf); - } - } - } - - // Overlay: Display Tables Rectangles - if (cfg->ShowTablesRects) - { - for (int table_n = 0; table_n < g.Tables.GetMapSize(); table_n++) - { - ImGuiTable* table = g.Tables.TryGetMapData(table_n); - if (table == NULL || table->LastFrameActive < g.FrameCount - 1) - continue; - ImDrawList* draw_list = GetForegroundDrawList(table->OuterWindow); - if (cfg->ShowTablesRectsType >= TRT_ColumnsRect) - { - for (int column_n = 0; column_n < table->ColumnsCount; column_n++) - { - ImRect r = Funcs::GetTableRect(table, cfg->ShowTablesRectsType, column_n); - ImU32 col = (table->HoveredColumnBody == column_n) ? IM_COL32(255, 255, 128, 255) : IM_COL32(255, 0, 128, 255); - float thickness = (table->HoveredColumnBody == column_n) ? 3.0f : 1.0f; - draw_list->AddRect(r.Min, r.Max, col, 0.0f, 0, thickness); - } - } - else - { - ImRect r = Funcs::GetTableRect(table, cfg->ShowTablesRectsType, -1); - draw_list->AddRect(r.Min, r.Max, IM_COL32(255, 0, 128, 255)); - } - } - } - -#ifdef IMGUI_HAS_DOCK - // Overlay: Display Docking info - if (cfg->ShowDockingNodes && g.IO.KeyCtrl && g.DebugHoveredDockNode) - { - char buf[64] = ""; - char* p = buf; - ImGuiDockNode* node = g.DebugHoveredDockNode; - ImDrawList* overlay_draw_list = node->HostWindow ? GetForegroundDrawList(node->HostWindow) : GetForegroundDrawList(GetMainViewport()); - p += ImFormatString(p, buf + IM_ARRAYSIZE(buf) - p, "DockId: %X%s\n", node->ID, node->IsCentralNode() ? " *CentralNode*" : ""); - p += ImFormatString(p, buf + IM_ARRAYSIZE(buf) - p, "WindowClass: %08X\n", node->WindowClass.ClassId); - p += ImFormatString(p, buf + IM_ARRAYSIZE(buf) - p, "Size: (%.0f, %.0f)\n", node->Size.x, node->Size.y); - p += ImFormatString(p, buf + IM_ARRAYSIZE(buf) - p, "SizeRef: (%.0f, %.0f)\n", node->SizeRef.x, node->SizeRef.y); - int depth = DockNodeGetDepth(node); - overlay_draw_list->AddRect(node->Pos + ImVec2(3, 3) * (float)depth, node->Pos + node->Size - ImVec2(3, 3) * (float)depth, IM_COL32(200, 100, 100, 255)); - ImVec2 pos = node->Pos + ImVec2(3, 3) * (float)depth; - overlay_draw_list->AddRectFilled(pos - ImVec2(1, 1), pos + CalcTextSize(buf) + ImVec2(1, 1), IM_COL32(200, 100, 100, 255)); - overlay_draw_list->AddText(NULL, 0.0f, pos, IM_COL32(255, 255, 255, 255), buf); - } -#endif // #ifdef IMGUI_HAS_DOCK - - End(); -} - -// [DEBUG] Display contents of Columns -void ImGui::DebugNodeColumns(ImGuiOldColumns* columns) -{ - if (!TreeNode((void*)(uintptr_t)columns->ID, "Columns Id: 0x%08X, Count: %d, Flags: 0x%04X", columns->ID, columns->Count, columns->Flags)) - return; - BulletText("Width: %.1f (MinX: %.1f, MaxX: %.1f)", columns->OffMaxX - columns->OffMinX, columns->OffMinX, columns->OffMaxX); - for (ImGuiOldColumnData& column : columns->Columns) - BulletText("Column %02d: OffsetNorm %.3f (= %.1f px)", (int)columns->Columns.index_from_ptr(&column), column.OffsetNorm, GetColumnOffsetFromNorm(columns, column.OffsetNorm)); - TreePop(); -} - -static void DebugNodeDockNodeFlags(ImGuiDockNodeFlags* p_flags, const char* label, bool enabled) -{ - using namespace ImGui; - PushID(label); - PushStyleVar(ImGuiStyleVar_FramePadding, ImVec2(0.0f, 0.0f)); - Text("%s:", label); - if (!enabled) - BeginDisabled(); - CheckboxFlags("NoResize", p_flags, ImGuiDockNodeFlags_NoResize); - CheckboxFlags("NoResizeX", p_flags, ImGuiDockNodeFlags_NoResizeX); - CheckboxFlags("NoResizeY",p_flags, ImGuiDockNodeFlags_NoResizeY); - CheckboxFlags("NoTabBar", p_flags, ImGuiDockNodeFlags_NoTabBar); - CheckboxFlags("HiddenTabBar", p_flags, ImGuiDockNodeFlags_HiddenTabBar); - CheckboxFlags("NoWindowMenuButton", p_flags, ImGuiDockNodeFlags_NoWindowMenuButton); - CheckboxFlags("NoCloseButton", p_flags, ImGuiDockNodeFlags_NoCloseButton); - CheckboxFlags("NoDocking", p_flags, ImGuiDockNodeFlags_NoDocking); // Multiple flags - CheckboxFlags("NoDockingSplit", p_flags, ImGuiDockNodeFlags_NoDockingSplit); - CheckboxFlags("NoDockingSplitOther", p_flags, ImGuiDockNodeFlags_NoDockingSplitOther); - CheckboxFlags("NoDockingOver", p_flags, ImGuiDockNodeFlags_NoDockingOverMe); - CheckboxFlags("NoDockingOverOther", p_flags, ImGuiDockNodeFlags_NoDockingOverOther); - CheckboxFlags("NoDockingOverEmpty", p_flags, ImGuiDockNodeFlags_NoDockingOverEmpty); - CheckboxFlags("NoUndocking", p_flags, ImGuiDockNodeFlags_NoUndocking); - if (!enabled) - EndDisabled(); - PopStyleVar(); - PopID(); -} - -// [DEBUG] Display contents of ImDockNode -void ImGui::DebugNodeDockNode(ImGuiDockNode* node, const char* label) -{ - ImGuiContext& g = *GImGui; - const bool is_alive = (g.FrameCount - node->LastFrameAlive < 2); // Submitted with ImGuiDockNodeFlags_KeepAliveOnly - const bool is_active = (g.FrameCount - node->LastFrameActive < 2); // Submitted - if (!is_alive) { PushStyleColor(ImGuiCol_Text, GetStyleColorVec4(ImGuiCol_TextDisabled)); } - bool open; - ImGuiTreeNodeFlags tree_node_flags = node->IsFocused ? ImGuiTreeNodeFlags_Selected : ImGuiTreeNodeFlags_None; - if (node->Windows.Size > 0) - open = TreeNodeEx((void*)(intptr_t)node->ID, tree_node_flags, "%s 0x%04X%s: %d windows (vis: '%s')", label, node->ID, node->IsVisible ? "" : " (hidden)", node->Windows.Size, node->VisibleWindow ? node->VisibleWindow->Name : "NULL"); - else - open = TreeNodeEx((void*)(intptr_t)node->ID, tree_node_flags, "%s 0x%04X%s: %s (vis: '%s')", label, node->ID, node->IsVisible ? "" : " (hidden)", (node->SplitAxis == ImGuiAxis_X) ? "horizontal split" : (node->SplitAxis == ImGuiAxis_Y) ? "vertical split" : "empty", node->VisibleWindow ? node->VisibleWindow->Name : "NULL"); - if (!is_alive) { PopStyleColor(); } - if (is_active && IsItemHovered()) - if (ImGuiWindow* window = node->HostWindow ? node->HostWindow : node->VisibleWindow) - GetForegroundDrawList(window)->AddRect(node->Pos, node->Pos + node->Size, IM_COL32(255, 255, 0, 255)); - if (open) - { - IM_ASSERT(node->ChildNodes[0] == NULL || node->ChildNodes[0]->ParentNode == node); - IM_ASSERT(node->ChildNodes[1] == NULL || node->ChildNodes[1]->ParentNode == node); - BulletText("Pos (%.0f,%.0f), Size (%.0f, %.0f) Ref (%.0f, %.0f)", - node->Pos.x, node->Pos.y, node->Size.x, node->Size.y, node->SizeRef.x, node->SizeRef.y); - DebugNodeWindow(node->HostWindow, "HostWindow"); - DebugNodeWindow(node->VisibleWindow, "VisibleWindow"); - BulletText("SelectedTabID: 0x%08X, LastFocusedNodeID: 0x%08X", node->SelectedTabId, node->LastFocusedNodeId); - BulletText("Misc:%s%s%s%s%s%s%s", - node->IsDockSpace() ? " IsDockSpace" : "", - node->IsCentralNode() ? " IsCentralNode" : "", - is_alive ? " IsAlive" : "", is_active ? " IsActive" : "", node->IsFocused ? " IsFocused" : "", - node->WantLockSizeOnce ? " WantLockSizeOnce" : "", - node->HasCentralNodeChild ? " HasCentralNodeChild" : ""); - if (TreeNode("flags", "Flags Merged: 0x%04X, Local: 0x%04X, InWindows: 0x%04X, Shared: 0x%04X", node->MergedFlags, node->LocalFlags, node->LocalFlagsInWindows, node->SharedFlags)) - { - if (BeginTable("flags", 4)) - { - TableNextColumn(); DebugNodeDockNodeFlags(&node->MergedFlags, "MergedFlags", false); - TableNextColumn(); DebugNodeDockNodeFlags(&node->LocalFlags, "LocalFlags", true); - TableNextColumn(); DebugNodeDockNodeFlags(&node->LocalFlagsInWindows, "LocalFlagsInWindows", false); - TableNextColumn(); DebugNodeDockNodeFlags(&node->SharedFlags, "SharedFlags", true); - EndTable(); - } - TreePop(); - } - if (node->ParentNode) - DebugNodeDockNode(node->ParentNode, "ParentNode"); - if (node->ChildNodes[0]) - DebugNodeDockNode(node->ChildNodes[0], "Child[0]"); - if (node->ChildNodes[1]) - DebugNodeDockNode(node->ChildNodes[1], "Child[1]"); - if (node->TabBar) - DebugNodeTabBar(node->TabBar, "TabBar"); - DebugNodeWindowsList(&node->Windows, "Windows"); - - TreePop(); - } -} - -// [DEBUG] Display contents of ImDrawList -// Note that both 'window' and 'viewport' may be NULL here. Viewport is generally null of destroyed popups which previously owned a viewport. -void ImGui::DebugNodeDrawList(ImGuiWindow* window, ImGuiViewportP* viewport, const ImDrawList* draw_list, const char* label) -{ - ImGuiContext& g = *GImGui; - ImGuiMetricsConfig* cfg = &g.DebugMetricsConfig; - int cmd_count = draw_list->CmdBuffer.Size; - if (cmd_count > 0 && draw_list->CmdBuffer.back().ElemCount == 0 && draw_list->CmdBuffer.back().UserCallback == NULL) - cmd_count--; - bool node_open = TreeNode(draw_list, "%s: '%s' %d vtx, %d indices, %d cmds", label, draw_list->_OwnerName ? draw_list->_OwnerName : "", draw_list->VtxBuffer.Size, draw_list->IdxBuffer.Size, cmd_count); - if (draw_list == GetWindowDrawList()) - { - SameLine(); - TextColored(ImVec4(1.0f, 0.4f, 0.4f, 1.0f), "CURRENTLY APPENDING"); // Can't display stats for active draw list! (we don't have the data double-buffered) - if (node_open) - TreePop(); - return; - } - - ImDrawList* fg_draw_list = viewport ? GetForegroundDrawList(viewport) : NULL; // Render additional visuals into the top-most draw list - if (window && IsItemHovered() && fg_draw_list) - fg_draw_list->AddRect(window->Pos, window->Pos + window->Size, IM_COL32(255, 255, 0, 255)); - if (!node_open) - return; - - if (window && !window->WasActive) - TextDisabled("Warning: owning Window is inactive. This DrawList is not being rendered!"); - - for (const ImDrawCmd* pcmd = draw_list->CmdBuffer.Data; pcmd < draw_list->CmdBuffer.Data + cmd_count; pcmd++) - { - if (pcmd->UserCallback) - { - BulletText("Callback %p, user_data %p", pcmd->UserCallback, pcmd->UserCallbackData); - continue; - } - - char buf[300]; - ImFormatString(buf, IM_ARRAYSIZE(buf), "DrawCmd:%5d tris, Tex 0x%p, ClipRect (%4.0f,%4.0f)-(%4.0f,%4.0f)", - pcmd->ElemCount / 3, (void*)(intptr_t)pcmd->TextureId, - pcmd->ClipRect.x, pcmd->ClipRect.y, pcmd->ClipRect.z, pcmd->ClipRect.w); - bool pcmd_node_open = TreeNode((void*)(pcmd - draw_list->CmdBuffer.begin()), "%s", buf); - if (IsItemHovered() && (cfg->ShowDrawCmdMesh || cfg->ShowDrawCmdBoundingBoxes) && fg_draw_list) - DebugNodeDrawCmdShowMeshAndBoundingBox(fg_draw_list, draw_list, pcmd, cfg->ShowDrawCmdMesh, cfg->ShowDrawCmdBoundingBoxes); - if (!pcmd_node_open) - continue; - - // Calculate approximate coverage area (touched pixel count) - // This will be in pixels squared as long there's no post-scaling happening to the renderer output. - const ImDrawIdx* idx_buffer = (draw_list->IdxBuffer.Size > 0) ? draw_list->IdxBuffer.Data : NULL; - const ImDrawVert* vtx_buffer = draw_list->VtxBuffer.Data + pcmd->VtxOffset; - float total_area = 0.0f; - for (unsigned int idx_n = pcmd->IdxOffset; idx_n < pcmd->IdxOffset + pcmd->ElemCount; ) - { - ImVec2 triangle[3]; - for (int n = 0; n < 3; n++, idx_n++) - triangle[n] = vtx_buffer[idx_buffer ? idx_buffer[idx_n] : idx_n].pos; - total_area += ImTriangleArea(triangle[0], triangle[1], triangle[2]); - } - - // Display vertex information summary. Hover to get all triangles drawn in wire-frame - ImFormatString(buf, IM_ARRAYSIZE(buf), "Mesh: ElemCount: %d, VtxOffset: +%d, IdxOffset: +%d, Area: ~%0.f px", pcmd->ElemCount, pcmd->VtxOffset, pcmd->IdxOffset, total_area); - Selectable(buf); - if (IsItemHovered() && fg_draw_list) - DebugNodeDrawCmdShowMeshAndBoundingBox(fg_draw_list, draw_list, pcmd, true, false); - - // Display individual triangles/vertices. Hover on to get the corresponding triangle highlighted. - ImGuiListClipper clipper; - clipper.Begin(pcmd->ElemCount / 3); // Manually coarse clip our print out of individual vertices to save CPU, only items that may be visible. - while (clipper.Step()) - for (int prim = clipper.DisplayStart, idx_i = pcmd->IdxOffset + clipper.DisplayStart * 3; prim < clipper.DisplayEnd; prim++) - { - char* buf_p = buf, * buf_end = buf + IM_ARRAYSIZE(buf); - ImVec2 triangle[3]; - for (int n = 0; n < 3; n++, idx_i++) - { - const ImDrawVert& v = vtx_buffer[idx_buffer ? idx_buffer[idx_i] : idx_i]; - triangle[n] = v.pos; - buf_p += ImFormatString(buf_p, buf_end - buf_p, "%s %04d: pos (%8.2f,%8.2f), uv (%.6f,%.6f), col %08X\n", - (n == 0) ? "Vert:" : " ", idx_i, v.pos.x, v.pos.y, v.uv.x, v.uv.y, v.col); - } - - Selectable(buf, false); - if (fg_draw_list && IsItemHovered()) - { - ImDrawListFlags backup_flags = fg_draw_list->Flags; - fg_draw_list->Flags &= ~ImDrawListFlags_AntiAliasedLines; // Disable AA on triangle outlines is more readable for very large and thin triangles. - fg_draw_list->AddPolyline(triangle, 3, IM_COL32(255, 255, 0, 255), ImDrawFlags_Closed, 1.0f); - fg_draw_list->Flags = backup_flags; - } - } - TreePop(); - } - TreePop(); -} - -// [DEBUG] Display mesh/aabb of a ImDrawCmd -void ImGui::DebugNodeDrawCmdShowMeshAndBoundingBox(ImDrawList* out_draw_list, const ImDrawList* draw_list, const ImDrawCmd* draw_cmd, bool show_mesh, bool show_aabb) -{ - IM_ASSERT(show_mesh || show_aabb); - - // Draw wire-frame version of all triangles - ImRect clip_rect = draw_cmd->ClipRect; - ImRect vtxs_rect(FLT_MAX, FLT_MAX, -FLT_MAX, -FLT_MAX); - ImDrawListFlags backup_flags = out_draw_list->Flags; - out_draw_list->Flags &= ~ImDrawListFlags_AntiAliasedLines; // Disable AA on triangle outlines is more readable for very large and thin triangles. - for (unsigned int idx_n = draw_cmd->IdxOffset, idx_end = draw_cmd->IdxOffset + draw_cmd->ElemCount; idx_n < idx_end; ) - { - ImDrawIdx* idx_buffer = (draw_list->IdxBuffer.Size > 0) ? draw_list->IdxBuffer.Data : NULL; // We don't hold on those pointers past iterations as ->AddPolyline() may invalidate them if out_draw_list==draw_list - ImDrawVert* vtx_buffer = draw_list->VtxBuffer.Data + draw_cmd->VtxOffset; - - ImVec2 triangle[3]; - for (int n = 0; n < 3; n++, idx_n++) - vtxs_rect.Add((triangle[n] = vtx_buffer[idx_buffer ? idx_buffer[idx_n] : idx_n].pos)); - if (show_mesh) - out_draw_list->AddPolyline(triangle, 3, IM_COL32(255, 255, 0, 255), ImDrawFlags_Closed, 1.0f); // In yellow: mesh triangles - } - // Draw bounding boxes - if (show_aabb) - { - out_draw_list->AddRect(ImTrunc(clip_rect.Min), ImTrunc(clip_rect.Max), IM_COL32(255, 0, 255, 255)); // In pink: clipping rectangle submitted to GPU - out_draw_list->AddRect(ImTrunc(vtxs_rect.Min), ImTrunc(vtxs_rect.Max), IM_COL32(0, 255, 255, 255)); // In cyan: bounding box of triangles - } - out_draw_list->Flags = backup_flags; -} - -// [DEBUG] Display details for a single font, called by ShowStyleEditor(). -void ImGui::DebugNodeFont(ImFont* font) -{ - bool opened = TreeNode(font, "Font: \"%s\"\n%.2f px, %d glyphs, %d file(s)", - font->ConfigData ? font->ConfigData[0].Name : "", font->FontSize, font->Glyphs.Size, font->ConfigDataCount); - SameLine(); - if (SmallButton("Set as default")) - GetIO().FontDefault = font; - if (!opened) - return; - - // Display preview text - PushFont(font); - Text("The quick brown fox jumps over the lazy dog"); - PopFont(); - - // Display details - SetNextItemWidth(GetFontSize() * 8); - DragFloat("Font scale", &font->Scale, 0.005f, 0.3f, 2.0f, "%.1f"); - SameLine(); MetricsHelpMarker( - "Note than the default embedded font is NOT meant to be scaled.\n\n" - "Font are currently rendered into bitmaps at a given size at the time of building the atlas. " - "You may oversample them to get some flexibility with scaling. " - "You can also render at multiple sizes and select which one to use at runtime.\n\n" - "(Glimmer of hope: the atlas system will be rewritten in the future to make scaling more flexible.)"); - Text("Ascent: %f, Descent: %f, Height: %f", font->Ascent, font->Descent, font->Ascent - font->Descent); - char c_str[5]; - Text("Fallback character: '%s' (U+%04X)", ImTextCharToUtf8(c_str, font->FallbackChar), font->FallbackChar); - Text("Ellipsis character: '%s' (U+%04X)", ImTextCharToUtf8(c_str, font->EllipsisChar), font->EllipsisChar); - const int surface_sqrt = (int)ImSqrt((float)font->MetricsTotalSurface); - Text("Texture Area: about %d px ~%dx%d px", font->MetricsTotalSurface, surface_sqrt, surface_sqrt); - for (int config_i = 0; config_i < font->ConfigDataCount; config_i++) - if (font->ConfigData) - if (const ImFontConfig* cfg = &font->ConfigData[config_i]) - BulletText("Input %d: \'%s\', Oversample: (%d,%d), PixelSnapH: %d, Offset: (%.1f,%.1f)", - config_i, cfg->Name, cfg->OversampleH, cfg->OversampleV, cfg->PixelSnapH, cfg->GlyphOffset.x, cfg->GlyphOffset.y); - - // Display all glyphs of the fonts in separate pages of 256 characters - if (TreeNode("Glyphs", "Glyphs (%d)", font->Glyphs.Size)) - { - ImDrawList* draw_list = GetWindowDrawList(); - const ImU32 glyph_col = GetColorU32(ImGuiCol_Text); - const float cell_size = font->FontSize * 1; - const float cell_spacing = GetStyle().ItemSpacing.y; - for (unsigned int base = 0; base <= IM_UNICODE_CODEPOINT_MAX; base += 256) - { - // Skip ahead if a large bunch of glyphs are not present in the font (test in chunks of 4k) - // This is only a small optimization to reduce the number of iterations when IM_UNICODE_MAX_CODEPOINT - // is large // (if ImWchar==ImWchar32 we will do at least about 272 queries here) - if (!(base & 4095) && font->IsGlyphRangeUnused(base, base + 4095)) - { - base += 4096 - 256; - continue; - } - - int count = 0; - for (unsigned int n = 0; n < 256; n++) - if (font->FindGlyphNoFallback((ImWchar)(base + n))) - count++; - if (count <= 0) - continue; - if (!TreeNode((void*)(intptr_t)base, "U+%04X..U+%04X (%d %s)", base, base + 255, count, count > 1 ? "glyphs" : "glyph")) - continue; - - // Draw a 16x16 grid of glyphs - ImVec2 base_pos = GetCursorScreenPos(); - for (unsigned int n = 0; n < 256; n++) - { - // We use ImFont::RenderChar as a shortcut because we don't have UTF-8 conversion functions - // available here and thus cannot easily generate a zero-terminated UTF-8 encoded string. - ImVec2 cell_p1(base_pos.x + (n % 16) * (cell_size + cell_spacing), base_pos.y + (n / 16) * (cell_size + cell_spacing)); - ImVec2 cell_p2(cell_p1.x + cell_size, cell_p1.y + cell_size); - const ImFontGlyph* glyph = font->FindGlyphNoFallback((ImWchar)(base + n)); - draw_list->AddRect(cell_p1, cell_p2, glyph ? IM_COL32(255, 255, 255, 100) : IM_COL32(255, 255, 255, 50)); - if (!glyph) - continue; - font->RenderChar(draw_list, cell_size, cell_p1, glyph_col, (ImWchar)(base + n)); - if (IsMouseHoveringRect(cell_p1, cell_p2) && BeginTooltip()) - { - DebugNodeFontGlyph(font, glyph); - EndTooltip(); - } - } - Dummy(ImVec2((cell_size + cell_spacing) * 16, (cell_size + cell_spacing) * 16)); - TreePop(); - } - TreePop(); - } - TreePop(); -} - -void ImGui::DebugNodeFontGlyph(ImFont*, const ImFontGlyph* glyph) -{ - Text("Codepoint: U+%04X", glyph->Codepoint); - Separator(); - Text("Visible: %d", glyph->Visible); - Text("AdvanceX: %.1f", glyph->AdvanceX); - Text("Pos: (%.2f,%.2f)->(%.2f,%.2f)", glyph->X0, glyph->Y0, glyph->X1, glyph->Y1); - Text("UV: (%.3f,%.3f)->(%.3f,%.3f)", glyph->U0, glyph->V0, glyph->U1, glyph->V1); -} - -// [DEBUG] Display contents of ImGuiStorage -void ImGui::DebugNodeStorage(ImGuiStorage* storage, const char* label) -{ - if (!TreeNode(label, "%s: %d entries, %d bytes", label, storage->Data.Size, storage->Data.size_in_bytes())) - return; - for (const ImGuiStorage::ImGuiStoragePair& p : storage->Data) - BulletText("Key 0x%08X Value { i: %d }", p.key, p.val_i); // Important: we currently don't store a type, real value may not be integer. - TreePop(); -} - -// [DEBUG] Display contents of ImGuiTabBar -void ImGui::DebugNodeTabBar(ImGuiTabBar* tab_bar, const char* label) -{ - // Standalone tab bars (not associated to docking/windows functionality) currently hold no discernible strings. - char buf[256]; - char* p = buf; - const char* buf_end = buf + IM_ARRAYSIZE(buf); - const bool is_active = (tab_bar->PrevFrameVisible >= GetFrameCount() - 2); - p += ImFormatString(p, buf_end - p, "%s 0x%08X (%d tabs)%s {", label, tab_bar->ID, tab_bar->Tabs.Size, is_active ? "" : " *Inactive*"); - for (int tab_n = 0; tab_n < ImMin(tab_bar->Tabs.Size, 3); tab_n++) - { - ImGuiTabItem* tab = &tab_bar->Tabs[tab_n]; - p += ImFormatString(p, buf_end - p, "%s'%s'", tab_n > 0 ? ", " : "", TabBarGetTabName(tab_bar, tab)); - } - p += ImFormatString(p, buf_end - p, (tab_bar->Tabs.Size > 3) ? " ... }" : " } "); - if (!is_active) { PushStyleColor(ImGuiCol_Text, GetStyleColorVec4(ImGuiCol_TextDisabled)); } - bool open = TreeNode(label, "%s", buf); - if (!is_active) { PopStyleColor(); } - if (is_active && IsItemHovered()) - { - ImDrawList* draw_list = GetForegroundDrawList(); - draw_list->AddRect(tab_bar->BarRect.Min, tab_bar->BarRect.Max, IM_COL32(255, 255, 0, 255)); - draw_list->AddLine(ImVec2(tab_bar->ScrollingRectMinX, tab_bar->BarRect.Min.y), ImVec2(tab_bar->ScrollingRectMinX, tab_bar->BarRect.Max.y), IM_COL32(0, 255, 0, 255)); - draw_list->AddLine(ImVec2(tab_bar->ScrollingRectMaxX, tab_bar->BarRect.Min.y), ImVec2(tab_bar->ScrollingRectMaxX, tab_bar->BarRect.Max.y), IM_COL32(0, 255, 0, 255)); - } - if (open) - { - for (int tab_n = 0; tab_n < tab_bar->Tabs.Size; tab_n++) - { - ImGuiTabItem* tab = &tab_bar->Tabs[tab_n]; - PushID(tab); - if (SmallButton("<")) { TabBarQueueReorder(tab_bar, tab, -1); } SameLine(0, 2); - if (SmallButton(">")) { TabBarQueueReorder(tab_bar, tab, +1); } SameLine(); - Text("%02d%c Tab 0x%08X '%s' Offset: %.2f, Width: %.2f/%.2f", - tab_n, (tab->ID == tab_bar->SelectedTabId) ? '*' : ' ', tab->ID, TabBarGetTabName(tab_bar, tab), tab->Offset, tab->Width, tab->ContentWidth); - PopID(); - } - TreePop(); - } -} - -void ImGui::DebugNodeViewport(ImGuiViewportP* viewport) -{ - SetNextItemOpen(true, ImGuiCond_Once); - if (TreeNode((void*)(intptr_t)viewport->ID, "Viewport #%d, ID: 0x%08X, Parent: 0x%08X, Window: \"%s\"", viewport->Idx, viewport->ID, viewport->ParentViewportId, viewport->Window ? viewport->Window->Name : "N/A")) - { - ImGuiWindowFlags flags = viewport->Flags; - BulletText("Main Pos: (%.0f,%.0f), Size: (%.0f,%.0f)\nWorkArea Offset Left: %.0f Top: %.0f, Right: %.0f, Bottom: %.0f\nMonitor: %d, DpiScale: %.0f%%", - viewport->Pos.x, viewport->Pos.y, viewport->Size.x, viewport->Size.y, - viewport->WorkOffsetMin.x, viewport->WorkOffsetMin.y, viewport->WorkOffsetMax.x, viewport->WorkOffsetMax.y, - viewport->PlatformMonitor, viewport->DpiScale * 100.0f); - if (viewport->Idx > 0) { SameLine(); if (SmallButton("Reset Pos")) { viewport->Pos = ImVec2(200, 200); viewport->UpdateWorkRect(); if (viewport->Window) viewport->Window->Pos = viewport->Pos; } } - BulletText("Flags: 0x%04X =%s%s%s%s%s%s%s%s%s%s%s%s%s", viewport->Flags, - //(flags & ImGuiViewportFlags_IsPlatformWindow) ? " IsPlatformWindow" : "", // Omitting because it is the standard - (flags & ImGuiViewportFlags_IsPlatformMonitor) ? " IsPlatformMonitor" : "", - (flags & ImGuiViewportFlags_IsMinimized) ? " IsMinimized" : "", - (flags & ImGuiViewportFlags_IsFocused) ? " IsFocused" : "", - (flags & ImGuiViewportFlags_OwnedByApp) ? " OwnedByApp" : "", - (flags & ImGuiViewportFlags_NoDecoration) ? " NoDecoration" : "", - (flags & ImGuiViewportFlags_NoTaskBarIcon) ? " NoTaskBarIcon" : "", - (flags & ImGuiViewportFlags_NoFocusOnAppearing) ? " NoFocusOnAppearing" : "", - (flags & ImGuiViewportFlags_NoFocusOnClick) ? " NoFocusOnClick" : "", - (flags & ImGuiViewportFlags_NoInputs) ? " NoInputs" : "", - (flags & ImGuiViewportFlags_NoRendererClear) ? " NoRendererClear" : "", - (flags & ImGuiViewportFlags_NoAutoMerge) ? " NoAutoMerge" : "", - (flags & ImGuiViewportFlags_TopMost) ? " TopMost" : "", - (flags & ImGuiViewportFlags_CanHostOtherWindows) ? " CanHostOtherWindows" : ""); - for (ImDrawList* draw_list : viewport->DrawDataP.CmdLists) - DebugNodeDrawList(NULL, viewport, draw_list, "DrawList"); - TreePop(); - } -} - -void ImGui::DebugNodeWindow(ImGuiWindow* window, const char* label) -{ - if (window == NULL) - { - BulletText("%s: NULL", label); - return; - } - - ImGuiContext& g = *GImGui; - const bool is_active = window->WasActive; - ImGuiTreeNodeFlags tree_node_flags = (window == g.NavWindow) ? ImGuiTreeNodeFlags_Selected : ImGuiTreeNodeFlags_None; - if (!is_active) { PushStyleColor(ImGuiCol_Text, GetStyleColorVec4(ImGuiCol_TextDisabled)); } - const bool open = TreeNodeEx(label, tree_node_flags, "%s '%s'%s", label, window->Name, is_active ? "" : " *Inactive*"); - if (!is_active) { PopStyleColor(); } - if (IsItemHovered() && is_active) - GetForegroundDrawList(window)->AddRect(window->Pos, window->Pos + window->Size, IM_COL32(255, 255, 0, 255)); - if (!open) - return; - - if (window->MemoryCompacted) - TextDisabled("Note: some memory buffers have been compacted/freed."); - - ImGuiWindowFlags flags = window->Flags; - DebugNodeDrawList(window, window->Viewport, window->DrawList, "DrawList"); - BulletText("Pos: (%.1f,%.1f), Size: (%.1f,%.1f), ContentSize (%.1f,%.1f) Ideal (%.1f,%.1f)", window->Pos.x, window->Pos.y, window->Size.x, window->Size.y, window->ContentSize.x, window->ContentSize.y, window->ContentSizeIdeal.x, window->ContentSizeIdeal.y); - BulletText("Flags: 0x%08X (%s%s%s%s%s%s%s%s%s..)", flags, - (flags & ImGuiWindowFlags_ChildWindow) ? "Child " : "", (flags & ImGuiWindowFlags_Tooltip) ? "Tooltip " : "", (flags & ImGuiWindowFlags_Popup) ? "Popup " : "", - (flags & ImGuiWindowFlags_Modal) ? "Modal " : "", (flags & ImGuiWindowFlags_ChildMenu) ? "ChildMenu " : "", (flags & ImGuiWindowFlags_NoSavedSettings) ? "NoSavedSettings " : "", - (flags & ImGuiWindowFlags_NoMouseInputs)? "NoMouseInputs":"", (flags & ImGuiWindowFlags_NoNavInputs) ? "NoNavInputs" : "", (flags & ImGuiWindowFlags_AlwaysAutoResize) ? "AlwaysAutoResize" : ""); - BulletText("WindowClassId: 0x%08X", window->WindowClass.ClassId); - BulletText("Scroll: (%.2f/%.2f,%.2f/%.2f) Scrollbar:%s%s", window->Scroll.x, window->ScrollMax.x, window->Scroll.y, window->ScrollMax.y, window->ScrollbarX ? "X" : "", window->ScrollbarY ? "Y" : ""); - BulletText("Active: %d/%d, WriteAccessed: %d, BeginOrderWithinContext: %d", window->Active, window->WasActive, window->WriteAccessed, (window->Active || window->WasActive) ? window->BeginOrderWithinContext : -1); - BulletText("Appearing: %d, Hidden: %d (CanSkip %d Cannot %d), SkipItems: %d", window->Appearing, window->Hidden, window->HiddenFramesCanSkipItems, window->HiddenFramesCannotSkipItems, window->SkipItems); - for (int layer = 0; layer < ImGuiNavLayer_COUNT; layer++) - { - ImRect r = window->NavRectRel[layer]; - if (r.Min.x >= r.Max.y && r.Min.y >= r.Max.y) - BulletText("NavLastIds[%d]: 0x%08X", layer, window->NavLastIds[layer]); - else - BulletText("NavLastIds[%d]: 0x%08X at +(%.1f,%.1f)(%.1f,%.1f)", layer, window->NavLastIds[layer], r.Min.x, r.Min.y, r.Max.x, r.Max.y); - DebugLocateItemOnHover(window->NavLastIds[layer]); - } - const ImVec2* pr = window->NavPreferredScoringPosRel; - for (int layer = 0; layer < ImGuiNavLayer_COUNT; layer++) - BulletText("NavPreferredScoringPosRel[%d] = {%.1f,%.1f)", layer, (pr[layer].x == FLT_MAX ? -99999.0f : pr[layer].x), (pr[layer].y == FLT_MAX ? -99999.0f : pr[layer].y)); // Display as 99999.0f so it looks neater. - BulletText("NavLayersActiveMask: %X, NavLastChildNavWindow: %s", window->DC.NavLayersActiveMask, window->NavLastChildNavWindow ? window->NavLastChildNavWindow->Name : "NULL"); - - BulletText("Viewport: %d%s, ViewportId: 0x%08X, ViewportPos: (%.1f,%.1f)", window->Viewport ? window->Viewport->Idx : -1, window->ViewportOwned ? " (Owned)" : "", window->ViewportId, window->ViewportPos.x, window->ViewportPos.y); - BulletText("ViewportMonitor: %d", window->Viewport ? window->Viewport->PlatformMonitor : -1); - BulletText("DockId: 0x%04X, DockOrder: %d, Act: %d, Vis: %d", window->DockId, window->DockOrder, window->DockIsActive, window->DockTabIsVisible); - if (window->DockNode || window->DockNodeAsHost) - DebugNodeDockNode(window->DockNodeAsHost ? window->DockNodeAsHost : window->DockNode, window->DockNodeAsHost ? "DockNodeAsHost" : "DockNode"); - - if (window->RootWindow != window) { DebugNodeWindow(window->RootWindow, "RootWindow"); } - if (window->RootWindowDockTree != window->RootWindow) { DebugNodeWindow(window->RootWindowDockTree, "RootWindowDockTree"); } - if (window->ParentWindow != NULL) { DebugNodeWindow(window->ParentWindow, "ParentWindow"); } - if (window->DC.ChildWindows.Size > 0) { DebugNodeWindowsList(&window->DC.ChildWindows, "ChildWindows"); } - if (window->ColumnsStorage.Size > 0 && TreeNode("Columns", "Columns sets (%d)", window->ColumnsStorage.Size)) - { - for (ImGuiOldColumns& columns : window->ColumnsStorage) - DebugNodeColumns(&columns); - TreePop(); - } - DebugNodeStorage(&window->StateStorage, "Storage"); - TreePop(); -} - -void ImGui::DebugNodeWindowSettings(ImGuiWindowSettings* settings) -{ - if (settings->WantDelete) - BeginDisabled(); - Text("0x%08X \"%s\" Pos (%d,%d) Size (%d,%d) Collapsed=%d", - settings->ID, settings->GetName(), settings->Pos.x, settings->Pos.y, settings->Size.x, settings->Size.y, settings->Collapsed); - if (settings->WantDelete) - EndDisabled(); -} - -void ImGui::DebugNodeWindowsList(ImVector* windows, const char* label) -{ - if (!TreeNode(label, "%s (%d)", label, windows->Size)) - return; - for (int i = windows->Size - 1; i >= 0; i--) // Iterate front to back - { - PushID((*windows)[i]); - DebugNodeWindow((*windows)[i], "Window"); - PopID(); - } - TreePop(); -} - -// FIXME-OPT: This is technically suboptimal, but it is simpler this way. -void ImGui::DebugNodeWindowsListByBeginStackParent(ImGuiWindow** windows, int windows_size, ImGuiWindow* parent_in_begin_stack) -{ - for (int i = 0; i < windows_size; i++) - { - ImGuiWindow* window = windows[i]; - if (window->ParentWindowInBeginStack != parent_in_begin_stack) - continue; - char buf[20]; - ImFormatString(buf, IM_ARRAYSIZE(buf), "[%04d] Window", window->BeginOrderWithinContext); - //BulletText("[%04d] Window '%s'", window->BeginOrderWithinContext, window->Name); - DebugNodeWindow(window, buf); - Indent(); - DebugNodeWindowsListByBeginStackParent(windows + i + 1, windows_size - i - 1, window); - Unindent(); - } -} - -//----------------------------------------------------------------------------- -// [SECTION] DEBUG LOG WINDOW -//----------------------------------------------------------------------------- - -void ImGui::DebugLog(const char* fmt, ...) -{ - va_list args; - va_start(args, fmt); - DebugLogV(fmt, args); - va_end(args); -} - -void ImGui::DebugLogV(const char* fmt, va_list args) -{ - ImGuiContext& g = *GImGui; - const int old_size = g.DebugLogBuf.size(); - g.DebugLogBuf.appendf("[%05d] ", g.FrameCount); - g.DebugLogBuf.appendfv(fmt, args); - g.DebugLogIndex.append(g.DebugLogBuf.c_str(), old_size, g.DebugLogBuf.size()); - if (g.DebugLogFlags & ImGuiDebugLogFlags_OutputToTTY) - IMGUI_DEBUG_PRINTF("%s", g.DebugLogBuf.begin() + old_size); -#ifdef IMGUI_ENABLE_TEST_ENGINE - if (g.DebugLogFlags & ImGuiDebugLogFlags_OutputToTestEngine) - IMGUI_TEST_ENGINE_LOG("%s", g.DebugLogBuf.begin() + old_size); -#endif -} - -void ImGui::ShowDebugLogWindow(bool* p_open) -{ - ImGuiContext& g = *GImGui; - if (!(g.NextWindowData.Flags & ImGuiNextWindowDataFlags_HasSize)) - SetNextWindowSize(ImVec2(0.0f, GetFontSize() * 12.0f), ImGuiCond_FirstUseEver); - if (!Begin("Dear ImGui Debug Log", p_open) || GetCurrentWindow()->BeginCount > 1) - { - End(); - return; - } - - CheckboxFlags("All", &g.DebugLogFlags, ImGuiDebugLogFlags_EventMask_); - SameLine(); CheckboxFlags("ActiveId", &g.DebugLogFlags, ImGuiDebugLogFlags_EventActiveId); - SameLine(); CheckboxFlags("Focus", &g.DebugLogFlags, ImGuiDebugLogFlags_EventFocus); - SameLine(); CheckboxFlags("Popup", &g.DebugLogFlags, ImGuiDebugLogFlags_EventPopup); - SameLine(); CheckboxFlags("Nav", &g.DebugLogFlags, ImGuiDebugLogFlags_EventNav); - SameLine(); if (CheckboxFlags("Clipper", &g.DebugLogFlags, ImGuiDebugLogFlags_EventClipper)) { g.DebugLogClipperAutoDisableFrames = 2; } if (IsItemHovered()) SetTooltip("Clipper log auto-disabled after 2 frames"); - //SameLine(); CheckboxFlags("Selection", &g.DebugLogFlags, ImGuiDebugLogFlags_EventSelection); - SameLine(); CheckboxFlags("IO", &g.DebugLogFlags, ImGuiDebugLogFlags_EventIO); - SameLine(); CheckboxFlags("Docking", &g.DebugLogFlags, ImGuiDebugLogFlags_EventDocking); - SameLine(); CheckboxFlags("Viewport", &g.DebugLogFlags, ImGuiDebugLogFlags_EventViewport); - - if (SmallButton("Clear")) - { - g.DebugLogBuf.clear(); - g.DebugLogIndex.clear(); - } - SameLine(); - if (SmallButton("Copy")) - SetClipboardText(g.DebugLogBuf.c_str()); - BeginChild("##log", ImVec2(0.0f, 0.0f), true, ImGuiWindowFlags_AlwaysVerticalScrollbar | ImGuiWindowFlags_AlwaysHorizontalScrollbar); - - ImGuiListClipper clipper; - clipper.Begin(g.DebugLogIndex.size()); - while (clipper.Step()) - for (int line_no = clipper.DisplayStart; line_no < clipper.DisplayEnd; line_no++) - { - const char* line_begin = g.DebugLogIndex.get_line_begin(g.DebugLogBuf.c_str(), line_no); - const char* line_end = g.DebugLogIndex.get_line_end(g.DebugLogBuf.c_str(), line_no); - TextUnformatted(line_begin, line_end); - ImRect text_rect = g.LastItemData.Rect; - if (IsItemHovered()) - for (const char* p = line_begin; p <= line_end - 10; p++) - { - ImGuiID id = 0; - if (p[0] != '0' || (p[1] != 'x' && p[1] != 'X') || sscanf(p + 2, "%X", &id) != 1) - continue; - ImVec2 p0 = CalcTextSize(line_begin, p); - ImVec2 p1 = CalcTextSize(p, p + 10); - g.LastItemData.Rect = ImRect(text_rect.Min + ImVec2(p0.x, 0.0f), text_rect.Min + ImVec2(p0.x + p1.x, p1.y)); - if (IsMouseHoveringRect(g.LastItemData.Rect.Min, g.LastItemData.Rect.Max, true)) - DebugLocateItemOnHover(id); - p += 10; - } - } - if (GetScrollY() >= GetScrollMaxY()) - SetScrollHereY(1.0f); - EndChild(); - - End(); -} - -//----------------------------------------------------------------------------- -// [SECTION] OTHER DEBUG TOOLS (ITEM PICKER, ID STACK TOOL) -//----------------------------------------------------------------------------- - -// Draw a small cross at current CursorPos in current window's DrawList -void ImGui::DebugDrawCursorPos(ImU32 col) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - ImVec2 pos = window->DC.CursorPos; - window->DrawList->AddLine(ImVec2(pos.x, pos.y - 3.0f), ImVec2(pos.x, pos.y + 4.0f), col, 1.0f); - window->DrawList->AddLine(ImVec2(pos.x - 3.0f, pos.y), ImVec2(pos.x + 4.0f, pos.y), col, 1.0f); -} - -// Draw a 10px wide rectangle around CurposPos.x using Line Y1/Y2 in current window's DrawList -void ImGui::DebugDrawLineExtents(ImU32 col) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - float curr_x = window->DC.CursorPos.x; - float line_y1 = (window->DC.IsSameLine ? window->DC.CursorPosPrevLine.y : window->DC.CursorPos.y); - float line_y2 = line_y1 + (window->DC.IsSameLine ? window->DC.PrevLineSize.y : window->DC.CurrLineSize.y); - window->DrawList->AddLine(ImVec2(curr_x - 5.0f, line_y1), ImVec2(curr_x + 5.0f, line_y1), col, 1.0f); - window->DrawList->AddLine(ImVec2(curr_x - 0.5f, line_y1), ImVec2(curr_x - 0.5f, line_y2), col, 1.0f); - window->DrawList->AddLine(ImVec2(curr_x - 5.0f, line_y2), ImVec2(curr_x + 5.0f, line_y2), col, 1.0f); -} - -// Draw last item rect in ForegroundDrawList (so it is always visible) -void ImGui::DebugDrawItemRect(ImU32 col) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - GetForegroundDrawList(window)->AddRect(g.LastItemData.Rect.Min, g.LastItemData.Rect.Max, col); -} - -// [DEBUG] Locate item position/rectangle given an ID. -static const ImU32 DEBUG_LOCATE_ITEM_COLOR = IM_COL32(0, 255, 0, 255); // Green - -void ImGui::DebugLocateItem(ImGuiID target_id) -{ - ImGuiContext& g = *GImGui; - g.DebugLocateId = target_id; - g.DebugLocateFrames = 2; -} - -void ImGui::DebugLocateItemOnHover(ImGuiID target_id) -{ - if (target_id == 0 || !IsItemHovered(ImGuiHoveredFlags_AllowWhenBlockedByActiveItem | ImGuiHoveredFlags_AllowWhenBlockedByPopup)) - return; - ImGuiContext& g = *GImGui; - DebugLocateItem(target_id); - GetForegroundDrawList(g.CurrentWindow)->AddRect(g.LastItemData.Rect.Min - ImVec2(3.0f, 3.0f), g.LastItemData.Rect.Max + ImVec2(3.0f, 3.0f), DEBUG_LOCATE_ITEM_COLOR); -} - -void ImGui::DebugLocateItemResolveWithLastItem() -{ - ImGuiContext& g = *GImGui; - ImGuiLastItemData item_data = g.LastItemData; - g.DebugLocateId = 0; - ImDrawList* draw_list = GetForegroundDrawList(g.CurrentWindow); - ImRect r = item_data.Rect; - r.Expand(3.0f); - ImVec2 p1 = g.IO.MousePos; - ImVec2 p2 = ImVec2((p1.x < r.Min.x) ? r.Min.x : (p1.x > r.Max.x) ? r.Max.x : p1.x, (p1.y < r.Min.y) ? r.Min.y : (p1.y > r.Max.y) ? r.Max.y : p1.y); - draw_list->AddRect(r.Min, r.Max, DEBUG_LOCATE_ITEM_COLOR); - draw_list->AddLine(p1, p2, DEBUG_LOCATE_ITEM_COLOR); -} - -// [DEBUG] Item picker tool - start with DebugStartItemPicker() - useful to visually select an item and break into its call-stack. -void ImGui::UpdateDebugToolItemPicker() -{ - ImGuiContext& g = *GImGui; - g.DebugItemPickerBreakId = 0; - if (!g.DebugItemPickerActive) - return; - - const ImGuiID hovered_id = g.HoveredIdPreviousFrame; - SetMouseCursor(ImGuiMouseCursor_Hand); - if (IsKeyPressed(ImGuiKey_Escape)) - g.DebugItemPickerActive = false; - const bool change_mapping = g.IO.KeyMods == (ImGuiMod_Ctrl | ImGuiMod_Shift); - if (!change_mapping && IsMouseClicked(g.DebugItemPickerMouseButton) && hovered_id) - { - g.DebugItemPickerBreakId = hovered_id; - g.DebugItemPickerActive = false; - } - for (int mouse_button = 0; mouse_button < 3; mouse_button++) - if (change_mapping && IsMouseClicked(mouse_button)) - g.DebugItemPickerMouseButton = (ImU8)mouse_button; - SetNextWindowBgAlpha(0.70f); - if (!BeginTooltip()) - return; - Text("HoveredId: 0x%08X", hovered_id); - Text("Press ESC to abort picking."); - const char* mouse_button_names[] = { "Left", "Right", "Middle" }; - if (change_mapping) - Text("Remap w/ Ctrl+Shift: click anywhere to select new mouse button."); - else - TextColored(GetStyleColorVec4(hovered_id ? ImGuiCol_Text : ImGuiCol_TextDisabled), "Click %s Button to break in debugger! (remap w/ Ctrl+Shift)", mouse_button_names[g.DebugItemPickerMouseButton]); - EndTooltip(); -} - -// [DEBUG] ID Stack Tool: update queries. Called by NewFrame() -void ImGui::UpdateDebugToolStackQueries() -{ - ImGuiContext& g = *GImGui; - ImGuiIDStackTool* tool = &g.DebugIDStackTool; - - // Clear hook when id stack tool is not visible - g.DebugHookIdInfo = 0; - if (g.FrameCount != tool->LastActiveFrame + 1) - return; - - // Update queries. The steps are: -1: query Stack, >= 0: query each stack item - // We can only perform 1 ID Info query every frame. This is designed so the GetID() tests are cheap and constant-time - const ImGuiID query_id = g.HoveredIdPreviousFrame ? g.HoveredIdPreviousFrame : g.ActiveId; - if (tool->QueryId != query_id) - { - tool->QueryId = query_id; - tool->StackLevel = -1; - tool->Results.resize(0); - } - if (query_id == 0) - return; - - // Advance to next stack level when we got our result, or after 2 frames (in case we never get a result) - int stack_level = tool->StackLevel; - if (stack_level >= 0 && stack_level < tool->Results.Size) - if (tool->Results[stack_level].QuerySuccess || tool->Results[stack_level].QueryFrameCount > 2) - tool->StackLevel++; - - // Update hook - stack_level = tool->StackLevel; - if (stack_level == -1) - g.DebugHookIdInfo = query_id; - if (stack_level >= 0 && stack_level < tool->Results.Size) - { - g.DebugHookIdInfo = tool->Results[stack_level].ID; - tool->Results[stack_level].QueryFrameCount++; - } -} - -// [DEBUG] ID Stack tool: hooks called by GetID() family functions -void ImGui::DebugHookIdInfo(ImGuiID id, ImGuiDataType data_type, const void* data_id, const void* data_id_end) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - ImGuiIDStackTool* tool = &g.DebugIDStackTool; - - // Step 0: stack query - // This assumes that the ID was computed with the current ID stack, which tends to be the case for our widget. - if (tool->StackLevel == -1) - { - tool->StackLevel++; - tool->Results.resize(window->IDStack.Size + 1, ImGuiStackLevelInfo()); - for (int n = 0; n < window->IDStack.Size + 1; n++) - tool->Results[n].ID = (n < window->IDStack.Size) ? window->IDStack[n] : id; - return; - } - - // Step 1+: query for individual level - IM_ASSERT(tool->StackLevel >= 0); - if (tool->StackLevel != window->IDStack.Size) - return; - ImGuiStackLevelInfo* info = &tool->Results[tool->StackLevel]; - IM_ASSERT(info->ID == id && info->QueryFrameCount > 0); - - switch (data_type) - { - case ImGuiDataType_S32: - ImFormatString(info->Desc, IM_ARRAYSIZE(info->Desc), "%d", (int)(intptr_t)data_id); - break; - case ImGuiDataType_String: - ImFormatString(info->Desc, IM_ARRAYSIZE(info->Desc), "%.*s", data_id_end ? (int)((const char*)data_id_end - (const char*)data_id) : (int)strlen((const char*)data_id), (const char*)data_id); - break; - case ImGuiDataType_Pointer: - ImFormatString(info->Desc, IM_ARRAYSIZE(info->Desc), "(void*)0x%p", data_id); - break; - case ImGuiDataType_ID: - if (info->Desc[0] != 0) // PushOverrideID() is often used to avoid hashing twice, which would lead to 2 calls to DebugHookIdInfo(). We prioritize the first one. - return; - ImFormatString(info->Desc, IM_ARRAYSIZE(info->Desc), "0x%08X [override]", id); - break; - default: - IM_ASSERT(0); - } - info->QuerySuccess = true; - info->DataType = data_type; -} - -static int StackToolFormatLevelInfo(ImGuiIDStackTool* tool, int n, bool format_for_ui, char* buf, size_t buf_size) -{ - ImGuiStackLevelInfo* info = &tool->Results[n]; - ImGuiWindow* window = (info->Desc[0] == 0 && n == 0) ? ImGui::FindWindowByID(info->ID) : NULL; - if (window) // Source: window name (because the root ID don't call GetID() and so doesn't get hooked) - return ImFormatString(buf, buf_size, format_for_ui ? "\"%s\" [window]" : "%s", window->Name); - if (info->QuerySuccess) // Source: GetID() hooks (prioritize over ItemInfo() because we frequently use patterns like: PushID(str), Button("") where they both have same id) - return ImFormatString(buf, buf_size, (format_for_ui && info->DataType == ImGuiDataType_String) ? "\"%s\"" : "%s", info->Desc); - if (tool->StackLevel < tool->Results.Size) // Only start using fallback below when all queries are done, so during queries we don't flickering ??? markers. - return (*buf = 0); -#ifdef IMGUI_ENABLE_TEST_ENGINE - if (const char* label = ImGuiTestEngine_FindItemDebugLabel(GImGui, info->ID)) // Source: ImGuiTestEngine's ItemInfo() - return ImFormatString(buf, buf_size, format_for_ui ? "??? \"%s\"" : "%s", label); -#endif - return ImFormatString(buf, buf_size, "???"); -} - -// ID Stack Tool: Display UI -void ImGui::ShowIDStackToolWindow(bool* p_open) -{ - ImGuiContext& g = *GImGui; - if (!(g.NextWindowData.Flags & ImGuiNextWindowDataFlags_HasSize)) - SetNextWindowSize(ImVec2(0.0f, GetFontSize() * 8.0f), ImGuiCond_FirstUseEver); - if (!Begin("Dear ImGui ID Stack Tool", p_open) || GetCurrentWindow()->BeginCount > 1) - { - End(); - return; - } - - // Display hovered/active status - ImGuiIDStackTool* tool = &g.DebugIDStackTool; - const ImGuiID hovered_id = g.HoveredIdPreviousFrame; - const ImGuiID active_id = g.ActiveId; -#ifdef IMGUI_ENABLE_TEST_ENGINE - Text("HoveredId: 0x%08X (\"%s\"), ActiveId: 0x%08X (\"%s\")", hovered_id, hovered_id ? ImGuiTestEngine_FindItemDebugLabel(&g, hovered_id) : "", active_id, active_id ? ImGuiTestEngine_FindItemDebugLabel(&g, active_id) : ""); -#else - Text("HoveredId: 0x%08X, ActiveId: 0x%08X", hovered_id, active_id); -#endif - SameLine(); - MetricsHelpMarker("Hover an item with the mouse to display elements of the ID Stack leading to the item's final ID.\nEach level of the stack correspond to a PushID() call.\nAll levels of the stack are hashed together to make the final ID of a widget (ID displayed at the bottom level of the stack).\nRead FAQ entry about the ID stack for details."); - - // CTRL+C to copy path - const float time_since_copy = (float)g.Time - tool->CopyToClipboardLastTime; - Checkbox("Ctrl+C: copy path to clipboard", &tool->CopyToClipboardOnCtrlC); - SameLine(); - TextColored((time_since_copy >= 0.0f && time_since_copy < 0.75f && ImFmod(time_since_copy, 0.25f) < 0.25f * 0.5f) ? ImVec4(1.f, 1.f, 0.3f, 1.f) : ImVec4(), "*COPIED*"); - if (tool->CopyToClipboardOnCtrlC && IsKeyDown(ImGuiMod_Ctrl) && IsKeyPressed(ImGuiKey_C)) - { - tool->CopyToClipboardLastTime = (float)g.Time; - char* p = g.TempBuffer.Data; - char* p_end = p + g.TempBuffer.Size; - for (int stack_n = 0; stack_n < tool->Results.Size && p + 3 < p_end; stack_n++) - { - *p++ = '/'; - char level_desc[256]; - StackToolFormatLevelInfo(tool, stack_n, false, level_desc, IM_ARRAYSIZE(level_desc)); - for (int n = 0; level_desc[n] && p + 2 < p_end; n++) - { - if (level_desc[n] == '/') - *p++ = '\\'; - *p++ = level_desc[n]; - } - } - *p = '\0'; - SetClipboardText(g.TempBuffer.Data); - } - - // Display decorated stack - tool->LastActiveFrame = g.FrameCount; - if (tool->Results.Size > 0 && BeginTable("##table", 3, ImGuiTableFlags_Borders)) - { - const float id_width = CalcTextSize("0xDDDDDDDD").x; - TableSetupColumn("Seed", ImGuiTableColumnFlags_WidthFixed, id_width); - TableSetupColumn("PushID", ImGuiTableColumnFlags_WidthStretch); - TableSetupColumn("Result", ImGuiTableColumnFlags_WidthFixed, id_width); - TableHeadersRow(); - for (int n = 0; n < tool->Results.Size; n++) - { - ImGuiStackLevelInfo* info = &tool->Results[n]; - TableNextColumn(); - Text("0x%08X", (n > 0) ? tool->Results[n - 1].ID : 0); - TableNextColumn(); - StackToolFormatLevelInfo(tool, n, true, g.TempBuffer.Data, g.TempBuffer.Size); - TextUnformatted(g.TempBuffer.Data); - TableNextColumn(); - Text("0x%08X", info->ID); - if (n == tool->Results.Size - 1) - TableSetBgColor(ImGuiTableBgTarget_CellBg, GetColorU32(ImGuiCol_Header)); - } - EndTable(); - } - End(); -} - -#else - -void ImGui::ShowMetricsWindow(bool*) {} -void ImGui::ShowFontAtlas(ImFontAtlas*) {} -void ImGui::DebugNodeColumns(ImGuiOldColumns*) {} -void ImGui::DebugNodeDrawList(ImGuiWindow*, ImGuiViewportP*, const ImDrawList*, const char*) {} -void ImGui::DebugNodeDrawCmdShowMeshAndBoundingBox(ImDrawList*, const ImDrawList*, const ImDrawCmd*, bool, bool) {} -void ImGui::DebugNodeFont(ImFont*) {} -void ImGui::DebugNodeStorage(ImGuiStorage*, const char*) {} -void ImGui::DebugNodeTabBar(ImGuiTabBar*, const char*) {} -void ImGui::DebugNodeWindow(ImGuiWindow*, const char*) {} -void ImGui::DebugNodeWindowSettings(ImGuiWindowSettings*) {} -void ImGui::DebugNodeWindowsList(ImVector*, const char*) {} -void ImGui::DebugNodeViewport(ImGuiViewportP*) {} - -void ImGui::DebugLog(const char*, ...) {} -void ImGui::DebugLogV(const char*, va_list) {} -void ImGui::ShowDebugLogWindow(bool*) {} -void ImGui::ShowIDStackToolWindow(bool*) {} -void ImGui::DebugHookIdInfo(ImGuiID, ImGuiDataType, const void*, const void*) {} -void ImGui::UpdateDebugToolItemPicker() {} -void ImGui::UpdateDebugToolStackQueries() {} - -#endif // #ifndef IMGUI_DISABLE_DEBUG_TOOLS - -//----------------------------------------------------------------------------- - -// Include imgui_user.inl at the end of imgui.cpp to access private data/functions that aren't exposed. -// Prefer just including imgui_internal.h from your code rather than using this define. If a declaration is missing from imgui_internal.h add it or request it on the github. -#ifdef IMGUI_INCLUDE_IMGUI_USER_INL -#include "imgui_user.inl" -#endif - -//----------------------------------------------------------------------------- - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/imgui.h b/app/jni/src/libultraship/extern/ImGui/imgui.h deleted file mode 100644 index 50b43f7..0000000 --- a/app/jni/src/libultraship/extern/ImGui/imgui.h +++ /dev/null @@ -1,3476 +0,0 @@ -// dear imgui, v1.90 WIP -// (headers) - -// Help: -// - See links below. -// - Call and read ImGui::ShowDemoWindow() in imgui_demo.cpp. All applications in examples/ are doing that. -// - Read top of imgui.cpp for more details, links and comments. - -// Resources: -// - FAQ https://dearimgui.com/faq -// - Getting Started https://dearimgui.com/getting-started -// - Homepage https://github.com/ocornut/imgui -// - Releases & changelog https://github.com/ocornut/imgui/releases -// - Gallery https://github.com/ocornut/imgui/issues/6897 (please post your screenshots/video there!) -// - Wiki https://github.com/ocornut/imgui/wiki (lots of good stuff there) -// - Glossary https://github.com/ocornut/imgui/wiki/Glossary -// - Issues & support https://github.com/ocornut/imgui/issues -// - Tests & Automation https://github.com/ocornut/imgui_test_engine - -// For first-time users having issues compiling/linking/running/loading fonts: -// please post in https://github.com/ocornut/imgui/discussions if you cannot find a solution in resources above. -// Everything else should be asked in 'Issues'! We are building a database of cross-linked knowledge there. - -// Library Version -// (Integer encoded as XYYZZ for use in #if preprocessor conditionals, e.g. '#if IMGUI_VERSION_NUM >= 12345') -#define IMGUI_VERSION "1.90 WIP" -#define IMGUI_VERSION_NUM 18995 -#define IMGUI_HAS_TABLE -#define IMGUI_HAS_VIEWPORT // Viewport WIP branch -#define IMGUI_HAS_DOCK // Docking WIP branch - -/* - -Index of this file: -// [SECTION] Header mess -// [SECTION] Forward declarations and basic types -// [SECTION] Dear ImGui end-user API functions -// [SECTION] Flags & Enumerations -// [SECTION] Helpers: Memory allocations macros, ImVector<> -// [SECTION] ImGuiStyle -// [SECTION] ImGuiIO -// [SECTION] Misc data structures (ImGuiInputTextCallbackData, ImGuiSizeCallbackData, ImGuiWindowClass, ImGuiPayload, ImGuiTableSortSpecs, ImGuiTableColumnSortSpecs) -// [SECTION] Helpers (ImGuiOnceUponAFrame, ImGuiTextFilter, ImGuiTextBuffer, ImGuiStorage, ImGuiListClipper, Math Operators, ImColor) -// [SECTION] Drawing API (ImDrawCallback, ImDrawCmd, ImDrawIdx, ImDrawVert, ImDrawChannel, ImDrawListSplitter, ImDrawFlags, ImDrawListFlags, ImDrawList, ImDrawData) -// [SECTION] Font API (ImFontConfig, ImFontGlyph, ImFontGlyphRangesBuilder, ImFontAtlasFlags, ImFontAtlas, ImFont) -// [SECTION] Viewports (ImGuiViewportFlags, ImGuiViewport) -// [SECTION] Platform Dependent Interfaces (ImGuiPlatformIO, ImGuiPlatformMonitor, ImGuiPlatformImeData) -// [SECTION] Obsolete functions and types - -*/ - -#pragma once - -// Configuration file with compile-time options -// (edit imconfig.h or '#define IMGUI_USER_CONFIG "myfilename.h" from your build system) -#ifdef IMGUI_USER_CONFIG -#include IMGUI_USER_CONFIG -#endif -#include "imconfig.h" - -#ifndef IMGUI_DISABLE - -//----------------------------------------------------------------------------- -// [SECTION] Header mess -//----------------------------------------------------------------------------- - -// Includes -#include // FLT_MIN, FLT_MAX -#include // va_list, va_start, va_end -#include // ptrdiff_t, NULL -#include // memset, memmove, memcpy, strlen, strchr, strcpy, strcmp - -// Define attributes of all API symbols declarations (e.g. for DLL under Windows) -// IMGUI_API is used for core imgui functions, IMGUI_IMPL_API is used for the default backends files (imgui_impl_xxx.h) -// Using dear imgui via a shared library is not recommended: we don't guarantee backward nor forward ABI compatibility + this is a call-heavy library and function call overhead adds up. -#ifndef IMGUI_API -#define IMGUI_API -#endif -#ifndef IMGUI_IMPL_API -#define IMGUI_IMPL_API IMGUI_API -#endif - -// Helper Macros -#ifndef IM_ASSERT -#include -#define IM_ASSERT(_EXPR) assert(_EXPR) // You can override the default assert handler by editing imconfig.h -#endif -#define IM_ARRAYSIZE(_ARR) ((int)(sizeof(_ARR) / sizeof(*(_ARR)))) // Size of a static C-style array. Don't use on pointers! -#define IM_UNUSED(_VAR) ((void)(_VAR)) // Used to silence "unused variable warnings". Often useful as asserts may be stripped out from final builds. -#define IM_OFFSETOF(_TYPE,_MEMBER) offsetof(_TYPE, _MEMBER) // Offset of _MEMBER within _TYPE. Standardized as offsetof() in C++11 -#define IMGUI_CHECKVERSION() ImGui::DebugCheckVersionAndDataLayout(IMGUI_VERSION, sizeof(ImGuiIO), sizeof(ImGuiStyle), sizeof(ImVec2), sizeof(ImVec4), sizeof(ImDrawVert), sizeof(ImDrawIdx)) - -// Helper Macros - IM_FMTARGS, IM_FMTLIST: Apply printf-style warnings to our formatting functions. -#if !defined(IMGUI_USE_STB_SPRINTF) && defined(__MINGW32__) && !defined(__clang__) -#define IM_FMTARGS(FMT) __attribute__((format(gnu_printf, FMT, FMT+1))) -#define IM_FMTLIST(FMT) __attribute__((format(gnu_printf, FMT, 0))) -#elif !defined(IMGUI_USE_STB_SPRINTF) && (defined(__clang__) || defined(__GNUC__)) -#define IM_FMTARGS(FMT) __attribute__((format(printf, FMT, FMT+1))) -#define IM_FMTLIST(FMT) __attribute__((format(printf, FMT, 0))) -#else -#define IM_FMTARGS(FMT) -#define IM_FMTLIST(FMT) -#endif - -// Disable some of MSVC most aggressive Debug runtime checks in function header/footer (used in some simple/low-level functions) -#if defined(_MSC_VER) && !defined(__clang__) && !defined(__INTEL_COMPILER) && !defined(IMGUI_DEBUG_PARANOID) -#define IM_MSVC_RUNTIME_CHECKS_OFF __pragma(runtime_checks("",off)) __pragma(check_stack(off)) __pragma(strict_gs_check(push,off)) -#define IM_MSVC_RUNTIME_CHECKS_RESTORE __pragma(runtime_checks("",restore)) __pragma(check_stack()) __pragma(strict_gs_check(pop)) -#else -#define IM_MSVC_RUNTIME_CHECKS_OFF -#define IM_MSVC_RUNTIME_CHECKS_RESTORE -#endif - -// Warnings -#ifdef _MSC_VER -#pragma warning (push) -#pragma warning (disable: 26495) // [Static Analyzer] Variable 'XXX' is uninitialized. Always initialize a member variable (type.6). -#endif -#if defined(__clang__) -#pragma clang diagnostic push -#if __has_warning("-Wunknown-warning-option") -#pragma clang diagnostic ignored "-Wunknown-warning-option" // warning: unknown warning group 'xxx' -#endif -#pragma clang diagnostic ignored "-Wunknown-pragmas" // warning: unknown warning group 'xxx' -#pragma clang diagnostic ignored "-Wold-style-cast" -#pragma clang diagnostic ignored "-Wzero-as-null-pointer-constant" -#pragma clang diagnostic ignored "-Wreserved-identifier" // warning: identifier '_Xxx' is reserved because it starts with '_' followed by a capital letter -#elif defined(__GNUC__) -#pragma GCC diagnostic push -#pragma GCC diagnostic ignored "-Wpragmas" // warning: unknown option after '#pragma GCC diagnostic' kind -#pragma GCC diagnostic ignored "-Wclass-memaccess" // [__GNUC__ >= 8] warning: 'memset/memcpy' clearing/writing an object of type 'xxxx' with no trivial copy-assignment; use assignment or value-initialization instead -#endif - -//----------------------------------------------------------------------------- -// [SECTION] Forward declarations and basic types -//----------------------------------------------------------------------------- - -// Forward declarations -struct ImDrawChannel; // Temporary storage to output draw commands out of order, used by ImDrawListSplitter and ImDrawList::ChannelsSplit() -struct ImDrawCmd; // A single draw command within a parent ImDrawList (generally maps to 1 GPU draw call, unless it is a callback) -struct ImDrawData; // All draw command lists required to render the frame + pos/size coordinates to use for the projection matrix. -struct ImDrawList; // A single draw command list (generally one per window, conceptually you may see this as a dynamic "mesh" builder) -struct ImDrawListSharedData; // Data shared among multiple draw lists (typically owned by parent ImGui context, but you may create one yourself) -struct ImDrawListSplitter; // Helper to split a draw list into different layers which can be drawn into out of order, then flattened back. -struct ImDrawVert; // A single vertex (pos + uv + col = 20 bytes by default. Override layout with IMGUI_OVERRIDE_DRAWVERT_STRUCT_LAYOUT) -struct ImFont; // Runtime data for a single font within a parent ImFontAtlas -struct ImFontAtlas; // Runtime data for multiple fonts, bake multiple fonts into a single texture, TTF/OTF font loader -struct ImFontBuilderIO; // Opaque interface to a font builder (stb_truetype or FreeType). -struct ImFontConfig; // Configuration data when adding a font or merging fonts -struct ImFontGlyph; // A single font glyph (code point + coordinates within in ImFontAtlas + offset) -struct ImFontGlyphRangesBuilder; // Helper to build glyph ranges from text/string data -struct ImColor; // Helper functions to create a color that can be converted to either u32 or float4 (*OBSOLETE* please avoid using) -struct ImGuiContext; // Dear ImGui context (opaque structure, unless including imgui_internal.h) -struct ImGuiIO; // Main configuration and I/O between your application and ImGui -struct ImGuiInputTextCallbackData; // Shared state of InputText() when using custom ImGuiInputTextCallback (rare/advanced use) -struct ImGuiKeyData; // Storage for ImGuiIO and IsKeyDown(), IsKeyPressed() etc functions. -struct ImGuiListClipper; // Helper to manually clip large list of items -struct ImGuiOnceUponAFrame; // Helper for running a block of code not more than once a frame -struct ImGuiPayload; // User data payload for drag and drop operations -struct ImGuiPlatformIO; // Multi-viewport support: interface for Platform/Renderer backends + viewports to render -struct ImGuiPlatformMonitor; // Multi-viewport support: user-provided bounds for each connected monitor/display. Used when positioning popups and tooltips to avoid them straddling monitors -struct ImGuiPlatformImeData; // Platform IME data for io.SetPlatformImeDataFn() function. -struct ImGuiSizeCallbackData; // Callback data when using SetNextWindowSizeConstraints() (rare/advanced use) -struct ImGuiStorage; // Helper for key->value storage -struct ImGuiStyle; // Runtime data for styling/colors -struct ImGuiTableSortSpecs; // Sorting specifications for a table (often handling sort specs for a single column, occasionally more) -struct ImGuiTableColumnSortSpecs; // Sorting specification for one column of a table -struct ImGuiTextBuffer; // Helper to hold and append into a text buffer (~string builder) -struct ImGuiTextFilter; // Helper to parse and apply text filters (e.g. "aaaaa[,bbbbb][,ccccc]") -struct ImGuiViewport; // A Platform Window (always 1 unless multi-viewport are enabled. One per platform window to output to). In the future may represent Platform Monitor -struct ImGuiWindowClass; // Window class (rare/advanced uses: provide hints to the platform backend via altered viewport flags and parent/child info) - -// Enumerations -// - We don't use strongly typed enums much because they add constraints (can't extend in private code, can't store typed in bit fields, extra casting on iteration) -// - Tip: Use your programming IDE navigation facilities on the names in the _central column_ below to find the actual flags/enum lists! -// In Visual Studio IDE: CTRL+comma ("Edit.GoToAll") can follow symbols in comments, whereas CTRL+F12 ("Edit.GoToImplementation") cannot. -// With Visual Assist installed: ALT+G ("VAssistX.GoToImplementation") can also follow symbols in comments. -enum ImGuiKey : int; // -> enum ImGuiKey // Enum: A key identifier (ImGuiKey_XXX or ImGuiMod_XXX value) -enum ImGuiMouseSource : int; // -> enum ImGuiMouseSource // Enum; A mouse input source identifier (Mouse, TouchScreen, Pen) -typedef int ImGuiCol; // -> enum ImGuiCol_ // Enum: A color identifier for styling -typedef int ImGuiCond; // -> enum ImGuiCond_ // Enum: A condition for many Set*() functions -typedef int ImGuiDataType; // -> enum ImGuiDataType_ // Enum: A primary data type -typedef int ImGuiDir; // -> enum ImGuiDir_ // Enum: A cardinal direction -typedef int ImGuiMouseButton; // -> enum ImGuiMouseButton_ // Enum: A mouse button identifier (0=left, 1=right, 2=middle) -typedef int ImGuiMouseCursor; // -> enum ImGuiMouseCursor_ // Enum: A mouse cursor shape -typedef int ImGuiSortDirection; // -> enum ImGuiSortDirection_ // Enum: A sorting direction (ascending or descending) -typedef int ImGuiStyleVar; // -> enum ImGuiStyleVar_ // Enum: A variable identifier for styling -typedef int ImGuiTableBgTarget; // -> enum ImGuiTableBgTarget_ // Enum: A color target for TableSetBgColor() - -// Flags (declared as int for compatibility with old C++, to allow using as flags without overhead, and to not pollute the top of this file) -// - Tip: Use your programming IDE navigation facilities on the names in the _central column_ below to find the actual flags/enum lists! -// In Visual Studio IDE: CTRL+comma ("Edit.GoToAll") can follow symbols in comments, whereas CTRL+F12 ("Edit.GoToImplementation") cannot. -// With Visual Assist installed: ALT+G ("VAssistX.GoToImplementation") can also follow symbols in comments. -typedef int ImDrawFlags; // -> enum ImDrawFlags_ // Flags: for ImDrawList functions -typedef int ImDrawListFlags; // -> enum ImDrawListFlags_ // Flags: for ImDrawList instance -typedef int ImFontAtlasFlags; // -> enum ImFontAtlasFlags_ // Flags: for ImFontAtlas build -typedef int ImGuiBackendFlags; // -> enum ImGuiBackendFlags_ // Flags: for io.BackendFlags -typedef int ImGuiButtonFlags; // -> enum ImGuiButtonFlags_ // Flags: for InvisibleButton() -typedef int ImGuiColorEditFlags; // -> enum ImGuiColorEditFlags_ // Flags: for ColorEdit4(), ColorPicker4() etc. -typedef int ImGuiConfigFlags; // -> enum ImGuiConfigFlags_ // Flags: for io.ConfigFlags -typedef int ImGuiComboFlags; // -> enum ImGuiComboFlags_ // Flags: for BeginCombo() -typedef int ImGuiDockNodeFlags; // -> enum ImGuiDockNodeFlags_ // Flags: for DockSpace() -typedef int ImGuiDragDropFlags; // -> enum ImGuiDragDropFlags_ // Flags: for BeginDragDropSource(), AcceptDragDropPayload() -typedef int ImGuiFocusedFlags; // -> enum ImGuiFocusedFlags_ // Flags: for IsWindowFocused() -typedef int ImGuiHoveredFlags; // -> enum ImGuiHoveredFlags_ // Flags: for IsItemHovered(), IsWindowHovered() etc. -typedef int ImGuiInputTextFlags; // -> enum ImGuiInputTextFlags_ // Flags: for InputText(), InputTextMultiline() -typedef int ImGuiKeyChord; // -> ImGuiKey | ImGuiMod_XXX // Flags: for storage only for now: an ImGuiKey optionally OR-ed with one or more ImGuiMod_XXX values. -typedef int ImGuiPopupFlags; // -> enum ImGuiPopupFlags_ // Flags: for OpenPopup*(), BeginPopupContext*(), IsPopupOpen() -typedef int ImGuiSelectableFlags; // -> enum ImGuiSelectableFlags_ // Flags: for Selectable() -typedef int ImGuiSliderFlags; // -> enum ImGuiSliderFlags_ // Flags: for DragFloat(), DragInt(), SliderFloat(), SliderInt() etc. -typedef int ImGuiTabBarFlags; // -> enum ImGuiTabBarFlags_ // Flags: for BeginTabBar() -typedef int ImGuiTabItemFlags; // -> enum ImGuiTabItemFlags_ // Flags: for BeginTabItem() -typedef int ImGuiTableFlags; // -> enum ImGuiTableFlags_ // Flags: For BeginTable() -typedef int ImGuiTableColumnFlags; // -> enum ImGuiTableColumnFlags_// Flags: For TableSetupColumn() -typedef int ImGuiTableRowFlags; // -> enum ImGuiTableRowFlags_ // Flags: For TableNextRow() -typedef int ImGuiTreeNodeFlags; // -> enum ImGuiTreeNodeFlags_ // Flags: for TreeNode(), TreeNodeEx(), CollapsingHeader() -typedef int ImGuiViewportFlags; // -> enum ImGuiViewportFlags_ // Flags: for ImGuiViewport -typedef int ImGuiWindowFlags; // -> enum ImGuiWindowFlags_ // Flags: for Begin(), BeginChild() - -// ImTexture: user data for renderer backend to identify a texture [Compile-time configurable type] -// - To use something else than an opaque void* pointer: override with e.g. '#define ImTextureID MyTextureType*' in your imconfig.h file. -// - This can be whatever to you want it to be! read the FAQ about ImTextureID for details. -#ifndef ImTextureID -typedef void* ImTextureID; // Default: store a pointer or an integer fitting in a pointer (most renderer backends are ok with that) -#endif - -// ImDrawIdx: vertex index. [Compile-time configurable type] -// - To use 16-bit indices + allow large meshes: backend need to set 'io.BackendFlags |= ImGuiBackendFlags_RendererHasVtxOffset' and handle ImDrawCmd::VtxOffset (recommended). -// - To use 32-bit indices: override with '#define ImDrawIdx unsigned int' in your imconfig.h file. -#ifndef ImDrawIdx -typedef unsigned short ImDrawIdx; // Default: 16-bit (for maximum compatibility with renderer backends) -#endif - -// Scalar data types -typedef unsigned int ImGuiID;// A unique ID used by widgets (typically the result of hashing a stack of string) -typedef signed char ImS8; // 8-bit signed integer -typedef unsigned char ImU8; // 8-bit unsigned integer -typedef signed short ImS16; // 16-bit signed integer -typedef unsigned short ImU16; // 16-bit unsigned integer -typedef signed int ImS32; // 32-bit signed integer == int -typedef unsigned int ImU32; // 32-bit unsigned integer (often used to store packed colors) -typedef signed long long ImS64; // 64-bit signed integer -typedef unsigned long long ImU64; // 64-bit unsigned integer - -// Character types -// (we generally use UTF-8 encoded string in the API. This is storage specifically for a decoded character used for keyboard input and display) -typedef unsigned int ImWchar32; // A single decoded U32 character/code point. We encode them as multi bytes UTF-8 when used in strings. -typedef unsigned short ImWchar16; // A single decoded U16 character/code point. We encode them as multi bytes UTF-8 when used in strings. -#ifdef IMGUI_USE_WCHAR32 // ImWchar [configurable type: override in imconfig.h with '#define IMGUI_USE_WCHAR32' to support Unicode planes 1-16] -typedef ImWchar32 ImWchar; -#else -typedef ImWchar16 ImWchar; -#endif - -// Callback and functions types -typedef int (*ImGuiInputTextCallback)(ImGuiInputTextCallbackData* data); // Callback function for ImGui::InputText() -typedef void (*ImGuiSizeCallback)(ImGuiSizeCallbackData* data); // Callback function for ImGui::SetNextWindowSizeConstraints() -typedef void* (*ImGuiMemAllocFunc)(size_t sz, void* user_data); // Function signature for ImGui::SetAllocatorFunctions() -typedef void (*ImGuiMemFreeFunc)(void* ptr, void* user_data); // Function signature for ImGui::SetAllocatorFunctions() - -// ImVec2: 2D vector used to store positions, sizes etc. [Compile-time configurable type] -// This is a frequently used type in the API. Consider using IM_VEC2_CLASS_EXTRA to create implicit cast from/to our preferred type. -IM_MSVC_RUNTIME_CHECKS_OFF -struct ImVec2 -{ - float x, y; - constexpr ImVec2() : x(0.0f), y(0.0f) { } - constexpr ImVec2(float _x, float _y) : x(_x), y(_y) { } - float& operator[] (size_t idx) { IM_ASSERT(idx == 0 || idx == 1); return ((float*)(void*)(char*)this)[idx]; } // We very rarely use this [] operator, so the assert overhead is fine. - float operator[] (size_t idx) const { IM_ASSERT(idx == 0 || idx == 1); return ((const float*)(const void*)(const char*)this)[idx]; } -#ifdef IM_VEC2_CLASS_EXTRA - IM_VEC2_CLASS_EXTRA // Define additional constructors and implicit cast operators in imconfig.h to convert back and forth between your math types and ImVec2. -#endif -}; - -// ImVec4: 4D vector used to store clipping rectangles, colors etc. [Compile-time configurable type] -struct ImVec4 -{ - float x, y, z, w; - constexpr ImVec4() : x(0.0f), y(0.0f), z(0.0f), w(0.0f) { } - constexpr ImVec4(float _x, float _y, float _z, float _w) : x(_x), y(_y), z(_z), w(_w) { } -#ifdef IM_VEC4_CLASS_EXTRA - IM_VEC4_CLASS_EXTRA // Define additional constructors and implicit cast operators in imconfig.h to convert back and forth between your math types and ImVec4. -#endif -}; -IM_MSVC_RUNTIME_CHECKS_RESTORE - -//----------------------------------------------------------------------------- -// [SECTION] Dear ImGui end-user API functions -// (Note that ImGui:: being a namespace, you can add extra ImGui:: functions in your own separate file. Please don't modify imgui source files!) -//----------------------------------------------------------------------------- - -namespace ImGui -{ - // Context creation and access - // - Each context create its own ImFontAtlas by default. You may instance one yourself and pass it to CreateContext() to share a font atlas between contexts. - // - DLL users: heaps and globals are not shared across DLL boundaries! You will need to call SetCurrentContext() + SetAllocatorFunctions() - // for each static/DLL boundary you are calling from. Read "Context and Memory Allocators" section of imgui.cpp for details. - IMGUI_API ImGuiContext* CreateContext(ImFontAtlas* shared_font_atlas = NULL); - IMGUI_API void DestroyContext(ImGuiContext* ctx = NULL); // NULL = destroy current context - IMGUI_API ImGuiContext* GetCurrentContext(); - IMGUI_API void SetCurrentContext(ImGuiContext* ctx); - - // Main - IMGUI_API ImGuiIO& GetIO(); // access the IO structure (mouse/keyboard/gamepad inputs, time, various configuration options/flags) - IMGUI_API ImGuiStyle& GetStyle(); // access the Style structure (colors, sizes). Always use PushStyleCol(), PushStyleVar() to modify style mid-frame! - IMGUI_API void NewFrame(); // start a new Dear ImGui frame, you can submit any command from this point until Render()/EndFrame(). - IMGUI_API void EndFrame(); // ends the Dear ImGui frame. automatically called by Render(). If you don't need to render data (skipping rendering) you may call EndFrame() without Render()... but you'll have wasted CPU already! If you don't need to render, better to not create any windows and not call NewFrame() at all! - IMGUI_API void Render(); // ends the Dear ImGui frame, finalize the draw data. You can then get call GetDrawData(). - IMGUI_API ImDrawData* GetDrawData(); // valid after Render() and until the next call to NewFrame(). this is what you have to render. - - // Demo, Debug, Information - IMGUI_API void ShowDemoWindow(bool* p_open = NULL); // create Demo window. demonstrate most ImGui features. call this to learn about the library! try to make it always available in your application! - IMGUI_API void ShowMetricsWindow(bool* p_open = NULL); // create Metrics/Debugger window. display Dear ImGui internals: windows, draw commands, various internal state, etc. - IMGUI_API void ShowDebugLogWindow(bool* p_open = NULL); // create Debug Log window. display a simplified log of important dear imgui events. - IMGUI_API void ShowIDStackToolWindow(bool* p_open = NULL); // create Stack Tool window. hover items with mouse to query information about the source of their unique ID. - IMGUI_API void ShowAboutWindow(bool* p_open = NULL); // create About window. display Dear ImGui version, credits and build/system information. - IMGUI_API void ShowStyleEditor(ImGuiStyle* ref = NULL); // add style editor block (not a window). you can pass in a reference ImGuiStyle structure to compare to, revert to and save to (else it uses the default style) - IMGUI_API bool ShowStyleSelector(const char* label); // add style selector block (not a window), essentially a combo listing the default styles. - IMGUI_API void ShowFontSelector(const char* label); // add font selector block (not a window), essentially a combo listing the loaded fonts. - IMGUI_API void ShowUserGuide(); // add basic help/info block (not a window): how to manipulate ImGui as an end-user (mouse/keyboard controls). - IMGUI_API const char* GetVersion(); // get the compiled version string e.g. "1.80 WIP" (essentially the value for IMGUI_VERSION from the compiled version of imgui.cpp) - - // Styles - IMGUI_API void StyleColorsDark(ImGuiStyle* dst = NULL); // new, recommended style (default) - IMGUI_API void StyleColorsLight(ImGuiStyle* dst = NULL); // best used with borders and a custom, thicker font - IMGUI_API void StyleColorsClassic(ImGuiStyle* dst = NULL); // classic imgui style - - // Windows - // - Begin() = push window to the stack and start appending to it. End() = pop window from the stack. - // - Passing 'bool* p_open != NULL' shows a window-closing widget in the upper-right corner of the window, - // which clicking will set the boolean to false when clicked. - // - You may append multiple times to the same window during the same frame by calling Begin()/End() pairs multiple times. - // Some information such as 'flags' or 'p_open' will only be considered by the first call to Begin(). - // - Begin() return false to indicate the window is collapsed or fully clipped, so you may early out and omit submitting - // anything to the window. Always call a matching End() for each Begin() call, regardless of its return value! - // [Important: due to legacy reason, this is inconsistent with most other functions such as BeginMenu/EndMenu, - // BeginPopup/EndPopup, etc. where the EndXXX call should only be called if the corresponding BeginXXX function - // returned true. Begin and BeginChild are the only odd ones out. Will be fixed in a future update.] - // - Note that the bottom of window stack always contains a window called "Debug". - IMGUI_API bool Begin(const char* name, bool* p_open = NULL, ImGuiWindowFlags flags = 0); - IMGUI_API void End(); - - // Child Windows - // - Use child windows to begin into a self-contained independent scrolling/clipping regions within a host window. Child windows can embed their own child. - // - For each independent axis of 'size': ==0.0f: use remaining host window size / >0.0f: fixed size / <0.0f: use remaining window size minus abs(size) / Each axis can use a different mode, e.g. ImVec2(0,400). - // - BeginChild() returns false to indicate the window is collapsed or fully clipped, so you may early out and omit submitting anything to the window. - // Always call a matching EndChild() for each BeginChild() call, regardless of its return value. - // [Important: due to legacy reason, this is inconsistent with most other functions such as BeginMenu/EndMenu, - // BeginPopup/EndPopup, etc. where the EndXXX call should only be called if the corresponding BeginXXX function - // returned true. Begin and BeginChild are the only odd ones out. Will be fixed in a future update.] - IMGUI_API bool BeginChild(const char* str_id, const ImVec2& size = ImVec2(0, 0), bool border = false, ImGuiWindowFlags flags = 0); - IMGUI_API bool BeginChild(ImGuiID id, const ImVec2& size = ImVec2(0, 0), bool border = false, ImGuiWindowFlags flags = 0); - IMGUI_API void EndChild(); - - // Windows Utilities - // - 'current window' = the window we are appending into while inside a Begin()/End() block. 'next window' = next window we will Begin() into. - IMGUI_API bool IsWindowAppearing(); - IMGUI_API bool IsWindowCollapsed(); - IMGUI_API bool IsWindowFocused(ImGuiFocusedFlags flags=0); // is current window focused? or its root/child, depending on flags. see flags for options. - IMGUI_API bool IsWindowHovered(ImGuiHoveredFlags flags=0); // is current window hovered (and typically: not blocked by a popup/modal)? see flags for options. NB: If you are trying to check whether your mouse should be dispatched to imgui or to your app, you should use the 'io.WantCaptureMouse' boolean for that! Please read the FAQ! - IMGUI_API ImDrawList* GetWindowDrawList(); // get draw list associated to the current window, to append your own drawing primitives - IMGUI_API float GetWindowDpiScale(); // get DPI scale currently associated to the current window's viewport. - IMGUI_API ImVec2 GetWindowPos(); // get current window position in screen space (note: it is unlikely you need to use this. Consider using current layout pos instead, GetCursorScreenPos()) - IMGUI_API ImVec2 GetWindowSize(); // get current window size (note: it is unlikely you need to use this. Consider using GetCursorScreenPos() and e.g. GetContentRegionAvail() instead) - IMGUI_API float GetWindowWidth(); // get current window width (shortcut for GetWindowSize().x) - IMGUI_API float GetWindowHeight(); // get current window height (shortcut for GetWindowSize().y) - IMGUI_API ImGuiViewport*GetWindowViewport(); // get viewport currently associated to the current window. - - // Window manipulation - // - Prefer using SetNextXXX functions (before Begin) rather that SetXXX functions (after Begin). - IMGUI_API void SetNextWindowPos(const ImVec2& pos, ImGuiCond cond = 0, const ImVec2& pivot = ImVec2(0, 0)); // set next window position. call before Begin(). use pivot=(0.5f,0.5f) to center on given point, etc. - IMGUI_API void SetNextWindowSize(const ImVec2& size, ImGuiCond cond = 0); // set next window size. set axis to 0.0f to force an auto-fit on this axis. call before Begin() - IMGUI_API void SetNextWindowSizeConstraints(const ImVec2& size_min, const ImVec2& size_max, ImGuiSizeCallback custom_callback = NULL, void* custom_callback_data = NULL); // set next window size limits. use -1,-1 on either X/Y axis to preserve the current size. Sizes will be rounded down. Use callback to apply non-trivial programmatic constraints. - IMGUI_API void SetNextWindowContentSize(const ImVec2& size); // set next window content size (~ scrollable client area, which enforce the range of scrollbars). Not including window decorations (title bar, menu bar, etc.) nor WindowPadding. set an axis to 0.0f to leave it automatic. call before Begin() - IMGUI_API void SetNextWindowCollapsed(bool collapsed, ImGuiCond cond = 0); // set next window collapsed state. call before Begin() - IMGUI_API void SetNextWindowFocus(); // set next window to be focused / top-most. call before Begin() - IMGUI_API void SetNextWindowScroll(const ImVec2& scroll); // set next window scrolling value (use < 0.0f to not affect a given axis). - IMGUI_API void SetNextWindowBgAlpha(float alpha); // set next window background color alpha. helper to easily override the Alpha component of ImGuiCol_WindowBg/ChildBg/PopupBg. you may also use ImGuiWindowFlags_NoBackground. - IMGUI_API void SetNextWindowViewport(ImGuiID viewport_id); // set next window viewport - IMGUI_API void SetWindowPos(const ImVec2& pos, ImGuiCond cond = 0); // (not recommended) set current window position - call within Begin()/End(). prefer using SetNextWindowPos(), as this may incur tearing and side-effects. - IMGUI_API void SetWindowSize(const ImVec2& size, ImGuiCond cond = 0); // (not recommended) set current window size - call within Begin()/End(). set to ImVec2(0, 0) to force an auto-fit. prefer using SetNextWindowSize(), as this may incur tearing and minor side-effects. - IMGUI_API void SetWindowCollapsed(bool collapsed, ImGuiCond cond = 0); // (not recommended) set current window collapsed state. prefer using SetNextWindowCollapsed(). - IMGUI_API void SetWindowFocus(); // (not recommended) set current window to be focused / top-most. prefer using SetNextWindowFocus(). - IMGUI_API void SetWindowFontScale(float scale); // [OBSOLETE] set font scale. Adjust IO.FontGlobalScale if you want to scale all windows. This is an old API! For correct scaling, prefer to reload font + rebuild ImFontAtlas + call style.ScaleAllSizes(). - IMGUI_API void SetWindowPos(const char* name, const ImVec2& pos, ImGuiCond cond = 0); // set named window position. - IMGUI_API void SetWindowSize(const char* name, const ImVec2& size, ImGuiCond cond = 0); // set named window size. set axis to 0.0f to force an auto-fit on this axis. - IMGUI_API void SetWindowCollapsed(const char* name, bool collapsed, ImGuiCond cond = 0); // set named window collapsed state - IMGUI_API void SetWindowFocus(const char* name); // set named window to be focused / top-most. use NULL to remove focus. - - // Content region - // - Retrieve available space from a given point. GetContentRegionAvail() is frequently useful. - // - Those functions are bound to be redesigned (they are confusing, incomplete and the Min/Max return values are in local window coordinates which increases confusion) - IMGUI_API ImVec2 GetContentRegionAvail(); // == GetContentRegionMax() - GetCursorPos() - IMGUI_API ImVec2 GetContentRegionMax(); // current content boundaries (typically window boundaries including scrolling, or current column boundaries), in windows coordinates - IMGUI_API ImVec2 GetWindowContentRegionMin(); // content boundaries min for the full window (roughly (0,0)-Scroll), in window coordinates - IMGUI_API ImVec2 GetWindowContentRegionMax(); // content boundaries max for the full window (roughly (0,0)+Size-Scroll) where Size can be overridden with SetNextWindowContentSize(), in window coordinates - - // Windows Scrolling - // - Any change of Scroll will be applied at the beginning of next frame in the first call to Begin(). - // - You may instead use SetNextWindowScroll() prior to calling Begin() to avoid this delay, as an alternative to using SetScrollX()/SetScrollY(). - IMGUI_API float GetScrollX(); // get scrolling amount [0 .. GetScrollMaxX()] - IMGUI_API float GetScrollY(); // get scrolling amount [0 .. GetScrollMaxY()] - IMGUI_API void SetScrollX(float scroll_x); // set scrolling amount [0 .. GetScrollMaxX()] - IMGUI_API void SetScrollY(float scroll_y); // set scrolling amount [0 .. GetScrollMaxY()] - IMGUI_API float GetScrollMaxX(); // get maximum scrolling amount ~~ ContentSize.x - WindowSize.x - DecorationsSize.x - IMGUI_API float GetScrollMaxY(); // get maximum scrolling amount ~~ ContentSize.y - WindowSize.y - DecorationsSize.y - IMGUI_API void SetScrollHereX(float center_x_ratio = 0.5f); // adjust scrolling amount to make current cursor position visible. center_x_ratio=0.0: left, 0.5: center, 1.0: right. When using to make a "default/current item" visible, consider using SetItemDefaultFocus() instead. - IMGUI_API void SetScrollHereY(float center_y_ratio = 0.5f); // adjust scrolling amount to make current cursor position visible. center_y_ratio=0.0: top, 0.5: center, 1.0: bottom. When using to make a "default/current item" visible, consider using SetItemDefaultFocus() instead. - IMGUI_API void SetScrollFromPosX(float local_x, float center_x_ratio = 0.5f); // adjust scrolling amount to make given position visible. Generally GetCursorStartPos() + offset to compute a valid position. - IMGUI_API void SetScrollFromPosY(float local_y, float center_y_ratio = 0.5f); // adjust scrolling amount to make given position visible. Generally GetCursorStartPos() + offset to compute a valid position. - - // Parameters stacks (shared) - IMGUI_API void PushFont(ImFont* font); // use NULL as a shortcut to push default font - IMGUI_API void PopFont(); - IMGUI_API void PushStyleColor(ImGuiCol idx, ImU32 col); // modify a style color. always use this if you modify the style after NewFrame(). - IMGUI_API void PushStyleColor(ImGuiCol idx, const ImVec4& col); - IMGUI_API void PopStyleColor(int count = 1); - IMGUI_API void PushStyleVar(ImGuiStyleVar idx, float val); // modify a style float variable. always use this if you modify the style after NewFrame(). - IMGUI_API void PushStyleVar(ImGuiStyleVar idx, const ImVec2& val); // modify a style ImVec2 variable. always use this if you modify the style after NewFrame(). - IMGUI_API void PopStyleVar(int count = 1); - IMGUI_API void PushTabStop(bool tab_stop); // == tab stop enable. Allow focusing using TAB/Shift-TAB, enabled by default but you can disable it for certain widgets - IMGUI_API void PopTabStop(); - IMGUI_API void PushButtonRepeat(bool repeat); // in 'repeat' mode, Button*() functions return repeated true in a typematic manner (using io.KeyRepeatDelay/io.KeyRepeatRate setting). Note that you can call IsItemActive() after any Button() to tell if the button is held in the current frame. - IMGUI_API void PopButtonRepeat(); - - // Parameters stacks (current window) - IMGUI_API void PushItemWidth(float item_width); // push width of items for common large "item+label" widgets. >0.0f: width in pixels, <0.0f align xx pixels to the right of window (so -FLT_MIN always align width to the right side). - IMGUI_API void PopItemWidth(); - IMGUI_API void SetNextItemWidth(float item_width); // set width of the _next_ common large "item+label" widget. >0.0f: width in pixels, <0.0f align xx pixels to the right of window (so -FLT_MIN always align width to the right side) - IMGUI_API float CalcItemWidth(); // width of item given pushed settings and current cursor position. NOT necessarily the width of last item unlike most 'Item' functions. - IMGUI_API void PushTextWrapPos(float wrap_local_pos_x = 0.0f); // push word-wrapping position for Text*() commands. < 0.0f: no wrapping; 0.0f: wrap to end of window (or column); > 0.0f: wrap at 'wrap_pos_x' position in window local space - IMGUI_API void PopTextWrapPos(); - - // Style read access - // - Use the ShowStyleEditor() function to interactively see/edit the colors. - IMGUI_API ImFont* GetFont(); // get current font - IMGUI_API float GetFontSize(); // get current font size (= height in pixels) of current font with current scale applied - IMGUI_API ImVec2 GetFontTexUvWhitePixel(); // get UV coordinate for a while pixel, useful to draw custom shapes via the ImDrawList API - IMGUI_API ImU32 GetColorU32(ImGuiCol idx, float alpha_mul = 1.0f); // retrieve given style color with style alpha applied and optional extra alpha multiplier, packed as a 32-bit value suitable for ImDrawList - IMGUI_API ImU32 GetColorU32(const ImVec4& col); // retrieve given color with style alpha applied, packed as a 32-bit value suitable for ImDrawList - IMGUI_API ImU32 GetColorU32(ImU32 col); // retrieve given color with style alpha applied, packed as a 32-bit value suitable for ImDrawList - IMGUI_API const ImVec4& GetStyleColorVec4(ImGuiCol idx); // retrieve style color as stored in ImGuiStyle structure. use to feed back into PushStyleColor(), otherwise use GetColorU32() to get style color with style alpha baked in. - - // Layout cursor positioning - // - By "cursor" we mean the current output position. - // - The typical widget behavior is to output themselves at the current cursor position, then move the cursor one line down. - // - You can call SameLine() between widgets to undo the last carriage return and output at the right of the preceding widget. - // - Attention! We currently have inconsistencies between window-local and absolute positions we will aim to fix with future API: - // - Absolute coordinate: GetCursorScreenPos(), SetCursorScreenPos(), all ImDrawList:: functions. -> this is the preferred way forward. - // - Window-local coordinates: SameLine(), GetCursorPos(), SetCursorPos(), GetCursorStartPos(), GetContentRegionMax(), GetWindowContentRegion*(), PushTextWrapPos() - // - GetCursorScreenPos() = GetCursorPos() + GetWindowPos(). GetWindowPos() is almost only ever useful to convert from window-local to absolute coordinates. - IMGUI_API ImVec2 GetCursorScreenPos(); // cursor position in absolute coordinates (prefer using this, also more useful to work with ImDrawList API). - IMGUI_API void SetCursorScreenPos(const ImVec2& pos); // cursor position in absolute coordinates - IMGUI_API ImVec2 GetCursorPos(); // [window-local] cursor position in window coordinates (relative to window position) - IMGUI_API float GetCursorPosX(); // [window-local] " - IMGUI_API float GetCursorPosY(); // [window-local] " - IMGUI_API void SetCursorPos(const ImVec2& local_pos); // [window-local] " - IMGUI_API void SetCursorPosX(float local_x); // [window-local] " - IMGUI_API void SetCursorPosY(float local_y); // [window-local] " - IMGUI_API ImVec2 GetCursorStartPos(); // [window-local] initial cursor position, in window coordinates - - // Other layout functions - IMGUI_API void Separator(); // separator, generally horizontal. inside a menu bar or in horizontal layout mode, this becomes a vertical separator. - IMGUI_API void SameLine(float offset_from_start_x=0.0f, float spacing=-1.0f); // call between widgets or groups to layout them horizontally. X position given in window coordinates. - IMGUI_API void NewLine(); // undo a SameLine() or force a new line when in a horizontal-layout context. - IMGUI_API void Spacing(); // add vertical spacing. - IMGUI_API void Dummy(const ImVec2& size); // add a dummy item of given size. unlike InvisibleButton(), Dummy() won't take the mouse click or be navigable into. - IMGUI_API void Indent(float indent_w = 0.0f); // move content position toward the right, by indent_w, or style.IndentSpacing if indent_w <= 0 - IMGUI_API void Unindent(float indent_w = 0.0f); // move content position back to the left, by indent_w, or style.IndentSpacing if indent_w <= 0 - IMGUI_API void BeginGroup(); // lock horizontal starting position - IMGUI_API void EndGroup(); // unlock horizontal starting position + capture the whole group bounding box into one "item" (so you can use IsItemHovered() or layout primitives such as SameLine() on whole group, etc.) - IMGUI_API void AlignTextToFramePadding(); // vertically align upcoming text baseline to FramePadding.y so that it will align properly to regularly framed items (call if you have text on a line before a framed item) - IMGUI_API float GetTextLineHeight(); // ~ FontSize - IMGUI_API float GetTextLineHeightWithSpacing(); // ~ FontSize + style.ItemSpacing.y (distance in pixels between 2 consecutive lines of text) - IMGUI_API float GetFrameHeight(); // ~ FontSize + style.FramePadding.y * 2 - IMGUI_API float GetFrameHeightWithSpacing(); // ~ FontSize + style.FramePadding.y * 2 + style.ItemSpacing.y (distance in pixels between 2 consecutive lines of framed widgets) - - // ID stack/scopes - // Read the FAQ (docs/FAQ.md or http://dearimgui.com/faq) for more details about how ID are handled in dear imgui. - // - Those questions are answered and impacted by understanding of the ID stack system: - // - "Q: Why is my widget not reacting when I click on it?" - // - "Q: How can I have widgets with an empty label?" - // - "Q: How can I have multiple widgets with the same label?" - // - Short version: ID are hashes of the entire ID stack. If you are creating widgets in a loop you most likely - // want to push a unique identifier (e.g. object pointer, loop index) to uniquely differentiate them. - // - You can also use the "Label##foobar" syntax within widget label to distinguish them from each others. - // - In this header file we use the "label"/"name" terminology to denote a string that will be displayed + used as an ID, - // whereas "str_id" denote a string that is only used as an ID and not normally displayed. - IMGUI_API void PushID(const char* str_id); // push string into the ID stack (will hash string). - IMGUI_API void PushID(const char* str_id_begin, const char* str_id_end); // push string into the ID stack (will hash string). - IMGUI_API void PushID(const void* ptr_id); // push pointer into the ID stack (will hash pointer). - IMGUI_API void PushID(int int_id); // push integer into the ID stack (will hash integer). - IMGUI_API void PopID(); // pop from the ID stack. - IMGUI_API ImGuiID GetID(const char* str_id); // calculate unique ID (hash of whole ID stack + given parameter). e.g. if you want to query into ImGuiStorage yourself - IMGUI_API ImGuiID GetID(const char* str_id_begin, const char* str_id_end); - IMGUI_API ImGuiID GetID(const void* ptr_id); - - // Widgets: Text - IMGUI_API void TextUnformatted(const char* text, const char* text_end = NULL); // raw text without formatting. Roughly equivalent to Text("%s", text) but: A) doesn't require null terminated string if 'text_end' is specified, B) it's faster, no memory copy is done, no buffer size limits, recommended for long chunks of text. - IMGUI_API void Text(const char* fmt, ...) IM_FMTARGS(1); // formatted text - IMGUI_API void TextV(const char* fmt, va_list args) IM_FMTLIST(1); - IMGUI_API void TextColored(const ImVec4& col, const char* fmt, ...) IM_FMTARGS(2); // shortcut for PushStyleColor(ImGuiCol_Text, col); Text(fmt, ...); PopStyleColor(); - IMGUI_API void TextColoredV(const ImVec4& col, const char* fmt, va_list args) IM_FMTLIST(2); - IMGUI_API void TextDisabled(const char* fmt, ...) IM_FMTARGS(1); // shortcut for PushStyleColor(ImGuiCol_Text, style.Colors[ImGuiCol_TextDisabled]); Text(fmt, ...); PopStyleColor(); - IMGUI_API void TextDisabledV(const char* fmt, va_list args) IM_FMTLIST(1); - IMGUI_API void TextWrapped(const char* fmt, ...) IM_FMTARGS(1); // shortcut for PushTextWrapPos(0.0f); Text(fmt, ...); PopTextWrapPos();. Note that this won't work on an auto-resizing window if there's no other widgets to extend the window width, yoy may need to set a size using SetNextWindowSize(). - IMGUI_API void TextWrappedV(const char* fmt, va_list args) IM_FMTLIST(1); - IMGUI_API void LabelText(const char* label, const char* fmt, ...) IM_FMTARGS(2); // display text+label aligned the same way as value+label widgets - IMGUI_API void LabelTextV(const char* label, const char* fmt, va_list args) IM_FMTLIST(2); - IMGUI_API void BulletText(const char* fmt, ...) IM_FMTARGS(1); // shortcut for Bullet()+Text() - IMGUI_API void BulletTextV(const char* fmt, va_list args) IM_FMTLIST(1); - IMGUI_API void SeparatorText(const char* label); // currently: formatted text with an horizontal line - - // Widgets: Main - // - Most widgets return true when the value has been changed or when pressed/selected - // - You may also use one of the many IsItemXXX functions (e.g. IsItemActive, IsItemHovered, etc.) to query widget state. - IMGUI_API bool Button(const char* label, const ImVec2& size = ImVec2(0, 0)); // button - IMGUI_API bool SmallButton(const char* label); // button with (FramePadding.y == 0) to easily embed within text - IMGUI_API bool InvisibleButton(const char* str_id, const ImVec2& size, ImGuiButtonFlags flags = 0); // flexible button behavior without the visuals, frequently useful to build custom behaviors using the public api (along with IsItemActive, IsItemHovered, etc.) - IMGUI_API bool ArrowButton(const char* str_id, ImGuiDir dir); // square button with an arrow shape - IMGUI_API bool Checkbox(const char* label, bool* v); - IMGUI_API bool CheckboxFlags(const char* label, int* flags, int flags_value); - IMGUI_API bool CheckboxFlags(const char* label, unsigned int* flags, unsigned int flags_value); - IMGUI_API bool RadioButton(const char* label, bool active); // use with e.g. if (RadioButton("one", my_value==1)) { my_value = 1; } - IMGUI_API bool RadioButton(const char* label, int* v, int v_button); // shortcut to handle the above pattern when value is an integer - IMGUI_API void ProgressBar(float fraction, const ImVec2& size_arg = ImVec2(-FLT_MIN, 0), const char* overlay = NULL); - IMGUI_API void Bullet(); // draw a small circle + keep the cursor on the same line. advance cursor x position by GetTreeNodeToLabelSpacing(), same distance that TreeNode() uses - - // Widgets: Images - // - Read about ImTextureID here: https://github.com/ocornut/imgui/wiki/Image-Loading-and-Displaying-Examples - // - Note that ImageButton() adds style.FramePadding*2.0f to provided size. This is in order to facilitate fitting an image in a button. - IMGUI_API void Image(ImTextureID user_texture_id, const ImVec2& size, const ImVec2& uv0 = ImVec2(0, 0), const ImVec2& uv1 = ImVec2(1, 1), const ImVec4& tint_col = ImVec4(1, 1, 1, 1), const ImVec4& border_col = ImVec4(0, 0, 0, 0)); - IMGUI_API bool ImageButton(const char* str_id, ImTextureID user_texture_id, const ImVec2& image_size, const ImVec2& uv0 = ImVec2(0, 0), const ImVec2& uv1 = ImVec2(1, 1), const ImVec4& bg_col = ImVec4(0, 0, 0, 0), const ImVec4& tint_col = ImVec4(1, 1, 1, 1)); - - // Widgets: Combo Box (Dropdown) - // - The BeginCombo()/EndCombo() api allows you to manage your contents and selection state however you want it, by creating e.g. Selectable() items. - // - The old Combo() api are helpers over BeginCombo()/EndCombo() which are kept available for convenience purpose. This is analogous to how ListBox are created. - IMGUI_API bool BeginCombo(const char* label, const char* preview_value, ImGuiComboFlags flags = 0); - IMGUI_API void EndCombo(); // only call EndCombo() if BeginCombo() returns true! - IMGUI_API bool Combo(const char* label, int* current_item, const char* const items[], int items_count, int popup_max_height_in_items = -1); - IMGUI_API bool Combo(const char* label, int* current_item, const char* items_separated_by_zeros, int popup_max_height_in_items = -1); // Separate items with \0 within a string, end item-list with \0\0. e.g. "One\0Two\0Three\0" - IMGUI_API bool Combo(const char* label, int* current_item, const char* (*getter)(void* user_data, int idx), void* user_data, int items_count, int popup_max_height_in_items = -1); - - // Widgets: Drag Sliders - // - CTRL+Click on any drag box to turn them into an input box. Manually input values aren't clamped by default and can go off-bounds. Use ImGuiSliderFlags_AlwaysClamp to always clamp. - // - For all the Float2/Float3/Float4/Int2/Int3/Int4 versions of every function, note that a 'float v[X]' function argument is the same as 'float* v', - // the array syntax is just a way to document the number of elements that are expected to be accessible. You can pass address of your first element out of a contiguous set, e.g. &myvector.x - // - Adjust format string to decorate the value with a prefix, a suffix, or adapt the editing and display precision e.g. "%.3f" -> 1.234; "%5.2f secs" -> 01.23 secs; "Biscuit: %.0f" -> Biscuit: 1; etc. - // - Format string may also be set to NULL or use the default format ("%f" or "%d"). - // - Speed are per-pixel of mouse movement (v_speed=0.2f: mouse needs to move by 5 pixels to increase value by 1). For gamepad/keyboard navigation, minimum speed is Max(v_speed, minimum_step_at_given_precision). - // - Use v_min < v_max to clamp edits to given limits. Note that CTRL+Click manual input can override those limits if ImGuiSliderFlags_AlwaysClamp is not used. - // - Use v_max = FLT_MAX / INT_MAX etc to avoid clamping to a maximum, same with v_min = -FLT_MAX / INT_MIN to avoid clamping to a minimum. - // - We use the same sets of flags for DragXXX() and SliderXXX() functions as the features are the same and it makes it easier to swap them. - // - Legacy: Pre-1.78 there are DragXXX() function signatures that take a final `float power=1.0f' argument instead of the `ImGuiSliderFlags flags=0' argument. - // If you get a warning converting a float to ImGuiSliderFlags, read https://github.com/ocornut/imgui/issues/3361 - IMGUI_API bool DragFloat(const char* label, float* v, float v_speed = 1.0f, float v_min = 0.0f, float v_max = 0.0f, const char* format = "%.3f", ImGuiSliderFlags flags = 0); // If v_min >= v_max we have no bound - IMGUI_API bool DragFloat2(const char* label, float v[2], float v_speed = 1.0f, float v_min = 0.0f, float v_max = 0.0f, const char* format = "%.3f", ImGuiSliderFlags flags = 0); - IMGUI_API bool DragFloat3(const char* label, float v[3], float v_speed = 1.0f, float v_min = 0.0f, float v_max = 0.0f, const char* format = "%.3f", ImGuiSliderFlags flags = 0); - IMGUI_API bool DragFloat4(const char* label, float v[4], float v_speed = 1.0f, float v_min = 0.0f, float v_max = 0.0f, const char* format = "%.3f", ImGuiSliderFlags flags = 0); - IMGUI_API bool DragFloatRange2(const char* label, float* v_current_min, float* v_current_max, float v_speed = 1.0f, float v_min = 0.0f, float v_max = 0.0f, const char* format = "%.3f", const char* format_max = NULL, ImGuiSliderFlags flags = 0); - IMGUI_API bool DragInt(const char* label, int* v, float v_speed = 1.0f, int v_min = 0, int v_max = 0, const char* format = "%d", ImGuiSliderFlags flags = 0); // If v_min >= v_max we have no bound - IMGUI_API bool DragInt2(const char* label, int v[2], float v_speed = 1.0f, int v_min = 0, int v_max = 0, const char* format = "%d", ImGuiSliderFlags flags = 0); - IMGUI_API bool DragInt3(const char* label, int v[3], float v_speed = 1.0f, int v_min = 0, int v_max = 0, const char* format = "%d", ImGuiSliderFlags flags = 0); - IMGUI_API bool DragInt4(const char* label, int v[4], float v_speed = 1.0f, int v_min = 0, int v_max = 0, const char* format = "%d", ImGuiSliderFlags flags = 0); - IMGUI_API bool DragIntRange2(const char* label, int* v_current_min, int* v_current_max, float v_speed = 1.0f, int v_min = 0, int v_max = 0, const char* format = "%d", const char* format_max = NULL, ImGuiSliderFlags flags = 0); - IMGUI_API bool DragScalar(const char* label, ImGuiDataType data_type, void* p_data, float v_speed = 1.0f, const void* p_min = NULL, const void* p_max = NULL, const char* format = NULL, ImGuiSliderFlags flags = 0); - IMGUI_API bool DragScalarN(const char* label, ImGuiDataType data_type, void* p_data, int components, float v_speed = 1.0f, const void* p_min = NULL, const void* p_max = NULL, const char* format = NULL, ImGuiSliderFlags flags = 0); - - // Widgets: Regular Sliders - // - CTRL+Click on any slider to turn them into an input box. Manually input values aren't clamped by default and can go off-bounds. Use ImGuiSliderFlags_AlwaysClamp to always clamp. - // - Adjust format string to decorate the value with a prefix, a suffix, or adapt the editing and display precision e.g. "%.3f" -> 1.234; "%5.2f secs" -> 01.23 secs; "Biscuit: %.0f" -> Biscuit: 1; etc. - // - Format string may also be set to NULL or use the default format ("%f" or "%d"). - // - Legacy: Pre-1.78 there are SliderXXX() function signatures that take a final `float power=1.0f' argument instead of the `ImGuiSliderFlags flags=0' argument. - // If you get a warning converting a float to ImGuiSliderFlags, read https://github.com/ocornut/imgui/issues/3361 - IMGUI_API bool SliderFloat(const char* label, float* v, float v_min, float v_max, const char* format = "%.3f", ImGuiSliderFlags flags = 0); // adjust format to decorate the value with a prefix or a suffix for in-slider labels or unit display. - IMGUI_API bool SliderFloat2(const char* label, float v[2], float v_min, float v_max, const char* format = "%.3f", ImGuiSliderFlags flags = 0); - IMGUI_API bool SliderFloat3(const char* label, float v[3], float v_min, float v_max, const char* format = "%.3f", ImGuiSliderFlags flags = 0); - IMGUI_API bool SliderFloat4(const char* label, float v[4], float v_min, float v_max, const char* format = "%.3f", ImGuiSliderFlags flags = 0); - IMGUI_API bool SliderAngle(const char* label, float* v_rad, float v_degrees_min = -360.0f, float v_degrees_max = +360.0f, const char* format = "%.0f deg", ImGuiSliderFlags flags = 0); - IMGUI_API bool SliderInt(const char* label, int* v, int v_min, int v_max, const char* format = "%d", ImGuiSliderFlags flags = 0); - IMGUI_API bool SliderInt2(const char* label, int v[2], int v_min, int v_max, const char* format = "%d", ImGuiSliderFlags flags = 0); - IMGUI_API bool SliderInt3(const char* label, int v[3], int v_min, int v_max, const char* format = "%d", ImGuiSliderFlags flags = 0); - IMGUI_API bool SliderInt4(const char* label, int v[4], int v_min, int v_max, const char* format = "%d", ImGuiSliderFlags flags = 0); - IMGUI_API bool SliderScalar(const char* label, ImGuiDataType data_type, void* p_data, const void* p_min, const void* p_max, const char* format = NULL, ImGuiSliderFlags flags = 0); - IMGUI_API bool SliderScalarN(const char* label, ImGuiDataType data_type, void* p_data, int components, const void* p_min, const void* p_max, const char* format = NULL, ImGuiSliderFlags flags = 0); - IMGUI_API bool VSliderFloat(const char* label, const ImVec2& size, float* v, float v_min, float v_max, const char* format = "%.3f", ImGuiSliderFlags flags = 0); - IMGUI_API bool VSliderInt(const char* label, const ImVec2& size, int* v, int v_min, int v_max, const char* format = "%d", ImGuiSliderFlags flags = 0); - IMGUI_API bool VSliderScalar(const char* label, const ImVec2& size, ImGuiDataType data_type, void* p_data, const void* p_min, const void* p_max, const char* format = NULL, ImGuiSliderFlags flags = 0); - - // Widgets: Input with Keyboard - // - If you want to use InputText() with std::string or any custom dynamic string type, see misc/cpp/imgui_stdlib.h and comments in imgui_demo.cpp. - // - Most of the ImGuiInputTextFlags flags are only useful for InputText() and not for InputFloatX, InputIntX, InputDouble etc. - IMGUI_API bool InputText(const char* label, char* buf, size_t buf_size, ImGuiInputTextFlags flags = 0, ImGuiInputTextCallback callback = NULL, void* user_data = NULL); - IMGUI_API bool InputTextMultiline(const char* label, char* buf, size_t buf_size, const ImVec2& size = ImVec2(0, 0), ImGuiInputTextFlags flags = 0, ImGuiInputTextCallback callback = NULL, void* user_data = NULL); - IMGUI_API bool InputTextWithHint(const char* label, const char* hint, char* buf, size_t buf_size, ImGuiInputTextFlags flags = 0, ImGuiInputTextCallback callback = NULL, void* user_data = NULL); - IMGUI_API bool InputFloat(const char* label, float* v, float step = 0.0f, float step_fast = 0.0f, const char* format = "%.3f", ImGuiInputTextFlags flags = 0); - IMGUI_API bool InputFloat2(const char* label, float v[2], const char* format = "%.3f", ImGuiInputTextFlags flags = 0); - IMGUI_API bool InputFloat3(const char* label, float v[3], const char* format = "%.3f", ImGuiInputTextFlags flags = 0); - IMGUI_API bool InputFloat4(const char* label, float v[4], const char* format = "%.3f", ImGuiInputTextFlags flags = 0); - IMGUI_API bool InputInt(const char* label, int* v, int step = 1, int step_fast = 100, ImGuiInputTextFlags flags = 0); - IMGUI_API bool InputInt2(const char* label, int v[2], ImGuiInputTextFlags flags = 0); - IMGUI_API bool InputInt3(const char* label, int v[3], ImGuiInputTextFlags flags = 0); - IMGUI_API bool InputInt4(const char* label, int v[4], ImGuiInputTextFlags flags = 0); - IMGUI_API bool InputDouble(const char* label, double* v, double step = 0.0, double step_fast = 0.0, const char* format = "%.6f", ImGuiInputTextFlags flags = 0); - IMGUI_API bool InputScalar(const char* label, ImGuiDataType data_type, void* p_data, const void* p_step = NULL, const void* p_step_fast = NULL, const char* format = NULL, ImGuiInputTextFlags flags = 0); - IMGUI_API bool InputScalarN(const char* label, ImGuiDataType data_type, void* p_data, int components, const void* p_step = NULL, const void* p_step_fast = NULL, const char* format = NULL, ImGuiInputTextFlags flags = 0); - - // Widgets: Color Editor/Picker (tip: the ColorEdit* functions have a little color square that can be left-clicked to open a picker, and right-clicked to open an option menu.) - // - Note that in C++ a 'float v[X]' function argument is the _same_ as 'float* v', the array syntax is just a way to document the number of elements that are expected to be accessible. - // - You can pass the address of a first float element out of a contiguous structure, e.g. &myvector.x - IMGUI_API bool ColorEdit3(const char* label, float col[3], ImGuiColorEditFlags flags = 0); - IMGUI_API bool ColorEdit4(const char* label, float col[4], ImGuiColorEditFlags flags = 0); - IMGUI_API bool ColorPicker3(const char* label, float col[3], ImGuiColorEditFlags flags = 0); - IMGUI_API bool ColorPicker4(const char* label, float col[4], ImGuiColorEditFlags flags = 0, const float* ref_col = NULL); - IMGUI_API bool ColorButton(const char* desc_id, const ImVec4& col, ImGuiColorEditFlags flags = 0, const ImVec2& size = ImVec2(0, 0)); // display a color square/button, hover for details, return true when pressed. - IMGUI_API void SetColorEditOptions(ImGuiColorEditFlags flags); // initialize current options (generally on application startup) if you want to select a default format, picker type, etc. User will be able to change many settings, unless you pass the _NoOptions flag to your calls. - - // Widgets: Trees - // - TreeNode functions return true when the node is open, in which case you need to also call TreePop() when you are finished displaying the tree node contents. - IMGUI_API bool TreeNode(const char* label); - IMGUI_API bool TreeNode(const char* str_id, const char* fmt, ...) IM_FMTARGS(2); // helper variation to easily decorelate the id from the displayed string. Read the FAQ about why and how to use ID. to align arbitrary text at the same level as a TreeNode() you can use Bullet(). - IMGUI_API bool TreeNode(const void* ptr_id, const char* fmt, ...) IM_FMTARGS(2); // " - IMGUI_API bool TreeNodeV(const char* str_id, const char* fmt, va_list args) IM_FMTLIST(2); - IMGUI_API bool TreeNodeV(const void* ptr_id, const char* fmt, va_list args) IM_FMTLIST(2); - IMGUI_API bool TreeNodeEx(const char* label, ImGuiTreeNodeFlags flags = 0); - IMGUI_API bool TreeNodeEx(const char* str_id, ImGuiTreeNodeFlags flags, const char* fmt, ...) IM_FMTARGS(3); - IMGUI_API bool TreeNodeEx(const void* ptr_id, ImGuiTreeNodeFlags flags, const char* fmt, ...) IM_FMTARGS(3); - IMGUI_API bool TreeNodeExV(const char* str_id, ImGuiTreeNodeFlags flags, const char* fmt, va_list args) IM_FMTLIST(3); - IMGUI_API bool TreeNodeExV(const void* ptr_id, ImGuiTreeNodeFlags flags, const char* fmt, va_list args) IM_FMTLIST(3); - IMGUI_API void TreePush(const char* str_id); // ~ Indent()+PushId(). Already called by TreeNode() when returning true, but you can call TreePush/TreePop yourself if desired. - IMGUI_API void TreePush(const void* ptr_id); // " - IMGUI_API void TreePop(); // ~ Unindent()+PopId() - IMGUI_API float GetTreeNodeToLabelSpacing(); // horizontal distance preceding label when using TreeNode*() or Bullet() == (g.FontSize + style.FramePadding.x*2) for a regular unframed TreeNode - IMGUI_API bool CollapsingHeader(const char* label, ImGuiTreeNodeFlags flags = 0); // if returning 'true' the header is open. doesn't indent nor push on ID stack. user doesn't have to call TreePop(). - IMGUI_API bool CollapsingHeader(const char* label, bool* p_visible, ImGuiTreeNodeFlags flags = 0); // when 'p_visible != NULL': if '*p_visible==true' display an additional small close button on upper right of the header which will set the bool to false when clicked, if '*p_visible==false' don't display the header. - IMGUI_API void SetNextItemOpen(bool is_open, ImGuiCond cond = 0); // set next TreeNode/CollapsingHeader open state. - - // Widgets: Selectables - // - A selectable highlights when hovered, and can display another color when selected. - // - Neighbors selectable extend their highlight bounds in order to leave no gap between them. This is so a series of selected Selectable appear contiguous. - IMGUI_API bool Selectable(const char* label, bool selected = false, ImGuiSelectableFlags flags = 0, const ImVec2& size = ImVec2(0, 0)); // "bool selected" carry the selection state (read-only). Selectable() is clicked is returns true so you can modify your selection state. size.x==0.0: use remaining width, size.x>0.0: specify width. size.y==0.0: use label height, size.y>0.0: specify height - IMGUI_API bool Selectable(const char* label, bool* p_selected, ImGuiSelectableFlags flags = 0, const ImVec2& size = ImVec2(0, 0)); // "bool* p_selected" point to the selection state (read-write), as a convenient helper. - - // Widgets: List Boxes - // - This is essentially a thin wrapper to using BeginChild/EndChild with some stylistic changes. - // - The BeginListBox()/EndListBox() api allows you to manage your contents and selection state however you want it, by creating e.g. Selectable() or any items. - // - The simplified/old ListBox() api are helpers over BeginListBox()/EndListBox() which are kept available for convenience purpose. This is analoguous to how Combos are created. - // - Choose frame width: size.x > 0.0f: custom / size.x < 0.0f or -FLT_MIN: right-align / size.x = 0.0f (default): use current ItemWidth - // - Choose frame height: size.y > 0.0f: custom / size.y < 0.0f or -FLT_MIN: bottom-align / size.y = 0.0f (default): arbitrary default height which can fit ~7 items - IMGUI_API bool BeginListBox(const char* label, const ImVec2& size = ImVec2(0, 0)); // open a framed scrolling region - IMGUI_API void EndListBox(); // only call EndListBox() if BeginListBox() returned true! - IMGUI_API bool ListBox(const char* label, int* current_item, const char* const items[], int items_count, int height_in_items = -1); - IMGUI_API bool ListBox(const char* label, int* current_item, const char* (*getter)(void* user_data, int idx), void* user_data, int items_count, int height_in_items = -1); - - // Widgets: Data Plotting - // - Consider using ImPlot (https://github.com/epezent/implot) which is much better! - IMGUI_API void PlotLines(const char* label, const float* values, int values_count, int values_offset = 0, const char* overlay_text = NULL, float scale_min = FLT_MAX, float scale_max = FLT_MAX, ImVec2 graph_size = ImVec2(0, 0), int stride = sizeof(float)); - IMGUI_API void PlotLines(const char* label, float(*values_getter)(void* data, int idx), void* data, int values_count, int values_offset = 0, const char* overlay_text = NULL, float scale_min = FLT_MAX, float scale_max = FLT_MAX, ImVec2 graph_size = ImVec2(0, 0)); - IMGUI_API void PlotHistogram(const char* label, const float* values, int values_count, int values_offset = 0, const char* overlay_text = NULL, float scale_min = FLT_MAX, float scale_max = FLT_MAX, ImVec2 graph_size = ImVec2(0, 0), int stride = sizeof(float)); - IMGUI_API void PlotHistogram(const char* label, float (*values_getter)(void* data, int idx), void* data, int values_count, int values_offset = 0, const char* overlay_text = NULL, float scale_min = FLT_MAX, float scale_max = FLT_MAX, ImVec2 graph_size = ImVec2(0, 0)); - - // Widgets: Value() Helpers. - // - Those are merely shortcut to calling Text() with a format string. Output single value in "name: value" format (tip: freely declare more in your code to handle your types. you can add functions to the ImGui namespace) - IMGUI_API void Value(const char* prefix, bool b); - IMGUI_API void Value(const char* prefix, int v); - IMGUI_API void Value(const char* prefix, unsigned int v); - IMGUI_API void Value(const char* prefix, float v, const char* float_format = NULL); - - // Widgets: Menus - // - Use BeginMenuBar() on a window ImGuiWindowFlags_MenuBar to append to its menu bar. - // - Use BeginMainMenuBar() to create a menu bar at the top of the screen and append to it. - // - Use BeginMenu() to create a menu. You can call BeginMenu() multiple time with the same identifier to append more items to it. - // - Not that MenuItem() keyboardshortcuts are displayed as a convenience but _not processed_ by Dear ImGui at the moment. - IMGUI_API bool BeginMenuBar(); // append to menu-bar of current window (requires ImGuiWindowFlags_MenuBar flag set on parent window). - IMGUI_API void EndMenuBar(); // only call EndMenuBar() if BeginMenuBar() returns true! - IMGUI_API bool BeginMainMenuBar(); // create and append to a full screen menu-bar. - IMGUI_API void EndMainMenuBar(); // only call EndMainMenuBar() if BeginMainMenuBar() returns true! - IMGUI_API bool BeginMenu(const char* label, bool enabled = true); // create a sub-menu entry. only call EndMenu() if this returns true! - IMGUI_API void EndMenu(); // only call EndMenu() if BeginMenu() returns true! - IMGUI_API bool MenuItem(const char* label, const char* shortcut = NULL, bool selected = false, bool enabled = true); // return true when activated. - IMGUI_API bool MenuItem(const char* label, const char* shortcut, bool* p_selected, bool enabled = true); // return true when activated + toggle (*p_selected) if p_selected != NULL - - // Tooltips - // - Tooltips are windows following the mouse. They do not take focus away. - // - A tooltip window can contain items of any types. SetTooltip() is a shortcut for the 'if (BeginTooltip()) { Text(...); EndTooltip(); }' idiom. - IMGUI_API bool BeginTooltip(); // begin/append a tooltip window. - IMGUI_API void EndTooltip(); // only call EndTooltip() if BeginTooltip()/BeginItemTooltip() returns true! - IMGUI_API void SetTooltip(const char* fmt, ...) IM_FMTARGS(1); // set a text-only tooltip. Often used after a ImGui::IsItemHovered() check. Override any previous call to SetTooltip(). - IMGUI_API void SetTooltipV(const char* fmt, va_list args) IM_FMTLIST(1); - - // Tooltips: helpers for showing a tooltip when hovering an item - // - BeginItemTooltip() is a shortcut for the 'if (IsItemHovered(ImGuiHoveredFlags_ForTooltip) && BeginTooltip())' idiom. - // - SetItemTooltip() is a shortcut for the 'if (IsItemHovered(ImGuiHoveredFlags_ForTooltip)) { SetTooltip(...); }' idiom. - // - Where 'ImGuiHoveredFlags_ForTooltip' itself is a shortcut to use 'style.HoverFlagsForTooltipMouse' or 'style.HoverFlagsForTooltipNav' depending on active input type. For mouse it defaults to 'ImGuiHoveredFlags_Stationary | ImGuiHoveredFlags_DelayShort'. - IMGUI_API bool BeginItemTooltip(); // begin/append a tooltip window if preceding item was hovered. - IMGUI_API void SetItemTooltip(const char* fmt, ...) IM_FMTARGS(1); // set a text-only tooltip if preceeding item was hovered. override any previous call to SetTooltip(). - IMGUI_API void SetItemTooltipV(const char* fmt, va_list args) IM_FMTLIST(1); - - // Popups, Modals - // - They block normal mouse hovering detection (and therefore most mouse interactions) behind them. - // - If not modal: they can be closed by clicking anywhere outside them, or by pressing ESCAPE. - // - Their visibility state (~bool) is held internally instead of being held by the programmer as we are used to with regular Begin*() calls. - // - The 3 properties above are related: we need to retain popup visibility state in the library because popups may be closed as any time. - // - You can bypass the hovering restriction by using ImGuiHoveredFlags_AllowWhenBlockedByPopup when calling IsItemHovered() or IsWindowHovered(). - // - IMPORTANT: Popup identifiers are relative to the current ID stack, so OpenPopup and BeginPopup generally needs to be at the same level of the stack. - // This is sometimes leading to confusing mistakes. May rework this in the future. - - // Popups: begin/end functions - // - BeginPopup(): query popup state, if open start appending into the window. Call EndPopup() afterwards. ImGuiWindowFlags are forwarded to the window. - // - BeginPopupModal(): block every interaction behind the window, cannot be closed by user, add a dimming background, has a title bar. - IMGUI_API bool BeginPopup(const char* str_id, ImGuiWindowFlags flags = 0); // return true if the popup is open, and you can start outputting to it. - IMGUI_API bool BeginPopupModal(const char* name, bool* p_open = NULL, ImGuiWindowFlags flags = 0); // return true if the modal is open, and you can start outputting to it. - IMGUI_API void EndPopup(); // only call EndPopup() if BeginPopupXXX() returns true! - - // Popups: open/close functions - // - OpenPopup(): set popup state to open. ImGuiPopupFlags are available for opening options. - // - If not modal: they can be closed by clicking anywhere outside them, or by pressing ESCAPE. - // - CloseCurrentPopup(): use inside the BeginPopup()/EndPopup() scope to close manually. - // - CloseCurrentPopup() is called by default by Selectable()/MenuItem() when activated (FIXME: need some options). - // - Use ImGuiPopupFlags_NoOpenOverExistingPopup to avoid opening a popup if there's already one at the same level. This is equivalent to e.g. testing for !IsAnyPopupOpen() prior to OpenPopup(). - // - Use IsWindowAppearing() after BeginPopup() to tell if a window just opened. - // - IMPORTANT: Notice that for OpenPopupOnItemClick() we exceptionally default flags to 1 (== ImGuiPopupFlags_MouseButtonRight) for backward compatibility with older API taking 'int mouse_button = 1' parameter - IMGUI_API void OpenPopup(const char* str_id, ImGuiPopupFlags popup_flags = 0); // call to mark popup as open (don't call every frame!). - IMGUI_API void OpenPopup(ImGuiID id, ImGuiPopupFlags popup_flags = 0); // id overload to facilitate calling from nested stacks - IMGUI_API void OpenPopupOnItemClick(const char* str_id = NULL, ImGuiPopupFlags popup_flags = 1); // helper to open popup when clicked on last item. Default to ImGuiPopupFlags_MouseButtonRight == 1. (note: actually triggers on the mouse _released_ event to be consistent with popup behaviors) - IMGUI_API void CloseCurrentPopup(); // manually close the popup we have begin-ed into. - - // Popups: open+begin combined functions helpers - // - Helpers to do OpenPopup+BeginPopup where the Open action is triggered by e.g. hovering an item and right-clicking. - // - They are convenient to easily create context menus, hence the name. - // - IMPORTANT: Notice that BeginPopupContextXXX takes ImGuiPopupFlags just like OpenPopup() and unlike BeginPopup(). For full consistency, we may add ImGuiWindowFlags to the BeginPopupContextXXX functions in the future. - // - IMPORTANT: Notice that we exceptionally default their flags to 1 (== ImGuiPopupFlags_MouseButtonRight) for backward compatibility with older API taking 'int mouse_button = 1' parameter, so if you add other flags remember to re-add the ImGuiPopupFlags_MouseButtonRight. - IMGUI_API bool BeginPopupContextItem(const char* str_id = NULL, ImGuiPopupFlags popup_flags = 1); // open+begin popup when clicked on last item. Use str_id==NULL to associate the popup to previous item. If you want to use that on a non-interactive item such as Text() you need to pass in an explicit ID here. read comments in .cpp! - IMGUI_API bool BeginPopupContextWindow(const char* str_id = NULL, ImGuiPopupFlags popup_flags = 1);// open+begin popup when clicked on current window. - IMGUI_API bool BeginPopupContextVoid(const char* str_id = NULL, ImGuiPopupFlags popup_flags = 1); // open+begin popup when clicked in void (where there are no windows). - - // Popups: query functions - // - IsPopupOpen(): return true if the popup is open at the current BeginPopup() level of the popup stack. - // - IsPopupOpen() with ImGuiPopupFlags_AnyPopupId: return true if any popup is open at the current BeginPopup() level of the popup stack. - // - IsPopupOpen() with ImGuiPopupFlags_AnyPopupId + ImGuiPopupFlags_AnyPopupLevel: return true if any popup is open. - IMGUI_API bool IsPopupOpen(const char* str_id, ImGuiPopupFlags flags = 0); // return true if the popup is open. - - // Tables - // - Full-featured replacement for old Columns API. - // - See Demo->Tables for demo code. See top of imgui_tables.cpp for general commentary. - // - See ImGuiTableFlags_ and ImGuiTableColumnFlags_ enums for a description of available flags. - // The typical call flow is: - // - 1. Call BeginTable(), early out if returning false. - // - 2. Optionally call TableSetupColumn() to submit column name/flags/defaults. - // - 3. Optionally call TableSetupScrollFreeze() to request scroll freezing of columns/rows. - // - 4. Optionally call TableHeadersRow() to submit a header row. Names are pulled from TableSetupColumn() data. - // - 5. Populate contents: - // - In most situations you can use TableNextRow() + TableSetColumnIndex(N) to start appending into a column. - // - If you are using tables as a sort of grid, where every column is holding the same type of contents, - // you may prefer using TableNextColumn() instead of TableNextRow() + TableSetColumnIndex(). - // TableNextColumn() will automatically wrap-around into the next row if needed. - // - IMPORTANT: Comparatively to the old Columns() API, we need to call TableNextColumn() for the first column! - // - Summary of possible call flow: - // -------------------------------------------------------------------------------------------------------- - // TableNextRow() -> TableSetColumnIndex(0) -> Text("Hello 0") -> TableSetColumnIndex(1) -> Text("Hello 1") // OK - // TableNextRow() -> TableNextColumn() -> Text("Hello 0") -> TableNextColumn() -> Text("Hello 1") // OK - // TableNextColumn() -> Text("Hello 0") -> TableNextColumn() -> Text("Hello 1") // OK: TableNextColumn() automatically gets to next row! - // TableNextRow() -> Text("Hello 0") // Not OK! Missing TableSetColumnIndex() or TableNextColumn()! Text will not appear! - // -------------------------------------------------------------------------------------------------------- - // - 5. Call EndTable() - IMGUI_API bool BeginTable(const char* str_id, int column, ImGuiTableFlags flags = 0, const ImVec2& outer_size = ImVec2(0.0f, 0.0f), float inner_width = 0.0f); - IMGUI_API void EndTable(); // only call EndTable() if BeginTable() returns true! - IMGUI_API void TableNextRow(ImGuiTableRowFlags row_flags = 0, float min_row_height = 0.0f); // append into the first cell of a new row. - IMGUI_API bool TableNextColumn(); // append into the next column (or first column of next row if currently in last column). Return true when column is visible. - IMGUI_API bool TableSetColumnIndex(int column_n); // append into the specified column. Return true when column is visible. - - // Tables: Headers & Columns declaration - // - Use TableSetupColumn() to specify label, resizing policy, default width/weight, id, various other flags etc. - // - Use TableHeadersRow() to create a header row and automatically submit a TableHeader() for each column. - // Headers are required to perform: reordering, sorting, and opening the context menu. - // The context menu can also be made available in columns body using ImGuiTableFlags_ContextMenuInBody. - // - You may manually submit headers using TableNextRow() + TableHeader() calls, but this is only useful in - // some advanced use cases (e.g. adding custom widgets in header row). - // - Use TableSetupScrollFreeze() to lock columns/rows so they stay visible when scrolled. - IMGUI_API void TableSetupColumn(const char* label, ImGuiTableColumnFlags flags = 0, float init_width_or_weight = 0.0f, ImGuiID user_id = 0); - IMGUI_API void TableSetupScrollFreeze(int cols, int rows); // lock columns/rows so they stay visible when scrolled. - IMGUI_API void TableHeader(const char* label); // submit one header cell manually (rarely used) - IMGUI_API void TableHeadersRow(); // submit a row with headers cells based on data provided to TableSetupColumn() + submit context menu - IMGUI_API void TableAngledHeadersRow(); // submit a row with angled headers for every column with the ImGuiTableColumnFlags_AngledHeader flag. MUST BE FIRST ROW. - - // Tables: Sorting & Miscellaneous functions - // - Sorting: call TableGetSortSpecs() to retrieve latest sort specs for the table. NULL when not sorting. - // When 'sort_specs->SpecsDirty == true' you should sort your data. It will be true when sorting specs have - // changed since last call, or the first time. Make sure to set 'SpecsDirty = false' after sorting, - // else you may wastefully sort your data every frame! - // - Functions args 'int column_n' treat the default value of -1 as the same as passing the current column index. - IMGUI_API ImGuiTableSortSpecs* TableGetSortSpecs(); // get latest sort specs for the table (NULL if not sorting). Lifetime: don't hold on this pointer over multiple frames or past any subsequent call to BeginTable(). - IMGUI_API int TableGetColumnCount(); // return number of columns (value passed to BeginTable) - IMGUI_API int TableGetColumnIndex(); // return current column index. - IMGUI_API int TableGetRowIndex(); // return current row index. - IMGUI_API const char* TableGetColumnName(int column_n = -1); // return "" if column didn't have a name declared by TableSetupColumn(). Pass -1 to use current column. - IMGUI_API ImGuiTableColumnFlags TableGetColumnFlags(int column_n = -1); // return column flags so you can query their Enabled/Visible/Sorted/Hovered status flags. Pass -1 to use current column. - IMGUI_API void TableSetColumnEnabled(int column_n, bool v);// change user accessible enabled/disabled state of a column. Set to false to hide the column. User can use the context menu to change this themselves (right-click in headers, or right-click in columns body with ImGuiTableFlags_ContextMenuInBody) - IMGUI_API void TableSetBgColor(ImGuiTableBgTarget target, ImU32 color, int column_n = -1); // change the color of a cell, row, or column. See ImGuiTableBgTarget_ flags for details. - - // Legacy Columns API (prefer using Tables!) - // - You can also use SameLine(pos_x) to mimic simplified columns. - IMGUI_API void Columns(int count = 1, const char* id = NULL, bool border = true); - IMGUI_API void NextColumn(); // next column, defaults to current row or next row if the current row is finished - IMGUI_API int GetColumnIndex(); // get current column index - IMGUI_API float GetColumnWidth(int column_index = -1); // get column width (in pixels). pass -1 to use current column - IMGUI_API void SetColumnWidth(int column_index, float width); // set column width (in pixels). pass -1 to use current column - IMGUI_API float GetColumnOffset(int column_index = -1); // get position of column line (in pixels, from the left side of the contents region). pass -1 to use current column, otherwise 0..GetColumnsCount() inclusive. column 0 is typically 0.0f - IMGUI_API void SetColumnOffset(int column_index, float offset_x); // set position of column line (in pixels, from the left side of the contents region). pass -1 to use current column - IMGUI_API int GetColumnsCount(); - - // Tab Bars, Tabs - // - Note: Tabs are automatically created by the docking system (when in 'docking' branch). Use this to create tab bars/tabs yourself. - IMGUI_API bool BeginTabBar(const char* str_id, ImGuiTabBarFlags flags = 0); // create and append into a TabBar - IMGUI_API void EndTabBar(); // only call EndTabBar() if BeginTabBar() returns true! - IMGUI_API bool BeginTabItem(const char* label, bool* p_open = NULL, ImGuiTabItemFlags flags = 0); // create a Tab. Returns true if the Tab is selected. - IMGUI_API void EndTabItem(); // only call EndTabItem() if BeginTabItem() returns true! - IMGUI_API bool TabItemButton(const char* label, ImGuiTabItemFlags flags = 0); // create a Tab behaving like a button. return true when clicked. cannot be selected in the tab bar. - IMGUI_API void SetTabItemClosed(const char* tab_or_docked_window_label); // notify TabBar or Docking system of a closed tab/window ahead (useful to reduce visual flicker on reorderable tab bars). For tab-bar: call after BeginTabBar() and before Tab submissions. Otherwise call with a window name. - - // Docking - // [BETA API] Enable with io.ConfigFlags |= ImGuiConfigFlags_DockingEnable. - // Note: You can use most Docking facilities without calling any API. You DO NOT need to call DockSpace() to use Docking! - // - Drag from window title bar or their tab to dock/undock. Hold SHIFT to disable docking. - // - Drag from window menu button (upper-left button) to undock an entire node (all windows). - // - When io.ConfigDockingWithShift == true, you instead need to hold SHIFT to enable docking. - // About dockspaces: - // - Use DockSpaceOverViewport() to create an explicit dock node covering the screen or a specific viewport. - // This is often used with ImGuiDockNodeFlags_PassthruCentralNode to make it transparent. - // - Use DockSpace() to create an explicit dock node _within_ an existing window. See Docking demo for details. - // - Important: Dockspaces need to be submitted _before_ any window they can host. Submit it early in your frame! - // - Important: Dockspaces need to be kept alive if hidden, otherwise windows docked into it will be undocked. - // e.g. if you have multiple tabs with a dockspace inside each tab: submit the non-visible dockspaces with ImGuiDockNodeFlags_KeepAliveOnly. - IMGUI_API ImGuiID DockSpace(ImGuiID id, const ImVec2& size = ImVec2(0, 0), ImGuiDockNodeFlags flags = 0, const ImGuiWindowClass* window_class = NULL); - IMGUI_API ImGuiID DockSpaceOverViewport(const ImGuiViewport* viewport = NULL, ImGuiDockNodeFlags flags = 0, const ImGuiWindowClass* window_class = NULL); - IMGUI_API void SetNextWindowDockID(ImGuiID dock_id, ImGuiCond cond = 0); // set next window dock id - IMGUI_API void SetNextWindowClass(const ImGuiWindowClass* window_class); // set next window class (control docking compatibility + provide hints to platform backend via custom viewport flags and platform parent/child relationship) - IMGUI_API ImGuiID GetWindowDockID(); - IMGUI_API bool IsWindowDocked(); // is current window docked into another window? - - // Logging/Capture - // - All text output from the interface can be captured into tty/file/clipboard. By default, tree nodes are automatically opened during logging. - IMGUI_API void LogToTTY(int auto_open_depth = -1); // start logging to tty (stdout) - IMGUI_API void LogToFile(int auto_open_depth = -1, const char* filename = NULL); // start logging to file - IMGUI_API void LogToClipboard(int auto_open_depth = -1); // start logging to OS clipboard - IMGUI_API void LogFinish(); // stop logging (close file, etc.) - IMGUI_API void LogButtons(); // helper to display buttons for logging to tty/file/clipboard - IMGUI_API void LogText(const char* fmt, ...) IM_FMTARGS(1); // pass text data straight to log (without being displayed) - IMGUI_API void LogTextV(const char* fmt, va_list args) IM_FMTLIST(1); - - // Drag and Drop - // - On source items, call BeginDragDropSource(), if it returns true also call SetDragDropPayload() + EndDragDropSource(). - // - On target candidates, call BeginDragDropTarget(), if it returns true also call AcceptDragDropPayload() + EndDragDropTarget(). - // - If you stop calling BeginDragDropSource() the payload is preserved however it won't have a preview tooltip (we currently display a fallback "..." tooltip, see #1725) - // - An item can be both drag source and drop target. - IMGUI_API bool BeginDragDropSource(ImGuiDragDropFlags flags = 0); // call after submitting an item which may be dragged. when this return true, you can call SetDragDropPayload() + EndDragDropSource() - IMGUI_API bool SetDragDropPayload(const char* type, const void* data, size_t sz, ImGuiCond cond = 0); // type is a user defined string of maximum 32 characters. Strings starting with '_' are reserved for dear imgui internal types. Data is copied and held by imgui. Return true when payload has been accepted. - IMGUI_API void EndDragDropSource(); // only call EndDragDropSource() if BeginDragDropSource() returns true! - IMGUI_API bool BeginDragDropTarget(); // call after submitting an item that may receive a payload. If this returns true, you can call AcceptDragDropPayload() + EndDragDropTarget() - IMGUI_API const ImGuiPayload* AcceptDragDropPayload(const char* type, ImGuiDragDropFlags flags = 0); // accept contents of a given type. If ImGuiDragDropFlags_AcceptBeforeDelivery is set you can peek into the payload before the mouse button is released. - IMGUI_API void EndDragDropTarget(); // only call EndDragDropTarget() if BeginDragDropTarget() returns true! - IMGUI_API const ImGuiPayload* GetDragDropPayload(); // peek directly into the current payload from anywhere. returns NULL when drag and drop is finished or inactive. use ImGuiPayload::IsDataType() to test for the payload type. - - // Disabling [BETA API] - // - Disable all user interactions and dim items visuals (applying style.DisabledAlpha over current colors) - // - Those can be nested but it cannot be used to enable an already disabled section (a single BeginDisabled(true) in the stack is enough to keep everything disabled) - // - BeginDisabled(false) essentially does nothing useful but is provided to facilitate use of boolean expressions. If you can avoid calling BeginDisabled(False)/EndDisabled() best to avoid it. - IMGUI_API void BeginDisabled(bool disabled = true); - IMGUI_API void EndDisabled(); - - // Clipping - // - Mouse hovering is affected by ImGui::PushClipRect() calls, unlike direct calls to ImDrawList::PushClipRect() which are render only. - IMGUI_API void PushClipRect(const ImVec2& clip_rect_min, const ImVec2& clip_rect_max, bool intersect_with_current_clip_rect); - IMGUI_API void PopClipRect(); - - // Focus, Activation - // - Prefer using "SetItemDefaultFocus()" over "if (IsWindowAppearing()) SetScrollHereY()" when applicable to signify "this is the default item" - IMGUI_API void SetItemDefaultFocus(); // make last item the default focused item of a window. - IMGUI_API void SetKeyboardFocusHere(int offset = 0); // focus keyboard on the next widget. Use positive 'offset' to access sub components of a multiple component widget. Use -1 to access previous widget. - - // Overlapping mode - IMGUI_API void SetNextItemAllowOverlap(); // allow next item to be overlapped by a subsequent item. Useful with invisible buttons, selectable, treenode covering an area where subsequent items may need to be added. Note that both Selectable() and TreeNode() have dedicated flags doing this. - - // Item/Widgets Utilities and Query Functions - // - Most of the functions are referring to the previous Item that has been submitted. - // - See Demo Window under "Widgets->Querying Status" for an interactive visualization of most of those functions. - IMGUI_API bool IsItemHovered(ImGuiHoveredFlags flags = 0); // is the last item hovered? (and usable, aka not blocked by a popup, etc.). See ImGuiHoveredFlags for more options. - IMGUI_API bool IsItemActive(); // is the last item active? (e.g. button being held, text field being edited. This will continuously return true while holding mouse button on an item. Items that don't interact will always return false) - IMGUI_API bool IsItemFocused(); // is the last item focused for keyboard/gamepad navigation? - IMGUI_API bool IsItemClicked(ImGuiMouseButton mouse_button = 0); // is the last item hovered and mouse clicked on? (**) == IsMouseClicked(mouse_button) && IsItemHovered()Important. (**) this is NOT equivalent to the behavior of e.g. Button(). Read comments in function definition. - IMGUI_API bool IsItemVisible(); // is the last item visible? (items may be out of sight because of clipping/scrolling) - IMGUI_API bool IsItemEdited(); // did the last item modify its underlying value this frame? or was pressed? This is generally the same as the "bool" return value of many widgets. - IMGUI_API bool IsItemActivated(); // was the last item just made active (item was previously inactive). - IMGUI_API bool IsItemDeactivated(); // was the last item just made inactive (item was previously active). Useful for Undo/Redo patterns with widgets that require continuous editing. - IMGUI_API bool IsItemDeactivatedAfterEdit(); // was the last item just made inactive and made a value change when it was active? (e.g. Slider/Drag moved). Useful for Undo/Redo patterns with widgets that require continuous editing. Note that you may get false positives (some widgets such as Combo()/ListBox()/Selectable() will return true even when clicking an already selected item). - IMGUI_API bool IsItemToggledOpen(); // was the last item open state toggled? set by TreeNode(). - IMGUI_API bool IsAnyItemHovered(); // is any item hovered? - IMGUI_API bool IsAnyItemActive(); // is any item active? - IMGUI_API bool IsAnyItemFocused(); // is any item focused? - IMGUI_API ImGuiID GetItemID(); // get ID of last item (~~ often same ImGui::GetID(label) beforehand) - IMGUI_API ImVec2 GetItemRectMin(); // get upper-left bounding rectangle of the last item (screen space) - IMGUI_API ImVec2 GetItemRectMax(); // get lower-right bounding rectangle of the last item (screen space) - IMGUI_API ImVec2 GetItemRectSize(); // get size of last item - - // Viewports - // - Currently represents the Platform Window created by the application which is hosting our Dear ImGui windows. - // - In 'docking' branch with multi-viewport enabled, we extend this concept to have multiple active viewports. - // - In the future we will extend this concept further to also represent Platform Monitor and support a "no main platform window" operation mode. - IMGUI_API ImGuiViewport* GetMainViewport(); // return primary/default viewport. This can never be NULL. - - // Background/Foreground Draw Lists - IMGUI_API ImDrawList* GetBackgroundDrawList(); // get background draw list for the viewport associated to the current window. this draw list will be the first rendering one. Useful to quickly draw shapes/text behind dear imgui contents. - IMGUI_API ImDrawList* GetForegroundDrawList(); // get foreground draw list for the viewport associated to the current window. this draw list will be the last rendered one. Useful to quickly draw shapes/text over dear imgui contents. - IMGUI_API ImDrawList* GetBackgroundDrawList(ImGuiViewport* viewport); // get background draw list for the given viewport. this draw list will be the first rendering one. Useful to quickly draw shapes/text behind dear imgui contents. - IMGUI_API ImDrawList* GetForegroundDrawList(ImGuiViewport* viewport); // get foreground draw list for the given viewport. this draw list will be the last rendered one. Useful to quickly draw shapes/text over dear imgui contents. - - // Miscellaneous Utilities - IMGUI_API bool IsRectVisible(const ImVec2& size); // test if rectangle (of given size, starting from cursor position) is visible / not clipped. - IMGUI_API bool IsRectVisible(const ImVec2& rect_min, const ImVec2& rect_max); // test if rectangle (in screen space) is visible / not clipped. to perform coarse clipping on user's side. - IMGUI_API double GetTime(); // get global imgui time. incremented by io.DeltaTime every frame. - IMGUI_API int GetFrameCount(); // get global imgui frame count. incremented by 1 every frame. - IMGUI_API ImDrawListSharedData* GetDrawListSharedData(); // you may use this when creating your own ImDrawList instances. - IMGUI_API const char* GetStyleColorName(ImGuiCol idx); // get a string corresponding to the enum value (for display, saving, etc.). - IMGUI_API void SetStateStorage(ImGuiStorage* storage); // replace current window storage with our own (if you want to manipulate it yourself, typically clear subsection of it) - IMGUI_API ImGuiStorage* GetStateStorage(); - IMGUI_API bool BeginChildFrame(ImGuiID id, const ImVec2& size, ImGuiWindowFlags flags = 0); // helper to create a child window / scrolling region that looks like a normal widget frame - IMGUI_API void EndChildFrame(); // always call EndChildFrame() regardless of BeginChildFrame() return values (which indicates a collapsed/clipped window) - - // Text Utilities - IMGUI_API ImVec2 CalcTextSize(const char* text, const char* text_end = NULL, bool hide_text_after_double_hash = false, float wrap_width = -1.0f); - - // Color Utilities - IMGUI_API ImVec4 ColorConvertU32ToFloat4(ImU32 in); - IMGUI_API ImU32 ColorConvertFloat4ToU32(const ImVec4& in); - IMGUI_API void ColorConvertRGBtoHSV(float r, float g, float b, float& out_h, float& out_s, float& out_v); - IMGUI_API void ColorConvertHSVtoRGB(float h, float s, float v, float& out_r, float& out_g, float& out_b); - - // Inputs Utilities: Keyboard/Mouse/Gamepad - // - the ImGuiKey enum contains all possible keyboard, mouse and gamepad inputs (e.g. ImGuiKey_A, ImGuiKey_MouseLeft, ImGuiKey_GamepadDpadUp...). - // - before v1.87, we used ImGuiKey to carry native/user indices as defined by each backends. About use of those legacy ImGuiKey values: - // - without IMGUI_DISABLE_OBSOLETE_KEYIO (legacy support): you can still use your legacy native/user indices (< 512) according to how your backend/engine stored them in io.KeysDown[], but need to cast them to ImGuiKey. - // - with IMGUI_DISABLE_OBSOLETE_KEYIO (this is the way forward): any use of ImGuiKey will assert with key < 512. GetKeyIndex() is pass-through and therefore deprecated (gone if IMGUI_DISABLE_OBSOLETE_KEYIO is defined). - IMGUI_API bool IsKeyDown(ImGuiKey key); // is key being held. - IMGUI_API bool IsKeyPressed(ImGuiKey key, bool repeat = true); // was key pressed (went from !Down to Down)? if repeat=true, uses io.KeyRepeatDelay / KeyRepeatRate - IMGUI_API bool IsKeyReleased(ImGuiKey key); // was key released (went from Down to !Down)? - IMGUI_API int GetKeyPressedAmount(ImGuiKey key, float repeat_delay, float rate); // uses provided repeat rate/delay. return a count, most often 0 or 1 but might be >1 if RepeatRate is small enough that DeltaTime > RepeatRate - IMGUI_API const char* GetKeyName(ImGuiKey key); // [DEBUG] returns English name of the key. Those names a provided for debugging purpose and are not meant to be saved persistently not compared. - IMGUI_API void SetNextFrameWantCaptureKeyboard(bool want_capture_keyboard); // Override io.WantCaptureKeyboard flag next frame (said flag is left for your application to handle, typically when true it instructs your app to ignore inputs). e.g. force capture keyboard when your widget is being hovered. This is equivalent to setting "io.WantCaptureKeyboard = want_capture_keyboard"; after the next NewFrame() call. - - // Inputs Utilities: Mouse specific - // - To refer to a mouse button, you may use named enums in your code e.g. ImGuiMouseButton_Left, ImGuiMouseButton_Right. - // - You can also use regular integer: it is forever guaranteed that 0=Left, 1=Right, 2=Middle. - // - Dragging operations are only reported after mouse has moved a certain distance away from the initial clicking position (see 'lock_threshold' and 'io.MouseDraggingThreshold') - IMGUI_API bool IsMouseDown(ImGuiMouseButton button); // is mouse button held? - IMGUI_API bool IsMouseClicked(ImGuiMouseButton button, bool repeat = false); // did mouse button clicked? (went from !Down to Down). Same as GetMouseClickedCount() == 1. - IMGUI_API bool IsMouseReleased(ImGuiMouseButton button); // did mouse button released? (went from Down to !Down) - IMGUI_API bool IsMouseDoubleClicked(ImGuiMouseButton button); // did mouse button double-clicked? Same as GetMouseClickedCount() == 2. (note that a double-click will also report IsMouseClicked() == true) - IMGUI_API int GetMouseClickedCount(ImGuiMouseButton button); // return the number of successive mouse-clicks at the time where a click happen (otherwise 0). - IMGUI_API bool IsMouseHoveringRect(const ImVec2& r_min, const ImVec2& r_max, bool clip = true);// is mouse hovering given bounding rect (in screen space). clipped by current clipping settings, but disregarding of other consideration of focus/window ordering/popup-block. - IMGUI_API bool IsMousePosValid(const ImVec2* mouse_pos = NULL); // by convention we use (-FLT_MAX,-FLT_MAX) to denote that there is no mouse available - IMGUI_API bool IsAnyMouseDown(); // [WILL OBSOLETE] is any mouse button held? This was designed for backends, but prefer having backend maintain a mask of held mouse buttons, because upcoming input queue system will make this invalid. - IMGUI_API ImVec2 GetMousePos(); // shortcut to ImGui::GetIO().MousePos provided by user, to be consistent with other calls - IMGUI_API ImVec2 GetMousePosOnOpeningCurrentPopup(); // retrieve mouse position at the time of opening popup we have BeginPopup() into (helper to avoid user backing that value themselves) - IMGUI_API bool IsMouseDragging(ImGuiMouseButton button, float lock_threshold = -1.0f); // is mouse dragging? (if lock_threshold < -1.0f, uses io.MouseDraggingThreshold) - IMGUI_API ImVec2 GetMouseDragDelta(ImGuiMouseButton button = 0, float lock_threshold = -1.0f); // return the delta from the initial clicking position while the mouse button is pressed or was just released. This is locked and return 0.0f until the mouse moves past a distance threshold at least once (if lock_threshold < -1.0f, uses io.MouseDraggingThreshold) - IMGUI_API void ResetMouseDragDelta(ImGuiMouseButton button = 0); // - IMGUI_API ImGuiMouseCursor GetMouseCursor(); // get desired mouse cursor shape. Important: reset in ImGui::NewFrame(), this is updated during the frame. valid before Render(). If you use software rendering by setting io.MouseDrawCursor ImGui will render those for you - IMGUI_API void SetMouseCursor(ImGuiMouseCursor cursor_type); // set desired mouse cursor shape - IMGUI_API void SetNextFrameWantCaptureMouse(bool want_capture_mouse); // Override io.WantCaptureMouse flag next frame (said flag is left for your application to handle, typical when true it instucts your app to ignore inputs). This is equivalent to setting "io.WantCaptureMouse = want_capture_mouse;" after the next NewFrame() call. - - // Clipboard Utilities - // - Also see the LogToClipboard() function to capture GUI into clipboard, or easily output text data to the clipboard. - IMGUI_API const char* GetClipboardText(); - IMGUI_API void SetClipboardText(const char* text); - - // Settings/.Ini Utilities - // - The disk functions are automatically called if io.IniFilename != NULL (default is "imgui.ini"). - // - Set io.IniFilename to NULL to load/save manually. Read io.WantSaveIniSettings description about handling .ini saving manually. - // - Important: default value "imgui.ini" is relative to current working dir! Most apps will want to lock this to an absolute path (e.g. same path as executables). - IMGUI_API void LoadIniSettingsFromDisk(const char* ini_filename); // call after CreateContext() and before the first call to NewFrame(). NewFrame() automatically calls LoadIniSettingsFromDisk(io.IniFilename). - IMGUI_API void LoadIniSettingsFromMemory(const char* ini_data, size_t ini_size=0); // call after CreateContext() and before the first call to NewFrame() to provide .ini data from your own data source. - IMGUI_API void SaveIniSettingsToDisk(const char* ini_filename); // this is automatically called (if io.IniFilename is not empty) a few seconds after any modification that should be reflected in the .ini file (and also by DestroyContext). - IMGUI_API const char* SaveIniSettingsToMemory(size_t* out_ini_size = NULL); // return a zero-terminated string with the .ini data which you can save by your own mean. call when io.WantSaveIniSettings is set, then save data by your own mean and clear io.WantSaveIniSettings. - - // Debug Utilities - IMGUI_API void DebugTextEncoding(const char* text); - IMGUI_API bool DebugCheckVersionAndDataLayout(const char* version_str, size_t sz_io, size_t sz_style, size_t sz_vec2, size_t sz_vec4, size_t sz_drawvert, size_t sz_drawidx); // This is called by IMGUI_CHECKVERSION() macro. - - // Memory Allocators - // - Those functions are not reliant on the current context. - // - DLL users: heaps and globals are not shared across DLL boundaries! You will need to call SetCurrentContext() + SetAllocatorFunctions() - // for each static/DLL boundary you are calling from. Read "Context and Memory Allocators" section of imgui.cpp for more details. - IMGUI_API void SetAllocatorFunctions(ImGuiMemAllocFunc alloc_func, ImGuiMemFreeFunc free_func, void* user_data = NULL); - IMGUI_API void GetAllocatorFunctions(ImGuiMemAllocFunc* p_alloc_func, ImGuiMemFreeFunc* p_free_func, void** p_user_data); - IMGUI_API void* MemAlloc(size_t size); - IMGUI_API void MemFree(void* ptr); - - // (Optional) Platform/OS interface for multi-viewport support - // Read comments around the ImGuiPlatformIO structure for more details. - // Note: You may use GetWindowViewport() to get the current viewport of the current window. - IMGUI_API ImGuiPlatformIO& GetPlatformIO(); // platform/renderer functions, for backend to setup + viewports list. - IMGUI_API void UpdatePlatformWindows(); // call in main loop. will call CreateWindow/ResizeWindow/etc. platform functions for each secondary viewport, and DestroyWindow for each inactive viewport. - IMGUI_API void RenderPlatformWindowsDefault(void* platform_render_arg = NULL, void* renderer_render_arg = NULL); // call in main loop. will call RenderWindow/SwapBuffers platform functions for each secondary viewport which doesn't have the ImGuiViewportFlags_Minimized flag set. May be reimplemented by user for custom rendering needs. - IMGUI_API void DestroyPlatformWindows(); // call DestroyWindow platform functions for all viewports. call from backend Shutdown() if you need to close platform windows before imgui shutdown. otherwise will be called by DestroyContext(). - IMGUI_API ImGuiViewport* FindViewportByID(ImGuiID id); // this is a helper for backends. - IMGUI_API ImGuiViewport* FindViewportByPlatformHandle(void* platform_handle); // this is a helper for backends. the type platform_handle is decided by the backend (e.g. HWND, MyWindow*, GLFWwindow* etc.) - -} // namespace ImGui - -//----------------------------------------------------------------------------- -// [SECTION] Flags & Enumerations -//----------------------------------------------------------------------------- - -// Flags for ImGui::Begin() -// (Those are per-window flags. There are shared flags in ImGuiIO: io.ConfigWindowsResizeFromEdges and io.ConfigWindowsMoveFromTitleBarOnly) -enum ImGuiWindowFlags_ -{ - ImGuiWindowFlags_None = 0, - ImGuiWindowFlags_NoTitleBar = 1 << 0, // Disable title-bar - ImGuiWindowFlags_NoResize = 1 << 1, // Disable user resizing with the lower-right grip - ImGuiWindowFlags_NoMove = 1 << 2, // Disable user moving the window - ImGuiWindowFlags_NoScrollbar = 1 << 3, // Disable scrollbars (window can still scroll with mouse or programmatically) - ImGuiWindowFlags_NoScrollWithMouse = 1 << 4, // Disable user vertically scrolling with mouse wheel. On child window, mouse wheel will be forwarded to the parent unless NoScrollbar is also set. - ImGuiWindowFlags_NoCollapse = 1 << 5, // Disable user collapsing window by double-clicking on it. Also referred to as Window Menu Button (e.g. within a docking node). - ImGuiWindowFlags_AlwaysAutoResize = 1 << 6, // Resize every window to its content every frame - ImGuiWindowFlags_NoBackground = 1 << 7, // Disable drawing background color (WindowBg, etc.) and outside border. Similar as using SetNextWindowBgAlpha(0.0f). - ImGuiWindowFlags_NoSavedSettings = 1 << 8, // Never load/save settings in .ini file - ImGuiWindowFlags_NoMouseInputs = 1 << 9, // Disable catching mouse, hovering test with pass through. - ImGuiWindowFlags_MenuBar = 1 << 10, // Has a menu-bar - ImGuiWindowFlags_HorizontalScrollbar = 1 << 11, // Allow horizontal scrollbar to appear (off by default). You may use SetNextWindowContentSize(ImVec2(width,0.0f)); prior to calling Begin() to specify width. Read code in imgui_demo in the "Horizontal Scrolling" section. - ImGuiWindowFlags_NoFocusOnAppearing = 1 << 12, // Disable taking focus when transitioning from hidden to visible state - ImGuiWindowFlags_NoBringToFrontOnFocus = 1 << 13, // Disable bringing window to front when taking focus (e.g. clicking on it or programmatically giving it focus) - ImGuiWindowFlags_AlwaysVerticalScrollbar= 1 << 14, // Always show vertical scrollbar (even if ContentSize.y < Size.y) - ImGuiWindowFlags_AlwaysHorizontalScrollbar=1<< 15, // Always show horizontal scrollbar (even if ContentSize.x < Size.x) - ImGuiWindowFlags_AlwaysUseWindowPadding = 1 << 16, // Ensure child windows without border uses style.WindowPadding (ignored by default for non-bordered child windows, because more convenient) - ImGuiWindowFlags_NoNavInputs = 1 << 18, // No gamepad/keyboard navigation within the window - ImGuiWindowFlags_NoNavFocus = 1 << 19, // No focusing toward this window with gamepad/keyboard navigation (e.g. skipped by CTRL+TAB) - ImGuiWindowFlags_UnsavedDocument = 1 << 20, // Display a dot next to the title. When used in a tab/docking context, tab is selected when clicking the X + closure is not assumed (will wait for user to stop submitting the tab). Otherwise closure is assumed when pressing the X, so if you keep submitting the tab may reappear at end of tab bar. - ImGuiWindowFlags_NoDocking = 1 << 21, // Disable docking of this window - - ImGuiWindowFlags_NoNav = ImGuiWindowFlags_NoNavInputs | ImGuiWindowFlags_NoNavFocus, - ImGuiWindowFlags_NoDecoration = ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_NoResize | ImGuiWindowFlags_NoScrollbar | ImGuiWindowFlags_NoCollapse, - ImGuiWindowFlags_NoInputs = ImGuiWindowFlags_NoMouseInputs | ImGuiWindowFlags_NoNavInputs | ImGuiWindowFlags_NoNavFocus, - - // [Internal] - ImGuiWindowFlags_NavFlattened = 1 << 23, // [BETA] On child window: allow gamepad/keyboard navigation to cross over parent border to this child or between sibling child windows. - ImGuiWindowFlags_ChildWindow = 1 << 24, // Don't use! For internal use by BeginChild() - ImGuiWindowFlags_Tooltip = 1 << 25, // Don't use! For internal use by BeginTooltip() - ImGuiWindowFlags_Popup = 1 << 26, // Don't use! For internal use by BeginPopup() - ImGuiWindowFlags_Modal = 1 << 27, // Don't use! For internal use by BeginPopupModal() - ImGuiWindowFlags_ChildMenu = 1 << 28, // Don't use! For internal use by BeginMenu() - ImGuiWindowFlags_DockNodeHost = 1 << 29, // Don't use! For internal use by Begin()/NewFrame() -}; - -// Flags for ImGui::InputText() -// (Those are per-item flags. There are shared flags in ImGuiIO: io.ConfigInputTextCursorBlink and io.ConfigInputTextEnterKeepActive) -enum ImGuiInputTextFlags_ -{ - ImGuiInputTextFlags_None = 0, - ImGuiInputTextFlags_CharsDecimal = 1 << 0, // Allow 0123456789.+-*/ - ImGuiInputTextFlags_CharsHexadecimal = 1 << 1, // Allow 0123456789ABCDEFabcdef - ImGuiInputTextFlags_CharsUppercase = 1 << 2, // Turn a..z into A..Z - ImGuiInputTextFlags_CharsNoBlank = 1 << 3, // Filter out spaces, tabs - ImGuiInputTextFlags_AutoSelectAll = 1 << 4, // Select entire text when first taking mouse focus - ImGuiInputTextFlags_EnterReturnsTrue = 1 << 5, // Return 'true' when Enter is pressed (as opposed to every time the value was modified). Consider looking at the IsItemDeactivatedAfterEdit() function. - ImGuiInputTextFlags_CallbackCompletion = 1 << 6, // Callback on pressing TAB (for completion handling) - ImGuiInputTextFlags_CallbackHistory = 1 << 7, // Callback on pressing Up/Down arrows (for history handling) - ImGuiInputTextFlags_CallbackAlways = 1 << 8, // Callback on each iteration. User code may query cursor position, modify text buffer. - ImGuiInputTextFlags_CallbackCharFilter = 1 << 9, // Callback on character inputs to replace or discard them. Modify 'EventChar' to replace or discard, or return 1 in callback to discard. - ImGuiInputTextFlags_AllowTabInput = 1 << 10, // Pressing TAB input a '\t' character into the text field - ImGuiInputTextFlags_CtrlEnterForNewLine = 1 << 11, // In multi-line mode, unfocus with Enter, add new line with Ctrl+Enter (default is opposite: unfocus with Ctrl+Enter, add line with Enter). - ImGuiInputTextFlags_NoHorizontalScroll = 1 << 12, // Disable following the cursor horizontally - ImGuiInputTextFlags_AlwaysOverwrite = 1 << 13, // Overwrite mode - ImGuiInputTextFlags_ReadOnly = 1 << 14, // Read-only mode - ImGuiInputTextFlags_Password = 1 << 15, // Password mode, display all characters as '*' - ImGuiInputTextFlags_NoUndoRedo = 1 << 16, // Disable undo/redo. Note that input text owns the text data while active, if you want to provide your own undo/redo stack you need e.g. to call ClearActiveID(). - ImGuiInputTextFlags_CharsScientific = 1 << 17, // Allow 0123456789.+-*/eE (Scientific notation input) - ImGuiInputTextFlags_CallbackResize = 1 << 18, // Callback on buffer capacity changes request (beyond 'buf_size' parameter value), allowing the string to grow. Notify when the string wants to be resized (for string types which hold a cache of their Size). You will be provided a new BufSize in the callback and NEED to honor it. (see misc/cpp/imgui_stdlib.h for an example of using this) - ImGuiInputTextFlags_CallbackEdit = 1 << 19, // Callback on any edit (note that InputText() already returns true on edit, the callback is useful mainly to manipulate the underlying buffer while focus is active) - ImGuiInputTextFlags_EscapeClearsAll = 1 << 20, // Escape key clears content if not empty, and deactivate otherwise (contrast to default behavior of Escape to revert) - - // Obsolete names - //ImGuiInputTextFlags_AlwaysInsertMode = ImGuiInputTextFlags_AlwaysOverwrite // [renamed in 1.82] name was not matching behavior -}; - -// Flags for ImGui::TreeNodeEx(), ImGui::CollapsingHeader*() -enum ImGuiTreeNodeFlags_ -{ - ImGuiTreeNodeFlags_None = 0, - ImGuiTreeNodeFlags_Selected = 1 << 0, // Draw as selected - ImGuiTreeNodeFlags_Framed = 1 << 1, // Draw frame with background (e.g. for CollapsingHeader) - ImGuiTreeNodeFlags_AllowOverlap = 1 << 2, // Hit testing to allow subsequent widgets to overlap this one - ImGuiTreeNodeFlags_NoTreePushOnOpen = 1 << 3, // Don't do a TreePush() when open (e.g. for CollapsingHeader) = no extra indent nor pushing on ID stack - ImGuiTreeNodeFlags_NoAutoOpenOnLog = 1 << 4, // Don't automatically and temporarily open node when Logging is active (by default logging will automatically open tree nodes) - ImGuiTreeNodeFlags_DefaultOpen = 1 << 5, // Default node to be open - ImGuiTreeNodeFlags_OpenOnDoubleClick = 1 << 6, // Need double-click to open node - ImGuiTreeNodeFlags_OpenOnArrow = 1 << 7, // Only open when clicking on the arrow part. If ImGuiTreeNodeFlags_OpenOnDoubleClick is also set, single-click arrow or double-click all box to open. - ImGuiTreeNodeFlags_Leaf = 1 << 8, // No collapsing, no arrow (use as a convenience for leaf nodes). - ImGuiTreeNodeFlags_Bullet = 1 << 9, // Display a bullet instead of arrow. IMPORTANT: node can still be marked open/close if you don't set the _Leaf flag! - ImGuiTreeNodeFlags_FramePadding = 1 << 10, // Use FramePadding (even for an unframed text node) to vertically align text baseline to regular widget height. Equivalent to calling AlignTextToFramePadding(). - ImGuiTreeNodeFlags_SpanAvailWidth = 1 << 11, // Extend hit box to the right-most edge, even if not framed. This is not the default in order to allow adding other items on the same line. In the future we may refactor the hit system to be front-to-back, allowing natural overlaps and then this can become the default. - ImGuiTreeNodeFlags_SpanFullWidth = 1 << 12, // Extend hit box to the left-most and right-most edges (bypass the indented area). - ImGuiTreeNodeFlags_SpanAllColumns = 1 << 13, // Frame will span all columns of its container table (text will still fit in current column) - ImGuiTreeNodeFlags_NavLeftJumpsBackHere = 1 << 14, // (WIP) Nav: left direction may move to this TreeNode() from any of its child (items submitted between TreeNode and TreePop) - //ImGuiTreeNodeFlags_NoScrollOnOpen = 1 << 14, // FIXME: TODO: Disable automatic scroll on TreePop() if node got just open and contents is not visible - ImGuiTreeNodeFlags_CollapsingHeader = ImGuiTreeNodeFlags_Framed | ImGuiTreeNodeFlags_NoTreePushOnOpen | ImGuiTreeNodeFlags_NoAutoOpenOnLog, - -#ifndef IMGUI_DISABLE_OBSOLETE_FUNCTIONS - ImGuiTreeNodeFlags_AllowItemOverlap = ImGuiTreeNodeFlags_AllowOverlap, // Renamed in 1.89.7 -#endif -}; - -// Flags for OpenPopup*(), BeginPopupContext*(), IsPopupOpen() functions. -// - To be backward compatible with older API which took an 'int mouse_button = 1' argument, we need to treat -// small flags values as a mouse button index, so we encode the mouse button in the first few bits of the flags. -// It is therefore guaranteed to be legal to pass a mouse button index in ImGuiPopupFlags. -// - For the same reason, we exceptionally default the ImGuiPopupFlags argument of BeginPopupContextXXX functions to 1 instead of 0. -// IMPORTANT: because the default parameter is 1 (==ImGuiPopupFlags_MouseButtonRight), if you rely on the default parameter -// and want to use another flag, you need to pass in the ImGuiPopupFlags_MouseButtonRight flag explicitly. -// - Multiple buttons currently cannot be combined/or-ed in those functions (we could allow it later). -enum ImGuiPopupFlags_ -{ - ImGuiPopupFlags_None = 0, - ImGuiPopupFlags_MouseButtonLeft = 0, // For BeginPopupContext*(): open on Left Mouse release. Guaranteed to always be == 0 (same as ImGuiMouseButton_Left) - ImGuiPopupFlags_MouseButtonRight = 1, // For BeginPopupContext*(): open on Right Mouse release. Guaranteed to always be == 1 (same as ImGuiMouseButton_Right) - ImGuiPopupFlags_MouseButtonMiddle = 2, // For BeginPopupContext*(): open on Middle Mouse release. Guaranteed to always be == 2 (same as ImGuiMouseButton_Middle) - ImGuiPopupFlags_MouseButtonMask_ = 0x1F, - ImGuiPopupFlags_MouseButtonDefault_ = 1, - ImGuiPopupFlags_NoOpenOverExistingPopup = 1 << 5, // For OpenPopup*(), BeginPopupContext*(): don't open if there's already a popup at the same level of the popup stack - ImGuiPopupFlags_NoOpenOverItems = 1 << 6, // For BeginPopupContextWindow(): don't return true when hovering items, only when hovering empty space - ImGuiPopupFlags_AnyPopupId = 1 << 7, // For IsPopupOpen(): ignore the ImGuiID parameter and test for any popup. - ImGuiPopupFlags_AnyPopupLevel = 1 << 8, // For IsPopupOpen(): search/test at any level of the popup stack (default test in the current level) - ImGuiPopupFlags_AnyPopup = ImGuiPopupFlags_AnyPopupId | ImGuiPopupFlags_AnyPopupLevel, -}; - -// Flags for ImGui::Selectable() -enum ImGuiSelectableFlags_ -{ - ImGuiSelectableFlags_None = 0, - ImGuiSelectableFlags_DontClosePopups = 1 << 0, // Clicking this doesn't close parent popup window - ImGuiSelectableFlags_SpanAllColumns = 1 << 1, // Frame will span all columns of its container table (text will still fit in current column) - ImGuiSelectableFlags_AllowDoubleClick = 1 << 2, // Generate press events on double clicks too - ImGuiSelectableFlags_Disabled = 1 << 3, // Cannot be selected, display grayed out text - ImGuiSelectableFlags_AllowOverlap = 1 << 4, // (WIP) Hit testing to allow subsequent widgets to overlap this one - -#ifndef IMGUI_DISABLE_OBSOLETE_FUNCTIONS - ImGuiSelectableFlags_AllowItemOverlap = ImGuiSelectableFlags_AllowOverlap, // Renamed in 1.89.7 -#endif -}; - -// Flags for ImGui::BeginCombo() -enum ImGuiComboFlags_ -{ - ImGuiComboFlags_None = 0, - ImGuiComboFlags_PopupAlignLeft = 1 << 0, // Align the popup toward the left by default - ImGuiComboFlags_HeightSmall = 1 << 1, // Max ~4 items visible. Tip: If you want your combo popup to be a specific size you can use SetNextWindowSizeConstraints() prior to calling BeginCombo() - ImGuiComboFlags_HeightRegular = 1 << 2, // Max ~8 items visible (default) - ImGuiComboFlags_HeightLarge = 1 << 3, // Max ~20 items visible - ImGuiComboFlags_HeightLargest = 1 << 4, // As many fitting items as possible - ImGuiComboFlags_NoArrowButton = 1 << 5, // Display on the preview box without the square arrow button - ImGuiComboFlags_NoPreview = 1 << 6, // Display only a square arrow button - ImGuiComboFlags_WidthFitPreview = 1 << 7, // Width dynamically calculated from preview contents - ImGuiComboFlags_HeightMask_ = ImGuiComboFlags_HeightSmall | ImGuiComboFlags_HeightRegular | ImGuiComboFlags_HeightLarge | ImGuiComboFlags_HeightLargest, -}; - -// Flags for ImGui::BeginTabBar() -enum ImGuiTabBarFlags_ -{ - ImGuiTabBarFlags_None = 0, - ImGuiTabBarFlags_Reorderable = 1 << 0, // Allow manually dragging tabs to re-order them + New tabs are appended at the end of list - ImGuiTabBarFlags_AutoSelectNewTabs = 1 << 1, // Automatically select new tabs when they appear - ImGuiTabBarFlags_TabListPopupButton = 1 << 2, // Disable buttons to open the tab list popup - ImGuiTabBarFlags_NoCloseWithMiddleMouseButton = 1 << 3, // Disable behavior of closing tabs (that are submitted with p_open != NULL) with middle mouse button. You can still repro this behavior on user's side with if (IsItemHovered() && IsMouseClicked(2)) *p_open = false. - ImGuiTabBarFlags_NoTabListScrollingButtons = 1 << 4, // Disable scrolling buttons (apply when fitting policy is ImGuiTabBarFlags_FittingPolicyScroll) - ImGuiTabBarFlags_NoTooltip = 1 << 5, // Disable tooltips when hovering a tab - ImGuiTabBarFlags_FittingPolicyResizeDown = 1 << 6, // Resize tabs when they don't fit - ImGuiTabBarFlags_FittingPolicyScroll = 1 << 7, // Add scroll buttons when tabs don't fit - ImGuiTabBarFlags_FittingPolicyMask_ = ImGuiTabBarFlags_FittingPolicyResizeDown | ImGuiTabBarFlags_FittingPolicyScroll, - ImGuiTabBarFlags_FittingPolicyDefault_ = ImGuiTabBarFlags_FittingPolicyResizeDown, -}; - -// Flags for ImGui::BeginTabItem() -enum ImGuiTabItemFlags_ -{ - ImGuiTabItemFlags_None = 0, - ImGuiTabItemFlags_UnsavedDocument = 1 << 0, // Display a dot next to the title + tab is selected when clicking the X + closure is not assumed (will wait for user to stop submitting the tab). Otherwise closure is assumed when pressing the X, so if you keep submitting the tab may reappear at end of tab bar. - ImGuiTabItemFlags_SetSelected = 1 << 1, // Trigger flag to programmatically make the tab selected when calling BeginTabItem() - ImGuiTabItemFlags_NoCloseWithMiddleMouseButton = 1 << 2, // Disable behavior of closing tabs (that are submitted with p_open != NULL) with middle mouse button. You can still repro this behavior on user's side with if (IsItemHovered() && IsMouseClicked(2)) *p_open = false. - ImGuiTabItemFlags_NoPushId = 1 << 3, // Don't call PushID(tab->ID)/PopID() on BeginTabItem()/EndTabItem() - ImGuiTabItemFlags_NoTooltip = 1 << 4, // Disable tooltip for the given tab - ImGuiTabItemFlags_NoReorder = 1 << 5, // Disable reordering this tab or having another tab cross over this tab - ImGuiTabItemFlags_Leading = 1 << 6, // Enforce the tab position to the left of the tab bar (after the tab list popup button) - ImGuiTabItemFlags_Trailing = 1 << 7, // Enforce the tab position to the right of the tab bar (before the scrolling buttons) -}; - -// Flags for ImGui::BeginTable() -// - Important! Sizing policies have complex and subtle side effects, much more so than you would expect. -// Read comments/demos carefully + experiment with live demos to get acquainted with them. -// - The DEFAULT sizing policies are: -// - Default to ImGuiTableFlags_SizingFixedFit if ScrollX is on, or if host window has ImGuiWindowFlags_AlwaysAutoResize. -// - Default to ImGuiTableFlags_SizingStretchSame if ScrollX is off. -// - When ScrollX is off: -// - Table defaults to ImGuiTableFlags_SizingStretchSame -> all Columns defaults to ImGuiTableColumnFlags_WidthStretch with same weight. -// - Columns sizing policy allowed: Stretch (default), Fixed/Auto. -// - Fixed Columns (if any) will generally obtain their requested width (unless the table cannot fit them all). -// - Stretch Columns will share the remaining width according to their respective weight. -// - Mixed Fixed/Stretch columns is possible but has various side-effects on resizing behaviors. -// The typical use of mixing sizing policies is: any number of LEADING Fixed columns, followed by one or two TRAILING Stretch columns. -// (this is because the visible order of columns have subtle but necessary effects on how they react to manual resizing). -// - When ScrollX is on: -// - Table defaults to ImGuiTableFlags_SizingFixedFit -> all Columns defaults to ImGuiTableColumnFlags_WidthFixed -// - Columns sizing policy allowed: Fixed/Auto mostly. -// - Fixed Columns can be enlarged as needed. Table will show a horizontal scrollbar if needed. -// - When using auto-resizing (non-resizable) fixed columns, querying the content width to use item right-alignment e.g. SetNextItemWidth(-FLT_MIN) doesn't make sense, would create a feedback loop. -// - Using Stretch columns OFTEN DOES NOT MAKE SENSE if ScrollX is on, UNLESS you have specified a value for 'inner_width' in BeginTable(). -// If you specify a value for 'inner_width' then effectively the scrolling space is known and Stretch or mixed Fixed/Stretch columns become meaningful again. -// - Read on documentation at the top of imgui_tables.cpp for details. -enum ImGuiTableFlags_ -{ - // Features - ImGuiTableFlags_None = 0, - ImGuiTableFlags_Resizable = 1 << 0, // Enable resizing columns. - ImGuiTableFlags_Reorderable = 1 << 1, // Enable reordering columns in header row (need calling TableSetupColumn() + TableHeadersRow() to display headers) - ImGuiTableFlags_Hideable = 1 << 2, // Enable hiding/disabling columns in context menu. - ImGuiTableFlags_Sortable = 1 << 3, // Enable sorting. Call TableGetSortSpecs() to obtain sort specs. Also see ImGuiTableFlags_SortMulti and ImGuiTableFlags_SortTristate. - ImGuiTableFlags_NoSavedSettings = 1 << 4, // Disable persisting columns order, width and sort settings in the .ini file. - ImGuiTableFlags_ContextMenuInBody = 1 << 5, // Right-click on columns body/contents will display table context menu. By default it is available in TableHeadersRow(). - // Decorations - ImGuiTableFlags_RowBg = 1 << 6, // Set each RowBg color with ImGuiCol_TableRowBg or ImGuiCol_TableRowBgAlt (equivalent of calling TableSetBgColor with ImGuiTableBgFlags_RowBg0 on each row manually) - ImGuiTableFlags_BordersInnerH = 1 << 7, // Draw horizontal borders between rows. - ImGuiTableFlags_BordersOuterH = 1 << 8, // Draw horizontal borders at the top and bottom. - ImGuiTableFlags_BordersInnerV = 1 << 9, // Draw vertical borders between columns. - ImGuiTableFlags_BordersOuterV = 1 << 10, // Draw vertical borders on the left and right sides. - ImGuiTableFlags_BordersH = ImGuiTableFlags_BordersInnerH | ImGuiTableFlags_BordersOuterH, // Draw horizontal borders. - ImGuiTableFlags_BordersV = ImGuiTableFlags_BordersInnerV | ImGuiTableFlags_BordersOuterV, // Draw vertical borders. - ImGuiTableFlags_BordersInner = ImGuiTableFlags_BordersInnerV | ImGuiTableFlags_BordersInnerH, // Draw inner borders. - ImGuiTableFlags_BordersOuter = ImGuiTableFlags_BordersOuterV | ImGuiTableFlags_BordersOuterH, // Draw outer borders. - ImGuiTableFlags_Borders = ImGuiTableFlags_BordersInner | ImGuiTableFlags_BordersOuter, // Draw all borders. - ImGuiTableFlags_NoBordersInBody = 1 << 11, // [ALPHA] Disable vertical borders in columns Body (borders will always appear in Headers). -> May move to style - ImGuiTableFlags_NoBordersInBodyUntilResize = 1 << 12, // [ALPHA] Disable vertical borders in columns Body until hovered for resize (borders will always appear in Headers). -> May move to style - // Sizing Policy (read above for defaults) - ImGuiTableFlags_SizingFixedFit = 1 << 13, // Columns default to _WidthFixed or _WidthAuto (if resizable or not resizable), matching contents width. - ImGuiTableFlags_SizingFixedSame = 2 << 13, // Columns default to _WidthFixed or _WidthAuto (if resizable or not resizable), matching the maximum contents width of all columns. Implicitly enable ImGuiTableFlags_NoKeepColumnsVisible. - ImGuiTableFlags_SizingStretchProp = 3 << 13, // Columns default to _WidthStretch with default weights proportional to each columns contents widths. - ImGuiTableFlags_SizingStretchSame = 4 << 13, // Columns default to _WidthStretch with default weights all equal, unless overridden by TableSetupColumn(). - // Sizing Extra Options - ImGuiTableFlags_NoHostExtendX = 1 << 16, // Make outer width auto-fit to columns, overriding outer_size.x value. Only available when ScrollX/ScrollY are disabled and Stretch columns are not used. - ImGuiTableFlags_NoHostExtendY = 1 << 17, // Make outer height stop exactly at outer_size.y (prevent auto-extending table past the limit). Only available when ScrollX/ScrollY are disabled. Data below the limit will be clipped and not visible. - ImGuiTableFlags_NoKeepColumnsVisible = 1 << 18, // Disable keeping column always minimally visible when ScrollX is off and table gets too small. Not recommended if columns are resizable. - ImGuiTableFlags_PreciseWidths = 1 << 19, // Disable distributing remainder width to stretched columns (width allocation on a 100-wide table with 3 columns: Without this flag: 33,33,34. With this flag: 33,33,33). With larger number of columns, resizing will appear to be less smooth. - // Clipping - ImGuiTableFlags_NoClip = 1 << 20, // Disable clipping rectangle for every individual columns (reduce draw command count, items will be able to overflow into other columns). Generally incompatible with TableSetupScrollFreeze(). - // Padding - ImGuiTableFlags_PadOuterX = 1 << 21, // Default if BordersOuterV is on. Enable outermost padding. Generally desirable if you have headers. - ImGuiTableFlags_NoPadOuterX = 1 << 22, // Default if BordersOuterV is off. Disable outermost padding. - ImGuiTableFlags_NoPadInnerX = 1 << 23, // Disable inner padding between columns (double inner padding if BordersOuterV is on, single inner padding if BordersOuterV is off). - // Scrolling - ImGuiTableFlags_ScrollX = 1 << 24, // Enable horizontal scrolling. Require 'outer_size' parameter of BeginTable() to specify the container size. Changes default sizing policy. Because this creates a child window, ScrollY is currently generally recommended when using ScrollX. - ImGuiTableFlags_ScrollY = 1 << 25, // Enable vertical scrolling. Require 'outer_size' parameter of BeginTable() to specify the container size. - // Sorting - ImGuiTableFlags_SortMulti = 1 << 26, // Hold shift when clicking headers to sort on multiple column. TableGetSortSpecs() may return specs where (SpecsCount > 1). - ImGuiTableFlags_SortTristate = 1 << 27, // Allow no sorting, disable default sorting. TableGetSortSpecs() may return specs where (SpecsCount == 0). - // Miscellaneous - ImGuiTableFlags_HighlightHoveredColumn = 1 << 28, // Highlight column headers when hovered (may evolve into a fuller highlight) - - // [Internal] Combinations and masks - ImGuiTableFlags_SizingMask_ = ImGuiTableFlags_SizingFixedFit | ImGuiTableFlags_SizingFixedSame | ImGuiTableFlags_SizingStretchProp | ImGuiTableFlags_SizingStretchSame, -}; - -// Flags for ImGui::TableSetupColumn() -enum ImGuiTableColumnFlags_ -{ - // Input configuration flags - ImGuiTableColumnFlags_None = 0, - ImGuiTableColumnFlags_Disabled = 1 << 0, // Overriding/master disable flag: hide column, won't show in context menu (unlike calling TableSetColumnEnabled() which manipulates the user accessible state) - ImGuiTableColumnFlags_DefaultHide = 1 << 1, // Default as a hidden/disabled column. - ImGuiTableColumnFlags_DefaultSort = 1 << 2, // Default as a sorting column. - ImGuiTableColumnFlags_WidthStretch = 1 << 3, // Column will stretch. Preferable with horizontal scrolling disabled (default if table sizing policy is _SizingStretchSame or _SizingStretchProp). - ImGuiTableColumnFlags_WidthFixed = 1 << 4, // Column will not stretch. Preferable with horizontal scrolling enabled (default if table sizing policy is _SizingFixedFit and table is resizable). - ImGuiTableColumnFlags_NoResize = 1 << 5, // Disable manual resizing. - ImGuiTableColumnFlags_NoReorder = 1 << 6, // Disable manual reordering this column, this will also prevent other columns from crossing over this column. - ImGuiTableColumnFlags_NoHide = 1 << 7, // Disable ability to hide/disable this column. - ImGuiTableColumnFlags_NoClip = 1 << 8, // Disable clipping for this column (all NoClip columns will render in a same draw command). - ImGuiTableColumnFlags_NoSort = 1 << 9, // Disable ability to sort on this field (even if ImGuiTableFlags_Sortable is set on the table). - ImGuiTableColumnFlags_NoSortAscending = 1 << 10, // Disable ability to sort in the ascending direction. - ImGuiTableColumnFlags_NoSortDescending = 1 << 11, // Disable ability to sort in the descending direction. - ImGuiTableColumnFlags_NoHeaderLabel = 1 << 12, // TableHeadersRow() will not submit horizontal label for this column. Convenient for some small columns. Name will still appear in context menu or in angled headers. - ImGuiTableColumnFlags_NoHeaderWidth = 1 << 13, // Disable header text width contribution to automatic column width. - ImGuiTableColumnFlags_PreferSortAscending = 1 << 14, // Make the initial sort direction Ascending when first sorting on this column (default). - ImGuiTableColumnFlags_PreferSortDescending = 1 << 15, // Make the initial sort direction Descending when first sorting on this column. - ImGuiTableColumnFlags_IndentEnable = 1 << 16, // Use current Indent value when entering cell (default for column 0). - ImGuiTableColumnFlags_IndentDisable = 1 << 17, // Ignore current Indent value when entering cell (default for columns > 0). Indentation changes _within_ the cell will still be honored. - ImGuiTableColumnFlags_AngledHeader = 1 << 18, // TableHeadersRow() will submit an angled header row for this column. Note this will add an extra row. - - // Output status flags, read-only via TableGetColumnFlags() - ImGuiTableColumnFlags_IsEnabled = 1 << 24, // Status: is enabled == not hidden by user/api (referred to as "Hide" in _DefaultHide and _NoHide) flags. - ImGuiTableColumnFlags_IsVisible = 1 << 25, // Status: is visible == is enabled AND not clipped by scrolling. - ImGuiTableColumnFlags_IsSorted = 1 << 26, // Status: is currently part of the sort specs - ImGuiTableColumnFlags_IsHovered = 1 << 27, // Status: is hovered by mouse - - // [Internal] Combinations and masks - ImGuiTableColumnFlags_WidthMask_ = ImGuiTableColumnFlags_WidthStretch | ImGuiTableColumnFlags_WidthFixed, - ImGuiTableColumnFlags_IndentMask_ = ImGuiTableColumnFlags_IndentEnable | ImGuiTableColumnFlags_IndentDisable, - ImGuiTableColumnFlags_StatusMask_ = ImGuiTableColumnFlags_IsEnabled | ImGuiTableColumnFlags_IsVisible | ImGuiTableColumnFlags_IsSorted | ImGuiTableColumnFlags_IsHovered, - ImGuiTableColumnFlags_NoDirectResize_ = 1 << 30, // [Internal] Disable user resizing this column directly (it may however we resized indirectly from its left edge) -}; - -// Flags for ImGui::TableNextRow() -enum ImGuiTableRowFlags_ -{ - ImGuiTableRowFlags_None = 0, - ImGuiTableRowFlags_Headers = 1 << 0, // Identify header row (set default background color + width of its contents accounted differently for auto column width) -}; - -// Enum for ImGui::TableSetBgColor() -// Background colors are rendering in 3 layers: -// - Layer 0: draw with RowBg0 color if set, otherwise draw with ColumnBg0 if set. -// - Layer 1: draw with RowBg1 color if set, otherwise draw with ColumnBg1 if set. -// - Layer 2: draw with CellBg color if set. -// The purpose of the two row/columns layers is to let you decide if a background color change should override or blend with the existing color. -// When using ImGuiTableFlags_RowBg on the table, each row has the RowBg0 color automatically set for odd/even rows. -// If you set the color of RowBg0 target, your color will override the existing RowBg0 color. -// If you set the color of RowBg1 or ColumnBg1 target, your color will blend over the RowBg0 color. -enum ImGuiTableBgTarget_ -{ - ImGuiTableBgTarget_None = 0, - ImGuiTableBgTarget_RowBg0 = 1, // Set row background color 0 (generally used for background, automatically set when ImGuiTableFlags_RowBg is used) - ImGuiTableBgTarget_RowBg1 = 2, // Set row background color 1 (generally used for selection marking) - ImGuiTableBgTarget_CellBg = 3, // Set cell background color (top-most color) -}; - -// Flags for ImGui::IsWindowFocused() -enum ImGuiFocusedFlags_ -{ - ImGuiFocusedFlags_None = 0, - ImGuiFocusedFlags_ChildWindows = 1 << 0, // Return true if any children of the window is focused - ImGuiFocusedFlags_RootWindow = 1 << 1, // Test from root window (top most parent of the current hierarchy) - ImGuiFocusedFlags_AnyWindow = 1 << 2, // Return true if any window is focused. Important: If you are trying to tell how to dispatch your low-level inputs, do NOT use this. Use 'io.WantCaptureMouse' instead! Please read the FAQ! - ImGuiFocusedFlags_NoPopupHierarchy = 1 << 3, // Do not consider popup hierarchy (do not treat popup emitter as parent of popup) (when used with _ChildWindows or _RootWindow) - ImGuiFocusedFlags_DockHierarchy = 1 << 4, // Consider docking hierarchy (treat dockspace host as parent of docked window) (when used with _ChildWindows or _RootWindow) - ImGuiFocusedFlags_RootAndChildWindows = ImGuiFocusedFlags_RootWindow | ImGuiFocusedFlags_ChildWindows, -}; - -// Flags for ImGui::IsItemHovered(), ImGui::IsWindowHovered() -// Note: if you are trying to check whether your mouse should be dispatched to Dear ImGui or to your app, you should use 'io.WantCaptureMouse' instead! Please read the FAQ! -// Note: windows with the ImGuiWindowFlags_NoInputs flag are ignored by IsWindowHovered() calls. -enum ImGuiHoveredFlags_ -{ - ImGuiHoveredFlags_None = 0, // Return true if directly over the item/window, not obstructed by another window, not obstructed by an active popup or modal blocking inputs under them. - ImGuiHoveredFlags_ChildWindows = 1 << 0, // IsWindowHovered() only: Return true if any children of the window is hovered - ImGuiHoveredFlags_RootWindow = 1 << 1, // IsWindowHovered() only: Test from root window (top most parent of the current hierarchy) - ImGuiHoveredFlags_AnyWindow = 1 << 2, // IsWindowHovered() only: Return true if any window is hovered - ImGuiHoveredFlags_NoPopupHierarchy = 1 << 3, // IsWindowHovered() only: Do not consider popup hierarchy (do not treat popup emitter as parent of popup) (when used with _ChildWindows or _RootWindow) - ImGuiHoveredFlags_DockHierarchy = 1 << 4, // IsWindowHovered() only: Consider docking hierarchy (treat dockspace host as parent of docked window) (when used with _ChildWindows or _RootWindow) - ImGuiHoveredFlags_AllowWhenBlockedByPopup = 1 << 5, // Return true even if a popup window is normally blocking access to this item/window - //ImGuiHoveredFlags_AllowWhenBlockedByModal = 1 << 6, // Return true even if a modal popup window is normally blocking access to this item/window. FIXME-TODO: Unavailable yet. - ImGuiHoveredFlags_AllowWhenBlockedByActiveItem = 1 << 7, // Return true even if an active item is blocking access to this item/window. Useful for Drag and Drop patterns. - ImGuiHoveredFlags_AllowWhenOverlappedByItem = 1 << 8, // IsItemHovered() only: Return true even if the item uses AllowOverlap mode and is overlapped by another hoverable item. - ImGuiHoveredFlags_AllowWhenOverlappedByWindow = 1 << 9, // IsItemHovered() only: Return true even if the position is obstructed or overlapped by another window. - ImGuiHoveredFlags_AllowWhenDisabled = 1 << 10, // IsItemHovered() only: Return true even if the item is disabled - ImGuiHoveredFlags_NoNavOverride = 1 << 11, // IsItemHovered() only: Disable using gamepad/keyboard navigation state when active, always query mouse - ImGuiHoveredFlags_AllowWhenOverlapped = ImGuiHoveredFlags_AllowWhenOverlappedByItem | ImGuiHoveredFlags_AllowWhenOverlappedByWindow, - ImGuiHoveredFlags_RectOnly = ImGuiHoveredFlags_AllowWhenBlockedByPopup | ImGuiHoveredFlags_AllowWhenBlockedByActiveItem | ImGuiHoveredFlags_AllowWhenOverlapped, - ImGuiHoveredFlags_RootAndChildWindows = ImGuiHoveredFlags_RootWindow | ImGuiHoveredFlags_ChildWindows, - - // Tooltips mode - // - typically used in IsItemHovered() + SetTooltip() sequence. - // - this is a shortcut to pull flags from 'style.HoverFlagsForTooltipMouse' or 'style.HoverFlagsForTooltipNav' where you can reconfigure desired behavior. - // e.g. 'TooltipHoveredFlagsForMouse' defaults to 'ImGuiHoveredFlags_Stationary | ImGuiHoveredFlags_DelayShort'. - // - for frequently actioned or hovered items providing a tooltip, you want may to use ImGuiHoveredFlags_ForTooltip (stationary + delay) so the tooltip doesn't show too often. - // - for items which main purpose is to be hovered, or items with low affordance, or in less consistent apps, prefer no delay or shorter delay. - ImGuiHoveredFlags_ForTooltip = 1 << 12, // Shortcut for standard flags when using IsItemHovered() + SetTooltip() sequence. - - // (Advanced) Mouse Hovering delays. - // - generally you can use ImGuiHoveredFlags_ForTooltip to use application-standardized flags. - // - use those if you need specific overrides. - ImGuiHoveredFlags_Stationary = 1 << 13, // Require mouse to be stationary for style.HoverStationaryDelay (~0.15 sec) _at least one time_. After this, can move on same item/window. Using the stationary test tends to reduces the need for a long delay. - ImGuiHoveredFlags_DelayNone = 1 << 14, // IsItemHovered() only: Return true immediately (default). As this is the default you generally ignore this. - ImGuiHoveredFlags_DelayShort = 1 << 15, // IsItemHovered() only: Return true after style.HoverDelayShort elapsed (~0.15 sec) (shared between items) + requires mouse to be stationary for style.HoverStationaryDelay (once per item). - ImGuiHoveredFlags_DelayNormal = 1 << 16, // IsItemHovered() only: Return true after style.HoverDelayNormal elapsed (~0.40 sec) (shared between items) + requires mouse to be stationary for style.HoverStationaryDelay (once per item). - ImGuiHoveredFlags_NoSharedDelay = 1 << 17, // IsItemHovered() only: Disable shared delay system where moving from one item to the next keeps the previous timer for a short time (standard for tooltips with long delays) -}; - -// Flags for ImGui::DockSpace(), shared/inherited by child nodes. -// (Some flags can be applied to individual nodes directly) -// FIXME-DOCK: Also see ImGuiDockNodeFlagsPrivate_ which may involve using the WIP and internal DockBuilder api. -enum ImGuiDockNodeFlags_ -{ - ImGuiDockNodeFlags_None = 0, - ImGuiDockNodeFlags_KeepAliveOnly = 1 << 0, // // Don't display the dockspace node but keep it alive. Windows docked into this dockspace node won't be undocked. - //ImGuiDockNodeFlags_NoCentralNode = 1 << 1, // // Disable Central Node (the node which can stay empty) - ImGuiDockNodeFlags_NoDockingOverCentralNode = 1 << 2, // // Disable docking over the Central Node, which will be always kept empty. - ImGuiDockNodeFlags_PassthruCentralNode = 1 << 3, // // Enable passthru dockspace: 1) DockSpace() will render a ImGuiCol_WindowBg background covering everything excepted the Central Node when empty. Meaning the host window should probably use SetNextWindowBgAlpha(0.0f) prior to Begin() when using this. 2) When Central Node is empty: let inputs pass-through + won't display a DockingEmptyBg background. See demo for details. - ImGuiDockNodeFlags_NoDockingSplit = 1 << 4, // // Disable other windows/nodes from splitting this node. - ImGuiDockNodeFlags_NoResize = 1 << 5, // Saved // Disable resizing node using the splitter/separators. Useful with programmatically setup dockspaces. - ImGuiDockNodeFlags_AutoHideTabBar = 1 << 6, // // Tab bar will automatically hide when there is a single window in the dock node. - ImGuiDockNodeFlags_NoUndocking = 1 << 7, // // Disable undocking this node. - -#ifndef IMGUI_DISABLE_OBSOLETE_FUNCTIONS - ImGuiDockNodeFlags_NoSplit = ImGuiDockNodeFlags_NoDockingSplit, // Renamed in 1.90 - ImGuiDockNodeFlags_NoDockingInCentralNode = ImGuiDockNodeFlags_NoDockingOverCentralNode, // Renamed in 1.90 -#endif -}; - -// Flags for ImGui::BeginDragDropSource(), ImGui::AcceptDragDropPayload() -enum ImGuiDragDropFlags_ -{ - ImGuiDragDropFlags_None = 0, - // BeginDragDropSource() flags - ImGuiDragDropFlags_SourceNoPreviewTooltip = 1 << 0, // Disable preview tooltip. By default, a successful call to BeginDragDropSource opens a tooltip so you can display a preview or description of the source contents. This flag disables this behavior. - ImGuiDragDropFlags_SourceNoDisableHover = 1 << 1, // By default, when dragging we clear data so that IsItemHovered() will return false, to avoid subsequent user code submitting tooltips. This flag disables this behavior so you can still call IsItemHovered() on the source item. - ImGuiDragDropFlags_SourceNoHoldToOpenOthers = 1 << 2, // Disable the behavior that allows to open tree nodes and collapsing header by holding over them while dragging a source item. - ImGuiDragDropFlags_SourceAllowNullID = 1 << 3, // Allow items such as Text(), Image() that have no unique identifier to be used as drag source, by manufacturing a temporary identifier based on their window-relative position. This is extremely unusual within the dear imgui ecosystem and so we made it explicit. - ImGuiDragDropFlags_SourceExtern = 1 << 4, // External source (from outside of dear imgui), won't attempt to read current item/window info. Will always return true. Only one Extern source can be active simultaneously. - ImGuiDragDropFlags_SourceAutoExpirePayload = 1 << 5, // Automatically expire the payload if the source cease to be submitted (otherwise payloads are persisting while being dragged) - // AcceptDragDropPayload() flags - ImGuiDragDropFlags_AcceptBeforeDelivery = 1 << 10, // AcceptDragDropPayload() will returns true even before the mouse button is released. You can then call IsDelivery() to test if the payload needs to be delivered. - ImGuiDragDropFlags_AcceptNoDrawDefaultRect = 1 << 11, // Do not draw the default highlight rectangle when hovering over target. - ImGuiDragDropFlags_AcceptNoPreviewTooltip = 1 << 12, // Request hiding the BeginDragDropSource tooltip from the BeginDragDropTarget site. - ImGuiDragDropFlags_AcceptPeekOnly = ImGuiDragDropFlags_AcceptBeforeDelivery | ImGuiDragDropFlags_AcceptNoDrawDefaultRect, // For peeking ahead and inspecting the payload before delivery. -}; - -// Standard Drag and Drop payload types. You can define you own payload types using short strings. Types starting with '_' are defined by Dear ImGui. -#define IMGUI_PAYLOAD_TYPE_COLOR_3F "_COL3F" // float[3]: Standard type for colors, without alpha. User code may use this type. -#define IMGUI_PAYLOAD_TYPE_COLOR_4F "_COL4F" // float[4]: Standard type for colors. User code may use this type. - -// A primary data type -enum ImGuiDataType_ -{ - ImGuiDataType_S8, // signed char / char (with sensible compilers) - ImGuiDataType_U8, // unsigned char - ImGuiDataType_S16, // short - ImGuiDataType_U16, // unsigned short - ImGuiDataType_S32, // int - ImGuiDataType_U32, // unsigned int - ImGuiDataType_S64, // long long / __int64 - ImGuiDataType_U64, // unsigned long long / unsigned __int64 - ImGuiDataType_Float, // float - ImGuiDataType_Double, // double - ImGuiDataType_COUNT -}; - -// A cardinal direction -enum ImGuiDir_ -{ - ImGuiDir_None = -1, - ImGuiDir_Left = 0, - ImGuiDir_Right = 1, - ImGuiDir_Up = 2, - ImGuiDir_Down = 3, - ImGuiDir_COUNT -}; - -// A sorting direction -enum ImGuiSortDirection_ -{ - ImGuiSortDirection_None = 0, - ImGuiSortDirection_Ascending = 1, // Ascending = 0->9, A->Z etc. - ImGuiSortDirection_Descending = 2 // Descending = 9->0, Z->A etc. -}; - -// A key identifier (ImGuiKey_XXX or ImGuiMod_XXX value): can represent Keyboard, Mouse and Gamepad values. -// All our named keys are >= 512. Keys value 0 to 511 are left unused as legacy native/opaque key values (< 1.87). -// Since >= 1.89 we increased typing (went from int to enum), some legacy code may need a cast to ImGuiKey. -// Read details about the 1.87 and 1.89 transition : https://github.com/ocornut/imgui/issues/4921 -// Note that "Keys" related to physical keys and are not the same concept as input "Characters", the later are submitted via io.AddInputCharacter(). -enum ImGuiKey : int -{ - // Keyboard - ImGuiKey_None = 0, - ImGuiKey_Tab = 512, // == ImGuiKey_NamedKey_BEGIN - ImGuiKey_LeftArrow, - ImGuiKey_RightArrow, - ImGuiKey_UpArrow, - ImGuiKey_DownArrow, - ImGuiKey_PageUp, - ImGuiKey_PageDown, - ImGuiKey_Home, - ImGuiKey_End, - ImGuiKey_Insert, - ImGuiKey_Delete, - ImGuiKey_Backspace, - ImGuiKey_Space, - ImGuiKey_Enter, - ImGuiKey_Escape, - ImGuiKey_LeftCtrl, ImGuiKey_LeftShift, ImGuiKey_LeftAlt, ImGuiKey_LeftSuper, - ImGuiKey_RightCtrl, ImGuiKey_RightShift, ImGuiKey_RightAlt, ImGuiKey_RightSuper, - ImGuiKey_Menu, - ImGuiKey_0, ImGuiKey_1, ImGuiKey_2, ImGuiKey_3, ImGuiKey_4, ImGuiKey_5, ImGuiKey_6, ImGuiKey_7, ImGuiKey_8, ImGuiKey_9, - ImGuiKey_A, ImGuiKey_B, ImGuiKey_C, ImGuiKey_D, ImGuiKey_E, ImGuiKey_F, ImGuiKey_G, ImGuiKey_H, ImGuiKey_I, ImGuiKey_J, - ImGuiKey_K, ImGuiKey_L, ImGuiKey_M, ImGuiKey_N, ImGuiKey_O, ImGuiKey_P, ImGuiKey_Q, ImGuiKey_R, ImGuiKey_S, ImGuiKey_T, - ImGuiKey_U, ImGuiKey_V, ImGuiKey_W, ImGuiKey_X, ImGuiKey_Y, ImGuiKey_Z, - ImGuiKey_F1, ImGuiKey_F2, ImGuiKey_F3, ImGuiKey_F4, ImGuiKey_F5, ImGuiKey_F6, - ImGuiKey_F7, ImGuiKey_F8, ImGuiKey_F9, ImGuiKey_F10, ImGuiKey_F11, ImGuiKey_F12, - ImGuiKey_F13, ImGuiKey_F14, ImGuiKey_F15, ImGuiKey_F16, ImGuiKey_F17, ImGuiKey_F18, - ImGuiKey_F19, ImGuiKey_F20, ImGuiKey_F21, ImGuiKey_F22, ImGuiKey_F23, ImGuiKey_F24, - ImGuiKey_Apostrophe, // ' - ImGuiKey_Comma, // , - ImGuiKey_Minus, // - - ImGuiKey_Period, // . - ImGuiKey_Slash, // / - ImGuiKey_Semicolon, // ; - ImGuiKey_Equal, // = - ImGuiKey_LeftBracket, // [ - ImGuiKey_Backslash, // \ (this text inhibit multiline comment caused by backslash) - ImGuiKey_RightBracket, // ] - ImGuiKey_GraveAccent, // ` - ImGuiKey_CapsLock, - ImGuiKey_ScrollLock, - ImGuiKey_NumLock, - ImGuiKey_PrintScreen, - ImGuiKey_Pause, - ImGuiKey_Keypad0, ImGuiKey_Keypad1, ImGuiKey_Keypad2, ImGuiKey_Keypad3, ImGuiKey_Keypad4, - ImGuiKey_Keypad5, ImGuiKey_Keypad6, ImGuiKey_Keypad7, ImGuiKey_Keypad8, ImGuiKey_Keypad9, - ImGuiKey_KeypadDecimal, - ImGuiKey_KeypadDivide, - ImGuiKey_KeypadMultiply, - ImGuiKey_KeypadSubtract, - ImGuiKey_KeypadAdd, - ImGuiKey_KeypadEnter, - ImGuiKey_KeypadEqual, - ImGuiKey_AppBack, // Available on some keyboard/mouses. Often referred as "Browser Back" - ImGuiKey_AppForward, - - // Gamepad (some of those are analog values, 0.0f to 1.0f) // NAVIGATION ACTION - // (download controller mapping PNG/PSD at http://dearimgui.com/controls_sheets) - ImGuiKey_GamepadStart, // Menu (Xbox) + (Switch) Start/Options (PS) - ImGuiKey_GamepadBack, // View (Xbox) - (Switch) Share (PS) - ImGuiKey_GamepadFaceLeft, // X (Xbox) Y (Switch) Square (PS) // Tap: Toggle Menu. Hold: Windowing mode (Focus/Move/Resize windows) - ImGuiKey_GamepadFaceRight, // B (Xbox) A (Switch) Circle (PS) // Cancel / Close / Exit - ImGuiKey_GamepadFaceUp, // Y (Xbox) X (Switch) Triangle (PS) // Text Input / On-screen Keyboard - ImGuiKey_GamepadFaceDown, // A (Xbox) B (Switch) Cross (PS) // Activate / Open / Toggle / Tweak - ImGuiKey_GamepadDpadLeft, // D-pad Left // Move / Tweak / Resize Window (in Windowing mode) - ImGuiKey_GamepadDpadRight, // D-pad Right // Move / Tweak / Resize Window (in Windowing mode) - ImGuiKey_GamepadDpadUp, // D-pad Up // Move / Tweak / Resize Window (in Windowing mode) - ImGuiKey_GamepadDpadDown, // D-pad Down // Move / Tweak / Resize Window (in Windowing mode) - ImGuiKey_GamepadL1, // L Bumper (Xbox) L (Switch) L1 (PS) // Tweak Slower / Focus Previous (in Windowing mode) - ImGuiKey_GamepadR1, // R Bumper (Xbox) R (Switch) R1 (PS) // Tweak Faster / Focus Next (in Windowing mode) - ImGuiKey_GamepadL2, // L Trig. (Xbox) ZL (Switch) L2 (PS) [Analog] - ImGuiKey_GamepadR2, // R Trig. (Xbox) ZR (Switch) R2 (PS) [Analog] - ImGuiKey_GamepadL3, // L Stick (Xbox) L3 (Switch) L3 (PS) - ImGuiKey_GamepadR3, // R Stick (Xbox) R3 (Switch) R3 (PS) - ImGuiKey_GamepadLStickLeft, // [Analog] // Move Window (in Windowing mode) - ImGuiKey_GamepadLStickRight, // [Analog] // Move Window (in Windowing mode) - ImGuiKey_GamepadLStickUp, // [Analog] // Move Window (in Windowing mode) - ImGuiKey_GamepadLStickDown, // [Analog] // Move Window (in Windowing mode) - ImGuiKey_GamepadRStickLeft, // [Analog] - ImGuiKey_GamepadRStickRight, // [Analog] - ImGuiKey_GamepadRStickUp, // [Analog] - ImGuiKey_GamepadRStickDown, // [Analog] - - // Aliases: Mouse Buttons (auto-submitted from AddMouseButtonEvent() calls) - // - This is mirroring the data also written to io.MouseDown[], io.MouseWheel, in a format allowing them to be accessed via standard key API. - ImGuiKey_MouseLeft, ImGuiKey_MouseRight, ImGuiKey_MouseMiddle, ImGuiKey_MouseX1, ImGuiKey_MouseX2, ImGuiKey_MouseWheelX, ImGuiKey_MouseWheelY, - - // [Internal] Reserved for mod storage - ImGuiKey_ReservedForModCtrl, ImGuiKey_ReservedForModShift, ImGuiKey_ReservedForModAlt, ImGuiKey_ReservedForModSuper, - ImGuiKey_COUNT, - - // Keyboard Modifiers (explicitly submitted by backend via AddKeyEvent() calls) - // - This is mirroring the data also written to io.KeyCtrl, io.KeyShift, io.KeyAlt, io.KeySuper, in a format allowing - // them to be accessed via standard key API, allowing calls such as IsKeyPressed(), IsKeyReleased(), querying duration etc. - // - Code polling every key (e.g. an interface to detect a key press for input mapping) might want to ignore those - // and prefer using the real keys (e.g. ImGuiKey_LeftCtrl, ImGuiKey_RightCtrl instead of ImGuiMod_Ctrl). - // - In theory the value of keyboard modifiers should be roughly equivalent to a logical or of the equivalent left/right keys. - // In practice: it's complicated; mods are often provided from different sources. Keyboard layout, IME, sticky keys and - // backends tend to interfere and break that equivalence. The safer decision is to relay that ambiguity down to the end-user... - ImGuiMod_None = 0, - ImGuiMod_Ctrl = 1 << 12, // Ctrl - ImGuiMod_Shift = 1 << 13, // Shift - ImGuiMod_Alt = 1 << 14, // Option/Menu - ImGuiMod_Super = 1 << 15, // Cmd/Super/Windows - ImGuiMod_Shortcut = 1 << 11, // Alias for Ctrl (non-macOS) _or_ Super (macOS). - ImGuiMod_Mask_ = 0xF800, // 5-bits - - // [Internal] Prior to 1.87 we required user to fill io.KeysDown[512] using their own native index + the io.KeyMap[] array. - // We are ditching this method but keeping a legacy path for user code doing e.g. IsKeyPressed(MY_NATIVE_KEY_CODE) - // If you need to iterate all keys (for e.g. an input mapper) you may use ImGuiKey_NamedKey_BEGIN..ImGuiKey_NamedKey_END. - ImGuiKey_NamedKey_BEGIN = 512, - ImGuiKey_NamedKey_END = ImGuiKey_COUNT, - ImGuiKey_NamedKey_COUNT = ImGuiKey_NamedKey_END - ImGuiKey_NamedKey_BEGIN, -#ifdef IMGUI_DISABLE_OBSOLETE_KEYIO - ImGuiKey_KeysData_SIZE = ImGuiKey_NamedKey_COUNT, // Size of KeysData[]: only hold named keys - ImGuiKey_KeysData_OFFSET = ImGuiKey_NamedKey_BEGIN, // Accesses to io.KeysData[] must use (key - ImGuiKey_KeysData_OFFSET) index. -#else - ImGuiKey_KeysData_SIZE = ImGuiKey_COUNT, // Size of KeysData[]: hold legacy 0..512 keycodes + named keys - ImGuiKey_KeysData_OFFSET = 0, // Accesses to io.KeysData[] must use (key - ImGuiKey_KeysData_OFFSET) index. -#endif - -#ifndef IMGUI_DISABLE_OBSOLETE_FUNCTIONS - ImGuiKey_ModCtrl = ImGuiMod_Ctrl, ImGuiKey_ModShift = ImGuiMod_Shift, ImGuiKey_ModAlt = ImGuiMod_Alt, ImGuiKey_ModSuper = ImGuiMod_Super, // Renamed in 1.89 - ImGuiKey_KeyPadEnter = ImGuiKey_KeypadEnter, // Renamed in 1.87 -#endif -}; - -#ifndef IMGUI_DISABLE_OBSOLETE_KEYIO -// OBSOLETED in 1.88 (from July 2022): ImGuiNavInput and io.NavInputs[]. -// Official backends between 1.60 and 1.86: will keep working and feed gamepad inputs as long as IMGUI_DISABLE_OBSOLETE_KEYIO is not set. -// Custom backends: feed gamepad inputs via io.AddKeyEvent() and ImGuiKey_GamepadXXX enums. -enum ImGuiNavInput -{ - ImGuiNavInput_Activate, ImGuiNavInput_Cancel, ImGuiNavInput_Input, ImGuiNavInput_Menu, ImGuiNavInput_DpadLeft, ImGuiNavInput_DpadRight, ImGuiNavInput_DpadUp, ImGuiNavInput_DpadDown, - ImGuiNavInput_LStickLeft, ImGuiNavInput_LStickRight, ImGuiNavInput_LStickUp, ImGuiNavInput_LStickDown, ImGuiNavInput_FocusPrev, ImGuiNavInput_FocusNext, ImGuiNavInput_TweakSlow, ImGuiNavInput_TweakFast, - ImGuiNavInput_COUNT, -}; -#endif - -// Configuration flags stored in io.ConfigFlags. Set by user/application. -enum ImGuiConfigFlags_ -{ - ImGuiConfigFlags_None = 0, - ImGuiConfigFlags_NavEnableKeyboard = 1 << 0, // Master keyboard navigation enable flag. Enable full Tabbing + directional arrows + space/enter to activate. - ImGuiConfigFlags_NavEnableGamepad = 1 << 1, // Master gamepad navigation enable flag. Backend also needs to set ImGuiBackendFlags_HasGamepad. - ImGuiConfigFlags_NavEnableSetMousePos = 1 << 2, // Instruct navigation to move the mouse cursor. May be useful on TV/console systems where moving a virtual mouse is awkward. Will update io.MousePos and set io.WantSetMousePos=true. If enabled you MUST honor io.WantSetMousePos requests in your backend, otherwise ImGui will react as if the mouse is jumping around back and forth. - ImGuiConfigFlags_NavNoCaptureKeyboard = 1 << 3, // Instruct navigation to not set the io.WantCaptureKeyboard flag when io.NavActive is set. - ImGuiConfigFlags_NoMouse = 1 << 4, // Instruct imgui to clear mouse position/buttons in NewFrame(). This allows ignoring the mouse information set by the backend. - ImGuiConfigFlags_NoMouseCursorChange = 1 << 5, // Instruct backend to not alter mouse cursor shape and visibility. Use if the backend cursor changes are interfering with yours and you don't want to use SetMouseCursor() to change mouse cursor. You may want to honor requests from imgui by reading GetMouseCursor() yourself instead. - - // [BETA] Docking - ImGuiConfigFlags_DockingEnable = 1 << 6, // Docking enable flags. - - // [BETA] Viewports - // When using viewports it is recommended that your default value for ImGuiCol_WindowBg is opaque (Alpha=1.0) so transition to a viewport won't be noticeable. - ImGuiConfigFlags_ViewportsEnable = 1 << 10, // Viewport enable flags (require both ImGuiBackendFlags_PlatformHasViewports + ImGuiBackendFlags_RendererHasViewports set by the respective backends) - ImGuiConfigFlags_DpiEnableScaleViewports= 1 << 14, // [BETA: Don't use] FIXME-DPI: Reposition and resize imgui windows when the DpiScale of a viewport changed (mostly useful for the main viewport hosting other window). Note that resizing the main window itself is up to your application. - ImGuiConfigFlags_DpiEnableScaleFonts = 1 << 15, // [BETA: Don't use] FIXME-DPI: Request bitmap-scaled fonts to match DpiScale. This is a very low-quality workaround. The correct way to handle DPI is _currently_ to replace the atlas and/or fonts in the Platform_OnChangedViewport callback, but this is all early work in progress. - - // User storage (to allow your backend/engine to communicate to code that may be shared between multiple projects. Those flags are NOT used by core Dear ImGui) - ImGuiConfigFlags_IsSRGB = 1 << 20, // Application is SRGB-aware. - ImGuiConfigFlags_IsTouchScreen = 1 << 21, // Application is using a touch screen instead of a mouse. -}; - -// Backend capabilities flags stored in io.BackendFlags. Set by imgui_impl_xxx or custom backend. -enum ImGuiBackendFlags_ -{ - ImGuiBackendFlags_None = 0, - ImGuiBackendFlags_HasGamepad = 1 << 0, // Backend Platform supports gamepad and currently has one connected. - ImGuiBackendFlags_HasMouseCursors = 1 << 1, // Backend Platform supports honoring GetMouseCursor() value to change the OS cursor shape. - ImGuiBackendFlags_HasSetMousePos = 1 << 2, // Backend Platform supports io.WantSetMousePos requests to reposition the OS mouse position (only used if ImGuiConfigFlags_NavEnableSetMousePos is set). - ImGuiBackendFlags_RendererHasVtxOffset = 1 << 3, // Backend Renderer supports ImDrawCmd::VtxOffset. This enables output of large meshes (64K+ vertices) while still using 16-bit indices. - - // [BETA] Viewports - ImGuiBackendFlags_PlatformHasViewports = 1 << 10, // Backend Platform supports multiple viewports. - ImGuiBackendFlags_HasMouseHoveredViewport=1 << 11, // Backend Platform supports calling io.AddMouseViewportEvent() with the viewport under the mouse. IF POSSIBLE, ignore viewports with the ImGuiViewportFlags_NoInputs flag (Win32 backend, GLFW 3.30+ backend can do this, SDL backend cannot). If this cannot be done, Dear ImGui needs to use a flawed heuristic to find the viewport under. - ImGuiBackendFlags_RendererHasViewports = 1 << 12, // Backend Renderer supports multiple viewports. -}; - -// Enumeration for PushStyleColor() / PopStyleColor() -enum ImGuiCol_ -{ - ImGuiCol_Text, - ImGuiCol_TextDisabled, - ImGuiCol_WindowBg, // Background of normal windows - ImGuiCol_ChildBg, // Background of child windows - ImGuiCol_PopupBg, // Background of popups, menus, tooltips windows - ImGuiCol_Border, - ImGuiCol_BorderShadow, - ImGuiCol_FrameBg, // Background of checkbox, radio button, plot, slider, text input - ImGuiCol_FrameBgHovered, - ImGuiCol_FrameBgActive, - ImGuiCol_TitleBg, - ImGuiCol_TitleBgActive, - ImGuiCol_TitleBgCollapsed, - ImGuiCol_MenuBarBg, - ImGuiCol_ScrollbarBg, - ImGuiCol_ScrollbarGrab, - ImGuiCol_ScrollbarGrabHovered, - ImGuiCol_ScrollbarGrabActive, - ImGuiCol_CheckMark, - ImGuiCol_SliderGrab, - ImGuiCol_SliderGrabActive, - ImGuiCol_Button, - ImGuiCol_ButtonHovered, - ImGuiCol_ButtonActive, - ImGuiCol_Header, // Header* colors are used for CollapsingHeader, TreeNode, Selectable, MenuItem - ImGuiCol_HeaderHovered, - ImGuiCol_HeaderActive, - ImGuiCol_Separator, - ImGuiCol_SeparatorHovered, - ImGuiCol_SeparatorActive, - ImGuiCol_ResizeGrip, // Resize grip in lower-right and lower-left corners of windows. - ImGuiCol_ResizeGripHovered, - ImGuiCol_ResizeGripActive, - ImGuiCol_Tab, // TabItem in a TabBar - ImGuiCol_TabHovered, - ImGuiCol_TabActive, - ImGuiCol_TabUnfocused, - ImGuiCol_TabUnfocusedActive, - ImGuiCol_DockingPreview, // Preview overlay color when about to docking something - ImGuiCol_DockingEmptyBg, // Background color for empty node (e.g. CentralNode with no window docked into it) - ImGuiCol_PlotLines, - ImGuiCol_PlotLinesHovered, - ImGuiCol_PlotHistogram, - ImGuiCol_PlotHistogramHovered, - ImGuiCol_TableHeaderBg, // Table header background - ImGuiCol_TableBorderStrong, // Table outer and header borders (prefer using Alpha=1.0 here) - ImGuiCol_TableBorderLight, // Table inner borders (prefer using Alpha=1.0 here) - ImGuiCol_TableRowBg, // Table row background (even rows) - ImGuiCol_TableRowBgAlt, // Table row background (odd rows) - ImGuiCol_TextSelectedBg, - ImGuiCol_DragDropTarget, // Rectangle highlighting a drop target - ImGuiCol_NavHighlight, // Gamepad/keyboard: current highlighted item - ImGuiCol_NavWindowingHighlight, // Highlight window when using CTRL+TAB - ImGuiCol_NavWindowingDimBg, // Darken/colorize entire screen behind the CTRL+TAB window list, when active - ImGuiCol_ModalWindowDimBg, // Darken/colorize entire screen behind a modal window, when one is active - ImGuiCol_COUNT -}; - -// Enumeration for PushStyleVar() / PopStyleVar() to temporarily modify the ImGuiStyle structure. -// - The enum only refers to fields of ImGuiStyle which makes sense to be pushed/popped inside UI code. -// During initialization or between frames, feel free to just poke into ImGuiStyle directly. -// - Tip: Use your programming IDE navigation facilities on the names in the _second column_ below to find the actual members and their description. -// In Visual Studio IDE: CTRL+comma ("Edit.GoToAll") can follow symbols in comments, whereas CTRL+F12 ("Edit.GoToImplementation") cannot. -// With Visual Assist installed: ALT+G ("VAssistX.GoToImplementation") can also follow symbols in comments. -// - When changing this enum, you need to update the associated internal table GStyleVarInfo[] accordingly. This is where we link enum values to members offset/type. -enum ImGuiStyleVar_ -{ - // Enum name --------------------- // Member in ImGuiStyle structure (see ImGuiStyle for descriptions) - ImGuiStyleVar_Alpha, // float Alpha - ImGuiStyleVar_DisabledAlpha, // float DisabledAlpha - ImGuiStyleVar_WindowPadding, // ImVec2 WindowPadding - ImGuiStyleVar_WindowRounding, // float WindowRounding - ImGuiStyleVar_WindowBorderSize, // float WindowBorderSize - ImGuiStyleVar_WindowMinSize, // ImVec2 WindowMinSize - ImGuiStyleVar_WindowTitleAlign, // ImVec2 WindowTitleAlign - ImGuiStyleVar_ChildRounding, // float ChildRounding - ImGuiStyleVar_ChildBorderSize, // float ChildBorderSize - ImGuiStyleVar_PopupRounding, // float PopupRounding - ImGuiStyleVar_PopupBorderSize, // float PopupBorderSize - ImGuiStyleVar_FramePadding, // ImVec2 FramePadding - ImGuiStyleVar_FrameRounding, // float FrameRounding - ImGuiStyleVar_FrameBorderSize, // float FrameBorderSize - ImGuiStyleVar_ItemSpacing, // ImVec2 ItemSpacing - ImGuiStyleVar_ItemInnerSpacing, // ImVec2 ItemInnerSpacing - ImGuiStyleVar_IndentSpacing, // float IndentSpacing - ImGuiStyleVar_CellPadding, // ImVec2 CellPadding - ImGuiStyleVar_ScrollbarSize, // float ScrollbarSize - ImGuiStyleVar_ScrollbarRounding, // float ScrollbarRounding - ImGuiStyleVar_GrabMinSize, // float GrabMinSize - ImGuiStyleVar_GrabRounding, // float GrabRounding - ImGuiStyleVar_TabRounding, // float TabRounding - ImGuiStyleVar_TabBarBorderSize, // float TabBarBorderSize - ImGuiStyleVar_ButtonTextAlign, // ImVec2 ButtonTextAlign - ImGuiStyleVar_SelectableTextAlign, // ImVec2 SelectableTextAlign - ImGuiStyleVar_SeparatorTextBorderSize,// float SeparatorTextBorderSize - ImGuiStyleVar_SeparatorTextAlign, // ImVec2 SeparatorTextAlign - ImGuiStyleVar_SeparatorTextPadding,// ImVec2 SeparatorTextPadding - ImGuiStyleVar_DockingSeparatorSize,// float DockingSeparatorSize - ImGuiStyleVar_COUNT -}; - -// Flags for InvisibleButton() [extended in imgui_internal.h] -enum ImGuiButtonFlags_ -{ - ImGuiButtonFlags_None = 0, - ImGuiButtonFlags_MouseButtonLeft = 1 << 0, // React on left mouse button (default) - ImGuiButtonFlags_MouseButtonRight = 1 << 1, // React on right mouse button - ImGuiButtonFlags_MouseButtonMiddle = 1 << 2, // React on center mouse button - - // [Internal] - ImGuiButtonFlags_MouseButtonMask_ = ImGuiButtonFlags_MouseButtonLeft | ImGuiButtonFlags_MouseButtonRight | ImGuiButtonFlags_MouseButtonMiddle, - ImGuiButtonFlags_MouseButtonDefault_ = ImGuiButtonFlags_MouseButtonLeft, -}; - -// Flags for ColorEdit3() / ColorEdit4() / ColorPicker3() / ColorPicker4() / ColorButton() -enum ImGuiColorEditFlags_ -{ - ImGuiColorEditFlags_None = 0, - ImGuiColorEditFlags_NoAlpha = 1 << 1, // // ColorEdit, ColorPicker, ColorButton: ignore Alpha component (will only read 3 components from the input pointer). - ImGuiColorEditFlags_NoPicker = 1 << 2, // // ColorEdit: disable picker when clicking on color square. - ImGuiColorEditFlags_NoOptions = 1 << 3, // // ColorEdit: disable toggling options menu when right-clicking on inputs/small preview. - ImGuiColorEditFlags_NoSmallPreview = 1 << 4, // // ColorEdit, ColorPicker: disable color square preview next to the inputs. (e.g. to show only the inputs) - ImGuiColorEditFlags_NoInputs = 1 << 5, // // ColorEdit, ColorPicker: disable inputs sliders/text widgets (e.g. to show only the small preview color square). - ImGuiColorEditFlags_NoTooltip = 1 << 6, // // ColorEdit, ColorPicker, ColorButton: disable tooltip when hovering the preview. - ImGuiColorEditFlags_NoLabel = 1 << 7, // // ColorEdit, ColorPicker: disable display of inline text label (the label is still forwarded to the tooltip and picker). - ImGuiColorEditFlags_NoSidePreview = 1 << 8, // // ColorPicker: disable bigger color preview on right side of the picker, use small color square preview instead. - ImGuiColorEditFlags_NoDragDrop = 1 << 9, // // ColorEdit: disable drag and drop target. ColorButton: disable drag and drop source. - ImGuiColorEditFlags_NoBorder = 1 << 10, // // ColorButton: disable border (which is enforced by default) - - // User Options (right-click on widget to change some of them). - ImGuiColorEditFlags_AlphaBar = 1 << 16, // // ColorEdit, ColorPicker: show vertical alpha bar/gradient in picker. - ImGuiColorEditFlags_AlphaPreview = 1 << 17, // // ColorEdit, ColorPicker, ColorButton: display preview as a transparent color over a checkerboard, instead of opaque. - ImGuiColorEditFlags_AlphaPreviewHalf= 1 << 18, // // ColorEdit, ColorPicker, ColorButton: display half opaque / half checkerboard, instead of opaque. - ImGuiColorEditFlags_HDR = 1 << 19, // // (WIP) ColorEdit: Currently only disable 0.0f..1.0f limits in RGBA edition (note: you probably want to use ImGuiColorEditFlags_Float flag as well). - ImGuiColorEditFlags_DisplayRGB = 1 << 20, // [Display] // ColorEdit: override _display_ type among RGB/HSV/Hex. ColorPicker: select any combination using one or more of RGB/HSV/Hex. - ImGuiColorEditFlags_DisplayHSV = 1 << 21, // [Display] // " - ImGuiColorEditFlags_DisplayHex = 1 << 22, // [Display] // " - ImGuiColorEditFlags_Uint8 = 1 << 23, // [DataType] // ColorEdit, ColorPicker, ColorButton: _display_ values formatted as 0..255. - ImGuiColorEditFlags_Float = 1 << 24, // [DataType] // ColorEdit, ColorPicker, ColorButton: _display_ values formatted as 0.0f..1.0f floats instead of 0..255 integers. No round-trip of value via integers. - ImGuiColorEditFlags_PickerHueBar = 1 << 25, // [Picker] // ColorPicker: bar for Hue, rectangle for Sat/Value. - ImGuiColorEditFlags_PickerHueWheel = 1 << 26, // [Picker] // ColorPicker: wheel for Hue, triangle for Sat/Value. - ImGuiColorEditFlags_InputRGB = 1 << 27, // [Input] // ColorEdit, ColorPicker: input and output data in RGB format. - ImGuiColorEditFlags_InputHSV = 1 << 28, // [Input] // ColorEdit, ColorPicker: input and output data in HSV format. - - // Defaults Options. You can set application defaults using SetColorEditOptions(). The intent is that you probably don't want to - // override them in most of your calls. Let the user choose via the option menu and/or call SetColorEditOptions() once during startup. - ImGuiColorEditFlags_DefaultOptions_ = ImGuiColorEditFlags_Uint8 | ImGuiColorEditFlags_DisplayRGB | ImGuiColorEditFlags_InputRGB | ImGuiColorEditFlags_PickerHueBar, - - // [Internal] Masks - ImGuiColorEditFlags_DisplayMask_ = ImGuiColorEditFlags_DisplayRGB | ImGuiColorEditFlags_DisplayHSV | ImGuiColorEditFlags_DisplayHex, - ImGuiColorEditFlags_DataTypeMask_ = ImGuiColorEditFlags_Uint8 | ImGuiColorEditFlags_Float, - ImGuiColorEditFlags_PickerMask_ = ImGuiColorEditFlags_PickerHueWheel | ImGuiColorEditFlags_PickerHueBar, - ImGuiColorEditFlags_InputMask_ = ImGuiColorEditFlags_InputRGB | ImGuiColorEditFlags_InputHSV, - - // Obsolete names - //ImGuiColorEditFlags_RGB = ImGuiColorEditFlags_DisplayRGB, ImGuiColorEditFlags_HSV = ImGuiColorEditFlags_DisplayHSV, ImGuiColorEditFlags_HEX = ImGuiColorEditFlags_DisplayHex // [renamed in 1.69] -}; - -// Flags for DragFloat(), DragInt(), SliderFloat(), SliderInt() etc. -// We use the same sets of flags for DragXXX() and SliderXXX() functions as the features are the same and it makes it easier to swap them. -// (Those are per-item flags. There are shared flags in ImGuiIO: io.ConfigDragClickToInputText) -enum ImGuiSliderFlags_ -{ - ImGuiSliderFlags_None = 0, - ImGuiSliderFlags_AlwaysClamp = 1 << 4, // Clamp value to min/max bounds when input manually with CTRL+Click. By default CTRL+Click allows going out of bounds. - ImGuiSliderFlags_Logarithmic = 1 << 5, // Make the widget logarithmic (linear otherwise). Consider using ImGuiSliderFlags_NoRoundToFormat with this if using a format-string with small amount of digits. - ImGuiSliderFlags_NoRoundToFormat = 1 << 6, // Disable rounding underlying value to match precision of the display format string (e.g. %.3f values are rounded to those 3 digits) - ImGuiSliderFlags_NoInput = 1 << 7, // Disable CTRL+Click or Enter key allowing to input text directly into the widget - ImGuiSliderFlags_InvalidMask_ = 0x7000000F, // [Internal] We treat using those bits as being potentially a 'float power' argument from the previous API that has got miscast to this enum, and will trigger an assert if needed. - - // Obsolete names - //ImGuiSliderFlags_ClampOnInput = ImGuiSliderFlags_AlwaysClamp, // [renamed in 1.79] -}; - -// Identify a mouse button. -// Those values are guaranteed to be stable and we frequently use 0/1 directly. Named enums provided for convenience. -enum ImGuiMouseButton_ -{ - ImGuiMouseButton_Left = 0, - ImGuiMouseButton_Right = 1, - ImGuiMouseButton_Middle = 2, - ImGuiMouseButton_COUNT = 5 -}; - -// Enumeration for GetMouseCursor() -// User code may request backend to display given cursor by calling SetMouseCursor(), which is why we have some cursors that are marked unused here -enum ImGuiMouseCursor_ -{ - ImGuiMouseCursor_None = -1, - ImGuiMouseCursor_Arrow = 0, - ImGuiMouseCursor_TextInput, // When hovering over InputText, etc. - ImGuiMouseCursor_ResizeAll, // (Unused by Dear ImGui functions) - ImGuiMouseCursor_ResizeNS, // When hovering over a horizontal border - ImGuiMouseCursor_ResizeEW, // When hovering over a vertical border or a column - ImGuiMouseCursor_ResizeNESW, // When hovering over the bottom-left corner of a window - ImGuiMouseCursor_ResizeNWSE, // When hovering over the bottom-right corner of a window - ImGuiMouseCursor_Hand, // (Unused by Dear ImGui functions. Use for e.g. hyperlinks) - ImGuiMouseCursor_NotAllowed, // When hovering something with disallowed interaction. Usually a crossed circle. - ImGuiMouseCursor_COUNT -}; - -// Enumeration for AddMouseSourceEvent() actual source of Mouse Input data. -// Historically we use "Mouse" terminology everywhere to indicate pointer data, e.g. MousePos, IsMousePressed(), io.AddMousePosEvent() -// But that "Mouse" data can come from different source which occasionally may be useful for application to know about. -// You can submit a change of pointer type using io.AddMouseSourceEvent(). -enum ImGuiMouseSource : int -{ - ImGuiMouseSource_Mouse = 0, // Input is coming from an actual mouse. - ImGuiMouseSource_TouchScreen, // Input is coming from a touch screen (no hovering prior to initial press, less precise initial press aiming, dual-axis wheeling possible). - ImGuiMouseSource_Pen, // Input is coming from a pressure/magnetic pen (often used in conjunction with high-sampling rates). - ImGuiMouseSource_COUNT -}; - -// Enumeration for ImGui::SetWindow***(), SetNextWindow***(), SetNextItem***() functions -// Represent a condition. -// Important: Treat as a regular enum! Do NOT combine multiple values using binary operators! All the functions above treat 0 as a shortcut to ImGuiCond_Always. -enum ImGuiCond_ -{ - ImGuiCond_None = 0, // No condition (always set the variable), same as _Always - ImGuiCond_Always = 1 << 0, // No condition (always set the variable), same as _None - ImGuiCond_Once = 1 << 1, // Set the variable once per runtime session (only the first call will succeed) - ImGuiCond_FirstUseEver = 1 << 2, // Set the variable if the object/window has no persistently saved data (no entry in .ini file) - ImGuiCond_Appearing = 1 << 3, // Set the variable if the object/window is appearing after being hidden/inactive (or the first time) -}; - -//----------------------------------------------------------------------------- -// [SECTION] Helpers: Memory allocations macros, ImVector<> -//----------------------------------------------------------------------------- - -//----------------------------------------------------------------------------- -// IM_MALLOC(), IM_FREE(), IM_NEW(), IM_PLACEMENT_NEW(), IM_DELETE() -// We call C++ constructor on own allocated memory via the placement "new(ptr) Type()" syntax. -// Defining a custom placement new() with a custom parameter allows us to bypass including which on some platforms complains when user has disabled exceptions. -//----------------------------------------------------------------------------- - -struct ImNewWrapper {}; -inline void* operator new(size_t, ImNewWrapper, void* ptr) { return ptr; } -inline void operator delete(void*, ImNewWrapper, void*) {} // This is only required so we can use the symmetrical new() -#define IM_ALLOC(_SIZE) ImGui::MemAlloc(_SIZE) -#define IM_FREE(_PTR) ImGui::MemFree(_PTR) -#define IM_PLACEMENT_NEW(_PTR) new(ImNewWrapper(), _PTR) -#define IM_NEW(_TYPE) new(ImNewWrapper(), ImGui::MemAlloc(sizeof(_TYPE))) _TYPE -template void IM_DELETE(T* p) { if (p) { p->~T(); ImGui::MemFree(p); } } - -//----------------------------------------------------------------------------- -// ImVector<> -// Lightweight std::vector<>-like class to avoid dragging dependencies (also, some implementations of STL with debug enabled are absurdly slow, we bypass it so our code runs fast in debug). -//----------------------------------------------------------------------------- -// - You generally do NOT need to care or use this ever. But we need to make it available in imgui.h because some of our public structures are relying on it. -// - We use std-like naming convention here, which is a little unusual for this codebase. -// - Important: clear() frees memory, resize(0) keep the allocated buffer. We use resize(0) a lot to intentionally recycle allocated buffers across frames and amortize our costs. -// - Important: our implementation does NOT call C++ constructors/destructors, we treat everything as raw data! This is intentional but be extra mindful of that, -// Do NOT use this class as a std::vector replacement in your own code! Many of the structures used by dear imgui can be safely initialized by a zero-memset. -//----------------------------------------------------------------------------- - -IM_MSVC_RUNTIME_CHECKS_OFF -template -struct ImVector -{ - int Size; - int Capacity; - T* Data; - - // Provide standard typedefs but we don't use them ourselves. - typedef T value_type; - typedef value_type* iterator; - typedef const value_type* const_iterator; - - // Constructors, destructor - inline ImVector() { Size = Capacity = 0; Data = NULL; } - inline ImVector(const ImVector& src) { Size = Capacity = 0; Data = NULL; operator=(src); } - inline ImVector& operator=(const ImVector& src) { clear(); resize(src.Size); if (src.Data) memcpy(Data, src.Data, (size_t)Size * sizeof(T)); return *this; } - inline ~ImVector() { if (Data) IM_FREE(Data); } // Important: does not destruct anything - - inline void clear() { if (Data) { Size = Capacity = 0; IM_FREE(Data); Data = NULL; } } // Important: does not destruct anything - inline void clear_delete() { for (int n = 0; n < Size; n++) IM_DELETE(Data[n]); clear(); } // Important: never called automatically! always explicit. - inline void clear_destruct() { for (int n = 0; n < Size; n++) Data[n].~T(); clear(); } // Important: never called automatically! always explicit. - - inline bool empty() const { return Size == 0; } - inline int size() const { return Size; } - inline int size_in_bytes() const { return Size * (int)sizeof(T); } - inline int max_size() const { return 0x7FFFFFFF / (int)sizeof(T); } - inline int capacity() const { return Capacity; } - inline T& operator[](int i) { IM_ASSERT(i >= 0 && i < Size); return Data[i]; } - inline const T& operator[](int i) const { IM_ASSERT(i >= 0 && i < Size); return Data[i]; } - - inline T* begin() { return Data; } - inline const T* begin() const { return Data; } - inline T* end() { return Data + Size; } - inline const T* end() const { return Data + Size; } - inline T& front() { IM_ASSERT(Size > 0); return Data[0]; } - inline const T& front() const { IM_ASSERT(Size > 0); return Data[0]; } - inline T& back() { IM_ASSERT(Size > 0); return Data[Size - 1]; } - inline const T& back() const { IM_ASSERT(Size > 0); return Data[Size - 1]; } - inline void swap(ImVector& rhs) { int rhs_size = rhs.Size; rhs.Size = Size; Size = rhs_size; int rhs_cap = rhs.Capacity; rhs.Capacity = Capacity; Capacity = rhs_cap; T* rhs_data = rhs.Data; rhs.Data = Data; Data = rhs_data; } - - inline int _grow_capacity(int sz) const { int new_capacity = Capacity ? (Capacity + Capacity / 2) : 8; return new_capacity > sz ? new_capacity : sz; } - inline void resize(int new_size) { if (new_size > Capacity) reserve(_grow_capacity(new_size)); Size = new_size; } - inline void resize(int new_size, const T& v) { if (new_size > Capacity) reserve(_grow_capacity(new_size)); if (new_size > Size) for (int n = Size; n < new_size; n++) memcpy(&Data[n], &v, sizeof(v)); Size = new_size; } - inline void shrink(int new_size) { IM_ASSERT(new_size <= Size); Size = new_size; } // Resize a vector to a smaller size, guaranteed not to cause a reallocation - inline void reserve(int new_capacity) { if (new_capacity <= Capacity) return; T* new_data = (T*)IM_ALLOC((size_t)new_capacity * sizeof(T)); if (Data) { memcpy(new_data, Data, (size_t)Size * sizeof(T)); IM_FREE(Data); } Data = new_data; Capacity = new_capacity; } - inline void reserve_discard(int new_capacity) { if (new_capacity <= Capacity) return; if (Data) IM_FREE(Data); Data = (T*)IM_ALLOC((size_t)new_capacity * sizeof(T)); Capacity = new_capacity; } - - // NB: It is illegal to call push_back/push_front/insert with a reference pointing inside the ImVector data itself! e.g. v.push_back(v[10]) is forbidden. - inline void push_back(const T& v) { if (Size == Capacity) reserve(_grow_capacity(Size + 1)); memcpy(&Data[Size], &v, sizeof(v)); Size++; } - inline void pop_back() { IM_ASSERT(Size > 0); Size--; } - inline void push_front(const T& v) { if (Size == 0) push_back(v); else insert(Data, v); } - inline T* erase(const T* it) { IM_ASSERT(it >= Data && it < Data + Size); const ptrdiff_t off = it - Data; memmove(Data + off, Data + off + 1, ((size_t)Size - (size_t)off - 1) * sizeof(T)); Size--; return Data + off; } - inline T* erase(const T* it, const T* it_last){ IM_ASSERT(it >= Data && it < Data + Size && it_last >= it && it_last <= Data + Size); const ptrdiff_t count = it_last - it; const ptrdiff_t off = it - Data; memmove(Data + off, Data + off + count, ((size_t)Size - (size_t)off - (size_t)count) * sizeof(T)); Size -= (int)count; return Data + off; } - inline T* erase_unsorted(const T* it) { IM_ASSERT(it >= Data && it < Data + Size); const ptrdiff_t off = it - Data; if (it < Data + Size - 1) memcpy(Data + off, Data + Size - 1, sizeof(T)); Size--; return Data + off; } - inline T* insert(const T* it, const T& v) { IM_ASSERT(it >= Data && it <= Data + Size); const ptrdiff_t off = it - Data; if (Size == Capacity) reserve(_grow_capacity(Size + 1)); if (off < (int)Size) memmove(Data + off + 1, Data + off, ((size_t)Size - (size_t)off) * sizeof(T)); memcpy(&Data[off], &v, sizeof(v)); Size++; return Data + off; } - inline bool contains(const T& v) const { const T* data = Data; const T* data_end = Data + Size; while (data < data_end) if (*data++ == v) return true; return false; } - inline T* find(const T& v) { T* data = Data; const T* data_end = Data + Size; while (data < data_end) if (*data == v) break; else ++data; return data; } - inline const T* find(const T& v) const { const T* data = Data; const T* data_end = Data + Size; while (data < data_end) if (*data == v) break; else ++data; return data; } - inline int find_index(const T& v) const { const T* data_end = Data + Size; const T* it = find(v); if (it == data_end) return -1; const ptrdiff_t off = it - Data; return (int)off; } - inline bool find_erase(const T& v) { const T* it = find(v); if (it < Data + Size) { erase(it); return true; } return false; } - inline bool find_erase_unsorted(const T& v) { const T* it = find(v); if (it < Data + Size) { erase_unsorted(it); return true; } return false; } - inline int index_from_ptr(const T* it) const { IM_ASSERT(it >= Data && it < Data + Size); const ptrdiff_t off = it - Data; return (int)off; } -}; -IM_MSVC_RUNTIME_CHECKS_RESTORE - -//----------------------------------------------------------------------------- -// [SECTION] ImGuiStyle -//----------------------------------------------------------------------------- -// You may modify the ImGui::GetStyle() main instance during initialization and before NewFrame(). -// During the frame, use ImGui::PushStyleVar(ImGuiStyleVar_XXXX)/PopStyleVar() to alter the main style values, -// and ImGui::PushStyleColor(ImGuiCol_XXX)/PopStyleColor() for colors. -//----------------------------------------------------------------------------- - -struct ImGuiStyle -{ - float Alpha; // Global alpha applies to everything in Dear ImGui. - float DisabledAlpha; // Additional alpha multiplier applied by BeginDisabled(). Multiply over current value of Alpha. - ImVec2 WindowPadding; // Padding within a window. - float WindowRounding; // Radius of window corners rounding. Set to 0.0f to have rectangular windows. Large values tend to lead to variety of artifacts and are not recommended. - float WindowBorderSize; // Thickness of border around windows. Generally set to 0.0f or 1.0f. (Other values are not well tested and more CPU/GPU costly). - ImVec2 WindowMinSize; // Minimum window size. This is a global setting. If you want to constrain individual windows, use SetNextWindowSizeConstraints(). - ImVec2 WindowTitleAlign; // Alignment for title bar text. Defaults to (0.0f,0.5f) for left-aligned,vertically centered. - ImGuiDir WindowMenuButtonPosition; // Side of the collapsing/docking button in the title bar (None/Left/Right). Defaults to ImGuiDir_Left. - float ChildRounding; // Radius of child window corners rounding. Set to 0.0f to have rectangular windows. - float ChildBorderSize; // Thickness of border around child windows. Generally set to 0.0f or 1.0f. (Other values are not well tested and more CPU/GPU costly). - float PopupRounding; // Radius of popup window corners rounding. (Note that tooltip windows use WindowRounding) - float PopupBorderSize; // Thickness of border around popup/tooltip windows. Generally set to 0.0f or 1.0f. (Other values are not well tested and more CPU/GPU costly). - ImVec2 FramePadding; // Padding within a framed rectangle (used by most widgets). - float FrameRounding; // Radius of frame corners rounding. Set to 0.0f to have rectangular frame (used by most widgets). - float FrameBorderSize; // Thickness of border around frames. Generally set to 0.0f or 1.0f. (Other values are not well tested and more CPU/GPU costly). - ImVec2 ItemSpacing; // Horizontal and vertical spacing between widgets/lines. - ImVec2 ItemInnerSpacing; // Horizontal and vertical spacing between within elements of a composed widget (e.g. a slider and its label). - ImVec2 CellPadding; // Padding within a table cell. CellPadding.y may be altered between different rows. - ImVec2 TouchExtraPadding; // Expand reactive bounding box for touch-based system where touch position is not accurate enough. Unfortunately we don't sort widgets so priority on overlap will always be given to the first widget. So don't grow this too much! - float IndentSpacing; // Horizontal indentation when e.g. entering a tree node. Generally == (FontSize + FramePadding.x*2). - float ColumnsMinSpacing; // Minimum horizontal spacing between two columns. Preferably > (FramePadding.x + 1). - float ScrollbarSize; // Width of the vertical scrollbar, Height of the horizontal scrollbar. - float ScrollbarRounding; // Radius of grab corners for scrollbar. - float GrabMinSize; // Minimum width/height of a grab box for slider/scrollbar. - float GrabRounding; // Radius of grabs corners rounding. Set to 0.0f to have rectangular slider grabs. - float LogSliderDeadzone; // The size in pixels of the dead-zone around zero on logarithmic sliders that cross zero. - float TabRounding; // Radius of upper corners of a tab. Set to 0.0f to have rectangular tabs. - float TabBorderSize; // Thickness of border around tabs. - float TabMinWidthForCloseButton; // Minimum width for close button to appear on an unselected tab when hovered. Set to 0.0f to always show when hovering, set to FLT_MAX to never show close button unless selected. - float TabBarBorderSize; // Thickness of tab-bar separator, which takes on the tab active color to denote focus. - float TableAngledHeadersAngle; // Angle of angled headers (supported values range from -50.0f degrees to +50.0f degrees). - ImGuiDir ColorButtonPosition; // Side of the color button in the ColorEdit4 widget (left/right). Defaults to ImGuiDir_Right. - ImVec2 ButtonTextAlign; // Alignment of button text when button is larger than text. Defaults to (0.5f, 0.5f) (centered). - ImVec2 SelectableTextAlign; // Alignment of selectable text. Defaults to (0.0f, 0.0f) (top-left aligned). It's generally important to keep this left-aligned if you want to lay multiple items on a same line. - float SeparatorTextBorderSize; // Thickkness of border in SeparatorText() - ImVec2 SeparatorTextAlign; // Alignment of text within the separator. Defaults to (0.0f, 0.5f) (left aligned, center). - ImVec2 SeparatorTextPadding; // Horizontal offset of text from each edge of the separator + spacing on other axis. Generally small values. .y is recommended to be == FramePadding.y. - ImVec2 DisplayWindowPadding; // Window position are clamped to be visible within the display area or monitors by at least this amount. Only applies to regular windows. - ImVec2 DisplaySafeAreaPadding; // If you cannot see the edges of your screen (e.g. on a TV) increase the safe area padding. Apply to popups/tooltips as well regular windows. NB: Prefer configuring your TV sets correctly! - float DockingSeparatorSize; // Thickness of resizing border between docked windows - float MouseCursorScale; // Scale software rendered mouse cursor (when io.MouseDrawCursor is enabled). We apply per-monitor DPI scaling over this scale. May be removed later. - bool AntiAliasedLines; // Enable anti-aliased lines/borders. Disable if you are really tight on CPU/GPU. Latched at the beginning of the frame (copied to ImDrawList). - bool AntiAliasedLinesUseTex; // Enable anti-aliased lines/borders using textures where possible. Require backend to render with bilinear filtering (NOT point/nearest filtering). Latched at the beginning of the frame (copied to ImDrawList). - bool AntiAliasedFill; // Enable anti-aliased edges around filled shapes (rounded rectangles, circles, etc.). Disable if you are really tight on CPU/GPU. Latched at the beginning of the frame (copied to ImDrawList). - float CurveTessellationTol; // Tessellation tolerance when using PathBezierCurveTo() without a specific number of segments. Decrease for highly tessellated curves (higher quality, more polygons), increase to reduce quality. - float CircleTessellationMaxError; // Maximum error (in pixels) allowed when using AddCircle()/AddCircleFilled() or drawing rounded corner rectangles with no explicit segment count specified. Decrease for higher quality but more geometry. - ImVec4 Colors[ImGuiCol_COUNT]; - - // Behaviors - // (It is possible to modify those fields mid-frame if specific behavior need it, unlike e.g. configuration fields in ImGuiIO) - float HoverStationaryDelay; // Delay for IsItemHovered(ImGuiHoveredFlags_Stationary). Time required to consider mouse stationary. - float HoverDelayShort; // Delay for IsItemHovered(ImGuiHoveredFlags_DelayShort). Usually used along with HoverStationaryDelay. - float HoverDelayNormal; // Delay for IsItemHovered(ImGuiHoveredFlags_DelayNormal). " - ImGuiHoveredFlags HoverFlagsForTooltipMouse;// Default flags when using IsItemHovered(ImGuiHoveredFlags_ForTooltip) or BeginItemTooltip()/SetItemTooltip() while using mouse. - ImGuiHoveredFlags HoverFlagsForTooltipNav; // Default flags when using IsItemHovered(ImGuiHoveredFlags_ForTooltip) or BeginItemTooltip()/SetItemTooltip() while using keyboard/gamepad. - - IMGUI_API ImGuiStyle(); - IMGUI_API void ScaleAllSizes(float scale_factor); -}; - -//----------------------------------------------------------------------------- -// [SECTION] ImGuiIO -//----------------------------------------------------------------------------- -// Communicate most settings and inputs/outputs to Dear ImGui using this structure. -// Access via ImGui::GetIO(). Read 'Programmer guide' section in .cpp file for general usage. -//----------------------------------------------------------------------------- - -// [Internal] Storage used by IsKeyDown(), IsKeyPressed() etc functions. -// If prior to 1.87 you used io.KeysDownDuration[] (which was marked as internal), you should use GetKeyData(key)->DownDuration and *NOT* io.KeysData[key]->DownDuration. -struct ImGuiKeyData -{ - bool Down; // True for if key is down - float DownDuration; // Duration the key has been down (<0.0f: not pressed, 0.0f: just pressed, >0.0f: time held) - float DownDurationPrev; // Last frame duration the key has been down - float AnalogValue; // 0.0f..1.0f for gamepad values -}; - -struct ImGuiIO -{ - //------------------------------------------------------------------ - // Configuration // Default value - //------------------------------------------------------------------ - - ImGuiConfigFlags ConfigFlags; // = 0 // See ImGuiConfigFlags_ enum. Set by user/application. Gamepad/keyboard navigation options, etc. - ImGuiBackendFlags BackendFlags; // = 0 // See ImGuiBackendFlags_ enum. Set by backend (imgui_impl_xxx files or custom backend) to communicate features supported by the backend. - ImVec2 DisplaySize; // // Main display size, in pixels (generally == GetMainViewport()->Size). May change every frame. - float DeltaTime; // = 1.0f/60.0f // Time elapsed since last frame, in seconds. May change every frame. - float IniSavingRate; // = 5.0f // Minimum time between saving positions/sizes to .ini file, in seconds. - const char* IniFilename; // = "imgui.ini" // Path to .ini file (important: default "imgui.ini" is relative to current working dir!). Set NULL to disable automatic .ini loading/saving or if you want to manually call LoadIniSettingsXXX() / SaveIniSettingsXXX() functions. - const char* LogFilename; // = "imgui_log.txt"// Path to .log file (default parameter to ImGui::LogToFile when no file is specified). - void* UserData; // = NULL // Store your own data. - - ImFontAtlas*Fonts; // // Font atlas: load, rasterize and pack one or more fonts into a single texture. - float FontGlobalScale; // = 1.0f // Global scale all fonts - bool FontAllowUserScaling; // = false // Allow user scaling text of individual window with CTRL+Wheel. - ImFont* FontDefault; // = NULL // Font to use on NewFrame(). Use NULL to uses Fonts->Fonts[0]. - ImVec2 DisplayFramebufferScale; // = (1, 1) // For retina display or other situations where window coordinates are different from framebuffer coordinates. This generally ends up in ImDrawData::FramebufferScale. - - // Docking options (when ImGuiConfigFlags_DockingEnable is set) - bool ConfigDockingNoSplit; // = false // Simplified docking mode: disable window splitting, so docking is limited to merging multiple windows together into tab-bars. - bool ConfigDockingWithShift; // = false // Enable docking with holding Shift key (reduce visual noise, allows dropping in wider space) - bool ConfigDockingAlwaysTabBar; // = false // [BETA] [FIXME: This currently creates regression with auto-sizing and general overhead] Make every single floating window display within a docking node. - bool ConfigDockingTransparentPayload;// = false // [BETA] Make window or viewport transparent when docking and only display docking boxes on the target viewport. Useful if rendering of multiple viewport cannot be synced. Best used with ConfigViewportsNoAutoMerge. - - // Viewport options (when ImGuiConfigFlags_ViewportsEnable is set) - bool ConfigViewportsNoAutoMerge; // = false; // Set to make all floating imgui windows always create their own viewport. Otherwise, they are merged into the main host viewports when overlapping it. May also set ImGuiViewportFlags_NoAutoMerge on individual viewport. - bool ConfigViewportsNoTaskBarIcon; // = false // Disable default OS task bar icon flag for secondary viewports. When a viewport doesn't want a task bar icon, ImGuiViewportFlags_NoTaskBarIcon will be set on it. - bool ConfigViewportsNoDecoration; // = true // Disable default OS window decoration flag for secondary viewports. When a viewport doesn't want window decorations, ImGuiViewportFlags_NoDecoration will be set on it. Enabling decoration can create subsequent issues at OS levels (e.g. minimum window size). - bool ConfigViewportsNoDefaultParent; // = false // Disable default OS parenting to main viewport for secondary viewports. By default, viewports are marked with ParentViewportId = , expecting the platform backend to setup a parent/child relationship between the OS windows (some backend may ignore this). Set to true if you want the default to be 0, then all viewports will be top-level OS windows. - - // Miscellaneous options - bool MouseDrawCursor; // = false // Request ImGui to draw a mouse cursor for you (if you are on a platform without a mouse cursor). Cannot be easily renamed to 'io.ConfigXXX' because this is frequently used by backend implementations. - bool ConfigMacOSXBehaviors; // = defined(__APPLE__) // OS X style: Text editing cursor movement using Alt instead of Ctrl, Shortcuts using Cmd/Super instead of Ctrl, Line/Text Start and End using Cmd+Arrows instead of Home/End, Double click selects by word instead of selecting whole text, Multi-selection in lists uses Cmd/Super instead of Ctrl. - bool ConfigInputTrickleEventQueue; // = true // Enable input queue trickling: some types of events submitted during the same frame (e.g. button down + up) will be spread over multiple frames, improving interactions with low framerates. - bool ConfigInputTextCursorBlink; // = true // Enable blinking cursor (optional as some users consider it to be distracting). - bool ConfigInputTextEnterKeepActive; // = false // [BETA] Pressing Enter will keep item active and select contents (single-line only). - bool ConfigDragClickToInputText; // = false // [BETA] Enable turning DragXXX widgets into text input with a simple mouse click-release (without moving). Not desirable on devices without a keyboard. - bool ConfigWindowsResizeFromEdges; // = true // Enable resizing of windows from their edges and from the lower-left corner. This requires (io.BackendFlags & ImGuiBackendFlags_HasMouseCursors) because it needs mouse cursor feedback. (This used to be a per-window ImGuiWindowFlags_ResizeFromAnySide flag) - bool ConfigWindowsMoveFromTitleBarOnly; // = false // Enable allowing to move windows only when clicking on their title bar. Does not apply to windows without a title bar. - float ConfigMemoryCompactTimer; // = 60.0f // Timer (in seconds) to free transient windows/tables memory buffers when unused. Set to -1.0f to disable. - - // Inputs Behaviors - // (other variables, ones which are expected to be tweaked within UI code, are exposed in ImGuiStyle) - float MouseDoubleClickTime; // = 0.30f // Time for a double-click, in seconds. - float MouseDoubleClickMaxDist; // = 6.0f // Distance threshold to stay in to validate a double-click, in pixels. - float MouseDragThreshold; // = 6.0f // Distance threshold before considering we are dragging. - float KeyRepeatDelay; // = 0.275f // When holding a key/button, time before it starts repeating, in seconds (for buttons in Repeat mode, etc.). - float KeyRepeatRate; // = 0.050f // When holding a key/button, rate at which it repeats, in seconds. - - //------------------------------------------------------------------ - // Debug options - //------------------------------------------------------------------ - - // Tools to test correct Begin/End and BeginChild/EndChild behaviors. - // Presently Begin()/End() and BeginChild()/EndChild() needs to ALWAYS be called in tandem, regardless of return value of BeginXXX() - // This is inconsistent with other BeginXXX functions and create confusion for many users. - // We expect to update the API eventually. In the meanwhile we provide tools to facilitate checking user-code behavior. - bool ConfigDebugBeginReturnValueOnce;// = false // First-time calls to Begin()/BeginChild() will return false. NEEDS TO BE SET AT APPLICATION BOOT TIME if you don't want to miss windows. - bool ConfigDebugBeginReturnValueLoop;// = false // Some calls to Begin()/BeginChild() will return false. Will cycle through window depths then repeat. Suggested use: add "io.ConfigDebugBeginReturnValue = io.KeyShift" in your main loop then occasionally press SHIFT. Windows should be flickering while running. - - // Option to deactivate io.AddFocusEvent(false) handling. May facilitate interactions with a debugger when focus loss leads to clearing inputs data. - // Backends may have other side-effects on focus loss, so this will reduce side-effects but not necessary remove all of them. - // Consider using e.g. Win32's IsDebuggerPresent() as an additional filter (or see ImOsIsDebuggerPresent() in imgui_test_engine/imgui_te_utils.cpp for a Unix compatible version). - bool ConfigDebugIgnoreFocusLoss; // = false // Ignore io.AddFocusEvent(false), consequently not calling io.ClearInputKeys() in input processing. - - // Option to audit .ini data - bool ConfigDebugIniSettings; // = false // Save .ini data with extra comments (particularly helpful for Docking, but makes saving slower) - - //------------------------------------------------------------------ - // Platform Functions - // (the imgui_impl_xxxx backend files are setting those up for you) - //------------------------------------------------------------------ - - // Optional: Platform/Renderer backend name (informational only! will be displayed in About Window) + User data for backend/wrappers to store their own stuff. - const char* BackendPlatformName; // = NULL - const char* BackendRendererName; // = NULL - void* BackendPlatformUserData; // = NULL // User data for platform backend - void* BackendRendererUserData; // = NULL // User data for renderer backend - void* BackendLanguageUserData; // = NULL // User data for non C++ programming language backend - - // Optional: Access OS clipboard - // (default to use native Win32 clipboard on Windows, otherwise uses a private clipboard. Override to access OS clipboard on other architectures) - const char* (*GetClipboardTextFn)(void* user_data); - void (*SetClipboardTextFn)(void* user_data, const char* text); - void* ClipboardUserData; - - // Optional: Notify OS Input Method Editor of the screen position of your cursor for text input position (e.g. when using Japanese/Chinese IME on Windows) - // (default to use native imm32 api on Windows) - void (*SetPlatformImeDataFn)(ImGuiViewport* viewport, ImGuiPlatformImeData* data); - - // Optional: Platform locale - ImWchar PlatformLocaleDecimalPoint; // '.' // [Experimental] Configure decimal point e.g. '.' or ',' useful for some languages (e.g. German), generally pulled from *localeconv()->decimal_point - - //------------------------------------------------------------------ - // Input - Call before calling NewFrame() - //------------------------------------------------------------------ - - // Input Functions - IMGUI_API void AddKeyEvent(ImGuiKey key, bool down); // Queue a new key down/up event. Key should be "translated" (as in, generally ImGuiKey_A matches the key end-user would use to emit an 'A' character) - IMGUI_API void AddKeyAnalogEvent(ImGuiKey key, bool down, float v); // Queue a new key down/up event for analog values (e.g. ImGuiKey_Gamepad_ values). Dead-zones should be handled by the backend. - IMGUI_API void AddMousePosEvent(float x, float y); // Queue a mouse position update. Use -FLT_MAX,-FLT_MAX to signify no mouse (e.g. app not focused and not hovered) - IMGUI_API void AddMouseButtonEvent(int button, bool down); // Queue a mouse button change - IMGUI_API void AddMouseWheelEvent(float wheel_x, float wheel_y); // Queue a mouse wheel update. wheel_y<0: scroll down, wheel_y>0: scroll up, wheel_x<0: scroll right, wheel_x>0: scroll left. - IMGUI_API void AddMouseSourceEvent(ImGuiMouseSource source); // Queue a mouse source change (Mouse/TouchScreen/Pen) - IMGUI_API void AddMouseViewportEvent(ImGuiID id); // Queue a mouse hovered viewport. Requires backend to set ImGuiBackendFlags_HasMouseHoveredViewport to call this (for multi-viewport support). - IMGUI_API void AddFocusEvent(bool focused); // Queue a gain/loss of focus for the application (generally based on OS/platform focus of your window) - IMGUI_API void AddInputCharacter(unsigned int c); // Queue a new character input - IMGUI_API void AddInputCharacterUTF16(ImWchar16 c); // Queue a new character input from a UTF-16 character, it can be a surrogate - IMGUI_API void AddInputCharactersUTF8(const char* str); // Queue a new characters input from a UTF-8 string - - IMGUI_API void SetKeyEventNativeData(ImGuiKey key, int native_keycode, int native_scancode, int native_legacy_index = -1); // [Optional] Specify index for legacy <1.87 IsKeyXXX() functions with native indices + specify native keycode, scancode. - IMGUI_API void SetAppAcceptingEvents(bool accepting_events); // Set master flag for accepting key/mouse/text events (default to true). Useful if you have native dialog boxes that are interrupting your application loop/refresh, and you want to disable events being queued while your app is frozen. - IMGUI_API void ClearEventsQueue(); // Clear all incoming events. - IMGUI_API void ClearInputKeys(); // Clear current keyboard/mouse/gamepad state + current frame text input buffer. Equivalent to releasing all keys/buttons. -#ifndef IMGUI_DISABLE_OBSOLETE_FUNCTIONS - IMGUI_API void ClearInputCharacters(); // [Obsolete] Clear the current frame text input buffer. Now included within ClearInputKeys(). -#endif - - //------------------------------------------------------------------ - // Output - Updated by NewFrame() or EndFrame()/Render() - // (when reading from the io.WantCaptureMouse, io.WantCaptureKeyboard flags to dispatch your inputs, it is - // generally easier and more correct to use their state BEFORE calling NewFrame(). See FAQ for details!) - //------------------------------------------------------------------ - - bool WantCaptureMouse; // Set when Dear ImGui will use mouse inputs, in this case do not dispatch them to your main game/application (either way, always pass on mouse inputs to imgui). (e.g. unclicked mouse is hovering over an imgui window, widget is active, mouse was clicked over an imgui window, etc.). - bool WantCaptureKeyboard; // Set when Dear ImGui will use keyboard inputs, in this case do not dispatch them to your main game/application (either way, always pass keyboard inputs to imgui). (e.g. InputText active, or an imgui window is focused and navigation is enabled, etc.). - bool WantTextInput; // Mobile/console: when set, you may display an on-screen keyboard. This is set by Dear ImGui when it wants textual keyboard input to happen (e.g. when a InputText widget is active). - bool WantSetMousePos; // MousePos has been altered, backend should reposition mouse on next frame. Rarely used! Set only when ImGuiConfigFlags_NavEnableSetMousePos flag is enabled. - bool WantSaveIniSettings; // When manual .ini load/save is active (io.IniFilename == NULL), this will be set to notify your application that you can call SaveIniSettingsToMemory() and save yourself. Important: clear io.WantSaveIniSettings yourself after saving! - bool NavActive; // Keyboard/Gamepad navigation is currently allowed (will handle ImGuiKey_NavXXX events) = a window is focused and it doesn't use the ImGuiWindowFlags_NoNavInputs flag. - bool NavVisible; // Keyboard/Gamepad navigation is visible and allowed (will handle ImGuiKey_NavXXX events). - float Framerate; // Estimate of application framerate (rolling average over 60 frames, based on io.DeltaTime), in frame per second. Solely for convenience. Slow applications may not want to use a moving average or may want to reset underlying buffers occasionally. - int MetricsRenderVertices; // Vertices output during last call to Render() - int MetricsRenderIndices; // Indices output during last call to Render() = number of triangles * 3 - int MetricsRenderWindows; // Number of visible windows - int MetricsActiveWindows; // Number of active windows - ImVec2 MouseDelta; // Mouse delta. Note that this is zero if either current or previous position are invalid (-FLT_MAX,-FLT_MAX), so a disappearing/reappearing mouse won't have a huge delta. - - // Legacy: before 1.87, we required backend to fill io.KeyMap[] (imgui->native map) during initialization and io.KeysDown[] (native indices) every frame. - // This is still temporarily supported as a legacy feature. However the new preferred scheme is for backend to call io.AddKeyEvent(). - // Old (<1.87): ImGui::IsKeyPressed(ImGui::GetIO().KeyMap[ImGuiKey_Space]) --> New (1.87+) ImGui::IsKeyPressed(ImGuiKey_Space) -#ifndef IMGUI_DISABLE_OBSOLETE_KEYIO - int KeyMap[ImGuiKey_COUNT]; // [LEGACY] Input: map of indices into the KeysDown[512] entries array which represent your "native" keyboard state. The first 512 are now unused and should be kept zero. Legacy backend will write into KeyMap[] using ImGuiKey_ indices which are always >512. - bool KeysDown[ImGuiKey_COUNT]; // [LEGACY] Input: Keyboard keys that are pressed (ideally left in the "native" order your engine has access to keyboard keys, so you can use your own defines/enums for keys). This used to be [512] sized. It is now ImGuiKey_COUNT to allow legacy io.KeysDown[GetKeyIndex(...)] to work without an overflow. - float NavInputs[ImGuiNavInput_COUNT]; // [LEGACY] Since 1.88, NavInputs[] was removed. Backends from 1.60 to 1.86 won't build. Feed gamepad inputs via io.AddKeyEvent() and ImGuiKey_GamepadXXX enums. -#endif -#ifndef IMGUI_DISABLE_OBSOLETE_FUNCTIONS - void* ImeWindowHandle; // = NULL // [Obsoleted in 1.87] Set ImGuiViewport::PlatformHandleRaw instead. Set this to your HWND to get automatic IME cursor positioning. -#else - void* _UnusedPadding; -#endif - - //------------------------------------------------------------------ - // [Internal] Dear ImGui will maintain those fields. Forward compatibility not guaranteed! - //------------------------------------------------------------------ - - ImGuiContext* Ctx; // Parent UI context (needs to be set explicitly by parent). - - // Main Input State - // (this block used to be written by backend, since 1.87 it is best to NOT write to those directly, call the AddXXX functions above instead) - // (reading from those variables is fair game, as they are extremely unlikely to be moving anywhere) - ImVec2 MousePos; // Mouse position, in pixels. Set to ImVec2(-FLT_MAX, -FLT_MAX) if mouse is unavailable (on another screen, etc.) - bool MouseDown[5]; // Mouse buttons: 0=left, 1=right, 2=middle + extras (ImGuiMouseButton_COUNT == 5). Dear ImGui mostly uses left and right buttons. Other buttons allow us to track if the mouse is being used by your application + available to user as a convenience via IsMouse** API. - float MouseWheel; // Mouse wheel Vertical: 1 unit scrolls about 5 lines text. >0 scrolls Up, <0 scrolls Down. Hold SHIFT to turn vertical scroll into horizontal scroll. - float MouseWheelH; // Mouse wheel Horizontal. >0 scrolls Left, <0 scrolls Right. Most users don't have a mouse with a horizontal wheel, may not be filled by all backends. - ImGuiMouseSource MouseSource; // Mouse actual input peripheral (Mouse/TouchScreen/Pen). - ImGuiID MouseHoveredViewport; // (Optional) Modify using io.AddMouseViewportEvent(). With multi-viewports: viewport the OS mouse is hovering. If possible _IGNORING_ viewports with the ImGuiViewportFlags_NoInputs flag is much better (few backends can handle that). Set io.BackendFlags |= ImGuiBackendFlags_HasMouseHoveredViewport if you can provide this info. If you don't imgui will infer the value using the rectangles and last focused time of the viewports it knows about (ignoring other OS windows). - bool KeyCtrl; // Keyboard modifier down: Control - bool KeyShift; // Keyboard modifier down: Shift - bool KeyAlt; // Keyboard modifier down: Alt - bool KeySuper; // Keyboard modifier down: Cmd/Super/Windows - - // Other state maintained from data above + IO function calls - ImGuiKeyChord KeyMods; // Key mods flags (any of ImGuiMod_Ctrl/ImGuiMod_Shift/ImGuiMod_Alt/ImGuiMod_Super flags, same as io.KeyCtrl/KeyShift/KeyAlt/KeySuper but merged into flags. DOES NOT CONTAINS ImGuiMod_Shortcut which is pretranslated). Read-only, updated by NewFrame() - ImGuiKeyData KeysData[ImGuiKey_KeysData_SIZE]; // Key state for all known keys. Use IsKeyXXX() functions to access this. - bool WantCaptureMouseUnlessPopupClose; // Alternative to WantCaptureMouse: (WantCaptureMouse == true && WantCaptureMouseUnlessPopupClose == false) when a click over void is expected to close a popup. - ImVec2 MousePosPrev; // Previous mouse position (note that MouseDelta is not necessary == MousePos-MousePosPrev, in case either position is invalid) - ImVec2 MouseClickedPos[5]; // Position at time of clicking - double MouseClickedTime[5]; // Time of last click (used to figure out double-click) - bool MouseClicked[5]; // Mouse button went from !Down to Down (same as MouseClickedCount[x] != 0) - bool MouseDoubleClicked[5]; // Has mouse button been double-clicked? (same as MouseClickedCount[x] == 2) - ImU16 MouseClickedCount[5]; // == 0 (not clicked), == 1 (same as MouseClicked[]), == 2 (double-clicked), == 3 (triple-clicked) etc. when going from !Down to Down - ImU16 MouseClickedLastCount[5]; // Count successive number of clicks. Stays valid after mouse release. Reset after another click is done. - bool MouseReleased[5]; // Mouse button went from Down to !Down - bool MouseDownOwned[5]; // Track if button was clicked inside a dear imgui window or over void blocked by a popup. We don't request mouse capture from the application if click started outside ImGui bounds. - bool MouseDownOwnedUnlessPopupClose[5]; // Track if button was clicked inside a dear imgui window. - bool MouseWheelRequestAxisSwap; // On a non-Mac system, holding SHIFT requests WheelY to perform the equivalent of a WheelX event. On a Mac system this is already enforced by the system. - float MouseDownDuration[5]; // Duration the mouse button has been down (0.0f == just clicked) - float MouseDownDurationPrev[5]; // Previous time the mouse button has been down - ImVec2 MouseDragMaxDistanceAbs[5]; // Maximum distance, absolute, on each axis, of how much mouse has traveled from the clicking point - float MouseDragMaxDistanceSqr[5]; // Squared maximum distance of how much mouse has traveled from the clicking point (used for moving thresholds) - float PenPressure; // Touch/Pen pressure (0.0f to 1.0f, should be >0.0f only when MouseDown[0] == true). Helper storage currently unused by Dear ImGui. - bool AppFocusLost; // Only modify via AddFocusEvent() - bool AppAcceptingEvents; // Only modify via SetAppAcceptingEvents() - ImS8 BackendUsingLegacyKeyArrays; // -1: unknown, 0: using AddKeyEvent(), 1: using legacy io.KeysDown[] - bool BackendUsingLegacyNavInputArray; // 0: using AddKeyAnalogEvent(), 1: writing to legacy io.NavInputs[] directly - ImWchar16 InputQueueSurrogate; // For AddInputCharacterUTF16() - ImVector InputQueueCharacters; // Queue of _characters_ input (obtained by platform backend). Fill using AddInputCharacter() helper. - - IMGUI_API ImGuiIO(); -}; - -//----------------------------------------------------------------------------- -// [SECTION] Misc data structures -//----------------------------------------------------------------------------- - -// Shared state of InputText(), passed as an argument to your callback when a ImGuiInputTextFlags_Callback* flag is used. -// The callback function should return 0 by default. -// Callbacks (follow a flag name and see comments in ImGuiInputTextFlags_ declarations for more details) -// - ImGuiInputTextFlags_CallbackEdit: Callback on buffer edit (note that InputText() already returns true on edit, the callback is useful mainly to manipulate the underlying buffer while focus is active) -// - ImGuiInputTextFlags_CallbackAlways: Callback on each iteration -// - ImGuiInputTextFlags_CallbackCompletion: Callback on pressing TAB -// - ImGuiInputTextFlags_CallbackHistory: Callback on pressing Up/Down arrows -// - ImGuiInputTextFlags_CallbackCharFilter: Callback on character inputs to replace or discard them. Modify 'EventChar' to replace or discard, or return 1 in callback to discard. -// - ImGuiInputTextFlags_CallbackResize: Callback on buffer capacity changes request (beyond 'buf_size' parameter value), allowing the string to grow. -struct ImGuiInputTextCallbackData -{ - ImGuiContext* Ctx; // Parent UI context - ImGuiInputTextFlags EventFlag; // One ImGuiInputTextFlags_Callback* // Read-only - ImGuiInputTextFlags Flags; // What user passed to InputText() // Read-only - void* UserData; // What user passed to InputText() // Read-only - - // Arguments for the different callback events - // - To modify the text buffer in a callback, prefer using the InsertChars() / DeleteChars() function. InsertChars() will take care of calling the resize callback if necessary. - // - If you know your edits are not going to resize the underlying buffer allocation, you may modify the contents of 'Buf[]' directly. You need to update 'BufTextLen' accordingly (0 <= BufTextLen < BufSize) and set 'BufDirty'' to true so InputText can update its internal state. - ImWchar EventChar; // Character input // Read-write // [CharFilter] Replace character with another one, or set to zero to drop. return 1 is equivalent to setting EventChar=0; - ImGuiKey EventKey; // Key pressed (Up/Down/TAB) // Read-only // [Completion,History] - char* Buf; // Text buffer // Read-write // [Resize] Can replace pointer / [Completion,History,Always] Only write to pointed data, don't replace the actual pointer! - int BufTextLen; // Text length (in bytes) // Read-write // [Resize,Completion,History,Always] Exclude zero-terminator storage. In C land: == strlen(some_text), in C++ land: string.length() - int BufSize; // Buffer size (in bytes) = capacity+1 // Read-only // [Resize,Completion,History,Always] Include zero-terminator storage. In C land == ARRAYSIZE(my_char_array), in C++ land: string.capacity()+1 - bool BufDirty; // Set if you modify Buf/BufTextLen! // Write // [Completion,History,Always] - int CursorPos; // // Read-write // [Completion,History,Always] - int SelectionStart; // // Read-write // [Completion,History,Always] == to SelectionEnd when no selection) - int SelectionEnd; // // Read-write // [Completion,History,Always] - - // Helper functions for text manipulation. - // Use those function to benefit from the CallbackResize behaviors. Calling those function reset the selection. - IMGUI_API ImGuiInputTextCallbackData(); - IMGUI_API void DeleteChars(int pos, int bytes_count); - IMGUI_API void InsertChars(int pos, const char* text, const char* text_end = NULL); - void SelectAll() { SelectionStart = 0; SelectionEnd = BufTextLen; } - void ClearSelection() { SelectionStart = SelectionEnd = BufTextLen; } - bool HasSelection() const { return SelectionStart != SelectionEnd; } -}; - -// Resizing callback data to apply custom constraint. As enabled by SetNextWindowSizeConstraints(). Callback is called during the next Begin(). -// NB: For basic min/max size constraint on each axis you don't need to use the callback! The SetNextWindowSizeConstraints() parameters are enough. -struct ImGuiSizeCallbackData -{ - void* UserData; // Read-only. What user passed to SetNextWindowSizeConstraints(). Generally store an integer or float in here (need reinterpret_cast<>). - ImVec2 Pos; // Read-only. Window position, for reference. - ImVec2 CurrentSize; // Read-only. Current window size. - ImVec2 DesiredSize; // Read-write. Desired size, based on user's mouse position. Write to this field to restrain resizing. -}; - -// [ALPHA] Rarely used / very advanced uses only. Use with SetNextWindowClass() and DockSpace() functions. -// Important: the content of this class is still highly WIP and likely to change and be refactored -// before we stabilize Docking features. Please be mindful if using this. -// Provide hints: -// - To the platform backend via altered viewport flags (enable/disable OS decoration, OS task bar icons, etc.) -// - To the platform backend for OS level parent/child relationships of viewport. -// - To the docking system for various options and filtering. -struct ImGuiWindowClass -{ - ImGuiID ClassId; // User data. 0 = Default class (unclassed). Windows of different classes cannot be docked with each others. - ImGuiID ParentViewportId; // Hint for the platform backend. -1: use default. 0: request platform backend to not parent the platform. != 0: request platform backend to create a parent<>child relationship between the platform windows. Not conforming backends are free to e.g. parent every viewport to the main viewport or not. - ImGuiViewportFlags ViewportFlagsOverrideSet; // Viewport flags to set when a window of this class owns a viewport. This allows you to enforce OS decoration or task bar icon, override the defaults on a per-window basis. - ImGuiViewportFlags ViewportFlagsOverrideClear; // Viewport flags to clear when a window of this class owns a viewport. This allows you to enforce OS decoration or task bar icon, override the defaults on a per-window basis. - ImGuiTabItemFlags TabItemFlagsOverrideSet; // [EXPERIMENTAL] TabItem flags to set when a window of this class gets submitted into a dock node tab bar. May use with ImGuiTabItemFlags_Leading or ImGuiTabItemFlags_Trailing. - ImGuiDockNodeFlags DockNodeFlagsOverrideSet; // [EXPERIMENTAL] Dock node flags to set when a window of this class is hosted by a dock node (it doesn't have to be selected!) - bool DockingAlwaysTabBar; // Set to true to enforce single floating windows of this class always having their own docking node (equivalent of setting the global io.ConfigDockingAlwaysTabBar) - bool DockingAllowUnclassed; // Set to true to allow windows of this class to be docked/merged with an unclassed window. // FIXME-DOCK: Move to DockNodeFlags override? - - ImGuiWindowClass() { memset(this, 0, sizeof(*this)); ParentViewportId = (ImGuiID)-1; DockingAllowUnclassed = true; } -}; - -// Data payload for Drag and Drop operations: AcceptDragDropPayload(), GetDragDropPayload() -struct ImGuiPayload -{ - // Members - void* Data; // Data (copied and owned by dear imgui) - int DataSize; // Data size - - // [Internal] - ImGuiID SourceId; // Source item id - ImGuiID SourceParentId; // Source parent id (if available) - int DataFrameCount; // Data timestamp - char DataType[32 + 1]; // Data type tag (short user-supplied string, 32 characters max) - bool Preview; // Set when AcceptDragDropPayload() was called and mouse has been hovering the target item (nb: handle overlapping drag targets) - bool Delivery; // Set when AcceptDragDropPayload() was called and mouse button is released over the target item. - - ImGuiPayload() { Clear(); } - void Clear() { SourceId = SourceParentId = 0; Data = NULL; DataSize = 0; memset(DataType, 0, sizeof(DataType)); DataFrameCount = -1; Preview = Delivery = false; } - bool IsDataType(const char* type) const { return DataFrameCount != -1 && strcmp(type, DataType) == 0; } - bool IsPreview() const { return Preview; } - bool IsDelivery() const { return Delivery; } -}; - -// Sorting specification for one column of a table (sizeof == 12 bytes) -struct ImGuiTableColumnSortSpecs -{ - ImGuiID ColumnUserID; // User id of the column (if specified by a TableSetupColumn() call) - ImS16 ColumnIndex; // Index of the column - ImS16 SortOrder; // Index within parent ImGuiTableSortSpecs (always stored in order starting from 0, tables sorted on a single criteria will always have a 0 here) - ImGuiSortDirection SortDirection : 8; // ImGuiSortDirection_Ascending or ImGuiSortDirection_Descending - - ImGuiTableColumnSortSpecs() { memset(this, 0, sizeof(*this)); } -}; - -// Sorting specifications for a table (often handling sort specs for a single column, occasionally more) -// Obtained by calling TableGetSortSpecs(). -// When 'SpecsDirty == true' you can sort your data. It will be true with sorting specs have changed since last call, or the first time. -// Make sure to set 'SpecsDirty = false' after sorting, else you may wastefully sort your data every frame! -struct ImGuiTableSortSpecs -{ - const ImGuiTableColumnSortSpecs* Specs; // Pointer to sort spec array. - int SpecsCount; // Sort spec count. Most often 1. May be > 1 when ImGuiTableFlags_SortMulti is enabled. May be == 0 when ImGuiTableFlags_SortTristate is enabled. - bool SpecsDirty; // Set to true when specs have changed since last time! Use this to sort again, then clear the flag. - - ImGuiTableSortSpecs() { memset(this, 0, sizeof(*this)); } -}; - -//----------------------------------------------------------------------------- -// [SECTION] Helpers (ImGuiOnceUponAFrame, ImGuiTextFilter, ImGuiTextBuffer, ImGuiStorage, ImGuiListClipper, Math Operators, ImColor) -//----------------------------------------------------------------------------- - -// Helper: Unicode defines -#define IM_UNICODE_CODEPOINT_INVALID 0xFFFD // Invalid Unicode code point (standard value). -#ifdef IMGUI_USE_WCHAR32 -#define IM_UNICODE_CODEPOINT_MAX 0x10FFFF // Maximum Unicode code point supported by this build. -#else -#define IM_UNICODE_CODEPOINT_MAX 0xFFFF // Maximum Unicode code point supported by this build. -#endif - -// Helper: Execute a block of code at maximum once a frame. Convenient if you want to quickly create a UI within deep-nested code that runs multiple times every frame. -// Usage: static ImGuiOnceUponAFrame oaf; if (oaf) ImGui::Text("This will be called only once per frame"); -struct ImGuiOnceUponAFrame -{ - ImGuiOnceUponAFrame() { RefFrame = -1; } - mutable int RefFrame; - operator bool() const { int current_frame = ImGui::GetFrameCount(); if (RefFrame == current_frame) return false; RefFrame = current_frame; return true; } -}; - -// Helper: Parse and apply text filters. In format "aaaaa[,bbbb][,ccccc]" -struct ImGuiTextFilter -{ - IMGUI_API ImGuiTextFilter(const char* default_filter = ""); - IMGUI_API bool Draw(const char* label = "Filter (inc,-exc)", float width = 0.0f); // Helper calling InputText+Build - IMGUI_API bool PassFilter(const char* text, const char* text_end = NULL) const; - IMGUI_API void Build(); - void Clear() { InputBuf[0] = 0; Build(); } - bool IsActive() const { return !Filters.empty(); } - - // [Internal] - struct ImGuiTextRange - { - const char* b; - const char* e; - - ImGuiTextRange() { b = e = NULL; } - ImGuiTextRange(const char* _b, const char* _e) { b = _b; e = _e; } - bool empty() const { return b == e; } - IMGUI_API void split(char separator, ImVector* out) const; - }; - char InputBuf[256]; - ImVectorFilters; - int CountGrep; -}; - -// Helper: Growable text buffer for logging/accumulating text -// (this could be called 'ImGuiTextBuilder' / 'ImGuiStringBuilder') -struct ImGuiTextBuffer -{ - ImVector Buf; - IMGUI_API static char EmptyString[1]; - - ImGuiTextBuffer() { } - inline char operator[](int i) const { IM_ASSERT(Buf.Data != NULL); return Buf.Data[i]; } - const char* begin() const { return Buf.Data ? &Buf.front() : EmptyString; } - const char* end() const { return Buf.Data ? &Buf.back() : EmptyString; } // Buf is zero-terminated, so end() will point on the zero-terminator - int size() const { return Buf.Size ? Buf.Size - 1 : 0; } - bool empty() const { return Buf.Size <= 1; } - void clear() { Buf.clear(); } - void reserve(int capacity) { Buf.reserve(capacity); } - const char* c_str() const { return Buf.Data ? Buf.Data : EmptyString; } - IMGUI_API void append(const char* str, const char* str_end = NULL); - IMGUI_API void appendf(const char* fmt, ...) IM_FMTARGS(2); - IMGUI_API void appendfv(const char* fmt, va_list args) IM_FMTLIST(2); -}; - -// Helper: Key->Value storage -// Typically you don't have to worry about this since a storage is held within each Window. -// We use it to e.g. store collapse state for a tree (Int 0/1) -// This is optimized for efficient lookup (dichotomy into a contiguous buffer) and rare insertion (typically tied to user interactions aka max once a frame) -// You can use it as custom user storage for temporary values. Declare your own storage if, for example: -// - You want to manipulate the open/close state of a particular sub-tree in your interface (tree node uses Int 0/1 to store their state). -// - You want to store custom debug data easily without adding or editing structures in your code (probably not efficient, but convenient) -// Types are NOT stored, so it is up to you to make sure your Key don't collide with different types. -struct ImGuiStorage -{ - // [Internal] - struct ImGuiStoragePair - { - ImGuiID key; - union { int val_i; float val_f; void* val_p; }; - ImGuiStoragePair(ImGuiID _key, int _val_i) { key = _key; val_i = _val_i; } - ImGuiStoragePair(ImGuiID _key, float _val_f) { key = _key; val_f = _val_f; } - ImGuiStoragePair(ImGuiID _key, void* _val_p) { key = _key; val_p = _val_p; } - }; - - ImVector Data; - - // - Get***() functions find pair, never add/allocate. Pairs are sorted so a query is O(log N) - // - Set***() functions find pair, insertion on demand if missing. - // - Sorted insertion is costly, paid once. A typical frame shouldn't need to insert any new pair. - void Clear() { Data.clear(); } - IMGUI_API int GetInt(ImGuiID key, int default_val = 0) const; - IMGUI_API void SetInt(ImGuiID key, int val); - IMGUI_API bool GetBool(ImGuiID key, bool default_val = false) const; - IMGUI_API void SetBool(ImGuiID key, bool val); - IMGUI_API float GetFloat(ImGuiID key, float default_val = 0.0f) const; - IMGUI_API void SetFloat(ImGuiID key, float val); - IMGUI_API void* GetVoidPtr(ImGuiID key) const; // default_val is NULL - IMGUI_API void SetVoidPtr(ImGuiID key, void* val); - - // - Get***Ref() functions finds pair, insert on demand if missing, return pointer. Useful if you intend to do Get+Set. - // - References are only valid until a new value is added to the storage. Calling a Set***() function or a Get***Ref() function invalidates the pointer. - // - A typical use case where this is convenient for quick hacking (e.g. add storage during a live Edit&Continue session if you can't modify existing struct) - // float* pvar = ImGui::GetFloatRef(key); ImGui::SliderFloat("var", pvar, 0, 100.0f); some_var += *pvar; - IMGUI_API int* GetIntRef(ImGuiID key, int default_val = 0); - IMGUI_API bool* GetBoolRef(ImGuiID key, bool default_val = false); - IMGUI_API float* GetFloatRef(ImGuiID key, float default_val = 0.0f); - IMGUI_API void** GetVoidPtrRef(ImGuiID key, void* default_val = NULL); - - // Use on your own storage if you know only integer are being stored (open/close all tree nodes) - IMGUI_API void SetAllInt(int val); - - // For quicker full rebuild of a storage (instead of an incremental one), you may add all your contents and then sort once. - IMGUI_API void BuildSortByKey(); -}; - -// Helper: Manually clip large list of items. -// If you have lots evenly spaced items and you have random access to the list, you can perform coarse -// clipping based on visibility to only submit items that are in view. -// The clipper calculates the range of visible items and advance the cursor to compensate for the non-visible items we have skipped. -// (Dear ImGui already clip items based on their bounds but: it needs to first layout the item to do so, and generally -// fetching/submitting your own data incurs additional cost. Coarse clipping using ImGuiListClipper allows you to easily -// scale using lists with tens of thousands of items without a problem) -// Usage: -// ImGuiListClipper clipper; -// clipper.Begin(1000); // We have 1000 elements, evenly spaced. -// while (clipper.Step()) -// for (int i = clipper.DisplayStart; i < clipper.DisplayEnd; i++) -// ImGui::Text("line number %d", i); -// Generally what happens is: -// - Clipper lets you process the first element (DisplayStart = 0, DisplayEnd = 1) regardless of it being visible or not. -// - User code submit that one element. -// - Clipper can measure the height of the first element -// - Clipper calculate the actual range of elements to display based on the current clipping rectangle, position the cursor before the first visible element. -// - User code submit visible elements. -// - The clipper also handles various subtleties related to keyboard/gamepad navigation, wrapping etc. -struct ImGuiListClipper -{ - ImGuiContext* Ctx; // Parent UI context - int DisplayStart; // First item to display, updated by each call to Step() - int DisplayEnd; // End of items to display (exclusive) - int ItemsCount; // [Internal] Number of items - float ItemsHeight; // [Internal] Height of item after a first step and item submission can calculate it - float StartPosY; // [Internal] Cursor position at the time of Begin() or after table frozen rows are all processed - void* TempData; // [Internal] Internal data - - // items_count: Use INT_MAX if you don't know how many items you have (in which case the cursor won't be advanced in the final step) - // items_height: Use -1.0f to be calculated automatically on first step. Otherwise pass in the distance between your items, typically GetTextLineHeightWithSpacing() or GetFrameHeightWithSpacing(). - IMGUI_API ImGuiListClipper(); - IMGUI_API ~ImGuiListClipper(); - IMGUI_API void Begin(int items_count, float items_height = -1.0f); - IMGUI_API void End(); // Automatically called on the last call of Step() that returns false. - IMGUI_API bool Step(); // Call until it returns false. The DisplayStart/DisplayEnd fields will be set and you can process/draw those items. - - // Call IncludeItemByIndex() or IncludeItemsByIndex() *BEFORE* first call to Step() if you need a range of items to not be clipped, regardless of their visibility. - // (Due to alignment / padding of certain items it is possible that an extra item may be included on either end of the display range). - inline void IncludeItemByIndex(int item_index) { IncludeItemsByIndex(item_index, item_index + 1); } - IMGUI_API void IncludeItemsByIndex(int item_begin, int item_end); // item_end is exclusive e.g. use (42, 42+1) to make item 42 never clipped. - -#ifndef IMGUI_DISABLE_OBSOLETE_FUNCTIONS - inline void IncludeRangeByIndices(int item_begin, int item_end) { IncludeItemsByIndex(item_begin, item_end); } // [renamed in 1.89.9] - inline void ForceDisplayRangeByIndices(int item_begin, int item_end) { IncludeItemsByIndex(item_begin, item_end); } // [renamed in 1.89.6] - //inline ImGuiListClipper(int items_count, float items_height = -1.0f) { memset(this, 0, sizeof(*this)); ItemsCount = -1; Begin(items_count, items_height); } // [removed in 1.79] -#endif -}; - -// Helpers macros to generate 32-bit encoded colors -// User can declare their own format by #defining the 5 _SHIFT/_MASK macros in their imconfig file. -#ifndef IM_COL32_R_SHIFT -#ifdef IMGUI_USE_BGRA_PACKED_COLOR -#define IM_COL32_R_SHIFT 16 -#define IM_COL32_G_SHIFT 8 -#define IM_COL32_B_SHIFT 0 -#define IM_COL32_A_SHIFT 24 -#define IM_COL32_A_MASK 0xFF000000 -#else -#define IM_COL32_R_SHIFT 0 -#define IM_COL32_G_SHIFT 8 -#define IM_COL32_B_SHIFT 16 -#define IM_COL32_A_SHIFT 24 -#define IM_COL32_A_MASK 0xFF000000 -#endif -#endif -#define IM_COL32(R,G,B,A) (((ImU32)(A)<> IM_COL32_R_SHIFT) & 0xFF) * (1.0f / 255.0f), (float)((rgba >> IM_COL32_G_SHIFT) & 0xFF) * (1.0f / 255.0f), (float)((rgba >> IM_COL32_B_SHIFT) & 0xFF) * (1.0f / 255.0f), (float)((rgba >> IM_COL32_A_SHIFT) & 0xFF) * (1.0f / 255.0f)) {} - inline operator ImU32() const { return ImGui::ColorConvertFloat4ToU32(Value); } - inline operator ImVec4() const { return Value; } - - // FIXME-OBSOLETE: May need to obsolete/cleanup those helpers. - inline void SetHSV(float h, float s, float v, float a = 1.0f){ ImGui::ColorConvertHSVtoRGB(h, s, v, Value.x, Value.y, Value.z); Value.w = a; } - static ImColor HSV(float h, float s, float v, float a = 1.0f) { float r, g, b; ImGui::ColorConvertHSVtoRGB(h, s, v, r, g, b); return ImColor(r, g, b, a); } -}; - -//----------------------------------------------------------------------------- -// [SECTION] Drawing API (ImDrawCmd, ImDrawIdx, ImDrawVert, ImDrawChannel, ImDrawListSplitter, ImDrawListFlags, ImDrawList, ImDrawData) -// Hold a series of drawing commands. The user provides a renderer for ImDrawData which essentially contains an array of ImDrawList. -//----------------------------------------------------------------------------- - -// The maximum line width to bake anti-aliased textures for. Build atlas with ImFontAtlasFlags_NoBakedLines to disable baking. -#ifndef IM_DRAWLIST_TEX_LINES_WIDTH_MAX -#define IM_DRAWLIST_TEX_LINES_WIDTH_MAX (63) -#endif - -// ImDrawCallback: Draw callbacks for advanced uses [configurable type: override in imconfig.h] -// NB: You most likely do NOT need to use draw callbacks just to create your own widget or customized UI rendering, -// you can poke into the draw list for that! Draw callback may be useful for example to: -// A) Change your GPU render state, -// B) render a complex 3D scene inside a UI element without an intermediate texture/render target, etc. -// The expected behavior from your rendering function is 'if (cmd.UserCallback != NULL) { cmd.UserCallback(parent_list, cmd); } else { RenderTriangles() }' -// If you want to override the signature of ImDrawCallback, you can simply use e.g. '#define ImDrawCallback MyDrawCallback' (in imconfig.h) + update rendering backend accordingly. -#ifndef ImDrawCallback -typedef void (*ImDrawCallback)(const ImDrawList* parent_list, const ImDrawCmd* cmd); -#endif - -// Special Draw callback value to request renderer backend to reset the graphics/render state. -// The renderer backend needs to handle this special value, otherwise it will crash trying to call a function at this address. -// This is useful for example if you submitted callbacks which you know have altered the render state and you want it to be restored. -// It is not done by default because they are many perfectly useful way of altering render state for imgui contents (e.g. changing shader/blending settings before an Image call). -#define ImDrawCallback_ResetRenderState (ImDrawCallback)(-1) - -// Typically, 1 command = 1 GPU draw call (unless command is a callback) -// - VtxOffset: When 'io.BackendFlags & ImGuiBackendFlags_RendererHasVtxOffset' is enabled, -// this fields allow us to render meshes larger than 64K vertices while keeping 16-bit indices. -// Backends made for <1.71. will typically ignore the VtxOffset fields. -// - The ClipRect/TextureId/VtxOffset fields must be contiguous as we memcmp() them together (this is asserted for). -struct ImDrawCmd -{ - ImVec4 ClipRect; // 4*4 // Clipping rectangle (x1, y1, x2, y2). Subtract ImDrawData->DisplayPos to get clipping rectangle in "viewport" coordinates - ImTextureID TextureId; // 4-8 // User-provided texture ID. Set by user in ImfontAtlas::SetTexID() for fonts or passed to Image*() functions. Ignore if never using images or multiple fonts atlas. - unsigned int VtxOffset; // 4 // Start offset in vertex buffer. ImGuiBackendFlags_RendererHasVtxOffset: always 0, otherwise may be >0 to support meshes larger than 64K vertices with 16-bit indices. - unsigned int IdxOffset; // 4 // Start offset in index buffer. - unsigned int ElemCount; // 4 // Number of indices (multiple of 3) to be rendered as triangles. Vertices are stored in the callee ImDrawList's vtx_buffer[] array, indices in idx_buffer[]. - ImDrawCallback UserCallback; // 4-8 // If != NULL, call the function instead of rendering the vertices. clip_rect and texture_id will be set normally. - void* UserCallbackData; // 4-8 // The draw callback code can access this. - - ImDrawCmd() { memset(this, 0, sizeof(*this)); } // Also ensure our padding fields are zeroed - - // Since 1.83: returns ImTextureID associated with this draw call. Warning: DO NOT assume this is always same as 'TextureId' (we will change this function for an upcoming feature) - inline ImTextureID GetTexID() const { return TextureId; } -}; - -// Vertex layout -#ifndef IMGUI_OVERRIDE_DRAWVERT_STRUCT_LAYOUT -struct ImDrawVert -{ - ImVec2 pos; - ImVec2 uv; - ImU32 col; -}; -#else -// You can override the vertex format layout by defining IMGUI_OVERRIDE_DRAWVERT_STRUCT_LAYOUT in imconfig.h -// The code expect ImVec2 pos (8 bytes), ImVec2 uv (8 bytes), ImU32 col (4 bytes), but you can re-order them or add other fields as needed to simplify integration in your engine. -// The type has to be described within the macro (you can either declare the struct or use a typedef). This is because ImVec2/ImU32 are likely not declared at the time you'd want to set your type up. -// NOTE: IMGUI DOESN'T CLEAR THE STRUCTURE AND DOESN'T CALL A CONSTRUCTOR SO ANY CUSTOM FIELD WILL BE UNINITIALIZED. IF YOU ADD EXTRA FIELDS (SUCH AS A 'Z' COORDINATES) YOU WILL NEED TO CLEAR THEM DURING RENDER OR TO IGNORE THEM. -IMGUI_OVERRIDE_DRAWVERT_STRUCT_LAYOUT; -#endif - -// [Internal] For use by ImDrawList -struct ImDrawCmdHeader -{ - ImVec4 ClipRect; - ImTextureID TextureId; - unsigned int VtxOffset; -}; - -// [Internal] For use by ImDrawListSplitter -struct ImDrawChannel -{ - ImVector _CmdBuffer; - ImVector _IdxBuffer; -}; - - -// Split/Merge functions are used to split the draw list into different layers which can be drawn into out of order. -// This is used by the Columns/Tables API, so items of each column can be batched together in a same draw call. -struct ImDrawListSplitter -{ - int _Current; // Current channel number (0) - int _Count; // Number of active channels (1+) - ImVector _Channels; // Draw channels (not resized down so _Count might be < Channels.Size) - - inline ImDrawListSplitter() { memset(this, 0, sizeof(*this)); } - inline ~ImDrawListSplitter() { ClearFreeMemory(); } - inline void Clear() { _Current = 0; _Count = 1; } // Do not clear Channels[] so our allocations are reused next frame - IMGUI_API void ClearFreeMemory(); - IMGUI_API void Split(ImDrawList* draw_list, int count); - IMGUI_API void Merge(ImDrawList* draw_list); - IMGUI_API void SetCurrentChannel(ImDrawList* draw_list, int channel_idx); -}; - -// Flags for ImDrawList functions -// (Legacy: bit 0 must always correspond to ImDrawFlags_Closed to be backward compatible with old API using a bool. Bits 1..3 must be unused) -enum ImDrawFlags_ -{ - ImDrawFlags_None = 0, - ImDrawFlags_Closed = 1 << 0, // PathStroke(), AddPolyline(): specify that shape should be closed (Important: this is always == 1 for legacy reason) - ImDrawFlags_RoundCornersTopLeft = 1 << 4, // AddRect(), AddRectFilled(), PathRect(): enable rounding top-left corner only (when rounding > 0.0f, we default to all corners). Was 0x01. - ImDrawFlags_RoundCornersTopRight = 1 << 5, // AddRect(), AddRectFilled(), PathRect(): enable rounding top-right corner only (when rounding > 0.0f, we default to all corners). Was 0x02. - ImDrawFlags_RoundCornersBottomLeft = 1 << 6, // AddRect(), AddRectFilled(), PathRect(): enable rounding bottom-left corner only (when rounding > 0.0f, we default to all corners). Was 0x04. - ImDrawFlags_RoundCornersBottomRight = 1 << 7, // AddRect(), AddRectFilled(), PathRect(): enable rounding bottom-right corner only (when rounding > 0.0f, we default to all corners). Wax 0x08. - ImDrawFlags_RoundCornersNone = 1 << 8, // AddRect(), AddRectFilled(), PathRect(): disable rounding on all corners (when rounding > 0.0f). This is NOT zero, NOT an implicit flag! - ImDrawFlags_RoundCornersTop = ImDrawFlags_RoundCornersTopLeft | ImDrawFlags_RoundCornersTopRight, - ImDrawFlags_RoundCornersBottom = ImDrawFlags_RoundCornersBottomLeft | ImDrawFlags_RoundCornersBottomRight, - ImDrawFlags_RoundCornersLeft = ImDrawFlags_RoundCornersBottomLeft | ImDrawFlags_RoundCornersTopLeft, - ImDrawFlags_RoundCornersRight = ImDrawFlags_RoundCornersBottomRight | ImDrawFlags_RoundCornersTopRight, - ImDrawFlags_RoundCornersAll = ImDrawFlags_RoundCornersTopLeft | ImDrawFlags_RoundCornersTopRight | ImDrawFlags_RoundCornersBottomLeft | ImDrawFlags_RoundCornersBottomRight, - ImDrawFlags_RoundCornersDefault_ = ImDrawFlags_RoundCornersAll, // Default to ALL corners if none of the _RoundCornersXX flags are specified. - ImDrawFlags_RoundCornersMask_ = ImDrawFlags_RoundCornersAll | ImDrawFlags_RoundCornersNone, -}; - -// Flags for ImDrawList instance. Those are set automatically by ImGui:: functions from ImGuiIO settings, and generally not manipulated directly. -// It is however possible to temporarily alter flags between calls to ImDrawList:: functions. -enum ImDrawListFlags_ -{ - ImDrawListFlags_None = 0, - ImDrawListFlags_AntiAliasedLines = 1 << 0, // Enable anti-aliased lines/borders (*2 the number of triangles for 1.0f wide line or lines thin enough to be drawn using textures, otherwise *3 the number of triangles) - ImDrawListFlags_AntiAliasedLinesUseTex = 1 << 1, // Enable anti-aliased lines/borders using textures when possible. Require backend to render with bilinear filtering (NOT point/nearest filtering). - ImDrawListFlags_AntiAliasedFill = 1 << 2, // Enable anti-aliased edge around filled shapes (rounded rectangles, circles). - ImDrawListFlags_AllowVtxOffset = 1 << 3, // Can emit 'VtxOffset > 0' to allow large meshes. Set when 'ImGuiBackendFlags_RendererHasVtxOffset' is enabled. -}; - -// Draw command list -// This is the low-level list of polygons that ImGui:: functions are filling. At the end of the frame, -// all command lists are passed to your ImGuiIO::RenderDrawListFn function for rendering. -// Each dear imgui window contains its own ImDrawList. You can use ImGui::GetWindowDrawList() to -// access the current window draw list and draw custom primitives. -// You can interleave normal ImGui:: calls and adding primitives to the current draw list. -// In single viewport mode, top-left is == GetMainViewport()->Pos (generally 0,0), bottom-right is == GetMainViewport()->Pos+Size (generally io.DisplaySize). -// You are totally free to apply whatever transformation matrix to want to the data (depending on the use of the transformation you may want to apply it to ClipRect as well!) -// Important: Primitives are always added to the list and not culled (culling is done at higher-level by ImGui:: functions), if you use this API a lot consider coarse culling your drawn objects. -struct ImDrawList -{ - // This is what you have to render - ImVector CmdBuffer; // Draw commands. Typically 1 command = 1 GPU draw call, unless the command is a callback. - ImVector IdxBuffer; // Index buffer. Each command consume ImDrawCmd::ElemCount of those - ImVector VtxBuffer; // Vertex buffer. - ImDrawListFlags Flags; // Flags, you may poke into these to adjust anti-aliasing settings per-primitive. - - // [Internal, used while building lists] - unsigned int _VtxCurrentIdx; // [Internal] generally == VtxBuffer.Size unless we are past 64K vertices, in which case this gets reset to 0. - ImDrawListSharedData* _Data; // Pointer to shared draw data (you can use ImGui::GetDrawListSharedData() to get the one from current ImGui context) - const char* _OwnerName; // Pointer to owner window's name for debugging - ImDrawVert* _VtxWritePtr; // [Internal] point within VtxBuffer.Data after each add command (to avoid using the ImVector<> operators too much) - ImDrawIdx* _IdxWritePtr; // [Internal] point within IdxBuffer.Data after each add command (to avoid using the ImVector<> operators too much) - ImVector _ClipRectStack; // [Internal] - ImVector _TextureIdStack; // [Internal] - ImVector _Path; // [Internal] current path building - ImDrawCmdHeader _CmdHeader; // [Internal] template of active commands. Fields should match those of CmdBuffer.back(). - ImDrawListSplitter _Splitter; // [Internal] for channels api (note: prefer using your own persistent instance of ImDrawListSplitter!) - float _FringeScale; // [Internal] anti-alias fringe is scaled by this value, this helps to keep things sharp while zooming at vertex buffer content - - // If you want to create ImDrawList instances, pass them ImGui::GetDrawListSharedData() or create and use your own ImDrawListSharedData (so you can use ImDrawList without ImGui) - ImDrawList(ImDrawListSharedData* shared_data) { memset(this, 0, sizeof(*this)); _Data = shared_data; } - - ~ImDrawList() { _ClearFreeMemory(); } - IMGUI_API void PushClipRect(const ImVec2& clip_rect_min, const ImVec2& clip_rect_max, bool intersect_with_current_clip_rect = false); // Render-level scissoring. This is passed down to your render function but not used for CPU-side coarse clipping. Prefer using higher-level ImGui::PushClipRect() to affect logic (hit-testing and widget culling) - IMGUI_API void PushClipRectFullScreen(); - IMGUI_API void PopClipRect(); - IMGUI_API void PushTextureID(ImTextureID texture_id); - IMGUI_API void PopTextureID(); - inline ImVec2 GetClipRectMin() const { const ImVec4& cr = _ClipRectStack.back(); return ImVec2(cr.x, cr.y); } - inline ImVec2 GetClipRectMax() const { const ImVec4& cr = _ClipRectStack.back(); return ImVec2(cr.z, cr.w); } - - // Primitives - // - Filled shapes must always use clockwise winding order. The anti-aliasing fringe depends on it. Counter-clockwise shapes will have "inward" anti-aliasing. - // - For rectangular primitives, "p_min" and "p_max" represent the upper-left and lower-right corners. - // - For circle primitives, use "num_segments == 0" to automatically calculate tessellation (preferred). - // In older versions (until Dear ImGui 1.77) the AddCircle functions defaulted to num_segments == 12. - // In future versions we will use textures to provide cheaper and higher-quality circles. - // Use AddNgon() and AddNgonFilled() functions if you need to guarantee a specific number of sides. - IMGUI_API void AddLine(const ImVec2& p1, const ImVec2& p2, ImU32 col, float thickness = 1.0f); - IMGUI_API void AddRect(const ImVec2& p_min, const ImVec2& p_max, ImU32 col, float rounding = 0.0f, ImDrawFlags flags = 0, float thickness = 1.0f); // a: upper-left, b: lower-right (== upper-left + size) - IMGUI_API void AddRectFilled(const ImVec2& p_min, const ImVec2& p_max, ImU32 col, float rounding = 0.0f, ImDrawFlags flags = 0); // a: upper-left, b: lower-right (== upper-left + size) - IMGUI_API void AddRectFilledMultiColor(const ImVec2& p_min, const ImVec2& p_max, ImU32 col_upr_left, ImU32 col_upr_right, ImU32 col_bot_right, ImU32 col_bot_left); - IMGUI_API void AddQuad(const ImVec2& p1, const ImVec2& p2, const ImVec2& p3, const ImVec2& p4, ImU32 col, float thickness = 1.0f); - IMGUI_API void AddQuadFilled(const ImVec2& p1, const ImVec2& p2, const ImVec2& p3, const ImVec2& p4, ImU32 col); - IMGUI_API void AddTriangle(const ImVec2& p1, const ImVec2& p2, const ImVec2& p3, ImU32 col, float thickness = 1.0f); - IMGUI_API void AddTriangleFilled(const ImVec2& p1, const ImVec2& p2, const ImVec2& p3, ImU32 col); - IMGUI_API void AddCircle(const ImVec2& center, float radius, ImU32 col, int num_segments = 0, float thickness = 1.0f); - IMGUI_API void AddCircleFilled(const ImVec2& center, float radius, ImU32 col, int num_segments = 0); - IMGUI_API void AddNgon(const ImVec2& center, float radius, ImU32 col, int num_segments, float thickness = 1.0f); - IMGUI_API void AddNgonFilled(const ImVec2& center, float radius, ImU32 col, int num_segments); - IMGUI_API void AddEllipse(const ImVec2& center, float radius_x, float radius_y, ImU32 col, float rot = 0.0f, int num_segments = 0, float thickness = 1.0f); - IMGUI_API void AddEllipseFilled(const ImVec2& center, float radius_x, float radius_y, ImU32 col, float rot = 0.0f, int num_segments = 0); - IMGUI_API void AddText(const ImVec2& pos, ImU32 col, const char* text_begin, const char* text_end = NULL); - IMGUI_API void AddText(const ImFont* font, float font_size, const ImVec2& pos, ImU32 col, const char* text_begin, const char* text_end = NULL, float wrap_width = 0.0f, const ImVec4* cpu_fine_clip_rect = NULL); - IMGUI_API void AddPolyline(const ImVec2* points, int num_points, ImU32 col, ImDrawFlags flags, float thickness); - IMGUI_API void AddConvexPolyFilled(const ImVec2* points, int num_points, ImU32 col); - IMGUI_API void AddBezierCubic(const ImVec2& p1, const ImVec2& p2, const ImVec2& p3, const ImVec2& p4, ImU32 col, float thickness, int num_segments = 0); // Cubic Bezier (4 control points) - IMGUI_API void AddBezierQuadratic(const ImVec2& p1, const ImVec2& p2, const ImVec2& p3, ImU32 col, float thickness, int num_segments = 0); // Quadratic Bezier (3 control points) - - // Image primitives - // - Read FAQ to understand what ImTextureID is. - // - "p_min" and "p_max" represent the upper-left and lower-right corners of the rectangle. - // - "uv_min" and "uv_max" represent the normalized texture coordinates to use for those corners. Using (0,0)->(1,1) texture coordinates will generally display the entire texture. - IMGUI_API void AddImage(ImTextureID user_texture_id, const ImVec2& p_min, const ImVec2& p_max, const ImVec2& uv_min = ImVec2(0, 0), const ImVec2& uv_max = ImVec2(1, 1), ImU32 col = IM_COL32_WHITE); - IMGUI_API void AddImageQuad(ImTextureID user_texture_id, const ImVec2& p1, const ImVec2& p2, const ImVec2& p3, const ImVec2& p4, const ImVec2& uv1 = ImVec2(0, 0), const ImVec2& uv2 = ImVec2(1, 0), const ImVec2& uv3 = ImVec2(1, 1), const ImVec2& uv4 = ImVec2(0, 1), ImU32 col = IM_COL32_WHITE); - IMGUI_API void AddImageRounded(ImTextureID user_texture_id, const ImVec2& p_min, const ImVec2& p_max, const ImVec2& uv_min, const ImVec2& uv_max, ImU32 col, float rounding, ImDrawFlags flags = 0); - - // Stateful path API, add points then finish with PathFillConvex() or PathStroke() - // - Filled shapes must always use clockwise winding order. The anti-aliasing fringe depends on it. Counter-clockwise shapes will have "inward" anti-aliasing. - inline void PathClear() { _Path.Size = 0; } - inline void PathLineTo(const ImVec2& pos) { _Path.push_back(pos); } - inline void PathLineToMergeDuplicate(const ImVec2& pos) { if (_Path.Size == 0 || memcmp(&_Path.Data[_Path.Size - 1], &pos, 8) != 0) _Path.push_back(pos); } - inline void PathFillConvex(ImU32 col) { AddConvexPolyFilled(_Path.Data, _Path.Size, col); _Path.Size = 0; } - inline void PathStroke(ImU32 col, ImDrawFlags flags = 0, float thickness = 1.0f) { AddPolyline(_Path.Data, _Path.Size, col, flags, thickness); _Path.Size = 0; } - IMGUI_API void PathArcTo(const ImVec2& center, float radius, float a_min, float a_max, int num_segments = 0); - IMGUI_API void PathArcToFast(const ImVec2& center, float radius, int a_min_of_12, int a_max_of_12); // Use precomputed angles for a 12 steps circle - IMGUI_API void PathEllipticalArcTo(const ImVec2& center, float radius_x, float radius_y, float rot, float a_min, float a_max, int num_segments = 0); // Ellipse - IMGUI_API void PathBezierCubicCurveTo(const ImVec2& p2, const ImVec2& p3, const ImVec2& p4, int num_segments = 0); // Cubic Bezier (4 control points) - IMGUI_API void PathBezierQuadraticCurveTo(const ImVec2& p2, const ImVec2& p3, int num_segments = 0); // Quadratic Bezier (3 control points) - IMGUI_API void PathRect(const ImVec2& rect_min, const ImVec2& rect_max, float rounding = 0.0f, ImDrawFlags flags = 0); - - // Advanced - IMGUI_API void AddCallback(ImDrawCallback callback, void* callback_data); // Your rendering function must check for 'UserCallback' in ImDrawCmd and call the function instead of rendering triangles. - IMGUI_API void AddDrawCmd(); // This is useful if you need to forcefully create a new draw call (to allow for dependent rendering / blending). Otherwise primitives are merged into the same draw-call as much as possible - IMGUI_API ImDrawList* CloneOutput() const; // Create a clone of the CmdBuffer/IdxBuffer/VtxBuffer. - - // Advanced: Channels - // - Use to split render into layers. By switching channels to can render out-of-order (e.g. submit FG primitives before BG primitives) - // - Use to minimize draw calls (e.g. if going back-and-forth between multiple clipping rectangles, prefer to append into separate channels then merge at the end) - // - This API shouldn't have been in ImDrawList in the first place! - // Prefer using your own persistent instance of ImDrawListSplitter as you can stack them. - // Using the ImDrawList::ChannelsXXXX you cannot stack a split over another. - inline void ChannelsSplit(int count) { _Splitter.Split(this, count); } - inline void ChannelsMerge() { _Splitter.Merge(this); } - inline void ChannelsSetCurrent(int n) { _Splitter.SetCurrentChannel(this, n); } - - // Advanced: Primitives allocations - // - We render triangles (three vertices) - // - All primitives needs to be reserved via PrimReserve() beforehand. - IMGUI_API void PrimReserve(int idx_count, int vtx_count); - IMGUI_API void PrimUnreserve(int idx_count, int vtx_count); - IMGUI_API void PrimRect(const ImVec2& a, const ImVec2& b, ImU32 col); // Axis aligned rectangle (composed of two triangles) - IMGUI_API void PrimRectUV(const ImVec2& a, const ImVec2& b, const ImVec2& uv_a, const ImVec2& uv_b, ImU32 col); - IMGUI_API void PrimQuadUV(const ImVec2& a, const ImVec2& b, const ImVec2& c, const ImVec2& d, const ImVec2& uv_a, const ImVec2& uv_b, const ImVec2& uv_c, const ImVec2& uv_d, ImU32 col); - inline void PrimWriteVtx(const ImVec2& pos, const ImVec2& uv, ImU32 col) { _VtxWritePtr->pos = pos; _VtxWritePtr->uv = uv; _VtxWritePtr->col = col; _VtxWritePtr++; _VtxCurrentIdx++; } - inline void PrimWriteIdx(ImDrawIdx idx) { *_IdxWritePtr = idx; _IdxWritePtr++; } - inline void PrimVtx(const ImVec2& pos, const ImVec2& uv, ImU32 col) { PrimWriteIdx((ImDrawIdx)_VtxCurrentIdx); PrimWriteVtx(pos, uv, col); } // Write vertex with unique index - - // Obsolete names - //inline void AddBezierCurve(const ImVec2& p1, const ImVec2& p2, const ImVec2& p3, const ImVec2& p4, ImU32 col, float thickness, int num_segments = 0) { AddBezierCubic(p1, p2, p3, p4, col, thickness, num_segments); } // OBSOLETED in 1.80 (Jan 2021) - //inline void PathBezierCurveTo(const ImVec2& p2, const ImVec2& p3, const ImVec2& p4, int num_segments = 0) { PathBezierCubicCurveTo(p2, p3, p4, num_segments); } // OBSOLETED in 1.80 (Jan 2021) - - // [Internal helpers] - IMGUI_API void _ResetForNewFrame(); - IMGUI_API void _ClearFreeMemory(); - IMGUI_API void _PopUnusedDrawCmd(); - IMGUI_API void _TryMergeDrawCmds(); - IMGUI_API void _OnChangedClipRect(); - IMGUI_API void _OnChangedTextureID(); - IMGUI_API void _OnChangedVtxOffset(); - IMGUI_API int _CalcCircleAutoSegmentCount(float radius) const; - IMGUI_API void _PathArcToFastEx(const ImVec2& center, float radius, int a_min_sample, int a_max_sample, int a_step); - IMGUI_API void _PathArcToN(const ImVec2& center, float radius, float a_min, float a_max, int num_segments); -}; - -// All draw data to render a Dear ImGui frame -// (NB: the style and the naming convention here is a little inconsistent, we currently preserve them for backward compatibility purpose, -// as this is one of the oldest structure exposed by the library! Basically, ImDrawList == CmdList) -struct ImDrawData -{ - bool Valid; // Only valid after Render() is called and before the next NewFrame() is called. - int CmdListsCount; // Number of ImDrawList* to render - int TotalIdxCount; // For convenience, sum of all ImDrawList's IdxBuffer.Size - int TotalVtxCount; // For convenience, sum of all ImDrawList's VtxBuffer.Size - ImVector CmdLists; // Array of ImDrawList* to render. The ImDrawLists are owned by ImGuiContext and only pointed to from here. - ImVec2 DisplayPos; // Top-left position of the viewport to render (== top-left of the orthogonal projection matrix to use) (== GetMainViewport()->Pos for the main viewport, == (0.0) in most single-viewport applications) - ImVec2 DisplaySize; // Size of the viewport to render (== GetMainViewport()->Size for the main viewport, == io.DisplaySize in most single-viewport applications) - ImVec2 FramebufferScale; // Amount of pixels for each unit of DisplaySize. Based on io.DisplayFramebufferScale. Generally (1,1) on normal display, (2,2) on OSX with Retina display. - ImGuiViewport* OwnerViewport; // Viewport carrying the ImDrawData instance, might be of use to the renderer (generally not). - - // Functions - ImDrawData() { Clear(); } - IMGUI_API void Clear(); - IMGUI_API void AddDrawList(ImDrawList* draw_list); // Helper to add an external draw list into an existing ImDrawData. - IMGUI_API void DeIndexAllBuffers(); // Helper to convert all buffers from indexed to non-indexed, in case you cannot render indexed. Note: this is slow and most likely a waste of resources. Always prefer indexed rendering! - IMGUI_API void ScaleClipRects(const ImVec2& fb_scale); // Helper to scale the ClipRect field of each ImDrawCmd. Use if your final output buffer is at a different scale than Dear ImGui expects, or if there is a difference between your window resolution and framebuffer resolution. -}; - -//----------------------------------------------------------------------------- -// [SECTION] Font API (ImFontConfig, ImFontGlyph, ImFontAtlasFlags, ImFontAtlas, ImFontGlyphRangesBuilder, ImFont) -//----------------------------------------------------------------------------- - -struct ImFontConfig -{ - void* FontData; // // TTF/OTF data - int FontDataSize; // // TTF/OTF data size - bool FontDataOwnedByAtlas; // true // TTF/OTF data ownership taken by the container ImFontAtlas (will delete memory itself). - int FontNo; // 0 // Index of font within TTF/OTF file - float SizePixels; // // Size in pixels for rasterizer (more or less maps to the resulting font height). - int OversampleH; // 2 // Rasterize at higher quality for sub-pixel positioning. Note the difference between 2 and 3 is minimal. You can reduce this to 1 for large glyphs save memory. Read https://github.com/nothings/stb/blob/master/tests/oversample/README.md for details. - int OversampleV; // 1 // Rasterize at higher quality for sub-pixel positioning. This is not really useful as we don't use sub-pixel positions on the Y axis. - bool PixelSnapH; // false // Align every glyph to pixel boundary. Useful e.g. if you are merging a non-pixel aligned font with the default font. If enabled, you can set OversampleH/V to 1. - ImVec2 GlyphExtraSpacing; // 0, 0 // Extra spacing (in pixels) between glyphs. Only X axis is supported for now. - ImVec2 GlyphOffset; // 0, 0 // Offset all glyphs from this font input. - const ImWchar* GlyphRanges; // NULL // THE ARRAY DATA NEEDS TO PERSIST AS LONG AS THE FONT IS ALIVE. Pointer to a user-provided list of Unicode range (2 value per range, values are inclusive, zero-terminated list). - float GlyphMinAdvanceX; // 0 // Minimum AdvanceX for glyphs, set Min to align font icons, set both Min/Max to enforce mono-space font - float GlyphMaxAdvanceX; // FLT_MAX // Maximum AdvanceX for glyphs - bool MergeMode; // false // Merge into previous ImFont, so you can combine multiple inputs font into one ImFont (e.g. ASCII font + icons + Japanese glyphs). You may want to use GlyphOffset.y when merge font of different heights. - unsigned int FontBuilderFlags; // 0 // Settings for custom font builder. THIS IS BUILDER IMPLEMENTATION DEPENDENT. Leave as zero if unsure. - float RasterizerMultiply; // 1.0f // Brighten (>1.0f) or darken (<1.0f) font output. Brightening small fonts may be a good workaround to make them more readable. - ImWchar EllipsisChar; // -1 // Explicitly specify unicode codepoint of ellipsis character. When fonts are being merged first specified ellipsis will be used. - - // [Internal] - char Name[40]; // Name (strictly to ease debugging) - ImFont* DstFont; - - IMGUI_API ImFontConfig(); -}; - -// Hold rendering data for one glyph. -// (Note: some language parsers may fail to convert the 31+1 bitfield members, in this case maybe drop store a single u32 or we can rework this) -struct ImFontGlyph -{ - unsigned int Colored : 1; // Flag to indicate glyph is colored and should generally ignore tinting (make it usable with no shift on little-endian as this is used in loops) - unsigned int Visible : 1; // Flag to indicate glyph has no visible pixels (e.g. space). Allow early out when rendering. - unsigned int Codepoint : 30; // 0x0000..0x10FFFF - float AdvanceX; // Distance to next character (= data from font + ImFontConfig::GlyphExtraSpacing.x baked in) - float X0, Y0, X1, Y1; // Glyph corners - float U0, V0, U1, V1; // Texture coordinates -}; - -// Helper to build glyph ranges from text/string data. Feed your application strings/characters to it then call BuildRanges(). -// This is essentially a tightly packed of vector of 64k booleans = 8KB storage. -struct ImFontGlyphRangesBuilder -{ - ImVector UsedChars; // Store 1-bit per Unicode code point (0=unused, 1=used) - - ImFontGlyphRangesBuilder() { Clear(); } - inline void Clear() { int size_in_bytes = (IM_UNICODE_CODEPOINT_MAX + 1) / 8; UsedChars.resize(size_in_bytes / (int)sizeof(ImU32)); memset(UsedChars.Data, 0, (size_t)size_in_bytes); } - inline bool GetBit(size_t n) const { int off = (int)(n >> 5); ImU32 mask = 1u << (n & 31); return (UsedChars[off] & mask) != 0; } // Get bit n in the array - inline void SetBit(size_t n) { int off = (int)(n >> 5); ImU32 mask = 1u << (n & 31); UsedChars[off] |= mask; } // Set bit n in the array - inline void AddChar(ImWchar c) { SetBit(c); } // Add character - IMGUI_API void AddText(const char* text, const char* text_end = NULL); // Add string (each character of the UTF-8 string are added) - IMGUI_API void AddRanges(const ImWchar* ranges); // Add ranges, e.g. builder.AddRanges(ImFontAtlas::GetGlyphRangesDefault()) to force add all of ASCII/Latin+Ext - IMGUI_API void BuildRanges(ImVector* out_ranges); // Output new ranges -}; - -// See ImFontAtlas::AddCustomRectXXX functions. -struct ImFontAtlasCustomRect -{ - unsigned short Width, Height; // Input // Desired rectangle dimension - unsigned short X, Y; // Output // Packed position in Atlas - unsigned int GlyphID; // Input // For custom font glyphs only (ID < 0x110000) - float GlyphAdvanceX; // Input // For custom font glyphs only: glyph xadvance - ImVec2 GlyphOffset; // Input // For custom font glyphs only: glyph display offset - ImFont* Font; // Input // For custom font glyphs only: target font - ImFontAtlasCustomRect() { Width = Height = 0; X = Y = 0xFFFF; GlyphID = 0; GlyphAdvanceX = 0.0f; GlyphOffset = ImVec2(0, 0); Font = NULL; } - bool IsPacked() const { return X != 0xFFFF; } -}; - -// Flags for ImFontAtlas build -enum ImFontAtlasFlags_ -{ - ImFontAtlasFlags_None = 0, - ImFontAtlasFlags_NoPowerOfTwoHeight = 1 << 0, // Don't round the height to next power of two - ImFontAtlasFlags_NoMouseCursors = 1 << 1, // Don't build software mouse cursors into the atlas (save a little texture memory) - ImFontAtlasFlags_NoBakedLines = 1 << 2, // Don't build thick line textures into the atlas (save a little texture memory, allow support for point/nearest filtering). The AntiAliasedLinesUseTex features uses them, otherwise they will be rendered using polygons (more expensive for CPU/GPU). -}; - -// Load and rasterize multiple TTF/OTF fonts into a same texture. The font atlas will build a single texture holding: -// - One or more fonts. -// - Custom graphics data needed to render the shapes needed by Dear ImGui. -// - Mouse cursor shapes for software cursor rendering (unless setting 'Flags |= ImFontAtlasFlags_NoMouseCursors' in the font atlas). -// It is the user-code responsibility to setup/build the atlas, then upload the pixel data into a texture accessible by your graphics api. -// - Optionally, call any of the AddFont*** functions. If you don't call any, the default font embedded in the code will be loaded for you. -// - Call GetTexDataAsAlpha8() or GetTexDataAsRGBA32() to build and retrieve pixels data. -// - Upload the pixels data into a texture within your graphics system (see imgui_impl_xxxx.cpp examples) -// - Call SetTexID(my_tex_id); and pass the pointer/identifier to your texture in a format natural to your graphics API. -// This value will be passed back to you during rendering to identify the texture. Read FAQ entry about ImTextureID for more details. -// Common pitfalls: -// - If you pass a 'glyph_ranges' array to AddFont*** functions, you need to make sure that your array persist up until the -// atlas is build (when calling GetTexData*** or Build()). We only copy the pointer, not the data. -// - Important: By default, AddFontFromMemoryTTF() takes ownership of the data. Even though we are not writing to it, we will free the pointer on destruction. -// You can set font_cfg->FontDataOwnedByAtlas=false to keep ownership of your data and it won't be freed, -// - Even though many functions are suffixed with "TTF", OTF data is supported just as well. -// - This is an old API and it is currently awkward for those and various other reasons! We will address them in the future! -struct ImFontAtlas -{ - IMGUI_API ImFontAtlas(); - IMGUI_API ~ImFontAtlas(); - IMGUI_API ImFont* AddFont(const ImFontConfig* font_cfg); - IMGUI_API ImFont* AddFontDefault(const ImFontConfig* font_cfg = NULL); - IMGUI_API ImFont* AddFontFromFileTTF(const char* filename, float size_pixels, const ImFontConfig* font_cfg = NULL, const ImWchar* glyph_ranges = NULL); - IMGUI_API ImFont* AddFontFromMemoryTTF(void* font_data, int font_data_size, float size_pixels, const ImFontConfig* font_cfg = NULL, const ImWchar* glyph_ranges = NULL); // Note: Transfer ownership of 'ttf_data' to ImFontAtlas! Will be deleted after destruction of the atlas. Set font_cfg->FontDataOwnedByAtlas=false to keep ownership of your data and it won't be freed. - IMGUI_API ImFont* AddFontFromMemoryCompressedTTF(const void* compressed_font_data, int compressed_font_data_size, float size_pixels, const ImFontConfig* font_cfg = NULL, const ImWchar* glyph_ranges = NULL); // 'compressed_font_data' still owned by caller. Compress with binary_to_compressed_c.cpp. - IMGUI_API ImFont* AddFontFromMemoryCompressedBase85TTF(const char* compressed_font_data_base85, float size_pixels, const ImFontConfig* font_cfg = NULL, const ImWchar* glyph_ranges = NULL); // 'compressed_font_data_base85' still owned by caller. Compress with binary_to_compressed_c.cpp with -base85 parameter. - IMGUI_API void ClearInputData(); // Clear input data (all ImFontConfig structures including sizes, TTF data, glyph ranges, etc.) = all the data used to build the texture and fonts. - IMGUI_API void ClearTexData(); // Clear output texture data (CPU side). Saves RAM once the texture has been copied to graphics memory. - IMGUI_API void ClearFonts(); // Clear output font data (glyphs storage, UV coordinates). - IMGUI_API void Clear(); // Clear all input and output. - - // Build atlas, retrieve pixel data. - // User is in charge of copying the pixels into graphics memory (e.g. create a texture with your engine). Then store your texture handle with SetTexID(). - // The pitch is always = Width * BytesPerPixels (1 or 4) - // Building in RGBA32 format is provided for convenience and compatibility, but note that unless you manually manipulate or copy color data into - // the texture (e.g. when using the AddCustomRect*** api), then the RGB pixels emitted will always be white (~75% of memory/bandwidth waste. - IMGUI_API bool Build(); // Build pixels data. This is called automatically for you by the GetTexData*** functions. - IMGUI_API void GetTexDataAsAlpha8(unsigned char** out_pixels, int* out_width, int* out_height, int* out_bytes_per_pixel = NULL); // 1 byte per-pixel - IMGUI_API void GetTexDataAsRGBA32(unsigned char** out_pixels, int* out_width, int* out_height, int* out_bytes_per_pixel = NULL); // 4 bytes-per-pixel - bool IsBuilt() const { return Fonts.Size > 0 && TexReady; } // Bit ambiguous: used to detect when user didn't build texture but effectively we should check TexID != 0 except that would be backend dependent... - void SetTexID(ImTextureID id) { TexID = id; } - - //------------------------------------------- - // Glyph Ranges - //------------------------------------------- - - // Helpers to retrieve list of common Unicode ranges (2 value per range, values are inclusive, zero-terminated list) - // NB: Make sure that your string are UTF-8 and NOT in your local code page. - // Read https://github.com/ocornut/imgui/blob/master/docs/FONTS.md/#about-utf-8-encoding for details. - // NB: Consider using ImFontGlyphRangesBuilder to build glyph ranges from textual data. - IMGUI_API const ImWchar* GetGlyphRangesDefault(); // Basic Latin, Extended Latin - IMGUI_API const ImWchar* GetGlyphRangesGreek(); // Default + Greek and Coptic - IMGUI_API const ImWchar* GetGlyphRangesKorean(); // Default + Korean characters - IMGUI_API const ImWchar* GetGlyphRangesJapanese(); // Default + Hiragana, Katakana, Half-Width, Selection of 2999 Ideographs - IMGUI_API const ImWchar* GetGlyphRangesChineseFull(); // Default + Half-Width + Japanese Hiragana/Katakana + full set of about 21000 CJK Unified Ideographs - IMGUI_API const ImWchar* GetGlyphRangesChineseSimplifiedCommon();// Default + Half-Width + Japanese Hiragana/Katakana + set of 2500 CJK Unified Ideographs for common simplified Chinese - IMGUI_API const ImWchar* GetGlyphRangesCyrillic(); // Default + about 400 Cyrillic characters - IMGUI_API const ImWchar* GetGlyphRangesThai(); // Default + Thai characters - IMGUI_API const ImWchar* GetGlyphRangesVietnamese(); // Default + Vietnamese characters - - //------------------------------------------- - // [BETA] Custom Rectangles/Glyphs API - //------------------------------------------- - - // You can request arbitrary rectangles to be packed into the atlas, for your own purposes. - // - After calling Build(), you can query the rectangle position and render your pixels. - // - If you render colored output, set 'atlas->TexPixelsUseColors = true' as this may help some backends decide of prefered texture format. - // - You can also request your rectangles to be mapped as font glyph (given a font + Unicode point), - // so you can render e.g. custom colorful icons and use them as regular glyphs. - // - Read docs/FONTS.md for more details about using colorful icons. - // - Note: this API may be redesigned later in order to support multi-monitor varying DPI settings. - IMGUI_API int AddCustomRectRegular(int width, int height); - IMGUI_API int AddCustomRectFontGlyph(ImFont* font, ImWchar id, int width, int height, float advance_x, const ImVec2& offset = ImVec2(0, 0)); - ImFontAtlasCustomRect* GetCustomRectByIndex(int index) { IM_ASSERT(index >= 0); return &CustomRects[index]; } - - // [Internal] - IMGUI_API void CalcCustomRectUV(const ImFontAtlasCustomRect* rect, ImVec2* out_uv_min, ImVec2* out_uv_max) const; - IMGUI_API bool GetMouseCursorTexData(ImGuiMouseCursor cursor, ImVec2* out_offset, ImVec2* out_size, ImVec2 out_uv_border[2], ImVec2 out_uv_fill[2]); - - //------------------------------------------- - // Members - //------------------------------------------- - - ImFontAtlasFlags Flags; // Build flags (see ImFontAtlasFlags_) - ImTextureID TexID; // User data to refer to the texture once it has been uploaded to user's graphic systems. It is passed back to you during rendering via the ImDrawCmd structure. - int TexDesiredWidth; // Texture width desired by user before Build(). Must be a power-of-two. If have many glyphs your graphics API have texture size restrictions you may want to increase texture width to decrease height. - int TexGlyphPadding; // Padding between glyphs within texture in pixels. Defaults to 1. If your rendering method doesn't rely on bilinear filtering you may set this to 0 (will also need to set AntiAliasedLinesUseTex = false). - bool Locked; // Marked as Locked by ImGui::NewFrame() so attempt to modify the atlas will assert. - void* UserData; // Store your own atlas related user-data (if e.g. you have multiple font atlas). - - // [Internal] - // NB: Access texture data via GetTexData*() calls! Which will setup a default font for you. - bool TexReady; // Set when texture was built matching current font input - bool TexPixelsUseColors; // Tell whether our texture data is known to use colors (rather than just alpha channel), in order to help backend select a format. - unsigned char* TexPixelsAlpha8; // 1 component per pixel, each component is unsigned 8-bit. Total size = TexWidth * TexHeight - unsigned int* TexPixelsRGBA32; // 4 component per pixel, each component is unsigned 8-bit. Total size = TexWidth * TexHeight * 4 - int TexWidth; // Texture width calculated during Build(). - int TexHeight; // Texture height calculated during Build(). - ImVec2 TexUvScale; // = (1.0f/TexWidth, 1.0f/TexHeight) - ImVec2 TexUvWhitePixel; // Texture coordinates to a white pixel - ImVector Fonts; // Hold all the fonts returned by AddFont*. Fonts[0] is the default font upon calling ImGui::NewFrame(), use ImGui::PushFont()/PopFont() to change the current font. - ImVector CustomRects; // Rectangles for packing custom texture data into the atlas. - ImVector ConfigData; // Configuration data - ImVec4 TexUvLines[IM_DRAWLIST_TEX_LINES_WIDTH_MAX + 1]; // UVs for baked anti-aliased lines - - // [Internal] Font builder - const ImFontBuilderIO* FontBuilderIO; // Opaque interface to a font builder (default to stb_truetype, can be changed to use FreeType by defining IMGUI_ENABLE_FREETYPE). - unsigned int FontBuilderFlags; // Shared flags (for all fonts) for custom font builder. THIS IS BUILD IMPLEMENTATION DEPENDENT. Per-font override is also available in ImFontConfig. - - // [Internal] Packing data - int PackIdMouseCursors; // Custom texture rectangle ID for white pixel and mouse cursors - int PackIdLines; // Custom texture rectangle ID for baked anti-aliased lines - - // [Obsolete] - //typedef ImFontAtlasCustomRect CustomRect; // OBSOLETED in 1.72+ - //typedef ImFontGlyphRangesBuilder GlyphRangesBuilder; // OBSOLETED in 1.67+ -}; - -// Font runtime data and rendering -// ImFontAtlas automatically loads a default embedded font for you when you call GetTexDataAsAlpha8() or GetTexDataAsRGBA32(). -struct ImFont -{ - // Members: Hot ~20/24 bytes (for CalcTextSize) - ImVector IndexAdvanceX; // 12-16 // out // // Sparse. Glyphs->AdvanceX in a directly indexable way (cache-friendly for CalcTextSize functions which only this this info, and are often bottleneck in large UI). - float FallbackAdvanceX; // 4 // out // = FallbackGlyph->AdvanceX - float FontSize; // 4 // in // // Height of characters/line, set during loading (don't change after loading) - - // Members: Hot ~28/40 bytes (for CalcTextSize + render loop) - ImVector IndexLookup; // 12-16 // out // // Sparse. Index glyphs by Unicode code-point. - ImVector Glyphs; // 12-16 // out // // All glyphs. - const ImFontGlyph* FallbackGlyph; // 4-8 // out // = FindGlyph(FontFallbackChar) - - // Members: Cold ~32/40 bytes - ImFontAtlas* ContainerAtlas; // 4-8 // out // // What we has been loaded into - const ImFontConfig* ConfigData; // 4-8 // in // // Pointer within ContainerAtlas->ConfigData - short ConfigDataCount; // 2 // in // ~ 1 // Number of ImFontConfig involved in creating this font. Bigger than 1 when merging multiple font sources into one ImFont. - ImWchar FallbackChar; // 2 // out // = FFFD/'?' // Character used if a glyph isn't found. - ImWchar EllipsisChar; // 2 // out // = '...'/'.'// Character used for ellipsis rendering. - short EllipsisCharCount; // 1 // out // 1 or 3 - float EllipsisWidth; // 4 // out // Width - float EllipsisCharStep; // 4 // out // Step between characters when EllipsisCount > 0 - bool DirtyLookupTables; // 1 // out // - float Scale; // 4 // in // = 1.f // Base font scale, multiplied by the per-window font scale which you can adjust with SetWindowFontScale() - float Ascent, Descent; // 4+4 // out // // Ascent: distance from top to bottom of e.g. 'A' [0..FontSize] - int MetricsTotalSurface;// 4 // out // // Total surface in pixels to get an idea of the font rasterization/texture cost (not exact, we approximate the cost of padding between glyphs) - ImU8 Used4kPagesMap[(IM_UNICODE_CODEPOINT_MAX+1)/4096/8]; // 2 bytes if ImWchar=ImWchar16, 34 bytes if ImWchar==ImWchar32. Store 1-bit for each block of 4K codepoints that has one active glyph. This is mainly used to facilitate iterations across all used codepoints. - - // Methods - IMGUI_API ImFont(); - IMGUI_API ~ImFont(); - IMGUI_API const ImFontGlyph*FindGlyph(ImWchar c) const; - IMGUI_API const ImFontGlyph*FindGlyphNoFallback(ImWchar c) const; - float GetCharAdvance(ImWchar c) const { return ((int)c < IndexAdvanceX.Size) ? IndexAdvanceX[(int)c] : FallbackAdvanceX; } - bool IsLoaded() const { return ContainerAtlas != NULL; } - const char* GetDebugName() const { return ConfigData ? ConfigData->Name : ""; } - - // 'max_width' stops rendering after a certain width (could be turned into a 2d size). FLT_MAX to disable. - // 'wrap_width' enable automatic word-wrapping across multiple lines to fit into given width. 0.0f to disable. - IMGUI_API ImVec2 CalcTextSizeA(float size, float max_width, float wrap_width, const char* text_begin, const char* text_end = NULL, const char** remaining = NULL) const; // utf8 - IMGUI_API const char* CalcWordWrapPositionA(float scale, const char* text, const char* text_end, float wrap_width) const; - IMGUI_API void RenderChar(ImDrawList* draw_list, float size, const ImVec2& pos, ImU32 col, ImWchar c) const; - IMGUI_API void RenderText(ImDrawList* draw_list, float size, const ImVec2& pos, ImU32 col, const ImVec4& clip_rect, const char* text_begin, const char* text_end, float wrap_width = 0.0f, bool cpu_fine_clip = false) const; - - // [Internal] Don't use! - IMGUI_API void BuildLookupTable(); - IMGUI_API void ClearOutputData(); - IMGUI_API void GrowIndex(int new_size); - IMGUI_API void AddGlyph(const ImFontConfig* src_cfg, ImWchar c, float x0, float y0, float x1, float y1, float u0, float v0, float u1, float v1, float advance_x); - IMGUI_API void AddRemapChar(ImWchar dst, ImWchar src, bool overwrite_dst = true); // Makes 'dst' character/glyph points to 'src' character/glyph. Currently needs to be called AFTER fonts have been built. - IMGUI_API void SetGlyphVisible(ImWchar c, bool visible); - IMGUI_API bool IsGlyphRangeUnused(unsigned int c_begin, unsigned int c_last); -}; - -//----------------------------------------------------------------------------- -// [SECTION] Viewports -//----------------------------------------------------------------------------- - -// Flags stored in ImGuiViewport::Flags, giving indications to the platform backends. -enum ImGuiViewportFlags_ -{ - ImGuiViewportFlags_None = 0, - ImGuiViewportFlags_IsPlatformWindow = 1 << 0, // Represent a Platform Window - ImGuiViewportFlags_IsPlatformMonitor = 1 << 1, // Represent a Platform Monitor (unused yet) - ImGuiViewportFlags_OwnedByApp = 1 << 2, // Platform Window: Was created/managed by the user application? (rather than our backend) - ImGuiViewportFlags_NoDecoration = 1 << 3, // Platform Window: Disable platform decorations: title bar, borders, etc. (generally set all windows, but if ImGuiConfigFlags_ViewportsDecoration is set we only set this on popups/tooltips) - ImGuiViewportFlags_NoTaskBarIcon = 1 << 4, // Platform Window: Disable platform task bar icon (generally set on popups/tooltips, or all windows if ImGuiConfigFlags_ViewportsNoTaskBarIcon is set) - ImGuiViewportFlags_NoFocusOnAppearing = 1 << 5, // Platform Window: Don't take focus when created. - ImGuiViewportFlags_NoFocusOnClick = 1 << 6, // Platform Window: Don't take focus when clicked on. - ImGuiViewportFlags_NoInputs = 1 << 7, // Platform Window: Make mouse pass through so we can drag this window while peaking behind it. - ImGuiViewportFlags_NoRendererClear = 1 << 8, // Platform Window: Renderer doesn't need to clear the framebuffer ahead (because we will fill it entirely). - ImGuiViewportFlags_NoAutoMerge = 1 << 9, // Platform Window: Avoid merging this window into another host window. This can only be set via ImGuiWindowClass viewport flags override (because we need to now ahead if we are going to create a viewport in the first place!). - ImGuiViewportFlags_TopMost = 1 << 10, // Platform Window: Display on top (for tooltips only). - ImGuiViewportFlags_CanHostOtherWindows = 1 << 11, // Viewport can host multiple imgui windows (secondary viewports are associated to a single window). // FIXME: In practice there's still probably code making the assumption that this is always and only on the MainViewport. Will fix once we add support for "no main viewport". - - // Output status flags (from Platform) - ImGuiViewportFlags_IsMinimized = 1 << 12, // Platform Window: Window is minimized, can skip render. When minimized we tend to avoid using the viewport pos/size for clipping window or testing if they are contained in the viewport. - ImGuiViewportFlags_IsFocused = 1 << 13, // Platform Window: Window is focused (last call to Platform_GetWindowFocus() returned true) -}; - -// - Currently represents the Platform Window created by the application which is hosting our Dear ImGui windows. -// - With multi-viewport enabled, we extend this concept to have multiple active viewports. -// - In the future we will extend this concept further to also represent Platform Monitor and support a "no main platform window" operation mode. -// - About Main Area vs Work Area: -// - Main Area = entire viewport. -// - Work Area = entire viewport minus sections used by main menu bars (for platform windows), or by task bar (for platform monitor). -// - Windows are generally trying to stay within the Work Area of their host viewport. -struct ImGuiViewport -{ - ImGuiID ID; // Unique identifier for the viewport - ImGuiViewportFlags Flags; // See ImGuiViewportFlags_ - ImVec2 Pos; // Main Area: Position of the viewport (Dear ImGui coordinates are the same as OS desktop/native coordinates) - ImVec2 Size; // Main Area: Size of the viewport. - ImVec2 WorkPos; // Work Area: Position of the viewport minus task bars, menus bars, status bars (>= Pos) - ImVec2 WorkSize; // Work Area: Size of the viewport minus task bars, menu bars, status bars (<= Size) - float DpiScale; // 1.0f = 96 DPI = No extra scale. - ImGuiID ParentViewportId; // (Advanced) 0: no parent. Instruct the platform backend to setup a parent/child relationship between platform windows. - ImDrawData* DrawData; // The ImDrawData corresponding to this viewport. Valid after Render() and until the next call to NewFrame(). - - // Platform/Backend Dependent Data - // Our design separate the Renderer and Platform backends to facilitate combining default backends with each others. - // When our create your own backend for a custom engine, it is possible that both Renderer and Platform will be handled - // by the same system and you may not need to use all the UserData/Handle fields. - // The library never uses those fields, they are merely storage to facilitate backend implementation. - void* RendererUserData; // void* to hold custom data structure for the renderer (e.g. swap chain, framebuffers etc.). generally set by your Renderer_CreateWindow function. - void* PlatformUserData; // void* to hold custom data structure for the OS / platform (e.g. windowing info, render context). generally set by your Platform_CreateWindow function. - void* PlatformHandle; // void* for FindViewportByPlatformHandle(). (e.g. suggested to use natural platform handle such as HWND, GLFWWindow*, SDL_Window*) - void* PlatformHandleRaw; // void* to hold lower-level, platform-native window handle (under Win32 this is expected to be a HWND, unused for other platforms), when using an abstraction layer like GLFW or SDL (where PlatformHandle would be a SDL_Window*) - bool PlatformWindowCreated; // Platform window has been created (Platform_CreateWindow() has been called). This is false during the first frame where a viewport is being created. - bool PlatformRequestMove; // Platform window requested move (e.g. window was moved by the OS / host window manager, authoritative position will be OS window position) - bool PlatformRequestResize; // Platform window requested resize (e.g. window was resized by the OS / host window manager, authoritative size will be OS window size) - bool PlatformRequestClose; // Platform window requested closure (e.g. window was moved by the OS / host window manager, e.g. pressing ALT-F4) - - ImGuiViewport() { memset(this, 0, sizeof(*this)); } - ~ImGuiViewport() { IM_ASSERT(PlatformUserData == NULL && RendererUserData == NULL); } - - // Helpers - ImVec2 GetCenter() const { return ImVec2(Pos.x + Size.x * 0.5f, Pos.y + Size.y * 0.5f); } - ImVec2 GetWorkCenter() const { return ImVec2(WorkPos.x + WorkSize.x * 0.5f, WorkPos.y + WorkSize.y * 0.5f); } -}; - -//----------------------------------------------------------------------------- -// [SECTION] Platform Dependent Interfaces (for e.g. multi-viewport support) -//----------------------------------------------------------------------------- -// [BETA] (Optional) This is completely optional, for advanced users! -// If you are new to Dear ImGui and trying to integrate it into your engine, you can probably ignore this for now. -// -// This feature allows you to seamlessly drag Dear ImGui windows outside of your application viewport. -// This is achieved by creating new Platform/OS windows on the fly, and rendering into them. -// Dear ImGui manages the viewport structures, and the backend create and maintain one Platform/OS window for each of those viewports. -// -// See Glossary https://github.com/ocornut/imgui/wiki/Glossary for details about some of the terminology. -// See Thread https://github.com/ocornut/imgui/issues/1542 for gifs, news and questions about this evolving feature. -// -// About the coordinates system: -// - When multi-viewports are enabled, all Dear ImGui coordinates become absolute coordinates (same as OS coordinates!) -// - So e.g. ImGui::SetNextWindowPos(ImVec2(0,0)) will position a window relative to your primary monitor! -// - If you want to position windows relative to your main application viewport, use ImGui::GetMainViewport()->Pos as a base position. -// -// Steps to use multi-viewports in your application, when using a default backend from the examples/ folder: -// - Application: Enable feature with 'io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable'. -// - Backend: The backend initialization will setup all necessary ImGuiPlatformIO's functions and update monitors info every frame. -// - Application: In your main loop, call ImGui::UpdatePlatformWindows(), ImGui::RenderPlatformWindowsDefault() after EndFrame() or Render(). -// - Application: Fix absolute coordinates used in ImGui::SetWindowPos() or ImGui::SetNextWindowPos() calls. -// -// Steps to use multi-viewports in your application, when using a custom backend: -// - Important: THIS IS NOT EASY TO DO and comes with many subtleties not described here! -// It's also an experimental feature, so some of the requirements may evolve. -// Consider using default backends if you can. Either way, carefully follow and refer to examples/ backends for details. -// - Application: Enable feature with 'io.ConfigFlags |= ImGuiConfigFlags_ViewportsEnable'. -// - Backend: Hook ImGuiPlatformIO's Platform_* and Renderer_* callbacks (see below). -// Set 'io.BackendFlags |= ImGuiBackendFlags_PlatformHasViewports' and 'io.BackendFlags |= ImGuiBackendFlags_PlatformHasViewports'. -// Update ImGuiPlatformIO's Monitors list every frame. -// Update MousePos every frame, in absolute coordinates. -// - Application: In your main loop, call ImGui::UpdatePlatformWindows(), ImGui::RenderPlatformWindowsDefault() after EndFrame() or Render(). -// You may skip calling RenderPlatformWindowsDefault() if its API is not convenient for your needs. Read comments below. -// - Application: Fix absolute coordinates used in ImGui::SetWindowPos() or ImGui::SetNextWindowPos() calls. -// -// About ImGui::RenderPlatformWindowsDefault(): -// - This function is a mostly a _helper_ for the common-most cases, and to facilitate using default backends. -// - You can check its simple source code to understand what it does. -// It basically iterates secondary viewports and call 4 functions that are setup in ImGuiPlatformIO, if available: -// Platform_RenderWindow(), Renderer_RenderWindow(), Platform_SwapBuffers(), Renderer_SwapBuffers() -// Those functions pointers exists only for the benefit of RenderPlatformWindowsDefault(). -// - If you have very specific rendering needs (e.g. flipping multiple swap-chain simultaneously, unusual sync/threading issues, etc.), -// you may be tempted to ignore RenderPlatformWindowsDefault() and write customized code to perform your renderingg. -// You may decide to setup the platform_io's *RenderWindow and *SwapBuffers pointers and call your functions through those pointers, -// or you may decide to never setup those pointers and call your code directly. They are a convenience, not an obligatory interface. -//----------------------------------------------------------------------------- - -// (Optional) Access via ImGui::GetPlatformIO() -struct ImGuiPlatformIO -{ - //------------------------------------------------------------------ - // Input - Backend interface/functions + Monitor List - //------------------------------------------------------------------ - - // (Optional) Platform functions (e.g. Win32, GLFW, SDL2) - // For reference, the second column shows which function are generally calling the Platform Functions: - // N = ImGui::NewFrame() ~ beginning of the dear imgui frame: read info from platform/OS windows (latest size/position) - // F = ImGui::Begin(), ImGui::EndFrame() ~ during the dear imgui frame - // U = ImGui::UpdatePlatformWindows() ~ after the dear imgui frame: create and update all platform/OS windows - // R = ImGui::RenderPlatformWindowsDefault() ~ render - // D = ImGui::DestroyPlatformWindows() ~ shutdown - // The general idea is that NewFrame() we will read the current Platform/OS state, and UpdatePlatformWindows() will write to it. - // - // The functions are designed so we can mix and match 2 imgui_impl_xxxx files, one for the Platform (~window/input handling), one for Renderer. - // Custom engine backends will often provide both Platform and Renderer interfaces and so may not need to use all functions. - // Platform functions are typically called before their Renderer counterpart, apart from Destroy which are called the other way. - - // Platform function --------------------------------------------------- Called by ----- - void (*Platform_CreateWindow)(ImGuiViewport* vp); // . . U . . // Create a new platform window for the given viewport - void (*Platform_DestroyWindow)(ImGuiViewport* vp); // N . U . D // - void (*Platform_ShowWindow)(ImGuiViewport* vp); // . . U . . // Newly created windows are initially hidden so SetWindowPos/Size/Title can be called on them before showing the window - void (*Platform_SetWindowPos)(ImGuiViewport* vp, ImVec2 pos); // . . U . . // Set platform window position (given the upper-left corner of client area) - ImVec2 (*Platform_GetWindowPos)(ImGuiViewport* vp); // N . . . . // - void (*Platform_SetWindowSize)(ImGuiViewport* vp, ImVec2 size); // . . U . . // Set platform window client area size (ignoring OS decorations such as OS title bar etc.) - ImVec2 (*Platform_GetWindowSize)(ImGuiViewport* vp); // N . . . . // Get platform window client area size - void (*Platform_SetWindowFocus)(ImGuiViewport* vp); // N . . . . // Move window to front and set input focus - bool (*Platform_GetWindowFocus)(ImGuiViewport* vp); // . . U . . // - bool (*Platform_GetWindowMinimized)(ImGuiViewport* vp); // N . . . . // Get platform window minimized state. When minimized, we generally won't attempt to get/set size and contents will be culled more easily - void (*Platform_SetWindowTitle)(ImGuiViewport* vp, const char* str); // . . U . . // Set platform window title (given an UTF-8 string) - void (*Platform_SetWindowAlpha)(ImGuiViewport* vp, float alpha); // . . U . . // (Optional) Setup global transparency (not per-pixel transparency) - void (*Platform_UpdateWindow)(ImGuiViewport* vp); // . . U . . // (Optional) Called by UpdatePlatformWindows(). Optional hook to allow the platform backend from doing general book-keeping every frame. - void (*Platform_RenderWindow)(ImGuiViewport* vp, void* render_arg); // . . . R . // (Optional) Main rendering (platform side! This is often unused, or just setting a "current" context for OpenGL bindings). 'render_arg' is the value passed to RenderPlatformWindowsDefault(). - void (*Platform_SwapBuffers)(ImGuiViewport* vp, void* render_arg); // . . . R . // (Optional) Call Present/SwapBuffers (platform side! This is often unused!). 'render_arg' is the value passed to RenderPlatformWindowsDefault(). - float (*Platform_GetWindowDpiScale)(ImGuiViewport* vp); // N . . . . // (Optional) [BETA] FIXME-DPI: DPI handling: Return DPI scale for this viewport. 1.0f = 96 DPI. - void (*Platform_OnChangedViewport)(ImGuiViewport* vp); // . F . . . // (Optional) [BETA] FIXME-DPI: DPI handling: Called during Begin() every time the viewport we are outputting into changes, so backend has a chance to swap fonts to adjust style. - int (*Platform_CreateVkSurface)(ImGuiViewport* vp, ImU64 vk_inst, const void* vk_allocators, ImU64* out_vk_surface); // (Optional) For a Vulkan Renderer to call into Platform code (since the surface creation needs to tie them both). - - // (Optional) Renderer functions (e.g. DirectX, OpenGL, Vulkan) - void (*Renderer_CreateWindow)(ImGuiViewport* vp); // . . U . . // Create swap chain, frame buffers etc. (called after Platform_CreateWindow) - void (*Renderer_DestroyWindow)(ImGuiViewport* vp); // N . U . D // Destroy swap chain, frame buffers etc. (called before Platform_DestroyWindow) - void (*Renderer_SetWindowSize)(ImGuiViewport* vp, ImVec2 size); // . . U . . // Resize swap chain, frame buffers etc. (called after Platform_SetWindowSize) - void (*Renderer_RenderWindow)(ImGuiViewport* vp, void* render_arg); // . . . R . // (Optional) Clear framebuffer, setup render target, then render the viewport->DrawData. 'render_arg' is the value passed to RenderPlatformWindowsDefault(). - void (*Renderer_SwapBuffers)(ImGuiViewport* vp, void* render_arg); // . . . R . // (Optional) Call Present/SwapBuffers. 'render_arg' is the value passed to RenderPlatformWindowsDefault(). - - // (Optional) Monitor list - // - Updated by: app/backend. Update every frame to dynamically support changing monitor or DPI configuration. - // - Used by: dear imgui to query DPI info, clamp popups/tooltips within same monitor and not have them straddle monitors. - ImVector Monitors; - - //------------------------------------------------------------------ - // Output - List of viewports to render into platform windows - //------------------------------------------------------------------ - - // Viewports list (the list is updated by calling ImGui::EndFrame or ImGui::Render) - // (in the future we will attempt to organize this feature to remove the need for a "main viewport") - ImVector Viewports; // Main viewports, followed by all secondary viewports. - ImGuiPlatformIO() { memset(this, 0, sizeof(*this)); } // Zero clear -}; - -// (Optional) This is required when enabling multi-viewport. Represent the bounds of each connected monitor/display and their DPI. -// We use this information for multiple DPI support + clamping the position of popups and tooltips so they don't straddle multiple monitors. -struct ImGuiPlatformMonitor -{ - ImVec2 MainPos, MainSize; // Coordinates of the area displayed on this monitor (Min = upper left, Max = bottom right) - ImVec2 WorkPos, WorkSize; // Coordinates without task bars / side bars / menu bars. Used to avoid positioning popups/tooltips inside this region. If you don't have this info, please copy the value for MainPos/MainSize. - float DpiScale; // 1.0f = 96 DPI - void* PlatformHandle; // Backend dependant data (e.g. HMONITOR, GLFWmonitor*, SDL Display Index, NSScreen*) - ImGuiPlatformMonitor() { MainPos = MainSize = WorkPos = WorkSize = ImVec2(0, 0); DpiScale = 1.0f; PlatformHandle = NULL; } -}; - -// (Optional) Support for IME (Input Method Editor) via the io.SetPlatformImeDataFn() function. -struct ImGuiPlatformImeData -{ - bool WantVisible; // A widget wants the IME to be visible - ImVec2 InputPos; // Position of the input cursor - float InputLineHeight; // Line height - - ImGuiPlatformImeData() { memset(this, 0, sizeof(*this)); } -}; - -//----------------------------------------------------------------------------- -// [SECTION] Obsolete functions and types -// (Will be removed! Read 'API BREAKING CHANGES' section in imgui.cpp for details) -// Please keep your copy of dear imgui up to date! Occasionally set '#define IMGUI_DISABLE_OBSOLETE_FUNCTIONS' in imconfig.h to stay ahead. -//----------------------------------------------------------------------------- - -namespace ImGui -{ -#ifndef IMGUI_DISABLE_OBSOLETE_KEYIO - IMGUI_API ImGuiKey GetKeyIndex(ImGuiKey key); // map ImGuiKey_* values into legacy native key index. == io.KeyMap[key] -#else - static inline ImGuiKey GetKeyIndex(ImGuiKey key) { IM_ASSERT(key >= ImGuiKey_NamedKey_BEGIN && key < ImGuiKey_NamedKey_END && "ImGuiKey and native_index was merged together and native_index is disabled by IMGUI_DISABLE_OBSOLETE_KEYIO. Please switch to ImGuiKey."); return key; } -#endif -} - -#ifndef IMGUI_DISABLE_OBSOLETE_FUNCTIONS -namespace ImGui -{ - // OBSOLETED in 1.90.0 (from September 2023) - static inline void ShowStackToolWindow(bool* p_open = NULL) { ShowIDStackToolWindow(p_open); } - IMGUI_API bool ListBox(const char* label, int* current_item, bool (*old_callback)(void* user_data, int idx, const char** out_text), void* user_data, int items_count, int height_in_items = -1); - IMGUI_API bool Combo(const char* label, int* current_item, bool (*old_callback)(void* user_data, int idx, const char** out_text), void* user_data, int items_count, int popup_max_height_in_items = -1); - // OBSOLETED in 1.89.7 (from June 2023) - IMGUI_API void SetItemAllowOverlap(); // Use SetNextItemAllowOverlap() before item. - // OBSOLETED in 1.89.4 (from March 2023) - static inline void PushAllowKeyboardFocus(bool tab_stop) { PushTabStop(tab_stop); } - static inline void PopAllowKeyboardFocus() { PopTabStop(); } - // OBSOLETED in 1.89 (from August 2022) - IMGUI_API bool ImageButton(ImTextureID user_texture_id, const ImVec2& size, const ImVec2& uv0 = ImVec2(0, 0), const ImVec2& uv1 = ImVec2(1, 1), int frame_padding = -1, const ImVec4& bg_col = ImVec4(0, 0, 0, 0), const ImVec4& tint_col = ImVec4(1, 1, 1, 1)); // Use new ImageButton() signature (explicit item id, regular FramePadding) - // OBSOLETED in 1.88 (from May 2022) - static inline void CaptureKeyboardFromApp(bool want_capture_keyboard = true) { SetNextFrameWantCaptureKeyboard(want_capture_keyboard); } // Renamed as name was misleading + removed default value. - static inline void CaptureMouseFromApp(bool want_capture_mouse = true) { SetNextFrameWantCaptureMouse(want_capture_mouse); } // Renamed as name was misleading + removed default value. - // OBSOLETED in 1.86 (from November 2021) - IMGUI_API void CalcListClipping(int items_count, float items_height, int* out_items_display_start, int* out_items_display_end); // Calculate coarse clipping for large list of evenly sized items. Prefer using ImGuiListClipper. - - // Some of the older obsolete names along with their replacement (commented out so they are not reported in IDE) - //-- OBSOLETED in 1.85 (from August 2021) - //static inline float GetWindowContentRegionWidth() { return GetWindowContentRegionMax().x - GetWindowContentRegionMin().x; } - //-- OBSOLETED in 1.81 (from February 2021) - //static inline bool ListBoxHeader(const char* label, const ImVec2& size = ImVec2(0, 0)) { return BeginListBox(label, size); } - //static inline bool ListBoxHeader(const char* label, int items_count, int height_in_items = -1) { float height = GetTextLineHeightWithSpacing() * ((height_in_items < 0 ? ImMin(items_count, 7) : height_in_items) + 0.25f) + GetStyle().FramePadding.y * 2.0f; return BeginListBox(label, ImVec2(0.0f, height)); } // Helper to calculate size from items_count and height_in_items - //static inline void ListBoxFooter() { EndListBox(); } - //-- OBSOLETED in 1.79 (from August 2020) - //static inline void OpenPopupContextItem(const char* str_id = NULL, ImGuiMouseButton mb = 1) { OpenPopupOnItemClick(str_id, mb); } // Bool return value removed. Use IsWindowAppearing() in BeginPopup() instead. Renamed in 1.77, renamed back in 1.79. Sorry! - //-- OBSOLETED in 1.78 (from June 2020): Old drag/sliders functions that took a 'float power > 1.0f' argument instead of ImGuiSliderFlags_Logarithmic. See github.com/ocornut/imgui/issues/3361 for details. - //IMGUI_API bool DragScalar(const char* label, ImGuiDataType data_type, void* p_data, float v_speed, const void* p_min, const void* p_max, const char* format, float power = 1.0f) // OBSOLETED in 1.78 (from June 2020) - //IMGUI_API bool DragScalarN(const char* label, ImGuiDataType data_type, void* p_data, int components, float v_speed, const void* p_min, const void* p_max, const char* format, float power = 1.0f); // OBSOLETED in 1.78 (from June 2020) - //IMGUI_API bool SliderScalar(const char* label, ImGuiDataType data_type, void* p_data, const void* p_min, const void* p_max, const char* format, float power = 1.0f); // OBSOLETED in 1.78 (from June 2020) - //IMGUI_API bool SliderScalarN(const char* label, ImGuiDataType data_type, void* p_data, int components, const void* p_min, const void* p_max, const char* format, float power = 1.0f); // OBSOLETED in 1.78 (from June 2020) - //static inline bool DragFloat(const char* label, float* v, float v_speed, float v_min, float v_max, const char* format, float power = 1.0f) { return DragScalar(label, ImGuiDataType_Float, v, v_speed, &v_min, &v_max, format, power); } // OBSOLETED in 1.78 (from June 2020) - //static inline bool DragFloat2(const char* label, float v[2], float v_speed, float v_min, float v_max, const char* format, float power = 1.0f) { return DragScalarN(label, ImGuiDataType_Float, v, 2, v_speed, &v_min, &v_max, format, power); } // OBSOLETED in 1.78 (from June 2020) - //static inline bool DragFloat3(const char* label, float v[3], float v_speed, float v_min, float v_max, const char* format, float power = 1.0f) { return DragScalarN(label, ImGuiDataType_Float, v, 3, v_speed, &v_min, &v_max, format, power); } // OBSOLETED in 1.78 (from June 2020) - //static inline bool DragFloat4(const char* label, float v[4], float v_speed, float v_min, float v_max, const char* format, float power = 1.0f) { return DragScalarN(label, ImGuiDataType_Float, v, 4, v_speed, &v_min, &v_max, format, power); } // OBSOLETED in 1.78 (from June 2020) - //static inline bool SliderFloat(const char* label, float* v, float v_min, float v_max, const char* format, float power = 1.0f) { return SliderScalar(label, ImGuiDataType_Float, v, &v_min, &v_max, format, power); } // OBSOLETED in 1.78 (from June 2020) - //static inline bool SliderFloat2(const char* label, float v[2], float v_min, float v_max, const char* format, float power = 1.0f) { return SliderScalarN(label, ImGuiDataType_Float, v, 2, &v_min, &v_max, format, power); } // OBSOLETED in 1.78 (from June 2020) - //static inline bool SliderFloat3(const char* label, float v[3], float v_min, float v_max, const char* format, float power = 1.0f) { return SliderScalarN(label, ImGuiDataType_Float, v, 3, &v_min, &v_max, format, power); } // OBSOLETED in 1.78 (from June 2020) - //static inline bool SliderFloat4(const char* label, float v[4], float v_min, float v_max, const char* format, float power = 1.0f) { return SliderScalarN(label, ImGuiDataType_Float, v, 4, &v_min, &v_max, format, power); } // OBSOLETED in 1.78 (from June 2020) - //-- OBSOLETED in 1.77 and before - //static inline bool BeginPopupContextWindow(const char* str_id, ImGuiMouseButton mb, bool over_items) { return BeginPopupContextWindow(str_id, mb | (over_items ? 0 : ImGuiPopupFlags_NoOpenOverItems)); } // OBSOLETED in 1.77 (from June 2020) - //static inline void TreeAdvanceToLabelPos() { SetCursorPosX(GetCursorPosX() + GetTreeNodeToLabelSpacing()); } // OBSOLETED in 1.72 (from July 2019) - //static inline void SetNextTreeNodeOpen(bool open, ImGuiCond cond = 0) { SetNextItemOpen(open, cond); } // OBSOLETED in 1.71 (from June 2019) - //static inline float GetContentRegionAvailWidth() { return GetContentRegionAvail().x; } // OBSOLETED in 1.70 (from May 2019) - //static inline ImDrawList* GetOverlayDrawList() { return GetForegroundDrawList(); } // OBSOLETED in 1.69 (from Mar 2019) - //static inline void SetScrollHere(float ratio = 0.5f) { SetScrollHereY(ratio); } // OBSOLETED in 1.66 (from Nov 2018) - //static inline bool IsItemDeactivatedAfterChange() { return IsItemDeactivatedAfterEdit(); } // OBSOLETED in 1.63 (from Aug 2018) - //-- OBSOLETED in 1.60 and before - //static inline bool IsAnyWindowFocused() { return IsWindowFocused(ImGuiFocusedFlags_AnyWindow); } // OBSOLETED in 1.60 (from Apr 2018) - //static inline bool IsAnyWindowHovered() { return IsWindowHovered(ImGuiHoveredFlags_AnyWindow); } // OBSOLETED in 1.60 (between Dec 2017 and Apr 2018) - //static inline void ShowTestWindow() { return ShowDemoWindow(); } // OBSOLETED in 1.53 (between Oct 2017 and Dec 2017) - //static inline bool IsRootWindowFocused() { return IsWindowFocused(ImGuiFocusedFlags_RootWindow); } // OBSOLETED in 1.53 (between Oct 2017 and Dec 2017) - //static inline bool IsRootWindowOrAnyChildFocused() { return IsWindowFocused(ImGuiFocusedFlags_RootAndChildWindows); } // OBSOLETED in 1.53 (between Oct 2017 and Dec 2017) - //static inline void SetNextWindowContentWidth(float w) { SetNextWindowContentSize(ImVec2(w, 0.0f)); } // OBSOLETED in 1.53 (between Oct 2017 and Dec 2017) - //static inline float GetItemsLineHeightWithSpacing() { return GetFrameHeightWithSpacing(); } // OBSOLETED in 1.53 (between Oct 2017 and Dec 2017) - //IMGUI_API bool Begin(char* name, bool* p_open, ImVec2 size_first_use, float bg_alpha = -1.0f, ImGuiWindowFlags flags=0); // OBSOLETED in 1.52 (between Aug 2017 and Oct 2017): Equivalent of using SetNextWindowSize(size, ImGuiCond_FirstUseEver) and SetNextWindowBgAlpha(). - //static inline bool IsRootWindowOrAnyChildHovered() { return IsWindowHovered(ImGuiHoveredFlags_RootAndChildWindows); } // OBSOLETED in 1.52 (between Aug 2017 and Oct 2017) - //static inline void AlignFirstTextHeightToWidgets() { AlignTextToFramePadding(); } // OBSOLETED in 1.52 (between Aug 2017 and Oct 2017) - //static inline void SetNextWindowPosCenter(ImGuiCond c=0) { SetNextWindowPos(GetMainViewport()->GetCenter(), c, ImVec2(0.5f,0.5f)); } // OBSOLETED in 1.52 (between Aug 2017 and Oct 2017) - //static inline bool IsItemHoveredRect() { return IsItemHovered(ImGuiHoveredFlags_RectOnly); } // OBSOLETED in 1.51 (between Jun 2017 and Aug 2017) - //static inline bool IsPosHoveringAnyWindow(const ImVec2&) { IM_ASSERT(0); return false; } // OBSOLETED in 1.51 (between Jun 2017 and Aug 2017): This was misleading and partly broken. You probably want to use the io.WantCaptureMouse flag instead. - //static inline bool IsMouseHoveringAnyWindow() { return IsWindowHovered(ImGuiHoveredFlags_AnyWindow); } // OBSOLETED in 1.51 (between Jun 2017 and Aug 2017) - //static inline bool IsMouseHoveringWindow() { return IsWindowHovered(ImGuiHoveredFlags_AllowWhenBlockedByPopup | ImGuiHoveredFlags_AllowWhenBlockedByActiveItem); } // OBSOLETED in 1.51 (between Jun 2017 and Aug 2017) - //-- OBSOLETED in 1.50 and before - //static inline bool CollapsingHeader(char* label, const char* str_id, bool framed = true, bool default_open = false) { return CollapsingHeader(label, (default_open ? (1 << 5) : 0)); } // OBSOLETED in 1.49 - //static inline ImFont*GetWindowFont() { return GetFont(); } // OBSOLETED in 1.48 - //static inline float GetWindowFontSize() { return GetFontSize(); } // OBSOLETED in 1.48 - //static inline void SetScrollPosHere() { SetScrollHere(); } // OBSOLETED in 1.42 -} - -//-- OBSOLETED in 1.82 (from Mars 2021): flags for AddRect(), AddRectFilled(), AddImageRounded(), PathRect() -//typedef ImDrawFlags ImDrawCornerFlags; -//enum ImDrawCornerFlags_ -//{ -// ImDrawCornerFlags_None = ImDrawFlags_RoundCornersNone, // Was == 0 prior to 1.82, this is now == ImDrawFlags_RoundCornersNone which is != 0 and not implicit -// ImDrawCornerFlags_TopLeft = ImDrawFlags_RoundCornersTopLeft, // Was == 0x01 (1 << 0) prior to 1.82. Order matches ImDrawFlags_NoRoundCorner* flag (we exploit this internally). -// ImDrawCornerFlags_TopRight = ImDrawFlags_RoundCornersTopRight, // Was == 0x02 (1 << 1) prior to 1.82. -// ImDrawCornerFlags_BotLeft = ImDrawFlags_RoundCornersBottomLeft, // Was == 0x04 (1 << 2) prior to 1.82. -// ImDrawCornerFlags_BotRight = ImDrawFlags_RoundCornersBottomRight, // Was == 0x08 (1 << 3) prior to 1.82. -// ImDrawCornerFlags_All = ImDrawFlags_RoundCornersAll, // Was == 0x0F prior to 1.82 -// ImDrawCornerFlags_Top = ImDrawCornerFlags_TopLeft | ImDrawCornerFlags_TopRight, -// ImDrawCornerFlags_Bot = ImDrawCornerFlags_BotLeft | ImDrawCornerFlags_BotRight, -// ImDrawCornerFlags_Left = ImDrawCornerFlags_TopLeft | ImDrawCornerFlags_BotLeft, -// ImDrawCornerFlags_Right = ImDrawCornerFlags_TopRight | ImDrawCornerFlags_BotRight, -//}; - -// RENAMED and MERGED both ImGuiKey_ModXXX and ImGuiModFlags_XXX into ImGuiMod_XXX (from September 2022) -// RENAMED ImGuiKeyModFlags -> ImGuiModFlags in 1.88 (from April 2022). Exceptionally commented out ahead of obscolescence schedule to reduce confusion and because they were not meant to be used in the first place. -typedef ImGuiKeyChord ImGuiModFlags; // == int. We generally use ImGuiKeyChord to mean "a ImGuiKey or-ed with any number of ImGuiMod_XXX value", but you may store only mods in there. -enum ImGuiModFlags_ { ImGuiModFlags_None = 0, ImGuiModFlags_Ctrl = ImGuiMod_Ctrl, ImGuiModFlags_Shift = ImGuiMod_Shift, ImGuiModFlags_Alt = ImGuiMod_Alt, ImGuiModFlags_Super = ImGuiMod_Super }; -//typedef ImGuiKeyChord ImGuiKeyModFlags; // == int -//enum ImGuiKeyModFlags_ { ImGuiKeyModFlags_None = 0, ImGuiKeyModFlags_Ctrl = ImGuiMod_Ctrl, ImGuiKeyModFlags_Shift = ImGuiMod_Shift, ImGuiKeyModFlags_Alt = ImGuiMod_Alt, ImGuiKeyModFlags_Super = ImGuiMod_Super }; - -#endif // #ifndef IMGUI_DISABLE_OBSOLETE_FUNCTIONS - -// RENAMED IMGUI_DISABLE_METRICS_WINDOW > IMGUI_DISABLE_DEBUG_TOOLS in 1.88 (from June 2022) -#if defined(IMGUI_DISABLE_METRICS_WINDOW) && !defined(IMGUI_DISABLE_OBSOLETE_FUNCTIONS) && !defined(IMGUI_DISABLE_DEBUG_TOOLS) -#define IMGUI_DISABLE_DEBUG_TOOLS -#endif -#if defined(IMGUI_DISABLE_METRICS_WINDOW) && defined(IMGUI_DISABLE_OBSOLETE_FUNCTIONS) -#error IMGUI_DISABLE_METRICS_WINDOW was renamed to IMGUI_DISABLE_DEBUG_TOOLS, please use new name. -#endif - -//----------------------------------------------------------------------------- - -#if defined(__clang__) -#pragma clang diagnostic pop -#elif defined(__GNUC__) -#pragma GCC diagnostic pop -#endif - -#ifdef _MSC_VER -#pragma warning (pop) -#endif - -// Include imgui_user.h at the end of imgui.h (convenient for user to only explicitly include vanilla imgui.h) -#ifdef IMGUI_INCLUDE_IMGUI_USER_H -#include "imgui_user.h" -#endif - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/imgui_demo.cpp b/app/jni/src/libultraship/extern/ImGui/imgui_demo.cpp deleted file mode 100644 index 2cc02b2..0000000 --- a/app/jni/src/libultraship/extern/ImGui/imgui_demo.cpp +++ /dev/null @@ -1,8682 +0,0 @@ -// dear imgui, v1.90 WIP -// (demo code) - -// Help: -// - Read FAQ at http://dearimgui.com/faq -// - Call and read ImGui::ShowDemoWindow() in imgui_demo.cpp. All applications in examples/ are doing that. -// - Need help integrating Dear ImGui in your codebase? -// - Read Getting Started https://github.com/ocornut/imgui/wiki/Getting-Started -// - Read 'Programmer guide' in imgui.cpp for notes on how to setup Dear ImGui in your codebase. -// Read imgui.cpp for more details, documentation and comments. -// Get the latest version at https://github.com/ocornut/imgui - -//--------------------------------------------------- -// PLEASE DO NOT REMOVE THIS FILE FROM YOUR PROJECT! -//--------------------------------------------------- -// Message to the person tempted to delete this file when integrating Dear ImGui into their codebase: -// Think again! It is the most useful reference code that you and other coders will want to refer to and call. -// Have the ImGui::ShowDemoWindow() function wired in an always-available debug menu of your game/app! -// Also include Metrics! ItemPicker! DebugLog! and other debug features. -// Removing this file from your project is hindering access to documentation for everyone in your team, -// likely leading you to poorer usage of the library. -// Everything in this file will be stripped out by the linker if you don't call ImGui::ShowDemoWindow(). -// If you want to link core Dear ImGui in your shipped builds but want a thorough guarantee that the demo will not be -// linked, you can setup your imconfig.h with #define IMGUI_DISABLE_DEMO_WINDOWS and those functions will be empty. -// In another situation, whenever you have Dear ImGui available you probably want this to be available for reference. -// Thank you, -// -Your beloved friend, imgui_demo.cpp (which you won't delete) - -//-------------------------------------------- -// ABOUT THE MEANING OF THE 'static' KEYWORD: -//-------------------------------------------- -// In this demo code, we frequently use 'static' variables inside functions. -// A static variable persists across calls. It is essentially a global variable but declared inside the scope of the function. -// Think of "static int n = 0;" as "global int n = 0;" ! -// We do this IN THE DEMO because we want: -// - to gather code and data in the same place. -// - to make the demo source code faster to read, faster to change, smaller in size. -// - it is also a convenient way of storing simple UI related information as long as your function -// doesn't need to be reentrant or used in multiple threads. -// This might be a pattern you will want to use in your code, but most of the data you would be working -// with in a complex codebase is likely going to be stored outside your functions. - -//----------------------------------------- -// ABOUT THE CODING STYLE OF OUR DEMO CODE -//----------------------------------------- -// The Demo code in this file is designed to be easy to copy-and-paste into your application! -// Because of this: -// - We never omit the ImGui:: prefix when calling functions, even though most code here is in the same namespace. -// - We try to declare static variables in the local scope, as close as possible to the code using them. -// - We never use any of the helpers/facilities used internally by Dear ImGui, unless available in the public API. -// - We never use maths operators on ImVec2/ImVec4. For our other sources files we use them, and they are provided -// by imgui.h using the IMGUI_DEFINE_MATH_OPERATORS define. For your own sources file they are optional -// and require you either enable those, either provide your own via IM_VEC2_CLASS_EXTRA in imconfig.h. -// Because we can't assume anything about your support of maths operators, we cannot use them in imgui_demo.cpp. - -// Navigating this file: -// - In Visual Studio IDE: CTRL+comma ("Edit.GoToAll") can follow symbols in comments, whereas CTRL+F12 ("Edit.GoToImplementation") cannot. -// - With Visual Assist installed: ALT+G ("VAssistX.GoToImplementation") can also follow symbols in comments. - -/* - -Index of this file: - -// [SECTION] Forward Declarations -// [SECTION] Helpers -// [SECTION] Demo Window / ShowDemoWindow() -// - ShowDemoWindow() -// - sub section: ShowDemoWindowWidgets() -// - sub section: ShowDemoWindowLayout() -// - sub section: ShowDemoWindowPopups() -// - sub section: ShowDemoWindowTables() -// - sub section: ShowDemoWindowInputs() -// [SECTION] About Window / ShowAboutWindow() -// [SECTION] Style Editor / ShowStyleEditor() -// [SECTION] User Guide / ShowUserGuide() -// [SECTION] Example App: Main Menu Bar / ShowExampleAppMainMenuBar() -// [SECTION] Example App: Debug Console / ShowExampleAppConsole() -// [SECTION] Example App: Debug Log / ShowExampleAppLog() -// [SECTION] Example App: Simple Layout / ShowExampleAppLayout() -// [SECTION] Example App: Property Editor / ShowExampleAppPropertyEditor() -// [SECTION] Example App: Long Text / ShowExampleAppLongText() -// [SECTION] Example App: Auto Resize / ShowExampleAppAutoResize() -// [SECTION] Example App: Constrained Resize / ShowExampleAppConstrainedResize() -// [SECTION] Example App: Simple overlay / ShowExampleAppSimpleOverlay() -// [SECTION] Example App: Fullscreen window / ShowExampleAppFullscreen() -// [SECTION] Example App: Manipulating window titles / ShowExampleAppWindowTitles() -// [SECTION] Example App: Custom Rendering using ImDrawList API / ShowExampleAppCustomRendering() -// [SECTION] Example App: Docking, DockSpace / ShowExampleAppDockSpace() -// [SECTION] Example App: Documents Handling / ShowExampleAppDocuments() - -*/ - -#if defined(_MSC_VER) && !defined(_CRT_SECURE_NO_WARNINGS) -#define _CRT_SECURE_NO_WARNINGS -#endif - -#include "imgui.h" -#ifndef IMGUI_DISABLE - -// System includes -#include // toupper -#include // INT_MIN, INT_MAX -#include // sqrtf, powf, cosf, sinf, floorf, ceilf -#include // vsnprintf, sscanf, printf -#include // NULL, malloc, free, atoi -#include // intptr_t -#if !defined(_MSC_VER) || _MSC_VER >= 1800 -#include // PRId64/PRIu64, not avail in some MinGW headers. -#endif - -// Visual Studio warnings -#ifdef _MSC_VER -#pragma warning (disable: 4127) // condition expression is constant -#pragma warning (disable: 4996) // 'This function or variable may be unsafe': strcpy, strdup, sprintf, vsnprintf, sscanf, fopen -#pragma warning (disable: 26451) // [Static Analyzer] Arithmetic overflow : Using operator 'xxx' on a 4 byte value and then casting the result to an 8 byte value. Cast the value to the wider type before calling operator 'xxx' to avoid overflow(io.2). -#endif - -// Clang/GCC warnings with -Weverything -#if defined(__clang__) -#if __has_warning("-Wunknown-warning-option") -#pragma clang diagnostic ignored "-Wunknown-warning-option" // warning: unknown warning group 'xxx' // not all warnings are known by all Clang versions and they tend to be rename-happy.. so ignoring warnings triggers new warnings on some configuration. Great! -#endif -#pragma clang diagnostic ignored "-Wunknown-pragmas" // warning: unknown warning group 'xxx' -#pragma clang diagnostic ignored "-Wold-style-cast" // warning: use of old-style cast // yes, they are more terse. -#pragma clang diagnostic ignored "-Wdeprecated-declarations" // warning: 'xx' is deprecated: The POSIX name for this.. // for strdup used in demo code (so user can copy & paste the code) -#pragma clang diagnostic ignored "-Wint-to-void-pointer-cast" // warning: cast to 'void *' from smaller integer type -#pragma clang diagnostic ignored "-Wformat-security" // warning: format string is not a string literal -#pragma clang diagnostic ignored "-Wexit-time-destructors" // warning: declaration requires an exit-time destructor // exit-time destruction order is undefined. if MemFree() leads to users code that has been disabled before exit it might cause problems. ImGui coding style welcomes static/globals. -#pragma clang diagnostic ignored "-Wunused-macros" // warning: macro is not used // we define snprintf/vsnprintf on Windows so they are available, but not always used. -#pragma clang diagnostic ignored "-Wzero-as-null-pointer-constant" // warning: zero as null pointer constant // some standard header variations use #define NULL 0 -#pragma clang diagnostic ignored "-Wdouble-promotion" // warning: implicit conversion from 'float' to 'double' when passing argument to function // using printf() is a misery with this as C++ va_arg ellipsis changes float to double. -#pragma clang diagnostic ignored "-Wreserved-id-macro" // warning: macro name is a reserved identifier -#pragma clang diagnostic ignored "-Wimplicit-int-float-conversion" // warning: implicit conversion from 'xxx' to 'float' may lose precision -#elif defined(__GNUC__) -#pragma GCC diagnostic ignored "-Wpragmas" // warning: unknown option after '#pragma GCC diagnostic' kind -#pragma GCC diagnostic ignored "-Wint-to-pointer-cast" // warning: cast to pointer from integer of different size -#pragma GCC diagnostic ignored "-Wformat-security" // warning: format string is not a string literal (potentially insecure) -#pragma GCC diagnostic ignored "-Wdouble-promotion" // warning: implicit conversion from 'float' to 'double' when passing argument to function -#pragma GCC diagnostic ignored "-Wconversion" // warning: conversion to 'xxxx' from 'xxxx' may alter its value -#pragma GCC diagnostic ignored "-Wmisleading-indentation" // [__GNUC__ >= 6] warning: this 'if' clause does not guard this statement // GCC 6.0+ only. See #883 on GitHub. -#endif - -// Play it nice with Windows users (Update: May 2018, Notepad now supports Unix-style carriage returns!) -#ifdef _WIN32 -#define IM_NEWLINE "\r\n" -#else -#define IM_NEWLINE "\n" -#endif - -// Helpers -#if defined(_MSC_VER) && !defined(snprintf) -#define snprintf _snprintf -#endif -#if defined(_MSC_VER) && !defined(vsnprintf) -#define vsnprintf _vsnprintf -#endif - -// Format specifiers for 64-bit values (hasn't been decently standardized before VS2013) -#if !defined(PRId64) && defined(_MSC_VER) -#define PRId64 "I64d" -#define PRIu64 "I64u" -#elif !defined(PRId64) -#define PRId64 "lld" -#define PRIu64 "llu" -#endif - -// Helpers macros -// We normally try to not use many helpers in imgui_demo.cpp in order to make code easier to copy and paste, -// but making an exception here as those are largely simplifying code... -// In other imgui sources we can use nicer internal functions from imgui_internal.h (ImMin/ImMax) but not in the demo. -#define IM_MIN(A, B) (((A) < (B)) ? (A) : (B)) -#define IM_MAX(A, B) (((A) >= (B)) ? (A) : (B)) -#define IM_CLAMP(V, MN, MX) ((V) < (MN) ? (MN) : (V) > (MX) ? (MX) : (V)) - -// Enforce cdecl calling convention for functions called by the standard library, in case compilation settings changed the default to e.g. __vectorcall -#ifndef IMGUI_CDECL -#ifdef _MSC_VER -#define IMGUI_CDECL __cdecl -#else -#define IMGUI_CDECL -#endif -#endif - -//----------------------------------------------------------------------------- -// [SECTION] Forward Declarations, Helpers -//----------------------------------------------------------------------------- - -#if !defined(IMGUI_DISABLE_DEMO_WINDOWS) - -// Forward Declarations -static void ShowExampleAppMainMenuBar(); -static void ShowExampleAppConsole(bool* p_open); -static void ShowExampleAppCustomRendering(bool* p_open); -static void ShowExampleAppDockSpace(bool* p_open); -static void ShowExampleAppDocuments(bool* p_open); -static void ShowExampleAppLog(bool* p_open); -static void ShowExampleAppLayout(bool* p_open); -static void ShowExampleAppPropertyEditor(bool* p_open); -static void ShowExampleAppSimpleOverlay(bool* p_open); -static void ShowExampleAppAutoResize(bool* p_open); -static void ShowExampleAppConstrainedResize(bool* p_open); -static void ShowExampleAppFullscreen(bool* p_open); -static void ShowExampleAppLongText(bool* p_open); -static void ShowExampleAppWindowTitles(bool* p_open); -static void ShowExampleMenuFile(); - -// We split the contents of the big ShowDemoWindow() function into smaller functions -// (because the link time of very large functions grow non-linearly) -static void ShowDemoWindowWidgets(); -static void ShowDemoWindowLayout(); -static void ShowDemoWindowPopups(); -static void ShowDemoWindowTables(); -static void ShowDemoWindowColumns(); -static void ShowDemoWindowInputs(); - -//----------------------------------------------------------------------------- -// [SECTION] Helpers -//----------------------------------------------------------------------------- - -// Helper to display a little (?) mark which shows a tooltip when hovered. -// In your own code you may want to display an actual icon if you are using a merged icon fonts (see docs/FONTS.md) -static void HelpMarker(const char* desc) -{ - ImGui::TextDisabled("(?)"); - if (ImGui::BeginItemTooltip()) - { - ImGui::PushTextWrapPos(ImGui::GetFontSize() * 35.0f); - ImGui::TextUnformatted(desc); - ImGui::PopTextWrapPos(); - ImGui::EndTooltip(); - } -} - -static void ShowDockingDisabledMessage() -{ - ImGuiIO& io = ImGui::GetIO(); - ImGui::Text("ERROR: Docking is not enabled! See Demo > Configuration."); - ImGui::Text("Set io.ConfigFlags |= ImGuiConfigFlags_DockingEnable in your code, or "); - ImGui::SameLine(0.0f, 0.0f); - if (ImGui::SmallButton("click here")) - io.ConfigFlags |= ImGuiConfigFlags_DockingEnable; -} - -// Helper to wire demo markers located in code to an interactive browser -typedef void (*ImGuiDemoMarkerCallback)(const char* file, int line, const char* section, void* user_data); -extern ImGuiDemoMarkerCallback GImGuiDemoMarkerCallback; -extern void* GImGuiDemoMarkerCallbackUserData; -ImGuiDemoMarkerCallback GImGuiDemoMarkerCallback = NULL; -void* GImGuiDemoMarkerCallbackUserData = NULL; -#define IMGUI_DEMO_MARKER(section) do { if (GImGuiDemoMarkerCallback != NULL) GImGuiDemoMarkerCallback(__FILE__, __LINE__, section, GImGuiDemoMarkerCallbackUserData); } while (0) - -//----------------------------------------------------------------------------- -// [SECTION] Demo Window / ShowDemoWindow() -//----------------------------------------------------------------------------- -// - ShowDemoWindow() -// - ShowDemoWindowWidgets() -// - ShowDemoWindowLayout() -// - ShowDemoWindowPopups() -// - ShowDemoWindowTables() -// - ShowDemoWindowColumns() -// - ShowDemoWindowInputs() -//----------------------------------------------------------------------------- - -// Demonstrate most Dear ImGui features (this is big function!) -// You may execute this function to experiment with the UI and understand what it does. -// You may then search for keywords in the code when you are interested by a specific feature. -void ImGui::ShowDemoWindow(bool* p_open) -{ - // Exceptionally add an extra assert here for people confused about initial Dear ImGui setup - // Most functions would normally just assert/crash if the context is missing. - IM_ASSERT(ImGui::GetCurrentContext() != NULL && "Missing Dear ImGui context. Refer to examples app!"); - - // Examples Apps (accessible from the "Examples" menu) - static bool show_app_main_menu_bar = false; - static bool show_app_console = false; - static bool show_app_custom_rendering = false; - static bool show_app_dockspace = false; - static bool show_app_documents = false; - static bool show_app_log = false; - static bool show_app_layout = false; - static bool show_app_property_editor = false; - static bool show_app_simple_overlay = false; - static bool show_app_auto_resize = false; - static bool show_app_constrained_resize = false; - static bool show_app_fullscreen = false; - static bool show_app_long_text = false; - static bool show_app_window_titles = false; - - if (show_app_main_menu_bar) ShowExampleAppMainMenuBar(); - if (show_app_dockspace) ShowExampleAppDockSpace(&show_app_dockspace); // Process the Docking app first, as explicit DockSpace() nodes needs to be submitted early (read comments near the DockSpace function) - if (show_app_documents) ShowExampleAppDocuments(&show_app_documents); // Process the Document app next, as it may also use a DockSpace() - if (show_app_console) ShowExampleAppConsole(&show_app_console); - if (show_app_custom_rendering) ShowExampleAppCustomRendering(&show_app_custom_rendering); - if (show_app_log) ShowExampleAppLog(&show_app_log); - if (show_app_layout) ShowExampleAppLayout(&show_app_layout); - if (show_app_property_editor) ShowExampleAppPropertyEditor(&show_app_property_editor); - if (show_app_simple_overlay) ShowExampleAppSimpleOverlay(&show_app_simple_overlay); - if (show_app_auto_resize) ShowExampleAppAutoResize(&show_app_auto_resize); - if (show_app_constrained_resize) ShowExampleAppConstrainedResize(&show_app_constrained_resize); - if (show_app_fullscreen) ShowExampleAppFullscreen(&show_app_fullscreen); - if (show_app_long_text) ShowExampleAppLongText(&show_app_long_text); - if (show_app_window_titles) ShowExampleAppWindowTitles(&show_app_window_titles); - - // Dear ImGui Tools (accessible from the "Tools" menu) - static bool show_tool_metrics = false; - static bool show_tool_debug_log = false; - static bool show_tool_id_stack_tool = false; - static bool show_tool_style_editor = false; - static bool show_tool_about = false; - - if (show_tool_metrics) - ImGui::ShowMetricsWindow(&show_tool_metrics); - if (show_tool_debug_log) - ImGui::ShowDebugLogWindow(&show_tool_debug_log); - if (show_tool_id_stack_tool) - ImGui::ShowIDStackToolWindow(&show_tool_id_stack_tool); - if (show_tool_style_editor) - { - ImGui::Begin("Dear ImGui Style Editor", &show_tool_style_editor); - ImGui::ShowStyleEditor(); - ImGui::End(); - } - if (show_tool_about) - ImGui::ShowAboutWindow(&show_tool_about); - - // Demonstrate the various window flags. Typically you would just use the default! - static bool no_titlebar = false; - static bool no_scrollbar = false; - static bool no_menu = false; - static bool no_move = false; - static bool no_resize = false; - static bool no_collapse = false; - static bool no_close = false; - static bool no_nav = false; - static bool no_background = false; - static bool no_bring_to_front = false; - static bool no_docking = false; - static bool unsaved_document = false; - - ImGuiWindowFlags window_flags = 0; - if (no_titlebar) window_flags |= ImGuiWindowFlags_NoTitleBar; - if (no_scrollbar) window_flags |= ImGuiWindowFlags_NoScrollbar; - if (!no_menu) window_flags |= ImGuiWindowFlags_MenuBar; - if (no_move) window_flags |= ImGuiWindowFlags_NoMove; - if (no_resize) window_flags |= ImGuiWindowFlags_NoResize; - if (no_collapse) window_flags |= ImGuiWindowFlags_NoCollapse; - if (no_nav) window_flags |= ImGuiWindowFlags_NoNav; - if (no_background) window_flags |= ImGuiWindowFlags_NoBackground; - if (no_bring_to_front) window_flags |= ImGuiWindowFlags_NoBringToFrontOnFocus; - if (no_docking) window_flags |= ImGuiWindowFlags_NoDocking; - if (unsaved_document) window_flags |= ImGuiWindowFlags_UnsavedDocument; - if (no_close) p_open = NULL; // Don't pass our bool* to Begin - - // We specify a default position/size in case there's no data in the .ini file. - // We only do it to make the demo applications a little more welcoming, but typically this isn't required. - const ImGuiViewport* main_viewport = ImGui::GetMainViewport(); - ImGui::SetNextWindowPos(ImVec2(main_viewport->WorkPos.x + 650, main_viewport->WorkPos.y + 20), ImGuiCond_FirstUseEver); - ImGui::SetNextWindowSize(ImVec2(550, 680), ImGuiCond_FirstUseEver); - - // Main body of the Demo window starts here. - if (!ImGui::Begin("Dear ImGui Demo", p_open, window_flags)) - { - // Early out if the window is collapsed, as an optimization. - ImGui::End(); - return; - } - - // Most "big" widgets share a common width settings by default. See 'Demo->Layout->Widgets Width' for details. - // e.g. Use 2/3 of the space for widgets and 1/3 for labels (right align) - //ImGui::PushItemWidth(-ImGui::GetWindowWidth() * 0.35f); - // e.g. Leave a fixed amount of width for labels (by passing a negative value), the rest goes to widgets. - ImGui::PushItemWidth(ImGui::GetFontSize() * -12); - - // Menu Bar - if (ImGui::BeginMenuBar()) - { - if (ImGui::BeginMenu("Menu")) - { - IMGUI_DEMO_MARKER("Menu/File"); - ShowExampleMenuFile(); - ImGui::EndMenu(); - } - if (ImGui::BeginMenu("Examples")) - { - IMGUI_DEMO_MARKER("Menu/Examples"); - ImGui::MenuItem("Main menu bar", NULL, &show_app_main_menu_bar); - - ImGui::SeparatorText("Mini apps"); - ImGui::MenuItem("Console", NULL, &show_app_console); - ImGui::MenuItem("Custom rendering", NULL, &show_app_custom_rendering); - ImGui::MenuItem("Dockspace", NULL, &show_app_dockspace); - ImGui::MenuItem("Documents", NULL, &show_app_documents); - ImGui::MenuItem("Log", NULL, &show_app_log); - ImGui::MenuItem("Property editor", NULL, &show_app_property_editor); - ImGui::MenuItem("Simple layout", NULL, &show_app_layout); - ImGui::MenuItem("Simple overlay", NULL, &show_app_simple_overlay); - - ImGui::SeparatorText("Concepts"); - ImGui::MenuItem("Auto-resizing window", NULL, &show_app_auto_resize); - ImGui::MenuItem("Constrained-resizing window", NULL, &show_app_constrained_resize); - ImGui::MenuItem("Fullscreen window", NULL, &show_app_fullscreen); - ImGui::MenuItem("Long text display", NULL, &show_app_long_text); - ImGui::MenuItem("Manipulating window titles", NULL, &show_app_window_titles); - - ImGui::EndMenu(); - } - //if (ImGui::MenuItem("MenuItem")) {} // You can also use MenuItem() inside a menu bar! - if (ImGui::BeginMenu("Tools")) - { - IMGUI_DEMO_MARKER("Menu/Tools"); -#ifndef IMGUI_DISABLE_DEBUG_TOOLS - const bool has_debug_tools = true; -#else - const bool has_debug_tools = false; -#endif - ImGui::MenuItem("Metrics/Debugger", NULL, &show_tool_metrics, has_debug_tools); - ImGui::MenuItem("Debug Log", NULL, &show_tool_debug_log, has_debug_tools); - ImGui::MenuItem("ID Stack Tool", NULL, &show_tool_id_stack_tool, has_debug_tools); - ImGui::MenuItem("Style Editor", NULL, &show_tool_style_editor); - ImGui::MenuItem("About Dear ImGui", NULL, &show_tool_about); - ImGui::EndMenu(); - } - ImGui::EndMenuBar(); - } - - ImGui::Text("dear imgui says hello! (%s) (%d)", IMGUI_VERSION, IMGUI_VERSION_NUM); - ImGui::Spacing(); - - IMGUI_DEMO_MARKER("Help"); - if (ImGui::CollapsingHeader("Help")) - { - ImGui::SeparatorText("ABOUT THIS DEMO:"); - ImGui::BulletText("Sections below are demonstrating many aspects of the library."); - ImGui::BulletText("The \"Examples\" menu above leads to more demo contents."); - ImGui::BulletText("The \"Tools\" menu above gives access to: About Box, Style Editor,\n" - "and Metrics/Debugger (general purpose Dear ImGui debugging tool)."); - - ImGui::SeparatorText("PROGRAMMER GUIDE:"); - ImGui::BulletText("See the ShowDemoWindow() code in imgui_demo.cpp. <- you are here!"); - ImGui::BulletText("See comments in imgui.cpp."); - ImGui::BulletText("See example applications in the examples/ folder."); - ImGui::BulletText("Read the FAQ at https://www.dearimgui.com/faq/"); - ImGui::BulletText("Set 'io.ConfigFlags |= NavEnableKeyboard' for keyboard controls."); - ImGui::BulletText("Set 'io.ConfigFlags |= NavEnableGamepad' for gamepad controls."); - - ImGui::SeparatorText("USER GUIDE:"); - ImGui::ShowUserGuide(); - } - - IMGUI_DEMO_MARKER("Configuration"); - if (ImGui::CollapsingHeader("Configuration")) - { - ImGuiIO& io = ImGui::GetIO(); - - if (ImGui::TreeNode("Configuration##2")) - { - ImGui::SeparatorText("General"); - ImGui::CheckboxFlags("io.ConfigFlags: NavEnableKeyboard", &io.ConfigFlags, ImGuiConfigFlags_NavEnableKeyboard); - ImGui::SameLine(); HelpMarker("Enable keyboard controls."); - ImGui::CheckboxFlags("io.ConfigFlags: NavEnableGamepad", &io.ConfigFlags, ImGuiConfigFlags_NavEnableGamepad); - ImGui::SameLine(); HelpMarker("Enable gamepad controls. Require backend to set io.BackendFlags |= ImGuiBackendFlags_HasGamepad.\n\nRead instructions in imgui.cpp for details."); - ImGui::CheckboxFlags("io.ConfigFlags: NavEnableSetMousePos", &io.ConfigFlags, ImGuiConfigFlags_NavEnableSetMousePos); - ImGui::SameLine(); HelpMarker("Instruct navigation to move the mouse cursor. See comment for ImGuiConfigFlags_NavEnableSetMousePos."); - ImGui::CheckboxFlags("io.ConfigFlags: NoMouse", &io.ConfigFlags, ImGuiConfigFlags_NoMouse); - if (io.ConfigFlags & ImGuiConfigFlags_NoMouse) - { - // The "NoMouse" option can get us stuck with a disabled mouse! Let's provide an alternative way to fix it: - if (fmodf((float)ImGui::GetTime(), 0.40f) < 0.20f) - { - ImGui::SameLine(); - ImGui::Text("<>"); - } - if (ImGui::IsKeyPressed(ImGuiKey_Space)) - io.ConfigFlags &= ~ImGuiConfigFlags_NoMouse; - } - ImGui::CheckboxFlags("io.ConfigFlags: NoMouseCursorChange", &io.ConfigFlags, ImGuiConfigFlags_NoMouseCursorChange); - ImGui::SameLine(); HelpMarker("Instruct backend to not alter mouse cursor shape and visibility."); - - ImGui::CheckboxFlags("io.ConfigFlags: DockingEnable", &io.ConfigFlags, ImGuiConfigFlags_DockingEnable); - ImGui::SameLine(); - if (io.ConfigDockingWithShift) - HelpMarker("Drag from window title bar or their tab to dock/undock. Hold SHIFT to enable docking.\n\nDrag from window menu button (upper-left button) to undock an entire node (all windows)."); - else - HelpMarker("Drag from window title bar or their tab to dock/undock. Hold SHIFT to disable docking.\n\nDrag from window menu button (upper-left button) to undock an entire node (all windows)."); - if (io.ConfigFlags & ImGuiConfigFlags_DockingEnable) - { - ImGui::Indent(); - ImGui::Checkbox("io.ConfigDockingNoSplit", &io.ConfigDockingNoSplit); - ImGui::SameLine(); HelpMarker("Simplified docking mode: disable window splitting, so docking is limited to merging multiple windows together into tab-bars."); - ImGui::Checkbox("io.ConfigDockingWithShift", &io.ConfigDockingWithShift); - ImGui::SameLine(); HelpMarker("Enable docking when holding Shift only (allow to drop in wider space, reduce visual noise)"); - ImGui::Checkbox("io.ConfigDockingAlwaysTabBar", &io.ConfigDockingAlwaysTabBar); - ImGui::SameLine(); HelpMarker("Create a docking node and tab-bar on single floating windows."); - ImGui::Checkbox("io.ConfigDockingTransparentPayload", &io.ConfigDockingTransparentPayload); - ImGui::SameLine(); HelpMarker("Make window or viewport transparent when docking and only display docking boxes on the target viewport. Useful if rendering of multiple viewport cannot be synced. Best used with ConfigViewportsNoAutoMerge."); - ImGui::Unindent(); - } - - ImGui::CheckboxFlags("io.ConfigFlags: ViewportsEnable", &io.ConfigFlags, ImGuiConfigFlags_ViewportsEnable); - ImGui::SameLine(); HelpMarker("[beta] Enable beta multi-viewports support. See ImGuiPlatformIO for details."); - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) - { - ImGui::Indent(); - ImGui::Checkbox("io.ConfigViewportsNoAutoMerge", &io.ConfigViewportsNoAutoMerge); - ImGui::SameLine(); HelpMarker("Set to make all floating imgui windows always create their own viewport. Otherwise, they are merged into the main host viewports when overlapping it."); - ImGui::Checkbox("io.ConfigViewportsNoTaskBarIcon", &io.ConfigViewportsNoTaskBarIcon); - ImGui::SameLine(); HelpMarker("Toggling this at runtime is normally unsupported (most platform backends won't refresh the task bar icon state right away)."); - ImGui::Checkbox("io.ConfigViewportsNoDecoration", &io.ConfigViewportsNoDecoration); - ImGui::SameLine(); HelpMarker("Toggling this at runtime is normally unsupported (most platform backends won't refresh the decoration right away)."); - ImGui::Checkbox("io.ConfigViewportsNoDefaultParent", &io.ConfigViewportsNoDefaultParent); - ImGui::SameLine(); HelpMarker("Toggling this at runtime is normally unsupported (most platform backends won't refresh the parenting right away)."); - ImGui::Unindent(); - } - - ImGui::Checkbox("io.ConfigInputTrickleEventQueue", &io.ConfigInputTrickleEventQueue); - ImGui::SameLine(); HelpMarker("Enable input queue trickling: some types of events submitted during the same frame (e.g. button down + up) will be spread over multiple frames, improving interactions with low framerates."); - ImGui::Checkbox("io.MouseDrawCursor", &io.MouseDrawCursor); - ImGui::SameLine(); HelpMarker("Instruct Dear ImGui to render a mouse cursor itself. Note that a mouse cursor rendered via your application GPU rendering path will feel more laggy than hardware cursor, but will be more in sync with your other visuals.\n\nSome desktop applications may use both kinds of cursors (e.g. enable software cursor only when resizing/dragging something)."); - - ImGui::SeparatorText("Widgets"); - ImGui::Checkbox("io.ConfigInputTextCursorBlink", &io.ConfigInputTextCursorBlink); - ImGui::SameLine(); HelpMarker("Enable blinking cursor (optional as some users consider it to be distracting)."); - ImGui::Checkbox("io.ConfigInputTextEnterKeepActive", &io.ConfigInputTextEnterKeepActive); - ImGui::SameLine(); HelpMarker("Pressing Enter will keep item active and select contents (single-line only)."); - ImGui::Checkbox("io.ConfigDragClickToInputText", &io.ConfigDragClickToInputText); - ImGui::SameLine(); HelpMarker("Enable turning DragXXX widgets into text input with a simple mouse click-release (without moving)."); - ImGui::Checkbox("io.ConfigWindowsResizeFromEdges", &io.ConfigWindowsResizeFromEdges); - ImGui::SameLine(); HelpMarker("Enable resizing of windows from their edges and from the lower-left corner.\nThis requires (io.BackendFlags & ImGuiBackendFlags_HasMouseCursors) because it needs mouse cursor feedback."); - ImGui::Checkbox("io.ConfigWindowsMoveFromTitleBarOnly", &io.ConfigWindowsMoveFromTitleBarOnly); - ImGui::Checkbox("io.ConfigMacOSXBehaviors", &io.ConfigMacOSXBehaviors); - ImGui::Text("Also see Style->Rendering for rendering options."); - - ImGui::SeparatorText("Debug"); - ImGui::BeginDisabled(); - ImGui::Checkbox("io.ConfigDebugBeginReturnValueOnce", &io.ConfigDebugBeginReturnValueOnce); // . - ImGui::EndDisabled(); - ImGui::SameLine(); HelpMarker("First calls to Begin()/BeginChild() will return false.\n\nTHIS OPTION IS DISABLED because it needs to be set at application boot-time to make sense. Showing the disabled option is a way to make this feature easier to discover"); - ImGui::Checkbox("io.ConfigDebugBeginReturnValueLoop", &io.ConfigDebugBeginReturnValueLoop); - ImGui::SameLine(); HelpMarker("Some calls to Begin()/BeginChild() will return false.\n\nWill cycle through window depths then repeat. Windows should be flickering while running."); - ImGui::Checkbox("io.ConfigDebugIgnoreFocusLoss", &io.ConfigDebugIgnoreFocusLoss); - ImGui::SameLine(); HelpMarker("Option to deactivate io.AddFocusEvent(false) handling. May facilitate interactions with a debugger when focus loss leads to clearing inputs data."); - ImGui::Checkbox("io.ConfigDebugIniSettings", &io.ConfigDebugIniSettings); - ImGui::SameLine(); HelpMarker("Option to save .ini data with extra comments (particularly helpful for Docking, but makes saving slower)."); - - ImGui::TreePop(); - ImGui::Spacing(); - } - - IMGUI_DEMO_MARKER("Configuration/Backend Flags"); - if (ImGui::TreeNode("Backend Flags")) - { - HelpMarker( - "Those flags are set by the backends (imgui_impl_xxx files) to specify their capabilities.\n" - "Here we expose them as read-only fields to avoid breaking interactions with your backend."); - - // Make a local copy to avoid modifying actual backend flags. - // FIXME: Maybe we need a BeginReadonly() equivalent to keep label bright? - ImGui::BeginDisabled(); - ImGui::CheckboxFlags("io.BackendFlags: HasGamepad", &io.BackendFlags, ImGuiBackendFlags_HasGamepad); - ImGui::CheckboxFlags("io.BackendFlags: HasMouseCursors", &io.BackendFlags, ImGuiBackendFlags_HasMouseCursors); - ImGui::CheckboxFlags("io.BackendFlags: HasSetMousePos", &io.BackendFlags, ImGuiBackendFlags_HasSetMousePos); - ImGui::CheckboxFlags("io.BackendFlags: PlatformHasViewports", &io.BackendFlags, ImGuiBackendFlags_PlatformHasViewports); - ImGui::CheckboxFlags("io.BackendFlags: HasMouseHoveredViewport",&io.BackendFlags, ImGuiBackendFlags_HasMouseHoveredViewport); - ImGui::CheckboxFlags("io.BackendFlags: RendererHasVtxOffset", &io.BackendFlags, ImGuiBackendFlags_RendererHasVtxOffset); - ImGui::CheckboxFlags("io.BackendFlags: RendererHasViewports", &io.BackendFlags, ImGuiBackendFlags_RendererHasViewports); - ImGui::EndDisabled(); - ImGui::TreePop(); - ImGui::Spacing(); - } - - IMGUI_DEMO_MARKER("Configuration/Style"); - if (ImGui::TreeNode("Style")) - { - HelpMarker("The same contents can be accessed in 'Tools->Style Editor' or by calling the ShowStyleEditor() function."); - ImGui::ShowStyleEditor(); - ImGui::TreePop(); - ImGui::Spacing(); - } - - IMGUI_DEMO_MARKER("Configuration/Capture, Logging"); - if (ImGui::TreeNode("Capture/Logging")) - { - HelpMarker( - "The logging API redirects all text output so you can easily capture the content of " - "a window or a block. Tree nodes can be automatically expanded.\n" - "Try opening any of the contents below in this window and then click one of the \"Log To\" button."); - ImGui::LogButtons(); - - HelpMarker("You can also call ImGui::LogText() to output directly to the log without a visual output."); - if (ImGui::Button("Copy \"Hello, world!\" to clipboard")) - { - ImGui::LogToClipboard(); - ImGui::LogText("Hello, world!"); - ImGui::LogFinish(); - } - ImGui::TreePop(); - } - } - - IMGUI_DEMO_MARKER("Window options"); - if (ImGui::CollapsingHeader("Window options")) - { - if (ImGui::BeginTable("split", 3)) - { - ImGui::TableNextColumn(); ImGui::Checkbox("No titlebar", &no_titlebar); - ImGui::TableNextColumn(); ImGui::Checkbox("No scrollbar", &no_scrollbar); - ImGui::TableNextColumn(); ImGui::Checkbox("No menu", &no_menu); - ImGui::TableNextColumn(); ImGui::Checkbox("No move", &no_move); - ImGui::TableNextColumn(); ImGui::Checkbox("No resize", &no_resize); - ImGui::TableNextColumn(); ImGui::Checkbox("No collapse", &no_collapse); - ImGui::TableNextColumn(); ImGui::Checkbox("No close", &no_close); - ImGui::TableNextColumn(); ImGui::Checkbox("No nav", &no_nav); - ImGui::TableNextColumn(); ImGui::Checkbox("No background", &no_background); - ImGui::TableNextColumn(); ImGui::Checkbox("No bring to front", &no_bring_to_front); - ImGui::TableNextColumn(); ImGui::Checkbox("No docking", &no_docking); - ImGui::TableNextColumn(); ImGui::Checkbox("Unsaved document", &unsaved_document); - ImGui::EndTable(); - } - } - - // All demo contents - ShowDemoWindowWidgets(); - ShowDemoWindowLayout(); - ShowDemoWindowPopups(); - ShowDemoWindowTables(); - ShowDemoWindowInputs(); - - // End of ShowDemoWindow() - ImGui::PopItemWidth(); - ImGui::End(); -} - -static void ShowDemoWindowWidgets() -{ - IMGUI_DEMO_MARKER("Widgets"); - if (!ImGui::CollapsingHeader("Widgets")) - return; - - static bool disable_all = false; // The Checkbox for that is inside the "Disabled" section at the bottom - if (disable_all) - ImGui::BeginDisabled(); - - IMGUI_DEMO_MARKER("Widgets/Basic"); - if (ImGui::TreeNode("Basic")) - { - ImGui::SeparatorText("General"); - - IMGUI_DEMO_MARKER("Widgets/Basic/Button"); - static int clicked = 0; - if (ImGui::Button("Button")) - clicked++; - if (clicked & 1) - { - ImGui::SameLine(); - ImGui::Text("Thanks for clicking me!"); - } - - IMGUI_DEMO_MARKER("Widgets/Basic/Checkbox"); - static bool check = true; - ImGui::Checkbox("checkbox", &check); - - IMGUI_DEMO_MARKER("Widgets/Basic/RadioButton"); - static int e = 0; - ImGui::RadioButton("radio a", &e, 0); ImGui::SameLine(); - ImGui::RadioButton("radio b", &e, 1); ImGui::SameLine(); - ImGui::RadioButton("radio c", &e, 2); - - // Color buttons, demonstrate using PushID() to add unique identifier in the ID stack, and changing style. - IMGUI_DEMO_MARKER("Widgets/Basic/Buttons (Colored)"); - for (int i = 0; i < 7; i++) - { - if (i > 0) - ImGui::SameLine(); - ImGui::PushID(i); - ImGui::PushStyleColor(ImGuiCol_Button, (ImVec4)ImColor::HSV(i / 7.0f, 0.6f, 0.6f)); - ImGui::PushStyleColor(ImGuiCol_ButtonHovered, (ImVec4)ImColor::HSV(i / 7.0f, 0.7f, 0.7f)); - ImGui::PushStyleColor(ImGuiCol_ButtonActive, (ImVec4)ImColor::HSV(i / 7.0f, 0.8f, 0.8f)); - ImGui::Button("Click"); - ImGui::PopStyleColor(3); - ImGui::PopID(); - } - - // Use AlignTextToFramePadding() to align text baseline to the baseline of framed widgets elements - // (otherwise a Text+SameLine+Button sequence will have the text a little too high by default!) - // See 'Demo->Layout->Text Baseline Alignment' for details. - ImGui::AlignTextToFramePadding(); - ImGui::Text("Hold to repeat:"); - ImGui::SameLine(); - - // Arrow buttons with Repeater - IMGUI_DEMO_MARKER("Widgets/Basic/Buttons (Repeating)"); - static int counter = 0; - float spacing = ImGui::GetStyle().ItemInnerSpacing.x; - ImGui::PushButtonRepeat(true); - if (ImGui::ArrowButton("##left", ImGuiDir_Left)) { counter--; } - ImGui::SameLine(0.0f, spacing); - if (ImGui::ArrowButton("##right", ImGuiDir_Right)) { counter++; } - ImGui::PopButtonRepeat(); - ImGui::SameLine(); - ImGui::Text("%d", counter); - - ImGui::Button("Tooltip"); - ImGui::SetItemTooltip("I am a tooltip"); - - ImGui::LabelText("label", "Value"); - - ImGui::SeparatorText("Inputs"); - - { - // To wire InputText() with std::string or any other custom string type, - // see the "Text Input > Resize Callback" section of this demo, and the misc/cpp/imgui_stdlib.h file. - IMGUI_DEMO_MARKER("Widgets/Basic/InputText"); - static char str0[128] = "Hello, world!"; - ImGui::InputText("input text", str0, IM_ARRAYSIZE(str0)); - ImGui::SameLine(); HelpMarker( - "USER:\n" - "Hold SHIFT or use mouse to select text.\n" - "CTRL+Left/Right to word jump.\n" - "CTRL+A or Double-Click to select all.\n" - "CTRL+X,CTRL+C,CTRL+V clipboard.\n" - "CTRL+Z,CTRL+Y undo/redo.\n" - "ESCAPE to revert.\n\n" - "PROGRAMMER:\n" - "You can use the ImGuiInputTextFlags_CallbackResize facility if you need to wire InputText() " - "to a dynamic string type. See misc/cpp/imgui_stdlib.h for an example (this is not demonstrated " - "in imgui_demo.cpp)."); - - static char str1[128] = ""; - ImGui::InputTextWithHint("input text (w/ hint)", "enter text here", str1, IM_ARRAYSIZE(str1)); - - IMGUI_DEMO_MARKER("Widgets/Basic/InputInt, InputFloat"); - static int i0 = 123; - ImGui::InputInt("input int", &i0); - - static float f0 = 0.001f; - ImGui::InputFloat("input float", &f0, 0.01f, 1.0f, "%.3f"); - - static double d0 = 999999.00000001; - ImGui::InputDouble("input double", &d0, 0.01f, 1.0f, "%.8f"); - - static float f1 = 1.e10f; - ImGui::InputFloat("input scientific", &f1, 0.0f, 0.0f, "%e"); - ImGui::SameLine(); HelpMarker( - "You can input value using the scientific notation,\n" - " e.g. \"1e+8\" becomes \"100000000\"."); - - static float vec4a[4] = { 0.10f, 0.20f, 0.30f, 0.44f }; - ImGui::InputFloat3("input float3", vec4a); - } - - ImGui::SeparatorText("Drags"); - - { - IMGUI_DEMO_MARKER("Widgets/Basic/DragInt, DragFloat"); - static int i1 = 50, i2 = 42; - ImGui::DragInt("drag int", &i1, 1); - ImGui::SameLine(); HelpMarker( - "Click and drag to edit value.\n" - "Hold SHIFT/ALT for faster/slower edit.\n" - "Double-click or CTRL+click to input value."); - - ImGui::DragInt("drag int 0..100", &i2, 1, 0, 100, "%d%%", ImGuiSliderFlags_AlwaysClamp); - - static float f1 = 1.00f, f2 = 0.0067f; - ImGui::DragFloat("drag float", &f1, 0.005f); - ImGui::DragFloat("drag small float", &f2, 0.0001f, 0.0f, 0.0f, "%.06f ns"); - } - - ImGui::SeparatorText("Sliders"); - - { - IMGUI_DEMO_MARKER("Widgets/Basic/SliderInt, SliderFloat"); - static int i1 = 0; - ImGui::SliderInt("slider int", &i1, -1, 3); - ImGui::SameLine(); HelpMarker("CTRL+click to input value."); - - static float f1 = 0.123f, f2 = 0.0f; - ImGui::SliderFloat("slider float", &f1, 0.0f, 1.0f, "ratio = %.3f"); - ImGui::SliderFloat("slider float (log)", &f2, -10.0f, 10.0f, "%.4f", ImGuiSliderFlags_Logarithmic); - - IMGUI_DEMO_MARKER("Widgets/Basic/SliderAngle"); - static float angle = 0.0f; - ImGui::SliderAngle("slider angle", &angle); - - // Using the format string to display a name instead of an integer. - // Here we completely omit '%d' from the format string, so it'll only display a name. - // This technique can also be used with DragInt(). - IMGUI_DEMO_MARKER("Widgets/Basic/Slider (enum)"); - enum Element { Element_Fire, Element_Earth, Element_Air, Element_Water, Element_COUNT }; - static int elem = Element_Fire; - const char* elems_names[Element_COUNT] = { "Fire", "Earth", "Air", "Water" }; - const char* elem_name = (elem >= 0 && elem < Element_COUNT) ? elems_names[elem] : "Unknown"; - ImGui::SliderInt("slider enum", &elem, 0, Element_COUNT - 1, elem_name); // Use ImGuiSliderFlags_NoInput flag to disable CTRL+Click here. - ImGui::SameLine(); HelpMarker("Using the format string parameter to display a name instead of the underlying integer."); - } - - ImGui::SeparatorText("Selectors/Pickers"); - - { - IMGUI_DEMO_MARKER("Widgets/Basic/ColorEdit3, ColorEdit4"); - static float col1[3] = { 1.0f, 0.0f, 0.2f }; - static float col2[4] = { 0.4f, 0.7f, 0.0f, 0.5f }; - ImGui::ColorEdit3("color 1", col1); - ImGui::SameLine(); HelpMarker( - "Click on the color square to open a color picker.\n" - "Click and hold to use drag and drop.\n" - "Right-click on the color square to show options.\n" - "CTRL+click on individual component to input value.\n"); - - ImGui::ColorEdit4("color 2", col2); - } - - { - // Using the _simplified_ one-liner Combo() api here - // See "Combo" section for examples of how to use the more flexible BeginCombo()/EndCombo() api. - IMGUI_DEMO_MARKER("Widgets/Basic/Combo"); - const char* items[] = { "AAAA", "BBBB", "CCCC", "DDDD", "EEEE", "FFFF", "GGGG", "HHHH", "IIIIIII", "JJJJ", "KKKKKKK" }; - static int item_current = 0; - ImGui::Combo("combo", &item_current, items, IM_ARRAYSIZE(items)); - ImGui::SameLine(); HelpMarker( - "Using the simplified one-liner Combo API here.\nRefer to the \"Combo\" section below for an explanation of how to use the more flexible and general BeginCombo/EndCombo API."); - } - - { - // Using the _simplified_ one-liner ListBox() api here - // See "List boxes" section for examples of how to use the more flexible BeginListBox()/EndListBox() api. - IMGUI_DEMO_MARKER("Widgets/Basic/ListBox"); - const char* items[] = { "Apple", "Banana", "Cherry", "Kiwi", "Mango", "Orange", "Pineapple", "Strawberry", "Watermelon" }; - static int item_current = 1; - ImGui::ListBox("listbox", &item_current, items, IM_ARRAYSIZE(items), 4); - ImGui::SameLine(); HelpMarker( - "Using the simplified one-liner ListBox API here.\nRefer to the \"List boxes\" section below for an explanation of how to use the more flexible and general BeginListBox/EndListBox API."); - } - - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Tooltips"); - if (ImGui::TreeNode("Tooltips")) - { - // Tooltips are windows following the mouse. They do not take focus away. - ImGui::SeparatorText("General"); - - // Typical use cases: - // - Short-form (text only): SetItemTooltip("Hello"); - // - Short-form (any contents): if (BeginItemTooltip()) { Text("Hello"); EndTooltip(); } - - // - Full-form (text only): if (IsItemHovered(...)) { SetTooltip("Hello"); } - // - Full-form (any contents): if (IsItemHovered(...) && BeginTooltip()) { Text("Hello"); EndTooltip(); } - - HelpMarker( - "Tooltip are typically created by using a IsItemHovered() + SetTooltip() sequence.\n\n" - "We provide a helper SetItemTooltip() function to perform the two with standards flags."); - - ImVec2 sz = ImVec2(-FLT_MIN, 0.0f); - - ImGui::Button("Basic", sz); - ImGui::SetItemTooltip("I am a tooltip"); - - ImGui::Button("Fancy", sz); - if (ImGui::BeginItemTooltip()) - { - ImGui::Text("I am a fancy tooltip"); - static float arr[] = { 0.6f, 0.1f, 1.0f, 0.5f, 0.92f, 0.1f, 0.2f }; - ImGui::PlotLines("Curve", arr, IM_ARRAYSIZE(arr)); - ImGui::Text("Sin(time) = %f", sinf((float)ImGui::GetTime())); - ImGui::EndTooltip(); - } - - ImGui::SeparatorText("Always On"); - - // Showcase NOT relying on a IsItemHovered() to emit a tooltip. - // Here the tooltip is always emitted when 'always_on == true'. - static int always_on = 0; - ImGui::RadioButton("Off", &always_on, 0); - ImGui::SameLine(); - ImGui::RadioButton("Always On (Simple)", &always_on, 1); - ImGui::SameLine(); - ImGui::RadioButton("Always On (Advanced)", &always_on, 2); - if (always_on == 1) - ImGui::SetTooltip("I am following you around."); - else if (always_on == 2 && ImGui::BeginTooltip()) - { - ImGui::ProgressBar(sinf((float)ImGui::GetTime()) * 0.5f + 0.5f, ImVec2(ImGui::GetFontSize() * 25, 0.0f)); - ImGui::EndTooltip(); - } - - ImGui::SeparatorText("Custom"); - - HelpMarker( - "Passing ImGuiHoveredFlags_ForTooltip to IsItemHovered() is the preferred way to standardize" - "tooltip activation details across your application. You may however decide to use custom" - "flags for a specific tooltip instance."); - - // The following examples are passed for documentation purpose but may not be useful to most users. - // Passing ImGuiHoveredFlags_ForTooltip to IsItemHovered() will pull ImGuiHoveredFlags flags values from - // 'style.HoverFlagsForTooltipMouse' or 'style.HoverFlagsForTooltipNav' depending on whether mouse or gamepad/keyboard is being used. - // With default settings, ImGuiHoveredFlags_ForTooltip is equivalent to ImGuiHoveredFlags_DelayShort + ImGuiHoveredFlags_Stationary. - ImGui::Button("Manual", sz); - if (ImGui::IsItemHovered(ImGuiHoveredFlags_ForTooltip)) - ImGui::SetTooltip("I am a manually emitted tooltip."); - - ImGui::Button("DelayNone", sz); - if (ImGui::IsItemHovered(ImGuiHoveredFlags_DelayNone)) - ImGui::SetTooltip("I am a tooltip with no delay."); - - ImGui::Button("DelayShort", sz); - if (ImGui::IsItemHovered(ImGuiHoveredFlags_DelayShort | ImGuiHoveredFlags_NoSharedDelay)) - ImGui::SetTooltip("I am a tooltip with a short delay (%0.2f sec).", ImGui::GetStyle().HoverDelayShort); - - ImGui::Button("DelayLong", sz); - if (ImGui::IsItemHovered(ImGuiHoveredFlags_DelayNormal | ImGuiHoveredFlags_NoSharedDelay)) - ImGui::SetTooltip("I am a tooltip with a long delay (%0.2f sec).", ImGui::GetStyle().HoverDelayNormal); - - ImGui::Button("Stationary", sz); - if (ImGui::IsItemHovered(ImGuiHoveredFlags_Stationary)) - ImGui::SetTooltip("I am a tooltip requiring mouse to be stationary before activating."); - - // Using ImGuiHoveredFlags_ForTooltip will pull flags from 'style.HoverFlagsForTooltipMouse' or 'style.HoverFlagsForTooltipNav', - // which default value include the ImGuiHoveredFlags_AllowWhenDisabled flag. - // As a result, Set - ImGui::BeginDisabled(); - ImGui::Button("Disabled item", sz); - ImGui::EndDisabled(); - if (ImGui::IsItemHovered(ImGuiHoveredFlags_ForTooltip)) - ImGui::SetTooltip("I am a a tooltip for a disabled item."); - - ImGui::TreePop(); - } - - // Testing ImGuiOnceUponAFrame helper. - //static ImGuiOnceUponAFrame once; - //for (int i = 0; i < 5; i++) - // if (once) - // ImGui::Text("This will be displayed only once."); - - IMGUI_DEMO_MARKER("Widgets/Tree Nodes"); - if (ImGui::TreeNode("Tree Nodes")) - { - IMGUI_DEMO_MARKER("Widgets/Tree Nodes/Basic trees"); - if (ImGui::TreeNode("Basic trees")) - { - for (int i = 0; i < 5; i++) - { - // Use SetNextItemOpen() so set the default state of a node to be open. We could - // also use TreeNodeEx() with the ImGuiTreeNodeFlags_DefaultOpen flag to achieve the same thing! - if (i == 0) - ImGui::SetNextItemOpen(true, ImGuiCond_Once); - - if (ImGui::TreeNode((void*)(intptr_t)i, "Child %d", i)) - { - ImGui::Text("blah blah"); - ImGui::SameLine(); - if (ImGui::SmallButton("button")) {} - ImGui::TreePop(); - } - } - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Tree Nodes/Advanced, with Selectable nodes"); - if (ImGui::TreeNode("Advanced, with Selectable nodes")) - { - HelpMarker( - "This is a more typical looking tree with selectable nodes.\n" - "Click to select, CTRL+Click to toggle, click on arrows or double-click to open."); - static ImGuiTreeNodeFlags base_flags = ImGuiTreeNodeFlags_OpenOnArrow | ImGuiTreeNodeFlags_OpenOnDoubleClick | ImGuiTreeNodeFlags_SpanAvailWidth; - static bool align_label_with_current_x_position = false; - static bool test_drag_and_drop = false; - ImGui::CheckboxFlags("ImGuiTreeNodeFlags_OpenOnArrow", &base_flags, ImGuiTreeNodeFlags_OpenOnArrow); - ImGui::CheckboxFlags("ImGuiTreeNodeFlags_OpenOnDoubleClick", &base_flags, ImGuiTreeNodeFlags_OpenOnDoubleClick); - ImGui::CheckboxFlags("ImGuiTreeNodeFlags_SpanAvailWidth", &base_flags, ImGuiTreeNodeFlags_SpanAvailWidth); ImGui::SameLine(); HelpMarker("Extend hit area to all available width instead of allowing more items to be laid out after the node."); - ImGui::CheckboxFlags("ImGuiTreeNodeFlags_SpanFullWidth", &base_flags, ImGuiTreeNodeFlags_SpanFullWidth); - ImGui::CheckboxFlags("ImGuiTreeNodeFlags_SpanAllColumns", &base_flags, ImGuiTreeNodeFlags_SpanAllColumns); ImGui::SameLine(); HelpMarker("For use in Tables only."); - ImGui::Checkbox("Align label with current X position", &align_label_with_current_x_position); - ImGui::Checkbox("Test tree node as drag source", &test_drag_and_drop); - ImGui::Text("Hello!"); - if (align_label_with_current_x_position) - ImGui::Unindent(ImGui::GetTreeNodeToLabelSpacing()); - - // 'selection_mask' is dumb representation of what may be user-side selection state. - // You may retain selection state inside or outside your objects in whatever format you see fit. - // 'node_clicked' is temporary storage of what node we have clicked to process selection at the end - /// of the loop. May be a pointer to your own node type, etc. - static int selection_mask = (1 << 2); - int node_clicked = -1; - for (int i = 0; i < 6; i++) - { - // Disable the default "open on single-click behavior" + set Selected flag according to our selection. - // To alter selection we use IsItemClicked() && !IsItemToggledOpen(), so clicking on an arrow doesn't alter selection. - ImGuiTreeNodeFlags node_flags = base_flags; - const bool is_selected = (selection_mask & (1 << i)) != 0; - if (is_selected) - node_flags |= ImGuiTreeNodeFlags_Selected; - if (i < 3) - { - // Items 0..2 are Tree Node - bool node_open = ImGui::TreeNodeEx((void*)(intptr_t)i, node_flags, "Selectable Node %d", i); - if (ImGui::IsItemClicked() && !ImGui::IsItemToggledOpen()) - node_clicked = i; - if (test_drag_and_drop && ImGui::BeginDragDropSource()) - { - ImGui::SetDragDropPayload("_TREENODE", NULL, 0); - ImGui::Text("This is a drag and drop source"); - ImGui::EndDragDropSource(); - } - if (node_open) - { - ImGui::BulletText("Blah blah\nBlah Blah"); - ImGui::TreePop(); - } - } - else - { - // Items 3..5 are Tree Leaves - // The only reason we use TreeNode at all is to allow selection of the leaf. Otherwise we can - // use BulletText() or advance the cursor by GetTreeNodeToLabelSpacing() and call Text(). - node_flags |= ImGuiTreeNodeFlags_Leaf | ImGuiTreeNodeFlags_NoTreePushOnOpen; // ImGuiTreeNodeFlags_Bullet - ImGui::TreeNodeEx((void*)(intptr_t)i, node_flags, "Selectable Leaf %d", i); - if (ImGui::IsItemClicked() && !ImGui::IsItemToggledOpen()) - node_clicked = i; - if (test_drag_and_drop && ImGui::BeginDragDropSource()) - { - ImGui::SetDragDropPayload("_TREENODE", NULL, 0); - ImGui::Text("This is a drag and drop source"); - ImGui::EndDragDropSource(); - } - } - } - if (node_clicked != -1) - { - // Update selection state - // (process outside of tree loop to avoid visual inconsistencies during the clicking frame) - if (ImGui::GetIO().KeyCtrl) - selection_mask ^= (1 << node_clicked); // CTRL+click to toggle - else //if (!(selection_mask & (1 << node_clicked))) // Depending on selection behavior you want, may want to preserve selection when clicking on item that is part of the selection - selection_mask = (1 << node_clicked); // Click to single-select - } - if (align_label_with_current_x_position) - ImGui::Indent(ImGui::GetTreeNodeToLabelSpacing()); - ImGui::TreePop(); - } - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Collapsing Headers"); - if (ImGui::TreeNode("Collapsing Headers")) - { - static bool closable_group = true; - ImGui::Checkbox("Show 2nd header", &closable_group); - if (ImGui::CollapsingHeader("Header", ImGuiTreeNodeFlags_None)) - { - ImGui::Text("IsItemHovered: %d", ImGui::IsItemHovered()); - for (int i = 0; i < 5; i++) - ImGui::Text("Some content %d", i); - } - if (ImGui::CollapsingHeader("Header with a close button", &closable_group)) - { - ImGui::Text("IsItemHovered: %d", ImGui::IsItemHovered()); - for (int i = 0; i < 5; i++) - ImGui::Text("More content %d", i); - } - /* - if (ImGui::CollapsingHeader("Header with a bullet", ImGuiTreeNodeFlags_Bullet)) - ImGui::Text("IsItemHovered: %d", ImGui::IsItemHovered()); - */ - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Bullets"); - if (ImGui::TreeNode("Bullets")) - { - ImGui::BulletText("Bullet point 1"); - ImGui::BulletText("Bullet point 2\nOn multiple lines"); - if (ImGui::TreeNode("Tree node")) - { - ImGui::BulletText("Another bullet point"); - ImGui::TreePop(); - } - ImGui::Bullet(); ImGui::Text("Bullet point 3 (two calls)"); - ImGui::Bullet(); ImGui::SmallButton("Button"); - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Text"); - if (ImGui::TreeNode("Text")) - { - IMGUI_DEMO_MARKER("Widgets/Text/Colored Text"); - if (ImGui::TreeNode("Colorful Text")) - { - // Using shortcut. You can use PushStyleColor()/PopStyleColor() for more flexibility. - ImGui::TextColored(ImVec4(1.0f, 0.0f, 1.0f, 1.0f), "Pink"); - ImGui::TextColored(ImVec4(1.0f, 1.0f, 0.0f, 1.0f), "Yellow"); - ImGui::TextDisabled("Disabled"); - ImGui::SameLine(); HelpMarker("The TextDisabled color is stored in ImGuiStyle."); - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Text/Word Wrapping"); - if (ImGui::TreeNode("Word Wrapping")) - { - // Using shortcut. You can use PushTextWrapPos()/PopTextWrapPos() for more flexibility. - ImGui::TextWrapped( - "This text should automatically wrap on the edge of the window. The current implementation " - "for text wrapping follows simple rules suitable for English and possibly other languages."); - ImGui::Spacing(); - - static float wrap_width = 200.0f; - ImGui::SliderFloat("Wrap width", &wrap_width, -20, 600, "%.0f"); - - ImDrawList* draw_list = ImGui::GetWindowDrawList(); - for (int n = 0; n < 2; n++) - { - ImGui::Text("Test paragraph %d:", n); - ImVec2 pos = ImGui::GetCursorScreenPos(); - ImVec2 marker_min = ImVec2(pos.x + wrap_width, pos.y); - ImVec2 marker_max = ImVec2(pos.x + wrap_width + 10, pos.y + ImGui::GetTextLineHeight()); - ImGui::PushTextWrapPos(ImGui::GetCursorPos().x + wrap_width); - if (n == 0) - ImGui::Text("The lazy dog is a good dog. This paragraph should fit within %.0f pixels. Testing a 1 character word. The quick brown fox jumps over the lazy dog.", wrap_width); - else - ImGui::Text("aaaaaaaa bbbbbbbb, c cccccccc,dddddddd. d eeeeeeee ffffffff. gggggggg!hhhhhhhh"); - - // Draw actual text bounding box, following by marker of our expected limit (should not overlap!) - draw_list->AddRect(ImGui::GetItemRectMin(), ImGui::GetItemRectMax(), IM_COL32(255, 255, 0, 255)); - draw_list->AddRectFilled(marker_min, marker_max, IM_COL32(255, 0, 255, 255)); - ImGui::PopTextWrapPos(); - } - - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Text/UTF-8 Text"); - if (ImGui::TreeNode("UTF-8 Text")) - { - // UTF-8 test with Japanese characters - // (Needs a suitable font? Try "Google Noto" or "Arial Unicode". See docs/FONTS.md for details.) - // - From C++11 you can use the u8"my text" syntax to encode literal strings as UTF-8 - // - For earlier compiler, you may be able to encode your sources as UTF-8 (e.g. in Visual Studio, you - // can save your source files as 'UTF-8 without signature'). - // - FOR THIS DEMO FILE ONLY, BECAUSE WE WANT TO SUPPORT OLD COMPILERS, WE ARE *NOT* INCLUDING RAW UTF-8 - // CHARACTERS IN THIS SOURCE FILE. Instead we are encoding a few strings with hexadecimal constants. - // Don't do this in your application! Please use u8"text in any language" in your application! - // Note that characters values are preserved even by InputText() if the font cannot be displayed, - // so you can safely copy & paste garbled characters into another application. - ImGui::TextWrapped( - "CJK text will only appear if the font was loaded with the appropriate CJK character ranges. " - "Call io.Fonts->AddFontFromFileTTF() manually to load extra character ranges. " - "Read docs/FONTS.md for details."); - ImGui::Text("Hiragana: \xe3\x81\x8b\xe3\x81\x8d\xe3\x81\x8f\xe3\x81\x91\xe3\x81\x93 (kakikukeko)"); // Normally we would use u8"blah blah" with the proper characters directly in the string. - ImGui::Text("Kanjis: \xe6\x97\xa5\xe6\x9c\xac\xe8\xaa\x9e (nihongo)"); - static char buf[32] = "\xe6\x97\xa5\xe6\x9c\xac\xe8\xaa\x9e"; - //static char buf[32] = u8"NIHONGO"; // <- this is how you would write it with C++11, using real kanjis - ImGui::InputText("UTF-8 input", buf, IM_ARRAYSIZE(buf)); - ImGui::TreePop(); - } - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Images"); - if (ImGui::TreeNode("Images")) - { - ImGuiIO& io = ImGui::GetIO(); - ImGui::TextWrapped( - "Below we are displaying the font texture (which is the only texture we have access to in this demo). " - "Use the 'ImTextureID' type as storage to pass pointers or identifier to your own texture data. " - "Hover the texture for a zoomed view!"); - - // Below we are displaying the font texture because it is the only texture we have access to inside the demo! - // Remember that ImTextureID is just storage for whatever you want it to be. It is essentially a value that - // will be passed to the rendering backend via the ImDrawCmd structure. - // If you use one of the default imgui_impl_XXXX.cpp rendering backend, they all have comments at the top - // of their respective source file to specify what they expect to be stored in ImTextureID, for example: - // - The imgui_impl_dx11.cpp renderer expect a 'ID3D11ShaderResourceView*' pointer - // - The imgui_impl_opengl3.cpp renderer expect a GLuint OpenGL texture identifier, etc. - // More: - // - If you decided that ImTextureID = MyEngineTexture*, then you can pass your MyEngineTexture* pointers - // to ImGui::Image(), and gather width/height through your own functions, etc. - // - You can use ShowMetricsWindow() to inspect the draw data that are being passed to your renderer, - // it will help you debug issues if you are confused about it. - // - Consider using the lower-level ImDrawList::AddImage() API, via ImGui::GetWindowDrawList()->AddImage(). - // - Read https://github.com/ocornut/imgui/blob/master/docs/FAQ.md - // - Read https://github.com/ocornut/imgui/wiki/Image-Loading-and-Displaying-Examples - ImTextureID my_tex_id = io.Fonts->TexID; - float my_tex_w = (float)io.Fonts->TexWidth; - float my_tex_h = (float)io.Fonts->TexHeight; - { - static bool use_text_color_for_tint = false; - ImGui::Checkbox("Use Text Color for Tint", &use_text_color_for_tint); - ImGui::Text("%.0fx%.0f", my_tex_w, my_tex_h); - ImVec2 pos = ImGui::GetCursorScreenPos(); - ImVec2 uv_min = ImVec2(0.0f, 0.0f); // Top-left - ImVec2 uv_max = ImVec2(1.0f, 1.0f); // Lower-right - ImVec4 tint_col = use_text_color_for_tint ? ImGui::GetStyleColorVec4(ImGuiCol_Text) : ImVec4(1.0f, 1.0f, 1.0f, 1.0f); // No tint - ImVec4 border_col = ImGui::GetStyleColorVec4(ImGuiCol_Border); - ImGui::Image(my_tex_id, ImVec2(my_tex_w, my_tex_h), uv_min, uv_max, tint_col, border_col); - if (ImGui::BeginItemTooltip()) - { - float region_sz = 32.0f; - float region_x = io.MousePos.x - pos.x - region_sz * 0.5f; - float region_y = io.MousePos.y - pos.y - region_sz * 0.5f; - float zoom = 4.0f; - if (region_x < 0.0f) { region_x = 0.0f; } - else if (region_x > my_tex_w - region_sz) { region_x = my_tex_w - region_sz; } - if (region_y < 0.0f) { region_y = 0.0f; } - else if (region_y > my_tex_h - region_sz) { region_y = my_tex_h - region_sz; } - ImGui::Text("Min: (%.2f, %.2f)", region_x, region_y); - ImGui::Text("Max: (%.2f, %.2f)", region_x + region_sz, region_y + region_sz); - ImVec2 uv0 = ImVec2((region_x) / my_tex_w, (region_y) / my_tex_h); - ImVec2 uv1 = ImVec2((region_x + region_sz) / my_tex_w, (region_y + region_sz) / my_tex_h); - ImGui::Image(my_tex_id, ImVec2(region_sz * zoom, region_sz * zoom), uv0, uv1, tint_col, border_col); - ImGui::EndTooltip(); - } - } - - IMGUI_DEMO_MARKER("Widgets/Images/Textured buttons"); - ImGui::TextWrapped("And now some textured buttons.."); - static int pressed_count = 0; - for (int i = 0; i < 8; i++) - { - // UV coordinates are often (0.0f, 0.0f) and (1.0f, 1.0f) to display an entire textures. - // Here are trying to display only a 32x32 pixels area of the texture, hence the UV computation. - // Read about UV coordinates here: https://github.com/ocornut/imgui/wiki/Image-Loading-and-Displaying-Examples - ImGui::PushID(i); - if (i > 0) - ImGui::PushStyleVar(ImGuiStyleVar_FramePadding, ImVec2(i - 1.0f, i - 1.0f)); - ImVec2 size = ImVec2(32.0f, 32.0f); // Size of the image we want to make visible - ImVec2 uv0 = ImVec2(0.0f, 0.0f); // UV coordinates for lower-left - ImVec2 uv1 = ImVec2(32.0f / my_tex_w, 32.0f / my_tex_h); // UV coordinates for (32,32) in our texture - ImVec4 bg_col = ImVec4(0.0f, 0.0f, 0.0f, 1.0f); // Black background - ImVec4 tint_col = ImVec4(1.0f, 1.0f, 1.0f, 1.0f); // No tint - if (ImGui::ImageButton("", my_tex_id, size, uv0, uv1, bg_col, tint_col)) - pressed_count += 1; - if (i > 0) - ImGui::PopStyleVar(); - ImGui::PopID(); - ImGui::SameLine(); - } - ImGui::NewLine(); - ImGui::Text("Pressed %d times.", pressed_count); - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Combo"); - if (ImGui::TreeNode("Combo")) - { - // Combo Boxes are also called "Dropdown" in other systems - // Expose flags as checkbox for the demo - static ImGuiComboFlags flags = 0; - ImGui::CheckboxFlags("ImGuiComboFlags_PopupAlignLeft", &flags, ImGuiComboFlags_PopupAlignLeft); - ImGui::SameLine(); HelpMarker("Only makes a difference if the popup is larger than the combo"); - if (ImGui::CheckboxFlags("ImGuiComboFlags_NoArrowButton", &flags, ImGuiComboFlags_NoArrowButton)) - flags &= ~ImGuiComboFlags_NoPreview; // Clear the other flag, as we cannot combine both - if (ImGui::CheckboxFlags("ImGuiComboFlags_NoPreview", &flags, ImGuiComboFlags_NoPreview)) - flags &= ~(ImGuiComboFlags_NoArrowButton | ImGuiComboFlags_WidthFitPreview); // Clear the other flag, as we cannot combine both - if (ImGui::CheckboxFlags("ImGuiComboFlags_WidthFitPreview", &flags, ImGuiComboFlags_WidthFitPreview)) - flags &= ~ImGuiComboFlags_NoPreview; - - // Using the generic BeginCombo() API, you have full control over how to display the combo contents. - // (your selection data could be an index, a pointer to the object, an id for the object, a flag intrusively - // stored in the object itself, etc.) - const char* items[] = { "AAAA", "BBBB", "CCCC", "DDDD", "EEEE", "FFFF", "GGGG", "HHHH", "IIII", "JJJJ", "KKKK", "LLLLLLL", "MMMM", "OOOOOOO" }; - static int item_current_idx = 0; // Here we store our selection data as an index. - const char* combo_preview_value = items[item_current_idx]; // Pass in the preview value visible before opening the combo (it could be anything) - if (ImGui::BeginCombo("combo 1", combo_preview_value, flags)) - { - for (int n = 0; n < IM_ARRAYSIZE(items); n++) - { - const bool is_selected = (item_current_idx == n); - if (ImGui::Selectable(items[n], is_selected)) - item_current_idx = n; - - // Set the initial focus when opening the combo (scrolling + keyboard navigation focus) - if (is_selected) - ImGui::SetItemDefaultFocus(); - } - ImGui::EndCombo(); - } - - // Simplified one-liner Combo() API, using values packed in a single constant string - // This is a convenience for when the selection set is small and known at compile-time. - static int item_current_2 = 0; - ImGui::Combo("combo 2 (one-liner)", &item_current_2, "aaaa\0bbbb\0cccc\0dddd\0eeee\0\0"); - - // Simplified one-liner Combo() using an array of const char* - // This is not very useful (may obsolete): prefer using BeginCombo()/EndCombo() for full control. - static int item_current_3 = -1; // If the selection isn't within 0..count, Combo won't display a preview - ImGui::Combo("combo 3 (array)", &item_current_3, items, IM_ARRAYSIZE(items)); - - // Simplified one-liner Combo() using an accessor function - static int item_current_4 = 0; - ImGui::Combo("combo 4 (function)", &item_current_4, [](void* data, int n) { return ((const char**)data)[n]; }, items, IM_ARRAYSIZE(items)); - - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/List Boxes"); - if (ImGui::TreeNode("List boxes")) - { - // Using the generic BeginListBox() API, you have full control over how to display the combo contents. - // (your selection data could be an index, a pointer to the object, an id for the object, a flag intrusively - // stored in the object itself, etc.) - const char* items[] = { "AAAA", "BBBB", "CCCC", "DDDD", "EEEE", "FFFF", "GGGG", "HHHH", "IIII", "JJJJ", "KKKK", "LLLLLLL", "MMMM", "OOOOOOO" }; - static int item_current_idx = 0; // Here we store our selection data as an index. - if (ImGui::BeginListBox("listbox 1")) - { - for (int n = 0; n < IM_ARRAYSIZE(items); n++) - { - const bool is_selected = (item_current_idx == n); - if (ImGui::Selectable(items[n], is_selected)) - item_current_idx = n; - - // Set the initial focus when opening the combo (scrolling + keyboard navigation focus) - if (is_selected) - ImGui::SetItemDefaultFocus(); - } - ImGui::EndListBox(); - } - - // Custom size: use all width, 5 items tall - ImGui::Text("Full-width:"); - if (ImGui::BeginListBox("##listbox 2", ImVec2(-FLT_MIN, 5 * ImGui::GetTextLineHeightWithSpacing()))) - { - for (int n = 0; n < IM_ARRAYSIZE(items); n++) - { - const bool is_selected = (item_current_idx == n); - if (ImGui::Selectable(items[n], is_selected)) - item_current_idx = n; - - // Set the initial focus when opening the combo (scrolling + keyboard navigation focus) - if (is_selected) - ImGui::SetItemDefaultFocus(); - } - ImGui::EndListBox(); - } - - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Selectables"); - if (ImGui::TreeNode("Selectables")) - { - // Selectable() has 2 overloads: - // - The one taking "bool selected" as a read-only selection information. - // When Selectable() has been clicked it returns true and you can alter selection state accordingly. - // - The one taking "bool* p_selected" as a read-write selection information (convenient in some cases) - // The earlier is more flexible, as in real application your selection may be stored in many different ways - // and not necessarily inside a bool value (e.g. in flags within objects, as an external list, etc). - IMGUI_DEMO_MARKER("Widgets/Selectables/Basic"); - if (ImGui::TreeNode("Basic")) - { - static bool selection[5] = { false, true, false, false }; - ImGui::Selectable("1. I am selectable", &selection[0]); - ImGui::Selectable("2. I am selectable", &selection[1]); - ImGui::Selectable("3. I am selectable", &selection[2]); - if (ImGui::Selectable("4. I am double clickable", selection[3], ImGuiSelectableFlags_AllowDoubleClick)) - if (ImGui::IsMouseDoubleClicked(0)) - selection[3] = !selection[3]; - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Selectables/Single Selection"); - if (ImGui::TreeNode("Selection State: Single Selection")) - { - static int selected = -1; - for (int n = 0; n < 5; n++) - { - char buf[32]; - sprintf(buf, "Object %d", n); - if (ImGui::Selectable(buf, selected == n)) - selected = n; - } - ImGui::TreePop(); - } - IMGUI_DEMO_MARKER("Widgets/Selectables/Multiple Selection"); - if (ImGui::TreeNode("Selection State: Multiple Selection")) - { - HelpMarker("Hold CTRL and click to select multiple items."); - static bool selection[5] = { false, false, false, false, false }; - for (int n = 0; n < 5; n++) - { - char buf[32]; - sprintf(buf, "Object %d", n); - if (ImGui::Selectable(buf, selection[n])) - { - if (!ImGui::GetIO().KeyCtrl) // Clear selection when CTRL is not held - memset(selection, 0, sizeof(selection)); - selection[n] ^= 1; - } - } - ImGui::TreePop(); - } - IMGUI_DEMO_MARKER("Widgets/Selectables/Rendering more items on the same line"); - if (ImGui::TreeNode("Rendering more items on the same line")) - { - // (1) Using SetNextItemAllowOverlap() - // (2) Using the Selectable() override that takes "bool* p_selected" parameter, the bool value is toggled automatically. - static bool selected[3] = { false, false, false }; - ImGui::SetNextItemAllowOverlap(); ImGui::Selectable("main.c", &selected[0]); ImGui::SameLine(); ImGui::SmallButton("Link 1"); - ImGui::SetNextItemAllowOverlap(); ImGui::Selectable("Hello.cpp", &selected[1]); ImGui::SameLine(); ImGui::SmallButton("Link 2"); - ImGui::SetNextItemAllowOverlap(); ImGui::Selectable("Hello.h", &selected[2]); ImGui::SameLine(); ImGui::SmallButton("Link 3"); - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Selectables/In columns"); - if (ImGui::TreeNode("In columns")) - { - static bool selected[10] = {}; - - if (ImGui::BeginTable("split1", 3, ImGuiTableFlags_Resizable | ImGuiTableFlags_NoSavedSettings | ImGuiTableFlags_Borders)) - { - for (int i = 0; i < 10; i++) - { - char label[32]; - sprintf(label, "Item %d", i); - ImGui::TableNextColumn(); - ImGui::Selectable(label, &selected[i]); // FIXME-TABLE: Selection overlap - } - ImGui::EndTable(); - } - ImGui::Spacing(); - if (ImGui::BeginTable("split2", 3, ImGuiTableFlags_Resizable | ImGuiTableFlags_NoSavedSettings | ImGuiTableFlags_Borders)) - { - for (int i = 0; i < 10; i++) - { - char label[32]; - sprintf(label, "Item %d", i); - ImGui::TableNextRow(); - ImGui::TableNextColumn(); - ImGui::Selectable(label, &selected[i], ImGuiSelectableFlags_SpanAllColumns); - ImGui::TableNextColumn(); - ImGui::Text("Some other contents"); - ImGui::TableNextColumn(); - ImGui::Text("123456"); - } - ImGui::EndTable(); - } - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Selectables/Grid"); - if (ImGui::TreeNode("Grid")) - { - static char selected[4][4] = { { 1, 0, 0, 0 }, { 0, 1, 0, 0 }, { 0, 0, 1, 0 }, { 0, 0, 0, 1 } }; - - // Add in a bit of silly fun... - const float time = (float)ImGui::GetTime(); - const bool winning_state = memchr(selected, 0, sizeof(selected)) == NULL; // If all cells are selected... - if (winning_state) - ImGui::PushStyleVar(ImGuiStyleVar_SelectableTextAlign, ImVec2(0.5f + 0.5f * cosf(time * 2.0f), 0.5f + 0.5f * sinf(time * 3.0f))); - - for (int y = 0; y < 4; y++) - for (int x = 0; x < 4; x++) - { - if (x > 0) - ImGui::SameLine(); - ImGui::PushID(y * 4 + x); - if (ImGui::Selectable("Sailor", selected[y][x] != 0, 0, ImVec2(50, 50))) - { - // Toggle clicked cell + toggle neighbors - selected[y][x] ^= 1; - if (x > 0) { selected[y][x - 1] ^= 1; } - if (x < 3) { selected[y][x + 1] ^= 1; } - if (y > 0) { selected[y - 1][x] ^= 1; } - if (y < 3) { selected[y + 1][x] ^= 1; } - } - ImGui::PopID(); - } - - if (winning_state) - ImGui::PopStyleVar(); - ImGui::TreePop(); - } - IMGUI_DEMO_MARKER("Widgets/Selectables/Alignment"); - if (ImGui::TreeNode("Alignment")) - { - HelpMarker( - "By default, Selectables uses style.SelectableTextAlign but it can be overridden on a per-item " - "basis using PushStyleVar(). You'll probably want to always keep your default situation to " - "left-align otherwise it becomes difficult to layout multiple items on a same line"); - static bool selected[3 * 3] = { true, false, true, false, true, false, true, false, true }; - for (int y = 0; y < 3; y++) - { - for (int x = 0; x < 3; x++) - { - ImVec2 alignment = ImVec2((float)x / 2.0f, (float)y / 2.0f); - char name[32]; - sprintf(name, "(%.1f,%.1f)", alignment.x, alignment.y); - if (x > 0) ImGui::SameLine(); - ImGui::PushStyleVar(ImGuiStyleVar_SelectableTextAlign, alignment); - ImGui::Selectable(name, &selected[3 * y + x], ImGuiSelectableFlags_None, ImVec2(80, 80)); - ImGui::PopStyleVar(); - } - } - ImGui::TreePop(); - } - ImGui::TreePop(); - } - - // To wire InputText() with std::string or any other custom string type, - // see the "Text Input > Resize Callback" section of this demo, and the misc/cpp/imgui_stdlib.h file. - IMGUI_DEMO_MARKER("Widgets/Text Input"); - if (ImGui::TreeNode("Text Input")) - { - IMGUI_DEMO_MARKER("Widgets/Text Input/Multi-line Text Input"); - if (ImGui::TreeNode("Multi-line Text Input")) - { - // Note: we are using a fixed-sized buffer for simplicity here. See ImGuiInputTextFlags_CallbackResize - // and the code in misc/cpp/imgui_stdlib.h for how to setup InputText() for dynamically resizing strings. - static char text[1024 * 16] = - "/*\n" - " The Pentium F00F bug, shorthand for F0 0F C7 C8,\n" - " the hexadecimal encoding of one offending instruction,\n" - " more formally, the invalid operand with locked CMPXCHG8B\n" - " instruction bug, is a design flaw in the majority of\n" - " Intel Pentium, Pentium MMX, and Pentium OverDrive\n" - " processors (all in the P5 microarchitecture).\n" - "*/\n\n" - "label:\n" - "\tlock cmpxchg8b eax\n"; - - static ImGuiInputTextFlags flags = ImGuiInputTextFlags_AllowTabInput; - HelpMarker("You can use the ImGuiInputTextFlags_CallbackResize facility if you need to wire InputTextMultiline() to a dynamic string type. See misc/cpp/imgui_stdlib.h for an example. (This is not demonstrated in imgui_demo.cpp because we don't want to include in here)"); - ImGui::CheckboxFlags("ImGuiInputTextFlags_ReadOnly", &flags, ImGuiInputTextFlags_ReadOnly); - ImGui::CheckboxFlags("ImGuiInputTextFlags_AllowTabInput", &flags, ImGuiInputTextFlags_AllowTabInput); - ImGui::CheckboxFlags("ImGuiInputTextFlags_CtrlEnterForNewLine", &flags, ImGuiInputTextFlags_CtrlEnterForNewLine); - ImGui::InputTextMultiline("##source", text, IM_ARRAYSIZE(text), ImVec2(-FLT_MIN, ImGui::GetTextLineHeight() * 16), flags); - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Text Input/Filtered Text Input"); - if (ImGui::TreeNode("Filtered Text Input")) - { - struct TextFilters - { - // Modify character input by altering 'data->Eventchar' (ImGuiInputTextFlags_CallbackCharFilter callback) - static int FilterCasingSwap(ImGuiInputTextCallbackData* data) - { - if (data->EventChar >= 'a' && data->EventChar <= 'z') { data->EventChar -= 'a' - 'A'; } // Lowercase becomes uppercase - else if (data->EventChar >= 'A' && data->EventChar <= 'Z') { data->EventChar += 'a' - 'A'; } // Uppercase becomes lowercase - return 0; - } - - // Return 0 (pass) if the character is 'i' or 'm' or 'g' or 'u' or 'i', otherwise return 1 (filter out) - static int FilterImGuiLetters(ImGuiInputTextCallbackData* data) - { - if (data->EventChar < 256 && strchr("imgui", (char)data->EventChar)) - return 0; - return 1; - } - }; - - static char buf1[32] = ""; ImGui::InputText("default", buf1, 32); - static char buf2[32] = ""; ImGui::InputText("decimal", buf2, 32, ImGuiInputTextFlags_CharsDecimal); - static char buf3[32] = ""; ImGui::InputText("hexadecimal", buf3, 32, ImGuiInputTextFlags_CharsHexadecimal | ImGuiInputTextFlags_CharsUppercase); - static char buf4[32] = ""; ImGui::InputText("uppercase", buf4, 32, ImGuiInputTextFlags_CharsUppercase); - static char buf5[32] = ""; ImGui::InputText("no blank", buf5, 32, ImGuiInputTextFlags_CharsNoBlank); - static char buf6[32] = ""; ImGui::InputText("casing swap", buf6, 32, ImGuiInputTextFlags_CallbackCharFilter, TextFilters::FilterCasingSwap); // Use CharFilter callback to replace characters. - static char buf7[32] = ""; ImGui::InputText("\"imgui\"", buf7, 32, ImGuiInputTextFlags_CallbackCharFilter, TextFilters::FilterImGuiLetters); // Use CharFilter callback to disable some characters. - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Text Input/Password input"); - if (ImGui::TreeNode("Password Input")) - { - static char password[64] = "password123"; - ImGui::InputText("password", password, IM_ARRAYSIZE(password), ImGuiInputTextFlags_Password); - ImGui::SameLine(); HelpMarker("Display all characters as '*'.\nDisable clipboard cut and copy.\nDisable logging.\n"); - ImGui::InputTextWithHint("password (w/ hint)", "", password, IM_ARRAYSIZE(password), ImGuiInputTextFlags_Password); - ImGui::InputText("password (clear)", password, IM_ARRAYSIZE(password)); - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Text Input/Completion, History, Edit Callbacks"); - if (ImGui::TreeNode("Completion, History, Edit Callbacks")) - { - struct Funcs - { - static int MyCallback(ImGuiInputTextCallbackData* data) - { - if (data->EventFlag == ImGuiInputTextFlags_CallbackCompletion) - { - data->InsertChars(data->CursorPos, ".."); - } - else if (data->EventFlag == ImGuiInputTextFlags_CallbackHistory) - { - if (data->EventKey == ImGuiKey_UpArrow) - { - data->DeleteChars(0, data->BufTextLen); - data->InsertChars(0, "Pressed Up!"); - data->SelectAll(); - } - else if (data->EventKey == ImGuiKey_DownArrow) - { - data->DeleteChars(0, data->BufTextLen); - data->InsertChars(0, "Pressed Down!"); - data->SelectAll(); - } - } - else if (data->EventFlag == ImGuiInputTextFlags_CallbackEdit) - { - // Toggle casing of first character - char c = data->Buf[0]; - if ((c >= 'a' && c <= 'z') || (c >= 'A' && c <= 'Z')) data->Buf[0] ^= 32; - data->BufDirty = true; - - // Increment a counter - int* p_int = (int*)data->UserData; - *p_int = *p_int + 1; - } - return 0; - } - }; - static char buf1[64]; - ImGui::InputText("Completion", buf1, 64, ImGuiInputTextFlags_CallbackCompletion, Funcs::MyCallback); - ImGui::SameLine(); HelpMarker("Here we append \"..\" each time Tab is pressed. See 'Examples>Console' for a more meaningful demonstration of using this callback."); - - static char buf2[64]; - ImGui::InputText("History", buf2, 64, ImGuiInputTextFlags_CallbackHistory, Funcs::MyCallback); - ImGui::SameLine(); HelpMarker("Here we replace and select text each time Up/Down are pressed. See 'Examples>Console' for a more meaningful demonstration of using this callback."); - - static char buf3[64]; - static int edit_count = 0; - ImGui::InputText("Edit", buf3, 64, ImGuiInputTextFlags_CallbackEdit, Funcs::MyCallback, (void*)&edit_count); - ImGui::SameLine(); HelpMarker("Here we toggle the casing of the first character on every edit + count edits."); - ImGui::SameLine(); ImGui::Text("(%d)", edit_count); - - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Text Input/Resize Callback"); - if (ImGui::TreeNode("Resize Callback")) - { - // To wire InputText() with std::string or any other custom string type, - // you can use the ImGuiInputTextFlags_CallbackResize flag + create a custom ImGui::InputText() wrapper - // using your preferred type. See misc/cpp/imgui_stdlib.h for an implementation of this using std::string. - HelpMarker( - "Using ImGuiInputTextFlags_CallbackResize to wire your custom string type to InputText().\n\n" - "See misc/cpp/imgui_stdlib.h for an implementation of this for std::string."); - struct Funcs - { - static int MyResizeCallback(ImGuiInputTextCallbackData* data) - { - if (data->EventFlag == ImGuiInputTextFlags_CallbackResize) - { - ImVector* my_str = (ImVector*)data->UserData; - IM_ASSERT(my_str->begin() == data->Buf); - my_str->resize(data->BufSize); // NB: On resizing calls, generally data->BufSize == data->BufTextLen + 1 - data->Buf = my_str->begin(); - } - return 0; - } - - // Note: Because ImGui:: is a namespace you would typically add your own function into the namespace. - // For example, you code may declare a function 'ImGui::InputText(const char* label, MyString* my_str)' - static bool MyInputTextMultiline(const char* label, ImVector* my_str, const ImVec2& size = ImVec2(0, 0), ImGuiInputTextFlags flags = 0) - { - IM_ASSERT((flags & ImGuiInputTextFlags_CallbackResize) == 0); - return ImGui::InputTextMultiline(label, my_str->begin(), (size_t)my_str->size(), size, flags | ImGuiInputTextFlags_CallbackResize, Funcs::MyResizeCallback, (void*)my_str); - } - }; - - // For this demo we are using ImVector as a string container. - // Note that because we need to store a terminating zero character, our size/capacity are 1 more - // than usually reported by a typical string class. - static ImVector my_str; - if (my_str.empty()) - my_str.push_back(0); - Funcs::MyInputTextMultiline("##MyStr", &my_str, ImVec2(-FLT_MIN, ImGui::GetTextLineHeight() * 16)); - ImGui::Text("Data: %p\nSize: %d\nCapacity: %d", (void*)my_str.begin(), my_str.size(), my_str.capacity()); - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Text Input/Miscellaneous"); - if (ImGui::TreeNode("Miscellaneous")) - { - static char buf1[16]; - static ImGuiInputTextFlags flags = ImGuiInputTextFlags_EscapeClearsAll; - ImGui::CheckboxFlags("ImGuiInputTextFlags_EscapeClearsAll", &flags, ImGuiInputTextFlags_EscapeClearsAll); - ImGui::CheckboxFlags("ImGuiInputTextFlags_ReadOnly", &flags, ImGuiInputTextFlags_ReadOnly); - ImGui::CheckboxFlags("ImGuiInputTextFlags_NoUndoRedo", &flags, ImGuiInputTextFlags_NoUndoRedo); - ImGui::InputText("Hello", buf1, IM_ARRAYSIZE(buf1), flags); - ImGui::TreePop(); - } - - ImGui::TreePop(); - } - - // Tabs - IMGUI_DEMO_MARKER("Widgets/Tabs"); - if (ImGui::TreeNode("Tabs")) - { - IMGUI_DEMO_MARKER("Widgets/Tabs/Basic"); - if (ImGui::TreeNode("Basic")) - { - ImGuiTabBarFlags tab_bar_flags = ImGuiTabBarFlags_None; - if (ImGui::BeginTabBar("MyTabBar", tab_bar_flags)) - { - if (ImGui::BeginTabItem("Avocado")) - { - ImGui::Text("This is the Avocado tab!\nblah blah blah blah blah"); - ImGui::EndTabItem(); - } - if (ImGui::BeginTabItem("Broccoli")) - { - ImGui::Text("This is the Broccoli tab!\nblah blah blah blah blah"); - ImGui::EndTabItem(); - } - if (ImGui::BeginTabItem("Cucumber")) - { - ImGui::Text("This is the Cucumber tab!\nblah blah blah blah blah"); - ImGui::EndTabItem(); - } - ImGui::EndTabBar(); - } - ImGui::Separator(); - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Tabs/Advanced & Close Button"); - if (ImGui::TreeNode("Advanced & Close Button")) - { - // Expose a couple of the available flags. In most cases you may just call BeginTabBar() with no flags (0). - static ImGuiTabBarFlags tab_bar_flags = ImGuiTabBarFlags_Reorderable; - ImGui::CheckboxFlags("ImGuiTabBarFlags_Reorderable", &tab_bar_flags, ImGuiTabBarFlags_Reorderable); - ImGui::CheckboxFlags("ImGuiTabBarFlags_AutoSelectNewTabs", &tab_bar_flags, ImGuiTabBarFlags_AutoSelectNewTabs); - ImGui::CheckboxFlags("ImGuiTabBarFlags_TabListPopupButton", &tab_bar_flags, ImGuiTabBarFlags_TabListPopupButton); - ImGui::CheckboxFlags("ImGuiTabBarFlags_NoCloseWithMiddleMouseButton", &tab_bar_flags, ImGuiTabBarFlags_NoCloseWithMiddleMouseButton); - if ((tab_bar_flags & ImGuiTabBarFlags_FittingPolicyMask_) == 0) - tab_bar_flags |= ImGuiTabBarFlags_FittingPolicyDefault_; - if (ImGui::CheckboxFlags("ImGuiTabBarFlags_FittingPolicyResizeDown", &tab_bar_flags, ImGuiTabBarFlags_FittingPolicyResizeDown)) - tab_bar_flags &= ~(ImGuiTabBarFlags_FittingPolicyMask_ ^ ImGuiTabBarFlags_FittingPolicyResizeDown); - if (ImGui::CheckboxFlags("ImGuiTabBarFlags_FittingPolicyScroll", &tab_bar_flags, ImGuiTabBarFlags_FittingPolicyScroll)) - tab_bar_flags &= ~(ImGuiTabBarFlags_FittingPolicyMask_ ^ ImGuiTabBarFlags_FittingPolicyScroll); - - // Tab Bar - const char* names[4] = { "Artichoke", "Beetroot", "Celery", "Daikon" }; - static bool opened[4] = { true, true, true, true }; // Persistent user state - for (int n = 0; n < IM_ARRAYSIZE(opened); n++) - { - if (n > 0) { ImGui::SameLine(); } - ImGui::Checkbox(names[n], &opened[n]); - } - - // Passing a bool* to BeginTabItem() is similar to passing one to Begin(): - // the underlying bool will be set to false when the tab is closed. - if (ImGui::BeginTabBar("MyTabBar", tab_bar_flags)) - { - for (int n = 0; n < IM_ARRAYSIZE(opened); n++) - if (opened[n] && ImGui::BeginTabItem(names[n], &opened[n], ImGuiTabItemFlags_None)) - { - ImGui::Text("This is the %s tab!", names[n]); - if (n & 1) - ImGui::Text("I am an odd tab."); - ImGui::EndTabItem(); - } - ImGui::EndTabBar(); - } - ImGui::Separator(); - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Tabs/TabItemButton & Leading-Trailing flags"); - if (ImGui::TreeNode("TabItemButton & Leading/Trailing flags")) - { - static ImVector active_tabs; - static int next_tab_id = 0; - if (next_tab_id == 0) // Initialize with some default tabs - for (int i = 0; i < 3; i++) - active_tabs.push_back(next_tab_id++); - - // TabItemButton() and Leading/Trailing flags are distinct features which we will demo together. - // (It is possible to submit regular tabs with Leading/Trailing flags, or TabItemButton tabs without Leading/Trailing flags... - // but they tend to make more sense together) - static bool show_leading_button = true; - static bool show_trailing_button = true; - ImGui::Checkbox("Show Leading TabItemButton()", &show_leading_button); - ImGui::Checkbox("Show Trailing TabItemButton()", &show_trailing_button); - - // Expose some other flags which are useful to showcase how they interact with Leading/Trailing tabs - static ImGuiTabBarFlags tab_bar_flags = ImGuiTabBarFlags_AutoSelectNewTabs | ImGuiTabBarFlags_Reorderable | ImGuiTabBarFlags_FittingPolicyResizeDown; - ImGui::CheckboxFlags("ImGuiTabBarFlags_TabListPopupButton", &tab_bar_flags, ImGuiTabBarFlags_TabListPopupButton); - if (ImGui::CheckboxFlags("ImGuiTabBarFlags_FittingPolicyResizeDown", &tab_bar_flags, ImGuiTabBarFlags_FittingPolicyResizeDown)) - tab_bar_flags &= ~(ImGuiTabBarFlags_FittingPolicyMask_ ^ ImGuiTabBarFlags_FittingPolicyResizeDown); - if (ImGui::CheckboxFlags("ImGuiTabBarFlags_FittingPolicyScroll", &tab_bar_flags, ImGuiTabBarFlags_FittingPolicyScroll)) - tab_bar_flags &= ~(ImGuiTabBarFlags_FittingPolicyMask_ ^ ImGuiTabBarFlags_FittingPolicyScroll); - - if (ImGui::BeginTabBar("MyTabBar", tab_bar_flags)) - { - // Demo a Leading TabItemButton(): click the "?" button to open a menu - if (show_leading_button) - if (ImGui::TabItemButton("?", ImGuiTabItemFlags_Leading | ImGuiTabItemFlags_NoTooltip)) - ImGui::OpenPopup("MyHelpMenu"); - if (ImGui::BeginPopup("MyHelpMenu")) - { - ImGui::Selectable("Hello!"); - ImGui::EndPopup(); - } - - // Demo Trailing Tabs: click the "+" button to add a new tab (in your app you may want to use a font icon instead of the "+") - // Note that we submit it before the regular tabs, but because of the ImGuiTabItemFlags_Trailing flag it will always appear at the end. - if (show_trailing_button) - if (ImGui::TabItemButton("+", ImGuiTabItemFlags_Trailing | ImGuiTabItemFlags_NoTooltip)) - active_tabs.push_back(next_tab_id++); // Add new tab - - // Submit our regular tabs - for (int n = 0; n < active_tabs.Size; ) - { - bool open = true; - char name[16]; - snprintf(name, IM_ARRAYSIZE(name), "%04d", active_tabs[n]); - if (ImGui::BeginTabItem(name, &open, ImGuiTabItemFlags_None)) - { - ImGui::Text("This is the %s tab!", name); - ImGui::EndTabItem(); - } - - if (!open) - active_tabs.erase(active_tabs.Data + n); - else - n++; - } - - ImGui::EndTabBar(); - } - ImGui::Separator(); - ImGui::TreePop(); - } - ImGui::TreePop(); - } - - // Plot/Graph widgets are not very good. - // Consider using a third-party library such as ImPlot: https://github.com/epezent/implot - // (see others https://github.com/ocornut/imgui/wiki/Useful-Extensions) - IMGUI_DEMO_MARKER("Widgets/Plotting"); - if (ImGui::TreeNode("Plotting")) - { - static bool animate = true; - ImGui::Checkbox("Animate", &animate); - - // Plot as lines and plot as histogram - IMGUI_DEMO_MARKER("Widgets/Plotting/PlotLines, PlotHistogram"); - static float arr[] = { 0.6f, 0.1f, 1.0f, 0.5f, 0.92f, 0.1f, 0.2f }; - ImGui::PlotLines("Frame Times", arr, IM_ARRAYSIZE(arr)); - ImGui::PlotHistogram("Histogram", arr, IM_ARRAYSIZE(arr), 0, NULL, 0.0f, 1.0f, ImVec2(0, 80.0f)); - - // Fill an array of contiguous float values to plot - // Tip: If your float aren't contiguous but part of a structure, you can pass a pointer to your first float - // and the sizeof() of your structure in the "stride" parameter. - static float values[90] = {}; - static int values_offset = 0; - static double refresh_time = 0.0; - if (!animate || refresh_time == 0.0) - refresh_time = ImGui::GetTime(); - while (refresh_time < ImGui::GetTime()) // Create data at fixed 60 Hz rate for the demo - { - static float phase = 0.0f; - values[values_offset] = cosf(phase); - values_offset = (values_offset + 1) % IM_ARRAYSIZE(values); - phase += 0.10f * values_offset; - refresh_time += 1.0f / 60.0f; - } - - // Plots can display overlay texts - // (in this example, we will display an average value) - { - float average = 0.0f; - for (int n = 0; n < IM_ARRAYSIZE(values); n++) - average += values[n]; - average /= (float)IM_ARRAYSIZE(values); - char overlay[32]; - sprintf(overlay, "avg %f", average); - ImGui::PlotLines("Lines", values, IM_ARRAYSIZE(values), values_offset, overlay, -1.0f, 1.0f, ImVec2(0, 80.0f)); - } - - // Use functions to generate output - // FIXME: This is actually VERY awkward because current plot API only pass in indices. - // We probably want an API passing floats and user provide sample rate/count. - struct Funcs - { - static float Sin(void*, int i) { return sinf(i * 0.1f); } - static float Saw(void*, int i) { return (i & 1) ? 1.0f : -1.0f; } - }; - static int func_type = 0, display_count = 70; - ImGui::SeparatorText("Functions"); - ImGui::SetNextItemWidth(ImGui::GetFontSize() * 8); - ImGui::Combo("func", &func_type, "Sin\0Saw\0"); - ImGui::SameLine(); - ImGui::SliderInt("Sample count", &display_count, 1, 400); - float (*func)(void*, int) = (func_type == 0) ? Funcs::Sin : Funcs::Saw; - ImGui::PlotLines("Lines", func, NULL, display_count, 0, NULL, -1.0f, 1.0f, ImVec2(0, 80)); - ImGui::PlotHistogram("Histogram", func, NULL, display_count, 0, NULL, -1.0f, 1.0f, ImVec2(0, 80)); - ImGui::Separator(); - - // Animate a simple progress bar - IMGUI_DEMO_MARKER("Widgets/Plotting/ProgressBar"); - static float progress = 0.0f, progress_dir = 1.0f; - if (animate) - { - progress += progress_dir * 0.4f * ImGui::GetIO().DeltaTime; - if (progress >= +1.1f) { progress = +1.1f; progress_dir *= -1.0f; } - if (progress <= -0.1f) { progress = -0.1f; progress_dir *= -1.0f; } - } - - // Typically we would use ImVec2(-1.0f,0.0f) or ImVec2(-FLT_MIN,0.0f) to use all available width, - // or ImVec2(width,0.0f) for a specified width. ImVec2(0.0f,0.0f) uses ItemWidth. - ImGui::ProgressBar(progress, ImVec2(0.0f, 0.0f)); - ImGui::SameLine(0.0f, ImGui::GetStyle().ItemInnerSpacing.x); - ImGui::Text("Progress Bar"); - - float progress_saturated = IM_CLAMP(progress, 0.0f, 1.0f); - char buf[32]; - sprintf(buf, "%d/%d", (int)(progress_saturated * 1753), 1753); - ImGui::ProgressBar(progress, ImVec2(0.f, 0.f), buf); - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Color"); - if (ImGui::TreeNode("Color/Picker Widgets")) - { - static ImVec4 color = ImVec4(114.0f / 255.0f, 144.0f / 255.0f, 154.0f / 255.0f, 200.0f / 255.0f); - - static bool alpha_preview = true; - static bool alpha_half_preview = false; - static bool drag_and_drop = true; - static bool options_menu = true; - static bool hdr = false; - ImGui::SeparatorText("Options"); - ImGui::Checkbox("With Alpha Preview", &alpha_preview); - ImGui::Checkbox("With Half Alpha Preview", &alpha_half_preview); - ImGui::Checkbox("With Drag and Drop", &drag_and_drop); - ImGui::Checkbox("With Options Menu", &options_menu); ImGui::SameLine(); HelpMarker("Right-click on the individual color widget to show options."); - ImGui::Checkbox("With HDR", &hdr); ImGui::SameLine(); HelpMarker("Currently all this does is to lift the 0..1 limits on dragging widgets."); - ImGuiColorEditFlags misc_flags = (hdr ? ImGuiColorEditFlags_HDR : 0) | (drag_and_drop ? 0 : ImGuiColorEditFlags_NoDragDrop) | (alpha_half_preview ? ImGuiColorEditFlags_AlphaPreviewHalf : (alpha_preview ? ImGuiColorEditFlags_AlphaPreview : 0)) | (options_menu ? 0 : ImGuiColorEditFlags_NoOptions); - - IMGUI_DEMO_MARKER("Widgets/Color/ColorEdit"); - ImGui::SeparatorText("Inline color editor"); - ImGui::Text("Color widget:"); - ImGui::SameLine(); HelpMarker( - "Click on the color square to open a color picker.\n" - "CTRL+click on individual component to input value.\n"); - ImGui::ColorEdit3("MyColor##1", (float*)&color, misc_flags); - - IMGUI_DEMO_MARKER("Widgets/Color/ColorEdit (HSV, with Alpha)"); - ImGui::Text("Color widget HSV with Alpha:"); - ImGui::ColorEdit4("MyColor##2", (float*)&color, ImGuiColorEditFlags_DisplayHSV | misc_flags); - - IMGUI_DEMO_MARKER("Widgets/Color/ColorEdit (float display)"); - ImGui::Text("Color widget with Float Display:"); - ImGui::ColorEdit4("MyColor##2f", (float*)&color, ImGuiColorEditFlags_Float | misc_flags); - - IMGUI_DEMO_MARKER("Widgets/Color/ColorButton (with Picker)"); - ImGui::Text("Color button with Picker:"); - ImGui::SameLine(); HelpMarker( - "With the ImGuiColorEditFlags_NoInputs flag you can hide all the slider/text inputs.\n" - "With the ImGuiColorEditFlags_NoLabel flag you can pass a non-empty label which will only " - "be used for the tooltip and picker popup."); - ImGui::ColorEdit4("MyColor##3", (float*)&color, ImGuiColorEditFlags_NoInputs | ImGuiColorEditFlags_NoLabel | misc_flags); - - IMGUI_DEMO_MARKER("Widgets/Color/ColorButton (with custom Picker popup)"); - ImGui::Text("Color button with Custom Picker Popup:"); - - // Generate a default palette. The palette will persist and can be edited. - static bool saved_palette_init = true; - static ImVec4 saved_palette[32] = {}; - if (saved_palette_init) - { - for (int n = 0; n < IM_ARRAYSIZE(saved_palette); n++) - { - ImGui::ColorConvertHSVtoRGB(n / 31.0f, 0.8f, 0.8f, - saved_palette[n].x, saved_palette[n].y, saved_palette[n].z); - saved_palette[n].w = 1.0f; // Alpha - } - saved_palette_init = false; - } - - static ImVec4 backup_color; - bool open_popup = ImGui::ColorButton("MyColor##3b", color, misc_flags); - ImGui::SameLine(0, ImGui::GetStyle().ItemInnerSpacing.x); - open_popup |= ImGui::Button("Palette"); - if (open_popup) - { - ImGui::OpenPopup("mypicker"); - backup_color = color; - } - if (ImGui::BeginPopup("mypicker")) - { - ImGui::Text("MY CUSTOM COLOR PICKER WITH AN AMAZING PALETTE!"); - ImGui::Separator(); - ImGui::ColorPicker4("##picker", (float*)&color, misc_flags | ImGuiColorEditFlags_NoSidePreview | ImGuiColorEditFlags_NoSmallPreview); - ImGui::SameLine(); - - ImGui::BeginGroup(); // Lock X position - ImGui::Text("Current"); - ImGui::ColorButton("##current", color, ImGuiColorEditFlags_NoPicker | ImGuiColorEditFlags_AlphaPreviewHalf, ImVec2(60, 40)); - ImGui::Text("Previous"); - if (ImGui::ColorButton("##previous", backup_color, ImGuiColorEditFlags_NoPicker | ImGuiColorEditFlags_AlphaPreviewHalf, ImVec2(60, 40))) - color = backup_color; - ImGui::Separator(); - ImGui::Text("Palette"); - for (int n = 0; n < IM_ARRAYSIZE(saved_palette); n++) - { - ImGui::PushID(n); - if ((n % 8) != 0) - ImGui::SameLine(0.0f, ImGui::GetStyle().ItemSpacing.y); - - ImGuiColorEditFlags palette_button_flags = ImGuiColorEditFlags_NoAlpha | ImGuiColorEditFlags_NoPicker | ImGuiColorEditFlags_NoTooltip; - if (ImGui::ColorButton("##palette", saved_palette[n], palette_button_flags, ImVec2(20, 20))) - color = ImVec4(saved_palette[n].x, saved_palette[n].y, saved_palette[n].z, color.w); // Preserve alpha! - - // Allow user to drop colors into each palette entry. Note that ColorButton() is already a - // drag source by default, unless specifying the ImGuiColorEditFlags_NoDragDrop flag. - if (ImGui::BeginDragDropTarget()) - { - if (const ImGuiPayload* payload = ImGui::AcceptDragDropPayload(IMGUI_PAYLOAD_TYPE_COLOR_3F)) - memcpy((float*)&saved_palette[n], payload->Data, sizeof(float) * 3); - if (const ImGuiPayload* payload = ImGui::AcceptDragDropPayload(IMGUI_PAYLOAD_TYPE_COLOR_4F)) - memcpy((float*)&saved_palette[n], payload->Data, sizeof(float) * 4); - ImGui::EndDragDropTarget(); - } - - ImGui::PopID(); - } - ImGui::EndGroup(); - ImGui::EndPopup(); - } - - IMGUI_DEMO_MARKER("Widgets/Color/ColorButton (simple)"); - ImGui::Text("Color button only:"); - static bool no_border = false; - ImGui::Checkbox("ImGuiColorEditFlags_NoBorder", &no_border); - ImGui::ColorButton("MyColor##3c", *(ImVec4*)&color, misc_flags | (no_border ? ImGuiColorEditFlags_NoBorder : 0), ImVec2(80, 80)); - - IMGUI_DEMO_MARKER("Widgets/Color/ColorPicker"); - ImGui::SeparatorText("Color picker"); - static bool alpha = true; - static bool alpha_bar = true; - static bool side_preview = true; - static bool ref_color = false; - static ImVec4 ref_color_v(1.0f, 0.0f, 1.0f, 0.5f); - static int display_mode = 0; - static int picker_mode = 0; - ImGui::Checkbox("With Alpha", &alpha); - ImGui::Checkbox("With Alpha Bar", &alpha_bar); - ImGui::Checkbox("With Side Preview", &side_preview); - if (side_preview) - { - ImGui::SameLine(); - ImGui::Checkbox("With Ref Color", &ref_color); - if (ref_color) - { - ImGui::SameLine(); - ImGui::ColorEdit4("##RefColor", &ref_color_v.x, ImGuiColorEditFlags_NoInputs | misc_flags); - } - } - ImGui::Combo("Display Mode", &display_mode, "Auto/Current\0None\0RGB Only\0HSV Only\0Hex Only\0"); - ImGui::SameLine(); HelpMarker( - "ColorEdit defaults to displaying RGB inputs if you don't specify a display mode, " - "but the user can change it with a right-click on those inputs.\n\nColorPicker defaults to displaying RGB+HSV+Hex " - "if you don't specify a display mode.\n\nYou can change the defaults using SetColorEditOptions()."); - ImGui::SameLine(); HelpMarker("When not specified explicitly (Auto/Current mode), user can right-click the picker to change mode."); - ImGuiColorEditFlags flags = misc_flags; - if (!alpha) flags |= ImGuiColorEditFlags_NoAlpha; // This is by default if you call ColorPicker3() instead of ColorPicker4() - if (alpha_bar) flags |= ImGuiColorEditFlags_AlphaBar; - if (!side_preview) flags |= ImGuiColorEditFlags_NoSidePreview; - if (picker_mode == 1) flags |= ImGuiColorEditFlags_PickerHueBar; - if (picker_mode == 2) flags |= ImGuiColorEditFlags_PickerHueWheel; - if (display_mode == 1) flags |= ImGuiColorEditFlags_NoInputs; // Disable all RGB/HSV/Hex displays - if (display_mode == 2) flags |= ImGuiColorEditFlags_DisplayRGB; // Override display mode - if (display_mode == 3) flags |= ImGuiColorEditFlags_DisplayHSV; - if (display_mode == 4) flags |= ImGuiColorEditFlags_DisplayHex; - ImGui::ColorPicker4("MyColor##4", (float*)&color, flags, ref_color ? &ref_color_v.x : NULL); - - ImGui::Text("Set defaults in code:"); - ImGui::SameLine(); HelpMarker( - "SetColorEditOptions() is designed to allow you to set boot-time default.\n" - "We don't have Push/Pop functions because you can force options on a per-widget basis if needed," - "and the user can change non-forced ones with the options menu.\nWe don't have a getter to avoid" - "encouraging you to persistently save values that aren't forward-compatible."); - if (ImGui::Button("Default: Uint8 + HSV + Hue Bar")) - ImGui::SetColorEditOptions(ImGuiColorEditFlags_Uint8 | ImGuiColorEditFlags_DisplayHSV | ImGuiColorEditFlags_PickerHueBar); - if (ImGui::Button("Default: Float + HDR + Hue Wheel")) - ImGui::SetColorEditOptions(ImGuiColorEditFlags_Float | ImGuiColorEditFlags_HDR | ImGuiColorEditFlags_PickerHueWheel); - - // Always both a small version of both types of pickers (to make it more visible in the demo to people who are skimming quickly through it) - ImGui::Text("Both types:"); - float w = (ImGui::GetContentRegionAvail().x - ImGui::GetStyle().ItemSpacing.y) * 0.40f; - ImGui::SetNextItemWidth(w); - ImGui::ColorPicker3("##MyColor##5", (float*)&color, ImGuiColorEditFlags_PickerHueBar | ImGuiColorEditFlags_NoSidePreview | ImGuiColorEditFlags_NoInputs | ImGuiColorEditFlags_NoAlpha); - ImGui::SameLine(); - ImGui::SetNextItemWidth(w); - ImGui::ColorPicker3("##MyColor##6", (float*)&color, ImGuiColorEditFlags_PickerHueWheel | ImGuiColorEditFlags_NoSidePreview | ImGuiColorEditFlags_NoInputs | ImGuiColorEditFlags_NoAlpha); - - // HSV encoded support (to avoid RGB<>HSV round trips and singularities when S==0 or V==0) - static ImVec4 color_hsv(0.23f, 1.0f, 1.0f, 1.0f); // Stored as HSV! - ImGui::Spacing(); - ImGui::Text("HSV encoded colors"); - ImGui::SameLine(); HelpMarker( - "By default, colors are given to ColorEdit and ColorPicker in RGB, but ImGuiColorEditFlags_InputHSV" - "allows you to store colors as HSV and pass them to ColorEdit and ColorPicker as HSV. This comes with the" - "added benefit that you can manipulate hue values with the picker even when saturation or value are zero."); - ImGui::Text("Color widget with InputHSV:"); - ImGui::ColorEdit4("HSV shown as RGB##1", (float*)&color_hsv, ImGuiColorEditFlags_DisplayRGB | ImGuiColorEditFlags_InputHSV | ImGuiColorEditFlags_Float); - ImGui::ColorEdit4("HSV shown as HSV##1", (float*)&color_hsv, ImGuiColorEditFlags_DisplayHSV | ImGuiColorEditFlags_InputHSV | ImGuiColorEditFlags_Float); - ImGui::DragFloat4("Raw HSV values", (float*)&color_hsv, 0.01f, 0.0f, 1.0f); - - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Drag and Slider Flags"); - if (ImGui::TreeNode("Drag/Slider Flags")) - { - // Demonstrate using advanced flags for DragXXX and SliderXXX functions. Note that the flags are the same! - static ImGuiSliderFlags flags = ImGuiSliderFlags_None; - ImGui::CheckboxFlags("ImGuiSliderFlags_AlwaysClamp", &flags, ImGuiSliderFlags_AlwaysClamp); - ImGui::SameLine(); HelpMarker("Always clamp value to min/max bounds (if any) when input manually with CTRL+Click."); - ImGui::CheckboxFlags("ImGuiSliderFlags_Logarithmic", &flags, ImGuiSliderFlags_Logarithmic); - ImGui::SameLine(); HelpMarker("Enable logarithmic editing (more precision for small values)."); - ImGui::CheckboxFlags("ImGuiSliderFlags_NoRoundToFormat", &flags, ImGuiSliderFlags_NoRoundToFormat); - ImGui::SameLine(); HelpMarker("Disable rounding underlying value to match precision of the format string (e.g. %.3f values are rounded to those 3 digits)."); - ImGui::CheckboxFlags("ImGuiSliderFlags_NoInput", &flags, ImGuiSliderFlags_NoInput); - ImGui::SameLine(); HelpMarker("Disable CTRL+Click or Enter key allowing to input text directly into the widget."); - - // Drags - static float drag_f = 0.5f; - static int drag_i = 50; - ImGui::Text("Underlying float value: %f", drag_f); - ImGui::DragFloat("DragFloat (0 -> 1)", &drag_f, 0.005f, 0.0f, 1.0f, "%.3f", flags); - ImGui::DragFloat("DragFloat (0 -> +inf)", &drag_f, 0.005f, 0.0f, FLT_MAX, "%.3f", flags); - ImGui::DragFloat("DragFloat (-inf -> 1)", &drag_f, 0.005f, -FLT_MAX, 1.0f, "%.3f", flags); - ImGui::DragFloat("DragFloat (-inf -> +inf)", &drag_f, 0.005f, -FLT_MAX, +FLT_MAX, "%.3f", flags); - ImGui::DragInt("DragInt (0 -> 100)", &drag_i, 0.5f, 0, 100, "%d", flags); - - // Sliders - static float slider_f = 0.5f; - static int slider_i = 50; - ImGui::Text("Underlying float value: %f", slider_f); - ImGui::SliderFloat("SliderFloat (0 -> 1)", &slider_f, 0.0f, 1.0f, "%.3f", flags); - ImGui::SliderInt("SliderInt (0 -> 100)", &slider_i, 0, 100, "%d", flags); - - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Range Widgets"); - if (ImGui::TreeNode("Range Widgets")) - { - static float begin = 10, end = 90; - static int begin_i = 100, end_i = 1000; - ImGui::DragFloatRange2("range float", &begin, &end, 0.25f, 0.0f, 100.0f, "Min: %.1f %%", "Max: %.1f %%", ImGuiSliderFlags_AlwaysClamp); - ImGui::DragIntRange2("range int", &begin_i, &end_i, 5, 0, 1000, "Min: %d units", "Max: %d units"); - ImGui::DragIntRange2("range int (no bounds)", &begin_i, &end_i, 5, 0, 0, "Min: %d units", "Max: %d units"); - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Data Types"); - if (ImGui::TreeNode("Data Types")) - { - // DragScalar/InputScalar/SliderScalar functions allow various data types - // - signed/unsigned - // - 8/16/32/64-bits - // - integer/float/double - // To avoid polluting the public API with all possible combinations, we use the ImGuiDataType enum - // to pass the type, and passing all arguments by pointer. - // This is the reason the test code below creates local variables to hold "zero" "one" etc. for each type. - // In practice, if you frequently use a given type that is not covered by the normal API entry points, - // you can wrap it yourself inside a 1 line function which can take typed argument as value instead of void*, - // and then pass their address to the generic function. For example: - // bool MySliderU64(const char *label, u64* value, u64 min = 0, u64 max = 0, const char* format = "%lld") - // { - // return SliderScalar(label, ImGuiDataType_U64, value, &min, &max, format); - // } - - // Setup limits (as helper variables so we can take their address, as explained above) - // Note: SliderScalar() functions have a maximum usable range of half the natural type maximum, hence the /2. - #ifndef LLONG_MIN - ImS64 LLONG_MIN = -9223372036854775807LL - 1; - ImS64 LLONG_MAX = 9223372036854775807LL; - ImU64 ULLONG_MAX = (2ULL * 9223372036854775807LL + 1); - #endif - const char s8_zero = 0, s8_one = 1, s8_fifty = 50, s8_min = -128, s8_max = 127; - const ImU8 u8_zero = 0, u8_one = 1, u8_fifty = 50, u8_min = 0, u8_max = 255; - const short s16_zero = 0, s16_one = 1, s16_fifty = 50, s16_min = -32768, s16_max = 32767; - const ImU16 u16_zero = 0, u16_one = 1, u16_fifty = 50, u16_min = 0, u16_max = 65535; - const ImS32 s32_zero = 0, s32_one = 1, s32_fifty = 50, s32_min = INT_MIN/2, s32_max = INT_MAX/2, s32_hi_a = INT_MAX/2 - 100, s32_hi_b = INT_MAX/2; - const ImU32 u32_zero = 0, u32_one = 1, u32_fifty = 50, u32_min = 0, u32_max = UINT_MAX/2, u32_hi_a = UINT_MAX/2 - 100, u32_hi_b = UINT_MAX/2; - const ImS64 s64_zero = 0, s64_one = 1, s64_fifty = 50, s64_min = LLONG_MIN/2, s64_max = LLONG_MAX/2, s64_hi_a = LLONG_MAX/2 - 100, s64_hi_b = LLONG_MAX/2; - const ImU64 u64_zero = 0, u64_one = 1, u64_fifty = 50, u64_min = 0, u64_max = ULLONG_MAX/2, u64_hi_a = ULLONG_MAX/2 - 100, u64_hi_b = ULLONG_MAX/2; - const float f32_zero = 0.f, f32_one = 1.f, f32_lo_a = -10000000000.0f, f32_hi_a = +10000000000.0f; - const double f64_zero = 0., f64_one = 1., f64_lo_a = -1000000000000000.0, f64_hi_a = +1000000000000000.0; - - // State - static char s8_v = 127; - static ImU8 u8_v = 255; - static short s16_v = 32767; - static ImU16 u16_v = 65535; - static ImS32 s32_v = -1; - static ImU32 u32_v = (ImU32)-1; - static ImS64 s64_v = -1; - static ImU64 u64_v = (ImU64)-1; - static float f32_v = 0.123f; - static double f64_v = 90000.01234567890123456789; - - const float drag_speed = 0.2f; - static bool drag_clamp = false; - IMGUI_DEMO_MARKER("Widgets/Data Types/Drags"); - ImGui::SeparatorText("Drags"); - ImGui::Checkbox("Clamp integers to 0..50", &drag_clamp); - ImGui::SameLine(); HelpMarker( - "As with every widget in dear imgui, we never modify values unless there is a user interaction.\n" - "You can override the clamping limits by using CTRL+Click to input a value."); - ImGui::DragScalar("drag s8", ImGuiDataType_S8, &s8_v, drag_speed, drag_clamp ? &s8_zero : NULL, drag_clamp ? &s8_fifty : NULL); - ImGui::DragScalar("drag u8", ImGuiDataType_U8, &u8_v, drag_speed, drag_clamp ? &u8_zero : NULL, drag_clamp ? &u8_fifty : NULL, "%u ms"); - ImGui::DragScalar("drag s16", ImGuiDataType_S16, &s16_v, drag_speed, drag_clamp ? &s16_zero : NULL, drag_clamp ? &s16_fifty : NULL); - ImGui::DragScalar("drag u16", ImGuiDataType_U16, &u16_v, drag_speed, drag_clamp ? &u16_zero : NULL, drag_clamp ? &u16_fifty : NULL, "%u ms"); - ImGui::DragScalar("drag s32", ImGuiDataType_S32, &s32_v, drag_speed, drag_clamp ? &s32_zero : NULL, drag_clamp ? &s32_fifty : NULL); - ImGui::DragScalar("drag s32 hex", ImGuiDataType_S32, &s32_v, drag_speed, drag_clamp ? &s32_zero : NULL, drag_clamp ? &s32_fifty : NULL, "0x%08X"); - ImGui::DragScalar("drag u32", ImGuiDataType_U32, &u32_v, drag_speed, drag_clamp ? &u32_zero : NULL, drag_clamp ? &u32_fifty : NULL, "%u ms"); - ImGui::DragScalar("drag s64", ImGuiDataType_S64, &s64_v, drag_speed, drag_clamp ? &s64_zero : NULL, drag_clamp ? &s64_fifty : NULL); - ImGui::DragScalar("drag u64", ImGuiDataType_U64, &u64_v, drag_speed, drag_clamp ? &u64_zero : NULL, drag_clamp ? &u64_fifty : NULL); - ImGui::DragScalar("drag float", ImGuiDataType_Float, &f32_v, 0.005f, &f32_zero, &f32_one, "%f"); - ImGui::DragScalar("drag float log", ImGuiDataType_Float, &f32_v, 0.005f, &f32_zero, &f32_one, "%f", ImGuiSliderFlags_Logarithmic); - ImGui::DragScalar("drag double", ImGuiDataType_Double, &f64_v, 0.0005f, &f64_zero, NULL, "%.10f grams"); - ImGui::DragScalar("drag double log",ImGuiDataType_Double, &f64_v, 0.0005f, &f64_zero, &f64_one, "0 < %.10f < 1", ImGuiSliderFlags_Logarithmic); - - IMGUI_DEMO_MARKER("Widgets/Data Types/Sliders"); - ImGui::SeparatorText("Sliders"); - ImGui::SliderScalar("slider s8 full", ImGuiDataType_S8, &s8_v, &s8_min, &s8_max, "%d"); - ImGui::SliderScalar("slider u8 full", ImGuiDataType_U8, &u8_v, &u8_min, &u8_max, "%u"); - ImGui::SliderScalar("slider s16 full", ImGuiDataType_S16, &s16_v, &s16_min, &s16_max, "%d"); - ImGui::SliderScalar("slider u16 full", ImGuiDataType_U16, &u16_v, &u16_min, &u16_max, "%u"); - ImGui::SliderScalar("slider s32 low", ImGuiDataType_S32, &s32_v, &s32_zero, &s32_fifty,"%d"); - ImGui::SliderScalar("slider s32 high", ImGuiDataType_S32, &s32_v, &s32_hi_a, &s32_hi_b, "%d"); - ImGui::SliderScalar("slider s32 full", ImGuiDataType_S32, &s32_v, &s32_min, &s32_max, "%d"); - ImGui::SliderScalar("slider s32 hex", ImGuiDataType_S32, &s32_v, &s32_zero, &s32_fifty, "0x%04X"); - ImGui::SliderScalar("slider u32 low", ImGuiDataType_U32, &u32_v, &u32_zero, &u32_fifty,"%u"); - ImGui::SliderScalar("slider u32 high", ImGuiDataType_U32, &u32_v, &u32_hi_a, &u32_hi_b, "%u"); - ImGui::SliderScalar("slider u32 full", ImGuiDataType_U32, &u32_v, &u32_min, &u32_max, "%u"); - ImGui::SliderScalar("slider s64 low", ImGuiDataType_S64, &s64_v, &s64_zero, &s64_fifty,"%" PRId64); - ImGui::SliderScalar("slider s64 high", ImGuiDataType_S64, &s64_v, &s64_hi_a, &s64_hi_b, "%" PRId64); - ImGui::SliderScalar("slider s64 full", ImGuiDataType_S64, &s64_v, &s64_min, &s64_max, "%" PRId64); - ImGui::SliderScalar("slider u64 low", ImGuiDataType_U64, &u64_v, &u64_zero, &u64_fifty,"%" PRIu64 " ms"); - ImGui::SliderScalar("slider u64 high", ImGuiDataType_U64, &u64_v, &u64_hi_a, &u64_hi_b, "%" PRIu64 " ms"); - ImGui::SliderScalar("slider u64 full", ImGuiDataType_U64, &u64_v, &u64_min, &u64_max, "%" PRIu64 " ms"); - ImGui::SliderScalar("slider float low", ImGuiDataType_Float, &f32_v, &f32_zero, &f32_one); - ImGui::SliderScalar("slider float low log", ImGuiDataType_Float, &f32_v, &f32_zero, &f32_one, "%.10f", ImGuiSliderFlags_Logarithmic); - ImGui::SliderScalar("slider float high", ImGuiDataType_Float, &f32_v, &f32_lo_a, &f32_hi_a, "%e"); - ImGui::SliderScalar("slider double low", ImGuiDataType_Double, &f64_v, &f64_zero, &f64_one, "%.10f grams"); - ImGui::SliderScalar("slider double low log",ImGuiDataType_Double, &f64_v, &f64_zero, &f64_one, "%.10f", ImGuiSliderFlags_Logarithmic); - ImGui::SliderScalar("slider double high", ImGuiDataType_Double, &f64_v, &f64_lo_a, &f64_hi_a, "%e grams"); - - ImGui::SeparatorText("Sliders (reverse)"); - ImGui::SliderScalar("slider s8 reverse", ImGuiDataType_S8, &s8_v, &s8_max, &s8_min, "%d"); - ImGui::SliderScalar("slider u8 reverse", ImGuiDataType_U8, &u8_v, &u8_max, &u8_min, "%u"); - ImGui::SliderScalar("slider s32 reverse", ImGuiDataType_S32, &s32_v, &s32_fifty, &s32_zero, "%d"); - ImGui::SliderScalar("slider u32 reverse", ImGuiDataType_U32, &u32_v, &u32_fifty, &u32_zero, "%u"); - ImGui::SliderScalar("slider s64 reverse", ImGuiDataType_S64, &s64_v, &s64_fifty, &s64_zero, "%" PRId64); - ImGui::SliderScalar("slider u64 reverse", ImGuiDataType_U64, &u64_v, &u64_fifty, &u64_zero, "%" PRIu64 " ms"); - - IMGUI_DEMO_MARKER("Widgets/Data Types/Inputs"); - static bool inputs_step = true; - ImGui::SeparatorText("Inputs"); - ImGui::Checkbox("Show step buttons", &inputs_step); - ImGui::InputScalar("input s8", ImGuiDataType_S8, &s8_v, inputs_step ? &s8_one : NULL, NULL, "%d"); - ImGui::InputScalar("input u8", ImGuiDataType_U8, &u8_v, inputs_step ? &u8_one : NULL, NULL, "%u"); - ImGui::InputScalar("input s16", ImGuiDataType_S16, &s16_v, inputs_step ? &s16_one : NULL, NULL, "%d"); - ImGui::InputScalar("input u16", ImGuiDataType_U16, &u16_v, inputs_step ? &u16_one : NULL, NULL, "%u"); - ImGui::InputScalar("input s32", ImGuiDataType_S32, &s32_v, inputs_step ? &s32_one : NULL, NULL, "%d"); - ImGui::InputScalar("input s32 hex", ImGuiDataType_S32, &s32_v, inputs_step ? &s32_one : NULL, NULL, "%04X"); - ImGui::InputScalar("input u32", ImGuiDataType_U32, &u32_v, inputs_step ? &u32_one : NULL, NULL, "%u"); - ImGui::InputScalar("input u32 hex", ImGuiDataType_U32, &u32_v, inputs_step ? &u32_one : NULL, NULL, "%08X"); - ImGui::InputScalar("input s64", ImGuiDataType_S64, &s64_v, inputs_step ? &s64_one : NULL); - ImGui::InputScalar("input u64", ImGuiDataType_U64, &u64_v, inputs_step ? &u64_one : NULL); - ImGui::InputScalar("input float", ImGuiDataType_Float, &f32_v, inputs_step ? &f32_one : NULL); - ImGui::InputScalar("input double", ImGuiDataType_Double, &f64_v, inputs_step ? &f64_one : NULL); - - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Multi-component Widgets"); - if (ImGui::TreeNode("Multi-component Widgets")) - { - static float vec4f[4] = { 0.10f, 0.20f, 0.30f, 0.44f }; - static int vec4i[4] = { 1, 5, 100, 255 }; - - ImGui::SeparatorText("2-wide"); - ImGui::InputFloat2("input float2", vec4f); - ImGui::DragFloat2("drag float2", vec4f, 0.01f, 0.0f, 1.0f); - ImGui::SliderFloat2("slider float2", vec4f, 0.0f, 1.0f); - ImGui::InputInt2("input int2", vec4i); - ImGui::DragInt2("drag int2", vec4i, 1, 0, 255); - ImGui::SliderInt2("slider int2", vec4i, 0, 255); - - ImGui::SeparatorText("3-wide"); - ImGui::InputFloat3("input float3", vec4f); - ImGui::DragFloat3("drag float3", vec4f, 0.01f, 0.0f, 1.0f); - ImGui::SliderFloat3("slider float3", vec4f, 0.0f, 1.0f); - ImGui::InputInt3("input int3", vec4i); - ImGui::DragInt3("drag int3", vec4i, 1, 0, 255); - ImGui::SliderInt3("slider int3", vec4i, 0, 255); - - ImGui::SeparatorText("4-wide"); - ImGui::InputFloat4("input float4", vec4f); - ImGui::DragFloat4("drag float4", vec4f, 0.01f, 0.0f, 1.0f); - ImGui::SliderFloat4("slider float4", vec4f, 0.0f, 1.0f); - ImGui::InputInt4("input int4", vec4i); - ImGui::DragInt4("drag int4", vec4i, 1, 0, 255); - ImGui::SliderInt4("slider int4", vec4i, 0, 255); - - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Vertical Sliders"); - if (ImGui::TreeNode("Vertical Sliders")) - { - const float spacing = 4; - ImGui::PushStyleVar(ImGuiStyleVar_ItemSpacing, ImVec2(spacing, spacing)); - - static int int_value = 0; - ImGui::VSliderInt("##int", ImVec2(18, 160), &int_value, 0, 5); - ImGui::SameLine(); - - static float values[7] = { 0.0f, 0.60f, 0.35f, 0.9f, 0.70f, 0.20f, 0.0f }; - ImGui::PushID("set1"); - for (int i = 0; i < 7; i++) - { - if (i > 0) ImGui::SameLine(); - ImGui::PushID(i); - ImGui::PushStyleColor(ImGuiCol_FrameBg, (ImVec4)ImColor::HSV(i / 7.0f, 0.5f, 0.5f)); - ImGui::PushStyleColor(ImGuiCol_FrameBgHovered, (ImVec4)ImColor::HSV(i / 7.0f, 0.6f, 0.5f)); - ImGui::PushStyleColor(ImGuiCol_FrameBgActive, (ImVec4)ImColor::HSV(i / 7.0f, 0.7f, 0.5f)); - ImGui::PushStyleColor(ImGuiCol_SliderGrab, (ImVec4)ImColor::HSV(i / 7.0f, 0.9f, 0.9f)); - ImGui::VSliderFloat("##v", ImVec2(18, 160), &values[i], 0.0f, 1.0f, ""); - if (ImGui::IsItemActive() || ImGui::IsItemHovered()) - ImGui::SetTooltip("%.3f", values[i]); - ImGui::PopStyleColor(4); - ImGui::PopID(); - } - ImGui::PopID(); - - ImGui::SameLine(); - ImGui::PushID("set2"); - static float values2[4] = { 0.20f, 0.80f, 0.40f, 0.25f }; - const int rows = 3; - const ImVec2 small_slider_size(18, (float)(int)((160.0f - (rows - 1) * spacing) / rows)); - for (int nx = 0; nx < 4; nx++) - { - if (nx > 0) ImGui::SameLine(); - ImGui::BeginGroup(); - for (int ny = 0; ny < rows; ny++) - { - ImGui::PushID(nx * rows + ny); - ImGui::VSliderFloat("##v", small_slider_size, &values2[nx], 0.0f, 1.0f, ""); - if (ImGui::IsItemActive() || ImGui::IsItemHovered()) - ImGui::SetTooltip("%.3f", values2[nx]); - ImGui::PopID(); - } - ImGui::EndGroup(); - } - ImGui::PopID(); - - ImGui::SameLine(); - ImGui::PushID("set3"); - for (int i = 0; i < 4; i++) - { - if (i > 0) ImGui::SameLine(); - ImGui::PushID(i); - ImGui::PushStyleVar(ImGuiStyleVar_GrabMinSize, 40); - ImGui::VSliderFloat("##v", ImVec2(40, 160), &values[i], 0.0f, 1.0f, "%.2f\nsec"); - ImGui::PopStyleVar(); - ImGui::PopID(); - } - ImGui::PopID(); - ImGui::PopStyleVar(); - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Drag and drop"); - if (ImGui::TreeNode("Drag and Drop")) - { - IMGUI_DEMO_MARKER("Widgets/Drag and drop/Standard widgets"); - if (ImGui::TreeNode("Drag and drop in standard widgets")) - { - // ColorEdit widgets automatically act as drag source and drag target. - // They are using standardized payload strings IMGUI_PAYLOAD_TYPE_COLOR_3F and IMGUI_PAYLOAD_TYPE_COLOR_4F - // to allow your own widgets to use colors in their drag and drop interaction. - // Also see 'Demo->Widgets->Color/Picker Widgets->Palette' demo. - HelpMarker("You can drag from the color squares."); - static float col1[3] = { 1.0f, 0.0f, 0.2f }; - static float col2[4] = { 0.4f, 0.7f, 0.0f, 0.5f }; - ImGui::ColorEdit3("color 1", col1); - ImGui::ColorEdit4("color 2", col2); - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Drag and drop/Copy-swap items"); - if (ImGui::TreeNode("Drag and drop to copy/swap items")) - { - enum Mode - { - Mode_Copy, - Mode_Move, - Mode_Swap - }; - static int mode = 0; - if (ImGui::RadioButton("Copy", mode == Mode_Copy)) { mode = Mode_Copy; } ImGui::SameLine(); - if (ImGui::RadioButton("Move", mode == Mode_Move)) { mode = Mode_Move; } ImGui::SameLine(); - if (ImGui::RadioButton("Swap", mode == Mode_Swap)) { mode = Mode_Swap; } - static const char* names[9] = - { - "Bobby", "Beatrice", "Betty", - "Brianna", "Barry", "Bernard", - "Bibi", "Blaine", "Bryn" - }; - for (int n = 0; n < IM_ARRAYSIZE(names); n++) - { - ImGui::PushID(n); - if ((n % 3) != 0) - ImGui::SameLine(); - ImGui::Button(names[n], ImVec2(60, 60)); - - // Our buttons are both drag sources and drag targets here! - if (ImGui::BeginDragDropSource(ImGuiDragDropFlags_None)) - { - // Set payload to carry the index of our item (could be anything) - ImGui::SetDragDropPayload("DND_DEMO_CELL", &n, sizeof(int)); - - // Display preview (could be anything, e.g. when dragging an image we could decide to display - // the filename and a small preview of the image, etc.) - if (mode == Mode_Copy) { ImGui::Text("Copy %s", names[n]); } - if (mode == Mode_Move) { ImGui::Text("Move %s", names[n]); } - if (mode == Mode_Swap) { ImGui::Text("Swap %s", names[n]); } - ImGui::EndDragDropSource(); - } - if (ImGui::BeginDragDropTarget()) - { - if (const ImGuiPayload* payload = ImGui::AcceptDragDropPayload("DND_DEMO_CELL")) - { - IM_ASSERT(payload->DataSize == sizeof(int)); - int payload_n = *(const int*)payload->Data; - if (mode == Mode_Copy) - { - names[n] = names[payload_n]; - } - if (mode == Mode_Move) - { - names[n] = names[payload_n]; - names[payload_n] = ""; - } - if (mode == Mode_Swap) - { - const char* tmp = names[n]; - names[n] = names[payload_n]; - names[payload_n] = tmp; - } - } - ImGui::EndDragDropTarget(); - } - ImGui::PopID(); - } - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Drag and Drop/Drag to reorder items (simple)"); - if (ImGui::TreeNode("Drag to reorder items (simple)")) - { - // Simple reordering - HelpMarker( - "We don't use the drag and drop api at all here! " - "Instead we query when the item is held but not hovered, and order items accordingly."); - static const char* item_names[] = { "Item One", "Item Two", "Item Three", "Item Four", "Item Five" }; - for (int n = 0; n < IM_ARRAYSIZE(item_names); n++) - { - const char* item = item_names[n]; - ImGui::Selectable(item); - - if (ImGui::IsItemActive() && !ImGui::IsItemHovered()) - { - int n_next = n + (ImGui::GetMouseDragDelta(0).y < 0.f ? -1 : 1); - if (n_next >= 0 && n_next < IM_ARRAYSIZE(item_names)) - { - item_names[n] = item_names[n_next]; - item_names[n_next] = item; - ImGui::ResetMouseDragDelta(); - } - } - } - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Drag and Drop/Tooltip at target location"); - if (ImGui::TreeNode("Tooltip at target location")) - { - for (int n = 0; n < 2; n++) - { - // Drop targets - ImGui::Button(n ? "drop here##1" : "drop here##0"); - if (ImGui::BeginDragDropTarget()) - { - ImGuiDragDropFlags drop_target_flags = ImGuiDragDropFlags_AcceptBeforeDelivery | ImGuiDragDropFlags_AcceptNoPreviewTooltip; - if (const ImGuiPayload* payload = ImGui::AcceptDragDropPayload(IMGUI_PAYLOAD_TYPE_COLOR_4F, drop_target_flags)) - { - IM_UNUSED(payload); - ImGui::SetMouseCursor(ImGuiMouseCursor_NotAllowed); - ImGui::BeginTooltip(); - ImGui::Text("Cannot drop here!"); - ImGui::EndTooltip(); - } - ImGui::EndDragDropTarget(); - } - - // Drop source - static ImVec4 col4 = { 1.0f, 0.0f, 0.2f, 1.0f }; - if (n == 0) - ImGui::ColorButton("drag me", col4); - - } - ImGui::TreePop(); - } - - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Querying Item Status (Edited,Active,Hovered etc.)"); - if (ImGui::TreeNode("Querying Item Status (Edited/Active/Hovered etc.)")) - { - // Select an item type - const char* item_names[] = - { - "Text", "Button", "Button (w/ repeat)", "Checkbox", "SliderFloat", "InputText", "InputTextMultiline", "InputFloat", - "InputFloat3", "ColorEdit4", "Selectable", "MenuItem", "TreeNode", "TreeNode (w/ double-click)", "Combo", "ListBox" - }; - static int item_type = 4; - static bool item_disabled = false; - ImGui::Combo("Item Type", &item_type, item_names, IM_ARRAYSIZE(item_names), IM_ARRAYSIZE(item_names)); - ImGui::SameLine(); - HelpMarker("Testing how various types of items are interacting with the IsItemXXX functions. Note that the bool return value of most ImGui function is generally equivalent to calling ImGui::IsItemHovered()."); - ImGui::Checkbox("Item Disabled", &item_disabled); - - // Submit selected items so we can query their status in the code following it. - bool ret = false; - static bool b = false; - static float col4f[4] = { 1.0f, 0.5, 0.0f, 1.0f }; - static char str[16] = {}; - if (item_disabled) - ImGui::BeginDisabled(true); - if (item_type == 0) { ImGui::Text("ITEM: Text"); } // Testing text items with no identifier/interaction - if (item_type == 1) { ret = ImGui::Button("ITEM: Button"); } // Testing button - if (item_type == 2) { ImGui::PushButtonRepeat(true); ret = ImGui::Button("ITEM: Button"); ImGui::PopButtonRepeat(); } // Testing button (with repeater) - if (item_type == 3) { ret = ImGui::Checkbox("ITEM: Checkbox", &b); } // Testing checkbox - if (item_type == 4) { ret = ImGui::SliderFloat("ITEM: SliderFloat", &col4f[0], 0.0f, 1.0f); } // Testing basic item - if (item_type == 5) { ret = ImGui::InputText("ITEM: InputText", &str[0], IM_ARRAYSIZE(str)); } // Testing input text (which handles tabbing) - if (item_type == 6) { ret = ImGui::InputTextMultiline("ITEM: InputTextMultiline", &str[0], IM_ARRAYSIZE(str)); } // Testing input text (which uses a child window) - if (item_type == 7) { ret = ImGui::InputFloat("ITEM: InputFloat", col4f, 1.0f); } // Testing +/- buttons on scalar input - if (item_type == 8) { ret = ImGui::InputFloat3("ITEM: InputFloat3", col4f); } // Testing multi-component items (IsItemXXX flags are reported merged) - if (item_type == 9) { ret = ImGui::ColorEdit4("ITEM: ColorEdit4", col4f); } // Testing multi-component items (IsItemXXX flags are reported merged) - if (item_type == 10){ ret = ImGui::Selectable("ITEM: Selectable"); } // Testing selectable item - if (item_type == 11){ ret = ImGui::MenuItem("ITEM: MenuItem"); } // Testing menu item (they use ImGuiButtonFlags_PressedOnRelease button policy) - if (item_type == 12){ ret = ImGui::TreeNode("ITEM: TreeNode"); if (ret) ImGui::TreePop(); } // Testing tree node - if (item_type == 13){ ret = ImGui::TreeNodeEx("ITEM: TreeNode w/ ImGuiTreeNodeFlags_OpenOnDoubleClick", ImGuiTreeNodeFlags_OpenOnDoubleClick | ImGuiTreeNodeFlags_NoTreePushOnOpen); } // Testing tree node with ImGuiButtonFlags_PressedOnDoubleClick button policy. - if (item_type == 14){ const char* items[] = { "Apple", "Banana", "Cherry", "Kiwi" }; static int current = 1; ret = ImGui::Combo("ITEM: Combo", ¤t, items, IM_ARRAYSIZE(items)); } - if (item_type == 15){ const char* items[] = { "Apple", "Banana", "Cherry", "Kiwi" }; static int current = 1; ret = ImGui::ListBox("ITEM: ListBox", ¤t, items, IM_ARRAYSIZE(items), IM_ARRAYSIZE(items)); } - - bool hovered_delay_none = ImGui::IsItemHovered(); - bool hovered_delay_stationary = ImGui::IsItemHovered(ImGuiHoveredFlags_Stationary); - bool hovered_delay_short = ImGui::IsItemHovered(ImGuiHoveredFlags_DelayShort); - bool hovered_delay_normal = ImGui::IsItemHovered(ImGuiHoveredFlags_DelayNormal); - bool hovered_delay_tooltip = ImGui::IsItemHovered(ImGuiHoveredFlags_ForTooltip); // = Normal + Stationary - - // Display the values of IsItemHovered() and other common item state functions. - // Note that the ImGuiHoveredFlags_XXX flags can be combined. - // Because BulletText is an item itself and that would affect the output of IsItemXXX functions, - // we query every state in a single call to avoid storing them and to simplify the code. - ImGui::BulletText( - "Return value = %d\n" - "IsItemFocused() = %d\n" - "IsItemHovered() = %d\n" - "IsItemHovered(_AllowWhenBlockedByPopup) = %d\n" - "IsItemHovered(_AllowWhenBlockedByActiveItem) = %d\n" - "IsItemHovered(_AllowWhenOverlappedByItem) = %d\n" - "IsItemHovered(_AllowWhenOverlappedByWindow) = %d\n" - "IsItemHovered(_AllowWhenDisabled) = %d\n" - "IsItemHovered(_RectOnly) = %d\n" - "IsItemActive() = %d\n" - "IsItemEdited() = %d\n" - "IsItemActivated() = %d\n" - "IsItemDeactivated() = %d\n" - "IsItemDeactivatedAfterEdit() = %d\n" - "IsItemVisible() = %d\n" - "IsItemClicked() = %d\n" - "IsItemToggledOpen() = %d\n" - "GetItemRectMin() = (%.1f, %.1f)\n" - "GetItemRectMax() = (%.1f, %.1f)\n" - "GetItemRectSize() = (%.1f, %.1f)", - ret, - ImGui::IsItemFocused(), - ImGui::IsItemHovered(), - ImGui::IsItemHovered(ImGuiHoveredFlags_AllowWhenBlockedByPopup), - ImGui::IsItemHovered(ImGuiHoveredFlags_AllowWhenBlockedByActiveItem), - ImGui::IsItemHovered(ImGuiHoveredFlags_AllowWhenOverlappedByItem), - ImGui::IsItemHovered(ImGuiHoveredFlags_AllowWhenOverlappedByWindow), - ImGui::IsItemHovered(ImGuiHoveredFlags_AllowWhenDisabled), - ImGui::IsItemHovered(ImGuiHoveredFlags_RectOnly), - ImGui::IsItemActive(), - ImGui::IsItemEdited(), - ImGui::IsItemActivated(), - ImGui::IsItemDeactivated(), - ImGui::IsItemDeactivatedAfterEdit(), - ImGui::IsItemVisible(), - ImGui::IsItemClicked(), - ImGui::IsItemToggledOpen(), - ImGui::GetItemRectMin().x, ImGui::GetItemRectMin().y, - ImGui::GetItemRectMax().x, ImGui::GetItemRectMax().y, - ImGui::GetItemRectSize().x, ImGui::GetItemRectSize().y - ); - ImGui::BulletText( - "with Hovering Delay or Stationary test:\n" - "IsItemHovered() = = %d\n" - "IsItemHovered(_Stationary) = %d\n" - "IsItemHovered(_DelayShort) = %d\n" - "IsItemHovered(_DelayNormal) = %d\n" - "IsItemHovered(_Tooltip) = %d", - hovered_delay_none, hovered_delay_stationary, hovered_delay_short, hovered_delay_normal, hovered_delay_tooltip); - - if (item_disabled) - ImGui::EndDisabled(); - - char buf[1] = ""; - ImGui::InputText("unused", buf, IM_ARRAYSIZE(buf), ImGuiInputTextFlags_ReadOnly); - ImGui::SameLine(); - HelpMarker("This widget is only here to be able to tab-out of the widgets above and see e.g. Deactivated() status."); - - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Querying Window Status (Focused,Hovered etc.)"); - if (ImGui::TreeNode("Querying Window Status (Focused/Hovered etc.)")) - { - static bool embed_all_inside_a_child_window = false; - ImGui::Checkbox("Embed everything inside a child window for testing _RootWindow flag.", &embed_all_inside_a_child_window); - if (embed_all_inside_a_child_window) - ImGui::BeginChild("outer_child", ImVec2(0, ImGui::GetFontSize() * 20.0f), true); - - // Testing IsWindowFocused() function with its various flags. - ImGui::BulletText( - "IsWindowFocused() = %d\n" - "IsWindowFocused(_ChildWindows) = %d\n" - "IsWindowFocused(_ChildWindows|_NoPopupHierarchy) = %d\n" - "IsWindowFocused(_ChildWindows|_DockHierarchy) = %d\n" - "IsWindowFocused(_ChildWindows|_RootWindow) = %d\n" - "IsWindowFocused(_ChildWindows|_RootWindow|_NoPopupHierarchy) = %d\n" - "IsWindowFocused(_ChildWindows|_RootWindow|_DockHierarchy) = %d\n" - "IsWindowFocused(_RootWindow) = %d\n" - "IsWindowFocused(_RootWindow|_NoPopupHierarchy) = %d\n" - "IsWindowFocused(_RootWindow|_DockHierarchy) = %d\n" - "IsWindowFocused(_AnyWindow) = %d\n", - ImGui::IsWindowFocused(), - ImGui::IsWindowFocused(ImGuiFocusedFlags_ChildWindows), - ImGui::IsWindowFocused(ImGuiFocusedFlags_ChildWindows | ImGuiFocusedFlags_NoPopupHierarchy), - ImGui::IsWindowFocused(ImGuiFocusedFlags_ChildWindows | ImGuiFocusedFlags_DockHierarchy), - ImGui::IsWindowFocused(ImGuiFocusedFlags_ChildWindows | ImGuiFocusedFlags_RootWindow), - ImGui::IsWindowFocused(ImGuiFocusedFlags_ChildWindows | ImGuiFocusedFlags_RootWindow | ImGuiFocusedFlags_NoPopupHierarchy), - ImGui::IsWindowFocused(ImGuiFocusedFlags_ChildWindows | ImGuiFocusedFlags_RootWindow | ImGuiFocusedFlags_DockHierarchy), - ImGui::IsWindowFocused(ImGuiFocusedFlags_RootWindow), - ImGui::IsWindowFocused(ImGuiFocusedFlags_RootWindow | ImGuiFocusedFlags_NoPopupHierarchy), - ImGui::IsWindowFocused(ImGuiFocusedFlags_RootWindow | ImGuiFocusedFlags_DockHierarchy), - ImGui::IsWindowFocused(ImGuiFocusedFlags_AnyWindow)); - - // Testing IsWindowHovered() function with its various flags. - ImGui::BulletText( - "IsWindowHovered() = %d\n" - "IsWindowHovered(_AllowWhenBlockedByPopup) = %d\n" - "IsWindowHovered(_AllowWhenBlockedByActiveItem) = %d\n" - "IsWindowHovered(_ChildWindows) = %d\n" - "IsWindowHovered(_ChildWindows|_NoPopupHierarchy) = %d\n" - "IsWindowHovered(_ChildWindows|_DockHierarchy) = %d\n" - "IsWindowHovered(_ChildWindows|_RootWindow) = %d\n" - "IsWindowHovered(_ChildWindows|_RootWindow|_NoPopupHierarchy) = %d\n" - "IsWindowHovered(_ChildWindows|_RootWindow|_DockHierarchy) = %d\n" - "IsWindowHovered(_RootWindow) = %d\n" - "IsWindowHovered(_RootWindow|_NoPopupHierarchy) = %d\n" - "IsWindowHovered(_RootWindow|_DockHierarchy) = %d\n" - "IsWindowHovered(_ChildWindows|_AllowWhenBlockedByPopup) = %d\n" - "IsWindowHovered(_AnyWindow) = %d\n" - "IsWindowHovered(_Stationary) = %d\n", - ImGui::IsWindowHovered(), - ImGui::IsWindowHovered(ImGuiHoveredFlags_AllowWhenBlockedByPopup), - ImGui::IsWindowHovered(ImGuiHoveredFlags_AllowWhenBlockedByActiveItem), - ImGui::IsWindowHovered(ImGuiHoveredFlags_ChildWindows), - ImGui::IsWindowHovered(ImGuiHoveredFlags_ChildWindows | ImGuiHoveredFlags_NoPopupHierarchy), - ImGui::IsWindowHovered(ImGuiHoveredFlags_ChildWindows | ImGuiHoveredFlags_DockHierarchy), - ImGui::IsWindowHovered(ImGuiHoveredFlags_ChildWindows | ImGuiHoveredFlags_RootWindow), - ImGui::IsWindowHovered(ImGuiHoveredFlags_ChildWindows | ImGuiHoveredFlags_RootWindow | ImGuiHoveredFlags_NoPopupHierarchy), - ImGui::IsWindowHovered(ImGuiHoveredFlags_ChildWindows | ImGuiHoveredFlags_RootWindow | ImGuiHoveredFlags_DockHierarchy), - ImGui::IsWindowHovered(ImGuiHoveredFlags_RootWindow), - ImGui::IsWindowHovered(ImGuiHoveredFlags_RootWindow | ImGuiHoveredFlags_NoPopupHierarchy), - ImGui::IsWindowHovered(ImGuiHoveredFlags_RootWindow | ImGuiHoveredFlags_DockHierarchy), - ImGui::IsWindowHovered(ImGuiHoveredFlags_ChildWindows | ImGuiHoveredFlags_AllowWhenBlockedByPopup), - ImGui::IsWindowHovered(ImGuiHoveredFlags_AnyWindow), - ImGui::IsWindowHovered(ImGuiHoveredFlags_Stationary)); - - ImGui::BeginChild("child", ImVec2(0, 50), true); - ImGui::Text("This is another child window for testing the _ChildWindows flag."); - ImGui::EndChild(); - if (embed_all_inside_a_child_window) - ImGui::EndChild(); - - // Calling IsItemHovered() after begin returns the hovered status of the title bar. - // This is useful in particular if you want to create a context menu associated to the title bar of a window. - // This will also work when docked into a Tab (the Tab replace the Title Bar and guarantee the same properties). - static bool test_window = false; - ImGui::Checkbox("Hovered/Active tests after Begin() for title bar testing", &test_window); - if (test_window) - { - // FIXME-DOCK: This window cannot be docked within the ImGui Demo window, this will cause a feedback loop and get them stuck. - // Could we fix this through an ImGuiWindowClass feature? Or an API call to tag our parent as "don't skip items"? - ImGui::Begin("Title bar Hovered/Active tests", &test_window); - if (ImGui::BeginPopupContextItem()) // <-- This is using IsItemHovered() - { - if (ImGui::MenuItem("Close")) { test_window = false; } - ImGui::EndPopup(); - } - ImGui::Text( - "IsItemHovered() after begin = %d (== is title bar hovered)\n" - "IsItemActive() after begin = %d (== is window being clicked/moved)\n", - ImGui::IsItemHovered(), ImGui::IsItemActive()); - ImGui::End(); - } - - ImGui::TreePop(); - } - - // Demonstrate BeginDisabled/EndDisabled using a checkbox located at the bottom of the section (which is a bit odd: - // logically we'd have this checkbox at the top of the section, but we don't want this feature to steal that space) - if (disable_all) - ImGui::EndDisabled(); - - IMGUI_DEMO_MARKER("Widgets/Disable Block"); - if (ImGui::TreeNode("Disable block")) - { - ImGui::Checkbox("Disable entire section above", &disable_all); - ImGui::SameLine(); HelpMarker("Demonstrate using BeginDisabled()/EndDisabled() across this section."); - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Widgets/Text Filter"); - if (ImGui::TreeNode("Text Filter")) - { - // Helper class to easy setup a text filter. - // You may want to implement a more feature-full filtering scheme in your own application. - HelpMarker("Not a widget per-se, but ImGuiTextFilter is a helper to perform simple filtering on text strings."); - static ImGuiTextFilter filter; - ImGui::Text("Filter usage:\n" - " \"\" display all lines\n" - " \"xxx\" display lines containing \"xxx\"\n" - " \"xxx,yyy\" display lines containing \"xxx\" or \"yyy\"\n" - " \"-xxx\" hide lines containing \"xxx\""); - filter.Draw(); - const char* lines[] = { "aaa1.c", "bbb1.c", "ccc1.c", "aaa2.cpp", "bbb2.cpp", "ccc2.cpp", "abc.h", "hello, world" }; - for (int i = 0; i < IM_ARRAYSIZE(lines); i++) - if (filter.PassFilter(lines[i])) - ImGui::BulletText("%s", lines[i]); - ImGui::TreePop(); - } -} - -static void ShowDemoWindowLayout() -{ - IMGUI_DEMO_MARKER("Layout"); - if (!ImGui::CollapsingHeader("Layout & Scrolling")) - return; - - IMGUI_DEMO_MARKER("Layout/Child windows"); - if (ImGui::TreeNode("Child windows")) - { - ImGui::SeparatorText("Child windows"); - - HelpMarker("Use child windows to begin into a self-contained independent scrolling/clipping regions within a host window."); - static bool disable_mouse_wheel = false; - static bool disable_menu = false; - ImGui::Checkbox("Disable Mouse Wheel", &disable_mouse_wheel); - ImGui::Checkbox("Disable Menu", &disable_menu); - - // Child 1: no border, enable horizontal scrollbar - { - ImGuiWindowFlags window_flags = ImGuiWindowFlags_HorizontalScrollbar; - if (disable_mouse_wheel) - window_flags |= ImGuiWindowFlags_NoScrollWithMouse; - ImGui::BeginChild("ChildL", ImVec2(ImGui::GetContentRegionAvail().x * 0.5f, 260), false, window_flags); - for (int i = 0; i < 100; i++) - ImGui::Text("%04d: scrollable region", i); - ImGui::EndChild(); - } - - ImGui::SameLine(); - - // Child 2: rounded border - { - ImGuiWindowFlags window_flags = ImGuiWindowFlags_None; - if (disable_mouse_wheel) - window_flags |= ImGuiWindowFlags_NoScrollWithMouse; - if (!disable_menu) - window_flags |= ImGuiWindowFlags_MenuBar; - ImGui::PushStyleVar(ImGuiStyleVar_ChildRounding, 5.0f); - ImGui::BeginChild("ChildR", ImVec2(0, 260), true, window_flags); - if (!disable_menu && ImGui::BeginMenuBar()) - { - if (ImGui::BeginMenu("Menu")) - { - ShowExampleMenuFile(); - ImGui::EndMenu(); - } - ImGui::EndMenuBar(); - } - if (ImGui::BeginTable("split", 2, ImGuiTableFlags_Resizable | ImGuiTableFlags_NoSavedSettings)) - { - for (int i = 0; i < 100; i++) - { - char buf[32]; - sprintf(buf, "%03d", i); - ImGui::TableNextColumn(); - ImGui::Button(buf, ImVec2(-FLT_MIN, 0.0f)); - } - ImGui::EndTable(); - } - ImGui::EndChild(); - ImGui::PopStyleVar(); - } - - ImGui::SeparatorText("Misc/Advanced"); - - // Demonstrate a few extra things - // - Changing ImGuiCol_ChildBg (which is transparent black in default styles) - // - Using SetCursorPos() to position child window (the child window is an item from the POV of parent window) - // You can also call SetNextWindowPos() to position the child window. The parent window will effectively - // layout from this position. - // - Using ImGui::GetItemRectMin/Max() to query the "item" state (because the child window is an item from - // the POV of the parent window). See 'Demo->Querying Status (Edited/Active/Hovered etc.)' for details. - { - static int offset_x = 0; - ImGui::SetNextItemWidth(ImGui::GetFontSize() * 8); - ImGui::DragInt("Offset X", &offset_x, 1.0f, -1000, 1000); - - ImGui::SetCursorPosX(ImGui::GetCursorPosX() + (float)offset_x); - ImGui::PushStyleColor(ImGuiCol_ChildBg, IM_COL32(255, 0, 0, 100)); - ImGui::BeginChild("Red", ImVec2(200, 100), true, ImGuiWindowFlags_None); - for (int n = 0; n < 50; n++) - ImGui::Text("Some test %d", n); - ImGui::EndChild(); - bool child_is_hovered = ImGui::IsItemHovered(); - ImVec2 child_rect_min = ImGui::GetItemRectMin(); - ImVec2 child_rect_max = ImGui::GetItemRectMax(); - ImGui::PopStyleColor(); - ImGui::Text("Hovered: %d", child_is_hovered); - ImGui::Text("Rect of child window is: (%.0f,%.0f) (%.0f,%.0f)", child_rect_min.x, child_rect_min.y, child_rect_max.x, child_rect_max.y); - } - - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Layout/Widgets Width"); - if (ImGui::TreeNode("Widgets Width")) - { - static float f = 0.0f; - static bool show_indented_items = true; - ImGui::Checkbox("Show indented items", &show_indented_items); - - // Use SetNextItemWidth() to set the width of a single upcoming item. - // Use PushItemWidth()/PopItemWidth() to set the width of a group of items. - // In real code use you'll probably want to choose width values that are proportional to your font size - // e.g. Using '20.0f * GetFontSize()' as width instead of '200.0f', etc. - - ImGui::Text("SetNextItemWidth/PushItemWidth(100)"); - ImGui::SameLine(); HelpMarker("Fixed width."); - ImGui::PushItemWidth(100); - ImGui::DragFloat("float##1b", &f); - if (show_indented_items) - { - ImGui::Indent(); - ImGui::DragFloat("float (indented)##1b", &f); - ImGui::Unindent(); - } - ImGui::PopItemWidth(); - - ImGui::Text("SetNextItemWidth/PushItemWidth(-100)"); - ImGui::SameLine(); HelpMarker("Align to right edge minus 100"); - ImGui::PushItemWidth(-100); - ImGui::DragFloat("float##2a", &f); - if (show_indented_items) - { - ImGui::Indent(); - ImGui::DragFloat("float (indented)##2b", &f); - ImGui::Unindent(); - } - ImGui::PopItemWidth(); - - ImGui::Text("SetNextItemWidth/PushItemWidth(GetContentRegionAvail().x * 0.5f)"); - ImGui::SameLine(); HelpMarker("Half of available width.\n(~ right-cursor_pos)\n(works within a column set)"); - ImGui::PushItemWidth(ImGui::GetContentRegionAvail().x * 0.5f); - ImGui::DragFloat("float##3a", &f); - if (show_indented_items) - { - ImGui::Indent(); - ImGui::DragFloat("float (indented)##3b", &f); - ImGui::Unindent(); - } - ImGui::PopItemWidth(); - - ImGui::Text("SetNextItemWidth/PushItemWidth(-GetContentRegionAvail().x * 0.5f)"); - ImGui::SameLine(); HelpMarker("Align to right edge minus half"); - ImGui::PushItemWidth(-ImGui::GetContentRegionAvail().x * 0.5f); - ImGui::DragFloat("float##4a", &f); - if (show_indented_items) - { - ImGui::Indent(); - ImGui::DragFloat("float (indented)##4b", &f); - ImGui::Unindent(); - } - ImGui::PopItemWidth(); - - // Demonstrate using PushItemWidth to surround three items. - // Calling SetNextItemWidth() before each of them would have the same effect. - ImGui::Text("SetNextItemWidth/PushItemWidth(-FLT_MIN)"); - ImGui::SameLine(); HelpMarker("Align to right edge"); - ImGui::PushItemWidth(-FLT_MIN); - ImGui::DragFloat("##float5a", &f); - if (show_indented_items) - { - ImGui::Indent(); - ImGui::DragFloat("float (indented)##5b", &f); - ImGui::Unindent(); - } - ImGui::PopItemWidth(); - - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Layout/Basic Horizontal Layout"); - if (ImGui::TreeNode("Basic Horizontal Layout")) - { - ImGui::TextWrapped("(Use ImGui::SameLine() to keep adding items to the right of the preceding item)"); - - // Text - IMGUI_DEMO_MARKER("Layout/Basic Horizontal Layout/SameLine"); - ImGui::Text("Two items: Hello"); ImGui::SameLine(); - ImGui::TextColored(ImVec4(1, 1, 0, 1), "Sailor"); - - // Adjust spacing - ImGui::Text("More spacing: Hello"); ImGui::SameLine(0, 20); - ImGui::TextColored(ImVec4(1, 1, 0, 1), "Sailor"); - - // Button - ImGui::AlignTextToFramePadding(); - ImGui::Text("Normal buttons"); ImGui::SameLine(); - ImGui::Button("Banana"); ImGui::SameLine(); - ImGui::Button("Apple"); ImGui::SameLine(); - ImGui::Button("Corniflower"); - - // Button - ImGui::Text("Small buttons"); ImGui::SameLine(); - ImGui::SmallButton("Like this one"); ImGui::SameLine(); - ImGui::Text("can fit within a text block."); - - // Aligned to arbitrary position. Easy/cheap column. - IMGUI_DEMO_MARKER("Layout/Basic Horizontal Layout/SameLine (with offset)"); - ImGui::Text("Aligned"); - ImGui::SameLine(150); ImGui::Text("x=150"); - ImGui::SameLine(300); ImGui::Text("x=300"); - ImGui::Text("Aligned"); - ImGui::SameLine(150); ImGui::SmallButton("x=150"); - ImGui::SameLine(300); ImGui::SmallButton("x=300"); - - // Checkbox - IMGUI_DEMO_MARKER("Layout/Basic Horizontal Layout/SameLine (more)"); - static bool c1 = false, c2 = false, c3 = false, c4 = false; - ImGui::Checkbox("My", &c1); ImGui::SameLine(); - ImGui::Checkbox("Tailor", &c2); ImGui::SameLine(); - ImGui::Checkbox("Is", &c3); ImGui::SameLine(); - ImGui::Checkbox("Rich", &c4); - - // Various - static float f0 = 1.0f, f1 = 2.0f, f2 = 3.0f; - ImGui::PushItemWidth(80); - const char* items[] = { "AAAA", "BBBB", "CCCC", "DDDD" }; - static int item = -1; - ImGui::Combo("Combo", &item, items, IM_ARRAYSIZE(items)); ImGui::SameLine(); - ImGui::SliderFloat("X", &f0, 0.0f, 5.0f); ImGui::SameLine(); - ImGui::SliderFloat("Y", &f1, 0.0f, 5.0f); ImGui::SameLine(); - ImGui::SliderFloat("Z", &f2, 0.0f, 5.0f); - ImGui::PopItemWidth(); - - ImGui::PushItemWidth(80); - ImGui::Text("Lists:"); - static int selection[4] = { 0, 1, 2, 3 }; - for (int i = 0; i < 4; i++) - { - if (i > 0) ImGui::SameLine(); - ImGui::PushID(i); - ImGui::ListBox("", &selection[i], items, IM_ARRAYSIZE(items)); - ImGui::PopID(); - //ImGui::SetItemTooltip("ListBox %d hovered", i); - } - ImGui::PopItemWidth(); - - // Dummy - IMGUI_DEMO_MARKER("Layout/Basic Horizontal Layout/Dummy"); - ImVec2 button_sz(40, 40); - ImGui::Button("A", button_sz); ImGui::SameLine(); - ImGui::Dummy(button_sz); ImGui::SameLine(); - ImGui::Button("B", button_sz); - - // Manually wrapping - // (we should eventually provide this as an automatic layout feature, but for now you can do it manually) - IMGUI_DEMO_MARKER("Layout/Basic Horizontal Layout/Manual wrapping"); - ImGui::Text("Manual wrapping:"); - ImGuiStyle& style = ImGui::GetStyle(); - int buttons_count = 20; - float window_visible_x2 = ImGui::GetWindowPos().x + ImGui::GetWindowContentRegionMax().x; - for (int n = 0; n < buttons_count; n++) - { - ImGui::PushID(n); - ImGui::Button("Box", button_sz); - float last_button_x2 = ImGui::GetItemRectMax().x; - float next_button_x2 = last_button_x2 + style.ItemSpacing.x + button_sz.x; // Expected position if next button was on same line - if (n + 1 < buttons_count && next_button_x2 < window_visible_x2) - ImGui::SameLine(); - ImGui::PopID(); - } - - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Layout/Groups"); - if (ImGui::TreeNode("Groups")) - { - HelpMarker( - "BeginGroup() basically locks the horizontal position for new line. " - "EndGroup() bundles the whole group so that you can use \"item\" functions such as " - "IsItemHovered()/IsItemActive() or SameLine() etc. on the whole group."); - ImGui::BeginGroup(); - { - ImGui::BeginGroup(); - ImGui::Button("AAA"); - ImGui::SameLine(); - ImGui::Button("BBB"); - ImGui::SameLine(); - ImGui::BeginGroup(); - ImGui::Button("CCC"); - ImGui::Button("DDD"); - ImGui::EndGroup(); - ImGui::SameLine(); - ImGui::Button("EEE"); - ImGui::EndGroup(); - ImGui::SetItemTooltip("First group hovered"); - } - // Capture the group size and create widgets using the same size - ImVec2 size = ImGui::GetItemRectSize(); - const float values[5] = { 0.5f, 0.20f, 0.80f, 0.60f, 0.25f }; - ImGui::PlotHistogram("##values", values, IM_ARRAYSIZE(values), 0, NULL, 0.0f, 1.0f, size); - - ImGui::Button("ACTION", ImVec2((size.x - ImGui::GetStyle().ItemSpacing.x) * 0.5f, size.y)); - ImGui::SameLine(); - ImGui::Button("REACTION", ImVec2((size.x - ImGui::GetStyle().ItemSpacing.x) * 0.5f, size.y)); - ImGui::EndGroup(); - ImGui::SameLine(); - - ImGui::Button("LEVERAGE\nBUZZWORD", size); - ImGui::SameLine(); - - if (ImGui::BeginListBox("List", size)) - { - ImGui::Selectable("Selected", true); - ImGui::Selectable("Not Selected", false); - ImGui::EndListBox(); - } - - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Layout/Text Baseline Alignment"); - if (ImGui::TreeNode("Text Baseline Alignment")) - { - { - ImGui::BulletText("Text baseline:"); - ImGui::SameLine(); HelpMarker( - "This is testing the vertical alignment that gets applied on text to keep it aligned with widgets. " - "Lines only composed of text or \"small\" widgets use less vertical space than lines with framed widgets."); - ImGui::Indent(); - - ImGui::Text("KO Blahblah"); ImGui::SameLine(); - ImGui::Button("Some framed item"); ImGui::SameLine(); - HelpMarker("Baseline of button will look misaligned with text.."); - - // If your line starts with text, call AlignTextToFramePadding() to align text to upcoming widgets. - // (because we don't know what's coming after the Text() statement, we need to move the text baseline - // down by FramePadding.y ahead of time) - ImGui::AlignTextToFramePadding(); - ImGui::Text("OK Blahblah"); ImGui::SameLine(); - ImGui::Button("Some framed item"); ImGui::SameLine(); - HelpMarker("We call AlignTextToFramePadding() to vertically align the text baseline by +FramePadding.y"); - - // SmallButton() uses the same vertical padding as Text - ImGui::Button("TEST##1"); ImGui::SameLine(); - ImGui::Text("TEST"); ImGui::SameLine(); - ImGui::SmallButton("TEST##2"); - - // If your line starts with text, call AlignTextToFramePadding() to align text to upcoming widgets. - ImGui::AlignTextToFramePadding(); - ImGui::Text("Text aligned to framed item"); ImGui::SameLine(); - ImGui::Button("Item##1"); ImGui::SameLine(); - ImGui::Text("Item"); ImGui::SameLine(); - ImGui::SmallButton("Item##2"); ImGui::SameLine(); - ImGui::Button("Item##3"); - - ImGui::Unindent(); - } - - ImGui::Spacing(); - - { - ImGui::BulletText("Multi-line text:"); - ImGui::Indent(); - ImGui::Text("One\nTwo\nThree"); ImGui::SameLine(); - ImGui::Text("Hello\nWorld"); ImGui::SameLine(); - ImGui::Text("Banana"); - - ImGui::Text("Banana"); ImGui::SameLine(); - ImGui::Text("Hello\nWorld"); ImGui::SameLine(); - ImGui::Text("One\nTwo\nThree"); - - ImGui::Button("HOP##1"); ImGui::SameLine(); - ImGui::Text("Banana"); ImGui::SameLine(); - ImGui::Text("Hello\nWorld"); ImGui::SameLine(); - ImGui::Text("Banana"); - - ImGui::Button("HOP##2"); ImGui::SameLine(); - ImGui::Text("Hello\nWorld"); ImGui::SameLine(); - ImGui::Text("Banana"); - ImGui::Unindent(); - } - - ImGui::Spacing(); - - { - ImGui::BulletText("Misc items:"); - ImGui::Indent(); - - // SmallButton() sets FramePadding to zero. Text baseline is aligned to match baseline of previous Button. - ImGui::Button("80x80", ImVec2(80, 80)); - ImGui::SameLine(); - ImGui::Button("50x50", ImVec2(50, 50)); - ImGui::SameLine(); - ImGui::Button("Button()"); - ImGui::SameLine(); - ImGui::SmallButton("SmallButton()"); - - // Tree - const float spacing = ImGui::GetStyle().ItemInnerSpacing.x; - ImGui::Button("Button##1"); - ImGui::SameLine(0.0f, spacing); - if (ImGui::TreeNode("Node##1")) - { - // Placeholder tree data - for (int i = 0; i < 6; i++) - ImGui::BulletText("Item %d..", i); - ImGui::TreePop(); - } - - // Vertically align text node a bit lower so it'll be vertically centered with upcoming widget. - // Otherwise you can use SmallButton() (smaller fit). - ImGui::AlignTextToFramePadding(); - - // Common mistake to avoid: if we want to SameLine after TreeNode we need to do it before we add - // other contents below the node. - bool node_open = ImGui::TreeNode("Node##2"); - ImGui::SameLine(0.0f, spacing); ImGui::Button("Button##2"); - if (node_open) - { - // Placeholder tree data - for (int i = 0; i < 6; i++) - ImGui::BulletText("Item %d..", i); - ImGui::TreePop(); - } - - // Bullet - ImGui::Button("Button##3"); - ImGui::SameLine(0.0f, spacing); - ImGui::BulletText("Bullet text"); - - ImGui::AlignTextToFramePadding(); - ImGui::BulletText("Node"); - ImGui::SameLine(0.0f, spacing); ImGui::Button("Button##4"); - ImGui::Unindent(); - } - - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Layout/Scrolling"); - if (ImGui::TreeNode("Scrolling")) - { - // Vertical scroll functions - IMGUI_DEMO_MARKER("Layout/Scrolling/Vertical"); - HelpMarker("Use SetScrollHereY() or SetScrollFromPosY() to scroll to a given vertical position."); - - static int track_item = 50; - static bool enable_track = true; - static bool enable_extra_decorations = false; - static float scroll_to_off_px = 0.0f; - static float scroll_to_pos_px = 200.0f; - - ImGui::Checkbox("Decoration", &enable_extra_decorations); - - ImGui::Checkbox("Track", &enable_track); - ImGui::PushItemWidth(100); - ImGui::SameLine(140); enable_track |= ImGui::DragInt("##item", &track_item, 0.25f, 0, 99, "Item = %d"); - - bool scroll_to_off = ImGui::Button("Scroll Offset"); - ImGui::SameLine(140); scroll_to_off |= ImGui::DragFloat("##off", &scroll_to_off_px, 1.00f, 0, FLT_MAX, "+%.0f px"); - - bool scroll_to_pos = ImGui::Button("Scroll To Pos"); - ImGui::SameLine(140); scroll_to_pos |= ImGui::DragFloat("##pos", &scroll_to_pos_px, 1.00f, -10, FLT_MAX, "X/Y = %.0f px"); - ImGui::PopItemWidth(); - - if (scroll_to_off || scroll_to_pos) - enable_track = false; - - ImGuiStyle& style = ImGui::GetStyle(); - float child_w = (ImGui::GetContentRegionAvail().x - 4 * style.ItemSpacing.x) / 5; - if (child_w < 1.0f) - child_w = 1.0f; - ImGui::PushID("##VerticalScrolling"); - for (int i = 0; i < 5; i++) - { - if (i > 0) ImGui::SameLine(); - ImGui::BeginGroup(); - const char* names[] = { "Top", "25%", "Center", "75%", "Bottom" }; - ImGui::TextUnformatted(names[i]); - - const ImGuiWindowFlags child_flags = enable_extra_decorations ? ImGuiWindowFlags_MenuBar : 0; - const ImGuiID child_id = ImGui::GetID((void*)(intptr_t)i); - const bool child_is_visible = ImGui::BeginChild(child_id, ImVec2(child_w, 200.0f), true, child_flags); - if (ImGui::BeginMenuBar()) - { - ImGui::TextUnformatted("abc"); - ImGui::EndMenuBar(); - } - if (scroll_to_off) - ImGui::SetScrollY(scroll_to_off_px); - if (scroll_to_pos) - ImGui::SetScrollFromPosY(ImGui::GetCursorStartPos().y + scroll_to_pos_px, i * 0.25f); - if (child_is_visible) // Avoid calling SetScrollHereY when running with culled items - { - for (int item = 0; item < 100; item++) - { - if (enable_track && item == track_item) - { - ImGui::TextColored(ImVec4(1, 1, 0, 1), "Item %d", item); - ImGui::SetScrollHereY(i * 0.25f); // 0.0f:top, 0.5f:center, 1.0f:bottom - } - else - { - ImGui::Text("Item %d", item); - } - } - } - float scroll_y = ImGui::GetScrollY(); - float scroll_max_y = ImGui::GetScrollMaxY(); - ImGui::EndChild(); - ImGui::Text("%.0f/%.0f", scroll_y, scroll_max_y); - ImGui::EndGroup(); - } - ImGui::PopID(); - - // Horizontal scroll functions - IMGUI_DEMO_MARKER("Layout/Scrolling/Horizontal"); - ImGui::Spacing(); - HelpMarker( - "Use SetScrollHereX() or SetScrollFromPosX() to scroll to a given horizontal position.\n\n" - "Because the clipping rectangle of most window hides half worth of WindowPadding on the " - "left/right, using SetScrollFromPosX(+1) will usually result in clipped text whereas the " - "equivalent SetScrollFromPosY(+1) wouldn't."); - ImGui::PushID("##HorizontalScrolling"); - for (int i = 0; i < 5; i++) - { - float child_height = ImGui::GetTextLineHeight() + style.ScrollbarSize + style.WindowPadding.y * 2.0f; - ImGuiWindowFlags child_flags = ImGuiWindowFlags_HorizontalScrollbar | (enable_extra_decorations ? ImGuiWindowFlags_AlwaysVerticalScrollbar : 0); - ImGuiID child_id = ImGui::GetID((void*)(intptr_t)i); - bool child_is_visible = ImGui::BeginChild(child_id, ImVec2(-100, child_height), true, child_flags); - if (scroll_to_off) - ImGui::SetScrollX(scroll_to_off_px); - if (scroll_to_pos) - ImGui::SetScrollFromPosX(ImGui::GetCursorStartPos().x + scroll_to_pos_px, i * 0.25f); - if (child_is_visible) // Avoid calling SetScrollHereY when running with culled items - { - for (int item = 0; item < 100; item++) - { - if (item > 0) - ImGui::SameLine(); - if (enable_track && item == track_item) - { - ImGui::TextColored(ImVec4(1, 1, 0, 1), "Item %d", item); - ImGui::SetScrollHereX(i * 0.25f); // 0.0f:left, 0.5f:center, 1.0f:right - } - else - { - ImGui::Text("Item %d", item); - } - } - } - float scroll_x = ImGui::GetScrollX(); - float scroll_max_x = ImGui::GetScrollMaxX(); - ImGui::EndChild(); - ImGui::SameLine(); - const char* names[] = { "Left", "25%", "Center", "75%", "Right" }; - ImGui::Text("%s\n%.0f/%.0f", names[i], scroll_x, scroll_max_x); - ImGui::Spacing(); - } - ImGui::PopID(); - - // Miscellaneous Horizontal Scrolling Demo - IMGUI_DEMO_MARKER("Layout/Scrolling/Horizontal (more)"); - HelpMarker( - "Horizontal scrolling for a window is enabled via the ImGuiWindowFlags_HorizontalScrollbar flag.\n\n" - "You may want to also explicitly specify content width by using SetNextWindowContentWidth() before Begin()."); - static int lines = 7; - ImGui::SliderInt("Lines", &lines, 1, 15); - ImGui::PushStyleVar(ImGuiStyleVar_FrameRounding, 3.0f); - ImGui::PushStyleVar(ImGuiStyleVar_FramePadding, ImVec2(2.0f, 1.0f)); - ImVec2 scrolling_child_size = ImVec2(0, ImGui::GetFrameHeightWithSpacing() * 7 + 30); - ImGui::BeginChild("scrolling", scrolling_child_size, true, ImGuiWindowFlags_HorizontalScrollbar); - for (int line = 0; line < lines; line++) - { - // Display random stuff. For the sake of this trivial demo we are using basic Button() + SameLine() - // If you want to create your own time line for a real application you may be better off manipulating - // the cursor position yourself, aka using SetCursorPos/SetCursorScreenPos to position the widgets - // yourself. You may also want to use the lower-level ImDrawList API. - int num_buttons = 10 + ((line & 1) ? line * 9 : line * 3); - for (int n = 0; n < num_buttons; n++) - { - if (n > 0) ImGui::SameLine(); - ImGui::PushID(n + line * 1000); - char num_buf[16]; - sprintf(num_buf, "%d", n); - const char* label = (!(n % 15)) ? "FizzBuzz" : (!(n % 3)) ? "Fizz" : (!(n % 5)) ? "Buzz" : num_buf; - float hue = n * 0.05f; - ImGui::PushStyleColor(ImGuiCol_Button, (ImVec4)ImColor::HSV(hue, 0.6f, 0.6f)); - ImGui::PushStyleColor(ImGuiCol_ButtonHovered, (ImVec4)ImColor::HSV(hue, 0.7f, 0.7f)); - ImGui::PushStyleColor(ImGuiCol_ButtonActive, (ImVec4)ImColor::HSV(hue, 0.8f, 0.8f)); - ImGui::Button(label, ImVec2(40.0f + sinf((float)(line + n)) * 20.0f, 0.0f)); - ImGui::PopStyleColor(3); - ImGui::PopID(); - } - } - float scroll_x = ImGui::GetScrollX(); - float scroll_max_x = ImGui::GetScrollMaxX(); - ImGui::EndChild(); - ImGui::PopStyleVar(2); - float scroll_x_delta = 0.0f; - ImGui::SmallButton("<<"); - if (ImGui::IsItemActive()) - scroll_x_delta = -ImGui::GetIO().DeltaTime * 1000.0f; - ImGui::SameLine(); - ImGui::Text("Scroll from code"); ImGui::SameLine(); - ImGui::SmallButton(">>"); - if (ImGui::IsItemActive()) - scroll_x_delta = +ImGui::GetIO().DeltaTime * 1000.0f; - ImGui::SameLine(); - ImGui::Text("%.0f/%.0f", scroll_x, scroll_max_x); - if (scroll_x_delta != 0.0f) - { - // Demonstrate a trick: you can use Begin to set yourself in the context of another window - // (here we are already out of your child window) - ImGui::BeginChild("scrolling"); - ImGui::SetScrollX(ImGui::GetScrollX() + scroll_x_delta); - ImGui::EndChild(); - } - ImGui::Spacing(); - - static bool show_horizontal_contents_size_demo_window = false; - ImGui::Checkbox("Show Horizontal contents size demo window", &show_horizontal_contents_size_demo_window); - - if (show_horizontal_contents_size_demo_window) - { - static bool show_h_scrollbar = true; - static bool show_button = true; - static bool show_tree_nodes = true; - static bool show_text_wrapped = false; - static bool show_columns = true; - static bool show_tab_bar = true; - static bool show_child = false; - static bool explicit_content_size = false; - static float contents_size_x = 300.0f; - if (explicit_content_size) - ImGui::SetNextWindowContentSize(ImVec2(contents_size_x, 0.0f)); - ImGui::Begin("Horizontal contents size demo window", &show_horizontal_contents_size_demo_window, show_h_scrollbar ? ImGuiWindowFlags_HorizontalScrollbar : 0); - IMGUI_DEMO_MARKER("Layout/Scrolling/Horizontal contents size demo window"); - ImGui::PushStyleVar(ImGuiStyleVar_ItemSpacing, ImVec2(2, 0)); - ImGui::PushStyleVar(ImGuiStyleVar_FramePadding, ImVec2(2, 0)); - HelpMarker("Test of different widgets react and impact the work rectangle growing when horizontal scrolling is enabled.\n\nUse 'Metrics->Tools->Show windows rectangles' to visualize rectangles."); - ImGui::Checkbox("H-scrollbar", &show_h_scrollbar); - ImGui::Checkbox("Button", &show_button); // Will grow contents size (unless explicitly overwritten) - ImGui::Checkbox("Tree nodes", &show_tree_nodes); // Will grow contents size and display highlight over full width - ImGui::Checkbox("Text wrapped", &show_text_wrapped);// Will grow and use contents size - ImGui::Checkbox("Columns", &show_columns); // Will use contents size - ImGui::Checkbox("Tab bar", &show_tab_bar); // Will use contents size - ImGui::Checkbox("Child", &show_child); // Will grow and use contents size - ImGui::Checkbox("Explicit content size", &explicit_content_size); - ImGui::Text("Scroll %.1f/%.1f %.1f/%.1f", ImGui::GetScrollX(), ImGui::GetScrollMaxX(), ImGui::GetScrollY(), ImGui::GetScrollMaxY()); - if (explicit_content_size) - { - ImGui::SameLine(); - ImGui::SetNextItemWidth(100); - ImGui::DragFloat("##csx", &contents_size_x); - ImVec2 p = ImGui::GetCursorScreenPos(); - ImGui::GetWindowDrawList()->AddRectFilled(p, ImVec2(p.x + 10, p.y + 10), IM_COL32_WHITE); - ImGui::GetWindowDrawList()->AddRectFilled(ImVec2(p.x + contents_size_x - 10, p.y), ImVec2(p.x + contents_size_x, p.y + 10), IM_COL32_WHITE); - ImGui::Dummy(ImVec2(0, 10)); - } - ImGui::PopStyleVar(2); - ImGui::Separator(); - if (show_button) - { - ImGui::Button("this is a 300-wide button", ImVec2(300, 0)); - } - if (show_tree_nodes) - { - bool open = true; - if (ImGui::TreeNode("this is a tree node")) - { - if (ImGui::TreeNode("another one of those tree node...")) - { - ImGui::Text("Some tree contents"); - ImGui::TreePop(); - } - ImGui::TreePop(); - } - ImGui::CollapsingHeader("CollapsingHeader", &open); - } - if (show_text_wrapped) - { - ImGui::TextWrapped("This text should automatically wrap on the edge of the work rectangle."); - } - if (show_columns) - { - ImGui::Text("Tables:"); - if (ImGui::BeginTable("table", 4, ImGuiTableFlags_Borders)) - { - for (int n = 0; n < 4; n++) - { - ImGui::TableNextColumn(); - ImGui::Text("Width %.2f", ImGui::GetContentRegionAvail().x); - } - ImGui::EndTable(); - } - ImGui::Text("Columns:"); - ImGui::Columns(4); - for (int n = 0; n < 4; n++) - { - ImGui::Text("Width %.2f", ImGui::GetColumnWidth()); - ImGui::NextColumn(); - } - ImGui::Columns(1); - } - if (show_tab_bar && ImGui::BeginTabBar("Hello")) - { - if (ImGui::BeginTabItem("OneOneOne")) { ImGui::EndTabItem(); } - if (ImGui::BeginTabItem("TwoTwoTwo")) { ImGui::EndTabItem(); } - if (ImGui::BeginTabItem("ThreeThreeThree")) { ImGui::EndTabItem(); } - if (ImGui::BeginTabItem("FourFourFour")) { ImGui::EndTabItem(); } - ImGui::EndTabBar(); - } - if (show_child) - { - ImGui::BeginChild("child", ImVec2(0, 0), true); - ImGui::EndChild(); - } - ImGui::End(); - } - - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Layout/Clipping"); - if (ImGui::TreeNode("Clipping")) - { - static ImVec2 size(100.0f, 100.0f); - static ImVec2 offset(30.0f, 30.0f); - ImGui::DragFloat2("size", (float*)&size, 0.5f, 1.0f, 200.0f, "%.0f"); - ImGui::TextWrapped("(Click and drag to scroll)"); - - HelpMarker( - "(Left) Using ImGui::PushClipRect():\n" - "Will alter ImGui hit-testing logic + ImDrawList rendering.\n" - "(use this if you want your clipping rectangle to affect interactions)\n\n" - "(Center) Using ImDrawList::PushClipRect():\n" - "Will alter ImDrawList rendering only.\n" - "(use this as a shortcut if you are only using ImDrawList calls)\n\n" - "(Right) Using ImDrawList::AddText() with a fine ClipRect:\n" - "Will alter only this specific ImDrawList::AddText() rendering.\n" - "This is often used internally to avoid altering the clipping rectangle and minimize draw calls."); - - for (int n = 0; n < 3; n++) - { - if (n > 0) - ImGui::SameLine(); - - ImGui::PushID(n); - ImGui::InvisibleButton("##canvas", size); - if (ImGui::IsItemActive() && ImGui::IsMouseDragging(ImGuiMouseButton_Left)) - { - offset.x += ImGui::GetIO().MouseDelta.x; - offset.y += ImGui::GetIO().MouseDelta.y; - } - ImGui::PopID(); - if (!ImGui::IsItemVisible()) // Skip rendering as ImDrawList elements are not clipped. - continue; - - const ImVec2 p0 = ImGui::GetItemRectMin(); - const ImVec2 p1 = ImGui::GetItemRectMax(); - const char* text_str = "Line 1 hello\nLine 2 clip me!"; - const ImVec2 text_pos = ImVec2(p0.x + offset.x, p0.y + offset.y); - ImDrawList* draw_list = ImGui::GetWindowDrawList(); - switch (n) - { - case 0: - ImGui::PushClipRect(p0, p1, true); - draw_list->AddRectFilled(p0, p1, IM_COL32(90, 90, 120, 255)); - draw_list->AddText(text_pos, IM_COL32_WHITE, text_str); - ImGui::PopClipRect(); - break; - case 1: - draw_list->PushClipRect(p0, p1, true); - draw_list->AddRectFilled(p0, p1, IM_COL32(90, 90, 120, 255)); - draw_list->AddText(text_pos, IM_COL32_WHITE, text_str); - draw_list->PopClipRect(); - break; - case 2: - ImVec4 clip_rect(p0.x, p0.y, p1.x, p1.y); // AddText() takes a ImVec4* here so let's convert. - draw_list->AddRectFilled(p0, p1, IM_COL32(90, 90, 120, 255)); - draw_list->AddText(ImGui::GetFont(), ImGui::GetFontSize(), text_pos, IM_COL32_WHITE, text_str, NULL, 0.0f, &clip_rect); - break; - } - } - - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Layout/Overlap Mode"); - if (ImGui::TreeNode("Overlap Mode")) - { - static bool enable_allow_overlap = true; - - HelpMarker( - "Hit-testing is by default performed in item submission order, which generally is perceived as 'back-to-front'.\n\n" - "By using SetNextItemAllowOverlap() you can notify that an item may be overlapped by another. Doing so alters the hovering logic: items using AllowOverlap mode requires an extra frame to accept hovered state."); - ImGui::Checkbox("Enable AllowOverlap", &enable_allow_overlap); - - ImVec2 button1_pos = ImGui::GetCursorScreenPos(); - ImVec2 button2_pos = ImVec2(button1_pos.x + 50.0f, button1_pos.y + 50.0f); - if (enable_allow_overlap) - ImGui::SetNextItemAllowOverlap(); - ImGui::Button("Button 1", ImVec2(80, 80)); - ImGui::SetCursorScreenPos(button2_pos); - ImGui::Button("Button 2", ImVec2(80, 80)); - - // This is typically used with width-spanning items. - // (note that Selectable() has a dedicated flag ImGuiSelectableFlags_AllowOverlap, which is a shortcut - // for using SetNextItemAllowOverlap(). For demo purpose we use SetNextItemAllowOverlap() here.) - if (enable_allow_overlap) - ImGui::SetNextItemAllowOverlap(); - ImGui::Selectable("Some Selectable", false); - ImGui::SameLine(); - ImGui::SmallButton("++"); - - ImGui::TreePop(); - } -} - -static void ShowDemoWindowPopups() -{ - IMGUI_DEMO_MARKER("Popups"); - if (!ImGui::CollapsingHeader("Popups & Modal windows")) - return; - - // The properties of popups windows are: - // - They block normal mouse hovering detection outside them. (*) - // - Unless modal, they can be closed by clicking anywhere outside them, or by pressing ESCAPE. - // - Their visibility state (~bool) is held internally by Dear ImGui instead of being held by the programmer as - // we are used to with regular Begin() calls. User can manipulate the visibility state by calling OpenPopup(). - // (*) One can use IsItemHovered(ImGuiHoveredFlags_AllowWhenBlockedByPopup) to bypass it and detect hovering even - // when normally blocked by a popup. - // Those three properties are connected. The library needs to hold their visibility state BECAUSE it can close - // popups at any time. - - // Typical use for regular windows: - // bool my_tool_is_active = false; if (ImGui::Button("Open")) my_tool_is_active = true; [...] if (my_tool_is_active) Begin("My Tool", &my_tool_is_active) { [...] } End(); - // Typical use for popups: - // if (ImGui::Button("Open")) ImGui::OpenPopup("MyPopup"); if (ImGui::BeginPopup("MyPopup") { [...] EndPopup(); } - - // With popups we have to go through a library call (here OpenPopup) to manipulate the visibility state. - // This may be a bit confusing at first but it should quickly make sense. Follow on the examples below. - - IMGUI_DEMO_MARKER("Popups/Popups"); - if (ImGui::TreeNode("Popups")) - { - ImGui::TextWrapped( - "When a popup is active, it inhibits interacting with windows that are behind the popup. " - "Clicking outside the popup closes it."); - - static int selected_fish = -1; - const char* names[] = { "Bream", "Haddock", "Mackerel", "Pollock", "Tilefish" }; - static bool toggles[] = { true, false, false, false, false }; - - // Simple selection popup (if you want to show the current selection inside the Button itself, - // you may want to build a string using the "###" operator to preserve a constant ID with a variable label) - if (ImGui::Button("Select..")) - ImGui::OpenPopup("my_select_popup"); - ImGui::SameLine(); - ImGui::TextUnformatted(selected_fish == -1 ? "" : names[selected_fish]); - if (ImGui::BeginPopup("my_select_popup")) - { - ImGui::SeparatorText("Aquarium"); - for (int i = 0; i < IM_ARRAYSIZE(names); i++) - if (ImGui::Selectable(names[i])) - selected_fish = i; - ImGui::EndPopup(); - } - - // Showing a menu with toggles - if (ImGui::Button("Toggle..")) - ImGui::OpenPopup("my_toggle_popup"); - if (ImGui::BeginPopup("my_toggle_popup")) - { - for (int i = 0; i < IM_ARRAYSIZE(names); i++) - ImGui::MenuItem(names[i], "", &toggles[i]); - if (ImGui::BeginMenu("Sub-menu")) - { - ImGui::MenuItem("Click me"); - ImGui::EndMenu(); - } - - ImGui::Separator(); - ImGui::Text("Tooltip here"); - ImGui::SetItemTooltip("I am a tooltip over a popup"); - - if (ImGui::Button("Stacked Popup")) - ImGui::OpenPopup("another popup"); - if (ImGui::BeginPopup("another popup")) - { - for (int i = 0; i < IM_ARRAYSIZE(names); i++) - ImGui::MenuItem(names[i], "", &toggles[i]); - if (ImGui::BeginMenu("Sub-menu")) - { - ImGui::MenuItem("Click me"); - if (ImGui::Button("Stacked Popup")) - ImGui::OpenPopup("another popup"); - if (ImGui::BeginPopup("another popup")) - { - ImGui::Text("I am the last one here."); - ImGui::EndPopup(); - } - ImGui::EndMenu(); - } - ImGui::EndPopup(); - } - ImGui::EndPopup(); - } - - // Call the more complete ShowExampleMenuFile which we use in various places of this demo - if (ImGui::Button("With a menu..")) - ImGui::OpenPopup("my_file_popup"); - if (ImGui::BeginPopup("my_file_popup", ImGuiWindowFlags_MenuBar)) - { - if (ImGui::BeginMenuBar()) - { - if (ImGui::BeginMenu("File")) - { - ShowExampleMenuFile(); - ImGui::EndMenu(); - } - if (ImGui::BeginMenu("Edit")) - { - ImGui::MenuItem("Dummy"); - ImGui::EndMenu(); - } - ImGui::EndMenuBar(); - } - ImGui::Text("Hello from popup!"); - ImGui::Button("This is a dummy button.."); - ImGui::EndPopup(); - } - - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Popups/Context menus"); - if (ImGui::TreeNode("Context menus")) - { - HelpMarker("\"Context\" functions are simple helpers to associate a Popup to a given Item or Window identifier."); - - // BeginPopupContextItem() is a helper to provide common/simple popup behavior of essentially doing: - // if (id == 0) - // id = GetItemID(); // Use last item id - // if (IsItemHovered() && IsMouseReleased(ImGuiMouseButton_Right)) - // OpenPopup(id); - // return BeginPopup(id); - // For advanced uses you may want to replicate and customize this code. - // See more details in BeginPopupContextItem(). - - // Example 1 - // When used after an item that has an ID (e.g. Button), we can skip providing an ID to BeginPopupContextItem(), - // and BeginPopupContextItem() will use the last item ID as the popup ID. - { - const char* names[5] = { "Label1", "Label2", "Label3", "Label4", "Label5" }; - static int selected = -1; - for (int n = 0; n < 5; n++) - { - if (ImGui::Selectable(names[n], selected == n)) - selected = n; - if (ImGui::BeginPopupContextItem()) // <-- use last item id as popup id - { - selected = n; - ImGui::Text("This a popup for \"%s\"!", names[n]); - if (ImGui::Button("Close")) - ImGui::CloseCurrentPopup(); - ImGui::EndPopup(); - } - ImGui::SetItemTooltip("Right-click to open popup"); - } - } - - // Example 2 - // Popup on a Text() element which doesn't have an identifier: we need to provide an identifier to BeginPopupContextItem(). - // Using an explicit identifier is also convenient if you want to activate the popups from different locations. - { - HelpMarker("Text() elements don't have stable identifiers so we need to provide one."); - static float value = 0.5f; - ImGui::Text("Value = %.3f <-- (1) right-click this text", value); - if (ImGui::BeginPopupContextItem("my popup")) - { - if (ImGui::Selectable("Set to zero")) value = 0.0f; - if (ImGui::Selectable("Set to PI")) value = 3.1415f; - ImGui::SetNextItemWidth(-FLT_MIN); - ImGui::DragFloat("##Value", &value, 0.1f, 0.0f, 0.0f); - ImGui::EndPopup(); - } - - // We can also use OpenPopupOnItemClick() to toggle the visibility of a given popup. - // Here we make it that right-clicking this other text element opens the same popup as above. - // The popup itself will be submitted by the code above. - ImGui::Text("(2) Or right-click this text"); - ImGui::OpenPopupOnItemClick("my popup", ImGuiPopupFlags_MouseButtonRight); - - // Back to square one: manually open the same popup. - if (ImGui::Button("(3) Or click this button")) - ImGui::OpenPopup("my popup"); - } - - // Example 3 - // When using BeginPopupContextItem() with an implicit identifier (NULL == use last item ID), - // we need to make sure your item identifier is stable. - // In this example we showcase altering the item label while preserving its identifier, using the ### operator (see FAQ). - { - HelpMarker("Showcase using a popup ID linked to item ID, with the item having a changing label + stable ID using the ### operator."); - static char name[32] = "Label1"; - char buf[64]; - sprintf(buf, "Button: %s###Button", name); // ### operator override ID ignoring the preceding label - ImGui::Button(buf); - if (ImGui::BeginPopupContextItem()) - { - ImGui::Text("Edit name:"); - ImGui::InputText("##edit", name, IM_ARRAYSIZE(name)); - if (ImGui::Button("Close")) - ImGui::CloseCurrentPopup(); - ImGui::EndPopup(); - } - ImGui::SameLine(); ImGui::Text("(<-- right-click here)"); - } - - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Popups/Modals"); - if (ImGui::TreeNode("Modals")) - { - ImGui::TextWrapped("Modal windows are like popups but the user cannot close them by clicking outside."); - - if (ImGui::Button("Delete..")) - ImGui::OpenPopup("Delete?"); - - // Always center this window when appearing - ImVec2 center = ImGui::GetMainViewport()->GetCenter(); - ImGui::SetNextWindowPos(center, ImGuiCond_Appearing, ImVec2(0.5f, 0.5f)); - - if (ImGui::BeginPopupModal("Delete?", NULL, ImGuiWindowFlags_AlwaysAutoResize)) - { - ImGui::Text("All those beautiful files will be deleted.\nThis operation cannot be undone!"); - ImGui::Separator(); - - //static int unused_i = 0; - //ImGui::Combo("Combo", &unused_i, "Delete\0Delete harder\0"); - - static bool dont_ask_me_next_time = false; - ImGui::PushStyleVar(ImGuiStyleVar_FramePadding, ImVec2(0, 0)); - ImGui::Checkbox("Don't ask me next time", &dont_ask_me_next_time); - ImGui::PopStyleVar(); - - if (ImGui::Button("OK", ImVec2(120, 0))) { ImGui::CloseCurrentPopup(); } - ImGui::SetItemDefaultFocus(); - ImGui::SameLine(); - if (ImGui::Button("Cancel", ImVec2(120, 0))) { ImGui::CloseCurrentPopup(); } - ImGui::EndPopup(); - } - - if (ImGui::Button("Stacked modals..")) - ImGui::OpenPopup("Stacked 1"); - if (ImGui::BeginPopupModal("Stacked 1", NULL, ImGuiWindowFlags_MenuBar)) - { - if (ImGui::BeginMenuBar()) - { - if (ImGui::BeginMenu("File")) - { - if (ImGui::MenuItem("Some menu item")) {} - ImGui::EndMenu(); - } - ImGui::EndMenuBar(); - } - ImGui::Text("Hello from Stacked The First\nUsing style.Colors[ImGuiCol_ModalWindowDimBg] behind it."); - - // Testing behavior of widgets stacking their own regular popups over the modal. - static int item = 1; - static float color[4] = { 0.4f, 0.7f, 0.0f, 0.5f }; - ImGui::Combo("Combo", &item, "aaaa\0bbbb\0cccc\0dddd\0eeee\0\0"); - ImGui::ColorEdit4("color", color); - - if (ImGui::Button("Add another modal..")) - ImGui::OpenPopup("Stacked 2"); - - // Also demonstrate passing a bool* to BeginPopupModal(), this will create a regular close button which - // will close the popup. Note that the visibility state of popups is owned by imgui, so the input value - // of the bool actually doesn't matter here. - bool unused_open = true; - if (ImGui::BeginPopupModal("Stacked 2", &unused_open)) - { - ImGui::Text("Hello from Stacked The Second!"); - if (ImGui::Button("Close")) - ImGui::CloseCurrentPopup(); - ImGui::EndPopup(); - } - - if (ImGui::Button("Close")) - ImGui::CloseCurrentPopup(); - ImGui::EndPopup(); - } - - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Popups/Menus inside a regular window"); - if (ImGui::TreeNode("Menus inside a regular window")) - { - ImGui::TextWrapped("Below we are testing adding menu items to a regular window. It's rather unusual but should work!"); - ImGui::Separator(); - - ImGui::MenuItem("Menu item", "CTRL+M"); - if (ImGui::BeginMenu("Menu inside a regular window")) - { - ShowExampleMenuFile(); - ImGui::EndMenu(); - } - ImGui::Separator(); - ImGui::TreePop(); - } -} - -// Dummy data structure that we use for the Table demo. -// (pre-C++11 doesn't allow us to instantiate ImVector template if this structure is defined inside the demo function) -namespace -{ -// We are passing our own identifier to TableSetupColumn() to facilitate identifying columns in the sorting code. -// This identifier will be passed down into ImGuiTableSortSpec::ColumnUserID. -// But it is possible to omit the user id parameter of TableSetupColumn() and just use the column index instead! (ImGuiTableSortSpec::ColumnIndex) -// If you don't use sorting, you will generally never care about giving column an ID! -enum MyItemColumnID -{ - MyItemColumnID_ID, - MyItemColumnID_Name, - MyItemColumnID_Action, - MyItemColumnID_Quantity, - MyItemColumnID_Description -}; - -struct MyItem -{ - int ID; - const char* Name; - int Quantity; - - // We have a problem which is affecting _only this demo_ and should not affect your code: - // As we don't rely on std:: or other third-party library to compile dear imgui, we only have reliable access to qsort(), - // however qsort doesn't allow passing user data to comparing function. - // As a workaround, we are storing the sort specs in a static/global for the comparing function to access. - // In your own use case you would probably pass the sort specs to your sorting/comparing functions directly and not use a global. - // We could technically call ImGui::TableGetSortSpecs() in CompareWithSortSpecs(), but considering that this function is called - // very often by the sorting algorithm it would be a little wasteful. - static const ImGuiTableSortSpecs* s_current_sort_specs; - - static void SortWithSortSpecs(ImGuiTableSortSpecs* sort_specs, MyItem* items, int items_count) - { - s_current_sort_specs = sort_specs; // Store in variable accessible by the sort function. - if (items_count > 1) - qsort(items, (size_t)items_count, sizeof(items[0]), MyItem::CompareWithSortSpecs); - s_current_sort_specs = NULL; - } - - // Compare function to be used by qsort() - static int IMGUI_CDECL CompareWithSortSpecs(const void* lhs, const void* rhs) - { - const MyItem* a = (const MyItem*)lhs; - const MyItem* b = (const MyItem*)rhs; - for (int n = 0; n < s_current_sort_specs->SpecsCount; n++) - { - // Here we identify columns using the ColumnUserID value that we ourselves passed to TableSetupColumn() - // We could also choose to identify columns based on their index (sort_spec->ColumnIndex), which is simpler! - const ImGuiTableColumnSortSpecs* sort_spec = &s_current_sort_specs->Specs[n]; - int delta = 0; - switch (sort_spec->ColumnUserID) - { - case MyItemColumnID_ID: delta = (a->ID - b->ID); break; - case MyItemColumnID_Name: delta = (strcmp(a->Name, b->Name)); break; - case MyItemColumnID_Quantity: delta = (a->Quantity - b->Quantity); break; - case MyItemColumnID_Description: delta = (strcmp(a->Name, b->Name)); break; - default: IM_ASSERT(0); break; - } - if (delta > 0) - return (sort_spec->SortDirection == ImGuiSortDirection_Ascending) ? +1 : -1; - if (delta < 0) - return (sort_spec->SortDirection == ImGuiSortDirection_Ascending) ? -1 : +1; - } - - // qsort() is instable so always return a way to differenciate items. - // Your own compare function may want to avoid fallback on implicit sort specs e.g. a Name compare if it wasn't already part of the sort specs. - return (a->ID - b->ID); - } -}; -const ImGuiTableSortSpecs* MyItem::s_current_sort_specs = NULL; -} - -// Make the UI compact because there are so many fields -static void PushStyleCompact() -{ - ImGuiStyle& style = ImGui::GetStyle(); - ImGui::PushStyleVar(ImGuiStyleVar_FramePadding, ImVec2(style.FramePadding.x, (float)(int)(style.FramePadding.y * 0.60f))); - ImGui::PushStyleVar(ImGuiStyleVar_ItemSpacing, ImVec2(style.ItemSpacing.x, (float)(int)(style.ItemSpacing.y * 0.60f))); -} - -static void PopStyleCompact() -{ - ImGui::PopStyleVar(2); -} - -// Show a combo box with a choice of sizing policies -static void EditTableSizingFlags(ImGuiTableFlags* p_flags) -{ - struct EnumDesc { ImGuiTableFlags Value; const char* Name; const char* Tooltip; }; - static const EnumDesc policies[] = - { - { ImGuiTableFlags_None, "Default", "Use default sizing policy:\n- ImGuiTableFlags_SizingFixedFit if ScrollX is on or if host window has ImGuiWindowFlags_AlwaysAutoResize.\n- ImGuiTableFlags_SizingStretchSame otherwise." }, - { ImGuiTableFlags_SizingFixedFit, "ImGuiTableFlags_SizingFixedFit", "Columns default to _WidthFixed (if resizable) or _WidthAuto (if not resizable), matching contents width." }, - { ImGuiTableFlags_SizingFixedSame, "ImGuiTableFlags_SizingFixedSame", "Columns are all the same width, matching the maximum contents width.\nImplicitly disable ImGuiTableFlags_Resizable and enable ImGuiTableFlags_NoKeepColumnsVisible." }, - { ImGuiTableFlags_SizingStretchProp, "ImGuiTableFlags_SizingStretchProp", "Columns default to _WidthStretch with weights proportional to their widths." }, - { ImGuiTableFlags_SizingStretchSame, "ImGuiTableFlags_SizingStretchSame", "Columns default to _WidthStretch with same weights." } - }; - int idx; - for (idx = 0; idx < IM_ARRAYSIZE(policies); idx++) - if (policies[idx].Value == (*p_flags & ImGuiTableFlags_SizingMask_)) - break; - const char* preview_text = (idx < IM_ARRAYSIZE(policies)) ? policies[idx].Name + (idx > 0 ? strlen("ImGuiTableFlags") : 0) : ""; - if (ImGui::BeginCombo("Sizing Policy", preview_text)) - { - for (int n = 0; n < IM_ARRAYSIZE(policies); n++) - if (ImGui::Selectable(policies[n].Name, idx == n)) - *p_flags = (*p_flags & ~ImGuiTableFlags_SizingMask_) | policies[n].Value; - ImGui::EndCombo(); - } - ImGui::SameLine(); - ImGui::TextDisabled("(?)"); - if (ImGui::BeginItemTooltip()) - { - ImGui::PushTextWrapPos(ImGui::GetFontSize() * 50.0f); - for (int m = 0; m < IM_ARRAYSIZE(policies); m++) - { - ImGui::Separator(); - ImGui::Text("%s:", policies[m].Name); - ImGui::Separator(); - ImGui::SetCursorPosX(ImGui::GetCursorPosX() + ImGui::GetStyle().IndentSpacing * 0.5f); - ImGui::TextUnformatted(policies[m].Tooltip); - } - ImGui::PopTextWrapPos(); - ImGui::EndTooltip(); - } -} - -static void EditTableColumnsFlags(ImGuiTableColumnFlags* p_flags) -{ - ImGui::CheckboxFlags("_Disabled", p_flags, ImGuiTableColumnFlags_Disabled); ImGui::SameLine(); HelpMarker("Master disable flag (also hide from context menu)"); - ImGui::CheckboxFlags("_DefaultHide", p_flags, ImGuiTableColumnFlags_DefaultHide); - ImGui::CheckboxFlags("_DefaultSort", p_flags, ImGuiTableColumnFlags_DefaultSort); - if (ImGui::CheckboxFlags("_WidthStretch", p_flags, ImGuiTableColumnFlags_WidthStretch)) - *p_flags &= ~(ImGuiTableColumnFlags_WidthMask_ ^ ImGuiTableColumnFlags_WidthStretch); - if (ImGui::CheckboxFlags("_WidthFixed", p_flags, ImGuiTableColumnFlags_WidthFixed)) - *p_flags &= ~(ImGuiTableColumnFlags_WidthMask_ ^ ImGuiTableColumnFlags_WidthFixed); - ImGui::CheckboxFlags("_NoResize", p_flags, ImGuiTableColumnFlags_NoResize); - ImGui::CheckboxFlags("_NoReorder", p_flags, ImGuiTableColumnFlags_NoReorder); - ImGui::CheckboxFlags("_NoHide", p_flags, ImGuiTableColumnFlags_NoHide); - ImGui::CheckboxFlags("_NoClip", p_flags, ImGuiTableColumnFlags_NoClip); - ImGui::CheckboxFlags("_NoSort", p_flags, ImGuiTableColumnFlags_NoSort); - ImGui::CheckboxFlags("_NoSortAscending", p_flags, ImGuiTableColumnFlags_NoSortAscending); - ImGui::CheckboxFlags("_NoSortDescending", p_flags, ImGuiTableColumnFlags_NoSortDescending); - ImGui::CheckboxFlags("_NoHeaderLabel", p_flags, ImGuiTableColumnFlags_NoHeaderLabel); - ImGui::CheckboxFlags("_NoHeaderWidth", p_flags, ImGuiTableColumnFlags_NoHeaderWidth); - ImGui::CheckboxFlags("_PreferSortAscending", p_flags, ImGuiTableColumnFlags_PreferSortAscending); - ImGui::CheckboxFlags("_PreferSortDescending", p_flags, ImGuiTableColumnFlags_PreferSortDescending); - ImGui::CheckboxFlags("_IndentEnable", p_flags, ImGuiTableColumnFlags_IndentEnable); ImGui::SameLine(); HelpMarker("Default for column 0"); - ImGui::CheckboxFlags("_IndentDisable", p_flags, ImGuiTableColumnFlags_IndentDisable); ImGui::SameLine(); HelpMarker("Default for column >0"); - ImGui::CheckboxFlags("_AngledHeader", p_flags, ImGuiTableColumnFlags_AngledHeader); -} - -static void ShowTableColumnsStatusFlags(ImGuiTableColumnFlags flags) -{ - ImGui::CheckboxFlags("_IsEnabled", &flags, ImGuiTableColumnFlags_IsEnabled); - ImGui::CheckboxFlags("_IsVisible", &flags, ImGuiTableColumnFlags_IsVisible); - ImGui::CheckboxFlags("_IsSorted", &flags, ImGuiTableColumnFlags_IsSorted); - ImGui::CheckboxFlags("_IsHovered", &flags, ImGuiTableColumnFlags_IsHovered); -} - -static void ShowDemoWindowTables() -{ - //ImGui::SetNextItemOpen(true, ImGuiCond_Once); - IMGUI_DEMO_MARKER("Tables"); - if (!ImGui::CollapsingHeader("Tables & Columns")) - return; - - // Using those as a base value to create width/height that are factor of the size of our font - const float TEXT_BASE_WIDTH = ImGui::CalcTextSize("A").x; - const float TEXT_BASE_HEIGHT = ImGui::GetTextLineHeightWithSpacing(); - - ImGui::PushID("Tables"); - - int open_action = -1; - if (ImGui::Button("Expand all")) - open_action = 1; - ImGui::SameLine(); - if (ImGui::Button("Collapse all")) - open_action = 0; - ImGui::SameLine(); - - // Options - static bool disable_indent = false; - ImGui::Checkbox("Disable tree indentation", &disable_indent); - ImGui::SameLine(); - HelpMarker("Disable the indenting of tree nodes so demo tables can use the full window width."); - ImGui::Separator(); - if (disable_indent) - ImGui::PushStyleVar(ImGuiStyleVar_IndentSpacing, 0.0f); - - // About Styling of tables - // Most settings are configured on a per-table basis via the flags passed to BeginTable() and TableSetupColumns APIs. - // There are however a few settings that a shared and part of the ImGuiStyle structure: - // style.CellPadding // Padding within each cell - // style.Colors[ImGuiCol_TableHeaderBg] // Table header background - // style.Colors[ImGuiCol_TableBorderStrong] // Table outer and header borders - // style.Colors[ImGuiCol_TableBorderLight] // Table inner borders - // style.Colors[ImGuiCol_TableRowBg] // Table row background when ImGuiTableFlags_RowBg is enabled (even rows) - // style.Colors[ImGuiCol_TableRowBgAlt] // Table row background when ImGuiTableFlags_RowBg is enabled (odds rows) - - // Demos - if (open_action != -1) - ImGui::SetNextItemOpen(open_action != 0); - IMGUI_DEMO_MARKER("Tables/Basic"); - if (ImGui::TreeNode("Basic")) - { - // Here we will showcase three different ways to output a table. - // They are very simple variations of a same thing! - - // [Method 1] Using TableNextRow() to create a new row, and TableSetColumnIndex() to select the column. - // In many situations, this is the most flexible and easy to use pattern. - HelpMarker("Using TableNextRow() + calling TableSetColumnIndex() _before_ each cell, in a loop."); - if (ImGui::BeginTable("table1", 3)) - { - for (int row = 0; row < 4; row++) - { - ImGui::TableNextRow(); - for (int column = 0; column < 3; column++) - { - ImGui::TableSetColumnIndex(column); - ImGui::Text("Row %d Column %d", row, column); - } - } - ImGui::EndTable(); - } - - // [Method 2] Using TableNextColumn() called multiple times, instead of using a for loop + TableSetColumnIndex(). - // This is generally more convenient when you have code manually submitting the contents of each column. - HelpMarker("Using TableNextRow() + calling TableNextColumn() _before_ each cell, manually."); - if (ImGui::BeginTable("table2", 3)) - { - for (int row = 0; row < 4; row++) - { - ImGui::TableNextRow(); - ImGui::TableNextColumn(); - ImGui::Text("Row %d", row); - ImGui::TableNextColumn(); - ImGui::Text("Some contents"); - ImGui::TableNextColumn(); - ImGui::Text("123.456"); - } - ImGui::EndTable(); - } - - // [Method 3] We call TableNextColumn() _before_ each cell. We never call TableNextRow(), - // as TableNextColumn() will automatically wrap around and create new rows as needed. - // This is generally more convenient when your cells all contains the same type of data. - HelpMarker( - "Only using TableNextColumn(), which tends to be convenient for tables where every cell contains the same type of contents.\n" - "This is also more similar to the old NextColumn() function of the Columns API, and provided to facilitate the Columns->Tables API transition."); - if (ImGui::BeginTable("table3", 3)) - { - for (int item = 0; item < 14; item++) - { - ImGui::TableNextColumn(); - ImGui::Text("Item %d", item); - } - ImGui::EndTable(); - } - - ImGui::TreePop(); - } - - if (open_action != -1) - ImGui::SetNextItemOpen(open_action != 0); - IMGUI_DEMO_MARKER("Tables/Borders, background"); - if (ImGui::TreeNode("Borders, background")) - { - // Expose a few Borders related flags interactively - enum ContentsType { CT_Text, CT_FillButton }; - static ImGuiTableFlags flags = ImGuiTableFlags_Borders | ImGuiTableFlags_RowBg; - static bool display_headers = false; - static int contents_type = CT_Text; - - PushStyleCompact(); - ImGui::CheckboxFlags("ImGuiTableFlags_RowBg", &flags, ImGuiTableFlags_RowBg); - ImGui::CheckboxFlags("ImGuiTableFlags_Borders", &flags, ImGuiTableFlags_Borders); - ImGui::SameLine(); HelpMarker("ImGuiTableFlags_Borders\n = ImGuiTableFlags_BordersInnerV\n | ImGuiTableFlags_BordersOuterV\n | ImGuiTableFlags_BordersInnerV\n | ImGuiTableFlags_BordersOuterH"); - ImGui::Indent(); - - ImGui::CheckboxFlags("ImGuiTableFlags_BordersH", &flags, ImGuiTableFlags_BordersH); - ImGui::Indent(); - ImGui::CheckboxFlags("ImGuiTableFlags_BordersOuterH", &flags, ImGuiTableFlags_BordersOuterH); - ImGui::CheckboxFlags("ImGuiTableFlags_BordersInnerH", &flags, ImGuiTableFlags_BordersInnerH); - ImGui::Unindent(); - - ImGui::CheckboxFlags("ImGuiTableFlags_BordersV", &flags, ImGuiTableFlags_BordersV); - ImGui::Indent(); - ImGui::CheckboxFlags("ImGuiTableFlags_BordersOuterV", &flags, ImGuiTableFlags_BordersOuterV); - ImGui::CheckboxFlags("ImGuiTableFlags_BordersInnerV", &flags, ImGuiTableFlags_BordersInnerV); - ImGui::Unindent(); - - ImGui::CheckboxFlags("ImGuiTableFlags_BordersOuter", &flags, ImGuiTableFlags_BordersOuter); - ImGui::CheckboxFlags("ImGuiTableFlags_BordersInner", &flags, ImGuiTableFlags_BordersInner); - ImGui::Unindent(); - - ImGui::AlignTextToFramePadding(); ImGui::Text("Cell contents:"); - ImGui::SameLine(); ImGui::RadioButton("Text", &contents_type, CT_Text); - ImGui::SameLine(); ImGui::RadioButton("FillButton", &contents_type, CT_FillButton); - ImGui::Checkbox("Display headers", &display_headers); - ImGui::CheckboxFlags("ImGuiTableFlags_NoBordersInBody", &flags, ImGuiTableFlags_NoBordersInBody); ImGui::SameLine(); HelpMarker("Disable vertical borders in columns Body (borders will always appear in Headers"); - PopStyleCompact(); - - if (ImGui::BeginTable("table1", 3, flags)) - { - // Display headers so we can inspect their interaction with borders. - // (Headers are not the main purpose of this section of the demo, so we are not elaborating on them too much. See other sections for details) - if (display_headers) - { - ImGui::TableSetupColumn("One"); - ImGui::TableSetupColumn("Two"); - ImGui::TableSetupColumn("Three"); - ImGui::TableHeadersRow(); - } - - for (int row = 0; row < 5; row++) - { - ImGui::TableNextRow(); - for (int column = 0; column < 3; column++) - { - ImGui::TableSetColumnIndex(column); - char buf[32]; - sprintf(buf, "Hello %d,%d", column, row); - if (contents_type == CT_Text) - ImGui::TextUnformatted(buf); - else if (contents_type == CT_FillButton) - ImGui::Button(buf, ImVec2(-FLT_MIN, 0.0f)); - } - } - ImGui::EndTable(); - } - ImGui::TreePop(); - } - - if (open_action != -1) - ImGui::SetNextItemOpen(open_action != 0); - IMGUI_DEMO_MARKER("Tables/Resizable, stretch"); - if (ImGui::TreeNode("Resizable, stretch")) - { - // By default, if we don't enable ScrollX the sizing policy for each column is "Stretch" - // All columns maintain a sizing weight, and they will occupy all available width. - static ImGuiTableFlags flags = ImGuiTableFlags_SizingStretchSame | ImGuiTableFlags_Resizable | ImGuiTableFlags_BordersOuter | ImGuiTableFlags_BordersV | ImGuiTableFlags_ContextMenuInBody; - PushStyleCompact(); - ImGui::CheckboxFlags("ImGuiTableFlags_Resizable", &flags, ImGuiTableFlags_Resizable); - ImGui::CheckboxFlags("ImGuiTableFlags_BordersV", &flags, ImGuiTableFlags_BordersV); - ImGui::SameLine(); HelpMarker("Using the _Resizable flag automatically enables the _BordersInnerV flag as well, this is why the resize borders are still showing when unchecking this."); - PopStyleCompact(); - - if (ImGui::BeginTable("table1", 3, flags)) - { - for (int row = 0; row < 5; row++) - { - ImGui::TableNextRow(); - for (int column = 0; column < 3; column++) - { - ImGui::TableSetColumnIndex(column); - ImGui::Text("Hello %d,%d", column, row); - } - } - ImGui::EndTable(); - } - ImGui::TreePop(); - } - - if (open_action != -1) - ImGui::SetNextItemOpen(open_action != 0); - IMGUI_DEMO_MARKER("Tables/Resizable, fixed"); - if (ImGui::TreeNode("Resizable, fixed")) - { - // Here we use ImGuiTableFlags_SizingFixedFit (even though _ScrollX is not set) - // So columns will adopt the "Fixed" policy and will maintain a fixed width regardless of the whole available width (unless table is small) - // If there is not enough available width to fit all columns, they will however be resized down. - // FIXME-TABLE: Providing a stretch-on-init would make sense especially for tables which don't have saved settings - HelpMarker( - "Using _Resizable + _SizingFixedFit flags.\n" - "Fixed-width columns generally makes more sense if you want to use horizontal scrolling.\n\n" - "Double-click a column border to auto-fit the column to its contents."); - PushStyleCompact(); - static ImGuiTableFlags flags = ImGuiTableFlags_SizingFixedFit | ImGuiTableFlags_Resizable | ImGuiTableFlags_BordersOuter | ImGuiTableFlags_BordersV | ImGuiTableFlags_ContextMenuInBody; - ImGui::CheckboxFlags("ImGuiTableFlags_NoHostExtendX", &flags, ImGuiTableFlags_NoHostExtendX); - PopStyleCompact(); - - if (ImGui::BeginTable("table1", 3, flags)) - { - for (int row = 0; row < 5; row++) - { - ImGui::TableNextRow(); - for (int column = 0; column < 3; column++) - { - ImGui::TableSetColumnIndex(column); - ImGui::Text("Hello %d,%d", column, row); - } - } - ImGui::EndTable(); - } - ImGui::TreePop(); - } - - if (open_action != -1) - ImGui::SetNextItemOpen(open_action != 0); - IMGUI_DEMO_MARKER("Tables/Resizable, mixed"); - if (ImGui::TreeNode("Resizable, mixed")) - { - HelpMarker( - "Using TableSetupColumn() to alter resizing policy on a per-column basis.\n\n" - "When combining Fixed and Stretch columns, generally you only want one, maybe two trailing columns to use _WidthStretch."); - static ImGuiTableFlags flags = ImGuiTableFlags_SizingFixedFit | ImGuiTableFlags_RowBg | ImGuiTableFlags_Borders | ImGuiTableFlags_Resizable | ImGuiTableFlags_Reorderable | ImGuiTableFlags_Hideable; - - if (ImGui::BeginTable("table1", 3, flags)) - { - ImGui::TableSetupColumn("AAA", ImGuiTableColumnFlags_WidthFixed); - ImGui::TableSetupColumn("BBB", ImGuiTableColumnFlags_WidthFixed); - ImGui::TableSetupColumn("CCC", ImGuiTableColumnFlags_WidthStretch); - ImGui::TableHeadersRow(); - for (int row = 0; row < 5; row++) - { - ImGui::TableNextRow(); - for (int column = 0; column < 3; column++) - { - ImGui::TableSetColumnIndex(column); - ImGui::Text("%s %d,%d", (column == 2) ? "Stretch" : "Fixed", column, row); - } - } - ImGui::EndTable(); - } - if (ImGui::BeginTable("table2", 6, flags)) - { - ImGui::TableSetupColumn("AAA", ImGuiTableColumnFlags_WidthFixed); - ImGui::TableSetupColumn("BBB", ImGuiTableColumnFlags_WidthFixed); - ImGui::TableSetupColumn("CCC", ImGuiTableColumnFlags_WidthFixed | ImGuiTableColumnFlags_DefaultHide); - ImGui::TableSetupColumn("DDD", ImGuiTableColumnFlags_WidthStretch); - ImGui::TableSetupColumn("EEE", ImGuiTableColumnFlags_WidthStretch); - ImGui::TableSetupColumn("FFF", ImGuiTableColumnFlags_WidthStretch | ImGuiTableColumnFlags_DefaultHide); - ImGui::TableHeadersRow(); - for (int row = 0; row < 5; row++) - { - ImGui::TableNextRow(); - for (int column = 0; column < 6; column++) - { - ImGui::TableSetColumnIndex(column); - ImGui::Text("%s %d,%d", (column >= 3) ? "Stretch" : "Fixed", column, row); - } - } - ImGui::EndTable(); - } - ImGui::TreePop(); - } - - if (open_action != -1) - ImGui::SetNextItemOpen(open_action != 0); - IMGUI_DEMO_MARKER("Tables/Reorderable, hideable, with headers"); - if (ImGui::TreeNode("Reorderable, hideable, with headers")) - { - HelpMarker( - "Click and drag column headers to reorder columns.\n\n" - "Right-click on a header to open a context menu."); - static ImGuiTableFlags flags = ImGuiTableFlags_Resizable | ImGuiTableFlags_Reorderable | ImGuiTableFlags_Hideable | ImGuiTableFlags_BordersOuter | ImGuiTableFlags_BordersV; - PushStyleCompact(); - ImGui::CheckboxFlags("ImGuiTableFlags_Resizable", &flags, ImGuiTableFlags_Resizable); - ImGui::CheckboxFlags("ImGuiTableFlags_Reorderable", &flags, ImGuiTableFlags_Reorderable); - ImGui::CheckboxFlags("ImGuiTableFlags_Hideable", &flags, ImGuiTableFlags_Hideable); - ImGui::CheckboxFlags("ImGuiTableFlags_NoBordersInBody", &flags, ImGuiTableFlags_NoBordersInBody); - ImGui::CheckboxFlags("ImGuiTableFlags_NoBordersInBodyUntilResize", &flags, ImGuiTableFlags_NoBordersInBodyUntilResize); ImGui::SameLine(); HelpMarker("Disable vertical borders in columns Body until hovered for resize (borders will always appear in Headers)"); - ImGui::CheckboxFlags("ImGuiTableFlags_HighlightHoveredColumn", &flags, ImGuiTableFlags_HighlightHoveredColumn); - PopStyleCompact(); - - if (ImGui::BeginTable("table1", 3, flags)) - { - // Submit columns name with TableSetupColumn() and call TableHeadersRow() to create a row with a header in each column. - // (Later we will show how TableSetupColumn() has other uses, optional flags, sizing weight etc.) - ImGui::TableSetupColumn("One"); - ImGui::TableSetupColumn("Two"); - ImGui::TableSetupColumn("Three"); - ImGui::TableHeadersRow(); - for (int row = 0; row < 6; row++) - { - ImGui::TableNextRow(); - for (int column = 0; column < 3; column++) - { - ImGui::TableSetColumnIndex(column); - ImGui::Text("Hello %d,%d", column, row); - } - } - ImGui::EndTable(); - } - - // Use outer_size.x == 0.0f instead of default to make the table as tight as possible (only valid when no scrolling and no stretch column) - if (ImGui::BeginTable("table2", 3, flags | ImGuiTableFlags_SizingFixedFit, ImVec2(0.0f, 0.0f))) - { - ImGui::TableSetupColumn("One"); - ImGui::TableSetupColumn("Two"); - ImGui::TableSetupColumn("Three"); - ImGui::TableHeadersRow(); - for (int row = 0; row < 6; row++) - { - ImGui::TableNextRow(); - for (int column = 0; column < 3; column++) - { - ImGui::TableSetColumnIndex(column); - ImGui::Text("Fixed %d,%d", column, row); - } - } - ImGui::EndTable(); - } - ImGui::TreePop(); - } - - if (open_action != -1) - ImGui::SetNextItemOpen(open_action != 0); - IMGUI_DEMO_MARKER("Tables/Padding"); - if (ImGui::TreeNode("Padding")) - { - // First example: showcase use of padding flags and effect of BorderOuterV/BorderInnerV on X padding. - // We don't expose BorderOuterH/BorderInnerH here because they have no effect on X padding. - HelpMarker( - "We often want outer padding activated when any using features which makes the edges of a column visible:\n" - "e.g.:\n" - "- BorderOuterV\n" - "- any form of row selection\n" - "Because of this, activating BorderOuterV sets the default to PadOuterX. Using PadOuterX or NoPadOuterX you can override the default.\n\n" - "Actual padding values are using style.CellPadding.\n\n" - "In this demo we don't show horizontal borders to emphasize how they don't affect default horizontal padding."); - - static ImGuiTableFlags flags1 = ImGuiTableFlags_BordersV; - PushStyleCompact(); - ImGui::CheckboxFlags("ImGuiTableFlags_PadOuterX", &flags1, ImGuiTableFlags_PadOuterX); - ImGui::SameLine(); HelpMarker("Enable outer-most padding (default if ImGuiTableFlags_BordersOuterV is set)"); - ImGui::CheckboxFlags("ImGuiTableFlags_NoPadOuterX", &flags1, ImGuiTableFlags_NoPadOuterX); - ImGui::SameLine(); HelpMarker("Disable outer-most padding (default if ImGuiTableFlags_BordersOuterV is not set)"); - ImGui::CheckboxFlags("ImGuiTableFlags_NoPadInnerX", &flags1, ImGuiTableFlags_NoPadInnerX); - ImGui::SameLine(); HelpMarker("Disable inner padding between columns (double inner padding if BordersOuterV is on, single inner padding if BordersOuterV is off)"); - ImGui::CheckboxFlags("ImGuiTableFlags_BordersOuterV", &flags1, ImGuiTableFlags_BordersOuterV); - ImGui::CheckboxFlags("ImGuiTableFlags_BordersInnerV", &flags1, ImGuiTableFlags_BordersInnerV); - static bool show_headers = false; - ImGui::Checkbox("show_headers", &show_headers); - PopStyleCompact(); - - if (ImGui::BeginTable("table_padding", 3, flags1)) - { - if (show_headers) - { - ImGui::TableSetupColumn("One"); - ImGui::TableSetupColumn("Two"); - ImGui::TableSetupColumn("Three"); - ImGui::TableHeadersRow(); - } - - for (int row = 0; row < 5; row++) - { - ImGui::TableNextRow(); - for (int column = 0; column < 3; column++) - { - ImGui::TableSetColumnIndex(column); - if (row == 0) - { - ImGui::Text("Avail %.2f", ImGui::GetContentRegionAvail().x); - } - else - { - char buf[32]; - sprintf(buf, "Hello %d,%d", column, row); - ImGui::Button(buf, ImVec2(-FLT_MIN, 0.0f)); - } - //if (ImGui::TableGetColumnFlags() & ImGuiTableColumnFlags_IsHovered) - // ImGui::TableSetBgColor(ImGuiTableBgTarget_CellBg, IM_COL32(0, 100, 0, 255)); - } - } - ImGui::EndTable(); - } - - // Second example: set style.CellPadding to (0.0) or a custom value. - // FIXME-TABLE: Vertical border effectively not displayed the same way as horizontal one... - HelpMarker("Setting style.CellPadding to (0,0) or a custom value."); - static ImGuiTableFlags flags2 = ImGuiTableFlags_Borders | ImGuiTableFlags_RowBg; - static ImVec2 cell_padding(0.0f, 0.0f); - static bool show_widget_frame_bg = true; - - PushStyleCompact(); - ImGui::CheckboxFlags("ImGuiTableFlags_Borders", &flags2, ImGuiTableFlags_Borders); - ImGui::CheckboxFlags("ImGuiTableFlags_BordersH", &flags2, ImGuiTableFlags_BordersH); - ImGui::CheckboxFlags("ImGuiTableFlags_BordersV", &flags2, ImGuiTableFlags_BordersV); - ImGui::CheckboxFlags("ImGuiTableFlags_BordersInner", &flags2, ImGuiTableFlags_BordersInner); - ImGui::CheckboxFlags("ImGuiTableFlags_BordersOuter", &flags2, ImGuiTableFlags_BordersOuter); - ImGui::CheckboxFlags("ImGuiTableFlags_RowBg", &flags2, ImGuiTableFlags_RowBg); - ImGui::CheckboxFlags("ImGuiTableFlags_Resizable", &flags2, ImGuiTableFlags_Resizable); - ImGui::Checkbox("show_widget_frame_bg", &show_widget_frame_bg); - ImGui::SliderFloat2("CellPadding", &cell_padding.x, 0.0f, 10.0f, "%.0f"); - PopStyleCompact(); - - ImGui::PushStyleVar(ImGuiStyleVar_CellPadding, cell_padding); - if (ImGui::BeginTable("table_padding_2", 3, flags2)) - { - static char text_bufs[3 * 5][16]; // Mini text storage for 3x5 cells - static bool init = true; - if (!show_widget_frame_bg) - ImGui::PushStyleColor(ImGuiCol_FrameBg, 0); - for (int cell = 0; cell < 3 * 5; cell++) - { - ImGui::TableNextColumn(); - if (init) - strcpy(text_bufs[cell], "edit me"); - ImGui::SetNextItemWidth(-FLT_MIN); - ImGui::PushID(cell); - ImGui::InputText("##cell", text_bufs[cell], IM_ARRAYSIZE(text_bufs[cell])); - ImGui::PopID(); - } - if (!show_widget_frame_bg) - ImGui::PopStyleColor(); - init = false; - ImGui::EndTable(); - } - ImGui::PopStyleVar(); - - ImGui::TreePop(); - } - - if (open_action != -1) - ImGui::SetNextItemOpen(open_action != 0); - IMGUI_DEMO_MARKER("Tables/Explicit widths"); - if (ImGui::TreeNode("Sizing policies")) - { - static ImGuiTableFlags flags1 = ImGuiTableFlags_BordersV | ImGuiTableFlags_BordersOuterH | ImGuiTableFlags_RowBg | ImGuiTableFlags_ContextMenuInBody; - PushStyleCompact(); - ImGui::CheckboxFlags("ImGuiTableFlags_Resizable", &flags1, ImGuiTableFlags_Resizable); - ImGui::CheckboxFlags("ImGuiTableFlags_NoHostExtendX", &flags1, ImGuiTableFlags_NoHostExtendX); - PopStyleCompact(); - - static ImGuiTableFlags sizing_policy_flags[4] = { ImGuiTableFlags_SizingFixedFit, ImGuiTableFlags_SizingFixedSame, ImGuiTableFlags_SizingStretchProp, ImGuiTableFlags_SizingStretchSame }; - for (int table_n = 0; table_n < 4; table_n++) - { - ImGui::PushID(table_n); - ImGui::SetNextItemWidth(TEXT_BASE_WIDTH * 30); - EditTableSizingFlags(&sizing_policy_flags[table_n]); - - // To make it easier to understand the different sizing policy, - // For each policy: we display one table where the columns have equal contents width, and one where the columns have different contents width. - if (ImGui::BeginTable("table1", 3, sizing_policy_flags[table_n] | flags1)) - { - for (int row = 0; row < 3; row++) - { - ImGui::TableNextRow(); - ImGui::TableNextColumn(); ImGui::Text("Oh dear"); - ImGui::TableNextColumn(); ImGui::Text("Oh dear"); - ImGui::TableNextColumn(); ImGui::Text("Oh dear"); - } - ImGui::EndTable(); - } - if (ImGui::BeginTable("table2", 3, sizing_policy_flags[table_n] | flags1)) - { - for (int row = 0; row < 3; row++) - { - ImGui::TableNextRow(); - ImGui::TableNextColumn(); ImGui::Text("AAAA"); - ImGui::TableNextColumn(); ImGui::Text("BBBBBBBB"); - ImGui::TableNextColumn(); ImGui::Text("CCCCCCCCCCCC"); - } - ImGui::EndTable(); - } - ImGui::PopID(); - } - - ImGui::Spacing(); - ImGui::TextUnformatted("Advanced"); - ImGui::SameLine(); - HelpMarker("This section allows you to interact and see the effect of various sizing policies depending on whether Scroll is enabled and the contents of your columns."); - - enum ContentsType { CT_ShowWidth, CT_ShortText, CT_LongText, CT_Button, CT_FillButton, CT_InputText }; - static ImGuiTableFlags flags = ImGuiTableFlags_ScrollY | ImGuiTableFlags_Borders | ImGuiTableFlags_RowBg | ImGuiTableFlags_Resizable; - static int contents_type = CT_ShowWidth; - static int column_count = 3; - - PushStyleCompact(); - ImGui::PushID("Advanced"); - ImGui::PushItemWidth(TEXT_BASE_WIDTH * 30); - EditTableSizingFlags(&flags); - ImGui::Combo("Contents", &contents_type, "Show width\0Short Text\0Long Text\0Button\0Fill Button\0InputText\0"); - if (contents_type == CT_FillButton) - { - ImGui::SameLine(); - HelpMarker("Be mindful that using right-alignment (e.g. size.x = -FLT_MIN) creates a feedback loop where contents width can feed into auto-column width can feed into contents width."); - } - ImGui::DragInt("Columns", &column_count, 0.1f, 1, 64, "%d", ImGuiSliderFlags_AlwaysClamp); - ImGui::CheckboxFlags("ImGuiTableFlags_Resizable", &flags, ImGuiTableFlags_Resizable); - ImGui::CheckboxFlags("ImGuiTableFlags_PreciseWidths", &flags, ImGuiTableFlags_PreciseWidths); - ImGui::SameLine(); HelpMarker("Disable distributing remainder width to stretched columns (width allocation on a 100-wide table with 3 columns: Without this flag: 33,33,34. With this flag: 33,33,33). With larger number of columns, resizing will appear to be less smooth."); - ImGui::CheckboxFlags("ImGuiTableFlags_ScrollX", &flags, ImGuiTableFlags_ScrollX); - ImGui::CheckboxFlags("ImGuiTableFlags_ScrollY", &flags, ImGuiTableFlags_ScrollY); - ImGui::CheckboxFlags("ImGuiTableFlags_NoClip", &flags, ImGuiTableFlags_NoClip); - ImGui::PopItemWidth(); - ImGui::PopID(); - PopStyleCompact(); - - if (ImGui::BeginTable("table2", column_count, flags, ImVec2(0.0f, TEXT_BASE_HEIGHT * 7))) - { - for (int cell = 0; cell < 10 * column_count; cell++) - { - ImGui::TableNextColumn(); - int column = ImGui::TableGetColumnIndex(); - int row = ImGui::TableGetRowIndex(); - - ImGui::PushID(cell); - char label[32]; - static char text_buf[32] = ""; - sprintf(label, "Hello %d,%d", column, row); - switch (contents_type) - { - case CT_ShortText: ImGui::TextUnformatted(label); break; - case CT_LongText: ImGui::Text("Some %s text %d,%d\nOver two lines..", column == 0 ? "long" : "longeeer", column, row); break; - case CT_ShowWidth: ImGui::Text("W: %.1f", ImGui::GetContentRegionAvail().x); break; - case CT_Button: ImGui::Button(label); break; - case CT_FillButton: ImGui::Button(label, ImVec2(-FLT_MIN, 0.0f)); break; - case CT_InputText: ImGui::SetNextItemWidth(-FLT_MIN); ImGui::InputText("##", text_buf, IM_ARRAYSIZE(text_buf)); break; - } - ImGui::PopID(); - } - ImGui::EndTable(); - } - ImGui::TreePop(); - } - - if (open_action != -1) - ImGui::SetNextItemOpen(open_action != 0); - IMGUI_DEMO_MARKER("Tables/Vertical scrolling, with clipping"); - if (ImGui::TreeNode("Vertical scrolling, with clipping")) - { - HelpMarker("Here we activate ScrollY, which will create a child window container to allow hosting scrollable contents.\n\nWe also demonstrate using ImGuiListClipper to virtualize the submission of many items."); - static ImGuiTableFlags flags = ImGuiTableFlags_ScrollY | ImGuiTableFlags_RowBg | ImGuiTableFlags_BordersOuter | ImGuiTableFlags_BordersV | ImGuiTableFlags_Resizable | ImGuiTableFlags_Reorderable | ImGuiTableFlags_Hideable; - - PushStyleCompact(); - ImGui::CheckboxFlags("ImGuiTableFlags_ScrollY", &flags, ImGuiTableFlags_ScrollY); - PopStyleCompact(); - - // When using ScrollX or ScrollY we need to specify a size for our table container! - // Otherwise by default the table will fit all available space, like a BeginChild() call. - ImVec2 outer_size = ImVec2(0.0f, TEXT_BASE_HEIGHT * 8); - if (ImGui::BeginTable("table_scrolly", 3, flags, outer_size)) - { - ImGui::TableSetupScrollFreeze(0, 1); // Make top row always visible - ImGui::TableSetupColumn("One", ImGuiTableColumnFlags_None); - ImGui::TableSetupColumn("Two", ImGuiTableColumnFlags_None); - ImGui::TableSetupColumn("Three", ImGuiTableColumnFlags_None); - ImGui::TableHeadersRow(); - - // Demonstrate using clipper for large vertical lists - ImGuiListClipper clipper; - clipper.Begin(1000); - while (clipper.Step()) - { - for (int row = clipper.DisplayStart; row < clipper.DisplayEnd; row++) - { - ImGui::TableNextRow(); - for (int column = 0; column < 3; column++) - { - ImGui::TableSetColumnIndex(column); - ImGui::Text("Hello %d,%d", column, row); - } - } - } - ImGui::EndTable(); - } - ImGui::TreePop(); - } - - if (open_action != -1) - ImGui::SetNextItemOpen(open_action != 0); - IMGUI_DEMO_MARKER("Tables/Horizontal scrolling"); - if (ImGui::TreeNode("Horizontal scrolling")) - { - HelpMarker( - "When ScrollX is enabled, the default sizing policy becomes ImGuiTableFlags_SizingFixedFit, " - "as automatically stretching columns doesn't make much sense with horizontal scrolling.\n\n" - "Also note that as of the current version, you will almost always want to enable ScrollY along with ScrollX," - "because the container window won't automatically extend vertically to fix contents (this may be improved in future versions)."); - static ImGuiTableFlags flags = ImGuiTableFlags_ScrollX | ImGuiTableFlags_ScrollY | ImGuiTableFlags_RowBg | ImGuiTableFlags_BordersOuter | ImGuiTableFlags_BordersV | ImGuiTableFlags_Resizable | ImGuiTableFlags_Reorderable | ImGuiTableFlags_Hideable; - static int freeze_cols = 1; - static int freeze_rows = 1; - - PushStyleCompact(); - ImGui::CheckboxFlags("ImGuiTableFlags_Resizable", &flags, ImGuiTableFlags_Resizable); - ImGui::CheckboxFlags("ImGuiTableFlags_ScrollX", &flags, ImGuiTableFlags_ScrollX); - ImGui::CheckboxFlags("ImGuiTableFlags_ScrollY", &flags, ImGuiTableFlags_ScrollY); - ImGui::SetNextItemWidth(ImGui::GetFrameHeight()); - ImGui::DragInt("freeze_cols", &freeze_cols, 0.2f, 0, 9, NULL, ImGuiSliderFlags_NoInput); - ImGui::SetNextItemWidth(ImGui::GetFrameHeight()); - ImGui::DragInt("freeze_rows", &freeze_rows, 0.2f, 0, 9, NULL, ImGuiSliderFlags_NoInput); - PopStyleCompact(); - - // When using ScrollX or ScrollY we need to specify a size for our table container! - // Otherwise by default the table will fit all available space, like a BeginChild() call. - ImVec2 outer_size = ImVec2(0.0f, TEXT_BASE_HEIGHT * 8); - if (ImGui::BeginTable("table_scrollx", 7, flags, outer_size)) - { - ImGui::TableSetupScrollFreeze(freeze_cols, freeze_rows); - ImGui::TableSetupColumn("Line #", ImGuiTableColumnFlags_NoHide); // Make the first column not hideable to match our use of TableSetupScrollFreeze() - ImGui::TableSetupColumn("One"); - ImGui::TableSetupColumn("Two"); - ImGui::TableSetupColumn("Three"); - ImGui::TableSetupColumn("Four"); - ImGui::TableSetupColumn("Five"); - ImGui::TableSetupColumn("Six"); - ImGui::TableHeadersRow(); - for (int row = 0; row < 20; row++) - { - ImGui::TableNextRow(); - for (int column = 0; column < 7; column++) - { - // Both TableNextColumn() and TableSetColumnIndex() return true when a column is visible or performing width measurement. - // Because here we know that: - // - A) all our columns are contributing the same to row height - // - B) column 0 is always visible, - // We only always submit this one column and can skip others. - // More advanced per-column clipping behaviors may benefit from polling the status flags via TableGetColumnFlags(). - if (!ImGui::TableSetColumnIndex(column) && column > 0) - continue; - if (column == 0) - ImGui::Text("Line %d", row); - else - ImGui::Text("Hello world %d,%d", column, row); - } - } - ImGui::EndTable(); - } - - ImGui::Spacing(); - ImGui::TextUnformatted("Stretch + ScrollX"); - ImGui::SameLine(); - HelpMarker( - "Showcase using Stretch columns + ScrollX together: " - "this is rather unusual and only makes sense when specifying an 'inner_width' for the table!\n" - "Without an explicit value, inner_width is == outer_size.x and therefore using Stretch columns + ScrollX together doesn't make sense."); - static ImGuiTableFlags flags2 = ImGuiTableFlags_SizingStretchSame | ImGuiTableFlags_ScrollX | ImGuiTableFlags_ScrollY | ImGuiTableFlags_BordersOuter | ImGuiTableFlags_RowBg | ImGuiTableFlags_ContextMenuInBody; - static float inner_width = 1000.0f; - PushStyleCompact(); - ImGui::PushID("flags3"); - ImGui::PushItemWidth(TEXT_BASE_WIDTH * 30); - ImGui::CheckboxFlags("ImGuiTableFlags_ScrollX", &flags2, ImGuiTableFlags_ScrollX); - ImGui::DragFloat("inner_width", &inner_width, 1.0f, 0.0f, FLT_MAX, "%.1f"); - ImGui::PopItemWidth(); - ImGui::PopID(); - PopStyleCompact(); - if (ImGui::BeginTable("table2", 7, flags2, outer_size, inner_width)) - { - for (int cell = 0; cell < 20 * 7; cell++) - { - ImGui::TableNextColumn(); - ImGui::Text("Hello world %d,%d", ImGui::TableGetColumnIndex(), ImGui::TableGetRowIndex()); - } - ImGui::EndTable(); - } - ImGui::TreePop(); - } - - if (open_action != -1) - ImGui::SetNextItemOpen(open_action != 0); - IMGUI_DEMO_MARKER("Tables/Columns flags"); - if (ImGui::TreeNode("Columns flags")) - { - // Create a first table just to show all the options/flags we want to make visible in our example! - const int column_count = 3; - const char* column_names[column_count] = { "One", "Two", "Three" }; - static ImGuiTableColumnFlags column_flags[column_count] = { ImGuiTableColumnFlags_DefaultSort, ImGuiTableColumnFlags_None, ImGuiTableColumnFlags_DefaultHide }; - static ImGuiTableColumnFlags column_flags_out[column_count] = { 0, 0, 0 }; // Output from TableGetColumnFlags() - - if (ImGui::BeginTable("table_columns_flags_checkboxes", column_count, ImGuiTableFlags_None)) - { - PushStyleCompact(); - for (int column = 0; column < column_count; column++) - { - ImGui::TableNextColumn(); - ImGui::PushID(column); - ImGui::AlignTextToFramePadding(); // FIXME-TABLE: Workaround for wrong text baseline propagation across columns - ImGui::Text("'%s'", column_names[column]); - ImGui::Spacing(); - ImGui::Text("Input flags:"); - EditTableColumnsFlags(&column_flags[column]); - ImGui::Spacing(); - ImGui::Text("Output flags:"); - ImGui::BeginDisabled(); - ShowTableColumnsStatusFlags(column_flags_out[column]); - ImGui::EndDisabled(); - ImGui::PopID(); - } - PopStyleCompact(); - ImGui::EndTable(); - } - - // Create the real table we care about for the example! - // We use a scrolling table to be able to showcase the difference between the _IsEnabled and _IsVisible flags above, otherwise in - // a non-scrolling table columns are always visible (unless using ImGuiTableFlags_NoKeepColumnsVisible + resizing the parent window down) - const ImGuiTableFlags flags - = ImGuiTableFlags_SizingFixedFit | ImGuiTableFlags_ScrollX | ImGuiTableFlags_ScrollY - | ImGuiTableFlags_RowBg | ImGuiTableFlags_BordersOuter | ImGuiTableFlags_BordersV - | ImGuiTableFlags_Resizable | ImGuiTableFlags_Reorderable | ImGuiTableFlags_Hideable | ImGuiTableFlags_Sortable; - ImVec2 outer_size = ImVec2(0.0f, TEXT_BASE_HEIGHT * 9); - if (ImGui::BeginTable("table_columns_flags", column_count, flags, outer_size)) - { - bool has_angled_header = false; - for (int column = 0; column < column_count; column++) - { - has_angled_header |= (column_flags[column] & ImGuiTableColumnFlags_AngledHeader) != 0; - ImGui::TableSetupColumn(column_names[column], column_flags[column]); - } - if (has_angled_header) - ImGui::TableAngledHeadersRow(); - ImGui::TableHeadersRow(); - for (int column = 0; column < column_count; column++) - column_flags_out[column] = ImGui::TableGetColumnFlags(column); - float indent_step = (float)((int)TEXT_BASE_WIDTH / 2); - for (int row = 0; row < 8; row++) - { - ImGui::Indent(indent_step); // Add some indentation to demonstrate usage of per-column IndentEnable/IndentDisable flags. - ImGui::TableNextRow(); - for (int column = 0; column < column_count; column++) - { - ImGui::TableSetColumnIndex(column); - ImGui::Text("%s %s", (column == 0) ? "Indented" : "Hello", ImGui::TableGetColumnName(column)); - } - } - ImGui::Unindent(indent_step * 8.0f); - - ImGui::EndTable(); - } - ImGui::TreePop(); - } - - if (open_action != -1) - ImGui::SetNextItemOpen(open_action != 0); - IMGUI_DEMO_MARKER("Tables/Columns widths"); - if (ImGui::TreeNode("Columns widths")) - { - HelpMarker("Using TableSetupColumn() to setup default width."); - - static ImGuiTableFlags flags1 = ImGuiTableFlags_Borders | ImGuiTableFlags_NoBordersInBodyUntilResize; - PushStyleCompact(); - ImGui::CheckboxFlags("ImGuiTableFlags_Resizable", &flags1, ImGuiTableFlags_Resizable); - ImGui::CheckboxFlags("ImGuiTableFlags_NoBordersInBodyUntilResize", &flags1, ImGuiTableFlags_NoBordersInBodyUntilResize); - PopStyleCompact(); - if (ImGui::BeginTable("table1", 3, flags1)) - { - // We could also set ImGuiTableFlags_SizingFixedFit on the table and all columns will default to ImGuiTableColumnFlags_WidthFixed. - ImGui::TableSetupColumn("one", ImGuiTableColumnFlags_WidthFixed, 100.0f); // Default to 100.0f - ImGui::TableSetupColumn("two", ImGuiTableColumnFlags_WidthFixed, 200.0f); // Default to 200.0f - ImGui::TableSetupColumn("three", ImGuiTableColumnFlags_WidthFixed); // Default to auto - ImGui::TableHeadersRow(); - for (int row = 0; row < 4; row++) - { - ImGui::TableNextRow(); - for (int column = 0; column < 3; column++) - { - ImGui::TableSetColumnIndex(column); - if (row == 0) - ImGui::Text("(w: %5.1f)", ImGui::GetContentRegionAvail().x); - else - ImGui::Text("Hello %d,%d", column, row); - } - } - ImGui::EndTable(); - } - - HelpMarker("Using TableSetupColumn() to setup explicit width.\n\nUnless _NoKeepColumnsVisible is set, fixed columns with set width may still be shrunk down if there's not enough space in the host."); - - static ImGuiTableFlags flags2 = ImGuiTableFlags_None; - PushStyleCompact(); - ImGui::CheckboxFlags("ImGuiTableFlags_NoKeepColumnsVisible", &flags2, ImGuiTableFlags_NoKeepColumnsVisible); - ImGui::CheckboxFlags("ImGuiTableFlags_BordersInnerV", &flags2, ImGuiTableFlags_BordersInnerV); - ImGui::CheckboxFlags("ImGuiTableFlags_BordersOuterV", &flags2, ImGuiTableFlags_BordersOuterV); - PopStyleCompact(); - if (ImGui::BeginTable("table2", 4, flags2)) - { - // We could also set ImGuiTableFlags_SizingFixedFit on the table and all columns will default to ImGuiTableColumnFlags_WidthFixed. - ImGui::TableSetupColumn("", ImGuiTableColumnFlags_WidthFixed, 100.0f); - ImGui::TableSetupColumn("", ImGuiTableColumnFlags_WidthFixed, TEXT_BASE_WIDTH * 15.0f); - ImGui::TableSetupColumn("", ImGuiTableColumnFlags_WidthFixed, TEXT_BASE_WIDTH * 30.0f); - ImGui::TableSetupColumn("", ImGuiTableColumnFlags_WidthFixed, TEXT_BASE_WIDTH * 15.0f); - for (int row = 0; row < 5; row++) - { - ImGui::TableNextRow(); - for (int column = 0; column < 4; column++) - { - ImGui::TableSetColumnIndex(column); - if (row == 0) - ImGui::Text("(w: %5.1f)", ImGui::GetContentRegionAvail().x); - else - ImGui::Text("Hello %d,%d", column, row); - } - } - ImGui::EndTable(); - } - ImGui::TreePop(); - } - - if (open_action != -1) - ImGui::SetNextItemOpen(open_action != 0); - IMGUI_DEMO_MARKER("Tables/Nested tables"); - if (ImGui::TreeNode("Nested tables")) - { - HelpMarker("This demonstrates embedding a table into another table cell."); - - if (ImGui::BeginTable("table_nested1", 2, ImGuiTableFlags_Borders | ImGuiTableFlags_Resizable | ImGuiTableFlags_Reorderable | ImGuiTableFlags_Hideable)) - { - ImGui::TableSetupColumn("A0"); - ImGui::TableSetupColumn("A1"); - ImGui::TableHeadersRow(); - - ImGui::TableNextColumn(); - ImGui::Text("A0 Row 0"); - { - float rows_height = TEXT_BASE_HEIGHT * 2; - if (ImGui::BeginTable("table_nested2", 2, ImGuiTableFlags_Borders | ImGuiTableFlags_Resizable | ImGuiTableFlags_Reorderable | ImGuiTableFlags_Hideable)) - { - ImGui::TableSetupColumn("B0"); - ImGui::TableSetupColumn("B1"); - ImGui::TableHeadersRow(); - - ImGui::TableNextRow(ImGuiTableRowFlags_None, rows_height); - ImGui::TableNextColumn(); - ImGui::Text("B0 Row 0"); - ImGui::TableNextColumn(); - ImGui::Text("B1 Row 0"); - ImGui::TableNextRow(ImGuiTableRowFlags_None, rows_height); - ImGui::TableNextColumn(); - ImGui::Text("B0 Row 1"); - ImGui::TableNextColumn(); - ImGui::Text("B1 Row 1"); - - ImGui::EndTable(); - } - } - ImGui::TableNextColumn(); ImGui::Text("A1 Row 0"); - ImGui::TableNextColumn(); ImGui::Text("A0 Row 1"); - ImGui::TableNextColumn(); ImGui::Text("A1 Row 1"); - ImGui::EndTable(); - } - ImGui::TreePop(); - } - - if (open_action != -1) - ImGui::SetNextItemOpen(open_action != 0); - IMGUI_DEMO_MARKER("Tables/Row height"); - if (ImGui::TreeNode("Row height")) - { - HelpMarker("You can pass a 'min_row_height' to TableNextRow().\n\nRows are padded with 'style.CellPadding.y' on top and bottom, so effectively the minimum row height will always be >= 'style.CellPadding.y * 2.0f'.\n\nWe cannot honor a _maximum_ row height as that would require a unique clipping rectangle per row."); - if (ImGui::BeginTable("table_row_height", 1, ImGuiTableFlags_Borders)) - { - for (int row = 0; row < 8; row++) - { - float min_row_height = (float)(int)(TEXT_BASE_HEIGHT * 0.30f * row); - ImGui::TableNextRow(ImGuiTableRowFlags_None, min_row_height); - ImGui::TableNextColumn(); - ImGui::Text("min_row_height = %.2f", min_row_height); - } - ImGui::EndTable(); - } - - HelpMarker("Showcase using SameLine(0,0) to share Current Line Height between cells.\n\nPlease note that Tables Row Height is not the same thing as Current Line Height, as a table cell may contains multiple lines."); - if (ImGui::BeginTable("table_share_lineheight", 2, ImGuiTableFlags_Borders)) - { - ImGui::TableNextRow(); - ImGui::TableNextColumn(); - ImGui::ColorButton("##1", ImVec4(0.13f, 0.26f, 0.40f, 1.0f), ImGuiColorEditFlags_None, ImVec2(40, 40)); - ImGui::TableNextColumn(); - ImGui::Text("Line 1"); - ImGui::Text("Line 2"); - - ImGui::TableNextRow(); - ImGui::TableNextColumn(); - ImGui::ColorButton("##2", ImVec4(0.13f, 0.26f, 0.40f, 1.0f), ImGuiColorEditFlags_None, ImVec2(40, 40)); - ImGui::TableNextColumn(); - ImGui::SameLine(0.0f, 0.0f); // Reuse line height from previous column - ImGui::Text("Line 1, with SameLine(0,0)"); - ImGui::Text("Line 2"); - - ImGui::EndTable(); - } - - HelpMarker("Showcase altering CellPadding.y between rows. Note that CellPadding.x is locked for the entire table."); - if (ImGui::BeginTable("table_changing_cellpadding_y", 1, ImGuiTableFlags_Borders)) - { - ImGuiStyle& style = ImGui::GetStyle(); - for (int row = 0; row < 8; row++) - { - if ((row % 3) == 2) - ImGui::PushStyleVar(ImGuiStyleVar_CellPadding, ImVec2(style.CellPadding.x, 20.0f)); - ImGui::TableNextRow(ImGuiTableRowFlags_None); - ImGui::TableNextColumn(); - ImGui::Text("CellPadding.y = %.2f", style.CellPadding.y); - if ((row % 3) == 2) - ImGui::PopStyleVar(); - } - ImGui::EndTable(); - } - - ImGui::TreePop(); - } - - if (open_action != -1) - ImGui::SetNextItemOpen(open_action != 0); - IMGUI_DEMO_MARKER("Tables/Outer size"); - if (ImGui::TreeNode("Outer size")) - { - // Showcasing use of ImGuiTableFlags_NoHostExtendX and ImGuiTableFlags_NoHostExtendY - // Important to that note how the two flags have slightly different behaviors! - ImGui::Text("Using NoHostExtendX and NoHostExtendY:"); - PushStyleCompact(); - static ImGuiTableFlags flags = ImGuiTableFlags_Borders | ImGuiTableFlags_Resizable | ImGuiTableFlags_ContextMenuInBody | ImGuiTableFlags_RowBg | ImGuiTableFlags_SizingFixedFit | ImGuiTableFlags_NoHostExtendX; - ImGui::CheckboxFlags("ImGuiTableFlags_NoHostExtendX", &flags, ImGuiTableFlags_NoHostExtendX); - ImGui::SameLine(); HelpMarker("Make outer width auto-fit to columns, overriding outer_size.x value.\n\nOnly available when ScrollX/ScrollY are disabled and Stretch columns are not used."); - ImGui::CheckboxFlags("ImGuiTableFlags_NoHostExtendY", &flags, ImGuiTableFlags_NoHostExtendY); - ImGui::SameLine(); HelpMarker("Make outer height stop exactly at outer_size.y (prevent auto-extending table past the limit).\n\nOnly available when ScrollX/ScrollY are disabled. Data below the limit will be clipped and not visible."); - PopStyleCompact(); - - ImVec2 outer_size = ImVec2(0.0f, TEXT_BASE_HEIGHT * 5.5f); - if (ImGui::BeginTable("table1", 3, flags, outer_size)) - { - for (int row = 0; row < 10; row++) - { - ImGui::TableNextRow(); - for (int column = 0; column < 3; column++) - { - ImGui::TableNextColumn(); - ImGui::Text("Cell %d,%d", column, row); - } - } - ImGui::EndTable(); - } - ImGui::SameLine(); - ImGui::Text("Hello!"); - - ImGui::Spacing(); - - ImGui::Text("Using explicit size:"); - if (ImGui::BeginTable("table2", 3, ImGuiTableFlags_Borders | ImGuiTableFlags_RowBg, ImVec2(TEXT_BASE_WIDTH * 30, 0.0f))) - { - for (int row = 0; row < 5; row++) - { - ImGui::TableNextRow(); - for (int column = 0; column < 3; column++) - { - ImGui::TableNextColumn(); - ImGui::Text("Cell %d,%d", column, row); - } - } - ImGui::EndTable(); - } - ImGui::SameLine(); - if (ImGui::BeginTable("table3", 3, ImGuiTableFlags_Borders | ImGuiTableFlags_RowBg, ImVec2(TEXT_BASE_WIDTH * 30, 0.0f))) - { - for (int row = 0; row < 3; row++) - { - ImGui::TableNextRow(0, TEXT_BASE_HEIGHT * 1.5f); - for (int column = 0; column < 3; column++) - { - ImGui::TableNextColumn(); - ImGui::Text("Cell %d,%d", column, row); - } - } - ImGui::EndTable(); - } - - ImGui::TreePop(); - } - - if (open_action != -1) - ImGui::SetNextItemOpen(open_action != 0); - IMGUI_DEMO_MARKER("Tables/Background color"); - if (ImGui::TreeNode("Background color")) - { - static ImGuiTableFlags flags = ImGuiTableFlags_RowBg; - static int row_bg_type = 1; - static int row_bg_target = 1; - static int cell_bg_type = 1; - - PushStyleCompact(); - ImGui::CheckboxFlags("ImGuiTableFlags_Borders", &flags, ImGuiTableFlags_Borders); - ImGui::CheckboxFlags("ImGuiTableFlags_RowBg", &flags, ImGuiTableFlags_RowBg); - ImGui::SameLine(); HelpMarker("ImGuiTableFlags_RowBg automatically sets RowBg0 to alternative colors pulled from the Style."); - ImGui::Combo("row bg type", (int*)&row_bg_type, "None\0Red\0Gradient\0"); - ImGui::Combo("row bg target", (int*)&row_bg_target, "RowBg0\0RowBg1\0"); ImGui::SameLine(); HelpMarker("Target RowBg0 to override the alternating odd/even colors,\nTarget RowBg1 to blend with them."); - ImGui::Combo("cell bg type", (int*)&cell_bg_type, "None\0Blue\0"); ImGui::SameLine(); HelpMarker("We are colorizing cells to B1->C2 here."); - IM_ASSERT(row_bg_type >= 0 && row_bg_type <= 2); - IM_ASSERT(row_bg_target >= 0 && row_bg_target <= 1); - IM_ASSERT(cell_bg_type >= 0 && cell_bg_type <= 1); - PopStyleCompact(); - - if (ImGui::BeginTable("table1", 5, flags)) - { - for (int row = 0; row < 6; row++) - { - ImGui::TableNextRow(); - - // Demonstrate setting a row background color with 'ImGui::TableSetBgColor(ImGuiTableBgTarget_RowBgX, ...)' - // We use a transparent color so we can see the one behind in case our target is RowBg1 and RowBg0 was already targeted by the ImGuiTableFlags_RowBg flag. - if (row_bg_type != 0) - { - ImU32 row_bg_color = ImGui::GetColorU32(row_bg_type == 1 ? ImVec4(0.7f, 0.3f, 0.3f, 0.65f) : ImVec4(0.2f + row * 0.1f, 0.2f, 0.2f, 0.65f)); // Flat or Gradient? - ImGui::TableSetBgColor(ImGuiTableBgTarget_RowBg0 + row_bg_target, row_bg_color); - } - - // Fill cells - for (int column = 0; column < 5; column++) - { - ImGui::TableSetColumnIndex(column); - ImGui::Text("%c%c", 'A' + row, '0' + column); - - // Change background of Cells B1->C2 - // Demonstrate setting a cell background color with 'ImGui::TableSetBgColor(ImGuiTableBgTarget_CellBg, ...)' - // (the CellBg color will be blended over the RowBg and ColumnBg colors) - // We can also pass a column number as a third parameter to TableSetBgColor() and do this outside the column loop. - if (row >= 1 && row <= 2 && column >= 1 && column <= 2 && cell_bg_type == 1) - { - ImU32 cell_bg_color = ImGui::GetColorU32(ImVec4(0.3f, 0.3f, 0.7f, 0.65f)); - ImGui::TableSetBgColor(ImGuiTableBgTarget_CellBg, cell_bg_color); - } - } - } - ImGui::EndTable(); - } - ImGui::TreePop(); - } - - if (open_action != -1) - ImGui::SetNextItemOpen(open_action != 0); - IMGUI_DEMO_MARKER("Tables/Tree view"); - if (ImGui::TreeNode("Tree view")) - { - static ImGuiTableFlags flags = ImGuiTableFlags_BordersV | ImGuiTableFlags_BordersOuterH | ImGuiTableFlags_Resizable | ImGuiTableFlags_RowBg | ImGuiTableFlags_NoBordersInBody; - - static ImGuiTreeNodeFlags tree_node_flags = ImGuiTreeNodeFlags_SpanAllColumns; - ImGui::CheckboxFlags("ImGuiTreeNodeFlags_SpanFullWidth", &tree_node_flags, ImGuiTreeNodeFlags_SpanFullWidth); - ImGui::CheckboxFlags("ImGuiTreeNodeFlags_SpanAllColumns", &tree_node_flags, ImGuiTreeNodeFlags_SpanAllColumns); - - if (ImGui::BeginTable("3ways", 3, flags)) - { - // The first column will use the default _WidthStretch when ScrollX is Off and _WidthFixed when ScrollX is On - ImGui::TableSetupColumn("Name", ImGuiTableColumnFlags_NoHide); - ImGui::TableSetupColumn("Size", ImGuiTableColumnFlags_WidthFixed, TEXT_BASE_WIDTH * 12.0f); - ImGui::TableSetupColumn("Type", ImGuiTableColumnFlags_WidthFixed, TEXT_BASE_WIDTH * 18.0f); - ImGui::TableHeadersRow(); - - // Simple storage to output a dummy file-system. - struct MyTreeNode - { - const char* Name; - const char* Type; - int Size; - int ChildIdx; - int ChildCount; - static void DisplayNode(const MyTreeNode* node, const MyTreeNode* all_nodes) - { - ImGui::TableNextRow(); - ImGui::TableNextColumn(); - const bool is_folder = (node->ChildCount > 0); - if (is_folder) - { - bool open = ImGui::TreeNodeEx(node->Name, tree_node_flags); - ImGui::TableNextColumn(); - ImGui::TextDisabled("--"); - ImGui::TableNextColumn(); - ImGui::TextUnformatted(node->Type); - if (open) - { - for (int child_n = 0; child_n < node->ChildCount; child_n++) - DisplayNode(&all_nodes[node->ChildIdx + child_n], all_nodes); - ImGui::TreePop(); - } - } - else - { - ImGui::TreeNodeEx(node->Name, tree_node_flags | ImGuiTreeNodeFlags_Leaf | ImGuiTreeNodeFlags_Bullet | ImGuiTreeNodeFlags_NoTreePushOnOpen); - ImGui::TableNextColumn(); - ImGui::Text("%d", node->Size); - ImGui::TableNextColumn(); - ImGui::TextUnformatted(node->Type); - } - } - }; - static const MyTreeNode nodes[] = - { - { "Root", "Folder", -1, 1, 3 }, // 0 - { "Music", "Folder", -1, 4, 2 }, // 1 - { "Textures", "Folder", -1, 6, 3 }, // 2 - { "desktop.ini", "System file", 1024, -1,-1 }, // 3 - { "File1_a.wav", "Audio file", 123000, -1,-1 }, // 4 - { "File1_b.wav", "Audio file", 456000, -1,-1 }, // 5 - { "Image001.png", "Image file", 203128, -1,-1 }, // 6 - { "Copy of Image001.png", "Image file", 203256, -1,-1 }, // 7 - { "Copy of Image001 (Final2).png","Image file", 203512, -1,-1 }, // 8 - }; - - MyTreeNode::DisplayNode(&nodes[0], nodes); - - ImGui::EndTable(); - } - ImGui::TreePop(); - } - - if (open_action != -1) - ImGui::SetNextItemOpen(open_action != 0); - IMGUI_DEMO_MARKER("Tables/Item width"); - if (ImGui::TreeNode("Item width")) - { - HelpMarker( - "Showcase using PushItemWidth() and how it is preserved on a per-column basis.\n\n" - "Note that on auto-resizing non-resizable fixed columns, querying the content width for e.g. right-alignment doesn't make sense."); - if (ImGui::BeginTable("table_item_width", 3, ImGuiTableFlags_Borders)) - { - ImGui::TableSetupColumn("small"); - ImGui::TableSetupColumn("half"); - ImGui::TableSetupColumn("right-align"); - ImGui::TableHeadersRow(); - - for (int row = 0; row < 3; row++) - { - ImGui::TableNextRow(); - if (row == 0) - { - // Setup ItemWidth once (instead of setting up every time, which is also possible but less efficient) - ImGui::TableSetColumnIndex(0); - ImGui::PushItemWidth(TEXT_BASE_WIDTH * 3.0f); // Small - ImGui::TableSetColumnIndex(1); - ImGui::PushItemWidth(-ImGui::GetContentRegionAvail().x * 0.5f); - ImGui::TableSetColumnIndex(2); - ImGui::PushItemWidth(-FLT_MIN); // Right-aligned - } - - // Draw our contents - static float dummy_f = 0.0f; - ImGui::PushID(row); - ImGui::TableSetColumnIndex(0); - ImGui::SliderFloat("float0", &dummy_f, 0.0f, 1.0f); - ImGui::TableSetColumnIndex(1); - ImGui::SliderFloat("float1", &dummy_f, 0.0f, 1.0f); - ImGui::TableSetColumnIndex(2); - ImGui::SliderFloat("##float2", &dummy_f, 0.0f, 1.0f); // No visible label since right-aligned - ImGui::PopID(); - } - ImGui::EndTable(); - } - ImGui::TreePop(); - } - - // Demonstrate using TableHeader() calls instead of TableHeadersRow() - if (open_action != -1) - ImGui::SetNextItemOpen(open_action != 0); - IMGUI_DEMO_MARKER("Tables/Custom headers"); - if (ImGui::TreeNode("Custom headers")) - { - const int COLUMNS_COUNT = 3; - if (ImGui::BeginTable("table_custom_headers", COLUMNS_COUNT, ImGuiTableFlags_Borders | ImGuiTableFlags_Reorderable | ImGuiTableFlags_Hideable)) - { - ImGui::TableSetupColumn("Apricot"); - ImGui::TableSetupColumn("Banana"); - ImGui::TableSetupColumn("Cherry"); - - // Dummy entire-column selection storage - // FIXME: It would be nice to actually demonstrate full-featured selection using those checkbox. - static bool column_selected[3] = {}; - - // Instead of calling TableHeadersRow() we'll submit custom headers ourselves - ImGui::TableNextRow(ImGuiTableRowFlags_Headers); - for (int column = 0; column < COLUMNS_COUNT; column++) - { - ImGui::TableSetColumnIndex(column); - const char* column_name = ImGui::TableGetColumnName(column); // Retrieve name passed to TableSetupColumn() - ImGui::PushID(column); - ImGui::PushStyleVar(ImGuiStyleVar_FramePadding, ImVec2(0, 0)); - ImGui::Checkbox("##checkall", &column_selected[column]); - ImGui::PopStyleVar(); - ImGui::SameLine(0.0f, ImGui::GetStyle().ItemInnerSpacing.x); - ImGui::TableHeader(column_name); - ImGui::PopID(); - } - - for (int row = 0; row < 5; row++) - { - ImGui::TableNextRow(); - for (int column = 0; column < 3; column++) - { - char buf[32]; - sprintf(buf, "Cell %d,%d", column, row); - ImGui::TableSetColumnIndex(column); - ImGui::Selectable(buf, column_selected[column]); - } - } - ImGui::EndTable(); - } - ImGui::TreePop(); - } - - // Demonstrate using ImGuiTableColumnFlags_AngledHeader flag to create angled headers - if (open_action != -1) - ImGui::SetNextItemOpen(open_action != 0); - IMGUI_DEMO_MARKER("Tables/Angled headers"); - if (ImGui::TreeNode("Angled headers")) - { - const char* column_names[] = { "Track", "cabasa", "ride", "smash", "tom-hi", "tom-mid", "tom-low", "hihat-o", "hihat-c", "snare-s", "snare-c", "clap", "rim", "kick" }; - const int columns_count = IM_ARRAYSIZE(column_names); - const int rows_count = 12; - - static ImGuiTableFlags table_flags = ImGuiTableFlags_SizingFixedFit | ImGuiTableFlags_ScrollX | ImGuiTableFlags_ScrollY | ImGuiTableFlags_BordersOuter | ImGuiTableFlags_BordersInnerH | ImGuiTableFlags_Hideable | ImGuiTableFlags_Resizable | ImGuiTableFlags_Reorderable | ImGuiTableFlags_HighlightHoveredColumn; - static bool bools[columns_count * rows_count] = {}; // Dummy storage selection storage - static int frozen_cols = 1; - static int frozen_rows = 2; - ImGui::CheckboxFlags("_ScrollX", &table_flags, ImGuiTableFlags_ScrollX); - ImGui::CheckboxFlags("_ScrollY", &table_flags, ImGuiTableFlags_ScrollY); - ImGui::CheckboxFlags("_NoBordersInBody", &table_flags, ImGuiTableFlags_NoBordersInBody); - ImGui::CheckboxFlags("_HighlightHoveredColumn", &table_flags, ImGuiTableFlags_HighlightHoveredColumn); - ImGui::SetNextItemWidth(ImGui::GetFontSize() * 8); - ImGui::SliderInt("Frozen columns", &frozen_cols, 0, 2); - ImGui::SliderInt("Frozen rows", &frozen_rows, 0, 2); - - if (ImGui::BeginTable("table_angled_headers", columns_count, table_flags, ImVec2(0.0f, TEXT_BASE_HEIGHT * 12))) - { - ImGui::TableSetupColumn(column_names[0], ImGuiTableColumnFlags_NoHide | ImGuiTableColumnFlags_NoReorder); - for (int n = 1; n < columns_count; n++) - ImGui::TableSetupColumn(column_names[n], ImGuiTableColumnFlags_AngledHeader | ImGuiTableColumnFlags_WidthFixed); - ImGui::TableSetupScrollFreeze(frozen_cols, frozen_rows); - - ImGui::TableAngledHeadersRow(); // Draw angled headers for all columns with the ImGuiTableColumnFlags_AngledHeader flag. - ImGui::TableHeadersRow(); // Draw remaining headers and allow access to context-menu and other functions. - for (int row = 0; row < rows_count; row++) - { - ImGui::PushID(row); - ImGui::TableNextRow(); - ImGui::TableSetColumnIndex(0); - ImGui::AlignTextToFramePadding(); - ImGui::Text("Track %d", row); - for (int column = 1; column < columns_count; column++) - if (ImGui::TableSetColumnIndex(column)) - { - ImGui::PushID(column); - ImGui::Checkbox("", &bools[row * columns_count + column]); - ImGui::PopID(); - } - ImGui::PopID(); - } - ImGui::EndTable(); - } - ImGui::TreePop(); - } - - // Demonstrate creating custom context menus inside columns, while playing it nice with context menus provided by TableHeadersRow()/TableHeader() - if (open_action != -1) - ImGui::SetNextItemOpen(open_action != 0); - IMGUI_DEMO_MARKER("Tables/Context menus"); - if (ImGui::TreeNode("Context menus")) - { - HelpMarker("By default, right-clicking over a TableHeadersRow()/TableHeader() line will open the default context-menu.\nUsing ImGuiTableFlags_ContextMenuInBody we also allow right-clicking over columns body."); - static ImGuiTableFlags flags1 = ImGuiTableFlags_Resizable | ImGuiTableFlags_Reorderable | ImGuiTableFlags_Hideable | ImGuiTableFlags_Borders | ImGuiTableFlags_ContextMenuInBody; - - PushStyleCompact(); - ImGui::CheckboxFlags("ImGuiTableFlags_ContextMenuInBody", &flags1, ImGuiTableFlags_ContextMenuInBody); - PopStyleCompact(); - - // Context Menus: first example - // [1.1] Right-click on the TableHeadersRow() line to open the default table context menu. - // [1.2] Right-click in columns also open the default table context menu (if ImGuiTableFlags_ContextMenuInBody is set) - const int COLUMNS_COUNT = 3; - if (ImGui::BeginTable("table_context_menu", COLUMNS_COUNT, flags1)) - { - ImGui::TableSetupColumn("One"); - ImGui::TableSetupColumn("Two"); - ImGui::TableSetupColumn("Three"); - - // [1.1]] Right-click on the TableHeadersRow() line to open the default table context menu. - ImGui::TableHeadersRow(); - - // Submit dummy contents - for (int row = 0; row < 4; row++) - { - ImGui::TableNextRow(); - for (int column = 0; column < COLUMNS_COUNT; column++) - { - ImGui::TableSetColumnIndex(column); - ImGui::Text("Cell %d,%d", column, row); - } - } - ImGui::EndTable(); - } - - // Context Menus: second example - // [2.1] Right-click on the TableHeadersRow() line to open the default table context menu. - // [2.2] Right-click on the ".." to open a custom popup - // [2.3] Right-click in columns to open another custom popup - HelpMarker("Demonstrate mixing table context menu (over header), item context button (over button) and custom per-colum context menu (over column body)."); - ImGuiTableFlags flags2 = ImGuiTableFlags_Resizable | ImGuiTableFlags_SizingFixedFit | ImGuiTableFlags_Reorderable | ImGuiTableFlags_Hideable | ImGuiTableFlags_Borders; - if (ImGui::BeginTable("table_context_menu_2", COLUMNS_COUNT, flags2)) - { - ImGui::TableSetupColumn("One"); - ImGui::TableSetupColumn("Two"); - ImGui::TableSetupColumn("Three"); - - // [2.1] Right-click on the TableHeadersRow() line to open the default table context menu. - ImGui::TableHeadersRow(); - for (int row = 0; row < 4; row++) - { - ImGui::TableNextRow(); - for (int column = 0; column < COLUMNS_COUNT; column++) - { - // Submit dummy contents - ImGui::TableSetColumnIndex(column); - ImGui::Text("Cell %d,%d", column, row); - ImGui::SameLine(); - - // [2.2] Right-click on the ".." to open a custom popup - ImGui::PushID(row * COLUMNS_COUNT + column); - ImGui::SmallButton(".."); - if (ImGui::BeginPopupContextItem()) - { - ImGui::Text("This is the popup for Button(\"..\") in Cell %d,%d", column, row); - if (ImGui::Button("Close")) - ImGui::CloseCurrentPopup(); - ImGui::EndPopup(); - } - ImGui::PopID(); - } - } - - // [2.3] Right-click anywhere in columns to open another custom popup - // (instead of testing for !IsAnyItemHovered() we could also call OpenPopup() with ImGuiPopupFlags_NoOpenOverExistingPopup - // to manage popup priority as the popups triggers, here "are we hovering a column" are overlapping) - int hovered_column = -1; - for (int column = 0; column < COLUMNS_COUNT + 1; column++) - { - ImGui::PushID(column); - if (ImGui::TableGetColumnFlags(column) & ImGuiTableColumnFlags_IsHovered) - hovered_column = column; - if (hovered_column == column && !ImGui::IsAnyItemHovered() && ImGui::IsMouseReleased(1)) - ImGui::OpenPopup("MyPopup"); - if (ImGui::BeginPopup("MyPopup")) - { - if (column == COLUMNS_COUNT) - ImGui::Text("This is a custom popup for unused space after the last column."); - else - ImGui::Text("This is a custom popup for Column %d", column); - if (ImGui::Button("Close")) - ImGui::CloseCurrentPopup(); - ImGui::EndPopup(); - } - ImGui::PopID(); - } - - ImGui::EndTable(); - ImGui::Text("Hovered column: %d", hovered_column); - } - ImGui::TreePop(); - } - - // Demonstrate creating multiple tables with the same ID - if (open_action != -1) - ImGui::SetNextItemOpen(open_action != 0); - IMGUI_DEMO_MARKER("Tables/Synced instances"); - if (ImGui::TreeNode("Synced instances")) - { - HelpMarker("Multiple tables with the same identifier will share their settings, width, visibility, order etc."); - - static ImGuiTableFlags flags = ImGuiTableFlags_Resizable | ImGuiTableFlags_Reorderable | ImGuiTableFlags_Hideable | ImGuiTableFlags_Borders | ImGuiTableFlags_SizingFixedFit | ImGuiTableFlags_NoSavedSettings; - ImGui::CheckboxFlags("ImGuiTableFlags_ScrollY", &flags, ImGuiTableFlags_ScrollY); - ImGui::CheckboxFlags("ImGuiTableFlags_SizingFixedFit", &flags, ImGuiTableFlags_SizingFixedFit); - ImGui::CheckboxFlags("ImGuiTableFlags_HighlightHoveredColumn", &flags, ImGuiTableFlags_HighlightHoveredColumn); - for (int n = 0; n < 3; n++) - { - char buf[32]; - sprintf(buf, "Synced Table %d", n); - bool open = ImGui::CollapsingHeader(buf, ImGuiTreeNodeFlags_DefaultOpen); - if (open && ImGui::BeginTable("Table", 3, flags, ImVec2(0.0f, ImGui::GetTextLineHeightWithSpacing() * 5))) - { - ImGui::TableSetupColumn("One"); - ImGui::TableSetupColumn("Two"); - ImGui::TableSetupColumn("Three"); - ImGui::TableHeadersRow(); - const int cell_count = (n == 1) ? 27 : 9; // Make second table have a scrollbar to verify that additional decoration is not affecting column positions. - for (int cell = 0; cell < cell_count; cell++) - { - ImGui::TableNextColumn(); - ImGui::Text("this cell %d", cell); - } - ImGui::EndTable(); - } - } - ImGui::TreePop(); - } - - // Demonstrate using Sorting facilities - // This is a simplified version of the "Advanced" example, where we mostly focus on the code necessary to handle sorting. - // Note that the "Advanced" example also showcase manually triggering a sort (e.g. if item quantities have been modified) - static const char* template_items_names[] = - { - "Banana", "Apple", "Cherry", "Watermelon", "Grapefruit", "Strawberry", "Mango", - "Kiwi", "Orange", "Pineapple", "Blueberry", "Plum", "Coconut", "Pear", "Apricot" - }; - if (open_action != -1) - ImGui::SetNextItemOpen(open_action != 0); - IMGUI_DEMO_MARKER("Tables/Sorting"); - if (ImGui::TreeNode("Sorting")) - { - // Create item list - static ImVector items; - if (items.Size == 0) - { - items.resize(50, MyItem()); - for (int n = 0; n < items.Size; n++) - { - const int template_n = n % IM_ARRAYSIZE(template_items_names); - MyItem& item = items[n]; - item.ID = n; - item.Name = template_items_names[template_n]; - item.Quantity = (n * n - n) % 20; // Assign default quantities - } - } - - // Options - static ImGuiTableFlags flags = - ImGuiTableFlags_Resizable | ImGuiTableFlags_Reorderable | ImGuiTableFlags_Hideable | ImGuiTableFlags_Sortable | ImGuiTableFlags_SortMulti - | ImGuiTableFlags_RowBg | ImGuiTableFlags_BordersOuter | ImGuiTableFlags_BordersV | ImGuiTableFlags_NoBordersInBody - | ImGuiTableFlags_ScrollY; - PushStyleCompact(); - ImGui::CheckboxFlags("ImGuiTableFlags_SortMulti", &flags, ImGuiTableFlags_SortMulti); - ImGui::SameLine(); HelpMarker("When sorting is enabled: hold shift when clicking headers to sort on multiple column. TableGetSortSpecs() may return specs where (SpecsCount > 1)."); - ImGui::CheckboxFlags("ImGuiTableFlags_SortTristate", &flags, ImGuiTableFlags_SortTristate); - ImGui::SameLine(); HelpMarker("When sorting is enabled: allow no sorting, disable default sorting. TableGetSortSpecs() may return specs where (SpecsCount == 0)."); - PopStyleCompact(); - - if (ImGui::BeginTable("table_sorting", 4, flags, ImVec2(0.0f, TEXT_BASE_HEIGHT * 15), 0.0f)) - { - // Declare columns - // We use the "user_id" parameter of TableSetupColumn() to specify a user id that will be stored in the sort specifications. - // This is so our sort function can identify a column given our own identifier. We could also identify them based on their index! - // Demonstrate using a mixture of flags among available sort-related flags: - // - ImGuiTableColumnFlags_DefaultSort - // - ImGuiTableColumnFlags_NoSort / ImGuiTableColumnFlags_NoSortAscending / ImGuiTableColumnFlags_NoSortDescending - // - ImGuiTableColumnFlags_PreferSortAscending / ImGuiTableColumnFlags_PreferSortDescending - ImGui::TableSetupColumn("ID", ImGuiTableColumnFlags_DefaultSort | ImGuiTableColumnFlags_WidthFixed, 0.0f, MyItemColumnID_ID); - ImGui::TableSetupColumn("Name", ImGuiTableColumnFlags_WidthFixed, 0.0f, MyItemColumnID_Name); - ImGui::TableSetupColumn("Action", ImGuiTableColumnFlags_NoSort | ImGuiTableColumnFlags_WidthFixed, 0.0f, MyItemColumnID_Action); - ImGui::TableSetupColumn("Quantity", ImGuiTableColumnFlags_PreferSortDescending | ImGuiTableColumnFlags_WidthStretch, 0.0f, MyItemColumnID_Quantity); - ImGui::TableSetupScrollFreeze(0, 1); // Make row always visible - ImGui::TableHeadersRow(); - - // Sort our data if sort specs have been changed! - if (ImGuiTableSortSpecs* sort_specs = ImGui::TableGetSortSpecs()) - if (sort_specs->SpecsDirty) - { - MyItem::SortWithSortSpecs(sort_specs, items.Data, items.Size); - sort_specs->SpecsDirty = false; - } - - // Demonstrate using clipper for large vertical lists - ImGuiListClipper clipper; - clipper.Begin(items.Size); - while (clipper.Step()) - for (int row_n = clipper.DisplayStart; row_n < clipper.DisplayEnd; row_n++) - { - // Display a data item - MyItem* item = &items[row_n]; - ImGui::PushID(item->ID); - ImGui::TableNextRow(); - ImGui::TableNextColumn(); - ImGui::Text("%04d", item->ID); - ImGui::TableNextColumn(); - ImGui::TextUnformatted(item->Name); - ImGui::TableNextColumn(); - ImGui::SmallButton("None"); - ImGui::TableNextColumn(); - ImGui::Text("%d", item->Quantity); - ImGui::PopID(); - } - ImGui::EndTable(); - } - ImGui::TreePop(); - } - - // In this example we'll expose most table flags and settings. - // For specific flags and settings refer to the corresponding section for more detailed explanation. - // This section is mostly useful to experiment with combining certain flags or settings with each others. - //ImGui::SetNextItemOpen(true, ImGuiCond_Once); // [DEBUG] - if (open_action != -1) - ImGui::SetNextItemOpen(open_action != 0); - IMGUI_DEMO_MARKER("Tables/Advanced"); - if (ImGui::TreeNode("Advanced")) - { - static ImGuiTableFlags flags = - ImGuiTableFlags_Resizable | ImGuiTableFlags_Reorderable | ImGuiTableFlags_Hideable - | ImGuiTableFlags_Sortable | ImGuiTableFlags_SortMulti - | ImGuiTableFlags_RowBg | ImGuiTableFlags_Borders | ImGuiTableFlags_NoBordersInBody - | ImGuiTableFlags_ScrollX | ImGuiTableFlags_ScrollY - | ImGuiTableFlags_SizingFixedFit; - static ImGuiTableColumnFlags columns_base_flags = ImGuiTableColumnFlags_None; - - enum ContentsType { CT_Text, CT_Button, CT_SmallButton, CT_FillButton, CT_Selectable, CT_SelectableSpanRow }; - static int contents_type = CT_SelectableSpanRow; - const char* contents_type_names[] = { "Text", "Button", "SmallButton", "FillButton", "Selectable", "Selectable (span row)" }; - static int freeze_cols = 1; - static int freeze_rows = 1; - static int items_count = IM_ARRAYSIZE(template_items_names) * 2; - static ImVec2 outer_size_value = ImVec2(0.0f, TEXT_BASE_HEIGHT * 12); - static float row_min_height = 0.0f; // Auto - static float inner_width_with_scroll = 0.0f; // Auto-extend - static bool outer_size_enabled = true; - static bool show_headers = true; - static bool show_wrapped_text = false; - //static ImGuiTextFilter filter; - //ImGui::SetNextItemOpen(true, ImGuiCond_Once); // FIXME-TABLE: Enabling this results in initial clipped first pass on table which tend to affect column sizing - if (ImGui::TreeNode("Options")) - { - // Make the UI compact because there are so many fields - PushStyleCompact(); - ImGui::PushItemWidth(TEXT_BASE_WIDTH * 28.0f); - - if (ImGui::TreeNodeEx("Features:", ImGuiTreeNodeFlags_DefaultOpen)) - { - ImGui::CheckboxFlags("ImGuiTableFlags_Resizable", &flags, ImGuiTableFlags_Resizable); - ImGui::CheckboxFlags("ImGuiTableFlags_Reorderable", &flags, ImGuiTableFlags_Reorderable); - ImGui::CheckboxFlags("ImGuiTableFlags_Hideable", &flags, ImGuiTableFlags_Hideable); - ImGui::CheckboxFlags("ImGuiTableFlags_Sortable", &flags, ImGuiTableFlags_Sortable); - ImGui::CheckboxFlags("ImGuiTableFlags_NoSavedSettings", &flags, ImGuiTableFlags_NoSavedSettings); - ImGui::CheckboxFlags("ImGuiTableFlags_ContextMenuInBody", &flags, ImGuiTableFlags_ContextMenuInBody); - ImGui::TreePop(); - } - - if (ImGui::TreeNodeEx("Decorations:", ImGuiTreeNodeFlags_DefaultOpen)) - { - ImGui::CheckboxFlags("ImGuiTableFlags_RowBg", &flags, ImGuiTableFlags_RowBg); - ImGui::CheckboxFlags("ImGuiTableFlags_BordersV", &flags, ImGuiTableFlags_BordersV); - ImGui::CheckboxFlags("ImGuiTableFlags_BordersOuterV", &flags, ImGuiTableFlags_BordersOuterV); - ImGui::CheckboxFlags("ImGuiTableFlags_BordersInnerV", &flags, ImGuiTableFlags_BordersInnerV); - ImGui::CheckboxFlags("ImGuiTableFlags_BordersH", &flags, ImGuiTableFlags_BordersH); - ImGui::CheckboxFlags("ImGuiTableFlags_BordersOuterH", &flags, ImGuiTableFlags_BordersOuterH); - ImGui::CheckboxFlags("ImGuiTableFlags_BordersInnerH", &flags, ImGuiTableFlags_BordersInnerH); - ImGui::CheckboxFlags("ImGuiTableFlags_NoBordersInBody", &flags, ImGuiTableFlags_NoBordersInBody); ImGui::SameLine(); HelpMarker("Disable vertical borders in columns Body (borders will always appear in Headers"); - ImGui::CheckboxFlags("ImGuiTableFlags_NoBordersInBodyUntilResize", &flags, ImGuiTableFlags_NoBordersInBodyUntilResize); ImGui::SameLine(); HelpMarker("Disable vertical borders in columns Body until hovered for resize (borders will always appear in Headers)"); - ImGui::TreePop(); - } - - if (ImGui::TreeNodeEx("Sizing:", ImGuiTreeNodeFlags_DefaultOpen)) - { - EditTableSizingFlags(&flags); - ImGui::SameLine(); HelpMarker("In the Advanced demo we override the policy of each column so those table-wide settings have less effect that typical."); - ImGui::CheckboxFlags("ImGuiTableFlags_NoHostExtendX", &flags, ImGuiTableFlags_NoHostExtendX); - ImGui::SameLine(); HelpMarker("Make outer width auto-fit to columns, overriding outer_size.x value.\n\nOnly available when ScrollX/ScrollY are disabled and Stretch columns are not used."); - ImGui::CheckboxFlags("ImGuiTableFlags_NoHostExtendY", &flags, ImGuiTableFlags_NoHostExtendY); - ImGui::SameLine(); HelpMarker("Make outer height stop exactly at outer_size.y (prevent auto-extending table past the limit).\n\nOnly available when ScrollX/ScrollY are disabled. Data below the limit will be clipped and not visible."); - ImGui::CheckboxFlags("ImGuiTableFlags_NoKeepColumnsVisible", &flags, ImGuiTableFlags_NoKeepColumnsVisible); - ImGui::SameLine(); HelpMarker("Only available if ScrollX is disabled."); - ImGui::CheckboxFlags("ImGuiTableFlags_PreciseWidths", &flags, ImGuiTableFlags_PreciseWidths); - ImGui::SameLine(); HelpMarker("Disable distributing remainder width to stretched columns (width allocation on a 100-wide table with 3 columns: Without this flag: 33,33,34. With this flag: 33,33,33). With larger number of columns, resizing will appear to be less smooth."); - ImGui::CheckboxFlags("ImGuiTableFlags_NoClip", &flags, ImGuiTableFlags_NoClip); - ImGui::SameLine(); HelpMarker("Disable clipping rectangle for every individual columns (reduce draw command count, items will be able to overflow into other columns). Generally incompatible with ScrollFreeze options."); - ImGui::TreePop(); - } - - if (ImGui::TreeNodeEx("Padding:", ImGuiTreeNodeFlags_DefaultOpen)) - { - ImGui::CheckboxFlags("ImGuiTableFlags_PadOuterX", &flags, ImGuiTableFlags_PadOuterX); - ImGui::CheckboxFlags("ImGuiTableFlags_NoPadOuterX", &flags, ImGuiTableFlags_NoPadOuterX); - ImGui::CheckboxFlags("ImGuiTableFlags_NoPadInnerX", &flags, ImGuiTableFlags_NoPadInnerX); - ImGui::TreePop(); - } - - if (ImGui::TreeNodeEx("Scrolling:", ImGuiTreeNodeFlags_DefaultOpen)) - { - ImGui::CheckboxFlags("ImGuiTableFlags_ScrollX", &flags, ImGuiTableFlags_ScrollX); - ImGui::SameLine(); - ImGui::SetNextItemWidth(ImGui::GetFrameHeight()); - ImGui::DragInt("freeze_cols", &freeze_cols, 0.2f, 0, 9, NULL, ImGuiSliderFlags_NoInput); - ImGui::CheckboxFlags("ImGuiTableFlags_ScrollY", &flags, ImGuiTableFlags_ScrollY); - ImGui::SameLine(); - ImGui::SetNextItemWidth(ImGui::GetFrameHeight()); - ImGui::DragInt("freeze_rows", &freeze_rows, 0.2f, 0, 9, NULL, ImGuiSliderFlags_NoInput); - ImGui::TreePop(); - } - - if (ImGui::TreeNodeEx("Sorting:", ImGuiTreeNodeFlags_DefaultOpen)) - { - ImGui::CheckboxFlags("ImGuiTableFlags_SortMulti", &flags, ImGuiTableFlags_SortMulti); - ImGui::SameLine(); HelpMarker("When sorting is enabled: hold shift when clicking headers to sort on multiple column. TableGetSortSpecs() may return specs where (SpecsCount > 1)."); - ImGui::CheckboxFlags("ImGuiTableFlags_SortTristate", &flags, ImGuiTableFlags_SortTristate); - ImGui::SameLine(); HelpMarker("When sorting is enabled: allow no sorting, disable default sorting. TableGetSortSpecs() may return specs where (SpecsCount == 0)."); - ImGui::TreePop(); - } - - if (ImGui::TreeNodeEx("Headers:", ImGuiTreeNodeFlags_DefaultOpen)) - { - ImGui::Checkbox("show_headers", &show_headers); - ImGui::CheckboxFlags("ImGuiTableFlags_HighlightHoveredColumn", &flags, ImGuiTableFlags_HighlightHoveredColumn); - ImGui::CheckboxFlags("ImGuiTableColumnFlags_AngledHeader", &columns_base_flags, ImGuiTableColumnFlags_AngledHeader); - ImGui::SameLine(); HelpMarker("Enable AngledHeader on all columns. Best enabled on selected narrow columns (see \"Angled headers\" section of the demo)."); - ImGui::TreePop(); - } - - if (ImGui::TreeNodeEx("Other:", ImGuiTreeNodeFlags_DefaultOpen)) - { - ImGui::Checkbox("show_wrapped_text", &show_wrapped_text); - - ImGui::DragFloat2("##OuterSize", &outer_size_value.x); - ImGui::SameLine(0.0f, ImGui::GetStyle().ItemInnerSpacing.x); - ImGui::Checkbox("outer_size", &outer_size_enabled); - ImGui::SameLine(); - HelpMarker("If scrolling is disabled (ScrollX and ScrollY not set):\n" - "- The table is output directly in the parent window.\n" - "- OuterSize.x < 0.0f will right-align the table.\n" - "- OuterSize.x = 0.0f will narrow fit the table unless there are any Stretch columns.\n" - "- OuterSize.y then becomes the minimum size for the table, which will extend vertically if there are more rows (unless NoHostExtendY is set)."); - - // From a user point of view we will tend to use 'inner_width' differently depending on whether our table is embedding scrolling. - // To facilitate toying with this demo we will actually pass 0.0f to the BeginTable() when ScrollX is disabled. - ImGui::DragFloat("inner_width (when ScrollX active)", &inner_width_with_scroll, 1.0f, 0.0f, FLT_MAX); - - ImGui::DragFloat("row_min_height", &row_min_height, 1.0f, 0.0f, FLT_MAX); - ImGui::SameLine(); HelpMarker("Specify height of the Selectable item."); - - ImGui::DragInt("items_count", &items_count, 0.1f, 0, 9999); - ImGui::Combo("items_type (first column)", &contents_type, contents_type_names, IM_ARRAYSIZE(contents_type_names)); - //filter.Draw("filter"); - ImGui::TreePop(); - } - - ImGui::PopItemWidth(); - PopStyleCompact(); - ImGui::Spacing(); - ImGui::TreePop(); - } - - // Update item list if we changed the number of items - static ImVector items; - static ImVector selection; - static bool items_need_sort = false; - if (items.Size != items_count) - { - items.resize(items_count, MyItem()); - for (int n = 0; n < items_count; n++) - { - const int template_n = n % IM_ARRAYSIZE(template_items_names); - MyItem& item = items[n]; - item.ID = n; - item.Name = template_items_names[template_n]; - item.Quantity = (template_n == 3) ? 10 : (template_n == 4) ? 20 : 0; // Assign default quantities - } - } - - const ImDrawList* parent_draw_list = ImGui::GetWindowDrawList(); - const int parent_draw_list_draw_cmd_count = parent_draw_list->CmdBuffer.Size; - ImVec2 table_scroll_cur, table_scroll_max; // For debug display - const ImDrawList* table_draw_list = NULL; // " - - // Submit table - const float inner_width_to_use = (flags & ImGuiTableFlags_ScrollX) ? inner_width_with_scroll : 0.0f; - if (ImGui::BeginTable("table_advanced", 6, flags, outer_size_enabled ? outer_size_value : ImVec2(0, 0), inner_width_to_use)) - { - // Declare columns - // We use the "user_id" parameter of TableSetupColumn() to specify a user id that will be stored in the sort specifications. - // This is so our sort function can identify a column given our own identifier. We could also identify them based on their index! - ImGui::TableSetupColumn("ID", columns_base_flags | ImGuiTableColumnFlags_DefaultSort | ImGuiTableColumnFlags_WidthFixed | ImGuiTableColumnFlags_NoHide, 0.0f, MyItemColumnID_ID); - ImGui::TableSetupColumn("Name", columns_base_flags | ImGuiTableColumnFlags_WidthFixed, 0.0f, MyItemColumnID_Name); - ImGui::TableSetupColumn("Action", columns_base_flags | ImGuiTableColumnFlags_NoSort | ImGuiTableColumnFlags_WidthFixed, 0.0f, MyItemColumnID_Action); - ImGui::TableSetupColumn("Quantity", columns_base_flags | ImGuiTableColumnFlags_PreferSortDescending, 0.0f, MyItemColumnID_Quantity); - ImGui::TableSetupColumn("Description", columns_base_flags | ((flags & ImGuiTableFlags_NoHostExtendX) ? 0 : ImGuiTableColumnFlags_WidthStretch), 0.0f, MyItemColumnID_Description); - ImGui::TableSetupColumn("Hidden", columns_base_flags | ImGuiTableColumnFlags_DefaultHide | ImGuiTableColumnFlags_NoSort); - ImGui::TableSetupScrollFreeze(freeze_cols, freeze_rows); - - // Sort our data if sort specs have been changed! - ImGuiTableSortSpecs* sort_specs = ImGui::TableGetSortSpecs(); - if (sort_specs && sort_specs->SpecsDirty) - items_need_sort = true; - if (sort_specs && items_need_sort && items.Size > 1) - { - MyItem::SortWithSortSpecs(sort_specs, items.Data, items.Size); - sort_specs->SpecsDirty = false; - } - items_need_sort = false; - - // Take note of whether we are currently sorting based on the Quantity field, - // we will use this to trigger sorting when we know the data of this column has been modified. - const bool sorts_specs_using_quantity = (ImGui::TableGetColumnFlags(3) & ImGuiTableColumnFlags_IsSorted) != 0; - - // Show headers - if (show_headers && (columns_base_flags & ImGuiTableColumnFlags_AngledHeader) != 0) - ImGui::TableAngledHeadersRow(); - if (show_headers) - ImGui::TableHeadersRow(); - - // Show data - // FIXME-TABLE FIXME-NAV: How we can get decent up/down even though we have the buttons here? - ImGui::PushButtonRepeat(true); -#if 1 - // Demonstrate using clipper for large vertical lists - ImGuiListClipper clipper; - clipper.Begin(items.Size); - while (clipper.Step()) - { - for (int row_n = clipper.DisplayStart; row_n < clipper.DisplayEnd; row_n++) -#else - // Without clipper - { - for (int row_n = 0; row_n < items.Size; row_n++) -#endif - { - MyItem* item = &items[row_n]; - //if (!filter.PassFilter(item->Name)) - // continue; - - const bool item_is_selected = selection.contains(item->ID); - ImGui::PushID(item->ID); - ImGui::TableNextRow(ImGuiTableRowFlags_None, row_min_height); - - // For the demo purpose we can select among different type of items submitted in the first column - ImGui::TableSetColumnIndex(0); - char label[32]; - sprintf(label, "%04d", item->ID); - if (contents_type == CT_Text) - ImGui::TextUnformatted(label); - else if (contents_type == CT_Button) - ImGui::Button(label); - else if (contents_type == CT_SmallButton) - ImGui::SmallButton(label); - else if (contents_type == CT_FillButton) - ImGui::Button(label, ImVec2(-FLT_MIN, 0.0f)); - else if (contents_type == CT_Selectable || contents_type == CT_SelectableSpanRow) - { - ImGuiSelectableFlags selectable_flags = (contents_type == CT_SelectableSpanRow) ? ImGuiSelectableFlags_SpanAllColumns | ImGuiSelectableFlags_AllowOverlap : ImGuiSelectableFlags_None; - if (ImGui::Selectable(label, item_is_selected, selectable_flags, ImVec2(0, row_min_height))) - { - if (ImGui::GetIO().KeyCtrl) - { - if (item_is_selected) - selection.find_erase_unsorted(item->ID); - else - selection.push_back(item->ID); - } - else - { - selection.clear(); - selection.push_back(item->ID); - } - } - } - - if (ImGui::TableSetColumnIndex(1)) - ImGui::TextUnformatted(item->Name); - - // Here we demonstrate marking our data set as needing to be sorted again if we modified a quantity, - // and we are currently sorting on the column showing the Quantity. - // To avoid triggering a sort while holding the button, we only trigger it when the button has been released. - // You will probably need a more advanced system in your code if you want to automatically sort when a specific entry changes. - if (ImGui::TableSetColumnIndex(2)) - { - if (ImGui::SmallButton("Chop")) { item->Quantity += 1; } - if (sorts_specs_using_quantity && ImGui::IsItemDeactivated()) { items_need_sort = true; } - ImGui::SameLine(); - if (ImGui::SmallButton("Eat")) { item->Quantity -= 1; } - if (sorts_specs_using_quantity && ImGui::IsItemDeactivated()) { items_need_sort = true; } - } - - if (ImGui::TableSetColumnIndex(3)) - ImGui::Text("%d", item->Quantity); - - ImGui::TableSetColumnIndex(4); - if (show_wrapped_text) - ImGui::TextWrapped("Lorem ipsum dolor sit amet"); - else - ImGui::Text("Lorem ipsum dolor sit amet"); - - if (ImGui::TableSetColumnIndex(5)) - ImGui::Text("1234"); - - ImGui::PopID(); - } - } - ImGui::PopButtonRepeat(); - - // Store some info to display debug details below - table_scroll_cur = ImVec2(ImGui::GetScrollX(), ImGui::GetScrollY()); - table_scroll_max = ImVec2(ImGui::GetScrollMaxX(), ImGui::GetScrollMaxY()); - table_draw_list = ImGui::GetWindowDrawList(); - ImGui::EndTable(); - } - static bool show_debug_details = false; - ImGui::Checkbox("Debug details", &show_debug_details); - if (show_debug_details && table_draw_list) - { - ImGui::SameLine(0.0f, 0.0f); - const int table_draw_list_draw_cmd_count = table_draw_list->CmdBuffer.Size; - if (table_draw_list == parent_draw_list) - ImGui::Text(": DrawCmd: +%d (in same window)", - table_draw_list_draw_cmd_count - parent_draw_list_draw_cmd_count); - else - ImGui::Text(": DrawCmd: +%d (in child window), Scroll: (%.f/%.f) (%.f/%.f)", - table_draw_list_draw_cmd_count - 1, table_scroll_cur.x, table_scroll_max.x, table_scroll_cur.y, table_scroll_max.y); - } - ImGui::TreePop(); - } - - ImGui::PopID(); - - ShowDemoWindowColumns(); - - if (disable_indent) - ImGui::PopStyleVar(); -} - -// Demonstrate old/legacy Columns API! -// [2020: Columns are under-featured and not maintained. Prefer using the more flexible and powerful BeginTable() API!] -static void ShowDemoWindowColumns() -{ - IMGUI_DEMO_MARKER("Columns (legacy API)"); - bool open = ImGui::TreeNode("Legacy Columns API"); - ImGui::SameLine(); - HelpMarker("Columns() is an old API! Prefer using the more flexible and powerful BeginTable() API!"); - if (!open) - return; - - // Basic columns - IMGUI_DEMO_MARKER("Columns (legacy API)/Basic"); - if (ImGui::TreeNode("Basic")) - { - ImGui::Text("Without border:"); - ImGui::Columns(3, "mycolumns3", false); // 3-ways, no border - ImGui::Separator(); - for (int n = 0; n < 14; n++) - { - char label[32]; - sprintf(label, "Item %d", n); - if (ImGui::Selectable(label)) {} - //if (ImGui::Button(label, ImVec2(-FLT_MIN,0.0f))) {} - ImGui::NextColumn(); - } - ImGui::Columns(1); - ImGui::Separator(); - - ImGui::Text("With border:"); - ImGui::Columns(4, "mycolumns"); // 4-ways, with border - ImGui::Separator(); - ImGui::Text("ID"); ImGui::NextColumn(); - ImGui::Text("Name"); ImGui::NextColumn(); - ImGui::Text("Path"); ImGui::NextColumn(); - ImGui::Text("Hovered"); ImGui::NextColumn(); - ImGui::Separator(); - const char* names[3] = { "One", "Two", "Three" }; - const char* paths[3] = { "/path/one", "/path/two", "/path/three" }; - static int selected = -1; - for (int i = 0; i < 3; i++) - { - char label[32]; - sprintf(label, "%04d", i); - if (ImGui::Selectable(label, selected == i, ImGuiSelectableFlags_SpanAllColumns)) - selected = i; - bool hovered = ImGui::IsItemHovered(); - ImGui::NextColumn(); - ImGui::Text(names[i]); ImGui::NextColumn(); - ImGui::Text(paths[i]); ImGui::NextColumn(); - ImGui::Text("%d", hovered); ImGui::NextColumn(); - } - ImGui::Columns(1); - ImGui::Separator(); - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Columns (legacy API)/Borders"); - if (ImGui::TreeNode("Borders")) - { - // NB: Future columns API should allow automatic horizontal borders. - static bool h_borders = true; - static bool v_borders = true; - static int columns_count = 4; - const int lines_count = 3; - ImGui::SetNextItemWidth(ImGui::GetFontSize() * 8); - ImGui::DragInt("##columns_count", &columns_count, 0.1f, 2, 10, "%d columns"); - if (columns_count < 2) - columns_count = 2; - ImGui::SameLine(); - ImGui::Checkbox("horizontal", &h_borders); - ImGui::SameLine(); - ImGui::Checkbox("vertical", &v_borders); - ImGui::Columns(columns_count, NULL, v_borders); - for (int i = 0; i < columns_count * lines_count; i++) - { - if (h_borders && ImGui::GetColumnIndex() == 0) - ImGui::Separator(); - ImGui::Text("%c%c%c", 'a' + i, 'a' + i, 'a' + i); - ImGui::Text("Width %.2f", ImGui::GetColumnWidth()); - ImGui::Text("Avail %.2f", ImGui::GetContentRegionAvail().x); - ImGui::Text("Offset %.2f", ImGui::GetColumnOffset()); - ImGui::Text("Long text that is likely to clip"); - ImGui::Button("Button", ImVec2(-FLT_MIN, 0.0f)); - ImGui::NextColumn(); - } - ImGui::Columns(1); - if (h_borders) - ImGui::Separator(); - ImGui::TreePop(); - } - - // Create multiple items in a same cell before switching to next column - IMGUI_DEMO_MARKER("Columns (legacy API)/Mixed items"); - if (ImGui::TreeNode("Mixed items")) - { - ImGui::Columns(3, "mixed"); - ImGui::Separator(); - - ImGui::Text("Hello"); - ImGui::Button("Banana"); - ImGui::NextColumn(); - - ImGui::Text("ImGui"); - ImGui::Button("Apple"); - static float foo = 1.0f; - ImGui::InputFloat("red", &foo, 0.05f, 0, "%.3f"); - ImGui::Text("An extra line here."); - ImGui::NextColumn(); - - ImGui::Text("Sailor"); - ImGui::Button("Corniflower"); - static float bar = 1.0f; - ImGui::InputFloat("blue", &bar, 0.05f, 0, "%.3f"); - ImGui::NextColumn(); - - if (ImGui::CollapsingHeader("Category A")) { ImGui::Text("Blah blah blah"); } ImGui::NextColumn(); - if (ImGui::CollapsingHeader("Category B")) { ImGui::Text("Blah blah blah"); } ImGui::NextColumn(); - if (ImGui::CollapsingHeader("Category C")) { ImGui::Text("Blah blah blah"); } ImGui::NextColumn(); - ImGui::Columns(1); - ImGui::Separator(); - ImGui::TreePop(); - } - - // Word wrapping - IMGUI_DEMO_MARKER("Columns (legacy API)/Word-wrapping"); - if (ImGui::TreeNode("Word-wrapping")) - { - ImGui::Columns(2, "word-wrapping"); - ImGui::Separator(); - ImGui::TextWrapped("The quick brown fox jumps over the lazy dog."); - ImGui::TextWrapped("Hello Left"); - ImGui::NextColumn(); - ImGui::TextWrapped("The quick brown fox jumps over the lazy dog."); - ImGui::TextWrapped("Hello Right"); - ImGui::Columns(1); - ImGui::Separator(); - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Columns (legacy API)/Horizontal Scrolling"); - if (ImGui::TreeNode("Horizontal Scrolling")) - { - ImGui::SetNextWindowContentSize(ImVec2(1500.0f, 0.0f)); - ImVec2 child_size = ImVec2(0, ImGui::GetFontSize() * 20.0f); - ImGui::BeginChild("##ScrollingRegion", child_size, false, ImGuiWindowFlags_HorizontalScrollbar); - ImGui::Columns(10); - - // Also demonstrate using clipper for large vertical lists - int ITEMS_COUNT = 2000; - ImGuiListClipper clipper; - clipper.Begin(ITEMS_COUNT); - while (clipper.Step()) - { - for (int i = clipper.DisplayStart; i < clipper.DisplayEnd; i++) - for (int j = 0; j < 10; j++) - { - ImGui::Text("Line %d Column %d...", i, j); - ImGui::NextColumn(); - } - } - ImGui::Columns(1); - ImGui::EndChild(); - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Columns (legacy API)/Tree"); - if (ImGui::TreeNode("Tree")) - { - ImGui::Columns(2, "tree", true); - for (int x = 0; x < 3; x++) - { - bool open1 = ImGui::TreeNode((void*)(intptr_t)x, "Node%d", x); - ImGui::NextColumn(); - ImGui::Text("Node contents"); - ImGui::NextColumn(); - if (open1) - { - for (int y = 0; y < 3; y++) - { - bool open2 = ImGui::TreeNode((void*)(intptr_t)y, "Node%d.%d", x, y); - ImGui::NextColumn(); - ImGui::Text("Node contents"); - if (open2) - { - ImGui::Text("Even more contents"); - if (ImGui::TreeNode("Tree in column")) - { - ImGui::Text("The quick brown fox jumps over the lazy dog"); - ImGui::TreePop(); - } - } - ImGui::NextColumn(); - if (open2) - ImGui::TreePop(); - } - ImGui::TreePop(); - } - } - ImGui::Columns(1); - ImGui::TreePop(); - } - - ImGui::TreePop(); -} - -static void ShowDemoWindowInputs() -{ - IMGUI_DEMO_MARKER("Inputs & Focus"); - if (ImGui::CollapsingHeader("Inputs & Focus")) - { - ImGuiIO& io = ImGui::GetIO(); - - // Display inputs submitted to ImGuiIO - IMGUI_DEMO_MARKER("Inputs & Focus/Inputs"); - ImGui::SetNextItemOpen(true, ImGuiCond_Once); - if (ImGui::TreeNode("Inputs")) - { - HelpMarker( - "This is a simplified view. See more detailed input state:\n" - "- in 'Tools->Metrics/Debugger->Inputs'.\n" - "- in 'Tools->Debug Log->IO'."); - if (ImGui::IsMousePosValid()) - ImGui::Text("Mouse pos: (%g, %g)", io.MousePos.x, io.MousePos.y); - else - ImGui::Text("Mouse pos: "); - ImGui::Text("Mouse delta: (%g, %g)", io.MouseDelta.x, io.MouseDelta.y); - ImGui::Text("Mouse down:"); - for (int i = 0; i < IM_ARRAYSIZE(io.MouseDown); i++) if (ImGui::IsMouseDown(i)) { ImGui::SameLine(); ImGui::Text("b%d (%.02f secs)", i, io.MouseDownDuration[i]); } - ImGui::Text("Mouse wheel: %.1f", io.MouseWheel); - - // We iterate both legacy native range and named ImGuiKey ranges, which is a little odd but this allows displaying the data for old/new backends. - // User code should never have to go through such hoops! You can generally iterate between ImGuiKey_NamedKey_BEGIN and ImGuiKey_NamedKey_END. -#ifdef IMGUI_DISABLE_OBSOLETE_KEYIO - struct funcs { static bool IsLegacyNativeDupe(ImGuiKey) { return false; } }; - ImGuiKey start_key = ImGuiKey_NamedKey_BEGIN; -#else - struct funcs { static bool IsLegacyNativeDupe(ImGuiKey key) { return key < 512 && ImGui::GetIO().KeyMap[key] != -1; } }; // Hide Native<>ImGuiKey duplicates when both exists in the array - ImGuiKey start_key = (ImGuiKey)0; -#endif - ImGui::Text("Keys down:"); for (ImGuiKey key = start_key; key < ImGuiKey_NamedKey_END; key = (ImGuiKey)(key + 1)) { if (funcs::IsLegacyNativeDupe(key) || !ImGui::IsKeyDown(key)) continue; ImGui::SameLine(); ImGui::Text((key < ImGuiKey_NamedKey_BEGIN) ? "\"%s\"" : "\"%s\" %d", ImGui::GetKeyName(key), key); } - ImGui::Text("Keys mods: %s%s%s%s", io.KeyCtrl ? "CTRL " : "", io.KeyShift ? "SHIFT " : "", io.KeyAlt ? "ALT " : "", io.KeySuper ? "SUPER " : ""); - ImGui::Text("Chars queue:"); for (int i = 0; i < io.InputQueueCharacters.Size; i++) { ImWchar c = io.InputQueueCharacters[i]; ImGui::SameLine(); ImGui::Text("\'%c\' (0x%04X)", (c > ' ' && c <= 255) ? (char)c : '?', c); } // FIXME: We should convert 'c' to UTF-8 here but the functions are not public. - - ImGui::TreePop(); - } - - // Display ImGuiIO output flags - IMGUI_DEMO_MARKER("Inputs & Focus/Outputs"); - ImGui::SetNextItemOpen(true, ImGuiCond_Once); - if (ImGui::TreeNode("Outputs")) - { - HelpMarker( - "The value of io.WantCaptureMouse and io.WantCaptureKeyboard are normally set by Dear ImGui " - "to instruct your application of how to route inputs. Typically, when a value is true, it means " - "Dear ImGui wants the corresponding inputs and we expect the underlying application to ignore them.\n\n" - "The most typical case is: when hovering a window, Dear ImGui set io.WantCaptureMouse to true, " - "and underlying application should ignore mouse inputs (in practice there are many and more subtle " - "rules leading to how those flags are set)."); - ImGui::Text("io.WantCaptureMouse: %d", io.WantCaptureMouse); - ImGui::Text("io.WantCaptureMouseUnlessPopupClose: %d", io.WantCaptureMouseUnlessPopupClose); - ImGui::Text("io.WantCaptureKeyboard: %d", io.WantCaptureKeyboard); - ImGui::Text("io.WantTextInput: %d", io.WantTextInput); - ImGui::Text("io.WantSetMousePos: %d", io.WantSetMousePos); - ImGui::Text("io.NavActive: %d, io.NavVisible: %d", io.NavActive, io.NavVisible); - - IMGUI_DEMO_MARKER("Inputs & Focus/Outputs/WantCapture override"); - if (ImGui::TreeNode("WantCapture override")) - { - HelpMarker( - "Hovering the colored canvas will override io.WantCaptureXXX fields.\n" - "Notice how normally (when set to none), the value of io.WantCaptureKeyboard would be false when hovering and true when clicking."); - static int capture_override_mouse = -1; - static int capture_override_keyboard = -1; - const char* capture_override_desc[] = { "None", "Set to false", "Set to true" }; - ImGui::SetNextItemWidth(ImGui::GetFontSize() * 15); - ImGui::SliderInt("SetNextFrameWantCaptureMouse() on hover", &capture_override_mouse, -1, +1, capture_override_desc[capture_override_mouse + 1], ImGuiSliderFlags_AlwaysClamp); - ImGui::SetNextItemWidth(ImGui::GetFontSize() * 15); - ImGui::SliderInt("SetNextFrameWantCaptureKeyboard() on hover", &capture_override_keyboard, -1, +1, capture_override_desc[capture_override_keyboard + 1], ImGuiSliderFlags_AlwaysClamp); - - ImGui::ColorButton("##panel", ImVec4(0.7f, 0.1f, 0.7f, 1.0f), ImGuiColorEditFlags_NoTooltip | ImGuiColorEditFlags_NoDragDrop, ImVec2(128.0f, 96.0f)); // Dummy item - if (ImGui::IsItemHovered() && capture_override_mouse != -1) - ImGui::SetNextFrameWantCaptureMouse(capture_override_mouse == 1); - if (ImGui::IsItemHovered() && capture_override_keyboard != -1) - ImGui::SetNextFrameWantCaptureKeyboard(capture_override_keyboard == 1); - - ImGui::TreePop(); - } - ImGui::TreePop(); - } - - // Display mouse cursors - IMGUI_DEMO_MARKER("Inputs & Focus/Mouse Cursors"); - if (ImGui::TreeNode("Mouse Cursors")) - { - const char* mouse_cursors_names[] = { "Arrow", "TextInput", "ResizeAll", "ResizeNS", "ResizeEW", "ResizeNESW", "ResizeNWSE", "Hand", "NotAllowed" }; - IM_ASSERT(IM_ARRAYSIZE(mouse_cursors_names) == ImGuiMouseCursor_COUNT); - - ImGuiMouseCursor current = ImGui::GetMouseCursor(); - ImGui::Text("Current mouse cursor = %d: %s", current, mouse_cursors_names[current]); - ImGui::BeginDisabled(true); - ImGui::CheckboxFlags("io.BackendFlags: HasMouseCursors", &io.BackendFlags, ImGuiBackendFlags_HasMouseCursors); - ImGui::EndDisabled(); - - ImGui::Text("Hover to see mouse cursors:"); - ImGui::SameLine(); HelpMarker( - "Your application can render a different mouse cursor based on what ImGui::GetMouseCursor() returns. " - "If software cursor rendering (io.MouseDrawCursor) is set ImGui will draw the right cursor for you, " - "otherwise your backend needs to handle it."); - for (int i = 0; i < ImGuiMouseCursor_COUNT; i++) - { - char label[32]; - sprintf(label, "Mouse cursor %d: %s", i, mouse_cursors_names[i]); - ImGui::Bullet(); ImGui::Selectable(label, false); - if (ImGui::IsItemHovered()) - ImGui::SetMouseCursor(i); - } - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Inputs & Focus/Tabbing"); - if (ImGui::TreeNode("Tabbing")) - { - ImGui::Text("Use TAB/SHIFT+TAB to cycle through keyboard editable fields."); - static char buf[32] = "hello"; - ImGui::InputText("1", buf, IM_ARRAYSIZE(buf)); - ImGui::InputText("2", buf, IM_ARRAYSIZE(buf)); - ImGui::InputText("3", buf, IM_ARRAYSIZE(buf)); - ImGui::PushTabStop(false); - ImGui::InputText("4 (tab skip)", buf, IM_ARRAYSIZE(buf)); - ImGui::SameLine(); HelpMarker("Item won't be cycled through when using TAB or Shift+Tab."); - ImGui::PopTabStop(); - ImGui::InputText("5", buf, IM_ARRAYSIZE(buf)); - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Inputs & Focus/Focus from code"); - if (ImGui::TreeNode("Focus from code")) - { - bool focus_1 = ImGui::Button("Focus on 1"); ImGui::SameLine(); - bool focus_2 = ImGui::Button("Focus on 2"); ImGui::SameLine(); - bool focus_3 = ImGui::Button("Focus on 3"); - int has_focus = 0; - static char buf[128] = "click on a button to set focus"; - - if (focus_1) ImGui::SetKeyboardFocusHere(); - ImGui::InputText("1", buf, IM_ARRAYSIZE(buf)); - if (ImGui::IsItemActive()) has_focus = 1; - - if (focus_2) ImGui::SetKeyboardFocusHere(); - ImGui::InputText("2", buf, IM_ARRAYSIZE(buf)); - if (ImGui::IsItemActive()) has_focus = 2; - - ImGui::PushTabStop(false); - if (focus_3) ImGui::SetKeyboardFocusHere(); - ImGui::InputText("3 (tab skip)", buf, IM_ARRAYSIZE(buf)); - if (ImGui::IsItemActive()) has_focus = 3; - ImGui::SameLine(); HelpMarker("Item won't be cycled through when using TAB or Shift+Tab."); - ImGui::PopTabStop(); - - if (has_focus) - ImGui::Text("Item with focus: %d", has_focus); - else - ImGui::Text("Item with focus: "); - - // Use >= 0 parameter to SetKeyboardFocusHere() to focus an upcoming item - static float f3[3] = { 0.0f, 0.0f, 0.0f }; - int focus_ahead = -1; - if (ImGui::Button("Focus on X")) { focus_ahead = 0; } ImGui::SameLine(); - if (ImGui::Button("Focus on Y")) { focus_ahead = 1; } ImGui::SameLine(); - if (ImGui::Button("Focus on Z")) { focus_ahead = 2; } - if (focus_ahead != -1) ImGui::SetKeyboardFocusHere(focus_ahead); - ImGui::SliderFloat3("Float3", &f3[0], 0.0f, 1.0f); - - ImGui::TextWrapped("NB: Cursor & selection are preserved when refocusing last used item in code."); - ImGui::TreePop(); - } - - IMGUI_DEMO_MARKER("Inputs & Focus/Dragging"); - if (ImGui::TreeNode("Dragging")) - { - ImGui::TextWrapped("You can use ImGui::GetMouseDragDelta(0) to query for the dragged amount on any widget."); - for (int button = 0; button < 3; button++) - { - ImGui::Text("IsMouseDragging(%d):", button); - ImGui::Text(" w/ default threshold: %d,", ImGui::IsMouseDragging(button)); - ImGui::Text(" w/ zero threshold: %d,", ImGui::IsMouseDragging(button, 0.0f)); - ImGui::Text(" w/ large threshold: %d,", ImGui::IsMouseDragging(button, 20.0f)); - } - - ImGui::Button("Drag Me"); - if (ImGui::IsItemActive()) - ImGui::GetForegroundDrawList()->AddLine(io.MouseClickedPos[0], io.MousePos, ImGui::GetColorU32(ImGuiCol_Button), 4.0f); // Draw a line between the button and the mouse cursor - - // Drag operations gets "unlocked" when the mouse has moved past a certain threshold - // (the default threshold is stored in io.MouseDragThreshold). You can request a lower or higher - // threshold using the second parameter of IsMouseDragging() and GetMouseDragDelta(). - ImVec2 value_raw = ImGui::GetMouseDragDelta(0, 0.0f); - ImVec2 value_with_lock_threshold = ImGui::GetMouseDragDelta(0); - ImVec2 mouse_delta = io.MouseDelta; - ImGui::Text("GetMouseDragDelta(0):"); - ImGui::Text(" w/ default threshold: (%.1f, %.1f)", value_with_lock_threshold.x, value_with_lock_threshold.y); - ImGui::Text(" w/ zero threshold: (%.1f, %.1f)", value_raw.x, value_raw.y); - ImGui::Text("io.MouseDelta: (%.1f, %.1f)", mouse_delta.x, mouse_delta.y); - ImGui::TreePop(); - } - } -} - -//----------------------------------------------------------------------------- -// [SECTION] About Window / ShowAboutWindow() -// Access from Dear ImGui Demo -> Tools -> About -//----------------------------------------------------------------------------- - -void ImGui::ShowAboutWindow(bool* p_open) -{ - if (!ImGui::Begin("About Dear ImGui", p_open, ImGuiWindowFlags_AlwaysAutoResize)) - { - ImGui::End(); - return; - } - IMGUI_DEMO_MARKER("Tools/About Dear ImGui"); - ImGui::Text("Dear ImGui %s (%d)", IMGUI_VERSION, IMGUI_VERSION_NUM); - ImGui::Separator(); - ImGui::Text("By Omar Cornut and all Dear ImGui contributors."); - ImGui::Text("Dear ImGui is licensed under the MIT License, see LICENSE for more information."); - ImGui::Text("If your company uses this, please consider sponsoring the project!"); - - static bool show_config_info = false; - ImGui::Checkbox("Config/Build Information", &show_config_info); - if (show_config_info) - { - ImGuiIO& io = ImGui::GetIO(); - ImGuiStyle& style = ImGui::GetStyle(); - - bool copy_to_clipboard = ImGui::Button("Copy to clipboard"); - ImVec2 child_size = ImVec2(0, ImGui::GetTextLineHeightWithSpacing() * 18); - ImGui::BeginChildFrame(ImGui::GetID("cfg_infos"), child_size, ImGuiWindowFlags_NoMove); - if (copy_to_clipboard) - { - ImGui::LogToClipboard(); - ImGui::LogText("```\n"); // Back quotes will make text appears without formatting when pasting on GitHub - } - - ImGui::Text("Dear ImGui %s (%d)", IMGUI_VERSION, IMGUI_VERSION_NUM); - ImGui::Separator(); - ImGui::Text("sizeof(size_t): %d, sizeof(ImDrawIdx): %d, sizeof(ImDrawVert): %d", (int)sizeof(size_t), (int)sizeof(ImDrawIdx), (int)sizeof(ImDrawVert)); - ImGui::Text("define: __cplusplus=%d", (int)__cplusplus); -#ifdef IMGUI_DISABLE_OBSOLETE_FUNCTIONS - ImGui::Text("define: IMGUI_DISABLE_OBSOLETE_FUNCTIONS"); -#endif -#ifdef IMGUI_DISABLE_OBSOLETE_KEYIO - ImGui::Text("define: IMGUI_DISABLE_OBSOLETE_KEYIO"); -#endif -#ifdef IMGUI_DISABLE_WIN32_DEFAULT_CLIPBOARD_FUNCTIONS - ImGui::Text("define: IMGUI_DISABLE_WIN32_DEFAULT_CLIPBOARD_FUNCTIONS"); -#endif -#ifdef IMGUI_DISABLE_WIN32_DEFAULT_IME_FUNCTIONS - ImGui::Text("define: IMGUI_DISABLE_WIN32_DEFAULT_IME_FUNCTIONS"); -#endif -#ifdef IMGUI_DISABLE_WIN32_FUNCTIONS - ImGui::Text("define: IMGUI_DISABLE_WIN32_FUNCTIONS"); -#endif -#ifdef IMGUI_DISABLE_DEFAULT_FORMAT_FUNCTIONS - ImGui::Text("define: IMGUI_DISABLE_DEFAULT_FORMAT_FUNCTIONS"); -#endif -#ifdef IMGUI_DISABLE_DEFAULT_MATH_FUNCTIONS - ImGui::Text("define: IMGUI_DISABLE_DEFAULT_MATH_FUNCTIONS"); -#endif -#ifdef IMGUI_DISABLE_DEFAULT_FILE_FUNCTIONS - ImGui::Text("define: IMGUI_DISABLE_DEFAULT_FILE_FUNCTIONS"); -#endif -#ifdef IMGUI_DISABLE_FILE_FUNCTIONS - ImGui::Text("define: IMGUI_DISABLE_FILE_FUNCTIONS"); -#endif -#ifdef IMGUI_DISABLE_DEFAULT_ALLOCATORS - ImGui::Text("define: IMGUI_DISABLE_DEFAULT_ALLOCATORS"); -#endif -#ifdef IMGUI_USE_BGRA_PACKED_COLOR - ImGui::Text("define: IMGUI_USE_BGRA_PACKED_COLOR"); -#endif -#ifdef _WIN32 - ImGui::Text("define: _WIN32"); -#endif -#ifdef _WIN64 - ImGui::Text("define: _WIN64"); -#endif -#ifdef __linux__ - ImGui::Text("define: __linux__"); -#endif -#ifdef __APPLE__ - ImGui::Text("define: __APPLE__"); -#endif -#ifdef _MSC_VER - ImGui::Text("define: _MSC_VER=%d", _MSC_VER); -#endif -#ifdef _MSVC_LANG - ImGui::Text("define: _MSVC_LANG=%d", (int)_MSVC_LANG); -#endif -#ifdef __MINGW32__ - ImGui::Text("define: __MINGW32__"); -#endif -#ifdef __MINGW64__ - ImGui::Text("define: __MINGW64__"); -#endif -#ifdef __GNUC__ - ImGui::Text("define: __GNUC__=%d", (int)__GNUC__); -#endif -#ifdef __clang_version__ - ImGui::Text("define: __clang_version__=%s", __clang_version__); -#endif -#ifdef __EMSCRIPTEN__ - ImGui::Text("define: __EMSCRIPTEN__"); -#endif -#ifdef IMGUI_HAS_VIEWPORT - ImGui::Text("define: IMGUI_HAS_VIEWPORT"); -#endif -#ifdef IMGUI_HAS_DOCK - ImGui::Text("define: IMGUI_HAS_DOCK"); -#endif - ImGui::Separator(); - ImGui::Text("io.BackendPlatformName: %s", io.BackendPlatformName ? io.BackendPlatformName : "NULL"); - ImGui::Text("io.BackendRendererName: %s", io.BackendRendererName ? io.BackendRendererName : "NULL"); - ImGui::Text("io.ConfigFlags: 0x%08X", io.ConfigFlags); - if (io.ConfigFlags & ImGuiConfigFlags_NavEnableKeyboard) ImGui::Text(" NavEnableKeyboard"); - if (io.ConfigFlags & ImGuiConfigFlags_NavEnableGamepad) ImGui::Text(" NavEnableGamepad"); - if (io.ConfigFlags & ImGuiConfigFlags_NavEnableSetMousePos) ImGui::Text(" NavEnableSetMousePos"); - if (io.ConfigFlags & ImGuiConfigFlags_NavNoCaptureKeyboard) ImGui::Text(" NavNoCaptureKeyboard"); - if (io.ConfigFlags & ImGuiConfigFlags_NoMouse) ImGui::Text(" NoMouse"); - if (io.ConfigFlags & ImGuiConfigFlags_NoMouseCursorChange) ImGui::Text(" NoMouseCursorChange"); - if (io.ConfigFlags & ImGuiConfigFlags_DockingEnable) ImGui::Text(" DockingEnable"); - if (io.ConfigFlags & ImGuiConfigFlags_ViewportsEnable) ImGui::Text(" ViewportsEnable"); - if (io.ConfigFlags & ImGuiConfigFlags_DpiEnableScaleViewports) ImGui::Text(" DpiEnableScaleViewports"); - if (io.ConfigFlags & ImGuiConfigFlags_DpiEnableScaleFonts) ImGui::Text(" DpiEnableScaleFonts"); - if (io.MouseDrawCursor) ImGui::Text("io.MouseDrawCursor"); - if (io.ConfigViewportsNoAutoMerge) ImGui::Text("io.ConfigViewportsNoAutoMerge"); - if (io.ConfigViewportsNoTaskBarIcon) ImGui::Text("io.ConfigViewportsNoTaskBarIcon"); - if (io.ConfigViewportsNoDecoration) ImGui::Text("io.ConfigViewportsNoDecoration"); - if (io.ConfigViewportsNoDefaultParent) ImGui::Text("io.ConfigViewportsNoDefaultParent"); - if (io.ConfigDockingNoSplit) ImGui::Text("io.ConfigDockingNoSplit"); - if (io.ConfigDockingWithShift) ImGui::Text("io.ConfigDockingWithShift"); - if (io.ConfigDockingAlwaysTabBar) ImGui::Text("io.ConfigDockingAlwaysTabBar"); - if (io.ConfigDockingTransparentPayload) ImGui::Text("io.ConfigDockingTransparentPayload"); - if (io.ConfigMacOSXBehaviors) ImGui::Text("io.ConfigMacOSXBehaviors"); - if (io.ConfigInputTextCursorBlink) ImGui::Text("io.ConfigInputTextCursorBlink"); - if (io.ConfigWindowsResizeFromEdges) ImGui::Text("io.ConfigWindowsResizeFromEdges"); - if (io.ConfigWindowsMoveFromTitleBarOnly) ImGui::Text("io.ConfigWindowsMoveFromTitleBarOnly"); - if (io.ConfigMemoryCompactTimer >= 0.0f) ImGui::Text("io.ConfigMemoryCompactTimer = %.1f", io.ConfigMemoryCompactTimer); - ImGui::Text("io.BackendFlags: 0x%08X", io.BackendFlags); - if (io.BackendFlags & ImGuiBackendFlags_HasGamepad) ImGui::Text(" HasGamepad"); - if (io.BackendFlags & ImGuiBackendFlags_HasMouseCursors) ImGui::Text(" HasMouseCursors"); - if (io.BackendFlags & ImGuiBackendFlags_HasSetMousePos) ImGui::Text(" HasSetMousePos"); - if (io.BackendFlags & ImGuiBackendFlags_PlatformHasViewports) ImGui::Text(" PlatformHasViewports"); - if (io.BackendFlags & ImGuiBackendFlags_HasMouseHoveredViewport)ImGui::Text(" HasMouseHoveredViewport"); - if (io.BackendFlags & ImGuiBackendFlags_RendererHasVtxOffset) ImGui::Text(" RendererHasVtxOffset"); - if (io.BackendFlags & ImGuiBackendFlags_RendererHasViewports) ImGui::Text(" RendererHasViewports"); - ImGui::Separator(); - ImGui::Text("io.Fonts: %d fonts, Flags: 0x%08X, TexSize: %d,%d", io.Fonts->Fonts.Size, io.Fonts->Flags, io.Fonts->TexWidth, io.Fonts->TexHeight); - ImGui::Text("io.DisplaySize: %.2f,%.2f", io.DisplaySize.x, io.DisplaySize.y); - ImGui::Text("io.DisplayFramebufferScale: %.2f,%.2f", io.DisplayFramebufferScale.x, io.DisplayFramebufferScale.y); - ImGui::Separator(); - ImGui::Text("style.WindowPadding: %.2f,%.2f", style.WindowPadding.x, style.WindowPadding.y); - ImGui::Text("style.WindowBorderSize: %.2f", style.WindowBorderSize); - ImGui::Text("style.FramePadding: %.2f,%.2f", style.FramePadding.x, style.FramePadding.y); - ImGui::Text("style.FrameRounding: %.2f", style.FrameRounding); - ImGui::Text("style.FrameBorderSize: %.2f", style.FrameBorderSize); - ImGui::Text("style.ItemSpacing: %.2f,%.2f", style.ItemSpacing.x, style.ItemSpacing.y); - ImGui::Text("style.ItemInnerSpacing: %.2f,%.2f", style.ItemInnerSpacing.x, style.ItemInnerSpacing.y); - - if (copy_to_clipboard) - { - ImGui::LogText("\n```\n"); - ImGui::LogFinish(); - } - ImGui::EndChildFrame(); - } - ImGui::End(); -} - -//----------------------------------------------------------------------------- -// [SECTION] Style Editor / ShowStyleEditor() -//----------------------------------------------------------------------------- -// - ShowFontSelector() -// - ShowStyleSelector() -// - ShowStyleEditor() -//----------------------------------------------------------------------------- - -// Forward declare ShowFontAtlas() which isn't worth putting in public API yet -namespace ImGui { IMGUI_API void ShowFontAtlas(ImFontAtlas* atlas); } - -// Demo helper function to select among loaded fonts. -// Here we use the regular BeginCombo()/EndCombo() api which is the more flexible one. -void ImGui::ShowFontSelector(const char* label) -{ - ImGuiIO& io = ImGui::GetIO(); - ImFont* font_current = ImGui::GetFont(); - if (ImGui::BeginCombo(label, font_current->GetDebugName())) - { - for (ImFont* font : io.Fonts->Fonts) - { - ImGui::PushID((void*)font); - if (ImGui::Selectable(font->GetDebugName(), font == font_current)) - io.FontDefault = font; - ImGui::PopID(); - } - ImGui::EndCombo(); - } - ImGui::SameLine(); - HelpMarker( - "- Load additional fonts with io.Fonts->AddFontFromFileTTF().\n" - "- The font atlas is built when calling io.Fonts->GetTexDataAsXXXX() or io.Fonts->Build().\n" - "- Read FAQ and docs/FONTS.md for more details.\n" - "- If you need to add/remove fonts at runtime (e.g. for DPI change), do it before calling NewFrame()."); -} - -// Demo helper function to select among default colors. See ShowStyleEditor() for more advanced options. -// Here we use the simplified Combo() api that packs items into a single literal string. -// Useful for quick combo boxes where the choices are known locally. -bool ImGui::ShowStyleSelector(const char* label) -{ - static int style_idx = -1; - if (ImGui::Combo(label, &style_idx, "Dark\0Light\0Classic\0")) - { - switch (style_idx) - { - case 0: ImGui::StyleColorsDark(); break; - case 1: ImGui::StyleColorsLight(); break; - case 2: ImGui::StyleColorsClassic(); break; - } - return true; - } - return false; -} - -void ImGui::ShowStyleEditor(ImGuiStyle* ref) -{ - IMGUI_DEMO_MARKER("Tools/Style Editor"); - // You can pass in a reference ImGuiStyle structure to compare to, revert to and save to - // (without a reference style pointer, we will use one compared locally as a reference) - ImGuiStyle& style = ImGui::GetStyle(); - static ImGuiStyle ref_saved_style; - - // Default to using internal storage as reference - static bool init = true; - if (init && ref == NULL) - ref_saved_style = style; - init = false; - if (ref == NULL) - ref = &ref_saved_style; - - ImGui::PushItemWidth(ImGui::GetWindowWidth() * 0.50f); - - if (ImGui::ShowStyleSelector("Colors##Selector")) - ref_saved_style = style; - ImGui::ShowFontSelector("Fonts##Selector"); - - // Simplified Settings (expose floating-pointer border sizes as boolean representing 0.0f or 1.0f) - if (ImGui::SliderFloat("FrameRounding", &style.FrameRounding, 0.0f, 12.0f, "%.0f")) - style.GrabRounding = style.FrameRounding; // Make GrabRounding always the same value as FrameRounding - { bool border = (style.WindowBorderSize > 0.0f); if (ImGui::Checkbox("WindowBorder", &border)) { style.WindowBorderSize = border ? 1.0f : 0.0f; } } - ImGui::SameLine(); - { bool border = (style.FrameBorderSize > 0.0f); if (ImGui::Checkbox("FrameBorder", &border)) { style.FrameBorderSize = border ? 1.0f : 0.0f; } } - ImGui::SameLine(); - { bool border = (style.PopupBorderSize > 0.0f); if (ImGui::Checkbox("PopupBorder", &border)) { style.PopupBorderSize = border ? 1.0f : 0.0f; } } - - // Save/Revert button - if (ImGui::Button("Save Ref")) - *ref = ref_saved_style = style; - ImGui::SameLine(); - if (ImGui::Button("Revert Ref")) - style = *ref; - ImGui::SameLine(); - HelpMarker( - "Save/Revert in local non-persistent storage. Default Colors definition are not affected. " - "Use \"Export\" below to save them somewhere."); - - ImGui::Separator(); - - if (ImGui::BeginTabBar("##tabs", ImGuiTabBarFlags_None)) - { - if (ImGui::BeginTabItem("Sizes")) - { - ImGui::SeparatorText("Main"); - ImGui::SliderFloat2("WindowPadding", (float*)&style.WindowPadding, 0.0f, 20.0f, "%.0f"); - ImGui::SliderFloat2("FramePadding", (float*)&style.FramePadding, 0.0f, 20.0f, "%.0f"); - ImGui::SliderFloat2("ItemSpacing", (float*)&style.ItemSpacing, 0.0f, 20.0f, "%.0f"); - ImGui::SliderFloat2("ItemInnerSpacing", (float*)&style.ItemInnerSpacing, 0.0f, 20.0f, "%.0f"); - ImGui::SliderFloat2("TouchExtraPadding", (float*)&style.TouchExtraPadding, 0.0f, 10.0f, "%.0f"); - ImGui::SliderFloat("IndentSpacing", &style.IndentSpacing, 0.0f, 30.0f, "%.0f"); - ImGui::SliderFloat("ScrollbarSize", &style.ScrollbarSize, 1.0f, 20.0f, "%.0f"); - ImGui::SliderFloat("GrabMinSize", &style.GrabMinSize, 1.0f, 20.0f, "%.0f"); - - ImGui::SeparatorText("Borders"); - ImGui::SliderFloat("WindowBorderSize", &style.WindowBorderSize, 0.0f, 1.0f, "%.0f"); - ImGui::SliderFloat("ChildBorderSize", &style.ChildBorderSize, 0.0f, 1.0f, "%.0f"); - ImGui::SliderFloat("PopupBorderSize", &style.PopupBorderSize, 0.0f, 1.0f, "%.0f"); - ImGui::SliderFloat("FrameBorderSize", &style.FrameBorderSize, 0.0f, 1.0f, "%.0f"); - ImGui::SliderFloat("TabBorderSize", &style.TabBorderSize, 0.0f, 1.0f, "%.0f"); - ImGui::SliderFloat("TabBarBorderSize", &style.TabBarBorderSize, 0.0f, 2.0f, "%.0f"); - - ImGui::SeparatorText("Rounding"); - ImGui::SliderFloat("WindowRounding", &style.WindowRounding, 0.0f, 12.0f, "%.0f"); - ImGui::SliderFloat("ChildRounding", &style.ChildRounding, 0.0f, 12.0f, "%.0f"); - ImGui::SliderFloat("FrameRounding", &style.FrameRounding, 0.0f, 12.0f, "%.0f"); - ImGui::SliderFloat("PopupRounding", &style.PopupRounding, 0.0f, 12.0f, "%.0f"); - ImGui::SliderFloat("ScrollbarRounding", &style.ScrollbarRounding, 0.0f, 12.0f, "%.0f"); - ImGui::SliderFloat("GrabRounding", &style.GrabRounding, 0.0f, 12.0f, "%.0f"); - ImGui::SliderFloat("TabRounding", &style.TabRounding, 0.0f, 12.0f, "%.0f"); - - ImGui::SeparatorText("Tables"); - ImGui::SliderFloat2("CellPadding", (float*)&style.CellPadding, 0.0f, 20.0f, "%.0f"); - ImGui::SliderAngle("TableAngledHeadersAngle", &style.TableAngledHeadersAngle, -50.0f, +50.0f); - - ImGui::SeparatorText("Widgets"); - ImGui::SliderFloat2("WindowTitleAlign", (float*)&style.WindowTitleAlign, 0.0f, 1.0f, "%.2f"); - int window_menu_button_position = style.WindowMenuButtonPosition + 1; - if (ImGui::Combo("WindowMenuButtonPosition", (int*)&window_menu_button_position, "None\0Left\0Right\0")) - style.WindowMenuButtonPosition = window_menu_button_position - 1; - ImGui::Combo("ColorButtonPosition", (int*)&style.ColorButtonPosition, "Left\0Right\0"); - ImGui::SliderFloat2("ButtonTextAlign", (float*)&style.ButtonTextAlign, 0.0f, 1.0f, "%.2f"); - ImGui::SameLine(); HelpMarker("Alignment applies when a button is larger than its text content."); - ImGui::SliderFloat2("SelectableTextAlign", (float*)&style.SelectableTextAlign, 0.0f, 1.0f, "%.2f"); - ImGui::SameLine(); HelpMarker("Alignment applies when a selectable is larger than its text content."); - ImGui::SliderFloat("SeparatorTextBorderSize", &style.SeparatorTextBorderSize, 0.0f, 10.0f, "%.0f"); - ImGui::SliderFloat2("SeparatorTextAlign", (float*)&style.SeparatorTextAlign, 0.0f, 1.0f, "%.2f"); - ImGui::SliderFloat2("SeparatorTextPadding", (float*)&style.SeparatorTextPadding, 0.0f, 40.0f, "%.0f"); - ImGui::SliderFloat("LogSliderDeadzone", &style.LogSliderDeadzone, 0.0f, 12.0f, "%.0f"); - - ImGui::SeparatorText("Docking"); - ImGui::SliderFloat("DockingSplitterSize", &style.DockingSeparatorSize, 0.0f, 12.0f, "%.0f"); - - ImGui::SeparatorText("Tooltips"); - for (int n = 0; n < 2; n++) - if (ImGui::TreeNodeEx(n == 0 ? "HoverFlagsForTooltipMouse" : "HoverFlagsForTooltipNav")) - { - ImGuiHoveredFlags* p = (n == 0) ? &style.HoverFlagsForTooltipMouse : &style.HoverFlagsForTooltipNav; - ImGui::CheckboxFlags("ImGuiHoveredFlags_DelayNone", p, ImGuiHoveredFlags_DelayNone); - ImGui::CheckboxFlags("ImGuiHoveredFlags_DelayShort", p, ImGuiHoveredFlags_DelayShort); - ImGui::CheckboxFlags("ImGuiHoveredFlags_DelayNormal", p, ImGuiHoveredFlags_DelayNormal); - ImGui::CheckboxFlags("ImGuiHoveredFlags_Stationary", p, ImGuiHoveredFlags_Stationary); - ImGui::CheckboxFlags("ImGuiHoveredFlags_NoSharedDelay", p, ImGuiHoveredFlags_NoSharedDelay); - ImGui::TreePop(); - } - - ImGui::SeparatorText("Misc"); - ImGui::SliderFloat2("DisplaySafeAreaPadding", (float*)&style.DisplaySafeAreaPadding, 0.0f, 30.0f, "%.0f"); ImGui::SameLine(); HelpMarker("Adjust if you cannot see the edges of your screen (e.g. on a TV where scaling has not been configured)."); - - ImGui::EndTabItem(); - } - - if (ImGui::BeginTabItem("Colors")) - { - static int output_dest = 0; - static bool output_only_modified = true; - if (ImGui::Button("Export")) - { - if (output_dest == 0) - ImGui::LogToClipboard(); - else - ImGui::LogToTTY(); - ImGui::LogText("ImVec4* colors = ImGui::GetStyle().Colors;" IM_NEWLINE); - for (int i = 0; i < ImGuiCol_COUNT; i++) - { - const ImVec4& col = style.Colors[i]; - const char* name = ImGui::GetStyleColorName(i); - if (!output_only_modified || memcmp(&col, &ref->Colors[i], sizeof(ImVec4)) != 0) - ImGui::LogText("colors[ImGuiCol_%s]%*s= ImVec4(%.2ff, %.2ff, %.2ff, %.2ff);" IM_NEWLINE, - name, 23 - (int)strlen(name), "", col.x, col.y, col.z, col.w); - } - ImGui::LogFinish(); - } - ImGui::SameLine(); ImGui::SetNextItemWidth(120); ImGui::Combo("##output_type", &output_dest, "To Clipboard\0To TTY\0"); - ImGui::SameLine(); ImGui::Checkbox("Only Modified Colors", &output_only_modified); - - static ImGuiTextFilter filter; - filter.Draw("Filter colors", ImGui::GetFontSize() * 16); - - static ImGuiColorEditFlags alpha_flags = 0; - if (ImGui::RadioButton("Opaque", alpha_flags == ImGuiColorEditFlags_None)) { alpha_flags = ImGuiColorEditFlags_None; } ImGui::SameLine(); - if (ImGui::RadioButton("Alpha", alpha_flags == ImGuiColorEditFlags_AlphaPreview)) { alpha_flags = ImGuiColorEditFlags_AlphaPreview; } ImGui::SameLine(); - if (ImGui::RadioButton("Both", alpha_flags == ImGuiColorEditFlags_AlphaPreviewHalf)) { alpha_flags = ImGuiColorEditFlags_AlphaPreviewHalf; } ImGui::SameLine(); - HelpMarker( - "In the color list:\n" - "Left-click on color square to open color picker,\n" - "Right-click to open edit options menu."); - - ImGui::BeginChild("##colors", ImVec2(0, 0), true, ImGuiWindowFlags_AlwaysVerticalScrollbar | ImGuiWindowFlags_AlwaysHorizontalScrollbar | ImGuiWindowFlags_NavFlattened); - ImGui::PushItemWidth(-160); - for (int i = 0; i < ImGuiCol_COUNT; i++) - { - const char* name = ImGui::GetStyleColorName(i); - if (!filter.PassFilter(name)) - continue; - ImGui::PushID(i); - ImGui::ColorEdit4("##color", (float*)&style.Colors[i], ImGuiColorEditFlags_AlphaBar | alpha_flags); - if (memcmp(&style.Colors[i], &ref->Colors[i], sizeof(ImVec4)) != 0) - { - // Tips: in a real user application, you may want to merge and use an icon font into the main font, - // so instead of "Save"/"Revert" you'd use icons! - // Read the FAQ and docs/FONTS.md about using icon fonts. It's really easy and super convenient! - ImGui::SameLine(0.0f, style.ItemInnerSpacing.x); if (ImGui::Button("Save")) { ref->Colors[i] = style.Colors[i]; } - ImGui::SameLine(0.0f, style.ItemInnerSpacing.x); if (ImGui::Button("Revert")) { style.Colors[i] = ref->Colors[i]; } - } - ImGui::SameLine(0.0f, style.ItemInnerSpacing.x); - ImGui::TextUnformatted(name); - ImGui::PopID(); - } - ImGui::PopItemWidth(); - ImGui::EndChild(); - - ImGui::EndTabItem(); - } - - if (ImGui::BeginTabItem("Fonts")) - { - ImGuiIO& io = ImGui::GetIO(); - ImFontAtlas* atlas = io.Fonts; - HelpMarker("Read FAQ and docs/FONTS.md for details on font loading."); - ImGui::ShowFontAtlas(atlas); - - // Post-baking font scaling. Note that this is NOT the nice way of scaling fonts, read below. - // (we enforce hard clamping manually as by default DragFloat/SliderFloat allows CTRL+Click text to get out of bounds). - const float MIN_SCALE = 0.3f; - const float MAX_SCALE = 2.0f; - HelpMarker( - "Those are old settings provided for convenience.\n" - "However, the _correct_ way of scaling your UI is currently to reload your font at the designed size, " - "rebuild the font atlas, and call style.ScaleAllSizes() on a reference ImGuiStyle structure.\n" - "Using those settings here will give you poor quality results."); - static float window_scale = 1.0f; - ImGui::PushItemWidth(ImGui::GetFontSize() * 8); - if (ImGui::DragFloat("window scale", &window_scale, 0.005f, MIN_SCALE, MAX_SCALE, "%.2f", ImGuiSliderFlags_AlwaysClamp)) // Scale only this window - ImGui::SetWindowFontScale(window_scale); - ImGui::DragFloat("global scale", &io.FontGlobalScale, 0.005f, MIN_SCALE, MAX_SCALE, "%.2f", ImGuiSliderFlags_AlwaysClamp); // Scale everything - ImGui::PopItemWidth(); - - ImGui::EndTabItem(); - } - - if (ImGui::BeginTabItem("Rendering")) - { - ImGui::Checkbox("Anti-aliased lines", &style.AntiAliasedLines); - ImGui::SameLine(); - HelpMarker("When disabling anti-aliasing lines, you'll probably want to disable borders in your style as well."); - - ImGui::Checkbox("Anti-aliased lines use texture", &style.AntiAliasedLinesUseTex); - ImGui::SameLine(); - HelpMarker("Faster lines using texture data. Require backend to render with bilinear filtering (not point/nearest filtering)."); - - ImGui::Checkbox("Anti-aliased fill", &style.AntiAliasedFill); - ImGui::PushItemWidth(ImGui::GetFontSize() * 8); - ImGui::DragFloat("Curve Tessellation Tolerance", &style.CurveTessellationTol, 0.02f, 0.10f, 10.0f, "%.2f"); - if (style.CurveTessellationTol < 0.10f) style.CurveTessellationTol = 0.10f; - - // When editing the "Circle Segment Max Error" value, draw a preview of its effect on auto-tessellated circles. - ImGui::DragFloat("Circle Tessellation Max Error", &style.CircleTessellationMaxError , 0.005f, 0.10f, 5.0f, "%.2f", ImGuiSliderFlags_AlwaysClamp); - const bool show_samples = ImGui::IsItemActive(); - if (show_samples) - ImGui::SetNextWindowPos(ImGui::GetCursorScreenPos()); - if (show_samples && ImGui::BeginTooltip()) - { - ImGui::TextUnformatted("(R = radius, N = number of segments)"); - ImGui::Spacing(); - ImDrawList* draw_list = ImGui::GetWindowDrawList(); - const float min_widget_width = ImGui::CalcTextSize("N: MMM\nR: MMM").x; - for (int n = 0; n < 8; n++) - { - const float RAD_MIN = 5.0f; - const float RAD_MAX = 70.0f; - const float rad = RAD_MIN + (RAD_MAX - RAD_MIN) * (float)n / (8.0f - 1.0f); - - ImGui::BeginGroup(); - - ImGui::Text("R: %.f\nN: %d", rad, draw_list->_CalcCircleAutoSegmentCount(rad)); - - const float canvas_width = IM_MAX(min_widget_width, rad * 2.0f); - const float offset_x = floorf(canvas_width * 0.5f); - const float offset_y = floorf(RAD_MAX); - - const ImVec2 p1 = ImGui::GetCursorScreenPos(); - draw_list->AddCircle(ImVec2(p1.x + offset_x, p1.y + offset_y), rad, ImGui::GetColorU32(ImGuiCol_Text)); - ImGui::Dummy(ImVec2(canvas_width, RAD_MAX * 2)); - - /* - const ImVec2 p2 = ImGui::GetCursorScreenPos(); - draw_list->AddCircleFilled(ImVec2(p2.x + offset_x, p2.y + offset_y), rad, ImGui::GetColorU32(ImGuiCol_Text)); - ImGui::Dummy(ImVec2(canvas_width, RAD_MAX * 2)); - */ - - ImGui::EndGroup(); - ImGui::SameLine(); - } - ImGui::EndTooltip(); - } - ImGui::SameLine(); - HelpMarker("When drawing circle primitives with \"num_segments == 0\" tesselation will be calculated automatically."); - - ImGui::DragFloat("Global Alpha", &style.Alpha, 0.005f, 0.20f, 1.0f, "%.2f"); // Not exposing zero here so user doesn't "lose" the UI (zero alpha clips all widgets). But application code could have a toggle to switch between zero and non-zero. - ImGui::DragFloat("Disabled Alpha", &style.DisabledAlpha, 0.005f, 0.0f, 1.0f, "%.2f"); ImGui::SameLine(); HelpMarker("Additional alpha multiplier for disabled items (multiply over current value of Alpha)."); - ImGui::PopItemWidth(); - - ImGui::EndTabItem(); - } - - ImGui::EndTabBar(); - } - - ImGui::PopItemWidth(); -} - -//----------------------------------------------------------------------------- -// [SECTION] User Guide / ShowUserGuide() -//----------------------------------------------------------------------------- - -void ImGui::ShowUserGuide() -{ - ImGuiIO& io = ImGui::GetIO(); - ImGui::BulletText("Double-click on title bar to collapse window."); - ImGui::BulletText( - "Click and drag on lower corner to resize window\n" - "(double-click to auto fit window to its contents)."); - ImGui::BulletText("CTRL+Click on a slider or drag box to input value as text."); - ImGui::BulletText("TAB/SHIFT+TAB to cycle through keyboard editable fields."); - ImGui::BulletText("CTRL+Tab to select a window."); - if (io.FontAllowUserScaling) - ImGui::BulletText("CTRL+Mouse Wheel to zoom window contents."); - ImGui::BulletText("While inputing text:\n"); - ImGui::Indent(); - ImGui::BulletText("CTRL+Left/Right to word jump."); - ImGui::BulletText("CTRL+A or double-click to select all."); - ImGui::BulletText("CTRL+X/C/V to use clipboard cut/copy/paste."); - ImGui::BulletText("CTRL+Z,CTRL+Y to undo/redo."); - ImGui::BulletText("ESCAPE to revert."); - ImGui::Unindent(); - ImGui::BulletText("With keyboard navigation enabled:"); - ImGui::Indent(); - ImGui::BulletText("Arrow keys to navigate."); - ImGui::BulletText("Space to activate a widget."); - ImGui::BulletText("Return to input text into a widget."); - ImGui::BulletText("Escape to deactivate a widget, close popup, exit child window."); - ImGui::BulletText("Alt to jump to the menu layer of a window."); - ImGui::Unindent(); -} - -//----------------------------------------------------------------------------- -// [SECTION] Example App: Main Menu Bar / ShowExampleAppMainMenuBar() -//----------------------------------------------------------------------------- -// - ShowExampleAppMainMenuBar() -// - ShowExampleMenuFile() -//----------------------------------------------------------------------------- - -// Demonstrate creating a "main" fullscreen menu bar and populating it. -// Note the difference between BeginMainMenuBar() and BeginMenuBar(): -// - BeginMenuBar() = menu-bar inside current window (which needs the ImGuiWindowFlags_MenuBar flag!) -// - BeginMainMenuBar() = helper to create menu-bar-sized window at the top of the main viewport + call BeginMenuBar() into it. -static void ShowExampleAppMainMenuBar() -{ - if (ImGui::BeginMainMenuBar()) - { - if (ImGui::BeginMenu("File")) - { - ShowExampleMenuFile(); - ImGui::EndMenu(); - } - if (ImGui::BeginMenu("Edit")) - { - if (ImGui::MenuItem("Undo", "CTRL+Z")) {} - if (ImGui::MenuItem("Redo", "CTRL+Y", false, false)) {} // Disabled item - ImGui::Separator(); - if (ImGui::MenuItem("Cut", "CTRL+X")) {} - if (ImGui::MenuItem("Copy", "CTRL+C")) {} - if (ImGui::MenuItem("Paste", "CTRL+V")) {} - ImGui::EndMenu(); - } - ImGui::EndMainMenuBar(); - } -} - -// Note that shortcuts are currently provided for display only -// (future version will add explicit flags to BeginMenu() to request processing shortcuts) -static void ShowExampleMenuFile() -{ - IMGUI_DEMO_MARKER("Examples/Menu"); - ImGui::MenuItem("(demo menu)", NULL, false, false); - if (ImGui::MenuItem("New")) {} - if (ImGui::MenuItem("Open", "Ctrl+O")) {} - if (ImGui::BeginMenu("Open Recent")) - { - ImGui::MenuItem("fish_hat.c"); - ImGui::MenuItem("fish_hat.inl"); - ImGui::MenuItem("fish_hat.h"); - if (ImGui::BeginMenu("More..")) - { - ImGui::MenuItem("Hello"); - ImGui::MenuItem("Sailor"); - if (ImGui::BeginMenu("Recurse..")) - { - ShowExampleMenuFile(); - ImGui::EndMenu(); - } - ImGui::EndMenu(); - } - ImGui::EndMenu(); - } - if (ImGui::MenuItem("Save", "Ctrl+S")) {} - if (ImGui::MenuItem("Save As..")) {} - - ImGui::Separator(); - IMGUI_DEMO_MARKER("Examples/Menu/Options"); - if (ImGui::BeginMenu("Options")) - { - static bool enabled = true; - ImGui::MenuItem("Enabled", "", &enabled); - ImGui::BeginChild("child", ImVec2(0, 60), true); - for (int i = 0; i < 10; i++) - ImGui::Text("Scrolling Text %d", i); - ImGui::EndChild(); - static float f = 0.5f; - static int n = 0; - ImGui::SliderFloat("Value", &f, 0.0f, 1.0f); - ImGui::InputFloat("Input", &f, 0.1f); - ImGui::Combo("Combo", &n, "Yes\0No\0Maybe\0\0"); - ImGui::EndMenu(); - } - - IMGUI_DEMO_MARKER("Examples/Menu/Colors"); - if (ImGui::BeginMenu("Colors")) - { - float sz = ImGui::GetTextLineHeight(); - for (int i = 0; i < ImGuiCol_COUNT; i++) - { - const char* name = ImGui::GetStyleColorName((ImGuiCol)i); - ImVec2 p = ImGui::GetCursorScreenPos(); - ImGui::GetWindowDrawList()->AddRectFilled(p, ImVec2(p.x + sz, p.y + sz), ImGui::GetColorU32((ImGuiCol)i)); - ImGui::Dummy(ImVec2(sz, sz)); - ImGui::SameLine(); - ImGui::MenuItem(name); - } - ImGui::EndMenu(); - } - - // Here we demonstrate appending again to the "Options" menu (which we already created above) - // Of course in this demo it is a little bit silly that this function calls BeginMenu("Options") twice. - // In a real code-base using it would make senses to use this feature from very different code locations. - if (ImGui::BeginMenu("Options")) // <-- Append! - { - IMGUI_DEMO_MARKER("Examples/Menu/Append to an existing menu"); - static bool b = true; - ImGui::Checkbox("SomeOption", &b); - ImGui::EndMenu(); - } - - if (ImGui::BeginMenu("Disabled", false)) // Disabled - { - IM_ASSERT(0); - } - if (ImGui::MenuItem("Checked", NULL, true)) {} - ImGui::Separator(); - if (ImGui::MenuItem("Quit", "Alt+F4")) {} -} - -//----------------------------------------------------------------------------- -// [SECTION] Example App: Debug Console / ShowExampleAppConsole() -//----------------------------------------------------------------------------- - -// Demonstrate creating a simple console window, with scrolling, filtering, completion and history. -// For the console example, we are using a more C++ like approach of declaring a class to hold both data and functions. -struct ExampleAppConsole -{ - char InputBuf[256]; - ImVector Items; - ImVector Commands; - ImVector History; - int HistoryPos; // -1: new line, 0..History.Size-1 browsing history. - ImGuiTextFilter Filter; - bool AutoScroll; - bool ScrollToBottom; - - ExampleAppConsole() - { - IMGUI_DEMO_MARKER("Examples/Console"); - ClearLog(); - memset(InputBuf, 0, sizeof(InputBuf)); - HistoryPos = -1; - - // "CLASSIFY" is here to provide the test case where "C"+[tab] completes to "CL" and display multiple matches. - Commands.push_back("HELP"); - Commands.push_back("HISTORY"); - Commands.push_back("CLEAR"); - Commands.push_back("CLASSIFY"); - AutoScroll = true; - ScrollToBottom = false; - AddLog("Welcome to Dear ImGui!"); - } - ~ExampleAppConsole() - { - ClearLog(); - for (int i = 0; i < History.Size; i++) - free(History[i]); - } - - // Portable helpers - static int Stricmp(const char* s1, const char* s2) { int d; while ((d = toupper(*s2) - toupper(*s1)) == 0 && *s1) { s1++; s2++; } return d; } - static int Strnicmp(const char* s1, const char* s2, int n) { int d = 0; while (n > 0 && (d = toupper(*s2) - toupper(*s1)) == 0 && *s1) { s1++; s2++; n--; } return d; } - static char* Strdup(const char* s) { IM_ASSERT(s); size_t len = strlen(s) + 1; void* buf = malloc(len); IM_ASSERT(buf); return (char*)memcpy(buf, (const void*)s, len); } - static void Strtrim(char* s) { char* str_end = s + strlen(s); while (str_end > s && str_end[-1] == ' ') str_end--; *str_end = 0; } - - void ClearLog() - { - for (int i = 0; i < Items.Size; i++) - free(Items[i]); - Items.clear(); - } - - void AddLog(const char* fmt, ...) IM_FMTARGS(2) - { - // FIXME-OPT - char buf[1024]; - va_list args; - va_start(args, fmt); - vsnprintf(buf, IM_ARRAYSIZE(buf), fmt, args); - buf[IM_ARRAYSIZE(buf)-1] = 0; - va_end(args); - Items.push_back(Strdup(buf)); - } - - void Draw(const char* title, bool* p_open) - { - ImGui::SetNextWindowSize(ImVec2(520, 600), ImGuiCond_FirstUseEver); - if (!ImGui::Begin(title, p_open)) - { - ImGui::End(); - return; - } - - // As a specific feature guaranteed by the library, after calling Begin() the last Item represent the title bar. - // So e.g. IsItemHovered() will return true when hovering the title bar. - // Here we create a context menu only available from the title bar. - if (ImGui::BeginPopupContextItem()) - { - if (ImGui::MenuItem("Close Console")) - *p_open = false; - ImGui::EndPopup(); - } - - ImGui::TextWrapped( - "This example implements a console with basic coloring, completion (TAB key) and history (Up/Down keys). A more elaborate " - "implementation may want to store entries along with extra data such as timestamp, emitter, etc."); - ImGui::TextWrapped("Enter 'HELP' for help."); - - // TODO: display items starting from the bottom - - if (ImGui::SmallButton("Add Debug Text")) { AddLog("%d some text", Items.Size); AddLog("some more text"); AddLog("display very important message here!"); } - ImGui::SameLine(); - if (ImGui::SmallButton("Add Debug Error")) { AddLog("[error] something went wrong"); } - ImGui::SameLine(); - if (ImGui::SmallButton("Clear")) { ClearLog(); } - ImGui::SameLine(); - bool copy_to_clipboard = ImGui::SmallButton("Copy"); - //static float t = 0.0f; if (ImGui::GetTime() - t > 0.02f) { t = ImGui::GetTime(); AddLog("Spam %f", t); } - - ImGui::Separator(); - - // Options menu - if (ImGui::BeginPopup("Options")) - { - ImGui::Checkbox("Auto-scroll", &AutoScroll); - ImGui::EndPopup(); - } - - // Options, Filter - if (ImGui::Button("Options")) - ImGui::OpenPopup("Options"); - ImGui::SameLine(); - Filter.Draw("Filter (\"incl,-excl\") (\"error\")", 180); - ImGui::Separator(); - - // Reserve enough left-over height for 1 separator + 1 input text - const float footer_height_to_reserve = ImGui::GetStyle().ItemSpacing.y + ImGui::GetFrameHeightWithSpacing(); - if (ImGui::BeginChild("ScrollingRegion", ImVec2(0, -footer_height_to_reserve), false, ImGuiWindowFlags_HorizontalScrollbar)) - { - if (ImGui::BeginPopupContextWindow()) - { - if (ImGui::Selectable("Clear")) ClearLog(); - ImGui::EndPopup(); - } - - // Display every line as a separate entry so we can change their color or add custom widgets. - // If you only want raw text you can use ImGui::TextUnformatted(log.begin(), log.end()); - // NB- if you have thousands of entries this approach may be too inefficient and may require user-side clipping - // to only process visible items. The clipper will automatically measure the height of your first item and then - // "seek" to display only items in the visible area. - // To use the clipper we can replace your standard loop: - // for (int i = 0; i < Items.Size; i++) - // With: - // ImGuiListClipper clipper; - // clipper.Begin(Items.Size); - // while (clipper.Step()) - // for (int i = clipper.DisplayStart; i < clipper.DisplayEnd; i++) - // - That your items are evenly spaced (same height) - // - That you have cheap random access to your elements (you can access them given their index, - // without processing all the ones before) - // You cannot this code as-is if a filter is active because it breaks the 'cheap random-access' property. - // We would need random-access on the post-filtered list. - // A typical application wanting coarse clipping and filtering may want to pre-compute an array of indices - // or offsets of items that passed the filtering test, recomputing this array when user changes the filter, - // and appending newly elements as they are inserted. This is left as a task to the user until we can manage - // to improve this example code! - // If your items are of variable height: - // - Split them into same height items would be simpler and facilitate random-seeking into your list. - // - Consider using manual call to IsRectVisible() and skipping extraneous decoration from your items. - ImGui::PushStyleVar(ImGuiStyleVar_ItemSpacing, ImVec2(4, 1)); // Tighten spacing - if (copy_to_clipboard) - ImGui::LogToClipboard(); - for (const char* item : Items) - { - if (!Filter.PassFilter(item)) - continue; - - // Normally you would store more information in your item than just a string. - // (e.g. make Items[] an array of structure, store color/type etc.) - ImVec4 color; - bool has_color = false; - if (strstr(item, "[error]")) { color = ImVec4(1.0f, 0.4f, 0.4f, 1.0f); has_color = true; } - else if (strncmp(item, "# ", 2) == 0) { color = ImVec4(1.0f, 0.8f, 0.6f, 1.0f); has_color = true; } - if (has_color) - ImGui::PushStyleColor(ImGuiCol_Text, color); - ImGui::TextUnformatted(item); - if (has_color) - ImGui::PopStyleColor(); - } - if (copy_to_clipboard) - ImGui::LogFinish(); - - // Keep up at the bottom of the scroll region if we were already at the bottom at the beginning of the frame. - // Using a scrollbar or mouse-wheel will take away from the bottom edge. - if (ScrollToBottom || (AutoScroll && ImGui::GetScrollY() >= ImGui::GetScrollMaxY())) - ImGui::SetScrollHereY(1.0f); - ScrollToBottom = false; - - ImGui::PopStyleVar(); - } - ImGui::EndChild(); - ImGui::Separator(); - - // Command-line - bool reclaim_focus = false; - ImGuiInputTextFlags input_text_flags = ImGuiInputTextFlags_EnterReturnsTrue | ImGuiInputTextFlags_EscapeClearsAll | ImGuiInputTextFlags_CallbackCompletion | ImGuiInputTextFlags_CallbackHistory; - if (ImGui::InputText("Input", InputBuf, IM_ARRAYSIZE(InputBuf), input_text_flags, &TextEditCallbackStub, (void*)this)) - { - char* s = InputBuf; - Strtrim(s); - if (s[0]) - ExecCommand(s); - strcpy(s, ""); - reclaim_focus = true; - } - - // Auto-focus on window apparition - ImGui::SetItemDefaultFocus(); - if (reclaim_focus) - ImGui::SetKeyboardFocusHere(-1); // Auto focus previous widget - - ImGui::End(); - } - - void ExecCommand(const char* command_line) - { - AddLog("# %s\n", command_line); - - // Insert into history. First find match and delete it so it can be pushed to the back. - // This isn't trying to be smart or optimal. - HistoryPos = -1; - for (int i = History.Size - 1; i >= 0; i--) - if (Stricmp(History[i], command_line) == 0) - { - free(History[i]); - History.erase(History.begin() + i); - break; - } - History.push_back(Strdup(command_line)); - - // Process command - if (Stricmp(command_line, "CLEAR") == 0) - { - ClearLog(); - } - else if (Stricmp(command_line, "HELP") == 0) - { - AddLog("Commands:"); - for (int i = 0; i < Commands.Size; i++) - AddLog("- %s", Commands[i]); - } - else if (Stricmp(command_line, "HISTORY") == 0) - { - int first = History.Size - 10; - for (int i = first > 0 ? first : 0; i < History.Size; i++) - AddLog("%3d: %s\n", i, History[i]); - } - else - { - AddLog("Unknown command: '%s'\n", command_line); - } - - // On command input, we scroll to bottom even if AutoScroll==false - ScrollToBottom = true; - } - - // In C++11 you'd be better off using lambdas for this sort of forwarding callbacks - static int TextEditCallbackStub(ImGuiInputTextCallbackData* data) - { - ExampleAppConsole* console = (ExampleAppConsole*)data->UserData; - return console->TextEditCallback(data); - } - - int TextEditCallback(ImGuiInputTextCallbackData* data) - { - //AddLog("cursor: %d, selection: %d-%d", data->CursorPos, data->SelectionStart, data->SelectionEnd); - switch (data->EventFlag) - { - case ImGuiInputTextFlags_CallbackCompletion: - { - // Example of TEXT COMPLETION - - // Locate beginning of current word - const char* word_end = data->Buf + data->CursorPos; - const char* word_start = word_end; - while (word_start > data->Buf) - { - const char c = word_start[-1]; - if (c == ' ' || c == '\t' || c == ',' || c == ';') - break; - word_start--; - } - - // Build a list of candidates - ImVector candidates; - for (int i = 0; i < Commands.Size; i++) - if (Strnicmp(Commands[i], word_start, (int)(word_end - word_start)) == 0) - candidates.push_back(Commands[i]); - - if (candidates.Size == 0) - { - // No match - AddLog("No match for \"%.*s\"!\n", (int)(word_end - word_start), word_start); - } - else if (candidates.Size == 1) - { - // Single match. Delete the beginning of the word and replace it entirely so we've got nice casing. - data->DeleteChars((int)(word_start - data->Buf), (int)(word_end - word_start)); - data->InsertChars(data->CursorPos, candidates[0]); - data->InsertChars(data->CursorPos, " "); - } - else - { - // Multiple matches. Complete as much as we can.. - // So inputing "C"+Tab will complete to "CL" then display "CLEAR" and "CLASSIFY" as matches. - int match_len = (int)(word_end - word_start); - for (;;) - { - int c = 0; - bool all_candidates_matches = true; - for (int i = 0; i < candidates.Size && all_candidates_matches; i++) - if (i == 0) - c = toupper(candidates[i][match_len]); - else if (c == 0 || c != toupper(candidates[i][match_len])) - all_candidates_matches = false; - if (!all_candidates_matches) - break; - match_len++; - } - - if (match_len > 0) - { - data->DeleteChars((int)(word_start - data->Buf), (int)(word_end - word_start)); - data->InsertChars(data->CursorPos, candidates[0], candidates[0] + match_len); - } - - // List matches - AddLog("Possible matches:\n"); - for (int i = 0; i < candidates.Size; i++) - AddLog("- %s\n", candidates[i]); - } - - break; - } - case ImGuiInputTextFlags_CallbackHistory: - { - // Example of HISTORY - const int prev_history_pos = HistoryPos; - if (data->EventKey == ImGuiKey_UpArrow) - { - if (HistoryPos == -1) - HistoryPos = History.Size - 1; - else if (HistoryPos > 0) - HistoryPos--; - } - else if (data->EventKey == ImGuiKey_DownArrow) - { - if (HistoryPos != -1) - if (++HistoryPos >= History.Size) - HistoryPos = -1; - } - - // A better implementation would preserve the data on the current input line along with cursor position. - if (prev_history_pos != HistoryPos) - { - const char* history_str = (HistoryPos >= 0) ? History[HistoryPos] : ""; - data->DeleteChars(0, data->BufTextLen); - data->InsertChars(0, history_str); - } - } - } - return 0; - } -}; - -static void ShowExampleAppConsole(bool* p_open) -{ - static ExampleAppConsole console; - console.Draw("Example: Console", p_open); -} - -//----------------------------------------------------------------------------- -// [SECTION] Example App: Debug Log / ShowExampleAppLog() -//----------------------------------------------------------------------------- - -// Usage: -// static ExampleAppLog my_log; -// my_log.AddLog("Hello %d world\n", 123); -// my_log.Draw("title"); -struct ExampleAppLog -{ - ImGuiTextBuffer Buf; - ImGuiTextFilter Filter; - ImVector LineOffsets; // Index to lines offset. We maintain this with AddLog() calls. - bool AutoScroll; // Keep scrolling if already at the bottom. - - ExampleAppLog() - { - AutoScroll = true; - Clear(); - } - - void Clear() - { - Buf.clear(); - LineOffsets.clear(); - LineOffsets.push_back(0); - } - - void AddLog(const char* fmt, ...) IM_FMTARGS(2) - { - int old_size = Buf.size(); - va_list args; - va_start(args, fmt); - Buf.appendfv(fmt, args); - va_end(args); - for (int new_size = Buf.size(); old_size < new_size; old_size++) - if (Buf[old_size] == '\n') - LineOffsets.push_back(old_size + 1); - } - - void Draw(const char* title, bool* p_open = NULL) - { - if (!ImGui::Begin(title, p_open)) - { - ImGui::End(); - return; - } - - // Options menu - if (ImGui::BeginPopup("Options")) - { - ImGui::Checkbox("Auto-scroll", &AutoScroll); - ImGui::EndPopup(); - } - - // Main window - if (ImGui::Button("Options")) - ImGui::OpenPopup("Options"); - ImGui::SameLine(); - bool clear = ImGui::Button("Clear"); - ImGui::SameLine(); - bool copy = ImGui::Button("Copy"); - ImGui::SameLine(); - Filter.Draw("Filter", -100.0f); - - ImGui::Separator(); - - if (ImGui::BeginChild("scrolling", ImVec2(0, 0), false, ImGuiWindowFlags_HorizontalScrollbar)) - { - if (clear) - Clear(); - if (copy) - ImGui::LogToClipboard(); - - ImGui::PushStyleVar(ImGuiStyleVar_ItemSpacing, ImVec2(0, 0)); - const char* buf = Buf.begin(); - const char* buf_end = Buf.end(); - if (Filter.IsActive()) - { - // In this example we don't use the clipper when Filter is enabled. - // This is because we don't have random access to the result of our filter. - // A real application processing logs with ten of thousands of entries may want to store the result of - // search/filter.. especially if the filtering function is not trivial (e.g. reg-exp). - for (int line_no = 0; line_no < LineOffsets.Size; line_no++) - { - const char* line_start = buf + LineOffsets[line_no]; - const char* line_end = (line_no + 1 < LineOffsets.Size) ? (buf + LineOffsets[line_no + 1] - 1) : buf_end; - if (Filter.PassFilter(line_start, line_end)) - ImGui::TextUnformatted(line_start, line_end); - } - } - else - { - // The simplest and easy way to display the entire buffer: - // ImGui::TextUnformatted(buf_begin, buf_end); - // And it'll just work. TextUnformatted() has specialization for large blob of text and will fast-forward - // to skip non-visible lines. Here we instead demonstrate using the clipper to only process lines that are - // within the visible area. - // If you have tens of thousands of items and their processing cost is non-negligible, coarse clipping them - // on your side is recommended. Using ImGuiListClipper requires - // - A) random access into your data - // - B) items all being the same height, - // both of which we can handle since we have an array pointing to the beginning of each line of text. - // When using the filter (in the block of code above) we don't have random access into the data to display - // anymore, which is why we don't use the clipper. Storing or skimming through the search result would make - // it possible (and would be recommended if you want to search through tens of thousands of entries). - ImGuiListClipper clipper; - clipper.Begin(LineOffsets.Size); - while (clipper.Step()) - { - for (int line_no = clipper.DisplayStart; line_no < clipper.DisplayEnd; line_no++) - { - const char* line_start = buf + LineOffsets[line_no]; - const char* line_end = (line_no + 1 < LineOffsets.Size) ? (buf + LineOffsets[line_no + 1] - 1) : buf_end; - ImGui::TextUnformatted(line_start, line_end); - } - } - clipper.End(); - } - ImGui::PopStyleVar(); - - // Keep up at the bottom of the scroll region if we were already at the bottom at the beginning of the frame. - // Using a scrollbar or mouse-wheel will take away from the bottom edge. - if (AutoScroll && ImGui::GetScrollY() >= ImGui::GetScrollMaxY()) - ImGui::SetScrollHereY(1.0f); - } - ImGui::EndChild(); - ImGui::End(); - } -}; - -// Demonstrate creating a simple log window with basic filtering. -static void ShowExampleAppLog(bool* p_open) -{ - static ExampleAppLog log; - - // For the demo: add a debug button _BEFORE_ the normal log window contents - // We take advantage of a rarely used feature: multiple calls to Begin()/End() are appending to the _same_ window. - // Most of the contents of the window will be added by the log.Draw() call. - ImGui::SetNextWindowSize(ImVec2(500, 400), ImGuiCond_FirstUseEver); - ImGui::Begin("Example: Log", p_open); - IMGUI_DEMO_MARKER("Examples/Log"); - if (ImGui::SmallButton("[Debug] Add 5 entries")) - { - static int counter = 0; - const char* categories[3] = { "info", "warn", "error" }; - const char* words[] = { "Bumfuzzled", "Cattywampus", "Snickersnee", "Abibliophobia", "Absquatulate", "Nincompoop", "Pauciloquent" }; - for (int n = 0; n < 5; n++) - { - const char* category = categories[counter % IM_ARRAYSIZE(categories)]; - const char* word = words[counter % IM_ARRAYSIZE(words)]; - log.AddLog("[%05d] [%s] Hello, current time is %.1f, here's a word: '%s'\n", - ImGui::GetFrameCount(), category, ImGui::GetTime(), word); - counter++; - } - } - ImGui::End(); - - // Actually call in the regular Log helper (which will Begin() into the same window as we just did) - log.Draw("Example: Log", p_open); -} - -//----------------------------------------------------------------------------- -// [SECTION] Example App: Simple Layout / ShowExampleAppLayout() -//----------------------------------------------------------------------------- - -// Demonstrate create a window with multiple child windows. -static void ShowExampleAppLayout(bool* p_open) -{ - ImGui::SetNextWindowSize(ImVec2(500, 440), ImGuiCond_FirstUseEver); - if (ImGui::Begin("Example: Simple layout", p_open, ImGuiWindowFlags_MenuBar)) - { - IMGUI_DEMO_MARKER("Examples/Simple layout"); - if (ImGui::BeginMenuBar()) - { - if (ImGui::BeginMenu("File")) - { - if (ImGui::MenuItem("Close", "Ctrl+W")) { *p_open = false; } - ImGui::EndMenu(); - } - ImGui::EndMenuBar(); - } - - // Left - static int selected = 0; - { - ImGui::BeginChild("left pane", ImVec2(150, 0), true); - for (int i = 0; i < 100; i++) - { - // FIXME: Good candidate to use ImGuiSelectableFlags_SelectOnNav - char label[128]; - sprintf(label, "MyObject %d", i); - if (ImGui::Selectable(label, selected == i)) - selected = i; - } - ImGui::EndChild(); - } - ImGui::SameLine(); - - // Right - { - ImGui::BeginGroup(); - ImGui::BeginChild("item view", ImVec2(0, -ImGui::GetFrameHeightWithSpacing())); // Leave room for 1 line below us - ImGui::Text("MyObject: %d", selected); - ImGui::Separator(); - if (ImGui::BeginTabBar("##Tabs", ImGuiTabBarFlags_None)) - { - if (ImGui::BeginTabItem("Description")) - { - ImGui::TextWrapped("Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. "); - ImGui::EndTabItem(); - } - if (ImGui::BeginTabItem("Details")) - { - ImGui::Text("ID: 0123456789"); - ImGui::EndTabItem(); - } - ImGui::EndTabBar(); - } - ImGui::EndChild(); - if (ImGui::Button("Revert")) {} - ImGui::SameLine(); - if (ImGui::Button("Save")) {} - ImGui::EndGroup(); - } - } - ImGui::End(); -} - -//----------------------------------------------------------------------------- -// [SECTION] Example App: Property Editor / ShowExampleAppPropertyEditor() -//----------------------------------------------------------------------------- - -static void ShowPlaceholderObject(const char* prefix, int uid) -{ - // Use object uid as identifier. Most commonly you could also use the object pointer as a base ID. - ImGui::PushID(uid); - - // Text and Tree nodes are less high than framed widgets, using AlignTextToFramePadding() we add vertical spacing to make the tree lines equal high. - ImGui::TableNextRow(); - ImGui::TableSetColumnIndex(0); - ImGui::AlignTextToFramePadding(); - bool node_open = ImGui::TreeNode("Object", "%s_%u", prefix, uid); - ImGui::TableSetColumnIndex(1); - ImGui::Text("my sailor is rich"); - - if (node_open) - { - static float placeholder_members[8] = { 0.0f, 0.0f, 1.0f, 3.1416f, 100.0f, 999.0f }; - for (int i = 0; i < 8; i++) - { - ImGui::PushID(i); // Use field index as identifier. - if (i < 2) - { - ShowPlaceholderObject("Child", 424242); - } - else - { - // Here we use a TreeNode to highlight on hover (we could use e.g. Selectable as well) - ImGui::TableNextRow(); - ImGui::TableSetColumnIndex(0); - ImGui::AlignTextToFramePadding(); - ImGuiTreeNodeFlags flags = ImGuiTreeNodeFlags_Leaf | ImGuiTreeNodeFlags_NoTreePushOnOpen | ImGuiTreeNodeFlags_Bullet; - ImGui::TreeNodeEx("Field", flags, "Field_%d", i); - - ImGui::TableSetColumnIndex(1); - ImGui::SetNextItemWidth(-FLT_MIN); - if (i >= 5) - ImGui::InputFloat("##value", &placeholder_members[i], 1.0f); - else - ImGui::DragFloat("##value", &placeholder_members[i], 0.01f); - ImGui::NextColumn(); - } - ImGui::PopID(); - } - ImGui::TreePop(); - } - ImGui::PopID(); -} - -// Demonstrate create a simple property editor. -// This demo is a bit lackluster nowadays, would be nice to improve. -static void ShowExampleAppPropertyEditor(bool* p_open) -{ - ImGui::SetNextWindowSize(ImVec2(430, 450), ImGuiCond_FirstUseEver); - if (!ImGui::Begin("Example: Property editor", p_open)) - { - ImGui::End(); - return; - } - - IMGUI_DEMO_MARKER("Examples/Property Editor"); - HelpMarker( - "This example shows how you may implement a property editor using two columns.\n" - "All objects/fields data are dummies here.\n"); - - ImGui::PushStyleVar(ImGuiStyleVar_FramePadding, ImVec2(2, 2)); - if (ImGui::BeginTable("##split", 2, ImGuiTableFlags_BordersOuter | ImGuiTableFlags_Resizable | ImGuiTableFlags_ScrollY)) - { - ImGui::TableSetupScrollFreeze(0, 1); - ImGui::TableSetupColumn("Object"); - ImGui::TableSetupColumn("Contents"); - ImGui::TableHeadersRow(); - - // Iterate placeholder objects (all the same data) - for (int obj_i = 0; obj_i < 4; obj_i++) - ShowPlaceholderObject("Object", obj_i); - - ImGui::EndTable(); - } - ImGui::PopStyleVar(); - ImGui::End(); -} - -//----------------------------------------------------------------------------- -// [SECTION] Example App: Long Text / ShowExampleAppLongText() -//----------------------------------------------------------------------------- - -// Demonstrate/test rendering huge amount of text, and the incidence of clipping. -static void ShowExampleAppLongText(bool* p_open) -{ - ImGui::SetNextWindowSize(ImVec2(520, 600), ImGuiCond_FirstUseEver); - if (!ImGui::Begin("Example: Long text display", p_open)) - { - ImGui::End(); - return; - } - IMGUI_DEMO_MARKER("Examples/Long text display"); - - static int test_type = 0; - static ImGuiTextBuffer log; - static int lines = 0; - ImGui::Text("Printing unusually long amount of text."); - ImGui::Combo("Test type", &test_type, - "Single call to TextUnformatted()\0" - "Multiple calls to Text(), clipped\0" - "Multiple calls to Text(), not clipped (slow)\0"); - ImGui::Text("Buffer contents: %d lines, %d bytes", lines, log.size()); - if (ImGui::Button("Clear")) { log.clear(); lines = 0; } - ImGui::SameLine(); - if (ImGui::Button("Add 1000 lines")) - { - for (int i = 0; i < 1000; i++) - log.appendf("%i The quick brown fox jumps over the lazy dog\n", lines + i); - lines += 1000; - } - ImGui::BeginChild("Log"); - switch (test_type) - { - case 0: - // Single call to TextUnformatted() with a big buffer - ImGui::TextUnformatted(log.begin(), log.end()); - break; - case 1: - { - // Multiple calls to Text(), manually coarsely clipped - demonstrate how to use the ImGuiListClipper helper. - ImGui::PushStyleVar(ImGuiStyleVar_ItemSpacing, ImVec2(0, 0)); - ImGuiListClipper clipper; - clipper.Begin(lines); - while (clipper.Step()) - for (int i = clipper.DisplayStart; i < clipper.DisplayEnd; i++) - ImGui::Text("%i The quick brown fox jumps over the lazy dog", i); - ImGui::PopStyleVar(); - break; - } - case 2: - // Multiple calls to Text(), not clipped (slow) - ImGui::PushStyleVar(ImGuiStyleVar_ItemSpacing, ImVec2(0, 0)); - for (int i = 0; i < lines; i++) - ImGui::Text("%i The quick brown fox jumps over the lazy dog", i); - ImGui::PopStyleVar(); - break; - } - ImGui::EndChild(); - ImGui::End(); -} - -//----------------------------------------------------------------------------- -// [SECTION] Example App: Auto Resize / ShowExampleAppAutoResize() -//----------------------------------------------------------------------------- - -// Demonstrate creating a window which gets auto-resized according to its content. -static void ShowExampleAppAutoResize(bool* p_open) -{ - if (!ImGui::Begin("Example: Auto-resizing window", p_open, ImGuiWindowFlags_AlwaysAutoResize)) - { - ImGui::End(); - return; - } - IMGUI_DEMO_MARKER("Examples/Auto-resizing window"); - - static int lines = 10; - ImGui::TextUnformatted( - "Window will resize every-frame to the size of its content.\n" - "Note that you probably don't want to query the window size to\n" - "output your content because that would create a feedback loop."); - ImGui::SliderInt("Number of lines", &lines, 1, 20); - for (int i = 0; i < lines; i++) - ImGui::Text("%*sThis is line %d", i * 4, "", i); // Pad with space to extend size horizontally - ImGui::End(); -} - -//----------------------------------------------------------------------------- -// [SECTION] Example App: Constrained Resize / ShowExampleAppConstrainedResize() -//----------------------------------------------------------------------------- - -// Demonstrate creating a window with custom resize constraints. -// Note that size constraints currently don't work on a docked window (when in 'docking' branch) -static void ShowExampleAppConstrainedResize(bool* p_open) -{ - struct CustomConstraints - { - // Helper functions to demonstrate programmatic constraints - // FIXME: This doesn't take account of decoration size (e.g. title bar), library should make this easier. - static void AspectRatio(ImGuiSizeCallbackData* data) { float aspect_ratio = *(float*)data->UserData; data->DesiredSize.x = IM_MAX(data->CurrentSize.x, data->CurrentSize.y); data->DesiredSize.y = (float)(int)(data->DesiredSize.x / aspect_ratio); } - static void Square(ImGuiSizeCallbackData* data) { data->DesiredSize.x = data->DesiredSize.y = IM_MAX(data->CurrentSize.x, data->CurrentSize.y); } - static void Step(ImGuiSizeCallbackData* data) { float step = *(float*)data->UserData; data->DesiredSize = ImVec2((int)(data->CurrentSize.x / step + 0.5f) * step, (int)(data->CurrentSize.y / step + 0.5f) * step); } - }; - - const char* test_desc[] = - { - "Between 100x100 and 500x500", - "At least 100x100", - "Resize vertical only", - "Resize horizontal only", - "Width Between 400 and 500", - "Custom: Aspect Ratio 16:9", - "Custom: Always Square", - "Custom: Fixed Steps (100)", - }; - - // Options - static bool auto_resize = false; - static bool window_padding = true; - static int type = 5; // Aspect Ratio - static int display_lines = 10; - - // Submit constraint - float aspect_ratio = 16.0f / 9.0f; - float fixed_step = 100.0f; - if (type == 0) ImGui::SetNextWindowSizeConstraints(ImVec2(100, 100), ImVec2(500, 500)); // Between 100x100 and 500x500 - if (type == 1) ImGui::SetNextWindowSizeConstraints(ImVec2(100, 100), ImVec2(FLT_MAX, FLT_MAX)); // Width > 100, Height > 100 - if (type == 2) ImGui::SetNextWindowSizeConstraints(ImVec2(-1, 0), ImVec2(-1, FLT_MAX)); // Vertical only - if (type == 3) ImGui::SetNextWindowSizeConstraints(ImVec2(0, -1), ImVec2(FLT_MAX, -1)); // Horizontal only - if (type == 4) ImGui::SetNextWindowSizeConstraints(ImVec2(400, -1), ImVec2(500, -1)); // Width Between and 400 and 500 - if (type == 5) ImGui::SetNextWindowSizeConstraints(ImVec2(0, 0), ImVec2(FLT_MAX, FLT_MAX), CustomConstraints::AspectRatio, (void*)&aspect_ratio); // Aspect ratio - if (type == 6) ImGui::SetNextWindowSizeConstraints(ImVec2(0, 0), ImVec2(FLT_MAX, FLT_MAX), CustomConstraints::Square); // Always Square - if (type == 7) ImGui::SetNextWindowSizeConstraints(ImVec2(0, 0), ImVec2(FLT_MAX, FLT_MAX), CustomConstraints::Step, (void*)&fixed_step); // Fixed Step - - // Submit window - if (!window_padding) - ImGui::PushStyleVar(ImGuiStyleVar_WindowPadding, ImVec2(0.0f, 0.0f)); - const ImGuiWindowFlags window_flags = auto_resize ? ImGuiWindowFlags_AlwaysAutoResize : 0; - const bool window_open = ImGui::Begin("Example: Constrained Resize", p_open, window_flags); - if (!window_padding) - ImGui::PopStyleVar(); - if (window_open) - { - IMGUI_DEMO_MARKER("Examples/Constrained Resizing window"); - if (ImGui::GetIO().KeyShift) - { - // Display a dummy viewport (in your real app you would likely use ImageButton() to display a texture. - ImVec2 avail_size = ImGui::GetContentRegionAvail(); - ImVec2 pos = ImGui::GetCursorScreenPos(); - ImGui::ColorButton("viewport", ImVec4(0.5f, 0.2f, 0.5f, 1.0f), ImGuiColorEditFlags_NoTooltip | ImGuiColorEditFlags_NoDragDrop, avail_size); - ImGui::SetCursorScreenPos(ImVec2(pos.x + 10, pos.y + 10)); - ImGui::Text("%.2f x %.2f", avail_size.x, avail_size.y); - } - else - { - ImGui::Text("(Hold SHIFT to display a dummy viewport)"); - if (ImGui::IsWindowDocked()) - ImGui::Text("Warning: Sizing Constraints won't work if the window is docked!"); - if (ImGui::Button("Set 200x200")) { ImGui::SetWindowSize(ImVec2(200, 200)); } ImGui::SameLine(); - if (ImGui::Button("Set 500x500")) { ImGui::SetWindowSize(ImVec2(500, 500)); } ImGui::SameLine(); - if (ImGui::Button("Set 800x200")) { ImGui::SetWindowSize(ImVec2(800, 200)); } - ImGui::SetNextItemWidth(ImGui::GetFontSize() * 20); - ImGui::Combo("Constraint", &type, test_desc, IM_ARRAYSIZE(test_desc)); - ImGui::SetNextItemWidth(ImGui::GetFontSize() * 20); - ImGui::DragInt("Lines", &display_lines, 0.2f, 1, 100); - ImGui::Checkbox("Auto-resize", &auto_resize); - ImGui::Checkbox("Window padding", &window_padding); - for (int i = 0; i < display_lines; i++) - ImGui::Text("%*sHello, sailor! Making this line long enough for the example.", i * 4, ""); - } - } - ImGui::End(); -} - -//----------------------------------------------------------------------------- -// [SECTION] Example App: Simple overlay / ShowExampleAppSimpleOverlay() -//----------------------------------------------------------------------------- - -// Demonstrate creating a simple static window with no decoration -// + a context-menu to choose which corner of the screen to use. -static void ShowExampleAppSimpleOverlay(bool* p_open) -{ - static int location = 0; - ImGuiIO& io = ImGui::GetIO(); - ImGuiWindowFlags window_flags = ImGuiWindowFlags_NoDecoration | ImGuiWindowFlags_NoDocking | ImGuiWindowFlags_AlwaysAutoResize | ImGuiWindowFlags_NoSavedSettings | ImGuiWindowFlags_NoFocusOnAppearing | ImGuiWindowFlags_NoNav; - if (location >= 0) - { - const float PAD = 10.0f; - const ImGuiViewport* viewport = ImGui::GetMainViewport(); - ImVec2 work_pos = viewport->WorkPos; // Use work area to avoid menu-bar/task-bar, if any! - ImVec2 work_size = viewport->WorkSize; - ImVec2 window_pos, window_pos_pivot; - window_pos.x = (location & 1) ? (work_pos.x + work_size.x - PAD) : (work_pos.x + PAD); - window_pos.y = (location & 2) ? (work_pos.y + work_size.y - PAD) : (work_pos.y + PAD); - window_pos_pivot.x = (location & 1) ? 1.0f : 0.0f; - window_pos_pivot.y = (location & 2) ? 1.0f : 0.0f; - ImGui::SetNextWindowPos(window_pos, ImGuiCond_Always, window_pos_pivot); - ImGui::SetNextWindowViewport(viewport->ID); - window_flags |= ImGuiWindowFlags_NoMove; - } - else if (location == -2) - { - // Center window - ImGui::SetNextWindowPos(ImGui::GetMainViewport()->GetCenter(), ImGuiCond_Always, ImVec2(0.5f, 0.5f)); - window_flags |= ImGuiWindowFlags_NoMove; - } - ImGui::SetNextWindowBgAlpha(0.35f); // Transparent background - if (ImGui::Begin("Example: Simple overlay", p_open, window_flags)) - { - IMGUI_DEMO_MARKER("Examples/Simple Overlay"); - ImGui::Text("Simple overlay\n" "(right-click to change position)"); - ImGui::Separator(); - if (ImGui::IsMousePosValid()) - ImGui::Text("Mouse Position: (%.1f,%.1f)", io.MousePos.x, io.MousePos.y); - else - ImGui::Text("Mouse Position: "); - if (ImGui::BeginPopupContextWindow()) - { - if (ImGui::MenuItem("Custom", NULL, location == -1)) location = -1; - if (ImGui::MenuItem("Center", NULL, location == -2)) location = -2; - if (ImGui::MenuItem("Top-left", NULL, location == 0)) location = 0; - if (ImGui::MenuItem("Top-right", NULL, location == 1)) location = 1; - if (ImGui::MenuItem("Bottom-left", NULL, location == 2)) location = 2; - if (ImGui::MenuItem("Bottom-right", NULL, location == 3)) location = 3; - if (p_open && ImGui::MenuItem("Close")) *p_open = false; - ImGui::EndPopup(); - } - } - ImGui::End(); -} - -//----------------------------------------------------------------------------- -// [SECTION] Example App: Fullscreen window / ShowExampleAppFullscreen() -//----------------------------------------------------------------------------- - -// Demonstrate creating a window covering the entire screen/viewport -static void ShowExampleAppFullscreen(bool* p_open) -{ - static bool use_work_area = true; - static ImGuiWindowFlags flags = ImGuiWindowFlags_NoDecoration | ImGuiWindowFlags_NoMove | ImGuiWindowFlags_NoSavedSettings; - - // We demonstrate using the full viewport area or the work area (without menu-bars, task-bars etc.) - // Based on your use case you may want one or the other. - const ImGuiViewport* viewport = ImGui::GetMainViewport(); - ImGui::SetNextWindowPos(use_work_area ? viewport->WorkPos : viewport->Pos); - ImGui::SetNextWindowSize(use_work_area ? viewport->WorkSize : viewport->Size); - - if (ImGui::Begin("Example: Fullscreen window", p_open, flags)) - { - ImGui::Checkbox("Use work area instead of main area", &use_work_area); - ImGui::SameLine(); - HelpMarker("Main Area = entire viewport,\nWork Area = entire viewport minus sections used by the main menu bars, task bars etc.\n\nEnable the main-menu bar in Examples menu to see the difference."); - - ImGui::CheckboxFlags("ImGuiWindowFlags_NoBackground", &flags, ImGuiWindowFlags_NoBackground); - ImGui::CheckboxFlags("ImGuiWindowFlags_NoDecoration", &flags, ImGuiWindowFlags_NoDecoration); - ImGui::Indent(); - ImGui::CheckboxFlags("ImGuiWindowFlags_NoTitleBar", &flags, ImGuiWindowFlags_NoTitleBar); - ImGui::CheckboxFlags("ImGuiWindowFlags_NoCollapse", &flags, ImGuiWindowFlags_NoCollapse); - ImGui::CheckboxFlags("ImGuiWindowFlags_NoScrollbar", &flags, ImGuiWindowFlags_NoScrollbar); - ImGui::Unindent(); - - if (p_open && ImGui::Button("Close this window")) - *p_open = false; - } - ImGui::End(); -} - -//----------------------------------------------------------------------------- -// [SECTION] Example App: Manipulating Window Titles / ShowExampleAppWindowTitles() -//----------------------------------------------------------------------------- - -// Demonstrate the use of "##" and "###" in identifiers to manipulate ID generation. -// This applies to all regular items as well. -// Read FAQ section "How can I have multiple widgets with the same label?" for details. -static void ShowExampleAppWindowTitles(bool*) -{ - const ImGuiViewport* viewport = ImGui::GetMainViewport(); - const ImVec2 base_pos = viewport->Pos; - - // By default, Windows are uniquely identified by their title. - // You can use the "##" and "###" markers to manipulate the display/ID. - - // Using "##" to display same title but have unique identifier. - ImGui::SetNextWindowPos(ImVec2(base_pos.x + 100, base_pos.y + 100), ImGuiCond_FirstUseEver); - ImGui::Begin("Same title as another window##1"); - IMGUI_DEMO_MARKER("Examples/Manipulating window titles"); - ImGui::Text("This is window 1.\nMy title is the same as window 2, but my identifier is unique."); - ImGui::End(); - - ImGui::SetNextWindowPos(ImVec2(base_pos.x + 100, base_pos.y + 200), ImGuiCond_FirstUseEver); - ImGui::Begin("Same title as another window##2"); - ImGui::Text("This is window 2.\nMy title is the same as window 1, but my identifier is unique."); - ImGui::End(); - - // Using "###" to display a changing title but keep a static identifier "AnimatedTitle" - char buf[128]; - sprintf(buf, "Animated title %c %d###AnimatedTitle", "|/-\\"[(int)(ImGui::GetTime() / 0.25f) & 3], ImGui::GetFrameCount()); - ImGui::SetNextWindowPos(ImVec2(base_pos.x + 100, base_pos.y + 300), ImGuiCond_FirstUseEver); - ImGui::Begin(buf); - ImGui::Text("This window has a changing title."); - ImGui::End(); -} - -//----------------------------------------------------------------------------- -// [SECTION] Example App: Custom Rendering using ImDrawList API / ShowExampleAppCustomRendering() -//----------------------------------------------------------------------------- - -// Demonstrate using the low-level ImDrawList to draw custom shapes. -static void ShowExampleAppCustomRendering(bool* p_open) -{ - if (!ImGui::Begin("Example: Custom rendering", p_open)) - { - ImGui::End(); - return; - } - IMGUI_DEMO_MARKER("Examples/Custom Rendering"); - - // Tip: If you do a lot of custom rendering, you probably want to use your own geometrical types and benefit of - // overloaded operators, etc. Define IM_VEC2_CLASS_EXTRA in imconfig.h to create implicit conversions between your - // types and ImVec2/ImVec4. Dear ImGui defines overloaded operators but they are internal to imgui.cpp and not - // exposed outside (to avoid messing with your types) In this example we are not using the maths operators! - - if (ImGui::BeginTabBar("##TabBar")) - { - if (ImGui::BeginTabItem("Primitives")) - { - ImGui::PushItemWidth(-ImGui::GetFontSize() * 15); - ImDrawList* draw_list = ImGui::GetWindowDrawList(); - - // Draw gradients - // (note that those are currently exacerbating our sRGB/Linear issues) - // Calling ImGui::GetColorU32() multiplies the given colors by the current Style Alpha, but you may pass the IM_COL32() directly as well.. - ImGui::Text("Gradients"); - ImVec2 gradient_size = ImVec2(ImGui::CalcItemWidth(), ImGui::GetFrameHeight()); - { - ImVec2 p0 = ImGui::GetCursorScreenPos(); - ImVec2 p1 = ImVec2(p0.x + gradient_size.x, p0.y + gradient_size.y); - ImU32 col_a = ImGui::GetColorU32(IM_COL32(0, 0, 0, 255)); - ImU32 col_b = ImGui::GetColorU32(IM_COL32(255, 255, 255, 255)); - draw_list->AddRectFilledMultiColor(p0, p1, col_a, col_b, col_b, col_a); - ImGui::InvisibleButton("##gradient1", gradient_size); - } - { - ImVec2 p0 = ImGui::GetCursorScreenPos(); - ImVec2 p1 = ImVec2(p0.x + gradient_size.x, p0.y + gradient_size.y); - ImU32 col_a = ImGui::GetColorU32(IM_COL32(0, 255, 0, 255)); - ImU32 col_b = ImGui::GetColorU32(IM_COL32(255, 0, 0, 255)); - draw_list->AddRectFilledMultiColor(p0, p1, col_a, col_b, col_b, col_a); - ImGui::InvisibleButton("##gradient2", gradient_size); - } - - // Draw a bunch of primitives - ImGui::Text("All primitives"); - static float sz = 36.0f; - static float thickness = 3.0f; - static int ngon_sides = 6; - static bool circle_segments_override = false; - static int circle_segments_override_v = 12; - static bool curve_segments_override = false; - static int curve_segments_override_v = 8; - static ImVec4 colf = ImVec4(1.0f, 1.0f, 0.4f, 1.0f); - ImGui::DragFloat("Size", &sz, 0.2f, 2.0f, 100.0f, "%.0f"); - ImGui::DragFloat("Thickness", &thickness, 0.05f, 1.0f, 8.0f, "%.02f"); - ImGui::SliderInt("N-gon sides", &ngon_sides, 3, 12); - ImGui::Checkbox("##circlesegmentoverride", &circle_segments_override); - ImGui::SameLine(0.0f, ImGui::GetStyle().ItemInnerSpacing.x); - circle_segments_override |= ImGui::SliderInt("Circle segments override", &circle_segments_override_v, 3, 40); - ImGui::Checkbox("##curvessegmentoverride", &curve_segments_override); - ImGui::SameLine(0.0f, ImGui::GetStyle().ItemInnerSpacing.x); - curve_segments_override |= ImGui::SliderInt("Curves segments override", &curve_segments_override_v, 3, 40); - ImGui::ColorEdit4("Color", &colf.x); - - const ImVec2 p = ImGui::GetCursorScreenPos(); - const ImU32 col = ImColor(colf); - const float spacing = 10.0f; - const ImDrawFlags corners_tl_br = ImDrawFlags_RoundCornersTopLeft | ImDrawFlags_RoundCornersBottomRight; - const float rounding = sz / 5.0f; - const int circle_segments = circle_segments_override ? circle_segments_override_v : 0; - const int curve_segments = curve_segments_override ? curve_segments_override_v : 0; - float x = p.x + 4.0f; - float y = p.y + 4.0f; - for (int n = 0; n < 2; n++) - { - // First line uses a thickness of 1.0f, second line uses the configurable thickness - float th = (n == 0) ? 1.0f : thickness; - draw_list->AddNgon(ImVec2(x + sz*0.5f, y + sz*0.5f), sz*0.5f, col, ngon_sides, th); x += sz + spacing; // N-gon - draw_list->AddCircle(ImVec2(x + sz*0.5f, y + sz*0.5f), sz*0.5f, col, circle_segments, th); x += sz + spacing; // Circle - draw_list->AddEllipse(ImVec2(x + sz*0.5f, y + sz*0.5f), sz*0.5f, sz*0.3f, col, -0.3f, circle_segments, th); x += sz + spacing; // Ellipse - draw_list->AddRect(ImVec2(x, y), ImVec2(x + sz, y + sz), col, 0.0f, ImDrawFlags_None, th); x += sz + spacing; // Square - draw_list->AddRect(ImVec2(x, y), ImVec2(x + sz, y + sz), col, rounding, ImDrawFlags_None, th); x += sz + spacing; // Square with all rounded corners - draw_list->AddRect(ImVec2(x, y), ImVec2(x + sz, y + sz), col, rounding, corners_tl_br, th); x += sz + spacing; // Square with two rounded corners - draw_list->AddTriangle(ImVec2(x+sz*0.5f,y), ImVec2(x+sz, y+sz-0.5f), ImVec2(x, y+sz-0.5f), col, th);x += sz + spacing; // Triangle - //draw_list->AddTriangle(ImVec2(x+sz*0.2f,y), ImVec2(x, y+sz-0.5f), ImVec2(x+sz*0.4f, y+sz-0.5f), col, th);x+= sz*0.4f + spacing; // Thin triangle - draw_list->AddLine(ImVec2(x, y), ImVec2(x + sz, y), col, th); x += sz + spacing; // Horizontal line (note: drawing a filled rectangle will be faster!) - draw_list->AddLine(ImVec2(x, y), ImVec2(x, y + sz), col, th); x += spacing; // Vertical line (note: drawing a filled rectangle will be faster!) - draw_list->AddLine(ImVec2(x, y), ImVec2(x + sz, y + sz), col, th); x += sz + spacing; // Diagonal line - - // Quadratic Bezier Curve (3 control points) - ImVec2 cp3[3] = { ImVec2(x, y + sz * 0.6f), ImVec2(x + sz * 0.5f, y - sz * 0.4f), ImVec2(x + sz, y + sz) }; - draw_list->AddBezierQuadratic(cp3[0], cp3[1], cp3[2], col, th, curve_segments); x += sz + spacing; - - // Cubic Bezier Curve (4 control points) - ImVec2 cp4[4] = { ImVec2(x, y), ImVec2(x + sz * 1.3f, y + sz * 0.3f), ImVec2(x + sz - sz * 1.3f, y + sz - sz * 0.3f), ImVec2(x + sz, y + sz) }; - draw_list->AddBezierCubic(cp4[0], cp4[1], cp4[2], cp4[3], col, th, curve_segments); - - x = p.x + 4; - y += sz + spacing; - } - draw_list->AddNgonFilled(ImVec2(x + sz * 0.5f, y + sz * 0.5f), sz * 0.5f, col, ngon_sides); x += sz + spacing; // N-gon - draw_list->AddCircleFilled(ImVec2(x + sz * 0.5f, y + sz * 0.5f), sz * 0.5f, col, circle_segments); x += sz + spacing; // Circle - draw_list->AddEllipseFilled(ImVec2(x + sz * 0.5f, y + sz * 0.5f), sz * 0.5f, sz * 0.3f, col, -0.3f, circle_segments); x += sz + spacing;// Ellipse - draw_list->AddRectFilled(ImVec2(x, y), ImVec2(x + sz, y + sz), col); x += sz + spacing; // Square - draw_list->AddRectFilled(ImVec2(x, y), ImVec2(x + sz, y + sz), col, 10.0f); x += sz + spacing; // Square with all rounded corners - draw_list->AddRectFilled(ImVec2(x, y), ImVec2(x + sz, y + sz), col, 10.0f, corners_tl_br); x += sz + spacing; // Square with two rounded corners - draw_list->AddTriangleFilled(ImVec2(x+sz*0.5f,y), ImVec2(x+sz, y+sz-0.5f), ImVec2(x, y+sz-0.5f), col); x += sz + spacing; // Triangle - //draw_list->AddTriangleFilled(ImVec2(x+sz*0.2f,y), ImVec2(x, y+sz-0.5f), ImVec2(x+sz*0.4f, y+sz-0.5f), col); x += sz*0.4f + spacing; // Thin triangle - draw_list->AddRectFilled(ImVec2(x, y), ImVec2(x + sz, y + thickness), col); x += sz + spacing; // Horizontal line (faster than AddLine, but only handle integer thickness) - draw_list->AddRectFilled(ImVec2(x, y), ImVec2(x + thickness, y + sz), col); x += spacing * 2.0f;// Vertical line (faster than AddLine, but only handle integer thickness) - draw_list->AddRectFilled(ImVec2(x, y), ImVec2(x + 1, y + 1), col); x += sz; // Pixel (faster than AddLine) - draw_list->AddRectFilledMultiColor(ImVec2(x, y), ImVec2(x + sz, y + sz), IM_COL32(0, 0, 0, 255), IM_COL32(255, 0, 0, 255), IM_COL32(255, 255, 0, 255), IM_COL32(0, 255, 0, 255)); - - ImGui::Dummy(ImVec2((sz + spacing) * 11.2f, (sz + spacing) * 3.0f)); - ImGui::PopItemWidth(); - ImGui::EndTabItem(); - } - - if (ImGui::BeginTabItem("Canvas")) - { - static ImVector points; - static ImVec2 scrolling(0.0f, 0.0f); - static bool opt_enable_grid = true; - static bool opt_enable_context_menu = true; - static bool adding_line = false; - - ImGui::Checkbox("Enable grid", &opt_enable_grid); - ImGui::Checkbox("Enable context menu", &opt_enable_context_menu); - ImGui::Text("Mouse Left: drag to add lines,\nMouse Right: drag to scroll, click for context menu."); - - // Typically you would use a BeginChild()/EndChild() pair to benefit from a clipping region + own scrolling. - // Here we demonstrate that this can be replaced by simple offsetting + custom drawing + PushClipRect/PopClipRect() calls. - // To use a child window instead we could use, e.g: - // ImGui::PushStyleVar(ImGuiStyleVar_WindowPadding, ImVec2(0, 0)); // Disable padding - // ImGui::PushStyleColor(ImGuiCol_ChildBg, IM_COL32(50, 50, 50, 255)); // Set a background color - // ImGui::BeginChild("canvas", ImVec2(0.0f, 0.0f), true, ImGuiWindowFlags_NoMove); - // ImGui::PopStyleColor(); - // ImGui::PopStyleVar(); - // [...] - // ImGui::EndChild(); - - // Using InvisibleButton() as a convenience 1) it will advance the layout cursor and 2) allows us to use IsItemHovered()/IsItemActive() - ImVec2 canvas_p0 = ImGui::GetCursorScreenPos(); // ImDrawList API uses screen coordinates! - ImVec2 canvas_sz = ImGui::GetContentRegionAvail(); // Resize canvas to what's available - if (canvas_sz.x < 50.0f) canvas_sz.x = 50.0f; - if (canvas_sz.y < 50.0f) canvas_sz.y = 50.0f; - ImVec2 canvas_p1 = ImVec2(canvas_p0.x + canvas_sz.x, canvas_p0.y + canvas_sz.y); - - // Draw border and background color - ImGuiIO& io = ImGui::GetIO(); - ImDrawList* draw_list = ImGui::GetWindowDrawList(); - draw_list->AddRectFilled(canvas_p0, canvas_p1, IM_COL32(50, 50, 50, 255)); - draw_list->AddRect(canvas_p0, canvas_p1, IM_COL32(255, 255, 255, 255)); - - // This will catch our interactions - ImGui::InvisibleButton("canvas", canvas_sz, ImGuiButtonFlags_MouseButtonLeft | ImGuiButtonFlags_MouseButtonRight); - const bool is_hovered = ImGui::IsItemHovered(); // Hovered - const bool is_active = ImGui::IsItemActive(); // Held - const ImVec2 origin(canvas_p0.x + scrolling.x, canvas_p0.y + scrolling.y); // Lock scrolled origin - const ImVec2 mouse_pos_in_canvas(io.MousePos.x - origin.x, io.MousePos.y - origin.y); - - // Add first and second point - if (is_hovered && !adding_line && ImGui::IsMouseClicked(ImGuiMouseButton_Left)) - { - points.push_back(mouse_pos_in_canvas); - points.push_back(mouse_pos_in_canvas); - adding_line = true; - } - if (adding_line) - { - points.back() = mouse_pos_in_canvas; - if (!ImGui::IsMouseDown(ImGuiMouseButton_Left)) - adding_line = false; - } - - // Pan (we use a zero mouse threshold when there's no context menu) - // You may decide to make that threshold dynamic based on whether the mouse is hovering something etc. - const float mouse_threshold_for_pan = opt_enable_context_menu ? -1.0f : 0.0f; - if (is_active && ImGui::IsMouseDragging(ImGuiMouseButton_Right, mouse_threshold_for_pan)) - { - scrolling.x += io.MouseDelta.x; - scrolling.y += io.MouseDelta.y; - } - - // Context menu (under default mouse threshold) - ImVec2 drag_delta = ImGui::GetMouseDragDelta(ImGuiMouseButton_Right); - if (opt_enable_context_menu && drag_delta.x == 0.0f && drag_delta.y == 0.0f) - ImGui::OpenPopupOnItemClick("context", ImGuiPopupFlags_MouseButtonRight); - if (ImGui::BeginPopup("context")) - { - if (adding_line) - points.resize(points.size() - 2); - adding_line = false; - if (ImGui::MenuItem("Remove one", NULL, false, points.Size > 0)) { points.resize(points.size() - 2); } - if (ImGui::MenuItem("Remove all", NULL, false, points.Size > 0)) { points.clear(); } - ImGui::EndPopup(); - } - - // Draw grid + all lines in the canvas - draw_list->PushClipRect(canvas_p0, canvas_p1, true); - if (opt_enable_grid) - { - const float GRID_STEP = 64.0f; - for (float x = fmodf(scrolling.x, GRID_STEP); x < canvas_sz.x; x += GRID_STEP) - draw_list->AddLine(ImVec2(canvas_p0.x + x, canvas_p0.y), ImVec2(canvas_p0.x + x, canvas_p1.y), IM_COL32(200, 200, 200, 40)); - for (float y = fmodf(scrolling.y, GRID_STEP); y < canvas_sz.y; y += GRID_STEP) - draw_list->AddLine(ImVec2(canvas_p0.x, canvas_p0.y + y), ImVec2(canvas_p1.x, canvas_p0.y + y), IM_COL32(200, 200, 200, 40)); - } - for (int n = 0; n < points.Size; n += 2) - draw_list->AddLine(ImVec2(origin.x + points[n].x, origin.y + points[n].y), ImVec2(origin.x + points[n + 1].x, origin.y + points[n + 1].y), IM_COL32(255, 255, 0, 255), 2.0f); - draw_list->PopClipRect(); - - ImGui::EndTabItem(); - } - - if (ImGui::BeginTabItem("BG/FG draw lists")) - { - static bool draw_bg = true; - static bool draw_fg = true; - ImGui::Checkbox("Draw in Background draw list", &draw_bg); - ImGui::SameLine(); HelpMarker("The Background draw list will be rendered below every Dear ImGui windows."); - ImGui::Checkbox("Draw in Foreground draw list", &draw_fg); - ImGui::SameLine(); HelpMarker("The Foreground draw list will be rendered over every Dear ImGui windows."); - ImVec2 window_pos = ImGui::GetWindowPos(); - ImVec2 window_size = ImGui::GetWindowSize(); - ImVec2 window_center = ImVec2(window_pos.x + window_size.x * 0.5f, window_pos.y + window_size.y * 0.5f); - if (draw_bg) - ImGui::GetBackgroundDrawList()->AddCircle(window_center, window_size.x * 0.6f, IM_COL32(255, 0, 0, 200), 0, 10 + 4); - if (draw_fg) - ImGui::GetForegroundDrawList()->AddCircle(window_center, window_size.y * 0.6f, IM_COL32(0, 255, 0, 200), 0, 10); - ImGui::EndTabItem(); - } - - // Demonstrate out-of-order rendering via channels splitting - // We use functions in ImDrawList as each draw list contains a convenience splitter, - // but you can also instantiate your own ImDrawListSplitter if you need to nest them. - if (ImGui::BeginTabItem("Draw Channels")) - { - ImDrawList* draw_list = ImGui::GetWindowDrawList(); - { - ImGui::Text("Blue shape is drawn first: appears in back"); - ImGui::Text("Red shape is drawn after: appears in front"); - ImVec2 p0 = ImGui::GetCursorScreenPos(); - draw_list->AddRectFilled(ImVec2(p0.x, p0.y), ImVec2(p0.x + 50, p0.y + 50), IM_COL32(0, 0, 255, 255)); // Blue - draw_list->AddRectFilled(ImVec2(p0.x + 25, p0.y + 25), ImVec2(p0.x + 75, p0.y + 75), IM_COL32(255, 0, 0, 255)); // Red - ImGui::Dummy(ImVec2(75, 75)); - } - ImGui::Separator(); - { - ImGui::Text("Blue shape is drawn first, into channel 1: appears in front"); - ImGui::Text("Red shape is drawn after, into channel 0: appears in back"); - ImVec2 p1 = ImGui::GetCursorScreenPos(); - - // Create 2 channels and draw a Blue shape THEN a Red shape. - // You can create any number of channels. Tables API use 1 channel per column in order to better batch draw calls. - draw_list->ChannelsSplit(2); - draw_list->ChannelsSetCurrent(1); - draw_list->AddRectFilled(ImVec2(p1.x, p1.y), ImVec2(p1.x + 50, p1.y + 50), IM_COL32(0, 0, 255, 255)); // Blue - draw_list->ChannelsSetCurrent(0); - draw_list->AddRectFilled(ImVec2(p1.x + 25, p1.y + 25), ImVec2(p1.x + 75, p1.y + 75), IM_COL32(255, 0, 0, 255)); // Red - - // Flatten/reorder channels. Red shape is in channel 0 and it appears below the Blue shape in channel 1. - // This works by copying draw indices only (vertices are not copied). - draw_list->ChannelsMerge(); - ImGui::Dummy(ImVec2(75, 75)); - ImGui::Text("After reordering, contents of channel 0 appears below channel 1."); - } - ImGui::EndTabItem(); - } - - ImGui::EndTabBar(); - } - - ImGui::End(); -} - -//----------------------------------------------------------------------------- -// [SECTION] Example App: Docking, DockSpace / ShowExampleAppDockSpace() -//----------------------------------------------------------------------------- - -// Demonstrate using DockSpace() to create an explicit docking node within an existing window. -// Note: You can use most Docking facilities without calling any API. You DO NOT need to call DockSpace() to use Docking! -// - Drag from window title bar or their tab to dock/undock. Hold SHIFT to disable docking. -// - Drag from window menu button (upper-left button) to undock an entire node (all windows). -// - When io.ConfigDockingWithShift == true, you instead need to hold SHIFT to enable docking. -// About dockspaces: -// - Use DockSpace() to create an explicit dock node _within_ an existing window. -// - Use DockSpaceOverViewport() to create an explicit dock node covering the screen or a specific viewport. -// This is often used with ImGuiDockNodeFlags_PassthruCentralNode. -// - Important: Dockspaces need to be submitted _before_ any window they can host. Submit it early in your frame! (*) -// - Important: Dockspaces need to be kept alive if hidden, otherwise windows docked into it will be undocked. -// e.g. if you have multiple tabs with a dockspace inside each tab: submit the non-visible dockspaces with ImGuiDockNodeFlags_KeepAliveOnly. -// (*) because of this constraint, the implicit \"Debug\" window can not be docked into an explicit DockSpace() node, -// because that window is submitted as part of the part of the NewFrame() call. An easy workaround is that you can create -// your own implicit "Debug##2" window after calling DockSpace() and leave it in the window stack for anyone to use. -void ShowExampleAppDockSpace(bool* p_open) -{ - // READ THIS !!! - // TL;DR; this demo is more complicated than what most users you would normally use. - // If we remove all options we are showcasing, this demo would become: - // void ShowExampleAppDockSpace() - // { - // ImGui::DockSpaceOverViewport(ImGui::GetMainViewport()); - // } - // In most cases you should be able to just call DockSpaceOverViewport() and ignore all the code below! - // In this specific demo, we are not using DockSpaceOverViewport() because: - // - (1) we allow the host window to be floating/moveable instead of filling the viewport (when opt_fullscreen == false) - // - (2) we allow the host window to have padding (when opt_padding == true) - // - (3) we expose many flags and need a way to have them visible. - // - (4) we have a local menu bar in the host window (vs. you could use BeginMainMenuBar() + DockSpaceOverViewport() - // in your code, but we don't here because we allow the window to be floating) - - static bool opt_fullscreen = true; - static bool opt_padding = false; - static ImGuiDockNodeFlags dockspace_flags = ImGuiDockNodeFlags_None; - - // We are using the ImGuiWindowFlags_NoDocking flag to make the parent window not dockable into, - // because it would be confusing to have two docking targets within each others. - ImGuiWindowFlags window_flags = ImGuiWindowFlags_MenuBar | ImGuiWindowFlags_NoDocking; - if (opt_fullscreen) - { - const ImGuiViewport* viewport = ImGui::GetMainViewport(); - ImGui::SetNextWindowPos(viewport->WorkPos); - ImGui::SetNextWindowSize(viewport->WorkSize); - ImGui::SetNextWindowViewport(viewport->ID); - ImGui::PushStyleVar(ImGuiStyleVar_WindowRounding, 0.0f); - ImGui::PushStyleVar(ImGuiStyleVar_WindowBorderSize, 0.0f); - window_flags |= ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_NoCollapse | ImGuiWindowFlags_NoResize | ImGuiWindowFlags_NoMove; - window_flags |= ImGuiWindowFlags_NoBringToFrontOnFocus | ImGuiWindowFlags_NoNavFocus; - } - else - { - dockspace_flags &= ~ImGuiDockNodeFlags_PassthruCentralNode; - } - - // When using ImGuiDockNodeFlags_PassthruCentralNode, DockSpace() will render our background - // and handle the pass-thru hole, so we ask Begin() to not render a background. - if (dockspace_flags & ImGuiDockNodeFlags_PassthruCentralNode) - window_flags |= ImGuiWindowFlags_NoBackground; - - // Important: note that we proceed even if Begin() returns false (aka window is collapsed). - // This is because we want to keep our DockSpace() active. If a DockSpace() is inactive, - // all active windows docked into it will lose their parent and become undocked. - // We cannot preserve the docking relationship between an active window and an inactive docking, otherwise - // any change of dockspace/settings would lead to windows being stuck in limbo and never being visible. - if (!opt_padding) - ImGui::PushStyleVar(ImGuiStyleVar_WindowPadding, ImVec2(0.0f, 0.0f)); - ImGui::Begin("DockSpace Demo", p_open, window_flags); - if (!opt_padding) - ImGui::PopStyleVar(); - - if (opt_fullscreen) - ImGui::PopStyleVar(2); - - // Submit the DockSpace - ImGuiIO& io = ImGui::GetIO(); - if (io.ConfigFlags & ImGuiConfigFlags_DockingEnable) - { - ImGuiID dockspace_id = ImGui::GetID("MyDockSpace"); - ImGui::DockSpace(dockspace_id, ImVec2(0.0f, 0.0f), dockspace_flags); - } - else - { - ShowDockingDisabledMessage(); - } - - if (ImGui::BeginMenuBar()) - { - if (ImGui::BeginMenu("Options")) - { - // Disabling fullscreen would allow the window to be moved to the front of other windows, - // which we can't undo at the moment without finer window depth/z control. - ImGui::MenuItem("Fullscreen", NULL, &opt_fullscreen); - ImGui::MenuItem("Padding", NULL, &opt_padding); - ImGui::Separator(); - - if (ImGui::MenuItem("Flag: NoDockingOverCentralNode", "", (dockspace_flags & ImGuiDockNodeFlags_NoDockingOverCentralNode) != 0)) { dockspace_flags ^= ImGuiDockNodeFlags_NoDockingOverCentralNode; } - if (ImGui::MenuItem("Flag: NoDockingSplit", "", (dockspace_flags & ImGuiDockNodeFlags_NoDockingSplit) != 0)) { dockspace_flags ^= ImGuiDockNodeFlags_NoDockingSplit; } - if (ImGui::MenuItem("Flag: NoUndocking", "", (dockspace_flags & ImGuiDockNodeFlags_NoUndocking) != 0)) { dockspace_flags ^= ImGuiDockNodeFlags_NoUndocking; } - if (ImGui::MenuItem("Flag: NoResize", "", (dockspace_flags & ImGuiDockNodeFlags_NoResize) != 0)) { dockspace_flags ^= ImGuiDockNodeFlags_NoResize; } - if (ImGui::MenuItem("Flag: AutoHideTabBar", "", (dockspace_flags & ImGuiDockNodeFlags_AutoHideTabBar) != 0)) { dockspace_flags ^= ImGuiDockNodeFlags_AutoHideTabBar; } - if (ImGui::MenuItem("Flag: PassthruCentralNode", "", (dockspace_flags & ImGuiDockNodeFlags_PassthruCentralNode) != 0, opt_fullscreen)) { dockspace_flags ^= ImGuiDockNodeFlags_PassthruCentralNode; } - ImGui::Separator(); - - if (ImGui::MenuItem("Close", NULL, false, p_open != NULL)) - *p_open = false; - ImGui::EndMenu(); - } - HelpMarker( - "When docking is enabled, you can ALWAYS dock MOST window into another! Try it now!" "\n" - "- Drag from window title bar or their tab to dock/undock." "\n" - "- Drag from window menu button (upper-left button) to undock an entire node (all windows)." "\n" - "- Hold SHIFT to disable docking (if io.ConfigDockingWithShift == false, default)" "\n" - "- Hold SHIFT to enable docking (if io.ConfigDockingWithShift == true)" "\n" - "This demo app has nothing to do with enabling docking!" "\n\n" - "This demo app only demonstrate the use of ImGui::DockSpace() which allows you to manually create a docking node _within_ another window." "\n\n" - "Read comments in ShowExampleAppDockSpace() for more details."); - - ImGui::EndMenuBar(); - } - - ImGui::End(); -} - -//----------------------------------------------------------------------------- -// [SECTION] Example App: Documents Handling / ShowExampleAppDocuments() -//----------------------------------------------------------------------------- - -// Simplified structure to mimic a Document model -struct MyDocument -{ - const char* Name; // Document title - bool Open; // Set when open (we keep an array of all available documents to simplify demo code!) - bool OpenPrev; // Copy of Open from last update. - bool Dirty; // Set when the document has been modified - bool WantClose; // Set when the document - ImVec4 Color; // An arbitrary variable associated to the document - - MyDocument(const char* name, bool open = true, const ImVec4& color = ImVec4(1.0f, 1.0f, 1.0f, 1.0f)) - { - Name = name; - Open = OpenPrev = open; - Dirty = false; - WantClose = false; - Color = color; - } - void DoOpen() { Open = true; } - void DoQueueClose() { WantClose = true; } - void DoForceClose() { Open = false; Dirty = false; } - void DoSave() { Dirty = false; } - - // Display placeholder contents for the Document - static void DisplayContents(MyDocument* doc) - { - ImGui::PushID(doc); - ImGui::Text("Document \"%s\"", doc->Name); - ImGui::PushStyleColor(ImGuiCol_Text, doc->Color); - ImGui::TextWrapped("Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua."); - ImGui::PopStyleColor(); - if (ImGui::Button("Modify", ImVec2(100, 0))) - doc->Dirty = true; - ImGui::SameLine(); - if (ImGui::Button("Save", ImVec2(100, 0))) - doc->DoSave(); - ImGui::ColorEdit3("color", &doc->Color.x); // Useful to test drag and drop and hold-dragged-to-open-tab behavior. - ImGui::PopID(); - } - - // Display context menu for the Document - static void DisplayContextMenu(MyDocument* doc) - { - if (!ImGui::BeginPopupContextItem()) - return; - - char buf[256]; - sprintf(buf, "Save %s", doc->Name); - if (ImGui::MenuItem(buf, "CTRL+S", false, doc->Open)) - doc->DoSave(); - if (ImGui::MenuItem("Close", "CTRL+W", false, doc->Open)) - doc->DoQueueClose(); - ImGui::EndPopup(); - } -}; - -struct ExampleAppDocuments -{ - ImVector Documents; - - ExampleAppDocuments() - { - Documents.push_back(MyDocument("Lettuce", true, ImVec4(0.4f, 0.8f, 0.4f, 1.0f))); - Documents.push_back(MyDocument("Eggplant", true, ImVec4(0.8f, 0.5f, 1.0f, 1.0f))); - Documents.push_back(MyDocument("Carrot", true, ImVec4(1.0f, 0.8f, 0.5f, 1.0f))); - Documents.push_back(MyDocument("Tomato", false, ImVec4(1.0f, 0.3f, 0.4f, 1.0f))); - Documents.push_back(MyDocument("A Rather Long Title", false)); - Documents.push_back(MyDocument("Some Document", false)); - } -}; - -// [Optional] Notify the system of Tabs/Windows closure that happened outside the regular tab interface. -// If a tab has been closed programmatically (aka closed from another source such as the Checkbox() in the demo, -// as opposed to clicking on the regular tab closing button) and stops being submitted, it will take a frame for -// the tab bar to notice its absence. During this frame there will be a gap in the tab bar, and if the tab that has -// disappeared was the selected one, the tab bar will report no selected tab during the frame. This will effectively -// give the impression of a flicker for one frame. -// We call SetTabItemClosed() to manually notify the Tab Bar or Docking system of removed tabs to avoid this glitch. -// Note that this completely optional, and only affect tab bars with the ImGuiTabBarFlags_Reorderable flag. -static void NotifyOfDocumentsClosedElsewhere(ExampleAppDocuments& app) -{ - for (MyDocument& doc : app.Documents) - { - if (!doc.Open && doc.OpenPrev) - ImGui::SetTabItemClosed(doc.Name); - doc.OpenPrev = doc.Open; - } -} - -void ShowExampleAppDocuments(bool* p_open) -{ - static ExampleAppDocuments app; - - // Options - enum Target - { - Target_None, - Target_Tab, // Create documents as local tab into a local tab bar - Target_DockSpaceAndWindow // Create documents as regular windows, and create an embedded dockspace - }; - static Target opt_target = Target_Tab; - static bool opt_reorderable = true; - static ImGuiTabBarFlags opt_fitting_flags = ImGuiTabBarFlags_FittingPolicyDefault_; - - // When (opt_target == Target_DockSpaceAndWindow) there is the possibily that one of our child Document window (e.g. "Eggplant") - // that we emit gets docked into the same spot as the parent window ("Example: Documents"). - // This would create a problematic feedback loop because selecting the "Eggplant" tab would make the "Example: Documents" tab - // not visible, which in turn would stop submitting the "Eggplant" window. - // We avoid this problem by submitting our documents window even if our parent window is not currently visible. - // Another solution may be to make the "Example: Documents" window use the ImGuiWindowFlags_NoDocking. - - bool window_contents_visible = ImGui::Begin("Example: Documents", p_open, ImGuiWindowFlags_MenuBar); - if (!window_contents_visible && opt_target != Target_DockSpaceAndWindow) - { - ImGui::End(); - return; - } - - // Menu - if (ImGui::BeginMenuBar()) - { - if (ImGui::BeginMenu("File")) - { - int open_count = 0; - for (MyDocument& doc : app.Documents) - open_count += doc.Open ? 1 : 0; - - if (ImGui::BeginMenu("Open", open_count < app.Documents.Size)) - { - for (MyDocument& doc : app.Documents) - if (!doc.Open && ImGui::MenuItem(doc.Name)) - doc.DoOpen(); - ImGui::EndMenu(); - } - if (ImGui::MenuItem("Close All Documents", NULL, false, open_count > 0)) - for (MyDocument& doc : app.Documents) - doc.DoQueueClose(); - if (ImGui::MenuItem("Exit", "Ctrl+F4") && p_open) - *p_open = false; - ImGui::EndMenu(); - } - ImGui::EndMenuBar(); - } - - // [Debug] List documents with one checkbox for each - for (int doc_n = 0; doc_n < app.Documents.Size; doc_n++) - { - MyDocument& doc = app.Documents[doc_n]; - if (doc_n > 0) - ImGui::SameLine(); - ImGui::PushID(&doc); - if (ImGui::Checkbox(doc.Name, &doc.Open)) - if (!doc.Open) - doc.DoForceClose(); - ImGui::PopID(); - } - ImGui::PushItemWidth(ImGui::GetFontSize() * 12); - ImGui::Combo("Output", (int*)&opt_target, "None\0TabBar+Tabs\0DockSpace+Window\0"); - ImGui::PopItemWidth(); - bool redock_all = false; - if (opt_target == Target_Tab) { ImGui::SameLine(); ImGui::Checkbox("Reorderable Tabs", &opt_reorderable); } - if (opt_target == Target_DockSpaceAndWindow) { ImGui::SameLine(); redock_all = ImGui::Button("Redock all"); } - - ImGui::Separator(); - - // About the ImGuiWindowFlags_UnsavedDocument / ImGuiTabItemFlags_UnsavedDocument flags. - // They have multiple effects: - // - Display a dot next to the title. - // - Tab is selected when clicking the X close button. - // - Closure is not assumed (will wait for user to stop submitting the tab). - // Otherwise closure is assumed when pressing the X, so if you keep submitting the tab may reappear at end of tab bar. - // We need to assume closure by default otherwise waiting for "lack of submission" on the next frame would leave an empty - // hole for one-frame, both in the tab-bar and in tab-contents when closing a tab/window. - // The rarely used SetTabItemClosed() function is a way to notify of programmatic closure to avoid the one-frame hole. - - // Tabs - if (opt_target == Target_Tab) - { - ImGuiTabBarFlags tab_bar_flags = (opt_fitting_flags) | (opt_reorderable ? ImGuiTabBarFlags_Reorderable : 0); - if (ImGui::BeginTabBar("##tabs", tab_bar_flags)) - { - if (opt_reorderable) - NotifyOfDocumentsClosedElsewhere(app); - - // [DEBUG] Stress tests - //if ((ImGui::GetFrameCount() % 30) == 0) docs[1].Open ^= 1; // [DEBUG] Automatically show/hide a tab. Test various interactions e.g. dragging with this on. - //if (ImGui::GetIO().KeyCtrl) ImGui::SetTabItemSelected(docs[1].Name); // [DEBUG] Test SetTabItemSelected(), probably not very useful as-is anyway.. - - // Submit Tabs - for (MyDocument& doc : app.Documents) - { - if (!doc.Open) - continue; - - ImGuiTabItemFlags tab_flags = (doc.Dirty ? ImGuiTabItemFlags_UnsavedDocument : 0); - bool visible = ImGui::BeginTabItem(doc.Name, &doc.Open, tab_flags); - - // Cancel attempt to close when unsaved add to save queue so we can display a popup. - if (!doc.Open && doc.Dirty) - { - doc.Open = true; - doc.DoQueueClose(); - } - - MyDocument::DisplayContextMenu(&doc); - if (visible) - { - MyDocument::DisplayContents(&doc); - ImGui::EndTabItem(); - } - } - - ImGui::EndTabBar(); - } - } - else if (opt_target == Target_DockSpaceAndWindow) - { - if (ImGui::GetIO().ConfigFlags & ImGuiConfigFlags_DockingEnable) - { - NotifyOfDocumentsClosedElsewhere(app); - - // Create a DockSpace node where any window can be docked - ImGuiID dockspace_id = ImGui::GetID("MyDockSpace"); - ImGui::DockSpace(dockspace_id); - - // Create Windows - for (int doc_n = 0; doc_n < app.Documents.Size; doc_n++) - { - MyDocument* doc = &app.Documents[doc_n]; - if (!doc->Open) - continue; - - ImGui::SetNextWindowDockID(dockspace_id, redock_all ? ImGuiCond_Always : ImGuiCond_FirstUseEver); - ImGuiWindowFlags window_flags = (doc->Dirty ? ImGuiWindowFlags_UnsavedDocument : 0); - bool visible = ImGui::Begin(doc->Name, &doc->Open, window_flags); - - // Cancel attempt to close when unsaved add to save queue so we can display a popup. - if (!doc->Open && doc->Dirty) - { - doc->Open = true; - doc->DoQueueClose(); - } - - MyDocument::DisplayContextMenu(doc); - if (visible) - MyDocument::DisplayContents(doc); - - ImGui::End(); - } - } - else - { - ShowDockingDisabledMessage(); - } - } - - // Early out other contents - if (!window_contents_visible) - { - ImGui::End(); - return; - } - - // Update closing queue - static ImVector close_queue; - if (close_queue.empty()) - { - // Close queue is locked once we started a popup - for (MyDocument& doc : app.Documents) - if (doc.WantClose) - { - doc.WantClose = false; - close_queue.push_back(&doc); - } - } - - // Display closing confirmation UI - if (!close_queue.empty()) - { - int close_queue_unsaved_documents = 0; - for (int n = 0; n < close_queue.Size; n++) - if (close_queue[n]->Dirty) - close_queue_unsaved_documents++; - - if (close_queue_unsaved_documents == 0) - { - // Close documents when all are unsaved - for (int n = 0; n < close_queue.Size; n++) - close_queue[n]->DoForceClose(); - close_queue.clear(); - } - else - { - if (!ImGui::IsPopupOpen("Save?")) - ImGui::OpenPopup("Save?"); - if (ImGui::BeginPopupModal("Save?", NULL, ImGuiWindowFlags_AlwaysAutoResize)) - { - ImGui::Text("Save change to the following items?"); - float item_height = ImGui::GetTextLineHeightWithSpacing(); - if (ImGui::BeginChildFrame(ImGui::GetID("frame"), ImVec2(-FLT_MIN, 6.25f * item_height))) - { - for (int n = 0; n < close_queue.Size; n++) - if (close_queue[n]->Dirty) - ImGui::Text("%s", close_queue[n]->Name); - } - ImGui::EndChildFrame(); - - ImVec2 button_size(ImGui::GetFontSize() * 7.0f, 0.0f); - if (ImGui::Button("Yes", button_size)) - { - for (int n = 0; n < close_queue.Size; n++) - { - if (close_queue[n]->Dirty) - close_queue[n]->DoSave(); - close_queue[n]->DoForceClose(); - } - close_queue.clear(); - ImGui::CloseCurrentPopup(); - } - ImGui::SameLine(); - if (ImGui::Button("No", button_size)) - { - for (int n = 0; n < close_queue.Size; n++) - close_queue[n]->DoForceClose(); - close_queue.clear(); - ImGui::CloseCurrentPopup(); - } - ImGui::SameLine(); - if (ImGui::Button("Cancel", button_size)) - { - close_queue.clear(); - ImGui::CloseCurrentPopup(); - } - ImGui::EndPopup(); - } - } - } - - ImGui::End(); -} - -// End of Demo code -#else - -void ImGui::ShowAboutWindow(bool*) {} -void ImGui::ShowDemoWindow(bool*) {} -void ImGui::ShowUserGuide() {} -void ImGui::ShowStyleEditor(ImGuiStyle*) {} - -#endif - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/imgui_draw.cpp b/app/jni/src/libultraship/extern/ImGui/imgui_draw.cpp deleted file mode 100644 index 9a7a89b..0000000 --- a/app/jni/src/libultraship/extern/ImGui/imgui_draw.cpp +++ /dev/null @@ -1,4327 +0,0 @@ -// dear imgui, v1.90 WIP -// (drawing and font code) - -/* - -Index of this file: - -// [SECTION] STB libraries implementation -// [SECTION] Style functions -// [SECTION] ImDrawList -// [SECTION] ImDrawListSplitter -// [SECTION] ImDrawData -// [SECTION] Helpers ShadeVertsXXX functions -// [SECTION] ImFontConfig -// [SECTION] ImFontAtlas -// [SECTION] ImFontAtlas glyph ranges helpers -// [SECTION] ImFontGlyphRangesBuilder -// [SECTION] ImFont -// [SECTION] ImGui Internal Render Helpers -// [SECTION] Decompression code -// [SECTION] Default font data (ProggyClean.ttf) - -*/ - -#if defined(_MSC_VER) && !defined(_CRT_SECURE_NO_WARNINGS) -#define _CRT_SECURE_NO_WARNINGS -#endif - -#ifndef IMGUI_DEFINE_MATH_OPERATORS -#define IMGUI_DEFINE_MATH_OPERATORS -#endif - -#include "imgui.h" -#ifndef IMGUI_DISABLE -#include "imgui_internal.h" -#ifdef IMGUI_ENABLE_FREETYPE -#include "misc/freetype/imgui_freetype.h" -#endif - -#include // vsnprintf, sscanf, printf - -// Visual Studio warnings -#ifdef _MSC_VER -#pragma warning (disable: 4127) // condition expression is constant -#pragma warning (disable: 4505) // unreferenced local function has been removed (stb stuff) -#pragma warning (disable: 4996) // 'This function or variable may be unsafe': strcpy, strdup, sprintf, vsnprintf, sscanf, fopen -#pragma warning (disable: 26451) // [Static Analyzer] Arithmetic overflow : Using operator 'xxx' on a 4 byte value and then casting the result to a 8 byte value. Cast the value to the wider type before calling operator 'xxx' to avoid overflow(io.2). -#pragma warning (disable: 26812) // [Static Analyzer] The enum type 'xxx' is unscoped. Prefer 'enum class' over 'enum' (Enum.3). [MSVC Static Analyzer) -#endif - -// Clang/GCC warnings with -Weverything -#if defined(__clang__) -#if __has_warning("-Wunknown-warning-option") -#pragma clang diagnostic ignored "-Wunknown-warning-option" // warning: unknown warning group 'xxx' // not all warnings are known by all Clang versions and they tend to be rename-happy.. so ignoring warnings triggers new warnings on some configuration. Great! -#endif -#pragma clang diagnostic ignored "-Wunknown-pragmas" // warning: unknown warning group 'xxx' -#pragma clang diagnostic ignored "-Wold-style-cast" // warning: use of old-style cast // yes, they are more terse. -#pragma clang diagnostic ignored "-Wfloat-equal" // warning: comparing floating point with == or != is unsafe // storing and comparing against same constants ok. -#pragma clang diagnostic ignored "-Wglobal-constructors" // warning: declaration requires a global destructor // similar to above, not sure what the exact difference is. -#pragma clang diagnostic ignored "-Wsign-conversion" // warning: implicit conversion changes signedness -#pragma clang diagnostic ignored "-Wzero-as-null-pointer-constant" // warning: zero as null pointer constant // some standard header variations use #define NULL 0 -#pragma clang diagnostic ignored "-Wcomma" // warning: possible misuse of comma operator here -#pragma clang diagnostic ignored "-Wreserved-id-macro" // warning: macro name is a reserved identifier -#pragma clang diagnostic ignored "-Wdouble-promotion" // warning: implicit conversion from 'float' to 'double' when passing argument to function // using printf() is a misery with this as C++ va_arg ellipsis changes float to double. -#pragma clang diagnostic ignored "-Wimplicit-int-float-conversion" // warning: implicit conversion from 'xxx' to 'float' may lose precision -#pragma clang diagnostic ignored "-Wreserved-identifier" // warning: identifier '_Xxx' is reserved because it starts with '_' followed by a capital letter -#elif defined(__GNUC__) -#pragma GCC diagnostic ignored "-Wpragmas" // warning: unknown option after '#pragma GCC diagnostic' kind -#pragma GCC diagnostic ignored "-Wunused-function" // warning: 'xxxx' defined but not used -#pragma GCC diagnostic ignored "-Wdouble-promotion" // warning: implicit conversion from 'float' to 'double' when passing argument to function -#pragma GCC diagnostic ignored "-Wconversion" // warning: conversion to 'xxxx' from 'xxxx' may alter its value -#pragma GCC diagnostic ignored "-Wstack-protector" // warning: stack protector not protecting local variables: variable length buffer -#pragma GCC diagnostic ignored "-Wclass-memaccess" // [__GNUC__ >= 8] warning: 'memset/memcpy' clearing/writing an object of type 'xxxx' with no trivial copy-assignment; use assignment or value-initialization instead -#endif - -//------------------------------------------------------------------------- -// [SECTION] STB libraries implementation (for stb_truetype and stb_rect_pack) -//------------------------------------------------------------------------- - -// Compile time options: -//#define IMGUI_STB_NAMESPACE ImStb -//#define IMGUI_STB_TRUETYPE_FILENAME "my_folder/stb_truetype.h" -//#define IMGUI_STB_RECT_PACK_FILENAME "my_folder/stb_rect_pack.h" -//#define IMGUI_DISABLE_STB_TRUETYPE_IMPLEMENTATION -//#define IMGUI_DISABLE_STB_RECT_PACK_IMPLEMENTATION - -#ifdef IMGUI_STB_NAMESPACE -namespace IMGUI_STB_NAMESPACE -{ -#endif - -#ifdef _MSC_VER -#pragma warning (push) -#pragma warning (disable: 4456) // declaration of 'xx' hides previous local declaration -#pragma warning (disable: 6011) // (stb_rectpack) Dereferencing NULL pointer 'cur->next'. -#pragma warning (disable: 6385) // (stb_truetype) Reading invalid data from 'buffer': the readable size is '_Old_3`kernel_width' bytes, but '3' bytes may be read. -#pragma warning (disable: 28182) // (stb_rectpack) Dereferencing NULL pointer. 'cur' contains the same NULL value as 'cur->next' did. -#endif - -#if defined(__clang__) -#pragma clang diagnostic push -#pragma clang diagnostic ignored "-Wunused-function" -#pragma clang diagnostic ignored "-Wmissing-prototypes" -#pragma clang diagnostic ignored "-Wimplicit-fallthrough" -#pragma clang diagnostic ignored "-Wcast-qual" // warning: cast from 'const xxxx *' to 'xxx *' drops const qualifier -#endif - -#if defined(__GNUC__) -#pragma GCC diagnostic push -#pragma GCC diagnostic ignored "-Wtype-limits" // warning: comparison is always true due to limited range of data type [-Wtype-limits] -#pragma GCC diagnostic ignored "-Wcast-qual" // warning: cast from type 'const xxxx *' to type 'xxxx *' casts away qualifiers -#endif - -#ifndef STB_RECT_PACK_IMPLEMENTATION // in case the user already have an implementation in the _same_ compilation unit (e.g. unity builds) -#ifndef IMGUI_DISABLE_STB_RECT_PACK_IMPLEMENTATION // in case the user already have an implementation in another compilation unit -#define STBRP_STATIC -#define STBRP_ASSERT(x) do { IM_ASSERT(x); } while (0) -#define STBRP_SORT ImQsort -#define STB_RECT_PACK_IMPLEMENTATION -#endif -#ifdef IMGUI_STB_RECT_PACK_FILENAME -#include IMGUI_STB_RECT_PACK_FILENAME -#else -#include "imstb_rectpack.h" -#endif -#endif - -#ifdef IMGUI_ENABLE_STB_TRUETYPE -#ifndef STB_TRUETYPE_IMPLEMENTATION // in case the user already have an implementation in the _same_ compilation unit (e.g. unity builds) -#ifndef IMGUI_DISABLE_STB_TRUETYPE_IMPLEMENTATION // in case the user already have an implementation in another compilation unit -#define STBTT_malloc(x,u) ((void)(u), IM_ALLOC(x)) -#define STBTT_free(x,u) ((void)(u), IM_FREE(x)) -#define STBTT_assert(x) do { IM_ASSERT(x); } while(0) -#define STBTT_fmod(x,y) ImFmod(x,y) -#define STBTT_sqrt(x) ImSqrt(x) -#define STBTT_pow(x,y) ImPow(x,y) -#define STBTT_fabs(x) ImFabs(x) -#define STBTT_ifloor(x) ((int)ImFloor(x)) -#define STBTT_iceil(x) ((int)ImCeil(x)) -#define STBTT_STATIC -#define STB_TRUETYPE_IMPLEMENTATION -#else -#define STBTT_DEF extern -#endif -#ifdef IMGUI_STB_TRUETYPE_FILENAME -#include IMGUI_STB_TRUETYPE_FILENAME -#else -#include "imstb_truetype.h" -#endif -#endif -#endif // IMGUI_ENABLE_STB_TRUETYPE - -#if defined(__GNUC__) -#pragma GCC diagnostic pop -#endif - -#if defined(__clang__) -#pragma clang diagnostic pop -#endif - -#if defined(_MSC_VER) -#pragma warning (pop) -#endif - -#ifdef IMGUI_STB_NAMESPACE -} // namespace ImStb -using namespace IMGUI_STB_NAMESPACE; -#endif - -//----------------------------------------------------------------------------- -// [SECTION] Style functions -//----------------------------------------------------------------------------- - -void ImGui::StyleColorsDark(ImGuiStyle* dst) -{ - ImGuiStyle* style = dst ? dst : &ImGui::GetStyle(); - ImVec4* colors = style->Colors; - - colors[ImGuiCol_Text] = ImVec4(1.00f, 1.00f, 1.00f, 1.00f); - colors[ImGuiCol_TextDisabled] = ImVec4(0.50f, 0.50f, 0.50f, 1.00f); - colors[ImGuiCol_WindowBg] = ImVec4(0.06f, 0.06f, 0.06f, 0.94f); - colors[ImGuiCol_ChildBg] = ImVec4(0.00f, 0.00f, 0.00f, 0.00f); - colors[ImGuiCol_PopupBg] = ImVec4(0.08f, 0.08f, 0.08f, 0.94f); - colors[ImGuiCol_Border] = ImVec4(0.43f, 0.43f, 0.50f, 0.50f); - colors[ImGuiCol_BorderShadow] = ImVec4(0.00f, 0.00f, 0.00f, 0.00f); - colors[ImGuiCol_FrameBg] = ImVec4(0.16f, 0.29f, 0.48f, 0.54f); - colors[ImGuiCol_FrameBgHovered] = ImVec4(0.26f, 0.59f, 0.98f, 0.40f); - colors[ImGuiCol_FrameBgActive] = ImVec4(0.26f, 0.59f, 0.98f, 0.67f); - colors[ImGuiCol_TitleBg] = ImVec4(0.04f, 0.04f, 0.04f, 1.00f); - colors[ImGuiCol_TitleBgActive] = ImVec4(0.16f, 0.29f, 0.48f, 1.00f); - colors[ImGuiCol_TitleBgCollapsed] = ImVec4(0.00f, 0.00f, 0.00f, 0.51f); - colors[ImGuiCol_MenuBarBg] = ImVec4(0.14f, 0.14f, 0.14f, 1.00f); - colors[ImGuiCol_ScrollbarBg] = ImVec4(0.02f, 0.02f, 0.02f, 0.53f); - colors[ImGuiCol_ScrollbarGrab] = ImVec4(0.31f, 0.31f, 0.31f, 1.00f); - colors[ImGuiCol_ScrollbarGrabHovered] = ImVec4(0.41f, 0.41f, 0.41f, 1.00f); - colors[ImGuiCol_ScrollbarGrabActive] = ImVec4(0.51f, 0.51f, 0.51f, 1.00f); - colors[ImGuiCol_CheckMark] = ImVec4(0.26f, 0.59f, 0.98f, 1.00f); - colors[ImGuiCol_SliderGrab] = ImVec4(0.24f, 0.52f, 0.88f, 1.00f); - colors[ImGuiCol_SliderGrabActive] = ImVec4(0.26f, 0.59f, 0.98f, 1.00f); - colors[ImGuiCol_Button] = ImVec4(0.26f, 0.59f, 0.98f, 0.40f); - colors[ImGuiCol_ButtonHovered] = ImVec4(0.26f, 0.59f, 0.98f, 1.00f); - colors[ImGuiCol_ButtonActive] = ImVec4(0.06f, 0.53f, 0.98f, 1.00f); - colors[ImGuiCol_Header] = ImVec4(0.26f, 0.59f, 0.98f, 0.31f); - colors[ImGuiCol_HeaderHovered] = ImVec4(0.26f, 0.59f, 0.98f, 0.80f); - colors[ImGuiCol_HeaderActive] = ImVec4(0.26f, 0.59f, 0.98f, 1.00f); - colors[ImGuiCol_Separator] = colors[ImGuiCol_Border]; - colors[ImGuiCol_SeparatorHovered] = ImVec4(0.10f, 0.40f, 0.75f, 0.78f); - colors[ImGuiCol_SeparatorActive] = ImVec4(0.10f, 0.40f, 0.75f, 1.00f); - colors[ImGuiCol_ResizeGrip] = ImVec4(0.26f, 0.59f, 0.98f, 0.20f); - colors[ImGuiCol_ResizeGripHovered] = ImVec4(0.26f, 0.59f, 0.98f, 0.67f); - colors[ImGuiCol_ResizeGripActive] = ImVec4(0.26f, 0.59f, 0.98f, 0.95f); - colors[ImGuiCol_Tab] = ImLerp(colors[ImGuiCol_Header], colors[ImGuiCol_TitleBgActive], 0.80f); - colors[ImGuiCol_TabHovered] = colors[ImGuiCol_HeaderHovered]; - colors[ImGuiCol_TabActive] = ImLerp(colors[ImGuiCol_HeaderActive], colors[ImGuiCol_TitleBgActive], 0.60f); - colors[ImGuiCol_TabUnfocused] = ImLerp(colors[ImGuiCol_Tab], colors[ImGuiCol_TitleBg], 0.80f); - colors[ImGuiCol_TabUnfocusedActive] = ImLerp(colors[ImGuiCol_TabActive], colors[ImGuiCol_TitleBg], 0.40f); - colors[ImGuiCol_DockingPreview] = colors[ImGuiCol_HeaderActive] * ImVec4(1.0f, 1.0f, 1.0f, 0.7f); - colors[ImGuiCol_DockingEmptyBg] = ImVec4(0.20f, 0.20f, 0.20f, 1.00f); - colors[ImGuiCol_PlotLines] = ImVec4(0.61f, 0.61f, 0.61f, 1.00f); - colors[ImGuiCol_PlotLinesHovered] = ImVec4(1.00f, 0.43f, 0.35f, 1.00f); - colors[ImGuiCol_PlotHistogram] = ImVec4(0.90f, 0.70f, 0.00f, 1.00f); - colors[ImGuiCol_PlotHistogramHovered] = ImVec4(1.00f, 0.60f, 0.00f, 1.00f); - colors[ImGuiCol_TableHeaderBg] = ImVec4(0.19f, 0.19f, 0.20f, 1.00f); - colors[ImGuiCol_TableBorderStrong] = ImVec4(0.31f, 0.31f, 0.35f, 1.00f); // Prefer using Alpha=1.0 here - colors[ImGuiCol_TableBorderLight] = ImVec4(0.23f, 0.23f, 0.25f, 1.00f); // Prefer using Alpha=1.0 here - colors[ImGuiCol_TableRowBg] = ImVec4(0.00f, 0.00f, 0.00f, 0.00f); - colors[ImGuiCol_TableRowBgAlt] = ImVec4(1.00f, 1.00f, 1.00f, 0.06f); - colors[ImGuiCol_TextSelectedBg] = ImVec4(0.26f, 0.59f, 0.98f, 0.35f); - colors[ImGuiCol_DragDropTarget] = ImVec4(1.00f, 1.00f, 0.00f, 0.90f); - colors[ImGuiCol_NavHighlight] = ImVec4(0.26f, 0.59f, 0.98f, 1.00f); - colors[ImGuiCol_NavWindowingHighlight] = ImVec4(1.00f, 1.00f, 1.00f, 0.70f); - colors[ImGuiCol_NavWindowingDimBg] = ImVec4(0.80f, 0.80f, 0.80f, 0.20f); - colors[ImGuiCol_ModalWindowDimBg] = ImVec4(0.80f, 0.80f, 0.80f, 0.35f); -} - -void ImGui::StyleColorsClassic(ImGuiStyle* dst) -{ - ImGuiStyle* style = dst ? dst : &ImGui::GetStyle(); - ImVec4* colors = style->Colors; - - colors[ImGuiCol_Text] = ImVec4(0.90f, 0.90f, 0.90f, 1.00f); - colors[ImGuiCol_TextDisabled] = ImVec4(0.60f, 0.60f, 0.60f, 1.00f); - colors[ImGuiCol_WindowBg] = ImVec4(0.00f, 0.00f, 0.00f, 0.85f); - colors[ImGuiCol_ChildBg] = ImVec4(0.00f, 0.00f, 0.00f, 0.00f); - colors[ImGuiCol_PopupBg] = ImVec4(0.11f, 0.11f, 0.14f, 0.92f); - colors[ImGuiCol_Border] = ImVec4(0.50f, 0.50f, 0.50f, 0.50f); - colors[ImGuiCol_BorderShadow] = ImVec4(0.00f, 0.00f, 0.00f, 0.00f); - colors[ImGuiCol_FrameBg] = ImVec4(0.43f, 0.43f, 0.43f, 0.39f); - colors[ImGuiCol_FrameBgHovered] = ImVec4(0.47f, 0.47f, 0.69f, 0.40f); - colors[ImGuiCol_FrameBgActive] = ImVec4(0.42f, 0.41f, 0.64f, 0.69f); - colors[ImGuiCol_TitleBg] = ImVec4(0.27f, 0.27f, 0.54f, 0.83f); - colors[ImGuiCol_TitleBgActive] = ImVec4(0.32f, 0.32f, 0.63f, 0.87f); - colors[ImGuiCol_TitleBgCollapsed] = ImVec4(0.40f, 0.40f, 0.80f, 0.20f); - colors[ImGuiCol_MenuBarBg] = ImVec4(0.40f, 0.40f, 0.55f, 0.80f); - colors[ImGuiCol_ScrollbarBg] = ImVec4(0.20f, 0.25f, 0.30f, 0.60f); - colors[ImGuiCol_ScrollbarGrab] = ImVec4(0.40f, 0.40f, 0.80f, 0.30f); - colors[ImGuiCol_ScrollbarGrabHovered] = ImVec4(0.40f, 0.40f, 0.80f, 0.40f); - colors[ImGuiCol_ScrollbarGrabActive] = ImVec4(0.41f, 0.39f, 0.80f, 0.60f); - colors[ImGuiCol_CheckMark] = ImVec4(0.90f, 0.90f, 0.90f, 0.50f); - colors[ImGuiCol_SliderGrab] = ImVec4(1.00f, 1.00f, 1.00f, 0.30f); - colors[ImGuiCol_SliderGrabActive] = ImVec4(0.41f, 0.39f, 0.80f, 0.60f); - colors[ImGuiCol_Button] = ImVec4(0.35f, 0.40f, 0.61f, 0.62f); - colors[ImGuiCol_ButtonHovered] = ImVec4(0.40f, 0.48f, 0.71f, 0.79f); - colors[ImGuiCol_ButtonActive] = ImVec4(0.46f, 0.54f, 0.80f, 1.00f); - colors[ImGuiCol_Header] = ImVec4(0.40f, 0.40f, 0.90f, 0.45f); - colors[ImGuiCol_HeaderHovered] = ImVec4(0.45f, 0.45f, 0.90f, 0.80f); - colors[ImGuiCol_HeaderActive] = ImVec4(0.53f, 0.53f, 0.87f, 0.80f); - colors[ImGuiCol_Separator] = ImVec4(0.50f, 0.50f, 0.50f, 0.60f); - colors[ImGuiCol_SeparatorHovered] = ImVec4(0.60f, 0.60f, 0.70f, 1.00f); - colors[ImGuiCol_SeparatorActive] = ImVec4(0.70f, 0.70f, 0.90f, 1.00f); - colors[ImGuiCol_ResizeGrip] = ImVec4(1.00f, 1.00f, 1.00f, 0.10f); - colors[ImGuiCol_ResizeGripHovered] = ImVec4(0.78f, 0.82f, 1.00f, 0.60f); - colors[ImGuiCol_ResizeGripActive] = ImVec4(0.78f, 0.82f, 1.00f, 0.90f); - colors[ImGuiCol_Tab] = ImLerp(colors[ImGuiCol_Header], colors[ImGuiCol_TitleBgActive], 0.80f); - colors[ImGuiCol_TabHovered] = colors[ImGuiCol_HeaderHovered]; - colors[ImGuiCol_TabActive] = ImLerp(colors[ImGuiCol_HeaderActive], colors[ImGuiCol_TitleBgActive], 0.60f); - colors[ImGuiCol_TabUnfocused] = ImLerp(colors[ImGuiCol_Tab], colors[ImGuiCol_TitleBg], 0.80f); - colors[ImGuiCol_TabUnfocusedActive] = ImLerp(colors[ImGuiCol_TabActive], colors[ImGuiCol_TitleBg], 0.40f); - colors[ImGuiCol_DockingPreview] = colors[ImGuiCol_Header] * ImVec4(1.0f, 1.0f, 1.0f, 0.7f); - colors[ImGuiCol_DockingEmptyBg] = ImVec4(0.20f, 0.20f, 0.20f, 1.00f); - colors[ImGuiCol_PlotLines] = ImVec4(1.00f, 1.00f, 1.00f, 1.00f); - colors[ImGuiCol_PlotLinesHovered] = ImVec4(0.90f, 0.70f, 0.00f, 1.00f); - colors[ImGuiCol_PlotHistogram] = ImVec4(0.90f, 0.70f, 0.00f, 1.00f); - colors[ImGuiCol_PlotHistogramHovered] = ImVec4(1.00f, 0.60f, 0.00f, 1.00f); - colors[ImGuiCol_TableHeaderBg] = ImVec4(0.27f, 0.27f, 0.38f, 1.00f); - colors[ImGuiCol_TableBorderStrong] = ImVec4(0.31f, 0.31f, 0.45f, 1.00f); // Prefer using Alpha=1.0 here - colors[ImGuiCol_TableBorderLight] = ImVec4(0.26f, 0.26f, 0.28f, 1.00f); // Prefer using Alpha=1.0 here - colors[ImGuiCol_TableRowBg] = ImVec4(0.00f, 0.00f, 0.00f, 0.00f); - colors[ImGuiCol_TableRowBgAlt] = ImVec4(1.00f, 1.00f, 1.00f, 0.07f); - colors[ImGuiCol_TextSelectedBg] = ImVec4(0.00f, 0.00f, 1.00f, 0.35f); - colors[ImGuiCol_DragDropTarget] = ImVec4(1.00f, 1.00f, 0.00f, 0.90f); - colors[ImGuiCol_NavHighlight] = colors[ImGuiCol_HeaderHovered]; - colors[ImGuiCol_NavWindowingHighlight] = ImVec4(1.00f, 1.00f, 1.00f, 0.70f); - colors[ImGuiCol_NavWindowingDimBg] = ImVec4(0.80f, 0.80f, 0.80f, 0.20f); - colors[ImGuiCol_ModalWindowDimBg] = ImVec4(0.20f, 0.20f, 0.20f, 0.35f); -} - -// Those light colors are better suited with a thicker font than the default one + FrameBorder -void ImGui::StyleColorsLight(ImGuiStyle* dst) -{ - ImGuiStyle* style = dst ? dst : &ImGui::GetStyle(); - ImVec4* colors = style->Colors; - - colors[ImGuiCol_Text] = ImVec4(0.00f, 0.00f, 0.00f, 1.00f); - colors[ImGuiCol_TextDisabled] = ImVec4(0.60f, 0.60f, 0.60f, 1.00f); - colors[ImGuiCol_WindowBg] = ImVec4(0.94f, 0.94f, 0.94f, 1.00f); - colors[ImGuiCol_ChildBg] = ImVec4(0.00f, 0.00f, 0.00f, 0.00f); - colors[ImGuiCol_PopupBg] = ImVec4(1.00f, 1.00f, 1.00f, 0.98f); - colors[ImGuiCol_Border] = ImVec4(0.00f, 0.00f, 0.00f, 0.30f); - colors[ImGuiCol_BorderShadow] = ImVec4(0.00f, 0.00f, 0.00f, 0.00f); - colors[ImGuiCol_FrameBg] = ImVec4(1.00f, 1.00f, 1.00f, 1.00f); - colors[ImGuiCol_FrameBgHovered] = ImVec4(0.26f, 0.59f, 0.98f, 0.40f); - colors[ImGuiCol_FrameBgActive] = ImVec4(0.26f, 0.59f, 0.98f, 0.67f); - colors[ImGuiCol_TitleBg] = ImVec4(0.96f, 0.96f, 0.96f, 1.00f); - colors[ImGuiCol_TitleBgActive] = ImVec4(0.82f, 0.82f, 0.82f, 1.00f); - colors[ImGuiCol_TitleBgCollapsed] = ImVec4(1.00f, 1.00f, 1.00f, 0.51f); - colors[ImGuiCol_MenuBarBg] = ImVec4(0.86f, 0.86f, 0.86f, 1.00f); - colors[ImGuiCol_ScrollbarBg] = ImVec4(0.98f, 0.98f, 0.98f, 0.53f); - colors[ImGuiCol_ScrollbarGrab] = ImVec4(0.69f, 0.69f, 0.69f, 0.80f); - colors[ImGuiCol_ScrollbarGrabHovered] = ImVec4(0.49f, 0.49f, 0.49f, 0.80f); - colors[ImGuiCol_ScrollbarGrabActive] = ImVec4(0.49f, 0.49f, 0.49f, 1.00f); - colors[ImGuiCol_CheckMark] = ImVec4(0.26f, 0.59f, 0.98f, 1.00f); - colors[ImGuiCol_SliderGrab] = ImVec4(0.26f, 0.59f, 0.98f, 0.78f); - colors[ImGuiCol_SliderGrabActive] = ImVec4(0.46f, 0.54f, 0.80f, 0.60f); - colors[ImGuiCol_Button] = ImVec4(0.26f, 0.59f, 0.98f, 0.40f); - colors[ImGuiCol_ButtonHovered] = ImVec4(0.26f, 0.59f, 0.98f, 1.00f); - colors[ImGuiCol_ButtonActive] = ImVec4(0.06f, 0.53f, 0.98f, 1.00f); - colors[ImGuiCol_Header] = ImVec4(0.26f, 0.59f, 0.98f, 0.31f); - colors[ImGuiCol_HeaderHovered] = ImVec4(0.26f, 0.59f, 0.98f, 0.80f); - colors[ImGuiCol_HeaderActive] = ImVec4(0.26f, 0.59f, 0.98f, 1.00f); - colors[ImGuiCol_Separator] = ImVec4(0.39f, 0.39f, 0.39f, 0.62f); - colors[ImGuiCol_SeparatorHovered] = ImVec4(0.14f, 0.44f, 0.80f, 0.78f); - colors[ImGuiCol_SeparatorActive] = ImVec4(0.14f, 0.44f, 0.80f, 1.00f); - colors[ImGuiCol_ResizeGrip] = ImVec4(0.35f, 0.35f, 0.35f, 0.17f); - colors[ImGuiCol_ResizeGripHovered] = ImVec4(0.26f, 0.59f, 0.98f, 0.67f); - colors[ImGuiCol_ResizeGripActive] = ImVec4(0.26f, 0.59f, 0.98f, 0.95f); - colors[ImGuiCol_Tab] = ImLerp(colors[ImGuiCol_Header], colors[ImGuiCol_TitleBgActive], 0.90f); - colors[ImGuiCol_TabHovered] = colors[ImGuiCol_HeaderHovered]; - colors[ImGuiCol_TabActive] = ImLerp(colors[ImGuiCol_HeaderActive], colors[ImGuiCol_TitleBgActive], 0.60f); - colors[ImGuiCol_TabUnfocused] = ImLerp(colors[ImGuiCol_Tab], colors[ImGuiCol_TitleBg], 0.80f); - colors[ImGuiCol_TabUnfocusedActive] = ImLerp(colors[ImGuiCol_TabActive], colors[ImGuiCol_TitleBg], 0.40f); - colors[ImGuiCol_DockingPreview] = colors[ImGuiCol_Header] * ImVec4(1.0f, 1.0f, 1.0f, 0.7f); - colors[ImGuiCol_DockingEmptyBg] = ImVec4(0.20f, 0.20f, 0.20f, 1.00f); - colors[ImGuiCol_PlotLines] = ImVec4(0.39f, 0.39f, 0.39f, 1.00f); - colors[ImGuiCol_PlotLinesHovered] = ImVec4(1.00f, 0.43f, 0.35f, 1.00f); - colors[ImGuiCol_PlotHistogram] = ImVec4(0.90f, 0.70f, 0.00f, 1.00f); - colors[ImGuiCol_PlotHistogramHovered] = ImVec4(1.00f, 0.45f, 0.00f, 1.00f); - colors[ImGuiCol_TableHeaderBg] = ImVec4(0.78f, 0.87f, 0.98f, 1.00f); - colors[ImGuiCol_TableBorderStrong] = ImVec4(0.57f, 0.57f, 0.64f, 1.00f); // Prefer using Alpha=1.0 here - colors[ImGuiCol_TableBorderLight] = ImVec4(0.68f, 0.68f, 0.74f, 1.00f); // Prefer using Alpha=1.0 here - colors[ImGuiCol_TableRowBg] = ImVec4(0.00f, 0.00f, 0.00f, 0.00f); - colors[ImGuiCol_TableRowBgAlt] = ImVec4(0.30f, 0.30f, 0.30f, 0.09f); - colors[ImGuiCol_TextSelectedBg] = ImVec4(0.26f, 0.59f, 0.98f, 0.35f); - colors[ImGuiCol_DragDropTarget] = ImVec4(0.26f, 0.59f, 0.98f, 0.95f); - colors[ImGuiCol_NavHighlight] = colors[ImGuiCol_HeaderHovered]; - colors[ImGuiCol_NavWindowingHighlight] = ImVec4(0.70f, 0.70f, 0.70f, 0.70f); - colors[ImGuiCol_NavWindowingDimBg] = ImVec4(0.20f, 0.20f, 0.20f, 0.20f); - colors[ImGuiCol_ModalWindowDimBg] = ImVec4(0.20f, 0.20f, 0.20f, 0.35f); -} - -//----------------------------------------------------------------------------- -// [SECTION] ImDrawList -//----------------------------------------------------------------------------- - -ImDrawListSharedData::ImDrawListSharedData() -{ - memset(this, 0, sizeof(*this)); - for (int i = 0; i < IM_ARRAYSIZE(ArcFastVtx); i++) - { - const float a = ((float)i * 2 * IM_PI) / (float)IM_ARRAYSIZE(ArcFastVtx); - ArcFastVtx[i] = ImVec2(ImCos(a), ImSin(a)); - } - ArcFastRadiusCutoff = IM_DRAWLIST_CIRCLE_AUTO_SEGMENT_CALC_R(IM_DRAWLIST_ARCFAST_SAMPLE_MAX, CircleSegmentMaxError); -} - -void ImDrawListSharedData::SetCircleTessellationMaxError(float max_error) -{ - if (CircleSegmentMaxError == max_error) - return; - - IM_ASSERT(max_error > 0.0f); - CircleSegmentMaxError = max_error; - for (int i = 0; i < IM_ARRAYSIZE(CircleSegmentCounts); i++) - { - const float radius = (float)i; - CircleSegmentCounts[i] = (ImU8)((i > 0) ? IM_DRAWLIST_CIRCLE_AUTO_SEGMENT_CALC(radius, CircleSegmentMaxError) : IM_DRAWLIST_ARCFAST_SAMPLE_MAX); - } - ArcFastRadiusCutoff = IM_DRAWLIST_CIRCLE_AUTO_SEGMENT_CALC_R(IM_DRAWLIST_ARCFAST_SAMPLE_MAX, CircleSegmentMaxError); -} - -// Initialize before use in a new frame. We always have a command ready in the buffer. -void ImDrawList::_ResetForNewFrame() -{ - // Verify that the ImDrawCmd fields we want to memcmp() are contiguous in memory. - IM_STATIC_ASSERT(IM_OFFSETOF(ImDrawCmd, ClipRect) == 0); - IM_STATIC_ASSERT(IM_OFFSETOF(ImDrawCmd, TextureId) == sizeof(ImVec4)); - IM_STATIC_ASSERT(IM_OFFSETOF(ImDrawCmd, VtxOffset) == sizeof(ImVec4) + sizeof(ImTextureID)); - if (_Splitter._Count > 1) - _Splitter.Merge(this); - - CmdBuffer.resize(0); - IdxBuffer.resize(0); - VtxBuffer.resize(0); - Flags = _Data->InitialFlags; - memset(&_CmdHeader, 0, sizeof(_CmdHeader)); - _VtxCurrentIdx = 0; - _VtxWritePtr = NULL; - _IdxWritePtr = NULL; - _ClipRectStack.resize(0); - _TextureIdStack.resize(0); - _Path.resize(0); - _Splitter.Clear(); - CmdBuffer.push_back(ImDrawCmd()); - _FringeScale = 1.0f; -} - -void ImDrawList::_ClearFreeMemory() -{ - CmdBuffer.clear(); - IdxBuffer.clear(); - VtxBuffer.clear(); - Flags = ImDrawListFlags_None; - _VtxCurrentIdx = 0; - _VtxWritePtr = NULL; - _IdxWritePtr = NULL; - _ClipRectStack.clear(); - _TextureIdStack.clear(); - _Path.clear(); - _Splitter.ClearFreeMemory(); -} - -ImDrawList* ImDrawList::CloneOutput() const -{ - ImDrawList* dst = IM_NEW(ImDrawList(_Data)); - dst->CmdBuffer = CmdBuffer; - dst->IdxBuffer = IdxBuffer; - dst->VtxBuffer = VtxBuffer; - dst->Flags = Flags; - return dst; -} - -void ImDrawList::AddDrawCmd() -{ - ImDrawCmd draw_cmd; - draw_cmd.ClipRect = _CmdHeader.ClipRect; // Same as calling ImDrawCmd_HeaderCopy() - draw_cmd.TextureId = _CmdHeader.TextureId; - draw_cmd.VtxOffset = _CmdHeader.VtxOffset; - draw_cmd.IdxOffset = IdxBuffer.Size; - - IM_ASSERT(draw_cmd.ClipRect.x <= draw_cmd.ClipRect.z && draw_cmd.ClipRect.y <= draw_cmd.ClipRect.w); - CmdBuffer.push_back(draw_cmd); -} - -// Pop trailing draw command (used before merging or presenting to user) -// Note that this leaves the ImDrawList in a state unfit for further commands, as most code assume that CmdBuffer.Size > 0 && CmdBuffer.back().UserCallback == NULL -void ImDrawList::_PopUnusedDrawCmd() -{ - while (CmdBuffer.Size > 0) - { - ImDrawCmd* curr_cmd = &CmdBuffer.Data[CmdBuffer.Size - 1]; - if (curr_cmd->ElemCount != 0 || curr_cmd->UserCallback != NULL) - return;// break; - CmdBuffer.pop_back(); - } -} - -void ImDrawList::AddCallback(ImDrawCallback callback, void* callback_data) -{ - IM_ASSERT_PARANOID(CmdBuffer.Size > 0); - ImDrawCmd* curr_cmd = &CmdBuffer.Data[CmdBuffer.Size - 1]; - IM_ASSERT(curr_cmd->UserCallback == NULL); - if (curr_cmd->ElemCount != 0) - { - AddDrawCmd(); - curr_cmd = &CmdBuffer.Data[CmdBuffer.Size - 1]; - } - curr_cmd->UserCallback = callback; - curr_cmd->UserCallbackData = callback_data; - - AddDrawCmd(); // Force a new command after us (see comment below) -} - -// Compare ClipRect, TextureId and VtxOffset with a single memcmp() -#define ImDrawCmd_HeaderSize (IM_OFFSETOF(ImDrawCmd, VtxOffset) + sizeof(unsigned int)) -#define ImDrawCmd_HeaderCompare(CMD_LHS, CMD_RHS) (memcmp(CMD_LHS, CMD_RHS, ImDrawCmd_HeaderSize)) // Compare ClipRect, TextureId, VtxOffset -#define ImDrawCmd_HeaderCopy(CMD_DST, CMD_SRC) (memcpy(CMD_DST, CMD_SRC, ImDrawCmd_HeaderSize)) // Copy ClipRect, TextureId, VtxOffset -#define ImDrawCmd_AreSequentialIdxOffset(CMD_0, CMD_1) (CMD_0->IdxOffset + CMD_0->ElemCount == CMD_1->IdxOffset) - -// Try to merge two last draw commands -void ImDrawList::_TryMergeDrawCmds() -{ - IM_ASSERT_PARANOID(CmdBuffer.Size > 0); - ImDrawCmd* curr_cmd = &CmdBuffer.Data[CmdBuffer.Size - 1]; - ImDrawCmd* prev_cmd = curr_cmd - 1; - if (ImDrawCmd_HeaderCompare(curr_cmd, prev_cmd) == 0 && ImDrawCmd_AreSequentialIdxOffset(prev_cmd, curr_cmd) && curr_cmd->UserCallback == NULL && prev_cmd->UserCallback == NULL) - { - prev_cmd->ElemCount += curr_cmd->ElemCount; - CmdBuffer.pop_back(); - } -} - -// Our scheme may appears a bit unusual, basically we want the most-common calls AddLine AddRect etc. to not have to perform any check so we always have a command ready in the stack. -// The cost of figuring out if a new command has to be added or if we can merge is paid in those Update** functions only. -void ImDrawList::_OnChangedClipRect() -{ - // If current command is used with different settings we need to add a new command - IM_ASSERT_PARANOID(CmdBuffer.Size > 0); - ImDrawCmd* curr_cmd = &CmdBuffer.Data[CmdBuffer.Size - 1]; - if (curr_cmd->ElemCount != 0 && memcmp(&curr_cmd->ClipRect, &_CmdHeader.ClipRect, sizeof(ImVec4)) != 0) - { - AddDrawCmd(); - return; - } - IM_ASSERT(curr_cmd->UserCallback == NULL); - - // Try to merge with previous command if it matches, else use current command - ImDrawCmd* prev_cmd = curr_cmd - 1; - if (curr_cmd->ElemCount == 0 && CmdBuffer.Size > 1 && ImDrawCmd_HeaderCompare(&_CmdHeader, prev_cmd) == 0 && ImDrawCmd_AreSequentialIdxOffset(prev_cmd, curr_cmd) && prev_cmd->UserCallback == NULL) - { - CmdBuffer.pop_back(); - return; - } - - curr_cmd->ClipRect = _CmdHeader.ClipRect; -} - -void ImDrawList::_OnChangedTextureID() -{ - // If current command is used with different settings we need to add a new command - IM_ASSERT_PARANOID(CmdBuffer.Size > 0); - ImDrawCmd* curr_cmd = &CmdBuffer.Data[CmdBuffer.Size - 1]; - if (curr_cmd->ElemCount != 0 && curr_cmd->TextureId != _CmdHeader.TextureId) - { - AddDrawCmd(); - return; - } - IM_ASSERT(curr_cmd->UserCallback == NULL); - - // Try to merge with previous command if it matches, else use current command - ImDrawCmd* prev_cmd = curr_cmd - 1; - if (curr_cmd->ElemCount == 0 && CmdBuffer.Size > 1 && ImDrawCmd_HeaderCompare(&_CmdHeader, prev_cmd) == 0 && ImDrawCmd_AreSequentialIdxOffset(prev_cmd, curr_cmd) && prev_cmd->UserCallback == NULL) - { - CmdBuffer.pop_back(); - return; - } - - curr_cmd->TextureId = _CmdHeader.TextureId; -} - -void ImDrawList::_OnChangedVtxOffset() -{ - // We don't need to compare curr_cmd->VtxOffset != _CmdHeader.VtxOffset because we know it'll be different at the time we call this. - _VtxCurrentIdx = 0; - IM_ASSERT_PARANOID(CmdBuffer.Size > 0); - ImDrawCmd* curr_cmd = &CmdBuffer.Data[CmdBuffer.Size - 1]; - //IM_ASSERT(curr_cmd->VtxOffset != _CmdHeader.VtxOffset); // See #3349 - if (curr_cmd->ElemCount != 0) - { - AddDrawCmd(); - return; - } - IM_ASSERT(curr_cmd->UserCallback == NULL); - curr_cmd->VtxOffset = _CmdHeader.VtxOffset; -} - -int ImDrawList::_CalcCircleAutoSegmentCount(float radius) const -{ - // Automatic segment count - const int radius_idx = (int)(radius + 0.999999f); // ceil to never reduce accuracy - if (radius_idx >= 0 && radius_idx < IM_ARRAYSIZE(_Data->CircleSegmentCounts)) - return _Data->CircleSegmentCounts[radius_idx]; // Use cached value - else - return IM_DRAWLIST_CIRCLE_AUTO_SEGMENT_CALC(radius, _Data->CircleSegmentMaxError); -} - -// Render-level scissoring. This is passed down to your render function but not used for CPU-side coarse clipping. Prefer using higher-level ImGui::PushClipRect() to affect logic (hit-testing and widget culling) -void ImDrawList::PushClipRect(const ImVec2& cr_min, const ImVec2& cr_max, bool intersect_with_current_clip_rect) -{ - ImVec4 cr(cr_min.x, cr_min.y, cr_max.x, cr_max.y); - if (intersect_with_current_clip_rect) - { - ImVec4 current = _CmdHeader.ClipRect; - if (cr.x < current.x) cr.x = current.x; - if (cr.y < current.y) cr.y = current.y; - if (cr.z > current.z) cr.z = current.z; - if (cr.w > current.w) cr.w = current.w; - } - cr.z = ImMax(cr.x, cr.z); - cr.w = ImMax(cr.y, cr.w); - - _ClipRectStack.push_back(cr); - _CmdHeader.ClipRect = cr; - _OnChangedClipRect(); -} - -void ImDrawList::PushClipRectFullScreen() -{ - PushClipRect(ImVec2(_Data->ClipRectFullscreen.x, _Data->ClipRectFullscreen.y), ImVec2(_Data->ClipRectFullscreen.z, _Data->ClipRectFullscreen.w)); -} - -void ImDrawList::PopClipRect() -{ - _ClipRectStack.pop_back(); - _CmdHeader.ClipRect = (_ClipRectStack.Size == 0) ? _Data->ClipRectFullscreen : _ClipRectStack.Data[_ClipRectStack.Size - 1]; - _OnChangedClipRect(); -} - -void ImDrawList::PushTextureID(ImTextureID texture_id) -{ - _TextureIdStack.push_back(texture_id); - _CmdHeader.TextureId = texture_id; - _OnChangedTextureID(); -} - -void ImDrawList::PopTextureID() -{ - _TextureIdStack.pop_back(); - _CmdHeader.TextureId = (_TextureIdStack.Size == 0) ? (ImTextureID)NULL : _TextureIdStack.Data[_TextureIdStack.Size - 1]; - _OnChangedTextureID(); -} - -// Reserve space for a number of vertices and indices. -// You must finish filling your reserved data before calling PrimReserve() again, as it may reallocate or -// submit the intermediate results. PrimUnreserve() can be used to release unused allocations. -void ImDrawList::PrimReserve(int idx_count, int vtx_count) -{ - // Large mesh support (when enabled) - IM_ASSERT_PARANOID(idx_count >= 0 && vtx_count >= 0); - if (sizeof(ImDrawIdx) == 2 && (_VtxCurrentIdx + vtx_count >= (1 << 16)) && (Flags & ImDrawListFlags_AllowVtxOffset)) - { - // FIXME: In theory we should be testing that vtx_count <64k here. - // In practice, RenderText() relies on reserving ahead for a worst case scenario so it is currently useful for us - // to not make that check until we rework the text functions to handle clipping and large horizontal lines better. - _CmdHeader.VtxOffset = VtxBuffer.Size; - _OnChangedVtxOffset(); - } - - ImDrawCmd* draw_cmd = &CmdBuffer.Data[CmdBuffer.Size - 1]; - draw_cmd->ElemCount += idx_count; - - int vtx_buffer_old_size = VtxBuffer.Size; - VtxBuffer.resize(vtx_buffer_old_size + vtx_count); - _VtxWritePtr = VtxBuffer.Data + vtx_buffer_old_size; - - int idx_buffer_old_size = IdxBuffer.Size; - IdxBuffer.resize(idx_buffer_old_size + idx_count); - _IdxWritePtr = IdxBuffer.Data + idx_buffer_old_size; -} - -// Release the a number of reserved vertices/indices from the end of the last reservation made with PrimReserve(). -void ImDrawList::PrimUnreserve(int idx_count, int vtx_count) -{ - IM_ASSERT_PARANOID(idx_count >= 0 && vtx_count >= 0); - - ImDrawCmd* draw_cmd = &CmdBuffer.Data[CmdBuffer.Size - 1]; - draw_cmd->ElemCount -= idx_count; - VtxBuffer.shrink(VtxBuffer.Size - vtx_count); - IdxBuffer.shrink(IdxBuffer.Size - idx_count); -} - -// Fully unrolled with inline call to keep our debug builds decently fast. -void ImDrawList::PrimRect(const ImVec2& a, const ImVec2& c, ImU32 col) -{ - ImVec2 b(c.x, a.y), d(a.x, c.y), uv(_Data->TexUvWhitePixel); - ImDrawIdx idx = (ImDrawIdx)_VtxCurrentIdx; - _IdxWritePtr[0] = idx; _IdxWritePtr[1] = (ImDrawIdx)(idx+1); _IdxWritePtr[2] = (ImDrawIdx)(idx+2); - _IdxWritePtr[3] = idx; _IdxWritePtr[4] = (ImDrawIdx)(idx+2); _IdxWritePtr[5] = (ImDrawIdx)(idx+3); - _VtxWritePtr[0].pos = a; _VtxWritePtr[0].uv = uv; _VtxWritePtr[0].col = col; - _VtxWritePtr[1].pos = b; _VtxWritePtr[1].uv = uv; _VtxWritePtr[1].col = col; - _VtxWritePtr[2].pos = c; _VtxWritePtr[2].uv = uv; _VtxWritePtr[2].col = col; - _VtxWritePtr[3].pos = d; _VtxWritePtr[3].uv = uv; _VtxWritePtr[3].col = col; - _VtxWritePtr += 4; - _VtxCurrentIdx += 4; - _IdxWritePtr += 6; -} - -void ImDrawList::PrimRectUV(const ImVec2& a, const ImVec2& c, const ImVec2& uv_a, const ImVec2& uv_c, ImU32 col) -{ - ImVec2 b(c.x, a.y), d(a.x, c.y), uv_b(uv_c.x, uv_a.y), uv_d(uv_a.x, uv_c.y); - ImDrawIdx idx = (ImDrawIdx)_VtxCurrentIdx; - _IdxWritePtr[0] = idx; _IdxWritePtr[1] = (ImDrawIdx)(idx+1); _IdxWritePtr[2] = (ImDrawIdx)(idx+2); - _IdxWritePtr[3] = idx; _IdxWritePtr[4] = (ImDrawIdx)(idx+2); _IdxWritePtr[5] = (ImDrawIdx)(idx+3); - _VtxWritePtr[0].pos = a; _VtxWritePtr[0].uv = uv_a; _VtxWritePtr[0].col = col; - _VtxWritePtr[1].pos = b; _VtxWritePtr[1].uv = uv_b; _VtxWritePtr[1].col = col; - _VtxWritePtr[2].pos = c; _VtxWritePtr[2].uv = uv_c; _VtxWritePtr[2].col = col; - _VtxWritePtr[3].pos = d; _VtxWritePtr[3].uv = uv_d; _VtxWritePtr[3].col = col; - _VtxWritePtr += 4; - _VtxCurrentIdx += 4; - _IdxWritePtr += 6; -} - -void ImDrawList::PrimQuadUV(const ImVec2& a, const ImVec2& b, const ImVec2& c, const ImVec2& d, const ImVec2& uv_a, const ImVec2& uv_b, const ImVec2& uv_c, const ImVec2& uv_d, ImU32 col) -{ - ImDrawIdx idx = (ImDrawIdx)_VtxCurrentIdx; - _IdxWritePtr[0] = idx; _IdxWritePtr[1] = (ImDrawIdx)(idx+1); _IdxWritePtr[2] = (ImDrawIdx)(idx+2); - _IdxWritePtr[3] = idx; _IdxWritePtr[4] = (ImDrawIdx)(idx+2); _IdxWritePtr[5] = (ImDrawIdx)(idx+3); - _VtxWritePtr[0].pos = a; _VtxWritePtr[0].uv = uv_a; _VtxWritePtr[0].col = col; - _VtxWritePtr[1].pos = b; _VtxWritePtr[1].uv = uv_b; _VtxWritePtr[1].col = col; - _VtxWritePtr[2].pos = c; _VtxWritePtr[2].uv = uv_c; _VtxWritePtr[2].col = col; - _VtxWritePtr[3].pos = d; _VtxWritePtr[3].uv = uv_d; _VtxWritePtr[3].col = col; - _VtxWritePtr += 4; - _VtxCurrentIdx += 4; - _IdxWritePtr += 6; -} - -// On AddPolyline() and AddConvexPolyFilled() we intentionally avoid using ImVec2 and superfluous function calls to optimize debug/non-inlined builds. -// - Those macros expects l-values and need to be used as their own statement. -// - Those macros are intentionally not surrounded by the 'do {} while (0)' idiom because even that translates to runtime with debug compilers. -#define IM_NORMALIZE2F_OVER_ZERO(VX,VY) { float d2 = VX*VX + VY*VY; if (d2 > 0.0f) { float inv_len = ImRsqrt(d2); VX *= inv_len; VY *= inv_len; } } (void)0 -#define IM_FIXNORMAL2F_MAX_INVLEN2 100.0f // 500.0f (see #4053, #3366) -#define IM_FIXNORMAL2F(VX,VY) { float d2 = VX*VX + VY*VY; if (d2 > 0.000001f) { float inv_len2 = 1.0f / d2; if (inv_len2 > IM_FIXNORMAL2F_MAX_INVLEN2) inv_len2 = IM_FIXNORMAL2F_MAX_INVLEN2; VX *= inv_len2; VY *= inv_len2; } } (void)0 - -// TODO: Thickness anti-aliased lines cap are missing their AA fringe. -// We avoid using the ImVec2 math operators here to reduce cost to a minimum for debug/non-inlined builds. -void ImDrawList::AddPolyline(const ImVec2* points, const int points_count, ImU32 col, ImDrawFlags flags, float thickness) -{ - if (points_count < 2 || (col & IM_COL32_A_MASK) == 0) - return; - - const bool closed = (flags & ImDrawFlags_Closed) != 0; - const ImVec2 opaque_uv = _Data->TexUvWhitePixel; - const int count = closed ? points_count : points_count - 1; // The number of line segments we need to draw - const bool thick_line = (thickness > _FringeScale); - - if (Flags & ImDrawListFlags_AntiAliasedLines) - { - // Anti-aliased stroke - const float AA_SIZE = _FringeScale; - const ImU32 col_trans = col & ~IM_COL32_A_MASK; - - // Thicknesses <1.0 should behave like thickness 1.0 - thickness = ImMax(thickness, 1.0f); - const int integer_thickness = (int)thickness; - const float fractional_thickness = thickness - integer_thickness; - - // Do we want to draw this line using a texture? - // - For now, only draw integer-width lines using textures to avoid issues with the way scaling occurs, could be improved. - // - If AA_SIZE is not 1.0f we cannot use the texture path. - const bool use_texture = (Flags & ImDrawListFlags_AntiAliasedLinesUseTex) && (integer_thickness < IM_DRAWLIST_TEX_LINES_WIDTH_MAX) && (fractional_thickness <= 0.00001f) && (AA_SIZE == 1.0f); - - // We should never hit this, because NewFrame() doesn't set ImDrawListFlags_AntiAliasedLinesUseTex unless ImFontAtlasFlags_NoBakedLines is off - IM_ASSERT_PARANOID(!use_texture || !(_Data->Font->ContainerAtlas->Flags & ImFontAtlasFlags_NoBakedLines)); - - const int idx_count = use_texture ? (count * 6) : (thick_line ? count * 18 : count * 12); - const int vtx_count = use_texture ? (points_count * 2) : (thick_line ? points_count * 4 : points_count * 3); - PrimReserve(idx_count, vtx_count); - - // Temporary buffer - // The first items are normals at each line point, then after that there are either 2 or 4 temp points for each line point - _Data->TempBuffer.reserve_discard(points_count * ((use_texture || !thick_line) ? 3 : 5)); - ImVec2* temp_normals = _Data->TempBuffer.Data; - ImVec2* temp_points = temp_normals + points_count; - - // Calculate normals (tangents) for each line segment - for (int i1 = 0; i1 < count; i1++) - { - const int i2 = (i1 + 1) == points_count ? 0 : i1 + 1; - float dx = points[i2].x - points[i1].x; - float dy = points[i2].y - points[i1].y; - IM_NORMALIZE2F_OVER_ZERO(dx, dy); - temp_normals[i1].x = dy; - temp_normals[i1].y = -dx; - } - if (!closed) - temp_normals[points_count - 1] = temp_normals[points_count - 2]; - - // If we are drawing a one-pixel-wide line without a texture, or a textured line of any width, we only need 2 or 3 vertices per point - if (use_texture || !thick_line) - { - // [PATH 1] Texture-based lines (thick or non-thick) - // [PATH 2] Non texture-based lines (non-thick) - - // The width of the geometry we need to draw - this is essentially pixels for the line itself, plus "one pixel" for AA. - // - In the texture-based path, we don't use AA_SIZE here because the +1 is tied to the generated texture - // (see ImFontAtlasBuildRenderLinesTexData() function), and so alternate values won't work without changes to that code. - // - In the non texture-based paths, we would allow AA_SIZE to potentially be != 1.0f with a patch (e.g. fringe_scale patch to - // allow scaling geometry while preserving one-screen-pixel AA fringe). - const float half_draw_size = use_texture ? ((thickness * 0.5f) + 1) : AA_SIZE; - - // If line is not closed, the first and last points need to be generated differently as there are no normals to blend - if (!closed) - { - temp_points[0] = points[0] + temp_normals[0] * half_draw_size; - temp_points[1] = points[0] - temp_normals[0] * half_draw_size; - temp_points[(points_count-1)*2+0] = points[points_count-1] + temp_normals[points_count-1] * half_draw_size; - temp_points[(points_count-1)*2+1] = points[points_count-1] - temp_normals[points_count-1] * half_draw_size; - } - - // Generate the indices to form a number of triangles for each line segment, and the vertices for the line edges - // This takes points n and n+1 and writes into n+1, with the first point in a closed line being generated from the final one (as n+1 wraps) - // FIXME-OPT: Merge the different loops, possibly remove the temporary buffer. - unsigned int idx1 = _VtxCurrentIdx; // Vertex index for start of line segment - for (int i1 = 0; i1 < count; i1++) // i1 is the first point of the line segment - { - const int i2 = (i1 + 1) == points_count ? 0 : i1 + 1; // i2 is the second point of the line segment - const unsigned int idx2 = ((i1 + 1) == points_count) ? _VtxCurrentIdx : (idx1 + (use_texture ? 2 : 3)); // Vertex index for end of segment - - // Average normals - float dm_x = (temp_normals[i1].x + temp_normals[i2].x) * 0.5f; - float dm_y = (temp_normals[i1].y + temp_normals[i2].y) * 0.5f; - IM_FIXNORMAL2F(dm_x, dm_y); - dm_x *= half_draw_size; // dm_x, dm_y are offset to the outer edge of the AA area - dm_y *= half_draw_size; - - // Add temporary vertexes for the outer edges - ImVec2* out_vtx = &temp_points[i2 * 2]; - out_vtx[0].x = points[i2].x + dm_x; - out_vtx[0].y = points[i2].y + dm_y; - out_vtx[1].x = points[i2].x - dm_x; - out_vtx[1].y = points[i2].y - dm_y; - - if (use_texture) - { - // Add indices for two triangles - _IdxWritePtr[0] = (ImDrawIdx)(idx2 + 0); _IdxWritePtr[1] = (ImDrawIdx)(idx1 + 0); _IdxWritePtr[2] = (ImDrawIdx)(idx1 + 1); // Right tri - _IdxWritePtr[3] = (ImDrawIdx)(idx2 + 1); _IdxWritePtr[4] = (ImDrawIdx)(idx1 + 1); _IdxWritePtr[5] = (ImDrawIdx)(idx2 + 0); // Left tri - _IdxWritePtr += 6; - } - else - { - // Add indexes for four triangles - _IdxWritePtr[0] = (ImDrawIdx)(idx2 + 0); _IdxWritePtr[1] = (ImDrawIdx)(idx1 + 0); _IdxWritePtr[2] = (ImDrawIdx)(idx1 + 2); // Right tri 1 - _IdxWritePtr[3] = (ImDrawIdx)(idx1 + 2); _IdxWritePtr[4] = (ImDrawIdx)(idx2 + 2); _IdxWritePtr[5] = (ImDrawIdx)(idx2 + 0); // Right tri 2 - _IdxWritePtr[6] = (ImDrawIdx)(idx2 + 1); _IdxWritePtr[7] = (ImDrawIdx)(idx1 + 1); _IdxWritePtr[8] = (ImDrawIdx)(idx1 + 0); // Left tri 1 - _IdxWritePtr[9] = (ImDrawIdx)(idx1 + 0); _IdxWritePtr[10] = (ImDrawIdx)(idx2 + 0); _IdxWritePtr[11] = (ImDrawIdx)(idx2 + 1); // Left tri 2 - _IdxWritePtr += 12; - } - - idx1 = idx2; - } - - // Add vertexes for each point on the line - if (use_texture) - { - // If we're using textures we only need to emit the left/right edge vertices - ImVec4 tex_uvs = _Data->TexUvLines[integer_thickness]; - /*if (fractional_thickness != 0.0f) // Currently always zero when use_texture==false! - { - const ImVec4 tex_uvs_1 = _Data->TexUvLines[integer_thickness + 1]; - tex_uvs.x = tex_uvs.x + (tex_uvs_1.x - tex_uvs.x) * fractional_thickness; // inlined ImLerp() - tex_uvs.y = tex_uvs.y + (tex_uvs_1.y - tex_uvs.y) * fractional_thickness; - tex_uvs.z = tex_uvs.z + (tex_uvs_1.z - tex_uvs.z) * fractional_thickness; - tex_uvs.w = tex_uvs.w + (tex_uvs_1.w - tex_uvs.w) * fractional_thickness; - }*/ - ImVec2 tex_uv0(tex_uvs.x, tex_uvs.y); - ImVec2 tex_uv1(tex_uvs.z, tex_uvs.w); - for (int i = 0; i < points_count; i++) - { - _VtxWritePtr[0].pos = temp_points[i * 2 + 0]; _VtxWritePtr[0].uv = tex_uv0; _VtxWritePtr[0].col = col; // Left-side outer edge - _VtxWritePtr[1].pos = temp_points[i * 2 + 1]; _VtxWritePtr[1].uv = tex_uv1; _VtxWritePtr[1].col = col; // Right-side outer edge - _VtxWritePtr += 2; - } - } - else - { - // If we're not using a texture, we need the center vertex as well - for (int i = 0; i < points_count; i++) - { - _VtxWritePtr[0].pos = points[i]; _VtxWritePtr[0].uv = opaque_uv; _VtxWritePtr[0].col = col; // Center of line - _VtxWritePtr[1].pos = temp_points[i * 2 + 0]; _VtxWritePtr[1].uv = opaque_uv; _VtxWritePtr[1].col = col_trans; // Left-side outer edge - _VtxWritePtr[2].pos = temp_points[i * 2 + 1]; _VtxWritePtr[2].uv = opaque_uv; _VtxWritePtr[2].col = col_trans; // Right-side outer edge - _VtxWritePtr += 3; - } - } - } - else - { - // [PATH 2] Non texture-based lines (thick): we need to draw the solid line core and thus require four vertices per point - const float half_inner_thickness = (thickness - AA_SIZE) * 0.5f; - - // If line is not closed, the first and last points need to be generated differently as there are no normals to blend - if (!closed) - { - const int points_last = points_count - 1; - temp_points[0] = points[0] + temp_normals[0] * (half_inner_thickness + AA_SIZE); - temp_points[1] = points[0] + temp_normals[0] * (half_inner_thickness); - temp_points[2] = points[0] - temp_normals[0] * (half_inner_thickness); - temp_points[3] = points[0] - temp_normals[0] * (half_inner_thickness + AA_SIZE); - temp_points[points_last * 4 + 0] = points[points_last] + temp_normals[points_last] * (half_inner_thickness + AA_SIZE); - temp_points[points_last * 4 + 1] = points[points_last] + temp_normals[points_last] * (half_inner_thickness); - temp_points[points_last * 4 + 2] = points[points_last] - temp_normals[points_last] * (half_inner_thickness); - temp_points[points_last * 4 + 3] = points[points_last] - temp_normals[points_last] * (half_inner_thickness + AA_SIZE); - } - - // Generate the indices to form a number of triangles for each line segment, and the vertices for the line edges - // This takes points n and n+1 and writes into n+1, with the first point in a closed line being generated from the final one (as n+1 wraps) - // FIXME-OPT: Merge the different loops, possibly remove the temporary buffer. - unsigned int idx1 = _VtxCurrentIdx; // Vertex index for start of line segment - for (int i1 = 0; i1 < count; i1++) // i1 is the first point of the line segment - { - const int i2 = (i1 + 1) == points_count ? 0 : (i1 + 1); // i2 is the second point of the line segment - const unsigned int idx2 = (i1 + 1) == points_count ? _VtxCurrentIdx : (idx1 + 4); // Vertex index for end of segment - - // Average normals - float dm_x = (temp_normals[i1].x + temp_normals[i2].x) * 0.5f; - float dm_y = (temp_normals[i1].y + temp_normals[i2].y) * 0.5f; - IM_FIXNORMAL2F(dm_x, dm_y); - float dm_out_x = dm_x * (half_inner_thickness + AA_SIZE); - float dm_out_y = dm_y * (half_inner_thickness + AA_SIZE); - float dm_in_x = dm_x * half_inner_thickness; - float dm_in_y = dm_y * half_inner_thickness; - - // Add temporary vertices - ImVec2* out_vtx = &temp_points[i2 * 4]; - out_vtx[0].x = points[i2].x + dm_out_x; - out_vtx[0].y = points[i2].y + dm_out_y; - out_vtx[1].x = points[i2].x + dm_in_x; - out_vtx[1].y = points[i2].y + dm_in_y; - out_vtx[2].x = points[i2].x - dm_in_x; - out_vtx[2].y = points[i2].y - dm_in_y; - out_vtx[3].x = points[i2].x - dm_out_x; - out_vtx[3].y = points[i2].y - dm_out_y; - - // Add indexes - _IdxWritePtr[0] = (ImDrawIdx)(idx2 + 1); _IdxWritePtr[1] = (ImDrawIdx)(idx1 + 1); _IdxWritePtr[2] = (ImDrawIdx)(idx1 + 2); - _IdxWritePtr[3] = (ImDrawIdx)(idx1 + 2); _IdxWritePtr[4] = (ImDrawIdx)(idx2 + 2); _IdxWritePtr[5] = (ImDrawIdx)(idx2 + 1); - _IdxWritePtr[6] = (ImDrawIdx)(idx2 + 1); _IdxWritePtr[7] = (ImDrawIdx)(idx1 + 1); _IdxWritePtr[8] = (ImDrawIdx)(idx1 + 0); - _IdxWritePtr[9] = (ImDrawIdx)(idx1 + 0); _IdxWritePtr[10] = (ImDrawIdx)(idx2 + 0); _IdxWritePtr[11] = (ImDrawIdx)(idx2 + 1); - _IdxWritePtr[12] = (ImDrawIdx)(idx2 + 2); _IdxWritePtr[13] = (ImDrawIdx)(idx1 + 2); _IdxWritePtr[14] = (ImDrawIdx)(idx1 + 3); - _IdxWritePtr[15] = (ImDrawIdx)(idx1 + 3); _IdxWritePtr[16] = (ImDrawIdx)(idx2 + 3); _IdxWritePtr[17] = (ImDrawIdx)(idx2 + 2); - _IdxWritePtr += 18; - - idx1 = idx2; - } - - // Add vertices - for (int i = 0; i < points_count; i++) - { - _VtxWritePtr[0].pos = temp_points[i * 4 + 0]; _VtxWritePtr[0].uv = opaque_uv; _VtxWritePtr[0].col = col_trans; - _VtxWritePtr[1].pos = temp_points[i * 4 + 1]; _VtxWritePtr[1].uv = opaque_uv; _VtxWritePtr[1].col = col; - _VtxWritePtr[2].pos = temp_points[i * 4 + 2]; _VtxWritePtr[2].uv = opaque_uv; _VtxWritePtr[2].col = col; - _VtxWritePtr[3].pos = temp_points[i * 4 + 3]; _VtxWritePtr[3].uv = opaque_uv; _VtxWritePtr[3].col = col_trans; - _VtxWritePtr += 4; - } - } - _VtxCurrentIdx += (ImDrawIdx)vtx_count; - } - else - { - // [PATH 4] Non texture-based, Non anti-aliased lines - const int idx_count = count * 6; - const int vtx_count = count * 4; // FIXME-OPT: Not sharing edges - PrimReserve(idx_count, vtx_count); - - for (int i1 = 0; i1 < count; i1++) - { - const int i2 = (i1 + 1) == points_count ? 0 : i1 + 1; - const ImVec2& p1 = points[i1]; - const ImVec2& p2 = points[i2]; - - float dx = p2.x - p1.x; - float dy = p2.y - p1.y; - IM_NORMALIZE2F_OVER_ZERO(dx, dy); - dx *= (thickness * 0.5f); - dy *= (thickness * 0.5f); - - _VtxWritePtr[0].pos.x = p1.x + dy; _VtxWritePtr[0].pos.y = p1.y - dx; _VtxWritePtr[0].uv = opaque_uv; _VtxWritePtr[0].col = col; - _VtxWritePtr[1].pos.x = p2.x + dy; _VtxWritePtr[1].pos.y = p2.y - dx; _VtxWritePtr[1].uv = opaque_uv; _VtxWritePtr[1].col = col; - _VtxWritePtr[2].pos.x = p2.x - dy; _VtxWritePtr[2].pos.y = p2.y + dx; _VtxWritePtr[2].uv = opaque_uv; _VtxWritePtr[2].col = col; - _VtxWritePtr[3].pos.x = p1.x - dy; _VtxWritePtr[3].pos.y = p1.y + dx; _VtxWritePtr[3].uv = opaque_uv; _VtxWritePtr[3].col = col; - _VtxWritePtr += 4; - - _IdxWritePtr[0] = (ImDrawIdx)(_VtxCurrentIdx); _IdxWritePtr[1] = (ImDrawIdx)(_VtxCurrentIdx + 1); _IdxWritePtr[2] = (ImDrawIdx)(_VtxCurrentIdx + 2); - _IdxWritePtr[3] = (ImDrawIdx)(_VtxCurrentIdx); _IdxWritePtr[4] = (ImDrawIdx)(_VtxCurrentIdx + 2); _IdxWritePtr[5] = (ImDrawIdx)(_VtxCurrentIdx + 3); - _IdxWritePtr += 6; - _VtxCurrentIdx += 4; - } - } -} - -// - We intentionally avoid using ImVec2 and its math operators here to reduce cost to a minimum for debug/non-inlined builds. -// - Filled shapes must always use clockwise winding order. The anti-aliasing fringe depends on it. Counter-clockwise shapes will have "inward" anti-aliasing. -void ImDrawList::AddConvexPolyFilled(const ImVec2* points, const int points_count, ImU32 col) -{ - if (points_count < 3 || (col & IM_COL32_A_MASK) == 0) - return; - - const ImVec2 uv = _Data->TexUvWhitePixel; - - if (Flags & ImDrawListFlags_AntiAliasedFill) - { - // Anti-aliased Fill - const float AA_SIZE = _FringeScale; - const ImU32 col_trans = col & ~IM_COL32_A_MASK; - const int idx_count = (points_count - 2)*3 + points_count * 6; - const int vtx_count = (points_count * 2); - PrimReserve(idx_count, vtx_count); - - // Add indexes for fill - unsigned int vtx_inner_idx = _VtxCurrentIdx; - unsigned int vtx_outer_idx = _VtxCurrentIdx + 1; - for (int i = 2; i < points_count; i++) - { - _IdxWritePtr[0] = (ImDrawIdx)(vtx_inner_idx); _IdxWritePtr[1] = (ImDrawIdx)(vtx_inner_idx + ((i - 1) << 1)); _IdxWritePtr[2] = (ImDrawIdx)(vtx_inner_idx + (i << 1)); - _IdxWritePtr += 3; - } - - // Compute normals - _Data->TempBuffer.reserve_discard(points_count); - ImVec2* temp_normals = _Data->TempBuffer.Data; - for (int i0 = points_count - 1, i1 = 0; i1 < points_count; i0 = i1++) - { - const ImVec2& p0 = points[i0]; - const ImVec2& p1 = points[i1]; - float dx = p1.x - p0.x; - float dy = p1.y - p0.y; - IM_NORMALIZE2F_OVER_ZERO(dx, dy); - temp_normals[i0].x = dy; - temp_normals[i0].y = -dx; - } - - for (int i0 = points_count - 1, i1 = 0; i1 < points_count; i0 = i1++) - { - // Average normals - const ImVec2& n0 = temp_normals[i0]; - const ImVec2& n1 = temp_normals[i1]; - float dm_x = (n0.x + n1.x) * 0.5f; - float dm_y = (n0.y + n1.y) * 0.5f; - IM_FIXNORMAL2F(dm_x, dm_y); - dm_x *= AA_SIZE * 0.5f; - dm_y *= AA_SIZE * 0.5f; - - // Add vertices - _VtxWritePtr[0].pos.x = (points[i1].x - dm_x); _VtxWritePtr[0].pos.y = (points[i1].y - dm_y); _VtxWritePtr[0].uv = uv; _VtxWritePtr[0].col = col; // Inner - _VtxWritePtr[1].pos.x = (points[i1].x + dm_x); _VtxWritePtr[1].pos.y = (points[i1].y + dm_y); _VtxWritePtr[1].uv = uv; _VtxWritePtr[1].col = col_trans; // Outer - _VtxWritePtr += 2; - - // Add indexes for fringes - _IdxWritePtr[0] = (ImDrawIdx)(vtx_inner_idx + (i1 << 1)); _IdxWritePtr[1] = (ImDrawIdx)(vtx_inner_idx + (i0 << 1)); _IdxWritePtr[2] = (ImDrawIdx)(vtx_outer_idx + (i0 << 1)); - _IdxWritePtr[3] = (ImDrawIdx)(vtx_outer_idx + (i0 << 1)); _IdxWritePtr[4] = (ImDrawIdx)(vtx_outer_idx + (i1 << 1)); _IdxWritePtr[5] = (ImDrawIdx)(vtx_inner_idx + (i1 << 1)); - _IdxWritePtr += 6; - } - _VtxCurrentIdx += (ImDrawIdx)vtx_count; - } - else - { - // Non Anti-aliased Fill - const int idx_count = (points_count - 2)*3; - const int vtx_count = points_count; - PrimReserve(idx_count, vtx_count); - for (int i = 0; i < vtx_count; i++) - { - _VtxWritePtr[0].pos = points[i]; _VtxWritePtr[0].uv = uv; _VtxWritePtr[0].col = col; - _VtxWritePtr++; - } - for (int i = 2; i < points_count; i++) - { - _IdxWritePtr[0] = (ImDrawIdx)(_VtxCurrentIdx); _IdxWritePtr[1] = (ImDrawIdx)(_VtxCurrentIdx + i - 1); _IdxWritePtr[2] = (ImDrawIdx)(_VtxCurrentIdx + i); - _IdxWritePtr += 3; - } - _VtxCurrentIdx += (ImDrawIdx)vtx_count; - } -} - -void ImDrawList::_PathArcToFastEx(const ImVec2& center, float radius, int a_min_sample, int a_max_sample, int a_step) -{ - if (radius < 0.5f) - { - _Path.push_back(center); - return; - } - - // Calculate arc auto segment step size - if (a_step <= 0) - a_step = IM_DRAWLIST_ARCFAST_SAMPLE_MAX / _CalcCircleAutoSegmentCount(radius); - - // Make sure we never do steps larger than one quarter of the circle - a_step = ImClamp(a_step, 1, IM_DRAWLIST_ARCFAST_TABLE_SIZE / 4); - - const int sample_range = ImAbs(a_max_sample - a_min_sample); - const int a_next_step = a_step; - - int samples = sample_range + 1; - bool extra_max_sample = false; - if (a_step > 1) - { - samples = sample_range / a_step + 1; - const int overstep = sample_range % a_step; - - if (overstep > 0) - { - extra_max_sample = true; - samples++; - - // When we have overstep to avoid awkwardly looking one long line and one tiny one at the end, - // distribute first step range evenly between them by reducing first step size. - if (sample_range > 0) - a_step -= (a_step - overstep) / 2; - } - } - - _Path.resize(_Path.Size + samples); - ImVec2* out_ptr = _Path.Data + (_Path.Size - samples); - - int sample_index = a_min_sample; - if (sample_index < 0 || sample_index >= IM_DRAWLIST_ARCFAST_SAMPLE_MAX) - { - sample_index = sample_index % IM_DRAWLIST_ARCFAST_SAMPLE_MAX; - if (sample_index < 0) - sample_index += IM_DRAWLIST_ARCFAST_SAMPLE_MAX; - } - - if (a_max_sample >= a_min_sample) - { - for (int a = a_min_sample; a <= a_max_sample; a += a_step, sample_index += a_step, a_step = a_next_step) - { - // a_step is clamped to IM_DRAWLIST_ARCFAST_SAMPLE_MAX, so we have guaranteed that it will not wrap over range twice or more - if (sample_index >= IM_DRAWLIST_ARCFAST_SAMPLE_MAX) - sample_index -= IM_DRAWLIST_ARCFAST_SAMPLE_MAX; - - const ImVec2 s = _Data->ArcFastVtx[sample_index]; - out_ptr->x = center.x + s.x * radius; - out_ptr->y = center.y + s.y * radius; - out_ptr++; - } - } - else - { - for (int a = a_min_sample; a >= a_max_sample; a -= a_step, sample_index -= a_step, a_step = a_next_step) - { - // a_step is clamped to IM_DRAWLIST_ARCFAST_SAMPLE_MAX, so we have guaranteed that it will not wrap over range twice or more - if (sample_index < 0) - sample_index += IM_DRAWLIST_ARCFAST_SAMPLE_MAX; - - const ImVec2 s = _Data->ArcFastVtx[sample_index]; - out_ptr->x = center.x + s.x * radius; - out_ptr->y = center.y + s.y * radius; - out_ptr++; - } - } - - if (extra_max_sample) - { - int normalized_max_sample = a_max_sample % IM_DRAWLIST_ARCFAST_SAMPLE_MAX; - if (normalized_max_sample < 0) - normalized_max_sample += IM_DRAWLIST_ARCFAST_SAMPLE_MAX; - - const ImVec2 s = _Data->ArcFastVtx[normalized_max_sample]; - out_ptr->x = center.x + s.x * radius; - out_ptr->y = center.y + s.y * radius; - out_ptr++; - } - - IM_ASSERT_PARANOID(_Path.Data + _Path.Size == out_ptr); -} - -void ImDrawList::_PathArcToN(const ImVec2& center, float radius, float a_min, float a_max, int num_segments) -{ - if (radius < 0.5f) - { - _Path.push_back(center); - return; - } - - // Note that we are adding a point at both a_min and a_max. - // If you are trying to draw a full closed circle you don't want the overlapping points! - _Path.reserve(_Path.Size + (num_segments + 1)); - for (int i = 0; i <= num_segments; i++) - { - const float a = a_min + ((float)i / (float)num_segments) * (a_max - a_min); - _Path.push_back(ImVec2(center.x + ImCos(a) * radius, center.y + ImSin(a) * radius)); - } -} - -// 0: East, 3: South, 6: West, 9: North, 12: East -void ImDrawList::PathArcToFast(const ImVec2& center, float radius, int a_min_of_12, int a_max_of_12) -{ - if (radius < 0.5f) - { - _Path.push_back(center); - return; - } - _PathArcToFastEx(center, radius, a_min_of_12 * IM_DRAWLIST_ARCFAST_SAMPLE_MAX / 12, a_max_of_12 * IM_DRAWLIST_ARCFAST_SAMPLE_MAX / 12, 0); -} - -void ImDrawList::PathArcTo(const ImVec2& center, float radius, float a_min, float a_max, int num_segments) -{ - if (radius < 0.5f) - { - _Path.push_back(center); - return; - } - - if (num_segments > 0) - { - _PathArcToN(center, radius, a_min, a_max, num_segments); - return; - } - - // Automatic segment count - if (radius <= _Data->ArcFastRadiusCutoff) - { - const bool a_is_reverse = a_max < a_min; - - // We are going to use precomputed values for mid samples. - // Determine first and last sample in lookup table that belong to the arc. - const float a_min_sample_f = IM_DRAWLIST_ARCFAST_SAMPLE_MAX * a_min / (IM_PI * 2.0f); - const float a_max_sample_f = IM_DRAWLIST_ARCFAST_SAMPLE_MAX * a_max / (IM_PI * 2.0f); - - const int a_min_sample = a_is_reverse ? (int)ImFloor(a_min_sample_f) : (int)ImCeil(a_min_sample_f); - const int a_max_sample = a_is_reverse ? (int)ImCeil(a_max_sample_f) : (int)ImFloor(a_max_sample_f); - const int a_mid_samples = a_is_reverse ? ImMax(a_min_sample - a_max_sample, 0) : ImMax(a_max_sample - a_min_sample, 0); - - const float a_min_segment_angle = a_min_sample * IM_PI * 2.0f / IM_DRAWLIST_ARCFAST_SAMPLE_MAX; - const float a_max_segment_angle = a_max_sample * IM_PI * 2.0f / IM_DRAWLIST_ARCFAST_SAMPLE_MAX; - const bool a_emit_start = ImAbs(a_min_segment_angle - a_min) >= 1e-5f; - const bool a_emit_end = ImAbs(a_max - a_max_segment_angle) >= 1e-5f; - - _Path.reserve(_Path.Size + (a_mid_samples + 1 + (a_emit_start ? 1 : 0) + (a_emit_end ? 1 : 0))); - if (a_emit_start) - _Path.push_back(ImVec2(center.x + ImCos(a_min) * radius, center.y + ImSin(a_min) * radius)); - if (a_mid_samples > 0) - _PathArcToFastEx(center, radius, a_min_sample, a_max_sample, 0); - if (a_emit_end) - _Path.push_back(ImVec2(center.x + ImCos(a_max) * radius, center.y + ImSin(a_max) * radius)); - } - else - { - const float arc_length = ImAbs(a_max - a_min); - const int circle_segment_count = _CalcCircleAutoSegmentCount(radius); - const int arc_segment_count = ImMax((int)ImCeil(circle_segment_count * arc_length / (IM_PI * 2.0f)), (int)(2.0f * IM_PI / arc_length)); - _PathArcToN(center, radius, a_min, a_max, arc_segment_count); - } -} - -void ImDrawList::PathEllipticalArcTo(const ImVec2& center, float radius_x, float radius_y, float rot, float a_min, float a_max, int num_segments) -{ - if (num_segments <= 0) - num_segments = _CalcCircleAutoSegmentCount(ImMax(radius_x, radius_y)); // A bit pessimistic, maybe there's a better computation to do here. - - _Path.reserve(_Path.Size + (num_segments + 1)); - - const float cos_rot = ImCos(rot); - const float sin_rot = ImSin(rot); - for (int i = 0; i <= num_segments; i++) - { - const float a = a_min + ((float)i / (float)num_segments) * (a_max - a_min); - ImVec2 point(ImCos(a) * radius_x, ImSin(a) * radius_y); - const float rel_x = (point.x * cos_rot) - (point.y * sin_rot); - const float rel_y = (point.x * sin_rot) + (point.y * cos_rot); - point.x = rel_x + center.x; - point.y = rel_y + center.y; - _Path.push_back(point); - } -} - -ImVec2 ImBezierCubicCalc(const ImVec2& p1, const ImVec2& p2, const ImVec2& p3, const ImVec2& p4, float t) -{ - float u = 1.0f - t; - float w1 = u * u * u; - float w2 = 3 * u * u * t; - float w3 = 3 * u * t * t; - float w4 = t * t * t; - return ImVec2(w1 * p1.x + w2 * p2.x + w3 * p3.x + w4 * p4.x, w1 * p1.y + w2 * p2.y + w3 * p3.y + w4 * p4.y); -} - -ImVec2 ImBezierQuadraticCalc(const ImVec2& p1, const ImVec2& p2, const ImVec2& p3, float t) -{ - float u = 1.0f - t; - float w1 = u * u; - float w2 = 2 * u * t; - float w3 = t * t; - return ImVec2(w1 * p1.x + w2 * p2.x + w3 * p3.x, w1 * p1.y + w2 * p2.y + w3 * p3.y); -} - -// Closely mimics ImBezierCubicClosestPointCasteljau() in imgui.cpp -static void PathBezierCubicCurveToCasteljau(ImVector* path, float x1, float y1, float x2, float y2, float x3, float y3, float x4, float y4, float tess_tol, int level) -{ - float dx = x4 - x1; - float dy = y4 - y1; - float d2 = (x2 - x4) * dy - (y2 - y4) * dx; - float d3 = (x3 - x4) * dy - (y3 - y4) * dx; - d2 = (d2 >= 0) ? d2 : -d2; - d3 = (d3 >= 0) ? d3 : -d3; - if ((d2 + d3) * (d2 + d3) < tess_tol * (dx * dx + dy * dy)) - { - path->push_back(ImVec2(x4, y4)); - } - else if (level < 10) - { - float x12 = (x1 + x2) * 0.5f, y12 = (y1 + y2) * 0.5f; - float x23 = (x2 + x3) * 0.5f, y23 = (y2 + y3) * 0.5f; - float x34 = (x3 + x4) * 0.5f, y34 = (y3 + y4) * 0.5f; - float x123 = (x12 + x23) * 0.5f, y123 = (y12 + y23) * 0.5f; - float x234 = (x23 + x34) * 0.5f, y234 = (y23 + y34) * 0.5f; - float x1234 = (x123 + x234) * 0.5f, y1234 = (y123 + y234) * 0.5f; - PathBezierCubicCurveToCasteljau(path, x1, y1, x12, y12, x123, y123, x1234, y1234, tess_tol, level + 1); - PathBezierCubicCurveToCasteljau(path, x1234, y1234, x234, y234, x34, y34, x4, y4, tess_tol, level + 1); - } -} - -static void PathBezierQuadraticCurveToCasteljau(ImVector* path, float x1, float y1, float x2, float y2, float x3, float y3, float tess_tol, int level) -{ - float dx = x3 - x1, dy = y3 - y1; - float det = (x2 - x3) * dy - (y2 - y3) * dx; - if (det * det * 4.0f < tess_tol * (dx * dx + dy * dy)) - { - path->push_back(ImVec2(x3, y3)); - } - else if (level < 10) - { - float x12 = (x1 + x2) * 0.5f, y12 = (y1 + y2) * 0.5f; - float x23 = (x2 + x3) * 0.5f, y23 = (y2 + y3) * 0.5f; - float x123 = (x12 + x23) * 0.5f, y123 = (y12 + y23) * 0.5f; - PathBezierQuadraticCurveToCasteljau(path, x1, y1, x12, y12, x123, y123, tess_tol, level + 1); - PathBezierQuadraticCurveToCasteljau(path, x123, y123, x23, y23, x3, y3, tess_tol, level + 1); - } -} - -void ImDrawList::PathBezierCubicCurveTo(const ImVec2& p2, const ImVec2& p3, const ImVec2& p4, int num_segments) -{ - ImVec2 p1 = _Path.back(); - if (num_segments == 0) - { - IM_ASSERT(_Data->CurveTessellationTol > 0.0f); - PathBezierCubicCurveToCasteljau(&_Path, p1.x, p1.y, p2.x, p2.y, p3.x, p3.y, p4.x, p4.y, _Data->CurveTessellationTol, 0); // Auto-tessellated - } - else - { - float t_step = 1.0f / (float)num_segments; - for (int i_step = 1; i_step <= num_segments; i_step++) - _Path.push_back(ImBezierCubicCalc(p1, p2, p3, p4, t_step * i_step)); - } -} - -void ImDrawList::PathBezierQuadraticCurveTo(const ImVec2& p2, const ImVec2& p3, int num_segments) -{ - ImVec2 p1 = _Path.back(); - if (num_segments == 0) - { - IM_ASSERT(_Data->CurveTessellationTol > 0.0f); - PathBezierQuadraticCurveToCasteljau(&_Path, p1.x, p1.y, p2.x, p2.y, p3.x, p3.y, _Data->CurveTessellationTol, 0);// Auto-tessellated - } - else - { - float t_step = 1.0f / (float)num_segments; - for (int i_step = 1; i_step <= num_segments; i_step++) - _Path.push_back(ImBezierQuadraticCalc(p1, p2, p3, t_step * i_step)); - } -} - -static inline ImDrawFlags FixRectCornerFlags(ImDrawFlags flags) -{ - /* - IM_STATIC_ASSERT(ImDrawFlags_RoundCornersTopLeft == (1 << 4)); -#ifndef IMGUI_DISABLE_OBSOLETE_FUNCTIONS - // Obsoleted in 1.82 (from February 2021). This code was stripped/simplified and mostly commented in 1.90 (from September 2023) - // - Legacy Support for hard coded ~0 (used to be a suggested equivalent to ImDrawCornerFlags_All) - if (flags == ~0) { return ImDrawFlags_RoundCornersAll; } - // - Legacy Support for hard coded 0x01 to 0x0F (matching 15 out of 16 old flags combinations). Read details in older version of this code. - if (flags >= 0x01 && flags <= 0x0F) { return (flags << 4); } - // We cannot support hard coded 0x00 with 'float rounding > 0.0f' --> replace with ImDrawFlags_RoundCornersNone or use 'float rounding = 0.0f' -#endif - */ - // If this assert triggers, please update your code replacing hardcoded values with new ImDrawFlags_RoundCorners* values. - // Note that ImDrawFlags_Closed (== 0x01) is an invalid flag for AddRect(), AddRectFilled(), PathRect() etc. anyway. - // See details in 1.82 Changelog as well as 2021/03/12 and 2023/09/08 entries in "API BREAKING CHANGES" section. - IM_ASSERT((flags & 0x0F) == 0 && "Misuse of legacy hardcoded ImDrawCornerFlags values!"); - - if ((flags & ImDrawFlags_RoundCornersMask_) == 0) - flags |= ImDrawFlags_RoundCornersAll; - - return flags; -} - -void ImDrawList::PathRect(const ImVec2& a, const ImVec2& b, float rounding, ImDrawFlags flags) -{ - if (rounding >= 0.5f) - { - flags = FixRectCornerFlags(flags); - rounding = ImMin(rounding, ImFabs(b.x - a.x) * (((flags & ImDrawFlags_RoundCornersTop) == ImDrawFlags_RoundCornersTop) || ((flags & ImDrawFlags_RoundCornersBottom) == ImDrawFlags_RoundCornersBottom) ? 0.5f : 1.0f) - 1.0f); - rounding = ImMin(rounding, ImFabs(b.y - a.y) * (((flags & ImDrawFlags_RoundCornersLeft) == ImDrawFlags_RoundCornersLeft) || ((flags & ImDrawFlags_RoundCornersRight) == ImDrawFlags_RoundCornersRight) ? 0.5f : 1.0f) - 1.0f); - } - if (rounding < 0.5f || (flags & ImDrawFlags_RoundCornersMask_) == ImDrawFlags_RoundCornersNone) - { - PathLineTo(a); - PathLineTo(ImVec2(b.x, a.y)); - PathLineTo(b); - PathLineTo(ImVec2(a.x, b.y)); - } - else - { - const float rounding_tl = (flags & ImDrawFlags_RoundCornersTopLeft) ? rounding : 0.0f; - const float rounding_tr = (flags & ImDrawFlags_RoundCornersTopRight) ? rounding : 0.0f; - const float rounding_br = (flags & ImDrawFlags_RoundCornersBottomRight) ? rounding : 0.0f; - const float rounding_bl = (flags & ImDrawFlags_RoundCornersBottomLeft) ? rounding : 0.0f; - PathArcToFast(ImVec2(a.x + rounding_tl, a.y + rounding_tl), rounding_tl, 6, 9); - PathArcToFast(ImVec2(b.x - rounding_tr, a.y + rounding_tr), rounding_tr, 9, 12); - PathArcToFast(ImVec2(b.x - rounding_br, b.y - rounding_br), rounding_br, 0, 3); - PathArcToFast(ImVec2(a.x + rounding_bl, b.y - rounding_bl), rounding_bl, 3, 6); - } -} - -void ImDrawList::AddLine(const ImVec2& p1, const ImVec2& p2, ImU32 col, float thickness) -{ - if ((col & IM_COL32_A_MASK) == 0) - return; - PathLineTo(p1 + ImVec2(0.5f, 0.5f)); - PathLineTo(p2 + ImVec2(0.5f, 0.5f)); - PathStroke(col, 0, thickness); -} - -// p_min = upper-left, p_max = lower-right -// Note we don't render 1 pixels sized rectangles properly. -void ImDrawList::AddRect(const ImVec2& p_min, const ImVec2& p_max, ImU32 col, float rounding, ImDrawFlags flags, float thickness) -{ - if ((col & IM_COL32_A_MASK) == 0) - return; - if (Flags & ImDrawListFlags_AntiAliasedLines) - PathRect(p_min + ImVec2(0.50f, 0.50f), p_max - ImVec2(0.50f, 0.50f), rounding, flags); - else - PathRect(p_min + ImVec2(0.50f, 0.50f), p_max - ImVec2(0.49f, 0.49f), rounding, flags); // Better looking lower-right corner and rounded non-AA shapes. - PathStroke(col, ImDrawFlags_Closed, thickness); -} - -void ImDrawList::AddRectFilled(const ImVec2& p_min, const ImVec2& p_max, ImU32 col, float rounding, ImDrawFlags flags) -{ - if ((col & IM_COL32_A_MASK) == 0) - return; - if (rounding < 0.5f || (flags & ImDrawFlags_RoundCornersMask_) == ImDrawFlags_RoundCornersNone) - { - PrimReserve(6, 4); - PrimRect(p_min, p_max, col); - } - else - { - PathRect(p_min, p_max, rounding, flags); - PathFillConvex(col); - } -} - -// p_min = upper-left, p_max = lower-right -void ImDrawList::AddRectFilledMultiColor(const ImVec2& p_min, const ImVec2& p_max, ImU32 col_upr_left, ImU32 col_upr_right, ImU32 col_bot_right, ImU32 col_bot_left) -{ - if (((col_upr_left | col_upr_right | col_bot_right | col_bot_left) & IM_COL32_A_MASK) == 0) - return; - - const ImVec2 uv = _Data->TexUvWhitePixel; - PrimReserve(6, 4); - PrimWriteIdx((ImDrawIdx)(_VtxCurrentIdx)); PrimWriteIdx((ImDrawIdx)(_VtxCurrentIdx + 1)); PrimWriteIdx((ImDrawIdx)(_VtxCurrentIdx + 2)); - PrimWriteIdx((ImDrawIdx)(_VtxCurrentIdx)); PrimWriteIdx((ImDrawIdx)(_VtxCurrentIdx + 2)); PrimWriteIdx((ImDrawIdx)(_VtxCurrentIdx + 3)); - PrimWriteVtx(p_min, uv, col_upr_left); - PrimWriteVtx(ImVec2(p_max.x, p_min.y), uv, col_upr_right); - PrimWriteVtx(p_max, uv, col_bot_right); - PrimWriteVtx(ImVec2(p_min.x, p_max.y), uv, col_bot_left); -} - -void ImDrawList::AddQuad(const ImVec2& p1, const ImVec2& p2, const ImVec2& p3, const ImVec2& p4, ImU32 col, float thickness) -{ - if ((col & IM_COL32_A_MASK) == 0) - return; - - PathLineTo(p1); - PathLineTo(p2); - PathLineTo(p3); - PathLineTo(p4); - PathStroke(col, ImDrawFlags_Closed, thickness); -} - -void ImDrawList::AddQuadFilled(const ImVec2& p1, const ImVec2& p2, const ImVec2& p3, const ImVec2& p4, ImU32 col) -{ - if ((col & IM_COL32_A_MASK) == 0) - return; - - PathLineTo(p1); - PathLineTo(p2); - PathLineTo(p3); - PathLineTo(p4); - PathFillConvex(col); -} - -void ImDrawList::AddTriangle(const ImVec2& p1, const ImVec2& p2, const ImVec2& p3, ImU32 col, float thickness) -{ - if ((col & IM_COL32_A_MASK) == 0) - return; - - PathLineTo(p1); - PathLineTo(p2); - PathLineTo(p3); - PathStroke(col, ImDrawFlags_Closed, thickness); -} - -void ImDrawList::AddTriangleFilled(const ImVec2& p1, const ImVec2& p2, const ImVec2& p3, ImU32 col) -{ - if ((col & IM_COL32_A_MASK) == 0) - return; - - PathLineTo(p1); - PathLineTo(p2); - PathLineTo(p3); - PathFillConvex(col); -} - -void ImDrawList::AddCircle(const ImVec2& center, float radius, ImU32 col, int num_segments, float thickness) -{ - if ((col & IM_COL32_A_MASK) == 0 || radius < 0.5f) - return; - - if (num_segments <= 0) - { - // Use arc with automatic segment count - _PathArcToFastEx(center, radius - 0.5f, 0, IM_DRAWLIST_ARCFAST_SAMPLE_MAX, 0); - _Path.Size--; - } - else - { - // Explicit segment count (still clamp to avoid drawing insanely tessellated shapes) - num_segments = ImClamp(num_segments, 3, IM_DRAWLIST_CIRCLE_AUTO_SEGMENT_MAX); - - // Because we are filling a closed shape we remove 1 from the count of segments/points - const float a_max = (IM_PI * 2.0f) * ((float)num_segments - 1.0f) / (float)num_segments; - PathArcTo(center, radius - 0.5f, 0.0f, a_max, num_segments - 1); - } - - PathStroke(col, ImDrawFlags_Closed, thickness); -} - -void ImDrawList::AddCircleFilled(const ImVec2& center, float radius, ImU32 col, int num_segments) -{ - if ((col & IM_COL32_A_MASK) == 0 || radius < 0.5f) - return; - - if (num_segments <= 0) - { - // Use arc with automatic segment count - _PathArcToFastEx(center, radius, 0, IM_DRAWLIST_ARCFAST_SAMPLE_MAX, 0); - _Path.Size--; - } - else - { - // Explicit segment count (still clamp to avoid drawing insanely tessellated shapes) - num_segments = ImClamp(num_segments, 3, IM_DRAWLIST_CIRCLE_AUTO_SEGMENT_MAX); - - // Because we are filling a closed shape we remove 1 from the count of segments/points - const float a_max = (IM_PI * 2.0f) * ((float)num_segments - 1.0f) / (float)num_segments; - PathArcTo(center, radius, 0.0f, a_max, num_segments - 1); - } - - PathFillConvex(col); -} - -// Guaranteed to honor 'num_segments' -void ImDrawList::AddNgon(const ImVec2& center, float radius, ImU32 col, int num_segments, float thickness) -{ - if ((col & IM_COL32_A_MASK) == 0 || num_segments <= 2) - return; - - // Because we are filling a closed shape we remove 1 from the count of segments/points - const float a_max = (IM_PI * 2.0f) * ((float)num_segments - 1.0f) / (float)num_segments; - PathArcTo(center, radius - 0.5f, 0.0f, a_max, num_segments - 1); - PathStroke(col, ImDrawFlags_Closed, thickness); -} - -// Guaranteed to honor 'num_segments' -void ImDrawList::AddNgonFilled(const ImVec2& center, float radius, ImU32 col, int num_segments) -{ - if ((col & IM_COL32_A_MASK) == 0 || num_segments <= 2) - return; - - // Because we are filling a closed shape we remove 1 from the count of segments/points - const float a_max = (IM_PI * 2.0f) * ((float)num_segments - 1.0f) / (float)num_segments; - PathArcTo(center, radius, 0.0f, a_max, num_segments - 1); - PathFillConvex(col); -} - -// Ellipse -void ImDrawList::AddEllipse(const ImVec2& center, float radius_x, float radius_y, ImU32 col, float rot, int num_segments, float thickness) -{ - if ((col & IM_COL32_A_MASK) == 0) - return; - - if (num_segments <= 0) - num_segments = _CalcCircleAutoSegmentCount(ImMax(radius_x, radius_y)); // A bit pessimistic, maybe there's a better computation to do here. - - // Because we are filling a closed shape we remove 1 from the count of segments/points - const float a_max = IM_PI * 2.0f * ((float)num_segments - 1.0f) / (float)num_segments; - PathEllipticalArcTo(center, radius_x, radius_y, rot, 0.0f, a_max, num_segments - 1); - PathStroke(col, true, thickness); -} - -void ImDrawList::AddEllipseFilled(const ImVec2& center, float radius_x, float radius_y, ImU32 col, float rot, int num_segments) -{ - if ((col & IM_COL32_A_MASK) == 0) - return; - - if (num_segments <= 0) - num_segments = _CalcCircleAutoSegmentCount(ImMax(radius_x, radius_y)); // A bit pessimistic, maybe there's a better computation to do here. - - // Because we are filling a closed shape we remove 1 from the count of segments/points - const float a_max = IM_PI * 2.0f * ((float)num_segments - 1.0f) / (float)num_segments; - PathEllipticalArcTo(center, radius_x, radius_y, rot, 0.0f, a_max, num_segments - 1); - PathFillConvex(col); -} - -// Cubic Bezier takes 4 controls points -void ImDrawList::AddBezierCubic(const ImVec2& p1, const ImVec2& p2, const ImVec2& p3, const ImVec2& p4, ImU32 col, float thickness, int num_segments) -{ - if ((col & IM_COL32_A_MASK) == 0) - return; - - PathLineTo(p1); - PathBezierCubicCurveTo(p2, p3, p4, num_segments); - PathStroke(col, 0, thickness); -} - -// Quadratic Bezier takes 3 controls points -void ImDrawList::AddBezierQuadratic(const ImVec2& p1, const ImVec2& p2, const ImVec2& p3, ImU32 col, float thickness, int num_segments) -{ - if ((col & IM_COL32_A_MASK) == 0) - return; - - PathLineTo(p1); - PathBezierQuadraticCurveTo(p2, p3, num_segments); - PathStroke(col, 0, thickness); -} - -void ImDrawList::AddText(const ImFont* font, float font_size, const ImVec2& pos, ImU32 col, const char* text_begin, const char* text_end, float wrap_width, const ImVec4* cpu_fine_clip_rect) -{ - if ((col & IM_COL32_A_MASK) == 0) - return; - - if (text_end == NULL) - text_end = text_begin + strlen(text_begin); - if (text_begin == text_end) - return; - - // Pull default font/size from the shared ImDrawListSharedData instance - if (font == NULL) - font = _Data->Font; - if (font_size == 0.0f) - font_size = _Data->FontSize; - - IM_ASSERT(font->ContainerAtlas->TexID == _CmdHeader.TextureId); // Use high-level ImGui::PushFont() or low-level ImDrawList::PushTextureId() to change font. - - ImVec4 clip_rect = _CmdHeader.ClipRect; - if (cpu_fine_clip_rect) - { - clip_rect.x = ImMax(clip_rect.x, cpu_fine_clip_rect->x); - clip_rect.y = ImMax(clip_rect.y, cpu_fine_clip_rect->y); - clip_rect.z = ImMin(clip_rect.z, cpu_fine_clip_rect->z); - clip_rect.w = ImMin(clip_rect.w, cpu_fine_clip_rect->w); - } - font->RenderText(this, font_size, pos, col, clip_rect, text_begin, text_end, wrap_width, cpu_fine_clip_rect != NULL); -} - -void ImDrawList::AddText(const ImVec2& pos, ImU32 col, const char* text_begin, const char* text_end) -{ - AddText(NULL, 0.0f, pos, col, text_begin, text_end); -} - -void ImDrawList::AddImage(ImTextureID user_texture_id, const ImVec2& p_min, const ImVec2& p_max, const ImVec2& uv_min, const ImVec2& uv_max, ImU32 col) -{ - if ((col & IM_COL32_A_MASK) == 0) - return; - - const bool push_texture_id = user_texture_id != _CmdHeader.TextureId; - if (push_texture_id) - PushTextureID(user_texture_id); - - PrimReserve(6, 4); - PrimRectUV(p_min, p_max, uv_min, uv_max, col); - - if (push_texture_id) - PopTextureID(); -} - -void ImDrawList::AddImageQuad(ImTextureID user_texture_id, const ImVec2& p1, const ImVec2& p2, const ImVec2& p3, const ImVec2& p4, const ImVec2& uv1, const ImVec2& uv2, const ImVec2& uv3, const ImVec2& uv4, ImU32 col) -{ - if ((col & IM_COL32_A_MASK) == 0) - return; - - const bool push_texture_id = user_texture_id != _CmdHeader.TextureId; - if (push_texture_id) - PushTextureID(user_texture_id); - - PrimReserve(6, 4); - PrimQuadUV(p1, p2, p3, p4, uv1, uv2, uv3, uv4, col); - - if (push_texture_id) - PopTextureID(); -} - -void ImDrawList::AddImageRounded(ImTextureID user_texture_id, const ImVec2& p_min, const ImVec2& p_max, const ImVec2& uv_min, const ImVec2& uv_max, ImU32 col, float rounding, ImDrawFlags flags) -{ - if ((col & IM_COL32_A_MASK) == 0) - return; - - flags = FixRectCornerFlags(flags); - if (rounding < 0.5f || (flags & ImDrawFlags_RoundCornersMask_) == ImDrawFlags_RoundCornersNone) - { - AddImage(user_texture_id, p_min, p_max, uv_min, uv_max, col); - return; - } - - const bool push_texture_id = user_texture_id != _CmdHeader.TextureId; - if (push_texture_id) - PushTextureID(user_texture_id); - - int vert_start_idx = VtxBuffer.Size; - PathRect(p_min, p_max, rounding, flags); - PathFillConvex(col); - int vert_end_idx = VtxBuffer.Size; - ImGui::ShadeVertsLinearUV(this, vert_start_idx, vert_end_idx, p_min, p_max, uv_min, uv_max, true); - - if (push_texture_id) - PopTextureID(); -} - - -//----------------------------------------------------------------------------- -// [SECTION] ImDrawListSplitter -//----------------------------------------------------------------------------- -// FIXME: This may be a little confusing, trying to be a little too low-level/optimal instead of just doing vector swap.. -//----------------------------------------------------------------------------- - -void ImDrawListSplitter::ClearFreeMemory() -{ - for (int i = 0; i < _Channels.Size; i++) - { - if (i == _Current) - memset(&_Channels[i], 0, sizeof(_Channels[i])); // Current channel is a copy of CmdBuffer/IdxBuffer, don't destruct again - _Channels[i]._CmdBuffer.clear(); - _Channels[i]._IdxBuffer.clear(); - } - _Current = 0; - _Count = 1; - _Channels.clear(); -} - -void ImDrawListSplitter::Split(ImDrawList* draw_list, int channels_count) -{ - IM_UNUSED(draw_list); - IM_ASSERT(_Current == 0 && _Count <= 1 && "Nested channel splitting is not supported. Please use separate instances of ImDrawListSplitter."); - int old_channels_count = _Channels.Size; - if (old_channels_count < channels_count) - { - _Channels.reserve(channels_count); // Avoid over reserving since this is likely to stay stable - _Channels.resize(channels_count); - } - _Count = channels_count; - - // Channels[] (24/32 bytes each) hold storage that we'll swap with draw_list->_CmdBuffer/_IdxBuffer - // The content of Channels[0] at this point doesn't matter. We clear it to make state tidy in a debugger but we don't strictly need to. - // When we switch to the next channel, we'll copy draw_list->_CmdBuffer/_IdxBuffer into Channels[0] and then Channels[1] into draw_list->CmdBuffer/_IdxBuffer - memset(&_Channels[0], 0, sizeof(ImDrawChannel)); - for (int i = 1; i < channels_count; i++) - { - if (i >= old_channels_count) - { - IM_PLACEMENT_NEW(&_Channels[i]) ImDrawChannel(); - } - else - { - _Channels[i]._CmdBuffer.resize(0); - _Channels[i]._IdxBuffer.resize(0); - } - } -} - -void ImDrawListSplitter::Merge(ImDrawList* draw_list) -{ - // Note that we never use or rely on _Channels.Size because it is merely a buffer that we never shrink back to 0 to keep all sub-buffers ready for use. - if (_Count <= 1) - return; - - SetCurrentChannel(draw_list, 0); - draw_list->_PopUnusedDrawCmd(); - - // Calculate our final buffer sizes. Also fix the incorrect IdxOffset values in each command. - int new_cmd_buffer_count = 0; - int new_idx_buffer_count = 0; - ImDrawCmd* last_cmd = (_Count > 0 && draw_list->CmdBuffer.Size > 0) ? &draw_list->CmdBuffer.back() : NULL; - int idx_offset = last_cmd ? last_cmd->IdxOffset + last_cmd->ElemCount : 0; - for (int i = 1; i < _Count; i++) - { - ImDrawChannel& ch = _Channels[i]; - if (ch._CmdBuffer.Size > 0 && ch._CmdBuffer.back().ElemCount == 0 && ch._CmdBuffer.back().UserCallback == NULL) // Equivalent of PopUnusedDrawCmd() - ch._CmdBuffer.pop_back(); - - if (ch._CmdBuffer.Size > 0 && last_cmd != NULL) - { - // Do not include ImDrawCmd_AreSequentialIdxOffset() in the compare as we rebuild IdxOffset values ourselves. - // Manipulating IdxOffset (e.g. by reordering draw commands like done by RenderDimmedBackgroundBehindWindow()) is not supported within a splitter. - ImDrawCmd* next_cmd = &ch._CmdBuffer[0]; - if (ImDrawCmd_HeaderCompare(last_cmd, next_cmd) == 0 && last_cmd->UserCallback == NULL && next_cmd->UserCallback == NULL) - { - // Merge previous channel last draw command with current channel first draw command if matching. - last_cmd->ElemCount += next_cmd->ElemCount; - idx_offset += next_cmd->ElemCount; - ch._CmdBuffer.erase(ch._CmdBuffer.Data); // FIXME-OPT: Improve for multiple merges. - } - } - if (ch._CmdBuffer.Size > 0) - last_cmd = &ch._CmdBuffer.back(); - new_cmd_buffer_count += ch._CmdBuffer.Size; - new_idx_buffer_count += ch._IdxBuffer.Size; - for (int cmd_n = 0; cmd_n < ch._CmdBuffer.Size; cmd_n++) - { - ch._CmdBuffer.Data[cmd_n].IdxOffset = idx_offset; - idx_offset += ch._CmdBuffer.Data[cmd_n].ElemCount; - } - } - draw_list->CmdBuffer.resize(draw_list->CmdBuffer.Size + new_cmd_buffer_count); - draw_list->IdxBuffer.resize(draw_list->IdxBuffer.Size + new_idx_buffer_count); - - // Write commands and indices in order (they are fairly small structures, we don't copy vertices only indices) - ImDrawCmd* cmd_write = draw_list->CmdBuffer.Data + draw_list->CmdBuffer.Size - new_cmd_buffer_count; - ImDrawIdx* idx_write = draw_list->IdxBuffer.Data + draw_list->IdxBuffer.Size - new_idx_buffer_count; - for (int i = 1; i < _Count; i++) - { - ImDrawChannel& ch = _Channels[i]; - if (int sz = ch._CmdBuffer.Size) { memcpy(cmd_write, ch._CmdBuffer.Data, sz * sizeof(ImDrawCmd)); cmd_write += sz; } - if (int sz = ch._IdxBuffer.Size) { memcpy(idx_write, ch._IdxBuffer.Data, sz * sizeof(ImDrawIdx)); idx_write += sz; } - } - draw_list->_IdxWritePtr = idx_write; - - // Ensure there's always a non-callback draw command trailing the command-buffer - if (draw_list->CmdBuffer.Size == 0 || draw_list->CmdBuffer.back().UserCallback != NULL) - draw_list->AddDrawCmd(); - - // If current command is used with different settings we need to add a new command - ImDrawCmd* curr_cmd = &draw_list->CmdBuffer.Data[draw_list->CmdBuffer.Size - 1]; - if (curr_cmd->ElemCount == 0) - ImDrawCmd_HeaderCopy(curr_cmd, &draw_list->_CmdHeader); // Copy ClipRect, TextureId, VtxOffset - else if (ImDrawCmd_HeaderCompare(curr_cmd, &draw_list->_CmdHeader) != 0) - draw_list->AddDrawCmd(); - - _Count = 1; -} - -void ImDrawListSplitter::SetCurrentChannel(ImDrawList* draw_list, int idx) -{ - IM_ASSERT(idx >= 0 && idx < _Count); - if (_Current == idx) - return; - - // Overwrite ImVector (12/16 bytes), four times. This is merely a silly optimization instead of doing .swap() - memcpy(&_Channels.Data[_Current]._CmdBuffer, &draw_list->CmdBuffer, sizeof(draw_list->CmdBuffer)); - memcpy(&_Channels.Data[_Current]._IdxBuffer, &draw_list->IdxBuffer, sizeof(draw_list->IdxBuffer)); - _Current = idx; - memcpy(&draw_list->CmdBuffer, &_Channels.Data[idx]._CmdBuffer, sizeof(draw_list->CmdBuffer)); - memcpy(&draw_list->IdxBuffer, &_Channels.Data[idx]._IdxBuffer, sizeof(draw_list->IdxBuffer)); - draw_list->_IdxWritePtr = draw_list->IdxBuffer.Data + draw_list->IdxBuffer.Size; - - // If current command is used with different settings we need to add a new command - ImDrawCmd* curr_cmd = (draw_list->CmdBuffer.Size == 0) ? NULL : &draw_list->CmdBuffer.Data[draw_list->CmdBuffer.Size - 1]; - if (curr_cmd == NULL) - draw_list->AddDrawCmd(); - else if (curr_cmd->ElemCount == 0) - ImDrawCmd_HeaderCopy(curr_cmd, &draw_list->_CmdHeader); // Copy ClipRect, TextureId, VtxOffset - else if (ImDrawCmd_HeaderCompare(curr_cmd, &draw_list->_CmdHeader) != 0) - draw_list->AddDrawCmd(); -} - -//----------------------------------------------------------------------------- -// [SECTION] ImDrawData -//----------------------------------------------------------------------------- - -void ImDrawData::Clear() -{ - Valid = false; - CmdListsCount = TotalIdxCount = TotalVtxCount = 0; - CmdLists.resize(0); // The ImDrawList are NOT owned by ImDrawData but e.g. by ImGuiContext, so we don't clear them. - DisplayPos = DisplaySize = FramebufferScale = ImVec2(0.0f, 0.0f); - OwnerViewport = NULL; -} - -// Important: 'out_list' is generally going to be draw_data->CmdLists, but may be another temporary list -// as long at it is expected that the result will be later merged into draw_data->CmdLists[]. -void ImGui::AddDrawListToDrawDataEx(ImDrawData* draw_data, ImVector* out_list, ImDrawList* draw_list) -{ - if (draw_list->CmdBuffer.Size == 0) - return; - if (draw_list->CmdBuffer.Size == 1 && draw_list->CmdBuffer[0].ElemCount == 0 && draw_list->CmdBuffer[0].UserCallback == NULL) - return; - - // Draw list sanity check. Detect mismatch between PrimReserve() calls and incrementing _VtxCurrentIdx, _VtxWritePtr etc. - // May trigger for you if you are using PrimXXX functions incorrectly. - IM_ASSERT(draw_list->VtxBuffer.Size == 0 || draw_list->_VtxWritePtr == draw_list->VtxBuffer.Data + draw_list->VtxBuffer.Size); - IM_ASSERT(draw_list->IdxBuffer.Size == 0 || draw_list->_IdxWritePtr == draw_list->IdxBuffer.Data + draw_list->IdxBuffer.Size); - if (!(draw_list->Flags & ImDrawListFlags_AllowVtxOffset)) - IM_ASSERT((int)draw_list->_VtxCurrentIdx == draw_list->VtxBuffer.Size); - - // Check that draw_list doesn't use more vertices than indexable (default ImDrawIdx = unsigned short = 2 bytes = 64K vertices per ImDrawList = per window) - // If this assert triggers because you are drawing lots of stuff manually: - // - First, make sure you are coarse clipping yourself and not trying to draw many things outside visible bounds. - // Be mindful that the lower-level ImDrawList API doesn't filter vertices. Use the Metrics/Debugger window to inspect draw list contents. - // - If you want large meshes with more than 64K vertices, you can either: - // (A) Handle the ImDrawCmd::VtxOffset value in your renderer backend, and set 'io.BackendFlags |= ImGuiBackendFlags_RendererHasVtxOffset'. - // Most example backends already support this from 1.71. Pre-1.71 backends won't. - // Some graphics API such as GL ES 1/2 don't have a way to offset the starting vertex so it is not supported for them. - // (B) Or handle 32-bit indices in your renderer backend, and uncomment '#define ImDrawIdx unsigned int' line in imconfig.h. - // Most example backends already support this. For example, the OpenGL example code detect index size at compile-time: - // glDrawElements(GL_TRIANGLES, (GLsizei)pcmd->ElemCount, sizeof(ImDrawIdx) == 2 ? GL_UNSIGNED_SHORT : GL_UNSIGNED_INT, idx_buffer_offset); - // Your own engine or render API may use different parameters or function calls to specify index sizes. - // 2 and 4 bytes indices are generally supported by most graphics API. - // - If for some reason neither of those solutions works for you, a workaround is to call BeginChild()/EndChild() before reaching - // the 64K limit to split your draw commands in multiple draw lists. - if (sizeof(ImDrawIdx) == 2) - IM_ASSERT(draw_list->_VtxCurrentIdx < (1 << 16) && "Too many vertices in ImDrawList using 16-bit indices. Read comment above"); - - // Add to output list + records state in ImDrawData - out_list->push_back(draw_list); - draw_data->CmdListsCount++; - draw_data->TotalVtxCount += draw_list->VtxBuffer.Size; - draw_data->TotalIdxCount += draw_list->IdxBuffer.Size; -} - -void ImDrawData::AddDrawList(ImDrawList* draw_list) -{ - IM_ASSERT(CmdLists.Size == CmdListsCount); - draw_list->_PopUnusedDrawCmd(); - ImGui::AddDrawListToDrawDataEx(this, &CmdLists, draw_list); -} - -// For backward compatibility: convert all buffers from indexed to de-indexed, in case you cannot render indexed. Note: this is slow and most likely a waste of resources. Always prefer indexed rendering! -void ImDrawData::DeIndexAllBuffers() -{ - ImVector new_vtx_buffer; - TotalVtxCount = TotalIdxCount = 0; - for (int i = 0; i < CmdListsCount; i++) - { - ImDrawList* cmd_list = CmdLists[i]; - if (cmd_list->IdxBuffer.empty()) - continue; - new_vtx_buffer.resize(cmd_list->IdxBuffer.Size); - for (int j = 0; j < cmd_list->IdxBuffer.Size; j++) - new_vtx_buffer[j] = cmd_list->VtxBuffer[cmd_list->IdxBuffer[j]]; - cmd_list->VtxBuffer.swap(new_vtx_buffer); - cmd_list->IdxBuffer.resize(0); - TotalVtxCount += cmd_list->VtxBuffer.Size; - } -} - -// Helper to scale the ClipRect field of each ImDrawCmd. -// Use if your final output buffer is at a different scale than draw_data->DisplaySize, -// or if there is a difference between your window resolution and framebuffer resolution. -void ImDrawData::ScaleClipRects(const ImVec2& fb_scale) -{ - for (ImDrawList* draw_list : CmdLists) - for (ImDrawCmd& cmd : draw_list->CmdBuffer) - cmd.ClipRect = ImVec4(cmd.ClipRect.x * fb_scale.x, cmd.ClipRect.y * fb_scale.y, cmd.ClipRect.z * fb_scale.x, cmd.ClipRect.w * fb_scale.y); -} - -//----------------------------------------------------------------------------- -// [SECTION] Helpers ShadeVertsXXX functions -//----------------------------------------------------------------------------- - -// Generic linear color gradient, write to RGB fields, leave A untouched. -void ImGui::ShadeVertsLinearColorGradientKeepAlpha(ImDrawList* draw_list, int vert_start_idx, int vert_end_idx, ImVec2 gradient_p0, ImVec2 gradient_p1, ImU32 col0, ImU32 col1) -{ - ImVec2 gradient_extent = gradient_p1 - gradient_p0; - float gradient_inv_length2 = 1.0f / ImLengthSqr(gradient_extent); - ImDrawVert* vert_start = draw_list->VtxBuffer.Data + vert_start_idx; - ImDrawVert* vert_end = draw_list->VtxBuffer.Data + vert_end_idx; - const int col0_r = (int)(col0 >> IM_COL32_R_SHIFT) & 0xFF; - const int col0_g = (int)(col0 >> IM_COL32_G_SHIFT) & 0xFF; - const int col0_b = (int)(col0 >> IM_COL32_B_SHIFT) & 0xFF; - const int col_delta_r = ((int)(col1 >> IM_COL32_R_SHIFT) & 0xFF) - col0_r; - const int col_delta_g = ((int)(col1 >> IM_COL32_G_SHIFT) & 0xFF) - col0_g; - const int col_delta_b = ((int)(col1 >> IM_COL32_B_SHIFT) & 0xFF) - col0_b; - for (ImDrawVert* vert = vert_start; vert < vert_end; vert++) - { - float d = ImDot(vert->pos - gradient_p0, gradient_extent); - float t = ImClamp(d * gradient_inv_length2, 0.0f, 1.0f); - int r = (int)(col0_r + col_delta_r * t); - int g = (int)(col0_g + col_delta_g * t); - int b = (int)(col0_b + col_delta_b * t); - vert->col = (r << IM_COL32_R_SHIFT) | (g << IM_COL32_G_SHIFT) | (b << IM_COL32_B_SHIFT) | (vert->col & IM_COL32_A_MASK); - } -} - -// Distribute UV over (a, b) rectangle -void ImGui::ShadeVertsLinearUV(ImDrawList* draw_list, int vert_start_idx, int vert_end_idx, const ImVec2& a, const ImVec2& b, const ImVec2& uv_a, const ImVec2& uv_b, bool clamp) -{ - const ImVec2 size = b - a; - const ImVec2 uv_size = uv_b - uv_a; - const ImVec2 scale = ImVec2( - size.x != 0.0f ? (uv_size.x / size.x) : 0.0f, - size.y != 0.0f ? (uv_size.y / size.y) : 0.0f); - - ImDrawVert* vert_start = draw_list->VtxBuffer.Data + vert_start_idx; - ImDrawVert* vert_end = draw_list->VtxBuffer.Data + vert_end_idx; - if (clamp) - { - const ImVec2 min = ImMin(uv_a, uv_b); - const ImVec2 max = ImMax(uv_a, uv_b); - for (ImDrawVert* vertex = vert_start; vertex < vert_end; ++vertex) - vertex->uv = ImClamp(uv_a + ImMul(ImVec2(vertex->pos.x, vertex->pos.y) - a, scale), min, max); - } - else - { - for (ImDrawVert* vertex = vert_start; vertex < vert_end; ++vertex) - vertex->uv = uv_a + ImMul(ImVec2(vertex->pos.x, vertex->pos.y) - a, scale); - } -} - -void ImGui::ShadeVertsTransformPos(ImDrawList* draw_list, int vert_start_idx, int vert_end_idx, const ImVec2& pivot_in, float cos_a, float sin_a, const ImVec2& pivot_out) -{ - ImDrawVert* vert_start = draw_list->VtxBuffer.Data + vert_start_idx; - ImDrawVert* vert_end = draw_list->VtxBuffer.Data + vert_end_idx; - for (ImDrawVert* vertex = vert_start; vertex < vert_end; ++vertex) - vertex->pos = ImRotate(vertex->pos- pivot_in, cos_a, sin_a) + pivot_out; -} - -//----------------------------------------------------------------------------- -// [SECTION] ImFontConfig -//----------------------------------------------------------------------------- - -ImFontConfig::ImFontConfig() -{ - memset(this, 0, sizeof(*this)); - FontDataOwnedByAtlas = true; - OversampleH = 2; - OversampleV = 1; - GlyphMaxAdvanceX = FLT_MAX; - RasterizerMultiply = 1.0f; - EllipsisChar = (ImWchar)-1; -} - -//----------------------------------------------------------------------------- -// [SECTION] ImFontAtlas -//----------------------------------------------------------------------------- - -// A work of art lies ahead! (. = white layer, X = black layer, others are blank) -// The 2x2 white texels on the top left are the ones we'll use everywhere in Dear ImGui to render filled shapes. -// (This is used when io.MouseDrawCursor = true) -const int FONT_ATLAS_DEFAULT_TEX_DATA_W = 122; // Actual texture will be 2 times that + 1 spacing. -const int FONT_ATLAS_DEFAULT_TEX_DATA_H = 27; -static const char FONT_ATLAS_DEFAULT_TEX_DATA_PIXELS[FONT_ATLAS_DEFAULT_TEX_DATA_W * FONT_ATLAS_DEFAULT_TEX_DATA_H + 1] = -{ - "..- -XXXXXXX- X - X -XXXXXXX - XXXXXXX- XX - XX XX " - "..- -X.....X- X.X - X.X -X.....X - X.....X- X..X -X..X X..X" - "--- -XXX.XXX- X...X - X...X -X....X - X....X- X..X -X...X X...X" - "X - X.X - X.....X - X.....X -X...X - X...X- X..X - X...X X...X " - "XX - X.X -X.......X- X.......X -X..X.X - X.X..X- X..X - X...X...X " - "X.X - X.X -XXXX.XXXX- XXXX.XXXX -X.X X.X - X.X X.X- X..XXX - X.....X " - "X..X - X.X - X.X - X.X -XX X.X - X.X XX- X..X..XXX - X...X " - "X...X - X.X - X.X - XX X.X XX - X.X - X.X - X..X..X..XX - X.X " - "X....X - X.X - X.X - X.X X.X X.X - X.X - X.X - X..X..X..X.X - X...X " - "X.....X - X.X - X.X - X..X X.X X..X - X.X - X.X -XXX X..X..X..X..X- X.....X " - "X......X - X.X - X.X - X...XXXXXX.XXXXXX...X - X.X XX-XX X.X -X..XX........X..X- X...X...X " - "X.......X - X.X - X.X -X.....................X- X.X X.X-X.X X.X -X...X...........X- X...X X...X " - "X........X - X.X - X.X - X...XXXXXX.XXXXXX...X - X.X..X-X..X.X - X..............X-X...X X...X" - "X.........X -XXX.XXX- X.X - X..X X.X X..X - X...X-X...X - X.............X-X..X X..X" - "X..........X-X.....X- X.X - X.X X.X X.X - X....X-X....X - X.............X- XX XX " - "X......XXXXX-XXXXXXX- X.X - XX X.X XX - X.....X-X.....X - X............X--------------" - "X...X..X --------- X.X - X.X - XXXXXXX-XXXXXXX - X...........X - " - "X..X X..X - -XXXX.XXXX- XXXX.XXXX ------------------------------------- X..........X - " - "X.X X..X - -X.......X- X.......X - XX XX - - X..........X - " - "XX X..X - - X.....X - X.....X - X.X X.X - - X........X - " - " X..X - - X...X - X...X - X..X X..X - - X........X - " - " XX - - X.X - X.X - X...XXXXXXXXXXXXX...X - - XXXXXXXXXX - " - "------------- - X - X -X.....................X- ------------------- " - " ----------------------------------- X...XXXXXXXXXXXXX...X - " - " - X..X X..X - " - " - X.X X.X - " - " - XX XX - " -}; - -static const ImVec2 FONT_ATLAS_DEFAULT_TEX_CURSOR_DATA[ImGuiMouseCursor_COUNT][3] = -{ - // Pos ........ Size ......... Offset ...... - { ImVec2( 0,3), ImVec2(12,19), ImVec2( 0, 0) }, // ImGuiMouseCursor_Arrow - { ImVec2(13,0), ImVec2( 7,16), ImVec2( 1, 8) }, // ImGuiMouseCursor_TextInput - { ImVec2(31,0), ImVec2(23,23), ImVec2(11,11) }, // ImGuiMouseCursor_ResizeAll - { ImVec2(21,0), ImVec2( 9,23), ImVec2( 4,11) }, // ImGuiMouseCursor_ResizeNS - { ImVec2(55,18),ImVec2(23, 9), ImVec2(11, 4) }, // ImGuiMouseCursor_ResizeEW - { ImVec2(73,0), ImVec2(17,17), ImVec2( 8, 8) }, // ImGuiMouseCursor_ResizeNESW - { ImVec2(55,0), ImVec2(17,17), ImVec2( 8, 8) }, // ImGuiMouseCursor_ResizeNWSE - { ImVec2(91,0), ImVec2(17,22), ImVec2( 5, 0) }, // ImGuiMouseCursor_Hand - { ImVec2(109,0),ImVec2(13,15), ImVec2( 6, 7) }, // ImGuiMouseCursor_NotAllowed -}; - -ImFontAtlas::ImFontAtlas() -{ - memset(this, 0, sizeof(*this)); - TexGlyphPadding = 1; - PackIdMouseCursors = PackIdLines = -1; -} - -ImFontAtlas::~ImFontAtlas() -{ - IM_ASSERT(!Locked && "Cannot modify a locked ImFontAtlas between NewFrame() and EndFrame/Render()!"); - Clear(); -} - -void ImFontAtlas::ClearInputData() -{ - IM_ASSERT(!Locked && "Cannot modify a locked ImFontAtlas between NewFrame() and EndFrame/Render()!"); - for (ImFontConfig& font_cfg : ConfigData) - if (font_cfg.FontData && font_cfg.FontDataOwnedByAtlas) - { - IM_FREE(font_cfg.FontData); - font_cfg.FontData = NULL; - } - - // When clearing this we lose access to the font name and other information used to build the font. - for (ImFont* font : Fonts) - if (font->ConfigData >= ConfigData.Data && font->ConfigData < ConfigData.Data + ConfigData.Size) - { - font->ConfigData = NULL; - font->ConfigDataCount = 0; - } - ConfigData.clear(); - CustomRects.clear(); - PackIdMouseCursors = PackIdLines = -1; - // Important: we leave TexReady untouched -} - -void ImFontAtlas::ClearTexData() -{ - IM_ASSERT(!Locked && "Cannot modify a locked ImFontAtlas between NewFrame() and EndFrame/Render()!"); - if (TexPixelsAlpha8) - IM_FREE(TexPixelsAlpha8); - if (TexPixelsRGBA32) - IM_FREE(TexPixelsRGBA32); - TexPixelsAlpha8 = NULL; - TexPixelsRGBA32 = NULL; - TexPixelsUseColors = false; - // Important: we leave TexReady untouched -} - -void ImFontAtlas::ClearFonts() -{ - IM_ASSERT(!Locked && "Cannot modify a locked ImFontAtlas between NewFrame() and EndFrame/Render()!"); - Fonts.clear_delete(); - TexReady = false; -} - -void ImFontAtlas::Clear() -{ - ClearInputData(); - ClearTexData(); - ClearFonts(); -} - -void ImFontAtlas::GetTexDataAsAlpha8(unsigned char** out_pixels, int* out_width, int* out_height, int* out_bytes_per_pixel) -{ - // Build atlas on demand - if (TexPixelsAlpha8 == NULL) - Build(); - - *out_pixels = TexPixelsAlpha8; - if (out_width) *out_width = TexWidth; - if (out_height) *out_height = TexHeight; - if (out_bytes_per_pixel) *out_bytes_per_pixel = 1; -} - -void ImFontAtlas::GetTexDataAsRGBA32(unsigned char** out_pixels, int* out_width, int* out_height, int* out_bytes_per_pixel) -{ - // Convert to RGBA32 format on demand - // Although it is likely to be the most commonly used format, our font rendering is 1 channel / 8 bpp - if (!TexPixelsRGBA32) - { - unsigned char* pixels = NULL; - GetTexDataAsAlpha8(&pixels, NULL, NULL); - if (pixels) - { - TexPixelsRGBA32 = (unsigned int*)IM_ALLOC((size_t)TexWidth * (size_t)TexHeight * 4); - const unsigned char* src = pixels; - unsigned int* dst = TexPixelsRGBA32; - for (int n = TexWidth * TexHeight; n > 0; n--) - *dst++ = IM_COL32(255, 255, 255, (unsigned int)(*src++)); - } - } - - *out_pixels = (unsigned char*)TexPixelsRGBA32; - if (out_width) *out_width = TexWidth; - if (out_height) *out_height = TexHeight; - if (out_bytes_per_pixel) *out_bytes_per_pixel = 4; -} - -ImFont* ImFontAtlas::AddFont(const ImFontConfig* font_cfg) -{ - IM_ASSERT(!Locked && "Cannot modify a locked ImFontAtlas between NewFrame() and EndFrame/Render()!"); - IM_ASSERT(font_cfg->FontData != NULL && font_cfg->FontDataSize > 0); - IM_ASSERT(font_cfg->SizePixels > 0.0f); - - // Create new font - if (!font_cfg->MergeMode) - Fonts.push_back(IM_NEW(ImFont)); - else - IM_ASSERT(!Fonts.empty() && "Cannot use MergeMode for the first font"); // When using MergeMode make sure that a font has already been added before. You can use ImGui::GetIO().Fonts->AddFontDefault() to add the default imgui font. - - ConfigData.push_back(*font_cfg); - ImFontConfig& new_font_cfg = ConfigData.back(); - if (new_font_cfg.DstFont == NULL) - new_font_cfg.DstFont = Fonts.back(); - if (!new_font_cfg.FontDataOwnedByAtlas) - { - new_font_cfg.FontData = IM_ALLOC(new_font_cfg.FontDataSize); - new_font_cfg.FontDataOwnedByAtlas = true; - memcpy(new_font_cfg.FontData, font_cfg->FontData, (size_t)new_font_cfg.FontDataSize); - } - - if (new_font_cfg.DstFont->EllipsisChar == (ImWchar)-1) - new_font_cfg.DstFont->EllipsisChar = font_cfg->EllipsisChar; - - ImFontAtlasUpdateConfigDataPointers(this); - - // Invalidate texture - TexReady = false; - ClearTexData(); - return new_font_cfg.DstFont; -} - -// Default font TTF is compressed with stb_compress then base85 encoded (see misc/fonts/binary_to_compressed_c.cpp for encoder) -static unsigned int stb_decompress_length(const unsigned char* input); -static unsigned int stb_decompress(unsigned char* output, const unsigned char* input, unsigned int length); -static const char* GetDefaultCompressedFontDataTTFBase85(); -static unsigned int Decode85Byte(char c) { return c >= '\\' ? c-36 : c-35; } -static void Decode85(const unsigned char* src, unsigned char* dst) -{ - while (*src) - { - unsigned int tmp = Decode85Byte(src[0]) + 85 * (Decode85Byte(src[1]) + 85 * (Decode85Byte(src[2]) + 85 * (Decode85Byte(src[3]) + 85 * Decode85Byte(src[4])))); - dst[0] = ((tmp >> 0) & 0xFF); dst[1] = ((tmp >> 8) & 0xFF); dst[2] = ((tmp >> 16) & 0xFF); dst[3] = ((tmp >> 24) & 0xFF); // We can't assume little-endianness. - src += 5; - dst += 4; - } -} - -// Load embedded ProggyClean.ttf at size 13, disable oversampling -ImFont* ImFontAtlas::AddFontDefault(const ImFontConfig* font_cfg_template) -{ - ImFontConfig font_cfg = font_cfg_template ? *font_cfg_template : ImFontConfig(); - if (!font_cfg_template) - { - font_cfg.OversampleH = font_cfg.OversampleV = 1; - font_cfg.PixelSnapH = true; - } - if (font_cfg.SizePixels <= 0.0f) - font_cfg.SizePixels = 13.0f * 1.0f; - if (font_cfg.Name[0] == '\0') - ImFormatString(font_cfg.Name, IM_ARRAYSIZE(font_cfg.Name), "ProggyClean.ttf, %dpx", (int)font_cfg.SizePixels); - font_cfg.EllipsisChar = (ImWchar)0x0085; - font_cfg.GlyphOffset.y = 1.0f * IM_TRUNC(font_cfg.SizePixels / 13.0f); // Add +1 offset per 13 units - - const char* ttf_compressed_base85 = GetDefaultCompressedFontDataTTFBase85(); - const ImWchar* glyph_ranges = font_cfg.GlyphRanges != NULL ? font_cfg.GlyphRanges : GetGlyphRangesDefault(); - ImFont* font = AddFontFromMemoryCompressedBase85TTF(ttf_compressed_base85, font_cfg.SizePixels, &font_cfg, glyph_ranges); - return font; -} - -ImFont* ImFontAtlas::AddFontFromFileTTF(const char* filename, float size_pixels, const ImFontConfig* font_cfg_template, const ImWchar* glyph_ranges) -{ - IM_ASSERT(!Locked && "Cannot modify a locked ImFontAtlas between NewFrame() and EndFrame/Render()!"); - size_t data_size = 0; - void* data = ImFileLoadToMemory(filename, "rb", &data_size, 0); - if (!data) - { - IM_ASSERT_USER_ERROR(0, "Could not load font file!"); - return NULL; - } - ImFontConfig font_cfg = font_cfg_template ? *font_cfg_template : ImFontConfig(); - if (font_cfg.Name[0] == '\0') - { - // Store a short copy of filename into into the font name for convenience - const char* p; - for (p = filename + strlen(filename); p > filename && p[-1] != '/' && p[-1] != '\\'; p--) {} - ImFormatString(font_cfg.Name, IM_ARRAYSIZE(font_cfg.Name), "%s, %.0fpx", p, size_pixels); - } - return AddFontFromMemoryTTF(data, (int)data_size, size_pixels, &font_cfg, glyph_ranges); -} - -// NB: Transfer ownership of 'ttf_data' to ImFontAtlas, unless font_cfg_template->FontDataOwnedByAtlas == false. Owned TTF buffer will be deleted after Build(). -ImFont* ImFontAtlas::AddFontFromMemoryTTF(void* font_data, int font_data_size, float size_pixels, const ImFontConfig* font_cfg_template, const ImWchar* glyph_ranges) -{ - IM_ASSERT(!Locked && "Cannot modify a locked ImFontAtlas between NewFrame() and EndFrame/Render()!"); - ImFontConfig font_cfg = font_cfg_template ? *font_cfg_template : ImFontConfig(); - IM_ASSERT(font_cfg.FontData == NULL); - IM_ASSERT(font_data_size > 100 && "Incorrect value for font_data_size!"); // Heuristic to prevent accidentally passing a wrong value to font_data_size. - font_cfg.FontData = font_data; - font_cfg.FontDataSize = font_data_size; - font_cfg.SizePixels = size_pixels > 0.0f ? size_pixels : font_cfg.SizePixels; - if (glyph_ranges) - font_cfg.GlyphRanges = glyph_ranges; - return AddFont(&font_cfg); -} - -ImFont* ImFontAtlas::AddFontFromMemoryCompressedTTF(const void* compressed_ttf_data, int compressed_ttf_size, float size_pixels, const ImFontConfig* font_cfg_template, const ImWchar* glyph_ranges) -{ - const unsigned int buf_decompressed_size = stb_decompress_length((const unsigned char*)compressed_ttf_data); - unsigned char* buf_decompressed_data = (unsigned char*)IM_ALLOC(buf_decompressed_size); - stb_decompress(buf_decompressed_data, (const unsigned char*)compressed_ttf_data, (unsigned int)compressed_ttf_size); - - ImFontConfig font_cfg = font_cfg_template ? *font_cfg_template : ImFontConfig(); - IM_ASSERT(font_cfg.FontData == NULL); - font_cfg.FontDataOwnedByAtlas = true; - return AddFontFromMemoryTTF(buf_decompressed_data, (int)buf_decompressed_size, size_pixels, &font_cfg, glyph_ranges); -} - -ImFont* ImFontAtlas::AddFontFromMemoryCompressedBase85TTF(const char* compressed_ttf_data_base85, float size_pixels, const ImFontConfig* font_cfg, const ImWchar* glyph_ranges) -{ - int compressed_ttf_size = (((int)strlen(compressed_ttf_data_base85) + 4) / 5) * 4; - void* compressed_ttf = IM_ALLOC((size_t)compressed_ttf_size); - Decode85((const unsigned char*)compressed_ttf_data_base85, (unsigned char*)compressed_ttf); - ImFont* font = AddFontFromMemoryCompressedTTF(compressed_ttf, compressed_ttf_size, size_pixels, font_cfg, glyph_ranges); - IM_FREE(compressed_ttf); - return font; -} - -int ImFontAtlas::AddCustomRectRegular(int width, int height) -{ - IM_ASSERT(width > 0 && width <= 0xFFFF); - IM_ASSERT(height > 0 && height <= 0xFFFF); - ImFontAtlasCustomRect r; - r.Width = (unsigned short)width; - r.Height = (unsigned short)height; - CustomRects.push_back(r); - return CustomRects.Size - 1; // Return index -} - -int ImFontAtlas::AddCustomRectFontGlyph(ImFont* font, ImWchar id, int width, int height, float advance_x, const ImVec2& offset) -{ -#ifdef IMGUI_USE_WCHAR32 - IM_ASSERT(id <= IM_UNICODE_CODEPOINT_MAX); -#endif - IM_ASSERT(font != NULL); - IM_ASSERT(width > 0 && width <= 0xFFFF); - IM_ASSERT(height > 0 && height <= 0xFFFF); - ImFontAtlasCustomRect r; - r.Width = (unsigned short)width; - r.Height = (unsigned short)height; - r.GlyphID = id; - r.GlyphAdvanceX = advance_x; - r.GlyphOffset = offset; - r.Font = font; - CustomRects.push_back(r); - return CustomRects.Size - 1; // Return index -} - -void ImFontAtlas::CalcCustomRectUV(const ImFontAtlasCustomRect* rect, ImVec2* out_uv_min, ImVec2* out_uv_max) const -{ - IM_ASSERT(TexWidth > 0 && TexHeight > 0); // Font atlas needs to be built before we can calculate UV coordinates - IM_ASSERT(rect->IsPacked()); // Make sure the rectangle has been packed - *out_uv_min = ImVec2((float)rect->X * TexUvScale.x, (float)rect->Y * TexUvScale.y); - *out_uv_max = ImVec2((float)(rect->X + rect->Width) * TexUvScale.x, (float)(rect->Y + rect->Height) * TexUvScale.y); -} - -bool ImFontAtlas::GetMouseCursorTexData(ImGuiMouseCursor cursor_type, ImVec2* out_offset, ImVec2* out_size, ImVec2 out_uv_border[2], ImVec2 out_uv_fill[2]) -{ - if (cursor_type <= ImGuiMouseCursor_None || cursor_type >= ImGuiMouseCursor_COUNT) - return false; - if (Flags & ImFontAtlasFlags_NoMouseCursors) - return false; - - IM_ASSERT(PackIdMouseCursors != -1); - ImFontAtlasCustomRect* r = GetCustomRectByIndex(PackIdMouseCursors); - ImVec2 pos = FONT_ATLAS_DEFAULT_TEX_CURSOR_DATA[cursor_type][0] + ImVec2((float)r->X, (float)r->Y); - ImVec2 size = FONT_ATLAS_DEFAULT_TEX_CURSOR_DATA[cursor_type][1]; - *out_size = size; - *out_offset = FONT_ATLAS_DEFAULT_TEX_CURSOR_DATA[cursor_type][2]; - out_uv_border[0] = (pos) * TexUvScale; - out_uv_border[1] = (pos + size) * TexUvScale; - pos.x += FONT_ATLAS_DEFAULT_TEX_DATA_W + 1; - out_uv_fill[0] = (pos) * TexUvScale; - out_uv_fill[1] = (pos + size) * TexUvScale; - return true; -} - -bool ImFontAtlas::Build() -{ - IM_ASSERT(!Locked && "Cannot modify a locked ImFontAtlas between NewFrame() and EndFrame/Render()!"); - - // Default font is none are specified - if (ConfigData.Size == 0) - AddFontDefault(); - - // Select builder - // - Note that we do not reassign to atlas->FontBuilderIO, since it is likely to point to static data which - // may mess with some hot-reloading schemes. If you need to assign to this (for dynamic selection) AND are - // using a hot-reloading scheme that messes up static data, store your own instance of ImFontBuilderIO somewhere - // and point to it instead of pointing directly to return value of the GetBuilderXXX functions. - const ImFontBuilderIO* builder_io = FontBuilderIO; - if (builder_io == NULL) - { -#ifdef IMGUI_ENABLE_FREETYPE - builder_io = ImGuiFreeType::GetBuilderForFreeType(); -#elif defined(IMGUI_ENABLE_STB_TRUETYPE) - builder_io = ImFontAtlasGetBuilderForStbTruetype(); -#else - IM_ASSERT(0); // Invalid Build function -#endif - } - - // Build - return builder_io->FontBuilder_Build(this); -} - -void ImFontAtlasBuildMultiplyCalcLookupTable(unsigned char out_table[256], float in_brighten_factor) -{ - for (unsigned int i = 0; i < 256; i++) - { - unsigned int value = (unsigned int)(i * in_brighten_factor); - out_table[i] = value > 255 ? 255 : (value & 0xFF); - } -} - -void ImFontAtlasBuildMultiplyRectAlpha8(const unsigned char table[256], unsigned char* pixels, int x, int y, int w, int h, int stride) -{ - IM_ASSERT_PARANOID(w <= stride); - unsigned char* data = pixels + x + y * stride; - for (int j = h; j > 0; j--, data += stride - w) - for (int i = w; i > 0; i--, data++) - *data = table[*data]; -} - -#ifdef IMGUI_ENABLE_STB_TRUETYPE -// Temporary data for one source font (multiple source fonts can be merged into one destination ImFont) -// (C++03 doesn't allow instancing ImVector<> with function-local types so we declare the type here.) -struct ImFontBuildSrcData -{ - stbtt_fontinfo FontInfo; - stbtt_pack_range PackRange; // Hold the list of codepoints to pack (essentially points to Codepoints.Data) - stbrp_rect* Rects; // Rectangle to pack. We first fill in their size and the packer will give us their position. - stbtt_packedchar* PackedChars; // Output glyphs - const ImWchar* SrcRanges; // Ranges as requested by user (user is allowed to request too much, e.g. 0x0020..0xFFFF) - int DstIndex; // Index into atlas->Fonts[] and dst_tmp_array[] - int GlyphsHighest; // Highest requested codepoint - int GlyphsCount; // Glyph count (excluding missing glyphs and glyphs already set by an earlier source font) - ImBitVector GlyphsSet; // Glyph bit map (random access, 1-bit per codepoint. This will be a maximum of 8KB) - ImVector GlyphsList; // Glyph codepoints list (flattened version of GlyphsSet) -}; - -// Temporary data for one destination ImFont* (multiple source fonts can be merged into one destination ImFont) -struct ImFontBuildDstData -{ - int SrcCount; // Number of source fonts targeting this destination font. - int GlyphsHighest; - int GlyphsCount; - ImBitVector GlyphsSet; // This is used to resolve collision when multiple sources are merged into a same destination font. -}; - -static void UnpackBitVectorToFlatIndexList(const ImBitVector* in, ImVector* out) -{ - IM_ASSERT(sizeof(in->Storage.Data[0]) == sizeof(int)); - const ImU32* it_begin = in->Storage.begin(); - const ImU32* it_end = in->Storage.end(); - for (const ImU32* it = it_begin; it < it_end; it++) - if (ImU32 entries_32 = *it) - for (ImU32 bit_n = 0; bit_n < 32; bit_n++) - if (entries_32 & ((ImU32)1 << bit_n)) - out->push_back((int)(((it - it_begin) << 5) + bit_n)); -} - -static bool ImFontAtlasBuildWithStbTruetype(ImFontAtlas* atlas) -{ - IM_ASSERT(atlas->ConfigData.Size > 0); - - ImFontAtlasBuildInit(atlas); - - // Clear atlas - atlas->TexID = (ImTextureID)NULL; - atlas->TexWidth = atlas->TexHeight = 0; - atlas->TexUvScale = ImVec2(0.0f, 0.0f); - atlas->TexUvWhitePixel = ImVec2(0.0f, 0.0f); - atlas->ClearTexData(); - - // Temporary storage for building - ImVector src_tmp_array; - ImVector dst_tmp_array; - src_tmp_array.resize(atlas->ConfigData.Size); - dst_tmp_array.resize(atlas->Fonts.Size); - memset(src_tmp_array.Data, 0, (size_t)src_tmp_array.size_in_bytes()); - memset(dst_tmp_array.Data, 0, (size_t)dst_tmp_array.size_in_bytes()); - - // 1. Initialize font loading structure, check font data validity - for (int src_i = 0; src_i < atlas->ConfigData.Size; src_i++) - { - ImFontBuildSrcData& src_tmp = src_tmp_array[src_i]; - ImFontConfig& cfg = atlas->ConfigData[src_i]; - IM_ASSERT(cfg.DstFont && (!cfg.DstFont->IsLoaded() || cfg.DstFont->ContainerAtlas == atlas)); - - // Find index from cfg.DstFont (we allow the user to set cfg.DstFont. Also it makes casual debugging nicer than when storing indices) - src_tmp.DstIndex = -1; - for (int output_i = 0; output_i < atlas->Fonts.Size && src_tmp.DstIndex == -1; output_i++) - if (cfg.DstFont == atlas->Fonts[output_i]) - src_tmp.DstIndex = output_i; - if (src_tmp.DstIndex == -1) - { - IM_ASSERT(src_tmp.DstIndex != -1); // cfg.DstFont not pointing within atlas->Fonts[] array? - return false; - } - // Initialize helper structure for font loading and verify that the TTF/OTF data is correct - const int font_offset = stbtt_GetFontOffsetForIndex((unsigned char*)cfg.FontData, cfg.FontNo); - IM_ASSERT(font_offset >= 0 && "FontData is incorrect, or FontNo cannot be found."); - if (!stbtt_InitFont(&src_tmp.FontInfo, (unsigned char*)cfg.FontData, font_offset)) - { - IM_ASSERT(0 && "stbtt_InitFont(): failed to parse FontData. It is correct and complete? Check FontDataSize."); - return false; - } - - // Measure highest codepoints - ImFontBuildDstData& dst_tmp = dst_tmp_array[src_tmp.DstIndex]; - src_tmp.SrcRanges = cfg.GlyphRanges ? cfg.GlyphRanges : atlas->GetGlyphRangesDefault(); - for (const ImWchar* src_range = src_tmp.SrcRanges; src_range[0] && src_range[1]; src_range += 2) - { - // Check for valid range. This may also help detect *some* dangling pointers, because a common - // user error is to setup ImFontConfig::GlyphRanges with a pointer to data that isn't persistent. - IM_ASSERT(src_range[0] <= src_range[1]); - src_tmp.GlyphsHighest = ImMax(src_tmp.GlyphsHighest, (int)src_range[1]); - } - dst_tmp.SrcCount++; - dst_tmp.GlyphsHighest = ImMax(dst_tmp.GlyphsHighest, src_tmp.GlyphsHighest); - } - - // 2. For every requested codepoint, check for their presence in the font data, and handle redundancy or overlaps between source fonts to avoid unused glyphs. - int total_glyphs_count = 0; - for (int src_i = 0; src_i < src_tmp_array.Size; src_i++) - { - ImFontBuildSrcData& src_tmp = src_tmp_array[src_i]; - ImFontBuildDstData& dst_tmp = dst_tmp_array[src_tmp.DstIndex]; - src_tmp.GlyphsSet.Create(src_tmp.GlyphsHighest + 1); - if (dst_tmp.GlyphsSet.Storage.empty()) - dst_tmp.GlyphsSet.Create(dst_tmp.GlyphsHighest + 1); - - for (const ImWchar* src_range = src_tmp.SrcRanges; src_range[0] && src_range[1]; src_range += 2) - for (unsigned int codepoint = src_range[0]; codepoint <= src_range[1]; codepoint++) - { - if (dst_tmp.GlyphsSet.TestBit(codepoint)) // Don't overwrite existing glyphs. We could make this an option for MergeMode (e.g. MergeOverwrite==true) - continue; - if (!stbtt_FindGlyphIndex(&src_tmp.FontInfo, codepoint)) // It is actually in the font? - continue; - - // Add to avail set/counters - src_tmp.GlyphsCount++; - dst_tmp.GlyphsCount++; - src_tmp.GlyphsSet.SetBit(codepoint); - dst_tmp.GlyphsSet.SetBit(codepoint); - total_glyphs_count++; - } - } - - // 3. Unpack our bit map into a flat list (we now have all the Unicode points that we know are requested _and_ available _and_ not overlapping another) - for (int src_i = 0; src_i < src_tmp_array.Size; src_i++) - { - ImFontBuildSrcData& src_tmp = src_tmp_array[src_i]; - src_tmp.GlyphsList.reserve(src_tmp.GlyphsCount); - UnpackBitVectorToFlatIndexList(&src_tmp.GlyphsSet, &src_tmp.GlyphsList); - src_tmp.GlyphsSet.Clear(); - IM_ASSERT(src_tmp.GlyphsList.Size == src_tmp.GlyphsCount); - } - for (int dst_i = 0; dst_i < dst_tmp_array.Size; dst_i++) - dst_tmp_array[dst_i].GlyphsSet.Clear(); - dst_tmp_array.clear(); - - // Allocate packing character data and flag packed characters buffer as non-packed (x0=y0=x1=y1=0) - // (We technically don't need to zero-clear buf_rects, but let's do it for the sake of sanity) - ImVector buf_rects; - ImVector buf_packedchars; - buf_rects.resize(total_glyphs_count); - buf_packedchars.resize(total_glyphs_count); - memset(buf_rects.Data, 0, (size_t)buf_rects.size_in_bytes()); - memset(buf_packedchars.Data, 0, (size_t)buf_packedchars.size_in_bytes()); - - // 4. Gather glyphs sizes so we can pack them in our virtual canvas. - int total_surface = 0; - int buf_rects_out_n = 0; - int buf_packedchars_out_n = 0; - for (int src_i = 0; src_i < src_tmp_array.Size; src_i++) - { - ImFontBuildSrcData& src_tmp = src_tmp_array[src_i]; - if (src_tmp.GlyphsCount == 0) - continue; - - src_tmp.Rects = &buf_rects[buf_rects_out_n]; - src_tmp.PackedChars = &buf_packedchars[buf_packedchars_out_n]; - buf_rects_out_n += src_tmp.GlyphsCount; - buf_packedchars_out_n += src_tmp.GlyphsCount; - - // Convert our ranges in the format stb_truetype wants - ImFontConfig& cfg = atlas->ConfigData[src_i]; - src_tmp.PackRange.font_size = cfg.SizePixels; - src_tmp.PackRange.first_unicode_codepoint_in_range = 0; - src_tmp.PackRange.array_of_unicode_codepoints = src_tmp.GlyphsList.Data; - src_tmp.PackRange.num_chars = src_tmp.GlyphsList.Size; - src_tmp.PackRange.chardata_for_range = src_tmp.PackedChars; - src_tmp.PackRange.h_oversample = (unsigned char)cfg.OversampleH; - src_tmp.PackRange.v_oversample = (unsigned char)cfg.OversampleV; - - // Gather the sizes of all rectangles we will need to pack (this loop is based on stbtt_PackFontRangesGatherRects) - const float scale = (cfg.SizePixels > 0) ? stbtt_ScaleForPixelHeight(&src_tmp.FontInfo, cfg.SizePixels) : stbtt_ScaleForMappingEmToPixels(&src_tmp.FontInfo, -cfg.SizePixels); - const int padding = atlas->TexGlyphPadding; - for (int glyph_i = 0; glyph_i < src_tmp.GlyphsList.Size; glyph_i++) - { - int x0, y0, x1, y1; - const int glyph_index_in_font = stbtt_FindGlyphIndex(&src_tmp.FontInfo, src_tmp.GlyphsList[glyph_i]); - IM_ASSERT(glyph_index_in_font != 0); - stbtt_GetGlyphBitmapBoxSubpixel(&src_tmp.FontInfo, glyph_index_in_font, scale * cfg.OversampleH, scale * cfg.OversampleV, 0, 0, &x0, &y0, &x1, &y1); - src_tmp.Rects[glyph_i].w = (stbrp_coord)(x1 - x0 + padding + cfg.OversampleH - 1); - src_tmp.Rects[glyph_i].h = (stbrp_coord)(y1 - y0 + padding + cfg.OversampleV - 1); - total_surface += src_tmp.Rects[glyph_i].w * src_tmp.Rects[glyph_i].h; - } - } - - // We need a width for the skyline algorithm, any width! - // The exact width doesn't really matter much, but some API/GPU have texture size limitations and increasing width can decrease height. - // User can override TexDesiredWidth and TexGlyphPadding if they wish, otherwise we use a simple heuristic to select the width based on expected surface. - const int surface_sqrt = (int)ImSqrt((float)total_surface) + 1; - atlas->TexHeight = 0; - if (atlas->TexDesiredWidth > 0) - atlas->TexWidth = atlas->TexDesiredWidth; - else - atlas->TexWidth = (surface_sqrt >= 4096 * 0.7f) ? 4096 : (surface_sqrt >= 2048 * 0.7f) ? 2048 : (surface_sqrt >= 1024 * 0.7f) ? 1024 : 512; - - // 5. Start packing - // Pack our extra data rectangles first, so it will be on the upper-left corner of our texture (UV will have small values). - const int TEX_HEIGHT_MAX = 1024 * 32; - stbtt_pack_context spc = {}; - stbtt_PackBegin(&spc, NULL, atlas->TexWidth, TEX_HEIGHT_MAX, 0, atlas->TexGlyphPadding, NULL); - ImFontAtlasBuildPackCustomRects(atlas, spc.pack_info); - - // 6. Pack each source font. No rendering yet, we are working with rectangles in an infinitely tall texture at this point. - for (int src_i = 0; src_i < src_tmp_array.Size; src_i++) - { - ImFontBuildSrcData& src_tmp = src_tmp_array[src_i]; - if (src_tmp.GlyphsCount == 0) - continue; - - stbrp_pack_rects((stbrp_context*)spc.pack_info, src_tmp.Rects, src_tmp.GlyphsCount); - - // Extend texture height and mark missing glyphs as non-packed so we won't render them. - // FIXME: We are not handling packing failure here (would happen if we got off TEX_HEIGHT_MAX or if a single if larger than TexWidth?) - for (int glyph_i = 0; glyph_i < src_tmp.GlyphsCount; glyph_i++) - if (src_tmp.Rects[glyph_i].was_packed) - atlas->TexHeight = ImMax(atlas->TexHeight, src_tmp.Rects[glyph_i].y + src_tmp.Rects[glyph_i].h); - } - - // 7. Allocate texture - atlas->TexHeight = (atlas->Flags & ImFontAtlasFlags_NoPowerOfTwoHeight) ? (atlas->TexHeight + 1) : ImUpperPowerOfTwo(atlas->TexHeight); - atlas->TexUvScale = ImVec2(1.0f / atlas->TexWidth, 1.0f / atlas->TexHeight); - atlas->TexPixelsAlpha8 = (unsigned char*)IM_ALLOC(atlas->TexWidth * atlas->TexHeight); - memset(atlas->TexPixelsAlpha8, 0, atlas->TexWidth * atlas->TexHeight); - spc.pixels = atlas->TexPixelsAlpha8; - spc.height = atlas->TexHeight; - - // 8. Render/rasterize font characters into the texture - for (int src_i = 0; src_i < src_tmp_array.Size; src_i++) - { - ImFontConfig& cfg = atlas->ConfigData[src_i]; - ImFontBuildSrcData& src_tmp = src_tmp_array[src_i]; - if (src_tmp.GlyphsCount == 0) - continue; - - stbtt_PackFontRangesRenderIntoRects(&spc, &src_tmp.FontInfo, &src_tmp.PackRange, 1, src_tmp.Rects); - - // Apply multiply operator - if (cfg.RasterizerMultiply != 1.0f) - { - unsigned char multiply_table[256]; - ImFontAtlasBuildMultiplyCalcLookupTable(multiply_table, cfg.RasterizerMultiply); - stbrp_rect* r = &src_tmp.Rects[0]; - for (int glyph_i = 0; glyph_i < src_tmp.GlyphsCount; glyph_i++, r++) - if (r->was_packed) - ImFontAtlasBuildMultiplyRectAlpha8(multiply_table, atlas->TexPixelsAlpha8, r->x, r->y, r->w, r->h, atlas->TexWidth * 1); - } - src_tmp.Rects = NULL; - } - - // End packing - stbtt_PackEnd(&spc); - buf_rects.clear(); - - // 9. Setup ImFont and glyphs for runtime - for (int src_i = 0; src_i < src_tmp_array.Size; src_i++) - { - // When merging fonts with MergeMode=true: - // - We can have multiple input fonts writing into a same destination font. - // - dst_font->ConfigData is != from cfg which is our source configuration. - ImFontBuildSrcData& src_tmp = src_tmp_array[src_i]; - ImFontConfig& cfg = atlas->ConfigData[src_i]; - ImFont* dst_font = cfg.DstFont; - - const float font_scale = stbtt_ScaleForPixelHeight(&src_tmp.FontInfo, cfg.SizePixels); - int unscaled_ascent, unscaled_descent, unscaled_line_gap; - stbtt_GetFontVMetrics(&src_tmp.FontInfo, &unscaled_ascent, &unscaled_descent, &unscaled_line_gap); - - const float ascent = ImTrunc(unscaled_ascent * font_scale + ((unscaled_ascent > 0.0f) ? +1 : -1)); - const float descent = ImTrunc(unscaled_descent * font_scale + ((unscaled_descent > 0.0f) ? +1 : -1)); - ImFontAtlasBuildSetupFont(atlas, dst_font, &cfg, ascent, descent); - const float font_off_x = cfg.GlyphOffset.x; - const float font_off_y = cfg.GlyphOffset.y + IM_ROUND(dst_font->Ascent); - - for (int glyph_i = 0; glyph_i < src_tmp.GlyphsCount; glyph_i++) - { - // Register glyph - const int codepoint = src_tmp.GlyphsList[glyph_i]; - const stbtt_packedchar& pc = src_tmp.PackedChars[glyph_i]; - stbtt_aligned_quad q; - float unused_x = 0.0f, unused_y = 0.0f; - stbtt_GetPackedQuad(src_tmp.PackedChars, atlas->TexWidth, atlas->TexHeight, glyph_i, &unused_x, &unused_y, &q, 0); - dst_font->AddGlyph(&cfg, (ImWchar)codepoint, q.x0 + font_off_x, q.y0 + font_off_y, q.x1 + font_off_x, q.y1 + font_off_y, q.s0, q.t0, q.s1, q.t1, pc.xadvance); - } - } - - // Cleanup - src_tmp_array.clear_destruct(); - - ImFontAtlasBuildFinish(atlas); - return true; -} - -const ImFontBuilderIO* ImFontAtlasGetBuilderForStbTruetype() -{ - static ImFontBuilderIO io; - io.FontBuilder_Build = ImFontAtlasBuildWithStbTruetype; - return &io; -} - -#endif // IMGUI_ENABLE_STB_TRUETYPE - -void ImFontAtlasUpdateConfigDataPointers(ImFontAtlas* atlas) -{ - for (ImFontConfig& font_cfg : atlas->ConfigData) - { - ImFont* font = font_cfg.DstFont; - if (!font_cfg.MergeMode) - { - font->ConfigData = &font_cfg; - font->ConfigDataCount = 0; - } - font->ConfigDataCount++; - } -} - -void ImFontAtlasBuildSetupFont(ImFontAtlas* atlas, ImFont* font, ImFontConfig* font_config, float ascent, float descent) -{ - if (!font_config->MergeMode) - { - font->ClearOutputData(); - font->FontSize = font_config->SizePixels; - IM_ASSERT(font->ConfigData == font_config); - font->ContainerAtlas = atlas; - font->Ascent = ascent; - font->Descent = descent; - } -} - -void ImFontAtlasBuildPackCustomRects(ImFontAtlas* atlas, void* stbrp_context_opaque) -{ - stbrp_context* pack_context = (stbrp_context*)stbrp_context_opaque; - IM_ASSERT(pack_context != NULL); - - ImVector& user_rects = atlas->CustomRects; - IM_ASSERT(user_rects.Size >= 1); // We expect at least the default custom rects to be registered, else something went wrong. -#ifdef __GNUC__ - if (user_rects.Size < 1) { __builtin_unreachable(); } // Workaround for GCC bug if IM_ASSERT() is defined to conditionally throw (see #5343) -#endif - - ImVector pack_rects; - pack_rects.resize(user_rects.Size); - memset(pack_rects.Data, 0, (size_t)pack_rects.size_in_bytes()); - for (int i = 0; i < user_rects.Size; i++) - { - pack_rects[i].w = user_rects[i].Width; - pack_rects[i].h = user_rects[i].Height; - } - stbrp_pack_rects(pack_context, &pack_rects[0], pack_rects.Size); - for (int i = 0; i < pack_rects.Size; i++) - if (pack_rects[i].was_packed) - { - user_rects[i].X = (unsigned short)pack_rects[i].x; - user_rects[i].Y = (unsigned short)pack_rects[i].y; - IM_ASSERT(pack_rects[i].w == user_rects[i].Width && pack_rects[i].h == user_rects[i].Height); - atlas->TexHeight = ImMax(atlas->TexHeight, pack_rects[i].y + pack_rects[i].h); - } -} - -void ImFontAtlasBuildRender8bppRectFromString(ImFontAtlas* atlas, int x, int y, int w, int h, const char* in_str, char in_marker_char, unsigned char in_marker_pixel_value) -{ - IM_ASSERT(x >= 0 && x + w <= atlas->TexWidth); - IM_ASSERT(y >= 0 && y + h <= atlas->TexHeight); - unsigned char* out_pixel = atlas->TexPixelsAlpha8 + x + (y * atlas->TexWidth); - for (int off_y = 0; off_y < h; off_y++, out_pixel += atlas->TexWidth, in_str += w) - for (int off_x = 0; off_x < w; off_x++) - out_pixel[off_x] = (in_str[off_x] == in_marker_char) ? in_marker_pixel_value : 0x00; -} - -void ImFontAtlasBuildRender32bppRectFromString(ImFontAtlas* atlas, int x, int y, int w, int h, const char* in_str, char in_marker_char, unsigned int in_marker_pixel_value) -{ - IM_ASSERT(x >= 0 && x + w <= atlas->TexWidth); - IM_ASSERT(y >= 0 && y + h <= atlas->TexHeight); - unsigned int* out_pixel = atlas->TexPixelsRGBA32 + x + (y * atlas->TexWidth); - for (int off_y = 0; off_y < h; off_y++, out_pixel += atlas->TexWidth, in_str += w) - for (int off_x = 0; off_x < w; off_x++) - out_pixel[off_x] = (in_str[off_x] == in_marker_char) ? in_marker_pixel_value : IM_COL32_BLACK_TRANS; -} - -static void ImFontAtlasBuildRenderDefaultTexData(ImFontAtlas* atlas) -{ - ImFontAtlasCustomRect* r = atlas->GetCustomRectByIndex(atlas->PackIdMouseCursors); - IM_ASSERT(r->IsPacked()); - - const int w = atlas->TexWidth; - if (!(atlas->Flags & ImFontAtlasFlags_NoMouseCursors)) - { - // Render/copy pixels - IM_ASSERT(r->Width == FONT_ATLAS_DEFAULT_TEX_DATA_W * 2 + 1 && r->Height == FONT_ATLAS_DEFAULT_TEX_DATA_H); - const int x_for_white = r->X; - const int x_for_black = r->X + FONT_ATLAS_DEFAULT_TEX_DATA_W + 1; - if (atlas->TexPixelsAlpha8 != NULL) - { - ImFontAtlasBuildRender8bppRectFromString(atlas, x_for_white, r->Y, FONT_ATLAS_DEFAULT_TEX_DATA_W, FONT_ATLAS_DEFAULT_TEX_DATA_H, FONT_ATLAS_DEFAULT_TEX_DATA_PIXELS, '.', 0xFF); - ImFontAtlasBuildRender8bppRectFromString(atlas, x_for_black, r->Y, FONT_ATLAS_DEFAULT_TEX_DATA_W, FONT_ATLAS_DEFAULT_TEX_DATA_H, FONT_ATLAS_DEFAULT_TEX_DATA_PIXELS, 'X', 0xFF); - } - else - { - ImFontAtlasBuildRender32bppRectFromString(atlas, x_for_white, r->Y, FONT_ATLAS_DEFAULT_TEX_DATA_W, FONT_ATLAS_DEFAULT_TEX_DATA_H, FONT_ATLAS_DEFAULT_TEX_DATA_PIXELS, '.', IM_COL32_WHITE); - ImFontAtlasBuildRender32bppRectFromString(atlas, x_for_black, r->Y, FONT_ATLAS_DEFAULT_TEX_DATA_W, FONT_ATLAS_DEFAULT_TEX_DATA_H, FONT_ATLAS_DEFAULT_TEX_DATA_PIXELS, 'X', IM_COL32_WHITE); - } - } - else - { - // Render 4 white pixels - IM_ASSERT(r->Width == 2 && r->Height == 2); - const int offset = (int)r->X + (int)r->Y * w; - if (atlas->TexPixelsAlpha8 != NULL) - { - atlas->TexPixelsAlpha8[offset] = atlas->TexPixelsAlpha8[offset + 1] = atlas->TexPixelsAlpha8[offset + w] = atlas->TexPixelsAlpha8[offset + w + 1] = 0xFF; - } - else - { - atlas->TexPixelsRGBA32[offset] = atlas->TexPixelsRGBA32[offset + 1] = atlas->TexPixelsRGBA32[offset + w] = atlas->TexPixelsRGBA32[offset + w + 1] = IM_COL32_WHITE; - } - } - atlas->TexUvWhitePixel = ImVec2((r->X + 0.5f) * atlas->TexUvScale.x, (r->Y + 0.5f) * atlas->TexUvScale.y); -} - -static void ImFontAtlasBuildRenderLinesTexData(ImFontAtlas* atlas) -{ - if (atlas->Flags & ImFontAtlasFlags_NoBakedLines) - return; - - // This generates a triangular shape in the texture, with the various line widths stacked on top of each other to allow interpolation between them - ImFontAtlasCustomRect* r = atlas->GetCustomRectByIndex(atlas->PackIdLines); - IM_ASSERT(r->IsPacked()); - for (unsigned int n = 0; n < IM_DRAWLIST_TEX_LINES_WIDTH_MAX + 1; n++) // +1 because of the zero-width row - { - // Each line consists of at least two empty pixels at the ends, with a line of solid pixels in the middle - unsigned int y = n; - unsigned int line_width = n; - unsigned int pad_left = (r->Width - line_width) / 2; - unsigned int pad_right = r->Width - (pad_left + line_width); - - // Write each slice - IM_ASSERT(pad_left + line_width + pad_right == r->Width && y < r->Height); // Make sure we're inside the texture bounds before we start writing pixels - if (atlas->TexPixelsAlpha8 != NULL) - { - unsigned char* write_ptr = &atlas->TexPixelsAlpha8[r->X + ((r->Y + y) * atlas->TexWidth)]; - for (unsigned int i = 0; i < pad_left; i++) - *(write_ptr + i) = 0x00; - - for (unsigned int i = 0; i < line_width; i++) - *(write_ptr + pad_left + i) = 0xFF; - - for (unsigned int i = 0; i < pad_right; i++) - *(write_ptr + pad_left + line_width + i) = 0x00; - } - else - { - unsigned int* write_ptr = &atlas->TexPixelsRGBA32[r->X + ((r->Y + y) * atlas->TexWidth)]; - for (unsigned int i = 0; i < pad_left; i++) - *(write_ptr + i) = IM_COL32(255, 255, 255, 0); - - for (unsigned int i = 0; i < line_width; i++) - *(write_ptr + pad_left + i) = IM_COL32_WHITE; - - for (unsigned int i = 0; i < pad_right; i++) - *(write_ptr + pad_left + line_width + i) = IM_COL32(255, 255, 255, 0); - } - - // Calculate UVs for this line - ImVec2 uv0 = ImVec2((float)(r->X + pad_left - 1), (float)(r->Y + y)) * atlas->TexUvScale; - ImVec2 uv1 = ImVec2((float)(r->X + pad_left + line_width + 1), (float)(r->Y + y + 1)) * atlas->TexUvScale; - float half_v = (uv0.y + uv1.y) * 0.5f; // Calculate a constant V in the middle of the row to avoid sampling artifacts - atlas->TexUvLines[n] = ImVec4(uv0.x, half_v, uv1.x, half_v); - } -} - -// Note: this is called / shared by both the stb_truetype and the FreeType builder -void ImFontAtlasBuildInit(ImFontAtlas* atlas) -{ - // Round font size - // - We started rounding in 1.90 WIP (18991) as our layout system currently doesn't support non-rounded font size well yet. - // - Note that using io.FontGlobalScale or SetWindowFontScale(), with are legacy-ish, partially supported features, can still lead to unrounded sizes. - // - We may support it better later and remove this rounding. - for (ImFontConfig& cfg : atlas->ConfigData) - cfg.SizePixels = ImTrunc(cfg.SizePixels); - - // Register texture region for mouse cursors or standard white pixels - if (atlas->PackIdMouseCursors < 0) - { - if (!(atlas->Flags & ImFontAtlasFlags_NoMouseCursors)) - atlas->PackIdMouseCursors = atlas->AddCustomRectRegular(FONT_ATLAS_DEFAULT_TEX_DATA_W * 2 + 1, FONT_ATLAS_DEFAULT_TEX_DATA_H); - else - atlas->PackIdMouseCursors = atlas->AddCustomRectRegular(2, 2); - } - - // Register texture region for thick lines - // The +2 here is to give space for the end caps, whilst height +1 is to accommodate the fact we have a zero-width row - if (atlas->PackIdLines < 0) - { - if (!(atlas->Flags & ImFontAtlasFlags_NoBakedLines)) - atlas->PackIdLines = atlas->AddCustomRectRegular(IM_DRAWLIST_TEX_LINES_WIDTH_MAX + 2, IM_DRAWLIST_TEX_LINES_WIDTH_MAX + 1); - } -} - -// This is called/shared by both the stb_truetype and the FreeType builder. -void ImFontAtlasBuildFinish(ImFontAtlas* atlas) -{ - // Render into our custom data blocks - IM_ASSERT(atlas->TexPixelsAlpha8 != NULL || atlas->TexPixelsRGBA32 != NULL); - ImFontAtlasBuildRenderDefaultTexData(atlas); - ImFontAtlasBuildRenderLinesTexData(atlas); - - // Register custom rectangle glyphs - for (int i = 0; i < atlas->CustomRects.Size; i++) - { - const ImFontAtlasCustomRect* r = &atlas->CustomRects[i]; - if (r->Font == NULL || r->GlyphID == 0) - continue; - - // Will ignore ImFontConfig settings: GlyphMinAdvanceX, GlyphMinAdvanceY, GlyphExtraSpacing, PixelSnapH - IM_ASSERT(r->Font->ContainerAtlas == atlas); - ImVec2 uv0, uv1; - atlas->CalcCustomRectUV(r, &uv0, &uv1); - r->Font->AddGlyph(NULL, (ImWchar)r->GlyphID, r->GlyphOffset.x, r->GlyphOffset.y, r->GlyphOffset.x + r->Width, r->GlyphOffset.y + r->Height, uv0.x, uv0.y, uv1.x, uv1.y, r->GlyphAdvanceX); - } - - // Build all fonts lookup tables - for (ImFont* font : atlas->Fonts) - if (font->DirtyLookupTables) - font->BuildLookupTable(); - - atlas->TexReady = true; -} - -// Retrieve list of range (2 int per range, values are inclusive) -const ImWchar* ImFontAtlas::GetGlyphRangesDefault() -{ - static const ImWchar ranges[] = - { - 0x0020, 0x00FF, // Basic Latin + Latin Supplement - 0, - }; - return &ranges[0]; -} - -const ImWchar* ImFontAtlas::GetGlyphRangesGreek() -{ - static const ImWchar ranges[] = - { - 0x0020, 0x00FF, // Basic Latin + Latin Supplement - 0x0370, 0x03FF, // Greek and Coptic - 0, - }; - return &ranges[0]; -} - -const ImWchar* ImFontAtlas::GetGlyphRangesKorean() -{ - static const ImWchar ranges[] = - { - 0x0020, 0x00FF, // Basic Latin + Latin Supplement - 0x3131, 0x3163, // Korean alphabets - 0xAC00, 0xD7A3, // Korean characters - 0xFFFD, 0xFFFD, // Invalid - 0, - }; - return &ranges[0]; -} - -const ImWchar* ImFontAtlas::GetGlyphRangesChineseFull() -{ - static const ImWchar ranges[] = - { - 0x0020, 0x00FF, // Basic Latin + Latin Supplement - 0x2000, 0x206F, // General Punctuation - 0x3000, 0x30FF, // CJK Symbols and Punctuations, Hiragana, Katakana - 0x31F0, 0x31FF, // Katakana Phonetic Extensions - 0xFF00, 0xFFEF, // Half-width characters - 0xFFFD, 0xFFFD, // Invalid - 0x4e00, 0x9FAF, // CJK Ideograms - 0, - }; - return &ranges[0]; -} - -static void UnpackAccumulativeOffsetsIntoRanges(int base_codepoint, const short* accumulative_offsets, int accumulative_offsets_count, ImWchar* out_ranges) -{ - for (int n = 0; n < accumulative_offsets_count; n++, out_ranges += 2) - { - out_ranges[0] = out_ranges[1] = (ImWchar)(base_codepoint + accumulative_offsets[n]); - base_codepoint += accumulative_offsets[n]; - } - out_ranges[0] = 0; -} - -//------------------------------------------------------------------------- -// [SECTION] ImFontAtlas glyph ranges helpers -//------------------------------------------------------------------------- - -const ImWchar* ImFontAtlas::GetGlyphRangesChineseSimplifiedCommon() -{ - // Store 2500 regularly used characters for Simplified Chinese. - // Sourced from https://zh.wiktionary.org/wiki/%E9%99%84%E5%BD%95:%E7%8E%B0%E4%BB%A3%E6%B1%89%E8%AF%AD%E5%B8%B8%E7%94%A8%E5%AD%97%E8%A1%A8 - // This table covers 97.97% of all characters used during the month in July, 1987. - // You can use ImFontGlyphRangesBuilder to create your own ranges derived from this, by merging existing ranges or adding new characters. - // (Stored as accumulative offsets from the initial unicode codepoint 0x4E00. This encoding is designed to helps us compact the source code size.) - static const short accumulative_offsets_from_0x4E00[] = - { - 0,1,2,4,1,1,1,1,2,1,3,2,1,2,2,1,1,1,1,1,5,2,1,2,3,3,3,2,2,4,1,1,1,2,1,5,2,3,1,2,1,2,1,1,2,1,1,2,2,1,4,1,1,1,1,5,10,1,2,19,2,1,2,1,2,1,2,1,2, - 1,5,1,6,3,2,1,2,2,1,1,1,4,8,5,1,1,4,1,1,3,1,2,1,5,1,2,1,1,1,10,1,1,5,2,4,6,1,4,2,2,2,12,2,1,1,6,1,1,1,4,1,1,4,6,5,1,4,2,2,4,10,7,1,1,4,2,4, - 2,1,4,3,6,10,12,5,7,2,14,2,9,1,1,6,7,10,4,7,13,1,5,4,8,4,1,1,2,28,5,6,1,1,5,2,5,20,2,2,9,8,11,2,9,17,1,8,6,8,27,4,6,9,20,11,27,6,68,2,2,1,1, - 1,2,1,2,2,7,6,11,3,3,1,1,3,1,2,1,1,1,1,1,3,1,1,8,3,4,1,5,7,2,1,4,4,8,4,2,1,2,1,1,4,5,6,3,6,2,12,3,1,3,9,2,4,3,4,1,5,3,3,1,3,7,1,5,1,1,1,1,2, - 3,4,5,2,3,2,6,1,1,2,1,7,1,7,3,4,5,15,2,2,1,5,3,22,19,2,1,1,1,1,2,5,1,1,1,6,1,1,12,8,2,9,18,22,4,1,1,5,1,16,1,2,7,10,15,1,1,6,2,4,1,2,4,1,6, - 1,1,3,2,4,1,6,4,5,1,2,1,1,2,1,10,3,1,3,2,1,9,3,2,5,7,2,19,4,3,6,1,1,1,1,1,4,3,2,1,1,1,2,5,3,1,1,1,2,2,1,1,2,1,1,2,1,3,1,1,1,3,7,1,4,1,1,2,1, - 1,2,1,2,4,4,3,8,1,1,1,2,1,3,5,1,3,1,3,4,6,2,2,14,4,6,6,11,9,1,15,3,1,28,5,2,5,5,3,1,3,4,5,4,6,14,3,2,3,5,21,2,7,20,10,1,2,19,2,4,28,28,2,3, - 2,1,14,4,1,26,28,42,12,40,3,52,79,5,14,17,3,2,2,11,3,4,6,3,1,8,2,23,4,5,8,10,4,2,7,3,5,1,1,6,3,1,2,2,2,5,28,1,1,7,7,20,5,3,29,3,17,26,1,8,4, - 27,3,6,11,23,5,3,4,6,13,24,16,6,5,10,25,35,7,3,2,3,3,14,3,6,2,6,1,4,2,3,8,2,1,1,3,3,3,4,1,1,13,2,2,4,5,2,1,14,14,1,2,2,1,4,5,2,3,1,14,3,12, - 3,17,2,16,5,1,2,1,8,9,3,19,4,2,2,4,17,25,21,20,28,75,1,10,29,103,4,1,2,1,1,4,2,4,1,2,3,24,2,2,2,1,1,2,1,3,8,1,1,1,2,1,1,3,1,1,1,6,1,5,3,1,1, - 1,3,4,1,1,5,2,1,5,6,13,9,16,1,1,1,1,3,2,3,2,4,5,2,5,2,2,3,7,13,7,2,2,1,1,1,1,2,3,3,2,1,6,4,9,2,1,14,2,14,2,1,18,3,4,14,4,11,41,15,23,15,23, - 176,1,3,4,1,1,1,1,5,3,1,2,3,7,3,1,1,2,1,2,4,4,6,2,4,1,9,7,1,10,5,8,16,29,1,1,2,2,3,1,3,5,2,4,5,4,1,1,2,2,3,3,7,1,6,10,1,17,1,44,4,6,2,1,1,6, - 5,4,2,10,1,6,9,2,8,1,24,1,2,13,7,8,8,2,1,4,1,3,1,3,3,5,2,5,10,9,4,9,12,2,1,6,1,10,1,1,7,7,4,10,8,3,1,13,4,3,1,6,1,3,5,2,1,2,17,16,5,2,16,6, - 1,4,2,1,3,3,6,8,5,11,11,1,3,3,2,4,6,10,9,5,7,4,7,4,7,1,1,4,2,1,3,6,8,7,1,6,11,5,5,3,24,9,4,2,7,13,5,1,8,82,16,61,1,1,1,4,2,2,16,10,3,8,1,1, - 6,4,2,1,3,1,1,1,4,3,8,4,2,2,1,1,1,1,1,6,3,5,1,1,4,6,9,2,1,1,1,2,1,7,2,1,6,1,5,4,4,3,1,8,1,3,3,1,3,2,2,2,2,3,1,6,1,2,1,2,1,3,7,1,8,2,1,2,1,5, - 2,5,3,5,10,1,2,1,1,3,2,5,11,3,9,3,5,1,1,5,9,1,2,1,5,7,9,9,8,1,3,3,3,6,8,2,3,2,1,1,32,6,1,2,15,9,3,7,13,1,3,10,13,2,14,1,13,10,2,1,3,10,4,15, - 2,15,15,10,1,3,9,6,9,32,25,26,47,7,3,2,3,1,6,3,4,3,2,8,5,4,1,9,4,2,2,19,10,6,2,3,8,1,2,2,4,2,1,9,4,4,4,6,4,8,9,2,3,1,1,1,1,3,5,5,1,3,8,4,6, - 2,1,4,12,1,5,3,7,13,2,5,8,1,6,1,2,5,14,6,1,5,2,4,8,15,5,1,23,6,62,2,10,1,1,8,1,2,2,10,4,2,2,9,2,1,1,3,2,3,1,5,3,3,2,1,3,8,1,1,1,11,3,1,1,4, - 3,7,1,14,1,2,3,12,5,2,5,1,6,7,5,7,14,11,1,3,1,8,9,12,2,1,11,8,4,4,2,6,10,9,13,1,1,3,1,5,1,3,2,4,4,1,18,2,3,14,11,4,29,4,2,7,1,3,13,9,2,2,5, - 3,5,20,7,16,8,5,72,34,6,4,22,12,12,28,45,36,9,7,39,9,191,1,1,1,4,11,8,4,9,2,3,22,1,1,1,1,4,17,1,7,7,1,11,31,10,2,4,8,2,3,2,1,4,2,16,4,32,2, - 3,19,13,4,9,1,5,2,14,8,1,1,3,6,19,6,5,1,16,6,2,10,8,5,1,2,3,1,5,5,1,11,6,6,1,3,3,2,6,3,8,1,1,4,10,7,5,7,7,5,8,9,2,1,3,4,1,1,3,1,3,3,2,6,16, - 1,4,6,3,1,10,6,1,3,15,2,9,2,10,25,13,9,16,6,2,2,10,11,4,3,9,1,2,6,6,5,4,30,40,1,10,7,12,14,33,6,3,6,7,3,1,3,1,11,14,4,9,5,12,11,49,18,51,31, - 140,31,2,2,1,5,1,8,1,10,1,4,4,3,24,1,10,1,3,6,6,16,3,4,5,2,1,4,2,57,10,6,22,2,22,3,7,22,6,10,11,36,18,16,33,36,2,5,5,1,1,1,4,10,1,4,13,2,7, - 5,2,9,3,4,1,7,43,3,7,3,9,14,7,9,1,11,1,1,3,7,4,18,13,1,14,1,3,6,10,73,2,2,30,6,1,11,18,19,13,22,3,46,42,37,89,7,3,16,34,2,2,3,9,1,7,1,1,1,2, - 2,4,10,7,3,10,3,9,5,28,9,2,6,13,7,3,1,3,10,2,7,2,11,3,6,21,54,85,2,1,4,2,2,1,39,3,21,2,2,5,1,1,1,4,1,1,3,4,15,1,3,2,4,4,2,3,8,2,20,1,8,7,13, - 4,1,26,6,2,9,34,4,21,52,10,4,4,1,5,12,2,11,1,7,2,30,12,44,2,30,1,1,3,6,16,9,17,39,82,2,2,24,7,1,7,3,16,9,14,44,2,1,2,1,2,3,5,2,4,1,6,7,5,3, - 2,6,1,11,5,11,2,1,18,19,8,1,3,24,29,2,1,3,5,2,2,1,13,6,5,1,46,11,3,5,1,1,5,8,2,10,6,12,6,3,7,11,2,4,16,13,2,5,1,1,2,2,5,2,28,5,2,23,10,8,4, - 4,22,39,95,38,8,14,9,5,1,13,5,4,3,13,12,11,1,9,1,27,37,2,5,4,4,63,211,95,2,2,2,1,3,5,2,1,1,2,2,1,1,1,3,2,4,1,2,1,1,5,2,2,1,1,2,3,1,3,1,1,1, - 3,1,4,2,1,3,6,1,1,3,7,15,5,3,2,5,3,9,11,4,2,22,1,6,3,8,7,1,4,28,4,16,3,3,25,4,4,27,27,1,4,1,2,2,7,1,3,5,2,28,8,2,14,1,8,6,16,25,3,3,3,14,3, - 3,1,1,2,1,4,6,3,8,4,1,1,1,2,3,6,10,6,2,3,18,3,2,5,5,4,3,1,5,2,5,4,23,7,6,12,6,4,17,11,9,5,1,1,10,5,12,1,1,11,26,33,7,3,6,1,17,7,1,5,12,1,11, - 2,4,1,8,14,17,23,1,2,1,7,8,16,11,9,6,5,2,6,4,16,2,8,14,1,11,8,9,1,1,1,9,25,4,11,19,7,2,15,2,12,8,52,7,5,19,2,16,4,36,8,1,16,8,24,26,4,6,2,9, - 5,4,36,3,28,12,25,15,37,27,17,12,59,38,5,32,127,1,2,9,17,14,4,1,2,1,1,8,11,50,4,14,2,19,16,4,17,5,4,5,26,12,45,2,23,45,104,30,12,8,3,10,2,2, - 3,3,1,4,20,7,2,9,6,15,2,20,1,3,16,4,11,15,6,134,2,5,59,1,2,2,2,1,9,17,3,26,137,10,211,59,1,2,4,1,4,1,1,1,2,6,2,3,1,1,2,3,2,3,1,3,4,4,2,3,3, - 1,4,3,1,7,2,2,3,1,2,1,3,3,3,2,2,3,2,1,3,14,6,1,3,2,9,6,15,27,9,34,145,1,1,2,1,1,1,1,2,1,1,1,1,2,2,2,3,1,2,1,1,1,2,3,5,8,3,5,2,4,1,3,2,2,2,12, - 4,1,1,1,10,4,5,1,20,4,16,1,15,9,5,12,2,9,2,5,4,2,26,19,7,1,26,4,30,12,15,42,1,6,8,172,1,1,4,2,1,1,11,2,2,4,2,1,2,1,10,8,1,2,1,4,5,1,2,5,1,8, - 4,1,3,4,2,1,6,2,1,3,4,1,2,1,1,1,1,12,5,7,2,4,3,1,1,1,3,3,6,1,2,2,3,3,3,2,1,2,12,14,11,6,6,4,12,2,8,1,7,10,1,35,7,4,13,15,4,3,23,21,28,52,5, - 26,5,6,1,7,10,2,7,53,3,2,1,1,1,2,163,532,1,10,11,1,3,3,4,8,2,8,6,2,2,23,22,4,2,2,4,2,1,3,1,3,3,5,9,8,2,1,2,8,1,10,2,12,21,20,15,105,2,3,1,1, - 3,2,3,1,1,2,5,1,4,15,11,19,1,1,1,1,5,4,5,1,1,2,5,3,5,12,1,2,5,1,11,1,1,15,9,1,4,5,3,26,8,2,1,3,1,1,15,19,2,12,1,2,5,2,7,2,19,2,20,6,26,7,5, - 2,2,7,34,21,13,70,2,128,1,1,2,1,1,2,1,1,3,2,2,2,15,1,4,1,3,4,42,10,6,1,49,85,8,1,2,1,1,4,4,2,3,6,1,5,7,4,3,211,4,1,2,1,2,5,1,2,4,2,2,6,5,6, - 10,3,4,48,100,6,2,16,296,5,27,387,2,2,3,7,16,8,5,38,15,39,21,9,10,3,7,59,13,27,21,47,5,21,6 - }; - static ImWchar base_ranges[] = // not zero-terminated - { - 0x0020, 0x00FF, // Basic Latin + Latin Supplement - 0x2000, 0x206F, // General Punctuation - 0x3000, 0x30FF, // CJK Symbols and Punctuations, Hiragana, Katakana - 0x31F0, 0x31FF, // Katakana Phonetic Extensions - 0xFF00, 0xFFEF, // Half-width characters - 0xFFFD, 0xFFFD // Invalid - }; - static ImWchar full_ranges[IM_ARRAYSIZE(base_ranges) + IM_ARRAYSIZE(accumulative_offsets_from_0x4E00) * 2 + 1] = { 0 }; - if (!full_ranges[0]) - { - memcpy(full_ranges, base_ranges, sizeof(base_ranges)); - UnpackAccumulativeOffsetsIntoRanges(0x4E00, accumulative_offsets_from_0x4E00, IM_ARRAYSIZE(accumulative_offsets_from_0x4E00), full_ranges + IM_ARRAYSIZE(base_ranges)); - } - return &full_ranges[0]; -} - -const ImWchar* ImFontAtlas::GetGlyphRangesJapanese() -{ - // 2999 ideograms code points for Japanese - // - 2136 Joyo (meaning "for regular use" or "for common use") Kanji code points - // - 863 Jinmeiyo (meaning "for personal name") Kanji code points - // - Sourced from official information provided by the government agencies of Japan: - // - List of Joyo Kanji by the Agency for Cultural Affairs - // - https://www.bunka.go.jp/kokugo_nihongo/sisaku/joho/joho/kijun/naikaku/kanji/ - // - List of Jinmeiyo Kanji by the Ministry of Justice - // - http://www.moj.go.jp/MINJI/minji86.html - // - Available under the terms of the Creative Commons Attribution 4.0 International (CC BY 4.0). - // - https://creativecommons.org/licenses/by/4.0/legalcode - // - You can generate this code by the script at: - // - https://github.com/vaiorabbit/everyday_use_kanji - // - References: - // - List of Joyo Kanji - // - (Wikipedia) https://en.wikipedia.org/wiki/List_of_j%C5%8Dy%C5%8D_kanji - // - List of Jinmeiyo Kanji - // - (Wikipedia) https://en.wikipedia.org/wiki/Jinmeiy%C5%8D_kanji - // - Missing 1 Joyo Kanji: U+20B9F (Kun'yomi: Shikaru, On'yomi: Shitsu,shichi), see https://github.com/ocornut/imgui/pull/3627 for details. - // You can use ImFontGlyphRangesBuilder to create your own ranges derived from this, by merging existing ranges or adding new characters. - // (Stored as accumulative offsets from the initial unicode codepoint 0x4E00. This encoding is designed to helps us compact the source code size.) - static const short accumulative_offsets_from_0x4E00[] = - { - 0,1,2,4,1,1,1,1,2,1,3,3,2,2,1,5,3,5,7,5,6,1,2,1,7,2,6,3,1,8,1,1,4,1,1,18,2,11,2,6,2,1,2,1,5,1,2,1,3,1,2,1,2,3,3,1,1,2,3,1,1,1,12,7,9,1,4,5,1, - 1,2,1,10,1,1,9,2,2,4,5,6,9,3,1,1,1,1,9,3,18,5,2,2,2,2,1,6,3,7,1,1,1,1,2,2,4,2,1,23,2,10,4,3,5,2,4,10,2,4,13,1,6,1,9,3,1,1,6,6,7,6,3,1,2,11,3, - 2,2,3,2,15,2,2,5,4,3,6,4,1,2,5,2,12,16,6,13,9,13,2,1,1,7,16,4,7,1,19,1,5,1,2,2,7,7,8,2,6,5,4,9,18,7,4,5,9,13,11,8,15,2,1,1,1,2,1,2,2,1,2,2,8, - 2,9,3,3,1,1,4,4,1,1,1,4,9,1,4,3,5,5,2,7,5,3,4,8,2,1,13,2,3,3,1,14,1,1,4,5,1,3,6,1,5,2,1,1,3,3,3,3,1,1,2,7,6,6,7,1,4,7,6,1,1,1,1,1,12,3,3,9,5, - 2,6,1,5,6,1,2,3,18,2,4,14,4,1,3,6,1,1,6,3,5,5,3,2,2,2,2,12,3,1,4,2,3,2,3,11,1,7,4,1,2,1,3,17,1,9,1,24,1,1,4,2,2,4,1,2,7,1,1,1,3,1,2,2,4,15,1, - 1,2,1,1,2,1,5,2,5,20,2,5,9,1,10,8,7,6,1,1,1,1,1,1,6,2,1,2,8,1,1,1,1,5,1,1,3,1,1,1,1,3,1,1,12,4,1,3,1,1,1,1,1,10,3,1,7,5,13,1,2,3,4,6,1,1,30, - 2,9,9,1,15,38,11,3,1,8,24,7,1,9,8,10,2,1,9,31,2,13,6,2,9,4,49,5,2,15,2,1,10,2,1,1,1,2,2,6,15,30,35,3,14,18,8,1,16,10,28,12,19,45,38,1,3,2,3, - 13,2,1,7,3,6,5,3,4,3,1,5,7,8,1,5,3,18,5,3,6,1,21,4,24,9,24,40,3,14,3,21,3,2,1,2,4,2,3,1,15,15,6,5,1,1,3,1,5,6,1,9,7,3,3,2,1,4,3,8,21,5,16,4, - 5,2,10,11,11,3,6,3,2,9,3,6,13,1,2,1,1,1,1,11,12,6,6,1,4,2,6,5,2,1,1,3,3,6,13,3,1,1,5,1,2,3,3,14,2,1,2,2,2,5,1,9,5,1,1,6,12,3,12,3,4,13,2,14, - 2,8,1,17,5,1,16,4,2,2,21,8,9,6,23,20,12,25,19,9,38,8,3,21,40,25,33,13,4,3,1,4,1,2,4,1,2,5,26,2,1,1,2,1,3,6,2,1,1,1,1,1,1,2,3,1,1,1,9,2,3,1,1, - 1,3,6,3,2,1,1,6,6,1,8,2,2,2,1,4,1,2,3,2,7,3,2,4,1,2,1,2,2,1,1,1,1,1,3,1,2,5,4,10,9,4,9,1,1,1,1,1,1,5,3,2,1,6,4,9,6,1,10,2,31,17,8,3,7,5,40,1, - 7,7,1,6,5,2,10,7,8,4,15,39,25,6,28,47,18,10,7,1,3,1,1,2,1,1,1,3,3,3,1,1,1,3,4,2,1,4,1,3,6,10,7,8,6,2,2,1,3,3,2,5,8,7,9,12,2,15,1,1,4,1,2,1,1, - 1,3,2,1,3,3,5,6,2,3,2,10,1,4,2,8,1,1,1,11,6,1,21,4,16,3,1,3,1,4,2,3,6,5,1,3,1,1,3,3,4,6,1,1,10,4,2,7,10,4,7,4,2,9,4,3,1,1,1,4,1,8,3,4,1,3,1, - 6,1,4,2,1,4,7,2,1,8,1,4,5,1,1,2,2,4,6,2,7,1,10,1,1,3,4,11,10,8,21,4,6,1,3,5,2,1,2,28,5,5,2,3,13,1,2,3,1,4,2,1,5,20,3,8,11,1,3,3,3,1,8,10,9,2, - 10,9,2,3,1,1,2,4,1,8,3,6,1,7,8,6,11,1,4,29,8,4,3,1,2,7,13,1,4,1,6,2,6,12,12,2,20,3,2,3,6,4,8,9,2,7,34,5,1,18,6,1,1,4,4,5,7,9,1,2,2,4,3,4,1,7, - 2,2,2,6,2,3,25,5,3,6,1,4,6,7,4,2,1,4,2,13,6,4,4,3,1,5,3,4,4,3,2,1,1,4,1,2,1,1,3,1,11,1,6,3,1,7,3,6,2,8,8,6,9,3,4,11,3,2,10,12,2,5,11,1,6,4,5, - 3,1,8,5,4,6,6,3,5,1,1,3,2,1,2,2,6,17,12,1,10,1,6,12,1,6,6,19,9,6,16,1,13,4,4,15,7,17,6,11,9,15,12,6,7,2,1,2,2,15,9,3,21,4,6,49,18,7,3,2,3,1, - 6,8,2,2,6,2,9,1,3,6,4,4,1,2,16,2,5,2,1,6,2,3,5,3,1,2,5,1,2,1,9,3,1,8,6,4,8,11,3,1,1,1,1,3,1,13,8,4,1,3,2,2,1,4,1,11,1,5,2,1,5,2,5,8,6,1,1,7, - 4,3,8,3,2,7,2,1,5,1,5,2,4,7,6,2,8,5,1,11,4,5,3,6,18,1,2,13,3,3,1,21,1,1,4,1,4,1,1,1,8,1,2,2,7,1,2,4,2,2,9,2,1,1,1,4,3,6,3,12,5,1,1,1,5,6,3,2, - 4,8,2,2,4,2,7,1,8,9,5,2,3,2,1,3,2,13,7,14,6,5,1,1,2,1,4,2,23,2,1,1,6,3,1,4,1,15,3,1,7,3,9,14,1,3,1,4,1,1,5,8,1,3,8,3,8,15,11,4,14,4,4,2,5,5, - 1,7,1,6,14,7,7,8,5,15,4,8,6,5,6,2,1,13,1,20,15,11,9,2,5,6,2,11,2,6,2,5,1,5,8,4,13,19,25,4,1,1,11,1,34,2,5,9,14,6,2,2,6,1,1,14,1,3,14,13,1,6, - 12,21,14,14,6,32,17,8,32,9,28,1,2,4,11,8,3,1,14,2,5,15,1,1,1,1,3,6,4,1,3,4,11,3,1,1,11,30,1,5,1,4,1,5,8,1,1,3,2,4,3,17,35,2,6,12,17,3,1,6,2, - 1,1,12,2,7,3,3,2,1,16,2,8,3,6,5,4,7,3,3,8,1,9,8,5,1,2,1,3,2,8,1,2,9,12,1,1,2,3,8,3,24,12,4,3,7,5,8,3,3,3,3,3,3,1,23,10,3,1,2,2,6,3,1,16,1,16, - 22,3,10,4,11,6,9,7,7,3,6,2,2,2,4,10,2,1,1,2,8,7,1,6,4,1,3,3,3,5,10,12,12,2,3,12,8,15,1,1,16,6,6,1,5,9,11,4,11,4,2,6,12,1,17,5,13,1,4,9,5,1,11, - 2,1,8,1,5,7,28,8,3,5,10,2,17,3,38,22,1,2,18,12,10,4,38,18,1,4,44,19,4,1,8,4,1,12,1,4,31,12,1,14,7,75,7,5,10,6,6,13,3,2,11,11,3,2,5,28,15,6,18, - 18,5,6,4,3,16,1,7,18,7,36,3,5,3,1,7,1,9,1,10,7,2,4,2,6,2,9,7,4,3,32,12,3,7,10,2,23,16,3,1,12,3,31,4,11,1,3,8,9,5,1,30,15,6,12,3,2,2,11,19,9, - 14,2,6,2,3,19,13,17,5,3,3,25,3,14,1,1,1,36,1,3,2,19,3,13,36,9,13,31,6,4,16,34,2,5,4,2,3,3,5,1,1,1,4,3,1,17,3,2,3,5,3,1,3,2,3,5,6,3,12,11,1,3, - 1,2,26,7,12,7,2,14,3,3,7,7,11,25,25,28,16,4,36,1,2,1,6,2,1,9,3,27,17,4,3,4,13,4,1,3,2,2,1,10,4,2,4,6,3,8,2,1,18,1,1,24,2,2,4,33,2,3,63,7,1,6, - 40,7,3,4,4,2,4,15,18,1,16,1,1,11,2,41,14,1,3,18,13,3,2,4,16,2,17,7,15,24,7,18,13,44,2,2,3,6,1,1,7,5,1,7,1,4,3,3,5,10,8,2,3,1,8,1,1,27,4,2,1, - 12,1,2,1,10,6,1,6,7,5,2,3,7,11,5,11,3,6,6,2,3,15,4,9,1,1,2,1,2,11,2,8,12,8,5,4,2,3,1,5,2,2,1,14,1,12,11,4,1,11,17,17,4,3,2,5,5,7,3,1,5,9,9,8, - 2,5,6,6,13,13,2,1,2,6,1,2,2,49,4,9,1,2,10,16,7,8,4,3,2,23,4,58,3,29,1,14,19,19,11,11,2,7,5,1,3,4,6,2,18,5,12,12,17,17,3,3,2,4,1,6,2,3,4,3,1, - 1,1,1,5,1,1,9,1,3,1,3,6,1,8,1,1,2,6,4,14,3,1,4,11,4,1,3,32,1,2,4,13,4,1,2,4,2,1,3,1,11,1,4,2,1,4,4,6,3,5,1,6,5,7,6,3,23,3,5,3,5,3,3,13,3,9,10, - 1,12,10,2,3,18,13,7,160,52,4,2,2,3,2,14,5,4,12,4,6,4,1,20,4,11,6,2,12,27,1,4,1,2,2,7,4,5,2,28,3,7,25,8,3,19,3,6,10,2,2,1,10,2,5,4,1,3,4,1,5, - 3,2,6,9,3,6,2,16,3,3,16,4,5,5,3,2,1,2,16,15,8,2,6,21,2,4,1,22,5,8,1,1,21,11,2,1,11,11,19,13,12,4,2,3,2,3,6,1,8,11,1,4,2,9,5,2,1,11,2,9,1,1,2, - 14,31,9,3,4,21,14,4,8,1,7,2,2,2,5,1,4,20,3,3,4,10,1,11,9,8,2,1,4,5,14,12,14,2,17,9,6,31,4,14,1,20,13,26,5,2,7,3,6,13,2,4,2,19,6,2,2,18,9,3,5, - 12,12,14,4,6,2,3,6,9,5,22,4,5,25,6,4,8,5,2,6,27,2,35,2,16,3,7,8,8,6,6,5,9,17,2,20,6,19,2,13,3,1,1,1,4,17,12,2,14,7,1,4,18,12,38,33,2,10,1,1, - 2,13,14,17,11,50,6,33,20,26,74,16,23,45,50,13,38,33,6,6,7,4,4,2,1,3,2,5,8,7,8,9,3,11,21,9,13,1,3,10,6,7,1,2,2,18,5,5,1,9,9,2,68,9,19,13,2,5, - 1,4,4,7,4,13,3,9,10,21,17,3,26,2,1,5,2,4,5,4,1,7,4,7,3,4,2,1,6,1,1,20,4,1,9,2,2,1,3,3,2,3,2,1,1,1,20,2,3,1,6,2,3,6,2,4,8,1,3,2,10,3,5,3,4,4, - 3,4,16,1,6,1,10,2,4,2,1,1,2,10,11,2,2,3,1,24,31,4,10,10,2,5,12,16,164,15,4,16,7,9,15,19,17,1,2,1,1,5,1,1,1,1,1,3,1,4,3,1,3,1,3,1,2,1,1,3,3,7, - 2,8,1,2,2,2,1,3,4,3,7,8,12,92,2,10,3,1,3,14,5,25,16,42,4,7,7,4,2,21,5,27,26,27,21,25,30,31,2,1,5,13,3,22,5,6,6,11,9,12,1,5,9,7,5,5,22,60,3,5, - 13,1,1,8,1,1,3,3,2,1,9,3,3,18,4,1,2,3,7,6,3,1,2,3,9,1,3,1,3,2,1,3,1,1,1,2,1,11,3,1,6,9,1,3,2,3,1,2,1,5,1,1,4,3,4,1,2,2,4,4,1,7,2,1,2,2,3,5,13, - 18,3,4,14,9,9,4,16,3,7,5,8,2,6,48,28,3,1,1,4,2,14,8,2,9,2,1,15,2,4,3,2,10,16,12,8,7,1,1,3,1,1,1,2,7,4,1,6,4,38,39,16,23,7,15,15,3,2,12,7,21, - 37,27,6,5,4,8,2,10,8,8,6,5,1,2,1,3,24,1,16,17,9,23,10,17,6,1,51,55,44,13,294,9,3,6,2,4,2,2,15,1,1,1,13,21,17,68,14,8,9,4,1,4,9,3,11,7,1,1,1, - 5,6,3,2,1,1,1,2,3,8,1,2,2,4,1,5,5,2,1,4,3,7,13,4,1,4,1,3,1,1,1,5,5,10,1,6,1,5,2,1,5,2,4,1,4,5,7,3,18,2,9,11,32,4,3,3,2,4,7,11,16,9,11,8,13,38, - 32,8,4,2,1,1,2,1,2,4,4,1,1,1,4,1,21,3,11,1,16,1,1,6,1,3,2,4,9,8,57,7,44,1,3,3,13,3,10,1,1,7,5,2,7,21,47,63,3,15,4,7,1,16,1,1,2,8,2,3,42,15,4, - 1,29,7,22,10,3,78,16,12,20,18,4,67,11,5,1,3,15,6,21,31,32,27,18,13,71,35,5,142,4,10,1,2,50,19,33,16,35,37,16,19,27,7,1,133,19,1,4,8,7,20,1,4, - 4,1,10,3,1,6,1,2,51,5,40,15,24,43,22928,11,1,13,154,70,3,1,1,7,4,10,1,2,1,1,2,1,2,1,2,2,1,1,2,1,1,1,1,1,2,1,1,1,1,1,1,1,1,1,1,1,1,1,2,1,1,1, - 3,2,1,1,1,1,2,1,1, - }; - static ImWchar base_ranges[] = // not zero-terminated - { - 0x0020, 0x00FF, // Basic Latin + Latin Supplement - 0x3000, 0x30FF, // CJK Symbols and Punctuations, Hiragana, Katakana - 0x31F0, 0x31FF, // Katakana Phonetic Extensions - 0xFF00, 0xFFEF, // Half-width characters - 0xFFFD, 0xFFFD // Invalid - }; - static ImWchar full_ranges[IM_ARRAYSIZE(base_ranges) + IM_ARRAYSIZE(accumulative_offsets_from_0x4E00)*2 + 1] = { 0 }; - if (!full_ranges[0]) - { - memcpy(full_ranges, base_ranges, sizeof(base_ranges)); - UnpackAccumulativeOffsetsIntoRanges(0x4E00, accumulative_offsets_from_0x4E00, IM_ARRAYSIZE(accumulative_offsets_from_0x4E00), full_ranges + IM_ARRAYSIZE(base_ranges)); - } - return &full_ranges[0]; -} - -const ImWchar* ImFontAtlas::GetGlyphRangesCyrillic() -{ - static const ImWchar ranges[] = - { - 0x0020, 0x00FF, // Basic Latin + Latin Supplement - 0x0400, 0x052F, // Cyrillic + Cyrillic Supplement - 0x2DE0, 0x2DFF, // Cyrillic Extended-A - 0xA640, 0xA69F, // Cyrillic Extended-B - 0, - }; - return &ranges[0]; -} - -const ImWchar* ImFontAtlas::GetGlyphRangesThai() -{ - static const ImWchar ranges[] = - { - 0x0020, 0x00FF, // Basic Latin - 0x2010, 0x205E, // Punctuations - 0x0E00, 0x0E7F, // Thai - 0, - }; - return &ranges[0]; -} - -const ImWchar* ImFontAtlas::GetGlyphRangesVietnamese() -{ - static const ImWchar ranges[] = - { - 0x0020, 0x00FF, // Basic Latin - 0x0102, 0x0103, - 0x0110, 0x0111, - 0x0128, 0x0129, - 0x0168, 0x0169, - 0x01A0, 0x01A1, - 0x01AF, 0x01B0, - 0x1EA0, 0x1EF9, - 0, - }; - return &ranges[0]; -} - -//----------------------------------------------------------------------------- -// [SECTION] ImFontGlyphRangesBuilder -//----------------------------------------------------------------------------- - -void ImFontGlyphRangesBuilder::AddText(const char* text, const char* text_end) -{ - while (text_end ? (text < text_end) : *text) - { - unsigned int c = 0; - int c_len = ImTextCharFromUtf8(&c, text, text_end); - text += c_len; - if (c_len == 0) - break; - AddChar((ImWchar)c); - } -} - -void ImFontGlyphRangesBuilder::AddRanges(const ImWchar* ranges) -{ - for (; ranges[0]; ranges += 2) - for (unsigned int c = ranges[0]; c <= ranges[1] && c <= IM_UNICODE_CODEPOINT_MAX; c++) //-V560 - AddChar((ImWchar)c); -} - -void ImFontGlyphRangesBuilder::BuildRanges(ImVector* out_ranges) -{ - const int max_codepoint = IM_UNICODE_CODEPOINT_MAX; - for (int n = 0; n <= max_codepoint; n++) - if (GetBit(n)) - { - out_ranges->push_back((ImWchar)n); - while (n < max_codepoint && GetBit(n + 1)) - n++; - out_ranges->push_back((ImWchar)n); - } - out_ranges->push_back(0); -} - -//----------------------------------------------------------------------------- -// [SECTION] ImFont -//----------------------------------------------------------------------------- - -ImFont::ImFont() -{ - FontSize = 0.0f; - FallbackAdvanceX = 0.0f; - FallbackChar = (ImWchar)-1; - EllipsisChar = (ImWchar)-1; - EllipsisWidth = EllipsisCharStep = 0.0f; - EllipsisCharCount = 0; - FallbackGlyph = NULL; - ContainerAtlas = NULL; - ConfigData = NULL; - ConfigDataCount = 0; - DirtyLookupTables = false; - Scale = 1.0f; - Ascent = Descent = 0.0f; - MetricsTotalSurface = 0; - memset(Used4kPagesMap, 0, sizeof(Used4kPagesMap)); -} - -ImFont::~ImFont() -{ - ClearOutputData(); -} - -void ImFont::ClearOutputData() -{ - FontSize = 0.0f; - FallbackAdvanceX = 0.0f; - Glyphs.clear(); - IndexAdvanceX.clear(); - IndexLookup.clear(); - FallbackGlyph = NULL; - ContainerAtlas = NULL; - DirtyLookupTables = true; - Ascent = Descent = 0.0f; - MetricsTotalSurface = 0; -} - -static ImWchar FindFirstExistingGlyph(ImFont* font, const ImWchar* candidate_chars, int candidate_chars_count) -{ - for (int n = 0; n < candidate_chars_count; n++) - if (font->FindGlyphNoFallback(candidate_chars[n]) != NULL) - return candidate_chars[n]; - return (ImWchar)-1; -} - -void ImFont::BuildLookupTable() -{ - int max_codepoint = 0; - for (int i = 0; i != Glyphs.Size; i++) - max_codepoint = ImMax(max_codepoint, (int)Glyphs[i].Codepoint); - - // Build lookup table - IM_ASSERT(Glyphs.Size > 0 && "Font has not loaded glyph!"); - IM_ASSERT(Glyphs.Size < 0xFFFF); // -1 is reserved - IndexAdvanceX.clear(); - IndexLookup.clear(); - DirtyLookupTables = false; - memset(Used4kPagesMap, 0, sizeof(Used4kPagesMap)); - GrowIndex(max_codepoint + 1); - for (int i = 0; i < Glyphs.Size; i++) - { - int codepoint = (int)Glyphs[i].Codepoint; - IndexAdvanceX[codepoint] = Glyphs[i].AdvanceX; - IndexLookup[codepoint] = (ImWchar)i; - - // Mark 4K page as used - const int page_n = codepoint / 4096; - Used4kPagesMap[page_n >> 3] |= 1 << (page_n & 7); - } - - // Create a glyph to handle TAB - // FIXME: Needs proper TAB handling but it needs to be contextualized (or we could arbitrary say that each string starts at "column 0" ?) - if (FindGlyph((ImWchar)' ')) - { - if (Glyphs.back().Codepoint != '\t') // So we can call this function multiple times (FIXME: Flaky) - Glyphs.resize(Glyphs.Size + 1); - ImFontGlyph& tab_glyph = Glyphs.back(); - tab_glyph = *FindGlyph((ImWchar)' '); - tab_glyph.Codepoint = '\t'; - tab_glyph.AdvanceX *= IM_TABSIZE; - IndexAdvanceX[(int)tab_glyph.Codepoint] = (float)tab_glyph.AdvanceX; - IndexLookup[(int)tab_glyph.Codepoint] = (ImWchar)(Glyphs.Size - 1); - } - - // Mark special glyphs as not visible (note that AddGlyph already mark as non-visible glyphs with zero-size polygons) - SetGlyphVisible((ImWchar)' ', false); - SetGlyphVisible((ImWchar)'\t', false); - - // Setup Fallback character - const ImWchar fallback_chars[] = { (ImWchar)IM_UNICODE_CODEPOINT_INVALID, (ImWchar)'?', (ImWchar)' ' }; - FallbackGlyph = FindGlyphNoFallback(FallbackChar); - if (FallbackGlyph == NULL) - { - FallbackChar = FindFirstExistingGlyph(this, fallback_chars, IM_ARRAYSIZE(fallback_chars)); - FallbackGlyph = FindGlyphNoFallback(FallbackChar); - if (FallbackGlyph == NULL) - { - FallbackGlyph = &Glyphs.back(); - FallbackChar = (ImWchar)FallbackGlyph->Codepoint; - } - } - FallbackAdvanceX = FallbackGlyph->AdvanceX; - for (int i = 0; i < max_codepoint + 1; i++) - if (IndexAdvanceX[i] < 0.0f) - IndexAdvanceX[i] = FallbackAdvanceX; - - // Setup Ellipsis character. It is required for rendering elided text. We prefer using U+2026 (horizontal ellipsis). - // However some old fonts may contain ellipsis at U+0085. Here we auto-detect most suitable ellipsis character. - // FIXME: Note that 0x2026 is rarely included in our font ranges. Because of this we are more likely to use three individual dots. - const ImWchar ellipsis_chars[] = { (ImWchar)0x2026, (ImWchar)0x0085 }; - const ImWchar dots_chars[] = { (ImWchar)'.', (ImWchar)0xFF0E }; - if (EllipsisChar == (ImWchar)-1) - EllipsisChar = FindFirstExistingGlyph(this, ellipsis_chars, IM_ARRAYSIZE(ellipsis_chars)); - const ImWchar dot_char = FindFirstExistingGlyph(this, dots_chars, IM_ARRAYSIZE(dots_chars)); - if (EllipsisChar != (ImWchar)-1) - { - EllipsisCharCount = 1; - EllipsisWidth = EllipsisCharStep = FindGlyph(EllipsisChar)->X1; - } - else if (dot_char != (ImWchar)-1) - { - const ImFontGlyph* glyph = FindGlyph(dot_char); - EllipsisChar = dot_char; - EllipsisCharCount = 3; - EllipsisCharStep = (glyph->X1 - glyph->X0) + 1.0f; - EllipsisWidth = EllipsisCharStep * 3.0f - 1.0f; - } -} - -// API is designed this way to avoid exposing the 4K page size -// e.g. use with IsGlyphRangeUnused(0, 255) -bool ImFont::IsGlyphRangeUnused(unsigned int c_begin, unsigned int c_last) -{ - unsigned int page_begin = (c_begin / 4096); - unsigned int page_last = (c_last / 4096); - for (unsigned int page_n = page_begin; page_n <= page_last; page_n++) - if ((page_n >> 3) < sizeof(Used4kPagesMap)) - if (Used4kPagesMap[page_n >> 3] & (1 << (page_n & 7))) - return false; - return true; -} - -void ImFont::SetGlyphVisible(ImWchar c, bool visible) -{ - if (ImFontGlyph* glyph = (ImFontGlyph*)(void*)FindGlyph((ImWchar)c)) - glyph->Visible = visible ? 1 : 0; -} - -void ImFont::GrowIndex(int new_size) -{ - IM_ASSERT(IndexAdvanceX.Size == IndexLookup.Size); - if (new_size <= IndexLookup.Size) - return; - IndexAdvanceX.resize(new_size, -1.0f); - IndexLookup.resize(new_size, (ImWchar)-1); -} - -// x0/y0/x1/y1 are offset from the character upper-left layout position, in pixels. Therefore x0/y0 are often fairly close to zero. -// Not to be mistaken with texture coordinates, which are held by u0/v0/u1/v1 in normalized format (0.0..1.0 on each texture axis). -// 'cfg' is not necessarily == 'this->ConfigData' because multiple source fonts+configs can be used to build one target font. -void ImFont::AddGlyph(const ImFontConfig* cfg, ImWchar codepoint, float x0, float y0, float x1, float y1, float u0, float v0, float u1, float v1, float advance_x) -{ - if (cfg != NULL) - { - // Clamp & recenter if needed - const float advance_x_original = advance_x; - advance_x = ImClamp(advance_x, cfg->GlyphMinAdvanceX, cfg->GlyphMaxAdvanceX); - if (advance_x != advance_x_original) - { - float char_off_x = cfg->PixelSnapH ? ImTrunc((advance_x - advance_x_original) * 0.5f) : (advance_x - advance_x_original) * 0.5f; - x0 += char_off_x; - x1 += char_off_x; - } - - // Snap to pixel - if (cfg->PixelSnapH) - advance_x = IM_ROUND(advance_x); - - // Bake spacing - advance_x += cfg->GlyphExtraSpacing.x; - } - - Glyphs.resize(Glyphs.Size + 1); - ImFontGlyph& glyph = Glyphs.back(); - glyph.Codepoint = (unsigned int)codepoint; - glyph.Visible = (x0 != x1) && (y0 != y1); - glyph.Colored = false; - glyph.X0 = x0; - glyph.Y0 = y0; - glyph.X1 = x1; - glyph.Y1 = y1; - glyph.U0 = u0; - glyph.V0 = v0; - glyph.U1 = u1; - glyph.V1 = v1; - glyph.AdvanceX = advance_x; - - // Compute rough surface usage metrics (+1 to account for average padding, +0.99 to round) - // We use (U1-U0)*TexWidth instead of X1-X0 to account for oversampling. - float pad = ContainerAtlas->TexGlyphPadding + 0.99f; - DirtyLookupTables = true; - MetricsTotalSurface += (int)((glyph.U1 - glyph.U0) * ContainerAtlas->TexWidth + pad) * (int)((glyph.V1 - glyph.V0) * ContainerAtlas->TexHeight + pad); -} - -void ImFont::AddRemapChar(ImWchar dst, ImWchar src, bool overwrite_dst) -{ - IM_ASSERT(IndexLookup.Size > 0); // Currently this can only be called AFTER the font has been built, aka after calling ImFontAtlas::GetTexDataAs*() function. - unsigned int index_size = (unsigned int)IndexLookup.Size; - - if (dst < index_size && IndexLookup.Data[dst] == (ImWchar)-1 && !overwrite_dst) // 'dst' already exists - return; - if (src >= index_size && dst >= index_size) // both 'dst' and 'src' don't exist -> no-op - return; - - GrowIndex(dst + 1); - IndexLookup[dst] = (src < index_size) ? IndexLookup.Data[src] : (ImWchar)-1; - IndexAdvanceX[dst] = (src < index_size) ? IndexAdvanceX.Data[src] : 1.0f; -} - -const ImFontGlyph* ImFont::FindGlyph(ImWchar c) const -{ - if (c >= (size_t)IndexLookup.Size) - return FallbackGlyph; - const ImWchar i = IndexLookup.Data[c]; - if (i == (ImWchar)-1) - return FallbackGlyph; - return &Glyphs.Data[i]; -} - -const ImFontGlyph* ImFont::FindGlyphNoFallback(ImWchar c) const -{ - if (c >= (size_t)IndexLookup.Size) - return NULL; - const ImWchar i = IndexLookup.Data[c]; - if (i == (ImWchar)-1) - return NULL; - return &Glyphs.Data[i]; -} - -// Wrapping skips upcoming blanks -static inline const char* CalcWordWrapNextLineStartA(const char* text, const char* text_end) -{ - while (text < text_end && ImCharIsBlankA(*text)) - text++; - if (*text == '\n') - text++; - return text; -} - -// Simple word-wrapping for English, not full-featured. Please submit failing cases! -// This will return the next location to wrap from. If no wrapping if necessary, this will fast-forward to e.g. text_end. -// FIXME: Much possible improvements (don't cut things like "word !", "word!!!" but cut within "word,,,,", more sensible support for punctuations, support for Unicode punctuations, etc.) -const char* ImFont::CalcWordWrapPositionA(float scale, const char* text, const char* text_end, float wrap_width) const -{ - // For references, possible wrap point marked with ^ - // "aaa bbb, ccc,ddd. eee fff. ggg!" - // ^ ^ ^ ^ ^__ ^ ^ - - // List of hardcoded separators: .,;!?'" - - // Skip extra blanks after a line returns (that includes not counting them in width computation) - // e.g. "Hello world" --> "Hello" "World" - - // Cut words that cannot possibly fit within one line. - // e.g.: "The tropical fish" with ~5 characters worth of width --> "The tr" "opical" "fish" - float line_width = 0.0f; - float word_width = 0.0f; - float blank_width = 0.0f; - wrap_width /= scale; // We work with unscaled widths to avoid scaling every characters - - const char* word_end = text; - const char* prev_word_end = NULL; - bool inside_word = true; - - const char* s = text; - IM_ASSERT(text_end != NULL); - while (s < text_end) - { - unsigned int c = (unsigned int)*s; - const char* next_s; - if (c < 0x80) - next_s = s + 1; - else - next_s = s + ImTextCharFromUtf8(&c, s, text_end); - - if (c < 32) - { - if (c == '\n') - { - line_width = word_width = blank_width = 0.0f; - inside_word = true; - s = next_s; - continue; - } - if (c == '\r') - { - s = next_s; - continue; - } - } - - const float char_width = ((int)c < IndexAdvanceX.Size ? IndexAdvanceX.Data[c] : FallbackAdvanceX); - if (ImCharIsBlankW(c)) - { - if (inside_word) - { - line_width += blank_width; - blank_width = 0.0f; - word_end = s; - } - blank_width += char_width; - inside_word = false; - } - else - { - word_width += char_width; - if (inside_word) - { - word_end = next_s; - } - else - { - prev_word_end = word_end; - line_width += word_width + blank_width; - word_width = blank_width = 0.0f; - } - - // Allow wrapping after punctuation. - inside_word = (c != '.' && c != ',' && c != ';' && c != '!' && c != '?' && c != '\"'); - } - - // We ignore blank width at the end of the line (they can be skipped) - if (line_width + word_width > wrap_width) - { - // Words that cannot possibly fit within an entire line will be cut anywhere. - if (word_width < wrap_width) - s = prev_word_end ? prev_word_end : word_end; - break; - } - - s = next_s; - } - - // Wrap_width is too small to fit anything. Force displaying 1 character to minimize the height discontinuity. - // +1 may not be a character start point in UTF-8 but it's ok because caller loops use (text >= word_wrap_eol). - if (s == text && text < text_end) - return s + 1; - return s; -} - -ImVec2 ImFont::CalcTextSizeA(float size, float max_width, float wrap_width, const char* text_begin, const char* text_end, const char** remaining) const -{ - if (!text_end) - text_end = text_begin + strlen(text_begin); // FIXME-OPT: Need to avoid this. - - const float line_height = size; - const float scale = size / FontSize; - - ImVec2 text_size = ImVec2(0, 0); - float line_width = 0.0f; - - const bool word_wrap_enabled = (wrap_width > 0.0f); - const char* word_wrap_eol = NULL; - - const char* s = text_begin; - while (s < text_end) - { - if (word_wrap_enabled) - { - // Calculate how far we can render. Requires two passes on the string data but keeps the code simple and not intrusive for what's essentially an uncommon feature. - if (!word_wrap_eol) - word_wrap_eol = CalcWordWrapPositionA(scale, s, text_end, wrap_width - line_width); - - if (s >= word_wrap_eol) - { - if (text_size.x < line_width) - text_size.x = line_width; - text_size.y += line_height; - line_width = 0.0f; - word_wrap_eol = NULL; - s = CalcWordWrapNextLineStartA(s, text_end); // Wrapping skips upcoming blanks - continue; - } - } - - // Decode and advance source - const char* prev_s = s; - unsigned int c = (unsigned int)*s; - if (c < 0x80) - s += 1; - else - s += ImTextCharFromUtf8(&c, s, text_end); - - if (c < 32) - { - if (c == '\n') - { - text_size.x = ImMax(text_size.x, line_width); - text_size.y += line_height; - line_width = 0.0f; - continue; - } - if (c == '\r') - continue; - } - - const float char_width = ((int)c < IndexAdvanceX.Size ? IndexAdvanceX.Data[c] : FallbackAdvanceX) * scale; - if (line_width + char_width >= max_width) - { - s = prev_s; - break; - } - - line_width += char_width; - } - - if (text_size.x < line_width) - text_size.x = line_width; - - if (line_width > 0 || text_size.y == 0.0f) - text_size.y += line_height; - - if (remaining) - *remaining = s; - - return text_size; -} - -// Note: as with every ImDrawList drawing function, this expects that the font atlas texture is bound. -void ImFont::RenderChar(ImDrawList* draw_list, float size, const ImVec2& pos, ImU32 col, ImWchar c) const -{ - const ImFontGlyph* glyph = FindGlyph(c); - if (!glyph || !glyph->Visible) - return; - if (glyph->Colored) - col |= ~IM_COL32_A_MASK; - float scale = (size >= 0.0f) ? (size / FontSize) : 1.0f; - float x = IM_TRUNC(pos.x); - float y = IM_TRUNC(pos.y); - draw_list->PrimReserve(6, 4); - draw_list->PrimRectUV(ImVec2(x + glyph->X0 * scale, y + glyph->Y0 * scale), ImVec2(x + glyph->X1 * scale, y + glyph->Y1 * scale), ImVec2(glyph->U0, glyph->V0), ImVec2(glyph->U1, glyph->V1), col); -} - -// Note: as with every ImDrawList drawing function, this expects that the font atlas texture is bound. -void ImFont::RenderText(ImDrawList* draw_list, float size, const ImVec2& pos, ImU32 col, const ImVec4& clip_rect, const char* text_begin, const char* text_end, float wrap_width, bool cpu_fine_clip) const -{ - if (!text_end) - text_end = text_begin + strlen(text_begin); // ImGui:: functions generally already provides a valid text_end, so this is merely to handle direct calls. - - // Align to be pixel perfect - float x = IM_TRUNC(pos.x); - float y = IM_TRUNC(pos.y); - if (y > clip_rect.w) - return; - - const float start_x = x; - const float scale = size / FontSize; - const float line_height = FontSize * scale; - const bool word_wrap_enabled = (wrap_width > 0.0f); - - // Fast-forward to first visible line - const char* s = text_begin; - if (y + line_height < clip_rect.y) - while (y + line_height < clip_rect.y && s < text_end) - { - const char* line_end = (const char*)memchr(s, '\n', text_end - s); - if (word_wrap_enabled) - { - // FIXME-OPT: This is not optimal as do first do a search for \n before calling CalcWordWrapPositionA(). - // If the specs for CalcWordWrapPositionA() were reworked to optionally return on \n we could combine both. - // However it is still better than nothing performing the fast-forward! - s = CalcWordWrapPositionA(scale, s, line_end ? line_end : text_end, wrap_width); - s = CalcWordWrapNextLineStartA(s, text_end); - } - else - { - s = line_end ? line_end + 1 : text_end; - } - y += line_height; - } - - // For large text, scan for the last visible line in order to avoid over-reserving in the call to PrimReserve() - // Note that very large horizontal line will still be affected by the issue (e.g. a one megabyte string buffer without a newline will likely crash atm) - if (text_end - s > 10000 && !word_wrap_enabled) - { - const char* s_end = s; - float y_end = y; - while (y_end < clip_rect.w && s_end < text_end) - { - s_end = (const char*)memchr(s_end, '\n', text_end - s_end); - s_end = s_end ? s_end + 1 : text_end; - y_end += line_height; - } - text_end = s_end; - } - if (s == text_end) - return; - - // Reserve vertices for remaining worse case (over-reserving is useful and easily amortized) - const int vtx_count_max = (int)(text_end - s) * 4; - const int idx_count_max = (int)(text_end - s) * 6; - const int idx_expected_size = draw_list->IdxBuffer.Size + idx_count_max; - draw_list->PrimReserve(idx_count_max, vtx_count_max); - ImDrawVert* vtx_write = draw_list->_VtxWritePtr; - ImDrawIdx* idx_write = draw_list->_IdxWritePtr; - unsigned int vtx_index = draw_list->_VtxCurrentIdx; - - const ImU32 col_untinted = col | ~IM_COL32_A_MASK; - const char* word_wrap_eol = NULL; - - while (s < text_end) - { - if (word_wrap_enabled) - { - // Calculate how far we can render. Requires two passes on the string data but keeps the code simple and not intrusive for what's essentially an uncommon feature. - if (!word_wrap_eol) - word_wrap_eol = CalcWordWrapPositionA(scale, s, text_end, wrap_width - (x - start_x)); - - if (s >= word_wrap_eol) - { - x = start_x; - y += line_height; - word_wrap_eol = NULL; - s = CalcWordWrapNextLineStartA(s, text_end); // Wrapping skips upcoming blanks - continue; - } - } - - // Decode and advance source - unsigned int c = (unsigned int)*s; - if (c < 0x80) - s += 1; - else - s += ImTextCharFromUtf8(&c, s, text_end); - - if (c < 32) - { - if (c == '\n') - { - x = start_x; - y += line_height; - if (y > clip_rect.w) - break; // break out of main loop - continue; - } - if (c == '\r') - continue; - } - - const ImFontGlyph* glyph = FindGlyph((ImWchar)c); - if (glyph == NULL) - continue; - - float char_width = glyph->AdvanceX * scale; - if (glyph->Visible) - { - // We don't do a second finer clipping test on the Y axis as we've already skipped anything before clip_rect.y and exit once we pass clip_rect.w - float x1 = x + glyph->X0 * scale; - float x2 = x + glyph->X1 * scale; - float y1 = y + glyph->Y0 * scale; - float y2 = y + glyph->Y1 * scale; - if (x1 <= clip_rect.z && x2 >= clip_rect.x) - { - // Render a character - float u1 = glyph->U0; - float v1 = glyph->V0; - float u2 = glyph->U1; - float v2 = glyph->V1; - - // CPU side clipping used to fit text in their frame when the frame is too small. Only does clipping for axis aligned quads. - if (cpu_fine_clip) - { - if (x1 < clip_rect.x) - { - u1 = u1 + (1.0f - (x2 - clip_rect.x) / (x2 - x1)) * (u2 - u1); - x1 = clip_rect.x; - } - if (y1 < clip_rect.y) - { - v1 = v1 + (1.0f - (y2 - clip_rect.y) / (y2 - y1)) * (v2 - v1); - y1 = clip_rect.y; - } - if (x2 > clip_rect.z) - { - u2 = u1 + ((clip_rect.z - x1) / (x2 - x1)) * (u2 - u1); - x2 = clip_rect.z; - } - if (y2 > clip_rect.w) - { - v2 = v1 + ((clip_rect.w - y1) / (y2 - y1)) * (v2 - v1); - y2 = clip_rect.w; - } - if (y1 >= y2) - { - x += char_width; - continue; - } - } - - // Support for untinted glyphs - ImU32 glyph_col = glyph->Colored ? col_untinted : col; - - // We are NOT calling PrimRectUV() here because non-inlined causes too much overhead in a debug builds. Inlined here: - { - vtx_write[0].pos.x = x1; vtx_write[0].pos.y = y1; vtx_write[0].col = glyph_col; vtx_write[0].uv.x = u1; vtx_write[0].uv.y = v1; - vtx_write[1].pos.x = x2; vtx_write[1].pos.y = y1; vtx_write[1].col = glyph_col; vtx_write[1].uv.x = u2; vtx_write[1].uv.y = v1; - vtx_write[2].pos.x = x2; vtx_write[2].pos.y = y2; vtx_write[2].col = glyph_col; vtx_write[2].uv.x = u2; vtx_write[2].uv.y = v2; - vtx_write[3].pos.x = x1; vtx_write[3].pos.y = y2; vtx_write[3].col = glyph_col; vtx_write[3].uv.x = u1; vtx_write[3].uv.y = v2; - idx_write[0] = (ImDrawIdx)(vtx_index); idx_write[1] = (ImDrawIdx)(vtx_index + 1); idx_write[2] = (ImDrawIdx)(vtx_index + 2); - idx_write[3] = (ImDrawIdx)(vtx_index); idx_write[4] = (ImDrawIdx)(vtx_index + 2); idx_write[5] = (ImDrawIdx)(vtx_index + 3); - vtx_write += 4; - vtx_index += 4; - idx_write += 6; - } - } - } - x += char_width; - } - - // Give back unused vertices (clipped ones, blanks) ~ this is essentially a PrimUnreserve() action. - draw_list->VtxBuffer.Size = (int)(vtx_write - draw_list->VtxBuffer.Data); // Same as calling shrink() - draw_list->IdxBuffer.Size = (int)(idx_write - draw_list->IdxBuffer.Data); - draw_list->CmdBuffer[draw_list->CmdBuffer.Size - 1].ElemCount -= (idx_expected_size - draw_list->IdxBuffer.Size); - draw_list->_VtxWritePtr = vtx_write; - draw_list->_IdxWritePtr = idx_write; - draw_list->_VtxCurrentIdx = vtx_index; -} - -//----------------------------------------------------------------------------- -// [SECTION] ImGui Internal Render Helpers -//----------------------------------------------------------------------------- -// Vaguely redesigned to stop accessing ImGui global state: -// - RenderArrow() -// - RenderBullet() -// - RenderCheckMark() -// - RenderArrowDockMenu() -// - RenderArrowPointingAt() -// - RenderRectFilledRangeH() -// - RenderRectFilledWithHole() -//----------------------------------------------------------------------------- -// Function in need of a redesign (legacy mess) -// - RenderColorRectWithAlphaCheckerboard() -//----------------------------------------------------------------------------- - -// Render an arrow aimed to be aligned with text (p_min is a position in the same space text would be positioned). To e.g. denote expanded/collapsed state -void ImGui::RenderArrow(ImDrawList* draw_list, ImVec2 pos, ImU32 col, ImGuiDir dir, float scale) -{ - const float h = draw_list->_Data->FontSize * 1.00f; - float r = h * 0.40f * scale; - ImVec2 center = pos + ImVec2(h * 0.50f, h * 0.50f * scale); - - ImVec2 a, b, c; - switch (dir) - { - case ImGuiDir_Up: - case ImGuiDir_Down: - if (dir == ImGuiDir_Up) r = -r; - a = ImVec2(+0.000f, +0.750f) * r; - b = ImVec2(-0.866f, -0.750f) * r; - c = ImVec2(+0.866f, -0.750f) * r; - break; - case ImGuiDir_Left: - case ImGuiDir_Right: - if (dir == ImGuiDir_Left) r = -r; - a = ImVec2(+0.750f, +0.000f) * r; - b = ImVec2(-0.750f, +0.866f) * r; - c = ImVec2(-0.750f, -0.866f) * r; - break; - case ImGuiDir_None: - case ImGuiDir_COUNT: - IM_ASSERT(0); - break; - } - draw_list->AddTriangleFilled(center + a, center + b, center + c, col); -} - -void ImGui::RenderBullet(ImDrawList* draw_list, ImVec2 pos, ImU32 col) -{ - // FIXME-OPT: This should be baked in font. - draw_list->AddCircleFilled(pos, draw_list->_Data->FontSize * 0.20f, col, 8); -} - -void ImGui::RenderCheckMark(ImDrawList* draw_list, ImVec2 pos, ImU32 col, float sz) -{ - float thickness = ImMax(sz / 5.0f, 1.0f); - sz -= thickness * 0.5f; - pos += ImVec2(thickness * 0.25f, thickness * 0.25f); - - float third = sz / 3.0f; - float bx = pos.x + third; - float by = pos.y + sz - third * 0.5f; - draw_list->PathLineTo(ImVec2(bx - third, by - third)); - draw_list->PathLineTo(ImVec2(bx, by)); - draw_list->PathLineTo(ImVec2(bx + third * 2.0f, by - third * 2.0f)); - draw_list->PathStroke(col, 0, thickness); -} - -// Render an arrow. 'pos' is position of the arrow tip. half_sz.x is length from base to tip. half_sz.y is length on each side. -void ImGui::RenderArrowPointingAt(ImDrawList* draw_list, ImVec2 pos, ImVec2 half_sz, ImGuiDir direction, ImU32 col) -{ - switch (direction) - { - case ImGuiDir_Left: draw_list->AddTriangleFilled(ImVec2(pos.x + half_sz.x, pos.y - half_sz.y), ImVec2(pos.x + half_sz.x, pos.y + half_sz.y), pos, col); return; - case ImGuiDir_Right: draw_list->AddTriangleFilled(ImVec2(pos.x - half_sz.x, pos.y + half_sz.y), ImVec2(pos.x - half_sz.x, pos.y - half_sz.y), pos, col); return; - case ImGuiDir_Up: draw_list->AddTriangleFilled(ImVec2(pos.x + half_sz.x, pos.y + half_sz.y), ImVec2(pos.x - half_sz.x, pos.y + half_sz.y), pos, col); return; - case ImGuiDir_Down: draw_list->AddTriangleFilled(ImVec2(pos.x - half_sz.x, pos.y - half_sz.y), ImVec2(pos.x + half_sz.x, pos.y - half_sz.y), pos, col); return; - case ImGuiDir_None: case ImGuiDir_COUNT: break; // Fix warnings - } -} - -// This is less wide than RenderArrow() and we use in dock nodes instead of the regular RenderArrow() to denote a change of functionality, -// and because the saved space means that the left-most tab label can stay at exactly the same position as the label of a loose window. -void ImGui::RenderArrowDockMenu(ImDrawList* draw_list, ImVec2 p_min, float sz, ImU32 col) -{ - draw_list->AddRectFilled(p_min + ImVec2(sz * 0.20f, sz * 0.15f), p_min + ImVec2(sz * 0.80f, sz * 0.30f), col); - RenderArrowPointingAt(draw_list, p_min + ImVec2(sz * 0.50f, sz * 0.85f), ImVec2(sz * 0.30f, sz * 0.40f), ImGuiDir_Down, col); -} - -static inline float ImAcos01(float x) -{ - if (x <= 0.0f) return IM_PI * 0.5f; - if (x >= 1.0f) return 0.0f; - return ImAcos(x); - //return (-0.69813170079773212f * x * x - 0.87266462599716477f) * x + 1.5707963267948966f; // Cheap approximation, may be enough for what we do. -} - -// FIXME: Cleanup and move code to ImDrawList. -void ImGui::RenderRectFilledRangeH(ImDrawList* draw_list, const ImRect& rect, ImU32 col, float x_start_norm, float x_end_norm, float rounding) -{ - if (x_end_norm == x_start_norm) - return; - if (x_start_norm > x_end_norm) - ImSwap(x_start_norm, x_end_norm); - - ImVec2 p0 = ImVec2(ImLerp(rect.Min.x, rect.Max.x, x_start_norm), rect.Min.y); - ImVec2 p1 = ImVec2(ImLerp(rect.Min.x, rect.Max.x, x_end_norm), rect.Max.y); - if (rounding == 0.0f) - { - draw_list->AddRectFilled(p0, p1, col, 0.0f); - return; - } - - rounding = ImClamp(ImMin((rect.Max.x - rect.Min.x) * 0.5f, (rect.Max.y - rect.Min.y) * 0.5f) - 1.0f, 0.0f, rounding); - const float inv_rounding = 1.0f / rounding; - const float arc0_b = ImAcos01(1.0f - (p0.x - rect.Min.x) * inv_rounding); - const float arc0_e = ImAcos01(1.0f - (p1.x - rect.Min.x) * inv_rounding); - const float half_pi = IM_PI * 0.5f; // We will == compare to this because we know this is the exact value ImAcos01 can return. - const float x0 = ImMax(p0.x, rect.Min.x + rounding); - if (arc0_b == arc0_e) - { - draw_list->PathLineTo(ImVec2(x0, p1.y)); - draw_list->PathLineTo(ImVec2(x0, p0.y)); - } - else if (arc0_b == 0.0f && arc0_e == half_pi) - { - draw_list->PathArcToFast(ImVec2(x0, p1.y - rounding), rounding, 3, 6); // BL - draw_list->PathArcToFast(ImVec2(x0, p0.y + rounding), rounding, 6, 9); // TR - } - else - { - draw_list->PathArcTo(ImVec2(x0, p1.y - rounding), rounding, IM_PI - arc0_e, IM_PI - arc0_b, 3); // BL - draw_list->PathArcTo(ImVec2(x0, p0.y + rounding), rounding, IM_PI + arc0_b, IM_PI + arc0_e, 3); // TR - } - if (p1.x > rect.Min.x + rounding) - { - const float arc1_b = ImAcos01(1.0f - (rect.Max.x - p1.x) * inv_rounding); - const float arc1_e = ImAcos01(1.0f - (rect.Max.x - p0.x) * inv_rounding); - const float x1 = ImMin(p1.x, rect.Max.x - rounding); - if (arc1_b == arc1_e) - { - draw_list->PathLineTo(ImVec2(x1, p0.y)); - draw_list->PathLineTo(ImVec2(x1, p1.y)); - } - else if (arc1_b == 0.0f && arc1_e == half_pi) - { - draw_list->PathArcToFast(ImVec2(x1, p0.y + rounding), rounding, 9, 12); // TR - draw_list->PathArcToFast(ImVec2(x1, p1.y - rounding), rounding, 0, 3); // BR - } - else - { - draw_list->PathArcTo(ImVec2(x1, p0.y + rounding), rounding, -arc1_e, -arc1_b, 3); // TR - draw_list->PathArcTo(ImVec2(x1, p1.y - rounding), rounding, +arc1_b, +arc1_e, 3); // BR - } - } - draw_list->PathFillConvex(col); -} - -void ImGui::RenderRectFilledWithHole(ImDrawList* draw_list, const ImRect& outer, const ImRect& inner, ImU32 col, float rounding) -{ - const bool fill_L = (inner.Min.x > outer.Min.x); - const bool fill_R = (inner.Max.x < outer.Max.x); - const bool fill_U = (inner.Min.y > outer.Min.y); - const bool fill_D = (inner.Max.y < outer.Max.y); - if (fill_L) draw_list->AddRectFilled(ImVec2(outer.Min.x, inner.Min.y), ImVec2(inner.Min.x, inner.Max.y), col, rounding, ImDrawFlags_RoundCornersNone | (fill_U ? 0 : ImDrawFlags_RoundCornersTopLeft) | (fill_D ? 0 : ImDrawFlags_RoundCornersBottomLeft)); - if (fill_R) draw_list->AddRectFilled(ImVec2(inner.Max.x, inner.Min.y), ImVec2(outer.Max.x, inner.Max.y), col, rounding, ImDrawFlags_RoundCornersNone | (fill_U ? 0 : ImDrawFlags_RoundCornersTopRight) | (fill_D ? 0 : ImDrawFlags_RoundCornersBottomRight)); - if (fill_U) draw_list->AddRectFilled(ImVec2(inner.Min.x, outer.Min.y), ImVec2(inner.Max.x, inner.Min.y), col, rounding, ImDrawFlags_RoundCornersNone | (fill_L ? 0 : ImDrawFlags_RoundCornersTopLeft) | (fill_R ? 0 : ImDrawFlags_RoundCornersTopRight)); - if (fill_D) draw_list->AddRectFilled(ImVec2(inner.Min.x, inner.Max.y), ImVec2(inner.Max.x, outer.Max.y), col, rounding, ImDrawFlags_RoundCornersNone | (fill_L ? 0 : ImDrawFlags_RoundCornersBottomLeft) | (fill_R ? 0 : ImDrawFlags_RoundCornersBottomRight)); - if (fill_L && fill_U) draw_list->AddRectFilled(ImVec2(outer.Min.x, outer.Min.y), ImVec2(inner.Min.x, inner.Min.y), col, rounding, ImDrawFlags_RoundCornersTopLeft); - if (fill_R && fill_U) draw_list->AddRectFilled(ImVec2(inner.Max.x, outer.Min.y), ImVec2(outer.Max.x, inner.Min.y), col, rounding, ImDrawFlags_RoundCornersTopRight); - if (fill_L && fill_D) draw_list->AddRectFilled(ImVec2(outer.Min.x, inner.Max.y), ImVec2(inner.Min.x, outer.Max.y), col, rounding, ImDrawFlags_RoundCornersBottomLeft); - if (fill_R && fill_D) draw_list->AddRectFilled(ImVec2(inner.Max.x, inner.Max.y), ImVec2(outer.Max.x, outer.Max.y), col, rounding, ImDrawFlags_RoundCornersBottomRight); -} - -ImDrawFlags ImGui::CalcRoundingFlagsForRectInRect(const ImRect& r_in, const ImRect& r_outer, float threshold) -{ - bool round_l = r_in.Min.x <= r_outer.Min.x + threshold; - bool round_r = r_in.Max.x >= r_outer.Max.x - threshold; - bool round_t = r_in.Min.y <= r_outer.Min.y + threshold; - bool round_b = r_in.Max.y >= r_outer.Max.y - threshold; - return ImDrawFlags_RoundCornersNone - | ((round_t && round_l) ? ImDrawFlags_RoundCornersTopLeft : 0) | ((round_t && round_r) ? ImDrawFlags_RoundCornersTopRight : 0) - | ((round_b && round_l) ? ImDrawFlags_RoundCornersBottomLeft : 0) | ((round_b && round_r) ? ImDrawFlags_RoundCornersBottomRight : 0); -} - -// Helper for ColorPicker4() -// NB: This is rather brittle and will show artifact when rounding this enabled if rounded corners overlap multiple cells. Caller currently responsible for avoiding that. -// Spent a non reasonable amount of time trying to getting this right for ColorButton with rounding+anti-aliasing+ImGuiColorEditFlags_HalfAlphaPreview flag + various grid sizes and offsets, and eventually gave up... probably more reasonable to disable rounding altogether. -// FIXME: uses ImGui::GetColorU32 -void ImGui::RenderColorRectWithAlphaCheckerboard(ImDrawList* draw_list, ImVec2 p_min, ImVec2 p_max, ImU32 col, float grid_step, ImVec2 grid_off, float rounding, ImDrawFlags flags) -{ - if ((flags & ImDrawFlags_RoundCornersMask_) == 0) - flags = ImDrawFlags_RoundCornersDefault_; - if (((col & IM_COL32_A_MASK) >> IM_COL32_A_SHIFT) < 0xFF) - { - ImU32 col_bg1 = GetColorU32(ImAlphaBlendColors(IM_COL32(204, 204, 204, 255), col)); - ImU32 col_bg2 = GetColorU32(ImAlphaBlendColors(IM_COL32(128, 128, 128, 255), col)); - draw_list->AddRectFilled(p_min, p_max, col_bg1, rounding, flags); - - int yi = 0; - for (float y = p_min.y + grid_off.y; y < p_max.y; y += grid_step, yi++) - { - float y1 = ImClamp(y, p_min.y, p_max.y), y2 = ImMin(y + grid_step, p_max.y); - if (y2 <= y1) - continue; - for (float x = p_min.x + grid_off.x + (yi & 1) * grid_step; x < p_max.x; x += grid_step * 2.0f) - { - float x1 = ImClamp(x, p_min.x, p_max.x), x2 = ImMin(x + grid_step, p_max.x); - if (x2 <= x1) - continue; - ImDrawFlags cell_flags = ImDrawFlags_RoundCornersNone; - if (y1 <= p_min.y) { if (x1 <= p_min.x) cell_flags |= ImDrawFlags_RoundCornersTopLeft; if (x2 >= p_max.x) cell_flags |= ImDrawFlags_RoundCornersTopRight; } - if (y2 >= p_max.y) { if (x1 <= p_min.x) cell_flags |= ImDrawFlags_RoundCornersBottomLeft; if (x2 >= p_max.x) cell_flags |= ImDrawFlags_RoundCornersBottomRight; } - - // Combine flags - cell_flags = (flags == ImDrawFlags_RoundCornersNone || cell_flags == ImDrawFlags_RoundCornersNone) ? ImDrawFlags_RoundCornersNone : (cell_flags & flags); - draw_list->AddRectFilled(ImVec2(x1, y1), ImVec2(x2, y2), col_bg2, rounding, cell_flags); - } - } - } - else - { - draw_list->AddRectFilled(p_min, p_max, col, rounding, flags); - } -} - -//----------------------------------------------------------------------------- -// [SECTION] Decompression code -//----------------------------------------------------------------------------- -// Compressed with stb_compress() then converted to a C array and encoded as base85. -// Use the program in misc/fonts/binary_to_compressed_c.cpp to create the array from a TTF file. -// The purpose of encoding as base85 instead of "0x00,0x01,..." style is only save on _source code_ size. -// Decompression from stb.h (public domain) by Sean Barrett https://github.com/nothings/stb/blob/master/stb.h -//----------------------------------------------------------------------------- - -static unsigned int stb_decompress_length(const unsigned char *input) -{ - return (input[8] << 24) + (input[9] << 16) + (input[10] << 8) + input[11]; -} - -static unsigned char *stb__barrier_out_e, *stb__barrier_out_b; -static const unsigned char *stb__barrier_in_b; -static unsigned char *stb__dout; -static void stb__match(const unsigned char *data, unsigned int length) -{ - // INVERSE of memmove... write each byte before copying the next... - IM_ASSERT(stb__dout + length <= stb__barrier_out_e); - if (stb__dout + length > stb__barrier_out_e) { stb__dout += length; return; } - if (data < stb__barrier_out_b) { stb__dout = stb__barrier_out_e+1; return; } - while (length--) *stb__dout++ = *data++; -} - -static void stb__lit(const unsigned char *data, unsigned int length) -{ - IM_ASSERT(stb__dout + length <= stb__barrier_out_e); - if (stb__dout + length > stb__barrier_out_e) { stb__dout += length; return; } - if (data < stb__barrier_in_b) { stb__dout = stb__barrier_out_e+1; return; } - memcpy(stb__dout, data, length); - stb__dout += length; -} - -#define stb__in2(x) ((i[x] << 8) + i[(x)+1]) -#define stb__in3(x) ((i[x] << 16) + stb__in2((x)+1)) -#define stb__in4(x) ((i[x] << 24) + stb__in3((x)+1)) - -static const unsigned char *stb_decompress_token(const unsigned char *i) -{ - if (*i >= 0x20) { // use fewer if's for cases that expand small - if (*i >= 0x80) stb__match(stb__dout-i[1]-1, i[0] - 0x80 + 1), i += 2; - else if (*i >= 0x40) stb__match(stb__dout-(stb__in2(0) - 0x4000 + 1), i[2]+1), i += 3; - else /* *i >= 0x20 */ stb__lit(i+1, i[0] - 0x20 + 1), i += 1 + (i[0] - 0x20 + 1); - } else { // more ifs for cases that expand large, since overhead is amortized - if (*i >= 0x18) stb__match(stb__dout-(stb__in3(0) - 0x180000 + 1), i[3]+1), i += 4; - else if (*i >= 0x10) stb__match(stb__dout-(stb__in3(0) - 0x100000 + 1), stb__in2(3)+1), i += 5; - else if (*i >= 0x08) stb__lit(i+2, stb__in2(0) - 0x0800 + 1), i += 2 + (stb__in2(0) - 0x0800 + 1); - else if (*i == 0x07) stb__lit(i+3, stb__in2(1) + 1), i += 3 + (stb__in2(1) + 1); - else if (*i == 0x06) stb__match(stb__dout-(stb__in3(1)+1), i[4]+1), i += 5; - else if (*i == 0x04) stb__match(stb__dout-(stb__in3(1)+1), stb__in2(4)+1), i += 6; - } - return i; -} - -static unsigned int stb_adler32(unsigned int adler32, unsigned char *buffer, unsigned int buflen) -{ - const unsigned long ADLER_MOD = 65521; - unsigned long s1 = adler32 & 0xffff, s2 = adler32 >> 16; - unsigned long blocklen = buflen % 5552; - - unsigned long i; - while (buflen) { - for (i=0; i + 7 < blocklen; i += 8) { - s1 += buffer[0], s2 += s1; - s1 += buffer[1], s2 += s1; - s1 += buffer[2], s2 += s1; - s1 += buffer[3], s2 += s1; - s1 += buffer[4], s2 += s1; - s1 += buffer[5], s2 += s1; - s1 += buffer[6], s2 += s1; - s1 += buffer[7], s2 += s1; - - buffer += 8; - } - - for (; i < blocklen; ++i) - s1 += *buffer++, s2 += s1; - - s1 %= ADLER_MOD, s2 %= ADLER_MOD; - buflen -= blocklen; - blocklen = 5552; - } - return (unsigned int)(s2 << 16) + (unsigned int)s1; -} - -static unsigned int stb_decompress(unsigned char *output, const unsigned char *i, unsigned int /*length*/) -{ - if (stb__in4(0) != 0x57bC0000) return 0; - if (stb__in4(4) != 0) return 0; // error! stream is > 4GB - const unsigned int olen = stb_decompress_length(i); - stb__barrier_in_b = i; - stb__barrier_out_e = output + olen; - stb__barrier_out_b = output; - i += 16; - - stb__dout = output; - for (;;) { - const unsigned char *old_i = i; - i = stb_decompress_token(i); - if (i == old_i) { - if (*i == 0x05 && i[1] == 0xfa) { - IM_ASSERT(stb__dout == output + olen); - if (stb__dout != output + olen) return 0; - if (stb_adler32(1, output, olen) != (unsigned int) stb__in4(2)) - return 0; - return olen; - } else { - IM_ASSERT(0); /* NOTREACHED */ - return 0; - } - } - IM_ASSERT(stb__dout <= output + olen); - if (stb__dout > output + olen) - return 0; - } -} - -//----------------------------------------------------------------------------- -// [SECTION] Default font data (ProggyClean.ttf) -//----------------------------------------------------------------------------- -// ProggyClean.ttf -// Copyright (c) 2004, 2005 Tristan Grimmer -// MIT license (see License.txt in http://www.upperbounds.net/download/ProggyClean.ttf.zip) -// Download and more information at http://upperbounds.net -//----------------------------------------------------------------------------- -// File: 'ProggyClean.ttf' (41208 bytes) -// Exported using misc/fonts/binary_to_compressed_c.cpp (with compression + base85 string encoding). -// The purpose of encoding as base85 instead of "0x00,0x01,..." style is only save on _source code_ size. -//----------------------------------------------------------------------------- -static const char proggy_clean_ttf_compressed_data_base85[11980 + 1] = - "7])#######hV0qs'/###[),##/l:$#Q6>##5[n42>c-TH`->>#/e>11NNV=Bv(*:.F?uu#(gRU.o0XGH`$vhLG1hxt9?W`#,5LsCp#-i>.r$<$6pD>Lb';9Crc6tgXmKVeU2cD4Eo3R/" - "2*>]b(MC;$jPfY.;h^`IWM9Qo#t'X#(v#Y9w0#1D$CIf;W'#pWUPXOuxXuU(H9M(1=Ke$$'5F%)]0^#0X@U.a$FBjVQTSDgEKnIS7EM9>ZY9w0#L;>>#Mx&4Mvt//L[MkA#W@lK.N'[0#7RL_&#w+F%HtG9M#XL`N&.,GM4Pg;--VsM.M0rJfLH2eTM`*oJMHRC`N" - "kfimM2J,W-jXS:)r0wK#@Fge$U>`w'N7G#$#fB#$E^$#:9:hk+eOe--6x)F7*E%?76%^GMHePW-Z5l'&GiF#$956:rS?dA#fiK:)Yr+`�j@'DbG&#^$PG.Ll+DNa&VZ>1i%h1S9u5o@YaaW$e+bROPOpxTO7Stwi1::iB1q)C_=dV26J;2,]7op$]uQr@_V7$q^%lQwtuHY]=DX,n3L#0PHDO4f9>dC@O>HBuKPpP*E,N+b3L#lpR/MrTEH.IAQk.a>D[.e;mc." - "x]Ip.PH^'/aqUO/$1WxLoW0[iLAw=4h(9.`G" - "CRUxHPeR`5Mjol(dUWxZa(>STrPkrJiWx`5U7F#.g*jrohGg`cg:lSTvEY/EV_7H4Q9[Z%cnv;JQYZ5q.l7Zeas:HOIZOB?Ggv:[7MI2k).'2($5FNP&EQ(,)" - "U]W]+fh18.vsai00);D3@4ku5P?DP8aJt+;qUM]=+b'8@;mViBKx0DE[-auGl8:PJ&Dj+M6OC]O^((##]`0i)drT;-7X`=-H3[igUnPG-NZlo.#k@h#=Ork$m>a>$-?Tm$UV(?#P6YY#" - "'/###xe7q.73rI3*pP/$1>s9)W,JrM7SN]'/4C#v$U`0#V.[0>xQsH$fEmPMgY2u7Kh(G%siIfLSoS+MK2eTM$=5,M8p`A.;_R%#u[K#$x4AG8.kK/HSB==-'Ie/QTtG?-.*^N-4B/ZM" - "_3YlQC7(p7q)&](`6_c)$/*JL(L-^(]$wIM`dPtOdGA,U3:w2M-0+WomX2u7lqM2iEumMTcsF?-aT=Z-97UEnXglEn1K-bnEO`gu" - "Ft(c%=;Am_Qs@jLooI&NX;]0#j4#F14;gl8-GQpgwhrq8'=l_f-b49'UOqkLu7-##oDY2L(te+Mch&gLYtJ,MEtJfLh'x'M=$CS-ZZ%P]8bZ>#S?YY#%Q&q'3^Fw&?D)UDNrocM3A76/" - "/oL?#h7gl85[qW/NDOk%16ij;+:1a'iNIdb-ou8.P*w,v5#EI$TWS>Pot-R*H'-SEpA:g)f+O$%%`kA#G=8RMmG1&O`>to8bC]T&$,n.LoO>29sp3dt-52U%VM#q7'DHpg+#Z9%H[Ket`e;)f#Km8&+DC$I46>#Kr]]u-[=99tts1.qb#q72g1WJO81q+eN'03'eM>&1XxY-caEnO" - "j%2n8)),?ILR5^.Ibn<-X-Mq7[a82Lq:F&#ce+S9wsCK*x`569E8ew'He]h:sI[2LM$[guka3ZRd6:t%IG:;$%YiJ:Nq=?eAw;/:nnDq0(CYcMpG)qLN4$##&J-XTt,%OVU4)S1+R-#dg0/Nn?Ku1^0f$B*P:Rowwm-`0PKjYDDM'3]d39VZHEl4,.j']Pk-M.h^&:0FACm$maq-&sgw0t7/6(^xtk%" - "LuH88Fj-ekm>GA#_>568x6(OFRl-IZp`&b,_P'$MhLbxfc$mj`,O;&%W2m`Zh:/)Uetw:aJ%]K9h:TcF]u_-Sj9,VK3M.*'&0D[Ca]J9gp8,kAW]" - "%(?A%R$f<->Zts'^kn=-^@c4%-pY6qI%J%1IGxfLU9CP8cbPlXv);C=b),<2mOvP8up,UVf3839acAWAW-W?#ao/^#%KYo8fRULNd2.>%m]UK:n%r$'sw]J;5pAoO_#2mO3n,'=H5(et" - "Hg*`+RLgv>=4U8guD$I%D:W>-r5V*%j*W:Kvej.Lp$'?;++O'>()jLR-^u68PHm8ZFWe+ej8h:9r6L*0//c&iH&R8pRbA#Kjm%upV1g:" - "a_#Ur7FuA#(tRh#.Y5K+@?3<-8m0$PEn;J:rh6?I6uG<-`wMU'ircp0LaE_OtlMb&1#6T.#FDKu#1Lw%u%+GM+X'e?YLfjM[VO0MbuFp7;>Q&#WIo)0@F%q7c#4XAXN-U&VBpqB>0ie&jhZ[?iLR@@_AvA-iQC(=ksRZRVp7`.=+NpBC%rh&3]R:8XDmE5^V8O(x<-+k?'(^](H.aREZSi,#1:[IXaZFOm<-ui#qUq2$##Ri;u75OK#(RtaW-K-F`S+cF]uN`-KMQ%rP/Xri.LRcB##=YL3BgM/3M" - "D?@f&1'BW-)Ju#bmmWCMkk&#TR`C,5d>g)F;t,4:@_l8G/5h4vUd%&%950:VXD'QdWoY-F$BtUwmfe$YqL'8(PWX(" - "P?^@Po3$##`MSs?DWBZ/S>+4%>fX,VWv/w'KD`LP5IbH;rTV>n3cEK8U#bX]l-/V+^lj3;vlMb&[5YQ8#pekX9JP3XUC72L,,?+Ni&co7ApnO*5NK,((W-i:$,kp'UDAO(G0Sq7MVjJs" - "bIu)'Z,*[>br5fX^:FPAWr-m2KgLQ_nN6'8uTGT5g)uLv:873UpTLgH+#FgpH'_o1780Ph8KmxQJ8#H72L4@768@Tm&Q" - "h4CB/5OvmA&,Q&QbUoi$a_%3M01H)4x7I^&KQVgtFnV+;[Pc>[m4k//,]1?#`VY[Jr*3&&slRfLiVZJ:]?=K3Sw=[$=uRB?3xk48@aege0jT6'N#(q%.O=?2S]u*(m<-" - "V8J'(1)G][68hW$5'q[GC&5j`TE?m'esFGNRM)j,ffZ?-qx8;->g4t*:CIP/[Qap7/9'#(1sao7w-.qNUdkJ)tCF&#B^;xGvn2r9FEPFFFcL@.iFNkTve$m%#QvQS8U@)2Z+3K:AKM5i" - "sZ88+dKQ)W6>J%CL`.d*(B`-n8D9oK-XV1q['-5k'cAZ69e;D_?$ZPP&s^+7])$*$#@QYi9,5P r+$%CE=68>K8r0=dSC%%(@p7" - ".m7jilQ02'0-VWAgTlGW'b)Tq7VT9q^*^$$.:&N@@" - "$&)WHtPm*5_rO0&e%K&#-30j(E4#'Zb.o/(Tpm$>K'f@[PvFl,hfINTNU6u'0pao7%XUp9]5.>%h`8_=VYbxuel.NTSsJfLacFu3B'lQSu/m6-Oqem8T+oE--$0a/k]uj9EwsG>%veR*" - "hv^BFpQj:K'#SJ,sB-'#](j.Lg92rTw-*n%@/;39rrJF,l#qV%OrtBeC6/,;qB3ebNW[?,Hqj2L.1NP&GjUR=1D8QaS3Up&@*9wP?+lo7b?@%'k4`p0Z$22%K3+iCZj?XJN4Nm&+YF]u" - "@-W$U%VEQ/,,>>#)D#%8cY#YZ?=,`Wdxu/ae&#" - "w6)R89tI#6@s'(6Bf7a&?S=^ZI_kS&ai`&=tE72L_D,;^R)7[$so8lKN%5/$(vdfq7+ebA#" - "u1p]ovUKW&Y%q]'>$1@-[xfn$7ZTp7mM,G,Ko7a&Gu%G[RMxJs[0MM%wci.LFDK)(%:_i2B5CsR8&9Z&#=mPEnm0f`<&c)QL5uJ#%u%lJj+D-r;BoFDoS97h5g)E#o:&S4weDF,9^Hoe`h*L+_a*NrLW-1pG_&2UdB8" - "6e%B/:=>)N4xeW.*wft-;$'58-ESqr#U`'6AQ]m&6/`Z>#S?YY#Vc;r7U2&326d=w&H####?TZ`*4?&.MK?LP8Vxg>$[QXc%QJv92.(Db*B)gb*BM9dM*hJMAo*c&#" - "b0v=Pjer]$gG&JXDf->'StvU7505l9$AFvgYRI^&<^b68?j#q9QX4SM'RO#&sL1IM.rJfLUAj221]d##DW=m83u5;'bYx,*Sl0hL(W;;$doB&O/TQ:(Z^xBdLjLV#*8U_72Lh+2Q8Cj0i:6hp&$C/:p(HK>T8Y[gHQ4`4)'$Ab(Nof%V'8hL&#SfD07&6D@M.*J:;$-rv29'M]8qMv-tLp,'886iaC=Hb*YJoKJ,(j%K=H`K.v9HggqBIiZu'QvBT.#=)0ukruV&.)3=(^1`o*Pj4<-#MJ+gLq9-##@HuZPN0]u:h7.T..G:;$/Usj(T7`Q8tT72LnYl<-qx8;-HV7Q-&Xdx%1a,hC=0u+HlsV>nuIQL-5" - "_>@kXQtMacfD.m-VAb8;IReM3$wf0''hra*so568'Ip&vRs849'MRYSp%:t:h5qSgwpEr$B>Q,;s(C#$)`svQuF$##-D,##,g68@2[T;.XSdN9Qe)rpt._K-#5wF)sP'##p#C0c%-Gb%" - "hd+<-j'Ai*x&&HMkT]C'OSl##5RG[JXaHN;d'uA#x._U;.`PU@(Z3dt4r152@:v,'R.Sj'w#0<-;kPI)FfJ&#AYJ&#//)>-k=m=*XnK$>=)72L]0I%>.G690a:$##<,);?;72#?x9+d;" - "^V'9;jY@;)br#q^YQpx:X#Te$Z^'=-=bGhLf:D6&bNwZ9-ZD#n^9HhLMr5G;']d&6'wYmTFmLq9wI>P(9mI[>kC-ekLC/R&CH+s'B;K-M6$EB%is00:" - "+A4[7xks.LrNk0&E)wILYF@2L'0Nb$+pv<(2.768/FrY&h$^3i&@+G%JT'<-,v`3;_)I9M^AE]CN?Cl2AZg+%4iTpT3$U4O]GKx'm9)b@p7YsvK3w^YR-" - "CdQ*:Ir<($u&)#(&?L9Rg3H)4fiEp^iI9O8KnTj,]H?D*r7'M;PwZ9K0E^k&-cpI;.p/6_vwoFMV<->#%Xi.LxVnrU(4&8/P+:hLSKj$#U%]49t'I:rgMi'FL@a:0Y-uA[39',(vbma*" - "hU%<-SRF`Tt:542R_VV$p@[p8DV[A,?1839FWdFTi1O*H&#(AL8[_P%.M>v^-))qOT*F5Cq0`Ye%+$B6i:7@0IXSsDiWP,##P`%/L-" - "S(qw%sf/@%#B6;/U7K]uZbi^Oc^2n%t<)'mEVE''n`WnJra$^TKvX5B>;_aSEK',(hwa0:i4G?.Bci.(X[?b*($,=-n<.Q%`(X=?+@Am*Js0&=3bh8K]mL69=Lb,OcZV/);TTm8VI;?%OtJ<(b4mq7M6:u?KRdFl*:xP?Yb.5)%w_I?7uk5JC+FS(m#i'k.'a0i)9<7b'fs'59hq$*5Uhv##pi^8+hIEBF`nvo`;'l0.^S1<-wUK2/Coh58KKhLj" - "M=SO*rfO`+qC`W-On.=AJ56>>i2@2LH6A:&5q`?9I3@@'04&p2/LVa*T-4<-i3;M9UvZd+N7>b*eIwg:CC)c<>nO&#$(>.Z-I&J(Q0Hd5Q%7Co-b`-cP)hI;*_F]u`Rb[.j8_Q/<&>uu+VsH$sM9TA%?)(vmJ80),P7E>)tjD%2L=-t#fK[%`v=Q8WlA2);Sa" - ">gXm8YB`1d@K#n]76-a$U,mF%Ul:#/'xoFM9QX-$.QN'>" - "[%$Z$uF6pA6Ki2O5:8w*vP1<-1`[G,)-m#>0`P&#eb#.3i)rtB61(o'$?X3B2Qft^ae_5tKL9MUe9b*sLEQ95C&`=G?@Mj=wh*'3E>=-<)Gt*Iw)'QG:`@I" - "wOf7&]1i'S01B+Ev/Nac#9S;=;YQpg_6U`*kVY39xK,[/6Aj7:'1Bm-_1EYfa1+o&o4hp7KN_Q(OlIo@S%;jVdn0'1h19w,WQhLI)3S#f$2(eb,jr*b;3Vw]*7NH%$c4Vs,eD9>XW8?N]o+(*pgC%/72LV-uW%iewS8W6m2rtCpo'RS1R84=@paTKt)>=%&1[)*vp'u+x,VrwN;&]kuO9JDbg=pO$J*.jVe;u'm0dr9l,<*wMK*Oe=g8lV_KEBFkO'oU]^=[-792#ok,)" - "i]lR8qQ2oA8wcRCZ^7w/Njh;?.stX?Q1>S1q4Bn$)K1<-rGdO'$Wr.Lc.CG)$/*JL4tNR/,SVO3,aUw'DJN:)Ss;wGn9A32ijw%FL+Z0Fn.U9;reSq)bmI32U==5ALuG&#Vf1398/pVo" - "1*c-(aY168o<`JsSbk-,1N;$>0:OUas(3:8Z972LSfF8eb=c-;>SPw7.6hn3m`9^Xkn(r.qS[0;T%&Qc=+STRxX'q1BNk3&*eu2;&8q$&x>Q#Q7^Tf+6<(d%ZVmj2bDi%.3L2n+4W'$P" - "iDDG)g,r%+?,$@?uou5tSe2aN_AQU*'IAO" - "URQ##V^Fv-XFbGM7Fl(N<3DhLGF%q.1rC$#:T__&Pi68%0xi_&[qFJ(77j_&JWoF.V735&T,[R*:xFR*K5>>#`bW-?4Ne_&6Ne_&6Ne_&n`kr-#GJcM6X;uM6X;uM(.a..^2TkL%oR(#" - ";u.T%fAr%4tJ8&><1=GHZ_+m9/#H1F^R#SC#*N=BA9(D?v[UiFY>>^8p,KKF.W]L29uLkLlu/+4T" - "w$)F./^n3+rlo+DB;5sIYGNk+i1t-69Jg--0pao7Sm#K)pdHW&;LuDNH@H>#/X-TI(;P>#,Gc>#0Su>#4`1?#8lC?#xL$#B.`$#F:r$#JF.%#NR@%#R_R%#Vke%#Zww%#_-4^Rh%Sflr-k'MS.o?.5/sWel/wpEM0%3'/1)K^f1-d>G21&v(35>V`39V7A4=onx4" - "A1OY5EI0;6Ibgr6M$HS7Q<)58C5w,;WoA*#[%T*#`1g*#d=#+#hI5+#lUG+#pbY+#tnl+#x$),#&1;,#*=M,#.I`,#2Ur,#6b.-#;w[H#iQtA#m^0B#qjBB#uvTB##-hB#'9$C#+E6C#" - "/QHC#3^ZC#7jmC#;v)D#?,)4kMYD4lVu`4m`:&5niUA5@(A5BA1]PBB:xlBCC=2CDLXMCEUtiCf&0g2'tN?PGT4CPGT4CPGT4CPGT4CPGT4CPGT4CPGT4CP" - "GT4CPGT4CPGT4CPGT4CPGT4CPGT4CP-qekC`.9kEg^+F$kwViFJTB&5KTB&5KTB&5KTB&5KTB&5KTB&5KTB&5KTB&5KTB&5KTB&5KTB&5KTB&5KTB&5KTB&5KTB&5o,^<-28ZI'O?;xp" - "O?;xpO?;xpO?;xpO?;xpO?;xpO?;xpO?;xpO?;xpO?;xpO?;xpO?;xpO?;xpO?;xp;7q-#lLYI:xvD=#"; - -static const char* GetDefaultCompressedFontDataTTFBase85() -{ - return proggy_clean_ttf_compressed_data_base85; -} - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/imgui_internal.h b/app/jni/src/libultraship/extern/ImGui/imgui_internal.h deleted file mode 100644 index a488cdf..0000000 --- a/app/jni/src/libultraship/extern/ImGui/imgui_internal.h +++ /dev/null @@ -1,3785 +0,0 @@ -// dear imgui, v1.90 WIP -// (internal structures/api) - -// You may use this file to debug, understand or extend Dear ImGui features but we don't provide any guarantee of forward compatibility. - -/* - -Index of this file: - -// [SECTION] Header mess -// [SECTION] Forward declarations -// [SECTION] Context pointer -// [SECTION] STB libraries includes -// [SECTION] Macros -// [SECTION] Generic helpers -// [SECTION] ImDrawList support -// [SECTION] Widgets support: flags, enums, data structures -// [SECTION] Inputs support -// [SECTION] Clipper support -// [SECTION] Navigation support -// [SECTION] Typing-select support -// [SECTION] Columns support -// [SECTION] Multi-select support -// [SECTION] Docking support -// [SECTION] Viewport support -// [SECTION] Settings support -// [SECTION] Localization support -// [SECTION] Metrics, Debug tools -// [SECTION] Generic context hooks -// [SECTION] ImGuiContext (main imgui context) -// [SECTION] ImGuiWindowTempData, ImGuiWindow -// [SECTION] Tab bar, Tab item support -// [SECTION] Table support -// [SECTION] ImGui internal API -// [SECTION] ImFontAtlas internal API -// [SECTION] Test Engine specific hooks (imgui_test_engine) - -*/ - -#pragma once -#ifndef IMGUI_DISABLE - -//----------------------------------------------------------------------------- -// [SECTION] Header mess -//----------------------------------------------------------------------------- - -#ifndef IMGUI_VERSION -#include "imgui.h" -#endif - -#include // FILE*, sscanf -#include // NULL, malloc, free, qsort, atoi, atof -#include // sqrtf, fabsf, fmodf, powf, floorf, ceilf, cosf, sinf -#include // INT_MIN, INT_MAX - -// Enable SSE intrinsics if available -#if (defined __SSE__ || defined __x86_64__ || defined _M_X64 || (defined(_M_IX86_FP) && (_M_IX86_FP >= 1))) && !defined(IMGUI_DISABLE_SSE) -#define IMGUI_ENABLE_SSE -#include -#endif - -// Visual Studio warnings -#ifdef _MSC_VER -#pragma warning (push) -#pragma warning (disable: 4251) // class 'xxx' needs to have dll-interface to be used by clients of struct 'xxx' // when IMGUI_API is set to__declspec(dllexport) -#pragma warning (disable: 26812) // The enum type 'xxx' is unscoped. Prefer 'enum class' over 'enum' (Enum.3). [MSVC Static Analyzer) -#pragma warning (disable: 26495) // [Static Analyzer] Variable 'XXX' is uninitialized. Always initialize a member variable (type.6). -#if defined(_MSC_VER) && _MSC_VER >= 1922 // MSVC 2019 16.2 or later -#pragma warning (disable: 5054) // operator '|': deprecated between enumerations of different types -#endif -#endif - -// Clang/GCC warnings with -Weverything -#if defined(__clang__) -#pragma clang diagnostic push -#if __has_warning("-Wunknown-warning-option") -#pragma clang diagnostic ignored "-Wunknown-warning-option" // warning: unknown warning group 'xxx' -#endif -#pragma clang diagnostic ignored "-Wunknown-pragmas" // warning: unknown warning group 'xxx' -#pragma clang diagnostic ignored "-Wfloat-equal" // warning: comparing floating point with == or != is unsafe // storing and comparing against same constants ok, for ImFloor() -#pragma clang diagnostic ignored "-Wunused-function" // for stb_textedit.h -#pragma clang diagnostic ignored "-Wmissing-prototypes" // for stb_textedit.h -#pragma clang diagnostic ignored "-Wold-style-cast" -#pragma clang diagnostic ignored "-Wzero-as-null-pointer-constant" -#pragma clang diagnostic ignored "-Wdouble-promotion" -#pragma clang diagnostic ignored "-Wimplicit-int-float-conversion" // warning: implicit conversion from 'xxx' to 'float' may lose precision -#pragma clang diagnostic ignored "-Wmissing-noreturn" // warning: function 'xxx' could be declared with attribute 'noreturn' -#elif defined(__GNUC__) -#pragma GCC diagnostic push -#pragma GCC diagnostic ignored "-Wpragmas" // warning: unknown option after '#pragma GCC diagnostic' kind -#pragma GCC diagnostic ignored "-Wclass-memaccess" // [__GNUC__ >= 8] warning: 'memset/memcpy' clearing/writing an object of type 'xxxx' with no trivial copy-assignment; use assignment or value-initialization instead -#endif - -// Legacy defines -#ifdef IMGUI_DISABLE_FORMAT_STRING_FUNCTIONS // Renamed in 1.74 -#error Use IMGUI_DISABLE_DEFAULT_FORMAT_FUNCTIONS -#endif -#ifdef IMGUI_DISABLE_MATH_FUNCTIONS // Renamed in 1.74 -#error Use IMGUI_DISABLE_DEFAULT_MATH_FUNCTIONS -#endif - -// Enable stb_truetype by default unless FreeType is enabled. -// You can compile with both by defining both IMGUI_ENABLE_FREETYPE and IMGUI_ENABLE_STB_TRUETYPE together. -#ifndef IMGUI_ENABLE_FREETYPE -#define IMGUI_ENABLE_STB_TRUETYPE -#endif - -//----------------------------------------------------------------------------- -// [SECTION] Forward declarations -//----------------------------------------------------------------------------- - -struct ImBitVector; // Store 1-bit per value -struct ImRect; // An axis-aligned rectangle (2 points) -struct ImDrawDataBuilder; // Helper to build a ImDrawData instance -struct ImDrawListSharedData; // Data shared between all ImDrawList instances -struct ImGuiColorMod; // Stacked color modifier, backup of modified data so we can restore it -struct ImGuiContext; // Main Dear ImGui context -struct ImGuiContextHook; // Hook for extensions like ImGuiTestEngine -struct ImGuiDataVarInfo; // Variable information (e.g. to avoid style variables from an enum) -struct ImGuiDataTypeInfo; // Type information associated to a ImGuiDataType enum -struct ImGuiDockContext; // Docking system context -struct ImGuiDockRequest; // Docking system dock/undock queued request -struct ImGuiDockNode; // Docking system node (hold a list of Windows OR two child dock nodes) -struct ImGuiDockNodeSettings; // Storage for a dock node in .ini file (we preserve those even if the associated dock node isn't active during the session) -struct ImGuiGroupData; // Stacked storage data for BeginGroup()/EndGroup() -struct ImGuiInputTextState; // Internal state of the currently focused/edited text input box -struct ImGuiInputTextDeactivateData;// Short term storage to backup text of a deactivating InputText() while another is stealing active id -struct ImGuiLastItemData; // Status storage for last submitted items -struct ImGuiLocEntry; // A localization entry. -struct ImGuiMenuColumns; // Simple column measurement, currently used for MenuItem() only -struct ImGuiNavItemData; // Result of a gamepad/keyboard directional navigation move query result -struct ImGuiNavTreeNodeData; // Temporary storage for last TreeNode() being a Left arrow landing candidate. -struct ImGuiMetricsConfig; // Storage for ShowMetricsWindow() and DebugNodeXXX() functions -struct ImGuiNextWindowData; // Storage for SetNextWindow** functions -struct ImGuiNextItemData; // Storage for SetNextItem** functions -struct ImGuiOldColumnData; // Storage data for a single column for legacy Columns() api -struct ImGuiOldColumns; // Storage data for a columns set for legacy Columns() api -struct ImGuiPopupData; // Storage for current popup stack -struct ImGuiSettingsHandler; // Storage for one type registered in the .ini file -struct ImGuiStackSizes; // Storage of stack sizes for debugging/asserting -struct ImGuiStyleMod; // Stacked style modifier, backup of modified data so we can restore it -struct ImGuiTabBar; // Storage for a tab bar -struct ImGuiTabItem; // Storage for a tab item (within a tab bar) -struct ImGuiTable; // Storage for a table -struct ImGuiTableColumn; // Storage for one column of a table -struct ImGuiTableInstanceData; // Storage for one instance of a same table -struct ImGuiTableTempData; // Temporary storage for one table (one per table in the stack), shared between tables. -struct ImGuiTableSettings; // Storage for a table .ini settings -struct ImGuiTableColumnsSettings; // Storage for a column .ini settings -struct ImGuiTypingSelectState; // Storage for GetTypingSelectRequest() -struct ImGuiTypingSelectRequest; // Storage for GetTypingSelectRequest() (aimed to be public) -struct ImGuiWindow; // Storage for one window -struct ImGuiWindowTempData; // Temporary storage for one window (that's the data which in theory we could ditch at the end of the frame, in practice we currently keep it for each window) -struct ImGuiWindowSettings; // Storage for a window .ini settings (we keep one of those even if the actual window wasn't instanced during this session) - -// Enumerations -// Use your programming IDE "Go to definition" facility on the names of the center columns to find the actual flags/enum lists. -enum ImGuiLocKey : int; // -> enum ImGuiLocKey // Enum: a localization entry for translation. -typedef int ImGuiDataAuthority; // -> enum ImGuiDataAuthority_ // Enum: for storing the source authority (dock node vs window) of a field -typedef int ImGuiLayoutType; // -> enum ImGuiLayoutType_ // Enum: Horizontal or vertical - -// Flags -typedef int ImGuiActivateFlags; // -> enum ImGuiActivateFlags_ // Flags: for navigation/focus function (will be for ActivateItem() later) -typedef int ImGuiDebugLogFlags; // -> enum ImGuiDebugLogFlags_ // Flags: for ShowDebugLogWindow(), g.DebugLogFlags -typedef int ImGuiFocusRequestFlags; // -> enum ImGuiFocusRequestFlags_ // Flags: for FocusWindow(); -typedef int ImGuiInputFlags; // -> enum ImGuiInputFlags_ // Flags: for IsKeyPressed(), IsMouseClicked(), SetKeyOwner(), SetItemKeyOwner() etc. -typedef int ImGuiItemFlags; // -> enum ImGuiItemFlags_ // Flags: for PushItemFlag(), g.LastItemData.InFlags -typedef int ImGuiItemStatusFlags; // -> enum ImGuiItemStatusFlags_ // Flags: for g.LastItemData.StatusFlags -typedef int ImGuiOldColumnFlags; // -> enum ImGuiOldColumnFlags_ // Flags: for BeginColumns() -typedef int ImGuiNavHighlightFlags; // -> enum ImGuiNavHighlightFlags_ // Flags: for RenderNavHighlight() -typedef int ImGuiNavMoveFlags; // -> enum ImGuiNavMoveFlags_ // Flags: for navigation requests -typedef int ImGuiNextItemDataFlags; // -> enum ImGuiNextItemDataFlags_ // Flags: for SetNextItemXXX() functions -typedef int ImGuiNextWindowDataFlags; // -> enum ImGuiNextWindowDataFlags_// Flags: for SetNextWindowXXX() functions -typedef int ImGuiScrollFlags; // -> enum ImGuiScrollFlags_ // Flags: for ScrollToItem() and navigation requests -typedef int ImGuiSeparatorFlags; // -> enum ImGuiSeparatorFlags_ // Flags: for SeparatorEx() -typedef int ImGuiTextFlags; // -> enum ImGuiTextFlags_ // Flags: for TextEx() -typedef int ImGuiTooltipFlags; // -> enum ImGuiTooltipFlags_ // Flags: for BeginTooltipEx() -typedef int ImGuiTypingSelectFlags; // -> enum ImGuiTypingSelectFlags_ // Flags: for GetTypingSelectRequest() - -typedef void (*ImGuiErrorLogCallback)(void* user_data, const char* fmt, ...); - -//----------------------------------------------------------------------------- -// [SECTION] Context pointer -// See implementation of this variable in imgui.cpp for comments and details. -//----------------------------------------------------------------------------- - -#ifndef GImGui -extern IMGUI_API ImGuiContext* GImGui; // Current implicit context pointer -#endif - -//------------------------------------------------------------------------- -// [SECTION] STB libraries includes -//------------------------------------------------------------------------- - -namespace ImStb -{ - -#undef STB_TEXTEDIT_STRING -#undef STB_TEXTEDIT_CHARTYPE -#define STB_TEXTEDIT_STRING ImGuiInputTextState -#define STB_TEXTEDIT_CHARTYPE ImWchar -#define STB_TEXTEDIT_GETWIDTH_NEWLINE (-1.0f) -#define STB_TEXTEDIT_UNDOSTATECOUNT 99 -#define STB_TEXTEDIT_UNDOCHARCOUNT 999 -#include "imstb_textedit.h" - -} // namespace ImStb - -//----------------------------------------------------------------------------- -// [SECTION] Macros -//----------------------------------------------------------------------------- - -// Internal Drag and Drop payload types. String starting with '_' are reserved for Dear ImGui. -#define IMGUI_PAYLOAD_TYPE_WINDOW "_IMWINDOW" // Payload == ImGuiWindow* - -// Debug Printing Into TTY -// (since IMGUI_VERSION_NUM >= 18729: IMGUI_DEBUG_LOG was reworked into IMGUI_DEBUG_PRINTF (and removed framecount from it). If you were using a #define IMGUI_DEBUG_LOG please rename) -#ifndef IMGUI_DEBUG_PRINTF -#ifndef IMGUI_DISABLE_DEFAULT_FORMAT_FUNCTIONS -#define IMGUI_DEBUG_PRINTF(_FMT,...) printf(_FMT, __VA_ARGS__) -#else -#define IMGUI_DEBUG_PRINTF(_FMT,...) ((void)0) -#endif -#endif - -// Debug Logging for ShowDebugLogWindow(). This is designed for relatively rare events so please don't spam. -#ifndef IMGUI_DISABLE_DEBUG_TOOLS -#define IMGUI_DEBUG_LOG(...) ImGui::DebugLog(__VA_ARGS__) -#else -#define IMGUI_DEBUG_LOG(...) ((void)0) -#endif -#define IMGUI_DEBUG_LOG_ACTIVEID(...) do { if (g.DebugLogFlags & ImGuiDebugLogFlags_EventActiveId) IMGUI_DEBUG_LOG(__VA_ARGS__); } while (0) -#define IMGUI_DEBUG_LOG_FOCUS(...) do { if (g.DebugLogFlags & ImGuiDebugLogFlags_EventFocus) IMGUI_DEBUG_LOG(__VA_ARGS__); } while (0) -#define IMGUI_DEBUG_LOG_POPUP(...) do { if (g.DebugLogFlags & ImGuiDebugLogFlags_EventPopup) IMGUI_DEBUG_LOG(__VA_ARGS__); } while (0) -#define IMGUI_DEBUG_LOG_NAV(...) do { if (g.DebugLogFlags & ImGuiDebugLogFlags_EventNav) IMGUI_DEBUG_LOG(__VA_ARGS__); } while (0) -#define IMGUI_DEBUG_LOG_SELECTION(...) do { if (g.DebugLogFlags & ImGuiDebugLogFlags_EventSelection)IMGUI_DEBUG_LOG(__VA_ARGS__); } while (0) -#define IMGUI_DEBUG_LOG_CLIPPER(...) do { if (g.DebugLogFlags & ImGuiDebugLogFlags_EventClipper) IMGUI_DEBUG_LOG(__VA_ARGS__); } while (0) -#define IMGUI_DEBUG_LOG_IO(...) do { if (g.DebugLogFlags & ImGuiDebugLogFlags_EventIO) IMGUI_DEBUG_LOG(__VA_ARGS__); } while (0) -#define IMGUI_DEBUG_LOG_DOCKING(...) do { if (g.DebugLogFlags & ImGuiDebugLogFlags_EventDocking) IMGUI_DEBUG_LOG(__VA_ARGS__); } while (0) -#define IMGUI_DEBUG_LOG_VIEWPORT(...) do { if (g.DebugLogFlags & ImGuiDebugLogFlags_EventViewport) IMGUI_DEBUG_LOG(__VA_ARGS__); } while (0) - -// Static Asserts -#define IM_STATIC_ASSERT(_COND) static_assert(_COND, "") - -// "Paranoid" Debug Asserts are meant to only be enabled during specific debugging/work, otherwise would slow down the code too much. -// We currently don't have many of those so the effect is currently negligible, but onward intent to add more aggressive ones in the code. -//#define IMGUI_DEBUG_PARANOID -#ifdef IMGUI_DEBUG_PARANOID -#define IM_ASSERT_PARANOID(_EXPR) IM_ASSERT(_EXPR) -#else -#define IM_ASSERT_PARANOID(_EXPR) -#endif - -// Error handling -// Down the line in some frameworks/languages we would like to have a way to redirect those to the programmer and recover from more faults. -#ifndef IM_ASSERT_USER_ERROR -#define IM_ASSERT_USER_ERROR(_EXP,_MSG) IM_ASSERT((_EXP) && _MSG) // Recoverable User Error -#endif - -// Misc Macros -#define IM_PI 3.14159265358979323846f -#ifdef _WIN32 -#define IM_NEWLINE "\r\n" // Play it nice with Windows users (Update: since 2018-05, Notepad finally appears to support Unix-style carriage returns!) -#else -#define IM_NEWLINE "\n" -#endif -#ifndef IM_TABSIZE // Until we move this to runtime and/or add proper tab support, at least allow users to compile-time override -#define IM_TABSIZE (4) -#endif -#define IM_MEMALIGN(_OFF,_ALIGN) (((_OFF) + ((_ALIGN) - 1)) & ~((_ALIGN) - 1)) // Memory align e.g. IM_ALIGN(0,4)=0, IM_ALIGN(1,4)=4, IM_ALIGN(4,4)=4, IM_ALIGN(5,4)=8 -#define IM_F32_TO_INT8_UNBOUND(_VAL) ((int)((_VAL) * 255.0f + ((_VAL)>=0 ? 0.5f : -0.5f))) // Unsaturated, for display purpose -#define IM_F32_TO_INT8_SAT(_VAL) ((int)(ImSaturate(_VAL) * 255.0f + 0.5f)) // Saturated, always output 0..255 -#define IM_TRUNC(_VAL) ((float)(int)(_VAL)) // ImTrunc() is not inlined in MSVC debug builds -#define IM_ROUND(_VAL) ((float)(int)((_VAL) + 0.5f)) // -#define IM_STRINGIFY_HELPER(_X) #_X -#define IM_STRINGIFY(_X) IM_STRINGIFY_HELPER(_X) // Preprocessor idiom to stringify e.g. an integer. -#ifndef IMGUI_DISABLE_OBSOLETE_FUNCTIONS -#define IM_FLOOR IM_TRUNC -#endif - -// Enforce cdecl calling convention for functions called by the standard library, in case compilation settings changed the default to e.g. __vectorcall -#ifdef _MSC_VER -#define IMGUI_CDECL __cdecl -#else -#define IMGUI_CDECL -#endif - -// Warnings -#if defined(_MSC_VER) && !defined(__clang__) -#define IM_MSVC_WARNING_SUPPRESS(XXXX) __pragma(warning(suppress: XXXX)) -#else -#define IM_MSVC_WARNING_SUPPRESS(XXXX) -#endif - -// Debug Tools -// Use 'Metrics/Debugger->Tools->Item Picker' to break into the call-stack of a specific item. -// This will call IM_DEBUG_BREAK() which you may redefine yourself. See https://github.com/scottt/debugbreak for more reference. -#ifndef IM_DEBUG_BREAK -#if defined (_MSC_VER) -#define IM_DEBUG_BREAK() __debugbreak() -#elif defined(__clang__) -#define IM_DEBUG_BREAK() __builtin_debugtrap() -#elif defined(__GNUC__) && (defined(__i386__) || defined(__x86_64__)) -#define IM_DEBUG_BREAK() __asm__ volatile("int $0x03") -#elif defined(__GNUC__) && defined(__thumb__) -#define IM_DEBUG_BREAK() __asm__ volatile(".inst 0xde01") -#elif defined(__GNUC__) && defined(__arm__) && !defined(__thumb__) -#define IM_DEBUG_BREAK() __asm__ volatile(".inst 0xe7f001f0"); -#else -#define IM_DEBUG_BREAK() IM_ASSERT(0) // It is expected that you define IM_DEBUG_BREAK() into something that will break nicely in a debugger! -#endif -#endif // #ifndef IM_DEBUG_BREAK - -// Format specifiers, printing 64-bit hasn't been decently standardized... -// In a real application you should be using PRId64 and PRIu64 from (non-windows) and on Windows define them yourself. -#if defined(_MSC_VER) && !defined(__clang__) -#define IM_PRId64 "I64d" -#define IM_PRIu64 "I64u" -#define IM_PRIX64 "I64X" -#else -#define IM_PRId64 "lld" -#define IM_PRIu64 "llu" -#define IM_PRIX64 "llX" -#endif - -//----------------------------------------------------------------------------- -// [SECTION] Generic helpers -// Note that the ImXXX helpers functions are lower-level than ImGui functions. -// ImGui functions or the ImGui context are never called/used from other ImXXX functions. -//----------------------------------------------------------------------------- -// - Helpers: Hashing -// - Helpers: Sorting -// - Helpers: Bit manipulation -// - Helpers: String -// - Helpers: Formatting -// - Helpers: UTF-8 <> wchar conversions -// - Helpers: ImVec2/ImVec4 operators -// - Helpers: Maths -// - Helpers: Geometry -// - Helper: ImVec1 -// - Helper: ImVec2ih -// - Helper: ImRect -// - Helper: ImBitArray -// - Helper: ImBitVector -// - Helper: ImSpan<>, ImSpanAllocator<> -// - Helper: ImPool<> -// - Helper: ImChunkStream<> -// - Helper: ImGuiTextIndex -//----------------------------------------------------------------------------- - -// Helpers: Hashing -IMGUI_API ImGuiID ImHashData(const void* data, size_t data_size, ImGuiID seed = 0); -IMGUI_API ImGuiID ImHashStr(const char* data, size_t data_size = 0, ImGuiID seed = 0); - -// Helpers: Sorting -#ifndef ImQsort -static inline void ImQsort(void* base, size_t count, size_t size_of_element, int(IMGUI_CDECL *compare_func)(void const*, void const*)) { if (count > 1) qsort(base, count, size_of_element, compare_func); } -#endif - -// Helpers: Color Blending -IMGUI_API ImU32 ImAlphaBlendColors(ImU32 col_a, ImU32 col_b); - -// Helpers: Bit manipulation -static inline bool ImIsPowerOfTwo(int v) { return v != 0 && (v & (v - 1)) == 0; } -static inline bool ImIsPowerOfTwo(ImU64 v) { return v != 0 && (v & (v - 1)) == 0; } -static inline int ImUpperPowerOfTwo(int v) { v--; v |= v >> 1; v |= v >> 2; v |= v >> 4; v |= v >> 8; v |= v >> 16; v++; return v; } - -// Helpers: String -IMGUI_API int ImStricmp(const char* str1, const char* str2); // Case insensitive compare. -IMGUI_API int ImStrnicmp(const char* str1, const char* str2, size_t count); // Case insensitive compare to a certain count. -IMGUI_API void ImStrncpy(char* dst, const char* src, size_t count); // Copy to a certain count and always zero terminate (strncpy doesn't). -IMGUI_API char* ImStrdup(const char* str); // Duplicate a string. -IMGUI_API char* ImStrdupcpy(char* dst, size_t* p_dst_size, const char* str); // Copy in provided buffer, recreate buffer if needed. -IMGUI_API const char* ImStrchrRange(const char* str_begin, const char* str_end, char c); // Find first occurrence of 'c' in string range. -IMGUI_API const char* ImStreolRange(const char* str, const char* str_end); // End end-of-line -IMGUI_API const char* ImStristr(const char* haystack, const char* haystack_end, const char* needle, const char* needle_end); // Find a substring in a string range. -IMGUI_API void ImStrTrimBlanks(char* str); // Remove leading and trailing blanks from a buffer. -IMGUI_API const char* ImStrSkipBlank(const char* str); // Find first non-blank character. -IMGUI_API int ImStrlenW(const ImWchar* str); // Computer string length (ImWchar string) -IMGUI_API const ImWchar*ImStrbolW(const ImWchar* buf_mid_line, const ImWchar* buf_begin); // Find beginning-of-line (ImWchar string) -IM_MSVC_RUNTIME_CHECKS_OFF -static inline char ImToUpper(char c) { return (c >= 'a' && c <= 'z') ? c &= ~32 : c; } -static inline bool ImCharIsBlankA(char c) { return c == ' ' || c == '\t'; } -static inline bool ImCharIsBlankW(unsigned int c) { return c == ' ' || c == '\t' || c == 0x3000; } -IM_MSVC_RUNTIME_CHECKS_RESTORE - -// Helpers: Formatting -IMGUI_API int ImFormatString(char* buf, size_t buf_size, const char* fmt, ...) IM_FMTARGS(3); -IMGUI_API int ImFormatStringV(char* buf, size_t buf_size, const char* fmt, va_list args) IM_FMTLIST(3); -IMGUI_API void ImFormatStringToTempBuffer(const char** out_buf, const char** out_buf_end, const char* fmt, ...) IM_FMTARGS(3); -IMGUI_API void ImFormatStringToTempBufferV(const char** out_buf, const char** out_buf_end, const char* fmt, va_list args) IM_FMTLIST(3); -IMGUI_API const char* ImParseFormatFindStart(const char* format); -IMGUI_API const char* ImParseFormatFindEnd(const char* format); -IMGUI_API const char* ImParseFormatTrimDecorations(const char* format, char* buf, size_t buf_size); -IMGUI_API void ImParseFormatSanitizeForPrinting(const char* fmt_in, char* fmt_out, size_t fmt_out_size); -IMGUI_API const char* ImParseFormatSanitizeForScanning(const char* fmt_in, char* fmt_out, size_t fmt_out_size); -IMGUI_API int ImParseFormatPrecision(const char* format, int default_value); - -// Helpers: UTF-8 <> wchar conversions -IMGUI_API const char* ImTextCharToUtf8(char out_buf[5], unsigned int c); // return out_buf -IMGUI_API int ImTextStrToUtf8(char* out_buf, int out_buf_size, const ImWchar* in_text, const ImWchar* in_text_end); // return output UTF-8 bytes count -IMGUI_API int ImTextCharFromUtf8(unsigned int* out_char, const char* in_text, const char* in_text_end); // read one character. return input UTF-8 bytes count -IMGUI_API int ImTextStrFromUtf8(ImWchar* out_buf, int out_buf_size, const char* in_text, const char* in_text_end, const char** in_remaining = NULL); // return input UTF-8 bytes count -IMGUI_API int ImTextCountCharsFromUtf8(const char* in_text, const char* in_text_end); // return number of UTF-8 code-points (NOT bytes count) -IMGUI_API int ImTextCountUtf8BytesFromChar(const char* in_text, const char* in_text_end); // return number of bytes to express one char in UTF-8 -IMGUI_API int ImTextCountUtf8BytesFromStr(const ImWchar* in_text, const ImWchar* in_text_end); // return number of bytes to express string in UTF-8 -IMGUI_API const char* ImTextFindPreviousUtf8Codepoint(const char* in_text_start, const char* in_text_curr); // return previous UTF-8 code-point. - -#ifdef IMGUI_DEFINE_MATH_OPERATORS -IM_MSVC_RUNTIME_CHECKS_OFF -static inline ImVec2 operator*(const ImVec2& lhs, const float rhs) { return ImVec2(lhs.x * rhs, lhs.y * rhs); } -static inline ImVec2 operator/(const ImVec2& lhs, const float rhs) { return ImVec2(lhs.x / rhs, lhs.y / rhs); } -static inline ImVec2 operator+(const ImVec2& lhs, const ImVec2& rhs) { return ImVec2(lhs.x + rhs.x, lhs.y + rhs.y); } -static inline ImVec2 operator-(const ImVec2& lhs, const ImVec2& rhs) { return ImVec2(lhs.x - rhs.x, lhs.y - rhs.y); } -static inline ImVec2 operator*(const ImVec2& lhs, const ImVec2& rhs) { return ImVec2(lhs.x * rhs.x, lhs.y * rhs.y); } -static inline ImVec2 operator/(const ImVec2& lhs, const ImVec2& rhs) { return ImVec2(lhs.x / rhs.x, lhs.y / rhs.y); } -static inline ImVec2& operator*=(ImVec2& lhs, const float rhs) { lhs.x *= rhs; lhs.y *= rhs; return lhs; } -static inline ImVec2& operator/=(ImVec2& lhs, const float rhs) { lhs.x /= rhs; lhs.y /= rhs; return lhs; } -static inline ImVec2& operator+=(ImVec2& lhs, const ImVec2& rhs) { lhs.x += rhs.x; lhs.y += rhs.y; return lhs; } -static inline ImVec2& operator-=(ImVec2& lhs, const ImVec2& rhs) { lhs.x -= rhs.x; lhs.y -= rhs.y; return lhs; } -static inline ImVec2& operator*=(ImVec2& lhs, const ImVec2& rhs) { lhs.x *= rhs.x; lhs.y *= rhs.y; return lhs; } -static inline ImVec2& operator/=(ImVec2& lhs, const ImVec2& rhs) { lhs.x /= rhs.x; lhs.y /= rhs.y; return lhs; } -static inline ImVec4 operator+(const ImVec4& lhs, const ImVec4& rhs) { return ImVec4(lhs.x + rhs.x, lhs.y + rhs.y, lhs.z + rhs.z, lhs.w + rhs.w); } -static inline ImVec4 operator-(const ImVec4& lhs, const ImVec4& rhs) { return ImVec4(lhs.x - rhs.x, lhs.y - rhs.y, lhs.z - rhs.z, lhs.w - rhs.w); } -static inline ImVec4 operator*(const ImVec4& lhs, const ImVec4& rhs) { return ImVec4(lhs.x * rhs.x, lhs.y * rhs.y, lhs.z * rhs.z, lhs.w * rhs.w); } -IM_MSVC_RUNTIME_CHECKS_RESTORE -#endif - -// Helpers: File System -#ifdef IMGUI_DISABLE_FILE_FUNCTIONS -#define IMGUI_DISABLE_DEFAULT_FILE_FUNCTIONS -typedef void* ImFileHandle; -static inline ImFileHandle ImFileOpen(const char*, const char*) { return NULL; } -static inline bool ImFileClose(ImFileHandle) { return false; } -static inline ImU64 ImFileGetSize(ImFileHandle) { return (ImU64)-1; } -static inline ImU64 ImFileRead(void*, ImU64, ImU64, ImFileHandle) { return 0; } -static inline ImU64 ImFileWrite(const void*, ImU64, ImU64, ImFileHandle) { return 0; } -#endif -#ifndef IMGUI_DISABLE_DEFAULT_FILE_FUNCTIONS -typedef FILE* ImFileHandle; -IMGUI_API ImFileHandle ImFileOpen(const char* filename, const char* mode); -IMGUI_API bool ImFileClose(ImFileHandle file); -IMGUI_API ImU64 ImFileGetSize(ImFileHandle file); -IMGUI_API ImU64 ImFileRead(void* data, ImU64 size, ImU64 count, ImFileHandle file); -IMGUI_API ImU64 ImFileWrite(const void* data, ImU64 size, ImU64 count, ImFileHandle file); -#else -#define IMGUI_DISABLE_TTY_FUNCTIONS // Can't use stdout, fflush if we are not using default file functions -#endif -IMGUI_API void* ImFileLoadToMemory(const char* filename, const char* mode, size_t* out_file_size = NULL, int padding_bytes = 0); - -// Helpers: Maths -IM_MSVC_RUNTIME_CHECKS_OFF -// - Wrapper for standard libs functions. (Note that imgui_demo.cpp does _not_ use them to keep the code easy to copy) -#ifndef IMGUI_DISABLE_DEFAULT_MATH_FUNCTIONS -#define ImFabs(X) fabsf(X) -#define ImSqrt(X) sqrtf(X) -#define ImFmod(X, Y) fmodf((X), (Y)) -#define ImCos(X) cosf(X) -#define ImSin(X) sinf(X) -#define ImAcos(X) acosf(X) -#define ImAtan2(Y, X) atan2f((Y), (X)) -#define ImAtof(STR) atof(STR) -#define ImCeil(X) ceilf(X) -static inline float ImPow(float x, float y) { return powf(x, y); } // DragBehaviorT/SliderBehaviorT uses ImPow with either float/double and need the precision -static inline double ImPow(double x, double y) { return pow(x, y); } -static inline float ImLog(float x) { return logf(x); } // DragBehaviorT/SliderBehaviorT uses ImLog with either float/double and need the precision -static inline double ImLog(double x) { return log(x); } -static inline int ImAbs(int x) { return x < 0 ? -x : x; } -static inline float ImAbs(float x) { return fabsf(x); } -static inline double ImAbs(double x) { return fabs(x); } -static inline float ImSign(float x) { return (x < 0.0f) ? -1.0f : (x > 0.0f) ? 1.0f : 0.0f; } // Sign operator - returns -1, 0 or 1 based on sign of argument -static inline double ImSign(double x) { return (x < 0.0) ? -1.0 : (x > 0.0) ? 1.0 : 0.0; } -#ifdef IMGUI_ENABLE_SSE -static inline float ImRsqrt(float x) { return _mm_cvtss_f32(_mm_rsqrt_ss(_mm_set_ss(x))); } -#else -static inline float ImRsqrt(float x) { return 1.0f / sqrtf(x); } -#endif -static inline double ImRsqrt(double x) { return 1.0 / sqrt(x); } -#endif -// - ImMin/ImMax/ImClamp/ImLerp/ImSwap are used by widgets which support variety of types: signed/unsigned int/long long float/double -// (Exceptionally using templates here but we could also redefine them for those types) -template static inline T ImMin(T lhs, T rhs) { return lhs < rhs ? lhs : rhs; } -template static inline T ImMax(T lhs, T rhs) { return lhs >= rhs ? lhs : rhs; } -template static inline T ImClamp(T v, T mn, T mx) { return (v < mn) ? mn : (v > mx) ? mx : v; } -template static inline T ImLerp(T a, T b, float t) { return (T)(a + (b - a) * t); } -template static inline void ImSwap(T& a, T& b) { T tmp = a; a = b; b = tmp; } -template static inline T ImAddClampOverflow(T a, T b, T mn, T mx) { if (b < 0 && (a < mn - b)) return mn; if (b > 0 && (a > mx - b)) return mx; return a + b; } -template static inline T ImSubClampOverflow(T a, T b, T mn, T mx) { if (b > 0 && (a < mn + b)) return mn; if (b < 0 && (a > mx + b)) return mx; return a - b; } -// - Misc maths helpers -static inline ImVec2 ImMin(const ImVec2& lhs, const ImVec2& rhs) { return ImVec2(lhs.x < rhs.x ? lhs.x : rhs.x, lhs.y < rhs.y ? lhs.y : rhs.y); } -static inline ImVec2 ImMax(const ImVec2& lhs, const ImVec2& rhs) { return ImVec2(lhs.x >= rhs.x ? lhs.x : rhs.x, lhs.y >= rhs.y ? lhs.y : rhs.y); } -static inline ImVec2 ImClamp(const ImVec2& v, const ImVec2& mn, ImVec2 mx) { return ImVec2((v.x < mn.x) ? mn.x : (v.x > mx.x) ? mx.x : v.x, (v.y < mn.y) ? mn.y : (v.y > mx.y) ? mx.y : v.y); } -static inline ImVec2 ImLerp(const ImVec2& a, const ImVec2& b, float t) { return ImVec2(a.x + (b.x - a.x) * t, a.y + (b.y - a.y) * t); } -static inline ImVec2 ImLerp(const ImVec2& a, const ImVec2& b, const ImVec2& t) { return ImVec2(a.x + (b.x - a.x) * t.x, a.y + (b.y - a.y) * t.y); } -static inline ImVec4 ImLerp(const ImVec4& a, const ImVec4& b, float t) { return ImVec4(a.x + (b.x - a.x) * t, a.y + (b.y - a.y) * t, a.z + (b.z - a.z) * t, a.w + (b.w - a.w) * t); } -static inline float ImSaturate(float f) { return (f < 0.0f) ? 0.0f : (f > 1.0f) ? 1.0f : f; } -static inline float ImLengthSqr(const ImVec2& lhs) { return (lhs.x * lhs.x) + (lhs.y * lhs.y); } -static inline float ImLengthSqr(const ImVec4& lhs) { return (lhs.x * lhs.x) + (lhs.y * lhs.y) + (lhs.z * lhs.z) + (lhs.w * lhs.w); } -static inline float ImInvLength(const ImVec2& lhs, float fail_value) { float d = (lhs.x * lhs.x) + (lhs.y * lhs.y); if (d > 0.0f) return ImRsqrt(d); return fail_value; } -static inline float ImTrunc(float f) { return (float)(int)(f); } -static inline ImVec2 ImTrunc(const ImVec2& v) { return ImVec2((float)(int)(v.x), (float)(int)(v.y)); } -static inline float ImFloor(float f) { return (float)((f >= 0 || (float)(int)f == f) ? (int)f : (int)f - 1); } // Decent replacement for floorf() -static inline ImVec2 ImFloor(const ImVec2& v) { return ImVec2(ImFloor(v.x), ImFloor(v.y)); } -static inline int ImModPositive(int a, int b) { return (a + b) % b; } -static inline float ImDot(const ImVec2& a, const ImVec2& b) { return a.x * b.x + a.y * b.y; } -static inline ImVec2 ImRotate(const ImVec2& v, float cos_a, float sin_a) { return ImVec2(v.x * cos_a - v.y * sin_a, v.x * sin_a + v.y * cos_a); } -static inline float ImLinearSweep(float current, float target, float speed) { if (current < target) return ImMin(current + speed, target); if (current > target) return ImMax(current - speed, target); return current; } -static inline ImVec2 ImMul(const ImVec2& lhs, const ImVec2& rhs) { return ImVec2(lhs.x * rhs.x, lhs.y * rhs.y); } -static inline bool ImIsFloatAboveGuaranteedIntegerPrecision(float f) { return f <= -16777216 || f >= 16777216; } -static inline float ImExponentialMovingAverage(float avg, float sample, int n) { avg -= avg / n; avg += sample / n; return avg; } -IM_MSVC_RUNTIME_CHECKS_RESTORE - -// Helpers: Geometry -IMGUI_API ImVec2 ImBezierCubicCalc(const ImVec2& p1, const ImVec2& p2, const ImVec2& p3, const ImVec2& p4, float t); -IMGUI_API ImVec2 ImBezierCubicClosestPoint(const ImVec2& p1, const ImVec2& p2, const ImVec2& p3, const ImVec2& p4, const ImVec2& p, int num_segments); // For curves with explicit number of segments -IMGUI_API ImVec2 ImBezierCubicClosestPointCasteljau(const ImVec2& p1, const ImVec2& p2, const ImVec2& p3, const ImVec2& p4, const ImVec2& p, float tess_tol);// For auto-tessellated curves you can use tess_tol = style.CurveTessellationTol -IMGUI_API ImVec2 ImBezierQuadraticCalc(const ImVec2& p1, const ImVec2& p2, const ImVec2& p3, float t); -IMGUI_API ImVec2 ImLineClosestPoint(const ImVec2& a, const ImVec2& b, const ImVec2& p); -IMGUI_API bool ImTriangleContainsPoint(const ImVec2& a, const ImVec2& b, const ImVec2& c, const ImVec2& p); -IMGUI_API ImVec2 ImTriangleClosestPoint(const ImVec2& a, const ImVec2& b, const ImVec2& c, const ImVec2& p); -IMGUI_API void ImTriangleBarycentricCoords(const ImVec2& a, const ImVec2& b, const ImVec2& c, const ImVec2& p, float& out_u, float& out_v, float& out_w); -inline float ImTriangleArea(const ImVec2& a, const ImVec2& b, const ImVec2& c) { return ImFabs((a.x * (b.y - c.y)) + (b.x * (c.y - a.y)) + (c.x * (a.y - b.y))) * 0.5f; } - -// Helper: ImVec1 (1D vector) -// (this odd construct is used to facilitate the transition between 1D and 2D, and the maintenance of some branches/patches) -IM_MSVC_RUNTIME_CHECKS_OFF -struct ImVec1 -{ - float x; - constexpr ImVec1() : x(0.0f) { } - constexpr ImVec1(float _x) : x(_x) { } -}; - -// Helper: ImVec2ih (2D vector, half-size integer, for long-term packed storage) -struct ImVec2ih -{ - short x, y; - constexpr ImVec2ih() : x(0), y(0) {} - constexpr ImVec2ih(short _x, short _y) : x(_x), y(_y) {} - constexpr explicit ImVec2ih(const ImVec2& rhs) : x((short)rhs.x), y((short)rhs.y) {} -}; - -// Helper: ImRect (2D axis aligned bounding-box) -// NB: we can't rely on ImVec2 math operators being available here! -struct IMGUI_API ImRect -{ - ImVec2 Min; // Upper-left - ImVec2 Max; // Lower-right - - constexpr ImRect() : Min(0.0f, 0.0f), Max(0.0f, 0.0f) {} - constexpr ImRect(const ImVec2& min, const ImVec2& max) : Min(min), Max(max) {} - constexpr ImRect(const ImVec4& v) : Min(v.x, v.y), Max(v.z, v.w) {} - constexpr ImRect(float x1, float y1, float x2, float y2) : Min(x1, y1), Max(x2, y2) {} - - ImVec2 GetCenter() const { return ImVec2((Min.x + Max.x) * 0.5f, (Min.y + Max.y) * 0.5f); } - ImVec2 GetSize() const { return ImVec2(Max.x - Min.x, Max.y - Min.y); } - float GetWidth() const { return Max.x - Min.x; } - float GetHeight() const { return Max.y - Min.y; } - float GetArea() const { return (Max.x - Min.x) * (Max.y - Min.y); } - ImVec2 GetTL() const { return Min; } // Top-left - ImVec2 GetTR() const { return ImVec2(Max.x, Min.y); } // Top-right - ImVec2 GetBL() const { return ImVec2(Min.x, Max.y); } // Bottom-left - ImVec2 GetBR() const { return Max; } // Bottom-right - bool Contains(const ImVec2& p) const { return p.x >= Min.x && p.y >= Min.y && p.x < Max.x && p.y < Max.y; } - bool Contains(const ImRect& r) const { return r.Min.x >= Min.x && r.Min.y >= Min.y && r.Max.x <= Max.x && r.Max.y <= Max.y; } - bool ContainsWithPad(const ImVec2& p, const ImVec2& pad) const { return p.x >= Min.x - pad.x && p.y >= Min.y - pad.y && p.x < Max.x + pad.x && p.y < Max.y + pad.y; } - bool Overlaps(const ImRect& r) const { return r.Min.y < Max.y && r.Max.y > Min.y && r.Min.x < Max.x && r.Max.x > Min.x; } - void Add(const ImVec2& p) { if (Min.x > p.x) Min.x = p.x; if (Min.y > p.y) Min.y = p.y; if (Max.x < p.x) Max.x = p.x; if (Max.y < p.y) Max.y = p.y; } - void Add(const ImRect& r) { if (Min.x > r.Min.x) Min.x = r.Min.x; if (Min.y > r.Min.y) Min.y = r.Min.y; if (Max.x < r.Max.x) Max.x = r.Max.x; if (Max.y < r.Max.y) Max.y = r.Max.y; } - void Expand(const float amount) { Min.x -= amount; Min.y -= amount; Max.x += amount; Max.y += amount; } - void Expand(const ImVec2& amount) { Min.x -= amount.x; Min.y -= amount.y; Max.x += amount.x; Max.y += amount.y; } - void Translate(const ImVec2& d) { Min.x += d.x; Min.y += d.y; Max.x += d.x; Max.y += d.y; } - void TranslateX(float dx) { Min.x += dx; Max.x += dx; } - void TranslateY(float dy) { Min.y += dy; Max.y += dy; } - void ClipWith(const ImRect& r) { Min = ImMax(Min, r.Min); Max = ImMin(Max, r.Max); } // Simple version, may lead to an inverted rectangle, which is fine for Contains/Overlaps test but not for display. - void ClipWithFull(const ImRect& r) { Min = ImClamp(Min, r.Min, r.Max); Max = ImClamp(Max, r.Min, r.Max); } // Full version, ensure both points are fully clipped. - void Floor() { Min.x = IM_TRUNC(Min.x); Min.y = IM_TRUNC(Min.y); Max.x = IM_TRUNC(Max.x); Max.y = IM_TRUNC(Max.y); } - bool IsInverted() const { return Min.x > Max.x || Min.y > Max.y; } - ImVec4 ToVec4() const { return ImVec4(Min.x, Min.y, Max.x, Max.y); } -}; - -// Helper: ImBitArray -#define IM_BITARRAY_TESTBIT(_ARRAY, _N) ((_ARRAY[(_N) >> 5] & ((ImU32)1 << ((_N) & 31))) != 0) // Macro version of ImBitArrayTestBit(): ensure args have side-effect or are costly! -#define IM_BITARRAY_CLEARBIT(_ARRAY, _N) ((_ARRAY[(_N) >> 5] &= ~((ImU32)1 << ((_N) & 31)))) // Macro version of ImBitArrayClearBit(): ensure args have side-effect or are costly! -inline size_t ImBitArrayGetStorageSizeInBytes(int bitcount) { return (size_t)((bitcount + 31) >> 5) << 2; } -inline void ImBitArrayClearAllBits(ImU32* arr, int bitcount){ memset(arr, 0, ImBitArrayGetStorageSizeInBytes(bitcount)); } -inline bool ImBitArrayTestBit(const ImU32* arr, int n) { ImU32 mask = (ImU32)1 << (n & 31); return (arr[n >> 5] & mask) != 0; } -inline void ImBitArrayClearBit(ImU32* arr, int n) { ImU32 mask = (ImU32)1 << (n & 31); arr[n >> 5] &= ~mask; } -inline void ImBitArraySetBit(ImU32* arr, int n) { ImU32 mask = (ImU32)1 << (n & 31); arr[n >> 5] |= mask; } -inline void ImBitArraySetBitRange(ImU32* arr, int n, int n2) // Works on range [n..n2) -{ - n2--; - while (n <= n2) - { - int a_mod = (n & 31); - int b_mod = (n2 > (n | 31) ? 31 : (n2 & 31)) + 1; - ImU32 mask = (ImU32)(((ImU64)1 << b_mod) - 1) & ~(ImU32)(((ImU64)1 << a_mod) - 1); - arr[n >> 5] |= mask; - n = (n + 32) & ~31; - } -} - -typedef ImU32* ImBitArrayPtr; // Name for use in structs - -// Helper: ImBitArray class (wrapper over ImBitArray functions) -// Store 1-bit per value. -template -struct ImBitArray -{ - ImU32 Storage[(BITCOUNT + 31) >> 5]; - ImBitArray() { ClearAllBits(); } - void ClearAllBits() { memset(Storage, 0, sizeof(Storage)); } - void SetAllBits() { memset(Storage, 255, sizeof(Storage)); } - bool TestBit(int n) const { n += OFFSET; IM_ASSERT(n >= 0 && n < BITCOUNT); return IM_BITARRAY_TESTBIT(Storage, n); } - void SetBit(int n) { n += OFFSET; IM_ASSERT(n >= 0 && n < BITCOUNT); ImBitArraySetBit(Storage, n); } - void ClearBit(int n) { n += OFFSET; IM_ASSERT(n >= 0 && n < BITCOUNT); ImBitArrayClearBit(Storage, n); } - void SetBitRange(int n, int n2) { n += OFFSET; n2 += OFFSET; IM_ASSERT(n >= 0 && n < BITCOUNT && n2 > n && n2 <= BITCOUNT); ImBitArraySetBitRange(Storage, n, n2); } // Works on range [n..n2) - bool operator[](int n) const { n += OFFSET; IM_ASSERT(n >= 0 && n < BITCOUNT); return IM_BITARRAY_TESTBIT(Storage, n); } -}; - -// Helper: ImBitVector -// Store 1-bit per value. -struct IMGUI_API ImBitVector -{ - ImVector Storage; - void Create(int sz) { Storage.resize((sz + 31) >> 5); memset(Storage.Data, 0, (size_t)Storage.Size * sizeof(Storage.Data[0])); } - void Clear() { Storage.clear(); } - bool TestBit(int n) const { IM_ASSERT(n < (Storage.Size << 5)); return IM_BITARRAY_TESTBIT(Storage.Data, n); } - void SetBit(int n) { IM_ASSERT(n < (Storage.Size << 5)); ImBitArraySetBit(Storage.Data, n); } - void ClearBit(int n) { IM_ASSERT(n < (Storage.Size << 5)); ImBitArrayClearBit(Storage.Data, n); } -}; -IM_MSVC_RUNTIME_CHECKS_RESTORE - -// Helper: ImSpan<> -// Pointing to a span of data we don't own. -template -struct ImSpan -{ - T* Data; - T* DataEnd; - - // Constructors, destructor - inline ImSpan() { Data = DataEnd = NULL; } - inline ImSpan(T* data, int size) { Data = data; DataEnd = data + size; } - inline ImSpan(T* data, T* data_end) { Data = data; DataEnd = data_end; } - - inline void set(T* data, int size) { Data = data; DataEnd = data + size; } - inline void set(T* data, T* data_end) { Data = data; DataEnd = data_end; } - inline int size() const { return (int)(ptrdiff_t)(DataEnd - Data); } - inline int size_in_bytes() const { return (int)(ptrdiff_t)(DataEnd - Data) * (int)sizeof(T); } - inline T& operator[](int i) { T* p = Data + i; IM_ASSERT(p >= Data && p < DataEnd); return *p; } - inline const T& operator[](int i) const { const T* p = Data + i; IM_ASSERT(p >= Data && p < DataEnd); return *p; } - - inline T* begin() { return Data; } - inline const T* begin() const { return Data; } - inline T* end() { return DataEnd; } - inline const T* end() const { return DataEnd; } - - // Utilities - inline int index_from_ptr(const T* it) const { IM_ASSERT(it >= Data && it < DataEnd); const ptrdiff_t off = it - Data; return (int)off; } -}; - -// Helper: ImSpanAllocator<> -// Facilitate storing multiple chunks into a single large block (the "arena") -// - Usage: call Reserve() N times, allocate GetArenaSizeInBytes() worth, pass it to SetArenaBasePtr(), call GetSpan() N times to retrieve the aligned ranges. -template -struct ImSpanAllocator -{ - char* BasePtr; - int CurrOff; - int CurrIdx; - int Offsets[CHUNKS]; - int Sizes[CHUNKS]; - - ImSpanAllocator() { memset(this, 0, sizeof(*this)); } - inline void Reserve(int n, size_t sz, int a=4) { IM_ASSERT(n == CurrIdx && n < CHUNKS); CurrOff = IM_MEMALIGN(CurrOff, a); Offsets[n] = CurrOff; Sizes[n] = (int)sz; CurrIdx++; CurrOff += (int)sz; } - inline int GetArenaSizeInBytes() { return CurrOff; } - inline void SetArenaBasePtr(void* base_ptr) { BasePtr = (char*)base_ptr; } - inline void* GetSpanPtrBegin(int n) { IM_ASSERT(n >= 0 && n < CHUNKS && CurrIdx == CHUNKS); return (void*)(BasePtr + Offsets[n]); } - inline void* GetSpanPtrEnd(int n) { IM_ASSERT(n >= 0 && n < CHUNKS && CurrIdx == CHUNKS); return (void*)(BasePtr + Offsets[n] + Sizes[n]); } - template - inline void GetSpan(int n, ImSpan* span) { span->set((T*)GetSpanPtrBegin(n), (T*)GetSpanPtrEnd(n)); } -}; - -// Helper: ImPool<> -// Basic keyed storage for contiguous instances, slow/amortized insertion, O(1) indexable, O(Log N) queries by ID over a dense/hot buffer, -// Honor constructor/destructor. Add/remove invalidate all pointers. Indexes have the same lifetime as the associated object. -typedef int ImPoolIdx; -template -struct ImPool -{ - ImVector Buf; // Contiguous data - ImGuiStorage Map; // ID->Index - ImPoolIdx FreeIdx; // Next free idx to use - ImPoolIdx AliveCount; // Number of active/alive items (for display purpose) - - ImPool() { FreeIdx = AliveCount = 0; } - ~ImPool() { Clear(); } - T* GetByKey(ImGuiID key) { int idx = Map.GetInt(key, -1); return (idx != -1) ? &Buf[idx] : NULL; } - T* GetByIndex(ImPoolIdx n) { return &Buf[n]; } - ImPoolIdx GetIndex(const T* p) const { IM_ASSERT(p >= Buf.Data && p < Buf.Data + Buf.Size); return (ImPoolIdx)(p - Buf.Data); } - T* GetOrAddByKey(ImGuiID key) { int* p_idx = Map.GetIntRef(key, -1); if (*p_idx != -1) return &Buf[*p_idx]; *p_idx = FreeIdx; return Add(); } - bool Contains(const T* p) const { return (p >= Buf.Data && p < Buf.Data + Buf.Size); } - void Clear() { for (int n = 0; n < Map.Data.Size; n++) { int idx = Map.Data[n].val_i; if (idx != -1) Buf[idx].~T(); } Map.Clear(); Buf.clear(); FreeIdx = AliveCount = 0; } - T* Add() { int idx = FreeIdx; if (idx == Buf.Size) { Buf.resize(Buf.Size + 1); FreeIdx++; } else { FreeIdx = *(int*)&Buf[idx]; } IM_PLACEMENT_NEW(&Buf[idx]) T(); AliveCount++; return &Buf[idx]; } - void Remove(ImGuiID key, const T* p) { Remove(key, GetIndex(p)); } - void Remove(ImGuiID key, ImPoolIdx idx) { Buf[idx].~T(); *(int*)&Buf[idx] = FreeIdx; FreeIdx = idx; Map.SetInt(key, -1); AliveCount--; } - void Reserve(int capacity) { Buf.reserve(capacity); Map.Data.reserve(capacity); } - - // To iterate a ImPool: for (int n = 0; n < pool.GetMapSize(); n++) if (T* t = pool.TryGetMapData(n)) { ... } - // Can be avoided if you know .Remove() has never been called on the pool, or AliveCount == GetMapSize() - int GetAliveCount() const { return AliveCount; } // Number of active/alive items in the pool (for display purpose) - int GetBufSize() const { return Buf.Size; } - int GetMapSize() const { return Map.Data.Size; } // It is the map we need iterate to find valid items, since we don't have "alive" storage anywhere - T* TryGetMapData(ImPoolIdx n) { int idx = Map.Data[n].val_i; if (idx == -1) return NULL; return GetByIndex(idx); } -#ifndef IMGUI_DISABLE_OBSOLETE_FUNCTIONS - int GetSize() { return GetMapSize(); } // For ImPlot: should use GetMapSize() from (IMGUI_VERSION_NUM >= 18304) -#endif -}; - -// Helper: ImChunkStream<> -// Build and iterate a contiguous stream of variable-sized structures. -// This is used by Settings to store persistent data while reducing allocation count. -// We store the chunk size first, and align the final size on 4 bytes boundaries. -// The tedious/zealous amount of casting is to avoid -Wcast-align warnings. -template -struct ImChunkStream -{ - ImVector Buf; - - void clear() { Buf.clear(); } - bool empty() const { return Buf.Size == 0; } - int size() const { return Buf.Size; } - T* alloc_chunk(size_t sz) { size_t HDR_SZ = 4; sz = IM_MEMALIGN(HDR_SZ + sz, 4u); int off = Buf.Size; Buf.resize(off + (int)sz); ((int*)(void*)(Buf.Data + off))[0] = (int)sz; return (T*)(void*)(Buf.Data + off + (int)HDR_SZ); } - T* begin() { size_t HDR_SZ = 4; if (!Buf.Data) return NULL; return (T*)(void*)(Buf.Data + HDR_SZ); } - T* next_chunk(T* p) { size_t HDR_SZ = 4; IM_ASSERT(p >= begin() && p < end()); p = (T*)(void*)((char*)(void*)p + chunk_size(p)); if (p == (T*)(void*)((char*)end() + HDR_SZ)) return (T*)0; IM_ASSERT(p < end()); return p; } - int chunk_size(const T* p) { return ((const int*)p)[-1]; } - T* end() { return (T*)(void*)(Buf.Data + Buf.Size); } - int offset_from_ptr(const T* p) { IM_ASSERT(p >= begin() && p < end()); const ptrdiff_t off = (const char*)p - Buf.Data; return (int)off; } - T* ptr_from_offset(int off) { IM_ASSERT(off >= 4 && off < Buf.Size); return (T*)(void*)(Buf.Data + off); } - void swap(ImChunkStream& rhs) { rhs.Buf.swap(Buf); } -}; - -// Helper: ImGuiTextIndex<> -// Maintain a line index for a text buffer. This is a strong candidate to be moved into the public API. -struct ImGuiTextIndex -{ - ImVector LineOffsets; - int EndOffset = 0; // Because we don't own text buffer we need to maintain EndOffset (may bake in LineOffsets?) - - void clear() { LineOffsets.clear(); EndOffset = 0; } - int size() { return LineOffsets.Size; } - const char* get_line_begin(const char* base, int n) { return base + LineOffsets[n]; } - const char* get_line_end(const char* base, int n) { return base + (n + 1 < LineOffsets.Size ? (LineOffsets[n + 1] - 1) : EndOffset); } - void append(const char* base, int old_size, int new_size); -}; - -//----------------------------------------------------------------------------- -// [SECTION] ImDrawList support -//----------------------------------------------------------------------------- - -// ImDrawList: Helper function to calculate a circle's segment count given its radius and a "maximum error" value. -// Estimation of number of circle segment based on error is derived using method described in https://stackoverflow.com/a/2244088/15194693 -// Number of segments (N) is calculated using equation: -// N = ceil ( pi / acos(1 - error / r) ) where r > 0, error <= r -// Our equation is significantly simpler that one in the post thanks for choosing segment that is -// perpendicular to X axis. Follow steps in the article from this starting condition and you will -// will get this result. -// -// Rendering circles with an odd number of segments, while mathematically correct will produce -// asymmetrical results on the raster grid. Therefore we're rounding N to next even number (7->8, 8->8, 9->10 etc.) -#define IM_ROUNDUP_TO_EVEN(_V) ((((_V) + 1) / 2) * 2) -#define IM_DRAWLIST_CIRCLE_AUTO_SEGMENT_MIN 4 -#define IM_DRAWLIST_CIRCLE_AUTO_SEGMENT_MAX 512 -#define IM_DRAWLIST_CIRCLE_AUTO_SEGMENT_CALC(_RAD,_MAXERROR) ImClamp(IM_ROUNDUP_TO_EVEN((int)ImCeil(IM_PI / ImAcos(1 - ImMin((_MAXERROR), (_RAD)) / (_RAD)))), IM_DRAWLIST_CIRCLE_AUTO_SEGMENT_MIN, IM_DRAWLIST_CIRCLE_AUTO_SEGMENT_MAX) - -// Raw equation from IM_DRAWLIST_CIRCLE_AUTO_SEGMENT_CALC rewritten for 'r' and 'error'. -#define IM_DRAWLIST_CIRCLE_AUTO_SEGMENT_CALC_R(_N,_MAXERROR) ((_MAXERROR) / (1 - ImCos(IM_PI / ImMax((float)(_N), IM_PI)))) -#define IM_DRAWLIST_CIRCLE_AUTO_SEGMENT_CALC_ERROR(_N,_RAD) ((1 - ImCos(IM_PI / ImMax((float)(_N), IM_PI))) / (_RAD)) - -// ImDrawList: Lookup table size for adaptive arc drawing, cover full circle. -#ifndef IM_DRAWLIST_ARCFAST_TABLE_SIZE -#define IM_DRAWLIST_ARCFAST_TABLE_SIZE 48 // Number of samples in lookup table. -#endif -#define IM_DRAWLIST_ARCFAST_SAMPLE_MAX IM_DRAWLIST_ARCFAST_TABLE_SIZE // Sample index _PathArcToFastEx() for 360 angle. - -// Data shared between all ImDrawList instances -// You may want to create your own instance of this if you want to use ImDrawList completely without ImGui. In that case, watch out for future changes to this structure. -struct IMGUI_API ImDrawListSharedData -{ - ImVec2 TexUvWhitePixel; // UV of white pixel in the atlas - ImFont* Font; // Current/default font (optional, for simplified AddText overload) - float FontSize; // Current/default font size (optional, for simplified AddText overload) - float CurveTessellationTol; // Tessellation tolerance when using PathBezierCurveTo() - float CircleSegmentMaxError; // Number of circle segments to use per pixel of radius for AddCircle() etc - ImVec4 ClipRectFullscreen; // Value for PushClipRectFullscreen() - ImDrawListFlags InitialFlags; // Initial flags at the beginning of the frame (it is possible to alter flags on a per-drawlist basis afterwards) - - // [Internal] Temp write buffer - ImVector TempBuffer; - - // [Internal] Lookup tables - ImVec2 ArcFastVtx[IM_DRAWLIST_ARCFAST_TABLE_SIZE]; // Sample points on the quarter of the circle. - float ArcFastRadiusCutoff; // Cutoff radius after which arc drawing will fallback to slower PathArcTo() - ImU8 CircleSegmentCounts[64]; // Precomputed segment count for given radius before we calculate it dynamically (to avoid calculation overhead) - const ImVec4* TexUvLines; // UV of anti-aliased lines in the atlas - - ImDrawListSharedData(); - void SetCircleTessellationMaxError(float max_error); -}; - -struct ImDrawDataBuilder -{ - ImVector* Layers[2]; // Pointers to global layers for: regular, tooltip. LayersP[0] is owned by DrawData. - ImVector LayerData1; - - ImDrawDataBuilder() { memset(this, 0, sizeof(*this)); } -}; - -//----------------------------------------------------------------------------- -// [SECTION] Widgets support: flags, enums, data structures -//----------------------------------------------------------------------------- - -// Flags used by upcoming items -// - input: PushItemFlag() manipulates g.CurrentItemFlags, ItemAdd() calls may add extra flags. -// - output: stored in g.LastItemData.InFlags -// Current window shared by all windows. -// This is going to be exposed in imgui.h when stabilized enough. -enum ImGuiItemFlags_ -{ - // Controlled by user - ImGuiItemFlags_None = 0, - ImGuiItemFlags_NoTabStop = 1 << 0, // false // Disable keyboard tabbing. This is a "lighter" version of ImGuiItemFlags_NoNav. - ImGuiItemFlags_ButtonRepeat = 1 << 1, // false // Button() will return true multiple times based on io.KeyRepeatDelay and io.KeyRepeatRate settings. - ImGuiItemFlags_Disabled = 1 << 2, // false // Disable interactions but doesn't affect visuals. See BeginDisabled()/EndDisabled(). See github.com/ocornut/imgui/issues/211 - ImGuiItemFlags_NoNav = 1 << 3, // false // Disable any form of focusing (keyboard/gamepad directional navigation and SetKeyboardFocusHere() calls) - ImGuiItemFlags_NoNavDefaultFocus = 1 << 4, // false // Disable item being a candidate for default focus (e.g. used by title bar items) - ImGuiItemFlags_SelectableDontClosePopup = 1 << 5, // false // Disable MenuItem/Selectable() automatically closing their popup window - ImGuiItemFlags_MixedValue = 1 << 6, // false // [BETA] Represent a mixed/indeterminate value, generally multi-selection where values differ. Currently only supported by Checkbox() (later should support all sorts of widgets) - ImGuiItemFlags_ReadOnly = 1 << 7, // false // [ALPHA] Allow hovering interactions but underlying value is not changed. - ImGuiItemFlags_NoWindowHoverableCheck = 1 << 8, // false // Disable hoverable check in ItemHoverable() - ImGuiItemFlags_AllowOverlap = 1 << 9, // false // Allow being overlapped by another widget. Not-hovered to Hovered transition deferred by a frame. - - // Controlled by widget code - ImGuiItemFlags_Inputable = 1 << 10, // false // [WIP] Auto-activate input mode when tab focused. Currently only used and supported by a few items before it becomes a generic feature. - ImGuiItemFlags_HasSelectionUserData = 1 << 11, // false // Set by SetNextItemSelectionUserData() -}; - -// Status flags for an already submitted item -// - output: stored in g.LastItemData.StatusFlags -enum ImGuiItemStatusFlags_ -{ - ImGuiItemStatusFlags_None = 0, - ImGuiItemStatusFlags_HoveredRect = 1 << 0, // Mouse position is within item rectangle (does NOT mean that the window is in correct z-order and can be hovered!, this is only one part of the most-common IsItemHovered test) - ImGuiItemStatusFlags_HasDisplayRect = 1 << 1, // g.LastItemData.DisplayRect is valid - ImGuiItemStatusFlags_Edited = 1 << 2, // Value exposed by item was edited in the current frame (should match the bool return value of most widgets) - ImGuiItemStatusFlags_ToggledSelection = 1 << 3, // Set when Selectable(), TreeNode() reports toggling a selection. We can't report "Selected", only state changes, in order to easily handle clipping with less issues. - ImGuiItemStatusFlags_ToggledOpen = 1 << 4, // Set when TreeNode() reports toggling their open state. - ImGuiItemStatusFlags_HasDeactivated = 1 << 5, // Set if the widget/group is able to provide data for the ImGuiItemStatusFlags_Deactivated flag. - ImGuiItemStatusFlags_Deactivated = 1 << 6, // Only valid if ImGuiItemStatusFlags_HasDeactivated is set. - ImGuiItemStatusFlags_HoveredWindow = 1 << 7, // Override the HoveredWindow test to allow cross-window hover testing. - ImGuiItemStatusFlags_FocusedByTabbing = 1 << 8, // Set when the Focusable item just got focused by Tabbing (FIXME: to be removed soon) - ImGuiItemStatusFlags_Visible = 1 << 9, // [WIP] Set when item is overlapping the current clipping rectangle (Used internally. Please don't use yet: API/system will change as we refactor Itemadd()). - - // Additional status + semantic for ImGuiTestEngine -#ifdef IMGUI_ENABLE_TEST_ENGINE - ImGuiItemStatusFlags_Openable = 1 << 20, // Item is an openable (e.g. TreeNode) - ImGuiItemStatusFlags_Opened = 1 << 21, // Opened status - ImGuiItemStatusFlags_Checkable = 1 << 22, // Item is a checkable (e.g. CheckBox, MenuItem) - ImGuiItemStatusFlags_Checked = 1 << 23, // Checked status - ImGuiItemStatusFlags_Inputable = 1 << 24, // Item is a text-inputable (e.g. InputText, SliderXXX, DragXXX) -#endif -}; - -// Extend ImGuiHoveredFlags_ -enum ImGuiHoveredFlagsPrivate_ -{ - ImGuiHoveredFlags_DelayMask_ = ImGuiHoveredFlags_DelayNone | ImGuiHoveredFlags_DelayShort | ImGuiHoveredFlags_DelayNormal | ImGuiHoveredFlags_NoSharedDelay, - ImGuiHoveredFlags_AllowedMaskForIsWindowHovered = ImGuiHoveredFlags_ChildWindows | ImGuiHoveredFlags_RootWindow | ImGuiHoveredFlags_AnyWindow | ImGuiHoveredFlags_NoPopupHierarchy | ImGuiHoveredFlags_DockHierarchy | ImGuiHoveredFlags_AllowWhenBlockedByPopup | ImGuiHoveredFlags_AllowWhenBlockedByActiveItem | ImGuiHoveredFlags_ForTooltip | ImGuiHoveredFlags_Stationary, - ImGuiHoveredFlags_AllowedMaskForIsItemHovered = ImGuiHoveredFlags_AllowWhenBlockedByPopup | ImGuiHoveredFlags_AllowWhenBlockedByActiveItem | ImGuiHoveredFlags_AllowWhenOverlapped | ImGuiHoveredFlags_AllowWhenDisabled | ImGuiHoveredFlags_NoNavOverride | ImGuiHoveredFlags_ForTooltip | ImGuiHoveredFlags_Stationary | ImGuiHoveredFlags_DelayMask_, -}; - -// Extend ImGuiInputTextFlags_ -enum ImGuiInputTextFlagsPrivate_ -{ - // [Internal] - ImGuiInputTextFlags_Multiline = 1 << 26, // For internal use by InputTextMultiline() - ImGuiInputTextFlags_NoMarkEdited = 1 << 27, // For internal use by functions using InputText() before reformatting data - ImGuiInputTextFlags_MergedItem = 1 << 28, // For internal use by TempInputText(), will skip calling ItemAdd(). Require bounding-box to strictly match. -}; - -// Extend ImGuiButtonFlags_ -enum ImGuiButtonFlagsPrivate_ -{ - ImGuiButtonFlags_PressedOnClick = 1 << 4, // return true on click (mouse down event) - ImGuiButtonFlags_PressedOnClickRelease = 1 << 5, // [Default] return true on click + release on same item <-- this is what the majority of Button are using - ImGuiButtonFlags_PressedOnClickReleaseAnywhere = 1 << 6, // return true on click + release even if the release event is not done while hovering the item - ImGuiButtonFlags_PressedOnRelease = 1 << 7, // return true on release (default requires click+release) - ImGuiButtonFlags_PressedOnDoubleClick = 1 << 8, // return true on double-click (default requires click+release) - ImGuiButtonFlags_PressedOnDragDropHold = 1 << 9, // return true when held into while we are drag and dropping another item (used by e.g. tree nodes, collapsing headers) - ImGuiButtonFlags_Repeat = 1 << 10, // hold to repeat - ImGuiButtonFlags_FlattenChildren = 1 << 11, // allow interactions even if a child window is overlapping - ImGuiButtonFlags_AllowOverlap = 1 << 12, // require previous frame HoveredId to either match id or be null before being usable. - ImGuiButtonFlags_DontClosePopups = 1 << 13, // disable automatically closing parent popup on press // [UNUSED] - //ImGuiButtonFlags_Disabled = 1 << 14, // disable interactions -> use BeginDisabled() or ImGuiItemFlags_Disabled - ImGuiButtonFlags_AlignTextBaseLine = 1 << 15, // vertically align button to match text baseline - ButtonEx() only // FIXME: Should be removed and handled by SmallButton(), not possible currently because of DC.CursorPosPrevLine - ImGuiButtonFlags_NoKeyModifiers = 1 << 16, // disable mouse interaction if a key modifier is held - ImGuiButtonFlags_NoHoldingActiveId = 1 << 17, // don't set ActiveId while holding the mouse (ImGuiButtonFlags_PressedOnClick only) - ImGuiButtonFlags_NoNavFocus = 1 << 18, // don't override navigation focus when activated (FIXME: this is essentially used everytime an item uses ImGuiItemFlags_NoNav, but because legacy specs don't requires LastItemData to be set ButtonBehavior(), we can't poll g.LastItemData.InFlags) - ImGuiButtonFlags_NoHoveredOnFocus = 1 << 19, // don't report as hovered when nav focus is on this item - ImGuiButtonFlags_NoSetKeyOwner = 1 << 20, // don't set key/input owner on the initial click (note: mouse buttons are keys! often, the key in question will be ImGuiKey_MouseLeft!) - ImGuiButtonFlags_NoTestKeyOwner = 1 << 21, // don't test key/input owner when polling the key (note: mouse buttons are keys! often, the key in question will be ImGuiKey_MouseLeft!) - ImGuiButtonFlags_PressedOnMask_ = ImGuiButtonFlags_PressedOnClick | ImGuiButtonFlags_PressedOnClickRelease | ImGuiButtonFlags_PressedOnClickReleaseAnywhere | ImGuiButtonFlags_PressedOnRelease | ImGuiButtonFlags_PressedOnDoubleClick | ImGuiButtonFlags_PressedOnDragDropHold, - ImGuiButtonFlags_PressedOnDefault_ = ImGuiButtonFlags_PressedOnClickRelease, -}; - -// Extend ImGuiComboFlags_ -enum ImGuiComboFlagsPrivate_ -{ - ImGuiComboFlags_CustomPreview = 1 << 20, // enable BeginComboPreview() -}; - -// Extend ImGuiSliderFlags_ -enum ImGuiSliderFlagsPrivate_ -{ - ImGuiSliderFlags_Vertical = 1 << 20, // Should this slider be orientated vertically? - ImGuiSliderFlags_ReadOnly = 1 << 21, // Consider using g.NextItemData.ItemFlags |= ImGuiItemFlags_ReadOnly instead. -}; - -// Extend ImGuiSelectableFlags_ -enum ImGuiSelectableFlagsPrivate_ -{ - // NB: need to be in sync with last value of ImGuiSelectableFlags_ - ImGuiSelectableFlags_NoHoldingActiveID = 1 << 20, - ImGuiSelectableFlags_SelectOnNav = 1 << 21, // (WIP) Auto-select when moved into. This is not exposed in public API as to handle multi-select and modifiers we will need user to explicitly control focus scope. May be replaced with a BeginSelection() API. - ImGuiSelectableFlags_SelectOnClick = 1 << 22, // Override button behavior to react on Click (default is Click+Release) - ImGuiSelectableFlags_SelectOnRelease = 1 << 23, // Override button behavior to react on Release (default is Click+Release) - ImGuiSelectableFlags_SpanAvailWidth = 1 << 24, // Span all avail width even if we declared less for layout purpose. FIXME: We may be able to remove this (added in 6251d379, 2bcafc86 for menus) - ImGuiSelectableFlags_SetNavIdOnHover = 1 << 25, // Set Nav/Focus ID on mouse hover (used by MenuItem) - ImGuiSelectableFlags_NoPadWithHalfSpacing = 1 << 26, // Disable padding each side with ItemSpacing * 0.5f - ImGuiSelectableFlags_NoSetKeyOwner = 1 << 27, // Don't set key/input owner on the initial click (note: mouse buttons are keys! often, the key in question will be ImGuiKey_MouseLeft!) -}; - -// Extend ImGuiTreeNodeFlags_ -enum ImGuiTreeNodeFlagsPrivate_ -{ - ImGuiTreeNodeFlags_ClipLabelForTrailingButton = 1 << 20, - ImGuiTreeNodeFlags_UpsideDownArrow = 1 << 21,// (FIXME-WIP) Turn Down arrow into an Up arrow, but reversed trees (#6517) -}; - -enum ImGuiSeparatorFlags_ -{ - ImGuiSeparatorFlags_None = 0, - ImGuiSeparatorFlags_Horizontal = 1 << 0, // Axis default to current layout type, so generally Horizontal unless e.g. in a menu bar - ImGuiSeparatorFlags_Vertical = 1 << 1, - ImGuiSeparatorFlags_SpanAllColumns = 1 << 2, // Make separator cover all columns of a legacy Columns() set. -}; - -// Flags for FocusWindow(). This is not called ImGuiFocusFlags to avoid confusion with public-facing ImGuiFocusedFlags. -// FIXME: Once we finishing replacing more uses of GetTopMostPopupModal()+IsWindowWithinBeginStackOf() -// and FindBlockingModal() with this, we may want to change the flag to be opt-out instead of opt-in. -enum ImGuiFocusRequestFlags_ -{ - ImGuiFocusRequestFlags_None = 0, - ImGuiFocusRequestFlags_RestoreFocusedChild = 1 << 0, // Find last focused child (if any) and focus it instead. - ImGuiFocusRequestFlags_UnlessBelowModal = 1 << 1, // Do not set focus if the window is below a modal. -}; - -enum ImGuiTextFlags_ -{ - ImGuiTextFlags_None = 0, - ImGuiTextFlags_NoWidthForLargeClippedText = 1 << 0, -}; - -enum ImGuiTooltipFlags_ -{ - ImGuiTooltipFlags_None = 0, - ImGuiTooltipFlags_OverridePrevious = 1 << 1, // Clear/ignore previously submitted tooltip (defaults to append) -}; - -// FIXME: this is in development, not exposed/functional as a generic feature yet. -// Horizontal/Vertical enums are fixed to 0/1 so they may be used to index ImVec2 -enum ImGuiLayoutType_ -{ - ImGuiLayoutType_Horizontal = 0, - ImGuiLayoutType_Vertical = 1 -}; - -enum ImGuiLogType -{ - ImGuiLogType_None = 0, - ImGuiLogType_TTY, - ImGuiLogType_File, - ImGuiLogType_Buffer, - ImGuiLogType_Clipboard, -}; - -// X/Y enums are fixed to 0/1 so they may be used to index ImVec2 -enum ImGuiAxis -{ - ImGuiAxis_None = -1, - ImGuiAxis_X = 0, - ImGuiAxis_Y = 1 -}; - -enum ImGuiPlotType -{ - ImGuiPlotType_Lines, - ImGuiPlotType_Histogram, -}; - -enum ImGuiPopupPositionPolicy -{ - ImGuiPopupPositionPolicy_Default, - ImGuiPopupPositionPolicy_ComboBox, - ImGuiPopupPositionPolicy_Tooltip, -}; - -struct ImGuiDataVarInfo -{ - ImGuiDataType Type; - ImU32 Count; // 1+ - ImU32 Offset; // Offset in parent structure - void* GetVarPtr(void* parent) const { return (void*)((unsigned char*)parent + Offset); } -}; - -struct ImGuiDataTypeTempStorage -{ - ImU8 Data[8]; // Can fit any data up to ImGuiDataType_COUNT -}; - -// Type information associated to one ImGuiDataType. Retrieve with DataTypeGetInfo(). -struct ImGuiDataTypeInfo -{ - size_t Size; // Size in bytes - const char* Name; // Short descriptive name for the type, for debugging - const char* PrintFmt; // Default printf format for the type - const char* ScanFmt; // Default scanf format for the type -}; - -// Extend ImGuiDataType_ -enum ImGuiDataTypePrivate_ -{ - ImGuiDataType_String = ImGuiDataType_COUNT + 1, - ImGuiDataType_Pointer, - ImGuiDataType_ID, -}; - -// Stacked color modifier, backup of modified data so we can restore it -struct ImGuiColorMod -{ - ImGuiCol Col; - ImVec4 BackupValue; -}; - -// Stacked style modifier, backup of modified data so we can restore it. Data type inferred from the variable. -struct ImGuiStyleMod -{ - ImGuiStyleVar VarIdx; - union { int BackupInt[2]; float BackupFloat[2]; }; - ImGuiStyleMod(ImGuiStyleVar idx, int v) { VarIdx = idx; BackupInt[0] = v; } - ImGuiStyleMod(ImGuiStyleVar idx, float v) { VarIdx = idx; BackupFloat[0] = v; } - ImGuiStyleMod(ImGuiStyleVar idx, ImVec2 v) { VarIdx = idx; BackupFloat[0] = v.x; BackupFloat[1] = v.y; } -}; - -// Storage data for BeginComboPreview()/EndComboPreview() -struct IMGUI_API ImGuiComboPreviewData -{ - ImRect PreviewRect; - ImVec2 BackupCursorPos; - ImVec2 BackupCursorMaxPos; - ImVec2 BackupCursorPosPrevLine; - float BackupPrevLineTextBaseOffset; - ImGuiLayoutType BackupLayout; - - ImGuiComboPreviewData() { memset(this, 0, sizeof(*this)); } -}; - -// Stacked storage data for BeginGroup()/EndGroup() -struct IMGUI_API ImGuiGroupData -{ - ImGuiID WindowID; - ImVec2 BackupCursorPos; - ImVec2 BackupCursorMaxPos; - ImVec2 BackupCursorPosPrevLine; - ImVec1 BackupIndent; - ImVec1 BackupGroupOffset; - ImVec2 BackupCurrLineSize; - float BackupCurrLineTextBaseOffset; - ImGuiID BackupActiveIdIsAlive; - bool BackupActiveIdPreviousFrameIsAlive; - bool BackupHoveredIdIsAlive; - bool BackupIsSameLine; - bool EmitItem; -}; - -// Simple column measurement, currently used for MenuItem() only.. This is very short-sighted/throw-away code and NOT a generic helper. -struct IMGUI_API ImGuiMenuColumns -{ - ImU32 TotalWidth; - ImU32 NextTotalWidth; - ImU16 Spacing; - ImU16 OffsetIcon; // Always zero for now - ImU16 OffsetLabel; // Offsets are locked in Update() - ImU16 OffsetShortcut; - ImU16 OffsetMark; - ImU16 Widths[4]; // Width of: Icon, Label, Shortcut, Mark (accumulators for current frame) - - ImGuiMenuColumns() { memset(this, 0, sizeof(*this)); } - void Update(float spacing, bool window_reappearing); - float DeclColumns(float w_icon, float w_label, float w_shortcut, float w_mark); - void CalcNextTotalWidth(bool update_offsets); -}; - -// Internal temporary state for deactivating InputText() instances. -struct IMGUI_API ImGuiInputTextDeactivatedState -{ - ImGuiID ID; // widget id owning the text state (which just got deactivated) - ImVector TextA; // text buffer - - ImGuiInputTextDeactivatedState() { memset(this, 0, sizeof(*this)); } - void ClearFreeMemory() { ID = 0; TextA.clear(); } -}; -// Internal state of the currently focused/edited text input box -// For a given item ID, access with ImGui::GetInputTextState() -struct IMGUI_API ImGuiInputTextState -{ - ImGuiContext* Ctx; // parent UI context (needs to be set explicitly by parent). - ImGuiID ID; // widget id owning the text state - int CurLenW, CurLenA; // we need to maintain our buffer length in both UTF-8 and wchar format. UTF-8 length is valid even if TextA is not. - ImVector TextW; // edit buffer, we need to persist but can't guarantee the persistence of the user-provided buffer. so we copy into own buffer. - ImVector TextA; // temporary UTF8 buffer for callbacks and other operations. this is not updated in every code-path! size=capacity. - ImVector InitialTextA; // backup of end-user buffer at the time of focus (in UTF-8, unaltered) - bool TextAIsValid; // temporary UTF8 buffer is not initially valid before we make the widget active (until then we pull the data from user argument) - int BufCapacityA; // end-user buffer capacity - float ScrollX; // horizontal scrolling/offset - ImStb::STB_TexteditState Stb; // state for stb_textedit.h - float CursorAnim; // timer for cursor blink, reset on every user action so the cursor reappears immediately - bool CursorFollow; // set when we want scrolling to follow the current cursor position (not always!) - bool SelectedAllMouseLock; // after a double-click to select all, we ignore further mouse drags to update selection - bool Edited; // edited this frame - ImGuiInputTextFlags Flags; // copy of InputText() flags. may be used to check if e.g. ImGuiInputTextFlags_Password is set. - - ImGuiInputTextState() { memset(this, 0, sizeof(*this)); } - void ClearText() { CurLenW = CurLenA = 0; TextW[0] = 0; TextA[0] = 0; CursorClamp(); } - void ClearFreeMemory() { TextW.clear(); TextA.clear(); InitialTextA.clear(); } - int GetUndoAvailCount() const { return Stb.undostate.undo_point; } - int GetRedoAvailCount() const { return STB_TEXTEDIT_UNDOSTATECOUNT - Stb.undostate.redo_point; } - void OnKeyPressed(int key); // Cannot be inline because we call in code in stb_textedit.h implementation - - // Cursor & Selection - void CursorAnimReset() { CursorAnim = -0.30f; } // After a user-input the cursor stays on for a while without blinking - void CursorClamp() { Stb.cursor = ImMin(Stb.cursor, CurLenW); Stb.select_start = ImMin(Stb.select_start, CurLenW); Stb.select_end = ImMin(Stb.select_end, CurLenW); } - bool HasSelection() const { return Stb.select_start != Stb.select_end; } - void ClearSelection() { Stb.select_start = Stb.select_end = Stb.cursor; } - int GetCursorPos() const { return Stb.cursor; } - int GetSelectionStart() const { return Stb.select_start; } - int GetSelectionEnd() const { return Stb.select_end; } - void SelectAll() { Stb.select_start = 0; Stb.cursor = Stb.select_end = CurLenW; Stb.has_preferred_x = 0; } -}; - -// Storage for current popup stack -struct ImGuiPopupData -{ - ImGuiID PopupId; // Set on OpenPopup() - ImGuiWindow* Window; // Resolved on BeginPopup() - may stay unresolved if user never calls OpenPopup() - ImGuiWindow* BackupNavWindow;// Set on OpenPopup(), a NavWindow that will be restored on popup close - int ParentNavLayer; // Resolved on BeginPopup(). Actually a ImGuiNavLayer type (declared down below), initialized to -1 which is not part of an enum, but serves well-enough as "not any of layers" value - int OpenFrameCount; // Set on OpenPopup() - ImGuiID OpenParentId; // Set on OpenPopup(), we need this to differentiate multiple menu sets from each others (e.g. inside menu bar vs loose menu items) - ImVec2 OpenPopupPos; // Set on OpenPopup(), preferred popup position (typically == OpenMousePos when using mouse) - ImVec2 OpenMousePos; // Set on OpenPopup(), copy of mouse position at the time of opening popup - - ImGuiPopupData() { memset(this, 0, sizeof(*this)); ParentNavLayer = OpenFrameCount = -1; } -}; - -enum ImGuiNextWindowDataFlags_ -{ - ImGuiNextWindowDataFlags_None = 0, - ImGuiNextWindowDataFlags_HasPos = 1 << 0, - ImGuiNextWindowDataFlags_HasSize = 1 << 1, - ImGuiNextWindowDataFlags_HasContentSize = 1 << 2, - ImGuiNextWindowDataFlags_HasCollapsed = 1 << 3, - ImGuiNextWindowDataFlags_HasSizeConstraint = 1 << 4, - ImGuiNextWindowDataFlags_HasFocus = 1 << 5, - ImGuiNextWindowDataFlags_HasBgAlpha = 1 << 6, - ImGuiNextWindowDataFlags_HasScroll = 1 << 7, - ImGuiNextWindowDataFlags_HasViewport = 1 << 8, - ImGuiNextWindowDataFlags_HasDock = 1 << 9, - ImGuiNextWindowDataFlags_HasWindowClass = 1 << 10, -}; - -// Storage for SetNexWindow** functions -struct ImGuiNextWindowData -{ - ImGuiNextWindowDataFlags Flags; - ImGuiCond PosCond; - ImGuiCond SizeCond; - ImGuiCond CollapsedCond; - ImGuiCond DockCond; - ImVec2 PosVal; - ImVec2 PosPivotVal; - ImVec2 SizeVal; - ImVec2 ContentSizeVal; - ImVec2 ScrollVal; - bool PosUndock; - bool CollapsedVal; - ImRect SizeConstraintRect; - ImGuiSizeCallback SizeCallback; - void* SizeCallbackUserData; - float BgAlphaVal; // Override background alpha - ImGuiID ViewportId; - ImGuiID DockId; - ImGuiWindowClass WindowClass; - ImVec2 MenuBarOffsetMinVal; // (Always on) This is not exposed publicly, so we don't clear it and it doesn't have a corresponding flag (could we? for consistency?) - - ImGuiNextWindowData() { memset(this, 0, sizeof(*this)); } - inline void ClearFlags() { Flags = ImGuiNextWindowDataFlags_None; } -}; - -// Multi-Selection item index or identifier when using SetNextItemSelectionUserData()/BeginMultiSelect() -// (Most users are likely to use this store an item INDEX but this may be used to store a POINTER as well.) -typedef ImS64 ImGuiSelectionUserData; - -enum ImGuiNextItemDataFlags_ -{ - ImGuiNextItemDataFlags_None = 0, - ImGuiNextItemDataFlags_HasWidth = 1 << 0, - ImGuiNextItemDataFlags_HasOpen = 1 << 1, -}; - -struct ImGuiNextItemData -{ - ImGuiNextItemDataFlags Flags; - ImGuiItemFlags ItemFlags; // Currently only tested/used for ImGuiItemFlags_AllowOverlap. - // Non-flags members are NOT cleared by ItemAdd() meaning they are still valid during NavProcessItem() - float Width; // Set by SetNextItemWidth() - ImGuiSelectionUserData SelectionUserData; // Set by SetNextItemSelectionUserData() (note that NULL/0 is a valid value, we use -1 == ImGuiSelectionUserData_Invalid to mark invalid values) - ImGuiCond OpenCond; - bool OpenVal; // Set by SetNextItemOpen() - - ImGuiNextItemData() { memset(this, 0, sizeof(*this)); SelectionUserData = -1; } - inline void ClearFlags() { Flags = ImGuiNextItemDataFlags_None; ItemFlags = ImGuiItemFlags_None; } // Also cleared manually by ItemAdd()! -}; - -// Status storage for the last submitted item -struct ImGuiLastItemData -{ - ImGuiID ID; - ImGuiItemFlags InFlags; // See ImGuiItemFlags_ - ImGuiItemStatusFlags StatusFlags; // See ImGuiItemStatusFlags_ - ImRect Rect; // Full rectangle - ImRect NavRect; // Navigation scoring rectangle (not displayed) - ImRect DisplayRect; // Display rectangle (only if ImGuiItemStatusFlags_HasDisplayRect is set) - - ImGuiLastItemData() { memset(this, 0, sizeof(*this)); } -}; - -// Store data emitted by TreeNode() for usage by TreePop() to implement ImGuiTreeNodeFlags_NavLeftJumpsBackHere. -// This is the minimum amount of data that we need to perform the equivalent of NavApplyItemToResult() and which we can't infer in TreePop() -// Only stored when the node is a potential candidate for landing on a Left arrow jump. -struct ImGuiNavTreeNodeData -{ - ImGuiID ID; - ImGuiItemFlags InFlags; - ImRect NavRect; -}; - -struct IMGUI_API ImGuiStackSizes -{ - short SizeOfIDStack; - short SizeOfColorStack; - short SizeOfStyleVarStack; - short SizeOfFontStack; - short SizeOfFocusScopeStack; - short SizeOfGroupStack; - short SizeOfItemFlagsStack; - short SizeOfBeginPopupStack; - short SizeOfDisabledStack; - - ImGuiStackSizes() { memset(this, 0, sizeof(*this)); } - void SetToContextState(ImGuiContext* ctx); - void CompareWithContextState(ImGuiContext* ctx); -}; - -// Data saved for each window pushed into the stack -struct ImGuiWindowStackData -{ - ImGuiWindow* Window; - ImGuiLastItemData ParentLastItemDataBackup; - ImGuiStackSizes StackSizesOnBegin; // Store size of various stacks for asserting -}; - -struct ImGuiShrinkWidthItem -{ - int Index; - float Width; - float InitialWidth; -}; - -struct ImGuiPtrOrIndex -{ - void* Ptr; // Either field can be set, not both. e.g. Dock node tab bars are loose while BeginTabBar() ones are in a pool. - int Index; // Usually index in a main pool. - - ImGuiPtrOrIndex(void* ptr) { Ptr = ptr; Index = -1; } - ImGuiPtrOrIndex(int index) { Ptr = NULL; Index = index; } -}; - -//----------------------------------------------------------------------------- -// [SECTION] Inputs support -//----------------------------------------------------------------------------- - -// Bit array for named keys -typedef ImBitArray ImBitArrayForNamedKeys; - -// [Internal] Key ranges -#define ImGuiKey_LegacyNativeKey_BEGIN 0 -#define ImGuiKey_LegacyNativeKey_END 512 -#define ImGuiKey_Keyboard_BEGIN (ImGuiKey_NamedKey_BEGIN) -#define ImGuiKey_Keyboard_END (ImGuiKey_GamepadStart) -#define ImGuiKey_Gamepad_BEGIN (ImGuiKey_GamepadStart) -#define ImGuiKey_Gamepad_END (ImGuiKey_GamepadRStickDown + 1) -#define ImGuiKey_Mouse_BEGIN (ImGuiKey_MouseLeft) -#define ImGuiKey_Mouse_END (ImGuiKey_MouseWheelY + 1) -#define ImGuiKey_Aliases_BEGIN (ImGuiKey_Mouse_BEGIN) -#define ImGuiKey_Aliases_END (ImGuiKey_Mouse_END) - -// [Internal] Named shortcuts for Navigation -#define ImGuiKey_NavKeyboardTweakSlow ImGuiMod_Ctrl -#define ImGuiKey_NavKeyboardTweakFast ImGuiMod_Shift -#define ImGuiKey_NavGamepadTweakSlow ImGuiKey_GamepadL1 -#define ImGuiKey_NavGamepadTweakFast ImGuiKey_GamepadR1 -#define ImGuiKey_NavGamepadActivate ImGuiKey_GamepadFaceDown -#define ImGuiKey_NavGamepadCancel ImGuiKey_GamepadFaceRight -#define ImGuiKey_NavGamepadMenu ImGuiKey_GamepadFaceLeft -#define ImGuiKey_NavGamepadInput ImGuiKey_GamepadFaceUp - -enum ImGuiInputEventType -{ - ImGuiInputEventType_None = 0, - ImGuiInputEventType_MousePos, - ImGuiInputEventType_MouseWheel, - ImGuiInputEventType_MouseButton, - ImGuiInputEventType_MouseViewport, - ImGuiInputEventType_Key, - ImGuiInputEventType_Text, - ImGuiInputEventType_Focus, - ImGuiInputEventType_COUNT -}; - -enum ImGuiInputSource -{ - ImGuiInputSource_None = 0, - ImGuiInputSource_Mouse, // Note: may be Mouse or TouchScreen or Pen. See io.MouseSource to distinguish them. - ImGuiInputSource_Keyboard, - ImGuiInputSource_Gamepad, - ImGuiInputSource_Clipboard, // Currently only used by InputText() - ImGuiInputSource_COUNT -}; - -// FIXME: Structures in the union below need to be declared as anonymous unions appears to be an extension? -// Using ImVec2() would fail on Clang 'union member 'MousePos' has a non-trivial default constructor' -struct ImGuiInputEventMousePos { float PosX, PosY; ImGuiMouseSource MouseSource; }; -struct ImGuiInputEventMouseWheel { float WheelX, WheelY; ImGuiMouseSource MouseSource; }; -struct ImGuiInputEventMouseButton { int Button; bool Down; ImGuiMouseSource MouseSource; }; -struct ImGuiInputEventMouseViewport { ImGuiID HoveredViewportID; }; -struct ImGuiInputEventKey { ImGuiKey Key; bool Down; float AnalogValue; }; -struct ImGuiInputEventText { unsigned int Char; }; -struct ImGuiInputEventAppFocused { bool Focused; }; - -struct ImGuiInputEvent -{ - ImGuiInputEventType Type; - ImGuiInputSource Source; - ImU32 EventId; // Unique, sequential increasing integer to identify an event (if you need to correlate them to other data). - union - { - ImGuiInputEventMousePos MousePos; // if Type == ImGuiInputEventType_MousePos - ImGuiInputEventMouseWheel MouseWheel; // if Type == ImGuiInputEventType_MouseWheel - ImGuiInputEventMouseButton MouseButton; // if Type == ImGuiInputEventType_MouseButton - ImGuiInputEventMouseViewport MouseViewport; // if Type == ImGuiInputEventType_MouseViewport - ImGuiInputEventKey Key; // if Type == ImGuiInputEventType_Key - ImGuiInputEventText Text; // if Type == ImGuiInputEventType_Text - ImGuiInputEventAppFocused AppFocused; // if Type == ImGuiInputEventType_Focus - }; - bool AddedByTestEngine; - - ImGuiInputEvent() { memset(this, 0, sizeof(*this)); } -}; - -// Input function taking an 'ImGuiID owner_id' argument defaults to (ImGuiKeyOwner_Any == 0) aka don't test ownership, which matches legacy behavior. -#define ImGuiKeyOwner_Any ((ImGuiID)0) // Accept key that have an owner, UNLESS a call to SetKeyOwner() explicitly used ImGuiInputFlags_LockThisFrame or ImGuiInputFlags_LockUntilRelease. -#define ImGuiKeyOwner_None ((ImGuiID)-1) // Require key to have no owner. - -typedef ImS16 ImGuiKeyRoutingIndex; - -// Routing table entry (sizeof() == 16 bytes) -struct ImGuiKeyRoutingData -{ - ImGuiKeyRoutingIndex NextEntryIndex; - ImU16 Mods; // Technically we'd only need 4-bits but for simplify we store ImGuiMod_ values which need 16-bits. ImGuiMod_Shortcut is already translated to Ctrl/Super. - ImU8 RoutingNextScore; // Lower is better (0: perfect score) - ImGuiID RoutingCurr; - ImGuiID RoutingNext; - - ImGuiKeyRoutingData() { NextEntryIndex = -1; Mods = 0; RoutingNextScore = 255; RoutingCurr = RoutingNext = ImGuiKeyOwner_None; } -}; - -// Routing table: maintain a desired owner for each possible key-chord (key + mods), and setup owner in NewFrame() when mods are matching. -// Stored in main context (1 instance) -struct ImGuiKeyRoutingTable -{ - ImGuiKeyRoutingIndex Index[ImGuiKey_NamedKey_COUNT]; // Index of first entry in Entries[] - ImVector Entries; - ImVector EntriesNext; // Double-buffer to avoid reallocation (could use a shared buffer) - - ImGuiKeyRoutingTable() { Clear(); } - void Clear() { for (int n = 0; n < IM_ARRAYSIZE(Index); n++) Index[n] = -1; Entries.clear(); EntriesNext.clear(); } -}; - -// This extends ImGuiKeyData but only for named keys (legacy keys don't support the new features) -// Stored in main context (1 per named key). In the future it might be merged into ImGuiKeyData. -struct ImGuiKeyOwnerData -{ - ImGuiID OwnerCurr; - ImGuiID OwnerNext; - bool LockThisFrame; // Reading this key requires explicit owner id (until end of frame). Set by ImGuiInputFlags_LockThisFrame. - bool LockUntilRelease; // Reading this key requires explicit owner id (until key is released). Set by ImGuiInputFlags_LockUntilRelease. When this is true LockThisFrame is always true as well. - - ImGuiKeyOwnerData() { OwnerCurr = OwnerNext = ImGuiKeyOwner_None; LockThisFrame = LockUntilRelease = false; } -}; - -// Flags for extended versions of IsKeyPressed(), IsMouseClicked(), Shortcut(), SetKeyOwner(), SetItemKeyOwner() -// Don't mistake with ImGuiInputTextFlags! (for ImGui::InputText() function) -enum ImGuiInputFlags_ -{ - // Flags for IsKeyPressed(), IsMouseClicked(), Shortcut() - ImGuiInputFlags_None = 0, - ImGuiInputFlags_Repeat = 1 << 0, // Return true on successive repeats. Default for legacy IsKeyPressed(). NOT Default for legacy IsMouseClicked(). MUST BE == 1. - ImGuiInputFlags_RepeatRateDefault = 1 << 1, // Repeat rate: Regular (default) - ImGuiInputFlags_RepeatRateNavMove = 1 << 2, // Repeat rate: Fast - ImGuiInputFlags_RepeatRateNavTweak = 1 << 3, // Repeat rate: Faster - ImGuiInputFlags_RepeatRateMask_ = ImGuiInputFlags_RepeatRateDefault | ImGuiInputFlags_RepeatRateNavMove | ImGuiInputFlags_RepeatRateNavTweak, - - // Flags for SetItemKeyOwner() - ImGuiInputFlags_CondHovered = 1 << 4, // Only set if item is hovered (default to both) - ImGuiInputFlags_CondActive = 1 << 5, // Only set if item is active (default to both) - ImGuiInputFlags_CondDefault_ = ImGuiInputFlags_CondHovered | ImGuiInputFlags_CondActive, - ImGuiInputFlags_CondMask_ = ImGuiInputFlags_CondHovered | ImGuiInputFlags_CondActive, - - // Flags for SetKeyOwner(), SetItemKeyOwner() - ImGuiInputFlags_LockThisFrame = 1 << 6, // Access to key data will require EXPLICIT owner ID (ImGuiKeyOwner_Any/0 will NOT accepted for polling). Cleared at end of frame. This is useful to make input-owner-aware code steal keys from non-input-owner-aware code. - ImGuiInputFlags_LockUntilRelease = 1 << 7, // Access to key data will require EXPLICIT owner ID (ImGuiKeyOwner_Any/0 will NOT accepted for polling). Cleared when the key is released or at end of each frame if key is released. This is useful to make input-owner-aware code steal keys from non-input-owner-aware code. - - // Routing policies for Shortcut() + low-level SetShortcutRouting() - // - The general idea is that several callers register interest in a shortcut, and only one owner gets it. - // - When a policy (other than _RouteAlways) is set, Shortcut() will register itself with SetShortcutRouting(), - // allowing the system to decide where to route the input among other route-aware calls. - // - Shortcut() uses ImGuiInputFlags_RouteFocused by default: meaning that a simple Shortcut() poll - // will register a route and only succeed when parent window is in the focus stack and if no-one - // with a higher priority is claiming the shortcut. - // - Using ImGuiInputFlags_RouteAlways is roughly equivalent to doing e.g. IsKeyPressed(key) + testing mods. - // - Priorities: GlobalHigh > Focused (when owner is active item) > Global > Focused (when focused window) > GlobalLow. - // - Can select only 1 policy among all available. - ImGuiInputFlags_RouteFocused = 1 << 8, // (Default) Register focused route: Accept inputs if window is in focus stack. Deep-most focused window takes inputs. ActiveId takes inputs over deep-most focused window. - ImGuiInputFlags_RouteGlobalLow = 1 << 9, // Register route globally (lowest priority: unless a focused window or active item registered the route) -> recommended Global priority. - ImGuiInputFlags_RouteGlobal = 1 << 10, // Register route globally (medium priority: unless an active item registered the route, e.g. CTRL+A registered by InputText). - ImGuiInputFlags_RouteGlobalHigh = 1 << 11, // Register route globally (highest priority: unlikely you need to use that: will interfere with every active items) - ImGuiInputFlags_RouteMask_ = ImGuiInputFlags_RouteFocused | ImGuiInputFlags_RouteGlobal | ImGuiInputFlags_RouteGlobalLow | ImGuiInputFlags_RouteGlobalHigh, // _Always not part of this! - ImGuiInputFlags_RouteAlways = 1 << 12, // Do not register route, poll keys directly. - ImGuiInputFlags_RouteUnlessBgFocused= 1 << 13, // Global routes will not be applied if underlying background/void is focused (== no Dear ImGui windows are focused). Useful for overlay applications. - ImGuiInputFlags_RouteExtraMask_ = ImGuiInputFlags_RouteAlways | ImGuiInputFlags_RouteUnlessBgFocused, - - // [Internal] Mask of which function support which flags - ImGuiInputFlags_SupportedByIsKeyPressed = ImGuiInputFlags_Repeat | ImGuiInputFlags_RepeatRateMask_, - ImGuiInputFlags_SupportedByShortcut = ImGuiInputFlags_Repeat | ImGuiInputFlags_RepeatRateMask_ | ImGuiInputFlags_RouteMask_ | ImGuiInputFlags_RouteExtraMask_, - ImGuiInputFlags_SupportedBySetKeyOwner = ImGuiInputFlags_LockThisFrame | ImGuiInputFlags_LockUntilRelease, - ImGuiInputFlags_SupportedBySetItemKeyOwner = ImGuiInputFlags_SupportedBySetKeyOwner | ImGuiInputFlags_CondMask_, -}; - -//----------------------------------------------------------------------------- -// [SECTION] Clipper support -//----------------------------------------------------------------------------- - -// Note that Max is exclusive, so perhaps should be using a Begin/End convention. -struct ImGuiListClipperRange -{ - int Min; - int Max; - bool PosToIndexConvert; // Begin/End are absolute position (will be converted to indices later) - ImS8 PosToIndexOffsetMin; // Add to Min after converting to indices - ImS8 PosToIndexOffsetMax; // Add to Min after converting to indices - - static ImGuiListClipperRange FromIndices(int min, int max) { ImGuiListClipperRange r = { min, max, false, 0, 0 }; return r; } - static ImGuiListClipperRange FromPositions(float y1, float y2, int off_min, int off_max) { ImGuiListClipperRange r = { (int)y1, (int)y2, true, (ImS8)off_min, (ImS8)off_max }; return r; } -}; - -// Temporary clipper data, buffers shared/reused between instances -struct ImGuiListClipperData -{ - ImGuiListClipper* ListClipper; - float LossynessOffset; - int StepNo; - int ItemsFrozen; - ImVector Ranges; - - ImGuiListClipperData() { memset(this, 0, sizeof(*this)); } - void Reset(ImGuiListClipper* clipper) { ListClipper = clipper; StepNo = ItemsFrozen = 0; Ranges.resize(0); } -}; - -//----------------------------------------------------------------------------- -// [SECTION] Navigation support -//----------------------------------------------------------------------------- - -enum ImGuiActivateFlags_ -{ - ImGuiActivateFlags_None = 0, - ImGuiActivateFlags_PreferInput = 1 << 0, // Favor activation that requires keyboard text input (e.g. for Slider/Drag). Default for Enter key. - ImGuiActivateFlags_PreferTweak = 1 << 1, // Favor activation for tweaking with arrows or gamepad (e.g. for Slider/Drag). Default for Space key and if keyboard is not used. - ImGuiActivateFlags_TryToPreserveState = 1 << 2, // Request widget to preserve state if it can (e.g. InputText will try to preserve cursor/selection) -}; - -// Early work-in-progress API for ScrollToItem() -enum ImGuiScrollFlags_ -{ - ImGuiScrollFlags_None = 0, - ImGuiScrollFlags_KeepVisibleEdgeX = 1 << 0, // If item is not visible: scroll as little as possible on X axis to bring item back into view [default for X axis] - ImGuiScrollFlags_KeepVisibleEdgeY = 1 << 1, // If item is not visible: scroll as little as possible on Y axis to bring item back into view [default for Y axis for windows that are already visible] - ImGuiScrollFlags_KeepVisibleCenterX = 1 << 2, // If item is not visible: scroll to make the item centered on X axis [rarely used] - ImGuiScrollFlags_KeepVisibleCenterY = 1 << 3, // If item is not visible: scroll to make the item centered on Y axis - ImGuiScrollFlags_AlwaysCenterX = 1 << 4, // Always center the result item on X axis [rarely used] - ImGuiScrollFlags_AlwaysCenterY = 1 << 5, // Always center the result item on Y axis [default for Y axis for appearing window) - ImGuiScrollFlags_NoScrollParent = 1 << 6, // Disable forwarding scrolling to parent window if required to keep item/rect visible (only scroll window the function was applied to). - ImGuiScrollFlags_MaskX_ = ImGuiScrollFlags_KeepVisibleEdgeX | ImGuiScrollFlags_KeepVisibleCenterX | ImGuiScrollFlags_AlwaysCenterX, - ImGuiScrollFlags_MaskY_ = ImGuiScrollFlags_KeepVisibleEdgeY | ImGuiScrollFlags_KeepVisibleCenterY | ImGuiScrollFlags_AlwaysCenterY, -}; - -enum ImGuiNavHighlightFlags_ -{ - ImGuiNavHighlightFlags_None = 0, - ImGuiNavHighlightFlags_TypeDefault = 1 << 0, - ImGuiNavHighlightFlags_TypeThin = 1 << 1, - ImGuiNavHighlightFlags_AlwaysDraw = 1 << 2, // Draw rectangular highlight if (g.NavId == id) _even_ when using the mouse. - ImGuiNavHighlightFlags_NoRounding = 1 << 3, -}; - -enum ImGuiNavMoveFlags_ -{ - ImGuiNavMoveFlags_None = 0, - ImGuiNavMoveFlags_LoopX = 1 << 0, // On failed request, restart from opposite side - ImGuiNavMoveFlags_LoopY = 1 << 1, - ImGuiNavMoveFlags_WrapX = 1 << 2, // On failed request, request from opposite side one line down (when NavDir==right) or one line up (when NavDir==left) - ImGuiNavMoveFlags_WrapY = 1 << 3, // This is not super useful but provided for completeness - ImGuiNavMoveFlags_WrapMask_ = ImGuiNavMoveFlags_LoopX | ImGuiNavMoveFlags_LoopY | ImGuiNavMoveFlags_WrapX | ImGuiNavMoveFlags_WrapY, - ImGuiNavMoveFlags_AllowCurrentNavId = 1 << 4, // Allow scoring and considering the current NavId as a move target candidate. This is used when the move source is offset (e.g. pressing PageDown actually needs to send a Up move request, if we are pressing PageDown from the bottom-most item we need to stay in place) - ImGuiNavMoveFlags_AlsoScoreVisibleSet = 1 << 5, // Store alternate result in NavMoveResultLocalVisible that only comprise elements that are already fully visible (used by PageUp/PageDown) - ImGuiNavMoveFlags_ScrollToEdgeY = 1 << 6, // Force scrolling to min/max (used by Home/End) // FIXME-NAV: Aim to remove or reword, probably unnecessary - ImGuiNavMoveFlags_Forwarded = 1 << 7, - ImGuiNavMoveFlags_DebugNoResult = 1 << 8, // Dummy scoring for debug purpose, don't apply result - ImGuiNavMoveFlags_FocusApi = 1 << 9, // Requests from focus API can land/focus/activate items even if they are marked with _NoTabStop (see NavProcessItemForTabbingRequest() for details) - ImGuiNavMoveFlags_IsTabbing = 1 << 10, // == Focus + Activate if item is Inputable + DontChangeNavHighlight - ImGuiNavMoveFlags_IsPageMove = 1 << 11, // Identify a PageDown/PageUp request. - ImGuiNavMoveFlags_Activate = 1 << 12, // Activate/select target item. - ImGuiNavMoveFlags_NoSelect = 1 << 13, // Don't trigger selection by not setting g.NavJustMovedTo - ImGuiNavMoveFlags_NoSetNavHighlight = 1 << 14, // Do not alter the visible state of keyboard vs mouse nav highlight -}; - -enum ImGuiNavLayer -{ - ImGuiNavLayer_Main = 0, // Main scrolling layer - ImGuiNavLayer_Menu = 1, // Menu layer (access with Alt) - ImGuiNavLayer_COUNT -}; - -struct ImGuiNavItemData -{ - ImGuiWindow* Window; // Init,Move // Best candidate window (result->ItemWindow->RootWindowForNav == request->Window) - ImGuiID ID; // Init,Move // Best candidate item ID - ImGuiID FocusScopeId; // Init,Move // Best candidate focus scope ID - ImRect RectRel; // Init,Move // Best candidate bounding box in window relative space - ImGuiItemFlags InFlags; // ????,Move // Best candidate item flags - ImGuiSelectionUserData SelectionUserData;//I+Mov // Best candidate SetNextItemSelectionData() value. - float DistBox; // Move // Best candidate box distance to current NavId - float DistCenter; // Move // Best candidate center distance to current NavId - float DistAxial; // Move // Best candidate axial distance to current NavId - - ImGuiNavItemData() { Clear(); } - void Clear() { Window = NULL; ID = FocusScopeId = 0; InFlags = 0; SelectionUserData = -1; DistBox = DistCenter = DistAxial = FLT_MAX; } -}; - -//----------------------------------------------------------------------------- -// [SECTION] Typing-select support -//----------------------------------------------------------------------------- - -// Flags for GetTypingSelectRequest() -enum ImGuiTypingSelectFlags_ -{ - ImGuiTypingSelectFlags_None = 0, - ImGuiTypingSelectFlags_AllowBackspace = 1 << 0, // Backspace to delete character inputs. If using: ensure GetTypingSelectRequest() is not called more than once per frame (filter by e.g. focus state) - ImGuiTypingSelectFlags_AllowSingleCharMode = 1 << 1, // Allow "single char" search mode which is activated when pressing the same character multiple times. -}; - -// Returned by GetTypingSelectRequest(), designed to eventually be public. -struct IMGUI_API ImGuiTypingSelectRequest -{ - ImGuiTypingSelectFlags Flags; // Flags passed to GetTypingSelectRequest() - int SearchBufferLen; - const char* SearchBuffer; // Search buffer contents (use full string. unless SingleCharMode is set, in which case use SingleCharSize). - bool SelectRequest; // Set when buffer was modified this frame, requesting a selection. - bool SingleCharMode; // Notify when buffer contains same character repeated, to implement special mode. In this situation it preferred to not display any on-screen search indication. - ImS8 SingleCharSize; // Length in bytes of first letter codepoint (1 for ascii, 2-4 for UTF-8). If (SearchBufferLen==RepeatCharSize) only 1 letter has been input. -}; - -// Storage for GetTypingSelectRequest() -struct IMGUI_API ImGuiTypingSelectState -{ - ImGuiTypingSelectRequest Request; // User-facing data - char SearchBuffer[64]; // Search buffer: no need to make dynamic as this search is very transient. - ImGuiID FocusScope; - int LastRequestFrame = 0; - float LastRequestTime = 0.0f; - bool SingleCharModeLock = false; // After a certain single char repeat count we lock into SingleCharMode. Two benefits: 1) buffer never fill, 2) we can provide an immediate SingleChar mode without timer elapsing. - - ImGuiTypingSelectState() { memset(this, 0, sizeof(*this)); } - void Clear() { SearchBuffer[0] = 0; SingleCharModeLock = false; } // We preserve remaining data for easier debugging -}; - -//----------------------------------------------------------------------------- -// [SECTION] Columns support -//----------------------------------------------------------------------------- - -// Flags for internal's BeginColumns(). Prefix using BeginTable() nowadays! -enum ImGuiOldColumnFlags_ -{ - ImGuiOldColumnFlags_None = 0, - ImGuiOldColumnFlags_NoBorder = 1 << 0, // Disable column dividers - ImGuiOldColumnFlags_NoResize = 1 << 1, // Disable resizing columns when clicking on the dividers - ImGuiOldColumnFlags_NoPreserveWidths = 1 << 2, // Disable column width preservation when adjusting columns - ImGuiOldColumnFlags_NoForceWithinWindow = 1 << 3, // Disable forcing columns to fit within window - ImGuiOldColumnFlags_GrowParentContentsSize = 1 << 4, // (WIP) Restore pre-1.51 behavior of extending the parent window contents size but _without affecting the columns width at all_. Will eventually remove. - - // Obsolete names (will be removed) -#ifndef IMGUI_DISABLE_OBSOLETE_FUNCTIONS - ImGuiColumnsFlags_None = ImGuiOldColumnFlags_None, - ImGuiColumnsFlags_NoBorder = ImGuiOldColumnFlags_NoBorder, - ImGuiColumnsFlags_NoResize = ImGuiOldColumnFlags_NoResize, - ImGuiColumnsFlags_NoPreserveWidths = ImGuiOldColumnFlags_NoPreserveWidths, - ImGuiColumnsFlags_NoForceWithinWindow = ImGuiOldColumnFlags_NoForceWithinWindow, - ImGuiColumnsFlags_GrowParentContentsSize = ImGuiOldColumnFlags_GrowParentContentsSize, -#endif -}; - -struct ImGuiOldColumnData -{ - float OffsetNorm; // Column start offset, normalized 0.0 (far left) -> 1.0 (far right) - float OffsetNormBeforeResize; - ImGuiOldColumnFlags Flags; // Not exposed - ImRect ClipRect; - - ImGuiOldColumnData() { memset(this, 0, sizeof(*this)); } -}; - -struct ImGuiOldColumns -{ - ImGuiID ID; - ImGuiOldColumnFlags Flags; - bool IsFirstFrame; - bool IsBeingResized; - int Current; - int Count; - float OffMinX, OffMaxX; // Offsets from HostWorkRect.Min.x - float LineMinY, LineMaxY; - float HostCursorPosY; // Backup of CursorPos at the time of BeginColumns() - float HostCursorMaxPosX; // Backup of CursorMaxPos at the time of BeginColumns() - ImRect HostInitialClipRect; // Backup of ClipRect at the time of BeginColumns() - ImRect HostBackupClipRect; // Backup of ClipRect during PushColumnsBackground()/PopColumnsBackground() - ImRect HostBackupParentWorkRect;//Backup of WorkRect at the time of BeginColumns() - ImVector Columns; - ImDrawListSplitter Splitter; - - ImGuiOldColumns() { memset(this, 0, sizeof(*this)); } -}; - -//----------------------------------------------------------------------------- -// [SECTION] Multi-select support -//----------------------------------------------------------------------------- - -// We always assume that -1 is an invalid value (which works for indices and pointers) -#define ImGuiSelectionUserData_Invalid ((ImGuiSelectionUserData)-1) - -#ifdef IMGUI_HAS_MULTI_SELECT -// -#endif // #ifdef IMGUI_HAS_MULTI_SELECT - -//----------------------------------------------------------------------------- -// [SECTION] Docking support -//----------------------------------------------------------------------------- - -#define DOCKING_HOST_DRAW_CHANNEL_BG 0 // Dock host: background fill -#define DOCKING_HOST_DRAW_CHANNEL_FG 1 // Dock host: decorations and contents - -#ifdef IMGUI_HAS_DOCK - -// Extend ImGuiDockNodeFlags_ -enum ImGuiDockNodeFlagsPrivate_ -{ - // [Internal] - ImGuiDockNodeFlags_DockSpace = 1 << 10, // Saved // A dockspace is a node that occupy space within an existing user window. Otherwise the node is floating and create its own window. - ImGuiDockNodeFlags_CentralNode = 1 << 11, // Saved // The central node has 2 main properties: stay visible when empty, only use "remaining" spaces from its neighbor. - ImGuiDockNodeFlags_NoTabBar = 1 << 12, // Saved // Tab bar is completely unavailable. No triangle in the corner to enable it back. - ImGuiDockNodeFlags_HiddenTabBar = 1 << 13, // Saved // Tab bar is hidden, with a triangle in the corner to show it again (NB: actual tab-bar instance may be destroyed as this is only used for single-window tab bar) - ImGuiDockNodeFlags_NoWindowMenuButton = 1 << 14, // Saved // Disable window/docking menu (that one that appears instead of the collapse button) - ImGuiDockNodeFlags_NoCloseButton = 1 << 15, // Saved // Disable close button - ImGuiDockNodeFlags_NoResizeX = 1 << 16, // // - ImGuiDockNodeFlags_NoResizeY = 1 << 17, // // - // Disable docking/undocking actions in this dockspace or individual node (existing docked nodes will be preserved) - // Those are not exposed in public because the desirable sharing/inheriting/copy-flag-on-split behaviors are quite difficult to design and understand. - // The two public flags ImGuiDockNodeFlags_NoDockingOverCentralNode/ImGuiDockNodeFlags_NoDockingSplit don't have those issues. - ImGuiDockNodeFlags_NoDockingSplitOther = 1 << 19, // // Disable this node from splitting other windows/nodes. - ImGuiDockNodeFlags_NoDockingOverMe = 1 << 20, // // Disable other windows/nodes from being docked over this node. - ImGuiDockNodeFlags_NoDockingOverOther = 1 << 21, // // Disable this node from being docked over another window or non-empty node. - ImGuiDockNodeFlags_NoDockingOverEmpty = 1 << 22, // // Disable this node from being docked over an empty node (e.g. DockSpace with no other windows) - ImGuiDockNodeFlags_NoDocking = ImGuiDockNodeFlags_NoDockingOverMe | ImGuiDockNodeFlags_NoDockingOverOther | ImGuiDockNodeFlags_NoDockingOverEmpty | ImGuiDockNodeFlags_NoDockingSplit | ImGuiDockNodeFlags_NoDockingSplitOther, - // Masks - ImGuiDockNodeFlags_SharedFlagsInheritMask_ = ~0, - ImGuiDockNodeFlags_NoResizeFlagsMask_ = ImGuiDockNodeFlags_NoResize | ImGuiDockNodeFlags_NoResizeX | ImGuiDockNodeFlags_NoResizeY, - // When splitting, those local flags are moved to the inheriting child, never duplicated - ImGuiDockNodeFlags_LocalFlagsTransferMask_ = ImGuiDockNodeFlags_NoDockingSplit | ImGuiDockNodeFlags_NoResizeFlagsMask_ | ImGuiDockNodeFlags_AutoHideTabBar | ImGuiDockNodeFlags_CentralNode | ImGuiDockNodeFlags_NoTabBar | ImGuiDockNodeFlags_HiddenTabBar | ImGuiDockNodeFlags_NoWindowMenuButton | ImGuiDockNodeFlags_NoCloseButton, - ImGuiDockNodeFlags_SavedFlagsMask_ = ImGuiDockNodeFlags_NoResizeFlagsMask_ | ImGuiDockNodeFlags_DockSpace | ImGuiDockNodeFlags_CentralNode | ImGuiDockNodeFlags_NoTabBar | ImGuiDockNodeFlags_HiddenTabBar | ImGuiDockNodeFlags_NoWindowMenuButton | ImGuiDockNodeFlags_NoCloseButton, -}; - -// Store the source authority (dock node vs window) of a field -enum ImGuiDataAuthority_ -{ - ImGuiDataAuthority_Auto, - ImGuiDataAuthority_DockNode, - ImGuiDataAuthority_Window, -}; - -enum ImGuiDockNodeState -{ - ImGuiDockNodeState_Unknown, - ImGuiDockNodeState_HostWindowHiddenBecauseSingleWindow, - ImGuiDockNodeState_HostWindowHiddenBecauseWindowsAreResizing, - ImGuiDockNodeState_HostWindowVisible, -}; - -// sizeof() 156~192 -struct IMGUI_API ImGuiDockNode -{ - ImGuiID ID; - ImGuiDockNodeFlags SharedFlags; // (Write) Flags shared by all nodes of a same dockspace hierarchy (inherited from the root node) - ImGuiDockNodeFlags LocalFlags; // (Write) Flags specific to this node - ImGuiDockNodeFlags LocalFlagsInWindows; // (Write) Flags specific to this node, applied from windows - ImGuiDockNodeFlags MergedFlags; // (Read) Effective flags (== SharedFlags | LocalFlagsInNode | LocalFlagsInWindows) - ImGuiDockNodeState State; - ImGuiDockNode* ParentNode; - ImGuiDockNode* ChildNodes[2]; // [Split node only] Child nodes (left/right or top/bottom). Consider switching to an array. - ImVector Windows; // Note: unordered list! Iterate TabBar->Tabs for user-order. - ImGuiTabBar* TabBar; - ImVec2 Pos; // Current position - ImVec2 Size; // Current size - ImVec2 SizeRef; // [Split node only] Last explicitly written-to size (overridden when using a splitter affecting the node), used to calculate Size. - ImGuiAxis SplitAxis; // [Split node only] Split axis (X or Y) - ImGuiWindowClass WindowClass; // [Root node only] - ImU32 LastBgColor; - - ImGuiWindow* HostWindow; - ImGuiWindow* VisibleWindow; // Generally point to window which is ID is == SelectedTabID, but when CTRL+Tabbing this can be a different window. - ImGuiDockNode* CentralNode; // [Root node only] Pointer to central node. - ImGuiDockNode* OnlyNodeWithWindows; // [Root node only] Set when there is a single visible node within the hierarchy. - int CountNodeWithWindows; // [Root node only] - int LastFrameAlive; // Last frame number the node was updated or kept alive explicitly with DockSpace() + ImGuiDockNodeFlags_KeepAliveOnly - int LastFrameActive; // Last frame number the node was updated. - int LastFrameFocused; // Last frame number the node was focused. - ImGuiID LastFocusedNodeId; // [Root node only] Which of our child docking node (any ancestor in the hierarchy) was last focused. - ImGuiID SelectedTabId; // [Leaf node only] Which of our tab/window is selected. - ImGuiID WantCloseTabId; // [Leaf node only] Set when closing a specific tab/window. - ImGuiID RefViewportId; // Reference viewport ID from visible window when HostWindow == NULL. - ImGuiDataAuthority AuthorityForPos :3; - ImGuiDataAuthority AuthorityForSize :3; - ImGuiDataAuthority AuthorityForViewport :3; - bool IsVisible :1; // Set to false when the node is hidden (usually disabled as it has no active window) - bool IsFocused :1; - bool IsBgDrawnThisFrame :1; - bool HasCloseButton :1; // Provide space for a close button (if any of the docked window has one). Note that button may be hidden on window without one. - bool HasWindowMenuButton :1; - bool HasCentralNodeChild :1; - bool WantCloseAll :1; // Set when closing all tabs at once. - bool WantLockSizeOnce :1; - bool WantMouseMove :1; // After a node extraction we need to transition toward moving the newly created host window - bool WantHiddenTabBarUpdate :1; - bool WantHiddenTabBarToggle :1; - - ImGuiDockNode(ImGuiID id); - ~ImGuiDockNode(); - bool IsRootNode() const { return ParentNode == NULL; } - bool IsDockSpace() const { return (MergedFlags & ImGuiDockNodeFlags_DockSpace) != 0; } - bool IsFloatingNode() const { return ParentNode == NULL && (MergedFlags & ImGuiDockNodeFlags_DockSpace) == 0; } - bool IsCentralNode() const { return (MergedFlags & ImGuiDockNodeFlags_CentralNode) != 0; } - bool IsHiddenTabBar() const { return (MergedFlags & ImGuiDockNodeFlags_HiddenTabBar) != 0; } // Hidden tab bar can be shown back by clicking the small triangle - bool IsNoTabBar() const { return (MergedFlags & ImGuiDockNodeFlags_NoTabBar) != 0; } // Never show a tab bar - bool IsSplitNode() const { return ChildNodes[0] != NULL; } - bool IsLeafNode() const { return ChildNodes[0] == NULL; } - bool IsEmpty() const { return ChildNodes[0] == NULL && Windows.Size == 0; } - ImRect Rect() const { return ImRect(Pos.x, Pos.y, Pos.x + Size.x, Pos.y + Size.y); } - - void SetLocalFlags(ImGuiDockNodeFlags flags) { LocalFlags = flags; UpdateMergedFlags(); } - void UpdateMergedFlags() { MergedFlags = SharedFlags | LocalFlags | LocalFlagsInWindows; } -}; - -// List of colors that are stored at the time of Begin() into Docked Windows. -// We currently store the packed colors in a simple array window->DockStyle.Colors[]. -// A better solution may involve appending into a log of colors in ImGuiContext + store offsets into those arrays in ImGuiWindow, -// but it would be more complex as we'd need to double-buffer both as e.g. drop target may refer to window from last frame. -enum ImGuiWindowDockStyleCol -{ - ImGuiWindowDockStyleCol_Text, - ImGuiWindowDockStyleCol_Tab, - ImGuiWindowDockStyleCol_TabHovered, - ImGuiWindowDockStyleCol_TabActive, - ImGuiWindowDockStyleCol_TabUnfocused, - ImGuiWindowDockStyleCol_TabUnfocusedActive, - ImGuiWindowDockStyleCol_COUNT -}; - -struct ImGuiWindowDockStyle -{ - ImU32 Colors[ImGuiWindowDockStyleCol_COUNT]; -}; - -struct ImGuiDockContext -{ - ImGuiStorage Nodes; // Map ID -> ImGuiDockNode*: Active nodes - ImVector Requests; - ImVector NodesSettings; - bool WantFullRebuild; - ImGuiDockContext() { memset(this, 0, sizeof(*this)); } -}; - -#endif // #ifdef IMGUI_HAS_DOCK - -//----------------------------------------------------------------------------- -// [SECTION] Viewport support -//----------------------------------------------------------------------------- - -// ImGuiViewport Private/Internals fields (cardinal sin: we are using inheritance!) -// Every instance of ImGuiViewport is in fact a ImGuiViewportP. -struct ImGuiViewportP : public ImGuiViewport -{ - ImGuiWindow* Window; // Set when the viewport is owned by a window (and ImGuiViewportFlags_CanHostOtherWindows is NOT set) - int Idx; - int LastFrameActive; // Last frame number this viewport was activated by a window - int LastFocusedStampCount; // Last stamp number from when a window hosted by this viewport was focused (by comparing this value between two viewport we have an implicit viewport z-order we use as fallback) - ImGuiID LastNameHash; - ImVec2 LastPos; - float Alpha; // Window opacity (when dragging dockable windows/viewports we make them transparent) - float LastAlpha; - bool LastFocusedHadNavWindow;// Instead of maintaining a LastFocusedWindow (which may harder to correctly maintain), we merely store weither NavWindow != NULL last time the viewport was focused. - short PlatformMonitor; - int BgFgDrawListsLastFrame[2]; // Last frame number the background (0) and foreground (1) draw lists were used - ImDrawList* BgFgDrawLists[2]; // Convenience background (0) and foreground (1) draw lists. We use them to draw software mouser cursor when io.MouseDrawCursor is set and to draw most debug overlays. - ImDrawData DrawDataP; - ImDrawDataBuilder DrawDataBuilder; // Temporary data while building final ImDrawData - ImVec2 LastPlatformPos; - ImVec2 LastPlatformSize; - ImVec2 LastRendererSize; - ImVec2 WorkOffsetMin; // Work Area: Offset from Pos to top-left corner of Work Area. Generally (0,0) or (0,+main_menu_bar_height). Work Area is Full Area but without menu-bars/status-bars (so WorkArea always fit inside Pos/Size!) - ImVec2 WorkOffsetMax; // Work Area: Offset from Pos+Size to bottom-right corner of Work Area. Generally (0,0) or (0,-status_bar_height). - ImVec2 BuildWorkOffsetMin; // Work Area: Offset being built during current frame. Generally >= 0.0f. - ImVec2 BuildWorkOffsetMax; // Work Area: Offset being built during current frame. Generally <= 0.0f. - - ImGuiViewportP() { Window = NULL; Idx = -1; LastFrameActive = BgFgDrawListsLastFrame[0] = BgFgDrawListsLastFrame[1] = LastFocusedStampCount = -1; LastNameHash = 0; Alpha = LastAlpha = 1.0f; LastFocusedHadNavWindow = false; PlatformMonitor = -1; BgFgDrawLists[0] = BgFgDrawLists[1] = NULL; LastPlatformPos = LastPlatformSize = LastRendererSize = ImVec2(FLT_MAX, FLT_MAX); } - ~ImGuiViewportP() { if (BgFgDrawLists[0]) IM_DELETE(BgFgDrawLists[0]); if (BgFgDrawLists[1]) IM_DELETE(BgFgDrawLists[1]); } - void ClearRequestFlags() { PlatformRequestClose = PlatformRequestMove = PlatformRequestResize = false; } - - // Calculate work rect pos/size given a set of offset (we have 1 pair of offset for rect locked from last frame data, and 1 pair for currently building rect) - ImVec2 CalcWorkRectPos(const ImVec2& off_min) const { return ImVec2(Pos.x + off_min.x, Pos.y + off_min.y); } - ImVec2 CalcWorkRectSize(const ImVec2& off_min, const ImVec2& off_max) const { return ImVec2(ImMax(0.0f, Size.x - off_min.x + off_max.x), ImMax(0.0f, Size.y - off_min.y + off_max.y)); } - void UpdateWorkRect() { WorkPos = CalcWorkRectPos(WorkOffsetMin); WorkSize = CalcWorkRectSize(WorkOffsetMin, WorkOffsetMax); } // Update public fields - - // Helpers to retrieve ImRect (we don't need to store BuildWorkRect as every access tend to change it, hence the code asymmetry) - ImRect GetMainRect() const { return ImRect(Pos.x, Pos.y, Pos.x + Size.x, Pos.y + Size.y); } - ImRect GetWorkRect() const { return ImRect(WorkPos.x, WorkPos.y, WorkPos.x + WorkSize.x, WorkPos.y + WorkSize.y); } - ImRect GetBuildWorkRect() const { ImVec2 pos = CalcWorkRectPos(BuildWorkOffsetMin); ImVec2 size = CalcWorkRectSize(BuildWorkOffsetMin, BuildWorkOffsetMax); return ImRect(pos.x, pos.y, pos.x + size.x, pos.y + size.y); } -}; - -//----------------------------------------------------------------------------- -// [SECTION] Settings support -//----------------------------------------------------------------------------- - -// Windows data saved in imgui.ini file -// Because we never destroy or rename ImGuiWindowSettings, we can store the names in a separate buffer easily. -// (this is designed to be stored in a ImChunkStream buffer, with the variable-length Name following our structure) -struct ImGuiWindowSettings -{ - ImGuiID ID; - ImVec2ih Pos; // NB: Settings position are stored RELATIVE to the viewport! Whereas runtime ones are absolute positions. - ImVec2ih Size; - ImVec2ih ViewportPos; - ImGuiID ViewportId; - ImGuiID DockId; // ID of last known DockNode (even if the DockNode is invisible because it has only 1 active window), or 0 if none. - ImGuiID ClassId; // ID of window class if specified - short DockOrder; // Order of the last time the window was visible within its DockNode. This is used to reorder windows that are reappearing on the same frame. Same value between windows that were active and windows that were none are possible. - bool Collapsed; - bool WantApply; // Set when loaded from .ini data (to enable merging/loading .ini data into an already running context) - bool WantDelete; // Set to invalidate/delete the settings entry - - ImGuiWindowSettings() { memset(this, 0, sizeof(*this)); DockOrder = -1; } - char* GetName() { return (char*)(this + 1); } -}; - -struct ImGuiSettingsHandler -{ - const char* TypeName; // Short description stored in .ini file. Disallowed characters: '[' ']' - ImGuiID TypeHash; // == ImHashStr(TypeName) - void (*ClearAllFn)(ImGuiContext* ctx, ImGuiSettingsHandler* handler); // Clear all settings data - void (*ReadInitFn)(ImGuiContext* ctx, ImGuiSettingsHandler* handler); // Read: Called before reading (in registration order) - void* (*ReadOpenFn)(ImGuiContext* ctx, ImGuiSettingsHandler* handler, const char* name); // Read: Called when entering into a new ini entry e.g. "[Window][Name]" - void (*ReadLineFn)(ImGuiContext* ctx, ImGuiSettingsHandler* handler, void* entry, const char* line); // Read: Called for every line of text within an ini entry - void (*ApplyAllFn)(ImGuiContext* ctx, ImGuiSettingsHandler* handler); // Read: Called after reading (in registration order) - void (*WriteAllFn)(ImGuiContext* ctx, ImGuiSettingsHandler* handler, ImGuiTextBuffer* out_buf); // Write: Output every entries into 'out_buf' - void* UserData; - - ImGuiSettingsHandler() { memset(this, 0, sizeof(*this)); } -}; - -//----------------------------------------------------------------------------- -// [SECTION] Localization support -//----------------------------------------------------------------------------- - -// This is experimental and not officially supported, it'll probably fall short of features, if/when it does we may backtrack. -enum ImGuiLocKey : int -{ - ImGuiLocKey_VersionStr, - ImGuiLocKey_TableSizeOne, - ImGuiLocKey_TableSizeAllFit, - ImGuiLocKey_TableSizeAllDefault, - ImGuiLocKey_TableResetOrder, - ImGuiLocKey_WindowingMainMenuBar, - ImGuiLocKey_WindowingPopup, - ImGuiLocKey_WindowingUntitled, - ImGuiLocKey_DockingHideTabBar, - ImGuiLocKey_DockingHoldShiftToDock, - ImGuiLocKey_COUNT -}; - -struct ImGuiLocEntry -{ - ImGuiLocKey Key; - const char* Text; -}; - - -//----------------------------------------------------------------------------- -// [SECTION] Metrics, Debug Tools -//----------------------------------------------------------------------------- - -enum ImGuiDebugLogFlags_ -{ - // Event types - ImGuiDebugLogFlags_None = 0, - ImGuiDebugLogFlags_EventActiveId = 1 << 0, - ImGuiDebugLogFlags_EventFocus = 1 << 1, - ImGuiDebugLogFlags_EventPopup = 1 << 2, - ImGuiDebugLogFlags_EventNav = 1 << 3, - ImGuiDebugLogFlags_EventClipper = 1 << 4, - ImGuiDebugLogFlags_EventSelection = 1 << 5, - ImGuiDebugLogFlags_EventIO = 1 << 6, - ImGuiDebugLogFlags_EventDocking = 1 << 7, - ImGuiDebugLogFlags_EventViewport = 1 << 8, - ImGuiDebugLogFlags_EventMask_ = ImGuiDebugLogFlags_EventActiveId | ImGuiDebugLogFlags_EventFocus | ImGuiDebugLogFlags_EventPopup | ImGuiDebugLogFlags_EventNav | ImGuiDebugLogFlags_EventClipper | ImGuiDebugLogFlags_EventSelection | ImGuiDebugLogFlags_EventIO | ImGuiDebugLogFlags_EventDocking | ImGuiDebugLogFlags_EventViewport, - ImGuiDebugLogFlags_OutputToTTY = 1 << 10, // Also send output to TTY - ImGuiDebugLogFlags_OutputToTestEngine = 1 << 11,// Also send output to Test Engine -}; - -struct ImGuiDebugAllocEntry -{ - int FrameCount; - ImS16 AllocCount; - ImS16 FreeCount; -}; - -struct ImGuiDebugAllocInfo -{ - int TotalAllocCount; // Number of call to MemAlloc(). - int TotalFreeCount; - ImS16 LastEntriesIdx; // Current index in buffer - ImGuiDebugAllocEntry LastEntriesBuf[6]; // Track last 6 frames that had allocations - - ImGuiDebugAllocInfo() { memset(this, 0, sizeof(*this)); } -}; - -struct ImGuiMetricsConfig -{ - bool ShowDebugLog = false; - bool ShowIDStackTool = false; - bool ShowWindowsRects = false; - bool ShowWindowsBeginOrder = false; - bool ShowTablesRects = false; - bool ShowDrawCmdMesh = true; - bool ShowDrawCmdBoundingBoxes = true; - bool ShowAtlasTintedWithTextColor = false; - bool ShowDockingNodes = false; - int ShowWindowsRectsType = -1; - int ShowTablesRectsType = -1; -}; - -struct ImGuiStackLevelInfo -{ - ImGuiID ID; - ImS8 QueryFrameCount; // >= 1: Query in progress - bool QuerySuccess; // Obtained result from DebugHookIdInfo() - ImGuiDataType DataType : 8; - char Desc[57]; // Arbitrarily sized buffer to hold a result (FIXME: could replace Results[] with a chunk stream?) FIXME: Now that we added CTRL+C this should be fixed. - - ImGuiStackLevelInfo() { memset(this, 0, sizeof(*this)); } -}; - -// State for ID Stack tool queries -struct ImGuiIDStackTool -{ - int LastActiveFrame; - int StackLevel; // -1: query stack and resize Results, >= 0: individual stack level - ImGuiID QueryId; // ID to query details for - ImVector Results; - bool CopyToClipboardOnCtrlC; - float CopyToClipboardLastTime; - - ImGuiIDStackTool() { memset(this, 0, sizeof(*this)); CopyToClipboardLastTime = -FLT_MAX; } -}; - -//----------------------------------------------------------------------------- -// [SECTION] Generic context hooks -//----------------------------------------------------------------------------- - -typedef void (*ImGuiContextHookCallback)(ImGuiContext* ctx, ImGuiContextHook* hook); -enum ImGuiContextHookType { ImGuiContextHookType_NewFramePre, ImGuiContextHookType_NewFramePost, ImGuiContextHookType_EndFramePre, ImGuiContextHookType_EndFramePost, ImGuiContextHookType_RenderPre, ImGuiContextHookType_RenderPost, ImGuiContextHookType_Shutdown, ImGuiContextHookType_PendingRemoval_ }; - -struct ImGuiContextHook -{ - ImGuiID HookId; // A unique ID assigned by AddContextHook() - ImGuiContextHookType Type; - ImGuiID Owner; - ImGuiContextHookCallback Callback; - void* UserData; - - ImGuiContextHook() { memset(this, 0, sizeof(*this)); } -}; - -//----------------------------------------------------------------------------- -// [SECTION] ImGuiContext (main Dear ImGui context) -//----------------------------------------------------------------------------- - -struct ImGuiContext -{ - bool Initialized; - bool FontAtlasOwnedByContext; // IO.Fonts-> is owned by the ImGuiContext and will be destructed along with it. - ImGuiIO IO; - ImGuiPlatformIO PlatformIO; - ImGuiStyle Style; - ImGuiConfigFlags ConfigFlagsCurrFrame; // = g.IO.ConfigFlags at the time of NewFrame() - ImGuiConfigFlags ConfigFlagsLastFrame; - ImFont* Font; // (Shortcut) == FontStack.empty() ? IO.Font : FontStack.back() - float FontSize; // (Shortcut) == FontBaseSize * g.CurrentWindow->FontWindowScale == window->FontSize(). Text height for current window. - float FontBaseSize; // (Shortcut) == IO.FontGlobalScale * Font->Scale * Font->FontSize. Base text height. - ImDrawListSharedData DrawListSharedData; - double Time; - int FrameCount; - int FrameCountEnded; - int FrameCountPlatformEnded; - int FrameCountRendered; - bool WithinFrameScope; // Set by NewFrame(), cleared by EndFrame() - bool WithinFrameScopeWithImplicitWindow; // Set by NewFrame(), cleared by EndFrame() when the implicit debug window has been pushed - bool WithinEndChild; // Set within EndChild() - bool GcCompactAll; // Request full GC - bool TestEngineHookItems; // Will call test engine hooks: ImGuiTestEngineHook_ItemAdd(), ImGuiTestEngineHook_ItemInfo(), ImGuiTestEngineHook_Log() - void* TestEngine; // Test engine user data - - // Inputs - ImVector InputEventsQueue; // Input events which will be trickled/written into IO structure. - ImVector InputEventsTrail; // Past input events processed in NewFrame(). This is to allow domain-specific application to access e.g mouse/pen trail. - ImGuiMouseSource InputEventsNextMouseSource; - ImU32 InputEventsNextEventId; - - // Windows state - ImVector Windows; // Windows, sorted in display order, back to front - ImVector WindowsFocusOrder; // Root windows, sorted in focus order, back to front. - ImVector WindowsTempSortBuffer; // Temporary buffer used in EndFrame() to reorder windows so parents are kept before their child - ImVector CurrentWindowStack; - ImGuiStorage WindowsById; // Map window's ImGuiID to ImGuiWindow* - int WindowsActiveCount; // Number of unique windows submitted by frame - ImVec2 WindowsHoverPadding; // Padding around resizable windows for which hovering on counts as hovering the window == ImMax(style.TouchExtraPadding, WINDOWS_HOVER_PADDING) - ImGuiWindow* CurrentWindow; // Window being drawn into - ImGuiWindow* HoveredWindow; // Window the mouse is hovering. Will typically catch mouse inputs. - ImGuiWindow* HoveredWindowUnderMovingWindow; // Hovered window ignoring MovingWindow. Only set if MovingWindow is set. - ImGuiWindow* MovingWindow; // Track the window we clicked on (in order to preserve focus). The actual window that is moved is generally MovingWindow->RootWindowDockTree. - ImGuiWindow* WheelingWindow; // Track the window we started mouse-wheeling on. Until a timer elapse or mouse has moved, generally keep scrolling the same window even if during the course of scrolling the mouse ends up hovering a child window. - ImVec2 WheelingWindowRefMousePos; - int WheelingWindowStartFrame; // This may be set one frame before WheelingWindow is != NULL - float WheelingWindowReleaseTimer; - ImVec2 WheelingWindowWheelRemainder; - ImVec2 WheelingAxisAvg; - - // Item/widgets state and tracking information - ImGuiID DebugHookIdInfo; // Will call core hooks: DebugHookIdInfo() from GetID functions, used by ID Stack Tool [next HoveredId/ActiveId to not pull in an extra cache-line] - ImGuiID HoveredId; // Hovered widget, filled during the frame - ImGuiID HoveredIdPreviousFrame; - bool HoveredIdAllowOverlap; - bool HoveredIdDisabled; // At least one widget passed the rect test, but has been discarded by disabled flag or popup inhibit. May be true even if HoveredId == 0. - float HoveredIdTimer; // Measure contiguous hovering time - float HoveredIdNotActiveTimer; // Measure contiguous hovering time where the item has not been active - ImGuiID ActiveId; // Active widget - ImGuiID ActiveIdIsAlive; // Active widget has been seen this frame (we can't use a bool as the ActiveId may change within the frame) - float ActiveIdTimer; - bool ActiveIdIsJustActivated; // Set at the time of activation for one frame - bool ActiveIdAllowOverlap; // Active widget allows another widget to steal active id (generally for overlapping widgets, but not always) - bool ActiveIdNoClearOnFocusLoss; // Disable losing active id if the active id window gets unfocused. - bool ActiveIdHasBeenPressedBefore; // Track whether the active id led to a press (this is to allow changing between PressOnClick and PressOnRelease without pressing twice). Used by range_select branch. - bool ActiveIdHasBeenEditedBefore; // Was the value associated to the widget Edited over the course of the Active state. - bool ActiveIdHasBeenEditedThisFrame; - ImVec2 ActiveIdClickOffset; // Clicked offset from upper-left corner, if applicable (currently only set by ButtonBehavior) - ImGuiWindow* ActiveIdWindow; - ImGuiInputSource ActiveIdSource; // Activating source: ImGuiInputSource_Mouse OR ImGuiInputSource_Keyboard OR ImGuiInputSource_Gamepad - int ActiveIdMouseButton; - ImGuiID ActiveIdPreviousFrame; - bool ActiveIdPreviousFrameIsAlive; - bool ActiveIdPreviousFrameHasBeenEditedBefore; - ImGuiWindow* ActiveIdPreviousFrameWindow; - ImGuiID LastActiveId; // Store the last non-zero ActiveId, useful for animation. - float LastActiveIdTimer; // Store the last non-zero ActiveId timer since the beginning of activation, useful for animation. - - // [EXPERIMENTAL] Key/Input Ownership + Shortcut Routing system - // - The idea is that instead of "eating" a given key, we can link to an owner. - // - Input query can then read input by specifying ImGuiKeyOwner_Any (== 0), ImGuiKeyOwner_None (== -1) or a custom ID. - // - Routing is requested ahead of time for a given chord (Key + Mods) and granted in NewFrame(). - ImGuiKeyOwnerData KeysOwnerData[ImGuiKey_NamedKey_COUNT]; - ImGuiKeyRoutingTable KeysRoutingTable; - ImU32 ActiveIdUsingNavDirMask; // Active widget will want to read those nav move requests (e.g. can activate a button and move away from it) - bool ActiveIdUsingAllKeyboardKeys; // Active widget will want to read all keyboard keys inputs. (FIXME: This is a shortcut for not taking ownership of 100+ keys but perhaps best to not have the inconsistency) -#ifndef IMGUI_DISABLE_OBSOLETE_KEYIO - ImU32 ActiveIdUsingNavInputMask; // If you used this. Since (IMGUI_VERSION_NUM >= 18804) : 'g.ActiveIdUsingNavInputMask |= (1 << ImGuiNavInput_Cancel);' becomes 'SetKeyOwner(ImGuiKey_Escape, g.ActiveId) and/or SetKeyOwner(ImGuiKey_NavGamepadCancel, g.ActiveId);' -#endif - - // Next window/item data - ImGuiID CurrentFocusScopeId; // == g.FocusScopeStack.back() - ImGuiItemFlags CurrentItemFlags; // == g.ItemFlagsStack.back() - ImGuiID DebugLocateId; // Storage for DebugLocateItemOnHover() feature: this is read by ItemAdd() so we keep it in a hot/cached location - ImGuiNextItemData NextItemData; // Storage for SetNextItem** functions - ImGuiLastItemData LastItemData; // Storage for last submitted item (setup by ItemAdd) - ImGuiNextWindowData NextWindowData; // Storage for SetNextWindow** functions - bool DebugShowGroupRects; - - // Shared stacks - ImVector ColorStack; // Stack for PushStyleColor()/PopStyleColor() - inherited by Begin() - ImVector StyleVarStack; // Stack for PushStyleVar()/PopStyleVar() - inherited by Begin() - ImVector FontStack; // Stack for PushFont()/PopFont() - inherited by Begin() - ImVector FocusScopeStack; // Stack for PushFocusScope()/PopFocusScope() - inherited by BeginChild(), pushed into by Begin() - ImVector ItemFlagsStack; // Stack for PushItemFlag()/PopItemFlag() - inherited by Begin() - ImVector GroupStack; // Stack for BeginGroup()/EndGroup() - not inherited by Begin() - ImVector OpenPopupStack; // Which popups are open (persistent) - ImVector BeginPopupStack; // Which level of BeginPopup() we are in (reset every frame) - ImVector NavTreeNodeStack; // Stack for TreeNode() when a NavLeft requested is emitted. - - int BeginMenuCount; - - // Viewports - ImVector Viewports; // Active viewports (always 1+, and generally 1 unless multi-viewports are enabled). Each viewports hold their copy of ImDrawData. - float CurrentDpiScale; // == CurrentViewport->DpiScale - ImGuiViewportP* CurrentViewport; // We track changes of viewport (happening in Begin) so we can call Platform_OnChangedViewport() - ImGuiViewportP* MouseViewport; - ImGuiViewportP* MouseLastHoveredViewport; // Last known viewport that was hovered by mouse (even if we are not hovering any viewport any more) + honoring the _NoInputs flag. - ImGuiID PlatformLastFocusedViewportId; - ImGuiPlatformMonitor FallbackMonitor; // Virtual monitor used as fallback if backend doesn't provide monitor information. - int ViewportCreatedCount; // Unique sequential creation counter (mostly for testing/debugging) - int PlatformWindowsCreatedCount; // Unique sequential creation counter (mostly for testing/debugging) - int ViewportFocusedStampCount; // Every time the front-most window changes, we stamp its viewport with an incrementing counter - - // Gamepad/keyboard Navigation - ImGuiWindow* NavWindow; // Focused window for navigation. Could be called 'FocusedWindow' - ImGuiID NavId; // Focused item for navigation - ImGuiID NavFocusScopeId; // Identify a selection scope (selection code often wants to "clear other items" when landing on an item of the selection set) - ImGuiID NavActivateId; // ~~ (g.ActiveId == 0) && (IsKeyPressed(ImGuiKey_Space) || IsKeyDown(ImGuiKey_Enter) || IsKeyPressed(ImGuiKey_NavGamepadActivate)) ? NavId : 0, also set when calling ActivateItem() - ImGuiID NavActivateDownId; // ~~ IsKeyDown(ImGuiKey_Space) || IsKeyDown(ImGuiKey_Enter) || IsKeyDown(ImGuiKey_NavGamepadActivate) ? NavId : 0 - ImGuiID NavActivatePressedId; // ~~ IsKeyPressed(ImGuiKey_Space) || IsKeyPressed(ImGuiKey_Enter) || IsKeyPressed(ImGuiKey_NavGamepadActivate) ? NavId : 0 (no repeat) - ImGuiActivateFlags NavActivateFlags; - ImGuiID NavJustMovedToId; // Just navigated to this id (result of a successfully MoveRequest). - ImGuiID NavJustMovedToFocusScopeId; // Just navigated to this focus scope id (result of a successfully MoveRequest). - ImGuiKeyChord NavJustMovedToKeyMods; - ImGuiID NavNextActivateId; // Set by ActivateItem(), queued until next frame. - ImGuiActivateFlags NavNextActivateFlags; - ImGuiInputSource NavInputSource; // Keyboard or Gamepad mode? THIS CAN ONLY BE ImGuiInputSource_Keyboard or ImGuiInputSource_Mouse - ImGuiNavLayer NavLayer; // Layer we are navigating on. For now the system is hard-coded for 0=main contents and 1=menu/title bar, may expose layers later. - ImGuiSelectionUserData NavLastValidSelectionUserData; // Last valid data passed to SetNextItemSelectionUser(), or -1. For current window. Not reset when focusing an item that doesn't have selection data. - bool NavIdIsAlive; // Nav widget has been seen this frame ~~ NavRectRel is valid - bool NavMousePosDirty; // When set we will update mouse position if (io.ConfigFlags & ImGuiConfigFlags_NavEnableSetMousePos) if set (NB: this not enabled by default) - bool NavDisableHighlight; // When user starts using mouse, we hide gamepad/keyboard highlight (NB: but they are still available, which is why NavDisableHighlight isn't always != NavDisableMouseHover) - bool NavDisableMouseHover; // When user starts using gamepad/keyboard, we hide mouse hovering highlight until mouse is touched again. - - // Navigation: Init & Move Requests - bool NavAnyRequest; // ~~ NavMoveRequest || NavInitRequest this is to perform early out in ItemAdd() - bool NavInitRequest; // Init request for appearing window to select first item - bool NavInitRequestFromMove; - ImGuiNavItemData NavInitResult; // Init request result (first item of the window, or one for which SetItemDefaultFocus() was called) - bool NavMoveSubmitted; // Move request submitted, will process result on next NewFrame() - bool NavMoveScoringItems; // Move request submitted, still scoring incoming items - bool NavMoveForwardToNextFrame; - ImGuiNavMoveFlags NavMoveFlags; - ImGuiScrollFlags NavMoveScrollFlags; - ImGuiKeyChord NavMoveKeyMods; - ImGuiDir NavMoveDir; // Direction of the move request (left/right/up/down) - ImGuiDir NavMoveDirForDebug; - ImGuiDir NavMoveClipDir; // FIXME-NAV: Describe the purpose of this better. Might want to rename? - ImRect NavScoringRect; // Rectangle used for scoring, in screen space. Based of window->NavRectRel[], modified for directional navigation scoring. - ImRect NavScoringNoClipRect; // Some nav operations (such as PageUp/PageDown) enforce a region which clipper will attempt to always keep submitted - int NavScoringDebugCount; // Metrics for debugging - int NavTabbingDir; // Generally -1 or +1, 0 when tabbing without a nav id - int NavTabbingCounter; // >0 when counting items for tabbing - ImGuiNavItemData NavMoveResultLocal; // Best move request candidate within NavWindow - ImGuiNavItemData NavMoveResultLocalVisible; // Best move request candidate within NavWindow that are mostly visible (when using ImGuiNavMoveFlags_AlsoScoreVisibleSet flag) - ImGuiNavItemData NavMoveResultOther; // Best move request candidate within NavWindow's flattened hierarchy (when using ImGuiWindowFlags_NavFlattened flag) - ImGuiNavItemData NavTabbingResultFirst; // First tabbing request candidate within NavWindow and flattened hierarchy - - // Navigation: Windowing (CTRL+TAB for list, or Menu button + keys or directional pads to move/resize) - ImGuiKeyChord ConfigNavWindowingKeyNext; // = ImGuiMod_Ctrl | ImGuiKey_Tab, for reconfiguration (see #4828) - ImGuiKeyChord ConfigNavWindowingKeyPrev; // = ImGuiMod_Ctrl | ImGuiMod_Shift | ImGuiKey_Tab - ImGuiWindow* NavWindowingTarget; // Target window when doing CTRL+Tab (or Pad Menu + FocusPrev/Next), this window is temporarily displayed top-most! - ImGuiWindow* NavWindowingTargetAnim; // Record of last valid NavWindowingTarget until DimBgRatio and NavWindowingHighlightAlpha becomes 0.0f, so the fade-out can stay on it. - ImGuiWindow* NavWindowingListWindow; // Internal window actually listing the CTRL+Tab contents - float NavWindowingTimer; - float NavWindowingHighlightAlpha; - bool NavWindowingToggleLayer; - ImVec2 NavWindowingAccumDeltaPos; - ImVec2 NavWindowingAccumDeltaSize; - - // Render - float DimBgRatio; // 0.0..1.0 animation when fading in a dimming background (for modal window and CTRL+TAB list) - - // Drag and Drop - bool DragDropActive; - bool DragDropWithinSource; // Set when within a BeginDragDropXXX/EndDragDropXXX block for a drag source. - bool DragDropWithinTarget; // Set when within a BeginDragDropXXX/EndDragDropXXX block for a drag target. - ImGuiDragDropFlags DragDropSourceFlags; - int DragDropSourceFrameCount; - int DragDropMouseButton; - ImGuiPayload DragDropPayload; - ImRect DragDropTargetRect; // Store rectangle of current target candidate (we favor small targets when overlapping) - ImGuiID DragDropTargetId; - ImGuiDragDropFlags DragDropAcceptFlags; - float DragDropAcceptIdCurrRectSurface; // Target item surface (we resolve overlapping targets by prioritizing the smaller surface) - ImGuiID DragDropAcceptIdCurr; // Target item id (set at the time of accepting the payload) - ImGuiID DragDropAcceptIdPrev; // Target item id from previous frame (we need to store this to allow for overlapping drag and drop targets) - int DragDropAcceptFrameCount; // Last time a target expressed a desire to accept the source - ImGuiID DragDropHoldJustPressedId; // Set when holding a payload just made ButtonBehavior() return a press. - ImVector DragDropPayloadBufHeap; // We don't expose the ImVector<> directly, ImGuiPayload only holds pointer+size - unsigned char DragDropPayloadBufLocal[16]; // Local buffer for small payloads - - // Clipper - int ClipperTempDataStacked; - ImVector ClipperTempData; - - // Tables - ImGuiTable* CurrentTable; - int TablesTempDataStacked; // Temporary table data size (because we leave previous instances undestructed, we generally don't use TablesTempData.Size) - ImVector TablesTempData; // Temporary table data (buffers reused/shared across instances, support nesting) - ImPool Tables; // Persistent table data - ImVector TablesLastTimeActive; // Last used timestamp of each tables (SOA, for efficient GC) - ImVector DrawChannelsTempMergeBuffer; - - // Tab bars - ImGuiTabBar* CurrentTabBar; - ImPool TabBars; - ImVector CurrentTabBarStack; - ImVector ShrinkWidthBuffer; - - // Hover Delay system - ImGuiID HoverItemDelayId; - ImGuiID HoverItemDelayIdPreviousFrame; - float HoverItemDelayTimer; // Currently used by IsItemHovered() - float HoverItemDelayClearTimer; // Currently used by IsItemHovered(): grace time before g.TooltipHoverTimer gets cleared. - ImGuiID HoverItemUnlockedStationaryId; // Mouse has once been stationary on this item. Only reset after departing the item. - ImGuiID HoverWindowUnlockedStationaryId; // Mouse has once been stationary on this window. Only reset after departing the window. - - // Mouse state - ImGuiMouseCursor MouseCursor; - float MouseStationaryTimer; // Time the mouse has been stationary (with some loose heuristic) - ImVec2 MouseLastValidPos; - - // Widget state - ImGuiInputTextState InputTextState; - ImGuiInputTextDeactivatedState InputTextDeactivatedState; - ImFont InputTextPasswordFont; - ImGuiID TempInputId; // Temporary text input when CTRL+clicking on a slider, etc. - ImGuiColorEditFlags ColorEditOptions; // Store user options for color edit widgets - ImGuiID ColorEditCurrentID; // Set temporarily while inside of the parent-most ColorEdit4/ColorPicker4 (because they call each others). - ImGuiID ColorEditSavedID; // ID we are saving/restoring HS for - float ColorEditSavedHue; // Backup of last Hue associated to LastColor, so we can restore Hue in lossy RGB<>HSV round trips - float ColorEditSavedSat; // Backup of last Saturation associated to LastColor, so we can restore Saturation in lossy RGB<>HSV round trips - ImU32 ColorEditSavedColor; // RGB value with alpha set to 0. - ImVec4 ColorPickerRef; // Initial/reference color at the time of opening the color picker. - ImGuiComboPreviewData ComboPreviewData; - float SliderGrabClickOffset; - float SliderCurrentAccum; // Accumulated slider delta when using navigation controls. - bool SliderCurrentAccumDirty; // Has the accumulated slider delta changed since last time we tried to apply it? - bool DragCurrentAccumDirty; - float DragCurrentAccum; // Accumulator for dragging modification. Always high-precision, not rounded by end-user precision settings - float DragSpeedDefaultRatio; // If speed == 0.0f, uses (max-min) * DragSpeedDefaultRatio - float ScrollbarClickDeltaToGrabCenter; // Distance between mouse and center of grab box, normalized in parent space. Use storage? - float DisabledAlphaBackup; // Backup for style.Alpha for BeginDisabled() - short DisabledStackSize; - short LockMarkEdited; - short TooltipOverrideCount; - ImVector ClipboardHandlerData; // If no custom clipboard handler is defined - ImVector MenusIdSubmittedThisFrame; // A list of menu IDs that were rendered at least once - ImGuiTypingSelectState TypingSelectState; // State for GetTypingSelectRequest() - - // Platform support - ImGuiPlatformImeData PlatformImeData; // Data updated by current frame - ImGuiPlatformImeData PlatformImeDataPrev; // Previous frame data (when changing we will call io.SetPlatformImeDataFn - ImGuiID PlatformImeViewport; - - // Extensions - // FIXME: We could provide an API to register one slot in an array held in ImGuiContext? - ImGuiDockContext DockContext; - void (*DockNodeWindowMenuHandler)(ImGuiContext* ctx, ImGuiDockNode* node, ImGuiTabBar* tab_bar); - - // Settings - bool SettingsLoaded; - float SettingsDirtyTimer; // Save .ini Settings to memory when time reaches zero - ImGuiTextBuffer SettingsIniData; // In memory .ini settings - ImVector SettingsHandlers; // List of .ini settings handlers - ImChunkStream SettingsWindows; // ImGuiWindow .ini settings entries - ImChunkStream SettingsTables; // ImGuiTable .ini settings entries - ImVector Hooks; // Hooks for extensions (e.g. test engine) - ImGuiID HookIdNext; // Next available HookId - - // Localization - const char* LocalizationTable[ImGuiLocKey_COUNT]; - - // Capture/Logging - bool LogEnabled; // Currently capturing - ImGuiLogType LogType; // Capture target - ImFileHandle LogFile; // If != NULL log to stdout/ file - ImGuiTextBuffer LogBuffer; // Accumulation buffer when log to clipboard. This is pointer so our GImGui static constructor doesn't call heap allocators. - const char* LogNextPrefix; - const char* LogNextSuffix; - float LogLinePosY; - bool LogLineFirstItem; - int LogDepthRef; - int LogDepthToExpand; - int LogDepthToExpandDefault; // Default/stored value for LogDepthMaxExpand if not specified in the LogXXX function call. - - // Debug Tools - ImGuiDebugLogFlags DebugLogFlags; - ImGuiTextBuffer DebugLogBuf; - ImGuiTextIndex DebugLogIndex; - ImU8 DebugLogClipperAutoDisableFrames; - ImU8 DebugLocateFrames; // For DebugLocateItemOnHover(). This is used together with DebugLocateId which is in a hot/cached spot above. - ImS8 DebugBeginReturnValueCullDepth; // Cycle between 0..9 then wrap around. - bool DebugItemPickerActive; // Item picker is active (started with DebugStartItemPicker()) - ImU8 DebugItemPickerMouseButton; - ImGuiID DebugItemPickerBreakId; // Will call IM_DEBUG_BREAK() when encountering this ID - ImGuiMetricsConfig DebugMetricsConfig; - ImGuiIDStackTool DebugIDStackTool; - ImGuiDebugAllocInfo DebugAllocInfo; - ImGuiDockNode* DebugHoveredDockNode; // Hovered dock node. - - // Misc - float FramerateSecPerFrame[60]; // Calculate estimate of framerate for user over the last 60 frames.. - int FramerateSecPerFrameIdx; - int FramerateSecPerFrameCount; - float FramerateSecPerFrameAccum; - int WantCaptureMouseNextFrame; // Explicit capture override via SetNextFrameWantCaptureMouse()/SetNextFrameWantCaptureKeyboard(). Default to -1. - int WantCaptureKeyboardNextFrame; // " - int WantTextInputNextFrame; - ImVector TempBuffer; // Temporary text buffer - - ImGuiContext(ImFontAtlas* shared_font_atlas) - { - IO.Ctx = this; - InputTextState.Ctx = this; - - Initialized = false; - ConfigFlagsCurrFrame = ConfigFlagsLastFrame = ImGuiConfigFlags_None; - FontAtlasOwnedByContext = shared_font_atlas ? false : true; - Font = NULL; - FontSize = FontBaseSize = 0.0f; - IO.Fonts = shared_font_atlas ? shared_font_atlas : IM_NEW(ImFontAtlas)(); - Time = 0.0f; - FrameCount = 0; - FrameCountEnded = FrameCountPlatformEnded = FrameCountRendered = -1; - WithinFrameScope = WithinFrameScopeWithImplicitWindow = WithinEndChild = false; - GcCompactAll = false; - TestEngineHookItems = false; - TestEngine = NULL; - - InputEventsNextMouseSource = ImGuiMouseSource_Mouse; - InputEventsNextEventId = 1; - - WindowsActiveCount = 0; - CurrentWindow = NULL; - HoveredWindow = NULL; - HoveredWindowUnderMovingWindow = NULL; - MovingWindow = NULL; - WheelingWindow = NULL; - WheelingWindowStartFrame = -1; - WheelingWindowReleaseTimer = 0.0f; - - DebugHookIdInfo = 0; - HoveredId = HoveredIdPreviousFrame = 0; - HoveredIdAllowOverlap = false; - HoveredIdDisabled = false; - HoveredIdTimer = HoveredIdNotActiveTimer = 0.0f; - ActiveId = 0; - ActiveIdIsAlive = 0; - ActiveIdTimer = 0.0f; - ActiveIdIsJustActivated = false; - ActiveIdAllowOverlap = false; - ActiveIdNoClearOnFocusLoss = false; - ActiveIdHasBeenPressedBefore = false; - ActiveIdHasBeenEditedBefore = false; - ActiveIdHasBeenEditedThisFrame = false; - ActiveIdClickOffset = ImVec2(-1, -1); - ActiveIdWindow = NULL; - ActiveIdSource = ImGuiInputSource_None; - ActiveIdMouseButton = -1; - ActiveIdPreviousFrame = 0; - ActiveIdPreviousFrameIsAlive = false; - ActiveIdPreviousFrameHasBeenEditedBefore = false; - ActiveIdPreviousFrameWindow = NULL; - LastActiveId = 0; - LastActiveIdTimer = 0.0f; - - ActiveIdUsingNavDirMask = 0x00; - ActiveIdUsingAllKeyboardKeys = false; -#ifndef IMGUI_DISABLE_OBSOLETE_KEYIO - ActiveIdUsingNavInputMask = 0x00; -#endif - - CurrentFocusScopeId = 0; - CurrentItemFlags = ImGuiItemFlags_None; - DebugShowGroupRects = false; - BeginMenuCount = 0; - - CurrentDpiScale = 0.0f; - CurrentViewport = NULL; - MouseViewport = MouseLastHoveredViewport = NULL; - PlatformLastFocusedViewportId = 0; - ViewportCreatedCount = PlatformWindowsCreatedCount = 0; - ViewportFocusedStampCount = 0; - - NavWindow = NULL; - NavId = NavFocusScopeId = NavActivateId = NavActivateDownId = NavActivatePressedId = 0; - NavJustMovedToId = NavJustMovedToFocusScopeId = NavNextActivateId = 0; - NavActivateFlags = NavNextActivateFlags = ImGuiActivateFlags_None; - NavJustMovedToKeyMods = ImGuiMod_None; - NavInputSource = ImGuiInputSource_Keyboard; - NavLayer = ImGuiNavLayer_Main; - NavLastValidSelectionUserData = ImGuiSelectionUserData_Invalid; - NavIdIsAlive = false; - NavMousePosDirty = false; - NavDisableHighlight = true; - NavDisableMouseHover = false; - NavAnyRequest = false; - NavInitRequest = false; - NavInitRequestFromMove = false; - NavMoveSubmitted = false; - NavMoveScoringItems = false; - NavMoveForwardToNextFrame = false; - NavMoveFlags = ImGuiNavMoveFlags_None; - NavMoveScrollFlags = ImGuiScrollFlags_None; - NavMoveKeyMods = ImGuiMod_None; - NavMoveDir = NavMoveDirForDebug = NavMoveClipDir = ImGuiDir_None; - NavScoringDebugCount = 0; - NavTabbingDir = 0; - NavTabbingCounter = 0; - - ConfigNavWindowingKeyNext = ImGuiMod_Ctrl | ImGuiKey_Tab; - ConfigNavWindowingKeyPrev = ImGuiMod_Ctrl | ImGuiMod_Shift | ImGuiKey_Tab; - NavWindowingTarget = NavWindowingTargetAnim = NavWindowingListWindow = NULL; - NavWindowingTimer = NavWindowingHighlightAlpha = 0.0f; - NavWindowingToggleLayer = false; - - DimBgRatio = 0.0f; - - DragDropActive = DragDropWithinSource = DragDropWithinTarget = false; - DragDropSourceFlags = ImGuiDragDropFlags_None; - DragDropSourceFrameCount = -1; - DragDropMouseButton = -1; - DragDropTargetId = 0; - DragDropAcceptFlags = ImGuiDragDropFlags_None; - DragDropAcceptIdCurrRectSurface = 0.0f; - DragDropAcceptIdPrev = DragDropAcceptIdCurr = 0; - DragDropAcceptFrameCount = -1; - DragDropHoldJustPressedId = 0; - memset(DragDropPayloadBufLocal, 0, sizeof(DragDropPayloadBufLocal)); - - ClipperTempDataStacked = 0; - - CurrentTable = NULL; - TablesTempDataStacked = 0; - CurrentTabBar = NULL; - - HoverItemDelayId = HoverItemDelayIdPreviousFrame = HoverItemUnlockedStationaryId = HoverWindowUnlockedStationaryId = 0; - HoverItemDelayTimer = HoverItemDelayClearTimer = 0.0f; - - MouseCursor = ImGuiMouseCursor_Arrow; - MouseStationaryTimer = 0.0f; - - TempInputId = 0; - ColorEditOptions = ImGuiColorEditFlags_DefaultOptions_; - ColorEditCurrentID = ColorEditSavedID = 0; - ColorEditSavedHue = ColorEditSavedSat = 0.0f; - ColorEditSavedColor = 0; - SliderGrabClickOffset = 0.0f; - SliderCurrentAccum = 0.0f; - SliderCurrentAccumDirty = false; - DragCurrentAccumDirty = false; - DragCurrentAccum = 0.0f; - DragSpeedDefaultRatio = 1.0f / 100.0f; - ScrollbarClickDeltaToGrabCenter = 0.0f; - DisabledAlphaBackup = 0.0f; - DisabledStackSize = 0; - LockMarkEdited = 0; - TooltipOverrideCount = 0; - - PlatformImeData.InputPos = ImVec2(0.0f, 0.0f); - PlatformImeDataPrev.InputPos = ImVec2(-1.0f, -1.0f); // Different to ensure initial submission - PlatformImeViewport = 0; - - DockNodeWindowMenuHandler = NULL; - - SettingsLoaded = false; - SettingsDirtyTimer = 0.0f; - HookIdNext = 0; - - memset(LocalizationTable, 0, sizeof(LocalizationTable)); - - LogEnabled = false; - LogType = ImGuiLogType_None; - LogNextPrefix = LogNextSuffix = NULL; - LogFile = NULL; - LogLinePosY = FLT_MAX; - LogLineFirstItem = false; - LogDepthRef = 0; - LogDepthToExpand = LogDepthToExpandDefault = 2; - - DebugLogFlags = ImGuiDebugLogFlags_OutputToTTY; - DebugLocateId = 0; - DebugLogClipperAutoDisableFrames = 0; - DebugLocateFrames = 0; - DebugBeginReturnValueCullDepth = -1; - DebugItemPickerActive = false; - DebugItemPickerMouseButton = ImGuiMouseButton_Left; - DebugItemPickerBreakId = 0; - DebugHoveredDockNode = NULL; - - memset(FramerateSecPerFrame, 0, sizeof(FramerateSecPerFrame)); - FramerateSecPerFrameIdx = FramerateSecPerFrameCount = 0; - FramerateSecPerFrameAccum = 0.0f; - WantCaptureMouseNextFrame = WantCaptureKeyboardNextFrame = WantTextInputNextFrame = -1; - } -}; - -//----------------------------------------------------------------------------- -// [SECTION] ImGuiWindowTempData, ImGuiWindow -//----------------------------------------------------------------------------- - -// Transient per-window data, reset at the beginning of the frame. This used to be called ImGuiDrawContext, hence the DC variable name in ImGuiWindow. -// (That's theory, in practice the delimitation between ImGuiWindow and ImGuiWindowTempData is quite tenuous and could be reconsidered..) -// (This doesn't need a constructor because we zero-clear it as part of ImGuiWindow and all frame-temporary data are setup on Begin) -struct IMGUI_API ImGuiWindowTempData -{ - // Layout - ImVec2 CursorPos; // Current emitting position, in absolute coordinates. - ImVec2 CursorPosPrevLine; - ImVec2 CursorStartPos; // Initial position after Begin(), generally ~ window position + WindowPadding. - ImVec2 CursorMaxPos; // Used to implicitly calculate ContentSize at the beginning of next frame, for scrolling range and auto-resize. Always growing during the frame. - ImVec2 IdealMaxPos; // Used to implicitly calculate ContentSizeIdeal at the beginning of next frame, for auto-resize only. Always growing during the frame. - ImVec2 CurrLineSize; - ImVec2 PrevLineSize; - float CurrLineTextBaseOffset; // Baseline offset (0.0f by default on a new line, generally == style.FramePadding.y when a framed item has been added). - float PrevLineTextBaseOffset; - bool IsSameLine; - bool IsSetPos; - ImVec1 Indent; // Indentation / start position from left of window (increased by TreePush/TreePop, etc.) - ImVec1 ColumnsOffset; // Offset to the current column (if ColumnsCurrent > 0). FIXME: This and the above should be a stack to allow use cases like Tree->Column->Tree. Need revamp columns API. - ImVec1 GroupOffset; - ImVec2 CursorStartPosLossyness;// Record the loss of precision of CursorStartPos due to really large scrolling amount. This is used by clipper to compensate and fix the most common use case of large scroll area. - - // Keyboard/Gamepad navigation - ImGuiNavLayer NavLayerCurrent; // Current layer, 0..31 (we currently only use 0..1) - short NavLayersActiveMask; // Which layers have been written to (result from previous frame) - short NavLayersActiveMaskNext;// Which layers have been written to (accumulator for current frame) - bool NavIsScrollPushableX; // Set when current work location may be scrolled horizontally when moving left / right. This is generally always true UNLESS within a column. - bool NavHideHighlightOneFrame; - bool NavWindowHasScrollY; // Set per window when scrolling can be used (== ScrollMax.y > 0.0f) - - // Miscellaneous - bool MenuBarAppending; // FIXME: Remove this - ImVec2 MenuBarOffset; // MenuBarOffset.x is sort of equivalent of a per-layer CursorPos.x, saved/restored as we switch to the menu bar. The only situation when MenuBarOffset.y is > 0 if when (SafeAreaPadding.y > FramePadding.y), often used on TVs. - ImGuiMenuColumns MenuColumns; // Simplified columns storage for menu items measurement - int TreeDepth; // Current tree depth. - ImU32 TreeJumpToParentOnPopMask; // Store a copy of !g.NavIdIsAlive for TreeDepth 0..31.. Could be turned into a ImU64 if necessary. - ImVector ChildWindows; - ImGuiStorage* StateStorage; // Current persistent per-window storage (store e.g. tree node open/close state) - ImGuiOldColumns* CurrentColumns; // Current columns set - int CurrentTableIdx; // Current table index (into g.Tables) - ImGuiLayoutType LayoutType; - ImGuiLayoutType ParentLayoutType; // Layout type of parent window at the time of Begin() - - // Local parameters stacks - // We store the current settings outside of the vectors to increase memory locality (reduce cache misses). The vectors are rarely modified. Also it allows us to not heap allocate for short-lived windows which are not using those settings. - float ItemWidth; // Current item width (>0.0: width in pixels, <0.0: align xx pixels to the right of window). - float TextWrapPos; // Current text wrap pos. - ImVector ItemWidthStack; // Store item widths to restore (attention: .back() is not == ItemWidth) - ImVector TextWrapPosStack; // Store text wrap pos to restore (attention: .back() is not == TextWrapPos) -}; - -// Storage for one window -struct IMGUI_API ImGuiWindow -{ - ImGuiContext* Ctx; // Parent UI context (needs to be set explicitly by parent). - char* Name; // Window name, owned by the window. - ImGuiID ID; // == ImHashStr(Name) - ImGuiWindowFlags Flags, FlagsPreviousFrame; // See enum ImGuiWindowFlags_ - ImGuiWindowClass WindowClass; // Advanced users only. Set with SetNextWindowClass() - ImGuiViewportP* Viewport; // Always set in Begin(). Inactive windows may have a NULL value here if their viewport was discarded. - ImGuiID ViewportId; // We backup the viewport id (since the viewport may disappear or never be created if the window is inactive) - ImVec2 ViewportPos; // We backup the viewport position (since the viewport may disappear or never be created if the window is inactive) - int ViewportAllowPlatformMonitorExtend; // Reset to -1 every frame (index is guaranteed to be valid between NewFrame..EndFrame), only used in the Appearing frame of a tooltip/popup to enforce clamping to a given monitor - ImVec2 Pos; // Position (always rounded-up to nearest pixel) - ImVec2 Size; // Current size (==SizeFull or collapsed title bar size) - ImVec2 SizeFull; // Size when non collapsed - ImVec2 ContentSize; // Size of contents/scrollable client area (calculated from the extents reach of the cursor) from previous frame. Does not include window decoration or window padding. - ImVec2 ContentSizeIdeal; - ImVec2 ContentSizeExplicit; // Size of contents/scrollable client area explicitly request by the user via SetNextWindowContentSize(). - ImVec2 WindowPadding; // Window padding at the time of Begin(). - float WindowRounding; // Window rounding at the time of Begin(). May be clamped lower to avoid rendering artifacts with title bar, menu bar etc. - float WindowBorderSize; // Window border size at the time of Begin(). - float DecoOuterSizeX1, DecoOuterSizeY1; // Left/Up offsets. Sum of non-scrolling outer decorations (X1 generally == 0.0f. Y1 generally = TitleBarHeight + MenuBarHeight). Locked during Begin(). - float DecoOuterSizeX2, DecoOuterSizeY2; // Right/Down offsets (X2 generally == ScrollbarSize.x, Y2 == ScrollbarSizes.y). - float DecoInnerSizeX1, DecoInnerSizeY1; // Applied AFTER/OVER InnerRect. Specialized for Tables as they use specialized form of clipping and frozen rows/columns are inside InnerRect (and not part of regular decoration sizes). - int NameBufLen; // Size of buffer storing Name. May be larger than strlen(Name)! - ImGuiID MoveId; // == window->GetID("#MOVE") - ImGuiID TabId; // == window->GetID("#TAB") - ImGuiID ChildId; // ID of corresponding item in parent window (for navigation to return from child window to parent window) - ImVec2 Scroll; - ImVec2 ScrollMax; - ImVec2 ScrollTarget; // target scroll position. stored as cursor position with scrolling canceled out, so the highest point is always 0.0f. (FLT_MAX for no change) - ImVec2 ScrollTargetCenterRatio; // 0.0f = scroll so that target position is at top, 0.5f = scroll so that target position is centered - ImVec2 ScrollTargetEdgeSnapDist; // 0.0f = no snapping, >0.0f snapping threshold - ImVec2 ScrollbarSizes; // Size taken by each scrollbars on their smaller axis. Pay attention! ScrollbarSizes.x == width of the vertical scrollbar, ScrollbarSizes.y = height of the horizontal scrollbar. - bool ScrollbarX, ScrollbarY; // Are scrollbars visible? - bool ViewportOwned; - bool Active; // Set to true on Begin(), unless Collapsed - bool WasActive; - bool WriteAccessed; // Set to true when any widget access the current window - bool Collapsed; // Set when collapsing window to become only title-bar - bool WantCollapseToggle; - bool SkipItems; // Set when items can safely be all clipped (e.g. window not visible or collapsed) - bool Appearing; // Set during the frame where the window is appearing (or re-appearing) - bool Hidden; // Do not display (== HiddenFrames*** > 0) - bool IsFallbackWindow; // Set on the "Debug##Default" window. - bool IsExplicitChild; // Set when passed _ChildWindow, left to false by BeginDocked() - bool HasCloseButton; // Set when the window has a close button (p_open != NULL) - signed char ResizeBorderHeld; // Current border being held for resize (-1: none, otherwise 0-3) - short BeginCount; // Number of Begin() during the current frame (generally 0 or 1, 1+ if appending via multiple Begin/End pairs) - short BeginCountPreviousFrame; // Number of Begin() during the previous frame - short BeginOrderWithinParent; // Begin() order within immediate parent window, if we are a child window. Otherwise 0. - short BeginOrderWithinContext; // Begin() order within entire imgui context. This is mostly used for debugging submission order related issues. - short FocusOrder; // Order within WindowsFocusOrder[], altered when windows are focused. - ImGuiID PopupId; // ID in the popup stack when this window is used as a popup/menu (because we use generic Name/ID for recycling) - ImS8 AutoFitFramesX, AutoFitFramesY; - ImS8 AutoFitChildAxises; - bool AutoFitOnlyGrows; - ImGuiDir AutoPosLastDirection; - ImS8 HiddenFramesCanSkipItems; // Hide the window for N frames - ImS8 HiddenFramesCannotSkipItems; // Hide the window for N frames while allowing items to be submitted so we can measure their size - ImS8 HiddenFramesForRenderOnly; // Hide the window until frame N at Render() time only - ImS8 DisableInputsFrames; // Disable window interactions for N frames - ImGuiCond SetWindowPosAllowFlags : 8; // store acceptable condition flags for SetNextWindowPos() use. - ImGuiCond SetWindowSizeAllowFlags : 8; // store acceptable condition flags for SetNextWindowSize() use. - ImGuiCond SetWindowCollapsedAllowFlags : 8; // store acceptable condition flags for SetNextWindowCollapsed() use. - ImGuiCond SetWindowDockAllowFlags : 8; // store acceptable condition flags for SetNextWindowDock() use. - ImVec2 SetWindowPosVal; // store window position when using a non-zero Pivot (position set needs to be processed when we know the window size) - ImVec2 SetWindowPosPivot; // store window pivot for positioning. ImVec2(0, 0) when positioning from top-left corner; ImVec2(0.5f, 0.5f) for centering; ImVec2(1, 1) for bottom right. - - ImVector IDStack; // ID stack. ID are hashes seeded with the value at the top of the stack. (In theory this should be in the TempData structure) - ImGuiWindowTempData DC; // Temporary per-window data, reset at the beginning of the frame. This used to be called ImGuiDrawContext, hence the "DC" variable name. - - // The best way to understand what those rectangles are is to use the 'Metrics->Tools->Show Windows Rectangles' viewer. - // The main 'OuterRect', omitted as a field, is window->Rect(). - ImRect OuterRectClipped; // == Window->Rect() just after setup in Begin(). == window->Rect() for root window. - ImRect InnerRect; // Inner rectangle (omit title bar, menu bar, scroll bar) - ImRect InnerClipRect; // == InnerRect shrunk by WindowPadding*0.5f on each side, clipped within viewport or parent clip rect. - ImRect WorkRect; // Initially covers the whole scrolling region. Reduced by containers e.g columns/tables when active. Shrunk by WindowPadding*1.0f on each side. This is meant to replace ContentRegionRect over time (from 1.71+ onward). - ImRect ParentWorkRect; // Backup of WorkRect before entering a container such as columns/tables. Used by e.g. SpanAllColumns functions to easily access. Stacked containers are responsible for maintaining this. // FIXME-WORKRECT: Could be a stack? - ImRect ClipRect; // Current clipping/scissoring rectangle, evolve as we are using PushClipRect(), etc. == DrawList->clip_rect_stack.back(). - ImRect ContentRegionRect; // FIXME: This is currently confusing/misleading. It is essentially WorkRect but not handling of scrolling. We currently rely on it as right/bottom aligned sizing operation need some size to rely on. - ImVec2ih HitTestHoleSize; // Define an optional rectangular hole where mouse will pass-through the window. - ImVec2ih HitTestHoleOffset; - - int LastFrameActive; // Last frame number the window was Active. - int LastFrameJustFocused; // Last frame number the window was made Focused. - float LastTimeActive; // Last timestamp the window was Active (using float as we don't need high precision there) - float ItemWidthDefault; - ImGuiStorage StateStorage; - ImVector ColumnsStorage; - float FontWindowScale; // User scale multiplier per-window, via SetWindowFontScale() - float FontDpiScale; - int SettingsOffset; // Offset into SettingsWindows[] (offsets are always valid as we only grow the array from the back) - - ImDrawList* DrawList; // == &DrawListInst (for backward compatibility reason with code using imgui_internal.h we keep this a pointer) - ImDrawList DrawListInst; - ImGuiWindow* ParentWindow; // If we are a child _or_ popup _or_ docked window, this is pointing to our parent. Otherwise NULL. - ImGuiWindow* ParentWindowInBeginStack; - ImGuiWindow* RootWindow; // Point to ourself or first ancestor that is not a child window. Doesn't cross through popups/dock nodes. - ImGuiWindow* RootWindowPopupTree; // Point to ourself or first ancestor that is not a child window. Cross through popups parent<>child. - ImGuiWindow* RootWindowDockTree; // Point to ourself or first ancestor that is not a child window. Cross through dock nodes. - ImGuiWindow* RootWindowForTitleBarHighlight; // Point to ourself or first ancestor which will display TitleBgActive color when this window is active. - ImGuiWindow* RootWindowForNav; // Point to ourself or first ancestor which doesn't have the NavFlattened flag. - - ImGuiWindow* NavLastChildNavWindow; // When going to the menu bar, we remember the child window we came from. (This could probably be made implicit if we kept g.Windows sorted by last focused including child window.) - ImGuiID NavLastIds[ImGuiNavLayer_COUNT]; // Last known NavId for this window, per layer (0/1) - ImRect NavRectRel[ImGuiNavLayer_COUNT]; // Reference rectangle, in window relative space - ImVec2 NavPreferredScoringPosRel[ImGuiNavLayer_COUNT]; // Preferred X/Y position updated when moving on a given axis, reset to FLT_MAX. - ImGuiID NavRootFocusScopeId; // Focus Scope ID at the time of Begin() - - int MemoryDrawListIdxCapacity; // Backup of last idx/vtx count, so when waking up the window we can preallocate and avoid iterative alloc/copy - int MemoryDrawListVtxCapacity; - bool MemoryCompacted; // Set when window extraneous data have been garbage collected - - // Docking - bool DockIsActive :1; // When docking artifacts are actually visible. When this is set, DockNode is guaranteed to be != NULL. ~~ (DockNode != NULL) && (DockNode->Windows.Size > 1). - bool DockNodeIsVisible :1; - bool DockTabIsVisible :1; // Is our window visible this frame? ~~ is the corresponding tab selected? - bool DockTabWantClose :1; - short DockOrder; // Order of the last time the window was visible within its DockNode. This is used to reorder windows that are reappearing on the same frame. Same value between windows that were active and windows that were none are possible. - ImGuiWindowDockStyle DockStyle; - ImGuiDockNode* DockNode; // Which node are we docked into. Important: Prefer testing DockIsActive in many cases as this will still be set when the dock node is hidden. - ImGuiDockNode* DockNodeAsHost; // Which node are we owning (for parent windows) - ImGuiID DockId; // Backup of last valid DockNode->ID, so single window remember their dock node id even when they are not bound any more - ImGuiItemStatusFlags DockTabItemStatusFlags; - ImRect DockTabItemRect; - -public: - ImGuiWindow(ImGuiContext* context, const char* name); - ~ImGuiWindow(); - - ImGuiID GetID(const char* str, const char* str_end = NULL); - ImGuiID GetID(const void* ptr); - ImGuiID GetID(int n); - ImGuiID GetIDFromRectangle(const ImRect& r_abs); - - // We don't use g.FontSize because the window may be != g.CurrentWindow. - ImRect Rect() const { return ImRect(Pos.x, Pos.y, Pos.x + Size.x, Pos.y + Size.y); } - float CalcFontSize() const { ImGuiContext& g = *Ctx; float scale = g.FontBaseSize * FontWindowScale * FontDpiScale; if (ParentWindow) scale *= ParentWindow->FontWindowScale; return scale; } - float TitleBarHeight() const { ImGuiContext& g = *Ctx; return (Flags & ImGuiWindowFlags_NoTitleBar) ? 0.0f : CalcFontSize() + g.Style.FramePadding.y * 2.0f; } - ImRect TitleBarRect() const { return ImRect(Pos, ImVec2(Pos.x + SizeFull.x, Pos.y + TitleBarHeight())); } - float MenuBarHeight() const { ImGuiContext& g = *Ctx; return (Flags & ImGuiWindowFlags_MenuBar) ? DC.MenuBarOffset.y + CalcFontSize() + g.Style.FramePadding.y * 2.0f : 0.0f; } - ImRect MenuBarRect() const { float y1 = Pos.y + TitleBarHeight(); return ImRect(Pos.x, y1, Pos.x + SizeFull.x, y1 + MenuBarHeight()); } -}; - -//----------------------------------------------------------------------------- -// [SECTION] Tab bar, Tab item support -//----------------------------------------------------------------------------- - -// Extend ImGuiTabBarFlags_ -enum ImGuiTabBarFlagsPrivate_ -{ - ImGuiTabBarFlags_DockNode = 1 << 20, // Part of a dock node [we don't use this in the master branch but it facilitate branch syncing to keep this around] - ImGuiTabBarFlags_IsFocused = 1 << 21, - ImGuiTabBarFlags_SaveSettings = 1 << 22, // FIXME: Settings are handled by the docking system, this only request the tab bar to mark settings dirty when reordering tabs -}; - -// Extend ImGuiTabItemFlags_ -enum ImGuiTabItemFlagsPrivate_ -{ - ImGuiTabItemFlags_SectionMask_ = ImGuiTabItemFlags_Leading | ImGuiTabItemFlags_Trailing, - ImGuiTabItemFlags_NoCloseButton = 1 << 20, // Track whether p_open was set or not (we'll need this info on the next frame to recompute ContentWidth during layout) - ImGuiTabItemFlags_Button = 1 << 21, // Used by TabItemButton, change the tab item behavior to mimic a button - ImGuiTabItemFlags_Unsorted = 1 << 22, // [Docking] Trailing tabs with the _Unsorted flag will be sorted based on the DockOrder of their Window. -}; - -// Storage for one active tab item (sizeof() 48 bytes) -struct ImGuiTabItem -{ - ImGuiID ID; - ImGuiTabItemFlags Flags; - ImGuiWindow* Window; // When TabItem is part of a DockNode's TabBar, we hold on to a window. - int LastFrameVisible; - int LastFrameSelected; // This allows us to infer an ordered list of the last activated tabs with little maintenance - float Offset; // Position relative to beginning of tab - float Width; // Width currently displayed - float ContentWidth; // Width of label, stored during BeginTabItem() call - float RequestedWidth; // Width optionally requested by caller, -1.0f is unused - ImS32 NameOffset; // When Window==NULL, offset to name within parent ImGuiTabBar::TabsNames - ImS16 BeginOrder; // BeginTabItem() order, used to re-order tabs after toggling ImGuiTabBarFlags_Reorderable - ImS16 IndexDuringLayout; // Index only used during TabBarLayout(). Tabs gets reordered so 'Tabs[n].IndexDuringLayout == n' but may mismatch during additions. - bool WantClose; // Marked as closed by SetTabItemClosed() - - ImGuiTabItem() { memset(this, 0, sizeof(*this)); LastFrameVisible = LastFrameSelected = -1; RequestedWidth = -1.0f; NameOffset = -1; BeginOrder = IndexDuringLayout = -1; } -}; - -// Storage for a tab bar (sizeof() 152 bytes) -struct IMGUI_API ImGuiTabBar -{ - ImVector Tabs; - ImGuiTabBarFlags Flags; - ImGuiID ID; // Zero for tab-bars used by docking - ImGuiID SelectedTabId; // Selected tab/window - ImGuiID NextSelectedTabId; // Next selected tab/window. Will also trigger a scrolling animation - ImGuiID VisibleTabId; // Can occasionally be != SelectedTabId (e.g. when previewing contents for CTRL+TAB preview) - int CurrFrameVisible; - int PrevFrameVisible; - ImRect BarRect; - float CurrTabsContentsHeight; - float PrevTabsContentsHeight; // Record the height of contents submitted below the tab bar - float WidthAllTabs; // Actual width of all tabs (locked during layout) - float WidthAllTabsIdeal; // Ideal width if all tabs were visible and not clipped - float ScrollingAnim; - float ScrollingTarget; - float ScrollingTargetDistToVisibility; - float ScrollingSpeed; - float ScrollingRectMinX; - float ScrollingRectMaxX; - float SeparatorMinX; - float SeparatorMaxX; - ImGuiID ReorderRequestTabId; - ImS16 ReorderRequestOffset; - ImS8 BeginCount; - bool WantLayout; - bool VisibleTabWasSubmitted; - bool TabsAddedNew; // Set to true when a new tab item or button has been added to the tab bar during last frame - ImS16 TabsActiveCount; // Number of tabs submitted this frame. - ImS16 LastTabItemIdx; // Index of last BeginTabItem() tab for use by EndTabItem() - float ItemSpacingY; - ImVec2 FramePadding; // style.FramePadding locked at the time of BeginTabBar() - ImVec2 BackupCursorPos; - ImGuiTextBuffer TabsNames; // For non-docking tab bar we re-append names in a contiguous buffer. - - ImGuiTabBar(); -}; - -//----------------------------------------------------------------------------- -// [SECTION] Table support -//----------------------------------------------------------------------------- - -#define IM_COL32_DISABLE IM_COL32(0,0,0,1) // Special sentinel code which cannot be used as a regular color. -#define IMGUI_TABLE_MAX_COLUMNS 512 // May be further lifted - -// Our current column maximum is 64 but we may raise that in the future. -typedef ImS16 ImGuiTableColumnIdx; -typedef ImU16 ImGuiTableDrawChannelIdx; - -// [Internal] sizeof() ~ 112 -// We use the terminology "Enabled" to refer to a column that is not Hidden by user/api. -// We use the terminology "Clipped" to refer to a column that is out of sight because of scrolling/clipping. -// This is in contrast with some user-facing api such as IsItemVisible() / IsRectVisible() which use "Visible" to mean "not clipped". -struct ImGuiTableColumn -{ - ImGuiTableColumnFlags Flags; // Flags after some patching (not directly same as provided by user). See ImGuiTableColumnFlags_ - float WidthGiven; // Final/actual width visible == (MaxX - MinX), locked in TableUpdateLayout(). May be > WidthRequest to honor minimum width, may be < WidthRequest to honor shrinking columns down in tight space. - float MinX; // Absolute positions - float MaxX; - float WidthRequest; // Master width absolute value when !(Flags & _WidthStretch). When Stretch this is derived every frame from StretchWeight in TableUpdateLayout() - float WidthAuto; // Automatic width - float StretchWeight; // Master width weight when (Flags & _WidthStretch). Often around ~1.0f initially. - float InitStretchWeightOrWidth; // Value passed to TableSetupColumn(). For Width it is a content width (_without padding_). - ImRect ClipRect; // Clipping rectangle for the column - ImGuiID UserID; // Optional, value passed to TableSetupColumn() - float WorkMinX; // Contents region min ~(MinX + CellPaddingX + CellSpacingX1) == cursor start position when entering column - float WorkMaxX; // Contents region max ~(MaxX - CellPaddingX - CellSpacingX2) - float ItemWidth; // Current item width for the column, preserved across rows - float ContentMaxXFrozen; // Contents maximum position for frozen rows (apart from headers), from which we can infer content width. - float ContentMaxXUnfrozen; - float ContentMaxXHeadersUsed; // Contents maximum position for headers rows (regardless of freezing). TableHeader() automatically softclip itself + report ideal desired size, to avoid creating extraneous draw calls - float ContentMaxXHeadersIdeal; - ImS16 NameOffset; // Offset into parent ColumnsNames[] - ImGuiTableColumnIdx DisplayOrder; // Index within Table's IndexToDisplayOrder[] (column may be reordered by users) - ImGuiTableColumnIdx IndexWithinEnabledSet; // Index within enabled/visible set (<= IndexToDisplayOrder) - ImGuiTableColumnIdx PrevEnabledColumn; // Index of prev enabled/visible column within Columns[], -1 if first enabled/visible column - ImGuiTableColumnIdx NextEnabledColumn; // Index of next enabled/visible column within Columns[], -1 if last enabled/visible column - ImGuiTableColumnIdx SortOrder; // Index of this column within sort specs, -1 if not sorting on this column, 0 for single-sort, may be >0 on multi-sort - ImGuiTableDrawChannelIdx DrawChannelCurrent; // Index within DrawSplitter.Channels[] - ImGuiTableDrawChannelIdx DrawChannelFrozen; // Draw channels for frozen rows (often headers) - ImGuiTableDrawChannelIdx DrawChannelUnfrozen; // Draw channels for unfrozen rows - bool IsEnabled; // IsUserEnabled && (Flags & ImGuiTableColumnFlags_Disabled) == 0 - bool IsUserEnabled; // Is the column not marked Hidden by the user? (unrelated to being off view, e.g. clipped by scrolling). - bool IsUserEnabledNextFrame; - bool IsVisibleX; // Is actually in view (e.g. overlapping the host window clipping rectangle, not scrolled). - bool IsVisibleY; - bool IsRequestOutput; // Return value for TableSetColumnIndex() / TableNextColumn(): whether we request user to output contents or not. - bool IsSkipItems; // Do we want item submissions to this column to be completely ignored (no layout will happen). - bool IsPreserveWidthAuto; - ImS8 NavLayerCurrent; // ImGuiNavLayer in 1 byte - ImU8 AutoFitQueue; // Queue of 8 values for the next 8 frames to request auto-fit - ImU8 CannotSkipItemsQueue; // Queue of 8 values for the next 8 frames to disable Clipped/SkipItem - ImU8 SortDirection : 2; // ImGuiSortDirection_Ascending or ImGuiSortDirection_Descending - ImU8 SortDirectionsAvailCount : 2; // Number of available sort directions (0 to 3) - ImU8 SortDirectionsAvailMask : 4; // Mask of available sort directions (1-bit each) - ImU8 SortDirectionsAvailList; // Ordered list of available sort directions (2-bits each, total 8-bits) - - ImGuiTableColumn() - { - memset(this, 0, sizeof(*this)); - StretchWeight = WidthRequest = -1.0f; - NameOffset = -1; - DisplayOrder = IndexWithinEnabledSet = -1; - PrevEnabledColumn = NextEnabledColumn = -1; - SortOrder = -1; - SortDirection = ImGuiSortDirection_None; - DrawChannelCurrent = DrawChannelFrozen = DrawChannelUnfrozen = (ImU8)-1; - } -}; - -// Transient cell data stored per row. -// sizeof() ~ 6 -struct ImGuiTableCellData -{ - ImU32 BgColor; // Actual color - ImGuiTableColumnIdx Column; // Column number -}; - -// Per-instance data that needs preserving across frames (seemingly most others do not need to be preserved aside from debug needs. Does that means they could be moved to ImGuiTableTempData?) -// sizeof() ~ 24 bytes -struct ImGuiTableInstanceData -{ - ImGuiID TableInstanceID; - float LastOuterHeight; // Outer height from last frame - float LastTopHeadersRowHeight; // Height of first consecutive header rows from last frame (FIXME: this is used assuming consecutive headers are in same frozen set) - float LastFrozenHeight; // Height of frozen section from last frame - int HoveredRowLast; // Index of row which was hovered last frame. - int HoveredRowNext; // Index of row hovered this frame, set after encountering it. - - ImGuiTableInstanceData() { TableInstanceID = 0; LastOuterHeight = LastTopHeadersRowHeight = LastFrozenHeight = 0.0f; HoveredRowLast = HoveredRowNext = -1; } -}; - -// FIXME-TABLE: more transient data could be stored in a stacked ImGuiTableTempData: e.g. SortSpecs, incoming RowData -// sizeof() ~ 580 bytes + heap allocs described in TableBeginInitMemory() -struct IMGUI_API ImGuiTable -{ - ImGuiID ID; - ImGuiTableFlags Flags; - void* RawData; // Single allocation to hold Columns[], DisplayOrderToIndex[] and RowCellData[] - ImGuiTableTempData* TempData; // Transient data while table is active. Point within g.CurrentTableStack[] - ImSpan Columns; // Point within RawData[] - ImSpan DisplayOrderToIndex; // Point within RawData[]. Store display order of columns (when not reordered, the values are 0...Count-1) - ImSpan RowCellData; // Point within RawData[]. Store cells background requests for current row. - ImBitArrayPtr EnabledMaskByDisplayOrder; // Column DisplayOrder -> IsEnabled map - ImBitArrayPtr EnabledMaskByIndex; // Column Index -> IsEnabled map (== not hidden by user/api) in a format adequate for iterating column without touching cold data - ImBitArrayPtr VisibleMaskByIndex; // Column Index -> IsVisibleX|IsVisibleY map (== not hidden by user/api && not hidden by scrolling/cliprect) - ImGuiTableFlags SettingsLoadedFlags; // Which data were loaded from the .ini file (e.g. when order is not altered we won't save order) - int SettingsOffset; // Offset in g.SettingsTables - int LastFrameActive; - int ColumnsCount; // Number of columns declared in BeginTable() - int CurrentRow; - int CurrentColumn; - ImS16 InstanceCurrent; // Count of BeginTable() calls with same ID in the same frame (generally 0). This is a little bit similar to BeginCount for a window, but multiple table with same ID look are multiple tables, they are just synched. - ImS16 InstanceInteracted; // Mark which instance (generally 0) of the same ID is being interacted with - float RowPosY1; - float RowPosY2; - float RowMinHeight; // Height submitted to TableNextRow() - float RowCellPaddingY; // Top and bottom padding. Reloaded during row change. - float RowTextBaseline; - float RowIndentOffsetX; - ImGuiTableRowFlags RowFlags : 16; // Current row flags, see ImGuiTableRowFlags_ - ImGuiTableRowFlags LastRowFlags : 16; - int RowBgColorCounter; // Counter for alternating background colors (can be fast-forwarded by e.g clipper), not same as CurrentRow because header rows typically don't increase this. - ImU32 RowBgColor[2]; // Background color override for current row. - ImU32 BorderColorStrong; - ImU32 BorderColorLight; - float BorderX1; - float BorderX2; - float HostIndentX; - float MinColumnWidth; - float OuterPaddingX; - float CellPaddingX; // Padding from each borders. Locked in BeginTable()/Layout. - float CellSpacingX1; // Spacing between non-bordered cells. Locked in BeginTable()/Layout. - float CellSpacingX2; - float InnerWidth; // User value passed to BeginTable(), see comments at the top of BeginTable() for details. - float ColumnsGivenWidth; // Sum of current column width - float ColumnsAutoFitWidth; // Sum of ideal column width in order nothing to be clipped, used for auto-fitting and content width submission in outer window - float ColumnsStretchSumWeights; // Sum of weight of all enabled stretching columns - float ResizedColumnNextWidth; - float ResizeLockMinContentsX2; // Lock minimum contents width while resizing down in order to not create feedback loops. But we allow growing the table. - float RefScale; // Reference scale to be able to rescale columns on font/dpi changes. - float AngledHeadersHeight; // Set by TableAngledHeadersRow(), used in TableUpdateLayout() - float AngledHeadersSlope; // Set by TableAngledHeadersRow(), used in TableUpdateLayout() - ImRect OuterRect; // Note: for non-scrolling table, OuterRect.Max.y is often FLT_MAX until EndTable(), unless a height has been specified in BeginTable(). - ImRect InnerRect; // InnerRect but without decoration. As with OuterRect, for non-scrolling tables, InnerRect.Max.y is - ImRect WorkRect; - ImRect InnerClipRect; - ImRect BgClipRect; // We use this to cpu-clip cell background color fill, evolve during the frame as we cross frozen rows boundaries - ImRect Bg0ClipRectForDrawCmd; // Actual ImDrawCmd clip rect for BG0/1 channel. This tends to be == OuterWindow->ClipRect at BeginTable() because output in BG0/BG1 is cpu-clipped - ImRect Bg2ClipRectForDrawCmd; // Actual ImDrawCmd clip rect for BG2 channel. This tends to be a correct, tight-fit, because output to BG2 are done by widgets relying on regular ClipRect. - ImRect HostClipRect; // This is used to check if we can eventually merge our columns draw calls into the current draw call of the current window. - ImRect HostBackupInnerClipRect; // Backup of InnerWindow->ClipRect during PushTableBackground()/PopTableBackground() - ImGuiWindow* OuterWindow; // Parent window for the table - ImGuiWindow* InnerWindow; // Window holding the table data (== OuterWindow or a child window) - ImGuiTextBuffer ColumnsNames; // Contiguous buffer holding columns names - ImDrawListSplitter* DrawSplitter; // Shortcut to TempData->DrawSplitter while in table. Isolate draw commands per columns to avoid switching clip rect constantly - ImGuiTableInstanceData InstanceDataFirst; - ImVector InstanceDataExtra; // FIXME-OPT: Using a small-vector pattern would be good. - ImGuiTableColumnSortSpecs SortSpecsSingle; - ImVector SortSpecsMulti; // FIXME-OPT: Using a small-vector pattern would be good. - ImGuiTableSortSpecs SortSpecs; // Public facing sorts specs, this is what we return in TableGetSortSpecs() - ImGuiTableColumnIdx SortSpecsCount; - ImGuiTableColumnIdx ColumnsEnabledCount; // Number of enabled columns (<= ColumnsCount) - ImGuiTableColumnIdx ColumnsEnabledFixedCount; // Number of enabled columns (<= ColumnsCount) - ImGuiTableColumnIdx DeclColumnsCount; // Count calls to TableSetupColumn() - ImGuiTableColumnIdx AngledHeadersCount; // Count columns with angled headers - ImGuiTableColumnIdx HoveredColumnBody; // Index of column whose visible region is being hovered. Important: == ColumnsCount when hovering empty region after the right-most column! - ImGuiTableColumnIdx HoveredColumnBorder; // Index of column whose right-border is being hovered (for resizing). - ImGuiTableColumnIdx HighlightColumnHeader; // Index of column which should be highlighted. - ImGuiTableColumnIdx AutoFitSingleColumn; // Index of single column requesting auto-fit. - ImGuiTableColumnIdx ResizedColumn; // Index of column being resized. Reset when InstanceCurrent==0. - ImGuiTableColumnIdx LastResizedColumn; // Index of column being resized from previous frame. - ImGuiTableColumnIdx HeldHeaderColumn; // Index of column header being held. - ImGuiTableColumnIdx ReorderColumn; // Index of column being reordered. (not cleared) - ImGuiTableColumnIdx ReorderColumnDir; // -1 or +1 - ImGuiTableColumnIdx LeftMostEnabledColumn; // Index of left-most non-hidden column. - ImGuiTableColumnIdx RightMostEnabledColumn; // Index of right-most non-hidden column. - ImGuiTableColumnIdx LeftMostStretchedColumn; // Index of left-most stretched column. - ImGuiTableColumnIdx RightMostStretchedColumn; // Index of right-most stretched column. - ImGuiTableColumnIdx ContextPopupColumn; // Column right-clicked on, of -1 if opening context menu from a neutral/empty spot - ImGuiTableColumnIdx FreezeRowsRequest; // Requested frozen rows count - ImGuiTableColumnIdx FreezeRowsCount; // Actual frozen row count (== FreezeRowsRequest, or == 0 when no scrolling offset) - ImGuiTableColumnIdx FreezeColumnsRequest; // Requested frozen columns count - ImGuiTableColumnIdx FreezeColumnsCount; // Actual frozen columns count (== FreezeColumnsRequest, or == 0 when no scrolling offset) - ImGuiTableColumnIdx RowCellDataCurrent; // Index of current RowCellData[] entry in current row - ImGuiTableDrawChannelIdx DummyDrawChannel; // Redirect non-visible columns here. - ImGuiTableDrawChannelIdx Bg2DrawChannelCurrent; // For Selectable() and other widgets drawing across columns after the freezing line. Index within DrawSplitter.Channels[] - ImGuiTableDrawChannelIdx Bg2DrawChannelUnfrozen; - bool IsLayoutLocked; // Set by TableUpdateLayout() which is called when beginning the first row. - bool IsInsideRow; // Set when inside TableBeginRow()/TableEndRow(). - bool IsInitializing; - bool IsSortSpecsDirty; - bool IsUsingHeaders; // Set when the first row had the ImGuiTableRowFlags_Headers flag. - bool IsContextPopupOpen; // Set when default context menu is open (also see: ContextPopupColumn, InstanceInteracted). - bool IsSettingsRequestLoad; - bool IsSettingsDirty; // Set when table settings have changed and needs to be reported into ImGuiTableSetttings data. - bool IsDefaultDisplayOrder; // Set when display order is unchanged from default (DisplayOrder contains 0...Count-1) - bool IsResetAllRequest; - bool IsResetDisplayOrderRequest; - bool IsUnfrozenRows; // Set when we got past the frozen row. - bool IsDefaultSizingPolicy; // Set if user didn't explicitly set a sizing policy in BeginTable() - bool IsActiveIdAliveBeforeTable; - bool IsActiveIdInTable; - bool HasScrollbarYCurr; // Whether ANY instance of this table had a vertical scrollbar during the current frame. - bool HasScrollbarYPrev; // Whether ANY instance of this table had a vertical scrollbar during the previous. - bool MemoryCompacted; - bool HostSkipItems; // Backup of InnerWindow->SkipItem at the end of BeginTable(), because we will overwrite InnerWindow->SkipItem on a per-column basis - - ImGuiTable() { memset(this, 0, sizeof(*this)); LastFrameActive = -1; } - ~ImGuiTable() { IM_FREE(RawData); } -}; - -// Transient data that are only needed between BeginTable() and EndTable(), those buffers are shared (1 per level of stacked table). -// - Accessing those requires chasing an extra pointer so for very frequently used data we leave them in the main table structure. -// - We also leave out of this structure data that tend to be particularly useful for debugging/metrics. -// sizeof() ~ 120 bytes. -struct IMGUI_API ImGuiTableTempData -{ - int TableIndex; // Index in g.Tables.Buf[] pool - float LastTimeActive; // Last timestamp this structure was used - float AngledheadersExtraWidth; // Used in EndTable() - - ImVec2 UserOuterSize; // outer_size.x passed to BeginTable() - ImDrawListSplitter DrawSplitter; - - ImRect HostBackupWorkRect; // Backup of InnerWindow->WorkRect at the end of BeginTable() - ImRect HostBackupParentWorkRect; // Backup of InnerWindow->ParentWorkRect at the end of BeginTable() - ImVec2 HostBackupPrevLineSize; // Backup of InnerWindow->DC.PrevLineSize at the end of BeginTable() - ImVec2 HostBackupCurrLineSize; // Backup of InnerWindow->DC.CurrLineSize at the end of BeginTable() - ImVec2 HostBackupCursorMaxPos; // Backup of InnerWindow->DC.CursorMaxPos at the end of BeginTable() - ImVec1 HostBackupColumnsOffset; // Backup of OuterWindow->DC.ColumnsOffset at the end of BeginTable() - float HostBackupItemWidth; // Backup of OuterWindow->DC.ItemWidth at the end of BeginTable() - int HostBackupItemWidthStackSize;//Backup of OuterWindow->DC.ItemWidthStack.Size at the end of BeginTable() - - ImGuiTableTempData() { memset(this, 0, sizeof(*this)); LastTimeActive = -1.0f; } -}; - -// sizeof() ~ 12 -struct ImGuiTableColumnSettings -{ - float WidthOrWeight; - ImGuiID UserID; - ImGuiTableColumnIdx Index; - ImGuiTableColumnIdx DisplayOrder; - ImGuiTableColumnIdx SortOrder; - ImU8 SortDirection : 2; - ImU8 IsEnabled : 1; // "Visible" in ini file - ImU8 IsStretch : 1; - - ImGuiTableColumnSettings() - { - WidthOrWeight = 0.0f; - UserID = 0; - Index = -1; - DisplayOrder = SortOrder = -1; - SortDirection = ImGuiSortDirection_None; - IsEnabled = 1; - IsStretch = 0; - } -}; - -// This is designed to be stored in a single ImChunkStream (1 header followed by N ImGuiTableColumnSettings, etc.) -struct ImGuiTableSettings -{ - ImGuiID ID; // Set to 0 to invalidate/delete the setting - ImGuiTableFlags SaveFlags; // Indicate data we want to save using the Resizable/Reorderable/Sortable/Hideable flags (could be using its own flags..) - float RefScale; // Reference scale to be able to rescale columns on font/dpi changes. - ImGuiTableColumnIdx ColumnsCount; - ImGuiTableColumnIdx ColumnsCountMax; // Maximum number of columns this settings instance can store, we can recycle a settings instance with lower number of columns but not higher - bool WantApply; // Set when loaded from .ini data (to enable merging/loading .ini data into an already running context) - - ImGuiTableSettings() { memset(this, 0, sizeof(*this)); } - ImGuiTableColumnSettings* GetColumnSettings() { return (ImGuiTableColumnSettings*)(this + 1); } -}; - -//----------------------------------------------------------------------------- -// [SECTION] ImGui internal API -// No guarantee of forward compatibility here! -//----------------------------------------------------------------------------- - -namespace ImGui -{ - // Windows - // We should always have a CurrentWindow in the stack (there is an implicit "Debug" window) - // If this ever crash because g.CurrentWindow is NULL it means that either - // - ImGui::NewFrame() has never been called, which is illegal. - // - You are calling ImGui functions after ImGui::EndFrame()/ImGui::Render() and before the next ImGui::NewFrame(), which is also illegal. - inline ImGuiWindow* GetCurrentWindowRead() { ImGuiContext& g = *GImGui; return g.CurrentWindow; } - inline ImGuiWindow* GetCurrentWindow() { ImGuiContext& g = *GImGui; g.CurrentWindow->WriteAccessed = true; return g.CurrentWindow; } - IMGUI_API ImGuiWindow* FindWindowByID(ImGuiID id); - IMGUI_API ImGuiWindow* FindWindowByName(const char* name); - IMGUI_API void UpdateWindowParentAndRootLinks(ImGuiWindow* window, ImGuiWindowFlags flags, ImGuiWindow* parent_window); - IMGUI_API ImVec2 CalcWindowNextAutoFitSize(ImGuiWindow* window); - IMGUI_API bool IsWindowChildOf(ImGuiWindow* window, ImGuiWindow* potential_parent, bool popup_hierarchy, bool dock_hierarchy); - IMGUI_API bool IsWindowWithinBeginStackOf(ImGuiWindow* window, ImGuiWindow* potential_parent); - IMGUI_API bool IsWindowAbove(ImGuiWindow* potential_above, ImGuiWindow* potential_below); - IMGUI_API bool IsWindowNavFocusable(ImGuiWindow* window); - IMGUI_API void SetWindowPos(ImGuiWindow* window, const ImVec2& pos, ImGuiCond cond = 0); - IMGUI_API void SetWindowSize(ImGuiWindow* window, const ImVec2& size, ImGuiCond cond = 0); - IMGUI_API void SetWindowCollapsed(ImGuiWindow* window, bool collapsed, ImGuiCond cond = 0); - IMGUI_API void SetWindowHitTestHole(ImGuiWindow* window, const ImVec2& pos, const ImVec2& size); - IMGUI_API void SetWindowHiddendAndSkipItemsForCurrentFrame(ImGuiWindow* window); - inline ImRect WindowRectAbsToRel(ImGuiWindow* window, const ImRect& r) { ImVec2 off = window->DC.CursorStartPos; return ImRect(r.Min.x - off.x, r.Min.y - off.y, r.Max.x - off.x, r.Max.y - off.y); } - inline ImRect WindowRectRelToAbs(ImGuiWindow* window, const ImRect& r) { ImVec2 off = window->DC.CursorStartPos; return ImRect(r.Min.x + off.x, r.Min.y + off.y, r.Max.x + off.x, r.Max.y + off.y); } - inline ImVec2 WindowPosRelToAbs(ImGuiWindow* window, const ImVec2& p) { ImVec2 off = window->DC.CursorStartPos; return ImVec2(p.x + off.x, p.y + off.y); } - - // Windows: Display Order and Focus Order - IMGUI_API void FocusWindow(ImGuiWindow* window, ImGuiFocusRequestFlags flags = 0); - IMGUI_API void FocusTopMostWindowUnderOne(ImGuiWindow* under_this_window, ImGuiWindow* ignore_window, ImGuiViewport* filter_viewport, ImGuiFocusRequestFlags flags); - IMGUI_API void BringWindowToFocusFront(ImGuiWindow* window); - IMGUI_API void BringWindowToDisplayFront(ImGuiWindow* window); - IMGUI_API void BringWindowToDisplayBack(ImGuiWindow* window); - IMGUI_API void BringWindowToDisplayBehind(ImGuiWindow* window, ImGuiWindow* above_window); - IMGUI_API int FindWindowDisplayIndex(ImGuiWindow* window); - IMGUI_API ImGuiWindow* FindBottomMostVisibleWindowWithinBeginStack(ImGuiWindow* window); - - // Fonts, drawing - IMGUI_API void SetCurrentFont(ImFont* font); - inline ImFont* GetDefaultFont() { ImGuiContext& g = *GImGui; return g.IO.FontDefault ? g.IO.FontDefault : g.IO.Fonts->Fonts[0]; } - inline ImDrawList* GetForegroundDrawList(ImGuiWindow* window) { return GetForegroundDrawList(window->Viewport); } - IMGUI_API void AddDrawListToDrawDataEx(ImDrawData* draw_data, ImVector* out_list, ImDrawList* draw_list); - - // Init - IMGUI_API void Initialize(); - IMGUI_API void Shutdown(); // Since 1.60 this is a _private_ function. You can call DestroyContext() to destroy the context created by CreateContext(). - - // NewFrame - IMGUI_API void UpdateInputEvents(bool trickle_fast_inputs); - IMGUI_API void UpdateHoveredWindowAndCaptureFlags(); - IMGUI_API void StartMouseMovingWindow(ImGuiWindow* window); - IMGUI_API void StartMouseMovingWindowOrNode(ImGuiWindow* window, ImGuiDockNode* node, bool undock_floating_node); - IMGUI_API void UpdateMouseMovingWindowNewFrame(); - IMGUI_API void UpdateMouseMovingWindowEndFrame(); - - // Generic context hooks - IMGUI_API ImGuiID AddContextHook(ImGuiContext* context, const ImGuiContextHook* hook); - IMGUI_API void RemoveContextHook(ImGuiContext* context, ImGuiID hook_to_remove); - IMGUI_API void CallContextHooks(ImGuiContext* context, ImGuiContextHookType type); - - // Viewports - IMGUI_API void TranslateWindowsInViewport(ImGuiViewportP* viewport, const ImVec2& old_pos, const ImVec2& new_pos); - IMGUI_API void ScaleWindowsInViewport(ImGuiViewportP* viewport, float scale); - IMGUI_API void DestroyPlatformWindow(ImGuiViewportP* viewport); - IMGUI_API void SetWindowViewport(ImGuiWindow* window, ImGuiViewportP* viewport); - IMGUI_API void SetCurrentViewport(ImGuiWindow* window, ImGuiViewportP* viewport); - IMGUI_API const ImGuiPlatformMonitor* GetViewportPlatformMonitor(ImGuiViewport* viewport); - IMGUI_API ImGuiViewportP* FindHoveredViewportFromPlatformWindowStack(const ImVec2& mouse_platform_pos); - - // Settings - IMGUI_API void MarkIniSettingsDirty(); - IMGUI_API void MarkIniSettingsDirty(ImGuiWindow* window); - IMGUI_API void ClearIniSettings(); - IMGUI_API void AddSettingsHandler(const ImGuiSettingsHandler* handler); - IMGUI_API void RemoveSettingsHandler(const char* type_name); - IMGUI_API ImGuiSettingsHandler* FindSettingsHandler(const char* type_name); - - // Settings - Windows - IMGUI_API ImGuiWindowSettings* CreateNewWindowSettings(const char* name); - IMGUI_API ImGuiWindowSettings* FindWindowSettingsByID(ImGuiID id); - IMGUI_API ImGuiWindowSettings* FindWindowSettingsByWindow(ImGuiWindow* window); - IMGUI_API void ClearWindowSettings(const char* name); - - // Localization - IMGUI_API void LocalizeRegisterEntries(const ImGuiLocEntry* entries, int count); - inline const char* LocalizeGetMsg(ImGuiLocKey key) { ImGuiContext& g = *GImGui; const char* msg = g.LocalizationTable[key]; return msg ? msg : "*Missing Text*"; } - - // Scrolling - IMGUI_API void SetScrollX(ImGuiWindow* window, float scroll_x); - IMGUI_API void SetScrollY(ImGuiWindow* window, float scroll_y); - IMGUI_API void SetScrollFromPosX(ImGuiWindow* window, float local_x, float center_x_ratio); - IMGUI_API void SetScrollFromPosY(ImGuiWindow* window, float local_y, float center_y_ratio); - - // Early work-in-progress API (ScrollToItem() will become public) - IMGUI_API void ScrollToItem(ImGuiScrollFlags flags = 0); - IMGUI_API void ScrollToRect(ImGuiWindow* window, const ImRect& rect, ImGuiScrollFlags flags = 0); - IMGUI_API ImVec2 ScrollToRectEx(ImGuiWindow* window, const ImRect& rect, ImGuiScrollFlags flags = 0); -//#ifndef IMGUI_DISABLE_OBSOLETE_FUNCTIONS - inline void ScrollToBringRectIntoView(ImGuiWindow* window, const ImRect& rect) { ScrollToRect(window, rect, ImGuiScrollFlags_KeepVisibleEdgeY); } -//#endif - - // Basic Accessors - inline ImGuiItemStatusFlags GetItemStatusFlags(){ ImGuiContext& g = *GImGui; return g.LastItemData.StatusFlags; } - inline ImGuiItemFlags GetItemFlags() { ImGuiContext& g = *GImGui; return g.LastItemData.InFlags; } - inline ImGuiID GetActiveID() { ImGuiContext& g = *GImGui; return g.ActiveId; } - inline ImGuiID GetFocusID() { ImGuiContext& g = *GImGui; return g.NavId; } - IMGUI_API void SetActiveID(ImGuiID id, ImGuiWindow* window); - IMGUI_API void SetFocusID(ImGuiID id, ImGuiWindow* window); - IMGUI_API void ClearActiveID(); - IMGUI_API ImGuiID GetHoveredID(); - IMGUI_API void SetHoveredID(ImGuiID id); - IMGUI_API void KeepAliveID(ImGuiID id); - IMGUI_API void MarkItemEdited(ImGuiID id); // Mark data associated to given item as "edited", used by IsItemDeactivatedAfterEdit() function. - IMGUI_API void PushOverrideID(ImGuiID id); // Push given value as-is at the top of the ID stack (whereas PushID combines old and new hashes) - IMGUI_API ImGuiID GetIDWithSeed(const char* str_id_begin, const char* str_id_end, ImGuiID seed); - IMGUI_API ImGuiID GetIDWithSeed(int n, ImGuiID seed); - - // Basic Helpers for widget code - IMGUI_API void ItemSize(const ImVec2& size, float text_baseline_y = -1.0f); - inline void ItemSize(const ImRect& bb, float text_baseline_y = -1.0f) { ItemSize(bb.GetSize(), text_baseline_y); } // FIXME: This is a misleading API since we expect CursorPos to be bb.Min. - IMGUI_API bool ItemAdd(const ImRect& bb, ImGuiID id, const ImRect* nav_bb = NULL, ImGuiItemFlags extra_flags = 0); - IMGUI_API bool ItemHoverable(const ImRect& bb, ImGuiID id, ImGuiItemFlags item_flags); - IMGUI_API bool IsWindowContentHoverable(ImGuiWindow* window, ImGuiHoveredFlags flags = 0); - IMGUI_API bool IsClippedEx(const ImRect& bb, ImGuiID id); - IMGUI_API void SetLastItemData(ImGuiID item_id, ImGuiItemFlags in_flags, ImGuiItemStatusFlags status_flags, const ImRect& item_rect); - IMGUI_API ImVec2 CalcItemSize(ImVec2 size, float default_w, float default_h); - IMGUI_API float CalcWrapWidthForPos(const ImVec2& pos, float wrap_pos_x); - IMGUI_API void PushMultiItemsWidths(int components, float width_full); - IMGUI_API bool IsItemToggledSelection(); // Was the last item selection toggled? (after Selectable(), TreeNode() etc. We only returns toggle _event_ in order to handle clipping correctly) - IMGUI_API ImVec2 GetContentRegionMaxAbs(); - IMGUI_API void ShrinkWidths(ImGuiShrinkWidthItem* items, int count, float width_excess); - - // Parameter stacks (shared) - IMGUI_API void PushItemFlag(ImGuiItemFlags option, bool enabled); - IMGUI_API void PopItemFlag(); - IMGUI_API const ImGuiDataVarInfo* GetStyleVarInfo(ImGuiStyleVar idx); - - // Logging/Capture - IMGUI_API void LogBegin(ImGuiLogType type, int auto_open_depth); // -> BeginCapture() when we design v2 api, for now stay under the radar by using the old name. - IMGUI_API void LogToBuffer(int auto_open_depth = -1); // Start logging/capturing to internal buffer - IMGUI_API void LogRenderedText(const ImVec2* ref_pos, const char* text, const char* text_end = NULL); - IMGUI_API void LogSetNextTextDecoration(const char* prefix, const char* suffix); - - // Popups, Modals, Tooltips - IMGUI_API bool BeginChildEx(const char* name, ImGuiID id, const ImVec2& size_arg, bool border, ImGuiWindowFlags flags); - IMGUI_API void OpenPopupEx(ImGuiID id, ImGuiPopupFlags popup_flags = ImGuiPopupFlags_None); - IMGUI_API void ClosePopupToLevel(int remaining, bool restore_focus_to_window_under_popup); - IMGUI_API void ClosePopupsOverWindow(ImGuiWindow* ref_window, bool restore_focus_to_window_under_popup); - IMGUI_API void ClosePopupsExceptModals(); - IMGUI_API bool IsPopupOpen(ImGuiID id, ImGuiPopupFlags popup_flags); - IMGUI_API bool BeginPopupEx(ImGuiID id, ImGuiWindowFlags extra_flags); - IMGUI_API bool BeginTooltipEx(ImGuiTooltipFlags tooltip_flags, ImGuiWindowFlags extra_window_flags); - IMGUI_API bool BeginTooltipHidden(); - IMGUI_API ImRect GetPopupAllowedExtentRect(ImGuiWindow* window); - IMGUI_API ImGuiWindow* GetTopMostPopupModal(); - IMGUI_API ImGuiWindow* GetTopMostAndVisiblePopupModal(); - IMGUI_API ImGuiWindow* FindBlockingModal(ImGuiWindow* window); - IMGUI_API ImVec2 FindBestWindowPosForPopup(ImGuiWindow* window); - IMGUI_API ImVec2 FindBestWindowPosForPopupEx(const ImVec2& ref_pos, const ImVec2& size, ImGuiDir* last_dir, const ImRect& r_outer, const ImRect& r_avoid, ImGuiPopupPositionPolicy policy); - - // Menus - IMGUI_API bool BeginViewportSideBar(const char* name, ImGuiViewport* viewport, ImGuiDir dir, float size, ImGuiWindowFlags window_flags); - IMGUI_API bool BeginMenuEx(const char* label, const char* icon, bool enabled = true); - IMGUI_API bool MenuItemEx(const char* label, const char* icon, const char* shortcut = NULL, bool selected = false, bool enabled = true); - - // Combos - IMGUI_API bool BeginComboPopup(ImGuiID popup_id, const ImRect& bb, ImGuiComboFlags flags); - IMGUI_API bool BeginComboPreview(); - IMGUI_API void EndComboPreview(); - - // Gamepad/Keyboard Navigation - IMGUI_API void NavInitWindow(ImGuiWindow* window, bool force_reinit); - IMGUI_API void NavInitRequestApplyResult(); - IMGUI_API bool NavMoveRequestButNoResultYet(); - IMGUI_API void NavMoveRequestSubmit(ImGuiDir move_dir, ImGuiDir clip_dir, ImGuiNavMoveFlags move_flags, ImGuiScrollFlags scroll_flags); - IMGUI_API void NavMoveRequestForward(ImGuiDir move_dir, ImGuiDir clip_dir, ImGuiNavMoveFlags move_flags, ImGuiScrollFlags scroll_flags); - IMGUI_API void NavMoveRequestResolveWithLastItem(ImGuiNavItemData* result); - IMGUI_API void NavMoveRequestResolveWithPastTreeNode(ImGuiNavItemData* result, ImGuiNavTreeNodeData* tree_node_data); - IMGUI_API void NavMoveRequestCancel(); - IMGUI_API void NavMoveRequestApplyResult(); - IMGUI_API void NavMoveRequestTryWrapping(ImGuiWindow* window, ImGuiNavMoveFlags move_flags); - IMGUI_API void NavClearPreferredPosForAxis(ImGuiAxis axis); - IMGUI_API void NavRestoreHighlightAfterMove(); - IMGUI_API void NavUpdateCurrentWindowIsScrollPushableX(); - IMGUI_API void SetNavWindow(ImGuiWindow* window); - IMGUI_API void SetNavID(ImGuiID id, ImGuiNavLayer nav_layer, ImGuiID focus_scope_id, const ImRect& rect_rel); - - // Focus/Activation - // This should be part of a larger set of API: FocusItem(offset = -1), FocusItemByID(id), ActivateItem(offset = -1), ActivateItemByID(id) etc. which are - // much harder to design and implement than expected. I have a couple of private branches on this matter but it's not simple. For now implementing the easy ones. - IMGUI_API void FocusItem(); // Focus last item (no selection/activation). - IMGUI_API void ActivateItemByID(ImGuiID id); // Activate an item by ID (button, checkbox, tree node etc.). Activation is queued and processed on the next frame when the item is encountered again. - - // Inputs - // FIXME: Eventually we should aim to move e.g. IsActiveIdUsingKey() into IsKeyXXX functions. - inline bool IsNamedKey(ImGuiKey key) { return key >= ImGuiKey_NamedKey_BEGIN && key < ImGuiKey_NamedKey_END; } - inline bool IsNamedKeyOrModKey(ImGuiKey key) { return (key >= ImGuiKey_NamedKey_BEGIN && key < ImGuiKey_NamedKey_END) || key == ImGuiMod_Ctrl || key == ImGuiMod_Shift || key == ImGuiMod_Alt || key == ImGuiMod_Super || key == ImGuiMod_Shortcut; } - inline bool IsLegacyKey(ImGuiKey key) { return key >= ImGuiKey_LegacyNativeKey_BEGIN && key < ImGuiKey_LegacyNativeKey_END; } - inline bool IsKeyboardKey(ImGuiKey key) { return key >= ImGuiKey_Keyboard_BEGIN && key < ImGuiKey_Keyboard_END; } - inline bool IsGamepadKey(ImGuiKey key) { return key >= ImGuiKey_Gamepad_BEGIN && key < ImGuiKey_Gamepad_END; } - inline bool IsMouseKey(ImGuiKey key) { return key >= ImGuiKey_Mouse_BEGIN && key < ImGuiKey_Mouse_END; } - inline bool IsAliasKey(ImGuiKey key) { return key >= ImGuiKey_Aliases_BEGIN && key < ImGuiKey_Aliases_END; } - inline ImGuiKeyChord ConvertShortcutMod(ImGuiKeyChord key_chord) { ImGuiContext& g = *GImGui; IM_ASSERT_PARANOID(key_chord & ImGuiMod_Shortcut); return (key_chord & ~ImGuiMod_Shortcut) | (g.IO.ConfigMacOSXBehaviors ? ImGuiMod_Super : ImGuiMod_Ctrl); } - inline ImGuiKey ConvertSingleModFlagToKey(ImGuiContext* ctx, ImGuiKey key) - { - ImGuiContext& g = *ctx; - if (key == ImGuiMod_Ctrl) return ImGuiKey_ReservedForModCtrl; - if (key == ImGuiMod_Shift) return ImGuiKey_ReservedForModShift; - if (key == ImGuiMod_Alt) return ImGuiKey_ReservedForModAlt; - if (key == ImGuiMod_Super) return ImGuiKey_ReservedForModSuper; - if (key == ImGuiMod_Shortcut) return (g.IO.ConfigMacOSXBehaviors ? ImGuiKey_ReservedForModSuper : ImGuiKey_ReservedForModCtrl); - return key; - } - - IMGUI_API ImGuiKeyData* GetKeyData(ImGuiContext* ctx, ImGuiKey key); - inline ImGuiKeyData* GetKeyData(ImGuiKey key) { ImGuiContext& g = *GImGui; return GetKeyData(&g, key); } - IMGUI_API void GetKeyChordName(ImGuiKeyChord key_chord, char* out_buf, int out_buf_size); - inline ImGuiKey MouseButtonToKey(ImGuiMouseButton button) { IM_ASSERT(button >= 0 && button < ImGuiMouseButton_COUNT); return (ImGuiKey)(ImGuiKey_MouseLeft + button); } - IMGUI_API bool IsMouseDragPastThreshold(ImGuiMouseButton button, float lock_threshold = -1.0f); - IMGUI_API ImVec2 GetKeyMagnitude2d(ImGuiKey key_left, ImGuiKey key_right, ImGuiKey key_up, ImGuiKey key_down); - IMGUI_API float GetNavTweakPressedAmount(ImGuiAxis axis); - IMGUI_API int CalcTypematicRepeatAmount(float t0, float t1, float repeat_delay, float repeat_rate); - IMGUI_API void GetTypematicRepeatRate(ImGuiInputFlags flags, float* repeat_delay, float* repeat_rate); - IMGUI_API void TeleportMousePos(const ImVec2& pos); - IMGUI_API void SetActiveIdUsingAllKeyboardKeys(); - inline bool IsActiveIdUsingNavDir(ImGuiDir dir) { ImGuiContext& g = *GImGui; return (g.ActiveIdUsingNavDirMask & (1 << dir)) != 0; } - - // [EXPERIMENTAL] Low-Level: Key/Input Ownership - // - The idea is that instead of "eating" a given input, we can link to an owner id. - // - Ownership is most often claimed as a result of reacting to a press/down event (but occasionally may be claimed ahead). - // - Input queries can then read input by specifying ImGuiKeyOwner_Any (== 0), ImGuiKeyOwner_None (== -1) or a custom ID. - // - Legacy input queries (without specifying an owner or _Any or _None) are equivalent to using ImGuiKeyOwner_Any (== 0). - // - Input ownership is automatically released on the frame after a key is released. Therefore: - // - for ownership registration happening as a result of a down/press event, the SetKeyOwner() call may be done once (common case). - // - for ownership registration happening ahead of a down/press event, the SetKeyOwner() call needs to be made every frame (happens if e.g. claiming ownership on hover). - // - SetItemKeyOwner() is a shortcut for common simple case. A custom widget will probably want to call SetKeyOwner() multiple times directly based on its interaction state. - // - This is marked experimental because not all widgets are fully honoring the Set/Test idioms. We will need to move forward step by step. - // Please open a GitHub Issue to submit your usage scenario or if there's a use case you need solved. - IMGUI_API ImGuiID GetKeyOwner(ImGuiKey key); - IMGUI_API void SetKeyOwner(ImGuiKey key, ImGuiID owner_id, ImGuiInputFlags flags = 0); - IMGUI_API void SetKeyOwnersForKeyChord(ImGuiKeyChord key, ImGuiID owner_id, ImGuiInputFlags flags = 0); - IMGUI_API void SetItemKeyOwner(ImGuiKey key, ImGuiInputFlags flags = 0); // Set key owner to last item if it is hovered or active. Equivalent to 'if (IsItemHovered() || IsItemActive()) { SetKeyOwner(key, GetItemID());'. - IMGUI_API bool TestKeyOwner(ImGuiKey key, ImGuiID owner_id); // Test that key is either not owned, either owned by 'owner_id' - inline ImGuiKeyOwnerData* GetKeyOwnerData(ImGuiContext* ctx, ImGuiKey key) { if (key & ImGuiMod_Mask_) key = ConvertSingleModFlagToKey(ctx, key); IM_ASSERT(IsNamedKey(key)); return &ctx->KeysOwnerData[key - ImGuiKey_NamedKey_BEGIN]; } - - // [EXPERIMENTAL] High-Level: Input Access functions w/ support for Key/Input Ownership - // - Important: legacy IsKeyPressed(ImGuiKey, bool repeat=true) _DEFAULTS_ to repeat, new IsKeyPressed() requires _EXPLICIT_ ImGuiInputFlags_Repeat flag. - // - Expected to be later promoted to public API, the prototypes are designed to replace existing ones (since owner_id can default to Any == 0) - // - Specifying a value for 'ImGuiID owner' will test that EITHER the key is NOT owned (UNLESS locked), EITHER the key is owned by 'owner'. - // Legacy functions use ImGuiKeyOwner_Any meaning that they typically ignore ownership, unless a call to SetKeyOwner() explicitly used ImGuiInputFlags_LockThisFrame or ImGuiInputFlags_LockUntilRelease. - // - Binding generators may want to ignore those for now, or suffix them with Ex() until we decide if this gets moved into public API. - IMGUI_API bool IsKeyDown(ImGuiKey key, ImGuiID owner_id); - IMGUI_API bool IsKeyPressed(ImGuiKey key, ImGuiID owner_id, ImGuiInputFlags flags = 0); // Important: when transitioning from old to new IsKeyPressed(): old API has "bool repeat = true", so would default to repeat. New API requiress explicit ImGuiInputFlags_Repeat. - IMGUI_API bool IsKeyReleased(ImGuiKey key, ImGuiID owner_id); - IMGUI_API bool IsMouseDown(ImGuiMouseButton button, ImGuiID owner_id); - IMGUI_API bool IsMouseClicked(ImGuiMouseButton button, ImGuiID owner_id, ImGuiInputFlags flags = 0); - IMGUI_API bool IsMouseReleased(ImGuiMouseButton button, ImGuiID owner_id); - - // [EXPERIMENTAL] Shortcut Routing - // - ImGuiKeyChord = a ImGuiKey optionally OR-red with ImGuiMod_Alt/ImGuiMod_Ctrl/ImGuiMod_Shift/ImGuiMod_Super. - // ImGuiKey_C (accepted by functions taking ImGuiKey or ImGuiKeyChord) - // ImGuiKey_C | ImGuiMod_Ctrl (accepted by functions taking ImGuiKeyChord) - // ONLY ImGuiMod_XXX values are legal to 'OR' with an ImGuiKey. You CANNOT 'OR' two ImGuiKey values. - // - When using one of the routing flags (e.g. ImGuiInputFlags_RouteFocused): routes requested ahead of time given a chord (key + modifiers) and a routing policy. - // - Routes are resolved during NewFrame(): if keyboard modifiers are matching current ones: SetKeyOwner() is called + route is granted for the frame. - // - Route is granted to a single owner. When multiple requests are made we have policies to select the winning route. - // - Multiple read sites may use the same owner id and will all get the granted route. - // - For routing: when owner_id is 0 we use the current Focus Scope ID as a default owner in order to identify our location. - IMGUI_API bool Shortcut(ImGuiKeyChord key_chord, ImGuiID owner_id = 0, ImGuiInputFlags flags = 0); - IMGUI_API bool SetShortcutRouting(ImGuiKeyChord key_chord, ImGuiID owner_id = 0, ImGuiInputFlags flags = 0); - IMGUI_API bool TestShortcutRouting(ImGuiKeyChord key_chord, ImGuiID owner_id); - IMGUI_API ImGuiKeyRoutingData* GetShortcutRoutingData(ImGuiKeyChord key_chord); - - // Docking - // (some functions are only declared in imgui.cpp, see Docking section) - IMGUI_API void DockContextInitialize(ImGuiContext* ctx); - IMGUI_API void DockContextShutdown(ImGuiContext* ctx); - IMGUI_API void DockContextClearNodes(ImGuiContext* ctx, ImGuiID root_id, bool clear_settings_refs); // Use root_id==0 to clear all - IMGUI_API void DockContextRebuildNodes(ImGuiContext* ctx); - IMGUI_API void DockContextNewFrameUpdateUndocking(ImGuiContext* ctx); - IMGUI_API void DockContextNewFrameUpdateDocking(ImGuiContext* ctx); - IMGUI_API void DockContextEndFrame(ImGuiContext* ctx); - IMGUI_API ImGuiID DockContextGenNodeID(ImGuiContext* ctx); - IMGUI_API void DockContextQueueDock(ImGuiContext* ctx, ImGuiWindow* target, ImGuiDockNode* target_node, ImGuiWindow* payload, ImGuiDir split_dir, float split_ratio, bool split_outer); - IMGUI_API void DockContextQueueUndockWindow(ImGuiContext* ctx, ImGuiWindow* window); - IMGUI_API void DockContextQueueUndockNode(ImGuiContext* ctx, ImGuiDockNode* node); - IMGUI_API void DockContextProcessUndockWindow(ImGuiContext* ctx, ImGuiWindow* window, bool clear_persistent_docking_ref = true); - IMGUI_API void DockContextProcessUndockNode(ImGuiContext* ctx, ImGuiDockNode* node); - IMGUI_API bool DockContextCalcDropPosForDocking(ImGuiWindow* target, ImGuiDockNode* target_node, ImGuiWindow* payload_window, ImGuiDockNode* payload_node, ImGuiDir split_dir, bool split_outer, ImVec2* out_pos); - IMGUI_API ImGuiDockNode*DockContextFindNodeByID(ImGuiContext* ctx, ImGuiID id); - IMGUI_API void DockNodeWindowMenuHandler_Default(ImGuiContext* ctx, ImGuiDockNode* node, ImGuiTabBar* tab_bar); - IMGUI_API bool DockNodeBeginAmendTabBar(ImGuiDockNode* node); - IMGUI_API void DockNodeEndAmendTabBar(); - inline ImGuiDockNode* DockNodeGetRootNode(ImGuiDockNode* node) { while (node->ParentNode) node = node->ParentNode; return node; } - inline bool DockNodeIsInHierarchyOf(ImGuiDockNode* node, ImGuiDockNode* parent) { while (node) { if (node == parent) return true; node = node->ParentNode; } return false; } - inline int DockNodeGetDepth(const ImGuiDockNode* node) { int depth = 0; while (node->ParentNode) { node = node->ParentNode; depth++; } return depth; } - inline ImGuiID DockNodeGetWindowMenuButtonId(const ImGuiDockNode* node) { return ImHashStr("#COLLAPSE", 0, node->ID); } - inline ImGuiDockNode* GetWindowDockNode() { ImGuiContext& g = *GImGui; return g.CurrentWindow->DockNode; } - IMGUI_API bool GetWindowAlwaysWantOwnTabBar(ImGuiWindow* window); - IMGUI_API void BeginDocked(ImGuiWindow* window, bool* p_open); - IMGUI_API void BeginDockableDragDropSource(ImGuiWindow* window); - IMGUI_API void BeginDockableDragDropTarget(ImGuiWindow* window); - IMGUI_API void SetWindowDock(ImGuiWindow* window, ImGuiID dock_id, ImGuiCond cond); - - // Docking - Builder function needs to be generally called before the node is used/submitted. - // - The DockBuilderXXX functions are designed to _eventually_ become a public API, but it is too early to expose it and guarantee stability. - // - Do not hold on ImGuiDockNode* pointers! They may be invalidated by any split/merge/remove operation and every frame. - // - To create a DockSpace() node, make sure to set the ImGuiDockNodeFlags_DockSpace flag when calling DockBuilderAddNode(). - // You can create dockspace nodes (attached to a window) _or_ floating nodes (carry its own window) with this API. - // - DockBuilderSplitNode() create 2 child nodes within 1 node. The initial node becomes a parent node. - // - If you intend to split the node immediately after creation using DockBuilderSplitNode(), make sure - // to call DockBuilderSetNodeSize() beforehand. If you don't, the resulting split sizes may not be reliable. - // - Call DockBuilderFinish() after you are done. - IMGUI_API void DockBuilderDockWindow(const char* window_name, ImGuiID node_id); - IMGUI_API ImGuiDockNode*DockBuilderGetNode(ImGuiID node_id); - inline ImGuiDockNode* DockBuilderGetCentralNode(ImGuiID node_id) { ImGuiDockNode* node = DockBuilderGetNode(node_id); if (!node) return NULL; return DockNodeGetRootNode(node)->CentralNode; } - IMGUI_API ImGuiID DockBuilderAddNode(ImGuiID node_id = 0, ImGuiDockNodeFlags flags = 0); - IMGUI_API void DockBuilderRemoveNode(ImGuiID node_id); // Remove node and all its child, undock all windows - IMGUI_API void DockBuilderRemoveNodeDockedWindows(ImGuiID node_id, bool clear_settings_refs = true); - IMGUI_API void DockBuilderRemoveNodeChildNodes(ImGuiID node_id); // Remove all split/hierarchy. All remaining docked windows will be re-docked to the remaining root node (node_id). - IMGUI_API void DockBuilderSetNodePos(ImGuiID node_id, ImVec2 pos); - IMGUI_API void DockBuilderSetNodeSize(ImGuiID node_id, ImVec2 size); - IMGUI_API ImGuiID DockBuilderSplitNode(ImGuiID node_id, ImGuiDir split_dir, float size_ratio_for_node_at_dir, ImGuiID* out_id_at_dir, ImGuiID* out_id_at_opposite_dir); // Create 2 child nodes in this parent node. - IMGUI_API void DockBuilderCopyDockSpace(ImGuiID src_dockspace_id, ImGuiID dst_dockspace_id, ImVector* in_window_remap_pairs); - IMGUI_API void DockBuilderCopyNode(ImGuiID src_node_id, ImGuiID dst_node_id, ImVector* out_node_remap_pairs); - IMGUI_API void DockBuilderCopyWindowSettings(const char* src_name, const char* dst_name); - IMGUI_API void DockBuilderFinish(ImGuiID node_id); - - // [EXPERIMENTAL] Focus Scope - // This is generally used to identify a unique input location (for e.g. a selection set) - // There is one per window (automatically set in Begin), but: - // - Selection patterns generally need to react (e.g. clear a selection) when landing on one item of the set. - // So in order to identify a set multiple lists in same window may each need a focus scope. - // If you imagine an hypothetical BeginSelectionGroup()/EndSelectionGroup() api, it would likely call PushFocusScope()/EndFocusScope() - // - Shortcut routing also use focus scope as a default location identifier if an owner is not provided. - // We don't use the ID Stack for this as it is common to want them separate. - IMGUI_API void PushFocusScope(ImGuiID id); - IMGUI_API void PopFocusScope(); - inline ImGuiID GetCurrentFocusScope() { ImGuiContext& g = *GImGui; return g.CurrentFocusScopeId; } // Focus scope we are outputting into, set by PushFocusScope() - - // Drag and Drop - IMGUI_API bool IsDragDropActive(); - IMGUI_API bool BeginDragDropTargetCustom(const ImRect& bb, ImGuiID id); - IMGUI_API void ClearDragDrop(); - IMGUI_API bool IsDragDropPayloadBeingAccepted(); - IMGUI_API void RenderDragDropTargetRect(const ImRect& bb); - - // Typing-Select API - IMGUI_API ImGuiTypingSelectRequest* GetTypingSelectRequest(ImGuiTypingSelectFlags flags = ImGuiTypingSelectFlags_None); - IMGUI_API int TypingSelectFindMatch(ImGuiTypingSelectRequest* req, int items_count, const char* (*get_item_name_func)(void*, int), void* user_data, int nav_item_idx); - IMGUI_API int TypingSelectFindNextSingleCharMatch(ImGuiTypingSelectRequest* req, int items_count, const char* (*get_item_name_func)(void*, int), void* user_data, int nav_item_idx); - IMGUI_API int TypingSelectFindBestLeadingMatch(ImGuiTypingSelectRequest* req, int items_count, const char* (*get_item_name_func)(void*, int), void* user_data); - - // Internal Columns API (this is not exposed because we will encourage transitioning to the Tables API) - IMGUI_API void SetWindowClipRectBeforeSetChannel(ImGuiWindow* window, const ImRect& clip_rect); - IMGUI_API void BeginColumns(const char* str_id, int count, ImGuiOldColumnFlags flags = 0); // setup number of columns. use an identifier to distinguish multiple column sets. close with EndColumns(). - IMGUI_API void EndColumns(); // close columns - IMGUI_API void PushColumnClipRect(int column_index); - IMGUI_API void PushColumnsBackground(); - IMGUI_API void PopColumnsBackground(); - IMGUI_API ImGuiID GetColumnsID(const char* str_id, int count); - IMGUI_API ImGuiOldColumns* FindOrCreateColumns(ImGuiWindow* window, ImGuiID id); - IMGUI_API float GetColumnOffsetFromNorm(const ImGuiOldColumns* columns, float offset_norm); - IMGUI_API float GetColumnNormFromOffset(const ImGuiOldColumns* columns, float offset); - - // Tables: Candidates for public API - IMGUI_API void TableOpenContextMenu(int column_n = -1); - IMGUI_API void TableSetColumnWidth(int column_n, float width); - IMGUI_API void TableSetColumnSortDirection(int column_n, ImGuiSortDirection sort_direction, bool append_to_sort_specs); - IMGUI_API int TableGetHoveredColumn(); // May use (TableGetColumnFlags() & ImGuiTableColumnFlags_IsHovered) instead. Return hovered column. return -1 when table is not hovered. return columns_count if the unused space at the right of visible columns is hovered. - IMGUI_API int TableGetHoveredRow(); // Retrieve *PREVIOUS FRAME* hovered row. This difference with TableGetHoveredColumn() is the reason why this is not public yet. - IMGUI_API float TableGetHeaderRowHeight(); - IMGUI_API float TableGetHeaderAngledMaxLabelWidth(); - IMGUI_API void TablePushBackgroundChannel(); - IMGUI_API void TablePopBackgroundChannel(); - IMGUI_API void TableAngledHeadersRowEx(float angle, float label_width = 0.0f); - - // Tables: Internals - inline ImGuiTable* GetCurrentTable() { ImGuiContext& g = *GImGui; return g.CurrentTable; } - IMGUI_API ImGuiTable* TableFindByID(ImGuiID id); - IMGUI_API bool BeginTableEx(const char* name, ImGuiID id, int columns_count, ImGuiTableFlags flags = 0, const ImVec2& outer_size = ImVec2(0, 0), float inner_width = 0.0f); - IMGUI_API void TableBeginInitMemory(ImGuiTable* table, int columns_count); - IMGUI_API void TableBeginApplyRequests(ImGuiTable* table); - IMGUI_API void TableSetupDrawChannels(ImGuiTable* table); - IMGUI_API void TableUpdateLayout(ImGuiTable* table); - IMGUI_API void TableUpdateBorders(ImGuiTable* table); - IMGUI_API void TableUpdateColumnsWeightFromWidth(ImGuiTable* table); - IMGUI_API void TableDrawBorders(ImGuiTable* table); - IMGUI_API void TableDrawContextMenu(ImGuiTable* table); - IMGUI_API bool TableBeginContextMenuPopup(ImGuiTable* table); - IMGUI_API void TableMergeDrawChannels(ImGuiTable* table); - inline ImGuiTableInstanceData* TableGetInstanceData(ImGuiTable* table, int instance_no) { if (instance_no == 0) return &table->InstanceDataFirst; return &table->InstanceDataExtra[instance_no - 1]; } - inline ImGuiID TableGetInstanceID(ImGuiTable* table, int instance_no) { return TableGetInstanceData(table, instance_no)->TableInstanceID; } - IMGUI_API void TableSortSpecsSanitize(ImGuiTable* table); - IMGUI_API void TableSortSpecsBuild(ImGuiTable* table); - IMGUI_API ImGuiSortDirection TableGetColumnNextSortDirection(ImGuiTableColumn* column); - IMGUI_API void TableFixColumnSortDirection(ImGuiTable* table, ImGuiTableColumn* column); - IMGUI_API float TableGetColumnWidthAuto(ImGuiTable* table, ImGuiTableColumn* column); - IMGUI_API void TableBeginRow(ImGuiTable* table); - IMGUI_API void TableEndRow(ImGuiTable* table); - IMGUI_API void TableBeginCell(ImGuiTable* table, int column_n); - IMGUI_API void TableEndCell(ImGuiTable* table); - IMGUI_API ImRect TableGetCellBgRect(const ImGuiTable* table, int column_n); - IMGUI_API const char* TableGetColumnName(const ImGuiTable* table, int column_n); - IMGUI_API ImGuiID TableGetColumnResizeID(ImGuiTable* table, int column_n, int instance_no = 0); - IMGUI_API float TableGetMaxColumnWidth(const ImGuiTable* table, int column_n); - IMGUI_API void TableSetColumnWidthAutoSingle(ImGuiTable* table, int column_n); - IMGUI_API void TableSetColumnWidthAutoAll(ImGuiTable* table); - IMGUI_API void TableRemove(ImGuiTable* table); - IMGUI_API void TableGcCompactTransientBuffers(ImGuiTable* table); - IMGUI_API void TableGcCompactTransientBuffers(ImGuiTableTempData* table); - IMGUI_API void TableGcCompactSettings(); - - // Tables: Settings - IMGUI_API void TableLoadSettings(ImGuiTable* table); - IMGUI_API void TableSaveSettings(ImGuiTable* table); - IMGUI_API void TableResetSettings(ImGuiTable* table); - IMGUI_API ImGuiTableSettings* TableGetBoundSettings(ImGuiTable* table); - IMGUI_API void TableSettingsAddSettingsHandler(); - IMGUI_API ImGuiTableSettings* TableSettingsCreate(ImGuiID id, int columns_count); - IMGUI_API ImGuiTableSettings* TableSettingsFindByID(ImGuiID id); - - // Tab Bars - inline ImGuiTabBar* GetCurrentTabBar() { ImGuiContext& g = *GImGui; return g.CurrentTabBar; } - IMGUI_API bool BeginTabBarEx(ImGuiTabBar* tab_bar, const ImRect& bb, ImGuiTabBarFlags flags); - IMGUI_API ImGuiTabItem* TabBarFindTabByID(ImGuiTabBar* tab_bar, ImGuiID tab_id); - IMGUI_API ImGuiTabItem* TabBarFindTabByOrder(ImGuiTabBar* tab_bar, int order); - IMGUI_API ImGuiTabItem* TabBarFindMostRecentlySelectedTabForActiveWindow(ImGuiTabBar* tab_bar); - IMGUI_API ImGuiTabItem* TabBarGetCurrentTab(ImGuiTabBar* tab_bar); - inline int TabBarGetTabOrder(ImGuiTabBar* tab_bar, ImGuiTabItem* tab) { return tab_bar->Tabs.index_from_ptr(tab); } - IMGUI_API const char* TabBarGetTabName(ImGuiTabBar* tab_bar, ImGuiTabItem* tab); - IMGUI_API void TabBarAddTab(ImGuiTabBar* tab_bar, ImGuiTabItemFlags tab_flags, ImGuiWindow* window); - IMGUI_API void TabBarRemoveTab(ImGuiTabBar* tab_bar, ImGuiID tab_id); - IMGUI_API void TabBarCloseTab(ImGuiTabBar* tab_bar, ImGuiTabItem* tab); - IMGUI_API void TabBarQueueFocus(ImGuiTabBar* tab_bar, ImGuiTabItem* tab); - IMGUI_API void TabBarQueueReorder(ImGuiTabBar* tab_bar, ImGuiTabItem* tab, int offset); - IMGUI_API void TabBarQueueReorderFromMousePos(ImGuiTabBar* tab_bar, ImGuiTabItem* tab, ImVec2 mouse_pos); - IMGUI_API bool TabBarProcessReorder(ImGuiTabBar* tab_bar); - IMGUI_API bool TabItemEx(ImGuiTabBar* tab_bar, const char* label, bool* p_open, ImGuiTabItemFlags flags, ImGuiWindow* docked_window); - IMGUI_API ImVec2 TabItemCalcSize(const char* label, bool has_close_button_or_unsaved_marker); - IMGUI_API ImVec2 TabItemCalcSize(ImGuiWindow* window); - IMGUI_API void TabItemBackground(ImDrawList* draw_list, const ImRect& bb, ImGuiTabItemFlags flags, ImU32 col); - IMGUI_API void TabItemLabelAndCloseButton(ImDrawList* draw_list, const ImRect& bb, ImGuiTabItemFlags flags, ImVec2 frame_padding, const char* label, ImGuiID tab_id, ImGuiID close_button_id, bool is_contents_visible, bool* out_just_closed, bool* out_text_clipped); - - // Render helpers - // AVOID USING OUTSIDE OF IMGUI.CPP! NOT FOR PUBLIC CONSUMPTION. THOSE FUNCTIONS ARE A MESS. THEIR SIGNATURE AND BEHAVIOR WILL CHANGE, THEY NEED TO BE REFACTORED INTO SOMETHING DECENT. - // NB: All position are in absolute pixels coordinates (we are never using window coordinates internally) - IMGUI_API void RenderText(ImVec2 pos, const char* text, const char* text_end = NULL, bool hide_text_after_hash = true); - IMGUI_API void RenderTextWrapped(ImVec2 pos, const char* text, const char* text_end, float wrap_width); - IMGUI_API void RenderTextClipped(const ImVec2& pos_min, const ImVec2& pos_max, const char* text, const char* text_end, const ImVec2* text_size_if_known, const ImVec2& align = ImVec2(0, 0), const ImRect* clip_rect = NULL); - IMGUI_API void RenderTextClippedEx(ImDrawList* draw_list, const ImVec2& pos_min, const ImVec2& pos_max, const char* text, const char* text_end, const ImVec2* text_size_if_known, const ImVec2& align = ImVec2(0, 0), const ImRect* clip_rect = NULL); - IMGUI_API void RenderTextEllipsis(ImDrawList* draw_list, const ImVec2& pos_min, const ImVec2& pos_max, float clip_max_x, float ellipsis_max_x, const char* text, const char* text_end, const ImVec2* text_size_if_known); - IMGUI_API void RenderFrame(ImVec2 p_min, ImVec2 p_max, ImU32 fill_col, bool border = true, float rounding = 0.0f); - IMGUI_API void RenderFrameBorder(ImVec2 p_min, ImVec2 p_max, float rounding = 0.0f); - IMGUI_API void RenderColorRectWithAlphaCheckerboard(ImDrawList* draw_list, ImVec2 p_min, ImVec2 p_max, ImU32 fill_col, float grid_step, ImVec2 grid_off, float rounding = 0.0f, ImDrawFlags flags = 0); - IMGUI_API void RenderNavHighlight(const ImRect& bb, ImGuiID id, ImGuiNavHighlightFlags flags = ImGuiNavHighlightFlags_TypeDefault); // Navigation highlight - IMGUI_API const char* FindRenderedTextEnd(const char* text, const char* text_end = NULL); // Find the optional ## from which we stop displaying text. - IMGUI_API void RenderMouseCursor(ImVec2 pos, float scale, ImGuiMouseCursor mouse_cursor, ImU32 col_fill, ImU32 col_border, ImU32 col_shadow); - - // Render helpers (those functions don't access any ImGui state!) - IMGUI_API void RenderArrow(ImDrawList* draw_list, ImVec2 pos, ImU32 col, ImGuiDir dir, float scale = 1.0f); - IMGUI_API void RenderBullet(ImDrawList* draw_list, ImVec2 pos, ImU32 col); - IMGUI_API void RenderCheckMark(ImDrawList* draw_list, ImVec2 pos, ImU32 col, float sz); - IMGUI_API void RenderArrowPointingAt(ImDrawList* draw_list, ImVec2 pos, ImVec2 half_sz, ImGuiDir direction, ImU32 col); - IMGUI_API void RenderArrowDockMenu(ImDrawList* draw_list, ImVec2 p_min, float sz, ImU32 col); - IMGUI_API void RenderRectFilledRangeH(ImDrawList* draw_list, const ImRect& rect, ImU32 col, float x_start_norm, float x_end_norm, float rounding); - IMGUI_API void RenderRectFilledWithHole(ImDrawList* draw_list, const ImRect& outer, const ImRect& inner, ImU32 col, float rounding); - IMGUI_API ImDrawFlags CalcRoundingFlagsForRectInRect(const ImRect& r_in, const ImRect& r_outer, float threshold); - - // Widgets - IMGUI_API void TextEx(const char* text, const char* text_end = NULL, ImGuiTextFlags flags = 0); - IMGUI_API bool ButtonEx(const char* label, const ImVec2& size_arg = ImVec2(0, 0), ImGuiButtonFlags flags = 0); - IMGUI_API bool ArrowButtonEx(const char* str_id, ImGuiDir dir, ImVec2 size_arg, ImGuiButtonFlags flags = 0); - IMGUI_API bool ImageButtonEx(ImGuiID id, ImTextureID texture_id, const ImVec2& image_size, const ImVec2& uv0, const ImVec2& uv1, const ImVec4& bg_col, const ImVec4& tint_col, ImGuiButtonFlags flags = 0); - IMGUI_API void SeparatorEx(ImGuiSeparatorFlags flags, float thickness = 1.0f); - IMGUI_API void SeparatorTextEx(ImGuiID id, const char* label, const char* label_end, float extra_width); - IMGUI_API bool CheckboxFlags(const char* label, ImS64* flags, ImS64 flags_value); - IMGUI_API bool CheckboxFlags(const char* label, ImU64* flags, ImU64 flags_value); - - // Widgets: Window Decorations - IMGUI_API bool CloseButton(ImGuiID id, const ImVec2& pos); - IMGUI_API bool CollapseButton(ImGuiID id, const ImVec2& pos, ImGuiDockNode* dock_node); - IMGUI_API void Scrollbar(ImGuiAxis axis); - IMGUI_API bool ScrollbarEx(const ImRect& bb, ImGuiID id, ImGuiAxis axis, ImS64* p_scroll_v, ImS64 avail_v, ImS64 contents_v, ImDrawFlags flags); - IMGUI_API ImRect GetWindowScrollbarRect(ImGuiWindow* window, ImGuiAxis axis); - IMGUI_API ImGuiID GetWindowScrollbarID(ImGuiWindow* window, ImGuiAxis axis); - IMGUI_API ImGuiID GetWindowResizeCornerID(ImGuiWindow* window, int n); // 0..3: corners - IMGUI_API ImGuiID GetWindowResizeBorderID(ImGuiWindow* window, ImGuiDir dir); - - // Widgets low-level behaviors - IMGUI_API bool ButtonBehavior(const ImRect& bb, ImGuiID id, bool* out_hovered, bool* out_held, ImGuiButtonFlags flags = 0); - IMGUI_API bool DragBehavior(ImGuiID id, ImGuiDataType data_type, void* p_v, float v_speed, const void* p_min, const void* p_max, const char* format, ImGuiSliderFlags flags); - IMGUI_API bool SliderBehavior(const ImRect& bb, ImGuiID id, ImGuiDataType data_type, void* p_v, const void* p_min, const void* p_max, const char* format, ImGuiSliderFlags flags, ImRect* out_grab_bb); - IMGUI_API bool SplitterBehavior(const ImRect& bb, ImGuiID id, ImGuiAxis axis, float* size1, float* size2, float min_size1, float min_size2, float hover_extend = 0.0f, float hover_visibility_delay = 0.0f, ImU32 bg_col = 0); - IMGUI_API bool TreeNodeBehavior(ImGuiID id, ImGuiTreeNodeFlags flags, const char* label, const char* label_end = NULL); - IMGUI_API void TreePushOverrideID(ImGuiID id); - IMGUI_API void TreeNodeSetOpen(ImGuiID id, bool open); - IMGUI_API bool TreeNodeUpdateNextOpen(ImGuiID id, ImGuiTreeNodeFlags flags); // Return open state. Consume previous SetNextItemOpen() data, if any. May return true when logging. - IMGUI_API void SetNextItemSelectionUserData(ImGuiSelectionUserData selection_user_data); - - // Template functions are instantiated in imgui_widgets.cpp for a finite number of types. - // To use them externally (for custom widget) you may need an "extern template" statement in your code in order to link to existing instances and silence Clang warnings (see #2036). - // e.g. " extern template IMGUI_API float RoundScalarWithFormatT(const char* format, ImGuiDataType data_type, float v); " - template IMGUI_API float ScaleRatioFromValueT(ImGuiDataType data_type, T v, T v_min, T v_max, bool is_logarithmic, float logarithmic_zero_epsilon, float zero_deadzone_size); - template IMGUI_API T ScaleValueFromRatioT(ImGuiDataType data_type, float t, T v_min, T v_max, bool is_logarithmic, float logarithmic_zero_epsilon, float zero_deadzone_size); - template IMGUI_API bool DragBehaviorT(ImGuiDataType data_type, T* v, float v_speed, T v_min, T v_max, const char* format, ImGuiSliderFlags flags); - template IMGUI_API bool SliderBehaviorT(const ImRect& bb, ImGuiID id, ImGuiDataType data_type, T* v, T v_min, T v_max, const char* format, ImGuiSliderFlags flags, ImRect* out_grab_bb); - template IMGUI_API T RoundScalarWithFormatT(const char* format, ImGuiDataType data_type, T v); - template IMGUI_API bool CheckboxFlagsT(const char* label, T* flags, T flags_value); - - // Data type helpers - IMGUI_API const ImGuiDataTypeInfo* DataTypeGetInfo(ImGuiDataType data_type); - IMGUI_API int DataTypeFormatString(char* buf, int buf_size, ImGuiDataType data_type, const void* p_data, const char* format); - IMGUI_API void DataTypeApplyOp(ImGuiDataType data_type, int op, void* output, const void* arg_1, const void* arg_2); - IMGUI_API bool DataTypeApplyFromText(const char* buf, ImGuiDataType data_type, void* p_data, const char* format); - IMGUI_API int DataTypeCompare(ImGuiDataType data_type, const void* arg_1, const void* arg_2); - IMGUI_API bool DataTypeClamp(ImGuiDataType data_type, void* p_data, const void* p_min, const void* p_max); - - // InputText - IMGUI_API bool InputTextEx(const char* label, const char* hint, char* buf, int buf_size, const ImVec2& size_arg, ImGuiInputTextFlags flags, ImGuiInputTextCallback callback = NULL, void* user_data = NULL); - IMGUI_API void InputTextDeactivateHook(ImGuiID id); - IMGUI_API bool TempInputText(const ImRect& bb, ImGuiID id, const char* label, char* buf, int buf_size, ImGuiInputTextFlags flags); - IMGUI_API bool TempInputScalar(const ImRect& bb, ImGuiID id, const char* label, ImGuiDataType data_type, void* p_data, const char* format, const void* p_clamp_min = NULL, const void* p_clamp_max = NULL); - inline bool TempInputIsActive(ImGuiID id) { ImGuiContext& g = *GImGui; return (g.ActiveId == id && g.TempInputId == id); } - inline ImGuiInputTextState* GetInputTextState(ImGuiID id) { ImGuiContext& g = *GImGui; return (id != 0 && g.InputTextState.ID == id) ? &g.InputTextState : NULL; } // Get input text state if active - - // Color - IMGUI_API void ColorTooltip(const char* text, const float* col, ImGuiColorEditFlags flags); - IMGUI_API void ColorEditOptionsPopup(const float* col, ImGuiColorEditFlags flags); - IMGUI_API void ColorPickerOptionsPopup(const float* ref_col, ImGuiColorEditFlags flags); - - // Plot - IMGUI_API int PlotEx(ImGuiPlotType plot_type, const char* label, float (*values_getter)(void* data, int idx), void* data, int values_count, int values_offset, const char* overlay_text, float scale_min, float scale_max, const ImVec2& size_arg); - - // Shade functions (write over already created vertices) - IMGUI_API void ShadeVertsLinearColorGradientKeepAlpha(ImDrawList* draw_list, int vert_start_idx, int vert_end_idx, ImVec2 gradient_p0, ImVec2 gradient_p1, ImU32 col0, ImU32 col1); - IMGUI_API void ShadeVertsLinearUV(ImDrawList* draw_list, int vert_start_idx, int vert_end_idx, const ImVec2& a, const ImVec2& b, const ImVec2& uv_a, const ImVec2& uv_b, bool clamp); - IMGUI_API void ShadeVertsTransformPos(ImDrawList* draw_list, int vert_start_idx, int vert_end_idx, const ImVec2& pivot_in, float cos_a, float sin_a, const ImVec2& pivot_out); - - // Garbage collection - IMGUI_API void GcCompactTransientMiscBuffers(); - IMGUI_API void GcCompactTransientWindowBuffers(ImGuiWindow* window); - IMGUI_API void GcAwakeTransientWindowBuffers(ImGuiWindow* window); - - // Debug Log - IMGUI_API void DebugLog(const char* fmt, ...) IM_FMTARGS(1); - IMGUI_API void DebugLogV(const char* fmt, va_list args) IM_FMTLIST(1); - IMGUI_API void DebugAllocHook(ImGuiDebugAllocInfo* info, int frame_count, void* ptr, size_t size); // size >= 0 : alloc, size = -1 : free - - // Debug Tools - IMGUI_API void ErrorCheckEndFrameRecover(ImGuiErrorLogCallback log_callback, void* user_data = NULL); - IMGUI_API void ErrorCheckEndWindowRecover(ImGuiErrorLogCallback log_callback, void* user_data = NULL); - IMGUI_API void ErrorCheckUsingSetCursorPosToExtendParentBoundaries(); - IMGUI_API void DebugDrawCursorPos(ImU32 col = IM_COL32(255, 0, 0, 255)); - IMGUI_API void DebugDrawLineExtents(ImU32 col = IM_COL32(255, 0, 0, 255)); - IMGUI_API void DebugDrawItemRect(ImU32 col = IM_COL32(255, 0, 0, 255)); - IMGUI_API void DebugLocateItem(ImGuiID target_id); // Call sparingly: only 1 at the same time! - IMGUI_API void DebugLocateItemOnHover(ImGuiID target_id); // Only call on reaction to a mouse Hover: because only 1 at the same time! - IMGUI_API void DebugLocateItemResolveWithLastItem(); - inline void DebugStartItemPicker() { ImGuiContext& g = *GImGui; g.DebugItemPickerActive = true; } - IMGUI_API void ShowFontAtlas(ImFontAtlas* atlas); - IMGUI_API void DebugHookIdInfo(ImGuiID id, ImGuiDataType data_type, const void* data_id, const void* data_id_end); - IMGUI_API void DebugNodeColumns(ImGuiOldColumns* columns); - IMGUI_API void DebugNodeDockNode(ImGuiDockNode* node, const char* label); - IMGUI_API void DebugNodeDrawList(ImGuiWindow* window, ImGuiViewportP* viewport, const ImDrawList* draw_list, const char* label); - IMGUI_API void DebugNodeDrawCmdShowMeshAndBoundingBox(ImDrawList* out_draw_list, const ImDrawList* draw_list, const ImDrawCmd* draw_cmd, bool show_mesh, bool show_aabb); - IMGUI_API void DebugNodeFont(ImFont* font); - IMGUI_API void DebugNodeFontGlyph(ImFont* font, const ImFontGlyph* glyph); - IMGUI_API void DebugNodeStorage(ImGuiStorage* storage, const char* label); - IMGUI_API void DebugNodeTabBar(ImGuiTabBar* tab_bar, const char* label); - IMGUI_API void DebugNodeTable(ImGuiTable* table); - IMGUI_API void DebugNodeTableSettings(ImGuiTableSettings* settings); - IMGUI_API void DebugNodeInputTextState(ImGuiInputTextState* state); - IMGUI_API void DebugNodeTypingSelectState(ImGuiTypingSelectState* state); - IMGUI_API void DebugNodeWindow(ImGuiWindow* window, const char* label); - IMGUI_API void DebugNodeWindowSettings(ImGuiWindowSettings* settings); - IMGUI_API void DebugNodeWindowsList(ImVector* windows, const char* label); - IMGUI_API void DebugNodeWindowsListByBeginStackParent(ImGuiWindow** windows, int windows_size, ImGuiWindow* parent_in_begin_stack); - IMGUI_API void DebugNodeViewport(ImGuiViewportP* viewport); - IMGUI_API void DebugRenderKeyboardPreview(ImDrawList* draw_list); - IMGUI_API void DebugRenderViewportThumbnail(ImDrawList* draw_list, ImGuiViewportP* viewport, const ImRect& bb); - - // Obsolete functions -#ifndef IMGUI_DISABLE_OBSOLETE_FUNCTIONS - inline void SetItemUsingMouseWheel() { SetItemKeyOwner(ImGuiKey_MouseWheelY); } // Changed in 1.89 - inline bool TreeNodeBehaviorIsOpen(ImGuiID id, ImGuiTreeNodeFlags flags = 0) { return TreeNodeUpdateNextOpen(id, flags); } // Renamed in 1.89 - - // Refactored focus/nav/tabbing system in 1.82 and 1.84. If you have old/custom copy-and-pasted widgets that used FocusableItemRegister(): - // (Old) IMGUI_VERSION_NUM < 18209: using 'ItemAdd(....)' and 'bool tab_focused = FocusableItemRegister(...)' - // (Old) IMGUI_VERSION_NUM >= 18209: using 'ItemAdd(..., ImGuiItemAddFlags_Focusable)' and 'bool tab_focused = (GetItemStatusFlags() & ImGuiItemStatusFlags_Focused) != 0' - // (New) IMGUI_VERSION_NUM >= 18413: using 'ItemAdd(..., ImGuiItemFlags_Inputable)' and 'bool tab_focused = (GetItemStatusFlags() & ImGuiItemStatusFlags_FocusedTabbing) != 0 || (g.NavActivateId == id && (g.NavActivateFlags & ImGuiActivateFlags_PreferInput))' (WIP) - // Widget code are simplified as there's no need to call FocusableItemUnregister() while managing the transition from regular widget to TempInputText() - inline bool FocusableItemRegister(ImGuiWindow* window, ImGuiID id) { IM_ASSERT(0); IM_UNUSED(window); IM_UNUSED(id); return false; } // -> pass ImGuiItemAddFlags_Inputable flag to ItemAdd() - inline void FocusableItemUnregister(ImGuiWindow* window) { IM_ASSERT(0); IM_UNUSED(window); } // -> unnecessary: TempInputText() uses ImGuiInputTextFlags_MergedItem -#endif -#ifndef IMGUI_DISABLE_OBSOLETE_KEYIO - inline bool IsKeyPressedMap(ImGuiKey key, bool repeat = true) { IM_ASSERT(IsNamedKey(key)); return IsKeyPressed(key, repeat); } // Removed in 1.87: Mapping from named key is always identity! -#endif - -} // namespace ImGui - - -//----------------------------------------------------------------------------- -// [SECTION] ImFontAtlas internal API -//----------------------------------------------------------------------------- - -// This structure is likely to evolve as we add support for incremental atlas updates -struct ImFontBuilderIO -{ - bool (*FontBuilder_Build)(ImFontAtlas* atlas); -}; - -// Helper for font builder -#ifdef IMGUI_ENABLE_STB_TRUETYPE -IMGUI_API const ImFontBuilderIO* ImFontAtlasGetBuilderForStbTruetype(); -#endif -IMGUI_API void ImFontAtlasUpdateConfigDataPointers(ImFontAtlas* atlas); -IMGUI_API void ImFontAtlasBuildInit(ImFontAtlas* atlas); -IMGUI_API void ImFontAtlasBuildSetupFont(ImFontAtlas* atlas, ImFont* font, ImFontConfig* font_config, float ascent, float descent); -IMGUI_API void ImFontAtlasBuildPackCustomRects(ImFontAtlas* atlas, void* stbrp_context_opaque); -IMGUI_API void ImFontAtlasBuildFinish(ImFontAtlas* atlas); -IMGUI_API void ImFontAtlasBuildRender8bppRectFromString(ImFontAtlas* atlas, int x, int y, int w, int h, const char* in_str, char in_marker_char, unsigned char in_marker_pixel_value); -IMGUI_API void ImFontAtlasBuildRender32bppRectFromString(ImFontAtlas* atlas, int x, int y, int w, int h, const char* in_str, char in_marker_char, unsigned int in_marker_pixel_value); -IMGUI_API void ImFontAtlasBuildMultiplyCalcLookupTable(unsigned char out_table[256], float in_multiply_factor); -IMGUI_API void ImFontAtlasBuildMultiplyRectAlpha8(const unsigned char table[256], unsigned char* pixels, int x, int y, int w, int h, int stride); - -//----------------------------------------------------------------------------- -// [SECTION] Test Engine specific hooks (imgui_test_engine) -//----------------------------------------------------------------------------- - -#ifdef IMGUI_ENABLE_TEST_ENGINE -extern void ImGuiTestEngineHook_ItemAdd(ImGuiContext* ctx, ImGuiID id, const ImRect& bb, const ImGuiLastItemData* item_data); // item_data may be NULL -extern void ImGuiTestEngineHook_ItemInfo(ImGuiContext* ctx, ImGuiID id, const char* label, ImGuiItemStatusFlags flags); -extern void ImGuiTestEngineHook_Log(ImGuiContext* ctx, const char* fmt, ...); -extern const char* ImGuiTestEngine_FindItemDebugLabel(ImGuiContext* ctx, ImGuiID id); - -// In IMGUI_VERSION_NUM >= 18934: changed IMGUI_TEST_ENGINE_ITEM_ADD(bb,id) to IMGUI_TEST_ENGINE_ITEM_ADD(id,bb,item_data); -#define IMGUI_TEST_ENGINE_ITEM_ADD(_ID,_BB,_ITEM_DATA) if (g.TestEngineHookItems) ImGuiTestEngineHook_ItemAdd(&g, _ID, _BB, _ITEM_DATA) // Register item bounding box -#define IMGUI_TEST_ENGINE_ITEM_INFO(_ID,_LABEL,_FLAGS) if (g.TestEngineHookItems) ImGuiTestEngineHook_ItemInfo(&g, _ID, _LABEL, _FLAGS) // Register item label and status flags (optional) -#define IMGUI_TEST_ENGINE_LOG(_FMT,...) if (g.TestEngineHookItems) ImGuiTestEngineHook_Log(&g, _FMT, __VA_ARGS__) // Custom log entry from user land into test log -#else -#define IMGUI_TEST_ENGINE_ITEM_ADD(_BB,_ID) ((void)0) -#define IMGUI_TEST_ENGINE_ITEM_INFO(_ID,_LABEL,_FLAGS) ((void)g) -#endif - -//----------------------------------------------------------------------------- - -#if defined(__clang__) -#pragma clang diagnostic pop -#elif defined(__GNUC__) -#pragma GCC diagnostic pop -#endif - -#ifdef _MSC_VER -#pragma warning (pop) -#endif - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/imgui_tables.cpp b/app/jni/src/libultraship/extern/ImGui/imgui_tables.cpp deleted file mode 100644 index e028376..0000000 --- a/app/jni/src/libultraship/extern/ImGui/imgui_tables.cpp +++ /dev/null @@ -1,4314 +0,0 @@ -// dear imgui, v1.90 WIP -// (tables and columns code) - -/* - -Index of this file: - -// [SECTION] Commentary -// [SECTION] Header mess -// [SECTION] Tables: Main code -// [SECTION] Tables: Simple accessors -// [SECTION] Tables: Row changes -// [SECTION] Tables: Columns changes -// [SECTION] Tables: Columns width management -// [SECTION] Tables: Drawing -// [SECTION] Tables: Sorting -// [SECTION] Tables: Headers -// [SECTION] Tables: Context Menu -// [SECTION] Tables: Settings (.ini data) -// [SECTION] Tables: Garbage Collection -// [SECTION] Tables: Debugging -// [SECTION] Columns, BeginColumns, EndColumns, etc. - -*/ - -// Navigating this file: -// - In Visual Studio IDE: CTRL+comma ("Edit.GoToAll") can follow symbols in comments, whereas CTRL+F12 ("Edit.GoToImplementation") cannot. -// - With Visual Assist installed: ALT+G ("VAssistX.GoToImplementation") can also follow symbols in comments. - -//----------------------------------------------------------------------------- -// [SECTION] Commentary -//----------------------------------------------------------------------------- - -//----------------------------------------------------------------------------- -// Typical tables call flow: (root level is generally public API): -//----------------------------------------------------------------------------- -// - BeginTable() user begin into a table -// | BeginChild() - (if ScrollX/ScrollY is set) -// | TableBeginInitMemory() - first time table is used -// | TableResetSettings() - on settings reset -// | TableLoadSettings() - on settings load -// | TableBeginApplyRequests() - apply queued resizing/reordering/hiding requests -// | - TableSetColumnWidth() - apply resizing width (for mouse resize, often requested by previous frame) -// | - TableUpdateColumnsWeightFromWidth()- recompute columns weights (of stretch columns) from their respective width -// - TableSetupColumn() user submit columns details (optional) -// - TableSetupScrollFreeze() user submit scroll freeze information (optional) -//----------------------------------------------------------------------------- -// - TableUpdateLayout() [Internal] followup to BeginTable(): setup everything: widths, columns positions, clipping rectangles. Automatically called by the FIRST call to TableNextRow() or TableHeadersRow(). -// | TableSetupDrawChannels() - setup ImDrawList channels -// | TableUpdateBorders() - detect hovering columns for resize, ahead of contents submission -// | TableDrawContextMenu() - draw right-click context menu -//----------------------------------------------------------------------------- -// - TableHeadersRow() or TableHeader() user submit a headers row (optional) -// | TableSortSpecsClickColumn() - when left-clicked: alter sort order and sort direction -// | TableOpenContextMenu() - when right-clicked: trigger opening of the default context menu -// - TableGetSortSpecs() user queries updated sort specs (optional, generally after submitting headers) -// - TableNextRow() user begin into a new row (also automatically called by TableHeadersRow()) -// | TableEndRow() - finish existing row -// | TableBeginRow() - add a new row -// - TableSetColumnIndex() / TableNextColumn() user begin into a cell -// | TableEndCell() - close existing column/cell -// | TableBeginCell() - enter into current column/cell -// - [...] user emit contents -//----------------------------------------------------------------------------- -// - EndTable() user ends the table -// | TableDrawBorders() - draw outer borders, inner vertical borders -// | TableMergeDrawChannels() - merge draw channels if clipping isn't required -// | EndChild() - (if ScrollX/ScrollY is set) -//----------------------------------------------------------------------------- - -//----------------------------------------------------------------------------- -// TABLE SIZING -//----------------------------------------------------------------------------- -// (Read carefully because this is subtle but it does make sense!) -//----------------------------------------------------------------------------- -// About 'outer_size': -// Its meaning needs to differ slightly depending on if we are using ScrollX/ScrollY flags. -// Default value is ImVec2(0.0f, 0.0f). -// X -// - outer_size.x <= 0.0f -> Right-align from window/work-rect right-most edge. With -FLT_MIN or 0.0f will align exactly on right-most edge. -// - outer_size.x > 0.0f -> Set Fixed width. -// Y with ScrollX/ScrollY disabled: we output table directly in current window -// - outer_size.y < 0.0f -> Bottom-align (but will auto extend, unless _NoHostExtendY is set). Not meaningful if parent window can vertically scroll. -// - outer_size.y = 0.0f -> No minimum height (but will auto extend, unless _NoHostExtendY is set) -// - outer_size.y > 0.0f -> Set Minimum height (but will auto extend, unless _NoHostExtendY is set) -// Y with ScrollX/ScrollY enabled: using a child window for scrolling -// - outer_size.y < 0.0f -> Bottom-align. Not meaningful if parent window can vertically scroll. -// - outer_size.y = 0.0f -> Bottom-align, consistent with BeginChild(). Not recommended unless table is last item in parent window. -// - outer_size.y > 0.0f -> Set Exact height. Recommended when using Scrolling on any axis. -//----------------------------------------------------------------------------- -// Outer size is also affected by the NoHostExtendX/NoHostExtendY flags. -// Important to note how the two flags have slightly different behaviors! -// - ImGuiTableFlags_NoHostExtendX -> Make outer width auto-fit to columns (overriding outer_size.x value). Only available when ScrollX/ScrollY are disabled and Stretch columns are not used. -// - ImGuiTableFlags_NoHostExtendY -> Make outer height stop exactly at outer_size.y (prevent auto-extending table past the limit). Only available when ScrollX/ScrollY is disabled. Data below the limit will be clipped and not visible. -// In theory ImGuiTableFlags_NoHostExtendY could be the default and any non-scrolling tables with outer_size.y != 0.0f would use exact height. -// This would be consistent but perhaps less useful and more confusing (as vertically clipped items are not useful and not easily noticeable). -//----------------------------------------------------------------------------- -// About 'inner_width': -// With ScrollX disabled: -// - inner_width -> *ignored* -// With ScrollX enabled: -// - inner_width < 0.0f -> *illegal* fit in known width (right align from outer_size.x) <-- weird -// - inner_width = 0.0f -> fit in outer_width: Fixed size columns will take space they need (if avail, otherwise shrink down), Stretch columns becomes Fixed columns. -// - inner_width > 0.0f -> override scrolling width, generally to be larger than outer_size.x. Fixed column take space they need (if avail, otherwise shrink down), Stretch columns share remaining space! -//----------------------------------------------------------------------------- -// Details: -// - If you want to use Stretch columns with ScrollX, you generally need to specify 'inner_width' otherwise the concept -// of "available space" doesn't make sense. -// - Even if not really useful, we allow 'inner_width < outer_size.x' for consistency and to facilitate understanding -// of what the value does. -//----------------------------------------------------------------------------- - -//----------------------------------------------------------------------------- -// COLUMNS SIZING POLICIES -// (Reference: ImGuiTableFlags_SizingXXX flags and ImGuiTableColumnFlags_WidthXXX flags) -//----------------------------------------------------------------------------- -// About overriding column sizing policy and width/weight with TableSetupColumn(): -// We use a default parameter of -1 for 'init_width'/'init_weight'. -// - with ImGuiTableColumnFlags_WidthFixed, init_width <= 0 (default) --> width is automatic -// - with ImGuiTableColumnFlags_WidthFixed, init_width > 0 (explicit) --> width is custom -// - with ImGuiTableColumnFlags_WidthStretch, init_weight <= 0 (default) --> weight is 1.0f -// - with ImGuiTableColumnFlags_WidthStretch, init_weight > 0 (explicit) --> weight is custom -// Widths are specified _without_ CellPadding. If you specify a width of 100.0f, the column will be cover (100.0f + Padding * 2.0f) -// and you can fit a 100.0f wide item in it without clipping and with padding honored. -//----------------------------------------------------------------------------- -// About default sizing policy (if you don't specify a ImGuiTableColumnFlags_WidthXXXX flag) -// - with Table policy ImGuiTableFlags_SizingFixedFit --> default Column policy is ImGuiTableColumnFlags_WidthFixed, default Width is equal to contents width -// - with Table policy ImGuiTableFlags_SizingFixedSame --> default Column policy is ImGuiTableColumnFlags_WidthFixed, default Width is max of all contents width -// - with Table policy ImGuiTableFlags_SizingStretchSame --> default Column policy is ImGuiTableColumnFlags_WidthStretch, default Weight is 1.0f -// - with Table policy ImGuiTableFlags_SizingStretchWeight --> default Column policy is ImGuiTableColumnFlags_WidthStretch, default Weight is proportional to contents -// Default Width and default Weight can be overridden when calling TableSetupColumn(). -//----------------------------------------------------------------------------- -// About mixing Fixed/Auto and Stretch columns together: -// - the typical use of mixing sizing policies is: any number of LEADING Fixed columns, followed by one or two TRAILING Stretch columns. -// - using mixed policies with ScrollX does not make much sense, as using Stretch columns with ScrollX does not make much sense in the first place! -// that is, unless 'inner_width' is passed to BeginTable() to explicitly provide a total width to layout columns in. -// - when using ImGuiTableFlags_SizingFixedSame with mixed columns, only the Fixed/Auto columns will match their widths to the width of the maximum contents. -// - when using ImGuiTableFlags_SizingStretchSame with mixed columns, only the Stretch columns will match their weights/widths. -//----------------------------------------------------------------------------- -// About using column width: -// If a column is manually resizable or has a width specified with TableSetupColumn(): -// - you may use GetContentRegionAvail().x to query the width available in a given column. -// - right-side alignment features such as SetNextItemWidth(-x) or PushItemWidth(-x) will rely on this width. -// If the column is not resizable and has no width specified with TableSetupColumn(): -// - its width will be automatic and be set to the max of items submitted. -// - therefore you generally cannot have ALL items of the columns use e.g. SetNextItemWidth(-FLT_MIN). -// - but if the column has one or more items of known/fixed size, this will become the reference width used by SetNextItemWidth(-FLT_MIN). -//----------------------------------------------------------------------------- - - -//----------------------------------------------------------------------------- -// TABLES CLIPPING/CULLING -//----------------------------------------------------------------------------- -// About clipping/culling of Rows in Tables: -// - For large numbers of rows, it is recommended you use ImGuiListClipper to submit only visible rows. -// ImGuiListClipper is reliant on the fact that rows are of equal height. -// See 'Demo->Tables->Vertical Scrolling' or 'Demo->Tables->Advanced' for a demo of using the clipper. -// - Note that auto-resizing columns don't play well with using the clipper. -// By default a table with _ScrollX but without _Resizable will have column auto-resize. -// So, if you want to use the clipper, make sure to either enable _Resizable, either setup columns width explicitly with _WidthFixed. -//----------------------------------------------------------------------------- -// About clipping/culling of Columns in Tables: -// - Both TableSetColumnIndex() and TableNextColumn() return true when the column is visible or performing -// width measurements. Otherwise, you may skip submitting the contents of a cell/column, BUT ONLY if you know -// it is not going to contribute to row height. -// In many situations, you may skip submitting contents for every column but one (e.g. the first one). -// - Case A: column is not hidden by user, and at least partially in sight (most common case). -// - Case B: column is clipped / out of sight (because of scrolling or parent ClipRect): TableNextColumn() return false as a hint but we still allow layout output. -// - Case C: column is hidden explicitly by the user (e.g. via the context menu, or _DefaultHide column flag, etc.). -// -// [A] [B] [C] -// TableNextColumn(): true false false -> [userland] when TableNextColumn() / TableSetColumnIndex() returns false, user can skip submitting items but only if the column doesn't contribute to row height. -// SkipItems: false false true -> [internal] when SkipItems is true, most widgets will early out if submitted, resulting is no layout output. -// ClipRect: normal zero-width zero-width -> [internal] when ClipRect is zero, ItemAdd() will return false and most widgets will early out mid-way. -// ImDrawList output: normal dummy dummy -> [internal] when using the dummy channel, ImDrawList submissions (if any) will be wasted (because cliprect is zero-width anyway). -// -// - We need to distinguish those cases because non-hidden columns that are clipped outside of scrolling bounds should still contribute their height to the row. -// However, in the majority of cases, the contribution to row height is the same for all columns, or the tallest cells are known by the programmer. -//----------------------------------------------------------------------------- -// About clipping/culling of whole Tables: -// - Scrolling tables with a known outer size can be clipped earlier as BeginTable() will return false. -//----------------------------------------------------------------------------- - -//----------------------------------------------------------------------------- -// [SECTION] Header mess -//----------------------------------------------------------------------------- - -#if defined(_MSC_VER) && !defined(_CRT_SECURE_NO_WARNINGS) -#define _CRT_SECURE_NO_WARNINGS -#endif - -#ifndef IMGUI_DEFINE_MATH_OPERATORS -#define IMGUI_DEFINE_MATH_OPERATORS -#endif - -#include "imgui.h" -#ifndef IMGUI_DISABLE -#include "imgui_internal.h" - -// System includes -#include // intptr_t - -// Visual Studio warnings -#ifdef _MSC_VER -#pragma warning (disable: 4127) // condition expression is constant -#pragma warning (disable: 4996) // 'This function or variable may be unsafe': strcpy, strdup, sprintf, vsnprintf, sscanf, fopen -#if defined(_MSC_VER) && _MSC_VER >= 1922 // MSVC 2019 16.2 or later -#pragma warning (disable: 5054) // operator '|': deprecated between enumerations of different types -#endif -#pragma warning (disable: 26451) // [Static Analyzer] Arithmetic overflow : Using operator 'xxx' on a 4 byte value and then casting the result to a 8 byte value. Cast the value to the wider type before calling operator 'xxx' to avoid overflow(io.2). -#pragma warning (disable: 26812) // [Static Analyzer] The enum type 'xxx' is unscoped. Prefer 'enum class' over 'enum' (Enum.3). -#endif - -// Clang/GCC warnings with -Weverything -#if defined(__clang__) -#if __has_warning("-Wunknown-warning-option") -#pragma clang diagnostic ignored "-Wunknown-warning-option" // warning: unknown warning group 'xxx' // not all warnings are known by all Clang versions and they tend to be rename-happy.. so ignoring warnings triggers new warnings on some configuration. Great! -#endif -#pragma clang diagnostic ignored "-Wunknown-pragmas" // warning: unknown warning group 'xxx' -#pragma clang diagnostic ignored "-Wold-style-cast" // warning: use of old-style cast // yes, they are more terse. -#pragma clang diagnostic ignored "-Wfloat-equal" // warning: comparing floating point with == or != is unsafe // storing and comparing against same constants (typically 0.0f) is ok. -#pragma clang diagnostic ignored "-Wformat-nonliteral" // warning: format string is not a string literal // passing non-literal to vsnformat(). yes, user passing incorrect format strings can crash the code. -#pragma clang diagnostic ignored "-Wsign-conversion" // warning: implicit conversion changes signedness -#pragma clang diagnostic ignored "-Wzero-as-null-pointer-constant" // warning: zero as null pointer constant // some standard header variations use #define NULL 0 -#pragma clang diagnostic ignored "-Wdouble-promotion" // warning: implicit conversion from 'float' to 'double' when passing argument to function // using printf() is a misery with this as C++ va_arg ellipsis changes float to double. -#pragma clang diagnostic ignored "-Wenum-enum-conversion" // warning: bitwise operation between different enumeration types ('XXXFlags_' and 'XXXFlagsPrivate_') -#pragma clang diagnostic ignored "-Wdeprecated-enum-enum-conversion"// warning: bitwise operation between different enumeration types ('XXXFlags_' and 'XXXFlagsPrivate_') is deprecated -#pragma clang diagnostic ignored "-Wimplicit-int-float-conversion" // warning: implicit conversion from 'xxx' to 'float' may lose precision -#elif defined(__GNUC__) -#pragma GCC diagnostic ignored "-Wpragmas" // warning: unknown option after '#pragma GCC diagnostic' kind -#pragma GCC diagnostic ignored "-Wformat-nonliteral" // warning: format not a string literal, format string not checked -#pragma GCC diagnostic ignored "-Wclass-memaccess" // [__GNUC__ >= 8] warning: 'memset/memcpy' clearing/writing an object of type 'xxxx' with no trivial copy-assignment; use assignment or value-initialization instead -#endif - -//----------------------------------------------------------------------------- -// [SECTION] Tables: Main code -//----------------------------------------------------------------------------- -// - TableFixFlags() [Internal] -// - TableFindByID() [Internal] -// - BeginTable() -// - BeginTableEx() [Internal] -// - TableBeginInitMemory() [Internal] -// - TableBeginApplyRequests() [Internal] -// - TableSetupColumnFlags() [Internal] -// - TableUpdateLayout() [Internal] -// - TableUpdateBorders() [Internal] -// - EndTable() -// - TableSetupColumn() -// - TableSetupScrollFreeze() -//----------------------------------------------------------------------------- - -// Configuration -static const int TABLE_DRAW_CHANNEL_BG0 = 0; -static const int TABLE_DRAW_CHANNEL_BG2_FROZEN = 1; -static const int TABLE_DRAW_CHANNEL_NOCLIP = 2; // When using ImGuiTableFlags_NoClip (this becomes the last visible channel) -static const float TABLE_BORDER_SIZE = 1.0f; // FIXME-TABLE: Currently hard-coded because of clipping assumptions with outer borders rendering. -static const float TABLE_RESIZE_SEPARATOR_HALF_THICKNESS = 4.0f; // Extend outside inner borders. -static const float TABLE_RESIZE_SEPARATOR_FEEDBACK_TIMER = 0.06f; // Delay/timer before making the hover feedback (color+cursor) visible because tables/columns tends to be more cramped. - -// Helper -inline ImGuiTableFlags TableFixFlags(ImGuiTableFlags flags, ImGuiWindow* outer_window) -{ - // Adjust flags: set default sizing policy - if ((flags & ImGuiTableFlags_SizingMask_) == 0) - flags |= ((flags & ImGuiTableFlags_ScrollX) || (outer_window->Flags & ImGuiWindowFlags_AlwaysAutoResize)) ? ImGuiTableFlags_SizingFixedFit : ImGuiTableFlags_SizingStretchSame; - - // Adjust flags: enable NoKeepColumnsVisible when using ImGuiTableFlags_SizingFixedSame - if ((flags & ImGuiTableFlags_SizingMask_) == ImGuiTableFlags_SizingFixedSame) - flags |= ImGuiTableFlags_NoKeepColumnsVisible; - - // Adjust flags: enforce borders when resizable - if (flags & ImGuiTableFlags_Resizable) - flags |= ImGuiTableFlags_BordersInnerV; - - // Adjust flags: disable NoHostExtendX/NoHostExtendY if we have any scrolling going on - if (flags & (ImGuiTableFlags_ScrollX | ImGuiTableFlags_ScrollY)) - flags &= ~(ImGuiTableFlags_NoHostExtendX | ImGuiTableFlags_NoHostExtendY); - - // Adjust flags: NoBordersInBodyUntilResize takes priority over NoBordersInBody - if (flags & ImGuiTableFlags_NoBordersInBodyUntilResize) - flags &= ~ImGuiTableFlags_NoBordersInBody; - - // Adjust flags: disable saved settings if there's nothing to save - if ((flags & (ImGuiTableFlags_Resizable | ImGuiTableFlags_Hideable | ImGuiTableFlags_Reorderable | ImGuiTableFlags_Sortable)) == 0) - flags |= ImGuiTableFlags_NoSavedSettings; - - // Inherit _NoSavedSettings from top-level window (child windows always have _NoSavedSettings set) - if (outer_window->RootWindow->Flags & ImGuiWindowFlags_NoSavedSettings) - flags |= ImGuiTableFlags_NoSavedSettings; - - return flags; -} - -ImGuiTable* ImGui::TableFindByID(ImGuiID id) -{ - ImGuiContext& g = *GImGui; - return g.Tables.GetByKey(id); -} - -// Read about "TABLE SIZING" at the top of this file. -bool ImGui::BeginTable(const char* str_id, int columns_count, ImGuiTableFlags flags, const ImVec2& outer_size, float inner_width) -{ - ImGuiID id = GetID(str_id); - return BeginTableEx(str_id, id, columns_count, flags, outer_size, inner_width); -} - -bool ImGui::BeginTableEx(const char* name, ImGuiID id, int columns_count, ImGuiTableFlags flags, const ImVec2& outer_size, float inner_width) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* outer_window = GetCurrentWindow(); - if (outer_window->SkipItems) // Consistent with other tables + beneficial side effect that assert on miscalling EndTable() will be more visible. - return false; - - // Sanity checks - IM_ASSERT(columns_count > 0 && columns_count < IMGUI_TABLE_MAX_COLUMNS); - if (flags & ImGuiTableFlags_ScrollX) - IM_ASSERT(inner_width >= 0.0f); - - // If an outer size is specified ahead we will be able to early out when not visible. Exact clipping criteria may evolve. - const bool use_child_window = (flags & (ImGuiTableFlags_ScrollX | ImGuiTableFlags_ScrollY)) != 0; - const ImVec2 avail_size = GetContentRegionAvail(); - const ImVec2 actual_outer_size = CalcItemSize(outer_size, ImMax(avail_size.x, 1.0f), use_child_window ? ImMax(avail_size.y, 1.0f) : 0.0f); - const ImRect outer_rect(outer_window->DC.CursorPos, outer_window->DC.CursorPos + actual_outer_size); - const bool outer_window_is_measuring_size = (outer_window->AutoFitFramesX > 0) || (outer_window->AutoFitFramesY > 0); // Doesn't apply to auto-fitting windows! - if (use_child_window && IsClippedEx(outer_rect, 0) && !outer_window_is_measuring_size) - { - ItemSize(outer_rect); - return false; - } - - // Acquire storage for the table - ImGuiTable* table = g.Tables.GetOrAddByKey(id); - const ImGuiTableFlags table_last_flags = table->Flags; - - // Acquire temporary buffers - const int table_idx = g.Tables.GetIndex(table); - if (++g.TablesTempDataStacked > g.TablesTempData.Size) - g.TablesTempData.resize(g.TablesTempDataStacked, ImGuiTableTempData()); - ImGuiTableTempData* temp_data = table->TempData = &g.TablesTempData[g.TablesTempDataStacked - 1]; - temp_data->TableIndex = table_idx; - table->DrawSplitter = &table->TempData->DrawSplitter; - table->DrawSplitter->Clear(); - - // Fix flags - table->IsDefaultSizingPolicy = (flags & ImGuiTableFlags_SizingMask_) == 0; - flags = TableFixFlags(flags, outer_window); - - // Initialize - const int previous_frame_active = table->LastFrameActive; - const int instance_no = (previous_frame_active != g.FrameCount) ? 0 : table->InstanceCurrent + 1; - table->ID = id; - table->Flags = flags; - table->LastFrameActive = g.FrameCount; - table->OuterWindow = table->InnerWindow = outer_window; - table->ColumnsCount = columns_count; - table->IsLayoutLocked = false; - table->InnerWidth = inner_width; - temp_data->UserOuterSize = outer_size; - - // Instance data (for instance 0, TableID == TableInstanceID) - ImGuiID instance_id; - table->InstanceCurrent = (ImS16)instance_no; - if (instance_no > 0) - { - IM_ASSERT(table->ColumnsCount == columns_count && "BeginTable(): Cannot change columns count mid-frame while preserving same ID"); - if (table->InstanceDataExtra.Size < instance_no) - table->InstanceDataExtra.push_back(ImGuiTableInstanceData()); - instance_id = GetIDWithSeed(instance_no, GetIDWithSeed("##Instances", NULL, id)); // Push "##Instances" followed by (int)instance_no in ID stack. - } - else - { - instance_id = id; - } - ImGuiTableInstanceData* table_instance = TableGetInstanceData(table, table->InstanceCurrent); - table_instance->TableInstanceID = instance_id; - - // When not using a child window, WorkRect.Max will grow as we append contents. - if (use_child_window) - { - // Ensure no vertical scrollbar appears if we only want horizontal one, to make flag consistent - // (we have no other way to disable vertical scrollbar of a window while keeping the horizontal one showing) - ImVec2 override_content_size(FLT_MAX, FLT_MAX); - if ((flags & ImGuiTableFlags_ScrollX) && !(flags & ImGuiTableFlags_ScrollY)) - override_content_size.y = FLT_MIN; - - // Ensure specified width (when not specified, Stretched columns will act as if the width == OuterWidth and - // never lead to any scrolling). We don't handle inner_width < 0.0f, we could potentially use it to right-align - // based on the right side of the child window work rect, which would require knowing ahead if we are going to - // have decoration taking horizontal spaces (typically a vertical scrollbar). - if ((flags & ImGuiTableFlags_ScrollX) && inner_width > 0.0f) - override_content_size.x = inner_width; - - if (override_content_size.x != FLT_MAX || override_content_size.y != FLT_MAX) - SetNextWindowContentSize(ImVec2(override_content_size.x != FLT_MAX ? override_content_size.x : 0.0f, override_content_size.y != FLT_MAX ? override_content_size.y : 0.0f)); - - // Reset scroll if we are reactivating it - if ((table_last_flags & (ImGuiTableFlags_ScrollX | ImGuiTableFlags_ScrollY)) == 0) - SetNextWindowScroll(ImVec2(0.0f, 0.0f)); - - // Create scrolling region (without border and zero window padding) - ImGuiWindowFlags child_flags = (flags & ImGuiTableFlags_ScrollX) ? ImGuiWindowFlags_HorizontalScrollbar : ImGuiWindowFlags_None; - BeginChildEx(name, instance_id, outer_rect.GetSize(), false, child_flags); - table->InnerWindow = g.CurrentWindow; - table->WorkRect = table->InnerWindow->WorkRect; - table->OuterRect = table->InnerWindow->Rect(); - table->InnerRect = table->InnerWindow->InnerRect; - IM_ASSERT(table->InnerWindow->WindowPadding.x == 0.0f && table->InnerWindow->WindowPadding.y == 0.0f && table->InnerWindow->WindowBorderSize == 0.0f); - - // Allow submitting when host is measuring - if (table->InnerWindow->SkipItems && outer_window_is_measuring_size) - table->InnerWindow->SkipItems = false; - - // When using multiple instances, ensure they have the same amount of horizontal decorations (aka vertical scrollbar) so stretched columns can be aligned) - if (instance_no == 0) - { - table->HasScrollbarYPrev = table->HasScrollbarYCurr; - table->HasScrollbarYCurr = false; - } - table->HasScrollbarYCurr |= table->InnerWindow->ScrollbarY; - } - else - { - // For non-scrolling tables, WorkRect == OuterRect == InnerRect. - // But at this point we do NOT have a correct value for .Max.y (unless a height has been explicitly passed in). It will only be updated in EndTable(). - table->WorkRect = table->OuterRect = table->InnerRect = outer_rect; - } - - // Push a standardized ID for both child-using and not-child-using tables - PushOverrideID(id); - if (instance_no > 0) - PushOverrideID(instance_id); // FIXME: Somehow this is not resolved by stack-tool, even tho GetIDWithSeed() submitted the symbol. - - // Backup a copy of host window members we will modify - ImGuiWindow* inner_window = table->InnerWindow; - table->HostIndentX = inner_window->DC.Indent.x; - table->HostClipRect = inner_window->ClipRect; - table->HostSkipItems = inner_window->SkipItems; - temp_data->HostBackupWorkRect = inner_window->WorkRect; - temp_data->HostBackupParentWorkRect = inner_window->ParentWorkRect; - temp_data->HostBackupColumnsOffset = outer_window->DC.ColumnsOffset; - temp_data->HostBackupPrevLineSize = inner_window->DC.PrevLineSize; - temp_data->HostBackupCurrLineSize = inner_window->DC.CurrLineSize; - temp_data->HostBackupCursorMaxPos = inner_window->DC.CursorMaxPos; - temp_data->HostBackupItemWidth = outer_window->DC.ItemWidth; - temp_data->HostBackupItemWidthStackSize = outer_window->DC.ItemWidthStack.Size; - inner_window->DC.PrevLineSize = inner_window->DC.CurrLineSize = ImVec2(0.0f, 0.0f); - - // Padding and Spacing - // - None ........Content..... Pad .....Content........ - // - PadOuter | Pad ..Content..... Pad .....Content.. Pad | - // - PadInner ........Content.. Pad | Pad ..Content........ - // - PadOuter+PadInner | Pad ..Content.. Pad | Pad ..Content.. Pad | - const bool pad_outer_x = (flags & ImGuiTableFlags_NoPadOuterX) ? false : (flags & ImGuiTableFlags_PadOuterX) ? true : (flags & ImGuiTableFlags_BordersOuterV) != 0; - const bool pad_inner_x = (flags & ImGuiTableFlags_NoPadInnerX) ? false : true; - const float inner_spacing_for_border = (flags & ImGuiTableFlags_BordersInnerV) ? TABLE_BORDER_SIZE : 0.0f; - const float inner_spacing_explicit = (pad_inner_x && (flags & ImGuiTableFlags_BordersInnerV) == 0) ? g.Style.CellPadding.x : 0.0f; - const float inner_padding_explicit = (pad_inner_x && (flags & ImGuiTableFlags_BordersInnerV) != 0) ? g.Style.CellPadding.x : 0.0f; - table->CellSpacingX1 = inner_spacing_explicit + inner_spacing_for_border; - table->CellSpacingX2 = inner_spacing_explicit; - table->CellPaddingX = inner_padding_explicit; - - const float outer_padding_for_border = (flags & ImGuiTableFlags_BordersOuterV) ? TABLE_BORDER_SIZE : 0.0f; - const float outer_padding_explicit = pad_outer_x ? g.Style.CellPadding.x : 0.0f; - table->OuterPaddingX = (outer_padding_for_border + outer_padding_explicit) - table->CellPaddingX; - - table->CurrentColumn = -1; - table->CurrentRow = -1; - table->RowBgColorCounter = 0; - table->LastRowFlags = ImGuiTableRowFlags_None; - table->InnerClipRect = (inner_window == outer_window) ? table->WorkRect : inner_window->ClipRect; - table->InnerClipRect.ClipWith(table->WorkRect); // We need this to honor inner_width - table->InnerClipRect.ClipWithFull(table->HostClipRect); - table->InnerClipRect.Max.y = (flags & ImGuiTableFlags_NoHostExtendY) ? ImMin(table->InnerClipRect.Max.y, inner_window->WorkRect.Max.y) : inner_window->ClipRect.Max.y; - - table->RowPosY1 = table->RowPosY2 = table->WorkRect.Min.y; // This is needed somehow - table->RowTextBaseline = 0.0f; // This will be cleared again by TableBeginRow() - table->RowCellPaddingY = 0.0f; - table->FreezeRowsRequest = table->FreezeRowsCount = 0; // This will be setup by TableSetupScrollFreeze(), if any - table->FreezeColumnsRequest = table->FreezeColumnsCount = 0; - table->IsUnfrozenRows = true; - table->DeclColumnsCount = table->AngledHeadersCount = 0; - if (previous_frame_active + 1 < g.FrameCount) - table->IsActiveIdInTable = false; - temp_data->AngledheadersExtraWidth = 0.0f; - - // Using opaque colors facilitate overlapping lines of the grid, otherwise we'd need to improve TableDrawBorders() - table->BorderColorStrong = GetColorU32(ImGuiCol_TableBorderStrong); - table->BorderColorLight = GetColorU32(ImGuiCol_TableBorderLight); - - // Make table current - g.CurrentTable = table; - outer_window->DC.NavIsScrollPushableX = false; // Shortcut for NavUpdateCurrentWindowIsScrollPushableX(); - outer_window->DC.CurrentTableIdx = table_idx; - if (inner_window != outer_window) // So EndChild() within the inner window can restore the table properly. - inner_window->DC.CurrentTableIdx = table_idx; - - if ((table_last_flags & ImGuiTableFlags_Reorderable) && (flags & ImGuiTableFlags_Reorderable) == 0) - table->IsResetDisplayOrderRequest = true; - - // Mark as used to avoid GC - if (table_idx >= g.TablesLastTimeActive.Size) - g.TablesLastTimeActive.resize(table_idx + 1, -1.0f); - g.TablesLastTimeActive[table_idx] = (float)g.Time; - temp_data->LastTimeActive = (float)g.Time; - table->MemoryCompacted = false; - - // Setup memory buffer (clear data if columns count changed) - ImGuiTableColumn* old_columns_to_preserve = NULL; - void* old_columns_raw_data = NULL; - const int old_columns_count = table->Columns.size(); - if (old_columns_count != 0 && old_columns_count != columns_count) - { - // Attempt to preserve width on column count change (#4046) - old_columns_to_preserve = table->Columns.Data; - old_columns_raw_data = table->RawData; - table->RawData = NULL; - } - if (table->RawData == NULL) - { - TableBeginInitMemory(table, columns_count); - table->IsInitializing = table->IsSettingsRequestLoad = true; - } - if (table->IsResetAllRequest) - TableResetSettings(table); - if (table->IsInitializing) - { - // Initialize - table->SettingsOffset = -1; - table->IsSortSpecsDirty = true; - table->InstanceInteracted = -1; - table->ContextPopupColumn = -1; - table->ReorderColumn = table->ResizedColumn = table->LastResizedColumn = -1; - table->AutoFitSingleColumn = -1; - table->HoveredColumnBody = table->HoveredColumnBorder = -1; - for (int n = 0; n < columns_count; n++) - { - ImGuiTableColumn* column = &table->Columns[n]; - if (old_columns_to_preserve && n < old_columns_count) - { - // FIXME: We don't attempt to preserve column order in this path. - *column = old_columns_to_preserve[n]; - } - else - { - float width_auto = column->WidthAuto; - *column = ImGuiTableColumn(); - column->WidthAuto = width_auto; - column->IsPreserveWidthAuto = true; // Preserve WidthAuto when reinitializing a live table: not technically necessary but remove a visible flicker - column->IsEnabled = column->IsUserEnabled = column->IsUserEnabledNextFrame = true; - } - column->DisplayOrder = table->DisplayOrderToIndex[n] = (ImGuiTableColumnIdx)n; - } - } - if (old_columns_raw_data) - IM_FREE(old_columns_raw_data); - - // Load settings - if (table->IsSettingsRequestLoad) - TableLoadSettings(table); - - // Handle DPI/font resize - // This is designed to facilitate DPI changes with the assumption that e.g. style.CellPadding has been scaled as well. - // It will also react to changing fonts with mixed results. It doesn't need to be perfect but merely provide a decent transition. - // FIXME-DPI: Provide consistent standards for reference size. Perhaps using g.CurrentDpiScale would be more self explanatory. - // This is will lead us to non-rounded WidthRequest in columns, which should work but is a poorly tested path. - const float new_ref_scale_unit = g.FontSize; // g.Font->GetCharAdvance('A') ? - if (table->RefScale != 0.0f && table->RefScale != new_ref_scale_unit) - { - const float scale_factor = new_ref_scale_unit / table->RefScale; - //IMGUI_DEBUG_PRINT("[table] %08X RefScaleUnit %.3f -> %.3f, scaling width by %.3f\n", table->ID, table->RefScaleUnit, new_ref_scale_unit, scale_factor); - for (int n = 0; n < columns_count; n++) - table->Columns[n].WidthRequest = table->Columns[n].WidthRequest * scale_factor; - } - table->RefScale = new_ref_scale_unit; - - // Disable output until user calls TableNextRow() or TableNextColumn() leading to the TableUpdateLayout() call.. - // This is not strictly necessary but will reduce cases were "out of table" output will be misleading to the user. - // Because we cannot safely assert in EndTable() when no rows have been created, this seems like our best option. - inner_window->SkipItems = true; - - // Clear names - // At this point the ->NameOffset field of each column will be invalid until TableUpdateLayout() or the first call to TableSetupColumn() - if (table->ColumnsNames.Buf.Size > 0) - table->ColumnsNames.Buf.resize(0); - - // Apply queued resizing/reordering/hiding requests - TableBeginApplyRequests(table); - - return true; -} - -// For reference, the average total _allocation count_ for a table is: -// + 0 (for ImGuiTable instance, we are pooling allocations in g.Tables[]) -// + 1 (for table->RawData allocated below) -// + 1 (for table->ColumnsNames, if names are used) -// Shared allocations for the maximum number of simultaneously nested tables (generally a very small number) -// + 1 (for table->Splitter._Channels) -// + 2 * active_channels_count (for ImDrawCmd and ImDrawIdx buffers inside channels) -// Where active_channels_count is variable but often == columns_count or == columns_count + 1, see TableSetupDrawChannels() for details. -// Unused channels don't perform their +2 allocations. -void ImGui::TableBeginInitMemory(ImGuiTable* table, int columns_count) -{ - // Allocate single buffer for our arrays - const int columns_bit_array_size = (int)ImBitArrayGetStorageSizeInBytes(columns_count); - ImSpanAllocator<6> span_allocator; - span_allocator.Reserve(0, columns_count * sizeof(ImGuiTableColumn)); - span_allocator.Reserve(1, columns_count * sizeof(ImGuiTableColumnIdx)); - span_allocator.Reserve(2, columns_count * sizeof(ImGuiTableCellData), 4); - for (int n = 3; n < 6; n++) - span_allocator.Reserve(n, columns_bit_array_size); - table->RawData = IM_ALLOC(span_allocator.GetArenaSizeInBytes()); - memset(table->RawData, 0, span_allocator.GetArenaSizeInBytes()); - span_allocator.SetArenaBasePtr(table->RawData); - span_allocator.GetSpan(0, &table->Columns); - span_allocator.GetSpan(1, &table->DisplayOrderToIndex); - span_allocator.GetSpan(2, &table->RowCellData); - table->EnabledMaskByDisplayOrder = (ImU32*)span_allocator.GetSpanPtrBegin(3); - table->EnabledMaskByIndex = (ImU32*)span_allocator.GetSpanPtrBegin(4); - table->VisibleMaskByIndex = (ImU32*)span_allocator.GetSpanPtrBegin(5); -} - -// Apply queued resizing/reordering/hiding requests -void ImGui::TableBeginApplyRequests(ImGuiTable* table) -{ - // Handle resizing request - // (We process this in the TableBegin() of the first instance of each table) - // FIXME-TABLE: Contains columns if our work area doesn't allow for scrolling? - if (table->InstanceCurrent == 0) - { - if (table->ResizedColumn != -1 && table->ResizedColumnNextWidth != FLT_MAX) - TableSetColumnWidth(table->ResizedColumn, table->ResizedColumnNextWidth); - table->LastResizedColumn = table->ResizedColumn; - table->ResizedColumnNextWidth = FLT_MAX; - table->ResizedColumn = -1; - - // Process auto-fit for single column, which is a special case for stretch columns and fixed columns with FixedSame policy. - // FIXME-TABLE: Would be nice to redistribute available stretch space accordingly to other weights, instead of giving it all to siblings. - if (table->AutoFitSingleColumn != -1) - { - TableSetColumnWidth(table->AutoFitSingleColumn, table->Columns[table->AutoFitSingleColumn].WidthAuto); - table->AutoFitSingleColumn = -1; - } - } - - // Handle reordering request - // Note: we don't clear ReorderColumn after handling the request. - if (table->InstanceCurrent == 0) - { - if (table->HeldHeaderColumn == -1 && table->ReorderColumn != -1) - table->ReorderColumn = -1; - table->HeldHeaderColumn = -1; - if (table->ReorderColumn != -1 && table->ReorderColumnDir != 0) - { - // We need to handle reordering across hidden columns. - // In the configuration below, moving C to the right of E will lead to: - // ... C [D] E ---> ... [D] E C (Column name/index) - // ... 2 3 4 ... 2 3 4 (Display order) - const int reorder_dir = table->ReorderColumnDir; - IM_ASSERT(reorder_dir == -1 || reorder_dir == +1); - IM_ASSERT(table->Flags & ImGuiTableFlags_Reorderable); - ImGuiTableColumn* src_column = &table->Columns[table->ReorderColumn]; - ImGuiTableColumn* dst_column = &table->Columns[(reorder_dir == -1) ? src_column->PrevEnabledColumn : src_column->NextEnabledColumn]; - IM_UNUSED(dst_column); - const int src_order = src_column->DisplayOrder; - const int dst_order = dst_column->DisplayOrder; - src_column->DisplayOrder = (ImGuiTableColumnIdx)dst_order; - for (int order_n = src_order + reorder_dir; order_n != dst_order + reorder_dir; order_n += reorder_dir) - table->Columns[table->DisplayOrderToIndex[order_n]].DisplayOrder -= (ImGuiTableColumnIdx)reorder_dir; - IM_ASSERT(dst_column->DisplayOrder == dst_order - reorder_dir); - - // Display order is stored in both columns->IndexDisplayOrder and table->DisplayOrder[]. Rebuild later from the former. - for (int column_n = 0; column_n < table->ColumnsCount; column_n++) - table->DisplayOrderToIndex[table->Columns[column_n].DisplayOrder] = (ImGuiTableColumnIdx)column_n; - table->ReorderColumnDir = 0; - table->IsSettingsDirty = true; - } - } - - // Handle display order reset request - if (table->IsResetDisplayOrderRequest) - { - for (int n = 0; n < table->ColumnsCount; n++) - table->DisplayOrderToIndex[n] = table->Columns[n].DisplayOrder = (ImGuiTableColumnIdx)n; - table->IsResetDisplayOrderRequest = false; - table->IsSettingsDirty = true; - } -} - -// Adjust flags: default width mode + stretch columns are not allowed when auto extending -static void TableSetupColumnFlags(ImGuiTable* table, ImGuiTableColumn* column, ImGuiTableColumnFlags flags_in) -{ - ImGuiTableColumnFlags flags = flags_in; - - // Sizing Policy - if ((flags & ImGuiTableColumnFlags_WidthMask_) == 0) - { - const ImGuiTableFlags table_sizing_policy = (table->Flags & ImGuiTableFlags_SizingMask_); - if (table_sizing_policy == ImGuiTableFlags_SizingFixedFit || table_sizing_policy == ImGuiTableFlags_SizingFixedSame) - flags |= ImGuiTableColumnFlags_WidthFixed; - else - flags |= ImGuiTableColumnFlags_WidthStretch; - } - else - { - IM_ASSERT(ImIsPowerOfTwo(flags & ImGuiTableColumnFlags_WidthMask_)); // Check that only 1 of each set is used. - } - - // Resize - if ((table->Flags & ImGuiTableFlags_Resizable) == 0) - flags |= ImGuiTableColumnFlags_NoResize; - - // Sorting - if ((flags & ImGuiTableColumnFlags_NoSortAscending) && (flags & ImGuiTableColumnFlags_NoSortDescending)) - flags |= ImGuiTableColumnFlags_NoSort; - - // Indentation - if ((flags & ImGuiTableColumnFlags_IndentMask_) == 0) - flags |= (table->Columns.index_from_ptr(column) == 0) ? ImGuiTableColumnFlags_IndentEnable : ImGuiTableColumnFlags_IndentDisable; - - // Alignment - //if ((flags & ImGuiTableColumnFlags_AlignMask_) == 0) - // flags |= ImGuiTableColumnFlags_AlignCenter; - //IM_ASSERT(ImIsPowerOfTwo(flags & ImGuiTableColumnFlags_AlignMask_)); // Check that only 1 of each set is used. - - // Preserve status flags - column->Flags = flags | (column->Flags & ImGuiTableColumnFlags_StatusMask_); - - // Build an ordered list of available sort directions - column->SortDirectionsAvailCount = column->SortDirectionsAvailMask = column->SortDirectionsAvailList = 0; - if (table->Flags & ImGuiTableFlags_Sortable) - { - int count = 0, mask = 0, list = 0; - if ((flags & ImGuiTableColumnFlags_PreferSortAscending) != 0 && (flags & ImGuiTableColumnFlags_NoSortAscending) == 0) { mask |= 1 << ImGuiSortDirection_Ascending; list |= ImGuiSortDirection_Ascending << (count << 1); count++; } - if ((flags & ImGuiTableColumnFlags_PreferSortDescending) != 0 && (flags & ImGuiTableColumnFlags_NoSortDescending) == 0) { mask |= 1 << ImGuiSortDirection_Descending; list |= ImGuiSortDirection_Descending << (count << 1); count++; } - if ((flags & ImGuiTableColumnFlags_PreferSortAscending) == 0 && (flags & ImGuiTableColumnFlags_NoSortAscending) == 0) { mask |= 1 << ImGuiSortDirection_Ascending; list |= ImGuiSortDirection_Ascending << (count << 1); count++; } - if ((flags & ImGuiTableColumnFlags_PreferSortDescending) == 0 && (flags & ImGuiTableColumnFlags_NoSortDescending) == 0) { mask |= 1 << ImGuiSortDirection_Descending; list |= ImGuiSortDirection_Descending << (count << 1); count++; } - if ((table->Flags & ImGuiTableFlags_SortTristate) || count == 0) { mask |= 1 << ImGuiSortDirection_None; count++; } - column->SortDirectionsAvailList = (ImU8)list; - column->SortDirectionsAvailMask = (ImU8)mask; - column->SortDirectionsAvailCount = (ImU8)count; - ImGui::TableFixColumnSortDirection(table, column); - } -} - -// Layout columns for the frame. This is in essence the followup to BeginTable() and this is our largest function. -// Runs on the first call to TableNextRow(), to give a chance for TableSetupColumn() and other TableSetupXXXXX() functions to be called first. -// FIXME-TABLE: Our width (and therefore our WorkRect) will be minimal in the first frame for _WidthAuto columns. -// Increase feedback side-effect with widgets relying on WorkRect.Max.x... Maybe provide a default distribution for _WidthAuto columns? -void ImGui::TableUpdateLayout(ImGuiTable* table) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(table->IsLayoutLocked == false); - - const ImGuiTableFlags table_sizing_policy = (table->Flags & ImGuiTableFlags_SizingMask_); - table->IsDefaultDisplayOrder = true; - table->ColumnsEnabledCount = 0; - ImBitArrayClearAllBits(table->EnabledMaskByIndex, table->ColumnsCount); - ImBitArrayClearAllBits(table->EnabledMaskByDisplayOrder, table->ColumnsCount); - table->LeftMostEnabledColumn = -1; - table->MinColumnWidth = ImMax(1.0f, g.Style.FramePadding.x * 1.0f); // g.Style.ColumnsMinSpacing; // FIXME-TABLE - - // [Part 1] Apply/lock Enabled and Order states. Calculate auto/ideal width for columns. Count fixed/stretch columns. - // Process columns in their visible orders as we are building the Prev/Next indices. - int count_fixed = 0; // Number of columns that have fixed sizing policies - int count_stretch = 0; // Number of columns that have stretch sizing policies - int prev_visible_column_idx = -1; - bool has_auto_fit_request = false; - bool has_resizable = false; - float stretch_sum_width_auto = 0.0f; - float fixed_max_width_auto = 0.0f; - for (int order_n = 0; order_n < table->ColumnsCount; order_n++) - { - const int column_n = table->DisplayOrderToIndex[order_n]; - if (column_n != order_n) - table->IsDefaultDisplayOrder = false; - ImGuiTableColumn* column = &table->Columns[column_n]; - - // Clear column setup if not submitted by user. Currently we make it mandatory to call TableSetupColumn() every frame. - // It would easily work without but we're not ready to guarantee it since e.g. names need resubmission anyway. - // We take a slight shortcut but in theory we could be calling TableSetupColumn() here with dummy values, it should yield the same effect. - if (table->DeclColumnsCount <= column_n) - { - TableSetupColumnFlags(table, column, ImGuiTableColumnFlags_None); - column->NameOffset = -1; - column->UserID = 0; - column->InitStretchWeightOrWidth = -1.0f; - } - - // Update Enabled state, mark settings and sort specs dirty - if (!(table->Flags & ImGuiTableFlags_Hideable) || (column->Flags & ImGuiTableColumnFlags_NoHide)) - column->IsUserEnabledNextFrame = true; - if (column->IsUserEnabled != column->IsUserEnabledNextFrame) - { - column->IsUserEnabled = column->IsUserEnabledNextFrame; - table->IsSettingsDirty = true; - } - column->IsEnabled = column->IsUserEnabled && (column->Flags & ImGuiTableColumnFlags_Disabled) == 0; - - if (column->SortOrder != -1 && !column->IsEnabled) - table->IsSortSpecsDirty = true; - if (column->SortOrder > 0 && !(table->Flags & ImGuiTableFlags_SortMulti)) - table->IsSortSpecsDirty = true; - - // Auto-fit unsized columns - const bool start_auto_fit = (column->Flags & ImGuiTableColumnFlags_WidthFixed) ? (column->WidthRequest < 0.0f) : (column->StretchWeight < 0.0f); - if (start_auto_fit) - column->AutoFitQueue = column->CannotSkipItemsQueue = (1 << 3) - 1; // Fit for three frames - - if (!column->IsEnabled) - { - column->IndexWithinEnabledSet = -1; - continue; - } - - // Mark as enabled and link to previous/next enabled column - column->PrevEnabledColumn = (ImGuiTableColumnIdx)prev_visible_column_idx; - column->NextEnabledColumn = -1; - if (prev_visible_column_idx != -1) - table->Columns[prev_visible_column_idx].NextEnabledColumn = (ImGuiTableColumnIdx)column_n; - else - table->LeftMostEnabledColumn = (ImGuiTableColumnIdx)column_n; - column->IndexWithinEnabledSet = table->ColumnsEnabledCount++; - ImBitArraySetBit(table->EnabledMaskByIndex, column_n); - ImBitArraySetBit(table->EnabledMaskByDisplayOrder, column->DisplayOrder); - prev_visible_column_idx = column_n; - IM_ASSERT(column->IndexWithinEnabledSet <= column->DisplayOrder); - - // Calculate ideal/auto column width (that's the width required for all contents to be visible without clipping) - // Combine width from regular rows + width from headers unless requested not to. - if (!column->IsPreserveWidthAuto) - column->WidthAuto = TableGetColumnWidthAuto(table, column); - - // Non-resizable columns keep their requested width (apply user value regardless of IsPreserveWidthAuto) - const bool column_is_resizable = (column->Flags & ImGuiTableColumnFlags_NoResize) == 0; - if (column_is_resizable) - has_resizable = true; - if ((column->Flags & ImGuiTableColumnFlags_WidthFixed) && column->InitStretchWeightOrWidth > 0.0f && !column_is_resizable) - column->WidthAuto = column->InitStretchWeightOrWidth; - - if (column->AutoFitQueue != 0x00) - has_auto_fit_request = true; - if (column->Flags & ImGuiTableColumnFlags_WidthStretch) - { - stretch_sum_width_auto += column->WidthAuto; - count_stretch++; - } - else - { - fixed_max_width_auto = ImMax(fixed_max_width_auto, column->WidthAuto); - count_fixed++; - } - } - if ((table->Flags & ImGuiTableFlags_Sortable) && table->SortSpecsCount == 0 && !(table->Flags & ImGuiTableFlags_SortTristate)) - table->IsSortSpecsDirty = true; - table->RightMostEnabledColumn = (ImGuiTableColumnIdx)prev_visible_column_idx; - IM_ASSERT(table->LeftMostEnabledColumn >= 0 && table->RightMostEnabledColumn >= 0); - - // [Part 2] Disable child window clipping while fitting columns. This is not strictly necessary but makes it possible to avoid - // the column fitting having to wait until the first visible frame of the child container (may or not be a good thing). Also see #6510. - // FIXME-TABLE: for always auto-resizing columns may not want to do that all the time. - if (has_auto_fit_request && table->OuterWindow != table->InnerWindow) - table->InnerWindow->SkipItems = false; - if (has_auto_fit_request) - table->IsSettingsDirty = true; - - // [Part 3] Fix column flags and record a few extra information. - float sum_width_requests = 0.0f; // Sum of all width for fixed and auto-resize columns, excluding width contributed by Stretch columns but including spacing/padding. - float stretch_sum_weights = 0.0f; // Sum of all weights for stretch columns. - table->LeftMostStretchedColumn = table->RightMostStretchedColumn = -1; - for (int column_n = 0; column_n < table->ColumnsCount; column_n++) - { - if (!IM_BITARRAY_TESTBIT(table->EnabledMaskByIndex, column_n)) - continue; - ImGuiTableColumn* column = &table->Columns[column_n]; - - const bool column_is_resizable = (column->Flags & ImGuiTableColumnFlags_NoResize) == 0; - if (column->Flags & ImGuiTableColumnFlags_WidthFixed) - { - // Apply same widths policy - float width_auto = column->WidthAuto; - if (table_sizing_policy == ImGuiTableFlags_SizingFixedSame && (column->AutoFitQueue != 0x00 || !column_is_resizable)) - width_auto = fixed_max_width_auto; - - // Apply automatic width - // Latch initial size for fixed columns and update it constantly for auto-resizing column (unless clipped!) - if (column->AutoFitQueue != 0x00) - column->WidthRequest = width_auto; - else if ((column->Flags & ImGuiTableColumnFlags_WidthFixed) && !column_is_resizable && column->IsRequestOutput) - column->WidthRequest = width_auto; - - // FIXME-TABLE: Increase minimum size during init frame to avoid biasing auto-fitting widgets - // (e.g. TextWrapped) too much. Otherwise what tends to happen is that TextWrapped would output a very - // large height (= first frame scrollbar display very off + clipper would skip lots of items). - // This is merely making the side-effect less extreme, but doesn't properly fixes it. - // FIXME: Move this to ->WidthGiven to avoid temporary lossyless? - // FIXME: This break IsPreserveWidthAuto from not flickering if the stored WidthAuto was smaller. - if (column->AutoFitQueue > 0x01 && table->IsInitializing && !column->IsPreserveWidthAuto) - column->WidthRequest = ImMax(column->WidthRequest, table->MinColumnWidth * 4.0f); // FIXME-TABLE: Another constant/scale? - sum_width_requests += column->WidthRequest; - } - else - { - // Initialize stretch weight - if (column->AutoFitQueue != 0x00 || column->StretchWeight < 0.0f || !column_is_resizable) - { - if (column->InitStretchWeightOrWidth > 0.0f) - column->StretchWeight = column->InitStretchWeightOrWidth; - else if (table_sizing_policy == ImGuiTableFlags_SizingStretchProp) - column->StretchWeight = (column->WidthAuto / stretch_sum_width_auto) * count_stretch; - else - column->StretchWeight = 1.0f; - } - - stretch_sum_weights += column->StretchWeight; - if (table->LeftMostStretchedColumn == -1 || table->Columns[table->LeftMostStretchedColumn].DisplayOrder > column->DisplayOrder) - table->LeftMostStretchedColumn = (ImGuiTableColumnIdx)column_n; - if (table->RightMostStretchedColumn == -1 || table->Columns[table->RightMostStretchedColumn].DisplayOrder < column->DisplayOrder) - table->RightMostStretchedColumn = (ImGuiTableColumnIdx)column_n; - } - column->IsPreserveWidthAuto = false; - sum_width_requests += table->CellPaddingX * 2.0f; - } - table->ColumnsEnabledFixedCount = (ImGuiTableColumnIdx)count_fixed; - table->ColumnsStretchSumWeights = stretch_sum_weights; - - // [Part 4] Apply final widths based on requested widths - const ImRect work_rect = table->WorkRect; - const float width_spacings = (table->OuterPaddingX * 2.0f) + (table->CellSpacingX1 + table->CellSpacingX2) * (table->ColumnsEnabledCount - 1); - const float width_removed = (table->HasScrollbarYPrev && !table->InnerWindow->ScrollbarY) ? g.Style.ScrollbarSize : 0.0f; // To synchronize decoration width of synched tables with mismatching scrollbar state (#5920) - const float width_avail = ImMax(1.0f, (((table->Flags & ImGuiTableFlags_ScrollX) && table->InnerWidth == 0.0f) ? table->InnerClipRect.GetWidth() : work_rect.GetWidth()) - width_removed); - const float width_avail_for_stretched_columns = width_avail - width_spacings - sum_width_requests; - float width_remaining_for_stretched_columns = width_avail_for_stretched_columns; - table->ColumnsGivenWidth = width_spacings + (table->CellPaddingX * 2.0f) * table->ColumnsEnabledCount; - for (int column_n = 0; column_n < table->ColumnsCount; column_n++) - { - if (!IM_BITARRAY_TESTBIT(table->EnabledMaskByIndex, column_n)) - continue; - ImGuiTableColumn* column = &table->Columns[column_n]; - - // Allocate width for stretched/weighted columns (StretchWeight gets converted into WidthRequest) - if (column->Flags & ImGuiTableColumnFlags_WidthStretch) - { - float weight_ratio = column->StretchWeight / stretch_sum_weights; - column->WidthRequest = IM_TRUNC(ImMax(width_avail_for_stretched_columns * weight_ratio, table->MinColumnWidth) + 0.01f); - width_remaining_for_stretched_columns -= column->WidthRequest; - } - - // [Resize Rule 1] The right-most Visible column is not resizable if there is at least one Stretch column - // See additional comments in TableSetColumnWidth(). - if (column->NextEnabledColumn == -1 && table->LeftMostStretchedColumn != -1) - column->Flags |= ImGuiTableColumnFlags_NoDirectResize_; - - // Assign final width, record width in case we will need to shrink - column->WidthGiven = ImTrunc(ImMax(column->WidthRequest, table->MinColumnWidth)); - table->ColumnsGivenWidth += column->WidthGiven; - } - - // [Part 5] Redistribute stretch remainder width due to rounding (remainder width is < 1.0f * number of Stretch column). - // Using right-to-left distribution (more likely to match resizing cursor). - if (width_remaining_for_stretched_columns >= 1.0f && !(table->Flags & ImGuiTableFlags_PreciseWidths)) - for (int order_n = table->ColumnsCount - 1; stretch_sum_weights > 0.0f && width_remaining_for_stretched_columns >= 1.0f && order_n >= 0; order_n--) - { - if (!IM_BITARRAY_TESTBIT(table->EnabledMaskByDisplayOrder, order_n)) - continue; - ImGuiTableColumn* column = &table->Columns[table->DisplayOrderToIndex[order_n]]; - if (!(column->Flags & ImGuiTableColumnFlags_WidthStretch)) - continue; - column->WidthRequest += 1.0f; - column->WidthGiven += 1.0f; - width_remaining_for_stretched_columns -= 1.0f; - } - - // Determine if table is hovered which will be used to flag columns as hovered. - // - In principle we'd like to use the equivalent of IsItemHovered(ImGuiHoveredFlags_AllowWhenBlockedByActiveItem), - // but because our item is partially submitted at this point we use ItemHoverable() and a workaround (temporarily - // clear ActiveId, which is equivalent to the change provided by _AllowWhenBLockedByActiveItem). - // - This allows columns to be marked as hovered when e.g. clicking a button inside the column, or using drag and drop. - ImGuiTableInstanceData* table_instance = TableGetInstanceData(table, table->InstanceCurrent); - table_instance->HoveredRowLast = table_instance->HoveredRowNext; - table_instance->HoveredRowNext = -1; - table->HoveredColumnBody = table->HoveredColumnBorder = -1; - const ImRect mouse_hit_rect(table->OuterRect.Min.x, table->OuterRect.Min.y, table->OuterRect.Max.x, ImMax(table->OuterRect.Max.y, table->OuterRect.Min.y + table_instance->LastOuterHeight)); - const ImGuiID backup_active_id = g.ActiveId; - g.ActiveId = 0; - const bool is_hovering_table = ItemHoverable(mouse_hit_rect, 0, ImGuiItemFlags_None); - g.ActiveId = backup_active_id; - - // Determine skewed MousePos.x to support angled headers. - float mouse_skewed_x = g.IO.MousePos.x; - if (table->AngledHeadersHeight > 0.0f) - if (g.IO.MousePos.y >= table->OuterRect.Min.y && g.IO.MousePos.y <= table->OuterRect.Min.y + table->AngledHeadersHeight) - mouse_skewed_x += ImTrunc((table->OuterRect.Min.y + table->AngledHeadersHeight - g.IO.MousePos.y) * table->AngledHeadersSlope); - - // [Part 6] Setup final position, offset, skip/clip states and clipping rectangles, detect hovered column - // Process columns in their visible orders as we are comparing the visible order and adjusting host_clip_rect while looping. - int visible_n = 0; - bool has_at_least_one_column_requesting_output = false; - bool offset_x_frozen = (table->FreezeColumnsCount > 0); - float offset_x = ((table->FreezeColumnsCount > 0) ? table->OuterRect.Min.x : work_rect.Min.x) + table->OuterPaddingX - table->CellSpacingX1; - ImRect host_clip_rect = table->InnerClipRect; - //host_clip_rect.Max.x += table->CellPaddingX + table->CellSpacingX2; - ImBitArrayClearAllBits(table->VisibleMaskByIndex, table->ColumnsCount); - for (int order_n = 0; order_n < table->ColumnsCount; order_n++) - { - const int column_n = table->DisplayOrderToIndex[order_n]; - ImGuiTableColumn* column = &table->Columns[column_n]; - - column->NavLayerCurrent = (ImS8)(table->FreezeRowsCount > 0 ? ImGuiNavLayer_Menu : ImGuiNavLayer_Main); // Use Count NOT request so Header line changes layer when frozen - - if (offset_x_frozen && table->FreezeColumnsCount == visible_n) - { - offset_x += work_rect.Min.x - table->OuterRect.Min.x; - offset_x_frozen = false; - } - - // Clear status flags - column->Flags &= ~ImGuiTableColumnFlags_StatusMask_; - - if (!IM_BITARRAY_TESTBIT(table->EnabledMaskByDisplayOrder, order_n)) - { - // Hidden column: clear a few fields and we are done with it for the remainder of the function. - // We set a zero-width clip rect but set Min.y/Max.y properly to not interfere with the clipper. - column->MinX = column->MaxX = column->WorkMinX = column->ClipRect.Min.x = column->ClipRect.Max.x = offset_x; - column->WidthGiven = 0.0f; - column->ClipRect.Min.y = work_rect.Min.y; - column->ClipRect.Max.y = FLT_MAX; - column->ClipRect.ClipWithFull(host_clip_rect); - column->IsVisibleX = column->IsVisibleY = column->IsRequestOutput = false; - column->IsSkipItems = true; - column->ItemWidth = 1.0f; - continue; - } - - // Detect hovered column - if (is_hovering_table && mouse_skewed_x >= column->ClipRect.Min.x && mouse_skewed_x < column->ClipRect.Max.x) - table->HoveredColumnBody = (ImGuiTableColumnIdx)column_n; - - // Lock start position - column->MinX = offset_x; - - // Lock width based on start position and minimum/maximum width for this position - float max_width = TableGetMaxColumnWidth(table, column_n); - column->WidthGiven = ImMin(column->WidthGiven, max_width); - column->WidthGiven = ImMax(column->WidthGiven, ImMin(column->WidthRequest, table->MinColumnWidth)); - column->MaxX = offset_x + column->WidthGiven + table->CellSpacingX1 + table->CellSpacingX2 + table->CellPaddingX * 2.0f; - - // Lock other positions - // - ClipRect.Min.x: Because merging draw commands doesn't compare min boundaries, we make ClipRect.Min.x match left bounds to be consistent regardless of merging. - // - ClipRect.Max.x: using WorkMaxX instead of MaxX (aka including padding) makes things more consistent when resizing down, tho slightly detrimental to visibility in very-small column. - // - ClipRect.Max.x: using MaxX makes it easier for header to receive hover highlight with no discontinuity and display sorting arrow. - // - FIXME-TABLE: We want equal width columns to have equal (ClipRect.Max.x - WorkMinX) width, which means ClipRect.max.x cannot stray off host_clip_rect.Max.x else right-most column may appear shorter. - column->WorkMinX = column->MinX + table->CellPaddingX + table->CellSpacingX1; - column->WorkMaxX = column->MaxX - table->CellPaddingX - table->CellSpacingX2; // Expected max - column->ItemWidth = ImTrunc(column->WidthGiven * 0.65f); - column->ClipRect.Min.x = column->MinX; - column->ClipRect.Min.y = work_rect.Min.y; - column->ClipRect.Max.x = column->MaxX; //column->WorkMaxX; - column->ClipRect.Max.y = FLT_MAX; - column->ClipRect.ClipWithFull(host_clip_rect); - - // Mark column as Clipped (not in sight) - // Note that scrolling tables (where inner_window != outer_window) handle Y clipped earlier in BeginTable() so IsVisibleY really only applies to non-scrolling tables. - // FIXME-TABLE: Because InnerClipRect.Max.y is conservatively ==outer_window->ClipRect.Max.y, we never can mark columns _Above_ the scroll line as not IsVisibleY. - // Taking advantage of LastOuterHeight would yield good results there... - // FIXME-TABLE: Y clipping is disabled because it effectively means not submitting will reduce contents width which is fed to outer_window->DC.CursorMaxPos.x, - // and this may be used (e.g. typically by outer_window using AlwaysAutoResize or outer_window's horizontal scrollbar, but could be something else). - // Possible solution to preserve last known content width for clipped column. Test 'table_reported_size' fails when enabling Y clipping and window is resized small. - column->IsVisibleX = (column->ClipRect.Max.x > column->ClipRect.Min.x); - column->IsVisibleY = true; // (column->ClipRect.Max.y > column->ClipRect.Min.y); - const bool is_visible = column->IsVisibleX; //&& column->IsVisibleY; - if (is_visible) - ImBitArraySetBit(table->VisibleMaskByIndex, column_n); - - // Mark column as requesting output from user. Note that fixed + non-resizable sets are auto-fitting at all times and therefore always request output. - column->IsRequestOutput = is_visible || column->AutoFitQueue != 0 || column->CannotSkipItemsQueue != 0; - - // Mark column as SkipItems (ignoring all items/layout) - // (table->HostSkipItems is a copy of inner_window->SkipItems before we cleared it above in Part 2) - column->IsSkipItems = !column->IsEnabled || table->HostSkipItems; - if (column->IsSkipItems) - IM_ASSERT(!is_visible); - if (column->IsRequestOutput && !column->IsSkipItems) - has_at_least_one_column_requesting_output = true; - - // Update status flags - column->Flags |= ImGuiTableColumnFlags_IsEnabled; - if (is_visible) - column->Flags |= ImGuiTableColumnFlags_IsVisible; - if (column->SortOrder != -1) - column->Flags |= ImGuiTableColumnFlags_IsSorted; - if (table->HoveredColumnBody == column_n) - column->Flags |= ImGuiTableColumnFlags_IsHovered; - - // Alignment - // FIXME-TABLE: This align based on the whole column width, not per-cell, and therefore isn't useful in - // many cases (to be able to honor this we might be able to store a log of cells width, per row, for - // visible rows, but nav/programmatic scroll would have visible artifacts.) - //if (column->Flags & ImGuiTableColumnFlags_AlignRight) - // column->WorkMinX = ImMax(column->WorkMinX, column->MaxX - column->ContentWidthRowsUnfrozen); - //else if (column->Flags & ImGuiTableColumnFlags_AlignCenter) - // column->WorkMinX = ImLerp(column->WorkMinX, ImMax(column->StartX, column->MaxX - column->ContentWidthRowsUnfrozen), 0.5f); - - // Reset content width variables - column->ContentMaxXFrozen = column->ContentMaxXUnfrozen = column->WorkMinX; - column->ContentMaxXHeadersUsed = column->ContentMaxXHeadersIdeal = column->WorkMinX; - - // Don't decrement auto-fit counters until container window got a chance to submit its items - if (table->HostSkipItems == false) - { - column->AutoFitQueue >>= 1; - column->CannotSkipItemsQueue >>= 1; - } - - if (visible_n < table->FreezeColumnsCount) - host_clip_rect.Min.x = ImClamp(column->MaxX + TABLE_BORDER_SIZE, host_clip_rect.Min.x, host_clip_rect.Max.x); - - offset_x += column->WidthGiven + table->CellSpacingX1 + table->CellSpacingX2 + table->CellPaddingX * 2.0f; - visible_n++; - } - - // In case the table is visible (e.g. decorations) but all columns clipped, we keep a column visible. - // Else if give no chance to a clipper-savy user to submit rows and therefore total contents height used by scrollbar. - if (has_at_least_one_column_requesting_output == false) - { - table->Columns[table->LeftMostEnabledColumn].IsRequestOutput = true; - table->Columns[table->LeftMostEnabledColumn].IsSkipItems = false; - } - - // [Part 7] Detect/store when we are hovering the unused space after the right-most column (so e.g. context menus can react on it) - // Clear Resizable flag if none of our column are actually resizable (either via an explicit _NoResize flag, either - // because of using _WidthAuto/_WidthStretch). This will hide the resizing option from the context menu. - const float unused_x1 = ImMax(table->WorkRect.Min.x, table->Columns[table->RightMostEnabledColumn].ClipRect.Max.x); - if (is_hovering_table && table->HoveredColumnBody == -1) - if (mouse_skewed_x >= unused_x1) - table->HoveredColumnBody = (ImGuiTableColumnIdx)table->ColumnsCount; - if (has_resizable == false && (table->Flags & ImGuiTableFlags_Resizable)) - table->Flags &= ~ImGuiTableFlags_Resizable; - - table->IsActiveIdAliveBeforeTable = (g.ActiveIdIsAlive != 0); - - // [Part 8] Lock actual OuterRect/WorkRect right-most position. - // This is done late to handle the case of fixed-columns tables not claiming more widths that they need. - // Because of this we are careful with uses of WorkRect and InnerClipRect before this point. - if (table->RightMostStretchedColumn != -1) - table->Flags &= ~ImGuiTableFlags_NoHostExtendX; - if (table->Flags & ImGuiTableFlags_NoHostExtendX) - { - table->OuterRect.Max.x = table->WorkRect.Max.x = unused_x1; - table->InnerClipRect.Max.x = ImMin(table->InnerClipRect.Max.x, unused_x1); - } - table->InnerWindow->ParentWorkRect = table->WorkRect; - table->BorderX1 = table->InnerClipRect.Min.x + ((table->Flags & ImGuiTableFlags_BordersOuterV) ? 1.0f : 0.0f); - table->BorderX2 = table->InnerClipRect.Max.x; - - // Setup window's WorkRect.Max.y for GetContentRegionAvail(). Other values will be updated in each TableBeginCell() call. - float window_content_max_y; - if (table->Flags & ImGuiTableFlags_NoHostExtendY) - window_content_max_y = table->OuterRect.Max.y; - else - window_content_max_y = ImMax(table->InnerWindow->ContentRegionRect.Max.y, (table->Flags & ImGuiTableFlags_ScrollY) ? 0.0f : table->OuterRect.Max.y); - table->InnerWindow->WorkRect.Max.y = ImClamp(window_content_max_y - g.Style.CellPadding.y, table->InnerWindow->WorkRect.Min.y, table->InnerWindow->WorkRect.Max.y); - - // [Part 9] Allocate draw channels and setup background cliprect - TableSetupDrawChannels(table); - - // [Part 10] Hit testing on borders - if (table->Flags & ImGuiTableFlags_Resizable) - TableUpdateBorders(table); - table_instance->LastTopHeadersRowHeight = 0.0f; - table->IsLayoutLocked = true; - table->IsUsingHeaders = false; - - // Highlight header - table->HighlightColumnHeader = -1; - if (table->IsContextPopupOpen && table->ContextPopupColumn != -1 && table->InstanceInteracted == table->InstanceCurrent) - table->HighlightColumnHeader = table->ContextPopupColumn; - else if ((table->Flags & ImGuiTableFlags_HighlightHoveredColumn) && table->HoveredColumnBody != -1 && table->HoveredColumnBody != table->ColumnsCount && table->HoveredColumnBorder == -1) - if (g.ActiveId == 0 || (table->IsActiveIdInTable || g.DragDropActive)) - table->HighlightColumnHeader = table->HoveredColumnBody; - - // [Part 11] Context menu - if (TableBeginContextMenuPopup(table)) - { - TableDrawContextMenu(table); - EndPopup(); - } - - // [Part 12] Sanitize and build sort specs before we have a chance to use them for display. - // This path will only be exercised when sort specs are modified before header rows (e.g. init or visibility change) - if (table->IsSortSpecsDirty && (table->Flags & ImGuiTableFlags_Sortable)) - TableSortSpecsBuild(table); - - // [Part 13] Setup inner window decoration size (for scrolling / nav tracking to properly take account of frozen rows/columns) - if (table->FreezeColumnsRequest > 0) - table->InnerWindow->DecoInnerSizeX1 = table->Columns[table->DisplayOrderToIndex[table->FreezeColumnsRequest - 1]].MaxX - table->OuterRect.Min.x; - if (table->FreezeRowsRequest > 0) - table->InnerWindow->DecoInnerSizeY1 = table_instance->LastFrozenHeight; - table_instance->LastFrozenHeight = 0.0f; - - // Initial state - ImGuiWindow* inner_window = table->InnerWindow; - if (table->Flags & ImGuiTableFlags_NoClip) - table->DrawSplitter->SetCurrentChannel(inner_window->DrawList, TABLE_DRAW_CHANNEL_NOCLIP); - else - inner_window->DrawList->PushClipRect(inner_window->ClipRect.Min, inner_window->ClipRect.Max, false); -} - -// Process hit-testing on resizing borders. Actual size change will be applied in EndTable() -// - Set table->HoveredColumnBorder with a short delay/timer to reduce visual feedback noise. -void ImGui::TableUpdateBorders(ImGuiTable* table) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(table->Flags & ImGuiTableFlags_Resizable); - - // At this point OuterRect height may be zero or under actual final height, so we rely on temporal coherency and - // use the final height from last frame. Because this is only affecting _interaction_ with columns, it is not - // really problematic (whereas the actual visual will be displayed in EndTable() and using the current frame height). - // Actual columns highlight/render will be performed in EndTable() and not be affected. - ImGuiTableInstanceData* table_instance = TableGetInstanceData(table, table->InstanceCurrent); - const float hit_half_width = TABLE_RESIZE_SEPARATOR_HALF_THICKNESS; - const float hit_y1 = (table->FreezeRowsCount >= 1 ? table->OuterRect.Min.y : table->WorkRect.Min.y) + table->AngledHeadersHeight; - const float hit_y2_body = ImMax(table->OuterRect.Max.y, hit_y1 + table_instance->LastOuterHeight); - const float hit_y2_head = hit_y1 + table_instance->LastTopHeadersRowHeight; - - for (int order_n = 0; order_n < table->ColumnsCount; order_n++) - { - if (!IM_BITARRAY_TESTBIT(table->EnabledMaskByDisplayOrder, order_n)) - continue; - - const int column_n = table->DisplayOrderToIndex[order_n]; - ImGuiTableColumn* column = &table->Columns[column_n]; - if (column->Flags & (ImGuiTableColumnFlags_NoResize | ImGuiTableColumnFlags_NoDirectResize_)) - continue; - - // ImGuiTableFlags_NoBordersInBodyUntilResize will be honored in TableDrawBorders() - const float border_y2_hit = (table->Flags & ImGuiTableFlags_NoBordersInBody) ? hit_y2_head : hit_y2_body; - if ((table->Flags & ImGuiTableFlags_NoBordersInBody) && table->IsUsingHeaders == false) - continue; - - if (!column->IsVisibleX && table->LastResizedColumn != column_n) - continue; - - ImGuiID column_id = TableGetColumnResizeID(table, column_n, table->InstanceCurrent); - ImRect hit_rect(column->MaxX - hit_half_width, hit_y1, column->MaxX + hit_half_width, border_y2_hit); - ItemAdd(hit_rect, column_id, NULL, ImGuiItemFlags_NoNav); - //GetForegroundDrawList()->AddRect(hit_rect.Min, hit_rect.Max, IM_COL32(255, 0, 0, 100)); - - bool hovered = false, held = false; - bool pressed = ButtonBehavior(hit_rect, column_id, &hovered, &held, ImGuiButtonFlags_FlattenChildren | ImGuiButtonFlags_PressedOnClick | ImGuiButtonFlags_PressedOnDoubleClick | ImGuiButtonFlags_NoNavFocus); - if (pressed && IsMouseDoubleClicked(0)) - { - TableSetColumnWidthAutoSingle(table, column_n); - ClearActiveID(); - held = false; - } - if (held) - { - if (table->LastResizedColumn == -1) - table->ResizeLockMinContentsX2 = table->RightMostEnabledColumn != -1 ? table->Columns[table->RightMostEnabledColumn].MaxX : -FLT_MAX; - table->ResizedColumn = (ImGuiTableColumnIdx)column_n; - table->InstanceInteracted = table->InstanceCurrent; - } - if ((hovered && g.HoveredIdTimer > TABLE_RESIZE_SEPARATOR_FEEDBACK_TIMER) || held) - { - table->HoveredColumnBorder = (ImGuiTableColumnIdx)column_n; - SetMouseCursor(ImGuiMouseCursor_ResizeEW); - } - } -} - -void ImGui::EndTable() -{ - ImGuiContext& g = *GImGui; - ImGuiTable* table = g.CurrentTable; - IM_ASSERT(table != NULL && "Only call EndTable() if BeginTable() returns true!"); - - // This assert would be very useful to catch a common error... unfortunately it would probably trigger in some - // cases, and for consistency user may sometimes output empty tables (and still benefit from e.g. outer border) - //IM_ASSERT(table->IsLayoutLocked && "Table unused: never called TableNextRow(), is that the intent?"); - - // If the user never got to call TableNextRow() or TableNextColumn(), we call layout ourselves to ensure all our - // code paths are consistent (instead of just hoping that TableBegin/TableEnd will work), get borders drawn, etc. - if (!table->IsLayoutLocked) - TableUpdateLayout(table); - - const ImGuiTableFlags flags = table->Flags; - ImGuiWindow* inner_window = table->InnerWindow; - ImGuiWindow* outer_window = table->OuterWindow; - ImGuiTableTempData* temp_data = table->TempData; - IM_ASSERT(inner_window == g.CurrentWindow); - IM_ASSERT(outer_window == inner_window || outer_window == inner_window->ParentWindow); - - if (table->IsInsideRow) - TableEndRow(table); - - // Context menu in columns body - if (flags & ImGuiTableFlags_ContextMenuInBody) - if (table->HoveredColumnBody != -1 && !IsAnyItemHovered() && IsMouseReleased(ImGuiMouseButton_Right)) - TableOpenContextMenu((int)table->HoveredColumnBody); - - // Finalize table height - ImGuiTableInstanceData* table_instance = TableGetInstanceData(table, table->InstanceCurrent); - inner_window->DC.PrevLineSize = temp_data->HostBackupPrevLineSize; - inner_window->DC.CurrLineSize = temp_data->HostBackupCurrLineSize; - inner_window->DC.CursorMaxPos = temp_data->HostBackupCursorMaxPos; - const float inner_content_max_y = table->RowPosY2; - IM_ASSERT(table->RowPosY2 == inner_window->DC.CursorPos.y); - if (inner_window != outer_window) - inner_window->DC.CursorMaxPos.y = inner_content_max_y; - else if (!(flags & ImGuiTableFlags_NoHostExtendY)) - table->OuterRect.Max.y = table->InnerRect.Max.y = ImMax(table->OuterRect.Max.y, inner_content_max_y); // Patch OuterRect/InnerRect height - table->WorkRect.Max.y = ImMax(table->WorkRect.Max.y, table->OuterRect.Max.y); - table_instance->LastOuterHeight = table->OuterRect.GetHeight(); - - // Setup inner scrolling range - // FIXME: This ideally should be done earlier, in BeginTable() SetNextWindowContentSize call, just like writing to inner_window->DC.CursorMaxPos.y, - // but since the later is likely to be impossible to do we'd rather update both axises together. - if (table->Flags & ImGuiTableFlags_ScrollX) - { - const float outer_padding_for_border = (table->Flags & ImGuiTableFlags_BordersOuterV) ? TABLE_BORDER_SIZE : 0.0f; - float max_pos_x = table->InnerWindow->DC.CursorMaxPos.x; - if (table->RightMostEnabledColumn != -1) - max_pos_x = ImMax(max_pos_x, table->Columns[table->RightMostEnabledColumn].WorkMaxX + table->CellPaddingX + table->OuterPaddingX - outer_padding_for_border); - if (table->ResizedColumn != -1) - max_pos_x = ImMax(max_pos_x, table->ResizeLockMinContentsX2); - table->InnerWindow->DC.CursorMaxPos.x = max_pos_x + table->TempData->AngledheadersExtraWidth; - } - - // Pop clipping rect - if (!(flags & ImGuiTableFlags_NoClip)) - inner_window->DrawList->PopClipRect(); - inner_window->ClipRect = inner_window->DrawList->_ClipRectStack.back(); - - // Draw borders - if ((flags & ImGuiTableFlags_Borders) != 0) - TableDrawBorders(table); - -#if 0 - // Strip out dummy channel draw calls - // We have no way to prevent user submitting direct ImDrawList calls into a hidden column (but ImGui:: calls will be clipped out) - // Pros: remove draw calls which will have no effect. since they'll have zero-size cliprect they may be early out anyway. - // Cons: making it harder for users watching metrics/debugger to spot the wasted vertices. - if (table->DummyDrawChannel != (ImGuiTableColumnIdx)-1) - { - ImDrawChannel* dummy_channel = &table->DrawSplitter._Channels[table->DummyDrawChannel]; - dummy_channel->_CmdBuffer.resize(0); - dummy_channel->_IdxBuffer.resize(0); - } -#endif - - // Flatten channels and merge draw calls - ImDrawListSplitter* splitter = table->DrawSplitter; - splitter->SetCurrentChannel(inner_window->DrawList, 0); - if ((table->Flags & ImGuiTableFlags_NoClip) == 0) - TableMergeDrawChannels(table); - splitter->Merge(inner_window->DrawList); - - // Update ColumnsAutoFitWidth to get us ahead for host using our size to auto-resize without waiting for next BeginTable() - float auto_fit_width_for_fixed = 0.0f; - float auto_fit_width_for_stretched = 0.0f; - float auto_fit_width_for_stretched_min = 0.0f; - for (int column_n = 0; column_n < table->ColumnsCount; column_n++) - if (IM_BITARRAY_TESTBIT(table->EnabledMaskByIndex, column_n)) - { - ImGuiTableColumn* column = &table->Columns[column_n]; - float column_width_request = ((column->Flags & ImGuiTableColumnFlags_WidthFixed) && !(column->Flags & ImGuiTableColumnFlags_NoResize)) ? column->WidthRequest : TableGetColumnWidthAuto(table, column); - if (column->Flags & ImGuiTableColumnFlags_WidthFixed) - auto_fit_width_for_fixed += column_width_request; - else - auto_fit_width_for_stretched += column_width_request; - if ((column->Flags & ImGuiTableColumnFlags_WidthStretch) && (column->Flags & ImGuiTableColumnFlags_NoResize) != 0) - auto_fit_width_for_stretched_min = ImMax(auto_fit_width_for_stretched_min, column_width_request / (column->StretchWeight / table->ColumnsStretchSumWeights)); - } - const float width_spacings = (table->OuterPaddingX * 2.0f) + (table->CellSpacingX1 + table->CellSpacingX2) * (table->ColumnsEnabledCount - 1); - table->ColumnsAutoFitWidth = width_spacings + (table->CellPaddingX * 2.0f) * table->ColumnsEnabledCount + auto_fit_width_for_fixed + ImMax(auto_fit_width_for_stretched, auto_fit_width_for_stretched_min); - - // Update scroll - if ((table->Flags & ImGuiTableFlags_ScrollX) == 0 && inner_window != outer_window) - { - inner_window->Scroll.x = 0.0f; - } - else if (table->LastResizedColumn != -1 && table->ResizedColumn == -1 && inner_window->ScrollbarX && table->InstanceInteracted == table->InstanceCurrent) - { - // When releasing a column being resized, scroll to keep the resulting column in sight - const float neighbor_width_to_keep_visible = table->MinColumnWidth + table->CellPaddingX * 2.0f; - ImGuiTableColumn* column = &table->Columns[table->LastResizedColumn]; - if (column->MaxX < table->InnerClipRect.Min.x) - SetScrollFromPosX(inner_window, column->MaxX - inner_window->Pos.x - neighbor_width_to_keep_visible, 1.0f); - else if (column->MaxX > table->InnerClipRect.Max.x) - SetScrollFromPosX(inner_window, column->MaxX - inner_window->Pos.x + neighbor_width_to_keep_visible, 1.0f); - } - - // Apply resizing/dragging at the end of the frame - if (table->ResizedColumn != -1 && table->InstanceCurrent == table->InstanceInteracted) - { - ImGuiTableColumn* column = &table->Columns[table->ResizedColumn]; - const float new_x2 = (g.IO.MousePos.x - g.ActiveIdClickOffset.x + TABLE_RESIZE_SEPARATOR_HALF_THICKNESS); - const float new_width = ImTrunc(new_x2 - column->MinX - table->CellSpacingX1 - table->CellPaddingX * 2.0f); - table->ResizedColumnNextWidth = new_width; - } - - table->IsActiveIdInTable = (g.ActiveIdIsAlive != 0 && table->IsActiveIdAliveBeforeTable == false); - - // Pop from id stack - IM_ASSERT_USER_ERROR(inner_window->IDStack.back() == table_instance->TableInstanceID, "Mismatching PushID/PopID!"); - IM_ASSERT_USER_ERROR(outer_window->DC.ItemWidthStack.Size >= temp_data->HostBackupItemWidthStackSize, "Too many PopItemWidth!"); - if (table->InstanceCurrent > 0) - PopID(); - PopID(); - - // Restore window data that we modified - const ImVec2 backup_outer_max_pos = outer_window->DC.CursorMaxPos; - inner_window->WorkRect = temp_data->HostBackupWorkRect; - inner_window->ParentWorkRect = temp_data->HostBackupParentWorkRect; - inner_window->SkipItems = table->HostSkipItems; - outer_window->DC.CursorPos = table->OuterRect.Min; - outer_window->DC.ItemWidth = temp_data->HostBackupItemWidth; - outer_window->DC.ItemWidthStack.Size = temp_data->HostBackupItemWidthStackSize; - outer_window->DC.ColumnsOffset = temp_data->HostBackupColumnsOffset; - - // Layout in outer window - // (FIXME: To allow auto-fit and allow desirable effect of SameLine() we dissociate 'used' vs 'ideal' size by overriding - // CursorPosPrevLine and CursorMaxPos manually. That should be a more general layout feature, see same problem e.g. #3414) - if (inner_window != outer_window) - { - EndChild(); - } - else - { - ItemSize(table->OuterRect.GetSize()); - ItemAdd(table->OuterRect, 0); - } - - // Override declared contents width/height to enable auto-resize while not needlessly adding a scrollbar - if (table->Flags & ImGuiTableFlags_NoHostExtendX) - { - // FIXME-TABLE: Could we remove this section? - // ColumnsAutoFitWidth may be one frame ahead here since for Fixed+NoResize is calculated from latest contents - IM_ASSERT((table->Flags & ImGuiTableFlags_ScrollX) == 0); - outer_window->DC.CursorMaxPos.x = ImMax(backup_outer_max_pos.x, table->OuterRect.Min.x + table->ColumnsAutoFitWidth); - } - else if (temp_data->UserOuterSize.x <= 0.0f) - { - const float decoration_size = table->TempData->AngledheadersExtraWidth + ((table->Flags & ImGuiTableFlags_ScrollX) ? inner_window->ScrollbarSizes.x : 0.0f); - outer_window->DC.IdealMaxPos.x = ImMax(outer_window->DC.IdealMaxPos.x, table->OuterRect.Min.x + table->ColumnsAutoFitWidth + decoration_size - temp_data->UserOuterSize.x); - outer_window->DC.CursorMaxPos.x = ImMax(backup_outer_max_pos.x, ImMin(table->OuterRect.Max.x, table->OuterRect.Min.x + table->ColumnsAutoFitWidth)); - } - else - { - outer_window->DC.CursorMaxPos.x = ImMax(backup_outer_max_pos.x, table->OuterRect.Max.x); - } - if (temp_data->UserOuterSize.y <= 0.0f) - { - const float decoration_size = (table->Flags & ImGuiTableFlags_ScrollY) ? inner_window->ScrollbarSizes.y : 0.0f; - outer_window->DC.IdealMaxPos.y = ImMax(outer_window->DC.IdealMaxPos.y, inner_content_max_y + decoration_size - temp_data->UserOuterSize.y); - outer_window->DC.CursorMaxPos.y = ImMax(backup_outer_max_pos.y, ImMin(table->OuterRect.Max.y, inner_content_max_y)); - } - else - { - // OuterRect.Max.y may already have been pushed downward from the initial value (unless ImGuiTableFlags_NoHostExtendY is set) - outer_window->DC.CursorMaxPos.y = ImMax(backup_outer_max_pos.y, table->OuterRect.Max.y); - } - - // Save settings - if (table->IsSettingsDirty) - TableSaveSettings(table); - table->IsInitializing = false; - - // Clear or restore current table, if any - IM_ASSERT(g.CurrentWindow == outer_window && g.CurrentTable == table); - IM_ASSERT(g.TablesTempDataStacked > 0); - temp_data = (--g.TablesTempDataStacked > 0) ? &g.TablesTempData[g.TablesTempDataStacked - 1] : NULL; - g.CurrentTable = temp_data ? g.Tables.GetByIndex(temp_data->TableIndex) : NULL; - if (g.CurrentTable) - { - g.CurrentTable->TempData = temp_data; - g.CurrentTable->DrawSplitter = &temp_data->DrawSplitter; - } - outer_window->DC.CurrentTableIdx = g.CurrentTable ? g.Tables.GetIndex(g.CurrentTable) : -1; - NavUpdateCurrentWindowIsScrollPushableX(); -} - -// See "COLUMNS SIZING POLICIES" comments at the top of this file -// If (init_width_or_weight <= 0.0f) it is ignored -void ImGui::TableSetupColumn(const char* label, ImGuiTableColumnFlags flags, float init_width_or_weight, ImGuiID user_id) -{ - ImGuiContext& g = *GImGui; - ImGuiTable* table = g.CurrentTable; - IM_ASSERT(table != NULL && "Need to call TableSetupColumn() after BeginTable()!"); - IM_ASSERT(table->IsLayoutLocked == false && "Need to call call TableSetupColumn() before first row!"); - IM_ASSERT((flags & ImGuiTableColumnFlags_StatusMask_) == 0 && "Illegal to pass StatusMask values to TableSetupColumn()"); - if (table->DeclColumnsCount >= table->ColumnsCount) - { - IM_ASSERT_USER_ERROR(table->DeclColumnsCount < table->ColumnsCount, "Called TableSetupColumn() too many times!"); - return; - } - - ImGuiTableColumn* column = &table->Columns[table->DeclColumnsCount]; - table->DeclColumnsCount++; - - // Assert when passing a width or weight if policy is entirely left to default, to avoid storing width into weight and vice-versa. - // Give a grace to users of ImGuiTableFlags_ScrollX. - if (table->IsDefaultSizingPolicy && (flags & ImGuiTableColumnFlags_WidthMask_) == 0 && (flags & ImGuiTableFlags_ScrollX) == 0) - IM_ASSERT(init_width_or_weight <= 0.0f && "Can only specify width/weight if sizing policy is set explicitly in either Table or Column."); - - // When passing a width automatically enforce WidthFixed policy - // (whereas TableSetupColumnFlags would default to WidthAuto if table is not Resizable) - if ((flags & ImGuiTableColumnFlags_WidthMask_) == 0 && init_width_or_weight > 0.0f) - if ((table->Flags & ImGuiTableFlags_SizingMask_) == ImGuiTableFlags_SizingFixedFit || (table->Flags & ImGuiTableFlags_SizingMask_) == ImGuiTableFlags_SizingFixedSame) - flags |= ImGuiTableColumnFlags_WidthFixed; - if (flags & ImGuiTableColumnFlags_AngledHeader) - { - flags |= ImGuiTableColumnFlags_NoHeaderLabel; - table->AngledHeadersCount++; - } - - TableSetupColumnFlags(table, column, flags); - column->UserID = user_id; - flags = column->Flags; - - // Initialize defaults - column->InitStretchWeightOrWidth = init_width_or_weight; - if (table->IsInitializing) - { - // Init width or weight - if (column->WidthRequest < 0.0f && column->StretchWeight < 0.0f) - { - if ((flags & ImGuiTableColumnFlags_WidthFixed) && init_width_or_weight > 0.0f) - column->WidthRequest = init_width_or_weight; - if (flags & ImGuiTableColumnFlags_WidthStretch) - column->StretchWeight = (init_width_or_weight > 0.0f) ? init_width_or_weight : -1.0f; - - // Disable auto-fit if an explicit width/weight has been specified - if (init_width_or_weight > 0.0f) - column->AutoFitQueue = 0x00; - } - - // Init default visibility/sort state - if ((flags & ImGuiTableColumnFlags_DefaultHide) && (table->SettingsLoadedFlags & ImGuiTableFlags_Hideable) == 0) - column->IsUserEnabled = column->IsUserEnabledNextFrame = false; - if (flags & ImGuiTableColumnFlags_DefaultSort && (table->SettingsLoadedFlags & ImGuiTableFlags_Sortable) == 0) - { - column->SortOrder = 0; // Multiple columns using _DefaultSort will be reassigned unique SortOrder values when building the sort specs. - column->SortDirection = (column->Flags & ImGuiTableColumnFlags_PreferSortDescending) ? (ImS8)ImGuiSortDirection_Descending : (ImU8)(ImGuiSortDirection_Ascending); - } - } - - // Store name (append with zero-terminator in contiguous buffer) - column->NameOffset = -1; - if (label != NULL && label[0] != 0) - { - column->NameOffset = (ImS16)table->ColumnsNames.size(); - table->ColumnsNames.append(label, label + strlen(label) + 1); - } -} - -// [Public] -void ImGui::TableSetupScrollFreeze(int columns, int rows) -{ - ImGuiContext& g = *GImGui; - ImGuiTable* table = g.CurrentTable; - IM_ASSERT(table != NULL && "Need to call TableSetupColumn() after BeginTable()!"); - IM_ASSERT(table->IsLayoutLocked == false && "Need to call TableSetupColumn() before first row!"); - IM_ASSERT(columns >= 0 && columns < IMGUI_TABLE_MAX_COLUMNS); - IM_ASSERT(rows >= 0 && rows < 128); // Arbitrary limit - - table->FreezeColumnsRequest = (table->Flags & ImGuiTableFlags_ScrollX) ? (ImGuiTableColumnIdx)ImMin(columns, table->ColumnsCount) : 0; - table->FreezeColumnsCount = (table->InnerWindow->Scroll.x != 0.0f) ? table->FreezeColumnsRequest : 0; - table->FreezeRowsRequest = (table->Flags & ImGuiTableFlags_ScrollY) ? (ImGuiTableColumnIdx)rows : 0; - table->FreezeRowsCount = (table->InnerWindow->Scroll.y != 0.0f) ? table->FreezeRowsRequest : 0; - table->IsUnfrozenRows = (table->FreezeRowsCount == 0); // Make sure this is set before TableUpdateLayout() so ImGuiListClipper can benefit from it.b - - // Ensure frozen columns are ordered in their section. We still allow multiple frozen columns to be reordered. - // FIXME-TABLE: This work for preserving 2143 into 21|43. How about 4321 turning into 21|43? (preserve relative order in each section) - for (int column_n = 0; column_n < table->FreezeColumnsRequest; column_n++) - { - int order_n = table->DisplayOrderToIndex[column_n]; - if (order_n != column_n && order_n >= table->FreezeColumnsRequest) - { - ImSwap(table->Columns[table->DisplayOrderToIndex[order_n]].DisplayOrder, table->Columns[table->DisplayOrderToIndex[column_n]].DisplayOrder); - ImSwap(table->DisplayOrderToIndex[order_n], table->DisplayOrderToIndex[column_n]); - } - } -} - -//----------------------------------------------------------------------------- -// [SECTION] Tables: Simple accessors -//----------------------------------------------------------------------------- -// - TableGetColumnCount() -// - TableGetColumnName() -// - TableGetColumnName() [Internal] -// - TableSetColumnEnabled() -// - TableGetColumnFlags() -// - TableGetCellBgRect() [Internal] -// - TableGetColumnResizeID() [Internal] -// - TableGetHoveredColumn() [Internal] -// - TableGetHoveredRow() [Internal] -// - TableSetBgColor() -//----------------------------------------------------------------------------- - -int ImGui::TableGetColumnCount() -{ - ImGuiContext& g = *GImGui; - ImGuiTable* table = g.CurrentTable; - return table ? table->ColumnsCount : 0; -} - -const char* ImGui::TableGetColumnName(int column_n) -{ - ImGuiContext& g = *GImGui; - ImGuiTable* table = g.CurrentTable; - if (!table) - return NULL; - if (column_n < 0) - column_n = table->CurrentColumn; - return TableGetColumnName(table, column_n); -} - -const char* ImGui::TableGetColumnName(const ImGuiTable* table, int column_n) -{ - if (table->IsLayoutLocked == false && column_n >= table->DeclColumnsCount) - return ""; // NameOffset is invalid at this point - const ImGuiTableColumn* column = &table->Columns[column_n]; - if (column->NameOffset == -1) - return ""; - return &table->ColumnsNames.Buf[column->NameOffset]; -} - -// Change user accessible enabled/disabled state of a column (often perceived as "showing/hiding" from users point of view) -// Note that end-user can use the context menu to change this themselves (right-click in headers, or right-click in columns body with ImGuiTableFlags_ContextMenuInBody) -// - Require table to have the ImGuiTableFlags_Hideable flag because we are manipulating user accessible state. -// - Request will be applied during next layout, which happens on the first call to TableNextRow() after BeginTable(). -// - For the getter you can test (TableGetColumnFlags() & ImGuiTableColumnFlags_IsEnabled) != 0. -// - Alternative: the ImGuiTableColumnFlags_Disabled is an overriding/master disable flag which will also hide the column from context menu. -void ImGui::TableSetColumnEnabled(int column_n, bool enabled) -{ - ImGuiContext& g = *GImGui; - ImGuiTable* table = g.CurrentTable; - IM_ASSERT(table != NULL); - if (!table) - return; - IM_ASSERT(table->Flags & ImGuiTableFlags_Hideable); // See comments above - if (column_n < 0) - column_n = table->CurrentColumn; - IM_ASSERT(column_n >= 0 && column_n < table->ColumnsCount); - ImGuiTableColumn* column = &table->Columns[column_n]; - column->IsUserEnabledNextFrame = enabled; -} - -// We allow querying for an extra column in order to poll the IsHovered state of the right-most section -ImGuiTableColumnFlags ImGui::TableGetColumnFlags(int column_n) -{ - ImGuiContext& g = *GImGui; - ImGuiTable* table = g.CurrentTable; - if (!table) - return ImGuiTableColumnFlags_None; - if (column_n < 0) - column_n = table->CurrentColumn; - if (column_n == table->ColumnsCount) - return (table->HoveredColumnBody == column_n) ? ImGuiTableColumnFlags_IsHovered : ImGuiTableColumnFlags_None; - return table->Columns[column_n].Flags; -} - -// Return the cell rectangle based on currently known height. -// - Important: we generally don't know our row height until the end of the row, so Max.y will be incorrect in many situations. -// The only case where this is correct is if we provided a min_row_height to TableNextRow() and don't go below it, or in TableEndRow() when we locked that height. -// - Important: if ImGuiTableFlags_PadOuterX is set but ImGuiTableFlags_PadInnerX is not set, the outer-most left and right -// columns report a small offset so their CellBgRect can extend up to the outer border. -// FIXME: But the rendering code in TableEndRow() nullifies that with clamping required for scrolling. -ImRect ImGui::TableGetCellBgRect(const ImGuiTable* table, int column_n) -{ - const ImGuiTableColumn* column = &table->Columns[column_n]; - float x1 = column->MinX; - float x2 = column->MaxX; - //if (column->PrevEnabledColumn == -1) - // x1 -= table->OuterPaddingX; - //if (column->NextEnabledColumn == -1) - // x2 += table->OuterPaddingX; - x1 = ImMax(x1, table->WorkRect.Min.x); - x2 = ImMin(x2, table->WorkRect.Max.x); - return ImRect(x1, table->RowPosY1, x2, table->RowPosY2); -} - -// Return the resizing ID for the right-side of the given column. -ImGuiID ImGui::TableGetColumnResizeID(ImGuiTable* table, int column_n, int instance_no) -{ - IM_ASSERT(column_n >= 0 && column_n < table->ColumnsCount); - ImGuiID instance_id = TableGetInstanceID(table, instance_no); - return instance_id + 1 + column_n; // FIXME: #6140: still not ideal -} - -// Return -1 when table is not hovered. return columns_count if hovering the unused space at the right of the right-most visible column. -int ImGui::TableGetHoveredColumn() -{ - ImGuiContext& g = *GImGui; - ImGuiTable* table = g.CurrentTable; - if (!table) - return -1; - return (int)table->HoveredColumnBody; -} - -// Return -1 when table is not hovered. Return maxrow+1 if in table but below last submitted row. -// *IMPORTANT* Unlike TableGetHoveredColumn(), this has a one frame latency in updating the value. -// This difference with is the reason why this is not public yet. -int ImGui::TableGetHoveredRow() -{ - ImGuiContext& g = *GImGui; - ImGuiTable* table = g.CurrentTable; - if (!table) - return -1; - ImGuiTableInstanceData* table_instance = TableGetInstanceData(table, table->InstanceCurrent); - return (int)table_instance->HoveredRowLast; -} - -void ImGui::TableSetBgColor(ImGuiTableBgTarget target, ImU32 color, int column_n) -{ - ImGuiContext& g = *GImGui; - ImGuiTable* table = g.CurrentTable; - IM_ASSERT(target != ImGuiTableBgTarget_None); - - if (color == IM_COL32_DISABLE) - color = 0; - - // We cannot draw neither the cell or row background immediately as we don't know the row height at this point in time. - switch (target) - { - case ImGuiTableBgTarget_CellBg: - { - if (table->RowPosY1 > table->InnerClipRect.Max.y) // Discard - return; - if (column_n == -1) - column_n = table->CurrentColumn; - if (!IM_BITARRAY_TESTBIT(table->VisibleMaskByIndex, column_n)) - return; - if (table->RowCellDataCurrent < 0 || table->RowCellData[table->RowCellDataCurrent].Column != column_n) - table->RowCellDataCurrent++; - ImGuiTableCellData* cell_data = &table->RowCellData[table->RowCellDataCurrent]; - cell_data->BgColor = color; - cell_data->Column = (ImGuiTableColumnIdx)column_n; - break; - } - case ImGuiTableBgTarget_RowBg0: - case ImGuiTableBgTarget_RowBg1: - { - if (table->RowPosY1 > table->InnerClipRect.Max.y) // Discard - return; - IM_ASSERT(column_n == -1); - int bg_idx = (target == ImGuiTableBgTarget_RowBg1) ? 1 : 0; - table->RowBgColor[bg_idx] = color; - break; - } - default: - IM_ASSERT(0); - } -} - -//------------------------------------------------------------------------- -// [SECTION] Tables: Row changes -//------------------------------------------------------------------------- -// - TableGetRowIndex() -// - TableNextRow() -// - TableBeginRow() [Internal] -// - TableEndRow() [Internal] -//------------------------------------------------------------------------- - -// [Public] Note: for row coloring we use ->RowBgColorCounter which is the same value without counting header rows -int ImGui::TableGetRowIndex() -{ - ImGuiContext& g = *GImGui; - ImGuiTable* table = g.CurrentTable; - if (!table) - return 0; - return table->CurrentRow; -} - -// [Public] Starts into the first cell of a new row -void ImGui::TableNextRow(ImGuiTableRowFlags row_flags, float row_min_height) -{ - ImGuiContext& g = *GImGui; - ImGuiTable* table = g.CurrentTable; - - if (!table->IsLayoutLocked) - TableUpdateLayout(table); - if (table->IsInsideRow) - TableEndRow(table); - - table->LastRowFlags = table->RowFlags; - table->RowFlags = row_flags; - table->RowCellPaddingY = g.Style.CellPadding.y; - table->RowMinHeight = row_min_height; - TableBeginRow(table); - - // We honor min_row_height requested by user, but cannot guarantee per-row maximum height, - // because that would essentially require a unique clipping rectangle per-cell. - table->RowPosY2 += table->RowCellPaddingY * 2.0f; - table->RowPosY2 = ImMax(table->RowPosY2, table->RowPosY1 + row_min_height); - - // Disable output until user calls TableNextColumn() - table->InnerWindow->SkipItems = true; -} - -// [Internal] Only called by TableNextRow() -void ImGui::TableBeginRow(ImGuiTable* table) -{ - ImGuiWindow* window = table->InnerWindow; - IM_ASSERT(!table->IsInsideRow); - - // New row - table->CurrentRow++; - table->CurrentColumn = -1; - table->RowBgColor[0] = table->RowBgColor[1] = IM_COL32_DISABLE; - table->RowCellDataCurrent = -1; - table->IsInsideRow = true; - - // Begin frozen rows - float next_y1 = table->RowPosY2; - if (table->CurrentRow == 0 && table->FreezeRowsCount > 0) - next_y1 = window->DC.CursorPos.y = table->OuterRect.Min.y; - - table->RowPosY1 = table->RowPosY2 = next_y1; - table->RowTextBaseline = 0.0f; - table->RowIndentOffsetX = window->DC.Indent.x - table->HostIndentX; // Lock indent - - window->DC.PrevLineTextBaseOffset = 0.0f; - window->DC.CursorPosPrevLine = ImVec2(window->DC.CursorPos.x, window->DC.CursorPos.y + table->RowCellPaddingY); // This allows users to call SameLine() to share LineSize between columns. - window->DC.PrevLineSize = window->DC.CurrLineSize = ImVec2(0.0f, 0.0f); // This allows users to call SameLine() to share LineSize between columns, and to call it from first column too. - window->DC.IsSameLine = window->DC.IsSetPos = false; - window->DC.CursorMaxPos.y = next_y1; - - // Making the header BG color non-transparent will allow us to overlay it multiple times when handling smooth dragging. - if (table->RowFlags & ImGuiTableRowFlags_Headers) - { - TableSetBgColor(ImGuiTableBgTarget_RowBg0, GetColorU32(ImGuiCol_TableHeaderBg)); - if (table->CurrentRow == 0) - table->IsUsingHeaders = true; - } -} - -// [Internal] Called by TableNextRow() -void ImGui::TableEndRow(ImGuiTable* table) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - IM_ASSERT(window == table->InnerWindow); - IM_ASSERT(table->IsInsideRow); - - if (table->CurrentColumn != -1) - TableEndCell(table); - - // Logging - if (g.LogEnabled) - LogRenderedText(NULL, "|"); - - // Position cursor at the bottom of our row so it can be used for e.g. clipping calculation. However it is - // likely that the next call to TableBeginCell() will reposition the cursor to take account of vertical padding. - window->DC.CursorPos.y = table->RowPosY2; - - // Row background fill - const float bg_y1 = table->RowPosY1; - const float bg_y2 = table->RowPosY2; - const bool unfreeze_rows_actual = (table->CurrentRow + 1 == table->FreezeRowsCount); - const bool unfreeze_rows_request = (table->CurrentRow + 1 == table->FreezeRowsRequest); - ImGuiTableInstanceData* table_instance = TableGetInstanceData(table, table->InstanceCurrent); - if ((table->RowFlags & ImGuiTableRowFlags_Headers) && (table->CurrentRow == 0 || (table->LastRowFlags & ImGuiTableRowFlags_Headers))) - table_instance->LastTopHeadersRowHeight += bg_y2 - bg_y1; - - const bool is_visible = (bg_y2 >= table->InnerClipRect.Min.y && bg_y1 <= table->InnerClipRect.Max.y); - if (is_visible) - { - // Update data for TableGetHoveredRow() - if (table->HoveredColumnBody != -1 && g.IO.MousePos.y >= bg_y1 && g.IO.MousePos.y < bg_y2) - table_instance->HoveredRowNext = table->CurrentRow; - - // Decide of background color for the row - ImU32 bg_col0 = 0; - ImU32 bg_col1 = 0; - if (table->RowBgColor[0] != IM_COL32_DISABLE) - bg_col0 = table->RowBgColor[0]; - else if (table->Flags & ImGuiTableFlags_RowBg) - bg_col0 = GetColorU32((table->RowBgColorCounter & 1) ? ImGuiCol_TableRowBgAlt : ImGuiCol_TableRowBg); - if (table->RowBgColor[1] != IM_COL32_DISABLE) - bg_col1 = table->RowBgColor[1]; - - // Decide of top border color - ImU32 top_border_col = 0; - const float border_size = TABLE_BORDER_SIZE; - if (table->CurrentRow > 0 && (table->Flags & ImGuiTableFlags_BordersInnerH)) - top_border_col = (table->LastRowFlags & ImGuiTableRowFlags_Headers) ? table->BorderColorStrong : table->BorderColorLight; - - const bool draw_cell_bg_color = table->RowCellDataCurrent >= 0; - const bool draw_strong_bottom_border = unfreeze_rows_actual; - if ((bg_col0 | bg_col1 | top_border_col) != 0 || draw_strong_bottom_border || draw_cell_bg_color) - { - // In theory we could call SetWindowClipRectBeforeSetChannel() but since we know TableEndRow() is - // always followed by a change of clipping rectangle we perform the smallest overwrite possible here. - if ((table->Flags & ImGuiTableFlags_NoClip) == 0) - window->DrawList->_CmdHeader.ClipRect = table->Bg0ClipRectForDrawCmd.ToVec4(); - table->DrawSplitter->SetCurrentChannel(window->DrawList, TABLE_DRAW_CHANNEL_BG0); - } - - // Draw row background - // We soft/cpu clip this so all backgrounds and borders can share the same clipping rectangle - if (bg_col0 || bg_col1) - { - ImRect row_rect(table->WorkRect.Min.x, bg_y1, table->WorkRect.Max.x, bg_y2); - row_rect.ClipWith(table->BgClipRect); - if (bg_col0 != 0 && row_rect.Min.y < row_rect.Max.y) - window->DrawList->AddRectFilled(row_rect.Min, row_rect.Max, bg_col0); - if (bg_col1 != 0 && row_rect.Min.y < row_rect.Max.y) - window->DrawList->AddRectFilled(row_rect.Min, row_rect.Max, bg_col1); - } - - // Draw cell background color - if (draw_cell_bg_color) - { - ImGuiTableCellData* cell_data_end = &table->RowCellData[table->RowCellDataCurrent]; - for (ImGuiTableCellData* cell_data = &table->RowCellData[0]; cell_data <= cell_data_end; cell_data++) - { - // As we render the BG here we need to clip things (for layout we would not) - // FIXME: This cancels the OuterPadding addition done by TableGetCellBgRect(), need to keep it while rendering correctly while scrolling. - const ImGuiTableColumn* column = &table->Columns[cell_data->Column]; - ImRect cell_bg_rect = TableGetCellBgRect(table, cell_data->Column); - cell_bg_rect.ClipWith(table->BgClipRect); - cell_bg_rect.Min.x = ImMax(cell_bg_rect.Min.x, column->ClipRect.Min.x); // So that first column after frozen one gets clipped when scrolling - cell_bg_rect.Max.x = ImMin(cell_bg_rect.Max.x, column->MaxX); - window->DrawList->AddRectFilled(cell_bg_rect.Min, cell_bg_rect.Max, cell_data->BgColor); - } - } - - // Draw top border - if (top_border_col && bg_y1 >= table->BgClipRect.Min.y && bg_y1 < table->BgClipRect.Max.y) - window->DrawList->AddLine(ImVec2(table->BorderX1, bg_y1), ImVec2(table->BorderX2, bg_y1), top_border_col, border_size); - - // Draw bottom border at the row unfreezing mark (always strong) - if (draw_strong_bottom_border && bg_y2 >= table->BgClipRect.Min.y && bg_y2 < table->BgClipRect.Max.y) - window->DrawList->AddLine(ImVec2(table->BorderX1, bg_y2), ImVec2(table->BorderX2, bg_y2), table->BorderColorStrong, border_size); - } - - // End frozen rows (when we are past the last frozen row line, teleport cursor and alter clipping rectangle) - // We need to do that in TableEndRow() instead of TableBeginRow() so the list clipper can mark end of row and - // get the new cursor position. - if (unfreeze_rows_request) - for (int column_n = 0; column_n < table->ColumnsCount; column_n++) - table->Columns[column_n].NavLayerCurrent = ImGuiNavLayer_Main; - if (unfreeze_rows_actual) - { - IM_ASSERT(table->IsUnfrozenRows == false); - const float y0 = ImMax(table->RowPosY2 + 1, window->InnerClipRect.Min.y); - table->IsUnfrozenRows = true; - table_instance->LastFrozenHeight = y0 - table->OuterRect.Min.y; - - // BgClipRect starts as table->InnerClipRect, reduce it now and make BgClipRectForDrawCmd == BgClipRect - table->BgClipRect.Min.y = table->Bg2ClipRectForDrawCmd.Min.y = ImMin(y0, window->InnerClipRect.Max.y); - table->BgClipRect.Max.y = table->Bg2ClipRectForDrawCmd.Max.y = window->InnerClipRect.Max.y; - table->Bg2DrawChannelCurrent = table->Bg2DrawChannelUnfrozen; - IM_ASSERT(table->Bg2ClipRectForDrawCmd.Min.y <= table->Bg2ClipRectForDrawCmd.Max.y); - - float row_height = table->RowPosY2 - table->RowPosY1; - table->RowPosY2 = window->DC.CursorPos.y = table->WorkRect.Min.y + table->RowPosY2 - table->OuterRect.Min.y; - table->RowPosY1 = table->RowPosY2 - row_height; - for (int column_n = 0; column_n < table->ColumnsCount; column_n++) - { - ImGuiTableColumn* column = &table->Columns[column_n]; - column->DrawChannelCurrent = column->DrawChannelUnfrozen; - column->ClipRect.Min.y = table->Bg2ClipRectForDrawCmd.Min.y; - } - - // Update cliprect ahead of TableBeginCell() so clipper can access to new ClipRect->Min.y - SetWindowClipRectBeforeSetChannel(window, table->Columns[0].ClipRect); - table->DrawSplitter->SetCurrentChannel(window->DrawList, table->Columns[0].DrawChannelCurrent); - } - - if (!(table->RowFlags & ImGuiTableRowFlags_Headers)) - table->RowBgColorCounter++; - table->IsInsideRow = false; -} - -//------------------------------------------------------------------------- -// [SECTION] Tables: Columns changes -//------------------------------------------------------------------------- -// - TableGetColumnIndex() -// - TableSetColumnIndex() -// - TableNextColumn() -// - TableBeginCell() [Internal] -// - TableEndCell() [Internal] -//------------------------------------------------------------------------- - -int ImGui::TableGetColumnIndex() -{ - ImGuiContext& g = *GImGui; - ImGuiTable* table = g.CurrentTable; - if (!table) - return 0; - return table->CurrentColumn; -} - -// [Public] Append into a specific column -bool ImGui::TableSetColumnIndex(int column_n) -{ - ImGuiContext& g = *GImGui; - ImGuiTable* table = g.CurrentTable; - if (!table) - return false; - - if (table->CurrentColumn != column_n) - { - if (table->CurrentColumn != -1) - TableEndCell(table); - IM_ASSERT(column_n >= 0 && table->ColumnsCount); - TableBeginCell(table, column_n); - } - - // Return whether the column is visible. User may choose to skip submitting items based on this return value, - // however they shouldn't skip submitting for columns that may have the tallest contribution to row height. - return table->Columns[column_n].IsRequestOutput; -} - -// [Public] Append into the next column, wrap and create a new row when already on last column -bool ImGui::TableNextColumn() -{ - ImGuiContext& g = *GImGui; - ImGuiTable* table = g.CurrentTable; - if (!table) - return false; - - if (table->IsInsideRow && table->CurrentColumn + 1 < table->ColumnsCount) - { - if (table->CurrentColumn != -1) - TableEndCell(table); - TableBeginCell(table, table->CurrentColumn + 1); - } - else - { - TableNextRow(); - TableBeginCell(table, 0); - } - - // Return whether the column is visible. User may choose to skip submitting items based on this return value, - // however they shouldn't skip submitting for columns that may have the tallest contribution to row height. - return table->Columns[table->CurrentColumn].IsRequestOutput; -} - - -// [Internal] Called by TableSetColumnIndex()/TableNextColumn() -// This is called very frequently, so we need to be mindful of unnecessary overhead. -// FIXME-TABLE FIXME-OPT: Could probably shortcut some things for non-active or clipped columns. -void ImGui::TableBeginCell(ImGuiTable* table, int column_n) -{ - ImGuiContext& g = *GImGui; - ImGuiTableColumn* column = &table->Columns[column_n]; - ImGuiWindow* window = table->InnerWindow; - table->CurrentColumn = column_n; - - // Start position is roughly ~~ CellRect.Min + CellPadding + Indent - float start_x = column->WorkMinX; - if (column->Flags & ImGuiTableColumnFlags_IndentEnable) - start_x += table->RowIndentOffsetX; // ~~ += window.DC.Indent.x - table->HostIndentX, except we locked it for the row. - - window->DC.CursorPos.x = start_x; - window->DC.CursorPos.y = table->RowPosY1 + table->RowCellPaddingY; - window->DC.CursorMaxPos.x = window->DC.CursorPos.x; - window->DC.ColumnsOffset.x = start_x - window->Pos.x - window->DC.Indent.x; // FIXME-WORKRECT - window->DC.CursorPosPrevLine.x = window->DC.CursorPos.x; // PrevLine.y is preserved. This allows users to call SameLine() to share LineSize between columns. - window->DC.CurrLineTextBaseOffset = table->RowTextBaseline; - window->DC.NavLayerCurrent = (ImGuiNavLayer)column->NavLayerCurrent; - - // Note how WorkRect.Max.y is only set once during layout - window->WorkRect.Min.y = window->DC.CursorPos.y; - window->WorkRect.Min.x = column->WorkMinX; - window->WorkRect.Max.x = column->WorkMaxX; - window->DC.ItemWidth = column->ItemWidth; - - window->SkipItems = column->IsSkipItems; - if (column->IsSkipItems) - { - g.LastItemData.ID = 0; - g.LastItemData.StatusFlags = 0; - } - - if (table->Flags & ImGuiTableFlags_NoClip) - { - // FIXME: if we end up drawing all borders/bg in EndTable, could remove this and just assert that channel hasn't changed. - table->DrawSplitter->SetCurrentChannel(window->DrawList, TABLE_DRAW_CHANNEL_NOCLIP); - //IM_ASSERT(table->DrawSplitter._Current == TABLE_DRAW_CHANNEL_NOCLIP); - } - else - { - // FIXME-TABLE: Could avoid this if draw channel is dummy channel? - SetWindowClipRectBeforeSetChannel(window, column->ClipRect); - table->DrawSplitter->SetCurrentChannel(window->DrawList, column->DrawChannelCurrent); - } - - // Logging - if (g.LogEnabled && !column->IsSkipItems) - { - LogRenderedText(&window->DC.CursorPos, "|"); - g.LogLinePosY = FLT_MAX; - } -} - -// [Internal] Called by TableNextRow()/TableSetColumnIndex()/TableNextColumn() -void ImGui::TableEndCell(ImGuiTable* table) -{ - ImGuiTableColumn* column = &table->Columns[table->CurrentColumn]; - ImGuiWindow* window = table->InnerWindow; - - if (window->DC.IsSetPos) - ErrorCheckUsingSetCursorPosToExtendParentBoundaries(); - - // Report maximum position so we can infer content size per column. - float* p_max_pos_x; - if (table->RowFlags & ImGuiTableRowFlags_Headers) - p_max_pos_x = &column->ContentMaxXHeadersUsed; // Useful in case user submit contents in header row that is not a TableHeader() call - else - p_max_pos_x = table->IsUnfrozenRows ? &column->ContentMaxXUnfrozen : &column->ContentMaxXFrozen; - *p_max_pos_x = ImMax(*p_max_pos_x, window->DC.CursorMaxPos.x); - if (column->IsEnabled) - table->RowPosY2 = ImMax(table->RowPosY2, window->DC.CursorMaxPos.y + table->RowCellPaddingY); - column->ItemWidth = window->DC.ItemWidth; - - // Propagate text baseline for the entire row - // FIXME-TABLE: Here we propagate text baseline from the last line of the cell.. instead of the first one. - table->RowTextBaseline = ImMax(table->RowTextBaseline, window->DC.PrevLineTextBaseOffset); -} - -//------------------------------------------------------------------------- -// [SECTION] Tables: Columns width management -//------------------------------------------------------------------------- -// - TableGetMaxColumnWidth() [Internal] -// - TableGetColumnWidthAuto() [Internal] -// - TableSetColumnWidth() -// - TableSetColumnWidthAutoSingle() [Internal] -// - TableSetColumnWidthAutoAll() [Internal] -// - TableUpdateColumnsWeightFromWidth() [Internal] -//------------------------------------------------------------------------- - -// Maximum column content width given current layout. Use column->MinX so this value on a per-column basis. -float ImGui::TableGetMaxColumnWidth(const ImGuiTable* table, int column_n) -{ - const ImGuiTableColumn* column = &table->Columns[column_n]; - float max_width = FLT_MAX; - const float min_column_distance = table->MinColumnWidth + table->CellPaddingX * 2.0f + table->CellSpacingX1 + table->CellSpacingX2; - if (table->Flags & ImGuiTableFlags_ScrollX) - { - // Frozen columns can't reach beyond visible width else scrolling will naturally break. - // (we use DisplayOrder as within a set of multiple frozen column reordering is possible) - if (column->DisplayOrder < table->FreezeColumnsRequest) - { - max_width = (table->InnerClipRect.Max.x - (table->FreezeColumnsRequest - column->DisplayOrder) * min_column_distance) - column->MinX; - max_width = max_width - table->OuterPaddingX - table->CellPaddingX - table->CellSpacingX2; - } - } - else if ((table->Flags & ImGuiTableFlags_NoKeepColumnsVisible) == 0) - { - // If horizontal scrolling if disabled, we apply a final lossless shrinking of columns in order to make - // sure they are all visible. Because of this we also know that all of the columns will always fit in - // table->WorkRect and therefore in table->InnerRect (because ScrollX is off) - // FIXME-TABLE: This is solved incorrectly but also quite a difficult problem to fix as we also want ClipRect width to match. - // See "table_width_distrib" and "table_width_keep_visible" tests - max_width = table->WorkRect.Max.x - (table->ColumnsEnabledCount - column->IndexWithinEnabledSet - 1) * min_column_distance - column->MinX; - //max_width -= table->CellSpacingX1; - max_width -= table->CellSpacingX2; - max_width -= table->CellPaddingX * 2.0f; - max_width -= table->OuterPaddingX; - } - return max_width; -} - -// Note this is meant to be stored in column->WidthAuto, please generally use the WidthAuto field -float ImGui::TableGetColumnWidthAuto(ImGuiTable* table, ImGuiTableColumn* column) -{ - const float content_width_body = ImMax(column->ContentMaxXFrozen, column->ContentMaxXUnfrozen) - column->WorkMinX; - const float content_width_headers = column->ContentMaxXHeadersIdeal - column->WorkMinX; - float width_auto = content_width_body; - if (!(column->Flags & ImGuiTableColumnFlags_NoHeaderWidth)) - width_auto = ImMax(width_auto, content_width_headers); - - // Non-resizable fixed columns preserve their requested width - if ((column->Flags & ImGuiTableColumnFlags_WidthFixed) && column->InitStretchWeightOrWidth > 0.0f) - if (!(table->Flags & ImGuiTableFlags_Resizable) || (column->Flags & ImGuiTableColumnFlags_NoResize)) - width_auto = column->InitStretchWeightOrWidth; - - return ImMax(width_auto, table->MinColumnWidth); -} - -// 'width' = inner column width, without padding -void ImGui::TableSetColumnWidth(int column_n, float width) -{ - ImGuiContext& g = *GImGui; - ImGuiTable* table = g.CurrentTable; - IM_ASSERT(table != NULL && table->IsLayoutLocked == false); - IM_ASSERT(column_n >= 0 && column_n < table->ColumnsCount); - ImGuiTableColumn* column_0 = &table->Columns[column_n]; - float column_0_width = width; - - // Apply constraints early - // Compare both requested and actual given width to avoid overwriting requested width when column is stuck (minimum size, bounded) - IM_ASSERT(table->MinColumnWidth > 0.0f); - const float min_width = table->MinColumnWidth; - const float max_width = ImMax(min_width, TableGetMaxColumnWidth(table, column_n)); - column_0_width = ImClamp(column_0_width, min_width, max_width); - if (column_0->WidthGiven == column_0_width || column_0->WidthRequest == column_0_width) - return; - - //IMGUI_DEBUG_PRINT("TableSetColumnWidth(%d, %.1f->%.1f)\n", column_0_idx, column_0->WidthGiven, column_0_width); - ImGuiTableColumn* column_1 = (column_0->NextEnabledColumn != -1) ? &table->Columns[column_0->NextEnabledColumn] : NULL; - - // In this surprisingly not simple because of how we support mixing Fixed and multiple Stretch columns. - // - All fixed: easy. - // - All stretch: easy. - // - One or more fixed + one stretch: easy. - // - One or more fixed + more than one stretch: tricky. - // Qt when manual resize is enabled only supports a single _trailing_ stretch column, we support more cases here. - - // When forwarding resize from Wn| to Fn+1| we need to be considerate of the _NoResize flag on Fn+1. - // FIXME-TABLE: Find a way to rewrite all of this so interactions feel more consistent for the user. - // Scenarios: - // - F1 F2 F3 resize from F1| or F2| --> ok: alter ->WidthRequested of Fixed column. Subsequent columns will be offset. - // - F1 F2 F3 resize from F3| --> ok: alter ->WidthRequested of Fixed column. If active, ScrollX extent can be altered. - // - F1 F2 W3 resize from F1| or F2| --> ok: alter ->WidthRequested of Fixed column. If active, ScrollX extent can be altered, but it doesn't make much sense as the Stretch column will always be minimal size. - // - F1 F2 W3 resize from W3| --> ok: no-op (disabled by Resize Rule 1) - // - W1 W2 W3 resize from W1| or W2| --> ok - // - W1 W2 W3 resize from W3| --> ok: no-op (disabled by Resize Rule 1) - // - W1 F2 F3 resize from F3| --> ok: no-op (disabled by Resize Rule 1) - // - W1 F2 resize from F2| --> ok: no-op (disabled by Resize Rule 1) - // - W1 W2 F3 resize from W1| or W2| --> ok - // - W1 F2 W3 resize from W1| or F2| --> ok - // - F1 W2 F3 resize from W2| --> ok - // - F1 W3 F2 resize from W3| --> ok - // - W1 F2 F3 resize from W1| --> ok: equivalent to resizing |F2. F3 will not move. - // - W1 F2 F3 resize from F2| --> ok - // All resizes from a Wx columns are locking other columns. - - // Possible improvements: - // - W1 W2 W3 resize W1| --> to not be stuck, both W2 and W3 would stretch down. Seems possible to fix. Would be most beneficial to simplify resize of all-weighted columns. - // - W3 F1 F2 resize W3| --> to not be stuck past F1|, both F1 and F2 would need to stretch down, which would be lossy or ambiguous. Seems hard to fix. - - // [Resize Rule 1] Can't resize from right of right-most visible column if there is any Stretch column. Implemented in TableUpdateLayout(). - - // If we have all Fixed columns OR resizing a Fixed column that doesn't come after a Stretch one, we can do an offsetting resize. - // This is the preferred resize path - if (column_0->Flags & ImGuiTableColumnFlags_WidthFixed) - if (!column_1 || table->LeftMostStretchedColumn == -1 || table->Columns[table->LeftMostStretchedColumn].DisplayOrder >= column_0->DisplayOrder) - { - column_0->WidthRequest = column_0_width; - table->IsSettingsDirty = true; - return; - } - - // We can also use previous column if there's no next one (this is used when doing an auto-fit on the right-most stretch column) - if (column_1 == NULL) - column_1 = (column_0->PrevEnabledColumn != -1) ? &table->Columns[column_0->PrevEnabledColumn] : NULL; - if (column_1 == NULL) - return; - - // Resizing from right-side of a Stretch column before a Fixed column forward sizing to left-side of fixed column. - // (old_a + old_b == new_a + new_b) --> (new_a == old_a + old_b - new_b) - float column_1_width = ImMax(column_1->WidthRequest - (column_0_width - column_0->WidthRequest), min_width); - column_0_width = column_0->WidthRequest + column_1->WidthRequest - column_1_width; - IM_ASSERT(column_0_width > 0.0f && column_1_width > 0.0f); - column_0->WidthRequest = column_0_width; - column_1->WidthRequest = column_1_width; - if ((column_0->Flags | column_1->Flags) & ImGuiTableColumnFlags_WidthStretch) - TableUpdateColumnsWeightFromWidth(table); - table->IsSettingsDirty = true; -} - -// Disable clipping then auto-fit, will take 2 frames -// (we don't take a shortcut for unclipped columns to reduce inconsistencies when e.g. resizing multiple columns) -void ImGui::TableSetColumnWidthAutoSingle(ImGuiTable* table, int column_n) -{ - // Single auto width uses auto-fit - ImGuiTableColumn* column = &table->Columns[column_n]; - if (!column->IsEnabled) - return; - column->CannotSkipItemsQueue = (1 << 0); - table->AutoFitSingleColumn = (ImGuiTableColumnIdx)column_n; -} - -void ImGui::TableSetColumnWidthAutoAll(ImGuiTable* table) -{ - for (int column_n = 0; column_n < table->ColumnsCount; column_n++) - { - ImGuiTableColumn* column = &table->Columns[column_n]; - if (!column->IsEnabled && !(column->Flags & ImGuiTableColumnFlags_WidthStretch)) // Cannot reset weight of hidden stretch column - continue; - column->CannotSkipItemsQueue = (1 << 0); - column->AutoFitQueue = (1 << 1); - } -} - -void ImGui::TableUpdateColumnsWeightFromWidth(ImGuiTable* table) -{ - IM_ASSERT(table->LeftMostStretchedColumn != -1 && table->RightMostStretchedColumn != -1); - - // Measure existing quantities - float visible_weight = 0.0f; - float visible_width = 0.0f; - for (int column_n = 0; column_n < table->ColumnsCount; column_n++) - { - ImGuiTableColumn* column = &table->Columns[column_n]; - if (!column->IsEnabled || !(column->Flags & ImGuiTableColumnFlags_WidthStretch)) - continue; - IM_ASSERT(column->StretchWeight > 0.0f); - visible_weight += column->StretchWeight; - visible_width += column->WidthRequest; - } - IM_ASSERT(visible_weight > 0.0f && visible_width > 0.0f); - - // Apply new weights - for (int column_n = 0; column_n < table->ColumnsCount; column_n++) - { - ImGuiTableColumn* column = &table->Columns[column_n]; - if (!column->IsEnabled || !(column->Flags & ImGuiTableColumnFlags_WidthStretch)) - continue; - column->StretchWeight = (column->WidthRequest / visible_width) * visible_weight; - IM_ASSERT(column->StretchWeight > 0.0f); - } -} - -//------------------------------------------------------------------------- -// [SECTION] Tables: Drawing -//------------------------------------------------------------------------- -// - TablePushBackgroundChannel() [Internal] -// - TablePopBackgroundChannel() [Internal] -// - TableSetupDrawChannels() [Internal] -// - TableMergeDrawChannels() [Internal] -// - TableGetColumnBorderCol() [Internal] -// - TableDrawBorders() [Internal] -//------------------------------------------------------------------------- - -// Bg2 is used by Selectable (and possibly other widgets) to render to the background. -// Unlike our Bg0/1 channel which we uses for RowBg/CellBg/Borders and where we guarantee all shapes to be CPU-clipped, the Bg2 channel being widgets-facing will rely on regular ClipRect. -void ImGui::TablePushBackgroundChannel() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - ImGuiTable* table = g.CurrentTable; - - // Optimization: avoid SetCurrentChannel() + PushClipRect() - table->HostBackupInnerClipRect = window->ClipRect; - SetWindowClipRectBeforeSetChannel(window, table->Bg2ClipRectForDrawCmd); - table->DrawSplitter->SetCurrentChannel(window->DrawList, table->Bg2DrawChannelCurrent); -} - -void ImGui::TablePopBackgroundChannel() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - ImGuiTable* table = g.CurrentTable; - ImGuiTableColumn* column = &table->Columns[table->CurrentColumn]; - - // Optimization: avoid PopClipRect() + SetCurrentChannel() - SetWindowClipRectBeforeSetChannel(window, table->HostBackupInnerClipRect); - table->DrawSplitter->SetCurrentChannel(window->DrawList, column->DrawChannelCurrent); -} - -// Allocate draw channels. Called by TableUpdateLayout() -// - We allocate them following storage order instead of display order so reordering columns won't needlessly -// increase overall dormant memory cost. -// - We isolate headers draw commands in their own channels instead of just altering clip rects. -// This is in order to facilitate merging of draw commands. -// - After crossing FreezeRowsCount, all columns see their current draw channel changed to a second set of channels. -// - We only use the dummy draw channel so we can push a null clipping rectangle into it without affecting other -// channels, while simplifying per-row/per-cell overhead. It will be empty and discarded when merged. -// - We allocate 1 or 2 background draw channels. This is because we know TablePushBackgroundChannel() is only used for -// horizontal spanning. If we allowed vertical spanning we'd need one background draw channel per merge group (1-4). -// Draw channel allocation (before merging): -// - NoClip --> 2+D+1 channels: bg0/1 + bg2 + foreground (same clip rect == always 1 draw call) -// - Clip --> 2+D+N channels -// - FreezeRows --> 2+D+N*2 (unless scrolling value is zero) -// - FreezeRows || FreezeColunns --> 3+D+N*2 (unless scrolling value is zero) -// Where D is 1 if any column is clipped or hidden (dummy channel) otherwise 0. -void ImGui::TableSetupDrawChannels(ImGuiTable* table) -{ - const int freeze_row_multiplier = (table->FreezeRowsCount > 0) ? 2 : 1; - const int channels_for_row = (table->Flags & ImGuiTableFlags_NoClip) ? 1 : table->ColumnsEnabledCount; - const int channels_for_bg = 1 + 1 * freeze_row_multiplier; - const int channels_for_dummy = (table->ColumnsEnabledCount < table->ColumnsCount || (memcmp(table->VisibleMaskByIndex, table->EnabledMaskByIndex, ImBitArrayGetStorageSizeInBytes(table->ColumnsCount)) != 0)) ? +1 : 0; - const int channels_total = channels_for_bg + (channels_for_row * freeze_row_multiplier) + channels_for_dummy; - table->DrawSplitter->Split(table->InnerWindow->DrawList, channels_total); - table->DummyDrawChannel = (ImGuiTableDrawChannelIdx)((channels_for_dummy > 0) ? channels_total - 1 : -1); - table->Bg2DrawChannelCurrent = TABLE_DRAW_CHANNEL_BG2_FROZEN; - table->Bg2DrawChannelUnfrozen = (ImGuiTableDrawChannelIdx)((table->FreezeRowsCount > 0) ? 2 + channels_for_row : TABLE_DRAW_CHANNEL_BG2_FROZEN); - - int draw_channel_current = 2; - for (int column_n = 0; column_n < table->ColumnsCount; column_n++) - { - ImGuiTableColumn* column = &table->Columns[column_n]; - if (column->IsVisibleX && column->IsVisibleY) - { - column->DrawChannelFrozen = (ImGuiTableDrawChannelIdx)(draw_channel_current); - column->DrawChannelUnfrozen = (ImGuiTableDrawChannelIdx)(draw_channel_current + (table->FreezeRowsCount > 0 ? channels_for_row + 1 : 0)); - if (!(table->Flags & ImGuiTableFlags_NoClip)) - draw_channel_current++; - } - else - { - column->DrawChannelFrozen = column->DrawChannelUnfrozen = table->DummyDrawChannel; - } - column->DrawChannelCurrent = column->DrawChannelFrozen; - } - - // Initial draw cmd starts with a BgClipRect that matches the one of its host, to facilitate merge draw commands by default. - // All our cell highlight are manually clipped with BgClipRect. When unfreezing it will be made smaller to fit scrolling rect. - // (This technically isn't part of setting up draw channels, but is reasonably related to be done here) - table->BgClipRect = table->InnerClipRect; - table->Bg0ClipRectForDrawCmd = table->OuterWindow->ClipRect; - table->Bg2ClipRectForDrawCmd = table->HostClipRect; - IM_ASSERT(table->BgClipRect.Min.y <= table->BgClipRect.Max.y); -} - -// This function reorder draw channels based on matching clip rectangle, to facilitate merging them. Called by EndTable(). -// For simplicity we call it TableMergeDrawChannels() but in fact it only reorder channels + overwrite ClipRect, -// actual merging is done by table->DrawSplitter.Merge() which is called right after TableMergeDrawChannels(). -// -// Columns where the contents didn't stray off their local clip rectangle can be merged. To achieve -// this we merge their clip rect and make them contiguous in the channel list, so they can be merged -// by the call to DrawSplitter.Merge() following to the call to this function. -// We reorder draw commands by arranging them into a maximum of 4 distinct groups: -// -// 1 group: 2 groups: 2 groups: 4 groups: -// [ 0. ] no freeze [ 0. ] row freeze [ 01 ] col freeze [ 01 ] row+col freeze -// [ .. ] or no scroll [ 2. ] and v-scroll [ .. ] and h-scroll [ 23 ] and v+h-scroll -// -// Each column itself can use 1 channel (row freeze disabled) or 2 channels (row freeze enabled). -// When the contents of a column didn't stray off its limit, we move its channels into the corresponding group -// based on its position (within frozen rows/columns groups or not). -// At the end of the operation our 1-4 groups will each have a ImDrawCmd using the same ClipRect. -// This function assume that each column are pointing to a distinct draw channel, -// otherwise merge_group->ChannelsCount will not match set bit count of merge_group->ChannelsMask. -// -// Column channels will not be merged into one of the 1-4 groups in the following cases: -// - The contents stray off its clipping rectangle (we only compare the MaxX value, not the MinX value). -// Direct ImDrawList calls won't be taken into account by default, if you use them make sure the ImGui:: bounds -// matches, by e.g. calling SetCursorScreenPos(). -// - The channel uses more than one draw command itself. We drop all our attempt at merging stuff here.. -// we could do better but it's going to be rare and probably not worth the hassle. -// Columns for which the draw channel(s) haven't been merged with other will use their own ImDrawCmd. -// -// This function is particularly tricky to understand.. take a breath. -void ImGui::TableMergeDrawChannels(ImGuiTable* table) -{ - ImGuiContext& g = *GImGui; - ImDrawListSplitter* splitter = table->DrawSplitter; - const bool has_freeze_v = (table->FreezeRowsCount > 0); - const bool has_freeze_h = (table->FreezeColumnsCount > 0); - IM_ASSERT(splitter->_Current == 0); - - // Track which groups we are going to attempt to merge, and which channels goes into each group. - struct MergeGroup - { - ImRect ClipRect; - int ChannelsCount = 0; - ImBitArrayPtr ChannelsMask = NULL; - }; - int merge_group_mask = 0x00; - MergeGroup merge_groups[4]; - - // Use a reusable temp buffer for the merge masks as they are dynamically sized. - const int max_draw_channels = (4 + table->ColumnsCount * 2); - const int size_for_masks_bitarrays_one = (int)ImBitArrayGetStorageSizeInBytes(max_draw_channels); - g.TempBuffer.reserve(size_for_masks_bitarrays_one * 5); - memset(g.TempBuffer.Data, 0, size_for_masks_bitarrays_one * 5); - for (int n = 0; n < IM_ARRAYSIZE(merge_groups); n++) - merge_groups[n].ChannelsMask = (ImBitArrayPtr)(void*)(g.TempBuffer.Data + (size_for_masks_bitarrays_one * n)); - ImBitArrayPtr remaining_mask = (ImBitArrayPtr)(void*)(g.TempBuffer.Data + (size_for_masks_bitarrays_one * 4)); - - // 1. Scan channels and take note of those which can be merged - for (int column_n = 0; column_n < table->ColumnsCount; column_n++) - { - if (!IM_BITARRAY_TESTBIT(table->VisibleMaskByIndex, column_n)) - continue; - ImGuiTableColumn* column = &table->Columns[column_n]; - - const int merge_group_sub_count = has_freeze_v ? 2 : 1; - for (int merge_group_sub_n = 0; merge_group_sub_n < merge_group_sub_count; merge_group_sub_n++) - { - const int channel_no = (merge_group_sub_n == 0) ? column->DrawChannelFrozen : column->DrawChannelUnfrozen; - - // Don't attempt to merge if there are multiple draw calls within the column - ImDrawChannel* src_channel = &splitter->_Channels[channel_no]; - if (src_channel->_CmdBuffer.Size > 0 && src_channel->_CmdBuffer.back().ElemCount == 0 && src_channel->_CmdBuffer.back().UserCallback == NULL) // Equivalent of PopUnusedDrawCmd() - src_channel->_CmdBuffer.pop_back(); - if (src_channel->_CmdBuffer.Size != 1) - continue; - - // Find out the width of this merge group and check if it will fit in our column - // (note that we assume that rendering didn't stray on the left direction. we should need a CursorMinPos to detect it) - if (!(column->Flags & ImGuiTableColumnFlags_NoClip)) - { - float content_max_x; - if (!has_freeze_v) - content_max_x = ImMax(column->ContentMaxXUnfrozen, column->ContentMaxXHeadersUsed); // No row freeze - else if (merge_group_sub_n == 0) - content_max_x = ImMax(column->ContentMaxXFrozen, column->ContentMaxXHeadersUsed); // Row freeze: use width before freeze - else - content_max_x = column->ContentMaxXUnfrozen; // Row freeze: use width after freeze - if (content_max_x > column->ClipRect.Max.x) - continue; - } - - const int merge_group_n = (has_freeze_h && column_n < table->FreezeColumnsCount ? 0 : 1) + (has_freeze_v && merge_group_sub_n == 0 ? 0 : 2); - IM_ASSERT(channel_no < max_draw_channels); - MergeGroup* merge_group = &merge_groups[merge_group_n]; - if (merge_group->ChannelsCount == 0) - merge_group->ClipRect = ImRect(+FLT_MAX, +FLT_MAX, -FLT_MAX, -FLT_MAX); - ImBitArraySetBit(merge_group->ChannelsMask, channel_no); - merge_group->ChannelsCount++; - merge_group->ClipRect.Add(src_channel->_CmdBuffer[0].ClipRect); - merge_group_mask |= (1 << merge_group_n); - } - - // Invalidate current draw channel - // (we don't clear DrawChannelFrozen/DrawChannelUnfrozen solely to facilitate debugging/later inspection of data) - column->DrawChannelCurrent = (ImGuiTableDrawChannelIdx)-1; - } - - // [DEBUG] Display merge groups -#if 0 - if (g.IO.KeyShift) - for (int merge_group_n = 0; merge_group_n < IM_ARRAYSIZE(merge_groups); merge_group_n++) - { - MergeGroup* merge_group = &merge_groups[merge_group_n]; - if (merge_group->ChannelsCount == 0) - continue; - char buf[32]; - ImFormatString(buf, 32, "MG%d:%d", merge_group_n, merge_group->ChannelsCount); - ImVec2 text_pos = merge_group->ClipRect.Min + ImVec2(4, 4); - ImVec2 text_size = CalcTextSize(buf, NULL); - GetForegroundDrawList()->AddRectFilled(text_pos, text_pos + text_size, IM_COL32(0, 0, 0, 255)); - GetForegroundDrawList()->AddText(text_pos, IM_COL32(255, 255, 0, 255), buf, NULL); - GetForegroundDrawList()->AddRect(merge_group->ClipRect.Min, merge_group->ClipRect.Max, IM_COL32(255, 255, 0, 255)); - } -#endif - - // 2. Rewrite channel list in our preferred order - if (merge_group_mask != 0) - { - // We skip channel 0 (Bg0/Bg1) and 1 (Bg2 frozen) from the shuffling since they won't move - see channels allocation in TableSetupDrawChannels(). - const int LEADING_DRAW_CHANNELS = 2; - g.DrawChannelsTempMergeBuffer.resize(splitter->_Count - LEADING_DRAW_CHANNELS); // Use shared temporary storage so the allocation gets amortized - ImDrawChannel* dst_tmp = g.DrawChannelsTempMergeBuffer.Data; - ImBitArraySetBitRange(remaining_mask, LEADING_DRAW_CHANNELS, splitter->_Count); - ImBitArrayClearBit(remaining_mask, table->Bg2DrawChannelUnfrozen); - IM_ASSERT(has_freeze_v == false || table->Bg2DrawChannelUnfrozen != TABLE_DRAW_CHANNEL_BG2_FROZEN); - int remaining_count = splitter->_Count - (has_freeze_v ? LEADING_DRAW_CHANNELS + 1 : LEADING_DRAW_CHANNELS); - //ImRect host_rect = (table->InnerWindow == table->OuterWindow) ? table->InnerClipRect : table->HostClipRect; - ImRect host_rect = table->HostClipRect; - for (int merge_group_n = 0; merge_group_n < IM_ARRAYSIZE(merge_groups); merge_group_n++) - { - if (int merge_channels_count = merge_groups[merge_group_n].ChannelsCount) - { - MergeGroup* merge_group = &merge_groups[merge_group_n]; - ImRect merge_clip_rect = merge_group->ClipRect; - - // Extend outer-most clip limits to match those of host, so draw calls can be merged even if - // outer-most columns have some outer padding offsetting them from their parent ClipRect. - // The principal cases this is dealing with are: - // - On a same-window table (not scrolling = single group), all fitting columns ClipRect -> will extend and match host ClipRect -> will merge - // - Columns can use padding and have left-most ClipRect.Min.x and right-most ClipRect.Max.x != from host ClipRect -> will extend and match host ClipRect -> will merge - // FIXME-TABLE FIXME-WORKRECT: We are wasting a merge opportunity on tables without scrolling if column doesn't fit - // within host clip rect, solely because of the half-padding difference between window->WorkRect and window->InnerClipRect. - if ((merge_group_n & 1) == 0 || !has_freeze_h) - merge_clip_rect.Min.x = ImMin(merge_clip_rect.Min.x, host_rect.Min.x); - if ((merge_group_n & 2) == 0 || !has_freeze_v) - merge_clip_rect.Min.y = ImMin(merge_clip_rect.Min.y, host_rect.Min.y); - if ((merge_group_n & 1) != 0) - merge_clip_rect.Max.x = ImMax(merge_clip_rect.Max.x, host_rect.Max.x); - if ((merge_group_n & 2) != 0 && (table->Flags & ImGuiTableFlags_NoHostExtendY) == 0) - merge_clip_rect.Max.y = ImMax(merge_clip_rect.Max.y, host_rect.Max.y); - //GetForegroundDrawList()->AddRect(merge_group->ClipRect.Min, merge_group->ClipRect.Max, IM_COL32(255, 0, 0, 200), 0.0f, 0, 1.0f); // [DEBUG] - //GetForegroundDrawList()->AddLine(merge_group->ClipRect.Min, merge_clip_rect.Min, IM_COL32(255, 100, 0, 200)); - //GetForegroundDrawList()->AddLine(merge_group->ClipRect.Max, merge_clip_rect.Max, IM_COL32(255, 100, 0, 200)); - remaining_count -= merge_group->ChannelsCount; - for (int n = 0; n < (size_for_masks_bitarrays_one >> 2); n++) - remaining_mask[n] &= ~merge_group->ChannelsMask[n]; - for (int n = 0; n < splitter->_Count && merge_channels_count != 0; n++) - { - // Copy + overwrite new clip rect - if (!IM_BITARRAY_TESTBIT(merge_group->ChannelsMask, n)) - continue; - IM_BITARRAY_CLEARBIT(merge_group->ChannelsMask, n); - merge_channels_count--; - - ImDrawChannel* channel = &splitter->_Channels[n]; - IM_ASSERT(channel->_CmdBuffer.Size == 1 && merge_clip_rect.Contains(ImRect(channel->_CmdBuffer[0].ClipRect))); - channel->_CmdBuffer[0].ClipRect = merge_clip_rect.ToVec4(); - memcpy(dst_tmp++, channel, sizeof(ImDrawChannel)); - } - } - - // Make sure Bg2DrawChannelUnfrozen appears in the middle of our groups (whereas Bg0/Bg1 and Bg2 frozen are fixed to 0 and 1) - if (merge_group_n == 1 && has_freeze_v) - memcpy(dst_tmp++, &splitter->_Channels[table->Bg2DrawChannelUnfrozen], sizeof(ImDrawChannel)); - } - - // Append unmergeable channels that we didn't reorder at the end of the list - for (int n = 0; n < splitter->_Count && remaining_count != 0; n++) - { - if (!IM_BITARRAY_TESTBIT(remaining_mask, n)) - continue; - ImDrawChannel* channel = &splitter->_Channels[n]; - memcpy(dst_tmp++, channel, sizeof(ImDrawChannel)); - remaining_count--; - } - IM_ASSERT(dst_tmp == g.DrawChannelsTempMergeBuffer.Data + g.DrawChannelsTempMergeBuffer.Size); - memcpy(splitter->_Channels.Data + LEADING_DRAW_CHANNELS, g.DrawChannelsTempMergeBuffer.Data, (splitter->_Count - LEADING_DRAW_CHANNELS) * sizeof(ImDrawChannel)); - } -} - -static ImU32 TableGetColumnBorderCol(ImGuiTable* table, int order_n, int column_n) -{ - const bool is_hovered = (table->HoveredColumnBorder == column_n); - const bool is_resized = (table->ResizedColumn == column_n) && (table->InstanceInteracted == table->InstanceCurrent); - const bool is_frozen_separator = (table->FreezeColumnsCount == order_n + 1); - if (is_resized || is_hovered) - return ImGui::GetColorU32(is_resized ? ImGuiCol_SeparatorActive : ImGuiCol_SeparatorHovered); - if (is_frozen_separator || (table->Flags & (ImGuiTableFlags_NoBordersInBody | ImGuiTableFlags_NoBordersInBodyUntilResize))) - return table->BorderColorStrong; - return table->BorderColorLight; -} - -// FIXME-TABLE: This is a mess, need to redesign how we render borders (as some are also done in TableEndRow) -void ImGui::TableDrawBorders(ImGuiTable* table) -{ - ImGuiWindow* inner_window = table->InnerWindow; - if (!table->OuterWindow->ClipRect.Overlaps(table->OuterRect)) - return; - - ImDrawList* inner_drawlist = inner_window->DrawList; - table->DrawSplitter->SetCurrentChannel(inner_drawlist, TABLE_DRAW_CHANNEL_BG0); - inner_drawlist->PushClipRect(table->Bg0ClipRectForDrawCmd.Min, table->Bg0ClipRectForDrawCmd.Max, false); - - // Draw inner border and resizing feedback - ImGuiTableInstanceData* table_instance = TableGetInstanceData(table, table->InstanceCurrent); - const float border_size = TABLE_BORDER_SIZE; - const float draw_y1 = ImMax(table->InnerRect.Min.y, (table->FreezeRowsCount >= 1 ? table->InnerRect.Min.y : table->WorkRect.Min.y) + table->AngledHeadersHeight) + ((table->Flags & ImGuiTableFlags_BordersOuterH) ? 1.0f : 0.0f); - const float draw_y2_body = table->InnerRect.Max.y; - const float draw_y2_head = table->IsUsingHeaders ? ImMin(table->InnerRect.Max.y, (table->FreezeRowsCount >= 1 ? table->InnerRect.Min.y : table->WorkRect.Min.y) + table_instance->LastTopHeadersRowHeight) : draw_y1; - if (table->Flags & ImGuiTableFlags_BordersInnerV) - { - for (int order_n = 0; order_n < table->ColumnsCount; order_n++) - { - if (!IM_BITARRAY_TESTBIT(table->EnabledMaskByDisplayOrder, order_n)) - continue; - - const int column_n = table->DisplayOrderToIndex[order_n]; - ImGuiTableColumn* column = &table->Columns[column_n]; - const bool is_hovered = (table->HoveredColumnBorder == column_n); - const bool is_resized = (table->ResizedColumn == column_n) && (table->InstanceInteracted == table->InstanceCurrent); - const bool is_resizable = (column->Flags & (ImGuiTableColumnFlags_NoResize | ImGuiTableColumnFlags_NoDirectResize_)) == 0; - const bool is_frozen_separator = (table->FreezeColumnsCount == order_n + 1); - if (column->MaxX > table->InnerClipRect.Max.x && !is_resized) - continue; - - // Decide whether right-most column is visible - if (column->NextEnabledColumn == -1 && !is_resizable) - if ((table->Flags & ImGuiTableFlags_SizingMask_) != ImGuiTableFlags_SizingFixedSame || (table->Flags & ImGuiTableFlags_NoHostExtendX)) - continue; - if (column->MaxX <= column->ClipRect.Min.x) // FIXME-TABLE FIXME-STYLE: Assume BorderSize==1, this is problematic if we want to increase the border size.. - continue; - - // Draw in outer window so right-most column won't be clipped - // Always draw full height border when being resized/hovered, or on the delimitation of frozen column scrolling. - float draw_y2 = (is_hovered || is_resized || is_frozen_separator || (table->Flags & (ImGuiTableFlags_NoBordersInBody | ImGuiTableFlags_NoBordersInBodyUntilResize)) == 0) ? draw_y2_body : draw_y2_head; - if (draw_y2 > draw_y1) - inner_drawlist->AddLine(ImVec2(column->MaxX, draw_y1), ImVec2(column->MaxX, draw_y2), TableGetColumnBorderCol(table, order_n, column_n), border_size); - } - } - - // Draw outer border - // FIXME: could use AddRect or explicit VLine/HLine helper? - if (table->Flags & ImGuiTableFlags_BordersOuter) - { - // Display outer border offset by 1 which is a simple way to display it without adding an extra draw call - // (Without the offset, in outer_window it would be rendered behind cells, because child windows are above their - // parent. In inner_window, it won't reach out over scrollbars. Another weird solution would be to display part - // of it in inner window, and the part that's over scrollbars in the outer window..) - // Either solution currently won't allow us to use a larger border size: the border would clipped. - const ImRect outer_border = table->OuterRect; - const ImU32 outer_col = table->BorderColorStrong; - if ((table->Flags & ImGuiTableFlags_BordersOuter) == ImGuiTableFlags_BordersOuter) - { - inner_drawlist->AddRect(outer_border.Min, outer_border.Max + ImVec2(1, 1), outer_col, 0.0f, 0, border_size); - } - else if (table->Flags & ImGuiTableFlags_BordersOuterV) - { - inner_drawlist->AddLine(outer_border.Min, ImVec2(outer_border.Min.x, outer_border.Max.y), outer_col, border_size); - inner_drawlist->AddLine(ImVec2(outer_border.Max.x, outer_border.Min.y), outer_border.Max, outer_col, border_size); - } - else if (table->Flags & ImGuiTableFlags_BordersOuterH) - { - inner_drawlist->AddLine(outer_border.Min, ImVec2(outer_border.Max.x, outer_border.Min.y), outer_col, border_size); - inner_drawlist->AddLine(ImVec2(outer_border.Min.x, outer_border.Max.y), outer_border.Max, outer_col, border_size); - } - } - if ((table->Flags & ImGuiTableFlags_BordersInnerH) && table->RowPosY2 < table->OuterRect.Max.y) - { - // Draw bottom-most row border between it is above outer border. - const float border_y = table->RowPosY2; - if (border_y >= table->BgClipRect.Min.y && border_y < table->BgClipRect.Max.y) - inner_drawlist->AddLine(ImVec2(table->BorderX1, border_y), ImVec2(table->BorderX2, border_y), table->BorderColorLight, border_size); - } - - inner_drawlist->PopClipRect(); -} - -//------------------------------------------------------------------------- -// [SECTION] Tables: Sorting -//------------------------------------------------------------------------- -// - TableGetSortSpecs() -// - TableFixColumnSortDirection() [Internal] -// - TableGetColumnNextSortDirection() [Internal] -// - TableSetColumnSortDirection() [Internal] -// - TableSortSpecsSanitize() [Internal] -// - TableSortSpecsBuild() [Internal] -//------------------------------------------------------------------------- - -// Return NULL if no sort specs (most often when ImGuiTableFlags_Sortable is not set) -// When 'sort_specs->SpecsDirty == true' you should sort your data. It will be true when sorting specs have -// changed since last call, or the first time. Make sure to set 'SpecsDirty = false' after sorting, -// else you may wastefully sort your data every frame! -// Lifetime: don't hold on this pointer over multiple frames or past any subsequent call to BeginTable()! -ImGuiTableSortSpecs* ImGui::TableGetSortSpecs() -{ - ImGuiContext& g = *GImGui; - ImGuiTable* table = g.CurrentTable; - IM_ASSERT(table != NULL); - - if (!(table->Flags & ImGuiTableFlags_Sortable)) - return NULL; - - // Require layout (in case TableHeadersRow() hasn't been called) as it may alter IsSortSpecsDirty in some paths. - if (!table->IsLayoutLocked) - TableUpdateLayout(table); - - TableSortSpecsBuild(table); - return &table->SortSpecs; -} - -static inline ImGuiSortDirection TableGetColumnAvailSortDirection(ImGuiTableColumn* column, int n) -{ - IM_ASSERT(n < column->SortDirectionsAvailCount); - return (column->SortDirectionsAvailList >> (n << 1)) & 0x03; -} - -// Fix sort direction if currently set on a value which is unavailable (e.g. activating NoSortAscending/NoSortDescending) -void ImGui::TableFixColumnSortDirection(ImGuiTable* table, ImGuiTableColumn* column) -{ - if (column->SortOrder == -1 || (column->SortDirectionsAvailMask & (1 << column->SortDirection)) != 0) - return; - column->SortDirection = (ImU8)TableGetColumnAvailSortDirection(column, 0); - table->IsSortSpecsDirty = true; -} - -// Calculate next sort direction that would be set after clicking the column -// - If the PreferSortDescending flag is set, we will default to a Descending direction on the first click. -// - Note that the PreferSortAscending flag is never checked, it is essentially the default and therefore a no-op. -IM_STATIC_ASSERT(ImGuiSortDirection_None == 0 && ImGuiSortDirection_Ascending == 1 && ImGuiSortDirection_Descending == 2); -ImGuiSortDirection ImGui::TableGetColumnNextSortDirection(ImGuiTableColumn* column) -{ - IM_ASSERT(column->SortDirectionsAvailCount > 0); - if (column->SortOrder == -1) - return TableGetColumnAvailSortDirection(column, 0); - for (int n = 0; n < 3; n++) - if (column->SortDirection == TableGetColumnAvailSortDirection(column, n)) - return TableGetColumnAvailSortDirection(column, (n + 1) % column->SortDirectionsAvailCount); - IM_ASSERT(0); - return ImGuiSortDirection_None; -} - -// Note that the NoSortAscending/NoSortDescending flags are processed in TableSortSpecsSanitize(), and they may change/revert -// the value of SortDirection. We could technically also do it here but it would be unnecessary and duplicate code. -void ImGui::TableSetColumnSortDirection(int column_n, ImGuiSortDirection sort_direction, bool append_to_sort_specs) -{ - ImGuiContext& g = *GImGui; - ImGuiTable* table = g.CurrentTable; - - if (!(table->Flags & ImGuiTableFlags_SortMulti)) - append_to_sort_specs = false; - if (!(table->Flags & ImGuiTableFlags_SortTristate)) - IM_ASSERT(sort_direction != ImGuiSortDirection_None); - - ImGuiTableColumnIdx sort_order_max = 0; - if (append_to_sort_specs) - for (int other_column_n = 0; other_column_n < table->ColumnsCount; other_column_n++) - sort_order_max = ImMax(sort_order_max, table->Columns[other_column_n].SortOrder); - - ImGuiTableColumn* column = &table->Columns[column_n]; - column->SortDirection = (ImU8)sort_direction; - if (column->SortDirection == ImGuiSortDirection_None) - column->SortOrder = -1; - else if (column->SortOrder == -1 || !append_to_sort_specs) - column->SortOrder = append_to_sort_specs ? sort_order_max + 1 : 0; - - for (int other_column_n = 0; other_column_n < table->ColumnsCount; other_column_n++) - { - ImGuiTableColumn* other_column = &table->Columns[other_column_n]; - if (other_column != column && !append_to_sort_specs) - other_column->SortOrder = -1; - TableFixColumnSortDirection(table, other_column); - } - table->IsSettingsDirty = true; - table->IsSortSpecsDirty = true; -} - -void ImGui::TableSortSpecsSanitize(ImGuiTable* table) -{ - IM_ASSERT(table->Flags & ImGuiTableFlags_Sortable); - - // Clear SortOrder from hidden column and verify that there's no gap or duplicate. - int sort_order_count = 0; - ImU64 sort_order_mask = 0x00; - for (int column_n = 0; column_n < table->ColumnsCount; column_n++) - { - ImGuiTableColumn* column = &table->Columns[column_n]; - if (column->SortOrder != -1 && !column->IsEnabled) - column->SortOrder = -1; - if (column->SortOrder == -1) - continue; - sort_order_count++; - sort_order_mask |= ((ImU64)1 << column->SortOrder); - IM_ASSERT(sort_order_count < (int)sizeof(sort_order_mask) * 8); - } - - const bool need_fix_linearize = ((ImU64)1 << sort_order_count) != (sort_order_mask + 1); - const bool need_fix_single_sort_order = (sort_order_count > 1) && !(table->Flags & ImGuiTableFlags_SortMulti); - if (need_fix_linearize || need_fix_single_sort_order) - { - ImU64 fixed_mask = 0x00; - for (int sort_n = 0; sort_n < sort_order_count; sort_n++) - { - // Fix: Rewrite sort order fields if needed so they have no gap or duplicate. - // (e.g. SortOrder 0 disappeared, SortOrder 1..2 exists --> rewrite then as SortOrder 0..1) - int column_with_smallest_sort_order = -1; - for (int column_n = 0; column_n < table->ColumnsCount; column_n++) - if ((fixed_mask & ((ImU64)1 << (ImU64)column_n)) == 0 && table->Columns[column_n].SortOrder != -1) - if (column_with_smallest_sort_order == -1 || table->Columns[column_n].SortOrder < table->Columns[column_with_smallest_sort_order].SortOrder) - column_with_smallest_sort_order = column_n; - IM_ASSERT(column_with_smallest_sort_order != -1); - fixed_mask |= ((ImU64)1 << column_with_smallest_sort_order); - table->Columns[column_with_smallest_sort_order].SortOrder = (ImGuiTableColumnIdx)sort_n; - - // Fix: Make sure only one column has a SortOrder if ImGuiTableFlags_MultiSortable is not set. - if (need_fix_single_sort_order) - { - sort_order_count = 1; - for (int column_n = 0; column_n < table->ColumnsCount; column_n++) - if (column_n != column_with_smallest_sort_order) - table->Columns[column_n].SortOrder = -1; - break; - } - } - } - - // Fallback default sort order (if no column with the ImGuiTableColumnFlags_DefaultSort flag) - if (sort_order_count == 0 && !(table->Flags & ImGuiTableFlags_SortTristate)) - for (int column_n = 0; column_n < table->ColumnsCount; column_n++) - { - ImGuiTableColumn* column = &table->Columns[column_n]; - if (column->IsEnabled && !(column->Flags & ImGuiTableColumnFlags_NoSort)) - { - sort_order_count = 1; - column->SortOrder = 0; - column->SortDirection = (ImU8)TableGetColumnAvailSortDirection(column, 0); - break; - } - } - - table->SortSpecsCount = (ImGuiTableColumnIdx)sort_order_count; -} - -void ImGui::TableSortSpecsBuild(ImGuiTable* table) -{ - bool dirty = table->IsSortSpecsDirty; - if (dirty) - { - TableSortSpecsSanitize(table); - table->SortSpecsMulti.resize(table->SortSpecsCount <= 1 ? 0 : table->SortSpecsCount); - table->SortSpecs.SpecsDirty = true; // Mark as dirty for user - table->IsSortSpecsDirty = false; // Mark as not dirty for us - } - - // Write output - ImGuiTableColumnSortSpecs* sort_specs = (table->SortSpecsCount == 0) ? NULL : (table->SortSpecsCount == 1) ? &table->SortSpecsSingle : table->SortSpecsMulti.Data; - if (dirty && sort_specs != NULL) - for (int column_n = 0; column_n < table->ColumnsCount; column_n++) - { - ImGuiTableColumn* column = &table->Columns[column_n]; - if (column->SortOrder == -1) - continue; - IM_ASSERT(column->SortOrder < table->SortSpecsCount); - ImGuiTableColumnSortSpecs* sort_spec = &sort_specs[column->SortOrder]; - sort_spec->ColumnUserID = column->UserID; - sort_spec->ColumnIndex = (ImGuiTableColumnIdx)column_n; - sort_spec->SortOrder = (ImGuiTableColumnIdx)column->SortOrder; - sort_spec->SortDirection = column->SortDirection; - } - - table->SortSpecs.Specs = sort_specs; - table->SortSpecs.SpecsCount = table->SortSpecsCount; -} - -//------------------------------------------------------------------------- -// [SECTION] Tables: Headers -//------------------------------------------------------------------------- -// - TableGetHeaderRowHeight() [Internal] -// - TableHeadersRow() -// - TableHeader() -// - TableAngledHeadersRow() -// - TableAngledHeadersRowEx() [Internal] -//------------------------------------------------------------------------- - -float ImGui::TableGetHeaderRowHeight() -{ - // Caring for a minor edge case: - // Calculate row height, for the unlikely case that some labels may be taller than others. - // If we didn't do that, uneven header height would highlight but smaller one before the tallest wouldn't catch input for all height. - // In your custom header row you may omit this all together and just call TableNextRow() without a height... - ImGuiContext& g = *GImGui; - ImGuiTable* table = g.CurrentTable; - float row_height = g.FontSize; - for (int column_n = 0; column_n < table->ColumnsCount; column_n++) - if (IM_BITARRAY_TESTBIT(table->EnabledMaskByIndex, column_n)) - if ((table->Columns[column_n].Flags & ImGuiTableColumnFlags_NoHeaderLabel) == 0) - row_height = ImMax(row_height, CalcTextSize(TableGetColumnName(table, column_n)).y); - return row_height + g.Style.CellPadding.y * 2.0f; -} - -float ImGui::TableGetHeaderAngledMaxLabelWidth() -{ - ImGuiContext& g = *GImGui; - ImGuiTable* table = g.CurrentTable; - float width = 0.0f; - for (int column_n = 0; column_n < table->ColumnsCount; column_n++) - if (IM_BITARRAY_TESTBIT(table->EnabledMaskByIndex, column_n)) - if (table->Columns[column_n].Flags & ImGuiTableColumnFlags_AngledHeader) - width = ImMax(width, CalcTextSize(TableGetColumnName(table, column_n), NULL, true).x); - return width + g.Style.CellPadding.x * 2.0f; -} - -// [Public] This is a helper to output TableHeader() calls based on the column names declared in TableSetupColumn(). -// The intent is that advanced users willing to create customized headers would not need to use this helper -// and can create their own! For example: TableHeader() may be preceeded by Checkbox() or other custom widgets. -// See 'Demo->Tables->Custom headers' for a demonstration of implementing a custom version of this. -// This code is constructed to not make much use of internal functions, as it is intended to be a template to copy. -// FIXME-TABLE: TableOpenContextMenu() and TableGetHeaderRowHeight() are not public. -void ImGui::TableHeadersRow() -{ - ImGuiContext& g = *GImGui; - ImGuiTable* table = g.CurrentTable; - IM_ASSERT(table != NULL && "Need to call TableHeadersRow() after BeginTable()!"); - - // Layout if not already done (this is automatically done by TableNextRow, we do it here solely to facilitate stepping in debugger as it is frequent to step in TableUpdateLayout) - if (!table->IsLayoutLocked) - TableUpdateLayout(table); - - // Open row - const float row_height = TableGetHeaderRowHeight(); - TableNextRow(ImGuiTableRowFlags_Headers, row_height); - const float row_y1 = GetCursorScreenPos().y; - if (table->HostSkipItems) // Merely an optimization, you may skip in your own code. - return; - - const int columns_count = TableGetColumnCount(); - for (int column_n = 0; column_n < columns_count; column_n++) - { - if (!TableSetColumnIndex(column_n)) - continue; - - // Push an id to allow unnamed labels (generally accidental, but let's behave nicely with them) - // In your own code you may omit the PushID/PopID all-together, provided you know they won't collide. - const char* name = (TableGetColumnFlags(column_n) & ImGuiTableColumnFlags_NoHeaderLabel) ? "" : TableGetColumnName(column_n); - PushID(column_n); - TableHeader(name); - PopID(); - } - - // Allow opening popup from the right-most section after the last column. - ImVec2 mouse_pos = ImGui::GetMousePos(); - if (IsMouseReleased(1) && TableGetHoveredColumn() == columns_count) - if (mouse_pos.y >= row_y1 && mouse_pos.y < row_y1 + row_height) - TableOpenContextMenu(columns_count); // Will open a non-column-specific popup. -} - -// Emit a column header (text + optional sort order) -// We cpu-clip text here so that all columns headers can be merged into a same draw call. -// Note that because of how we cpu-clip and display sorting indicators, you _cannot_ use SameLine() after a TableHeader() -void ImGui::TableHeader(const char* label) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - if (window->SkipItems) - return; - - ImGuiTable* table = g.CurrentTable; - IM_ASSERT(table != NULL && "Need to call TableHeader() after BeginTable()!"); - IM_ASSERT(table->CurrentColumn != -1); - const int column_n = table->CurrentColumn; - ImGuiTableColumn* column = &table->Columns[column_n]; - - // Label - if (label == NULL) - label = ""; - const char* label_end = FindRenderedTextEnd(label); - ImVec2 label_size = CalcTextSize(label, label_end, true); - ImVec2 label_pos = window->DC.CursorPos; - - // If we already got a row height, there's use that. - // FIXME-TABLE: Padding problem if the correct outer-padding CellBgRect strays off our ClipRect? - ImRect cell_r = TableGetCellBgRect(table, column_n); - float label_height = ImMax(label_size.y, table->RowMinHeight - table->RowCellPaddingY * 2.0f); - - // Calculate ideal size for sort order arrow - float w_arrow = 0.0f; - float w_sort_text = 0.0f; - char sort_order_suf[4] = ""; - const float ARROW_SCALE = 0.65f; - if ((table->Flags & ImGuiTableFlags_Sortable) && !(column->Flags & ImGuiTableColumnFlags_NoSort)) - { - w_arrow = ImTrunc(g.FontSize * ARROW_SCALE + g.Style.FramePadding.x); - if (column->SortOrder > 0) - { - ImFormatString(sort_order_suf, IM_ARRAYSIZE(sort_order_suf), "%d", column->SortOrder + 1); - w_sort_text = g.Style.ItemInnerSpacing.x + CalcTextSize(sort_order_suf).x; - } - } - - // We feed our unclipped width to the column without writing on CursorMaxPos, so that column is still considering for merging. - float max_pos_x = label_pos.x + label_size.x + w_sort_text + w_arrow; - column->ContentMaxXHeadersUsed = ImMax(column->ContentMaxXHeadersUsed, column->WorkMaxX); - column->ContentMaxXHeadersIdeal = ImMax(column->ContentMaxXHeadersIdeal, max_pos_x); - - // Keep header highlighted when context menu is open. - ImGuiID id = window->GetID(label); - ImRect bb(cell_r.Min.x, cell_r.Min.y, cell_r.Max.x, ImMax(cell_r.Max.y, cell_r.Min.y + label_height + g.Style.CellPadding.y * 2.0f)); - ItemSize(ImVec2(0.0f, label_height)); // Don't declare unclipped width, it'll be fed ContentMaxPosHeadersIdeal - if (!ItemAdd(bb, id)) - return; - - //GetForegroundDrawList()->AddRect(cell_r.Min, cell_r.Max, IM_COL32(255, 0, 0, 255)); // [DEBUG] - //GetForegroundDrawList()->AddRect(bb.Min, bb.Max, IM_COL32(255, 0, 0, 255)); // [DEBUG] - - // Using AllowOverlap mode because we cover the whole cell, and we want user to be able to submit subsequent items. - const bool highlight = (table->HighlightColumnHeader == column_n); - bool hovered, held; - bool pressed = ButtonBehavior(bb, id, &hovered, &held, ImGuiButtonFlags_AllowOverlap); - if (held || hovered || highlight) - { - const ImU32 col = GetColorU32(held ? ImGuiCol_HeaderActive : hovered ? ImGuiCol_HeaderHovered : ImGuiCol_Header); - //RenderFrame(bb.Min, bb.Max, col, false, 0.0f); - TableSetBgColor(ImGuiTableBgTarget_CellBg, col, table->CurrentColumn); - } - else - { - // Submit single cell bg color in the case we didn't submit a full header row - if ((table->RowFlags & ImGuiTableRowFlags_Headers) == 0) - TableSetBgColor(ImGuiTableBgTarget_CellBg, GetColorU32(ImGuiCol_TableHeaderBg), table->CurrentColumn); - } - RenderNavHighlight(bb, id, ImGuiNavHighlightFlags_TypeThin | ImGuiNavHighlightFlags_NoRounding); - if (held) - table->HeldHeaderColumn = (ImGuiTableColumnIdx)column_n; - window->DC.CursorPos.y -= g.Style.ItemSpacing.y * 0.5f; - - // Drag and drop to re-order columns. - // FIXME-TABLE: Scroll request while reordering a column and it lands out of the scrolling zone. - if (held && (table->Flags & ImGuiTableFlags_Reorderable) && IsMouseDragging(0) && !g.DragDropActive) - { - // While moving a column it will jump on the other side of the mouse, so we also test for MouseDelta.x - table->ReorderColumn = (ImGuiTableColumnIdx)column_n; - table->InstanceInteracted = table->InstanceCurrent; - - // We don't reorder: through the frozen<>unfrozen line, or through a column that is marked with ImGuiTableColumnFlags_NoReorder. - if (g.IO.MouseDelta.x < 0.0f && g.IO.MousePos.x < cell_r.Min.x) - if (ImGuiTableColumn* prev_column = (column->PrevEnabledColumn != -1) ? &table->Columns[column->PrevEnabledColumn] : NULL) - if (!((column->Flags | prev_column->Flags) & ImGuiTableColumnFlags_NoReorder)) - if ((column->IndexWithinEnabledSet < table->FreezeColumnsRequest) == (prev_column->IndexWithinEnabledSet < table->FreezeColumnsRequest)) - table->ReorderColumnDir = -1; - if (g.IO.MouseDelta.x > 0.0f && g.IO.MousePos.x > cell_r.Max.x) - if (ImGuiTableColumn* next_column = (column->NextEnabledColumn != -1) ? &table->Columns[column->NextEnabledColumn] : NULL) - if (!((column->Flags | next_column->Flags) & ImGuiTableColumnFlags_NoReorder)) - if ((column->IndexWithinEnabledSet < table->FreezeColumnsRequest) == (next_column->IndexWithinEnabledSet < table->FreezeColumnsRequest)) - table->ReorderColumnDir = +1; - } - - // Sort order arrow - const float ellipsis_max = ImMax(cell_r.Max.x - w_arrow - w_sort_text, label_pos.x); - if ((table->Flags & ImGuiTableFlags_Sortable) && !(column->Flags & ImGuiTableColumnFlags_NoSort)) - { - if (column->SortOrder != -1) - { - float x = ImMax(cell_r.Min.x, cell_r.Max.x - w_arrow - w_sort_text); - float y = label_pos.y; - if (column->SortOrder > 0) - { - PushStyleColor(ImGuiCol_Text, GetColorU32(ImGuiCol_Text, 0.70f)); - RenderText(ImVec2(x + g.Style.ItemInnerSpacing.x, y), sort_order_suf); - PopStyleColor(); - x += w_sort_text; - } - RenderArrow(window->DrawList, ImVec2(x, y), GetColorU32(ImGuiCol_Text), column->SortDirection == ImGuiSortDirection_Ascending ? ImGuiDir_Up : ImGuiDir_Down, ARROW_SCALE); - } - - // Handle clicking on column header to adjust Sort Order - if (pressed && table->ReorderColumn != column_n) - { - ImGuiSortDirection sort_direction = TableGetColumnNextSortDirection(column); - TableSetColumnSortDirection(column_n, sort_direction, g.IO.KeyShift); - } - } - - // Render clipped label. Clipping here ensure that in the majority of situations, all our header cells will - // be merged into a single draw call. - //window->DrawList->AddCircleFilled(ImVec2(ellipsis_max, label_pos.y), 40, IM_COL32_WHITE); - RenderTextEllipsis(window->DrawList, label_pos, ImVec2(ellipsis_max, label_pos.y + label_height + g.Style.FramePadding.y), ellipsis_max, ellipsis_max, label, label_end, &label_size); - - const bool text_clipped = label_size.x > (ellipsis_max - label_pos.x); - if (text_clipped && hovered && g.ActiveId == 0) - SetItemTooltip("%.*s", (int)(label_end - label), label); - - // We don't use BeginPopupContextItem() because we want the popup to stay up even after the column is hidden - if (IsMouseReleased(1) && IsItemHovered()) - TableOpenContextMenu(column_n); -} - -// Unlike TableHeadersRow() it is not expected that you can reimplement or customize this with custom widgets. -// FIXME: highlight without ImGuiTableFlags_HighlightHoveredColumn -// FIXME: No hit-testing/button on the angled header. -void ImGui::TableAngledHeadersRow() -{ - ImGuiContext& g = *GImGui; - TableAngledHeadersRowEx(g.Style.TableAngledHeadersAngle, 0.0f); -} - -void ImGui::TableAngledHeadersRowEx(float angle, float max_label_width) -{ - ImGuiContext& g = *GImGui; - ImGuiTable* table = g.CurrentTable; - ImGuiWindow* window = g.CurrentWindow; - ImDrawList* draw_list = window->DrawList; - IM_ASSERT(table != NULL && "Need to call TableHeadersRow() after BeginTable()!"); - IM_ASSERT(table->CurrentRow == -1 && "Must be first row"); - - if (max_label_width == 0.0f) - max_label_width = TableGetHeaderAngledMaxLabelWidth(); - - // Angle argument expressed in (-IM_PI/2 .. +IM_PI/2) as it is easier to think about for user. - const bool flip_label = (angle < 0.0f); - angle -= IM_PI * 0.5f; - const float cos_a = ImCos(angle); - const float sin_a = ImSin(angle); - const float label_cos_a = flip_label ? ImCos(angle + IM_PI) : cos_a; - const float label_sin_a = flip_label ? ImSin(angle + IM_PI) : sin_a; - const ImVec2 unit_right = ImVec2(cos_a, sin_a); - - // Calculate our base metrics and set angled headers data _before_ the first call to TableNextRow() - // FIXME-STYLE: Would it be better for user to submit 'max_label_width' or 'row_height' ? One can be derived from the other. - const float header_height = table->RowCellPaddingY * 2.0f + g.FontSize; - const float row_height = ImFabs(ImRotate(ImVec2(max_label_width, flip_label ? +header_height : -header_height), cos_a, sin_a).y); - const ImVec2 header_angled_vector = unit_right * (row_height / -sin_a); - table->AngledHeadersHeight = row_height; - table->AngledHeadersSlope = (sin_a != 0.0f) ? (cos_a / sin_a) : 0.0f; - - // Declare row, override and draw our own background - TableNextRow(ImGuiTableRowFlags_Headers, row_height); - TableNextColumn(); - table->DrawSplitter->SetCurrentChannel(draw_list, TABLE_DRAW_CHANNEL_BG0); - float clip_rect_min_x = table->BgClipRect.Min.x; - if (table->FreezeColumnsCount > 0) - clip_rect_min_x = ImMax(clip_rect_min_x, table->Columns[table->FreezeColumnsCount - 1].MaxX); - TableSetBgColor(ImGuiTableBgTarget_RowBg0, 0); // Cancel - PushClipRect(table->BgClipRect.Min, table->BgClipRect.Max, false); // Span all columns - draw_list->AddRectFilled(table->BgClipRect.Min, table->BgClipRect.Max, GetColorU32(ImGuiCol_TableHeaderBg, 0.25f)); // FIXME-STYLE: Change row background with an arbitrary color. - PushClipRect(ImVec2(clip_rect_min_x, table->BgClipRect.Min.y), table->BgClipRect.Max, true); // Span all columns - - const ImRect row_r(table->WorkRect.Min.x, table->BgClipRect.Min.y, table->WorkRect.Max.x, window->DC.CursorPos.y + row_height); - const ImGuiID row_id = GetID("##AngledHeaders"); - ButtonBehavior(row_r, row_id, NULL, NULL); - KeepAliveID(row_id); - - ImGuiTableInstanceData* table_instance = TableGetInstanceData(table, table->InstanceCurrent); - int highlight_column_n = table->HighlightColumnHeader; - if (highlight_column_n == -1 && table->HoveredColumnBody != -1) - if (table_instance->HoveredRowLast == 0 && table->HoveredColumnBorder == -1 && (g.ActiveId == 0 || g.ActiveId == row_id || (table->IsActiveIdInTable || g.DragDropActive))) - highlight_column_n = table->HoveredColumnBody; - - float max_x = 0.0f; - for (int pass = 0; pass < 2; pass++) - for (int order_n = 0; order_n < table->ColumnsCount; order_n++) - { - if (!IM_BITARRAY_TESTBIT(table->EnabledMaskByDisplayOrder, order_n)) - continue; - const int column_n = table->DisplayOrderToIndex[order_n]; - ImGuiTableColumn* column = &table->Columns[column_n]; - if ((column->Flags & ImGuiTableColumnFlags_AngledHeader) == 0) // Note: can't rely on ImGuiTableColumnFlags_IsVisible test here. - continue; - - ImVec2 bg_shape[4]; - bg_shape[0] = ImVec2(column->MaxX, row_r.Max.y); - bg_shape[1] = ImVec2(column->MinX, row_r.Max.y); - bg_shape[2] = bg_shape[1] + header_angled_vector; - bg_shape[3] = bg_shape[0] + header_angled_vector; - if (pass == 0) - { - // Draw shape - draw_list->AddQuadFilled(bg_shape[0], bg_shape[1], bg_shape[2], bg_shape[3], GetColorU32(ImGuiCol_TableHeaderBg)); - if (column_n == highlight_column_n) - draw_list->AddQuadFilled(bg_shape[0], bg_shape[1], bg_shape[2], bg_shape[3], GetColorU32(ImGuiCol_Header)); // Highlight on hover - //draw_list->AddQuad(bg_shape[0], bg_shape[1], bg_shape[2], bg_shape[3], GetColorU32(ImGuiCol_TableBorderLight), 1.0f); - max_x = ImMax(max_x, bg_shape[3].x); - - // Draw label (first draw at an offset where RenderTextXXX() function won't meddle with applying current ClipRect, then transform to final offset) - // FIXME: May be worth tidying up all those operations to make them easier to understand. - const char* label_name = TableGetColumnName(table, column_n); - const float clip_width = max_label_width - (sin_a * table->RowCellPaddingY); - ImRect label_r(window->ClipRect.Min, window->ClipRect.Min + ImVec2(clip_width + (flip_label ? 0.0f : table->CellPaddingX), header_height + table->RowCellPaddingY)); - ImVec2 label_size = CalcTextSize(label_name, NULL, true); - ImVec2 label_off = ImVec2(flip_label ? ImMax(0.0f, max_label_width - label_size.x - table->CellPaddingX) : table->CellPaddingX, table->RowCellPaddingY); - int vtx_idx_begin = draw_list->_VtxCurrentIdx; - RenderTextEllipsis(draw_list, label_r.Min + label_off, label_r.Max, label_r.Max.x, label_r.Max.x, label_name, NULL, &label_size); - //if (g.IO.KeyShift) { draw_list->AddRect(label_r.Min, label_r.Max, IM_COL32(0, 255, 0, 255), 0.0f, 0, 2.0f); } - int vtx_idx_end = draw_list->_VtxCurrentIdx; - - // Rotate and offset label - ImVec2 pivot_in = label_r.GetBL(); - ImVec2 pivot_out = ImVec2(column->WorkMinX, row_r.Max.y) + (flip_label ? (unit_right * clip_width) : ImVec2(header_height, 0.0f)); - ShadeVertsTransformPos(draw_list, vtx_idx_begin, vtx_idx_end, pivot_in, label_cos_a, label_sin_a, pivot_out); // Rotate and offset - } - if (pass == 1) - { - // Draw border - draw_list->AddLine(bg_shape[0], bg_shape[3], TableGetColumnBorderCol(table, order_n, column_n)); - } - } - PopClipRect(); - PopClipRect(); - table->TempData->AngledheadersExtraWidth = ImMax(0.0f, max_x - table->Columns[table->RightMostEnabledColumn].MaxX); -} - -//------------------------------------------------------------------------- -// [SECTION] Tables: Context Menu -//------------------------------------------------------------------------- -// - TableOpenContextMenu() [Internal] -// - TableDrawContextMenu() [Internal] -//------------------------------------------------------------------------- - -// Use -1 to open menu not specific to a given column. -void ImGui::TableOpenContextMenu(int column_n) -{ - ImGuiContext& g = *GImGui; - ImGuiTable* table = g.CurrentTable; - if (column_n == -1 && table->CurrentColumn != -1) // When called within a column automatically use this one (for consistency) - column_n = table->CurrentColumn; - if (column_n == table->ColumnsCount) // To facilitate using with TableGetHoveredColumn() - column_n = -1; - IM_ASSERT(column_n >= -1 && column_n < table->ColumnsCount); - if (table->Flags & (ImGuiTableFlags_Resizable | ImGuiTableFlags_Reorderable | ImGuiTableFlags_Hideable)) - { - table->IsContextPopupOpen = true; - table->ContextPopupColumn = (ImGuiTableColumnIdx)column_n; - table->InstanceInteracted = table->InstanceCurrent; - const ImGuiID context_menu_id = ImHashStr("##ContextMenu", 0, table->ID); - OpenPopupEx(context_menu_id, ImGuiPopupFlags_None); - } -} - -bool ImGui::TableBeginContextMenuPopup(ImGuiTable* table) -{ - if (!table->IsContextPopupOpen || table->InstanceCurrent != table->InstanceInteracted) - return false; - const ImGuiID context_menu_id = ImHashStr("##ContextMenu", 0, table->ID); - if (BeginPopupEx(context_menu_id, ImGuiWindowFlags_AlwaysAutoResize | ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_NoSavedSettings)) - return true; - table->IsContextPopupOpen = false; - return false; -} - -// Output context menu into current window (generally a popup) -// FIXME-TABLE: Ideally this should be writable by the user. Full programmatic access to that data? -void ImGui::TableDrawContextMenu(ImGuiTable* table) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - if (window->SkipItems) - return; - - bool want_separator = false; - const int column_n = (table->ContextPopupColumn >= 0 && table->ContextPopupColumn < table->ColumnsCount) ? table->ContextPopupColumn : -1; - ImGuiTableColumn* column = (column_n != -1) ? &table->Columns[column_n] : NULL; - - // Sizing - if (table->Flags & ImGuiTableFlags_Resizable) - { - if (column != NULL) - { - const bool can_resize = !(column->Flags & ImGuiTableColumnFlags_NoResize) && column->IsEnabled; - if (MenuItem(LocalizeGetMsg(ImGuiLocKey_TableSizeOne), NULL, false, can_resize)) // "###SizeOne" - TableSetColumnWidthAutoSingle(table, column_n); - } - - const char* size_all_desc; - if (table->ColumnsEnabledFixedCount == table->ColumnsEnabledCount && (table->Flags & ImGuiTableFlags_SizingMask_) != ImGuiTableFlags_SizingFixedSame) - size_all_desc = LocalizeGetMsg(ImGuiLocKey_TableSizeAllFit); // "###SizeAll" All fixed - else - size_all_desc = LocalizeGetMsg(ImGuiLocKey_TableSizeAllDefault); // "###SizeAll" All stretch or mixed - if (MenuItem(size_all_desc, NULL)) - TableSetColumnWidthAutoAll(table); - want_separator = true; - } - - // Ordering - if (table->Flags & ImGuiTableFlags_Reorderable) - { - if (MenuItem(LocalizeGetMsg(ImGuiLocKey_TableResetOrder), NULL, false, !table->IsDefaultDisplayOrder)) - table->IsResetDisplayOrderRequest = true; - want_separator = true; - } - - // Reset all (should work but seems unnecessary/noisy to expose?) - //if (MenuItem("Reset all")) - // table->IsResetAllRequest = true; - - // Sorting - // (modify TableOpenContextMenu() to add _Sortable flag if enabling this) -#if 0 - if ((table->Flags & ImGuiTableFlags_Sortable) && column != NULL && (column->Flags & ImGuiTableColumnFlags_NoSort) == 0) - { - if (want_separator) - Separator(); - want_separator = true; - - bool append_to_sort_specs = g.IO.KeyShift; - if (MenuItem("Sort in Ascending Order", NULL, column->SortOrder != -1 && column->SortDirection == ImGuiSortDirection_Ascending, (column->Flags & ImGuiTableColumnFlags_NoSortAscending) == 0)) - TableSetColumnSortDirection(table, column_n, ImGuiSortDirection_Ascending, append_to_sort_specs); - if (MenuItem("Sort in Descending Order", NULL, column->SortOrder != -1 && column->SortDirection == ImGuiSortDirection_Descending, (column->Flags & ImGuiTableColumnFlags_NoSortDescending) == 0)) - TableSetColumnSortDirection(table, column_n, ImGuiSortDirection_Descending, append_to_sort_specs); - } -#endif - - // Hiding / Visibility - if (table->Flags & ImGuiTableFlags_Hideable) - { - if (want_separator) - Separator(); - want_separator = true; - - PushItemFlag(ImGuiItemFlags_SelectableDontClosePopup, true); - for (int other_column_n = 0; other_column_n < table->ColumnsCount; other_column_n++) - { - ImGuiTableColumn* other_column = &table->Columns[other_column_n]; - if (other_column->Flags & ImGuiTableColumnFlags_Disabled) - continue; - - const char* name = TableGetColumnName(table, other_column_n); - if (name == NULL || name[0] == 0) - name = ""; - - // Make sure we can't hide the last active column - bool menu_item_active = (other_column->Flags & ImGuiTableColumnFlags_NoHide) ? false : true; - if (other_column->IsUserEnabled && table->ColumnsEnabledCount <= 1) - menu_item_active = false; - if (MenuItem(name, NULL, other_column->IsUserEnabled, menu_item_active)) - other_column->IsUserEnabledNextFrame = !other_column->IsUserEnabled; - } - PopItemFlag(); - } -} - -//------------------------------------------------------------------------- -// [SECTION] Tables: Settings (.ini data) -//------------------------------------------------------------------------- -// FIXME: The binding/finding/creating flow are too confusing. -//------------------------------------------------------------------------- -// - TableSettingsInit() [Internal] -// - TableSettingsCalcChunkSize() [Internal] -// - TableSettingsCreate() [Internal] -// - TableSettingsFindByID() [Internal] -// - TableGetBoundSettings() [Internal] -// - TableResetSettings() -// - TableSaveSettings() [Internal] -// - TableLoadSettings() [Internal] -// - TableSettingsHandler_ClearAll() [Internal] -// - TableSettingsHandler_ApplyAll() [Internal] -// - TableSettingsHandler_ReadOpen() [Internal] -// - TableSettingsHandler_ReadLine() [Internal] -// - TableSettingsHandler_WriteAll() [Internal] -// - TableSettingsInstallHandler() [Internal] -//------------------------------------------------------------------------- -// [Init] 1: TableSettingsHandler_ReadXXXX() Load and parse .ini file into TableSettings. -// [Main] 2: TableLoadSettings() When table is created, bind Table to TableSettings, serialize TableSettings data into Table. -// [Main] 3: TableSaveSettings() When table properties are modified, serialize Table data into bound or new TableSettings, mark .ini as dirty. -// [Main] 4: TableSettingsHandler_WriteAll() When .ini file is dirty (which can come from other source), save TableSettings into .ini file. -//------------------------------------------------------------------------- - -// Clear and initialize empty settings instance -static void TableSettingsInit(ImGuiTableSettings* settings, ImGuiID id, int columns_count, int columns_count_max) -{ - IM_PLACEMENT_NEW(settings) ImGuiTableSettings(); - ImGuiTableColumnSettings* settings_column = settings->GetColumnSettings(); - for (int n = 0; n < columns_count_max; n++, settings_column++) - IM_PLACEMENT_NEW(settings_column) ImGuiTableColumnSettings(); - settings->ID = id; - settings->ColumnsCount = (ImGuiTableColumnIdx)columns_count; - settings->ColumnsCountMax = (ImGuiTableColumnIdx)columns_count_max; - settings->WantApply = true; -} - -static size_t TableSettingsCalcChunkSize(int columns_count) -{ - return sizeof(ImGuiTableSettings) + (size_t)columns_count * sizeof(ImGuiTableColumnSettings); -} - -ImGuiTableSettings* ImGui::TableSettingsCreate(ImGuiID id, int columns_count) -{ - ImGuiContext& g = *GImGui; - ImGuiTableSettings* settings = g.SettingsTables.alloc_chunk(TableSettingsCalcChunkSize(columns_count)); - TableSettingsInit(settings, id, columns_count, columns_count); - return settings; -} - -// Find existing settings -ImGuiTableSettings* ImGui::TableSettingsFindByID(ImGuiID id) -{ - // FIXME-OPT: Might want to store a lookup map for this? - ImGuiContext& g = *GImGui; - for (ImGuiTableSettings* settings = g.SettingsTables.begin(); settings != NULL; settings = g.SettingsTables.next_chunk(settings)) - if (settings->ID == id) - return settings; - return NULL; -} - -// Get settings for a given table, NULL if none -ImGuiTableSettings* ImGui::TableGetBoundSettings(ImGuiTable* table) -{ - if (table->SettingsOffset != -1) - { - ImGuiContext& g = *GImGui; - ImGuiTableSettings* settings = g.SettingsTables.ptr_from_offset(table->SettingsOffset); - IM_ASSERT(settings->ID == table->ID); - if (settings->ColumnsCountMax >= table->ColumnsCount) - return settings; // OK - settings->ID = 0; // Invalidate storage, we won't fit because of a count change - } - return NULL; -} - -// Restore initial state of table (with or without saved settings) -void ImGui::TableResetSettings(ImGuiTable* table) -{ - table->IsInitializing = table->IsSettingsDirty = true; - table->IsResetAllRequest = false; - table->IsSettingsRequestLoad = false; // Don't reload from ini - table->SettingsLoadedFlags = ImGuiTableFlags_None; // Mark as nothing loaded so our initialized data becomes authoritative -} - -void ImGui::TableSaveSettings(ImGuiTable* table) -{ - table->IsSettingsDirty = false; - if (table->Flags & ImGuiTableFlags_NoSavedSettings) - return; - - // Bind or create settings data - ImGuiContext& g = *GImGui; - ImGuiTableSettings* settings = TableGetBoundSettings(table); - if (settings == NULL) - { - settings = TableSettingsCreate(table->ID, table->ColumnsCount); - table->SettingsOffset = g.SettingsTables.offset_from_ptr(settings); - } - settings->ColumnsCount = (ImGuiTableColumnIdx)table->ColumnsCount; - - // Serialize ImGuiTable/ImGuiTableColumn into ImGuiTableSettings/ImGuiTableColumnSettings - IM_ASSERT(settings->ID == table->ID); - IM_ASSERT(settings->ColumnsCount == table->ColumnsCount && settings->ColumnsCountMax >= settings->ColumnsCount); - ImGuiTableColumn* column = table->Columns.Data; - ImGuiTableColumnSettings* column_settings = settings->GetColumnSettings(); - - bool save_ref_scale = false; - settings->SaveFlags = ImGuiTableFlags_None; - for (int n = 0; n < table->ColumnsCount; n++, column++, column_settings++) - { - const float width_or_weight = (column->Flags & ImGuiTableColumnFlags_WidthStretch) ? column->StretchWeight : column->WidthRequest; - column_settings->WidthOrWeight = width_or_weight; - column_settings->Index = (ImGuiTableColumnIdx)n; - column_settings->DisplayOrder = column->DisplayOrder; - column_settings->SortOrder = column->SortOrder; - column_settings->SortDirection = column->SortDirection; - column_settings->IsEnabled = column->IsUserEnabled; - column_settings->IsStretch = (column->Flags & ImGuiTableColumnFlags_WidthStretch) ? 1 : 0; - if ((column->Flags & ImGuiTableColumnFlags_WidthStretch) == 0) - save_ref_scale = true; - - // We skip saving some data in the .ini file when they are unnecessary to restore our state. - // Note that fixed width where initial width was derived from auto-fit will always be saved as InitStretchWeightOrWidth will be 0.0f. - // FIXME-TABLE: We don't have logic to easily compare SortOrder to DefaultSortOrder yet so it's always saved when present. - if (width_or_weight != column->InitStretchWeightOrWidth) - settings->SaveFlags |= ImGuiTableFlags_Resizable; - if (column->DisplayOrder != n) - settings->SaveFlags |= ImGuiTableFlags_Reorderable; - if (column->SortOrder != -1) - settings->SaveFlags |= ImGuiTableFlags_Sortable; - if (column->IsUserEnabled != ((column->Flags & ImGuiTableColumnFlags_DefaultHide) == 0)) - settings->SaveFlags |= ImGuiTableFlags_Hideable; - } - settings->SaveFlags &= table->Flags; - settings->RefScale = save_ref_scale ? table->RefScale : 0.0f; - - MarkIniSettingsDirty(); -} - -void ImGui::TableLoadSettings(ImGuiTable* table) -{ - ImGuiContext& g = *GImGui; - table->IsSettingsRequestLoad = false; - if (table->Flags & ImGuiTableFlags_NoSavedSettings) - return; - - // Bind settings - ImGuiTableSettings* settings; - if (table->SettingsOffset == -1) - { - settings = TableSettingsFindByID(table->ID); - if (settings == NULL) - return; - if (settings->ColumnsCount != table->ColumnsCount) // Allow settings if columns count changed. We could otherwise decide to return... - table->IsSettingsDirty = true; - table->SettingsOffset = g.SettingsTables.offset_from_ptr(settings); - } - else - { - settings = TableGetBoundSettings(table); - } - - table->SettingsLoadedFlags = settings->SaveFlags; - table->RefScale = settings->RefScale; - - // Serialize ImGuiTableSettings/ImGuiTableColumnSettings into ImGuiTable/ImGuiTableColumn - ImGuiTableColumnSettings* column_settings = settings->GetColumnSettings(); - ImU64 display_order_mask = 0; - for (int data_n = 0; data_n < settings->ColumnsCount; data_n++, column_settings++) - { - int column_n = column_settings->Index; - if (column_n < 0 || column_n >= table->ColumnsCount) - continue; - - ImGuiTableColumn* column = &table->Columns[column_n]; - if (settings->SaveFlags & ImGuiTableFlags_Resizable) - { - if (column_settings->IsStretch) - column->StretchWeight = column_settings->WidthOrWeight; - else - column->WidthRequest = column_settings->WidthOrWeight; - column->AutoFitQueue = 0x00; - } - if (settings->SaveFlags & ImGuiTableFlags_Reorderable) - column->DisplayOrder = column_settings->DisplayOrder; - else - column->DisplayOrder = (ImGuiTableColumnIdx)column_n; - display_order_mask |= (ImU64)1 << column->DisplayOrder; - column->IsUserEnabled = column->IsUserEnabledNextFrame = column_settings->IsEnabled; - column->SortOrder = column_settings->SortOrder; - column->SortDirection = column_settings->SortDirection; - } - - // Validate and fix invalid display order data - const ImU64 expected_display_order_mask = (settings->ColumnsCount == 64) ? ~0 : ((ImU64)1 << settings->ColumnsCount) - 1; - if (display_order_mask != expected_display_order_mask) - for (int column_n = 0; column_n < table->ColumnsCount; column_n++) - table->Columns[column_n].DisplayOrder = (ImGuiTableColumnIdx)column_n; - - // Rebuild index - for (int column_n = 0; column_n < table->ColumnsCount; column_n++) - table->DisplayOrderToIndex[table->Columns[column_n].DisplayOrder] = (ImGuiTableColumnIdx)column_n; -} - -static void TableSettingsHandler_ClearAll(ImGuiContext* ctx, ImGuiSettingsHandler*) -{ - ImGuiContext& g = *ctx; - for (int i = 0; i != g.Tables.GetMapSize(); i++) - if (ImGuiTable* table = g.Tables.TryGetMapData(i)) - table->SettingsOffset = -1; - g.SettingsTables.clear(); -} - -// Apply to existing windows (if any) -static void TableSettingsHandler_ApplyAll(ImGuiContext* ctx, ImGuiSettingsHandler*) -{ - ImGuiContext& g = *ctx; - for (int i = 0; i != g.Tables.GetMapSize(); i++) - if (ImGuiTable* table = g.Tables.TryGetMapData(i)) - { - table->IsSettingsRequestLoad = true; - table->SettingsOffset = -1; - } -} - -static void* TableSettingsHandler_ReadOpen(ImGuiContext*, ImGuiSettingsHandler*, const char* name) -{ - ImGuiID id = 0; - int columns_count = 0; - if (sscanf(name, "0x%08X,%d", &id, &columns_count) < 2) - return NULL; - - if (ImGuiTableSettings* settings = ImGui::TableSettingsFindByID(id)) - { - if (settings->ColumnsCountMax >= columns_count) - { - TableSettingsInit(settings, id, columns_count, settings->ColumnsCountMax); // Recycle - return settings; - } - settings->ID = 0; // Invalidate storage, we won't fit because of a count change - } - return ImGui::TableSettingsCreate(id, columns_count); -} - -static void TableSettingsHandler_ReadLine(ImGuiContext*, ImGuiSettingsHandler*, void* entry, const char* line) -{ - // "Column 0 UserID=0x42AD2D21 Width=100 Visible=1 Order=0 Sort=0v" - ImGuiTableSettings* settings = (ImGuiTableSettings*)entry; - float f = 0.0f; - int column_n = 0, r = 0, n = 0; - - if (sscanf(line, "RefScale=%f", &f) == 1) { settings->RefScale = f; return; } - - if (sscanf(line, "Column %d%n", &column_n, &r) == 1) - { - if (column_n < 0 || column_n >= settings->ColumnsCount) - return; - line = ImStrSkipBlank(line + r); - char c = 0; - ImGuiTableColumnSettings* column = settings->GetColumnSettings() + column_n; - column->Index = (ImGuiTableColumnIdx)column_n; - if (sscanf(line, "UserID=0x%08X%n", (ImU32*)&n, &r)==1) { line = ImStrSkipBlank(line + r); column->UserID = (ImGuiID)n; } - if (sscanf(line, "Width=%d%n", &n, &r) == 1) { line = ImStrSkipBlank(line + r); column->WidthOrWeight = (float)n; column->IsStretch = 0; settings->SaveFlags |= ImGuiTableFlags_Resizable; } - if (sscanf(line, "Weight=%f%n", &f, &r) == 1) { line = ImStrSkipBlank(line + r); column->WidthOrWeight = f; column->IsStretch = 1; settings->SaveFlags |= ImGuiTableFlags_Resizable; } - if (sscanf(line, "Visible=%d%n", &n, &r) == 1) { line = ImStrSkipBlank(line + r); column->IsEnabled = (ImU8)n; settings->SaveFlags |= ImGuiTableFlags_Hideable; } - if (sscanf(line, "Order=%d%n", &n, &r) == 1) { line = ImStrSkipBlank(line + r); column->DisplayOrder = (ImGuiTableColumnIdx)n; settings->SaveFlags |= ImGuiTableFlags_Reorderable; } - if (sscanf(line, "Sort=%d%c%n", &n, &c, &r) == 2) { line = ImStrSkipBlank(line + r); column->SortOrder = (ImGuiTableColumnIdx)n; column->SortDirection = (c == '^') ? ImGuiSortDirection_Descending : ImGuiSortDirection_Ascending; settings->SaveFlags |= ImGuiTableFlags_Sortable; } - } -} - -static void TableSettingsHandler_WriteAll(ImGuiContext* ctx, ImGuiSettingsHandler* handler, ImGuiTextBuffer* buf) -{ - ImGuiContext& g = *ctx; - for (ImGuiTableSettings* settings = g.SettingsTables.begin(); settings != NULL; settings = g.SettingsTables.next_chunk(settings)) - { - if (settings->ID == 0) // Skip ditched settings - continue; - - // TableSaveSettings() may clear some of those flags when we establish that the data can be stripped - // (e.g. Order was unchanged) - const bool save_size = (settings->SaveFlags & ImGuiTableFlags_Resizable) != 0; - const bool save_visible = (settings->SaveFlags & ImGuiTableFlags_Hideable) != 0; - const bool save_order = (settings->SaveFlags & ImGuiTableFlags_Reorderable) != 0; - const bool save_sort = (settings->SaveFlags & ImGuiTableFlags_Sortable) != 0; - if (!save_size && !save_visible && !save_order && !save_sort) - continue; - - buf->reserve(buf->size() + 30 + settings->ColumnsCount * 50); // ballpark reserve - buf->appendf("[%s][0x%08X,%d]\n", handler->TypeName, settings->ID, settings->ColumnsCount); - if (settings->RefScale != 0.0f) - buf->appendf("RefScale=%g\n", settings->RefScale); - ImGuiTableColumnSettings* column = settings->GetColumnSettings(); - for (int column_n = 0; column_n < settings->ColumnsCount; column_n++, column++) - { - // "Column 0 UserID=0x42AD2D21 Width=100 Visible=1 Order=0 Sort=0v" - bool save_column = column->UserID != 0 || save_size || save_visible || save_order || (save_sort && column->SortOrder != -1); - if (!save_column) - continue; - buf->appendf("Column %-2d", column_n); - if (column->UserID != 0) { buf->appendf(" UserID=%08X", column->UserID); } - if (save_size && column->IsStretch) { buf->appendf(" Weight=%.4f", column->WidthOrWeight); } - if (save_size && !column->IsStretch) { buf->appendf(" Width=%d", (int)column->WidthOrWeight); } - if (save_visible) { buf->appendf(" Visible=%d", column->IsEnabled); } - if (save_order) { buf->appendf(" Order=%d", column->DisplayOrder); } - if (save_sort && column->SortOrder != -1) { buf->appendf(" Sort=%d%c", column->SortOrder, (column->SortDirection == ImGuiSortDirection_Ascending) ? 'v' : '^'); } - buf->append("\n"); - } - buf->append("\n"); - } -} - -void ImGui::TableSettingsAddSettingsHandler() -{ - ImGuiSettingsHandler ini_handler; - ini_handler.TypeName = "Table"; - ini_handler.TypeHash = ImHashStr("Table"); - ini_handler.ClearAllFn = TableSettingsHandler_ClearAll; - ini_handler.ReadOpenFn = TableSettingsHandler_ReadOpen; - ini_handler.ReadLineFn = TableSettingsHandler_ReadLine; - ini_handler.ApplyAllFn = TableSettingsHandler_ApplyAll; - ini_handler.WriteAllFn = TableSettingsHandler_WriteAll; - AddSettingsHandler(&ini_handler); -} - -//------------------------------------------------------------------------- -// [SECTION] Tables: Garbage Collection -//------------------------------------------------------------------------- -// - TableRemove() [Internal] -// - TableGcCompactTransientBuffers() [Internal] -// - TableGcCompactSettings() [Internal] -//------------------------------------------------------------------------- - -// Remove Table (currently only used by TestEngine) -void ImGui::TableRemove(ImGuiTable* table) -{ - //IMGUI_DEBUG_PRINT("TableRemove() id=0x%08X\n", table->ID); - ImGuiContext& g = *GImGui; - int table_idx = g.Tables.GetIndex(table); - //memset(table->RawData.Data, 0, table->RawData.size_in_bytes()); - //memset(table, 0, sizeof(ImGuiTable)); - g.Tables.Remove(table->ID, table); - g.TablesLastTimeActive[table_idx] = -1.0f; -} - -// Free up/compact internal Table buffers for when it gets unused -void ImGui::TableGcCompactTransientBuffers(ImGuiTable* table) -{ - //IMGUI_DEBUG_PRINT("TableGcCompactTransientBuffers() id=0x%08X\n", table->ID); - ImGuiContext& g = *GImGui; - IM_ASSERT(table->MemoryCompacted == false); - table->SortSpecs.Specs = NULL; - table->SortSpecsMulti.clear(); - table->IsSortSpecsDirty = true; // FIXME: In theory shouldn't have to leak into user performing a sort on resume. - table->ColumnsNames.clear(); - table->MemoryCompacted = true; - for (int n = 0; n < table->ColumnsCount; n++) - table->Columns[n].NameOffset = -1; - g.TablesLastTimeActive[g.Tables.GetIndex(table)] = -1.0f; -} - -void ImGui::TableGcCompactTransientBuffers(ImGuiTableTempData* temp_data) -{ - temp_data->DrawSplitter.ClearFreeMemory(); - temp_data->LastTimeActive = -1.0f; -} - -// Compact and remove unused settings data (currently only used by TestEngine) -void ImGui::TableGcCompactSettings() -{ - ImGuiContext& g = *GImGui; - int required_memory = 0; - for (ImGuiTableSettings* settings = g.SettingsTables.begin(); settings != NULL; settings = g.SettingsTables.next_chunk(settings)) - if (settings->ID != 0) - required_memory += (int)TableSettingsCalcChunkSize(settings->ColumnsCount); - if (required_memory == g.SettingsTables.Buf.Size) - return; - ImChunkStream new_chunk_stream; - new_chunk_stream.Buf.reserve(required_memory); - for (ImGuiTableSettings* settings = g.SettingsTables.begin(); settings != NULL; settings = g.SettingsTables.next_chunk(settings)) - if (settings->ID != 0) - memcpy(new_chunk_stream.alloc_chunk(TableSettingsCalcChunkSize(settings->ColumnsCount)), settings, TableSettingsCalcChunkSize(settings->ColumnsCount)); - g.SettingsTables.swap(new_chunk_stream); -} - - -//------------------------------------------------------------------------- -// [SECTION] Tables: Debugging -//------------------------------------------------------------------------- -// - DebugNodeTable() [Internal] -//------------------------------------------------------------------------- - -#ifndef IMGUI_DISABLE_DEBUG_TOOLS - -static const char* DebugNodeTableGetSizingPolicyDesc(ImGuiTableFlags sizing_policy) -{ - sizing_policy &= ImGuiTableFlags_SizingMask_; - if (sizing_policy == ImGuiTableFlags_SizingFixedFit) { return "FixedFit"; } - if (sizing_policy == ImGuiTableFlags_SizingFixedSame) { return "FixedSame"; } - if (sizing_policy == ImGuiTableFlags_SizingStretchProp) { return "StretchProp"; } - if (sizing_policy == ImGuiTableFlags_SizingStretchSame) { return "StretchSame"; } - return "N/A"; -} - -void ImGui::DebugNodeTable(ImGuiTable* table) -{ - const bool is_active = (table->LastFrameActive >= GetFrameCount() - 2); // Note that fully clipped early out scrolling tables will appear as inactive here. - if (!is_active) { PushStyleColor(ImGuiCol_Text, GetStyleColorVec4(ImGuiCol_TextDisabled)); } - bool open = TreeNode(table, "Table 0x%08X (%d columns, in '%s')%s", table->ID, table->ColumnsCount, table->OuterWindow->Name, is_active ? "" : " *Inactive*"); - if (!is_active) { PopStyleColor(); } - if (IsItemHovered()) - GetForegroundDrawList()->AddRect(table->OuterRect.Min, table->OuterRect.Max, IM_COL32(255, 255, 0, 255)); - if (IsItemVisible() && table->HoveredColumnBody != -1) - GetForegroundDrawList()->AddRect(GetItemRectMin(), GetItemRectMax(), IM_COL32(255, 255, 0, 255)); - if (!open) - return; - if (table->InstanceCurrent > 0) - Text("** %d instances of same table! Some data below will refer to last instance.", table->InstanceCurrent + 1); - bool clear_settings = SmallButton("Clear settings"); - BulletText("OuterRect: Pos: (%.1f,%.1f) Size: (%.1f,%.1f) Sizing: '%s'", table->OuterRect.Min.x, table->OuterRect.Min.y, table->OuterRect.GetWidth(), table->OuterRect.GetHeight(), DebugNodeTableGetSizingPolicyDesc(table->Flags)); - BulletText("ColumnsGivenWidth: %.1f, ColumnsAutoFitWidth: %.1f, InnerWidth: %.1f%s", table->ColumnsGivenWidth, table->ColumnsAutoFitWidth, table->InnerWidth, table->InnerWidth == 0.0f ? " (auto)" : ""); - BulletText("CellPaddingX: %.1f, CellSpacingX: %.1f/%.1f, OuterPaddingX: %.1f", table->CellPaddingX, table->CellSpacingX1, table->CellSpacingX2, table->OuterPaddingX); - BulletText("HoveredColumnBody: %d, HoveredColumnBorder: %d", table->HoveredColumnBody, table->HoveredColumnBorder); - BulletText("ResizedColumn: %d, ReorderColumn: %d, HeldHeaderColumn: %d", table->ResizedColumn, table->ReorderColumn, table->HeldHeaderColumn); - for (int n = 0; n < table->InstanceCurrent + 1; n++) - { - ImGuiTableInstanceData* table_instance = TableGetInstanceData(table, n); - BulletText("Instance %d: HoveredRow: %d, LastOuterHeight: %.2f", n, table_instance->HoveredRowLast, table_instance->LastOuterHeight); - } - //BulletText("BgDrawChannels: %d/%d", 0, table->BgDrawChannelUnfrozen); - float sum_weights = 0.0f; - for (int n = 0; n < table->ColumnsCount; n++) - if (table->Columns[n].Flags & ImGuiTableColumnFlags_WidthStretch) - sum_weights += table->Columns[n].StretchWeight; - for (int n = 0; n < table->ColumnsCount; n++) - { - ImGuiTableColumn* column = &table->Columns[n]; - const char* name = TableGetColumnName(table, n); - char buf[512]; - ImFormatString(buf, IM_ARRAYSIZE(buf), - "Column %d order %d '%s': offset %+.2f to %+.2f%s\n" - "Enabled: %d, VisibleX/Y: %d/%d, RequestOutput: %d, SkipItems: %d, DrawChannels: %d,%d\n" - "WidthGiven: %.1f, Request/Auto: %.1f/%.1f, StretchWeight: %.3f (%.1f%%)\n" - "MinX: %.1f, MaxX: %.1f (%+.1f), ClipRect: %.1f to %.1f (+%.1f)\n" - "ContentWidth: %.1f,%.1f, HeadersUsed/Ideal %.1f/%.1f\n" - "Sort: %d%s, UserID: 0x%08X, Flags: 0x%04X: %s%s%s..", - n, column->DisplayOrder, name, column->MinX - table->WorkRect.Min.x, column->MaxX - table->WorkRect.Min.x, (n < table->FreezeColumnsRequest) ? " (Frozen)" : "", - column->IsEnabled, column->IsVisibleX, column->IsVisibleY, column->IsRequestOutput, column->IsSkipItems, column->DrawChannelFrozen, column->DrawChannelUnfrozen, - column->WidthGiven, column->WidthRequest, column->WidthAuto, column->StretchWeight, column->StretchWeight > 0.0f ? (column->StretchWeight / sum_weights) * 100.0f : 0.0f, - column->MinX, column->MaxX, column->MaxX - column->MinX, column->ClipRect.Min.x, column->ClipRect.Max.x, column->ClipRect.Max.x - column->ClipRect.Min.x, - column->ContentMaxXFrozen - column->WorkMinX, column->ContentMaxXUnfrozen - column->WorkMinX, column->ContentMaxXHeadersUsed - column->WorkMinX, column->ContentMaxXHeadersIdeal - column->WorkMinX, - column->SortOrder, (column->SortDirection == ImGuiSortDirection_Ascending) ? " (Asc)" : (column->SortDirection == ImGuiSortDirection_Descending) ? " (Des)" : "", column->UserID, column->Flags, - (column->Flags & ImGuiTableColumnFlags_WidthStretch) ? "WidthStretch " : "", - (column->Flags & ImGuiTableColumnFlags_WidthFixed) ? "WidthFixed " : "", - (column->Flags & ImGuiTableColumnFlags_NoResize) ? "NoResize " : ""); - Bullet(); - Selectable(buf); - if (IsItemHovered()) - { - ImRect r(column->MinX, table->OuterRect.Min.y, column->MaxX, table->OuterRect.Max.y); - GetForegroundDrawList()->AddRect(r.Min, r.Max, IM_COL32(255, 255, 0, 255)); - } - } - if (ImGuiTableSettings* settings = TableGetBoundSettings(table)) - DebugNodeTableSettings(settings); - if (clear_settings) - table->IsResetAllRequest = true; - TreePop(); -} - -void ImGui::DebugNodeTableSettings(ImGuiTableSettings* settings) -{ - if (!TreeNode((void*)(intptr_t)settings->ID, "Settings 0x%08X (%d columns)", settings->ID, settings->ColumnsCount)) - return; - BulletText("SaveFlags: 0x%08X", settings->SaveFlags); - BulletText("ColumnsCount: %d (max %d)", settings->ColumnsCount, settings->ColumnsCountMax); - for (int n = 0; n < settings->ColumnsCount; n++) - { - ImGuiTableColumnSettings* column_settings = &settings->GetColumnSettings()[n]; - ImGuiSortDirection sort_dir = (column_settings->SortOrder != -1) ? (ImGuiSortDirection)column_settings->SortDirection : ImGuiSortDirection_None; - BulletText("Column %d Order %d SortOrder %d %s Vis %d %s %7.3f UserID 0x%08X", - n, column_settings->DisplayOrder, column_settings->SortOrder, - (sort_dir == ImGuiSortDirection_Ascending) ? "Asc" : (sort_dir == ImGuiSortDirection_Descending) ? "Des" : "---", - column_settings->IsEnabled, column_settings->IsStretch ? "Weight" : "Width ", column_settings->WidthOrWeight, column_settings->UserID); - } - TreePop(); -} - -#else // #ifndef IMGUI_DISABLE_DEBUG_TOOLS - -void ImGui::DebugNodeTable(ImGuiTable*) {} -void ImGui::DebugNodeTableSettings(ImGuiTableSettings*) {} - -#endif - - -//------------------------------------------------------------------------- -// [SECTION] Columns, BeginColumns, EndColumns, etc. -// (This is a legacy API, prefer using BeginTable/EndTable!) -//------------------------------------------------------------------------- -// FIXME: sizing is lossy when columns width is very small (default width may turn negative etc.) -//------------------------------------------------------------------------- -// - SetWindowClipRectBeforeSetChannel() [Internal] -// - GetColumnIndex() -// - GetColumnsCount() -// - GetColumnOffset() -// - GetColumnWidth() -// - SetColumnOffset() -// - SetColumnWidth() -// - PushColumnClipRect() [Internal] -// - PushColumnsBackground() [Internal] -// - PopColumnsBackground() [Internal] -// - FindOrCreateColumns() [Internal] -// - GetColumnsID() [Internal] -// - BeginColumns() -// - NextColumn() -// - EndColumns() -// - Columns() -//------------------------------------------------------------------------- - -// [Internal] Small optimization to avoid calls to PopClipRect/SetCurrentChannel/PushClipRect in sequences, -// they would meddle many times with the underlying ImDrawCmd. -// Instead, we do a preemptive overwrite of clipping rectangle _without_ altering the command-buffer and let -// the subsequent single call to SetCurrentChannel() does it things once. -void ImGui::SetWindowClipRectBeforeSetChannel(ImGuiWindow* window, const ImRect& clip_rect) -{ - ImVec4 clip_rect_vec4 = clip_rect.ToVec4(); - window->ClipRect = clip_rect; - window->DrawList->_CmdHeader.ClipRect = clip_rect_vec4; - window->DrawList->_ClipRectStack.Data[window->DrawList->_ClipRectStack.Size - 1] = clip_rect_vec4; -} - -int ImGui::GetColumnIndex() -{ - ImGuiWindow* window = GetCurrentWindowRead(); - return window->DC.CurrentColumns ? window->DC.CurrentColumns->Current : 0; -} - -int ImGui::GetColumnsCount() -{ - ImGuiWindow* window = GetCurrentWindowRead(); - return window->DC.CurrentColumns ? window->DC.CurrentColumns->Count : 1; -} - -float ImGui::GetColumnOffsetFromNorm(const ImGuiOldColumns* columns, float offset_norm) -{ - return offset_norm * (columns->OffMaxX - columns->OffMinX); -} - -float ImGui::GetColumnNormFromOffset(const ImGuiOldColumns* columns, float offset) -{ - return offset / (columns->OffMaxX - columns->OffMinX); -} - -static const float COLUMNS_HIT_RECT_HALF_WIDTH = 4.0f; - -static float GetDraggedColumnOffset(ImGuiOldColumns* columns, int column_index) -{ - // Active (dragged) column always follow mouse. The reason we need this is that dragging a column to the right edge of an auto-resizing - // window creates a feedback loop because we store normalized positions. So while dragging we enforce absolute positioning. - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - IM_ASSERT(column_index > 0); // We are not supposed to drag column 0. - IM_ASSERT(g.ActiveId == columns->ID + ImGuiID(column_index)); - - float x = g.IO.MousePos.x - g.ActiveIdClickOffset.x + COLUMNS_HIT_RECT_HALF_WIDTH - window->Pos.x; - x = ImMax(x, ImGui::GetColumnOffset(column_index - 1) + g.Style.ColumnsMinSpacing); - if ((columns->Flags & ImGuiOldColumnFlags_NoPreserveWidths)) - x = ImMin(x, ImGui::GetColumnOffset(column_index + 1) - g.Style.ColumnsMinSpacing); - - return x; -} - -float ImGui::GetColumnOffset(int column_index) -{ - ImGuiWindow* window = GetCurrentWindowRead(); - ImGuiOldColumns* columns = window->DC.CurrentColumns; - if (columns == NULL) - return 0.0f; - - if (column_index < 0) - column_index = columns->Current; - IM_ASSERT(column_index < columns->Columns.Size); - - const float t = columns->Columns[column_index].OffsetNorm; - const float x_offset = ImLerp(columns->OffMinX, columns->OffMaxX, t); - return x_offset; -} - -static float GetColumnWidthEx(ImGuiOldColumns* columns, int column_index, bool before_resize = false) -{ - if (column_index < 0) - column_index = columns->Current; - - float offset_norm; - if (before_resize) - offset_norm = columns->Columns[column_index + 1].OffsetNormBeforeResize - columns->Columns[column_index].OffsetNormBeforeResize; - else - offset_norm = columns->Columns[column_index + 1].OffsetNorm - columns->Columns[column_index].OffsetNorm; - return ImGui::GetColumnOffsetFromNorm(columns, offset_norm); -} - -float ImGui::GetColumnWidth(int column_index) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - ImGuiOldColumns* columns = window->DC.CurrentColumns; - if (columns == NULL) - return GetContentRegionAvail().x; - - if (column_index < 0) - column_index = columns->Current; - return GetColumnOffsetFromNorm(columns, columns->Columns[column_index + 1].OffsetNorm - columns->Columns[column_index].OffsetNorm); -} - -void ImGui::SetColumnOffset(int column_index, float offset) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - ImGuiOldColumns* columns = window->DC.CurrentColumns; - IM_ASSERT(columns != NULL); - - if (column_index < 0) - column_index = columns->Current; - IM_ASSERT(column_index < columns->Columns.Size); - - const bool preserve_width = !(columns->Flags & ImGuiOldColumnFlags_NoPreserveWidths) && (column_index < columns->Count - 1); - const float width = preserve_width ? GetColumnWidthEx(columns, column_index, columns->IsBeingResized) : 0.0f; - - if (!(columns->Flags & ImGuiOldColumnFlags_NoForceWithinWindow)) - offset = ImMin(offset, columns->OffMaxX - g.Style.ColumnsMinSpacing * (columns->Count - column_index)); - columns->Columns[column_index].OffsetNorm = GetColumnNormFromOffset(columns, offset - columns->OffMinX); - - if (preserve_width) - SetColumnOffset(column_index + 1, offset + ImMax(g.Style.ColumnsMinSpacing, width)); -} - -void ImGui::SetColumnWidth(int column_index, float width) -{ - ImGuiWindow* window = GetCurrentWindowRead(); - ImGuiOldColumns* columns = window->DC.CurrentColumns; - IM_ASSERT(columns != NULL); - - if (column_index < 0) - column_index = columns->Current; - SetColumnOffset(column_index + 1, GetColumnOffset(column_index) + width); -} - -void ImGui::PushColumnClipRect(int column_index) -{ - ImGuiWindow* window = GetCurrentWindowRead(); - ImGuiOldColumns* columns = window->DC.CurrentColumns; - if (column_index < 0) - column_index = columns->Current; - - ImGuiOldColumnData* column = &columns->Columns[column_index]; - PushClipRect(column->ClipRect.Min, column->ClipRect.Max, false); -} - -// Get into the columns background draw command (which is generally the same draw command as before we called BeginColumns) -void ImGui::PushColumnsBackground() -{ - ImGuiWindow* window = GetCurrentWindowRead(); - ImGuiOldColumns* columns = window->DC.CurrentColumns; - if (columns->Count == 1) - return; - - // Optimization: avoid SetCurrentChannel() + PushClipRect() - columns->HostBackupClipRect = window->ClipRect; - SetWindowClipRectBeforeSetChannel(window, columns->HostInitialClipRect); - columns->Splitter.SetCurrentChannel(window->DrawList, 0); -} - -void ImGui::PopColumnsBackground() -{ - ImGuiWindow* window = GetCurrentWindowRead(); - ImGuiOldColumns* columns = window->DC.CurrentColumns; - if (columns->Count == 1) - return; - - // Optimization: avoid PopClipRect() + SetCurrentChannel() - SetWindowClipRectBeforeSetChannel(window, columns->HostBackupClipRect); - columns->Splitter.SetCurrentChannel(window->DrawList, columns->Current + 1); -} - -ImGuiOldColumns* ImGui::FindOrCreateColumns(ImGuiWindow* window, ImGuiID id) -{ - // We have few columns per window so for now we don't need bother much with turning this into a faster lookup. - for (int n = 0; n < window->ColumnsStorage.Size; n++) - if (window->ColumnsStorage[n].ID == id) - return &window->ColumnsStorage[n]; - - window->ColumnsStorage.push_back(ImGuiOldColumns()); - ImGuiOldColumns* columns = &window->ColumnsStorage.back(); - columns->ID = id; - return columns; -} - -ImGuiID ImGui::GetColumnsID(const char* str_id, int columns_count) -{ - ImGuiWindow* window = GetCurrentWindow(); - - // Differentiate column ID with an arbitrary prefix for cases where users name their columns set the same as another widget. - // In addition, when an identifier isn't explicitly provided we include the number of columns in the hash to make it uniquer. - PushID(0x11223347 + (str_id ? 0 : columns_count)); - ImGuiID id = window->GetID(str_id ? str_id : "columns"); - PopID(); - - return id; -} - -void ImGui::BeginColumns(const char* str_id, int columns_count, ImGuiOldColumnFlags flags) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = GetCurrentWindow(); - - IM_ASSERT(columns_count >= 1); - IM_ASSERT(window->DC.CurrentColumns == NULL); // Nested columns are currently not supported - - // Acquire storage for the columns set - ImGuiID id = GetColumnsID(str_id, columns_count); - ImGuiOldColumns* columns = FindOrCreateColumns(window, id); - IM_ASSERT(columns->ID == id); - columns->Current = 0; - columns->Count = columns_count; - columns->Flags = flags; - window->DC.CurrentColumns = columns; - window->DC.NavIsScrollPushableX = false; // Shortcut for NavUpdateCurrentWindowIsScrollPushableX(); - - columns->HostCursorPosY = window->DC.CursorPos.y; - columns->HostCursorMaxPosX = window->DC.CursorMaxPos.x; - columns->HostInitialClipRect = window->ClipRect; - columns->HostBackupParentWorkRect = window->ParentWorkRect; - window->ParentWorkRect = window->WorkRect; - - // Set state for first column - // We aim so that the right-most column will have the same clipping width as other after being clipped by parent ClipRect - const float column_padding = g.Style.ItemSpacing.x; - const float half_clip_extend_x = ImTrunc(ImMax(window->WindowPadding.x * 0.5f, window->WindowBorderSize)); - const float max_1 = window->WorkRect.Max.x + column_padding - ImMax(column_padding - window->WindowPadding.x, 0.0f); - const float max_2 = window->WorkRect.Max.x + half_clip_extend_x; - columns->OffMinX = window->DC.Indent.x - column_padding + ImMax(column_padding - window->WindowPadding.x, 0.0f); - columns->OffMaxX = ImMax(ImMin(max_1, max_2) - window->Pos.x, columns->OffMinX + 1.0f); - columns->LineMinY = columns->LineMaxY = window->DC.CursorPos.y; - - // Clear data if columns count changed - if (columns->Columns.Size != 0 && columns->Columns.Size != columns_count + 1) - columns->Columns.resize(0); - - // Initialize default widths - columns->IsFirstFrame = (columns->Columns.Size == 0); - if (columns->Columns.Size == 0) - { - columns->Columns.reserve(columns_count + 1); - for (int n = 0; n < columns_count + 1; n++) - { - ImGuiOldColumnData column; - column.OffsetNorm = n / (float)columns_count; - columns->Columns.push_back(column); - } - } - - for (int n = 0; n < columns_count; n++) - { - // Compute clipping rectangle - ImGuiOldColumnData* column = &columns->Columns[n]; - float clip_x1 = IM_ROUND(window->Pos.x + GetColumnOffset(n)); - float clip_x2 = IM_ROUND(window->Pos.x + GetColumnOffset(n + 1) - 1.0f); - column->ClipRect = ImRect(clip_x1, -FLT_MAX, clip_x2, +FLT_MAX); - column->ClipRect.ClipWithFull(window->ClipRect); - } - - if (columns->Count > 1) - { - columns->Splitter.Split(window->DrawList, 1 + columns->Count); - columns->Splitter.SetCurrentChannel(window->DrawList, 1); - PushColumnClipRect(0); - } - - // We don't generally store Indent.x inside ColumnsOffset because it may be manipulated by the user. - float offset_0 = GetColumnOffset(columns->Current); - float offset_1 = GetColumnOffset(columns->Current + 1); - float width = offset_1 - offset_0; - PushItemWidth(width * 0.65f); - window->DC.ColumnsOffset.x = ImMax(column_padding - window->WindowPadding.x, 0.0f); - window->DC.CursorPos.x = IM_TRUNC(window->Pos.x + window->DC.Indent.x + window->DC.ColumnsOffset.x); - window->WorkRect.Max.x = window->Pos.x + offset_1 - column_padding; - window->WorkRect.Max.y = window->ContentRegionRect.Max.y; -} - -void ImGui::NextColumn() -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems || window->DC.CurrentColumns == NULL) - return; - - ImGuiContext& g = *GImGui; - ImGuiOldColumns* columns = window->DC.CurrentColumns; - - if (columns->Count == 1) - { - window->DC.CursorPos.x = IM_TRUNC(window->Pos.x + window->DC.Indent.x + window->DC.ColumnsOffset.x); - IM_ASSERT(columns->Current == 0); - return; - } - - // Next column - if (++columns->Current == columns->Count) - columns->Current = 0; - - PopItemWidth(); - - // Optimization: avoid PopClipRect() + SetCurrentChannel() + PushClipRect() - // (which would needlessly attempt to update commands in the wrong channel, then pop or overwrite them), - ImGuiOldColumnData* column = &columns->Columns[columns->Current]; - SetWindowClipRectBeforeSetChannel(window, column->ClipRect); - columns->Splitter.SetCurrentChannel(window->DrawList, columns->Current + 1); - - const float column_padding = g.Style.ItemSpacing.x; - columns->LineMaxY = ImMax(columns->LineMaxY, window->DC.CursorPos.y); - if (columns->Current > 0) - { - // Columns 1+ ignore IndentX (by canceling it out) - // FIXME-COLUMNS: Unnecessary, could be locked? - window->DC.ColumnsOffset.x = GetColumnOffset(columns->Current) - window->DC.Indent.x + column_padding; - } - else - { - // New row/line: column 0 honor IndentX. - window->DC.ColumnsOffset.x = ImMax(column_padding - window->WindowPadding.x, 0.0f); - window->DC.IsSameLine = false; - columns->LineMinY = columns->LineMaxY; - } - window->DC.CursorPos.x = IM_TRUNC(window->Pos.x + window->DC.Indent.x + window->DC.ColumnsOffset.x); - window->DC.CursorPos.y = columns->LineMinY; - window->DC.CurrLineSize = ImVec2(0.0f, 0.0f); - window->DC.CurrLineTextBaseOffset = 0.0f; - - // FIXME-COLUMNS: Share code with BeginColumns() - move code on columns setup. - float offset_0 = GetColumnOffset(columns->Current); - float offset_1 = GetColumnOffset(columns->Current + 1); - float width = offset_1 - offset_0; - PushItemWidth(width * 0.65f); - window->WorkRect.Max.x = window->Pos.x + offset_1 - column_padding; -} - -void ImGui::EndColumns() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = GetCurrentWindow(); - ImGuiOldColumns* columns = window->DC.CurrentColumns; - IM_ASSERT(columns != NULL); - - PopItemWidth(); - if (columns->Count > 1) - { - PopClipRect(); - columns->Splitter.Merge(window->DrawList); - } - - const ImGuiOldColumnFlags flags = columns->Flags; - columns->LineMaxY = ImMax(columns->LineMaxY, window->DC.CursorPos.y); - window->DC.CursorPos.y = columns->LineMaxY; - if (!(flags & ImGuiOldColumnFlags_GrowParentContentsSize)) - window->DC.CursorMaxPos.x = columns->HostCursorMaxPosX; // Restore cursor max pos, as columns don't grow parent - - // Draw columns borders and handle resize - // The IsBeingResized flag ensure we preserve pre-resize columns width so back-and-forth are not lossy - bool is_being_resized = false; - if (!(flags & ImGuiOldColumnFlags_NoBorder) && !window->SkipItems) - { - // We clip Y boundaries CPU side because very long triangles are mishandled by some GPU drivers. - const float y1 = ImMax(columns->HostCursorPosY, window->ClipRect.Min.y); - const float y2 = ImMin(window->DC.CursorPos.y, window->ClipRect.Max.y); - int dragging_column = -1; - for (int n = 1; n < columns->Count; n++) - { - ImGuiOldColumnData* column = &columns->Columns[n]; - float x = window->Pos.x + GetColumnOffset(n); - const ImGuiID column_id = columns->ID + ImGuiID(n); - const float column_hit_hw = COLUMNS_HIT_RECT_HALF_WIDTH; - const ImRect column_hit_rect(ImVec2(x - column_hit_hw, y1), ImVec2(x + column_hit_hw, y2)); - if (!ItemAdd(column_hit_rect, column_id, NULL, ImGuiItemFlags_NoNav)) - continue; - - bool hovered = false, held = false; - if (!(flags & ImGuiOldColumnFlags_NoResize)) - { - ButtonBehavior(column_hit_rect, column_id, &hovered, &held); - if (hovered || held) - g.MouseCursor = ImGuiMouseCursor_ResizeEW; - if (held && !(column->Flags & ImGuiOldColumnFlags_NoResize)) - dragging_column = n; - } - - // Draw column - const ImU32 col = GetColorU32(held ? ImGuiCol_SeparatorActive : hovered ? ImGuiCol_SeparatorHovered : ImGuiCol_Separator); - const float xi = IM_TRUNC(x); - window->DrawList->AddLine(ImVec2(xi, y1 + 1.0f), ImVec2(xi, y2), col); - } - - // Apply dragging after drawing the column lines, so our rendered lines are in sync with how items were displayed during the frame. - if (dragging_column != -1) - { - if (!columns->IsBeingResized) - for (int n = 0; n < columns->Count + 1; n++) - columns->Columns[n].OffsetNormBeforeResize = columns->Columns[n].OffsetNorm; - columns->IsBeingResized = is_being_resized = true; - float x = GetDraggedColumnOffset(columns, dragging_column); - SetColumnOffset(dragging_column, x); - } - } - columns->IsBeingResized = is_being_resized; - - window->WorkRect = window->ParentWorkRect; - window->ParentWorkRect = columns->HostBackupParentWorkRect; - window->DC.CurrentColumns = NULL; - window->DC.ColumnsOffset.x = 0.0f; - window->DC.CursorPos.x = IM_TRUNC(window->Pos.x + window->DC.Indent.x + window->DC.ColumnsOffset.x); - NavUpdateCurrentWindowIsScrollPushableX(); -} - -void ImGui::Columns(int columns_count, const char* id, bool border) -{ - ImGuiWindow* window = GetCurrentWindow(); - IM_ASSERT(columns_count >= 1); - - ImGuiOldColumnFlags flags = (border ? 0 : ImGuiOldColumnFlags_NoBorder); - //flags |= ImGuiOldColumnFlags_NoPreserveWidths; // NB: Legacy behavior - ImGuiOldColumns* columns = window->DC.CurrentColumns; - if (columns != NULL && columns->Count == columns_count && columns->Flags == flags) - return; - - if (columns != NULL) - EndColumns(); - - if (columns_count != 1) - BeginColumns(id, columns_count, flags); -} - -//------------------------------------------------------------------------- - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/imgui_widgets.cpp b/app/jni/src/libultraship/extern/ImGui/imgui_widgets.cpp deleted file mode 100644 index 01d1432..0000000 --- a/app/jni/src/libultraship/extern/ImGui/imgui_widgets.cpp +++ /dev/null @@ -1,9049 +0,0 @@ -// dear imgui, v1.90 WIP -// (widgets code) - -/* - -Index of this file: - -// [SECTION] Forward Declarations -// [SECTION] Widgets: Text, etc. -// [SECTION] Widgets: Main (Button, Image, Checkbox, RadioButton, ProgressBar, Bullet, etc.) -// [SECTION] Widgets: Low-level Layout helpers (Spacing, Dummy, NewLine, Separator, etc.) -// [SECTION] Widgets: ComboBox -// [SECTION] Data Type and Data Formatting Helpers -// [SECTION] Widgets: DragScalar, DragFloat, DragInt, etc. -// [SECTION] Widgets: SliderScalar, SliderFloat, SliderInt, etc. -// [SECTION] Widgets: InputScalar, InputFloat, InputInt, etc. -// [SECTION] Widgets: InputText, InputTextMultiline -// [SECTION] Widgets: ColorEdit, ColorPicker, ColorButton, etc. -// [SECTION] Widgets: TreeNode, CollapsingHeader, etc. -// [SECTION] Widgets: Selectable -// [SECTION] Widgets: Typing-Select support -// [SECTION] Widgets: Multi-Select support -// [SECTION] Widgets: ListBox -// [SECTION] Widgets: PlotLines, PlotHistogram -// [SECTION] Widgets: Value helpers -// [SECTION] Widgets: MenuItem, BeginMenu, EndMenu, etc. -// [SECTION] Widgets: BeginTabBar, EndTabBar, etc. -// [SECTION] Widgets: BeginTabItem, EndTabItem, etc. -// [SECTION] Widgets: Columns, BeginColumns, EndColumns, etc. - -*/ - -#if defined(_MSC_VER) && !defined(_CRT_SECURE_NO_WARNINGS) -#define _CRT_SECURE_NO_WARNINGS -#endif - -#ifndef IMGUI_DEFINE_MATH_OPERATORS -#define IMGUI_DEFINE_MATH_OPERATORS -#endif - -#include "imgui.h" -#ifndef IMGUI_DISABLE -#include "imgui_internal.h" - -// System includes -#include // intptr_t - -//------------------------------------------------------------------------- -// Warnings -//------------------------------------------------------------------------- - -// Visual Studio warnings -#ifdef _MSC_VER -#pragma warning (disable: 4127) // condition expression is constant -#pragma warning (disable: 4996) // 'This function or variable may be unsafe': strcpy, strdup, sprintf, vsnprintf, sscanf, fopen -#if defined(_MSC_VER) && _MSC_VER >= 1922 // MSVC 2019 16.2 or later -#pragma warning (disable: 5054) // operator '|': deprecated between enumerations of different types -#endif -#pragma warning (disable: 26451) // [Static Analyzer] Arithmetic overflow : Using operator 'xxx' on a 4 byte value and then casting the result to a 8 byte value. Cast the value to the wider type before calling operator 'xxx' to avoid overflow(io.2). -#pragma warning (disable: 26812) // [Static Analyzer] The enum type 'xxx' is unscoped. Prefer 'enum class' over 'enum' (Enum.3). -#endif - -// Clang/GCC warnings with -Weverything -#if defined(__clang__) -#if __has_warning("-Wunknown-warning-option") -#pragma clang diagnostic ignored "-Wunknown-warning-option" // warning: unknown warning group 'xxx' // not all warnings are known by all Clang versions and they tend to be rename-happy.. so ignoring warnings triggers new warnings on some configuration. Great! -#endif -#pragma clang diagnostic ignored "-Wunknown-pragmas" // warning: unknown warning group 'xxx' -#pragma clang diagnostic ignored "-Wold-style-cast" // warning: use of old-style cast // yes, they are more terse. -#pragma clang diagnostic ignored "-Wfloat-equal" // warning: comparing floating point with == or != is unsafe // storing and comparing against same constants (typically 0.0f) is ok. -#pragma clang diagnostic ignored "-Wformat-nonliteral" // warning: format string is not a string literal // passing non-literal to vsnformat(). yes, user passing incorrect format strings can crash the code. -#pragma clang diagnostic ignored "-Wsign-conversion" // warning: implicit conversion changes signedness -#pragma clang diagnostic ignored "-Wzero-as-null-pointer-constant" // warning: zero as null pointer constant // some standard header variations use #define NULL 0 -#pragma clang diagnostic ignored "-Wdouble-promotion" // warning: implicit conversion from 'float' to 'double' when passing argument to function // using printf() is a misery with this as C++ va_arg ellipsis changes float to double. -#pragma clang diagnostic ignored "-Wenum-enum-conversion" // warning: bitwise operation between different enumeration types ('XXXFlags_' and 'XXXFlagsPrivate_') -#pragma clang diagnostic ignored "-Wdeprecated-enum-enum-conversion"// warning: bitwise operation between different enumeration types ('XXXFlags_' and 'XXXFlagsPrivate_') is deprecated -#pragma clang diagnostic ignored "-Wimplicit-int-float-conversion" // warning: implicit conversion from 'xxx' to 'float' may lose precision -#elif defined(__GNUC__) -#pragma GCC diagnostic ignored "-Wpragmas" // warning: unknown option after '#pragma GCC diagnostic' kind -#pragma GCC diagnostic ignored "-Wformat-nonliteral" // warning: format not a string literal, format string not checked -#pragma GCC diagnostic ignored "-Wclass-memaccess" // [__GNUC__ >= 8] warning: 'memset/memcpy' clearing/writing an object of type 'xxxx' with no trivial copy-assignment; use assignment or value-initialization instead -#pragma GCC diagnostic ignored "-Wdeprecated-enum-enum-conversion" // warning: bitwise operation between different enumeration types ('XXXFlags_' and 'XXXFlagsPrivate_') is deprecated -#endif - -//------------------------------------------------------------------------- -// Data -//------------------------------------------------------------------------- - -// Widgets -static const float DRAGDROP_HOLD_TO_OPEN_TIMER = 0.70f; // Time for drag-hold to activate items accepting the ImGuiButtonFlags_PressedOnDragDropHold button behavior. -static const float DRAG_MOUSE_THRESHOLD_FACTOR = 0.50f; // Multiplier for the default value of io.MouseDragThreshold to make DragFloat/DragInt react faster to mouse drags. - -// Those MIN/MAX values are not define because we need to point to them -static const signed char IM_S8_MIN = -128; -static const signed char IM_S8_MAX = 127; -static const unsigned char IM_U8_MIN = 0; -static const unsigned char IM_U8_MAX = 0xFF; -static const signed short IM_S16_MIN = -32768; -static const signed short IM_S16_MAX = 32767; -static const unsigned short IM_U16_MIN = 0; -static const unsigned short IM_U16_MAX = 0xFFFF; -static const ImS32 IM_S32_MIN = INT_MIN; // (-2147483647 - 1), (0x80000000); -static const ImS32 IM_S32_MAX = INT_MAX; // (2147483647), (0x7FFFFFFF) -static const ImU32 IM_U32_MIN = 0; -static const ImU32 IM_U32_MAX = UINT_MAX; // (0xFFFFFFFF) -#ifdef LLONG_MIN -static const ImS64 IM_S64_MIN = LLONG_MIN; // (-9223372036854775807ll - 1ll); -static const ImS64 IM_S64_MAX = LLONG_MAX; // (9223372036854775807ll); -#else -static const ImS64 IM_S64_MIN = -9223372036854775807LL - 1; -static const ImS64 IM_S64_MAX = 9223372036854775807LL; -#endif -static const ImU64 IM_U64_MIN = 0; -#ifdef ULLONG_MAX -static const ImU64 IM_U64_MAX = ULLONG_MAX; // (0xFFFFFFFFFFFFFFFFull); -#else -static const ImU64 IM_U64_MAX = (2ULL * 9223372036854775807LL + 1); -#endif - -//------------------------------------------------------------------------- -// [SECTION] Forward Declarations -//------------------------------------------------------------------------- - -// For InputTextEx() -static bool InputTextFilterCharacter(ImGuiContext* ctx, unsigned int* p_char, ImGuiInputTextFlags flags, ImGuiInputTextCallback callback, void* user_data, ImGuiInputSource input_source); -static int InputTextCalcTextLenAndLineCount(const char* text_begin, const char** out_text_end); -static ImVec2 InputTextCalcTextSizeW(ImGuiContext* ctx, const ImWchar* text_begin, const ImWchar* text_end, const ImWchar** remaining = NULL, ImVec2* out_offset = NULL, bool stop_on_new_line = false); - -//------------------------------------------------------------------------- -// [SECTION] Widgets: Text, etc. -//------------------------------------------------------------------------- -// - TextEx() [Internal] -// - TextUnformatted() -// - Text() -// - TextV() -// - TextColored() -// - TextColoredV() -// - TextDisabled() -// - TextDisabledV() -// - TextWrapped() -// - TextWrappedV() -// - LabelText() -// - LabelTextV() -// - BulletText() -// - BulletTextV() -//------------------------------------------------------------------------- - -void ImGui::TextEx(const char* text, const char* text_end, ImGuiTextFlags flags) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return; - ImGuiContext& g = *GImGui; - - // Accept null ranges - if (text == text_end) - text = text_end = ""; - - // Calculate length - const char* text_begin = text; - if (text_end == NULL) - text_end = text + strlen(text); // FIXME-OPT - - const ImVec2 text_pos(window->DC.CursorPos.x, window->DC.CursorPos.y + window->DC.CurrLineTextBaseOffset); - const float wrap_pos_x = window->DC.TextWrapPos; - const bool wrap_enabled = (wrap_pos_x >= 0.0f); - if (text_end - text <= 2000 || wrap_enabled) - { - // Common case - const float wrap_width = wrap_enabled ? CalcWrapWidthForPos(window->DC.CursorPos, wrap_pos_x) : 0.0f; - const ImVec2 text_size = CalcTextSize(text_begin, text_end, false, wrap_width); - - ImRect bb(text_pos, text_pos + text_size); - ItemSize(text_size, 0.0f); - if (!ItemAdd(bb, 0)) - return; - - // Render (we don't hide text after ## in this end-user function) - RenderTextWrapped(bb.Min, text_begin, text_end, wrap_width); - } - else - { - // Long text! - // Perform manual coarse clipping to optimize for long multi-line text - // - From this point we will only compute the width of lines that are visible. Optimization only available when word-wrapping is disabled. - // - We also don't vertically center the text within the line full height, which is unlikely to matter because we are likely the biggest and only item on the line. - // - We use memchr(), pay attention that well optimized versions of those str/mem functions are much faster than a casually written loop. - const char* line = text; - const float line_height = GetTextLineHeight(); - ImVec2 text_size(0, 0); - - // Lines to skip (can't skip when logging text) - ImVec2 pos = text_pos; - if (!g.LogEnabled) - { - int lines_skippable = (int)((window->ClipRect.Min.y - text_pos.y) / line_height); - if (lines_skippable > 0) - { - int lines_skipped = 0; - while (line < text_end && lines_skipped < lines_skippable) - { - const char* line_end = (const char*)memchr(line, '\n', text_end - line); - if (!line_end) - line_end = text_end; - if ((flags & ImGuiTextFlags_NoWidthForLargeClippedText) == 0) - text_size.x = ImMax(text_size.x, CalcTextSize(line, line_end).x); - line = line_end + 1; - lines_skipped++; - } - pos.y += lines_skipped * line_height; - } - } - - // Lines to render - if (line < text_end) - { - ImRect line_rect(pos, pos + ImVec2(FLT_MAX, line_height)); - while (line < text_end) - { - if (IsClippedEx(line_rect, 0)) - break; - - const char* line_end = (const char*)memchr(line, '\n', text_end - line); - if (!line_end) - line_end = text_end; - text_size.x = ImMax(text_size.x, CalcTextSize(line, line_end).x); - RenderText(pos, line, line_end, false); - line = line_end + 1; - line_rect.Min.y += line_height; - line_rect.Max.y += line_height; - pos.y += line_height; - } - - // Count remaining lines - int lines_skipped = 0; - while (line < text_end) - { - const char* line_end = (const char*)memchr(line, '\n', text_end - line); - if (!line_end) - line_end = text_end; - if ((flags & ImGuiTextFlags_NoWidthForLargeClippedText) == 0) - text_size.x = ImMax(text_size.x, CalcTextSize(line, line_end).x); - line = line_end + 1; - lines_skipped++; - } - pos.y += lines_skipped * line_height; - } - text_size.y = (pos - text_pos).y; - - ImRect bb(text_pos, text_pos + text_size); - ItemSize(text_size, 0.0f); - ItemAdd(bb, 0); - } -} - -void ImGui::TextUnformatted(const char* text, const char* text_end) -{ - TextEx(text, text_end, ImGuiTextFlags_NoWidthForLargeClippedText); -} - -void ImGui::Text(const char* fmt, ...) -{ - va_list args; - va_start(args, fmt); - TextV(fmt, args); - va_end(args); -} - -void ImGui::TextV(const char* fmt, va_list args) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return; - - const char* text, *text_end; - ImFormatStringToTempBufferV(&text, &text_end, fmt, args); - TextEx(text, text_end, ImGuiTextFlags_NoWidthForLargeClippedText); -} - -void ImGui::TextColored(const ImVec4& col, const char* fmt, ...) -{ - va_list args; - va_start(args, fmt); - TextColoredV(col, fmt, args); - va_end(args); -} - -void ImGui::TextColoredV(const ImVec4& col, const char* fmt, va_list args) -{ - PushStyleColor(ImGuiCol_Text, col); - TextV(fmt, args); - PopStyleColor(); -} - -void ImGui::TextDisabled(const char* fmt, ...) -{ - va_list args; - va_start(args, fmt); - TextDisabledV(fmt, args); - va_end(args); -} - -void ImGui::TextDisabledV(const char* fmt, va_list args) -{ - ImGuiContext& g = *GImGui; - PushStyleColor(ImGuiCol_Text, g.Style.Colors[ImGuiCol_TextDisabled]); - TextV(fmt, args); - PopStyleColor(); -} - -void ImGui::TextWrapped(const char* fmt, ...) -{ - va_list args; - va_start(args, fmt); - TextWrappedV(fmt, args); - va_end(args); -} - -void ImGui::TextWrappedV(const char* fmt, va_list args) -{ - ImGuiContext& g = *GImGui; - const bool need_backup = (g.CurrentWindow->DC.TextWrapPos < 0.0f); // Keep existing wrap position if one is already set - if (need_backup) - PushTextWrapPos(0.0f); - TextV(fmt, args); - if (need_backup) - PopTextWrapPos(); -} - -void ImGui::LabelText(const char* label, const char* fmt, ...) -{ - va_list args; - va_start(args, fmt); - LabelTextV(label, fmt, args); - va_end(args); -} - -// Add a label+text combo aligned to other label+value widgets -void ImGui::LabelTextV(const char* label, const char* fmt, va_list args) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return; - - ImGuiContext& g = *GImGui; - const ImGuiStyle& style = g.Style; - const float w = CalcItemWidth(); - - const char* value_text_begin, *value_text_end; - ImFormatStringToTempBufferV(&value_text_begin, &value_text_end, fmt, args); - const ImVec2 value_size = CalcTextSize(value_text_begin, value_text_end, false); - const ImVec2 label_size = CalcTextSize(label, NULL, true); - - const ImVec2 pos = window->DC.CursorPos; - const ImRect value_bb(pos, pos + ImVec2(w, value_size.y + style.FramePadding.y * 2)); - const ImRect total_bb(pos, pos + ImVec2(w + (label_size.x > 0.0f ? style.ItemInnerSpacing.x + label_size.x : 0.0f), ImMax(value_size.y, label_size.y) + style.FramePadding.y * 2)); - ItemSize(total_bb, style.FramePadding.y); - if (!ItemAdd(total_bb, 0)) - return; - - // Render - RenderTextClipped(value_bb.Min + style.FramePadding, value_bb.Max, value_text_begin, value_text_end, &value_size, ImVec2(0.0f, 0.0f)); - if (label_size.x > 0.0f) - RenderText(ImVec2(value_bb.Max.x + style.ItemInnerSpacing.x, value_bb.Min.y + style.FramePadding.y), label); -} - -void ImGui::BulletText(const char* fmt, ...) -{ - va_list args; - va_start(args, fmt); - BulletTextV(fmt, args); - va_end(args); -} - -// Text with a little bullet aligned to the typical tree node. -void ImGui::BulletTextV(const char* fmt, va_list args) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return; - - ImGuiContext& g = *GImGui; - const ImGuiStyle& style = g.Style; - - const char* text_begin, *text_end; - ImFormatStringToTempBufferV(&text_begin, &text_end, fmt, args); - const ImVec2 label_size = CalcTextSize(text_begin, text_end, false); - const ImVec2 total_size = ImVec2(g.FontSize + (label_size.x > 0.0f ? (label_size.x + style.FramePadding.x * 2) : 0.0f), label_size.y); // Empty text doesn't add padding - ImVec2 pos = window->DC.CursorPos; - pos.y += window->DC.CurrLineTextBaseOffset; - ItemSize(total_size, 0.0f); - const ImRect bb(pos, pos + total_size); - if (!ItemAdd(bb, 0)) - return; - - // Render - ImU32 text_col = GetColorU32(ImGuiCol_Text); - RenderBullet(window->DrawList, bb.Min + ImVec2(style.FramePadding.x + g.FontSize * 0.5f, g.FontSize * 0.5f), text_col); - RenderText(bb.Min + ImVec2(g.FontSize + style.FramePadding.x * 2, 0.0f), text_begin, text_end, false); -} - -//------------------------------------------------------------------------- -// [SECTION] Widgets: Main -//------------------------------------------------------------------------- -// - ButtonBehavior() [Internal] -// - Button() -// - SmallButton() -// - InvisibleButton() -// - ArrowButton() -// - CloseButton() [Internal] -// - CollapseButton() [Internal] -// - GetWindowScrollbarID() [Internal] -// - GetWindowScrollbarRect() [Internal] -// - Scrollbar() [Internal] -// - ScrollbarEx() [Internal] -// - Image() -// - ImageButton() -// - Checkbox() -// - CheckboxFlagsT() [Internal] -// - CheckboxFlags() -// - RadioButton() -// - ProgressBar() -// - Bullet() -//------------------------------------------------------------------------- - -// The ButtonBehavior() function is key to many interactions and used by many/most widgets. -// Because we handle so many cases (keyboard/gamepad navigation, drag and drop) and many specific behavior (via ImGuiButtonFlags_), -// this code is a little complex. -// By far the most common path is interacting with the Mouse using the default ImGuiButtonFlags_PressedOnClickRelease button behavior. -// See the series of events below and the corresponding state reported by dear imgui: -//------------------------------------------------------------------------------------------------------------------------------------------------ -// with PressedOnClickRelease: return-value IsItemHovered() IsItemActive() IsItemActivated() IsItemDeactivated() IsItemClicked() -// Frame N+0 (mouse is outside bb) - - - - - - -// Frame N+1 (mouse moves inside bb) - true - - - - -// Frame N+2 (mouse button is down) - true true true - true -// Frame N+3 (mouse button is down) - true true - - - -// Frame N+4 (mouse moves outside bb) - - true - - - -// Frame N+5 (mouse moves inside bb) - true true - - - -// Frame N+6 (mouse button is released) true true - - true - -// Frame N+7 (mouse button is released) - true - - - - -// Frame N+8 (mouse moves outside bb) - - - - - - -//------------------------------------------------------------------------------------------------------------------------------------------------ -// with PressedOnClick: return-value IsItemHovered() IsItemActive() IsItemActivated() IsItemDeactivated() IsItemClicked() -// Frame N+2 (mouse button is down) true true true true - true -// Frame N+3 (mouse button is down) - true true - - - -// Frame N+6 (mouse button is released) - true - - true - -// Frame N+7 (mouse button is released) - true - - - - -//------------------------------------------------------------------------------------------------------------------------------------------------ -// with PressedOnRelease: return-value IsItemHovered() IsItemActive() IsItemActivated() IsItemDeactivated() IsItemClicked() -// Frame N+2 (mouse button is down) - true - - - true -// Frame N+3 (mouse button is down) - true - - - - -// Frame N+6 (mouse button is released) true true - - - - -// Frame N+7 (mouse button is released) - true - - - - -//------------------------------------------------------------------------------------------------------------------------------------------------ -// with PressedOnDoubleClick: return-value IsItemHovered() IsItemActive() IsItemActivated() IsItemDeactivated() IsItemClicked() -// Frame N+0 (mouse button is down) - true - - - true -// Frame N+1 (mouse button is down) - true - - - - -// Frame N+2 (mouse button is released) - true - - - - -// Frame N+3 (mouse button is released) - true - - - - -// Frame N+4 (mouse button is down) true true true true - true -// Frame N+5 (mouse button is down) - true true - - - -// Frame N+6 (mouse button is released) - true - - true - -// Frame N+7 (mouse button is released) - true - - - - -//------------------------------------------------------------------------------------------------------------------------------------------------ -// Note that some combinations are supported, -// - PressedOnDragDropHold can generally be associated with any flag. -// - PressedOnDoubleClick can be associated by PressedOnClickRelease/PressedOnRelease, in which case the second release event won't be reported. -//------------------------------------------------------------------------------------------------------------------------------------------------ -// The behavior of the return-value changes when ImGuiButtonFlags_Repeat is set: -// Repeat+ Repeat+ Repeat+ Repeat+ -// PressedOnClickRelease PressedOnClick PressedOnRelease PressedOnDoubleClick -//------------------------------------------------------------------------------------------------------------------------------------------------- -// Frame N+0 (mouse button is down) - true - true -// ... - - - - -// Frame N + RepeatDelay true true - true -// ... - - - - -// Frame N + RepeatDelay + RepeatRate*N true true - true -//------------------------------------------------------------------------------------------------------------------------------------------------- - -bool ImGui::ButtonBehavior(const ImRect& bb, ImGuiID id, bool* out_hovered, bool* out_held, ImGuiButtonFlags flags) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = GetCurrentWindow(); - - // Default only reacts to left mouse button - if ((flags & ImGuiButtonFlags_MouseButtonMask_) == 0) - flags |= ImGuiButtonFlags_MouseButtonDefault_; - - // Default behavior requires click + release inside bounding box - if ((flags & ImGuiButtonFlags_PressedOnMask_) == 0) - flags |= ImGuiButtonFlags_PressedOnDefault_; - - // Default behavior inherited from item flags - // Note that _both_ ButtonFlags and ItemFlags are valid sources, so copy one into the item_flags and only check that. - ImGuiItemFlags item_flags = (g.LastItemData.ID == id ? g.LastItemData.InFlags : g.CurrentItemFlags); - if (flags & ImGuiButtonFlags_AllowOverlap) - item_flags |= ImGuiItemFlags_AllowOverlap; - if (flags & ImGuiButtonFlags_Repeat) - item_flags |= ImGuiItemFlags_ButtonRepeat; - - ImGuiWindow* backup_hovered_window = g.HoveredWindow; - const bool flatten_hovered_children = (flags & ImGuiButtonFlags_FlattenChildren) && g.HoveredWindow && g.HoveredWindow->RootWindowDockTree == window->RootWindowDockTree; - if (flatten_hovered_children) - g.HoveredWindow = window; - -#ifdef IMGUI_ENABLE_TEST_ENGINE - // Alternate registration spot, for when caller didn't use ItemAdd() - if (id != 0 && g.LastItemData.ID != id) - IMGUI_TEST_ENGINE_ITEM_ADD(id, bb, NULL); -#endif - - bool pressed = false; - bool hovered = ItemHoverable(bb, id, item_flags); - - // Special mode for Drag and Drop where holding button pressed for a long time while dragging another item triggers the button - if (g.DragDropActive && (flags & ImGuiButtonFlags_PressedOnDragDropHold) && !(g.DragDropSourceFlags & ImGuiDragDropFlags_SourceNoHoldToOpenOthers)) - if (IsItemHovered(ImGuiHoveredFlags_AllowWhenBlockedByActiveItem)) - { - hovered = true; - SetHoveredID(id); - if (g.HoveredIdTimer - g.IO.DeltaTime <= DRAGDROP_HOLD_TO_OPEN_TIMER && g.HoveredIdTimer >= DRAGDROP_HOLD_TO_OPEN_TIMER) - { - pressed = true; - g.DragDropHoldJustPressedId = id; - FocusWindow(window); - } - } - - if (flatten_hovered_children) - g.HoveredWindow = backup_hovered_window; - - // Mouse handling - const ImGuiID test_owner_id = (flags & ImGuiButtonFlags_NoTestKeyOwner) ? ImGuiKeyOwner_Any : id; - if (hovered) - { - // Poll mouse buttons - // - 'mouse_button_clicked' is generally carried into ActiveIdMouseButton when setting ActiveId. - // - Technically we only need some values in one code path, but since this is gated by hovered test this is fine. - int mouse_button_clicked = -1; - int mouse_button_released = -1; - for (int button = 0; button < 3; button++) - if (flags & (ImGuiButtonFlags_MouseButtonLeft << button)) // Handle ImGuiButtonFlags_MouseButtonRight and ImGuiButtonFlags_MouseButtonMiddle here. - { - if (IsMouseClicked(button, test_owner_id) && mouse_button_clicked == -1) { mouse_button_clicked = button; } - if (IsMouseReleased(button, test_owner_id) && mouse_button_released == -1) { mouse_button_released = button; } - } - - // Process initial action - if (!(flags & ImGuiButtonFlags_NoKeyModifiers) || (!g.IO.KeyCtrl && !g.IO.KeyShift && !g.IO.KeyAlt)) - { - if (mouse_button_clicked != -1 && g.ActiveId != id) - { - if (!(flags & ImGuiButtonFlags_NoSetKeyOwner)) - SetKeyOwner(MouseButtonToKey(mouse_button_clicked), id); - if (flags & (ImGuiButtonFlags_PressedOnClickRelease | ImGuiButtonFlags_PressedOnClickReleaseAnywhere)) - { - SetActiveID(id, window); - g.ActiveIdMouseButton = mouse_button_clicked; - if (!(flags & ImGuiButtonFlags_NoNavFocus)) - SetFocusID(id, window); - FocusWindow(window); - } - if ((flags & ImGuiButtonFlags_PressedOnClick) || ((flags & ImGuiButtonFlags_PressedOnDoubleClick) && g.IO.MouseClickedCount[mouse_button_clicked] == 2)) - { - pressed = true; - if (flags & ImGuiButtonFlags_NoHoldingActiveId) - ClearActiveID(); - else - SetActiveID(id, window); // Hold on ID - if (!(flags & ImGuiButtonFlags_NoNavFocus)) - SetFocusID(id, window); - g.ActiveIdMouseButton = mouse_button_clicked; - FocusWindow(window); - } - } - if (flags & ImGuiButtonFlags_PressedOnRelease) - { - if (mouse_button_released != -1) - { - const bool has_repeated_at_least_once = (item_flags & ImGuiItemFlags_ButtonRepeat) && g.IO.MouseDownDurationPrev[mouse_button_released] >= g.IO.KeyRepeatDelay; // Repeat mode trumps on release behavior - if (!has_repeated_at_least_once) - pressed = true; - if (!(flags & ImGuiButtonFlags_NoNavFocus)) - SetFocusID(id, window); - ClearActiveID(); - } - } - - // 'Repeat' mode acts when held regardless of _PressedOn flags (see table above). - // Relies on repeat logic of IsMouseClicked() but we may as well do it ourselves if we end up exposing finer RepeatDelay/RepeatRate settings. - if (g.ActiveId == id && (item_flags & ImGuiItemFlags_ButtonRepeat)) - if (g.IO.MouseDownDuration[g.ActiveIdMouseButton] > 0.0f && IsMouseClicked(g.ActiveIdMouseButton, test_owner_id, ImGuiInputFlags_Repeat)) - pressed = true; - } - - if (pressed) - g.NavDisableHighlight = true; - } - - // Gamepad/Keyboard navigation - // We report navigated item as hovered but we don't set g.HoveredId to not interfere with mouse. - if (g.NavId == id && !g.NavDisableHighlight && g.NavDisableMouseHover && (g.ActiveId == 0 || g.ActiveId == id || g.ActiveId == window->MoveId)) - if (!(flags & ImGuiButtonFlags_NoHoveredOnFocus)) - hovered = true; - if (g.NavActivateDownId == id) - { - bool nav_activated_by_code = (g.NavActivateId == id); - bool nav_activated_by_inputs = (g.NavActivatePressedId == id); - if (!nav_activated_by_inputs && (item_flags & ImGuiItemFlags_ButtonRepeat)) - { - // Avoid pressing multiple keys from triggering excessive amount of repeat events - const ImGuiKeyData* key1 = GetKeyData(ImGuiKey_Space); - const ImGuiKeyData* key2 = GetKeyData(ImGuiKey_Enter); - const ImGuiKeyData* key3 = GetKeyData(ImGuiKey_NavGamepadActivate); - const float t1 = ImMax(ImMax(key1->DownDuration, key2->DownDuration), key3->DownDuration); - nav_activated_by_inputs = CalcTypematicRepeatAmount(t1 - g.IO.DeltaTime, t1, g.IO.KeyRepeatDelay, g.IO.KeyRepeatRate) > 0; - } - if (nav_activated_by_code || nav_activated_by_inputs) - { - // Set active id so it can be queried by user via IsItemActive(), equivalent of holding the mouse button. - pressed = true; - SetActiveID(id, window); - g.ActiveIdSource = g.NavInputSource; - if (!(flags & ImGuiButtonFlags_NoNavFocus)) - SetFocusID(id, window); - } - } - - // Process while held - bool held = false; - if (g.ActiveId == id) - { - if (g.ActiveIdSource == ImGuiInputSource_Mouse) - { - if (g.ActiveIdIsJustActivated) - g.ActiveIdClickOffset = g.IO.MousePos - bb.Min; - - const int mouse_button = g.ActiveIdMouseButton; - if (mouse_button == -1) - { - // Fallback for the rare situation were g.ActiveId was set programmatically or from another widget (e.g. #6304). - ClearActiveID(); - } - else if (IsMouseDown(mouse_button, test_owner_id)) - { - held = true; - } - else - { - bool release_in = hovered && (flags & ImGuiButtonFlags_PressedOnClickRelease) != 0; - bool release_anywhere = (flags & ImGuiButtonFlags_PressedOnClickReleaseAnywhere) != 0; - if ((release_in || release_anywhere) && !g.DragDropActive) - { - // Report as pressed when releasing the mouse (this is the most common path) - bool is_double_click_release = (flags & ImGuiButtonFlags_PressedOnDoubleClick) && g.IO.MouseReleased[mouse_button] && g.IO.MouseClickedLastCount[mouse_button] == 2; - bool is_repeating_already = (item_flags & ImGuiItemFlags_ButtonRepeat) && g.IO.MouseDownDurationPrev[mouse_button] >= g.IO.KeyRepeatDelay; // Repeat mode trumps - bool is_button_avail_or_owned = TestKeyOwner(MouseButtonToKey(mouse_button), test_owner_id); - if (!is_double_click_release && !is_repeating_already && is_button_avail_or_owned) - pressed = true; - } - ClearActiveID(); - } - if (!(flags & ImGuiButtonFlags_NoNavFocus)) - g.NavDisableHighlight = true; - } - else if (g.ActiveIdSource == ImGuiInputSource_Keyboard || g.ActiveIdSource == ImGuiInputSource_Gamepad) - { - // When activated using Nav, we hold on the ActiveID until activation button is released - if (g.NavActivateDownId != id) - ClearActiveID(); - } - if (pressed) - g.ActiveIdHasBeenPressedBefore = true; - } - - if (out_hovered) *out_hovered = hovered; - if (out_held) *out_held = held; - - return pressed; -} - -bool ImGui::ButtonEx(const char* label, const ImVec2& size_arg, ImGuiButtonFlags flags) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - - ImGuiContext& g = *GImGui; - const ImGuiStyle& style = g.Style; - const ImGuiID id = window->GetID(label); - const ImVec2 label_size = CalcTextSize(label, NULL, true); - - ImVec2 pos = window->DC.CursorPos; - if ((flags & ImGuiButtonFlags_AlignTextBaseLine) && style.FramePadding.y < window->DC.CurrLineTextBaseOffset) // Try to vertically align buttons that are smaller/have no padding so that text baseline matches (bit hacky, since it shouldn't be a flag) - pos.y += window->DC.CurrLineTextBaseOffset - style.FramePadding.y; - ImVec2 size = CalcItemSize(size_arg, label_size.x + style.FramePadding.x * 2.0f, label_size.y + style.FramePadding.y * 2.0f); - - const ImRect bb(pos, pos + size); - ItemSize(size, style.FramePadding.y); - if (!ItemAdd(bb, id)) - return false; - - bool hovered, held; - bool pressed = ButtonBehavior(bb, id, &hovered, &held, flags); - - // Render - const ImU32 col = GetColorU32((held && hovered) ? ImGuiCol_ButtonActive : hovered ? ImGuiCol_ButtonHovered : ImGuiCol_Button); - RenderNavHighlight(bb, id); - RenderFrame(bb.Min, bb.Max, col, true, style.FrameRounding); - - if (g.LogEnabled) - LogSetNextTextDecoration("[", "]"); - RenderTextClipped(bb.Min + style.FramePadding, bb.Max - style.FramePadding, label, NULL, &label_size, style.ButtonTextAlign, &bb); - - // Automatically close popups - //if (pressed && !(flags & ImGuiButtonFlags_DontClosePopups) && (window->Flags & ImGuiWindowFlags_Popup)) - // CloseCurrentPopup(); - - IMGUI_TEST_ENGINE_ITEM_INFO(id, label, g.LastItemData.StatusFlags); - return pressed; -} - -bool ImGui::Button(const char* label, const ImVec2& size_arg) -{ - return ButtonEx(label, size_arg, ImGuiButtonFlags_None); -} - -// Small buttons fits within text without additional vertical spacing. -bool ImGui::SmallButton(const char* label) -{ - ImGuiContext& g = *GImGui; - float backup_padding_y = g.Style.FramePadding.y; - g.Style.FramePadding.y = 0.0f; - bool pressed = ButtonEx(label, ImVec2(0, 0), ImGuiButtonFlags_AlignTextBaseLine); - g.Style.FramePadding.y = backup_padding_y; - return pressed; -} - -// Tip: use ImGui::PushID()/PopID() to push indices or pointers in the ID stack. -// Then you can keep 'str_id' empty or the same for all your buttons (instead of creating a string based on a non-string id) -bool ImGui::InvisibleButton(const char* str_id, const ImVec2& size_arg, ImGuiButtonFlags flags) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - - // Cannot use zero-size for InvisibleButton(). Unlike Button() there is not way to fallback using the label size. - IM_ASSERT(size_arg.x != 0.0f && size_arg.y != 0.0f); - - const ImGuiID id = window->GetID(str_id); - ImVec2 size = CalcItemSize(size_arg, 0.0f, 0.0f); - const ImRect bb(window->DC.CursorPos, window->DC.CursorPos + size); - ItemSize(size); - if (!ItemAdd(bb, id)) - return false; - - bool hovered, held; - bool pressed = ButtonBehavior(bb, id, &hovered, &held, flags); - - IMGUI_TEST_ENGINE_ITEM_INFO(id, str_id, g.LastItemData.StatusFlags); - return pressed; -} - -bool ImGui::ArrowButtonEx(const char* str_id, ImGuiDir dir, ImVec2 size, ImGuiButtonFlags flags) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - - const ImGuiID id = window->GetID(str_id); - const ImRect bb(window->DC.CursorPos, window->DC.CursorPos + size); - const float default_size = GetFrameHeight(); - ItemSize(size, (size.y >= default_size) ? g.Style.FramePadding.y : -1.0f); - if (!ItemAdd(bb, id)) - return false; - - bool hovered, held; - bool pressed = ButtonBehavior(bb, id, &hovered, &held, flags); - - // Render - const ImU32 bg_col = GetColorU32((held && hovered) ? ImGuiCol_ButtonActive : hovered ? ImGuiCol_ButtonHovered : ImGuiCol_Button); - const ImU32 text_col = GetColorU32(ImGuiCol_Text); - RenderNavHighlight(bb, id); - RenderFrame(bb.Min, bb.Max, bg_col, true, g.Style.FrameRounding); - RenderArrow(window->DrawList, bb.Min + ImVec2(ImMax(0.0f, (size.x - g.FontSize) * 0.5f), ImMax(0.0f, (size.y - g.FontSize) * 0.5f)), text_col, dir); - - IMGUI_TEST_ENGINE_ITEM_INFO(id, str_id, g.LastItemData.StatusFlags); - return pressed; -} - -bool ImGui::ArrowButton(const char* str_id, ImGuiDir dir) -{ - float sz = GetFrameHeight(); - return ArrowButtonEx(str_id, dir, ImVec2(sz, sz), ImGuiButtonFlags_None); -} - -// Button to close a window -bool ImGui::CloseButton(ImGuiID id, const ImVec2& pos) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - - // Tweak 1: Shrink hit-testing area if button covers an abnormally large proportion of the visible region. That's in order to facilitate moving the window away. (#3825) - // This may better be applied as a general hit-rect reduction mechanism for all widgets to ensure the area to move window is always accessible? - const ImRect bb(pos, pos + ImVec2(g.FontSize, g.FontSize)); - ImRect bb_interact = bb; - const float area_to_visible_ratio = window->OuterRectClipped.GetArea() / bb.GetArea(); - if (area_to_visible_ratio < 1.5f) - bb_interact.Expand(ImTrunc(bb_interact.GetSize() * -0.25f)); - - // Tweak 2: We intentionally allow interaction when clipped so that a mechanical Alt,Right,Activate sequence can always close a window. - // (this isn't the common behavior of buttons, but it doesn't affect the user because navigation tends to keep items visible in scrolling layer). - bool is_clipped = !ItemAdd(bb_interact, id); - - bool hovered, held; - bool pressed = ButtonBehavior(bb_interact, id, &hovered, &held); - if (is_clipped) - return pressed; - - // Render - // FIXME: Clarify this mess - ImU32 col = GetColorU32(held ? ImGuiCol_ButtonActive : ImGuiCol_ButtonHovered); - ImVec2 center = bb.GetCenter(); - if (hovered) - window->DrawList->AddCircleFilled(center, ImMax(2.0f, g.FontSize * 0.5f + 1.0f), col); - - float cross_extent = g.FontSize * 0.5f * 0.7071f - 1.0f; - ImU32 cross_col = GetColorU32(ImGuiCol_Text); - center -= ImVec2(0.5f, 0.5f); - window->DrawList->AddLine(center + ImVec2(+cross_extent, +cross_extent), center + ImVec2(-cross_extent, -cross_extent), cross_col, 1.0f); - window->DrawList->AddLine(center + ImVec2(+cross_extent, -cross_extent), center + ImVec2(-cross_extent, +cross_extent), cross_col, 1.0f); - - return pressed; -} - -// The Collapse button also functions as a Dock Menu button. -bool ImGui::CollapseButton(ImGuiID id, const ImVec2& pos, ImGuiDockNode* dock_node) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - - ImRect bb(pos, pos + ImVec2(g.FontSize, g.FontSize)); - bool is_clipped = !ItemAdd(bb, id); - bool hovered, held; - bool pressed = ButtonBehavior(bb, id, &hovered, &held, ImGuiButtonFlags_None); - if (is_clipped) - return pressed; - - // Render - //bool is_dock_menu = (window->DockNodeAsHost && !window->Collapsed); - ImU32 bg_col = GetColorU32((held && hovered) ? ImGuiCol_ButtonActive : hovered ? ImGuiCol_ButtonHovered : ImGuiCol_Button); - ImU32 text_col = GetColorU32(ImGuiCol_Text); - if (hovered || held) - window->DrawList->AddCircleFilled(bb.GetCenter() + ImVec2(0.0f, -0.5f), g.FontSize * 0.5f + 1.0f, bg_col); - - if (dock_node) - RenderArrowDockMenu(window->DrawList, bb.Min, g.FontSize, text_col); - else - RenderArrow(window->DrawList, bb.Min, text_col, window->Collapsed ? ImGuiDir_Right : ImGuiDir_Down, 1.0f); - - // Switch to moving the window after mouse is moved beyond the initial drag threshold - if (IsItemActive() && IsMouseDragging(0)) - StartMouseMovingWindowOrNode(window, dock_node, true); - - return pressed; -} - -ImGuiID ImGui::GetWindowScrollbarID(ImGuiWindow* window, ImGuiAxis axis) -{ - return window->GetID(axis == ImGuiAxis_X ? "#SCROLLX" : "#SCROLLY"); -} - -// Return scrollbar rectangle, must only be called for corresponding axis if window->ScrollbarX/Y is set. -ImRect ImGui::GetWindowScrollbarRect(ImGuiWindow* window, ImGuiAxis axis) -{ - const ImRect outer_rect = window->Rect(); - const ImRect inner_rect = window->InnerRect; - const float border_size = window->WindowBorderSize; - const float scrollbar_size = window->ScrollbarSizes[axis ^ 1]; // (ScrollbarSizes.x = width of Y scrollbar; ScrollbarSizes.y = height of X scrollbar) - IM_ASSERT(scrollbar_size > 0.0f); - if (axis == ImGuiAxis_X) - return ImRect(inner_rect.Min.x, ImMax(outer_rect.Min.y, outer_rect.Max.y - border_size - scrollbar_size), inner_rect.Max.x - border_size, outer_rect.Max.y - border_size); - else - return ImRect(ImMax(outer_rect.Min.x, outer_rect.Max.x - border_size - scrollbar_size), inner_rect.Min.y, outer_rect.Max.x - border_size, inner_rect.Max.y - border_size); -} - -void ImGui::Scrollbar(ImGuiAxis axis) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - const ImGuiID id = GetWindowScrollbarID(window, axis); - - // Calculate scrollbar bounding box - ImRect bb = GetWindowScrollbarRect(window, axis); - ImDrawFlags rounding_corners = ImDrawFlags_RoundCornersNone; - if (axis == ImGuiAxis_X) - { - rounding_corners |= ImDrawFlags_RoundCornersBottomLeft; - if (!window->ScrollbarY) - rounding_corners |= ImDrawFlags_RoundCornersBottomRight; - } - else - { - if ((window->Flags & ImGuiWindowFlags_NoTitleBar) && !(window->Flags & ImGuiWindowFlags_MenuBar)) - rounding_corners |= ImDrawFlags_RoundCornersTopRight; - if (!window->ScrollbarX) - rounding_corners |= ImDrawFlags_RoundCornersBottomRight; - } - float size_avail = window->InnerRect.Max[axis] - window->InnerRect.Min[axis]; - float size_contents = window->ContentSize[axis] + window->WindowPadding[axis] * 2.0f; - ImS64 scroll = (ImS64)window->Scroll[axis]; - ScrollbarEx(bb, id, axis, &scroll, (ImS64)size_avail, (ImS64)size_contents, rounding_corners); - window->Scroll[axis] = (float)scroll; -} - -// Vertical/Horizontal scrollbar -// The entire piece of code below is rather confusing because: -// - We handle absolute seeking (when first clicking outside the grab) and relative manipulation (afterward or when clicking inside the grab) -// - We store values as normalized ratio and in a form that allows the window content to change while we are holding on a scrollbar -// - We handle both horizontal and vertical scrollbars, which makes the terminology not ideal. -// Still, the code should probably be made simpler.. -bool ImGui::ScrollbarEx(const ImRect& bb_frame, ImGuiID id, ImGuiAxis axis, ImS64* p_scroll_v, ImS64 size_avail_v, ImS64 size_contents_v, ImDrawFlags flags) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - if (window->SkipItems) - return false; - - const float bb_frame_width = bb_frame.GetWidth(); - const float bb_frame_height = bb_frame.GetHeight(); - if (bb_frame_width <= 0.0f || bb_frame_height <= 0.0f) - return false; - - // When we are too small, start hiding and disabling the grab (this reduce visual noise on very small window and facilitate using the window resize grab) - float alpha = 1.0f; - if ((axis == ImGuiAxis_Y) && bb_frame_height < g.FontSize + g.Style.FramePadding.y * 2.0f) - alpha = ImSaturate((bb_frame_height - g.FontSize) / (g.Style.FramePadding.y * 2.0f)); - if (alpha <= 0.0f) - return false; - - const ImGuiStyle& style = g.Style; - const bool allow_interaction = (alpha >= 1.0f); - - ImRect bb = bb_frame; - bb.Expand(ImVec2(-ImClamp(IM_TRUNC((bb_frame_width - 2.0f) * 0.5f), 0.0f, 3.0f), -ImClamp(IM_TRUNC((bb_frame_height - 2.0f) * 0.5f), 0.0f, 3.0f))); - - // V denote the main, longer axis of the scrollbar (= height for a vertical scrollbar) - const float scrollbar_size_v = (axis == ImGuiAxis_X) ? bb.GetWidth() : bb.GetHeight(); - - // Calculate the height of our grabbable box. It generally represent the amount visible (vs the total scrollable amount) - // But we maintain a minimum size in pixel to allow for the user to still aim inside. - IM_ASSERT(ImMax(size_contents_v, size_avail_v) > 0.0f); // Adding this assert to check if the ImMax(XXX,1.0f) is still needed. PLEASE CONTACT ME if this triggers. - const ImS64 win_size_v = ImMax(ImMax(size_contents_v, size_avail_v), (ImS64)1); - const float grab_h_pixels = ImClamp(scrollbar_size_v * ((float)size_avail_v / (float)win_size_v), style.GrabMinSize, scrollbar_size_v); - const float grab_h_norm = grab_h_pixels / scrollbar_size_v; - - // Handle input right away. None of the code of Begin() is relying on scrolling position before calling Scrollbar(). - bool held = false; - bool hovered = false; - ItemAdd(bb_frame, id, NULL, ImGuiItemFlags_NoNav); - ButtonBehavior(bb, id, &hovered, &held, ImGuiButtonFlags_NoNavFocus); - - const ImS64 scroll_max = ImMax((ImS64)1, size_contents_v - size_avail_v); - float scroll_ratio = ImSaturate((float)*p_scroll_v / (float)scroll_max); - float grab_v_norm = scroll_ratio * (scrollbar_size_v - grab_h_pixels) / scrollbar_size_v; // Grab position in normalized space - if (held && allow_interaction && grab_h_norm < 1.0f) - { - const float scrollbar_pos_v = bb.Min[axis]; - const float mouse_pos_v = g.IO.MousePos[axis]; - - // Click position in scrollbar normalized space (0.0f->1.0f) - const float clicked_v_norm = ImSaturate((mouse_pos_v - scrollbar_pos_v) / scrollbar_size_v); - SetHoveredID(id); - - bool seek_absolute = false; - if (g.ActiveIdIsJustActivated) - { - // On initial click calculate the distance between mouse and the center of the grab - seek_absolute = (clicked_v_norm < grab_v_norm || clicked_v_norm > grab_v_norm + grab_h_norm); - if (seek_absolute) - g.ScrollbarClickDeltaToGrabCenter = 0.0f; - else - g.ScrollbarClickDeltaToGrabCenter = clicked_v_norm - grab_v_norm - grab_h_norm * 0.5f; - } - - // Apply scroll (p_scroll_v will generally point on one member of window->Scroll) - // It is ok to modify Scroll here because we are being called in Begin() after the calculation of ContentSize and before setting up our starting position - const float scroll_v_norm = ImSaturate((clicked_v_norm - g.ScrollbarClickDeltaToGrabCenter - grab_h_norm * 0.5f) / (1.0f - grab_h_norm)); - *p_scroll_v = (ImS64)(scroll_v_norm * scroll_max); - - // Update values for rendering - scroll_ratio = ImSaturate((float)*p_scroll_v / (float)scroll_max); - grab_v_norm = scroll_ratio * (scrollbar_size_v - grab_h_pixels) / scrollbar_size_v; - - // Update distance to grab now that we have seeked and saturated - if (seek_absolute) - g.ScrollbarClickDeltaToGrabCenter = clicked_v_norm - grab_v_norm - grab_h_norm * 0.5f; - } - - // Render - const ImU32 bg_col = GetColorU32(ImGuiCol_ScrollbarBg); - const ImU32 grab_col = GetColorU32(held ? ImGuiCol_ScrollbarGrabActive : hovered ? ImGuiCol_ScrollbarGrabHovered : ImGuiCol_ScrollbarGrab, alpha); - window->DrawList->AddRectFilled(bb_frame.Min, bb_frame.Max, bg_col, window->WindowRounding, flags); - ImRect grab_rect; - if (axis == ImGuiAxis_X) - grab_rect = ImRect(ImLerp(bb.Min.x, bb.Max.x, grab_v_norm), bb.Min.y, ImLerp(bb.Min.x, bb.Max.x, grab_v_norm) + grab_h_pixels, bb.Max.y); - else - grab_rect = ImRect(bb.Min.x, ImLerp(bb.Min.y, bb.Max.y, grab_v_norm), bb.Max.x, ImLerp(bb.Min.y, bb.Max.y, grab_v_norm) + grab_h_pixels); - window->DrawList->AddRectFilled(grab_rect.Min, grab_rect.Max, grab_col, style.ScrollbarRounding); - - return held; -} - -void ImGui::Image(ImTextureID user_texture_id, const ImVec2& size, const ImVec2& uv0, const ImVec2& uv1, const ImVec4& tint_col, const ImVec4& border_col) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return; - - ImRect bb(window->DC.CursorPos, window->DC.CursorPos + size); - if (border_col.w > 0.0f) - bb.Max += ImVec2(2, 2); - ItemSize(bb); - if (!ItemAdd(bb, 0)) - return; - - if (border_col.w > 0.0f) - { - window->DrawList->AddRect(bb.Min, bb.Max, GetColorU32(border_col), 0.0f); - window->DrawList->AddImage(user_texture_id, bb.Min + ImVec2(1, 1), bb.Max - ImVec2(1, 1), uv0, uv1, GetColorU32(tint_col)); - } - else - { - window->DrawList->AddImage(user_texture_id, bb.Min, bb.Max, uv0, uv1, GetColorU32(tint_col)); - } -} - -// ImageButton() is flawed as 'id' is always derived from 'texture_id' (see #2464 #1390) -// We provide this internal helper to write your own variant while we figure out how to redesign the public ImageButton() API. -bool ImGui::ImageButtonEx(ImGuiID id, ImTextureID texture_id, const ImVec2& image_size, const ImVec2& uv0, const ImVec2& uv1, const ImVec4& bg_col, const ImVec4& tint_col, ImGuiButtonFlags flags) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - - const ImVec2 padding = g.Style.FramePadding; - const ImRect bb(window->DC.CursorPos, window->DC.CursorPos + image_size + padding * 2.0f); - ItemSize(bb); - if (!ItemAdd(bb, id)) - return false; - - bool hovered, held; - bool pressed = ButtonBehavior(bb, id, &hovered, &held, flags); - - // Render - const ImU32 col = GetColorU32((held && hovered) ? ImGuiCol_ButtonActive : hovered ? ImGuiCol_ButtonHovered : ImGuiCol_Button); - RenderNavHighlight(bb, id); - RenderFrame(bb.Min, bb.Max, col, true, ImClamp((float)ImMin(padding.x, padding.y), 0.0f, g.Style.FrameRounding)); - if (bg_col.w > 0.0f) - window->DrawList->AddRectFilled(bb.Min + padding, bb.Max - padding, GetColorU32(bg_col)); - window->DrawList->AddImage(texture_id, bb.Min + padding, bb.Max - padding, uv0, uv1, GetColorU32(tint_col)); - - return pressed; -} - -// Note that ImageButton() adds style.FramePadding*2.0f to provided size. This is in order to facilitate fitting an image in a button. -bool ImGui::ImageButton(const char* str_id, ImTextureID user_texture_id, const ImVec2& image_size, const ImVec2& uv0, const ImVec2& uv1, const ImVec4& bg_col, const ImVec4& tint_col) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - if (window->SkipItems) - return false; - - return ImageButtonEx(window->GetID(str_id), user_texture_id, image_size, uv0, uv1, bg_col, tint_col); -} - -#ifndef IMGUI_DISABLE_OBSOLETE_FUNCTIONS -// Legacy API obsoleted in 1.89. Two differences with new ImageButton() -// - new ImageButton() requires an explicit 'const char* str_id' Old ImageButton() used opaque imTextureId (created issue with: multiple buttons with same image, transient texture id values, opaque computation of ID) -// - new ImageButton() always use style.FramePadding Old ImageButton() had an override argument. -// If you need to change padding with new ImageButton() you can use PushStyleVar(ImGuiStyleVar_FramePadding, value), consistent with other Button functions. -bool ImGui::ImageButton(ImTextureID user_texture_id, const ImVec2& size, const ImVec2& uv0, const ImVec2& uv1, int frame_padding, const ImVec4& bg_col, const ImVec4& tint_col) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - if (window->SkipItems) - return false; - - // Default to using texture ID as ID. User can still push string/integer prefixes. - PushID((void*)(intptr_t)user_texture_id); - const ImGuiID id = window->GetID("#image"); - PopID(); - - if (frame_padding >= 0) - PushStyleVar(ImGuiStyleVar_FramePadding, ImVec2((float)frame_padding, (float)frame_padding)); - bool ret = ImageButtonEx(id, user_texture_id, size, uv0, uv1, bg_col, tint_col); - if (frame_padding >= 0) - PopStyleVar(); - return ret; -} -#endif // #ifndef IMGUI_DISABLE_OBSOLETE_FUNCTIONS - -bool ImGui::Checkbox(const char* label, bool* v) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - - ImGuiContext& g = *GImGui; - const ImGuiStyle& style = g.Style; - const ImGuiID id = window->GetID(label); - const ImVec2 label_size = CalcTextSize(label, NULL, true); - - const float square_sz = GetFrameHeight(); - const ImVec2 pos = window->DC.CursorPos; - const ImRect total_bb(pos, pos + ImVec2(square_sz + (label_size.x > 0.0f ? style.ItemInnerSpacing.x + label_size.x : 0.0f), label_size.y + style.FramePadding.y * 2.0f)); - ItemSize(total_bb, style.FramePadding.y); - if (!ItemAdd(total_bb, id)) - { - IMGUI_TEST_ENGINE_ITEM_INFO(id, label, g.LastItemData.StatusFlags | ImGuiItemStatusFlags_Checkable | (*v ? ImGuiItemStatusFlags_Checked : 0)); - return false; - } - - bool hovered, held; - bool pressed = ButtonBehavior(total_bb, id, &hovered, &held); - if (pressed) - { - *v = !(*v); - MarkItemEdited(id); - } - - const ImRect check_bb(pos, pos + ImVec2(square_sz, square_sz)); - RenderNavHighlight(total_bb, id); - RenderFrame(check_bb.Min, check_bb.Max, GetColorU32((held && hovered) ? ImGuiCol_FrameBgActive : hovered ? ImGuiCol_FrameBgHovered : ImGuiCol_FrameBg), true, style.FrameRounding); - ImU32 check_col = GetColorU32(ImGuiCol_CheckMark); - bool mixed_value = (g.LastItemData.InFlags & ImGuiItemFlags_MixedValue) != 0; - if (mixed_value) - { - // Undocumented tristate/mixed/indeterminate checkbox (#2644) - // This may seem awkwardly designed because the aim is to make ImGuiItemFlags_MixedValue supported by all widgets (not just checkbox) - ImVec2 pad(ImMax(1.0f, IM_TRUNC(square_sz / 3.6f)), ImMax(1.0f, IM_TRUNC(square_sz / 3.6f))); - window->DrawList->AddRectFilled(check_bb.Min + pad, check_bb.Max - pad, check_col, style.FrameRounding); - } - else if (*v) - { - const float pad = ImMax(1.0f, IM_TRUNC(square_sz / 6.0f)); - RenderCheckMark(window->DrawList, check_bb.Min + ImVec2(pad, pad), check_col, square_sz - pad * 2.0f); - } - - ImVec2 label_pos = ImVec2(check_bb.Max.x + style.ItemInnerSpacing.x, check_bb.Min.y + style.FramePadding.y); - if (g.LogEnabled) - LogRenderedText(&label_pos, mixed_value ? "[~]" : *v ? "[x]" : "[ ]"); - if (label_size.x > 0.0f) - RenderText(label_pos, label); - - IMGUI_TEST_ENGINE_ITEM_INFO(id, label, g.LastItemData.StatusFlags | ImGuiItemStatusFlags_Checkable | (*v ? ImGuiItemStatusFlags_Checked : 0)); - return pressed; -} - -template -bool ImGui::CheckboxFlagsT(const char* label, T* flags, T flags_value) -{ - bool all_on = (*flags & flags_value) == flags_value; - bool any_on = (*flags & flags_value) != 0; - bool pressed; - if (!all_on && any_on) - { - ImGuiContext& g = *GImGui; - g.NextItemData.ItemFlags |= ImGuiItemFlags_MixedValue; - pressed = Checkbox(label, &all_on); - } - else - { - pressed = Checkbox(label, &all_on); - - } - if (pressed) - { - if (all_on) - *flags |= flags_value; - else - *flags &= ~flags_value; - } - return pressed; -} - -bool ImGui::CheckboxFlags(const char* label, int* flags, int flags_value) -{ - return CheckboxFlagsT(label, flags, flags_value); -} - -bool ImGui::CheckboxFlags(const char* label, unsigned int* flags, unsigned int flags_value) -{ - return CheckboxFlagsT(label, flags, flags_value); -} - -bool ImGui::CheckboxFlags(const char* label, ImS64* flags, ImS64 flags_value) -{ - return CheckboxFlagsT(label, flags, flags_value); -} - -bool ImGui::CheckboxFlags(const char* label, ImU64* flags, ImU64 flags_value) -{ - return CheckboxFlagsT(label, flags, flags_value); -} - -bool ImGui::RadioButton(const char* label, bool active) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - - ImGuiContext& g = *GImGui; - const ImGuiStyle& style = g.Style; - const ImGuiID id = window->GetID(label); - const ImVec2 label_size = CalcTextSize(label, NULL, true); - - const float square_sz = GetFrameHeight(); - const ImVec2 pos = window->DC.CursorPos; - const ImRect check_bb(pos, pos + ImVec2(square_sz, square_sz)); - const ImRect total_bb(pos, pos + ImVec2(square_sz + (label_size.x > 0.0f ? style.ItemInnerSpacing.x + label_size.x : 0.0f), label_size.y + style.FramePadding.y * 2.0f)); - ItemSize(total_bb, style.FramePadding.y); - if (!ItemAdd(total_bb, id)) - return false; - - ImVec2 center = check_bb.GetCenter(); - center.x = IM_ROUND(center.x); - center.y = IM_ROUND(center.y); - const float radius = (square_sz - 1.0f) * 0.5f; - - bool hovered, held; - bool pressed = ButtonBehavior(total_bb, id, &hovered, &held); - if (pressed) - MarkItemEdited(id); - - RenderNavHighlight(total_bb, id); - const int num_segment = window->DrawList->_CalcCircleAutoSegmentCount(radius); - window->DrawList->AddCircleFilled(center, radius, GetColorU32((held && hovered) ? ImGuiCol_FrameBgActive : hovered ? ImGuiCol_FrameBgHovered : ImGuiCol_FrameBg), num_segment); - if (active) - { - const float pad = ImMax(1.0f, IM_TRUNC(square_sz / 6.0f)); - window->DrawList->AddCircleFilled(center, radius - pad, GetColorU32(ImGuiCol_CheckMark)); - } - - if (style.FrameBorderSize > 0.0f) - { - window->DrawList->AddCircle(center + ImVec2(1, 1), radius, GetColorU32(ImGuiCol_BorderShadow), num_segment, style.FrameBorderSize); - window->DrawList->AddCircle(center, radius, GetColorU32(ImGuiCol_Border), num_segment, style.FrameBorderSize); - } - - ImVec2 label_pos = ImVec2(check_bb.Max.x + style.ItemInnerSpacing.x, check_bb.Min.y + style.FramePadding.y); - if (g.LogEnabled) - LogRenderedText(&label_pos, active ? "(x)" : "( )"); - if (label_size.x > 0.0f) - RenderText(label_pos, label); - - IMGUI_TEST_ENGINE_ITEM_INFO(id, label, g.LastItemData.StatusFlags); - return pressed; -} - -// FIXME: This would work nicely if it was a public template, e.g. 'template RadioButton(const char* label, T* v, T v_button)', but I'm not sure how we would expose it.. -bool ImGui::RadioButton(const char* label, int* v, int v_button) -{ - const bool pressed = RadioButton(label, *v == v_button); - if (pressed) - *v = v_button; - return pressed; -} - -// size_arg (for each axis) < 0.0f: align to end, 0.0f: auto, > 0.0f: specified size -void ImGui::ProgressBar(float fraction, const ImVec2& size_arg, const char* overlay) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return; - - ImGuiContext& g = *GImGui; - const ImGuiStyle& style = g.Style; - - ImVec2 pos = window->DC.CursorPos; - ImVec2 size = CalcItemSize(size_arg, CalcItemWidth(), g.FontSize + style.FramePadding.y * 2.0f); - ImRect bb(pos, pos + size); - ItemSize(size, style.FramePadding.y); - if (!ItemAdd(bb, 0)) - return; - - // Render - fraction = ImSaturate(fraction); - RenderFrame(bb.Min, bb.Max, GetColorU32(ImGuiCol_FrameBg), true, style.FrameRounding); - bb.Expand(ImVec2(-style.FrameBorderSize, -style.FrameBorderSize)); - const ImVec2 fill_br = ImVec2(ImLerp(bb.Min.x, bb.Max.x, fraction), bb.Max.y); - RenderRectFilledRangeH(window->DrawList, bb, GetColorU32(ImGuiCol_PlotHistogram), 0.0f, fraction, style.FrameRounding); - - // Default displaying the fraction as percentage string, but user can override it - char overlay_buf[32]; - if (!overlay) - { - ImFormatString(overlay_buf, IM_ARRAYSIZE(overlay_buf), "%.0f%%", fraction * 100 + 0.01f); - overlay = overlay_buf; - } - - ImVec2 overlay_size = CalcTextSize(overlay, NULL); - if (overlay_size.x > 0.0f) - RenderTextClipped(ImVec2(ImClamp(fill_br.x + style.ItemSpacing.x, bb.Min.x, bb.Max.x - overlay_size.x - style.ItemInnerSpacing.x), bb.Min.y), bb.Max, overlay, NULL, &overlay_size, ImVec2(0.0f, 0.5f), &bb); -} - -void ImGui::Bullet() -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return; - - ImGuiContext& g = *GImGui; - const ImGuiStyle& style = g.Style; - const float line_height = ImMax(ImMin(window->DC.CurrLineSize.y, g.FontSize + style.FramePadding.y * 2), g.FontSize); - const ImRect bb(window->DC.CursorPos, window->DC.CursorPos + ImVec2(g.FontSize, line_height)); - ItemSize(bb); - if (!ItemAdd(bb, 0)) - { - SameLine(0, style.FramePadding.x * 2); - return; - } - - // Render and stay on same line - ImU32 text_col = GetColorU32(ImGuiCol_Text); - RenderBullet(window->DrawList, bb.Min + ImVec2(style.FramePadding.x + g.FontSize * 0.5f, line_height * 0.5f), text_col); - SameLine(0, style.FramePadding.x * 2.0f); -} - -//------------------------------------------------------------------------- -// [SECTION] Widgets: Low-level Layout helpers -//------------------------------------------------------------------------- -// - Spacing() -// - Dummy() -// - NewLine() -// - AlignTextToFramePadding() -// - SeparatorEx() [Internal] -// - Separator() -// - SplitterBehavior() [Internal] -// - ShrinkWidths() [Internal] -//------------------------------------------------------------------------- - -void ImGui::Spacing() -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return; - ItemSize(ImVec2(0, 0)); -} - -void ImGui::Dummy(const ImVec2& size) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return; - - const ImRect bb(window->DC.CursorPos, window->DC.CursorPos + size); - ItemSize(size); - ItemAdd(bb, 0); -} - -void ImGui::NewLine() -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return; - - ImGuiContext& g = *GImGui; - const ImGuiLayoutType backup_layout_type = window->DC.LayoutType; - window->DC.LayoutType = ImGuiLayoutType_Vertical; - window->DC.IsSameLine = false; - if (window->DC.CurrLineSize.y > 0.0f) // In the event that we are on a line with items that is smaller that FontSize high, we will preserve its height. - ItemSize(ImVec2(0, 0)); - else - ItemSize(ImVec2(0.0f, g.FontSize)); - window->DC.LayoutType = backup_layout_type; -} - -void ImGui::AlignTextToFramePadding() -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return; - - ImGuiContext& g = *GImGui; - window->DC.CurrLineSize.y = ImMax(window->DC.CurrLineSize.y, g.FontSize + g.Style.FramePadding.y * 2); - window->DC.CurrLineTextBaseOffset = ImMax(window->DC.CurrLineTextBaseOffset, g.Style.FramePadding.y); -} - -// Horizontal/vertical separating line -// FIXME: Surprisingly, this seemingly trivial widget is a victim of many different legacy/tricky layout issues. -// Note how thickness == 1.0f is handled specifically as not moving CursorPos by 'thickness', but other values are. -void ImGui::SeparatorEx(ImGuiSeparatorFlags flags, float thickness) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return; - - ImGuiContext& g = *GImGui; - IM_ASSERT(ImIsPowerOfTwo(flags & (ImGuiSeparatorFlags_Horizontal | ImGuiSeparatorFlags_Vertical))); // Check that only 1 option is selected - IM_ASSERT(thickness > 0.0f); - - if (flags & ImGuiSeparatorFlags_Vertical) - { - // Vertical separator, for menu bars (use current line height). - float y1 = window->DC.CursorPos.y; - float y2 = window->DC.CursorPos.y + window->DC.CurrLineSize.y; - const ImRect bb(ImVec2(window->DC.CursorPos.x, y1), ImVec2(window->DC.CursorPos.x + thickness, y2)); - ItemSize(ImVec2(thickness, 0.0f)); - if (!ItemAdd(bb, 0)) - return; - - // Draw - window->DrawList->AddRectFilled(bb.Min, bb.Max, GetColorU32(ImGuiCol_Separator)); - if (g.LogEnabled) - LogText(" |"); - } - else if (flags & ImGuiSeparatorFlags_Horizontal) - { - // Horizontal Separator - float x1 = window->DC.CursorPos.x; - float x2 = window->WorkRect.Max.x; - - // Preserve legacy behavior inside Columns() - // Before Tables API happened, we relied on Separator() to span all columns of a Columns() set. - // We currently don't need to provide the same feature for tables because tables naturally have border features. - ImGuiOldColumns* columns = (flags & ImGuiSeparatorFlags_SpanAllColumns) ? window->DC.CurrentColumns : NULL; - if (columns) - { - x1 = window->Pos.x + window->DC.Indent.x; // Used to be Pos.x before 2023/10/03 - x2 = window->Pos.x + window->Size.x; - PushColumnsBackground(); - } - - // We don't provide our width to the layout so that it doesn't get feed back into AutoFit - // FIXME: This prevents ->CursorMaxPos based bounding box evaluation from working (e.g. TableEndCell) - const float thickness_for_layout = (thickness == 1.0f) ? 0.0f : thickness; // FIXME: See 1.70/1.71 Separator() change: makes legacy 1-px separator not affect layout yet. Should change. - const ImRect bb(ImVec2(x1, window->DC.CursorPos.y), ImVec2(x2, window->DC.CursorPos.y + thickness)); - ItemSize(ImVec2(0.0f, thickness_for_layout)); - - if (ItemAdd(bb, 0)) - { - // Draw - window->DrawList->AddRectFilled(bb.Min, bb.Max, GetColorU32(ImGuiCol_Separator)); - if (g.LogEnabled) - LogRenderedText(&bb.Min, "--------------------------------\n"); - - } - if (columns) - { - PopColumnsBackground(); - columns->LineMinY = window->DC.CursorPos.y; - } - } -} - -void ImGui::Separator() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - if (window->SkipItems) - return; - - // Those flags should eventually be configurable by the user - // FIXME: We cannot g.Style.SeparatorTextBorderSize for thickness as it relates to SeparatorText() which is a decorated separator, not defaulting to 1.0f. - ImGuiSeparatorFlags flags = (window->DC.LayoutType == ImGuiLayoutType_Horizontal) ? ImGuiSeparatorFlags_Vertical : ImGuiSeparatorFlags_Horizontal; - - // Only applies to legacy Columns() api as they relied on Separator() a lot. - if (window->DC.CurrentColumns) - flags |= ImGuiSeparatorFlags_SpanAllColumns; - - SeparatorEx(flags, 1.0f); -} - -void ImGui::SeparatorTextEx(ImGuiID id, const char* label, const char* label_end, float extra_w) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - ImGuiStyle& style = g.Style; - - const ImVec2 label_size = CalcTextSize(label, label_end, false); - const ImVec2 pos = window->DC.CursorPos; - const ImVec2 padding = style.SeparatorTextPadding; - - const float separator_thickness = style.SeparatorTextBorderSize; - const ImVec2 min_size(label_size.x + extra_w + padding.x * 2.0f, ImMax(label_size.y + padding.y * 2.0f, separator_thickness)); - const ImRect bb(pos, ImVec2(window->WorkRect.Max.x, pos.y + min_size.y)); - const float text_baseline_y = ImTrunc((bb.GetHeight() - label_size.y) * style.SeparatorTextAlign.y + 0.99999f); //ImMax(padding.y, ImTrunc((style.SeparatorTextSize - label_size.y) * 0.5f)); - ItemSize(min_size, text_baseline_y); - if (!ItemAdd(bb, id)) - return; - - const float sep1_x1 = pos.x; - const float sep2_x2 = bb.Max.x; - const float seps_y = ImTrunc((bb.Min.y + bb.Max.y) * 0.5f + 0.99999f); - - const float label_avail_w = ImMax(0.0f, sep2_x2 - sep1_x1 - padding.x * 2.0f); - const ImVec2 label_pos(pos.x + padding.x + ImMax(0.0f, (label_avail_w - label_size.x - extra_w) * style.SeparatorTextAlign.x), pos.y + text_baseline_y); // FIXME-ALIGN - - // This allows using SameLine() to position something in the 'extra_w' - window->DC.CursorPosPrevLine.x = label_pos.x + label_size.x; - - const ImU32 separator_col = GetColorU32(ImGuiCol_Separator); - if (label_size.x > 0.0f) - { - const float sep1_x2 = label_pos.x - style.ItemSpacing.x; - const float sep2_x1 = label_pos.x + label_size.x + extra_w + style.ItemSpacing.x; - if (sep1_x2 > sep1_x1 && separator_thickness > 0.0f) - window->DrawList->AddLine(ImVec2(sep1_x1, seps_y), ImVec2(sep1_x2, seps_y), separator_col, separator_thickness); - if (sep2_x2 > sep2_x1 && separator_thickness > 0.0f) - window->DrawList->AddLine(ImVec2(sep2_x1, seps_y), ImVec2(sep2_x2, seps_y), separator_col, separator_thickness); - if (g.LogEnabled) - LogSetNextTextDecoration("---", NULL); - RenderTextEllipsis(window->DrawList, label_pos, ImVec2(bb.Max.x, bb.Max.y + style.ItemSpacing.y), bb.Max.x, bb.Max.x, label, label_end, &label_size); - } - else - { - if (g.LogEnabled) - LogText("---"); - if (separator_thickness > 0.0f) - window->DrawList->AddLine(ImVec2(sep1_x1, seps_y), ImVec2(sep2_x2, seps_y), separator_col, separator_thickness); - } -} - -void ImGui::SeparatorText(const char* label) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return; - - // The SeparatorText() vs SeparatorTextEx() distinction is designed to be considerate that we may want: - // - allow separator-text to be draggable items (would require a stable ID + a noticeable highlight) - // - this high-level entry point to allow formatting? (which in turns may require ID separate from formatted string) - // - because of this we probably can't turn 'const char* label' into 'const char* fmt, ...' - // Otherwise, we can decide that users wanting to drag this would layout a dedicated drag-item, - // and then we can turn this into a format function. - SeparatorTextEx(0, label, FindRenderedTextEnd(label), 0.0f); -} - -// Using 'hover_visibility_delay' allows us to hide the highlight and mouse cursor for a short time, which can be convenient to reduce visual noise. -bool ImGui::SplitterBehavior(const ImRect& bb, ImGuiID id, ImGuiAxis axis, float* size1, float* size2, float min_size1, float min_size2, float hover_extend, float hover_visibility_delay, ImU32 bg_col) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - - if (!ItemAdd(bb, id, NULL, ImGuiItemFlags_NoNav)) - return false; - - // FIXME: AFAIK the only leftover reason for passing ImGuiButtonFlags_AllowOverlap here is - // to allow caller of SplitterBehavior() to call SetItemAllowOverlap() after the item. - // Nowadays we would instead want to use SetNextItemAllowOverlap() before the item. - ImGuiButtonFlags button_flags = ImGuiButtonFlags_FlattenChildren; -#ifndef IMGUI_DISABLE_OBSOLETE_FUNCTIONS - button_flags |= ImGuiButtonFlags_AllowOverlap; -#endif - - bool hovered, held; - ImRect bb_interact = bb; - bb_interact.Expand(axis == ImGuiAxis_Y ? ImVec2(0.0f, hover_extend) : ImVec2(hover_extend, 0.0f)); - ButtonBehavior(bb_interact, id, &hovered, &held, button_flags); - if (hovered) - g.LastItemData.StatusFlags |= ImGuiItemStatusFlags_HoveredRect; // for IsItemHovered(), because bb_interact is larger than bb - - if (held || (hovered && g.HoveredIdPreviousFrame == id && g.HoveredIdTimer >= hover_visibility_delay)) - SetMouseCursor(axis == ImGuiAxis_Y ? ImGuiMouseCursor_ResizeNS : ImGuiMouseCursor_ResizeEW); - - ImRect bb_render = bb; - if (held) - { - ImVec2 mouse_delta_2d = g.IO.MousePos - g.ActiveIdClickOffset - bb_interact.Min; - float mouse_delta = (axis == ImGuiAxis_Y) ? mouse_delta_2d.y : mouse_delta_2d.x; - - // Minimum pane size - float size_1_maximum_delta = ImMax(0.0f, *size1 - min_size1); - float size_2_maximum_delta = ImMax(0.0f, *size2 - min_size2); - if (mouse_delta < -size_1_maximum_delta) - mouse_delta = -size_1_maximum_delta; - if (mouse_delta > size_2_maximum_delta) - mouse_delta = size_2_maximum_delta; - - // Apply resize - if (mouse_delta != 0.0f) - { - if (mouse_delta < 0.0f) - IM_ASSERT(*size1 + mouse_delta >= min_size1); - if (mouse_delta > 0.0f) - IM_ASSERT(*size2 - mouse_delta >= min_size2); - *size1 += mouse_delta; - *size2 -= mouse_delta; - bb_render.Translate((axis == ImGuiAxis_X) ? ImVec2(mouse_delta, 0.0f) : ImVec2(0.0f, mouse_delta)); - MarkItemEdited(id); - } - } - - // Render at new position - if (bg_col & IM_COL32_A_MASK) - window->DrawList->AddRectFilled(bb_render.Min, bb_render.Max, bg_col, 0.0f); - const ImU32 col = GetColorU32(held ? ImGuiCol_SeparatorActive : (hovered && g.HoveredIdTimer >= hover_visibility_delay) ? ImGuiCol_SeparatorHovered : ImGuiCol_Separator); - window->DrawList->AddRectFilled(bb_render.Min, bb_render.Max, col, 0.0f); - - return held; -} - -static int IMGUI_CDECL ShrinkWidthItemComparer(const void* lhs, const void* rhs) -{ - const ImGuiShrinkWidthItem* a = (const ImGuiShrinkWidthItem*)lhs; - const ImGuiShrinkWidthItem* b = (const ImGuiShrinkWidthItem*)rhs; - if (int d = (int)(b->Width - a->Width)) - return d; - return (b->Index - a->Index); -} - -// Shrink excess width from a set of item, by removing width from the larger items first. -// Set items Width to -1.0f to disable shrinking this item. -void ImGui::ShrinkWidths(ImGuiShrinkWidthItem* items, int count, float width_excess) -{ - if (count == 1) - { - if (items[0].Width >= 0.0f) - items[0].Width = ImMax(items[0].Width - width_excess, 1.0f); - return; - } - ImQsort(items, (size_t)count, sizeof(ImGuiShrinkWidthItem), ShrinkWidthItemComparer); - int count_same_width = 1; - while (width_excess > 0.0f && count_same_width < count) - { - while (count_same_width < count && items[0].Width <= items[count_same_width].Width) - count_same_width++; - float max_width_to_remove_per_item = (count_same_width < count && items[count_same_width].Width >= 0.0f) ? (items[0].Width - items[count_same_width].Width) : (items[0].Width - 1.0f); - if (max_width_to_remove_per_item <= 0.0f) - break; - float width_to_remove_per_item = ImMin(width_excess / count_same_width, max_width_to_remove_per_item); - for (int item_n = 0; item_n < count_same_width; item_n++) - items[item_n].Width -= width_to_remove_per_item; - width_excess -= width_to_remove_per_item * count_same_width; - } - - // Round width and redistribute remainder - // Ensure that e.g. the right-most tab of a shrunk tab-bar always reaches exactly at the same distance from the right-most edge of the tab bar separator. - width_excess = 0.0f; - for (int n = 0; n < count; n++) - { - float width_rounded = ImTrunc(items[n].Width); - width_excess += items[n].Width - width_rounded; - items[n].Width = width_rounded; - } - while (width_excess > 0.0f) - for (int n = 0; n < count && width_excess > 0.0f; n++) - { - float width_to_add = ImMin(items[n].InitialWidth - items[n].Width, 1.0f); - items[n].Width += width_to_add; - width_excess -= width_to_add; - } -} - -//------------------------------------------------------------------------- -// [SECTION] Widgets: ComboBox -//------------------------------------------------------------------------- -// - CalcMaxPopupHeightFromItemCount() [Internal] -// - BeginCombo() -// - BeginComboPopup() [Internal] -// - EndCombo() -// - BeginComboPreview() [Internal] -// - EndComboPreview() [Internal] -// - Combo() -//------------------------------------------------------------------------- - -static float CalcMaxPopupHeightFromItemCount(int items_count) -{ - ImGuiContext& g = *GImGui; - if (items_count <= 0) - return FLT_MAX; - return (g.FontSize + g.Style.ItemSpacing.y) * items_count - g.Style.ItemSpacing.y + (g.Style.WindowPadding.y * 2); -} - -bool ImGui::BeginCombo(const char* label, const char* preview_value, ImGuiComboFlags flags) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = GetCurrentWindow(); - - ImGuiNextWindowDataFlags backup_next_window_data_flags = g.NextWindowData.Flags; - g.NextWindowData.ClearFlags(); // We behave like Begin() and need to consume those values - if (window->SkipItems) - return false; - - const ImGuiStyle& style = g.Style; - const ImGuiID id = window->GetID(label); - IM_ASSERT((flags & (ImGuiComboFlags_NoArrowButton | ImGuiComboFlags_NoPreview)) != (ImGuiComboFlags_NoArrowButton | ImGuiComboFlags_NoPreview)); // Can't use both flags together - if (flags & ImGuiComboFlags_WidthFitPreview) - IM_ASSERT((flags & (ImGuiComboFlags_NoPreview | ImGuiComboFlags_CustomPreview)) == 0); - - const float arrow_size = (flags & ImGuiComboFlags_NoArrowButton) ? 0.0f : GetFrameHeight(); - const ImVec2 label_size = CalcTextSize(label, NULL, true); - const float preview_width = ((flags & ImGuiComboFlags_WidthFitPreview) && (preview_value != NULL)) ? CalcTextSize(preview_value, NULL, true).x : 0.0f; - const float w = (flags & ImGuiComboFlags_NoPreview) ? arrow_size : ((flags & ImGuiComboFlags_WidthFitPreview) ? (arrow_size + preview_width + style.FramePadding.x * 2.0f) : CalcItemWidth()); - const ImRect bb(window->DC.CursorPos, window->DC.CursorPos + ImVec2(w, label_size.y + style.FramePadding.y * 2.0f)); - const ImRect total_bb(bb.Min, bb.Max + ImVec2(label_size.x > 0.0f ? style.ItemInnerSpacing.x + label_size.x : 0.0f, 0.0f)); - ItemSize(total_bb, style.FramePadding.y); - if (!ItemAdd(total_bb, id, &bb)) - return false; - - // Open on click - bool hovered, held; - bool pressed = ButtonBehavior(bb, id, &hovered, &held); - const ImGuiID popup_id = ImHashStr("##ComboPopup", 0, id); - bool popup_open = IsPopupOpen(popup_id, ImGuiPopupFlags_None); - if (pressed && !popup_open) - { - OpenPopupEx(popup_id, ImGuiPopupFlags_None); - popup_open = true; - } - - // Render shape - const ImU32 frame_col = GetColorU32(hovered ? ImGuiCol_FrameBgHovered : ImGuiCol_FrameBg); - const float value_x2 = ImMax(bb.Min.x, bb.Max.x - arrow_size); - RenderNavHighlight(bb, id); - if (!(flags & ImGuiComboFlags_NoPreview)) - window->DrawList->AddRectFilled(bb.Min, ImVec2(value_x2, bb.Max.y), frame_col, style.FrameRounding, (flags & ImGuiComboFlags_NoArrowButton) ? ImDrawFlags_RoundCornersAll : ImDrawFlags_RoundCornersLeft); - if (!(flags & ImGuiComboFlags_NoArrowButton)) - { - ImU32 bg_col = GetColorU32((popup_open || hovered) ? ImGuiCol_ButtonHovered : ImGuiCol_Button); - ImU32 text_col = GetColorU32(ImGuiCol_Text); - window->DrawList->AddRectFilled(ImVec2(value_x2, bb.Min.y), bb.Max, bg_col, style.FrameRounding, (w <= arrow_size) ? ImDrawFlags_RoundCornersAll : ImDrawFlags_RoundCornersRight); - if (value_x2 + arrow_size - style.FramePadding.x <= bb.Max.x) - RenderArrow(window->DrawList, ImVec2(value_x2 + style.FramePadding.y, bb.Min.y + style.FramePadding.y), text_col, ImGuiDir_Down, 1.0f); - } - RenderFrameBorder(bb.Min, bb.Max, style.FrameRounding); - - // Custom preview - if (flags & ImGuiComboFlags_CustomPreview) - { - g.ComboPreviewData.PreviewRect = ImRect(bb.Min.x, bb.Min.y, value_x2, bb.Max.y); - IM_ASSERT(preview_value == NULL || preview_value[0] == 0); - preview_value = NULL; - } - - // Render preview and label - if (preview_value != NULL && !(flags & ImGuiComboFlags_NoPreview)) - { - if (g.LogEnabled) - LogSetNextTextDecoration("{", "}"); - RenderTextClipped(bb.Min + style.FramePadding, ImVec2(value_x2, bb.Max.y), preview_value, NULL, NULL); - } - if (label_size.x > 0) - RenderText(ImVec2(bb.Max.x + style.ItemInnerSpacing.x, bb.Min.y + style.FramePadding.y), label); - - if (!popup_open) - return false; - - g.NextWindowData.Flags = backup_next_window_data_flags; - return BeginComboPopup(popup_id, bb, flags); -} - -bool ImGui::BeginComboPopup(ImGuiID popup_id, const ImRect& bb, ImGuiComboFlags flags) -{ - ImGuiContext& g = *GImGui; - if (!IsPopupOpen(popup_id, ImGuiPopupFlags_None)) - { - g.NextWindowData.ClearFlags(); - return false; - } - - // Set popup size - float w = bb.GetWidth(); - if (g.NextWindowData.Flags & ImGuiNextWindowDataFlags_HasSizeConstraint) - { - g.NextWindowData.SizeConstraintRect.Min.x = ImMax(g.NextWindowData.SizeConstraintRect.Min.x, w); - } - else - { - if ((flags & ImGuiComboFlags_HeightMask_) == 0) - flags |= ImGuiComboFlags_HeightRegular; - IM_ASSERT(ImIsPowerOfTwo(flags & ImGuiComboFlags_HeightMask_)); // Only one - int popup_max_height_in_items = -1; - if (flags & ImGuiComboFlags_HeightRegular) popup_max_height_in_items = 8; - else if (flags & ImGuiComboFlags_HeightSmall) popup_max_height_in_items = 4; - else if (flags & ImGuiComboFlags_HeightLarge) popup_max_height_in_items = 20; - ImVec2 constraint_min(0.0f, 0.0f), constraint_max(FLT_MAX, FLT_MAX); - if ((g.NextWindowData.Flags & ImGuiNextWindowDataFlags_HasSize) == 0 || g.NextWindowData.SizeVal.x <= 0.0f) // Don't apply constraints if user specified a size - constraint_min.x = w; - if ((g.NextWindowData.Flags & ImGuiNextWindowDataFlags_HasSize) == 0 || g.NextWindowData.SizeVal.y <= 0.0f) - constraint_max.y = CalcMaxPopupHeightFromItemCount(popup_max_height_in_items); - SetNextWindowSizeConstraints(constraint_min, constraint_max); - } - - // This is essentially a specialized version of BeginPopupEx() - char name[16]; - ImFormatString(name, IM_ARRAYSIZE(name), "##Combo_%02d", g.BeginPopupStack.Size); // Recycle windows based on depth - - // Set position given a custom constraint (peak into expected window size so we can position it) - // FIXME: This might be easier to express with an hypothetical SetNextWindowPosConstraints() function? - // FIXME: This might be moved to Begin() or at least around the same spot where Tooltips and other Popups are calling FindBestWindowPosForPopupEx()? - if (ImGuiWindow* popup_window = FindWindowByName(name)) - if (popup_window->WasActive) - { - // Always override 'AutoPosLastDirection' to not leave a chance for a past value to affect us. - ImVec2 size_expected = CalcWindowNextAutoFitSize(popup_window); - popup_window->AutoPosLastDirection = (flags & ImGuiComboFlags_PopupAlignLeft) ? ImGuiDir_Left : ImGuiDir_Down; // Left = "Below, Toward Left", Down = "Below, Toward Right (default)" - ImRect r_outer = GetPopupAllowedExtentRect(popup_window); - ImVec2 pos = FindBestWindowPosForPopupEx(bb.GetBL(), size_expected, &popup_window->AutoPosLastDirection, r_outer, bb, ImGuiPopupPositionPolicy_ComboBox); - SetNextWindowPos(pos); - } - - // We don't use BeginPopupEx() solely because we have a custom name string, which we could make an argument to BeginPopupEx() - ImGuiWindowFlags window_flags = ImGuiWindowFlags_AlwaysAutoResize | ImGuiWindowFlags_Popup | ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_NoResize | ImGuiWindowFlags_NoSavedSettings | ImGuiWindowFlags_NoMove; - PushStyleVar(ImGuiStyleVar_WindowPadding, ImVec2(g.Style.FramePadding.x, g.Style.WindowPadding.y)); // Horizontally align ourselves with the framed text - bool ret = Begin(name, NULL, window_flags); - PopStyleVar(); - if (!ret) - { - EndPopup(); - IM_ASSERT(0); // This should never happen as we tested for IsPopupOpen() above - return false; - } - return true; -} - -void ImGui::EndCombo() -{ - EndPopup(); -} - -// Call directly after the BeginCombo/EndCombo block. The preview is designed to only host non-interactive elements -// (Experimental, see GitHub issues: #1658, #4168) -bool ImGui::BeginComboPreview() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - ImGuiComboPreviewData* preview_data = &g.ComboPreviewData; - - if (window->SkipItems || !(g.LastItemData.StatusFlags & ImGuiItemStatusFlags_Visible)) - return false; - IM_ASSERT(g.LastItemData.Rect.Min.x == preview_data->PreviewRect.Min.x && g.LastItemData.Rect.Min.y == preview_data->PreviewRect.Min.y); // Didn't call after BeginCombo/EndCombo block or forgot to pass ImGuiComboFlags_CustomPreview flag? - if (!window->ClipRect.Overlaps(preview_data->PreviewRect)) // Narrower test (optional) - return false; - - // FIXME: This could be contained in a PushWorkRect() api - preview_data->BackupCursorPos = window->DC.CursorPos; - preview_data->BackupCursorMaxPos = window->DC.CursorMaxPos; - preview_data->BackupCursorPosPrevLine = window->DC.CursorPosPrevLine; - preview_data->BackupPrevLineTextBaseOffset = window->DC.PrevLineTextBaseOffset; - preview_data->BackupLayout = window->DC.LayoutType; - window->DC.CursorPos = preview_data->PreviewRect.Min + g.Style.FramePadding; - window->DC.CursorMaxPos = window->DC.CursorPos; - window->DC.LayoutType = ImGuiLayoutType_Horizontal; - window->DC.IsSameLine = false; - PushClipRect(preview_data->PreviewRect.Min, preview_data->PreviewRect.Max, true); - - return true; -} - -void ImGui::EndComboPreview() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - ImGuiComboPreviewData* preview_data = &g.ComboPreviewData; - - // FIXME: Using CursorMaxPos approximation instead of correct AABB which we will store in ImDrawCmd in the future - ImDrawList* draw_list = window->DrawList; - if (window->DC.CursorMaxPos.x < preview_data->PreviewRect.Max.x && window->DC.CursorMaxPos.y < preview_data->PreviewRect.Max.y) - if (draw_list->CmdBuffer.Size > 1) // Unlikely case that the PushClipRect() didn't create a command - { - draw_list->_CmdHeader.ClipRect = draw_list->CmdBuffer[draw_list->CmdBuffer.Size - 1].ClipRect = draw_list->CmdBuffer[draw_list->CmdBuffer.Size - 2].ClipRect; - draw_list->_TryMergeDrawCmds(); - } - PopClipRect(); - window->DC.CursorPos = preview_data->BackupCursorPos; - window->DC.CursorMaxPos = ImMax(window->DC.CursorMaxPos, preview_data->BackupCursorMaxPos); - window->DC.CursorPosPrevLine = preview_data->BackupCursorPosPrevLine; - window->DC.PrevLineTextBaseOffset = preview_data->BackupPrevLineTextBaseOffset; - window->DC.LayoutType = preview_data->BackupLayout; - window->DC.IsSameLine = false; - preview_data->PreviewRect = ImRect(); -} - -// Getter for the old Combo() API: const char*[] -static const char* Items_ArrayGetter(void* data, int idx) -{ - const char* const* items = (const char* const*)data; - return items[idx]; -} - -// Getter for the old Combo() API: "item1\0item2\0item3\0" -static const char* Items_SingleStringGetter(void* data, int idx) -{ - const char* items_separated_by_zeros = (const char*)data; - int items_count = 0; - const char* p = items_separated_by_zeros; - while (*p) - { - if (idx == items_count) - break; - p += strlen(p) + 1; - items_count++; - } - return *p ? p : NULL; -} - -// Old API, prefer using BeginCombo() nowadays if you can. -bool ImGui::Combo(const char* label, int* current_item, const char* (*getter)(void* user_data, int idx), void* user_data, int items_count, int popup_max_height_in_items) -{ - ImGuiContext& g = *GImGui; - - // Call the getter to obtain the preview string which is a parameter to BeginCombo() - const char* preview_value = NULL; - if (*current_item >= 0 && *current_item < items_count) - preview_value = getter(user_data, *current_item); - - // The old Combo() API exposed "popup_max_height_in_items". The new more general BeginCombo() API doesn't have/need it, but we emulate it here. - if (popup_max_height_in_items != -1 && !(g.NextWindowData.Flags & ImGuiNextWindowDataFlags_HasSizeConstraint)) - SetNextWindowSizeConstraints(ImVec2(0, 0), ImVec2(FLT_MAX, CalcMaxPopupHeightFromItemCount(popup_max_height_in_items))); - - if (!BeginCombo(label, preview_value, ImGuiComboFlags_None)) - return false; - - // Display items - // FIXME-OPT: Use clipper (but we need to disable it on the appearing frame to make sure our call to SetItemDefaultFocus() is processed) - bool value_changed = false; - for (int i = 0; i < items_count; i++) - { - const char* item_text = getter(user_data, i); - if (item_text == NULL) - item_text = "*Unknown item*"; - - PushID(i); - const bool item_selected = (i == *current_item); - if (Selectable(item_text, item_selected) && *current_item != i) - { - value_changed = true; - *current_item = i; - } - if (item_selected) - SetItemDefaultFocus(); - PopID(); - } - - EndCombo(); - - if (value_changed) - MarkItemEdited(g.LastItemData.ID); - - return value_changed; -} - -// Combo box helper allowing to pass an array of strings. -bool ImGui::Combo(const char* label, int* current_item, const char* const items[], int items_count, int height_in_items) -{ - const bool value_changed = Combo(label, current_item, Items_ArrayGetter, (void*)items, items_count, height_in_items); - return value_changed; -} - -// Combo box helper allowing to pass all items in a single string literal holding multiple zero-terminated items "item1\0item2\0" -bool ImGui::Combo(const char* label, int* current_item, const char* items_separated_by_zeros, int height_in_items) -{ - int items_count = 0; - const char* p = items_separated_by_zeros; // FIXME-OPT: Avoid computing this, or at least only when combo is open - while (*p) - { - p += strlen(p) + 1; - items_count++; - } - bool value_changed = Combo(label, current_item, Items_SingleStringGetter, (void*)items_separated_by_zeros, items_count, height_in_items); - return value_changed; -} - -#ifndef IMGUI_DISABLE_OBSOLETE_FUNCTIONS - -struct ImGuiGetNameFromIndexOldToNewCallbackData { void* UserData; bool (*OldCallback)(void*, int, const char**); }; -static const char* ImGuiGetNameFromIndexOldToNewCallback(void* user_data, int idx) -{ - ImGuiGetNameFromIndexOldToNewCallbackData* data = (ImGuiGetNameFromIndexOldToNewCallbackData*)user_data; - const char* s = NULL; - data->OldCallback(data->UserData, idx, &s); - return s; -} - -bool ImGui::ListBox(const char* label, int* current_item, bool (*old_getter)(void*, int, const char**), void* user_data, int items_count, int height_in_items) -{ - ImGuiGetNameFromIndexOldToNewCallbackData old_to_new_data = { user_data, old_getter }; - return ListBox(label, current_item, ImGuiGetNameFromIndexOldToNewCallback, &old_to_new_data, items_count, height_in_items); -} -bool ImGui::Combo(const char* label, int* current_item, bool (*old_getter)(void*, int, const char**), void* user_data, int items_count, int popup_max_height_in_items) -{ - ImGuiGetNameFromIndexOldToNewCallbackData old_to_new_data = { user_data, old_getter }; - return Combo(label, current_item, ImGuiGetNameFromIndexOldToNewCallback, &old_to_new_data, items_count, popup_max_height_in_items); -} - -#endif - -//------------------------------------------------------------------------- -// [SECTION] Data Type and Data Formatting Helpers [Internal] -//------------------------------------------------------------------------- -// - DataTypeGetInfo() -// - DataTypeFormatString() -// - DataTypeApplyOp() -// - DataTypeApplyOpFromText() -// - DataTypeCompare() -// - DataTypeClamp() -// - GetMinimumStepAtDecimalPrecision -// - RoundScalarWithFormat<>() -//------------------------------------------------------------------------- - -static const ImGuiDataTypeInfo GDataTypeInfo[] = -{ - { sizeof(char), "S8", "%d", "%d" }, // ImGuiDataType_S8 - { sizeof(unsigned char), "U8", "%u", "%u" }, - { sizeof(short), "S16", "%d", "%d" }, // ImGuiDataType_S16 - { sizeof(unsigned short), "U16", "%u", "%u" }, - { sizeof(int), "S32", "%d", "%d" }, // ImGuiDataType_S32 - { sizeof(unsigned int), "U32", "%u", "%u" }, -#ifdef _MSC_VER - { sizeof(ImS64), "S64", "%I64d","%I64d" }, // ImGuiDataType_S64 - { sizeof(ImU64), "U64", "%I64u","%I64u" }, -#else - { sizeof(ImS64), "S64", "%lld", "%lld" }, // ImGuiDataType_S64 - { sizeof(ImU64), "U64", "%llu", "%llu" }, -#endif - { sizeof(float), "float", "%.3f","%f" }, // ImGuiDataType_Float (float are promoted to double in va_arg) - { sizeof(double), "double","%f", "%lf" }, // ImGuiDataType_Double -}; -IM_STATIC_ASSERT(IM_ARRAYSIZE(GDataTypeInfo) == ImGuiDataType_COUNT); - -const ImGuiDataTypeInfo* ImGui::DataTypeGetInfo(ImGuiDataType data_type) -{ - IM_ASSERT(data_type >= 0 && data_type < ImGuiDataType_COUNT); - return &GDataTypeInfo[data_type]; -} - -int ImGui::DataTypeFormatString(char* buf, int buf_size, ImGuiDataType data_type, const void* p_data, const char* format) -{ - // Signedness doesn't matter when pushing integer arguments - if (data_type == ImGuiDataType_S32 || data_type == ImGuiDataType_U32) - return ImFormatString(buf, buf_size, format, *(const ImU32*)p_data); - if (data_type == ImGuiDataType_S64 || data_type == ImGuiDataType_U64) - return ImFormatString(buf, buf_size, format, *(const ImU64*)p_data); - if (data_type == ImGuiDataType_Float) - return ImFormatString(buf, buf_size, format, *(const float*)p_data); - if (data_type == ImGuiDataType_Double) - return ImFormatString(buf, buf_size, format, *(const double*)p_data); - if (data_type == ImGuiDataType_S8) - return ImFormatString(buf, buf_size, format, *(const ImS8*)p_data); - if (data_type == ImGuiDataType_U8) - return ImFormatString(buf, buf_size, format, *(const ImU8*)p_data); - if (data_type == ImGuiDataType_S16) - return ImFormatString(buf, buf_size, format, *(const ImS16*)p_data); - if (data_type == ImGuiDataType_U16) - return ImFormatString(buf, buf_size, format, *(const ImU16*)p_data); - IM_ASSERT(0); - return 0; -} - -void ImGui::DataTypeApplyOp(ImGuiDataType data_type, int op, void* output, const void* arg1, const void* arg2) -{ - IM_ASSERT(op == '+' || op == '-'); - switch (data_type) - { - case ImGuiDataType_S8: - if (op == '+') { *(ImS8*)output = ImAddClampOverflow(*(const ImS8*)arg1, *(const ImS8*)arg2, IM_S8_MIN, IM_S8_MAX); } - if (op == '-') { *(ImS8*)output = ImSubClampOverflow(*(const ImS8*)arg1, *(const ImS8*)arg2, IM_S8_MIN, IM_S8_MAX); } - return; - case ImGuiDataType_U8: - if (op == '+') { *(ImU8*)output = ImAddClampOverflow(*(const ImU8*)arg1, *(const ImU8*)arg2, IM_U8_MIN, IM_U8_MAX); } - if (op == '-') { *(ImU8*)output = ImSubClampOverflow(*(const ImU8*)arg1, *(const ImU8*)arg2, IM_U8_MIN, IM_U8_MAX); } - return; - case ImGuiDataType_S16: - if (op == '+') { *(ImS16*)output = ImAddClampOverflow(*(const ImS16*)arg1, *(const ImS16*)arg2, IM_S16_MIN, IM_S16_MAX); } - if (op == '-') { *(ImS16*)output = ImSubClampOverflow(*(const ImS16*)arg1, *(const ImS16*)arg2, IM_S16_MIN, IM_S16_MAX); } - return; - case ImGuiDataType_U16: - if (op == '+') { *(ImU16*)output = ImAddClampOverflow(*(const ImU16*)arg1, *(const ImU16*)arg2, IM_U16_MIN, IM_U16_MAX); } - if (op == '-') { *(ImU16*)output = ImSubClampOverflow(*(const ImU16*)arg1, *(const ImU16*)arg2, IM_U16_MIN, IM_U16_MAX); } - return; - case ImGuiDataType_S32: - if (op == '+') { *(ImS32*)output = ImAddClampOverflow(*(const ImS32*)arg1, *(const ImS32*)arg2, IM_S32_MIN, IM_S32_MAX); } - if (op == '-') { *(ImS32*)output = ImSubClampOverflow(*(const ImS32*)arg1, *(const ImS32*)arg2, IM_S32_MIN, IM_S32_MAX); } - return; - case ImGuiDataType_U32: - if (op == '+') { *(ImU32*)output = ImAddClampOverflow(*(const ImU32*)arg1, *(const ImU32*)arg2, IM_U32_MIN, IM_U32_MAX); } - if (op == '-') { *(ImU32*)output = ImSubClampOverflow(*(const ImU32*)arg1, *(const ImU32*)arg2, IM_U32_MIN, IM_U32_MAX); } - return; - case ImGuiDataType_S64: - if (op == '+') { *(ImS64*)output = ImAddClampOverflow(*(const ImS64*)arg1, *(const ImS64*)arg2, IM_S64_MIN, IM_S64_MAX); } - if (op == '-') { *(ImS64*)output = ImSubClampOverflow(*(const ImS64*)arg1, *(const ImS64*)arg2, IM_S64_MIN, IM_S64_MAX); } - return; - case ImGuiDataType_U64: - if (op == '+') { *(ImU64*)output = ImAddClampOverflow(*(const ImU64*)arg1, *(const ImU64*)arg2, IM_U64_MIN, IM_U64_MAX); } - if (op == '-') { *(ImU64*)output = ImSubClampOverflow(*(const ImU64*)arg1, *(const ImU64*)arg2, IM_U64_MIN, IM_U64_MAX); } - return; - case ImGuiDataType_Float: - if (op == '+') { *(float*)output = *(const float*)arg1 + *(const float*)arg2; } - if (op == '-') { *(float*)output = *(const float*)arg1 - *(const float*)arg2; } - return; - case ImGuiDataType_Double: - if (op == '+') { *(double*)output = *(const double*)arg1 + *(const double*)arg2; } - if (op == '-') { *(double*)output = *(const double*)arg1 - *(const double*)arg2; } - return; - case ImGuiDataType_COUNT: break; - } - IM_ASSERT(0); -} - -// User can input math operators (e.g. +100) to edit a numerical values. -// NB: This is _not_ a full expression evaluator. We should probably add one and replace this dumb mess.. -bool ImGui::DataTypeApplyFromText(const char* buf, ImGuiDataType data_type, void* p_data, const char* format) -{ - while (ImCharIsBlankA(*buf)) - buf++; - if (!buf[0]) - return false; - - // Copy the value in an opaque buffer so we can compare at the end of the function if it changed at all. - const ImGuiDataTypeInfo* type_info = DataTypeGetInfo(data_type); - ImGuiDataTypeTempStorage data_backup; - memcpy(&data_backup, p_data, type_info->Size); - - // Sanitize format - // - For float/double we have to ignore format with precision (e.g. "%.2f") because sscanf doesn't take them in, so force them into %f and %lf - // - In theory could treat empty format as using default, but this would only cover rare/bizarre case of using InputScalar() + integer + format string without %. - char format_sanitized[32]; - if (data_type == ImGuiDataType_Float || data_type == ImGuiDataType_Double) - format = type_info->ScanFmt; - else - format = ImParseFormatSanitizeForScanning(format, format_sanitized, IM_ARRAYSIZE(format_sanitized)); - - // Small types need a 32-bit buffer to receive the result from scanf() - int v32 = 0; - if (sscanf(buf, format, type_info->Size >= 4 ? p_data : &v32) < 1) - return false; - if (type_info->Size < 4) - { - if (data_type == ImGuiDataType_S8) - *(ImS8*)p_data = (ImS8)ImClamp(v32, (int)IM_S8_MIN, (int)IM_S8_MAX); - else if (data_type == ImGuiDataType_U8) - *(ImU8*)p_data = (ImU8)ImClamp(v32, (int)IM_U8_MIN, (int)IM_U8_MAX); - else if (data_type == ImGuiDataType_S16) - *(ImS16*)p_data = (ImS16)ImClamp(v32, (int)IM_S16_MIN, (int)IM_S16_MAX); - else if (data_type == ImGuiDataType_U16) - *(ImU16*)p_data = (ImU16)ImClamp(v32, (int)IM_U16_MIN, (int)IM_U16_MAX); - else - IM_ASSERT(0); - } - - return memcmp(&data_backup, p_data, type_info->Size) != 0; -} - -template -static int DataTypeCompareT(const T* lhs, const T* rhs) -{ - if (*lhs < *rhs) return -1; - if (*lhs > *rhs) return +1; - return 0; -} - -int ImGui::DataTypeCompare(ImGuiDataType data_type, const void* arg_1, const void* arg_2) -{ - switch (data_type) - { - case ImGuiDataType_S8: return DataTypeCompareT((const ImS8* )arg_1, (const ImS8* )arg_2); - case ImGuiDataType_U8: return DataTypeCompareT((const ImU8* )arg_1, (const ImU8* )arg_2); - case ImGuiDataType_S16: return DataTypeCompareT((const ImS16* )arg_1, (const ImS16* )arg_2); - case ImGuiDataType_U16: return DataTypeCompareT((const ImU16* )arg_1, (const ImU16* )arg_2); - case ImGuiDataType_S32: return DataTypeCompareT((const ImS32* )arg_1, (const ImS32* )arg_2); - case ImGuiDataType_U32: return DataTypeCompareT((const ImU32* )arg_1, (const ImU32* )arg_2); - case ImGuiDataType_S64: return DataTypeCompareT((const ImS64* )arg_1, (const ImS64* )arg_2); - case ImGuiDataType_U64: return DataTypeCompareT((const ImU64* )arg_1, (const ImU64* )arg_2); - case ImGuiDataType_Float: return DataTypeCompareT((const float* )arg_1, (const float* )arg_2); - case ImGuiDataType_Double: return DataTypeCompareT((const double*)arg_1, (const double*)arg_2); - case ImGuiDataType_COUNT: break; - } - IM_ASSERT(0); - return 0; -} - -template -static bool DataTypeClampT(T* v, const T* v_min, const T* v_max) -{ - // Clamp, both sides are optional, return true if modified - if (v_min && *v < *v_min) { *v = *v_min; return true; } - if (v_max && *v > *v_max) { *v = *v_max; return true; } - return false; -} - -bool ImGui::DataTypeClamp(ImGuiDataType data_type, void* p_data, const void* p_min, const void* p_max) -{ - switch (data_type) - { - case ImGuiDataType_S8: return DataTypeClampT((ImS8* )p_data, (const ImS8* )p_min, (const ImS8* )p_max); - case ImGuiDataType_U8: return DataTypeClampT((ImU8* )p_data, (const ImU8* )p_min, (const ImU8* )p_max); - case ImGuiDataType_S16: return DataTypeClampT((ImS16* )p_data, (const ImS16* )p_min, (const ImS16* )p_max); - case ImGuiDataType_U16: return DataTypeClampT((ImU16* )p_data, (const ImU16* )p_min, (const ImU16* )p_max); - case ImGuiDataType_S32: return DataTypeClampT((ImS32* )p_data, (const ImS32* )p_min, (const ImS32* )p_max); - case ImGuiDataType_U32: return DataTypeClampT((ImU32* )p_data, (const ImU32* )p_min, (const ImU32* )p_max); - case ImGuiDataType_S64: return DataTypeClampT((ImS64* )p_data, (const ImS64* )p_min, (const ImS64* )p_max); - case ImGuiDataType_U64: return DataTypeClampT((ImU64* )p_data, (const ImU64* )p_min, (const ImU64* )p_max); - case ImGuiDataType_Float: return DataTypeClampT((float* )p_data, (const float* )p_min, (const float* )p_max); - case ImGuiDataType_Double: return DataTypeClampT((double*)p_data, (const double*)p_min, (const double*)p_max); - case ImGuiDataType_COUNT: break; - } - IM_ASSERT(0); - return false; -} - -static float GetMinimumStepAtDecimalPrecision(int decimal_precision) -{ - static const float min_steps[10] = { 1.0f, 0.1f, 0.01f, 0.001f, 0.0001f, 0.00001f, 0.000001f, 0.0000001f, 0.00000001f, 0.000000001f }; - if (decimal_precision < 0) - return FLT_MIN; - return (decimal_precision < IM_ARRAYSIZE(min_steps)) ? min_steps[decimal_precision] : ImPow(10.0f, (float)-decimal_precision); -} - -template -TYPE ImGui::RoundScalarWithFormatT(const char* format, ImGuiDataType data_type, TYPE v) -{ - IM_UNUSED(data_type); - IM_ASSERT(data_type == ImGuiDataType_Float || data_type == ImGuiDataType_Double); - const char* fmt_start = ImParseFormatFindStart(format); - if (fmt_start[0] != '%' || fmt_start[1] == '%') // Don't apply if the value is not visible in the format string - return v; - - // Sanitize format - char fmt_sanitized[32]; - ImParseFormatSanitizeForPrinting(fmt_start, fmt_sanitized, IM_ARRAYSIZE(fmt_sanitized)); - fmt_start = fmt_sanitized; - - // Format value with our rounding, and read back - char v_str[64]; - ImFormatString(v_str, IM_ARRAYSIZE(v_str), fmt_start, v); - const char* p = v_str; - while (*p == ' ') - p++; - v = (TYPE)ImAtof(p); - - return v; -} - -//------------------------------------------------------------------------- -// [SECTION] Widgets: DragScalar, DragFloat, DragInt, etc. -//------------------------------------------------------------------------- -// - DragBehaviorT<>() [Internal] -// - DragBehavior() [Internal] -// - DragScalar() -// - DragScalarN() -// - DragFloat() -// - DragFloat2() -// - DragFloat3() -// - DragFloat4() -// - DragFloatRange2() -// - DragInt() -// - DragInt2() -// - DragInt3() -// - DragInt4() -// - DragIntRange2() -//------------------------------------------------------------------------- - -// This is called by DragBehavior() when the widget is active (held by mouse or being manipulated with Nav controls) -template -bool ImGui::DragBehaviorT(ImGuiDataType data_type, TYPE* v, float v_speed, const TYPE v_min, const TYPE v_max, const char* format, ImGuiSliderFlags flags) -{ - ImGuiContext& g = *GImGui; - const ImGuiAxis axis = (flags & ImGuiSliderFlags_Vertical) ? ImGuiAxis_Y : ImGuiAxis_X; - const bool is_clamped = (v_min < v_max); - const bool is_logarithmic = (flags & ImGuiSliderFlags_Logarithmic) != 0; - const bool is_floating_point = (data_type == ImGuiDataType_Float) || (data_type == ImGuiDataType_Double); - - // Default tweak speed - if (v_speed == 0.0f && is_clamped && (v_max - v_min < FLT_MAX)) - v_speed = (float)((v_max - v_min) * g.DragSpeedDefaultRatio); - - // Inputs accumulates into g.DragCurrentAccum, which is flushed into the current value as soon as it makes a difference with our precision settings - float adjust_delta = 0.0f; - if (g.ActiveIdSource == ImGuiInputSource_Mouse && IsMousePosValid() && IsMouseDragPastThreshold(0, g.IO.MouseDragThreshold * DRAG_MOUSE_THRESHOLD_FACTOR)) - { - adjust_delta = g.IO.MouseDelta[axis]; - if (g.IO.KeyAlt) - adjust_delta *= 1.0f / 100.0f; - if (g.IO.KeyShift) - adjust_delta *= 10.0f; - } - else if (g.ActiveIdSource == ImGuiInputSource_Keyboard || g.ActiveIdSource == ImGuiInputSource_Gamepad) - { - const int decimal_precision = is_floating_point ? ImParseFormatPrecision(format, 3) : 0; - const bool tweak_slow = IsKeyDown((g.NavInputSource == ImGuiInputSource_Gamepad) ? ImGuiKey_NavGamepadTweakSlow : ImGuiKey_NavKeyboardTweakSlow); - const bool tweak_fast = IsKeyDown((g.NavInputSource == ImGuiInputSource_Gamepad) ? ImGuiKey_NavGamepadTweakFast : ImGuiKey_NavKeyboardTweakFast); - const float tweak_factor = tweak_slow ? 1.0f / 1.0f : tweak_fast ? 10.0f : 1.0f; - adjust_delta = GetNavTweakPressedAmount(axis) * tweak_factor; - v_speed = ImMax(v_speed, GetMinimumStepAtDecimalPrecision(decimal_precision)); - } - adjust_delta *= v_speed; - - // For vertical drag we currently assume that Up=higher value (like we do with vertical sliders). This may become a parameter. - if (axis == ImGuiAxis_Y) - adjust_delta = -adjust_delta; - - // For logarithmic use our range is effectively 0..1 so scale the delta into that range - if (is_logarithmic && (v_max - v_min < FLT_MAX) && ((v_max - v_min) > 0.000001f)) // Epsilon to avoid /0 - adjust_delta /= (float)(v_max - v_min); - - // Clear current value on activation - // Avoid altering values and clamping when we are _already_ past the limits and heading in the same direction, so e.g. if range is 0..255, current value is 300 and we are pushing to the right side, keep the 300. - bool is_just_activated = g.ActiveIdIsJustActivated; - bool is_already_past_limits_and_pushing_outward = is_clamped && ((*v >= v_max && adjust_delta > 0.0f) || (*v <= v_min && adjust_delta < 0.0f)); - if (is_just_activated || is_already_past_limits_and_pushing_outward) - { - g.DragCurrentAccum = 0.0f; - g.DragCurrentAccumDirty = false; - } - else if (adjust_delta != 0.0f) - { - g.DragCurrentAccum += adjust_delta; - g.DragCurrentAccumDirty = true; - } - - if (!g.DragCurrentAccumDirty) - return false; - - TYPE v_cur = *v; - FLOATTYPE v_old_ref_for_accum_remainder = (FLOATTYPE)0.0f; - - float logarithmic_zero_epsilon = 0.0f; // Only valid when is_logarithmic is true - const float zero_deadzone_halfsize = 0.0f; // Drag widgets have no deadzone (as it doesn't make sense) - if (is_logarithmic) - { - // When using logarithmic sliders, we need to clamp to avoid hitting zero, but our choice of clamp value greatly affects slider precision. We attempt to use the specified precision to estimate a good lower bound. - const int decimal_precision = is_floating_point ? ImParseFormatPrecision(format, 3) : 1; - logarithmic_zero_epsilon = ImPow(0.1f, (float)decimal_precision); - - // Convert to parametric space, apply delta, convert back - float v_old_parametric = ScaleRatioFromValueT(data_type, v_cur, v_min, v_max, is_logarithmic, logarithmic_zero_epsilon, zero_deadzone_halfsize); - float v_new_parametric = v_old_parametric + g.DragCurrentAccum; - v_cur = ScaleValueFromRatioT(data_type, v_new_parametric, v_min, v_max, is_logarithmic, logarithmic_zero_epsilon, zero_deadzone_halfsize); - v_old_ref_for_accum_remainder = v_old_parametric; - } - else - { - v_cur += (SIGNEDTYPE)g.DragCurrentAccum; - } - - // Round to user desired precision based on format string - if (is_floating_point && !(flags & ImGuiSliderFlags_NoRoundToFormat)) - v_cur = RoundScalarWithFormatT(format, data_type, v_cur); - - // Preserve remainder after rounding has been applied. This also allow slow tweaking of values. - g.DragCurrentAccumDirty = false; - if (is_logarithmic) - { - // Convert to parametric space, apply delta, convert back - float v_new_parametric = ScaleRatioFromValueT(data_type, v_cur, v_min, v_max, is_logarithmic, logarithmic_zero_epsilon, zero_deadzone_halfsize); - g.DragCurrentAccum -= (float)(v_new_parametric - v_old_ref_for_accum_remainder); - } - else - { - g.DragCurrentAccum -= (float)((SIGNEDTYPE)v_cur - (SIGNEDTYPE)*v); - } - - // Lose zero sign for float/double - if (v_cur == (TYPE)-0) - v_cur = (TYPE)0; - - // Clamp values (+ handle overflow/wrap-around for integer types) - if (*v != v_cur && is_clamped) - { - if (v_cur < v_min || (v_cur > *v && adjust_delta < 0.0f && !is_floating_point)) - v_cur = v_min; - if (v_cur > v_max || (v_cur < *v && adjust_delta > 0.0f && !is_floating_point)) - v_cur = v_max; - } - - // Apply result - if (*v == v_cur) - return false; - *v = v_cur; - return true; -} - -bool ImGui::DragBehavior(ImGuiID id, ImGuiDataType data_type, void* p_v, float v_speed, const void* p_min, const void* p_max, const char* format, ImGuiSliderFlags flags) -{ - // Read imgui.cpp "API BREAKING CHANGES" section for 1.78 if you hit this assert. - IM_ASSERT((flags == 1 || (flags & ImGuiSliderFlags_InvalidMask_) == 0) && "Invalid ImGuiSliderFlags flags! Has the 'float power' argument been mistakenly cast to flags? Call function with ImGuiSliderFlags_Logarithmic flags instead."); - - ImGuiContext& g = *GImGui; - if (g.ActiveId == id) - { - // Those are the things we can do easily outside the DragBehaviorT<> template, saves code generation. - if (g.ActiveIdSource == ImGuiInputSource_Mouse && !g.IO.MouseDown[0]) - ClearActiveID(); - else if ((g.ActiveIdSource == ImGuiInputSource_Keyboard || g.ActiveIdSource == ImGuiInputSource_Gamepad) && g.NavActivatePressedId == id && !g.ActiveIdIsJustActivated) - ClearActiveID(); - } - if (g.ActiveId != id) - return false; - if ((g.LastItemData.InFlags & ImGuiItemFlags_ReadOnly) || (flags & ImGuiSliderFlags_ReadOnly)) - return false; - - switch (data_type) - { - case ImGuiDataType_S8: { ImS32 v32 = (ImS32)*(ImS8*)p_v; bool r = DragBehaviorT(ImGuiDataType_S32, &v32, v_speed, p_min ? *(const ImS8*) p_min : IM_S8_MIN, p_max ? *(const ImS8*)p_max : IM_S8_MAX, format, flags); if (r) *(ImS8*)p_v = (ImS8)v32; return r; } - case ImGuiDataType_U8: { ImU32 v32 = (ImU32)*(ImU8*)p_v; bool r = DragBehaviorT(ImGuiDataType_U32, &v32, v_speed, p_min ? *(const ImU8*) p_min : IM_U8_MIN, p_max ? *(const ImU8*)p_max : IM_U8_MAX, format, flags); if (r) *(ImU8*)p_v = (ImU8)v32; return r; } - case ImGuiDataType_S16: { ImS32 v32 = (ImS32)*(ImS16*)p_v; bool r = DragBehaviorT(ImGuiDataType_S32, &v32, v_speed, p_min ? *(const ImS16*)p_min : IM_S16_MIN, p_max ? *(const ImS16*)p_max : IM_S16_MAX, format, flags); if (r) *(ImS16*)p_v = (ImS16)v32; return r; } - case ImGuiDataType_U16: { ImU32 v32 = (ImU32)*(ImU16*)p_v; bool r = DragBehaviorT(ImGuiDataType_U32, &v32, v_speed, p_min ? *(const ImU16*)p_min : IM_U16_MIN, p_max ? *(const ImU16*)p_max : IM_U16_MAX, format, flags); if (r) *(ImU16*)p_v = (ImU16)v32; return r; } - case ImGuiDataType_S32: return DragBehaviorT(data_type, (ImS32*)p_v, v_speed, p_min ? *(const ImS32* )p_min : IM_S32_MIN, p_max ? *(const ImS32* )p_max : IM_S32_MAX, format, flags); - case ImGuiDataType_U32: return DragBehaviorT(data_type, (ImU32*)p_v, v_speed, p_min ? *(const ImU32* )p_min : IM_U32_MIN, p_max ? *(const ImU32* )p_max : IM_U32_MAX, format, flags); - case ImGuiDataType_S64: return DragBehaviorT(data_type, (ImS64*)p_v, v_speed, p_min ? *(const ImS64* )p_min : IM_S64_MIN, p_max ? *(const ImS64* )p_max : IM_S64_MAX, format, flags); - case ImGuiDataType_U64: return DragBehaviorT(data_type, (ImU64*)p_v, v_speed, p_min ? *(const ImU64* )p_min : IM_U64_MIN, p_max ? *(const ImU64* )p_max : IM_U64_MAX, format, flags); - case ImGuiDataType_Float: return DragBehaviorT(data_type, (float*)p_v, v_speed, p_min ? *(const float* )p_min : -FLT_MAX, p_max ? *(const float* )p_max : FLT_MAX, format, flags); - case ImGuiDataType_Double: return DragBehaviorT(data_type, (double*)p_v, v_speed, p_min ? *(const double*)p_min : -DBL_MAX, p_max ? *(const double*)p_max : DBL_MAX, format, flags); - case ImGuiDataType_COUNT: break; - } - IM_ASSERT(0); - return false; -} - -// Note: p_data, p_min and p_max are _pointers_ to a memory address holding the data. For a Drag widget, p_min and p_max are optional. -// Read code of e.g. DragFloat(), DragInt() etc. or examples in 'Demo->Widgets->Data Types' to understand how to use this function directly. -bool ImGui::DragScalar(const char* label, ImGuiDataType data_type, void* p_data, float v_speed, const void* p_min, const void* p_max, const char* format, ImGuiSliderFlags flags) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - - ImGuiContext& g = *GImGui; - const ImGuiStyle& style = g.Style; - const ImGuiID id = window->GetID(label); - const float w = CalcItemWidth(); - - const ImVec2 label_size = CalcTextSize(label, NULL, true); - const ImRect frame_bb(window->DC.CursorPos, window->DC.CursorPos + ImVec2(w, label_size.y + style.FramePadding.y * 2.0f)); - const ImRect total_bb(frame_bb.Min, frame_bb.Max + ImVec2(label_size.x > 0.0f ? style.ItemInnerSpacing.x + label_size.x : 0.0f, 0.0f)); - - const bool temp_input_allowed = (flags & ImGuiSliderFlags_NoInput) == 0; - ItemSize(total_bb, style.FramePadding.y); - if (!ItemAdd(total_bb, id, &frame_bb, temp_input_allowed ? ImGuiItemFlags_Inputable : 0)) - return false; - - // Default format string when passing NULL - if (format == NULL) - format = DataTypeGetInfo(data_type)->PrintFmt; - - const bool hovered = ItemHoverable(frame_bb, id, g.LastItemData.InFlags); - bool temp_input_is_active = temp_input_allowed && TempInputIsActive(id); - if (!temp_input_is_active) - { - // Tabbing or CTRL-clicking on Drag turns it into an InputText - const bool input_requested_by_tabbing = temp_input_allowed && (g.LastItemData.StatusFlags & ImGuiItemStatusFlags_FocusedByTabbing) != 0; - const bool clicked = hovered && IsMouseClicked(0, id); - const bool double_clicked = (hovered && g.IO.MouseClickedCount[0] == 2 && TestKeyOwner(ImGuiKey_MouseLeft, id)); - const bool make_active = (input_requested_by_tabbing || clicked || double_clicked || g.NavActivateId == id); - if (make_active && (clicked || double_clicked)) - SetKeyOwner(ImGuiKey_MouseLeft, id); - if (make_active && temp_input_allowed) - if (input_requested_by_tabbing || (clicked && g.IO.KeyCtrl) || double_clicked || (g.NavActivateId == id && (g.NavActivateFlags & ImGuiActivateFlags_PreferInput))) - temp_input_is_active = true; - - // (Optional) simple click (without moving) turns Drag into an InputText - if (g.IO.ConfigDragClickToInputText && temp_input_allowed && !temp_input_is_active) - if (g.ActiveId == id && hovered && g.IO.MouseReleased[0] && !IsMouseDragPastThreshold(0, g.IO.MouseDragThreshold * DRAG_MOUSE_THRESHOLD_FACTOR)) - { - g.NavActivateId = id; - g.NavActivateFlags = ImGuiActivateFlags_PreferInput; - temp_input_is_active = true; - } - - if (make_active && !temp_input_is_active) - { - SetActiveID(id, window); - SetFocusID(id, window); - FocusWindow(window); - g.ActiveIdUsingNavDirMask = (1 << ImGuiDir_Left) | (1 << ImGuiDir_Right); - } - } - - if (temp_input_is_active) - { - // Only clamp CTRL+Click input when ImGuiSliderFlags_AlwaysClamp is set - const bool is_clamp_input = (flags & ImGuiSliderFlags_AlwaysClamp) != 0 && (p_min == NULL || p_max == NULL || DataTypeCompare(data_type, p_min, p_max) < 0); - return TempInputScalar(frame_bb, id, label, data_type, p_data, format, is_clamp_input ? p_min : NULL, is_clamp_input ? p_max : NULL); - } - - // Draw frame - const ImU32 frame_col = GetColorU32(g.ActiveId == id ? ImGuiCol_FrameBgActive : hovered ? ImGuiCol_FrameBgHovered : ImGuiCol_FrameBg); - RenderNavHighlight(frame_bb, id); - RenderFrame(frame_bb.Min, frame_bb.Max, frame_col, true, style.FrameRounding); - - // Drag behavior - const bool value_changed = DragBehavior(id, data_type, p_data, v_speed, p_min, p_max, format, flags); - if (value_changed) - MarkItemEdited(id); - - // Display value using user-provided display format so user can add prefix/suffix/decorations to the value. - char value_buf[64]; - const char* value_buf_end = value_buf + DataTypeFormatString(value_buf, IM_ARRAYSIZE(value_buf), data_type, p_data, format); - if (g.LogEnabled) - LogSetNextTextDecoration("{", "}"); - RenderTextClipped(frame_bb.Min, frame_bb.Max, value_buf, value_buf_end, NULL, ImVec2(0.5f, 0.5f)); - - if (label_size.x > 0.0f) - RenderText(ImVec2(frame_bb.Max.x + style.ItemInnerSpacing.x, frame_bb.Min.y + style.FramePadding.y), label); - - IMGUI_TEST_ENGINE_ITEM_INFO(id, label, g.LastItemData.StatusFlags | (temp_input_allowed ? ImGuiItemStatusFlags_Inputable : 0)); - return value_changed; -} - -bool ImGui::DragScalarN(const char* label, ImGuiDataType data_type, void* p_data, int components, float v_speed, const void* p_min, const void* p_max, const char* format, ImGuiSliderFlags flags) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - - ImGuiContext& g = *GImGui; - bool value_changed = false; - BeginGroup(); - PushID(label); - PushMultiItemsWidths(components, CalcItemWidth()); - size_t type_size = GDataTypeInfo[data_type].Size; - for (int i = 0; i < components; i++) - { - PushID(i); - if (i > 0) - SameLine(0, g.Style.ItemInnerSpacing.x); - value_changed |= DragScalar("", data_type, p_data, v_speed, p_min, p_max, format, flags); - PopID(); - PopItemWidth(); - p_data = (void*)((char*)p_data + type_size); - } - PopID(); - - const char* label_end = FindRenderedTextEnd(label); - if (label != label_end) - { - SameLine(0, g.Style.ItemInnerSpacing.x); - TextEx(label, label_end); - } - - EndGroup(); - return value_changed; -} - -bool ImGui::DragFloat(const char* label, float* v, float v_speed, float v_min, float v_max, const char* format, ImGuiSliderFlags flags) -{ - return DragScalar(label, ImGuiDataType_Float, v, v_speed, &v_min, &v_max, format, flags); -} - -bool ImGui::DragFloat2(const char* label, float v[2], float v_speed, float v_min, float v_max, const char* format, ImGuiSliderFlags flags) -{ - return DragScalarN(label, ImGuiDataType_Float, v, 2, v_speed, &v_min, &v_max, format, flags); -} - -bool ImGui::DragFloat3(const char* label, float v[3], float v_speed, float v_min, float v_max, const char* format, ImGuiSliderFlags flags) -{ - return DragScalarN(label, ImGuiDataType_Float, v, 3, v_speed, &v_min, &v_max, format, flags); -} - -bool ImGui::DragFloat4(const char* label, float v[4], float v_speed, float v_min, float v_max, const char* format, ImGuiSliderFlags flags) -{ - return DragScalarN(label, ImGuiDataType_Float, v, 4, v_speed, &v_min, &v_max, format, flags); -} - -// NB: You likely want to specify the ImGuiSliderFlags_AlwaysClamp when using this. -bool ImGui::DragFloatRange2(const char* label, float* v_current_min, float* v_current_max, float v_speed, float v_min, float v_max, const char* format, const char* format_max, ImGuiSliderFlags flags) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - - ImGuiContext& g = *GImGui; - PushID(label); - BeginGroup(); - PushMultiItemsWidths(2, CalcItemWidth()); - - float min_min = (v_min >= v_max) ? -FLT_MAX : v_min; - float min_max = (v_min >= v_max) ? *v_current_max : ImMin(v_max, *v_current_max); - ImGuiSliderFlags min_flags = flags | ((min_min == min_max) ? ImGuiSliderFlags_ReadOnly : 0); - bool value_changed = DragScalar("##min", ImGuiDataType_Float, v_current_min, v_speed, &min_min, &min_max, format, min_flags); - PopItemWidth(); - SameLine(0, g.Style.ItemInnerSpacing.x); - - float max_min = (v_min >= v_max) ? *v_current_min : ImMax(v_min, *v_current_min); - float max_max = (v_min >= v_max) ? FLT_MAX : v_max; - ImGuiSliderFlags max_flags = flags | ((max_min == max_max) ? ImGuiSliderFlags_ReadOnly : 0); - value_changed |= DragScalar("##max", ImGuiDataType_Float, v_current_max, v_speed, &max_min, &max_max, format_max ? format_max : format, max_flags); - PopItemWidth(); - SameLine(0, g.Style.ItemInnerSpacing.x); - - TextEx(label, FindRenderedTextEnd(label)); - EndGroup(); - PopID(); - - return value_changed; -} - -// NB: v_speed is float to allow adjusting the drag speed with more precision -bool ImGui::DragInt(const char* label, int* v, float v_speed, int v_min, int v_max, const char* format, ImGuiSliderFlags flags) -{ - return DragScalar(label, ImGuiDataType_S32, v, v_speed, &v_min, &v_max, format, flags); -} - -bool ImGui::DragInt2(const char* label, int v[2], float v_speed, int v_min, int v_max, const char* format, ImGuiSliderFlags flags) -{ - return DragScalarN(label, ImGuiDataType_S32, v, 2, v_speed, &v_min, &v_max, format, flags); -} - -bool ImGui::DragInt3(const char* label, int v[3], float v_speed, int v_min, int v_max, const char* format, ImGuiSliderFlags flags) -{ - return DragScalarN(label, ImGuiDataType_S32, v, 3, v_speed, &v_min, &v_max, format, flags); -} - -bool ImGui::DragInt4(const char* label, int v[4], float v_speed, int v_min, int v_max, const char* format, ImGuiSliderFlags flags) -{ - return DragScalarN(label, ImGuiDataType_S32, v, 4, v_speed, &v_min, &v_max, format, flags); -} - -// NB: You likely want to specify the ImGuiSliderFlags_AlwaysClamp when using this. -bool ImGui::DragIntRange2(const char* label, int* v_current_min, int* v_current_max, float v_speed, int v_min, int v_max, const char* format, const char* format_max, ImGuiSliderFlags flags) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - - ImGuiContext& g = *GImGui; - PushID(label); - BeginGroup(); - PushMultiItemsWidths(2, CalcItemWidth()); - - int min_min = (v_min >= v_max) ? INT_MIN : v_min; - int min_max = (v_min >= v_max) ? *v_current_max : ImMin(v_max, *v_current_max); - ImGuiSliderFlags min_flags = flags | ((min_min == min_max) ? ImGuiSliderFlags_ReadOnly : 0); - bool value_changed = DragInt("##min", v_current_min, v_speed, min_min, min_max, format, min_flags); - PopItemWidth(); - SameLine(0, g.Style.ItemInnerSpacing.x); - - int max_min = (v_min >= v_max) ? *v_current_min : ImMax(v_min, *v_current_min); - int max_max = (v_min >= v_max) ? INT_MAX : v_max; - ImGuiSliderFlags max_flags = flags | ((max_min == max_max) ? ImGuiSliderFlags_ReadOnly : 0); - value_changed |= DragInt("##max", v_current_max, v_speed, max_min, max_max, format_max ? format_max : format, max_flags); - PopItemWidth(); - SameLine(0, g.Style.ItemInnerSpacing.x); - - TextEx(label, FindRenderedTextEnd(label)); - EndGroup(); - PopID(); - - return value_changed; -} - -//------------------------------------------------------------------------- -// [SECTION] Widgets: SliderScalar, SliderFloat, SliderInt, etc. -//------------------------------------------------------------------------- -// - ScaleRatioFromValueT<> [Internal] -// - ScaleValueFromRatioT<> [Internal] -// - SliderBehaviorT<>() [Internal] -// - SliderBehavior() [Internal] -// - SliderScalar() -// - SliderScalarN() -// - SliderFloat() -// - SliderFloat2() -// - SliderFloat3() -// - SliderFloat4() -// - SliderAngle() -// - SliderInt() -// - SliderInt2() -// - SliderInt3() -// - SliderInt4() -// - VSliderScalar() -// - VSliderFloat() -// - VSliderInt() -//------------------------------------------------------------------------- - -// Convert a value v in the output space of a slider into a parametric position on the slider itself (the logical opposite of ScaleValueFromRatioT) -template -float ImGui::ScaleRatioFromValueT(ImGuiDataType data_type, TYPE v, TYPE v_min, TYPE v_max, bool is_logarithmic, float logarithmic_zero_epsilon, float zero_deadzone_halfsize) -{ - if (v_min == v_max) - return 0.0f; - IM_UNUSED(data_type); - - const TYPE v_clamped = (v_min < v_max) ? ImClamp(v, v_min, v_max) : ImClamp(v, v_max, v_min); - if (is_logarithmic) - { - bool flipped = v_max < v_min; - - if (flipped) // Handle the case where the range is backwards - ImSwap(v_min, v_max); - - // Fudge min/max to avoid getting close to log(0) - FLOATTYPE v_min_fudged = (ImAbs((FLOATTYPE)v_min) < logarithmic_zero_epsilon) ? ((v_min < 0.0f) ? -logarithmic_zero_epsilon : logarithmic_zero_epsilon) : (FLOATTYPE)v_min; - FLOATTYPE v_max_fudged = (ImAbs((FLOATTYPE)v_max) < logarithmic_zero_epsilon) ? ((v_max < 0.0f) ? -logarithmic_zero_epsilon : logarithmic_zero_epsilon) : (FLOATTYPE)v_max; - - // Awkward special cases - we need ranges of the form (-100 .. 0) to convert to (-100 .. -epsilon), not (-100 .. epsilon) - if ((v_min == 0.0f) && (v_max < 0.0f)) - v_min_fudged = -logarithmic_zero_epsilon; - else if ((v_max == 0.0f) && (v_min < 0.0f)) - v_max_fudged = -logarithmic_zero_epsilon; - - float result; - if (v_clamped <= v_min_fudged) - result = 0.0f; // Workaround for values that are in-range but below our fudge - else if (v_clamped >= v_max_fudged) - result = 1.0f; // Workaround for values that are in-range but above our fudge - else if ((v_min * v_max) < 0.0f) // Range crosses zero, so split into two portions - { - float zero_point_center = (-(float)v_min) / ((float)v_max - (float)v_min); // The zero point in parametric space. There's an argument we should take the logarithmic nature into account when calculating this, but for now this should do (and the most common case of a symmetrical range works fine) - float zero_point_snap_L = zero_point_center - zero_deadzone_halfsize; - float zero_point_snap_R = zero_point_center + zero_deadzone_halfsize; - if (v == 0.0f) - result = zero_point_center; // Special case for exactly zero - else if (v < 0.0f) - result = (1.0f - (float)(ImLog(-(FLOATTYPE)v_clamped / logarithmic_zero_epsilon) / ImLog(-v_min_fudged / logarithmic_zero_epsilon))) * zero_point_snap_L; - else - result = zero_point_snap_R + ((float)(ImLog((FLOATTYPE)v_clamped / logarithmic_zero_epsilon) / ImLog(v_max_fudged / logarithmic_zero_epsilon)) * (1.0f - zero_point_snap_R)); - } - else if ((v_min < 0.0f) || (v_max < 0.0f)) // Entirely negative slider - result = 1.0f - (float)(ImLog(-(FLOATTYPE)v_clamped / -v_max_fudged) / ImLog(-v_min_fudged / -v_max_fudged)); - else - result = (float)(ImLog((FLOATTYPE)v_clamped / v_min_fudged) / ImLog(v_max_fudged / v_min_fudged)); - - return flipped ? (1.0f - result) : result; - } - else - { - // Linear slider - return (float)((FLOATTYPE)(SIGNEDTYPE)(v_clamped - v_min) / (FLOATTYPE)(SIGNEDTYPE)(v_max - v_min)); - } -} - -// Convert a parametric position on a slider into a value v in the output space (the logical opposite of ScaleRatioFromValueT) -template -TYPE ImGui::ScaleValueFromRatioT(ImGuiDataType data_type, float t, TYPE v_min, TYPE v_max, bool is_logarithmic, float logarithmic_zero_epsilon, float zero_deadzone_halfsize) -{ - // We special-case the extents because otherwise our logarithmic fudging can lead to "mathematically correct" - // but non-intuitive behaviors like a fully-left slider not actually reaching the minimum value. Also generally simpler. - if (t <= 0.0f || v_min == v_max) - return v_min; - if (t >= 1.0f) - return v_max; - - TYPE result = (TYPE)0; - if (is_logarithmic) - { - // Fudge min/max to avoid getting silly results close to zero - FLOATTYPE v_min_fudged = (ImAbs((FLOATTYPE)v_min) < logarithmic_zero_epsilon) ? ((v_min < 0.0f) ? -logarithmic_zero_epsilon : logarithmic_zero_epsilon) : (FLOATTYPE)v_min; - FLOATTYPE v_max_fudged = (ImAbs((FLOATTYPE)v_max) < logarithmic_zero_epsilon) ? ((v_max < 0.0f) ? -logarithmic_zero_epsilon : logarithmic_zero_epsilon) : (FLOATTYPE)v_max; - - const bool flipped = v_max < v_min; // Check if range is "backwards" - if (flipped) - ImSwap(v_min_fudged, v_max_fudged); - - // Awkward special case - we need ranges of the form (-100 .. 0) to convert to (-100 .. -epsilon), not (-100 .. epsilon) - if ((v_max == 0.0f) && (v_min < 0.0f)) - v_max_fudged = -logarithmic_zero_epsilon; - - float t_with_flip = flipped ? (1.0f - t) : t; // t, but flipped if necessary to account for us flipping the range - - if ((v_min * v_max) < 0.0f) // Range crosses zero, so we have to do this in two parts - { - float zero_point_center = (-(float)ImMin(v_min, v_max)) / ImAbs((float)v_max - (float)v_min); // The zero point in parametric space - float zero_point_snap_L = zero_point_center - zero_deadzone_halfsize; - float zero_point_snap_R = zero_point_center + zero_deadzone_halfsize; - if (t_with_flip >= zero_point_snap_L && t_with_flip <= zero_point_snap_R) - result = (TYPE)0.0f; // Special case to make getting exactly zero possible (the epsilon prevents it otherwise) - else if (t_with_flip < zero_point_center) - result = (TYPE)-(logarithmic_zero_epsilon * ImPow(-v_min_fudged / logarithmic_zero_epsilon, (FLOATTYPE)(1.0f - (t_with_flip / zero_point_snap_L)))); - else - result = (TYPE)(logarithmic_zero_epsilon * ImPow(v_max_fudged / logarithmic_zero_epsilon, (FLOATTYPE)((t_with_flip - zero_point_snap_R) / (1.0f - zero_point_snap_R)))); - } - else if ((v_min < 0.0f) || (v_max < 0.0f)) // Entirely negative slider - result = (TYPE)-(-v_max_fudged * ImPow(-v_min_fudged / -v_max_fudged, (FLOATTYPE)(1.0f - t_with_flip))); - else - result = (TYPE)(v_min_fudged * ImPow(v_max_fudged / v_min_fudged, (FLOATTYPE)t_with_flip)); - } - else - { - // Linear slider - const bool is_floating_point = (data_type == ImGuiDataType_Float) || (data_type == ImGuiDataType_Double); - if (is_floating_point) - { - result = ImLerp(v_min, v_max, t); - } - else if (t < 1.0) - { - // - For integer values we want the clicking position to match the grab box so we round above - // This code is carefully tuned to work with large values (e.g. high ranges of U64) while preserving this property.. - // - Not doing a *1.0 multiply at the end of a range as it tends to be lossy. While absolute aiming at a large s64/u64 - // range is going to be imprecise anyway, with this check we at least make the edge values matches expected limits. - FLOATTYPE v_new_off_f = (SIGNEDTYPE)(v_max - v_min) * t; - result = (TYPE)((SIGNEDTYPE)v_min + (SIGNEDTYPE)(v_new_off_f + (FLOATTYPE)(v_min > v_max ? -0.5 : 0.5))); - } - } - - return result; -} - -// FIXME: Try to move more of the code into shared SliderBehavior() -template -bool ImGui::SliderBehaviorT(const ImRect& bb, ImGuiID id, ImGuiDataType data_type, TYPE* v, const TYPE v_min, const TYPE v_max, const char* format, ImGuiSliderFlags flags, ImRect* out_grab_bb) -{ - ImGuiContext& g = *GImGui; - const ImGuiStyle& style = g.Style; - - const ImGuiAxis axis = (flags & ImGuiSliderFlags_Vertical) ? ImGuiAxis_Y : ImGuiAxis_X; - const bool is_logarithmic = (flags & ImGuiSliderFlags_Logarithmic) != 0; - const bool is_floating_point = (data_type == ImGuiDataType_Float) || (data_type == ImGuiDataType_Double); - const float v_range_f = (float)(v_min < v_max ? v_max - v_min : v_min - v_max); // We don't need high precision for what we do with it. - - // Calculate bounds - const float grab_padding = 2.0f; // FIXME: Should be part of style. - const float slider_sz = (bb.Max[axis] - bb.Min[axis]) - grab_padding * 2.0f; - float grab_sz = style.GrabMinSize; - if (!is_floating_point && v_range_f >= 0.0f) // v_range_f < 0 may happen on integer overflows - grab_sz = ImMax(slider_sz / (v_range_f + 1), style.GrabMinSize); // For integer sliders: if possible have the grab size represent 1 unit - grab_sz = ImMin(grab_sz, slider_sz); - const float slider_usable_sz = slider_sz - grab_sz; - const float slider_usable_pos_min = bb.Min[axis] + grab_padding + grab_sz * 0.5f; - const float slider_usable_pos_max = bb.Max[axis] - grab_padding - grab_sz * 0.5f; - - float logarithmic_zero_epsilon = 0.0f; // Only valid when is_logarithmic is true - float zero_deadzone_halfsize = 0.0f; // Only valid when is_logarithmic is true - if (is_logarithmic) - { - // When using logarithmic sliders, we need to clamp to avoid hitting zero, but our choice of clamp value greatly affects slider precision. We attempt to use the specified precision to estimate a good lower bound. - const int decimal_precision = is_floating_point ? ImParseFormatPrecision(format, 3) : 1; - logarithmic_zero_epsilon = ImPow(0.1f, (float)decimal_precision); - zero_deadzone_halfsize = (style.LogSliderDeadzone * 0.5f) / ImMax(slider_usable_sz, 1.0f); - } - - // Process interacting with the slider - bool value_changed = false; - if (g.ActiveId == id) - { - bool set_new_value = false; - float clicked_t = 0.0f; - if (g.ActiveIdSource == ImGuiInputSource_Mouse) - { - if (!g.IO.MouseDown[0]) - { - ClearActiveID(); - } - else - { - const float mouse_abs_pos = g.IO.MousePos[axis]; - if (g.ActiveIdIsJustActivated) - { - float grab_t = ScaleRatioFromValueT(data_type, *v, v_min, v_max, is_logarithmic, logarithmic_zero_epsilon, zero_deadzone_halfsize); - if (axis == ImGuiAxis_Y) - grab_t = 1.0f - grab_t; - const float grab_pos = ImLerp(slider_usable_pos_min, slider_usable_pos_max, grab_t); - const bool clicked_around_grab = (mouse_abs_pos >= grab_pos - grab_sz * 0.5f - 1.0f) && (mouse_abs_pos <= grab_pos + grab_sz * 0.5f + 1.0f); // No harm being extra generous here. - g.SliderGrabClickOffset = (clicked_around_grab && is_floating_point) ? mouse_abs_pos - grab_pos : 0.0f; - } - if (slider_usable_sz > 0.0f) - clicked_t = ImSaturate((mouse_abs_pos - g.SliderGrabClickOffset - slider_usable_pos_min) / slider_usable_sz); - if (axis == ImGuiAxis_Y) - clicked_t = 1.0f - clicked_t; - set_new_value = true; - } - } - else if (g.ActiveIdSource == ImGuiInputSource_Keyboard || g.ActiveIdSource == ImGuiInputSource_Gamepad) - { - if (g.ActiveIdIsJustActivated) - { - g.SliderCurrentAccum = 0.0f; // Reset any stored nav delta upon activation - g.SliderCurrentAccumDirty = false; - } - - float input_delta = (axis == ImGuiAxis_X) ? GetNavTweakPressedAmount(axis) : -GetNavTweakPressedAmount(axis); - if (input_delta != 0.0f) - { - const bool tweak_slow = IsKeyDown((g.NavInputSource == ImGuiInputSource_Gamepad) ? ImGuiKey_NavGamepadTweakSlow : ImGuiKey_NavKeyboardTweakSlow); - const bool tweak_fast = IsKeyDown((g.NavInputSource == ImGuiInputSource_Gamepad) ? ImGuiKey_NavGamepadTweakFast : ImGuiKey_NavKeyboardTweakFast); - const int decimal_precision = is_floating_point ? ImParseFormatPrecision(format, 3) : 0; - if (decimal_precision > 0) - { - input_delta /= 100.0f; // Gamepad/keyboard tweak speeds in % of slider bounds - if (tweak_slow) - input_delta /= 10.0f; - } - else - { - if ((v_range_f >= -100.0f && v_range_f <= 100.0f && v_range_f != 0.0f) || tweak_slow) - input_delta = ((input_delta < 0.0f) ? -1.0f : +1.0f) / v_range_f; // Gamepad/keyboard tweak speeds in integer steps - else - input_delta /= 100.0f; - } - if (tweak_fast) - input_delta *= 10.0f; - - g.SliderCurrentAccum += input_delta; - g.SliderCurrentAccumDirty = true; - } - - float delta = g.SliderCurrentAccum; - if (g.NavActivatePressedId == id && !g.ActiveIdIsJustActivated) - { - ClearActiveID(); - } - else if (g.SliderCurrentAccumDirty) - { - clicked_t = ScaleRatioFromValueT(data_type, *v, v_min, v_max, is_logarithmic, logarithmic_zero_epsilon, zero_deadzone_halfsize); - - if ((clicked_t >= 1.0f && delta > 0.0f) || (clicked_t <= 0.0f && delta < 0.0f)) // This is to avoid applying the saturation when already past the limits - { - set_new_value = false; - g.SliderCurrentAccum = 0.0f; // If pushing up against the limits, don't continue to accumulate - } - else - { - set_new_value = true; - float old_clicked_t = clicked_t; - clicked_t = ImSaturate(clicked_t + delta); - - // Calculate what our "new" clicked_t will be, and thus how far we actually moved the slider, and subtract this from the accumulator - TYPE v_new = ScaleValueFromRatioT(data_type, clicked_t, v_min, v_max, is_logarithmic, logarithmic_zero_epsilon, zero_deadzone_halfsize); - if (is_floating_point && !(flags & ImGuiSliderFlags_NoRoundToFormat)) - v_new = RoundScalarWithFormatT(format, data_type, v_new); - float new_clicked_t = ScaleRatioFromValueT(data_type, v_new, v_min, v_max, is_logarithmic, logarithmic_zero_epsilon, zero_deadzone_halfsize); - - if (delta > 0) - g.SliderCurrentAccum -= ImMin(new_clicked_t - old_clicked_t, delta); - else - g.SliderCurrentAccum -= ImMax(new_clicked_t - old_clicked_t, delta); - } - - g.SliderCurrentAccumDirty = false; - } - } - - if (set_new_value) - if ((g.LastItemData.InFlags & ImGuiItemFlags_ReadOnly) || (flags & ImGuiSliderFlags_ReadOnly)) - set_new_value = false; - - if (set_new_value) - { - TYPE v_new = ScaleValueFromRatioT(data_type, clicked_t, v_min, v_max, is_logarithmic, logarithmic_zero_epsilon, zero_deadzone_halfsize); - - // Round to user desired precision based on format string - if (is_floating_point && !(flags & ImGuiSliderFlags_NoRoundToFormat)) - v_new = RoundScalarWithFormatT(format, data_type, v_new); - - // Apply result - if (*v != v_new) - { - *v = v_new; - value_changed = true; - } - } - } - - if (slider_sz < 1.0f) - { - *out_grab_bb = ImRect(bb.Min, bb.Min); - } - else - { - // Output grab position so it can be displayed by the caller - float grab_t = ScaleRatioFromValueT(data_type, *v, v_min, v_max, is_logarithmic, logarithmic_zero_epsilon, zero_deadzone_halfsize); - if (axis == ImGuiAxis_Y) - grab_t = 1.0f - grab_t; - const float grab_pos = ImLerp(slider_usable_pos_min, slider_usable_pos_max, grab_t); - if (axis == ImGuiAxis_X) - *out_grab_bb = ImRect(grab_pos - grab_sz * 0.5f, bb.Min.y + grab_padding, grab_pos + grab_sz * 0.5f, bb.Max.y - grab_padding); - else - *out_grab_bb = ImRect(bb.Min.x + grab_padding, grab_pos - grab_sz * 0.5f, bb.Max.x - grab_padding, grab_pos + grab_sz * 0.5f); - } - - return value_changed; -} - -// For 32-bit and larger types, slider bounds are limited to half the natural type range. -// So e.g. an integer Slider between INT_MAX-10 and INT_MAX will fail, but an integer Slider between INT_MAX/2-10 and INT_MAX/2 will be ok. -// It would be possible to lift that limitation with some work but it doesn't seem to be worth it for sliders. -bool ImGui::SliderBehavior(const ImRect& bb, ImGuiID id, ImGuiDataType data_type, void* p_v, const void* p_min, const void* p_max, const char* format, ImGuiSliderFlags flags, ImRect* out_grab_bb) -{ - // Read imgui.cpp "API BREAKING CHANGES" section for 1.78 if you hit this assert. - IM_ASSERT((flags == 1 || (flags & ImGuiSliderFlags_InvalidMask_) == 0) && "Invalid ImGuiSliderFlags flag! Has the 'float power' argument been mistakenly cast to flags? Call function with ImGuiSliderFlags_Logarithmic flags instead."); - - switch (data_type) - { - case ImGuiDataType_S8: { ImS32 v32 = (ImS32)*(ImS8*)p_v; bool r = SliderBehaviorT(bb, id, ImGuiDataType_S32, &v32, *(const ImS8*)p_min, *(const ImS8*)p_max, format, flags, out_grab_bb); if (r) *(ImS8*)p_v = (ImS8)v32; return r; } - case ImGuiDataType_U8: { ImU32 v32 = (ImU32)*(ImU8*)p_v; bool r = SliderBehaviorT(bb, id, ImGuiDataType_U32, &v32, *(const ImU8*)p_min, *(const ImU8*)p_max, format, flags, out_grab_bb); if (r) *(ImU8*)p_v = (ImU8)v32; return r; } - case ImGuiDataType_S16: { ImS32 v32 = (ImS32)*(ImS16*)p_v; bool r = SliderBehaviorT(bb, id, ImGuiDataType_S32, &v32, *(const ImS16*)p_min, *(const ImS16*)p_max, format, flags, out_grab_bb); if (r) *(ImS16*)p_v = (ImS16)v32; return r; } - case ImGuiDataType_U16: { ImU32 v32 = (ImU32)*(ImU16*)p_v; bool r = SliderBehaviorT(bb, id, ImGuiDataType_U32, &v32, *(const ImU16*)p_min, *(const ImU16*)p_max, format, flags, out_grab_bb); if (r) *(ImU16*)p_v = (ImU16)v32; return r; } - case ImGuiDataType_S32: - IM_ASSERT(*(const ImS32*)p_min >= IM_S32_MIN / 2 && *(const ImS32*)p_max <= IM_S32_MAX / 2); - return SliderBehaviorT(bb, id, data_type, (ImS32*)p_v, *(const ImS32*)p_min, *(const ImS32*)p_max, format, flags, out_grab_bb); - case ImGuiDataType_U32: - IM_ASSERT(*(const ImU32*)p_max <= IM_U32_MAX / 2); - return SliderBehaviorT(bb, id, data_type, (ImU32*)p_v, *(const ImU32*)p_min, *(const ImU32*)p_max, format, flags, out_grab_bb); - case ImGuiDataType_S64: - IM_ASSERT(*(const ImS64*)p_min >= IM_S64_MIN / 2 && *(const ImS64*)p_max <= IM_S64_MAX / 2); - return SliderBehaviorT(bb, id, data_type, (ImS64*)p_v, *(const ImS64*)p_min, *(const ImS64*)p_max, format, flags, out_grab_bb); - case ImGuiDataType_U64: - IM_ASSERT(*(const ImU64*)p_max <= IM_U64_MAX / 2); - return SliderBehaviorT(bb, id, data_type, (ImU64*)p_v, *(const ImU64*)p_min, *(const ImU64*)p_max, format, flags, out_grab_bb); - case ImGuiDataType_Float: - IM_ASSERT(*(const float*)p_min >= -FLT_MAX / 2.0f && *(const float*)p_max <= FLT_MAX / 2.0f); - return SliderBehaviorT(bb, id, data_type, (float*)p_v, *(const float*)p_min, *(const float*)p_max, format, flags, out_grab_bb); - case ImGuiDataType_Double: - IM_ASSERT(*(const double*)p_min >= -DBL_MAX / 2.0f && *(const double*)p_max <= DBL_MAX / 2.0f); - return SliderBehaviorT(bb, id, data_type, (double*)p_v, *(const double*)p_min, *(const double*)p_max, format, flags, out_grab_bb); - case ImGuiDataType_COUNT: break; - } - IM_ASSERT(0); - return false; -} - -// Note: p_data, p_min and p_max are _pointers_ to a memory address holding the data. For a slider, they are all required. -// Read code of e.g. SliderFloat(), SliderInt() etc. or examples in 'Demo->Widgets->Data Types' to understand how to use this function directly. -bool ImGui::SliderScalar(const char* label, ImGuiDataType data_type, void* p_data, const void* p_min, const void* p_max, const char* format, ImGuiSliderFlags flags) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - - ImGuiContext& g = *GImGui; - const ImGuiStyle& style = g.Style; - const ImGuiID id = window->GetID(label); - const float w = CalcItemWidth(); - - const ImVec2 label_size = CalcTextSize(label, NULL, true); - const ImRect frame_bb(window->DC.CursorPos, window->DC.CursorPos + ImVec2(w, label_size.y + style.FramePadding.y * 2.0f)); - const ImRect total_bb(frame_bb.Min, frame_bb.Max + ImVec2(label_size.x > 0.0f ? style.ItemInnerSpacing.x + label_size.x : 0.0f, 0.0f)); - - const bool temp_input_allowed = (flags & ImGuiSliderFlags_NoInput) == 0; - ItemSize(total_bb, style.FramePadding.y); - if (!ItemAdd(total_bb, id, &frame_bb, temp_input_allowed ? ImGuiItemFlags_Inputable : 0)) - return false; - - // Default format string when passing NULL - if (format == NULL) - format = DataTypeGetInfo(data_type)->PrintFmt; - - const bool hovered = ItemHoverable(frame_bb, id, g.LastItemData.InFlags); - bool temp_input_is_active = temp_input_allowed && TempInputIsActive(id); - if (!temp_input_is_active) - { - // Tabbing or CTRL-clicking on Slider turns it into an input box - const bool input_requested_by_tabbing = temp_input_allowed && (g.LastItemData.StatusFlags & ImGuiItemStatusFlags_FocusedByTabbing) != 0; - const bool clicked = hovered && IsMouseClicked(0, id); - const bool make_active = (input_requested_by_tabbing || clicked || g.NavActivateId == id); - if (make_active && clicked) - SetKeyOwner(ImGuiKey_MouseLeft, id); - if (make_active && temp_input_allowed) - if (input_requested_by_tabbing || (clicked && g.IO.KeyCtrl) || (g.NavActivateId == id && (g.NavActivateFlags & ImGuiActivateFlags_PreferInput))) - temp_input_is_active = true; - - if (make_active && !temp_input_is_active) - { - SetActiveID(id, window); - SetFocusID(id, window); - FocusWindow(window); - g.ActiveIdUsingNavDirMask |= (1 << ImGuiDir_Left) | (1 << ImGuiDir_Right); - } - } - - if (temp_input_is_active) - { - // Only clamp CTRL+Click input when ImGuiSliderFlags_AlwaysClamp is set - const bool is_clamp_input = (flags & ImGuiSliderFlags_AlwaysClamp) != 0; - return TempInputScalar(frame_bb, id, label, data_type, p_data, format, is_clamp_input ? p_min : NULL, is_clamp_input ? p_max : NULL); - } - - // Draw frame - const ImU32 frame_col = GetColorU32(g.ActiveId == id ? ImGuiCol_FrameBgActive : hovered ? ImGuiCol_FrameBgHovered : ImGuiCol_FrameBg); - RenderNavHighlight(frame_bb, id); - RenderFrame(frame_bb.Min, frame_bb.Max, frame_col, true, g.Style.FrameRounding); - - // Slider behavior - ImRect grab_bb; - const bool value_changed = SliderBehavior(frame_bb, id, data_type, p_data, p_min, p_max, format, flags, &grab_bb); - if (value_changed) - MarkItemEdited(id); - - // Render grab - if (grab_bb.Max.x > grab_bb.Min.x) - window->DrawList->AddRectFilled(grab_bb.Min, grab_bb.Max, GetColorU32(g.ActiveId == id ? ImGuiCol_SliderGrabActive : ImGuiCol_SliderGrab), style.GrabRounding); - - // Display value using user-provided display format so user can add prefix/suffix/decorations to the value. - char value_buf[64]; - const char* value_buf_end = value_buf + DataTypeFormatString(value_buf, IM_ARRAYSIZE(value_buf), data_type, p_data, format); - if (g.LogEnabled) - LogSetNextTextDecoration("{", "}"); - RenderTextClipped(frame_bb.Min, frame_bb.Max, value_buf, value_buf_end, NULL, ImVec2(0.5f, 0.5f)); - - if (label_size.x > 0.0f) - RenderText(ImVec2(frame_bb.Max.x + style.ItemInnerSpacing.x, frame_bb.Min.y + style.FramePadding.y), label); - - IMGUI_TEST_ENGINE_ITEM_INFO(id, label, g.LastItemData.StatusFlags | (temp_input_allowed ? ImGuiItemStatusFlags_Inputable : 0)); - return value_changed; -} - -// Add multiple sliders on 1 line for compact edition of multiple components -bool ImGui::SliderScalarN(const char* label, ImGuiDataType data_type, void* v, int components, const void* v_min, const void* v_max, const char* format, ImGuiSliderFlags flags) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - - ImGuiContext& g = *GImGui; - bool value_changed = false; - BeginGroup(); - PushID(label); - PushMultiItemsWidths(components, CalcItemWidth()); - size_t type_size = GDataTypeInfo[data_type].Size; - for (int i = 0; i < components; i++) - { - PushID(i); - if (i > 0) - SameLine(0, g.Style.ItemInnerSpacing.x); - value_changed |= SliderScalar("", data_type, v, v_min, v_max, format, flags); - PopID(); - PopItemWidth(); - v = (void*)((char*)v + type_size); - } - PopID(); - - const char* label_end = FindRenderedTextEnd(label); - if (label != label_end) - { - SameLine(0, g.Style.ItemInnerSpacing.x); - TextEx(label, label_end); - } - - EndGroup(); - return value_changed; -} - -bool ImGui::SliderFloat(const char* label, float* v, float v_min, float v_max, const char* format, ImGuiSliderFlags flags) -{ - return SliderScalar(label, ImGuiDataType_Float, v, &v_min, &v_max, format, flags); -} - -bool ImGui::SliderFloat2(const char* label, float v[2], float v_min, float v_max, const char* format, ImGuiSliderFlags flags) -{ - return SliderScalarN(label, ImGuiDataType_Float, v, 2, &v_min, &v_max, format, flags); -} - -bool ImGui::SliderFloat3(const char* label, float v[3], float v_min, float v_max, const char* format, ImGuiSliderFlags flags) -{ - return SliderScalarN(label, ImGuiDataType_Float, v, 3, &v_min, &v_max, format, flags); -} - -bool ImGui::SliderFloat4(const char* label, float v[4], float v_min, float v_max, const char* format, ImGuiSliderFlags flags) -{ - return SliderScalarN(label, ImGuiDataType_Float, v, 4, &v_min, &v_max, format, flags); -} - -bool ImGui::SliderAngle(const char* label, float* v_rad, float v_degrees_min, float v_degrees_max, const char* format, ImGuiSliderFlags flags) -{ - if (format == NULL) - format = "%.0f deg"; - float v_deg = (*v_rad) * 360.0f / (2 * IM_PI); - bool value_changed = SliderFloat(label, &v_deg, v_degrees_min, v_degrees_max, format, flags); - *v_rad = v_deg * (2 * IM_PI) / 360.0f; - return value_changed; -} - -bool ImGui::SliderInt(const char* label, int* v, int v_min, int v_max, const char* format, ImGuiSliderFlags flags) -{ - return SliderScalar(label, ImGuiDataType_S32, v, &v_min, &v_max, format, flags); -} - -bool ImGui::SliderInt2(const char* label, int v[2], int v_min, int v_max, const char* format, ImGuiSliderFlags flags) -{ - return SliderScalarN(label, ImGuiDataType_S32, v, 2, &v_min, &v_max, format, flags); -} - -bool ImGui::SliderInt3(const char* label, int v[3], int v_min, int v_max, const char* format, ImGuiSliderFlags flags) -{ - return SliderScalarN(label, ImGuiDataType_S32, v, 3, &v_min, &v_max, format, flags); -} - -bool ImGui::SliderInt4(const char* label, int v[4], int v_min, int v_max, const char* format, ImGuiSliderFlags flags) -{ - return SliderScalarN(label, ImGuiDataType_S32, v, 4, &v_min, &v_max, format, flags); -} - -bool ImGui::VSliderScalar(const char* label, const ImVec2& size, ImGuiDataType data_type, void* p_data, const void* p_min, const void* p_max, const char* format, ImGuiSliderFlags flags) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - - ImGuiContext& g = *GImGui; - const ImGuiStyle& style = g.Style; - const ImGuiID id = window->GetID(label); - - const ImVec2 label_size = CalcTextSize(label, NULL, true); - const ImRect frame_bb(window->DC.CursorPos, window->DC.CursorPos + size); - const ImRect bb(frame_bb.Min, frame_bb.Max + ImVec2(label_size.x > 0.0f ? style.ItemInnerSpacing.x + label_size.x : 0.0f, 0.0f)); - - ItemSize(bb, style.FramePadding.y); - if (!ItemAdd(frame_bb, id)) - return false; - - // Default format string when passing NULL - if (format == NULL) - format = DataTypeGetInfo(data_type)->PrintFmt; - - const bool hovered = ItemHoverable(frame_bb, id, g.LastItemData.InFlags); - const bool clicked = hovered && IsMouseClicked(0, id); - if (clicked || g.NavActivateId == id) - { - if (clicked) - SetKeyOwner(ImGuiKey_MouseLeft, id); - SetActiveID(id, window); - SetFocusID(id, window); - FocusWindow(window); - g.ActiveIdUsingNavDirMask |= (1 << ImGuiDir_Up) | (1 << ImGuiDir_Down); - } - - // Draw frame - const ImU32 frame_col = GetColorU32(g.ActiveId == id ? ImGuiCol_FrameBgActive : hovered ? ImGuiCol_FrameBgHovered : ImGuiCol_FrameBg); - RenderNavHighlight(frame_bb, id); - RenderFrame(frame_bb.Min, frame_bb.Max, frame_col, true, g.Style.FrameRounding); - - // Slider behavior - ImRect grab_bb; - const bool value_changed = SliderBehavior(frame_bb, id, data_type, p_data, p_min, p_max, format, flags | ImGuiSliderFlags_Vertical, &grab_bb); - if (value_changed) - MarkItemEdited(id); - - // Render grab - if (grab_bb.Max.y > grab_bb.Min.y) - window->DrawList->AddRectFilled(grab_bb.Min, grab_bb.Max, GetColorU32(g.ActiveId == id ? ImGuiCol_SliderGrabActive : ImGuiCol_SliderGrab), style.GrabRounding); - - // Display value using user-provided display format so user can add prefix/suffix/decorations to the value. - // For the vertical slider we allow centered text to overlap the frame padding - char value_buf[64]; - const char* value_buf_end = value_buf + DataTypeFormatString(value_buf, IM_ARRAYSIZE(value_buf), data_type, p_data, format); - RenderTextClipped(ImVec2(frame_bb.Min.x, frame_bb.Min.y + style.FramePadding.y), frame_bb.Max, value_buf, value_buf_end, NULL, ImVec2(0.5f, 0.0f)); - if (label_size.x > 0.0f) - RenderText(ImVec2(frame_bb.Max.x + style.ItemInnerSpacing.x, frame_bb.Min.y + style.FramePadding.y), label); - - return value_changed; -} - -bool ImGui::VSliderFloat(const char* label, const ImVec2& size, float* v, float v_min, float v_max, const char* format, ImGuiSliderFlags flags) -{ - return VSliderScalar(label, size, ImGuiDataType_Float, v, &v_min, &v_max, format, flags); -} - -bool ImGui::VSliderInt(const char* label, const ImVec2& size, int* v, int v_min, int v_max, const char* format, ImGuiSliderFlags flags) -{ - return VSliderScalar(label, size, ImGuiDataType_S32, v, &v_min, &v_max, format, flags); -} - -//------------------------------------------------------------------------- -// [SECTION] Widgets: InputScalar, InputFloat, InputInt, etc. -//------------------------------------------------------------------------- -// - ImParseFormatFindStart() [Internal] -// - ImParseFormatFindEnd() [Internal] -// - ImParseFormatTrimDecorations() [Internal] -// - ImParseFormatSanitizeForPrinting() [Internal] -// - ImParseFormatSanitizeForScanning() [Internal] -// - ImParseFormatPrecision() [Internal] -// - TempInputTextScalar() [Internal] -// - InputScalar() -// - InputScalarN() -// - InputFloat() -// - InputFloat2() -// - InputFloat3() -// - InputFloat4() -// - InputInt() -// - InputInt2() -// - InputInt3() -// - InputInt4() -// - InputDouble() -//------------------------------------------------------------------------- - -// We don't use strchr() because our strings are usually very short and often start with '%' -const char* ImParseFormatFindStart(const char* fmt) -{ - while (char c = fmt[0]) - { - if (c == '%' && fmt[1] != '%') - return fmt; - else if (c == '%') - fmt++; - fmt++; - } - return fmt; -} - -const char* ImParseFormatFindEnd(const char* fmt) -{ - // Printf/scanf types modifiers: I/L/h/j/l/t/w/z. Other uppercase letters qualify as types aka end of the format. - if (fmt[0] != '%') - return fmt; - const unsigned int ignored_uppercase_mask = (1 << ('I'-'A')) | (1 << ('L'-'A')); - const unsigned int ignored_lowercase_mask = (1 << ('h'-'a')) | (1 << ('j'-'a')) | (1 << ('l'-'a')) | (1 << ('t'-'a')) | (1 << ('w'-'a')) | (1 << ('z'-'a')); - for (char c; (c = *fmt) != 0; fmt++) - { - if (c >= 'A' && c <= 'Z' && ((1 << (c - 'A')) & ignored_uppercase_mask) == 0) - return fmt + 1; - if (c >= 'a' && c <= 'z' && ((1 << (c - 'a')) & ignored_lowercase_mask) == 0) - return fmt + 1; - } - return fmt; -} - -// Extract the format out of a format string with leading or trailing decorations -// fmt = "blah blah" -> return "" -// fmt = "%.3f" -> return fmt -// fmt = "hello %.3f" -> return fmt + 6 -// fmt = "%.3f hello" -> return buf written with "%.3f" -const char* ImParseFormatTrimDecorations(const char* fmt, char* buf, size_t buf_size) -{ - const char* fmt_start = ImParseFormatFindStart(fmt); - if (fmt_start[0] != '%') - return ""; - const char* fmt_end = ImParseFormatFindEnd(fmt_start); - if (fmt_end[0] == 0) // If we only have leading decoration, we don't need to copy the data. - return fmt_start; - ImStrncpy(buf, fmt_start, ImMin((size_t)(fmt_end - fmt_start) + 1, buf_size)); - return buf; -} - -// Sanitize format -// - Zero terminate so extra characters after format (e.g. "%f123") don't confuse atof/atoi -// - stb_sprintf.h supports several new modifiers which format numbers in a way that also makes them incompatible atof/atoi. -void ImParseFormatSanitizeForPrinting(const char* fmt_in, char* fmt_out, size_t fmt_out_size) -{ - const char* fmt_end = ImParseFormatFindEnd(fmt_in); - IM_UNUSED(fmt_out_size); - IM_ASSERT((size_t)(fmt_end - fmt_in + 1) < fmt_out_size); // Format is too long, let us know if this happens to you! - while (fmt_in < fmt_end) - { - char c = *fmt_in++; - if (c != '\'' && c != '$' && c != '_') // Custom flags provided by stb_sprintf.h. POSIX 2008 also supports '. - *(fmt_out++) = c; - } - *fmt_out = 0; // Zero-terminate -} - -// - For scanning we need to remove all width and precision fields and flags "%+3.7f" -> "%f". BUT don't strip types like "%I64d" which includes digits. ! "%07I64d" -> "%I64d" -const char* ImParseFormatSanitizeForScanning(const char* fmt_in, char* fmt_out, size_t fmt_out_size) -{ - const char* fmt_end = ImParseFormatFindEnd(fmt_in); - const char* fmt_out_begin = fmt_out; - IM_UNUSED(fmt_out_size); - IM_ASSERT((size_t)(fmt_end - fmt_in + 1) < fmt_out_size); // Format is too long, let us know if this happens to you! - bool has_type = false; - while (fmt_in < fmt_end) - { - char c = *fmt_in++; - if (!has_type && ((c >= '0' && c <= '9') || c == '.' || c == '+' || c == '#')) - continue; - has_type |= ((c >= 'a' && c <= 'z') || (c >= 'A' && c <= 'Z')); // Stop skipping digits - if (c != '\'' && c != '$' && c != '_') // Custom flags provided by stb_sprintf.h. POSIX 2008 also supports '. - *(fmt_out++) = c; - } - *fmt_out = 0; // Zero-terminate - return fmt_out_begin; -} - -template -static const char* ImAtoi(const char* src, TYPE* output) -{ - int negative = 0; - if (*src == '-') { negative = 1; src++; } - if (*src == '+') { src++; } - TYPE v = 0; - while (*src >= '0' && *src <= '9') - v = (v * 10) + (*src++ - '0'); - *output = negative ? -v : v; - return src; -} - -// Parse display precision back from the display format string -// FIXME: This is still used by some navigation code path to infer a minimum tweak step, but we should aim to rework widgets so it isn't needed. -int ImParseFormatPrecision(const char* fmt, int default_precision) -{ - fmt = ImParseFormatFindStart(fmt); - if (fmt[0] != '%') - return default_precision; - fmt++; - while (*fmt >= '0' && *fmt <= '9') - fmt++; - int precision = INT_MAX; - if (*fmt == '.') - { - fmt = ImAtoi(fmt + 1, &precision); - if (precision < 0 || precision > 99) - precision = default_precision; - } - if (*fmt == 'e' || *fmt == 'E') // Maximum precision with scientific notation - precision = -1; - if ((*fmt == 'g' || *fmt == 'G') && precision == INT_MAX) - precision = -1; - return (precision == INT_MAX) ? default_precision : precision; -} - -// Create text input in place of another active widget (e.g. used when doing a CTRL+Click on drag/slider widgets) -// FIXME: Facilitate using this in variety of other situations. -bool ImGui::TempInputText(const ImRect& bb, ImGuiID id, const char* label, char* buf, int buf_size, ImGuiInputTextFlags flags) -{ - // On the first frame, g.TempInputTextId == 0, then on subsequent frames it becomes == id. - // We clear ActiveID on the first frame to allow the InputText() taking it back. - ImGuiContext& g = *GImGui; - const bool init = (g.TempInputId != id); - if (init) - ClearActiveID(); - - g.CurrentWindow->DC.CursorPos = bb.Min; - bool value_changed = InputTextEx(label, NULL, buf, buf_size, bb.GetSize(), flags | ImGuiInputTextFlags_MergedItem); - if (init) - { - // First frame we started displaying the InputText widget, we expect it to take the active id. - IM_ASSERT(g.ActiveId == id); - g.TempInputId = g.ActiveId; - } - return value_changed; -} - -static inline ImGuiInputTextFlags InputScalar_DefaultCharsFilter(ImGuiDataType data_type, const char* format) -{ - if (data_type == ImGuiDataType_Float || data_type == ImGuiDataType_Double) - return ImGuiInputTextFlags_CharsScientific; - const char format_last_char = format[0] ? format[strlen(format) - 1] : 0; - return (format_last_char == 'x' || format_last_char == 'X') ? ImGuiInputTextFlags_CharsHexadecimal : ImGuiInputTextFlags_CharsDecimal; -} - -// Note that Drag/Slider functions are only forwarding the min/max values clamping values if the ImGuiSliderFlags_AlwaysClamp flag is set! -// This is intended: this way we allow CTRL+Click manual input to set a value out of bounds, for maximum flexibility. -// However this may not be ideal for all uses, as some user code may break on out of bound values. -bool ImGui::TempInputScalar(const ImRect& bb, ImGuiID id, const char* label, ImGuiDataType data_type, void* p_data, const char* format, const void* p_clamp_min, const void* p_clamp_max) -{ - // FIXME: May need to clarify display behavior if format doesn't contain %. - // "%d" -> "%d" / "There are %d items" -> "%d" / "items" -> "%d" (fallback). Also see #6405 - const ImGuiDataTypeInfo* type_info = DataTypeGetInfo(data_type); - char fmt_buf[32]; - char data_buf[32]; - format = ImParseFormatTrimDecorations(format, fmt_buf, IM_ARRAYSIZE(fmt_buf)); - if (format[0] == 0) - format = type_info->PrintFmt; - DataTypeFormatString(data_buf, IM_ARRAYSIZE(data_buf), data_type, p_data, format); - ImStrTrimBlanks(data_buf); - - ImGuiInputTextFlags flags = ImGuiInputTextFlags_AutoSelectAll | ImGuiInputTextFlags_NoMarkEdited; - flags |= InputScalar_DefaultCharsFilter(data_type, format); - - bool value_changed = false; - if (TempInputText(bb, id, label, data_buf, IM_ARRAYSIZE(data_buf), flags)) - { - // Backup old value - size_t data_type_size = type_info->Size; - ImGuiDataTypeTempStorage data_backup; - memcpy(&data_backup, p_data, data_type_size); - - // Apply new value (or operations) then clamp - DataTypeApplyFromText(data_buf, data_type, p_data, format); - if (p_clamp_min || p_clamp_max) - { - if (p_clamp_min && p_clamp_max && DataTypeCompare(data_type, p_clamp_min, p_clamp_max) > 0) - ImSwap(p_clamp_min, p_clamp_max); - DataTypeClamp(data_type, p_data, p_clamp_min, p_clamp_max); - } - - // Only mark as edited if new value is different - value_changed = memcmp(&data_backup, p_data, data_type_size) != 0; - if (value_changed) - MarkItemEdited(id); - } - return value_changed; -} - -// Note: p_data, p_step, p_step_fast are _pointers_ to a memory address holding the data. For an Input widget, p_step and p_step_fast are optional. -// Read code of e.g. InputFloat(), InputInt() etc. or examples in 'Demo->Widgets->Data Types' to understand how to use this function directly. -bool ImGui::InputScalar(const char* label, ImGuiDataType data_type, void* p_data, const void* p_step, const void* p_step_fast, const char* format, ImGuiInputTextFlags flags) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - - ImGuiContext& g = *GImGui; - ImGuiStyle& style = g.Style; - - if (format == NULL) - format = DataTypeGetInfo(data_type)->PrintFmt; - - char buf[64]; - DataTypeFormatString(buf, IM_ARRAYSIZE(buf), data_type, p_data, format); - - // Testing ActiveId as a minor optimization as filtering is not needed until active - if (g.ActiveId == 0 && (flags & (ImGuiInputTextFlags_CharsDecimal | ImGuiInputTextFlags_CharsHexadecimal | ImGuiInputTextFlags_CharsScientific)) == 0) - flags |= InputScalar_DefaultCharsFilter(data_type, format); - flags |= ImGuiInputTextFlags_AutoSelectAll | ImGuiInputTextFlags_NoMarkEdited; // We call MarkItemEdited() ourselves by comparing the actual data rather than the string. - - bool value_changed = false; - if (p_step == NULL) - { - if (InputText(label, buf, IM_ARRAYSIZE(buf), flags)) - value_changed = DataTypeApplyFromText(buf, data_type, p_data, format); - } - else - { - const float button_size = GetFrameHeight(); - - BeginGroup(); // The only purpose of the group here is to allow the caller to query item data e.g. IsItemActive() - PushID(label); - SetNextItemWidth(ImMax(1.0f, CalcItemWidth() - (button_size + style.ItemInnerSpacing.x) * 2)); - if (InputText("", buf, IM_ARRAYSIZE(buf), flags)) // PushId(label) + "" gives us the expected ID from outside point of view - value_changed = DataTypeApplyFromText(buf, data_type, p_data, format); - IMGUI_TEST_ENGINE_ITEM_INFO(g.LastItemData.ID, label, g.LastItemData.StatusFlags | ImGuiItemStatusFlags_Inputable); - - // Step buttons - const ImVec2 backup_frame_padding = style.FramePadding; - style.FramePadding.x = style.FramePadding.y; - ImGuiButtonFlags button_flags = ImGuiButtonFlags_Repeat | ImGuiButtonFlags_DontClosePopups; - if (flags & ImGuiInputTextFlags_ReadOnly) - BeginDisabled(); - SameLine(0, style.ItemInnerSpacing.x); - if (ButtonEx("-", ImVec2(button_size, button_size), button_flags)) - { - DataTypeApplyOp(data_type, '-', p_data, p_data, g.IO.KeyCtrl && p_step_fast ? p_step_fast : p_step); - value_changed = true; - } - SameLine(0, style.ItemInnerSpacing.x); - if (ButtonEx("+", ImVec2(button_size, button_size), button_flags)) - { - DataTypeApplyOp(data_type, '+', p_data, p_data, g.IO.KeyCtrl && p_step_fast ? p_step_fast : p_step); - value_changed = true; - } - if (flags & ImGuiInputTextFlags_ReadOnly) - EndDisabled(); - - const char* label_end = FindRenderedTextEnd(label); - if (label != label_end) - { - SameLine(0, style.ItemInnerSpacing.x); - TextEx(label, label_end); - } - style.FramePadding = backup_frame_padding; - - PopID(); - EndGroup(); - } - if (value_changed) - MarkItemEdited(g.LastItemData.ID); - - return value_changed; -} - -bool ImGui::InputScalarN(const char* label, ImGuiDataType data_type, void* p_data, int components, const void* p_step, const void* p_step_fast, const char* format, ImGuiInputTextFlags flags) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - - ImGuiContext& g = *GImGui; - bool value_changed = false; - BeginGroup(); - PushID(label); - PushMultiItemsWidths(components, CalcItemWidth()); - size_t type_size = GDataTypeInfo[data_type].Size; - for (int i = 0; i < components; i++) - { - PushID(i); - if (i > 0) - SameLine(0, g.Style.ItemInnerSpacing.x); - value_changed |= InputScalar("", data_type, p_data, p_step, p_step_fast, format, flags); - PopID(); - PopItemWidth(); - p_data = (void*)((char*)p_data + type_size); - } - PopID(); - - const char* label_end = FindRenderedTextEnd(label); - if (label != label_end) - { - SameLine(0.0f, g.Style.ItemInnerSpacing.x); - TextEx(label, label_end); - } - - EndGroup(); - return value_changed; -} - -bool ImGui::InputFloat(const char* label, float* v, float step, float step_fast, const char* format, ImGuiInputTextFlags flags) -{ - flags |= ImGuiInputTextFlags_CharsScientific; - return InputScalar(label, ImGuiDataType_Float, (void*)v, (void*)(step > 0.0f ? &step : NULL), (void*)(step_fast > 0.0f ? &step_fast : NULL), format, flags); -} - -bool ImGui::InputFloat2(const char* label, float v[2], const char* format, ImGuiInputTextFlags flags) -{ - return InputScalarN(label, ImGuiDataType_Float, v, 2, NULL, NULL, format, flags); -} - -bool ImGui::InputFloat3(const char* label, float v[3], const char* format, ImGuiInputTextFlags flags) -{ - return InputScalarN(label, ImGuiDataType_Float, v, 3, NULL, NULL, format, flags); -} - -bool ImGui::InputFloat4(const char* label, float v[4], const char* format, ImGuiInputTextFlags flags) -{ - return InputScalarN(label, ImGuiDataType_Float, v, 4, NULL, NULL, format, flags); -} - -bool ImGui::InputInt(const char* label, int* v, int step, int step_fast, ImGuiInputTextFlags flags) -{ - // Hexadecimal input provided as a convenience but the flag name is awkward. Typically you'd use InputText() to parse your own data, if you want to handle prefixes. - const char* format = (flags & ImGuiInputTextFlags_CharsHexadecimal) ? "%08X" : "%d"; - return InputScalar(label, ImGuiDataType_S32, (void*)v, (void*)(step > 0 ? &step : NULL), (void*)(step_fast > 0 ? &step_fast : NULL), format, flags); -} - -bool ImGui::InputInt2(const char* label, int v[2], ImGuiInputTextFlags flags) -{ - return InputScalarN(label, ImGuiDataType_S32, v, 2, NULL, NULL, "%d", flags); -} - -bool ImGui::InputInt3(const char* label, int v[3], ImGuiInputTextFlags flags) -{ - return InputScalarN(label, ImGuiDataType_S32, v, 3, NULL, NULL, "%d", flags); -} - -bool ImGui::InputInt4(const char* label, int v[4], ImGuiInputTextFlags flags) -{ - return InputScalarN(label, ImGuiDataType_S32, v, 4, NULL, NULL, "%d", flags); -} - -bool ImGui::InputDouble(const char* label, double* v, double step, double step_fast, const char* format, ImGuiInputTextFlags flags) -{ - flags |= ImGuiInputTextFlags_CharsScientific; - return InputScalar(label, ImGuiDataType_Double, (void*)v, (void*)(step > 0.0 ? &step : NULL), (void*)(step_fast > 0.0 ? &step_fast : NULL), format, flags); -} - -//------------------------------------------------------------------------- -// [SECTION] Widgets: InputText, InputTextMultiline, InputTextWithHint -//------------------------------------------------------------------------- -// - InputText() -// - InputTextWithHint() -// - InputTextMultiline() -// - InputTextGetCharInfo() [Internal] -// - InputTextReindexLines() [Internal] -// - InputTextReindexLinesRange() [Internal] -// - InputTextEx() [Internal] -// - DebugNodeInputTextState() [Internal] -//------------------------------------------------------------------------- - -bool ImGui::InputText(const char* label, char* buf, size_t buf_size, ImGuiInputTextFlags flags, ImGuiInputTextCallback callback, void* user_data) -{ - IM_ASSERT(!(flags & ImGuiInputTextFlags_Multiline)); // call InputTextMultiline() - return InputTextEx(label, NULL, buf, (int)buf_size, ImVec2(0, 0), flags, callback, user_data); -} - -bool ImGui::InputTextMultiline(const char* label, char* buf, size_t buf_size, const ImVec2& size, ImGuiInputTextFlags flags, ImGuiInputTextCallback callback, void* user_data) -{ - return InputTextEx(label, NULL, buf, (int)buf_size, size, flags | ImGuiInputTextFlags_Multiline, callback, user_data); -} - -bool ImGui::InputTextWithHint(const char* label, const char* hint, char* buf, size_t buf_size, ImGuiInputTextFlags flags, ImGuiInputTextCallback callback, void* user_data) -{ - IM_ASSERT(!(flags & ImGuiInputTextFlags_Multiline)); // call InputTextMultiline() or InputTextEx() manually if you need multi-line + hint. - return InputTextEx(label, hint, buf, (int)buf_size, ImVec2(0, 0), flags, callback, user_data); -} - -static int InputTextCalcTextLenAndLineCount(const char* text_begin, const char** out_text_end) -{ - int line_count = 0; - const char* s = text_begin; - while (char c = *s++) // We are only matching for \n so we can ignore UTF-8 decoding - if (c == '\n') - line_count++; - s--; - if (s[0] != '\n' && s[0] != '\r') - line_count++; - *out_text_end = s; - return line_count; -} - -static ImVec2 InputTextCalcTextSizeW(ImGuiContext* ctx, const ImWchar* text_begin, const ImWchar* text_end, const ImWchar** remaining, ImVec2* out_offset, bool stop_on_new_line) -{ - ImGuiContext& g = *ctx; - ImFont* font = g.Font; - const float line_height = g.FontSize; - const float scale = line_height / font->FontSize; - - ImVec2 text_size = ImVec2(0, 0); - float line_width = 0.0f; - - const ImWchar* s = text_begin; - while (s < text_end) - { - unsigned int c = (unsigned int)(*s++); - if (c == '\n') - { - text_size.x = ImMax(text_size.x, line_width); - text_size.y += line_height; - line_width = 0.0f; - if (stop_on_new_line) - break; - continue; - } - if (c == '\r') - continue; - - const float char_width = font->GetCharAdvance((ImWchar)c) * scale; - line_width += char_width; - } - - if (text_size.x < line_width) - text_size.x = line_width; - - if (out_offset) - *out_offset = ImVec2(line_width, text_size.y + line_height); // offset allow for the possibility of sitting after a trailing \n - - if (line_width > 0 || text_size.y == 0.0f) // whereas size.y will ignore the trailing \n - text_size.y += line_height; - - if (remaining) - *remaining = s; - - return text_size; -} - -// Wrapper for stb_textedit.h to edit text (our wrapper is for: statically sized buffer, single-line, wchar characters. InputText converts between UTF-8 and wchar) -namespace ImStb -{ - -static int STB_TEXTEDIT_STRINGLEN(const ImGuiInputTextState* obj) { return obj->CurLenW; } -static ImWchar STB_TEXTEDIT_GETCHAR(const ImGuiInputTextState* obj, int idx) { IM_ASSERT(idx <= obj->CurLenW); return obj->TextW[idx]; } -static float STB_TEXTEDIT_GETWIDTH(ImGuiInputTextState* obj, int line_start_idx, int char_idx) { ImWchar c = obj->TextW[line_start_idx + char_idx]; if (c == '\n') return STB_TEXTEDIT_GETWIDTH_NEWLINE; ImGuiContext& g = *obj->Ctx; return g.Font->GetCharAdvance(c) * (g.FontSize / g.Font->FontSize); } -static int STB_TEXTEDIT_KEYTOTEXT(int key) { return key >= 0x200000 ? 0 : key; } -static ImWchar STB_TEXTEDIT_NEWLINE = '\n'; -static void STB_TEXTEDIT_LAYOUTROW(StbTexteditRow* r, ImGuiInputTextState* obj, int line_start_idx) -{ - const ImWchar* text = obj->TextW.Data; - const ImWchar* text_remaining = NULL; - const ImVec2 size = InputTextCalcTextSizeW(obj->Ctx, text + line_start_idx, text + obj->CurLenW, &text_remaining, NULL, true); - r->x0 = 0.0f; - r->x1 = size.x; - r->baseline_y_delta = size.y; - r->ymin = 0.0f; - r->ymax = size.y; - r->num_chars = (int)(text_remaining - (text + line_start_idx)); -} - -static bool is_separator(unsigned int c) -{ - return c==',' || c==';' || c=='(' || c==')' || c=='{' || c=='}' || c=='[' || c==']' || c=='|' || c=='\n' || c=='\r' || c=='.' || c=='!'; -} - -static int is_word_boundary_from_right(ImGuiInputTextState* obj, int idx) -{ - // When ImGuiInputTextFlags_Password is set, we don't want actions such as CTRL+Arrow to leak the fact that underlying data are blanks or separators. - if ((obj->Flags & ImGuiInputTextFlags_Password) || idx <= 0) - return 0; - - bool prev_white = ImCharIsBlankW(obj->TextW[idx - 1]); - bool prev_separ = is_separator(obj->TextW[idx - 1]); - bool curr_white = ImCharIsBlankW(obj->TextW[idx]); - bool curr_separ = is_separator(obj->TextW[idx]); - return ((prev_white || prev_separ) && !(curr_separ || curr_white)) || (curr_separ && !prev_separ); -} -static int is_word_boundary_from_left(ImGuiInputTextState* obj, int idx) -{ - if ((obj->Flags & ImGuiInputTextFlags_Password) || idx <= 0) - return 0; - - bool prev_white = ImCharIsBlankW(obj->TextW[idx]); - bool prev_separ = is_separator(obj->TextW[idx]); - bool curr_white = ImCharIsBlankW(obj->TextW[idx - 1]); - bool curr_separ = is_separator(obj->TextW[idx - 1]); - return ((prev_white) && !(curr_separ || curr_white)) || (curr_separ && !prev_separ); -} -static int STB_TEXTEDIT_MOVEWORDLEFT_IMPL(ImGuiInputTextState* obj, int idx) { idx--; while (idx >= 0 && !is_word_boundary_from_right(obj, idx)) idx--; return idx < 0 ? 0 : idx; } -static int STB_TEXTEDIT_MOVEWORDRIGHT_MAC(ImGuiInputTextState* obj, int idx) { idx++; int len = obj->CurLenW; while (idx < len && !is_word_boundary_from_left(obj, idx)) idx++; return idx > len ? len : idx; } -static int STB_TEXTEDIT_MOVEWORDRIGHT_WIN(ImGuiInputTextState* obj, int idx) { idx++; int len = obj->CurLenW; while (idx < len && !is_word_boundary_from_right(obj, idx)) idx++; return idx > len ? len : idx; } -static int STB_TEXTEDIT_MOVEWORDRIGHT_IMPL(ImGuiInputTextState* obj, int idx) { ImGuiContext& g = *obj->Ctx; if (g.IO.ConfigMacOSXBehaviors) return STB_TEXTEDIT_MOVEWORDRIGHT_MAC(obj, idx); else return STB_TEXTEDIT_MOVEWORDRIGHT_WIN(obj, idx); } -#define STB_TEXTEDIT_MOVEWORDLEFT STB_TEXTEDIT_MOVEWORDLEFT_IMPL // They need to be #define for stb_textedit.h -#define STB_TEXTEDIT_MOVEWORDRIGHT STB_TEXTEDIT_MOVEWORDRIGHT_IMPL - -static void STB_TEXTEDIT_DELETECHARS(ImGuiInputTextState* obj, int pos, int n) -{ - ImWchar* dst = obj->TextW.Data + pos; - - // We maintain our buffer length in both UTF-8 and wchar formats - obj->Edited = true; - obj->CurLenA -= ImTextCountUtf8BytesFromStr(dst, dst + n); - obj->CurLenW -= n; - - // Offset remaining text (FIXME-OPT: Use memmove) - const ImWchar* src = obj->TextW.Data + pos + n; - while (ImWchar c = *src++) - *dst++ = c; - *dst = '\0'; -} - -static bool STB_TEXTEDIT_INSERTCHARS(ImGuiInputTextState* obj, int pos, const ImWchar* new_text, int new_text_len) -{ - const bool is_resizable = (obj->Flags & ImGuiInputTextFlags_CallbackResize) != 0; - const int text_len = obj->CurLenW; - IM_ASSERT(pos <= text_len); - - const int new_text_len_utf8 = ImTextCountUtf8BytesFromStr(new_text, new_text + new_text_len); - if (!is_resizable && (new_text_len_utf8 + obj->CurLenA + 1 > obj->BufCapacityA)) - return false; - - // Grow internal buffer if needed - if (new_text_len + text_len + 1 > obj->TextW.Size) - { - if (!is_resizable) - return false; - IM_ASSERT(text_len < obj->TextW.Size); - obj->TextW.resize(text_len + ImClamp(new_text_len * 4, 32, ImMax(256, new_text_len)) + 1); - } - - ImWchar* text = obj->TextW.Data; - if (pos != text_len) - memmove(text + pos + new_text_len, text + pos, (size_t)(text_len - pos) * sizeof(ImWchar)); - memcpy(text + pos, new_text, (size_t)new_text_len * sizeof(ImWchar)); - - obj->Edited = true; - obj->CurLenW += new_text_len; - obj->CurLenA += new_text_len_utf8; - obj->TextW[obj->CurLenW] = '\0'; - - return true; -} - -// We don't use an enum so we can build even with conflicting symbols (if another user of stb_textedit.h leak their STB_TEXTEDIT_K_* symbols) -#define STB_TEXTEDIT_K_LEFT 0x200000 // keyboard input to move cursor left -#define STB_TEXTEDIT_K_RIGHT 0x200001 // keyboard input to move cursor right -#define STB_TEXTEDIT_K_UP 0x200002 // keyboard input to move cursor up -#define STB_TEXTEDIT_K_DOWN 0x200003 // keyboard input to move cursor down -#define STB_TEXTEDIT_K_LINESTART 0x200004 // keyboard input to move cursor to start of line -#define STB_TEXTEDIT_K_LINEEND 0x200005 // keyboard input to move cursor to end of line -#define STB_TEXTEDIT_K_TEXTSTART 0x200006 // keyboard input to move cursor to start of text -#define STB_TEXTEDIT_K_TEXTEND 0x200007 // keyboard input to move cursor to end of text -#define STB_TEXTEDIT_K_DELETE 0x200008 // keyboard input to delete selection or character under cursor -#define STB_TEXTEDIT_K_BACKSPACE 0x200009 // keyboard input to delete selection or character left of cursor -#define STB_TEXTEDIT_K_UNDO 0x20000A // keyboard input to perform undo -#define STB_TEXTEDIT_K_REDO 0x20000B // keyboard input to perform redo -#define STB_TEXTEDIT_K_WORDLEFT 0x20000C // keyboard input to move cursor left one word -#define STB_TEXTEDIT_K_WORDRIGHT 0x20000D // keyboard input to move cursor right one word -#define STB_TEXTEDIT_K_PGUP 0x20000E // keyboard input to move cursor up a page -#define STB_TEXTEDIT_K_PGDOWN 0x20000F // keyboard input to move cursor down a page -#define STB_TEXTEDIT_K_SHIFT 0x400000 - -#define STB_TEXTEDIT_IMPLEMENTATION -#define STB_TEXTEDIT_memmove memmove -#include "imstb_textedit.h" - -// stb_textedit internally allows for a single undo record to do addition and deletion, but somehow, calling -// the stb_textedit_paste() function creates two separate records, so we perform it manually. (FIXME: Report to nothings/stb?) -static void stb_textedit_replace(ImGuiInputTextState* str, STB_TexteditState* state, const STB_TEXTEDIT_CHARTYPE* text, int text_len) -{ - stb_text_makeundo_replace(str, state, 0, str->CurLenW, text_len); - ImStb::STB_TEXTEDIT_DELETECHARS(str, 0, str->CurLenW); - state->cursor = state->select_start = state->select_end = 0; - if (text_len <= 0) - return; - if (ImStb::STB_TEXTEDIT_INSERTCHARS(str, 0, text, text_len)) - { - state->cursor = state->select_start = state->select_end = text_len; - state->has_preferred_x = 0; - return; - } - IM_ASSERT(0); // Failed to insert character, normally shouldn't happen because of how we currently use stb_textedit_replace() -} - -} // namespace ImStb - -void ImGuiInputTextState::OnKeyPressed(int key) -{ - stb_textedit_key(this, &Stb, key); - CursorFollow = true; - CursorAnimReset(); -} - -ImGuiInputTextCallbackData::ImGuiInputTextCallbackData() -{ - memset(this, 0, sizeof(*this)); -} - -// Public API to manipulate UTF-8 text -// We expose UTF-8 to the user (unlike the STB_TEXTEDIT_* functions which are manipulating wchar) -// FIXME: The existence of this rarely exercised code path is a bit of a nuisance. -void ImGuiInputTextCallbackData::DeleteChars(int pos, int bytes_count) -{ - IM_ASSERT(pos + bytes_count <= BufTextLen); - char* dst = Buf + pos; - const char* src = Buf + pos + bytes_count; - while (char c = *src++) - *dst++ = c; - *dst = '\0'; - - if (CursorPos >= pos + bytes_count) - CursorPos -= bytes_count; - else if (CursorPos >= pos) - CursorPos = pos; - SelectionStart = SelectionEnd = CursorPos; - BufDirty = true; - BufTextLen -= bytes_count; -} - -void ImGuiInputTextCallbackData::InsertChars(int pos, const char* new_text, const char* new_text_end) -{ - // Accept null ranges - if (new_text == new_text_end) - return; - - const bool is_resizable = (Flags & ImGuiInputTextFlags_CallbackResize) != 0; - const int new_text_len = new_text_end ? (int)(new_text_end - new_text) : (int)strlen(new_text); - if (new_text_len + BufTextLen >= BufSize) - { - if (!is_resizable) - return; - - // Contrary to STB_TEXTEDIT_INSERTCHARS() this is working in the UTF8 buffer, hence the mildly similar code (until we remove the U16 buffer altogether!) - ImGuiContext& g = *Ctx; - ImGuiInputTextState* edit_state = &g.InputTextState; - IM_ASSERT(edit_state->ID != 0 && g.ActiveId == edit_state->ID); - IM_ASSERT(Buf == edit_state->TextA.Data); - int new_buf_size = BufTextLen + ImClamp(new_text_len * 4, 32, ImMax(256, new_text_len)) + 1; - edit_state->TextA.reserve(new_buf_size + 1); - Buf = edit_state->TextA.Data; - BufSize = edit_state->BufCapacityA = new_buf_size; - } - - if (BufTextLen != pos) - memmove(Buf + pos + new_text_len, Buf + pos, (size_t)(BufTextLen - pos)); - memcpy(Buf + pos, new_text, (size_t)new_text_len * sizeof(char)); - Buf[BufTextLen + new_text_len] = '\0'; - - if (CursorPos >= pos) - CursorPos += new_text_len; - SelectionStart = SelectionEnd = CursorPos; - BufDirty = true; - BufTextLen += new_text_len; -} - -// Return false to discard a character. -static bool InputTextFilterCharacter(ImGuiContext* ctx, unsigned int* p_char, ImGuiInputTextFlags flags, ImGuiInputTextCallback callback, void* user_data, ImGuiInputSource input_source) -{ - IM_ASSERT(input_source == ImGuiInputSource_Keyboard || input_source == ImGuiInputSource_Clipboard); - unsigned int c = *p_char; - - // Filter non-printable (NB: isprint is unreliable! see #2467) - bool apply_named_filters = true; - if (c < 0x20) - { - bool pass = false; - pass |= (c == '\n' && (flags & ImGuiInputTextFlags_Multiline)); // Note that an Enter KEY will emit \r and be ignored (we poll for KEY in InputText() code) - pass |= (c == '\t' && (flags & ImGuiInputTextFlags_AllowTabInput)); - if (!pass) - return false; - apply_named_filters = false; // Override named filters below so newline and tabs can still be inserted. - } - - if (input_source != ImGuiInputSource_Clipboard) - { - // We ignore Ascii representation of delete (emitted from Backspace on OSX, see #2578, #2817) - if (c == 127) - return false; - - // Filter private Unicode range. GLFW on OSX seems to send private characters for special keys like arrow keys (FIXME) - if (c >= 0xE000 && c <= 0xF8FF) - return false; - } - - // Filter Unicode ranges we are not handling in this build - if (c > IM_UNICODE_CODEPOINT_MAX) - return false; - - // Generic named filters - if (apply_named_filters && (flags & (ImGuiInputTextFlags_CharsDecimal | ImGuiInputTextFlags_CharsHexadecimal | ImGuiInputTextFlags_CharsUppercase | ImGuiInputTextFlags_CharsNoBlank | ImGuiInputTextFlags_CharsScientific))) - { - // The libc allows overriding locale, with e.g. 'setlocale(LC_NUMERIC, "de_DE.UTF-8");' which affect the output/input of printf/scanf to use e.g. ',' instead of '.'. - // The standard mandate that programs starts in the "C" locale where the decimal point is '.'. - // We don't really intend to provide widespread support for it, but out of empathy for people stuck with using odd API, we support the bare minimum aka overriding the decimal point. - // Change the default decimal_point with: - // ImGui::GetIO()->PlatformLocaleDecimalPoint = *localeconv()->decimal_point; - // Users of non-default decimal point (in particular ',') may be affected by word-selection logic (is_word_boundary_from_right/is_word_boundary_from_left) functions. - ImGuiContext& g = *ctx; - const unsigned c_decimal_point = (unsigned int)g.IO.PlatformLocaleDecimalPoint; - if (flags & (ImGuiInputTextFlags_CharsDecimal | ImGuiInputTextFlags_CharsScientific)) - if (c == '.' || c == ',') - c = c_decimal_point; - - // Full-width -> half-width conversion for numeric fields (https://en.wikipedia.org/wiki/Halfwidth_and_Fullwidth_Forms_(Unicode_block) - // While this is mostly convenient, this has the side-effect for uninformed users accidentally inputting full-width characters that they may - // scratch their head as to why it works in numerical fields vs in generic text fields it would require support in the font. - if (flags & (ImGuiInputTextFlags_CharsDecimal | ImGuiInputTextFlags_CharsScientific | ImGuiInputTextFlags_CharsHexadecimal)) - if (c >= 0xFF01 && c <= 0xFF5E) - c = c - 0xFF01 + 0x21; - - // Allow 0-9 . - + * / - if (flags & ImGuiInputTextFlags_CharsDecimal) - if (!(c >= '0' && c <= '9') && (c != c_decimal_point) && (c != '-') && (c != '+') && (c != '*') && (c != '/')) - return false; - - // Allow 0-9 . - + * / e E - if (flags & ImGuiInputTextFlags_CharsScientific) - if (!(c >= '0' && c <= '9') && (c != c_decimal_point) && (c != '-') && (c != '+') && (c != '*') && (c != '/') && (c != 'e') && (c != 'E')) - return false; - - // Allow 0-9 a-F A-F - if (flags & ImGuiInputTextFlags_CharsHexadecimal) - if (!(c >= '0' && c <= '9') && !(c >= 'a' && c <= 'f') && !(c >= 'A' && c <= 'F')) - return false; - - // Turn a-z into A-Z - if (flags & ImGuiInputTextFlags_CharsUppercase) - if (c >= 'a' && c <= 'z') - c += (unsigned int)('A' - 'a'); - - if (flags & ImGuiInputTextFlags_CharsNoBlank) - if (ImCharIsBlankW(c)) - return false; - - *p_char = c; - } - - // Custom callback filter - if (flags & ImGuiInputTextFlags_CallbackCharFilter) - { - ImGuiContext& g = *GImGui; - ImGuiInputTextCallbackData callback_data; - callback_data.Ctx = &g; - callback_data.EventFlag = ImGuiInputTextFlags_CallbackCharFilter; - callback_data.EventChar = (ImWchar)c; - callback_data.Flags = flags; - callback_data.UserData = user_data; - if (callback(&callback_data) != 0) - return false; - *p_char = callback_data.EventChar; - if (!callback_data.EventChar) - return false; - } - - return true; -} - -// Find the shortest single replacement we can make to get the new text from the old text. -// Important: needs to be run before TextW is rewritten with the new characters because calling STB_TEXTEDIT_GETCHAR() at the end. -// FIXME: Ideally we should transition toward (1) making InsertChars()/DeleteChars() update undo-stack (2) discourage (and keep reconcile) or obsolete (and remove reconcile) accessing buffer directly. -static void InputTextReconcileUndoStateAfterUserCallback(ImGuiInputTextState* state, const char* new_buf_a, int new_length_a) -{ - ImGuiContext& g = *GImGui; - const ImWchar* old_buf = state->TextW.Data; - const int old_length = state->CurLenW; - const int new_length = ImTextCountCharsFromUtf8(new_buf_a, new_buf_a + new_length_a); - g.TempBuffer.reserve_discard((new_length + 1) * sizeof(ImWchar)); - ImWchar* new_buf = (ImWchar*)(void*)g.TempBuffer.Data; - ImTextStrFromUtf8(new_buf, new_length + 1, new_buf_a, new_buf_a + new_length_a); - - const int shorter_length = ImMin(old_length, new_length); - int first_diff; - for (first_diff = 0; first_diff < shorter_length; first_diff++) - if (old_buf[first_diff] != new_buf[first_diff]) - break; - if (first_diff == old_length && first_diff == new_length) - return; - - int old_last_diff = old_length - 1; - int new_last_diff = new_length - 1; - for (; old_last_diff >= first_diff && new_last_diff >= first_diff; old_last_diff--, new_last_diff--) - if (old_buf[old_last_diff] != new_buf[new_last_diff]) - break; - - const int insert_len = new_last_diff - first_diff + 1; - const int delete_len = old_last_diff - first_diff + 1; - if (insert_len > 0 || delete_len > 0) - if (STB_TEXTEDIT_CHARTYPE* p = stb_text_createundo(&state->Stb.undostate, first_diff, delete_len, insert_len)) - for (int i = 0; i < delete_len; i++) - p[i] = ImStb::STB_TEXTEDIT_GETCHAR(state, first_diff + i); -} - -// As InputText() retain textual data and we currently provide a path for user to not retain it (via local variables) -// we need some form of hook to reapply data back to user buffer on deactivation frame. (#4714) -// It would be more desirable that we discourage users from taking advantage of the "user not retaining data" trick, -// but that more likely be attractive when we do have _NoLiveEdit flag available. -void ImGui::InputTextDeactivateHook(ImGuiID id) -{ - ImGuiContext& g = *GImGui; - ImGuiInputTextState* state = &g.InputTextState; - if (id == 0 || state->ID != id) - return; - g.InputTextDeactivatedState.ID = state->ID; - if (state->Flags & ImGuiInputTextFlags_ReadOnly) - { - g.InputTextDeactivatedState.TextA.resize(0); // In theory this data won't be used, but clear to be neat. - } - else - { - IM_ASSERT(state->TextA.Data != 0); - g.InputTextDeactivatedState.TextA.resize(state->CurLenA + 1); - memcpy(g.InputTextDeactivatedState.TextA.Data, state->TextA.Data, state->CurLenA + 1); - } -} - -// Edit a string of text -// - buf_size account for the zero-terminator, so a buf_size of 6 can hold "Hello" but not "Hello!". -// This is so we can easily call InputText() on static arrays using ARRAYSIZE() and to match -// Note that in std::string world, capacity() would omit 1 byte used by the zero-terminator. -// - When active, hold on a privately held copy of the text (and apply back to 'buf'). So changing 'buf' while the InputText is active has no effect. -// - If you want to use ImGui::InputText() with std::string, see misc/cpp/imgui_stdlib.h -// (FIXME: Rather confusing and messy function, among the worse part of our codebase, expecting to rewrite a V2 at some point.. Partly because we are -// doing UTF8 > U16 > UTF8 conversions on the go to easily interface with stb_textedit. Ideally should stay in UTF-8 all the time. See https://github.com/nothings/stb/issues/188) -bool ImGui::InputTextEx(const char* label, const char* hint, char* buf, int buf_size, const ImVec2& size_arg, ImGuiInputTextFlags flags, ImGuiInputTextCallback callback, void* callback_user_data) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - - IM_ASSERT(buf != NULL && buf_size >= 0); - IM_ASSERT(!((flags & ImGuiInputTextFlags_CallbackHistory) && (flags & ImGuiInputTextFlags_Multiline))); // Can't use both together (they both use up/down keys) - IM_ASSERT(!((flags & ImGuiInputTextFlags_CallbackCompletion) && (flags & ImGuiInputTextFlags_AllowTabInput))); // Can't use both together (they both use tab key) - - ImGuiContext& g = *GImGui; - ImGuiIO& io = g.IO; - const ImGuiStyle& style = g.Style; - - const bool RENDER_SELECTION_WHEN_INACTIVE = false; - const bool is_multiline = (flags & ImGuiInputTextFlags_Multiline) != 0; - const bool is_readonly = (flags & ImGuiInputTextFlags_ReadOnly) != 0; - const bool is_password = (flags & ImGuiInputTextFlags_Password) != 0; - const bool is_undoable = (flags & ImGuiInputTextFlags_NoUndoRedo) == 0; - const bool is_resizable = (flags & ImGuiInputTextFlags_CallbackResize) != 0; - if (is_resizable) - IM_ASSERT(callback != NULL); // Must provide a callback if you set the ImGuiInputTextFlags_CallbackResize flag! - - if (is_multiline) // Open group before calling GetID() because groups tracks id created within their scope (including the scrollbar) - BeginGroup(); - const ImGuiID id = window->GetID(label); - const ImVec2 label_size = CalcTextSize(label, NULL, true); - const ImVec2 frame_size = CalcItemSize(size_arg, CalcItemWidth(), (is_multiline ? g.FontSize * 8.0f : label_size.y) + style.FramePadding.y * 2.0f); // Arbitrary default of 8 lines high for multi-line - const ImVec2 total_size = ImVec2(frame_size.x + (label_size.x > 0.0f ? style.ItemInnerSpacing.x + label_size.x : 0.0f), frame_size.y); - - const ImRect frame_bb(window->DC.CursorPos, window->DC.CursorPos + frame_size); - const ImRect total_bb(frame_bb.Min, frame_bb.Min + total_size); - - ImGuiWindow* draw_window = window; - ImVec2 inner_size = frame_size; - ImGuiItemStatusFlags item_status_flags = 0; - ImGuiLastItemData item_data_backup; - if (is_multiline) - { - ImVec2 backup_pos = window->DC.CursorPos; - ItemSize(total_bb, style.FramePadding.y); - if (!ItemAdd(total_bb, id, &frame_bb, ImGuiItemFlags_Inputable)) - { - EndGroup(); - return false; - } - item_status_flags = g.LastItemData.StatusFlags; - item_data_backup = g.LastItemData; - window->DC.CursorPos = backup_pos; - - // Prevent NavActivate reactivating in BeginChild(). - const ImGuiID backup_activate_id = g.NavActivateId; - if (g.ActiveId == id) // Prevent reactivation - g.NavActivateId = 0; - - // We reproduce the contents of BeginChildFrame() in order to provide 'label' so our window internal data are easier to read/debug. - PushStyleColor(ImGuiCol_ChildBg, style.Colors[ImGuiCol_FrameBg]); - PushStyleVar(ImGuiStyleVar_ChildRounding, style.FrameRounding); - PushStyleVar(ImGuiStyleVar_ChildBorderSize, style.FrameBorderSize); - PushStyleVar(ImGuiStyleVar_WindowPadding, ImVec2(0, 0)); // Ensure no clip rect so mouse hover can reach FramePadding edges - bool child_visible = BeginChildEx(label, id, frame_bb.GetSize(), true, ImGuiWindowFlags_NoMove); - g.NavActivateId = backup_activate_id; - PopStyleVar(3); - PopStyleColor(); - if (!child_visible) - { - EndChild(); - EndGroup(); - return false; - } - draw_window = g.CurrentWindow; // Child window - draw_window->DC.NavLayersActiveMaskNext |= (1 << draw_window->DC.NavLayerCurrent); // This is to ensure that EndChild() will display a navigation highlight so we can "enter" into it. - draw_window->DC.CursorPos += style.FramePadding; - inner_size.x -= draw_window->ScrollbarSizes.x; - } - else - { - // Support for internal ImGuiInputTextFlags_MergedItem flag, which could be redesigned as an ItemFlags if needed (with test performed in ItemAdd) - ItemSize(total_bb, style.FramePadding.y); - if (!(flags & ImGuiInputTextFlags_MergedItem)) - if (!ItemAdd(total_bb, id, &frame_bb, ImGuiItemFlags_Inputable)) - return false; - item_status_flags = g.LastItemData.StatusFlags; - } - const bool hovered = ItemHoverable(frame_bb, id, g.LastItemData.InFlags); - if (hovered) - g.MouseCursor = ImGuiMouseCursor_TextInput; - - // We are only allowed to access the state if we are already the active widget. - ImGuiInputTextState* state = GetInputTextState(id); - - const bool input_requested_by_tabbing = (item_status_flags & ImGuiItemStatusFlags_FocusedByTabbing) != 0; - const bool input_requested_by_nav = (g.ActiveId != id) && ((g.NavActivateId == id) && ((g.NavActivateFlags & ImGuiActivateFlags_PreferInput) || (g.NavInputSource == ImGuiInputSource_Keyboard))); - - const bool user_clicked = hovered && io.MouseClicked[0]; - const bool user_scroll_finish = is_multiline && state != NULL && g.ActiveId == 0 && g.ActiveIdPreviousFrame == GetWindowScrollbarID(draw_window, ImGuiAxis_Y); - const bool user_scroll_active = is_multiline && state != NULL && g.ActiveId == GetWindowScrollbarID(draw_window, ImGuiAxis_Y); - bool clear_active_id = false; - bool select_all = false; - - float scroll_y = is_multiline ? draw_window->Scroll.y : FLT_MAX; - - const bool init_changed_specs = (state != NULL && state->Stb.single_line != !is_multiline); // state != NULL means its our state. - const bool init_make_active = (user_clicked || user_scroll_finish || input_requested_by_nav || input_requested_by_tabbing); - const bool init_state = (init_make_active || user_scroll_active); - if ((init_state && g.ActiveId != id) || init_changed_specs) - { - // Access state even if we don't own it yet. - state = &g.InputTextState; - state->CursorAnimReset(); - - // Backup state of deactivating item so they'll have a chance to do a write to output buffer on the same frame they report IsItemDeactivatedAfterEdit (#4714) - InputTextDeactivateHook(state->ID); - - // Take a copy of the initial buffer value (both in original UTF-8 format and converted to wchar) - // From the moment we focused we are ignoring the content of 'buf' (unless we are in read-only mode) - const int buf_len = (int)strlen(buf); - state->InitialTextA.resize(buf_len + 1); // UTF-8. we use +1 to make sure that .Data is always pointing to at least an empty string. - memcpy(state->InitialTextA.Data, buf, buf_len + 1); - - // Preserve cursor position and undo/redo stack if we come back to same widget - // FIXME: Since we reworked this on 2022/06, may want to differenciate recycle_cursor vs recycle_undostate? - bool recycle_state = (state->ID == id && !init_changed_specs); - if (recycle_state && (state->CurLenA != buf_len || (state->TextAIsValid && strncmp(state->TextA.Data, buf, buf_len) != 0))) - recycle_state = false; - - // Start edition - const char* buf_end = NULL; - state->ID = id; - state->TextW.resize(buf_size + 1); // wchar count <= UTF-8 count. we use +1 to make sure that .Data is always pointing to at least an empty string. - state->TextA.resize(0); - state->TextAIsValid = false; // TextA is not valid yet (we will display buf until then) - state->CurLenW = ImTextStrFromUtf8(state->TextW.Data, buf_size, buf, NULL, &buf_end); - state->CurLenA = (int)(buf_end - buf); // We can't get the result from ImStrncpy() above because it is not UTF-8 aware. Here we'll cut off malformed UTF-8. - - if (recycle_state) - { - // Recycle existing cursor/selection/undo stack but clamp position - // Note a single mouse click will override the cursor/position immediately by calling stb_textedit_click handler. - state->CursorClamp(); - } - else - { - state->ScrollX = 0.0f; - stb_textedit_initialize_state(&state->Stb, !is_multiline); - } - - if (!is_multiline) - { - if (flags & ImGuiInputTextFlags_AutoSelectAll) - select_all = true; - if (input_requested_by_nav && (!recycle_state || !(g.NavActivateFlags & ImGuiActivateFlags_TryToPreserveState))) - select_all = true; - if (input_requested_by_tabbing || (user_clicked && io.KeyCtrl)) - select_all = true; - } - - if (flags & ImGuiInputTextFlags_AlwaysOverwrite) - state->Stb.insert_mode = 1; // stb field name is indeed incorrect (see #2863) - } - - const bool is_osx = io.ConfigMacOSXBehaviors; - if (g.ActiveId != id && init_make_active) - { - IM_ASSERT(state && state->ID == id); - SetActiveID(id, window); - SetFocusID(id, window); - FocusWindow(window); - } - if (g.ActiveId == id) - { - // Declare some inputs, the other are registered and polled via Shortcut() routing system. - if (user_clicked) - SetKeyOwner(ImGuiKey_MouseLeft, id); - g.ActiveIdUsingNavDirMask |= (1 << ImGuiDir_Left) | (1 << ImGuiDir_Right); - if (is_multiline || (flags & ImGuiInputTextFlags_CallbackHistory)) - g.ActiveIdUsingNavDirMask |= (1 << ImGuiDir_Up) | (1 << ImGuiDir_Down); - SetKeyOwner(ImGuiKey_Home, id); - SetKeyOwner(ImGuiKey_End, id); - if (is_multiline) - { - SetKeyOwner(ImGuiKey_PageUp, id); - SetKeyOwner(ImGuiKey_PageDown, id); - } - if (is_osx) - SetKeyOwner(ImGuiMod_Alt, id); - if (flags & (ImGuiInputTextFlags_CallbackCompletion | ImGuiInputTextFlags_AllowTabInput)) // Disable keyboard tabbing out as we will use the \t character. - SetShortcutRouting(ImGuiKey_Tab, id); - } - - // We have an edge case if ActiveId was set through another widget (e.g. widget being swapped), clear id immediately (don't wait until the end of the function) - if (g.ActiveId == id && state == NULL) - ClearActiveID(); - - // Release focus when we click outside - if (g.ActiveId == id && io.MouseClicked[0] && !init_state && !init_make_active) //-V560 - clear_active_id = true; - - // Lock the decision of whether we are going to take the path displaying the cursor or selection - bool render_cursor = (g.ActiveId == id) || (state && user_scroll_active); - bool render_selection = state && (state->HasSelection() || select_all) && (RENDER_SELECTION_WHEN_INACTIVE || render_cursor); - bool value_changed = false; - bool validated = false; - - // When read-only we always use the live data passed to the function - // FIXME-OPT: Because our selection/cursor code currently needs the wide text we need to convert it when active, which is not ideal :( - if (is_readonly && state != NULL && (render_cursor || render_selection)) - { - const char* buf_end = NULL; - state->TextW.resize(buf_size + 1); - state->CurLenW = ImTextStrFromUtf8(state->TextW.Data, state->TextW.Size, buf, NULL, &buf_end); - state->CurLenA = (int)(buf_end - buf); - state->CursorClamp(); - render_selection &= state->HasSelection(); - } - - // Select the buffer to render. - const bool buf_display_from_state = (render_cursor || render_selection || g.ActiveId == id) && !is_readonly && state && state->TextAIsValid; - const bool is_displaying_hint = (hint != NULL && (buf_display_from_state ? state->TextA.Data : buf)[0] == 0); - - // Password pushes a temporary font with only a fallback glyph - if (is_password && !is_displaying_hint) - { - const ImFontGlyph* glyph = g.Font->FindGlyph('*'); - ImFont* password_font = &g.InputTextPasswordFont; - password_font->FontSize = g.Font->FontSize; - password_font->Scale = g.Font->Scale; - password_font->Ascent = g.Font->Ascent; - password_font->Descent = g.Font->Descent; - password_font->ContainerAtlas = g.Font->ContainerAtlas; - password_font->FallbackGlyph = glyph; - password_font->FallbackAdvanceX = glyph->AdvanceX; - IM_ASSERT(password_font->Glyphs.empty() && password_font->IndexAdvanceX.empty() && password_font->IndexLookup.empty()); - PushFont(password_font); - } - - // Process mouse inputs and character inputs - int backup_current_text_length = 0; - if (g.ActiveId == id) - { - IM_ASSERT(state != NULL); - backup_current_text_length = state->CurLenA; - state->Edited = false; - state->BufCapacityA = buf_size; - state->Flags = flags; - - // Although we are active we don't prevent mouse from hovering other elements unless we are interacting right now with the widget. - // Down the line we should have a cleaner library-wide concept of Selected vs Active. - g.ActiveIdAllowOverlap = !io.MouseDown[0]; - - // Edit in progress - const float mouse_x = (io.MousePos.x - frame_bb.Min.x - style.FramePadding.x) + state->ScrollX; - const float mouse_y = (is_multiline ? (io.MousePos.y - draw_window->DC.CursorPos.y) : (g.FontSize * 0.5f)); - - if (select_all) - { - state->SelectAll(); - state->SelectedAllMouseLock = true; - } - else if (hovered && io.MouseClickedCount[0] >= 2 && !io.KeyShift) - { - stb_textedit_click(state, &state->Stb, mouse_x, mouse_y); - const int multiclick_count = (io.MouseClickedCount[0] - 2); - if ((multiclick_count % 2) == 0) - { - // Double-click: Select word - // We always use the "Mac" word advance for double-click select vs CTRL+Right which use the platform dependent variant: - // FIXME: There are likely many ways to improve this behavior, but there's no "right" behavior (depends on use-case, software, OS) - const bool is_bol = (state->Stb.cursor == 0) || ImStb::STB_TEXTEDIT_GETCHAR(state, state->Stb.cursor - 1) == '\n'; - if (STB_TEXT_HAS_SELECTION(&state->Stb) || !is_bol) - state->OnKeyPressed(STB_TEXTEDIT_K_WORDLEFT); - //state->OnKeyPressed(STB_TEXTEDIT_K_WORDRIGHT | STB_TEXTEDIT_K_SHIFT); - if (!STB_TEXT_HAS_SELECTION(&state->Stb)) - ImStb::stb_textedit_prep_selection_at_cursor(&state->Stb); - state->Stb.cursor = ImStb::STB_TEXTEDIT_MOVEWORDRIGHT_MAC(state, state->Stb.cursor); - state->Stb.select_end = state->Stb.cursor; - ImStb::stb_textedit_clamp(state, &state->Stb); - } - else - { - // Triple-click: Select line - const bool is_eol = ImStb::STB_TEXTEDIT_GETCHAR(state, state->Stb.cursor) == '\n'; - state->OnKeyPressed(STB_TEXTEDIT_K_LINESTART); - state->OnKeyPressed(STB_TEXTEDIT_K_LINEEND | STB_TEXTEDIT_K_SHIFT); - state->OnKeyPressed(STB_TEXTEDIT_K_RIGHT | STB_TEXTEDIT_K_SHIFT); - if (!is_eol && is_multiline) - { - ImSwap(state->Stb.select_start, state->Stb.select_end); - state->Stb.cursor = state->Stb.select_end; - } - state->CursorFollow = false; - } - state->CursorAnimReset(); - } - else if (io.MouseClicked[0] && !state->SelectedAllMouseLock) - { - if (hovered) - { - if (io.KeyShift) - stb_textedit_drag(state, &state->Stb, mouse_x, mouse_y); - else - stb_textedit_click(state, &state->Stb, mouse_x, mouse_y); - state->CursorAnimReset(); - } - } - else if (io.MouseDown[0] && !state->SelectedAllMouseLock && (io.MouseDelta.x != 0.0f || io.MouseDelta.y != 0.0f)) - { - stb_textedit_drag(state, &state->Stb, mouse_x, mouse_y); - state->CursorAnimReset(); - state->CursorFollow = true; - } - if (state->SelectedAllMouseLock && !io.MouseDown[0]) - state->SelectedAllMouseLock = false; - - // We expect backends to emit a Tab key but some also emit a Tab character which we ignore (#2467, #1336) - // (For Tab and Enter: Win32/SFML/Allegro are sending both keys and chars, GLFW and SDL are only sending keys. For Space they all send all threes) - if ((flags & ImGuiInputTextFlags_AllowTabInput) && Shortcut(ImGuiKey_Tab, id) && !is_readonly) - { - unsigned int c = '\t'; // Insert TAB - if (InputTextFilterCharacter(&g, &c, flags, callback, callback_user_data, ImGuiInputSource_Keyboard)) - state->OnKeyPressed((int)c); - } - - // Process regular text input (before we check for Return because using some IME will effectively send a Return?) - // We ignore CTRL inputs, but need to allow ALT+CTRL as some keyboards (e.g. German) use AltGR (which _is_ Alt+Ctrl) to input certain characters. - const bool ignore_char_inputs = (io.KeyCtrl && !io.KeyAlt) || (is_osx && io.KeySuper); - if (io.InputQueueCharacters.Size > 0) - { - if (!ignore_char_inputs && !is_readonly && !input_requested_by_nav) - for (int n = 0; n < io.InputQueueCharacters.Size; n++) - { - // Insert character if they pass filtering - unsigned int c = (unsigned int)io.InputQueueCharacters[n]; - if (c == '\t') // Skip Tab, see above. - continue; - if (InputTextFilterCharacter(&g, &c, flags, callback, callback_user_data, ImGuiInputSource_Keyboard)) - state->OnKeyPressed((int)c); - } - - // Consume characters - io.InputQueueCharacters.resize(0); - } - } - - // Process other shortcuts/key-presses - bool revert_edit = false; - if (g.ActiveId == id && !g.ActiveIdIsJustActivated && !clear_active_id) - { - IM_ASSERT(state != NULL); - - const int row_count_per_page = ImMax((int)((inner_size.y - style.FramePadding.y) / g.FontSize), 1); - state->Stb.row_count_per_page = row_count_per_page; - - const int k_mask = (io.KeyShift ? STB_TEXTEDIT_K_SHIFT : 0); - const bool is_wordmove_key_down = is_osx ? io.KeyAlt : io.KeyCtrl; // OS X style: Text editing cursor movement using Alt instead of Ctrl - const bool is_startend_key_down = is_osx && io.KeySuper && !io.KeyCtrl && !io.KeyAlt; // OS X style: Line/Text Start and End using Cmd+Arrows instead of Home/End - - // Using Shortcut() with ImGuiInputFlags_RouteFocused (default policy) to allow routing operations for other code (e.g. calling window trying to use CTRL+A and CTRL+B: formet would be handled by InputText) - // Otherwise we could simply assume that we own the keys as we are active. - const ImGuiInputFlags f_repeat = ImGuiInputFlags_Repeat; - const bool is_cut = (Shortcut(ImGuiMod_Shortcut | ImGuiKey_X, id, f_repeat) || Shortcut(ImGuiMod_Shift | ImGuiKey_Delete, id, f_repeat)) && !is_readonly && !is_password && (!is_multiline || state->HasSelection()); - const bool is_copy = (Shortcut(ImGuiMod_Shortcut | ImGuiKey_C, id) || Shortcut(ImGuiMod_Ctrl | ImGuiKey_Insert, id)) && !is_password && (!is_multiline || state->HasSelection()); - const bool is_paste = (Shortcut(ImGuiMod_Shortcut | ImGuiKey_V, id, f_repeat) || Shortcut(ImGuiMod_Shift | ImGuiKey_Insert, id, f_repeat)) && !is_readonly; - const bool is_undo = (Shortcut(ImGuiMod_Shortcut | ImGuiKey_Z, id, f_repeat)) && !is_readonly && is_undoable; - const bool is_redo = (Shortcut(ImGuiMod_Shortcut | ImGuiKey_Y, id, f_repeat) || (is_osx && Shortcut(ImGuiMod_Shortcut | ImGuiMod_Shift | ImGuiKey_Z, id, f_repeat))) && !is_readonly && is_undoable; - const bool is_select_all = Shortcut(ImGuiMod_Shortcut | ImGuiKey_A, id); - - // We allow validate/cancel with Nav source (gamepad) to makes it easier to undo an accidental NavInput press with no keyboard wired, but otherwise it isn't very useful. - const bool nav_gamepad_active = (io.ConfigFlags & ImGuiConfigFlags_NavEnableGamepad) != 0 && (io.BackendFlags & ImGuiBackendFlags_HasGamepad) != 0; - const bool is_enter_pressed = IsKeyPressed(ImGuiKey_Enter, true) || IsKeyPressed(ImGuiKey_KeypadEnter, true); - const bool is_gamepad_validate = nav_gamepad_active && (IsKeyPressed(ImGuiKey_NavGamepadActivate, false) || IsKeyPressed(ImGuiKey_NavGamepadInput, false)); - const bool is_cancel = Shortcut(ImGuiKey_Escape, id, f_repeat) || (nav_gamepad_active && Shortcut(ImGuiKey_NavGamepadCancel, id, f_repeat)); - - // FIXME: Should use more Shortcut() and reduce IsKeyPressed()+SetKeyOwner(), but requires modifiers combination to be taken account of. - if (IsKeyPressed(ImGuiKey_LeftArrow)) { state->OnKeyPressed((is_startend_key_down ? STB_TEXTEDIT_K_LINESTART : is_wordmove_key_down ? STB_TEXTEDIT_K_WORDLEFT : STB_TEXTEDIT_K_LEFT) | k_mask); } - else if (IsKeyPressed(ImGuiKey_RightArrow)) { state->OnKeyPressed((is_startend_key_down ? STB_TEXTEDIT_K_LINEEND : is_wordmove_key_down ? STB_TEXTEDIT_K_WORDRIGHT : STB_TEXTEDIT_K_RIGHT) | k_mask); } - else if (IsKeyPressed(ImGuiKey_UpArrow) && is_multiline) { if (io.KeyCtrl) SetScrollY(draw_window, ImMax(draw_window->Scroll.y - g.FontSize, 0.0f)); else state->OnKeyPressed((is_startend_key_down ? STB_TEXTEDIT_K_TEXTSTART : STB_TEXTEDIT_K_UP) | k_mask); } - else if (IsKeyPressed(ImGuiKey_DownArrow) && is_multiline) { if (io.KeyCtrl) SetScrollY(draw_window, ImMin(draw_window->Scroll.y + g.FontSize, GetScrollMaxY())); else state->OnKeyPressed((is_startend_key_down ? STB_TEXTEDIT_K_TEXTEND : STB_TEXTEDIT_K_DOWN) | k_mask); } - else if (IsKeyPressed(ImGuiKey_PageUp) && is_multiline) { state->OnKeyPressed(STB_TEXTEDIT_K_PGUP | k_mask); scroll_y -= row_count_per_page * g.FontSize; } - else if (IsKeyPressed(ImGuiKey_PageDown) && is_multiline) { state->OnKeyPressed(STB_TEXTEDIT_K_PGDOWN | k_mask); scroll_y += row_count_per_page * g.FontSize; } - else if (IsKeyPressed(ImGuiKey_Home)) { state->OnKeyPressed(io.KeyCtrl ? STB_TEXTEDIT_K_TEXTSTART | k_mask : STB_TEXTEDIT_K_LINESTART | k_mask); } - else if (IsKeyPressed(ImGuiKey_End)) { state->OnKeyPressed(io.KeyCtrl ? STB_TEXTEDIT_K_TEXTEND | k_mask : STB_TEXTEDIT_K_LINEEND | k_mask); } - else if (IsKeyPressed(ImGuiKey_Delete) && !is_readonly && !is_cut) - { - if (!state->HasSelection()) - { - // OSX doesn't seem to have Super+Delete to delete until end-of-line, so we don't emulate that (as opposed to Super+Backspace) - if (is_wordmove_key_down) - state->OnKeyPressed(STB_TEXTEDIT_K_WORDRIGHT | STB_TEXTEDIT_K_SHIFT); - } - state->OnKeyPressed(STB_TEXTEDIT_K_DELETE | k_mask); - } - else if (IsKeyPressed(ImGuiKey_Backspace) && !is_readonly) - { - if (!state->HasSelection()) - { - if (is_wordmove_key_down) - state->OnKeyPressed(STB_TEXTEDIT_K_WORDLEFT | STB_TEXTEDIT_K_SHIFT); - else if (is_osx && io.KeySuper && !io.KeyAlt && !io.KeyCtrl) - state->OnKeyPressed(STB_TEXTEDIT_K_LINESTART | STB_TEXTEDIT_K_SHIFT); - } - state->OnKeyPressed(STB_TEXTEDIT_K_BACKSPACE | k_mask); - } - else if (is_enter_pressed || is_gamepad_validate) - { - // Determine if we turn Enter into a \n character - bool ctrl_enter_for_new_line = (flags & ImGuiInputTextFlags_CtrlEnterForNewLine) != 0; - if (!is_multiline || is_gamepad_validate || (ctrl_enter_for_new_line && !io.KeyCtrl) || (!ctrl_enter_for_new_line && io.KeyCtrl)) - { - validated = true; - if (io.ConfigInputTextEnterKeepActive && !is_multiline) - state->SelectAll(); // No need to scroll - else - clear_active_id = true; - } - else if (!is_readonly) - { - unsigned int c = '\n'; // Insert new line - if (InputTextFilterCharacter(&g, &c, flags, callback, callback_user_data, ImGuiInputSource_Keyboard)) - state->OnKeyPressed((int)c); - } - } - else if (is_cancel) - { - if (flags & ImGuiInputTextFlags_EscapeClearsAll) - { - if (buf[0] != 0) - { - revert_edit = true; - } - else - { - render_cursor = render_selection = false; - clear_active_id = true; - } - } - else - { - clear_active_id = revert_edit = true; - render_cursor = render_selection = false; - } - } - else if (is_undo || is_redo) - { - state->OnKeyPressed(is_undo ? STB_TEXTEDIT_K_UNDO : STB_TEXTEDIT_K_REDO); - state->ClearSelection(); - } - else if (is_select_all) - { - state->SelectAll(); - state->CursorFollow = true; - } - else if (is_cut || is_copy) - { - // Cut, Copy - if (io.SetClipboardTextFn) - { - const int ib = state->HasSelection() ? ImMin(state->Stb.select_start, state->Stb.select_end) : 0; - const int ie = state->HasSelection() ? ImMax(state->Stb.select_start, state->Stb.select_end) : state->CurLenW; - const int clipboard_data_len = ImTextCountUtf8BytesFromStr(state->TextW.Data + ib, state->TextW.Data + ie) + 1; - char* clipboard_data = (char*)IM_ALLOC(clipboard_data_len * sizeof(char)); - ImTextStrToUtf8(clipboard_data, clipboard_data_len, state->TextW.Data + ib, state->TextW.Data + ie); - SetClipboardText(clipboard_data); - MemFree(clipboard_data); - } - if (is_cut) - { - if (!state->HasSelection()) - state->SelectAll(); - state->CursorFollow = true; - stb_textedit_cut(state, &state->Stb); - } - } - else if (is_paste) - { - if (const char* clipboard = GetClipboardText()) - { - // Filter pasted buffer - const int clipboard_len = (int)strlen(clipboard); - ImWchar* clipboard_filtered = (ImWchar*)IM_ALLOC((clipboard_len + 1) * sizeof(ImWchar)); - int clipboard_filtered_len = 0; - for (const char* s = clipboard; *s != 0; ) - { - unsigned int c; - s += ImTextCharFromUtf8(&c, s, NULL); - if (!InputTextFilterCharacter(&g, &c, flags, callback, callback_user_data, ImGuiInputSource_Clipboard)) - continue; - clipboard_filtered[clipboard_filtered_len++] = (ImWchar)c; - } - clipboard_filtered[clipboard_filtered_len] = 0; - if (clipboard_filtered_len > 0) // If everything was filtered, ignore the pasting operation - { - stb_textedit_paste(state, &state->Stb, clipboard_filtered, clipboard_filtered_len); - state->CursorFollow = true; - } - MemFree(clipboard_filtered); - } - } - - // Update render selection flag after events have been handled, so selection highlight can be displayed during the same frame. - render_selection |= state->HasSelection() && (RENDER_SELECTION_WHEN_INACTIVE || render_cursor); - } - - // Process callbacks and apply result back to user's buffer. - const char* apply_new_text = NULL; - int apply_new_text_length = 0; - if (g.ActiveId == id) - { - IM_ASSERT(state != NULL); - if (revert_edit && !is_readonly) - { - if (flags & ImGuiInputTextFlags_EscapeClearsAll) - { - // Clear input - IM_ASSERT(buf[0] != 0); - apply_new_text = ""; - apply_new_text_length = 0; - value_changed = true; - STB_TEXTEDIT_CHARTYPE empty_string; - stb_textedit_replace(state, &state->Stb, &empty_string, 0); - } - else if (strcmp(buf, state->InitialTextA.Data) != 0) - { - // Restore initial value. Only return true if restoring to the initial value changes the current buffer contents. - // Push records into the undo stack so we can CTRL+Z the revert operation itself - apply_new_text = state->InitialTextA.Data; - apply_new_text_length = state->InitialTextA.Size - 1; - value_changed = true; - ImVector w_text; - if (apply_new_text_length > 0) - { - w_text.resize(ImTextCountCharsFromUtf8(apply_new_text, apply_new_text + apply_new_text_length) + 1); - ImTextStrFromUtf8(w_text.Data, w_text.Size, apply_new_text, apply_new_text + apply_new_text_length); - } - stb_textedit_replace(state, &state->Stb, w_text.Data, (apply_new_text_length > 0) ? (w_text.Size - 1) : 0); - } - } - - // Apply ASCII value - if (!is_readonly) - { - state->TextAIsValid = true; - state->TextA.resize(state->TextW.Size * 4 + 1); - ImTextStrToUtf8(state->TextA.Data, state->TextA.Size, state->TextW.Data, NULL); - } - - // When using 'ImGuiInputTextFlags_EnterReturnsTrue' as a special case we reapply the live buffer back to the input buffer - // before clearing ActiveId, even though strictly speaking it wasn't modified on this frame. - // If we didn't do that, code like InputInt() with ImGuiInputTextFlags_EnterReturnsTrue would fail. - // This also allows the user to use InputText() with ImGuiInputTextFlags_EnterReturnsTrue without maintaining any user-side storage - // (please note that if you use this property along ImGuiInputTextFlags_CallbackResize you can end up with your temporary string object - // unnecessarily allocating once a frame, either store your string data, either if you don't then don't use ImGuiInputTextFlags_CallbackResize). - const bool apply_edit_back_to_user_buffer = !revert_edit || (validated && (flags & ImGuiInputTextFlags_EnterReturnsTrue) != 0); - if (apply_edit_back_to_user_buffer) - { - // Apply new value immediately - copy modified buffer back - // Note that as soon as the input box is active, the in-widget value gets priority over any underlying modification of the input buffer - // FIXME: We actually always render 'buf' when calling DrawList->AddText, making the comment above incorrect. - // FIXME-OPT: CPU waste to do this every time the widget is active, should mark dirty state from the stb_textedit callbacks. - - // User callback - if ((flags & (ImGuiInputTextFlags_CallbackCompletion | ImGuiInputTextFlags_CallbackHistory | ImGuiInputTextFlags_CallbackEdit | ImGuiInputTextFlags_CallbackAlways)) != 0) - { - IM_ASSERT(callback != NULL); - - // The reason we specify the usage semantic (Completion/History) is that Completion needs to disable keyboard TABBING at the moment. - ImGuiInputTextFlags event_flag = 0; - ImGuiKey event_key = ImGuiKey_None; - if ((flags & ImGuiInputTextFlags_CallbackCompletion) != 0 && Shortcut(ImGuiKey_Tab, id)) - { - event_flag = ImGuiInputTextFlags_CallbackCompletion; - event_key = ImGuiKey_Tab; - } - else if ((flags & ImGuiInputTextFlags_CallbackHistory) != 0 && IsKeyPressed(ImGuiKey_UpArrow)) - { - event_flag = ImGuiInputTextFlags_CallbackHistory; - event_key = ImGuiKey_UpArrow; - } - else if ((flags & ImGuiInputTextFlags_CallbackHistory) != 0 && IsKeyPressed(ImGuiKey_DownArrow)) - { - event_flag = ImGuiInputTextFlags_CallbackHistory; - event_key = ImGuiKey_DownArrow; - } - else if ((flags & ImGuiInputTextFlags_CallbackEdit) && state->Edited) - { - event_flag = ImGuiInputTextFlags_CallbackEdit; - } - else if (flags & ImGuiInputTextFlags_CallbackAlways) - { - event_flag = ImGuiInputTextFlags_CallbackAlways; - } - - if (event_flag) - { - ImGuiInputTextCallbackData callback_data; - callback_data.Ctx = &g; - callback_data.EventFlag = event_flag; - callback_data.Flags = flags; - callback_data.UserData = callback_user_data; - - char* callback_buf = is_readonly ? buf : state->TextA.Data; - callback_data.EventKey = event_key; - callback_data.Buf = callback_buf; - callback_data.BufTextLen = state->CurLenA; - callback_data.BufSize = state->BufCapacityA; - callback_data.BufDirty = false; - - // We have to convert from wchar-positions to UTF-8-positions, which can be pretty slow (an incentive to ditch the ImWchar buffer, see https://github.com/nothings/stb/issues/188) - ImWchar* text = state->TextW.Data; - const int utf8_cursor_pos = callback_data.CursorPos = ImTextCountUtf8BytesFromStr(text, text + state->Stb.cursor); - const int utf8_selection_start = callback_data.SelectionStart = ImTextCountUtf8BytesFromStr(text, text + state->Stb.select_start); - const int utf8_selection_end = callback_data.SelectionEnd = ImTextCountUtf8BytesFromStr(text, text + state->Stb.select_end); - - // Call user code - callback(&callback_data); - - // Read back what user may have modified - callback_buf = is_readonly ? buf : state->TextA.Data; // Pointer may have been invalidated by a resize callback - IM_ASSERT(callback_data.Buf == callback_buf); // Invalid to modify those fields - IM_ASSERT(callback_data.BufSize == state->BufCapacityA); - IM_ASSERT(callback_data.Flags == flags); - const bool buf_dirty = callback_data.BufDirty; - if (callback_data.CursorPos != utf8_cursor_pos || buf_dirty) { state->Stb.cursor = ImTextCountCharsFromUtf8(callback_data.Buf, callback_data.Buf + callback_data.CursorPos); state->CursorFollow = true; } - if (callback_data.SelectionStart != utf8_selection_start || buf_dirty) { state->Stb.select_start = (callback_data.SelectionStart == callback_data.CursorPos) ? state->Stb.cursor : ImTextCountCharsFromUtf8(callback_data.Buf, callback_data.Buf + callback_data.SelectionStart); } - if (callback_data.SelectionEnd != utf8_selection_end || buf_dirty) { state->Stb.select_end = (callback_data.SelectionEnd == callback_data.SelectionStart) ? state->Stb.select_start : ImTextCountCharsFromUtf8(callback_data.Buf, callback_data.Buf + callback_data.SelectionEnd); } - if (buf_dirty) - { - IM_ASSERT((flags & ImGuiInputTextFlags_ReadOnly) == 0); - IM_ASSERT(callback_data.BufTextLen == (int)strlen(callback_data.Buf)); // You need to maintain BufTextLen if you change the text! - InputTextReconcileUndoStateAfterUserCallback(state, callback_data.Buf, callback_data.BufTextLen); // FIXME: Move the rest of this block inside function and rename to InputTextReconcileStateAfterUserCallback() ? - if (callback_data.BufTextLen > backup_current_text_length && is_resizable) - state->TextW.resize(state->TextW.Size + (callback_data.BufTextLen - backup_current_text_length)); // Worse case scenario resize - state->CurLenW = ImTextStrFromUtf8(state->TextW.Data, state->TextW.Size, callback_data.Buf, NULL); - state->CurLenA = callback_data.BufTextLen; // Assume correct length and valid UTF-8 from user, saves us an extra strlen() - state->CursorAnimReset(); - } - } - } - - // Will copy result string if modified - if (!is_readonly && strcmp(state->TextA.Data, buf) != 0) - { - apply_new_text = state->TextA.Data; - apply_new_text_length = state->CurLenA; - value_changed = true; - } - } - } - - // Handle reapplying final data on deactivation (see InputTextDeactivateHook() for details) - if (g.InputTextDeactivatedState.ID == id) - { - if (g.ActiveId != id && IsItemDeactivatedAfterEdit() && !is_readonly && strcmp(g.InputTextDeactivatedState.TextA.Data, buf) != 0) - { - apply_new_text = g.InputTextDeactivatedState.TextA.Data; - apply_new_text_length = g.InputTextDeactivatedState.TextA.Size - 1; - value_changed = true; - //IMGUI_DEBUG_LOG("InputText(): apply Deactivated data for 0x%08X: \"%.*s\".\n", id, apply_new_text_length, apply_new_text); - } - g.InputTextDeactivatedState.ID = 0; - } - - // Copy result to user buffer. This can currently only happen when (g.ActiveId == id) - if (apply_new_text != NULL) - { - // We cannot test for 'backup_current_text_length != apply_new_text_length' here because we have no guarantee that the size - // of our owned buffer matches the size of the string object held by the user, and by design we allow InputText() to be used - // without any storage on user's side. - IM_ASSERT(apply_new_text_length >= 0); - if (is_resizable) - { - ImGuiInputTextCallbackData callback_data; - callback_data.Ctx = &g; - callback_data.EventFlag = ImGuiInputTextFlags_CallbackResize; - callback_data.Flags = flags; - callback_data.Buf = buf; - callback_data.BufTextLen = apply_new_text_length; - callback_data.BufSize = ImMax(buf_size, apply_new_text_length + 1); - callback_data.UserData = callback_user_data; - callback(&callback_data); - buf = callback_data.Buf; - buf_size = callback_data.BufSize; - apply_new_text_length = ImMin(callback_data.BufTextLen, buf_size - 1); - IM_ASSERT(apply_new_text_length <= buf_size); - } - //IMGUI_DEBUG_PRINT("InputText(\"%s\"): apply_new_text length %d\n", label, apply_new_text_length); - - // If the underlying buffer resize was denied or not carried to the next frame, apply_new_text_length+1 may be >= buf_size. - ImStrncpy(buf, apply_new_text, ImMin(apply_new_text_length + 1, buf_size)); - } - - // Release active ID at the end of the function (so e.g. pressing Return still does a final application of the value) - // Otherwise request text input ahead for next frame. - if (g.ActiveId == id && clear_active_id) - ClearActiveID(); - else if (g.ActiveId == id) - g.WantTextInputNextFrame = 1; - - // Render frame - if (!is_multiline) - { - RenderNavHighlight(frame_bb, id); - RenderFrame(frame_bb.Min, frame_bb.Max, GetColorU32(ImGuiCol_FrameBg), true, style.FrameRounding); - } - - const ImVec4 clip_rect(frame_bb.Min.x, frame_bb.Min.y, frame_bb.Min.x + inner_size.x, frame_bb.Min.y + inner_size.y); // Not using frame_bb.Max because we have adjusted size - ImVec2 draw_pos = is_multiline ? draw_window->DC.CursorPos : frame_bb.Min + style.FramePadding; - ImVec2 text_size(0.0f, 0.0f); - - // Set upper limit of single-line InputTextEx() at 2 million characters strings. The current pathological worst case is a long line - // without any carriage return, which would makes ImFont::RenderText() reserve too many vertices and probably crash. Avoid it altogether. - // Note that we only use this limit on single-line InputText(), so a pathologically large line on a InputTextMultiline() would still crash. - const int buf_display_max_length = 2 * 1024 * 1024; - const char* buf_display = buf_display_from_state ? state->TextA.Data : buf; //-V595 - const char* buf_display_end = NULL; // We have specialized paths below for setting the length - if (is_displaying_hint) - { - buf_display = hint; - buf_display_end = hint + strlen(hint); - } - - // Render text. We currently only render selection when the widget is active or while scrolling. - // FIXME: We could remove the '&& render_cursor' to keep rendering selection when inactive. - if (render_cursor || render_selection) - { - IM_ASSERT(state != NULL); - if (!is_displaying_hint) - buf_display_end = buf_display + state->CurLenA; - - // Render text (with cursor and selection) - // This is going to be messy. We need to: - // - Display the text (this alone can be more easily clipped) - // - Handle scrolling, highlight selection, display cursor (those all requires some form of 1d->2d cursor position calculation) - // - Measure text height (for scrollbar) - // We are attempting to do most of that in **one main pass** to minimize the computation cost (non-negligible for large amount of text) + 2nd pass for selection rendering (we could merge them by an extra refactoring effort) - // FIXME: This should occur on buf_display but we'd need to maintain cursor/select_start/select_end for UTF-8. - const ImWchar* text_begin = state->TextW.Data; - ImVec2 cursor_offset, select_start_offset; - - { - // Find lines numbers straddling 'cursor' (slot 0) and 'select_start' (slot 1) positions. - const ImWchar* searches_input_ptr[2] = { NULL, NULL }; - int searches_result_line_no[2] = { -1000, -1000 }; - int searches_remaining = 0; - if (render_cursor) - { - searches_input_ptr[0] = text_begin + state->Stb.cursor; - searches_result_line_no[0] = -1; - searches_remaining++; - } - if (render_selection) - { - searches_input_ptr[1] = text_begin + ImMin(state->Stb.select_start, state->Stb.select_end); - searches_result_line_no[1] = -1; - searches_remaining++; - } - - // Iterate all lines to find our line numbers - // In multi-line mode, we never exit the loop until all lines are counted, so add one extra to the searches_remaining counter. - searches_remaining += is_multiline ? 1 : 0; - int line_count = 0; - //for (const ImWchar* s = text_begin; (s = (const ImWchar*)wcschr((const wchar_t*)s, (wchar_t)'\n')) != NULL; s++) // FIXME-OPT: Could use this when wchar_t are 16-bit - for (const ImWchar* s = text_begin; *s != 0; s++) - if (*s == '\n') - { - line_count++; - if (searches_result_line_no[0] == -1 && s >= searches_input_ptr[0]) { searches_result_line_no[0] = line_count; if (--searches_remaining <= 0) break; } - if (searches_result_line_no[1] == -1 && s >= searches_input_ptr[1]) { searches_result_line_no[1] = line_count; if (--searches_remaining <= 0) break; } - } - line_count++; - if (searches_result_line_no[0] == -1) - searches_result_line_no[0] = line_count; - if (searches_result_line_no[1] == -1) - searches_result_line_no[1] = line_count; - - // Calculate 2d position by finding the beginning of the line and measuring distance - cursor_offset.x = InputTextCalcTextSizeW(&g, ImStrbolW(searches_input_ptr[0], text_begin), searches_input_ptr[0]).x; - cursor_offset.y = searches_result_line_no[0] * g.FontSize; - if (searches_result_line_no[1] >= 0) - { - select_start_offset.x = InputTextCalcTextSizeW(&g, ImStrbolW(searches_input_ptr[1], text_begin), searches_input_ptr[1]).x; - select_start_offset.y = searches_result_line_no[1] * g.FontSize; - } - - // Store text height (note that we haven't calculated text width at all, see GitHub issues #383, #1224) - if (is_multiline) - text_size = ImVec2(inner_size.x, line_count * g.FontSize); - } - - // Scroll - if (render_cursor && state->CursorFollow) - { - // Horizontal scroll in chunks of quarter width - if (!(flags & ImGuiInputTextFlags_NoHorizontalScroll)) - { - const float scroll_increment_x = inner_size.x * 0.25f; - const float visible_width = inner_size.x - style.FramePadding.x; - if (cursor_offset.x < state->ScrollX) - state->ScrollX = IM_TRUNC(ImMax(0.0f, cursor_offset.x - scroll_increment_x)); - else if (cursor_offset.x - visible_width >= state->ScrollX) - state->ScrollX = IM_TRUNC(cursor_offset.x - visible_width + scroll_increment_x); - } - else - { - state->ScrollX = 0.0f; - } - - // Vertical scroll - if (is_multiline) - { - // Test if cursor is vertically visible - if (cursor_offset.y - g.FontSize < scroll_y) - scroll_y = ImMax(0.0f, cursor_offset.y - g.FontSize); - else if (cursor_offset.y - (inner_size.y - style.FramePadding.y * 2.0f) >= scroll_y) - scroll_y = cursor_offset.y - inner_size.y + style.FramePadding.y * 2.0f; - const float scroll_max_y = ImMax((text_size.y + style.FramePadding.y * 2.0f) - inner_size.y, 0.0f); - scroll_y = ImClamp(scroll_y, 0.0f, scroll_max_y); - draw_pos.y += (draw_window->Scroll.y - scroll_y); // Manipulate cursor pos immediately avoid a frame of lag - draw_window->Scroll.y = scroll_y; - } - - state->CursorFollow = false; - } - - // Draw selection - const ImVec2 draw_scroll = ImVec2(state->ScrollX, 0.0f); - if (render_selection) - { - const ImWchar* text_selected_begin = text_begin + ImMin(state->Stb.select_start, state->Stb.select_end); - const ImWchar* text_selected_end = text_begin + ImMax(state->Stb.select_start, state->Stb.select_end); - - ImU32 bg_color = GetColorU32(ImGuiCol_TextSelectedBg, render_cursor ? 1.0f : 0.6f); // FIXME: current code flow mandate that render_cursor is always true here, we are leaving the transparent one for tests. - float bg_offy_up = is_multiline ? 0.0f : -1.0f; // FIXME: those offsets should be part of the style? they don't play so well with multi-line selection. - float bg_offy_dn = is_multiline ? 0.0f : 2.0f; - ImVec2 rect_pos = draw_pos + select_start_offset - draw_scroll; - for (const ImWchar* p = text_selected_begin; p < text_selected_end; ) - { - if (rect_pos.y > clip_rect.w + g.FontSize) - break; - if (rect_pos.y < clip_rect.y) - { - //p = (const ImWchar*)wmemchr((const wchar_t*)p, '\n', text_selected_end - p); // FIXME-OPT: Could use this when wchar_t are 16-bit - //p = p ? p + 1 : text_selected_end; - while (p < text_selected_end) - if (*p++ == '\n') - break; - } - else - { - ImVec2 rect_size = InputTextCalcTextSizeW(&g, p, text_selected_end, &p, NULL, true); - if (rect_size.x <= 0.0f) rect_size.x = IM_TRUNC(g.Font->GetCharAdvance((ImWchar)' ') * 0.50f); // So we can see selected empty lines - ImRect rect(rect_pos + ImVec2(0.0f, bg_offy_up - g.FontSize), rect_pos + ImVec2(rect_size.x, bg_offy_dn)); - rect.ClipWith(clip_rect); - if (rect.Overlaps(clip_rect)) - draw_window->DrawList->AddRectFilled(rect.Min, rect.Max, bg_color); - } - rect_pos.x = draw_pos.x - draw_scroll.x; - rect_pos.y += g.FontSize; - } - } - - // We test for 'buf_display_max_length' as a way to avoid some pathological cases (e.g. single-line 1 MB string) which would make ImDrawList crash. - if (is_multiline || (buf_display_end - buf_display) < buf_display_max_length) - { - ImU32 col = GetColorU32(is_displaying_hint ? ImGuiCol_TextDisabled : ImGuiCol_Text); - draw_window->DrawList->AddText(g.Font, g.FontSize, draw_pos - draw_scroll, col, buf_display, buf_display_end, 0.0f, is_multiline ? NULL : &clip_rect); - } - - // Draw blinking cursor - if (render_cursor) - { - state->CursorAnim += io.DeltaTime; - bool cursor_is_visible = (!g.IO.ConfigInputTextCursorBlink) || (state->CursorAnim <= 0.0f) || ImFmod(state->CursorAnim, 1.20f) <= 0.80f; - ImVec2 cursor_screen_pos = ImTrunc(draw_pos + cursor_offset - draw_scroll); - ImRect cursor_screen_rect(cursor_screen_pos.x, cursor_screen_pos.y - g.FontSize + 0.5f, cursor_screen_pos.x + 1.0f, cursor_screen_pos.y - 1.5f); - if (cursor_is_visible && cursor_screen_rect.Overlaps(clip_rect)) - draw_window->DrawList->AddLine(cursor_screen_rect.Min, cursor_screen_rect.GetBL(), GetColorU32(ImGuiCol_Text)); - - // Notify OS of text input position for advanced IME (-1 x offset so that Windows IME can cover our cursor. Bit of an extra nicety.) - if (!is_readonly) - { - g.PlatformImeData.WantVisible = true; - g.PlatformImeData.InputPos = ImVec2(cursor_screen_pos.x - 1.0f, cursor_screen_pos.y - g.FontSize); - g.PlatformImeData.InputLineHeight = g.FontSize; - g.PlatformImeViewport = window->Viewport->ID; - } - } - } - else - { - // Render text only (no selection, no cursor) - if (is_multiline) - text_size = ImVec2(inner_size.x, InputTextCalcTextLenAndLineCount(buf_display, &buf_display_end) * g.FontSize); // We don't need width - else if (!is_displaying_hint && g.ActiveId == id) - buf_display_end = buf_display + state->CurLenA; - else if (!is_displaying_hint) - buf_display_end = buf_display + strlen(buf_display); - - if (is_multiline || (buf_display_end - buf_display) < buf_display_max_length) - { - ImU32 col = GetColorU32(is_displaying_hint ? ImGuiCol_TextDisabled : ImGuiCol_Text); - draw_window->DrawList->AddText(g.Font, g.FontSize, draw_pos, col, buf_display, buf_display_end, 0.0f, is_multiline ? NULL : &clip_rect); - } - } - - if (is_password && !is_displaying_hint) - PopFont(); - - if (is_multiline) - { - // For focus requests to work on our multiline we need to ensure our child ItemAdd() call specifies the ImGuiItemFlags_Inputable (ref issue #4761)... - Dummy(ImVec2(text_size.x, text_size.y + style.FramePadding.y)); - g.NextItemData.ItemFlags |= ImGuiItemFlags_Inputable | ImGuiItemFlags_NoTabStop; - EndChild(); - item_data_backup.StatusFlags |= (g.LastItemData.StatusFlags & ImGuiItemStatusFlags_HoveredWindow); - - // ...and then we need to undo the group overriding last item data, which gets a bit messy as EndGroup() tries to forward scrollbar being active... - // FIXME: This quite messy/tricky, should attempt to get rid of the child window. - EndGroup(); - if (g.LastItemData.ID == 0) - { - g.LastItemData.ID = id; - g.LastItemData.InFlags = item_data_backup.InFlags; - g.LastItemData.StatusFlags = item_data_backup.StatusFlags; - } - } - - // Log as text - if (g.LogEnabled && (!is_password || is_displaying_hint)) - { - LogSetNextTextDecoration("{", "}"); - LogRenderedText(&draw_pos, buf_display, buf_display_end); - } - - if (label_size.x > 0) - RenderText(ImVec2(frame_bb.Max.x + style.ItemInnerSpacing.x, frame_bb.Min.y + style.FramePadding.y), label); - - if (value_changed && !(flags & ImGuiInputTextFlags_NoMarkEdited)) - MarkItemEdited(id); - - IMGUI_TEST_ENGINE_ITEM_INFO(id, label, g.LastItemData.StatusFlags | ImGuiItemStatusFlags_Inputable); - if ((flags & ImGuiInputTextFlags_EnterReturnsTrue) != 0) - return validated; - else - return value_changed; -} - -void ImGui::DebugNodeInputTextState(ImGuiInputTextState* state) -{ -#ifndef IMGUI_DISABLE_DEBUG_TOOLS - ImGuiContext& g = *GImGui; - ImStb::STB_TexteditState* stb_state = &state->Stb; - ImStb::StbUndoState* undo_state = &stb_state->undostate; - Text("ID: 0x%08X, ActiveID: 0x%08X", state->ID, g.ActiveId); - DebugLocateItemOnHover(state->ID); - Text("CurLenW: %d, CurLenA: %d, Cursor: %d, Selection: %d..%d", state->CurLenW, state->CurLenA, stb_state->cursor, stb_state->select_start, stb_state->select_end); - Text("has_preferred_x: %d (%.2f)", stb_state->has_preferred_x, stb_state->preferred_x); - Text("undo_point: %d, redo_point: %d, undo_char_point: %d, redo_char_point: %d", undo_state->undo_point, undo_state->redo_point, undo_state->undo_char_point, undo_state->redo_char_point); - if (BeginChild("undopoints", ImVec2(0.0f, GetTextLineHeight() * 15), true)) // Visualize undo state - { - PushStyleVar(ImGuiStyleVar_ItemSpacing, ImVec2(0, 0)); - for (int n = 0; n < STB_TEXTEDIT_UNDOSTATECOUNT; n++) - { - ImStb::StbUndoRecord* undo_rec = &undo_state->undo_rec[n]; - const char undo_rec_type = (n < undo_state->undo_point) ? 'u' : (n >= undo_state->redo_point) ? 'r' : ' '; - if (undo_rec_type == ' ') - BeginDisabled(); - char buf[64] = ""; - if (undo_rec_type != ' ' && undo_rec->char_storage != -1) - ImTextStrToUtf8(buf, IM_ARRAYSIZE(buf), undo_state->undo_char + undo_rec->char_storage, undo_state->undo_char + undo_rec->char_storage + undo_rec->insert_length); - Text("%c [%02d] where %03d, insert %03d, delete %03d, char_storage %03d \"%s\"", - undo_rec_type, n, undo_rec->where, undo_rec->insert_length, undo_rec->delete_length, undo_rec->char_storage, buf); - if (undo_rec_type == ' ') - EndDisabled(); - } - PopStyleVar(); - } - EndChild(); -#else - IM_UNUSED(state); -#endif -} - -//------------------------------------------------------------------------- -// [SECTION] Widgets: ColorEdit, ColorPicker, ColorButton, etc. -//------------------------------------------------------------------------- -// - ColorEdit3() -// - ColorEdit4() -// - ColorPicker3() -// - RenderColorRectWithAlphaCheckerboard() [Internal] -// - ColorPicker4() -// - ColorButton() -// - SetColorEditOptions() -// - ColorTooltip() [Internal] -// - ColorEditOptionsPopup() [Internal] -// - ColorPickerOptionsPopup() [Internal] -//------------------------------------------------------------------------- - -bool ImGui::ColorEdit3(const char* label, float col[3], ImGuiColorEditFlags flags) -{ - return ColorEdit4(label, col, flags | ImGuiColorEditFlags_NoAlpha); -} - -static void ColorEditRestoreH(const float* col, float* H) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(g.ColorEditCurrentID != 0); - if (g.ColorEditSavedID != g.ColorEditCurrentID || g.ColorEditSavedColor != ImGui::ColorConvertFloat4ToU32(ImVec4(col[0], col[1], col[2], 0))) - return; - *H = g.ColorEditSavedHue; -} - -// ColorEdit supports RGB and HSV inputs. In case of RGB input resulting color may have undefined hue and/or saturation. -// Since widget displays both RGB and HSV values we must preserve hue and saturation to prevent these values resetting. -static void ColorEditRestoreHS(const float* col, float* H, float* S, float* V) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(g.ColorEditCurrentID != 0); - if (g.ColorEditSavedID != g.ColorEditCurrentID || g.ColorEditSavedColor != ImGui::ColorConvertFloat4ToU32(ImVec4(col[0], col[1], col[2], 0))) - return; - - // When S == 0, H is undefined. - // When H == 1 it wraps around to 0. - if (*S == 0.0f || (*H == 0.0f && g.ColorEditSavedHue == 1)) - *H = g.ColorEditSavedHue; - - // When V == 0, S is undefined. - if (*V == 0.0f) - *S = g.ColorEditSavedSat; -} - -// Edit colors components (each component in 0.0f..1.0f range). -// See enum ImGuiColorEditFlags_ for available options. e.g. Only access 3 floats if ImGuiColorEditFlags_NoAlpha flag is set. -// With typical options: Left-click on color square to open color picker. Right-click to open option menu. CTRL-Click over input fields to edit them and TAB to go to next item. -bool ImGui::ColorEdit4(const char* label, float col[4], ImGuiColorEditFlags flags) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - - ImGuiContext& g = *GImGui; - const ImGuiStyle& style = g.Style; - const float square_sz = GetFrameHeight(); - const float w_full = CalcItemWidth(); - const float w_button = (flags & ImGuiColorEditFlags_NoSmallPreview) ? 0.0f : (square_sz + style.ItemInnerSpacing.x); - const float w_inputs = w_full - w_button; - const char* label_display_end = FindRenderedTextEnd(label); - g.NextItemData.ClearFlags(); - - BeginGroup(); - PushID(label); - const bool set_current_color_edit_id = (g.ColorEditCurrentID == 0); - if (set_current_color_edit_id) - g.ColorEditCurrentID = window->IDStack.back(); - - // If we're not showing any slider there's no point in doing any HSV conversions - const ImGuiColorEditFlags flags_untouched = flags; - if (flags & ImGuiColorEditFlags_NoInputs) - flags = (flags & (~ImGuiColorEditFlags_DisplayMask_)) | ImGuiColorEditFlags_DisplayRGB | ImGuiColorEditFlags_NoOptions; - - // Context menu: display and modify options (before defaults are applied) - if (!(flags & ImGuiColorEditFlags_NoOptions)) - ColorEditOptionsPopup(col, flags); - - // Read stored options - if (!(flags & ImGuiColorEditFlags_DisplayMask_)) - flags |= (g.ColorEditOptions & ImGuiColorEditFlags_DisplayMask_); - if (!(flags & ImGuiColorEditFlags_DataTypeMask_)) - flags |= (g.ColorEditOptions & ImGuiColorEditFlags_DataTypeMask_); - if (!(flags & ImGuiColorEditFlags_PickerMask_)) - flags |= (g.ColorEditOptions & ImGuiColorEditFlags_PickerMask_); - if (!(flags & ImGuiColorEditFlags_InputMask_)) - flags |= (g.ColorEditOptions & ImGuiColorEditFlags_InputMask_); - flags |= (g.ColorEditOptions & ~(ImGuiColorEditFlags_DisplayMask_ | ImGuiColorEditFlags_DataTypeMask_ | ImGuiColorEditFlags_PickerMask_ | ImGuiColorEditFlags_InputMask_)); - IM_ASSERT(ImIsPowerOfTwo(flags & ImGuiColorEditFlags_DisplayMask_)); // Check that only 1 is selected - IM_ASSERT(ImIsPowerOfTwo(flags & ImGuiColorEditFlags_InputMask_)); // Check that only 1 is selected - - const bool alpha = (flags & ImGuiColorEditFlags_NoAlpha) == 0; - const bool hdr = (flags & ImGuiColorEditFlags_HDR) != 0; - const int components = alpha ? 4 : 3; - - // Convert to the formats we need - float f[4] = { col[0], col[1], col[2], alpha ? col[3] : 1.0f }; - if ((flags & ImGuiColorEditFlags_InputHSV) && (flags & ImGuiColorEditFlags_DisplayRGB)) - ColorConvertHSVtoRGB(f[0], f[1], f[2], f[0], f[1], f[2]); - else if ((flags & ImGuiColorEditFlags_InputRGB) && (flags & ImGuiColorEditFlags_DisplayHSV)) - { - // Hue is lost when converting from grayscale rgb (saturation=0). Restore it. - ColorConvertRGBtoHSV(f[0], f[1], f[2], f[0], f[1], f[2]); - ColorEditRestoreHS(col, &f[0], &f[1], &f[2]); - } - int i[4] = { IM_F32_TO_INT8_UNBOUND(f[0]), IM_F32_TO_INT8_UNBOUND(f[1]), IM_F32_TO_INT8_UNBOUND(f[2]), IM_F32_TO_INT8_UNBOUND(f[3]) }; - - bool value_changed = false; - bool value_changed_as_float = false; - - const ImVec2 pos = window->DC.CursorPos; - const float inputs_offset_x = (style.ColorButtonPosition == ImGuiDir_Left) ? w_button : 0.0f; - window->DC.CursorPos.x = pos.x + inputs_offset_x; - - if ((flags & (ImGuiColorEditFlags_DisplayRGB | ImGuiColorEditFlags_DisplayHSV)) != 0 && (flags & ImGuiColorEditFlags_NoInputs) == 0) - { - // RGB/HSV 0..255 Sliders - const float w_item_one = ImMax(1.0f, IM_TRUNC((w_inputs - (style.ItemInnerSpacing.x) * (components - 1)) / (float)components)); - const float w_item_last = ImMax(1.0f, IM_TRUNC(w_inputs - (w_item_one + style.ItemInnerSpacing.x) * (components - 1))); - - const bool hide_prefix = (w_item_one <= CalcTextSize((flags & ImGuiColorEditFlags_Float) ? "M:0.000" : "M:000").x); - static const char* ids[4] = { "##X", "##Y", "##Z", "##W" }; - static const char* fmt_table_int[3][4] = - { - { "%3d", "%3d", "%3d", "%3d" }, // Short display - { "R:%3d", "G:%3d", "B:%3d", "A:%3d" }, // Long display for RGBA - { "H:%3d", "S:%3d", "V:%3d", "A:%3d" } // Long display for HSVA - }; - static const char* fmt_table_float[3][4] = - { - { "%0.3f", "%0.3f", "%0.3f", "%0.3f" }, // Short display - { "R:%0.3f", "G:%0.3f", "B:%0.3f", "A:%0.3f" }, // Long display for RGBA - { "H:%0.3f", "S:%0.3f", "V:%0.3f", "A:%0.3f" } // Long display for HSVA - }; - const int fmt_idx = hide_prefix ? 0 : (flags & ImGuiColorEditFlags_DisplayHSV) ? 2 : 1; - - for (int n = 0; n < components; n++) - { - if (n > 0) - SameLine(0, style.ItemInnerSpacing.x); - SetNextItemWidth((n + 1 < components) ? w_item_one : w_item_last); - - // FIXME: When ImGuiColorEditFlags_HDR flag is passed HS values snap in weird ways when SV values go below 0. - if (flags & ImGuiColorEditFlags_Float) - { - value_changed |= DragFloat(ids[n], &f[n], 1.0f / 255.0f, 0.0f, hdr ? 0.0f : 1.0f, fmt_table_float[fmt_idx][n]); - value_changed_as_float |= value_changed; - } - else - { - value_changed |= DragInt(ids[n], &i[n], 1.0f, 0, hdr ? 0 : 255, fmt_table_int[fmt_idx][n]); - } - if (!(flags & ImGuiColorEditFlags_NoOptions)) - OpenPopupOnItemClick("context", ImGuiPopupFlags_MouseButtonRight); - } - } - else if ((flags & ImGuiColorEditFlags_DisplayHex) != 0 && (flags & ImGuiColorEditFlags_NoInputs) == 0) - { - // RGB Hexadecimal Input - char buf[64]; - if (alpha) - ImFormatString(buf, IM_ARRAYSIZE(buf), "#%02X%02X%02X%02X", ImClamp(i[0], 0, 255), ImClamp(i[1], 0, 255), ImClamp(i[2], 0, 255), ImClamp(i[3], 0, 255)); - else - ImFormatString(buf, IM_ARRAYSIZE(buf), "#%02X%02X%02X", ImClamp(i[0], 0, 255), ImClamp(i[1], 0, 255), ImClamp(i[2], 0, 255)); - SetNextItemWidth(w_inputs); - if (InputText("##Text", buf, IM_ARRAYSIZE(buf), ImGuiInputTextFlags_CharsHexadecimal | ImGuiInputTextFlags_CharsUppercase)) - { - value_changed = true; - char* p = buf; - while (*p == '#' || ImCharIsBlankA(*p)) - p++; - i[0] = i[1] = i[2] = 0; - i[3] = 0xFF; // alpha default to 255 is not parsed by scanf (e.g. inputting #FFFFFF omitting alpha) - int r; - if (alpha) - r = sscanf(p, "%02X%02X%02X%02X", (unsigned int*)&i[0], (unsigned int*)&i[1], (unsigned int*)&i[2], (unsigned int*)&i[3]); // Treat at unsigned (%X is unsigned) - else - r = sscanf(p, "%02X%02X%02X", (unsigned int*)&i[0], (unsigned int*)&i[1], (unsigned int*)&i[2]); - IM_UNUSED(r); // Fixes C6031: Return value ignored: 'sscanf'. - } - if (!(flags & ImGuiColorEditFlags_NoOptions)) - OpenPopupOnItemClick("context", ImGuiPopupFlags_MouseButtonRight); - } - - ImGuiWindow* picker_active_window = NULL; - if (!(flags & ImGuiColorEditFlags_NoSmallPreview)) - { - const float button_offset_x = ((flags & ImGuiColorEditFlags_NoInputs) || (style.ColorButtonPosition == ImGuiDir_Left)) ? 0.0f : w_inputs + style.ItemInnerSpacing.x; - window->DC.CursorPos = ImVec2(pos.x + button_offset_x, pos.y); - - const ImVec4 col_v4(col[0], col[1], col[2], alpha ? col[3] : 1.0f); - if (ColorButton("##ColorButton", col_v4, flags)) - { - if (!(flags & ImGuiColorEditFlags_NoPicker)) - { - // Store current color and open a picker - g.ColorPickerRef = col_v4; - OpenPopup("picker"); - SetNextWindowPos(g.LastItemData.Rect.GetBL() + ImVec2(0.0f, style.ItemSpacing.y)); - } - } - if (!(flags & ImGuiColorEditFlags_NoOptions)) - OpenPopupOnItemClick("context", ImGuiPopupFlags_MouseButtonRight); - - if (BeginPopup("picker")) - { - if (g.CurrentWindow->BeginCount == 1) - { - picker_active_window = g.CurrentWindow; - if (label != label_display_end) - { - TextEx(label, label_display_end); - Spacing(); - } - ImGuiColorEditFlags picker_flags_to_forward = ImGuiColorEditFlags_DataTypeMask_ | ImGuiColorEditFlags_PickerMask_ | ImGuiColorEditFlags_InputMask_ | ImGuiColorEditFlags_HDR | ImGuiColorEditFlags_NoAlpha | ImGuiColorEditFlags_AlphaBar; - ImGuiColorEditFlags picker_flags = (flags_untouched & picker_flags_to_forward) | ImGuiColorEditFlags_DisplayMask_ | ImGuiColorEditFlags_NoLabel | ImGuiColorEditFlags_AlphaPreviewHalf; - SetNextItemWidth(square_sz * 12.0f); // Use 256 + bar sizes? - value_changed |= ColorPicker4("##picker", col, picker_flags, &g.ColorPickerRef.x); - } - EndPopup(); - } - } - - if (label != label_display_end && !(flags & ImGuiColorEditFlags_NoLabel)) - { - // Position not necessarily next to last submitted button (e.g. if style.ColorButtonPosition == ImGuiDir_Left), - // but we need to use SameLine() to setup baseline correctly. Might want to refactor SameLine() to simplify this. - SameLine(0.0f, style.ItemInnerSpacing.x); - window->DC.CursorPos.x = pos.x + ((flags & ImGuiColorEditFlags_NoInputs) ? w_button : w_full + style.ItemInnerSpacing.x); - TextEx(label, label_display_end); - } - - // Convert back - if (value_changed && picker_active_window == NULL) - { - if (!value_changed_as_float) - for (int n = 0; n < 4; n++) - f[n] = i[n] / 255.0f; - if ((flags & ImGuiColorEditFlags_DisplayHSV) && (flags & ImGuiColorEditFlags_InputRGB)) - { - g.ColorEditSavedHue = f[0]; - g.ColorEditSavedSat = f[1]; - ColorConvertHSVtoRGB(f[0], f[1], f[2], f[0], f[1], f[2]); - g.ColorEditSavedID = g.ColorEditCurrentID; - g.ColorEditSavedColor = ColorConvertFloat4ToU32(ImVec4(f[0], f[1], f[2], 0)); - } - if ((flags & ImGuiColorEditFlags_DisplayRGB) && (flags & ImGuiColorEditFlags_InputHSV)) - ColorConvertRGBtoHSV(f[0], f[1], f[2], f[0], f[1], f[2]); - - col[0] = f[0]; - col[1] = f[1]; - col[2] = f[2]; - if (alpha) - col[3] = f[3]; - } - - if (set_current_color_edit_id) - g.ColorEditCurrentID = 0; - PopID(); - EndGroup(); - - // Drag and Drop Target - // NB: The flag test is merely an optional micro-optimization, BeginDragDropTarget() does the same test. - if ((g.LastItemData.StatusFlags & ImGuiItemStatusFlags_HoveredRect) && !(flags & ImGuiColorEditFlags_NoDragDrop) && BeginDragDropTarget()) - { - bool accepted_drag_drop = false; - if (const ImGuiPayload* payload = AcceptDragDropPayload(IMGUI_PAYLOAD_TYPE_COLOR_3F)) - { - memcpy((float*)col, payload->Data, sizeof(float) * 3); // Preserve alpha if any //-V512 //-V1086 - value_changed = accepted_drag_drop = true; - } - if (const ImGuiPayload* payload = AcceptDragDropPayload(IMGUI_PAYLOAD_TYPE_COLOR_4F)) - { - memcpy((float*)col, payload->Data, sizeof(float) * components); - value_changed = accepted_drag_drop = true; - } - - // Drag-drop payloads are always RGB - if (accepted_drag_drop && (flags & ImGuiColorEditFlags_InputHSV)) - ColorConvertRGBtoHSV(col[0], col[1], col[2], col[0], col[1], col[2]); - EndDragDropTarget(); - } - - // When picker is being actively used, use its active id so IsItemActive() will function on ColorEdit4(). - if (picker_active_window && g.ActiveId != 0 && g.ActiveIdWindow == picker_active_window) - g.LastItemData.ID = g.ActiveId; - - if (value_changed && g.LastItemData.ID != 0) // In case of ID collision, the second EndGroup() won't catch g.ActiveId - MarkItemEdited(g.LastItemData.ID); - - return value_changed; -} - -bool ImGui::ColorPicker3(const char* label, float col[3], ImGuiColorEditFlags flags) -{ - float col4[4] = { col[0], col[1], col[2], 1.0f }; - if (!ColorPicker4(label, col4, flags | ImGuiColorEditFlags_NoAlpha)) - return false; - col[0] = col4[0]; col[1] = col4[1]; col[2] = col4[2]; - return true; -} - -// Helper for ColorPicker4() -static void RenderArrowsForVerticalBar(ImDrawList* draw_list, ImVec2 pos, ImVec2 half_sz, float bar_w, float alpha) -{ - ImU32 alpha8 = IM_F32_TO_INT8_SAT(alpha); - ImGui::RenderArrowPointingAt(draw_list, ImVec2(pos.x + half_sz.x + 1, pos.y), ImVec2(half_sz.x + 2, half_sz.y + 1), ImGuiDir_Right, IM_COL32(0,0,0,alpha8)); - ImGui::RenderArrowPointingAt(draw_list, ImVec2(pos.x + half_sz.x, pos.y), half_sz, ImGuiDir_Right, IM_COL32(255,255,255,alpha8)); - ImGui::RenderArrowPointingAt(draw_list, ImVec2(pos.x + bar_w - half_sz.x - 1, pos.y), ImVec2(half_sz.x + 2, half_sz.y + 1), ImGuiDir_Left, IM_COL32(0,0,0,alpha8)); - ImGui::RenderArrowPointingAt(draw_list, ImVec2(pos.x + bar_w - half_sz.x, pos.y), half_sz, ImGuiDir_Left, IM_COL32(255,255,255,alpha8)); -} - -// Note: ColorPicker4() only accesses 3 floats if ImGuiColorEditFlags_NoAlpha flag is set. -// (In C++ the 'float col[4]' notation for a function argument is equivalent to 'float* col', we only specify a size to facilitate understanding of the code.) -// FIXME: we adjust the big color square height based on item width, which may cause a flickering feedback loop (if automatic height makes a vertical scrollbar appears, affecting automatic width..) -// FIXME: this is trying to be aware of style.Alpha but not fully correct. Also, the color wheel will have overlapping glitches with (style.Alpha < 1.0) -bool ImGui::ColorPicker4(const char* label, float col[4], ImGuiColorEditFlags flags, const float* ref_col) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - - ImDrawList* draw_list = window->DrawList; - ImGuiStyle& style = g.Style; - ImGuiIO& io = g.IO; - - const float width = CalcItemWidth(); - g.NextItemData.ClearFlags(); - - PushID(label); - const bool set_current_color_edit_id = (g.ColorEditCurrentID == 0); - if (set_current_color_edit_id) - g.ColorEditCurrentID = window->IDStack.back(); - BeginGroup(); - - if (!(flags & ImGuiColorEditFlags_NoSidePreview)) - flags |= ImGuiColorEditFlags_NoSmallPreview; - - // Context menu: display and store options. - if (!(flags & ImGuiColorEditFlags_NoOptions)) - ColorPickerOptionsPopup(col, flags); - - // Read stored options - if (!(flags & ImGuiColorEditFlags_PickerMask_)) - flags |= ((g.ColorEditOptions & ImGuiColorEditFlags_PickerMask_) ? g.ColorEditOptions : ImGuiColorEditFlags_DefaultOptions_) & ImGuiColorEditFlags_PickerMask_; - if (!(flags & ImGuiColorEditFlags_InputMask_)) - flags |= ((g.ColorEditOptions & ImGuiColorEditFlags_InputMask_) ? g.ColorEditOptions : ImGuiColorEditFlags_DefaultOptions_) & ImGuiColorEditFlags_InputMask_; - IM_ASSERT(ImIsPowerOfTwo(flags & ImGuiColorEditFlags_PickerMask_)); // Check that only 1 is selected - IM_ASSERT(ImIsPowerOfTwo(flags & ImGuiColorEditFlags_InputMask_)); // Check that only 1 is selected - if (!(flags & ImGuiColorEditFlags_NoOptions)) - flags |= (g.ColorEditOptions & ImGuiColorEditFlags_AlphaBar); - - // Setup - int components = (flags & ImGuiColorEditFlags_NoAlpha) ? 3 : 4; - bool alpha_bar = (flags & ImGuiColorEditFlags_AlphaBar) && !(flags & ImGuiColorEditFlags_NoAlpha); - ImVec2 picker_pos = window->DC.CursorPos; - float square_sz = GetFrameHeight(); - float bars_width = square_sz; // Arbitrary smallish width of Hue/Alpha picking bars - float sv_picker_size = ImMax(bars_width * 1, width - (alpha_bar ? 2 : 1) * (bars_width + style.ItemInnerSpacing.x)); // Saturation/Value picking box - float bar0_pos_x = picker_pos.x + sv_picker_size + style.ItemInnerSpacing.x; - float bar1_pos_x = bar0_pos_x + bars_width + style.ItemInnerSpacing.x; - float bars_triangles_half_sz = IM_TRUNC(bars_width * 0.20f); - - float backup_initial_col[4]; - memcpy(backup_initial_col, col, components * sizeof(float)); - - float wheel_thickness = sv_picker_size * 0.08f; - float wheel_r_outer = sv_picker_size * 0.50f; - float wheel_r_inner = wheel_r_outer - wheel_thickness; - ImVec2 wheel_center(picker_pos.x + (sv_picker_size + bars_width)*0.5f, picker_pos.y + sv_picker_size * 0.5f); - - // Note: the triangle is displayed rotated with triangle_pa pointing to Hue, but most coordinates stays unrotated for logic. - float triangle_r = wheel_r_inner - (int)(sv_picker_size * 0.027f); - ImVec2 triangle_pa = ImVec2(triangle_r, 0.0f); // Hue point. - ImVec2 triangle_pb = ImVec2(triangle_r * -0.5f, triangle_r * -0.866025f); // Black point. - ImVec2 triangle_pc = ImVec2(triangle_r * -0.5f, triangle_r * +0.866025f); // White point. - - float H = col[0], S = col[1], V = col[2]; - float R = col[0], G = col[1], B = col[2]; - if (flags & ImGuiColorEditFlags_InputRGB) - { - // Hue is lost when converting from grayscale rgb (saturation=0). Restore it. - ColorConvertRGBtoHSV(R, G, B, H, S, V); - ColorEditRestoreHS(col, &H, &S, &V); - } - else if (flags & ImGuiColorEditFlags_InputHSV) - { - ColorConvertHSVtoRGB(H, S, V, R, G, B); - } - - bool value_changed = false, value_changed_h = false, value_changed_sv = false; - - PushItemFlag(ImGuiItemFlags_NoNav, true); - if (flags & ImGuiColorEditFlags_PickerHueWheel) - { - // Hue wheel + SV triangle logic - InvisibleButton("hsv", ImVec2(sv_picker_size + style.ItemInnerSpacing.x + bars_width, sv_picker_size)); - if (IsItemActive()) - { - ImVec2 initial_off = g.IO.MouseClickedPos[0] - wheel_center; - ImVec2 current_off = g.IO.MousePos - wheel_center; - float initial_dist2 = ImLengthSqr(initial_off); - if (initial_dist2 >= (wheel_r_inner - 1) * (wheel_r_inner - 1) && initial_dist2 <= (wheel_r_outer + 1) * (wheel_r_outer + 1)) - { - // Interactive with Hue wheel - H = ImAtan2(current_off.y, current_off.x) / IM_PI * 0.5f; - if (H < 0.0f) - H += 1.0f; - value_changed = value_changed_h = true; - } - float cos_hue_angle = ImCos(-H * 2.0f * IM_PI); - float sin_hue_angle = ImSin(-H * 2.0f * IM_PI); - if (ImTriangleContainsPoint(triangle_pa, triangle_pb, triangle_pc, ImRotate(initial_off, cos_hue_angle, sin_hue_angle))) - { - // Interacting with SV triangle - ImVec2 current_off_unrotated = ImRotate(current_off, cos_hue_angle, sin_hue_angle); - if (!ImTriangleContainsPoint(triangle_pa, triangle_pb, triangle_pc, current_off_unrotated)) - current_off_unrotated = ImTriangleClosestPoint(triangle_pa, triangle_pb, triangle_pc, current_off_unrotated); - float uu, vv, ww; - ImTriangleBarycentricCoords(triangle_pa, triangle_pb, triangle_pc, current_off_unrotated, uu, vv, ww); - V = ImClamp(1.0f - vv, 0.0001f, 1.0f); - S = ImClamp(uu / V, 0.0001f, 1.0f); - value_changed = value_changed_sv = true; - } - } - if (!(flags & ImGuiColorEditFlags_NoOptions)) - OpenPopupOnItemClick("context", ImGuiPopupFlags_MouseButtonRight); - } - else if (flags & ImGuiColorEditFlags_PickerHueBar) - { - // SV rectangle logic - InvisibleButton("sv", ImVec2(sv_picker_size, sv_picker_size)); - if (IsItemActive()) - { - S = ImSaturate((io.MousePos.x - picker_pos.x) / (sv_picker_size - 1)); - V = 1.0f - ImSaturate((io.MousePos.y - picker_pos.y) / (sv_picker_size - 1)); - ColorEditRestoreH(col, &H); // Greatly reduces hue jitter and reset to 0 when hue == 255 and color is rapidly modified using SV square. - value_changed = value_changed_sv = true; - } - if (!(flags & ImGuiColorEditFlags_NoOptions)) - OpenPopupOnItemClick("context", ImGuiPopupFlags_MouseButtonRight); - - // Hue bar logic - SetCursorScreenPos(ImVec2(bar0_pos_x, picker_pos.y)); - InvisibleButton("hue", ImVec2(bars_width, sv_picker_size)); - if (IsItemActive()) - { - H = ImSaturate((io.MousePos.y - picker_pos.y) / (sv_picker_size - 1)); - value_changed = value_changed_h = true; - } - } - - // Alpha bar logic - if (alpha_bar) - { - SetCursorScreenPos(ImVec2(bar1_pos_x, picker_pos.y)); - InvisibleButton("alpha", ImVec2(bars_width, sv_picker_size)); - if (IsItemActive()) - { - col[3] = 1.0f - ImSaturate((io.MousePos.y - picker_pos.y) / (sv_picker_size - 1)); - value_changed = true; - } - } - PopItemFlag(); // ImGuiItemFlags_NoNav - - if (!(flags & ImGuiColorEditFlags_NoSidePreview)) - { - SameLine(0, style.ItemInnerSpacing.x); - BeginGroup(); - } - - if (!(flags & ImGuiColorEditFlags_NoLabel)) - { - const char* label_display_end = FindRenderedTextEnd(label); - if (label != label_display_end) - { - if ((flags & ImGuiColorEditFlags_NoSidePreview)) - SameLine(0, style.ItemInnerSpacing.x); - TextEx(label, label_display_end); - } - } - - if (!(flags & ImGuiColorEditFlags_NoSidePreview)) - { - PushItemFlag(ImGuiItemFlags_NoNavDefaultFocus, true); - ImVec4 col_v4(col[0], col[1], col[2], (flags & ImGuiColorEditFlags_NoAlpha) ? 1.0f : col[3]); - if ((flags & ImGuiColorEditFlags_NoLabel)) - Text("Current"); - - ImGuiColorEditFlags sub_flags_to_forward = ImGuiColorEditFlags_InputMask_ | ImGuiColorEditFlags_HDR | ImGuiColorEditFlags_AlphaPreview | ImGuiColorEditFlags_AlphaPreviewHalf | ImGuiColorEditFlags_NoTooltip; - ColorButton("##current", col_v4, (flags & sub_flags_to_forward), ImVec2(square_sz * 3, square_sz * 2)); - if (ref_col != NULL) - { - Text("Original"); - ImVec4 ref_col_v4(ref_col[0], ref_col[1], ref_col[2], (flags & ImGuiColorEditFlags_NoAlpha) ? 1.0f : ref_col[3]); - if (ColorButton("##original", ref_col_v4, (flags & sub_flags_to_forward), ImVec2(square_sz * 3, square_sz * 2))) - { - memcpy(col, ref_col, components * sizeof(float)); - value_changed = true; - } - } - PopItemFlag(); - EndGroup(); - } - - // Convert back color to RGB - if (value_changed_h || value_changed_sv) - { - if (flags & ImGuiColorEditFlags_InputRGB) - { - ColorConvertHSVtoRGB(H, S, V, col[0], col[1], col[2]); - g.ColorEditSavedHue = H; - g.ColorEditSavedSat = S; - g.ColorEditSavedID = g.ColorEditCurrentID; - g.ColorEditSavedColor = ColorConvertFloat4ToU32(ImVec4(col[0], col[1], col[2], 0)); - } - else if (flags & ImGuiColorEditFlags_InputHSV) - { - col[0] = H; - col[1] = S; - col[2] = V; - } - } - - // R,G,B and H,S,V slider color editor - bool value_changed_fix_hue_wrap = false; - if ((flags & ImGuiColorEditFlags_NoInputs) == 0) - { - PushItemWidth((alpha_bar ? bar1_pos_x : bar0_pos_x) + bars_width - picker_pos.x); - ImGuiColorEditFlags sub_flags_to_forward = ImGuiColorEditFlags_DataTypeMask_ | ImGuiColorEditFlags_InputMask_ | ImGuiColorEditFlags_HDR | ImGuiColorEditFlags_NoAlpha | ImGuiColorEditFlags_NoOptions | ImGuiColorEditFlags_NoSmallPreview | ImGuiColorEditFlags_AlphaPreview | ImGuiColorEditFlags_AlphaPreviewHalf; - ImGuiColorEditFlags sub_flags = (flags & sub_flags_to_forward) | ImGuiColorEditFlags_NoPicker; - if (flags & ImGuiColorEditFlags_DisplayRGB || (flags & ImGuiColorEditFlags_DisplayMask_) == 0) - if (ColorEdit4("##rgb", col, sub_flags | ImGuiColorEditFlags_DisplayRGB)) - { - // FIXME: Hackily differentiating using the DragInt (ActiveId != 0 && !ActiveIdAllowOverlap) vs. using the InputText or DropTarget. - // For the later we don't want to run the hue-wrap canceling code. If you are well versed in HSV picker please provide your input! (See #2050) - value_changed_fix_hue_wrap = (g.ActiveId != 0 && !g.ActiveIdAllowOverlap); - value_changed = true; - } - if (flags & ImGuiColorEditFlags_DisplayHSV || (flags & ImGuiColorEditFlags_DisplayMask_) == 0) - value_changed |= ColorEdit4("##hsv", col, sub_flags | ImGuiColorEditFlags_DisplayHSV); - if (flags & ImGuiColorEditFlags_DisplayHex || (flags & ImGuiColorEditFlags_DisplayMask_) == 0) - value_changed |= ColorEdit4("##hex", col, sub_flags | ImGuiColorEditFlags_DisplayHex); - PopItemWidth(); - } - - // Try to cancel hue wrap (after ColorEdit4 call), if any - if (value_changed_fix_hue_wrap && (flags & ImGuiColorEditFlags_InputRGB)) - { - float new_H, new_S, new_V; - ColorConvertRGBtoHSV(col[0], col[1], col[2], new_H, new_S, new_V); - if (new_H <= 0 && H > 0) - { - if (new_V <= 0 && V != new_V) - ColorConvertHSVtoRGB(H, S, new_V <= 0 ? V * 0.5f : new_V, col[0], col[1], col[2]); - else if (new_S <= 0) - ColorConvertHSVtoRGB(H, new_S <= 0 ? S * 0.5f : new_S, new_V, col[0], col[1], col[2]); - } - } - - if (value_changed) - { - if (flags & ImGuiColorEditFlags_InputRGB) - { - R = col[0]; - G = col[1]; - B = col[2]; - ColorConvertRGBtoHSV(R, G, B, H, S, V); - ColorEditRestoreHS(col, &H, &S, &V); // Fix local Hue as display below will use it immediately. - } - else if (flags & ImGuiColorEditFlags_InputHSV) - { - H = col[0]; - S = col[1]; - V = col[2]; - ColorConvertHSVtoRGB(H, S, V, R, G, B); - } - } - - const int style_alpha8 = IM_F32_TO_INT8_SAT(style.Alpha); - const ImU32 col_black = IM_COL32(0,0,0,style_alpha8); - const ImU32 col_white = IM_COL32(255,255,255,style_alpha8); - const ImU32 col_midgrey = IM_COL32(128,128,128,style_alpha8); - const ImU32 col_hues[6 + 1] = { IM_COL32(255,0,0,style_alpha8), IM_COL32(255,255,0,style_alpha8), IM_COL32(0,255,0,style_alpha8), IM_COL32(0,255,255,style_alpha8), IM_COL32(0,0,255,style_alpha8), IM_COL32(255,0,255,style_alpha8), IM_COL32(255,0,0,style_alpha8) }; - - ImVec4 hue_color_f(1, 1, 1, style.Alpha); ColorConvertHSVtoRGB(H, 1, 1, hue_color_f.x, hue_color_f.y, hue_color_f.z); - ImU32 hue_color32 = ColorConvertFloat4ToU32(hue_color_f); - ImU32 user_col32_striped_of_alpha = ColorConvertFloat4ToU32(ImVec4(R, G, B, style.Alpha)); // Important: this is still including the main rendering/style alpha!! - - ImVec2 sv_cursor_pos; - - if (flags & ImGuiColorEditFlags_PickerHueWheel) - { - // Render Hue Wheel - const float aeps = 0.5f / wheel_r_outer; // Half a pixel arc length in radians (2pi cancels out). - const int segment_per_arc = ImMax(4, (int)wheel_r_outer / 12); - for (int n = 0; n < 6; n++) - { - const float a0 = (n) /6.0f * 2.0f * IM_PI - aeps; - const float a1 = (n+1.0f)/6.0f * 2.0f * IM_PI + aeps; - const int vert_start_idx = draw_list->VtxBuffer.Size; - draw_list->PathArcTo(wheel_center, (wheel_r_inner + wheel_r_outer)*0.5f, a0, a1, segment_per_arc); - draw_list->PathStroke(col_white, 0, wheel_thickness); - const int vert_end_idx = draw_list->VtxBuffer.Size; - - // Paint colors over existing vertices - ImVec2 gradient_p0(wheel_center.x + ImCos(a0) * wheel_r_inner, wheel_center.y + ImSin(a0) * wheel_r_inner); - ImVec2 gradient_p1(wheel_center.x + ImCos(a1) * wheel_r_inner, wheel_center.y + ImSin(a1) * wheel_r_inner); - ShadeVertsLinearColorGradientKeepAlpha(draw_list, vert_start_idx, vert_end_idx, gradient_p0, gradient_p1, col_hues[n], col_hues[n + 1]); - } - - // Render Cursor + preview on Hue Wheel - float cos_hue_angle = ImCos(H * 2.0f * IM_PI); - float sin_hue_angle = ImSin(H * 2.0f * IM_PI); - ImVec2 hue_cursor_pos(wheel_center.x + cos_hue_angle * (wheel_r_inner + wheel_r_outer) * 0.5f, wheel_center.y + sin_hue_angle * (wheel_r_inner + wheel_r_outer) * 0.5f); - float hue_cursor_rad = value_changed_h ? wheel_thickness * 0.65f : wheel_thickness * 0.55f; - int hue_cursor_segments = draw_list->_CalcCircleAutoSegmentCount(hue_cursor_rad); // Lock segment count so the +1 one matches others. - draw_list->AddCircleFilled(hue_cursor_pos, hue_cursor_rad, hue_color32, hue_cursor_segments); - draw_list->AddCircle(hue_cursor_pos, hue_cursor_rad + 1, col_midgrey, hue_cursor_segments); - draw_list->AddCircle(hue_cursor_pos, hue_cursor_rad, col_white, hue_cursor_segments); - - // Render SV triangle (rotated according to hue) - ImVec2 tra = wheel_center + ImRotate(triangle_pa, cos_hue_angle, sin_hue_angle); - ImVec2 trb = wheel_center + ImRotate(triangle_pb, cos_hue_angle, sin_hue_angle); - ImVec2 trc = wheel_center + ImRotate(triangle_pc, cos_hue_angle, sin_hue_angle); - ImVec2 uv_white = GetFontTexUvWhitePixel(); - draw_list->PrimReserve(3, 3); - draw_list->PrimVtx(tra, uv_white, hue_color32); - draw_list->PrimVtx(trb, uv_white, col_black); - draw_list->PrimVtx(trc, uv_white, col_white); - draw_list->AddTriangle(tra, trb, trc, col_midgrey, 1.5f); - sv_cursor_pos = ImLerp(ImLerp(trc, tra, ImSaturate(S)), trb, ImSaturate(1 - V)); - } - else if (flags & ImGuiColorEditFlags_PickerHueBar) - { - // Render SV Square - draw_list->AddRectFilledMultiColor(picker_pos, picker_pos + ImVec2(sv_picker_size, sv_picker_size), col_white, hue_color32, hue_color32, col_white); - draw_list->AddRectFilledMultiColor(picker_pos, picker_pos + ImVec2(sv_picker_size, sv_picker_size), 0, 0, col_black, col_black); - RenderFrameBorder(picker_pos, picker_pos + ImVec2(sv_picker_size, sv_picker_size), 0.0f); - sv_cursor_pos.x = ImClamp(IM_ROUND(picker_pos.x + ImSaturate(S) * sv_picker_size), picker_pos.x + 2, picker_pos.x + sv_picker_size - 2); // Sneakily prevent the circle to stick out too much - sv_cursor_pos.y = ImClamp(IM_ROUND(picker_pos.y + ImSaturate(1 - V) * sv_picker_size), picker_pos.y + 2, picker_pos.y + sv_picker_size - 2); - - // Render Hue Bar - for (int i = 0; i < 6; ++i) - draw_list->AddRectFilledMultiColor(ImVec2(bar0_pos_x, picker_pos.y + i * (sv_picker_size / 6)), ImVec2(bar0_pos_x + bars_width, picker_pos.y + (i + 1) * (sv_picker_size / 6)), col_hues[i], col_hues[i], col_hues[i + 1], col_hues[i + 1]); - float bar0_line_y = IM_ROUND(picker_pos.y + H * sv_picker_size); - RenderFrameBorder(ImVec2(bar0_pos_x, picker_pos.y), ImVec2(bar0_pos_x + bars_width, picker_pos.y + sv_picker_size), 0.0f); - RenderArrowsForVerticalBar(draw_list, ImVec2(bar0_pos_x - 1, bar0_line_y), ImVec2(bars_triangles_half_sz + 1, bars_triangles_half_sz), bars_width + 2.0f, style.Alpha); - } - - // Render cursor/preview circle (clamp S/V within 0..1 range because floating points colors may lead HSV values to be out of range) - float sv_cursor_rad = value_changed_sv ? 10.0f : 6.0f; - int sv_cursor_segments = draw_list->_CalcCircleAutoSegmentCount(sv_cursor_rad); // Lock segment count so the +1 one matches others. - draw_list->AddCircleFilled(sv_cursor_pos, sv_cursor_rad, user_col32_striped_of_alpha, sv_cursor_segments); - draw_list->AddCircle(sv_cursor_pos, sv_cursor_rad + 1, col_midgrey, sv_cursor_segments); - draw_list->AddCircle(sv_cursor_pos, sv_cursor_rad, col_white, sv_cursor_segments); - - // Render alpha bar - if (alpha_bar) - { - float alpha = ImSaturate(col[3]); - ImRect bar1_bb(bar1_pos_x, picker_pos.y, bar1_pos_x + bars_width, picker_pos.y + sv_picker_size); - RenderColorRectWithAlphaCheckerboard(draw_list, bar1_bb.Min, bar1_bb.Max, 0, bar1_bb.GetWidth() / 2.0f, ImVec2(0.0f, 0.0f)); - draw_list->AddRectFilledMultiColor(bar1_bb.Min, bar1_bb.Max, user_col32_striped_of_alpha, user_col32_striped_of_alpha, user_col32_striped_of_alpha & ~IM_COL32_A_MASK, user_col32_striped_of_alpha & ~IM_COL32_A_MASK); - float bar1_line_y = IM_ROUND(picker_pos.y + (1.0f - alpha) * sv_picker_size); - RenderFrameBorder(bar1_bb.Min, bar1_bb.Max, 0.0f); - RenderArrowsForVerticalBar(draw_list, ImVec2(bar1_pos_x - 1, bar1_line_y), ImVec2(bars_triangles_half_sz + 1, bars_triangles_half_sz), bars_width + 2.0f, style.Alpha); - } - - EndGroup(); - - if (value_changed && memcmp(backup_initial_col, col, components * sizeof(float)) == 0) - value_changed = false; - if (value_changed && g.LastItemData.ID != 0) // In case of ID collision, the second EndGroup() won't catch g.ActiveId - MarkItemEdited(g.LastItemData.ID); - - if (set_current_color_edit_id) - g.ColorEditCurrentID = 0; - PopID(); - - return value_changed; -} - -// A little color square. Return true when clicked. -// FIXME: May want to display/ignore the alpha component in the color display? Yet show it in the tooltip. -// 'desc_id' is not called 'label' because we don't display it next to the button, but only in the tooltip. -// Note that 'col' may be encoded in HSV if ImGuiColorEditFlags_InputHSV is set. -bool ImGui::ColorButton(const char* desc_id, const ImVec4& col, ImGuiColorEditFlags flags, const ImVec2& size_arg) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - - ImGuiContext& g = *GImGui; - const ImGuiID id = window->GetID(desc_id); - const float default_size = GetFrameHeight(); - const ImVec2 size(size_arg.x == 0.0f ? default_size : size_arg.x, size_arg.y == 0.0f ? default_size : size_arg.y); - const ImRect bb(window->DC.CursorPos, window->DC.CursorPos + size); - ItemSize(bb, (size.y >= default_size) ? g.Style.FramePadding.y : 0.0f); - if (!ItemAdd(bb, id)) - return false; - - bool hovered, held; - bool pressed = ButtonBehavior(bb, id, &hovered, &held); - - if (flags & ImGuiColorEditFlags_NoAlpha) - flags &= ~(ImGuiColorEditFlags_AlphaPreview | ImGuiColorEditFlags_AlphaPreviewHalf); - - ImVec4 col_rgb = col; - if (flags & ImGuiColorEditFlags_InputHSV) - ColorConvertHSVtoRGB(col_rgb.x, col_rgb.y, col_rgb.z, col_rgb.x, col_rgb.y, col_rgb.z); - - ImVec4 col_rgb_without_alpha(col_rgb.x, col_rgb.y, col_rgb.z, 1.0f); - float grid_step = ImMin(size.x, size.y) / 2.99f; - float rounding = ImMin(g.Style.FrameRounding, grid_step * 0.5f); - ImRect bb_inner = bb; - float off = 0.0f; - if ((flags & ImGuiColorEditFlags_NoBorder) == 0) - { - off = -0.75f; // The border (using Col_FrameBg) tends to look off when color is near-opaque and rounding is enabled. This offset seemed like a good middle ground to reduce those artifacts. - bb_inner.Expand(off); - } - if ((flags & ImGuiColorEditFlags_AlphaPreviewHalf) && col_rgb.w < 1.0f) - { - float mid_x = IM_ROUND((bb_inner.Min.x + bb_inner.Max.x) * 0.5f); - RenderColorRectWithAlphaCheckerboard(window->DrawList, ImVec2(bb_inner.Min.x + grid_step, bb_inner.Min.y), bb_inner.Max, GetColorU32(col_rgb), grid_step, ImVec2(-grid_step + off, off), rounding, ImDrawFlags_RoundCornersRight); - window->DrawList->AddRectFilled(bb_inner.Min, ImVec2(mid_x, bb_inner.Max.y), GetColorU32(col_rgb_without_alpha), rounding, ImDrawFlags_RoundCornersLeft); - } - else - { - // Because GetColorU32() multiplies by the global style Alpha and we don't want to display a checkerboard if the source code had no alpha - ImVec4 col_source = (flags & ImGuiColorEditFlags_AlphaPreview) ? col_rgb : col_rgb_without_alpha; - if (col_source.w < 1.0f) - RenderColorRectWithAlphaCheckerboard(window->DrawList, bb_inner.Min, bb_inner.Max, GetColorU32(col_source), grid_step, ImVec2(off, off), rounding); - else - window->DrawList->AddRectFilled(bb_inner.Min, bb_inner.Max, GetColorU32(col_source), rounding); - } - RenderNavHighlight(bb, id); - if ((flags & ImGuiColorEditFlags_NoBorder) == 0) - { - if (g.Style.FrameBorderSize > 0.0f) - RenderFrameBorder(bb.Min, bb.Max, rounding); - else - window->DrawList->AddRect(bb.Min, bb.Max, GetColorU32(ImGuiCol_FrameBg), rounding); // Color button are often in need of some sort of border - } - - // Drag and Drop Source - // NB: The ActiveId test is merely an optional micro-optimization, BeginDragDropSource() does the same test. - if (g.ActiveId == id && !(flags & ImGuiColorEditFlags_NoDragDrop) && BeginDragDropSource()) - { - if (flags & ImGuiColorEditFlags_NoAlpha) - SetDragDropPayload(IMGUI_PAYLOAD_TYPE_COLOR_3F, &col_rgb, sizeof(float) * 3, ImGuiCond_Once); - else - SetDragDropPayload(IMGUI_PAYLOAD_TYPE_COLOR_4F, &col_rgb, sizeof(float) * 4, ImGuiCond_Once); - ColorButton(desc_id, col, flags); - SameLine(); - TextEx("Color"); - EndDragDropSource(); - } - - // Tooltip - if (!(flags & ImGuiColorEditFlags_NoTooltip) && hovered && IsItemHovered(ImGuiHoveredFlags_ForTooltip)) - ColorTooltip(desc_id, &col.x, flags & (ImGuiColorEditFlags_InputMask_ | ImGuiColorEditFlags_NoAlpha | ImGuiColorEditFlags_AlphaPreview | ImGuiColorEditFlags_AlphaPreviewHalf)); - - return pressed; -} - -// Initialize/override default color options -void ImGui::SetColorEditOptions(ImGuiColorEditFlags flags) -{ - ImGuiContext& g = *GImGui; - if ((flags & ImGuiColorEditFlags_DisplayMask_) == 0) - flags |= ImGuiColorEditFlags_DefaultOptions_ & ImGuiColorEditFlags_DisplayMask_; - if ((flags & ImGuiColorEditFlags_DataTypeMask_) == 0) - flags |= ImGuiColorEditFlags_DefaultOptions_ & ImGuiColorEditFlags_DataTypeMask_; - if ((flags & ImGuiColorEditFlags_PickerMask_) == 0) - flags |= ImGuiColorEditFlags_DefaultOptions_ & ImGuiColorEditFlags_PickerMask_; - if ((flags & ImGuiColorEditFlags_InputMask_) == 0) - flags |= ImGuiColorEditFlags_DefaultOptions_ & ImGuiColorEditFlags_InputMask_; - IM_ASSERT(ImIsPowerOfTwo(flags & ImGuiColorEditFlags_DisplayMask_)); // Check only 1 option is selected - IM_ASSERT(ImIsPowerOfTwo(flags & ImGuiColorEditFlags_DataTypeMask_)); // Check only 1 option is selected - IM_ASSERT(ImIsPowerOfTwo(flags & ImGuiColorEditFlags_PickerMask_)); // Check only 1 option is selected - IM_ASSERT(ImIsPowerOfTwo(flags & ImGuiColorEditFlags_InputMask_)); // Check only 1 option is selected - g.ColorEditOptions = flags; -} - -// Note: only access 3 floats if ImGuiColorEditFlags_NoAlpha flag is set. -void ImGui::ColorTooltip(const char* text, const float* col, ImGuiColorEditFlags flags) -{ - ImGuiContext& g = *GImGui; - - if (!BeginTooltipEx(ImGuiTooltipFlags_OverridePrevious, ImGuiWindowFlags_None)) - return; - const char* text_end = text ? FindRenderedTextEnd(text, NULL) : text; - if (text_end > text) - { - TextEx(text, text_end); - Separator(); - } - - ImVec2 sz(g.FontSize * 3 + g.Style.FramePadding.y * 2, g.FontSize * 3 + g.Style.FramePadding.y * 2); - ImVec4 cf(col[0], col[1], col[2], (flags & ImGuiColorEditFlags_NoAlpha) ? 1.0f : col[3]); - int cr = IM_F32_TO_INT8_SAT(col[0]), cg = IM_F32_TO_INT8_SAT(col[1]), cb = IM_F32_TO_INT8_SAT(col[2]), ca = (flags & ImGuiColorEditFlags_NoAlpha) ? 255 : IM_F32_TO_INT8_SAT(col[3]); - ColorButton("##preview", cf, (flags & (ImGuiColorEditFlags_InputMask_ | ImGuiColorEditFlags_NoAlpha | ImGuiColorEditFlags_AlphaPreview | ImGuiColorEditFlags_AlphaPreviewHalf)) | ImGuiColorEditFlags_NoTooltip, sz); - SameLine(); - if ((flags & ImGuiColorEditFlags_InputRGB) || !(flags & ImGuiColorEditFlags_InputMask_)) - { - if (flags & ImGuiColorEditFlags_NoAlpha) - Text("#%02X%02X%02X\nR: %d, G: %d, B: %d\n(%.3f, %.3f, %.3f)", cr, cg, cb, cr, cg, cb, col[0], col[1], col[2]); - else - Text("#%02X%02X%02X%02X\nR:%d, G:%d, B:%d, A:%d\n(%.3f, %.3f, %.3f, %.3f)", cr, cg, cb, ca, cr, cg, cb, ca, col[0], col[1], col[2], col[3]); - } - else if (flags & ImGuiColorEditFlags_InputHSV) - { - if (flags & ImGuiColorEditFlags_NoAlpha) - Text("H: %.3f, S: %.3f, V: %.3f", col[0], col[1], col[2]); - else - Text("H: %.3f, S: %.3f, V: %.3f, A: %.3f", col[0], col[1], col[2], col[3]); - } - EndTooltip(); -} - -void ImGui::ColorEditOptionsPopup(const float* col, ImGuiColorEditFlags flags) -{ - bool allow_opt_inputs = !(flags & ImGuiColorEditFlags_DisplayMask_); - bool allow_opt_datatype = !(flags & ImGuiColorEditFlags_DataTypeMask_); - if ((!allow_opt_inputs && !allow_opt_datatype) || !BeginPopup("context")) - return; - ImGuiContext& g = *GImGui; - g.LockMarkEdited++; - ImGuiColorEditFlags opts = g.ColorEditOptions; - if (allow_opt_inputs) - { - if (RadioButton("RGB", (opts & ImGuiColorEditFlags_DisplayRGB) != 0)) opts = (opts & ~ImGuiColorEditFlags_DisplayMask_) | ImGuiColorEditFlags_DisplayRGB; - if (RadioButton("HSV", (opts & ImGuiColorEditFlags_DisplayHSV) != 0)) opts = (opts & ~ImGuiColorEditFlags_DisplayMask_) | ImGuiColorEditFlags_DisplayHSV; - if (RadioButton("Hex", (opts & ImGuiColorEditFlags_DisplayHex) != 0)) opts = (opts & ~ImGuiColorEditFlags_DisplayMask_) | ImGuiColorEditFlags_DisplayHex; - } - if (allow_opt_datatype) - { - if (allow_opt_inputs) Separator(); - if (RadioButton("0..255", (opts & ImGuiColorEditFlags_Uint8) != 0)) opts = (opts & ~ImGuiColorEditFlags_DataTypeMask_) | ImGuiColorEditFlags_Uint8; - if (RadioButton("0.00..1.00", (opts & ImGuiColorEditFlags_Float) != 0)) opts = (opts & ~ImGuiColorEditFlags_DataTypeMask_) | ImGuiColorEditFlags_Float; - } - - if (allow_opt_inputs || allow_opt_datatype) - Separator(); - if (Button("Copy as..", ImVec2(-1, 0))) - OpenPopup("Copy"); - if (BeginPopup("Copy")) - { - int cr = IM_F32_TO_INT8_SAT(col[0]), cg = IM_F32_TO_INT8_SAT(col[1]), cb = IM_F32_TO_INT8_SAT(col[2]), ca = (flags & ImGuiColorEditFlags_NoAlpha) ? 255 : IM_F32_TO_INT8_SAT(col[3]); - char buf[64]; - ImFormatString(buf, IM_ARRAYSIZE(buf), "(%.3ff, %.3ff, %.3ff, %.3ff)", col[0], col[1], col[2], (flags & ImGuiColorEditFlags_NoAlpha) ? 1.0f : col[3]); - if (Selectable(buf)) - SetClipboardText(buf); - ImFormatString(buf, IM_ARRAYSIZE(buf), "(%d,%d,%d,%d)", cr, cg, cb, ca); - if (Selectable(buf)) - SetClipboardText(buf); - ImFormatString(buf, IM_ARRAYSIZE(buf), "#%02X%02X%02X", cr, cg, cb); - if (Selectable(buf)) - SetClipboardText(buf); - if (!(flags & ImGuiColorEditFlags_NoAlpha)) - { - ImFormatString(buf, IM_ARRAYSIZE(buf), "#%02X%02X%02X%02X", cr, cg, cb, ca); - if (Selectable(buf)) - SetClipboardText(buf); - } - EndPopup(); - } - - g.ColorEditOptions = opts; - EndPopup(); - g.LockMarkEdited--; -} - -void ImGui::ColorPickerOptionsPopup(const float* ref_col, ImGuiColorEditFlags flags) -{ - bool allow_opt_picker = !(flags & ImGuiColorEditFlags_PickerMask_); - bool allow_opt_alpha_bar = !(flags & ImGuiColorEditFlags_NoAlpha) && !(flags & ImGuiColorEditFlags_AlphaBar); - if ((!allow_opt_picker && !allow_opt_alpha_bar) || !BeginPopup("context")) - return; - ImGuiContext& g = *GImGui; - g.LockMarkEdited++; - if (allow_opt_picker) - { - ImVec2 picker_size(g.FontSize * 8, ImMax(g.FontSize * 8 - (GetFrameHeight() + g.Style.ItemInnerSpacing.x), 1.0f)); // FIXME: Picker size copied from main picker function - PushItemWidth(picker_size.x); - for (int picker_type = 0; picker_type < 2; picker_type++) - { - // Draw small/thumbnail version of each picker type (over an invisible button for selection) - if (picker_type > 0) Separator(); - PushID(picker_type); - ImGuiColorEditFlags picker_flags = ImGuiColorEditFlags_NoInputs | ImGuiColorEditFlags_NoOptions | ImGuiColorEditFlags_NoLabel | ImGuiColorEditFlags_NoSidePreview | (flags & ImGuiColorEditFlags_NoAlpha); - if (picker_type == 0) picker_flags |= ImGuiColorEditFlags_PickerHueBar; - if (picker_type == 1) picker_flags |= ImGuiColorEditFlags_PickerHueWheel; - ImVec2 backup_pos = GetCursorScreenPos(); - if (Selectable("##selectable", false, 0, picker_size)) // By default, Selectable() is closing popup - g.ColorEditOptions = (g.ColorEditOptions & ~ImGuiColorEditFlags_PickerMask_) | (picker_flags & ImGuiColorEditFlags_PickerMask_); - SetCursorScreenPos(backup_pos); - ImVec4 previewing_ref_col; - memcpy(&previewing_ref_col, ref_col, sizeof(float) * ((picker_flags & ImGuiColorEditFlags_NoAlpha) ? 3 : 4)); - ColorPicker4("##previewing_picker", &previewing_ref_col.x, picker_flags); - PopID(); - } - PopItemWidth(); - } - if (allow_opt_alpha_bar) - { - if (allow_opt_picker) Separator(); - CheckboxFlags("Alpha Bar", &g.ColorEditOptions, ImGuiColorEditFlags_AlphaBar); - } - EndPopup(); - g.LockMarkEdited--; -} - -//------------------------------------------------------------------------- -// [SECTION] Widgets: TreeNode, CollapsingHeader, etc. -//------------------------------------------------------------------------- -// - TreeNode() -// - TreeNodeV() -// - TreeNodeEx() -// - TreeNodeExV() -// - TreeNodeBehavior() [Internal] -// - TreePush() -// - TreePop() -// - GetTreeNodeToLabelSpacing() -// - SetNextItemOpen() -// - CollapsingHeader() -//------------------------------------------------------------------------- - -bool ImGui::TreeNode(const char* str_id, const char* fmt, ...) -{ - va_list args; - va_start(args, fmt); - bool is_open = TreeNodeExV(str_id, 0, fmt, args); - va_end(args); - return is_open; -} - -bool ImGui::TreeNode(const void* ptr_id, const char* fmt, ...) -{ - va_list args; - va_start(args, fmt); - bool is_open = TreeNodeExV(ptr_id, 0, fmt, args); - va_end(args); - return is_open; -} - -bool ImGui::TreeNode(const char* label) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - return TreeNodeBehavior(window->GetID(label), 0, label, NULL); -} - -bool ImGui::TreeNodeV(const char* str_id, const char* fmt, va_list args) -{ - return TreeNodeExV(str_id, 0, fmt, args); -} - -bool ImGui::TreeNodeV(const void* ptr_id, const char* fmt, va_list args) -{ - return TreeNodeExV(ptr_id, 0, fmt, args); -} - -bool ImGui::TreeNodeEx(const char* label, ImGuiTreeNodeFlags flags) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - - return TreeNodeBehavior(window->GetID(label), flags, label, NULL); -} - -bool ImGui::TreeNodeEx(const char* str_id, ImGuiTreeNodeFlags flags, const char* fmt, ...) -{ - va_list args; - va_start(args, fmt); - bool is_open = TreeNodeExV(str_id, flags, fmt, args); - va_end(args); - return is_open; -} - -bool ImGui::TreeNodeEx(const void* ptr_id, ImGuiTreeNodeFlags flags, const char* fmt, ...) -{ - va_list args; - va_start(args, fmt); - bool is_open = TreeNodeExV(ptr_id, flags, fmt, args); - va_end(args); - return is_open; -} - -bool ImGui::TreeNodeExV(const char* str_id, ImGuiTreeNodeFlags flags, const char* fmt, va_list args) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - - const char* label, *label_end; - ImFormatStringToTempBufferV(&label, &label_end, fmt, args); - return TreeNodeBehavior(window->GetID(str_id), flags, label, label_end); -} - -bool ImGui::TreeNodeExV(const void* ptr_id, ImGuiTreeNodeFlags flags, const char* fmt, va_list args) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - - const char* label, *label_end; - ImFormatStringToTempBufferV(&label, &label_end, fmt, args); - return TreeNodeBehavior(window->GetID(ptr_id), flags, label, label_end); -} - -void ImGui::TreeNodeSetOpen(ImGuiID id, bool open) -{ - ImGuiContext& g = *GImGui; - ImGuiStorage* storage = g.CurrentWindow->DC.StateStorage; - storage->SetInt(id, open ? 1 : 0); -} - -bool ImGui::TreeNodeUpdateNextOpen(ImGuiID id, ImGuiTreeNodeFlags flags) -{ - if (flags & ImGuiTreeNodeFlags_Leaf) - return true; - - // We only write to the tree storage if the user clicks (or explicitly use the SetNextItemOpen function) - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - ImGuiStorage* storage = window->DC.StateStorage; - - bool is_open; - if (g.NextItemData.Flags & ImGuiNextItemDataFlags_HasOpen) - { - if (g.NextItemData.OpenCond & ImGuiCond_Always) - { - is_open = g.NextItemData.OpenVal; - TreeNodeSetOpen(id, is_open); - } - else - { - // We treat ImGuiCond_Once and ImGuiCond_FirstUseEver the same because tree node state are not saved persistently. - const int stored_value = storage->GetInt(id, -1); - if (stored_value == -1) - { - is_open = g.NextItemData.OpenVal; - TreeNodeSetOpen(id, is_open); - } - else - { - is_open = stored_value != 0; - } - } - } - else - { - is_open = storage->GetInt(id, (flags & ImGuiTreeNodeFlags_DefaultOpen) ? 1 : 0) != 0; - } - - // When logging is enabled, we automatically expand tree nodes (but *NOT* collapsing headers.. seems like sensible behavior). - // NB- If we are above max depth we still allow manually opened nodes to be logged. - if (g.LogEnabled && !(flags & ImGuiTreeNodeFlags_NoAutoOpenOnLog) && (window->DC.TreeDepth - g.LogDepthRef) < g.LogDepthToExpand) - is_open = true; - - return is_open; -} - -bool ImGui::TreeNodeBehavior(ImGuiID id, ImGuiTreeNodeFlags flags, const char* label, const char* label_end) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - - ImGuiContext& g = *GImGui; - const ImGuiStyle& style = g.Style; - const bool display_frame = (flags & ImGuiTreeNodeFlags_Framed) != 0; - const ImVec2 padding = (display_frame || (flags & ImGuiTreeNodeFlags_FramePadding)) ? style.FramePadding : ImVec2(style.FramePadding.x, ImMin(window->DC.CurrLineTextBaseOffset, style.FramePadding.y)); - - if (!label_end) - label_end = FindRenderedTextEnd(label); - const ImVec2 label_size = CalcTextSize(label, label_end, false); - - // We vertically grow up to current line height up the typical widget height. - const float frame_height = ImMax(ImMin(window->DC.CurrLineSize.y, g.FontSize + style.FramePadding.y * 2), label_size.y + padding.y * 2); - const bool span_all_columns = (flags & ImGuiTreeNodeFlags_SpanAllColumns) != 0 && (g.CurrentTable != NULL); - ImRect frame_bb; - frame_bb.Min.x = span_all_columns ? window->ParentWorkRect.Min.x : (flags & ImGuiTreeNodeFlags_SpanFullWidth) ? window->WorkRect.Min.x : window->DC.CursorPos.x; - frame_bb.Min.y = window->DC.CursorPos.y; - frame_bb.Max.x = span_all_columns ? window->ParentWorkRect.Max.x : window->WorkRect.Max.x; - frame_bb.Max.y = window->DC.CursorPos.y + frame_height; - if (display_frame) - { - // Framed header expand a little outside the default padding, to the edge of InnerClipRect - // (FIXME: May remove this at some point and make InnerClipRect align with WindowPadding.x instead of WindowPadding.x*0.5f) - frame_bb.Min.x -= IM_TRUNC(window->WindowPadding.x * 0.5f - 1.0f); - frame_bb.Max.x += IM_TRUNC(window->WindowPadding.x * 0.5f); - } - - const float text_offset_x = g.FontSize + (display_frame ? padding.x * 3 : padding.x * 2); // Collapsing arrow width + Spacing - const float text_offset_y = ImMax(padding.y, window->DC.CurrLineTextBaseOffset); // Latch before ItemSize changes it - const float text_width = g.FontSize + (label_size.x > 0.0f ? label_size.x + padding.x * 2 : 0.0f); // Include collapsing - ImVec2 text_pos(window->DC.CursorPos.x + text_offset_x, window->DC.CursorPos.y + text_offset_y); - ItemSize(ImVec2(text_width, frame_height), padding.y); - - // For regular tree nodes, we arbitrary allow to click past 2 worth of ItemSpacing - ImRect interact_bb = frame_bb; - if (!display_frame && (flags & (ImGuiTreeNodeFlags_SpanAvailWidth | ImGuiTreeNodeFlags_SpanFullWidth | ImGuiTreeNodeFlags_SpanAllColumns)) == 0) - interact_bb.Max.x = frame_bb.Min.x + text_width + style.ItemSpacing.x * 2.0f; - - // Modify ClipRect for the ItemAdd(), faster than doing a PushColumnsBackground/PushTableBackgroundChannel for every Selectable.. - const float backup_clip_rect_min_x = window->ClipRect.Min.x; - const float backup_clip_rect_max_x = window->ClipRect.Max.x; - if (span_all_columns) - { - window->ClipRect.Min.x = window->ParentWorkRect.Min.x; - window->ClipRect.Max.x = window->ParentWorkRect.Max.x; - } - - // Compute open and multi-select states before ItemAdd() as it clear NextItem data. - bool is_open = TreeNodeUpdateNextOpen(id, flags); - bool item_add = ItemAdd(interact_bb, id); - g.LastItemData.StatusFlags |= ImGuiItemStatusFlags_HasDisplayRect; - g.LastItemData.DisplayRect = frame_bb; - - if (span_all_columns) - { - window->ClipRect.Min.x = backup_clip_rect_min_x; - window->ClipRect.Max.x = backup_clip_rect_max_x; - } - - // If a NavLeft request is happening and ImGuiTreeNodeFlags_NavLeftJumpsBackHere enabled: - // Store data for the current depth to allow returning to this node from any child item. - // For this purpose we essentially compare if g.NavIdIsAlive went from 0 to 1 between TreeNode() and TreePop(). - // It will become tempting to enable ImGuiTreeNodeFlags_NavLeftJumpsBackHere by default or move it to ImGuiStyle. - // Currently only supports 32 level deep and we are fine with (1 << Depth) overflowing into a zero, easy to increase. - if (is_open && !g.NavIdIsAlive && (flags & ImGuiTreeNodeFlags_NavLeftJumpsBackHere) && !(flags & ImGuiTreeNodeFlags_NoTreePushOnOpen)) - if (g.NavMoveDir == ImGuiDir_Left && g.NavWindow == window && NavMoveRequestButNoResultYet()) - { - g.NavTreeNodeStack.resize(g.NavTreeNodeStack.Size + 1); - ImGuiNavTreeNodeData* nav_tree_node_data = &g.NavTreeNodeStack.back(); - nav_tree_node_data->ID = id; - nav_tree_node_data->InFlags = g.LastItemData.InFlags; - nav_tree_node_data->NavRect = g.LastItemData.NavRect; - window->DC.TreeJumpToParentOnPopMask |= (1 << window->DC.TreeDepth); - } - - const bool is_leaf = (flags & ImGuiTreeNodeFlags_Leaf) != 0; - if (!item_add) - { - if (is_open && !(flags & ImGuiTreeNodeFlags_NoTreePushOnOpen)) - TreePushOverrideID(id); - IMGUI_TEST_ENGINE_ITEM_INFO(g.LastItemData.ID, label, g.LastItemData.StatusFlags | (is_leaf ? 0 : ImGuiItemStatusFlags_Openable) | (is_open ? ImGuiItemStatusFlags_Opened : 0)); - return is_open; - } - - if (span_all_columns) - TablePushBackgroundChannel(); - - ImGuiButtonFlags button_flags = ImGuiTreeNodeFlags_None; - if ((flags & ImGuiTreeNodeFlags_AllowOverlap) || (g.LastItemData.InFlags & ImGuiItemFlags_AllowOverlap)) - button_flags |= ImGuiButtonFlags_AllowOverlap; - if (!is_leaf) - button_flags |= ImGuiButtonFlags_PressedOnDragDropHold; - - // We allow clicking on the arrow section with keyboard modifiers held, in order to easily - // allow browsing a tree while preserving selection with code implementing multi-selection patterns. - // When clicking on the rest of the tree node we always disallow keyboard modifiers. - const float arrow_hit_x1 = (text_pos.x - text_offset_x) - style.TouchExtraPadding.x; - const float arrow_hit_x2 = (text_pos.x - text_offset_x) + (g.FontSize + padding.x * 2.0f) + style.TouchExtraPadding.x; - const bool is_mouse_x_over_arrow = (g.IO.MousePos.x >= arrow_hit_x1 && g.IO.MousePos.x < arrow_hit_x2); - if (window != g.HoveredWindow || !is_mouse_x_over_arrow) - button_flags |= ImGuiButtonFlags_NoKeyModifiers; - - // Open behaviors can be altered with the _OpenOnArrow and _OnOnDoubleClick flags. - // Some alteration have subtle effects (e.g. toggle on MouseUp vs MouseDown events) due to requirements for multi-selection and drag and drop support. - // - Single-click on label = Toggle on MouseUp (default, when _OpenOnArrow=0) - // - Single-click on arrow = Toggle on MouseDown (when _OpenOnArrow=0) - // - Single-click on arrow = Toggle on MouseDown (when _OpenOnArrow=1) - // - Double-click on label = Toggle on MouseDoubleClick (when _OpenOnDoubleClick=1) - // - Double-click on arrow = Toggle on MouseDoubleClick (when _OpenOnDoubleClick=1 and _OpenOnArrow=0) - // It is rather standard that arrow click react on Down rather than Up. - // We set ImGuiButtonFlags_PressedOnClickRelease on OpenOnDoubleClick because we want the item to be active on the initial MouseDown in order for drag and drop to work. - if (is_mouse_x_over_arrow) - button_flags |= ImGuiButtonFlags_PressedOnClick; - else if (flags & ImGuiTreeNodeFlags_OpenOnDoubleClick) - button_flags |= ImGuiButtonFlags_PressedOnClickRelease | ImGuiButtonFlags_PressedOnDoubleClick; - else - button_flags |= ImGuiButtonFlags_PressedOnClickRelease; - - bool selected = (flags & ImGuiTreeNodeFlags_Selected) != 0; - const bool was_selected = selected; - - bool hovered, held; - bool pressed = ButtonBehavior(interact_bb, id, &hovered, &held, button_flags); - bool toggled = false; - if (!is_leaf) - { - if (pressed && g.DragDropHoldJustPressedId != id) - { - if ((flags & (ImGuiTreeNodeFlags_OpenOnArrow | ImGuiTreeNodeFlags_OpenOnDoubleClick)) == 0 || (g.NavActivateId == id)) - toggled = true; - if (flags & ImGuiTreeNodeFlags_OpenOnArrow) - toggled |= is_mouse_x_over_arrow && !g.NavDisableMouseHover; // Lightweight equivalent of IsMouseHoveringRect() since ButtonBehavior() already did the job - if ((flags & ImGuiTreeNodeFlags_OpenOnDoubleClick) && g.IO.MouseClickedCount[0] == 2) - toggled = true; - } - else if (pressed && g.DragDropHoldJustPressedId == id) - { - IM_ASSERT(button_flags & ImGuiButtonFlags_PressedOnDragDropHold); - if (!is_open) // When using Drag and Drop "hold to open" we keep the node highlighted after opening, but never close it again. - toggled = true; - } - - if (g.NavId == id && g.NavMoveDir == ImGuiDir_Left && is_open) - { - toggled = true; - NavClearPreferredPosForAxis(ImGuiAxis_X); - NavMoveRequestCancel(); - } - if (g.NavId == id && g.NavMoveDir == ImGuiDir_Right && !is_open) // If there's something upcoming on the line we may want to give it the priority? - { - toggled = true; - NavClearPreferredPosForAxis(ImGuiAxis_X); - NavMoveRequestCancel(); - } - - if (toggled) - { - is_open = !is_open; - window->DC.StateStorage->SetInt(id, is_open); - g.LastItemData.StatusFlags |= ImGuiItemStatusFlags_ToggledOpen; - } - } - - // In this branch, TreeNodeBehavior() cannot toggle the selection so this will never trigger. - if (selected != was_selected) //-V547 - g.LastItemData.StatusFlags |= ImGuiItemStatusFlags_ToggledSelection; - - // Render - const ImU32 text_col = GetColorU32(ImGuiCol_Text); - ImGuiNavHighlightFlags nav_highlight_flags = ImGuiNavHighlightFlags_TypeThin; - if (display_frame) - { - // Framed type - const ImU32 bg_col = GetColorU32((held && hovered) ? ImGuiCol_HeaderActive : hovered ? ImGuiCol_HeaderHovered : ImGuiCol_Header); - RenderFrame(frame_bb.Min, frame_bb.Max, bg_col, true, style.FrameRounding); - RenderNavHighlight(frame_bb, id, nav_highlight_flags); - if (flags & ImGuiTreeNodeFlags_Bullet) - RenderBullet(window->DrawList, ImVec2(text_pos.x - text_offset_x * 0.60f, text_pos.y + g.FontSize * 0.5f), text_col); - else if (!is_leaf) - RenderArrow(window->DrawList, ImVec2(text_pos.x - text_offset_x + padding.x, text_pos.y), text_col, is_open ? ((flags & ImGuiTreeNodeFlags_UpsideDownArrow) ? ImGuiDir_Up : ImGuiDir_Down) : ImGuiDir_Right, 1.0f); - else // Leaf without bullet, left-adjusted text - text_pos.x -= text_offset_x -padding.x; - if (flags & ImGuiTreeNodeFlags_ClipLabelForTrailingButton) - frame_bb.Max.x -= g.FontSize + style.FramePadding.x; - - if (g.LogEnabled) - LogSetNextTextDecoration("###", "###"); - } - else - { - // Unframed typed for tree nodes - if (hovered || selected) - { - const ImU32 bg_col = GetColorU32((held && hovered) ? ImGuiCol_HeaderActive : hovered ? ImGuiCol_HeaderHovered : ImGuiCol_Header); - RenderFrame(frame_bb.Min, frame_bb.Max, bg_col, false); - } - RenderNavHighlight(frame_bb, id, nav_highlight_flags); - if (flags & ImGuiTreeNodeFlags_Bullet) - RenderBullet(window->DrawList, ImVec2(text_pos.x - text_offset_x * 0.5f, text_pos.y + g.FontSize * 0.5f), text_col); - else if (!is_leaf) - RenderArrow(window->DrawList, ImVec2(text_pos.x - text_offset_x + padding.x, text_pos.y + g.FontSize * 0.15f), text_col, is_open ? ((flags & ImGuiTreeNodeFlags_UpsideDownArrow) ? ImGuiDir_Up : ImGuiDir_Down) : ImGuiDir_Right, 0.70f); - if (g.LogEnabled) - LogSetNextTextDecoration(">", NULL); - } - - if (span_all_columns) - TablePopBackgroundChannel(); - - // Label - if (display_frame) - RenderTextClipped(text_pos, frame_bb.Max, label, label_end, &label_size); - else - RenderText(text_pos, label, label_end, false); - - if (is_open && !(flags & ImGuiTreeNodeFlags_NoTreePushOnOpen)) - TreePushOverrideID(id); - IMGUI_TEST_ENGINE_ITEM_INFO(id, label, g.LastItemData.StatusFlags | (is_leaf ? 0 : ImGuiItemStatusFlags_Openable) | (is_open ? ImGuiItemStatusFlags_Opened : 0)); - return is_open; -} - -void ImGui::TreePush(const char* str_id) -{ - ImGuiWindow* window = GetCurrentWindow(); - Indent(); - window->DC.TreeDepth++; - PushID(str_id); -} - -void ImGui::TreePush(const void* ptr_id) -{ - ImGuiWindow* window = GetCurrentWindow(); - Indent(); - window->DC.TreeDepth++; - PushID(ptr_id); -} - -void ImGui::TreePushOverrideID(ImGuiID id) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - Indent(); - window->DC.TreeDepth++; - PushOverrideID(id); -} - -void ImGui::TreePop() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - Unindent(); - - window->DC.TreeDepth--; - ImU32 tree_depth_mask = (1 << window->DC.TreeDepth); - - // Handle Left arrow to move to parent tree node (when ImGuiTreeNodeFlags_NavLeftJumpsBackHere is enabled) - if (window->DC.TreeJumpToParentOnPopMask & tree_depth_mask) // Only set during request - { - ImGuiNavTreeNodeData* nav_tree_node_data = &g.NavTreeNodeStack.back(); - IM_ASSERT(nav_tree_node_data->ID == window->IDStack.back()); - if (g.NavIdIsAlive && g.NavMoveDir == ImGuiDir_Left && g.NavWindow == window && NavMoveRequestButNoResultYet()) - NavMoveRequestResolveWithPastTreeNode(&g.NavMoveResultLocal, nav_tree_node_data); - g.NavTreeNodeStack.pop_back(); - } - window->DC.TreeJumpToParentOnPopMask &= tree_depth_mask - 1; - - IM_ASSERT(window->IDStack.Size > 1); // There should always be 1 element in the IDStack (pushed during window creation). If this triggers you called TreePop/PopID too much. - PopID(); -} - -// Horizontal distance preceding label when using TreeNode() or Bullet() -float ImGui::GetTreeNodeToLabelSpacing() -{ - ImGuiContext& g = *GImGui; - return g.FontSize + (g.Style.FramePadding.x * 2.0f); -} - -// Set next TreeNode/CollapsingHeader open state. -void ImGui::SetNextItemOpen(bool is_open, ImGuiCond cond) -{ - ImGuiContext& g = *GImGui; - if (g.CurrentWindow->SkipItems) - return; - g.NextItemData.Flags |= ImGuiNextItemDataFlags_HasOpen; - g.NextItemData.OpenVal = is_open; - g.NextItemData.OpenCond = cond ? cond : ImGuiCond_Always; -} - -// CollapsingHeader returns true when opened but do not indent nor push into the ID stack (because of the ImGuiTreeNodeFlags_NoTreePushOnOpen flag). -// This is basically the same as calling TreeNodeEx(label, ImGuiTreeNodeFlags_CollapsingHeader). You can remove the _NoTreePushOnOpen flag if you want behavior closer to normal TreeNode(). -bool ImGui::CollapsingHeader(const char* label, ImGuiTreeNodeFlags flags) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - - return TreeNodeBehavior(window->GetID(label), flags | ImGuiTreeNodeFlags_CollapsingHeader, label); -} - -// p_visible == NULL : regular collapsing header -// p_visible != NULL && *p_visible == true : show a small close button on the corner of the header, clicking the button will set *p_visible = false -// p_visible != NULL && *p_visible == false : do not show the header at all -// Do not mistake this with the Open state of the header itself, which you can adjust with SetNextItemOpen() or ImGuiTreeNodeFlags_DefaultOpen. -bool ImGui::CollapsingHeader(const char* label, bool* p_visible, ImGuiTreeNodeFlags flags) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - - if (p_visible && !*p_visible) - return false; - - ImGuiID id = window->GetID(label); - flags |= ImGuiTreeNodeFlags_CollapsingHeader; - if (p_visible) - flags |= ImGuiTreeNodeFlags_AllowOverlap | ImGuiTreeNodeFlags_ClipLabelForTrailingButton; - bool is_open = TreeNodeBehavior(id, flags, label); - if (p_visible != NULL) - { - // Create a small overlapping close button - // FIXME: We can evolve this into user accessible helpers to add extra buttons on title bars, headers, etc. - // FIXME: CloseButton can overlap into text, need find a way to clip the text somehow. - ImGuiContext& g = *GImGui; - ImGuiLastItemData last_item_backup = g.LastItemData; - float button_size = g.FontSize; - float button_x = ImMax(g.LastItemData.Rect.Min.x, g.LastItemData.Rect.Max.x - g.Style.FramePadding.x - button_size); - float button_y = g.LastItemData.Rect.Min.y + g.Style.FramePadding.y; - ImGuiID close_button_id = GetIDWithSeed("#CLOSE", NULL, id); - if (CloseButton(close_button_id, ImVec2(button_x, button_y))) - *p_visible = false; - g.LastItemData = last_item_backup; - } - - return is_open; -} - -//------------------------------------------------------------------------- -// [SECTION] Widgets: Selectable -//------------------------------------------------------------------------- -// - Selectable() -//------------------------------------------------------------------------- - -// Tip: pass a non-visible label (e.g. "##hello") then you can use the space to draw other text or image. -// But you need to make sure the ID is unique, e.g. enclose calls in PushID/PopID or use ##unique_id. -// With this scheme, ImGuiSelectableFlags_SpanAllColumns and ImGuiSelectableFlags_AllowOverlap are also frequently used flags. -// FIXME: Selectable() with (size.x == 0.0f) and (SelectableTextAlign.x > 0.0f) followed by SameLine() is currently not supported. -bool ImGui::Selectable(const char* label, bool selected, ImGuiSelectableFlags flags, const ImVec2& size_arg) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - - ImGuiContext& g = *GImGui; - const ImGuiStyle& style = g.Style; - - // Submit label or explicit size to ItemSize(), whereas ItemAdd() will submit a larger/spanning rectangle. - ImGuiID id = window->GetID(label); - ImVec2 label_size = CalcTextSize(label, NULL, true); - ImVec2 size(size_arg.x != 0.0f ? size_arg.x : label_size.x, size_arg.y != 0.0f ? size_arg.y : label_size.y); - ImVec2 pos = window->DC.CursorPos; - pos.y += window->DC.CurrLineTextBaseOffset; - ItemSize(size, 0.0f); - - // Fill horizontal space - // We don't support (size < 0.0f) in Selectable() because the ItemSpacing extension would make explicitly right-aligned sizes not visibly match other widgets. - const bool span_all_columns = (flags & ImGuiSelectableFlags_SpanAllColumns) != 0; - const float min_x = span_all_columns ? window->ParentWorkRect.Min.x : pos.x; - const float max_x = span_all_columns ? window->ParentWorkRect.Max.x : window->WorkRect.Max.x; - if (size_arg.x == 0.0f || (flags & ImGuiSelectableFlags_SpanAvailWidth)) - size.x = ImMax(label_size.x, max_x - min_x); - - // Text stays at the submission position, but bounding box may be extended on both sides - const ImVec2 text_min = pos; - const ImVec2 text_max(min_x + size.x, pos.y + size.y); - - // Selectables are meant to be tightly packed together with no click-gap, so we extend their box to cover spacing between selectable. - ImRect bb(min_x, pos.y, text_max.x, text_max.y); - if ((flags & ImGuiSelectableFlags_NoPadWithHalfSpacing) == 0) - { - const float spacing_x = span_all_columns ? 0.0f : style.ItemSpacing.x; - const float spacing_y = style.ItemSpacing.y; - const float spacing_L = IM_TRUNC(spacing_x * 0.50f); - const float spacing_U = IM_TRUNC(spacing_y * 0.50f); - bb.Min.x -= spacing_L; - bb.Min.y -= spacing_U; - bb.Max.x += (spacing_x - spacing_L); - bb.Max.y += (spacing_y - spacing_U); - } - //if (g.IO.KeyCtrl) { GetForegroundDrawList()->AddRect(bb.Min, bb.Max, IM_COL32(0, 255, 0, 255)); } - - // Modify ClipRect for the ItemAdd(), faster than doing a PushColumnsBackground/PushTableBackgroundChannel for every Selectable.. - const float backup_clip_rect_min_x = window->ClipRect.Min.x; - const float backup_clip_rect_max_x = window->ClipRect.Max.x; - if (span_all_columns) - { - window->ClipRect.Min.x = window->ParentWorkRect.Min.x; - window->ClipRect.Max.x = window->ParentWorkRect.Max.x; - } - - const bool disabled_item = (flags & ImGuiSelectableFlags_Disabled) != 0; - const bool item_add = ItemAdd(bb, id, NULL, disabled_item ? ImGuiItemFlags_Disabled : ImGuiItemFlags_None); - if (span_all_columns) - { - window->ClipRect.Min.x = backup_clip_rect_min_x; - window->ClipRect.Max.x = backup_clip_rect_max_x; - } - - if (!item_add) - return false; - - const bool disabled_global = (g.CurrentItemFlags & ImGuiItemFlags_Disabled) != 0; - if (disabled_item && !disabled_global) // Only testing this as an optimization - BeginDisabled(); - - // FIXME: We can standardize the behavior of those two, we could also keep the fast path of override ClipRect + full push on render only, - // which would be advantageous since most selectable are not selected. - if (span_all_columns && window->DC.CurrentColumns) - PushColumnsBackground(); - else if (span_all_columns && g.CurrentTable) - TablePushBackgroundChannel(); - - // We use NoHoldingActiveID on menus so user can click and _hold_ on a menu then drag to browse child entries - ImGuiButtonFlags button_flags = 0; - if (flags & ImGuiSelectableFlags_NoHoldingActiveID) { button_flags |= ImGuiButtonFlags_NoHoldingActiveId; } - if (flags & ImGuiSelectableFlags_NoSetKeyOwner) { button_flags |= ImGuiButtonFlags_NoSetKeyOwner; } - if (flags & ImGuiSelectableFlags_SelectOnClick) { button_flags |= ImGuiButtonFlags_PressedOnClick; } - if (flags & ImGuiSelectableFlags_SelectOnRelease) { button_flags |= ImGuiButtonFlags_PressedOnRelease; } - if (flags & ImGuiSelectableFlags_AllowDoubleClick) { button_flags |= ImGuiButtonFlags_PressedOnClickRelease | ImGuiButtonFlags_PressedOnDoubleClick; } - if ((flags & ImGuiSelectableFlags_AllowOverlap) || (g.LastItemData.InFlags & ImGuiItemFlags_AllowOverlap)) { button_flags |= ImGuiButtonFlags_AllowOverlap; } - - const bool was_selected = selected; - bool hovered, held; - bool pressed = ButtonBehavior(bb, id, &hovered, &held, button_flags); - - // Auto-select when moved into - // - This will be more fully fleshed in the range-select branch - // - This is not exposed as it won't nicely work with some user side handling of shift/control - // - We cannot do 'if (g.NavJustMovedToId != id) { selected = false; pressed = was_selected; }' for two reasons - // - (1) it would require focus scope to be set, need exposing PushFocusScope() or equivalent (e.g. BeginSelection() calling PushFocusScope()) - // - (2) usage will fail with clipped items - // The multi-select API aim to fix those issues, e.g. may be replaced with a BeginSelection() API. - if ((flags & ImGuiSelectableFlags_SelectOnNav) && g.NavJustMovedToId != 0 && g.NavJustMovedToFocusScopeId == g.CurrentFocusScopeId) - if (g.NavJustMovedToId == id) - selected = pressed = true; - - // Update NavId when clicking or when Hovering (this doesn't happen on most widgets), so navigation can be resumed with gamepad/keyboard - if (pressed || (hovered && (flags & ImGuiSelectableFlags_SetNavIdOnHover))) - { - if (!g.NavDisableMouseHover && g.NavWindow == window && g.NavLayer == window->DC.NavLayerCurrent) - { - SetNavID(id, window->DC.NavLayerCurrent, g.CurrentFocusScopeId, WindowRectAbsToRel(window, bb)); // (bb == NavRect) - g.NavDisableHighlight = true; - } - } - if (pressed) - MarkItemEdited(id); - - // In this branch, Selectable() cannot toggle the selection so this will never trigger. - if (selected != was_selected) //-V547 - g.LastItemData.StatusFlags |= ImGuiItemStatusFlags_ToggledSelection; - - // Render - if (hovered || selected) - { - const ImU32 col = GetColorU32((held && hovered) ? ImGuiCol_HeaderActive : hovered ? ImGuiCol_HeaderHovered : ImGuiCol_Header); - RenderFrame(bb.Min, bb.Max, col, false, 0.0f); - } - if (g.NavId == id) - RenderNavHighlight(bb, id, ImGuiNavHighlightFlags_TypeThin | ImGuiNavHighlightFlags_NoRounding); - - if (span_all_columns && window->DC.CurrentColumns) - PopColumnsBackground(); - else if (span_all_columns && g.CurrentTable) - TablePopBackgroundChannel(); - - RenderTextClipped(text_min, text_max, label, NULL, &label_size, style.SelectableTextAlign, &bb); - - // Automatically close popups - if (pressed && (window->Flags & ImGuiWindowFlags_Popup) && !(flags & ImGuiSelectableFlags_DontClosePopups) && !(g.LastItemData.InFlags & ImGuiItemFlags_SelectableDontClosePopup)) - CloseCurrentPopup(); - - if (disabled_item && !disabled_global) - EndDisabled(); - - IMGUI_TEST_ENGINE_ITEM_INFO(id, label, g.LastItemData.StatusFlags); - return pressed; //-V1020 -} - -bool ImGui::Selectable(const char* label, bool* p_selected, ImGuiSelectableFlags flags, const ImVec2& size_arg) -{ - if (Selectable(label, *p_selected, flags, size_arg)) - { - *p_selected = !*p_selected; - return true; - } - return false; -} - - -//------------------------------------------------------------------------- -// [SECTION] Widgets: Typing-Select support -//------------------------------------------------------------------------- - -// [Experimental] Currently not exposed in public API. -// Consume character inputs and return search request, if any. -// This would typically only be called on the focused window or location you want to grab inputs for, e.g. -// if (ImGui::IsWindowFocused(...)) -// if (ImGuiTypingSelectRequest* req = ImGui::GetTypingSelectRequest()) -// focus_idx = ImGui::TypingSelectFindMatch(req, my_items.size(), [](void*, int n) { return my_items[n]->Name; }, &my_items, -1); -// However the code is written in a way where calling it from multiple locations is safe (e.g. to obtain buffer). -ImGuiTypingSelectRequest* ImGui::GetTypingSelectRequest(ImGuiTypingSelectFlags flags) -{ - ImGuiContext& g = *GImGui; - ImGuiTypingSelectState* data = &g.TypingSelectState; - ImGuiTypingSelectRequest* out_request = &data->Request; - - // Clear buffer - const float TYPING_SELECT_RESET_TIMER = 1.80f; // FIXME: Potentially move to IO config. - const int TYPING_SELECT_SINGLE_CHAR_COUNT_FOR_LOCK = 4; // Lock single char matching when repeating same char 4 times - if (data->SearchBuffer[0] != 0) - { - bool clear_buffer = false; - clear_buffer |= (g.NavFocusScopeId != data->FocusScope); - clear_buffer |= (data->LastRequestTime + TYPING_SELECT_RESET_TIMER < g.Time); - clear_buffer |= g.NavAnyRequest; - clear_buffer |= g.ActiveId != 0 && g.NavActivateId == 0; // Allow temporary SPACE activation to not interfere - clear_buffer |= IsKeyPressed(ImGuiKey_Escape) || IsKeyPressed(ImGuiKey_Enter); - clear_buffer |= IsKeyPressed(ImGuiKey_Backspace) && (flags & ImGuiTypingSelectFlags_AllowBackspace) == 0; - //if (clear_buffer) { IMGUI_DEBUG_LOG("GetTypingSelectRequest(): Clear SearchBuffer.\n"); } - if (clear_buffer) - data->Clear(); - } - - // Append to buffer - const int buffer_max_len = IM_ARRAYSIZE(data->SearchBuffer) - 1; - int buffer_len = (int)strlen(data->SearchBuffer); - bool select_request = false; - for (ImWchar w : g.IO.InputQueueCharacters) - { - const int w_len = ImTextCountUtf8BytesFromStr(&w, &w + 1); - if (w < 32 || (buffer_len == 0 && ImCharIsBlankW(w)) || (buffer_len + w_len > buffer_max_len)) // Ignore leading blanks - continue; - char w_buf[5]; - ImTextCharToUtf8(w_buf, (unsigned int)w); - if (data->SingleCharModeLock && w_len == out_request->SingleCharSize && memcmp(w_buf, data->SearchBuffer, w_len) == 0) - { - select_request = true; // Same character: don't need to append to buffer. - continue; - } - if (data->SingleCharModeLock) - { - data->Clear(); // Different character: clear - buffer_len = 0; - } - memcpy(data->SearchBuffer + buffer_len, w_buf, w_len + 1); // Append - buffer_len += w_len; - select_request = true; - } - g.IO.InputQueueCharacters.resize(0); - - // Handle backspace - if ((flags & ImGuiTypingSelectFlags_AllowBackspace) && IsKeyPressed(ImGuiKey_Backspace, 0, ImGuiInputFlags_Repeat)) - { - char* p = (char*)(void*)ImTextFindPreviousUtf8Codepoint(data->SearchBuffer, data->SearchBuffer + buffer_len); - *p = 0; - buffer_len = (int)(p - data->SearchBuffer); - } - - // Return request if any - if (buffer_len == 0) - return NULL; - if (select_request) - { - data->FocusScope = g.NavFocusScopeId; - data->LastRequestFrame = g.FrameCount; - data->LastRequestTime = (float)g.Time; - } - out_request->Flags = flags; - out_request->SearchBufferLen = buffer_len; - out_request->SearchBuffer = data->SearchBuffer; - out_request->SelectRequest = (data->LastRequestFrame == g.FrameCount); - out_request->SingleCharMode = false; - out_request->SingleCharSize = 0; - - // Calculate if buffer contains the same character repeated. - // - This can be used to implement a special search mode on first character. - // - Performed on UTF-8 codepoint for correctness. - // - SingleCharMode is always set for first input character, because it usually leads to a "next". - if (flags & ImGuiTypingSelectFlags_AllowSingleCharMode) - { - const char* buf_begin = out_request->SearchBuffer; - const char* buf_end = out_request->SearchBuffer + out_request->SearchBufferLen; - const int c0_len = ImTextCountUtf8BytesFromChar(buf_begin, buf_end); - const char* p = buf_begin + c0_len; - for (; p < buf_end; p += c0_len) - if (memcmp(buf_begin, p, (size_t)c0_len) != 0) - break; - const int single_char_count = (p == buf_end) ? (out_request->SearchBufferLen / c0_len) : 0; - out_request->SingleCharMode = (single_char_count > 0 || data->SingleCharModeLock); - out_request->SingleCharSize = (ImS8)c0_len; - data->SingleCharModeLock |= (single_char_count >= TYPING_SELECT_SINGLE_CHAR_COUNT_FOR_LOCK); // From now on we stop search matching to lock to single char mode. - } - - return out_request; -} - -static int ImStrimatchlen(const char* s1, const char* s1_end, const char* s2) -{ - int match_len = 0; - while (s1 < s1_end && ImToUpper(*s1++) == ImToUpper(*s2++)) - match_len++; - return match_len; -} - -// Default handler for finding a result for typing-select. You may implement your own. -// You might want to display a tooltip to visualize the current request SearchBuffer -// When SingleCharMode is set: -// - it is better to NOT display a tooltip of other on-screen display indicator. -// - the index of the currently focused item is required. -// if your SetNextItemSelectionData() values are indices, you can obtain it from ImGuiMultiSelectIO::NavIdItem, otherwise from g.NavLastValidSelectionUserData. -int ImGui::TypingSelectFindMatch(ImGuiTypingSelectRequest* req, int items_count, const char* (*get_item_name_func)(void*, int), void* user_data, int nav_item_idx) -{ - if (req == NULL || req->SelectRequest == false) // Support NULL parameter so both calls can be done from same spot. - return -1; - int idx = -1; - if (req->SingleCharMode && (req->Flags & ImGuiTypingSelectFlags_AllowSingleCharMode)) - idx = TypingSelectFindNextSingleCharMatch(req, items_count, get_item_name_func, user_data, nav_item_idx); - else - idx = TypingSelectFindBestLeadingMatch(req, items_count, get_item_name_func, user_data); - if (idx != -1) - NavRestoreHighlightAfterMove(); - return idx; -} - -// Special handling when a single character is repeated: perform search on a single letter and goes to next. -int ImGui::TypingSelectFindNextSingleCharMatch(ImGuiTypingSelectRequest* req, int items_count, const char* (*get_item_name_func)(void*, int), void* user_data, int nav_item_idx) -{ - // FIXME: Assume selection user data is index. Would be extremely practical. - //if (nav_item_idx == -1) - // nav_item_idx = (int)g.NavLastValidSelectionUserData; - - int first_match_idx = -1; - bool return_next_match = false; - for (int idx = 0; idx < items_count; idx++) - { - const char* item_name = get_item_name_func(user_data, idx); - if (ImStrimatchlen(req->SearchBuffer, req->SearchBuffer + req->SingleCharSize, item_name) < req->SingleCharSize) - continue; - if (return_next_match) // Return next matching item after current item. - return idx; - if (first_match_idx == -1 && nav_item_idx == -1) // Return first match immediately if we don't have a nav_item_idx value. - return idx; - if (first_match_idx == -1) // Record first match for wrapping. - first_match_idx = idx; - if (nav_item_idx == idx) // Record that we encountering nav_item so we can return next match. - return_next_match = true; - } - return first_match_idx; // First result -} - -int ImGui::TypingSelectFindBestLeadingMatch(ImGuiTypingSelectRequest* req, int items_count, const char* (*get_item_name_func)(void*, int), void* user_data) -{ - int longest_match_idx = -1; - int longest_match_len = 0; - for (int idx = 0; idx < items_count; idx++) - { - const char* item_name = get_item_name_func(user_data, idx); - const int match_len = ImStrimatchlen(req->SearchBuffer, req->SearchBuffer + req->SearchBufferLen, item_name); - if (match_len <= longest_match_len) - continue; - longest_match_idx = idx; - longest_match_len = match_len; - if (match_len == req->SearchBufferLen) - break; - } - return longest_match_idx; -} - -void ImGui::DebugNodeTypingSelectState(ImGuiTypingSelectState* data) -{ -#ifndef IMGUI_DISABLE_DEBUG_TOOLS - Text("SearchBuffer = \"%s\"", data->SearchBuffer); - Text("SingleCharMode = %d, Size = %d, Lock = %d", data->Request.SingleCharMode, data->Request.SingleCharSize, data->SingleCharModeLock); - Text("LastRequest = time: %.2f, frame: %d", data->LastRequestTime, data->LastRequestFrame); -#else - IM_UNUSED(data); -#endif -} - - -//------------------------------------------------------------------------- -// [SECTION] Widgets: Multi-Select support -//------------------------------------------------------------------------- - -void ImGui::SetNextItemSelectionUserData(ImGuiSelectionUserData selection_user_data) -{ - // Note that flags will be cleared by ItemAdd(), so it's only useful for Navigation code! - // This designed so widgets can also cheaply set this before calling ItemAdd(), so we are not tied to MultiSelect api. - ImGuiContext& g = *GImGui; - g.NextItemData.ItemFlags |= ImGuiItemFlags_HasSelectionUserData; - g.NextItemData.SelectionUserData = selection_user_data; -} - - -//------------------------------------------------------------------------- -// [SECTION] Widgets: ListBox -//------------------------------------------------------------------------- -// - BeginListBox() -// - EndListBox() -// - ListBox() -//------------------------------------------------------------------------- - -// Tip: To have a list filling the entire window width, use size.x = -FLT_MIN and pass an non-visible label e.g. "##empty" -// Tip: If your vertical size is calculated from an item count (e.g. 10 * item_height) consider adding a fractional part to facilitate seeing scrolling boundaries (e.g. 10.25 * item_height). -bool ImGui::BeginListBox(const char* label, const ImVec2& size_arg) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - - const ImGuiStyle& style = g.Style; - const ImGuiID id = GetID(label); - const ImVec2 label_size = CalcTextSize(label, NULL, true); - - // Size default to hold ~7.25 items. - // Fractional number of items helps seeing that we can scroll down/up without looking at scrollbar. - ImVec2 size = ImTrunc(CalcItemSize(size_arg, CalcItemWidth(), GetTextLineHeightWithSpacing() * 7.25f + style.FramePadding.y * 2.0f)); - ImVec2 frame_size = ImVec2(size.x, ImMax(size.y, label_size.y)); - ImRect frame_bb(window->DC.CursorPos, window->DC.CursorPos + frame_size); - ImRect bb(frame_bb.Min, frame_bb.Max + ImVec2(label_size.x > 0.0f ? style.ItemInnerSpacing.x + label_size.x : 0.0f, 0.0f)); - g.NextItemData.ClearFlags(); - - if (!IsRectVisible(bb.Min, bb.Max)) - { - ItemSize(bb.GetSize(), style.FramePadding.y); - ItemAdd(bb, 0, &frame_bb); - g.NextWindowData.ClearFlags(); // We behave like Begin() and need to consume those values - return false; - } - - // FIXME-OPT: We could omit the BeginGroup() if label_size.x but would need to omit the EndGroup() as well. - BeginGroup(); - if (label_size.x > 0.0f) - { - ImVec2 label_pos = ImVec2(frame_bb.Max.x + style.ItemInnerSpacing.x, frame_bb.Min.y + style.FramePadding.y); - RenderText(label_pos, label); - window->DC.CursorMaxPos = ImMax(window->DC.CursorMaxPos, label_pos + label_size); - } - - BeginChildFrame(id, frame_bb.GetSize()); - return true; -} - -void ImGui::EndListBox() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - IM_ASSERT((window->Flags & ImGuiWindowFlags_ChildWindow) && "Mismatched BeginListBox/EndListBox calls. Did you test the return value of BeginListBox?"); - IM_UNUSED(window); - - EndChildFrame(); - EndGroup(); // This is only required to be able to do IsItemXXX query on the whole ListBox including label -} - -bool ImGui::ListBox(const char* label, int* current_item, const char* const items[], int items_count, int height_items) -{ - const bool value_changed = ListBox(label, current_item, Items_ArrayGetter, (void*)items, items_count, height_items); - return value_changed; -} - -// This is merely a helper around BeginListBox(), EndListBox(). -// Considering using those directly to submit custom data or store selection differently. -bool ImGui::ListBox(const char* label, int* current_item, const char* (*getter)(void* user_data, int idx), void* user_data, int items_count, int height_in_items) -{ - ImGuiContext& g = *GImGui; - - // Calculate size from "height_in_items" - if (height_in_items < 0) - height_in_items = ImMin(items_count, 7); - float height_in_items_f = height_in_items + 0.25f; - ImVec2 size(0.0f, ImTrunc(GetTextLineHeightWithSpacing() * height_in_items_f + g.Style.FramePadding.y * 2.0f)); - - if (!BeginListBox(label, size)) - return false; - - // Assume all items have even height (= 1 line of text). If you need items of different height, - // you can create a custom version of ListBox() in your code without using the clipper. - bool value_changed = false; - ImGuiListClipper clipper; - clipper.Begin(items_count, GetTextLineHeightWithSpacing()); // We know exactly our line height here so we pass it as a minor optimization, but generally you don't need to. - while (clipper.Step()) - for (int i = clipper.DisplayStart; i < clipper.DisplayEnd; i++) - { - const char* item_text = getter(user_data, i); - if (item_text == NULL) - item_text = "*Unknown item*"; - - PushID(i); - const bool item_selected = (i == *current_item); - if (Selectable(item_text, item_selected)) - { - *current_item = i; - value_changed = true; - } - if (item_selected) - SetItemDefaultFocus(); - PopID(); - } - EndListBox(); - - if (value_changed) - MarkItemEdited(g.LastItemData.ID); - - return value_changed; -} - -//------------------------------------------------------------------------- -// [SECTION] Widgets: PlotLines, PlotHistogram -//------------------------------------------------------------------------- -// - PlotEx() [Internal] -// - PlotLines() -// - PlotHistogram() -//------------------------------------------------------------------------- -// Plot/Graph widgets are not very good. -// Consider writing your own, or using a third-party one, see: -// - ImPlot https://github.com/epezent/implot -// - others https://github.com/ocornut/imgui/wiki/Useful-Extensions -//------------------------------------------------------------------------- - -int ImGui::PlotEx(ImGuiPlotType plot_type, const char* label, float (*values_getter)(void* data, int idx), void* data, int values_count, int values_offset, const char* overlay_text, float scale_min, float scale_max, const ImVec2& size_arg) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return -1; - - const ImGuiStyle& style = g.Style; - const ImGuiID id = window->GetID(label); - - const ImVec2 label_size = CalcTextSize(label, NULL, true); - const ImVec2 frame_size = CalcItemSize(size_arg, CalcItemWidth(), label_size.y + style.FramePadding.y * 2.0f); - - const ImRect frame_bb(window->DC.CursorPos, window->DC.CursorPos + frame_size); - const ImRect inner_bb(frame_bb.Min + style.FramePadding, frame_bb.Max - style.FramePadding); - const ImRect total_bb(frame_bb.Min, frame_bb.Max + ImVec2(label_size.x > 0.0f ? style.ItemInnerSpacing.x + label_size.x : 0.0f, 0)); - ItemSize(total_bb, style.FramePadding.y); - if (!ItemAdd(total_bb, 0, &frame_bb)) - return -1; - const bool hovered = ItemHoverable(frame_bb, id, g.LastItemData.InFlags); - - // Determine scale from values if not specified - if (scale_min == FLT_MAX || scale_max == FLT_MAX) - { - float v_min = FLT_MAX; - float v_max = -FLT_MAX; - for (int i = 0; i < values_count; i++) - { - const float v = values_getter(data, i); - if (v != v) // Ignore NaN values - continue; - v_min = ImMin(v_min, v); - v_max = ImMax(v_max, v); - } - if (scale_min == FLT_MAX) - scale_min = v_min; - if (scale_max == FLT_MAX) - scale_max = v_max; - } - - RenderFrame(frame_bb.Min, frame_bb.Max, GetColorU32(ImGuiCol_FrameBg), true, style.FrameRounding); - - const int values_count_min = (plot_type == ImGuiPlotType_Lines) ? 2 : 1; - int idx_hovered = -1; - if (values_count >= values_count_min) - { - int res_w = ImMin((int)frame_size.x, values_count) + ((plot_type == ImGuiPlotType_Lines) ? -1 : 0); - int item_count = values_count + ((plot_type == ImGuiPlotType_Lines) ? -1 : 0); - - // Tooltip on hover - if (hovered && inner_bb.Contains(g.IO.MousePos)) - { - const float t = ImClamp((g.IO.MousePos.x - inner_bb.Min.x) / (inner_bb.Max.x - inner_bb.Min.x), 0.0f, 0.9999f); - const int v_idx = (int)(t * item_count); - IM_ASSERT(v_idx >= 0 && v_idx < values_count); - - const float v0 = values_getter(data, (v_idx + values_offset) % values_count); - const float v1 = values_getter(data, (v_idx + 1 + values_offset) % values_count); - if (plot_type == ImGuiPlotType_Lines) - SetTooltip("%d: %8.4g\n%d: %8.4g", v_idx, v0, v_idx + 1, v1); - else if (plot_type == ImGuiPlotType_Histogram) - SetTooltip("%d: %8.4g", v_idx, v0); - idx_hovered = v_idx; - } - - const float t_step = 1.0f / (float)res_w; - const float inv_scale = (scale_min == scale_max) ? 0.0f : (1.0f / (scale_max - scale_min)); - - float v0 = values_getter(data, (0 + values_offset) % values_count); - float t0 = 0.0f; - ImVec2 tp0 = ImVec2( t0, 1.0f - ImSaturate((v0 - scale_min) * inv_scale) ); // Point in the normalized space of our target rectangle - float histogram_zero_line_t = (scale_min * scale_max < 0.0f) ? (1 + scale_min * inv_scale) : (scale_min < 0.0f ? 0.0f : 1.0f); // Where does the zero line stands - - const ImU32 col_base = GetColorU32((plot_type == ImGuiPlotType_Lines) ? ImGuiCol_PlotLines : ImGuiCol_PlotHistogram); - const ImU32 col_hovered = GetColorU32((plot_type == ImGuiPlotType_Lines) ? ImGuiCol_PlotLinesHovered : ImGuiCol_PlotHistogramHovered); - - for (int n = 0; n < res_w; n++) - { - const float t1 = t0 + t_step; - const int v1_idx = (int)(t0 * item_count + 0.5f); - IM_ASSERT(v1_idx >= 0 && v1_idx < values_count); - const float v1 = values_getter(data, (v1_idx + values_offset + 1) % values_count); - const ImVec2 tp1 = ImVec2( t1, 1.0f - ImSaturate((v1 - scale_min) * inv_scale) ); - - // NB: Draw calls are merged together by the DrawList system. Still, we should render our batch are lower level to save a bit of CPU. - ImVec2 pos0 = ImLerp(inner_bb.Min, inner_bb.Max, tp0); - ImVec2 pos1 = ImLerp(inner_bb.Min, inner_bb.Max, (plot_type == ImGuiPlotType_Lines) ? tp1 : ImVec2(tp1.x, histogram_zero_line_t)); - if (plot_type == ImGuiPlotType_Lines) - { - window->DrawList->AddLine(pos0, pos1, idx_hovered == v1_idx ? col_hovered : col_base); - } - else if (plot_type == ImGuiPlotType_Histogram) - { - if (pos1.x >= pos0.x + 2.0f) - pos1.x -= 1.0f; - window->DrawList->AddRectFilled(pos0, pos1, idx_hovered == v1_idx ? col_hovered : col_base); - } - - t0 = t1; - tp0 = tp1; - } - } - - // Text overlay - if (overlay_text) - RenderTextClipped(ImVec2(frame_bb.Min.x, frame_bb.Min.y + style.FramePadding.y), frame_bb.Max, overlay_text, NULL, NULL, ImVec2(0.5f, 0.0f)); - - if (label_size.x > 0.0f) - RenderText(ImVec2(frame_bb.Max.x + style.ItemInnerSpacing.x, inner_bb.Min.y), label); - - // Return hovered index or -1 if none are hovered. - // This is currently not exposed in the public API because we need a larger redesign of the whole thing, but in the short-term we are making it available in PlotEx(). - return idx_hovered; -} - -struct ImGuiPlotArrayGetterData -{ - const float* Values; - int Stride; - - ImGuiPlotArrayGetterData(const float* values, int stride) { Values = values; Stride = stride; } -}; - -static float Plot_ArrayGetter(void* data, int idx) -{ - ImGuiPlotArrayGetterData* plot_data = (ImGuiPlotArrayGetterData*)data; - const float v = *(const float*)(const void*)((const unsigned char*)plot_data->Values + (size_t)idx * plot_data->Stride); - return v; -} - -void ImGui::PlotLines(const char* label, const float* values, int values_count, int values_offset, const char* overlay_text, float scale_min, float scale_max, ImVec2 graph_size, int stride) -{ - ImGuiPlotArrayGetterData data(values, stride); - PlotEx(ImGuiPlotType_Lines, label, &Plot_ArrayGetter, (void*)&data, values_count, values_offset, overlay_text, scale_min, scale_max, graph_size); -} - -void ImGui::PlotLines(const char* label, float (*values_getter)(void* data, int idx), void* data, int values_count, int values_offset, const char* overlay_text, float scale_min, float scale_max, ImVec2 graph_size) -{ - PlotEx(ImGuiPlotType_Lines, label, values_getter, data, values_count, values_offset, overlay_text, scale_min, scale_max, graph_size); -} - -void ImGui::PlotHistogram(const char* label, const float* values, int values_count, int values_offset, const char* overlay_text, float scale_min, float scale_max, ImVec2 graph_size, int stride) -{ - ImGuiPlotArrayGetterData data(values, stride); - PlotEx(ImGuiPlotType_Histogram, label, &Plot_ArrayGetter, (void*)&data, values_count, values_offset, overlay_text, scale_min, scale_max, graph_size); -} - -void ImGui::PlotHistogram(const char* label, float (*values_getter)(void* data, int idx), void* data, int values_count, int values_offset, const char* overlay_text, float scale_min, float scale_max, ImVec2 graph_size) -{ - PlotEx(ImGuiPlotType_Histogram, label, values_getter, data, values_count, values_offset, overlay_text, scale_min, scale_max, graph_size); -} - -//------------------------------------------------------------------------- -// [SECTION] Widgets: Value helpers -// Those is not very useful, legacy API. -//------------------------------------------------------------------------- -// - Value() -//------------------------------------------------------------------------- - -void ImGui::Value(const char* prefix, bool b) -{ - Text("%s: %s", prefix, (b ? "true" : "false")); -} - -void ImGui::Value(const char* prefix, int v) -{ - Text("%s: %d", prefix, v); -} - -void ImGui::Value(const char* prefix, unsigned int v) -{ - Text("%s: %d", prefix, v); -} - -void ImGui::Value(const char* prefix, float v, const char* float_format) -{ - if (float_format) - { - char fmt[64]; - ImFormatString(fmt, IM_ARRAYSIZE(fmt), "%%s: %s", float_format); - Text(fmt, prefix, v); - } - else - { - Text("%s: %.3f", prefix, v); - } -} - -//------------------------------------------------------------------------- -// [SECTION] MenuItem, BeginMenu, EndMenu, etc. -//------------------------------------------------------------------------- -// - ImGuiMenuColumns [Internal] -// - BeginMenuBar() -// - EndMenuBar() -// - BeginMainMenuBar() -// - EndMainMenuBar() -// - BeginMenu() -// - EndMenu() -// - MenuItemEx() [Internal] -// - MenuItem() -//------------------------------------------------------------------------- - -// Helpers for internal use -void ImGuiMenuColumns::Update(float spacing, bool window_reappearing) -{ - if (window_reappearing) - memset(Widths, 0, sizeof(Widths)); - Spacing = (ImU16)spacing; - CalcNextTotalWidth(true); - memset(Widths, 0, sizeof(Widths)); - TotalWidth = NextTotalWidth; - NextTotalWidth = 0; -} - -void ImGuiMenuColumns::CalcNextTotalWidth(bool update_offsets) -{ - ImU16 offset = 0; - bool want_spacing = false; - for (int i = 0; i < IM_ARRAYSIZE(Widths); i++) - { - ImU16 width = Widths[i]; - if (want_spacing && width > 0) - offset += Spacing; - want_spacing |= (width > 0); - if (update_offsets) - { - if (i == 1) { OffsetLabel = offset; } - if (i == 2) { OffsetShortcut = offset; } - if (i == 3) { OffsetMark = offset; } - } - offset += width; - } - NextTotalWidth = offset; -} - -float ImGuiMenuColumns::DeclColumns(float w_icon, float w_label, float w_shortcut, float w_mark) -{ - Widths[0] = ImMax(Widths[0], (ImU16)w_icon); - Widths[1] = ImMax(Widths[1], (ImU16)w_label); - Widths[2] = ImMax(Widths[2], (ImU16)w_shortcut); - Widths[3] = ImMax(Widths[3], (ImU16)w_mark); - CalcNextTotalWidth(false); - return (float)ImMax(TotalWidth, NextTotalWidth); -} - -// FIXME: Provided a rectangle perhaps e.g. a BeginMenuBarEx() could be used anywhere.. -// Currently the main responsibility of this function being to setup clip-rect + horizontal layout + menu navigation layer. -// Ideally we also want this to be responsible for claiming space out of the main window scrolling rectangle, in which case ImGuiWindowFlags_MenuBar will become unnecessary. -// Then later the same system could be used for multiple menu-bars, scrollbars, side-bars. -bool ImGui::BeginMenuBar() -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - if (!(window->Flags & ImGuiWindowFlags_MenuBar)) - return false; - - IM_ASSERT(!window->DC.MenuBarAppending); - BeginGroup(); // Backup position on layer 0 // FIXME: Misleading to use a group for that backup/restore - PushID("##menubar"); - - // We don't clip with current window clipping rectangle as it is already set to the area below. However we clip with window full rect. - // We remove 1 worth of rounding to Max.x to that text in long menus and small windows don't tend to display over the lower-right rounded area, which looks particularly glitchy. - ImRect bar_rect = window->MenuBarRect(); - ImRect clip_rect(IM_ROUND(bar_rect.Min.x + window->WindowBorderSize), IM_ROUND(bar_rect.Min.y + window->WindowBorderSize), IM_ROUND(ImMax(bar_rect.Min.x, bar_rect.Max.x - ImMax(window->WindowRounding, window->WindowBorderSize))), IM_ROUND(bar_rect.Max.y)); - clip_rect.ClipWith(window->OuterRectClipped); - PushClipRect(clip_rect.Min, clip_rect.Max, false); - - // We overwrite CursorMaxPos because BeginGroup sets it to CursorPos (essentially the .EmitItem hack in EndMenuBar() would need something analogous here, maybe a BeginGroupEx() with flags). - window->DC.CursorPos = window->DC.CursorMaxPos = ImVec2(bar_rect.Min.x + window->DC.MenuBarOffset.x, bar_rect.Min.y + window->DC.MenuBarOffset.y); - window->DC.LayoutType = ImGuiLayoutType_Horizontal; - window->DC.IsSameLine = false; - window->DC.NavLayerCurrent = ImGuiNavLayer_Menu; - window->DC.MenuBarAppending = true; - AlignTextToFramePadding(); - return true; -} - -void ImGui::EndMenuBar() -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return; - ImGuiContext& g = *GImGui; - - // Nav: When a move request within one of our child menu failed, capture the request to navigate among our siblings. - if (NavMoveRequestButNoResultYet() && (g.NavMoveDir == ImGuiDir_Left || g.NavMoveDir == ImGuiDir_Right) && (g.NavWindow->Flags & ImGuiWindowFlags_ChildMenu)) - { - // Try to find out if the request is for one of our child menu - ImGuiWindow* nav_earliest_child = g.NavWindow; - while (nav_earliest_child->ParentWindow && (nav_earliest_child->ParentWindow->Flags & ImGuiWindowFlags_ChildMenu)) - nav_earliest_child = nav_earliest_child->ParentWindow; - if (nav_earliest_child->ParentWindow == window && nav_earliest_child->DC.ParentLayoutType == ImGuiLayoutType_Horizontal && (g.NavMoveFlags & ImGuiNavMoveFlags_Forwarded) == 0) - { - // To do so we claim focus back, restore NavId and then process the movement request for yet another frame. - // This involve a one-frame delay which isn't very problematic in this situation. We could remove it by scoring in advance for multiple window (probably not worth bothering) - const ImGuiNavLayer layer = ImGuiNavLayer_Menu; - IM_ASSERT(window->DC.NavLayersActiveMaskNext & (1 << layer)); // Sanity check (FIXME: Seems unnecessary) - FocusWindow(window); - SetNavID(window->NavLastIds[layer], layer, 0, window->NavRectRel[layer]); - g.NavDisableHighlight = true; // Hide highlight for the current frame so we don't see the intermediary selection. - g.NavDisableMouseHover = g.NavMousePosDirty = true; - NavMoveRequestForward(g.NavMoveDir, g.NavMoveClipDir, g.NavMoveFlags, g.NavMoveScrollFlags); // Repeat - } - } - - IM_MSVC_WARNING_SUPPRESS(6011); // Static Analysis false positive "warning C6011: Dereferencing NULL pointer 'window'" - IM_ASSERT(window->Flags & ImGuiWindowFlags_MenuBar); - IM_ASSERT(window->DC.MenuBarAppending); - PopClipRect(); - PopID(); - window->DC.MenuBarOffset.x = window->DC.CursorPos.x - window->Pos.x; // Save horizontal position so next append can reuse it. This is kinda equivalent to a per-layer CursorPos. - - // FIXME: Extremely confusing, cleanup by (a) working on WorkRect stack system (b) not using a Group confusingly here. - ImGuiGroupData& group_data = g.GroupStack.back(); - group_data.EmitItem = false; - ImVec2 restore_cursor_max_pos = group_data.BackupCursorMaxPos; - window->DC.IdealMaxPos.x = ImMax(window->DC.IdealMaxPos.x, window->DC.CursorMaxPos.x - window->Scroll.x); // Convert ideal extents for scrolling layer equivalent. - EndGroup(); // Restore position on layer 0 // FIXME: Misleading to use a group for that backup/restore - window->DC.LayoutType = ImGuiLayoutType_Vertical; - window->DC.IsSameLine = false; - window->DC.NavLayerCurrent = ImGuiNavLayer_Main; - window->DC.MenuBarAppending = false; - window->DC.CursorMaxPos = restore_cursor_max_pos; -} - -// Important: calling order matters! -// FIXME: Somehow overlapping with docking tech. -// FIXME: The "rect-cut" aspect of this could be formalized into a lower-level helper (rect-cut: https://halt.software/dead-simple-layouts) -bool ImGui::BeginViewportSideBar(const char* name, ImGuiViewport* viewport_p, ImGuiDir dir, float axis_size, ImGuiWindowFlags window_flags) -{ - IM_ASSERT(dir != ImGuiDir_None); - - ImGuiWindow* bar_window = FindWindowByName(name); - ImGuiViewportP* viewport = (ImGuiViewportP*)(void*)(viewport_p ? viewport_p : GetMainViewport()); - if (bar_window == NULL || bar_window->BeginCount == 0) - { - // Calculate and set window size/position - ImRect avail_rect = viewport->GetBuildWorkRect(); - ImGuiAxis axis = (dir == ImGuiDir_Up || dir == ImGuiDir_Down) ? ImGuiAxis_Y : ImGuiAxis_X; - ImVec2 pos = avail_rect.Min; - if (dir == ImGuiDir_Right || dir == ImGuiDir_Down) - pos[axis] = avail_rect.Max[axis] - axis_size; - ImVec2 size = avail_rect.GetSize(); - size[axis] = axis_size; - SetNextWindowPos(pos); - SetNextWindowSize(size); - - // Report our size into work area (for next frame) using actual window size - if (dir == ImGuiDir_Up || dir == ImGuiDir_Left) - viewport->BuildWorkOffsetMin[axis] += axis_size; - else if (dir == ImGuiDir_Down || dir == ImGuiDir_Right) - viewport->BuildWorkOffsetMax[axis] -= axis_size; - } - - window_flags |= ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_NoResize | ImGuiWindowFlags_NoMove | ImGuiWindowFlags_NoDocking; - SetNextWindowViewport(viewport->ID); // Enforce viewport so we don't create our own viewport when ImGuiConfigFlags_ViewportsNoMerge is set. - PushStyleVar(ImGuiStyleVar_WindowRounding, 0.0f); - PushStyleVar(ImGuiStyleVar_WindowMinSize, ImVec2(0, 0)); // Lift normal size constraint - bool is_open = Begin(name, NULL, window_flags); - PopStyleVar(2); - - return is_open; -} - -bool ImGui::BeginMainMenuBar() -{ - ImGuiContext& g = *GImGui; - ImGuiViewportP* viewport = (ImGuiViewportP*)(void*)GetMainViewport(); - - // Notify of viewport change so GetFrameHeight() can be accurate in case of DPI change - SetCurrentViewport(NULL, viewport); - - // For the main menu bar, which cannot be moved, we honor g.Style.DisplaySafeAreaPadding to ensure text can be visible on a TV set. - // FIXME: This could be generalized as an opt-in way to clamp window->DC.CursorStartPos to avoid SafeArea? - // FIXME: Consider removing support for safe area down the line... it's messy. Nowadays consoles have support for TV calibration in OS settings. - g.NextWindowData.MenuBarOffsetMinVal = ImVec2(g.Style.DisplaySafeAreaPadding.x, ImMax(g.Style.DisplaySafeAreaPadding.y - g.Style.FramePadding.y, 0.0f)); - ImGuiWindowFlags window_flags = ImGuiWindowFlags_NoScrollbar | ImGuiWindowFlags_NoSavedSettings | ImGuiWindowFlags_MenuBar; - float height = GetFrameHeight(); - bool is_open = BeginViewportSideBar("##MainMenuBar", viewport, ImGuiDir_Up, height, window_flags); - g.NextWindowData.MenuBarOffsetMinVal = ImVec2(0.0f, 0.0f); - - if (is_open) - BeginMenuBar(); - else - End(); - return is_open; -} - -void ImGui::EndMainMenuBar() -{ - EndMenuBar(); - - // When the user has left the menu layer (typically: closed menus through activation of an item), we restore focus to the previous window - // FIXME: With this strategy we won't be able to restore a NULL focus. - ImGuiContext& g = *GImGui; - if (g.CurrentWindow == g.NavWindow && g.NavLayer == ImGuiNavLayer_Main && !g.NavAnyRequest) - FocusTopMostWindowUnderOne(g.NavWindow, NULL, NULL, ImGuiFocusRequestFlags_UnlessBelowModal | ImGuiFocusRequestFlags_RestoreFocusedChild); - - End(); -} - -static bool IsRootOfOpenMenuSet() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - if ((g.OpenPopupStack.Size <= g.BeginPopupStack.Size) || (window->Flags & ImGuiWindowFlags_ChildMenu)) - return false; - - // Initially we used 'upper_popup->OpenParentId == window->IDStack.back()' to differentiate multiple menu sets from each others - // (e.g. inside menu bar vs loose menu items) based on parent ID. - // This would however prevent the use of e.g. PushID() user code submitting menus. - // Previously this worked between popup and a first child menu because the first child menu always had the _ChildWindow flag, - // making hovering on parent popup possible while first child menu was focused - but this was generally a bug with other side effects. - // Instead we don't treat Popup specifically (in order to consistently support menu features in them), maybe the first child menu of a Popup - // doesn't have the _ChildWindow flag, and we rely on this IsRootOfOpenMenuSet() check to allow hovering between root window/popup and first child menu. - // In the end, lack of ID check made it so we could no longer differentiate between separate menu sets. To compensate for that, we at least check parent window nav layer. - // This fixes the most common case of menu opening on hover when moving between window content and menu bar. Multiple different menu sets in same nav layer would still - // open on hover, but that should be a lesser problem, because if such menus are close in proximity in window content then it won't feel weird and if they are far apart - // it likely won't be a problem anyone runs into. - const ImGuiPopupData* upper_popup = &g.OpenPopupStack[g.BeginPopupStack.Size]; - if (window->DC.NavLayerCurrent != upper_popup->ParentNavLayer) - return false; - return upper_popup->Window && (upper_popup->Window->Flags & ImGuiWindowFlags_ChildMenu) && ImGui::IsWindowChildOf(upper_popup->Window, window, true, false); -} - -bool ImGui::BeginMenuEx(const char* label, const char* icon, bool enabled) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - - ImGuiContext& g = *GImGui; - const ImGuiStyle& style = g.Style; - const ImGuiID id = window->GetID(label); - bool menu_is_open = IsPopupOpen(id, ImGuiPopupFlags_None); - - // Sub-menus are ChildWindow so that mouse can be hovering across them (otherwise top-most popup menu would steal focus and not allow hovering on parent menu) - // The first menu in a hierarchy isn't so hovering doesn't get across (otherwise e.g. resizing borders with ImGuiButtonFlags_FlattenChildren would react), but top-most BeginMenu() will bypass that limitation. - ImGuiWindowFlags window_flags = ImGuiWindowFlags_ChildMenu | ImGuiWindowFlags_AlwaysAutoResize | ImGuiWindowFlags_NoMove | ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_NoSavedSettings | ImGuiWindowFlags_NoNavFocus; - if (window->Flags & ImGuiWindowFlags_ChildMenu) - window_flags |= ImGuiWindowFlags_ChildWindow; - - // If a menu with same the ID was already submitted, we will append to it, matching the behavior of Begin(). - // We are relying on a O(N) search - so O(N log N) over the frame - which seems like the most efficient for the expected small amount of BeginMenu() calls per frame. - // If somehow this is ever becoming a problem we can switch to use e.g. ImGuiStorage mapping key to last frame used. - if (g.MenusIdSubmittedThisFrame.contains(id)) - { - if (menu_is_open) - menu_is_open = BeginPopupEx(id, window_flags); // menu_is_open can be 'false' when the popup is completely clipped (e.g. zero size display) - else - g.NextWindowData.ClearFlags(); // we behave like Begin() and need to consume those values - return menu_is_open; - } - - // Tag menu as used. Next time BeginMenu() with same ID is called it will append to existing menu - g.MenusIdSubmittedThisFrame.push_back(id); - - ImVec2 label_size = CalcTextSize(label, NULL, true); - - // Odd hack to allow hovering across menus of a same menu-set (otherwise we wouldn't be able to hover parent without always being a Child window) - // This is only done for items for the menu set and not the full parent window. - const bool menuset_is_open = IsRootOfOpenMenuSet(); - if (menuset_is_open) - PushItemFlag(ImGuiItemFlags_NoWindowHoverableCheck, true); - - // The reference position stored in popup_pos will be used by Begin() to find a suitable position for the child menu, - // However the final position is going to be different! It is chosen by FindBestWindowPosForPopup(). - // e.g. Menus tend to overlap each other horizontally to amplify relative Z-ordering. - ImVec2 popup_pos, pos = window->DC.CursorPos; - PushID(label); - if (!enabled) - BeginDisabled(); - const ImGuiMenuColumns* offsets = &window->DC.MenuColumns; - bool pressed; - - // We use ImGuiSelectableFlags_NoSetKeyOwner to allow down on one menu item, move, up on another. - const ImGuiSelectableFlags selectable_flags = ImGuiSelectableFlags_NoHoldingActiveID | ImGuiSelectableFlags_NoSetKeyOwner | ImGuiSelectableFlags_SelectOnClick | ImGuiSelectableFlags_DontClosePopups; - if (window->DC.LayoutType == ImGuiLayoutType_Horizontal) - { - // Menu inside an horizontal menu bar - // Selectable extend their highlight by half ItemSpacing in each direction. - // For ChildMenu, the popup position will be overwritten by the call to FindBestWindowPosForPopup() in Begin() - popup_pos = ImVec2(pos.x - 1.0f - IM_TRUNC(style.ItemSpacing.x * 0.5f), pos.y - style.FramePadding.y + window->MenuBarHeight()); - window->DC.CursorPos.x += IM_TRUNC(style.ItemSpacing.x * 0.5f); - PushStyleVar(ImGuiStyleVar_ItemSpacing, ImVec2(style.ItemSpacing.x * 2.0f, style.ItemSpacing.y)); - float w = label_size.x; - ImVec2 text_pos(window->DC.CursorPos.x + offsets->OffsetLabel, window->DC.CursorPos.y + window->DC.CurrLineTextBaseOffset); - pressed = Selectable("", menu_is_open, selectable_flags, ImVec2(w, label_size.y)); - RenderText(text_pos, label); - PopStyleVar(); - window->DC.CursorPos.x += IM_TRUNC(style.ItemSpacing.x * (-1.0f + 0.5f)); // -1 spacing to compensate the spacing added when Selectable() did a SameLine(). It would also work to call SameLine() ourselves after the PopStyleVar(). - } - else - { - // Menu inside a regular/vertical menu - // (In a typical menu window where all items are BeginMenu() or MenuItem() calls, extra_w will always be 0.0f. - // Only when they are other items sticking out we're going to add spacing, yet only register minimum width into the layout system. - popup_pos = ImVec2(pos.x, pos.y - style.WindowPadding.y); - float icon_w = (icon && icon[0]) ? CalcTextSize(icon, NULL).x : 0.0f; - float checkmark_w = IM_TRUNC(g.FontSize * 1.20f); - float min_w = window->DC.MenuColumns.DeclColumns(icon_w, label_size.x, 0.0f, checkmark_w); // Feedback to next frame - float extra_w = ImMax(0.0f, GetContentRegionAvail().x - min_w); - ImVec2 text_pos(window->DC.CursorPos.x + offsets->OffsetLabel, window->DC.CursorPos.y + window->DC.CurrLineTextBaseOffset); - pressed = Selectable("", menu_is_open, selectable_flags | ImGuiSelectableFlags_SpanAvailWidth, ImVec2(min_w, label_size.y)); - RenderText(text_pos, label); - if (icon_w > 0.0f) - RenderText(pos + ImVec2(offsets->OffsetIcon, 0.0f), icon); - RenderArrow(window->DrawList, pos + ImVec2(offsets->OffsetMark + extra_w + g.FontSize * 0.30f, 0.0f), GetColorU32(ImGuiCol_Text), ImGuiDir_Right); - } - if (!enabled) - EndDisabled(); - - const bool hovered = (g.HoveredId == id) && enabled && !g.NavDisableMouseHover; - if (menuset_is_open) - PopItemFlag(); - - bool want_open = false; - bool want_close = false; - if (window->DC.LayoutType == ImGuiLayoutType_Vertical) // (window->Flags & (ImGuiWindowFlags_Popup|ImGuiWindowFlags_ChildMenu)) - { - // Close menu when not hovering it anymore unless we are moving roughly in the direction of the menu - // Implement http://bjk5.com/post/44698559168/breaking-down-amazons-mega-dropdown to avoid using timers, so menus feels more reactive. - bool moving_toward_child_menu = false; - ImGuiPopupData* child_popup = (g.BeginPopupStack.Size < g.OpenPopupStack.Size) ? &g.OpenPopupStack[g.BeginPopupStack.Size] : NULL; // Popup candidate (testing below) - ImGuiWindow* child_menu_window = (child_popup && child_popup->Window && child_popup->Window->ParentWindow == window) ? child_popup->Window : NULL; - if (g.HoveredWindow == window && child_menu_window != NULL) - { - float ref_unit = g.FontSize; // FIXME-DPI - float child_dir = (window->Pos.x < child_menu_window->Pos.x) ? 1.0f : -1.0f; - ImRect next_window_rect = child_menu_window->Rect(); - ImVec2 ta = (g.IO.MousePos - g.IO.MouseDelta); - ImVec2 tb = (child_dir > 0.0f) ? next_window_rect.GetTL() : next_window_rect.GetTR(); - ImVec2 tc = (child_dir > 0.0f) ? next_window_rect.GetBL() : next_window_rect.GetBR(); - float extra = ImClamp(ImFabs(ta.x - tb.x) * 0.30f, ref_unit * 0.5f, ref_unit * 2.5f); // add a bit of extra slack. - ta.x += child_dir * -0.5f; - tb.x += child_dir * ref_unit; - tc.x += child_dir * ref_unit; - tb.y = ta.y + ImMax((tb.y - extra) - ta.y, -ref_unit * 8.0f); // triangle has maximum height to limit the slope and the bias toward large sub-menus - tc.y = ta.y + ImMin((tc.y + extra) - ta.y, +ref_unit * 8.0f); - moving_toward_child_menu = ImTriangleContainsPoint(ta, tb, tc, g.IO.MousePos); - //GetForegroundDrawList()->AddTriangleFilled(ta, tb, tc, moving_toward_child_menu ? IM_COL32(0,128,0,128) : IM_COL32(128,0,0,128)); // [DEBUG] - } - - // The 'HovereWindow == window' check creates an inconsistency (e.g. moving away from menu slowly tends to hit same window, whereas moving away fast does not) - // But we also need to not close the top-menu menu when moving over void. Perhaps we should extend the triangle check to a larger polygon. - // (Remember to test this on BeginPopup("A")->BeginMenu("B") sequence which behaves slightly differently as B isn't a Child of A and hovering isn't shared.) - if (menu_is_open && !hovered && g.HoveredWindow == window && !moving_toward_child_menu && !g.NavDisableMouseHover && g.ActiveId == 0) - want_close = true; - - // Open - if (!menu_is_open && pressed) // Click/activate to open - want_open = true; - else if (!menu_is_open && hovered && !moving_toward_child_menu) // Hover to open - want_open = true; - if (g.NavId == id && g.NavMoveDir == ImGuiDir_Right) // Nav-Right to open - { - want_open = true; - NavMoveRequestCancel(); - } - } - else - { - // Menu bar - if (menu_is_open && pressed && menuset_is_open) // Click an open menu again to close it - { - want_close = true; - want_open = menu_is_open = false; - } - else if (pressed || (hovered && menuset_is_open && !menu_is_open)) // First click to open, then hover to open others - { - want_open = true; - } - else if (g.NavId == id && g.NavMoveDir == ImGuiDir_Down) // Nav-Down to open - { - want_open = true; - NavMoveRequestCancel(); - } - } - - if (!enabled) // explicitly close if an open menu becomes disabled, facilitate users code a lot in pattern such as 'if (BeginMenu("options", has_object)) { ..use object.. }' - want_close = true; - if (want_close && IsPopupOpen(id, ImGuiPopupFlags_None)) - ClosePopupToLevel(g.BeginPopupStack.Size, true); - - IMGUI_TEST_ENGINE_ITEM_INFO(id, label, g.LastItemData.StatusFlags | ImGuiItemStatusFlags_Openable | (menu_is_open ? ImGuiItemStatusFlags_Opened : 0)); - PopID(); - - if (want_open && !menu_is_open && g.OpenPopupStack.Size > g.BeginPopupStack.Size) - { - // Don't reopen/recycle same menu level in the same frame, first close the other menu and yield for a frame. - OpenPopup(label); - } - else if (want_open) - { - menu_is_open = true; - OpenPopup(label); - } - - if (menu_is_open) - { - ImGuiLastItemData last_item_in_parent = g.LastItemData; - SetNextWindowPos(popup_pos, ImGuiCond_Always); // Note: misleading: the value will serve as reference for FindBestWindowPosForPopup(), not actual pos. - PushStyleVar(ImGuiStyleVar_ChildRounding, style.PopupRounding); // First level will use _PopupRounding, subsequent will use _ChildRounding - menu_is_open = BeginPopupEx(id, window_flags); // menu_is_open can be 'false' when the popup is completely clipped (e.g. zero size display) - PopStyleVar(); - if (menu_is_open) - { - // Restore LastItemData so IsItemXXXX functions can work after BeginMenu()/EndMenu() - // (This fixes using IsItemClicked() and IsItemHovered(), but IsItemHovered() also relies on its support for ImGuiItemFlags_NoWindowHoverableCheck) - g.LastItemData = last_item_in_parent; - if (g.HoveredWindow == window) - g.LastItemData.StatusFlags |= ImGuiItemStatusFlags_HoveredWindow; - } - } - else - { - g.NextWindowData.ClearFlags(); // We behave like Begin() and need to consume those values - } - - return menu_is_open; -} - -bool ImGui::BeginMenu(const char* label, bool enabled) -{ - return BeginMenuEx(label, NULL, enabled); -} - -void ImGui::EndMenu() -{ - // Nav: When a left move request our menu failed, close ourselves. - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - IM_ASSERT(window->Flags & ImGuiWindowFlags_Popup); // Mismatched BeginMenu()/EndMenu() calls - ImGuiWindow* parent_window = window->ParentWindow; // Should always be != NULL is we passed assert. - if (window->BeginCount == window->BeginCountPreviousFrame) - if (g.NavMoveDir == ImGuiDir_Left && NavMoveRequestButNoResultYet()) - if (g.NavWindow && (g.NavWindow->RootWindowForNav == window) && parent_window->DC.LayoutType == ImGuiLayoutType_Vertical) - { - ClosePopupToLevel(g.BeginPopupStack.Size - 1, true); - NavMoveRequestCancel(); - } - - EndPopup(); -} - -bool ImGui::MenuItemEx(const char* label, const char* icon, const char* shortcut, bool selected, bool enabled) -{ - ImGuiWindow* window = GetCurrentWindow(); - if (window->SkipItems) - return false; - - ImGuiContext& g = *GImGui; - ImGuiStyle& style = g.Style; - ImVec2 pos = window->DC.CursorPos; - ImVec2 label_size = CalcTextSize(label, NULL, true); - - // See BeginMenuEx() for comments about this. - const bool menuset_is_open = IsRootOfOpenMenuSet(); - if (menuset_is_open) - PushItemFlag(ImGuiItemFlags_NoWindowHoverableCheck, true); - - // We've been using the equivalent of ImGuiSelectableFlags_SetNavIdOnHover on all Selectable() since early Nav system days (commit 43ee5d73), - // but I am unsure whether this should be kept at all. For now moved it to be an opt-in feature used by menus only. - bool pressed; - PushID(label); - if (!enabled) - BeginDisabled(); - - // We use ImGuiSelectableFlags_NoSetKeyOwner to allow down on one menu item, move, up on another. - const ImGuiSelectableFlags selectable_flags = ImGuiSelectableFlags_SelectOnRelease | ImGuiSelectableFlags_NoSetKeyOwner | ImGuiSelectableFlags_SetNavIdOnHover; - const ImGuiMenuColumns* offsets = &window->DC.MenuColumns; - if (window->DC.LayoutType == ImGuiLayoutType_Horizontal) - { - // Mimic the exact layout spacing of BeginMenu() to allow MenuItem() inside a menu bar, which is a little misleading but may be useful - // Note that in this situation: we don't render the shortcut, we render a highlight instead of the selected tick mark. - float w = label_size.x; - window->DC.CursorPos.x += IM_TRUNC(style.ItemSpacing.x * 0.5f); - ImVec2 text_pos(window->DC.CursorPos.x + offsets->OffsetLabel, window->DC.CursorPos.y + window->DC.CurrLineTextBaseOffset); - PushStyleVar(ImGuiStyleVar_ItemSpacing, ImVec2(style.ItemSpacing.x * 2.0f, style.ItemSpacing.y)); - pressed = Selectable("", selected, selectable_flags, ImVec2(w, 0.0f)); - PopStyleVar(); - if (g.LastItemData.StatusFlags & ImGuiItemStatusFlags_Visible) - RenderText(text_pos, label); - window->DC.CursorPos.x += IM_TRUNC(style.ItemSpacing.x * (-1.0f + 0.5f)); // -1 spacing to compensate the spacing added when Selectable() did a SameLine(). It would also work to call SameLine() ourselves after the PopStyleVar(). - } - else - { - // Menu item inside a vertical menu - // (In a typical menu window where all items are BeginMenu() or MenuItem() calls, extra_w will always be 0.0f. - // Only when they are other items sticking out we're going to add spacing, yet only register minimum width into the layout system. - float icon_w = (icon && icon[0]) ? CalcTextSize(icon, NULL).x : 0.0f; - float shortcut_w = (shortcut && shortcut[0]) ? CalcTextSize(shortcut, NULL).x : 0.0f; - float checkmark_w = IM_TRUNC(g.FontSize * 1.20f); - float min_w = window->DC.MenuColumns.DeclColumns(icon_w, label_size.x, shortcut_w, checkmark_w); // Feedback for next frame - float stretch_w = ImMax(0.0f, GetContentRegionAvail().x - min_w); - pressed = Selectable("", false, selectable_flags | ImGuiSelectableFlags_SpanAvailWidth, ImVec2(min_w, label_size.y)); - if (g.LastItemData.StatusFlags & ImGuiItemStatusFlags_Visible) - { - RenderText(pos + ImVec2(offsets->OffsetLabel, 0.0f), label); - if (icon_w > 0.0f) - RenderText(pos + ImVec2(offsets->OffsetIcon, 0.0f), icon); - if (shortcut_w > 0.0f) - { - PushStyleColor(ImGuiCol_Text, style.Colors[ImGuiCol_TextDisabled]); - RenderText(pos + ImVec2(offsets->OffsetShortcut + stretch_w, 0.0f), shortcut, NULL, false); - PopStyleColor(); - } - if (selected) - RenderCheckMark(window->DrawList, pos + ImVec2(offsets->OffsetMark + stretch_w + g.FontSize * 0.40f, g.FontSize * 0.134f * 0.5f), GetColorU32(ImGuiCol_Text), g.FontSize * 0.866f); - } - } - IMGUI_TEST_ENGINE_ITEM_INFO(g.LastItemData.ID, label, g.LastItemData.StatusFlags | ImGuiItemStatusFlags_Checkable | (selected ? ImGuiItemStatusFlags_Checked : 0)); - if (!enabled) - EndDisabled(); - PopID(); - if (menuset_is_open) - PopItemFlag(); - - return pressed; -} - -bool ImGui::MenuItem(const char* label, const char* shortcut, bool selected, bool enabled) -{ - return MenuItemEx(label, NULL, shortcut, selected, enabled); -} - -bool ImGui::MenuItem(const char* label, const char* shortcut, bool* p_selected, bool enabled) -{ - if (MenuItemEx(label, NULL, shortcut, p_selected ? *p_selected : false, enabled)) - { - if (p_selected) - *p_selected = !*p_selected; - return true; - } - return false; -} - -//------------------------------------------------------------------------- -// [SECTION] Widgets: BeginTabBar, EndTabBar, etc. -//------------------------------------------------------------------------- -// - BeginTabBar() -// - BeginTabBarEx() [Internal] -// - EndTabBar() -// - TabBarLayout() [Internal] -// - TabBarCalcTabID() [Internal] -// - TabBarCalcMaxTabWidth() [Internal] -// - TabBarFindTabById() [Internal] -// - TabBarFindTabByOrder() [Internal] -// - TabBarFindMostRecentlySelectedTabForActiveWindow() [Internal] -// - TabBarGetCurrentTab() [Internal] -// - TabBarGetTabName() [Internal] -// - TabBarAddTab() [Internal] -// - TabBarRemoveTab() [Internal] -// - TabBarCloseTab() [Internal] -// - TabBarScrollClamp() [Internal] -// - TabBarScrollToTab() [Internal] -// - TabBarQueueFocus() [Internal] -// - TabBarQueueReorder() [Internal] -// - TabBarProcessReorderFromMousePos() [Internal] -// - TabBarProcessReorder() [Internal] -// - TabBarScrollingButtons() [Internal] -// - TabBarTabListPopupButton() [Internal] -//------------------------------------------------------------------------- - -struct ImGuiTabBarSection -{ - int TabCount; // Number of tabs in this section. - float Width; // Sum of width of tabs in this section (after shrinking down) - float Spacing; // Horizontal spacing at the end of the section. - - ImGuiTabBarSection() { memset(this, 0, sizeof(*this)); } -}; - -namespace ImGui -{ - static void TabBarLayout(ImGuiTabBar* tab_bar); - static ImU32 TabBarCalcTabID(ImGuiTabBar* tab_bar, const char* label, ImGuiWindow* docked_window); - static float TabBarCalcMaxTabWidth(); - static float TabBarScrollClamp(ImGuiTabBar* tab_bar, float scrolling); - static void TabBarScrollToTab(ImGuiTabBar* tab_bar, ImGuiID tab_id, ImGuiTabBarSection* sections); - static ImGuiTabItem* TabBarScrollingButtons(ImGuiTabBar* tab_bar); - static ImGuiTabItem* TabBarTabListPopupButton(ImGuiTabBar* tab_bar); -} - -ImGuiTabBar::ImGuiTabBar() -{ - memset(this, 0, sizeof(*this)); - CurrFrameVisible = PrevFrameVisible = -1; - LastTabItemIdx = -1; -} - -static inline int TabItemGetSectionIdx(const ImGuiTabItem* tab) -{ - return (tab->Flags & ImGuiTabItemFlags_Leading) ? 0 : (tab->Flags & ImGuiTabItemFlags_Trailing) ? 2 : 1; -} - -static int IMGUI_CDECL TabItemComparerBySection(const void* lhs, const void* rhs) -{ - const ImGuiTabItem* a = (const ImGuiTabItem*)lhs; - const ImGuiTabItem* b = (const ImGuiTabItem*)rhs; - const int a_section = TabItemGetSectionIdx(a); - const int b_section = TabItemGetSectionIdx(b); - if (a_section != b_section) - return a_section - b_section; - return (int)(a->IndexDuringLayout - b->IndexDuringLayout); -} - -static int IMGUI_CDECL TabItemComparerByBeginOrder(const void* lhs, const void* rhs) -{ - const ImGuiTabItem* a = (const ImGuiTabItem*)lhs; - const ImGuiTabItem* b = (const ImGuiTabItem*)rhs; - return (int)(a->BeginOrder - b->BeginOrder); -} - -static ImGuiTabBar* GetTabBarFromTabBarRef(const ImGuiPtrOrIndex& ref) -{ - ImGuiContext& g = *GImGui; - return ref.Ptr ? (ImGuiTabBar*)ref.Ptr : g.TabBars.GetByIndex(ref.Index); -} - -static ImGuiPtrOrIndex GetTabBarRefFromTabBar(ImGuiTabBar* tab_bar) -{ - ImGuiContext& g = *GImGui; - if (g.TabBars.Contains(tab_bar)) - return ImGuiPtrOrIndex(g.TabBars.GetIndex(tab_bar)); - return ImGuiPtrOrIndex(tab_bar); -} - -bool ImGui::BeginTabBar(const char* str_id, ImGuiTabBarFlags flags) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - if (window->SkipItems) - return false; - - ImGuiID id = window->GetID(str_id); - ImGuiTabBar* tab_bar = g.TabBars.GetOrAddByKey(id); - ImRect tab_bar_bb = ImRect(window->DC.CursorPos.x, window->DC.CursorPos.y, window->WorkRect.Max.x, window->DC.CursorPos.y + g.FontSize + g.Style.FramePadding.y * 2); - tab_bar->ID = id; - tab_bar->SeparatorMinX = tab_bar->BarRect.Min.x - IM_TRUNC(window->WindowPadding.x * 0.5f); - tab_bar->SeparatorMaxX = tab_bar->BarRect.Max.x + IM_TRUNC(window->WindowPadding.x * 0.5f); - return BeginTabBarEx(tab_bar, tab_bar_bb, flags | ImGuiTabBarFlags_IsFocused); -} - -bool ImGui::BeginTabBarEx(ImGuiTabBar* tab_bar, const ImRect& tab_bar_bb, ImGuiTabBarFlags flags) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - if (window->SkipItems) - return false; - - IM_ASSERT(tab_bar->ID != 0); - if ((flags & ImGuiTabBarFlags_DockNode) == 0) - PushOverrideID(tab_bar->ID); - - // Add to stack - g.CurrentTabBarStack.push_back(GetTabBarRefFromTabBar(tab_bar)); - g.CurrentTabBar = tab_bar; - - // Append with multiple BeginTabBar()/EndTabBar() pairs. - tab_bar->BackupCursorPos = window->DC.CursorPos; - if (tab_bar->CurrFrameVisible == g.FrameCount) - { - window->DC.CursorPos = ImVec2(tab_bar->BarRect.Min.x, tab_bar->BarRect.Max.y + tab_bar->ItemSpacingY); - tab_bar->BeginCount++; - return true; - } - - // Ensure correct ordering when toggling ImGuiTabBarFlags_Reorderable flag, or when a new tab was added while being not reorderable - if ((flags & ImGuiTabBarFlags_Reorderable) != (tab_bar->Flags & ImGuiTabBarFlags_Reorderable) || (tab_bar->TabsAddedNew && !(flags & ImGuiTabBarFlags_Reorderable))) - if ((flags & ImGuiTabBarFlags_DockNode) == 0) // FIXME: TabBar with DockNode can now be hybrid - ImQsort(tab_bar->Tabs.Data, tab_bar->Tabs.Size, sizeof(ImGuiTabItem), TabItemComparerByBeginOrder); - tab_bar->TabsAddedNew = false; - - // Flags - if ((flags & ImGuiTabBarFlags_FittingPolicyMask_) == 0) - flags |= ImGuiTabBarFlags_FittingPolicyDefault_; - - tab_bar->Flags = flags; - tab_bar->BarRect = tab_bar_bb; - tab_bar->WantLayout = true; // Layout will be done on the first call to ItemTab() - tab_bar->PrevFrameVisible = tab_bar->CurrFrameVisible; - tab_bar->CurrFrameVisible = g.FrameCount; - tab_bar->PrevTabsContentsHeight = tab_bar->CurrTabsContentsHeight; - tab_bar->CurrTabsContentsHeight = 0.0f; - tab_bar->ItemSpacingY = g.Style.ItemSpacing.y; - tab_bar->FramePadding = g.Style.FramePadding; - tab_bar->TabsActiveCount = 0; - tab_bar->LastTabItemIdx = -1; - tab_bar->BeginCount = 1; - - // Set cursor pos in a way which only be used in the off-chance the user erroneously submits item before BeginTabItem(): items will overlap - window->DC.CursorPos = ImVec2(tab_bar->BarRect.Min.x, tab_bar->BarRect.Max.y + tab_bar->ItemSpacingY); - - // Draw separator - // (it would be misleading to draw this in EndTabBar() suggesting that it may be drawn over tabs, as tab bar are appendable) - const ImU32 col = GetColorU32((flags & ImGuiTabBarFlags_IsFocused) ? ImGuiCol_TabActive : ImGuiCol_TabUnfocusedActive); - if (g.Style.TabBarBorderSize > 0.0f) - { - const float y = tab_bar->BarRect.Max.y; - window->DrawList->AddRectFilled(ImVec2(tab_bar->SeparatorMinX, y - g.Style.TabBarBorderSize), ImVec2(tab_bar->SeparatorMaxX, y), col); - } - return true; -} - -void ImGui::EndTabBar() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - if (window->SkipItems) - return; - - ImGuiTabBar* tab_bar = g.CurrentTabBar; - if (tab_bar == NULL) - { - IM_ASSERT_USER_ERROR(tab_bar != NULL, "Mismatched BeginTabBar()/EndTabBar()!"); - return; - } - - // Fallback in case no TabItem have been submitted - if (tab_bar->WantLayout) - TabBarLayout(tab_bar); - - // Restore the last visible height if no tab is visible, this reduce vertical flicker/movement when a tabs gets removed without calling SetTabItemClosed(). - const bool tab_bar_appearing = (tab_bar->PrevFrameVisible + 1 < g.FrameCount); - if (tab_bar->VisibleTabWasSubmitted || tab_bar->VisibleTabId == 0 || tab_bar_appearing) - { - tab_bar->CurrTabsContentsHeight = ImMax(window->DC.CursorPos.y - tab_bar->BarRect.Max.y, tab_bar->CurrTabsContentsHeight); - window->DC.CursorPos.y = tab_bar->BarRect.Max.y + tab_bar->CurrTabsContentsHeight; - } - else - { - window->DC.CursorPos.y = tab_bar->BarRect.Max.y + tab_bar->PrevTabsContentsHeight; - } - if (tab_bar->BeginCount > 1) - window->DC.CursorPos = tab_bar->BackupCursorPos; - - tab_bar->LastTabItemIdx = -1; - if ((tab_bar->Flags & ImGuiTabBarFlags_DockNode) == 0) - PopID(); - - g.CurrentTabBarStack.pop_back(); - g.CurrentTabBar = g.CurrentTabBarStack.empty() ? NULL : GetTabBarFromTabBarRef(g.CurrentTabBarStack.back()); -} - -// Scrolling happens only in the central section (leading/trailing sections are not scrolling) -static float TabBarCalcScrollableWidth(ImGuiTabBar* tab_bar, ImGuiTabBarSection* sections) -{ - return tab_bar->BarRect.GetWidth() - sections[0].Width - sections[2].Width - sections[1].Spacing; -} - -// This is called only once a frame before by the first call to ItemTab() -// The reason we're not calling it in BeginTabBar() is to leave a chance to the user to call the SetTabItemClosed() functions. -static void ImGui::TabBarLayout(ImGuiTabBar* tab_bar) -{ - ImGuiContext& g = *GImGui; - tab_bar->WantLayout = false; - - // Garbage collect by compacting list - // Detect if we need to sort out tab list (e.g. in rare case where a tab changed section) - int tab_dst_n = 0; - bool need_sort_by_section = false; - ImGuiTabBarSection sections[3]; // Layout sections: Leading, Central, Trailing - for (int tab_src_n = 0; tab_src_n < tab_bar->Tabs.Size; tab_src_n++) - { - ImGuiTabItem* tab = &tab_bar->Tabs[tab_src_n]; - if (tab->LastFrameVisible < tab_bar->PrevFrameVisible || tab->WantClose) - { - // Remove tab - if (tab_bar->VisibleTabId == tab->ID) { tab_bar->VisibleTabId = 0; } - if (tab_bar->SelectedTabId == tab->ID) { tab_bar->SelectedTabId = 0; } - if (tab_bar->NextSelectedTabId == tab->ID) { tab_bar->NextSelectedTabId = 0; } - continue; - } - if (tab_dst_n != tab_src_n) - tab_bar->Tabs[tab_dst_n] = tab_bar->Tabs[tab_src_n]; - - tab = &tab_bar->Tabs[tab_dst_n]; - tab->IndexDuringLayout = (ImS16)tab_dst_n; - - // We will need sorting if tabs have changed section (e.g. moved from one of Leading/Central/Trailing to another) - int curr_tab_section_n = TabItemGetSectionIdx(tab); - if (tab_dst_n > 0) - { - ImGuiTabItem* prev_tab = &tab_bar->Tabs[tab_dst_n - 1]; - int prev_tab_section_n = TabItemGetSectionIdx(prev_tab); - if (curr_tab_section_n == 0 && prev_tab_section_n != 0) - need_sort_by_section = true; - if (prev_tab_section_n == 2 && curr_tab_section_n != 2) - need_sort_by_section = true; - } - - sections[curr_tab_section_n].TabCount++; - tab_dst_n++; - } - if (tab_bar->Tabs.Size != tab_dst_n) - tab_bar->Tabs.resize(tab_dst_n); - - if (need_sort_by_section) - ImQsort(tab_bar->Tabs.Data, tab_bar->Tabs.Size, sizeof(ImGuiTabItem), TabItemComparerBySection); - - // Calculate spacing between sections - sections[0].Spacing = sections[0].TabCount > 0 && (sections[1].TabCount + sections[2].TabCount) > 0 ? g.Style.ItemInnerSpacing.x : 0.0f; - sections[1].Spacing = sections[1].TabCount > 0 && sections[2].TabCount > 0 ? g.Style.ItemInnerSpacing.x : 0.0f; - - // Setup next selected tab - ImGuiID scroll_to_tab_id = 0; - if (tab_bar->NextSelectedTabId) - { - tab_bar->SelectedTabId = tab_bar->NextSelectedTabId; - tab_bar->NextSelectedTabId = 0; - scroll_to_tab_id = tab_bar->SelectedTabId; - } - - // Process order change request (we could probably process it when requested but it's just saner to do it in a single spot). - if (tab_bar->ReorderRequestTabId != 0) - { - if (TabBarProcessReorder(tab_bar)) - if (tab_bar->ReorderRequestTabId == tab_bar->SelectedTabId) - scroll_to_tab_id = tab_bar->ReorderRequestTabId; - tab_bar->ReorderRequestTabId = 0; - } - - // Tab List Popup (will alter tab_bar->BarRect and therefore the available width!) - const bool tab_list_popup_button = (tab_bar->Flags & ImGuiTabBarFlags_TabListPopupButton) != 0; - if (tab_list_popup_button) - if (ImGuiTabItem* tab_to_select = TabBarTabListPopupButton(tab_bar)) // NB: Will alter BarRect.Min.x! - scroll_to_tab_id = tab_bar->SelectedTabId = tab_to_select->ID; - - // Leading/Trailing tabs will be shrink only if central one aren't visible anymore, so layout the shrink data as: leading, trailing, central - // (whereas our tabs are stored as: leading, central, trailing) - int shrink_buffer_indexes[3] = { 0, sections[0].TabCount + sections[2].TabCount, sections[0].TabCount }; - g.ShrinkWidthBuffer.resize(tab_bar->Tabs.Size); - - // Compute ideal tabs widths + store them into shrink buffer - ImGuiTabItem* most_recently_selected_tab = NULL; - int curr_section_n = -1; - bool found_selected_tab_id = false; - for (int tab_n = 0; tab_n < tab_bar->Tabs.Size; tab_n++) - { - ImGuiTabItem* tab = &tab_bar->Tabs[tab_n]; - IM_ASSERT(tab->LastFrameVisible >= tab_bar->PrevFrameVisible); - - if ((most_recently_selected_tab == NULL || most_recently_selected_tab->LastFrameSelected < tab->LastFrameSelected) && !(tab->Flags & ImGuiTabItemFlags_Button)) - most_recently_selected_tab = tab; - if (tab->ID == tab_bar->SelectedTabId) - found_selected_tab_id = true; - if (scroll_to_tab_id == 0 && g.NavJustMovedToId == tab->ID) - scroll_to_tab_id = tab->ID; - - // Refresh tab width immediately, otherwise changes of style e.g. style.FramePadding.x would noticeably lag in the tab bar. - // Additionally, when using TabBarAddTab() to manipulate tab bar order we occasionally insert new tabs that don't have a width yet, - // and we cannot wait for the next BeginTabItem() call. We cannot compute this width within TabBarAddTab() because font size depends on the active window. - const char* tab_name = TabBarGetTabName(tab_bar, tab); - const bool has_close_button_or_unsaved_marker = (tab->Flags & ImGuiTabItemFlags_NoCloseButton) == 0 || (tab->Flags & ImGuiTabItemFlags_UnsavedDocument); - tab->ContentWidth = (tab->RequestedWidth >= 0.0f) ? tab->RequestedWidth : TabItemCalcSize(tab_name, has_close_button_or_unsaved_marker).x; - - int section_n = TabItemGetSectionIdx(tab); - ImGuiTabBarSection* section = §ions[section_n]; - section->Width += tab->ContentWidth + (section_n == curr_section_n ? g.Style.ItemInnerSpacing.x : 0.0f); - curr_section_n = section_n; - - // Store data so we can build an array sorted by width if we need to shrink tabs down - IM_MSVC_WARNING_SUPPRESS(6385); - ImGuiShrinkWidthItem* shrink_width_item = &g.ShrinkWidthBuffer[shrink_buffer_indexes[section_n]++]; - shrink_width_item->Index = tab_n; - shrink_width_item->Width = shrink_width_item->InitialWidth = tab->ContentWidth; - tab->Width = ImMax(tab->ContentWidth, 1.0f); - } - - // Compute total ideal width (used for e.g. auto-resizing a window) - tab_bar->WidthAllTabsIdeal = 0.0f; - for (int section_n = 0; section_n < 3; section_n++) - tab_bar->WidthAllTabsIdeal += sections[section_n].Width + sections[section_n].Spacing; - - // Horizontal scrolling buttons - // (note that TabBarScrollButtons() will alter BarRect.Max.x) - if ((tab_bar->WidthAllTabsIdeal > tab_bar->BarRect.GetWidth() && tab_bar->Tabs.Size > 1) && !(tab_bar->Flags & ImGuiTabBarFlags_NoTabListScrollingButtons) && (tab_bar->Flags & ImGuiTabBarFlags_FittingPolicyScroll)) - if (ImGuiTabItem* scroll_and_select_tab = TabBarScrollingButtons(tab_bar)) - { - scroll_to_tab_id = scroll_and_select_tab->ID; - if ((scroll_and_select_tab->Flags & ImGuiTabItemFlags_Button) == 0) - tab_bar->SelectedTabId = scroll_to_tab_id; - } - - // Shrink widths if full tabs don't fit in their allocated space - float section_0_w = sections[0].Width + sections[0].Spacing; - float section_1_w = sections[1].Width + sections[1].Spacing; - float section_2_w = sections[2].Width + sections[2].Spacing; - bool central_section_is_visible = (section_0_w + section_2_w) < tab_bar->BarRect.GetWidth(); - float width_excess; - if (central_section_is_visible) - width_excess = ImMax(section_1_w - (tab_bar->BarRect.GetWidth() - section_0_w - section_2_w), 0.0f); // Excess used to shrink central section - else - width_excess = (section_0_w + section_2_w) - tab_bar->BarRect.GetWidth(); // Excess used to shrink leading/trailing section - - // With ImGuiTabBarFlags_FittingPolicyScroll policy, we will only shrink leading/trailing if the central section is not visible anymore - if (width_excess >= 1.0f && ((tab_bar->Flags & ImGuiTabBarFlags_FittingPolicyResizeDown) || !central_section_is_visible)) - { - int shrink_data_count = (central_section_is_visible ? sections[1].TabCount : sections[0].TabCount + sections[2].TabCount); - int shrink_data_offset = (central_section_is_visible ? sections[0].TabCount + sections[2].TabCount : 0); - ShrinkWidths(g.ShrinkWidthBuffer.Data + shrink_data_offset, shrink_data_count, width_excess); - - // Apply shrunk values into tabs and sections - for (int tab_n = shrink_data_offset; tab_n < shrink_data_offset + shrink_data_count; tab_n++) - { - ImGuiTabItem* tab = &tab_bar->Tabs[g.ShrinkWidthBuffer[tab_n].Index]; - float shrinked_width = IM_TRUNC(g.ShrinkWidthBuffer[tab_n].Width); - if (shrinked_width < 0.0f) - continue; - - shrinked_width = ImMax(1.0f, shrinked_width); - int section_n = TabItemGetSectionIdx(tab); - sections[section_n].Width -= (tab->Width - shrinked_width); - tab->Width = shrinked_width; - } - } - - // Layout all active tabs - int section_tab_index = 0; - float tab_offset = 0.0f; - tab_bar->WidthAllTabs = 0.0f; - for (int section_n = 0; section_n < 3; section_n++) - { - ImGuiTabBarSection* section = §ions[section_n]; - if (section_n == 2) - tab_offset = ImMin(ImMax(0.0f, tab_bar->BarRect.GetWidth() - section->Width), tab_offset); - - for (int tab_n = 0; tab_n < section->TabCount; tab_n++) - { - ImGuiTabItem* tab = &tab_bar->Tabs[section_tab_index + tab_n]; - tab->Offset = tab_offset; - tab->NameOffset = -1; - tab_offset += tab->Width + (tab_n < section->TabCount - 1 ? g.Style.ItemInnerSpacing.x : 0.0f); - } - tab_bar->WidthAllTabs += ImMax(section->Width + section->Spacing, 0.0f); - tab_offset += section->Spacing; - section_tab_index += section->TabCount; - } - - // Clear name buffers - tab_bar->TabsNames.Buf.resize(0); - - // If we have lost the selected tab, select the next most recently active one - if (found_selected_tab_id == false) - tab_bar->SelectedTabId = 0; - if (tab_bar->SelectedTabId == 0 && tab_bar->NextSelectedTabId == 0 && most_recently_selected_tab != NULL) - scroll_to_tab_id = tab_bar->SelectedTabId = most_recently_selected_tab->ID; - - // Lock in visible tab - tab_bar->VisibleTabId = tab_bar->SelectedTabId; - tab_bar->VisibleTabWasSubmitted = false; - - // CTRL+TAB can override visible tab temporarily - if (g.NavWindowingTarget != NULL && g.NavWindowingTarget->DockNode && g.NavWindowingTarget->DockNode->TabBar == tab_bar) - tab_bar->VisibleTabId = scroll_to_tab_id = g.NavWindowingTarget->TabId; - - // Apply request requests - if (scroll_to_tab_id != 0) - TabBarScrollToTab(tab_bar, scroll_to_tab_id, sections); - else if ((tab_bar->Flags & ImGuiTabBarFlags_FittingPolicyScroll) && IsMouseHoveringRect(tab_bar->BarRect.Min, tab_bar->BarRect.Max, true) && IsWindowContentHoverable(g.CurrentWindow)) - { - const float wheel = g.IO.MouseWheelRequestAxisSwap ? g.IO.MouseWheel : g.IO.MouseWheelH; - const ImGuiKey wheel_key = g.IO.MouseWheelRequestAxisSwap ? ImGuiKey_MouseWheelY : ImGuiKey_MouseWheelX; - if (TestKeyOwner(wheel_key, tab_bar->ID) && wheel != 0.0f) - { - const float scroll_step = wheel * TabBarCalcScrollableWidth(tab_bar, sections) / 3.0f; - tab_bar->ScrollingTargetDistToVisibility = 0.0f; - tab_bar->ScrollingTarget = TabBarScrollClamp(tab_bar, tab_bar->ScrollingTarget - scroll_step); - } - SetKeyOwner(wheel_key, tab_bar->ID); - } - - // Update scrolling - tab_bar->ScrollingAnim = TabBarScrollClamp(tab_bar, tab_bar->ScrollingAnim); - tab_bar->ScrollingTarget = TabBarScrollClamp(tab_bar, tab_bar->ScrollingTarget); - if (tab_bar->ScrollingAnim != tab_bar->ScrollingTarget) - { - // Scrolling speed adjust itself so we can always reach our target in 1/3 seconds. - // Teleport if we are aiming far off the visible line - tab_bar->ScrollingSpeed = ImMax(tab_bar->ScrollingSpeed, 70.0f * g.FontSize); - tab_bar->ScrollingSpeed = ImMax(tab_bar->ScrollingSpeed, ImFabs(tab_bar->ScrollingTarget - tab_bar->ScrollingAnim) / 0.3f); - const bool teleport = (tab_bar->PrevFrameVisible + 1 < g.FrameCount) || (tab_bar->ScrollingTargetDistToVisibility > 10.0f * g.FontSize); - tab_bar->ScrollingAnim = teleport ? tab_bar->ScrollingTarget : ImLinearSweep(tab_bar->ScrollingAnim, tab_bar->ScrollingTarget, g.IO.DeltaTime * tab_bar->ScrollingSpeed); - } - else - { - tab_bar->ScrollingSpeed = 0.0f; - } - tab_bar->ScrollingRectMinX = tab_bar->BarRect.Min.x + sections[0].Width + sections[0].Spacing; - tab_bar->ScrollingRectMaxX = tab_bar->BarRect.Max.x - sections[2].Width - sections[1].Spacing; - - // Actual layout in host window (we don't do it in BeginTabBar() so as not to waste an extra frame) - ImGuiWindow* window = g.CurrentWindow; - window->DC.CursorPos = tab_bar->BarRect.Min; - ItemSize(ImVec2(tab_bar->WidthAllTabs, tab_bar->BarRect.GetHeight()), tab_bar->FramePadding.y); - window->DC.IdealMaxPos.x = ImMax(window->DC.IdealMaxPos.x, tab_bar->BarRect.Min.x + tab_bar->WidthAllTabsIdeal); -} - -// Dockable windows uses Name/ID in the global namespace. Non-dockable items use the ID stack. -static ImU32 ImGui::TabBarCalcTabID(ImGuiTabBar* tab_bar, const char* label, ImGuiWindow* docked_window) -{ - if (docked_window != NULL) - { - IM_UNUSED(tab_bar); - IM_ASSERT(tab_bar->Flags & ImGuiTabBarFlags_DockNode); - ImGuiID id = docked_window->TabId; - KeepAliveID(id); - return id; - } - else - { - ImGuiWindow* window = GImGui->CurrentWindow; - return window->GetID(label); - } -} - -static float ImGui::TabBarCalcMaxTabWidth() -{ - ImGuiContext& g = *GImGui; - return g.FontSize * 20.0f; -} - -ImGuiTabItem* ImGui::TabBarFindTabByID(ImGuiTabBar* tab_bar, ImGuiID tab_id) -{ - if (tab_id != 0) - for (int n = 0; n < tab_bar->Tabs.Size; n++) - if (tab_bar->Tabs[n].ID == tab_id) - return &tab_bar->Tabs[n]; - return NULL; -} - -// Order = visible order, not submission order! (which is tab->BeginOrder) -ImGuiTabItem* ImGui::TabBarFindTabByOrder(ImGuiTabBar* tab_bar, int order) -{ - if (order < 0 || order >= tab_bar->Tabs.Size) - return NULL; - return &tab_bar->Tabs[order]; -} - -// FIXME: See references to #2304 in TODO.txt -ImGuiTabItem* ImGui::TabBarFindMostRecentlySelectedTabForActiveWindow(ImGuiTabBar* tab_bar) -{ - ImGuiTabItem* most_recently_selected_tab = NULL; - for (int tab_n = 0; tab_n < tab_bar->Tabs.Size; tab_n++) - { - ImGuiTabItem* tab = &tab_bar->Tabs[tab_n]; - if (most_recently_selected_tab == NULL || most_recently_selected_tab->LastFrameSelected < tab->LastFrameSelected) - if (tab->Window && tab->Window->WasActive) - most_recently_selected_tab = tab; - } - return most_recently_selected_tab; -} - -ImGuiTabItem* ImGui::TabBarGetCurrentTab(ImGuiTabBar* tab_bar) -{ - if (tab_bar->LastTabItemIdx <= 0 || tab_bar->LastTabItemIdx >= tab_bar->Tabs.Size) - return NULL; - return &tab_bar->Tabs[tab_bar->LastTabItemIdx]; -} - -const char* ImGui::TabBarGetTabName(ImGuiTabBar* tab_bar, ImGuiTabItem* tab) -{ - if (tab->Window) - return tab->Window->Name; - if (tab->NameOffset == -1) - return "N/A"; - IM_ASSERT(tab->NameOffset < tab_bar->TabsNames.Buf.Size); - return tab_bar->TabsNames.Buf.Data + tab->NameOffset; -} - -// The purpose of this call is to register tab in advance so we can control their order at the time they appear. -// Otherwise calling this is unnecessary as tabs are appending as needed by the BeginTabItem() function. -void ImGui::TabBarAddTab(ImGuiTabBar* tab_bar, ImGuiTabItemFlags tab_flags, ImGuiWindow* window) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(TabBarFindTabByID(tab_bar, window->TabId) == NULL); - IM_ASSERT(g.CurrentTabBar != tab_bar); // Can't work while the tab bar is active as our tab doesn't have an X offset yet, in theory we could/should test something like (tab_bar->CurrFrameVisible < g.FrameCount) but we'd need to solve why triggers the commented early-out assert in BeginTabBarEx() (probably dock node going from implicit to explicit in same frame) - - if (!window->HasCloseButton) - tab_flags |= ImGuiTabItemFlags_NoCloseButton; // Set _NoCloseButton immediately because it will be used for first-frame width calculation. - - ImGuiTabItem new_tab; - new_tab.ID = window->TabId; - new_tab.Flags = tab_flags; - new_tab.LastFrameVisible = tab_bar->CurrFrameVisible; // Required so BeginTabBar() doesn't ditch the tab - if (new_tab.LastFrameVisible == -1) - new_tab.LastFrameVisible = g.FrameCount - 1; - new_tab.Window = window; // Required so tab bar layout can compute the tab width before tab submission - tab_bar->Tabs.push_back(new_tab); -} - -// The *TabId fields are already set by the docking system _before_ the actual TabItem was created, so we clear them regardless. -void ImGui::TabBarRemoveTab(ImGuiTabBar* tab_bar, ImGuiID tab_id) -{ - if (ImGuiTabItem* tab = TabBarFindTabByID(tab_bar, tab_id)) - tab_bar->Tabs.erase(tab); - if (tab_bar->VisibleTabId == tab_id) { tab_bar->VisibleTabId = 0; } - if (tab_bar->SelectedTabId == tab_id) { tab_bar->SelectedTabId = 0; } - if (tab_bar->NextSelectedTabId == tab_id) { tab_bar->NextSelectedTabId = 0; } -} - -// Called on manual closure attempt -void ImGui::TabBarCloseTab(ImGuiTabBar* tab_bar, ImGuiTabItem* tab) -{ - if (tab->Flags & ImGuiTabItemFlags_Button) - return; // A button appended with TabItemButton(). - - if (!(tab->Flags & ImGuiTabItemFlags_UnsavedDocument)) - { - // This will remove a frame of lag for selecting another tab on closure. - // However we don't run it in the case where the 'Unsaved' flag is set, so user gets a chance to fully undo the closure - tab->WantClose = true; - if (tab_bar->VisibleTabId == tab->ID) - { - tab->LastFrameVisible = -1; - tab_bar->SelectedTabId = tab_bar->NextSelectedTabId = 0; - } - } - else - { - // Actually select before expecting closure attempt (on an UnsavedDocument tab user is expect to e.g. show a popup) - if (tab_bar->VisibleTabId != tab->ID) - TabBarQueueFocus(tab_bar, tab); - } -} - -static float ImGui::TabBarScrollClamp(ImGuiTabBar* tab_bar, float scrolling) -{ - scrolling = ImMin(scrolling, tab_bar->WidthAllTabs - tab_bar->BarRect.GetWidth()); - return ImMax(scrolling, 0.0f); -} - -// Note: we may scroll to tab that are not selected! e.g. using keyboard arrow keys -static void ImGui::TabBarScrollToTab(ImGuiTabBar* tab_bar, ImGuiID tab_id, ImGuiTabBarSection* sections) -{ - ImGuiTabItem* tab = TabBarFindTabByID(tab_bar, tab_id); - if (tab == NULL) - return; - if (tab->Flags & ImGuiTabItemFlags_SectionMask_) - return; - - ImGuiContext& g = *GImGui; - float margin = g.FontSize * 1.0f; // When to scroll to make Tab N+1 visible always make a bit of N visible to suggest more scrolling area (since we don't have a scrollbar) - int order = TabBarGetTabOrder(tab_bar, tab); - - // Scrolling happens only in the central section (leading/trailing sections are not scrolling) - float scrollable_width = TabBarCalcScrollableWidth(tab_bar, sections); - - // We make all tabs positions all relative Sections[0].Width to make code simpler - float tab_x1 = tab->Offset - sections[0].Width + (order > sections[0].TabCount - 1 ? -margin : 0.0f); - float tab_x2 = tab->Offset - sections[0].Width + tab->Width + (order + 1 < tab_bar->Tabs.Size - sections[2].TabCount ? margin : 1.0f); - tab_bar->ScrollingTargetDistToVisibility = 0.0f; - if (tab_bar->ScrollingTarget > tab_x1 || (tab_x2 - tab_x1 >= scrollable_width)) - { - // Scroll to the left - tab_bar->ScrollingTargetDistToVisibility = ImMax(tab_bar->ScrollingAnim - tab_x2, 0.0f); - tab_bar->ScrollingTarget = tab_x1; - } - else if (tab_bar->ScrollingTarget < tab_x2 - scrollable_width) - { - // Scroll to the right - tab_bar->ScrollingTargetDistToVisibility = ImMax((tab_x1 - scrollable_width) - tab_bar->ScrollingAnim, 0.0f); - tab_bar->ScrollingTarget = tab_x2 - scrollable_width; - } -} - -void ImGui::TabBarQueueFocus(ImGuiTabBar* tab_bar, ImGuiTabItem* tab) -{ - tab_bar->NextSelectedTabId = tab->ID; -} - -void ImGui::TabBarQueueReorder(ImGuiTabBar* tab_bar, ImGuiTabItem* tab, int offset) -{ - IM_ASSERT(offset != 0); - IM_ASSERT(tab_bar->ReorderRequestTabId == 0); - tab_bar->ReorderRequestTabId = tab->ID; - tab_bar->ReorderRequestOffset = (ImS16)offset; -} - -void ImGui::TabBarQueueReorderFromMousePos(ImGuiTabBar* tab_bar, ImGuiTabItem* src_tab, ImVec2 mouse_pos) -{ - ImGuiContext& g = *GImGui; - IM_ASSERT(tab_bar->ReorderRequestTabId == 0); - if ((tab_bar->Flags & ImGuiTabBarFlags_Reorderable) == 0) - return; - - const bool is_central_section = (src_tab->Flags & ImGuiTabItemFlags_SectionMask_) == 0; - const float bar_offset = tab_bar->BarRect.Min.x - (is_central_section ? tab_bar->ScrollingTarget : 0); - - // Count number of contiguous tabs we are crossing over - const int dir = (bar_offset + src_tab->Offset) > mouse_pos.x ? -1 : +1; - const int src_idx = tab_bar->Tabs.index_from_ptr(src_tab); - int dst_idx = src_idx; - for (int i = src_idx; i >= 0 && i < tab_bar->Tabs.Size; i += dir) - { - // Reordered tabs must share the same section - const ImGuiTabItem* dst_tab = &tab_bar->Tabs[i]; - if (dst_tab->Flags & ImGuiTabItemFlags_NoReorder) - break; - if ((dst_tab->Flags & ImGuiTabItemFlags_SectionMask_) != (src_tab->Flags & ImGuiTabItemFlags_SectionMask_)) - break; - dst_idx = i; - - // Include spacing after tab, so when mouse cursor is between tabs we would not continue checking further tabs that are not hovered. - const float x1 = bar_offset + dst_tab->Offset - g.Style.ItemInnerSpacing.x; - const float x2 = bar_offset + dst_tab->Offset + dst_tab->Width + g.Style.ItemInnerSpacing.x; - //GetForegroundDrawList()->AddRect(ImVec2(x1, tab_bar->BarRect.Min.y), ImVec2(x2, tab_bar->BarRect.Max.y), IM_COL32(255, 0, 0, 255)); - if ((dir < 0 && mouse_pos.x > x1) || (dir > 0 && mouse_pos.x < x2)) - break; - } - - if (dst_idx != src_idx) - TabBarQueueReorder(tab_bar, src_tab, dst_idx - src_idx); -} - -bool ImGui::TabBarProcessReorder(ImGuiTabBar* tab_bar) -{ - ImGuiTabItem* tab1 = TabBarFindTabByID(tab_bar, tab_bar->ReorderRequestTabId); - if (tab1 == NULL || (tab1->Flags & ImGuiTabItemFlags_NoReorder)) - return false; - - //IM_ASSERT(tab_bar->Flags & ImGuiTabBarFlags_Reorderable); // <- this may happen when using debug tools - int tab2_order = TabBarGetTabOrder(tab_bar, tab1) + tab_bar->ReorderRequestOffset; - if (tab2_order < 0 || tab2_order >= tab_bar->Tabs.Size) - return false; - - // Reordered tabs must share the same section - // (Note: TabBarQueueReorderFromMousePos() also has a similar test but since we allow direct calls to TabBarQueueReorder() we do it here too) - ImGuiTabItem* tab2 = &tab_bar->Tabs[tab2_order]; - if (tab2->Flags & ImGuiTabItemFlags_NoReorder) - return false; - if ((tab1->Flags & ImGuiTabItemFlags_SectionMask_) != (tab2->Flags & ImGuiTabItemFlags_SectionMask_)) - return false; - - ImGuiTabItem item_tmp = *tab1; - ImGuiTabItem* src_tab = (tab_bar->ReorderRequestOffset > 0) ? tab1 + 1 : tab2; - ImGuiTabItem* dst_tab = (tab_bar->ReorderRequestOffset > 0) ? tab1 : tab2 + 1; - const int move_count = (tab_bar->ReorderRequestOffset > 0) ? tab_bar->ReorderRequestOffset : -tab_bar->ReorderRequestOffset; - memmove(dst_tab, src_tab, move_count * sizeof(ImGuiTabItem)); - *tab2 = item_tmp; - - if (tab_bar->Flags & ImGuiTabBarFlags_SaveSettings) - MarkIniSettingsDirty(); - return true; -} - -static ImGuiTabItem* ImGui::TabBarScrollingButtons(ImGuiTabBar* tab_bar) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - - const ImVec2 arrow_button_size(g.FontSize - 2.0f, g.FontSize + g.Style.FramePadding.y * 2.0f); - const float scrolling_buttons_width = arrow_button_size.x * 2.0f; - - const ImVec2 backup_cursor_pos = window->DC.CursorPos; - //window->DrawList->AddRect(ImVec2(tab_bar->BarRect.Max.x - scrolling_buttons_width, tab_bar->BarRect.Min.y), ImVec2(tab_bar->BarRect.Max.x, tab_bar->BarRect.Max.y), IM_COL32(255,0,0,255)); - - int select_dir = 0; - ImVec4 arrow_col = g.Style.Colors[ImGuiCol_Text]; - arrow_col.w *= 0.5f; - - PushStyleColor(ImGuiCol_Text, arrow_col); - PushStyleColor(ImGuiCol_Button, ImVec4(0, 0, 0, 0)); - const float backup_repeat_delay = g.IO.KeyRepeatDelay; - const float backup_repeat_rate = g.IO.KeyRepeatRate; - g.IO.KeyRepeatDelay = 0.250f; - g.IO.KeyRepeatRate = 0.200f; - float x = ImMax(tab_bar->BarRect.Min.x, tab_bar->BarRect.Max.x - scrolling_buttons_width); - window->DC.CursorPos = ImVec2(x, tab_bar->BarRect.Min.y); - if (ArrowButtonEx("##<", ImGuiDir_Left, arrow_button_size, ImGuiButtonFlags_PressedOnClick | ImGuiButtonFlags_Repeat)) - select_dir = -1; - window->DC.CursorPos = ImVec2(x + arrow_button_size.x, tab_bar->BarRect.Min.y); - if (ArrowButtonEx("##>", ImGuiDir_Right, arrow_button_size, ImGuiButtonFlags_PressedOnClick | ImGuiButtonFlags_Repeat)) - select_dir = +1; - PopStyleColor(2); - g.IO.KeyRepeatRate = backup_repeat_rate; - g.IO.KeyRepeatDelay = backup_repeat_delay; - - ImGuiTabItem* tab_to_scroll_to = NULL; - if (select_dir != 0) - if (ImGuiTabItem* tab_item = TabBarFindTabByID(tab_bar, tab_bar->SelectedTabId)) - { - int selected_order = TabBarGetTabOrder(tab_bar, tab_item); - int target_order = selected_order + select_dir; - - // Skip tab item buttons until another tab item is found or end is reached - while (tab_to_scroll_to == NULL) - { - // If we are at the end of the list, still scroll to make our tab visible - tab_to_scroll_to = &tab_bar->Tabs[(target_order >= 0 && target_order < tab_bar->Tabs.Size) ? target_order : selected_order]; - - // Cross through buttons - // (even if first/last item is a button, return it so we can update the scroll) - if (tab_to_scroll_to->Flags & ImGuiTabItemFlags_Button) - { - target_order += select_dir; - selected_order += select_dir; - tab_to_scroll_to = (target_order < 0 || target_order >= tab_bar->Tabs.Size) ? tab_to_scroll_to : NULL; - } - } - } - window->DC.CursorPos = backup_cursor_pos; - tab_bar->BarRect.Max.x -= scrolling_buttons_width + 1.0f; - - return tab_to_scroll_to; -} - -static ImGuiTabItem* ImGui::TabBarTabListPopupButton(ImGuiTabBar* tab_bar) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - - // We use g.Style.FramePadding.y to match the square ArrowButton size - const float tab_list_popup_button_width = g.FontSize + g.Style.FramePadding.y; - const ImVec2 backup_cursor_pos = window->DC.CursorPos; - window->DC.CursorPos = ImVec2(tab_bar->BarRect.Min.x - g.Style.FramePadding.y, tab_bar->BarRect.Min.y); - tab_bar->BarRect.Min.x += tab_list_popup_button_width; - - ImVec4 arrow_col = g.Style.Colors[ImGuiCol_Text]; - arrow_col.w *= 0.5f; - PushStyleColor(ImGuiCol_Text, arrow_col); - PushStyleColor(ImGuiCol_Button, ImVec4(0, 0, 0, 0)); - bool open = BeginCombo("##v", NULL, ImGuiComboFlags_NoPreview | ImGuiComboFlags_HeightLargest); - PopStyleColor(2); - - ImGuiTabItem* tab_to_select = NULL; - if (open) - { - for (int tab_n = 0; tab_n < tab_bar->Tabs.Size; tab_n++) - { - ImGuiTabItem* tab = &tab_bar->Tabs[tab_n]; - if (tab->Flags & ImGuiTabItemFlags_Button) - continue; - - const char* tab_name = TabBarGetTabName(tab_bar, tab); - if (Selectable(tab_name, tab_bar->SelectedTabId == tab->ID)) - tab_to_select = tab; - } - EndCombo(); - } - - window->DC.CursorPos = backup_cursor_pos; - return tab_to_select; -} - -//------------------------------------------------------------------------- -// [SECTION] Widgets: BeginTabItem, EndTabItem, etc. -//------------------------------------------------------------------------- -// - BeginTabItem() -// - EndTabItem() -// - TabItemButton() -// - TabItemEx() [Internal] -// - SetTabItemClosed() -// - TabItemCalcSize() [Internal] -// - TabItemBackground() [Internal] -// - TabItemLabelAndCloseButton() [Internal] -//------------------------------------------------------------------------- - -bool ImGui::BeginTabItem(const char* label, bool* p_open, ImGuiTabItemFlags flags) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - if (window->SkipItems) - return false; - - ImGuiTabBar* tab_bar = g.CurrentTabBar; - if (tab_bar == NULL) - { - IM_ASSERT_USER_ERROR(tab_bar, "Needs to be called between BeginTabBar() and EndTabBar()!"); - return false; - } - IM_ASSERT((flags & ImGuiTabItemFlags_Button) == 0); // BeginTabItem() Can't be used with button flags, use TabItemButton() instead! - - bool ret = TabItemEx(tab_bar, label, p_open, flags, NULL); - if (ret && !(flags & ImGuiTabItemFlags_NoPushId)) - { - ImGuiTabItem* tab = &tab_bar->Tabs[tab_bar->LastTabItemIdx]; - PushOverrideID(tab->ID); // We already hashed 'label' so push into the ID stack directly instead of doing another hash through PushID(label) - } - return ret; -} - -void ImGui::EndTabItem() -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - if (window->SkipItems) - return; - - ImGuiTabBar* tab_bar = g.CurrentTabBar; - if (tab_bar == NULL) - { - IM_ASSERT_USER_ERROR(tab_bar != NULL, "Needs to be called between BeginTabBar() and EndTabBar()!"); - return; - } - IM_ASSERT(tab_bar->LastTabItemIdx >= 0); - ImGuiTabItem* tab = &tab_bar->Tabs[tab_bar->LastTabItemIdx]; - if (!(tab->Flags & ImGuiTabItemFlags_NoPushId)) - PopID(); -} - -bool ImGui::TabItemButton(const char* label, ImGuiTabItemFlags flags) -{ - ImGuiContext& g = *GImGui; - ImGuiWindow* window = g.CurrentWindow; - if (window->SkipItems) - return false; - - ImGuiTabBar* tab_bar = g.CurrentTabBar; - if (tab_bar == NULL) - { - IM_ASSERT_USER_ERROR(tab_bar != NULL, "Needs to be called between BeginTabBar() and EndTabBar()!"); - return false; - } - return TabItemEx(tab_bar, label, NULL, flags | ImGuiTabItemFlags_Button | ImGuiTabItemFlags_NoReorder, NULL); -} - -bool ImGui::TabItemEx(ImGuiTabBar* tab_bar, const char* label, bool* p_open, ImGuiTabItemFlags flags, ImGuiWindow* docked_window) -{ - // Layout whole tab bar if not already done - ImGuiContext& g = *GImGui; - if (tab_bar->WantLayout) - { - ImGuiNextItemData backup_next_item_data = g.NextItemData; - TabBarLayout(tab_bar); - g.NextItemData = backup_next_item_data; - } - ImGuiWindow* window = g.CurrentWindow; - if (window->SkipItems) - return false; - - const ImGuiStyle& style = g.Style; - const ImGuiID id = TabBarCalcTabID(tab_bar, label, docked_window); - - // If the user called us with *p_open == false, we early out and don't render. - // We make a call to ItemAdd() so that attempts to use a contextual popup menu with an implicit ID won't use an older ID. - IMGUI_TEST_ENGINE_ITEM_INFO(id, label, g.LastItemData.StatusFlags); - if (p_open && !*p_open) - { - ItemAdd(ImRect(), id, NULL, ImGuiItemFlags_NoNav); - return false; - } - - IM_ASSERT(!p_open || !(flags & ImGuiTabItemFlags_Button)); - IM_ASSERT((flags & (ImGuiTabItemFlags_Leading | ImGuiTabItemFlags_Trailing)) != (ImGuiTabItemFlags_Leading | ImGuiTabItemFlags_Trailing)); // Can't use both Leading and Trailing - - // Store into ImGuiTabItemFlags_NoCloseButton, also honor ImGuiTabItemFlags_NoCloseButton passed by user (although not documented) - if (flags & ImGuiTabItemFlags_NoCloseButton) - p_open = NULL; - else if (p_open == NULL) - flags |= ImGuiTabItemFlags_NoCloseButton; - - // Acquire tab data - ImGuiTabItem* tab = TabBarFindTabByID(tab_bar, id); - bool tab_is_new = false; - if (tab == NULL) - { - tab_bar->Tabs.push_back(ImGuiTabItem()); - tab = &tab_bar->Tabs.back(); - tab->ID = id; - tab_bar->TabsAddedNew = tab_is_new = true; - } - tab_bar->LastTabItemIdx = (ImS16)tab_bar->Tabs.index_from_ptr(tab); - - // Calculate tab contents size - ImVec2 size = TabItemCalcSize(label, (p_open != NULL) || (flags & ImGuiTabItemFlags_UnsavedDocument)); - tab->RequestedWidth = -1.0f; - if (g.NextItemData.Flags & ImGuiNextItemDataFlags_HasWidth) - size.x = tab->RequestedWidth = g.NextItemData.Width; - if (tab_is_new) - tab->Width = ImMax(1.0f, size.x); - tab->ContentWidth = size.x; - tab->BeginOrder = tab_bar->TabsActiveCount++; - - const bool tab_bar_appearing = (tab_bar->PrevFrameVisible + 1 < g.FrameCount); - const bool tab_bar_focused = (tab_bar->Flags & ImGuiTabBarFlags_IsFocused) != 0; - const bool tab_appearing = (tab->LastFrameVisible + 1 < g.FrameCount); - const bool tab_just_unsaved = (flags & ImGuiTabItemFlags_UnsavedDocument) && !(tab->Flags & ImGuiTabItemFlags_UnsavedDocument); - const bool is_tab_button = (flags & ImGuiTabItemFlags_Button) != 0; - tab->LastFrameVisible = g.FrameCount; - tab->Flags = flags; - tab->Window = docked_window; - - // Append name _WITH_ the zero-terminator - // (regular tabs are permitted in a DockNode tab bar, but window tabs not permitted in a non-DockNode tab bar) - if (docked_window != NULL) - { - IM_ASSERT(tab_bar->Flags & ImGuiTabBarFlags_DockNode); - tab->NameOffset = -1; - } - else - { - tab->NameOffset = (ImS32)tab_bar->TabsNames.size(); - tab_bar->TabsNames.append(label, label + strlen(label) + 1); - } - - // Update selected tab - if (!is_tab_button) - { - if (tab_appearing && (tab_bar->Flags & ImGuiTabBarFlags_AutoSelectNewTabs) && tab_bar->NextSelectedTabId == 0) - if (!tab_bar_appearing || tab_bar->SelectedTabId == 0) - TabBarQueueFocus(tab_bar, tab); // New tabs gets activated - if ((flags & ImGuiTabItemFlags_SetSelected) && (tab_bar->SelectedTabId != id)) // _SetSelected can only be passed on explicit tab bar - TabBarQueueFocus(tab_bar, tab); - } - - // Lock visibility - // (Note: tab_contents_visible != tab_selected... because CTRL+TAB operations may preview some tabs without selecting them!) - bool tab_contents_visible = (tab_bar->VisibleTabId == id); - if (tab_contents_visible) - tab_bar->VisibleTabWasSubmitted = true; - - // On the very first frame of a tab bar we let first tab contents be visible to minimize appearing glitches - if (!tab_contents_visible && tab_bar->SelectedTabId == 0 && tab_bar_appearing && docked_window == NULL) - if (tab_bar->Tabs.Size == 1 && !(tab_bar->Flags & ImGuiTabBarFlags_AutoSelectNewTabs)) - tab_contents_visible = true; - - // Note that tab_is_new is not necessarily the same as tab_appearing! When a tab bar stops being submitted - // and then gets submitted again, the tabs will have 'tab_appearing=true' but 'tab_is_new=false'. - if (tab_appearing && (!tab_bar_appearing || tab_is_new)) - { - ItemAdd(ImRect(), id, NULL, ImGuiItemFlags_NoNav); - if (is_tab_button) - return false; - return tab_contents_visible; - } - - if (tab_bar->SelectedTabId == id) - tab->LastFrameSelected = g.FrameCount; - - // Backup current layout position - const ImVec2 backup_main_cursor_pos = window->DC.CursorPos; - - // Layout - const bool is_central_section = (tab->Flags & ImGuiTabItemFlags_SectionMask_) == 0; - size.x = tab->Width; - if (is_central_section) - window->DC.CursorPos = tab_bar->BarRect.Min + ImVec2(IM_TRUNC(tab->Offset - tab_bar->ScrollingAnim), 0.0f); - else - window->DC.CursorPos = tab_bar->BarRect.Min + ImVec2(tab->Offset, 0.0f); - ImVec2 pos = window->DC.CursorPos; - ImRect bb(pos, pos + size); - - // We don't have CPU clipping primitives to clip the CloseButton (until it becomes a texture), so need to add an extra draw call (temporary in the case of vertical animation) - const bool want_clip_rect = is_central_section && (bb.Min.x < tab_bar->ScrollingRectMinX || bb.Max.x > tab_bar->ScrollingRectMaxX); - if (want_clip_rect) - PushClipRect(ImVec2(ImMax(bb.Min.x, tab_bar->ScrollingRectMinX), bb.Min.y - 1), ImVec2(tab_bar->ScrollingRectMaxX, bb.Max.y), true); - - ImVec2 backup_cursor_max_pos = window->DC.CursorMaxPos; - ItemSize(bb.GetSize(), style.FramePadding.y); - window->DC.CursorMaxPos = backup_cursor_max_pos; - - if (!ItemAdd(bb, id)) - { - if (want_clip_rect) - PopClipRect(); - window->DC.CursorPos = backup_main_cursor_pos; - return tab_contents_visible; - } - - // Click to Select a tab - ImGuiButtonFlags button_flags = ((is_tab_button ? ImGuiButtonFlags_PressedOnClickRelease : ImGuiButtonFlags_PressedOnClick) | ImGuiButtonFlags_AllowOverlap); - if (g.DragDropActive && !g.DragDropPayload.IsDataType(IMGUI_PAYLOAD_TYPE_WINDOW)) // FIXME: May be an opt-in property of the payload to disable this - button_flags |= ImGuiButtonFlags_PressedOnDragDropHold; - bool hovered, held; - bool pressed = ButtonBehavior(bb, id, &hovered, &held, button_flags); - if (pressed && !is_tab_button) - TabBarQueueFocus(tab_bar, tab); - - // Transfer active id window so the active id is not owned by the dock host (as StartMouseMovingWindow() - // will only do it on the drag). This allows FocusWindow() to be more conservative in how it clears active id. - if (held && docked_window && g.ActiveId == id && g.ActiveIdIsJustActivated) - g.ActiveIdWindow = docked_window; - - // Drag and drop a single floating window node moves it - ImGuiDockNode* node = docked_window ? docked_window->DockNode : NULL; - const bool single_floating_window_node = node && node->IsFloatingNode() && (node->Windows.Size == 1); - if (held && single_floating_window_node && IsMouseDragging(0, 0.0f)) - { - // Move - StartMouseMovingWindow(docked_window); - } - else if (held && !tab_appearing && IsMouseDragging(0)) - { - // Drag and drop: re-order tabs - int drag_dir = 0; - float drag_distance_from_edge_x = 0.0f; - if (!g.DragDropActive && ((tab_bar->Flags & ImGuiTabBarFlags_Reorderable) || (docked_window != NULL))) - { - // While moving a tab it will jump on the other side of the mouse, so we also test for MouseDelta.x - if (g.IO.MouseDelta.x < 0.0f && g.IO.MousePos.x < bb.Min.x) - { - drag_dir = -1; - drag_distance_from_edge_x = bb.Min.x - g.IO.MousePos.x; - TabBarQueueReorderFromMousePos(tab_bar, tab, g.IO.MousePos); - } - else if (g.IO.MouseDelta.x > 0.0f && g.IO.MousePos.x > bb.Max.x) - { - drag_dir = +1; - drag_distance_from_edge_x = g.IO.MousePos.x - bb.Max.x; - TabBarQueueReorderFromMousePos(tab_bar, tab, g.IO.MousePos); - } - } - - // Extract a Dockable window out of it's tab bar - const bool can_undock = docked_window != NULL && !(docked_window->Flags & ImGuiWindowFlags_NoMove) && !(node->MergedFlags & ImGuiDockNodeFlags_NoUndocking); - if (can_undock) - { - // We use a variable threshold to distinguish dragging tabs within a tab bar and extracting them out of the tab bar - bool undocking_tab = (g.DragDropActive && g.DragDropPayload.SourceId == id); - if (!undocking_tab) //&& (!g.IO.ConfigDockingWithShift || g.IO.KeyShift) - { - float threshold_base = g.FontSize; - float threshold_x = (threshold_base * 2.2f); - float threshold_y = (threshold_base * 1.5f) + ImClamp((ImFabs(g.IO.MouseDragMaxDistanceAbs[0].x) - threshold_base * 2.0f) * 0.20f, 0.0f, threshold_base * 4.0f); - //GetForegroundDrawList()->AddRect(ImVec2(bb.Min.x - threshold_x, bb.Min.y - threshold_y), ImVec2(bb.Max.x + threshold_x, bb.Max.y + threshold_y), IM_COL32_WHITE); // [DEBUG] - - float distance_from_edge_y = ImMax(bb.Min.y - g.IO.MousePos.y, g.IO.MousePos.y - bb.Max.y); - if (distance_from_edge_y >= threshold_y) - undocking_tab = true; - if (drag_distance_from_edge_x > threshold_x) - if ((drag_dir < 0 && TabBarGetTabOrder(tab_bar, tab) == 0) || (drag_dir > 0 && TabBarGetTabOrder(tab_bar, tab) == tab_bar->Tabs.Size - 1)) - undocking_tab = true; - } - - if (undocking_tab) - { - // Undock - // FIXME: refactor to share more code with e.g. StartMouseMovingWindow - DockContextQueueUndockWindow(&g, docked_window); - g.MovingWindow = docked_window; - SetActiveID(g.MovingWindow->MoveId, g.MovingWindow); - g.ActiveIdClickOffset -= g.MovingWindow->Pos - bb.Min; - g.ActiveIdNoClearOnFocusLoss = true; - SetActiveIdUsingAllKeyboardKeys(); - } - } - } - -#if 0 - if (hovered && g.HoveredIdNotActiveTimer > TOOLTIP_DELAY && bb.GetWidth() < tab->ContentWidth) - { - // Enlarge tab display when hovering - bb.Max.x = bb.Min.x + IM_TRUNC(ImLerp(bb.GetWidth(), tab->ContentWidth, ImSaturate((g.HoveredIdNotActiveTimer - 0.40f) * 6.0f))); - display_draw_list = GetForegroundDrawList(window); - TabItemBackground(display_draw_list, bb, flags, GetColorU32(ImGuiCol_TitleBgActive)); - } -#endif - - // Render tab shape - ImDrawList* display_draw_list = window->DrawList; - const ImU32 tab_col = GetColorU32((held || hovered) ? ImGuiCol_TabHovered : tab_contents_visible ? (tab_bar_focused ? ImGuiCol_TabActive : ImGuiCol_TabUnfocusedActive) : (tab_bar_focused ? ImGuiCol_Tab : ImGuiCol_TabUnfocused)); - TabItemBackground(display_draw_list, bb, flags, tab_col); - RenderNavHighlight(bb, id); - - // Select with right mouse button. This is so the common idiom for context menu automatically highlight the current widget. - const bool hovered_unblocked = IsItemHovered(ImGuiHoveredFlags_AllowWhenBlockedByPopup); - if (hovered_unblocked && (IsMouseClicked(1) || IsMouseReleased(1)) && !is_tab_button) - TabBarQueueFocus(tab_bar, tab); - - if (tab_bar->Flags & ImGuiTabBarFlags_NoCloseWithMiddleMouseButton) - flags |= ImGuiTabItemFlags_NoCloseWithMiddleMouseButton; - - // Render tab label, process close button - const ImGuiID close_button_id = p_open ? GetIDWithSeed("#CLOSE", NULL, docked_window ? docked_window->ID : id) : 0; - bool just_closed; - bool text_clipped; - TabItemLabelAndCloseButton(display_draw_list, bb, tab_just_unsaved ? (flags & ~ImGuiTabItemFlags_UnsavedDocument) : flags, tab_bar->FramePadding, label, id, close_button_id, tab_contents_visible, &just_closed, &text_clipped); - if (just_closed && p_open != NULL) - { - *p_open = false; - TabBarCloseTab(tab_bar, tab); - } - - // Forward Hovered state so IsItemHovered() after Begin() can work (even though we are technically hovering our parent) - // That state is copied to window->DockTabItemStatusFlags by our caller. - if (docked_window && (hovered || g.HoveredId == close_button_id)) - g.LastItemData.StatusFlags |= ImGuiItemStatusFlags_HoveredWindow; - - // Restore main window position so user can draw there - if (want_clip_rect) - PopClipRect(); - window->DC.CursorPos = backup_main_cursor_pos; - - // Tooltip - // (Won't work over the close button because ItemOverlap systems messes up with HoveredIdTimer-> seems ok) - // (We test IsItemHovered() to discard e.g. when another item is active or drag and drop over the tab bar, which g.HoveredId ignores) - // FIXME: This is a mess. - // FIXME: We may want disabled tab to still display the tooltip? - if (text_clipped && g.HoveredId == id && !held) - if (!(tab_bar->Flags & ImGuiTabBarFlags_NoTooltip) && !(tab->Flags & ImGuiTabItemFlags_NoTooltip)) - SetItemTooltip("%.*s", (int)(FindRenderedTextEnd(label) - label), label); - - IM_ASSERT(!is_tab_button || !(tab_bar->SelectedTabId == tab->ID && is_tab_button)); // TabItemButton should not be selected - if (is_tab_button) - return pressed; - return tab_contents_visible; -} - -// [Public] This is call is 100% optional but it allows to remove some one-frame glitches when a tab has been unexpectedly removed. -// To use it to need to call the function SetTabItemClosed() between BeginTabBar() and EndTabBar(). -// Tabs closed by the close button will automatically be flagged to avoid this issue. -void ImGui::SetTabItemClosed(const char* label) -{ - ImGuiContext& g = *GImGui; - bool is_within_manual_tab_bar = g.CurrentTabBar && !(g.CurrentTabBar->Flags & ImGuiTabBarFlags_DockNode); - if (is_within_manual_tab_bar) - { - ImGuiTabBar* tab_bar = g.CurrentTabBar; - ImGuiID tab_id = TabBarCalcTabID(tab_bar, label, NULL); - if (ImGuiTabItem* tab = TabBarFindTabByID(tab_bar, tab_id)) - tab->WantClose = true; // Will be processed by next call to TabBarLayout() - } - else if (ImGuiWindow* window = FindWindowByName(label)) - { - if (window->DockIsActive) - if (ImGuiDockNode* node = window->DockNode) - { - ImGuiID tab_id = TabBarCalcTabID(node->TabBar, label, window); - TabBarRemoveTab(node->TabBar, tab_id); - window->DockTabWantClose = true; - } - } -} - -ImVec2 ImGui::TabItemCalcSize(const char* label, bool has_close_button_or_unsaved_marker) -{ - ImGuiContext& g = *GImGui; - ImVec2 label_size = CalcTextSize(label, NULL, true); - ImVec2 size = ImVec2(label_size.x + g.Style.FramePadding.x, label_size.y + g.Style.FramePadding.y * 2.0f); - if (has_close_button_or_unsaved_marker) - size.x += g.Style.FramePadding.x + (g.Style.ItemInnerSpacing.x + g.FontSize); // We use Y intentionally to fit the close button circle. - else - size.x += g.Style.FramePadding.x + 1.0f; - return ImVec2(ImMin(size.x, TabBarCalcMaxTabWidth()), size.y); -} - -ImVec2 ImGui::TabItemCalcSize(ImGuiWindow* window) -{ - return TabItemCalcSize(window->Name, window->HasCloseButton || (window->Flags & ImGuiWindowFlags_UnsavedDocument)); -} - -void ImGui::TabItemBackground(ImDrawList* draw_list, const ImRect& bb, ImGuiTabItemFlags flags, ImU32 col) -{ - // While rendering tabs, we trim 1 pixel off the top of our bounding box so they can fit within a regular frame height while looking "detached" from it. - ImGuiContext& g = *GImGui; - const float width = bb.GetWidth(); - IM_UNUSED(flags); - IM_ASSERT(width > 0.0f); - const float rounding = ImMax(0.0f, ImMin((flags & ImGuiTabItemFlags_Button) ? g.Style.FrameRounding : g.Style.TabRounding, width * 0.5f - 1.0f)); - const float y1 = bb.Min.y + 1.0f; - const float y2 = bb.Max.y - g.Style.TabBarBorderSize; - draw_list->PathLineTo(ImVec2(bb.Min.x, y2)); - draw_list->PathArcToFast(ImVec2(bb.Min.x + rounding, y1 + rounding), rounding, 6, 9); - draw_list->PathArcToFast(ImVec2(bb.Max.x - rounding, y1 + rounding), rounding, 9, 12); - draw_list->PathLineTo(ImVec2(bb.Max.x, y2)); - draw_list->PathFillConvex(col); - if (g.Style.TabBorderSize > 0.0f) - { - draw_list->PathLineTo(ImVec2(bb.Min.x + 0.5f, y2)); - draw_list->PathArcToFast(ImVec2(bb.Min.x + rounding + 0.5f, y1 + rounding + 0.5f), rounding, 6, 9); - draw_list->PathArcToFast(ImVec2(bb.Max.x - rounding - 0.5f, y1 + rounding + 0.5f), rounding, 9, 12); - draw_list->PathLineTo(ImVec2(bb.Max.x - 0.5f, y2)); - draw_list->PathStroke(GetColorU32(ImGuiCol_Border), 0, g.Style.TabBorderSize); - } -} - -// Render text label (with custom clipping) + Unsaved Document marker + Close Button logic -// We tend to lock style.FramePadding for a given tab-bar, hence the 'frame_padding' parameter. -void ImGui::TabItemLabelAndCloseButton(ImDrawList* draw_list, const ImRect& bb, ImGuiTabItemFlags flags, ImVec2 frame_padding, const char* label, ImGuiID tab_id, ImGuiID close_button_id, bool is_contents_visible, bool* out_just_closed, bool* out_text_clipped) -{ - ImGuiContext& g = *GImGui; - ImVec2 label_size = CalcTextSize(label, NULL, true); - - if (out_just_closed) - *out_just_closed = false; - if (out_text_clipped) - *out_text_clipped = false; - - if (bb.GetWidth() <= 1.0f) - return; - - // In Style V2 we'll have full override of all colors per state (e.g. focused, selected) - // But right now if you want to alter text color of tabs this is what you need to do. -#if 0 - const float backup_alpha = g.Style.Alpha; - if (!is_contents_visible) - g.Style.Alpha *= 0.7f; -#endif - - // Render text label (with clipping + alpha gradient) + unsaved marker - ImRect text_pixel_clip_bb(bb.Min.x + frame_padding.x, bb.Min.y + frame_padding.y, bb.Max.x - frame_padding.x, bb.Max.y); - ImRect text_ellipsis_clip_bb = text_pixel_clip_bb; - - // Return clipped state ignoring the close button - if (out_text_clipped) - { - *out_text_clipped = (text_ellipsis_clip_bb.Min.x + label_size.x) > text_pixel_clip_bb.Max.x; - //draw_list->AddCircle(text_ellipsis_clip_bb.Min, 3.0f, *out_text_clipped ? IM_COL32(255, 0, 0, 255) : IM_COL32(0, 255, 0, 255)); - } - - const float button_sz = g.FontSize; - const ImVec2 button_pos(ImMax(bb.Min.x, bb.Max.x - frame_padding.x - button_sz), bb.Min.y + frame_padding.y); - - // Close Button & Unsaved Marker - // We are relying on a subtle and confusing distinction between 'hovered' and 'g.HoveredId' which happens because we are using ImGuiButtonFlags_AllowOverlapMode + SetItemAllowOverlap() - // 'hovered' will be true when hovering the Tab but NOT when hovering the close button - // 'g.HoveredId==id' will be true when hovering the Tab including when hovering the close button - // 'g.ActiveId==close_button_id' will be true when we are holding on the close button, in which case both hovered booleans are false - bool close_button_pressed = false; - bool close_button_visible = false; - if (close_button_id != 0) - if (is_contents_visible || bb.GetWidth() >= ImMax(button_sz, g.Style.TabMinWidthForCloseButton)) - if (g.HoveredId == tab_id || g.HoveredId == close_button_id || g.ActiveId == tab_id || g.ActiveId == close_button_id) - close_button_visible = true; - bool unsaved_marker_visible = (flags & ImGuiTabItemFlags_UnsavedDocument) != 0 && (button_pos.x + button_sz <= bb.Max.x); - - if (close_button_visible) - { - ImGuiLastItemData last_item_backup = g.LastItemData; - if (CloseButton(close_button_id, button_pos)) - close_button_pressed = true; - g.LastItemData = last_item_backup; - - // Close with middle mouse button - if (!(flags & ImGuiTabItemFlags_NoCloseWithMiddleMouseButton) && IsMouseClicked(2)) - close_button_pressed = true; - } - else if (unsaved_marker_visible) - { - const ImRect bullet_bb(button_pos, button_pos + ImVec2(button_sz, button_sz)); - RenderBullet(draw_list, bullet_bb.GetCenter(), GetColorU32(ImGuiCol_Text)); - } - - // This is all rather complicated - // (the main idea is that because the close button only appears on hover, we don't want it to alter the ellipsis position) - // FIXME: if FramePadding is noticeably large, ellipsis_max_x will be wrong here (e.g. #3497), maybe for consistency that parameter of RenderTextEllipsis() shouldn't exist.. - float ellipsis_max_x = close_button_visible ? text_pixel_clip_bb.Max.x : bb.Max.x - 1.0f; - if (close_button_visible || unsaved_marker_visible) - { - text_pixel_clip_bb.Max.x -= close_button_visible ? (button_sz) : (button_sz * 0.80f); - text_ellipsis_clip_bb.Max.x -= unsaved_marker_visible ? (button_sz * 0.80f) : 0.0f; - ellipsis_max_x = text_pixel_clip_bb.Max.x; - } - RenderTextEllipsis(draw_list, text_ellipsis_clip_bb.Min, text_ellipsis_clip_bb.Max, text_pixel_clip_bb.Max.x, ellipsis_max_x, label, NULL, &label_size); - -#if 0 - if (!is_contents_visible) - g.Style.Alpha = backup_alpha; -#endif - - if (out_just_closed) - *out_just_closed = close_button_pressed; -} - - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/imstb_rectpack.h b/app/jni/src/libultraship/extern/ImGui/imstb_rectpack.h deleted file mode 100644 index f6917e7..0000000 --- a/app/jni/src/libultraship/extern/ImGui/imstb_rectpack.h +++ /dev/null @@ -1,627 +0,0 @@ -// [DEAR IMGUI] -// This is a slightly modified version of stb_rect_pack.h 1.01. -// Grep for [DEAR IMGUI] to find the changes. -// -// stb_rect_pack.h - v1.01 - public domain - rectangle packing -// Sean Barrett 2014 -// -// Useful for e.g. packing rectangular textures into an atlas. -// Does not do rotation. -// -// Before #including, -// -// #define STB_RECT_PACK_IMPLEMENTATION -// -// in the file that you want to have the implementation. -// -// Not necessarily the awesomest packing method, but better than -// the totally naive one in stb_truetype (which is primarily what -// this is meant to replace). -// -// Has only had a few tests run, may have issues. -// -// More docs to come. -// -// No memory allocations; uses qsort() and assert() from stdlib. -// Can override those by defining STBRP_SORT and STBRP_ASSERT. -// -// This library currently uses the Skyline Bottom-Left algorithm. -// -// Please note: better rectangle packers are welcome! Please -// implement them to the same API, but with a different init -// function. -// -// Credits -// -// Library -// Sean Barrett -// Minor features -// Martins Mozeiko -// github:IntellectualKitty -// -// Bugfixes / warning fixes -// Jeremy Jaussaud -// Fabian Giesen -// -// Version history: -// -// 1.01 (2021-07-11) always use large rect mode, expose STBRP__MAXVAL in public section -// 1.00 (2019-02-25) avoid small space waste; gracefully fail too-wide rectangles -// 0.99 (2019-02-07) warning fixes -// 0.11 (2017-03-03) return packing success/fail result -// 0.10 (2016-10-25) remove cast-away-const to avoid warnings -// 0.09 (2016-08-27) fix compiler warnings -// 0.08 (2015-09-13) really fix bug with empty rects (w=0 or h=0) -// 0.07 (2015-09-13) fix bug with empty rects (w=0 or h=0) -// 0.06 (2015-04-15) added STBRP_SORT to allow replacing qsort -// 0.05: added STBRP_ASSERT to allow replacing assert -// 0.04: fixed minor bug in STBRP_LARGE_RECTS support -// 0.01: initial release -// -// LICENSE -// -// See end of file for license information. - -////////////////////////////////////////////////////////////////////////////// -// -// INCLUDE SECTION -// - -#ifndef STB_INCLUDE_STB_RECT_PACK_H -#define STB_INCLUDE_STB_RECT_PACK_H - -#define STB_RECT_PACK_VERSION 1 - -#ifdef STBRP_STATIC -#define STBRP_DEF static -#else -#define STBRP_DEF extern -#endif - -#ifdef __cplusplus -extern "C" { -#endif - -typedef struct stbrp_context stbrp_context; -typedef struct stbrp_node stbrp_node; -typedef struct stbrp_rect stbrp_rect; - -typedef int stbrp_coord; - -#define STBRP__MAXVAL 0x7fffffff -// Mostly for internal use, but this is the maximum supported coordinate value. - -STBRP_DEF int stbrp_pack_rects (stbrp_context *context, stbrp_rect *rects, int num_rects); -// Assign packed locations to rectangles. The rectangles are of type -// 'stbrp_rect' defined below, stored in the array 'rects', and there -// are 'num_rects' many of them. -// -// Rectangles which are successfully packed have the 'was_packed' flag -// set to a non-zero value and 'x' and 'y' store the minimum location -// on each axis (i.e. bottom-left in cartesian coordinates, top-left -// if you imagine y increasing downwards). Rectangles which do not fit -// have the 'was_packed' flag set to 0. -// -// You should not try to access the 'rects' array from another thread -// while this function is running, as the function temporarily reorders -// the array while it executes. -// -// To pack into another rectangle, you need to call stbrp_init_target -// again. To continue packing into the same rectangle, you can call -// this function again. Calling this multiple times with multiple rect -// arrays will probably produce worse packing results than calling it -// a single time with the full rectangle array, but the option is -// available. -// -// The function returns 1 if all of the rectangles were successfully -// packed and 0 otherwise. - -struct stbrp_rect -{ - // reserved for your use: - int id; - - // input: - stbrp_coord w, h; - - // output: - stbrp_coord x, y; - int was_packed; // non-zero if valid packing - -}; // 16 bytes, nominally - - -STBRP_DEF void stbrp_init_target (stbrp_context *context, int width, int height, stbrp_node *nodes, int num_nodes); -// Initialize a rectangle packer to: -// pack a rectangle that is 'width' by 'height' in dimensions -// using temporary storage provided by the array 'nodes', which is 'num_nodes' long -// -// You must call this function every time you start packing into a new target. -// -// There is no "shutdown" function. The 'nodes' memory must stay valid for -// the following stbrp_pack_rects() call (or calls), but can be freed after -// the call (or calls) finish. -// -// Note: to guarantee best results, either: -// 1. make sure 'num_nodes' >= 'width' -// or 2. call stbrp_allow_out_of_mem() defined below with 'allow_out_of_mem = 1' -// -// If you don't do either of the above things, widths will be quantized to multiples -// of small integers to guarantee the algorithm doesn't run out of temporary storage. -// -// If you do #2, then the non-quantized algorithm will be used, but the algorithm -// may run out of temporary storage and be unable to pack some rectangles. - -STBRP_DEF void stbrp_setup_allow_out_of_mem (stbrp_context *context, int allow_out_of_mem); -// Optionally call this function after init but before doing any packing to -// change the handling of the out-of-temp-memory scenario, described above. -// If you call init again, this will be reset to the default (false). - - -STBRP_DEF void stbrp_setup_heuristic (stbrp_context *context, int heuristic); -// Optionally select which packing heuristic the library should use. Different -// heuristics will produce better/worse results for different data sets. -// If you call init again, this will be reset to the default. - -enum -{ - STBRP_HEURISTIC_Skyline_default=0, - STBRP_HEURISTIC_Skyline_BL_sortHeight = STBRP_HEURISTIC_Skyline_default, - STBRP_HEURISTIC_Skyline_BF_sortHeight -}; - - -////////////////////////////////////////////////////////////////////////////// -// -// the details of the following structures don't matter to you, but they must -// be visible so you can handle the memory allocations for them - -struct stbrp_node -{ - stbrp_coord x,y; - stbrp_node *next; -}; - -struct stbrp_context -{ - int width; - int height; - int align; - int init_mode; - int heuristic; - int num_nodes; - stbrp_node *active_head; - stbrp_node *free_head; - stbrp_node extra[2]; // we allocate two extra nodes so optimal user-node-count is 'width' not 'width+2' -}; - -#ifdef __cplusplus -} -#endif - -#endif - -////////////////////////////////////////////////////////////////////////////// -// -// IMPLEMENTATION SECTION -// - -#ifdef STB_RECT_PACK_IMPLEMENTATION -#ifndef STBRP_SORT -#include -#define STBRP_SORT qsort -#endif - -#ifndef STBRP_ASSERT -#include -#define STBRP_ASSERT assert -#endif - -#ifdef _MSC_VER -#define STBRP__NOTUSED(v) (void)(v) -#define STBRP__CDECL __cdecl -#else -#define STBRP__NOTUSED(v) (void)sizeof(v) -#define STBRP__CDECL -#endif - -enum -{ - STBRP__INIT_skyline = 1 -}; - -STBRP_DEF void stbrp_setup_heuristic(stbrp_context *context, int heuristic) -{ - switch (context->init_mode) { - case STBRP__INIT_skyline: - STBRP_ASSERT(heuristic == STBRP_HEURISTIC_Skyline_BL_sortHeight || heuristic == STBRP_HEURISTIC_Skyline_BF_sortHeight); - context->heuristic = heuristic; - break; - default: - STBRP_ASSERT(0); - } -} - -STBRP_DEF void stbrp_setup_allow_out_of_mem(stbrp_context *context, int allow_out_of_mem) -{ - if (allow_out_of_mem) - // if it's ok to run out of memory, then don't bother aligning them; - // this gives better packing, but may fail due to OOM (even though - // the rectangles easily fit). @TODO a smarter approach would be to only - // quantize once we've hit OOM, then we could get rid of this parameter. - context->align = 1; - else { - // if it's not ok to run out of memory, then quantize the widths - // so that num_nodes is always enough nodes. - // - // I.e. num_nodes * align >= width - // align >= width / num_nodes - // align = ceil(width/num_nodes) - - context->align = (context->width + context->num_nodes-1) / context->num_nodes; - } -} - -STBRP_DEF void stbrp_init_target(stbrp_context *context, int width, int height, stbrp_node *nodes, int num_nodes) -{ - int i; - - for (i=0; i < num_nodes-1; ++i) - nodes[i].next = &nodes[i+1]; - nodes[i].next = NULL; - context->init_mode = STBRP__INIT_skyline; - context->heuristic = STBRP_HEURISTIC_Skyline_default; - context->free_head = &nodes[0]; - context->active_head = &context->extra[0]; - context->width = width; - context->height = height; - context->num_nodes = num_nodes; - stbrp_setup_allow_out_of_mem(context, 0); - - // node 0 is the full width, node 1 is the sentinel (lets us not store width explicitly) - context->extra[0].x = 0; - context->extra[0].y = 0; - context->extra[0].next = &context->extra[1]; - context->extra[1].x = (stbrp_coord) width; - context->extra[1].y = (1<<30); - context->extra[1].next = NULL; -} - -// find minimum y position if it starts at x1 -static int stbrp__skyline_find_min_y(stbrp_context *c, stbrp_node *first, int x0, int width, int *pwaste) -{ - stbrp_node *node = first; - int x1 = x0 + width; - int min_y, visited_width, waste_area; - - STBRP__NOTUSED(c); - - STBRP_ASSERT(first->x <= x0); - - #if 0 - // skip in case we're past the node - while (node->next->x <= x0) - ++node; - #else - STBRP_ASSERT(node->next->x > x0); // we ended up handling this in the caller for efficiency - #endif - - STBRP_ASSERT(node->x <= x0); - - min_y = 0; - waste_area = 0; - visited_width = 0; - while (node->x < x1) { - if (node->y > min_y) { - // raise min_y higher. - // we've accounted for all waste up to min_y, - // but we'll now add more waste for everything we've visted - waste_area += visited_width * (node->y - min_y); - min_y = node->y; - // the first time through, visited_width might be reduced - if (node->x < x0) - visited_width += node->next->x - x0; - else - visited_width += node->next->x - node->x; - } else { - // add waste area - int under_width = node->next->x - node->x; - if (under_width + visited_width > width) - under_width = width - visited_width; - waste_area += under_width * (min_y - node->y); - visited_width += under_width; - } - node = node->next; - } - - *pwaste = waste_area; - return min_y; -} - -typedef struct -{ - int x,y; - stbrp_node **prev_link; -} stbrp__findresult; - -static stbrp__findresult stbrp__skyline_find_best_pos(stbrp_context *c, int width, int height) -{ - int best_waste = (1<<30), best_x, best_y = (1 << 30); - stbrp__findresult fr; - stbrp_node **prev, *node, *tail, **best = NULL; - - // align to multiple of c->align - width = (width + c->align - 1); - width -= width % c->align; - STBRP_ASSERT(width % c->align == 0); - - // if it can't possibly fit, bail immediately - if (width > c->width || height > c->height) { - fr.prev_link = NULL; - fr.x = fr.y = 0; - return fr; - } - - node = c->active_head; - prev = &c->active_head; - while (node->x + width <= c->width) { - int y,waste; - y = stbrp__skyline_find_min_y(c, node, node->x, width, &waste); - if (c->heuristic == STBRP_HEURISTIC_Skyline_BL_sortHeight) { // actually just want to test BL - // bottom left - if (y < best_y) { - best_y = y; - best = prev; - } - } else { - // best-fit - if (y + height <= c->height) { - // can only use it if it first vertically - if (y < best_y || (y == best_y && waste < best_waste)) { - best_y = y; - best_waste = waste; - best = prev; - } - } - } - prev = &node->next; - node = node->next; - } - - best_x = (best == NULL) ? 0 : (*best)->x; - - // if doing best-fit (BF), we also have to try aligning right edge to each node position - // - // e.g, if fitting - // - // ____________________ - // |____________________| - // - // into - // - // | | - // | ____________| - // |____________| - // - // then right-aligned reduces waste, but bottom-left BL is always chooses left-aligned - // - // This makes BF take about 2x the time - - if (c->heuristic == STBRP_HEURISTIC_Skyline_BF_sortHeight) { - tail = c->active_head; - node = c->active_head; - prev = &c->active_head; - // find first node that's admissible - while (tail->x < width) - tail = tail->next; - while (tail) { - int xpos = tail->x - width; - int y,waste; - STBRP_ASSERT(xpos >= 0); - // find the left position that matches this - while (node->next->x <= xpos) { - prev = &node->next; - node = node->next; - } - STBRP_ASSERT(node->next->x > xpos && node->x <= xpos); - y = stbrp__skyline_find_min_y(c, node, xpos, width, &waste); - if (y + height <= c->height) { - if (y <= best_y) { - if (y < best_y || waste < best_waste || (waste==best_waste && xpos < best_x)) { - best_x = xpos; - //STBRP_ASSERT(y <= best_y); [DEAR IMGUI] - best_y = y; - best_waste = waste; - best = prev; - } - } - } - tail = tail->next; - } - } - - fr.prev_link = best; - fr.x = best_x; - fr.y = best_y; - return fr; -} - -static stbrp__findresult stbrp__skyline_pack_rectangle(stbrp_context *context, int width, int height) -{ - // find best position according to heuristic - stbrp__findresult res = stbrp__skyline_find_best_pos(context, width, height); - stbrp_node *node, *cur; - - // bail if: - // 1. it failed - // 2. the best node doesn't fit (we don't always check this) - // 3. we're out of memory - if (res.prev_link == NULL || res.y + height > context->height || context->free_head == NULL) { - res.prev_link = NULL; - return res; - } - - // on success, create new node - node = context->free_head; - node->x = (stbrp_coord) res.x; - node->y = (stbrp_coord) (res.y + height); - - context->free_head = node->next; - - // insert the new node into the right starting point, and - // let 'cur' point to the remaining nodes needing to be - // stiched back in - - cur = *res.prev_link; - if (cur->x < res.x) { - // preserve the existing one, so start testing with the next one - stbrp_node *next = cur->next; - cur->next = node; - cur = next; - } else { - *res.prev_link = node; - } - - // from here, traverse cur and free the nodes, until we get to one - // that shouldn't be freed - while (cur->next && cur->next->x <= res.x + width) { - stbrp_node *next = cur->next; - // move the current node to the free list - cur->next = context->free_head; - context->free_head = cur; - cur = next; - } - - // stitch the list back in - node->next = cur; - - if (cur->x < res.x + width) - cur->x = (stbrp_coord) (res.x + width); - -#ifdef _DEBUG - cur = context->active_head; - while (cur->x < context->width) { - STBRP_ASSERT(cur->x < cur->next->x); - cur = cur->next; - } - STBRP_ASSERT(cur->next == NULL); - - { - int count=0; - cur = context->active_head; - while (cur) { - cur = cur->next; - ++count; - } - cur = context->free_head; - while (cur) { - cur = cur->next; - ++count; - } - STBRP_ASSERT(count == context->num_nodes+2); - } -#endif - - return res; -} - -static int STBRP__CDECL rect_height_compare(const void *a, const void *b) -{ - const stbrp_rect *p = (const stbrp_rect *) a; - const stbrp_rect *q = (const stbrp_rect *) b; - if (p->h > q->h) - return -1; - if (p->h < q->h) - return 1; - return (p->w > q->w) ? -1 : (p->w < q->w); -} - -static int STBRP__CDECL rect_original_order(const void *a, const void *b) -{ - const stbrp_rect *p = (const stbrp_rect *) a; - const stbrp_rect *q = (const stbrp_rect *) b; - return (p->was_packed < q->was_packed) ? -1 : (p->was_packed > q->was_packed); -} - -STBRP_DEF int stbrp_pack_rects(stbrp_context *context, stbrp_rect *rects, int num_rects) -{ - int i, all_rects_packed = 1; - - // we use the 'was_packed' field internally to allow sorting/unsorting - for (i=0; i < num_rects; ++i) { - rects[i].was_packed = i; - } - - // sort according to heuristic - STBRP_SORT(rects, num_rects, sizeof(rects[0]), rect_height_compare); - - for (i=0; i < num_rects; ++i) { - if (rects[i].w == 0 || rects[i].h == 0) { - rects[i].x = rects[i].y = 0; // empty rect needs no space - } else { - stbrp__findresult fr = stbrp__skyline_pack_rectangle(context, rects[i].w, rects[i].h); - if (fr.prev_link) { - rects[i].x = (stbrp_coord) fr.x; - rects[i].y = (stbrp_coord) fr.y; - } else { - rects[i].x = rects[i].y = STBRP__MAXVAL; - } - } - } - - // unsort - STBRP_SORT(rects, num_rects, sizeof(rects[0]), rect_original_order); - - // set was_packed flags and all_rects_packed status - for (i=0; i < num_rects; ++i) { - rects[i].was_packed = !(rects[i].x == STBRP__MAXVAL && rects[i].y == STBRP__MAXVAL); - if (!rects[i].was_packed) - all_rects_packed = 0; - } - - // return the all_rects_packed status - return all_rects_packed; -} -#endif - -/* ------------------------------------------------------------------------------- -This software is available under 2 licenses -- choose whichever you prefer. ------------------------------------------------------------------------------- -ALTERNATIVE A - MIT License -Copyright (c) 2017 Sean Barrett -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. ------------------------------------------------------------------------------- -ALTERNATIVE B - Public Domain (www.unlicense.org) -This is free and unencumbered software released into the public domain. -Anyone is free to copy, modify, publish, use, compile, sell, or distribute this -software, either in source code form or as a compiled binary, for any purpose, -commercial or non-commercial, and by any means. -In jurisdictions that recognize copyright laws, the author or authors of this -software dedicate any and all copyright interest in the software to the public -domain. We make this dedication for the benefit of the public at large and to -the detriment of our heirs and successors. We intend this dedication to be an -overt act of relinquishment in perpetuity of all present and future rights to -this software under copyright law. -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 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. ------------------------------------------------------------------------------- -*/ diff --git a/app/jni/src/libultraship/extern/ImGui/imstb_textedit.h b/app/jni/src/libultraship/extern/ImGui/imstb_textedit.h deleted file mode 100644 index 062d13d..0000000 --- a/app/jni/src/libultraship/extern/ImGui/imstb_textedit.h +++ /dev/null @@ -1,1440 +0,0 @@ -// [DEAR IMGUI] -// This is a slightly modified version of stb_textedit.h 1.14. -// Those changes would need to be pushed into nothings/stb: -// - Fix in stb_textedit_discard_redo (see https://github.com/nothings/stb/issues/321) -// - Fix in stb_textedit_find_charpos to handle last line (see https://github.com/ocornut/imgui/issues/6000 + #6783) -// Grep for [DEAR IMGUI] to find the changes. - -// stb_textedit.h - v1.14 - public domain - Sean Barrett -// Development of this library was sponsored by RAD Game Tools -// -// This C header file implements the guts of a multi-line text-editing -// widget; you implement display, word-wrapping, and low-level string -// insertion/deletion, and stb_textedit will map user inputs into -// insertions & deletions, plus updates to the cursor position, -// selection state, and undo state. -// -// It is intended for use in games and other systems that need to build -// their own custom widgets and which do not have heavy text-editing -// requirements (this library is not recommended for use for editing large -// texts, as its performance does not scale and it has limited undo). -// -// Non-trivial behaviors are modelled after Windows text controls. -// -// -// LICENSE -// -// See end of file for license information. -// -// -// DEPENDENCIES -// -// Uses the C runtime function 'memmove', which you can override -// by defining STB_TEXTEDIT_memmove before the implementation. -// Uses no other functions. Performs no runtime allocations. -// -// -// VERSION HISTORY -// -// 1.14 (2021-07-11) page up/down, various fixes -// 1.13 (2019-02-07) fix bug in undo size management -// 1.12 (2018-01-29) user can change STB_TEXTEDIT_KEYTYPE, fix redo to avoid crash -// 1.11 (2017-03-03) fix HOME on last line, dragging off single-line textfield -// 1.10 (2016-10-25) supress warnings about casting away const with -Wcast-qual -// 1.9 (2016-08-27) customizable move-by-word -// 1.8 (2016-04-02) better keyboard handling when mouse button is down -// 1.7 (2015-09-13) change y range handling in case baseline is non-0 -// 1.6 (2015-04-15) allow STB_TEXTEDIT_memmove -// 1.5 (2014-09-10) add support for secondary keys for OS X -// 1.4 (2014-08-17) fix signed/unsigned warnings -// 1.3 (2014-06-19) fix mouse clicking to round to nearest char boundary -// 1.2 (2014-05-27) fix some RAD types that had crept into the new code -// 1.1 (2013-12-15) move-by-word (requires STB_TEXTEDIT_IS_SPACE ) -// 1.0 (2012-07-26) improve documentation, initial public release -// 0.3 (2012-02-24) bugfixes, single-line mode; insert mode -// 0.2 (2011-11-28) fixes to undo/redo -// 0.1 (2010-07-08) initial version -// -// ADDITIONAL CONTRIBUTORS -// -// Ulf Winklemann: move-by-word in 1.1 -// Fabian Giesen: secondary key inputs in 1.5 -// Martins Mozeiko: STB_TEXTEDIT_memmove in 1.6 -// Louis Schnellbach: page up/down in 1.14 -// -// Bugfixes: -// Scott Graham -// Daniel Keller -// Omar Cornut -// Dan Thompson -// -// USAGE -// -// This file behaves differently depending on what symbols you define -// before including it. -// -// -// Header-file mode: -// -// If you do not define STB_TEXTEDIT_IMPLEMENTATION before including this, -// it will operate in "header file" mode. In this mode, it declares a -// single public symbol, STB_TexteditState, which encapsulates the current -// state of a text widget (except for the string, which you will store -// separately). -// -// To compile in this mode, you must define STB_TEXTEDIT_CHARTYPE to a -// primitive type that defines a single character (e.g. char, wchar_t, etc). -// -// To save space or increase undo-ability, you can optionally define the -// following things that are used by the undo system: -// -// STB_TEXTEDIT_POSITIONTYPE small int type encoding a valid cursor position -// STB_TEXTEDIT_UNDOSTATECOUNT the number of undo states to allow -// STB_TEXTEDIT_UNDOCHARCOUNT the number of characters to store in the undo buffer -// -// If you don't define these, they are set to permissive types and -// moderate sizes. The undo system does no memory allocations, so -// it grows STB_TexteditState by the worst-case storage which is (in bytes): -// -// [4 + 3 * sizeof(STB_TEXTEDIT_POSITIONTYPE)] * STB_TEXTEDIT_UNDOSTATECOUNT -// + sizeof(STB_TEXTEDIT_CHARTYPE) * STB_TEXTEDIT_UNDOCHARCOUNT -// -// -// Implementation mode: -// -// If you define STB_TEXTEDIT_IMPLEMENTATION before including this, it -// will compile the implementation of the text edit widget, depending -// on a large number of symbols which must be defined before the include. -// -// The implementation is defined only as static functions. You will then -// need to provide your own APIs in the same file which will access the -// static functions. -// -// The basic concept is that you provide a "string" object which -// behaves like an array of characters. stb_textedit uses indices to -// refer to positions in the string, implicitly representing positions -// in the displayed textedit. This is true for both plain text and -// rich text; even with rich text stb_truetype interacts with your -// code as if there was an array of all the displayed characters. -// -// Symbols that must be the same in header-file and implementation mode: -// -// STB_TEXTEDIT_CHARTYPE the character type -// STB_TEXTEDIT_POSITIONTYPE small type that is a valid cursor position -// STB_TEXTEDIT_UNDOSTATECOUNT the number of undo states to allow -// STB_TEXTEDIT_UNDOCHARCOUNT the number of characters to store in the undo buffer -// -// Symbols you must define for implementation mode: -// -// STB_TEXTEDIT_STRING the type of object representing a string being edited, -// typically this is a wrapper object with other data you need -// -// STB_TEXTEDIT_STRINGLEN(obj) the length of the string (ideally O(1)) -// STB_TEXTEDIT_LAYOUTROW(&r,obj,n) returns the results of laying out a line of characters -// starting from character #n (see discussion below) -// STB_TEXTEDIT_GETWIDTH(obj,n,i) returns the pixel delta from the xpos of the i'th character -// to the xpos of the i+1'th char for a line of characters -// starting at character #n (i.e. accounts for kerning -// with previous char) -// STB_TEXTEDIT_KEYTOTEXT(k) maps a keyboard input to an insertable character -// (return type is int, -1 means not valid to insert) -// STB_TEXTEDIT_GETCHAR(obj,i) returns the i'th character of obj, 0-based -// STB_TEXTEDIT_NEWLINE the character returned by _GETCHAR() we recognize -// as manually wordwrapping for end-of-line positioning -// -// STB_TEXTEDIT_DELETECHARS(obj,i,n) delete n characters starting at i -// STB_TEXTEDIT_INSERTCHARS(obj,i,c*,n) insert n characters at i (pointed to by STB_TEXTEDIT_CHARTYPE*) -// -// STB_TEXTEDIT_K_SHIFT a power of two that is or'd in to a keyboard input to represent the shift key -// -// STB_TEXTEDIT_K_LEFT keyboard input to move cursor left -// STB_TEXTEDIT_K_RIGHT keyboard input to move cursor right -// STB_TEXTEDIT_K_UP keyboard input to move cursor up -// STB_TEXTEDIT_K_DOWN keyboard input to move cursor down -// STB_TEXTEDIT_K_PGUP keyboard input to move cursor up a page -// STB_TEXTEDIT_K_PGDOWN keyboard input to move cursor down a page -// STB_TEXTEDIT_K_LINESTART keyboard input to move cursor to start of line // e.g. HOME -// STB_TEXTEDIT_K_LINEEND keyboard input to move cursor to end of line // e.g. END -// STB_TEXTEDIT_K_TEXTSTART keyboard input to move cursor to start of text // e.g. ctrl-HOME -// STB_TEXTEDIT_K_TEXTEND keyboard input to move cursor to end of text // e.g. ctrl-END -// STB_TEXTEDIT_K_DELETE keyboard input to delete selection or character under cursor -// STB_TEXTEDIT_K_BACKSPACE keyboard input to delete selection or character left of cursor -// STB_TEXTEDIT_K_UNDO keyboard input to perform undo -// STB_TEXTEDIT_K_REDO keyboard input to perform redo -// -// Optional: -// STB_TEXTEDIT_K_INSERT keyboard input to toggle insert mode -// STB_TEXTEDIT_IS_SPACE(ch) true if character is whitespace (e.g. 'isspace'), -// required for default WORDLEFT/WORDRIGHT handlers -// STB_TEXTEDIT_MOVEWORDLEFT(obj,i) custom handler for WORDLEFT, returns index to move cursor to -// STB_TEXTEDIT_MOVEWORDRIGHT(obj,i) custom handler for WORDRIGHT, returns index to move cursor to -// STB_TEXTEDIT_K_WORDLEFT keyboard input to move cursor left one word // e.g. ctrl-LEFT -// STB_TEXTEDIT_K_WORDRIGHT keyboard input to move cursor right one word // e.g. ctrl-RIGHT -// STB_TEXTEDIT_K_LINESTART2 secondary keyboard input to move cursor to start of line -// STB_TEXTEDIT_K_LINEEND2 secondary keyboard input to move cursor to end of line -// STB_TEXTEDIT_K_TEXTSTART2 secondary keyboard input to move cursor to start of text -// STB_TEXTEDIT_K_TEXTEND2 secondary keyboard input to move cursor to end of text -// -// Keyboard input must be encoded as a single integer value; e.g. a character code -// and some bitflags that represent shift states. to simplify the interface, SHIFT must -// be a bitflag, so we can test the shifted state of cursor movements to allow selection, -// i.e. (STB_TEXTEDIT_K_RIGHT|STB_TEXTEDIT_K_SHIFT) should be shifted right-arrow. -// -// You can encode other things, such as CONTROL or ALT, in additional bits, and -// then test for their presence in e.g. STB_TEXTEDIT_K_WORDLEFT. For example, -// my Windows implementations add an additional CONTROL bit, and an additional KEYDOWN -// bit. Then all of the STB_TEXTEDIT_K_ values bitwise-or in the KEYDOWN bit, -// and I pass both WM_KEYDOWN and WM_CHAR events to the "key" function in the -// API below. The control keys will only match WM_KEYDOWN events because of the -// keydown bit I add, and STB_TEXTEDIT_KEYTOTEXT only tests for the KEYDOWN -// bit so it only decodes WM_CHAR events. -// -// STB_TEXTEDIT_LAYOUTROW returns information about the shape of one displayed -// row of characters assuming they start on the i'th character--the width and -// the height and the number of characters consumed. This allows this library -// to traverse the entire layout incrementally. You need to compute word-wrapping -// here. -// -// Each textfield keeps its own insert mode state, which is not how normal -// applications work. To keep an app-wide insert mode, update/copy the -// "insert_mode" field of STB_TexteditState before/after calling API functions. -// -// API -// -// void stb_textedit_initialize_state(STB_TexteditState *state, int is_single_line) -// -// void stb_textedit_click(STB_TEXTEDIT_STRING *str, STB_TexteditState *state, float x, float y) -// void stb_textedit_drag(STB_TEXTEDIT_STRING *str, STB_TexteditState *state, float x, float y) -// int stb_textedit_cut(STB_TEXTEDIT_STRING *str, STB_TexteditState *state) -// int stb_textedit_paste(STB_TEXTEDIT_STRING *str, STB_TexteditState *state, STB_TEXTEDIT_CHARTYPE *text, int len) -// void stb_textedit_key(STB_TEXTEDIT_STRING *str, STB_TexteditState *state, STB_TEXEDIT_KEYTYPE key) -// -// Each of these functions potentially updates the string and updates the -// state. -// -// initialize_state: -// set the textedit state to a known good default state when initially -// constructing the textedit. -// -// click: -// call this with the mouse x,y on a mouse down; it will update the cursor -// and reset the selection start/end to the cursor point. the x,y must -// be relative to the text widget, with (0,0) being the top left. -// -// drag: -// call this with the mouse x,y on a mouse drag/up; it will update the -// cursor and the selection end point -// -// cut: -// call this to delete the current selection; returns true if there was -// one. you should FIRST copy the current selection to the system paste buffer. -// (To copy, just copy the current selection out of the string yourself.) -// -// paste: -// call this to paste text at the current cursor point or over the current -// selection if there is one. -// -// key: -// call this for keyboard inputs sent to the textfield. you can use it -// for "key down" events or for "translated" key events. if you need to -// do both (as in Win32), or distinguish Unicode characters from control -// inputs, set a high bit to distinguish the two; then you can define the -// various definitions like STB_TEXTEDIT_K_LEFT have the is-key-event bit -// set, and make STB_TEXTEDIT_KEYTOCHAR check that the is-key-event bit is -// clear. STB_TEXTEDIT_KEYTYPE defaults to int, but you can #define it to -// anything other type you wante before including. -// -// -// When rendering, you can read the cursor position and selection state from -// the STB_TexteditState. -// -// -// Notes: -// -// This is designed to be usable in IMGUI, so it allows for the possibility of -// running in an IMGUI that has NOT cached the multi-line layout. For this -// reason, it provides an interface that is compatible with computing the -// layout incrementally--we try to make sure we make as few passes through -// as possible. (For example, to locate the mouse pointer in the text, we -// could define functions that return the X and Y positions of characters -// and binary search Y and then X, but if we're doing dynamic layout this -// will run the layout algorithm many times, so instead we manually search -// forward in one pass. Similar logic applies to e.g. up-arrow and -// down-arrow movement.) -// -// If it's run in a widget that *has* cached the layout, then this is less -// efficient, but it's not horrible on modern computers. But you wouldn't -// want to edit million-line files with it. - - -//////////////////////////////////////////////////////////////////////////// -//////////////////////////////////////////////////////////////////////////// -//// -//// Header-file mode -//// -//// - -#ifndef INCLUDE_STB_TEXTEDIT_H -#define INCLUDE_STB_TEXTEDIT_H - -//////////////////////////////////////////////////////////////////////// -// -// STB_TexteditState -// -// Definition of STB_TexteditState which you should store -// per-textfield; it includes cursor position, selection state, -// and undo state. -// - -#ifndef STB_TEXTEDIT_UNDOSTATECOUNT -#define STB_TEXTEDIT_UNDOSTATECOUNT 99 -#endif -#ifndef STB_TEXTEDIT_UNDOCHARCOUNT -#define STB_TEXTEDIT_UNDOCHARCOUNT 999 -#endif -#ifndef STB_TEXTEDIT_CHARTYPE -#define STB_TEXTEDIT_CHARTYPE int -#endif -#ifndef STB_TEXTEDIT_POSITIONTYPE -#define STB_TEXTEDIT_POSITIONTYPE int -#endif - -typedef struct -{ - // private data - STB_TEXTEDIT_POSITIONTYPE where; - STB_TEXTEDIT_POSITIONTYPE insert_length; - STB_TEXTEDIT_POSITIONTYPE delete_length; - int char_storage; -} StbUndoRecord; - -typedef struct -{ - // private data - StbUndoRecord undo_rec [STB_TEXTEDIT_UNDOSTATECOUNT]; - STB_TEXTEDIT_CHARTYPE undo_char[STB_TEXTEDIT_UNDOCHARCOUNT]; - short undo_point, redo_point; - int undo_char_point, redo_char_point; -} StbUndoState; - -typedef struct -{ - ///////////////////// - // - // public data - // - - int cursor; - // position of the text cursor within the string - - int select_start; // selection start point - int select_end; - // selection start and end point in characters; if equal, no selection. - // note that start may be less than or greater than end (e.g. when - // dragging the mouse, start is where the initial click was, and you - // can drag in either direction) - - unsigned char insert_mode; - // each textfield keeps its own insert mode state. to keep an app-wide - // insert mode, copy this value in/out of the app state - - int row_count_per_page; - // page size in number of row. - // this value MUST be set to >0 for pageup or pagedown in multilines documents. - - ///////////////////// - // - // private data - // - unsigned char cursor_at_end_of_line; // not implemented yet - unsigned char initialized; - unsigned char has_preferred_x; - unsigned char single_line; - unsigned char padding1, padding2, padding3; - float preferred_x; // this determines where the cursor up/down tries to seek to along x - StbUndoState undostate; -} STB_TexteditState; - - -//////////////////////////////////////////////////////////////////////// -// -// StbTexteditRow -// -// Result of layout query, used by stb_textedit to determine where -// the text in each row is. - -// result of layout query -typedef struct -{ - float x0,x1; // starting x location, end x location (allows for align=right, etc) - float baseline_y_delta; // position of baseline relative to previous row's baseline - float ymin,ymax; // height of row above and below baseline - int num_chars; -} StbTexteditRow; -#endif //INCLUDE_STB_TEXTEDIT_H - - -//////////////////////////////////////////////////////////////////////////// -//////////////////////////////////////////////////////////////////////////// -//// -//// Implementation mode -//// -//// - - -// implementation isn't include-guarded, since it might have indirectly -// included just the "header" portion -#ifdef STB_TEXTEDIT_IMPLEMENTATION - -#ifndef STB_TEXTEDIT_memmove -#include -#define STB_TEXTEDIT_memmove memmove -#endif - - -///////////////////////////////////////////////////////////////////////////// -// -// Mouse input handling -// - -// traverse the layout to locate the nearest character to a display position -static int stb_text_locate_coord(STB_TEXTEDIT_STRING *str, float x, float y) -{ - StbTexteditRow r; - int n = STB_TEXTEDIT_STRINGLEN(str); - float base_y = 0, prev_x; - int i=0, k; - - r.x0 = r.x1 = 0; - r.ymin = r.ymax = 0; - r.num_chars = 0; - - // search rows to find one that straddles 'y' - while (i < n) { - STB_TEXTEDIT_LAYOUTROW(&r, str, i); - if (r.num_chars <= 0) - return n; - - if (i==0 && y < base_y + r.ymin) - return 0; - - if (y < base_y + r.ymax) - break; - - i += r.num_chars; - base_y += r.baseline_y_delta; - } - - // below all text, return 'after' last character - if (i >= n) - return n; - - // check if it's before the beginning of the line - if (x < r.x0) - return i; - - // check if it's before the end of the line - if (x < r.x1) { - // search characters in row for one that straddles 'x' - prev_x = r.x0; - for (k=0; k < r.num_chars; ++k) { - float w = STB_TEXTEDIT_GETWIDTH(str, i, k); - if (x < prev_x+w) { - if (x < prev_x+w/2) - return k+i; - else - return k+i+1; - } - prev_x += w; - } - // shouldn't happen, but if it does, fall through to end-of-line case - } - - // if the last character is a newline, return that. otherwise return 'after' the last character - if (STB_TEXTEDIT_GETCHAR(str, i+r.num_chars-1) == STB_TEXTEDIT_NEWLINE) - return i+r.num_chars-1; - else - return i+r.num_chars; -} - -// API click: on mouse down, move the cursor to the clicked location, and reset the selection -static void stb_textedit_click(STB_TEXTEDIT_STRING *str, STB_TexteditState *state, float x, float y) -{ - // In single-line mode, just always make y = 0. This lets the drag keep working if the mouse - // goes off the top or bottom of the text - if( state->single_line ) - { - StbTexteditRow r; - STB_TEXTEDIT_LAYOUTROW(&r, str, 0); - y = r.ymin; - } - - state->cursor = stb_text_locate_coord(str, x, y); - state->select_start = state->cursor; - state->select_end = state->cursor; - state->has_preferred_x = 0; -} - -// API drag: on mouse drag, move the cursor and selection endpoint to the clicked location -static void stb_textedit_drag(STB_TEXTEDIT_STRING *str, STB_TexteditState *state, float x, float y) -{ - int p = 0; - - // In single-line mode, just always make y = 0. This lets the drag keep working if the mouse - // goes off the top or bottom of the text - if( state->single_line ) - { - StbTexteditRow r; - STB_TEXTEDIT_LAYOUTROW(&r, str, 0); - y = r.ymin; - } - - if (state->select_start == state->select_end) - state->select_start = state->cursor; - - p = stb_text_locate_coord(str, x, y); - state->cursor = state->select_end = p; -} - -///////////////////////////////////////////////////////////////////////////// -// -// Keyboard input handling -// - -// forward declarations -static void stb_text_undo(STB_TEXTEDIT_STRING *str, STB_TexteditState *state); -static void stb_text_redo(STB_TEXTEDIT_STRING *str, STB_TexteditState *state); -static void stb_text_makeundo_delete(STB_TEXTEDIT_STRING *str, STB_TexteditState *state, int where, int length); -static void stb_text_makeundo_insert(STB_TexteditState *state, int where, int length); -static void stb_text_makeundo_replace(STB_TEXTEDIT_STRING *str, STB_TexteditState *state, int where, int old_length, int new_length); - -typedef struct -{ - float x,y; // position of n'th character - float height; // height of line - int first_char, length; // first char of row, and length - int prev_first; // first char of previous row -} StbFindState; - -// find the x/y location of a character, and remember info about the previous row in -// case we get a move-up event (for page up, we'll have to rescan) -static void stb_textedit_find_charpos(StbFindState *find, STB_TEXTEDIT_STRING *str, int n, int single_line) -{ - StbTexteditRow r; - int prev_start = 0; - int z = STB_TEXTEDIT_STRINGLEN(str); - int i=0, first; - - if (n == z && single_line) { - // special case if it's at the end (may not be needed?) - STB_TEXTEDIT_LAYOUTROW(&r, str, 0); - find->y = 0; - find->first_char = 0; - find->length = z; - find->height = r.ymax - r.ymin; - find->x = r.x1; - return; - } - - // search rows to find the one that straddles character n - find->y = 0; - - for(;;) { - STB_TEXTEDIT_LAYOUTROW(&r, str, i); - if (n < i + r.num_chars) - break; - if (i + r.num_chars == z && z > 0 && STB_TEXTEDIT_GETCHAR(str, z - 1) != STB_TEXTEDIT_NEWLINE) // [DEAR IMGUI] special handling for last line - break; // [DEAR IMGUI] - prev_start = i; - i += r.num_chars; - find->y += r.baseline_y_delta; - if (i == z) // [DEAR IMGUI] - { - r.num_chars = 0; // [DEAR IMGUI] - break; // [DEAR IMGUI] - } - } - - find->first_char = first = i; - find->length = r.num_chars; - find->height = r.ymax - r.ymin; - find->prev_first = prev_start; - - // now scan to find xpos - find->x = r.x0; - for (i=0; first+i < n; ++i) - find->x += STB_TEXTEDIT_GETWIDTH(str, first, i); -} - -#define STB_TEXT_HAS_SELECTION(s) ((s)->select_start != (s)->select_end) - -// make the selection/cursor state valid if client altered the string -static void stb_textedit_clamp(STB_TEXTEDIT_STRING *str, STB_TexteditState *state) -{ - int n = STB_TEXTEDIT_STRINGLEN(str); - if (STB_TEXT_HAS_SELECTION(state)) { - if (state->select_start > n) state->select_start = n; - if (state->select_end > n) state->select_end = n; - // if clamping forced them to be equal, move the cursor to match - if (state->select_start == state->select_end) - state->cursor = state->select_start; - } - if (state->cursor > n) state->cursor = n; -} - -// delete characters while updating undo -static void stb_textedit_delete(STB_TEXTEDIT_STRING *str, STB_TexteditState *state, int where, int len) -{ - stb_text_makeundo_delete(str, state, where, len); - STB_TEXTEDIT_DELETECHARS(str, where, len); - state->has_preferred_x = 0; -} - -// delete the section -static void stb_textedit_delete_selection(STB_TEXTEDIT_STRING *str, STB_TexteditState *state) -{ - stb_textedit_clamp(str, state); - if (STB_TEXT_HAS_SELECTION(state)) { - if (state->select_start < state->select_end) { - stb_textedit_delete(str, state, state->select_start, state->select_end - state->select_start); - state->select_end = state->cursor = state->select_start; - } else { - stb_textedit_delete(str, state, state->select_end, state->select_start - state->select_end); - state->select_start = state->cursor = state->select_end; - } - state->has_preferred_x = 0; - } -} - -// canoncialize the selection so start <= end -static void stb_textedit_sortselection(STB_TexteditState *state) -{ - if (state->select_end < state->select_start) { - int temp = state->select_end; - state->select_end = state->select_start; - state->select_start = temp; - } -} - -// move cursor to first character of selection -static void stb_textedit_move_to_first(STB_TexteditState *state) -{ - if (STB_TEXT_HAS_SELECTION(state)) { - stb_textedit_sortselection(state); - state->cursor = state->select_start; - state->select_end = state->select_start; - state->has_preferred_x = 0; - } -} - -// move cursor to last character of selection -static void stb_textedit_move_to_last(STB_TEXTEDIT_STRING *str, STB_TexteditState *state) -{ - if (STB_TEXT_HAS_SELECTION(state)) { - stb_textedit_sortselection(state); - stb_textedit_clamp(str, state); - state->cursor = state->select_end; - state->select_start = state->select_end; - state->has_preferred_x = 0; - } -} - -#ifdef STB_TEXTEDIT_IS_SPACE -static int is_word_boundary( STB_TEXTEDIT_STRING *str, int idx ) -{ - return idx > 0 ? (STB_TEXTEDIT_IS_SPACE( STB_TEXTEDIT_GETCHAR(str,idx-1) ) && !STB_TEXTEDIT_IS_SPACE( STB_TEXTEDIT_GETCHAR(str, idx) ) ) : 1; -} - -#ifndef STB_TEXTEDIT_MOVEWORDLEFT -static int stb_textedit_move_to_word_previous( STB_TEXTEDIT_STRING *str, int c ) -{ - --c; // always move at least one character - while( c >= 0 && !is_word_boundary( str, c ) ) - --c; - - if( c < 0 ) - c = 0; - - return c; -} -#define STB_TEXTEDIT_MOVEWORDLEFT stb_textedit_move_to_word_previous -#endif - -#ifndef STB_TEXTEDIT_MOVEWORDRIGHT -static int stb_textedit_move_to_word_next( STB_TEXTEDIT_STRING *str, int c ) -{ - const int len = STB_TEXTEDIT_STRINGLEN(str); - ++c; // always move at least one character - while( c < len && !is_word_boundary( str, c ) ) - ++c; - - if( c > len ) - c = len; - - return c; -} -#define STB_TEXTEDIT_MOVEWORDRIGHT stb_textedit_move_to_word_next -#endif - -#endif - -// update selection and cursor to match each other -static void stb_textedit_prep_selection_at_cursor(STB_TexteditState *state) -{ - if (!STB_TEXT_HAS_SELECTION(state)) - state->select_start = state->select_end = state->cursor; - else - state->cursor = state->select_end; -} - -// API cut: delete selection -static int stb_textedit_cut(STB_TEXTEDIT_STRING *str, STB_TexteditState *state) -{ - if (STB_TEXT_HAS_SELECTION(state)) { - stb_textedit_delete_selection(str,state); // implicitly clamps - state->has_preferred_x = 0; - return 1; - } - return 0; -} - -// API paste: replace existing selection with passed-in text -static int stb_textedit_paste_internal(STB_TEXTEDIT_STRING *str, STB_TexteditState *state, STB_TEXTEDIT_CHARTYPE *text, int len) -{ - // if there's a selection, the paste should delete it - stb_textedit_clamp(str, state); - stb_textedit_delete_selection(str,state); - // try to insert the characters - if (STB_TEXTEDIT_INSERTCHARS(str, state->cursor, text, len)) { - stb_text_makeundo_insert(state, state->cursor, len); - state->cursor += len; - state->has_preferred_x = 0; - return 1; - } - // note: paste failure will leave deleted selection, may be restored with an undo (see https://github.com/nothings/stb/issues/734 for details) - return 0; -} - -#ifndef STB_TEXTEDIT_KEYTYPE -#define STB_TEXTEDIT_KEYTYPE int -#endif - -// API key: process a keyboard input -static void stb_textedit_key(STB_TEXTEDIT_STRING *str, STB_TexteditState *state, STB_TEXTEDIT_KEYTYPE key) -{ -retry: - switch (key) { - default: { - int c = STB_TEXTEDIT_KEYTOTEXT(key); - if (c > 0) { - STB_TEXTEDIT_CHARTYPE ch = (STB_TEXTEDIT_CHARTYPE) c; - - // can't add newline in single-line mode - if (c == '\n' && state->single_line) - break; - - if (state->insert_mode && !STB_TEXT_HAS_SELECTION(state) && state->cursor < STB_TEXTEDIT_STRINGLEN(str)) { - stb_text_makeundo_replace(str, state, state->cursor, 1, 1); - STB_TEXTEDIT_DELETECHARS(str, state->cursor, 1); - if (STB_TEXTEDIT_INSERTCHARS(str, state->cursor, &ch, 1)) { - ++state->cursor; - state->has_preferred_x = 0; - } - } else { - stb_textedit_delete_selection(str,state); // implicitly clamps - if (STB_TEXTEDIT_INSERTCHARS(str, state->cursor, &ch, 1)) { - stb_text_makeundo_insert(state, state->cursor, 1); - ++state->cursor; - state->has_preferred_x = 0; - } - } - } - break; - } - -#ifdef STB_TEXTEDIT_K_INSERT - case STB_TEXTEDIT_K_INSERT: - state->insert_mode = !state->insert_mode; - break; -#endif - - case STB_TEXTEDIT_K_UNDO: - stb_text_undo(str, state); - state->has_preferred_x = 0; - break; - - case STB_TEXTEDIT_K_REDO: - stb_text_redo(str, state); - state->has_preferred_x = 0; - break; - - case STB_TEXTEDIT_K_LEFT: - // if currently there's a selection, move cursor to start of selection - if (STB_TEXT_HAS_SELECTION(state)) - stb_textedit_move_to_first(state); - else - if (state->cursor > 0) - --state->cursor; - state->has_preferred_x = 0; - break; - - case STB_TEXTEDIT_K_RIGHT: - // if currently there's a selection, move cursor to end of selection - if (STB_TEXT_HAS_SELECTION(state)) - stb_textedit_move_to_last(str, state); - else - ++state->cursor; - stb_textedit_clamp(str, state); - state->has_preferred_x = 0; - break; - - case STB_TEXTEDIT_K_LEFT | STB_TEXTEDIT_K_SHIFT: - stb_textedit_clamp(str, state); - stb_textedit_prep_selection_at_cursor(state); - // move selection left - if (state->select_end > 0) - --state->select_end; - state->cursor = state->select_end; - state->has_preferred_x = 0; - break; - -#ifdef STB_TEXTEDIT_MOVEWORDLEFT - case STB_TEXTEDIT_K_WORDLEFT: - if (STB_TEXT_HAS_SELECTION(state)) - stb_textedit_move_to_first(state); - else { - state->cursor = STB_TEXTEDIT_MOVEWORDLEFT(str, state->cursor); - stb_textedit_clamp( str, state ); - } - break; - - case STB_TEXTEDIT_K_WORDLEFT | STB_TEXTEDIT_K_SHIFT: - if( !STB_TEXT_HAS_SELECTION( state ) ) - stb_textedit_prep_selection_at_cursor(state); - - state->cursor = STB_TEXTEDIT_MOVEWORDLEFT(str, state->cursor); - state->select_end = state->cursor; - - stb_textedit_clamp( str, state ); - break; -#endif - -#ifdef STB_TEXTEDIT_MOVEWORDRIGHT - case STB_TEXTEDIT_K_WORDRIGHT: - if (STB_TEXT_HAS_SELECTION(state)) - stb_textedit_move_to_last(str, state); - else { - state->cursor = STB_TEXTEDIT_MOVEWORDRIGHT(str, state->cursor); - stb_textedit_clamp( str, state ); - } - break; - - case STB_TEXTEDIT_K_WORDRIGHT | STB_TEXTEDIT_K_SHIFT: - if( !STB_TEXT_HAS_SELECTION( state ) ) - stb_textedit_prep_selection_at_cursor(state); - - state->cursor = STB_TEXTEDIT_MOVEWORDRIGHT(str, state->cursor); - state->select_end = state->cursor; - - stb_textedit_clamp( str, state ); - break; -#endif - - case STB_TEXTEDIT_K_RIGHT | STB_TEXTEDIT_K_SHIFT: - stb_textedit_prep_selection_at_cursor(state); - // move selection right - ++state->select_end; - stb_textedit_clamp(str, state); - state->cursor = state->select_end; - state->has_preferred_x = 0; - break; - - case STB_TEXTEDIT_K_DOWN: - case STB_TEXTEDIT_K_DOWN | STB_TEXTEDIT_K_SHIFT: - case STB_TEXTEDIT_K_PGDOWN: - case STB_TEXTEDIT_K_PGDOWN | STB_TEXTEDIT_K_SHIFT: { - StbFindState find; - StbTexteditRow row; - int i, j, sel = (key & STB_TEXTEDIT_K_SHIFT) != 0; - int is_page = (key & ~STB_TEXTEDIT_K_SHIFT) == STB_TEXTEDIT_K_PGDOWN; - int row_count = is_page ? state->row_count_per_page : 1; - - if (!is_page && state->single_line) { - // on windows, up&down in single-line behave like left&right - key = STB_TEXTEDIT_K_RIGHT | (key & STB_TEXTEDIT_K_SHIFT); - goto retry; - } - - if (sel) - stb_textedit_prep_selection_at_cursor(state); - else if (STB_TEXT_HAS_SELECTION(state)) - stb_textedit_move_to_last(str, state); - - // compute current position of cursor point - stb_textedit_clamp(str, state); - stb_textedit_find_charpos(&find, str, state->cursor, state->single_line); - - for (j = 0; j < row_count; ++j) { - float x, goal_x = state->has_preferred_x ? state->preferred_x : find.x; - int start = find.first_char + find.length; - - if (find.length == 0) - break; - - // [DEAR IMGUI] - // going down while being on the last line shouldn't bring us to that line end - if (STB_TEXTEDIT_GETCHAR(str, find.first_char + find.length - 1) != STB_TEXTEDIT_NEWLINE) - break; - - // now find character position down a row - state->cursor = start; - STB_TEXTEDIT_LAYOUTROW(&row, str, state->cursor); - x = row.x0; - for (i=0; i < row.num_chars; ++i) { - float dx = STB_TEXTEDIT_GETWIDTH(str, start, i); - #ifdef STB_TEXTEDIT_GETWIDTH_NEWLINE - if (dx == STB_TEXTEDIT_GETWIDTH_NEWLINE) - break; - #endif - x += dx; - if (x > goal_x) - break; - ++state->cursor; - } - stb_textedit_clamp(str, state); - - state->has_preferred_x = 1; - state->preferred_x = goal_x; - - if (sel) - state->select_end = state->cursor; - - // go to next line - find.first_char = find.first_char + find.length; - find.length = row.num_chars; - } - break; - } - - case STB_TEXTEDIT_K_UP: - case STB_TEXTEDIT_K_UP | STB_TEXTEDIT_K_SHIFT: - case STB_TEXTEDIT_K_PGUP: - case STB_TEXTEDIT_K_PGUP | STB_TEXTEDIT_K_SHIFT: { - StbFindState find; - StbTexteditRow row; - int i, j, prev_scan, sel = (key & STB_TEXTEDIT_K_SHIFT) != 0; - int is_page = (key & ~STB_TEXTEDIT_K_SHIFT) == STB_TEXTEDIT_K_PGUP; - int row_count = is_page ? state->row_count_per_page : 1; - - if (!is_page && state->single_line) { - // on windows, up&down become left&right - key = STB_TEXTEDIT_K_LEFT | (key & STB_TEXTEDIT_K_SHIFT); - goto retry; - } - - if (sel) - stb_textedit_prep_selection_at_cursor(state); - else if (STB_TEXT_HAS_SELECTION(state)) - stb_textedit_move_to_first(state); - - // compute current position of cursor point - stb_textedit_clamp(str, state); - stb_textedit_find_charpos(&find, str, state->cursor, state->single_line); - - for (j = 0; j < row_count; ++j) { - float x, goal_x = state->has_preferred_x ? state->preferred_x : find.x; - - // can only go up if there's a previous row - if (find.prev_first == find.first_char) - break; - - // now find character position up a row - state->cursor = find.prev_first; - STB_TEXTEDIT_LAYOUTROW(&row, str, state->cursor); - x = row.x0; - for (i=0; i < row.num_chars; ++i) { - float dx = STB_TEXTEDIT_GETWIDTH(str, find.prev_first, i); - #ifdef STB_TEXTEDIT_GETWIDTH_NEWLINE - if (dx == STB_TEXTEDIT_GETWIDTH_NEWLINE) - break; - #endif - x += dx; - if (x > goal_x) - break; - ++state->cursor; - } - stb_textedit_clamp(str, state); - - state->has_preferred_x = 1; - state->preferred_x = goal_x; - - if (sel) - state->select_end = state->cursor; - - // go to previous line - // (we need to scan previous line the hard way. maybe we could expose this as a new API function?) - prev_scan = find.prev_first > 0 ? find.prev_first - 1 : 0; - while (prev_scan > 0 && STB_TEXTEDIT_GETCHAR(str, prev_scan - 1) != STB_TEXTEDIT_NEWLINE) - --prev_scan; - find.first_char = find.prev_first; - find.prev_first = prev_scan; - } - break; - } - - case STB_TEXTEDIT_K_DELETE: - case STB_TEXTEDIT_K_DELETE | STB_TEXTEDIT_K_SHIFT: - if (STB_TEXT_HAS_SELECTION(state)) - stb_textedit_delete_selection(str, state); - else { - int n = STB_TEXTEDIT_STRINGLEN(str); - if (state->cursor < n) - stb_textedit_delete(str, state, state->cursor, 1); - } - state->has_preferred_x = 0; - break; - - case STB_TEXTEDIT_K_BACKSPACE: - case STB_TEXTEDIT_K_BACKSPACE | STB_TEXTEDIT_K_SHIFT: - if (STB_TEXT_HAS_SELECTION(state)) - stb_textedit_delete_selection(str, state); - else { - stb_textedit_clamp(str, state); - if (state->cursor > 0) { - stb_textedit_delete(str, state, state->cursor-1, 1); - --state->cursor; - } - } - state->has_preferred_x = 0; - break; - -#ifdef STB_TEXTEDIT_K_TEXTSTART2 - case STB_TEXTEDIT_K_TEXTSTART2: -#endif - case STB_TEXTEDIT_K_TEXTSTART: - state->cursor = state->select_start = state->select_end = 0; - state->has_preferred_x = 0; - break; - -#ifdef STB_TEXTEDIT_K_TEXTEND2 - case STB_TEXTEDIT_K_TEXTEND2: -#endif - case STB_TEXTEDIT_K_TEXTEND: - state->cursor = STB_TEXTEDIT_STRINGLEN(str); - state->select_start = state->select_end = 0; - state->has_preferred_x = 0; - break; - -#ifdef STB_TEXTEDIT_K_TEXTSTART2 - case STB_TEXTEDIT_K_TEXTSTART2 | STB_TEXTEDIT_K_SHIFT: -#endif - case STB_TEXTEDIT_K_TEXTSTART | STB_TEXTEDIT_K_SHIFT: - stb_textedit_prep_selection_at_cursor(state); - state->cursor = state->select_end = 0; - state->has_preferred_x = 0; - break; - -#ifdef STB_TEXTEDIT_K_TEXTEND2 - case STB_TEXTEDIT_K_TEXTEND2 | STB_TEXTEDIT_K_SHIFT: -#endif - case STB_TEXTEDIT_K_TEXTEND | STB_TEXTEDIT_K_SHIFT: - stb_textedit_prep_selection_at_cursor(state); - state->cursor = state->select_end = STB_TEXTEDIT_STRINGLEN(str); - state->has_preferred_x = 0; - break; - - -#ifdef STB_TEXTEDIT_K_LINESTART2 - case STB_TEXTEDIT_K_LINESTART2: -#endif - case STB_TEXTEDIT_K_LINESTART: - stb_textedit_clamp(str, state); - stb_textedit_move_to_first(state); - if (state->single_line) - state->cursor = 0; - else while (state->cursor > 0 && STB_TEXTEDIT_GETCHAR(str, state->cursor-1) != STB_TEXTEDIT_NEWLINE) - --state->cursor; - state->has_preferred_x = 0; - break; - -#ifdef STB_TEXTEDIT_K_LINEEND2 - case STB_TEXTEDIT_K_LINEEND2: -#endif - case STB_TEXTEDIT_K_LINEEND: { - int n = STB_TEXTEDIT_STRINGLEN(str); - stb_textedit_clamp(str, state); - stb_textedit_move_to_first(state); - if (state->single_line) - state->cursor = n; - else while (state->cursor < n && STB_TEXTEDIT_GETCHAR(str, state->cursor) != STB_TEXTEDIT_NEWLINE) - ++state->cursor; - state->has_preferred_x = 0; - break; - } - -#ifdef STB_TEXTEDIT_K_LINESTART2 - case STB_TEXTEDIT_K_LINESTART2 | STB_TEXTEDIT_K_SHIFT: -#endif - case STB_TEXTEDIT_K_LINESTART | STB_TEXTEDIT_K_SHIFT: - stb_textedit_clamp(str, state); - stb_textedit_prep_selection_at_cursor(state); - if (state->single_line) - state->cursor = 0; - else while (state->cursor > 0 && STB_TEXTEDIT_GETCHAR(str, state->cursor-1) != STB_TEXTEDIT_NEWLINE) - --state->cursor; - state->select_end = state->cursor; - state->has_preferred_x = 0; - break; - -#ifdef STB_TEXTEDIT_K_LINEEND2 - case STB_TEXTEDIT_K_LINEEND2 | STB_TEXTEDIT_K_SHIFT: -#endif - case STB_TEXTEDIT_K_LINEEND | STB_TEXTEDIT_K_SHIFT: { - int n = STB_TEXTEDIT_STRINGLEN(str); - stb_textedit_clamp(str, state); - stb_textedit_prep_selection_at_cursor(state); - if (state->single_line) - state->cursor = n; - else while (state->cursor < n && STB_TEXTEDIT_GETCHAR(str, state->cursor) != STB_TEXTEDIT_NEWLINE) - ++state->cursor; - state->select_end = state->cursor; - state->has_preferred_x = 0; - break; - } - } -} - -///////////////////////////////////////////////////////////////////////////// -// -// Undo processing -// -// @OPTIMIZE: the undo/redo buffer should be circular - -static void stb_textedit_flush_redo(StbUndoState *state) -{ - state->redo_point = STB_TEXTEDIT_UNDOSTATECOUNT; - state->redo_char_point = STB_TEXTEDIT_UNDOCHARCOUNT; -} - -// discard the oldest entry in the undo list -static void stb_textedit_discard_undo(StbUndoState *state) -{ - if (state->undo_point > 0) { - // if the 0th undo state has characters, clean those up - if (state->undo_rec[0].char_storage >= 0) { - int n = state->undo_rec[0].insert_length, i; - // delete n characters from all other records - state->undo_char_point -= n; - STB_TEXTEDIT_memmove(state->undo_char, state->undo_char + n, (size_t) (state->undo_char_point*sizeof(STB_TEXTEDIT_CHARTYPE))); - for (i=0; i < state->undo_point; ++i) - if (state->undo_rec[i].char_storage >= 0) - state->undo_rec[i].char_storage -= n; // @OPTIMIZE: get rid of char_storage and infer it - } - --state->undo_point; - STB_TEXTEDIT_memmove(state->undo_rec, state->undo_rec+1, (size_t) (state->undo_point*sizeof(state->undo_rec[0]))); - } -} - -// discard the oldest entry in the redo list--it's bad if this -// ever happens, but because undo & redo have to store the actual -// characters in different cases, the redo character buffer can -// fill up even though the undo buffer didn't -static void stb_textedit_discard_redo(StbUndoState *state) -{ - int k = STB_TEXTEDIT_UNDOSTATECOUNT-1; - - if (state->redo_point <= k) { - // if the k'th undo state has characters, clean those up - if (state->undo_rec[k].char_storage >= 0) { - int n = state->undo_rec[k].insert_length, i; - // move the remaining redo character data to the end of the buffer - state->redo_char_point += n; - STB_TEXTEDIT_memmove(state->undo_char + state->redo_char_point, state->undo_char + state->redo_char_point-n, (size_t) ((STB_TEXTEDIT_UNDOCHARCOUNT - state->redo_char_point)*sizeof(STB_TEXTEDIT_CHARTYPE))); - // adjust the position of all the other records to account for above memmove - for (i=state->redo_point; i < k; ++i) - if (state->undo_rec[i].char_storage >= 0) - state->undo_rec[i].char_storage += n; - } - // now move all the redo records towards the end of the buffer; the first one is at 'redo_point' - // [DEAR IMGUI] - size_t move_size = (size_t)((STB_TEXTEDIT_UNDOSTATECOUNT - state->redo_point - 1) * sizeof(state->undo_rec[0])); - const char* buf_begin = (char*)state->undo_rec; (void)buf_begin; - const char* buf_end = (char*)state->undo_rec + sizeof(state->undo_rec); (void)buf_end; - IM_ASSERT(((char*)(state->undo_rec + state->redo_point)) >= buf_begin); - IM_ASSERT(((char*)(state->undo_rec + state->redo_point + 1) + move_size) <= buf_end); - STB_TEXTEDIT_memmove(state->undo_rec + state->redo_point+1, state->undo_rec + state->redo_point, move_size); - - // now move redo_point to point to the new one - ++state->redo_point; - } -} - -static StbUndoRecord *stb_text_create_undo_record(StbUndoState *state, int numchars) -{ - // any time we create a new undo record, we discard redo - stb_textedit_flush_redo(state); - - // if we have no free records, we have to make room, by sliding the - // existing records down - if (state->undo_point == STB_TEXTEDIT_UNDOSTATECOUNT) - stb_textedit_discard_undo(state); - - // if the characters to store won't possibly fit in the buffer, we can't undo - if (numchars > STB_TEXTEDIT_UNDOCHARCOUNT) { - state->undo_point = 0; - state->undo_char_point = 0; - return NULL; - } - - // if we don't have enough free characters in the buffer, we have to make room - while (state->undo_char_point + numchars > STB_TEXTEDIT_UNDOCHARCOUNT) - stb_textedit_discard_undo(state); - - return &state->undo_rec[state->undo_point++]; -} - -static STB_TEXTEDIT_CHARTYPE *stb_text_createundo(StbUndoState *state, int pos, int insert_len, int delete_len) -{ - StbUndoRecord *r = stb_text_create_undo_record(state, insert_len); - if (r == NULL) - return NULL; - - r->where = pos; - r->insert_length = (STB_TEXTEDIT_POSITIONTYPE) insert_len; - r->delete_length = (STB_TEXTEDIT_POSITIONTYPE) delete_len; - - if (insert_len == 0) { - r->char_storage = -1; - return NULL; - } else { - r->char_storage = state->undo_char_point; - state->undo_char_point += insert_len; - return &state->undo_char[r->char_storage]; - } -} - -static void stb_text_undo(STB_TEXTEDIT_STRING *str, STB_TexteditState *state) -{ - StbUndoState *s = &state->undostate; - StbUndoRecord u, *r; - if (s->undo_point == 0) - return; - - // we need to do two things: apply the undo record, and create a redo record - u = s->undo_rec[s->undo_point-1]; - r = &s->undo_rec[s->redo_point-1]; - r->char_storage = -1; - - r->insert_length = u.delete_length; - r->delete_length = u.insert_length; - r->where = u.where; - - if (u.delete_length) { - // if the undo record says to delete characters, then the redo record will - // need to re-insert the characters that get deleted, so we need to store - // them. - - // there are three cases: - // there's enough room to store the characters - // characters stored for *redoing* don't leave room for redo - // characters stored for *undoing* don't leave room for redo - // if the last is true, we have to bail - - if (s->undo_char_point + u.delete_length >= STB_TEXTEDIT_UNDOCHARCOUNT) { - // the undo records take up too much character space; there's no space to store the redo characters - r->insert_length = 0; - } else { - int i; - - // there's definitely room to store the characters eventually - while (s->undo_char_point + u.delete_length > s->redo_char_point) { - // should never happen: - if (s->redo_point == STB_TEXTEDIT_UNDOSTATECOUNT) - return; - // there's currently not enough room, so discard a redo record - stb_textedit_discard_redo(s); - } - r = &s->undo_rec[s->redo_point-1]; - - r->char_storage = s->redo_char_point - u.delete_length; - s->redo_char_point = s->redo_char_point - u.delete_length; - - // now save the characters - for (i=0; i < u.delete_length; ++i) - s->undo_char[r->char_storage + i] = STB_TEXTEDIT_GETCHAR(str, u.where + i); - } - - // now we can carry out the deletion - STB_TEXTEDIT_DELETECHARS(str, u.where, u.delete_length); - } - - // check type of recorded action: - if (u.insert_length) { - // easy case: was a deletion, so we need to insert n characters - STB_TEXTEDIT_INSERTCHARS(str, u.where, &s->undo_char[u.char_storage], u.insert_length); - s->undo_char_point -= u.insert_length; - } - - state->cursor = u.where + u.insert_length; - - s->undo_point--; - s->redo_point--; -} - -static void stb_text_redo(STB_TEXTEDIT_STRING *str, STB_TexteditState *state) -{ - StbUndoState *s = &state->undostate; - StbUndoRecord *u, r; - if (s->redo_point == STB_TEXTEDIT_UNDOSTATECOUNT) - return; - - // we need to do two things: apply the redo record, and create an undo record - u = &s->undo_rec[s->undo_point]; - r = s->undo_rec[s->redo_point]; - - // we KNOW there must be room for the undo record, because the redo record - // was derived from an undo record - - u->delete_length = r.insert_length; - u->insert_length = r.delete_length; - u->where = r.where; - u->char_storage = -1; - - if (r.delete_length) { - // the redo record requires us to delete characters, so the undo record - // needs to store the characters - - if (s->undo_char_point + u->insert_length > s->redo_char_point) { - u->insert_length = 0; - u->delete_length = 0; - } else { - int i; - u->char_storage = s->undo_char_point; - s->undo_char_point = s->undo_char_point + u->insert_length; - - // now save the characters - for (i=0; i < u->insert_length; ++i) - s->undo_char[u->char_storage + i] = STB_TEXTEDIT_GETCHAR(str, u->where + i); - } - - STB_TEXTEDIT_DELETECHARS(str, r.where, r.delete_length); - } - - if (r.insert_length) { - // easy case: need to insert n characters - STB_TEXTEDIT_INSERTCHARS(str, r.where, &s->undo_char[r.char_storage], r.insert_length); - s->redo_char_point += r.insert_length; - } - - state->cursor = r.where + r.insert_length; - - s->undo_point++; - s->redo_point++; -} - -static void stb_text_makeundo_insert(STB_TexteditState *state, int where, int length) -{ - stb_text_createundo(&state->undostate, where, 0, length); -} - -static void stb_text_makeundo_delete(STB_TEXTEDIT_STRING *str, STB_TexteditState *state, int where, int length) -{ - int i; - STB_TEXTEDIT_CHARTYPE *p = stb_text_createundo(&state->undostate, where, length, 0); - if (p) { - for (i=0; i < length; ++i) - p[i] = STB_TEXTEDIT_GETCHAR(str, where+i); - } -} - -static void stb_text_makeundo_replace(STB_TEXTEDIT_STRING *str, STB_TexteditState *state, int where, int old_length, int new_length) -{ - int i; - STB_TEXTEDIT_CHARTYPE *p = stb_text_createundo(&state->undostate, where, old_length, new_length); - if (p) { - for (i=0; i < old_length; ++i) - p[i] = STB_TEXTEDIT_GETCHAR(str, where+i); - } -} - -// reset the state to default -static void stb_textedit_clear_state(STB_TexteditState *state, int is_single_line) -{ - state->undostate.undo_point = 0; - state->undostate.undo_char_point = 0; - state->undostate.redo_point = STB_TEXTEDIT_UNDOSTATECOUNT; - state->undostate.redo_char_point = STB_TEXTEDIT_UNDOCHARCOUNT; - state->select_end = state->select_start = 0; - state->cursor = 0; - state->has_preferred_x = 0; - state->preferred_x = 0; - state->cursor_at_end_of_line = 0; - state->initialized = 1; - state->single_line = (unsigned char) is_single_line; - state->insert_mode = 0; - state->row_count_per_page = 0; -} - -// API initialize -static void stb_textedit_initialize_state(STB_TexteditState *state, int is_single_line) -{ - stb_textedit_clear_state(state, is_single_line); -} - -#if defined(__GNUC__) || defined(__clang__) -#pragma GCC diagnostic push -#pragma GCC diagnostic ignored "-Wcast-qual" -#endif - -static int stb_textedit_paste(STB_TEXTEDIT_STRING *str, STB_TexteditState *state, STB_TEXTEDIT_CHARTYPE const *ctext, int len) -{ - return stb_textedit_paste_internal(str, state, (STB_TEXTEDIT_CHARTYPE *) ctext, len); -} - -#if defined(__GNUC__) || defined(__clang__) -#pragma GCC diagnostic pop -#endif - -#endif//STB_TEXTEDIT_IMPLEMENTATION - -/* ------------------------------------------------------------------------------- -This software is available under 2 licenses -- choose whichever you prefer. ------------------------------------------------------------------------------- -ALTERNATIVE A - MIT License -Copyright (c) 2017 Sean Barrett -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. ------------------------------------------------------------------------------- -ALTERNATIVE B - Public Domain (www.unlicense.org) -This is free and unencumbered software released into the public domain. -Anyone is free to copy, modify, publish, use, compile, sell, or distribute this -software, either in source code form or as a compiled binary, for any purpose, -commercial or non-commercial, and by any means. -In jurisdictions that recognize copyright laws, the author or authors of this -software dedicate any and all copyright interest in the software to the public -domain. We make this dedication for the benefit of the public at large and to -the detriment of our heirs and successors. We intend this dedication to be an -overt act of relinquishment in perpetuity of all present and future rights to -this software under copyright law. -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 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. ------------------------------------------------------------------------------- -*/ diff --git a/app/jni/src/libultraship/extern/ImGui/imstb_truetype.h b/app/jni/src/libultraship/extern/ImGui/imstb_truetype.h deleted file mode 100644 index 35c827e..0000000 --- a/app/jni/src/libultraship/extern/ImGui/imstb_truetype.h +++ /dev/null @@ -1,5085 +0,0 @@ -// [DEAR IMGUI] -// This is a slightly modified version of stb_truetype.h 1.26. -// Mostly fixing for compiler and static analyzer warnings. -// Grep for [DEAR IMGUI] to find the changes. - -// stb_truetype.h - v1.26 - public domain -// authored from 2009-2021 by Sean Barrett / RAD Game Tools -// -// ======================================================================= -// -// NO SECURITY GUARANTEE -- DO NOT USE THIS ON UNTRUSTED FONT FILES -// -// This library does no range checking of the offsets found in the file, -// meaning an attacker can use it to read arbitrary memory. -// -// ======================================================================= -// -// This library processes TrueType files: -// parse files -// extract glyph metrics -// extract glyph shapes -// render glyphs to one-channel bitmaps with antialiasing (box filter) -// render glyphs to one-channel SDF bitmaps (signed-distance field/function) -// -// Todo: -// non-MS cmaps -// crashproof on bad data -// hinting? (no longer patented) -// cleartype-style AA? -// optimize: use simple memory allocator for intermediates -// optimize: build edge-list directly from curves -// optimize: rasterize directly from curves? -// -// ADDITIONAL CONTRIBUTORS -// -// Mikko Mononen: compound shape support, more cmap formats -// Tor Andersson: kerning, subpixel rendering -// Dougall Johnson: OpenType / Type 2 font handling -// Daniel Ribeiro Maciel: basic GPOS-based kerning -// -// Misc other: -// Ryan Gordon -// Simon Glass -// github:IntellectualKitty -// Imanol Celaya -// Daniel Ribeiro Maciel -// -// Bug/warning reports/fixes: -// "Zer" on mollyrocket Fabian "ryg" Giesen github:NiLuJe -// Cass Everitt Martins Mozeiko github:aloucks -// stoiko (Haemimont Games) Cap Petschulat github:oyvindjam -// Brian Hook Omar Cornut github:vassvik -// Walter van Niftrik Ryan Griege -// David Gow Peter LaValle -// David Given Sergey Popov -// Ivan-Assen Ivanov Giumo X. Clanjor -// Anthony Pesch Higor Euripedes -// Johan Duparc Thomas Fields -// Hou Qiming Derek Vinyard -// Rob Loach Cort Stratton -// Kenney Phillis Jr. Brian Costabile -// Ken Voskuil (kaesve) -// -// VERSION HISTORY -// -// 1.26 (2021-08-28) fix broken rasterizer -// 1.25 (2021-07-11) many fixes -// 1.24 (2020-02-05) fix warning -// 1.23 (2020-02-02) query SVG data for glyphs; query whole kerning table (but only kern not GPOS) -// 1.22 (2019-08-11) minimize missing-glyph duplication; fix kerning if both 'GPOS' and 'kern' are defined -// 1.21 (2019-02-25) fix warning -// 1.20 (2019-02-07) PackFontRange skips missing codepoints; GetScaleFontVMetrics() -// 1.19 (2018-02-11) GPOS kerning, STBTT_fmod -// 1.18 (2018-01-29) add missing function -// 1.17 (2017-07-23) make more arguments const; doc fix -// 1.16 (2017-07-12) SDF support -// 1.15 (2017-03-03) make more arguments const -// 1.14 (2017-01-16) num-fonts-in-TTC function -// 1.13 (2017-01-02) support OpenType fonts, certain Apple fonts -// 1.12 (2016-10-25) suppress warnings about casting away const with -Wcast-qual -// 1.11 (2016-04-02) fix unused-variable warning -// 1.10 (2016-04-02) user-defined fabs(); rare memory leak; remove duplicate typedef -// 1.09 (2016-01-16) warning fix; avoid crash on outofmem; use allocation userdata properly -// 1.08 (2015-09-13) document stbtt_Rasterize(); fixes for vertical & horizontal edges -// 1.07 (2015-08-01) allow PackFontRanges to accept arrays of sparse codepoints; -// variant PackFontRanges to pack and render in separate phases; -// fix stbtt_GetFontOFfsetForIndex (never worked for non-0 input?); -// fixed an assert() bug in the new rasterizer -// replace assert() with STBTT_assert() in new rasterizer -// -// Full history can be found at the end of this file. -// -// LICENSE -// -// See end of file for license information. -// -// USAGE -// -// Include this file in whatever places need to refer to it. In ONE C/C++ -// file, write: -// #define STB_TRUETYPE_IMPLEMENTATION -// before the #include of this file. This expands out the actual -// implementation into that C/C++ file. -// -// To make the implementation private to the file that generates the implementation, -// #define STBTT_STATIC -// -// Simple 3D API (don't ship this, but it's fine for tools and quick start) -// stbtt_BakeFontBitmap() -- bake a font to a bitmap for use as texture -// stbtt_GetBakedQuad() -- compute quad to draw for a given char -// -// Improved 3D API (more shippable): -// #include "stb_rect_pack.h" -- optional, but you really want it -// stbtt_PackBegin() -// stbtt_PackSetOversampling() -- for improved quality on small fonts -// stbtt_PackFontRanges() -- pack and renders -// stbtt_PackEnd() -// stbtt_GetPackedQuad() -// -// "Load" a font file from a memory buffer (you have to keep the buffer loaded) -// stbtt_InitFont() -// stbtt_GetFontOffsetForIndex() -- indexing for TTC font collections -// stbtt_GetNumberOfFonts() -- number of fonts for TTC font collections -// -// Render a unicode codepoint to a bitmap -// stbtt_GetCodepointBitmap() -- allocates and returns a bitmap -// stbtt_MakeCodepointBitmap() -- renders into bitmap you provide -// stbtt_GetCodepointBitmapBox() -- how big the bitmap must be -// -// Character advance/positioning -// stbtt_GetCodepointHMetrics() -// stbtt_GetFontVMetrics() -// stbtt_GetFontVMetricsOS2() -// stbtt_GetCodepointKernAdvance() -// -// Starting with version 1.06, the rasterizer was replaced with a new, -// faster and generally-more-precise rasterizer. The new rasterizer more -// accurately measures pixel coverage for anti-aliasing, except in the case -// where multiple shapes overlap, in which case it overestimates the AA pixel -// coverage. Thus, anti-aliasing of intersecting shapes may look wrong. If -// this turns out to be a problem, you can re-enable the old rasterizer with -// #define STBTT_RASTERIZER_VERSION 1 -// which will incur about a 15% speed hit. -// -// ADDITIONAL DOCUMENTATION -// -// Immediately after this block comment are a series of sample programs. -// -// After the sample programs is the "header file" section. This section -// includes documentation for each API function. -// -// Some important concepts to understand to use this library: -// -// Codepoint -// Characters are defined by unicode codepoints, e.g. 65 is -// uppercase A, 231 is lowercase c with a cedilla, 0x7e30 is -// the hiragana for "ma". -// -// Glyph -// A visual character shape (every codepoint is rendered as -// some glyph) -// -// Glyph index -// A font-specific integer ID representing a glyph -// -// Baseline -// Glyph shapes are defined relative to a baseline, which is the -// bottom of uppercase characters. Characters extend both above -// and below the baseline. -// -// Current Point -// As you draw text to the screen, you keep track of a "current point" -// which is the origin of each character. The current point's vertical -// position is the baseline. Even "baked fonts" use this model. -// -// Vertical Font Metrics -// The vertical qualities of the font, used to vertically position -// and space the characters. See docs for stbtt_GetFontVMetrics. -// -// Font Size in Pixels or Points -// The preferred interface for specifying font sizes in stb_truetype -// is to specify how tall the font's vertical extent should be in pixels. -// If that sounds good enough, skip the next paragraph. -// -// Most font APIs instead use "points", which are a common typographic -// measurement for describing font size, defined as 72 points per inch. -// stb_truetype provides a point API for compatibility. However, true -// "per inch" conventions don't make much sense on computer displays -// since different monitors have different number of pixels per -// inch. For example, Windows traditionally uses a convention that -// there are 96 pixels per inch, thus making 'inch' measurements have -// nothing to do with inches, and thus effectively defining a point to -// be 1.333 pixels. Additionally, the TrueType font data provides -// an explicit scale factor to scale a given font's glyphs to points, -// but the author has observed that this scale factor is often wrong -// for non-commercial fonts, thus making fonts scaled in points -// according to the TrueType spec incoherently sized in practice. -// -// DETAILED USAGE: -// -// Scale: -// Select how high you want the font to be, in points or pixels. -// Call ScaleForPixelHeight or ScaleForMappingEmToPixels to compute -// a scale factor SF that will be used by all other functions. -// -// Baseline: -// You need to select a y-coordinate that is the baseline of where -// your text will appear. Call GetFontBoundingBox to get the baseline-relative -// bounding box for all characters. SF*-y0 will be the distance in pixels -// that the worst-case character could extend above the baseline, so if -// you want the top edge of characters to appear at the top of the -// screen where y=0, then you would set the baseline to SF*-y0. -// -// Current point: -// Set the current point where the first character will appear. The -// first character could extend left of the current point; this is font -// dependent. You can either choose a current point that is the leftmost -// point and hope, or add some padding, or check the bounding box or -// left-side-bearing of the first character to be displayed and set -// the current point based on that. -// -// Displaying a character: -// Compute the bounding box of the character. It will contain signed values -// relative to . I.e. if it returns x0,y0,x1,y1, -// then the character should be displayed in the rectangle from -// to = 32 && *text < 128) { - stbtt_aligned_quad q; - stbtt_GetBakedQuad(cdata, 512,512, *text-32, &x,&y,&q,1);//1=opengl & d3d10+,0=d3d9 - glTexCoord2f(q.s0,q.t0); glVertex2f(q.x0,q.y0); - glTexCoord2f(q.s1,q.t0); glVertex2f(q.x1,q.y0); - glTexCoord2f(q.s1,q.t1); glVertex2f(q.x1,q.y1); - glTexCoord2f(q.s0,q.t1); glVertex2f(q.x0,q.y1); - } - ++text; - } - glEnd(); -} -#endif -// -// -////////////////////////////////////////////////////////////////////////////// -// -// Complete program (this compiles): get a single bitmap, print as ASCII art -// -#if 0 -#include -#define STB_TRUETYPE_IMPLEMENTATION // force following include to generate implementation -#include "stb_truetype.h" - -char ttf_buffer[1<<25]; - -int main(int argc, char **argv) -{ - stbtt_fontinfo font; - unsigned char *bitmap; - int w,h,i,j,c = (argc > 1 ? atoi(argv[1]) : 'a'), s = (argc > 2 ? atoi(argv[2]) : 20); - - fread(ttf_buffer, 1, 1<<25, fopen(argc > 3 ? argv[3] : "c:/windows/fonts/arialbd.ttf", "rb")); - - stbtt_InitFont(&font, ttf_buffer, stbtt_GetFontOffsetForIndex(ttf_buffer,0)); - bitmap = stbtt_GetCodepointBitmap(&font, 0,stbtt_ScaleForPixelHeight(&font, s), c, &w, &h, 0,0); - - for (j=0; j < h; ++j) { - for (i=0; i < w; ++i) - putchar(" .:ioVM@"[bitmap[j*w+i]>>5]); - putchar('\n'); - } - return 0; -} -#endif -// -// Output: -// -// .ii. -// @@@@@@. -// V@Mio@@o -// :i. V@V -// :oM@@M -// :@@@MM@M -// @@o o@M -// :@@. M@M -// @@@o@@@@ -// :M@@V:@@. -// -////////////////////////////////////////////////////////////////////////////// -// -// Complete program: print "Hello World!" banner, with bugs -// -#if 0 -char buffer[24<<20]; -unsigned char screen[20][79]; - -int main(int arg, char **argv) -{ - stbtt_fontinfo font; - int i,j,ascent,baseline,ch=0; - float scale, xpos=2; // leave a little padding in case the character extends left - char *text = "Heljo World!"; // intentionally misspelled to show 'lj' brokenness - - fread(buffer, 1, 1000000, fopen("c:/windows/fonts/arialbd.ttf", "rb")); - stbtt_InitFont(&font, buffer, 0); - - scale = stbtt_ScaleForPixelHeight(&font, 15); - stbtt_GetFontVMetrics(&font, &ascent,0,0); - baseline = (int) (ascent*scale); - - while (text[ch]) { - int advance,lsb,x0,y0,x1,y1; - float x_shift = xpos - (float) floor(xpos); - stbtt_GetCodepointHMetrics(&font, text[ch], &advance, &lsb); - stbtt_GetCodepointBitmapBoxSubpixel(&font, text[ch], scale,scale,x_shift,0, &x0,&y0,&x1,&y1); - stbtt_MakeCodepointBitmapSubpixel(&font, &screen[baseline + y0][(int) xpos + x0], x1-x0,y1-y0, 79, scale,scale,x_shift,0, text[ch]); - // note that this stomps the old data, so where character boxes overlap (e.g. 'lj') it's wrong - // because this API is really for baking character bitmaps into textures. if you want to render - // a sequence of characters, you really need to render each bitmap to a temp buffer, then - // "alpha blend" that into the working buffer - xpos += (advance * scale); - if (text[ch+1]) - xpos += scale*stbtt_GetCodepointKernAdvance(&font, text[ch],text[ch+1]); - ++ch; - } - - for (j=0; j < 20; ++j) { - for (i=0; i < 78; ++i) - putchar(" .:ioVM@"[screen[j][i]>>5]); - putchar('\n'); - } - - return 0; -} -#endif - - -////////////////////////////////////////////////////////////////////////////// -////////////////////////////////////////////////////////////////////////////// -//// -//// INTEGRATION WITH YOUR CODEBASE -//// -//// The following sections allow you to supply alternate definitions -//// of C library functions used by stb_truetype, e.g. if you don't -//// link with the C runtime library. - -#ifdef STB_TRUETYPE_IMPLEMENTATION - // #define your own (u)stbtt_int8/16/32 before including to override this - #ifndef stbtt_uint8 - typedef unsigned char stbtt_uint8; - typedef signed char stbtt_int8; - typedef unsigned short stbtt_uint16; - typedef signed short stbtt_int16; - typedef unsigned int stbtt_uint32; - typedef signed int stbtt_int32; - #endif - - typedef char stbtt__check_size32[sizeof(stbtt_int32)==4 ? 1 : -1]; - typedef char stbtt__check_size16[sizeof(stbtt_int16)==2 ? 1 : -1]; - - // e.g. #define your own STBTT_ifloor/STBTT_iceil() to avoid math.h - #ifndef STBTT_ifloor - #include - #define STBTT_ifloor(x) ((int) floor(x)) - #define STBTT_iceil(x) ((int) ceil(x)) - #endif - - #ifndef STBTT_sqrt - #include - #define STBTT_sqrt(x) sqrt(x) - #define STBTT_pow(x,y) pow(x,y) - #endif - - #ifndef STBTT_fmod - #include - #define STBTT_fmod(x,y) fmod(x,y) - #endif - - #ifndef STBTT_cos - #include - #define STBTT_cos(x) cos(x) - #define STBTT_acos(x) acos(x) - #endif - - #ifndef STBTT_fabs - #include - #define STBTT_fabs(x) fabs(x) - #endif - - // #define your own functions "STBTT_malloc" / "STBTT_free" to avoid malloc.h - #ifndef STBTT_malloc - #include - #define STBTT_malloc(x,u) ((void)(u),malloc(x)) - #define STBTT_free(x,u) ((void)(u),free(x)) - #endif - - #ifndef STBTT_assert - #include - #define STBTT_assert(x) assert(x) - #endif - - #ifndef STBTT_strlen - #include - #define STBTT_strlen(x) strlen(x) - #endif - - #ifndef STBTT_memcpy - #include - #define STBTT_memcpy memcpy - #define STBTT_memset memset - #endif -#endif - -/////////////////////////////////////////////////////////////////////////////// -/////////////////////////////////////////////////////////////////////////////// -//// -//// INTERFACE -//// -//// - -#ifndef __STB_INCLUDE_STB_TRUETYPE_H__ -#define __STB_INCLUDE_STB_TRUETYPE_H__ - -#ifdef STBTT_STATIC -#define STBTT_DEF static -#else -#define STBTT_DEF extern -#endif - -#ifdef __cplusplus -extern "C" { -#endif - -// private structure -typedef struct -{ - unsigned char *data; - int cursor; - int size; -} stbtt__buf; - -////////////////////////////////////////////////////////////////////////////// -// -// TEXTURE BAKING API -// -// If you use this API, you only have to call two functions ever. -// - -typedef struct -{ - unsigned short x0,y0,x1,y1; // coordinates of bbox in bitmap - float xoff,yoff,xadvance; -} stbtt_bakedchar; - -STBTT_DEF int stbtt_BakeFontBitmap(const unsigned char *data, int offset, // font location (use offset=0 for plain .ttf) - float pixel_height, // height of font in pixels - unsigned char *pixels, int pw, int ph, // bitmap to be filled in - int first_char, int num_chars, // characters to bake - stbtt_bakedchar *chardata); // you allocate this, it's num_chars long -// if return is positive, the first unused row of the bitmap -// if return is negative, returns the negative of the number of characters that fit -// if return is 0, no characters fit and no rows were used -// This uses a very crappy packing. - -typedef struct -{ - float x0,y0,s0,t0; // top-left - float x1,y1,s1,t1; // bottom-right -} stbtt_aligned_quad; - -STBTT_DEF void stbtt_GetBakedQuad(const stbtt_bakedchar *chardata, int pw, int ph, // same data as above - int char_index, // character to display - float *xpos, float *ypos, // pointers to current position in screen pixel space - stbtt_aligned_quad *q, // output: quad to draw - int opengl_fillrule); // true if opengl fill rule; false if DX9 or earlier -// Call GetBakedQuad with char_index = 'character - first_char', and it -// creates the quad you need to draw and advances the current position. -// -// The coordinate system used assumes y increases downwards. -// -// Characters will extend both above and below the current position; -// see discussion of "BASELINE" above. -// -// It's inefficient; you might want to c&p it and optimize it. - -STBTT_DEF void stbtt_GetScaledFontVMetrics(const unsigned char *fontdata, int index, float size, float *ascent, float *descent, float *lineGap); -// Query the font vertical metrics without having to create a font first. - - -////////////////////////////////////////////////////////////////////////////// -// -// NEW TEXTURE BAKING API -// -// This provides options for packing multiple fonts into one atlas, not -// perfectly but better than nothing. - -typedef struct -{ - unsigned short x0,y0,x1,y1; // coordinates of bbox in bitmap - float xoff,yoff,xadvance; - float xoff2,yoff2; -} stbtt_packedchar; - -typedef struct stbtt_pack_context stbtt_pack_context; -typedef struct stbtt_fontinfo stbtt_fontinfo; -#ifndef STB_RECT_PACK_VERSION -typedef struct stbrp_rect stbrp_rect; -#endif - -STBTT_DEF int stbtt_PackBegin(stbtt_pack_context *spc, unsigned char *pixels, int width, int height, int stride_in_bytes, int padding, void *alloc_context); -// Initializes a packing context stored in the passed-in stbtt_pack_context. -// Future calls using this context will pack characters into the bitmap passed -// in here: a 1-channel bitmap that is width * height. stride_in_bytes is -// the distance from one row to the next (or 0 to mean they are packed tightly -// together). "padding" is the amount of padding to leave between each -// character (normally you want '1' for bitmaps you'll use as textures with -// bilinear filtering). -// -// Returns 0 on failure, 1 on success. - -STBTT_DEF void stbtt_PackEnd (stbtt_pack_context *spc); -// Cleans up the packing context and frees all memory. - -#define STBTT_POINT_SIZE(x) (-(x)) - -STBTT_DEF int stbtt_PackFontRange(stbtt_pack_context *spc, const unsigned char *fontdata, int font_index, float font_size, - int first_unicode_char_in_range, int num_chars_in_range, stbtt_packedchar *chardata_for_range); -// Creates character bitmaps from the font_index'th font found in fontdata (use -// font_index=0 if you don't know what that is). It creates num_chars_in_range -// bitmaps for characters with unicode values starting at first_unicode_char_in_range -// and increasing. Data for how to render them is stored in chardata_for_range; -// pass these to stbtt_GetPackedQuad to get back renderable quads. -// -// font_size is the full height of the character from ascender to descender, -// as computed by stbtt_ScaleForPixelHeight. To use a point size as computed -// by stbtt_ScaleForMappingEmToPixels, wrap the point size in STBTT_POINT_SIZE() -// and pass that result as 'font_size': -// ..., 20 , ... // font max minus min y is 20 pixels tall -// ..., STBTT_POINT_SIZE(20), ... // 'M' is 20 pixels tall - -typedef struct -{ - float font_size; - int first_unicode_codepoint_in_range; // if non-zero, then the chars are continuous, and this is the first codepoint - int *array_of_unicode_codepoints; // if non-zero, then this is an array of unicode codepoints - int num_chars; - stbtt_packedchar *chardata_for_range; // output - unsigned char h_oversample, v_oversample; // don't set these, they're used internally -} stbtt_pack_range; - -STBTT_DEF int stbtt_PackFontRanges(stbtt_pack_context *spc, const unsigned char *fontdata, int font_index, stbtt_pack_range *ranges, int num_ranges); -// Creates character bitmaps from multiple ranges of characters stored in -// ranges. This will usually create a better-packed bitmap than multiple -// calls to stbtt_PackFontRange. Note that you can call this multiple -// times within a single PackBegin/PackEnd. - -STBTT_DEF void stbtt_PackSetOversampling(stbtt_pack_context *spc, unsigned int h_oversample, unsigned int v_oversample); -// Oversampling a font increases the quality by allowing higher-quality subpixel -// positioning, and is especially valuable at smaller text sizes. -// -// This function sets the amount of oversampling for all following calls to -// stbtt_PackFontRange(s) or stbtt_PackFontRangesGatherRects for a given -// pack context. The default (no oversampling) is achieved by h_oversample=1 -// and v_oversample=1. The total number of pixels required is -// h_oversample*v_oversample larger than the default; for example, 2x2 -// oversampling requires 4x the storage of 1x1. For best results, render -// oversampled textures with bilinear filtering. Look at the readme in -// stb/tests/oversample for information about oversampled fonts -// -// To use with PackFontRangesGather etc., you must set it before calls -// call to PackFontRangesGatherRects. - -STBTT_DEF void stbtt_PackSetSkipMissingCodepoints(stbtt_pack_context *spc, int skip); -// If skip != 0, this tells stb_truetype to skip any codepoints for which -// there is no corresponding glyph. If skip=0, which is the default, then -// codepoints without a glyph recived the font's "missing character" glyph, -// typically an empty box by convention. - -STBTT_DEF void stbtt_GetPackedQuad(const stbtt_packedchar *chardata, int pw, int ph, // same data as above - int char_index, // character to display - float *xpos, float *ypos, // pointers to current position in screen pixel space - stbtt_aligned_quad *q, // output: quad to draw - int align_to_integer); - -STBTT_DEF int stbtt_PackFontRangesGatherRects(stbtt_pack_context *spc, const stbtt_fontinfo *info, stbtt_pack_range *ranges, int num_ranges, stbrp_rect *rects); -STBTT_DEF void stbtt_PackFontRangesPackRects(stbtt_pack_context *spc, stbrp_rect *rects, int num_rects); -STBTT_DEF int stbtt_PackFontRangesRenderIntoRects(stbtt_pack_context *spc, const stbtt_fontinfo *info, stbtt_pack_range *ranges, int num_ranges, stbrp_rect *rects); -// Calling these functions in sequence is roughly equivalent to calling -// stbtt_PackFontRanges(). If you more control over the packing of multiple -// fonts, or if you want to pack custom data into a font texture, take a look -// at the source to of stbtt_PackFontRanges() and create a custom version -// using these functions, e.g. call GatherRects multiple times, -// building up a single array of rects, then call PackRects once, -// then call RenderIntoRects repeatedly. This may result in a -// better packing than calling PackFontRanges multiple times -// (or it may not). - -// this is an opaque structure that you shouldn't mess with which holds -// all the context needed from PackBegin to PackEnd. -struct stbtt_pack_context { - void *user_allocator_context; - void *pack_info; - int width; - int height; - int stride_in_bytes; - int padding; - int skip_missing; - unsigned int h_oversample, v_oversample; - unsigned char *pixels; - void *nodes; -}; - -////////////////////////////////////////////////////////////////////////////// -// -// FONT LOADING -// -// - -STBTT_DEF int stbtt_GetNumberOfFonts(const unsigned char *data); -// This function will determine the number of fonts in a font file. TrueType -// collection (.ttc) files may contain multiple fonts, while TrueType font -// (.ttf) files only contain one font. The number of fonts can be used for -// indexing with the previous function where the index is between zero and one -// less than the total fonts. If an error occurs, -1 is returned. - -STBTT_DEF int stbtt_GetFontOffsetForIndex(const unsigned char *data, int index); -// Each .ttf/.ttc file may have more than one font. Each font has a sequential -// index number starting from 0. Call this function to get the font offset for -// a given index; it returns -1 if the index is out of range. A regular .ttf -// file will only define one font and it always be at offset 0, so it will -// return '0' for index 0, and -1 for all other indices. - -// The following structure is defined publicly so you can declare one on -// the stack or as a global or etc, but you should treat it as opaque. -struct stbtt_fontinfo -{ - void * userdata; - unsigned char * data; // pointer to .ttf file - int fontstart; // offset of start of font - - int numGlyphs; // number of glyphs, needed for range checking - - int loca,head,glyf,hhea,hmtx,kern,gpos,svg; // table locations as offset from start of .ttf - int index_map; // a cmap mapping for our chosen character encoding - int indexToLocFormat; // format needed to map from glyph index to glyph - - stbtt__buf cff; // cff font data - stbtt__buf charstrings; // the charstring index - stbtt__buf gsubrs; // global charstring subroutines index - stbtt__buf subrs; // private charstring subroutines index - stbtt__buf fontdicts; // array of font dicts - stbtt__buf fdselect; // map from glyph to fontdict -}; - -STBTT_DEF int stbtt_InitFont(stbtt_fontinfo *info, const unsigned char *data, int offset); -// Given an offset into the file that defines a font, this function builds -// the necessary cached info for the rest of the system. You must allocate -// the stbtt_fontinfo yourself, and stbtt_InitFont will fill it out. You don't -// need to do anything special to free it, because the contents are pure -// value data with no additional data structures. Returns 0 on failure. - - -////////////////////////////////////////////////////////////////////////////// -// -// CHARACTER TO GLYPH-INDEX CONVERSIOn - -STBTT_DEF int stbtt_FindGlyphIndex(const stbtt_fontinfo *info, int unicode_codepoint); -// If you're going to perform multiple operations on the same character -// and you want a speed-up, call this function with the character you're -// going to process, then use glyph-based functions instead of the -// codepoint-based functions. -// Returns 0 if the character codepoint is not defined in the font. - - -////////////////////////////////////////////////////////////////////////////// -// -// CHARACTER PROPERTIES -// - -STBTT_DEF float stbtt_ScaleForPixelHeight(const stbtt_fontinfo *info, float pixels); -// computes a scale factor to produce a font whose "height" is 'pixels' tall. -// Height is measured as the distance from the highest ascender to the lowest -// descender; in other words, it's equivalent to calling stbtt_GetFontVMetrics -// and computing: -// scale = pixels / (ascent - descent) -// so if you prefer to measure height by the ascent only, use a similar calculation. - -STBTT_DEF float stbtt_ScaleForMappingEmToPixels(const stbtt_fontinfo *info, float pixels); -// computes a scale factor to produce a font whose EM size is mapped to -// 'pixels' tall. This is probably what traditional APIs compute, but -// I'm not positive. - -STBTT_DEF void stbtt_GetFontVMetrics(const stbtt_fontinfo *info, int *ascent, int *descent, int *lineGap); -// ascent is the coordinate above the baseline the font extends; descent -// is the coordinate below the baseline the font extends (i.e. it is typically negative) -// lineGap is the spacing between one row's descent and the next row's ascent... -// so you should advance the vertical position by "*ascent - *descent + *lineGap" -// these are expressed in unscaled coordinates, so you must multiply by -// the scale factor for a given size - -STBTT_DEF int stbtt_GetFontVMetricsOS2(const stbtt_fontinfo *info, int *typoAscent, int *typoDescent, int *typoLineGap); -// analogous to GetFontVMetrics, but returns the "typographic" values from the OS/2 -// table (specific to MS/Windows TTF files). -// -// Returns 1 on success (table present), 0 on failure. - -STBTT_DEF void stbtt_GetFontBoundingBox(const stbtt_fontinfo *info, int *x0, int *y0, int *x1, int *y1); -// the bounding box around all possible characters - -STBTT_DEF void stbtt_GetCodepointHMetrics(const stbtt_fontinfo *info, int codepoint, int *advanceWidth, int *leftSideBearing); -// leftSideBearing is the offset from the current horizontal position to the left edge of the character -// advanceWidth is the offset from the current horizontal position to the next horizontal position -// these are expressed in unscaled coordinates - -STBTT_DEF int stbtt_GetCodepointKernAdvance(const stbtt_fontinfo *info, int ch1, int ch2); -// an additional amount to add to the 'advance' value between ch1 and ch2 - -STBTT_DEF int stbtt_GetCodepointBox(const stbtt_fontinfo *info, int codepoint, int *x0, int *y0, int *x1, int *y1); -// Gets the bounding box of the visible part of the glyph, in unscaled coordinates - -STBTT_DEF void stbtt_GetGlyphHMetrics(const stbtt_fontinfo *info, int glyph_index, int *advanceWidth, int *leftSideBearing); -STBTT_DEF int stbtt_GetGlyphKernAdvance(const stbtt_fontinfo *info, int glyph1, int glyph2); -STBTT_DEF int stbtt_GetGlyphBox(const stbtt_fontinfo *info, int glyph_index, int *x0, int *y0, int *x1, int *y1); -// as above, but takes one or more glyph indices for greater efficiency - -typedef struct stbtt_kerningentry -{ - int glyph1; // use stbtt_FindGlyphIndex - int glyph2; - int advance; -} stbtt_kerningentry; - -STBTT_DEF int stbtt_GetKerningTableLength(const stbtt_fontinfo *info); -STBTT_DEF int stbtt_GetKerningTable(const stbtt_fontinfo *info, stbtt_kerningentry* table, int table_length); -// Retrieves a complete list of all of the kerning pairs provided by the font -// stbtt_GetKerningTable never writes more than table_length entries and returns how many entries it did write. -// The table will be sorted by (a.glyph1 == b.glyph1)?(a.glyph2 < b.glyph2):(a.glyph1 < b.glyph1) - -////////////////////////////////////////////////////////////////////////////// -// -// GLYPH SHAPES (you probably don't need these, but they have to go before -// the bitmaps for C declaration-order reasons) -// - -#ifndef STBTT_vmove // you can predefine these to use different values (but why?) - enum { - STBTT_vmove=1, - STBTT_vline, - STBTT_vcurve, - STBTT_vcubic - }; -#endif - -#ifndef stbtt_vertex // you can predefine this to use different values - // (we share this with other code at RAD) - #define stbtt_vertex_type short // can't use stbtt_int16 because that's not visible in the header file - typedef struct - { - stbtt_vertex_type x,y,cx,cy,cx1,cy1; - unsigned char type,padding; - } stbtt_vertex; -#endif - -STBTT_DEF int stbtt_IsGlyphEmpty(const stbtt_fontinfo *info, int glyph_index); -// returns non-zero if nothing is drawn for this glyph - -STBTT_DEF int stbtt_GetCodepointShape(const stbtt_fontinfo *info, int unicode_codepoint, stbtt_vertex **vertices); -STBTT_DEF int stbtt_GetGlyphShape(const stbtt_fontinfo *info, int glyph_index, stbtt_vertex **vertices); -// returns # of vertices and fills *vertices with the pointer to them -// these are expressed in "unscaled" coordinates -// -// The shape is a series of contours. Each one starts with -// a STBTT_moveto, then consists of a series of mixed -// STBTT_lineto and STBTT_curveto segments. A lineto -// draws a line from previous endpoint to its x,y; a curveto -// draws a quadratic bezier from previous endpoint to -// its x,y, using cx,cy as the bezier control point. - -STBTT_DEF void stbtt_FreeShape(const stbtt_fontinfo *info, stbtt_vertex *vertices); -// frees the data allocated above - -STBTT_DEF unsigned char *stbtt_FindSVGDoc(const stbtt_fontinfo *info, int gl); -STBTT_DEF int stbtt_GetCodepointSVG(const stbtt_fontinfo *info, int unicode_codepoint, const char **svg); -STBTT_DEF int stbtt_GetGlyphSVG(const stbtt_fontinfo *info, int gl, const char **svg); -// fills svg with the character's SVG data. -// returns data size or 0 if SVG not found. - -////////////////////////////////////////////////////////////////////////////// -// -// BITMAP RENDERING -// - -STBTT_DEF void stbtt_FreeBitmap(unsigned char *bitmap, void *userdata); -// frees the bitmap allocated below - -STBTT_DEF unsigned char *stbtt_GetCodepointBitmap(const stbtt_fontinfo *info, float scale_x, float scale_y, int codepoint, int *width, int *height, int *xoff, int *yoff); -// allocates a large-enough single-channel 8bpp bitmap and renders the -// specified character/glyph at the specified scale into it, with -// antialiasing. 0 is no coverage (transparent), 255 is fully covered (opaque). -// *width & *height are filled out with the width & height of the bitmap, -// which is stored left-to-right, top-to-bottom. -// -// xoff/yoff are the offset it pixel space from the glyph origin to the top-left of the bitmap - -STBTT_DEF unsigned char *stbtt_GetCodepointBitmapSubpixel(const stbtt_fontinfo *info, float scale_x, float scale_y, float shift_x, float shift_y, int codepoint, int *width, int *height, int *xoff, int *yoff); -// the same as stbtt_GetCodepoitnBitmap, but you can specify a subpixel -// shift for the character - -STBTT_DEF void stbtt_MakeCodepointBitmap(const stbtt_fontinfo *info, unsigned char *output, int out_w, int out_h, int out_stride, float scale_x, float scale_y, int codepoint); -// the same as stbtt_GetCodepointBitmap, but you pass in storage for the bitmap -// in the form of 'output', with row spacing of 'out_stride' bytes. the bitmap -// is clipped to out_w/out_h bytes. Call stbtt_GetCodepointBitmapBox to get the -// width and height and positioning info for it first. - -STBTT_DEF void stbtt_MakeCodepointBitmapSubpixel(const stbtt_fontinfo *info, unsigned char *output, int out_w, int out_h, int out_stride, float scale_x, float scale_y, float shift_x, float shift_y, int codepoint); -// same as stbtt_MakeCodepointBitmap, but you can specify a subpixel -// shift for the character - -STBTT_DEF void stbtt_MakeCodepointBitmapSubpixelPrefilter(const stbtt_fontinfo *info, unsigned char *output, int out_w, int out_h, int out_stride, float scale_x, float scale_y, float shift_x, float shift_y, int oversample_x, int oversample_y, float *sub_x, float *sub_y, int codepoint); -// same as stbtt_MakeCodepointBitmapSubpixel, but prefiltering -// is performed (see stbtt_PackSetOversampling) - -STBTT_DEF void stbtt_GetCodepointBitmapBox(const stbtt_fontinfo *font, int codepoint, float scale_x, float scale_y, int *ix0, int *iy0, int *ix1, int *iy1); -// get the bbox of the bitmap centered around the glyph origin; so the -// bitmap width is ix1-ix0, height is iy1-iy0, and location to place -// the bitmap top left is (leftSideBearing*scale,iy0). -// (Note that the bitmap uses y-increases-down, but the shape uses -// y-increases-up, so CodepointBitmapBox and CodepointBox are inverted.) - -STBTT_DEF void stbtt_GetCodepointBitmapBoxSubpixel(const stbtt_fontinfo *font, int codepoint, float scale_x, float scale_y, float shift_x, float shift_y, int *ix0, int *iy0, int *ix1, int *iy1); -// same as stbtt_GetCodepointBitmapBox, but you can specify a subpixel -// shift for the character - -// the following functions are equivalent to the above functions, but operate -// on glyph indices instead of Unicode codepoints (for efficiency) -STBTT_DEF unsigned char *stbtt_GetGlyphBitmap(const stbtt_fontinfo *info, float scale_x, float scale_y, int glyph, int *width, int *height, int *xoff, int *yoff); -STBTT_DEF unsigned char *stbtt_GetGlyphBitmapSubpixel(const stbtt_fontinfo *info, float scale_x, float scale_y, float shift_x, float shift_y, int glyph, int *width, int *height, int *xoff, int *yoff); -STBTT_DEF void stbtt_MakeGlyphBitmap(const stbtt_fontinfo *info, unsigned char *output, int out_w, int out_h, int out_stride, float scale_x, float scale_y, int glyph); -STBTT_DEF void stbtt_MakeGlyphBitmapSubpixel(const stbtt_fontinfo *info, unsigned char *output, int out_w, int out_h, int out_stride, float scale_x, float scale_y, float shift_x, float shift_y, int glyph); -STBTT_DEF void stbtt_MakeGlyphBitmapSubpixelPrefilter(const stbtt_fontinfo *info, unsigned char *output, int out_w, int out_h, int out_stride, float scale_x, float scale_y, float shift_x, float shift_y, int oversample_x, int oversample_y, float *sub_x, float *sub_y, int glyph); -STBTT_DEF void stbtt_GetGlyphBitmapBox(const stbtt_fontinfo *font, int glyph, float scale_x, float scale_y, int *ix0, int *iy0, int *ix1, int *iy1); -STBTT_DEF void stbtt_GetGlyphBitmapBoxSubpixel(const stbtt_fontinfo *font, int glyph, float scale_x, float scale_y,float shift_x, float shift_y, int *ix0, int *iy0, int *ix1, int *iy1); - - -// @TODO: don't expose this structure -typedef struct -{ - int w,h,stride; - unsigned char *pixels; -} stbtt__bitmap; - -// rasterize a shape with quadratic beziers into a bitmap -STBTT_DEF void stbtt_Rasterize(stbtt__bitmap *result, // 1-channel bitmap to draw into - float flatness_in_pixels, // allowable error of curve in pixels - stbtt_vertex *vertices, // array of vertices defining shape - int num_verts, // number of vertices in above array - float scale_x, float scale_y, // scale applied to input vertices - float shift_x, float shift_y, // translation applied to input vertices - int x_off, int y_off, // another translation applied to input - int invert, // if non-zero, vertically flip shape - void *userdata); // context for to STBTT_MALLOC - -////////////////////////////////////////////////////////////////////////////// -// -// Signed Distance Function (or Field) rendering - -STBTT_DEF void stbtt_FreeSDF(unsigned char *bitmap, void *userdata); -// frees the SDF bitmap allocated below - -STBTT_DEF unsigned char * stbtt_GetGlyphSDF(const stbtt_fontinfo *info, float scale, int glyph, int padding, unsigned char onedge_value, float pixel_dist_scale, int *width, int *height, int *xoff, int *yoff); -STBTT_DEF unsigned char * stbtt_GetCodepointSDF(const stbtt_fontinfo *info, float scale, int codepoint, int padding, unsigned char onedge_value, float pixel_dist_scale, int *width, int *height, int *xoff, int *yoff); -// These functions compute a discretized SDF field for a single character, suitable for storing -// in a single-channel texture, sampling with bilinear filtering, and testing against -// larger than some threshold to produce scalable fonts. -// info -- the font -// scale -- controls the size of the resulting SDF bitmap, same as it would be creating a regular bitmap -// glyph/codepoint -- the character to generate the SDF for -// padding -- extra "pixels" around the character which are filled with the distance to the character (not 0), -// which allows effects like bit outlines -// onedge_value -- value 0-255 to test the SDF against to reconstruct the character (i.e. the isocontour of the character) -// pixel_dist_scale -- what value the SDF should increase by when moving one SDF "pixel" away from the edge (on the 0..255 scale) -// if positive, > onedge_value is inside; if negative, < onedge_value is inside -// width,height -- output height & width of the SDF bitmap (including padding) -// xoff,yoff -- output origin of the character -// return value -- a 2D array of bytes 0..255, width*height in size -// -// pixel_dist_scale & onedge_value are a scale & bias that allows you to make -// optimal use of the limited 0..255 for your application, trading off precision -// and special effects. SDF values outside the range 0..255 are clamped to 0..255. -// -// Example: -// scale = stbtt_ScaleForPixelHeight(22) -// padding = 5 -// onedge_value = 180 -// pixel_dist_scale = 180/5.0 = 36.0 -// -// This will create an SDF bitmap in which the character is about 22 pixels -// high but the whole bitmap is about 22+5+5=32 pixels high. To produce a filled -// shape, sample the SDF at each pixel and fill the pixel if the SDF value -// is greater than or equal to 180/255. (You'll actually want to antialias, -// which is beyond the scope of this example.) Additionally, you can compute -// offset outlines (e.g. to stroke the character border inside & outside, -// or only outside). For example, to fill outside the character up to 3 SDF -// pixels, you would compare against (180-36.0*3)/255 = 72/255. The above -// choice of variables maps a range from 5 pixels outside the shape to -// 2 pixels inside the shape to 0..255; this is intended primarily for apply -// outside effects only (the interior range is needed to allow proper -// antialiasing of the font at *smaller* sizes) -// -// The function computes the SDF analytically at each SDF pixel, not by e.g. -// building a higher-res bitmap and approximating it. In theory the quality -// should be as high as possible for an SDF of this size & representation, but -// unclear if this is true in practice (perhaps building a higher-res bitmap -// and computing from that can allow drop-out prevention). -// -// The algorithm has not been optimized at all, so expect it to be slow -// if computing lots of characters or very large sizes. - - - -////////////////////////////////////////////////////////////////////////////// -// -// Finding the right font... -// -// You should really just solve this offline, keep your own tables -// of what font is what, and don't try to get it out of the .ttf file. -// That's because getting it out of the .ttf file is really hard, because -// the names in the file can appear in many possible encodings, in many -// possible languages, and e.g. if you need a case-insensitive comparison, -// the details of that depend on the encoding & language in a complex way -// (actually underspecified in truetype, but also gigantic). -// -// But you can use the provided functions in two possible ways: -// stbtt_FindMatchingFont() will use *case-sensitive* comparisons on -// unicode-encoded names to try to find the font you want; -// you can run this before calling stbtt_InitFont() -// -// stbtt_GetFontNameString() lets you get any of the various strings -// from the file yourself and do your own comparisons on them. -// You have to have called stbtt_InitFont() first. - - -STBTT_DEF int stbtt_FindMatchingFont(const unsigned char *fontdata, const char *name, int flags); -// returns the offset (not index) of the font that matches, or -1 if none -// if you use STBTT_MACSTYLE_DONTCARE, use a font name like "Arial Bold". -// if you use any other flag, use a font name like "Arial"; this checks -// the 'macStyle' header field; i don't know if fonts set this consistently -#define STBTT_MACSTYLE_DONTCARE 0 -#define STBTT_MACSTYLE_BOLD 1 -#define STBTT_MACSTYLE_ITALIC 2 -#define STBTT_MACSTYLE_UNDERSCORE 4 -#define STBTT_MACSTYLE_NONE 8 // <= not same as 0, this makes us check the bitfield is 0 - -STBTT_DEF int stbtt_CompareUTF8toUTF16_bigendian(const char *s1, int len1, const char *s2, int len2); -// returns 1/0 whether the first string interpreted as utf8 is identical to -// the second string interpreted as big-endian utf16... useful for strings from next func - -STBTT_DEF const char *stbtt_GetFontNameString(const stbtt_fontinfo *font, int *length, int platformID, int encodingID, int languageID, int nameID); -// returns the string (which may be big-endian double byte, e.g. for unicode) -// and puts the length in bytes in *length. -// -// some of the values for the IDs are below; for more see the truetype spec: -// http://developer.apple.com/textfonts/TTRefMan/RM06/Chap6name.html -// http://www.microsoft.com/typography/otspec/name.htm - -enum { // platformID - STBTT_PLATFORM_ID_UNICODE =0, - STBTT_PLATFORM_ID_MAC =1, - STBTT_PLATFORM_ID_ISO =2, - STBTT_PLATFORM_ID_MICROSOFT =3 -}; - -enum { // encodingID for STBTT_PLATFORM_ID_UNICODE - STBTT_UNICODE_EID_UNICODE_1_0 =0, - STBTT_UNICODE_EID_UNICODE_1_1 =1, - STBTT_UNICODE_EID_ISO_10646 =2, - STBTT_UNICODE_EID_UNICODE_2_0_BMP=3, - STBTT_UNICODE_EID_UNICODE_2_0_FULL=4 -}; - -enum { // encodingID for STBTT_PLATFORM_ID_MICROSOFT - STBTT_MS_EID_SYMBOL =0, - STBTT_MS_EID_UNICODE_BMP =1, - STBTT_MS_EID_SHIFTJIS =2, - STBTT_MS_EID_UNICODE_FULL =10 -}; - -enum { // encodingID for STBTT_PLATFORM_ID_MAC; same as Script Manager codes - STBTT_MAC_EID_ROMAN =0, STBTT_MAC_EID_ARABIC =4, - STBTT_MAC_EID_JAPANESE =1, STBTT_MAC_EID_HEBREW =5, - STBTT_MAC_EID_CHINESE_TRAD =2, STBTT_MAC_EID_GREEK =6, - STBTT_MAC_EID_KOREAN =3, STBTT_MAC_EID_RUSSIAN =7 -}; - -enum { // languageID for STBTT_PLATFORM_ID_MICROSOFT; same as LCID... - // problematic because there are e.g. 16 english LCIDs and 16 arabic LCIDs - STBTT_MS_LANG_ENGLISH =0x0409, STBTT_MS_LANG_ITALIAN =0x0410, - STBTT_MS_LANG_CHINESE =0x0804, STBTT_MS_LANG_JAPANESE =0x0411, - STBTT_MS_LANG_DUTCH =0x0413, STBTT_MS_LANG_KOREAN =0x0412, - STBTT_MS_LANG_FRENCH =0x040c, STBTT_MS_LANG_RUSSIAN =0x0419, - STBTT_MS_LANG_GERMAN =0x0407, STBTT_MS_LANG_SPANISH =0x0409, - STBTT_MS_LANG_HEBREW =0x040d, STBTT_MS_LANG_SWEDISH =0x041D -}; - -enum { // languageID for STBTT_PLATFORM_ID_MAC - STBTT_MAC_LANG_ENGLISH =0 , STBTT_MAC_LANG_JAPANESE =11, - STBTT_MAC_LANG_ARABIC =12, STBTT_MAC_LANG_KOREAN =23, - STBTT_MAC_LANG_DUTCH =4 , STBTT_MAC_LANG_RUSSIAN =32, - STBTT_MAC_LANG_FRENCH =1 , STBTT_MAC_LANG_SPANISH =6 , - STBTT_MAC_LANG_GERMAN =2 , STBTT_MAC_LANG_SWEDISH =5 , - STBTT_MAC_LANG_HEBREW =10, STBTT_MAC_LANG_CHINESE_SIMPLIFIED =33, - STBTT_MAC_LANG_ITALIAN =3 , STBTT_MAC_LANG_CHINESE_TRAD =19 -}; - -#ifdef __cplusplus -} -#endif - -#endif // __STB_INCLUDE_STB_TRUETYPE_H__ - -/////////////////////////////////////////////////////////////////////////////// -/////////////////////////////////////////////////////////////////////////////// -//// -//// IMPLEMENTATION -//// -//// - -#ifdef STB_TRUETYPE_IMPLEMENTATION - -#ifndef STBTT_MAX_OVERSAMPLE -#define STBTT_MAX_OVERSAMPLE 8 -#endif - -#if STBTT_MAX_OVERSAMPLE > 255 -#error "STBTT_MAX_OVERSAMPLE cannot be > 255" -#endif - -typedef int stbtt__test_oversample_pow2[(STBTT_MAX_OVERSAMPLE & (STBTT_MAX_OVERSAMPLE-1)) == 0 ? 1 : -1]; - -#ifndef STBTT_RASTERIZER_VERSION -#define STBTT_RASTERIZER_VERSION 2 -#endif - -#ifdef _MSC_VER -#define STBTT__NOTUSED(v) (void)(v) -#else -#define STBTT__NOTUSED(v) (void)sizeof(v) -#endif - -////////////////////////////////////////////////////////////////////////// -// -// stbtt__buf helpers to parse data from file -// - -static stbtt_uint8 stbtt__buf_get8(stbtt__buf *b) -{ - if (b->cursor >= b->size) - return 0; - return b->data[b->cursor++]; -} - -static stbtt_uint8 stbtt__buf_peek8(stbtt__buf *b) -{ - if (b->cursor >= b->size) - return 0; - return b->data[b->cursor]; -} - -static void stbtt__buf_seek(stbtt__buf *b, int o) -{ - STBTT_assert(!(o > b->size || o < 0)); - b->cursor = (o > b->size || o < 0) ? b->size : o; -} - -static void stbtt__buf_skip(stbtt__buf *b, int o) -{ - stbtt__buf_seek(b, b->cursor + o); -} - -static stbtt_uint32 stbtt__buf_get(stbtt__buf *b, int n) -{ - stbtt_uint32 v = 0; - int i; - STBTT_assert(n >= 1 && n <= 4); - for (i = 0; i < n; i++) - v = (v << 8) | stbtt__buf_get8(b); - return v; -} - -static stbtt__buf stbtt__new_buf(const void *p, size_t size) -{ - stbtt__buf r; - STBTT_assert(size < 0x40000000); - r.data = (stbtt_uint8*) p; - r.size = (int) size; - r.cursor = 0; - return r; -} - -#define stbtt__buf_get16(b) stbtt__buf_get((b), 2) -#define stbtt__buf_get32(b) stbtt__buf_get((b), 4) - -static stbtt__buf stbtt__buf_range(const stbtt__buf *b, int o, int s) -{ - stbtt__buf r = stbtt__new_buf(NULL, 0); - if (o < 0 || s < 0 || o > b->size || s > b->size - o) return r; - r.data = b->data + o; - r.size = s; - return r; -} - -static stbtt__buf stbtt__cff_get_index(stbtt__buf *b) -{ - int count, start, offsize; - start = b->cursor; - count = stbtt__buf_get16(b); - if (count) { - offsize = stbtt__buf_get8(b); - STBTT_assert(offsize >= 1 && offsize <= 4); - stbtt__buf_skip(b, offsize * count); - stbtt__buf_skip(b, stbtt__buf_get(b, offsize) - 1); - } - return stbtt__buf_range(b, start, b->cursor - start); -} - -static stbtt_uint32 stbtt__cff_int(stbtt__buf *b) -{ - int b0 = stbtt__buf_get8(b); - if (b0 >= 32 && b0 <= 246) return b0 - 139; - else if (b0 >= 247 && b0 <= 250) return (b0 - 247)*256 + stbtt__buf_get8(b) + 108; - else if (b0 >= 251 && b0 <= 254) return -(b0 - 251)*256 - stbtt__buf_get8(b) - 108; - else if (b0 == 28) return stbtt__buf_get16(b); - else if (b0 == 29) return stbtt__buf_get32(b); - STBTT_assert(0); - return 0; -} - -static void stbtt__cff_skip_operand(stbtt__buf *b) { - int v, b0 = stbtt__buf_peek8(b); - STBTT_assert(b0 >= 28); - if (b0 == 30) { - stbtt__buf_skip(b, 1); - while (b->cursor < b->size) { - v = stbtt__buf_get8(b); - if ((v & 0xF) == 0xF || (v >> 4) == 0xF) - break; - } - } else { - stbtt__cff_int(b); - } -} - -static stbtt__buf stbtt__dict_get(stbtt__buf *b, int key) -{ - stbtt__buf_seek(b, 0); - while (b->cursor < b->size) { - int start = b->cursor, end, op; - while (stbtt__buf_peek8(b) >= 28) - stbtt__cff_skip_operand(b); - end = b->cursor; - op = stbtt__buf_get8(b); - if (op == 12) op = stbtt__buf_get8(b) | 0x100; - if (op == key) return stbtt__buf_range(b, start, end-start); - } - return stbtt__buf_range(b, 0, 0); -} - -static void stbtt__dict_get_ints(stbtt__buf *b, int key, int outcount, stbtt_uint32 *out) -{ - int i; - stbtt__buf operands = stbtt__dict_get(b, key); - for (i = 0; i < outcount && operands.cursor < operands.size; i++) - out[i] = stbtt__cff_int(&operands); -} - -static int stbtt__cff_index_count(stbtt__buf *b) -{ - stbtt__buf_seek(b, 0); - return stbtt__buf_get16(b); -} - -static stbtt__buf stbtt__cff_index_get(stbtt__buf b, int i) -{ - int count, offsize, start, end; - stbtt__buf_seek(&b, 0); - count = stbtt__buf_get16(&b); - offsize = stbtt__buf_get8(&b); - STBTT_assert(i >= 0 && i < count); - STBTT_assert(offsize >= 1 && offsize <= 4); - stbtt__buf_skip(&b, i*offsize); - start = stbtt__buf_get(&b, offsize); - end = stbtt__buf_get(&b, offsize); - return stbtt__buf_range(&b, 2+(count+1)*offsize+start, end - start); -} - -////////////////////////////////////////////////////////////////////////// -// -// accessors to parse data from file -// - -// on platforms that don't allow misaligned reads, if we want to allow -// truetype fonts that aren't padded to alignment, define ALLOW_UNALIGNED_TRUETYPE - -#define ttBYTE(p) (* (stbtt_uint8 *) (p)) -#define ttCHAR(p) (* (stbtt_int8 *) (p)) -#define ttFixed(p) ttLONG(p) - -static stbtt_uint16 ttUSHORT(stbtt_uint8 *p) { return p[0]*256 + p[1]; } -static stbtt_int16 ttSHORT(stbtt_uint8 *p) { return p[0]*256 + p[1]; } -static stbtt_uint32 ttULONG(stbtt_uint8 *p) { return (p[0]<<24) + (p[1]<<16) + (p[2]<<8) + p[3]; } -static stbtt_int32 ttLONG(stbtt_uint8 *p) { return (p[0]<<24) + (p[1]<<16) + (p[2]<<8) + p[3]; } - -#define stbtt_tag4(p,c0,c1,c2,c3) ((p)[0] == (c0) && (p)[1] == (c1) && (p)[2] == (c2) && (p)[3] == (c3)) -#define stbtt_tag(p,str) stbtt_tag4(p,str[0],str[1],str[2],str[3]) - -static int stbtt__isfont(stbtt_uint8 *font) -{ - // check the version number - if (stbtt_tag4(font, '1',0,0,0)) return 1; // TrueType 1 - if (stbtt_tag(font, "typ1")) return 1; // TrueType with type 1 font -- we don't support this! - if (stbtt_tag(font, "OTTO")) return 1; // OpenType with CFF - if (stbtt_tag4(font, 0,1,0,0)) return 1; // OpenType 1.0 - if (stbtt_tag(font, "true")) return 1; // Apple specification for TrueType fonts - return 0; -} - -// @OPTIMIZE: binary search -static stbtt_uint32 stbtt__find_table(stbtt_uint8 *data, stbtt_uint32 fontstart, const char *tag) -{ - stbtt_int32 num_tables = ttUSHORT(data+fontstart+4); - stbtt_uint32 tabledir = fontstart + 12; - stbtt_int32 i; - for (i=0; i < num_tables; ++i) { - stbtt_uint32 loc = tabledir + 16*i; - if (stbtt_tag(data+loc+0, tag)) - return ttULONG(data+loc+8); - } - return 0; -} - -static int stbtt_GetFontOffsetForIndex_internal(unsigned char *font_collection, int index) -{ - // if it's just a font, there's only one valid index - if (stbtt__isfont(font_collection)) - return index == 0 ? 0 : -1; - - // check if it's a TTC - if (stbtt_tag(font_collection, "ttcf")) { - // version 1? - if (ttULONG(font_collection+4) == 0x00010000 || ttULONG(font_collection+4) == 0x00020000) { - stbtt_int32 n = ttLONG(font_collection+8); - if (index >= n) - return -1; - return ttULONG(font_collection+12+index*4); - } - } - return -1; -} - -static int stbtt_GetNumberOfFonts_internal(unsigned char *font_collection) -{ - // if it's just a font, there's only one valid font - if (stbtt__isfont(font_collection)) - return 1; - - // check if it's a TTC - if (stbtt_tag(font_collection, "ttcf")) { - // version 1? - if (ttULONG(font_collection+4) == 0x00010000 || ttULONG(font_collection+4) == 0x00020000) { - return ttLONG(font_collection+8); - } - } - return 0; -} - -static stbtt__buf stbtt__get_subrs(stbtt__buf cff, stbtt__buf fontdict) -{ - stbtt_uint32 subrsoff = 0, private_loc[2] = { 0, 0 }; - stbtt__buf pdict; - stbtt__dict_get_ints(&fontdict, 18, 2, private_loc); - if (!private_loc[1] || !private_loc[0]) return stbtt__new_buf(NULL, 0); - pdict = stbtt__buf_range(&cff, private_loc[1], private_loc[0]); - stbtt__dict_get_ints(&pdict, 19, 1, &subrsoff); - if (!subrsoff) return stbtt__new_buf(NULL, 0); - stbtt__buf_seek(&cff, private_loc[1]+subrsoff); - return stbtt__cff_get_index(&cff); -} - -// since most people won't use this, find this table the first time it's needed -static int stbtt__get_svg(stbtt_fontinfo *info) -{ - stbtt_uint32 t; - if (info->svg < 0) { - t = stbtt__find_table(info->data, info->fontstart, "SVG "); - if (t) { - stbtt_uint32 offset = ttULONG(info->data + t + 2); - info->svg = t + offset; - } else { - info->svg = 0; - } - } - return info->svg; -} - -static int stbtt_InitFont_internal(stbtt_fontinfo *info, unsigned char *data, int fontstart) -{ - stbtt_uint32 cmap, t; - stbtt_int32 i,numTables; - - info->data = data; - info->fontstart = fontstart; - info->cff = stbtt__new_buf(NULL, 0); - - cmap = stbtt__find_table(data, fontstart, "cmap"); // required - info->loca = stbtt__find_table(data, fontstart, "loca"); // required - info->head = stbtt__find_table(data, fontstart, "head"); // required - info->glyf = stbtt__find_table(data, fontstart, "glyf"); // required - info->hhea = stbtt__find_table(data, fontstart, "hhea"); // required - info->hmtx = stbtt__find_table(data, fontstart, "hmtx"); // required - info->kern = stbtt__find_table(data, fontstart, "kern"); // not required - info->gpos = stbtt__find_table(data, fontstart, "GPOS"); // not required - - if (!cmap || !info->head || !info->hhea || !info->hmtx) - return 0; - if (info->glyf) { - // required for truetype - if (!info->loca) return 0; - } else { - // initialization for CFF / Type2 fonts (OTF) - stbtt__buf b, topdict, topdictidx; - stbtt_uint32 cstype = 2, charstrings = 0, fdarrayoff = 0, fdselectoff = 0; - stbtt_uint32 cff; - - cff = stbtt__find_table(data, fontstart, "CFF "); - if (!cff) return 0; - - info->fontdicts = stbtt__new_buf(NULL, 0); - info->fdselect = stbtt__new_buf(NULL, 0); - - // @TODO this should use size from table (not 512MB) - info->cff = stbtt__new_buf(data+cff, 512*1024*1024); - b = info->cff; - - // read the header - stbtt__buf_skip(&b, 2); - stbtt__buf_seek(&b, stbtt__buf_get8(&b)); // hdrsize - - // @TODO the name INDEX could list multiple fonts, - // but we just use the first one. - stbtt__cff_get_index(&b); // name INDEX - topdictidx = stbtt__cff_get_index(&b); - topdict = stbtt__cff_index_get(topdictidx, 0); - stbtt__cff_get_index(&b); // string INDEX - info->gsubrs = stbtt__cff_get_index(&b); - - stbtt__dict_get_ints(&topdict, 17, 1, &charstrings); - stbtt__dict_get_ints(&topdict, 0x100 | 6, 1, &cstype); - stbtt__dict_get_ints(&topdict, 0x100 | 36, 1, &fdarrayoff); - stbtt__dict_get_ints(&topdict, 0x100 | 37, 1, &fdselectoff); - info->subrs = stbtt__get_subrs(b, topdict); - - // we only support Type 2 charstrings - if (cstype != 2) return 0; - if (charstrings == 0) return 0; - - if (fdarrayoff) { - // looks like a CID font - if (!fdselectoff) return 0; - stbtt__buf_seek(&b, fdarrayoff); - info->fontdicts = stbtt__cff_get_index(&b); - info->fdselect = stbtt__buf_range(&b, fdselectoff, b.size-fdselectoff); - } - - stbtt__buf_seek(&b, charstrings); - info->charstrings = stbtt__cff_get_index(&b); - } - - t = stbtt__find_table(data, fontstart, "maxp"); - if (t) - info->numGlyphs = ttUSHORT(data+t+4); - else - info->numGlyphs = 0xffff; - - info->svg = -1; - - // find a cmap encoding table we understand *now* to avoid searching - // later. (todo: could make this installable) - // the same regardless of glyph. - numTables = ttUSHORT(data + cmap + 2); - info->index_map = 0; - for (i=0; i < numTables; ++i) { - stbtt_uint32 encoding_record = cmap + 4 + 8 * i; - // find an encoding we understand: - switch(ttUSHORT(data+encoding_record)) { - case STBTT_PLATFORM_ID_MICROSOFT: - switch (ttUSHORT(data+encoding_record+2)) { - case STBTT_MS_EID_UNICODE_BMP: - case STBTT_MS_EID_UNICODE_FULL: - // MS/Unicode - info->index_map = cmap + ttULONG(data+encoding_record+4); - break; - } - break; - case STBTT_PLATFORM_ID_UNICODE: - // Mac/iOS has these - // all the encodingIDs are unicode, so we don't bother to check it - info->index_map = cmap + ttULONG(data+encoding_record+4); - break; - } - } - if (info->index_map == 0) - return 0; - - info->indexToLocFormat = ttUSHORT(data+info->head + 50); - return 1; -} - -STBTT_DEF int stbtt_FindGlyphIndex(const stbtt_fontinfo *info, int unicode_codepoint) -{ - stbtt_uint8 *data = info->data; - stbtt_uint32 index_map = info->index_map; - - stbtt_uint16 format = ttUSHORT(data + index_map + 0); - if (format == 0) { // apple byte encoding - stbtt_int32 bytes = ttUSHORT(data + index_map + 2); - if (unicode_codepoint < bytes-6) - return ttBYTE(data + index_map + 6 + unicode_codepoint); - return 0; - } else if (format == 6) { - stbtt_uint32 first = ttUSHORT(data + index_map + 6); - stbtt_uint32 count = ttUSHORT(data + index_map + 8); - if ((stbtt_uint32) unicode_codepoint >= first && (stbtt_uint32) unicode_codepoint < first+count) - return ttUSHORT(data + index_map + 10 + (unicode_codepoint - first)*2); - return 0; - } else if (format == 2) { - STBTT_assert(0); // @TODO: high-byte mapping for japanese/chinese/korean - return 0; - } else if (format == 4) { // standard mapping for windows fonts: binary search collection of ranges - stbtt_uint16 segcount = ttUSHORT(data+index_map+6) >> 1; - stbtt_uint16 searchRange = ttUSHORT(data+index_map+8) >> 1; - stbtt_uint16 entrySelector = ttUSHORT(data+index_map+10); - stbtt_uint16 rangeShift = ttUSHORT(data+index_map+12) >> 1; - - // do a binary search of the segments - stbtt_uint32 endCount = index_map + 14; - stbtt_uint32 search = endCount; - - if (unicode_codepoint > 0xffff) - return 0; - - // they lie from endCount .. endCount + segCount - // but searchRange is the nearest power of two, so... - if (unicode_codepoint >= ttUSHORT(data + search + rangeShift*2)) - search += rangeShift*2; - - // now decrement to bias correctly to find smallest - search -= 2; - while (entrySelector) { - stbtt_uint16 end; - searchRange >>= 1; - end = ttUSHORT(data + search + searchRange*2); - if (unicode_codepoint > end) - search += searchRange*2; - --entrySelector; - } - search += 2; - - { - stbtt_uint16 offset, start, last; - stbtt_uint16 item = (stbtt_uint16) ((search - endCount) >> 1); - - start = ttUSHORT(data + index_map + 14 + segcount*2 + 2 + 2*item); - last = ttUSHORT(data + endCount + 2*item); - if (unicode_codepoint < start || unicode_codepoint > last) - return 0; - - offset = ttUSHORT(data + index_map + 14 + segcount*6 + 2 + 2*item); - if (offset == 0) - return (stbtt_uint16) (unicode_codepoint + ttSHORT(data + index_map + 14 + segcount*4 + 2 + 2*item)); - - return ttUSHORT(data + offset + (unicode_codepoint-start)*2 + index_map + 14 + segcount*6 + 2 + 2*item); - } - } else if (format == 12 || format == 13) { - stbtt_uint32 ngroups = ttULONG(data+index_map+12); - stbtt_int32 low,high; - low = 0; high = (stbtt_int32)ngroups; - // Binary search the right group. - while (low < high) { - stbtt_int32 mid = low + ((high-low) >> 1); // rounds down, so low <= mid < high - stbtt_uint32 start_char = ttULONG(data+index_map+16+mid*12); - stbtt_uint32 end_char = ttULONG(data+index_map+16+mid*12+4); - if ((stbtt_uint32) unicode_codepoint < start_char) - high = mid; - else if ((stbtt_uint32) unicode_codepoint > end_char) - low = mid+1; - else { - stbtt_uint32 start_glyph = ttULONG(data+index_map+16+mid*12+8); - if (format == 12) - return start_glyph + unicode_codepoint-start_char; - else // format == 13 - return start_glyph; - } - } - return 0; // not found - } - // @TODO - STBTT_assert(0); - return 0; -} - -STBTT_DEF int stbtt_GetCodepointShape(const stbtt_fontinfo *info, int unicode_codepoint, stbtt_vertex **vertices) -{ - return stbtt_GetGlyphShape(info, stbtt_FindGlyphIndex(info, unicode_codepoint), vertices); -} - -static void stbtt_setvertex(stbtt_vertex *v, stbtt_uint8 type, stbtt_int32 x, stbtt_int32 y, stbtt_int32 cx, stbtt_int32 cy) -{ - v->type = type; - v->x = (stbtt_int16) x; - v->y = (stbtt_int16) y; - v->cx = (stbtt_int16) cx; - v->cy = (stbtt_int16) cy; -} - -static int stbtt__GetGlyfOffset(const stbtt_fontinfo *info, int glyph_index) -{ - int g1,g2; - - STBTT_assert(!info->cff.size); - - if (glyph_index >= info->numGlyphs) return -1; // glyph index out of range - if (info->indexToLocFormat >= 2) return -1; // unknown index->glyph map format - - if (info->indexToLocFormat == 0) { - g1 = info->glyf + ttUSHORT(info->data + info->loca + glyph_index * 2) * 2; - g2 = info->glyf + ttUSHORT(info->data + info->loca + glyph_index * 2 + 2) * 2; - } else { - g1 = info->glyf + ttULONG (info->data + info->loca + glyph_index * 4); - g2 = info->glyf + ttULONG (info->data + info->loca + glyph_index * 4 + 4); - } - - return g1==g2 ? -1 : g1; // if length is 0, return -1 -} - -static int stbtt__GetGlyphInfoT2(const stbtt_fontinfo *info, int glyph_index, int *x0, int *y0, int *x1, int *y1); - -STBTT_DEF int stbtt_GetGlyphBox(const stbtt_fontinfo *info, int glyph_index, int *x0, int *y0, int *x1, int *y1) -{ - if (info->cff.size) { - stbtt__GetGlyphInfoT2(info, glyph_index, x0, y0, x1, y1); - } else { - int g = stbtt__GetGlyfOffset(info, glyph_index); - if (g < 0) return 0; - - if (x0) *x0 = ttSHORT(info->data + g + 2); - if (y0) *y0 = ttSHORT(info->data + g + 4); - if (x1) *x1 = ttSHORT(info->data + g + 6); - if (y1) *y1 = ttSHORT(info->data + g + 8); - } - return 1; -} - -STBTT_DEF int stbtt_GetCodepointBox(const stbtt_fontinfo *info, int codepoint, int *x0, int *y0, int *x1, int *y1) -{ - return stbtt_GetGlyphBox(info, stbtt_FindGlyphIndex(info,codepoint), x0,y0,x1,y1); -} - -STBTT_DEF int stbtt_IsGlyphEmpty(const stbtt_fontinfo *info, int glyph_index) -{ - stbtt_int16 numberOfContours; - int g; - if (info->cff.size) - return stbtt__GetGlyphInfoT2(info, glyph_index, NULL, NULL, NULL, NULL) == 0; - g = stbtt__GetGlyfOffset(info, glyph_index); - if (g < 0) return 1; - numberOfContours = ttSHORT(info->data + g); - return numberOfContours == 0; -} - -static int stbtt__close_shape(stbtt_vertex *vertices, int num_vertices, int was_off, int start_off, - stbtt_int32 sx, stbtt_int32 sy, stbtt_int32 scx, stbtt_int32 scy, stbtt_int32 cx, stbtt_int32 cy) -{ - if (start_off) { - if (was_off) - stbtt_setvertex(&vertices[num_vertices++], STBTT_vcurve, (cx+scx)>>1, (cy+scy)>>1, cx,cy); - stbtt_setvertex(&vertices[num_vertices++], STBTT_vcurve, sx,sy,scx,scy); - } else { - if (was_off) - stbtt_setvertex(&vertices[num_vertices++], STBTT_vcurve,sx,sy,cx,cy); - else - stbtt_setvertex(&vertices[num_vertices++], STBTT_vline,sx,sy,0,0); - } - return num_vertices; -} - -static int stbtt__GetGlyphShapeTT(const stbtt_fontinfo *info, int glyph_index, stbtt_vertex **pvertices) -{ - stbtt_int16 numberOfContours; - stbtt_uint8 *endPtsOfContours; - stbtt_uint8 *data = info->data; - stbtt_vertex *vertices=0; - int num_vertices=0; - int g = stbtt__GetGlyfOffset(info, glyph_index); - - *pvertices = NULL; - - if (g < 0) return 0; - - numberOfContours = ttSHORT(data + g); - - if (numberOfContours > 0) { - stbtt_uint8 flags=0,flagcount; - stbtt_int32 ins, i,j=0,m,n, next_move, was_off=0, off, start_off=0; - stbtt_int32 x,y,cx,cy,sx,sy, scx,scy; - stbtt_uint8 *points; - endPtsOfContours = (data + g + 10); - ins = ttUSHORT(data + g + 10 + numberOfContours * 2); - points = data + g + 10 + numberOfContours * 2 + 2 + ins; - - n = 1+ttUSHORT(endPtsOfContours + numberOfContours*2-2); - - m = n + 2*numberOfContours; // a loose bound on how many vertices we might need - vertices = (stbtt_vertex *) STBTT_malloc(m * sizeof(vertices[0]), info->userdata); - if (vertices == 0) - return 0; - - next_move = 0; - flagcount=0; - - // in first pass, we load uninterpreted data into the allocated array - // above, shifted to the end of the array so we won't overwrite it when - // we create our final data starting from the front - - off = m - n; // starting offset for uninterpreted data, regardless of how m ends up being calculated - - // first load flags - - for (i=0; i < n; ++i) { - if (flagcount == 0) { - flags = *points++; - if (flags & 8) - flagcount = *points++; - } else - --flagcount; - vertices[off+i].type = flags; - } - - // now load x coordinates - x=0; - for (i=0; i < n; ++i) { - flags = vertices[off+i].type; - if (flags & 2) { - stbtt_int16 dx = *points++; - x += (flags & 16) ? dx : -dx; // ??? - } else { - if (!(flags & 16)) { - x = x + (stbtt_int16) (points[0]*256 + points[1]); - points += 2; - } - } - vertices[off+i].x = (stbtt_int16) x; - } - - // now load y coordinates - y=0; - for (i=0; i < n; ++i) { - flags = vertices[off+i].type; - if (flags & 4) { - stbtt_int16 dy = *points++; - y += (flags & 32) ? dy : -dy; // ??? - } else { - if (!(flags & 32)) { - y = y + (stbtt_int16) (points[0]*256 + points[1]); - points += 2; - } - } - vertices[off+i].y = (stbtt_int16) y; - } - - // now convert them to our format - num_vertices=0; - sx = sy = cx = cy = scx = scy = 0; - for (i=0; i < n; ++i) { - flags = vertices[off+i].type; - x = (stbtt_int16) vertices[off+i].x; - y = (stbtt_int16) vertices[off+i].y; - - if (next_move == i) { - if (i != 0) - num_vertices = stbtt__close_shape(vertices, num_vertices, was_off, start_off, sx,sy,scx,scy,cx,cy); - - // now start the new one - start_off = !(flags & 1); - if (start_off) { - // if we start off with an off-curve point, then when we need to find a point on the curve - // where we can start, and we need to save some state for when we wraparound. - scx = x; - scy = y; - if (!(vertices[off+i+1].type & 1)) { - // next point is also a curve point, so interpolate an on-point curve - sx = (x + (stbtt_int32) vertices[off+i+1].x) >> 1; - sy = (y + (stbtt_int32) vertices[off+i+1].y) >> 1; - } else { - // otherwise just use the next point as our start point - sx = (stbtt_int32) vertices[off+i+1].x; - sy = (stbtt_int32) vertices[off+i+1].y; - ++i; // we're using point i+1 as the starting point, so skip it - } - } else { - sx = x; - sy = y; - } - stbtt_setvertex(&vertices[num_vertices++], STBTT_vmove,sx,sy,0,0); - was_off = 0; - next_move = 1 + ttUSHORT(endPtsOfContours+j*2); - ++j; - } else { - if (!(flags & 1)) { // if it's a curve - if (was_off) // two off-curve control points in a row means interpolate an on-curve midpoint - stbtt_setvertex(&vertices[num_vertices++], STBTT_vcurve, (cx+x)>>1, (cy+y)>>1, cx, cy); - cx = x; - cy = y; - was_off = 1; - } else { - if (was_off) - stbtt_setvertex(&vertices[num_vertices++], STBTT_vcurve, x,y, cx, cy); - else - stbtt_setvertex(&vertices[num_vertices++], STBTT_vline, x,y,0,0); - was_off = 0; - } - } - } - num_vertices = stbtt__close_shape(vertices, num_vertices, was_off, start_off, sx,sy,scx,scy,cx,cy); - } else if (numberOfContours < 0) { - // Compound shapes. - int more = 1; - stbtt_uint8 *comp = data + g + 10; - num_vertices = 0; - vertices = 0; - while (more) { - stbtt_uint16 flags, gidx; - int comp_num_verts = 0, i; - stbtt_vertex *comp_verts = 0, *tmp = 0; - float mtx[6] = {1,0,0,1,0,0}, m, n; - - flags = ttSHORT(comp); comp+=2; - gidx = ttSHORT(comp); comp+=2; - - if (flags & 2) { // XY values - if (flags & 1) { // shorts - mtx[4] = ttSHORT(comp); comp+=2; - mtx[5] = ttSHORT(comp); comp+=2; - } else { - mtx[4] = ttCHAR(comp); comp+=1; - mtx[5] = ttCHAR(comp); comp+=1; - } - } - else { - // @TODO handle matching point - STBTT_assert(0); - } - if (flags & (1<<3)) { // WE_HAVE_A_SCALE - mtx[0] = mtx[3] = ttSHORT(comp)/16384.0f; comp+=2; - mtx[1] = mtx[2] = 0; - } else if (flags & (1<<6)) { // WE_HAVE_AN_X_AND_YSCALE - mtx[0] = ttSHORT(comp)/16384.0f; comp+=2; - mtx[1] = mtx[2] = 0; - mtx[3] = ttSHORT(comp)/16384.0f; comp+=2; - } else if (flags & (1<<7)) { // WE_HAVE_A_TWO_BY_TWO - mtx[0] = ttSHORT(comp)/16384.0f; comp+=2; - mtx[1] = ttSHORT(comp)/16384.0f; comp+=2; - mtx[2] = ttSHORT(comp)/16384.0f; comp+=2; - mtx[3] = ttSHORT(comp)/16384.0f; comp+=2; - } - - // Find transformation scales. - m = (float) STBTT_sqrt(mtx[0]*mtx[0] + mtx[1]*mtx[1]); - n = (float) STBTT_sqrt(mtx[2]*mtx[2] + mtx[3]*mtx[3]); - - // Get indexed glyph. - comp_num_verts = stbtt_GetGlyphShape(info, gidx, &comp_verts); - if (comp_num_verts > 0) { - // Transform vertices. - for (i = 0; i < comp_num_verts; ++i) { - stbtt_vertex* v = &comp_verts[i]; - stbtt_vertex_type x,y; - x=v->x; y=v->y; - v->x = (stbtt_vertex_type)(m * (mtx[0]*x + mtx[2]*y + mtx[4])); - v->y = (stbtt_vertex_type)(n * (mtx[1]*x + mtx[3]*y + mtx[5])); - x=v->cx; y=v->cy; - v->cx = (stbtt_vertex_type)(m * (mtx[0]*x + mtx[2]*y + mtx[4])); - v->cy = (stbtt_vertex_type)(n * (mtx[1]*x + mtx[3]*y + mtx[5])); - } - // Append vertices. - tmp = (stbtt_vertex*)STBTT_malloc((num_vertices+comp_num_verts)*sizeof(stbtt_vertex), info->userdata); - if (!tmp) { - if (vertices) STBTT_free(vertices, info->userdata); - if (comp_verts) STBTT_free(comp_verts, info->userdata); - return 0; - } - if (num_vertices > 0 && vertices) STBTT_memcpy(tmp, vertices, num_vertices*sizeof(stbtt_vertex)); - STBTT_memcpy(tmp+num_vertices, comp_verts, comp_num_verts*sizeof(stbtt_vertex)); - if (vertices) STBTT_free(vertices, info->userdata); - vertices = tmp; - STBTT_free(comp_verts, info->userdata); - num_vertices += comp_num_verts; - } - // More components ? - more = flags & (1<<5); - } - } else { - // numberOfCounters == 0, do nothing - } - - *pvertices = vertices; - return num_vertices; -} - -typedef struct -{ - int bounds; - int started; - float first_x, first_y; - float x, y; - stbtt_int32 min_x, max_x, min_y, max_y; - - stbtt_vertex *pvertices; - int num_vertices; -} stbtt__csctx; - -#define STBTT__CSCTX_INIT(bounds) {bounds,0, 0,0, 0,0, 0,0,0,0, NULL, 0} - -static void stbtt__track_vertex(stbtt__csctx *c, stbtt_int32 x, stbtt_int32 y) -{ - if (x > c->max_x || !c->started) c->max_x = x; - if (y > c->max_y || !c->started) c->max_y = y; - if (x < c->min_x || !c->started) c->min_x = x; - if (y < c->min_y || !c->started) c->min_y = y; - c->started = 1; -} - -static void stbtt__csctx_v(stbtt__csctx *c, stbtt_uint8 type, stbtt_int32 x, stbtt_int32 y, stbtt_int32 cx, stbtt_int32 cy, stbtt_int32 cx1, stbtt_int32 cy1) -{ - if (c->bounds) { - stbtt__track_vertex(c, x, y); - if (type == STBTT_vcubic) { - stbtt__track_vertex(c, cx, cy); - stbtt__track_vertex(c, cx1, cy1); - } - } else { - stbtt_setvertex(&c->pvertices[c->num_vertices], type, x, y, cx, cy); - c->pvertices[c->num_vertices].cx1 = (stbtt_int16) cx1; - c->pvertices[c->num_vertices].cy1 = (stbtt_int16) cy1; - } - c->num_vertices++; -} - -static void stbtt__csctx_close_shape(stbtt__csctx *ctx) -{ - if (ctx->first_x != ctx->x || ctx->first_y != ctx->y) - stbtt__csctx_v(ctx, STBTT_vline, (int)ctx->first_x, (int)ctx->first_y, 0, 0, 0, 0); -} - -static void stbtt__csctx_rmove_to(stbtt__csctx *ctx, float dx, float dy) -{ - stbtt__csctx_close_shape(ctx); - ctx->first_x = ctx->x = ctx->x + dx; - ctx->first_y = ctx->y = ctx->y + dy; - stbtt__csctx_v(ctx, STBTT_vmove, (int)ctx->x, (int)ctx->y, 0, 0, 0, 0); -} - -static void stbtt__csctx_rline_to(stbtt__csctx *ctx, float dx, float dy) -{ - ctx->x += dx; - ctx->y += dy; - stbtt__csctx_v(ctx, STBTT_vline, (int)ctx->x, (int)ctx->y, 0, 0, 0, 0); -} - -static void stbtt__csctx_rccurve_to(stbtt__csctx *ctx, float dx1, float dy1, float dx2, float dy2, float dx3, float dy3) -{ - float cx1 = ctx->x + dx1; - float cy1 = ctx->y + dy1; - float cx2 = cx1 + dx2; - float cy2 = cy1 + dy2; - ctx->x = cx2 + dx3; - ctx->y = cy2 + dy3; - stbtt__csctx_v(ctx, STBTT_vcubic, (int)ctx->x, (int)ctx->y, (int)cx1, (int)cy1, (int)cx2, (int)cy2); -} - -static stbtt__buf stbtt__get_subr(stbtt__buf idx, int n) -{ - int count = stbtt__cff_index_count(&idx); - int bias = 107; - if (count >= 33900) - bias = 32768; - else if (count >= 1240) - bias = 1131; - n += bias; - if (n < 0 || n >= count) - return stbtt__new_buf(NULL, 0); - return stbtt__cff_index_get(idx, n); -} - -static stbtt__buf stbtt__cid_get_glyph_subrs(const stbtt_fontinfo *info, int glyph_index) -{ - stbtt__buf fdselect = info->fdselect; - int nranges, start, end, v, fmt, fdselector = -1, i; - - stbtt__buf_seek(&fdselect, 0); - fmt = stbtt__buf_get8(&fdselect); - if (fmt == 0) { - // untested - stbtt__buf_skip(&fdselect, glyph_index); - fdselector = stbtt__buf_get8(&fdselect); - } else if (fmt == 3) { - nranges = stbtt__buf_get16(&fdselect); - start = stbtt__buf_get16(&fdselect); - for (i = 0; i < nranges; i++) { - v = stbtt__buf_get8(&fdselect); - end = stbtt__buf_get16(&fdselect); - if (glyph_index >= start && glyph_index < end) { - fdselector = v; - break; - } - start = end; - } - } - if (fdselector == -1) return stbtt__new_buf(NULL, 0); // [DEAR IMGUI] fixed, see #6007 and nothings/stb#1422 - return stbtt__get_subrs(info->cff, stbtt__cff_index_get(info->fontdicts, fdselector)); -} - -static int stbtt__run_charstring(const stbtt_fontinfo *info, int glyph_index, stbtt__csctx *c) -{ - int in_header = 1, maskbits = 0, subr_stack_height = 0, sp = 0, v, i, b0; - int has_subrs = 0, clear_stack; - float s[48]; - stbtt__buf subr_stack[10], subrs = info->subrs, b; - float f; - -#define STBTT__CSERR(s) (0) - - // this currently ignores the initial width value, which isn't needed if we have hmtx - b = stbtt__cff_index_get(info->charstrings, glyph_index); - while (b.cursor < b.size) { - i = 0; - clear_stack = 1; - b0 = stbtt__buf_get8(&b); - switch (b0) { - // @TODO implement hinting - case 0x13: // hintmask - case 0x14: // cntrmask - if (in_header) - maskbits += (sp / 2); // implicit "vstem" - in_header = 0; - stbtt__buf_skip(&b, (maskbits + 7) / 8); - break; - - case 0x01: // hstem - case 0x03: // vstem - case 0x12: // hstemhm - case 0x17: // vstemhm - maskbits += (sp / 2); - break; - - case 0x15: // rmoveto - in_header = 0; - if (sp < 2) return STBTT__CSERR("rmoveto stack"); - stbtt__csctx_rmove_to(c, s[sp-2], s[sp-1]); - break; - case 0x04: // vmoveto - in_header = 0; - if (sp < 1) return STBTT__CSERR("vmoveto stack"); - stbtt__csctx_rmove_to(c, 0, s[sp-1]); - break; - case 0x16: // hmoveto - in_header = 0; - if (sp < 1) return STBTT__CSERR("hmoveto stack"); - stbtt__csctx_rmove_to(c, s[sp-1], 0); - break; - - case 0x05: // rlineto - if (sp < 2) return STBTT__CSERR("rlineto stack"); - for (; i + 1 < sp; i += 2) - stbtt__csctx_rline_to(c, s[i], s[i+1]); - break; - - // hlineto/vlineto and vhcurveto/hvcurveto alternate horizontal and vertical - // starting from a different place. - - case 0x07: // vlineto - if (sp < 1) return STBTT__CSERR("vlineto stack"); - goto vlineto; - case 0x06: // hlineto - if (sp < 1) return STBTT__CSERR("hlineto stack"); - for (;;) { - if (i >= sp) break; - stbtt__csctx_rline_to(c, s[i], 0); - i++; - vlineto: - if (i >= sp) break; - stbtt__csctx_rline_to(c, 0, s[i]); - i++; - } - break; - - case 0x1F: // hvcurveto - if (sp < 4) return STBTT__CSERR("hvcurveto stack"); - goto hvcurveto; - case 0x1E: // vhcurveto - if (sp < 4) return STBTT__CSERR("vhcurveto stack"); - for (;;) { - if (i + 3 >= sp) break; - stbtt__csctx_rccurve_to(c, 0, s[i], s[i+1], s[i+2], s[i+3], (sp - i == 5) ? s[i + 4] : 0.0f); - i += 4; - hvcurveto: - if (i + 3 >= sp) break; - stbtt__csctx_rccurve_to(c, s[i], 0, s[i+1], s[i+2], (sp - i == 5) ? s[i+4] : 0.0f, s[i+3]); - i += 4; - } - break; - - case 0x08: // rrcurveto - if (sp < 6) return STBTT__CSERR("rcurveline stack"); - for (; i + 5 < sp; i += 6) - stbtt__csctx_rccurve_to(c, s[i], s[i+1], s[i+2], s[i+3], s[i+4], s[i+5]); - break; - - case 0x18: // rcurveline - if (sp < 8) return STBTT__CSERR("rcurveline stack"); - for (; i + 5 < sp - 2; i += 6) - stbtt__csctx_rccurve_to(c, s[i], s[i+1], s[i+2], s[i+3], s[i+4], s[i+5]); - if (i + 1 >= sp) return STBTT__CSERR("rcurveline stack"); - stbtt__csctx_rline_to(c, s[i], s[i+1]); - break; - - case 0x19: // rlinecurve - if (sp < 8) return STBTT__CSERR("rlinecurve stack"); - for (; i + 1 < sp - 6; i += 2) - stbtt__csctx_rline_to(c, s[i], s[i+1]); - if (i + 5 >= sp) return STBTT__CSERR("rlinecurve stack"); - stbtt__csctx_rccurve_to(c, s[i], s[i+1], s[i+2], s[i+3], s[i+4], s[i+5]); - break; - - case 0x1A: // vvcurveto - case 0x1B: // hhcurveto - if (sp < 4) return STBTT__CSERR("(vv|hh)curveto stack"); - f = 0.0; - if (sp & 1) { f = s[i]; i++; } - for (; i + 3 < sp; i += 4) { - if (b0 == 0x1B) - stbtt__csctx_rccurve_to(c, s[i], f, s[i+1], s[i+2], s[i+3], 0.0); - else - stbtt__csctx_rccurve_to(c, f, s[i], s[i+1], s[i+2], 0.0, s[i+3]); - f = 0.0; - } - break; - - case 0x0A: // callsubr - if (!has_subrs) { - if (info->fdselect.size) - subrs = stbtt__cid_get_glyph_subrs(info, glyph_index); - has_subrs = 1; - } - // FALLTHROUGH - case 0x1D: // callgsubr - if (sp < 1) return STBTT__CSERR("call(g|)subr stack"); - v = (int) s[--sp]; - if (subr_stack_height >= 10) return STBTT__CSERR("recursion limit"); - subr_stack[subr_stack_height++] = b; - b = stbtt__get_subr(b0 == 0x0A ? subrs : info->gsubrs, v); - if (b.size == 0) return STBTT__CSERR("subr not found"); - b.cursor = 0; - clear_stack = 0; - break; - - case 0x0B: // return - if (subr_stack_height <= 0) return STBTT__CSERR("return outside subr"); - b = subr_stack[--subr_stack_height]; - clear_stack = 0; - break; - - case 0x0E: // endchar - stbtt__csctx_close_shape(c); - return 1; - - case 0x0C: { // two-byte escape - float dx1, dx2, dx3, dx4, dx5, dx6, dy1, dy2, dy3, dy4, dy5, dy6; - float dx, dy; - int b1 = stbtt__buf_get8(&b); - switch (b1) { - // @TODO These "flex" implementations ignore the flex-depth and resolution, - // and always draw beziers. - case 0x22: // hflex - if (sp < 7) return STBTT__CSERR("hflex stack"); - dx1 = s[0]; - dx2 = s[1]; - dy2 = s[2]; - dx3 = s[3]; - dx4 = s[4]; - dx5 = s[5]; - dx6 = s[6]; - stbtt__csctx_rccurve_to(c, dx1, 0, dx2, dy2, dx3, 0); - stbtt__csctx_rccurve_to(c, dx4, 0, dx5, -dy2, dx6, 0); - break; - - case 0x23: // flex - if (sp < 13) return STBTT__CSERR("flex stack"); - dx1 = s[0]; - dy1 = s[1]; - dx2 = s[2]; - dy2 = s[3]; - dx3 = s[4]; - dy3 = s[5]; - dx4 = s[6]; - dy4 = s[7]; - dx5 = s[8]; - dy5 = s[9]; - dx6 = s[10]; - dy6 = s[11]; - //fd is s[12] - stbtt__csctx_rccurve_to(c, dx1, dy1, dx2, dy2, dx3, dy3); - stbtt__csctx_rccurve_to(c, dx4, dy4, dx5, dy5, dx6, dy6); - break; - - case 0x24: // hflex1 - if (sp < 9) return STBTT__CSERR("hflex1 stack"); - dx1 = s[0]; - dy1 = s[1]; - dx2 = s[2]; - dy2 = s[3]; - dx3 = s[4]; - dx4 = s[5]; - dx5 = s[6]; - dy5 = s[7]; - dx6 = s[8]; - stbtt__csctx_rccurve_to(c, dx1, dy1, dx2, dy2, dx3, 0); - stbtt__csctx_rccurve_to(c, dx4, 0, dx5, dy5, dx6, -(dy1+dy2+dy5)); - break; - - case 0x25: // flex1 - if (sp < 11) return STBTT__CSERR("flex1 stack"); - dx1 = s[0]; - dy1 = s[1]; - dx2 = s[2]; - dy2 = s[3]; - dx3 = s[4]; - dy3 = s[5]; - dx4 = s[6]; - dy4 = s[7]; - dx5 = s[8]; - dy5 = s[9]; - dx6 = dy6 = s[10]; - dx = dx1+dx2+dx3+dx4+dx5; - dy = dy1+dy2+dy3+dy4+dy5; - if (STBTT_fabs(dx) > STBTT_fabs(dy)) - dy6 = -dy; - else - dx6 = -dx; - stbtt__csctx_rccurve_to(c, dx1, dy1, dx2, dy2, dx3, dy3); - stbtt__csctx_rccurve_to(c, dx4, dy4, dx5, dy5, dx6, dy6); - break; - - default: - return STBTT__CSERR("unimplemented"); - } - } break; - - default: - if (b0 != 255 && b0 != 28 && b0 < 32) - return STBTT__CSERR("reserved operator"); - - // push immediate - if (b0 == 255) { - f = (float)(stbtt_int32)stbtt__buf_get32(&b) / 0x10000; - } else { - stbtt__buf_skip(&b, -1); - f = (float)(stbtt_int16)stbtt__cff_int(&b); - } - if (sp >= 48) return STBTT__CSERR("push stack overflow"); - s[sp++] = f; - clear_stack = 0; - break; - } - if (clear_stack) sp = 0; - } - return STBTT__CSERR("no endchar"); - -#undef STBTT__CSERR -} - -static int stbtt__GetGlyphShapeT2(const stbtt_fontinfo *info, int glyph_index, stbtt_vertex **pvertices) -{ - // runs the charstring twice, once to count and once to output (to avoid realloc) - stbtt__csctx count_ctx = STBTT__CSCTX_INIT(1); - stbtt__csctx output_ctx = STBTT__CSCTX_INIT(0); - if (stbtt__run_charstring(info, glyph_index, &count_ctx)) { - *pvertices = (stbtt_vertex*)STBTT_malloc(count_ctx.num_vertices*sizeof(stbtt_vertex), info->userdata); - output_ctx.pvertices = *pvertices; - if (stbtt__run_charstring(info, glyph_index, &output_ctx)) { - STBTT_assert(output_ctx.num_vertices == count_ctx.num_vertices); - return output_ctx.num_vertices; - } - } - *pvertices = NULL; - return 0; -} - -static int stbtt__GetGlyphInfoT2(const stbtt_fontinfo *info, int glyph_index, int *x0, int *y0, int *x1, int *y1) -{ - stbtt__csctx c = STBTT__CSCTX_INIT(1); - int r = stbtt__run_charstring(info, glyph_index, &c); - if (x0) *x0 = r ? c.min_x : 0; - if (y0) *y0 = r ? c.min_y : 0; - if (x1) *x1 = r ? c.max_x : 0; - if (y1) *y1 = r ? c.max_y : 0; - return r ? c.num_vertices : 0; -} - -STBTT_DEF int stbtt_GetGlyphShape(const stbtt_fontinfo *info, int glyph_index, stbtt_vertex **pvertices) -{ - if (!info->cff.size) - return stbtt__GetGlyphShapeTT(info, glyph_index, pvertices); - else - return stbtt__GetGlyphShapeT2(info, glyph_index, pvertices); -} - -STBTT_DEF void stbtt_GetGlyphHMetrics(const stbtt_fontinfo *info, int glyph_index, int *advanceWidth, int *leftSideBearing) -{ - stbtt_uint16 numOfLongHorMetrics = ttUSHORT(info->data+info->hhea + 34); - if (glyph_index < numOfLongHorMetrics) { - if (advanceWidth) *advanceWidth = ttSHORT(info->data + info->hmtx + 4*glyph_index); - if (leftSideBearing) *leftSideBearing = ttSHORT(info->data + info->hmtx + 4*glyph_index + 2); - } else { - if (advanceWidth) *advanceWidth = ttSHORT(info->data + info->hmtx + 4*(numOfLongHorMetrics-1)); - if (leftSideBearing) *leftSideBearing = ttSHORT(info->data + info->hmtx + 4*numOfLongHorMetrics + 2*(glyph_index - numOfLongHorMetrics)); - } -} - -STBTT_DEF int stbtt_GetKerningTableLength(const stbtt_fontinfo *info) -{ - stbtt_uint8 *data = info->data + info->kern; - - // we only look at the first table. it must be 'horizontal' and format 0. - if (!info->kern) - return 0; - if (ttUSHORT(data+2) < 1) // number of tables, need at least 1 - return 0; - if (ttUSHORT(data+8) != 1) // horizontal flag must be set in format - return 0; - - return ttUSHORT(data+10); -} - -STBTT_DEF int stbtt_GetKerningTable(const stbtt_fontinfo *info, stbtt_kerningentry* table, int table_length) -{ - stbtt_uint8 *data = info->data + info->kern; - int k, length; - - // we only look at the first table. it must be 'horizontal' and format 0. - if (!info->kern) - return 0; - if (ttUSHORT(data+2) < 1) // number of tables, need at least 1 - return 0; - if (ttUSHORT(data+8) != 1) // horizontal flag must be set in format - return 0; - - length = ttUSHORT(data+10); - if (table_length < length) - length = table_length; - - for (k = 0; k < length; k++) - { - table[k].glyph1 = ttUSHORT(data+18+(k*6)); - table[k].glyph2 = ttUSHORT(data+20+(k*6)); - table[k].advance = ttSHORT(data+22+(k*6)); - } - - return length; -} - -static int stbtt__GetGlyphKernInfoAdvance(const stbtt_fontinfo *info, int glyph1, int glyph2) -{ - stbtt_uint8 *data = info->data + info->kern; - stbtt_uint32 needle, straw; - int l, r, m; - - // we only look at the first table. it must be 'horizontal' and format 0. - if (!info->kern) - return 0; - if (ttUSHORT(data+2) < 1) // number of tables, need at least 1 - return 0; - if (ttUSHORT(data+8) != 1) // horizontal flag must be set in format - return 0; - - l = 0; - r = ttUSHORT(data+10) - 1; - needle = glyph1 << 16 | glyph2; - while (l <= r) { - m = (l + r) >> 1; - straw = ttULONG(data+18+(m*6)); // note: unaligned read - if (needle < straw) - r = m - 1; - else if (needle > straw) - l = m + 1; - else - return ttSHORT(data+22+(m*6)); - } - return 0; -} - -static stbtt_int32 stbtt__GetCoverageIndex(stbtt_uint8 *coverageTable, int glyph) -{ - stbtt_uint16 coverageFormat = ttUSHORT(coverageTable); - switch (coverageFormat) { - case 1: { - stbtt_uint16 glyphCount = ttUSHORT(coverageTable + 2); - - // Binary search. - stbtt_int32 l=0, r=glyphCount-1, m; - int straw, needle=glyph; - while (l <= r) { - stbtt_uint8 *glyphArray = coverageTable + 4; - stbtt_uint16 glyphID; - m = (l + r) >> 1; - glyphID = ttUSHORT(glyphArray + 2 * m); - straw = glyphID; - if (needle < straw) - r = m - 1; - else if (needle > straw) - l = m + 1; - else { - return m; - } - } - break; - } - - case 2: { - stbtt_uint16 rangeCount = ttUSHORT(coverageTable + 2); - stbtt_uint8 *rangeArray = coverageTable + 4; - - // Binary search. - stbtt_int32 l=0, r=rangeCount-1, m; - int strawStart, strawEnd, needle=glyph; - while (l <= r) { - stbtt_uint8 *rangeRecord; - m = (l + r) >> 1; - rangeRecord = rangeArray + 6 * m; - strawStart = ttUSHORT(rangeRecord); - strawEnd = ttUSHORT(rangeRecord + 2); - if (needle < strawStart) - r = m - 1; - else if (needle > strawEnd) - l = m + 1; - else { - stbtt_uint16 startCoverageIndex = ttUSHORT(rangeRecord + 4); - return startCoverageIndex + glyph - strawStart; - } - } - break; - } - - default: return -1; // unsupported - } - - return -1; -} - -static stbtt_int32 stbtt__GetGlyphClass(stbtt_uint8 *classDefTable, int glyph) -{ - stbtt_uint16 classDefFormat = ttUSHORT(classDefTable); - switch (classDefFormat) - { - case 1: { - stbtt_uint16 startGlyphID = ttUSHORT(classDefTable + 2); - stbtt_uint16 glyphCount = ttUSHORT(classDefTable + 4); - stbtt_uint8 *classDef1ValueArray = classDefTable + 6; - - if (glyph >= startGlyphID && glyph < startGlyphID + glyphCount) - return (stbtt_int32)ttUSHORT(classDef1ValueArray + 2 * (glyph - startGlyphID)); - break; - } - - case 2: { - stbtt_uint16 classRangeCount = ttUSHORT(classDefTable + 2); - stbtt_uint8 *classRangeRecords = classDefTable + 4; - - // Binary search. - stbtt_int32 l=0, r=classRangeCount-1, m; - int strawStart, strawEnd, needle=glyph; - while (l <= r) { - stbtt_uint8 *classRangeRecord; - m = (l + r) >> 1; - classRangeRecord = classRangeRecords + 6 * m; - strawStart = ttUSHORT(classRangeRecord); - strawEnd = ttUSHORT(classRangeRecord + 2); - if (needle < strawStart) - r = m - 1; - else if (needle > strawEnd) - l = m + 1; - else - return (stbtt_int32)ttUSHORT(classRangeRecord + 4); - } - break; - } - - default: - return -1; // Unsupported definition type, return an error. - } - - // "All glyphs not assigned to a class fall into class 0". (OpenType spec) - return 0; -} - -// Define to STBTT_assert(x) if you want to break on unimplemented formats. -#define STBTT_GPOS_TODO_assert(x) - -static stbtt_int32 stbtt__GetGlyphGPOSInfoAdvance(const stbtt_fontinfo *info, int glyph1, int glyph2) -{ - stbtt_uint16 lookupListOffset; - stbtt_uint8 *lookupList; - stbtt_uint16 lookupCount; - stbtt_uint8 *data; - stbtt_int32 i, sti; - - if (!info->gpos) return 0; - - data = info->data + info->gpos; - - if (ttUSHORT(data+0) != 1) return 0; // Major version 1 - if (ttUSHORT(data+2) != 0) return 0; // Minor version 0 - - lookupListOffset = ttUSHORT(data+8); - lookupList = data + lookupListOffset; - lookupCount = ttUSHORT(lookupList); - - for (i=0; i= pairSetCount) return 0; - - needle=glyph2; - r=pairValueCount-1; - l=0; - - // Binary search. - while (l <= r) { - stbtt_uint16 secondGlyph; - stbtt_uint8 *pairValue; - m = (l + r) >> 1; - pairValue = pairValueArray + (2 + valueRecordPairSizeInBytes) * m; - secondGlyph = ttUSHORT(pairValue); - straw = secondGlyph; - if (needle < straw) - r = m - 1; - else if (needle > straw) - l = m + 1; - else { - stbtt_int16 xAdvance = ttSHORT(pairValue + 2); - return xAdvance; - } - } - } else - return 0; - break; - } - - case 2: { - stbtt_uint16 valueFormat1 = ttUSHORT(table + 4); - stbtt_uint16 valueFormat2 = ttUSHORT(table + 6); - if (valueFormat1 == 4 && valueFormat2 == 0) { // Support more formats? - stbtt_uint16 classDef1Offset = ttUSHORT(table + 8); - stbtt_uint16 classDef2Offset = ttUSHORT(table + 10); - int glyph1class = stbtt__GetGlyphClass(table + classDef1Offset, glyph1); - int glyph2class = stbtt__GetGlyphClass(table + classDef2Offset, glyph2); - - stbtt_uint16 class1Count = ttUSHORT(table + 12); - stbtt_uint16 class2Count = ttUSHORT(table + 14); - stbtt_uint8 *class1Records, *class2Records; - stbtt_int16 xAdvance; - - if (glyph1class < 0 || glyph1class >= class1Count) return 0; // malformed - if (glyph2class < 0 || glyph2class >= class2Count) return 0; // malformed - - class1Records = table + 16; - class2Records = class1Records + 2 * (glyph1class * class2Count); - xAdvance = ttSHORT(class2Records + 2 * glyph2class); - return xAdvance; - } else - return 0; - break; - } - - default: - return 0; // Unsupported position format - } - } - } - - return 0; -} - -STBTT_DEF int stbtt_GetGlyphKernAdvance(const stbtt_fontinfo *info, int g1, int g2) -{ - int xAdvance = 0; - - if (info->gpos) - xAdvance += stbtt__GetGlyphGPOSInfoAdvance(info, g1, g2); - else if (info->kern) - xAdvance += stbtt__GetGlyphKernInfoAdvance(info, g1, g2); - - return xAdvance; -} - -STBTT_DEF int stbtt_GetCodepointKernAdvance(const stbtt_fontinfo *info, int ch1, int ch2) -{ - if (!info->kern && !info->gpos) // if no kerning table, don't waste time looking up both codepoint->glyphs - return 0; - return stbtt_GetGlyphKernAdvance(info, stbtt_FindGlyphIndex(info,ch1), stbtt_FindGlyphIndex(info,ch2)); -} - -STBTT_DEF void stbtt_GetCodepointHMetrics(const stbtt_fontinfo *info, int codepoint, int *advanceWidth, int *leftSideBearing) -{ - stbtt_GetGlyphHMetrics(info, stbtt_FindGlyphIndex(info,codepoint), advanceWidth, leftSideBearing); -} - -STBTT_DEF void stbtt_GetFontVMetrics(const stbtt_fontinfo *info, int *ascent, int *descent, int *lineGap) -{ - if (ascent ) *ascent = ttSHORT(info->data+info->hhea + 4); - if (descent) *descent = ttSHORT(info->data+info->hhea + 6); - if (lineGap) *lineGap = ttSHORT(info->data+info->hhea + 8); -} - -STBTT_DEF int stbtt_GetFontVMetricsOS2(const stbtt_fontinfo *info, int *typoAscent, int *typoDescent, int *typoLineGap) -{ - int tab = stbtt__find_table(info->data, info->fontstart, "OS/2"); - if (!tab) - return 0; - if (typoAscent ) *typoAscent = ttSHORT(info->data+tab + 68); - if (typoDescent) *typoDescent = ttSHORT(info->data+tab + 70); - if (typoLineGap) *typoLineGap = ttSHORT(info->data+tab + 72); - return 1; -} - -STBTT_DEF void stbtt_GetFontBoundingBox(const stbtt_fontinfo *info, int *x0, int *y0, int *x1, int *y1) -{ - *x0 = ttSHORT(info->data + info->head + 36); - *y0 = ttSHORT(info->data + info->head + 38); - *x1 = ttSHORT(info->data + info->head + 40); - *y1 = ttSHORT(info->data + info->head + 42); -} - -STBTT_DEF float stbtt_ScaleForPixelHeight(const stbtt_fontinfo *info, float height) -{ - int fheight = ttSHORT(info->data + info->hhea + 4) - ttSHORT(info->data + info->hhea + 6); - return (float) height / fheight; -} - -STBTT_DEF float stbtt_ScaleForMappingEmToPixels(const stbtt_fontinfo *info, float pixels) -{ - int unitsPerEm = ttUSHORT(info->data + info->head + 18); - return pixels / unitsPerEm; -} - -STBTT_DEF void stbtt_FreeShape(const stbtt_fontinfo *info, stbtt_vertex *v) -{ - STBTT_free(v, info->userdata); -} - -STBTT_DEF stbtt_uint8 *stbtt_FindSVGDoc(const stbtt_fontinfo *info, int gl) -{ - int i; - stbtt_uint8 *data = info->data; - stbtt_uint8 *svg_doc_list = data + stbtt__get_svg((stbtt_fontinfo *) info); - - int numEntries = ttUSHORT(svg_doc_list); - stbtt_uint8 *svg_docs = svg_doc_list + 2; - - for(i=0; i= ttUSHORT(svg_doc)) && (gl <= ttUSHORT(svg_doc + 2))) - return svg_doc; - } - return 0; -} - -STBTT_DEF int stbtt_GetGlyphSVG(const stbtt_fontinfo *info, int gl, const char **svg) -{ - stbtt_uint8 *data = info->data; - stbtt_uint8 *svg_doc; - - if (info->svg == 0) - return 0; - - svg_doc = stbtt_FindSVGDoc(info, gl); - if (svg_doc != NULL) { - *svg = (char *) data + info->svg + ttULONG(svg_doc + 4); - return ttULONG(svg_doc + 8); - } else { - return 0; - } -} - -STBTT_DEF int stbtt_GetCodepointSVG(const stbtt_fontinfo *info, int unicode_codepoint, const char **svg) -{ - return stbtt_GetGlyphSVG(info, stbtt_FindGlyphIndex(info, unicode_codepoint), svg); -} - -////////////////////////////////////////////////////////////////////////////// -// -// antialiasing software rasterizer -// - -STBTT_DEF void stbtt_GetGlyphBitmapBoxSubpixel(const stbtt_fontinfo *font, int glyph, float scale_x, float scale_y,float shift_x, float shift_y, int *ix0, int *iy0, int *ix1, int *iy1) -{ - int x0=0,y0=0,x1,y1; // =0 suppresses compiler warning - if (!stbtt_GetGlyphBox(font, glyph, &x0,&y0,&x1,&y1)) { - // e.g. space character - if (ix0) *ix0 = 0; - if (iy0) *iy0 = 0; - if (ix1) *ix1 = 0; - if (iy1) *iy1 = 0; - } else { - // move to integral bboxes (treating pixels as little squares, what pixels get touched)? - if (ix0) *ix0 = STBTT_ifloor( x0 * scale_x + shift_x); - if (iy0) *iy0 = STBTT_ifloor(-y1 * scale_y + shift_y); - if (ix1) *ix1 = STBTT_iceil ( x1 * scale_x + shift_x); - if (iy1) *iy1 = STBTT_iceil (-y0 * scale_y + shift_y); - } -} - -STBTT_DEF void stbtt_GetGlyphBitmapBox(const stbtt_fontinfo *font, int glyph, float scale_x, float scale_y, int *ix0, int *iy0, int *ix1, int *iy1) -{ - stbtt_GetGlyphBitmapBoxSubpixel(font, glyph, scale_x, scale_y,0.0f,0.0f, ix0, iy0, ix1, iy1); -} - -STBTT_DEF void stbtt_GetCodepointBitmapBoxSubpixel(const stbtt_fontinfo *font, int codepoint, float scale_x, float scale_y, float shift_x, float shift_y, int *ix0, int *iy0, int *ix1, int *iy1) -{ - stbtt_GetGlyphBitmapBoxSubpixel(font, stbtt_FindGlyphIndex(font,codepoint), scale_x, scale_y,shift_x,shift_y, ix0,iy0,ix1,iy1); -} - -STBTT_DEF void stbtt_GetCodepointBitmapBox(const stbtt_fontinfo *font, int codepoint, float scale_x, float scale_y, int *ix0, int *iy0, int *ix1, int *iy1) -{ - stbtt_GetCodepointBitmapBoxSubpixel(font, codepoint, scale_x, scale_y,0.0f,0.0f, ix0,iy0,ix1,iy1); -} - -////////////////////////////////////////////////////////////////////////////// -// -// Rasterizer - -typedef struct stbtt__hheap_chunk -{ - struct stbtt__hheap_chunk *next; -} stbtt__hheap_chunk; - -typedef struct stbtt__hheap -{ - struct stbtt__hheap_chunk *head; - void *first_free; - int num_remaining_in_head_chunk; -} stbtt__hheap; - -static void *stbtt__hheap_alloc(stbtt__hheap *hh, size_t size, void *userdata) -{ - if (hh->first_free) { - void *p = hh->first_free; - hh->first_free = * (void **) p; - return p; - } else { - if (hh->num_remaining_in_head_chunk == 0) { - int count = (size < 32 ? 2000 : size < 128 ? 800 : 100); - stbtt__hheap_chunk *c = (stbtt__hheap_chunk *) STBTT_malloc(sizeof(stbtt__hheap_chunk) + size * count, userdata); - if (c == NULL) - return NULL; - c->next = hh->head; - hh->head = c; - hh->num_remaining_in_head_chunk = count; - } - --hh->num_remaining_in_head_chunk; - return (char *) (hh->head) + sizeof(stbtt__hheap_chunk) + size * hh->num_remaining_in_head_chunk; - } -} - -static void stbtt__hheap_free(stbtt__hheap *hh, void *p) -{ - *(void **) p = hh->first_free; - hh->first_free = p; -} - -static void stbtt__hheap_cleanup(stbtt__hheap *hh, void *userdata) -{ - stbtt__hheap_chunk *c = hh->head; - while (c) { - stbtt__hheap_chunk *n = c->next; - STBTT_free(c, userdata); - c = n; - } -} - -typedef struct stbtt__edge { - float x0,y0, x1,y1; - int invert; -} stbtt__edge; - - -typedef struct stbtt__active_edge -{ - struct stbtt__active_edge *next; - #if STBTT_RASTERIZER_VERSION==1 - int x,dx; - float ey; - int direction; - #elif STBTT_RASTERIZER_VERSION==2 - float fx,fdx,fdy; - float direction; - float sy; - float ey; - #else - #error "Unrecognized value of STBTT_RASTERIZER_VERSION" - #endif -} stbtt__active_edge; - -#if STBTT_RASTERIZER_VERSION == 1 -#define STBTT_FIXSHIFT 10 -#define STBTT_FIX (1 << STBTT_FIXSHIFT) -#define STBTT_FIXMASK (STBTT_FIX-1) - -static stbtt__active_edge *stbtt__new_active(stbtt__hheap *hh, stbtt__edge *e, int off_x, float start_point, void *userdata) -{ - stbtt__active_edge *z = (stbtt__active_edge *) stbtt__hheap_alloc(hh, sizeof(*z), userdata); - float dxdy = (e->x1 - e->x0) / (e->y1 - e->y0); - STBTT_assert(z != NULL); - if (!z) return z; - - // round dx down to avoid overshooting - if (dxdy < 0) - z->dx = -STBTT_ifloor(STBTT_FIX * -dxdy); - else - z->dx = STBTT_ifloor(STBTT_FIX * dxdy); - - z->x = STBTT_ifloor(STBTT_FIX * e->x0 + z->dx * (start_point - e->y0)); // use z->dx so when we offset later it's by the same amount - z->x -= off_x * STBTT_FIX; - - z->ey = e->y1; - z->next = 0; - z->direction = e->invert ? 1 : -1; - return z; -} -#elif STBTT_RASTERIZER_VERSION == 2 -static stbtt__active_edge *stbtt__new_active(stbtt__hheap *hh, stbtt__edge *e, int off_x, float start_point, void *userdata) -{ - stbtt__active_edge *z = (stbtt__active_edge *) stbtt__hheap_alloc(hh, sizeof(*z), userdata); - float dxdy = (e->x1 - e->x0) / (e->y1 - e->y0); - STBTT_assert(z != NULL); - //STBTT_assert(e->y0 <= start_point); - if (!z) return z; - z->fdx = dxdy; - z->fdy = dxdy != 0.0f ? (1.0f/dxdy) : 0.0f; - z->fx = e->x0 + dxdy * (start_point - e->y0); - z->fx -= off_x; - z->direction = e->invert ? 1.0f : -1.0f; - z->sy = e->y0; - z->ey = e->y1; - z->next = 0; - return z; -} -#else -#error "Unrecognized value of STBTT_RASTERIZER_VERSION" -#endif - -#if STBTT_RASTERIZER_VERSION == 1 -// note: this routine clips fills that extend off the edges... ideally this -// wouldn't happen, but it could happen if the truetype glyph bounding boxes -// are wrong, or if the user supplies a too-small bitmap -static void stbtt__fill_active_edges(unsigned char *scanline, int len, stbtt__active_edge *e, int max_weight) -{ - // non-zero winding fill - int x0=0, w=0; - - while (e) { - if (w == 0) { - // if we're currently at zero, we need to record the edge start point - x0 = e->x; w += e->direction; - } else { - int x1 = e->x; w += e->direction; - // if we went to zero, we need to draw - if (w == 0) { - int i = x0 >> STBTT_FIXSHIFT; - int j = x1 >> STBTT_FIXSHIFT; - - if (i < len && j >= 0) { - if (i == j) { - // x0,x1 are the same pixel, so compute combined coverage - scanline[i] = scanline[i] + (stbtt_uint8) ((x1 - x0) * max_weight >> STBTT_FIXSHIFT); - } else { - if (i >= 0) // add antialiasing for x0 - scanline[i] = scanline[i] + (stbtt_uint8) (((STBTT_FIX - (x0 & STBTT_FIXMASK)) * max_weight) >> STBTT_FIXSHIFT); - else - i = -1; // clip - - if (j < len) // add antialiasing for x1 - scanline[j] = scanline[j] + (stbtt_uint8) (((x1 & STBTT_FIXMASK) * max_weight) >> STBTT_FIXSHIFT); - else - j = len; // clip - - for (++i; i < j; ++i) // fill pixels between x0 and x1 - scanline[i] = scanline[i] + (stbtt_uint8) max_weight; - } - } - } - } - - e = e->next; - } -} - -static void stbtt__rasterize_sorted_edges(stbtt__bitmap *result, stbtt__edge *e, int n, int vsubsample, int off_x, int off_y, void *userdata) -{ - stbtt__hheap hh = { 0, 0, 0 }; - stbtt__active_edge *active = NULL; - int y,j=0; - int max_weight = (255 / vsubsample); // weight per vertical scanline - int s; // vertical subsample index - unsigned char scanline_data[512], *scanline; - - if (result->w > 512) - scanline = (unsigned char *) STBTT_malloc(result->w, userdata); - else - scanline = scanline_data; - - y = off_y * vsubsample; - e[n].y0 = (off_y + result->h) * (float) vsubsample + 1; - - while (j < result->h) { - STBTT_memset(scanline, 0, result->w); - for (s=0; s < vsubsample; ++s) { - // find center of pixel for this scanline - float scan_y = y + 0.5f; - stbtt__active_edge **step = &active; - - // update all active edges; - // remove all active edges that terminate before the center of this scanline - while (*step) { - stbtt__active_edge * z = *step; - if (z->ey <= scan_y) { - *step = z->next; // delete from list - STBTT_assert(z->direction); - z->direction = 0; - stbtt__hheap_free(&hh, z); - } else { - z->x += z->dx; // advance to position for current scanline - step = &((*step)->next); // advance through list - } - } - - // resort the list if needed - for(;;) { - int changed=0; - step = &active; - while (*step && (*step)->next) { - if ((*step)->x > (*step)->next->x) { - stbtt__active_edge *t = *step; - stbtt__active_edge *q = t->next; - - t->next = q->next; - q->next = t; - *step = q; - changed = 1; - } - step = &(*step)->next; - } - if (!changed) break; - } - - // insert all edges that start before the center of this scanline -- omit ones that also end on this scanline - while (e->y0 <= scan_y) { - if (e->y1 > scan_y) { - stbtt__active_edge *z = stbtt__new_active(&hh, e, off_x, scan_y, userdata); - if (z != NULL) { - // find insertion point - if (active == NULL) - active = z; - else if (z->x < active->x) { - // insert at front - z->next = active; - active = z; - } else { - // find thing to insert AFTER - stbtt__active_edge *p = active; - while (p->next && p->next->x < z->x) - p = p->next; - // at this point, p->next->x is NOT < z->x - z->next = p->next; - p->next = z; - } - } - } - ++e; - } - - // now process all active edges in XOR fashion - if (active) - stbtt__fill_active_edges(scanline, result->w, active, max_weight); - - ++y; - } - STBTT_memcpy(result->pixels + j * result->stride, scanline, result->w); - ++j; - } - - stbtt__hheap_cleanup(&hh, userdata); - - if (scanline != scanline_data) - STBTT_free(scanline, userdata); -} - -#elif STBTT_RASTERIZER_VERSION == 2 - -// the edge passed in here does not cross the vertical line at x or the vertical line at x+1 -// (i.e. it has already been clipped to those) -static void stbtt__handle_clipped_edge(float *scanline, int x, stbtt__active_edge *e, float x0, float y0, float x1, float y1) -{ - if (y0 == y1) return; - STBTT_assert(y0 < y1); - STBTT_assert(e->sy <= e->ey); - if (y0 > e->ey) return; - if (y1 < e->sy) return; - if (y0 < e->sy) { - x0 += (x1-x0) * (e->sy - y0) / (y1-y0); - y0 = e->sy; - } - if (y1 > e->ey) { - x1 += (x1-x0) * (e->ey - y1) / (y1-y0); - y1 = e->ey; - } - - if (x0 == x) - STBTT_assert(x1 <= x+1); - else if (x0 == x+1) - STBTT_assert(x1 >= x); - else if (x0 <= x) - STBTT_assert(x1 <= x); - else if (x0 >= x+1) - STBTT_assert(x1 >= x+1); - else - STBTT_assert(x1 >= x && x1 <= x+1); - - if (x0 <= x && x1 <= x) - scanline[x] += e->direction * (y1-y0); - else if (x0 >= x+1 && x1 >= x+1) - ; - else { - STBTT_assert(x0 >= x && x0 <= x+1 && x1 >= x && x1 <= x+1); - scanline[x] += e->direction * (y1-y0) * (1-((x0-x)+(x1-x))/2); // coverage = 1 - average x position - } -} - -static float stbtt__sized_trapezoid_area(float height, float top_width, float bottom_width) -{ - STBTT_assert(top_width >= 0); - STBTT_assert(bottom_width >= 0); - return (top_width + bottom_width) / 2.0f * height; -} - -static float stbtt__position_trapezoid_area(float height, float tx0, float tx1, float bx0, float bx1) -{ - return stbtt__sized_trapezoid_area(height, tx1 - tx0, bx1 - bx0); -} - -static float stbtt__sized_triangle_area(float height, float width) -{ - return height * width / 2; -} - -static void stbtt__fill_active_edges_new(float *scanline, float *scanline_fill, int len, stbtt__active_edge *e, float y_top) -{ - float y_bottom = y_top+1; - - while (e) { - // brute force every pixel - - // compute intersection points with top & bottom - STBTT_assert(e->ey >= y_top); - - if (e->fdx == 0) { - float x0 = e->fx; - if (x0 < len) { - if (x0 >= 0) { - stbtt__handle_clipped_edge(scanline,(int) x0,e, x0,y_top, x0,y_bottom); - stbtt__handle_clipped_edge(scanline_fill-1,(int) x0+1,e, x0,y_top, x0,y_bottom); - } else { - stbtt__handle_clipped_edge(scanline_fill-1,0,e, x0,y_top, x0,y_bottom); - } - } - } else { - float x0 = e->fx; - float dx = e->fdx; - float xb = x0 + dx; - float x_top, x_bottom; - float sy0,sy1; - float dy = e->fdy; - STBTT_assert(e->sy <= y_bottom && e->ey >= y_top); - - // compute endpoints of line segment clipped to this scanline (if the - // line segment starts on this scanline. x0 is the intersection of the - // line with y_top, but that may be off the line segment. - if (e->sy > y_top) { - x_top = x0 + dx * (e->sy - y_top); - sy0 = e->sy; - } else { - x_top = x0; - sy0 = y_top; - } - if (e->ey < y_bottom) { - x_bottom = x0 + dx * (e->ey - y_top); - sy1 = e->ey; - } else { - x_bottom = xb; - sy1 = y_bottom; - } - - if (x_top >= 0 && x_bottom >= 0 && x_top < len && x_bottom < len) { - // from here on, we don't have to range check x values - - if ((int) x_top == (int) x_bottom) { - float height; - // simple case, only spans one pixel - int x = (int) x_top; - height = (sy1 - sy0) * e->direction; - STBTT_assert(x >= 0 && x < len); - scanline[x] += stbtt__position_trapezoid_area(height, x_top, x+1.0f, x_bottom, x+1.0f); - scanline_fill[x] += height; // everything right of this pixel is filled - } else { - int x,x1,x2; - float y_crossing, y_final, step, sign, area; - // covers 2+ pixels - if (x_top > x_bottom) { - // flip scanline vertically; signed area is the same - float t; - sy0 = y_bottom - (sy0 - y_top); - sy1 = y_bottom - (sy1 - y_top); - t = sy0, sy0 = sy1, sy1 = t; - t = x_bottom, x_bottom = x_top, x_top = t; - dx = -dx; - dy = -dy; - t = x0, x0 = xb, xb = t; - } - STBTT_assert(dy >= 0); - STBTT_assert(dx >= 0); - - x1 = (int) x_top; - x2 = (int) x_bottom; - // compute intersection with y axis at x1+1 - y_crossing = y_top + dy * (x1+1 - x0); - - // compute intersection with y axis at x2 - y_final = y_top + dy * (x2 - x0); - - // x1 x_top x2 x_bottom - // y_top +------|-----+------------+------------+--------|---+------------+ - // | | | | | | - // | | | | | | - // sy0 | Txxxxx|............|............|............|............| - // y_crossing | *xxxxx.......|............|............|............| - // | | xxxxx..|............|............|............| - // | | /- xx*xxxx........|............|............| - // | | dy < | xxxxxx..|............|............| - // y_final | | \- | xx*xxx.........|............| - // sy1 | | | | xxxxxB...|............| - // | | | | | | - // | | | | | | - // y_bottom +------------+------------+------------+------------+------------+ - // - // goal is to measure the area covered by '.' in each pixel - - // if x2 is right at the right edge of x1, y_crossing can blow up, github #1057 - // @TODO: maybe test against sy1 rather than y_bottom? - if (y_crossing > y_bottom) - y_crossing = y_bottom; - - sign = e->direction; - - // area of the rectangle covered from sy0..y_crossing - area = sign * (y_crossing-sy0); - - // area of the triangle (x_top,sy0), (x1+1,sy0), (x1+1,y_crossing) - scanline[x1] += stbtt__sized_triangle_area(area, x1+1 - x_top); - - // check if final y_crossing is blown up; no test case for this - if (y_final > y_bottom) { - int denom = (x2 - (x1+1)); - y_final = y_bottom; - if (denom != 0) { // [DEAR IMGUI] Avoid div by zero (https://github.com/nothings/stb/issues/1316) - dy = (y_final - y_crossing ) / denom; // if denom=0, y_final = y_crossing, so y_final <= y_bottom - } - } - - // in second pixel, area covered by line segment found in first pixel - // is always a rectangle 1 wide * the height of that line segment; this - // is exactly what the variable 'area' stores. it also gets a contribution - // from the line segment within it. the THIRD pixel will get the first - // pixel's rectangle contribution, the second pixel's rectangle contribution, - // and its own contribution. the 'own contribution' is the same in every pixel except - // the leftmost and rightmost, a trapezoid that slides down in each pixel. - // the second pixel's contribution to the third pixel will be the - // rectangle 1 wide times the height change in the second pixel, which is dy. - - step = sign * dy * 1; // dy is dy/dx, change in y for every 1 change in x, - // which multiplied by 1-pixel-width is how much pixel area changes for each step in x - // so the area advances by 'step' every time - - for (x = x1+1; x < x2; ++x) { - scanline[x] += area + step/2; // area of trapezoid is 1*step/2 - area += step; - } - STBTT_assert(STBTT_fabs(area) <= 1.01f); // accumulated error from area += step unless we round step down - STBTT_assert(sy1 > y_final-0.01f); - - // area covered in the last pixel is the rectangle from all the pixels to the left, - // plus the trapezoid filled by the line segment in this pixel all the way to the right edge - scanline[x2] += area + sign * stbtt__position_trapezoid_area(sy1-y_final, (float) x2, x2+1.0f, x_bottom, x2+1.0f); - - // the rest of the line is filled based on the total height of the line segment in this pixel - scanline_fill[x2] += sign * (sy1-sy0); - } - } else { - // if edge goes outside of box we're drawing, we require - // clipping logic. since this does not match the intended use - // of this library, we use a different, very slow brute - // force implementation - // note though that this does happen some of the time because - // x_top and x_bottom can be extrapolated at the top & bottom of - // the shape and actually lie outside the bounding box - int x; - for (x=0; x < len; ++x) { - // cases: - // - // there can be up to two intersections with the pixel. any intersection - // with left or right edges can be handled by splitting into two (or three) - // regions. intersections with top & bottom do not necessitate case-wise logic. - // - // the old way of doing this found the intersections with the left & right edges, - // then used some simple logic to produce up to three segments in sorted order - // from top-to-bottom. however, this had a problem: if an x edge was epsilon - // across the x border, then the corresponding y position might not be distinct - // from the other y segment, and it might ignored as an empty segment. to avoid - // that, we need to explicitly produce segments based on x positions. - - // rename variables to clearly-defined pairs - float y0 = y_top; - float x1 = (float) (x); - float x2 = (float) (x+1); - float x3 = xb; - float y3 = y_bottom; - - // x = e->x + e->dx * (y-y_top) - // (y-y_top) = (x - e->x) / e->dx - // y = (x - e->x) / e->dx + y_top - float y1 = (x - x0) / dx + y_top; - float y2 = (x+1 - x0) / dx + y_top; - - if (x0 < x1 && x3 > x2) { // three segments descending down-right - stbtt__handle_clipped_edge(scanline,x,e, x0,y0, x1,y1); - stbtt__handle_clipped_edge(scanline,x,e, x1,y1, x2,y2); - stbtt__handle_clipped_edge(scanline,x,e, x2,y2, x3,y3); - } else if (x3 < x1 && x0 > x2) { // three segments descending down-left - stbtt__handle_clipped_edge(scanline,x,e, x0,y0, x2,y2); - stbtt__handle_clipped_edge(scanline,x,e, x2,y2, x1,y1); - stbtt__handle_clipped_edge(scanline,x,e, x1,y1, x3,y3); - } else if (x0 < x1 && x3 > x1) { // two segments across x, down-right - stbtt__handle_clipped_edge(scanline,x,e, x0,y0, x1,y1); - stbtt__handle_clipped_edge(scanline,x,e, x1,y1, x3,y3); - } else if (x3 < x1 && x0 > x1) { // two segments across x, down-left - stbtt__handle_clipped_edge(scanline,x,e, x0,y0, x1,y1); - stbtt__handle_clipped_edge(scanline,x,e, x1,y1, x3,y3); - } else if (x0 < x2 && x3 > x2) { // two segments across x+1, down-right - stbtt__handle_clipped_edge(scanline,x,e, x0,y0, x2,y2); - stbtt__handle_clipped_edge(scanline,x,e, x2,y2, x3,y3); - } else if (x3 < x2 && x0 > x2) { // two segments across x+1, down-left - stbtt__handle_clipped_edge(scanline,x,e, x0,y0, x2,y2); - stbtt__handle_clipped_edge(scanline,x,e, x2,y2, x3,y3); - } else { // one segment - stbtt__handle_clipped_edge(scanline,x,e, x0,y0, x3,y3); - } - } - } - } - e = e->next; - } -} - -// directly AA rasterize edges w/o supersampling -static void stbtt__rasterize_sorted_edges(stbtt__bitmap *result, stbtt__edge *e, int n, int vsubsample, int off_x, int off_y, void *userdata) -{ - stbtt__hheap hh = { 0, 0, 0 }; - stbtt__active_edge *active = NULL; - int y,j=0, i; - float scanline_data[129], *scanline, *scanline2; - - STBTT__NOTUSED(vsubsample); - - if (result->w > 64) - scanline = (float *) STBTT_malloc((result->w*2+1) * sizeof(float), userdata); - else - scanline = scanline_data; - - scanline2 = scanline + result->w; - - y = off_y; - e[n].y0 = (float) (off_y + result->h) + 1; - - while (j < result->h) { - // find center of pixel for this scanline - float scan_y_top = y + 0.0f; - float scan_y_bottom = y + 1.0f; - stbtt__active_edge **step = &active; - - STBTT_memset(scanline , 0, result->w*sizeof(scanline[0])); - STBTT_memset(scanline2, 0, (result->w+1)*sizeof(scanline[0])); - - // update all active edges; - // remove all active edges that terminate before the top of this scanline - while (*step) { - stbtt__active_edge * z = *step; - if (z->ey <= scan_y_top) { - *step = z->next; // delete from list - STBTT_assert(z->direction); - z->direction = 0; - stbtt__hheap_free(&hh, z); - } else { - step = &((*step)->next); // advance through list - } - } - - // insert all edges that start before the bottom of this scanline - while (e->y0 <= scan_y_bottom) { - if (e->y0 != e->y1) { - stbtt__active_edge *z = stbtt__new_active(&hh, e, off_x, scan_y_top, userdata); - if (z != NULL) { - if (j == 0 && off_y != 0) { - if (z->ey < scan_y_top) { - // this can happen due to subpixel positioning and some kind of fp rounding error i think - z->ey = scan_y_top; - } - } - STBTT_assert(z->ey >= scan_y_top); // if we get really unlucky a tiny bit of an edge can be out of bounds - // insert at front - z->next = active; - active = z; - } - } - ++e; - } - - // now process all active edges - if (active) - stbtt__fill_active_edges_new(scanline, scanline2+1, result->w, active, scan_y_top); - - { - float sum = 0; - for (i=0; i < result->w; ++i) { - float k; - int m; - sum += scanline2[i]; - k = scanline[i] + sum; - k = (float) STBTT_fabs(k)*255 + 0.5f; - m = (int) k; - if (m > 255) m = 255; - result->pixels[j*result->stride + i] = (unsigned char) m; - } - } - // advance all the edges - step = &active; - while (*step) { - stbtt__active_edge *z = *step; - z->fx += z->fdx; // advance to position for current scanline - step = &((*step)->next); // advance through list - } - - ++y; - ++j; - } - - stbtt__hheap_cleanup(&hh, userdata); - - if (scanline != scanline_data) - STBTT_free(scanline, userdata); -} -#else -#error "Unrecognized value of STBTT_RASTERIZER_VERSION" -#endif - -#define STBTT__COMPARE(a,b) ((a)->y0 < (b)->y0) - -static void stbtt__sort_edges_ins_sort(stbtt__edge *p, int n) -{ - int i,j; - for (i=1; i < n; ++i) { - stbtt__edge t = p[i], *a = &t; - j = i; - while (j > 0) { - stbtt__edge *b = &p[j-1]; - int c = STBTT__COMPARE(a,b); - if (!c) break; - p[j] = p[j-1]; - --j; - } - if (i != j) - p[j] = t; - } -} - -static void stbtt__sort_edges_quicksort(stbtt__edge *p, int n) -{ - /* threshold for transitioning to insertion sort */ - while (n > 12) { - stbtt__edge t; - int c01,c12,c,m,i,j; - - /* compute median of three */ - m = n >> 1; - c01 = STBTT__COMPARE(&p[0],&p[m]); - c12 = STBTT__COMPARE(&p[m],&p[n-1]); - /* if 0 >= mid >= end, or 0 < mid < end, then use mid */ - if (c01 != c12) { - /* otherwise, we'll need to swap something else to middle */ - int z; - c = STBTT__COMPARE(&p[0],&p[n-1]); - /* 0>mid && midn => n; 0 0 */ - /* 0n: 0>n => 0; 0 n */ - z = (c == c12) ? 0 : n-1; - t = p[z]; - p[z] = p[m]; - p[m] = t; - } - /* now p[m] is the median-of-three */ - /* swap it to the beginning so it won't move around */ - t = p[0]; - p[0] = p[m]; - p[m] = t; - - /* partition loop */ - i=1; - j=n-1; - for(;;) { - /* handling of equality is crucial here */ - /* for sentinels & efficiency with duplicates */ - for (;;++i) { - if (!STBTT__COMPARE(&p[i], &p[0])) break; - } - for (;;--j) { - if (!STBTT__COMPARE(&p[0], &p[j])) break; - } - /* make sure we haven't crossed */ - if (i >= j) break; - t = p[i]; - p[i] = p[j]; - p[j] = t; - - ++i; - --j; - } - /* recurse on smaller side, iterate on larger */ - if (j < (n-i)) { - stbtt__sort_edges_quicksort(p,j); - p = p+i; - n = n-i; - } else { - stbtt__sort_edges_quicksort(p+i, n-i); - n = j; - } - } -} - -static void stbtt__sort_edges(stbtt__edge *p, int n) -{ - stbtt__sort_edges_quicksort(p, n); - stbtt__sort_edges_ins_sort(p, n); -} - -typedef struct -{ - float x,y; -} stbtt__point; - -static void stbtt__rasterize(stbtt__bitmap *result, stbtt__point *pts, int *wcount, int windings, float scale_x, float scale_y, float shift_x, float shift_y, int off_x, int off_y, int invert, void *userdata) -{ - float y_scale_inv = invert ? -scale_y : scale_y; - stbtt__edge *e; - int n,i,j,k,m; -#if STBTT_RASTERIZER_VERSION == 1 - int vsubsample = result->h < 8 ? 15 : 5; -#elif STBTT_RASTERIZER_VERSION == 2 - int vsubsample = 1; -#else - #error "Unrecognized value of STBTT_RASTERIZER_VERSION" -#endif - // vsubsample should divide 255 evenly; otherwise we won't reach full opacity - - // now we have to blow out the windings into explicit edge lists - n = 0; - for (i=0; i < windings; ++i) - n += wcount[i]; - - e = (stbtt__edge *) STBTT_malloc(sizeof(*e) * (n+1), userdata); // add an extra one as a sentinel - if (e == 0) return; - n = 0; - - m=0; - for (i=0; i < windings; ++i) { - stbtt__point *p = pts + m; - m += wcount[i]; - j = wcount[i]-1; - for (k=0; k < wcount[i]; j=k++) { - int a=k,b=j; - // skip the edge if horizontal - if (p[j].y == p[k].y) - continue; - // add edge from j to k to the list - e[n].invert = 0; - if (invert ? p[j].y > p[k].y : p[j].y < p[k].y) { - e[n].invert = 1; - a=j,b=k; - } - e[n].x0 = p[a].x * scale_x + shift_x; - e[n].y0 = (p[a].y * y_scale_inv + shift_y) * vsubsample; - e[n].x1 = p[b].x * scale_x + shift_x; - e[n].y1 = (p[b].y * y_scale_inv + shift_y) * vsubsample; - ++n; - } - } - - // now sort the edges by their highest point (should snap to integer, and then by x) - //STBTT_sort(e, n, sizeof(e[0]), stbtt__edge_compare); - stbtt__sort_edges(e, n); - - // now, traverse the scanlines and find the intersections on each scanline, use xor winding rule - stbtt__rasterize_sorted_edges(result, e, n, vsubsample, off_x, off_y, userdata); - - STBTT_free(e, userdata); -} - -static void stbtt__add_point(stbtt__point *points, int n, float x, float y) -{ - if (!points) return; // during first pass, it's unallocated - points[n].x = x; - points[n].y = y; -} - -// tessellate until threshold p is happy... @TODO warped to compensate for non-linear stretching -static int stbtt__tesselate_curve(stbtt__point *points, int *num_points, float x0, float y0, float x1, float y1, float x2, float y2, float objspace_flatness_squared, int n) -{ - // midpoint - float mx = (x0 + 2*x1 + x2)/4; - float my = (y0 + 2*y1 + y2)/4; - // versus directly drawn line - float dx = (x0+x2)/2 - mx; - float dy = (y0+y2)/2 - my; - if (n > 16) // 65536 segments on one curve better be enough! - return 1; - if (dx*dx+dy*dy > objspace_flatness_squared) { // half-pixel error allowed... need to be smaller if AA - stbtt__tesselate_curve(points, num_points, x0,y0, (x0+x1)/2.0f,(y0+y1)/2.0f, mx,my, objspace_flatness_squared,n+1); - stbtt__tesselate_curve(points, num_points, mx,my, (x1+x2)/2.0f,(y1+y2)/2.0f, x2,y2, objspace_flatness_squared,n+1); - } else { - stbtt__add_point(points, *num_points,x2,y2); - *num_points = *num_points+1; - } - return 1; -} - -static void stbtt__tesselate_cubic(stbtt__point *points, int *num_points, float x0, float y0, float x1, float y1, float x2, float y2, float x3, float y3, float objspace_flatness_squared, int n) -{ - // @TODO this "flatness" calculation is just made-up nonsense that seems to work well enough - float dx0 = x1-x0; - float dy0 = y1-y0; - float dx1 = x2-x1; - float dy1 = y2-y1; - float dx2 = x3-x2; - float dy2 = y3-y2; - float dx = x3-x0; - float dy = y3-y0; - float longlen = (float) (STBTT_sqrt(dx0*dx0+dy0*dy0)+STBTT_sqrt(dx1*dx1+dy1*dy1)+STBTT_sqrt(dx2*dx2+dy2*dy2)); - float shortlen = (float) STBTT_sqrt(dx*dx+dy*dy); - float flatness_squared = longlen*longlen-shortlen*shortlen; - - if (n > 16) // 65536 segments on one curve better be enough! - return; - - if (flatness_squared > objspace_flatness_squared) { - float x01 = (x0+x1)/2; - float y01 = (y0+y1)/2; - float x12 = (x1+x2)/2; - float y12 = (y1+y2)/2; - float x23 = (x2+x3)/2; - float y23 = (y2+y3)/2; - - float xa = (x01+x12)/2; - float ya = (y01+y12)/2; - float xb = (x12+x23)/2; - float yb = (y12+y23)/2; - - float mx = (xa+xb)/2; - float my = (ya+yb)/2; - - stbtt__tesselate_cubic(points, num_points, x0,y0, x01,y01, xa,ya, mx,my, objspace_flatness_squared,n+1); - stbtt__tesselate_cubic(points, num_points, mx,my, xb,yb, x23,y23, x3,y3, objspace_flatness_squared,n+1); - } else { - stbtt__add_point(points, *num_points,x3,y3); - *num_points = *num_points+1; - } -} - -// returns number of contours -static stbtt__point *stbtt_FlattenCurves(stbtt_vertex *vertices, int num_verts, float objspace_flatness, int **contour_lengths, int *num_contours, void *userdata) -{ - stbtt__point *points=0; - int num_points=0; - - float objspace_flatness_squared = objspace_flatness * objspace_flatness; - int i,n=0,start=0, pass; - - // count how many "moves" there are to get the contour count - for (i=0; i < num_verts; ++i) - if (vertices[i].type == STBTT_vmove) - ++n; - - *num_contours = n; - if (n == 0) return 0; - - *contour_lengths = (int *) STBTT_malloc(sizeof(**contour_lengths) * n, userdata); - - if (*contour_lengths == 0) { - *num_contours = 0; - return 0; - } - - // make two passes through the points so we don't need to realloc - for (pass=0; pass < 2; ++pass) { - float x=0,y=0; - if (pass == 1) { - points = (stbtt__point *) STBTT_malloc(num_points * sizeof(points[0]), userdata); - if (points == NULL) goto error; - } - num_points = 0; - n= -1; - for (i=0; i < num_verts; ++i) { - switch (vertices[i].type) { - case STBTT_vmove: - // start the next contour - if (n >= 0) - (*contour_lengths)[n] = num_points - start; - ++n; - start = num_points; - - x = vertices[i].x, y = vertices[i].y; - stbtt__add_point(points, num_points++, x,y); - break; - case STBTT_vline: - x = vertices[i].x, y = vertices[i].y; - stbtt__add_point(points, num_points++, x, y); - break; - case STBTT_vcurve: - stbtt__tesselate_curve(points, &num_points, x,y, - vertices[i].cx, vertices[i].cy, - vertices[i].x, vertices[i].y, - objspace_flatness_squared, 0); - x = vertices[i].x, y = vertices[i].y; - break; - case STBTT_vcubic: - stbtt__tesselate_cubic(points, &num_points, x,y, - vertices[i].cx, vertices[i].cy, - vertices[i].cx1, vertices[i].cy1, - vertices[i].x, vertices[i].y, - objspace_flatness_squared, 0); - x = vertices[i].x, y = vertices[i].y; - break; - } - } - (*contour_lengths)[n] = num_points - start; - } - - return points; -error: - STBTT_free(points, userdata); - STBTT_free(*contour_lengths, userdata); - *contour_lengths = 0; - *num_contours = 0; - return NULL; -} - -STBTT_DEF void stbtt_Rasterize(stbtt__bitmap *result, float flatness_in_pixels, stbtt_vertex *vertices, int num_verts, float scale_x, float scale_y, float shift_x, float shift_y, int x_off, int y_off, int invert, void *userdata) -{ - float scale = scale_x > scale_y ? scale_y : scale_x; - int winding_count = 0; - int *winding_lengths = NULL; - stbtt__point *windings = stbtt_FlattenCurves(vertices, num_verts, flatness_in_pixels / scale, &winding_lengths, &winding_count, userdata); - if (windings) { - stbtt__rasterize(result, windings, winding_lengths, winding_count, scale_x, scale_y, shift_x, shift_y, x_off, y_off, invert, userdata); - STBTT_free(winding_lengths, userdata); - STBTT_free(windings, userdata); - } -} - -STBTT_DEF void stbtt_FreeBitmap(unsigned char *bitmap, void *userdata) -{ - STBTT_free(bitmap, userdata); -} - -STBTT_DEF unsigned char *stbtt_GetGlyphBitmapSubpixel(const stbtt_fontinfo *info, float scale_x, float scale_y, float shift_x, float shift_y, int glyph, int *width, int *height, int *xoff, int *yoff) -{ - int ix0,iy0,ix1,iy1; - stbtt__bitmap gbm; - stbtt_vertex *vertices; - int num_verts = stbtt_GetGlyphShape(info, glyph, &vertices); - - if (scale_x == 0) scale_x = scale_y; - if (scale_y == 0) { - if (scale_x == 0) { - STBTT_free(vertices, info->userdata); - return NULL; - } - scale_y = scale_x; - } - - stbtt_GetGlyphBitmapBoxSubpixel(info, glyph, scale_x, scale_y, shift_x, shift_y, &ix0,&iy0,&ix1,&iy1); - - // now we get the size - gbm.w = (ix1 - ix0); - gbm.h = (iy1 - iy0); - gbm.pixels = NULL; // in case we error - - if (width ) *width = gbm.w; - if (height) *height = gbm.h; - if (xoff ) *xoff = ix0; - if (yoff ) *yoff = iy0; - - if (gbm.w && gbm.h) { - gbm.pixels = (unsigned char *) STBTT_malloc(gbm.w * gbm.h, info->userdata); - if (gbm.pixels) { - gbm.stride = gbm.w; - - stbtt_Rasterize(&gbm, 0.35f, vertices, num_verts, scale_x, scale_y, shift_x, shift_y, ix0, iy0, 1, info->userdata); - } - } - STBTT_free(vertices, info->userdata); - return gbm.pixels; -} - -STBTT_DEF unsigned char *stbtt_GetGlyphBitmap(const stbtt_fontinfo *info, float scale_x, float scale_y, int glyph, int *width, int *height, int *xoff, int *yoff) -{ - return stbtt_GetGlyphBitmapSubpixel(info, scale_x, scale_y, 0.0f, 0.0f, glyph, width, height, xoff, yoff); -} - -STBTT_DEF void stbtt_MakeGlyphBitmapSubpixel(const stbtt_fontinfo *info, unsigned char *output, int out_w, int out_h, int out_stride, float scale_x, float scale_y, float shift_x, float shift_y, int glyph) -{ - int ix0,iy0; - stbtt_vertex *vertices; - int num_verts = stbtt_GetGlyphShape(info, glyph, &vertices); - stbtt__bitmap gbm; - - stbtt_GetGlyphBitmapBoxSubpixel(info, glyph, scale_x, scale_y, shift_x, shift_y, &ix0,&iy0,0,0); - gbm.pixels = output; - gbm.w = out_w; - gbm.h = out_h; - gbm.stride = out_stride; - - if (gbm.w && gbm.h) - stbtt_Rasterize(&gbm, 0.35f, vertices, num_verts, scale_x, scale_y, shift_x, shift_y, ix0,iy0, 1, info->userdata); - - STBTT_free(vertices, info->userdata); -} - -STBTT_DEF void stbtt_MakeGlyphBitmap(const stbtt_fontinfo *info, unsigned char *output, int out_w, int out_h, int out_stride, float scale_x, float scale_y, int glyph) -{ - stbtt_MakeGlyphBitmapSubpixel(info, output, out_w, out_h, out_stride, scale_x, scale_y, 0.0f,0.0f, glyph); -} - -STBTT_DEF unsigned char *stbtt_GetCodepointBitmapSubpixel(const stbtt_fontinfo *info, float scale_x, float scale_y, float shift_x, float shift_y, int codepoint, int *width, int *height, int *xoff, int *yoff) -{ - return stbtt_GetGlyphBitmapSubpixel(info, scale_x, scale_y,shift_x,shift_y, stbtt_FindGlyphIndex(info,codepoint), width,height,xoff,yoff); -} - -STBTT_DEF void stbtt_MakeCodepointBitmapSubpixelPrefilter(const stbtt_fontinfo *info, unsigned char *output, int out_w, int out_h, int out_stride, float scale_x, float scale_y, float shift_x, float shift_y, int oversample_x, int oversample_y, float *sub_x, float *sub_y, int codepoint) -{ - stbtt_MakeGlyphBitmapSubpixelPrefilter(info, output, out_w, out_h, out_stride, scale_x, scale_y, shift_x, shift_y, oversample_x, oversample_y, sub_x, sub_y, stbtt_FindGlyphIndex(info,codepoint)); -} - -STBTT_DEF void stbtt_MakeCodepointBitmapSubpixel(const stbtt_fontinfo *info, unsigned char *output, int out_w, int out_h, int out_stride, float scale_x, float scale_y, float shift_x, float shift_y, int codepoint) -{ - stbtt_MakeGlyphBitmapSubpixel(info, output, out_w, out_h, out_stride, scale_x, scale_y, shift_x, shift_y, stbtt_FindGlyphIndex(info,codepoint)); -} - -STBTT_DEF unsigned char *stbtt_GetCodepointBitmap(const stbtt_fontinfo *info, float scale_x, float scale_y, int codepoint, int *width, int *height, int *xoff, int *yoff) -{ - return stbtt_GetCodepointBitmapSubpixel(info, scale_x, scale_y, 0.0f,0.0f, codepoint, width,height,xoff,yoff); -} - -STBTT_DEF void stbtt_MakeCodepointBitmap(const stbtt_fontinfo *info, unsigned char *output, int out_w, int out_h, int out_stride, float scale_x, float scale_y, int codepoint) -{ - stbtt_MakeCodepointBitmapSubpixel(info, output, out_w, out_h, out_stride, scale_x, scale_y, 0.0f,0.0f, codepoint); -} - -////////////////////////////////////////////////////////////////////////////// -// -// bitmap baking -// -// This is SUPER-CRAPPY packing to keep source code small - -static int stbtt_BakeFontBitmap_internal(unsigned char *data, int offset, // font location (use offset=0 for plain .ttf) - float pixel_height, // height of font in pixels - unsigned char *pixels, int pw, int ph, // bitmap to be filled in - int first_char, int num_chars, // characters to bake - stbtt_bakedchar *chardata) -{ - float scale; - int x,y,bottom_y, i; - stbtt_fontinfo f; - f.userdata = NULL; - if (!stbtt_InitFont(&f, data, offset)) - return -1; - STBTT_memset(pixels, 0, pw*ph); // background of 0 around pixels - x=y=1; - bottom_y = 1; - - scale = stbtt_ScaleForPixelHeight(&f, pixel_height); - - for (i=0; i < num_chars; ++i) { - int advance, lsb, x0,y0,x1,y1,gw,gh; - int g = stbtt_FindGlyphIndex(&f, first_char + i); - stbtt_GetGlyphHMetrics(&f, g, &advance, &lsb); - stbtt_GetGlyphBitmapBox(&f, g, scale,scale, &x0,&y0,&x1,&y1); - gw = x1-x0; - gh = y1-y0; - if (x + gw + 1 >= pw) - y = bottom_y, x = 1; // advance to next row - if (y + gh + 1 >= ph) // check if it fits vertically AFTER potentially moving to next row - return -i; - STBTT_assert(x+gw < pw); - STBTT_assert(y+gh < ph); - stbtt_MakeGlyphBitmap(&f, pixels+x+y*pw, gw,gh,pw, scale,scale, g); - chardata[i].x0 = (stbtt_int16) x; - chardata[i].y0 = (stbtt_int16) y; - chardata[i].x1 = (stbtt_int16) (x + gw); - chardata[i].y1 = (stbtt_int16) (y + gh); - chardata[i].xadvance = scale * advance; - chardata[i].xoff = (float) x0; - chardata[i].yoff = (float) y0; - x = x + gw + 1; - if (y+gh+1 > bottom_y) - bottom_y = y+gh+1; - } - return bottom_y; -} - -STBTT_DEF void stbtt_GetBakedQuad(const stbtt_bakedchar *chardata, int pw, int ph, int char_index, float *xpos, float *ypos, stbtt_aligned_quad *q, int opengl_fillrule) -{ - float d3d_bias = opengl_fillrule ? 0 : -0.5f; - float ipw = 1.0f / pw, iph = 1.0f / ph; - const stbtt_bakedchar *b = chardata + char_index; - int round_x = STBTT_ifloor((*xpos + b->xoff) + 0.5f); - int round_y = STBTT_ifloor((*ypos + b->yoff) + 0.5f); - - q->x0 = round_x + d3d_bias; - q->y0 = round_y + d3d_bias; - q->x1 = round_x + b->x1 - b->x0 + d3d_bias; - q->y1 = round_y + b->y1 - b->y0 + d3d_bias; - - q->s0 = b->x0 * ipw; - q->t0 = b->y0 * iph; - q->s1 = b->x1 * ipw; - q->t1 = b->y1 * iph; - - *xpos += b->xadvance; -} - -////////////////////////////////////////////////////////////////////////////// -// -// rectangle packing replacement routines if you don't have stb_rect_pack.h -// - -#ifndef STB_RECT_PACK_VERSION - -typedef int stbrp_coord; - -//////////////////////////////////////////////////////////////////////////////////// -// // -// // -// COMPILER WARNING ?!?!? // -// // -// // -// if you get a compile warning due to these symbols being defined more than // -// once, move #include "stb_rect_pack.h" before #include "stb_truetype.h" // -// // -//////////////////////////////////////////////////////////////////////////////////// - -typedef struct -{ - int width,height; - int x,y,bottom_y; -} stbrp_context; - -typedef struct -{ - unsigned char x; -} stbrp_node; - -struct stbrp_rect -{ - stbrp_coord x,y; - int id,w,h,was_packed; -}; - -static void stbrp_init_target(stbrp_context *con, int pw, int ph, stbrp_node *nodes, int num_nodes) -{ - con->width = pw; - con->height = ph; - con->x = 0; - con->y = 0; - con->bottom_y = 0; - STBTT__NOTUSED(nodes); - STBTT__NOTUSED(num_nodes); -} - -static void stbrp_pack_rects(stbrp_context *con, stbrp_rect *rects, int num_rects) -{ - int i; - for (i=0; i < num_rects; ++i) { - if (con->x + rects[i].w > con->width) { - con->x = 0; - con->y = con->bottom_y; - } - if (con->y + rects[i].h > con->height) - break; - rects[i].x = con->x; - rects[i].y = con->y; - rects[i].was_packed = 1; - con->x += rects[i].w; - if (con->y + rects[i].h > con->bottom_y) - con->bottom_y = con->y + rects[i].h; - } - for ( ; i < num_rects; ++i) - rects[i].was_packed = 0; -} -#endif - -////////////////////////////////////////////////////////////////////////////// -// -// bitmap baking -// -// This is SUPER-AWESOME (tm Ryan Gordon) packing using stb_rect_pack.h. If -// stb_rect_pack.h isn't available, it uses the BakeFontBitmap strategy. - -STBTT_DEF int stbtt_PackBegin(stbtt_pack_context *spc, unsigned char *pixels, int pw, int ph, int stride_in_bytes, int padding, void *alloc_context) -{ - stbrp_context *context = (stbrp_context *) STBTT_malloc(sizeof(*context) ,alloc_context); - int num_nodes = pw - padding; - stbrp_node *nodes = (stbrp_node *) STBTT_malloc(sizeof(*nodes ) * num_nodes,alloc_context); - - if (context == NULL || nodes == NULL) { - if (context != NULL) STBTT_free(context, alloc_context); - if (nodes != NULL) STBTT_free(nodes , alloc_context); - return 0; - } - - spc->user_allocator_context = alloc_context; - spc->width = pw; - spc->height = ph; - spc->pixels = pixels; - spc->pack_info = context; - spc->nodes = nodes; - spc->padding = padding; - spc->stride_in_bytes = stride_in_bytes != 0 ? stride_in_bytes : pw; - spc->h_oversample = 1; - spc->v_oversample = 1; - spc->skip_missing = 0; - - stbrp_init_target(context, pw-padding, ph-padding, nodes, num_nodes); - - if (pixels) - STBTT_memset(pixels, 0, pw*ph); // background of 0 around pixels - - return 1; -} - -STBTT_DEF void stbtt_PackEnd (stbtt_pack_context *spc) -{ - STBTT_free(spc->nodes , spc->user_allocator_context); - STBTT_free(spc->pack_info, spc->user_allocator_context); -} - -STBTT_DEF void stbtt_PackSetOversampling(stbtt_pack_context *spc, unsigned int h_oversample, unsigned int v_oversample) -{ - STBTT_assert(h_oversample <= STBTT_MAX_OVERSAMPLE); - STBTT_assert(v_oversample <= STBTT_MAX_OVERSAMPLE); - if (h_oversample <= STBTT_MAX_OVERSAMPLE) - spc->h_oversample = h_oversample; - if (v_oversample <= STBTT_MAX_OVERSAMPLE) - spc->v_oversample = v_oversample; -} - -STBTT_DEF void stbtt_PackSetSkipMissingCodepoints(stbtt_pack_context *spc, int skip) -{ - spc->skip_missing = skip; -} - -#define STBTT__OVER_MASK (STBTT_MAX_OVERSAMPLE-1) - -static void stbtt__h_prefilter(unsigned char *pixels, int w, int h, int stride_in_bytes, unsigned int kernel_width) -{ - unsigned char buffer[STBTT_MAX_OVERSAMPLE]; - int safe_w = w - kernel_width; - int j; - STBTT_memset(buffer, 0, STBTT_MAX_OVERSAMPLE); // suppress bogus warning from VS2013 -analyze - for (j=0; j < h; ++j) { - int i; - unsigned int total; - STBTT_memset(buffer, 0, kernel_width); - - total = 0; - - // make kernel_width a constant in common cases so compiler can optimize out the divide - switch (kernel_width) { - case 2: - for (i=0; i <= safe_w; ++i) { - total += pixels[i] - buffer[i & STBTT__OVER_MASK]; - buffer[(i+kernel_width) & STBTT__OVER_MASK] = pixels[i]; - pixels[i] = (unsigned char) (total / 2); - } - break; - case 3: - for (i=0; i <= safe_w; ++i) { - total += pixels[i] - buffer[i & STBTT__OVER_MASK]; - buffer[(i+kernel_width) & STBTT__OVER_MASK] = pixels[i]; - pixels[i] = (unsigned char) (total / 3); - } - break; - case 4: - for (i=0; i <= safe_w; ++i) { - total += pixels[i] - buffer[i & STBTT__OVER_MASK]; - buffer[(i+kernel_width) & STBTT__OVER_MASK] = pixels[i]; - pixels[i] = (unsigned char) (total / 4); - } - break; - case 5: - for (i=0; i <= safe_w; ++i) { - total += pixels[i] - buffer[i & STBTT__OVER_MASK]; - buffer[(i+kernel_width) & STBTT__OVER_MASK] = pixels[i]; - pixels[i] = (unsigned char) (total / 5); - } - break; - default: - for (i=0; i <= safe_w; ++i) { - total += pixels[i] - buffer[i & STBTT__OVER_MASK]; - buffer[(i+kernel_width) & STBTT__OVER_MASK] = pixels[i]; - pixels[i] = (unsigned char) (total / kernel_width); - } - break; - } - - for (; i < w; ++i) { - STBTT_assert(pixels[i] == 0); - total -= buffer[i & STBTT__OVER_MASK]; - pixels[i] = (unsigned char) (total / kernel_width); - } - - pixels += stride_in_bytes; - } -} - -static void stbtt__v_prefilter(unsigned char *pixels, int w, int h, int stride_in_bytes, unsigned int kernel_width) -{ - unsigned char buffer[STBTT_MAX_OVERSAMPLE]; - int safe_h = h - kernel_width; - int j; - STBTT_memset(buffer, 0, STBTT_MAX_OVERSAMPLE); // suppress bogus warning from VS2013 -analyze - for (j=0; j < w; ++j) { - int i; - unsigned int total; - STBTT_memset(buffer, 0, kernel_width); - - total = 0; - - // make kernel_width a constant in common cases so compiler can optimize out the divide - switch (kernel_width) { - case 2: - for (i=0; i <= safe_h; ++i) { - total += pixels[i*stride_in_bytes] - buffer[i & STBTT__OVER_MASK]; - buffer[(i+kernel_width) & STBTT__OVER_MASK] = pixels[i*stride_in_bytes]; - pixels[i*stride_in_bytes] = (unsigned char) (total / 2); - } - break; - case 3: - for (i=0; i <= safe_h; ++i) { - total += pixels[i*stride_in_bytes] - buffer[i & STBTT__OVER_MASK]; - buffer[(i+kernel_width) & STBTT__OVER_MASK] = pixels[i*stride_in_bytes]; - pixels[i*stride_in_bytes] = (unsigned char) (total / 3); - } - break; - case 4: - for (i=0; i <= safe_h; ++i) { - total += pixels[i*stride_in_bytes] - buffer[i & STBTT__OVER_MASK]; - buffer[(i+kernel_width) & STBTT__OVER_MASK] = pixels[i*stride_in_bytes]; - pixels[i*stride_in_bytes] = (unsigned char) (total / 4); - } - break; - case 5: - for (i=0; i <= safe_h; ++i) { - total += pixels[i*stride_in_bytes] - buffer[i & STBTT__OVER_MASK]; - buffer[(i+kernel_width) & STBTT__OVER_MASK] = pixels[i*stride_in_bytes]; - pixels[i*stride_in_bytes] = (unsigned char) (total / 5); - } - break; - default: - for (i=0; i <= safe_h; ++i) { - total += pixels[i*stride_in_bytes] - buffer[i & STBTT__OVER_MASK]; - buffer[(i+kernel_width) & STBTT__OVER_MASK] = pixels[i*stride_in_bytes]; - pixels[i*stride_in_bytes] = (unsigned char) (total / kernel_width); - } - break; - } - - for (; i < h; ++i) { - STBTT_assert(pixels[i*stride_in_bytes] == 0); - total -= buffer[i & STBTT__OVER_MASK]; - pixels[i*stride_in_bytes] = (unsigned char) (total / kernel_width); - } - - pixels += 1; - } -} - -static float stbtt__oversample_shift(int oversample) -{ - if (!oversample) - return 0.0f; - - // The prefilter is a box filter of width "oversample", - // which shifts phase by (oversample - 1)/2 pixels in - // oversampled space. We want to shift in the opposite - // direction to counter this. - return (float)-(oversample - 1) / (2.0f * (float)oversample); -} - -// rects array must be big enough to accommodate all characters in the given ranges -STBTT_DEF int stbtt_PackFontRangesGatherRects(stbtt_pack_context *spc, const stbtt_fontinfo *info, stbtt_pack_range *ranges, int num_ranges, stbrp_rect *rects) -{ - int i,j,k; - int missing_glyph_added = 0; - - k=0; - for (i=0; i < num_ranges; ++i) { - float fh = ranges[i].font_size; - float scale = fh > 0 ? stbtt_ScaleForPixelHeight(info, fh) : stbtt_ScaleForMappingEmToPixels(info, -fh); - ranges[i].h_oversample = (unsigned char) spc->h_oversample; - ranges[i].v_oversample = (unsigned char) spc->v_oversample; - for (j=0; j < ranges[i].num_chars; ++j) { - int x0,y0,x1,y1; - int codepoint = ranges[i].array_of_unicode_codepoints == NULL ? ranges[i].first_unicode_codepoint_in_range + j : ranges[i].array_of_unicode_codepoints[j]; - int glyph = stbtt_FindGlyphIndex(info, codepoint); - if (glyph == 0 && (spc->skip_missing || missing_glyph_added)) { - rects[k].w = rects[k].h = 0; - } else { - stbtt_GetGlyphBitmapBoxSubpixel(info,glyph, - scale * spc->h_oversample, - scale * spc->v_oversample, - 0,0, - &x0,&y0,&x1,&y1); - rects[k].w = (stbrp_coord) (x1-x0 + spc->padding + spc->h_oversample-1); - rects[k].h = (stbrp_coord) (y1-y0 + spc->padding + spc->v_oversample-1); - if (glyph == 0) - missing_glyph_added = 1; - } - ++k; - } - } - - return k; -} - -STBTT_DEF void stbtt_MakeGlyphBitmapSubpixelPrefilter(const stbtt_fontinfo *info, unsigned char *output, int out_w, int out_h, int out_stride, float scale_x, float scale_y, float shift_x, float shift_y, int prefilter_x, int prefilter_y, float *sub_x, float *sub_y, int glyph) -{ - stbtt_MakeGlyphBitmapSubpixel(info, - output, - out_w - (prefilter_x - 1), - out_h - (prefilter_y - 1), - out_stride, - scale_x, - scale_y, - shift_x, - shift_y, - glyph); - - if (prefilter_x > 1) - stbtt__h_prefilter(output, out_w, out_h, out_stride, prefilter_x); - - if (prefilter_y > 1) - stbtt__v_prefilter(output, out_w, out_h, out_stride, prefilter_y); - - *sub_x = stbtt__oversample_shift(prefilter_x); - *sub_y = stbtt__oversample_shift(prefilter_y); -} - -// rects array must be big enough to accommodate all characters in the given ranges -STBTT_DEF int stbtt_PackFontRangesRenderIntoRects(stbtt_pack_context *spc, const stbtt_fontinfo *info, stbtt_pack_range *ranges, int num_ranges, stbrp_rect *rects) -{ - int i,j,k, missing_glyph = -1, return_value = 1; - - // save current values - int old_h_over = spc->h_oversample; - int old_v_over = spc->v_oversample; - - k = 0; - for (i=0; i < num_ranges; ++i) { - float fh = ranges[i].font_size; - float scale = fh > 0 ? stbtt_ScaleForPixelHeight(info, fh) : stbtt_ScaleForMappingEmToPixels(info, -fh); - float recip_h,recip_v,sub_x,sub_y; - spc->h_oversample = ranges[i].h_oversample; - spc->v_oversample = ranges[i].v_oversample; - recip_h = 1.0f / spc->h_oversample; - recip_v = 1.0f / spc->v_oversample; - sub_x = stbtt__oversample_shift(spc->h_oversample); - sub_y = stbtt__oversample_shift(spc->v_oversample); - for (j=0; j < ranges[i].num_chars; ++j) { - stbrp_rect *r = &rects[k]; - if (r->was_packed && r->w != 0 && r->h != 0) { - stbtt_packedchar *bc = &ranges[i].chardata_for_range[j]; - int advance, lsb, x0,y0,x1,y1; - int codepoint = ranges[i].array_of_unicode_codepoints == NULL ? ranges[i].first_unicode_codepoint_in_range + j : ranges[i].array_of_unicode_codepoints[j]; - int glyph = stbtt_FindGlyphIndex(info, codepoint); - stbrp_coord pad = (stbrp_coord) spc->padding; - - // pad on left and top - r->x += pad; - r->y += pad; - r->w -= pad; - r->h -= pad; - stbtt_GetGlyphHMetrics(info, glyph, &advance, &lsb); - stbtt_GetGlyphBitmapBox(info, glyph, - scale * spc->h_oversample, - scale * spc->v_oversample, - &x0,&y0,&x1,&y1); - stbtt_MakeGlyphBitmapSubpixel(info, - spc->pixels + r->x + r->y*spc->stride_in_bytes, - r->w - spc->h_oversample+1, - r->h - spc->v_oversample+1, - spc->stride_in_bytes, - scale * spc->h_oversample, - scale * spc->v_oversample, - 0,0, - glyph); - - if (spc->h_oversample > 1) - stbtt__h_prefilter(spc->pixels + r->x + r->y*spc->stride_in_bytes, - r->w, r->h, spc->stride_in_bytes, - spc->h_oversample); - - if (spc->v_oversample > 1) - stbtt__v_prefilter(spc->pixels + r->x + r->y*spc->stride_in_bytes, - r->w, r->h, spc->stride_in_bytes, - spc->v_oversample); - - bc->x0 = (stbtt_int16) r->x; - bc->y0 = (stbtt_int16) r->y; - bc->x1 = (stbtt_int16) (r->x + r->w); - bc->y1 = (stbtt_int16) (r->y + r->h); - bc->xadvance = scale * advance; - bc->xoff = (float) x0 * recip_h + sub_x; - bc->yoff = (float) y0 * recip_v + sub_y; - bc->xoff2 = (x0 + r->w) * recip_h + sub_x; - bc->yoff2 = (y0 + r->h) * recip_v + sub_y; - - if (glyph == 0) - missing_glyph = j; - } else if (spc->skip_missing) { - return_value = 0; - } else if (r->was_packed && r->w == 0 && r->h == 0 && missing_glyph >= 0) { - ranges[i].chardata_for_range[j] = ranges[i].chardata_for_range[missing_glyph]; - } else { - return_value = 0; // if any fail, report failure - } - - ++k; - } - } - - // restore original values - spc->h_oversample = old_h_over; - spc->v_oversample = old_v_over; - - return return_value; -} - -STBTT_DEF void stbtt_PackFontRangesPackRects(stbtt_pack_context *spc, stbrp_rect *rects, int num_rects) -{ - stbrp_pack_rects((stbrp_context *) spc->pack_info, rects, num_rects); -} - -STBTT_DEF int stbtt_PackFontRanges(stbtt_pack_context *spc, const unsigned char *fontdata, int font_index, stbtt_pack_range *ranges, int num_ranges) -{ - stbtt_fontinfo info; - int i, j, n, return_value; // [DEAR IMGUI] removed = 1; - //stbrp_context *context = (stbrp_context *) spc->pack_info; - stbrp_rect *rects; - - // flag all characters as NOT packed - for (i=0; i < num_ranges; ++i) - for (j=0; j < ranges[i].num_chars; ++j) - ranges[i].chardata_for_range[j].x0 = - ranges[i].chardata_for_range[j].y0 = - ranges[i].chardata_for_range[j].x1 = - ranges[i].chardata_for_range[j].y1 = 0; - - n = 0; - for (i=0; i < num_ranges; ++i) - n += ranges[i].num_chars; - - rects = (stbrp_rect *) STBTT_malloc(sizeof(*rects) * n, spc->user_allocator_context); - if (rects == NULL) - return 0; - - info.userdata = spc->user_allocator_context; - stbtt_InitFont(&info, fontdata, stbtt_GetFontOffsetForIndex(fontdata,font_index)); - - n = stbtt_PackFontRangesGatherRects(spc, &info, ranges, num_ranges, rects); - - stbtt_PackFontRangesPackRects(spc, rects, n); - - return_value = stbtt_PackFontRangesRenderIntoRects(spc, &info, ranges, num_ranges, rects); - - STBTT_free(rects, spc->user_allocator_context); - return return_value; -} - -STBTT_DEF int stbtt_PackFontRange(stbtt_pack_context *spc, const unsigned char *fontdata, int font_index, float font_size, - int first_unicode_codepoint_in_range, int num_chars_in_range, stbtt_packedchar *chardata_for_range) -{ - stbtt_pack_range range; - range.first_unicode_codepoint_in_range = first_unicode_codepoint_in_range; - range.array_of_unicode_codepoints = NULL; - range.num_chars = num_chars_in_range; - range.chardata_for_range = chardata_for_range; - range.font_size = font_size; - return stbtt_PackFontRanges(spc, fontdata, font_index, &range, 1); -} - -STBTT_DEF void stbtt_GetScaledFontVMetrics(const unsigned char *fontdata, int index, float size, float *ascent, float *descent, float *lineGap) -{ - int i_ascent, i_descent, i_lineGap; - float scale; - stbtt_fontinfo info; - stbtt_InitFont(&info, fontdata, stbtt_GetFontOffsetForIndex(fontdata, index)); - scale = size > 0 ? stbtt_ScaleForPixelHeight(&info, size) : stbtt_ScaleForMappingEmToPixels(&info, -size); - stbtt_GetFontVMetrics(&info, &i_ascent, &i_descent, &i_lineGap); - *ascent = (float) i_ascent * scale; - *descent = (float) i_descent * scale; - *lineGap = (float) i_lineGap * scale; -} - -STBTT_DEF void stbtt_GetPackedQuad(const stbtt_packedchar *chardata, int pw, int ph, int char_index, float *xpos, float *ypos, stbtt_aligned_quad *q, int align_to_integer) -{ - float ipw = 1.0f / pw, iph = 1.0f / ph; - const stbtt_packedchar *b = chardata + char_index; - - if (align_to_integer) { - float x = (float) STBTT_ifloor((*xpos + b->xoff) + 0.5f); - float y = (float) STBTT_ifloor((*ypos + b->yoff) + 0.5f); - q->x0 = x; - q->y0 = y; - q->x1 = x + b->xoff2 - b->xoff; - q->y1 = y + b->yoff2 - b->yoff; - } else { - q->x0 = *xpos + b->xoff; - q->y0 = *ypos + b->yoff; - q->x1 = *xpos + b->xoff2; - q->y1 = *ypos + b->yoff2; - } - - q->s0 = b->x0 * ipw; - q->t0 = b->y0 * iph; - q->s1 = b->x1 * ipw; - q->t1 = b->y1 * iph; - - *xpos += b->xadvance; -} - -////////////////////////////////////////////////////////////////////////////// -// -// sdf computation -// - -#define STBTT_min(a,b) ((a) < (b) ? (a) : (b)) -#define STBTT_max(a,b) ((a) < (b) ? (b) : (a)) - -static int stbtt__ray_intersect_bezier(float orig[2], float ray[2], float q0[2], float q1[2], float q2[2], float hits[2][2]) -{ - float q0perp = q0[1]*ray[0] - q0[0]*ray[1]; - float q1perp = q1[1]*ray[0] - q1[0]*ray[1]; - float q2perp = q2[1]*ray[0] - q2[0]*ray[1]; - float roperp = orig[1]*ray[0] - orig[0]*ray[1]; - - float a = q0perp - 2*q1perp + q2perp; - float b = q1perp - q0perp; - float c = q0perp - roperp; - - float s0 = 0., s1 = 0.; - int num_s = 0; - - if (a != 0.0) { - float discr = b*b - a*c; - if (discr > 0.0) { - float rcpna = -1 / a; - float d = (float) STBTT_sqrt(discr); - s0 = (b+d) * rcpna; - s1 = (b-d) * rcpna; - if (s0 >= 0.0 && s0 <= 1.0) - num_s = 1; - if (d > 0.0 && s1 >= 0.0 && s1 <= 1.0) { - if (num_s == 0) s0 = s1; - ++num_s; - } - } - } else { - // 2*b*s + c = 0 - // s = -c / (2*b) - s0 = c / (-2 * b); - if (s0 >= 0.0 && s0 <= 1.0) - num_s = 1; - } - - if (num_s == 0) - return 0; - else { - float rcp_len2 = 1 / (ray[0]*ray[0] + ray[1]*ray[1]); - float rayn_x = ray[0] * rcp_len2, rayn_y = ray[1] * rcp_len2; - - float q0d = q0[0]*rayn_x + q0[1]*rayn_y; - float q1d = q1[0]*rayn_x + q1[1]*rayn_y; - float q2d = q2[0]*rayn_x + q2[1]*rayn_y; - float rod = orig[0]*rayn_x + orig[1]*rayn_y; - - float q10d = q1d - q0d; - float q20d = q2d - q0d; - float q0rd = q0d - rod; - - hits[0][0] = q0rd + s0*(2.0f - 2.0f*s0)*q10d + s0*s0*q20d; - hits[0][1] = a*s0+b; - - if (num_s > 1) { - hits[1][0] = q0rd + s1*(2.0f - 2.0f*s1)*q10d + s1*s1*q20d; - hits[1][1] = a*s1+b; - return 2; - } else { - return 1; - } - } -} - -static int equal(float *a, float *b) -{ - return (a[0] == b[0] && a[1] == b[1]); -} - -static int stbtt__compute_crossings_x(float x, float y, int nverts, stbtt_vertex *verts) -{ - int i; - float orig[2], ray[2] = { 1, 0 }; - float y_frac; - int winding = 0; - - // make sure y never passes through a vertex of the shape - y_frac = (float) STBTT_fmod(y, 1.0f); - if (y_frac < 0.01f) - y += 0.01f; - else if (y_frac > 0.99f) - y -= 0.01f; - - orig[0] = x; - orig[1] = y; - - // test a ray from (-infinity,y) to (x,y) - for (i=0; i < nverts; ++i) { - if (verts[i].type == STBTT_vline) { - int x0 = (int) verts[i-1].x, y0 = (int) verts[i-1].y; - int x1 = (int) verts[i ].x, y1 = (int) verts[i ].y; - if (y > STBTT_min(y0,y1) && y < STBTT_max(y0,y1) && x > STBTT_min(x0,x1)) { - float x_inter = (y - y0) / (y1 - y0) * (x1-x0) + x0; - if (x_inter < x) - winding += (y0 < y1) ? 1 : -1; - } - } - if (verts[i].type == STBTT_vcurve) { - int x0 = (int) verts[i-1].x , y0 = (int) verts[i-1].y ; - int x1 = (int) verts[i ].cx, y1 = (int) verts[i ].cy; - int x2 = (int) verts[i ].x , y2 = (int) verts[i ].y ; - int ax = STBTT_min(x0,STBTT_min(x1,x2)), ay = STBTT_min(y0,STBTT_min(y1,y2)); - int by = STBTT_max(y0,STBTT_max(y1,y2)); - if (y > ay && y < by && x > ax) { - float q0[2],q1[2],q2[2]; - float hits[2][2]; - q0[0] = (float)x0; - q0[1] = (float)y0; - q1[0] = (float)x1; - q1[1] = (float)y1; - q2[0] = (float)x2; - q2[1] = (float)y2; - if (equal(q0,q1) || equal(q1,q2)) { - x0 = (int)verts[i-1].x; - y0 = (int)verts[i-1].y; - x1 = (int)verts[i ].x; - y1 = (int)verts[i ].y; - if (y > STBTT_min(y0,y1) && y < STBTT_max(y0,y1) && x > STBTT_min(x0,x1)) { - float x_inter = (y - y0) / (y1 - y0) * (x1-x0) + x0; - if (x_inter < x) - winding += (y0 < y1) ? 1 : -1; - } - } else { - int num_hits = stbtt__ray_intersect_bezier(orig, ray, q0, q1, q2, hits); - if (num_hits >= 1) - if (hits[0][0] < 0) - winding += (hits[0][1] < 0 ? -1 : 1); - if (num_hits >= 2) - if (hits[1][0] < 0) - winding += (hits[1][1] < 0 ? -1 : 1); - } - } - } - } - return winding; -} - -static float stbtt__cuberoot( float x ) -{ - if (x<0) - return -(float) STBTT_pow(-x,1.0f/3.0f); - else - return (float) STBTT_pow( x,1.0f/3.0f); -} - -// x^3 + a*x^2 + b*x + c = 0 -static int stbtt__solve_cubic(float a, float b, float c, float* r) -{ - float s = -a / 3; - float p = b - a*a / 3; - float q = a * (2*a*a - 9*b) / 27 + c; - float p3 = p*p*p; - float d = q*q + 4*p3 / 27; - if (d >= 0) { - float z = (float) STBTT_sqrt(d); - float u = (-q + z) / 2; - float v = (-q - z) / 2; - u = stbtt__cuberoot(u); - v = stbtt__cuberoot(v); - r[0] = s + u + v; - return 1; - } else { - float u = (float) STBTT_sqrt(-p/3); - float v = (float) STBTT_acos(-STBTT_sqrt(-27/p3) * q / 2) / 3; // p3 must be negative, since d is negative - float m = (float) STBTT_cos(v); - float n = (float) STBTT_cos(v-3.141592/2)*1.732050808f; - r[0] = s + u * 2 * m; - r[1] = s - u * (m + n); - r[2] = s - u * (m - n); - - //STBTT_assert( STBTT_fabs(((r[0]+a)*r[0]+b)*r[0]+c) < 0.05f); // these asserts may not be safe at all scales, though they're in bezier t parameter units so maybe? - //STBTT_assert( STBTT_fabs(((r[1]+a)*r[1]+b)*r[1]+c) < 0.05f); - //STBTT_assert( STBTT_fabs(((r[2]+a)*r[2]+b)*r[2]+c) < 0.05f); - return 3; - } -} - -STBTT_DEF unsigned char * stbtt_GetGlyphSDF(const stbtt_fontinfo *info, float scale, int glyph, int padding, unsigned char onedge_value, float pixel_dist_scale, int *width, int *height, int *xoff, int *yoff) -{ - float scale_x = scale, scale_y = scale; - int ix0,iy0,ix1,iy1; - int w,h; - unsigned char *data; - - if (scale == 0) return NULL; - - stbtt_GetGlyphBitmapBoxSubpixel(info, glyph, scale, scale, 0.0f,0.0f, &ix0,&iy0,&ix1,&iy1); - - // if empty, return NULL - if (ix0 == ix1 || iy0 == iy1) - return NULL; - - ix0 -= padding; - iy0 -= padding; - ix1 += padding; - iy1 += padding; - - w = (ix1 - ix0); - h = (iy1 - iy0); - - if (width ) *width = w; - if (height) *height = h; - if (xoff ) *xoff = ix0; - if (yoff ) *yoff = iy0; - - // invert for y-downwards bitmaps - scale_y = -scale_y; - - { - int x,y,i,j; - float *precompute; - stbtt_vertex *verts; - int num_verts = stbtt_GetGlyphShape(info, glyph, &verts); - data = (unsigned char *) STBTT_malloc(w * h, info->userdata); - precompute = (float *) STBTT_malloc(num_verts * sizeof(float), info->userdata); - - for (i=0,j=num_verts-1; i < num_verts; j=i++) { - if (verts[i].type == STBTT_vline) { - float x0 = verts[i].x*scale_x, y0 = verts[i].y*scale_y; - float x1 = verts[j].x*scale_x, y1 = verts[j].y*scale_y; - float dist = (float) STBTT_sqrt((x1-x0)*(x1-x0) + (y1-y0)*(y1-y0)); - precompute[i] = (dist == 0) ? 0.0f : 1.0f / dist; - } else if (verts[i].type == STBTT_vcurve) { - float x2 = verts[j].x *scale_x, y2 = verts[j].y *scale_y; - float x1 = verts[i].cx*scale_x, y1 = verts[i].cy*scale_y; - float x0 = verts[i].x *scale_x, y0 = verts[i].y *scale_y; - float bx = x0 - 2*x1 + x2, by = y0 - 2*y1 + y2; - float len2 = bx*bx + by*by; - if (len2 != 0.0f) - precompute[i] = 1.0f / (bx*bx + by*by); - else - precompute[i] = 0.0f; - } else - precompute[i] = 0.0f; - } - - for (y=iy0; y < iy1; ++y) { - for (x=ix0; x < ix1; ++x) { - float val; - float min_dist = 999999.0f; - float sx = (float) x + 0.5f; - float sy = (float) y + 0.5f; - float x_gspace = (sx / scale_x); - float y_gspace = (sy / scale_y); - - int winding = stbtt__compute_crossings_x(x_gspace, y_gspace, num_verts, verts); // @OPTIMIZE: this could just be a rasterization, but needs to be line vs. non-tesselated curves so a new path - - for (i=0; i < num_verts; ++i) { - float x0 = verts[i].x*scale_x, y0 = verts[i].y*scale_y; - - if (verts[i].type == STBTT_vline && precompute[i] != 0.0f) { - float x1 = verts[i-1].x*scale_x, y1 = verts[i-1].y*scale_y; - - float dist,dist2 = (x0-sx)*(x0-sx) + (y0-sy)*(y0-sy); - if (dist2 < min_dist*min_dist) - min_dist = (float) STBTT_sqrt(dist2); - - // coarse culling against bbox - //if (sx > STBTT_min(x0,x1)-min_dist && sx < STBTT_max(x0,x1)+min_dist && - // sy > STBTT_min(y0,y1)-min_dist && sy < STBTT_max(y0,y1)+min_dist) - dist = (float) STBTT_fabs((x1-x0)*(y0-sy) - (y1-y0)*(x0-sx)) * precompute[i]; - STBTT_assert(i != 0); - if (dist < min_dist) { - // check position along line - // x' = x0 + t*(x1-x0), y' = y0 + t*(y1-y0) - // minimize (x'-sx)*(x'-sx)+(y'-sy)*(y'-sy) - float dx = x1-x0, dy = y1-y0; - float px = x0-sx, py = y0-sy; - // minimize (px+t*dx)^2 + (py+t*dy)^2 = px*px + 2*px*dx*t + t^2*dx*dx + py*py + 2*py*dy*t + t^2*dy*dy - // derivative: 2*px*dx + 2*py*dy + (2*dx*dx+2*dy*dy)*t, set to 0 and solve - float t = -(px*dx + py*dy) / (dx*dx + dy*dy); - if (t >= 0.0f && t <= 1.0f) - min_dist = dist; - } - } else if (verts[i].type == STBTT_vcurve) { - float x2 = verts[i-1].x *scale_x, y2 = verts[i-1].y *scale_y; - float x1 = verts[i ].cx*scale_x, y1 = verts[i ].cy*scale_y; - float box_x0 = STBTT_min(STBTT_min(x0,x1),x2); - float box_y0 = STBTT_min(STBTT_min(y0,y1),y2); - float box_x1 = STBTT_max(STBTT_max(x0,x1),x2); - float box_y1 = STBTT_max(STBTT_max(y0,y1),y2); - // coarse culling against bbox to avoid computing cubic unnecessarily - if (sx > box_x0-min_dist && sx < box_x1+min_dist && sy > box_y0-min_dist && sy < box_y1+min_dist) { - int num=0; - float ax = x1-x0, ay = y1-y0; - float bx = x0 - 2*x1 + x2, by = y0 - 2*y1 + y2; - float mx = x0 - sx, my = y0 - sy; - float res[3] = {0.f,0.f,0.f}; - float px,py,t,it,dist2; - float a_inv = precompute[i]; - if (a_inv == 0.0) { // if a_inv is 0, it's 2nd degree so use quadratic formula - float a = 3*(ax*bx + ay*by); - float b = 2*(ax*ax + ay*ay) + (mx*bx+my*by); - float c = mx*ax+my*ay; - if (a == 0.0) { // if a is 0, it's linear - if (b != 0.0) { - res[num++] = -c/b; - } - } else { - float discriminant = b*b - 4*a*c; - if (discriminant < 0) - num = 0; - else { - float root = (float) STBTT_sqrt(discriminant); - res[0] = (-b - root)/(2*a); - res[1] = (-b + root)/(2*a); - num = 2; // don't bother distinguishing 1-solution case, as code below will still work - } - } - } else { - float b = 3*(ax*bx + ay*by) * a_inv; // could precompute this as it doesn't depend on sample point - float c = (2*(ax*ax + ay*ay) + (mx*bx+my*by)) * a_inv; - float d = (mx*ax+my*ay) * a_inv; - num = stbtt__solve_cubic(b, c, d, res); - } - dist2 = (x0-sx)*(x0-sx) + (y0-sy)*(y0-sy); - if (dist2 < min_dist*min_dist) - min_dist = (float) STBTT_sqrt(dist2); - - if (num >= 1 && res[0] >= 0.0f && res[0] <= 1.0f) { - t = res[0], it = 1.0f - t; - px = it*it*x0 + 2*t*it*x1 + t*t*x2; - py = it*it*y0 + 2*t*it*y1 + t*t*y2; - dist2 = (px-sx)*(px-sx) + (py-sy)*(py-sy); - if (dist2 < min_dist * min_dist) - min_dist = (float) STBTT_sqrt(dist2); - } - if (num >= 2 && res[1] >= 0.0f && res[1] <= 1.0f) { - t = res[1], it = 1.0f - t; - px = it*it*x0 + 2*t*it*x1 + t*t*x2; - py = it*it*y0 + 2*t*it*y1 + t*t*y2; - dist2 = (px-sx)*(px-sx) + (py-sy)*(py-sy); - if (dist2 < min_dist * min_dist) - min_dist = (float) STBTT_sqrt(dist2); - } - if (num >= 3 && res[2] >= 0.0f && res[2] <= 1.0f) { - t = res[2], it = 1.0f - t; - px = it*it*x0 + 2*t*it*x1 + t*t*x2; - py = it*it*y0 + 2*t*it*y1 + t*t*y2; - dist2 = (px-sx)*(px-sx) + (py-sy)*(py-sy); - if (dist2 < min_dist * min_dist) - min_dist = (float) STBTT_sqrt(dist2); - } - } - } - } - if (winding == 0) - min_dist = -min_dist; // if outside the shape, value is negative - val = onedge_value + pixel_dist_scale * min_dist; - if (val < 0) - val = 0; - else if (val > 255) - val = 255; - data[(y-iy0)*w+(x-ix0)] = (unsigned char) val; - } - } - STBTT_free(precompute, info->userdata); - STBTT_free(verts, info->userdata); - } - return data; -} - -STBTT_DEF unsigned char * stbtt_GetCodepointSDF(const stbtt_fontinfo *info, float scale, int codepoint, int padding, unsigned char onedge_value, float pixel_dist_scale, int *width, int *height, int *xoff, int *yoff) -{ - return stbtt_GetGlyphSDF(info, scale, stbtt_FindGlyphIndex(info, codepoint), padding, onedge_value, pixel_dist_scale, width, height, xoff, yoff); -} - -STBTT_DEF void stbtt_FreeSDF(unsigned char *bitmap, void *userdata) -{ - STBTT_free(bitmap, userdata); -} - -////////////////////////////////////////////////////////////////////////////// -// -// font name matching -- recommended not to use this -// - -// check if a utf8 string contains a prefix which is the utf16 string; if so return length of matching utf8 string -static stbtt_int32 stbtt__CompareUTF8toUTF16_bigendian_prefix(stbtt_uint8 *s1, stbtt_int32 len1, stbtt_uint8 *s2, stbtt_int32 len2) -{ - stbtt_int32 i=0; - - // convert utf16 to utf8 and compare the results while converting - while (len2) { - stbtt_uint16 ch = s2[0]*256 + s2[1]; - if (ch < 0x80) { - if (i >= len1) return -1; - if (s1[i++] != ch) return -1; - } else if (ch < 0x800) { - if (i+1 >= len1) return -1; - if (s1[i++] != 0xc0 + (ch >> 6)) return -1; - if (s1[i++] != 0x80 + (ch & 0x3f)) return -1; - } else if (ch >= 0xd800 && ch < 0xdc00) { - stbtt_uint32 c; - stbtt_uint16 ch2 = s2[2]*256 + s2[3]; - if (i+3 >= len1) return -1; - c = ((ch - 0xd800) << 10) + (ch2 - 0xdc00) + 0x10000; - if (s1[i++] != 0xf0 + (c >> 18)) return -1; - if (s1[i++] != 0x80 + ((c >> 12) & 0x3f)) return -1; - if (s1[i++] != 0x80 + ((c >> 6) & 0x3f)) return -1; - if (s1[i++] != 0x80 + ((c ) & 0x3f)) return -1; - s2 += 2; // plus another 2 below - len2 -= 2; - } else if (ch >= 0xdc00 && ch < 0xe000) { - return -1; - } else { - if (i+2 >= len1) return -1; - if (s1[i++] != 0xe0 + (ch >> 12)) return -1; - if (s1[i++] != 0x80 + ((ch >> 6) & 0x3f)) return -1; - if (s1[i++] != 0x80 + ((ch ) & 0x3f)) return -1; - } - s2 += 2; - len2 -= 2; - } - return i; -} - -static int stbtt_CompareUTF8toUTF16_bigendian_internal(char *s1, int len1, char *s2, int len2) -{ - return len1 == stbtt__CompareUTF8toUTF16_bigendian_prefix((stbtt_uint8*) s1, len1, (stbtt_uint8*) s2, len2); -} - -// returns results in whatever encoding you request... but note that 2-byte encodings -// will be BIG-ENDIAN... use stbtt_CompareUTF8toUTF16_bigendian() to compare -STBTT_DEF const char *stbtt_GetFontNameString(const stbtt_fontinfo *font, int *length, int platformID, int encodingID, int languageID, int nameID) -{ - stbtt_int32 i,count,stringOffset; - stbtt_uint8 *fc = font->data; - stbtt_uint32 offset = font->fontstart; - stbtt_uint32 nm = stbtt__find_table(fc, offset, "name"); - if (!nm) return NULL; - - count = ttUSHORT(fc+nm+2); - stringOffset = nm + ttUSHORT(fc+nm+4); - for (i=0; i < count; ++i) { - stbtt_uint32 loc = nm + 6 + 12 * i; - if (platformID == ttUSHORT(fc+loc+0) && encodingID == ttUSHORT(fc+loc+2) - && languageID == ttUSHORT(fc+loc+4) && nameID == ttUSHORT(fc+loc+6)) { - *length = ttUSHORT(fc+loc+8); - return (const char *) (fc+stringOffset+ttUSHORT(fc+loc+10)); - } - } - return NULL; -} - -static int stbtt__matchpair(stbtt_uint8 *fc, stbtt_uint32 nm, stbtt_uint8 *name, stbtt_int32 nlen, stbtt_int32 target_id, stbtt_int32 next_id) -{ - stbtt_int32 i; - stbtt_int32 count = ttUSHORT(fc+nm+2); - stbtt_int32 stringOffset = nm + ttUSHORT(fc+nm+4); - - for (i=0; i < count; ++i) { - stbtt_uint32 loc = nm + 6 + 12 * i; - stbtt_int32 id = ttUSHORT(fc+loc+6); - if (id == target_id) { - // find the encoding - stbtt_int32 platform = ttUSHORT(fc+loc+0), encoding = ttUSHORT(fc+loc+2), language = ttUSHORT(fc+loc+4); - - // is this a Unicode encoding? - if (platform == 0 || (platform == 3 && encoding == 1) || (platform == 3 && encoding == 10)) { - stbtt_int32 slen = ttUSHORT(fc+loc+8); - stbtt_int32 off = ttUSHORT(fc+loc+10); - - // check if there's a prefix match - stbtt_int32 matchlen = stbtt__CompareUTF8toUTF16_bigendian_prefix(name, nlen, fc+stringOffset+off,slen); - if (matchlen >= 0) { - // check for target_id+1 immediately following, with same encoding & language - if (i+1 < count && ttUSHORT(fc+loc+12+6) == next_id && ttUSHORT(fc+loc+12) == platform && ttUSHORT(fc+loc+12+2) == encoding && ttUSHORT(fc+loc+12+4) == language) { - slen = ttUSHORT(fc+loc+12+8); - off = ttUSHORT(fc+loc+12+10); - if (slen == 0) { - if (matchlen == nlen) - return 1; - } else if (matchlen < nlen && name[matchlen] == ' ') { - ++matchlen; - if (stbtt_CompareUTF8toUTF16_bigendian_internal((char*) (name+matchlen), nlen-matchlen, (char*)(fc+stringOffset+off),slen)) - return 1; - } - } else { - // if nothing immediately following - if (matchlen == nlen) - return 1; - } - } - } - - // @TODO handle other encodings - } - } - return 0; -} - -static int stbtt__matches(stbtt_uint8 *fc, stbtt_uint32 offset, stbtt_uint8 *name, stbtt_int32 flags) -{ - stbtt_int32 nlen = (stbtt_int32) STBTT_strlen((char *) name); - stbtt_uint32 nm,hd; - if (!stbtt__isfont(fc+offset)) return 0; - - // check italics/bold/underline flags in macStyle... - if (flags) { - hd = stbtt__find_table(fc, offset, "head"); - if ((ttUSHORT(fc+hd+44) & 7) != (flags & 7)) return 0; - } - - nm = stbtt__find_table(fc, offset, "name"); - if (!nm) return 0; - - if (flags) { - // if we checked the macStyle flags, then just check the family and ignore the subfamily - if (stbtt__matchpair(fc, nm, name, nlen, 16, -1)) return 1; - if (stbtt__matchpair(fc, nm, name, nlen, 1, -1)) return 1; - if (stbtt__matchpair(fc, nm, name, nlen, 3, -1)) return 1; - } else { - if (stbtt__matchpair(fc, nm, name, nlen, 16, 17)) return 1; - if (stbtt__matchpair(fc, nm, name, nlen, 1, 2)) return 1; - if (stbtt__matchpair(fc, nm, name, nlen, 3, -1)) return 1; - } - - return 0; -} - -static int stbtt_FindMatchingFont_internal(unsigned char *font_collection, char *name_utf8, stbtt_int32 flags) -{ - stbtt_int32 i; - for (i=0;;++i) { - stbtt_int32 off = stbtt_GetFontOffsetForIndex(font_collection, i); - if (off < 0) return off; - if (stbtt__matches((stbtt_uint8 *) font_collection, off, (stbtt_uint8*) name_utf8, flags)) - return off; - } -} - -#if defined(__GNUC__) || defined(__clang__) -#pragma GCC diagnostic push -#pragma GCC diagnostic ignored "-Wcast-qual" -#endif - -STBTT_DEF int stbtt_BakeFontBitmap(const unsigned char *data, int offset, - float pixel_height, unsigned char *pixels, int pw, int ph, - int first_char, int num_chars, stbtt_bakedchar *chardata) -{ - return stbtt_BakeFontBitmap_internal((unsigned char *) data, offset, pixel_height, pixels, pw, ph, first_char, num_chars, chardata); -} - -STBTT_DEF int stbtt_GetFontOffsetForIndex(const unsigned char *data, int index) -{ - return stbtt_GetFontOffsetForIndex_internal((unsigned char *) data, index); -} - -STBTT_DEF int stbtt_GetNumberOfFonts(const unsigned char *data) -{ - return stbtt_GetNumberOfFonts_internal((unsigned char *) data); -} - -STBTT_DEF int stbtt_InitFont(stbtt_fontinfo *info, const unsigned char *data, int offset) -{ - return stbtt_InitFont_internal(info, (unsigned char *) data, offset); -} - -STBTT_DEF int stbtt_FindMatchingFont(const unsigned char *fontdata, const char *name, int flags) -{ - return stbtt_FindMatchingFont_internal((unsigned char *) fontdata, (char *) name, flags); -} - -STBTT_DEF int stbtt_CompareUTF8toUTF16_bigendian(const char *s1, int len1, const char *s2, int len2) -{ - return stbtt_CompareUTF8toUTF16_bigendian_internal((char *) s1, len1, (char *) s2, len2); -} - -#if defined(__GNUC__) || defined(__clang__) -#pragma GCC diagnostic pop -#endif - -#endif // STB_TRUETYPE_IMPLEMENTATION - - -// FULL VERSION HISTORY -// -// 1.25 (2021-07-11) many fixes -// 1.24 (2020-02-05) fix warning -// 1.23 (2020-02-02) query SVG data for glyphs; query whole kerning table (but only kern not GPOS) -// 1.22 (2019-08-11) minimize missing-glyph duplication; fix kerning if both 'GPOS' and 'kern' are defined -// 1.21 (2019-02-25) fix warning -// 1.20 (2019-02-07) PackFontRange skips missing codepoints; GetScaleFontVMetrics() -// 1.19 (2018-02-11) OpenType GPOS kerning (horizontal only), STBTT_fmod -// 1.18 (2018-01-29) add missing function -// 1.17 (2017-07-23) make more arguments const; doc fix -// 1.16 (2017-07-12) SDF support -// 1.15 (2017-03-03) make more arguments const -// 1.14 (2017-01-16) num-fonts-in-TTC function -// 1.13 (2017-01-02) support OpenType fonts, certain Apple fonts -// 1.12 (2016-10-25) suppress warnings about casting away const with -Wcast-qual -// 1.11 (2016-04-02) fix unused-variable warning -// 1.10 (2016-04-02) allow user-defined fabs() replacement -// fix memory leak if fontsize=0.0 -// fix warning from duplicate typedef -// 1.09 (2016-01-16) warning fix; avoid crash on outofmem; use alloc userdata for PackFontRanges -// 1.08 (2015-09-13) document stbtt_Rasterize(); fixes for vertical & horizontal edges -// 1.07 (2015-08-01) allow PackFontRanges to accept arrays of sparse codepoints; -// allow PackFontRanges to pack and render in separate phases; -// fix stbtt_GetFontOFfsetForIndex (never worked for non-0 input?); -// fixed an assert() bug in the new rasterizer -// replace assert() with STBTT_assert() in new rasterizer -// 1.06 (2015-07-14) performance improvements (~35% faster on x86 and x64 on test machine) -// also more precise AA rasterizer, except if shapes overlap -// remove need for STBTT_sort -// 1.05 (2015-04-15) fix misplaced definitions for STBTT_STATIC -// 1.04 (2015-04-15) typo in example -// 1.03 (2015-04-12) STBTT_STATIC, fix memory leak in new packing, various fixes -// 1.02 (2014-12-10) fix various warnings & compile issues w/ stb_rect_pack, C++ -// 1.01 (2014-12-08) fix subpixel position when oversampling to exactly match -// non-oversampled; STBTT_POINT_SIZE for packed case only -// 1.00 (2014-12-06) add new PackBegin etc. API, w/ support for oversampling -// 0.99 (2014-09-18) fix multiple bugs with subpixel rendering (ryg) -// 0.9 (2014-08-07) support certain mac/iOS fonts without an MS platformID -// 0.8b (2014-07-07) fix a warning -// 0.8 (2014-05-25) fix a few more warnings -// 0.7 (2013-09-25) bugfix: subpixel glyph bug fixed in 0.5 had come back -// 0.6c (2012-07-24) improve documentation -// 0.6b (2012-07-20) fix a few more warnings -// 0.6 (2012-07-17) fix warnings; added stbtt_ScaleForMappingEmToPixels, -// stbtt_GetFontBoundingBox, stbtt_IsGlyphEmpty -// 0.5 (2011-12-09) bugfixes: -// subpixel glyph renderer computed wrong bounding box -// first vertex of shape can be off-curve (FreeSans) -// 0.4b (2011-12-03) fixed an error in the font baking example -// 0.4 (2011-12-01) kerning, subpixel rendering (tor) -// bugfixes for: -// codepoint-to-glyph conversion using table fmt=12 -// codepoint-to-glyph conversion using table fmt=4 -// stbtt_GetBakedQuad with non-square texture (Zer) -// updated Hello World! sample to use kerning and subpixel -// fixed some warnings -// 0.3 (2009-06-24) cmap fmt=12, compound shapes (MM) -// userdata, malloc-from-userdata, non-zero fill (stb) -// 0.2 (2009-03-11) Fix unsigned/signed char warnings -// 0.1 (2009-03-09) First public release -// - -/* ------------------------------------------------------------------------------- -This software is available under 2 licenses -- choose whichever you prefer. ------------------------------------------------------------------------------- -ALTERNATIVE A - MIT License -Copyright (c) 2017 Sean Barrett -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. ------------------------------------------------------------------------------- -ALTERNATIVE B - Public Domain (www.unlicense.org) -This is free and unencumbered software released into the public domain. -Anyone is free to copy, modify, publish, use, compile, sell, or distribute this -software, either in source code form or as a compiled binary, for any purpose, -commercial or non-commercial, and by any means. -In jurisdictions that recognize copyright laws, the author or authors of this -software dedicate any and all copyright interest in the software to the public -domain. We make this dedication for the benefit of the public at large and to -the detriment of our heirs and successors. We intend this dedication to be an -overt act of relinquishment in perpetuity of all present and future rights to -this software under copyright law. -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 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. ------------------------------------------------------------------------------- -*/ diff --git a/app/jni/src/libultraship/extern/ImGui/misc/README.txt b/app/jni/src/libultraship/extern/ImGui/misc/README.txt deleted file mode 100644 index b4ce89f..0000000 --- a/app/jni/src/libultraship/extern/ImGui/misc/README.txt +++ /dev/null @@ -1,23 +0,0 @@ - -misc/cpp/ - InputText() wrappers for C++ standard library (STL) type: std::string. - This is also an example of how you may wrap your own similar types. - -misc/debuggers/ - Helper files for popular debuggers. - With the .natvis file, types like ImVector<> will be displayed nicely in Visual Studio debugger. - -misc/fonts/ - Fonts loading/merging instructions (e.g. How to handle glyph ranges, how to merge icons fonts). - Command line tool "binary_to_compressed_c" to create compressed arrays to embed data in source code. - Suggested fonts and links. - -misc/freetype/ - Font atlas builder/rasterizer using FreeType instead of stb_truetype. - Benefit from better FreeType rasterization, in particular for small fonts. - -misc/single_file/ - Single-file header stub. - We use this to validate compiling all *.cpp files in a same compilation unit. - Users of that technique (also called "Unity builds") can generally provide this themselves, - so we don't really recommend you use this in your projects. diff --git a/app/jni/src/libultraship/extern/ImGui/misc/cpp/README.txt b/app/jni/src/libultraship/extern/ImGui/misc/cpp/README.txt deleted file mode 100644 index 17f0a3c..0000000 --- a/app/jni/src/libultraship/extern/ImGui/misc/cpp/README.txt +++ /dev/null @@ -1,13 +0,0 @@ - -imgui_stdlib.h + imgui_stdlib.cpp - InputText() wrappers for C++ standard library (STL) type: std::string. - This is also an example of how you may wrap your own similar types. - -imgui_scoped.h - [Experimental, not currently in main repository] - Additional header file with some RAII-style wrappers for common Dear ImGui functions. - Try by merging: https://github.com/ocornut/imgui/pull/2197 - Discuss at: https://github.com/ocornut/imgui/issues/2096 - -See more C++ related extension (fmt, RAII, syntaxis sugar) on Wiki: - https://github.com/ocornut/imgui/wiki/Useful-Extensions#cness diff --git a/app/jni/src/libultraship/extern/ImGui/misc/cpp/imgui_stdlib.cpp b/app/jni/src/libultraship/extern/ImGui/misc/cpp/imgui_stdlib.cpp deleted file mode 100644 index cf69aa8..0000000 --- a/app/jni/src/libultraship/extern/ImGui/misc/cpp/imgui_stdlib.cpp +++ /dev/null @@ -1,85 +0,0 @@ -// dear imgui: wrappers for C++ standard library (STL) types (std::string, etc.) -// This is also an example of how you may wrap your own similar types. - -// Changelog: -// - v0.10: Initial version. Added InputText() / InputTextMultiline() calls with std::string - -// See more C++ related extension (fmt, RAII, syntaxis sugar) on Wiki: -// https://github.com/ocornut/imgui/wiki/Useful-Extensions#cness - -#include "imgui.h" -#include "imgui_stdlib.h" - -// Clang warnings with -Weverything -#if defined(__clang__) -#pragma clang diagnostic push -#pragma clang diagnostic ignored "-Wsign-conversion" // warning: implicit conversion changes signedness -#endif - -struct InputTextCallback_UserData -{ - std::string* Str; - ImGuiInputTextCallback ChainCallback; - void* ChainCallbackUserData; -}; - -static int InputTextCallback(ImGuiInputTextCallbackData* data) -{ - InputTextCallback_UserData* user_data = (InputTextCallback_UserData*)data->UserData; - if (data->EventFlag == ImGuiInputTextFlags_CallbackResize) - { - // Resize string callback - // If for some reason we refuse the new length (BufTextLen) and/or capacity (BufSize) we need to set them back to what we want. - std::string* str = user_data->Str; - IM_ASSERT(data->Buf == str->c_str()); - str->resize(data->BufTextLen); - data->Buf = (char*)str->c_str(); - } - else if (user_data->ChainCallback) - { - // Forward to user callback, if any - data->UserData = user_data->ChainCallbackUserData; - return user_data->ChainCallback(data); - } - return 0; -} - -bool ImGui::InputText(const char* label, std::string* str, ImGuiInputTextFlags flags, ImGuiInputTextCallback callback, void* user_data) -{ - IM_ASSERT((flags & ImGuiInputTextFlags_CallbackResize) == 0); - flags |= ImGuiInputTextFlags_CallbackResize; - - InputTextCallback_UserData cb_user_data; - cb_user_data.Str = str; - cb_user_data.ChainCallback = callback; - cb_user_data.ChainCallbackUserData = user_data; - return InputText(label, (char*)str->c_str(), str->capacity() + 1, flags, InputTextCallback, &cb_user_data); -} - -bool ImGui::InputTextMultiline(const char* label, std::string* str, const ImVec2& size, ImGuiInputTextFlags flags, ImGuiInputTextCallback callback, void* user_data) -{ - IM_ASSERT((flags & ImGuiInputTextFlags_CallbackResize) == 0); - flags |= ImGuiInputTextFlags_CallbackResize; - - InputTextCallback_UserData cb_user_data; - cb_user_data.Str = str; - cb_user_data.ChainCallback = callback; - cb_user_data.ChainCallbackUserData = user_data; - return InputTextMultiline(label, (char*)str->c_str(), str->capacity() + 1, size, flags, InputTextCallback, &cb_user_data); -} - -bool ImGui::InputTextWithHint(const char* label, const char* hint, std::string* str, ImGuiInputTextFlags flags, ImGuiInputTextCallback callback, void* user_data) -{ - IM_ASSERT((flags & ImGuiInputTextFlags_CallbackResize) == 0); - flags |= ImGuiInputTextFlags_CallbackResize; - - InputTextCallback_UserData cb_user_data; - cb_user_data.Str = str; - cb_user_data.ChainCallback = callback; - cb_user_data.ChainCallbackUserData = user_data; - return InputTextWithHint(label, hint, (char*)str->c_str(), str->capacity() + 1, flags, InputTextCallback, &cb_user_data); -} - -#if defined(__clang__) -#pragma clang diagnostic pop -#endif diff --git a/app/jni/src/libultraship/extern/ImGui/misc/cpp/imgui_stdlib.h b/app/jni/src/libultraship/extern/ImGui/misc/cpp/imgui_stdlib.h deleted file mode 100644 index 835a808..0000000 --- a/app/jni/src/libultraship/extern/ImGui/misc/cpp/imgui_stdlib.h +++ /dev/null @@ -1,21 +0,0 @@ -// dear imgui: wrappers for C++ standard library (STL) types (std::string, etc.) -// This is also an example of how you may wrap your own similar types. - -// Changelog: -// - v0.10: Initial version. Added InputText() / InputTextMultiline() calls with std::string - -// See more C++ related extension (fmt, RAII, syntaxis sugar) on Wiki: -// https://github.com/ocornut/imgui/wiki/Useful-Extensions#cness - -#pragma once - -#include - -namespace ImGui -{ - // ImGui::InputText() with std::string - // Because text input needs dynamic resizing, we need to setup a callback to grow the capacity - IMGUI_API bool InputText(const char* label, std::string* str, ImGuiInputTextFlags flags = 0, ImGuiInputTextCallback callback = nullptr, void* user_data = nullptr); - IMGUI_API bool InputTextMultiline(const char* label, std::string* str, const ImVec2& size = ImVec2(0, 0), ImGuiInputTextFlags flags = 0, ImGuiInputTextCallback callback = nullptr, void* user_data = nullptr); - IMGUI_API bool InputTextWithHint(const char* label, const char* hint, std::string* str, ImGuiInputTextFlags flags = 0, ImGuiInputTextCallback callback = nullptr, void* user_data = nullptr); -} diff --git a/app/jni/src/libultraship/extern/ImGui/misc/debuggers/README.txt b/app/jni/src/libultraship/extern/ImGui/misc/debuggers/README.txt deleted file mode 100644 index 3f4ba83..0000000 --- a/app/jni/src/libultraship/extern/ImGui/misc/debuggers/README.txt +++ /dev/null @@ -1,16 +0,0 @@ - -HELPER FILES FOR POPULAR DEBUGGERS - -imgui.gdb - GDB: disable stepping into trivial functions. - (read comments inside file for details) - -imgui.natstepfilter - Visual Studio Debugger: disable stepping into trivial functions. - (read comments inside file for details) - -imgui.natvis - Visual Studio Debugger: describe Dear ImGui types for better display. - With this, types like ImVector<> will be displayed nicely in the debugger. - (read comments inside file for details) - diff --git a/app/jni/src/libultraship/extern/ImGui/misc/debuggers/imgui.gdb b/app/jni/src/libultraship/extern/ImGui/misc/debuggers/imgui.gdb deleted file mode 100644 index 000ff6e..0000000 --- a/app/jni/src/libultraship/extern/ImGui/misc/debuggers/imgui.gdb +++ /dev/null @@ -1,12 +0,0 @@ -# GDB configuration to aid debugging experience - -# To enable these customizations edit $HOME/.gdbinit (or ./.gdbinit if local gdbinit is enabled) and add: -# add-auto-load-safe-path /path/to/imgui.gdb -# source /path/to/imgui.gdb -# -# More Information at: -# * https://sourceware.org/gdb/current/onlinedocs/gdb/gdbinit-man.html -# * https://sourceware.org/gdb/current/onlinedocs/gdb/Init-File-in-the-Current-Directory.html#Init-File-in-the-Current-Directory - -# Disable stepping into trivial functions -skip -rfunction Im(Vec2|Vec4|Strv|Vector|Span)::.+ diff --git a/app/jni/src/libultraship/extern/ImGui/misc/debuggers/imgui.natstepfilter b/app/jni/src/libultraship/extern/ImGui/misc/debuggers/imgui.natstepfilter deleted file mode 100644 index 6825c93..0000000 --- a/app/jni/src/libultraship/extern/ImGui/misc/debuggers/imgui.natstepfilter +++ /dev/null @@ -1,31 +0,0 @@ - - - - - - - - (ImVec2|ImVec4|ImStrv)::.+ - NoStepInto - - - (ImVector|ImSpan).*::operator.+ - NoStepInto - - - diff --git a/app/jni/src/libultraship/extern/ImGui/misc/debuggers/imgui.natvis b/app/jni/src/libultraship/extern/ImGui/misc/debuggers/imgui.natvis deleted file mode 100644 index 94d17a8..0000000 --- a/app/jni/src/libultraship/extern/ImGui/misc/debuggers/imgui.natvis +++ /dev/null @@ -1,62 +0,0 @@ - - - - - - - {{Size={Size} Capacity={Capacity}}} - - - Size - Data - - - - - - {{Size={DataEnd-Data} }} - - - DataEnd-Data - Data - - - - - - {{x={x,g} y={y,g}}} - - - - {{x={x,g} y={y,g} z={z,g} w={w,g}}} - - - - {{Min=({Min.x,g} {Min.y,g}) Max=({Max.x,g} {Max.y,g}) Size=({Max.x-Min.x,g} {Max.y-Min.y,g})}} - - Min - Max - Max.x - Min.x - Max.y - Min.y - - - - - {{Name {Name,s} Active {(Active||WasActive)?1:0,d} Child {(Flags & 0x01000000)?1:0,d} Popup {(Flags & 0x04000000)?1:0,d} Hidden {(Hidden)?1:0,d}} - - - - {{ID {ID,x} Pos=({Pos.x,g} {Pos.y,g}) Size=({Size.x,g} {Size.y,g}) Parent {(ParentNode==0)?0:ParentNode->ID,x} Childs {(ChildNodes[0] != 0)+(ChildNodes[1] != 0)} Windows {Windows.Size} } - - - diff --git a/app/jni/src/libultraship/extern/ImGui/misc/fonts/Cousine-Regular.ttf b/app/jni/src/libultraship/extern/ImGui/misc/fonts/Cousine-Regular.ttf deleted file mode 100644 index 70a0bf9..0000000 Binary files a/app/jni/src/libultraship/extern/ImGui/misc/fonts/Cousine-Regular.ttf and /dev/null differ diff --git a/app/jni/src/libultraship/extern/ImGui/misc/fonts/DroidSans.ttf b/app/jni/src/libultraship/extern/ImGui/misc/fonts/DroidSans.ttf deleted file mode 100644 index 767c63a..0000000 Binary files a/app/jni/src/libultraship/extern/ImGui/misc/fonts/DroidSans.ttf and /dev/null differ diff --git a/app/jni/src/libultraship/extern/ImGui/misc/fonts/Karla-Regular.ttf b/app/jni/src/libultraship/extern/ImGui/misc/fonts/Karla-Regular.ttf deleted file mode 100644 index 81b3de6..0000000 Binary files a/app/jni/src/libultraship/extern/ImGui/misc/fonts/Karla-Regular.ttf and /dev/null differ diff --git a/app/jni/src/libultraship/extern/ImGui/misc/fonts/ProggyClean.ttf b/app/jni/src/libultraship/extern/ImGui/misc/fonts/ProggyClean.ttf deleted file mode 100644 index 0270cdf..0000000 Binary files a/app/jni/src/libultraship/extern/ImGui/misc/fonts/ProggyClean.ttf and /dev/null differ diff --git a/app/jni/src/libultraship/extern/ImGui/misc/fonts/ProggyTiny.ttf b/app/jni/src/libultraship/extern/ImGui/misc/fonts/ProggyTiny.ttf deleted file mode 100644 index 1c4312c..0000000 Binary files a/app/jni/src/libultraship/extern/ImGui/misc/fonts/ProggyTiny.ttf and /dev/null differ diff --git a/app/jni/src/libultraship/extern/ImGui/misc/fonts/Roboto-Medium.ttf b/app/jni/src/libultraship/extern/ImGui/misc/fonts/Roboto-Medium.ttf deleted file mode 100644 index 39c63d7..0000000 Binary files a/app/jni/src/libultraship/extern/ImGui/misc/fonts/Roboto-Medium.ttf and /dev/null differ diff --git a/app/jni/src/libultraship/extern/ImGui/misc/fonts/binary_to_compressed_c.cpp b/app/jni/src/libultraship/extern/ImGui/misc/fonts/binary_to_compressed_c.cpp deleted file mode 100644 index f41d20f..0000000 --- a/app/jni/src/libultraship/extern/ImGui/misc/fonts/binary_to_compressed_c.cpp +++ /dev/null @@ -1,388 +0,0 @@ -// dear imgui -// (binary_to_compressed_c.cpp) -// Helper tool to turn a file into a C array, if you want to embed font data in your source code. - -// The data is first compressed with stb_compress() to reduce source code size, -// then encoded in Base85 to fit in a string so we can fit roughly 4 bytes of compressed data into 5 bytes of source code (suggested by @mmalex) -// (If we used 32-bit constants it would require take 11 bytes of source code to encode 4 bytes, and be endianness dependent) -// Note that even with compression, the output array is likely to be bigger than the binary file.. -// Load compressed TTF fonts with ImGui::GetIO().Fonts->AddFontFromMemoryCompressedTTF() - -// Build with, e.g: -// # cl.exe binary_to_compressed_c.cpp -// # g++ binary_to_compressed_c.cpp -// # clang++ binary_to_compressed_c.cpp -// You can also find a precompiled Windows binary in the binary/demo package available from https://github.com/ocornut/imgui - -// Usage: -// binary_to_compressed_c.exe [-base85] [-nocompress] [-nostatic] -// Usage example: -// # binary_to_compressed_c.exe myfont.ttf MyFont > myfont.cpp -// # binary_to_compressed_c.exe -base85 myfont.ttf MyFont > myfont.cpp - -#define _CRT_SECURE_NO_WARNINGS -#include -#include -#include -#include - -// stb_compress* from stb.h - declaration -typedef unsigned int stb_uint; -typedef unsigned char stb_uchar; -stb_uint stb_compress(stb_uchar* out, stb_uchar* in, stb_uint len); - -static bool binary_to_compressed_c(const char* filename, const char* symbol, bool use_base85_encoding, bool use_compression, bool use_static); - -int main(int argc, char** argv) -{ - if (argc < 3) - { - printf("Syntax: %s [-base85] [-nocompress] [-nostatic] \n", argv[0]); - return 0; - } - - int argn = 1; - bool use_base85_encoding = false; - bool use_compression = true; - bool use_static = true; - while (argn < (argc - 2) && argv[argn][0] == '-') - { - if (strcmp(argv[argn], "-base85") == 0) { use_base85_encoding = true; argn++; } - else if (strcmp(argv[argn], "-nocompress") == 0) { use_compression = false; argn++; } - else if (strcmp(argv[argn], "-nostatic") == 0) { use_static = false; argn++; } - else - { - fprintf(stderr, "Unknown argument: '%s'\n", argv[argn]); - return 1; - } - } - - bool ret = binary_to_compressed_c(argv[argn], argv[argn + 1], use_base85_encoding, use_compression, use_static); - if (!ret) - fprintf(stderr, "Error opening or reading file: '%s'\n", argv[argn]); - return ret ? 0 : 1; -} - -char Encode85Byte(unsigned int x) -{ - x = (x % 85) + 35; - return (char)((x >= '\\') ? x + 1 : x); -} - -bool binary_to_compressed_c(const char* filename, const char* symbol, bool use_base85_encoding, bool use_compression, bool use_static) -{ - // Read file - FILE* f = fopen(filename, "rb"); - if (!f) return false; - int data_sz; - if (fseek(f, 0, SEEK_END) || (data_sz = (int)ftell(f)) == -1 || fseek(f, 0, SEEK_SET)) { fclose(f); return false; } - char* data = new char[data_sz + 4]; - if (fread(data, 1, data_sz, f) != (size_t)data_sz) { fclose(f); delete[] data; return false; } - memset((void*)(((char*)data) + data_sz), 0, 4); - fclose(f); - - // Compress - int maxlen = data_sz + 512 + (data_sz >> 2) + sizeof(int); // total guess - char* compressed = use_compression ? new char[maxlen] : data; - int compressed_sz = use_compression ? stb_compress((stb_uchar*)compressed, (stb_uchar*)data, data_sz) : data_sz; - if (use_compression) - memset(compressed + compressed_sz, 0, maxlen - compressed_sz); - - // Output as Base85 encoded - FILE* out = stdout; - fprintf(out, "// File: '%s' (%d bytes)\n", filename, (int)data_sz); - fprintf(out, "// Exported using binary_to_compressed_c.cpp\n"); - const char* static_str = use_static ? "static " : ""; - const char* compressed_str = use_compression ? "compressed_" : ""; - if (use_base85_encoding) - { - fprintf(out, "%sconst char %s_%sdata_base85[%d+1] =\n \"", static_str, symbol, compressed_str, (int)((compressed_sz + 3) / 4)*5); - char prev_c = 0; - for (int src_i = 0; src_i < compressed_sz; src_i += 4) - { - // This is made a little more complicated by the fact that ??X sequences are interpreted as trigraphs by old C/C++ compilers. So we need to escape pairs of ??. - unsigned int d = *(unsigned int*)(compressed + src_i); - for (unsigned int n5 = 0; n5 < 5; n5++, d /= 85) - { - char c = Encode85Byte(d); - fprintf(out, (c == '?' && prev_c == '?') ? "\\%c" : "%c", c); - prev_c = c; - } - if ((src_i % 112) == 112 - 4) - fprintf(out, "\"\n \""); - } - fprintf(out, "\";\n\n"); - } - else - { - fprintf(out, "%sconst unsigned int %s_%ssize = %d;\n", static_str, symbol, compressed_str, (int)compressed_sz); - fprintf(out, "%sconst unsigned int %s_%sdata[%d/4] =\n{", static_str, symbol, compressed_str, (int)((compressed_sz + 3) / 4)*4); - int column = 0; - for (int i = 0; i < compressed_sz; i += 4) - { - unsigned int d = *(unsigned int*)(compressed + i); - if ((column++ % 12) == 0) - fprintf(out, "\n 0x%08x, ", d); - else - fprintf(out, "0x%08x, ", d); - } - fprintf(out, "\n};\n\n"); - } - - // Cleanup - delete[] data; - if (use_compression) - delete[] compressed; - return true; -} - -// stb_compress* from stb.h - definition - -//////////////////// compressor /////////////////////// - -static stb_uint stb_adler32(stb_uint adler32, stb_uchar *buffer, stb_uint buflen) -{ - const unsigned long ADLER_MOD = 65521; - unsigned long s1 = adler32 & 0xffff, s2 = adler32 >> 16; - unsigned long blocklen, i; - - blocklen = buflen % 5552; - while (buflen) { - for (i=0; i + 7 < blocklen; i += 8) { - s1 += buffer[0], s2 += s1; - s1 += buffer[1], s2 += s1; - s1 += buffer[2], s2 += s1; - s1 += buffer[3], s2 += s1; - s1 += buffer[4], s2 += s1; - s1 += buffer[5], s2 += s1; - s1 += buffer[6], s2 += s1; - s1 += buffer[7], s2 += s1; - - buffer += 8; - } - - for (; i < blocklen; ++i) - s1 += *buffer++, s2 += s1; - - s1 %= ADLER_MOD, s2 %= ADLER_MOD; - buflen -= blocklen; - blocklen = 5552; - } - return (s2 << 16) + s1; -} - -static unsigned int stb_matchlen(stb_uchar *m1, stb_uchar *m2, stb_uint maxlen) -{ - stb_uint i; - for (i=0; i < maxlen; ++i) - if (m1[i] != m2[i]) return i; - return i; -} - -// simple implementation that just takes the source data in a big block - -static stb_uchar *stb__out; -static FILE *stb__outfile; -static stb_uint stb__outbytes; - -static void stb__write(unsigned char v) -{ - fputc(v, stb__outfile); - ++stb__outbytes; -} - -//#define stb_out(v) (stb__out ? *stb__out++ = (stb_uchar) (v) : stb__write((stb_uchar) (v))) -#define stb_out(v) do { if (stb__out) *stb__out++ = (stb_uchar) (v); else stb__write((stb_uchar) (v)); } while (0) - -static void stb_out2(stb_uint v) { stb_out(v >> 8); stb_out(v); } -static void stb_out3(stb_uint v) { stb_out(v >> 16); stb_out(v >> 8); stb_out(v); } -static void stb_out4(stb_uint v) { stb_out(v >> 24); stb_out(v >> 16); stb_out(v >> 8 ); stb_out(v); } - -static void outliterals(stb_uchar *in, int numlit) -{ - while (numlit > 65536) { - outliterals(in,65536); - in += 65536; - numlit -= 65536; - } - - if (numlit == 0) ; - else if (numlit <= 32) stb_out (0x000020 + numlit-1); - else if (numlit <= 2048) stb_out2(0x000800 + numlit-1); - else /* numlit <= 65536) */ stb_out3(0x070000 + numlit-1); - - if (stb__out) { - memcpy(stb__out,in,numlit); - stb__out += numlit; - } else - fwrite(in, 1, numlit, stb__outfile); -} - -static int stb__window = 0x40000; // 256K - -static int stb_not_crap(int best, int dist) -{ - return ((best > 2 && dist <= 0x00100) - || (best > 5 && dist <= 0x04000) - || (best > 7 && dist <= 0x80000)); -} - -static stb_uint stb__hashsize = 32768; - -// note that you can play with the hashing functions all you -// want without needing to change the decompressor -#define stb__hc(q,h,c) (((h) << 7) + ((h) >> 25) + q[c]) -#define stb__hc2(q,h,c,d) (((h) << 14) + ((h) >> 18) + (q[c] << 7) + q[d]) -#define stb__hc3(q,c,d,e) ((q[c] << 14) + (q[d] << 7) + q[e]) - -static unsigned int stb__running_adler; - -static int stb_compress_chunk(stb_uchar *history, - stb_uchar *start, - stb_uchar *end, - int length, - int *pending_literals, - stb_uchar **chash, - stb_uint mask) -{ - (void)history; - int window = stb__window; - stb_uint match_max; - stb_uchar *lit_start = start - *pending_literals; - stb_uchar *q = start; - -#define STB__SCRAMBLE(h) (((h) + ((h) >> 16)) & mask) - - // stop short of the end so we don't scan off the end doing - // the hashing; this means we won't compress the last few bytes - // unless they were part of something longer - while (q < start+length && q+12 < end) { - int m; - stb_uint h1,h2,h3,h4, h; - stb_uchar *t; - int best = 2, dist=0; - - if (q+65536 > end) - match_max = (stb_uint)(end-q); - else - match_max = 65536; - -#define stb__nc(b,d) ((d) <= window && ((b) > 9 || stb_not_crap((int)(b),(int)(d)))) - -#define STB__TRY(t,p) /* avoid retrying a match we already tried */ \ - if (p ? dist != (int)(q-t) : 1) \ - if ((m = stb_matchlen(t, q, match_max)) > best) \ - if (stb__nc(m,q-(t))) \ - best = m, dist = (int)(q - (t)) - - // rather than search for all matches, only try 4 candidate locations, - // chosen based on 4 different hash functions of different lengths. - // this strategy is inspired by LZO; hashing is unrolled here using the - // 'hc' macro - h = stb__hc3(q,0, 1, 2); h1 = STB__SCRAMBLE(h); - t = chash[h1]; if (t) STB__TRY(t,0); - h = stb__hc2(q,h, 3, 4); h2 = STB__SCRAMBLE(h); - h = stb__hc2(q,h, 5, 6); t = chash[h2]; if (t) STB__TRY(t,1); - h = stb__hc2(q,h, 7, 8); h3 = STB__SCRAMBLE(h); - h = stb__hc2(q,h, 9,10); t = chash[h3]; if (t) STB__TRY(t,1); - h = stb__hc2(q,h,11,12); h4 = STB__SCRAMBLE(h); - t = chash[h4]; if (t) STB__TRY(t,1); - - // because we use a shared hash table, can only update it - // _after_ we've probed all of them - chash[h1] = chash[h2] = chash[h3] = chash[h4] = q; - - if (best > 2) - assert(dist > 0); - - // see if our best match qualifies - if (best < 3) { // fast path literals - ++q; - } else if (best > 2 && best <= 0x80 && dist <= 0x100) { - outliterals(lit_start, (int)(q-lit_start)); lit_start = (q += best); - stb_out(0x80 + best-1); - stb_out(dist-1); - } else if (best > 5 && best <= 0x100 && dist <= 0x4000) { - outliterals(lit_start, (int)(q-lit_start)); lit_start = (q += best); - stb_out2(0x4000 + dist-1); - stb_out(best-1); - } else if (best > 7 && best <= 0x100 && dist <= 0x80000) { - outliterals(lit_start, (int)(q-lit_start)); lit_start = (q += best); - stb_out3(0x180000 + dist-1); - stb_out(best-1); - } else if (best > 8 && best <= 0x10000 && dist <= 0x80000) { - outliterals(lit_start, (int)(q-lit_start)); lit_start = (q += best); - stb_out3(0x100000 + dist-1); - stb_out2(best-1); - } else if (best > 9 && dist <= 0x1000000) { - if (best > 65536) best = 65536; - outliterals(lit_start, (int)(q-lit_start)); lit_start = (q += best); - if (best <= 0x100) { - stb_out(0x06); - stb_out3(dist-1); - stb_out(best-1); - } else { - stb_out(0x04); - stb_out3(dist-1); - stb_out2(best-1); - } - } else { // fallback literals if no match was a balanced tradeoff - ++q; - } - } - - // if we didn't get all the way, add the rest to literals - if (q-start < length) - q = start+length; - - // the literals are everything from lit_start to q - *pending_literals = (int)(q - lit_start); - - stb__running_adler = stb_adler32(stb__running_adler, start, (stb_uint)(q - start)); - return (int)(q - start); -} - -static int stb_compress_inner(stb_uchar *input, stb_uint length) -{ - int literals = 0; - stb_uint len,i; - - stb_uchar **chash; - chash = (stb_uchar**) malloc(stb__hashsize * sizeof(stb_uchar*)); - if (chash == nullptr) return 0; // failure - for (i=0; i < stb__hashsize; ++i) - chash[i] = nullptr; - - // stream signature - stb_out(0x57); stb_out(0xbc); - stb_out2(0); - - stb_out4(0); // 64-bit length requires 32-bit leading 0 - stb_out4(length); - stb_out4(stb__window); - - stb__running_adler = 1; - - len = stb_compress_chunk(input, input, input+length, length, &literals, chash, stb__hashsize-1); - assert(len == length); - - outliterals(input+length - literals, literals); - - free(chash); - - stb_out2(0x05fa); // end opcode - - stb_out4(stb__running_adler); - - return 1; // success -} - -stb_uint stb_compress(stb_uchar *out, stb_uchar *input, stb_uint length) -{ - stb__out = out; - stb__outfile = nullptr; - - stb_compress_inner(input, length); - - return (stb_uint)(stb__out - out); -} diff --git a/app/jni/src/libultraship/extern/ImGui/misc/freetype/README.md b/app/jni/src/libultraship/extern/ImGui/misc/freetype/README.md deleted file mode 100644 index 275a538..0000000 --- a/app/jni/src/libultraship/extern/ImGui/misc/freetype/README.md +++ /dev/null @@ -1,44 +0,0 @@ -# imgui_freetype - -Build font atlases using FreeType instead of stb_truetype (which is the default font rasterizer). -
by @vuhdo, @mikesart, @ocornut. - -### Usage - -1. Get latest FreeType binaries or build yourself (under Windows you may use vcpkg with `vcpkg install freetype --triplet=x64-windows`, `vcpkg integrate install`). -2. Add imgui_freetype.h/cpp alongside your project files. -3. Add `#define IMGUI_ENABLE_FREETYPE` in your [imconfig.h](https://github.com/ocornut/imgui/blob/master/imconfig.h) file - -### About Gamma Correct Blending - -FreeType assumes blending in linear space rather than gamma space. -See FreeType note for [FT_Render_Glyph](https://freetype.org/freetype2/docs/reference/ft2-glyph_retrieval.html#ft_render_glyph). -For correct results you need to be using sRGB and convert to linear space in the pixel shader output. -The default Dear ImGui styles will be impacted by this change (alpha values will need tweaking). - -### Testbed for toying with settings (for developers) - -See https://gist.github.com/ocornut/b3a9ecf13502fd818799a452969649ad - -### Known issues - -- Oversampling settings are ignored but also not so much necessary with the higher quality rendering. - -### Comparison - -Small, thin anti-aliased fonts typically benefit a lot from FreeType's hinting: -![comparing_font_rasterizers](https://user-images.githubusercontent.com/8225057/107550178-fef87f00-6bd0-11eb-8d09-e2edb2f0ccfc.gif) - -### Colorful glyphs/emojis - -You can use the `ImGuiFreeTypeBuilderFlags_LoadColor` flag to load certain colorful glyphs. See the -["Using Colorful Glyphs/Emojis"](https://github.com/ocornut/imgui/blob/master/docs/FONTS.md#using-colorful-glyphsemojis) section of FONTS.md. - -![colored glyphs](https://user-images.githubusercontent.com/8225057/106171241-9dc4ba80-6191-11eb-8a69-ca1467b206d1.png) - -### Using OpenType SVG fonts (SVGinOT) -- *SVG in Open Type* is a standard by Adobe and Mozilla for color OpenType and Open Font Format fonts. It allows font creators to embed complete SVG files within a font enabling full color and even animations. -- Popular fonts such as [twemoji](https://github.com/13rac1/twemoji-color-font) and fonts made with [scfbuild](https://github.com/13rac1/scfbuild) is SVGinOT -- Requires: [lunasvg](https://github.com/sammycage/lunasvg) v2.3.2 and above - 1. Add `#define IMGUI_ENABLE_FREETYPE_LUNASVG` in your `imconfig.h`. - 2. Get latest lunasvg binaries or build yourself. Under Windows you may use vcpkg with: `vcpkg install lunasvg --triplet=x64-windows`. diff --git a/app/jni/src/libultraship/extern/ImGui/misc/freetype/imgui_freetype.cpp b/app/jni/src/libultraship/extern/ImGui/misc/freetype/imgui_freetype.cpp deleted file mode 100644 index 2e855de..0000000 --- a/app/jni/src/libultraship/extern/ImGui/misc/freetype/imgui_freetype.cpp +++ /dev/null @@ -1,944 +0,0 @@ -// dear imgui: FreeType font builder (used as a replacement for the stb_truetype builder) -// (code) - -// Get the latest version at https://github.com/ocornut/imgui/tree/master/misc/freetype -// Original code by @vuhdo (Aleksei Skriabin). Improvements by @mikesart. Maintained since 2019 by @ocornut. - -// CHANGELOG -// (minor and older changes stripped away, please see git history for details) -// 2023/08/01: added support for SVG fonts, enable by using '#define IMGUI_ENABLE_FREETYPE_LUNASVG' (#6591) -// 2023/01/04: fixed a packing issue which in some occurrences would prevent large amount of glyphs from being packed correctly. -// 2021/08/23: fixed crash when FT_Render_Glyph() fails to render a glyph and returns NULL. -// 2021/03/05: added ImGuiFreeTypeBuilderFlags_Bitmap to load bitmap glyphs. -// 2021/03/02: set 'atlas->TexPixelsUseColors = true' to help some backends with deciding of a prefered texture format. -// 2021/01/28: added support for color-layered glyphs via ImGuiFreeTypeBuilderFlags_LoadColor (require Freetype 2.10+). -// 2021/01/26: simplified integration by using '#define IMGUI_ENABLE_FREETYPE'. renamed ImGuiFreeType::XXX flags to ImGuiFreeTypeBuilderFlags_XXX for consistency with other API. removed ImGuiFreeType::BuildFontAtlas(). -// 2020/06/04: fix for rare case where FT_Get_Char_Index() succeed but FT_Load_Glyph() fails. -// 2019/02/09: added RasterizerFlags::Monochrome flag to disable font anti-aliasing (combine with ::MonoHinting for best results!) -// 2019/01/15: added support for imgui allocators + added FreeType only override function SetAllocatorFunctions(). -// 2019/01/10: re-factored to match big update in STB builder. fixed texture height waste. fixed redundant glyphs when merging. support for glyph padding. -// 2018/06/08: added support for ImFontConfig::GlyphMinAdvanceX, GlyphMaxAdvanceX. -// 2018/02/04: moved to main imgui repository (away from http://www.github.com/ocornut/imgui_club) -// 2018/01/22: fix for addition of ImFontAtlas::TexUvscale member. -// 2017/10/22: minor inconsequential change to match change in master (removed an unnecessary statement). -// 2017/09/26: fixes for imgui internal changes. -// 2017/08/26: cleanup, optimizations, support for ImFontConfig::RasterizerFlags, ImFontConfig::RasterizerMultiply. -// 2017/08/16: imported from https://github.com/Vuhdo/imgui_freetype into http://www.github.com/ocornut/imgui_club, updated for latest changes in ImFontAtlas, minor tweaks. - -// About Gamma Correct Blending: -// - FreeType assumes blending in linear space rather than gamma space. -// - See https://www.freetype.org/freetype2/docs/reference/ft2-base_interface.html#FT_Render_Glyph -// - For correct results you need to be using sRGB and convert to linear space in the pixel shader output. -// - The default dear imgui styles will be impacted by this change (alpha values will need tweaking). - -// FIXME: cfg.OversampleH, OversampleV are not supported (but perhaps not so necessary with this rasterizer). - -#include "imgui.h" -#ifndef IMGUI_DISABLE -#include "imgui_freetype.h" -#include "imgui_internal.h" // ImMin,ImMax,ImFontAtlasBuild*, -#include -#include -#include FT_FREETYPE_H // -#include FT_MODULE_H // -#include FT_GLYPH_H // -#include FT_SYNTHESIS_H // - -#ifdef IMGUI_ENABLE_FREETYPE_LUNASVG -#include FT_OTSVG_H // -#include FT_BBOX_H // -#include -#if !((FREETYPE_MAJOR >= 2) && (FREETYPE_MINOR >= 12)) -#error IMGUI_ENABLE_FREETYPE_LUNASVG requires FreeType version >= 2.12 -#endif -#endif - -#ifdef _MSC_VER -#pragma warning (push) -#pragma warning (disable: 4505) // unreferenced local function has been removed (stb stuff) -#pragma warning (disable: 26812) // [Static Analyzer] The enum type 'xxx' is unscoped. Prefer 'enum class' over 'enum' (Enum.3). -#endif - -#ifdef __GNUC__ -#pragma GCC diagnostic push -#pragma GCC diagnostic ignored "-Wpragmas" // warning: unknown option after '#pragma GCC diagnostic' kind -#pragma GCC diagnostic ignored "-Wunused-function" // warning: 'xxxx' defined but not used -#ifndef __clang__ -#pragma GCC diagnostic ignored "-Wsubobject-linkage" // warning: 'xxxx' has a field 'xxxx' whose type uses the anonymous namespace -#endif -#endif - -//------------------------------------------------------------------------- -// Data -//------------------------------------------------------------------------- - -// Default memory allocators -static void* ImGuiFreeTypeDefaultAllocFunc(size_t size, void* user_data) { IM_UNUSED(user_data); return IM_ALLOC(size); } -static void ImGuiFreeTypeDefaultFreeFunc(void* ptr, void* user_data) { IM_UNUSED(user_data); IM_FREE(ptr); } - -// Current memory allocators -static void* (*GImGuiFreeTypeAllocFunc)(size_t size, void* user_data) = ImGuiFreeTypeDefaultAllocFunc; -static void (*GImGuiFreeTypeFreeFunc)(void* ptr, void* user_data) = ImGuiFreeTypeDefaultFreeFunc; -static void* GImGuiFreeTypeAllocatorUserData = nullptr; - -// Lunasvg support -#ifdef IMGUI_ENABLE_FREETYPE_LUNASVG -static FT_Error ImGuiLunasvgPortInit(FT_Pointer* state); -static void ImGuiLunasvgPortFree(FT_Pointer* state); -static FT_Error ImGuiLunasvgPortRender(FT_GlyphSlot slot, FT_Pointer* _state); -static FT_Error ImGuiLunasvgPortPresetSlot(FT_GlyphSlot slot, FT_Bool cache, FT_Pointer* _state); -#endif - -//------------------------------------------------------------------------- -// Code -//------------------------------------------------------------------------- - -namespace -{ - // Glyph metrics: - // -------------- - // - // xmin xmax - // | | - // |<-------- width -------->| - // | | - // | +-------------------------+----------------- ymax - // | | ggggggggg ggggg | ^ ^ - // | | g:::::::::ggg::::g | | | - // | | g:::::::::::::::::g | | | - // | | g::::::ggggg::::::gg | | | - // | | g:::::g g:::::g | | | - // offsetX -|-------->| g:::::g g:::::g | offsetY | - // | | g:::::g g:::::g | | | - // | | g::::::g g:::::g | | | - // | | g:::::::ggggg:::::g | | | - // | | g::::::::::::::::g | | height - // | | gg::::::::::::::g | | | - // baseline ---*---------|---- gggggggg::::::g-----*-------- | - // / | | g:::::g | | - // origin | | gggggg g:::::g | | - // | | g:::::gg gg:::::g | | - // | | g::::::ggg:::::::g | | - // | | gg:::::::::::::g | | - // | | ggg::::::ggg | | - // | | gggggg | v - // | +-------------------------+----------------- ymin - // | | - // |------------- advanceX ----------->| - - // A structure that describe a glyph. - struct GlyphInfo - { - int Width; // Glyph's width in pixels. - int Height; // Glyph's height in pixels. - FT_Int OffsetX; // The distance from the origin ("pen position") to the left of the glyph. - FT_Int OffsetY; // The distance from the origin to the top of the glyph. This is usually a value < 0. - float AdvanceX; // The distance from the origin to the origin of the next glyph. This is usually a value > 0. - bool IsColored; // The glyph is colored - }; - - // Font parameters and metrics. - struct FontInfo - { - uint32_t PixelHeight; // Size this font was generated with. - float Ascender; // The pixel extents above the baseline in pixels (typically positive). - float Descender; // The extents below the baseline in pixels (typically negative). - float LineSpacing; // The baseline-to-baseline distance. Note that it usually is larger than the sum of the ascender and descender taken as absolute values. There is also no guarantee that no glyphs extend above or below subsequent baselines when using this distance. Think of it as a value the designer of the font finds appropriate. - float LineGap; // The spacing in pixels between one row's descent and the next row's ascent. - float MaxAdvanceWidth; // This field gives the maximum horizontal cursor advance for all glyphs in the font. - }; - - // FreeType glyph rasterizer. - // NB: No ctor/dtor, explicitly call Init()/Shutdown() - struct FreeTypeFont - { - bool InitFont(FT_Library ft_library, const ImFontConfig& cfg, unsigned int extra_user_flags); // Initialize from an external data buffer. Doesn't copy data, and you must ensure it stays valid up to this object lifetime. - void CloseFont(); - void SetPixelHeight(int pixel_height); // Change font pixel size. All following calls to RasterizeGlyph() will use this size - const FT_Glyph_Metrics* LoadGlyph(uint32_t in_codepoint); - const FT_Bitmap* RenderGlyphAndGetInfo(GlyphInfo* out_glyph_info); - void BlitGlyph(const FT_Bitmap* ft_bitmap, uint32_t* dst, uint32_t dst_pitch, unsigned char* multiply_table = nullptr); - ~FreeTypeFont() { CloseFont(); } - - // [Internals] - FontInfo Info; // Font descriptor of the current font. - FT_Face Face; - unsigned int UserFlags; // = ImFontConfig::RasterizerFlags - FT_Int32 LoadFlags; - FT_Render_Mode RenderMode; - }; - - // From SDL_ttf: Handy routines for converting from fixed point - #define FT_CEIL(X) (((X + 63) & -64) / 64) - - bool FreeTypeFont::InitFont(FT_Library ft_library, const ImFontConfig& cfg, unsigned int extra_font_builder_flags) - { - FT_Error error = FT_New_Memory_Face(ft_library, (uint8_t*)cfg.FontData, (uint32_t)cfg.FontDataSize, (uint32_t)cfg.FontNo, &Face); - if (error != 0) - return false; - error = FT_Select_Charmap(Face, FT_ENCODING_UNICODE); - if (error != 0) - return false; - - // Convert to FreeType flags (NB: Bold and Oblique are processed separately) - UserFlags = cfg.FontBuilderFlags | extra_font_builder_flags; - - LoadFlags = 0; - if ((UserFlags & ImGuiFreeTypeBuilderFlags_Bitmap) == 0) - LoadFlags |= FT_LOAD_NO_BITMAP; - - if (UserFlags & ImGuiFreeTypeBuilderFlags_NoHinting) - LoadFlags |= FT_LOAD_NO_HINTING; - if (UserFlags & ImGuiFreeTypeBuilderFlags_NoAutoHint) - LoadFlags |= FT_LOAD_NO_AUTOHINT; - if (UserFlags & ImGuiFreeTypeBuilderFlags_ForceAutoHint) - LoadFlags |= FT_LOAD_FORCE_AUTOHINT; - if (UserFlags & ImGuiFreeTypeBuilderFlags_LightHinting) - LoadFlags |= FT_LOAD_TARGET_LIGHT; - else if (UserFlags & ImGuiFreeTypeBuilderFlags_MonoHinting) - LoadFlags |= FT_LOAD_TARGET_MONO; - else - LoadFlags |= FT_LOAD_TARGET_NORMAL; - - if (UserFlags & ImGuiFreeTypeBuilderFlags_Monochrome) - RenderMode = FT_RENDER_MODE_MONO; - else - RenderMode = FT_RENDER_MODE_NORMAL; - - if (UserFlags & ImGuiFreeTypeBuilderFlags_LoadColor) - LoadFlags |= FT_LOAD_COLOR; - - memset(&Info, 0, sizeof(Info)); - SetPixelHeight((uint32_t)cfg.SizePixels); - - return true; - } - - void FreeTypeFont::CloseFont() - { - if (Face) - { - FT_Done_Face(Face); - Face = nullptr; - } - } - - void FreeTypeFont::SetPixelHeight(int pixel_height) - { - // Vuhdo: I'm not sure how to deal with font sizes properly. As far as I understand, currently ImGui assumes that the 'pixel_height' - // is a maximum height of an any given glyph, i.e. it's the sum of font's ascender and descender. Seems strange to me. - // NB: FT_Set_Pixel_Sizes() doesn't seem to get us the same result. - FT_Size_RequestRec req; - req.type = (UserFlags & ImGuiFreeTypeBuilderFlags_Bitmap) ? FT_SIZE_REQUEST_TYPE_NOMINAL : FT_SIZE_REQUEST_TYPE_REAL_DIM; - req.width = 0; - req.height = (uint32_t)pixel_height * 64; - req.horiResolution = 0; - req.vertResolution = 0; - FT_Request_Size(Face, &req); - - // Update font info - FT_Size_Metrics metrics = Face->size->metrics; - Info.PixelHeight = (uint32_t)pixel_height; - Info.Ascender = (float)FT_CEIL(metrics.ascender); - Info.Descender = (float)FT_CEIL(metrics.descender); - Info.LineSpacing = (float)FT_CEIL(metrics.height); - Info.LineGap = (float)FT_CEIL(metrics.height - metrics.ascender + metrics.descender); - Info.MaxAdvanceWidth = (float)FT_CEIL(metrics.max_advance); - } - - const FT_Glyph_Metrics* FreeTypeFont::LoadGlyph(uint32_t codepoint) - { - uint32_t glyph_index = FT_Get_Char_Index(Face, codepoint); - if (glyph_index == 0) - return nullptr; - - // If this crash for you: FreeType 2.11.0 has a crash bug on some bitmap/colored fonts. - // - https://gitlab.freedesktop.org/freetype/freetype/-/issues/1076 - // - https://github.com/ocornut/imgui/issues/4567 - // - https://github.com/ocornut/imgui/issues/4566 - // You can use FreeType 2.10, or the patched version of 2.11.0 in VcPkg, or probably any upcoming FreeType version. - FT_Error error = FT_Load_Glyph(Face, glyph_index, LoadFlags); - if (error) - return nullptr; - - // Need an outline for this to work - FT_GlyphSlot slot = Face->glyph; -#ifdef IMGUI_ENABLE_FREETYPE_LUNASVG - IM_ASSERT(slot->format == FT_GLYPH_FORMAT_OUTLINE || slot->format == FT_GLYPH_FORMAT_BITMAP || slot->format == FT_GLYPH_FORMAT_SVG); -#else -#if ((FREETYPE_MAJOR >= 2) && (FREETYPE_MINOR >= 12)) - IM_ASSERT(slot->format != FT_GLYPH_FORMAT_SVG && "The font contains SVG glyphs, you'll need to enable IMGUI_ENABLE_FREETYPE_LUNASVG in imconfig.h and install required libraries in order to use this font"); -#endif - IM_ASSERT(slot->format == FT_GLYPH_FORMAT_OUTLINE || slot->format == FT_GLYPH_FORMAT_BITMAP); -#endif // IMGUI_ENABLE_FREETYPE_LUNASVG - - // Apply convenience transform (this is not picking from real "Bold"/"Italic" fonts! Merely applying FreeType helper transform. Oblique == Slanting) - if (UserFlags & ImGuiFreeTypeBuilderFlags_Bold) - FT_GlyphSlot_Embolden(slot); - if (UserFlags & ImGuiFreeTypeBuilderFlags_Oblique) - { - FT_GlyphSlot_Oblique(slot); - //FT_BBox bbox; - //FT_Outline_Get_BBox(&slot->outline, &bbox); - //slot->metrics.width = bbox.xMax - bbox.xMin; - //slot->metrics.height = bbox.yMax - bbox.yMin; - } - - return &slot->metrics; - } - - const FT_Bitmap* FreeTypeFont::RenderGlyphAndGetInfo(GlyphInfo* out_glyph_info) - { - FT_GlyphSlot slot = Face->glyph; - FT_Error error = FT_Render_Glyph(slot, RenderMode); - if (error != 0) - return nullptr; - - FT_Bitmap* ft_bitmap = &Face->glyph->bitmap; - out_glyph_info->Width = (int)ft_bitmap->width; - out_glyph_info->Height = (int)ft_bitmap->rows; - out_glyph_info->OffsetX = Face->glyph->bitmap_left; - out_glyph_info->OffsetY = -Face->glyph->bitmap_top; - out_glyph_info->AdvanceX = (float)FT_CEIL(slot->advance.x); - out_glyph_info->IsColored = (ft_bitmap->pixel_mode == FT_PIXEL_MODE_BGRA); - - return ft_bitmap; - } - - void FreeTypeFont::BlitGlyph(const FT_Bitmap* ft_bitmap, uint32_t* dst, uint32_t dst_pitch, unsigned char* multiply_table) - { - IM_ASSERT(ft_bitmap != nullptr); - const uint32_t w = ft_bitmap->width; - const uint32_t h = ft_bitmap->rows; - const uint8_t* src = ft_bitmap->buffer; - const uint32_t src_pitch = ft_bitmap->pitch; - - switch (ft_bitmap->pixel_mode) - { - case FT_PIXEL_MODE_GRAY: // Grayscale image, 1 byte per pixel. - { - if (multiply_table == nullptr) - { - for (uint32_t y = 0; y < h; y++, src += src_pitch, dst += dst_pitch) - for (uint32_t x = 0; x < w; x++) - dst[x] = IM_COL32(255, 255, 255, src[x]); - } - else - { - for (uint32_t y = 0; y < h; y++, src += src_pitch, dst += dst_pitch) - for (uint32_t x = 0; x < w; x++) - dst[x] = IM_COL32(255, 255, 255, multiply_table[src[x]]); - } - break; - } - case FT_PIXEL_MODE_MONO: // Monochrome image, 1 bit per pixel. The bits in each byte are ordered from MSB to LSB. - { - uint8_t color0 = multiply_table ? multiply_table[0] : 0; - uint8_t color1 = multiply_table ? multiply_table[255] : 255; - for (uint32_t y = 0; y < h; y++, src += src_pitch, dst += dst_pitch) - { - uint8_t bits = 0; - const uint8_t* bits_ptr = src; - for (uint32_t x = 0; x < w; x++, bits <<= 1) - { - if ((x & 7) == 0) - bits = *bits_ptr++; - dst[x] = IM_COL32(255, 255, 255, (bits & 0x80) ? color1 : color0); - } - } - break; - } - case FT_PIXEL_MODE_BGRA: - { - // FIXME: Converting pre-multiplied alpha to straight. Doesn't smell good. - #define DE_MULTIPLY(color, alpha) (ImU32)(255.0f * (float)color / (float)alpha + 0.5f) - if (multiply_table == nullptr) - { - for (uint32_t y = 0; y < h; y++, src += src_pitch, dst += dst_pitch) - for (uint32_t x = 0; x < w; x++) - { - uint8_t r = src[x * 4 + 2], g = src[x * 4 + 1], b = src[x * 4], a = src[x * 4 + 3]; - dst[x] = IM_COL32(DE_MULTIPLY(r, a), DE_MULTIPLY(g, a), DE_MULTIPLY(b, a), a); - } - } - else - { - for (uint32_t y = 0; y < h; y++, src += src_pitch, dst += dst_pitch) - { - for (uint32_t x = 0; x < w; x++) - { - uint8_t r = src[x * 4 + 2], g = src[x * 4 + 1], b = src[x * 4], a = src[x * 4 + 3]; - dst[x] = IM_COL32(multiply_table[DE_MULTIPLY(r, a)], multiply_table[DE_MULTIPLY(g, a)], multiply_table[DE_MULTIPLY(b, a)], multiply_table[a]); - } - } - } - #undef DE_MULTIPLY - break; - } - default: - IM_ASSERT(0 && "FreeTypeFont::BlitGlyph(): Unknown bitmap pixel mode!"); - } - } -} // namespace - -#ifndef STB_RECT_PACK_IMPLEMENTATION // in case the user already have an implementation in the _same_ compilation unit (e.g. unity builds) -#ifndef IMGUI_DISABLE_STB_RECT_PACK_IMPLEMENTATION -#define STBRP_ASSERT(x) do { IM_ASSERT(x); } while (0) -#define STBRP_STATIC -#define STB_RECT_PACK_IMPLEMENTATION -#endif -#ifdef IMGUI_STB_RECT_PACK_FILENAME -#include IMGUI_STB_RECT_PACK_FILENAME -#else -#include "imstb_rectpack.h" -#endif -#endif - -struct ImFontBuildSrcGlyphFT -{ - GlyphInfo Info; - uint32_t Codepoint; - unsigned int* BitmapData; // Point within one of the dst_tmp_bitmap_buffers[] array - - ImFontBuildSrcGlyphFT() { memset((void*)this, 0, sizeof(*this)); } -}; - -struct ImFontBuildSrcDataFT -{ - FreeTypeFont Font; - stbrp_rect* Rects; // Rectangle to pack. We first fill in their size and the packer will give us their position. - const ImWchar* SrcRanges; // Ranges as requested by user (user is allowed to request too much, e.g. 0x0020..0xFFFF) - int DstIndex; // Index into atlas->Fonts[] and dst_tmp_array[] - int GlyphsHighest; // Highest requested codepoint - int GlyphsCount; // Glyph count (excluding missing glyphs and glyphs already set by an earlier source font) - ImBitVector GlyphsSet; // Glyph bit map (random access, 1-bit per codepoint. This will be a maximum of 8KB) - ImVector GlyphsList; -}; - -// Temporary data for one destination ImFont* (multiple source fonts can be merged into one destination ImFont) -struct ImFontBuildDstDataFT -{ - int SrcCount; // Number of source fonts targeting this destination font. - int GlyphsHighest; - int GlyphsCount; - ImBitVector GlyphsSet; // This is used to resolve collision when multiple sources are merged into a same destination font. -}; - -bool ImFontAtlasBuildWithFreeTypeEx(FT_Library ft_library, ImFontAtlas* atlas, unsigned int extra_flags) -{ - IM_ASSERT(atlas->ConfigData.Size > 0); - - ImFontAtlasBuildInit(atlas); - - // Clear atlas - atlas->TexID = (ImTextureID)nullptr; - atlas->TexWidth = atlas->TexHeight = 0; - atlas->TexUvScale = ImVec2(0.0f, 0.0f); - atlas->TexUvWhitePixel = ImVec2(0.0f, 0.0f); - atlas->ClearTexData(); - - // Temporary storage for building - bool src_load_color = false; - ImVector src_tmp_array; - ImVector dst_tmp_array; - src_tmp_array.resize(atlas->ConfigData.Size); - dst_tmp_array.resize(atlas->Fonts.Size); - memset((void*)src_tmp_array.Data, 0, (size_t)src_tmp_array.size_in_bytes()); - memset((void*)dst_tmp_array.Data, 0, (size_t)dst_tmp_array.size_in_bytes()); - - // 1. Initialize font loading structure, check font data validity - for (int src_i = 0; src_i < atlas->ConfigData.Size; src_i++) - { - ImFontBuildSrcDataFT& src_tmp = src_tmp_array[src_i]; - ImFontConfig& cfg = atlas->ConfigData[src_i]; - FreeTypeFont& font_face = src_tmp.Font; - IM_ASSERT(cfg.DstFont && (!cfg.DstFont->IsLoaded() || cfg.DstFont->ContainerAtlas == atlas)); - - // Find index from cfg.DstFont (we allow the user to set cfg.DstFont. Also it makes casual debugging nicer than when storing indices) - src_tmp.DstIndex = -1; - for (int output_i = 0; output_i < atlas->Fonts.Size && src_tmp.DstIndex == -1; output_i++) - if (cfg.DstFont == atlas->Fonts[output_i]) - src_tmp.DstIndex = output_i; - IM_ASSERT(src_tmp.DstIndex != -1); // cfg.DstFont not pointing within atlas->Fonts[] array? - if (src_tmp.DstIndex == -1) - return false; - - // Load font - if (!font_face.InitFont(ft_library, cfg, extra_flags)) - return false; - - // Measure highest codepoints - src_load_color |= (cfg.FontBuilderFlags & ImGuiFreeTypeBuilderFlags_LoadColor) != 0; - ImFontBuildDstDataFT& dst_tmp = dst_tmp_array[src_tmp.DstIndex]; - src_tmp.SrcRanges = cfg.GlyphRanges ? cfg.GlyphRanges : atlas->GetGlyphRangesDefault(); - for (const ImWchar* src_range = src_tmp.SrcRanges; src_range[0] && src_range[1]; src_range += 2) - { - // Check for valid range. This may also help detect *some* dangling pointers, because a common - // user error is to setup ImFontConfig::GlyphRanges with a pointer to data that isn't persistent. - IM_ASSERT(src_range[0] <= src_range[1]); - src_tmp.GlyphsHighest = ImMax(src_tmp.GlyphsHighest, (int)src_range[1]); - } - dst_tmp.SrcCount++; - dst_tmp.GlyphsHighest = ImMax(dst_tmp.GlyphsHighest, src_tmp.GlyphsHighest); - } - - // 2. For every requested codepoint, check for their presence in the font data, and handle redundancy or overlaps between source fonts to avoid unused glyphs. - int total_glyphs_count = 0; - for (int src_i = 0; src_i < src_tmp_array.Size; src_i++) - { - ImFontBuildSrcDataFT& src_tmp = src_tmp_array[src_i]; - ImFontBuildDstDataFT& dst_tmp = dst_tmp_array[src_tmp.DstIndex]; - src_tmp.GlyphsSet.Create(src_tmp.GlyphsHighest + 1); - if (dst_tmp.GlyphsSet.Storage.empty()) - dst_tmp.GlyphsSet.Create(dst_tmp.GlyphsHighest + 1); - - for (const ImWchar* src_range = src_tmp.SrcRanges; src_range[0] && src_range[1]; src_range += 2) - for (int codepoint = src_range[0]; codepoint <= (int)src_range[1]; codepoint++) - { - if (dst_tmp.GlyphsSet.TestBit(codepoint)) // Don't overwrite existing glyphs. We could make this an option (e.g. MergeOverwrite) - continue; - uint32_t glyph_index = FT_Get_Char_Index(src_tmp.Font.Face, codepoint); // It is actually in the font? (FIXME-OPT: We are not storing the glyph_index..) - if (glyph_index == 0) - continue; - - // Add to avail set/counters - src_tmp.GlyphsCount++; - dst_tmp.GlyphsCount++; - src_tmp.GlyphsSet.SetBit(codepoint); - dst_tmp.GlyphsSet.SetBit(codepoint); - total_glyphs_count++; - } - } - - // 3. Unpack our bit map into a flat list (we now have all the Unicode points that we know are requested _and_ available _and_ not overlapping another) - for (int src_i = 0; src_i < src_tmp_array.Size; src_i++) - { - ImFontBuildSrcDataFT& src_tmp = src_tmp_array[src_i]; - src_tmp.GlyphsList.reserve(src_tmp.GlyphsCount); - - IM_ASSERT(sizeof(src_tmp.GlyphsSet.Storage.Data[0]) == sizeof(ImU32)); - const ImU32* it_begin = src_tmp.GlyphsSet.Storage.begin(); - const ImU32* it_end = src_tmp.GlyphsSet.Storage.end(); - for (const ImU32* it = it_begin; it < it_end; it++) - if (ImU32 entries_32 = *it) - for (ImU32 bit_n = 0; bit_n < 32; bit_n++) - if (entries_32 & ((ImU32)1 << bit_n)) - { - ImFontBuildSrcGlyphFT src_glyph; - src_glyph.Codepoint = (ImWchar)(((it - it_begin) << 5) + bit_n); - //src_glyph.GlyphIndex = 0; // FIXME-OPT: We had this info in the previous step and lost it.. - src_tmp.GlyphsList.push_back(src_glyph); - } - src_tmp.GlyphsSet.Clear(); - IM_ASSERT(src_tmp.GlyphsList.Size == src_tmp.GlyphsCount); - } - for (int dst_i = 0; dst_i < dst_tmp_array.Size; dst_i++) - dst_tmp_array[dst_i].GlyphsSet.Clear(); - dst_tmp_array.clear(); - - // Allocate packing character data and flag packed characters buffer as non-packed (x0=y0=x1=y1=0) - // (We technically don't need to zero-clear buf_rects, but let's do it for the sake of sanity) - ImVector buf_rects; - buf_rects.resize(total_glyphs_count); - memset(buf_rects.Data, 0, (size_t)buf_rects.size_in_bytes()); - - // Allocate temporary rasterization data buffers. - // We could not find a way to retrieve accurate glyph size without rendering them. - // (e.g. slot->metrics->width not always matching bitmap->width, especially considering the Oblique transform) - // We allocate in chunks of 256 KB to not waste too much extra memory ahead. Hopefully users of FreeType won't mind the temporary allocations. - const int BITMAP_BUFFERS_CHUNK_SIZE = 256 * 1024; - int buf_bitmap_current_used_bytes = 0; - ImVector buf_bitmap_buffers; - buf_bitmap_buffers.push_back((unsigned char*)IM_ALLOC(BITMAP_BUFFERS_CHUNK_SIZE)); - - // 4. Gather glyphs sizes so we can pack them in our virtual canvas. - // 8. Render/rasterize font characters into the texture - int total_surface = 0; - int buf_rects_out_n = 0; - for (int src_i = 0; src_i < src_tmp_array.Size; src_i++) - { - ImFontBuildSrcDataFT& src_tmp = src_tmp_array[src_i]; - ImFontConfig& cfg = atlas->ConfigData[src_i]; - if (src_tmp.GlyphsCount == 0) - continue; - - src_tmp.Rects = &buf_rects[buf_rects_out_n]; - buf_rects_out_n += src_tmp.GlyphsCount; - - // Compute multiply table if requested - const bool multiply_enabled = (cfg.RasterizerMultiply != 1.0f); - unsigned char multiply_table[256]; - if (multiply_enabled) - ImFontAtlasBuildMultiplyCalcLookupTable(multiply_table, cfg.RasterizerMultiply); - - // Gather the sizes of all rectangles we will need to pack - const int padding = atlas->TexGlyphPadding; - for (int glyph_i = 0; glyph_i < src_tmp.GlyphsList.Size; glyph_i++) - { - ImFontBuildSrcGlyphFT& src_glyph = src_tmp.GlyphsList[glyph_i]; - - const FT_Glyph_Metrics* metrics = src_tmp.Font.LoadGlyph(src_glyph.Codepoint); - if (metrics == nullptr) - continue; - - // Render glyph into a bitmap (currently held by FreeType) - const FT_Bitmap* ft_bitmap = src_tmp.Font.RenderGlyphAndGetInfo(&src_glyph.Info); - if (ft_bitmap == nullptr) - continue; - - // Allocate new temporary chunk if needed - const int bitmap_size_in_bytes = src_glyph.Info.Width * src_glyph.Info.Height * 4; - if (buf_bitmap_current_used_bytes + bitmap_size_in_bytes > BITMAP_BUFFERS_CHUNK_SIZE) - { - buf_bitmap_current_used_bytes = 0; - buf_bitmap_buffers.push_back((unsigned char*)IM_ALLOC(BITMAP_BUFFERS_CHUNK_SIZE)); - } - IM_ASSERT(buf_bitmap_current_used_bytes + bitmap_size_in_bytes <= BITMAP_BUFFERS_CHUNK_SIZE); // We could probably allocate custom-sized buffer instead. - - // Blit rasterized pixels to our temporary buffer and keep a pointer to it. - src_glyph.BitmapData = (unsigned int*)(buf_bitmap_buffers.back() + buf_bitmap_current_used_bytes); - buf_bitmap_current_used_bytes += bitmap_size_in_bytes; - src_tmp.Font.BlitGlyph(ft_bitmap, src_glyph.BitmapData, src_glyph.Info.Width, multiply_enabled ? multiply_table : nullptr); - - src_tmp.Rects[glyph_i].w = (stbrp_coord)(src_glyph.Info.Width + padding); - src_tmp.Rects[glyph_i].h = (stbrp_coord)(src_glyph.Info.Height + padding); - total_surface += src_tmp.Rects[glyph_i].w * src_tmp.Rects[glyph_i].h; - } - } - - // We need a width for the skyline algorithm, any width! - // The exact width doesn't really matter much, but some API/GPU have texture size limitations and increasing width can decrease height. - // User can override TexDesiredWidth and TexGlyphPadding if they wish, otherwise we use a simple heuristic to select the width based on expected surface. - const int surface_sqrt = (int)ImSqrt((float)total_surface) + 1; - atlas->TexHeight = 0; - if (atlas->TexDesiredWidth > 0) - atlas->TexWidth = atlas->TexDesiredWidth; - else - atlas->TexWidth = (surface_sqrt >= 4096 * 0.7f) ? 4096 : (surface_sqrt >= 2048 * 0.7f) ? 2048 : (surface_sqrt >= 1024 * 0.7f) ? 1024 : 512; - - // 5. Start packing - // Pack our extra data rectangles first, so it will be on the upper-left corner of our texture (UV will have small values). - const int TEX_HEIGHT_MAX = 1024 * 32; - const int num_nodes_for_packing_algorithm = atlas->TexWidth - atlas->TexGlyphPadding; - ImVector pack_nodes; - pack_nodes.resize(num_nodes_for_packing_algorithm); - stbrp_context pack_context; - stbrp_init_target(&pack_context, atlas->TexWidth - atlas->TexGlyphPadding, TEX_HEIGHT_MAX - atlas->TexGlyphPadding, pack_nodes.Data, pack_nodes.Size); - ImFontAtlasBuildPackCustomRects(atlas, &pack_context); - - // 6. Pack each source font. No rendering yet, we are working with rectangles in an infinitely tall texture at this point. - for (int src_i = 0; src_i < src_tmp_array.Size; src_i++) - { - ImFontBuildSrcDataFT& src_tmp = src_tmp_array[src_i]; - if (src_tmp.GlyphsCount == 0) - continue; - - stbrp_pack_rects(&pack_context, src_tmp.Rects, src_tmp.GlyphsCount); - - // Extend texture height and mark missing glyphs as non-packed so we won't render them. - // FIXME: We are not handling packing failure here (would happen if we got off TEX_HEIGHT_MAX or if a single if larger than TexWidth?) - for (int glyph_i = 0; glyph_i < src_tmp.GlyphsCount; glyph_i++) - if (src_tmp.Rects[glyph_i].was_packed) - atlas->TexHeight = ImMax(atlas->TexHeight, src_tmp.Rects[glyph_i].y + src_tmp.Rects[glyph_i].h); - } - - // 7. Allocate texture - atlas->TexHeight = (atlas->Flags & ImFontAtlasFlags_NoPowerOfTwoHeight) ? (atlas->TexHeight + 1) : ImUpperPowerOfTwo(atlas->TexHeight); - atlas->TexUvScale = ImVec2(1.0f / atlas->TexWidth, 1.0f / atlas->TexHeight); - if (src_load_color) - { - size_t tex_size = (size_t)atlas->TexWidth * atlas->TexHeight * 4; - atlas->TexPixelsRGBA32 = (unsigned int*)IM_ALLOC(tex_size); - memset(atlas->TexPixelsRGBA32, 0, tex_size); - } - else - { - size_t tex_size = (size_t)atlas->TexWidth * atlas->TexHeight * 1; - atlas->TexPixelsAlpha8 = (unsigned char*)IM_ALLOC(tex_size); - memset(atlas->TexPixelsAlpha8, 0, tex_size); - } - - // 8. Copy rasterized font characters back into the main texture - // 9. Setup ImFont and glyphs for runtime - bool tex_use_colors = false; - for (int src_i = 0; src_i < src_tmp_array.Size; src_i++) - { - ImFontBuildSrcDataFT& src_tmp = src_tmp_array[src_i]; - if (src_tmp.GlyphsCount == 0) - continue; - - // When merging fonts with MergeMode=true: - // - We can have multiple input fonts writing into a same destination font. - // - dst_font->ConfigData is != from cfg which is our source configuration. - ImFontConfig& cfg = atlas->ConfigData[src_i]; - ImFont* dst_font = cfg.DstFont; - - const float ascent = src_tmp.Font.Info.Ascender; - const float descent = src_tmp.Font.Info.Descender; - ImFontAtlasBuildSetupFont(atlas, dst_font, &cfg, ascent, descent); - const float font_off_x = cfg.GlyphOffset.x; - const float font_off_y = cfg.GlyphOffset.y + IM_ROUND(dst_font->Ascent); - - const int padding = atlas->TexGlyphPadding; - for (int glyph_i = 0; glyph_i < src_tmp.GlyphsCount; glyph_i++) - { - ImFontBuildSrcGlyphFT& src_glyph = src_tmp.GlyphsList[glyph_i]; - stbrp_rect& pack_rect = src_tmp.Rects[glyph_i]; - IM_ASSERT(pack_rect.was_packed); - if (pack_rect.w == 0 && pack_rect.h == 0) - continue; - - GlyphInfo& info = src_glyph.Info; - IM_ASSERT(info.Width + padding <= pack_rect.w); - IM_ASSERT(info.Height + padding <= pack_rect.h); - const int tx = pack_rect.x + padding; - const int ty = pack_rect.y + padding; - - // Register glyph - float x0 = info.OffsetX + font_off_x; - float y0 = info.OffsetY + font_off_y; - float x1 = x0 + info.Width; - float y1 = y0 + info.Height; - float u0 = (tx) / (float)atlas->TexWidth; - float v0 = (ty) / (float)atlas->TexHeight; - float u1 = (tx + info.Width) / (float)atlas->TexWidth; - float v1 = (ty + info.Height) / (float)atlas->TexHeight; - dst_font->AddGlyph(&cfg, (ImWchar)src_glyph.Codepoint, x0, y0, x1, y1, u0, v0, u1, v1, info.AdvanceX); - - ImFontGlyph* dst_glyph = &dst_font->Glyphs.back(); - IM_ASSERT(dst_glyph->Codepoint == src_glyph.Codepoint); - if (src_glyph.Info.IsColored) - dst_glyph->Colored = tex_use_colors = true; - - // Blit from temporary buffer to final texture - size_t blit_src_stride = (size_t)src_glyph.Info.Width; - size_t blit_dst_stride = (size_t)atlas->TexWidth; - unsigned int* blit_src = src_glyph.BitmapData; - if (atlas->TexPixelsAlpha8 != nullptr) - { - unsigned char* blit_dst = atlas->TexPixelsAlpha8 + (ty * blit_dst_stride) + tx; - for (int y = 0; y < info.Height; y++, blit_dst += blit_dst_stride, blit_src += blit_src_stride) - for (int x = 0; x < info.Width; x++) - blit_dst[x] = (unsigned char)((blit_src[x] >> IM_COL32_A_SHIFT) & 0xFF); - } - else - { - unsigned int* blit_dst = atlas->TexPixelsRGBA32 + (ty * blit_dst_stride) + tx; - for (int y = 0; y < info.Height; y++, blit_dst += blit_dst_stride, blit_src += blit_src_stride) - for (int x = 0; x < info.Width; x++) - blit_dst[x] = blit_src[x]; - } - } - - src_tmp.Rects = nullptr; - } - atlas->TexPixelsUseColors = tex_use_colors; - - // Cleanup - for (int buf_i = 0; buf_i < buf_bitmap_buffers.Size; buf_i++) - IM_FREE(buf_bitmap_buffers[buf_i]); - src_tmp_array.clear_destruct(); - - ImFontAtlasBuildFinish(atlas); - - return true; -} - -// FreeType memory allocation callbacks -static void* FreeType_Alloc(FT_Memory /*memory*/, long size) -{ - return GImGuiFreeTypeAllocFunc((size_t)size, GImGuiFreeTypeAllocatorUserData); -} - -static void FreeType_Free(FT_Memory /*memory*/, void* block) -{ - GImGuiFreeTypeFreeFunc(block, GImGuiFreeTypeAllocatorUserData); -} - -static void* FreeType_Realloc(FT_Memory /*memory*/, long cur_size, long new_size, void* block) -{ - // Implement realloc() as we don't ask user to provide it. - if (block == nullptr) - return GImGuiFreeTypeAllocFunc((size_t)new_size, GImGuiFreeTypeAllocatorUserData); - - if (new_size == 0) - { - GImGuiFreeTypeFreeFunc(block, GImGuiFreeTypeAllocatorUserData); - return nullptr; - } - - if (new_size > cur_size) - { - void* new_block = GImGuiFreeTypeAllocFunc((size_t)new_size, GImGuiFreeTypeAllocatorUserData); - memcpy(new_block, block, (size_t)cur_size); - GImGuiFreeTypeFreeFunc(block, GImGuiFreeTypeAllocatorUserData); - return new_block; - } - - return block; -} - -static bool ImFontAtlasBuildWithFreeType(ImFontAtlas* atlas) -{ - // FreeType memory management: https://www.freetype.org/freetype2/docs/design/design-4.html - FT_MemoryRec_ memory_rec = {}; - memory_rec.user = nullptr; - memory_rec.alloc = &FreeType_Alloc; - memory_rec.free = &FreeType_Free; - memory_rec.realloc = &FreeType_Realloc; - - // https://www.freetype.org/freetype2/docs/reference/ft2-module_management.html#FT_New_Library - FT_Library ft_library; - FT_Error error = FT_New_Library(&memory_rec, &ft_library); - if (error != 0) - return false; - - // If you don't call FT_Add_Default_Modules() the rest of code may work, but FreeType won't use our custom allocator. - FT_Add_Default_Modules(ft_library); - -#ifdef IMGUI_ENABLE_FREETYPE_LUNASVG - // Install svg hooks for FreeType - // https://freetype.org/freetype2/docs/reference/ft2-properties.html#svg-hooks - // https://freetype.org/freetype2/docs/reference/ft2-svg_fonts.html#svg_fonts - SVG_RendererHooks hooks = { ImGuiLunasvgPortInit, ImGuiLunasvgPortFree, ImGuiLunasvgPortRender, ImGuiLunasvgPortPresetSlot }; - FT_Property_Set(ft_library, "ot-svg", "svg-hooks", &hooks); -#endif // IMGUI_ENABLE_FREETYPE_LUNASVG - - bool ret = ImFontAtlasBuildWithFreeTypeEx(ft_library, atlas, atlas->FontBuilderFlags); - FT_Done_Library(ft_library); - - return ret; -} - -const ImFontBuilderIO* ImGuiFreeType::GetBuilderForFreeType() -{ - static ImFontBuilderIO io; - io.FontBuilder_Build = ImFontAtlasBuildWithFreeType; - return &io; -} - -void ImGuiFreeType::SetAllocatorFunctions(void* (*alloc_func)(size_t sz, void* user_data), void (*free_func)(void* ptr, void* user_data), void* user_data) -{ - GImGuiFreeTypeAllocFunc = alloc_func; - GImGuiFreeTypeFreeFunc = free_func; - GImGuiFreeTypeAllocatorUserData = user_data; -} - -#ifdef IMGUI_ENABLE_FREETYPE_LUNASVG -// For more details, see https://gitlab.freedesktop.org/freetype/freetype-demos/-/blob/master/src/rsvg-port.c -// The original code from the demo is licensed under CeCILL-C Free Software License Agreement (https://gitlab.freedesktop.org/freetype/freetype/-/blob/master/LICENSE.TXT) -struct LunasvgPortState -{ - FT_Error err = FT_Err_Ok; - lunasvg::Matrix matrix; - std::unique_ptr svg = nullptr; -}; - -static FT_Error ImGuiLunasvgPortInit(FT_Pointer* _state) -{ - *_state = IM_NEW(LunasvgPortState)(); - return FT_Err_Ok; -} - -static void ImGuiLunasvgPortFree(FT_Pointer* _state) -{ - IM_DELETE(*(LunasvgPortState**)_state); -} - -static FT_Error ImGuiLunasvgPortRender(FT_GlyphSlot slot, FT_Pointer* _state) -{ - LunasvgPortState* state = *(LunasvgPortState**)_state; - - // If there was an error while loading the svg in ImGuiLunasvgPortPresetSlot(), the renderer hook still get called, so just returns the error. - if (state->err != FT_Err_Ok) - return state->err; - - // rows is height, pitch (or stride) equals to width * sizeof(int32) - lunasvg::Bitmap bitmap((uint8_t*)slot->bitmap.buffer, slot->bitmap.width, slot->bitmap.rows, slot->bitmap.pitch); - state->svg->setMatrix(state->svg->matrix().identity()); // Reset the svg matrix to the default value - state->svg->render(bitmap, state->matrix); // state->matrix is already scaled and translated - state->err = FT_Err_Ok; - return state->err; -} - -static FT_Error ImGuiLunasvgPortPresetSlot(FT_GlyphSlot slot, FT_Bool cache, FT_Pointer* _state) -{ - FT_SVG_Document document = (FT_SVG_Document)slot->other; - LunasvgPortState* state = *(LunasvgPortState**)_state; - FT_Size_Metrics& metrics = document->metrics; - - // This function is called twice, once in the FT_Load_Glyph() and another right before ImGuiLunasvgPortRender(). - // If it's the latter, don't do anything because it's // already done in the former. - if (cache) - return state->err; - - state->svg = lunasvg::Document::loadFromData((const char*)document->svg_document, document->svg_document_length); - if (state->svg == nullptr) - { - state->err = FT_Err_Invalid_SVG_Document; - return state->err; - } - - lunasvg::Box box = state->svg->box(); - double scale = std::min(metrics.x_ppem / box.w, metrics.y_ppem / box.h); - double xx = (double)document->transform.xx / (1 << 16); - double xy = -(double)document->transform.xy / (1 << 16); - double yx = -(double)document->transform.yx / (1 << 16); - double yy = (double)document->transform.yy / (1 << 16); - double x0 = (double)document->delta.x / 64 * box.w / metrics.x_ppem; - double y0 = -(double)document->delta.y / 64 * box.h / metrics.y_ppem; - - // Scale and transform, we don't translate the svg yet - state->matrix.identity(); - state->matrix.scale(scale, scale); - state->matrix.transform(xx, xy, yx, yy, x0, y0); - state->svg->setMatrix(state->matrix); - - // Pre-translate the matrix for the rendering step - state->matrix.translate(-box.x, -box.y); - - // Get the box again after the transformation - box = state->svg->box(); - - // Calculate the bitmap size - slot->bitmap_left = FT_Int(box.x); - slot->bitmap_top = FT_Int(-box.y); - slot->bitmap.rows = (unsigned int)(ImCeil((float)box.h)); - slot->bitmap.width = (unsigned int)(ImCeil((float)box.w)); - slot->bitmap.pitch = slot->bitmap.width * 4; - slot->bitmap.pixel_mode = FT_PIXEL_MODE_BGRA; - - // Compute all the bearings and set them correctly. The outline is scaled already, we just need to use the bounding box. - double metrics_width = box.w; - double metrics_height = box.h; - double horiBearingX = box.x; - double horiBearingY = -box.y; - double vertBearingX = slot->metrics.horiBearingX / 64.0 - slot->metrics.horiAdvance / 64.0 / 2.0; - double vertBearingY = (slot->metrics.vertAdvance / 64.0 - slot->metrics.height / 64.0) / 2.0; - slot->metrics.width = FT_Pos(IM_ROUND(metrics_width * 64.0)); // Using IM_ROUND() assume width and height are positive - slot->metrics.height = FT_Pos(IM_ROUND(metrics_height * 64.0)); - slot->metrics.horiBearingX = FT_Pos(horiBearingX * 64); - slot->metrics.horiBearingY = FT_Pos(horiBearingY * 64); - slot->metrics.vertBearingX = FT_Pos(vertBearingX * 64); - slot->metrics.vertBearingY = FT_Pos(vertBearingY * 64); - - if (slot->metrics.vertAdvance == 0) - slot->metrics.vertAdvance = FT_Pos(metrics_height * 1.2 * 64.0); - - state->err = FT_Err_Ok; - return state->err; -} - -#endif // #ifdef IMGUI_ENABLE_FREETYPE_LUNASVG - -//----------------------------------------------------------------------------- - -#ifdef __GNUC__ -#pragma GCC diagnostic pop -#endif - -#ifdef _MSC_VER -#pragma warning (pop) -#endif - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/misc/freetype/imgui_freetype.h b/app/jni/src/libultraship/extern/ImGui/misc/freetype/imgui_freetype.h deleted file mode 100644 index cc58ba6..0000000 --- a/app/jni/src/libultraship/extern/ImGui/misc/freetype/imgui_freetype.h +++ /dev/null @@ -1,52 +0,0 @@ -// dear imgui: FreeType font builder (used as a replacement for the stb_truetype builder) -// (headers) - -#pragma once -#include "imgui.h" // IMGUI_API -#ifndef IMGUI_DISABLE - -// Forward declarations -struct ImFontAtlas; -struct ImFontBuilderIO; - -// Hinting greatly impacts visuals (and glyph sizes). -// - By default, hinting is enabled and the font's native hinter is preferred over the auto-hinter. -// - When disabled, FreeType generates blurrier glyphs, more or less matches the stb_truetype.h -// - The Default hinting mode usually looks good, but may distort glyphs in an unusual way. -// - The Light hinting mode generates fuzzier glyphs but better matches Microsoft's rasterizer. -// You can set those flags globaly in ImFontAtlas::FontBuilderFlags -// You can set those flags on a per font basis in ImFontConfig::FontBuilderFlags -enum ImGuiFreeTypeBuilderFlags -{ - ImGuiFreeTypeBuilderFlags_NoHinting = 1 << 0, // Disable hinting. This generally generates 'blurrier' bitmap glyphs when the glyph are rendered in any of the anti-aliased modes. - ImGuiFreeTypeBuilderFlags_NoAutoHint = 1 << 1, // Disable auto-hinter. - ImGuiFreeTypeBuilderFlags_ForceAutoHint = 1 << 2, // Indicates that the auto-hinter is preferred over the font's native hinter. - ImGuiFreeTypeBuilderFlags_LightHinting = 1 << 3, // A lighter hinting algorithm for gray-level modes. Many generated glyphs are fuzzier but better resemble their original shape. This is achieved by snapping glyphs to the pixel grid only vertically (Y-axis), as is done by Microsoft's ClearType and Adobe's proprietary font renderer. This preserves inter-glyph spacing in horizontal text. - ImGuiFreeTypeBuilderFlags_MonoHinting = 1 << 4, // Strong hinting algorithm that should only be used for monochrome output. - ImGuiFreeTypeBuilderFlags_Bold = 1 << 5, // Styling: Should we artificially embolden the font? - ImGuiFreeTypeBuilderFlags_Oblique = 1 << 6, // Styling: Should we slant the font, emulating italic style? - ImGuiFreeTypeBuilderFlags_Monochrome = 1 << 7, // Disable anti-aliasing. Combine this with MonoHinting for best results! - ImGuiFreeTypeBuilderFlags_LoadColor = 1 << 8, // Enable FreeType color-layered glyphs - ImGuiFreeTypeBuilderFlags_Bitmap = 1 << 9 // Enable FreeType bitmap glyphs -}; - -namespace ImGuiFreeType -{ - // This is automatically assigned when using '#define IMGUI_ENABLE_FREETYPE'. - // If you need to dynamically select between multiple builders: - // - you can manually assign this builder with 'atlas->FontBuilderIO = ImGuiFreeType::GetBuilderForFreeType()' - // - prefer deep-copying this into your own ImFontBuilderIO instance if you use hot-reloading that messes up static data. - IMGUI_API const ImFontBuilderIO* GetBuilderForFreeType(); - - // Override allocators. By default ImGuiFreeType will use IM_ALLOC()/IM_FREE() - // However, as FreeType does lots of allocations we provide a way for the user to redirect it to a separate memory heap if desired. - IMGUI_API void SetAllocatorFunctions(void* (*alloc_func)(size_t sz, void* user_data), void (*free_func)(void* ptr, void* user_data), void* user_data = nullptr); - - // Obsolete names (will be removed soon) - // Prefer using '#define IMGUI_ENABLE_FREETYPE' -#ifndef IMGUI_DISABLE_OBSOLETE_FUNCTIONS - static inline bool BuildFontAtlas(ImFontAtlas* atlas, unsigned int flags = 0) { atlas->FontBuilderIO = GetBuilderForFreeType(); atlas->FontBuilderFlags = flags; return atlas->Build(); } -#endif -} - -#endif // #ifndef IMGUI_DISABLE diff --git a/app/jni/src/libultraship/extern/ImGui/misc/single_file/imgui_single_file.h b/app/jni/src/libultraship/extern/ImGui/misc/single_file/imgui_single_file.h deleted file mode 100644 index 7ca31e0..0000000 --- a/app/jni/src/libultraship/extern/ImGui/misc/single_file/imgui_single_file.h +++ /dev/null @@ -1,29 +0,0 @@ -// dear imgui: single-file wrapper include -// We use this to validate compiling all *.cpp files in a same compilation unit. -// Users of that technique (also called "Unity builds") can generally provide this themselves, -// so we don't really recommend you use this in your projects. - -// Do this: -// #define IMGUI_IMPLEMENTATION -// Before you include this file in *one* C++ file to create the implementation. -// Using this in your project will leak the contents of imgui_internal.h and ImVec2 operators in this compilation unit. - -#ifdef IMGUI_IMPLEMENTATION -#define IMGUI_DEFINE_MATH_OPERATORS -#endif - -#include "../../imgui.h" -#ifdef IMGUI_ENABLE_FREETYPE -#include "../../misc/freetype/imgui_freetype.h" -#endif - -#ifdef IMGUI_IMPLEMENTATION -#include "../../imgui.cpp" -#include "../../imgui_demo.cpp" -#include "../../imgui_draw.cpp" -#include "../../imgui_tables.cpp" -#include "../../imgui_widgets.cpp" -#ifdef IMGUI_ENABLE_FREETYPE -#include "../../misc/freetype/imgui_freetype.cpp" -#endif -#endif diff --git a/app/jni/src/libultraship/extern/StormLib/.gitignore b/app/jni/src/libultraship/extern/StormLib/.gitignore deleted file mode 100644 index 3d764df..0000000 --- a/app/jni/src/libultraship/extern/StormLib/.gitignore +++ /dev/null @@ -1,167 +0,0 @@ -################# -## Eclipse -################# - -*.pydevproject -.project -.metadata -bin/ -tmp/ -*.tmp -*.bak -*.swp -*~.nib -local.properties -.classpath -.settings/ -.loadpath - -# External tool builders -.externalToolBuilders/ - -# Locally stored "Eclipse launch configurations" -*.launch - -# CDT-specific -.cproject - -# PDT-specific -.buildpath - - -################# -## Visual Studio -################# - -## Ignore Visual Studio temporary files, build results, and -## files generated by popular Visual Studio add-ons. - -# User-specific files -*.suo -*.user -*.sln.docstates - -# Build results -[Dd]ebug/ -[Rr]elease/ -*_i.c -*_p.c -*.ilk -*.meta -*.obj -*.pch -*.pdb -*.pgc -*.pgd -*.rsp -*.sbr -*.tlb -*.tli -*.tlh -*.tmp -*.vspscc -.builds -*.dotCover -*.o -*.dylib - -## TODO: If you have NuGet Package Restore enabled, uncomment this -#packages/ - -# Visual C++ cache files -ipch/ -*.aps -*.ncb -*.opensdf -*.sdf - -# Visual Studio profiler -*.psess -*.vsp - -# ReSharper is a .NET coding add-in -_ReSharper* - -# Installshield output folder -[Ee]xpress - -# DocProject is a documentation generator add-in -DocProject/buildhelp/ -DocProject/Help/*.HxT -DocProject/Help/*.HxC -DocProject/Help/*.hhc -DocProject/Help/*.hhk -DocProject/Help/*.hhp -DocProject/Help/Html2 -DocProject/Help/html - -# Click-Once directory -publish - -# Others -[Bb]in -[Oo]bj -sql -TestResults -*.Cache -ClientBin -stylecop.* -~$* -*.dbmdl -Generated_Code #added for RIA/Silverlight projects - -# Backup & report files from converting an old project file to a newer -# Visual Studio version. Backup files are not needed, because we have git ;-) -_UpgradeReport_Files/ -Backup*/ -UpgradeLog*.XML - - - -############ -## Windows -############ - -# Windows image file caches -Thumbs.db - -# Folder config file -Desktop.ini - - -############# -## Python -############# - -*.py[co] - -# Packages -*.egg -*.egg-info -dist -build -eggs -parts -bin -var -sdist -develop-eggs -.installed.cfg - -# Installer logs -pip-log.txt - -# Unit test / coverage reports -.coverage -.tox - -#Translations -*.mo - -#Mr Developer -.mr.developer.cfg - -# Mac crap -.DS_Store -**/project.xcworkspace -**/xcuserdata diff --git a/app/jni/src/libultraship/extern/StormLib/CMakeLists.txt b/app/jni/src/libultraship/extern/StormLib/CMakeLists.txt deleted file mode 100644 index c480d40..0000000 --- a/app/jni/src/libultraship/extern/StormLib/CMakeLists.txt +++ /dev/null @@ -1,400 +0,0 @@ -project(StormLib) -cmake_minimum_required(VERSION 3.10) - -set(LIBRARY_NAME storm) -set(CMAKE_CXX_STANDARD 11) -set(CMAKE_CXX_EXTENSIONS OFF) -set(CMAKE_CXX_STANDARD_REQUIRED ON) - -include(CMakeDependentOption) - -option(BUILD_SHARED_LIBS "Compile shared libraries" OFF) -option(STORM_SKIP_INSTALL "Skip installing files" OFF) -option(STORM_USE_BUNDLED_LIBRARIES - "Force use of bundled dependencies instead of system libraries." - OFF -) -option(STORM_BUILD_TESTS - "Compile StormLib test application" OFF -# "BUILD_TESTING" OFF # Stay coherent with CTest variables -) - -set(SRC_FILES - src/adpcm/adpcm.cpp - src/huffman/huff.cpp - src/jenkins/lookup3.c - src/lzma/C/LzFind.c - src/lzma/C/LzmaDec.c - src/lzma/C/LzmaEnc.c - src/pklib/explode.c - src/pklib/implode.c - src/sparse/sparse.cpp - src/FileStream.cpp - src/SBaseCommon.cpp - src/SBaseDumpData.cpp - src/SBaseFileTable.cpp - src/SBaseSubTypes.cpp - src/SCompression.cpp - src/SFileAddFile.cpp - src/SFileAttributes.cpp - src/SFileCompactArchive.cpp - src/SFileCreateArchive.cpp - src/SFileExtractFile.cpp - src/SFileFindFile.cpp - src/SFileGetFileInfo.cpp - src/SFileListFile.cpp - src/SFileOpenArchive.cpp - src/SFileOpenFileEx.cpp - src/SFilePatchArchives.cpp - src/SFileReadFile.cpp - src/SFileVerify.cpp - src/libtomcrypt/src/pk/rsa/rsa_verify_simple.c - src/libtomcrypt/src/misc/crypt_libc.c -) - -if(MSVC) - # This file is used to create a DLL on windows - # Use BUILD_SHARED_LIBS to create StormLib.dll - set(STORM_DEF_FILES - src/DllMain.def - ) -endif() - -set(TOMCRYPT_FILES - src/libtomcrypt/src/hashes/hash_memory.c - src/libtomcrypt/src/hashes/md5.c - src/libtomcrypt/src/hashes/sha1.c - src/libtomcrypt/src/math/ltm_desc.c - src/libtomcrypt/src/math/multi.c - src/libtomcrypt/src/math/rand_prime.c - src/libtomcrypt/src/misc/base64_decode.c - src/libtomcrypt/src/misc/crypt_argchk.c - src/libtomcrypt/src/misc/crypt_find_hash.c - src/libtomcrypt/src/misc/crypt_find_prng.c - src/libtomcrypt/src/misc/crypt_hash_descriptor.c - src/libtomcrypt/src/misc/crypt_hash_is_valid.c - src/libtomcrypt/src/misc/crypt_ltc_mp_descriptor.c - src/libtomcrypt/src/misc/crypt_prng_descriptor.c - src/libtomcrypt/src/misc/crypt_prng_is_valid.c - src/libtomcrypt/src/misc/crypt_register_hash.c - src/libtomcrypt/src/misc/crypt_register_prng.c - src/libtomcrypt/src/misc/zeromem.c - src/libtomcrypt/src/pk/asn1/der_decode_bit_string.c - src/libtomcrypt/src/pk/asn1/der_decode_boolean.c - src/libtomcrypt/src/pk/asn1/der_decode_choice.c - src/libtomcrypt/src/pk/asn1/der_decode_ia5_string.c - src/libtomcrypt/src/pk/asn1/der_decode_integer.c - src/libtomcrypt/src/pk/asn1/der_decode_object_identifier.c - src/libtomcrypt/src/pk/asn1/der_decode_octet_string.c - src/libtomcrypt/src/pk/asn1/der_decode_printable_string.c - src/libtomcrypt/src/pk/asn1/der_decode_sequence_ex.c - src/libtomcrypt/src/pk/asn1/der_decode_sequence_flexi.c - src/libtomcrypt/src/pk/asn1/der_decode_sequence_multi.c - src/libtomcrypt/src/pk/asn1/der_decode_short_integer.c - src/libtomcrypt/src/pk/asn1/der_decode_utctime.c - src/libtomcrypt/src/pk/asn1/der_decode_utf8_string.c - src/libtomcrypt/src/pk/asn1/der_encode_bit_string.c - src/libtomcrypt/src/pk/asn1/der_encode_boolean.c - src/libtomcrypt/src/pk/asn1/der_encode_ia5_string.c - src/libtomcrypt/src/pk/asn1/der_encode_integer.c - src/libtomcrypt/src/pk/asn1/der_encode_object_identifier.c - src/libtomcrypt/src/pk/asn1/der_encode_octet_string.c - src/libtomcrypt/src/pk/asn1/der_encode_printable_string.c - src/libtomcrypt/src/pk/asn1/der_encode_sequence_ex.c - src/libtomcrypt/src/pk/asn1/der_encode_sequence_multi.c - src/libtomcrypt/src/pk/asn1/der_encode_set.c - src/libtomcrypt/src/pk/asn1/der_encode_setof.c - src/libtomcrypt/src/pk/asn1/der_encode_short_integer.c - src/libtomcrypt/src/pk/asn1/der_encode_utctime.c - src/libtomcrypt/src/pk/asn1/der_encode_utf8_string.c - src/libtomcrypt/src/pk/asn1/der_length_bit_string.c - src/libtomcrypt/src/pk/asn1/der_length_boolean.c - src/libtomcrypt/src/pk/asn1/der_length_ia5_string.c - src/libtomcrypt/src/pk/asn1/der_length_integer.c - src/libtomcrypt/src/pk/asn1/der_length_object_identifier.c - src/libtomcrypt/src/pk/asn1/der_length_octet_string.c - src/libtomcrypt/src/pk/asn1/der_length_printable_string.c - src/libtomcrypt/src/pk/asn1/der_length_sequence.c - src/libtomcrypt/src/pk/asn1/der_length_utctime.c - src/libtomcrypt/src/pk/asn1/der_sequence_free.c - src/libtomcrypt/src/pk/asn1/der_length_utf8_string.c - src/libtomcrypt/src/pk/asn1/der_length_short_integer.c - src/libtomcrypt/src/pk/ecc/ltc_ecc_map.c - src/libtomcrypt/src/pk/ecc/ltc_ecc_mul2add.c - src/libtomcrypt/src/pk/ecc/ltc_ecc_mulmod.c - src/libtomcrypt/src/pk/ecc/ltc_ecc_points.c - src/libtomcrypt/src/pk/ecc/ltc_ecc_projective_add_point.c - src/libtomcrypt/src/pk/ecc/ltc_ecc_projective_dbl_point.c - src/libtomcrypt/src/pk/pkcs1/pkcs_1_mgf1.c - src/libtomcrypt/src/pk/pkcs1/pkcs_1_oaep_decode.c - src/libtomcrypt/src/pk/pkcs1/pkcs_1_pss_decode.c - src/libtomcrypt/src/pk/pkcs1/pkcs_1_pss_encode.c - src/libtomcrypt/src/pk/pkcs1/pkcs_1_v1_5_decode.c - src/libtomcrypt/src/pk/pkcs1/pkcs_1_v1_5_encode.c - src/libtomcrypt/src/pk/rsa/rsa_exptmod.c - src/libtomcrypt/src/pk/rsa/rsa_free.c - src/libtomcrypt/src/pk/rsa/rsa_import.c - src/libtomcrypt/src/pk/rsa/rsa_make_key.c - src/libtomcrypt/src/pk/rsa/rsa_sign_hash.c - src/libtomcrypt/src/pk/rsa/rsa_verify_hash.c -) - -set(TOMMATH_FILES - src/libtommath/bncore.c - src/libtommath/bn_fast_mp_invmod.c - src/libtommath/bn_fast_mp_montgomery_reduce.c - src/libtommath/bn_fast_s_mp_mul_digs.c - src/libtommath/bn_fast_s_mp_mul_high_digs.c - src/libtommath/bn_fast_s_mp_sqr.c - src/libtommath/bn_mp_2expt.c - src/libtommath/bn_mp_abs.c - src/libtommath/bn_mp_add.c - src/libtommath/bn_mp_addmod.c - src/libtommath/bn_mp_add_d.c - src/libtommath/bn_mp_and.c - src/libtommath/bn_mp_clamp.c - src/libtommath/bn_mp_clear.c - src/libtommath/bn_mp_clear_multi.c - src/libtommath/bn_mp_cmp.c - src/libtommath/bn_mp_cmp_d.c - src/libtommath/bn_mp_cmp_mag.c - src/libtommath/bn_mp_cnt_lsb.c - src/libtommath/bn_mp_copy.c - src/libtommath/bn_mp_count_bits.c - src/libtommath/bn_mp_div.c - src/libtommath/bn_mp_div_2.c - src/libtommath/bn_mp_div_2d.c - src/libtommath/bn_mp_div_3.c - src/libtommath/bn_mp_div_d.c - src/libtommath/bn_mp_dr_is_modulus.c - src/libtommath/bn_mp_dr_reduce.c - src/libtommath/bn_mp_dr_setup.c - src/libtommath/bn_mp_exch.c - src/libtommath/bn_mp_exptmod.c - src/libtommath/bn_mp_exptmod_fast.c - src/libtommath/bn_mp_expt_d.c - src/libtommath/bn_mp_exteuclid.c - src/libtommath/bn_mp_fread.c - src/libtommath/bn_mp_fwrite.c - src/libtommath/bn_mp_gcd.c - src/libtommath/bn_mp_get_int.c - src/libtommath/bn_mp_grow.c - src/libtommath/bn_mp_init.c - src/libtommath/bn_mp_init_copy.c - src/libtommath/bn_mp_init_multi.c - src/libtommath/bn_mp_init_set.c - src/libtommath/bn_mp_init_set_int.c - src/libtommath/bn_mp_init_size.c - src/libtommath/bn_mp_invmod.c - src/libtommath/bn_mp_invmod_slow.c - src/libtommath/bn_mp_is_square.c - src/libtommath/bn_mp_jacobi.c - src/libtommath/bn_mp_karatsuba_mul.c - src/libtommath/bn_mp_karatsuba_sqr.c - src/libtommath/bn_mp_lcm.c - src/libtommath/bn_mp_lshd.c - src/libtommath/bn_mp_mod.c - src/libtommath/bn_mp_mod_2d.c - src/libtommath/bn_mp_mod_d.c - src/libtommath/bn_mp_montgomery_calc_normalization.c - src/libtommath/bn_mp_montgomery_reduce.c - src/libtommath/bn_mp_montgomery_setup.c - src/libtommath/bn_mp_mul.c - src/libtommath/bn_mp_mulmod.c - src/libtommath/bn_mp_mul_2.c - src/libtommath/bn_mp_mul_2d.c - src/libtommath/bn_mp_mul_d.c - src/libtommath/bn_mp_neg.c - src/libtommath/bn_mp_n_root.c - src/libtommath/bn_mp_or.c - src/libtommath/bn_mp_prime_fermat.c - src/libtommath/bn_mp_prime_is_divisible.c - src/libtommath/bn_mp_prime_is_prime.c - src/libtommath/bn_mp_prime_miller_rabin.c - src/libtommath/bn_mp_prime_next_prime.c - src/libtommath/bn_mp_prime_rabin_miller_trials.c - src/libtommath/bn_mp_prime_random_ex.c - src/libtommath/bn_mp_radix_size.c - src/libtommath/bn_mp_radix_smap.c - src/libtommath/bn_mp_rand.c - src/libtommath/bn_mp_read_radix.c - src/libtommath/bn_mp_read_signed_bin.c - src/libtommath/bn_mp_read_unsigned_bin.c - src/libtommath/bn_mp_reduce.c - src/libtommath/bn_mp_reduce_2k.c - src/libtommath/bn_mp_reduce_2k_l.c - src/libtommath/bn_mp_reduce_2k_setup.c - src/libtommath/bn_mp_reduce_2k_setup_l.c - src/libtommath/bn_mp_reduce_is_2k.c - src/libtommath/bn_mp_reduce_is_2k_l.c - src/libtommath/bn_mp_reduce_setup.c - src/libtommath/bn_mp_rshd.c - src/libtommath/bn_mp_set.c - src/libtommath/bn_mp_set_int.c - src/libtommath/bn_mp_shrink.c - src/libtommath/bn_mp_signed_bin_size.c - src/libtommath/bn_mp_sqr.c - src/libtommath/bn_mp_sqrmod.c - src/libtommath/bn_mp_sqrt.c - src/libtommath/bn_mp_sub.c - src/libtommath/bn_mp_submod.c - src/libtommath/bn_mp_sub_d.c - src/libtommath/bn_mp_toom_mul.c - src/libtommath/bn_mp_toom_sqr.c - src/libtommath/bn_mp_toradix.c - src/libtommath/bn_mp_toradix_n.c - src/libtommath/bn_mp_to_signed_bin.c - src/libtommath/bn_mp_to_signed_bin_n.c - src/libtommath/bn_mp_to_unsigned_bin.c - src/libtommath/bn_mp_to_unsigned_bin_n.c - src/libtommath/bn_mp_unsigned_bin_size.c - src/libtommath/bn_mp_xor.c - src/libtommath/bn_mp_zero.c - src/libtommath/bn_prime_tab.c - src/libtommath/bn_reverse.c - src/libtommath/bn_s_mp_add.c - src/libtommath/bn_s_mp_exptmod.c - src/libtommath/bn_s_mp_mul_digs.c - src/libtommath/bn_s_mp_mul_high_digs.c - src/libtommath/bn_s_mp_sqr.c - src/libtommath/bn_s_mp_sub.c -) - -set(BZIP2_FILES - src/bzip2/blocksort.c - src/bzip2/bzlib.c - src/bzip2/compress.c - src/bzip2/crctable.c - src/bzip2/decompress.c - src/bzip2/huffman.c - src/bzip2/randtable.c -) - -set(ZLIB_FILES - src/zlib/adler32.c - src/zlib/compress.c - src/zlib/crc32.c - src/zlib/deflate.c - src/zlib/inffast.c - src/zlib/inflate.c - src/zlib/inftrees.c - src/zlib/trees.c - src/zlib/zutil.c -) - -set(TEST_SRC_FILES - test/StormTest.cpp -) - -add_definitions(-D_7ZIP_ST -DBZ_STRICT_ANSI) -set(LINK_LIBS) - -find_package(ZLIB) -if (ZLIB_FOUND AND NOT STORM_USE_BUNDLED_LIBRARIES) - set(LINK_LIBS ${LINK_LIBS} ZLIB::ZLIB) - add_definitions(-D__SYS_ZLIB) -else() - set(SRC_FILES ${SRC_FILES} ${ZLIB_FILES}) -endif() - -find_package(BZip2) -if (BZIP2_FOUND AND NOT STORM_USE_BUNDLED_LIBRARIES) - set(LINK_LIBS ${LINK_LIBS} BZip2::BZip2) - add_definitions(-D__SYS_BZLIB) -else() - set(SRC_FILES ${SRC_FILES} ${BZIP2_FILES}) -endif() - -if(WIN32) - set(SRC_ADDITIONAL_FILES ${TOMCRYPT_FILES} ${TOMMATH_FILES}) - set(LINK_LIBS ${LINK_LIBS} wininet) -else() - option(WITH_LIBTOMCRYPT "Use system LibTomCrypt library" OFF) - if(WITH_LIBTOMCRYPT) - include(FindPkgConfig) - pkg_check_modules(PC_LIBTOMCRYPT libtomcrypt REQUIRED) - find_path(LIBTOMCRYPT_INCLUDE_DIR NAMES tomcrypt.h HINTS ${PC_LIBTOMCRYPT_INCLUDE_DIRS} REQUIRED) - find_library(LIBTOMCRYPT_LIBRARY NAMES tomcrypt HINTS ${PC_LIBTOMCRYPT_LIBRARY_DIRS} REQUIRED) - set(LINK_LIBS ${LINK_LIBS} ${LIBTOMCRYPT_LIBRARY}) - include_directories(${LIBTOMCRYPT_INCLUDE_DIR}) - else() - set(SRC_ADDITIONAL_FILES ${TOMCRYPT_FILES} ${TOMMATH_FILES}) - endif() -endif() - -if(${CMAKE_SYSTEM_NAME} MATCHES "(Free|Net|Open)BSD") - message(STATUS "Using BSD port") - set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -DO_LARGEFILE=0 -Dstat64=stat -Dlstat64=lstat -Dlseek64=lseek -Doff64_t=off_t -Dfstat64=fstat -Dftruncate64=ftruncate") -endif() - -add_library(${LIBRARY_NAME} ${LIB_TYPE} ${SRC_FILES} ${SRC_ADDITIONAL_FILES} ${STORM_DEF_FILES}) -if(WIN32) - set_target_properties(${LIBRARY_NAME} PROPERTIES OUTPUT_NAME "StormLib") -endif() - -target_link_libraries(${LIBRARY_NAME} ${LINK_LIBS}) -target_compile_definitions(${LIBRARY_NAME} INTERFACE STORMLIB_NO_AUTO_LINK) #CMake will take care of the linking -target_include_directories(${LIBRARY_NAME} PUBLIC src/) -set_target_properties(${LIBRARY_NAME} PROPERTIES PUBLIC_HEADER "src/StormLib.h;src/StormPort.h") -if(BUILD_SHARED_LIBS) - message(STATUS "Linking against dependent libraries dynamically") - - if(APPLE) - set_target_properties(${LIBRARY_NAME} PROPERTIES FRAMEWORK true) - set_target_properties(${LIBRARY_NAME} PROPERTIES LINK_FLAGS "-framework Carbon") - endif() - if(UNIX) - SET(VERSION_MAJOR "9") - SET(VERSION_MINOR "22") - SET(VERSION_PATCH "0") - SET(VERSION_STRING "${VERSION_MAJOR}.${VERSION_MINOR}.${VERSION_PATCH}") - set_target_properties(${LIBRARY_NAME} PROPERTIES VERSION "${VERSION_STRING}") - set_target_properties(${LIBRARY_NAME} PROPERTIES SOVERSION "${VERSION_MAJOR}") - endif() -else() - message(STATUS "Linking against dependent libraries statically") -endif() - -if (NOT STORM_SKIP_INSTALL) - install(TARGETS ${LIBRARY_NAME} - RUNTIME DESTINATION bin - LIBRARY DESTINATION lib - ARCHIVE DESTINATION lib - FRAMEWORK DESTINATION /Library/Frameworks - PUBLIC_HEADER DESTINATION include - INCLUDES DESTINATION include) - - #CPack configurtion - SET(CPACK_GENERATOR "DEB" "RPM") - SET(CPACK_PACKAGE_NAME ${PROJECT_NAME}) - SET(CPACK_PACKAGE_DESCRIPTION_SUMMARY "MPQ manipulation library") - SET(CPACK_PACKAGE_VENDOR "Ladislav Zezula") - SET(CPACK_PACKAGE_DESCRIPTION_FILE "${CMAKE_CURRENT_SOURCE_DIR}/README.md") - SET(CPACK_RESOURCE_FILE_LICENSE "${CMAKE_CURRENT_SOURCE_DIR}/LICENSE") - SET(CPACK_PACKAGE_VERSION_MAJOR "${VERSION_MAJOR}") - SET(CPACK_PACKAGE_VERSION_MINOR "${VERSION_MINOR}") - SET(CPACK_PACKAGE_VERSION "${VERSION_MAJOR}.${VERSION_MINOR}") - - #DEB configuration - SET(CPACK_DEBIAN_PACKAGE_SECTION "libs") - SET(CPACK_DEBIAN_PACKAGE_HOMEPAGE "http://www.zezula.net/en/mpq/stormlib.html") - SET(CPACK_DEBIAN_PACKAGE_MAINTAINER "imbacen@gmail.com") - SET(CPACK_DEBIAN_PACKAGE_ARCHITECTURE "amd64") - SET(CPACK_DEBIAN_PACKAGE_DEPENDS "zlib1g,bzip2") - - #RPM configuration - SET(CPACK_RPM_PACKAGE_RELEASE 1) - SET(CPACK_RPM_PACKAGE_LICENSE "${CMAKE_CURRENT_SOURCE_DIR}/LICENSE") - SET(CPACK_RPM_PACKAGE_GROUP "${PROJECT_NAME}") - SET(CPACK_RPM_PACKAGE_URL "http://www.zezula.net/en/mpq/stormlib.html") - SET(CPACK_RPM_PACKAGE_REQUIRES "zlib,bzip2") - - INCLUDE(CPack) -endif() - -if(STORM_BUILD_TESTS) - add_executable(StormLib_test ${TEST_SRC_FILES}) - target_link_libraries(StormLib_test ${LIBRARY_NAME}) - install(TARGETS StormLib_test RUNTIME DESTINATION bin) -endif() - diff --git a/app/jni/src/libultraship/extern/StormLib/Info.plist b/app/jni/src/libultraship/extern/StormLib/Info.plist deleted file mode 100644 index 0e1ae01..0000000 --- a/app/jni/src/libultraship/extern/StormLib/Info.plist +++ /dev/null @@ -1,22 +0,0 @@ - - - - - CFBundleDevelopmentRegion - English - CFBundleExecutable - ${EXECUTABLE_NAME} - CFBundleIdentifier - net.zezula.${PRODUCT_NAME:rfc1034Identifier} - CFBundleName - ${PRODUCT_NAME} - CFBundleInfoDictionaryVersion - 6.0 - CFBundlePackageType - FMWK - CFBundleSignature - ???? - CFBundleVersion - 8.01 - - diff --git a/app/jni/src/libultraship/extern/StormLib/LICENSE b/app/jni/src/libultraship/extern/StormLib/LICENSE deleted file mode 100644 index 2cb432d..0000000 --- a/app/jni/src/libultraship/extern/StormLib/LICENSE +++ /dev/null @@ -1,21 +0,0 @@ -The MIT License (MIT) - -Copyright (c) 1999-2013 Ladislav Zezula - -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. diff --git a/app/jni/src/libultraship/extern/StormLib/Premake5.lua b/app/jni/src/libultraship/extern/StormLib/Premake5.lua deleted file mode 100644 index 957ed36..0000000 --- a/app/jni/src/libultraship/extern/StormLib/Premake5.lua +++ /dev/null @@ -1,132 +0,0 @@ - -solution 'StormLib' - location 'build' - language 'C++' - configurations { 'Debug', 'Release', } - platforms { 'x32', 'x64' } - - targetdir 'bin' - objdir 'bin' - - files { - 'src/**.h', - 'src/**.c', - 'src/**.cpp', - 'doc/*.txt', - } - - removefiles { - 'src/adpcm/*_old.*', - 'src/huffman/*_old.*', - 'src/huffman/huff_patch.*', - 'src/pklib/crc32.c', - 'src/zlib/compress.c', - } - - filter 'configurations:Debug*' - flags { 'Symbols' } - defines { '_DEBUG' } - optimize 'Debug' - - filter 'configurations:Release*' - defines { 'NDEBUG' } - optimize 'Full' - - filter 'system:windows' - links { 'wininet', } - defines { 'WINDOWS', '_WINDOWS' } - - filter { 'system:windows', 'platforms:x32' } - defines { 'WIN32', '_WIN32' } - - filter { 'system:windows', 'platforms:x64' } - defines { 'WIN64', '_WIN64' } - - filter 'system:linux' - defines { '_7ZIP_ST', 'BZ_STRICT_ANSI' } - removefiles { - 'src/lzma/C/LzFindMt.*', - 'src/lzma/C/Threads.*', - } - --------------------------------------------------------------------------------- - -project 'StormLib' - kind 'StaticLib' - - removefiles 'src/SBaseDumpData.cpp' - - configurations { - 'DebugAD', -- Debug Ansi Dynamic - 'DebugAS', -- Debug Ansi Static - 'DebugUD', -- Debug Unicode Dynamic - 'DebugUS', -- Debug Unicode Static - 'ReleaseAD', -- Release Ansi Dynamic - 'ReleaseAS', -- Release Ansi Static - 'ReleaseUD', -- Release Unicode Dynamic' - 'ReleaseUS', -- Release Unicode Static - } - - configmap { - ['Debug'] = 'DebugUS', - ['Release'] = 'ReleaseUS', - } - - filter 'configurations:*S' - flags { 'StaticRuntime' } - - filter { 'configurations:*U*', 'action:vs*' } - flags { 'Unicode' } - - filter { 'configurations:*U*', 'not action:vs*' } - defines { 'UNICODE', '_UNICODE' } - - filter 'DebugAD' - targetsuffix 'DAD' - filter 'ReleaseAD' - targetsuffix 'RAD' - filter 'DebugAS' - targetsuffix 'DAS' - filter 'ReleaseAS' - targetsuffix 'RAS' - filter 'DebugUD' - targetsuffix 'DUD' - filter 'ReleaseUD' - targetsuffix 'RUD' - filter 'DebugUS' - targetsuffix 'DUS' - filter 'ReleaseUS' - targetsuffix 'RUS' - --------------------------------------------------------------------------------- - -project 'StormLib_dll' - kind 'SharedLib' - - targetname 'Stormlib' - - files { - 'stormlib_dll/DllMain.c', - 'stormlib_dll/StormLib.def', - } - - removefiles 'src/SBaseDumpData.cpp' - - filter { 'system:windows', 'action:gmake' } - linkoptions { - '-Xlinker --enable-stdcall-fixup', - '../stormlib_dll/StormLib.def', - } - - filter 'Debug' - targetsuffix '_d' - --------------------------------------------------------------------------------- - -project 'StormLib_test' - kind 'ConsoleApp' - - files { - 'test/StormTest.cpp', - } - diff --git a/app/jni/src/libultraship/extern/StormLib/Publish.bat b/app/jni/src/libultraship/extern/StormLib/Publish.bat deleted file mode 100644 index b5c71fc..0000000 --- a/app/jni/src/libultraship/extern/StormLib/Publish.bat +++ /dev/null @@ -1,25 +0,0 @@ -@echo off -rem This BAT file updates the ZIP file that is to be uploaded to web -rem Only use when both 32-bit and 64-bit are properly compiled - -set STORMLIB_NAME=stormlib-9.00 - -echo Creating %STORMLIB_NAME%.zip ... -cd \Ladik\Appdir -zip.exe -ur9 ..\WWW\web\download\%STORMLIB_NAME%.zip StormLib\doc\* -zip.exe -ur9 ..\WWW\web\download\%STORMLIB_NAME%.zip StormLib\src\* -zip.exe -ur9 ..\WWW\web\download\%STORMLIB_NAME%.zip StormLib\storm_dll\* -zip.exe -ur9 ..\WWW\web\download\%STORMLIB_NAME%.zip StormLib\StormLib.xcodeproj\* -zip.exe -ur9 ..\WWW\web\download\%STORMLIB_NAME%.zip StormLib\stormlib_dll\* -zip.exe -ur9 ..\WWW\web\download\%STORMLIB_NAME%.zip StormLib\test\* -zip.exe -u9 ..\WWW\web\download\%STORMLIB_NAME%.zip StormLib\CMakeLists.txt -zip.exe -u9 ..\WWW\web\download\%STORMLIB_NAME%.zip StormLib\makefile.* -zip.exe -u9 ..\WWW\web\download\%STORMLIB_NAME%.zip StormLib\Info.plist -zip.exe -u9 ..\WWW\web\download\%STORMLIB_NAME%.zip StormLib\*.bat -zip.exe -u9 ..\WWW\web\download\%STORMLIB_NAME%.zip StormLib\*.sln -zip.exe -u9 ..\WWW\web\download\%STORMLIB_NAME%.zip StormLib\*.vcproj -zip.exe -u9 ..\WWW\web\download\%STORMLIB_NAME%.zip StormLib\*.vcxproj -echo. - -echo Press any key to exit ... -pause >nul diff --git a/app/jni/src/libultraship/extern/StormLib/README.md b/app/jni/src/libultraship/extern/StormLib/README.md deleted file mode 100644 index 919b54a..0000000 --- a/app/jni/src/libultraship/extern/StormLib/README.md +++ /dev/null @@ -1,39 +0,0 @@ -# StormLib - -This is official repository for the StomLib library, an open-source project that can work with Blizzard MPQ archives. - -## Installation and basic usage -### Linux -1. Download latest release -2. Install StormLib: -``` -$ cd -$ cmake CMakeLists.txt -$ make -$ make install -``` -3. Include StormLib in your project: `#include ` -4. Make sure you compile your project with `-lstorm -lz -lbz2` - -### Windows (Visual Studio 2008) -1. Download the latest release of StormLib -2. Open the solution file `StormLib_vs08.sln` in Visual Studio 2008 -3. Choose "Build / Batch Build" and select every build of "StormLib" -4. Choose "Rebuild" -5. The result libraries are in `.\bin\Win32` and `.\bin\x64` - -### Windows (Visual Studio 2017 or 2019) -0. Make sure you have SDK 10.0.17134.0 installed -1. Download the latest release of StormLib -2. Open the solution file `StormLib_vs19.sln` in Visual Studio 2017/2019 -3. Choose "Build / Batch Build" and select every build of "StormLib" -4. Choose "Rebuild" -5. The result libraries are in `.\bin\Win32` and `.\bin\x64` - -### Windows (Test Project) -1. Include the main StormLib header: `#include ` -2. Set the correct library directory for StormLibXYZ.lib: - * X: D = Debug, R = Release - * Y: A = ANSI build, U = Unicode build - * Z: S = Using static CRT library, D = Using Dynamic CRT library -3. Rebuild diff --git a/app/jni/src/libultraship/extern/StormLib/StormLib.kdev4 b/app/jni/src/libultraship/extern/StormLib/StormLib.kdev4 deleted file mode 100644 index c9a6ab5..0000000 --- a/app/jni/src/libultraship/extern/StormLib/StormLib.kdev4 +++ /dev/null @@ -1,3 +0,0 @@ -[Project] -Manager=KDevCMakeManager -Name=StormLib diff --git a/app/jni/src/libultraship/extern/StormLib/StormLib.xcodeproj/project.pbxproj b/app/jni/src/libultraship/extern/StormLib/StormLib.xcodeproj/project.pbxproj deleted file mode 100644 index cc77a68..0000000 --- a/app/jni/src/libultraship/extern/StormLib/StormLib.xcodeproj/project.pbxproj +++ /dev/null @@ -1,2104 +0,0 @@ -// !$*UTF8*$! -{ - archiveVersion = 1; - classes = { - }; - objectVersion = 46; - objects = { - -/* Begin PBXBuildFile section */ - 221F6A741168529C0026C852 /* LzmaDec.h in Headers */ = {isa = PBXBuildFile; fileRef = 221F6A721168529C0026C852 /* LzmaDec.h */; }; - 221F6A751168529C0026C852 /* LzmaEnc.h in Headers */ = {isa = PBXBuildFile; fileRef = 221F6A731168529C0026C852 /* LzmaEnc.h */; }; - 221F6A761168529C0026C852 /* LzmaDec.h in Headers */ = {isa = PBXBuildFile; fileRef = 221F6A721168529C0026C852 /* LzmaDec.h */; }; - 221F6A771168529C0026C852 /* LzmaEnc.h in Headers */ = {isa = PBXBuildFile; fileRef = 221F6A731168529C0026C852 /* LzmaEnc.h */; }; - 221F6A7B116852AA0026C852 /* LzmaEnc.c in Sources */ = {isa = PBXBuildFile; fileRef = 221F6A7A116852AA0026C852 /* LzmaEnc.c */; }; - 221F6A7C116852AA0026C852 /* LzmaEnc.c in Sources */ = {isa = PBXBuildFile; fileRef = 221F6A7A116852AA0026C852 /* LzmaEnc.c */; }; - 221F6A7E116852B20026C852 /* LzmaDec.c in Sources */ = {isa = PBXBuildFile; fileRef = 221F6A7D116852B20026C852 /* LzmaDec.c */; }; - 221F6A7F116852B20026C852 /* LzmaDec.c in Sources */ = {isa = PBXBuildFile; fileRef = 221F6A7D116852B20026C852 /* LzmaDec.c */; }; - 221F6AB51168545B0026C852 /* LzFind.c in Sources */ = {isa = PBXBuildFile; fileRef = 221F6AB31168545B0026C852 /* LzFind.c */; }; - 221F6AB61168545B0026C852 /* LzFind.h in Headers */ = {isa = PBXBuildFile; fileRef = 221F6AB41168545B0026C852 /* LzFind.h */; }; - 221F6AB71168545B0026C852 /* LzFind.c in Sources */ = {isa = PBXBuildFile; fileRef = 221F6AB31168545B0026C852 /* LzFind.c */; }; - 221F6AB81168545B0026C852 /* LzFind.h in Headers */ = {isa = PBXBuildFile; fileRef = 221F6AB41168545B0026C852 /* LzFind.h */; }; - 221F6ABA116854730026C852 /* LzHash.h in Headers */ = {isa = PBXBuildFile; fileRef = 221F6AB9116854730026C852 /* LzHash.h */; }; - 221F6ABB116854730026C852 /* LzHash.h in Headers */ = {isa = PBXBuildFile; fileRef = 221F6AB9116854730026C852 /* LzHash.h */; }; - 221F6ABD116854870026C852 /* Types.h in Headers */ = {isa = PBXBuildFile; fileRef = 221F6ABC116854870026C852 /* Types.h */; }; - 221F6ABE116854870026C852 /* Types.h in Headers */ = {isa = PBXBuildFile; fileRef = 221F6ABC116854870026C852 /* Types.h */; }; - 2254917B11948CE70044424D /* crypt_ltc_mp_descriptor.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9184811933FCF0083AC69 /* crypt_ltc_mp_descriptor.c */; settings = {COMPILER_FLAGS = "-fno-common"; }; }; - 225530DB1056BC7900FA646A /* huff.h in Headers */ = {isa = PBXBuildFile; fileRef = 32ED009D0D03542A00AB0B4E /* huff.h */; }; - 225530DE1056BC7900FA646A /* pklib.h in Headers */ = {isa = PBXBuildFile; fileRef = 32ED00A80D03542A00AB0B4E /* pklib.h */; }; - 225530DF1056BC7900FA646A /* StormCommon.h in Headers */ = {isa = PBXBuildFile; fileRef = 32ED00AB0D03542A00AB0B4E /* StormCommon.h */; }; - 225530E01056BC7900FA646A /* StormLib.h in Headers */ = {isa = PBXBuildFile; fileRef = 32ED00B60D03542A00AB0B4E /* StormLib.h */; settings = {ATTRIBUTES = (Public, ); }; }; - 225530E11056BC7900FA646A /* StormPort.h in Headers */ = {isa = PBXBuildFile; fileRef = 32ED00B70D03542A00AB0B4E /* StormPort.h */; settings = {ATTRIBUTES = (Public, ); }; }; - 225530E31056BC8700FA646A /* huff.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 32ED009C0D03542A00AB0B4E /* huff.cpp */; }; - 225530E61056BC8700FA646A /* explode.c in Sources */ = {isa = PBXBuildFile; fileRef = 32ED00A60D03542A00AB0B4E /* explode.c */; }; - 225530E71056BC8700FA646A /* implode.c in Sources */ = {isa = PBXBuildFile; fileRef = 32ED00A70D03542A00AB0B4E /* implode.c */; }; - 225530E81056BC8700FA646A /* SFileAttributes.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 32ED00A90D03542A00AB0B4E /* SFileAttributes.cpp */; }; - 225530E91056BC8700FA646A /* SBaseCommon.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 32ED00AA0D03542A00AB0B4E /* SBaseCommon.cpp */; }; - 225530EA1056BC8700FA646A /* SCompression.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 32ED00AC0D03542A00AB0B4E /* SCompression.cpp */; }; - 225530EB1056BC8700FA646A /* SFileCompactArchive.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 32ED00AD0D03542A00AB0B4E /* SFileCompactArchive.cpp */; }; - 225530EC1056BC8700FA646A /* SFileCreateArchive.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 32ED00AE0D03542A00AB0B4E /* SFileCreateArchive.cpp */; }; - 225530ED1056BC8700FA646A /* SFileExtractFile.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 32ED00AF0D03542A00AB0B4E /* SFileExtractFile.cpp */; }; - 225530EE1056BC8700FA646A /* SFileFindFile.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 32ED00B00D03542A00AB0B4E /* SFileFindFile.cpp */; }; - 225530EF1056BC8700FA646A /* SFileOpenArchive.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 32ED00B10D03542A00AB0B4E /* SFileOpenArchive.cpp */; }; - 225530F01056BC8700FA646A /* SFileOpenFileEx.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 32ED00B20D03542A00AB0B4E /* SFileOpenFileEx.cpp */; }; - 225530F11056BC8700FA646A /* SFileReadFile.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 32ED00B30D03542A00AB0B4E /* SFileReadFile.cpp */; }; - 225530F21056BC8700FA646A /* SFileListFile.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 32ED00B40D03542A00AB0B4E /* SFileListFile.cpp */; }; - 225C734D1257CCC70009E8DA /* lookup.h in Headers */ = {isa = PBXBuildFile; fileRef = 225C734B1257CCC70009E8DA /* lookup.h */; }; - 225C734F1257CCC70009E8DA /* lookup.h in Headers */ = {isa = PBXBuildFile; fileRef = 225C734B1257CCC70009E8DA /* lookup.h */; }; - 225C73501257CCC70009E8DA /* lookup3.c in Sources */ = {isa = PBXBuildFile; fileRef = 225C734C1257CCC70009E8DA /* lookup3.c */; }; - 225C73541257CD0C0009E8DA /* SBaseFileTable.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 225C73531257CD0C0009E8DA /* SBaseFileTable.cpp */; }; - 225C73551257CD0C0009E8DA /* SBaseFileTable.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 225C73531257CD0C0009E8DA /* SBaseFileTable.cpp */; }; - 225C735A1257CD1F0009E8DA /* lookup3.c in Sources */ = {isa = PBXBuildFile; fileRef = 225C734C1257CCC70009E8DA /* lookup3.c */; }; - 225FAC9C0E53BAA100DA2CAE /* huff.h in Headers */ = {isa = PBXBuildFile; fileRef = 32ED009D0D03542A00AB0B4E /* huff.h */; }; - 225FAC9F0E53BAA100DA2CAE /* pklib.h in Headers */ = {isa = PBXBuildFile; fileRef = 32ED00A80D03542A00AB0B4E /* pklib.h */; }; - 225FACA00E53BAA100DA2CAE /* StormCommon.h in Headers */ = {isa = PBXBuildFile; fileRef = 32ED00AB0D03542A00AB0B4E /* StormCommon.h */; }; - 225FACA10E53BAA100DA2CAE /* StormLib.h in Headers */ = {isa = PBXBuildFile; fileRef = 32ED00B60D03542A00AB0B4E /* StormLib.h */; settings = {ATTRIBUTES = (Public, ); }; }; - 225FACA20E53BAA100DA2CAE /* StormPort.h in Headers */ = {isa = PBXBuildFile; fileRef = 32ED00B70D03542A00AB0B4E /* StormPort.h */; settings = {ATTRIBUTES = (Public, ); }; }; - 225FACA50E53BAB400DA2CAE /* huff.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 32ED009C0D03542A00AB0B4E /* huff.cpp */; }; - 225FACA90E53BAB400DA2CAE /* explode.c in Sources */ = {isa = PBXBuildFile; fileRef = 32ED00A60D03542A00AB0B4E /* explode.c */; }; - 225FACAA0E53BAB400DA2CAE /* implode.c in Sources */ = {isa = PBXBuildFile; fileRef = 32ED00A70D03542A00AB0B4E /* implode.c */; }; - 225FACAB0E53BAB400DA2CAE /* SFileAttributes.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 32ED00A90D03542A00AB0B4E /* SFileAttributes.cpp */; }; - 225FACAC0E53BAB400DA2CAE /* SBaseCommon.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 32ED00AA0D03542A00AB0B4E /* SBaseCommon.cpp */; }; - 225FACAD0E53BAB400DA2CAE /* SCompression.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 32ED00AC0D03542A00AB0B4E /* SCompression.cpp */; }; - 225FACAE0E53BAB400DA2CAE /* SFileCompactArchive.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 32ED00AD0D03542A00AB0B4E /* SFileCompactArchive.cpp */; }; - 225FACAF0E53BAB400DA2CAE /* SFileCreateArchive.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 32ED00AE0D03542A00AB0B4E /* SFileCreateArchive.cpp */; }; - 225FACB00E53BAB400DA2CAE /* SFileExtractFile.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 32ED00AF0D03542A00AB0B4E /* SFileExtractFile.cpp */; }; - 225FACB10E53BAB400DA2CAE /* SFileFindFile.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 32ED00B00D03542A00AB0B4E /* SFileFindFile.cpp */; }; - 225FACB20E53BAB400DA2CAE /* SFileOpenArchive.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 32ED00B10D03542A00AB0B4E /* SFileOpenArchive.cpp */; }; - 225FACB30E53BAB400DA2CAE /* SFileOpenFileEx.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 32ED00B20D03542A00AB0B4E /* SFileOpenFileEx.cpp */; }; - 225FACB40E53BAB400DA2CAE /* SFileReadFile.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 32ED00B30D03542A00AB0B4E /* SFileReadFile.cpp */; }; - 225FACB50E53BAB400DA2CAE /* SFileListFile.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 32ED00B40D03542A00AB0B4E /* SFileListFile.cpp */; }; - 225FADD40E53C06600DA2CAE /* libbz2.dylib in Frameworks */ = {isa = PBXBuildFile; fileRef = 32D20A8A0CF3902D00230E7A /* libbz2.dylib */; settings = {ATTRIBUTES = (Required, ); }; }; - 225FADD50E53C06600DA2CAE /* libz.dylib in Frameworks */ = {isa = PBXBuildFile; fileRef = 32D20A8B0CF3902D00230E7A /* libz.dylib */; settings = {ATTRIBUTES = (Required, ); }; }; - 226C7CA71857DE9400AB689C /* SBaseDumpData.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 226C7CA61857DE9400AB689C /* SBaseDumpData.cpp */; }; - 226C7CA81857DE9400AB689C /* SBaseDumpData.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 226C7CA61857DE9400AB689C /* SBaseDumpData.cpp */; }; - 226C7CAA1857DEAC00AB689C /* SBaseSubTypes.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 226C7CA91857DEAC00AB689C /* SBaseSubTypes.cpp */; }; - 226C7CAB1857DEAC00AB689C /* SBaseSubTypes.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 226C7CA91857DEAC00AB689C /* SBaseSubTypes.cpp */; }; - 226C7CAD1857DEEB00AB689C /* SFileGetFileInfo.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 226C7CAC1857DEEB00AB689C /* SFileGetFileInfo.cpp */; }; - 226C7CAE1857DEEB00AB689C /* SFileGetFileInfo.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 226C7CAC1857DEEB00AB689C /* SFileGetFileInfo.cpp */; }; - 228B538411BF7D0D001A58DA /* FileStream.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 228B538311BF7D0D001A58DA /* FileStream.cpp */; }; - 228B538511BF7D0D001A58DA /* FileStream.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 228B538311BF7D0D001A58DA /* FileStream.cpp */; }; - 22954AD211D463AB0064B264 /* Test.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 2295488911D45A820064B264 /* Test.cpp */; }; - 22954AD311D463B50064B264 /* libStormLib.a in Frameworks */ = {isa = PBXBuildFile; fileRef = 225530D41056BAC800FA646A /* libStormLib.a */; }; - 22954AD611D463BE0064B264 /* libbz2.dylib in Frameworks */ = {isa = PBXBuildFile; fileRef = 32D20A8A0CF3902D00230E7A /* libbz2.dylib */; }; - 22954AD711D463BE0064B264 /* libz.dylib in Frameworks */ = {isa = PBXBuildFile; fileRef = 32D20A8B0CF3902D00230E7A /* libz.dylib */; }; - 2299D9D71167EFA8005C19BF /* adpcm.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 2299D9D51167EFA8005C19BF /* adpcm.cpp */; }; - 2299D9D81167EFA8005C19BF /* adpcm.h in Headers */ = {isa = PBXBuildFile; fileRef = 2299D9D61167EFA8005C19BF /* adpcm.h */; }; - 2299D9D91167EFA8005C19BF /* adpcm.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 2299D9D51167EFA8005C19BF /* adpcm.cpp */; }; - 2299D9DA1167EFA8005C19BF /* adpcm.h in Headers */ = {isa = PBXBuildFile; fileRef = 2299D9D61167EFA8005C19BF /* adpcm.h */; }; - 2299D9DE1167EFC6005C19BF /* sparse.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 2299D9DC1167EFC6005C19BF /* sparse.cpp */; }; - 2299D9DF1167EFC6005C19BF /* sparse.h in Headers */ = {isa = PBXBuildFile; fileRef = 2299D9DD1167EFC6005C19BF /* sparse.h */; }; - 2299D9E01167EFC6005C19BF /* sparse.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 2299D9DC1167EFC6005C19BF /* sparse.cpp */; }; - 2299D9E11167EFC6005C19BF /* sparse.h in Headers */ = {isa = PBXBuildFile; fileRef = 2299D9DD1167EFC6005C19BF /* sparse.h */; }; - 2299DA4E1167FD16005C19BF /* SFileAddFile.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 2299DA4D1167FD16005C19BF /* SFileAddFile.cpp */; }; - 2299DA4F1167FD16005C19BF /* SFileAddFile.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 2299DA4D1167FD16005C19BF /* SFileAddFile.cpp */; }; - 22AEA122123125D800359B16 /* SFilePatchArchives.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 22AEA121123125D800359B16 /* SFilePatchArchives.cpp */; }; - 22AEA123123125D800359B16 /* SFilePatchArchives.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 22AEA121123125D800359B16 /* SFilePatchArchives.cpp */; }; - 22C9187D11933FCF0083AC69 /* hash_memory.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9182B11933FCF0083AC69 /* hash_memory.c */; }; - 22C9187E11933FCF0083AC69 /* md5.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9182C11933FCF0083AC69 /* md5.c */; }; - 22C9187F11933FCF0083AC69 /* sha1.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9182D11933FCF0083AC69 /* sha1.c */; }; - 22C9188011933FCF0083AC69 /* tomcrypt.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C9182F11933FCF0083AC69 /* tomcrypt.h */; }; - 22C9188111933FCF0083AC69 /* tomcrypt_argchk.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C9183011933FCF0083AC69 /* tomcrypt_argchk.h */; }; - 22C9188211933FCF0083AC69 /* tomcrypt_cfg.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C9183111933FCF0083AC69 /* tomcrypt_cfg.h */; }; - 22C9188311933FCF0083AC69 /* tomcrypt_cipher.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C9183211933FCF0083AC69 /* tomcrypt_cipher.h */; }; - 22C9188411933FCF0083AC69 /* tomcrypt_custom.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C9183311933FCF0083AC69 /* tomcrypt_custom.h */; }; - 22C9188511933FCF0083AC69 /* tomcrypt_hash.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C9183411933FCF0083AC69 /* tomcrypt_hash.h */; }; - 22C9188611933FCF0083AC69 /* tomcrypt_mac.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C9183511933FCF0083AC69 /* tomcrypt_mac.h */; }; - 22C9188711933FCF0083AC69 /* tomcrypt_macros.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C9183611933FCF0083AC69 /* tomcrypt_macros.h */; }; - 22C9188811933FCF0083AC69 /* tomcrypt_math.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C9183711933FCF0083AC69 /* tomcrypt_math.h */; }; - 22C9188911933FCF0083AC69 /* tomcrypt_misc.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C9183811933FCF0083AC69 /* tomcrypt_misc.h */; }; - 22C9188A11933FCF0083AC69 /* tomcrypt_pk.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C9183911933FCF0083AC69 /* tomcrypt_pk.h */; }; - 22C9188B11933FCF0083AC69 /* tomcrypt_pkcs.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C9183A11933FCF0083AC69 /* tomcrypt_pkcs.h */; }; - 22C9188C11933FCF0083AC69 /* tomcrypt_prng.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C9183B11933FCF0083AC69 /* tomcrypt_prng.h */; }; - 22C9188D11933FCF0083AC69 /* ltm_desc.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9183D11933FCF0083AC69 /* ltm_desc.c */; }; - 22C9188E11933FCF0083AC69 /* multi.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9183E11933FCF0083AC69 /* multi.c */; }; - 22C9188F11933FCF0083AC69 /* rand_prime.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9183F11933FCF0083AC69 /* rand_prime.c */; }; - 22C9189011933FCF0083AC69 /* base64_decode.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9184111933FCF0083AC69 /* base64_decode.c */; }; - 22C9189111933FCF0083AC69 /* crypt_argchk.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9184211933FCF0083AC69 /* crypt_argchk.c */; }; - 22C9189211933FCF0083AC69 /* crypt_find_hash.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9184311933FCF0083AC69 /* crypt_find_hash.c */; }; - 22C9189311933FCF0083AC69 /* crypt_find_prng.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9184411933FCF0083AC69 /* crypt_find_prng.c */; }; - 22C9189411933FCF0083AC69 /* crypt_hash_descriptor.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9184511933FCF0083AC69 /* crypt_hash_descriptor.c */; }; - 22C9189511933FCF0083AC69 /* crypt_hash_is_valid.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9184611933FCF0083AC69 /* crypt_hash_is_valid.c */; }; - 22C9189611933FCF0083AC69 /* crypt_libc.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9184711933FCF0083AC69 /* crypt_libc.c */; }; - 22C9189811933FCF0083AC69 /* crypt_prng_descriptor.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9184911933FCF0083AC69 /* crypt_prng_descriptor.c */; }; - 22C9189911933FCF0083AC69 /* crypt_prng_is_valid.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9184A11933FCF0083AC69 /* crypt_prng_is_valid.c */; }; - 22C9189A11933FCF0083AC69 /* crypt_register_hash.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9184B11933FCF0083AC69 /* crypt_register_hash.c */; }; - 22C9189B11933FCF0083AC69 /* crypt_register_prng.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9184C11933FCF0083AC69 /* crypt_register_prng.c */; }; - 22C9189C11933FCF0083AC69 /* zeromem.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9184D11933FCF0083AC69 /* zeromem.c */; }; - 22C9189D11933FCF0083AC69 /* der_decode_bit_string.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185011933FCF0083AC69 /* der_decode_bit_string.c */; }; - 22C9189E11933FCF0083AC69 /* der_decode_boolean.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185111933FCF0083AC69 /* der_decode_boolean.c */; }; - 22C9189F11933FCF0083AC69 /* der_decode_choice.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185211933FCF0083AC69 /* der_decode_choice.c */; }; - 22C918A011933FCF0083AC69 /* der_decode_ia5_string.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185311933FCF0083AC69 /* der_decode_ia5_string.c */; }; - 22C918A111933FCF0083AC69 /* der_decode_integer.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185411933FCF0083AC69 /* der_decode_integer.c */; }; - 22C918A211933FCF0083AC69 /* der_decode_object_identifier.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185511933FCF0083AC69 /* der_decode_object_identifier.c */; }; - 22C918A311933FCF0083AC69 /* der_decode_octet_string.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185611933FCF0083AC69 /* der_decode_octet_string.c */; }; - 22C918A411933FCF0083AC69 /* der_decode_printable_string.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185711933FCF0083AC69 /* der_decode_printable_string.c */; }; - 22C918A511933FCF0083AC69 /* der_decode_sequence_ex.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185811933FCF0083AC69 /* der_decode_sequence_ex.c */; }; - 22C918A611933FCF0083AC69 /* der_decode_sequence_flexi.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185911933FCF0083AC69 /* der_decode_sequence_flexi.c */; }; - 22C918A711933FCF0083AC69 /* der_decode_sequence_multi.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185A11933FCF0083AC69 /* der_decode_sequence_multi.c */; }; - 22C918A811933FCF0083AC69 /* der_decode_short_integer.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185B11933FCF0083AC69 /* der_decode_short_integer.c */; }; - 22C918A911933FCF0083AC69 /* der_decode_utctime.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185C11933FCF0083AC69 /* der_decode_utctime.c */; }; - 22C918AA11933FCF0083AC69 /* der_decode_utf8_string.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185D11933FCF0083AC69 /* der_decode_utf8_string.c */; }; - 22C918AB11933FCF0083AC69 /* der_length_bit_string.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185E11933FCF0083AC69 /* der_length_bit_string.c */; }; - 22C918AC11933FCF0083AC69 /* der_length_boolean.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185F11933FCF0083AC69 /* der_length_boolean.c */; }; - 22C918AD11933FCF0083AC69 /* der_length_ia5_string.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9186011933FCF0083AC69 /* der_length_ia5_string.c */; }; - 22C918AE11933FCF0083AC69 /* der_length_integer.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9186111933FCF0083AC69 /* der_length_integer.c */; }; - 22C918AF11933FCF0083AC69 /* der_length_object_identifier.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9186211933FCF0083AC69 /* der_length_object_identifier.c */; }; - 22C918B011933FCF0083AC69 /* der_length_octet_string.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9186311933FCF0083AC69 /* der_length_octet_string.c */; }; - 22C918B111933FCF0083AC69 /* der_length_printable_string.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9186411933FCF0083AC69 /* der_length_printable_string.c */; }; - 22C918B211933FCF0083AC69 /* der_length_sequence.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9186511933FCF0083AC69 /* der_length_sequence.c */; }; - 22C918B311933FCF0083AC69 /* der_length_short_integer.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9186611933FCF0083AC69 /* der_length_short_integer.c */; }; - 22C918B411933FCF0083AC69 /* der_length_utctime.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9186711933FCF0083AC69 /* der_length_utctime.c */; }; - 22C918B511933FCF0083AC69 /* der_length_utf8_string.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9186811933FCF0083AC69 /* der_length_utf8_string.c */; }; - 22C918B611933FCF0083AC69 /* der_sequence_free.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9186911933FCF0083AC69 /* der_sequence_free.c */; }; - 22C918B711933FCF0083AC69 /* ltc_ecc_map.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9186B11933FCF0083AC69 /* ltc_ecc_map.c */; }; - 22C918B811933FCF0083AC69 /* ltc_ecc_mul2add.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9186C11933FCF0083AC69 /* ltc_ecc_mul2add.c */; }; - 22C918B911933FCF0083AC69 /* ltc_ecc_mulmod.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9186D11933FCF0083AC69 /* ltc_ecc_mulmod.c */; }; - 22C918BA11933FCF0083AC69 /* ltc_ecc_points.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9186E11933FCF0083AC69 /* ltc_ecc_points.c */; }; - 22C918BB11933FCF0083AC69 /* ltc_ecc_projective_add_point.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9186F11933FCF0083AC69 /* ltc_ecc_projective_add_point.c */; }; - 22C918BC11933FCF0083AC69 /* ltc_ecc_projective_dbl_point.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9187011933FCF0083AC69 /* ltc_ecc_projective_dbl_point.c */; }; - 22C918BD11933FCF0083AC69 /* pkcs_1_mgf1.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9187211933FCF0083AC69 /* pkcs_1_mgf1.c */; }; - 22C918BE11933FCF0083AC69 /* pkcs_1_oaep_decode.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9187311933FCF0083AC69 /* pkcs_1_oaep_decode.c */; }; - 22C918BF11933FCF0083AC69 /* pkcs_1_pss_decode.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9187411933FCF0083AC69 /* pkcs_1_pss_decode.c */; }; - 22C918C011933FCF0083AC69 /* pkcs_1_v1_5_decode.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9187511933FCF0083AC69 /* pkcs_1_v1_5_decode.c */; }; - 22C918C111933FCF0083AC69 /* rsa_exptmod.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9187711933FCF0083AC69 /* rsa_exptmod.c */; }; - 22C918C211933FCF0083AC69 /* rsa_free.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9187811933FCF0083AC69 /* rsa_free.c */; }; - 22C918C311933FCF0083AC69 /* rsa_import.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9187911933FCF0083AC69 /* rsa_import.c */; }; - 22C918C411933FCF0083AC69 /* rsa_make_key.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9187A11933FCF0083AC69 /* rsa_make_key.c */; }; - 22C918C511933FCF0083AC69 /* rsa_verify_hash.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9187B11933FCF0083AC69 /* rsa_verify_hash.c */; }; - 22C918C611933FCF0083AC69 /* rsa_verify_simple.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9187C11933FCF0083AC69 /* rsa_verify_simple.c */; }; - 22C918C711933FCF0083AC69 /* hash_memory.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9182B11933FCF0083AC69 /* hash_memory.c */; }; - 22C918C811933FCF0083AC69 /* md5.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9182C11933FCF0083AC69 /* md5.c */; }; - 22C918C911933FCF0083AC69 /* sha1.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9182D11933FCF0083AC69 /* sha1.c */; }; - 22C918CA11933FCF0083AC69 /* tomcrypt.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C9182F11933FCF0083AC69 /* tomcrypt.h */; }; - 22C918CB11933FCF0083AC69 /* tomcrypt_argchk.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C9183011933FCF0083AC69 /* tomcrypt_argchk.h */; }; - 22C918CC11933FCF0083AC69 /* tomcrypt_cfg.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C9183111933FCF0083AC69 /* tomcrypt_cfg.h */; }; - 22C918CD11933FCF0083AC69 /* tomcrypt_cipher.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C9183211933FCF0083AC69 /* tomcrypt_cipher.h */; }; - 22C918CE11933FCF0083AC69 /* tomcrypt_custom.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C9183311933FCF0083AC69 /* tomcrypt_custom.h */; }; - 22C918CF11933FCF0083AC69 /* tomcrypt_hash.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C9183411933FCF0083AC69 /* tomcrypt_hash.h */; }; - 22C918D011933FCF0083AC69 /* tomcrypt_mac.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C9183511933FCF0083AC69 /* tomcrypt_mac.h */; }; - 22C918D111933FCF0083AC69 /* tomcrypt_macros.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C9183611933FCF0083AC69 /* tomcrypt_macros.h */; }; - 22C918D211933FCF0083AC69 /* tomcrypt_math.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C9183711933FCF0083AC69 /* tomcrypt_math.h */; }; - 22C918D311933FCF0083AC69 /* tomcrypt_misc.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C9183811933FCF0083AC69 /* tomcrypt_misc.h */; }; - 22C918D411933FCF0083AC69 /* tomcrypt_pk.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C9183911933FCF0083AC69 /* tomcrypt_pk.h */; }; - 22C918D511933FCF0083AC69 /* tomcrypt_pkcs.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C9183A11933FCF0083AC69 /* tomcrypt_pkcs.h */; }; - 22C918D611933FCF0083AC69 /* tomcrypt_prng.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C9183B11933FCF0083AC69 /* tomcrypt_prng.h */; }; - 22C918D711933FCF0083AC69 /* ltm_desc.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9183D11933FCF0083AC69 /* ltm_desc.c */; }; - 22C918D811933FCF0083AC69 /* multi.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9183E11933FCF0083AC69 /* multi.c */; }; - 22C918D911933FCF0083AC69 /* rand_prime.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9183F11933FCF0083AC69 /* rand_prime.c */; }; - 22C918DA11933FCF0083AC69 /* base64_decode.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9184111933FCF0083AC69 /* base64_decode.c */; }; - 22C918DB11933FCF0083AC69 /* crypt_argchk.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9184211933FCF0083AC69 /* crypt_argchk.c */; }; - 22C918DC11933FCF0083AC69 /* crypt_find_hash.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9184311933FCF0083AC69 /* crypt_find_hash.c */; }; - 22C918DD11933FCF0083AC69 /* crypt_find_prng.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9184411933FCF0083AC69 /* crypt_find_prng.c */; }; - 22C918DE11933FCF0083AC69 /* crypt_hash_descriptor.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9184511933FCF0083AC69 /* crypt_hash_descriptor.c */; }; - 22C918DF11933FCF0083AC69 /* crypt_hash_is_valid.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9184611933FCF0083AC69 /* crypt_hash_is_valid.c */; }; - 22C918E011933FCF0083AC69 /* crypt_libc.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9184711933FCF0083AC69 /* crypt_libc.c */; }; - 22C918E111933FCF0083AC69 /* crypt_ltc_mp_descriptor.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9184811933FCF0083AC69 /* crypt_ltc_mp_descriptor.c */; }; - 22C918E211933FCF0083AC69 /* crypt_prng_descriptor.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9184911933FCF0083AC69 /* crypt_prng_descriptor.c */; }; - 22C918E311933FCF0083AC69 /* crypt_prng_is_valid.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9184A11933FCF0083AC69 /* crypt_prng_is_valid.c */; }; - 22C918E411933FCF0083AC69 /* crypt_register_hash.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9184B11933FCF0083AC69 /* crypt_register_hash.c */; }; - 22C918E511933FCF0083AC69 /* crypt_register_prng.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9184C11933FCF0083AC69 /* crypt_register_prng.c */; }; - 22C918E611933FCF0083AC69 /* zeromem.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9184D11933FCF0083AC69 /* zeromem.c */; }; - 22C918E711933FCF0083AC69 /* der_decode_bit_string.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185011933FCF0083AC69 /* der_decode_bit_string.c */; }; - 22C918E811933FCF0083AC69 /* der_decode_boolean.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185111933FCF0083AC69 /* der_decode_boolean.c */; }; - 22C918E911933FCF0083AC69 /* der_decode_choice.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185211933FCF0083AC69 /* der_decode_choice.c */; }; - 22C918EA11933FCF0083AC69 /* der_decode_ia5_string.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185311933FCF0083AC69 /* der_decode_ia5_string.c */; }; - 22C918EB11933FCF0083AC69 /* der_decode_integer.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185411933FCF0083AC69 /* der_decode_integer.c */; }; - 22C918EC11933FCF0083AC69 /* der_decode_object_identifier.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185511933FCF0083AC69 /* der_decode_object_identifier.c */; }; - 22C918ED11933FCF0083AC69 /* der_decode_octet_string.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185611933FCF0083AC69 /* der_decode_octet_string.c */; }; - 22C918EE11933FCF0083AC69 /* der_decode_printable_string.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185711933FCF0083AC69 /* der_decode_printable_string.c */; }; - 22C918EF11933FCF0083AC69 /* der_decode_sequence_ex.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185811933FCF0083AC69 /* der_decode_sequence_ex.c */; }; - 22C918F011933FCF0083AC69 /* der_decode_sequence_flexi.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185911933FCF0083AC69 /* der_decode_sequence_flexi.c */; }; - 22C918F111933FCF0083AC69 /* der_decode_sequence_multi.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185A11933FCF0083AC69 /* der_decode_sequence_multi.c */; }; - 22C918F211933FCF0083AC69 /* der_decode_short_integer.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185B11933FCF0083AC69 /* der_decode_short_integer.c */; }; - 22C918F311933FCF0083AC69 /* der_decode_utctime.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185C11933FCF0083AC69 /* der_decode_utctime.c */; }; - 22C918F411933FCF0083AC69 /* der_decode_utf8_string.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185D11933FCF0083AC69 /* der_decode_utf8_string.c */; }; - 22C918F511933FCF0083AC69 /* der_length_bit_string.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185E11933FCF0083AC69 /* der_length_bit_string.c */; }; - 22C918F611933FCF0083AC69 /* der_length_boolean.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9185F11933FCF0083AC69 /* der_length_boolean.c */; }; - 22C918F711933FCF0083AC69 /* der_length_ia5_string.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9186011933FCF0083AC69 /* der_length_ia5_string.c */; }; - 22C918F811933FCF0083AC69 /* der_length_integer.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9186111933FCF0083AC69 /* der_length_integer.c */; }; - 22C918F911933FCF0083AC69 /* der_length_object_identifier.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9186211933FCF0083AC69 /* der_length_object_identifier.c */; }; - 22C918FA11933FCF0083AC69 /* der_length_octet_string.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9186311933FCF0083AC69 /* der_length_octet_string.c */; }; - 22C918FB11933FCF0083AC69 /* der_length_printable_string.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9186411933FCF0083AC69 /* der_length_printable_string.c */; }; - 22C918FC11933FCF0083AC69 /* der_length_sequence.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9186511933FCF0083AC69 /* der_length_sequence.c */; }; - 22C918FD11933FCF0083AC69 /* der_length_short_integer.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9186611933FCF0083AC69 /* der_length_short_integer.c */; }; - 22C918FE11933FCF0083AC69 /* der_length_utctime.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9186711933FCF0083AC69 /* der_length_utctime.c */; }; - 22C918FF11933FCF0083AC69 /* der_length_utf8_string.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9186811933FCF0083AC69 /* der_length_utf8_string.c */; }; - 22C9190011933FCF0083AC69 /* der_sequence_free.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9186911933FCF0083AC69 /* der_sequence_free.c */; }; - 22C9190111933FCF0083AC69 /* ltc_ecc_map.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9186B11933FCF0083AC69 /* ltc_ecc_map.c */; }; - 22C9190211933FCF0083AC69 /* ltc_ecc_mul2add.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9186C11933FCF0083AC69 /* ltc_ecc_mul2add.c */; }; - 22C9190311933FCF0083AC69 /* ltc_ecc_mulmod.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9186D11933FCF0083AC69 /* ltc_ecc_mulmod.c */; }; - 22C9190411933FCF0083AC69 /* ltc_ecc_points.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9186E11933FCF0083AC69 /* ltc_ecc_points.c */; }; - 22C9190511933FCF0083AC69 /* ltc_ecc_projective_add_point.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9186F11933FCF0083AC69 /* ltc_ecc_projective_add_point.c */; }; - 22C9190611933FCF0083AC69 /* ltc_ecc_projective_dbl_point.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9187011933FCF0083AC69 /* ltc_ecc_projective_dbl_point.c */; }; - 22C9190711933FCF0083AC69 /* pkcs_1_mgf1.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9187211933FCF0083AC69 /* pkcs_1_mgf1.c */; }; - 22C9190811933FCF0083AC69 /* pkcs_1_oaep_decode.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9187311933FCF0083AC69 /* pkcs_1_oaep_decode.c */; }; - 22C9190911933FCF0083AC69 /* pkcs_1_pss_decode.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9187411933FCF0083AC69 /* pkcs_1_pss_decode.c */; }; - 22C9190A11933FCF0083AC69 /* pkcs_1_v1_5_decode.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9187511933FCF0083AC69 /* pkcs_1_v1_5_decode.c */; }; - 22C9190B11933FCF0083AC69 /* rsa_exptmod.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9187711933FCF0083AC69 /* rsa_exptmod.c */; }; - 22C9190C11933FCF0083AC69 /* rsa_free.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9187811933FCF0083AC69 /* rsa_free.c */; }; - 22C9190D11933FCF0083AC69 /* rsa_import.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9187911933FCF0083AC69 /* rsa_import.c */; }; - 22C9190E11933FCF0083AC69 /* rsa_make_key.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9187A11933FCF0083AC69 /* rsa_make_key.c */; }; - 22C9190F11933FCF0083AC69 /* rsa_verify_hash.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9187B11933FCF0083AC69 /* rsa_verify_hash.c */; }; - 22C9191011933FCF0083AC69 /* rsa_verify_simple.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9187C11933FCF0083AC69 /* rsa_verify_simple.c */; }; - 22C9198A1193400A0083AC69 /* bn_fast_mp_invmod.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919111193400A0083AC69 /* bn_fast_mp_invmod.c */; }; - 22C9198B1193400A0083AC69 /* bn_fast_mp_montgomery_reduce.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919121193400A0083AC69 /* bn_fast_mp_montgomery_reduce.c */; }; - 22C9198C1193400A0083AC69 /* bn_fast_s_mp_mul_digs.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919131193400A0083AC69 /* bn_fast_s_mp_mul_digs.c */; }; - 22C9198D1193400A0083AC69 /* bn_fast_s_mp_mul_high_digs.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919141193400A0083AC69 /* bn_fast_s_mp_mul_high_digs.c */; }; - 22C9198E1193400A0083AC69 /* bn_fast_s_mp_sqr.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919151193400A0083AC69 /* bn_fast_s_mp_sqr.c */; }; - 22C9198F1193400A0083AC69 /* bn_mp_2expt.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919161193400A0083AC69 /* bn_mp_2expt.c */; }; - 22C919901193400A0083AC69 /* bn_mp_abs.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919171193400A0083AC69 /* bn_mp_abs.c */; }; - 22C919911193400A0083AC69 /* bn_mp_add_d.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919181193400A0083AC69 /* bn_mp_add_d.c */; }; - 22C919921193400A0083AC69 /* bn_mp_add.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919191193400A0083AC69 /* bn_mp_add.c */; }; - 22C919931193400A0083AC69 /* bn_mp_addmod.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9191A1193400A0083AC69 /* bn_mp_addmod.c */; }; - 22C919941193400A0083AC69 /* bn_mp_and.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9191B1193400A0083AC69 /* bn_mp_and.c */; }; - 22C919951193400A0083AC69 /* bn_mp_clamp.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9191C1193400A0083AC69 /* bn_mp_clamp.c */; }; - 22C919961193400A0083AC69 /* bn_mp_clear_multi.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9191D1193400A0083AC69 /* bn_mp_clear_multi.c */; }; - 22C919971193400A0083AC69 /* bn_mp_clear.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9191E1193400A0083AC69 /* bn_mp_clear.c */; }; - 22C919981193400A0083AC69 /* bn_mp_cmp_d.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9191F1193400A0083AC69 /* bn_mp_cmp_d.c */; }; - 22C919991193400A0083AC69 /* bn_mp_cmp_mag.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919201193400A0083AC69 /* bn_mp_cmp_mag.c */; }; - 22C9199A1193400A0083AC69 /* bn_mp_cmp.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919211193400A0083AC69 /* bn_mp_cmp.c */; }; - 22C9199B1193400A0083AC69 /* bn_mp_cnt_lsb.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919221193400A0083AC69 /* bn_mp_cnt_lsb.c */; }; - 22C9199C1193400A0083AC69 /* bn_mp_copy.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919231193400A0083AC69 /* bn_mp_copy.c */; }; - 22C9199D1193400A0083AC69 /* bn_mp_count_bits.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919241193400A0083AC69 /* bn_mp_count_bits.c */; }; - 22C9199E1193400A0083AC69 /* bn_mp_div_2.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919251193400A0083AC69 /* bn_mp_div_2.c */; }; - 22C9199F1193400A0083AC69 /* bn_mp_div_2d.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919261193400A0083AC69 /* bn_mp_div_2d.c */; }; - 22C919A01193400A0083AC69 /* bn_mp_div_3.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919271193400A0083AC69 /* bn_mp_div_3.c */; }; - 22C919A11193400A0083AC69 /* bn_mp_div_d.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919281193400A0083AC69 /* bn_mp_div_d.c */; }; - 22C919A21193400A0083AC69 /* bn_mp_div.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919291193400A0083AC69 /* bn_mp_div.c */; }; - 22C919A31193400A0083AC69 /* bn_mp_dr_is_modulus.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9192A1193400A0083AC69 /* bn_mp_dr_is_modulus.c */; }; - 22C919A41193400A0083AC69 /* bn_mp_dr_reduce.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9192B1193400A0083AC69 /* bn_mp_dr_reduce.c */; }; - 22C919A51193400A0083AC69 /* bn_mp_dr_setup.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9192C1193400A0083AC69 /* bn_mp_dr_setup.c */; }; - 22C919A61193400A0083AC69 /* bn_mp_exch.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9192D1193400A0083AC69 /* bn_mp_exch.c */; }; - 22C919A71193400A0083AC69 /* bn_mp_expt_d.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9192E1193400A0083AC69 /* bn_mp_expt_d.c */; }; - 22C919A81193400A0083AC69 /* bn_mp_exptmod_fast.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9192F1193400A0083AC69 /* bn_mp_exptmod_fast.c */; }; - 22C919A91193400A0083AC69 /* bn_mp_exptmod.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919301193400A0083AC69 /* bn_mp_exptmod.c */; }; - 22C919AA1193400A0083AC69 /* bn_mp_exteuclid.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919311193400A0083AC69 /* bn_mp_exteuclid.c */; }; - 22C919AB1193400A0083AC69 /* bn_mp_fread.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919321193400A0083AC69 /* bn_mp_fread.c */; }; - 22C919AC1193400A0083AC69 /* bn_mp_fwrite.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919331193400A0083AC69 /* bn_mp_fwrite.c */; }; - 22C919AD1193400A0083AC69 /* bn_mp_gcd.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919341193400A0083AC69 /* bn_mp_gcd.c */; }; - 22C919AE1193400A0083AC69 /* bn_mp_get_int.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919351193400A0083AC69 /* bn_mp_get_int.c */; }; - 22C919AF1193400A0083AC69 /* bn_mp_grow.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919361193400A0083AC69 /* bn_mp_grow.c */; }; - 22C919B01193400A0083AC69 /* bn_mp_init_copy.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919371193400A0083AC69 /* bn_mp_init_copy.c */; }; - 22C919B11193400A0083AC69 /* bn_mp_init_multi.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919381193400A0083AC69 /* bn_mp_init_multi.c */; }; - 22C919B21193400A0083AC69 /* bn_mp_init_set_int.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919391193400A0083AC69 /* bn_mp_init_set_int.c */; }; - 22C919B31193400A0083AC69 /* bn_mp_init_set.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9193A1193400A0083AC69 /* bn_mp_init_set.c */; }; - 22C919B41193400A0083AC69 /* bn_mp_init_size.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9193B1193400A0083AC69 /* bn_mp_init_size.c */; }; - 22C919B51193400A0083AC69 /* bn_mp_init.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9193C1193400A0083AC69 /* bn_mp_init.c */; }; - 22C919B61193400A0083AC69 /* bn_mp_invmod_slow.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9193D1193400A0083AC69 /* bn_mp_invmod_slow.c */; }; - 22C919B71193400A0083AC69 /* bn_mp_invmod.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9193E1193400A0083AC69 /* bn_mp_invmod.c */; }; - 22C919B81193400A0083AC69 /* bn_mp_is_square.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9193F1193400A0083AC69 /* bn_mp_is_square.c */; }; - 22C919B91193400A0083AC69 /* bn_mp_jacobi.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919401193400A0083AC69 /* bn_mp_jacobi.c */; }; - 22C919BA1193400A0083AC69 /* bn_mp_karatsuba_mul.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919411193400A0083AC69 /* bn_mp_karatsuba_mul.c */; }; - 22C919BB1193400A0083AC69 /* bn_mp_karatsuba_sqr.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919421193400A0083AC69 /* bn_mp_karatsuba_sqr.c */; }; - 22C919BC1193400A0083AC69 /* bn_mp_lcm.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919431193400A0083AC69 /* bn_mp_lcm.c */; }; - 22C919BD1193400A0083AC69 /* bn_mp_lshd.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919441193400A0083AC69 /* bn_mp_lshd.c */; }; - 22C919BE1193400A0083AC69 /* bn_mp_mod_2d.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919451193400A0083AC69 /* bn_mp_mod_2d.c */; }; - 22C919BF1193400A0083AC69 /* bn_mp_mod_d.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919461193400A0083AC69 /* bn_mp_mod_d.c */; }; - 22C919C01193400A0083AC69 /* bn_mp_mod.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919471193400A0083AC69 /* bn_mp_mod.c */; }; - 22C919C11193400A0083AC69 /* bn_mp_montgomery_calc_normalization.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919481193400A0083AC69 /* bn_mp_montgomery_calc_normalization.c */; }; - 22C919C21193400A0083AC69 /* bn_mp_montgomery_reduce.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919491193400A0083AC69 /* bn_mp_montgomery_reduce.c */; }; - 22C919C31193400A0083AC69 /* bn_mp_montgomery_setup.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9194A1193400A0083AC69 /* bn_mp_montgomery_setup.c */; }; - 22C919C41193400A0083AC69 /* bn_mp_mul_2.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9194B1193400A0083AC69 /* bn_mp_mul_2.c */; }; - 22C919C51193400A0083AC69 /* bn_mp_mul_2d.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9194C1193400A0083AC69 /* bn_mp_mul_2d.c */; }; - 22C919C61193400A0083AC69 /* bn_mp_mul_d.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9194D1193400A0083AC69 /* bn_mp_mul_d.c */; }; - 22C919C71193400A0083AC69 /* bn_mp_mul.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9194E1193400A0083AC69 /* bn_mp_mul.c */; }; - 22C919C81193400A0083AC69 /* bn_mp_mulmod.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9194F1193400A0083AC69 /* bn_mp_mulmod.c */; }; - 22C919C91193400A0083AC69 /* bn_mp_n_root.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919501193400A0083AC69 /* bn_mp_n_root.c */; }; - 22C919CA1193400A0083AC69 /* bn_mp_neg.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919511193400A0083AC69 /* bn_mp_neg.c */; }; - 22C919CB1193400A0083AC69 /* bn_mp_or.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919521193400A0083AC69 /* bn_mp_or.c */; }; - 22C919CC1193400A0083AC69 /* bn_mp_prime_fermat.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919531193400A0083AC69 /* bn_mp_prime_fermat.c */; }; - 22C919CD1193400A0083AC69 /* bn_mp_prime_is_divisible.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919541193400A0083AC69 /* bn_mp_prime_is_divisible.c */; }; - 22C919CE1193400A0083AC69 /* bn_mp_prime_is_prime.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919551193400A0083AC69 /* bn_mp_prime_is_prime.c */; }; - 22C919CF1193400A0083AC69 /* bn_mp_prime_miller_rabin.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919561193400A0083AC69 /* bn_mp_prime_miller_rabin.c */; }; - 22C919D01193400A0083AC69 /* bn_mp_prime_next_prime.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919571193400A0083AC69 /* bn_mp_prime_next_prime.c */; }; - 22C919D11193400A0083AC69 /* bn_mp_prime_rabin_miller_trials.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919581193400A0083AC69 /* bn_mp_prime_rabin_miller_trials.c */; }; - 22C919D21193400A0083AC69 /* bn_mp_prime_random_ex.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919591193400A0083AC69 /* bn_mp_prime_random_ex.c */; }; - 22C919D31193400A0083AC69 /* bn_mp_radix_size.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9195A1193400A0083AC69 /* bn_mp_radix_size.c */; }; - 22C919D41193400A0083AC69 /* bn_mp_radix_smap.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9195B1193400A0083AC69 /* bn_mp_radix_smap.c */; }; - 22C919D51193400A0083AC69 /* bn_mp_rand.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9195C1193400A0083AC69 /* bn_mp_rand.c */; }; - 22C919D61193400A0083AC69 /* bn_mp_read_radix.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9195D1193400A0083AC69 /* bn_mp_read_radix.c */; }; - 22C919D71193400A0083AC69 /* bn_mp_read_signed_bin.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9195E1193400A0083AC69 /* bn_mp_read_signed_bin.c */; }; - 22C919D81193400A0083AC69 /* bn_mp_read_unsigned_bin.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9195F1193400A0083AC69 /* bn_mp_read_unsigned_bin.c */; }; - 22C919D91193400A0083AC69 /* bn_mp_reduce_2k_l.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919601193400A0083AC69 /* bn_mp_reduce_2k_l.c */; }; - 22C919DA1193400A0083AC69 /* bn_mp_reduce_2k_setup_l.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919611193400A0083AC69 /* bn_mp_reduce_2k_setup_l.c */; }; - 22C919DB1193400A0083AC69 /* bn_mp_reduce_2k_setup.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919621193400A0083AC69 /* bn_mp_reduce_2k_setup.c */; }; - 22C919DC1193400A0083AC69 /* bn_mp_reduce_2k.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919631193400A0083AC69 /* bn_mp_reduce_2k.c */; }; - 22C919DD1193400A0083AC69 /* bn_mp_reduce_is_2k_l.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919641193400A0083AC69 /* bn_mp_reduce_is_2k_l.c */; }; - 22C919DE1193400A0083AC69 /* bn_mp_reduce_is_2k.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919651193400A0083AC69 /* bn_mp_reduce_is_2k.c */; }; - 22C919DF1193400A0083AC69 /* bn_mp_reduce_setup.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919661193400A0083AC69 /* bn_mp_reduce_setup.c */; }; - 22C919E01193400A0083AC69 /* bn_mp_reduce.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919671193400A0083AC69 /* bn_mp_reduce.c */; }; - 22C919E11193400A0083AC69 /* bn_mp_rshd.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919681193400A0083AC69 /* bn_mp_rshd.c */; }; - 22C919E21193400A0083AC69 /* bn_mp_set_int.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919691193400A0083AC69 /* bn_mp_set_int.c */; }; - 22C919E31193400A0083AC69 /* bn_mp_set.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9196A1193400A0083AC69 /* bn_mp_set.c */; }; - 22C919E41193400A0083AC69 /* bn_mp_shrink.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9196B1193400A0083AC69 /* bn_mp_shrink.c */; }; - 22C919E51193400A0083AC69 /* bn_mp_signed_bin_size.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9196C1193400A0083AC69 /* bn_mp_signed_bin_size.c */; }; - 22C919E61193400A0083AC69 /* bn_mp_sqr.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9196D1193400A0083AC69 /* bn_mp_sqr.c */; }; - 22C919E71193400A0083AC69 /* bn_mp_sqrmod.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9196E1193400A0083AC69 /* bn_mp_sqrmod.c */; }; - 22C919E81193400A0083AC69 /* bn_mp_sqrt.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9196F1193400A0083AC69 /* bn_mp_sqrt.c */; }; - 22C919E91193400A0083AC69 /* bn_mp_sub_d.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919701193400A0083AC69 /* bn_mp_sub_d.c */; }; - 22C919EA1193400A0083AC69 /* bn_mp_sub.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919711193400A0083AC69 /* bn_mp_sub.c */; }; - 22C919EB1193400A0083AC69 /* bn_mp_submod.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919721193400A0083AC69 /* bn_mp_submod.c */; }; - 22C919EC1193400A0083AC69 /* bn_mp_to_signed_bin_n.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919731193400A0083AC69 /* bn_mp_to_signed_bin_n.c */; }; - 22C919ED1193400A0083AC69 /* bn_mp_to_signed_bin.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919741193400A0083AC69 /* bn_mp_to_signed_bin.c */; }; - 22C919EE1193400A0083AC69 /* bn_mp_to_unsigned_bin_n.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919751193400A0083AC69 /* bn_mp_to_unsigned_bin_n.c */; }; - 22C919EF1193400A0083AC69 /* bn_mp_to_unsigned_bin.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919761193400A0083AC69 /* bn_mp_to_unsigned_bin.c */; }; - 22C919F01193400A0083AC69 /* bn_mp_toom_mul.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919771193400A0083AC69 /* bn_mp_toom_mul.c */; }; - 22C919F11193400A0083AC69 /* bn_mp_toom_sqr.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919781193400A0083AC69 /* bn_mp_toom_sqr.c */; }; - 22C919F21193400A0083AC69 /* bn_mp_toradix_n.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919791193400A0083AC69 /* bn_mp_toradix_n.c */; }; - 22C919F31193400A0083AC69 /* bn_mp_toradix.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9197A1193400A0083AC69 /* bn_mp_toradix.c */; }; - 22C919F41193400A0083AC69 /* bn_mp_unsigned_bin_size.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9197B1193400A0083AC69 /* bn_mp_unsigned_bin_size.c */; }; - 22C919F51193400A0083AC69 /* bn_mp_xor.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9197C1193400A0083AC69 /* bn_mp_xor.c */; }; - 22C919F61193400A0083AC69 /* bn_mp_zero.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9197D1193400A0083AC69 /* bn_mp_zero.c */; }; - 22C919F71193400A0083AC69 /* bn_prime_tab.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9197E1193400A0083AC69 /* bn_prime_tab.c */; }; - 22C919F81193400A0083AC69 /* bn_reverse.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9197F1193400A0083AC69 /* bn_reverse.c */; }; - 22C919F91193400A0083AC69 /* bn_s_mp_add.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919801193400A0083AC69 /* bn_s_mp_add.c */; }; - 22C919FA1193400A0083AC69 /* bn_s_mp_exptmod.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919811193400A0083AC69 /* bn_s_mp_exptmod.c */; }; - 22C919FB1193400A0083AC69 /* bn_s_mp_mul_digs.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919821193400A0083AC69 /* bn_s_mp_mul_digs.c */; }; - 22C919FC1193400A0083AC69 /* bn_s_mp_mul_high_digs.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919831193400A0083AC69 /* bn_s_mp_mul_high_digs.c */; }; - 22C919FD1193400A0083AC69 /* bn_s_mp_sqr.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919841193400A0083AC69 /* bn_s_mp_sqr.c */; }; - 22C919FE1193400A0083AC69 /* bn_s_mp_sub.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919851193400A0083AC69 /* bn_s_mp_sub.c */; }; - 22C919FF1193400A0083AC69 /* bncore.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919861193400A0083AC69 /* bncore.c */; }; - 22C91A001193400A0083AC69 /* tommath_class.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C919871193400A0083AC69 /* tommath_class.h */; }; - 22C91A011193400A0083AC69 /* tommath_superclass.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C919881193400A0083AC69 /* tommath_superclass.h */; }; - 22C91A021193400A0083AC69 /* tommath.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C919891193400A0083AC69 /* tommath.h */; }; - 22C91A031193400A0083AC69 /* bn_fast_mp_invmod.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919111193400A0083AC69 /* bn_fast_mp_invmod.c */; }; - 22C91A041193400A0083AC69 /* bn_fast_mp_montgomery_reduce.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919121193400A0083AC69 /* bn_fast_mp_montgomery_reduce.c */; }; - 22C91A051193400A0083AC69 /* bn_fast_s_mp_mul_digs.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919131193400A0083AC69 /* bn_fast_s_mp_mul_digs.c */; }; - 22C91A061193400A0083AC69 /* bn_fast_s_mp_mul_high_digs.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919141193400A0083AC69 /* bn_fast_s_mp_mul_high_digs.c */; }; - 22C91A071193400A0083AC69 /* bn_fast_s_mp_sqr.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919151193400A0083AC69 /* bn_fast_s_mp_sqr.c */; }; - 22C91A081193400A0083AC69 /* bn_mp_2expt.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919161193400A0083AC69 /* bn_mp_2expt.c */; }; - 22C91A091193400A0083AC69 /* bn_mp_abs.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919171193400A0083AC69 /* bn_mp_abs.c */; }; - 22C91A0A1193400A0083AC69 /* bn_mp_add_d.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919181193400A0083AC69 /* bn_mp_add_d.c */; }; - 22C91A0B1193400A0083AC69 /* bn_mp_add.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919191193400A0083AC69 /* bn_mp_add.c */; }; - 22C91A0C1193400A0083AC69 /* bn_mp_addmod.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9191A1193400A0083AC69 /* bn_mp_addmod.c */; }; - 22C91A0D1193400A0083AC69 /* bn_mp_and.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9191B1193400A0083AC69 /* bn_mp_and.c */; }; - 22C91A0E1193400A0083AC69 /* bn_mp_clamp.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9191C1193400A0083AC69 /* bn_mp_clamp.c */; }; - 22C91A0F1193400A0083AC69 /* bn_mp_clear_multi.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9191D1193400A0083AC69 /* bn_mp_clear_multi.c */; }; - 22C91A101193400A0083AC69 /* bn_mp_clear.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9191E1193400A0083AC69 /* bn_mp_clear.c */; }; - 22C91A111193400A0083AC69 /* bn_mp_cmp_d.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9191F1193400A0083AC69 /* bn_mp_cmp_d.c */; }; - 22C91A121193400A0083AC69 /* bn_mp_cmp_mag.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919201193400A0083AC69 /* bn_mp_cmp_mag.c */; }; - 22C91A131193400A0083AC69 /* bn_mp_cmp.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919211193400A0083AC69 /* bn_mp_cmp.c */; }; - 22C91A141193400A0083AC69 /* bn_mp_cnt_lsb.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919221193400A0083AC69 /* bn_mp_cnt_lsb.c */; }; - 22C91A151193400A0083AC69 /* bn_mp_copy.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919231193400A0083AC69 /* bn_mp_copy.c */; }; - 22C91A161193400A0083AC69 /* bn_mp_count_bits.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919241193400A0083AC69 /* bn_mp_count_bits.c */; }; - 22C91A171193400A0083AC69 /* bn_mp_div_2.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919251193400A0083AC69 /* bn_mp_div_2.c */; }; - 22C91A181193400A0083AC69 /* bn_mp_div_2d.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919261193400A0083AC69 /* bn_mp_div_2d.c */; }; - 22C91A191193400A0083AC69 /* bn_mp_div_3.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919271193400A0083AC69 /* bn_mp_div_3.c */; }; - 22C91A1A1193400A0083AC69 /* bn_mp_div_d.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919281193400A0083AC69 /* bn_mp_div_d.c */; }; - 22C91A1B1193400A0083AC69 /* bn_mp_div.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919291193400A0083AC69 /* bn_mp_div.c */; }; - 22C91A1C1193400A0083AC69 /* bn_mp_dr_is_modulus.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9192A1193400A0083AC69 /* bn_mp_dr_is_modulus.c */; }; - 22C91A1D1193400A0083AC69 /* bn_mp_dr_reduce.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9192B1193400A0083AC69 /* bn_mp_dr_reduce.c */; }; - 22C91A1E1193400A0083AC69 /* bn_mp_dr_setup.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9192C1193400A0083AC69 /* bn_mp_dr_setup.c */; }; - 22C91A1F1193400A0083AC69 /* bn_mp_exch.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9192D1193400A0083AC69 /* bn_mp_exch.c */; }; - 22C91A201193400A0083AC69 /* bn_mp_expt_d.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9192E1193400A0083AC69 /* bn_mp_expt_d.c */; }; - 22C91A211193400A0083AC69 /* bn_mp_exptmod_fast.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9192F1193400A0083AC69 /* bn_mp_exptmod_fast.c */; }; - 22C91A221193400A0083AC69 /* bn_mp_exptmod.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919301193400A0083AC69 /* bn_mp_exptmod.c */; }; - 22C91A231193400A0083AC69 /* bn_mp_exteuclid.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919311193400A0083AC69 /* bn_mp_exteuclid.c */; }; - 22C91A241193400A0083AC69 /* bn_mp_fread.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919321193400A0083AC69 /* bn_mp_fread.c */; }; - 22C91A251193400A0083AC69 /* bn_mp_fwrite.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919331193400A0083AC69 /* bn_mp_fwrite.c */; }; - 22C91A261193400A0083AC69 /* bn_mp_gcd.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919341193400A0083AC69 /* bn_mp_gcd.c */; }; - 22C91A271193400A0083AC69 /* bn_mp_get_int.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919351193400A0083AC69 /* bn_mp_get_int.c */; }; - 22C91A281193400A0083AC69 /* bn_mp_grow.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919361193400A0083AC69 /* bn_mp_grow.c */; }; - 22C91A291193400A0083AC69 /* bn_mp_init_copy.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919371193400A0083AC69 /* bn_mp_init_copy.c */; }; - 22C91A2A1193400A0083AC69 /* bn_mp_init_multi.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919381193400A0083AC69 /* bn_mp_init_multi.c */; }; - 22C91A2B1193400A0083AC69 /* bn_mp_init_set_int.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919391193400A0083AC69 /* bn_mp_init_set_int.c */; }; - 22C91A2C1193400A0083AC69 /* bn_mp_init_set.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9193A1193400A0083AC69 /* bn_mp_init_set.c */; }; - 22C91A2D1193400A0083AC69 /* bn_mp_init_size.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9193B1193400A0083AC69 /* bn_mp_init_size.c */; }; - 22C91A2E1193400A0083AC69 /* bn_mp_init.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9193C1193400A0083AC69 /* bn_mp_init.c */; }; - 22C91A2F1193400A0083AC69 /* bn_mp_invmod_slow.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9193D1193400A0083AC69 /* bn_mp_invmod_slow.c */; }; - 22C91A301193400A0083AC69 /* bn_mp_invmod.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9193E1193400A0083AC69 /* bn_mp_invmod.c */; }; - 22C91A311193400A0083AC69 /* bn_mp_is_square.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9193F1193400A0083AC69 /* bn_mp_is_square.c */; }; - 22C91A321193400A0083AC69 /* bn_mp_jacobi.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919401193400A0083AC69 /* bn_mp_jacobi.c */; }; - 22C91A331193400A0083AC69 /* bn_mp_karatsuba_mul.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919411193400A0083AC69 /* bn_mp_karatsuba_mul.c */; }; - 22C91A341193400A0083AC69 /* bn_mp_karatsuba_sqr.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919421193400A0083AC69 /* bn_mp_karatsuba_sqr.c */; }; - 22C91A351193400A0083AC69 /* bn_mp_lcm.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919431193400A0083AC69 /* bn_mp_lcm.c */; }; - 22C91A361193400A0083AC69 /* bn_mp_lshd.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919441193400A0083AC69 /* bn_mp_lshd.c */; }; - 22C91A371193400A0083AC69 /* bn_mp_mod_2d.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919451193400A0083AC69 /* bn_mp_mod_2d.c */; }; - 22C91A381193400A0083AC69 /* bn_mp_mod_d.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919461193400A0083AC69 /* bn_mp_mod_d.c */; }; - 22C91A391193400A0083AC69 /* bn_mp_mod.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919471193400A0083AC69 /* bn_mp_mod.c */; }; - 22C91A3A1193400A0083AC69 /* bn_mp_montgomery_calc_normalization.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919481193400A0083AC69 /* bn_mp_montgomery_calc_normalization.c */; }; - 22C91A3B1193400A0083AC69 /* bn_mp_montgomery_reduce.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919491193400A0083AC69 /* bn_mp_montgomery_reduce.c */; }; - 22C91A3C1193400A0083AC69 /* bn_mp_montgomery_setup.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9194A1193400A0083AC69 /* bn_mp_montgomery_setup.c */; }; - 22C91A3D1193400A0083AC69 /* bn_mp_mul_2.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9194B1193400A0083AC69 /* bn_mp_mul_2.c */; }; - 22C91A3E1193400A0083AC69 /* bn_mp_mul_2d.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9194C1193400A0083AC69 /* bn_mp_mul_2d.c */; }; - 22C91A3F1193400A0083AC69 /* bn_mp_mul_d.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9194D1193400A0083AC69 /* bn_mp_mul_d.c */; }; - 22C91A401193400A0083AC69 /* bn_mp_mul.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9194E1193400A0083AC69 /* bn_mp_mul.c */; }; - 22C91A411193400A0083AC69 /* bn_mp_mulmod.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9194F1193400A0083AC69 /* bn_mp_mulmod.c */; }; - 22C91A421193400A0083AC69 /* bn_mp_n_root.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919501193400A0083AC69 /* bn_mp_n_root.c */; }; - 22C91A431193400A0083AC69 /* bn_mp_neg.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919511193400A0083AC69 /* bn_mp_neg.c */; }; - 22C91A441193400A0083AC69 /* bn_mp_or.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919521193400A0083AC69 /* bn_mp_or.c */; }; - 22C91A451193400A0083AC69 /* bn_mp_prime_fermat.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919531193400A0083AC69 /* bn_mp_prime_fermat.c */; }; - 22C91A461193400A0083AC69 /* bn_mp_prime_is_divisible.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919541193400A0083AC69 /* bn_mp_prime_is_divisible.c */; }; - 22C91A471193400A0083AC69 /* bn_mp_prime_is_prime.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919551193400A0083AC69 /* bn_mp_prime_is_prime.c */; }; - 22C91A481193400A0083AC69 /* bn_mp_prime_miller_rabin.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919561193400A0083AC69 /* bn_mp_prime_miller_rabin.c */; }; - 22C91A491193400A0083AC69 /* bn_mp_prime_next_prime.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919571193400A0083AC69 /* bn_mp_prime_next_prime.c */; }; - 22C91A4A1193400A0083AC69 /* bn_mp_prime_rabin_miller_trials.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919581193400A0083AC69 /* bn_mp_prime_rabin_miller_trials.c */; }; - 22C91A4B1193400A0083AC69 /* bn_mp_prime_random_ex.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919591193400A0083AC69 /* bn_mp_prime_random_ex.c */; }; - 22C91A4C1193400A0083AC69 /* bn_mp_radix_size.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9195A1193400A0083AC69 /* bn_mp_radix_size.c */; }; - 22C91A4D1193400A0083AC69 /* bn_mp_radix_smap.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9195B1193400A0083AC69 /* bn_mp_radix_smap.c */; }; - 22C91A4E1193400A0083AC69 /* bn_mp_rand.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9195C1193400A0083AC69 /* bn_mp_rand.c */; }; - 22C91A4F1193400A0083AC69 /* bn_mp_read_radix.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9195D1193400A0083AC69 /* bn_mp_read_radix.c */; }; - 22C91A501193400A0083AC69 /* bn_mp_read_signed_bin.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9195E1193400A0083AC69 /* bn_mp_read_signed_bin.c */; }; - 22C91A511193400A0083AC69 /* bn_mp_read_unsigned_bin.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9195F1193400A0083AC69 /* bn_mp_read_unsigned_bin.c */; }; - 22C91A521193400A0083AC69 /* bn_mp_reduce_2k_l.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919601193400A0083AC69 /* bn_mp_reduce_2k_l.c */; }; - 22C91A531193400A0083AC69 /* bn_mp_reduce_2k_setup_l.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919611193400A0083AC69 /* bn_mp_reduce_2k_setup_l.c */; }; - 22C91A541193400A0083AC69 /* bn_mp_reduce_2k_setup.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919621193400A0083AC69 /* bn_mp_reduce_2k_setup.c */; }; - 22C91A551193400A0083AC69 /* bn_mp_reduce_2k.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919631193400A0083AC69 /* bn_mp_reduce_2k.c */; }; - 22C91A561193400A0083AC69 /* bn_mp_reduce_is_2k_l.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919641193400A0083AC69 /* bn_mp_reduce_is_2k_l.c */; }; - 22C91A571193400A0083AC69 /* bn_mp_reduce_is_2k.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919651193400A0083AC69 /* bn_mp_reduce_is_2k.c */; }; - 22C91A581193400A0083AC69 /* bn_mp_reduce_setup.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919661193400A0083AC69 /* bn_mp_reduce_setup.c */; }; - 22C91A591193400A0083AC69 /* bn_mp_reduce.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919671193400A0083AC69 /* bn_mp_reduce.c */; }; - 22C91A5A1193400A0083AC69 /* bn_mp_rshd.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919681193400A0083AC69 /* bn_mp_rshd.c */; }; - 22C91A5B1193400A0083AC69 /* bn_mp_set_int.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919691193400A0083AC69 /* bn_mp_set_int.c */; }; - 22C91A5C1193400A0083AC69 /* bn_mp_set.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9196A1193400A0083AC69 /* bn_mp_set.c */; }; - 22C91A5D1193400A0083AC69 /* bn_mp_shrink.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9196B1193400A0083AC69 /* bn_mp_shrink.c */; }; - 22C91A5E1193400A0083AC69 /* bn_mp_signed_bin_size.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9196C1193400A0083AC69 /* bn_mp_signed_bin_size.c */; }; - 22C91A5F1193400A0083AC69 /* bn_mp_sqr.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9196D1193400A0083AC69 /* bn_mp_sqr.c */; }; - 22C91A601193400A0083AC69 /* bn_mp_sqrmod.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9196E1193400A0083AC69 /* bn_mp_sqrmod.c */; }; - 22C91A611193400A0083AC69 /* bn_mp_sqrt.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9196F1193400A0083AC69 /* bn_mp_sqrt.c */; }; - 22C91A621193400A0083AC69 /* bn_mp_sub_d.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919701193400A0083AC69 /* bn_mp_sub_d.c */; }; - 22C91A631193400A0083AC69 /* bn_mp_sub.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919711193400A0083AC69 /* bn_mp_sub.c */; }; - 22C91A641193400A0083AC69 /* bn_mp_submod.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919721193400A0083AC69 /* bn_mp_submod.c */; }; - 22C91A651193400A0083AC69 /* bn_mp_to_signed_bin_n.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919731193400A0083AC69 /* bn_mp_to_signed_bin_n.c */; }; - 22C91A661193400A0083AC69 /* bn_mp_to_signed_bin.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919741193400A0083AC69 /* bn_mp_to_signed_bin.c */; }; - 22C91A671193400A0083AC69 /* bn_mp_to_unsigned_bin_n.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919751193400A0083AC69 /* bn_mp_to_unsigned_bin_n.c */; }; - 22C91A681193400A0083AC69 /* bn_mp_to_unsigned_bin.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919761193400A0083AC69 /* bn_mp_to_unsigned_bin.c */; }; - 22C91A691193400A0083AC69 /* bn_mp_toom_mul.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919771193400A0083AC69 /* bn_mp_toom_mul.c */; }; - 22C91A6A1193400A0083AC69 /* bn_mp_toom_sqr.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919781193400A0083AC69 /* bn_mp_toom_sqr.c */; }; - 22C91A6B1193400A0083AC69 /* bn_mp_toradix_n.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919791193400A0083AC69 /* bn_mp_toradix_n.c */; }; - 22C91A6C1193400A0083AC69 /* bn_mp_toradix.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9197A1193400A0083AC69 /* bn_mp_toradix.c */; }; - 22C91A6D1193400A0083AC69 /* bn_mp_unsigned_bin_size.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9197B1193400A0083AC69 /* bn_mp_unsigned_bin_size.c */; }; - 22C91A6E1193400A0083AC69 /* bn_mp_xor.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9197C1193400A0083AC69 /* bn_mp_xor.c */; }; - 22C91A6F1193400A0083AC69 /* bn_mp_zero.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9197D1193400A0083AC69 /* bn_mp_zero.c */; }; - 22C91A701193400A0083AC69 /* bn_prime_tab.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9197E1193400A0083AC69 /* bn_prime_tab.c */; }; - 22C91A711193400A0083AC69 /* bn_reverse.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C9197F1193400A0083AC69 /* bn_reverse.c */; }; - 22C91A721193400A0083AC69 /* bn_s_mp_add.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919801193400A0083AC69 /* bn_s_mp_add.c */; }; - 22C91A731193400A0083AC69 /* bn_s_mp_exptmod.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919811193400A0083AC69 /* bn_s_mp_exptmod.c */; }; - 22C91A741193400A0083AC69 /* bn_s_mp_mul_digs.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919821193400A0083AC69 /* bn_s_mp_mul_digs.c */; }; - 22C91A751193400A0083AC69 /* bn_s_mp_mul_high_digs.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919831193400A0083AC69 /* bn_s_mp_mul_high_digs.c */; }; - 22C91A761193400A0083AC69 /* bn_s_mp_sqr.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919841193400A0083AC69 /* bn_s_mp_sqr.c */; }; - 22C91A771193400A0083AC69 /* bn_s_mp_sub.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919851193400A0083AC69 /* bn_s_mp_sub.c */; }; - 22C91A781193400A0083AC69 /* bncore.c in Sources */ = {isa = PBXBuildFile; fileRef = 22C919861193400A0083AC69 /* bncore.c */; }; - 22C91A791193400A0083AC69 /* tommath_class.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C919871193400A0083AC69 /* tommath_class.h */; }; - 22C91A7A1193400A0083AC69 /* tommath_superclass.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C919881193400A0083AC69 /* tommath_superclass.h */; }; - 22C91A7B1193400A0083AC69 /* tommath.h in Headers */ = {isa = PBXBuildFile; fileRef = 22C919891193400A0083AC69 /* tommath.h */; }; - 22EC6044154B28A000679228 /* FileStream.h in Headers */ = {isa = PBXBuildFile; fileRef = 22EC6043154B28A000679228 /* FileStream.h */; }; - 22EC6045154B28A000679228 /* FileStream.h in Headers */ = {isa = PBXBuildFile; fileRef = 22EC6043154B28A000679228 /* FileStream.h */; }; - 22F5A9C51193DFBA00F8B121 /* SFileVerify.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 22F5A9C41193DFBA00F8B121 /* SFileVerify.cpp */; }; - 22F5A9C61193DFBA00F8B121 /* SFileVerify.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 22F5A9C41193DFBA00F8B121 /* SFileVerify.cpp */; }; - E60816D61B707A9000B283F7 /* rsa_sign_hash.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816D51B707A9000B283F7 /* rsa_sign_hash.c */; }; - E60816D71B707A9B00B283F7 /* rsa_sign_hash.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816D51B707A9000B283F7 /* rsa_sign_hash.c */; }; - E60816D91B707B1800B283F7 /* pkcs_1_pss_encode.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816D81B707B1800B283F7 /* pkcs_1_pss_encode.c */; }; - E60816DA1B707B1800B283F7 /* pkcs_1_pss_encode.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816D81B707B1800B283F7 /* pkcs_1_pss_encode.c */; }; - E60816DC1B707B2700B283F7 /* pkcs_1_v1_5_encode.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816DB1B707B2700B283F7 /* pkcs_1_v1_5_encode.c */; }; - E60816DD1B707B2700B283F7 /* pkcs_1_v1_5_encode.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816DB1B707B2700B283F7 /* pkcs_1_v1_5_encode.c */; }; - E60816DF1B707B5700B283F7 /* der_encode_sequence_ex.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816DE1B707B5700B283F7 /* der_encode_sequence_ex.c */; }; - E60816E01B707B5700B283F7 /* der_encode_sequence_ex.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816DE1B707B5700B283F7 /* der_encode_sequence_ex.c */; }; - E60816EE1B707B7200B283F7 /* der_encode_bit_string.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816E11B707B7200B283F7 /* der_encode_bit_string.c */; }; - E60816EF1B707B7200B283F7 /* der_encode_bit_string.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816E11B707B7200B283F7 /* der_encode_bit_string.c */; }; - E60816F01B707B7200B283F7 /* der_encode_boolean.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816E21B707B7200B283F7 /* der_encode_boolean.c */; }; - E60816F11B707B7200B283F7 /* der_encode_boolean.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816E21B707B7200B283F7 /* der_encode_boolean.c */; }; - E60816F21B707B7200B283F7 /* der_encode_ia5_string.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816E31B707B7200B283F7 /* der_encode_ia5_string.c */; }; - E60816F31B707B7200B283F7 /* der_encode_ia5_string.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816E31B707B7200B283F7 /* der_encode_ia5_string.c */; }; - E60816F41B707B7200B283F7 /* der_encode_integer.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816E41B707B7200B283F7 /* der_encode_integer.c */; }; - E60816F51B707B7200B283F7 /* der_encode_integer.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816E41B707B7200B283F7 /* der_encode_integer.c */; }; - E60816F61B707B7200B283F7 /* der_encode_object_identifier.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816E51B707B7200B283F7 /* der_encode_object_identifier.c */; }; - E60816F71B707B7200B283F7 /* der_encode_object_identifier.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816E51B707B7200B283F7 /* der_encode_object_identifier.c */; }; - E60816F81B707B7200B283F7 /* der_encode_octet_string.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816E61B707B7200B283F7 /* der_encode_octet_string.c */; }; - E60816F91B707B7200B283F7 /* der_encode_octet_string.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816E61B707B7200B283F7 /* der_encode_octet_string.c */; }; - E60816FA1B707B7200B283F7 /* der_encode_printable_string.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816E71B707B7200B283F7 /* der_encode_printable_string.c */; }; - E60816FB1B707B7200B283F7 /* der_encode_printable_string.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816E71B707B7200B283F7 /* der_encode_printable_string.c */; }; - E60816FC1B707B7200B283F7 /* der_encode_sequence_multi.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816E81B707B7200B283F7 /* der_encode_sequence_multi.c */; }; - E60816FD1B707B7200B283F7 /* der_encode_sequence_multi.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816E81B707B7200B283F7 /* der_encode_sequence_multi.c */; }; - E60816FE1B707B7200B283F7 /* der_encode_set.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816E91B707B7200B283F7 /* der_encode_set.c */; }; - E60816FF1B707B7200B283F7 /* der_encode_set.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816E91B707B7200B283F7 /* der_encode_set.c */; }; - E60817001B707B7200B283F7 /* der_encode_setof.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816EA1B707B7200B283F7 /* der_encode_setof.c */; }; - E60817011B707B7200B283F7 /* der_encode_setof.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816EA1B707B7200B283F7 /* der_encode_setof.c */; }; - E60817021B707B7200B283F7 /* der_encode_short_integer.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816EB1B707B7200B283F7 /* der_encode_short_integer.c */; }; - E60817031B707B7200B283F7 /* der_encode_short_integer.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816EB1B707B7200B283F7 /* der_encode_short_integer.c */; }; - E60817041B707B7200B283F7 /* der_encode_utctime.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816EC1B707B7200B283F7 /* der_encode_utctime.c */; }; - E60817051B707B7200B283F7 /* der_encode_utctime.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816EC1B707B7200B283F7 /* der_encode_utctime.c */; }; - E60817061B707B7200B283F7 /* der_encode_utf8_string.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816ED1B707B7200B283F7 /* der_encode_utf8_string.c */; }; - E60817071B707B7200B283F7 /* der_encode_utf8_string.c in Sources */ = {isa = PBXBuildFile; fileRef = E60816ED1B707B7200B283F7 /* der_encode_utf8_string.c */; }; -/* End PBXBuildFile section */ - -/* Begin PBXContainerItemProxy section */ - 2229F62E11D4653600118914 /* PBXContainerItemProxy */ = { - isa = PBXContainerItemProxy; - containerPortal = 0867D690FE84028FC02AAC07 /* Project object */; - proxyType = 1; - remoteGlobalIDString = 225530D31056BAC800FA646A; - remoteInfo = StormLib; - }; -/* End PBXContainerItemProxy section */ - -/* Begin PBXFileReference section */ - 221F6A721168529C0026C852 /* LzmaDec.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = LzmaDec.h; path = C/LzmaDec.h; sourceTree = ""; }; - 221F6A731168529C0026C852 /* LzmaEnc.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = LzmaEnc.h; path = C/LzmaEnc.h; sourceTree = ""; }; - 221F6A7A116852AA0026C852 /* LzmaEnc.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; name = LzmaEnc.c; path = C/LzmaEnc.c; sourceTree = ""; }; - 221F6A7D116852B20026C852 /* LzmaDec.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; name = LzmaDec.c; path = C/LzmaDec.c; sourceTree = ""; }; - 221F6AB31168545B0026C852 /* LzFind.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; name = LzFind.c; path = C/LzFind.c; sourceTree = ""; }; - 221F6AB41168545B0026C852 /* LzFind.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = LzFind.h; path = C/LzFind.h; sourceTree = ""; }; - 221F6AB9116854730026C852 /* LzHash.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = LzHash.h; path = C/LzHash.h; sourceTree = ""; }; - 221F6ABC116854870026C852 /* Types.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = Types.h; path = C/Types.h; sourceTree = ""; }; - 2253A19F10568A83001909F9 /* StormLib.exp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.exports; name = StormLib.exp; path = stormlib_dll/StormLib.exp; sourceTree = ""; }; - 225530D41056BAC800FA646A /* libStormLib.a */ = {isa = PBXFileReference; explicitFileType = archive.ar; includeInIndex = 0; path = libStormLib.a; sourceTree = BUILT_PRODUCTS_DIR; }; - 225C734B1257CCC70009E8DA /* lookup.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = lookup.h; sourceTree = ""; }; - 225C734C1257CCC70009E8DA /* lookup3.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = lookup3.c; sourceTree = ""; }; - 225C73531257CD0C0009E8DA /* SBaseFileTable.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = SBaseFileTable.cpp; path = src/SBaseFileTable.cpp; sourceTree = ""; }; - 225FAC940E53B7F800DA2CAE /* StormLib.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = StormLib.framework; sourceTree = BUILT_PRODUCTS_DIR; }; - 225FAC950E53B7F800DA2CAE /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; - 226C7CA61857DE9400AB689C /* SBaseDumpData.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = SBaseDumpData.cpp; path = src/SBaseDumpData.cpp; sourceTree = ""; }; - 226C7CA91857DEAC00AB689C /* SBaseSubTypes.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = SBaseSubTypes.cpp; path = src/SBaseSubTypes.cpp; sourceTree = ""; }; - 226C7CAC1857DEEB00AB689C /* SFileGetFileInfo.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = SFileGetFileInfo.cpp; path = src/SFileGetFileInfo.cpp; sourceTree = ""; }; - 228B538311BF7D0D001A58DA /* FileStream.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = FileStream.cpp; path = src/FileStream.cpp; sourceTree = ""; }; - 2295488911D45A820064B264 /* Test.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = Test.cpp; path = test/Test.cpp; sourceTree = ""; }; - 22954ACE11D463A30064B264 /* StormLib_Test */ = {isa = PBXFileReference; explicitFileType = "compiled.mach-o.executable"; includeInIndex = 0; path = StormLib_Test; sourceTree = BUILT_PRODUCTS_DIR; }; - 2299D9D51167EFA8005C19BF /* adpcm.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = adpcm.cpp; sourceTree = ""; }; - 2299D9D61167EFA8005C19BF /* adpcm.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = adpcm.h; sourceTree = ""; }; - 2299D9DC1167EFC6005C19BF /* sparse.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = sparse.cpp; sourceTree = ""; }; - 2299D9DD1167EFC6005C19BF /* sparse.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = sparse.h; sourceTree = ""; }; - 2299DA4D1167FD16005C19BF /* SFileAddFile.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = SFileAddFile.cpp; path = src/SFileAddFile.cpp; sourceTree = ""; }; - 22AEA121123125D800359B16 /* SFilePatchArchives.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = SFilePatchArchives.cpp; path = src/SFilePatchArchives.cpp; sourceTree = ""; }; - 22C9182B11933FCF0083AC69 /* hash_memory.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = hash_memory.c; sourceTree = ""; }; - 22C9182C11933FCF0083AC69 /* md5.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = md5.c; sourceTree = ""; }; - 22C9182D11933FCF0083AC69 /* sha1.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = sha1.c; sourceTree = ""; }; - 22C9182F11933FCF0083AC69 /* tomcrypt.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = tomcrypt.h; sourceTree = ""; }; - 22C9183011933FCF0083AC69 /* tomcrypt_argchk.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = tomcrypt_argchk.h; sourceTree = ""; }; - 22C9183111933FCF0083AC69 /* tomcrypt_cfg.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = tomcrypt_cfg.h; sourceTree = ""; }; - 22C9183211933FCF0083AC69 /* tomcrypt_cipher.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = tomcrypt_cipher.h; sourceTree = ""; }; - 22C9183311933FCF0083AC69 /* tomcrypt_custom.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = tomcrypt_custom.h; sourceTree = ""; }; - 22C9183411933FCF0083AC69 /* tomcrypt_hash.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = tomcrypt_hash.h; sourceTree = ""; }; - 22C9183511933FCF0083AC69 /* tomcrypt_mac.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = tomcrypt_mac.h; sourceTree = ""; }; - 22C9183611933FCF0083AC69 /* tomcrypt_macros.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = tomcrypt_macros.h; sourceTree = ""; }; - 22C9183711933FCF0083AC69 /* tomcrypt_math.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = tomcrypt_math.h; sourceTree = ""; }; - 22C9183811933FCF0083AC69 /* tomcrypt_misc.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = tomcrypt_misc.h; sourceTree = ""; }; - 22C9183911933FCF0083AC69 /* tomcrypt_pk.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = tomcrypt_pk.h; sourceTree = ""; }; - 22C9183A11933FCF0083AC69 /* tomcrypt_pkcs.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = tomcrypt_pkcs.h; sourceTree = ""; }; - 22C9183B11933FCF0083AC69 /* tomcrypt_prng.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = tomcrypt_prng.h; sourceTree = ""; }; - 22C9183D11933FCF0083AC69 /* ltm_desc.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = ltm_desc.c; sourceTree = ""; }; - 22C9183E11933FCF0083AC69 /* multi.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = multi.c; sourceTree = ""; }; - 22C9183F11933FCF0083AC69 /* rand_prime.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = rand_prime.c; sourceTree = ""; }; - 22C9184111933FCF0083AC69 /* base64_decode.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = base64_decode.c; sourceTree = ""; }; - 22C9184211933FCF0083AC69 /* crypt_argchk.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = crypt_argchk.c; sourceTree = ""; }; - 22C9184311933FCF0083AC69 /* crypt_find_hash.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = crypt_find_hash.c; sourceTree = ""; }; - 22C9184411933FCF0083AC69 /* crypt_find_prng.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = crypt_find_prng.c; sourceTree = ""; }; - 22C9184511933FCF0083AC69 /* crypt_hash_descriptor.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = crypt_hash_descriptor.c; sourceTree = ""; }; - 22C9184611933FCF0083AC69 /* crypt_hash_is_valid.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = crypt_hash_is_valid.c; sourceTree = ""; }; - 22C9184711933FCF0083AC69 /* crypt_libc.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = crypt_libc.c; sourceTree = ""; }; - 22C9184811933FCF0083AC69 /* crypt_ltc_mp_descriptor.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = crypt_ltc_mp_descriptor.c; sourceTree = ""; }; - 22C9184911933FCF0083AC69 /* crypt_prng_descriptor.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = crypt_prng_descriptor.c; sourceTree = ""; }; - 22C9184A11933FCF0083AC69 /* crypt_prng_is_valid.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = crypt_prng_is_valid.c; sourceTree = ""; }; - 22C9184B11933FCF0083AC69 /* crypt_register_hash.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = crypt_register_hash.c; sourceTree = ""; }; - 22C9184C11933FCF0083AC69 /* crypt_register_prng.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = crypt_register_prng.c; sourceTree = ""; }; - 22C9184D11933FCF0083AC69 /* zeromem.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = zeromem.c; sourceTree = ""; }; - 22C9185011933FCF0083AC69 /* der_decode_bit_string.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_decode_bit_string.c; sourceTree = ""; }; - 22C9185111933FCF0083AC69 /* der_decode_boolean.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_decode_boolean.c; sourceTree = ""; }; - 22C9185211933FCF0083AC69 /* der_decode_choice.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_decode_choice.c; sourceTree = ""; }; - 22C9185311933FCF0083AC69 /* der_decode_ia5_string.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_decode_ia5_string.c; sourceTree = ""; }; - 22C9185411933FCF0083AC69 /* der_decode_integer.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_decode_integer.c; sourceTree = ""; }; - 22C9185511933FCF0083AC69 /* der_decode_object_identifier.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_decode_object_identifier.c; sourceTree = ""; }; - 22C9185611933FCF0083AC69 /* der_decode_octet_string.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_decode_octet_string.c; sourceTree = ""; }; - 22C9185711933FCF0083AC69 /* der_decode_printable_string.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_decode_printable_string.c; sourceTree = ""; }; - 22C9185811933FCF0083AC69 /* der_decode_sequence_ex.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_decode_sequence_ex.c; sourceTree = ""; }; - 22C9185911933FCF0083AC69 /* der_decode_sequence_flexi.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_decode_sequence_flexi.c; sourceTree = ""; }; - 22C9185A11933FCF0083AC69 /* der_decode_sequence_multi.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_decode_sequence_multi.c; sourceTree = ""; }; - 22C9185B11933FCF0083AC69 /* der_decode_short_integer.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_decode_short_integer.c; sourceTree = ""; }; - 22C9185C11933FCF0083AC69 /* der_decode_utctime.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_decode_utctime.c; sourceTree = ""; }; - 22C9185D11933FCF0083AC69 /* der_decode_utf8_string.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_decode_utf8_string.c; sourceTree = ""; }; - 22C9185E11933FCF0083AC69 /* der_length_bit_string.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_length_bit_string.c; sourceTree = ""; }; - 22C9185F11933FCF0083AC69 /* der_length_boolean.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_length_boolean.c; sourceTree = ""; }; - 22C9186011933FCF0083AC69 /* der_length_ia5_string.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_length_ia5_string.c; sourceTree = ""; }; - 22C9186111933FCF0083AC69 /* der_length_integer.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_length_integer.c; sourceTree = ""; }; - 22C9186211933FCF0083AC69 /* der_length_object_identifier.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_length_object_identifier.c; sourceTree = ""; }; - 22C9186311933FCF0083AC69 /* der_length_octet_string.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_length_octet_string.c; sourceTree = ""; }; - 22C9186411933FCF0083AC69 /* der_length_printable_string.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_length_printable_string.c; sourceTree = ""; }; - 22C9186511933FCF0083AC69 /* der_length_sequence.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_length_sequence.c; sourceTree = ""; }; - 22C9186611933FCF0083AC69 /* der_length_short_integer.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_length_short_integer.c; sourceTree = ""; }; - 22C9186711933FCF0083AC69 /* der_length_utctime.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_length_utctime.c; sourceTree = ""; }; - 22C9186811933FCF0083AC69 /* der_length_utf8_string.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_length_utf8_string.c; sourceTree = ""; }; - 22C9186911933FCF0083AC69 /* der_sequence_free.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_sequence_free.c; sourceTree = ""; }; - 22C9186B11933FCF0083AC69 /* ltc_ecc_map.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = ltc_ecc_map.c; sourceTree = ""; }; - 22C9186C11933FCF0083AC69 /* ltc_ecc_mul2add.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = ltc_ecc_mul2add.c; sourceTree = ""; }; - 22C9186D11933FCF0083AC69 /* ltc_ecc_mulmod.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = ltc_ecc_mulmod.c; sourceTree = ""; }; - 22C9186E11933FCF0083AC69 /* ltc_ecc_points.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = ltc_ecc_points.c; sourceTree = ""; }; - 22C9186F11933FCF0083AC69 /* ltc_ecc_projective_add_point.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = ltc_ecc_projective_add_point.c; sourceTree = ""; }; - 22C9187011933FCF0083AC69 /* ltc_ecc_projective_dbl_point.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = ltc_ecc_projective_dbl_point.c; sourceTree = ""; }; - 22C9187211933FCF0083AC69 /* pkcs_1_mgf1.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = pkcs_1_mgf1.c; sourceTree = ""; }; - 22C9187311933FCF0083AC69 /* pkcs_1_oaep_decode.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = pkcs_1_oaep_decode.c; sourceTree = ""; }; - 22C9187411933FCF0083AC69 /* pkcs_1_pss_decode.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = pkcs_1_pss_decode.c; sourceTree = ""; }; - 22C9187511933FCF0083AC69 /* pkcs_1_v1_5_decode.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = pkcs_1_v1_5_decode.c; sourceTree = ""; }; - 22C9187711933FCF0083AC69 /* rsa_exptmod.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = rsa_exptmod.c; sourceTree = ""; }; - 22C9187811933FCF0083AC69 /* rsa_free.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = rsa_free.c; sourceTree = ""; }; - 22C9187911933FCF0083AC69 /* rsa_import.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = rsa_import.c; sourceTree = ""; }; - 22C9187A11933FCF0083AC69 /* rsa_make_key.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = rsa_make_key.c; sourceTree = ""; }; - 22C9187B11933FCF0083AC69 /* rsa_verify_hash.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = rsa_verify_hash.c; sourceTree = ""; }; - 22C9187C11933FCF0083AC69 /* rsa_verify_simple.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = rsa_verify_simple.c; sourceTree = ""; }; - 22C919111193400A0083AC69 /* bn_fast_mp_invmod.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_fast_mp_invmod.c; sourceTree = ""; }; - 22C919121193400A0083AC69 /* bn_fast_mp_montgomery_reduce.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_fast_mp_montgomery_reduce.c; sourceTree = ""; }; - 22C919131193400A0083AC69 /* bn_fast_s_mp_mul_digs.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_fast_s_mp_mul_digs.c; sourceTree = ""; }; - 22C919141193400A0083AC69 /* bn_fast_s_mp_mul_high_digs.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_fast_s_mp_mul_high_digs.c; sourceTree = ""; }; - 22C919151193400A0083AC69 /* bn_fast_s_mp_sqr.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_fast_s_mp_sqr.c; sourceTree = ""; }; - 22C919161193400A0083AC69 /* bn_mp_2expt.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_2expt.c; sourceTree = ""; }; - 22C919171193400A0083AC69 /* bn_mp_abs.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_abs.c; sourceTree = ""; }; - 22C919181193400A0083AC69 /* bn_mp_add_d.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_add_d.c; sourceTree = ""; }; - 22C919191193400A0083AC69 /* bn_mp_add.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_add.c; sourceTree = ""; }; - 22C9191A1193400A0083AC69 /* bn_mp_addmod.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_addmod.c; sourceTree = ""; }; - 22C9191B1193400A0083AC69 /* bn_mp_and.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_and.c; sourceTree = ""; }; - 22C9191C1193400A0083AC69 /* bn_mp_clamp.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_clamp.c; sourceTree = ""; }; - 22C9191D1193400A0083AC69 /* bn_mp_clear_multi.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_clear_multi.c; sourceTree = ""; }; - 22C9191E1193400A0083AC69 /* bn_mp_clear.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_clear.c; sourceTree = ""; }; - 22C9191F1193400A0083AC69 /* bn_mp_cmp_d.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_cmp_d.c; sourceTree = ""; }; - 22C919201193400A0083AC69 /* bn_mp_cmp_mag.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_cmp_mag.c; sourceTree = ""; }; - 22C919211193400A0083AC69 /* bn_mp_cmp.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_cmp.c; sourceTree = ""; }; - 22C919221193400A0083AC69 /* bn_mp_cnt_lsb.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_cnt_lsb.c; sourceTree = ""; }; - 22C919231193400A0083AC69 /* bn_mp_copy.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_copy.c; sourceTree = ""; }; - 22C919241193400A0083AC69 /* bn_mp_count_bits.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_count_bits.c; sourceTree = ""; }; - 22C919251193400A0083AC69 /* bn_mp_div_2.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_div_2.c; sourceTree = ""; }; - 22C919261193400A0083AC69 /* bn_mp_div_2d.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_div_2d.c; sourceTree = ""; }; - 22C919271193400A0083AC69 /* bn_mp_div_3.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_div_3.c; sourceTree = ""; }; - 22C919281193400A0083AC69 /* bn_mp_div_d.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_div_d.c; sourceTree = ""; }; - 22C919291193400A0083AC69 /* bn_mp_div.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_div.c; sourceTree = ""; }; - 22C9192A1193400A0083AC69 /* bn_mp_dr_is_modulus.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_dr_is_modulus.c; sourceTree = ""; }; - 22C9192B1193400A0083AC69 /* bn_mp_dr_reduce.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_dr_reduce.c; sourceTree = ""; }; - 22C9192C1193400A0083AC69 /* bn_mp_dr_setup.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_dr_setup.c; sourceTree = ""; }; - 22C9192D1193400A0083AC69 /* bn_mp_exch.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_exch.c; sourceTree = ""; }; - 22C9192E1193400A0083AC69 /* bn_mp_expt_d.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_expt_d.c; sourceTree = ""; }; - 22C9192F1193400A0083AC69 /* bn_mp_exptmod_fast.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_exptmod_fast.c; sourceTree = ""; }; - 22C919301193400A0083AC69 /* bn_mp_exptmod.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_exptmod.c; sourceTree = ""; }; - 22C919311193400A0083AC69 /* bn_mp_exteuclid.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_exteuclid.c; sourceTree = ""; }; - 22C919321193400A0083AC69 /* bn_mp_fread.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_fread.c; sourceTree = ""; }; - 22C919331193400A0083AC69 /* bn_mp_fwrite.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_fwrite.c; sourceTree = ""; }; - 22C919341193400A0083AC69 /* bn_mp_gcd.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_gcd.c; sourceTree = ""; }; - 22C919351193400A0083AC69 /* bn_mp_get_int.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_get_int.c; sourceTree = ""; }; - 22C919361193400A0083AC69 /* bn_mp_grow.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_grow.c; sourceTree = ""; }; - 22C919371193400A0083AC69 /* bn_mp_init_copy.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_init_copy.c; sourceTree = ""; }; - 22C919381193400A0083AC69 /* bn_mp_init_multi.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_init_multi.c; sourceTree = ""; }; - 22C919391193400A0083AC69 /* bn_mp_init_set_int.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_init_set_int.c; sourceTree = ""; }; - 22C9193A1193400A0083AC69 /* bn_mp_init_set.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_init_set.c; sourceTree = ""; }; - 22C9193B1193400A0083AC69 /* bn_mp_init_size.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_init_size.c; sourceTree = ""; }; - 22C9193C1193400A0083AC69 /* bn_mp_init.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_init.c; sourceTree = ""; }; - 22C9193D1193400A0083AC69 /* bn_mp_invmod_slow.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_invmod_slow.c; sourceTree = ""; }; - 22C9193E1193400A0083AC69 /* bn_mp_invmod.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_invmod.c; sourceTree = ""; }; - 22C9193F1193400A0083AC69 /* bn_mp_is_square.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_is_square.c; sourceTree = ""; }; - 22C919401193400A0083AC69 /* bn_mp_jacobi.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_jacobi.c; sourceTree = ""; }; - 22C919411193400A0083AC69 /* bn_mp_karatsuba_mul.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_karatsuba_mul.c; sourceTree = ""; }; - 22C919421193400A0083AC69 /* bn_mp_karatsuba_sqr.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_karatsuba_sqr.c; sourceTree = ""; }; - 22C919431193400A0083AC69 /* bn_mp_lcm.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_lcm.c; sourceTree = ""; }; - 22C919441193400A0083AC69 /* bn_mp_lshd.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_lshd.c; sourceTree = ""; }; - 22C919451193400A0083AC69 /* bn_mp_mod_2d.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_mod_2d.c; sourceTree = ""; }; - 22C919461193400A0083AC69 /* bn_mp_mod_d.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_mod_d.c; sourceTree = ""; }; - 22C919471193400A0083AC69 /* bn_mp_mod.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_mod.c; sourceTree = ""; }; - 22C919481193400A0083AC69 /* bn_mp_montgomery_calc_normalization.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_montgomery_calc_normalization.c; sourceTree = ""; }; - 22C919491193400A0083AC69 /* bn_mp_montgomery_reduce.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_montgomery_reduce.c; sourceTree = ""; }; - 22C9194A1193400A0083AC69 /* bn_mp_montgomery_setup.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_montgomery_setup.c; sourceTree = ""; }; - 22C9194B1193400A0083AC69 /* bn_mp_mul_2.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_mul_2.c; sourceTree = ""; }; - 22C9194C1193400A0083AC69 /* bn_mp_mul_2d.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_mul_2d.c; sourceTree = ""; }; - 22C9194D1193400A0083AC69 /* bn_mp_mul_d.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_mul_d.c; sourceTree = ""; }; - 22C9194E1193400A0083AC69 /* bn_mp_mul.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_mul.c; sourceTree = ""; }; - 22C9194F1193400A0083AC69 /* bn_mp_mulmod.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_mulmod.c; sourceTree = ""; }; - 22C919501193400A0083AC69 /* bn_mp_n_root.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_n_root.c; sourceTree = ""; }; - 22C919511193400A0083AC69 /* bn_mp_neg.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_neg.c; sourceTree = ""; }; - 22C919521193400A0083AC69 /* bn_mp_or.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_or.c; sourceTree = ""; }; - 22C919531193400A0083AC69 /* bn_mp_prime_fermat.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_prime_fermat.c; sourceTree = ""; }; - 22C919541193400A0083AC69 /* bn_mp_prime_is_divisible.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_prime_is_divisible.c; sourceTree = ""; }; - 22C919551193400A0083AC69 /* bn_mp_prime_is_prime.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_prime_is_prime.c; sourceTree = ""; }; - 22C919561193400A0083AC69 /* bn_mp_prime_miller_rabin.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_prime_miller_rabin.c; sourceTree = ""; }; - 22C919571193400A0083AC69 /* bn_mp_prime_next_prime.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_prime_next_prime.c; sourceTree = ""; }; - 22C919581193400A0083AC69 /* bn_mp_prime_rabin_miller_trials.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_prime_rabin_miller_trials.c; sourceTree = ""; }; - 22C919591193400A0083AC69 /* bn_mp_prime_random_ex.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_prime_random_ex.c; sourceTree = ""; }; - 22C9195A1193400A0083AC69 /* bn_mp_radix_size.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_radix_size.c; sourceTree = ""; }; - 22C9195B1193400A0083AC69 /* bn_mp_radix_smap.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_radix_smap.c; sourceTree = ""; }; - 22C9195C1193400A0083AC69 /* bn_mp_rand.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_rand.c; sourceTree = ""; }; - 22C9195D1193400A0083AC69 /* bn_mp_read_radix.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_read_radix.c; sourceTree = ""; }; - 22C9195E1193400A0083AC69 /* bn_mp_read_signed_bin.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_read_signed_bin.c; sourceTree = ""; }; - 22C9195F1193400A0083AC69 /* bn_mp_read_unsigned_bin.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_read_unsigned_bin.c; sourceTree = ""; }; - 22C919601193400A0083AC69 /* bn_mp_reduce_2k_l.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_reduce_2k_l.c; sourceTree = ""; }; - 22C919611193400A0083AC69 /* bn_mp_reduce_2k_setup_l.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_reduce_2k_setup_l.c; sourceTree = ""; }; - 22C919621193400A0083AC69 /* bn_mp_reduce_2k_setup.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_reduce_2k_setup.c; sourceTree = ""; }; - 22C919631193400A0083AC69 /* bn_mp_reduce_2k.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_reduce_2k.c; sourceTree = ""; }; - 22C919641193400A0083AC69 /* bn_mp_reduce_is_2k_l.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_reduce_is_2k_l.c; sourceTree = ""; }; - 22C919651193400A0083AC69 /* bn_mp_reduce_is_2k.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_reduce_is_2k.c; sourceTree = ""; }; - 22C919661193400A0083AC69 /* bn_mp_reduce_setup.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_reduce_setup.c; sourceTree = ""; }; - 22C919671193400A0083AC69 /* bn_mp_reduce.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_reduce.c; sourceTree = ""; }; - 22C919681193400A0083AC69 /* bn_mp_rshd.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_rshd.c; sourceTree = ""; }; - 22C919691193400A0083AC69 /* bn_mp_set_int.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_set_int.c; sourceTree = ""; }; - 22C9196A1193400A0083AC69 /* bn_mp_set.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_set.c; sourceTree = ""; }; - 22C9196B1193400A0083AC69 /* bn_mp_shrink.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_shrink.c; sourceTree = ""; }; - 22C9196C1193400A0083AC69 /* bn_mp_signed_bin_size.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_signed_bin_size.c; sourceTree = ""; }; - 22C9196D1193400A0083AC69 /* bn_mp_sqr.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_sqr.c; sourceTree = ""; }; - 22C9196E1193400A0083AC69 /* bn_mp_sqrmod.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_sqrmod.c; sourceTree = ""; }; - 22C9196F1193400A0083AC69 /* bn_mp_sqrt.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_sqrt.c; sourceTree = ""; }; - 22C919701193400A0083AC69 /* bn_mp_sub_d.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_sub_d.c; sourceTree = ""; }; - 22C919711193400A0083AC69 /* bn_mp_sub.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_sub.c; sourceTree = ""; }; - 22C919721193400A0083AC69 /* bn_mp_submod.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_submod.c; sourceTree = ""; }; - 22C919731193400A0083AC69 /* bn_mp_to_signed_bin_n.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_to_signed_bin_n.c; sourceTree = ""; }; - 22C919741193400A0083AC69 /* bn_mp_to_signed_bin.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_to_signed_bin.c; sourceTree = ""; }; - 22C919751193400A0083AC69 /* bn_mp_to_unsigned_bin_n.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_to_unsigned_bin_n.c; sourceTree = ""; }; - 22C919761193400A0083AC69 /* bn_mp_to_unsigned_bin.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_to_unsigned_bin.c; sourceTree = ""; }; - 22C919771193400A0083AC69 /* bn_mp_toom_mul.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_toom_mul.c; sourceTree = ""; }; - 22C919781193400A0083AC69 /* bn_mp_toom_sqr.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_toom_sqr.c; sourceTree = ""; }; - 22C919791193400A0083AC69 /* bn_mp_toradix_n.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_toradix_n.c; sourceTree = ""; }; - 22C9197A1193400A0083AC69 /* bn_mp_toradix.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_toradix.c; sourceTree = ""; }; - 22C9197B1193400A0083AC69 /* bn_mp_unsigned_bin_size.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_unsigned_bin_size.c; sourceTree = ""; }; - 22C9197C1193400A0083AC69 /* bn_mp_xor.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_xor.c; sourceTree = ""; }; - 22C9197D1193400A0083AC69 /* bn_mp_zero.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_mp_zero.c; sourceTree = ""; }; - 22C9197E1193400A0083AC69 /* bn_prime_tab.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_prime_tab.c; sourceTree = ""; }; - 22C9197F1193400A0083AC69 /* bn_reverse.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_reverse.c; sourceTree = ""; }; - 22C919801193400A0083AC69 /* bn_s_mp_add.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_s_mp_add.c; sourceTree = ""; }; - 22C919811193400A0083AC69 /* bn_s_mp_exptmod.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_s_mp_exptmod.c; sourceTree = ""; }; - 22C919821193400A0083AC69 /* bn_s_mp_mul_digs.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_s_mp_mul_digs.c; sourceTree = ""; }; - 22C919831193400A0083AC69 /* bn_s_mp_mul_high_digs.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_s_mp_mul_high_digs.c; sourceTree = ""; }; - 22C919841193400A0083AC69 /* bn_s_mp_sqr.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_s_mp_sqr.c; sourceTree = ""; }; - 22C919851193400A0083AC69 /* bn_s_mp_sub.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bn_s_mp_sub.c; sourceTree = ""; }; - 22C919861193400A0083AC69 /* bncore.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bncore.c; sourceTree = ""; }; - 22C919871193400A0083AC69 /* tommath_class.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = tommath_class.h; sourceTree = ""; }; - 22C919881193400A0083AC69 /* tommath_superclass.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = tommath_superclass.h; sourceTree = ""; }; - 22C919891193400A0083AC69 /* tommath.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = tommath.h; sourceTree = ""; }; - 22EC6043154B28A000679228 /* FileStream.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = FileStream.h; path = src/FileStream.h; sourceTree = ""; }; - 22F5A9C41193DFBA00F8B121 /* SFileVerify.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = SFileVerify.cpp; path = src/SFileVerify.cpp; sourceTree = ""; }; - 32D20A8A0CF3902D00230E7A /* libbz2.dylib */ = {isa = PBXFileReference; lastKnownFileType = "compiled.mach-o.dylib"; name = libbz2.dylib; path = /usr/lib/libbz2.dylib; sourceTree = ""; }; - 32D20A8B0CF3902D00230E7A /* libz.dylib */ = {isa = PBXFileReference; lastKnownFileType = "compiled.mach-o.dylib"; name = libz.dylib; path = /usr/lib/libz.dylib; sourceTree = ""; }; - 32ED009C0D03542A00AB0B4E /* huff.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = huff.cpp; sourceTree = ""; }; - 32ED009D0D03542A00AB0B4E /* huff.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = huff.h; sourceTree = ""; }; - 32ED00A60D03542A00AB0B4E /* explode.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = explode.c; sourceTree = ""; }; - 32ED00A70D03542A00AB0B4E /* implode.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = implode.c; sourceTree = ""; }; - 32ED00A80D03542A00AB0B4E /* pklib.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = pklib.h; sourceTree = ""; }; - 32ED00A90D03542A00AB0B4E /* SFileAttributes.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = SFileAttributes.cpp; path = src/SFileAttributes.cpp; sourceTree = ""; }; - 32ED00AA0D03542A00AB0B4E /* SBaseCommon.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = SBaseCommon.cpp; path = src/SBaseCommon.cpp; sourceTree = ""; }; - 32ED00AB0D03542A00AB0B4E /* StormCommon.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = StormCommon.h; path = src/StormCommon.h; sourceTree = ""; }; - 32ED00AC0D03542A00AB0B4E /* SCompression.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = SCompression.cpp; path = src/SCompression.cpp; sourceTree = ""; }; - 32ED00AD0D03542A00AB0B4E /* SFileCompactArchive.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = SFileCompactArchive.cpp; path = src/SFileCompactArchive.cpp; sourceTree = ""; }; - 32ED00AE0D03542A00AB0B4E /* SFileCreateArchive.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = SFileCreateArchive.cpp; path = src/SFileCreateArchive.cpp; sourceTree = ""; }; - 32ED00AF0D03542A00AB0B4E /* SFileExtractFile.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = SFileExtractFile.cpp; path = src/SFileExtractFile.cpp; sourceTree = ""; }; - 32ED00B00D03542A00AB0B4E /* SFileFindFile.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = SFileFindFile.cpp; path = src/SFileFindFile.cpp; sourceTree = ""; }; - 32ED00B10D03542A00AB0B4E /* SFileOpenArchive.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = SFileOpenArchive.cpp; path = src/SFileOpenArchive.cpp; sourceTree = ""; }; - 32ED00B20D03542A00AB0B4E /* SFileOpenFileEx.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = SFileOpenFileEx.cpp; path = src/SFileOpenFileEx.cpp; sourceTree = ""; }; - 32ED00B30D03542A00AB0B4E /* SFileReadFile.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = SFileReadFile.cpp; path = src/SFileReadFile.cpp; sourceTree = ""; }; - 32ED00B40D03542A00AB0B4E /* SFileListFile.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = SFileListFile.cpp; path = src/SFileListFile.cpp; sourceTree = ""; }; - 32ED00B60D03542A00AB0B4E /* StormLib.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = StormLib.h; path = src/StormLib.h; sourceTree = ""; }; - 32ED00B70D03542A00AB0B4E /* StormPort.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = StormPort.h; path = src/StormPort.h; sourceTree = ""; }; - E60816D51B707A9000B283F7 /* rsa_sign_hash.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = rsa_sign_hash.c; sourceTree = ""; }; - E60816D81B707B1800B283F7 /* pkcs_1_pss_encode.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = pkcs_1_pss_encode.c; sourceTree = ""; }; - E60816DB1B707B2700B283F7 /* pkcs_1_v1_5_encode.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = pkcs_1_v1_5_encode.c; sourceTree = ""; }; - E60816DE1B707B5700B283F7 /* der_encode_sequence_ex.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_encode_sequence_ex.c; sourceTree = ""; }; - E60816E11B707B7200B283F7 /* der_encode_bit_string.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_encode_bit_string.c; sourceTree = ""; }; - E60816E21B707B7200B283F7 /* der_encode_boolean.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_encode_boolean.c; sourceTree = ""; }; - E60816E31B707B7200B283F7 /* der_encode_ia5_string.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_encode_ia5_string.c; sourceTree = ""; }; - E60816E41B707B7200B283F7 /* der_encode_integer.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_encode_integer.c; sourceTree = ""; }; - E60816E51B707B7200B283F7 /* der_encode_object_identifier.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_encode_object_identifier.c; sourceTree = ""; }; - E60816E61B707B7200B283F7 /* der_encode_octet_string.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_encode_octet_string.c; sourceTree = ""; }; - E60816E71B707B7200B283F7 /* der_encode_printable_string.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_encode_printable_string.c; sourceTree = ""; }; - E60816E81B707B7200B283F7 /* der_encode_sequence_multi.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_encode_sequence_multi.c; sourceTree = ""; }; - E60816E91B707B7200B283F7 /* der_encode_set.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_encode_set.c; sourceTree = ""; }; - E60816EA1B707B7200B283F7 /* der_encode_setof.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_encode_setof.c; sourceTree = ""; }; - E60816EB1B707B7200B283F7 /* der_encode_short_integer.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_encode_short_integer.c; sourceTree = ""; }; - E60816EC1B707B7200B283F7 /* der_encode_utctime.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_encode_utctime.c; sourceTree = ""; }; - E60816ED1B707B7200B283F7 /* der_encode_utf8_string.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = der_encode_utf8_string.c; sourceTree = ""; }; -/* End PBXFileReference section */ - -/* Begin PBXFrameworksBuildPhase section */ - 225530D21056BAC800FA646A /* Frameworks */ = { - isa = PBXFrameworksBuildPhase; - buildActionMask = 2147483647; - files = ( - ); - runOnlyForDeploymentPostprocessing = 0; - }; - 225FAC920E53B7F800DA2CAE /* Frameworks */ = { - isa = PBXFrameworksBuildPhase; - buildActionMask = 2147483647; - files = ( - 225FADD40E53C06600DA2CAE /* libbz2.dylib in Frameworks */, - 225FADD50E53C06600DA2CAE /* libz.dylib in Frameworks */, - ); - runOnlyForDeploymentPostprocessing = 0; - }; - 22954ACC11D463A30064B264 /* Frameworks */ = { - isa = PBXFrameworksBuildPhase; - buildActionMask = 2147483647; - files = ( - 22954AD611D463BE0064B264 /* libbz2.dylib in Frameworks */, - 22954AD711D463BE0064B264 /* libz.dylib in Frameworks */, - 22954AD311D463B50064B264 /* libStormLib.a in Frameworks */, - ); - runOnlyForDeploymentPostprocessing = 0; - }; -/* End PBXFrameworksBuildPhase section */ - -/* Begin PBXGroup section */ - 034768DDFF38A45A11DB9C8B /* Products */ = { - isa = PBXGroup; - children = ( - 225FAC940E53B7F800DA2CAE /* StormLib.framework */, - 225530D41056BAC800FA646A /* libStormLib.a */, - 22954ACE11D463A30064B264 /* StormLib_Test */, - ); - name = Products; - sourceTree = ""; - }; - 0867D691FE84028FC02AAC07 /* stormlib */ = { - isa = PBXGroup; - children = ( - 32DBEE830D00E58F00DB1E81 /* Source */, - 2295488711D45A520064B264 /* Test */, - 0867D69AFE84028FC02AAC07 /* External Frameworks and Libraries */, - 22B54B321054B287001D6436 /* Resources */, - 034768DDFF38A45A11DB9C8B /* Products */, - 2253A19F10568A83001909F9 /* StormLib.exp */, - ); - name = stormlib; - sourceTree = ""; - }; - 0867D69AFE84028FC02AAC07 /* External Frameworks and Libraries */ = { - isa = PBXGroup; - children = ( - 32D20A8A0CF3902D00230E7A /* libbz2.dylib */, - 32D20A8B0CF3902D00230E7A /* libz.dylib */, - ); - name = "External Frameworks and Libraries"; - sourceTree = ""; - }; - 221F652D116851D70026C852 /* lzma */ = { - isa = PBXGroup; - children = ( - 221F6AB31168545B0026C852 /* LzFind.c */, - 221F6AB41168545B0026C852 /* LzFind.h */, - 221F6AB9116854730026C852 /* LzHash.h */, - 221F6A7D116852B20026C852 /* LzmaDec.c */, - 221F6A721168529C0026C852 /* LzmaDec.h */, - 221F6A7A116852AA0026C852 /* LzmaEnc.c */, - 221F6A731168529C0026C852 /* LzmaEnc.h */, - 221F6ABC116854870026C852 /* Types.h */, - ); - name = lzma; - path = src/lzma; - sourceTree = ""; - }; - 225C734A1257CCC70009E8DA /* jenkins */ = { - isa = PBXGroup; - children = ( - 225C734B1257CCC70009E8DA /* lookup.h */, - 225C734C1257CCC70009E8DA /* lookup3.c */, - ); - name = jenkins; - path = src/jenkins; - sourceTree = ""; - }; - 2295488711D45A520064B264 /* Test */ = { - isa = PBXGroup; - children = ( - 2295488911D45A820064B264 /* Test.cpp */, - ); - name = Test; - sourceTree = ""; - }; - 2299D9D41167EFA8005C19BF /* adpcm */ = { - isa = PBXGroup; - children = ( - 2299D9D51167EFA8005C19BF /* adpcm.cpp */, - 2299D9D61167EFA8005C19BF /* adpcm.h */, - ); - name = adpcm; - path = src/adpcm; - sourceTree = ""; - }; - 2299D9DB1167EFC6005C19BF /* sparse */ = { - isa = PBXGroup; - children = ( - 2299D9DC1167EFC6005C19BF /* sparse.cpp */, - 2299D9DD1167EFC6005C19BF /* sparse.h */, - ); - name = sparse; - path = src/sparse; - sourceTree = ""; - }; - 22B54B321054B287001D6436 /* Resources */ = { - isa = PBXGroup; - children = ( - 225FAC950E53B7F800DA2CAE /* Info.plist */, - ); - name = Resources; - sourceTree = ""; - }; - 22C9181D11933E3A0083AC69 /* libtomcrypt */ = { - isa = PBXGroup; - children = ( - 22C9182A11933FCF0083AC69 /* hashes */, - 22C9182E11933FCF0083AC69 /* headers */, - 22C9183C11933FCF0083AC69 /* math */, - 22C9184011933FCF0083AC69 /* misc */, - 22C9184E11933FCF0083AC69 /* pk */, - ); - name = libtomcrypt; - path = src/libtomcrypt; - sourceTree = ""; - }; - 22C9181E11933E470083AC69 /* libtommath */ = { - isa = PBXGroup; - children = ( - 22C919111193400A0083AC69 /* bn_fast_mp_invmod.c */, - 22C919121193400A0083AC69 /* bn_fast_mp_montgomery_reduce.c */, - 22C919131193400A0083AC69 /* bn_fast_s_mp_mul_digs.c */, - 22C919141193400A0083AC69 /* bn_fast_s_mp_mul_high_digs.c */, - 22C919151193400A0083AC69 /* bn_fast_s_mp_sqr.c */, - 22C919161193400A0083AC69 /* bn_mp_2expt.c */, - 22C919171193400A0083AC69 /* bn_mp_abs.c */, - 22C919181193400A0083AC69 /* bn_mp_add_d.c */, - 22C919191193400A0083AC69 /* bn_mp_add.c */, - 22C9191A1193400A0083AC69 /* bn_mp_addmod.c */, - 22C9191B1193400A0083AC69 /* bn_mp_and.c */, - 22C9191C1193400A0083AC69 /* bn_mp_clamp.c */, - 22C9191D1193400A0083AC69 /* bn_mp_clear_multi.c */, - 22C9191E1193400A0083AC69 /* bn_mp_clear.c */, - 22C9191F1193400A0083AC69 /* bn_mp_cmp_d.c */, - 22C919201193400A0083AC69 /* bn_mp_cmp_mag.c */, - 22C919211193400A0083AC69 /* bn_mp_cmp.c */, - 22C919221193400A0083AC69 /* bn_mp_cnt_lsb.c */, - 22C919231193400A0083AC69 /* bn_mp_copy.c */, - 22C919241193400A0083AC69 /* bn_mp_count_bits.c */, - 22C919251193400A0083AC69 /* bn_mp_div_2.c */, - 22C919261193400A0083AC69 /* bn_mp_div_2d.c */, - 22C919271193400A0083AC69 /* bn_mp_div_3.c */, - 22C919281193400A0083AC69 /* bn_mp_div_d.c */, - 22C919291193400A0083AC69 /* bn_mp_div.c */, - 22C9192A1193400A0083AC69 /* bn_mp_dr_is_modulus.c */, - 22C9192B1193400A0083AC69 /* bn_mp_dr_reduce.c */, - 22C9192C1193400A0083AC69 /* bn_mp_dr_setup.c */, - 22C9192D1193400A0083AC69 /* bn_mp_exch.c */, - 22C9192E1193400A0083AC69 /* bn_mp_expt_d.c */, - 22C9192F1193400A0083AC69 /* bn_mp_exptmod_fast.c */, - 22C919301193400A0083AC69 /* bn_mp_exptmod.c */, - 22C919311193400A0083AC69 /* bn_mp_exteuclid.c */, - 22C919321193400A0083AC69 /* bn_mp_fread.c */, - 22C919331193400A0083AC69 /* bn_mp_fwrite.c */, - 22C919341193400A0083AC69 /* bn_mp_gcd.c */, - 22C919351193400A0083AC69 /* bn_mp_get_int.c */, - 22C919361193400A0083AC69 /* bn_mp_grow.c */, - 22C919371193400A0083AC69 /* bn_mp_init_copy.c */, - 22C919381193400A0083AC69 /* bn_mp_init_multi.c */, - 22C919391193400A0083AC69 /* bn_mp_init_set_int.c */, - 22C9193A1193400A0083AC69 /* bn_mp_init_set.c */, - 22C9193B1193400A0083AC69 /* bn_mp_init_size.c */, - 22C9193C1193400A0083AC69 /* bn_mp_init.c */, - 22C9193D1193400A0083AC69 /* bn_mp_invmod_slow.c */, - 22C9193E1193400A0083AC69 /* bn_mp_invmod.c */, - 22C9193F1193400A0083AC69 /* bn_mp_is_square.c */, - 22C919401193400A0083AC69 /* bn_mp_jacobi.c */, - 22C919411193400A0083AC69 /* bn_mp_karatsuba_mul.c */, - 22C919421193400A0083AC69 /* bn_mp_karatsuba_sqr.c */, - 22C919431193400A0083AC69 /* bn_mp_lcm.c */, - 22C919441193400A0083AC69 /* bn_mp_lshd.c */, - 22C919451193400A0083AC69 /* bn_mp_mod_2d.c */, - 22C919461193400A0083AC69 /* bn_mp_mod_d.c */, - 22C919471193400A0083AC69 /* bn_mp_mod.c */, - 22C919481193400A0083AC69 /* bn_mp_montgomery_calc_normalization.c */, - 22C919491193400A0083AC69 /* bn_mp_montgomery_reduce.c */, - 22C9194A1193400A0083AC69 /* bn_mp_montgomery_setup.c */, - 22C9194B1193400A0083AC69 /* bn_mp_mul_2.c */, - 22C9194C1193400A0083AC69 /* bn_mp_mul_2d.c */, - 22C9194D1193400A0083AC69 /* bn_mp_mul_d.c */, - 22C9194E1193400A0083AC69 /* bn_mp_mul.c */, - 22C9194F1193400A0083AC69 /* bn_mp_mulmod.c */, - 22C919501193400A0083AC69 /* bn_mp_n_root.c */, - 22C919511193400A0083AC69 /* bn_mp_neg.c */, - 22C919521193400A0083AC69 /* bn_mp_or.c */, - 22C919531193400A0083AC69 /* bn_mp_prime_fermat.c */, - 22C919541193400A0083AC69 /* bn_mp_prime_is_divisible.c */, - 22C919551193400A0083AC69 /* bn_mp_prime_is_prime.c */, - 22C919561193400A0083AC69 /* bn_mp_prime_miller_rabin.c */, - 22C919571193400A0083AC69 /* bn_mp_prime_next_prime.c */, - 22C919581193400A0083AC69 /* bn_mp_prime_rabin_miller_trials.c */, - 22C919591193400A0083AC69 /* bn_mp_prime_random_ex.c */, - 22C9195A1193400A0083AC69 /* bn_mp_radix_size.c */, - 22C9195B1193400A0083AC69 /* bn_mp_radix_smap.c */, - 22C9195C1193400A0083AC69 /* bn_mp_rand.c */, - 22C9195D1193400A0083AC69 /* bn_mp_read_radix.c */, - 22C9195E1193400A0083AC69 /* bn_mp_read_signed_bin.c */, - 22C9195F1193400A0083AC69 /* bn_mp_read_unsigned_bin.c */, - 22C919601193400A0083AC69 /* bn_mp_reduce_2k_l.c */, - 22C919611193400A0083AC69 /* bn_mp_reduce_2k_setup_l.c */, - 22C919621193400A0083AC69 /* bn_mp_reduce_2k_setup.c */, - 22C919631193400A0083AC69 /* bn_mp_reduce_2k.c */, - 22C919641193400A0083AC69 /* bn_mp_reduce_is_2k_l.c */, - 22C919651193400A0083AC69 /* bn_mp_reduce_is_2k.c */, - 22C919661193400A0083AC69 /* bn_mp_reduce_setup.c */, - 22C919671193400A0083AC69 /* bn_mp_reduce.c */, - 22C919681193400A0083AC69 /* bn_mp_rshd.c */, - 22C919691193400A0083AC69 /* bn_mp_set_int.c */, - 22C9196A1193400A0083AC69 /* bn_mp_set.c */, - 22C9196B1193400A0083AC69 /* bn_mp_shrink.c */, - 22C9196C1193400A0083AC69 /* bn_mp_signed_bin_size.c */, - 22C9196D1193400A0083AC69 /* bn_mp_sqr.c */, - 22C9196E1193400A0083AC69 /* bn_mp_sqrmod.c */, - 22C9196F1193400A0083AC69 /* bn_mp_sqrt.c */, - 22C919701193400A0083AC69 /* bn_mp_sub_d.c */, - 22C919711193400A0083AC69 /* bn_mp_sub.c */, - 22C919721193400A0083AC69 /* bn_mp_submod.c */, - 22C919731193400A0083AC69 /* bn_mp_to_signed_bin_n.c */, - 22C919741193400A0083AC69 /* bn_mp_to_signed_bin.c */, - 22C919751193400A0083AC69 /* bn_mp_to_unsigned_bin_n.c */, - 22C919761193400A0083AC69 /* bn_mp_to_unsigned_bin.c */, - 22C919771193400A0083AC69 /* bn_mp_toom_mul.c */, - 22C919781193400A0083AC69 /* bn_mp_toom_sqr.c */, - 22C919791193400A0083AC69 /* bn_mp_toradix_n.c */, - 22C9197A1193400A0083AC69 /* bn_mp_toradix.c */, - 22C9197B1193400A0083AC69 /* bn_mp_unsigned_bin_size.c */, - 22C9197C1193400A0083AC69 /* bn_mp_xor.c */, - 22C9197D1193400A0083AC69 /* bn_mp_zero.c */, - 22C9197E1193400A0083AC69 /* bn_prime_tab.c */, - 22C9197F1193400A0083AC69 /* bn_reverse.c */, - 22C919801193400A0083AC69 /* bn_s_mp_add.c */, - 22C919811193400A0083AC69 /* bn_s_mp_exptmod.c */, - 22C919821193400A0083AC69 /* bn_s_mp_mul_digs.c */, - 22C919831193400A0083AC69 /* bn_s_mp_mul_high_digs.c */, - 22C919841193400A0083AC69 /* bn_s_mp_sqr.c */, - 22C919851193400A0083AC69 /* bn_s_mp_sub.c */, - 22C919861193400A0083AC69 /* bncore.c */, - 22C919871193400A0083AC69 /* tommath_class.h */, - 22C919881193400A0083AC69 /* tommath_superclass.h */, - 22C919891193400A0083AC69 /* tommath.h */, - ); - name = libtommath; - path = src/libtommath; - sourceTree = ""; - }; - 22C9182A11933FCF0083AC69 /* hashes */ = { - isa = PBXGroup; - children = ( - 22C9182B11933FCF0083AC69 /* hash_memory.c */, - 22C9182C11933FCF0083AC69 /* md5.c */, - 22C9182D11933FCF0083AC69 /* sha1.c */, - ); - name = hashes; - path = src/hashes; - sourceTree = ""; - }; - 22C9182E11933FCF0083AC69 /* headers */ = { - isa = PBXGroup; - children = ( - 22C9182F11933FCF0083AC69 /* tomcrypt.h */, - 22C9183011933FCF0083AC69 /* tomcrypt_argchk.h */, - 22C9183111933FCF0083AC69 /* tomcrypt_cfg.h */, - 22C9183211933FCF0083AC69 /* tomcrypt_cipher.h */, - 22C9183311933FCF0083AC69 /* tomcrypt_custom.h */, - 22C9183411933FCF0083AC69 /* tomcrypt_hash.h */, - 22C9183511933FCF0083AC69 /* tomcrypt_mac.h */, - 22C9183611933FCF0083AC69 /* tomcrypt_macros.h */, - 22C9183711933FCF0083AC69 /* tomcrypt_math.h */, - 22C9183811933FCF0083AC69 /* tomcrypt_misc.h */, - 22C9183911933FCF0083AC69 /* tomcrypt_pk.h */, - 22C9183A11933FCF0083AC69 /* tomcrypt_pkcs.h */, - 22C9183B11933FCF0083AC69 /* tomcrypt_prng.h */, - ); - name = headers; - path = src/headers; - sourceTree = ""; - }; - 22C9183C11933FCF0083AC69 /* math */ = { - isa = PBXGroup; - children = ( - 22C9183D11933FCF0083AC69 /* ltm_desc.c */, - 22C9183E11933FCF0083AC69 /* multi.c */, - 22C9183F11933FCF0083AC69 /* rand_prime.c */, - ); - name = math; - path = src/math; - sourceTree = ""; - }; - 22C9184011933FCF0083AC69 /* misc */ = { - isa = PBXGroup; - children = ( - 22C9184111933FCF0083AC69 /* base64_decode.c */, - 22C9184211933FCF0083AC69 /* crypt_argchk.c */, - 22C9184311933FCF0083AC69 /* crypt_find_hash.c */, - 22C9184411933FCF0083AC69 /* crypt_find_prng.c */, - 22C9184511933FCF0083AC69 /* crypt_hash_descriptor.c */, - 22C9184611933FCF0083AC69 /* crypt_hash_is_valid.c */, - 22C9184711933FCF0083AC69 /* crypt_libc.c */, - 22C9184811933FCF0083AC69 /* crypt_ltc_mp_descriptor.c */, - 22C9184911933FCF0083AC69 /* crypt_prng_descriptor.c */, - 22C9184A11933FCF0083AC69 /* crypt_prng_is_valid.c */, - 22C9184B11933FCF0083AC69 /* crypt_register_hash.c */, - 22C9184C11933FCF0083AC69 /* crypt_register_prng.c */, - 22C9184D11933FCF0083AC69 /* zeromem.c */, - ); - name = misc; - path = src/misc; - sourceTree = ""; - }; - 22C9184E11933FCF0083AC69 /* pk */ = { - isa = PBXGroup; - children = ( - 22C9184F11933FCF0083AC69 /* asn1 */, - 22C9186A11933FCF0083AC69 /* ecc */, - 22C9187111933FCF0083AC69 /* pkcs1 */, - 22C9187611933FCF0083AC69 /* rsa */, - ); - name = pk; - path = src/pk; - sourceTree = ""; - }; - 22C9184F11933FCF0083AC69 /* asn1 */ = { - isa = PBXGroup; - children = ( - E60816E11B707B7200B283F7 /* der_encode_bit_string.c */, - E60816E21B707B7200B283F7 /* der_encode_boolean.c */, - E60816E31B707B7200B283F7 /* der_encode_ia5_string.c */, - E60816E41B707B7200B283F7 /* der_encode_integer.c */, - E60816E51B707B7200B283F7 /* der_encode_object_identifier.c */, - E60816E61B707B7200B283F7 /* der_encode_octet_string.c */, - E60816E71B707B7200B283F7 /* der_encode_printable_string.c */, - E60816E81B707B7200B283F7 /* der_encode_sequence_multi.c */, - E60816E91B707B7200B283F7 /* der_encode_set.c */, - E60816EA1B707B7200B283F7 /* der_encode_setof.c */, - E60816EB1B707B7200B283F7 /* der_encode_short_integer.c */, - E60816EC1B707B7200B283F7 /* der_encode_utctime.c */, - E60816ED1B707B7200B283F7 /* der_encode_utf8_string.c */, - E60816DE1B707B5700B283F7 /* der_encode_sequence_ex.c */, - 22C9185011933FCF0083AC69 /* der_decode_bit_string.c */, - 22C9185111933FCF0083AC69 /* der_decode_boolean.c */, - 22C9185211933FCF0083AC69 /* der_decode_choice.c */, - 22C9185311933FCF0083AC69 /* der_decode_ia5_string.c */, - 22C9185411933FCF0083AC69 /* der_decode_integer.c */, - 22C9185511933FCF0083AC69 /* der_decode_object_identifier.c */, - 22C9185611933FCF0083AC69 /* der_decode_octet_string.c */, - 22C9185711933FCF0083AC69 /* der_decode_printable_string.c */, - 22C9185811933FCF0083AC69 /* der_decode_sequence_ex.c */, - 22C9185911933FCF0083AC69 /* der_decode_sequence_flexi.c */, - 22C9185A11933FCF0083AC69 /* der_decode_sequence_multi.c */, - 22C9185B11933FCF0083AC69 /* der_decode_short_integer.c */, - 22C9185C11933FCF0083AC69 /* der_decode_utctime.c */, - 22C9185D11933FCF0083AC69 /* der_decode_utf8_string.c */, - 22C9185E11933FCF0083AC69 /* der_length_bit_string.c */, - 22C9185F11933FCF0083AC69 /* der_length_boolean.c */, - 22C9186011933FCF0083AC69 /* der_length_ia5_string.c */, - 22C9186111933FCF0083AC69 /* der_length_integer.c */, - 22C9186211933FCF0083AC69 /* der_length_object_identifier.c */, - 22C9186311933FCF0083AC69 /* der_length_octet_string.c */, - 22C9186411933FCF0083AC69 /* der_length_printable_string.c */, - 22C9186511933FCF0083AC69 /* der_length_sequence.c */, - 22C9186611933FCF0083AC69 /* der_length_short_integer.c */, - 22C9186711933FCF0083AC69 /* der_length_utctime.c */, - 22C9186811933FCF0083AC69 /* der_length_utf8_string.c */, - 22C9186911933FCF0083AC69 /* der_sequence_free.c */, - ); - path = asn1; - sourceTree = ""; - }; - 22C9186A11933FCF0083AC69 /* ecc */ = { - isa = PBXGroup; - children = ( - 22C9186B11933FCF0083AC69 /* ltc_ecc_map.c */, - 22C9186C11933FCF0083AC69 /* ltc_ecc_mul2add.c */, - 22C9186D11933FCF0083AC69 /* ltc_ecc_mulmod.c */, - 22C9186E11933FCF0083AC69 /* ltc_ecc_points.c */, - 22C9186F11933FCF0083AC69 /* ltc_ecc_projective_add_point.c */, - 22C9187011933FCF0083AC69 /* ltc_ecc_projective_dbl_point.c */, - ); - path = ecc; - sourceTree = ""; - }; - 22C9187111933FCF0083AC69 /* pkcs1 */ = { - isa = PBXGroup; - children = ( - E60816DB1B707B2700B283F7 /* pkcs_1_v1_5_encode.c */, - E60816D81B707B1800B283F7 /* pkcs_1_pss_encode.c */, - 22C9187211933FCF0083AC69 /* pkcs_1_mgf1.c */, - 22C9187311933FCF0083AC69 /* pkcs_1_oaep_decode.c */, - 22C9187411933FCF0083AC69 /* pkcs_1_pss_decode.c */, - 22C9187511933FCF0083AC69 /* pkcs_1_v1_5_decode.c */, - ); - path = pkcs1; - sourceTree = ""; - }; - 22C9187611933FCF0083AC69 /* rsa */ = { - isa = PBXGroup; - children = ( - E60816D51B707A9000B283F7 /* rsa_sign_hash.c */, - 22C9187711933FCF0083AC69 /* rsa_exptmod.c */, - 22C9187811933FCF0083AC69 /* rsa_free.c */, - 22C9187911933FCF0083AC69 /* rsa_import.c */, - 22C9187A11933FCF0083AC69 /* rsa_make_key.c */, - 22C9187B11933FCF0083AC69 /* rsa_verify_hash.c */, - 22C9187C11933FCF0083AC69 /* rsa_verify_simple.c */, - ); - path = rsa; - sourceTree = ""; - }; - 32DBEE830D00E58F00DB1E81 /* Source */ = { - isa = PBXGroup; - children = ( - 2299D9D41167EFA8005C19BF /* adpcm */, - 32ED009B0D03542A00AB0B4E /* huffman */, - 225C734A1257CCC70009E8DA /* jenkins */, - 22C9181D11933E3A0083AC69 /* libtomcrypt */, - 22C9181E11933E470083AC69 /* libtommath */, - 221F652D116851D70026C852 /* lzma */, - 32ED00A40D03542A00AB0B4E /* pklib */, - 2299D9DB1167EFC6005C19BF /* sparse */, - 228B538311BF7D0D001A58DA /* FileStream.cpp */, - 22EC6043154B28A000679228 /* FileStream.h */, - 32ED00AA0D03542A00AB0B4E /* SBaseCommon.cpp */, - 226C7CA61857DE9400AB689C /* SBaseDumpData.cpp */, - 225C73531257CD0C0009E8DA /* SBaseFileTable.cpp */, - 226C7CA91857DEAC00AB689C /* SBaseSubTypes.cpp */, - 32ED00AC0D03542A00AB0B4E /* SCompression.cpp */, - 2299DA4D1167FD16005C19BF /* SFileAddFile.cpp */, - 32ED00A90D03542A00AB0B4E /* SFileAttributes.cpp */, - 32ED00AD0D03542A00AB0B4E /* SFileCompactArchive.cpp */, - 32ED00AE0D03542A00AB0B4E /* SFileCreateArchive.cpp */, - 32ED00AF0D03542A00AB0B4E /* SFileExtractFile.cpp */, - 32ED00B00D03542A00AB0B4E /* SFileFindFile.cpp */, - 226C7CAC1857DEEB00AB689C /* SFileGetFileInfo.cpp */, - 32ED00B40D03542A00AB0B4E /* SFileListFile.cpp */, - 32ED00B10D03542A00AB0B4E /* SFileOpenArchive.cpp */, - 32ED00B20D03542A00AB0B4E /* SFileOpenFileEx.cpp */, - 22AEA121123125D800359B16 /* SFilePatchArchives.cpp */, - 32ED00B30D03542A00AB0B4E /* SFileReadFile.cpp */, - 22F5A9C41193DFBA00F8B121 /* SFileVerify.cpp */, - 32ED00AB0D03542A00AB0B4E /* StormCommon.h */, - 32ED00B60D03542A00AB0B4E /* StormLib.h */, - 32ED00B70D03542A00AB0B4E /* StormPort.h */, - ); - name = Source; - sourceTree = ""; - }; - 32ED009B0D03542A00AB0B4E /* huffman */ = { - isa = PBXGroup; - children = ( - 32ED009C0D03542A00AB0B4E /* huff.cpp */, - 32ED009D0D03542A00AB0B4E /* huff.h */, - ); - name = huffman; - path = src/huffman; - sourceTree = ""; - }; - 32ED00A40D03542A00AB0B4E /* pklib */ = { - isa = PBXGroup; - children = ( - 32ED00A60D03542A00AB0B4E /* explode.c */, - 32ED00A70D03542A00AB0B4E /* implode.c */, - 32ED00A80D03542A00AB0B4E /* pklib.h */, - ); - name = pklib; - path = src/pklib; - sourceTree = ""; - }; -/* End PBXGroup section */ - -/* Begin PBXHeadersBuildPhase section */ - 225530D01056BAC800FA646A /* Headers */ = { - isa = PBXHeadersBuildPhase; - buildActionMask = 2147483647; - files = ( - 225530DB1056BC7900FA646A /* huff.h in Headers */, - 225530DE1056BC7900FA646A /* pklib.h in Headers */, - 225530DF1056BC7900FA646A /* StormCommon.h in Headers */, - 225530E01056BC7900FA646A /* StormLib.h in Headers */, - 225530E11056BC7900FA646A /* StormPort.h in Headers */, - 2299D9DA1167EFA8005C19BF /* adpcm.h in Headers */, - 2299D9E11167EFC6005C19BF /* sparse.h in Headers */, - 221F6A761168529C0026C852 /* LzmaDec.h in Headers */, - 221F6A771168529C0026C852 /* LzmaEnc.h in Headers */, - 221F6AB81168545B0026C852 /* LzFind.h in Headers */, - 221F6ABB116854730026C852 /* LzHash.h in Headers */, - 221F6ABE116854870026C852 /* Types.h in Headers */, - 22C9188011933FCF0083AC69 /* tomcrypt.h in Headers */, - 22C9188111933FCF0083AC69 /* tomcrypt_argchk.h in Headers */, - 22C9188211933FCF0083AC69 /* tomcrypt_cfg.h in Headers */, - 22C9188311933FCF0083AC69 /* tomcrypt_cipher.h in Headers */, - 22C9188411933FCF0083AC69 /* tomcrypt_custom.h in Headers */, - 22C9188511933FCF0083AC69 /* tomcrypt_hash.h in Headers */, - 22C9188611933FCF0083AC69 /* tomcrypt_mac.h in Headers */, - 22C9188711933FCF0083AC69 /* tomcrypt_macros.h in Headers */, - 22C9188811933FCF0083AC69 /* tomcrypt_math.h in Headers */, - 22C9188911933FCF0083AC69 /* tomcrypt_misc.h in Headers */, - 22C9188A11933FCF0083AC69 /* tomcrypt_pk.h in Headers */, - 22C9188B11933FCF0083AC69 /* tomcrypt_pkcs.h in Headers */, - 22C9188C11933FCF0083AC69 /* tomcrypt_prng.h in Headers */, - 22C91A001193400A0083AC69 /* tommath_class.h in Headers */, - 22C91A011193400A0083AC69 /* tommath_superclass.h in Headers */, - 22C91A021193400A0083AC69 /* tommath.h in Headers */, - 225C734F1257CCC70009E8DA /* lookup.h in Headers */, - 22EC6044154B28A000679228 /* FileStream.h in Headers */, - ); - runOnlyForDeploymentPostprocessing = 0; - }; - 225FAC8F0E53B7F800DA2CAE /* Headers */ = { - isa = PBXHeadersBuildPhase; - buildActionMask = 2147483647; - files = ( - 225FAC9C0E53BAA100DA2CAE /* huff.h in Headers */, - 225FAC9F0E53BAA100DA2CAE /* pklib.h in Headers */, - 225FACA00E53BAA100DA2CAE /* StormCommon.h in Headers */, - 225FACA10E53BAA100DA2CAE /* StormLib.h in Headers */, - 225FACA20E53BAA100DA2CAE /* StormPort.h in Headers */, - 2299D9D81167EFA8005C19BF /* adpcm.h in Headers */, - 2299D9DF1167EFC6005C19BF /* sparse.h in Headers */, - 221F6A741168529C0026C852 /* LzmaDec.h in Headers */, - 221F6A751168529C0026C852 /* LzmaEnc.h in Headers */, - 221F6AB61168545B0026C852 /* LzFind.h in Headers */, - 221F6ABA116854730026C852 /* LzHash.h in Headers */, - 221F6ABD116854870026C852 /* Types.h in Headers */, - 22C918CA11933FCF0083AC69 /* tomcrypt.h in Headers */, - 22C918CB11933FCF0083AC69 /* tomcrypt_argchk.h in Headers */, - 22C918CC11933FCF0083AC69 /* tomcrypt_cfg.h in Headers */, - 22C918CD11933FCF0083AC69 /* tomcrypt_cipher.h in Headers */, - 22C918CE11933FCF0083AC69 /* tomcrypt_custom.h in Headers */, - 22C918CF11933FCF0083AC69 /* tomcrypt_hash.h in Headers */, - 22C918D011933FCF0083AC69 /* tomcrypt_mac.h in Headers */, - 22C918D111933FCF0083AC69 /* tomcrypt_macros.h in Headers */, - 22C918D211933FCF0083AC69 /* tomcrypt_math.h in Headers */, - 22C918D311933FCF0083AC69 /* tomcrypt_misc.h in Headers */, - 22C918D411933FCF0083AC69 /* tomcrypt_pk.h in Headers */, - 22C918D511933FCF0083AC69 /* tomcrypt_pkcs.h in Headers */, - 22C918D611933FCF0083AC69 /* tomcrypt_prng.h in Headers */, - 22C91A791193400A0083AC69 /* tommath_class.h in Headers */, - 22C91A7A1193400A0083AC69 /* tommath_superclass.h in Headers */, - 22C91A7B1193400A0083AC69 /* tommath.h in Headers */, - 225C734D1257CCC70009E8DA /* lookup.h in Headers */, - 22EC6045154B28A000679228 /* FileStream.h in Headers */, - ); - runOnlyForDeploymentPostprocessing = 0; - }; -/* End PBXHeadersBuildPhase section */ - -/* Begin PBXNativeTarget section */ - 225530D31056BAC800FA646A /* StormLib */ = { - isa = PBXNativeTarget; - buildConfigurationList = 225530D71056BB1600FA646A /* Build configuration list for PBXNativeTarget "StormLib" */; - buildPhases = ( - 225530D01056BAC800FA646A /* Headers */, - 225530D11056BAC800FA646A /* Sources */, - 225530D21056BAC800FA646A /* Frameworks */, - ); - buildRules = ( - ); - dependencies = ( - ); - name = StormLib; - productName = StormLib; - productReference = 225530D41056BAC800FA646A /* libStormLib.a */; - productType = "com.apple.product-type.library.static"; - }; - 225FAC930E53B7F800DA2CAE /* StormLibFramework */ = { - isa = PBXNativeTarget; - buildConfigurationList = 225FAC980E53B7F900DA2CAE /* Build configuration list for PBXNativeTarget "StormLibFramework" */; - buildPhases = ( - 225FAC8F0E53B7F800DA2CAE /* Headers */, - 225FAC900E53B7F800DA2CAE /* Resources */, - 225FAC910E53B7F800DA2CAE /* Sources */, - 225FAC920E53B7F800DA2CAE /* Frameworks */, - ); - buildRules = ( - ); - dependencies = ( - ); - name = StormLibFramework; - productName = StormLib; - productReference = 225FAC940E53B7F800DA2CAE /* StormLib.framework */; - productType = "com.apple.product-type.framework"; - }; - 22954ACD11D463A30064B264 /* StormLib_Test */ = { - isa = PBXNativeTarget; - buildConfigurationList = 22954AD911D463E00064B264 /* Build configuration list for PBXNativeTarget "StormLib_Test" */; - buildPhases = ( - 22954ACB11D463A30064B264 /* Sources */, - 22954ACC11D463A30064B264 /* Frameworks */, - ); - buildRules = ( - ); - dependencies = ( - 2229F62F11D4653600118914 /* PBXTargetDependency */, - ); - name = StormLib_Test; - productName = StormLib_Test; - productReference = 22954ACE11D463A30064B264 /* StormLib_Test */; - productType = "com.apple.product-type.tool"; - }; -/* End PBXNativeTarget section */ - -/* Begin PBXProject section */ - 0867D690FE84028FC02AAC07 /* Project object */ = { - isa = PBXProject; - attributes = { - LastUpgradeCheck = 0500; - }; - buildConfigurationList = 1DEB916408733D950010E9CD /* Build configuration list for PBXProject "StormLib" */; - compatibilityVersion = "Xcode 3.2"; - developmentRegion = English; - hasScannedForEncodings = 1; - knownRegions = ( - en, - ); - mainGroup = 0867D691FE84028FC02AAC07 /* stormlib */; - productRefGroup = 034768DDFF38A45A11DB9C8B /* Products */; - projectDirPath = ""; - projectRoot = ""; - targets = ( - 225530D31056BAC800FA646A /* StormLib */, - 225FAC930E53B7F800DA2CAE /* StormLibFramework */, - 22954ACD11D463A30064B264 /* StormLib_Test */, - ); - }; -/* End PBXProject section */ - -/* Begin PBXResourcesBuildPhase section */ - 225FAC900E53B7F800DA2CAE /* Resources */ = { - isa = PBXResourcesBuildPhase; - buildActionMask = 2147483647; - files = ( - ); - runOnlyForDeploymentPostprocessing = 0; - }; -/* End PBXResourcesBuildPhase section */ - -/* Begin PBXSourcesBuildPhase section */ - 225530D11056BAC800FA646A /* Sources */ = { - isa = PBXSourcesBuildPhase; - buildActionMask = 2147483647; - files = ( - 225530E31056BC8700FA646A /* huff.cpp in Sources */, - 225530E61056BC8700FA646A /* explode.c in Sources */, - 226C7CA71857DE9400AB689C /* SBaseDumpData.cpp in Sources */, - 225530E71056BC8700FA646A /* implode.c in Sources */, - 225530E81056BC8700FA646A /* SFileAttributes.cpp in Sources */, - 226C7CAA1857DEAC00AB689C /* SBaseSubTypes.cpp in Sources */, - 225530E91056BC8700FA646A /* SBaseCommon.cpp in Sources */, - 225530EA1056BC8700FA646A /* SCompression.cpp in Sources */, - 225530EB1056BC8700FA646A /* SFileCompactArchive.cpp in Sources */, - 225530EC1056BC8700FA646A /* SFileCreateArchive.cpp in Sources */, - 225530ED1056BC8700FA646A /* SFileExtractFile.cpp in Sources */, - E60816F81B707B7200B283F7 /* der_encode_octet_string.c in Sources */, - 225530EE1056BC8700FA646A /* SFileFindFile.cpp in Sources */, - 225530EF1056BC8700FA646A /* SFileOpenArchive.cpp in Sources */, - 226C7CAD1857DEEB00AB689C /* SFileGetFileInfo.cpp in Sources */, - 225530F01056BC8700FA646A /* SFileOpenFileEx.cpp in Sources */, - 225530F11056BC8700FA646A /* SFileReadFile.cpp in Sources */, - 225530F21056BC8700FA646A /* SFileListFile.cpp in Sources */, - 2299D9D91167EFA8005C19BF /* adpcm.cpp in Sources */, - 2299D9E01167EFC6005C19BF /* sparse.cpp in Sources */, - 2299DA4F1167FD16005C19BF /* SFileAddFile.cpp in Sources */, - 221F6A7C116852AA0026C852 /* LzmaEnc.c in Sources */, - 221F6A7F116852B20026C852 /* LzmaDec.c in Sources */, - 221F6AB71168545B0026C852 /* LzFind.c in Sources */, - 22C9187D11933FCF0083AC69 /* hash_memory.c in Sources */, - 22C9187E11933FCF0083AC69 /* md5.c in Sources */, - 22C9187F11933FCF0083AC69 /* sha1.c in Sources */, - 22C9188D11933FCF0083AC69 /* ltm_desc.c in Sources */, - 22C9188E11933FCF0083AC69 /* multi.c in Sources */, - 22C9188F11933FCF0083AC69 /* rand_prime.c in Sources */, - 22C9189011933FCF0083AC69 /* base64_decode.c in Sources */, - 22C9189111933FCF0083AC69 /* crypt_argchk.c in Sources */, - 22C9189211933FCF0083AC69 /* crypt_find_hash.c in Sources */, - 22C9189311933FCF0083AC69 /* crypt_find_prng.c in Sources */, - 22C9189411933FCF0083AC69 /* crypt_hash_descriptor.c in Sources */, - 22C9189511933FCF0083AC69 /* crypt_hash_is_valid.c in Sources */, - 22C9189611933FCF0083AC69 /* crypt_libc.c in Sources */, - 2254917B11948CE70044424D /* crypt_ltc_mp_descriptor.c in Sources */, - 22C9189811933FCF0083AC69 /* crypt_prng_descriptor.c in Sources */, - 22C9189911933FCF0083AC69 /* crypt_prng_is_valid.c in Sources */, - 22C9189A11933FCF0083AC69 /* crypt_register_hash.c in Sources */, - 22C9189B11933FCF0083AC69 /* crypt_register_prng.c in Sources */, - 22C9189C11933FCF0083AC69 /* zeromem.c in Sources */, - 22C9189D11933FCF0083AC69 /* der_decode_bit_string.c in Sources */, - 22C9189E11933FCF0083AC69 /* der_decode_boolean.c in Sources */, - 22C9189F11933FCF0083AC69 /* der_decode_choice.c in Sources */, - 22C918A011933FCF0083AC69 /* der_decode_ia5_string.c in Sources */, - 22C918A111933FCF0083AC69 /* der_decode_integer.c in Sources */, - 22C918A211933FCF0083AC69 /* der_decode_object_identifier.c in Sources */, - 22C918A311933FCF0083AC69 /* der_decode_octet_string.c in Sources */, - 22C918A411933FCF0083AC69 /* der_decode_printable_string.c in Sources */, - 22C918A511933FCF0083AC69 /* der_decode_sequence_ex.c in Sources */, - 22C918A611933FCF0083AC69 /* der_decode_sequence_flexi.c in Sources */, - 22C918A711933FCF0083AC69 /* der_decode_sequence_multi.c in Sources */, - 22C918A811933FCF0083AC69 /* der_decode_short_integer.c in Sources */, - 22C918A911933FCF0083AC69 /* der_decode_utctime.c in Sources */, - 22C918AA11933FCF0083AC69 /* der_decode_utf8_string.c in Sources */, - E60816F01B707B7200B283F7 /* der_encode_boolean.c in Sources */, - 22C918AB11933FCF0083AC69 /* der_length_bit_string.c in Sources */, - 22C918AC11933FCF0083AC69 /* der_length_boolean.c in Sources */, - 22C918AD11933FCF0083AC69 /* der_length_ia5_string.c in Sources */, - 22C918AE11933FCF0083AC69 /* der_length_integer.c in Sources */, - 22C918AF11933FCF0083AC69 /* der_length_object_identifier.c in Sources */, - 22C918B011933FCF0083AC69 /* der_length_octet_string.c in Sources */, - 22C918B111933FCF0083AC69 /* der_length_printable_string.c in Sources */, - 22C918B211933FCF0083AC69 /* der_length_sequence.c in Sources */, - 22C918B311933FCF0083AC69 /* der_length_short_integer.c in Sources */, - 22C918B411933FCF0083AC69 /* der_length_utctime.c in Sources */, - 22C918B511933FCF0083AC69 /* der_length_utf8_string.c in Sources */, - 22C918B611933FCF0083AC69 /* der_sequence_free.c in Sources */, - 22C918B711933FCF0083AC69 /* ltc_ecc_map.c in Sources */, - 22C918B811933FCF0083AC69 /* ltc_ecc_mul2add.c in Sources */, - 22C918B911933FCF0083AC69 /* ltc_ecc_mulmod.c in Sources */, - 22C918BA11933FCF0083AC69 /* ltc_ecc_points.c in Sources */, - 22C918BB11933FCF0083AC69 /* ltc_ecc_projective_add_point.c in Sources */, - 22C918BC11933FCF0083AC69 /* ltc_ecc_projective_dbl_point.c in Sources */, - 22C918BD11933FCF0083AC69 /* pkcs_1_mgf1.c in Sources */, - 22C918BE11933FCF0083AC69 /* pkcs_1_oaep_decode.c in Sources */, - 22C918BF11933FCF0083AC69 /* pkcs_1_pss_decode.c in Sources */, - 22C918C011933FCF0083AC69 /* pkcs_1_v1_5_decode.c in Sources */, - 22C918C111933FCF0083AC69 /* rsa_exptmod.c in Sources */, - 22C918C211933FCF0083AC69 /* rsa_free.c in Sources */, - 22C918C311933FCF0083AC69 /* rsa_import.c in Sources */, - 22C918C411933FCF0083AC69 /* rsa_make_key.c in Sources */, - 22C918C511933FCF0083AC69 /* rsa_verify_hash.c in Sources */, - 22C918C611933FCF0083AC69 /* rsa_verify_simple.c in Sources */, - 22C9198A1193400A0083AC69 /* bn_fast_mp_invmod.c in Sources */, - 22C9198B1193400A0083AC69 /* bn_fast_mp_montgomery_reduce.c in Sources */, - E60816F61B707B7200B283F7 /* der_encode_object_identifier.c in Sources */, - 22C9198C1193400A0083AC69 /* bn_fast_s_mp_mul_digs.c in Sources */, - E60816FA1B707B7200B283F7 /* der_encode_printable_string.c in Sources */, - 22C9198D1193400A0083AC69 /* bn_fast_s_mp_mul_high_digs.c in Sources */, - 22C9198E1193400A0083AC69 /* bn_fast_s_mp_sqr.c in Sources */, - 22C9198F1193400A0083AC69 /* bn_mp_2expt.c in Sources */, - 22C919901193400A0083AC69 /* bn_mp_abs.c in Sources */, - 22C919911193400A0083AC69 /* bn_mp_add_d.c in Sources */, - 22C919921193400A0083AC69 /* bn_mp_add.c in Sources */, - 22C919931193400A0083AC69 /* bn_mp_addmod.c in Sources */, - 22C919941193400A0083AC69 /* bn_mp_and.c in Sources */, - 22C919951193400A0083AC69 /* bn_mp_clamp.c in Sources */, - 22C919961193400A0083AC69 /* bn_mp_clear_multi.c in Sources */, - 22C919971193400A0083AC69 /* bn_mp_clear.c in Sources */, - 22C919981193400A0083AC69 /* bn_mp_cmp_d.c in Sources */, - 22C919991193400A0083AC69 /* bn_mp_cmp_mag.c in Sources */, - 22C9199A1193400A0083AC69 /* bn_mp_cmp.c in Sources */, - 22C9199B1193400A0083AC69 /* bn_mp_cnt_lsb.c in Sources */, - 22C9199C1193400A0083AC69 /* bn_mp_copy.c in Sources */, - 22C9199D1193400A0083AC69 /* bn_mp_count_bits.c in Sources */, - E60816F41B707B7200B283F7 /* der_encode_integer.c in Sources */, - E60817061B707B7200B283F7 /* der_encode_utf8_string.c in Sources */, - 22C9199E1193400A0083AC69 /* bn_mp_div_2.c in Sources */, - 22C9199F1193400A0083AC69 /* bn_mp_div_2d.c in Sources */, - 22C919A01193400A0083AC69 /* bn_mp_div_3.c in Sources */, - 22C919A11193400A0083AC69 /* bn_mp_div_d.c in Sources */, - 22C919A21193400A0083AC69 /* bn_mp_div.c in Sources */, - 22C919A31193400A0083AC69 /* bn_mp_dr_is_modulus.c in Sources */, - 22C919A41193400A0083AC69 /* bn_mp_dr_reduce.c in Sources */, - 22C919A51193400A0083AC69 /* bn_mp_dr_setup.c in Sources */, - 22C919A61193400A0083AC69 /* bn_mp_exch.c in Sources */, - 22C919A71193400A0083AC69 /* bn_mp_expt_d.c in Sources */, - 22C919A81193400A0083AC69 /* bn_mp_exptmod_fast.c in Sources */, - 22C919A91193400A0083AC69 /* bn_mp_exptmod.c in Sources */, - 22C919AA1193400A0083AC69 /* bn_mp_exteuclid.c in Sources */, - 22C919AB1193400A0083AC69 /* bn_mp_fread.c in Sources */, - 22C919AC1193400A0083AC69 /* bn_mp_fwrite.c in Sources */, - 22C919AD1193400A0083AC69 /* bn_mp_gcd.c in Sources */, - 22C919AE1193400A0083AC69 /* bn_mp_get_int.c in Sources */, - 22C919AF1193400A0083AC69 /* bn_mp_grow.c in Sources */, - 22C919B01193400A0083AC69 /* bn_mp_init_copy.c in Sources */, - 22C919B11193400A0083AC69 /* bn_mp_init_multi.c in Sources */, - 22C919B21193400A0083AC69 /* bn_mp_init_set_int.c in Sources */, - 22C919B31193400A0083AC69 /* bn_mp_init_set.c in Sources */, - 22C919B41193400A0083AC69 /* bn_mp_init_size.c in Sources */, - 22C919B51193400A0083AC69 /* bn_mp_init.c in Sources */, - E60816D91B707B1800B283F7 /* pkcs_1_pss_encode.c in Sources */, - 22C919B61193400A0083AC69 /* bn_mp_invmod_slow.c in Sources */, - 22C919B71193400A0083AC69 /* bn_mp_invmod.c in Sources */, - 22C919B81193400A0083AC69 /* bn_mp_is_square.c in Sources */, - 22C919B91193400A0083AC69 /* bn_mp_jacobi.c in Sources */, - 22C919BA1193400A0083AC69 /* bn_mp_karatsuba_mul.c in Sources */, - 22C919BB1193400A0083AC69 /* bn_mp_karatsuba_sqr.c in Sources */, - 22C919BC1193400A0083AC69 /* bn_mp_lcm.c in Sources */, - 22C919BD1193400A0083AC69 /* bn_mp_lshd.c in Sources */, - 22C919BE1193400A0083AC69 /* bn_mp_mod_2d.c in Sources */, - 22C919BF1193400A0083AC69 /* bn_mp_mod_d.c in Sources */, - 22C919C01193400A0083AC69 /* bn_mp_mod.c in Sources */, - 22C919C11193400A0083AC69 /* bn_mp_montgomery_calc_normalization.c in Sources */, - 22C919C21193400A0083AC69 /* bn_mp_montgomery_reduce.c in Sources */, - E60817021B707B7200B283F7 /* der_encode_short_integer.c in Sources */, - 22C919C31193400A0083AC69 /* bn_mp_montgomery_setup.c in Sources */, - E60816DC1B707B2700B283F7 /* pkcs_1_v1_5_encode.c in Sources */, - 22C919C41193400A0083AC69 /* bn_mp_mul_2.c in Sources */, - E60816FC1B707B7200B283F7 /* der_encode_sequence_multi.c in Sources */, - 22C919C51193400A0083AC69 /* bn_mp_mul_2d.c in Sources */, - 22C919C61193400A0083AC69 /* bn_mp_mul_d.c in Sources */, - 22C919C71193400A0083AC69 /* bn_mp_mul.c in Sources */, - E60816EE1B707B7200B283F7 /* der_encode_bit_string.c in Sources */, - 22C919C81193400A0083AC69 /* bn_mp_mulmod.c in Sources */, - 22C919C91193400A0083AC69 /* bn_mp_n_root.c in Sources */, - 22C919CA1193400A0083AC69 /* bn_mp_neg.c in Sources */, - 22C919CB1193400A0083AC69 /* bn_mp_or.c in Sources */, - 22C919CC1193400A0083AC69 /* bn_mp_prime_fermat.c in Sources */, - 22C919CD1193400A0083AC69 /* bn_mp_prime_is_divisible.c in Sources */, - 22C919CE1193400A0083AC69 /* bn_mp_prime_is_prime.c in Sources */, - E60816D61B707A9000B283F7 /* rsa_sign_hash.c in Sources */, - 22C919CF1193400A0083AC69 /* bn_mp_prime_miller_rabin.c in Sources */, - 22C919D01193400A0083AC69 /* bn_mp_prime_next_prime.c in Sources */, - 22C919D11193400A0083AC69 /* bn_mp_prime_rabin_miller_trials.c in Sources */, - 22C919D21193400A0083AC69 /* bn_mp_prime_random_ex.c in Sources */, - 22C919D31193400A0083AC69 /* bn_mp_radix_size.c in Sources */, - 22C919D41193400A0083AC69 /* bn_mp_radix_smap.c in Sources */, - 22C919D51193400A0083AC69 /* bn_mp_rand.c in Sources */, - 22C919D61193400A0083AC69 /* bn_mp_read_radix.c in Sources */, - 22C919D71193400A0083AC69 /* bn_mp_read_signed_bin.c in Sources */, - 22C919D81193400A0083AC69 /* bn_mp_read_unsigned_bin.c in Sources */, - 22C919D91193400A0083AC69 /* bn_mp_reduce_2k_l.c in Sources */, - 22C919DA1193400A0083AC69 /* bn_mp_reduce_2k_setup_l.c in Sources */, - 22C919DB1193400A0083AC69 /* bn_mp_reduce_2k_setup.c in Sources */, - E60816FE1B707B7200B283F7 /* der_encode_set.c in Sources */, - E60817001B707B7200B283F7 /* der_encode_setof.c in Sources */, - 22C919DC1193400A0083AC69 /* bn_mp_reduce_2k.c in Sources */, - 22C919DD1193400A0083AC69 /* bn_mp_reduce_is_2k_l.c in Sources */, - E60817041B707B7200B283F7 /* der_encode_utctime.c in Sources */, - 22C919DE1193400A0083AC69 /* bn_mp_reduce_is_2k.c in Sources */, - 22C919DF1193400A0083AC69 /* bn_mp_reduce_setup.c in Sources */, - 22C919E01193400A0083AC69 /* bn_mp_reduce.c in Sources */, - 22C919E11193400A0083AC69 /* bn_mp_rshd.c in Sources */, - 22C919E21193400A0083AC69 /* bn_mp_set_int.c in Sources */, - 22C919E31193400A0083AC69 /* bn_mp_set.c in Sources */, - 22C919E41193400A0083AC69 /* bn_mp_shrink.c in Sources */, - 22C919E51193400A0083AC69 /* bn_mp_signed_bin_size.c in Sources */, - 22C919E61193400A0083AC69 /* bn_mp_sqr.c in Sources */, - 22C919E71193400A0083AC69 /* bn_mp_sqrmod.c in Sources */, - 22C919E81193400A0083AC69 /* bn_mp_sqrt.c in Sources */, - 22C919E91193400A0083AC69 /* bn_mp_sub_d.c in Sources */, - 22C919EA1193400A0083AC69 /* bn_mp_sub.c in Sources */, - 22C919EB1193400A0083AC69 /* bn_mp_submod.c in Sources */, - 22C919EC1193400A0083AC69 /* bn_mp_to_signed_bin_n.c in Sources */, - 22C919ED1193400A0083AC69 /* bn_mp_to_signed_bin.c in Sources */, - 22C919EE1193400A0083AC69 /* bn_mp_to_unsigned_bin_n.c in Sources */, - 22C919EF1193400A0083AC69 /* bn_mp_to_unsigned_bin.c in Sources */, - 22C919F01193400A0083AC69 /* bn_mp_toom_mul.c in Sources */, - 22C919F11193400A0083AC69 /* bn_mp_toom_sqr.c in Sources */, - 22C919F21193400A0083AC69 /* bn_mp_toradix_n.c in Sources */, - 22C919F31193400A0083AC69 /* bn_mp_toradix.c in Sources */, - 22C919F41193400A0083AC69 /* bn_mp_unsigned_bin_size.c in Sources */, - E60816F21B707B7200B283F7 /* der_encode_ia5_string.c in Sources */, - E60816DF1B707B5700B283F7 /* der_encode_sequence_ex.c in Sources */, - 22C919F51193400A0083AC69 /* bn_mp_xor.c in Sources */, - 22C919F61193400A0083AC69 /* bn_mp_zero.c in Sources */, - 22C919F71193400A0083AC69 /* bn_prime_tab.c in Sources */, - 22C919F81193400A0083AC69 /* bn_reverse.c in Sources */, - 22C919F91193400A0083AC69 /* bn_s_mp_add.c in Sources */, - 22C919FA1193400A0083AC69 /* bn_s_mp_exptmod.c in Sources */, - 22C919FB1193400A0083AC69 /* bn_s_mp_mul_digs.c in Sources */, - 22C919FC1193400A0083AC69 /* bn_s_mp_mul_high_digs.c in Sources */, - 22C919FD1193400A0083AC69 /* bn_s_mp_sqr.c in Sources */, - 22C919FE1193400A0083AC69 /* bn_s_mp_sub.c in Sources */, - 22C919FF1193400A0083AC69 /* bncore.c in Sources */, - 22F5A9C51193DFBA00F8B121 /* SFileVerify.cpp in Sources */, - 228B538511BF7D0D001A58DA /* FileStream.cpp in Sources */, - 22AEA123123125D800359B16 /* SFilePatchArchives.cpp in Sources */, - 225C73501257CCC70009E8DA /* lookup3.c in Sources */, - 225C73551257CD0C0009E8DA /* SBaseFileTable.cpp in Sources */, - ); - runOnlyForDeploymentPostprocessing = 0; - }; - 225FAC910E53B7F800DA2CAE /* Sources */ = { - isa = PBXSourcesBuildPhase; - buildActionMask = 2147483647; - files = ( - 225FACA50E53BAB400DA2CAE /* huff.cpp in Sources */, - 225FACA90E53BAB400DA2CAE /* explode.c in Sources */, - 226C7CA81857DE9400AB689C /* SBaseDumpData.cpp in Sources */, - 225FACAA0E53BAB400DA2CAE /* implode.c in Sources */, - 225FACAB0E53BAB400DA2CAE /* SFileAttributes.cpp in Sources */, - 226C7CAB1857DEAC00AB689C /* SBaseSubTypes.cpp in Sources */, - 225FACAC0E53BAB400DA2CAE /* SBaseCommon.cpp in Sources */, - 225FACAD0E53BAB400DA2CAE /* SCompression.cpp in Sources */, - 225FACAE0E53BAB400DA2CAE /* SFileCompactArchive.cpp in Sources */, - 225FACAF0E53BAB400DA2CAE /* SFileCreateArchive.cpp in Sources */, - 225FACB00E53BAB400DA2CAE /* SFileExtractFile.cpp in Sources */, - E60816F91B707B7200B283F7 /* der_encode_octet_string.c in Sources */, - 225FACB10E53BAB400DA2CAE /* SFileFindFile.cpp in Sources */, - 225FACB20E53BAB400DA2CAE /* SFileOpenArchive.cpp in Sources */, - 226C7CAE1857DEEB00AB689C /* SFileGetFileInfo.cpp in Sources */, - 225FACB30E53BAB400DA2CAE /* SFileOpenFileEx.cpp in Sources */, - 225FACB40E53BAB400DA2CAE /* SFileReadFile.cpp in Sources */, - 225FACB50E53BAB400DA2CAE /* SFileListFile.cpp in Sources */, - 2299D9D71167EFA8005C19BF /* adpcm.cpp in Sources */, - 2299D9DE1167EFC6005C19BF /* sparse.cpp in Sources */, - 2299DA4E1167FD16005C19BF /* SFileAddFile.cpp in Sources */, - 221F6A7B116852AA0026C852 /* LzmaEnc.c in Sources */, - 221F6A7E116852B20026C852 /* LzmaDec.c in Sources */, - 221F6AB51168545B0026C852 /* LzFind.c in Sources */, - 22C918C711933FCF0083AC69 /* hash_memory.c in Sources */, - 22C918C811933FCF0083AC69 /* md5.c in Sources */, - 22C918C911933FCF0083AC69 /* sha1.c in Sources */, - 22C918D711933FCF0083AC69 /* ltm_desc.c in Sources */, - 22C918D811933FCF0083AC69 /* multi.c in Sources */, - 22C918D911933FCF0083AC69 /* rand_prime.c in Sources */, - 22C918DA11933FCF0083AC69 /* base64_decode.c in Sources */, - 22C918DB11933FCF0083AC69 /* crypt_argchk.c in Sources */, - 22C918DC11933FCF0083AC69 /* crypt_find_hash.c in Sources */, - 22C918DD11933FCF0083AC69 /* crypt_find_prng.c in Sources */, - 22C918DE11933FCF0083AC69 /* crypt_hash_descriptor.c in Sources */, - 22C918DF11933FCF0083AC69 /* crypt_hash_is_valid.c in Sources */, - 22C918E011933FCF0083AC69 /* crypt_libc.c in Sources */, - 22C918E111933FCF0083AC69 /* crypt_ltc_mp_descriptor.c in Sources */, - 22C918E211933FCF0083AC69 /* crypt_prng_descriptor.c in Sources */, - 22C918E311933FCF0083AC69 /* crypt_prng_is_valid.c in Sources */, - 22C918E411933FCF0083AC69 /* crypt_register_hash.c in Sources */, - 22C918E511933FCF0083AC69 /* crypt_register_prng.c in Sources */, - 22C918E611933FCF0083AC69 /* zeromem.c in Sources */, - 22C918E711933FCF0083AC69 /* der_decode_bit_string.c in Sources */, - 22C918E811933FCF0083AC69 /* der_decode_boolean.c in Sources */, - 22C918E911933FCF0083AC69 /* der_decode_choice.c in Sources */, - 22C918EA11933FCF0083AC69 /* der_decode_ia5_string.c in Sources */, - 22C918EB11933FCF0083AC69 /* der_decode_integer.c in Sources */, - 22C918EC11933FCF0083AC69 /* der_decode_object_identifier.c in Sources */, - 22C918ED11933FCF0083AC69 /* der_decode_octet_string.c in Sources */, - 22C918EE11933FCF0083AC69 /* der_decode_printable_string.c in Sources */, - 22C918EF11933FCF0083AC69 /* der_decode_sequence_ex.c in Sources */, - 22C918F011933FCF0083AC69 /* der_decode_sequence_flexi.c in Sources */, - 22C918F111933FCF0083AC69 /* der_decode_sequence_multi.c in Sources */, - 22C918F211933FCF0083AC69 /* der_decode_short_integer.c in Sources */, - 22C918F311933FCF0083AC69 /* der_decode_utctime.c in Sources */, - 22C918F411933FCF0083AC69 /* der_decode_utf8_string.c in Sources */, - E60816F11B707B7200B283F7 /* der_encode_boolean.c in Sources */, - 22C918F511933FCF0083AC69 /* der_length_bit_string.c in Sources */, - 22C918F611933FCF0083AC69 /* der_length_boolean.c in Sources */, - 22C918F711933FCF0083AC69 /* der_length_ia5_string.c in Sources */, - 22C918F811933FCF0083AC69 /* der_length_integer.c in Sources */, - 22C918F911933FCF0083AC69 /* der_length_object_identifier.c in Sources */, - 22C918FA11933FCF0083AC69 /* der_length_octet_string.c in Sources */, - 22C918FB11933FCF0083AC69 /* der_length_printable_string.c in Sources */, - 22C918FC11933FCF0083AC69 /* der_length_sequence.c in Sources */, - 22C918FD11933FCF0083AC69 /* der_length_short_integer.c in Sources */, - 22C918FE11933FCF0083AC69 /* der_length_utctime.c in Sources */, - 22C918FF11933FCF0083AC69 /* der_length_utf8_string.c in Sources */, - 22C9190011933FCF0083AC69 /* der_sequence_free.c in Sources */, - 22C9190111933FCF0083AC69 /* ltc_ecc_map.c in Sources */, - 22C9190211933FCF0083AC69 /* ltc_ecc_mul2add.c in Sources */, - 22C9190311933FCF0083AC69 /* ltc_ecc_mulmod.c in Sources */, - 22C9190411933FCF0083AC69 /* ltc_ecc_points.c in Sources */, - 22C9190511933FCF0083AC69 /* ltc_ecc_projective_add_point.c in Sources */, - 22C9190611933FCF0083AC69 /* ltc_ecc_projective_dbl_point.c in Sources */, - 22C9190711933FCF0083AC69 /* pkcs_1_mgf1.c in Sources */, - 22C9190811933FCF0083AC69 /* pkcs_1_oaep_decode.c in Sources */, - 22C9190911933FCF0083AC69 /* pkcs_1_pss_decode.c in Sources */, - 22C9190A11933FCF0083AC69 /* pkcs_1_v1_5_decode.c in Sources */, - 22C9190B11933FCF0083AC69 /* rsa_exptmod.c in Sources */, - 22C9190C11933FCF0083AC69 /* rsa_free.c in Sources */, - 22C9190D11933FCF0083AC69 /* rsa_import.c in Sources */, - 22C9190E11933FCF0083AC69 /* rsa_make_key.c in Sources */, - 22C9190F11933FCF0083AC69 /* rsa_verify_hash.c in Sources */, - 22C9191011933FCF0083AC69 /* rsa_verify_simple.c in Sources */, - 22C91A031193400A0083AC69 /* bn_fast_mp_invmod.c in Sources */, - 22C91A041193400A0083AC69 /* bn_fast_mp_montgomery_reduce.c in Sources */, - E60816F71B707B7200B283F7 /* der_encode_object_identifier.c in Sources */, - 22C91A051193400A0083AC69 /* bn_fast_s_mp_mul_digs.c in Sources */, - E60816FB1B707B7200B283F7 /* der_encode_printable_string.c in Sources */, - 22C91A061193400A0083AC69 /* bn_fast_s_mp_mul_high_digs.c in Sources */, - 22C91A071193400A0083AC69 /* bn_fast_s_mp_sqr.c in Sources */, - 22C91A081193400A0083AC69 /* bn_mp_2expt.c in Sources */, - 22C91A091193400A0083AC69 /* bn_mp_abs.c in Sources */, - 22C91A0A1193400A0083AC69 /* bn_mp_add_d.c in Sources */, - 22C91A0B1193400A0083AC69 /* bn_mp_add.c in Sources */, - 22C91A0C1193400A0083AC69 /* bn_mp_addmod.c in Sources */, - 22C91A0D1193400A0083AC69 /* bn_mp_and.c in Sources */, - 22C91A0E1193400A0083AC69 /* bn_mp_clamp.c in Sources */, - 22C91A0F1193400A0083AC69 /* bn_mp_clear_multi.c in Sources */, - 22C91A101193400A0083AC69 /* bn_mp_clear.c in Sources */, - 22C91A111193400A0083AC69 /* bn_mp_cmp_d.c in Sources */, - 22C91A121193400A0083AC69 /* bn_mp_cmp_mag.c in Sources */, - 22C91A131193400A0083AC69 /* bn_mp_cmp.c in Sources */, - 22C91A141193400A0083AC69 /* bn_mp_cnt_lsb.c in Sources */, - 22C91A151193400A0083AC69 /* bn_mp_copy.c in Sources */, - 22C91A161193400A0083AC69 /* bn_mp_count_bits.c in Sources */, - E60816F51B707B7200B283F7 /* der_encode_integer.c in Sources */, - E60817071B707B7200B283F7 /* der_encode_utf8_string.c in Sources */, - 22C91A171193400A0083AC69 /* bn_mp_div_2.c in Sources */, - 22C91A181193400A0083AC69 /* bn_mp_div_2d.c in Sources */, - 22C91A191193400A0083AC69 /* bn_mp_div_3.c in Sources */, - 22C91A1A1193400A0083AC69 /* bn_mp_div_d.c in Sources */, - 22C91A1B1193400A0083AC69 /* bn_mp_div.c in Sources */, - 22C91A1C1193400A0083AC69 /* bn_mp_dr_is_modulus.c in Sources */, - 22C91A1D1193400A0083AC69 /* bn_mp_dr_reduce.c in Sources */, - 22C91A1E1193400A0083AC69 /* bn_mp_dr_setup.c in Sources */, - 22C91A1F1193400A0083AC69 /* bn_mp_exch.c in Sources */, - 22C91A201193400A0083AC69 /* bn_mp_expt_d.c in Sources */, - 22C91A211193400A0083AC69 /* bn_mp_exptmod_fast.c in Sources */, - 22C91A221193400A0083AC69 /* bn_mp_exptmod.c in Sources */, - 22C91A231193400A0083AC69 /* bn_mp_exteuclid.c in Sources */, - 22C91A241193400A0083AC69 /* bn_mp_fread.c in Sources */, - 22C91A251193400A0083AC69 /* bn_mp_fwrite.c in Sources */, - 22C91A261193400A0083AC69 /* bn_mp_gcd.c in Sources */, - 22C91A271193400A0083AC69 /* bn_mp_get_int.c in Sources */, - 22C91A281193400A0083AC69 /* bn_mp_grow.c in Sources */, - 22C91A291193400A0083AC69 /* bn_mp_init_copy.c in Sources */, - 22C91A2A1193400A0083AC69 /* bn_mp_init_multi.c in Sources */, - 22C91A2B1193400A0083AC69 /* bn_mp_init_set_int.c in Sources */, - 22C91A2C1193400A0083AC69 /* bn_mp_init_set.c in Sources */, - 22C91A2D1193400A0083AC69 /* bn_mp_init_size.c in Sources */, - 22C91A2E1193400A0083AC69 /* bn_mp_init.c in Sources */, - E60816DA1B707B1800B283F7 /* pkcs_1_pss_encode.c in Sources */, - 22C91A2F1193400A0083AC69 /* bn_mp_invmod_slow.c in Sources */, - 22C91A301193400A0083AC69 /* bn_mp_invmod.c in Sources */, - 22C91A311193400A0083AC69 /* bn_mp_is_square.c in Sources */, - 22C91A321193400A0083AC69 /* bn_mp_jacobi.c in Sources */, - 22C91A331193400A0083AC69 /* bn_mp_karatsuba_mul.c in Sources */, - 22C91A341193400A0083AC69 /* bn_mp_karatsuba_sqr.c in Sources */, - 22C91A351193400A0083AC69 /* bn_mp_lcm.c in Sources */, - 22C91A361193400A0083AC69 /* bn_mp_lshd.c in Sources */, - 22C91A371193400A0083AC69 /* bn_mp_mod_2d.c in Sources */, - 22C91A381193400A0083AC69 /* bn_mp_mod_d.c in Sources */, - 22C91A391193400A0083AC69 /* bn_mp_mod.c in Sources */, - 22C91A3A1193400A0083AC69 /* bn_mp_montgomery_calc_normalization.c in Sources */, - 22C91A3B1193400A0083AC69 /* bn_mp_montgomery_reduce.c in Sources */, - E60817031B707B7200B283F7 /* der_encode_short_integer.c in Sources */, - 22C91A3C1193400A0083AC69 /* bn_mp_montgomery_setup.c in Sources */, - E60816DD1B707B2700B283F7 /* pkcs_1_v1_5_encode.c in Sources */, - 22C91A3D1193400A0083AC69 /* bn_mp_mul_2.c in Sources */, - E60816FD1B707B7200B283F7 /* der_encode_sequence_multi.c in Sources */, - 22C91A3E1193400A0083AC69 /* bn_mp_mul_2d.c in Sources */, - 22C91A3F1193400A0083AC69 /* bn_mp_mul_d.c in Sources */, - 22C91A401193400A0083AC69 /* bn_mp_mul.c in Sources */, - E60816EF1B707B7200B283F7 /* der_encode_bit_string.c in Sources */, - 22C91A411193400A0083AC69 /* bn_mp_mulmod.c in Sources */, - 22C91A421193400A0083AC69 /* bn_mp_n_root.c in Sources */, - 22C91A431193400A0083AC69 /* bn_mp_neg.c in Sources */, - 22C91A441193400A0083AC69 /* bn_mp_or.c in Sources */, - 22C91A451193400A0083AC69 /* bn_mp_prime_fermat.c in Sources */, - 22C91A461193400A0083AC69 /* bn_mp_prime_is_divisible.c in Sources */, - 22C91A471193400A0083AC69 /* bn_mp_prime_is_prime.c in Sources */, - E60816D71B707A9B00B283F7 /* rsa_sign_hash.c in Sources */, - 22C91A481193400A0083AC69 /* bn_mp_prime_miller_rabin.c in Sources */, - 22C91A491193400A0083AC69 /* bn_mp_prime_next_prime.c in Sources */, - 22C91A4A1193400A0083AC69 /* bn_mp_prime_rabin_miller_trials.c in Sources */, - 22C91A4B1193400A0083AC69 /* bn_mp_prime_random_ex.c in Sources */, - 22C91A4C1193400A0083AC69 /* bn_mp_radix_size.c in Sources */, - 22C91A4D1193400A0083AC69 /* bn_mp_radix_smap.c in Sources */, - 22C91A4E1193400A0083AC69 /* bn_mp_rand.c in Sources */, - 22C91A4F1193400A0083AC69 /* bn_mp_read_radix.c in Sources */, - 22C91A501193400A0083AC69 /* bn_mp_read_signed_bin.c in Sources */, - 22C91A511193400A0083AC69 /* bn_mp_read_unsigned_bin.c in Sources */, - 22C91A521193400A0083AC69 /* bn_mp_reduce_2k_l.c in Sources */, - 22C91A531193400A0083AC69 /* bn_mp_reduce_2k_setup_l.c in Sources */, - 22C91A541193400A0083AC69 /* bn_mp_reduce_2k_setup.c in Sources */, - E60816FF1B707B7200B283F7 /* der_encode_set.c in Sources */, - E60817011B707B7200B283F7 /* der_encode_setof.c in Sources */, - 22C91A551193400A0083AC69 /* bn_mp_reduce_2k.c in Sources */, - 22C91A561193400A0083AC69 /* bn_mp_reduce_is_2k_l.c in Sources */, - E60817051B707B7200B283F7 /* der_encode_utctime.c in Sources */, - 22C91A571193400A0083AC69 /* bn_mp_reduce_is_2k.c in Sources */, - 22C91A581193400A0083AC69 /* bn_mp_reduce_setup.c in Sources */, - 22C91A591193400A0083AC69 /* bn_mp_reduce.c in Sources */, - 22C91A5A1193400A0083AC69 /* bn_mp_rshd.c in Sources */, - 22C91A5B1193400A0083AC69 /* bn_mp_set_int.c in Sources */, - 22C91A5C1193400A0083AC69 /* bn_mp_set.c in Sources */, - 22C91A5D1193400A0083AC69 /* bn_mp_shrink.c in Sources */, - 22C91A5E1193400A0083AC69 /* bn_mp_signed_bin_size.c in Sources */, - 22C91A5F1193400A0083AC69 /* bn_mp_sqr.c in Sources */, - 22C91A601193400A0083AC69 /* bn_mp_sqrmod.c in Sources */, - 22C91A611193400A0083AC69 /* bn_mp_sqrt.c in Sources */, - 22C91A621193400A0083AC69 /* bn_mp_sub_d.c in Sources */, - 22C91A631193400A0083AC69 /* bn_mp_sub.c in Sources */, - 22C91A641193400A0083AC69 /* bn_mp_submod.c in Sources */, - 22C91A651193400A0083AC69 /* bn_mp_to_signed_bin_n.c in Sources */, - 22C91A661193400A0083AC69 /* bn_mp_to_signed_bin.c in Sources */, - 22C91A671193400A0083AC69 /* bn_mp_to_unsigned_bin_n.c in Sources */, - 22C91A681193400A0083AC69 /* bn_mp_to_unsigned_bin.c in Sources */, - 22C91A691193400A0083AC69 /* bn_mp_toom_mul.c in Sources */, - 22C91A6A1193400A0083AC69 /* bn_mp_toom_sqr.c in Sources */, - 22C91A6B1193400A0083AC69 /* bn_mp_toradix_n.c in Sources */, - 22C91A6C1193400A0083AC69 /* bn_mp_toradix.c in Sources */, - 22C91A6D1193400A0083AC69 /* bn_mp_unsigned_bin_size.c in Sources */, - E60816F31B707B7200B283F7 /* der_encode_ia5_string.c in Sources */, - E60816E01B707B5700B283F7 /* der_encode_sequence_ex.c in Sources */, - 22C91A6E1193400A0083AC69 /* bn_mp_xor.c in Sources */, - 22C91A6F1193400A0083AC69 /* bn_mp_zero.c in Sources */, - 22C91A701193400A0083AC69 /* bn_prime_tab.c in Sources */, - 22C91A711193400A0083AC69 /* bn_reverse.c in Sources */, - 22C91A721193400A0083AC69 /* bn_s_mp_add.c in Sources */, - 22C91A731193400A0083AC69 /* bn_s_mp_exptmod.c in Sources */, - 22C91A741193400A0083AC69 /* bn_s_mp_mul_digs.c in Sources */, - 22C91A751193400A0083AC69 /* bn_s_mp_mul_high_digs.c in Sources */, - 22C91A761193400A0083AC69 /* bn_s_mp_sqr.c in Sources */, - 22C91A771193400A0083AC69 /* bn_s_mp_sub.c in Sources */, - 22C91A781193400A0083AC69 /* bncore.c in Sources */, - 22F5A9C61193DFBA00F8B121 /* SFileVerify.cpp in Sources */, - 228B538411BF7D0D001A58DA /* FileStream.cpp in Sources */, - 22AEA122123125D800359B16 /* SFilePatchArchives.cpp in Sources */, - 225C73541257CD0C0009E8DA /* SBaseFileTable.cpp in Sources */, - 225C735A1257CD1F0009E8DA /* lookup3.c in Sources */, - ); - runOnlyForDeploymentPostprocessing = 0; - }; - 22954ACB11D463A30064B264 /* Sources */ = { - isa = PBXSourcesBuildPhase; - buildActionMask = 2147483647; - files = ( - 22954AD211D463AB0064B264 /* Test.cpp in Sources */, - ); - runOnlyForDeploymentPostprocessing = 0; - }; -/* End PBXSourcesBuildPhase section */ - -/* Begin PBXTargetDependency section */ - 2229F62F11D4653600118914 /* PBXTargetDependency */ = { - isa = PBXTargetDependency; - target = 225530D31056BAC800FA646A /* StormLib */; - targetProxy = 2229F62E11D4653600118914 /* PBXContainerItemProxy */; - }; -/* End PBXTargetDependency section */ - -/* Begin XCBuildConfiguration section */ - 1DEB916508733D950010E9CD /* Debug */ = { - isa = XCBuildConfiguration; - buildSettings = { - ALWAYS_SEARCH_USER_PATHS = NO; - ARCHS = "$(ARCHS_STANDARD_32_64_BIT)"; - COPY_PHASE_STRIP = NO; - DEBUG_INFORMATION_FORMAT = dwarf; - GCC_C_LANGUAGE_STANDARD = c89; - GCC_GENERATE_DEBUGGING_SYMBOLS = YES; - GCC_OPTIMIZATION_LEVEL = 0; - GCC_PREPROCESSOR_DEFINITIONS_NOT_USED_IN_PRECOMPS = ( - _7ZIP_ST, - _DEBUG, - ); - GCC_VERSION = ""; - GCC_WARN_ABOUT_RETURN_TYPE = YES; - GCC_WARN_UNUSED_VARIABLE = YES; - MACOSX_DEPLOYMENT_TARGET = 10.6; - ONLY_ACTIVE_ARCH = YES; - SDKROOT = macosx; - STRIP_INSTALLED_PRODUCT = NO; - }; - name = Debug; - }; - 1DEB916608733D950010E9CD /* Release */ = { - isa = XCBuildConfiguration; - buildSettings = { - ALWAYS_SEARCH_USER_PATHS = NO; - ARCHS = "$(ARCHS_STANDARD_32_64_BIT)"; - COPY_PHASE_STRIP = YES; - DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym"; - GCC_C_LANGUAGE_STANDARD = c89; - GCC_GENERATE_DEBUGGING_SYMBOLS = NO; - GCC_PREPROCESSOR_DEFINITIONS_NOT_USED_IN_PRECOMPS = _7ZIP_ST; - GCC_VERSION = ""; - GCC_WARN_ABOUT_RETURN_TYPE = YES; - GCC_WARN_UNUSED_VARIABLE = YES; - MACOSX_DEPLOYMENT_TARGET = 10.6; - SDKROOT = macosx; - STRIP_INSTALLED_PRODUCT = YES; - }; - name = Release; - }; - 225530D51056BAC900FA646A /* Debug */ = { - isa = XCBuildConfiguration; - buildSettings = { - COPY_PHASE_STRIP = NO; - GCC_DYNAMIC_NO_PIC = NO; - GCC_OPTIMIZATION_LEVEL = 0; - GCC_VERSION = ""; - INSTALL_PATH = /usr/local/lib; - PRODUCT_NAME = StormLib; - }; - name = Debug; - }; - 225530D61056BAC900FA646A /* Release */ = { - isa = XCBuildConfiguration; - buildSettings = { - COPY_PHASE_STRIP = YES; - GCC_VERSION = ""; - INSTALL_PATH = /usr/local/lib; - PRODUCT_NAME = StormLib; - }; - name = Release; - }; - 225FAC960E53B7F900DA2CAE /* Debug */ = { - isa = XCBuildConfiguration; - buildSettings = { - COMBINE_HIDPI_IMAGES = YES; - EXPORTED_SYMBOLS_FILE = "$(PROJECT_DIR)/stormlib_dll/StormLib.exp"; - FRAMEWORK_VERSION = A; - GCC_DYNAMIC_NO_PIC = NO; - GCC_VERSION = com.apple.compilers.llvm.clang.1_0; - INFOPLIST_FILE = Info.plist; - INSTALL_PATH = "$(LOCAL_LIBRARY_DIR)/Frameworks"; - PRODUCT_NAME = StormLib; - }; - name = Debug; - }; - 225FAC970E53B7F900DA2CAE /* Release */ = { - isa = XCBuildConfiguration; - buildSettings = { - COMBINE_HIDPI_IMAGES = YES; - EXPORTED_SYMBOLS_FILE = "$(PROJECT_DIR)/stormlib_dll/StormLib.exp"; - FRAMEWORK_VERSION = A; - GCC_VERSION = com.apple.compilers.llvm.clang.1_0; - INFOPLIST_FILE = Info.plist; - INSTALL_PATH = "$(LOCAL_LIBRARY_DIR)/Frameworks"; - PRODUCT_NAME = StormLib; - }; - name = Release; - }; - 22954AD011D463A40064B264 /* Debug */ = { - isa = XCBuildConfiguration; - buildSettings = { - ALWAYS_SEARCH_USER_PATHS = NO; - COPY_PHASE_STRIP = NO; - GCC_DYNAMIC_NO_PIC = NO; - GCC_OPTIMIZATION_LEVEL = 0; - GCC_PREPROCESSOR_DEFINITIONS_NOT_USED_IN_PRECOMPS = ( - _7ZIP_ST, - _DEBUG, - __STORMLIB_TEST__, - ); - GCC_VERSION = com.apple.compilers.llvm.clang.1_0; - INSTALL_PATH = /usr/local/bin; - PRODUCT_NAME = StormLib_Test; - }; - name = Debug; - }; - 22954AD111D463A40064B264 /* Release */ = { - isa = XCBuildConfiguration; - buildSettings = { - ALWAYS_SEARCH_USER_PATHS = NO; - COPY_PHASE_STRIP = YES; - DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym"; - GCC_VERSION = com.apple.compilers.llvm.clang.1_0; - INSTALL_PATH = /usr/local/bin; - PRODUCT_NAME = StormLib_Test; - }; - name = Release; - }; -/* End XCBuildConfiguration section */ - -/* Begin XCConfigurationList section */ - 1DEB916408733D950010E9CD /* Build configuration list for PBXProject "StormLib" */ = { - isa = XCConfigurationList; - buildConfigurations = ( - 1DEB916508733D950010E9CD /* Debug */, - 1DEB916608733D950010E9CD /* Release */, - ); - defaultConfigurationIsVisible = 0; - defaultConfigurationName = Debug; - }; - 225530D71056BB1600FA646A /* Build configuration list for PBXNativeTarget "StormLib" */ = { - isa = XCConfigurationList; - buildConfigurations = ( - 225530D51056BAC900FA646A /* Debug */, - 225530D61056BAC900FA646A /* Release */, - ); - defaultConfigurationIsVisible = 0; - defaultConfigurationName = Debug; - }; - 225FAC980E53B7F900DA2CAE /* Build configuration list for PBXNativeTarget "StormLibFramework" */ = { - isa = XCConfigurationList; - buildConfigurations = ( - 225FAC960E53B7F900DA2CAE /* Debug */, - 225FAC970E53B7F900DA2CAE /* Release */, - ); - defaultConfigurationIsVisible = 0; - defaultConfigurationName = Debug; - }; - 22954AD911D463E00064B264 /* Build configuration list for PBXNativeTarget "StormLib_Test" */ = { - isa = XCConfigurationList; - buildConfigurations = ( - 22954AD011D463A40064B264 /* Debug */, - 22954AD111D463A40064B264 /* Release */, - ); - defaultConfigurationIsVisible = 0; - defaultConfigurationName = Debug; - }; -/* End XCConfigurationList section */ - }; - rootObject = 0867D690FE84028FC02AAC07 /* Project object */; -} diff --git a/app/jni/src/libultraship/extern/StormLib/StormLib_vs08.sln b/app/jni/src/libultraship/extern/StormLib/StormLib_vs08.sln deleted file mode 100644 index 005e29f..0000000 --- a/app/jni/src/libultraship/extern/StormLib/StormLib_vs08.sln +++ /dev/null @@ -1,139 +0,0 @@ -Microsoft Visual Studio Solution File, Format Version 10.00 -# Visual Studio 2008 -Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "StormLib", "StormLib_vs08.vcproj", "{78424708-1F6E-4D4B-920C-FB6D26847055}" -EndProject -Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "StormLib_dll", "StormLib_vs08_dll.vcproj", "{CB385198-50B1-4CF4-883B-11F042DED6AA}" -EndProject -Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "StormLib_test", "StormLib_vs08_test.vcproj", "{AA561A7B-26EA-49AF-90E8-C53C1FA2965D}" -EndProject -Global - GlobalSection(SolutionConfigurationPlatforms) = preSolution - Debug|Win32 = Debug|Win32 - Debug|x64 = Debug|x64 - DebugAD|Win32 = DebugAD|Win32 - DebugAD|x64 = DebugAD|x64 - DebugAS|Win32 = DebugAS|Win32 - DebugAS|x64 = DebugAS|x64 - DebugUD|Win32 = DebugUD|Win32 - DebugUD|x64 = DebugUD|x64 - DebugUS|Win32 = DebugUS|Win32 - DebugUS|x64 = DebugUS|x64 - Release|Win32 = Release|Win32 - Release|x64 = Release|x64 - ReleaseAD|Win32 = ReleaseAD|Win32 - ReleaseAD|x64 = ReleaseAD|x64 - ReleaseAS|Win32 = ReleaseAS|Win32 - ReleaseAS|x64 = ReleaseAS|x64 - ReleaseUD|Win32 = ReleaseUD|Win32 - ReleaseUD|x64 = ReleaseUD|x64 - ReleaseUS|Win32 = ReleaseUS|Win32 - ReleaseUS|x64 = ReleaseUS|x64 - EndGlobalSection - GlobalSection(ProjectConfigurationPlatforms) = postSolution - {78424708-1F6E-4D4B-920C-FB6D26847055}.Debug|Win32.ActiveCfg = DebugUS|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.Debug|x64.ActiveCfg = DebugUS|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.Debug|x64.Build.0 = DebugUS|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugAD|Win32.ActiveCfg = DebugAD|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugAD|Win32.Build.0 = DebugAD|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugAD|x64.ActiveCfg = DebugAD|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugAD|x64.Build.0 = DebugAD|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugAS|Win32.ActiveCfg = DebugAS|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugAS|Win32.Build.0 = DebugAS|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugAS|x64.ActiveCfg = DebugAS|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugAS|x64.Build.0 = DebugAS|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugUD|Win32.ActiveCfg = DebugUD|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugUD|Win32.Build.0 = DebugUD|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugUD|x64.ActiveCfg = DebugUD|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugUD|x64.Build.0 = DebugUD|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugUS|Win32.ActiveCfg = DebugUS|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugUS|Win32.Build.0 = DebugUS|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugUS|x64.ActiveCfg = DebugUS|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugUS|x64.Build.0 = DebugUS|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.Release|Win32.ActiveCfg = ReleaseUS|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.Release|x64.ActiveCfg = ReleaseUS|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.Release|x64.Build.0 = ReleaseUS|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseAD|Win32.ActiveCfg = ReleaseAD|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseAD|Win32.Build.0 = ReleaseAD|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseAD|x64.ActiveCfg = ReleaseAD|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseAD|x64.Build.0 = ReleaseAD|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseAS|Win32.ActiveCfg = ReleaseAS|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseAS|Win32.Build.0 = ReleaseAS|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseAS|x64.ActiveCfg = ReleaseAS|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseAS|x64.Build.0 = ReleaseAS|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseUD|Win32.ActiveCfg = ReleaseUD|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseUD|Win32.Build.0 = ReleaseUD|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseUD|x64.ActiveCfg = ReleaseUD|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseUD|x64.Build.0 = ReleaseUD|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseUS|Win32.ActiveCfg = ReleaseUS|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseUS|Win32.Build.0 = ReleaseUS|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseUS|x64.ActiveCfg = ReleaseUS|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseUS|x64.Build.0 = ReleaseUS|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.Debug|Win32.ActiveCfg = Debug|Win32 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.Debug|Win32.Build.0 = Debug|Win32 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.Debug|x64.ActiveCfg = Debug|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.Debug|x64.Build.0 = Debug|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.DebugAD|Win32.ActiveCfg = Debug|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.DebugAD|x64.ActiveCfg = Debug|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.DebugAD|x64.Build.0 = Debug|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.DebugAS|Win32.ActiveCfg = Debug|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.DebugAS|x64.ActiveCfg = Debug|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.DebugAS|x64.Build.0 = Debug|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.DebugUD|Win32.ActiveCfg = Debug|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.DebugUD|x64.ActiveCfg = Debug|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.DebugUD|x64.Build.0 = Debug|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.DebugUS|Win32.ActiveCfg = Debug|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.DebugUS|x64.ActiveCfg = Debug|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.DebugUS|x64.Build.0 = Debug|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.Release|Win32.ActiveCfg = Release|Win32 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.Release|Win32.Build.0 = Release|Win32 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.Release|x64.ActiveCfg = Release|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.Release|x64.Build.0 = Release|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.ReleaseAD|Win32.ActiveCfg = Release|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.ReleaseAD|x64.ActiveCfg = Release|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.ReleaseAD|x64.Build.0 = Release|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.ReleaseAS|Win32.ActiveCfg = Release|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.ReleaseAS|x64.ActiveCfg = Release|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.ReleaseAS|x64.Build.0 = Release|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.ReleaseUD|Win32.ActiveCfg = Release|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.ReleaseUD|x64.ActiveCfg = Release|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.ReleaseUD|x64.Build.0 = Release|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.ReleaseUS|Win32.ActiveCfg = Release|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.ReleaseUS|x64.ActiveCfg = Release|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.ReleaseUS|x64.Build.0 = Release|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.Debug|Win32.ActiveCfg = Debug|Win32 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.Debug|Win32.Build.0 = Debug|Win32 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.Debug|x64.ActiveCfg = Debug|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.Debug|x64.Build.0 = Debug|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.DebugAD|Win32.ActiveCfg = Debug|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.DebugAD|x64.ActiveCfg = Debug|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.DebugAD|x64.Build.0 = Debug|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.DebugAS|Win32.ActiveCfg = Debug|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.DebugAS|x64.ActiveCfg = Debug|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.DebugAS|x64.Build.0 = Debug|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.DebugUD|Win32.ActiveCfg = Debug|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.DebugUD|x64.ActiveCfg = Debug|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.DebugUD|x64.Build.0 = Debug|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.DebugUS|Win32.ActiveCfg = Debug|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.DebugUS|x64.ActiveCfg = Debug|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.DebugUS|x64.Build.0 = Debug|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.Release|Win32.ActiveCfg = Release|Win32 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.Release|Win32.Build.0 = Release|Win32 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.Release|x64.ActiveCfg = Release|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.Release|x64.Build.0 = Release|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.ReleaseAD|Win32.ActiveCfg = Release|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.ReleaseAD|x64.ActiveCfg = Release|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.ReleaseAD|x64.Build.0 = Release|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.ReleaseAS|Win32.ActiveCfg = Release|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.ReleaseAS|x64.ActiveCfg = Release|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.ReleaseAS|x64.Build.0 = Release|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.ReleaseUD|Win32.ActiveCfg = Release|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.ReleaseUD|x64.ActiveCfg = Release|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.ReleaseUD|x64.Build.0 = Release|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.ReleaseUS|Win32.ActiveCfg = Release|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.ReleaseUS|x64.ActiveCfg = Release|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.ReleaseUS|x64.Build.0 = Release|x64 - EndGlobalSection - GlobalSection(SolutionProperties) = preSolution - HideSolutionNode = FALSE - EndGlobalSection -EndGlobal diff --git a/app/jni/src/libultraship/extern/StormLib/StormLib_vs08.vcproj b/app/jni/src/libultraship/extern/StormLib/StormLib_vs08.vcproj deleted file mode 100644 index 4f59a1b..0000000 --- a/app/jni/src/libultraship/extern/StormLib/StormLib_vs08.vcproj +++ /dev/null @@ -1,5017 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/app/jni/src/libultraship/extern/StormLib/StormLib_vs08_dll.vcproj b/app/jni/src/libultraship/extern/StormLib/StormLib_vs08_dll.vcproj deleted file mode 100644 index 8658887..0000000 --- a/app/jni/src/libultraship/extern/StormLib/StormLib_vs08_dll.vcproj +++ /dev/null @@ -1,2663 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/app/jni/src/libultraship/extern/StormLib/StormLib_vs08_test.vcproj b/app/jni/src/libultraship/extern/StormLib/StormLib_vs08_test.vcproj deleted file mode 100644 index 2f03a0b..0000000 --- a/app/jni/src/libultraship/extern/StormLib/StormLib_vs08_test.vcproj +++ /dev/null @@ -1,2101 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/app/jni/src/libultraship/extern/StormLib/StormLib_vs19.sln b/app/jni/src/libultraship/extern/StormLib/StormLib_vs19.sln deleted file mode 100644 index 586dd6b..0000000 --- a/app/jni/src/libultraship/extern/StormLib/StormLib_vs19.sln +++ /dev/null @@ -1,162 +0,0 @@ -Microsoft Visual Studio Solution File, Format Version 12.00 -# Visual Studio 15 -VisualStudioVersion = 15.0.28010.2050 -MinimumVisualStudioVersion = 10.0.40219.1 -Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "StormLib", "StormLib_vs19.vcxproj", "{78424708-1F6E-4D4B-920C-FB6D26847055}" -EndProject -Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "StormLib_dll", "StormLib_vs19_dll.vcxproj", "{CB385198-50B1-4CF4-883B-11F042DED6AA}" -EndProject -Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "StormLib_test", "StormLib_vs19_test.vcxproj", "{AA561A7B-26EA-49AF-90E8-C53C1FA2965D}" -EndProject -Global - GlobalSection(SolutionConfigurationPlatforms) = preSolution - Debug|Win32 = Debug|Win32 - Debug|x64 = Debug|x64 - DebugAD|Win32 = DebugAD|Win32 - DebugAD|x64 = DebugAD|x64 - DebugAS|Win32 = DebugAS|Win32 - DebugAS|x64 = DebugAS|x64 - DebugUD|Win32 = DebugUD|Win32 - DebugUD|x64 = DebugUD|x64 - DebugUS|Win32 = DebugUS|Win32 - DebugUS|x64 = DebugUS|x64 - Release|Win32 = Release|Win32 - Release|x64 = Release|x64 - ReleaseAD|Win32 = ReleaseAD|Win32 - ReleaseAD|x64 = ReleaseAD|x64 - ReleaseAS|Win32 = ReleaseAS|Win32 - ReleaseAS|x64 = ReleaseAS|x64 - ReleaseUD|Win32 = ReleaseUD|Win32 - ReleaseUD|x64 = ReleaseUD|x64 - ReleaseUS|Win32 = ReleaseUS|Win32 - ReleaseUS|x64 = ReleaseUS|x64 - EndGlobalSection - GlobalSection(ProjectConfigurationPlatforms) = postSolution - {78424708-1F6E-4D4B-920C-FB6D26847055}.Debug|Win32.ActiveCfg = DebugUS|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.Debug|Win32.Build.0 = DebugUS|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.Debug|x64.ActiveCfg = DebugUS|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.Debug|x64.Build.0 = DebugUS|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugAD|Win32.ActiveCfg = DebugAD|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugAD|Win32.Build.0 = DebugAD|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugAD|x64.ActiveCfg = DebugAD|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugAD|x64.Build.0 = DebugAD|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugAS|Win32.ActiveCfg = DebugAS|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugAS|Win32.Build.0 = DebugAS|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugAS|x64.ActiveCfg = DebugAS|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugAS|x64.Build.0 = DebugAS|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugUD|Win32.ActiveCfg = DebugUD|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugUD|Win32.Build.0 = DebugUD|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugUD|x64.ActiveCfg = DebugUD|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugUD|x64.Build.0 = DebugUD|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugUS|Win32.ActiveCfg = DebugUS|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugUS|Win32.Build.0 = DebugUS|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugUS|x64.ActiveCfg = DebugUS|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.DebugUS|x64.Build.0 = DebugUS|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.Release|Win32.ActiveCfg = ReleaseUS|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.Release|Win32.Build.0 = ReleaseUS|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.Release|x64.ActiveCfg = ReleaseUS|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.Release|x64.Build.0 = ReleaseUS|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseAD|Win32.ActiveCfg = ReleaseAD|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseAD|Win32.Build.0 = ReleaseAD|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseAD|x64.ActiveCfg = ReleaseAD|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseAD|x64.Build.0 = ReleaseAD|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseAS|Win32.ActiveCfg = ReleaseAS|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseAS|Win32.Build.0 = ReleaseAS|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseAS|x64.ActiveCfg = ReleaseAS|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseAS|x64.Build.0 = ReleaseAS|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseUD|Win32.ActiveCfg = ReleaseUD|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseUD|Win32.Build.0 = ReleaseUD|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseUD|x64.ActiveCfg = ReleaseUD|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseUD|x64.Build.0 = ReleaseUD|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseUS|Win32.ActiveCfg = ReleaseUS|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseUS|Win32.Build.0 = ReleaseUS|Win32 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseUS|x64.ActiveCfg = ReleaseUS|x64 - {78424708-1F6E-4D4B-920C-FB6D26847055}.ReleaseUS|x64.Build.0 = ReleaseUS|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.Debug|Win32.ActiveCfg = Debug|Win32 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.Debug|Win32.Build.0 = Debug|Win32 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.Debug|x64.ActiveCfg = Debug|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.Debug|x64.Build.0 = Debug|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.DebugAD|Win32.ActiveCfg = Debug|Win32 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.DebugAD|Win32.Build.0 = Debug|Win32 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.DebugAD|x64.ActiveCfg = Debug|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.DebugAD|x64.Build.0 = Debug|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.DebugAS|Win32.ActiveCfg = Debug|Win32 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.DebugAS|Win32.Build.0 = Debug|Win32 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.DebugAS|x64.ActiveCfg = Debug|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.DebugAS|x64.Build.0 = Debug|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.DebugUD|Win32.ActiveCfg = Debug|Win32 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.DebugUD|Win32.Build.0 = Debug|Win32 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.DebugUD|x64.ActiveCfg = Debug|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.DebugUD|x64.Build.0 = Debug|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.DebugUS|Win32.ActiveCfg = Debug|Win32 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.DebugUS|Win32.Build.0 = Debug|Win32 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.DebugUS|x64.ActiveCfg = Debug|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.DebugUS|x64.Build.0 = Debug|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.Release|Win32.ActiveCfg = Release|Win32 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.Release|Win32.Build.0 = Release|Win32 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.Release|x64.ActiveCfg = Release|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.Release|x64.Build.0 = Release|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.ReleaseAD|Win32.ActiveCfg = Release|Win32 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.ReleaseAD|Win32.Build.0 = Release|Win32 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.ReleaseAD|x64.ActiveCfg = Release|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.ReleaseAD|x64.Build.0 = Release|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.ReleaseAS|Win32.ActiveCfg = Release|Win32 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.ReleaseAS|Win32.Build.0 = Release|Win32 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.ReleaseAS|x64.ActiveCfg = Release|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.ReleaseAS|x64.Build.0 = Release|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.ReleaseUD|Win32.ActiveCfg = Release|Win32 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.ReleaseUD|Win32.Build.0 = Release|Win32 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.ReleaseUD|x64.ActiveCfg = Release|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.ReleaseUD|x64.Build.0 = Release|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.ReleaseUS|Win32.ActiveCfg = Release|Win32 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.ReleaseUS|Win32.Build.0 = Release|Win32 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.ReleaseUS|x64.ActiveCfg = Release|x64 - {CB385198-50B1-4CF4-883B-11F042DED6AA}.ReleaseUS|x64.Build.0 = Release|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.Debug|Win32.ActiveCfg = Debug|Win32 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.Debug|Win32.Build.0 = Debug|Win32 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.Debug|x64.ActiveCfg = Debug|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.Debug|x64.Build.0 = Debug|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.DebugAD|Win32.ActiveCfg = Debug|Win32 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.DebugAD|Win32.Build.0 = Debug|Win32 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.DebugAD|x64.ActiveCfg = Debug|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.DebugAD|x64.Build.0 = Debug|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.DebugAS|Win32.ActiveCfg = Debug|Win32 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.DebugAS|Win32.Build.0 = Debug|Win32 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.DebugAS|x64.ActiveCfg = Debug|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.DebugAS|x64.Build.0 = Debug|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.DebugUD|Win32.ActiveCfg = Debug|Win32 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.DebugUD|Win32.Build.0 = Debug|Win32 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.DebugUD|x64.ActiveCfg = Debug|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.DebugUD|x64.Build.0 = Debug|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.DebugUS|Win32.ActiveCfg = Debug|Win32 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.DebugUS|Win32.Build.0 = Debug|Win32 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.DebugUS|x64.ActiveCfg = Debug|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.DebugUS|x64.Build.0 = Debug|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.Release|Win32.ActiveCfg = Release|Win32 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.Release|Win32.Build.0 = Release|Win32 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.Release|x64.ActiveCfg = Release|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.Release|x64.Build.0 = Release|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.ReleaseAD|Win32.ActiveCfg = Release|Win32 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.ReleaseAD|Win32.Build.0 = Release|Win32 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.ReleaseAD|x64.ActiveCfg = Release|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.ReleaseAD|x64.Build.0 = Release|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.ReleaseAS|Win32.ActiveCfg = Release|Win32 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.ReleaseAS|Win32.Build.0 = Release|Win32 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.ReleaseAS|x64.ActiveCfg = Release|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.ReleaseAS|x64.Build.0 = Release|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.ReleaseUD|Win32.ActiveCfg = Release|Win32 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.ReleaseUD|Win32.Build.0 = Release|Win32 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.ReleaseUD|x64.ActiveCfg = Release|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.ReleaseUD|x64.Build.0 = Release|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.ReleaseUS|Win32.ActiveCfg = Release|Win32 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.ReleaseUS|Win32.Build.0 = Release|Win32 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.ReleaseUS|x64.ActiveCfg = Release|x64 - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D}.ReleaseUS|x64.Build.0 = Release|x64 - EndGlobalSection - GlobalSection(SolutionProperties) = preSolution - HideSolutionNode = FALSE - EndGlobalSection - GlobalSection(ExtensibilityGlobals) = postSolution - SolutionGuid = {04583FA5-D423-4B0D-A42B-F7D44C70991C} - EndGlobalSection -EndGlobal diff --git a/app/jni/src/libultraship/extern/StormLib/StormLib_vs19.vcxproj b/app/jni/src/libultraship/extern/StormLib/StormLib_vs19.vcxproj deleted file mode 100644 index eba3ea2..0000000 --- a/app/jni/src/libultraship/extern/StormLib/StormLib_vs19.vcxproj +++ /dev/null @@ -1,1217 +0,0 @@ - - - - - DebugAD - Win32 - - - DebugAD - x64 - - - DebugAS - Win32 - - - DebugAS - x64 - - - DebugUD - Win32 - - - DebugUD - x64 - - - DebugUS - Win32 - - - DebugUS - x64 - - - ReleaseAD - Win32 - - - ReleaseAD - x64 - - - ReleaseAS - Win32 - - - ReleaseAS - x64 - - - ReleaseUD - Win32 - - - ReleaseUD - x64 - - - ReleaseUS - Win32 - - - ReleaseUS - x64 - - - - StormLib - {78424708-1F6E-4D4B-920C-FB6D26847055} - StormLib - false - 10.0.17134.0 - StaticLibrary - v141_xp - false - - - - MultiByte - - - MultiByte - - - MultiByte - - - MultiByte - - - MultiByte - - - MultiByte - - - MultiByte - - - MultiByte - - - Unicode - - - Unicode - - - Unicode - - - Unicode - - - Unicode - - - Unicode - - - Unicode - - - Unicode - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - <_ProjectFileVersion>11.0.50727.1 - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - $(ProjectName)DAD - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - $(ProjectName)DAD - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - $(ProjectName)DAS - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - $(ProjectName)DAS - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - $(ProjectName)RAD - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - $(ProjectName)RAD - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - $(ProjectName)RAS - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - $(ProjectName)RAS - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - $(ProjectName)DUD - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - $(ProjectName)DUD - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - $(ProjectName)DUS - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - $(ProjectName)DUS - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - $(ProjectName)RUD - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - $(ProjectName)RUD - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - $(ProjectName)RUS - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - $(ProjectName)RUS - - - - Disabled - WIN32;_DEBUG;_LIB;%(PreprocessorDefinitions) - EnableFastChecks - MultiThreadedDebugDLL - - Level1 - ProgramDatabase - true - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)/$(TargetName).lib - - - - - - - - - X64 - - - Disabled - WIN32;_DEBUG;_LIB;%(PreprocessorDefinitions) - EnableFastChecks - MultiThreadedDebugDLL - - Level1 - ProgramDatabase - true - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)/$(TargetName).lib - - - - - - - - - Disabled - WIN32;_DEBUG;_LIB;%(PreprocessorDefinitions) - EnableFastChecks - MultiThreadedDebug - - Level1 - ProgramDatabase - true - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)/$(TargetName).lib - - - - - - - - - X64 - - - Disabled - WIN32;_DEBUG;_LIB;%(PreprocessorDefinitions) - EnableFastChecks - MultiThreadedDebug - - Level1 - ProgramDatabase - true - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)/$(TargetName).lib - - - - - - - - - MaxSpeed - WIN32;NDEBUG;_LIB;%(PreprocessorDefinitions) - MultiThreadedDLL - - Level1 - ProgramDatabase - true - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)/$(TargetName).lib - - - - - - - - - X64 - - - MaxSpeed - WIN32;NDEBUG;_LIB;%(PreprocessorDefinitions) - MultiThreadedDLL - - Level1 - ProgramDatabase - true - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)/$(TargetName).lib - - - - - - - - - MaxSpeed - WIN32;NDEBUG;_LIB;%(PreprocessorDefinitions) - MultiThreaded - - Level1 - ProgramDatabase - true - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)/$(TargetName).lib - - - - - - - - - X64 - - - MaxSpeed - WIN32;NDEBUG;_LIB;%(PreprocessorDefinitions) - MultiThreaded - - Level1 - ProgramDatabase - true - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)/$(TargetName).lib - - - - - - - - - Disabled - WIN32;_DEBUG;_LIB;%(PreprocessorDefinitions) - EnableFastChecks - MultiThreadedDebugDLL - - Level1 - ProgramDatabase - true - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)/$(TargetName).lib - - - - - - - - - X64 - - - Disabled - WIN32;_DEBUG;_LIB;%(PreprocessorDefinitions) - EnableFastChecks - MultiThreadedDebugDLL - - Level1 - ProgramDatabase - true - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)/$(TargetName).lib - - - - - - - - - Disabled - WIN32;_DEBUG;_LIB;%(PreprocessorDefinitions) - EnableFastChecks - MultiThreadedDebug - - Level1 - ProgramDatabase - true - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)/$(TargetName).lib - - - - - - - - - X64 - - - Disabled - WIN32;_DEBUG;_LIB;%(PreprocessorDefinitions) - EnableFastChecks - MultiThreadedDebug - - Level1 - ProgramDatabase - true - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)/$(TargetName).lib - - - - - - - - - MaxSpeed - WIN32;NDEBUG;_LIB;%(PreprocessorDefinitions) - MultiThreadedDLL - - Level1 - ProgramDatabase - true - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)/$(TargetName).lib - - - - - - - - - X64 - - - MaxSpeed - WIN32;NDEBUG;_LIB;%(PreprocessorDefinitions) - MultiThreadedDLL - - Level1 - ProgramDatabase - true - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)/$(TargetName).lib - - - - - - - - - MaxSpeed - WIN32;NDEBUG;_LIB;%(PreprocessorDefinitions) - MultiThreaded - - Level1 - ProgramDatabase - true - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)/$(TargetName).lib - - - - - - - - - X64 - - - MaxSpeed - WIN32;NDEBUG;_LIB;%(PreprocessorDefinitions) - MultiThreaded - - Level1 - ProgramDatabase - true - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)/$(TargetName).lib - - - - - - - - - - - - - - - - - - - - - - - - Create - StormCommon.h - Level4 - - - - - - - - - - - - - - - - - - - - Create - StormCommon.h - Level4 - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - - - Create - StormCommon.h - Level4 - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - - - Use - StormCommon.h - Use - StormCommon.h - Use - StormCommon.h - Use - StormCommon.h - Use - StormCommon.h - Use - StormCommon.h - Use - StormCommon.h - Use - StormCommon.h - Use - StormCommon.h - Use - StormCommon.h - Use - StormCommon.h - Use - StormCommon.h - Use - StormCommon.h - Use - StormCommon.h - Use - StormCommon.h - Use - StormCommon.h - Level4 - Level4 - Level4 - Level4 - Level4 - Level4 - Level4 - Level4 - Level4 - Level4 - Level4 - Level4 - Level4 - Level4 - Level4 - Level4 - - - Create - StormCommon.h - Level4 - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - - - Create - StormCommon.h - Level4 - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - - - Create - StormCommon.h - Level4 - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - - - Create - StormCommon.h - Level4 - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - - - Create - StormCommon.h - Level4 - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - - - Create - StormCommon.h - Level4 - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - - - Create - StormCommon.h - Level4 - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - - - Create - StormCommon.h - Level4 - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - - - Create - StormCommon.h - Level4 - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - - - Create - StormCommon.h - Level4 - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - - - Create - StormCommon.h - Level4 - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - - - Create - StormCommon.h - Level4 - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - - - Create - StormCommon.h - Level4 - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - - - Create - StormCommon.h - Level4 - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - Use - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/StormLib_vs19.vcxproj.filters b/app/jni/src/libultraship/extern/StormLib/StormLib_vs19.vcxproj.filters deleted file mode 100644 index 37915d2..0000000 --- a/app/jni/src/libultraship/extern/StormLib/StormLib_vs19.vcxproj.filters +++ /dev/null @@ -1,830 +0,0 @@ - - - - - {595d6bc1-89d0-4fb8-98f6-be35e73727c4} - - - {721663d8-8692-476f-b0fd-71fdadf69929} - - - {9cc24144-d198-4bd1-b941-b946bd61b982} - - - {be0080d3-fc04-4442-9e28-b4cc2641177d} - - - {adb84a97-8a0c-4988-9473-452326110dff} - - - {87256d6a-e658-4f60-8759-6bff32a35eb2} - - - {d730d7c1-2960-49d2-ba0d-d1a91dd08964} - - - {13e5ccb1-06f1-4d10-bdc1-825b51c64dbf} - - - {73f7f025-7366-4d76-8d60-4327e00b9d18} - - - {be21c641-7727-4d7b-919e-c895d801db17} - - - {694a7758-f909-4b8e-aa13-4d06a8c70eff} - - - {3f01cae6-5676-4f33-bb38-215341eedfc4} - - - {63d75851-c430-4c76-aa08-3398523aab4a} - - - {11175e9e-e9f1-405c-961b-933e72503cdd} - - - {e30512f4-bdf8-4460-823d-475bd8f08d28} - - - {d2889ef6-3f12-4a9b-8624-8d061748ff03} - - - {02c6dfb8-4a58-46c5-bb35-69ba6215a3a6} - - - {563829a0-aaa3-4af2-88a2-8c6445d2754b} - - - {e82b0d03-77ff-46dc-b5a4-5b469224222a} - - - {cb92df18-9435-4db9-997a-e0e7d532cd26} - - - {2920175c-439c-4fd5-b94e-8cf1d3aaadd3} - - - - - Doc Files - - - Doc Files - - - Doc Files - - - - - Header Files - - - Source Files\adpcm - - - Source Files\huffman - - - Source Files\pklib - - - Source Files\sparse - - - Source Files\jenkins - - - Header Files - - - Header Files - - - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files\adpcm - - - Source Files\bzip2 - - - Source Files\bzip2 - - - Source Files\bzip2 - - - Source Files\bzip2 - - - Source Files\bzip2 - - - Source Files\bzip2 - - - Source Files\bzip2 - - - Source Files\huffman - - - Source Files\libtomcrypt\hashes - - - Source Files\libtomcrypt\hashes - - - Source Files\libtomcrypt\hashes - - - Source Files\libtomcrypt\math - - - Source Files\libtomcrypt\math - - - Source Files\libtomcrypt\math - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\ecc - - - Source Files\libtomcrypt\pk\ecc - - - Source Files\libtomcrypt\pk\ecc - - - Source Files\libtomcrypt\pk\ecc - - - Source Files\libtomcrypt\pk\ecc - - - Source Files\libtomcrypt\pk\ecc - - - Source Files\libtomcrypt\pk\pkcs1 - - - Source Files\libtomcrypt\pk\pkcs1 - - - Source Files\libtomcrypt\pk\pkcs1 - - - Source Files\libtomcrypt\pk\pkcs1 - - - Source Files\libtomcrypt\pk\rsa - - - Source Files\libtomcrypt\pk\rsa - - - Source Files\libtomcrypt\pk\rsa - - - Source Files\libtomcrypt\pk\rsa - - - Source Files\libtomcrypt\pk\rsa - - - Source Files\libtomcrypt\pk\rsa - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\lzma - - - Source Files\lzma - - - Source Files\lzma - - - Source Files\lzma - - - Source Files\lzma - - - Source Files\pklib - - - Source Files\pklib - - - Source Files\sparse - - - Source Files\zlib - - - Source Files\zlib - - - Source Files\zlib - - - Source Files\zlib - - - Source Files\zlib - - - Source Files\zlib - - - Source Files\zlib - - - Source Files\zlib - - - Source Files\jenkins - - - Source Files\zlib - - - Source Files - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\pkcs1 - - - Source Files\libtomcrypt\pk\pkcs1 - - - Source Files\libtomcrypt\pk\rsa - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/StormLib_vs19_dll.vcxproj b/app/jni/src/libultraship/extern/StormLib/StormLib_vs19_dll.vcxproj deleted file mode 100644 index ba888e9..0000000 --- a/app/jni/src/libultraship/extern/StormLib/StormLib_vs19_dll.vcxproj +++ /dev/null @@ -1,541 +0,0 @@ - - - - - Debug - Win32 - - - Debug - x64 - - - Release - Win32 - - - Release - x64 - - - - StormLib_dll - {CB385198-50B1-4CF4-883B-11F042DED6AA} - StormLib_dll - Win32Proj - 10.0.17134.0 - - - - DynamicLibrary - v141_xp - Unicode - true - - - DynamicLibrary - v141_xp - Unicode - - - DynamicLibrary - v141_xp - Unicode - true - - - DynamicLibrary - v141_xp - Unicode - - - - - - - - - - - - - - - - - - - <_ProjectFileVersion>14.0.25431.1 - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - true - StormLib - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - true - StormLib - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - false - StormLib - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - false - StormLib - - - - Disabled - WIN32;_DEBUG;_WINDOWS;_USRDLL;%(PreprocessorDefinitions) - EnableFastChecks - MultiThreadedDebug - - Level1 - ProgramDatabase - true - - - $(OutDir)StormLib.dll - .\src\DllMain.def - true - Windows - false - - MachineX86 - - - - - X64 - - - Disabled - WIN32;_DEBUG;_WINDOWS;_USRDLL;%(PreprocessorDefinitions) - EnableFastChecks - MultiThreadedDebug - - Level1 - ProgramDatabase - true - - - $(OutDir)StormLib.dll - .\src\DllMain.def - true - Windows - false - - MachineX64 - - - - - WIN32;NDEBUG;_WINDOWS;_USRDLL;%(PreprocessorDefinitions) - MultiThreaded - - Level1 - ProgramDatabase - true - - - $(OutDir)StormLib.dll - .\src\DllMain.def - true - Windows - true - true - false - - MachineX86 - - - - - X64 - - - WIN32;NDEBUG;_WINDOWS;_USRDLL;%(PreprocessorDefinitions) - MultiThreaded - - Level1 - ProgramDatabase - true - - - $(OutDir)StormLib.dll - .\src\DllMain.def - true - Windows - true - true - false - - MachineX64 - - - - - - - - - - - - - - - - - - - - - - - - - - - - Level4 - Level4 - Level4 - Level4 - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - - - - - - - - - - - Level4 - Level4 - Level4 - Level4 - - - - - - - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/StormLib_vs19_dll.vcxproj.filters b/app/jni/src/libultraship/extern/StormLib/StormLib_vs19_dll.vcxproj.filters deleted file mode 100644 index 644488f..0000000 --- a/app/jni/src/libultraship/extern/StormLib/StormLib_vs19_dll.vcxproj.filters +++ /dev/null @@ -1,838 +0,0 @@ - - - - - {b352ea2c-4169-4b60-85bc-82eadd5a9d2e} - - - {9171b211-949a-4dc1-a028-edf0a2ed4605} - - - {712a20a0-c7a8-4e56-947b-2cf030bbb287} - - - {83502600-f49c-43b1-afe6-038d3560a859} - - - {ea8b08a3-5c21-48e0-b75f-78eaa2adbc22} - - - {593ac5e7-fe06-42b8-8025-e3bd725f95d8} - - - {9887a885-78fa-4164-80b9-9db6b0c11f86} - - - {7db62947-d38d-48e9-8b52-4cad226394a6} - - - {b435fecf-9a65-4f2e-8d64-7dfc70de3137} - - - {d8ad7878-9e42-427a-b5b6-ae51d92b92cf} - - - {07806629-c061-49ed-8212-0585d25fae23} - - - {ca554d9f-b602-452a-971e-86b537ee2ad1} - - - {46e1697c-e6c2-4a8c-b4d2-0142311bb48b} - - - {99279e07-2e33-44c9-8f37-0b810ee4ba25} - - - {04fbcfe0-3023-4fa0-8e36-26ab024a4abf} - - - {4720c7a0-f4aa-4737-978c-9efe8b429906} - - - {856c9964-4d85-40e9-8cbd-f4c672c07780} - - - {7ad3c876-768a-45bc-85b1-38cd492814ea} - - - {22e86a97-80e9-45a0-ac8e-70d7ea848f35} - - - {7b2ea923-8454-4073-bb9c-85de0f66caa1} - - - {5404ec38-706a-47f8-97b7-941c2574ddf2} - - - - - Doc Files - - - Doc Files - - - Doc Files - - - - - Header Files - - - Header Files - - - Header Files - - - Source Files\adpcm - - - Source Files\huffman - - - Source Files\pklib - - - Source Files\sparse - - - Source Files\jenkins - - - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files\adpcm - - - Source Files\bzip2 - - - Source Files\bzip2 - - - Source Files\bzip2 - - - Source Files\bzip2 - - - Source Files\bzip2 - - - Source Files\bzip2 - - - Source Files\bzip2 - - - Source Files\huffman - - - Source Files\libtomcrypt\hashes - - - Source Files\libtomcrypt\hashes - - - Source Files\libtomcrypt\hashes - - - Source Files\libtomcrypt\math - - - Source Files\libtomcrypt\math - - - Source Files\libtomcrypt\math - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\ecc - - - Source Files\libtomcrypt\pk\ecc - - - Source Files\libtomcrypt\pk\ecc - - - Source Files\libtomcrypt\pk\ecc - - - Source Files\libtomcrypt\pk\ecc - - - Source Files\libtomcrypt\pk\ecc - - - Source Files\libtomcrypt\pk\pkcs1 - - - Source Files\libtomcrypt\pk\pkcs1 - - - Source Files\libtomcrypt\pk\pkcs1 - - - Source Files\libtomcrypt\pk\pkcs1 - - - Source Files\libtomcrypt\pk\pkcs1 - - - Source Files\libtomcrypt\pk\pkcs1 - - - Source Files\libtomcrypt\pk\rsa - - - Source Files\libtomcrypt\pk\rsa - - - Source Files\libtomcrypt\pk\rsa - - - Source Files\libtomcrypt\pk\rsa - - - Source Files\libtomcrypt\pk\rsa - - - Source Files\libtomcrypt\pk\rsa - - - Source Files\libtomcrypt\pk\rsa - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\lzma - - - Source Files\lzma - - - Source Files\lzma - - - Source Files\lzma - - - Source Files\lzma - - - Source Files\pklib - - - Source Files\pklib - - - Source Files\sparse - - - Source Files\zlib - - - Source Files\zlib - - - Source Files\zlib - - - Source Files\zlib - - - Source Files\zlib - - - Source Files\zlib - - - Source Files\zlib - - - Source Files\zlib - - - Source Files\zlib - - - Source Files\jenkins - - - Source Files - - - - - Source Files - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/StormLib_vs19_test.vcxproj b/app/jni/src/libultraship/extern/StormLib/StormLib_vs19_test.vcxproj deleted file mode 100644 index d293549..0000000 --- a/app/jni/src/libultraship/extern/StormLib/StormLib_vs19_test.vcxproj +++ /dev/null @@ -1,553 +0,0 @@ - - - - - Debug - Win32 - - - Debug - x64 - - - Release - Win32 - - - Release - x64 - - - - StormLib_test - {AA561A7B-26EA-49AF-90E8-C53C1FA2965D} - StormLib_test - Win32Proj - 10.0.17134.0 - - - - Application - v141_xp - Unicode - true - - - Application - v141_xp - Unicode - - - Application - v141_xp - Unicode - true - - - Application - v141_xp - Unicode - - - - - - - - - - - - - - - - - - - - <_ProjectFileVersion>14.0.25431.1 - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - true - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - true - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - false - - - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - ./bin/$(ProjectName)/$(Platform)/$(Configuration)\ - false - - - - Disabled - WIN32;_DEBUG;_CONSOLE;__STORMLIB_TEST__;%(PreprocessorDefinitions) - EnableFastChecks - MultiThreadedDebug - - Level1 - EditAndContinue - Default - true - - - true - Console - false - - MachineX86 - false - - - - - X64 - - - Disabled - WIN32;_DEBUG;_CONSOLE;__STORMLIB_TEST__;%(PreprocessorDefinitions) - EnableFastChecks - MultiThreadedDebug - - Level1 - ProgramDatabase - Default - true - - - true - Console - false - - MachineX64 - false - - - - - WIN32;NDEBUG;_CONSOLE;__STORMLIB_TEST__;%(PreprocessorDefinitions) - MultiThreaded - - Level1 - ProgramDatabase - true - - - true - Console - true - true - false - - MachineX86 - false - - - - - X64 - - - WIN32;NDEBUG;_CONSOLE;__STORMLIB_TEST__;%(PreprocessorDefinitions) - MultiThreaded - - Level1 - ProgramDatabase - true - - - true - Console - true - true - false - - MachineX64 - false - - - - - - - - - - - - - - - - - - - - - Level4 - Level4 - - - - - - - - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - - - Level1 - Level1 - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - Level4 - Level4 - Level4 - Level4 - - - - - - - - - - - - - Level4 - Level4 - Level4 - Level4 - - - - - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/StormLib_vs19_test.vcxproj.filters b/app/jni/src/libultraship/extern/StormLib/StormLib_vs19_test.vcxproj.filters deleted file mode 100644 index 18f619a..0000000 --- a/app/jni/src/libultraship/extern/StormLib/StormLib_vs19_test.vcxproj.filters +++ /dev/null @@ -1,839 +0,0 @@ - - - - - {1dbbb48c-9db9-4fdb-a903-223ed233cc21} - - - {ab878eef-1074-4594-bac5-272c05774bd8} - - - {640f063a-5028-4ba1-9007-96d98a634561} - - - {6e8cfdab-fca3-4737-8905-6154bc657e15} - - - {a810fdb6-0d21-4279-8e39-b2de644170c0} - - - {7861b4fb-1471-4573-92ea-08c06dc14b93} - - - {8ba6c5c7-3ad0-44e6-8829-5020fce13d49} - - - {92cb0c1d-86f0-4735-9e4e-b07df664c359} - - - {f7fb3d55-94af-4a6e-be7b-76cb909e7325} - - - {337159fe-94a7-45a8-a91b-fa8b9d06b2ae} - - - {359bb3d3-71d5-47e7-967a-1fada7882e4d} - - - {775dbb7e-ef06-4660-9d84-50ff2557ef54} - - - {2e5d39cc-482c-4775-8830-79f8314e72e4} - - - {1e0ef267-228e-4c59-8d88-e3b33aeaff49} - - - {98330deb-0b92-4f02-8016-8a33dc5f5d29} - - - {fa78c716-784a-43a0-a548-db413431973b} - - - {5308566b-d3fd-4561-a7fb-982a63662793} - - - {d5371a5f-1630-4e79-9e7e-1ef654a2ddec} - - - {c2971fba-aff1-42ab-9f4f-71707edabf77} - - - {4f4fe3d6-6f2b-4c83-9cf9-f1d108ecd854} - - - {5aaea51e-4b7c-4a35-b35c-96c2fc7750f1} - - - - - Doc Files - - - Doc Files - - - Doc Files - - - - - Header Files - - - Header Files - - - Header Files - - - Header Files - - - Source Files\adpcm - - - Source Files\huffman - - - Source Files\pklib - - - Source Files\sparse - - - Source Files\jenkins - - - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files - - - Source Files\adpcm - - - Source Files\bzip2 - - - Source Files\bzip2 - - - Source Files\bzip2 - - - Source Files\bzip2 - - - Source Files\bzip2 - - - Source Files\bzip2 - - - Source Files\bzip2 - - - Source Files\huffman - - - Source Files\libtomcrypt\hashes - - - Source Files\libtomcrypt\hashes - - - Source Files\libtomcrypt\hashes - - - Source Files\libtomcrypt\math - - - Source Files\libtomcrypt\math - - - Source Files\libtomcrypt\math - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\misc - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\asn1 - - - Source Files\libtomcrypt\pk\ecc - - - Source Files\libtomcrypt\pk\ecc - - - Source Files\libtomcrypt\pk\ecc - - - Source Files\libtomcrypt\pk\ecc - - - Source Files\libtomcrypt\pk\ecc - - - Source Files\libtomcrypt\pk\ecc - - - Source Files\libtomcrypt\pk\pkcs1 - - - Source Files\libtomcrypt\pk\pkcs1 - - - Source Files\libtomcrypt\pk\pkcs1 - - - Source Files\libtomcrypt\pk\pkcs1 - - - Source Files\libtomcrypt\pk\pkcs1 - - - Source Files\libtomcrypt\pk\pkcs1 - - - Source Files\libtomcrypt\pk\rsa - - - Source Files\libtomcrypt\pk\rsa - - - Source Files\libtomcrypt\pk\rsa - - - Source Files\libtomcrypt\pk\rsa - - - Source Files\libtomcrypt\pk\rsa - - - Source Files\libtomcrypt\pk\rsa - - - Source Files\libtomcrypt\pk\rsa - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\libtommath - - - Source Files\lzma - - - Source Files\lzma - - - Source Files\lzma - - - Source Files\lzma - - - Source Files\lzma - - - Source Files\pklib - - - Source Files\pklib - - - Source Files\sparse - - - Source Files\zlib - - - Source Files\zlib - - - Source Files\zlib - - - Source Files\zlib - - - Source Files\zlib - - - Source Files\zlib - - - Source Files\zlib - - - Source Files\zlib - - - Source Files\zlib - - - Source Files\jenkins - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/doc/History.txt b/app/jni/src/libultraship/extern/StormLib/doc/History.txt deleted file mode 100644 index b6a098c..0000000 --- a/app/jni/src/libultraship/extern/StormLib/doc/History.txt +++ /dev/null @@ -1,78 +0,0 @@ - - StormLib history - ================ - - Version 9.11 - - - Fixed bug in processing HET table. - - Version 9.10 - - - Support for weak-signing - - Anti-protector: New Spazzler - - Version 9.00 - - - Support for streaming (master-mirror) - - Support for multi-file MPQs used by some WoW versions - - Opening maps protected by Spazzler protector - - Opening maps protected by BOBA protector - - Version 8.02 - - - Support for UNICODE encoding for on-disk files - - Optimized file deleting - - Version 8.01 - - - SFileFindFirstFile and SFileFindNextFile no longer find files that have - patch file in the oldest MPQ in the patch chain - - Write support for MPQs version 4 - - Version 8.00 - - - Updated support for protected maps from Warcraft III - - Version 7.11 - - - Support for MPQs v 3.0 (WOW-Cataclysm BETA) - - StormLib now deals properly with files that have MPQ_SECTOR_CHECKSUM missing, - but have sector checksum entry present in the sector offset table - - Version 7.10 - - - Support for partial MPQs ("interface.MPQ.part") - - The only operation that is externally allowed to do with internal files - ("(listfile)", "(attributes)" and "(signature)") is reading. Attempt to modify any of the file - fails and GetLastError returns ERROR_INTERNAL_FILE - - Fixed memory leak that has occured when writing more than one sector to the file at once - - Version 7.01 - - - Support for adding files from memory - - Fixed improper validation of handles to MPQ file and MPQ archive - - Fixed bug where StormLib didn't save CRC32 of the file when added to archive - - Version 7.00 - - - Properly deals with MPQs protected by w3xMaster - - Major rewrite - - Fixed support for (attributes) - - Added file verification - - Added MPQ signature verification - - Version 6.22 - - - Properly deals with MPQs protected by w3xMaster - - Version 6.21 - - - SFileRenameFile now properly re-crypts the file if necessary. - - SFileFindFirstFile correctly deals with deleted files - - Version 6.20 - - - Fixed lots of bugs when processing files with same names but different locales - - Fixed bugs when repeately extracts the same file with MPQ_FILE_SINGLE_UNIT flag - - Added SFileFlushArchive - - Fixed issue opening AVI files renamed to MPQ using SFileCreateArchiveEx diff --git a/app/jni/src/libultraship/extern/StormLib/doc/The MoPaQ File Format 0.9.txt b/app/jni/src/libultraship/extern/StormLib/doc/The MoPaQ File Format 0.9.txt deleted file mode 100644 index ce8d8f7..0000000 --- a/app/jni/src/libultraship/extern/StormLib/doc/The MoPaQ File Format 0.9.txt +++ /dev/null @@ -1,318 +0,0 @@ -THE MOPAQ ARCHIVE FORMAT -v0.9 (Thursday, June 30, 2005) -by Justin Olbrantz(Quantam) - -Distribution and reproduction of this specification are allowed without limitation, as long as it is not altered. Quoting -in other works is freely allowed, as long as the source and author of the quote is stated. - -TABLE OF CONTENTS -1. Introduction to the MoPaQ Format -2. The MoPaQ Format - 2.1 General Archive Layout - 2.2 Archive Header - 2.3 Block Table - 2.4 Hash Table - 2.5 File Data - 2.6 Listfile - 2.7 Extended Attributes - 2.8 Weak (Old) Digital Signature - 2.9 Strong (New) Digital Signature -3. Algorithm Source Code - 3.1 Encryption/Decryption - 3.2 Hashing - 3.3 Conversion of FILETIME and time_t - -1. INTRODUCTION TO THE MOPAQ FORMAT -The MoPaQ (or MPQ) format is an archive file format designed by Mike O'Brien (hence the name Mike O'brien PaCK) at Blizzard -Entertainment. The format has been used in all Blizzard games since (and including) Diablo. It is heavily optimized to be -a read-only game archive format, and excels at this role. - -The Blizzard MoPaQ-reading functions are contained in the Storm module, which my be either statically or dynamically linked. -The Blizzard MoPaQ-writing functions are contained in the MPQAPI module, which is always statically linked. - -2. THE MOPAQ FORMAT -All numbers in the MoPaQ format are in little endian. Data types are listed either as int (integer, the number of bits specified), -byte (8 bits), and char (bytes which contain ASCII characters). All sizes and offsets are in bytes, unless specified otherwise. -Structure members are listed in the following general form: -offset from the beginning of the structure: data type(array size) member name : member description - -2.1 GENERAL ARCHIVE LAYOUT -- Archive Header -- File Data -- File Data - Special Files -- Hash Table -- Block Table -- Strong Digital signature - -This is the usual archive format, and is not absolutely essential. Some archives have been observed placing the hash table -and file table after the archive header, and before the file data. - -2.2 ARCHIVE HEADER -00h: char(4) Magic : Indicates that the file is a MoPaQ archive. Must be ASCII "MPQ" 1Ah. -04h: int32 HeaderSize : Size of the archive header. Should be 32. -08h: int32 ArchiveSize : Size of the whole archive, including the header. Does not include the strong digital signature, if present. -This size is used, among other things, for determining the region to hash in computing the digital signature. -0Ch: int16 Unknown : Unknown -0Eh: int8 SectorSizeShift : Power of two exponent specifying the number of 512-byte disk sectors in each logical sector -in the archive. The size of each logical sector the archive is 512 * 2^SectorSizeShift. Bugs in the Storm library dictate -that this should always be 3 (4096 byte sectors). -10h: int32 HashTableOffset : Offset to the beginning of the hash table, relative to the beginning of the archive. -14h: int32 BlockTableOffset : Offset to the beginning of the block table, relative to the beginning of the archive. -18h: int32 HashTableEntries : Number of entries in the hash table. Must be a power of two, and must be less than 2^16. -1Ch: int32 BlockTableEntries : Number of entries in the block table. - -The archive header is the first structure in the archive, at archive offset 0, but the archive does not need to be at offset -0 of the containing file. The offset of the archive in the file is referred to here as ArchiveOffset. If the archive is not -at the beginning of the file, it must begin at a disk sector boundary (512 bytes). Early versions of Storm require that the -archive be at the end of the containing file (ArchiveOffset + ArchiveSize = file size), but this is not required in newer -versions (due to the strong digital signature not being considered a part of the archive). - -2.3 BLOCK TABLE -The block table contains entries for each region in the archive. Regions may be either files or empty space, which may be -overwritten by new files (typically this space is from deleted file data). The block table is encrypted, using the hash -of "(block table)" as the key. Each entry is structured as follows: - -00h: int32 BlockOffset : Offset of the beginning of the block, relative to the beginning of the archive. Meaningless if the block size is 0. -04h: int32 BlockSize : Size of the block in the archive. -08h: int32 FileSize : Size of the file data stored in the block. Only valid if the block is a file, otherwise meaningless, and should be 0. If the file is compressed, this is the size of the uncompressed file data. -0Ch: int32 Flags : Bit mask of the flags for the block. The following values are conclusively identified: - 80000000h: Block is a file, and follows the file data format; otherwise, block is free space, and may be overwritten. If the block is not a file, all other flags should be cleared. - 01000000h: File is stored as a single unit, rather than split into sectors. - 00020000h: The file's encryption key is adjusted by the block offset and file size (explained in detail in the File Data section). File must be encrypted. - 00010000h: File is encrypted. - 00000200h: File is compressed. Mutually exclusive to file imploded. - 00000100h: File is imploded. Mutually exclusive to file compressed. - -2.4 HASH TABLE -Instead of storing file names, for quick access MoPaQs use a fixed, power of two-size hash table of files in the archive. A file is uniquely identified by its file path, its language, and its platform. The home entry for a file in the hash table is computed as a hash of the file path. In the event of a collision (the home entry is occupied by another file), progressive overflow is used, and the file is placed in the next available hash table entry. Searches for a desired file in the hash table proceed from the home entry for the file until either the file is found, the entire hash table is searched, or an empty hash table entry (FileBlockIndex of FFFFFFFFh) is encountered. The hash table is encrypted using the hash of "(hash table)" as the key. Each entry is structured as follows: - -00h: int32 FilePathHashA : The hash of the file path, using method A. -04h: int32 FilePathHashB : The hash of the file path, using method B. -08h: int16 Language : The language of the file. This is a Windows LANGID data type, and uses the same values. 0 indicates the default language (American English), or that the file is language-neutral. -0Ah: int8 Platform : The platform the file is used for. 0 indicates the default platform. No other values have been observed. -0Ch: int32 FileBlockIndex : If the hash table entry is valid, this is the index into the block table of the file. Otherwise, one of the following two values: - FFFFFFFFh: Hash table entry is empty, and has always been empty. Terminates searches for a given file. - FFFFFFFEh: Hash table entry is empty, but was valid at some point (in other words, the file was deleted). Does not terminate searches for a given file. - -2.5 FILE DATA -00h: int32(SectorsInFile + 1) SectorOffsetTable : Offsets to the start of each sector's data, relative to the beginning of the file data. Not present if this information is calculatable (see details below). -immediately following SectorOffsetTable: SectorData : Data of each sector in the file, packed end to end (see details below). - -Normally, file data is split up into sectors, for simple streaming. All sectors, save for the last, will contain as many bytes of file data as specified in the archive header's SectorSizeShift; the last sector may be smaller than this, depending on the size of the file data. This sector size is the size of the raw file data; if the file is compressed, the compressed sector will be smaller or the same size as the uncompressed sector size. Individual sectors in a compressed file may be stored uncompressed; this occurs if and only if the sector could not be compressed by the algorithm used (if the compressed sector size was greater than or equal to the size of the raw data), and is indicated by the sector's compressed size in SectorOffsetTable being equal to the uncompressed size of the sector (which may be calculated from the FileSize). - -If the sector is compressed (but not imploded), a bit mask byte of the compression algorithm(s) used to compress the sector is appended to the beginning of the compressed sector data. This additional byte counts towards the total size of the sector; if the size of the sector (including this byte) exceeds or matches the uncompressed size of the sector data, the sector will be stored uncompressed, and this byte omitted. Multiple compression algorithms may be used on the same sector; in this case, successive compression occurs in the order the algorithms are listed below, and decompression occurs in the opposite order. For implimentations of all of these algorithms, see StormLib. - 40h: IMA ADPCM mono - 80h: IMA ADPCM stereo - 01h: Huffman encoded - 02h: Deflated (see ZLib) - 08h: Imploded (see PKWare Data Compression Library) - 10h: BZip2 compressed (see BZip2) - -If the file is stored as a single unit (indicated in the file's Flags), there is effectively only a single sector, which -contains the entire file. - -If the file is encrypted, each sector (after compression and appendage of the compression type byte, if applicable) -is encrypted with the file's key. The base key for a file is determined by a hash of the file name stripped of the -directory (i.e. the key for a file named "directory\file" would be computed as the hash of "file"). If this key is -adjusted, as indicated in the file's Flags, the final key is calculated as ((base key + BlockOffset - ArchiveOffset) -XOR FileSize) (StormLib - an open-source implementation of the MoPaQ reading and writing functions, -by Ladislav Zezula - incorrectly uses an AND in place of the XOR). Each sector is encrypted using the key + the -0-based index of the sector in the file. The SectorOffsetTable, if present, is encrypted using the key - 1. - -The SectorOffsetTable is omitted when the sizes and offsets of all sectors in the file are calculatable from the FileSize. -This can happen in several circumstances. If the file is not compressed/imploded, then the size and offset of all sectors -is known, based on the archive's SectorSizeShift. If the file is stored as a single unit compressed/imploded, then the -SectorOffsetTable is omitted, as the single file "sector" corresponds to BlockSize and FileSize, as mentioned previously. -Note that the SectorOffsetTable will always be present if the file is compressed/imploded and the file is not stored as -a single unit, even if there is only a single sector in the file (the size of the file is less than or equal to the -archive's sector size). - -2.6 LISTFILE -The listfile is a very simple extension to the MoPaQ format that contains the file paths of (most) files in the archive. -The languages and platforms of the files are not stored in the listfile. The listfile is contained in the file "(listfile)", -and is simply a non-Unix-style text file with one file path on each line, lines terminated with the bytes 0Dh 0Ah. The file -"(listfile)" may not be listed in the listfile. - -2.7 EXTENDED ATTRIBUTES -The extended attributes are optional file attributes for files in the block table. These attributes were added at times after -the MoPaQ format was already finalized, and it is not necessary for every archive to have all (or any) of the extended attributes. -If an archive contains a given attribute, there will be an instance of that attribute for every block in the block table, although -the attribute will be meaningless if the block is not a file. The order of the attributes for blocks correspond to the order of the -blocks in the block table, and are of the same number. The attributes are stored in parallel arrays in the "(attributes)" file, -in the archive. The attributes corresponding to this file need not be valid (and logically cannot be). Unlike all the other -structures in the MoPaQ format, entries in the extended attributes are NOT guaranteed to be aligned. Also note that in some -archives, malicious zeroing of the attributes has been observed, perhaps with the intent of breaking archive viewers. This -file is structured as follows: - -00h: int32 Version : Specifies the extended attributes format version. For now, must be 100. -04h: int32 AttributesPresent : Bit mask of the extended attributes present in the archive: - 00000001h: File CRC32s. - 00000002h: File timestamps. - 00000004h: File MD5s. -08h: int32(BlockTableEntries) CRC32s : CRC32s of the (uncompressed) file data for each block in the archive. Omitted if the -archive does not have CRC32s. immediately after CRC32s: FILETIME(BlockTableEntries) Timestamps : Timestamps for each block -in the archive. The format is that of the Windows FILETIME structure. Omitted if the archive does not have timestamps. -immediately after Timestamps: MD5(BlockTableEntries) MD5s : MD5s of the (uncompressed) file data for each block in the archive. -Omitted if the archive does not have MD5s. - -2.8 WEAK DIGITAL SIGNATURE -The weak digital signature is a digital signature using Microsoft CryptoAPI. It is an implimentation of the RSASSA-PKCS1-v1_5 -digital signature protocol, using the MD5 hashing algorithm and a 512-bit (weak) RSA key (for more information about this -protocol, see the RSA Labs PKCS1 specification). The public key and exponent are stored in a resource in Storm. The signature -is stored uncompressed, unencrypted in the file "(signature)" in the archive. The archive is hashed from the beginning of the -archive (ArchiveOffset in the containing file) to the end of the archive (the length indicated by ArchiveSize); the signature -file is added to the archive before signing, and the space occupied by the file is considered to be all binary 0s during -signing/verification. This file is structured as follows: - -00h: int32 Unknown : Must be 0. -04h: int32 Unknown : must be 0. -08h: int512 Signature : The digital signature. Like all other numbers in the MoPaQ format, this is stored in little-endian order. - -2.9 STRONG DIGITAL SIGNATURE -The strong digital signature uses a simple proprietary implementation of RSA signing, using the SHA-1 hashing algorithm and -a 2048-bit (strong) RSA key. The default public key and exponent are stored in Storm, but other keys may be used as well. -The strong digital signature is stored immediately after the archive, in the containing file; the entire archive (ArchiveSize -bytes, starting at ArchiveOffset in the containing file) is hashed as a single block. The signature has the following format: - -00h: char(4) Magic : Indicates the presence of a digital signature. Must be "NGIS" ("SIGN" backwards). -04h: int2048 Signature : The digital signature, stored in little-endian format. - -When the Signature field is decrypted with the public key and exponent, and the result stored in little-endian order, it is structured as follows: - -00h: byte Padding : Must be 0Bh. -01h: byte(235) Padding : Must be BBh. -ECh: byte(20) SHA-1 : SHA-1 hash of the archive, in standard SHA-1 format. - -3. ALGORITHM SOURCE CODE -3.1 ENCRYPTION/DECRYPTION -I believe this was derived at some point from code in StormLib. Assumes the long type to be 32 bits, and the machine to be little endian order. - -unsigned long dwCryptTable[0x500]; - -void InitializeCryptTable() -{ - unsigned long seed = 0x00100001; - unsigned long index1 = 0; - unsigned long index2 = 0; - int i; - - for (index1 = 0; index1 < 0x100; index1++) - { - for (index2 = index1, i = 0; i < 5; i++, index2 += 0x100) - { - unsigned long temp1, temp2; - - seed = (seed * 125 + 3) % 0x2AAAAB; - temp1 = (seed & 0xFFFF) << 0x10; - - seed = (seed * 125 + 3) % 0x2AAAAB; - temp2 = (seed & 0xFFFF); - - dwCryptTable[index2] = (temp1 | temp2); - } - } -} - -void EncryptData(void *lpbyBuffer, unsigned long dwLength, unsigned long dwKey) -{ - unsigned long *lpdwBuffer = (unsigned long *)lpbyBuffer; - unsigned long seed = 0xEEEEEEEE; - unsigned long ch; - - assert(lpbyBuffer); - - dwLength /= sizeof(unsigned long); - - while(dwLength-- > 0) - { - seed += dwCryptTable[0x400 + (dwKey & 0xFF)]; - ch = *lpdwBuffer ^ (dwKey + seed); - - dwKey = ((~dwKey << 0x15) + 0x11111111) | (dwKey >> 0x0B); - seed = *lpdwBuffer + seed + (seed << 5) + 3; - - *lpdwBuffer++ = ch; - } -} - -void DecryptData(void *lpbyBuffer, unsigned long dwLength, unsigned long dwKey) -{ - unsigned long *lpdwBuffer = (unsigned long *)lpbyBuffer; - unsigned long seed = 0xEEEEEEEE; - unsigned long ch; - - assert(lpbyBuffer); - - dwLength /= sizeof(unsigned long); - - while(dwLength-- > 0) - { - seed += dwCryptTable[0x400 + (dwKey & 0xFF)]; - ch = *lpdwBuffer ^ (dwKey + seed); - - dwKey = ((~dwKey << 0x15) + 0x11111111) | (dwKey >> 0x0B); - seed = ch + seed + (seed << 5) + 3; - - *lpdwBuffer++ = ch; - } -} - -3.2 HASHING -Based on code from StormLib. - -// Different types of hashes to make with HashString -#define MPQ_HASH_TABLE_OFFSET 0 -#define MPQ_HASH_NAME_A 1 -#define MPQ_HASH_NAME_B 2 -#define MPQ_HASH_FILE_KEY 3 - -unsigned long HashString(const char *lpszString, unsigned long dwHashType) -{ - unsigned long seed1 = 0x7FED7FED; - unsigned long seed2 = 0xEEEEEEEE; - int ch; - - while (*lpszString != 0) - { - ch = toupper(*lpszString++); - - seed1 = dwCryptTable[(dwHashType * 0xFF) + ch] ^ (seed1 + seed2); - seed2 = ch + seed1 + seed2 + (seed2 << 5) + 3; - } - return seed1; -} - -3.3 CONVERSION OF FILETIME AND time_t - -#define EPOCH_OFFSET 116444736000000000ULL // Number of 100 ns units between 01/01/1601 and 01/01/1970 - -bool GetTimeFromFileTime(FILETIME &fileTime, time_t &time) -{ - // The FILETIME represents a 64-bit integer: the number of 100 ns units since January 1, 1601 - unsigned long long nTime = ((unsigned long long)fileTime.dwHighDateTime << 32) + fileTime.dwLowDateTime; - - if (nTime < EPOCH_OFFSET) - return false; - - nTime -= EPOCH_OFFSET; // Convert the time base from 01/01/1601 to 01/01/1970 - nTime /= 10000000ULL; // Convert 100 ns to sec - - time = (time_t)nTime; - - // Test for overflow (FILETIME is 64 bits, time_t is 32 bits) - if ((nTime - (unsigned long long)time) > 0) - return false; - - return true; -} - -void GetFileTimeFromTime(time_t &time, FILETIME &fileTime) -{ - unsigned long long nTime = (unsigned long long)time; - - nTime *= 10000000ULL; - nTime += EPOCH_OFFSET; - - fileTime.dwLowDateTime = (DWORD)nTime; - fileTime.dwHighDateTime = (DWORD)(nTime >> 32); -} diff --git a/app/jni/src/libultraship/extern/StormLib/doc/The MoPaQ File Format 1.0.txt b/app/jni/src/libultraship/extern/StormLib/doc/The MoPaQ File Format 1.0.txt deleted file mode 100644 index 2f13945..0000000 --- a/app/jni/src/libultraship/extern/StormLib/doc/The MoPaQ File Format 1.0.txt +++ /dev/null @@ -1,433 +0,0 @@ -THE MOPAQ ARCHIVE FORMAT -v1.0 (Friday, September 1, 2006) -by Justin Olbrantz(Quantam) - -Distribution and reproduction of this specification are allowed without limitation, as long as it is not altered. Quotation in other works is freely allowed, as long as the source and author of the quote are stated. - -TABLE OF CONTENTS -1. Introduction to the MoPaQ Format -2. The MoPaQ Format - 2.1 General Archive Layout - 2.2 Archive Header - 2.3 Block Table - 2.4 Extended Block Table - 2.5 Hash Table - 2.6 File Data - 2.7 Listfile - 2.8 Extended Attributes - 2.9 Weak (Old) Digital Signature - 2.10 Strong (New) Digital Signature -3. Algorithm Source Code - 3.1 Encryption/Decryption - 3.2 Hashing and File Key Computation - 3.3 Finding Files - 3.4 Deleting Files - 3.5 Conversion of FILETIME and time_t - 3.6 Forming a 64-bit Large Archive Offset from 32-bit and 16-bit Components -4. Revision History - -1. INTRODUCTION TO THE MOPAQ FORMAT -The MoPaQ (or MPQ) format is an archive file format designed by Mike O'Brien (hence the name Mike O'brien PaCK) at Blizzard Entertainment. The format has been used in all Blizzard games since (and including) Diablo. It is heavily optimized to be a read-only game archive format, and excels at this role. - -The Blizzard MoPaQ-reading functions are contained in the Storm module, which my be either statically or dynamically linked. The Blizzard MoPaQ-writing functions are contained in the MPQAPI module, which is always statically linked. - -StormLib - mentioned several times in this specification - is an open-source MoPaQ reading and writing library written by Ladislav Zezula (no affiliation with Blizzard Entertainment). While it's a bit dated, and does not support all of the newer MoPaQ features, it contains source code to the more exotic compression methods used by MoPaQ, such as the PKWare implode algorithm, MoPaQ's huffman compression algorithm, and the IMA ADPCM compression used by MoPaQ. - -2. THE MOPAQ FORMAT -All numbers in the MoPaQ format are in little endian byte order; signed numbers use the two's complement system. Data types are listed either as int (integer, the number of bits specified), byte (8 bits), or char (bytes which contain ASCII characters). All sizes and offsets are in bytes, unless specified otherwise. Structure members are listed in the following general form: -offset from the beginning of the structure: data type(array size) member name : member description - -2.1 GENERAL ARCHIVE LAYOUT -- Archive Header -- File Data -- File Data - Special Files -- Hash Table -- Block Table -- Extended Block Table -- Strong Digital signature - -This is the usual archive format, but it is not mandatory. Some archives have been observed placing the hash table and file table after the archive header, and before the file data. - -2.2 ARCHIVE HEADER -00h: char(4) Magic : Indicates that the file is a MoPaQ archive. Must be ASCII "MPQ" 1Ah. -04h: int32 HeaderSize : Size of the archive header. -08h: int32 ArchiveSize : Size of the whole archive, including the header. Does not include the strong digital signature, if present. This size is used, among other things, for determining the region to hash in computing the digital signature. This field is deprecated in the Burning Crusade MoPaQ format, and the size of the archive is calculated as the size from the beginning of the archive to the end of the hash table, block table, or extended block table (whichever is largest). -0Ch: int16 FormatVersion : MoPaQ format version. MPQAPI will not open archives where this is negative. Known versions: - 0000h: Original format. HeaderSize should be 20h, and large archives are not supported. - 0001h: Burning Crusade format. Header size should be 2Ch, and large archives are supported. -0Eh: int8 SectorSizeShift : Power of two exponent specifying the number of 512-byte disk sectors in each logical sector in the archive. The size of each logical sector in the archive is 512 * 2^SectorSizeShift. Bugs in the Storm library dictate that this should always be 3 (4096 byte sectors). -10h: int32 HashTableOffset : Offset to the beginning of the hash table, relative to the beginning of the archive. -14h: int32 BlockTableOffset : Offset to the beginning of the block table, relative to the beginning of the archive. -18h: int32 HashTableEntries : Number of entries in the hash table. Must be a power of two, and must be less than 2^16 for the original MoPaQ format, or less than 2^20 for the Burning Crusade format. -1Ch: int32 BlockTableEntries : Number of entries in the block table. -Fields only present in the Burning Crusade format and later: -20h: int64 ExtendedBlockTableOffset : Offset to the beginning of the extended block table, relative to the beginning of the archive. -28h: int16 HashTableOffsetHigh : High 16 bits of the hash table offset for large archives. -2Ah: int16 BlockTableOffsetHigh : High 16 bits of the block table offset for large archives. - -The archive header is the first structure in the archive, at archive offset 0; however, the archive does not need to be at offset 0 of the containing file. The offset of the archive in the file is referred to here as ArchiveOffset. If the archive is not at the beginning of the file, it must begin at a disk sector boundary (512 bytes). Early versions of Storm require that the archive be at the end of the containing file (ArchiveOffset + ArchiveSize = file size), but this is not required in newer versions (due to the strong digital signature not being considered a part of the archive). - -2.3 BLOCK TABLE -The block table contains entries for each region in the archive. Regions may be either files, empty space, which may be overwritten by new files (typically this space is from deleted file data), or unused block table entries. Empty space entries should have BlockOffset and BlockSize nonzero, and FileSize and Flags zero; unused block table entries should have BlockSize, FileSize, and Flags zero. The block table is encrypted, using the hash of "(block table)" as the key. Each entry is structured as follows: - -00h: int32 BlockOffset : Offset of the beginning of the block, relative to the beginning of the archive. -04h: int32 BlockSize : Size of the block in the archive. -08h: int32 FileSize : Size of the file data stored in the block. Only valid if the block is a file; otherwise meaningless, and should be 0. If the file is compressed, this is the size of the uncompressed file data. -0Ch: int32 Flags : Bit mask of the flags for the block. The following values are conclusively identified: - 80000000h: Block is a file, and follows the file data format; otherwise, block is free space or unused. If the block is not a file, all other flags should be cleared, and FileSize should be 0. - 01000000h: File is stored as a single unit, rather than split into sectors. - 00020000h: The file's encryption key is adjusted by the block offset and file size (explained in detail in the File Data section). File must be encrypted. - 00010000h: File is encrypted. - 00000200h: File is compressed. File cannot be imploded. - 00000100h: File is imploded. File cannot be compressed. - -2.4 EXTENDED BLOCK TABLE -The extended block table was added to support archives larger than 4 gigabytes (2^32 bytes). The table contains the upper bits of the archive offsets for each block in the block table. It is simply an array of int16s, which become bits 32-47 of the archive offsets for each block, with bits 48-63 being zero. Individual blocks in the archive are still limited to 4 gigabytes in size. This table is only present in Burning Crusade format archives that exceed 4 gigabytes size. - -As of the Burning Crusade Friends and Family beta, this table is not encrypted. - -2.5 HASH TABLE -Instead of storing file names, for quick access MoPaQs use a fixed, power of two-size hash table of files in the archive. A file is uniquely identified by its file path, its language, and its platform. The home entry for a file in the hash table is computed as a hash of the file path. In the event of a collision (the home entry is occupied by another file), progressive overflow is used, and the file is placed in the next available hash table entry. Searches for a desired file in the hash table proceed from the home entry for the file until either the file is found, the entire hash table is searched, or an empty hash table entry (FileBlockIndex of FFFFFFFFh) is encountered. The hash table is encrypted using the hash of "(hash table)" as the key. Each entry is structured as follows: - -00h: int32 FilePathHashA : The hash of the file path, using method A. -04h: int32 FilePathHashB : The hash of the file path, using method B. -08h: int16 Language : The language of the file. This is a Windows LANGID data type, and uses the same values. 0 indicates the default language (American English), or that the file is language-neutral. -0Ah: int8 Platform : The platform the file is used for. 0 indicates the default platform. No other values have been observed. -0Ch: int32 FileBlockIndex : If the hash table entry is valid, this is the index into the block table of the file. Otherwise, one of the following two values: - FFFFFFFFh: Hash table entry is empty, and has always been empty. Terminates searches for a given file. - FFFFFFFEh: Hash table entry is empty, but was valid at some point (in other words, the file was deleted). Does not terminate searches for a given file. - -2.6 FILE DATA -The data for each file is composed of the following structure: -00h: int32(SectorsInFile + 1) SectorOffsetTable : Offsets to the start of each sector, relative to the beginning of the file data. The last entry contains the file size, making it possible to easily calculate the size of any given sector. This table is not present if this information can be calculated (see details below). -immediately following SectorOffsetTable: SECTOR Sectors(SectorsInFile) : Data of each sector in the file, packed end to end (see details below). - -Normally, file data is split up into sectors, for simple streaming. All sectors, save for the last, will contain as many bytes of file data as specified in the archive header's SectorSizeShift; the last sector may contain less than this, depending on the size of the entire file's data. If the file is compressed or imploded, the sector will be smaller or the same size as the file data it contains. Individual sectors in a compressed or imploded file may be stored uncompressed; this occurs if and only if the file data the sector contains could not be compressed by the algorithm(s) used (if the compressed sector size was greater than or equal to the size of the file data), and is indicated by the sector's size in SectorOffsetTable being equal to the size of the file data in the sector (which may be calculated from the FileSize). - -The format of each sector depends on the kind of sector it is. Uncompressed sectors are simply the the raw file data contained in the sector. Imploded sectors are the raw compressed data following compression with the implode algorithm (these sectors can only be in imploded files). Compressed sectors (only found in compressed - not imploded - files) are compressed with one or more compression algorithms, and have the following structure: -00h: byte CompressionMask : Mask of the compression types applied to this sector. If multiple compression types are used, they are applied in the order listed below, and decompression is performed in the opposite order. This byte counts towards the total sector size, meaning that the sector will be stored uncompressed if the data cannot be compressed by at least two bytes; as well, this byte is encrypted with the sector data, if applicable. The following compression types are defined (for implementations of these algorithms, see StormLib): - 40h: IMA ADPCM mono - 80h: IMA ADPCM stereo - 01h: Huffman encoded - 02h: Deflated (see ZLib) - 08h: Imploded (see PKWare Data Compression Library) - 10h: BZip2 compressed (see BZip2) -01h: byte(SectorSize - 1) SectorData : The compressed data for the sector. - -If the file is stored as a single unit (indicated in the file's Flags), there is effectively only a single sector, which contains the entire file data. - -If the file is encrypted, each sector (after compression/implosion, if applicable) is encrypted with the file's key. The base key for a file is determined by a hash of the file name stripped of the directory (i.e. the key for a file named "directory\file" would be computed as the hash of "file"). If this key is adjusted, as indicated in the file's Flags, the final key is calculated as ((base key + BlockOffset - ArchiveOffset) XOR FileSize) (StormLib incorrectly uses an AND in place of the XOR). Each sector is encrypted using the key + the 0-based index of the sector in the file. The SectorOffsetTable, if present, is encrypted using the key - 1. - -The SectorOffsetTable is omitted when the sizes and offsets of all sectors in the file are calculatable from the FileSize. This can happen in several circumstances. If the file is not compressed/imploded, then the size and offset of all sectors is known, based on the archive's SectorSizeShift. If the file is stored as a single unit compressed/imploded, then the SectorOffsetTable is omitted, as the single file "sector" corresponds to BlockSize and FileSize, as mentioned previously. However, the SectorOffsetTable will be present if the file is compressed/imploded and the file is not stored as a single unit, even if there is only a single sector in the file (the size of the file is less than or equal to the archive's sector size). - -2.7 LISTFILE -The listfile is a very simple extension to the MoPaQ format that contains the file paths of (most) files in the archive. The languages and platforms of the files are not stored in the listfile. The listfile is contained in the file "(listfile)" (default language and platform), and is simply a text file with file paths separated by ';', 0Dh, 0Ah, or some combination of these. The file "(listfile)" may not be listed in the listfile. - -2.8 EXTENDED ATTRIBUTES -The extended attributes are optional file attributes for files in the block table. These attributes were added at times after the MoPaQ format was already finalized, and it is not necessary for every archive to have all (or any) of the extended attributes. If an archive contains a given attribute, there will be an instance of that attribute for every block in the block table, although the attribute will be meaningless if the block is not a file. The order of the attributes for blocks correspond to the order of the blocks in the block table, and are of the same number. The attributes are stored in parallel arrays in the "(attributes)" file (default language and platform), in the archive. The attributes corresponding to this file need not be valid (and logically cannot be). Unlike all the other structures in the MoPaQ format, entries in the extended attributes are NOT guaranteed to be aligned. Also note that in some archives, malicious zeroing of the attributes has been observed, perhaps with the intent of breaking archive viewers. This file is structured as follows: - -00h: int32 Version : Specifies the extended attributes format version. For now, must be 100. -04h: int32 AttributesPresent : Bit mask of the extended attributes present in the archive: - 00000001h: File CRC32s. - 00000002h: File timestamps. - 00000004h: File MD5s. -08h: int32(BlockTableEntries) CRC32s : CRC32s of the (uncompressed) file data for each block in the archive. Omitted if the archive does not have CRC32s. -immediately after CRC32s: FILETIME(BlockTableEntries) Timestamps : Timestamps for each block in the archive. The format is that of the Windows FILETIME structure. Omitted if the archive does not have timestamps. -immediately after Timestamps: MD5(BlockTableEntries) MD5s : MD5s of the (uncompressed) file data for each block in the archive. Omitted if the archive does not have MD5s. - -2.9 WEAK DIGITAL SIGNATURE -The weak digital signature is a digital signature using Microsoft CryptoAPI. It is an implimentation -of the RSASSA-PKCS1-v1_5 digital signature protocol, using the MD5 hashing algorithm and a 512-bit (weak) -RSA key (for more information about this protocol, see the RSA Labs PKCS1 specification). The public key -and exponent are stored in a resource in Storm, the private key is stored in a separate file, whose filename -is passed to MPQAPI (the private key is not stored in MPQAPI). The signature is stored uncompressed, -unencrypted in the file "(signature)" (default language and platform) in the archive. The archive -is hashed from the beginning of the archive (ArchiveOffset in the containing file) to the end of -the archive (the length indicated by ArchiveSize, or calculated in the Burning Crusade MoPaQ format); -the signature file is added to the archive before signing, and the space occupied by the file is considered -to be all binary 0s during signing/verification. This file is structured as follows: - -00h: int32 Unknown : Must be 0. -04h: int32 Unknown : Must be 0. -08h: int512 Signature : The digital signature. Like all other numbers in the MoPaQ format, this is stored -in little-endian order. The structure of this, when decrypted, follows the RSASSA-PKCS1-v1_5 specification; -this format is rather icky to work with (I wrote a program to verify this signature using nothing but an MD5 -function and huge integer functions; it wasn't pleasant), and best left to an encryption library such as Cryto++. - -2.10 STRONG DIGITAL SIGNATURE -The strong digital signature uses a simple proprietary implementation of RSA signing, using the SHA-1 hashing algorithm and a 2048-bit (strong) RSA key. The default public key and exponent are stored in Storm, but other keys may be used as well. The strong digital signature is stored immediately after the archive, in the containing file; the entire archive (ArchiveSize bytes, starting at ArchiveOffset in the containing file) is hashed as a single block. The signature has the following format: - -00h: char(4) Magic : Indicates the presence of a digital signature. Must be "NGIS" ("SIGN" backwards). -04h: int2048 Signature : The digital signature, stored in little-endian format. - -When the Signature field is decrypted with the public key and exponent, and the resulting large integer is stored in little-endian order, it is structured as follows: - -00h: byte Padding : Must be 0Bh. -01h: byte(235) Padding : Must be BBh. -ECh: byte(20) SHA-1 : SHA-1 hash of the archive, in standard SHA-1 byte order. - -3. ALGORITHM SOURCE CODE -All of the sample code here assumes little endian machine byte order, that the short type is 16 bits, that the long type is 32 bits, and that the long long type is 64 bits. Adjustments must be made if these assumptions are not correct on a given platform. All code not credited otherwise was written by myself in the writing of this specification. - -3.1 ENCRYPTION/DECRYPTION -Based on code from StormLib. - -unsigned long dwCryptTable[0x500]; - -// The encryption and hashing functions use a number table in their procedures. This table must be initialized before the functions are called the first time. -void InitializeCryptTable() -{ - unsigned long seed = 0x00100001; - unsigned long index1 = 0; - unsigned long index2 = 0; - int i; - - for (index1 = 0; index1 < 0x100; index1++) - { - for (index2 = index1, i = 0; i < 5; i++, index2 += 0x100) - { - unsigned long temp1, temp2; - - seed = (seed * 125 + 3) % 0x2AAAAB; - temp1 = (seed & 0xFFFF) << 0x10; - - seed = (seed * 125 + 3) % 0x2AAAAB; - temp2 = (seed & 0xFFFF); - - dwCryptTable[index2] = (temp1 | temp2); - } - } -} - -void EncryptData(void *lpbyBuffer, unsigned long dwLength, unsigned long dwKey) -{ - assert(lpbyBuffer); - - unsigned long *lpdwBuffer = (unsigned long *)lpbyBuffer; - unsigned long seed = 0xEEEEEEEE; - unsigned long ch; - - dwLength /= sizeof(unsigned long); - - while(dwLength-- > 0) - { - seed += dwCryptTable[0x400 + (dwKey & 0xFF)]; - ch = *lpdwBuffer ^ (dwKey + seed); - - dwKey = ((~dwKey << 0x15) + 0x11111111) | (dwKey >> 0x0B); - seed = *lpdwBuffer + seed + (seed << 5) + 3; - - *lpdwBuffer++ = ch; - } -} - -void DecryptData(void *lpbyBuffer, unsigned long dwLength, unsigned long dwKey) -{ - assert(lpbyBuffer); - - unsigned long *lpdwBuffer = (unsigned long *)lpbyBuffer; - unsigned long seed = 0xEEEEEEEEL; - unsigned long ch; - - dwLength /= sizeof(unsigned long); - - while(dwLength-- > 0) - { - seed += dwCryptTable[0x400 + (dwKey & 0xFF)]; - ch = *lpdwBuffer ^ (dwKey + seed); - - dwKey = ((~dwKey << 0x15) + 0x11111111L) | (dwKey >> 0x0B); - seed = ch + seed + (seed << 5) + 3; - - *lpdwBuffer++ = ch; - } -} - -3.2 HASHING AND FILE KEY COMPUTATION -These functions may have been derived from StormLib code at some point in the very distant past. It was so long ago that I don't remember for certain. - -// Different types of hashes to make with HashString -#define MPQ_HASH_TABLE_OFFSET 0 -#define MPQ_HASH_NAME_A 1 -#define MPQ_HASH_NAME_B 2 -#define MPQ_HASH_FILE_KEY 3 - -// Based on code from StormLib. -unsigned long HashString(const char *lpszString, unsigned long dwHashType) -{ - assert(lpszString); - assert(dwHashType <= MPQ_HASH_FILE_KEY); - - unsigned long seed1 = 0x7FED7FEDL; - unsigned long seed2 = 0xEEEEEEEEL; - int ch; - - while (*lpszString != 0) - { - ch = toupper(*lpszString++); - - seed1 = dwCryptTable[(dwHashType * 0x100) + ch] ^ (seed1 + seed2); - seed2 = ch + seed1 + seed2 + (seed2 << 5) + 3; - } - return seed1; -} - -#define BLOCK_OFFSET_ADJUSTED_KEY 0x00020000L - -unsigned long ComputeFileKey(const char *lpszFilePath, const BlockTableEntry &blockEntry, unsigned long nArchiveOffset) -{ - assert(lpszFilePath); - - // Find the file name part of the path - const char *lpszFileName = strrchr(lpszFilePath, '\\'); - if (lpszFileName) - lpszFileName++; // Skip the \ - else - lpszFileName = lpszFilePath; - - // Hash the name to get the base key - unsigned long nFileKey = HashString(lpszFileName, MPQ_HASH_FILE_KEY); - - // Offset-adjust the key if necessary - if (blockEntry.Flags & BLOCK_OFFSET_ADJUSTED_KEY) - nFileKey = (nFileKey + blockEntry.BlockOffset) ^ blockEntry.FileSize; - - return nFileKey; -} - -3.3 FINDING FILES - -#define MPQ_HASH_ENTRY_EMPTY 0xFFFFFFFFL -#define MPQ_HASH_ENTRY_DELETED 0xFFFFFFFEL - -bool FindFileInHashTable(const HashTableEntry *lpHashTable, unsigned long nHashTableSize, const char *lpszFilePath, unsigned short nLang, unsigned char nPlatform, unsigned long &iFileHashEntry) -{ - assert(lpHashTable); - assert(nHashTableSize); - assert(lpszFilePath); - - // Find the home entry in the hash table for the file - unsigned long iInitEntry = HashString(lpszFilePath, MPQ_HASH_TABLE_OFFSET) & (nHashTableSize - 1); - - // Is there anything there at all? - if (lpHashTable[iInitEntry].FileBlockIndex == MPQ_HASH_ENTRY_EMPTY) - return false; - - // Compute the hashes to compare the hash table entry against - unsigned long nNameHashA = HashString(lpszFilePath, MPQ_HASH_NAME_A), - nNameHashB = HashString(lpszFilePath, MPQ_HASH_NAME_B), - iCurEntry = iInitEntry; - - // Check each entry in the hash table till a termination point is reached - do - { - if (lpHashTable[iCurEntry].FileBlockIndex != MPQ_HASH_ENTRY_DELETED) - { - if (lpHashTable[iCurEntry].FilePathHashA == nNameHashA - && lpHashTable[iCurEntry].FilePathHashB == nNameHashB - && lpHashTable[iCurEntry].Language == nLang - && lpHashTable[iCurEntry].Platform == nPlatform) - { - iFileHashEntry = iCurEntry; - - return true; - } - } - - iCurEntry = (iCurEntry + 1) & (nHashTableSize - 1); - } while (iCurEntry != iInitEntry && lpHashTable[iCurEntry].FileBlockIndex != MPQ_HASH_ENTRY_EMPTY); - - return false; -} - -3.4 DELETING FILES - -bool DeleteFile(HashTableEntry *lpHashTable, unsigned long nHashTableSize, BlockTableEntry *lpBlockTable, const char *lpszFilePath, unsigned short nLang, unsigned char nPlatform) -{ - assert(lpHashTable); - assert(nHashTableSize); - assert(lpBlockTable); - - // Find the file in the hash table - unsigned long iFileHashEntry; - - if (!FindFileInHashTable(lpHashTable, nHashTableSize, lpszFilePath, nLang, nPlatform, iFileHashEntry)) - return false; - - // Get the block table index before we nuke the hash table entry - unsigned long iFileBlockEntry = lpHashTable[iFileHashEntry].FileBlockIndex; - - // Delete the file's entry in the hash table - memset(&lpHashTable[iFileHashEntry], 0xFF, sizeof(HashTableEntry)); - - // If the next entry is empty, mark this one as empty; otherwise, mark this as deleted. - if (lpHashTable[(iFileHashEntry + 1) & (nHashTableSize - 1)].FileBlockIndex == MPQ_HASH_ENTRY_EMPTY) - lpHashTable[iFileHashEntry].FileBlockIndex = MPQ_HASH_ENTRY_EMPTY; - else - lpHashTable[iFileHashEntry].FileBlockIndex = MPQ_HASH_ENTRY_DELETED; - - // If the block occupies space, mark the block as free space; otherwise, clear the block table entry. - if (lpBlockTable[iFileBlockEntry].BlockSize > 0) - { - lpBlockTable[iFileBlockEntry].FileSize = 0; - lpBlockTable[iFileBlockEntry].Flags = 0; - } - else - memset(&lpBlockTable[iFileBlockEntry], 0, sizeof(BlockTableEntry); - - return true; -} - -3.5 CONVERSION OF FILETIME AND time_t -This code assumes that the base ("zero") date for time_t is 01/01/1970. This is true on Windows, Unix System V systems, and Mac OS X. It is unknown whether this is true on all other platforms. You'll need to research this yourself, if you plan on porting it somewhere else. - -#define EPOCH_OFFSET 116444736000000000ULL // Number of 100 ns units between 01/01/1601 and 01/01/1970 - -bool GetTimeFromFileTime(const FILETIME &fileTime, time_t &time) -{ - // The FILETIME represents a 64-bit integer: the number of 100 ns units since January 1, 1601 - unsigned long long nTime = ((unsigned long long)fileTime.dwHighDateTime << 32) + fileTime.dwLowDateTime; - - if (nTime < EPOCH_OFFSET) - return false; - - nTime -= EPOCH_OFFSET; // Convert the time base from 01/01/1601 to 01/01/1970 - nTime /= 10000000ULL; // Convert 100 ns to sec - - time = (time_t)nTime; - - // Test for overflow (FILETIME is 64 bits, time_t is 32 bits) - if ((nTime - (unsigned long long)time) > 0) - return false; - - return true; -} - -void GetFileTimeFromTime(const time_t &time, FILETIME &fileTime) -{ - unsigned long long nTime = (unsigned long long)time; - - nTime *= 10000000ULL; - nTime += EPOCH_OFFSET; - - fileTime.dwLowDateTime = (DWORD)nTime; - fileTime.dwHighDateTime = (DWORD)(nTime >> 32); -} - -3.6 FORMING A 64-BIT LARGE ARCHIVE OFFSET FROM 32-BIT AND 16-BIT COMPONENTS -unsigned long long MakeLargeArchiveOffset(unsigned long nOffsetLow, unsigned short nOffsetHigh) -{ - return ((unsigned long long)nOffsetHigh << 32) + (unsigned long long)nOffsetLow; -} - -4. REVISION HISTORY -1.0 - - Updated to include most of the changes found in the Burning Crusade Friends and Family beta - -0.91. - - Updated several structure member descriptions - - Listed the full set of characters that can separate list file entries - - Noted that (attributes), (listfile), and (signature) use the default language and platform codes - - Redid part of the file data specs to clarify the format of sectors - - Enhanced descriptions of the different kinds of block table entries - - Added ComputeFileKey, FindFileInHashTable, and DeleteFile source \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-deDE.txt b/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-deDE.txt deleted file mode 100644 index cac6671..0000000 --- a/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-deDE.txt +++ /dev/null @@ -1 +0,0 @@ -UCMXF6EJY352EFH4XFRXCFH2XC9MQRZK \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-enGB.txt b/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-enGB.txt deleted file mode 100644 index 2bc9c83..0000000 --- a/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-enGB.txt +++ /dev/null @@ -1 +0,0 @@ -MMKVHY48RP7WXP4GHYBQ7SL9J9UNPHBP \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-enSG.txt b/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-enSG.txt deleted file mode 100644 index e6f1ec2..0000000 --- a/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-enSG.txt +++ /dev/null @@ -1 +0,0 @@ -8MXLWHQ7VGGLTZ9MQZQSFDCLJYET3CPP \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-enUS.txt b/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-enUS.txt deleted file mode 100644 index 8d73e61..0000000 --- a/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-enUS.txt +++ /dev/null @@ -1 +0,0 @@ -EJ2R5TM6XFE2GUNG5QDGHKQ9UAKPWZSZ \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-esES.txt b/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-esES.txt deleted file mode 100644 index 6b1b0a1..0000000 --- a/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-esES.txt +++ /dev/null @@ -1 +0,0 @@ -PBGFBE42Z6LNK65UGJQ3WZVMCLP4HQQT \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-esMX.txt b/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-esMX.txt deleted file mode 100644 index 504759e..0000000 --- a/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-esMX.txt +++ /dev/null @@ -1 +0,0 @@ -X7SEJJS9TSGCW5P28EBSC47AJPEY8VU2 \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-frFR.txt b/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-frFR.txt deleted file mode 100644 index bb35a2b..0000000 --- a/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-frFR.txt +++ /dev/null @@ -1 +0,0 @@ -5KVBQA8VYE6XRY3DLGC5ZDE4XS4P7YA2 \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-itIT.txt b/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-itIT.txt deleted file mode 100644 index a62031d..0000000 --- a/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-itIT.txt +++ /dev/null @@ -1 +0,0 @@ -478JD2K56EVNVVY4XX8TDWYT5B8KB254 \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-koKR.txt b/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-koKR.txt deleted file mode 100644 index 296ffcc..0000000 --- a/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-koKR.txt +++ /dev/null @@ -1 +0,0 @@ -8TS4VNFQRZTN6YWHE9CHVDH9NVWD474A \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-plPL.txt b/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-plPL.txt deleted file mode 100644 index a92563c..0000000 --- a/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-plPL.txt +++ /dev/null @@ -1 +0,0 @@ -LJ52Z32DF4LZ4ZJJXVKK3AZQA6GABLJB \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-ptBR.txt b/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-ptBR.txt deleted file mode 100644 index e6e5c35..0000000 --- a/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-ptBR.txt +++ /dev/null @@ -1 +0,0 @@ -K6BDHY2ECUE2545YKNLBJPVYWHE7XYAG \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-zhTW.txt b/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-zhTW.txt deleted file mode 100644 index 138a544..0000000 --- a/app/jni/src/libultraship/extern/StormLib/doc/d3-authenticationcode/d3-authenticationcode-zhTW.txt +++ /dev/null @@ -1 +0,0 @@ -6VWCQTN8V3ZZMRUCZXV8A8CGUX2TAA8H \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/doc/hots-authenticationcode/hots-authenticationcode-bgdl.txt b/app/jni/src/libultraship/extern/StormLib/doc/hots-authenticationcode/hots-authenticationcode-bgdl.txt deleted file mode 100644 index 6dfe0ee..0000000 --- a/app/jni/src/libultraship/extern/StormLib/doc/hots-authenticationcode/hots-authenticationcode-bgdl.txt +++ /dev/null @@ -1 +0,0 @@ -S48B6CDTN5XEQAKQDJNDLJBJ73FDFM3U \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-deDE.txt b/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-deDE.txt deleted file mode 100644 index 029d733..0000000 --- a/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-deDE.txt +++ /dev/null @@ -1 +0,0 @@ -Y45MD3CAK4KXSSXHYD9VY64Z8EKJ4XFX \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-enGB.txt b/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-enGB.txt deleted file mode 100644 index 7f66f8b..0000000 --- a/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-enGB.txt +++ /dev/null @@ -1 +0,0 @@ -G8MN8UDG6NA2ANGY6A3DNY82HRGF29ZH \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-enUS.txt b/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-enUS.txt deleted file mode 100644 index 0a4f5b8..0000000 --- a/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-enUS.txt +++ /dev/null @@ -1 +0,0 @@ -3DH5RE5NVM5GTFD85LXGWT6FK859ETR5 \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-esES.txt b/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-esES.txt deleted file mode 100644 index fba8c8d..0000000 --- a/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-esES.txt +++ /dev/null @@ -1 +0,0 @@ -8WLKUAXE94PFQU4Y249PAZ24N4R4XKTQ \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-esMX.txt b/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-esMX.txt deleted file mode 100644 index bb020c6..0000000 --- a/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-esMX.txt +++ /dev/null @@ -1 +0,0 @@ -A34DXX3VHGGXSQBRFE5UFFDXMF9G4G54 \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-frFR.txt b/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-frFR.txt deleted file mode 100644 index 37bcc4a..0000000 --- a/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-frFR.txt +++ /dev/null @@ -1 +0,0 @@ -ZG7J9K938HJEFWPQUA768MA2PFER6EAJ \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-itIT.txt b/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-itIT.txt deleted file mode 100644 index a665f69..0000000 --- a/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-itIT.txt +++ /dev/null @@ -1 +0,0 @@ -NE7CUNNNTVAPXV7E3G2BSVBWGVMW8BL2 \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-koKR.txt b/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-koKR.txt deleted file mode 100644 index e6346df..0000000 --- a/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-koKR.txt +++ /dev/null @@ -1 +0,0 @@ -3V9E2FTMBM9QQWK7U6MAMWAZWQDB838F \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-plPL.txt b/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-plPL.txt deleted file mode 100644 index 564efc4..0000000 --- a/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-plPL.txt +++ /dev/null @@ -1 +0,0 @@ -2NSFB8MELULJ83U6YHA3UP6K4MQD48L6 \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-ptBR.txt b/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-ptBR.txt deleted file mode 100644 index e8f8172..0000000 --- a/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-ptBR.txt +++ /dev/null @@ -1 +0,0 @@ -QA2TZ9EWZ4CUU8BMB5WXCTY65F9CSW4E \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-ruRU.txt b/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-ruRU.txt deleted file mode 100644 index 1b93b5b..0000000 --- a/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-ruRU.txt +++ /dev/null @@ -1 +0,0 @@ -VHB378W64BAT9SH7D68VV9NLQDK9YEGT \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-zhTW.txt b/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-zhTW.txt deleted file mode 100644 index 409a8c1..0000000 --- a/app/jni/src/libultraship/extern/StormLib/doc/sc2-authenticationcode/sc2-authenticationcode-zhTW.txt +++ /dev/null @@ -1 +0,0 @@ -U3NFQJV4M6GC7KBN9XQJ3BRDN3PLD9NE \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/make-msvc.bat b/app/jni/src/libultraship/extern/StormLib/make-msvc.bat deleted file mode 100644 index 80d99fe..0000000 --- a/app/jni/src/libultraship/extern/StormLib/make-msvc.bat +++ /dev/null @@ -1,85 +0,0 @@ -:: Build file for Visual Studio 2008 and 2017 -@echo off - -:: Save the values of INCLUDE, LIB and PATH -set SAVE_INCLUDE=%INCLUDE% -set SAVE_LIB=%LIB% -set SAVE_PATH=%PATH% -set LIB_NAME=StormLib - -:: Determine where the program files are, both for 64-bit and 32-bit Windows -if exist "%ProgramFiles%" set PROGRAM_FILES_DIR=%ProgramFiles% -if exist "%ProgramFiles(x86)%" set PROGRAM_FILES_DIR=%ProgramFiles(x86)% - -:: Determine the installed version of Visual Studio (Prioritize Enterprise over Professional) -if exist "%PROGRAM_FILES_DIR%\Microsoft Visual Studio 9.0\VC\vcvarsall.bat" set VCVARS_2008=%PROGRAM_FILES_DIR%\Microsoft Visual Studio 9.0\VC\vcvarsall.bat -if exist "%PROGRAM_FILES_DIR%\Microsoft Visual Studio\2017\Community\VC\Auxiliary\Build\vcvarsall.bat" set VCVARS_2017=%PROGRAM_FILES_DIR%\Microsoft Visual Studio\2017\Community\VC\Auxiliary\Build\vcvarsall.bat -if exist "%PROGRAM_FILES_DIR%\Microsoft Visual Studio\2017\Professional\VC\Auxiliary\Build\vcvarsall.bat" set VCVARS_2017=%PROGRAM_FILES_DIR%\Microsoft Visual Studio\2017\Professional\VC\Auxiliary\Build\vcvarsall.bat -if exist "%PROGRAM_FILES_DIR%\Microsoft Visual Studio\2017\Enterprise\VC\Auxiliary\Build\vcvarsall.bat" set VCVARS_2017=%PROGRAM_FILES_DIR%\Microsoft Visual Studio\2017\Enterprise\VC\Auxiliary\Build\vcvarsall.bat -if exist "%PROGRAM_FILES_DIR%\Microsoft Visual Studio\2019\Community\VC\Auxiliary\Build\vcvarsall.bat" set VCVARS_2019=%PROGRAM_FILES_DIR%\Microsoft Visual Studio\2019\Community\VC\Auxiliary\Build\vcvarsall.bat -if exist "%PROGRAM_FILES_DIR%\Microsoft Visual Studio\2019\Professional\VC\Auxiliary\Build\vcvarsall.bat" set VCVARS_2019=%PROGRAM_FILES_DIR%\Microsoft Visual Studio\2019\Professional\VC\Auxiliary\Build\vcvarsall.bat -if exist "%PROGRAM_FILES_DIR%\Microsoft Visual Studio\2019\Enterprise\VC\Auxiliary\Build\vcvarsall.bat" set VCVARS_2019=%PROGRAM_FILES_DIR%\Microsoft Visual Studio\2019\Enterprise\VC\Auxiliary\Build\vcvarsall.bat - -:: Build all libraries using Visual Studio 2008 and 2019 -if not "x%VCVARS_2008%" == "x" call :BuildLibs "%VCVARS_2008%" x86 %LIB_NAME%_vs08.sln \vs2008 -if not "x%VCVARS_2008%" == "x" call :BuildLibs "%VCVARS_2008%" x64 %LIB_NAME%_vs08.sln \vs2008 -if not "x%VCVARS_2019%" == "x" call :BuildLibs "%VCVARS_2019%" x86 %LIB_NAME%_vs19.sln -if not "x%VCVARS_2019%" == "x" call :BuildLibs "%VCVARS_2019%" x64 %LIB_NAME%_vs19.sln -goto:eof - -::----------------------------------------------------------------------------- -:: Build all 8 configurations of the library -:: -:: Parameters: -:: -:: %1 Full path to the VCVARS.BAT file -:: %2 Target build platform (x86 or x64) -:: %3 Plain name of the .sln solution file ("StormLib_vs19.sln") -:: %4 Subdirectory for the target folder of the library ("\vs2008" or "") -:: - -:BuildLibs -if not exist %1 goto:eof -call %1 %2 -if "%2" == "x86" set SLN_TRG=Win32 -if "%2" == "x86" set LIB_TRG=lib32%4 -if "%2" == "x64" set SLN_TRG=x64 -if "%2" == "x64" set LIB_TRG=lib64%4 - -call :BuildAndCopyLib %3 %SLN_TRG% %LIB_TRG% DebugAD -call :BuildAndCopyLib %3 %SLN_TRG% %LIB_TRG% DebugAS -call :BuildAndCopyLib %3 %SLN_TRG% %LIB_TRG% DebugUD -call :BuildAndCopyLib %3 %SLN_TRG% %LIB_TRG% DebugUS -call :BuildAndCopyLib %3 %SLN_TRG% %LIB_TRG% ReleaseAD -call :BuildAndCopyLib %3 %SLN_TRG% %LIB_TRG% ReleaseAS -call :BuildAndCopyLib %3 %SLN_TRG% %LIB_TRG% ReleaseUD -call :BuildAndCopyLib %3 %SLN_TRG% %LIB_TRG% ReleaseUS - -:: Restore environment variables to the old level -set INCLUDE=%SAVE_INCLUDE% -set LIB=%SAVE_LIB% -set PATH=%SAVE_PATH% -set VSINSTALLDIR= -set VCINSTALLDIR= -set DevEnvDir= -goto:eof - -::----------------------------------------------------------------------------- -:: Build and update a particular subvariant of the library -:: -:: Parameters: -:: -:: %1 Plain name of the .sln solution file ("StormLib_vs19.sln") -:: %2 Target build platform ("Win32" or "x64") -:: %3 Target directory for the library ("lib32", "lib32\vs2008", "lib64" or "lib64\vs2008") -:: %4 Subvariant of the library ("DebugAD", "ReleaseUS", ...) -:: - -:BuildAndCopyLib -if not exist %1 goto:eof -devenv.com %1 /project "%LIB_NAME%" /rebuild "%4|%2" -if not exist ..\aaa goto:eof -xcopy.exe /Y /D .\src\StormLib.h ..\aaa\inc >nul -xcopy.exe /Y /D .\src\StormPort.h ..\aaa\inc >nul -xcopy.exe /Y /D .\bin\StormLib\%2\%4\*.lib ..\aaa\%3 >nul -goto:eof diff --git a/app/jni/src/libultraship/extern/StormLib/make.bat b/app/jni/src/libultraship/extern/StormLib/make.bat deleted file mode 100644 index 7b29207..0000000 --- a/app/jni/src/libultraship/extern/StormLib/make.bat +++ /dev/null @@ -1,46 +0,0 @@ -@echo off -if not "x%WDKDIR%" == "x" goto SELECT_LIB -echo The WDKDIR environment variable is not set -echo Set this variable to your WDK directory (without ending backslash) -echo Example: set WDKDIR C:\WinDDK\6001 -pause -goto:eof - -:SELECT_LIB -set PROJECT_DIR=%~dp0 -set LIBRARY_NAME=StormLibWDK - -:PREPARE_SOURCES -echo Preparing sources ... -copy .\src\wdk\sources-cpp.cpp . >nul -copy .\src\wdk\sources-wdk-* . >nul -echo. - -:BUILD_LIB_32 -echo Building %LIBRARY_NAME%.lib (32-bit) ... -set DDKBUILDENV= -call %WDKDIR%\bin\setenv.bat %WDKDIR%\ fre w2k -cd %PROJECT_DIR% -build.exe -czgw -del buildfre_w2k_x86.log -echo. - -:BUILD_LIB_64 -echo Building %LIBRARY_NAME%.lib (64-bit) ... -set DDKBUILDENV= -call %WDKDIR%\bin\setenv.bat %WDKDIR%\ fre x64 WLH -cd %PROJECT_DIR% -build.exe -czgw -del buildfre_wlh_amd64.log -echo. - -:COPY_LIBS -xcopy /Y /D .\src\StormLib.h ..\aaa\inc >nul -xcopy /Y /D .\src\StormPort.h ..\aaa\inc >nul -xcopy /Y /D .\objfre_w2k_x86\i386\%LIBRARY_NAME%.lib ..\aaa\lib32\%LIBRARY_NAME%.lib >nul -xcopy /Y /D .\objfre_wlh_amd64\amd64\%LIBRARY_NAME%.lib ..\aaa\lib64\%LIBRARY_NAME%.lib >nul - -:CLEANUP -if exist sources-cpp.cpp del sources-cpp.cpp -if exist sources-wdk-* del sources-wdk-* -if exist build.bat del build.bat diff --git a/app/jni/src/libultraship/extern/StormLib/sources b/app/jni/src/libultraship/extern/StormLib/sources deleted file mode 100644 index eaa49ad..0000000 --- a/app/jni/src/libultraship/extern/StormLib/sources +++ /dev/null @@ -1,14 +0,0 @@ -TARGETNAME=StormLibWDK -TARGETTYPE=LIBRARY -USE_MSVCRT=1 - -C_DEFINES=$(C_DEFINES) -DUNICODE -D_UNICODE -DWDK_BUILD - -SOURCES=sources-cpp.cpp \ - sources-wdk-bzip2.c \ - sources-wdk-ltc.c \ - sources-wdk-lzma.c \ - sources-wdk-misc.c \ - sources-wdk-tomcrypt.c \ - sources-wdk-tommath.c \ - sources-wdk-zlib.c diff --git a/app/jni/src/libultraship/extern/StormLib/src/DllMain.c b/app/jni/src/libultraship/extern/StormLib/src/DllMain.c deleted file mode 100644 index 98eb003..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/DllMain.c +++ /dev/null @@ -1,24 +0,0 @@ -/*****************************************************************************/ -/* DllMain.c Copyright (c) Ladislav Zezula 2006 */ -/*---------------------------------------------------------------------------*/ -/* Description: DllMain for the StormLib.dll library */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 23.11.06 1.00 Lad The first version of DllMain.c */ -/*****************************************************************************/ - -#define WIN32_LEAN_AND_MEAN -#include - -//----------------------------------------------------------------------------- -// DllMain - -BOOL WINAPI DllMain(HINSTANCE hInst, DWORD dwReason, LPVOID lpReserved) -{ - UNREFERENCED_PARAMETER(hInst); - UNREFERENCED_PARAMETER(dwReason); - UNREFERENCED_PARAMETER(lpReserved); - - return TRUE; -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/DllMain.def b/app/jni/src/libultraship/extern/StormLib/src/DllMain.def deleted file mode 100644 index bce2877..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/DllMain.def +++ /dev/null @@ -1,79 +0,0 @@ -; -; Export file for Windows -; Copyright (c) 2007-2010 Ladislav Zezula -; ladik@zezula.net -; - -LIBRARY StormLib.dll - -EXPORTS - - SFileSetLocale - SFileGetLocale - - SFileOpenArchive - SFileCreateArchive - SFileCreateArchive2 - SFileFlushArchive - SFileCloseArchive - - SFileAddListFile - - SFileSetCompactCallback - SFileCompactArchive - - SFileGetMaxFileCount - SFileSetMaxFileCount - - SFileGetAttributes - SFileSetAttributes - SFileUpdateFileAttributes - - SFileOpenPatchArchive - SFileIsPatchedArchive - - SFileOpenFileEx - SFileGetFileSize - SFileSetFilePointer - SFileReadFile - SFileCloseFile - - SFileHasFile - SFileGetFileName - SFileGetFileInfo - - SFileExtractFile - - SFileVerifyFile - SFileVerifyRawData - SFileVerifyArchive - - SFileFindFirstFile - SFileFindNextFile - SFileFindClose - - SListFileFindFirstFile - SListFileFindNextFile - SListFileFindClose - - SFileEnumLocales - - SFileCreateFile - SFileWriteFile - SFileFinishFile - SFileAddFileEx - SFileAddFile - SFileAddWave - SFileRemoveFile - SFileRenameFile - SFileSetFileLocale - SFileSetDataCompression - SFileSetAddFileCallback - - SCompImplode - SCompExplode - SCompCompress - SCompDecompress - - GetLastError=Kernel32.GetLastError - SetLastError=Kernel32.SetLastError diff --git a/app/jni/src/libultraship/extern/StormLib/src/DllMain.rc b/app/jni/src/libultraship/extern/StormLib/src/DllMain.rc deleted file mode 100644 index 27f43e2..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/DllMain.rc +++ /dev/null @@ -1,114 +0,0 @@ -// Microsoft Visual C++ generated resource script. -// -#include "resource.h" - -#define APSTUDIO_READONLY_SYMBOLS -///////////////////////////////////////////////////////////////////////////// -// -// Generated from the TEXTINCLUDE 2 resource. -// -#include "afxres.h" - -///////////////////////////////////////////////////////////////////////////// -#undef APSTUDIO_READONLY_SYMBOLS - -///////////////////////////////////////////////////////////////////////////// -// Neutral resources - -#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_NEU) -#ifdef _WIN32 -LANGUAGE LANG_NEUTRAL, SUBLANG_NEUTRAL -#pragma code_page(1250) -#endif //_WIN32 - -///////////////////////////////////////////////////////////////////////////// -// -// Version -// - -VS_VERSION_INFO VERSIONINFO - FILEVERSION 9,22,0,3 - PRODUCTVERSION 9,22,0,3 - FILEFLAGSMASK 0x17L -#ifdef _DEBUG - FILEFLAGS 0x1L -#else - FILEFLAGS 0x0L -#endif - FILEOS 0x4L - FILETYPE 0x0L - FILESUBTYPE 0x0L -BEGIN - BLOCK "StringFileInfo" - BEGIN - BLOCK "040504b0" - BEGIN - VALUE "Comments", "http://www.zezula.net/mpq.html" - VALUE "FileDescription", "StormLib library for reading Blizzard MPQ archives" - VALUE "FileVersion", "9, 22, 0, 3\0" - VALUE "InternalName", "StormLib" - VALUE "LegalCopyright", "Copyright (c) 2014 - 2020 Ladislav Zezula" - VALUE "OriginalFilename", "StormLib.dll" - VALUE "ProductName", "StormLib" - VALUE "ProductVersion", "9, 22, 0, 3\0" - END - END - BLOCK "VarFileInfo" - BEGIN - VALUE "Translation", 0x405, 1200 - END -END - -#endif // Neutral resources -///////////////////////////////////////////////////////////////////////////// - - -///////////////////////////////////////////////////////////////////////////// -// Czech resources - -#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_CSY) -#ifdef _WIN32 -LANGUAGE LANG_CZECH, SUBLANG_DEFAULT -#pragma code_page(1250) -#endif //_WIN32 - -#ifdef APSTUDIO_INVOKED -///////////////////////////////////////////////////////////////////////////// -// -// TEXTINCLUDE -// - -2 TEXTINCLUDE -BEGIN - "#include ""afxres.h""\r\n" - "\0" -END - -3 TEXTINCLUDE -BEGIN - "\r\n" - "\0" -END - -1 TEXTINCLUDE -BEGIN - "resource.h\0" -END - -#endif // APSTUDIO_INVOKED - -#endif // Czech resources -///////////////////////////////////////////////////////////////////////////// - - - -#ifndef APSTUDIO_INVOKED -///////////////////////////////////////////////////////////////////////////// -// -// Generated from the TEXTINCLUDE 3 resource. -// - - -///////////////////////////////////////////////////////////////////////////// -#endif // not APSTUDIO_INVOKED - diff --git a/app/jni/src/libultraship/extern/StormLib/src/FileStream.cpp b/app/jni/src/libultraship/extern/StormLib/src/FileStream.cpp deleted file mode 100644 index c431cb6..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/FileStream.cpp +++ /dev/null @@ -1,2928 +0,0 @@ -/*****************************************************************************/ -/* FileStream.cpp Copyright (c) Ladislav Zezula 2010 */ -/*---------------------------------------------------------------------------*/ -/* File stream support for StormLib */ -/* */ -/* Windows support: Written by Ladislav Zezula */ -/* Mac support: Written by Sam Wilkins */ -/* Linux support: Written by Sam Wilkins and Ivan Komissarov */ -/* Big-endian: Written & debugged by Sam Wilkins */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 11.06.10 1.00 Lad Derived from StormPortMac.cpp and StormPortLinux.cpp */ -/*****************************************************************************/ - -#define __STORMLIB_SELF__ -#include "StormLib.h" -#include "StormCommon.h" -#include "FileStream.h" - -#ifdef _MSC_VER -#pragma comment(lib, "wininet.lib") // Internet functions for HTTP stream -#pragma warning(disable: 4800) // 'BOOL' : forcing value to bool 'true' or 'false' (performance warning) -#endif - -//----------------------------------------------------------------------------- -// Local defines - -#ifndef INVALID_HANDLE_VALUE -#define INVALID_HANDLE_VALUE ((HANDLE)-1) -#endif - -//----------------------------------------------------------------------------- -// Local functions - platform-specific functions - -#ifndef STORMLIB_WINDOWS - -#ifndef STORMLIB_WIIU -static thread_local DWORD dwLastError = ERROR_SUCCESS; -#else -static DWORD dwLastError = ERROR_SUCCESS; -#endif - -DWORD GetLastError() -{ - return dwLastError; -} - -void SetLastError(DWORD dwErrCode) -{ - dwLastError = dwErrCode; -} -#endif - -static DWORD StringToInt(const char * szString) -{ - DWORD dwValue = 0; - - while('0' <= szString[0] && szString[0] <= '9') - { - dwValue = (dwValue * 10) + (szString[0] - '0'); - szString++; - } - - return dwValue; -} - -static void CreateNameWithSuffix(LPTSTR szBuffer, size_t cchMaxChars, LPCTSTR szName, unsigned int nValue) -{ - LPTSTR szBufferEnd = szBuffer + cchMaxChars - 1; - - // Copy the name - while(szBuffer < szBufferEnd && szName[0] != 0) - *szBuffer++ = *szName++; - - // Append "." - if(szBuffer < szBufferEnd) - *szBuffer++ = '.'; - - // Append the number - IntToString(szBuffer, szBufferEnd - szBuffer + 1, nValue); -} - -//----------------------------------------------------------------------------- -// Dummy init function - -static void BaseNone_Init(TFileStream *) -{ - // Nothing here -} - -//----------------------------------------------------------------------------- -// Local functions - base file support - -static bool BaseFile_Create(TFileStream * pStream) -{ -#ifdef STORMLIB_WINDOWS - { - DWORD dwWriteShare = (pStream->dwFlags & STREAM_FLAG_WRITE_SHARE) ? FILE_SHARE_WRITE : 0; - - pStream->Base.File.hFile = CreateFile(pStream->szFileName, - GENERIC_READ | GENERIC_WRITE, - dwWriteShare | FILE_SHARE_READ, - NULL, - CREATE_ALWAYS, - 0, - NULL); - if(pStream->Base.File.hFile == INVALID_HANDLE_VALUE) - return false; - } -#endif - -#if defined(STORMLIB_MAC) || defined(STORMLIB_LINUX) - { - intptr_t handle; - - handle = open(pStream->szFileName, O_RDWR | O_CREAT | O_TRUNC | O_LARGEFILE, S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH); - if(handle == -1) - { - pStream->Base.File.hFile = INVALID_HANDLE_VALUE; - dwLastError = errno; - return false; - } - - pStream->Base.File.hFile = (HANDLE)handle; - } -#endif - - // Reset the file size and position - pStream->Base.File.FileSize = 0; - pStream->Base.File.FilePos = 0; - return true; -} - -static bool BaseFile_Open(TFileStream * pStream, const TCHAR * szFileName, DWORD dwStreamFlags) -{ -#ifdef STORMLIB_WINDOWS - { - ULARGE_INTEGER FileSize; - DWORD dwWriteAccess = (dwStreamFlags & STREAM_FLAG_READ_ONLY) ? 0 : FILE_WRITE_DATA | FILE_APPEND_DATA | FILE_WRITE_ATTRIBUTES; - DWORD dwWriteShare = (dwStreamFlags & STREAM_FLAG_WRITE_SHARE) ? FILE_SHARE_WRITE : 0; - - // Open the file - pStream->Base.File.hFile = CreateFile(szFileName, - FILE_READ_DATA | FILE_READ_ATTRIBUTES | dwWriteAccess, - FILE_SHARE_READ | dwWriteShare, - NULL, - OPEN_EXISTING, - 0, - NULL); - if(pStream->Base.File.hFile == INVALID_HANDLE_VALUE) - return false; - - // Query the file size - FileSize.LowPart = GetFileSize(pStream->Base.File.hFile, &FileSize.HighPart); - pStream->Base.File.FileSize = FileSize.QuadPart; - - // Query last write time - GetFileTime(pStream->Base.File.hFile, NULL, NULL, (LPFILETIME)&pStream->Base.File.FileTime); - } -#endif - -#if defined(STORMLIB_MAC) || defined(STORMLIB_LINUX) - { - struct stat64 fileinfo; - int oflag = (dwStreamFlags & STREAM_FLAG_READ_ONLY) ? O_RDONLY : O_RDWR; - intptr_t handle; - - // Open the file - handle = open(szFileName, oflag | O_LARGEFILE); - if(handle == -1) - { - pStream->Base.File.hFile = INVALID_HANDLE_VALUE; - dwLastError = errno; - return false; - } - - // Get the file size - if(fstat64(handle, &fileinfo) == -1) - { - pStream->Base.File.hFile = INVALID_HANDLE_VALUE; - dwLastError = errno; - close(handle); - return false; - } - - // time_t is number of seconds since 1.1.1970, UTC. - // 1 second = 10000000 (decimal) in FILETIME - // Set the start to 1.1.1970 00:00:00 - pStream->Base.File.FileTime = 0x019DB1DED53E8000ULL + (10000000 * fileinfo.st_mtime); - pStream->Base.File.FileSize = (ULONGLONG)fileinfo.st_size; - pStream->Base.File.hFile = (HANDLE)handle; - } -#endif - - // Reset the file position - pStream->Base.File.FilePos = 0; - return true; -} - -static bool BaseFile_Read( - TFileStream * pStream, // Pointer to an open stream - ULONGLONG * pByteOffset, // Pointer to file byte offset. If NULL, it reads from the current position - void * pvBuffer, // Pointer to data to be read - DWORD dwBytesToRead) // Number of bytes to read from the file -{ - ULONGLONG ByteOffset = (pByteOffset != NULL) ? *pByteOffset : pStream->Base.File.FilePos; - DWORD dwBytesRead = 0; // Must be set by platform-specific code - -#ifdef STORMLIB_WINDOWS - { - // Note: StormLib no longer supports Windows 9x. - // Thus, we can use the OVERLAPPED structure to specify - // file offset to read from file. This allows us to skip - // one system call to SetFilePointer - - // Update the byte offset - pStream->Base.File.FilePos = ByteOffset; - - // Read the data - if(dwBytesToRead != 0) - { - OVERLAPPED Overlapped; - - Overlapped.OffsetHigh = (DWORD)(ByteOffset >> 32); - Overlapped.Offset = (DWORD)ByteOffset; - Overlapped.hEvent = NULL; - if(!ReadFile(pStream->Base.File.hFile, pvBuffer, dwBytesToRead, &dwBytesRead, &Overlapped)) - return false; - } - } -#endif - -#if defined(STORMLIB_MAC) || defined(STORMLIB_LINUX) - { - ssize_t bytes_read; - - // If the byte offset is different from the current file position, - // we have to update the file position xxx - if(ByteOffset != pStream->Base.File.FilePos) - { - lseek64((intptr_t)pStream->Base.File.hFile, (off64_t)(ByteOffset), SEEK_SET); - pStream->Base.File.FilePos = ByteOffset; - } - - // Perform the read operation - if(dwBytesToRead != 0) - { - bytes_read = read((intptr_t)pStream->Base.File.hFile, pvBuffer, (size_t)dwBytesToRead); - if(bytes_read == -1) - { - dwLastError = errno; - return false; - } - - dwBytesRead = (DWORD)(size_t)bytes_read; - } - } -#endif - - // Increment the current file position by number of bytes read - // If the number of bytes read doesn't match to required amount, return false - pStream->Base.File.FilePos = ByteOffset + dwBytesRead; - if(dwBytesRead != dwBytesToRead) - SetLastError(ERROR_HANDLE_EOF); - return (dwBytesRead == dwBytesToRead); -} - -/** - * \a pStream Pointer to an open stream - * \a pByteOffset Pointer to file byte offset. If NULL, writes to current position - * \a pvBuffer Pointer to data to be written - * \a dwBytesToWrite Number of bytes to write to the file - */ - -static bool BaseFile_Write(TFileStream * pStream, ULONGLONG * pByteOffset, const void * pvBuffer, DWORD dwBytesToWrite) -{ - ULONGLONG ByteOffset = (pByteOffset != NULL) ? *pByteOffset : pStream->Base.File.FilePos; - DWORD dwBytesWritten = 0; // Must be set by platform-specific code - -#ifdef STORMLIB_WINDOWS - { - // Note: StormLib no longer supports Windows 9x. - // Thus, we can use the OVERLAPPED structure to specify - // file offset to read from file. This allows us to skip - // one system call to SetFilePointer - - // Update the byte offset - pStream->Base.File.FilePos = ByteOffset; - - // Read the data - if(dwBytesToWrite != 0) - { - OVERLAPPED Overlapped; - - Overlapped.OffsetHigh = (DWORD)(ByteOffset >> 32); - Overlapped.Offset = (DWORD)ByteOffset; - Overlapped.hEvent = NULL; - if(!WriteFile(pStream->Base.File.hFile, pvBuffer, dwBytesToWrite, &dwBytesWritten, &Overlapped)) - return false; - } - } -#endif - -#if defined(STORMLIB_MAC) || defined(STORMLIB_LINUX) - { - ssize_t bytes_written; - - // If the byte offset is different from the current file position, - // we have to update the file position - if(ByteOffset != pStream->Base.File.FilePos) - { - lseek64((intptr_t)pStream->Base.File.hFile, (off64_t)(ByteOffset), SEEK_SET); - pStream->Base.File.FilePos = ByteOffset; - } - - // Perform the read operation - bytes_written = write((intptr_t)pStream->Base.File.hFile, pvBuffer, (size_t)dwBytesToWrite); - if(bytes_written == -1) - { - dwLastError = errno; - return false; - } - - dwBytesWritten = (DWORD)(size_t)bytes_written; - } -#endif - - // Increment the current file position by number of bytes read - pStream->Base.File.FilePos = ByteOffset + dwBytesWritten; - - // Also modify the file size, if needed - if(pStream->Base.File.FilePos > pStream->Base.File.FileSize) - pStream->Base.File.FileSize = pStream->Base.File.FilePos; - - if(dwBytesWritten != dwBytesToWrite) - SetLastError(ERROR_DISK_FULL); - return (dwBytesWritten == dwBytesToWrite); -} - -/** - * \a pStream Pointer to an open stream - * \a NewFileSize New size of the file - */ -static bool BaseFile_Resize(TFileStream * pStream, ULONGLONG NewFileSize) -{ -#ifdef STORMLIB_WINDOWS - { - LONG FileSizeHi = (LONG)(NewFileSize >> 32); - LONG FileSizeLo; - DWORD dwNewPos; - bool bResult; - - // Set the position at the new file size - dwNewPos = SetFilePointer(pStream->Base.File.hFile, (LONG)NewFileSize, &FileSizeHi, FILE_BEGIN); - if(dwNewPos == INVALID_SET_FILE_POINTER && GetLastError() != ERROR_SUCCESS) - return false; - - // Set the current file pointer as the end of the file - bResult = (bool)SetEndOfFile(pStream->Base.File.hFile); - if(bResult) - pStream->Base.File.FileSize = NewFileSize; - - // Restore the file position - FileSizeHi = (LONG)(pStream->Base.File.FilePos >> 32); - FileSizeLo = (LONG)(pStream->Base.File.FilePos); - SetFilePointer(pStream->Base.File.hFile, FileSizeLo, &FileSizeHi, FILE_BEGIN); - return bResult; - } -#endif - -#if defined(STORMLIB_MAC) || defined(STORMLIB_LINUX) - { - if(ftruncate64((intptr_t)pStream->Base.File.hFile, (off64_t)NewFileSize) == -1) - { - dwLastError = errno; - return false; - } - - pStream->Base.File.FileSize = NewFileSize; - return true; - } -#endif -} - -// Gives the current file size -static bool BaseFile_GetSize(TFileStream * pStream, ULONGLONG * pFileSize) -{ - // Note: Used by all thre base providers. - // Requires the TBaseData union to have the same layout for all three base providers - *pFileSize = pStream->Base.File.FileSize; - return true; -} - -// Gives the current file position -static bool BaseFile_GetPos(TFileStream * pStream, ULONGLONG * pByteOffset) -{ - // Note: Used by all thre base providers. - // Requires the TBaseData union to have the same layout for all three base providers - *pByteOffset = pStream->Base.File.FilePos; - return true; -} - -// Renames the file pointed by pStream so that it contains data from pNewStream -static bool BaseFile_Replace(TFileStream * pStream, TFileStream * pNewStream) -{ -#ifdef STORMLIB_WINDOWS - // Delete the original stream file. Don't check the result value, - // because if the file doesn't exist, it would fail - DeleteFile(pStream->szFileName); - - // Rename the new file to the old stream's file - return (bool)MoveFile(pNewStream->szFileName, pStream->szFileName); -#endif - -#if defined(STORMLIB_MAC) || defined(STORMLIB_LINUX) - // "rename" on Linux also works if the target file exists - if(rename(pNewStream->szFileName, pStream->szFileName) == -1) - { - dwLastError = errno; - return false; - } - - return true; -#endif -} - -static void BaseFile_Close(TFileStream * pStream) -{ - if(pStream->Base.File.hFile != INVALID_HANDLE_VALUE) - { -#ifdef STORMLIB_WINDOWS - CloseHandle(pStream->Base.File.hFile); -#endif - -#if defined(STORMLIB_MAC) || defined(STORMLIB_LINUX) - close((intptr_t)pStream->Base.File.hFile); -#endif - } - - // Also invalidate the handle - pStream->Base.File.hFile = INVALID_HANDLE_VALUE; -} - -// Initializes base functions for the disk file -static void BaseFile_Init(TFileStream * pStream) -{ - pStream->BaseCreate = BaseFile_Create; - pStream->BaseOpen = BaseFile_Open; - pStream->BaseRead = BaseFile_Read; - pStream->BaseWrite = BaseFile_Write; - pStream->BaseResize = BaseFile_Resize; - pStream->BaseGetSize = BaseFile_GetSize; - pStream->BaseGetPos = BaseFile_GetPos; - pStream->BaseClose = BaseFile_Close; -} - -//----------------------------------------------------------------------------- -// Local functions - base memory-mapped file support - -#ifdef STORMLIB_WINDOWS - -typedef struct _SECTION_BASIC_INFORMATION -{ - PVOID BaseAddress; - ULONG Attributes; - LARGE_INTEGER Size; -} SECTION_BASIC_INFORMATION, *PSECTION_BASIC_INFORMATION; - -typedef ULONG (WINAPI * NTQUERYSECTION)( - IN HANDLE SectionHandle, - IN ULONG SectionInformationClass, - OUT PVOID SectionInformation, - IN SIZE_T Length, - OUT PSIZE_T ResultLength); - -static bool RetrieveFileMappingSize(HANDLE hSection, ULARGE_INTEGER & RefFileSize) -{ - SECTION_BASIC_INFORMATION BasicInfo = {0}; - NTQUERYSECTION PfnQuerySection; - HMODULE hNtdll; - SIZE_T ReturnLength = 0; - - if((hNtdll = GetModuleHandle(_T("ntdll.dll"))) != NULL) - { - PfnQuerySection = (NTQUERYSECTION)GetProcAddress(hNtdll, "NtQuerySection"); - if(PfnQuerySection != NULL) - { - if(PfnQuerySection(hSection, 0, &BasicInfo, sizeof(SECTION_BASIC_INFORMATION), &ReturnLength) == 0) - { - RefFileSize.HighPart = BasicInfo.Size.HighPart; - RefFileSize.LowPart = BasicInfo.Size.LowPart; - return true; - } - } - } - - return false; -} -#endif - -static bool BaseMap_Open(TFileStream * pStream, LPCTSTR szFileName, DWORD dwStreamFlags) -{ -#ifdef STORMLIB_WINDOWS - - ULARGE_INTEGER FileSize = {0}; - HANDLE hFile = INVALID_HANDLE_VALUE; - HANDLE hMap = NULL; - bool bResult = false; - - // Keep compiler happy - dwStreamFlags = dwStreamFlags; - - // 1) Try to treat "szFileName" as a section name - hMap = OpenFileMapping(SECTION_QUERY | FILE_MAP_READ, FALSE, szFileName); - if(hMap != NULL) - { - // Try to retrieve the size of the mapping - if(!RetrieveFileMappingSize(hMap, FileSize)) - { - CloseHandle(hMap); - hMap = NULL; - } - } - - // 2) Treat the name as file name - else - { - hFile = CreateFile(szFileName, FILE_READ_DATA, FILE_SHARE_READ, NULL, OPEN_EXISTING, 0, NULL); - if(hFile != INVALID_HANDLE_VALUE) - { - // Retrieve file size. Don't allow mapping file of a zero size. - FileSize.LowPart = GetFileSize(hFile, &FileSize.HighPart); - if(FileSize.QuadPart != 0) - { - // Now create file mapping over the file - hMap = CreateFileMapping(hFile, NULL, PAGE_READONLY, 0, 0, NULL); - } - } - } - - // Did it succeed? - if(hMap != NULL) - { - // Map the entire view into memory - // Note that this operation will fail if the file can't fit - // into usermode address space - pStream->Base.Map.pbFile = (LPBYTE)MapViewOfFile(hMap, FILE_MAP_READ, 0, 0, 0); - if(pStream->Base.Map.pbFile != NULL) - { - // Retrieve file time. If it's named section, put 0 - if(hFile != INVALID_HANDLE_VALUE) - GetFileTime(hFile, NULL, NULL, (LPFILETIME)&pStream->Base.Map.FileTime); - - // Retrieve file size and position - pStream->Base.Map.FileSize = FileSize.QuadPart; - pStream->Base.Map.FilePos = 0; - bResult = true; - } - - // Close the map handle - CloseHandle(hMap); - } - - // Close the file handle - if(hFile != INVALID_HANDLE_VALUE) - CloseHandle(hFile); - - // Return the result of the operation - return bResult; - -#elif defined(STORMLIB_HAS_MMAP) - - struct stat64 fileinfo; - intptr_t handle; - bool bResult = false; - - // Open the file - handle = open(szFileName, O_RDONLY); - if(handle != -1) - { - // Get the file size - if(fstat64(handle, &fileinfo) != -1) - { - pStream->Base.Map.pbFile = (LPBYTE)mmap(NULL, (size_t)fileinfo.st_size, PROT_READ, MAP_PRIVATE, handle, 0); - if(pStream->Base.Map.pbFile != NULL) - { - // time_t is number of seconds since 1.1.1970, UTC. - // 1 second = 10000000 (decimal) in FILETIME - // Set the start to 1.1.1970 00:00:00 - pStream->Base.Map.FileTime = 0x019DB1DED53E8000ULL + (10000000 * fileinfo.st_mtime); - pStream->Base.Map.FileSize = (ULONGLONG)fileinfo.st_size; - pStream->Base.Map.FilePos = 0; - bResult = true; - } - } - close(handle); - } - - // Did the mapping fail? - if(bResult == false) - dwLastError = errno; - return bResult; - -#else - - // File mapping is not supported - return false; - -#endif -} - -static bool BaseMap_Read( - TFileStream * pStream, // Pointer to an open stream - ULONGLONG * pByteOffset, // Pointer to file byte offset. If NULL, it reads from the current position - void * pvBuffer, // Pointer to data to be read - DWORD dwBytesToRead) // Number of bytes to read from the file -{ - ULONGLONG ByteOffset = (pByteOffset != NULL) ? *pByteOffset : pStream->Base.Map.FilePos; - - // Do we have to read anything at all? - if(dwBytesToRead != 0) - { - // Don't allow reading past file size - if((ByteOffset + dwBytesToRead) > pStream->Base.Map.FileSize) - return false; - - // Copy the required data - memcpy(pvBuffer, pStream->Base.Map.pbFile + (size_t)ByteOffset, dwBytesToRead); - } - - // Move the current file position - pStream->Base.Map.FilePos += dwBytesToRead; - return true; -} - -static void BaseMap_Close(TFileStream * pStream) -{ - -#ifdef STORMLIB_WINDOWS - - if(pStream->Base.Map.pbFile != NULL) - UnmapViewOfFile(pStream->Base.Map.pbFile); - -#elif defined(STORMLIB_HAS_MMAP) - - if(pStream->Base.Map.pbFile != NULL) - munmap(pStream->Base.Map.pbFile, (size_t )pStream->Base.Map.FileSize); - -#endif - - pStream->Base.Map.pbFile = NULL; -} - -// Initializes base functions for the mapped file -static void BaseMap_Init(TFileStream * pStream) -{ - // Supply the file stream functions - pStream->BaseOpen = BaseMap_Open; - pStream->BaseRead = BaseMap_Read; - pStream->BaseGetSize = BaseFile_GetSize; // Reuse BaseFile function - pStream->BaseGetPos = BaseFile_GetPos; // Reuse BaseFile function - pStream->BaseClose = BaseMap_Close; - - // Mapped files are read-only - pStream->dwFlags |= STREAM_FLAG_READ_ONLY; -} - -//----------------------------------------------------------------------------- -// Local functions - base HTTP file support - -static const TCHAR * BaseHttp_ExtractServerName(const TCHAR * szFileName, TCHAR * szServerName) -{ - // Check for HTTP - if(!_tcsnicmp(szFileName, _T("http://"), 7)) - szFileName += 7; - - // Cut off the server name - if(szServerName != NULL) - { - while(szFileName[0] != 0 && szFileName[0] != _T('/')) - *szServerName++ = *szFileName++; - *szServerName = 0; - } - else - { - while(szFileName[0] != 0 && szFileName[0] != _T('/')) - szFileName++; - } - - // Return the remainder - return szFileName; -} - -static bool BaseHttp_Open(TFileStream * pStream, const TCHAR * szFileName, DWORD dwStreamFlags) -{ -#ifdef STORMLIB_WINDOWS - - HINTERNET hRequest; - DWORD dwTemp = 0; - - // Keep compiler happy - dwStreamFlags = dwStreamFlags; - - // Don't connect to the internet - if(!InternetGetConnectedState(&dwTemp, 0)) - return false; - - // Initiate the connection to the internet - pStream->Base.Http.hInternet = InternetOpen(_T("StormLib HTTP MPQ reader"), - INTERNET_OPEN_TYPE_PRECONFIG, - NULL, - NULL, - 0); - if(pStream->Base.Http.hInternet != NULL) - { - TCHAR szServerName[MAX_PATH]; - DWORD dwFlags = INTERNET_FLAG_KEEP_CONNECTION | INTERNET_FLAG_NO_UI | INTERNET_FLAG_NO_CACHE_WRITE; - - // Initiate connection with the server - szFileName = BaseHttp_ExtractServerName(szFileName, szServerName); - pStream->Base.Http.hConnect = InternetConnect(pStream->Base.Http.hInternet, - szServerName, - INTERNET_DEFAULT_HTTP_PORT, - NULL, - NULL, - INTERNET_SERVICE_HTTP, - dwFlags, - 0); - if(pStream->Base.Http.hConnect != NULL) - { - // Open HTTP request to the file - hRequest = HttpOpenRequest(pStream->Base.Http.hConnect, _T("GET"), szFileName, NULL, NULL, NULL, INTERNET_FLAG_NO_CACHE_WRITE, 0); - if(hRequest != NULL) - { - if(HttpSendRequest(hRequest, NULL, 0, NULL, 0)) - { - ULONGLONG FileTime = 0; - DWORD dwFileSize = 0; - DWORD dwDataSize; - DWORD dwIndex = 0; - TCHAR StatusCode[0x08]; - - // Check if the file succeeded to open - dwDataSize = sizeof(StatusCode); - if(HttpQueryInfo(hRequest, HTTP_QUERY_STATUS_CODE, StatusCode, &dwDataSize, &dwIndex)) - { - if(_tcscmp(StatusCode, _T("200"))) - { - InternetCloseHandle(hRequest); - SetLastError(ERROR_FILE_NOT_FOUND); - return false; - } - } - - // Check if the MPQ has Last Modified field - dwDataSize = sizeof(ULONGLONG); - if(HttpQueryInfo(hRequest, HTTP_QUERY_LAST_MODIFIED | HTTP_QUERY_FLAG_SYSTEMTIME, &FileTime, &dwDataSize, &dwIndex)) - pStream->Base.Http.FileTime = FileTime; - - // Verify if the server supports random access - dwDataSize = sizeof(DWORD); - if(HttpQueryInfo(hRequest, HTTP_QUERY_CONTENT_LENGTH | HTTP_QUERY_FLAG_NUMBER, &dwFileSize, &dwDataSize, &dwIndex)) - { - if(dwFileSize != 0) - { - InternetCloseHandle(hRequest); - pStream->Base.Http.FileSize = dwFileSize; - pStream->Base.Http.FilePos = 0; - return true; - } - } - } - - // Close the request - InternetCloseHandle(hRequest); - } - - // Close the connection handle - InternetCloseHandle(pStream->Base.Http.hConnect); - pStream->Base.Http.hConnect = NULL; - } - - // Close the internet handle - InternetCloseHandle(pStream->Base.Http.hInternet); - pStream->Base.Http.hInternet = NULL; - } - - // If the file is not there or is not available for random access, report error - pStream->BaseClose(pStream); - return false; - -#else - - // Not supported - SetLastError(ERROR_NOT_SUPPORTED); - pStream = pStream; - return false; - -#endif -} - -static bool BaseHttp_Read( - TFileStream * pStream, // Pointer to an open stream - ULONGLONG * pByteOffset, // Pointer to file byte offset. If NULL, it reads from the current position - void * pvBuffer, // Pointer to data to be read - DWORD dwBytesToRead) // Number of bytes to read from the file -{ -#ifdef STORMLIB_WINDOWS - ULONGLONG ByteOffset = (pByteOffset != NULL) ? *pByteOffset : pStream->Base.Http.FilePos; - DWORD dwTotalBytesRead = 0; - - // Do we have to read anything at all? - if(dwBytesToRead != 0) - { - HINTERNET hRequest; - LPCTSTR szFileName; - LPBYTE pbBuffer = (LPBYTE)pvBuffer; - TCHAR szRangeRequest[0x80]; - DWORD dwStartOffset = (DWORD)ByteOffset; - DWORD dwEndOffset = dwStartOffset + dwBytesToRead; - - // Open HTTP request to the file - szFileName = BaseHttp_ExtractServerName(pStream->szFileName, NULL); - hRequest = HttpOpenRequest(pStream->Base.Http.hConnect, _T("GET"), szFileName, NULL, NULL, NULL, INTERNET_FLAG_NO_CACHE_WRITE, 0); - if(hRequest != NULL) - { - // Add range request to the HTTP headers - // http://www.clevercomponents.com/articles/article015/resuming.asp - wsprintf(szRangeRequest, _T("Range: bytes=%u-%u"), (unsigned int)dwStartOffset, (unsigned int)dwEndOffset); - HttpAddRequestHeaders(hRequest, szRangeRequest, 0xFFFFFFFF, HTTP_ADDREQ_FLAG_ADD_IF_NEW); - - // Send the request to the server - if(HttpSendRequest(hRequest, NULL, 0, NULL, 0)) - { - while(dwTotalBytesRead < dwBytesToRead) - { - DWORD dwBlockBytesToRead = dwBytesToRead - dwTotalBytesRead; - DWORD dwBlockBytesRead = 0; - - // Read the block from the file - if(dwBlockBytesToRead > 0x200) - dwBlockBytesToRead = 0x200; - InternetReadFile(hRequest, pbBuffer, dwBlockBytesToRead, &dwBlockBytesRead); - - // Check for end - if(dwBlockBytesRead == 0) - break; - - // Move buffers - dwTotalBytesRead += dwBlockBytesRead; - pbBuffer += dwBlockBytesRead; - } - } - InternetCloseHandle(hRequest); - } - } - - // Increment the current file position by number of bytes read - pStream->Base.Http.FilePos = ByteOffset + dwTotalBytesRead; - - // If the number of bytes read doesn't match the required amount, return false - if(dwTotalBytesRead != dwBytesToRead) - SetLastError(ERROR_HANDLE_EOF); - return (dwTotalBytesRead == dwBytesToRead); - -#else - - // Not supported - pStream = pStream; - pByteOffset = pByteOffset; - pvBuffer = pvBuffer; - dwBytesToRead = dwBytesToRead; - SetLastError(ERROR_NOT_SUPPORTED); - return false; - -#endif -} - -static void BaseHttp_Close(TFileStream * pStream) -{ -#ifdef STORMLIB_WINDOWS - if(pStream->Base.Http.hConnect != NULL) - InternetCloseHandle(pStream->Base.Http.hConnect); - pStream->Base.Http.hConnect = NULL; - - if(pStream->Base.Http.hInternet != NULL) - InternetCloseHandle(pStream->Base.Http.hInternet); - pStream->Base.Http.hInternet = NULL; -#else - pStream = pStream; -#endif -} - -// Initializes base functions for the mapped file -static void BaseHttp_Init(TFileStream * pStream) -{ - // Supply the stream functions - pStream->BaseOpen = BaseHttp_Open; - pStream->BaseRead = BaseHttp_Read; - pStream->BaseGetSize = BaseFile_GetSize; // Reuse BaseFile function - pStream->BaseGetPos = BaseFile_GetPos; // Reuse BaseFile function - pStream->BaseClose = BaseHttp_Close; - - // HTTP files are read-only - pStream->dwFlags |= STREAM_FLAG_READ_ONLY; -} - -//----------------------------------------------------------------------------- -// Local functions - base block-based support - -// Generic function that loads blocks from the file -// The function groups the block with the same availability, -// so the called BlockRead can finish the request in a single system call -static bool BlockStream_Read( - TBlockStream * pStream, // Pointer to an open stream - ULONGLONG * pByteOffset, // Pointer to file byte offset. If NULL, it reads from the current position - void * pvBuffer, // Pointer to data to be read - DWORD dwBytesToRead) // Number of bytes to read from the file -{ - ULONGLONG BlockOffset0; - ULONGLONG BlockOffset; - ULONGLONG ByteOffset; - ULONGLONG EndOffset; - LPBYTE TransferBuffer; - LPBYTE BlockBuffer; - DWORD BlockBufferOffset; // Offset of the desired data in the block buffer - DWORD BytesNeeded; // Number of bytes that really need to be read - DWORD BlockSize = pStream->BlockSize; - DWORD BlockCount; - bool bPrevBlockAvailable; - bool bCallbackCalled = false; - bool bBlockAvailable; - bool bResult = true; - - // The base block read function must be present - assert(pStream->BlockRead != NULL); - - // NOP reading of zero bytes - if(dwBytesToRead == 0) - return true; - - // Get the current position in the stream - ByteOffset = (pByteOffset != NULL) ? pByteOffset[0] : pStream->StreamPos; - EndOffset = ByteOffset + dwBytesToRead; - if(EndOffset > pStream->StreamSize) - { - SetLastError(ERROR_HANDLE_EOF); - return false; - } - - // Calculate the block parameters - BlockOffset0 = BlockOffset = ByteOffset & ~((ULONGLONG)BlockSize - 1); - BlockCount = (DWORD)(((EndOffset - BlockOffset) + (BlockSize - 1)) / BlockSize); - BytesNeeded = (DWORD)(EndOffset - BlockOffset); - - // Remember where we have our data - assert((BlockSize & (BlockSize - 1)) == 0); - BlockBufferOffset = (DWORD)(ByteOffset & (BlockSize - 1)); - - // Allocate buffer for reading blocks - TransferBuffer = BlockBuffer = STORM_ALLOC(BYTE, (BlockCount * BlockSize)); - if(TransferBuffer == NULL) - { - SetLastError(ERROR_NOT_ENOUGH_MEMORY); - return false; - } - - // If all blocks are available, just read all blocks at once - if(pStream->IsComplete == 0) - { - // Now parse the blocks and send the block read request - // to all blocks with the same availability - assert(pStream->BlockCheck != NULL); - bPrevBlockAvailable = pStream->BlockCheck(pStream, BlockOffset); - - // Loop as long as we have something to read - while(BlockOffset < EndOffset) - { - // Determine availability of the next block - bBlockAvailable = pStream->BlockCheck(pStream, BlockOffset); - - // If the availability has changed, read all blocks up to this one - if(bBlockAvailable != bPrevBlockAvailable) - { - // Call the file stream callback, if the block is not available - if(pStream->pMaster && pStream->pfnCallback && bPrevBlockAvailable == false) - { - pStream->pfnCallback(pStream->UserData, BlockOffset0, (DWORD)(BlockOffset - BlockOffset0)); - bCallbackCalled = true; - } - - // Load the continuous blocks with the same availability - assert(BlockOffset > BlockOffset0); - bResult = pStream->BlockRead(pStream, BlockOffset0, BlockOffset, BlockBuffer, BytesNeeded, bPrevBlockAvailable); - if(!bResult) - break; - - // Move the block offset - BlockBuffer += (DWORD)(BlockOffset - BlockOffset0); - BytesNeeded -= (DWORD)(BlockOffset - BlockOffset0); - bPrevBlockAvailable = bBlockAvailable; - BlockOffset0 = BlockOffset; - } - - // Move to the block offset in the stream - BlockOffset += BlockSize; - } - - // If there is a block(s) remaining to be read, do it - if(BlockOffset > BlockOffset0) - { - // Call the file stream callback, if the block is not available - if(pStream->pMaster && pStream->pfnCallback && bPrevBlockAvailable == false) - { - pStream->pfnCallback(pStream->UserData, BlockOffset0, (DWORD)(BlockOffset - BlockOffset0)); - bCallbackCalled = true; - } - - // Read the complete blocks from the file - if(BlockOffset > pStream->StreamSize) - BlockOffset = pStream->StreamSize; - bResult = pStream->BlockRead(pStream, BlockOffset0, BlockOffset, BlockBuffer, BytesNeeded, bPrevBlockAvailable); - } - } - else - { - // Read the complete blocks from the file - if(EndOffset > pStream->StreamSize) - EndOffset = pStream->StreamSize; - bResult = pStream->BlockRead(pStream, BlockOffset, EndOffset, BlockBuffer, BytesNeeded, true); - } - - // Now copy the data to the user buffer - if(bResult) - { - memcpy(pvBuffer, TransferBuffer + BlockBufferOffset, dwBytesToRead); - pStream->StreamPos = ByteOffset + dwBytesToRead; - } - else - { - // If the block read failed, set the last error - SetLastError(ERROR_FILE_INCOMPLETE); - } - - // Call the callback to indicate we are done - if(bCallbackCalled) - pStream->pfnCallback(pStream->UserData, 0, 0); - - // Free the block buffer and return - STORM_FREE(TransferBuffer); - return bResult; -} - -static bool BlockStream_GetSize(TFileStream * pStream, ULONGLONG * pFileSize) -{ - *pFileSize = pStream->StreamSize; - return true; -} - -static bool BlockStream_GetPos(TFileStream * pStream, ULONGLONG * pByteOffset) -{ - *pByteOffset = pStream->StreamPos; - return true; -} - -static void BlockStream_Close(TBlockStream * pStream) -{ - // Free the data map, if any - if(pStream->FileBitmap != NULL) - STORM_FREE(pStream->FileBitmap); - pStream->FileBitmap = NULL; - - // Call the base class for closing the stream - pStream->BaseClose(pStream); -} - -//----------------------------------------------------------------------------- -// File stream allocation function - -static STREAM_INIT StreamBaseInit[4] = -{ - BaseFile_Init, - BaseMap_Init, - BaseHttp_Init, - BaseNone_Init -}; - -// This function allocates an empty structure for the file stream -// The stream structure is created as flat block, variable length -// The file name is placed after the end of the stream structure data -static TFileStream * AllocateFileStream( - const TCHAR * szFileName, - size_t StreamSize, - DWORD dwStreamFlags) -{ - TFileStream * pMaster = NULL; - TFileStream * pStream; - const TCHAR * szNextFile = szFileName; - size_t FileNameSize; - - // Sanity check - assert(StreamSize != 0); - - // The caller can specify chain of files in the following form: - // C:\archive.MPQ*http://www.server.com/MPQs/archive-server.MPQ - // In that case, we use the part after "*" as master file name - while(szNextFile[0] != 0 && szNextFile[0] != _T('*')) - szNextFile++; - FileNameSize = (size_t)((szNextFile - szFileName) * sizeof(TCHAR)); - - // If we have a next file, we need to open it as master stream - // Note that we don't care if the master stream exists or not, - // If it doesn't, later attempts to read missing file block will fail - if(szNextFile[0] == _T('*')) - { - // Don't allow another master file in the string - if(_tcschr(szNextFile + 1, _T('*')) != NULL) - { - SetLastError(ERROR_INVALID_PARAMETER); - return NULL; - } - - // Open the master file - pMaster = FileStream_OpenFile(szNextFile + 1, STREAM_FLAG_READ_ONLY); - } - - // Allocate the stream structure for the given stream type - pStream = (TFileStream *)STORM_ALLOC(BYTE, StreamSize + FileNameSize + sizeof(TCHAR)); - if(pStream != NULL) - { - // Zero the entire structure - memset(pStream, 0, StreamSize); - pStream->pMaster = pMaster; - pStream->dwFlags = dwStreamFlags; - - // Initialize the file name - pStream->szFileName = (TCHAR *)((BYTE *)pStream + StreamSize); - memcpy(pStream->szFileName, szFileName, FileNameSize); - pStream->szFileName[FileNameSize / sizeof(TCHAR)] = 0; - - // Initialize the stream functions - StreamBaseInit[dwStreamFlags & 0x03](pStream); - } - - return pStream; -} - -//----------------------------------------------------------------------------- -// Local functions - flat stream support - -static DWORD FlatStream_CheckFile(TBlockStream * pStream) -{ - LPBYTE FileBitmap = (LPBYTE)pStream->FileBitmap; - DWORD WholeByteCount = (pStream->BlockCount / 8); - DWORD ExtraBitsCount = (pStream->BlockCount & 7); - BYTE ExpectedValue; - - // Verify the whole bytes - their value must be 0xFF - for(DWORD i = 0; i < WholeByteCount; i++) - { - if(FileBitmap[i] != 0xFF) - return 0; - } - - // If there are extra bits, calculate the mask - if(ExtraBitsCount != 0) - { - ExpectedValue = (BYTE)((1 << ExtraBitsCount) - 1); - if(FileBitmap[WholeByteCount] != ExpectedValue) - return 0; - } - - // Yes, the file is complete - return 1; -} - -static bool FlatStream_LoadBitmap(TBlockStream * pStream) -{ - FILE_BITMAP_FOOTER Footer; - ULONGLONG ByteOffset; - LPBYTE FileBitmap; - DWORD BlockCount; - DWORD BitmapSize; - - // Do not load the bitmap if we should not have to - if(!(pStream->dwFlags & STREAM_FLAG_USE_BITMAP)) - return false; - - // Only if the size is greater than size of bitmap footer - if(pStream->Base.File.FileSize > sizeof(FILE_BITMAP_FOOTER)) - { - // Load the bitmap footer - ByteOffset = pStream->Base.File.FileSize - sizeof(FILE_BITMAP_FOOTER); - if(pStream->BaseRead(pStream, &ByteOffset, &Footer, sizeof(FILE_BITMAP_FOOTER))) - { - // Make sure that the array is properly BSWAP-ed - BSWAP_ARRAY32_UNSIGNED((LPDWORD)(&Footer), sizeof(FILE_BITMAP_FOOTER)); - - // Verify if there is actually a footer - if(Footer.Signature == ID_FILE_BITMAP_FOOTER && Footer.Version == 0x03) - { - // Get the offset of the bitmap, number of blocks and size of the bitmap - ByteOffset = MAKE_OFFSET64(Footer.MapOffsetHi, Footer.MapOffsetLo); - BlockCount = (DWORD)(((ByteOffset - 1) / Footer.BlockSize) + 1); - BitmapSize = ((BlockCount + 7) / 8); - - // Check if the sizes match - if(ByteOffset + BitmapSize + sizeof(FILE_BITMAP_FOOTER) == pStream->Base.File.FileSize) - { - // Allocate space for the bitmap - FileBitmap = STORM_ALLOC(BYTE, BitmapSize); - if(FileBitmap != NULL) - { - // Load the bitmap bits - if(!pStream->BaseRead(pStream, &ByteOffset, FileBitmap, BitmapSize)) - { - STORM_FREE(FileBitmap); - return false; - } - - // Update the stream size - pStream->BuildNumber = Footer.BuildNumber; - pStream->StreamSize = ByteOffset; - - // Fill the bitmap information - pStream->FileBitmap = FileBitmap; - pStream->BitmapSize = BitmapSize; - pStream->BlockSize = Footer.BlockSize; - pStream->BlockCount = BlockCount; - pStream->IsComplete = FlatStream_CheckFile(pStream); - return true; - } - } - } - } - } - - return false; -} - -static void FlatStream_UpdateBitmap( - TBlockStream * pStream, // Pointer to an open stream - ULONGLONG StartOffset, - ULONGLONG EndOffset) -{ - LPBYTE FileBitmap = (LPBYTE)pStream->FileBitmap; - DWORD BlockIndex; - DWORD BlockSize = pStream->BlockSize; - DWORD ByteIndex; - BYTE BitMask; - - // Sanity checks - assert((StartOffset & (BlockSize - 1)) == 0); - assert(FileBitmap != NULL); - - // Calculate the index of the block - BlockIndex = (DWORD)(StartOffset / BlockSize); - ByteIndex = (BlockIndex / 0x08); - BitMask = (BYTE)(1 << (BlockIndex & 0x07)); - - // Set all bits for the specified range - while(StartOffset < EndOffset) - { - // Set the bit - FileBitmap[ByteIndex] |= BitMask; - - // Move all - StartOffset += BlockSize; - ByteIndex += (BitMask >> 0x07); - BitMask = (BitMask >> 0x07) | (BitMask << 0x01); - } - - // Increment the bitmap update count - pStream->IsModified = 1; -} - -static bool FlatStream_BlockCheck( - TBlockStream * pStream, // Pointer to an open stream - ULONGLONG BlockOffset) -{ - LPBYTE FileBitmap = (LPBYTE)pStream->FileBitmap; - DWORD BlockIndex; - BYTE BitMask; - - // Sanity checks - assert((BlockOffset & (pStream->BlockSize - 1)) == 0); - assert(FileBitmap != NULL); - - // Calculate the index of the block - BlockIndex = (DWORD)(BlockOffset / pStream->BlockSize); - BitMask = (BYTE)(1 << (BlockIndex & 0x07)); - - // Check if the bit is present - return (FileBitmap[BlockIndex / 0x08] & BitMask) ? true : false; -} - -static bool FlatStream_BlockRead( - TBlockStream * pStream, // Pointer to an open stream - ULONGLONG StartOffset, - ULONGLONG EndOffset, - LPBYTE BlockBuffer, - DWORD BytesNeeded, - bool bAvailable) -{ - DWORD BytesToRead = (DWORD)(EndOffset - StartOffset); - - // The starting offset must be aligned to size of the block - assert(pStream->FileBitmap != NULL); - assert((StartOffset & (pStream->BlockSize - 1)) == 0); - assert(StartOffset < EndOffset); - - // If the blocks are not available, we need to load them from the master - // and then save to the mirror - if(bAvailable == false) - { - // If we have no master, we cannot satisfy read request - if(pStream->pMaster == NULL) - return false; - - // Load the blocks from the master stream - // Note that we always have to read complete blocks - // so they get properly stored to the mirror stream - if(!FileStream_Read(pStream->pMaster, &StartOffset, BlockBuffer, BytesToRead)) - return false; - - // Store the loaded blocks to the mirror file. - // Note that this operation is not required to succeed - if(pStream->BaseWrite(pStream, &StartOffset, BlockBuffer, BytesToRead)) - FlatStream_UpdateBitmap(pStream, StartOffset, EndOffset); - - return true; - } - else - { - if(BytesToRead > BytesNeeded) - BytesToRead = BytesNeeded; - return pStream->BaseRead(pStream, &StartOffset, BlockBuffer, BytesToRead); - } -} - -static void FlatStream_Close(TBlockStream * pStream) -{ - FILE_BITMAP_FOOTER Footer; - - if(pStream->FileBitmap && pStream->IsModified) - { - // Write the file bitmap - pStream->BaseWrite(pStream, &pStream->StreamSize, pStream->FileBitmap, pStream->BitmapSize); - - // Prepare and write the file footer - Footer.Signature = ID_FILE_BITMAP_FOOTER; - Footer.Version = 3; - Footer.BuildNumber = pStream->BuildNumber; - Footer.MapOffsetLo = (DWORD)(pStream->StreamSize & 0xFFFFFFFF); - Footer.MapOffsetHi = (DWORD)(pStream->StreamSize >> 0x20); - Footer.BlockSize = pStream->BlockSize; - BSWAP_ARRAY32_UNSIGNED(&Footer, sizeof(FILE_BITMAP_FOOTER)); - pStream->BaseWrite(pStream, NULL, &Footer, sizeof(FILE_BITMAP_FOOTER)); - } - - // Close the base class - BlockStream_Close(pStream); -} - -static bool FlatStream_CreateMirror(TBlockStream * pStream) -{ - ULONGLONG MasterSize = 0; - ULONGLONG MirrorSize = 0; - LPBYTE FileBitmap = NULL; - DWORD dwBitmapSize; - DWORD dwBlockCount; - bool bNeedCreateMirrorStream = true; - bool bNeedResizeMirrorStream = true; - - // Do we have master function and base creation function? - if(pStream->pMaster == NULL || pStream->BaseCreate == NULL) - return false; - - // Retrieve the master file size, block count and bitmap size - FileStream_GetSize(pStream->pMaster, &MasterSize); - dwBlockCount = (DWORD)((MasterSize + DEFAULT_BLOCK_SIZE - 1) / DEFAULT_BLOCK_SIZE); - dwBitmapSize = (DWORD)((dwBlockCount + 7) / 8); - - // Setup stream size and position - pStream->BuildNumber = DEFAULT_BUILD_NUMBER; // BUGBUG: Really??? - pStream->StreamSize = MasterSize; - pStream->StreamPos = 0; - - // Open the base stream for write access - if(pStream->BaseOpen(pStream, pStream->szFileName, 0)) - { - // If the file open succeeded, check if the file size matches required size - pStream->BaseGetSize(pStream, &MirrorSize); - if(MirrorSize == MasterSize + dwBitmapSize + sizeof(FILE_BITMAP_FOOTER)) - { - // Attempt to load an existing file bitmap - if(FlatStream_LoadBitmap(pStream)) - return true; - - // We need to create new file bitmap - bNeedResizeMirrorStream = false; - } - - // We need to create mirror stream - bNeedCreateMirrorStream = false; - } - - // Create a new stream, if needed - if(bNeedCreateMirrorStream) - { - if(!pStream->BaseCreate(pStream)) - return false; - } - - // If we need to, then resize the mirror stream - if(bNeedResizeMirrorStream) - { - if(!pStream->BaseResize(pStream, MasterSize + dwBitmapSize + sizeof(FILE_BITMAP_FOOTER))) - return false; - } - - // Allocate the bitmap array - FileBitmap = STORM_ALLOC(BYTE, dwBitmapSize); - if(FileBitmap == NULL) - return false; - - // Initialize the bitmap - memset(FileBitmap, 0, dwBitmapSize); - pStream->FileBitmap = FileBitmap; - pStream->BitmapSize = dwBitmapSize; - pStream->BlockSize = DEFAULT_BLOCK_SIZE; - pStream->BlockCount = dwBlockCount; - pStream->IsComplete = 0; - pStream->IsModified = 1; - - // Note: Don't write the stream bitmap right away. - // Doing so would cause sparse file resize on NTFS, - // which would take long time on larger files. - return true; -} - -static TFileStream * FlatStream_Open(const TCHAR * szFileName, DWORD dwStreamFlags) -{ - TBlockStream * pStream; - ULONGLONG ByteOffset = 0; - - // Create new empty stream - pStream = (TBlockStream *)AllocateFileStream(szFileName, sizeof(TBlockStream), dwStreamFlags); - if(pStream == NULL) - return NULL; - - // Do we have a master stream? - if(pStream->pMaster != NULL) - { - if(!FlatStream_CreateMirror(pStream)) - { - FileStream_Close(pStream); - SetLastError(ERROR_FILE_NOT_FOUND); - return NULL; - } - } - else - { - // Attempt to open the base stream - if(!pStream->BaseOpen(pStream, pStream->szFileName, dwStreamFlags)) - { - FileStream_Close(pStream); - return NULL; - } - - // Load the bitmap, if required to - if(dwStreamFlags & STREAM_FLAG_USE_BITMAP) - FlatStream_LoadBitmap(pStream); - } - - // If we have a stream bitmap, set the reading functions - // which check presence of each file block - if(pStream->FileBitmap != NULL) - { - // Set the stream position to zero. Stream size is already set - assert(pStream->StreamSize != 0); - pStream->StreamPos = 0; - pStream->dwFlags |= STREAM_FLAG_READ_ONLY; - - // Supply the stream functions - pStream->StreamRead = (STREAM_READ)BlockStream_Read; - pStream->StreamGetSize = BlockStream_GetSize; - pStream->StreamGetPos = BlockStream_GetPos; - pStream->StreamClose = (STREAM_CLOSE)FlatStream_Close; - - // Supply the block functions - pStream->BlockCheck = (BLOCK_CHECK)FlatStream_BlockCheck; - pStream->BlockRead = (BLOCK_READ)FlatStream_BlockRead; - } - else - { - // Reset the base position to zero - pStream->BaseRead(pStream, &ByteOffset, NULL, 0); - - // Setup stream size and position - pStream->StreamSize = pStream->Base.File.FileSize; - pStream->StreamPos = 0; - - // Set the base functions - pStream->StreamRead = pStream->BaseRead; - pStream->StreamWrite = pStream->BaseWrite; - pStream->StreamResize = pStream->BaseResize; - pStream->StreamGetSize = pStream->BaseGetSize; - pStream->StreamGetPos = pStream->BaseGetPos; - pStream->StreamClose = pStream->BaseClose; - } - - return pStream; -} - -//----------------------------------------------------------------------------- -// Local functions - partial stream support - -static bool IsPartHeader(PPART_FILE_HEADER pPartHdr) -{ - // Version number must be 2 - if(pPartHdr->PartialVersion == 2) - { - // GameBuildNumber must be an ASCII number - if(isdigit(pPartHdr->GameBuildNumber[0]) && isdigit(pPartHdr->GameBuildNumber[1]) && isdigit(pPartHdr->GameBuildNumber[2])) - { - // Block size must be power of 2 - if((pPartHdr->BlockSize & (pPartHdr->BlockSize - 1)) == 0) - return true; - } - } - - return false; -} - -static DWORD PartStream_CheckFile(TBlockStream * pStream) -{ - PPART_FILE_MAP_ENTRY FileBitmap = (PPART_FILE_MAP_ENTRY)pStream->FileBitmap; - DWORD dwBlockCount; - - // Get the number of blocks - dwBlockCount = (DWORD)((pStream->StreamSize + pStream->BlockSize - 1) / pStream->BlockSize); - - // Check all blocks - for(DWORD i = 0; i < dwBlockCount; i++, FileBitmap++) - { - // Few sanity checks - assert(FileBitmap->LargeValueHi == 0); - assert(FileBitmap->LargeValueLo == 0); - assert(FileBitmap->Flags == 0 || FileBitmap->Flags == 3); - - // Check if this block is present - if(FileBitmap->Flags != 3) - return 0; - } - - // Yes, the file is complete - return 1; -} - -static bool PartStream_LoadBitmap(TBlockStream * pStream) -{ - PPART_FILE_MAP_ENTRY FileBitmap; - PART_FILE_HEADER PartHdr; - ULONGLONG ByteOffset = 0; - ULONGLONG StreamSize = 0; - DWORD BlockCount; - DWORD BitmapSize; - - // Only if the size is greater than size of the bitmap header - if(pStream->Base.File.FileSize > sizeof(PART_FILE_HEADER)) - { - // Attempt to read PART file header - if(pStream->BaseRead(pStream, &ByteOffset, &PartHdr, sizeof(PART_FILE_HEADER))) - { - // We need to swap PART file header on big-endian platforms - BSWAP_ARRAY32_UNSIGNED(&PartHdr, sizeof(PART_FILE_HEADER)); - - // Verify the PART file header - if(IsPartHeader(&PartHdr)) - { - // Get the number of blocks and size of one block - StreamSize = MAKE_OFFSET64(PartHdr.FileSizeHi, PartHdr.FileSizeLo); - ByteOffset = sizeof(PART_FILE_HEADER); - BlockCount = (DWORD)((StreamSize + PartHdr.BlockSize - 1) / PartHdr.BlockSize); - BitmapSize = BlockCount * sizeof(PART_FILE_MAP_ENTRY); - - // Check if sizes match - if((ByteOffset + BitmapSize) < pStream->Base.File.FileSize) - { - // Allocate space for the array of PART_FILE_MAP_ENTRY - FileBitmap = STORM_ALLOC(PART_FILE_MAP_ENTRY, BlockCount); - if(FileBitmap != NULL) - { - // Load the block map - if(!pStream->BaseRead(pStream, &ByteOffset, FileBitmap, BitmapSize)) - { - STORM_FREE(FileBitmap); - return false; - } - - // Make sure that the byte order is correct - BSWAP_ARRAY32_UNSIGNED(FileBitmap, BitmapSize); - - // Update the stream size - pStream->BuildNumber = StringToInt(PartHdr.GameBuildNumber); - pStream->StreamSize = StreamSize; - - // Fill the bitmap information - pStream->FileBitmap = FileBitmap; - pStream->BitmapSize = BitmapSize; - pStream->BlockSize = PartHdr.BlockSize; - pStream->BlockCount = BlockCount; - pStream->IsComplete = PartStream_CheckFile(pStream); - return true; - } - } - } - } - } - - return false; -} - -static void PartStream_UpdateBitmap( - TBlockStream * pStream, // Pointer to an open stream - ULONGLONG StartOffset, - ULONGLONG EndOffset, - ULONGLONG RealOffset) -{ - PPART_FILE_MAP_ENTRY FileBitmap; - DWORD BlockSize = pStream->BlockSize; - - // Sanity checks - assert((StartOffset & (BlockSize - 1)) == 0); - assert(pStream->FileBitmap != NULL); - - // Calculate the first entry in the block map - FileBitmap = (PPART_FILE_MAP_ENTRY)pStream->FileBitmap + (StartOffset / BlockSize); - - // Set all bits for the specified range - while(StartOffset < EndOffset) - { - // Set the bit - FileBitmap->BlockOffsHi = (DWORD)(RealOffset >> 0x20); - FileBitmap->BlockOffsLo = (DWORD)(RealOffset & 0xFFFFFFFF); - FileBitmap->Flags = 3; - - // Move all - StartOffset += BlockSize; - RealOffset += BlockSize; - FileBitmap++; - } - - // Increment the bitmap update count - pStream->IsModified = 1; -} - -static bool PartStream_BlockCheck( - TBlockStream * pStream, // Pointer to an open stream - ULONGLONG BlockOffset) -{ - PPART_FILE_MAP_ENTRY FileBitmap; - - // Sanity checks - assert((BlockOffset & (pStream->BlockSize - 1)) == 0); - assert(pStream->FileBitmap != NULL); - - // Calculate the block map entry - FileBitmap = (PPART_FILE_MAP_ENTRY)pStream->FileBitmap + (BlockOffset / pStream->BlockSize); - - // Check if the flags are present - return (FileBitmap->Flags & 0x03) ? true : false; -} - -static bool PartStream_BlockRead( - TBlockStream * pStream, - ULONGLONG StartOffset, - ULONGLONG EndOffset, - LPBYTE BlockBuffer, - DWORD BytesNeeded, - bool bAvailable) -{ - PPART_FILE_MAP_ENTRY FileBitmap; - ULONGLONG ByteOffset; - DWORD BytesToRead; - DWORD BlockIndex = (DWORD)(StartOffset / pStream->BlockSize); - - // The starting offset must be aligned to size of the block - assert(pStream->FileBitmap != NULL); - assert((StartOffset & (pStream->BlockSize - 1)) == 0); - assert(StartOffset < EndOffset); - - // If the blocks are not available, we need to load them from the master - // and then save to the mirror - if(bAvailable == false) - { - // If we have no master, we cannot satisfy read request - if(pStream->pMaster == NULL) - return false; - - // Load the blocks from the master stream - // Note that we always have to read complete blocks - // so they get properly stored to the mirror stream - BytesToRead = (DWORD)(EndOffset - StartOffset); - if(!FileStream_Read(pStream->pMaster, &StartOffset, BlockBuffer, BytesToRead)) - return false; - - // The loaded blocks are going to be stored to the end of the file - // Note that this operation is not required to succeed - if(pStream->BaseGetSize(pStream, &ByteOffset)) - { - // Store the loaded blocks to the mirror file. - if(pStream->BaseWrite(pStream, &ByteOffset, BlockBuffer, BytesToRead)) - { - PartStream_UpdateBitmap(pStream, StartOffset, EndOffset, ByteOffset); - } - } - } - else - { - // Get the file map entry - FileBitmap = (PPART_FILE_MAP_ENTRY)pStream->FileBitmap + BlockIndex; - - // Read all blocks - while(StartOffset < EndOffset) - { - // Get the number of bytes to be read - BytesToRead = (DWORD)(EndOffset - StartOffset); - if(BytesToRead > pStream->BlockSize) - BytesToRead = pStream->BlockSize; - if(BytesToRead > BytesNeeded) - BytesToRead = BytesNeeded; - - // Read the block - ByteOffset = MAKE_OFFSET64(FileBitmap->BlockOffsHi, FileBitmap->BlockOffsLo); - if(!pStream->BaseRead(pStream, &ByteOffset, BlockBuffer, BytesToRead)) - return false; - - // Move the pointers - StartOffset += pStream->BlockSize; - BlockBuffer += pStream->BlockSize; - BytesNeeded -= pStream->BlockSize; - FileBitmap++; - } - } - - return true; -} - -static void PartStream_Close(TBlockStream * pStream) -{ - PART_FILE_HEADER PartHeader; - ULONGLONG ByteOffset = 0; - - if(pStream->FileBitmap && pStream->IsModified) - { - // Prepare the part file header - memset(&PartHeader, 0, sizeof(PART_FILE_HEADER)); - PartHeader.PartialVersion = 2; - PartHeader.FileSizeHi = (DWORD)(pStream->StreamSize >> 0x20); - PartHeader.FileSizeLo = (DWORD)(pStream->StreamSize & 0xFFFFFFFF); - PartHeader.BlockSize = pStream->BlockSize; - - // Make sure that the header is properly BSWAPed - BSWAP_ARRAY32_UNSIGNED(&PartHeader, sizeof(PART_FILE_HEADER)); - IntToString(PartHeader.GameBuildNumber, _countof(PartHeader.GameBuildNumber), pStream->BuildNumber); - - // Write the part header - pStream->BaseWrite(pStream, &ByteOffset, &PartHeader, sizeof(PART_FILE_HEADER)); - - // Write the block bitmap - BSWAP_ARRAY32_UNSIGNED(pStream->FileBitmap, pStream->BitmapSize); - pStream->BaseWrite(pStream, NULL, pStream->FileBitmap, pStream->BitmapSize); - } - - // Close the base class - BlockStream_Close(pStream); -} - -static bool PartStream_CreateMirror(TBlockStream * pStream) -{ - ULONGLONG RemainingSize; - ULONGLONG MasterSize = 0; - ULONGLONG MirrorSize = 0; - LPBYTE FileBitmap = NULL; - DWORD dwBitmapSize; - DWORD dwBlockCount; - bool bNeedCreateMirrorStream = true; - bool bNeedResizeMirrorStream = true; - - // Do we have master function and base creation function? - if(pStream->pMaster == NULL || pStream->BaseCreate == NULL) - return false; - - // Retrieve the master file size, block count and bitmap size - FileStream_GetSize(pStream->pMaster, &MasterSize); - dwBlockCount = (DWORD)((MasterSize + DEFAULT_BLOCK_SIZE - 1) / DEFAULT_BLOCK_SIZE); - dwBitmapSize = (DWORD)(dwBlockCount * sizeof(PART_FILE_MAP_ENTRY)); - - // Setup stream size and position - pStream->BuildNumber = DEFAULT_BUILD_NUMBER; // BUGBUG: Really??? - pStream->StreamSize = MasterSize; - pStream->StreamPos = 0; - - // Open the base stream for write access - if(pStream->BaseOpen(pStream, pStream->szFileName, 0)) - { - // If the file open succeeded, check if the file size matches required size - pStream->BaseGetSize(pStream, &MirrorSize); - if(MirrorSize >= sizeof(PART_FILE_HEADER) + dwBitmapSize) - { - // Check if the remaining size is aligned to block - RemainingSize = MirrorSize - sizeof(PART_FILE_HEADER) - dwBitmapSize; - if((RemainingSize & (DEFAULT_BLOCK_SIZE - 1)) == 0 || RemainingSize == MasterSize) - { - // Attempt to load an existing file bitmap - if(PartStream_LoadBitmap(pStream)) - return true; - } - } - - // We need to create mirror stream - bNeedCreateMirrorStream = false; - } - - // Create a new stream, if needed - if(bNeedCreateMirrorStream) - { - if(!pStream->BaseCreate(pStream)) - return false; - } - - // If we need to, then resize the mirror stream - if(bNeedResizeMirrorStream) - { - if(!pStream->BaseResize(pStream, sizeof(PART_FILE_HEADER) + dwBitmapSize)) - return false; - } - - // Allocate the bitmap array - FileBitmap = STORM_ALLOC(BYTE, dwBitmapSize); - if(FileBitmap == NULL) - return false; - - // Initialize the bitmap - memset(FileBitmap, 0, dwBitmapSize); - pStream->FileBitmap = FileBitmap; - pStream->BitmapSize = dwBitmapSize; - pStream->BlockSize = DEFAULT_BLOCK_SIZE; - pStream->BlockCount = dwBlockCount; - pStream->IsComplete = 0; - pStream->IsModified = 1; - - // Note: Don't write the stream bitmap right away. - // Doing so would cause sparse file resize on NTFS, - // which would take long time on larger files. - return true; -} - - -static TFileStream * PartStream_Open(const TCHAR * szFileName, DWORD dwStreamFlags) -{ - TBlockStream * pStream; - - // Create new empty stream - pStream = (TBlockStream *)AllocateFileStream(szFileName, sizeof(TBlockStream), dwStreamFlags); - if(pStream == NULL) - return NULL; - - // Do we have a master stream? - if(pStream->pMaster != NULL) - { - if(!PartStream_CreateMirror(pStream)) - { - FileStream_Close(pStream); - SetLastError(ERROR_FILE_NOT_FOUND); - return NULL; - } - } - else - { - // Attempt to open the base stream - if(!pStream->BaseOpen(pStream, pStream->szFileName, dwStreamFlags)) - { - FileStream_Close(pStream); - return NULL; - } - - // Load the part stream block map - if(!PartStream_LoadBitmap(pStream)) - { - FileStream_Close(pStream); - SetLastError(ERROR_BAD_FORMAT); - return NULL; - } - } - - // Set the stream position to zero. Stream size is already set - assert(pStream->StreamSize != 0); - pStream->StreamPos = 0; - pStream->dwFlags |= STREAM_FLAG_READ_ONLY; - - // Set new function pointers - pStream->StreamRead = (STREAM_READ)BlockStream_Read; - pStream->StreamGetPos = BlockStream_GetPos; - pStream->StreamGetSize = BlockStream_GetSize; - pStream->StreamClose = (STREAM_CLOSE)PartStream_Close; - - // Supply the block functions - pStream->BlockCheck = (BLOCK_CHECK)PartStream_BlockCheck; - pStream->BlockRead = (BLOCK_READ)PartStream_BlockRead; - return pStream; -} - -//----------------------------------------------------------------------------- -// Local functions - MPQE stream support - -static const char * szKeyTemplate = "expand 32-byte k000000000000000000000000000000000000000000000000"; - -static const char * AuthCodeArray[] = -{ - // Starcraft II (Heart of the Swarm) - // Authentication code URL: http://dist.blizzard.com/mediakey/hots-authenticationcode-bgdl.txt - // -0C- -1C--08- -18--04- -14--00- -10- - "S48B6CDTN5XEQAKQDJNDLJBJ73FDFM3U", // SC2 Heart of the Swarm-all : "expand 32-byte kQAKQ0000FM3UN5XE000073FD6CDT0000LJBJS48B0000DJND" - - // Diablo III: Agent.exe (1.0.0.954) - // Address of decryption routine: 00502b00 - // Pointer to decryptor object: ECX - // Pointer to key: ECX+0x5C - // Authentication code URL: http://dist.blizzard.com/mediakey/d3-authenticationcode-enGB.txt - // -0C- -1C--08- -18--04- -14--00- -10- - "UCMXF6EJY352EFH4XFRXCFH2XC9MQRZK", // Diablo III Installer (deDE): "expand 32-byte kEFH40000QRZKY3520000XC9MF6EJ0000CFH2UCMX0000XFRX" - "MMKVHY48RP7WXP4GHYBQ7SL9J9UNPHBP", // Diablo III Installer (enGB): "expand 32-byte kXP4G0000PHBPRP7W0000J9UNHY4800007SL9MMKV0000HYBQ" - "8MXLWHQ7VGGLTZ9MQZQSFDCLJYET3CPP", // Diablo III Installer (enSG): "expand 32-byte kTZ9M00003CPPVGGL0000JYETWHQ70000FDCL8MXL0000QZQS" - "EJ2R5TM6XFE2GUNG5QDGHKQ9UAKPWZSZ", // Diablo III Installer (enUS): "expand 32-byte kGUNG0000WZSZXFE20000UAKP5TM60000HKQ9EJ2R00005QDG" - "PBGFBE42Z6LNK65UGJQ3WZVMCLP4HQQT", // Diablo III Installer (esES): "expand 32-byte kK65U0000HQQTZ6LN0000CLP4BE420000WZVMPBGF0000GJQ3" - "X7SEJJS9TSGCW5P28EBSC47AJPEY8VU2", // Diablo III Installer (esMX): "expand 32-byte kW5P200008VU2TSGC0000JPEYJJS90000C47AX7SE00008EBS" - "5KVBQA8VYE6XRY3DLGC5ZDE4XS4P7YA2", // Diablo III Installer (frFR): "expand 32-byte kRY3D00007YA2YE6X0000XS4PQA8V0000ZDE45KVB0000LGC5" - "478JD2K56EVNVVY4XX8TDWYT5B8KB254", // Diablo III Installer (itIT): "expand 32-byte kVVY40000B2546EVN00005B8KD2K50000DWYT478J0000XX8T" - "8TS4VNFQRZTN6YWHE9CHVDH9NVWD474A", // Diablo III Installer (koKR): "expand 32-byte k6YWH0000474ARZTN0000NVWDVNFQ0000VDH98TS40000E9CH" - "LJ52Z32DF4LZ4ZJJXVKK3AZQA6GABLJB", // Diablo III Installer (plPL): "expand 32-byte k4ZJJ0000BLJBF4LZ0000A6GAZ32D00003AZQLJ520000XVKK" - "K6BDHY2ECUE2545YKNLBJPVYWHE7XYAG", // Diablo III Installer (ptBR): "expand 32-byte k545Y0000XYAGCUE20000WHE7HY2E0000JPVYK6BD0000KNLB" - "NDVW8GWLAYCRPGRNY8RT7ZZUQU63VLPR", // Diablo III Installer (ruRU): "expand 32-byte kXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX" - "6VWCQTN8V3ZZMRUCZXV8A8CGUX2TAA8H", // Diablo III Installer (zhTW): "expand 32-byte kMRUC0000AA8HV3ZZ0000UX2TQTN80000A8CG6VWC0000ZXV8" -// "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX", // Diablo III Installer (zhCN): "expand 32-byte kXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX" - - // Starcraft II (Wings of Liberty): Installer.exe (4.1.1.4219) - // Address of decryption routine: 0053A3D0 - // Pointer to decryptor object: ECX - // Pointer to key: ECX+0x5C - // Authentication code URL: http://dist.blizzard.com/mediakey/sc2-authenticationcode-enUS.txt - // -0C- -1C--08- -18--04- -14--00- -10- - "Y45MD3CAK4KXSSXHYD9VY64Z8EKJ4XFX", // SC2 Wings of Liberty (deDE): "expand 32-byte kSSXH00004XFXK4KX00008EKJD3CA0000Y64ZY45M0000YD9V" - "G8MN8UDG6NA2ANGY6A3DNY82HRGF29ZH", // SC2 Wings of Liberty (enGB): "expand 32-byte kANGY000029ZH6NA20000HRGF8UDG0000NY82G8MN00006A3D" - "W9RRHLB2FDU9WW5B3ECEBLRSFWZSF7HW", // SC2 Wings of Liberty (enSG): "expand 32-byte kWW5B0000F7HWFDU90000FWZSHLB20000BLRSW9RR00003ECE" - "3DH5RE5NVM5GTFD85LXGWT6FK859ETR5", // SC2 Wings of Liberty (enUS): "expand 32-byte kTFD80000ETR5VM5G0000K859RE5N0000WT6F3DH500005LXG" - "8WLKUAXE94PFQU4Y249PAZ24N4R4XKTQ", // SC2 Wings of Liberty (esES): "expand 32-byte kQU4Y0000XKTQ94PF0000N4R4UAXE0000AZ248WLK0000249P" - "A34DXX3VHGGXSQBRFE5UFFDXMF9G4G54", // SC2 Wings of Liberty (esMX): "expand 32-byte kSQBR00004G54HGGX0000MF9GXX3V0000FFDXA34D0000FE5U" - "ZG7J9K938HJEFWPQUA768MA2PFER6EAJ", // SC2 Wings of Liberty (frFR): "expand 32-byte kFWPQ00006EAJ8HJE0000PFER9K9300008MA2ZG7J0000UA76" - "NE7CUNNNTVAPXV7E3G2BSVBWGVMW8BL2", // SC2 Wings of Liberty (itIT): "expand 32-byte kXV7E00008BL2TVAP0000GVMWUNNN0000SVBWNE7C00003G2B" - "3V9E2FTMBM9QQWK7U6MAMWAZWQDB838F", // SC2 Wings of Liberty (koKR): "expand 32-byte kQWK70000838FBM9Q0000WQDB2FTM0000MWAZ3V9E0000U6MA" - "2NSFB8MELULJ83U6YHA3UP6K4MQD48L6", // SC2 Wings of Liberty (plPL): "expand 32-byte k83U6000048L6LULJ00004MQDB8ME0000UP6K2NSF0000YHA3" - "QA2TZ9EWZ4CUU8BMB5WXCTY65F9CSW4E", // SC2 Wings of Liberty (ptBR): "expand 32-byte kU8BM0000SW4EZ4CU00005F9CZ9EW0000CTY6QA2T0000B5WX" - "VHB378W64BAT9SH7D68VV9NLQDK9YEGT", // SC2 Wings of Liberty (ruRU): "expand 32-byte k9SH70000YEGT4BAT0000QDK978W60000V9NLVHB30000D68V" - "U3NFQJV4M6GC7KBN9XQJ3BRDN3PLD9NE", // SC2 Wings of Liberty (zhTW): "expand 32-byte k7KBN0000D9NEM6GC0000N3PLQJV400003BRDU3NF00009XQJ" - - NULL -}; - -static DWORD Rol32(DWORD dwValue, DWORD dwRolCount) -{ - DWORD dwShiftRight = 32 - dwRolCount; - - return (dwValue << dwRolCount) | (dwValue >> dwShiftRight); -} - -static void CreateKeyFromAuthCode( - LPBYTE pbKeyBuffer, - const char * szAuthCode) -{ - LPDWORD KeyPosition = (LPDWORD)(pbKeyBuffer + 0x10); - LPDWORD AuthCode32 = (LPDWORD)szAuthCode; - - memcpy(pbKeyBuffer, szKeyTemplate, MPQE_CHUNK_SIZE); - KeyPosition[0x00] = AuthCode32[0x03]; - KeyPosition[0x02] = AuthCode32[0x07]; - KeyPosition[0x03] = AuthCode32[0x02]; - KeyPosition[0x05] = AuthCode32[0x06]; - KeyPosition[0x06] = AuthCode32[0x01]; - KeyPosition[0x08] = AuthCode32[0x05]; - KeyPosition[0x09] = AuthCode32[0x00]; - KeyPosition[0x0B] = AuthCode32[0x04]; - BSWAP_ARRAY32_UNSIGNED(pbKeyBuffer, MPQE_CHUNK_SIZE); -} - -static void DecryptFileChunk( - DWORD * MpqData, - LPBYTE pbKey, - ULONGLONG ByteOffset, - DWORD dwLength) -{ - ULONGLONG ChunkOffset; - DWORD KeyShuffled[0x10]; - DWORD KeyMirror[0x10]; - DWORD RoundCount = 0x14; - - // Prepare the key - ChunkOffset = ByteOffset / MPQE_CHUNK_SIZE; - memcpy(KeyMirror, pbKey, MPQE_CHUNK_SIZE); - BSWAP_ARRAY32_UNSIGNED(KeyMirror, MPQE_CHUNK_SIZE); - KeyMirror[0x05] = (DWORD)(ChunkOffset >> 32); - KeyMirror[0x08] = (DWORD)(ChunkOffset); - - while(dwLength >= MPQE_CHUNK_SIZE) - { - // Shuffle the key - part 1 - KeyShuffled[0x0E] = KeyMirror[0x00]; - KeyShuffled[0x0C] = KeyMirror[0x01]; - KeyShuffled[0x05] = KeyMirror[0x02]; - KeyShuffled[0x0F] = KeyMirror[0x03]; - KeyShuffled[0x0A] = KeyMirror[0x04]; - KeyShuffled[0x07] = KeyMirror[0x05]; - KeyShuffled[0x0B] = KeyMirror[0x06]; - KeyShuffled[0x09] = KeyMirror[0x07]; - KeyShuffled[0x03] = KeyMirror[0x08]; - KeyShuffled[0x06] = KeyMirror[0x09]; - KeyShuffled[0x08] = KeyMirror[0x0A]; - KeyShuffled[0x0D] = KeyMirror[0x0B]; - KeyShuffled[0x02] = KeyMirror[0x0C]; - KeyShuffled[0x04] = KeyMirror[0x0D]; - KeyShuffled[0x01] = KeyMirror[0x0E]; - KeyShuffled[0x00] = KeyMirror[0x0F]; - - // Shuffle the key - part 2 - for(DWORD i = 0; i < RoundCount; i += 2) - { - KeyShuffled[0x0A] = KeyShuffled[0x0A] ^ Rol32((KeyShuffled[0x0E] + KeyShuffled[0x02]), 0x07); - KeyShuffled[0x03] = KeyShuffled[0x03] ^ Rol32((KeyShuffled[0x0A] + KeyShuffled[0x0E]), 0x09); - KeyShuffled[0x02] = KeyShuffled[0x02] ^ Rol32((KeyShuffled[0x03] + KeyShuffled[0x0A]), 0x0D); - KeyShuffled[0x0E] = KeyShuffled[0x0E] ^ Rol32((KeyShuffled[0x02] + KeyShuffled[0x03]), 0x12); - - KeyShuffled[0x07] = KeyShuffled[0x07] ^ Rol32((KeyShuffled[0x0C] + KeyShuffled[0x04]), 0x07); - KeyShuffled[0x06] = KeyShuffled[0x06] ^ Rol32((KeyShuffled[0x07] + KeyShuffled[0x0C]), 0x09); - KeyShuffled[0x04] = KeyShuffled[0x04] ^ Rol32((KeyShuffled[0x06] + KeyShuffled[0x07]), 0x0D); - KeyShuffled[0x0C] = KeyShuffled[0x0C] ^ Rol32((KeyShuffled[0x04] + KeyShuffled[0x06]), 0x12); - - KeyShuffled[0x0B] = KeyShuffled[0x0B] ^ Rol32((KeyShuffled[0x05] + KeyShuffled[0x01]), 0x07); - KeyShuffled[0x08] = KeyShuffled[0x08] ^ Rol32((KeyShuffled[0x0B] + KeyShuffled[0x05]), 0x09); - KeyShuffled[0x01] = KeyShuffled[0x01] ^ Rol32((KeyShuffled[0x08] + KeyShuffled[0x0B]), 0x0D); - KeyShuffled[0x05] = KeyShuffled[0x05] ^ Rol32((KeyShuffled[0x01] + KeyShuffled[0x08]), 0x12); - - KeyShuffled[0x09] = KeyShuffled[0x09] ^ Rol32((KeyShuffled[0x0F] + KeyShuffled[0x00]), 0x07); - KeyShuffled[0x0D] = KeyShuffled[0x0D] ^ Rol32((KeyShuffled[0x09] + KeyShuffled[0x0F]), 0x09); - KeyShuffled[0x00] = KeyShuffled[0x00] ^ Rol32((KeyShuffled[0x0D] + KeyShuffled[0x09]), 0x0D); - KeyShuffled[0x0F] = KeyShuffled[0x0F] ^ Rol32((KeyShuffled[0x00] + KeyShuffled[0x0D]), 0x12); - - KeyShuffled[0x04] = KeyShuffled[0x04] ^ Rol32((KeyShuffled[0x0E] + KeyShuffled[0x09]), 0x07); - KeyShuffled[0x08] = KeyShuffled[0x08] ^ Rol32((KeyShuffled[0x04] + KeyShuffled[0x0E]), 0x09); - KeyShuffled[0x09] = KeyShuffled[0x09] ^ Rol32((KeyShuffled[0x08] + KeyShuffled[0x04]), 0x0D); - KeyShuffled[0x0E] = KeyShuffled[0x0E] ^ Rol32((KeyShuffled[0x09] + KeyShuffled[0x08]), 0x12); - - KeyShuffled[0x01] = KeyShuffled[0x01] ^ Rol32((KeyShuffled[0x0C] + KeyShuffled[0x0A]), 0x07); - KeyShuffled[0x0D] = KeyShuffled[0x0D] ^ Rol32((KeyShuffled[0x01] + KeyShuffled[0x0C]), 0x09); - KeyShuffled[0x0A] = KeyShuffled[0x0A] ^ Rol32((KeyShuffled[0x0D] + KeyShuffled[0x01]), 0x0D); - KeyShuffled[0x0C] = KeyShuffled[0x0C] ^ Rol32((KeyShuffled[0x0A] + KeyShuffled[0x0D]), 0x12); - - KeyShuffled[0x00] = KeyShuffled[0x00] ^ Rol32((KeyShuffled[0x05] + KeyShuffled[0x07]), 0x07); - KeyShuffled[0x03] = KeyShuffled[0x03] ^ Rol32((KeyShuffled[0x00] + KeyShuffled[0x05]), 0x09); - KeyShuffled[0x07] = KeyShuffled[0x07] ^ Rol32((KeyShuffled[0x03] + KeyShuffled[0x00]), 0x0D); - KeyShuffled[0x05] = KeyShuffled[0x05] ^ Rol32((KeyShuffled[0x07] + KeyShuffled[0x03]), 0x12); - - KeyShuffled[0x02] = KeyShuffled[0x02] ^ Rol32((KeyShuffled[0x0F] + KeyShuffled[0x0B]), 0x07); - KeyShuffled[0x06] = KeyShuffled[0x06] ^ Rol32((KeyShuffled[0x02] + KeyShuffled[0x0F]), 0x09); - KeyShuffled[0x0B] = KeyShuffled[0x0B] ^ Rol32((KeyShuffled[0x06] + KeyShuffled[0x02]), 0x0D); - KeyShuffled[0x0F] = KeyShuffled[0x0F] ^ Rol32((KeyShuffled[0x0B] + KeyShuffled[0x06]), 0x12); - } - - // Decrypt one data chunk - BSWAP_ARRAY32_UNSIGNED(MpqData, MPQE_CHUNK_SIZE); - MpqData[0x00] = MpqData[0x00] ^ (KeyShuffled[0x0E] + KeyMirror[0x00]); - MpqData[0x01] = MpqData[0x01] ^ (KeyShuffled[0x04] + KeyMirror[0x0D]); - MpqData[0x02] = MpqData[0x02] ^ (KeyShuffled[0x08] + KeyMirror[0x0A]); - MpqData[0x03] = MpqData[0x03] ^ (KeyShuffled[0x09] + KeyMirror[0x07]); - MpqData[0x04] = MpqData[0x04] ^ (KeyShuffled[0x0A] + KeyMirror[0x04]); - MpqData[0x05] = MpqData[0x05] ^ (KeyShuffled[0x0C] + KeyMirror[0x01]); - MpqData[0x06] = MpqData[0x06] ^ (KeyShuffled[0x01] + KeyMirror[0x0E]); - MpqData[0x07] = MpqData[0x07] ^ (KeyShuffled[0x0D] + KeyMirror[0x0B]); - MpqData[0x08] = MpqData[0x08] ^ (KeyShuffled[0x03] + KeyMirror[0x08]); - MpqData[0x09] = MpqData[0x09] ^ (KeyShuffled[0x07] + KeyMirror[0x05]); - MpqData[0x0A] = MpqData[0x0A] ^ (KeyShuffled[0x05] + KeyMirror[0x02]); - MpqData[0x0B] = MpqData[0x0B] ^ (KeyShuffled[0x00] + KeyMirror[0x0F]); - MpqData[0x0C] = MpqData[0x0C] ^ (KeyShuffled[0x02] + KeyMirror[0x0C]); - MpqData[0x0D] = MpqData[0x0D] ^ (KeyShuffled[0x06] + KeyMirror[0x09]); - MpqData[0x0E] = MpqData[0x0E] ^ (KeyShuffled[0x0B] + KeyMirror[0x06]); - MpqData[0x0F] = MpqData[0x0F] ^ (KeyShuffled[0x0F] + KeyMirror[0x03]); - BSWAP_ARRAY32_UNSIGNED(MpqData, MPQE_CHUNK_SIZE); - - // Update byte offset in the key - KeyMirror[0x08]++; - if(KeyMirror[0x08] == 0) - KeyMirror[0x05]++; - - // Move pointers and decrease number of bytes to decrypt - MpqData += (MPQE_CHUNK_SIZE / sizeof(DWORD)); - dwLength -= MPQE_CHUNK_SIZE; - } -} - -static bool MpqeStream_DetectFileKey(TEncryptedStream * pStream) -{ - ULONGLONG ByteOffset = 0; - BYTE EncryptedHeader[MPQE_CHUNK_SIZE]; - BYTE FileHeader[MPQE_CHUNK_SIZE]; - - // Read the first file chunk - if(pStream->BaseRead(pStream, &ByteOffset, EncryptedHeader, sizeof(EncryptedHeader))) - { - // We just try all known keys one by one - for(int i = 0; AuthCodeArray[i] != NULL; i++) - { - // Prepare they decryption key from game serial number - CreateKeyFromAuthCode(pStream->Key, AuthCodeArray[i]); - - // Try to decrypt with the given key - memcpy(FileHeader, EncryptedHeader, MPQE_CHUNK_SIZE); - DecryptFileChunk((LPDWORD)FileHeader, pStream->Key, ByteOffset, MPQE_CHUNK_SIZE); - - // We check the decrypted data - // All known encrypted MPQs have header at the begin of the file, - // so we check for MPQ signature there. - if(FileHeader[0] == 'M' && FileHeader[1] == 'P' && FileHeader[2] == 'Q') - { - // Update the stream size - pStream->StreamSize = pStream->Base.File.FileSize; - - // Fill the block information - pStream->BlockSize = MPQE_CHUNK_SIZE; - pStream->BlockCount = (DWORD)(pStream->Base.File.FileSize + MPQE_CHUNK_SIZE - 1) / MPQE_CHUNK_SIZE; - pStream->IsComplete = 1; - return true; - } - } - } - - // Key not found, sorry - return false; -} - -static bool MpqeStream_BlockRead( - TEncryptedStream * pStream, - ULONGLONG StartOffset, - ULONGLONG EndOffset, - LPBYTE BlockBuffer, - DWORD BytesNeeded, - bool bAvailable) -{ - DWORD dwBytesToRead; - - assert((StartOffset & (pStream->BlockSize - 1)) == 0); - assert(StartOffset < EndOffset); - assert(bAvailable != false); - BytesNeeded = BytesNeeded; - bAvailable = bAvailable; - - // Read the file from the stream as-is - // Limit the reading to number of blocks really needed - dwBytesToRead = (DWORD)(EndOffset - StartOffset); - if(!pStream->BaseRead(pStream, &StartOffset, BlockBuffer, dwBytesToRead)) - return false; - - // Decrypt the data - dwBytesToRead = (dwBytesToRead + MPQE_CHUNK_SIZE - 1) & ~(MPQE_CHUNK_SIZE - 1); - DecryptFileChunk((LPDWORD)BlockBuffer, pStream->Key, StartOffset, dwBytesToRead); - return true; -} - -static TFileStream * MpqeStream_Open(const TCHAR * szFileName, DWORD dwStreamFlags) -{ - TEncryptedStream * pStream; - - // Create new empty stream - pStream = (TEncryptedStream *)AllocateFileStream(szFileName, sizeof(TEncryptedStream), dwStreamFlags); - if(pStream == NULL) - return NULL; - - // Attempt to open the base stream - assert(pStream->BaseOpen != NULL); - if(!pStream->BaseOpen(pStream, pStream->szFileName, dwStreamFlags)) - return NULL; - - // Determine the encryption key for the MPQ - if(MpqeStream_DetectFileKey(pStream)) - { - // Set the stream position and size - assert(pStream->StreamSize != 0); - pStream->StreamPos = 0; - pStream->dwFlags |= STREAM_FLAG_READ_ONLY; - - // Set new function pointers - pStream->StreamRead = (STREAM_READ)BlockStream_Read; - pStream->StreamGetPos = BlockStream_GetPos; - pStream->StreamGetSize = BlockStream_GetSize; - pStream->StreamClose = pStream->BaseClose; - - // Supply the block functions - pStream->BlockRead = (BLOCK_READ)MpqeStream_BlockRead; - return pStream; - } - - // Cleanup the stream and return - FileStream_Close(pStream); - SetLastError(ERROR_UNKNOWN_FILE_KEY); - return NULL; -} - -//----------------------------------------------------------------------------- -// Local functions - Block4 stream support - -#define BLOCK4_BLOCK_SIZE 0x4000 // Size of one block -#define BLOCK4_HASH_SIZE 0x20 // Size of MD5 hash that is after each block -#define BLOCK4_MAX_BLOCKS 0x00002000 // Maximum amount of blocks per file -#define BLOCK4_MAX_FSIZE 0x08040000 // Max size of one file - -static bool Block4Stream_BlockRead( - TBlockStream * pStream, // Pointer to an open stream - ULONGLONG StartOffset, - ULONGLONG EndOffset, - LPBYTE BlockBuffer, - DWORD BytesNeeded, - bool bAvailable) -{ - TBaseProviderData * BaseArray = (TBaseProviderData *)pStream->FileBitmap; - ULONGLONG ByteOffset; - DWORD BytesToRead; - DWORD StreamIndex; - DWORD BlockIndex; - bool bResult; - - // The starting offset must be aligned to size of the block - assert(pStream->FileBitmap != NULL); - assert((StartOffset & (pStream->BlockSize - 1)) == 0); - assert(StartOffset < EndOffset); - assert(bAvailable == true); - - // Keep compiler happy - bAvailable = bAvailable; - EndOffset = EndOffset; - - while(BytesNeeded != 0) - { - // Calculate the block index and the file index - StreamIndex = (DWORD)((StartOffset / pStream->BlockSize) / BLOCK4_MAX_BLOCKS); - BlockIndex = (DWORD)((StartOffset / pStream->BlockSize) % BLOCK4_MAX_BLOCKS); - if(StreamIndex > pStream->BitmapSize) - return false; - - // Calculate the block offset - ByteOffset = ((ULONGLONG)BlockIndex * (BLOCK4_BLOCK_SIZE + BLOCK4_HASH_SIZE)); - BytesToRead = STORMLIB_MIN(BytesNeeded, BLOCK4_BLOCK_SIZE); - - // Read from the base stream - pStream->Base = BaseArray[StreamIndex]; - bResult = pStream->BaseRead(pStream, &ByteOffset, BlockBuffer, BytesToRead); - BaseArray[StreamIndex] = pStream->Base; - - // Did the result succeed? - if(bResult == false) - return false; - - // Move pointers - StartOffset += BytesToRead; - BlockBuffer += BytesToRead; - BytesNeeded -= BytesToRead; - } - - return true; -} - - -static void Block4Stream_Close(TBlockStream * pStream) -{ - TBaseProviderData * BaseArray = (TBaseProviderData *)pStream->FileBitmap; - - // If we have a non-zero count of base streams, - // we have to close them all - if(BaseArray != NULL) - { - // Close all base streams - for(DWORD i = 0; i < pStream->BitmapSize; i++) - { - memcpy(&pStream->Base, BaseArray + i, sizeof(TBaseProviderData)); - pStream->BaseClose(pStream); - } - } - - // Free the data map, if any - if(pStream->FileBitmap != NULL) - STORM_FREE(pStream->FileBitmap); - pStream->FileBitmap = NULL; - - // Do not call the BaseClose function, - // we closed all handles already - return; -} - -static TFileStream * Block4Stream_Open(const TCHAR * szFileName, DWORD dwStreamFlags) -{ - TBaseProviderData * NewBaseArray = NULL; - ULONGLONG RemainderBlock; - ULONGLONG BlockCount; - ULONGLONG FileSize; - TBlockStream * pStream; - TCHAR * szNameBuff; - size_t nNameLength; - DWORD dwBaseFiles = 0; - DWORD dwBaseFlags; - - // Create new empty stream - pStream = (TBlockStream *)AllocateFileStream(szFileName, sizeof(TBlockStream), dwStreamFlags); - if(pStream == NULL) - return NULL; - - // Sanity check - assert(pStream->BaseOpen != NULL); - - // Get the length of the file name without numeric suffix - nNameLength = _tcslen(pStream->szFileName); - if(pStream->szFileName[nNameLength - 2] == '.' && pStream->szFileName[nNameLength - 1] == '0') - nNameLength -= 2; - pStream->szFileName[nNameLength] = 0; - - // Supply the stream functions - pStream->StreamRead = (STREAM_READ)BlockStream_Read; - pStream->StreamGetSize = BlockStream_GetSize; - pStream->StreamGetPos = BlockStream_GetPos; - pStream->StreamClose = (STREAM_CLOSE)Block4Stream_Close; - pStream->BlockRead = (BLOCK_READ)Block4Stream_BlockRead; - - // Allocate work space for numeric names - szNameBuff = STORM_ALLOC(TCHAR, nNameLength + 4); - if(szNameBuff != NULL) - { - // Set the base flags - dwBaseFlags = (dwStreamFlags & STREAM_PROVIDERS_MASK) | STREAM_FLAG_READ_ONLY; - - // Go all suffixes from 0 to 30 - for(int nSuffix = 0; nSuffix < 30; nSuffix++) - { - // Open the n-th file - CreateNameWithSuffix(szNameBuff, nNameLength + 4, pStream->szFileName, nSuffix); - if(!pStream->BaseOpen(pStream, szNameBuff, dwBaseFlags)) - break; - - // If the open succeeded, we re-allocate the base provider array - NewBaseArray = STORM_ALLOC(TBaseProviderData, dwBaseFiles + 1); - if(NewBaseArray == NULL) - { - SetLastError(ERROR_NOT_ENOUGH_MEMORY); - return NULL; - } - - // Copy the old base data array to the new base data array - if(pStream->FileBitmap != NULL) - { - memcpy(NewBaseArray, pStream->FileBitmap, sizeof(TBaseProviderData) * dwBaseFiles); - STORM_FREE(pStream->FileBitmap); - } - - // Also copy the opened base array - memcpy(NewBaseArray + dwBaseFiles, &pStream->Base, sizeof(TBaseProviderData)); - pStream->FileBitmap = NewBaseArray; - dwBaseFiles++; - - // Get the size of the base stream - pStream->BaseGetSize(pStream, &FileSize); - assert(FileSize <= BLOCK4_MAX_FSIZE); - RemainderBlock = FileSize % (BLOCK4_BLOCK_SIZE + BLOCK4_HASH_SIZE); - BlockCount = FileSize / (BLOCK4_BLOCK_SIZE + BLOCK4_HASH_SIZE); - - // Increment the stream size and number of blocks - pStream->StreamSize += (BlockCount * BLOCK4_BLOCK_SIZE); - pStream->BlockCount += (DWORD)BlockCount; - - // Is this the last file? - if(FileSize < BLOCK4_MAX_FSIZE) - { - if(RemainderBlock) - { - pStream->StreamSize += (RemainderBlock - BLOCK4_HASH_SIZE); - pStream->BlockCount++; - } - break; - } - } - - // Fill the remainining block stream variables - pStream->BitmapSize = dwBaseFiles; - pStream->BlockSize = BLOCK4_BLOCK_SIZE; - pStream->IsComplete = 1; - pStream->IsModified = 0; - - // Fill the remaining stream variables - pStream->StreamPos = 0; - pStream->dwFlags |= STREAM_FLAG_READ_ONLY; - - STORM_FREE(szNameBuff); - } - - // If we opened something, return success - if(dwBaseFiles == 0) - { - FileStream_Close(pStream); - SetLastError(ERROR_FILE_NOT_FOUND); - pStream = NULL; - } - - return pStream; -} - -//----------------------------------------------------------------------------- -// Public functions - -/** - * This function creates a new file for read-write access - * - * - If the current platform supports file sharing, - * the file must be created for read sharing (i.e. another application - * can open the file for read, but not for write) - * - If the file does not exist, the function must create new one - * - If the file exists, the function must rewrite it and set to zero size - * - The parameters of the function must be validate by the caller - * - The function must initialize all stream function pointers in TFileStream - * - If the function fails from any reason, it must close all handles - * and free all memory that has been allocated in the process of stream creation, - * including the TFileStream structure itself - * - * \a szFileName Name of the file to create - */ - -TFileStream * FileStream_CreateFile( - const TCHAR * szFileName, - DWORD dwStreamFlags) -{ - TFileStream * pStream; - - // We only support creation of flat, local file - if((dwStreamFlags & (STREAM_PROVIDERS_MASK)) != (STREAM_PROVIDER_FLAT | BASE_PROVIDER_FILE)) - { - SetLastError(ERROR_NOT_SUPPORTED); - return NULL; - } - - // Allocate file stream structure for flat stream - pStream = AllocateFileStream(szFileName, sizeof(TBlockStream), dwStreamFlags); - if(pStream != NULL) - { - // Attempt to create the disk file - if(BaseFile_Create(pStream)) - { - // Fill the stream provider functions - pStream->StreamRead = pStream->BaseRead; - pStream->StreamWrite = pStream->BaseWrite; - pStream->StreamResize = pStream->BaseResize; - pStream->StreamGetSize = pStream->BaseGetSize; - pStream->StreamGetPos = pStream->BaseGetPos; - pStream->StreamClose = pStream->BaseClose; - return pStream; - } - - // File create failed, delete the stream - STORM_FREE(pStream); - pStream = NULL; - } - - // Return the stream - return pStream; -} - -/** - * This function opens an existing file for read or read-write access - * - If the current platform supports file sharing, - * the file must be open for read sharing (i.e. another application - * can open the file for read, but not for write) - * - If the file does not exist, the function must return NULL - * - If the file exists but cannot be open, then function must return NULL - * - The parameters of the function must be validate by the caller - * - The function must initialize all stream function pointers in TFileStream - * - If the function fails from any reason, it must close all handles - * and free all memory that has been allocated in the process of stream creation, - * including the TFileStream structure itself - * - * \a szFileName Name of the file to open - * \a dwStreamFlags specifies the provider and base storage type - */ - -TFileStream * FileStream_OpenFile( - const TCHAR * szFileName, - DWORD dwStreamFlags) -{ - DWORD dwProvider = dwStreamFlags & STREAM_PROVIDERS_MASK; - size_t nPrefixLength = FileStream_Prefix(szFileName, &dwProvider); - - // Re-assemble the stream flags - dwStreamFlags = (dwStreamFlags & STREAM_OPTIONS_MASK) | dwProvider; - szFileName += nPrefixLength; - - // Perform provider-specific open - switch(dwStreamFlags & STREAM_PROVIDER_MASK) - { - case STREAM_PROVIDER_FLAT: - return FlatStream_Open(szFileName, dwStreamFlags); - - case STREAM_PROVIDER_PARTIAL: - return PartStream_Open(szFileName, dwStreamFlags); - - case STREAM_PROVIDER_MPQE: - return MpqeStream_Open(szFileName, dwStreamFlags); - - case STREAM_PROVIDER_BLOCK4: - return Block4Stream_Open(szFileName, dwStreamFlags); - - default: - SetLastError(ERROR_INVALID_PARAMETER); - return NULL; - } -} - -/** - * Returns the file name of the stream - * - * \a pStream Pointer to an open stream - */ -const TCHAR * FileStream_GetFileName(TFileStream * pStream) -{ - assert(pStream != NULL); - return pStream->szFileName; -} - -/** - * Returns the length of the provider prefix. Returns zero if no prefix - * - * \a szFileName Pointer to a stream name (file, mapped file, URL) - * \a pdwStreamProvider Pointer to a DWORD variable that receives stream provider (STREAM_PROVIDER_XXX) - */ - -size_t FileStream_Prefix(const TCHAR * szFileName, DWORD * pdwProvider) -{ - size_t nPrefixLength1 = 0; - size_t nPrefixLength2 = 0; - DWORD dwProvider = 0; - - if(szFileName != NULL) - { - // - // Determine the stream provider - // - - if(!_tcsnicmp(szFileName, _T("flat-"), 5)) - { - dwProvider |= STREAM_PROVIDER_FLAT; - nPrefixLength1 = 5; - } - - else if(!_tcsnicmp(szFileName, _T("part-"), 5)) - { - dwProvider |= STREAM_PROVIDER_PARTIAL; - nPrefixLength1 = 5; - } - - else if(!_tcsnicmp(szFileName, _T("mpqe-"), 5)) - { - dwProvider |= STREAM_PROVIDER_MPQE; - nPrefixLength1 = 5; - } - - else if(!_tcsnicmp(szFileName, _T("blk4-"), 5)) - { - dwProvider |= STREAM_PROVIDER_BLOCK4; - nPrefixLength1 = 5; - } - - // - // Determine the base provider - // - - if(!_tcsnicmp(szFileName+nPrefixLength1, _T("file:"), 5)) - { - dwProvider |= BASE_PROVIDER_FILE; - nPrefixLength2 = 5; - } - - else if(!_tcsnicmp(szFileName+nPrefixLength1, _T("map:"), 4)) - { - dwProvider |= BASE_PROVIDER_MAP; - nPrefixLength2 = 4; - } - - else if(!_tcsnicmp(szFileName+nPrefixLength1, _T("http:"), 5)) - { - dwProvider |= BASE_PROVIDER_HTTP; - nPrefixLength2 = 5; - } - - // Only accept stream provider if we recognized the base provider - if(nPrefixLength2 != 0) - { - // It is also allowed to put "//" after the base provider, e.g. "file://", "http://" - if(szFileName[nPrefixLength1+nPrefixLength2] == '/' && szFileName[nPrefixLength1+nPrefixLength2+1] == '/') - nPrefixLength2 += 2; - - if(pdwProvider != NULL) - *pdwProvider = dwProvider; - return nPrefixLength1 + nPrefixLength2; - } - } - - return 0; -} - -/** - * Sets a download callback. Whenever the stream needs to download one or more blocks - * from the server, the callback is called - * - * \a pStream Pointer to an open stream - * \a pfnCallback Pointer to callback function - * \a pvUserData Arbitrary user pointer passed to the download callback - */ - -bool FileStream_SetCallback(TFileStream * pStream, SFILE_DOWNLOAD_CALLBACK pfnCallback, void * pvUserData) -{ - TBlockStream * pBlockStream = (TBlockStream *)pStream; - - if(pStream->BlockRead == NULL) - { - SetLastError(ERROR_NOT_SUPPORTED); - return false; - } - - pBlockStream->pfnCallback = pfnCallback; - pBlockStream->UserData = pvUserData; - return true; -} - -/** - * This function gives the block map. The 'pvBitmap' pointer must point to a buffer - * of at least sizeof(STREAM_BLOCK_MAP) size. It can also have size of the complete - * block map (i.e. sizeof(STREAM_BLOCK_MAP) + BitmapSize). In that case, the function - * also copies the bit-based block map. - * - * \a pStream Pointer to an open stream - * \a pvBitmap Pointer to buffer where the block map will be stored - * \a cbBitmap Length of the buffer, of the block map - * \a cbLengthNeeded Length of the bitmap, in bytes - */ - -bool FileStream_GetBitmap(TFileStream * pStream, void * pvBitmap, DWORD cbBitmap, DWORD * pcbLengthNeeded) -{ - TStreamBitmap * pBitmap = (TStreamBitmap *)pvBitmap; - TBlockStream * pBlockStream = (TBlockStream *)pStream; - ULONGLONG BlockOffset; - LPBYTE Bitmap = (LPBYTE)(pBitmap + 1); - DWORD BitmapSize; - DWORD BlockCount; - DWORD BlockSize; - bool bResult = false; - - // Retrieve the size of one block - if(pStream->BlockCheck != NULL) - { - BlockCount = pBlockStream->BlockCount; - BlockSize = pBlockStream->BlockSize; - } - else - { - BlockCount = (DWORD)((pStream->StreamSize + DEFAULT_BLOCK_SIZE - 1) / DEFAULT_BLOCK_SIZE); - BlockSize = DEFAULT_BLOCK_SIZE; - } - - // Fill-in the variables - BitmapSize = (BlockCount + 7) / 8; - - // Give the number of blocks - if(pcbLengthNeeded != NULL) - pcbLengthNeeded[0] = sizeof(TStreamBitmap) + BitmapSize; - - // If the length of the buffer is not enough - if(pvBitmap != NULL && cbBitmap != 0) - { - // Give the STREAM_BLOCK_MAP structure - if(cbBitmap >= sizeof(TStreamBitmap)) - { - pBitmap->StreamSize = pStream->StreamSize; - pBitmap->BitmapSize = BitmapSize; - pBitmap->BlockCount = BlockCount; - pBitmap->BlockSize = BlockSize; - pBitmap->IsComplete = (pStream->BlockCheck != NULL) ? pBlockStream->IsComplete : 1; - bResult = true; - } - - // Give the block bitmap, if enough space - if(cbBitmap >= sizeof(TStreamBitmap) + BitmapSize) - { - // Version with bitmap present - if(pStream->BlockCheck != NULL) - { - DWORD ByteIndex = 0; - BYTE BitMask = 0x01; - - // Initialize the map with zeros - memset(Bitmap, 0, BitmapSize); - - // Fill the map - for(BlockOffset = 0; BlockOffset < pStream->StreamSize; BlockOffset += BlockSize) - { - // Set the bit if the block is present - if(pBlockStream->BlockCheck(pStream, BlockOffset)) - Bitmap[ByteIndex] |= BitMask; - - // Move bit position - ByteIndex += (BitMask >> 0x07); - BitMask = (BitMask >> 0x07) | (BitMask << 0x01); - } - } - else - { - memset(Bitmap, 0xFF, BitmapSize); - } - } - } - - // Set last error value and return - if(bResult == false) - SetLastError(ERROR_INSUFFICIENT_BUFFER); - return bResult; -} - -/** - * Reads data from the stream - * - * - Returns true if the read operation succeeded and all bytes have been read - * - Returns false if either read failed or not all bytes have been read - * - If the pByteOffset is NULL, the function must read the data from the current file position - * - The function can be called with dwBytesToRead = 0. In that case, pvBuffer is ignored - * and the function just adjusts file pointer. - * - * \a pStream Pointer to an open stream - * \a pByteOffset Pointer to file byte offset. If NULL, it reads from the current position - * \a pvBuffer Pointer to data to be read - * \a dwBytesToRead Number of bytes to read from the file - * - * \returns - * - If the function reads the required amount of bytes, it returns true. - * - If the function reads less than required bytes, it returns false and GetLastError() returns ERROR_HANDLE_EOF - * - If the function fails, it reads false and GetLastError() returns an error code different from ERROR_HANDLE_EOF - */ -bool FileStream_Read(TFileStream * pStream, ULONGLONG * pByteOffset, void * pvBuffer, DWORD dwBytesToRead) -{ - assert(pStream->StreamRead != NULL); - return pStream->StreamRead(pStream, pByteOffset, pvBuffer, dwBytesToRead); -} - -/** - * This function writes data to the stream - * - * - Returns true if the write operation succeeded and all bytes have been written - * - Returns false if either write failed or not all bytes have been written - * - If the pByteOffset is NULL, the function must write the data to the current file position - * - * \a pStream Pointer to an open stream - * \a pByteOffset Pointer to file byte offset. If NULL, it reads from the current position - * \a pvBuffer Pointer to data to be written - * \a dwBytesToWrite Number of bytes to write to the file - */ -bool FileStream_Write(TFileStream * pStream, ULONGLONG * pByteOffset, const void * pvBuffer, DWORD dwBytesToWrite) -{ - if(pStream->dwFlags & STREAM_FLAG_READ_ONLY) - { - SetLastError(ERROR_ACCESS_DENIED); - return false; - } - - assert(pStream->StreamWrite != NULL); - return pStream->StreamWrite(pStream, pByteOffset, pvBuffer, dwBytesToWrite); -} - -/** - * Returns the size of a file - * - * \a pStream Pointer to an open stream - * \a FileSize Pointer where to store the file size - */ -bool FileStream_GetSize(TFileStream * pStream, ULONGLONG * pFileSize) -{ - assert(pStream->StreamGetSize != NULL); - return pStream->StreamGetSize(pStream, pFileSize); -} - -/** - * Sets the size of a file - * - * \a pStream Pointer to an open stream - * \a NewFileSize File size to set - */ -bool FileStream_SetSize(TFileStream * pStream, ULONGLONG NewFileSize) -{ - if(pStream->dwFlags & STREAM_FLAG_READ_ONLY) - { - SetLastError(ERROR_ACCESS_DENIED); - return false; - } - - assert(pStream->StreamResize != NULL); - return pStream->StreamResize(pStream, NewFileSize); -} - -/** - * This function returns the current file position - * \a pStream - * \a pByteOffset - */ -bool FileStream_GetPos(TFileStream * pStream, ULONGLONG * pByteOffset) -{ - assert(pStream->StreamGetPos != NULL); - return pStream->StreamGetPos(pStream, pByteOffset); -} - -/** - * Returns the last write time of a file - * - * \a pStream Pointer to an open stream - * \a pFileType Pointer where to store the file last write time - */ -bool FileStream_GetTime(TFileStream * pStream, ULONGLONG * pFileTime) -{ - // Just use the saved filetime value - *pFileTime = pStream->Base.File.FileTime; - return true; -} - -/** - * Returns the stream flags - * - * \a pStream Pointer to an open stream - * \a pdwStreamFlags Pointer where to store the stream flags - */ -bool FileStream_GetFlags(TFileStream * pStream, LPDWORD pdwStreamFlags) -{ - *pdwStreamFlags = pStream->dwFlags; - return true; -} - -/** - * Switches a stream with another. Used for final phase of archive compacting. - * Performs these steps: - * - * 1) Closes the handle to the existing MPQ - * 2) Renames the temporary MPQ to the original MPQ, overwrites existing one - * 3) Opens the MPQ stores the handle and stream position to the new stream structure - * - * \a pStream Pointer to an open stream - * \a pNewStream Temporary ("working") stream (created during archive compacting) - */ -bool FileStream_Replace(TFileStream * pStream, TFileStream * pNewStream) -{ - // Only supported on flat files - if((pStream->dwFlags & STREAM_PROVIDERS_MASK) != (STREAM_PROVIDER_FLAT | BASE_PROVIDER_FILE)) - { - SetLastError(ERROR_NOT_SUPPORTED); - return false; - } - - // Not supported on read-only streams - if(pStream->dwFlags & STREAM_FLAG_READ_ONLY) - { - SetLastError(ERROR_ACCESS_DENIED); - return false; - } - - // Close both stream's base providers - pNewStream->BaseClose(pNewStream); - pStream->BaseClose(pStream); - - // Now we have to delete the (now closed) old file and rename the new file - if(!BaseFile_Replace(pStream, pNewStream)) - return false; - - // Now open the base file again - if(!BaseFile_Open(pStream, pStream->szFileName, pStream->dwFlags)) - return false; - - // Cleanup the new stream - FileStream_Close(pNewStream); - return true; -} - -/** - * This function closes an archive file and frees any data buffers - * that have been allocated for stream management. The function must also - * support partially allocated structure, i.e. one or more buffers - * can be NULL, if there was an allocation failure during the process - * - * \a pStream Pointer to an open stream - */ -void FileStream_Close(TFileStream * pStream) -{ - // Check if the stream structure is allocated at all - if(pStream != NULL) - { - // Free the master stream, if any - if(pStream->pMaster != NULL) - FileStream_Close(pStream->pMaster); - pStream->pMaster = NULL; - - // Close the stream provider - if(pStream->StreamClose != NULL) - pStream->StreamClose(pStream); - - // ... or close base stream, if any - else if(pStream->BaseClose != NULL) - pStream->BaseClose(pStream); - - // Free the stream itself - STORM_FREE(pStream); - } -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/FileStream.h b/app/jni/src/libultraship/extern/StormLib/src/FileStream.h deleted file mode 100644 index 2bc118b..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/FileStream.h +++ /dev/null @@ -1,217 +0,0 @@ -/*****************************************************************************/ -/* FileStream.h Copyright (c) Ladislav Zezula 2012 */ -/*---------------------------------------------------------------------------*/ -/* Description: Definitions for FileStream object */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 14.04.12 1.00 Lad The first version of FileStream.h */ -/*****************************************************************************/ - -#ifndef __FILESTREAM_H__ -#define __FILESTREAM_H__ - -//----------------------------------------------------------------------------- -// Function prototypes - -typedef void (*STREAM_INIT)( - struct TFileStream * pStream // Pointer to an unopened stream -); - -typedef bool (*STREAM_CREATE)( - struct TFileStream * pStream // Pointer to an unopened stream - ); - -typedef bool (*STREAM_OPEN)( - struct TFileStream * pStream, // Pointer to an unopened stream - const TCHAR * szFileName, // Pointer to file name to be open - DWORD dwStreamFlags // Stream flags - ); - -typedef bool (*STREAM_READ)( - struct TFileStream * pStream, // Pointer to an open stream - ULONGLONG * pByteOffset, // Pointer to file byte offset. If NULL, it reads from the current position - void * pvBuffer, // Pointer to data to be read - DWORD dwBytesToRead // Number of bytes to read from the file - ); - -typedef bool (*STREAM_WRITE)( - struct TFileStream * pStream, // Pointer to an open stream - ULONGLONG * pByteOffset, // Pointer to file byte offset. If NULL, it writes to the current position - const void * pvBuffer, // Pointer to data to be written - DWORD dwBytesToWrite // Number of bytes to read from the file - ); - -typedef bool (*STREAM_RESIZE)( - struct TFileStream * pStream, // Pointer to an open stream - ULONGLONG FileSize // New size for the file, in bytes - ); - -typedef bool (*STREAM_GETSIZE)( - struct TFileStream * pStream, // Pointer to an open stream - ULONGLONG * pFileSize // Receives the file size, in bytes - ); - -typedef bool (*STREAM_GETPOS)( - struct TFileStream * pStream, // Pointer to an open stream - ULONGLONG * pByteOffset // Pointer to store current file position - ); - -typedef void (*STREAM_CLOSE)( - struct TFileStream * pStream // Pointer to an open stream - ); - -typedef bool (*BLOCK_READ)( - struct TFileStream * pStream, // Pointer to a block-oriented stream - ULONGLONG StartOffset, // Byte offset of start of the block array - ULONGLONG EndOffset, // End offset (either end of the block or end of the file) - LPBYTE BlockBuffer, // Pointer to block-aligned buffer - DWORD BytesNeeded, // Number of bytes that are really needed - bool bAvailable // true if the block is available - ); - -typedef bool (*BLOCK_CHECK)( - struct TFileStream * pStream, // Pointer to a block-oriented stream - ULONGLONG BlockOffset // Offset of the file to check - ); - -typedef void (*BLOCK_SAVEMAP)( - struct TFileStream * pStream // Pointer to a block-oriented stream - ); - -//----------------------------------------------------------------------------- -// Local structures - partial file structure and bitmap footer - -#define ID_FILE_BITMAP_FOOTER 0x33767470 // Signature of the file bitmap footer ('ptv3') -#define DEFAULT_BLOCK_SIZE 0x00004000 // Default size of the stream block -#define DEFAULT_BUILD_NUMBER 10958 // Build number for newly created partial MPQs - -typedef struct _PART_FILE_HEADER -{ - DWORD PartialVersion; // Always set to 2 - char GameBuildNumber[0x20]; // Minimum build number of the game that can use this MPQ - DWORD Flags; // Flags (details unknown) - DWORD FileSizeLo; // Low 32 bits of the contained file size - DWORD FileSizeHi; // High 32 bits of the contained file size - DWORD BlockSize; // Size of one file block, in bytes - -} PART_FILE_HEADER, *PPART_FILE_HEADER; - -// Structure describing the block-to-file map entry -typedef struct _PART_FILE_MAP_ENTRY -{ - DWORD Flags; // 3 = the block is present in the file - DWORD BlockOffsLo; // Low 32 bits of the block position in the file - DWORD BlockOffsHi; // High 32 bits of the block position in the file - DWORD LargeValueLo; // 64-bit value, meaning is unknown - DWORD LargeValueHi; - -} PART_FILE_MAP_ENTRY, *PPART_FILE_MAP_ENTRY; - -typedef struct _FILE_BITMAP_FOOTER -{ - DWORD Signature; // 'ptv3' (ID_FILE_BITMAP_FOOTER) - DWORD Version; // Unknown, seems to always have value of 3 (version?) - DWORD BuildNumber; // Game build number for that MPQ - DWORD MapOffsetLo; // Low 32-bits of the offset of the bit map - DWORD MapOffsetHi; // High 32-bits of the offset of the bit map - DWORD BlockSize; // Size of one block (usually 0x4000 bytes) - -} FILE_BITMAP_FOOTER, *PFILE_BITMAP_FOOTER; - -//----------------------------------------------------------------------------- -// Structure for file stream - -union TBaseProviderData -{ - struct - { - ULONGLONG FileSize; // Size of the file - ULONGLONG FilePos; // Current file position - ULONGLONG FileTime; // Last write time - HANDLE hFile; // File handle - } File; - - struct - { - ULONGLONG FileSize; // Size of the file - ULONGLONG FilePos; // Current file position - ULONGLONG FileTime; // Last write time - LPBYTE pbFile; // Pointer to mapped view - } Map; - - struct - { - ULONGLONG FileSize; // Size of the file - ULONGLONG FilePos; // Current file position - ULONGLONG FileTime; // Last write time - HANDLE hInternet; // Internet handle - HANDLE hConnect; // Connection to the internet server - } Http; -}; - -struct TFileStream -{ - // Stream provider functions - STREAM_READ StreamRead; // Pointer to stream read function for this archive. Do not use directly. - STREAM_WRITE StreamWrite; // Pointer to stream write function for this archive. Do not use directly. - STREAM_RESIZE StreamResize; // Pointer to function changing file size - STREAM_GETSIZE StreamGetSize; // Pointer to function returning file size - STREAM_GETPOS StreamGetPos; // Pointer to function that returns current file position - STREAM_CLOSE StreamClose; // Pointer to function closing the stream - - // Block-oriented functions - BLOCK_READ BlockRead; // Pointer to function reading one or more blocks - BLOCK_CHECK BlockCheck; // Pointer to function checking whether the block is present - - // Base provider functions - STREAM_CREATE BaseCreate; // Pointer to base create function - STREAM_OPEN BaseOpen; // Pointer to base open function - STREAM_READ BaseRead; // Read from the stream - STREAM_WRITE BaseWrite; // Write to the stream - STREAM_RESIZE BaseResize; // Pointer to function changing file size - STREAM_GETSIZE BaseGetSize; // Pointer to function returning file size - STREAM_GETPOS BaseGetPos; // Pointer to function that returns current file position - STREAM_CLOSE BaseClose; // Pointer to function closing the stream - - // Base provider data (file size, file position) - TBaseProviderData Base; - - // Stream provider data - TFileStream * pMaster; // Master stream (e.g. MPQ on a web server) - TCHAR * szFileName; // File name (self-relative pointer) - - ULONGLONG StreamSize; // Stream size (can be less than file size) - ULONGLONG StreamPos; // Stream position - DWORD BuildNumber; // Game build number - DWORD dwFlags; // Stream flags - - // Followed by stream provider data, with variable length -}; - -//----------------------------------------------------------------------------- -// Structures for block-oriented stream - -struct TBlockStream : public TFileStream -{ - SFILE_DOWNLOAD_CALLBACK pfnCallback; // Callback for downloading - void * FileBitmap; // Array of bits for file blocks - void * UserData; // User data to be passed to the download callback - DWORD BitmapSize; // Size of the file bitmap (in bytes) - DWORD BlockSize; // Size of one block, in bytes - DWORD BlockCount; // Number of data blocks in the file - DWORD IsComplete; // If nonzero, no blocks are missing - DWORD IsModified; // nonzero if the bitmap has been modified -}; - -//----------------------------------------------------------------------------- -// Structure for encrypted stream - -#define MPQE_CHUNK_SIZE 0x40 // Size of one chunk to be decrypted - -struct TEncryptedStream : public TBlockStream -{ - BYTE Key[MPQE_CHUNK_SIZE]; // File key -}; - -#endif // __FILESTREAM_H__ diff --git a/app/jni/src/libultraship/extern/StormLib/src/SBaseCommon.cpp b/app/jni/src/libultraship/extern/StormLib/src/SBaseCommon.cpp deleted file mode 100644 index 6fed00e..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/SBaseCommon.cpp +++ /dev/null @@ -1,1970 +0,0 @@ -/*****************************************************************************/ -/* SBaseCommon.cpp Copyright (c) Ladislav Zezula 2003 */ -/*---------------------------------------------------------------------------*/ -/* Common functions for StormLib, used by all SFile*** modules */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 24.03.03 1.00 Lad The first version of SFileCommon.cpp */ -/* 19.11.03 1.01 Dan Big endian handling */ -/* 12.06.04 1.01 Lad Renamed to SCommon.cpp */ -/* 06.09.10 1.01 Lad Renamed to SBaseCommon.cpp */ -/*****************************************************************************/ - -#define __STORMLIB_SELF__ -#include "StormLib.h" -#include "StormCommon.h" - -char StormLibCopyright[] = "StormLib v " STORMLIB_VERSION_STRING " Copyright Ladislav Zezula 1998-2014"; - -//----------------------------------------------------------------------------- -// Local variables - -DWORD g_dwMpqSignature = ID_MPQ; // Marker for MPQ header -DWORD g_dwHashTableKey = MPQ_KEY_HASH_TABLE; // Key for hash table -DWORD g_dwBlockTableKey = MPQ_KEY_BLOCK_TABLE; // Key for block table -LCID g_lcFileLocale = 0; // Compound of file locale and platform - -//----------------------------------------------------------------------------- -// Conversion to uppercase/lowercase - -// Converts ASCII characters to lowercase -// Converts slash (0x2F) to backslash (0x5C) -unsigned char AsciiToLowerTable[256] = -{ - 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F, - 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1A, 0x1B, 0x1C, 0x1D, 0x1E, 0x1F, - 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2A, 0x2B, 0x2C, 0x2D, 0x2E, 0x5C, - 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39, 0x3A, 0x3B, 0x3C, 0x3D, 0x3E, 0x3F, - 0x40, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67, 0x68, 0x69, 0x6A, 0x6B, 0x6C, 0x6D, 0x6E, 0x6F, - 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77, 0x78, 0x79, 0x7A, 0x5B, 0x5C, 0x5D, 0x5E, 0x5F, - 0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67, 0x68, 0x69, 0x6A, 0x6B, 0x6C, 0x6D, 0x6E, 0x6F, - 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77, 0x78, 0x79, 0x7A, 0x7B, 0x7C, 0x7D, 0x7E, 0x7F, - 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87, 0x88, 0x89, 0x8A, 0x8B, 0x8C, 0x8D, 0x8E, 0x8F, - 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97, 0x98, 0x99, 0x9A, 0x9B, 0x9C, 0x9D, 0x9E, 0x9F, - 0xA0, 0xA1, 0xA2, 0xA3, 0xA4, 0xA5, 0xA6, 0xA7, 0xA8, 0xA9, 0xAA, 0xAB, 0xAC, 0xAD, 0xAE, 0xAF, - 0xB0, 0xB1, 0xB2, 0xB3, 0xB4, 0xB5, 0xB6, 0xB7, 0xB8, 0xB9, 0xBA, 0xBB, 0xBC, 0xBD, 0xBE, 0xBF, - 0xC0, 0xC1, 0xC2, 0xC3, 0xC4, 0xC5, 0xC6, 0xC7, 0xC8, 0xC9, 0xCA, 0xCB, 0xCC, 0xCD, 0xCE, 0xCF, - 0xD0, 0xD1, 0xD2, 0xD3, 0xD4, 0xD5, 0xD6, 0xD7, 0xD8, 0xD9, 0xDA, 0xDB, 0xDC, 0xDD, 0xDE, 0xDF, - 0xE0, 0xE1, 0xE2, 0xE3, 0xE4, 0xE5, 0xE6, 0xE7, 0xE8, 0xE9, 0xEA, 0xEB, 0xEC, 0xED, 0xEE, 0xEF, - 0xF0, 0xF1, 0xF2, 0xF3, 0xF4, 0xF5, 0xF6, 0xF7, 0xF8, 0xF9, 0xFA, 0xFB, 0xFC, 0xFD, 0xFE, 0xFF -}; - -// Converts ASCII characters to uppercase -// Converts slash (0x2F) to backslash (0x5C) -unsigned char AsciiToUpperTable[256] = -{ - 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F, - 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1A, 0x1B, 0x1C, 0x1D, 0x1E, 0x1F, - 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2A, 0x2B, 0x2C, 0x2D, 0x2E, 0x5C, - 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39, 0x3A, 0x3B, 0x3C, 0x3D, 0x3E, 0x3F, - 0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47, 0x48, 0x49, 0x4A, 0x4B, 0x4C, 0x4D, 0x4E, 0x4F, - 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57, 0x58, 0x59, 0x5A, 0x5B, 0x5C, 0x5D, 0x5E, 0x5F, - 0x60, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47, 0x48, 0x49, 0x4A, 0x4B, 0x4C, 0x4D, 0x4E, 0x4F, - 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57, 0x58, 0x59, 0x5A, 0x7B, 0x7C, 0x7D, 0x7E, 0x7F, - 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87, 0x88, 0x89, 0x8A, 0x8B, 0x8C, 0x8D, 0x8E, 0x8F, - 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97, 0x98, 0x99, 0x9A, 0x9B, 0x9C, 0x9D, 0x9E, 0x9F, - 0xA0, 0xA1, 0xA2, 0xA3, 0xA4, 0xA5, 0xA6, 0xA7, 0xA8, 0xA9, 0xAA, 0xAB, 0xAC, 0xAD, 0xAE, 0xAF, - 0xB0, 0xB1, 0xB2, 0xB3, 0xB4, 0xB5, 0xB6, 0xB7, 0xB8, 0xB9, 0xBA, 0xBB, 0xBC, 0xBD, 0xBE, 0xBF, - 0xC0, 0xC1, 0xC2, 0xC3, 0xC4, 0xC5, 0xC6, 0xC7, 0xC8, 0xC9, 0xCA, 0xCB, 0xCC, 0xCD, 0xCE, 0xCF, - 0xD0, 0xD1, 0xD2, 0xD3, 0xD4, 0xD5, 0xD6, 0xD7, 0xD8, 0xD9, 0xDA, 0xDB, 0xDC, 0xDD, 0xDE, 0xDF, - 0xE0, 0xE1, 0xE2, 0xE3, 0xE4, 0xE5, 0xE6, 0xE7, 0xE8, 0xE9, 0xEA, 0xEB, 0xEC, 0xED, 0xEE, 0xEF, - 0xF0, 0xF1, 0xF2, 0xF3, 0xF4, 0xF5, 0xF6, 0xF7, 0xF8, 0xF9, 0xFA, 0xFB, 0xFC, 0xFD, 0xFE, 0xFF -}; - -// Converts ASCII characters to uppercase -// Does NOT convert slash (0x2F) to backslash (0x5C) -unsigned char AsciiToUpperTable_Slash[256] = -{ - 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F, - 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1A, 0x1B, 0x1C, 0x1D, 0x1E, 0x1F, - 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2A, 0x2B, 0x2C, 0x2D, 0x2E, 0x2F, - 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39, 0x3A, 0x3B, 0x3C, 0x3D, 0x3E, 0x3F, - 0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47, 0x48, 0x49, 0x4A, 0x4B, 0x4C, 0x4D, 0x4E, 0x4F, - 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57, 0x58, 0x59, 0x5A, 0x5B, 0x5C, 0x5D, 0x5E, 0x5F, - 0x60, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47, 0x48, 0x49, 0x4A, 0x4B, 0x4C, 0x4D, 0x4E, 0x4F, - 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57, 0x58, 0x59, 0x5A, 0x7B, 0x7C, 0x7D, 0x7E, 0x7F, - 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87, 0x88, 0x89, 0x8A, 0x8B, 0x8C, 0x8D, 0x8E, 0x8F, - 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97, 0x98, 0x99, 0x9A, 0x9B, 0x9C, 0x9D, 0x9E, 0x9F, - 0xA0, 0xA1, 0xA2, 0xA3, 0xA4, 0xA5, 0xA6, 0xA7, 0xA8, 0xA9, 0xAA, 0xAB, 0xAC, 0xAD, 0xAE, 0xAF, - 0xB0, 0xB1, 0xB2, 0xB3, 0xB4, 0xB5, 0xB6, 0xB7, 0xB8, 0xB9, 0xBA, 0xBB, 0xBC, 0xBD, 0xBE, 0xBF, - 0xC0, 0xC1, 0xC2, 0xC3, 0xC4, 0xC5, 0xC6, 0xC7, 0xC8, 0xC9, 0xCA, 0xCB, 0xCC, 0xCD, 0xCE, 0xCF, - 0xD0, 0xD1, 0xD2, 0xD3, 0xD4, 0xD5, 0xD6, 0xD7, 0xD8, 0xD9, 0xDA, 0xDB, 0xDC, 0xDD, 0xDE, 0xDF, - 0xE0, 0xE1, 0xE2, 0xE3, 0xE4, 0xE5, 0xE6, 0xE7, 0xE8, 0xE9, 0xEA, 0xEB, 0xEC, 0xED, 0xEE, 0xEF, - 0xF0, 0xF1, 0xF2, 0xF3, 0xF4, 0xF5, 0xF6, 0xF7, 0xF8, 0xF9, 0xFA, 0xFB, 0xFC, 0xFD, 0xFE, 0xFF -}; - -//----------------------------------------------------------------------------- -// Safe string functions (for ANSI builds) - -char * StringCopy(char * szTarget, size_t cchTarget, const char * szSource) -{ - size_t cchSource = 0; - - if(cchTarget > 0) - { - cchSource = strlen(szSource); - - if(cchSource >= cchTarget) - cchSource = cchTarget - 1; - - memcpy(szTarget, szSource, cchSource); - szTarget[cchSource] = 0; - } - - return szTarget + cchSource; -} - -void StringCat(char * szTarget, size_t cchTargetMax, const char * szSource) -{ - // Get the current length of the target - size_t cchTarget = strlen(szTarget); - - // Copy the string to the target - if(cchTarget < cchTargetMax) - { - StringCopy(szTarget + cchTarget, (cchTargetMax - cchTarget), szSource); - } -} - -void StringCreatePseudoFileName(char * szBuffer, size_t cchMaxChars, unsigned int nIndex, const char * szExtension) -{ - char * szBufferEnd = szBuffer + cchMaxChars; - - // "File" - szBuffer = StringCopy(szBuffer, (szBufferEnd - szBuffer), "File"); - - // Number - szBuffer = IntToString(szBuffer, szBufferEnd - szBuffer + 1, nIndex, 8); - - // Dot - if(szBuffer < szBufferEnd) - *szBuffer++ = '.'; - - // Extension - while(szExtension[0] == '.') - szExtension++; - StringCopy(szBuffer, (szBufferEnd - szBuffer), szExtension); -} - -//----------------------------------------------------------------------------- -// Utility functions (UNICODE) only exist in the ANSI version of the library -// In ANSI builds, TCHAR = char, so we don't need these functions implemented - -#ifdef _UNICODE -void StringCopy(TCHAR * szTarget, size_t cchTarget, const char * szSource) -{ - if(cchTarget > 0) - { - size_t cchSource = strlen(szSource); - - if(cchSource >= cchTarget) - cchSource = cchTarget - 1; - - mbstowcs(szTarget, szSource, cchSource); - szTarget[cchSource] = 0; - } -} - -void StringCopy(char * szTarget, size_t cchTarget, const TCHAR * szSource) -{ - if(cchTarget > 0) - { - size_t cchSource = _tcslen(szSource); - - if(cchSource >= cchTarget) - cchSource = cchTarget - 1; - - wcstombs(szTarget, szSource, cchSource); - szTarget[cchSource] = 0; - } -} - -void StringCopy(TCHAR * szTarget, size_t cchTarget, const TCHAR * szSource) -{ - if(cchTarget > 0) - { - size_t cchSource = _tcslen(szSource); - - if(cchSource >= cchTarget) - cchSource = cchTarget - 1; - - memcpy(szTarget, szSource, cchSource * sizeof(TCHAR)); - szTarget[cchSource] = 0; - } -} - -void StringCat(TCHAR * szTarget, size_t cchTargetMax, const TCHAR * szSource) -{ - // Get the current length of the target - size_t cchTarget = _tcslen(szTarget); - - // Copy the string to the target - if(cchTarget < cchTargetMax) - { - StringCopy(szTarget + cchTarget, (cchTargetMax - cchTarget), szSource); - } -} -#endif - -//----------------------------------------------------------------------------- -// Storm hashing functions - -#define STORM_BUFFER_SIZE 0x500 -#define HASH_INDEX_MASK(ha) (ha->pHeader->dwHashTableSize ? (ha->pHeader->dwHashTableSize - 1) : 0) - -static DWORD StormBuffer[STORM_BUFFER_SIZE]; // Buffer for the decryption engine -static bool bMpqCryptographyInitialized = false; - -void InitializeMpqCryptography() -{ - DWORD dwSeed = 0x00100001; - DWORD index1 = 0; - DWORD index2 = 0; - int i; - - // Initialize the decryption buffer. - // Do nothing if already done. - if(bMpqCryptographyInitialized == false) - { - for(index1 = 0; index1 < 0x100; index1++) - { - for(index2 = index1, i = 0; i < 5; i++, index2 += 0x100) - { - DWORD temp1, temp2; - - dwSeed = (dwSeed * 125 + 3) % 0x2AAAAB; - temp1 = (dwSeed & 0xFFFF) << 0x10; - - dwSeed = (dwSeed * 125 + 3) % 0x2AAAAB; - temp2 = (dwSeed & 0xFFFF); - - StormBuffer[index2] = (temp1 | temp2); - } - } - - // Also register both MD5 and SHA1 hash algorithms - register_hash(&md5_desc); - register_hash(&sha1_desc); - - // Use LibTomMath as support math library for LibTomCrypt - ltc_mp = ltm_desc; - - // Don't do that again - bMpqCryptographyInitialized = true; - } -} - -// -// Note: Implementation of this function in WorldEdit.exe and storm.dll -// incorrectly treats the character as signed, which leads to the -// a buffer underflow if the character in the file name >= 0x80: -// The following steps happen when *pbKey == 0xBF and dwHashType == 0x0000 -// (calculating hash index) -// -// 1) Result of AsciiToUpperTable_Slash[*pbKey++] is sign-extended to 0xffffffbf -// 2) The "ch" is added to dwHashType (0xffffffbf + 0x0000 => 0xffffffbf) -// 3) The result is used as index to the StormBuffer table, -// thus dereferences a random value BEFORE the begin of StormBuffer. -// -// As result, MPQs containing files with non-ANSI characters will not work between -// various game versions and localizations. Even WorldEdit, after importing a file -// with Korean characters in the name, cannot open the file back. -// -DWORD HashString(const char * szFileName, DWORD dwHashType) -{ - LPBYTE pbKey = (BYTE *)szFileName; - DWORD dwSeed1 = 0x7FED7FED; - DWORD dwSeed2 = 0xEEEEEEEE; - DWORD ch; - - while(*pbKey != 0) - { - // Convert the input character to uppercase - // Convert slash (0x2F) to backslash (0x5C) - ch = AsciiToUpperTable[*pbKey++]; - - dwSeed1 = StormBuffer[dwHashType + ch] ^ (dwSeed1 + dwSeed2); - dwSeed2 = ch + dwSeed1 + dwSeed2 + (dwSeed2 << 5) + 3; - } - - return dwSeed1; -} - -DWORD HashStringSlash(const char * szFileName, DWORD dwHashType) -{ - LPBYTE pbKey = (BYTE *)szFileName; - DWORD dwSeed1 = 0x7FED7FED; - DWORD dwSeed2 = 0xEEEEEEEE; - DWORD ch; - - while(*pbKey != 0) - { - // Convert the input character to uppercase - // DON'T convert slash (0x2F) to backslash (0x5C) - ch = AsciiToUpperTable_Slash[*pbKey++]; - - dwSeed1 = StormBuffer[dwHashType + ch] ^ (dwSeed1 + dwSeed2); - dwSeed2 = ch + dwSeed1 + dwSeed2 + (dwSeed2 << 5) + 3; - } - - return dwSeed1; -} - -DWORD HashStringLower(const char * szFileName, DWORD dwHashType) -{ - LPBYTE pbKey = (BYTE *)szFileName; - DWORD dwSeed1 = 0x7FED7FED; - DWORD dwSeed2 = 0xEEEEEEEE; - DWORD ch; - - while(*pbKey != 0) - { - // Convert the input character to lower - // DON'T convert slash (0x2F) to backslash (0x5C) - ch = AsciiToLowerTable[*pbKey++]; - - dwSeed1 = StormBuffer[dwHashType + ch] ^ (dwSeed1 + dwSeed2); - dwSeed2 = ch + dwSeed1 + dwSeed2 + (dwSeed2 << 5) + 3; - } - - return dwSeed1; -} - -//----------------------------------------------------------------------------- -// Calculates the hash table size for a given amount of files - -// Returns the nearest higher power of two. -// If the value is already a power of two, returns the same value -DWORD GetNearestPowerOfTwo(DWORD dwFileCount) -{ - dwFileCount --; - - dwFileCount |= dwFileCount >> 1; - dwFileCount |= dwFileCount >> 2; - dwFileCount |= dwFileCount >> 4; - dwFileCount |= dwFileCount >> 8; - dwFileCount |= dwFileCount >> 16; - - return dwFileCount + 1; -} -/* -DWORD GetNearestPowerOfTwo(DWORD dwFileCount) -{ - DWORD dwPowerOfTwo = HASH_TABLE_SIZE_MIN; - - // For zero files, there is no hash table needed - if(dwFileCount == 0) - return 0; - - // Round the hash table size up to the nearest power of two - // Don't allow the hash table size go over allowed maximum - while(dwPowerOfTwo < HASH_TABLE_SIZE_MAX && dwPowerOfTwo < dwFileCount) - dwPowerOfTwo <<= 1; - return dwPowerOfTwo; -} -*/ -//----------------------------------------------------------------------------- -// Calculates a Jenkin's Encrypting and decrypting MPQ file data - -ULONGLONG HashStringJenkins(const char * szFileName) -{ - LPBYTE pbFileName = (LPBYTE)szFileName; - char szNameBuff[0x108]; - size_t nLength = 0; - unsigned int primary_hash = 1; - unsigned int secondary_hash = 2; - - // Normalize the file name - convert to uppercase, and convert "/" to "\\". - if(pbFileName != NULL) - { - char * szNamePtr = szNameBuff; - char * szNameEnd = szNamePtr + sizeof(szNameBuff); - - // Normalize the file name. Doesn't have to be zero terminated for hashing - while(szNamePtr < szNameEnd && pbFileName[0] != 0) - *szNamePtr++ = (char)AsciiToLowerTable[*pbFileName++]; - nLength = szNamePtr - szNameBuff; - } - - // Thanks Quantam for finding out what the algorithm is. - // I am really getting old for reversing large chunks of assembly - // that does hashing :-) - hashlittle2(szNameBuff, nLength, &secondary_hash, &primary_hash); - - // Combine those 2 together - return ((ULONGLONG)primary_hash << 0x20) | (ULONGLONG)secondary_hash; -} - -//----------------------------------------------------------------------------- -// Default flags for (attributes) and (listfile) - -DWORD GetDefaultSpecialFileFlags(DWORD dwFileSize, USHORT wFormatVersion) -{ - // Fixed for format 1.0 - if(wFormatVersion == MPQ_FORMAT_VERSION_1) - return MPQ_FILE_COMPRESS | MPQ_FILE_ENCRYPTED | MPQ_FILE_FIX_KEY; - - // Size-dependent for formats 2.0-4.0 - return (dwFileSize > 0x4000) ? (MPQ_FILE_COMPRESS | MPQ_FILE_SECTOR_CRC) : (MPQ_FILE_COMPRESS | MPQ_FILE_SINGLE_UNIT); -} - - -//----------------------------------------------------------------------------- -// Encrypting/Decrypting MPQ data block - -static DWORD EncryptUInt32Unaligned(LPDWORD DataPointer, DWORD i, DWORD dwXorKey) -{ - LPBYTE pbDataPointer = (LPBYTE)(DataPointer + i); - LPBYTE pbXorKey = (LPBYTE)(&dwXorKey); - DWORD dwValue32; - - // Retrieve the value - dwValue32 = ((DWORD)pbDataPointer[0] << 0x00) | - ((DWORD)pbDataPointer[1] << 0x08) | - ((DWORD)pbDataPointer[2] << 0x10) | - ((DWORD)pbDataPointer[3] << 0x18); - - // Perform unaligned XOR - pbDataPointer[0] = (pbDataPointer[0] ^ pbXorKey[0]); - pbDataPointer[1] = (pbDataPointer[1] ^ pbXorKey[1]); - pbDataPointer[2] = (pbDataPointer[2] ^ pbXorKey[2]); - pbDataPointer[3] = (pbDataPointer[3] ^ pbXorKey[3]); - return dwValue32; -} - -void EncryptMpqBlock(void * pvDataBlock, DWORD dwLength, DWORD dwKey1) -{ - LPDWORD DataPointer = (LPDWORD)pvDataBlock; - DWORD dwValue32; - DWORD dwKey2 = 0xEEEEEEEE; - - // Round to DWORDs - dwLength >>= 2; - - // We need different approach on non-aligned buffers - if(STORMLIB_DWORD_ALIGNED(DataPointer)) - { - for(DWORD i = 0; i < dwLength; i++) - { - // Modify the second key - dwKey2 += StormBuffer[MPQ_HASH_KEY2_MIX + (dwKey1 & 0xFF)]; - - // We can use 32-bit approach, when the buffer is aligned - DataPointer[i] = (dwValue32 = DataPointer[i]) ^ (dwKey1 + dwKey2); - - dwKey1 = ((~dwKey1 << 0x15) + 0x11111111) | (dwKey1 >> 0x0B); - dwKey2 = dwValue32 + dwKey2 + (dwKey2 << 5) + 3; - } - } - else - { - for(DWORD i = 0; i < dwLength; i++) - { - // Modify the second key - dwKey2 += StormBuffer[MPQ_HASH_KEY2_MIX + (dwKey1 & 0xFF)]; - - // The data are unaligned. Make sure we don't cause data misalignment error - dwValue32 = EncryptUInt32Unaligned(DataPointer, i, (dwKey1 + dwKey2)); - - dwKey1 = ((~dwKey1 << 0x15) + 0x11111111) | (dwKey1 >> 0x0B); - dwKey2 = dwValue32 + dwKey2 + (dwKey2 << 5) + 3; - } - } -} - -static DWORD DecryptUInt32Unaligned(LPDWORD DataPointer, DWORD i, DWORD dwXorKey) -{ - LPBYTE pbDataPointer = (LPBYTE)(DataPointer + i); - LPBYTE pbXorKey = (LPBYTE)(&dwXorKey); - - // Perform unaligned XOR - pbDataPointer[0] = (pbDataPointer[0] ^ pbXorKey[0]); - pbDataPointer[1] = (pbDataPointer[1] ^ pbXorKey[1]); - pbDataPointer[2] = (pbDataPointer[2] ^ pbXorKey[2]); - pbDataPointer[3] = (pbDataPointer[3] ^ pbXorKey[3]); - - // Retrieve the value - return ((DWORD)pbDataPointer[0] << 0x00) | - ((DWORD)pbDataPointer[1] << 0x08) | - ((DWORD)pbDataPointer[2] << 0x10) | - ((DWORD)pbDataPointer[3] << 0x18); -} - -void DecryptMpqBlock(void * pvDataBlock, DWORD dwLength, DWORD dwKey1) -{ - LPDWORD DataPointer = (LPDWORD)pvDataBlock; - DWORD dwValue32; - DWORD dwKey2 = 0xEEEEEEEE; - - // Round to DWORDs - dwLength >>= 2; - - // We need different approach on non-aligned buffers - if(STORMLIB_DWORD_ALIGNED(DataPointer)) - { - for(DWORD i = 0; i < dwLength; i++) - { - // Modify the second key - dwKey2 += StormBuffer[MPQ_HASH_KEY2_MIX + (dwKey1 & 0xFF)]; - - // We can use 32-bit approach, when the buffer is aligned - DataPointer[i] = dwValue32 = DataPointer[i] ^ (dwKey1 + dwKey2); - - dwKey1 = ((~dwKey1 << 0x15) + 0x11111111) | (dwKey1 >> 0x0B); - dwKey2 = dwValue32 + dwKey2 + (dwKey2 << 5) + 3; - } - } - else - { - for(DWORD i = 0; i < dwLength; i++) - { - // Modify the second key - dwKey2 += StormBuffer[MPQ_HASH_KEY2_MIX + (dwKey1 & 0xFF)]; - - // The data are unaligned. Make sure we don't cause data misalignment error - dwValue32 = DecryptUInt32Unaligned(DataPointer, i, (dwKey1 + dwKey2)); - - dwKey1 = ((~dwKey1 << 0x15) + 0x11111111) | (dwKey1 >> 0x0B); - dwKey2 = dwValue32 + dwKey2 + (dwKey2 << 5) + 3; - } - } -} - -/** - * Functions tries to get file decryption key. This comes from these facts - * - * - We know the decrypted value of the first DWORD in the encrypted data - * - We know the decrypted value of the second DWORD (at least aproximately) - * - There is only 256 variants of how the second key is modified - * - * The first iteration of dwKey1 and dwKey2 is this: - * - * dwKey2 = 0xEEEEEEEE + StormBuffer[MPQ_HASH_KEY2_MIX + (dwKey1 & 0xFF)] - * dwDecrypted0 = DataBlock[0] ^ (dwKey1 + dwKey2); - * - * This means: - * - * (dwKey1 + dwKey2) = DataBlock[0] ^ dwDecrypted0; - * - */ - -DWORD DetectFileKeyBySectorSize(LPDWORD EncryptedData, DWORD dwSectorSize, DWORD dwDecrypted0) -{ - // We must have at least 2 DWORDs there to be able to decrypt something - if(dwSectorSize >= 0x08) - { - // Also try subsequent three values. This is because the value of the sector offset[0] - // could be higher than the total size of the sector table. - // Example MPQ: MPQ_2021_v1_CantExtractCHK.scx - for(DWORD dwDecrypted4 = dwDecrypted0 + 4; dwDecrypted0 < dwDecrypted4; dwDecrypted0++) - { - DWORD dwDecrypted1Max = dwSectorSize + dwDecrypted0; - DWORD dwKey1PlusKey2; - DWORD DataBlock[2]; - - // Get the value of the combined encryption key - dwKey1PlusKey2 = (EncryptedData[0] ^ dwDecrypted0) - 0xEEEEEEEE; - - // Try all 256 combinations of dwKey1 - for(DWORD i = 0; i < 0x100; i++) - { - DWORD dwSaveKey1; - DWORD dwKey1 = dwKey1PlusKey2 - StormBuffer[MPQ_HASH_KEY2_MIX + i]; - DWORD dwKey2 = 0xEEEEEEEE; - - // Modify the second key and decrypt the first DWORD - dwKey2 += StormBuffer[MPQ_HASH_KEY2_MIX + (dwKey1 & 0xFF)]; - DataBlock[0] = EncryptedData[0] ^ (dwKey1 + dwKey2); - - // Did we obtain the same value like dwDecrypted0? - if(DataBlock[0] == dwDecrypted0) - { - // Save this key value. Increment by one because - // we are decrypting sector offset table - dwSaveKey1 = dwKey1 + 1; - - // Rotate both keys - dwKey1 = ((~dwKey1 << 0x15) + 0x11111111) | (dwKey1 >> 0x0B); - dwKey2 = DataBlock[0] + dwKey2 + (dwKey2 << 5) + 3; - - // Modify the second key again and decrypt the second DWORD - dwKey2 += StormBuffer[MPQ_HASH_KEY2_MIX + (dwKey1 & 0xFF)]; - DataBlock[1] = EncryptedData[1] ^ (dwKey1 + dwKey2); - - // Now compare the results - if(DataBlock[1] <= dwDecrypted1Max) - return dwSaveKey1; - } - } - } - } - - // Key not found - return 0; -} - -// Function tries to detect file encryption key based on expected file content -// It is the same function like before, except that we know the value of the second DWORD -DWORD DetectFileKeyByKnownContent(void * pvEncryptedData, DWORD dwDecrypted0, DWORD dwDecrypted1) -{ - LPDWORD EncryptedData = (LPDWORD)pvEncryptedData; - DWORD dwKey1PlusKey2; - DWORD DataBlock[2]; - - // Get the value of the combined encryption key - dwKey1PlusKey2 = (EncryptedData[0] ^ dwDecrypted0) - 0xEEEEEEEE; - - // Try all 256 combinations of dwKey1 - for(DWORD i = 0; i < 0x100; i++) - { - DWORD dwSaveKey1; - DWORD dwKey1 = dwKey1PlusKey2 - StormBuffer[MPQ_HASH_KEY2_MIX + i]; - DWORD dwKey2 = 0xEEEEEEEE; - - // Modify the second key and decrypt the first DWORD - dwKey2 += StormBuffer[MPQ_HASH_KEY2_MIX + (dwKey1 & 0xFF)]; - DataBlock[0] = EncryptedData[0] ^ (dwKey1 + dwKey2); - - // Did we obtain the same value like dwDecrypted0? - if(DataBlock[0] == dwDecrypted0) - { - // Save this key value - dwSaveKey1 = dwKey1; - - // Rotate both keys - dwKey1 = ((~dwKey1 << 0x15) + 0x11111111) | (dwKey1 >> 0x0B); - dwKey2 = DataBlock[0] + dwKey2 + (dwKey2 << 5) + 3; - - // Modify the second key again and decrypt the second DWORD - dwKey2 += StormBuffer[MPQ_HASH_KEY2_MIX + (dwKey1 & 0xFF)]; - DataBlock[1] = EncryptedData[1] ^ (dwKey1 + dwKey2); - - // Now compare the results - if(DataBlock[1] == dwDecrypted1) - return dwSaveKey1; - } - } - - // Key not found - return 0; -} - -DWORD DetectFileKeyByContent(void * pvEncryptedData, DWORD dwSectorSize, DWORD dwFileSize) -{ - DWORD dwFileKey; - - // Try to break the file encryption key as if it was a WAVE file - if(dwSectorSize >= 0x0C) - { - dwFileKey = DetectFileKeyByKnownContent(pvEncryptedData, 0x46464952, dwFileSize - 8); - if(dwFileKey != 0) - return dwFileKey; - } - - // Try to break the encryption key as if it was an EXE file - if(dwSectorSize > 0x40) - { - dwFileKey = DetectFileKeyByKnownContent(pvEncryptedData, 0x00905A4D, 0x00000003); - if(dwFileKey != 0) - return dwFileKey; - } - - // Try to break the encryption key as if it was a XML file - if(dwSectorSize > 0x04) - { - dwFileKey = DetectFileKeyByKnownContent(pvEncryptedData, 0x6D783F3C, 0x6576206C); - if(dwFileKey != 0) - return dwFileKey; - } - - // Not detected, sorry - return 0; -} - -DWORD DecryptFileKey( - const char * szFileName, - ULONGLONG MpqPos, - DWORD dwFileSize, - DWORD dwFlags) -{ - DWORD dwFileKey; - DWORD dwMpqPos = (DWORD)MpqPos; - - // File key is calculated from plain name - szFileName = GetPlainFileName(szFileName); - dwFileKey = HashString(szFileName, MPQ_HASH_FILE_KEY); - - // Fix the key, if needed - if(dwFlags & MPQ_FILE_FIX_KEY) - dwFileKey = (dwFileKey + dwMpqPos) ^ dwFileSize; - - // Return the key - return dwFileKey; -} - -//----------------------------------------------------------------------------- -// Handle validation functions - -TMPQArchive * IsValidMpqHandle(HANDLE hMpq) -{ - TMPQArchive * ha = (TMPQArchive *)hMpq; - - return (ha != NULL && ha->pHeader != NULL && ha->pHeader->dwID == g_dwMpqSignature) ? ha : NULL; -} - -TMPQFile * IsValidFileHandle(HANDLE hFile) -{ - TMPQFile * hf = (TMPQFile *)hFile; - - // Must not be NULL - if(hf != NULL && hf->dwMagic == ID_MPQ_FILE) - { - // Local file handle? - if(hf->pStream != NULL) - return hf; - - // Also verify the MPQ handle within the file handle - if(IsValidMpqHandle(hf->ha)) - return hf; - } - - return NULL; -} - -//----------------------------------------------------------------------------- -// Hash table and block table manipulation - -// Attempts to search a free hash entry, or an entry whose names and locale matches -TMPQHash * FindFreeHashEntry(TMPQArchive * ha, DWORD dwStartIndex, DWORD dwName1, DWORD dwName2, LCID lcFileLocale) -{ - TMPQHash * pDeletedEntry = NULL; // If a deleted entry was found in the continuous hash range - TMPQHash * pFreeEntry = NULL; // If a free entry was found in the continuous hash range - DWORD dwHashIndexMask = HASH_INDEX_MASK(ha); - DWORD dwIndex; - USHORT Locale = SFILE_LOCALE(lcFileLocale); - - // Set the initial index - dwStartIndex = dwIndex = (dwStartIndex & dwHashIndexMask); - - // Search the hash table and return the found entries in the following priority: - // 1) - // 2) - // 3) - // 4) NULL - for(;;) - { - TMPQHash * pHash = ha->pHashTable + dwIndex; - - // If we found a matching entry, return that one - if(pHash->dwName1 == dwName1 && pHash->dwName2 == dwName2 && pHash->Locale == Locale) - return pHash; - - // If we found a deleted entry, remember it but keep searching - if(pHash->dwBlockIndex == HASH_ENTRY_DELETED && pDeletedEntry == NULL) - pDeletedEntry = pHash; - - // If we found a free entry, we need to stop searching - if(pHash->dwBlockIndex == HASH_ENTRY_FREE) - { - pFreeEntry = pHash; - break; - } - - // Move to the next hash entry. - // If we reached the starting entry, it's failure. - dwIndex = (dwIndex + 1) & dwHashIndexMask; - if(dwIndex == dwStartIndex) - break; - } - - // If we found a deleted entry, return that one preferentially - return (pDeletedEntry != NULL) ? pDeletedEntry : pFreeEntry; -} - -// Retrieves the first hash entry for the given file. -// Every locale version of a file has its own hash entry -TMPQHash * GetFirstHashEntry(TMPQArchive * ha, const char * szFileName) -{ - DWORD dwHashIndexMask = HASH_INDEX_MASK(ha); - DWORD dwStartIndex = ha->pfnHashString(szFileName, MPQ_HASH_TABLE_INDEX); - DWORD dwName1 = ha->pfnHashString(szFileName, MPQ_HASH_NAME_A); - DWORD dwName2 = ha->pfnHashString(szFileName, MPQ_HASH_NAME_B); - DWORD dwIndex; - - // Set the initial index - dwStartIndex = dwIndex = (dwStartIndex & dwHashIndexMask); - - // Search the hash table - for(;;) - { - TMPQHash * pHash = ha->pHashTable + dwIndex; - - // If the entry matches, we found it. - if(pHash->dwName1 == dwName1 && pHash->dwName2 == dwName2 && MPQ_BLOCK_INDEX(pHash) < ha->dwFileTableSize) - return pHash; - - // If that hash entry is a free entry, it means we haven't found the file - if(pHash->dwBlockIndex == HASH_ENTRY_FREE) - return NULL; - - // Move to the next hash entry. Stop searching - // if we got reached the original hash entry - dwIndex = (dwIndex + 1) & dwHashIndexMask; - if(dwIndex == dwStartIndex) - return NULL; - } -} - -TMPQHash * GetNextHashEntry(TMPQArchive * ha, TMPQHash * pFirstHash, TMPQHash * pHash) -{ - DWORD dwHashIndexMask = HASH_INDEX_MASK(ha); - DWORD dwStartIndex = (DWORD)(pFirstHash - ha->pHashTable); - DWORD dwName1 = pHash->dwName1; - DWORD dwName2 = pHash->dwName2; - DWORD dwIndex = (DWORD)(pHash - ha->pHashTable); - - // Now go for any next entry that follows the pHash, - // until either free hash entry was found, or the start entry was reached - for(;;) - { - // Move to the next hash entry. Stop searching - // if we got reached the original hash entry - dwIndex = (dwIndex + 1) & dwHashIndexMask; - if(dwIndex == dwStartIndex) - return NULL; - pHash = ha->pHashTable + dwIndex; - - // If the entry matches, we found it. - if(pHash->dwName1 == dwName1 && pHash->dwName2 == dwName2 && MPQ_BLOCK_INDEX(pHash) < ha->dwFileTableSize) - return pHash; - - // If that hash entry is a free entry, it means we haven't found the file - if(pHash->dwBlockIndex == HASH_ENTRY_FREE) - return NULL; - } -} - -// Allocates an entry in the hash table -TMPQHash * AllocateHashEntry( - TMPQArchive * ha, - TFileEntry * pFileEntry, - LCID lcFileLocale) -{ - TMPQHash * pHash; - DWORD dwStartIndex = ha->pfnHashString(pFileEntry->szFileName, MPQ_HASH_TABLE_INDEX); - DWORD dwName1 = ha->pfnHashString(pFileEntry->szFileName, MPQ_HASH_NAME_A); - DWORD dwName2 = ha->pfnHashString(pFileEntry->szFileName, MPQ_HASH_NAME_B); - - // Attempt to find a free hash entry - pHash = FindFreeHashEntry(ha, dwStartIndex, dwName1, dwName2, lcFileLocale); - if(pHash != NULL) - { - // Fill the free hash entry - pHash->dwName1 = dwName1; - pHash->dwName2 = dwName2; - pHash->Locale = SFILE_LOCALE(lcFileLocale); - pHash->Platform = SFILE_PLATFORM(lcFileLocale); - pHash->Reserved = 0; - pHash->dwBlockIndex = (DWORD)(pFileEntry - ha->pFileTable); - } - - return pHash; -} - -// Finds a free space in the MPQ where to store next data -// The free space begins beyond the file that is stored at the fuhrtest -// position in the MPQ. (listfile), (attributes) and (signature) are ignored, -// unless the MPQ is being flushed. -ULONGLONG FindFreeMpqSpace(TMPQArchive * ha) -{ - TMPQHeader * pHeader = ha->pHeader; - TFileEntry * pFileTableEnd = ha->pFileTable + ha->dwFileTableSize; - TFileEntry * pFileEntry; - ULONGLONG FreeSpacePos = ha->pHeader->dwHeaderSize; - DWORD dwChunkCount; - - TFileEntry* startEntry = (ha->useFreeSpaceOptimization && ha->lastFreeSpaceEntry != nullptr) ? ha->lastFreeSpaceEntry : ha->pFileTable; - - // Parse the entire block table - for(pFileEntry = startEntry; pFileEntry < pFileTableEnd; pFileEntry++) - { - // Only take existing files with nonzero size - if((pFileEntry->dwFlags & MPQ_FILE_EXISTS) && (pFileEntry->dwCmpSize != 0)) - { - // If we are not saving MPQ tables, ignore internal MPQ files - if((ha->dwFlags & MPQ_FLAG_SAVING_TABLES) == 0 && IsInternalMpqFileName(pFileEntry->szFileName)) - continue; - - // If the end of the file is bigger than current MPQ table pos, update it - if((pFileEntry->ByteOffset + pFileEntry->dwCmpSize) > FreeSpacePos) - { - // Get the end of the file data - FreeSpacePos = pFileEntry->ByteOffset + pFileEntry->dwCmpSize; - - // Add the MD5 chunks, if present - if(pHeader->dwRawChunkSize != 0 && pFileEntry->dwCmpSize != 0) - { - dwChunkCount = ((pFileEntry->dwCmpSize - 1) / pHeader->dwRawChunkSize) + 1; - FreeSpacePos += dwChunkCount * MD5_DIGEST_SIZE; - } - - ha->lastFreeSpaceEntry = pFileEntry; - } - } - } - - // Give the free space position to the caller - return FreeSpacePos; -} - -//----------------------------------------------------------------------------- -// Common functions - MPQ File - -TMPQFile * CreateFileHandle(TMPQArchive * ha, TFileEntry * pFileEntry) -{ - TMPQFile * hf; - - // Allocate space for TMPQFile - hf = STORM_ALLOC(TMPQFile, 1); - if(hf != NULL) - { - // Fill the file structure - memset(hf, 0, sizeof(TMPQFile)); - hf->dwMagic = ID_MPQ_FILE; - hf->pStream = NULL; - hf->ha = ha; - - // If the called entered a file entry, we also copy informations from the file entry - if(ha != NULL && pFileEntry != NULL) - { - // Set the raw position and MPQ position - hf->RawFilePos = FileOffsetFromMpqOffset(ha, pFileEntry->ByteOffset); - hf->MpqFilePos = pFileEntry->ByteOffset; - - // Set the data size - hf->dwDataSize = pFileEntry->dwFileSize; - hf->pFileEntry = pFileEntry; - } - } - - return hf; -} - -TMPQFile * CreateWritableHandle(TMPQArchive * ha, DWORD dwFileSize) -{ - ULONGLONG FreeMpqSpace; - ULONGLONG TempPos; - TMPQFile * hf; - - // We need to find the position in the MPQ where we save the file data - FreeMpqSpace = FindFreeMpqSpace(ha); - - // When format V1, the size of the archive cannot exceed 4 GB - if(ha->pHeader->wFormatVersion == MPQ_FORMAT_VERSION_1) - { - TempPos = FreeMpqSpace + - dwFileSize + - (ha->pHeader->dwHashTableSize * sizeof(TMPQHash)) + - (ha->dwFileTableSize * sizeof(TMPQBlock)); - if((TempPos >> 32) != 0) - { - SetLastError(ERROR_DISK_FULL); - return NULL; - } - } - - // Allocate the file handle - hf = CreateFileHandle(ha, NULL); - if(hf == NULL) - { - SetLastError(ERROR_NOT_ENOUGH_MEMORY); - return NULL; - } - - // We need to find the position in the MPQ where we save the file data - hf->MpqFilePos = FreeMpqSpace; - hf->bIsWriteHandle = true; - return hf; -} - -// Loads a table from MPQ. -// Can be used for hash table, block table, sector offset table or sector checksum table -void * LoadMpqTable( - TMPQArchive * ha, - ULONGLONG ByteOffset, - LPBYTE pbTableHash, - DWORD dwCompressedSize, - DWORD dwTableSize, - DWORD dwKey, - DWORD * PtrRealTableSize) -{ - ULONGLONG FileSize = 0; - LPBYTE pbCompressed = NULL; - LPBYTE pbMpqTable; - LPBYTE pbToRead; - DWORD dwBytesToRead = dwCompressedSize; - DWORD dwErrCode = ERROR_SUCCESS; - - // Allocate the MPQ table - pbMpqTable = pbToRead = STORM_ALLOC(BYTE, dwTableSize); - if(pbMpqTable != NULL) - { - // Check if the MPQ table is encrypted - if(dwCompressedSize < dwTableSize) - { - // Allocate temporary buffer for holding compressed data - pbCompressed = pbToRead = STORM_ALLOC(BYTE, dwCompressedSize); - if(pbCompressed == NULL) - { - STORM_FREE(pbMpqTable); - return NULL; - } - } - - // Get the file offset from which we will read the table - // Note: According to Storm.dll from Warcraft III (version 2002), - // if the hash table position is 0xFFFFFFFF, no SetFilePointer call is done - // and the table is loaded from the current file offset - if(ByteOffset == SFILE_INVALID_POS) - FileStream_GetPos(ha->pStream, &ByteOffset); - - // On archives v 1.0, hash table and block table can go beyond EOF. - // Storm.dll reads as much as possible, then fills the missing part with zeros. - // Abused by Spazzler map protector which sets hash table size to 0x00100000 - // Abused by NP_Protect in MPQs v4 as well - if(ha->pHeader->wFormatVersion == MPQ_FORMAT_VERSION_1) - { - // Cut the table size - FileStream_GetSize(ha->pStream, &FileSize); - if((ByteOffset + dwBytesToRead) > FileSize) - { - // Fill the extra data with zeros - dwBytesToRead = (DWORD)(FileSize - ByteOffset); - memset(pbMpqTable + dwBytesToRead, 0, (dwTableSize - dwBytesToRead)); - } - } - - // Give the caller information that the table was cut - if(PtrRealTableSize != NULL) - { - PtrRealTableSize[0] = dwBytesToRead; - } - - // If everything succeeded, read the raw table from the MPQ - if(FileStream_Read(ha->pStream, &ByteOffset, pbToRead, dwBytesToRead)) - { - // Verify the MD5 of the table, if present - if(!VerifyDataBlockHash(pbToRead, dwBytesToRead, pbTableHash)) - { - dwErrCode = ERROR_FILE_CORRUPT; - } - } - else - { - dwErrCode = GetLastError(); - } - - if(dwErrCode == ERROR_SUCCESS) - { - // First of all, decrypt the table - if(dwKey != 0) - { - BSWAP_ARRAY32_UNSIGNED(pbToRead, dwCompressedSize); - DecryptMpqBlock(pbToRead, dwCompressedSize, dwKey); - BSWAP_ARRAY32_UNSIGNED(pbToRead, dwCompressedSize); - } - - // If the table is compressed, decompress it - if(dwCompressedSize < dwTableSize) - { - int cbOutBuffer = (int)dwTableSize; - int cbInBuffer = (int)dwCompressedSize; - - if(!SCompDecompress2(pbMpqTable, &cbOutBuffer, pbCompressed, cbInBuffer)) - dwErrCode = GetLastError(); - } - - // Make sure that the table is properly byte-swapped - BSWAP_ARRAY32_UNSIGNED(pbMpqTable, dwTableSize); - } - - // If read failed, free the table and return - if(dwErrCode != ERROR_SUCCESS) - { - STORM_FREE(pbMpqTable); - pbMpqTable = NULL; - } - - // Free the compression buffer, if any - if(pbCompressed != NULL) - STORM_FREE(pbCompressed); - } - - // Return the MPQ table - return pbMpqTable; -} - -unsigned char * AllocateMd5Buffer( - DWORD dwRawDataSize, - DWORD dwChunkSize, - LPDWORD pcbMd5Size) -{ - unsigned char * md5_array; - DWORD cbMd5Size; - - // Sanity check - assert(dwRawDataSize != 0); - assert(dwChunkSize != 0); - - // Calculate how many MD5's we will calculate - cbMd5Size = (((dwRawDataSize - 1) / dwChunkSize) + 1) * MD5_DIGEST_SIZE; - - // Allocate space for array or MD5s - md5_array = STORM_ALLOC(BYTE, cbMd5Size); - - // Give the size of the MD5 array - if(pcbMd5Size != NULL) - *pcbMd5Size = cbMd5Size; - return md5_array; -} - -// Allocates sector buffer and sector offset table -DWORD AllocateSectorBuffer(TMPQFile * hf) -{ - TMPQArchive * ha = hf->ha; - - // Caller of AllocateSectorBuffer must ensure these - assert(hf->pbFileSector == NULL); - assert(hf->pFileEntry != NULL); - assert(hf->ha != NULL); - - // Don't allocate anything if the file has zero size - if(hf->pFileEntry->dwFileSize == 0 || hf->dwDataSize == 0) - return ERROR_SUCCESS; - - // Determine the file sector size and allocate buffer for it - hf->dwSectorSize = (hf->pFileEntry->dwFlags & MPQ_FILE_SINGLE_UNIT) ? hf->dwDataSize : ha->dwSectorSize; - hf->pbFileSector = STORM_ALLOC(BYTE, hf->dwSectorSize); - hf->dwSectorOffs = SFILE_INVALID_POS; - - // Return result - return (hf->pbFileSector != NULL) ? ERROR_SUCCESS : ERROR_NOT_ENOUGH_MEMORY; -} - -// Allocates sector offset table -DWORD AllocatePatchInfo(TMPQFile * hf, bool bLoadFromFile) -{ - TMPQArchive * ha = hf->ha; - DWORD dwLength = sizeof(TPatchInfo); - - // The following conditions must be true - assert(hf->pFileEntry->dwFlags & MPQ_FILE_PATCH_FILE); - assert(hf->pPatchInfo == NULL); - -__AllocateAndLoadPatchInfo: - - // Allocate space for patch header. Start with default size, - // and if its size if bigger, then we reload them - hf->pPatchInfo = STORM_ALLOC(TPatchInfo, 1); - if(hf->pPatchInfo == NULL) - return ERROR_NOT_ENOUGH_MEMORY; - - // Do we have to load the patch header from the file ? - if(bLoadFromFile) - { - // Load the patch header - if(!FileStream_Read(ha->pStream, &hf->RawFilePos, hf->pPatchInfo, dwLength)) - { - // Free the patch info - STORM_FREE(hf->pPatchInfo); - hf->pPatchInfo = NULL; - return GetLastError(); - } - - // Perform necessary swapping - hf->pPatchInfo->dwLength = BSWAP_INT32_UNSIGNED(hf->pPatchInfo->dwLength); - hf->pPatchInfo->dwFlags = BSWAP_INT32_UNSIGNED(hf->pPatchInfo->dwFlags); - hf->pPatchInfo->dwDataSize = BSWAP_INT32_UNSIGNED(hf->pPatchInfo->dwDataSize); - - // Verify the size of the patch header - // If it's not default size, we have to reload them - if(hf->pPatchInfo->dwLength > dwLength) - { - // Free the patch info - dwLength = hf->pPatchInfo->dwLength; - STORM_FREE(hf->pPatchInfo); - hf->pPatchInfo = NULL; - - // If the length is out of all possible ranges, fail the operation - if(dwLength > 0x400) - return ERROR_FILE_CORRUPT; - goto __AllocateAndLoadPatchInfo; - } - - // Patch file data size according to the patch header - hf->dwDataSize = hf->pPatchInfo->dwDataSize; - } - else - { - memset(hf->pPatchInfo, 0, dwLength); - } - - // Save the final length to the patch header - hf->pPatchInfo->dwLength = dwLength; - hf->pPatchInfo->dwFlags = 0x80000000; - return ERROR_SUCCESS; -} - -// Allocates sector offset table -DWORD AllocateSectorOffsets(TMPQFile * hf, bool bLoadFromFile) -{ - TMPQArchive * ha = hf->ha; - TFileEntry * pFileEntry = hf->pFileEntry; - DWORD dwSectorOffsLen; - bool bSectorOffsetTableCorrupt = false; - - // Caller of AllocateSectorOffsets must ensure these - assert(hf->SectorOffsets == NULL); - assert(hf->pFileEntry != NULL); - assert(hf->dwDataSize != 0); - assert(hf->ha != NULL); - - // If the file is stored as single unit, just set number of sectors to 1 - if(pFileEntry->dwFlags & MPQ_FILE_SINGLE_UNIT) - { - hf->dwSectorCount = 1; - return ERROR_SUCCESS; - } - - // Calculate the number of data sectors - // Note that this doesn't work if the file size is zero - hf->dwSectorCount = ((hf->dwDataSize - 1) / hf->dwSectorSize) + 1; - - // Calculate the number of file sectors - dwSectorOffsLen = (hf->dwSectorCount + 1) * sizeof(DWORD); - - // If MPQ_FILE_SECTOR_CRC flag is set, there will either be extra DWORD - // or an array of MD5's. Either way, we read at least 4 bytes more - // in order to save additional read from the file. - if(pFileEntry->dwFlags & MPQ_FILE_SECTOR_CRC) - dwSectorOffsLen += sizeof(DWORD); - - // Only allocate and load the table if the file is compressed - if(pFileEntry->dwFlags & MPQ_FILE_COMPRESS_MASK) - { - __LoadSectorOffsets: - - // Allocate the sector offset table - hf->SectorOffsets = STORM_ALLOC(DWORD, (dwSectorOffsLen / sizeof(DWORD))); - if(hf->SectorOffsets == NULL) - return ERROR_NOT_ENOUGH_MEMORY; - - // Only read from the file if we are supposed to do so - if(bLoadFromFile) - { - ULONGLONG RawFilePos = hf->RawFilePos; - - // Append the length of the patch info, if any - if(hf->pPatchInfo != NULL) - { - if((RawFilePos + hf->pPatchInfo->dwLength) < RawFilePos) - return ERROR_FILE_CORRUPT; - RawFilePos += hf->pPatchInfo->dwLength; - } - - // Load the sector offsets from the file - if(!FileStream_Read(ha->pStream, &RawFilePos, hf->SectorOffsets, dwSectorOffsLen)) - { - // Free the sector offsets - STORM_FREE(hf->SectorOffsets); - hf->SectorOffsets = NULL; - return GetLastError(); - } - - // Swap the sector positions - BSWAP_ARRAY32_UNSIGNED(hf->SectorOffsets, dwSectorOffsLen); - - // Decrypt loaded sector positions if necessary - if(pFileEntry->dwFlags & MPQ_FILE_ENCRYPTED) - { - // If we don't know the file key, try to find it. - if(hf->dwFileKey == 0) - { - hf->dwFileKey = DetectFileKeyBySectorSize(hf->SectorOffsets, ha->dwSectorSize, dwSectorOffsLen); - if(hf->dwFileKey == 0) - { - STORM_FREE(hf->SectorOffsets); - hf->SectorOffsets = NULL; - return ERROR_UNKNOWN_FILE_KEY; - } - } - - // Decrypt sector positions - DecryptMpqBlock(hf->SectorOffsets, dwSectorOffsLen, hf->dwFileKey - 1); - } - - // - // Validate the sector offset table - // - // Note: Some MPQ protectors put the actual file data before the sector offset table. - // In this case, the sector offsets are negative (> 0x80000000). - // - - for(DWORD i = 0; i < hf->dwSectorCount; i++) - { - DWORD dwSectorOffset1 = hf->SectorOffsets[i+1]; - DWORD dwSectorOffset0 = hf->SectorOffsets[i]; - - // Every following sector offset must be bigger than the previous one - if(dwSectorOffset1 < dwSectorOffset0) - { - bSectorOffsetTableCorrupt = true; - break; - } - - // The sector size must not be bigger than compressed file size - // Edit: Yes, but apparently, in original Storm.dll, the compressed - // size is not checked anywhere. However, we need to do this check - // in order to sector offset table malformed by MPQ protectors - if((dwSectorOffset1 - dwSectorOffset0) > ha->dwSectorSize) - { - bSectorOffsetTableCorrupt = true; - break; - } - } - - // If data corruption detected, free the sector offset table - if(bSectorOffsetTableCorrupt) - { - STORM_FREE(hf->SectorOffsets); - hf->SectorOffsets = NULL; - return ERROR_FILE_CORRUPT; - } - - // - // There may be various extra DWORDs loaded after the sector offset table. - // They are mostly empty on WoW release MPQs, but on MPQs from PTR, - // they contain random non-zero data. Their meaning is unknown. - // - // These extra values are, however, included in the dwCmpSize in the file - // table. We cannot ignore them, because compacting archive would fail - // - - // Clear the lower 2 bits in order to make sure that the value is aligned to 4 bytes - if((hf->SectorOffsets[0] & 0xFFFFFFFC) > dwSectorOffsLen) - { - // MPQ protectors put some ridiculous values there. We must limit the extra bytes - if(hf->SectorOffsets[0] > (dwSectorOffsLen + 0x400)) - return ERROR_FILE_CORRUPT; - - // Free the old sector offset table - dwSectorOffsLen = hf->SectorOffsets[0]; - STORM_FREE(hf->SectorOffsets); - goto __LoadSectorOffsets; - } - } - else - { - memset(hf->SectorOffsets, 0, dwSectorOffsLen); - hf->SectorOffsets[0] = dwSectorOffsLen; - } - } - - return ERROR_SUCCESS; -} - -DWORD AllocateSectorChecksums(TMPQFile * hf, bool bLoadFromFile) -{ - TMPQArchive * ha = hf->ha; - TFileEntry * pFileEntry = hf->pFileEntry; - ULONGLONG RawFilePos; - DWORD dwCompressedSize = 0; - DWORD dwExpectedSize; - DWORD dwCrcOffset; // Offset of the CRC table, relative to file offset in the MPQ - DWORD dwCrcSize; - - // Caller of AllocateSectorChecksums must ensure these - assert(hf->SectorChksums == NULL); - assert(hf->SectorOffsets != NULL); - assert(hf->pFileEntry != NULL); - assert(hf->ha != NULL); - - // Single unit files don't have sector checksums - if(pFileEntry->dwFlags & MPQ_FILE_SINGLE_UNIT) - return ERROR_SUCCESS; - - // Caller must ensure that we are only called when we have sector checksums - assert(pFileEntry->dwFlags & MPQ_FILE_SECTOR_CRC); - - // - // Older MPQs store an array of CRC32's after - // the raw file data in the MPQ. - // - // In newer MPQs, the (since Cataclysm BETA) the (attributes) file - // contains additional 32-bit values beyond the sector table. - // Their number depends on size of the (attributes), but their - // meaning is unknown. They are usually zeroed in retail game files, - // but contain some sort of checksum in BETA MPQs - // - - // Does the size of the file table match with the CRC32-based checksums? - dwExpectedSize = (hf->dwSectorCount + 2) * sizeof(DWORD); - if(hf->SectorOffsets[0] != 0 && hf->SectorOffsets[0] == dwExpectedSize) - { - // If we are not loading from the MPQ file, we just allocate the sector table - // In that case, do not check any sizes - if(bLoadFromFile == false) - { - hf->SectorChksums = STORM_ALLOC(DWORD, hf->dwSectorCount); - if(hf->SectorChksums == NULL) - return ERROR_NOT_ENOUGH_MEMORY; - - // Fill the checksum table with zeros - memset(hf->SectorChksums, 0, hf->dwSectorCount * sizeof(DWORD)); - return ERROR_SUCCESS; - } - else - { - // Is there valid size of the sector checksums? - if(hf->SectorOffsets[hf->dwSectorCount + 1] >= hf->SectorOffsets[hf->dwSectorCount]) - dwCompressedSize = hf->SectorOffsets[hf->dwSectorCount + 1] - hf->SectorOffsets[hf->dwSectorCount]; - - // Ignore cases when the length is too small or too big. - if(dwCompressedSize < sizeof(DWORD) || dwCompressedSize > hf->dwSectorSize) - return ERROR_SUCCESS; - - // Calculate offset of the CRC table - dwCrcSize = hf->dwSectorCount * sizeof(DWORD); - dwCrcOffset = hf->SectorOffsets[hf->dwSectorCount]; - RawFilePos = CalculateRawSectorOffset(hf, dwCrcOffset); - - // Now read the table from the MPQ - hf->SectorChksums = (DWORD *)LoadMpqTable(ha, RawFilePos, NULL, dwCompressedSize, dwCrcSize, 0, NULL); - if(hf->SectorChksums == NULL) - return ERROR_NOT_ENOUGH_MEMORY; - } - } - - // If the size doesn't match, we ignore sector checksums -// assert(false); - return ERROR_SUCCESS; -} - -DWORD WritePatchInfo(TMPQFile * hf) -{ - TMPQArchive * ha = hf->ha; - TPatchInfo * pPatchInfo = hf->pPatchInfo; - - // The caller must make sure that this function is only called - // when the following is true. - assert(hf->pFileEntry->dwFlags & MPQ_FILE_PATCH_FILE); - assert(pPatchInfo != NULL); - - BSWAP_ARRAY32_UNSIGNED(pPatchInfo, 3 * sizeof(DWORD)); - if(!FileStream_Write(ha->pStream, &hf->RawFilePos, pPatchInfo, sizeof(TPatchInfo))) - return GetLastError(); - - return ERROR_SUCCESS; -} - -DWORD WriteSectorOffsets(TMPQFile * hf) -{ - TMPQArchive * ha = hf->ha; - TFileEntry * pFileEntry = hf->pFileEntry; - ULONGLONG RawFilePos = hf->RawFilePos; - DWORD dwSectorOffsLen; - - // The caller must make sure that this function is only called - // when the following is true. - assert(hf->pFileEntry->dwFlags & MPQ_FILE_COMPRESS_MASK); - assert(hf->SectorOffsets != NULL); - dwSectorOffsLen = hf->SectorOffsets[0]; - - // If file is encrypted, sector positions are also encrypted - if(pFileEntry->dwFlags & MPQ_FILE_ENCRYPTED) - EncryptMpqBlock(hf->SectorOffsets, dwSectorOffsLen, hf->dwFileKey - 1); - BSWAP_ARRAY32_UNSIGNED(hf->SectorOffsets, dwSectorOffsLen); - - // Adjust sector offset table position, if we also have patch info - if(hf->pPatchInfo != NULL) - RawFilePos += hf->pPatchInfo->dwLength; - - // Write sector offsets to the archive - if(!FileStream_Write(ha->pStream, &RawFilePos, hf->SectorOffsets, dwSectorOffsLen)) - return GetLastError(); - - // Not necessary, as the sector checksums - // are going to be freed when this is done. -// BSWAP_ARRAY32_UNSIGNED(hf->SectorOffsets, dwSectorOffsLen); - return ERROR_SUCCESS; -} - -DWORD WriteSectorChecksums(TMPQFile * hf) -{ - TMPQArchive * ha = hf->ha; - ULONGLONG RawFilePos; - TFileEntry * pFileEntry = hf->pFileEntry; - LPBYTE pbCompressed; - DWORD dwCompressedSize = 0; - DWORD dwErrCode = ERROR_SUCCESS; - DWORD dwCrcSize; - int nOutSize; - - // The caller must make sure that this function is only called - // when the following is true. - assert(hf->pFileEntry->dwFlags & MPQ_FILE_SECTOR_CRC); - assert(hf->SectorOffsets != NULL); - assert(hf->SectorChksums != NULL); - - // If the MPQ has MD5 of each raw data chunk, - // we leave sector offsets empty - if(ha->pHeader->dwRawChunkSize != 0) - { - hf->SectorOffsets[hf->dwSectorCount + 1] = hf->SectorOffsets[hf->dwSectorCount]; - return ERROR_SUCCESS; - } - - // Calculate size of the checksum array - dwCrcSize = hf->dwSectorCount * sizeof(DWORD); - - // Allocate buffer for compressed sector CRCs. - pbCompressed = STORM_ALLOC(BYTE, dwCrcSize); - if(pbCompressed == NULL) - return ERROR_NOT_ENOUGH_MEMORY; - - // Perform the compression - BSWAP_ARRAY32_UNSIGNED(hf->SectorChksums, dwCrcSize); - - nOutSize = (int)dwCrcSize; - SCompCompress(pbCompressed, &nOutSize, hf->SectorChksums, (int)dwCrcSize, MPQ_COMPRESSION_ZLIB, 0, 0); - dwCompressedSize = (DWORD)nOutSize; - - // Write the sector CRCs to the archive - RawFilePos = hf->RawFilePos + hf->SectorOffsets[hf->dwSectorCount]; - if(hf->pPatchInfo != NULL) - RawFilePos += hf->pPatchInfo->dwLength; - if(!FileStream_Write(ha->pStream, &RawFilePos, pbCompressed, dwCompressedSize)) - dwErrCode = GetLastError(); - - // Not necessary, as the sector checksums - // are going to be freed when this is done. -// BSWAP_ARRAY32_UNSIGNED(hf->SectorChksums, dwCrcSize); - - // Store the sector CRCs - hf->SectorOffsets[hf->dwSectorCount + 1] = hf->SectorOffsets[hf->dwSectorCount] + dwCompressedSize; - pFileEntry->dwCmpSize += dwCompressedSize; - STORM_FREE(pbCompressed); - return dwErrCode; -} - -DWORD WriteMemDataMD5( - TFileStream * pStream, - ULONGLONG RawDataOffs, - void * pvRawData, - DWORD dwRawDataSize, - DWORD dwChunkSize, - LPDWORD pcbTotalSize) -{ - unsigned char * md5_array; - unsigned char * md5; - LPBYTE pbRawData = (LPBYTE)pvRawData; - DWORD dwBytesRemaining = dwRawDataSize; - DWORD dwMd5ArraySize = 0; - DWORD dwErrCode = ERROR_SUCCESS; - - // Allocate buffer for array of MD5 - md5_array = md5 = AllocateMd5Buffer(dwRawDataSize, dwChunkSize, &dwMd5ArraySize); - if(md5_array == NULL) - return ERROR_NOT_ENOUGH_MEMORY; - - // For every file chunk, calculate MD5 - while(dwBytesRemaining != 0) - { - // Get the remaining number of bytes to read - dwChunkSize = STORMLIB_MIN(dwBytesRemaining, dwChunkSize); - - // Calculate MD5 - CalculateDataBlockHash(pbRawData, dwChunkSize, md5); - md5 += MD5_DIGEST_SIZE; - - // Move offset and size - dwBytesRemaining -= dwChunkSize; - pbRawData += dwChunkSize; - } - - // Write the array od MD5's to the file - RawDataOffs += dwRawDataSize; - if(!FileStream_Write(pStream, &RawDataOffs, md5_array, dwMd5ArraySize)) - dwErrCode = GetLastError(); - - // Give the caller the size of the MD5 array - if(pcbTotalSize != NULL) - *pcbTotalSize = dwRawDataSize + dwMd5ArraySize; - - // Free buffers and exit - STORM_FREE(md5_array); - return dwErrCode; -} - - -// Writes the MD5 for each chunk of the raw file data -DWORD WriteMpqDataMD5( - TFileStream * pStream, - ULONGLONG RawDataOffs, - DWORD dwRawDataSize, - DWORD dwChunkSize) -{ - unsigned char * md5_array; - unsigned char * md5; - LPBYTE pbFileChunk; - DWORD dwMd5ArraySize = 0; - DWORD dwToRead = dwRawDataSize; - DWORD dwErrCode = ERROR_SUCCESS; - - // Allocate buffer for array of MD5 - md5_array = md5 = AllocateMd5Buffer(dwRawDataSize, dwChunkSize, &dwMd5ArraySize); - if(md5_array == NULL) - return ERROR_NOT_ENOUGH_MEMORY; - - // Allocate space for file chunk - pbFileChunk = STORM_ALLOC(BYTE, dwChunkSize); - if(pbFileChunk == NULL) - { - STORM_FREE(md5_array); - return ERROR_NOT_ENOUGH_MEMORY; - } - - // For every file chunk, calculate MD5 - while(dwRawDataSize != 0) - { - // Get the remaining number of bytes to read - dwToRead = STORMLIB_MIN(dwRawDataSize, dwChunkSize); - - // Read the chunk - if(!FileStream_Read(pStream, &RawDataOffs, pbFileChunk, dwToRead)) - { - dwErrCode = GetLastError(); - break; - } - - // Calculate MD5 - CalculateDataBlockHash(pbFileChunk, dwToRead, md5); - md5 += MD5_DIGEST_SIZE; - - // Move offset and size - RawDataOffs += dwToRead; - dwRawDataSize -= dwToRead; - } - - // Write the array od MD5's to the file - if(dwErrCode == ERROR_SUCCESS) - { - if(!FileStream_Write(pStream, NULL, md5_array, dwMd5ArraySize)) - dwErrCode = GetLastError(); - } - - // Free buffers and exit - STORM_FREE(pbFileChunk); - STORM_FREE(md5_array); - return dwErrCode; -} - -// Frees the structure for MPQ file -void FreeFileHandle(TMPQFile *& hf) -{ - if(hf != NULL) - { - // If we have patch file attached to this one, free it first - if(hf->hfPatch != NULL) - FreeFileHandle(hf->hfPatch); - - // Then free all buffers allocated in the file structure - if(hf->pbFileData != NULL) - STORM_FREE(hf->pbFileData); - if(hf->pPatchInfo != NULL) - STORM_FREE(hf->pPatchInfo); - if(hf->SectorOffsets != NULL) - STORM_FREE(hf->SectorOffsets); - if(hf->SectorChksums != NULL) - STORM_FREE(hf->SectorChksums); - if(hf->hctx != NULL) - STORM_FREE(hf->hctx); - if(hf->pbFileSector != NULL) - STORM_FREE(hf->pbFileSector); - if(hf->pStream != NULL) - FileStream_Close(hf->pStream); - STORM_FREE(hf); - hf = NULL; - } -} - -// Frees the MPQ archive -void FreeArchiveHandle(TMPQArchive *& ha) -{ - if(ha != NULL) - { - // First of all, free the patch archive, if any - if(ha->haPatch != NULL) - FreeArchiveHandle(ha->haPatch); - - // Free the patch prefix, if any - if(ha->pPatchPrefix != NULL) - STORM_FREE(ha->pPatchPrefix); - - // Close the file stream - FileStream_Close(ha->pStream); - ha->pStream = NULL; - - // Free the file names from the file table - if(ha->pFileTable != NULL) - { - for(DWORD i = 0; i < ha->dwFileTableSize; i++) - { - if(ha->pFileTable[i].szFileName != NULL) - STORM_FREE(ha->pFileTable[i].szFileName); - ha->pFileTable[i].szFileName = NULL; - } - - // Then free all buffers allocated in the archive structure - STORM_FREE(ha->pFileTable); - } - - if(ha->pHashTable != NULL) - STORM_FREE(ha->pHashTable); - if(ha->pHetTable != NULL) - FreeHetTable(ha->pHetTable); - STORM_FREE(ha); - ha = NULL; - } -} - -bool IsInternalMpqFileName(const char * szFileName) -{ - if(szFileName != NULL && szFileName[0] == '(') - { - if(!_stricmp(szFileName, LISTFILE_NAME) || - !_stricmp(szFileName, ATTRIBUTES_NAME) || - !_stricmp(szFileName, SIGNATURE_NAME)) - { - return true; - } - } - - return false; -} - -// Verifies if the file name is a pseudo-name -bool IsPseudoFileName(const char * szFileName, DWORD * pdwFileIndex) -{ - DWORD dwFileIndex = 0; - - if(szFileName != NULL) - { - // Must be "File########.ext" - if(!_strnicmp(szFileName, "File", 4)) - { - // Check 8 digits - for(int i = 4; i < 4+8; i++) - { - if(szFileName[i] < '0' || szFileName[i] > '9') - return false; - dwFileIndex = (dwFileIndex * 10) + (szFileName[i] - '0'); - } - - // An extension must follow - if(szFileName[12] == '.') - { - if(pdwFileIndex != NULL) - *pdwFileIndex = dwFileIndex; - return true; - } - } - } - - // Not a pseudo-name - return false; -} - -//----------------------------------------------------------------------------- -// Functions calculating and verifying the MD5 signature - -bool IsValidMD5(LPBYTE pbMd5) -{ - LPDWORD Md5 = (LPDWORD)pbMd5; - - return ((Md5 != NULL) && (Md5[0] | Md5[1] | Md5[2] | Md5[3])) ? true : false; -} - -bool IsValidSignature(LPBYTE pbSignature) -{ - LPDWORD Signature = (LPDWORD)pbSignature; - DWORD SigValid = 0; - - for(int i = 0; i < MPQ_WEAK_SIGNATURE_SIZE / sizeof(DWORD); i++) - SigValid |= Signature[i]; - - return (SigValid != 0) ? true : false; -} - - -bool VerifyDataBlockHash(void * pvDataBlock, DWORD cbDataBlock, LPBYTE expected_md5) -{ - hash_state md5_state; - BYTE md5_digest[MD5_DIGEST_SIZE]; - bool bResult = true; - - // Don't verify the block if the MD5 is not valid. - if(IsValidMD5(expected_md5)) - { - // Calculate the MD5 of the data block - md5_init(&md5_state); - md5_process(&md5_state, (unsigned char *)pvDataBlock, cbDataBlock); - md5_done(&md5_state, md5_digest); - - // Does the MD5's match? - bResult = (memcmp(md5_digest, expected_md5, MD5_DIGEST_SIZE) == 0); - } - - return bResult; -} - -void CalculateDataBlockHash(void * pvDataBlock, DWORD cbDataBlock, LPBYTE md5_hash) -{ - hash_state md5_state; - - md5_init(&md5_state); - md5_process(&md5_state, (unsigned char *)pvDataBlock, cbDataBlock); - md5_done(&md5_state, md5_hash); -} - -//----------------------------------------------------------------------------- -// Swapping functions - -#ifndef STORMLIB_LITTLE_ENDIAN - -// Swaps a signed 16-bit integer -int16_t SwapInt16(uint16_t val) -{ - return (val << 8) | ((val >> 8) & 0xFF); -} - -// Swaps an unsigned 16-bit integer -uint16_t SwapUInt16(uint16_t val) -{ - return (val << 8) | (val >> 8 ); -} - -// Swaps a signed 32-bit integer -int32_t SwapInt32(uint32_t val) -{ - val = ((val << 8) & 0xFF00FF00) | ((val >> 8) & 0xFF00FF ); - return (val << 16) | ((val >> 16) & 0xFFFF); -} - -// Swaps an unsigned 32-bit integer -uint32_t SwapUInt32(uint32_t val) -{ - val = ((val << 8) & 0xFF00FF00 ) | ((val >> 8) & 0xFF00FF ); - return (val << 16) | (val >> 16); -} - -// Swaps a signed 64-bit integer -int64_t SwapInt64(uint64_t val) -{ - val = ((val << 8) & 0xFF00FF00FF00FF00ULL ) | ((val >> 8) & 0x00FF00FF00FF00FFULL ); - val = ((val << 16) & 0xFFFF0000FFFF0000ULL ) | ((val >> 16) & 0x0000FFFF0000FFFFULL ); - return (val << 32) | ((val >> 32) & 0xFFFFFFFFULL); -} - -// Swaps an unsigned 64-bit integer -uint64_t SwapUInt64(uint64_t val) -{ - val = ((val << 8) & 0xFF00FF00FF00FF00ULL ) | ((val >> 8) & 0x00FF00FF00FF00FFULL ); - val = ((val << 16) & 0xFFFF0000FFFF0000ULL ) | ((val >> 16) & 0x0000FFFF0000FFFFULL ); - return (val << 32) | (val >> 32); -} - -// Swaps array of unsigned 16-bit integers -void ConvertUInt16Buffer(void * ptr, size_t length) -{ - uint16_t * buffer = (uint16_t *)ptr; - uint32_t nElements = (uint32_t)(length / sizeof(uint16_t)); - - while(nElements-- > 0) - { - *buffer = SwapUInt16(*buffer); - buffer++; - } -} - -// Swaps array of unsigned 32-bit integers -void ConvertUInt32Buffer(void * ptr, size_t length) -{ - uint32_t * buffer = (uint32_t *)ptr; - uint32_t nElements = (uint32_t)(length / sizeof(uint32_t)); - - while(nElements-- > 0) - { - *buffer = SwapUInt32(*buffer); - buffer++; - } -} - -// Swaps array of unsigned 64-bit integers -void ConvertUInt64Buffer(void * ptr, size_t length) -{ - uint64_t * buffer = (uint64_t *)ptr; - uint32_t nElements = (uint32_t)(length / sizeof(uint64_t)); - - while(nElements-- > 0) - { - *buffer = SwapUInt64(*buffer); - buffer++; - } -} - -// Swaps the TMPQHeader structure -void ConvertTMPQHeader(void *header, uint16_t version) -{ - TMPQHeader * theHeader = (TMPQHeader *)header; - - // Swap header part version 1 - if(version >= MPQ_FORMAT_VERSION_1) - { - theHeader->dwID = SwapUInt32(theHeader->dwID); - theHeader->dwHeaderSize = SwapUInt32(theHeader->dwHeaderSize); - theHeader->dwArchiveSize = SwapUInt32(theHeader->dwArchiveSize); - theHeader->wFormatVersion = SwapUInt16(theHeader->wFormatVersion); - theHeader->wSectorSize = SwapUInt16(theHeader->wSectorSize); - theHeader->dwHashTablePos = SwapUInt32(theHeader->dwHashTablePos); - theHeader->dwBlockTablePos = SwapUInt32(theHeader->dwBlockTablePos); - theHeader->dwHashTableSize = SwapUInt32(theHeader->dwHashTableSize); - theHeader->dwBlockTableSize = SwapUInt32(theHeader->dwBlockTableSize); - } - - if(version >= MPQ_FORMAT_VERSION_2) - { - theHeader->HiBlockTablePos64 = SwapUInt64(theHeader->HiBlockTablePos64); - theHeader->wHashTablePosHi = SwapUInt16(theHeader->wHashTablePosHi); - theHeader->wBlockTablePosHi = SwapUInt16(theHeader->wBlockTablePosHi); - } - - if(version >= MPQ_FORMAT_VERSION_3) - { - theHeader->ArchiveSize64 = SwapUInt64(theHeader->ArchiveSize64); - theHeader->BetTablePos64 = SwapUInt64(theHeader->BetTablePos64); - theHeader->HetTablePos64 = SwapUInt64(theHeader->HetTablePos64); - } - - if(version >= MPQ_FORMAT_VERSION_4) - { - theHeader->HashTableSize64 = SwapUInt64(theHeader->HashTableSize64); - theHeader->BlockTableSize64 = SwapUInt64(theHeader->BlockTableSize64); - theHeader->HiBlockTableSize64 = SwapUInt64(theHeader->HiBlockTableSize64); - theHeader->HetTableSize64 = SwapUInt64(theHeader->HetTableSize64); - theHeader->BetTableSize64 = SwapUInt64(theHeader->BetTableSize64); - } -} - -#endif // STORMLIB_LITTLE_ENDIAN diff --git a/app/jni/src/libultraship/extern/StormLib/src/SBaseDumpData.cpp b/app/jni/src/libultraship/extern/StormLib/src/SBaseDumpData.cpp deleted file mode 100644 index 16313dd..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/SBaseDumpData.cpp +++ /dev/null @@ -1,183 +0,0 @@ -/*****************************************************************************/ -/* SBaseDumpData.cpp Copyright (c) Ladislav Zezula 2011 */ -/*---------------------------------------------------------------------------*/ -/* Description : */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 26.01.11 1.00 Lad The first version of SBaseDumpData.cpp */ -/*****************************************************************************/ - -#define __STORMLIB_SELF__ -#include "StormLib.h" -#include "StormCommon.h" - -#ifdef __STORMLIB_DUMP_DATA__ - -void DumpMpqHeader(TMPQHeader * pHeader) -{ - printf("== MPQ Header =================================\n"); - printf("DWORD dwID = %08X\n", pHeader->dwID); - printf("DWORD dwHeaderSize = %08X\n", pHeader->dwHeaderSize); - printf("DWORD dwArchiveSize = %08X\n", pHeader->dwArchiveSize); - printf("USHORT wFormatVersion = %04X\n", pHeader->wFormatVersion); - printf("USHORT wSectorSize = %04X\n", pHeader->wSectorSize); - printf("DWORD dwHashTablePos = %08X\n", pHeader->dwHashTablePos); - printf("DWORD dwBlockTablePos = %08X\n", pHeader->dwBlockTablePos); - printf("DWORD dwHashTableSize = %08X\n", pHeader->dwHashTableSize); - printf("DWORD dwBlockTableSize = %08X\n", pHeader->dwBlockTableSize); - printf("ULONGLONG HiBlockTablePos64 = %016llX\n", pHeader->HiBlockTablePos64); - printf("USHORT wHashTablePosHi = %04X\n", pHeader->wHashTablePosHi); - printf("USHORT wBlockTablePosHi = %04X\n", pHeader->wBlockTablePosHi); - printf("ULONGLONG ArchiveSize64 = %016llX\n", pHeader->ArchiveSize64); - printf("ULONGLONG BetTablePos64 = %016llX\n", pHeader->BetTablePos64); - printf("ULONGLONG HetTablePos64 = %016llX\n", pHeader->HetTablePos64); - printf("ULONGLONG HashTableSize64 = %016llX\n", pHeader->HashTableSize64); - printf("ULONGLONG BlockTableSize64 = %016llX\n", pHeader->BlockTableSize64); - printf("ULONGLONG HiBlockTableSize64 = %016llX\n", pHeader->HiBlockTableSize64); - printf("ULONGLONG HetTableSize64 = %016llX\n", pHeader->HetTableSize64); - printf("ULONGLONG BetTableSize64 = %016llX\n", pHeader->BetTableSize64); - printf("DWORD dwRawChunkSize = %08X\n", pHeader->dwRawChunkSize); - printf("-----------------------------------------------\n\n"); -} - -void DumpHashTable(TMPQHash * pHashTable, DWORD dwHashTableSize) -{ - DWORD i; - - if(pHashTable == NULL || dwHashTableSize == 0) - return; - - printf("== Hash Table =================================\n"); - for(i = 0; i < dwHashTableSize; i++) - { - printf("[%08x] %08X %08X %04X %02X %08X\n", i, - pHashTable[i].dwName1, - pHashTable[i].dwName2, - pHashTable[i].Locale, - pHashTable[i].Platform, - pHashTable[i].dwBlockIndex); - } - printf("-----------------------------------------------\n\n"); -} - -void DumpHetAndBetTable(TMPQHetTable * pHetTable, TMPQBetTable * pBetTable) -{ - DWORD i; - - if(pHetTable == NULL || pBetTable == NULL) - return; - - printf("== HET Header =================================\n"); - printf("ULONGLONG AndMask64 = %016llX\n", pHetTable->AndMask64); - printf("ULONGLONG OrMask64 = %016llX\n", pHetTable->OrMask64); - printf("DWORD dwEntryCount = %08X\n", pHetTable->dwEntryCount); - printf("DWORD dwTotalCount = %08X\n", pHetTable->dwTotalCount); - printf("DWORD dwNameHashBitSize = %08X\n", pHetTable->dwNameHashBitSize); - printf("DWORD dwIndexSizeTotal = %08X\n", pHetTable->dwIndexSizeTotal); - printf("DWORD dwIndexSizeExtra = %08X\n", pHetTable->dwIndexSizeExtra); - printf("DWORD dwIndexSize = %08X\n", pHetTable->dwIndexSize); - printf("-----------------------------------------------\n\n"); - - printf("== BET Header =================================\n"); - printf("DWORD dwTableEntrySize = %08X\n", pBetTable->dwTableEntrySize); - printf("DWORD dwBitIndex_FilePos = %08X\n", pBetTable->dwBitIndex_FilePos); - printf("DWORD dwBitIndex_FileSize = %08X\n", pBetTable->dwBitIndex_FileSize); - printf("DWORD dwBitIndex_CmpSize = %08X\n", pBetTable->dwBitIndex_CmpSize); - printf("DWORD dwBitIndex_FlagIndex = %08X\n", pBetTable->dwBitIndex_FlagIndex); - printf("DWORD dwBitIndex_Unknown = %08X\n", pBetTable->dwBitIndex_Unknown); - printf("DWORD dwBitCount_FilePos = %08X\n", pBetTable->dwBitCount_FilePos); - printf("DWORD dwBitCount_FileSize = %08X\n", pBetTable->dwBitCount_FileSize); - printf("DWORD dwBitCount_CmpSize = %08X\n", pBetTable->dwBitCount_CmpSize); - printf("DWORD dwBitCount_FlagIndex = %08X\n", pBetTable->dwBitCount_FlagIndex); - printf("DWORD dwBitCount_Unknown = %08X\n", pBetTable->dwBitCount_Unknown); - printf("DWORD dwBitTotal_NameHash2 = %08X\n", pBetTable->dwBitTotal_NameHash2); - printf("DWORD dwBitExtra_NameHash2 = %08X\n", pBetTable->dwBitExtra_NameHash2); - printf("DWORD dwBitCount_NameHash2 = %08X\n", pBetTable->dwBitCount_NameHash2); - printf("DWORD dwEntryCount = %08X\n", pBetTable->dwEntryCount); - printf("DWORD dwFlagCount = %08X\n", pBetTable->dwFlagCount); - printf("-----------------------------------------------\n\n"); - - printf("== HET & Bet Table ======================================================================\n\n"); - printf("HetIdx HetHash BetIdx BetHash ByteOffset FileSize CmpSize FlgIdx Flags \n"); - printf("------ ------- ------ ---------------- ---------------- -------- -------- ------ --------\n"); - for(i = 0; i < pHetTable->dwTotalCount; i++) - { - ULONGLONG ByteOffset = 0; - ULONGLONG BetHash = 0; - DWORD dwFileSize = 0; - DWORD dwCmpSize = 0; - DWORD dwFlagIndex = 0; - DWORD dwFlags = 0; - DWORD dwBetIndex = 0; - - GetMPQBits(pHetTable->pBetIndexes, i * pHetTable->dwIndexSizeTotal, - pHetTable->dwIndexSize, - &dwBetIndex, 4); - - if(dwBetIndex < pHetTable->dwTotalCount) - { - DWORD dwEntryIndex = pBetTable->dwTableEntrySize * dwBetIndex; - - GetMPQBits(pBetTable->pNameHashes, dwBetIndex * pBetTable->dwBitTotal_NameHash2, - pBetTable->dwBitCount_NameHash2, - &BetHash, 8); - - GetMPQBits(pBetTable->pFileTable, dwEntryIndex + pBetTable->dwBitIndex_FilePos, - pBetTable->dwBitCount_FilePos, - &ByteOffset, 8); - - GetMPQBits(pBetTable->pFileTable, dwEntryIndex + pBetTable->dwBitIndex_FileSize, - pBetTable->dwBitCount_FileSize, - &dwFileSize, 4); - - GetMPQBits(pBetTable->pFileTable, dwEntryIndex + pBetTable->dwBitIndex_CmpSize, - pBetTable->dwBitCount_CmpSize, - &dwCmpSize, 4); - - GetMPQBits(pBetTable->pFileTable, dwEntryIndex + pBetTable->dwBitIndex_FlagIndex, - pBetTable->dwBitCount_FlagIndex, - &dwFlagIndex, 4); - - dwFlags = pBetTable->pFileFlags[dwFlagIndex]; - } - - printf(" %04X %02lX %04X %016llX %016llX %08X %08X %04X %08X\n", i, - pHetTable->pNameHashes[i], - dwBetIndex, - BetHash, - ByteOffset, - dwFileSize, - dwCmpSize, - dwFlagIndex, - dwFlags); - } - printf("-----------------------------------------------------------------------------------------\n"); -} - -void DumpFileTable(TFileEntry * pFileTable, DWORD dwFileTableSize) -{ - DWORD i; - - if(pFileTable == NULL || dwFileTableSize == 0) - return; - - printf("== File Table =================================\n"); - for(i = 0; i < dwFileTableSize; i++, pFileTable++) - { - printf("[%04u] %08X-%08X %08X-%08X %08X-%08X 0x%08X 0x%08X 0x%08X %s\n", i, - (DWORD)(pFileTable->FileNameHash >> 0x20), - (DWORD)(pFileTable->FileNameHash & 0xFFFFFFFF), - (DWORD)(pFileTable->ByteOffset >> 0x20), - (DWORD)(pFileTable->ByteOffset & 0xFFFFFFFF), - (DWORD)(pFileTable->FileTime >> 0x20), - (DWORD)(pFileTable->FileTime & 0xFFFFFFFF), - pFileTable->dwFileSize, - pFileTable->dwCmpSize, - pFileTable->dwFlags, - pFileTable->szFileName != NULL ? pFileTable->szFileName : ""); - } - printf("-----------------------------------------------\n\n"); -} - -#endif // __STORMLIB_DUMP_DATA__ diff --git a/app/jni/src/libultraship/extern/StormLib/src/SBaseFileTable.cpp b/app/jni/src/libultraship/extern/StormLib/src/SBaseFileTable.cpp deleted file mode 100644 index b68de51..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/SBaseFileTable.cpp +++ /dev/null @@ -1,3119 +0,0 @@ -/*****************************************************************************/ -/* SBaseFileTable.cpp Copyright (c) Ladislav Zezula 2010 */ -/*---------------------------------------------------------------------------*/ -/* Description: Common handler for classic and new hash&block tables */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 06.09.10 1.00 Lad The first version of SBaseFileTable.cpp */ -/*****************************************************************************/ - -#define __STORMLIB_SELF__ -#include "StormLib.h" -#include "StormCommon.h" - -//----------------------------------------------------------------------------- -// Local defines - -#define INVALID_FLAG_VALUE 0xCCCCCCCC -#define MAX_FLAG_INDEX 512 - -//----------------------------------------------------------------------------- -// Support for calculating bit sizes - -static void InitFileFlagArray(LPDWORD FlagArray) -{ - memset(FlagArray, 0xCC, MAX_FLAG_INDEX * sizeof(DWORD)); -} - -static DWORD GetFileFlagIndex(LPDWORD FlagArray, DWORD dwFlags) -{ - // Find free or equal entry in the flag array - for(DWORD dwFlagIndex = 0; dwFlagIndex < MAX_FLAG_INDEX; dwFlagIndex++) - { - if(FlagArray[dwFlagIndex] == INVALID_FLAG_VALUE || FlagArray[dwFlagIndex] == dwFlags) - { - FlagArray[dwFlagIndex] = dwFlags; - return dwFlagIndex; - } - } - - // This should never happen - assert(false); - return 0xFFFFFFFF; -} - -static DWORD GetNecessaryBitCount(ULONGLONG MaxValue) -{ - DWORD dwBitCount = 0; - - while(MaxValue > 0) - { - MaxValue >>= 1; - dwBitCount++; - } - - return dwBitCount; -} - -//----------------------------------------------------------------------------- -// Implementation of the TMPQBits struct - -struct TMPQBits -{ - static TMPQBits * Create(DWORD NumberOfBits, BYTE FillValue); - - void GetBits(unsigned int nBitPosition, unsigned int nBitLength, void * pvBuffer, int nResultSize); - void SetBits(unsigned int nBitPosition, unsigned int nBitLength, void * pvBuffer, int nResultSize); - - static const USHORT SetBitsMask[]; // Bit mask for each number of bits (0-8) - - DWORD NumberOfBytes; // Total number of bytes in "Elements" - DWORD NumberOfBits; // Total number of bits that are available - BYTE Elements[1]; // Array of elements (variable length) -}; - -const USHORT TMPQBits::SetBitsMask[] = {0x00, 0x01, 0x03, 0x07, 0x0F, 0x1F, 0x3F, 0x7F, 0xFF}; - -TMPQBits * TMPQBits::Create( - DWORD NumberOfBits, - BYTE FillValue) -{ - TMPQBits * pBitArray; - size_t nSize = sizeof(TMPQBits) + (NumberOfBits + 7) / 8; - - // Allocate the bit array - pBitArray = (TMPQBits *)STORM_ALLOC(BYTE, nSize); - if(pBitArray != NULL) - { - memset(pBitArray, FillValue, nSize); - pBitArray->NumberOfBytes = (NumberOfBits + 7) / 8; - pBitArray->NumberOfBits = NumberOfBits; - } - - return pBitArray; -} - -void TMPQBits::GetBits( - unsigned int nBitPosition, - unsigned int nBitLength, - void * pvBuffer, - int nResultByteSize) -{ - unsigned char * pbBuffer = (unsigned char *)pvBuffer; - unsigned int nBytePosition0 = (nBitPosition / 8); - unsigned int nBytePosition1 = nBytePosition0 + 1; - unsigned int nByteLength = (nBitLength / 8); - unsigned int nBitOffset = (nBitPosition & 0x07); - unsigned char BitBuffer; - - // Keep compiler happy for platforms where nResultByteSize is not used - nResultByteSize = nResultByteSize; - -#ifdef _DEBUG - // Check if the target is properly zeroed - for(int i = 0; i < nResultByteSize; i++) - assert(pbBuffer[i] == 0); -#endif - -#ifndef STORMLIB_LITTLE_ENDIAN - // Adjust the buffer pointer for big endian platforms - pbBuffer += (nResultByteSize - 1); -#endif - - // Copy whole bytes, if any - while(nByteLength > 0) - { - // Is the current position in the Elements byte-aligned? - if(nBitOffset != 0) - { - BitBuffer = (unsigned char)((Elements[nBytePosition0] >> nBitOffset) | (Elements[nBytePosition1] << (0x08 - nBitOffset))); - } - else - { - BitBuffer = Elements[nBytePosition0]; - } - -#ifdef STORMLIB_LITTLE_ENDIAN - *pbBuffer++ = BitBuffer; -#else - *pbBuffer-- = BitBuffer; -#endif - - // Move byte positions and lengths - nBytePosition1++; - nBytePosition0++; - nByteLength--; - } - - // Get the rest of the bits - nBitLength = (nBitLength & 0x07); - if(nBitLength != 0) - { - *pbBuffer = (unsigned char)(Elements[nBytePosition0] >> nBitOffset); - - if(nBitLength > (8 - nBitOffset)) - *pbBuffer = (unsigned char)((Elements[nBytePosition1] << (8 - nBitOffset)) | (Elements[nBytePosition0] >> nBitOffset)); - - *pbBuffer &= (0x01 << nBitLength) - 1; - } -} - -void TMPQBits::SetBits( - unsigned int nBitPosition, - unsigned int nBitLength, - void * pvBuffer, - int nResultByteSize) -{ - unsigned char * pbBuffer = (unsigned char *)pvBuffer; - unsigned int nBytePosition = (nBitPosition / 8); - unsigned int nBitOffset = (nBitPosition & 0x07); - unsigned short BitBuffer = 0; - unsigned short AndMask = 0; - unsigned short OneByte = 0; - - // Keep compiler happy for platforms where nResultByteSize is not used - nResultByteSize = nResultByteSize; - -#ifndef STORMLIB_LITTLE_ENDIAN - // Adjust the buffer pointer for big endian platforms - pbBuffer += (nResultByteSize - 1); -#endif - - // Copy whole bytes, if any - while(nBitLength > 8) - { - // Reload the bit buffer -#ifdef STORMLIB_LITTLE_ENDIAN - OneByte = *pbBuffer++; -#else - OneByte = *pbBuffer--; -#endif - // Update the BitBuffer and AndMask for the bit array - BitBuffer = (BitBuffer >> 0x08) | (OneByte << nBitOffset); - AndMask = (AndMask >> 0x08) | (0x00FF << nBitOffset); - - // Update the byte in the array - Elements[nBytePosition] = (BYTE)((Elements[nBytePosition] & ~AndMask) | BitBuffer); - - // Move byte positions and lengths - nBytePosition++; - nBitLength -= 0x08; - } - - if(nBitLength != 0) - { - // Reload the bit buffer - OneByte = *pbBuffer; - - // Update the AND mask for the last bit - BitBuffer = (BitBuffer >> 0x08) | (OneByte << nBitOffset); - AndMask = (AndMask >> 0x08) | (SetBitsMask[nBitLength] << nBitOffset); - - // Update the byte in the array - Elements[nBytePosition] = (BYTE)((Elements[nBytePosition] & ~AndMask) | BitBuffer); - - // Update the next byte, if needed - if(AndMask & 0xFF00) - { - nBytePosition++; - BitBuffer >>= 0x08; - AndMask >>= 0x08; - - Elements[nBytePosition] = (BYTE)((Elements[nBytePosition] & ~AndMask) | BitBuffer); - } - } -} - -void GetMPQBits(TMPQBits * pBits, unsigned int nBitPosition, unsigned int nBitLength, void * pvBuffer, int nResultByteSize) -{ - pBits->GetBits(nBitPosition, nBitLength, pvBuffer, nResultByteSize); -} - -//----------------------------------------------------------------------------- -// Support for MPQ header - -static bool VerifyTablePosition64( - ULONGLONG MpqOffset, // Position of the MPQ header - ULONGLONG TableOffset, // Position of the MPQ table, relative to MPQ header - ULONGLONG TableSize, // Size of the MPQ table, in bytes - ULONGLONG FileSize) // Size of the entire file, in bytes -{ - if(TableOffset != 0) - { - // Verify overflows - if((MpqOffset + TableOffset) < MpqOffset) - return false; - if((MpqOffset + TableOffset + TableSize) < MpqOffset) - return false; - - // Verify sizes - if(TableOffset >= FileSize || TableSize >= FileSize) - return false; - if((MpqOffset + TableOffset) >= FileSize) - return false; - if((MpqOffset + TableOffset + TableSize) >= FileSize) - return false; - } - return true; -} - -static bool VerifyTableTandemPositions( - ULONGLONG MpqOffset, // Position of the MPQ header - ULONGLONG TableOffset1, // 1st table: Position, relative to MPQ header - ULONGLONG TableSize1, // 1st table: Size in bytes - ULONGLONG TableOffset2, // 2nd table: Position, relative to MPQ header - ULONGLONG TableSize2, // 2nd table: Size in bytes - ULONGLONG FileSize) // Size of the entire file, in bytes -{ - return VerifyTablePosition64(MpqOffset, TableOffset1, TableSize1, FileSize) && - VerifyTablePosition64(MpqOffset, TableOffset2, TableSize2, FileSize); -} - -static ULONGLONG DetermineArchiveSize_V1( - TMPQArchive * ha, - TMPQHeader * pHeader, - ULONGLONG MpqOffset, - ULONGLONG FileSize) -{ - ULONGLONG ByteOffset; - ULONGLONG EndOfMpq = FileSize; - DWORD SignatureHeader = 0; - DWORD dwArchiveSize32; - - // This could only be called for MPQs version 1.0 - assert(pHeader->wFormatVersion == MPQ_FORMAT_VERSION_1); - - // Check if we can rely on the archive size in the header - if(pHeader->dwBlockTablePos < pHeader->dwArchiveSize) - { - // The block table cannot be compressed, so the sizes must match - if((pHeader->dwArchiveSize - pHeader->dwBlockTablePos) == (pHeader->dwBlockTableSize * sizeof(TMPQBlock))) - return pHeader->dwArchiveSize; - - // If the archive size in the header is less than real file size - dwArchiveSize32 = (DWORD)(FileSize - MpqOffset); - if(pHeader->dwArchiveSize == dwArchiveSize32) - return pHeader->dwArchiveSize; - } - - // Check if there is a signature header - if((EndOfMpq - MpqOffset) > (MPQ_STRONG_SIGNATURE_SIZE + 4)) - { - ByteOffset = EndOfMpq - MPQ_STRONG_SIGNATURE_SIZE - 4; - if(FileStream_Read(ha->pStream, &ByteOffset, &SignatureHeader, sizeof(DWORD))) - { - if(BSWAP_INT32_UNSIGNED(SignatureHeader) == MPQ_STRONG_SIGNATURE_ID) - EndOfMpq = EndOfMpq - MPQ_STRONG_SIGNATURE_SIZE - 4; - } - } - - // Return the returned archive size - return (EndOfMpq - MpqOffset); -} - -static ULONGLONG DetermineArchiveSize_V2( - TMPQHeader * pHeader, - ULONGLONG MpqOffset, - ULONGLONG FileSize) -{ - ULONGLONG EndOfMpq = FileSize; - DWORD dwArchiveSize32; - - // This could only be called for MPQs version 2.0 - assert(pHeader->wFormatVersion == MPQ_FORMAT_VERSION_2); - - // Check if we can rely on the archive size in the header - if((FileSize >> 0x20) == 0) - { - if(pHeader->dwBlockTablePos < pHeader->dwArchiveSize) - { - if((pHeader->dwArchiveSize - pHeader->dwBlockTablePos) <= (pHeader->dwBlockTableSize * sizeof(TMPQBlock))) - return pHeader->dwArchiveSize; - - // If the archive size in the header is less than real file size - dwArchiveSize32 = (DWORD)(FileSize - MpqOffset); - if(pHeader->dwArchiveSize <= dwArchiveSize32) - return pHeader->dwArchiveSize; - } - } - - // Return the calculated archive size - return (EndOfMpq - MpqOffset); -} - -static ULONGLONG DetermineArchiveSize_V4( - TMPQHeader * pHeader, - ULONGLONG /* MpqOffset */, - ULONGLONG /* FileSize */) -{ - ULONGLONG ArchiveSize = 0; - ULONGLONG EndOfTable; - - // This could only be called for MPQs version 4 - assert(pHeader->wFormatVersion == MPQ_FORMAT_VERSION_4); - - // Check position of BET table, if correct - if((pHeader->BetTablePos64 >> 0x20) == 0 && (pHeader->BetTableSize64 >> 0x20) == 0) - { - EndOfTable = pHeader->BetTablePos64 + pHeader->BetTableSize64; - if(EndOfTable > ArchiveSize) - ArchiveSize = EndOfTable; - } - - // Check position of HET table, if correct - if((pHeader->HetTablePos64 >> 0x20) == 0 && (pHeader->HetTableSize64 >> 0x20) == 0) - { - EndOfTable = pHeader->HetTablePos64 + pHeader->HetTableSize64; - if(EndOfTable > ArchiveSize) - ArchiveSize = EndOfTable; - } - - EndOfTable = pHeader->dwHashTablePos + pHeader->dwHashTableSize * sizeof(TMPQHash); - if(EndOfTable > ArchiveSize) - ArchiveSize = EndOfTable; - - EndOfTable = pHeader->dwBlockTablePos + pHeader->dwBlockTableSize * sizeof(TMPQBlock); - if(EndOfTable > ArchiveSize) - ArchiveSize = EndOfTable; - - // Return the calculated archive size - return ArchiveSize; -} - -ULONGLONG FileOffsetFromMpqOffset(TMPQArchive * ha, ULONGLONG MpqOffset) -{ - if(ha->pHeader->wFormatVersion == MPQ_FORMAT_VERSION_1) - { - // For MPQ archive v1, any file offset is only 32-bit - return (ULONGLONG)((DWORD)ha->MpqPos + (DWORD)MpqOffset); - } - else - { - // For MPQ archive v2+, file offsets are full 64-bit - return ha->MpqPos + MpqOffset; - } -} - -ULONGLONG CalculateRawSectorOffset( - TMPQFile * hf, - DWORD dwSectorOffset) -{ - ULONGLONG RawFilePos; - - // Must be used for files within a MPQ - assert(hf->ha != NULL); - assert(hf->ha->pHeader != NULL); - - // - // Some MPQ protectors place the sector offset table after the actual file data. - // Sector offsets in the sector offset table are negative. When added - // to MPQ file offset from the block table entry, the result is a correct - // position of the file data in the MPQ. - // - // For MPQs version 1.0, the offset is purely 32-bit - // - - RawFilePos = hf->RawFilePos + dwSectorOffset; - if(hf->ha->pHeader->wFormatVersion == MPQ_FORMAT_VERSION_1) - RawFilePos = (DWORD)hf->ha->MpqPos + (DWORD)hf->pFileEntry->ByteOffset + dwSectorOffset; - - // We also have to add patch header size, if patch header is present - if(hf->pPatchInfo != NULL) - RawFilePos += hf->pPatchInfo->dwLength; - - // Return the result offset - return RawFilePos; -} - -// This function converts the MPQ header so it always looks like version 4 -DWORD ConvertMpqHeaderToFormat4( - TMPQArchive * ha, - ULONGLONG ByteOffset, - ULONGLONG FileSize, - DWORD dwFlags, - MTYPE MapType) -{ - TMPQHeader * pHeader = (TMPQHeader *)ha->HeaderData; - ULONGLONG BlockTablePos64 = 0; - ULONGLONG HashTablePos64 = 0; - ULONGLONG BlockTableMask = (ULONGLONG)-1; - ULONGLONG MaxOffset; - USHORT wFormatVersion = BSWAP_INT16_UNSIGNED(pHeader->wFormatVersion); - bool bHashBlockOffsetOK = false; - bool bHetBetOffsetOK = false; - DWORD dwErrCode = ERROR_SUCCESS; - - // If version 1.0 is forced, then the format version is forced to be 1.0 - // Reason: Storm.dll in Warcraft III ignores format version value - if((MapType == MapTypeWarcraft3) || (dwFlags & MPQ_OPEN_FORCE_MPQ_V1)) - wFormatVersion = MPQ_FORMAT_VERSION_1; - - // Don't accept format 3 for Starcraft II maps - if((MapType == MapTypeStarcraft2) && (pHeader->wFormatVersion > MPQ_FORMAT_VERSION_2)) - wFormatVersion = MPQ_FORMAT_VERSION_4; - - // Format-specific fixes - switch(wFormatVersion) - { - case MPQ_FORMAT_VERSION_1: - - // Check for malformed MPQ header version 1.0 - BSWAP_TMPQHEADER(pHeader, MPQ_FORMAT_VERSION_1); - if(pHeader->wFormatVersion != MPQ_FORMAT_VERSION_1 || pHeader->dwHeaderSize != MPQ_HEADER_SIZE_V1) - { - pHeader->wFormatVersion = MPQ_FORMAT_VERSION_1; - pHeader->dwHeaderSize = MPQ_HEADER_SIZE_V1; - ha->dwFlags |= MPQ_FLAG_MALFORMED; - } - - // - // Note: The value of "dwArchiveSize" member in the MPQ header - // is ignored by Storm.dll and can contain garbage value - // ("w3xmaster" protector). - // - - Label_ArchiveVersion1: - if(pHeader->dwBlockTableSize > 1) // Prevent empty MPQs being marked as malformed - { - if(pHeader->dwHashTablePos <= pHeader->dwHeaderSize || (pHeader->dwHashTablePos & 0x80000000)) - ha->dwFlags |= MPQ_FLAG_MALFORMED; - if(pHeader->dwBlockTablePos <= pHeader->dwHeaderSize || (pHeader->dwBlockTablePos & 0x80000000)) - ha->dwFlags |= MPQ_FLAG_MALFORMED; - } - - // Only low byte of sector size is really used - if(pHeader->wSectorSize & 0xFF00) - ha->dwFlags |= MPQ_FLAG_MALFORMED; - pHeader->wSectorSize = pHeader->wSectorSize & 0xFF; - - // Fill the rest of the header - memset((LPBYTE)pHeader + MPQ_HEADER_SIZE_V1, 0, sizeof(TMPQHeader) - MPQ_HEADER_SIZE_V1); - pHeader->BlockTableSize64 = pHeader->dwBlockTableSize * sizeof(TMPQBlock); - pHeader->HashTableSize64 = pHeader->dwHashTableSize * sizeof(TMPQHash); - pHeader->ArchiveSize64 = pHeader->dwArchiveSize; - - // Block table position must be calculated as 32-bit value - // Note: BOBA protector puts block table before the MPQ header, so it is negative - BlockTablePos64 = (ULONGLONG)((DWORD)ByteOffset + pHeader->dwBlockTablePos); - BlockTableMask = 0xFFFFFFF0; - - // Determine the archive size on malformed MPQs - if(ha->dwFlags & MPQ_FLAG_MALFORMED) - { - // Calculate the archive size - pHeader->ArchiveSize64 = DetermineArchiveSize_V1(ha, pHeader, ByteOffset, FileSize); - pHeader->dwArchiveSize = (DWORD)pHeader->ArchiveSize64; - } - - // EWIX_v8_7.w3x: TMPQHeader::dwBlockTableSize = 0x00319601 - // Size of TFileTable goes to ~200MB, so we artificially cut it - if(BlockTablePos64 + (pHeader->dwBlockTableSize * sizeof(TMPQBlock)) > FileSize) - { - pHeader->dwBlockTableSize = (DWORD)((FileSize - BlockTablePos64) / sizeof(TMPQBlock)); - pHeader->BlockTableSize64 = pHeader->dwBlockTableSize * sizeof(TMPQBlock); - } - break; - - case MPQ_FORMAT_VERSION_2: - - // Check for malformed MPQ header version 1.0 - BSWAP_TMPQHEADER(pHeader, MPQ_FORMAT_VERSION_2); - if(pHeader->wFormatVersion != MPQ_FORMAT_VERSION_2 || pHeader->dwHeaderSize != MPQ_HEADER_SIZE_V2) - { - pHeader->wFormatVersion = MPQ_FORMAT_VERSION_1; - pHeader->dwHeaderSize = MPQ_HEADER_SIZE_V1; - ha->dwFlags |= MPQ_FLAG_MALFORMED; - goto Label_ArchiveVersion1; - } - - // Fill the rest of the header with zeros - memset((LPBYTE)pHeader + MPQ_HEADER_SIZE_V2, 0, sizeof(TMPQHeader) - MPQ_HEADER_SIZE_V2); - - // Calculate the expected hash table size - pHeader->HashTableSize64 = (pHeader->dwHashTableSize * sizeof(TMPQHash)); - HashTablePos64 = MAKE_OFFSET64(pHeader->wHashTablePosHi, pHeader->dwHashTablePos); - - // Calculate the expected block table size - pHeader->BlockTableSize64 = (pHeader->dwBlockTableSize * sizeof(TMPQBlock)); - BlockTablePos64 = MAKE_OFFSET64(pHeader->wBlockTablePosHi, pHeader->dwBlockTablePos); - - // We require the block table to follow hash table - if(BlockTablePos64 >= HashTablePos64) - { - // HashTableSize64 may be less than TblSize * sizeof(TMPQHash). - // That means that the hash table is compressed. - pHeader->HashTableSize64 = BlockTablePos64 - HashTablePos64; - - // Calculate the compressed block table size - if(pHeader->HiBlockTablePos64 != 0) - { - // BlockTableSize64 may be less than TblSize * sizeof(TMPQBlock). - // That means that the block table is compressed. - pHeader->BlockTableSize64 = pHeader->HiBlockTablePos64 - BlockTablePos64; - assert(pHeader->BlockTableSize64 <= (pHeader->dwBlockTableSize * sizeof(TMPQBlock))); - - // Determine real archive size - pHeader->ArchiveSize64 = DetermineArchiveSize_V2(pHeader, ByteOffset, FileSize); - - // Calculate the size of the hi-block table - pHeader->HiBlockTableSize64 = pHeader->ArchiveSize64 - pHeader->HiBlockTablePos64; - assert(pHeader->HiBlockTableSize64 == (pHeader->dwBlockTableSize * sizeof(USHORT))); - } - else - { - // Determine real archive size - pHeader->ArchiveSize64 = DetermineArchiveSize_V2(pHeader, ByteOffset, FileSize); - - // Calculate size of the block table - pHeader->BlockTableSize64 = pHeader->ArchiveSize64 - BlockTablePos64; - assert(pHeader->BlockTableSize64 <= (pHeader->dwBlockTableSize * sizeof(TMPQBlock))); - } - } - else - { - pHeader->ArchiveSize64 = pHeader->dwArchiveSize; - ha->dwFlags |= MPQ_FLAG_MALFORMED; - } - - // Add the MPQ Offset - BlockTablePos64 += ByteOffset; - break; - - case MPQ_FORMAT_VERSION_3: - - // In MPQ format 3.0, the entire header is optional - // and the size of the header can actually be identical - // to size of header 2.0 - BSWAP_TMPQHEADER(pHeader, MPQ_FORMAT_VERSION_3); - if(pHeader->dwHeaderSize < MPQ_HEADER_SIZE_V3) - { - pHeader->ArchiveSize64 = pHeader->dwArchiveSize; - pHeader->HetTablePos64 = 0; - pHeader->BetTablePos64 = 0; - } - - // - // We need to calculate the compressed size of each table. We assume the following order: - // 1) HET table - // 2) BET table - // 3) Classic hash table - // 4) Classic block table - // 5) Hi-block table - // - - // Fill the rest of the header with zeros - memset((LPBYTE)pHeader + MPQ_HEADER_SIZE_V3, 0, sizeof(TMPQHeader) - MPQ_HEADER_SIZE_V3); - BlockTablePos64 = MAKE_OFFSET64(pHeader->wBlockTablePosHi, pHeader->dwBlockTablePos); - HashTablePos64 = MAKE_OFFSET64(pHeader->wHashTablePosHi, pHeader->dwHashTablePos); - MaxOffset = pHeader->ArchiveSize64; - - // Size of the hi-block table - if(pHeader->HiBlockTablePos64) - { - pHeader->HiBlockTableSize64 = MaxOffset - pHeader->HiBlockTablePos64; - MaxOffset = pHeader->HiBlockTablePos64; - } - - // Size of the block table - if(BlockTablePos64) - { - pHeader->BlockTableSize64 = MaxOffset - BlockTablePos64; - MaxOffset = BlockTablePos64; - } - - // Size of the hash table - if(HashTablePos64) - { - pHeader->HashTableSize64 = MaxOffset - HashTablePos64; - MaxOffset = HashTablePos64; - } - - // Size of the BET table - if(pHeader->BetTablePos64) - { - pHeader->BetTableSize64 = MaxOffset - pHeader->BetTablePos64; - MaxOffset = pHeader->BetTablePos64; - } - - // Size of the HET table - if(pHeader->HetTablePos64) - { - pHeader->HetTableSize64 = MaxOffset - pHeader->HetTablePos64; -// MaxOffset = pHeader->HetTablePos64; - } - - // Add the MPQ Offset - BlockTablePos64 += ByteOffset; - break; - - case MPQ_FORMAT_VERSION_4: - - // Verify header MD5. Header MD5 is calculated from the MPQ header since the 'MPQ\x1A' - // signature until the position of header MD5 at offset 0xC0 - BSWAP_TMPQHEADER(pHeader, MPQ_FORMAT_VERSION_4); - - // Apparently, Starcraft II only accepts MPQ headers where the MPQ header hash matches - // If MD5 doesn't match, we ignore this offset. We also ignore it if there's no MD5 at all - if(!IsValidMD5(pHeader->MD5_MpqHeader)) - return ERROR_FAKE_MPQ_HEADER; - if(!VerifyDataBlockHash(pHeader, MPQ_HEADER_SIZE_V4 - MD5_DIGEST_SIZE, pHeader->MD5_MpqHeader)) - return ERROR_FAKE_MPQ_HEADER; - - // HiBlockTable must be 0 for archives under 4GB - if((pHeader->ArchiveSize64 >> 0x20) == 0 && pHeader->HiBlockTablePos64 != 0) - return ERROR_FAKE_MPQ_HEADER; - - // Is the "HET&BET" table tandem OK? - bHetBetOffsetOK = VerifyTableTandemPositions(ByteOffset, - pHeader->HetTablePos64, pHeader->HetTableSize64, - pHeader->BetTablePos64, pHeader->BetTableSize64, - FileSize); - - // Is the "Hash&Block" table tandem OK? - bHashBlockOffsetOK = VerifyTableTandemPositions(ByteOffset, - pHeader->dwHashTablePos, pHeader->HashTableSize64, - pHeader->dwBlockTablePos, pHeader->BlockTableSize64, - FileSize); - - // At least one pair must be OK - if(bHetBetOffsetOK == false && bHashBlockOffsetOK == false) - return ERROR_FAKE_MPQ_HEADER; - - // Check for malformed MPQs - if(pHeader->wFormatVersion != MPQ_FORMAT_VERSION_4 || (ByteOffset + pHeader->ArchiveSize64) != FileSize || (ByteOffset + pHeader->HiBlockTablePos64) >= FileSize) - { - pHeader->wFormatVersion = MPQ_FORMAT_VERSION_4; - pHeader->dwHeaderSize = MPQ_HEADER_SIZE_V4; - ha->dwFlags |= MPQ_FLAG_MALFORMED; - } - - // Recalculate archive size - if(ha->dwFlags & MPQ_FLAG_MALFORMED) - { - // Calculate the archive size - pHeader->ArchiveSize64 = DetermineArchiveSize_V4(pHeader, ByteOffset, FileSize); - pHeader->dwArchiveSize = (DWORD)pHeader->ArchiveSize64; - } - - // Calculate the block table position - BlockTablePos64 = ByteOffset + MAKE_OFFSET64(pHeader->wBlockTablePosHi, pHeader->dwBlockTablePos); - break; - - default: - - // Check if it's a War of the Immortal data file (SQP) - // If not, we treat it as malformed MPQ version 1.0 - if(ConvertSqpHeaderToFormat4(ha, FileSize, dwFlags) != ERROR_SUCCESS) - { - pHeader->wFormatVersion = MPQ_FORMAT_VERSION_1; - pHeader->dwHeaderSize = MPQ_HEADER_SIZE_V1; - ha->dwFlags |= MPQ_FLAG_MALFORMED; - goto Label_ArchiveVersion1; - } - - // Calculate the block table position - BlockTablePos64 = ByteOffset + MAKE_OFFSET64(pHeader->wBlockTablePosHi, pHeader->dwBlockTablePos); - break; - } - - // Handle case when block table is placed before the MPQ header - // Used by BOBA protector - if(BlockTablePos64 < ByteOffset) - ha->dwFlags |= MPQ_FLAG_MALFORMED; - return dwErrCode; -} - -//----------------------------------------------------------------------------- -// Support for hash table - -// Hash entry verification when the file table does not exist yet -bool IsValidHashEntry(TMPQArchive * ha, TMPQHash * pHash) -{ - TFileEntry * pFileEntry = ha->pFileTable + MPQ_BLOCK_INDEX(pHash); - - return ((MPQ_BLOCK_INDEX(pHash) < ha->dwFileTableSize) && (pFileEntry->dwFlags & MPQ_FILE_EXISTS)) ? true : false; -} - -// Hash entry verification when the file table does not exist yet -static bool IsValidHashEntry1(TMPQArchive * ha, TMPQHash * pHash, TMPQBlock * pBlockTable) -{ - ULONGLONG ByteOffset; - TMPQBlock * pBlock; - - // The block index is considered valid if it's less than block table size - if(MPQ_BLOCK_INDEX(pHash) < ha->pHeader->dwBlockTableSize) - { - // Calculate the block table position - pBlock = pBlockTable + MPQ_BLOCK_INDEX(pHash); - - // Check whether this is an existing file - // Also we do not allow to be file size greater than 2GB - if((pBlock->dwFlags & MPQ_FILE_EXISTS) && (pBlock->dwFSize & 0x80000000) == 0) - { - // The begin of the file must be within the archive - ByteOffset = FileOffsetFromMpqOffset(ha, pBlock->dwFilePos); - return (ByteOffset < ha->FileSize); - } - } - - return false; -} - -// Returns a hash table entry in the following order: -// 1) A hash table entry with the preferred locale and platform -// 2) A hash table entry with the neutral|matching locale and neutral|matching platform -// 3) NULL -// Storm_2016.dll: 15020940 -static TMPQHash * GetHashEntryLocale(TMPQArchive * ha, const char * szFileName, LCID lcFileLocale) -{ - TMPQHash * pFirstHash = GetFirstHashEntry(ha, szFileName); - TMPQHash * pBestEntry = NULL; - TMPQHash * pHash = pFirstHash; - USHORT Locale = SFILE_LOCALE(lcFileLocale); - BYTE Platform = SFILE_PLATFORM(lcFileLocale); - - // Parse the found hashes - while(pHash != NULL) - { - // Storm_2016.dll: 150209CB - // If the hash entry matches both locale and platform, return it immediately - // Only do that for non-0 locale&platform, because for loc&plat=0, there's different - // processing in Warcraft III vs. Starcraft, which is abused by some protectors. - if((Locale || Platform) && pHash->Locale == Locale && pHash->Platform == Platform) - return pHash; - - // Storm_2016.dll: 150209D9 - // If (locale matches or is neutral) AND (platform matches or is neutral), remember this as the best entry - // Also remember the first matching entry for Starcraft maps - if(pHash->Locale == 0 || pHash->Locale == Locale) - { - if(pHash->Platform == 0 || pHash->Platform == Platform) - { - pBestEntry = pHash; - } - } - - // Get the next hash entry for that file - pHash = GetNextHashEntry(ha, pFirstHash, pHash); - } - - // Return the best entry that we found - return pBestEntry; -} - -// Returns a hash table entry in the following order: -// 1) A hash table entry with the preferred locale&platform -// 2) NULL -// In case there are multiple items with the same locale&platform, -// we need to return the last one. This is because it must correspond to SFileOpenFileEx -static TMPQHash * GetHashEntryExact(TMPQArchive * ha, const char * szFileName, LCID lcFileLocale) -{ - TMPQHash * pFirstHash = GetFirstHashEntry(ha, szFileName); - TMPQHash * pBestHash = NULL; - TMPQHash * pHash = pFirstHash; - USHORT Locale = SFILE_LOCALE(lcFileLocale); - BYTE Platform = SFILE_PLATFORM(lcFileLocale); - - // Parse the found hashes - while(pHash != NULL) - { - // If the locales match, we remember this one as the best one - if(pHash->Locale == Locale && pHash->Platform == Platform) - pBestHash = pHash; - - // Get the next hash entry for that file - pHash = GetNextHashEntry(ha, pFirstHash, pHash); - } - - // Return the best hash or NULL - return pBestHash; -} - -// Defragment the file table so it does not contain any gaps -// Note: As long as all values of all TMPQHash::dwBlockIndex -// are not HASH_ENTRY_FREE, the startup search index does not matter. -// Hash table is circular, so as long as there is no terminator, -// all entries will be found. -/* -static TMPQHash * DefragmentHashTable( - TMPQArchive * ha, - TMPQHash * pHashTable, - TMPQBlock * pBlockTable) -{ - TMPQHeader * pHeader = ha->pHeader; - TMPQHash * pHashTableEnd = pHashTable + pHeader->dwHashTableSize; - TMPQHash * pSource = pHashTable; - TMPQHash * pTarget = pHashTable; - DWORD dwFirstFreeEntry; - DWORD dwNewTableSize; - - // Sanity checks - assert(pHeader->wFormatVersion == MPQ_FORMAT_VERSION_1); - assert(pHeader->HiBlockTablePos64 == 0); - - // Parse the hash table and move the entries to the begin of it - for(pSource = pHashTable; pSource < pHashTableEnd; pSource++) - { - // Check whether this is a valid hash table entry - if(IsValidHashEntry1(ha, pSource, pBlockTable)) - { - // Copy the hash table entry back - if(pSource > pTarget) - pTarget[0] = pSource[0]; - - // Move the target - pTarget++; - } - } - - // Calculate how many entries in the hash table we really need - dwFirstFreeEntry = (DWORD)(pTarget - pHashTable); - dwNewTableSize = GetNearestPowerOfTwo(dwFirstFreeEntry); - - // Fill the rest with entries that look like deleted - pHashTableEnd = pHashTable + dwNewTableSize; - pSource = pHashTable + dwFirstFreeEntry; - memset(pSource, 0xFF, (dwNewTableSize - dwFirstFreeEntry) * sizeof(TMPQHash)); - - // Mark the block indexes as deleted - for(; pSource < pHashTableEnd; pSource++) - pSource->dwBlockIndex = HASH_ENTRY_DELETED; - - // Free some of the space occupied by the hash table - if(dwNewTableSize < pHeader->dwHashTableSize) - { - pHashTable = STORM_REALLOC(TMPQHash, pHashTable, dwNewTableSize); - ha->pHeader->BlockTableSize64 = dwNewTableSize * sizeof(TMPQHash); - ha->pHeader->dwHashTableSize = dwNewTableSize; - } - - return pHashTable; -} -*/ - -static DWORD BuildFileTableFromBlockTable( - TMPQArchive * ha, - TMPQBlock * pBlockTable) -{ - TFileEntry * pFileEntry; - TMPQHeader * pHeader = ha->pHeader; - TMPQBlock * pBlock; - TMPQHash * pHashTableEnd; - TMPQHash * pHash; - LPDWORD DefragmentTable = NULL; - DWORD dwItemCount = 0; - - // Sanity checks - assert(ha->pFileTable != NULL); - assert(ha->dwFileTableSize >= ha->dwMaxFileCount); - - // - // Defragmentation of the hash table was removed. The reason is a MPQ protector, - // two hash entries with the same name, where only the second one is valid. - // The index of the first entry (HashString(szFileName, 0)) points to the second one: - // - // NameA NameB BlkIdx Name - // B701656E FCFB1EED 0000001C staredit\scenario.chk (correct one) - // --> B701656E FCFB1EED 0000001D staredit\scenario.chk (corrupt one) - // - // Defragmenting the hash table corrupts the order and "staredit\scenario.chk" can't be read - // Example MPQ: MPQ_2022_v1_Sniper.scx - // - - //if(ha->dwFlags & MPQ_FLAG_HASH_TABLE_CUT) - //{ - // ha->pHashTable = DefragmentHashTable(ha, ha->pHashTable, pBlockTable); - // ha->dwMaxFileCount = pHeader->dwHashTableSize; - //} - - // If the hash table or block table is cut, - // we will defragment the block table - if(ha->dwFlags & (MPQ_FLAG_HASH_TABLE_CUT | MPQ_FLAG_BLOCK_TABLE_CUT)) - { - // Sanity checks - assert(pHeader->HiBlockTablePos64 == 0); - - // Allocate the translation table - DefragmentTable = STORM_ALLOC(DWORD, pHeader->dwBlockTableSize); - if(DefragmentTable == NULL) - return ERROR_NOT_ENOUGH_MEMORY; - - // Fill the translation table - memset(DefragmentTable, 0xFF, pHeader->dwBlockTableSize * sizeof(DWORD)); - } - - // Parse the entire hash table - pHashTableEnd = ha->pHashTable + pHeader->dwHashTableSize; - for(pHash = ha->pHashTable; pHash < pHashTableEnd; pHash++) - { - // - // We need to properly handle these cases: - // - Multiple hash entries (same file name) point to the same block entry - // - Multiple hash entries (different file name) point to the same block entry - // - // Ignore all hash table entries where: - // - Block Index >= BlockTableSize - // - Flags of the appropriate block table entry - // - - if(IsValidHashEntry1(ha, pHash, pBlockTable)) - { - DWORD dwOldIndex = MPQ_BLOCK_INDEX(pHash); - DWORD dwNewIndex = MPQ_BLOCK_INDEX(pHash); - - // Determine the new block index - if(DefragmentTable != NULL) - { - // Need to handle case when multiple hash - // entries point to the same block entry - if(DefragmentTable[dwOldIndex] == HASH_ENTRY_FREE) - { - DefragmentTable[dwOldIndex] = dwItemCount; - dwNewIndex = dwItemCount++; - } - else - { - dwNewIndex = DefragmentTable[dwOldIndex]; - } - - // Fix the pointer in the hash entry - pHash->dwBlockIndex = dwNewIndex; - - // Dump the relocation entry -// printf("Relocating hash entry %08X-%08X: %08X -> %08X\n", pHash->dwName1, pHash->dwName2, dwBlockIndex, dwNewIndex); - } - - // Get the pointer to the file entry and the block entry - pFileEntry = ha->pFileTable + dwNewIndex; - pBlock = pBlockTable + dwOldIndex; - - // ByteOffset is only valid if file size is not zero - pFileEntry->ByteOffset = pBlock->dwFilePos; - if(pFileEntry->ByteOffset == 0 && pBlock->dwFSize == 0) - pFileEntry->ByteOffset = ha->pHeader->dwHeaderSize; - - // Clear file flags that are unknown to this type of map. - pFileEntry->dwFlags = pBlock->dwFlags & ha->dwValidFileFlags; - - // Fill the rest of the file entry - pFileEntry->dwFileSize = pBlock->dwFSize; - pFileEntry->dwCmpSize = pBlock->dwCSize; - } - } - - // Free the translation table - if(DefragmentTable != NULL) - { - // If we defragmented the block table in the process, - // free some memory by shrinking the file table - if(ha->dwFileTableSize > ha->dwMaxFileCount) - { - ha->pFileTable = STORM_REALLOC(TFileEntry, ha->pFileTable, ha->dwMaxFileCount); - ha->pHeader->BlockTableSize64 = ha->dwMaxFileCount * sizeof(TMPQBlock); - ha->pHeader->dwBlockTableSize = ha->dwMaxFileCount; - ha->dwFileTableSize = ha->dwMaxFileCount; - } - -// DumpFileTable(ha->pFileTable, ha->dwFileTableSize); - - // Free the translation table - STORM_FREE(DefragmentTable); - } - - return ERROR_SUCCESS; -} - -static TMPQHash * TranslateHashTable( - TMPQArchive * ha, - ULONGLONG * pcbTableSize) -{ - TMPQHash * pHashTable; - size_t HashTableSize; - - // Allocate copy of the hash table - pHashTable = STORM_ALLOC(TMPQHash, ha->pHeader->dwHashTableSize); - if(pHashTable != NULL) - { - // Copy the hash table - HashTableSize = sizeof(TMPQHash) * ha->pHeader->dwHashTableSize; - memcpy(pHashTable, ha->pHashTable, HashTableSize); - - // Give the size to the caller - if(pcbTableSize != NULL) - { - *pcbTableSize = (ULONGLONG)HashTableSize; - } - } - - return pHashTable; -} - -// Also used in SFileGetFileInfo -TMPQBlock * TranslateBlockTable( - TMPQArchive * ha, - ULONGLONG * pcbTableSize, - bool * pbNeedHiBlockTable) -{ - TFileEntry * pFileEntry = ha->pFileTable; - TMPQBlock * pBlockTable; - TMPQBlock * pBlock; - DWORD NeedHiBlockTable = 0; - DWORD dwBlockTableSize = ha->pHeader->dwBlockTableSize; - - // Allocate copy of the hash table - pBlockTable = pBlock = STORM_ALLOC(TMPQBlock, dwBlockTableSize); - if(pBlockTable != NULL) - { - // Convert the block table - for(DWORD i = 0; i < dwBlockTableSize; i++) - { - NeedHiBlockTable |= (DWORD)(pFileEntry->ByteOffset >> 32); - pBlock->dwFilePos = (DWORD)pFileEntry->ByteOffset; - pBlock->dwFSize = pFileEntry->dwFileSize; - pBlock->dwCSize = pFileEntry->dwCmpSize; - pBlock->dwFlags = pFileEntry->dwFlags; - - pFileEntry++; - pBlock++; - } - - // Give the size to the caller - if(pcbTableSize != NULL) - *pcbTableSize = (ULONGLONG)dwBlockTableSize * sizeof(TMPQBlock); - - if(pbNeedHiBlockTable != NULL) - *pbNeedHiBlockTable = NeedHiBlockTable ? true : false; - } - - return pBlockTable; -} - -static USHORT * TranslateHiBlockTable( - TMPQArchive * ha, - ULONGLONG * pcbTableSize) -{ - TFileEntry * pFileEntry = ha->pFileTable; - USHORT * pHiBlockTable; - USHORT * pHiBlock; - DWORD dwBlockTableSize = ha->pHeader->dwBlockTableSize; - - // Allocate copy of the hash table - pHiBlockTable = pHiBlock = STORM_ALLOC(USHORT, dwBlockTableSize); - if(pHiBlockTable != NULL) - { - // Copy the block table - for(DWORD i = 0; i < dwBlockTableSize; i++) - pHiBlock[i] = (USHORT)(pFileEntry[i].ByteOffset >> 0x20); - - // Give the size to the caller - if(pcbTableSize != NULL) - *pcbTableSize = (ULONGLONG)dwBlockTableSize * sizeof(USHORT); - } - - return pHiBlockTable; -} - -//----------------------------------------------------------------------------- -// General EXT table functions - -TMPQExtHeader * LoadExtTable( - TMPQArchive * ha, - ULONGLONG ByteOffset, - size_t Size, - DWORD dwSignature, - DWORD dwKey) -{ - TMPQExtHeader * pCompressed = NULL; // Compressed table - TMPQExtHeader * pExtTable = NULL; // Uncompressed table - - // Do nothing if the size is zero - if(ByteOffset != 0 && Size != 0) - { - // Allocate size for the compressed table - pExtTable = (TMPQExtHeader *)STORM_ALLOC(BYTE, Size); - if(pExtTable != NULL) - { - // Load the table from the MPQ - ByteOffset += ha->MpqPos; - if(!FileStream_Read(ha->pStream, &ByteOffset, pExtTable, (DWORD)Size)) - { - STORM_FREE(pExtTable); - return NULL; - } - - // Swap the ext table header - BSWAP_ARRAY32_UNSIGNED(pExtTable, sizeof(TMPQExtHeader)); - if(pExtTable->dwSignature != dwSignature) - { - STORM_FREE(pExtTable); - return NULL; - } - - // Decrypt the block - BSWAP_ARRAY32_UNSIGNED(pExtTable + 1, pExtTable->dwDataSize); - DecryptMpqBlock(pExtTable + 1, (DWORD)(Size - sizeof(TMPQExtHeader)), dwKey); - BSWAP_ARRAY32_UNSIGNED(pExtTable + 1, pExtTable->dwDataSize); - - // If the table is compressed, decompress it - if((pExtTable->dwDataSize + sizeof(TMPQExtHeader)) > Size) - { - pCompressed = pExtTable; - pExtTable = (TMPQExtHeader *)STORM_ALLOC(BYTE, sizeof(TMPQExtHeader) + pCompressed->dwDataSize); - if(pExtTable != NULL) - { - int cbOutBuffer = (int)pCompressed->dwDataSize; - int cbInBuffer = (int)Size; - - // Decompress the extended table - pExtTable->dwSignature = pCompressed->dwSignature; - pExtTable->dwVersion = pCompressed->dwVersion; - pExtTable->dwDataSize = pCompressed->dwDataSize; - if(!SCompDecompress2(pExtTable + 1, &cbOutBuffer, pCompressed + 1, cbInBuffer)) - { - STORM_FREE(pExtTable); - pExtTable = NULL; - } - } - - // Free the compressed block - STORM_FREE(pCompressed); - } - } - } - - // Return the decompressed table to the caller - return pExtTable; -} - -static DWORD SaveMpqTable( - TMPQArchive * ha, - void * pMpqTable, - ULONGLONG ByteOffset, - size_t Size, - unsigned char * md5, - DWORD dwKey, - bool bCompress) -{ - ULONGLONG FileOffset; - void * pCompressed = NULL; - DWORD dwErrCode = ERROR_SUCCESS; - - // Do we have to compress the table? - if(bCompress) - { - int cbOutBuffer = (int)Size; - int cbInBuffer = (int)Size; - - // Allocate extra space for compressed table - pCompressed = STORM_ALLOC(BYTE, Size); - if(pCompressed == NULL) - return ERROR_NOT_ENOUGH_MEMORY; - - // Compress the table - SCompCompress(pCompressed, &cbOutBuffer, pMpqTable, cbInBuffer, MPQ_COMPRESSION_ZLIB, 0, 0); - - // If the compression failed, revert it. Otherwise, swap the tables - if(cbOutBuffer >= cbInBuffer) - { - STORM_FREE(pCompressed); - pCompressed = NULL; - } - else - { - pMpqTable = pCompressed; - } - } - - // Encrypt the table - if(dwKey != 0) - { - BSWAP_ARRAY32_UNSIGNED(pMpqTable, Size); - EncryptMpqBlock(pMpqTable, (DWORD)Size, dwKey); - BSWAP_ARRAY32_UNSIGNED(pMpqTable, Size); - } - - // Calculate the MD5 - if(md5 != NULL) - { - CalculateDataBlockHash(pMpqTable, (DWORD)Size, md5); - } - - // Save the table to the MPQ - BSWAP_ARRAY32_UNSIGNED(pMpqTable, Size); - FileOffset = ha->MpqPos + ByteOffset; - if(!FileStream_Write(ha->pStream, &FileOffset, pMpqTable, (DWORD)Size)) - dwErrCode = GetLastError(); - - // Free the compressed table, if any - if(pCompressed != NULL) - STORM_FREE(pCompressed); - return dwErrCode; -} - -static DWORD SaveExtTable( - TMPQArchive * ha, - TMPQExtHeader * pExtTable, - ULONGLONG ByteOffset, - DWORD dwTableSize, - unsigned char * md5, - DWORD dwKey, - bool bCompress, - LPDWORD pcbTotalSize) -{ - ULONGLONG FileOffset; - TMPQExtHeader * pCompressed = NULL; - DWORD cbTotalSize = 0; - DWORD dwErrCode = ERROR_SUCCESS; - - // Do we have to compress the table? - if(bCompress) - { - int cbOutBuffer = (int)dwTableSize; - int cbInBuffer = (int)dwTableSize; - - // Allocate extra space for compressed table - pCompressed = (TMPQExtHeader *)STORM_ALLOC(BYTE, dwTableSize); - if(pCompressed == NULL) - return ERROR_NOT_ENOUGH_MEMORY; - - // Compress the table - pCompressed->dwSignature = pExtTable->dwSignature; - pCompressed->dwVersion = pExtTable->dwVersion; - pCompressed->dwDataSize = pExtTable->dwDataSize; - SCompCompress((pCompressed + 1), &cbOutBuffer, (pExtTable + 1), cbInBuffer, MPQ_COMPRESSION_ZLIB, 0, 0); - - // If the compression failed, revert it. Otherwise, swap the tables - if(cbOutBuffer >= cbInBuffer) - { - STORM_FREE(pCompressed); - pCompressed = NULL; - } - else - { - pExtTable = pCompressed; - } - } - - // Encrypt the table - if(dwKey != 0) - { - BSWAP_ARRAY32_UNSIGNED(pExtTable + 1, pExtTable->dwDataSize); - EncryptMpqBlock(pExtTable + 1, (DWORD)(dwTableSize - sizeof(TMPQExtHeader)), dwKey); - BSWAP_ARRAY32_UNSIGNED(pExtTable + 1, pExtTable->dwDataSize); - } - - // Calculate the MD5 of the table after - if(md5 != NULL) - { - CalculateDataBlockHash(pExtTable, dwTableSize, md5); - } - - // Save the table to the MPQ - FileOffset = ha->MpqPos + ByteOffset; - if(FileStream_Write(ha->pStream, &FileOffset, pExtTable, dwTableSize)) - cbTotalSize += dwTableSize; - else - dwErrCode = GetLastError(); - - // We have to write raw data MD5 - if(dwErrCode == ERROR_SUCCESS && ha->pHeader->dwRawChunkSize != 0) - { - dwErrCode = WriteMemDataMD5(ha->pStream, - FileOffset, - pExtTable, - dwTableSize, - ha->pHeader->dwRawChunkSize, - &cbTotalSize); - } - - // Give the total written size, if needed - if(pcbTotalSize != NULL) - *pcbTotalSize = cbTotalSize; - - // Free the compressed table, if any - if(pCompressed != NULL) - STORM_FREE(pCompressed); - return dwErrCode; -} - -//----------------------------------------------------------------------------- -// Support for HET table - -static void CreateHetHeader( - TMPQHetTable * pHetTable, - TMPQHetHeader * pHetHeader) -{ - // Fill the common header - pHetHeader->ExtHdr.dwSignature = HET_TABLE_SIGNATURE; - pHetHeader->ExtHdr.dwVersion = 1; - pHetHeader->ExtHdr.dwDataSize = 0; - - // Fill the HET header - pHetHeader->dwEntryCount = pHetTable->dwEntryCount; - pHetHeader->dwTotalCount = pHetTable->dwTotalCount; - pHetHeader->dwNameHashBitSize = pHetTable->dwNameHashBitSize; - pHetHeader->dwIndexSizeTotal = pHetTable->dwIndexSizeTotal; - pHetHeader->dwIndexSizeExtra = pHetTable->dwIndexSizeExtra; - pHetHeader->dwIndexSize = pHetTable->dwIndexSize; - pHetHeader->dwIndexTableSize = ((pHetHeader->dwIndexSizeTotal * pHetTable->dwTotalCount) + 7) / 8; - - // Calculate the total size needed for holding HET table - pHetHeader->ExtHdr.dwDataSize = - pHetHeader->dwTableSize = sizeof(TMPQHetHeader) - sizeof(TMPQExtHeader) + - pHetHeader->dwTotalCount + - pHetHeader->dwIndexTableSize; -} - -TMPQHetTable * CreateHetTable(DWORD dwEntryCount, DWORD dwTotalCount, DWORD dwNameHashBitSize, LPBYTE pbSrcData) -{ - TMPQHetTable * pHetTable; - - pHetTable = STORM_ALLOC(TMPQHetTable, 1); - if(pHetTable != NULL) - { - // Zero the HET table - memset(pHetTable, 0, sizeof(TMPQHetTable)); - - // Hash sizes less than 0x40 bits are not tested - assert(dwNameHashBitSize == 0x40); - - // Calculate masks - pHetTable->AndMask64 = ((dwNameHashBitSize != 0x40) ? ((ULONGLONG)1 << dwNameHashBitSize) : 0) - 1; - pHetTable->OrMask64 = (ULONGLONG)1 << (dwNameHashBitSize - 1); - - // If the total count is not entered, use default - if(dwTotalCount == 0) - dwTotalCount = (dwEntryCount * 4) / 3; - - // Store the HET table parameters - pHetTable->dwEntryCount = dwEntryCount; - pHetTable->dwTotalCount = dwTotalCount; - pHetTable->dwNameHashBitSize = dwNameHashBitSize; - pHetTable->dwIndexSizeTotal = GetNecessaryBitCount(dwEntryCount); - pHetTable->dwIndexSizeExtra = 0; - pHetTable->dwIndexSize = pHetTable->dwIndexSizeTotal; - - // Allocate array of hashes - pHetTable->pNameHashes = STORM_ALLOC(BYTE, dwTotalCount); - if(pHetTable->pNameHashes != NULL) - { - // Make sure the data are initialized - memset(pHetTable->pNameHashes, 0, dwTotalCount); - - // Allocate the bit array for file indexes - pHetTable->pBetIndexes = TMPQBits::Create(dwTotalCount * pHetTable->dwIndexSizeTotal, 0xFF); - if(pHetTable->pBetIndexes != NULL) - { - // Initialize the HET table from the source data (if given) - if(pbSrcData != NULL) - { - // Copy the name hashes - memcpy(pHetTable->pNameHashes, pbSrcData, dwTotalCount); - - // Copy the file indexes - memcpy(pHetTable->pBetIndexes->Elements, pbSrcData + dwTotalCount, pHetTable->pBetIndexes->NumberOfBytes); - } - - // Return the result HET table - return pHetTable; - } - - // Free the name hashes - STORM_FREE(pHetTable->pNameHashes); - } - - STORM_FREE(pHetTable); - } - - // Failed - return NULL; -} - -static DWORD InsertHetEntry(TMPQHetTable * pHetTable, ULONGLONG FileNameHash, DWORD dwFileIndex) -{ - DWORD StartIndex; - DWORD Index; - BYTE NameHash1; - - // Get the start index and the high 8 bits of the name hash - StartIndex = Index = (DWORD)(FileNameHash % pHetTable->dwTotalCount); - NameHash1 = (BYTE)(FileNameHash >> (pHetTable->dwNameHashBitSize - 8)); - - // Find a place where to put it - for(;;) - { - // Did we find a free HET entry? - if(pHetTable->pNameHashes[Index] == HET_ENTRY_FREE) - { - // Set the entry in the name hash table - pHetTable->pNameHashes[Index] = NameHash1; - - // Set the entry in the file index table - pHetTable->pBetIndexes->SetBits(pHetTable->dwIndexSizeTotal * Index, - pHetTable->dwIndexSize, - &dwFileIndex, - 4); - return ERROR_SUCCESS; - } - - // Move to the next entry in the HET table - // If we came to the start index again, we are done - Index = (Index + 1) % pHetTable->dwTotalCount; - if(Index == StartIndex) - break; - } - - // No space in the HET table. Should never happen, - // because the HET table is created according to the number of files - assert(false); - return ERROR_DISK_FULL; -} - -static TMPQHetTable * TranslateHetTable(TMPQHetHeader * pHetHeader) -{ - TMPQHetTable * pHetTable = NULL; - LPBYTE pbSrcData = (LPBYTE)(pHetHeader + 1); - - // Sanity check - assert(pHetHeader->ExtHdr.dwSignature == HET_TABLE_SIGNATURE); - assert(pHetHeader->ExtHdr.dwVersion == 1); - - // Verify size of the HET table - if(pHetHeader->ExtHdr.dwDataSize >= (sizeof(TMPQHetHeader) - sizeof(TMPQExtHeader))) - { - // Verify the size of the table in the header - if(pHetHeader->ExtHdr.dwDataSize >= pHetHeader->dwTableSize) - { - // The size of the HET table must be sum of header, hash and index table size - if((sizeof(TMPQHetHeader) - sizeof(TMPQExtHeader) + pHetHeader->dwTotalCount + pHetHeader->dwIndexTableSize) == pHetHeader->dwTableSize) - { - // So far, all MPQs with HET Table have had total number of entries equal to 4/3 of file count - // Exception: "2010 - Starcraft II\!maps\Tya's Zerg Defense (unprotected).SC2Map" -// assert(((pHetHeader->dwEntryCount * 4) / 3) == pHetHeader->dwTotalCount); - - // The size of one index is predictable as well - assert(GetNecessaryBitCount(pHetHeader->dwEntryCount) == pHetHeader->dwIndexSizeTotal); - - // The size of index table (in entries) is expected - // to be the same like the hash table size (in bytes) - assert(((pHetHeader->dwTotalCount * pHetHeader->dwIndexSizeTotal) + 7) / 8 == pHetHeader->dwIndexTableSize); - - // Create translated table - pHetTable = CreateHetTable(pHetHeader->dwEntryCount, pHetHeader->dwTotalCount, pHetHeader->dwNameHashBitSize, pbSrcData); - if(pHetTable != NULL) - { - // Now the sizes in the hash table should be already set - assert(pHetTable->dwEntryCount == pHetHeader->dwEntryCount); - assert(pHetTable->dwTotalCount == pHetHeader->dwTotalCount); - assert(pHetTable->dwIndexSizeTotal == pHetHeader->dwIndexSizeTotal); - - // Copy the missing variables - pHetTable->dwIndexSizeExtra = pHetHeader->dwIndexSizeExtra; - pHetTable->dwIndexSize = pHetHeader->dwIndexSize; - } - } - } - } - - return pHetTable; -} - -static TMPQExtHeader * TranslateHetTable(TMPQHetTable * pHetTable, ULONGLONG * pcbHetTable) -{ - TMPQHetHeader * pHetHeader = NULL; - TMPQHetHeader HetHeader; - LPBYTE pbLinearTable = NULL; - LPBYTE pbTrgData; - - // Prepare header of the HET table - CreateHetHeader(pHetTable, &HetHeader); - - // Allocate space for the linear table - pbLinearTable = STORM_ALLOC(BYTE, sizeof(TMPQExtHeader) + HetHeader.dwTableSize); - if(pbLinearTable != NULL) - { - // Copy the table header - pHetHeader = (TMPQHetHeader *)pbLinearTable; - memcpy(pHetHeader, &HetHeader, sizeof(TMPQHetHeader)); - pbTrgData = (LPBYTE)(pHetHeader + 1); - - // Copy the array of name hashes - memcpy(pbTrgData, pHetTable->pNameHashes, pHetTable->dwTotalCount); - pbTrgData += pHetTable->dwTotalCount; - - // Copy the bit array of BET indexes - memcpy(pbTrgData, pHetTable->pBetIndexes->Elements, HetHeader.dwIndexTableSize); - - // Calculate the total size of the table, including the TMPQExtHeader - if(pcbHetTable != NULL) - { - *pcbHetTable = (ULONGLONG)(sizeof(TMPQExtHeader) + HetHeader.dwTableSize); - } - } - - // Keep Coverity happy - assert((TMPQExtHeader *)&pHetHeader->ExtHdr == (TMPQExtHeader *)pbLinearTable); - return (TMPQExtHeader *)pbLinearTable; -} - -static DWORD GetFileIndex_Het(TMPQArchive * ha, const char * szFileName) -{ - TMPQHetTable * pHetTable = ha->pHetTable; - ULONGLONG FileNameHash; - DWORD StartIndex; - DWORD Index; - BYTE NameHash1; // Upper 8 bits of the masked file name hash - - // If there are no entries in the HET table, do nothing - if(pHetTable->dwEntryCount == 0) - return HASH_ENTRY_FREE; - - // Do nothing if the MPQ has no HET table - assert(ha->pHetTable != NULL); - - // Calculate 64-bit hash of the file name - FileNameHash = (HashStringJenkins(szFileName) & pHetTable->AndMask64) | pHetTable->OrMask64; - - // Split the file name hash into two parts: - // NameHash1: The highest 8 bits of the name hash - // NameHash2: File name hash limited to hash size - // Note: Our file table contains full name hash, no need to cut the high 8 bits before comparison - NameHash1 = (BYTE)(FileNameHash >> (pHetTable->dwNameHashBitSize - 8)); - - // Calculate the starting index to the hash table - StartIndex = Index = (DWORD)(FileNameHash % pHetTable->dwTotalCount); - - // Go through HET table until we find a terminator - while(pHetTable->pNameHashes[Index] != HET_ENTRY_FREE) - { - // Did we find a match ? - if(pHetTable->pNameHashes[Index] == NameHash1) - { - DWORD dwFileIndex = 0; - - // Get the file index - pHetTable->pBetIndexes->GetBits(pHetTable->dwIndexSizeTotal * Index, - pHetTable->dwIndexSize, - &dwFileIndex, - sizeof(DWORD)); - - // Verify the FileNameHash against the entry in the table of name hashes - if(dwFileIndex <= ha->dwFileTableSize && ha->pFileTable[dwFileIndex].FileNameHash == FileNameHash) - { - return dwFileIndex; - } - } - - // Move to the next entry in the HET table - // If we came to the start index again, we are done - Index = (Index + 1) % pHetTable->dwTotalCount; - if(Index == StartIndex) - break; - } - - // File not found - return HASH_ENTRY_FREE; -} - -void FreeHetTable(TMPQHetTable * pHetTable) -{ - if(pHetTable != NULL) - { - if(pHetTable->pNameHashes != NULL) - STORM_FREE(pHetTable->pNameHashes); - if(pHetTable->pBetIndexes != NULL) - STORM_FREE(pHetTable->pBetIndexes); - - STORM_FREE(pHetTable); - } -} - -//----------------------------------------------------------------------------- -// Support for BET table - -static void CreateBetHeader( - TMPQArchive * ha, - TMPQBetHeader * pBetHeader) -{ - TFileEntry * pFileTableEnd = ha->pFileTable + ha->dwFileTableSize; - TFileEntry * pFileEntry; - ULONGLONG MaxByteOffset = 0; - DWORD FlagArray[MAX_FLAG_INDEX]; - DWORD dwMaxFlagIndex = 0; - DWORD dwMaxFileSize = 0; - DWORD dwMaxCmpSize = 0; - DWORD dwFlagIndex; - - // Initialize array of flag combinations - InitFileFlagArray(FlagArray); - - // Fill the common header - pBetHeader->ExtHdr.dwSignature = BET_TABLE_SIGNATURE; - pBetHeader->ExtHdr.dwVersion = 1; - pBetHeader->ExtHdr.dwDataSize = 0; - - // Get the maximum values for the BET table - pFileTableEnd = ha->pFileTable + ha->pHeader->dwBlockTableSize; - for(pFileEntry = ha->pFileTable; pFileEntry < pFileTableEnd; pFileEntry++) - { - // - // Note: Deleted files must be counted as well - // - - // Highest file position in the MPQ - if(pFileEntry->ByteOffset > MaxByteOffset) - MaxByteOffset = pFileEntry->ByteOffset; - - // Biggest file size - if(pFileEntry->dwFileSize > dwMaxFileSize) - dwMaxFileSize = pFileEntry->dwFileSize; - - // Biggest compressed size - if(pFileEntry->dwCmpSize > dwMaxCmpSize) - dwMaxCmpSize = pFileEntry->dwCmpSize; - - // Check if this flag was there before - dwFlagIndex = GetFileFlagIndex(FlagArray, pFileEntry->dwFlags); - if(dwFlagIndex > dwMaxFlagIndex) - dwMaxFlagIndex = dwFlagIndex; - } - - // Now save bit count for every piece of file information - pBetHeader->dwBitIndex_FilePos = 0; - pBetHeader->dwBitCount_FilePos = GetNecessaryBitCount(MaxByteOffset); - - pBetHeader->dwBitIndex_FileSize = pBetHeader->dwBitIndex_FilePos + pBetHeader->dwBitCount_FilePos; - pBetHeader->dwBitCount_FileSize = GetNecessaryBitCount(dwMaxFileSize); - - pBetHeader->dwBitIndex_CmpSize = pBetHeader->dwBitIndex_FileSize + pBetHeader->dwBitCount_FileSize; - pBetHeader->dwBitCount_CmpSize = GetNecessaryBitCount(dwMaxCmpSize); - - pBetHeader->dwBitIndex_FlagIndex = pBetHeader->dwBitIndex_CmpSize + pBetHeader->dwBitCount_CmpSize; - pBetHeader->dwBitCount_FlagIndex = GetNecessaryBitCount(dwMaxFlagIndex + 1); - - pBetHeader->dwBitIndex_Unknown = pBetHeader->dwBitIndex_FlagIndex + pBetHeader->dwBitCount_FlagIndex; - pBetHeader->dwBitCount_Unknown = 0; - - // Calculate the total size of one entry - pBetHeader->dwTableEntrySize = pBetHeader->dwBitCount_FilePos + - pBetHeader->dwBitCount_FileSize + - pBetHeader->dwBitCount_CmpSize + - pBetHeader->dwBitCount_FlagIndex + - pBetHeader->dwBitCount_Unknown; - - // Save the file count and flag count - pBetHeader->dwEntryCount = ha->pHeader->dwBlockTableSize; - pBetHeader->dwFlagCount = dwMaxFlagIndex + 1; - pBetHeader->dwUnknown08 = 0x10; - - // Save the total size of the BET hash - pBetHeader->dwBitTotal_NameHash2 = ha->pHetTable->dwNameHashBitSize - 0x08; - pBetHeader->dwBitExtra_NameHash2 = 0; - pBetHeader->dwBitCount_NameHash2 = pBetHeader->dwBitTotal_NameHash2; - pBetHeader->dwNameHashArraySize = ((pBetHeader->dwBitTotal_NameHash2 * pBetHeader->dwEntryCount) + 7) / 8; - - // Save the total table size - pBetHeader->ExtHdr.dwDataSize = - pBetHeader->dwTableSize = sizeof(TMPQBetHeader) - sizeof(TMPQExtHeader) + - pBetHeader->dwFlagCount * sizeof(DWORD) + - ((pBetHeader->dwTableEntrySize * pBetHeader->dwEntryCount) + 7) / 8 + - pBetHeader->dwNameHashArraySize; -} - -TMPQBetTable * CreateBetTable(DWORD dwEntryCount) -{ - TMPQBetTable * pBetTable; - - // Allocate BET table - pBetTable = STORM_ALLOC(TMPQBetTable, 1); - if(pBetTable != NULL) - { - memset(pBetTable, 0, sizeof(TMPQBetTable)); - pBetTable->dwEntryCount = dwEntryCount; - } - - return pBetTable; -} - -static TMPQBetTable * TranslateBetTable( - TMPQArchive * ha, - TMPQBetHeader * pBetHeader) -{ - TMPQBetTable * pBetTable = NULL; - LPBYTE pbSrcData = (LPBYTE)(pBetHeader + 1); - DWORD LengthInBytes = 0; - - // Sanity check - assert(pBetHeader->ExtHdr.dwSignature == BET_TABLE_SIGNATURE); - assert(pBetHeader->ExtHdr.dwVersion == 1); - assert(ha->pHetTable != NULL); - ha = ha; - - // Verify size of the HET table - if(pBetHeader->ExtHdr.dwDataSize >= (sizeof(TMPQBetHeader) - sizeof(TMPQExtHeader))) - { - // Verify the size of the table in the header - if(pBetHeader->ExtHdr.dwDataSize >= pBetHeader->dwTableSize) - { - // The number of entries in the BET table must be the same like number of entries in the block table - // Note: Ignored if there is no block table - //assert(pBetHeader->dwEntryCount == ha->pHeader->dwBlockTableSize); - assert(pBetHeader->dwEntryCount <= ha->dwMaxFileCount); - - // The number of entries in the BET table must be the same like number of entries in the HET table - // Note that if it's not, it is not a problem - //assert(pBetHeader->dwEntryCount == ha->pHetTable->dwEntryCount); - - // Create translated table - pBetTable = CreateBetTable(pBetHeader->dwEntryCount); - if(pBetTable != NULL) - { - // Copy the variables from the header to the BetTable - pBetTable->dwTableEntrySize = pBetHeader->dwTableEntrySize; - pBetTable->dwBitIndex_FilePos = pBetHeader->dwBitIndex_FilePos; - pBetTable->dwBitIndex_FileSize = pBetHeader->dwBitIndex_FileSize; - pBetTable->dwBitIndex_CmpSize = pBetHeader->dwBitIndex_CmpSize; - pBetTable->dwBitIndex_FlagIndex = pBetHeader->dwBitIndex_FlagIndex; - pBetTable->dwBitIndex_Unknown = pBetHeader->dwBitIndex_Unknown; - pBetTable->dwBitCount_FilePos = pBetHeader->dwBitCount_FilePos; - pBetTable->dwBitCount_FileSize = pBetHeader->dwBitCount_FileSize; - pBetTable->dwBitCount_CmpSize = pBetHeader->dwBitCount_CmpSize; - pBetTable->dwBitCount_FlagIndex = pBetHeader->dwBitCount_FlagIndex; - pBetTable->dwBitCount_Unknown = pBetHeader->dwBitCount_Unknown; - - // Since we don't know what the "unknown" is, we'll assert when it's zero - assert(pBetTable->dwBitCount_Unknown == 0); - - // Allocate array for flags - if(pBetHeader->dwFlagCount != 0) - { - // Allocate array for file flags and load it - pBetTable->pFileFlags = STORM_ALLOC(DWORD, pBetHeader->dwFlagCount); - if(pBetTable->pFileFlags != NULL) - { - LengthInBytes = pBetHeader->dwFlagCount * sizeof(DWORD); - memcpy(pBetTable->pFileFlags, pbSrcData, LengthInBytes); - BSWAP_ARRAY32_UNSIGNED(pBetTable->pFileFlags, LengthInBytes); - pbSrcData += LengthInBytes; - } - - // Save the number of flags - pBetTable->dwFlagCount = pBetHeader->dwFlagCount; - } - - // Load the bit-based file table - pBetTable->pFileTable = TMPQBits::Create(pBetTable->dwTableEntrySize * pBetHeader->dwEntryCount, 0); - if(pBetTable->pFileTable != NULL) - { - LengthInBytes = (pBetTable->pFileTable->NumberOfBits + 7) / 8; - memcpy(pBetTable->pFileTable->Elements, pbSrcData, LengthInBytes); - pbSrcData += LengthInBytes; - } - - // Fill the sizes of BET hash - pBetTable->dwBitTotal_NameHash2 = pBetHeader->dwBitTotal_NameHash2; - pBetTable->dwBitExtra_NameHash2 = pBetHeader->dwBitExtra_NameHash2; - pBetTable->dwBitCount_NameHash2 = pBetHeader->dwBitCount_NameHash2; - - // Create and load the array of BET hashes - pBetTable->pNameHashes = TMPQBits::Create(pBetTable->dwBitTotal_NameHash2 * pBetHeader->dwEntryCount, 0); - if(pBetTable->pNameHashes != NULL) - { - LengthInBytes = (pBetTable->pNameHashes->NumberOfBits + 7) / 8; - memcpy(pBetTable->pNameHashes->Elements, pbSrcData, LengthInBytes); -// pbSrcData += LengthInBytes; - } - - // Dump both tables -// DumpHetAndBetTable(ha->pHetTable, pBetTable); - } - } - } - - return pBetTable; -} - -TMPQExtHeader * TranslateBetTable( - TMPQArchive * ha, - ULONGLONG * pcbBetTable) -{ - TMPQBetHeader * pBetHeader = NULL; - TMPQBetHeader BetHeader; - TFileEntry * pFileTableEnd = ha->pFileTable + ha->dwFileTableSize; - TFileEntry * pFileEntry; - TMPQBits * pBitArray = NULL; - LPBYTE pbLinearTable = NULL; - LPBYTE pbTrgData; - DWORD LengthInBytes; - DWORD FlagArray[MAX_FLAG_INDEX]; - - // Calculate the bit sizes of various entries - InitFileFlagArray(FlagArray); - CreateBetHeader(ha, &BetHeader); - - // Allocate space - pbLinearTable = STORM_ALLOC(BYTE, sizeof(TMPQExtHeader) + BetHeader.dwTableSize); - if(pbLinearTable != NULL) - { - // Copy the BET header to the linear buffer - pBetHeader = (TMPQBetHeader *)pbLinearTable; - memcpy(pBetHeader, &BetHeader, sizeof(TMPQBetHeader)); - pbTrgData = (LPBYTE)(pBetHeader + 1); - - // Save the bit-based block table - pBitArray = TMPQBits::Create(BetHeader.dwEntryCount * BetHeader.dwTableEntrySize, 0); - if(pBitArray != NULL) - { - DWORD dwFlagIndex = 0; - DWORD nBitOffset = 0; - - // Construct the bit-based file table - pFileTableEnd = ha->pFileTable + BetHeader.dwEntryCount; - for(pFileEntry = ha->pFileTable; pFileEntry < pFileTableEnd; pFileEntry++) - { - // - // Note: Missing files must be included as well - // - - // Save the byte offset - pBitArray->SetBits(nBitOffset + BetHeader.dwBitIndex_FilePos, - BetHeader.dwBitCount_FilePos, - &pFileEntry->ByteOffset, - 8); - pBitArray->SetBits(nBitOffset + BetHeader.dwBitIndex_FileSize, - BetHeader.dwBitCount_FileSize, - &pFileEntry->dwFileSize, - 4); - pBitArray->SetBits(nBitOffset + BetHeader.dwBitIndex_CmpSize, - BetHeader.dwBitCount_CmpSize, - &pFileEntry->dwCmpSize, - 4); - - // Save the flag index - dwFlagIndex = GetFileFlagIndex(FlagArray, pFileEntry->dwFlags); - pBitArray->SetBits(nBitOffset + BetHeader.dwBitIndex_FlagIndex, - BetHeader.dwBitCount_FlagIndex, - &dwFlagIndex, - 4); - - // Move the bit offset - nBitOffset += BetHeader.dwTableEntrySize; - } - - // Write the array of flags - LengthInBytes = BetHeader.dwFlagCount * sizeof(DWORD); - memcpy(pbTrgData, FlagArray, LengthInBytes); - BSWAP_ARRAY32_UNSIGNED(pbTrgData, LengthInBytes); - pbTrgData += LengthInBytes; - - // Write the bit-based block table - LengthInBytes = (pBitArray->NumberOfBits + 7) / 8; - memcpy(pbTrgData, pBitArray->Elements, LengthInBytes); - pbTrgData += LengthInBytes; - - // Free the bit array - STORM_FREE(pBitArray); - } - - // Create bit array for name hashes - pBitArray = TMPQBits::Create(BetHeader.dwBitTotal_NameHash2 * BetHeader.dwEntryCount, 0); - if(pBitArray != NULL) - { - DWORD dwFileIndex = 0; - - for(pFileEntry = ha->pFileTable; pFileEntry < pFileTableEnd; pFileEntry++) - { - // Insert the name hash to the bit array - pBitArray->SetBits(BetHeader.dwBitTotal_NameHash2 * dwFileIndex, - BetHeader.dwBitCount_NameHash2, - &pFileEntry->FileNameHash, - 8); - - assert(dwFileIndex < BetHeader.dwEntryCount); - dwFileIndex++; - } - - // Write the array of BET hashes - LengthInBytes = (pBitArray->NumberOfBits + 7) / 8; - memcpy(pbTrgData, pBitArray->Elements, LengthInBytes); -// pbTrgData += LengthInBytes; - - // Free the bit array - STORM_FREE(pBitArray); - } - - // Write the size of the BET table in the MPQ - if(pcbBetTable != NULL) - { - *pcbBetTable = (ULONGLONG)(sizeof(TMPQExtHeader) + BetHeader.dwTableSize); - } - } - - // Keep Coverity happy - assert((TMPQExtHeader *)&pBetHeader->ExtHdr == (TMPQExtHeader *)pbLinearTable); - return (TMPQExtHeader *)pbLinearTable; -} - -void FreeBetTable(TMPQBetTable * pBetTable) -{ - if(pBetTable != NULL) - { - if(pBetTable->pFileTable != NULL) - STORM_FREE(pBetTable->pFileTable); - if(pBetTable->pFileFlags != NULL) - STORM_FREE(pBetTable->pFileFlags); - if(pBetTable->pNameHashes != NULL) - STORM_FREE(pBetTable->pNameHashes); - - STORM_FREE(pBetTable); - } -} - -//----------------------------------------------------------------------------- -// Support for file table - -TFileEntry * GetFileEntryLocale(TMPQArchive * ha, const char * szFileName, LCID lcFileLocale, LPDWORD PtrHashIndex) -{ - TMPQHash * pHash; - DWORD dwFileIndex; - - // First, we have to search the classic hash table - // This is because on renaming, deleting, or changing locale, - // we will need the pointer to hash table entry - if(ha->pHashTable != NULL) - { - pHash = GetHashEntryLocale(ha, szFileName, lcFileLocale); - if(pHash != NULL && MPQ_BLOCK_INDEX(pHash) < ha->dwFileTableSize) - { - if(PtrHashIndex != NULL) - PtrHashIndex[0] = (DWORD)(pHash - ha->pHashTable); - return ha->pFileTable + MPQ_BLOCK_INDEX(pHash); - } - } - - // If we have HET table in the MPQ, try to find the file in HET table - if(ha->pHetTable != NULL) - { - dwFileIndex = GetFileIndex_Het(ha, szFileName); - if(dwFileIndex != HASH_ENTRY_FREE) - return ha->pFileTable + dwFileIndex; - } - - // Not found - return NULL; -} - -TFileEntry * GetFileEntryExact(TMPQArchive * ha, const char * szFileName, LCID lcFileLocale, LPDWORD PtrHashIndex) -{ - TMPQHash * pHash; - DWORD dwFileIndex; - - // If the hash table is present, find the entry from hash table - if(ha->pHashTable != NULL) - { - pHash = GetHashEntryExact(ha, szFileName, lcFileLocale); - if(pHash != NULL && MPQ_BLOCK_INDEX(pHash) < ha->dwFileTableSize) - { - if(PtrHashIndex != NULL) - PtrHashIndex[0] = (DWORD)(pHash - ha->pHashTable); - return ha->pFileTable + MPQ_BLOCK_INDEX(pHash); - } - } - - // If we have HET table in the MPQ, try to find the file in HET table - if(ha->pHetTable != NULL) - { - dwFileIndex = GetFileIndex_Het(ha, szFileName); - if(dwFileIndex != HASH_ENTRY_FREE) - { - if(PtrHashIndex != NULL) - PtrHashIndex[0] = HASH_ENTRY_FREE; - return ha->pFileTable + dwFileIndex; - } - } - - // Not found - return NULL; -} - -void AllocateFileName(TMPQArchive * ha, TFileEntry * pFileEntry, const char * szFileName) -{ - // Sanity check - assert(pFileEntry != NULL); - - // If the file name is pseudo file name, free it at this point - if(IsPseudoFileName(pFileEntry->szFileName, NULL)) - { - if(pFileEntry->szFileName != NULL) - STORM_FREE(pFileEntry->szFileName); - pFileEntry->szFileName = NULL; - } - - // Only allocate new file name if it's not there yet - if(pFileEntry->szFileName == NULL) - { - pFileEntry->szFileName = STORM_ALLOC(char, strlen(szFileName) + 1); - if(pFileEntry->szFileName != NULL) - strcpy(pFileEntry->szFileName, szFileName); - } - - // We also need to create the file name hash - if(ha->pHetTable != NULL) - { - ULONGLONG AndMask64 = ha->pHetTable->AndMask64; - ULONGLONG OrMask64 = ha->pHetTable->OrMask64; - - pFileEntry->FileNameHash = (HashStringJenkins(szFileName) & AndMask64) | OrMask64; - } -} - -TFileEntry * AllocateFileEntry(TMPQArchive * ha, const char * szFileName, LCID lcFileLocale, LPDWORD PtrHashIndex) -{ - TFileEntry * pFileTableEnd = ha->pFileTable + ha->dwFileTableSize; - TFileEntry * pFreeEntry = NULL; - TFileEntry * pFileEntry; - TMPQHash * pHash = NULL; - DWORD dwReservedFiles = ha->dwReservedFiles; - DWORD dwFreeCount = 0; - - // Sanity check: File table size must be greater or equal to max file count - assert(ha->dwFileTableSize >= ha->dwMaxFileCount); - - // If we are saving MPQ tables, we don't tale number of reserved files into account - dwReservedFiles = (ha->dwFlags & MPQ_FLAG_SAVING_TABLES) ? 0 : ha->dwReservedFiles; - - // Now find a free entry in the file table. - // Note that in the case when free entries are in the middle, - // we need to use these - for(pFileEntry = ha->pFileTable; pFileEntry < pFileTableEnd; pFileEntry++) - { - if((pFileEntry->dwFlags & MPQ_FILE_EXISTS) == 0) - { - // Remember the first free entry - if(pFreeEntry == NULL) - pFreeEntry = pFileEntry; - dwFreeCount++; - - // If the number of free items is greater than number - // of reserved items, We can add the file - if(dwFreeCount > dwReservedFiles) - break; - } - } - - // If the total number of free entries is less than number of reserved files, - // we cannot add the file to the archive - if(pFreeEntry == NULL || dwFreeCount <= dwReservedFiles) - return NULL; - - // Initialize the file entry and set its file name - memset(pFreeEntry, 0, sizeof(TFileEntry)); - AllocateFileName(ha, pFreeEntry, szFileName); - - // If the archive has a hash table, we need to first free entry there - if(ha->pHashTable != NULL) - { - // Make sure that the entry is not there yet - assert(GetHashEntryExact(ha, szFileName, lcFileLocale) == NULL); - - // Find a free hash table entry for the name - pHash = AllocateHashEntry(ha, pFreeEntry, lcFileLocale); - if(pHash == NULL) - return NULL; - - // Set the file index to the hash table - pHash->dwBlockIndex = (DWORD)(pFreeEntry - ha->pFileTable); - PtrHashIndex[0] = (DWORD)(pHash - ha->pHashTable); - } - - // If the archive has a HET table, just do some checks - // Note: Don't bother modifying the HET table. It will be rebuilt from scratch after, anyway - if(ha->pHetTable != NULL) - { - assert(GetFileIndex_Het(ha, szFileName) == HASH_ENTRY_FREE); - } - - // Return the free table entry - return pFreeEntry; -} - -DWORD RenameFileEntry( - TMPQArchive * ha, - TMPQFile * hf, - const char * szNewFileName) -{ - TFileEntry * pFileEntry = hf->pFileEntry; - TMPQHash * pHashEntry = hf->pHashEntry; - LCID lcFileLocale = 0; - - // If the archive hash hash table, we need to free the hash table entry - if(ha->pHashTable != NULL) - { - // The file must have hash table entry assigned - // Will exit if there are multiple HASH entries pointing to the same file entry - if(pHashEntry == NULL) - return ERROR_NOT_SUPPORTED; - - // Save the locale - lcFileLocale = SFILE_MAKE_LCID(pHashEntry->Locale, pHashEntry->Platform); - - // Mark the hash table entry as deleted - pHashEntry->dwName1 = 0xFFFFFFFF; - pHashEntry->dwName2 = 0xFFFFFFFF; - pHashEntry->Locale = 0xFFFF; - pHashEntry->Platform = 0xFF; - pHashEntry->Reserved = 0xFF; - pHashEntry->dwBlockIndex = HASH_ENTRY_DELETED; - } - - // Free the old file name - if(pFileEntry->szFileName != NULL) - STORM_FREE(pFileEntry->szFileName); - pFileEntry->szFileName = NULL; - - // Allocate new file name - AllocateFileName(ha, pFileEntry, szNewFileName); - - // Allocate new hash entry - if(ha->pHashTable != NULL) - { - // Since we freed one hash entry before, this must succeed - hf->pHashEntry = AllocateHashEntry(ha, pFileEntry, lcFileLocale); - assert(hf->pHashEntry != NULL); - } - - return ERROR_SUCCESS; -} - -DWORD DeleteFileEntry(TMPQArchive * ha, TMPQFile * hf) -{ - TFileEntry * pFileEntry = hf->pFileEntry; - TMPQHash * pHashEntry = hf->pHashEntry; - - // If the archive hash hash table, we need to free the hash table entry - if(ha->pHashTable != NULL) - { - // The file must have hash table entry assigned - // Will exit if there are multiple HASH entries pointing to the same file entry - if(pHashEntry == NULL) - return ERROR_NOT_SUPPORTED; - - // Mark the hash table entry as deleted - pHashEntry->dwName1 = 0xFFFFFFFF; - pHashEntry->dwName2 = 0xFFFFFFFF; - pHashEntry->Locale = 0xFFFF; - pHashEntry->Platform = 0xFF; - pHashEntry->Reserved = 0xFF; - pHashEntry->dwBlockIndex = HASH_ENTRY_DELETED; - } - - // Free the file name, and set the file entry as deleted - if(pFileEntry->szFileName != NULL) - STORM_FREE(pFileEntry->szFileName); - pFileEntry->szFileName = NULL; - - // - // Don't modify the HET table, because it gets recreated by the caller - // Don't decrement the number of entries in the file table - // Keep Byte Offset, file size, compressed size, CRC32 and MD5 - // Clear the file name hash and the MPQ_FILE_EXISTS bit - // - - pFileEntry->dwFlags &= ~MPQ_FILE_EXISTS; - pFileEntry->FileNameHash = 0; - return ERROR_SUCCESS; -} - -DWORD InvalidateInternalFile(TMPQArchive * ha, const char * szFileName, DWORD dwFlagNone, DWORD dwFlagNew, DWORD dwForceAddTheFile = 0) -{ - TMPQFile * hf = NULL; - DWORD dwFileFlags = MPQ_FILE_DEFAULT_INTERNAL; - DWORD dwErrCode = ERROR_FILE_NOT_FOUND; - - // Open the file from the MPQ - if(SFileOpenFileEx((HANDLE)ha, szFileName, SFILE_OPEN_BASE_FILE, (HANDLE *)&hf)) - { - // Remember the file flags - dwFileFlags = hf->pFileEntry->dwFlags; - - // Delete the file entry - dwErrCode = DeleteFileEntry(ha, hf); - if(dwErrCode == ERROR_SUCCESS) - dwForceAddTheFile = 1; - - // Close the file - FreeFileHandle(hf); - } - - // Are we going to add the file? - if(dwForceAddTheFile) - { - ha->dwFlags |= dwFlagNew; - ha->dwReservedFiles++; - } - else - { - ha->dwFlags |= dwFlagNone; - dwFileFlags = 0; - } - - // Return the intended file flags - return dwFileFlags; -} - -void InvalidateInternalFiles(TMPQArchive * ha) -{ - // Do nothing if we are in the middle of saving internal files - if(!(ha->dwFlags & MPQ_FLAG_SAVING_TABLES)) - { - // - // We clear the file entries for (listfile), (attributes) and (signature) - // For each internal file cleared, we increment the number - // of reserved entries in the file table. - // - - // Invalidate the (listfile), if not done yet - if((ha->dwFlags & (MPQ_FLAG_LISTFILE_NONE | MPQ_FLAG_LISTFILE_NEW)) == 0) - { - ha->dwFileFlags1 = InvalidateInternalFile(ha, LISTFILE_NAME, MPQ_FLAG_LISTFILE_NONE, MPQ_FLAG_LISTFILE_NEW, (ha->dwFlags & MPQ_FLAG_LISTFILE_FORCE)); - } - - // Invalidate the (attributes), if not done yet - if((ha->dwFlags & (MPQ_FLAG_ATTRIBUTES_NONE | MPQ_FLAG_ATTRIBUTES_NEW)) == 0) - { - ha->dwFileFlags2 = InvalidateInternalFile(ha, ATTRIBUTES_NAME, MPQ_FLAG_ATTRIBUTES_NONE, MPQ_FLAG_ATTRIBUTES_NEW); - } - - // Invalidate the (signature), if not done yet - if((ha->dwFlags & (MPQ_FLAG_SIGNATURE_NONE | MPQ_FLAG_SIGNATURE_NEW)) == 0) - { - ha->dwFileFlags3 = InvalidateInternalFile(ha, SIGNATURE_NAME, MPQ_FLAG_SIGNATURE_NONE, MPQ_FLAG_SIGNATURE_NEW); - } - - // Remember that the MPQ has been changed - ha->dwFlags |= MPQ_FLAG_CHANGED; - } -} - -//----------------------------------------------------------------------------- -// Support for file tables - hash table, block table, hi-block table - -DWORD CreateHashTable(TMPQArchive * ha, DWORD dwHashTableSize) -{ - TMPQHash * pHashTable; - - // Sanity checks - assert((dwHashTableSize & (dwHashTableSize - 1)) == 0); - assert(ha->pHashTable == NULL); - - // If the required hash table size is zero, don't create anything - if(dwHashTableSize == 0) - dwHashTableSize = HASH_TABLE_SIZE_DEFAULT; - - // Create the hash table - pHashTable = STORM_ALLOC(TMPQHash, dwHashTableSize); - if(pHashTable == NULL) - return ERROR_NOT_ENOUGH_MEMORY; - - // Fill it - memset(pHashTable, 0xFF, dwHashTableSize * sizeof(TMPQHash)); - ha->pHeader->dwHashTableSize = dwHashTableSize; - ha->dwMaxFileCount = dwHashTableSize; - ha->pHashTable = pHashTable; - return ERROR_SUCCESS; -} - -static TMPQHash * LoadHashTable(TMPQArchive * ha) -{ - TMPQHeader * pHeader = ha->pHeader; - ULONGLONG ByteOffset; - TMPQHash * pHashTable = NULL; - DWORD dwTableSize; - DWORD dwCmpSize; - DWORD dwRealTableSize = 0; - - // Note: It is allowed to load hash table if it is at offset 0. - // Example: MPQ_2016_v1_ProtectedMap_HashOffsIsZero.w3x -// if(pHeader->dwHashTablePos == 0 && pHeader->wHashTablePosHi == 0) -// return NULL; - - // If the hash table size is zero, do nothing - if(pHeader->dwHashTableSize == 0) - return NULL; - - // Load the hash table for MPQ variations - switch(ha->dwSubType) - { - case MPQ_SUBTYPE_MPQ: - - // Calculate the position and size of the hash table - ByteOffset = FileOffsetFromMpqOffset(ha, MAKE_OFFSET64(pHeader->wHashTablePosHi, pHeader->dwHashTablePos)); - dwTableSize = pHeader->dwHashTableSize * sizeof(TMPQHash); - dwCmpSize = (DWORD)pHeader->HashTableSize64; - - // Read, decrypt and uncompress the hash table - pHashTable = (TMPQHash *)LoadMpqTable(ha, ByteOffset, pHeader->MD5_HashTable, dwCmpSize, dwTableSize, g_dwHashTableKey, &dwRealTableSize); -// DumpHashTable(pHashTable, pHeader->dwHashTableSize); - - // If the hash table was cut, we can/have to defragment it - if(pHashTable != NULL && dwRealTableSize != 0 && dwRealTableSize < dwTableSize) - { - ha->dwRealHashTableSize = dwRealTableSize; - ha->dwFlags |= (MPQ_FLAG_MALFORMED | MPQ_FLAG_HASH_TABLE_CUT); - } - break; - - case MPQ_SUBTYPE_SQP: - pHashTable = LoadSqpHashTable(ha); - break; - - case MPQ_SUBTYPE_MPK: - pHashTable = LoadMpkHashTable(ha); - break; - } - - // Return the loaded hash table - return pHashTable; -} - -DWORD CreateFileTable(TMPQArchive * ha, DWORD dwFileTableSize) -{ - ha->pFileTable = STORM_ALLOC(TFileEntry, dwFileTableSize); - if(ha->pFileTable == NULL) - return ERROR_NOT_ENOUGH_MEMORY; - - memset(ha->pFileTable, 0x00, sizeof(TFileEntry) * dwFileTableSize); - ha->dwFileTableSize = dwFileTableSize; - return ERROR_SUCCESS; -} - -TMPQBlock * LoadBlockTable(TMPQArchive * ha, bool /* bDontFixEntries */) -{ - TMPQHeader * pHeader = ha->pHeader; - TMPQBlock * pBlockTable = NULL; - ULONGLONG ByteOffset; - DWORD dwTableSize; - DWORD dwCmpSize; - DWORD dwRealTableSize; - - // Note: It is possible that the block table starts at offset 0 - // Example: MPQ_2016_v1_ProtectedMap_HashOffsIsZero.w3x -// if(pHeader->dwBlockTablePos == 0 && pHeader->wBlockTablePosHi == 0) -// return NULL; - - // Do nothing if the block table size is zero - if(pHeader->dwBlockTableSize == 0) - return NULL; - - // Load the block table for MPQ variations - switch(ha->dwSubType) - { - case MPQ_SUBTYPE_MPQ: - - // Calculate byte position of the block table - ByteOffset = FileOffsetFromMpqOffset(ha, MAKE_OFFSET64(pHeader->wBlockTablePosHi, pHeader->dwBlockTablePos)); - dwTableSize = pHeader->dwBlockTableSize * sizeof(TMPQBlock); - dwCmpSize = (DWORD)pHeader->BlockTableSize64; - - // Read, decrypt and uncompress the block table - pBlockTable = (TMPQBlock * )LoadMpqTable(ha, ByteOffset, NULL, dwCmpSize, dwTableSize, g_dwBlockTableKey, &dwRealTableSize); - - // If the block table was cut, we need to remember it - if(pBlockTable != NULL && dwRealTableSize && dwRealTableSize < dwTableSize) - ha->dwFlags |= (MPQ_FLAG_MALFORMED | MPQ_FLAG_BLOCK_TABLE_CUT); - break; - - case MPQ_SUBTYPE_SQP: - - pBlockTable = LoadSqpBlockTable(ha); - break; - - case MPQ_SUBTYPE_MPK: - - pBlockTable = LoadMpkBlockTable(ha); - break; - } - - return pBlockTable; -} - -TMPQHetTable * LoadHetTable(TMPQArchive * ha) -{ - TMPQExtHeader * pExtTable; - TMPQHetTable * pHetTable = NULL; - TMPQHeader * pHeader = ha->pHeader; - - // If the HET table position is not 0, we expect the table to be present - if(pHeader->HetTablePos64 && pHeader->HetTableSize64) - { - // Attempt to load the HET table (Hash Extended Table) - pExtTable = LoadExtTable(ha, pHeader->HetTablePos64, (size_t)pHeader->HetTableSize64, HET_TABLE_SIGNATURE, MPQ_KEY_HASH_TABLE); - if(pExtTable != NULL) - { - // Translate the loaded table into HET table. - pHetTable = TranslateHetTable((TMPQHetHeader *)pExtTable); - STORM_FREE(pExtTable); - } - } - - return pHetTable; -} - -TMPQBetTable * LoadBetTable(TMPQArchive * ha) -{ - TMPQExtHeader * pExtTable; - TMPQBetTable * pBetTable = NULL; - TMPQHeader * pHeader = ha->pHeader; - - // If the BET table position is not 0, we expect the table to be present - if(pHeader->BetTablePos64 && pHeader->BetTableSize64) - { - // Attempt to load the HET table (Hash Extended Table) - pExtTable = LoadExtTable(ha, pHeader->BetTablePos64, (size_t)pHeader->BetTableSize64, BET_TABLE_SIGNATURE, MPQ_KEY_BLOCK_TABLE); - if(pExtTable != NULL) - { - // If succeeded, we translate the BET table - // to more readable form - pBetTable = TranslateBetTable(ha, (TMPQBetHeader *)pExtTable); - STORM_FREE(pExtTable); - } - } - - return pBetTable; -} - -DWORD LoadAnyHashTable(TMPQArchive * ha) -{ - TMPQHeader * pHeader = ha->pHeader; - - // If the MPQ archive is empty, don't bother trying to load anything - if(pHeader->dwHashTableSize == 0 && pHeader->HetTableSize64 == 0) - return CreateHashTable(ha, HASH_TABLE_SIZE_DEFAULT); - - // Try to load HET table - if(pHeader->HetTablePos64 != 0) - ha->pHetTable = LoadHetTable(ha); - - // Try to load classic hash table - // Note that we load the classic hash table even when HET table exists, - // because if the MPQ gets modified and saved, hash table must be there - if(pHeader->dwHashTableSize) - ha->pHashTable = LoadHashTable(ha); - - // At least one of the tables must be present - if(ha->pHetTable == NULL && ha->pHashTable == NULL) - return ERROR_FILE_CORRUPT; - - // Set the maximum file count to the size of the hash table. - // Note: We don't care about HET table limits, because HET table is rebuilt - // after each file add/rename/delete. - ha->dwMaxFileCount = (ha->pHashTable != NULL) ? pHeader->dwHashTableSize : HASH_TABLE_SIZE_MAX; - return ERROR_SUCCESS; -} - -static DWORD BuildFileTable_Classic(TMPQArchive * ha) -{ - TMPQHeader * pHeader = ha->pHeader; - TMPQBlock * pBlockTable; - DWORD dwErrCode = ERROR_SUCCESS; - - // Sanity checks - assert(ha->pHashTable != NULL); - assert(ha->pFileTable != NULL); - - // If the MPQ has no block table, do nothing - if(pHeader->dwBlockTableSize == 0) - return ERROR_SUCCESS; - assert(ha->dwFileTableSize >= pHeader->dwBlockTableSize); - - // Load the block table - // WARNING! ha->pFileTable can change in the process!! - pBlockTable = (TMPQBlock *)LoadBlockTable(ha); - if(pBlockTable != NULL) - { - dwErrCode = BuildFileTableFromBlockTable(ha, pBlockTable); - STORM_FREE(pBlockTable); - } - else - { - dwErrCode = ERROR_NOT_ENOUGH_MEMORY; - } - - // Load the hi-block table - if(dwErrCode == ERROR_SUCCESS && pHeader->HiBlockTablePos64 != 0) - { - ULONGLONG ByteOffset; - USHORT * pHiBlockTable = NULL; - DWORD dwTableSize = pHeader->dwBlockTableSize * sizeof(USHORT); - - // Allocate space for the hi-block table - // Note: pHeader->dwBlockTableSize can be zero !!! - pHiBlockTable = STORM_ALLOC(USHORT, pHeader->dwBlockTableSize + 1); - if(pHiBlockTable != NULL) - { - // Load the hi-block table. It is not encrypted, nor compressed - ByteOffset = ha->MpqPos + pHeader->HiBlockTablePos64; - if(!FileStream_Read(ha->pStream, &ByteOffset, pHiBlockTable, dwTableSize)) - dwErrCode = GetLastError(); - - // Now merge the hi-block table to the file table - if(dwErrCode == ERROR_SUCCESS) - { - TFileEntry * pFileEntry = ha->pFileTable; - - // Swap the hi-block table - BSWAP_ARRAY16_UNSIGNED(pHiBlockTable, dwTableSize); - - // Add the high file offset to the base file offset. - for(DWORD i = 0; i < pHeader->dwBlockTableSize; i++, pFileEntry++) - pFileEntry->ByteOffset = MAKE_OFFSET64(pHiBlockTable[i], pFileEntry->ByteOffset); - } - - // Free the hi-block table - STORM_FREE(pHiBlockTable); - } - else - { - dwErrCode = ERROR_NOT_ENOUGH_MEMORY; - } - } - - return dwErrCode; -} - -static DWORD BuildFileTable_HetBet(TMPQArchive * ha) -{ - TMPQHetTable * pHetTable = ha->pHetTable; - TMPQBetTable * pBetTable; - TFileEntry * pFileEntry = ha->pFileTable; - TMPQBits * pBitArray; - DWORD dwBitPosition = 0; - DWORD i; - DWORD dwErrCode = ERROR_FILE_CORRUPT; - - // Load the BET table from the MPQ - pBetTable = LoadBetTable(ha); - if(pBetTable != NULL) - { - // Verify the size of NameHash2 in the BET table. - // It has to be 8 bits less than the information in HET table - if((pBetTable->dwBitCount_NameHash2 + 8) != pHetTable->dwNameHashBitSize) - { - FreeBetTable(pBetTable); - return ERROR_FILE_CORRUPT; - } - - // Step one: Fill the name indexes - for(i = 0; i < pHetTable->dwTotalCount; i++) - { - DWORD dwFileIndex = 0; - - // Is the entry in the HET table occupied? - if(pHetTable->pNameHashes[i] != HET_ENTRY_FREE) - { - // Load the index to the BET table - pHetTable->pBetIndexes->GetBits(pHetTable->dwIndexSizeTotal * i, - pHetTable->dwIndexSize, - &dwFileIndex, - 4); - // Overflow test - if(dwFileIndex < pBetTable->dwEntryCount) - { - ULONGLONG NameHash1 = pHetTable->pNameHashes[i]; - ULONGLONG NameHash2 = 0; - - // Load the BET hash - pBetTable->pNameHashes->GetBits(pBetTable->dwBitTotal_NameHash2 * dwFileIndex, - pBetTable->dwBitCount_NameHash2, - &NameHash2, - 8); - - // Combine both part of the name hash and put it to the file table - pFileEntry = ha->pFileTable + dwFileIndex; - pFileEntry->FileNameHash = (NameHash1 << pBetTable->dwBitCount_NameHash2) | NameHash2; - } - } - } - - // Go through the entire BET table and convert it to the file table. - pFileEntry = ha->pFileTable; - pBitArray = pBetTable->pFileTable; - for(i = 0; i < pBetTable->dwEntryCount; i++) - { - DWORD dwFlagIndex = 0; - - // Read the file position - pBitArray->GetBits(dwBitPosition + pBetTable->dwBitIndex_FilePos, - pBetTable->dwBitCount_FilePos, - &pFileEntry->ByteOffset, - 8); - - // Read the file size - pBitArray->GetBits(dwBitPosition + pBetTable->dwBitIndex_FileSize, - pBetTable->dwBitCount_FileSize, - &pFileEntry->dwFileSize, - 4); - - // Read the compressed size - pBitArray->GetBits(dwBitPosition + pBetTable->dwBitIndex_CmpSize, - pBetTable->dwBitCount_CmpSize, - &pFileEntry->dwCmpSize, - 4); - - - // Read the flag index - if(pBetTable->dwFlagCount != 0) - { - pBitArray->GetBits(dwBitPosition + pBetTable->dwBitIndex_FlagIndex, - pBetTable->dwBitCount_FlagIndex, - &dwFlagIndex, - 4); - pFileEntry->dwFlags = pBetTable->pFileFlags[dwFlagIndex]; - } - - // - // TODO: Locale (?) - // - - // Move the current bit position - dwBitPosition += pBetTable->dwTableEntrySize; - pFileEntry++; - } - - // Set the current size of the file table - FreeBetTable(pBetTable); - dwErrCode = ERROR_SUCCESS; - } - else - { - dwErrCode = ERROR_FILE_CORRUPT; - } - - return dwErrCode; -} - -DWORD BuildFileTable(TMPQArchive * ha) -{ - DWORD dwFileTableSize; - bool bFileTableCreated = false; - - // Sanity checks - assert(ha->pFileTable == NULL); - assert(ha->dwFileTableSize == 0); - assert(ha->dwMaxFileCount != 0); - - // Determine the allocation size for the file table - dwFileTableSize = STORMLIB_MAX(ha->pHeader->dwBlockTableSize, ha->dwMaxFileCount); - - // Allocate the file table with size determined before - ha->pFileTable = STORM_ALLOC(TFileEntry, dwFileTableSize); - if(ha->pFileTable == NULL) - return ERROR_NOT_ENOUGH_MEMORY; - - // Fill the table with zeros - memset(ha->pFileTable, 0, dwFileTableSize * sizeof(TFileEntry)); - ha->dwFileTableSize = dwFileTableSize; - - // If we have HET table, we load file table from the BET table - // Note: If BET table is corrupt or missing, we set the archive as read only - if(ha->pHetTable != NULL) - { - if(BuildFileTable_HetBet(ha) != ERROR_SUCCESS) - ha->dwFlags |= MPQ_FLAG_READ_ONLY; - else - bFileTableCreated = true; - } - - // If we have hash table, we load the file table from the block table - // Note: If block table is corrupt or missing, we set the archive as read only - if(ha->pHashTable != NULL) - { - if(BuildFileTable_Classic(ha) != ERROR_SUCCESS) - ha->dwFlags |= MPQ_FLAG_READ_ONLY; - else - bFileTableCreated = true; - } - - // Return result - return bFileTableCreated ? ERROR_SUCCESS : ERROR_FILE_CORRUPT; -} - -/* -void UpdateBlockTableSize(TMPQArchive * ha) -{ - TFileEntry * pFileTableEnd = ha->pFileTable + ha->dwFileTableSize; - TFileEntry * pFileEntry; - DWORD dwBlockTableSize = 0; - - // Calculate the number of files - for(pFileEntry = ha->pFileTable; pFileEntry < pFileTableEnd; pFileEntry++) - { - // If the source table entry is valid, - if(pFileEntry->dwFlags & MPQ_FILE_EXISTS) - dwBlockTableSize = (DWORD)(pFileEntry - ha->pFileTable) + 1; - } - - // Save the block table size to the MPQ header - ha->pHeader->dwBlockTableSize = ha->dwReservedFiles + dwBlockTableSize; -} -*/ - -// Defragment the file table so it does not contain any gaps -DWORD DefragmentFileTable(TMPQArchive * ha) -{ - TFileEntry * pFileTableEnd = ha->pFileTable + ha->dwFileTableSize; - TFileEntry * pSource = ha->pFileTable; - TFileEntry * pTarget = ha->pFileTable; - LPDWORD DefragmentTable; - DWORD dwBlockTableSize = 0; - DWORD dwSrcIndex; - DWORD dwTrgIndex; - - // Allocate brand new file table - DefragmentTable = STORM_ALLOC(DWORD, ha->dwFileTableSize); - if(DefragmentTable != NULL) - { - // Clear the file table - memset(DefragmentTable, 0xFF, sizeof(DWORD) * ha->dwFileTableSize); - - // Parse the entire file table and defragment it - for(; pSource < pFileTableEnd; pSource++) - { - // If the source table entry is valid, - if(pSource->dwFlags & MPQ_FILE_EXISTS) - { - // Remember the index conversion - dwSrcIndex = (DWORD)(pSource - ha->pFileTable); - dwTrgIndex = (DWORD)(pTarget - ha->pFileTable); - DefragmentTable[dwSrcIndex] = dwTrgIndex; - - // Move the entry, if needed - if(pTarget != pSource) - pTarget[0] = pSource[0]; - pTarget++; - - // Update the block table size - dwBlockTableSize = (DWORD)(pTarget - ha->pFileTable); - } - else - { - // If there is file name left, free it - if(pSource->szFileName != NULL) - STORM_FREE(pSource->szFileName); - pSource->szFileName = NULL; - } - } - - // Did we defragment something? - if(pTarget < pFileTableEnd) - { - // Clear the remaining file entries - memset(pTarget, 0, (pFileTableEnd - pTarget) * sizeof(TFileEntry)); - - // Go through the hash table and relocate the block indexes - if(ha->pHashTable != NULL) - { - TMPQHash * pHashTableEnd = ha->pHashTable + ha->pHeader->dwHashTableSize; - TMPQHash * pHash; - DWORD dwNewBlockIndex; - - for(pHash = ha->pHashTable; pHash < pHashTableEnd; pHash++) - { - if(MPQ_BLOCK_INDEX(pHash) < ha->dwFileTableSize) - { - // If that block entry is there, set it to the hash entry - // If not, set it as DELETED - dwNewBlockIndex = DefragmentTable[MPQ_BLOCK_INDEX(pHash)]; - pHash->dwBlockIndex = (dwNewBlockIndex != HASH_ENTRY_FREE) ? dwNewBlockIndex : HASH_ENTRY_DELETED; - } - } - } - } - - // Save the block table size - ha->pHeader->dwBlockTableSize = ha->dwReservedFiles + dwBlockTableSize; - - // Free the defragment table - STORM_FREE(DefragmentTable); - } - - return ERROR_SUCCESS; -} - -// Rebuilds the HET table from scratch based on the file table -// Used after a modifying operation (add, rename, delete) -DWORD RebuildHetTable(TMPQArchive * ha) -{ - TMPQHetTable * pOldHetTable = ha->pHetTable; - TFileEntry * pFileTableEnd; - TFileEntry * pFileEntry; - DWORD dwBlockTableSize = ha->dwFileTableSize; - DWORD dwErrCode = ERROR_SUCCESS; - - // If we are in the state of saving MPQ tables, the real size of block table - // must already have been calculated. Use that value instead - if(ha->dwFlags & MPQ_FLAG_SAVING_TABLES) - { - assert(ha->pHeader->dwBlockTableSize != 0); - dwBlockTableSize = ha->pHeader->dwBlockTableSize; - } - - // Create new HET table based on the total number of entries in the file table - // Note that if we fail to create it, we just stop using HET table - ha->pHetTable = CreateHetTable(dwBlockTableSize, 0, 0x40, NULL); - if(ha->pHetTable != NULL) - { - // Go through the file table again and insert all existing files - pFileTableEnd = ha->pFileTable + dwBlockTableSize; - for(pFileEntry = ha->pFileTable; pFileEntry < pFileTableEnd; pFileEntry++) - { - if(pFileEntry->dwFlags & MPQ_FILE_EXISTS) - { - // Get the high - dwErrCode = InsertHetEntry(ha->pHetTable, pFileEntry->FileNameHash, (DWORD)(pFileEntry - ha->pFileTable)); - if(dwErrCode != ERROR_SUCCESS) - break; - } - } - } - - // Free the old HET table - FreeHetTable(pOldHetTable); - return dwErrCode; -} - -// Rebuilds the file table, removing all deleted file entries. -// Used when compacting the archive -DWORD RebuildFileTable(TMPQArchive * ha, DWORD dwNewHashTableSize) -{ - TFileEntry * pFileEntry; - TMPQHash * pHashTableEnd = ha->pHashTable + ha->pHeader->dwHashTableSize; - TMPQHash * pOldHashTable = ha->pHashTable; - TMPQHash * pHashTable = NULL; - TMPQHash * pHash; - DWORD dwErrCode = ERROR_SUCCESS; - - // The new hash table size must be greater or equal to the current hash table size - assert(dwNewHashTableSize >= ha->pHeader->dwHashTableSize); - assert(dwNewHashTableSize >= ha->dwMaxFileCount); - assert((dwNewHashTableSize & (dwNewHashTableSize - 1)) == 0); - assert(ha->pHashTable != NULL); - - // Reallocate the new file table, if needed - if(dwNewHashTableSize > ha->dwFileTableSize) - { - ha->pFileTable = STORM_REALLOC(TFileEntry, ha->pFileTable, dwNewHashTableSize); - if(ha->pFileTable == NULL) - return ERROR_NOT_ENOUGH_MEMORY; - - memset(ha->pFileTable + ha->dwFileTableSize, 0, (dwNewHashTableSize - ha->dwFileTableSize) * sizeof(TFileEntry)); - } - - // Allocate new hash table - if(dwErrCode == ERROR_SUCCESS) - { - pHashTable = STORM_ALLOC(TMPQHash, dwNewHashTableSize); - if(pHashTable == NULL) - dwErrCode = ERROR_NOT_ENOUGH_MEMORY; - } - - // If both succeeded, we need to rebuild the file table - if(dwErrCode == ERROR_SUCCESS) - { - // Make sure that the hash table is properly filled - memset(pHashTable, 0xFF, sizeof(TMPQHash) * dwNewHashTableSize); - ha->pHashTable = pHashTable; - - // Set the new limits to the MPQ archive - ha->pHeader->dwHashTableSize = dwNewHashTableSize; - - // Parse the old hash table and copy all entries to the new table - for(pHash = pOldHashTable; pHash < pHashTableEnd; pHash++) - { - if(IsValidHashEntry(ha, pHash)) - { - pFileEntry = ha->pFileTable + MPQ_BLOCK_INDEX(pHash); - AllocateHashEntry(ha, pFileEntry, SFILE_MAKE_LCID(pHash->Locale, pHash->Platform)); - } - } - - // Increment the max file count for the file - ha->dwFileTableSize = dwNewHashTableSize; - ha->dwMaxFileCount = dwNewHashTableSize; - ha->dwFlags |= MPQ_FLAG_CHANGED; - } - - // Now free the remaining entries - if(pOldHashTable != NULL) - STORM_FREE(pOldHashTable); - return dwErrCode; -} - -// Saves MPQ header, hash table, block table and hi-block table. -DWORD SaveMPQTables(TMPQArchive * ha) -{ - TMPQExtHeader * pHetTable = NULL; - TMPQExtHeader * pBetTable = NULL; - TMPQHeader * pHeader = ha->pHeader; - TMPQBlock * pBlockTable = NULL; - TMPQHash * pHashTable = NULL; - ULONGLONG HetTableSize64 = 0; - ULONGLONG BetTableSize64 = 0; - ULONGLONG HashTableSize64 = 0; - ULONGLONG BlockTableSize64 = 0; - ULONGLONG HiBlockTableSize64 = 0; - ULONGLONG TablePos = 0; // A table position, relative to the begin of the MPQ - USHORT * pHiBlockTable = NULL; - DWORD cbTotalSize; - bool bNeedHiBlockTable = false; - DWORD dwErrCode = ERROR_SUCCESS; - - // We expect this function to be called only when tables have been changed - assert(ha->dwFlags & MPQ_FLAG_CHANGED); - - // Find the space where the MPQ tables will be saved - TablePos = FindFreeMpqSpace(ha); - - // If the MPQ has HET table, we prepare a ready-to-save version - if(dwErrCode == ERROR_SUCCESS && ha->pHetTable != NULL) - { - pHetTable = TranslateHetTable(ha->pHetTable, &HetTableSize64); - if(pHetTable == NULL) - dwErrCode = ERROR_NOT_ENOUGH_MEMORY; - } - - // If the MPQ has HET table, we also must create BET table to be saved - if(dwErrCode == ERROR_SUCCESS && ha->pHetTable != NULL) - { - pBetTable = TranslateBetTable(ha, &BetTableSize64); - if(pBetTable == NULL) - dwErrCode = ERROR_NOT_ENOUGH_MEMORY; - } - - // Now create hash table - if(dwErrCode == ERROR_SUCCESS && ha->pHashTable != NULL) - { - pHashTable = TranslateHashTable(ha, &HashTableSize64); - if(pHashTable == NULL) - dwErrCode = ERROR_NOT_ENOUGH_MEMORY; - } - - // Create block table - if(dwErrCode == ERROR_SUCCESS && ha->pFileTable != NULL) - { - pBlockTable = TranslateBlockTable(ha, &BlockTableSize64, &bNeedHiBlockTable); - if(pBlockTable == NULL) - dwErrCode = ERROR_NOT_ENOUGH_MEMORY; - } - - // Create hi-block table, if needed - if(dwErrCode == ERROR_SUCCESS && bNeedHiBlockTable) - { - pHiBlockTable = TranslateHiBlockTable(ha, &HiBlockTableSize64); - if(pHiBlockTable == NULL) - dwErrCode = ERROR_NOT_ENOUGH_MEMORY; - } - - // Write the HET table, if any - if(dwErrCode == ERROR_SUCCESS && pHetTable != NULL) - { - pHeader->HetTableSize64 = HetTableSize64; - pHeader->HetTablePos64 = TablePos; - dwErrCode = SaveExtTable(ha, pHetTable, TablePos, (DWORD)HetTableSize64, pHeader->MD5_HetTable, MPQ_KEY_HASH_TABLE, false, &cbTotalSize); - TablePos += cbTotalSize; - } - - // Write the BET table, if any - if(dwErrCode == ERROR_SUCCESS && pBetTable != NULL) - { - pHeader->BetTableSize64 = BetTableSize64; - pHeader->BetTablePos64 = TablePos; - dwErrCode = SaveExtTable(ha, pBetTable, TablePos, (DWORD)BetTableSize64, pHeader->MD5_BetTable, MPQ_KEY_BLOCK_TABLE, false, &cbTotalSize); - TablePos += cbTotalSize; - } - - // Write the hash table, if we have any - if(dwErrCode == ERROR_SUCCESS && pHashTable != NULL) - { - pHeader->HashTableSize64 = HashTableSize64; - pHeader->wHashTablePosHi = (USHORT)(TablePos >> 32); - pHeader->dwHashTableSize = (DWORD)(HashTableSize64 / sizeof(TMPQHash)); - pHeader->dwHashTablePos = (DWORD)TablePos; - dwErrCode = SaveMpqTable(ha, pHashTable, TablePos, (size_t)HashTableSize64, pHeader->MD5_HashTable, MPQ_KEY_HASH_TABLE, false); - TablePos += HashTableSize64; - } - - // Write the block table, if we have any - if(dwErrCode == ERROR_SUCCESS && pBlockTable != NULL) - { - pHeader->BlockTableSize64 = BlockTableSize64; - pHeader->wBlockTablePosHi = (USHORT)(TablePos >> 32); - pHeader->dwBlockTableSize = (DWORD)(BlockTableSize64 / sizeof(TMPQBlock)); - pHeader->dwBlockTablePos = (DWORD)TablePos; - dwErrCode = SaveMpqTable(ha, pBlockTable, TablePos, (size_t)BlockTableSize64, pHeader->MD5_BlockTable, MPQ_KEY_BLOCK_TABLE, false); - TablePos += BlockTableSize64; - } - - // Write the hi-block table, if we have any - if(dwErrCode == ERROR_SUCCESS && pHiBlockTable != NULL) - { - ULONGLONG ByteOffset = ha->MpqPos + TablePos; - - pHeader->HiBlockTableSize64 = HiBlockTableSize64; - pHeader->HiBlockTablePos64 = TablePos; - BSWAP_ARRAY16_UNSIGNED(pHiBlockTable, HiBlockTableSize64); - - if(!FileStream_Write(ha->pStream, &ByteOffset, pHiBlockTable, (DWORD)HiBlockTableSize64)) - dwErrCode = GetLastError(); - TablePos += HiBlockTableSize64; - } - - // Cut the MPQ - if(dwErrCode == ERROR_SUCCESS) - { - ULONGLONG FileSize = ha->MpqPos + TablePos; - - if(!FileStream_SetSize(ha->pStream, FileSize)) - dwErrCode = GetLastError(); - } - - // Write the MPQ header - if(dwErrCode == ERROR_SUCCESS) - { - TMPQHeader SaveMpqHeader; - - // Update the size of the archive - pHeader->ArchiveSize64 = TablePos; - pHeader->dwArchiveSize = (DWORD)TablePos; - - // Update the MD5 of the archive header - CalculateDataBlockHash(pHeader, MPQ_HEADER_SIZE_V4 - MD5_DIGEST_SIZE, pHeader->MD5_MpqHeader); - - // Write the MPQ header to the file - memcpy(&SaveMpqHeader, pHeader, pHeader->dwHeaderSize); - BSWAP_TMPQHEADER(&SaveMpqHeader, MPQ_FORMAT_VERSION_1); - BSWAP_TMPQHEADER(&SaveMpqHeader, MPQ_FORMAT_VERSION_2); - BSWAP_TMPQHEADER(&SaveMpqHeader, MPQ_FORMAT_VERSION_3); - BSWAP_TMPQHEADER(&SaveMpqHeader, MPQ_FORMAT_VERSION_4); - if(!FileStream_Write(ha->pStream, &ha->MpqPos, &SaveMpqHeader, pHeader->dwHeaderSize)) - dwErrCode = GetLastError(); - } - - // Clear the changed flag - if(dwErrCode == ERROR_SUCCESS) - ha->dwFlags &= ~MPQ_FLAG_CHANGED; - - // Cleanup and exit - if(pHetTable != NULL) - STORM_FREE(pHetTable); - if(pBetTable != NULL) - STORM_FREE(pBetTable); - if(pHashTable != NULL) - STORM_FREE(pHashTable); - if(pBlockTable != NULL) - STORM_FREE(pBlockTable); - if(pHiBlockTable != NULL) - STORM_FREE(pHiBlockTable); - return dwErrCode; -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/SBaseSubTypes.cpp b/app/jni/src/libultraship/extern/StormLib/src/SBaseSubTypes.cpp deleted file mode 100644 index 59be7e8..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/SBaseSubTypes.cpp +++ /dev/null @@ -1,622 +0,0 @@ -/*****************************************************************************/ -/* SBaseSubTypes.cpp Copyright (c) Ladislav Zezula 2013 */ -/*---------------------------------------------------------------------------*/ -/* Conversion routines for archive formats that are similar to MPQ format */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 02.11.11 1.00 Lad The first version of SBaseSubTypes.cpp */ -/*****************************************************************************/ - -#define __STORMLIB_SELF__ -#include "StormLib.h" -#include "StormCommon.h" - -/*****************************************************************************/ -/* */ -/* Support for SQP file format (War of the Immortals) */ -/* */ -/*****************************************************************************/ - -typedef struct _TSQPHeader -{ - // The ID_MPQ ('MPQ\x1A') signature - DWORD dwID; - - // Size of the archive header - DWORD dwHeaderSize; - - // 32-bit size of MPQ archive - DWORD dwArchiveSize; - - // Offset to the beginning of the hash table, relative to the beginning of the archive. - DWORD dwHashTablePos; - - // Offset to the beginning of the block table, relative to the beginning of the archive. - DWORD dwBlockTablePos; - - // Number of entries in the hash table. Must be a power of two, and must be less than 2^16 for - // the original MoPaQ format, or less than 2^20 for the Burning Crusade format. - DWORD dwHashTableSize; - - // Number of entries in the block table - DWORD dwBlockTableSize; - - // Must be zero for SQP files - USHORT wFormatVersion; - - // Power of two exponent specifying the number of 512-byte disk sectors in each file sector - // in the archive. The size of each file sector in the archive is 512 * 2 ^ wSectorSize. - USHORT wSectorSize; - -} TSQPHeader; - -typedef struct _TSQPHash -{ - // Most likely the Locale + Platform - DWORD dwAlwaysZero; - - // If the hash table entry is valid, this is the index into the block table of the file. - // Otherwise, one of the following two values: - // - FFFFFFFFh: Hash table entry is empty, and has always been empty. - // Terminates searches for a given file. - // - FFFFFFFEh: Hash table entry is empty, but was valid at some point (a deleted file). - // Does not terminate searches for a given file. - DWORD dwBlockIndex; - - // The hash of the file path, using method A. - DWORD dwName1; - - // The hash of the file path, using method B. - DWORD dwName2; - -} TSQPHash; - -typedef struct _TSQPBlock -{ - // Offset of the beginning of the file, relative to the beginning of the archive. - DWORD dwFilePos; - - // Flags for the file. See MPQ_FILE_XXXX constants - DWORD dwFlags; - - // Compressed file size - DWORD dwCSize; - - // Uncompressed file size - DWORD dwFSize; - -} TSQPBlock; - -//----------------------------------------------------------------------------- -// Functions - SQP file format - -// This function converts SQP file header into MPQ file header -DWORD ConvertSqpHeaderToFormat4( - TMPQArchive * ha, - ULONGLONG FileSize, - DWORD dwFlags) -{ - TSQPHeader * pSqpHeader = (TSQPHeader *)ha->HeaderData; - TMPQHeader Header; - - // SQP files from War of the Immortal use MPQ file format with slightly - // modified structure. These fields have different position: - // - // Offset TMPQHeader TSQPHeader - // ------ ---------- ----------- - // 000C wFormatVersion dwHashTablePos (lo) - // 000E wSectorSize dwHashTablePos (hi) - // 001C dwBlockTableSize (lo) wBlockSize - // 001E dwHashTableSize (hi) wFormatVersion - - // Can't open the archive with certain flags - if(dwFlags & MPQ_OPEN_FORCE_MPQ_V1) - return ERROR_FILE_CORRUPT; - - // The file must not be greater than 4 GB - if((FileSize >> 0x20) != 0) - return ERROR_FILE_CORRUPT; - - // Translate the SQP header into a MPQ header - memset(&Header, 0, sizeof(TMPQHeader)); - Header.dwID = BSWAP_INT32_UNSIGNED(pSqpHeader->dwID); - Header.dwHeaderSize = BSWAP_INT32_UNSIGNED(pSqpHeader->dwHeaderSize); - Header.dwArchiveSize = BSWAP_INT32_UNSIGNED(pSqpHeader->dwArchiveSize); - Header.dwHashTablePos = BSWAP_INT32_UNSIGNED(pSqpHeader->dwHashTablePos); - Header.dwBlockTablePos = BSWAP_INT32_UNSIGNED(pSqpHeader->dwBlockTablePos); - Header.dwHashTableSize = BSWAP_INT32_UNSIGNED(pSqpHeader->dwHashTableSize); - Header.dwBlockTableSize = BSWAP_INT32_UNSIGNED(pSqpHeader->dwBlockTableSize); - Header.wFormatVersion = BSWAP_INT16_UNSIGNED(pSqpHeader->wFormatVersion); - Header.wSectorSize = BSWAP_INT16_UNSIGNED(pSqpHeader->wSectorSize); - - // Verify the SQP header - if(Header.dwID == g_dwMpqSignature && Header.dwHeaderSize == sizeof(TSQPHeader) && Header.dwArchiveSize == FileSize) - { - // Check for fixed values of version and sector size - if(Header.wFormatVersion == MPQ_FORMAT_VERSION_1 && Header.wSectorSize == 3) - { - // Initialize the fields of 3.0 header - Header.ArchiveSize64 = Header.dwArchiveSize; - Header.HashTableSize64 = Header.dwHashTableSize * sizeof(TMPQHash); - Header.BlockTableSize64 = Header.dwBlockTableSize * sizeof(TMPQBlock); - - // Copy the converted MPQ header back - memcpy(ha->HeaderData, &Header, sizeof(TMPQHeader)); - - // Mark this file as SQP file - ha->pfnHashString = HashStringSlash; - ha->dwFlags |= MPQ_FLAG_READ_ONLY; - ha->dwSubType = MPQ_SUBTYPE_SQP; - return ERROR_SUCCESS; - } - } - - return ERROR_FILE_CORRUPT; -} - -void * LoadSqpTable(TMPQArchive * ha, DWORD dwByteOffset, DWORD cbTableSize, DWORD dwKey) -{ - ULONGLONG ByteOffset; - LPBYTE pbSqpTable; - - // Allocate buffer for the table - pbSqpTable = STORM_ALLOC(BYTE, cbTableSize); - if(pbSqpTable != NULL) - { - // Load the table - ByteOffset = ha->MpqPos + dwByteOffset; - if(FileStream_Read(ha->pStream, &ByteOffset, pbSqpTable, cbTableSize)) - { - // Decrypt the SQP table - DecryptMpqBlock(pbSqpTable, cbTableSize, dwKey); - return pbSqpTable; - } - - // Free the table - STORM_FREE(pbSqpTable); - } - - return NULL; -} - -TMPQHash * LoadSqpHashTable(TMPQArchive * ha) -{ - TMPQHeader * pHeader = ha->pHeader; - TSQPHash * pSqpHashTable; - TSQPHash * pSqpHashEnd; - TSQPHash * pSqpHash; - TMPQHash * pMpqHash; - DWORD dwErrCode = ERROR_SUCCESS; - - // Load the hash table - pSqpHashTable = (TSQPHash *)LoadSqpTable(ha, pHeader->dwHashTablePos, pHeader->dwHashTableSize * sizeof(TSQPHash), MPQ_KEY_HASH_TABLE); - if(pSqpHashTable != NULL) - { - // Parse the entire hash table and convert it to MPQ hash table - pSqpHashEnd = pSqpHashTable + pHeader->dwHashTableSize; - pMpqHash = (TMPQHash *)pSqpHashTable; - for(pSqpHash = pSqpHashTable; pSqpHash < pSqpHashEnd; pSqpHash++, pMpqHash++) - { - // Ignore free entries - if(pSqpHash->dwBlockIndex != HASH_ENTRY_FREE) - { - // Store the hash entry to a temporary variable - TSQPHash TempEntry = *pSqpHash; - - // Check block index against the size of the block table - if(pHeader->dwBlockTableSize <= MPQ_BLOCK_INDEX(pSqpHash) && pSqpHash->dwBlockIndex < HASH_ENTRY_DELETED) - dwErrCode = ERROR_FILE_CORRUPT; - - // We do not support nonzero locale and platform ID - if(pSqpHash->dwAlwaysZero != 0 && pSqpHash->dwAlwaysZero != HASH_ENTRY_FREE) - dwErrCode = ERROR_FILE_CORRUPT; - - // Copy the entry to the MPQ hash entry - pMpqHash->dwName1 = TempEntry.dwName1; - pMpqHash->dwName2 = TempEntry.dwName2; - pMpqHash->dwBlockIndex = MPQ_BLOCK_INDEX(&TempEntry); - pMpqHash->Locale = 0; - pMpqHash->Platform = 0; - pMpqHash->Reserved = 0; - } - } - - // If an error occured, we need to free the hash table - if(dwErrCode != ERROR_SUCCESS) - { - STORM_FREE(pSqpHashTable); - pSqpHashTable = NULL; - } - } - - // Return the converted hash table (or NULL on failure) - return (TMPQHash *)pSqpHashTable; -} - -// Loads the SQP Block table and converts it to a MPQ block table -TMPQBlock * LoadSqpBlockTable(TMPQArchive * ha) -{ - TMPQHeader * pHeader = ha->pHeader; - TSQPBlock * pSqpBlockTable; - TSQPBlock * pSqpBlockEnd; - TSQPBlock * pSqpBlock; - TMPQBlock * pMpqBlock; - DWORD dwErrCode = ERROR_SUCCESS; - - // Load the hash table - pSqpBlockTable = (TSQPBlock *)LoadSqpTable(ha, pHeader->dwBlockTablePos, pHeader->dwBlockTableSize * sizeof(TSQPBlock), MPQ_KEY_BLOCK_TABLE); - if(pSqpBlockTable != NULL) - { - // Parse the entire hash table and convert it to MPQ hash table - pSqpBlockEnd = pSqpBlockTable + pHeader->dwBlockTableSize; - pMpqBlock = (TMPQBlock *)pSqpBlockTable; - for(pSqpBlock = pSqpBlockTable; pSqpBlock < pSqpBlockEnd; pSqpBlock++, pMpqBlock++) - { - // Store the block entry to a temporary variable - TSQPBlock TempEntry = *pSqpBlock; - - // Check for valid flags - if(pSqpBlock->dwFlags & ~MPQ_FILE_VALID_FLAGS) - dwErrCode = ERROR_FILE_CORRUPT; - - // Convert SQP block table entry to MPQ block table entry - pMpqBlock->dwFilePos = TempEntry.dwFilePos; - pMpqBlock->dwCSize = TempEntry.dwCSize; - pMpqBlock->dwFSize = TempEntry.dwFSize; - pMpqBlock->dwFlags = TempEntry.dwFlags; - } - - // If an error occured, we need to free the hash table - if(dwErrCode != ERROR_SUCCESS) - { - STORM_FREE(pSqpBlockTable); - pSqpBlockTable = NULL; - } - } - - // Return the converted hash table (or NULL on failure) - return (TMPQBlock *)pSqpBlockTable; -} - -/*****************************************************************************/ -/* */ -/* Support for MPK file format (Longwu Online) */ -/* */ -/*****************************************************************************/ - -#define MPK_FILE_UNKNOWN_0001 0x00000001 // Seems to be always present -#define MPK_FILE_UNKNOWN_0010 0x00000010 // Seems to be always present -#define MPK_FILE_COMPRESSED 0x00000100 // Indicates a compressed file -#define MPK_FILE_UNKNOWN_2000 0x00002000 // Seems to be always present -#define MPK_FILE_EXISTS 0x01000000 // Seems to be always present - -typedef struct _TMPKHeader -{ - // The ID_MPK ('MPK\x1A') signature - DWORD dwID; - - // Contains '2000' - DWORD dwVersion; - - // 32-bit size of the archive - DWORD dwArchiveSize; - - // Size of the archive header - DWORD dwHeaderSize; - - DWORD dwHashTablePos; - DWORD dwHashTableSize; - DWORD dwBlockTablePos; - DWORD dwBlockTableSize; - DWORD dwUnknownPos; - DWORD dwUnknownSize; -} TMPKHeader; - - -typedef struct _TMPKHash -{ - // The hash of the file path, using method A. - DWORD dwName1; - - // The hash of the file path, using method B. - DWORD dwName2; - - // The hash of the file path, using method C. - DWORD dwName3; - - // If the hash table entry is valid, this is the index into the block table of the file. - // Otherwise, one of the following two values: - // - FFFFFFFFh: Hash table entry is empty, and has always been empty. - // Terminates searches for a given file. - // - FFFFFFFEh: Hash table entry is empty, but was valid at some point (a deleted file). - // Does not terminate searches for a given file. - DWORD dwBlockIndex; - -} TMPKHash; - -typedef struct _TMPKBlock -{ - DWORD dwFlags; // 0x1121 - Compressed , 0x1120 - Not compressed - DWORD dwFilePos; // Offset of the beginning of the file, relative to the beginning of the archive. - DWORD dwFSize; // Uncompressed file size - DWORD dwCSize; // Compressed file size - DWORD dwUnknown; // 0x86364E6D -} TMPKBlock; - -//----------------------------------------------------------------------------- -// Local variables - MPK file format - -static const unsigned char MpkDecryptionKey[512] = -{ - 0x60, 0x20, 0x29, 0xE1, 0x01, 0xCE, 0xAA, 0xFE, 0xA3, 0xAB, 0x8E, 0x30, 0xAF, 0x02, 0xD1, 0x7D, - 0x41, 0x24, 0x06, 0xBD, 0xAE, 0xBE, 0x43, 0xC3, 0xBA, 0xB7, 0x08, 0x13, 0x51, 0xCF, 0xF8, 0xF7, - 0x25, 0x42, 0xA5, 0x4A, 0xDA, 0x0F, 0x52, 0x1C, 0x90, 0x3B, 0x63, 0x49, 0x36, 0xF6, 0xDD, 0x1B, - 0xEA, 0x58, 0xD4, 0x40, 0x70, 0x61, 0x55, 0x09, 0xCD, 0x0B, 0xA2, 0x4B, 0x68, 0x2C, 0x8A, 0xF1, - 0x3C, 0x3A, 0x65, 0xBB, 0xA1, 0xA8, 0x23, 0x97, 0xFD, 0x15, 0x00, 0x94, 0x88, 0x33, 0x59, 0xE9, - 0xFB, 0x69, 0x21, 0xEF, 0x85, 0x5B, 0x57, 0x6C, 0xFA, 0xB5, 0xEE, 0xB8, 0x71, 0xDC, 0xB1, 0x38, - 0x0C, 0x0A, 0x5C, 0x56, 0xC9, 0xB4, 0x84, 0x17, 0x1E, 0xE5, 0xD3, 0x5A, 0xCC, 0xFC, 0x11, 0x86, - 0x7F, 0x45, 0x4F, 0x54, 0xC8, 0x8D, 0x73, 0x89, 0x79, 0x5D, 0xB3, 0xBF, 0xB9, 0xE3, 0x93, 0xE4, - 0x6F, 0x35, 0x2D, 0x46, 0xF2, 0x76, 0xC5, 0x7E, 0xE2, 0xA4, 0xE6, 0xD9, 0x6E, 0x48, 0x34, 0x2B, - 0xC6, 0x5F, 0xBC, 0xA0, 0x6D, 0x0D, 0x47, 0x6B, 0x95, 0x96, 0x92, 0x91, 0xB2, 0x27, 0xEB, 0x9E, - 0xEC, 0x8F, 0xDF, 0x9C, 0x74, 0x99, 0x64, 0xF5, 0xFF, 0x28, 0xB6, 0x37, 0xF3, 0x7C, 0x81, 0x03, - 0x44, 0x62, 0x1F, 0xDB, 0x04, 0x7B, 0xB0, 0x9B, 0x31, 0xA7, 0xDE, 0x78, 0x9F, 0xAD, 0x0E, 0x3F, - 0x3E, 0x4D, 0xC7, 0xD7, 0x39, 0x19, 0x5E, 0xC2, 0xD0, 0xAC, 0xE8, 0x1A, 0x87, 0x8B, 0x07, 0x05, - 0x22, 0xED, 0x72, 0x2E, 0x1D, 0xC1, 0xA9, 0xD6, 0xE0, 0x83, 0xD5, 0xD8, 0xCB, 0x80, 0xF0, 0x66, - 0x7A, 0x9D, 0x50, 0xF9, 0x10, 0x4E, 0x16, 0x14, 0x77, 0x75, 0x6A, 0x67, 0xD2, 0xC0, 0xA6, 0xC4, - 0x53, 0x8C, 0x32, 0xCA, 0x82, 0x2A, 0x18, 0x9A, 0xF4, 0x4C, 0x3D, 0x26, 0x12, 0xE7, 0x98, 0x2F, - 0x4A, 0x04, 0x0D, 0xAF, 0xB4, 0xCF, 0x12, 0xCE, 0x1A, 0x37, 0x61, 0x39, 0x60, 0x95, 0xBE, 0x25, - 0xE4, 0x6E, 0xFC, 0x1B, 0xE7, 0x49, 0xE6, 0x67, 0xF6, 0xC5, 0xCB, 0x2F, 0x27, 0xD4, 0x68, 0xB2, - 0x01, 0x52, 0xD0, 0x46, 0x11, 0x20, 0xFB, 0x9D, 0xA9, 0x02, 0xF5, 0x8F, 0x3D, 0x82, 0xD3, 0xFF, - 0x0B, 0xB8, 0xF2, 0x4D, 0x8E, 0x81, 0x2C, 0xAB, 0x5F, 0xC4, 0x41, 0x29, 0x40, 0xFA, 0xC0, 0xBF, - 0x33, 0x10, 0x21, 0x16, 0xB0, 0x71, 0x83, 0x96, 0x8D, 0x2B, 0x23, 0x3B, 0xF9, 0xC1, 0xE5, 0x72, - 0xE2, 0x1C, 0x26, 0xF0, 0x73, 0x36, 0x63, 0x56, 0x31, 0x4E, 0x6B, 0x55, 0x62, 0x79, 0xC6, 0x91, - 0x00, 0x35, 0xB1, 0x2A, 0xA6, 0x42, 0xDF, 0xEB, 0x3C, 0x51, 0xEA, 0x97, 0x57, 0x94, 0x8C, 0x80, - 0x34, 0x5C, 0xD2, 0x76, 0xA4, 0xE9, 0x85, 0xE8, 0xBB, 0x78, 0xE0, 0xB5, 0xAD, 0x0F, 0x87, 0x70, - 0xDD, 0xAE, 0xF4, 0xD9, 0x66, 0x54, 0x6F, 0xCC, 0x4C, 0x77, 0x3E, 0xCD, 0xF1, 0x75, 0x0A, 0xA1, - 0x28, 0x9B, 0x9A, 0x7E, 0x4B, 0x98, 0x99, 0x47, 0xFE, 0xA5, 0xF7, 0xB7, 0xA3, 0xE1, 0x9F, 0xBC, - 0x93, 0x44, 0x3A, 0x08, 0x89, 0x22, 0xEE, 0xB9, 0x45, 0xD6, 0x06, 0x09, 0xC9, 0xBD, 0x14, 0x0C, - 0xB6, 0x5E, 0x9C, 0x7A, 0x65, 0x59, 0xAA, 0x19, 0x5B, 0x7C, 0x18, 0x43, 0x92, 0x13, 0x15, 0x7B, - 0xED, 0xD5, 0xC7, 0x17, 0xEF, 0x86, 0x90, 0xC2, 0x74, 0x64, 0xF3, 0xDC, 0x6C, 0x38, 0x05, 0x1D, - 0xC8, 0x0E, 0xEC, 0x6A, 0x32, 0xDA, 0xD7, 0xC3, 0xDB, 0x8B, 0x24, 0xB3, 0x5D, 0x2E, 0xBA, 0xA2, - 0xD8, 0x03, 0x88, 0x7D, 0x7F, 0x69, 0x8A, 0xFD, 0xCA, 0x4F, 0x30, 0x9E, 0xA0, 0xD1, 0x5A, 0x53, - 0xDE, 0x3F, 0x84, 0xAC, 0xF8, 0xA7, 0x2D, 0x1F, 0x1E, 0xE3, 0x58, 0x50, 0x6D, 0x48, 0x07, 0xA8 -}; - -//----------------------------------------------------------------------------- -// Functions - MPK file format - -// This function converts MPK file header into MPQ file header -DWORD ConvertMpkHeaderToFormat4( - TMPQArchive * ha, - ULONGLONG FileSize, - DWORD dwFlags) -{ - TMPKHeader * pMpkHeader = (TMPKHeader *)ha->HeaderData; - TMPQHeader Header; - - // Can't open the archive with certain flags - if(dwFlags & MPQ_OPEN_FORCE_MPQ_V1) - return ERROR_FILE_CORRUPT; - - // Translate the MPK header into a MPQ header - // Note: Hash table size and block table size are in bytes, not in entries - memset(&Header, 0, sizeof(TMPQHeader)); - Header.dwID = BSWAP_INT32_UNSIGNED(pMpkHeader->dwID); - Header.dwArchiveSize = BSWAP_INT32_UNSIGNED(pMpkHeader->dwArchiveSize); - Header.dwHeaderSize = BSWAP_INT32_UNSIGNED(pMpkHeader->dwHeaderSize); - Header.dwHashTablePos = BSWAP_INT32_UNSIGNED(pMpkHeader->dwHashTablePos); - Header.dwHashTableSize = BSWAP_INT32_UNSIGNED(pMpkHeader->dwHashTableSize) / sizeof(TMPKHash); - Header.dwBlockTablePos = BSWAP_INT32_UNSIGNED(pMpkHeader->dwBlockTablePos); - Header.dwBlockTableSize = BSWAP_INT32_UNSIGNED(pMpkHeader->dwBlockTableSize) / sizeof(TMPKBlock); -// Header.dwUnknownPos = BSWAP_INT32_UNSIGNED(pMpkHeader->dwUnknownPos); -// Header.dwUnknownSize = BSWAP_INT32_UNSIGNED(pMpkHeader->dwUnknownSize); - assert(Header.dwHeaderSize == sizeof(TMPKHeader)); - - // Verify the MPK header - if(Header.dwID == ID_MPK && Header.dwHeaderSize == sizeof(TMPKHeader) && Header.dwArchiveSize == (DWORD)FileSize) - { - // The header ID must be ID_MPQ - Header.dwID = g_dwMpqSignature; - Header.wFormatVersion = MPQ_FORMAT_VERSION_1; - Header.wSectorSize = 3; - - // Initialize the fields of 3.0 header - Header.ArchiveSize64 = Header.dwArchiveSize; - Header.HashTableSize64 = Header.dwHashTableSize * sizeof(TMPQHash); - Header.BlockTableSize64 = Header.dwBlockTableSize * sizeof(TMPQBlock); - - // Copy the converted MPQ header back - memcpy(ha->HeaderData, &Header, sizeof(TMPQHeader)); - - // Mark this file as MPK file - ha->pfnHashString = HashStringLower; - ha->dwFlags |= MPQ_FLAG_READ_ONLY; - ha->dwSubType = MPQ_SUBTYPE_MPK; - return ERROR_SUCCESS; - } - return ERROR_FILE_CORRUPT; -} - -// Attempts to search a free hash entry in the hash table being converted. -// The created hash table must always be of nonzero size, -// should have no duplicated items and no deleted entries -TMPQHash * FindFreeHashEntry(TMPQHash * pHashTable, DWORD dwHashTableSize, DWORD dwStartIndex) -{ - TMPQHash * pHash; - DWORD dwIndex; - - // Set the initial index - dwStartIndex = dwIndex = (dwStartIndex & (dwHashTableSize - 1)); - assert(dwHashTableSize != 0); - - // Search the hash table and return the found entries in the following priority: - for(;;) - { - // We are not expecting to find matching entry in the hash table being built - // We are not expecting to find deleted entry either - pHash = pHashTable + dwIndex; - - // If we found a free entry, we need to stop searching - if(pHash->dwBlockIndex == HASH_ENTRY_FREE) - return pHash; - - // Move to the next hash entry. - // If we reached the starting entry, it's failure. - dwIndex = (dwIndex + 1) & (dwHashTableSize - 1); - if(dwIndex == dwStartIndex) - break; - } - - // We haven't found anything - assert(false); - return NULL; -} - -void DecryptMpkTable(void * pvMpkTable, size_t cbSize) -{ - LPBYTE pbMpkTable = (LPBYTE)pvMpkTable; - - for(size_t i = 0; i < cbSize; i++) - pbMpkTable[i] = MpkDecryptionKey[pbMpkTable[i]]; -} - -void * LoadMpkTable(TMPQArchive * ha, DWORD dwByteOffset, DWORD cbTableSize) -{ - ULONGLONG ByteOffset; - LPBYTE pbMpkTable = NULL; - - // Allocate space for the table - pbMpkTable = STORM_ALLOC(BYTE, cbTableSize); - if(pbMpkTable != NULL) - { - // Load and the MPK hash table - ByteOffset = ha->MpqPos + dwByteOffset; - if(FileStream_Read(ha->pStream, &ByteOffset, pbMpkTable, cbTableSize)) - { - // Decrypt the table - DecryptMpkTable(pbMpkTable, cbTableSize); - return pbMpkTable; - } - - // Free the MPK table - STORM_FREE(pbMpkTable); - pbMpkTable = NULL; - } - - // Return the table - return pbMpkTable; -} - -TMPQHash * LoadMpkHashTable(TMPQArchive * ha) -{ - TMPQHeader * pHeader = ha->pHeader; - TMPQHash * pHashTable = NULL; - TMPKHash * pMpkHash; - TMPQHash * pHash = NULL; - DWORD dwHashTableSize = pHeader->dwHashTableSize; - - // MPKs use different hash table searching. - // Instead of using MPQ_HASH_TABLE_INDEX hash as index, - // they store the value directly in the hash table. - // Also for faster searching, the hash table is sorted ascending by the value - - // Load and decrypt the MPK hash table. - pMpkHash = (TMPKHash *)LoadMpkTable(ha, pHeader->dwHashTablePos, pHeader->dwHashTableSize * sizeof(TMPKHash)); - if(pMpkHash != NULL) - { - // Calculate the hash table size as if it was real MPQ hash table - pHeader->dwHashTableSize = GetNearestPowerOfTwo(pHeader->dwHashTableSize); - pHeader->HashTableSize64 = pHeader->dwHashTableSize * sizeof(TMPQHash); - - // Now allocate table that will serve like a true MPQ hash table, - // so we translate the MPK hash table to MPQ hash table - pHashTable = STORM_ALLOC(TMPQHash, pHeader->dwHashTableSize); - if(pHashTable != NULL) - { - // Set the entire hash table to free - memset(pHashTable, 0xFF, (size_t)pHeader->HashTableSize64); - - // Copy the MPK hash table into MPQ hash table - for(DWORD i = 0; i < dwHashTableSize; i++) - { - // Finds the free hash entry in the hash table - // We don't expect any errors here, because we are putting files to empty hash table - pHash = FindFreeHashEntry(pHashTable, pHeader->dwHashTableSize, pMpkHash[i].dwName1); - assert(pHash->dwBlockIndex == HASH_ENTRY_FREE); - - // Copy the MPK hash entry to the hash table - pHash->dwBlockIndex = pMpkHash[i].dwBlockIndex; - pHash->Locale = 0; - pHash->Platform = 0; - pHash->Reserved = 0; - pHash->dwName1 = pMpkHash[i].dwName2; - pHash->dwName2 = pMpkHash[i].dwName3; - } - } - - // Free the temporary hash table - STORM_FREE(pMpkHash); - } - - return pHashTable; -} - -static DWORD ConvertMpkFlagsToMpqFlags(DWORD dwMpkFlags) -{ - DWORD dwMpqFlags = MPQ_FILE_EXISTS; - - // Check for flags that are always present - assert((dwMpkFlags & MPK_FILE_UNKNOWN_0001) != 0); - assert((dwMpkFlags & MPK_FILE_UNKNOWN_0010) != 0); - assert((dwMpkFlags & MPK_FILE_UNKNOWN_2000) != 0); - assert((dwMpkFlags & MPK_FILE_EXISTS) != 0); - - // Append the compressed flag - dwMpqFlags |= (dwMpkFlags & MPK_FILE_COMPRESSED) ? MPQ_FILE_COMPRESS : 0; - - // All files in the MPQ seem to be single unit files - dwMpqFlags |= MPQ_FILE_ENCRYPTED | MPQ_FILE_SINGLE_UNIT; - - return dwMpqFlags; -} - -TMPQBlock * LoadMpkBlockTable(TMPQArchive * ha) -{ - TMPQHeader * pHeader = ha->pHeader; - TMPKBlock * pMpkBlockTable; - TMPKBlock * pMpkBlockEnd; - TMPQBlock * pBlockTable = NULL; - TMPKBlock * pMpkBlock; - TMPQBlock * pMpqBlock; - - // Load and decrypt the MPK block table - pMpkBlockTable = pMpkBlock = (TMPKBlock *)LoadMpkTable(ha, pHeader->dwBlockTablePos, pHeader->dwBlockTableSize * sizeof(TMPKBlock)); - if(pMpkBlockTable != NULL) - { - // Allocate buffer for MPQ-like block table - pBlockTable = pMpqBlock = STORM_ALLOC(TMPQBlock, pHeader->dwBlockTableSize); - if(pBlockTable != NULL) - { - // Convert the MPK block table to MPQ block table - pMpkBlockEnd = pMpkBlockTable + pHeader->dwBlockTableSize; - while(pMpkBlock < pMpkBlockEnd) - { - // Translate the MPK block table entry to MPQ block table entry - pMpqBlock->dwFilePos = pMpkBlock->dwFilePos; - pMpqBlock->dwCSize = pMpkBlock->dwCSize; - pMpqBlock->dwFSize = pMpkBlock->dwFSize; - pMpqBlock->dwFlags = ConvertMpkFlagsToMpqFlags(pMpkBlock->dwFlags); - - // Move both - pMpkBlock++; - pMpqBlock++; - } - } - - // Free the MPK block table - STORM_FREE(pMpkBlockTable); - } - - return pBlockTable; -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/SCompression.cpp b/app/jni/src/libultraship/extern/StormLib/src/SCompression.cpp deleted file mode 100644 index 54c84b4..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/SCompression.cpp +++ /dev/null @@ -1,1162 +0,0 @@ -/*****************************************************************************/ -/* SCompression.cpp Copyright (c) Ladislav Zezula 2003 */ -/*---------------------------------------------------------------------------*/ -/* This module serves as a bridge between StormLib code and (de)compression */ -/* functions. All (de)compression calls go (and should only go) through this */ -/* module. No system headers should be included in this module to prevent */ -/* compile-time problems. */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 01.04.03 1.00 Lad The first version of SCompression.cpp */ -/* 19.11.03 1.01 Dan Big endian handling */ -/*****************************************************************************/ - -#define __STORMLIB_SELF__ -#include "StormLib.h" -#include "StormCommon.h" - -//----------------------------------------------------------------------------- -// Local structures - -// Information about the input and output buffers for pklib -typedef struct -{ - unsigned char * pbInBuff; // Pointer to input data buffer - unsigned char * pbInBuffEnd; // End of the input buffer - unsigned char * pbOutBuff; // Pointer to output data buffer - unsigned char * pbOutBuffEnd; // Pointer to output data buffer -} TDataInfo; - -// Prototype of the compression function -// Function doesn't return an error. A success means that the size of compressed buffer -// is lower than size of uncompressed buffer. -typedef void (*COMPRESS)( - void * pvOutBuffer, // [out] Pointer to the buffer where the compressed data will be stored - int * pcbOutBuffer, // [in] Pointer to length of the buffer pointed by pvOutBuffer - void * pvInBuffer, // [in] Pointer to the buffer with data to compress - int cbInBuffer, // [in] Length of the buffer pointer by pvInBuffer - int * pCmpType, // [in] Compression-method specific value. ADPCM Setups this for the following Huffman compression - int nCmpLevel); // [in] Compression specific value. ADPCM uses this. Should be set to zero. - -// Prototype of the decompression function -// Returns 1 if success, 0 if failure -typedef int (*DECOMPRESS)( - void * pvOutBuffer, // [out] Pointer to the buffer where to store decompressed data - int * pcbOutBuffer, // [in] Pointer to total size of the buffer pointed by pvOutBuffer - // [out] Contains length of the decompressed data - void * pvInBuffer, // [in] Pointer to data to be decompressed - int cbInBuffer); // [in] Length of the data to be decompressed - -// Table of compression functions -typedef struct -{ - unsigned long uMask; // Compression mask - COMPRESS Compress; // Compression function -} TCompressTable; - -// Table of decompression functions -typedef struct -{ - unsigned long uMask; // Decompression bit - DECOMPRESS Decompress; // Decompression function -} TDecompressTable; - - -/*****************************************************************************/ -/* */ -/* Support for Huffman compression (0x01) */ -/* */ -/*****************************************************************************/ - -void Compress_huff(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer, int * pCmpType, int nCmpLevel) -{ - THuffmannTree ht(true); - TOutputStream os(pvOutBuffer, *pcbOutBuffer); - - STORMLIB_UNUSED(nCmpLevel); - *pcbOutBuffer = ht.Compress(&os, pvInBuffer, cbInBuffer, *pCmpType); -} - -int Decompress_huff(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer) -{ - THuffmannTree ht(false); - TInputStream is(pvInBuffer, cbInBuffer); - - *pcbOutBuffer = ht.Decompress(pvOutBuffer, *pcbOutBuffer, &is); - return (*pcbOutBuffer == 0) ? 0 : 1; -} - -/******************************************************************************/ -/* */ -/* Support for ZLIB compression (0x02) */ -/* */ -/******************************************************************************/ - -void Compress_ZLIB(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer, int * pCmpType, int nCmpLevel) -{ - z_stream z; // Stream information for zlib - int windowBits; - int nResult; - - // Keep compilers happy - STORMLIB_UNUSED(pCmpType); - STORMLIB_UNUSED(nCmpLevel); - - // Fill the stream structure for zlib - z.next_in = (Bytef *)pvInBuffer; - z.avail_in = (uInt)cbInBuffer; - z.total_in = cbInBuffer; - z.next_out = (Bytef *)pvOutBuffer; - z.avail_out = *pcbOutBuffer; - z.total_out = 0; - z.zalloc = NULL; - z.zfree = NULL; - - // Determine the proper window bits (WoW.exe build 12694) - if(cbInBuffer <= 0x100) - windowBits = 8; - else if(cbInBuffer <= 0x200) - windowBits = 9; - else if(cbInBuffer <= 0x400) - windowBits = 10; - else if(cbInBuffer <= 0x800) - windowBits = 11; - else if(cbInBuffer <= 0x1000) - windowBits = 12; - else if(cbInBuffer <= 0x2000) - windowBits = 13; - else if(cbInBuffer <= 0x4000) - windowBits = 14; - else - windowBits = 15; - - // Initialize the compression. - // Storm.dll uses zlib version 1.1.3 - // Wow.exe uses zlib version 1.2.3 - nResult = deflateInit2(&z, - 6, // Compression level used by WoW MPQs - Z_DEFLATED, - windowBits, - 8, - Z_DEFAULT_STRATEGY); - if(nResult == Z_OK) - { - // Call zlib to compress the data - nResult = deflate(&z, Z_FINISH); - - if(nResult == Z_OK || nResult == Z_STREAM_END) - *pcbOutBuffer = z.total_out; - - deflateEnd(&z); - } -} - -int Decompress_ZLIB(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer) -{ - z_stream z; // Stream information for zlib - int nResult; - - // Fill the stream structure for zlib - z.next_in = (Bytef *)pvInBuffer; - z.avail_in = (uInt)cbInBuffer; - z.total_in = cbInBuffer; - z.next_out = (Bytef *)pvOutBuffer; - z.avail_out = *pcbOutBuffer; - z.total_out = 0; - z.zalloc = NULL; - z.zfree = NULL; - - // Initialize the decompression structure. Storm.dll uses zlib version 1.1.3 - if((nResult = inflateInit(&z)) == Z_OK) - { - // Call zlib to decompress the data - nResult = inflate(&z, Z_FINISH); - *pcbOutBuffer = z.total_out; - inflateEnd(&z); - } - - return (nResult >= Z_OK); -} - -/******************************************************************************/ -/* */ -/* Support functions for PKWARE Data Compression Library compression (0x08) */ -/* */ -/******************************************************************************/ - -// Function loads data from the input buffer. Used by Pklib's "implode" -// and "explode" function as user-defined callback -// Returns number of bytes loaded -// -// char * buf - Pointer to a buffer where to store loaded data -// unsigned int * size - Max. number of bytes to read -// void * param - Custom pointer, parameter of implode/explode - -static unsigned int ReadInputData(char * buf, unsigned int * size, void * param) -{ - TDataInfo * pInfo = (TDataInfo *)param; - unsigned int nMaxAvail = (unsigned int)(pInfo->pbInBuffEnd - pInfo->pbInBuff); - unsigned int nToRead = *size; - - // Check the case when not enough data available - if(nToRead > nMaxAvail) - nToRead = nMaxAvail; - - // Load data and increment offsets - memcpy(buf, pInfo->pbInBuff, nToRead); - pInfo->pbInBuff += nToRead; - assert(pInfo->pbInBuff <= pInfo->pbInBuffEnd); - return nToRead; -} - -// Function for store output data. Used by Pklib's "implode" and "explode" -// as user-defined callback -// -// char * buf - Pointer to data to be written -// unsigned int * size - Number of bytes to write -// void * param - Custom pointer, parameter of implode/explode - -static void WriteOutputData(char * buf, unsigned int * size, void * param) -{ - TDataInfo * pInfo = (TDataInfo *)param; - unsigned int nMaxWrite = (unsigned int)(pInfo->pbOutBuffEnd - pInfo->pbOutBuff); - unsigned int nToWrite = *size; - - // Check the case when not enough space in the output buffer - if(nToWrite > nMaxWrite) - nToWrite = nMaxWrite; - - // Write output data and increments offsets - memcpy(pInfo->pbOutBuff, buf, nToWrite); - pInfo->pbOutBuff += nToWrite; - assert(pInfo->pbOutBuff <= pInfo->pbOutBuffEnd); -} - -static void Compress_PKLIB(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer, int * pCmpType, int nCmpLevel) -{ - TDataInfo Info; // Data information - char * work_buf = STORM_ALLOC(char, CMP_BUFFER_SIZE);// Pklib's work buffer - unsigned int dict_size; // Dictionary size - unsigned int ctype = CMP_BINARY; // Compression type - - // Keep compilers happy - STORMLIB_UNUSED(pCmpType); - STORMLIB_UNUSED(nCmpLevel); - - // Handle no-memory condition - if(work_buf != NULL) - { - // Fill data information structure - memset(work_buf, 0, CMP_BUFFER_SIZE); - Info.pbInBuff = (unsigned char *)pvInBuffer; - Info.pbInBuffEnd = (unsigned char *)pvInBuffer + cbInBuffer; - Info.pbOutBuff = (unsigned char *)pvOutBuffer; - Info.pbOutBuffEnd = (unsigned char *)pvOutBuffer + *pcbOutBuffer; - - // - // Set the dictionary size - // - // Diablo I uses fixed dictionary size of CMP_IMPLODE_DICT_SIZE3 - // Starcraft I uses the variable dictionary size based on algorithm below - // - - if (cbInBuffer < 0x600) - dict_size = CMP_IMPLODE_DICT_SIZE1; - else if(0x600 <= cbInBuffer && cbInBuffer < 0xC00) - dict_size = CMP_IMPLODE_DICT_SIZE2; - else - dict_size = CMP_IMPLODE_DICT_SIZE3; - - // Do the compression - if(implode(ReadInputData, WriteOutputData, work_buf, &Info, &ctype, &dict_size) == CMP_NO_ERROR) - *pcbOutBuffer = (int)(Info.pbOutBuff - (unsigned char *)pvOutBuffer); - - STORM_FREE(work_buf); - } -} - -static int Decompress_PKLIB(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer) -{ - TDataInfo Info; // Data information - char * work_buf; - int nResult = 0; - - // Allocate Pklib's work buffer - if((work_buf = STORM_ALLOC(char, EXP_BUFFER_SIZE)) != NULL) - { - // Fill data information structure - memset(work_buf, 0, EXP_BUFFER_SIZE); - Info.pbInBuff = (unsigned char *)pvInBuffer; - Info.pbInBuffEnd = (unsigned char *)pvInBuffer + cbInBuffer; - Info.pbOutBuff = (unsigned char *)pvOutBuffer; - Info.pbOutBuffEnd = (unsigned char *)pvOutBuffer + *pcbOutBuffer; - - // Do the decompression - if(explode(ReadInputData, WriteOutputData, work_buf, &Info) == CMP_NO_ERROR) - nResult = 1; - - // Give away the number of decompressed bytes - *pcbOutBuffer = (int)(Info.pbOutBuff - (unsigned char *)pvOutBuffer); - STORM_FREE(work_buf); - } - - return nResult; -} - -/******************************************************************************/ -/* */ -/* Support for Bzip2 compression (0x10) */ -/* */ -/******************************************************************************/ - -static void Compress_BZIP2(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer, int * pCmpType, int nCmpLevel) -{ - bz_stream strm; - int blockSize100k = 9; - int workFactor = 30; - int bzError; - - // Keep compilers happy - STORMLIB_UNUSED(pCmpType); - STORMLIB_UNUSED(nCmpLevel); - - // Initialize the BZIP2 compression - strm.bzalloc = NULL; - strm.bzfree = NULL; - strm.opaque = NULL; - - // Blizzard uses 9 as blockSize100k, (0x30 as workFactor) - // Last checked on Starcraft II - if(BZ2_bzCompressInit(&strm, blockSize100k, 0, workFactor) == BZ_OK) - { - strm.next_in = (char *)pvInBuffer; - strm.avail_in = cbInBuffer; - strm.next_out = (char *)pvOutBuffer; - strm.avail_out = *pcbOutBuffer; - - // Perform the compression - for(;;) - { - bzError = BZ2_bzCompress(&strm, (strm.avail_in != 0) ? BZ_RUN : BZ_FINISH); - if(bzError == BZ_STREAM_END || bzError < 0) - break; - } - - // Put the stream into idle state - BZ2_bzCompressEnd(&strm); - - if(bzError > 0) - *pcbOutBuffer = strm.total_out_lo32; - } -} - -static int Decompress_BZIP2(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer) -{ - bz_stream strm; - int nResult; - - // Initialize the BZIP2 decompression - strm.next_in = (char *)pvInBuffer; - strm.avail_in = cbInBuffer; - strm.next_out = (char *)pvOutBuffer; - strm.avail_out = *pcbOutBuffer; - strm.bzalloc = NULL; - strm.bzfree = NULL; - strm.opaque = NULL; - - // Initialize decompression - if((nResult = BZ2_bzDecompressInit(&strm, 0, 0)) == BZ_OK) - { - // Perform the decompression - nResult = BZ2_bzDecompress(&strm); - *pcbOutBuffer = strm.total_out_lo32; - BZ2_bzDecompressEnd(&strm); - } - - return (nResult >= BZ_OK); -} - -/******************************************************************************/ -/* */ -/* Support functions for LZMA compression (0x12) */ -/* */ -/******************************************************************************/ - -#define LZMA_HEADER_SIZE (1 + LZMA_PROPS_SIZE + 8) - -static SRes LZMA_Callback_Progress(void * /* p */, UInt64 /* inSize */, UInt64 /* outSize */) -{ - return SZ_OK; -} - -static void * LZMA_Callback_Alloc(void *p, size_t size) -{ - p = p; - return STORM_ALLOC(BYTE, size); -} - -/* address can be 0 */ -static void LZMA_Callback_Free(void *p, void *address) -{ - p = p; - if(address != NULL) - STORM_FREE(address); -} - -// -// Note: So far, I haven't seen any files compressed by LZMA. -// This code haven't been verified against code ripped from Starcraft II Beta, -// but we know that Starcraft LZMA decompression code is able to decompress -// the data compressed by StormLib. -// - -static void Compress_LZMA(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer, int * pCmpType, int nCmpLevel) -{ - ICompressProgress Progress; - CLzmaEncProps props; - ISzAlloc SzAlloc; - Byte * pbOutBuffer = (Byte *)pvOutBuffer; - Byte * destBuffer; - SizeT destLen = *pcbOutBuffer; - SizeT srcLen = cbInBuffer; - Byte encodedProps[LZMA_PROPS_SIZE]; - size_t encodedPropsSize = LZMA_PROPS_SIZE; - SRes nResult; - - // Keep compilers happy - STORMLIB_UNUSED(pCmpType); - STORMLIB_UNUSED(nCmpLevel); - - // Fill the callbacks in structures - Progress.Progress = LZMA_Callback_Progress; - SzAlloc.Alloc = LZMA_Callback_Alloc; - SzAlloc.Free = LZMA_Callback_Free; - - // Initialize properties - LzmaEncProps_Init(&props); - - // Perform compression - destBuffer = (Byte *)pvOutBuffer + LZMA_HEADER_SIZE; - destLen = *pcbOutBuffer - LZMA_HEADER_SIZE; - nResult = LzmaEncode(destBuffer, - &destLen, - (Byte *)pvInBuffer, - srcLen, - &props, - encodedProps, - &encodedPropsSize, - 0, - &Progress, - &SzAlloc, - &SzAlloc); - if(nResult != SZ_OK) - return; - - // If we failed to compress the data - if(destLen >= (SizeT)(*pcbOutBuffer - LZMA_HEADER_SIZE)) - return; - - // Write "useFilter" variable. Blizzard MPQ must not use filter. - *pbOutBuffer++ = 0; - - // Copy the encoded properties to the output buffer - memcpy(pvOutBuffer, encodedProps, encodedPropsSize); - pbOutBuffer += encodedPropsSize; - - // Copy the size of the data - *pbOutBuffer++ = (unsigned char)(srcLen >> 0x00); - *pbOutBuffer++ = (unsigned char)(srcLen >> 0x08); - *pbOutBuffer++ = (unsigned char)(srcLen >> 0x10); - *pbOutBuffer++ = (unsigned char)(srcLen >> 0x18); - *pbOutBuffer++ = 0; - *pbOutBuffer++ = 0; - *pbOutBuffer++ = 0; - *pbOutBuffer++ = 0; - - // Give the size of the data to the caller - *pcbOutBuffer = (unsigned int)(destLen + LZMA_HEADER_SIZE); -} - -static int Decompress_LZMA(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer) -{ - ELzmaStatus LzmaStatus; - ISzAlloc SzAlloc; - Byte * destBuffer = (Byte *)pvOutBuffer; - Byte * srcBuffer = (Byte *)pvInBuffer; - SizeT destLen = *pcbOutBuffer; - SizeT srcLen = cbInBuffer; - SRes nResult; - - // There must be at least 0x0E bytes in the buffer - if(srcLen <= LZMA_HEADER_SIZE) - return 0; - - // We only accept blocks that have no filter used - if(*srcBuffer != 0) - return 0; - - // Fill the callbacks in structures - SzAlloc.Alloc = LZMA_Callback_Alloc; - SzAlloc.Free = LZMA_Callback_Free; - - // Perform compression - srcLen = cbInBuffer - LZMA_HEADER_SIZE; - nResult = LzmaDecode(destBuffer, - &destLen, - srcBuffer + LZMA_HEADER_SIZE, - &srcLen, - srcBuffer + 1, - LZMA_PROPS_SIZE, - LZMA_FINISH_END, - &LzmaStatus, - &SzAlloc); - if(nResult != SZ_OK) - return 0; - - *pcbOutBuffer = (unsigned int)destLen; - return 1; -} - -static int Decompress_LZMA_MPK(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer) -{ - ELzmaStatus LzmaStatus; - ISzAlloc SzAlloc; - Byte * destBuffer = (Byte *)pvOutBuffer; - Byte * srcBuffer = (Byte *)pvInBuffer; - SizeT destLen = *pcbOutBuffer; - SizeT srcLen = cbInBuffer; - SRes nResult; - BYTE LZMA_Props[] = {0x5D, 0x00, 0x00, 0x00, 0x01}; - - // There must be at least 0x0E bytes in the buffer - if(srcLen <= sizeof(LZMA_Props)) - return 0; - - // Verify the props header - if(memcmp(pvInBuffer, LZMA_Props, sizeof(LZMA_Props))) - return 0; - - // Fill the callbacks in structures - SzAlloc.Alloc = LZMA_Callback_Alloc; - SzAlloc.Free = LZMA_Callback_Free; - - // Perform compression - srcLen = cbInBuffer - sizeof(LZMA_Props); - nResult = LzmaDecode(destBuffer, - &destLen, - srcBuffer + sizeof(LZMA_Props), - &srcLen, - srcBuffer, - sizeof(LZMA_Props), - LZMA_FINISH_END, - &LzmaStatus, - &SzAlloc); - if(nResult != SZ_OK) - return 0; - - *pcbOutBuffer = (unsigned int)destLen; - return 1; -} - -/******************************************************************************/ -/* */ -/* Support functions for SPARSE compression (0x20) */ -/* */ -/******************************************************************************/ - -void Compress_SPARSE(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer, int * pCmpType, int nCmpLevel) -{ - // Keep compilers happy - STORMLIB_UNUSED(pCmpType); - STORMLIB_UNUSED(nCmpLevel); - - CompressSparse(pvOutBuffer, pcbOutBuffer, pvInBuffer, cbInBuffer); -} - -int Decompress_SPARSE(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer) -{ - return DecompressSparse(pvOutBuffer, pcbOutBuffer, pvInBuffer, cbInBuffer); -} - -/******************************************************************************/ -/* */ -/* Support for ADPCM mono compression (0x40) */ -/* */ -/******************************************************************************/ - -static void Compress_ADPCM_mono(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer, int * pCmpType, int nCmpLevel) -{ - // Prepare the compression level for Huffmann compression, - // which will be called as next step - if(0 < nCmpLevel && nCmpLevel <= 2) - { - nCmpLevel = 4; - *pCmpType = 6; - } - else if(nCmpLevel == 3) - { - nCmpLevel = 6; - *pCmpType = 8; - } - else - { - nCmpLevel = 5; - *pCmpType = 7; - } - *pcbOutBuffer = CompressADPCM(pvOutBuffer, *pcbOutBuffer, pvInBuffer, cbInBuffer, 1, nCmpLevel); -} - -static int Decompress_ADPCM_mono(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer) -{ - *pcbOutBuffer = DecompressADPCM(pvOutBuffer, *pcbOutBuffer, pvInBuffer, cbInBuffer, 1); - return 1; -} - -/******************************************************************************/ -/* */ -/* Support for ADPCM stereo compression (0x80) */ -/* */ -/******************************************************************************/ - -static void Compress_ADPCM_stereo(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer, int * pCmpType, int nCmpLevel) -{ - // Prepare the compression level for Huffmann compression, - // which will be called as next step - if(0 < nCmpLevel && nCmpLevel <= 2) - { - nCmpLevel = 4; - *pCmpType = 6; - } - else if(nCmpLevel == 3) - { - nCmpLevel = 6; - *pCmpType = 8; - } - else - { - nCmpLevel = 5; - *pCmpType = 7; - } - *pcbOutBuffer = CompressADPCM(pvOutBuffer, *pcbOutBuffer, pvInBuffer, cbInBuffer, 2, nCmpLevel); -} - -static int Decompress_ADPCM_stereo(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer) -{ - *pcbOutBuffer = DecompressADPCM(pvOutBuffer, *pcbOutBuffer, pvInBuffer, cbInBuffer, 2); - return 1; -} - -/******************************************************************************/ -/* */ -/* Support for ADPCM mono & stereo (Starcraft I BETA - like) */ -/* */ -/******************************************************************************/ - -static int Decompress_ADPCM1_sc1b(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer) -{ - *pcbOutBuffer = DecompressADPCM_SC1B(pvOutBuffer, *pcbOutBuffer, pvInBuffer, cbInBuffer, 1); - return 1; -} - -static int Decompress_ADPCM2_sc1b(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer) -{ - *pcbOutBuffer = DecompressADPCM_SC1B(pvOutBuffer, *pcbOutBuffer, pvInBuffer, cbInBuffer, 2); - return 1; -} - -/*****************************************************************************/ -/* */ -/* SCompImplode */ -/* */ -/*****************************************************************************/ - -int WINAPI SCompImplode(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer) -{ - int cbOutBuffer; - - // Check for valid parameters - if(!pcbOutBuffer || *pcbOutBuffer < cbInBuffer || !pvOutBuffer || !pvInBuffer) - { - SetLastError(ERROR_INVALID_PARAMETER); - return 0; - } - - // Perform the compression - cbOutBuffer = *pcbOutBuffer; - Compress_PKLIB(pvOutBuffer, &cbOutBuffer, pvInBuffer, cbInBuffer, NULL, 0); - - // If the compression was unsuccessful, copy the data as-is - if(cbOutBuffer >= *pcbOutBuffer) - { - memcpy(pvOutBuffer, pvInBuffer, cbInBuffer); - cbOutBuffer = *pcbOutBuffer; - } - - *pcbOutBuffer = cbOutBuffer; - return 1; -} - -/*****************************************************************************/ -/* */ -/* SCompExplode */ -/* */ -/*****************************************************************************/ - -int WINAPI SCompExplode(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer) -{ - int cbOutBuffer; - - // Check for valid parameters - if(!pcbOutBuffer || *pcbOutBuffer < cbInBuffer || !pvOutBuffer || !pvInBuffer) - { - SetLastError(ERROR_INVALID_PARAMETER); - return 0; - } - - // If the input length is the same as output length, do nothing. - cbOutBuffer = *pcbOutBuffer; - if(cbInBuffer == cbOutBuffer) - { - // If the buffers are equal, don't copy anything. - if(pvInBuffer == pvOutBuffer) - return 1; - - memcpy(pvOutBuffer, pvInBuffer, cbInBuffer); - return 1; - } - - // Perform decompression - if(!Decompress_PKLIB(pvOutBuffer, &cbOutBuffer, pvInBuffer, cbInBuffer)) - { - SetLastError(ERROR_FILE_CORRUPT); - return 0; - } - - *pcbOutBuffer = cbOutBuffer; - return 1; -} - -/*****************************************************************************/ -/* */ -/* SCompCompress */ -/* */ -/*****************************************************************************/ - -// This table contains compress functions which can be applied to -// uncompressed data. Each bit means the corresponding -// compression method/function must be applied. -// -// WAVes compression Data compression -// ------------------ ------------------- -// 1st sector - 0x08 0x08 (D, HF, W2, SC, D2) -// Next sectors - 0x81 0x02 (W3) - -static TCompressTable cmp_table[] = -{ - {MPQ_COMPRESSION_SPARSE, Compress_SPARSE}, // Sparse compression - {MPQ_COMPRESSION_ADPCM_MONO, Compress_ADPCM_mono}, // IMA ADPCM mono compression - {MPQ_COMPRESSION_ADPCM_STEREO, Compress_ADPCM_stereo}, // IMA ADPCM stereo compression - {MPQ_COMPRESSION_HUFFMANN, Compress_huff}, // Huffmann compression - {MPQ_COMPRESSION_ZLIB, Compress_ZLIB}, // Compression with the "zlib" library - {MPQ_COMPRESSION_PKWARE, Compress_PKLIB}, // Compression with Pkware DCL - {MPQ_COMPRESSION_BZIP2, Compress_BZIP2} // Compression Bzip2 library -}; - -int WINAPI SCompCompress(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer, unsigned uCompressionMask, int nCmpType, int nCmpLevel) -{ - COMPRESS CompressFuncArray[0x10]; // Array of compression functions, applied sequentially - unsigned char CompressByte[0x10]; // CompressByte for each method in the CompressFuncArray array - unsigned char * pbWorkBuffer = NULL; // Temporary storage for decompressed data - unsigned char * pbOutBuffer = (unsigned char *)pvOutBuffer; - unsigned char * pbOutput = (unsigned char *)pvOutBuffer;// Current output buffer - unsigned char * pbInput = (unsigned char *)pvInBuffer; // Current input buffer - int nCompressCount = 0; - int nCompressIndex = 0; - int nAtLeastOneCompressionDone = 0; - int cbOutBuffer = 0; - int cbInLength = cbInBuffer; - int nResult = 1; - - // Check for valid parameters - if(!pcbOutBuffer || *pcbOutBuffer < cbInBuffer || !pvOutBuffer || !pvInBuffer) - { - SetLastError(ERROR_INVALID_PARAMETER); - return 0; - } - - // Zero input length brings zero output length - if(cbInBuffer == 0) - { - *pcbOutBuffer = 0; - return true; - } - - // Setup the compression function array - if(uCompressionMask == MPQ_COMPRESSION_LZMA) - { - CompressFuncArray[0] = Compress_LZMA; - CompressByte[0] = (char)uCompressionMask; - nCompressCount = 1; - } - else - { - // Fill the compressions array - for(size_t i = 0; i < _countof(cmp_table); i++) - { - // If the mask agrees, insert the compression function to the array - if(uCompressionMask & cmp_table[i].uMask) - { - CompressFuncArray[nCompressCount] = cmp_table[i].Compress; - CompressByte[nCompressCount] = (unsigned char)cmp_table[i].uMask; - uCompressionMask &= ~cmp_table[i].uMask; - nCompressCount++; - } - } - - // If at least one of the compressions remaing unknown, return an error - if(uCompressionMask != 0) - { - SetLastError(ERROR_NOT_SUPPORTED); - return 0; - } - } - - // If there is at least one compression, do it - if(nCompressCount > 0) - { - // If we need to do more than 1 compression, allocate intermediate buffer - if(nCompressCount > 1) - { - pbWorkBuffer = STORM_ALLOC(unsigned char, *pcbOutBuffer); - if(pbWorkBuffer == NULL) - { - SetLastError(ERROR_NOT_ENOUGH_MEMORY); - return 0; - } - } - - // Get the current compression index - nCompressIndex = nCompressCount - 1; - - // Perform all compressions in the array - for(int i = 0; i < nCompressCount; i++) - { - // Choose the proper output buffer - pbOutput = (nCompressIndex & 1) ? pbWorkBuffer : pbOutBuffer; - nCompressIndex--; - - // Perform the (next) compression - // Note that if the compression method is unable to compress the input data block - // by at least 2 bytes, we consider it as failure and will use source data instead - cbOutBuffer = *pcbOutBuffer - 1; - CompressFuncArray[i](pbOutput + 1, &cbOutBuffer, pbInput, cbInLength, &nCmpType, nCmpLevel); - - // If the compression failed, we copy the input buffer as-is. - // Note that there is one extra byte at the end of the intermediate buffer, so it should be OK - if(cbOutBuffer > (cbInLength - 2)) - { - memcpy(pbOutput + nAtLeastOneCompressionDone, pbInput, cbInLength); - cbOutBuffer = cbInLength; - } - else - { - // Remember that we have done at least one compression - nAtLeastOneCompressionDone = 1; - uCompressionMask |= CompressByte[i]; - } - - // Now point input buffer to the output buffer - pbInput = pbOutput + nAtLeastOneCompressionDone; - cbInLength = cbOutBuffer; - } - - // If at least one compression succeeded, put the compression - // mask to the begin of the output buffer - if(nAtLeastOneCompressionDone) - *pbOutBuffer = (unsigned char)uCompressionMask; - *pcbOutBuffer = cbOutBuffer + nAtLeastOneCompressionDone; - } - else - { - memcpy(pvOutBuffer, pvInBuffer, cbInBuffer); - *pcbOutBuffer = cbInBuffer; - } - - // Cleanup and return - if(pbWorkBuffer != NULL) - STORM_FREE(pbWorkBuffer); - return nResult; -} - -/*****************************************************************************/ -/* */ -/* SCompDecompress */ -/* */ -/*****************************************************************************/ - -// This table contains decompress functions which can be applied to -// uncompressed data. The compression mask is stored in the first byte -// of compressed data -static TDecompressTable dcmp_table[] = -{ - {MPQ_COMPRESSION_BZIP2, Decompress_BZIP2}, // Decompression with Bzip2 library - {MPQ_COMPRESSION_PKWARE, Decompress_PKLIB}, // Decompression with Pkware Data Compression Library - {MPQ_COMPRESSION_ZLIB, Decompress_ZLIB}, // Decompression with the "zlib" library - {MPQ_COMPRESSION_HUFFMANN, Decompress_huff}, // Huffmann decompression - {MPQ_COMPRESSION_ADPCM_STEREO, Decompress_ADPCM_stereo}, // IMA ADPCM stereo decompression - {MPQ_COMPRESSION_ADPCM_MONO, Decompress_ADPCM_mono}, // IMA ADPCM mono decompression - {MPQ_COMPRESSION_SPARSE, Decompress_SPARSE} // Sparse decompression -}; - -// Decompression table specific for Starcraft I BETA -// WAVE files are compressed by different ADPCM compression -static TDecompressTable dcmp_table_sc1b[] = -{ - {MPQ_COMPRESSION_PKWARE, Decompress_PKLIB}, // Decompression with Pkware Data Compression Library - {MPQ_COMPRESSION_HUFFMANN, Decompress_huff}, // Huffmann decompression - {0x10, Decompress_ADPCM1_sc1b}, // IMA ADPCM mono decompression - {0x20, Decompress_ADPCM2_sc1b}, // IMA ADPCM stereo decompression -}; - -static int SCompDecompressInternal(TDecompressTable * table, size_t table_length, void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer) -{ - unsigned char * pbWorkBuffer = NULL; - unsigned char * pbOutBuffer = (unsigned char *)pvOutBuffer; - unsigned char * pbInBuffer = (unsigned char *)pvInBuffer; - unsigned char * pbOutput = (unsigned char *)pvOutBuffer; - unsigned char * pbInput; - unsigned uCompressionMask; // Decompressions applied to the data - unsigned uCompressionCopy; // Decompressions applied to the data - int cbOutBuffer = *pcbOutBuffer; // Current size of the output buffer - int cbInLength; // Current size of the input buffer - int nCompressCount = 0; // Number of compressions to be applied - int nCompressIndex = 0; - int nResult = 1; - - // Verify buffer sizes - if(cbOutBuffer < cbInBuffer || cbInBuffer < 1) - return 0; - - // If the input length is the same as output length, do nothing. - if(cbOutBuffer == cbInBuffer) - { - // If the buffers are equal, don't copy anything. - if(pvInBuffer != pvOutBuffer) - memcpy(pvOutBuffer, pvInBuffer, cbInBuffer); - return 1; - } - - // Get applied compression types and decrement data length - uCompressionMask = uCompressionCopy = (unsigned char)(*pbInBuffer++); - cbInBuffer--; - - // Get current compressed data and length of it - pbInput = pbInBuffer; - cbInLength = cbInBuffer; - - // This compression function doesn't support LZMA - assert(uCompressionMask != MPQ_COMPRESSION_LZMA); - - // Parse the compression mask - for(size_t i = 0; i < table_length; i++) - { - // If the mask agrees, insert the compression function to the array - if(uCompressionMask & table[i].uMask) - { - uCompressionCopy &= ~table[i].uMask; - nCompressCount++; - } - } - - // If at least one of the compressions remaing unknown, return an error - if(nCompressCount == 0 || uCompressionCopy != 0) - { - SetLastError(ERROR_NOT_SUPPORTED); - return 0; - } - - // If there is more than one compression, we have to allocate extra buffer - if(nCompressCount > 1) - { - pbWorkBuffer = STORM_ALLOC(unsigned char, cbOutBuffer); - if(pbWorkBuffer == NULL) - { - SetLastError(ERROR_NOT_ENOUGH_MEMORY); - return 0; - } - } - - // Get the current compression index - nCompressIndex = nCompressCount - 1; - - // Apply all decompressions - for(size_t i = 0; i < table_length; i++) - { - // Perform the (next) decompression - if(uCompressionMask & table[i].uMask) - { - // Get the correct output buffer - pbOutput = (nCompressIndex & 1) ? pbWorkBuffer : pbOutBuffer; - nCompressIndex--; - - // Perform the decompression - cbOutBuffer = *pcbOutBuffer; - nResult = table[i].Decompress(pbOutput, &cbOutBuffer, pbInput, cbInLength); - if(nResult == 0 || cbOutBuffer == 0) - { - SetLastError(ERROR_FILE_CORRUPT); - nResult = 0; - break; - } - - // Switch buffers - cbInLength = cbOutBuffer; - pbInput = pbOutput; - } - } - - // Put the length of the decompressed data to the output buffer - *pcbOutBuffer = cbOutBuffer; - - // Cleanup and return - if(pbWorkBuffer != NULL) - STORM_FREE(pbWorkBuffer); - return nResult; -} - -int WINAPI SCompDecompress(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer) -{ - return SCompDecompressInternal(dcmp_table, _countof(dcmp_table), pvOutBuffer, pcbOutBuffer, pvInBuffer, cbInBuffer); -} - -int WINAPI SCompDecompress_SC1B(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer) -{ - return SCompDecompressInternal(dcmp_table_sc1b, _countof(dcmp_table_sc1b), pvOutBuffer, pcbOutBuffer, pvInBuffer, cbInBuffer); -} - -int WINAPI SCompDecompress2(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer) -{ - DECOMPRESS pfnDecompress1 = NULL; - DECOMPRESS pfnDecompress2 = NULL; - unsigned char * pbWorkBuffer = (unsigned char *)pvOutBuffer; - unsigned char * pbInBuffer = (unsigned char *)pvInBuffer; - int cbWorkBuffer = *pcbOutBuffer; - int nResult; - char CompressionMethod; - - // Verify buffer sizes - if(*pcbOutBuffer < cbInBuffer || cbInBuffer < 1) - return 0; - - // If the outputbuffer is as big as input buffer, just copy the block - if(*pcbOutBuffer == cbInBuffer) - { - if(pvOutBuffer != pvInBuffer) - memcpy(pvOutBuffer, pvInBuffer, cbInBuffer); - return 1; - } - - // Get the compression methods - CompressionMethod = *pbInBuffer++; - cbInBuffer--; - - // We only recognize a fixed set of compression methods - switch((unsigned char)CompressionMethod) - { - case MPQ_COMPRESSION_ZLIB: - pfnDecompress1 = Decompress_ZLIB; - break; - - case MPQ_COMPRESSION_PKWARE: - pfnDecompress1 = Decompress_PKLIB; - break; - - case MPQ_COMPRESSION_BZIP2: - pfnDecompress1 = Decompress_BZIP2; - break; - - case MPQ_COMPRESSION_LZMA: - pfnDecompress1 = Decompress_LZMA; - break; - - case MPQ_COMPRESSION_SPARSE: - pfnDecompress1 = Decompress_SPARSE; - break; - - case (MPQ_COMPRESSION_SPARSE | MPQ_COMPRESSION_ZLIB): - pfnDecompress1 = Decompress_ZLIB; - pfnDecompress2 = Decompress_SPARSE; - break; - - case (MPQ_COMPRESSION_SPARSE | MPQ_COMPRESSION_BZIP2): - pfnDecompress1 = Decompress_BZIP2; - pfnDecompress2 = Decompress_SPARSE; - break; - - // - // Note: Any combination including MPQ_COMPRESSION_ADPCM_MONO, - // MPQ_COMPRESSION_ADPCM_STEREO or MPQ_COMPRESSION_HUFFMANN - // is not supported by newer MPQs. - // - - case (MPQ_COMPRESSION_ADPCM_MONO | MPQ_COMPRESSION_HUFFMANN): - pfnDecompress1 = Decompress_huff; - pfnDecompress2 = Decompress_ADPCM_mono; - break; - - case (MPQ_COMPRESSION_ADPCM_STEREO | MPQ_COMPRESSION_HUFFMANN): - pfnDecompress1 = Decompress_huff; - pfnDecompress2 = Decompress_ADPCM_stereo; - break; - - default: - SetLastError(ERROR_FILE_CORRUPT); - return 0; - } - - // If we have to use two decompressions, allocate temporary buffer - if(pfnDecompress2 != NULL) - { - pbWorkBuffer = STORM_ALLOC(unsigned char, *pcbOutBuffer); - if(pbWorkBuffer == NULL) - { - SetLastError(ERROR_NOT_ENOUGH_MEMORY); - return 0; - } - } - - // Apply the first decompression method - nResult = pfnDecompress1(pbWorkBuffer, &cbWorkBuffer, pbInBuffer, cbInBuffer); - - // Apply the second decompression method, if any - if(pfnDecompress2 != NULL && nResult != 0) - { - cbInBuffer = cbWorkBuffer; - cbWorkBuffer = *pcbOutBuffer; - nResult = pfnDecompress2(pvOutBuffer, &cbWorkBuffer, pbWorkBuffer, cbInBuffer); - } - - // Supply the output buffer size - *pcbOutBuffer = cbWorkBuffer; - - // Free temporary buffer - if(pbWorkBuffer != pvOutBuffer) - STORM_FREE(pbWorkBuffer); - - if(nResult == 0) - SetLastError(ERROR_FILE_CORRUPT); - return nResult; -} - -/*****************************************************************************/ -/* */ -/* File decompression for MPK archives */ -/* */ -/*****************************************************************************/ - -int SCompDecompressMpk(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer) -{ - return Decompress_LZMA_MPK(pvOutBuffer, pcbOutBuffer, pvInBuffer, cbInBuffer); -} - diff --git a/app/jni/src/libultraship/extern/StormLib/src/SFileAddFile.cpp b/app/jni/src/libultraship/extern/StormLib/src/SFileAddFile.cpp deleted file mode 100644 index b1288f1..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/SFileAddFile.cpp +++ /dev/null @@ -1,1321 +0,0 @@ -/*****************************************************************************/ -/* SFileAddFile.cpp Copyright (c) Ladislav Zezula 2010 */ -/*---------------------------------------------------------------------------*/ -/* MPQ Editing functions */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 27.03.10 1.00 Lad Splitted from SFileCreateArchiveEx.cpp */ -/* 21.04.13 1.01 Dea AddFile callback now part of TMPQArchive */ -/*****************************************************************************/ - -#define __STORMLIB_SELF__ -#include "StormLib.h" -#include "StormCommon.h" - -//----------------------------------------------------------------------------- -// Local variables - -// Mask for lossy compressions -#define MPQ_LOSSY_COMPRESSION_MASK (MPQ_COMPRESSION_ADPCM_MONO | MPQ_COMPRESSION_ADPCM_STEREO | MPQ_COMPRESSION_HUFFMANN) - -// Data compression for SFileAddFile -// Kept here for compatibility with code that was created with StormLib version < 6.50 -static DWORD DefaultDataCompression = MPQ_COMPRESSION_PKWARE; - -//----------------------------------------------------------------------------- -// WAVE verification - -#define FILE_SIGNATURE_RIFF 0x46464952 -#define FILE_SIGNATURE_WAVE 0x45564157 -#define FILE_SIGNATURE_FMT 0x20746D66 -#define AUDIO_FORMAT_PCM 1 - -typedef struct _WAVE_FILE_HEADER -{ - DWORD dwChunkId; // 0x52494646 ("RIFF") - DWORD dwChunkSize; // Size of that chunk, in bytes - DWORD dwFormat; // Must be 0x57415645 ("WAVE") - - // Format sub-chunk - DWORD dwSubChunk1Id; // 0x666d7420 ("fmt ") - DWORD dwSubChunk1Size; // 0x16 for PCM - USHORT wAudioFormat; // 1 = PCM. Other value means some sort of compression - USHORT wChannels; // Number of channels - DWORD dwSampleRate; // 8000, 44100, etc. - DWORD dwBytesRate; // SampleRate * NumChannels * BitsPerSample/8 - USHORT wBlockAlign; // NumChannels * BitsPerSample/8 - USHORT wBitsPerSample; // 8 bits = 8, 16 bits = 16, etc. - - // Followed by "data" sub-chunk (we don't care) -} WAVE_FILE_HEADER, *PWAVE_FILE_HEADER; - -static bool IsWaveFile_16BitsPerAdpcmSample( - LPBYTE pbFileData, - DWORD cbFileData, - LPDWORD pdwChannels) -{ - PWAVE_FILE_HEADER pWaveHdr = (PWAVE_FILE_HEADER)pbFileData; - - // The amount of file data must be at least size of WAVE header - if(cbFileData > sizeof(WAVE_FILE_HEADER)) - { - // Check for the RIFF header - if(pWaveHdr->dwChunkId == FILE_SIGNATURE_RIFF && pWaveHdr->dwFormat == FILE_SIGNATURE_WAVE) - { - // Check for ADPCM format - if(pWaveHdr->dwSubChunk1Id == FILE_SIGNATURE_FMT && pWaveHdr->wAudioFormat == AUDIO_FORMAT_PCM) - { - // Now the number of bits per sample must be at least 16. - // If not, the WAVE file gets corrupted by the ADPCM compression - if(pWaveHdr->wBitsPerSample >= 0x10) - { - *pdwChannels = pWaveHdr->wChannels; - return true; - } - } - } - } - - return false; -} - -static DWORD FillWritableHandle( - TMPQArchive * ha, - TMPQFile * hf, - ULONGLONG FileTime, - DWORD dwFileSize, - DWORD dwFlags) -{ - TFileEntry * pFileEntry = hf->pFileEntry; - - // Initialize the hash entry for the file - hf->RawFilePos = ha->MpqPos + hf->MpqFilePos; - hf->dwDataSize = dwFileSize; - - // Initialize the block table entry for the file - pFileEntry->ByteOffset = hf->MpqFilePos; - pFileEntry->dwFileSize = dwFileSize; - pFileEntry->dwCmpSize = 0; - pFileEntry->dwFlags = dwFlags | MPQ_FILE_EXISTS; - - // Initialize hashing of the file - if((hf->hctx = STORM_ALLOC(hash_state, 1)) != NULL) - md5_init((hash_state *)hf->hctx); - - // Fill-in file time and CRC - pFileEntry->FileTime = FileTime; - pFileEntry->dwCrc32 = crc32(0, Z_NULL, 0); - - // Mark the archive as modified - ha->dwFlags |= MPQ_FLAG_CHANGED; - - // Call the callback, if needed - if(ha->pfnAddFileCB != NULL) - ha->pfnAddFileCB(ha->pvAddFileUserData, 0, hf->dwDataSize, false); - hf->dwAddFileError = ERROR_SUCCESS; - - return ERROR_SUCCESS; -} - -//----------------------------------------------------------------------------- -// MPQ write data functions - -static DWORD WriteDataToMpqFile( - TMPQArchive * ha, - TMPQFile * hf, - LPBYTE pbFileData, - DWORD dwDataSize, - DWORD dwCompression) -{ - TFileEntry * pFileEntry = hf->pFileEntry; - ULONGLONG ByteOffset; - LPBYTE pbCompressed = NULL; // Compressed (target) data - LPBYTE pbToWrite = hf->pbFileSector; // Data to write to the file - DWORD dwErrCode = ERROR_SUCCESS; - int nCompressionLevel; // ADPCM compression level (only used for wave files) - - // Make sure that the caller won't overrun the previously initiated file size - assert(hf->dwFilePos + dwDataSize <= pFileEntry->dwFileSize); - assert(hf->dwSectorCount != 0); - assert(hf->pbFileSector != NULL); - if((hf->dwFilePos + dwDataSize) > pFileEntry->dwFileSize) - return ERROR_DISK_FULL; - - // Now write all data to the file sector buffer - if(dwErrCode == ERROR_SUCCESS) - { - DWORD dwBytesInSector = hf->dwFilePos % hf->dwSectorSize; - DWORD dwSectorIndex = hf->dwFilePos / hf->dwSectorSize; - DWORD dwBytesToCopy; - - // Process all data. - while(dwDataSize != 0) - { - dwBytesToCopy = dwDataSize; - - // Check for sector overflow - if(dwBytesToCopy > (hf->dwSectorSize - dwBytesInSector)) - dwBytesToCopy = (hf->dwSectorSize - dwBytesInSector); - - // Copy the data to the file sector - memcpy(hf->pbFileSector + dwBytesInSector, pbFileData, dwBytesToCopy); - dwBytesInSector += dwBytesToCopy; - pbFileData += dwBytesToCopy; - dwDataSize -= dwBytesToCopy; - - // Update the file position - hf->dwFilePos += dwBytesToCopy; - - // If the current sector is full, or if the file is already full, - // then write the data to the MPQ - if(dwBytesInSector >= hf->dwSectorSize || hf->dwFilePos >= pFileEntry->dwFileSize) - { - // Set the position in the file - ByteOffset = hf->RawFilePos + pFileEntry->dwCmpSize; - - // Update MD5 and CRC32 of the file - if(hf->hctx != NULL) - md5_process((hash_state *)hf->hctx, hf->pbFileSector, dwBytesInSector); - hf->dwCrc32 = crc32(hf->dwCrc32, hf->pbFileSector, dwBytesInSector); - - // Compress the file sector, if needed - if(pFileEntry->dwFlags & MPQ_FILE_COMPRESS_MASK) - { - int nOutBuffer = (int)dwBytesInSector; - int nInBuffer = (int)dwBytesInSector; - - // If the file is compressed, allocate buffer for the compressed data. - // Note that we allocate buffer that is a bit longer than sector size, - // for case if the compression method performs a buffer overrun - if(pbCompressed == NULL) - { - pbToWrite = pbCompressed = STORM_ALLOC(BYTE, hf->dwSectorSize + 0x100); - if(pbCompressed == NULL) - { - dwErrCode = ERROR_NOT_ENOUGH_MEMORY; - break; - } - } - - // - // Note that both SCompImplode and SCompCompress copy data as-is, - // if they are unable to compress the data. - // - - if(pFileEntry->dwFlags & MPQ_FILE_IMPLODE) - { - SCompImplode(pbCompressed, &nOutBuffer, hf->pbFileSector, nInBuffer); - } - - if(pFileEntry->dwFlags & MPQ_FILE_COMPRESS) - { - // If this is the first sector, we need to override the given compression - // by the first sector compression. This is because the entire sector must - // be compressed by the same compression. - // - // Test case: - // - // WRITE_FILE(hFile, pvBuffer, 0x10, MPQ_COMPRESSION_PKWARE) // Write 0x10 bytes (sector 0) - // WRITE_FILE(hFile, pvBuffer, 0x10, MPQ_COMPRESSION_ADPCM_MONO) // Write 0x10 bytes (still sector 0) - // WRITE_FILE(hFile, pvBuffer, 0x10, MPQ_COMPRESSION_ADPCM_MONO) // Write 0x10 bytes (still sector 0) - // WRITE_FILE(hFile, pvBuffer, 0x10, MPQ_COMPRESSION_ADPCM_MONO) // Write 0x10 bytes (still sector 0) - dwCompression = (dwSectorIndex == 0) ? hf->dwCompression0 : dwCompression; - - // If the caller wants ADPCM compression, we will set wave compression level to 4, - // which corresponds to medium quality - nCompressionLevel = (dwCompression & MPQ_LOSSY_COMPRESSION_MASK) ? 4 : -1; - SCompCompress(pbCompressed, &nOutBuffer, hf->pbFileSector, nInBuffer, (unsigned)dwCompression, 0, nCompressionLevel); - } - - // Update sector positions - dwBytesInSector = nOutBuffer; - if(hf->SectorOffsets != NULL) - hf->SectorOffsets[dwSectorIndex+1] = hf->SectorOffsets[dwSectorIndex] + dwBytesInSector; - - // We have to calculate sector CRC, if enabled - if(hf->SectorChksums != NULL) - hf->SectorChksums[dwSectorIndex] = adler32(0, pbCompressed, nOutBuffer); - } - - // Encrypt the sector, if necessary - if(pFileEntry->dwFlags & MPQ_FILE_ENCRYPTED) - { - BSWAP_ARRAY32_UNSIGNED(pbToWrite, dwBytesInSector); - EncryptMpqBlock(pbToWrite, dwBytesInSector, hf->dwFileKey + dwSectorIndex); - BSWAP_ARRAY32_UNSIGNED(pbToWrite, dwBytesInSector); - } - - // Write the file sector - if(!FileStream_Write(ha->pStream, &ByteOffset, pbToWrite, dwBytesInSector)) - { - dwErrCode = GetLastError(); - break; - } - - // Call the compact callback, if any - if(ha->pfnAddFileCB != NULL) - ha->pfnAddFileCB(ha->pvAddFileUserData, hf->dwFilePos, hf->dwDataSize, false); - - // Update the compressed file size - pFileEntry->dwCmpSize += dwBytesInSector; - dwBytesInSector = 0; - dwSectorIndex++; - } - } - } - - // Cleanup - if(pbCompressed != NULL) - STORM_FREE(pbCompressed); - return dwErrCode; -} - -//----------------------------------------------------------------------------- -// Recrypts file data for file renaming - -static DWORD RecryptFileData( - TMPQArchive * ha, - TMPQFile * hf, - const char * szFileName, - const char * szNewFileName) -{ - ULONGLONG RawFilePos; - TFileEntry * pFileEntry = hf->pFileEntry; - DWORD dwBytesToRecrypt = pFileEntry->dwCmpSize; - DWORD dwOldKey; - DWORD dwNewKey; - DWORD dwErrCode = ERROR_SUCCESS; - - // The file must be encrypted - assert(pFileEntry->dwFlags & MPQ_FILE_ENCRYPTED); - - // File decryption key is calculated from the plain name - szNewFileName = GetPlainFileName(szNewFileName); - szFileName = GetPlainFileName(szFileName); - - // Calculate both file keys - dwOldKey = DecryptFileKey(szFileName, pFileEntry->ByteOffset, pFileEntry->dwFileSize, pFileEntry->dwFlags); - dwNewKey = DecryptFileKey(szNewFileName, pFileEntry->ByteOffset, pFileEntry->dwFileSize, pFileEntry->dwFlags); - - // Incase the keys are equal, don't recrypt the file - if(dwNewKey == dwOldKey) - return ERROR_SUCCESS; - hf->dwFileKey = dwOldKey; - - // Calculate the raw position of the file in the archive - hf->MpqFilePos = pFileEntry->ByteOffset; - hf->RawFilePos = ha->MpqPos + hf->MpqFilePos; - - // Allocate buffer for file transfer - dwErrCode = AllocateSectorBuffer(hf); - if(dwErrCode != ERROR_SUCCESS) - return dwErrCode; - - // Also allocate buffer for sector offsets - // Note: Don't load sector checksums, we don't need to recrypt them - dwErrCode = AllocateSectorOffsets(hf, true); - if(dwErrCode != ERROR_SUCCESS) - return dwErrCode; - - // If we have sector offsets, recrypt these as well - if(hf->SectorOffsets != NULL) - { - // Allocate secondary buffer for sectors copy - DWORD * SectorOffsetsCopy = STORM_ALLOC(DWORD, hf->SectorOffsets[0] / sizeof(DWORD)); - DWORD dwSectorOffsLen = hf->SectorOffsets[0]; - - if(SectorOffsetsCopy == NULL) - return ERROR_NOT_ENOUGH_MEMORY; - - // Recrypt the array of sector offsets - memcpy(SectorOffsetsCopy, hf->SectorOffsets, dwSectorOffsLen); - EncryptMpqBlock(SectorOffsetsCopy, dwSectorOffsLen, dwNewKey - 1); - BSWAP_ARRAY32_UNSIGNED(SectorOffsetsCopy, dwSectorOffsLen); - - // Write the recrypted array back - if(!FileStream_Write(ha->pStream, &hf->RawFilePos, SectorOffsetsCopy, dwSectorOffsLen)) - dwErrCode = GetLastError(); - STORM_FREE(SectorOffsetsCopy); - } - - // Now we have to recrypt all file sectors. We do it without - // recompression, because recompression is not necessary in this case - if(dwErrCode == ERROR_SUCCESS) - { - for(DWORD dwSector = 0; dwSector < hf->dwSectorCount; dwSector++) - { - DWORD dwRawDataInSector = hf->dwSectorSize; - DWORD dwRawByteOffset = dwSector * hf->dwSectorSize; - - // Last sector: If there is not enough bytes remaining in the file, cut the raw size - if(dwRawDataInSector > dwBytesToRecrypt) - dwRawDataInSector = dwBytesToRecrypt; - - // Fix the raw data length if the file is compressed - if(hf->SectorOffsets != NULL) - { - dwRawDataInSector = hf->SectorOffsets[dwSector+1] - hf->SectorOffsets[dwSector]; - dwRawByteOffset = hf->SectorOffsets[dwSector]; - } - - // Calculate the raw file offset of the file sector - RawFilePos = CalculateRawSectorOffset(hf, dwRawByteOffset); - - // Read the file sector - if(!FileStream_Read(ha->pStream, &RawFilePos, hf->pbFileSector, dwRawDataInSector)) - { - dwErrCode = GetLastError(); - break; - } - - // If necessary, re-encrypt the sector - // Note: Recompression is not necessary here. Unlike encryption, - // the compression does not depend on the position of the file in MPQ. - BSWAP_ARRAY32_UNSIGNED(hf->pbFileSector, dwRawDataInSector); - DecryptMpqBlock(hf->pbFileSector, dwRawDataInSector, dwOldKey + dwSector); - EncryptMpqBlock(hf->pbFileSector, dwRawDataInSector, dwNewKey + dwSector); - BSWAP_ARRAY32_UNSIGNED(hf->pbFileSector, dwRawDataInSector); - - // Write the sector back - if(!FileStream_Write(ha->pStream, &RawFilePos, hf->pbFileSector, dwRawDataInSector)) - { - dwErrCode = GetLastError(); - break; - } - - // Decrement number of bytes remaining - dwBytesToRecrypt -= hf->dwSectorSize; - } - } - - return dwErrCode; -} - -//----------------------------------------------------------------------------- -// Internal support for MPQ modifications - -DWORD SFileAddFile_Init( - TMPQArchive * ha, - const char * szFileName, - ULONGLONG FileTime, - DWORD dwFileSize, - LCID lcFileLocale, - DWORD dwFlags, - TMPQFile ** phf) -{ - TFileEntry * pFileEntry = NULL; - TMPQFile * hf = NULL; // File structure for newly added file - DWORD dwHashIndex = HASH_ENTRY_FREE; - DWORD dwErrCode = ERROR_SUCCESS; - - // - // Note: This is an internal function so no validity checks are done. - // It is the caller's responsibility to make sure that no invalid - // flags get to this point - // - - // Sestor CRC is not allowed with single unit files - if(dwFlags & MPQ_FILE_SINGLE_UNIT) - dwFlags &= ~MPQ_FILE_SECTOR_CRC; - - // Sector CRC is not allowed if the file is not compressed - if(!(dwFlags & MPQ_FILE_COMPRESS_MASK)) - dwFlags &= ~MPQ_FILE_SECTOR_CRC; - - // Fix Key is not allowed if the file is not encrypted - if(!(dwFlags & MPQ_FILE_ENCRYPTED)) - dwFlags &= ~MPQ_FILE_FIX_KEY; - - // If the MPQ is of version 3.0 or higher, we ignore file locale. - // This is because HET and BET tables have no known support for it - if(ha->pHeader->wFormatVersion >= MPQ_FORMAT_VERSION_3) - lcFileLocale = 0; - - // Allocate the TMPQFile entry for newly added file - hf = CreateWritableHandle(ha, dwFileSize); - if(hf == NULL) - return false; - - // Allocate file entry in the MPQ - if(dwErrCode == ERROR_SUCCESS) - { - // Check if the file already exists in the archive - pFileEntry = GetFileEntryExact(ha, szFileName, lcFileLocale, &dwHashIndex); - if(pFileEntry != NULL) - { - if(dwFlags & MPQ_FILE_REPLACEEXISTING) - InvalidateInternalFiles(ha); - else - dwErrCode = ERROR_ALREADY_EXISTS; - } - else - { - // Attempt to allocate new file entry - pFileEntry = AllocateFileEntry(ha, szFileName, lcFileLocale, &dwHashIndex); - if(pFileEntry != NULL) - InvalidateInternalFiles(ha); - else - dwErrCode = ERROR_DISK_FULL; - } - - // Set the file entry to the file structure - hf->pFileEntry = pFileEntry; - } - - // Prepare the pointer to hash table entry - if(dwErrCode == ERROR_SUCCESS && ha->pHashTable != NULL && dwHashIndex < ha->pHeader->dwHashTableSize) - { - hf->pHashEntry = ha->pHashTable + dwHashIndex; - hf->pHashEntry->Locale = SFILE_LOCALE(lcFileLocale); - hf->pHashEntry->Platform = SFILE_PLATFORM(lcFileLocale); - hf->pHashEntry->Reserved = 0; - } - - // Prepare the file key - if(dwErrCode == ERROR_SUCCESS && (dwFlags & MPQ_FILE_ENCRYPTED)) - { - hf->dwFileKey = DecryptFileKey(szFileName, hf->MpqFilePos, dwFileSize, dwFlags); - if(hf->dwFileKey == 0) - dwErrCode = ERROR_UNKNOWN_FILE_KEY; - } - - // Fill the file entry and TMPQFile structure - if(dwErrCode == ERROR_SUCCESS) - { - // At this point, the file name in the file entry must be set - assert(pFileEntry->szFileName != NULL); - assert(_stricmp(pFileEntry->szFileName, szFileName) == 0); - - dwErrCode = FillWritableHandle(ha, hf, FileTime, dwFileSize, dwFlags); - } - - // Free the file handle if failed - if(dwErrCode != ERROR_SUCCESS && hf != NULL) - FreeFileHandle(hf); - - // Give the handle to the caller - *phf = hf; - return dwErrCode; -} - -DWORD SFileAddFile_Init( - TMPQArchive * ha, - TMPQFile * hfSrc, - TMPQFile ** phf) -{ - TFileEntry * pFileEntry = NULL; - TMPQFile * hf = NULL; // File structure for newly added file - ULONGLONG FileTime = hfSrc->pFileEntry->FileTime; - DWORD dwFileSize = hfSrc->pFileEntry->dwFileSize; - DWORD dwFlags = hfSrc->pFileEntry->dwFlags; - DWORD dwErrCode = ERROR_SUCCESS; - - // Allocate the TMPQFile entry for newly added file - hf = CreateWritableHandle(ha, dwFileSize); - if(hf == NULL) - dwErrCode = ERROR_NOT_ENOUGH_MEMORY; - - // We need to keep the file entry index the same like in the source archive - // This is because multiple hash table entries can point to the same file entry - if(dwErrCode == ERROR_SUCCESS) - { - // Retrieve the file entry for the target file - pFileEntry = ha->pFileTable + (hfSrc->pFileEntry - hfSrc->ha->pFileTable); - - // Copy all variables except file name - if((pFileEntry->dwFlags & MPQ_FILE_EXISTS) == 0) - { - pFileEntry[0] = hfSrc->pFileEntry[0]; - pFileEntry->szFileName = NULL; - } - else - dwErrCode = ERROR_ALREADY_EXISTS; - - // Set the file entry to the file structure - hf->pFileEntry = pFileEntry; - } - - // Prepare the pointer to hash table entry - if(dwErrCode == ERROR_SUCCESS && ha->pHashTable != NULL && hfSrc->pHashEntry != NULL) - { - hf->dwHashIndex = (DWORD)(hfSrc->pHashEntry - hfSrc->ha->pHashTable); - hf->pHashEntry = ha->pHashTable + hf->dwHashIndex; - } - - // Prepare the file key (copy from source file) - if(dwErrCode == ERROR_SUCCESS && (dwFlags & MPQ_FILE_ENCRYPTED)) - { - hf->dwFileKey = hfSrc->dwFileKey; - if(hf->dwFileKey == 0) - dwErrCode = ERROR_UNKNOWN_FILE_KEY; - } - - // Fill the file entry and TMPQFile structure - if(dwErrCode == ERROR_SUCCESS) - { - dwErrCode = FillWritableHandle(ha, hf, FileTime, dwFileSize, dwFlags); - } - - // Free the file handle if failed - if(dwErrCode != ERROR_SUCCESS && hf != NULL) - FreeFileHandle(hf); - - // Give the handle to the caller - *phf = hf; - return dwErrCode; -} - -DWORD SFileAddFile_Write(TMPQFile * hf, const void * pvData, DWORD dwSize, DWORD dwCompression) -{ - TMPQArchive * ha; - TFileEntry * pFileEntry; - DWORD dwErrCode = ERROR_SUCCESS; - - // Don't bother if the caller gave us zero size - if(pvData == NULL || dwSize == 0) - return ERROR_SUCCESS; - - // Get pointer to the MPQ archive - pFileEntry = hf->pFileEntry; - ha = hf->ha; - - // Allocate file buffers - if(hf->pbFileSector == NULL) - { - ULONGLONG RawFilePos = hf->RawFilePos; - - // Allocate buffer for file sector - hf->dwAddFileError = dwErrCode = AllocateSectorBuffer(hf); - if(dwErrCode != ERROR_SUCCESS) - return dwErrCode; - - // Allocate patch info, if the data is patch - if(hf->pPatchInfo == NULL && IsIncrementalPatchFile(pvData, dwSize, &hf->dwPatchedFileSize)) - { - // Set the MPQ_FILE_PATCH_FILE flag - pFileEntry->dwFlags |= MPQ_FILE_PATCH_FILE; - - // Allocate the patch info - hf->dwAddFileError = dwErrCode = AllocatePatchInfo(hf, false); - if(dwErrCode != ERROR_SUCCESS) - return dwErrCode; - } - - // Allocate sector offsets - if(hf->SectorOffsets == NULL) - { - hf->dwAddFileError = dwErrCode = AllocateSectorOffsets(hf, false); - if(dwErrCode != ERROR_SUCCESS) - return dwErrCode; - } - - // Create array of sector checksums - if(hf->SectorChksums == NULL && (pFileEntry->dwFlags & MPQ_FILE_SECTOR_CRC)) - { - hf->dwAddFileError = dwErrCode = AllocateSectorChecksums(hf, false); - if(dwErrCode != ERROR_SUCCESS) - return dwErrCode; - } - - // Pre-save the patch info, if any - if(hf->pPatchInfo != NULL) - { - if(!FileStream_Write(ha->pStream, &RawFilePos, hf->pPatchInfo, hf->pPatchInfo->dwLength)) - dwErrCode = GetLastError(); - - pFileEntry->dwCmpSize += hf->pPatchInfo->dwLength; - RawFilePos += hf->pPatchInfo->dwLength; - } - - // Pre-save the sector offset table, just to reserve space in the file. - // Note that we dont need to swap the sector positions, nor encrypt the table - // at the moment, as it will be written again after writing all file sectors. - if(hf->SectorOffsets != NULL) - { - if(!FileStream_Write(ha->pStream, &RawFilePos, hf->SectorOffsets, hf->SectorOffsets[0])) - dwErrCode = GetLastError(); - - pFileEntry->dwCmpSize += hf->SectorOffsets[0]; - RawFilePos += hf->SectorOffsets[0]; - } - } - - // Write the MPQ data to the file - if(dwErrCode == ERROR_SUCCESS) - { - // Save the first sector compression to the file structure - // Note that the entire first file sector will be compressed - // by compression that was passed to the first call of SFileAddFile_Write - if(hf->dwFilePos == 0) - hf->dwCompression0 = dwCompression; - - // Write the data to the MPQ - dwErrCode = WriteDataToMpqFile(ha, hf, (LPBYTE)pvData, dwSize, dwCompression); - } - - // If it succeeded and we wrote all the file data, - // we need to re-save sector offset table - if(dwErrCode == ERROR_SUCCESS) - { - if(hf->dwFilePos >= pFileEntry->dwFileSize) - { - // Finish calculating CRC32 - pFileEntry->dwCrc32 = hf->dwCrc32; - - // Finish calculating MD5 - if(hf->hctx != NULL) - md5_done((hash_state *)hf->hctx, pFileEntry->md5); - - // If we also have sector checksums, write them to the file - if(hf->SectorChksums != NULL) - { - dwErrCode = WriteSectorChecksums(hf); - } - - // Now write patch info - if(hf->pPatchInfo != NULL) - { - memcpy(hf->pPatchInfo->md5, pFileEntry->md5, MD5_DIGEST_SIZE); - hf->pPatchInfo->dwDataSize = pFileEntry->dwFileSize; - pFileEntry->dwFileSize = hf->dwPatchedFileSize; - dwErrCode = WritePatchInfo(hf); - } - - // Now write sector offsets to the file - if(hf->SectorOffsets != NULL) - { - dwErrCode = WriteSectorOffsets(hf); - } - - // Write the MD5 hashes of each file chunk, if required - if(ha->pHeader->dwRawChunkSize != 0) - { - dwErrCode = WriteMpqDataMD5(ha->pStream, - ha->MpqPos + pFileEntry->ByteOffset, - hf->pFileEntry->dwCmpSize, - ha->pHeader->dwRawChunkSize); - } - } - } - - // Update the archive size - if((ha->MpqPos + pFileEntry->ByteOffset + pFileEntry->dwCmpSize) > ha->FileSize) - ha->FileSize = ha->MpqPos + pFileEntry->ByteOffset + pFileEntry->dwCmpSize; - - // Store the error code from the Write File operation - hf->dwAddFileError = dwErrCode; - return dwErrCode; -} - -DWORD SFileAddFile_Finish(TMPQFile * hf) -{ - TMPQArchive * ha = hf->ha; - TFileEntry * pFileEntry = hf->pFileEntry; - DWORD dwErrCode = hf->dwAddFileError; - - // If all previous operations succeeded, we can update the MPQ - if(dwErrCode == ERROR_SUCCESS) - { - // Verify if the caller wrote the file properly - if(hf->pPatchInfo == NULL) - { - assert(pFileEntry != NULL); - if(hf->dwFilePos != pFileEntry->dwFileSize) - dwErrCode = ERROR_CAN_NOT_COMPLETE; - } - else - { - if(hf->dwFilePos != hf->pPatchInfo->dwDataSize) - dwErrCode = ERROR_CAN_NOT_COMPLETE; - } - } - - // Now we need to recreate the HET table, if exists - if(dwErrCode == ERROR_SUCCESS && ha->pHetTable != NULL) - { - dwErrCode = RebuildHetTable(ha); - } - - // Update the block table size - if(dwErrCode == ERROR_SUCCESS) - { - // Call the user callback, if any - if(ha->pfnAddFileCB != NULL) - ha->pfnAddFileCB(ha->pvAddFileUserData, hf->dwDataSize, hf->dwDataSize, true); - } - else - { - // Free the file entry in MPQ tables - if(pFileEntry != NULL) - DeleteFileEntry(ha, hf); - } - - // Clear the add file callback - FreeFileHandle(hf); - return dwErrCode; -} - -//----------------------------------------------------------------------------- -// Adds data as file to the archive - -bool WINAPI SFileCreateFile( - HANDLE hMpq, - const char * szArchivedName, - ULONGLONG FileTime, - DWORD dwFileSize, - LCID lcFileLocale, - DWORD dwFlags, - HANDLE * phFile) -{ - TMPQArchive * ha = (TMPQArchive *)hMpq; - DWORD dwErrCode = ERROR_SUCCESS; - - // Check valid parameters - if(!IsValidMpqHandle(hMpq)) - dwErrCode = ERROR_INVALID_HANDLE; - if(szArchivedName == NULL || *szArchivedName == 0) - dwErrCode = ERROR_INVALID_PARAMETER; - if(phFile == NULL) - dwErrCode = ERROR_INVALID_PARAMETER; - - // Don't allow to add file if the MPQ is open for read only - if(dwErrCode == ERROR_SUCCESS) - { - if(ha->dwFlags & MPQ_FLAG_READ_ONLY) - dwErrCode = ERROR_ACCESS_DENIED; - - // Don't allow to add a file under pseudo-file name - if(IsPseudoFileName(szArchivedName, NULL)) - dwErrCode = ERROR_INVALID_PARAMETER; - - // Don't allow to add any of the internal files - if(IsInternalMpqFileName(szArchivedName)) - dwErrCode = ERROR_INTERNAL_FILE; - } - - // Perform validity check of the MPQ flags - if(dwErrCode == ERROR_SUCCESS) - { - // Mask all unsupported flags out - dwFlags &= ha->dwValidFileFlags; - - // Check for valid flag combinations - if((dwFlags & (MPQ_FILE_IMPLODE | MPQ_FILE_COMPRESS)) == (MPQ_FILE_IMPLODE | MPQ_FILE_COMPRESS)) - dwErrCode = ERROR_INVALID_PARAMETER; - } - - // Initiate the add file operation - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = SFileAddFile_Init(ha, szArchivedName, FileTime, dwFileSize, lcFileLocale, dwFlags, (TMPQFile **)phFile); - - // Deal with the errors - if(dwErrCode != ERROR_SUCCESS) - SetLastError(dwErrCode); - return (dwErrCode == ERROR_SUCCESS); -} - -bool WINAPI SFileWriteFile( - HANDLE hFile, - const void * pvData, - DWORD dwSize, - DWORD dwCompression) -{ - TMPQFile * hf = (TMPQFile *)hFile; - DWORD dwErrCode = ERROR_SUCCESS; - - // Check the proper parameters - if(!IsValidFileHandle(hFile)) - dwErrCode = ERROR_INVALID_HANDLE; - if(hf->bIsWriteHandle == false) - dwErrCode = ERROR_INVALID_HANDLE; - - // Special checks for single unit files - if(dwErrCode == ERROR_SUCCESS && (hf->pFileEntry->dwFlags & MPQ_FILE_SINGLE_UNIT)) - { - // - // Note: Blizzard doesn't support single unit files - // that are stored as encrypted or imploded. We will allow them here, - // the calling application must ensure that such flag combination doesn't get here - // - -// if(dwFlags & MPQ_FILE_IMPLODE) -// dwErrCode = ERROR_INVALID_PARAMETER; -// -// if(dwFlags & MPQ_FILE_ENCRYPTED) -// dwErrCode = ERROR_INVALID_PARAMETER; - - // Lossy compression is not allowed on single unit files - if(dwCompression & MPQ_LOSSY_COMPRESSION_MASK) - dwErrCode = ERROR_INVALID_PARAMETER; - } - - - // Write the data to the file - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = SFileAddFile_Write(hf, pvData, dwSize, dwCompression); - - // Deal with errors - if(dwErrCode != ERROR_SUCCESS) - SetLastError(dwErrCode); - return (dwErrCode == ERROR_SUCCESS); -} - -bool WINAPI SFileFinishFile(HANDLE hFile) -{ - TMPQFile * hf = (TMPQFile *)hFile; - DWORD dwErrCode = ERROR_SUCCESS; - - // Check the proper parameters - if(!IsValidFileHandle(hFile)) - dwErrCode = ERROR_INVALID_HANDLE; - if(hf->bIsWriteHandle == false) - dwErrCode = ERROR_INVALID_HANDLE; - - // Finish the file - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = SFileAddFile_Finish(hf); - - // Deal with errors - if(dwErrCode != ERROR_SUCCESS) - SetLastError(dwErrCode); - return (dwErrCode == ERROR_SUCCESS); -} - -//----------------------------------------------------------------------------- -// Adds a file to the archive - -bool WINAPI SFileAddFileEx( - HANDLE hMpq, - const TCHAR * szFileName, - const char * szArchivedName, - DWORD dwFlags, - DWORD dwCompression, // Compression of the first sector - DWORD dwCompressionNext) // Compression of next sectors -{ - ULONGLONG FileSize = 0; - ULONGLONG FileTime = 0; - TFileStream * pStream = NULL; - HANDLE hMpqFile = NULL; - LPBYTE pbFileData = NULL; - DWORD dwBytesRemaining = 0; - DWORD dwBytesToRead; - DWORD dwSectorSize = 0x1000; - DWORD dwChannels = 0; - bool bIsAdpcmCompression = false; - bool bIsFirstSector = true; - DWORD dwErrCode = ERROR_SUCCESS; - - // Check parameters - if(hMpq == NULL || szFileName == NULL || *szFileName == 0) - { - SetLastError(ERROR_INVALID_PARAMETER); - return false; - } - - // Open added file - pStream = FileStream_OpenFile(szFileName, STREAM_FLAG_READ_ONLY | STREAM_PROVIDER_FLAT | BASE_PROVIDER_FILE); - if(pStream == NULL) - return false; - - // Files bigger than 4GB cannot be added to MPQ - FileStream_GetTime(pStream, &FileTime); - FileStream_GetSize(pStream, &FileSize); - if(FileSize >> 32) - dwErrCode = ERROR_DISK_FULL; - - // Allocate data buffer for reading from the source file - if(dwErrCode == ERROR_SUCCESS) - { - dwBytesRemaining = (DWORD)FileSize; - pbFileData = STORM_ALLOC(BYTE, dwSectorSize); - if(pbFileData == NULL) - dwErrCode = ERROR_NOT_ENOUGH_MEMORY; - } - - // Deal with various combination of compressions - if(dwErrCode == ERROR_SUCCESS) - { - // When the compression for next blocks is set to default, - // we will copy the compression for the first sector - if(dwCompressionNext == MPQ_COMPRESSION_NEXT_SAME) - dwCompressionNext = dwCompression; - - // If the caller wants ADPCM compression, we make sure - // that the first sector is not compressed with lossy compression - if(dwCompressionNext & (MPQ_COMPRESSION_ADPCM_MONO | MPQ_COMPRESSION_ADPCM_STEREO)) - { - // The compression of the first file sector must not be ADPCM - // in order not to corrupt the headers - if(dwCompression & (MPQ_COMPRESSION_ADPCM_MONO | MPQ_COMPRESSION_ADPCM_STEREO)) - dwCompression = MPQ_COMPRESSION_PKWARE; - - // Remove both flag mono and stereo flags. - // They will be re-added according to WAVE type - dwCompressionNext &= ~(MPQ_COMPRESSION_ADPCM_MONO | MPQ_COMPRESSION_ADPCM_STEREO); - bIsAdpcmCompression = true; - } - - // Initiate adding file to the MPQ - if(!SFileCreateFile(hMpq, szArchivedName, FileTime, (DWORD)FileSize, g_lcFileLocale, dwFlags, &hMpqFile)) - dwErrCode = GetLastError(); - } - - // Write the file data to the MPQ - while(dwErrCode == ERROR_SUCCESS && dwBytesRemaining != 0) - { - // Get the number of bytes remaining in the source file - dwBytesToRead = dwBytesRemaining; - if(dwBytesToRead > dwSectorSize) - dwBytesToRead = dwSectorSize; - - // Read data from the local file - if(!FileStream_Read(pStream, NULL, pbFileData, dwBytesToRead)) - { - dwErrCode = GetLastError(); - break; - } - - // If the file being added is a WAVE file, we check number of channels - if(bIsFirstSector && bIsAdpcmCompression) - { - // The file must really be a WAVE file with at least 16 bits per sample, - // otherwise the ADPCM compression will corrupt it - if(IsWaveFile_16BitsPerAdpcmSample(pbFileData, dwBytesToRead, &dwChannels)) - { - // Setup the compression of next sectors according to number of channels - dwCompressionNext |= (dwChannels == 1) ? MPQ_COMPRESSION_ADPCM_MONO : MPQ_COMPRESSION_ADPCM_STEREO; - } - else - { - // Setup the compression of next sectors to a lossless compression - dwCompressionNext = (dwCompression & MPQ_LOSSY_COMPRESSION_MASK) ? MPQ_COMPRESSION_PKWARE : dwCompression; - } - - bIsFirstSector = false; - } - - // Add the file sectors to the MPQ - if(!SFileWriteFile(hMpqFile, pbFileData, dwBytesToRead, dwCompression)) - { - dwErrCode = GetLastError(); - break; - } - - // Set the next data compression - dwBytesRemaining -= dwBytesToRead; - dwCompression = dwCompressionNext; - } - - // Finish the file writing - if(hMpqFile != NULL) - { - if(!SFileFinishFile(hMpqFile)) - dwErrCode = GetLastError(); - } - - // Cleanup and exit - if(pbFileData != NULL) - STORM_FREE(pbFileData); - if(pStream != NULL) - FileStream_Close(pStream); - if(dwErrCode != ERROR_SUCCESS) - SetLastError(dwErrCode); - return (dwErrCode == ERROR_SUCCESS); -} - -// Adds a data file into the archive -bool WINAPI SFileAddFile(HANDLE hMpq, const TCHAR * szFileName, const char * szArchivedName, DWORD dwFlags) -{ - return SFileAddFileEx(hMpq, - szFileName, - szArchivedName, - dwFlags, - DefaultDataCompression, - DefaultDataCompression); -} - -// Adds a WAVE file into the archive -bool WINAPI SFileAddWave(HANDLE hMpq, const TCHAR * szFileName, const char * szArchivedName, DWORD dwFlags, DWORD dwQuality) -{ - DWORD dwCompression = 0; - - // - // Note to wave compression level: - // The following conversion table applied: - // High quality: WaveCompressionLevel = -1 - // Medium quality: WaveCompressionLevel = 4 - // Low quality: WaveCompressionLevel = 2 - // - // Starcraft files are packed as Mono (0x41) on medium quality. - // Because this compression is not used anymore, our compression functions - // will default to WaveCompressionLevel = 4 when using ADPCM compression - // - - // Convert quality to data compression - switch(dwQuality) - { - case MPQ_WAVE_QUALITY_HIGH: -// WaveCompressionLevel = -1; - dwCompression = MPQ_COMPRESSION_PKWARE; - break; - - case MPQ_WAVE_QUALITY_MEDIUM: -// WaveCompressionLevel = 4; - dwCompression = MPQ_COMPRESSION_ADPCM_STEREO | MPQ_COMPRESSION_HUFFMANN; - break; - - case MPQ_WAVE_QUALITY_LOW: -// WaveCompressionLevel = 2; - dwCompression = MPQ_COMPRESSION_ADPCM_STEREO | MPQ_COMPRESSION_HUFFMANN; - break; - } - - return SFileAddFileEx(hMpq, - szFileName, - szArchivedName, - dwFlags, - MPQ_COMPRESSION_PKWARE, // First sector should be compressed as data - dwCompression); // Next sectors should be compressed as WAVE -} - -//----------------------------------------------------------------------------- -// bool SFileRemoveFile(HANDLE hMpq, char * szFileName) -// -// This function removes a file from the archive. -// - -bool WINAPI SFileRemoveFile(HANDLE hMpq, const char * szFileName, DWORD dwSearchScope) -{ - TMPQArchive * ha = IsValidMpqHandle(hMpq); - TMPQFile * hf = NULL; - DWORD dwErrCode = ERROR_SUCCESS; - - // Keep compiler happy - dwSearchScope = dwSearchScope; - - // Check the parameters - if(ha == NULL) - dwErrCode = ERROR_INVALID_HANDLE; - if(szFileName == NULL || *szFileName == 0) - dwErrCode = ERROR_INVALID_PARAMETER; - if(IsInternalMpqFileName(szFileName)) - dwErrCode = ERROR_INTERNAL_FILE; - - // Do not allow to remove files from read-only or patched MPQs - if(dwErrCode == ERROR_SUCCESS) - { - if((ha->dwFlags & MPQ_FLAG_READ_ONLY) || (ha->haPatch != NULL)) - dwErrCode = ERROR_ACCESS_DENIED; - } - - // If all checks have passed, we can delete the file from the MPQ - if(dwErrCode == ERROR_SUCCESS) - { - // Open the file from the MPQ - if(SFileOpenFileEx(hMpq, szFileName, SFILE_OPEN_BASE_FILE, (HANDLE *)&hf)) - { - // Delete the file entry - dwErrCode = DeleteFileEntry(ha, hf); - FreeFileHandle(hf); - } - else - dwErrCode = GetLastError(); - } - - // If the file has been deleted, we need to invalidate - // the internal files and recreate HET table - if(dwErrCode == ERROR_SUCCESS) - { - // Invalidate the entries for internal files - // After we are done with MPQ changes, we need to re-create them anyway - InvalidateInternalFiles(ha); - - // - // Don't rebuild HET table now; the file's flags indicate - // that it's been deleted, which is enough - // - } - - // Resolve error and exit - if(dwErrCode != ERROR_SUCCESS) - SetLastError(dwErrCode); - return (dwErrCode == ERROR_SUCCESS); -} - -// Renames the file within the archive. -bool WINAPI SFileRenameFile(HANDLE hMpq, const char * szFileName, const char * szNewFileName) -{ - TMPQArchive * ha = IsValidMpqHandle(hMpq); - TMPQFile * hf; - DWORD dwErrCode = ERROR_SUCCESS; - - // Test the valid parameters - if(ha == NULL) - dwErrCode = ERROR_INVALID_HANDLE; - if(szFileName == NULL || *szFileName == 0 || szNewFileName == NULL || *szNewFileName == 0) - dwErrCode = ERROR_INVALID_PARAMETER; - if(IsInternalMpqFileName(szFileName) || IsInternalMpqFileName(szNewFileName)) - dwErrCode = ERROR_INTERNAL_FILE; - - // Do not allow to rename files in MPQ open for read only - if(dwErrCode == ERROR_SUCCESS) - { - if(ha->dwFlags & MPQ_FLAG_READ_ONLY) - dwErrCode = ERROR_ACCESS_DENIED; - } - - // Open the new file. If exists, we don't allow rename operation - if(dwErrCode == ERROR_SUCCESS) - { - if(GetFileEntryLocale(ha, szNewFileName, g_lcFileLocale) != NULL) - dwErrCode = ERROR_ALREADY_EXISTS; - } - - // Open the file from the MPQ - if(dwErrCode == ERROR_SUCCESS) - { - // Attempt to open the file - if(SFileOpenFileEx(hMpq, szFileName, SFILE_OPEN_BASE_FILE, (HANDLE *)&hf)) - { - ULONGLONG RawDataOffs; - TFileEntry * pFileEntry = hf->pFileEntry; - - // Invalidate the entries for internal files - InvalidateInternalFiles(ha); - - // Rename the file entry in the table - dwErrCode = RenameFileEntry(ha, hf, szNewFileName); - - // If the file is encrypted, we have to re-crypt the file content - // with the new decryption key - if((dwErrCode == ERROR_SUCCESS) && (pFileEntry->dwFlags & MPQ_FILE_ENCRYPTED)) - { - // Recrypt the file data in the MPQ - dwErrCode = RecryptFileData(ha, hf, szFileName, szNewFileName); - - // Update the MD5 of the raw block - if(dwErrCode == ERROR_SUCCESS && ha->pHeader->dwRawChunkSize != 0) - { - RawDataOffs = ha->MpqPos + pFileEntry->ByteOffset; - WriteMpqDataMD5(ha->pStream, - RawDataOffs, - pFileEntry->dwCmpSize, - ha->pHeader->dwRawChunkSize); - } - } - - // Free the file handle - FreeFileHandle(hf); - } - else - { - dwErrCode = GetLastError(); - } - } - - // We also need to rebuild the HET table, if present - if(dwErrCode == ERROR_SUCCESS && ha->pHetTable != NULL) - dwErrCode = RebuildHetTable(ha); - - // Resolve error and exit - if(dwErrCode != ERROR_SUCCESS) - SetLastError(dwErrCode); - return (dwErrCode == ERROR_SUCCESS); -} - -//----------------------------------------------------------------------------- -// Sets default data compression for SFileAddFile - -bool WINAPI SFileSetDataCompression(DWORD DataCompression) -{ - unsigned int uValidMask = (MPQ_COMPRESSION_ZLIB | MPQ_COMPRESSION_PKWARE | MPQ_COMPRESSION_BZIP2 | MPQ_COMPRESSION_SPARSE); - - if((DataCompression & uValidMask) != DataCompression) - { - SetLastError(ERROR_INVALID_PARAMETER); - return false; - } - - DefaultDataCompression = DataCompression; - return true; -} - -//----------------------------------------------------------------------------- -// Changes locale ID of a file - -bool WINAPI SFileSetFileLocale(HANDLE hFile, LCID lcNewLocale) -{ - TMPQArchive * ha; - TFileEntry * pFileEntry; - TMPQFile * hf = IsValidFileHandle(hFile); - - // Invalid handle => do nothing - if(hf == NULL) - { - SetLastError(ERROR_INVALID_HANDLE); - return false; - } - - // Do not allow to rename files in MPQ open for read only - ha = hf->ha; - if(ha->dwFlags & MPQ_FLAG_READ_ONLY) - { - SetLastError(ERROR_ACCESS_DENIED); - return false; - } - - // Do not allow unnamed access - if(hf->pFileEntry->szFileName == NULL) - { - SetLastError(ERROR_CAN_NOT_COMPLETE); - return false; - } - - // Do not allow to change locale of any internal file - if(IsInternalMpqFileName(hf->pFileEntry->szFileName)) - { - SetLastError(ERROR_INTERNAL_FILE); - return false; - } - - // Do not allow changing file locales if there is no hash table - if(hf->pHashEntry == NULL) - { - SetLastError(ERROR_NOT_SUPPORTED); - return false; - } - - // We have to check if the file+locale is not already there - pFileEntry = GetFileEntryLocale(ha, hf->pFileEntry->szFileName, lcNewLocale, NULL); - if(pFileEntry != NULL) - { - SetLastError(ERROR_ALREADY_EXISTS); - return false; - } - - // Update the locale in the hash table entry - hf->pHashEntry->Locale = SFILE_LOCALE(lcNewLocale); - hf->pHashEntry->Platform = SFILE_PLATFORM(lcNewLocale); - hf->pHashEntry->Reserved = 0; - ha->dwFlags |= MPQ_FLAG_CHANGED; - return true; -} - -//----------------------------------------------------------------------------- -// Sets add file callback - -bool WINAPI SFileSetAddFileCallback(HANDLE hMpq, SFILE_ADDFILE_CALLBACK AddFileCB, void * pvUserData) -{ - TMPQArchive * ha = (TMPQArchive *) hMpq; - - if(!IsValidMpqHandle(hMpq)) - { - SetLastError(ERROR_INVALID_HANDLE); - return false; - } - - ha->pvAddFileUserData = pvUserData; - ha->pfnAddFileCB = AddFileCB; - return true; -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/SFileAttributes.cpp b/app/jni/src/libultraship/extern/StormLib/src/SFileAttributes.cpp deleted file mode 100644 index e22a09f..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/SFileAttributes.cpp +++ /dev/null @@ -1,570 +0,0 @@ -/*****************************************************************************/ -/* SAttrFile.cpp Copyright (c) Ladislav Zezula 2007 */ -/*---------------------------------------------------------------------------*/ -/* Description: */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 12.06.04 1.00 Lad The first version of SAttrFile.cpp */ -/*****************************************************************************/ - -#define __STORMLIB_SELF__ -#include "StormLib.h" -#include "StormCommon.h" - -//----------------------------------------------------------------------------- -// Local structures - -typedef struct _MPQ_ATTRIBUTES_HEADER -{ - DWORD dwVersion; // Version of the (attributes) file. Must be 100 (0x64) - DWORD dwFlags; // See MPQ_ATTRIBUTE_XXXX - - // Followed by an array of CRC32 - // Followed by an array of file times - // Followed by an array of MD5 - // Followed by an array of patch bits - - // Note: The MD5 in (attributes), if present, is a hash of the entire file. - // In case the file is an incremental patch, it contains MD5 of the file - // after being patched. - -} MPQ_ATTRIBUTES_HEADER, *PMPQ_ATTRIBUTES_HEADER; - -//----------------------------------------------------------------------------- -// Local functions - -static DWORD GetSizeOfAttributesFile(DWORD dwAttrFlags, DWORD dwBlockTableSize) -{ - DWORD cbAttrFile = sizeof(MPQ_ATTRIBUTES_HEADER); - - // Calculate size of the (attributes) file - if(dwAttrFlags & MPQ_ATTRIBUTE_CRC32) - cbAttrFile += dwBlockTableSize * sizeof(DWORD); - if(dwAttrFlags & MPQ_ATTRIBUTE_FILETIME) - cbAttrFile += dwBlockTableSize * sizeof(ULONGLONG); - if(dwAttrFlags & MPQ_ATTRIBUTE_MD5) - cbAttrFile += dwBlockTableSize * MD5_DIGEST_SIZE; - - // The bit array has been created without the last bit belonging to (attributes) - // When the number of files is a multiplier of 8 plus one, then the size of (attributes) - // if 1 byte less than expected. - // Example: wow-update-13164.MPQ: BlockTableSize = 0x62E1, but there's only 0xC5C bytes - if(dwAttrFlags & MPQ_ATTRIBUTE_PATCH_BIT) - cbAttrFile += (dwBlockTableSize + 6) / 8; - - return cbAttrFile; -} - -static DWORD CheckSizeOfAttributesFile(DWORD cbAttrFile, DWORD dwAttrFlags, DWORD dwBlockTableSize) -{ - DWORD cbHeaderSize = sizeof(MPQ_ATTRIBUTES_HEADER); - DWORD cbChecksumSize1 = 0; - DWORD cbChecksumSize2 = 0; - DWORD cbFileTimeSize1 = 0; - DWORD cbFileTimeSize2 = 0; - DWORD cbFileHashSize1 = 0; - DWORD cbFileHashSize2 = 0; - DWORD cbPatchBitSize1 = 0; - DWORD cbPatchBitSize2 = 0; - DWORD cbPatchBitSize3 = 0; - - // - // Various variants with the patch bit - // - // interface.MPQ.part from WoW build 10958 has - // the MPQ_ATTRIBUTE_PATCH_BIT set, but there's an array of DWORDs instead. - // The array is filled with zeros, so we don't know what it should contain - // - // Zenith.SC2MAP has the MPQ_ATTRIBUTE_PATCH_BIT set, but the bit array is missing - // - // Elimination Tournament 2.w3x's (attributes) have one entry less - // - // There may be two variants: Either the (attributes) file has full - // number of entries, or has one entry less - // - - // Get the expected size of CRC32 array - if(dwAttrFlags & MPQ_ATTRIBUTE_CRC32) - { - cbChecksumSize1 += dwBlockTableSize * sizeof(DWORD); - cbChecksumSize2 += cbChecksumSize1 - sizeof(DWORD); - } - - // Get the expected size of FILETIME array - if(dwAttrFlags & MPQ_ATTRIBUTE_FILETIME) - { - cbFileTimeSize1 += dwBlockTableSize * sizeof(ULONGLONG); - cbFileTimeSize2 += cbFileTimeSize1 - sizeof(ULONGLONG); - } - - // Get the expected size of MD5 array - if(dwAttrFlags & MPQ_ATTRIBUTE_MD5) - { - cbFileHashSize1 += dwBlockTableSize * MD5_DIGEST_SIZE; - cbFileHashSize2 += cbFileHashSize1 - MD5_DIGEST_SIZE; - } - - // Get the expected size of patch bit array - if(dwAttrFlags & MPQ_ATTRIBUTE_PATCH_BIT) - { - cbPatchBitSize1 = - cbPatchBitSize2 = ((dwBlockTableSize + 6) / 8); - cbPatchBitSize3 = dwBlockTableSize * sizeof(DWORD); - } - - // Check if the (attributes) file entry count is equal to our file table size - if(cbAttrFile == (cbHeaderSize + cbChecksumSize1 + cbFileTimeSize1 + cbFileHashSize1 + cbPatchBitSize1)) - return dwBlockTableSize; - - // Check if the (attributes) file entry count is equal to our file table size minus one - if(cbAttrFile == (cbHeaderSize + cbChecksumSize2 + cbFileTimeSize2 + cbFileHashSize2 + cbPatchBitSize2)) - return dwBlockTableSize - 1; - - // Zenith.SC2MAP has the MPQ_ATTRIBUTE_PATCH_BIT set, but the bit array is missing - if(cbAttrFile == (cbHeaderSize + cbChecksumSize1 + cbFileTimeSize1 + cbFileHashSize1)) - return dwBlockTableSize; - - // interface.MPQ.part (WoW build 10958) has the MPQ_ATTRIBUTE_PATCH_BIT set - // but there's an array of DWORDs (filled with zeros) instead of array of bits - if(cbAttrFile == (cbHeaderSize + cbChecksumSize1 + cbFileTimeSize1 + cbFileHashSize1 + cbPatchBitSize3)) - return dwBlockTableSize; - -#ifdef __STORMLIB_TEST__ - // Invalid size of the (attributes) file - // Note that many MPQs, especially Warcraft III maps have the size of (attributes) invalid. - // We only perform this check if this is the STORMLIB testprogram itself -// assert(false); -#endif - - return 0; -} - -static DWORD LoadAttributesFile(TMPQArchive * ha, LPBYTE pbAttrFile, DWORD cbAttrFile) -{ - LPBYTE pbAttrFileEnd = pbAttrFile + cbAttrFile; - LPBYTE pbAttrPtr = pbAttrFile; - DWORD dwAttributesEntries = 0; - DWORD i; - - // Load and verify the header - if((pbAttrPtr + sizeof(MPQ_ATTRIBUTES_HEADER)) <= pbAttrFileEnd) - { - PMPQ_ATTRIBUTES_HEADER pAttrHeader = (PMPQ_ATTRIBUTES_HEADER)pbAttrPtr; - - // Verify the header version - BSWAP_ARRAY32_UNSIGNED(pAttrHeader, sizeof(MPQ_ATTRIBUTES_HEADER)); - if(pAttrHeader->dwVersion != MPQ_ATTRIBUTES_V1) - return ERROR_BAD_FORMAT; - - // Verify the flags - if(pAttrHeader->dwFlags & ~MPQ_ATTRIBUTE_ALL) - return ERROR_BAD_FORMAT; - - // Verify whether file size of (attributes) is expected - dwAttributesEntries = CheckSizeOfAttributesFile(cbAttrFile, pAttrHeader->dwFlags, ha->pHeader->dwBlockTableSize); - if(dwAttributesEntries == 0) - return ERROR_BAD_FORMAT; - - ha->dwAttrFlags = pAttrHeader->dwFlags; - pbAttrPtr = (LPBYTE)(pAttrHeader + 1); - } - - // Load the CRC32 (if present) - if(ha->dwAttrFlags & MPQ_ATTRIBUTE_CRC32) - { - LPDWORD ArrayCRC32 = (LPDWORD)pbAttrPtr; - DWORD cbArraySize = dwAttributesEntries * sizeof(DWORD); - - // Verify if there's enough data - if((pbAttrPtr + cbArraySize) > pbAttrFileEnd) - return ERROR_FILE_CORRUPT; - - BSWAP_ARRAY32_UNSIGNED(ArrayCRC32, cbArraySize); - for(i = 0; i < dwAttributesEntries; i++) - ha->pFileTable[i].dwCrc32 = ArrayCRC32[i]; - pbAttrPtr += cbArraySize; - } - - // Load the FILETIME (if present) - if(ha->dwAttrFlags & MPQ_ATTRIBUTE_FILETIME) - { - ULONGLONG * ArrayFileTime = (ULONGLONG *)pbAttrPtr; - DWORD cbArraySize = dwAttributesEntries * sizeof(ULONGLONG); - - // Verify if there's enough data - if((pbAttrPtr + cbArraySize) > pbAttrFileEnd) - return ERROR_FILE_CORRUPT; - - BSWAP_ARRAY64_UNSIGNED(ArrayFileTime, cbArraySize); - for(i = 0; i < dwAttributesEntries; i++) - ha->pFileTable[i].FileTime = ArrayFileTime[i]; - pbAttrPtr += cbArraySize; - } - - // Load the MD5 (if present) - if(ha->dwAttrFlags & MPQ_ATTRIBUTE_MD5) - { - LPBYTE ArrayMd5 = pbAttrPtr; - DWORD cbArraySize = dwAttributesEntries * MD5_DIGEST_SIZE; - - // Verify if there's enough data - if((pbAttrPtr + cbArraySize) > pbAttrFileEnd) - return ERROR_FILE_CORRUPT; - - for(i = 0; i < dwAttributesEntries; i++) - { - memcpy(ha->pFileTable[i].md5, ArrayMd5, MD5_DIGEST_SIZE); - ArrayMd5 += MD5_DIGEST_SIZE; - } - pbAttrPtr += cbArraySize; - } - - // Read the patch bit for each file (if present) - if(ha->dwAttrFlags & MPQ_ATTRIBUTE_PATCH_BIT) - { - LPBYTE pbBitArray = pbAttrPtr; - DWORD cbArraySize = (dwAttributesEntries + 7) / 8; - DWORD dwByteIndex = 0; - DWORD dwBitMask = 0x80; - - // Verify if there's enough data - if((pbAttrPtr + cbArraySize) == pbAttrFileEnd) - { - for(i = 0; i < dwAttributesEntries; i++) - { - ha->pFileTable[i].dwFlags |= (pbBitArray[dwByteIndex] & dwBitMask) ? MPQ_FILE_PATCH_FILE : 0; - dwByteIndex += (dwBitMask & 0x01); - dwBitMask = (dwBitMask << 0x07) | (dwBitMask >> 0x01); - } - } - } - - return ERROR_SUCCESS; -} - -static LPBYTE CreateAttributesFile(TMPQArchive * ha, DWORD * pcbAttrFile) -{ - PMPQ_ATTRIBUTES_HEADER pAttrHeader; - TFileEntry * pFileTableEnd = ha->pFileTable + ha->pHeader->dwBlockTableSize; - TFileEntry * pFileEntry; - LPBYTE pbAttrFile; - LPBYTE pbAttrPtr; - size_t cbAttrFile; - - // Check if we need patch bits in the (attributes) file - for(pFileEntry = ha->pFileTable; pFileEntry < pFileTableEnd; pFileEntry++) - { - if(pFileEntry->dwFlags & MPQ_FILE_PATCH_FILE) - { - ha->dwAttrFlags |= MPQ_ATTRIBUTE_PATCH_BIT; - break; - } - } - - // Allocate the buffer for holding the entire (attributes) - // Allocate 1 byte more (See GetSizeOfAttributesFile for more info) - cbAttrFile = GetSizeOfAttributesFile(ha->dwAttrFlags, ha->pHeader->dwBlockTableSize); - pbAttrFile = pbAttrPtr = STORM_ALLOC(BYTE, cbAttrFile + 1); - if(pbAttrFile != NULL) - { - // Make sure it's all zeroed - memset(pbAttrFile, 0, cbAttrFile + 1); - - // Write the header of the (attributes) file - pAttrHeader = (PMPQ_ATTRIBUTES_HEADER)pbAttrPtr; - pAttrHeader->dwVersion = BSWAP_INT32_UNSIGNED(100); - pAttrHeader->dwFlags = BSWAP_INT32_UNSIGNED((ha->dwAttrFlags & MPQ_ATTRIBUTE_ALL)); - pbAttrPtr = (LPBYTE)(pAttrHeader + 1); - - // Write the array of CRC32, if present - if(ha->dwAttrFlags & MPQ_ATTRIBUTE_CRC32) - { - LPDWORD pArrayCRC32 = (LPDWORD)pbAttrPtr; - - // Copy from file table - for(pFileEntry = ha->pFileTable; pFileEntry < pFileTableEnd; pFileEntry++) - *pArrayCRC32++ = BSWAP_INT32_UNSIGNED(pFileEntry->dwCrc32); - - // Update pointer - pbAttrPtr = (LPBYTE)pArrayCRC32; - } - - // Write the array of file time - if(ha->dwAttrFlags & MPQ_ATTRIBUTE_FILETIME) - { - ULONGLONG * pArrayFileTime = (ULONGLONG *)pbAttrPtr; - - // Copy from file table - for(pFileEntry = ha->pFileTable; pFileEntry < pFileTableEnd; pFileEntry++) - *pArrayFileTime++ = BSWAP_INT64_UNSIGNED(pFileEntry->FileTime); - - // Update pointer - pbAttrPtr = (LPBYTE)pArrayFileTime; - } - - // Write the array of MD5s - if(ha->dwAttrFlags & MPQ_ATTRIBUTE_MD5) - { - LPBYTE pbArrayMD5 = pbAttrPtr; - - // Copy from file table - for(pFileEntry = ha->pFileTable; pFileEntry < pFileTableEnd; pFileEntry++) - { - memcpy(pbArrayMD5, pFileEntry->md5, MD5_DIGEST_SIZE); - pbArrayMD5 += MD5_DIGEST_SIZE; - } - - // Update pointer - pbAttrPtr = pbArrayMD5; - } - - // Write the array of patch bits - if(ha->dwAttrFlags & MPQ_ATTRIBUTE_PATCH_BIT) - { - LPBYTE pbBitArray = pbAttrPtr; - DWORD dwByteIndex = 0; - BYTE dwBitMask = 0x80; - - // Copy from file table - for(pFileEntry = ha->pFileTable; pFileEntry < pFileTableEnd; pFileEntry++) - { - // Set the bit, if needed - if(pFileEntry->dwFlags & MPQ_FILE_PATCH_FILE) - pbBitArray[dwByteIndex] |= dwBitMask; - - // Update bit index and bit mask - dwByteIndex += (dwBitMask & 0x01); - dwBitMask = (dwBitMask << 0x07) | (dwBitMask >> 0x01); - } - - // Move past the bit array - pbAttrPtr += (ha->pHeader->dwBlockTableSize + 6) / 8; - } - - // Now we expect that current position matches the estimated size - // Note that if there is 1 extra bit above the byte size, - // the table is actually 1 byte shorter in Blizzard MPQs. See GetSizeOfAttributesFile - assert((size_t)(pbAttrPtr - pbAttrFile) == cbAttrFile); - } - - // Give away the attributes file - if(pcbAttrFile != NULL) - *pcbAttrFile = (DWORD)cbAttrFile; - return pbAttrFile; -} - -//----------------------------------------------------------------------------- -// Public functions (internal use by StormLib) - -DWORD SAttrLoadAttributes(TMPQArchive * ha) -{ - HANDLE hFile = NULL; - LPBYTE pbAttrFile; - DWORD dwBytesRead; - DWORD cbAttrFile = 0; - DWORD dwErrCode = ERROR_FILE_CORRUPT; - - // File table must be initialized - assert(ha->pFileTable != NULL); - assert((ha->dwFlags & MPQ_FLAG_BLOCK_TABLE_CUT) == 0); - - // Don't load the attributes file from malformed Warcraft III maps - if(ha->dwFlags & MPQ_FLAG_MALFORMED) - return ERROR_FILE_CORRUPT; - - // Attempt to open the "(attributes)" file. - if(SFileOpenFileEx((HANDLE)ha, ATTRIBUTES_NAME, SFILE_OPEN_ANY_LOCALE, &hFile)) - { - // Retrieve and check size of the (attributes) file - cbAttrFile = SFileGetFileSize(hFile, NULL); - - // Integer overflow check - if((cbAttrFile + 1) > cbAttrFile) - { - // Size of the (attributes) might be 1 byte less than expected - // See GetSizeOfAttributesFile for more info - pbAttrFile = STORM_ALLOC(BYTE, cbAttrFile + 1); - if(pbAttrFile != NULL) - { - // Set the last byte to 0 in case the size should be 1 byte greater - pbAttrFile[cbAttrFile] = 0; - - // Load the entire file to memory - SFileReadFile(hFile, pbAttrFile, cbAttrFile, &dwBytesRead, NULL); - if(dwBytesRead == cbAttrFile) - dwErrCode = LoadAttributesFile(ha, pbAttrFile, cbAttrFile); - - // Free the buffer - STORM_FREE(pbAttrFile); - } - } - - // Close the attributes file - SFileCloseFile(hFile); - } - - return dwErrCode; -} - -// Saves the (attributes) to the MPQ -DWORD SAttrFileSaveToMpq(TMPQArchive * ha) -{ - TMPQFile * hf = NULL; - LPBYTE pbAttrFile; - DWORD cbAttrFile = 0; - DWORD dwErrCode = ERROR_SUCCESS; - - // Only save the attributes if we should do so - if(ha->dwFileFlags2 != 0) - { - // At this point, we expect to have at least one reserved entry in the file table - assert(ha->dwFlags & MPQ_FLAG_ATTRIBUTES_NEW); - assert(ha->dwReservedFiles > 0); - - // Create the raw data that is to be written to (attributes) - // Note: Blizzard MPQs have entries for (listfile) and (attributes), - // but they are filled empty - pbAttrFile = CreateAttributesFile(ha, &cbAttrFile); - if(pbAttrFile != NULL) - { - // Determine the real flags for (attributes) - if(ha->dwFileFlags2 == MPQ_FILE_DEFAULT_INTERNAL) - ha->dwFileFlags2 = GetDefaultSpecialFileFlags(cbAttrFile, ha->pHeader->wFormatVersion); - - // Create the attributes file in the MPQ - dwErrCode = SFileAddFile_Init(ha, ATTRIBUTES_NAME, - 0, - cbAttrFile, - LANG_NEUTRAL, - ha->dwFileFlags2 | MPQ_FILE_REPLACEEXISTING, - &hf); - - // Write the attributes file raw data to it - if(dwErrCode == ERROR_SUCCESS) - { - // Write the content of the attributes file to the MPQ - dwErrCode = SFileAddFile_Write(hf, pbAttrFile, cbAttrFile, MPQ_COMPRESSION_ZLIB); - SFileAddFile_Finish(hf); - } - - // Clear the number of reserved files - ha->dwFlags &= ~(MPQ_FLAG_ATTRIBUTES_NEW | MPQ_FLAG_ATTRIBUTES_NONE); - ha->dwReservedFiles--; - - // Free the attributes buffer - STORM_FREE(pbAttrFile); - } - else - { - // If the (attributes) file would be empty, its OK - dwErrCode = (cbAttrFile == 0) ? ERROR_SUCCESS : ERROR_NOT_ENOUGH_MEMORY; - } - } - - return dwErrCode; -} - -//----------------------------------------------------------------------------- -// Public functions - -DWORD WINAPI SFileGetAttributes(HANDLE hMpq) -{ - TMPQArchive * ha = (TMPQArchive *)hMpq; - - // Verify the parameters - if(!IsValidMpqHandle(hMpq)) - { - SetLastError(ERROR_INVALID_PARAMETER); - return SFILE_INVALID_ATTRIBUTES; - } - - return ha->dwAttrFlags; -} - -bool WINAPI SFileSetAttributes(HANDLE hMpq, DWORD dwFlags) -{ - TMPQArchive * ha = (TMPQArchive *)hMpq; - - // Verify the parameters - if(!IsValidMpqHandle(hMpq)) - { - SetLastError(ERROR_INVALID_PARAMETER); - return false; - } - - // Not allowed when the archive is read-only - if(ha->dwFlags & MPQ_FLAG_READ_ONLY) - { - SetLastError(ERROR_ACCESS_DENIED); - return false; - } - - // Set the attributes - InvalidateInternalFiles(ha); - ha->dwAttrFlags = (dwFlags & MPQ_ATTRIBUTE_ALL); - return true; -} - -bool WINAPI SFileUpdateFileAttributes(HANDLE hMpq, const char * szFileName) -{ - hash_state md5_state; - TMPQArchive * ha = (TMPQArchive *)hMpq; - TMPQFile * hf; - BYTE Buffer[0x1000]; - HANDLE hFile = NULL; - DWORD dwTotalBytes = 0; - DWORD dwBytesRead; - DWORD dwCrc32; - - // Verify the parameters - if(!IsValidMpqHandle(ha)) - { - SetLastError(ERROR_INVALID_PARAMETER); - return false; - } - - // Not allowed when the archive is read-only - if(ha->dwFlags & MPQ_FLAG_READ_ONLY) - { - SetLastError(ERROR_ACCESS_DENIED); - return false; - } - - // Attempt to open the file - if(!SFileOpenFileEx(hMpq, szFileName, SFILE_OPEN_BASE_FILE, &hFile)) - return false; - - // Get the file size - hf = (TMPQFile *)hFile; - dwTotalBytes = hf->pFileEntry->dwFileSize; - - // Initialize the CRC32 and MD5 contexts - md5_init(&md5_state); - dwCrc32 = crc32(0, Z_NULL, 0); - - // Go through entire file and calculate both CRC32 and MD5 - while(dwTotalBytes != 0) - { - // Read data from file - SFileReadFile(hFile, Buffer, sizeof(Buffer), &dwBytesRead, NULL); - if(dwBytesRead == 0) - break; - - // Update CRC32 and MD5 - dwCrc32 = crc32(dwCrc32, Buffer, dwBytesRead); - md5_process(&md5_state, Buffer, dwBytesRead); - - // Decrement the total size - dwTotalBytes -= dwBytesRead; - } - - // Update both CRC32 and MD5 - hf->pFileEntry->dwCrc32 = dwCrc32; - md5_done(&md5_state, hf->pFileEntry->md5); - - // Remember that we need to save the MPQ tables - InvalidateInternalFiles(ha); - SFileCloseFile(hFile); - return true; -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/SFileCompactArchive.cpp b/app/jni/src/libultraship/extern/StormLib/src/SFileCompactArchive.cpp deleted file mode 100644 index d4525b6..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/SFileCompactArchive.cpp +++ /dev/null @@ -1,654 +0,0 @@ -/*****************************************************************************/ -/* SFileCompactArchive.cpp Copyright (c) Ladislav Zezula 2003 */ -/*---------------------------------------------------------------------------*/ -/* Archive compacting function */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 14.04.03 1.00 Lad Splitted from SFileCreateArchiveEx.cpp */ -/* 19.11.03 1.01 Dan Big endian handling */ -/* 21.04.13 1.02 Dea Compact callback now part of TMPQArchive */ -/*****************************************************************************/ - -#define __STORMLIB_SELF__ -#include "StormLib.h" -#include "StormCommon.h" - -/*****************************************************************************/ -/* Local functions */ -/*****************************************************************************/ - -static DWORD CheckIfAllFilesKnown(TMPQArchive * ha) -{ - TFileEntry * pFileTableEnd = ha->pFileTable + ha->dwFileTableSize; - TFileEntry * pFileEntry; - DWORD dwBlockIndex = 0; - DWORD dwErrCode = ERROR_SUCCESS; - - // Verify the file table - if(dwErrCode == ERROR_SUCCESS) - { - for(pFileEntry = ha->pFileTable; pFileEntry < pFileTableEnd; pFileEntry++, dwBlockIndex++) - { - // If there is an existing entry in the file table, check its name - if(pFileEntry->dwFlags & MPQ_FILE_EXISTS) - { - // The name must be valid and must not be a pseudo-name - if(pFileEntry->szFileName == NULL || IsPseudoFileName(pFileEntry->szFileName, NULL)) - { - dwErrCode = ERROR_UNKNOWN_FILE_NAMES; - break; - } - } - } - } - - return dwErrCode; -} - -static DWORD CheckIfAllKeysKnown(TMPQArchive * ha, const TCHAR * szListFile, LPDWORD pFileKeys) -{ - TFileEntry * pFileTableEnd = ha->pFileTable + ha->dwFileTableSize; - TFileEntry * pFileEntry; - DWORD dwBlockIndex = 0; - DWORD dwErrCode = ERROR_SUCCESS; - - // Add the listfile to the MPQ - if(szListFile != NULL) - { - // Notify the user - if(ha->pfnCompactCB != NULL) - ha->pfnCompactCB(ha->pvCompactUserData, CCB_CHECKING_FILES, ha->CompactBytesProcessed, ha->CompactTotalBytes); - - dwErrCode = SFileAddListFile((HANDLE)ha, szListFile); - } - - // Verify the file table - if(dwErrCode == ERROR_SUCCESS) - { - for(pFileEntry = ha->pFileTable; pFileEntry < pFileTableEnd; pFileEntry++, dwBlockIndex++) - { - // If the file exists and it's encrypted - if(pFileEntry->dwFlags & MPQ_FILE_EXISTS) - { - // If we know the name, we decrypt the file key from the file name - if(pFileEntry->szFileName != NULL && !IsPseudoFileName(pFileEntry->szFileName, NULL)) - { - // Give the key to the caller - pFileKeys[dwBlockIndex] = DecryptFileKey(pFileEntry->szFileName, - pFileEntry->ByteOffset, - pFileEntry->dwFileSize, - pFileEntry->dwFlags); - continue; - } - - // We don't know the encryption key of this file, - // thus we cannot compact the file - dwErrCode = ERROR_UNKNOWN_FILE_NAMES; - break; - } - } - } - - return dwErrCode; -} - -static DWORD CopyNonMpqData( - TMPQArchive * ha, - TFileStream * pSrcStream, - TFileStream * pTrgStream, - ULONGLONG & ByteOffset, - ULONGLONG & ByteCount) -{ - ULONGLONG DataSize = ByteCount; - DWORD dwToRead; - char DataBuffer[0x1000]; - DWORD dwErrCode = ERROR_SUCCESS; - - // Copy the data - while(DataSize > 0) - { - // Get the proper size of data - dwToRead = sizeof(DataBuffer); - if(DataSize < dwToRead) - dwToRead = (DWORD)DataSize; - - // Read from the source stream - if(!FileStream_Read(pSrcStream, &ByteOffset, DataBuffer, dwToRead)) - { - dwErrCode = GetLastError(); - break; - } - - // Write to the target stream - if(!FileStream_Write(pTrgStream, NULL, DataBuffer, dwToRead)) - { - dwErrCode = GetLastError(); - break; - } - - // Update the progress - if(ha->pfnCompactCB != NULL) - { - ha->CompactBytesProcessed += dwToRead; - ha->pfnCompactCB(ha->pvCompactUserData, CCB_COPYING_NON_MPQ_DATA, ha->CompactBytesProcessed, ha->CompactTotalBytes); - } - - // Decrement the number of data to be copied - ByteOffset += dwToRead; - DataSize -= dwToRead; - } - - return dwErrCode; -} - -// Copies all file sectors into another archive. -static DWORD CopyMpqFileSectors( - TMPQArchive * ha, - TMPQFile * hf, - TFileStream * pNewStream, - ULONGLONG MpqFilePos) // MPQ file position in the new archive -{ - TFileEntry * pFileEntry = hf->pFileEntry; - ULONGLONG RawFilePos; // Used for calculating sector offset in the old MPQ archive - DWORD dwBytesToCopy = pFileEntry->dwCmpSize; - DWORD dwPatchSize = 0; // Size of patch header - DWORD dwFileKey1 = 0; // File key used for decryption - DWORD dwFileKey2 = 0; // File key used for encryption - DWORD dwCmpSize = 0; // Compressed file size, including patch header - DWORD dwErrCode = ERROR_SUCCESS; - - // Resolve decryption keys. Note that the file key given - // in the TMPQFile structure also includes the key adjustment - if(dwErrCode == ERROR_SUCCESS && (pFileEntry->dwFlags & MPQ_FILE_ENCRYPTED)) - { - dwFileKey2 = dwFileKey1 = hf->dwFileKey; - if(pFileEntry->dwFlags & MPQ_FILE_FIX_KEY) - { - dwFileKey2 = (dwFileKey1 ^ pFileEntry->dwFileSize) - (DWORD)pFileEntry->ByteOffset; - dwFileKey2 = (dwFileKey2 + (DWORD)MpqFilePos) ^ pFileEntry->dwFileSize; - } - } - - // If we have to save patch header, do it - if(dwErrCode == ERROR_SUCCESS && hf->pPatchInfo != NULL) - { - BSWAP_ARRAY32_UNSIGNED(hf->pPatchInfo, sizeof(DWORD) * 3); - if(!FileStream_Write(pNewStream, NULL, hf->pPatchInfo, hf->pPatchInfo->dwLength)) - dwErrCode = GetLastError(); - - // Save the size of the patch info - dwPatchSize = hf->pPatchInfo->dwLength; - } - - // If we have to save sector offset table, do it. - if(dwErrCode == ERROR_SUCCESS && hf->SectorOffsets != NULL) - { - DWORD * SectorOffsetsCopy = STORM_ALLOC(DWORD, hf->SectorOffsets[0] / sizeof(DWORD)); - DWORD dwSectorOffsLen = hf->SectorOffsets[0]; - - assert((pFileEntry->dwFlags & MPQ_FILE_SINGLE_UNIT) == 0); - assert(pFileEntry->dwFlags & MPQ_FILE_COMPRESS_MASK); - - if(SectorOffsetsCopy == NULL) - dwErrCode = ERROR_NOT_ENOUGH_MEMORY; - - // Encrypt the secondary sector offset table and write it to the target file - if(dwErrCode == ERROR_SUCCESS) - { - memcpy(SectorOffsetsCopy, hf->SectorOffsets, dwSectorOffsLen); - if(pFileEntry->dwFlags & MPQ_FILE_ENCRYPTED) - EncryptMpqBlock(SectorOffsetsCopy, dwSectorOffsLen, dwFileKey2 - 1); - - BSWAP_ARRAY32_UNSIGNED(SectorOffsetsCopy, dwSectorOffsLen); - if(!FileStream_Write(pNewStream, NULL, SectorOffsetsCopy, dwSectorOffsLen)) - dwErrCode = GetLastError(); - - dwBytesToCopy -= dwSectorOffsLen; - dwCmpSize += dwSectorOffsLen; - } - - // Update compact progress - if(ha->pfnCompactCB != NULL) - { - ha->CompactBytesProcessed += dwSectorOffsLen; - ha->pfnCompactCB(ha->pvCompactUserData, CCB_COMPACTING_FILES, ha->CompactBytesProcessed, ha->CompactTotalBytes); - } - - STORM_FREE(SectorOffsetsCopy); - } - - // Now we have to copy all file sectors. We do it without - // recompression, because recompression is not necessary in this case - if(dwErrCode == ERROR_SUCCESS) - { - for(DWORD dwSector = 0; dwSector < hf->dwSectorCount; dwSector++) - { - DWORD dwRawDataInSector = hf->dwSectorSize; - DWORD dwRawByteOffset = dwSector * hf->dwSectorSize; - - // Fix the raw data length if the file is compressed - if(hf->SectorOffsets != NULL) - { - dwRawDataInSector = hf->SectorOffsets[dwSector+1] - hf->SectorOffsets[dwSector]; - dwRawByteOffset = hf->SectorOffsets[dwSector]; - } - - // Last sector: If there is not enough bytes remaining in the file, cut the raw size - if(dwRawDataInSector > dwBytesToCopy) - dwRawDataInSector = dwBytesToCopy; - - // Calculate the raw file offset of the file sector - RawFilePos = CalculateRawSectorOffset(hf, dwRawByteOffset); - - // Read the file sector - if(!FileStream_Read(ha->pStream, &RawFilePos, hf->pbFileSector, dwRawDataInSector)) - { - dwErrCode = GetLastError(); - break; - } - - // If necessary, re-encrypt the sector - // Note: Recompression is not necessary here. Unlike encryption, - // the compression does not depend on the position of the file in MPQ. - if((pFileEntry->dwFlags & MPQ_FILE_ENCRYPTED) && dwFileKey1 != dwFileKey2) - { - BSWAP_ARRAY32_UNSIGNED(hf->pbFileSector, dwRawDataInSector); - DecryptMpqBlock(hf->pbFileSector, dwRawDataInSector, dwFileKey1 + dwSector); - EncryptMpqBlock(hf->pbFileSector, dwRawDataInSector, dwFileKey2 + dwSector); - BSWAP_ARRAY32_UNSIGNED(hf->pbFileSector, dwRawDataInSector); - } - - // Now write the sector back to the file - if(!FileStream_Write(pNewStream, NULL, hf->pbFileSector, dwRawDataInSector)) - { - dwErrCode = GetLastError(); - break; - } - - // Update compact progress - if(ha->pfnCompactCB != NULL) - { - ha->CompactBytesProcessed += dwRawDataInSector; - ha->pfnCompactCB(ha->pvCompactUserData, CCB_COMPACTING_FILES, ha->CompactBytesProcessed, ha->CompactTotalBytes); - } - - // Adjust byte counts - dwBytesToCopy -= dwRawDataInSector; - dwCmpSize += dwRawDataInSector; - } - } - - // Copy the sector CRCs, if any - // Sector CRCs are always compressed (not imploded) and unencrypted - if(dwErrCode == ERROR_SUCCESS && hf->SectorOffsets != NULL && hf->SectorChksums != NULL) - { - DWORD dwCrcLength; - - dwCrcLength = hf->SectorOffsets[hf->dwSectorCount + 1] - hf->SectorOffsets[hf->dwSectorCount]; - if(dwCrcLength != 0) - { - if(!FileStream_Read(ha->pStream, NULL, hf->SectorChksums, dwCrcLength)) - dwErrCode = GetLastError(); - - if(!FileStream_Write(pNewStream, NULL, hf->SectorChksums, dwCrcLength)) - dwErrCode = GetLastError(); - - // Update compact progress - if(ha->pfnCompactCB != NULL) - { - ha->CompactBytesProcessed += dwCrcLength; - ha->pfnCompactCB(ha->pvCompactUserData, CCB_COMPACTING_FILES, ha->CompactBytesProcessed, ha->CompactTotalBytes); - } - - // Size of the CRC block is also included in the compressed file size - dwBytesToCopy -= dwCrcLength; - dwCmpSize += dwCrcLength; - } - } - - // There might be extra data beyond sector checksum table - // Sometimes, these data are even part of sector offset table - // Examples: - // 2012 - WoW\15354\locale-enGB.MPQ:DBFilesClient\SpellLevels.dbc - // 2012 - WoW\15354\locale-enGB.MPQ:Interface\AddOns\Blizzard_AuctionUI\Blizzard_AuctionUI.xml - if(dwErrCode == ERROR_SUCCESS && dwBytesToCopy != 0) - { - LPBYTE pbExtraData; - - // Allocate space for the extra data - pbExtraData = STORM_ALLOC(BYTE, dwBytesToCopy); - if(pbExtraData != NULL) - { - if(!FileStream_Read(ha->pStream, NULL, pbExtraData, dwBytesToCopy)) - dwErrCode = GetLastError(); - - if(!FileStream_Write(pNewStream, NULL, pbExtraData, dwBytesToCopy)) - dwErrCode = GetLastError(); - - // Include these extra data in the compressed size - dwCmpSize += dwBytesToCopy; - STORM_FREE(pbExtraData); - } - else - dwErrCode = ERROR_NOT_ENOUGH_MEMORY; - } - - // Write the MD5's of the raw file data, if needed - if(dwErrCode == ERROR_SUCCESS && ha->pHeader->dwRawChunkSize != 0) - { - dwErrCode = WriteMpqDataMD5(pNewStream, - ha->MpqPos + MpqFilePos, - pFileEntry->dwCmpSize, - ha->pHeader->dwRawChunkSize); - } - - // Verify the number of bytes written - if(dwErrCode == ERROR_SUCCESS) - { - // At this point, number of bytes written should be exactly - // the same like the compressed file size. If it isn't, - // there's something wrong (an unknown archive version, MPQ malformation, ...) - // - // Note: Diablo savegames have very weird layout, and the file "hero" - // seems to have improper compressed size. Instead of real compressed size, - // the "dwCmpSize" member of the block table entry contains - // uncompressed size of file data + size of the sector table. - // If we compact the archive, Diablo will refuse to load the game - // - // Note: Some patch files in WOW patches don't count the patch header - // into compressed size - // - - if(!(dwCmpSize <= pFileEntry->dwCmpSize && pFileEntry->dwCmpSize <= dwCmpSize + dwPatchSize)) - { - dwErrCode = ERROR_FILE_CORRUPT; - assert(false); - } - } - - return dwErrCode; -} - -static DWORD CopyMpqFiles(TMPQArchive * ha, LPDWORD pFileKeys, TFileStream * pNewStream) -{ - TFileEntry * pFileTableEnd = ha->pFileTable + ha->dwFileTableSize; - TFileEntry * pFileEntry; - TMPQFile * hf = NULL; - ULONGLONG MpqFilePos; - DWORD dwErrCode = ERROR_SUCCESS; - - // Walk through all files and write them to the destination MPQ archive - for(pFileEntry = ha->pFileTable; pFileEntry < pFileTableEnd; pFileEntry++) - { - // Copy all the file sectors - // Only do that when the file has nonzero size - if((pFileEntry->dwFlags & MPQ_FILE_EXISTS)) - { - // Query the position where the destination file will be - FileStream_GetPos(pNewStream, &MpqFilePos); - MpqFilePos = MpqFilePos - ha->MpqPos; - - // Perform file copy ONLY if the file has nonzero size - if(pFileEntry->dwFileSize != 0) - { - // Allocate structure for the MPQ file - hf = CreateFileHandle(ha, pFileEntry); - if(hf == NULL) - return ERROR_NOT_ENOUGH_MEMORY; - - // Set the file decryption key - hf->dwFileKey = pFileKeys[pFileEntry - ha->pFileTable]; - - // If the file is a patch file, load the patch header - if(pFileEntry->dwFlags & MPQ_FILE_PATCH_FILE) - { - dwErrCode = AllocatePatchInfo(hf, true); - if(dwErrCode != ERROR_SUCCESS) - break; - } - - // Allocate buffers for file sector and sector offset table - dwErrCode = AllocateSectorBuffer(hf); - if(dwErrCode != ERROR_SUCCESS) - break; - - // Also allocate sector offset table and sector checksum table - dwErrCode = AllocateSectorOffsets(hf, true); - if(dwErrCode != ERROR_SUCCESS) - break; - - // Also load sector checksums, if any - if(pFileEntry->dwFlags & MPQ_FILE_SECTOR_CRC) - { - dwErrCode = AllocateSectorChecksums(hf, false); - if(dwErrCode != ERROR_SUCCESS) - break; - } - - // Copy all file sectors - dwErrCode = CopyMpqFileSectors(ha, hf, pNewStream, MpqFilePos); - if(dwErrCode != ERROR_SUCCESS) - break; - - // Free buffers. This also sets "hf" to NULL. - FreeFileHandle(hf); - } - - // Note: DO NOT update the compressed size in the file entry, no matter how bad it is. - pFileEntry->ByteOffset = MpqFilePos; - } - } - - // Cleanup and exit - if(hf != NULL) - FreeFileHandle(hf); - return dwErrCode; -} - -/*****************************************************************************/ -/* Public functions */ -/*****************************************************************************/ - -//----------------------------------------------------------------------------- -// Changing hash table size - -DWORD WINAPI SFileGetMaxFileCount(HANDLE hMpq) -{ - TMPQArchive * ha = (TMPQArchive *)hMpq; - - return ha->dwMaxFileCount; -} - -bool WINAPI SFileSetMaxFileCount(HANDLE hMpq, DWORD dwMaxFileCount) -{ - TMPQArchive * ha = (TMPQArchive *)hMpq; - DWORD dwNewHashTableSize = 0; - DWORD dwErrCode = ERROR_SUCCESS; - - // Test the valid parameters - if(!IsValidMpqHandle(hMpq)) - dwErrCode = ERROR_INVALID_HANDLE; - if(ha->dwFlags & MPQ_FLAG_READ_ONLY) - dwErrCode = ERROR_ACCESS_DENIED; - if(dwMaxFileCount < ha->dwFileTableSize) - dwErrCode = ERROR_DISK_FULL; - - // ALL file names must be known in order to be able to rebuild hash table - if(dwErrCode == ERROR_SUCCESS && ha->pHashTable != NULL) - { - dwErrCode = CheckIfAllFilesKnown(ha); - if(dwErrCode == ERROR_SUCCESS) - { - // Calculate the hash table size for the new file limit - dwNewHashTableSize = GetNearestPowerOfTwo(dwMaxFileCount); - - // Rebuild both file tables - dwErrCode = RebuildFileTable(ha, dwNewHashTableSize); - } - } - - // We always have to rebuild the (attributes) file due to file table change - if(dwErrCode == ERROR_SUCCESS) - { - // Invalidate (listfile) and (attributes) - InvalidateInternalFiles(ha); - - // Rebuild the HET table, if we have any - if(ha->pHetTable != NULL) - dwErrCode = RebuildHetTable(ha); - } - - // Return the error - if(dwErrCode != ERROR_SUCCESS) - SetLastError(dwErrCode); - return (dwErrCode == ERROR_SUCCESS); -} - -//----------------------------------------------------------------------------- -// Archive compacting - -bool WINAPI SFileSetCompactCallback(HANDLE hMpq, SFILE_COMPACT_CALLBACK pfnCompactCB, void * pvUserData) -{ - TMPQArchive * ha = (TMPQArchive *) hMpq; - - if (!IsValidMpqHandle(hMpq)) - { - SetLastError(ERROR_INVALID_HANDLE); - return false; - } - - ha->pfnCompactCB = pfnCompactCB; - ha->pvCompactUserData = pvUserData; - return true; -} - -bool WINAPI SFileCompactArchive(HANDLE hMpq, const TCHAR * szListFile, bool /* bReserved */) -{ - TFileStream * pTempStream = NULL; - TMPQArchive * ha = (TMPQArchive *)hMpq; - ULONGLONG ByteOffset; - ULONGLONG ByteCount; - LPDWORD pFileKeys = NULL; - TCHAR szTempFile[MAX_PATH+1] = _T(""); - DWORD dwErrCode = ERROR_SUCCESS; - - // Test the valid parameters - if(!IsValidMpqHandle(hMpq)) - dwErrCode = ERROR_INVALID_HANDLE; - if(ha->dwFlags & MPQ_FLAG_READ_ONLY) - dwErrCode = ERROR_ACCESS_DENIED; - - // If the MPQ is changed at this moment, we have to flush the archive - if(dwErrCode == ERROR_SUCCESS && (ha->dwFlags & MPQ_FLAG_CHANGED)) - { - SFileFlushArchive(hMpq); - } - - // Create the table with file keys - if(dwErrCode == ERROR_SUCCESS) - { - if((pFileKeys = STORM_ALLOC(DWORD, ha->dwFileTableSize)) != NULL) - memset(pFileKeys, 0, sizeof(DWORD) * ha->dwFileTableSize); - else - dwErrCode = ERROR_NOT_ENOUGH_MEMORY; - } - - // First of all, we have to check of we are able to decrypt all files. - // If not, sorry, but the archive cannot be compacted. - if(dwErrCode == ERROR_SUCCESS) - { - // Initialize the progress variables for compact callback - FileStream_GetSize(ha->pStream, &(ha->CompactTotalBytes)); - ha->CompactBytesProcessed = 0; - dwErrCode = CheckIfAllKeysKnown(ha, szListFile, pFileKeys); - } - - // Get the temporary file name and create it - if(dwErrCode == ERROR_SUCCESS) - { - // Create temporary file name. Prevent buffer overflow - StringCopy(szTempFile, _countof(szTempFile), FileStream_GetFileName(ha->pStream)); - StringCat(szTempFile, _countof(szTempFile), _T(".tmp")); - - // Create temporary file - pTempStream = FileStream_CreateFile(szTempFile, STREAM_PROVIDER_FLAT | BASE_PROVIDER_FILE); - if(pTempStream == NULL) - dwErrCode = GetLastError(); - } - - // Write the data before MPQ user data (if any) - if(dwErrCode == ERROR_SUCCESS && ha->UserDataPos != 0) - { - // Inform the application about the progress - if(ha->pfnCompactCB != NULL) - ha->pfnCompactCB(ha->pvCompactUserData, CCB_COPYING_NON_MPQ_DATA, ha->CompactBytesProcessed, ha->CompactTotalBytes); - - ByteOffset = 0; - ByteCount = ha->UserDataPos; - dwErrCode = CopyNonMpqData(ha, ha->pStream, pTempStream, ByteOffset, ByteCount); - } - - // Write the MPQ user data (if any) - if(dwErrCode == ERROR_SUCCESS && ha->MpqPos > ha->UserDataPos) - { - // At this point, we assume that the user data size is equal - // to pUserData->dwHeaderOffs. - // If this assumption doesn't work, then we have an unknown version of MPQ - ByteOffset = ha->UserDataPos; - ByteCount = ha->MpqPos - ha->UserDataPos; - - assert(ha->pUserData != NULL); - assert(ha->pUserData->dwHeaderOffs == ByteCount); - dwErrCode = CopyNonMpqData(ha, ha->pStream, pTempStream, ByteOffset, ByteCount); - } - - // Write the MPQ header - if(dwErrCode == ERROR_SUCCESS) - { - TMPQHeader SaveMpqHeader; - - // Write the MPQ header to the file - memcpy(&SaveMpqHeader, ha->pHeader, ha->pHeader->dwHeaderSize); - BSWAP_TMPQHEADER(&SaveMpqHeader, MPQ_FORMAT_VERSION_1); - BSWAP_TMPQHEADER(&SaveMpqHeader, MPQ_FORMAT_VERSION_2); - BSWAP_TMPQHEADER(&SaveMpqHeader, MPQ_FORMAT_VERSION_3); - BSWAP_TMPQHEADER(&SaveMpqHeader, MPQ_FORMAT_VERSION_4); - if(!FileStream_Write(pTempStream, NULL, &SaveMpqHeader, ha->pHeader->dwHeaderSize)) - dwErrCode = GetLastError(); - - // Update the progress - ha->CompactBytesProcessed += ha->pHeader->dwHeaderSize; - } - - // Now copy all files - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = CopyMpqFiles(ha, pFileKeys, pTempStream); - - // If succeeded, switch the streams - if(dwErrCode == ERROR_SUCCESS) - { - ha->dwFlags |= MPQ_FLAG_CHANGED; - if(FileStream_Replace(ha->pStream, pTempStream)) - pTempStream = NULL; - else - dwErrCode = ERROR_CAN_NOT_COMPLETE; - } - - // Final user notification - if(dwErrCode == ERROR_SUCCESS && ha->pfnCompactCB != NULL) - { - ha->CompactBytesProcessed += (ha->pHeader->dwHashTableSize * sizeof(TMPQHash)); - ha->CompactBytesProcessed += (ha->dwFileTableSize * sizeof(TMPQBlock)); - ha->pfnCompactCB(ha->pvCompactUserData, CCB_CLOSING_ARCHIVE, ha->CompactBytesProcessed, ha->CompactTotalBytes); - } - - // Cleanup and return - if(pTempStream != NULL) - FileStream_Close(pTempStream); - if(pFileKeys != NULL) - STORM_FREE(pFileKeys); - if(dwErrCode != ERROR_SUCCESS) - SetLastError(dwErrCode); - return (dwErrCode == ERROR_SUCCESS); -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/SFileCreateArchive.cpp b/app/jni/src/libultraship/extern/StormLib/src/SFileCreateArchive.cpp deleted file mode 100644 index 4facb47..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/SFileCreateArchive.cpp +++ /dev/null @@ -1,277 +0,0 @@ -/*****************************************************************************/ -/* SFileCreateArchive.cpp Copyright (c) Ladislav Zezula 2003 */ -/*---------------------------------------------------------------------------*/ -/* MPQ Editing functions */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 24.03.03 1.00 Lad Splitted from SFileOpenArchive.cpp */ -/* 08.06.10 1.00 Lad Renamed to SFileCreateArchive.cpp */ -/*****************************************************************************/ - -#define __STORMLIB_SELF__ -#include "StormLib.h" -#include "StormCommon.h" - -//----------------------------------------------------------------------------- -// Local variables - -static const DWORD MpqHeaderSizes[] = -{ - MPQ_HEADER_SIZE_V1, - MPQ_HEADER_SIZE_V2, - MPQ_HEADER_SIZE_V3, - MPQ_HEADER_SIZE_V4 -}; - -//----------------------------------------------------------------------------- -// Local functions - -static USHORT GetSectorSizeShift(DWORD dwSectorSize) -{ - USHORT wSectorSizeShift = 0; - - while(dwSectorSize > 0x200) - { - dwSectorSize >>= 1; - wSectorSizeShift++; - } - - return wSectorSizeShift; -} - -static DWORD WriteNakedMPQHeader(TMPQArchive * ha) -{ - TMPQHeader * pHeader = ha->pHeader; - TMPQHeader Header; - DWORD dwBytesToWrite = pHeader->dwHeaderSize; - DWORD dwErrCode = ERROR_SUCCESS; - - // Prepare the naked MPQ header - memset(&Header, 0, sizeof(TMPQHeader)); - Header.dwID = pHeader->dwID; - Header.dwHeaderSize = pHeader->dwHeaderSize; - Header.dwArchiveSize = pHeader->dwHeaderSize; - Header.wFormatVersion = pHeader->wFormatVersion; - Header.wSectorSize = pHeader->wSectorSize; - - // Write it to the file - BSWAP_TMPQHEADER(&Header, MPQ_FORMAT_VERSION_1); - BSWAP_TMPQHEADER(&Header, MPQ_FORMAT_VERSION_2); - BSWAP_TMPQHEADER(&Header, MPQ_FORMAT_VERSION_3); - BSWAP_TMPQHEADER(&Header, MPQ_FORMAT_VERSION_4); - if(!FileStream_Write(ha->pStream, &ha->MpqPos, &Header, dwBytesToWrite)) - dwErrCode = GetLastError(); - - return dwErrCode; -} - -//----------------------------------------------------------------------------- -// Creates a new MPQ archive. - -bool WINAPI SFileCreateArchive(const TCHAR * szMpqName, DWORD dwCreateFlags, DWORD dwMaxFileCount, HANDLE * phMpq) -{ - SFILE_CREATE_MPQ CreateInfo; - - // Fill the create structure - memset(&CreateInfo, 0, sizeof(SFILE_CREATE_MPQ)); - CreateInfo.cbSize = sizeof(SFILE_CREATE_MPQ); - CreateInfo.dwMpqVersion = (dwCreateFlags & MPQ_CREATE_ARCHIVE_VMASK) >> FLAGS_TO_FORMAT_SHIFT; - CreateInfo.dwStreamFlags = STREAM_PROVIDER_FLAT | BASE_PROVIDER_FILE; - CreateInfo.dwFileFlags1 = (dwCreateFlags & MPQ_CREATE_LISTFILE) ? MPQ_FILE_DEFAULT_INTERNAL : 0; - CreateInfo.dwFileFlags2 = (dwCreateFlags & MPQ_CREATE_ATTRIBUTES) ? MPQ_FILE_DEFAULT_INTERNAL : 0; - CreateInfo.dwFileFlags3 = (dwCreateFlags & MPQ_CREATE_SIGNATURE) ? MPQ_FILE_DEFAULT_INTERNAL : 0; - CreateInfo.dwAttrFlags = (dwCreateFlags & MPQ_CREATE_ATTRIBUTES) ? (MPQ_ATTRIBUTE_CRC32 | MPQ_ATTRIBUTE_FILETIME | MPQ_ATTRIBUTE_MD5) : 0; - CreateInfo.dwSectorSize = (CreateInfo.dwMpqVersion >= MPQ_FORMAT_VERSION_3) ? 0x4000 : 0x1000; - CreateInfo.dwRawChunkSize = (CreateInfo.dwMpqVersion >= MPQ_FORMAT_VERSION_4) ? 0x4000 : 0; - CreateInfo.dwMaxFileCount = dwMaxFileCount; - - // Set the proper attribute parts - if((CreateInfo.dwMpqVersion >= MPQ_FORMAT_VERSION_3) && (dwCreateFlags & MPQ_CREATE_ATTRIBUTES)) - CreateInfo.dwAttrFlags |= MPQ_ATTRIBUTE_PATCH_BIT; - - // Backward compatibility: SFileCreateArchive always used to add (listfile) - // We would break loads of applications if we change that - CreateInfo.dwFileFlags1 = MPQ_FILE_DEFAULT_INTERNAL; - - // Let the main function create the archive - return SFileCreateArchive2(szMpqName, &CreateInfo, phMpq); -} - -bool WINAPI SFileCreateArchive2(const TCHAR * szMpqName, PSFILE_CREATE_MPQ pCreateInfo, HANDLE * phMpq) -{ - TFileStream * pStream = NULL; // File stream - TMPQArchive * ha = NULL; // MPQ archive handle - TMPQHeader * pHeader; - ULONGLONG MpqPos = 0; // Position of MPQ header in the file - HANDLE hMpq = NULL; - DWORD dwBlockTableSize = 0; // Initial block table size - DWORD dwHashTableSize = 0; - DWORD dwReservedFiles = 0; // Number of reserved file entries - DWORD dwMpqFlags = 0; - DWORD dwErrCode = ERROR_SUCCESS; - - // Check the parameters, if they are valid - if(szMpqName == NULL || *szMpqName == 0 || pCreateInfo == NULL || phMpq == NULL) - { - SetLastError(ERROR_INVALID_PARAMETER); - return false; - } - - // Verify if all variables in SFILE_CREATE_MPQ are correct - if((pCreateInfo->cbSize == 0 || pCreateInfo->cbSize > sizeof(SFILE_CREATE_MPQ)) || - (pCreateInfo->dwMpqVersion > MPQ_FORMAT_VERSION_4) || - (pCreateInfo->pvUserData != NULL || pCreateInfo->cbUserData != 0) || - (pCreateInfo->dwAttrFlags & ~MPQ_ATTRIBUTE_ALL) || - (pCreateInfo->dwSectorSize & (pCreateInfo->dwSectorSize - 1)) || - (pCreateInfo->dwRawChunkSize & (pCreateInfo->dwRawChunkSize - 1))) - { - SetLastError(ERROR_INVALID_PARAMETER); - return false; - } - - // One time initialization of MPQ cryptography - InitializeMpqCryptography(); - - // We verify if the file already exists and if it's a MPQ archive. - // If yes, we won't allow to overwrite it. - if(SFileOpenArchive(szMpqName, 0, STREAM_PROVIDER_FLAT | BASE_PROVIDER_FILE | MPQ_OPEN_NO_ATTRIBUTES | MPQ_OPEN_NO_LISTFILE, &hMpq)) - { - SFileCloseArchive(hMpq); - SetLastError(ERROR_ALREADY_EXISTS); - return false; - } - - // - // At this point, we have to create the archive. - // - If the file exists, convert it to MPQ archive. - // - If the file doesn't exist, create new empty file - // - - pStream = FileStream_OpenFile(szMpqName, pCreateInfo->dwStreamFlags); - if(pStream == NULL) - { - pStream = FileStream_CreateFile(szMpqName, pCreateInfo->dwStreamFlags); - if(pStream == NULL) - return false; - } - - // Increment the maximum amount of files to have space for (listfile) - if(pCreateInfo->dwMaxFileCount && pCreateInfo->dwFileFlags1) - { - dwMpqFlags |= MPQ_FLAG_LISTFILE_NEW; - dwReservedFiles++; - } - - // Increment the maximum amount of files to have space for (attributes) - if(pCreateInfo->dwMaxFileCount && pCreateInfo->dwFileFlags2 && pCreateInfo->dwAttrFlags) - { - dwMpqFlags |= MPQ_FLAG_ATTRIBUTES_NEW; - dwReservedFiles++; - } - - // Increment the maximum amount of files to have space for (signature) - if(pCreateInfo->dwMaxFileCount && pCreateInfo->dwFileFlags3) - { - dwMpqFlags |= MPQ_FLAG_SIGNATURE_NEW; - dwReservedFiles++; - } - - // If file count is not zero, initialize the hash table size - dwHashTableSize = GetNearestPowerOfTwo(pCreateInfo->dwMaxFileCount + dwReservedFiles); - - // Retrieve the file size and round it up to 0x200 bytes - FileStream_GetSize(pStream, &MpqPos); - MpqPos = (MpqPos + 0x1FF) & (ULONGLONG)0xFFFFFFFFFFFFFE00ULL; - if(!FileStream_SetSize(pStream, MpqPos)) - dwErrCode = GetLastError(); - -#ifdef _DEBUG - // Debug code, used for testing StormLib -// dwBlockTableSize = dwHashTableSize * 2; -#endif - - // Create the archive handle - if(dwErrCode == ERROR_SUCCESS) - { - if((ha = STORM_ALLOC(TMPQArchive, 1)) == NULL) - dwErrCode = ERROR_NOT_ENOUGH_MEMORY; - } - - // Fill the MPQ archive handle structure - if(dwErrCode == ERROR_SUCCESS) - { - memset(ha, 0, sizeof(TMPQArchive)); - ha->pfnHashString = HashStringSlash; - ha->pStream = pStream; - ha->dwSectorSize = pCreateInfo->dwSectorSize; - ha->UserDataPos = MpqPos; - ha->MpqPos = MpqPos; - ha->pHeader = pHeader = (TMPQHeader *)ha->HeaderData; - ha->dwMaxFileCount = dwHashTableSize; - ha->dwFileTableSize = 0; - ha->dwReservedFiles = dwReservedFiles; - ha->dwValidFileFlags = (pCreateInfo->dwMpqVersion > 1) ? MPQ_FILE_VALID_FLAGS : MPQ_FILE_VALID_FLAGS_W3X; - ha->dwFileFlags1 = pCreateInfo->dwFileFlags1; - ha->dwFileFlags2 = pCreateInfo->dwFileFlags2; - ha->dwFileFlags3 = pCreateInfo->dwFileFlags3 ? MPQ_FILE_EXISTS : 0; - ha->dwAttrFlags = pCreateInfo->dwAttrFlags; - ha->dwFlags = dwMpqFlags | MPQ_FLAG_CHANGED; - ha->useFreeSpaceOptimization = true; - ha->lastFreeSpaceEntry = nullptr; - pStream = NULL; - - // Fill the MPQ header - memset(pHeader, 0, sizeof(ha->HeaderData)); - pHeader->dwID = g_dwMpqSignature; - pHeader->dwHeaderSize = MpqHeaderSizes[pCreateInfo->dwMpqVersion]; - pHeader->dwArchiveSize = pHeader->dwHeaderSize + dwHashTableSize * sizeof(TMPQHash); - pHeader->wFormatVersion = (USHORT)pCreateInfo->dwMpqVersion; - pHeader->wSectorSize = GetSectorSizeShift(ha->dwSectorSize); - pHeader->dwHashTablePos = pHeader->dwHeaderSize; - pHeader->dwHashTableSize = dwHashTableSize; - pHeader->dwBlockTablePos = pHeader->dwHashTablePos + dwHashTableSize * sizeof(TMPQHash); - pHeader->dwBlockTableSize = dwBlockTableSize; - - // For MPQs version 4 and higher, we set the size of raw data block - // for calculating MD5 - if(pCreateInfo->dwMpqVersion >= MPQ_FORMAT_VERSION_4) - pHeader->dwRawChunkSize = pCreateInfo->dwRawChunkSize; - - // Write the naked MPQ header - dwErrCode = WriteNakedMPQHeader(ha); - } - - // Create initial HET table, if the caller required an MPQ format 3.0 or newer - if(dwErrCode == ERROR_SUCCESS && pCreateInfo->dwMpqVersion >= MPQ_FORMAT_VERSION_3 && pCreateInfo->dwMaxFileCount != 0) - { - ha->pHetTable = CreateHetTable(ha->dwFileTableSize, 0, 0x40, NULL); - if(ha->pHetTable == NULL) - dwErrCode = ERROR_NOT_ENOUGH_MEMORY; - } - - // Create initial hash table - if(dwErrCode == ERROR_SUCCESS && dwHashTableSize != 0) - { - dwErrCode = CreateHashTable(ha, dwHashTableSize); - } - - // Create initial file table - if(dwErrCode == ERROR_SUCCESS && ha->dwMaxFileCount != 0) - { - dwErrCode = CreateFileTable(ha, ha->dwMaxFileCount); - } - - // Cleanup : If an error, delete all buffers and return - if(dwErrCode != ERROR_SUCCESS) - { - FileStream_Close(pStream); - FreeArchiveHandle(ha); - SetLastError(dwErrCode); - ha = NULL; - } - - // Return the values - *phMpq = (HANDLE)ha; - return (dwErrCode == ERROR_SUCCESS); -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/SFileExtractFile.cpp b/app/jni/src/libultraship/extern/StormLib/src/SFileExtractFile.cpp deleted file mode 100644 index 6b3b767..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/SFileExtractFile.cpp +++ /dev/null @@ -1,64 +0,0 @@ -/*****************************************************************************/ -/* SFileExtractFile.cpp Copyright (c) Ladislav Zezula 2003 */ -/*---------------------------------------------------------------------------*/ -/* Simple extracting utility */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 20.06.03 1.00 Lad The first version of SFileExtractFile.cpp */ -/*****************************************************************************/ - -#define __STORMLIB_SELF__ -#include "StormLib.h" -#include "StormCommon.h" - -bool WINAPI SFileExtractFile(HANDLE hMpq, const char * szToExtract, const TCHAR * szExtracted, DWORD dwSearchScope) -{ - TFileStream * pLocalFile = NULL; - HANDLE hMpqFile = NULL; - DWORD dwErrCode = ERROR_SUCCESS; - - // Open the MPQ file - if(dwErrCode == ERROR_SUCCESS) - { - if(!SFileOpenFileEx(hMpq, szToExtract, dwSearchScope, &hMpqFile)) - dwErrCode = GetLastError(); - } - - // Create the local file - if(dwErrCode == ERROR_SUCCESS) - { - pLocalFile = FileStream_CreateFile(szExtracted, 0); - if(pLocalFile == NULL) - dwErrCode = GetLastError(); - } - - // Copy the file's content - while(dwErrCode == ERROR_SUCCESS) - { - char szBuffer[0x1000]; - DWORD dwTransferred = 0; - - // dwTransferred is only set to nonzero if something has been read. - // dwErrCode can be ERROR_SUCCESS or ERROR_HANDLE_EOF - if(!SFileReadFile(hMpqFile, szBuffer, sizeof(szBuffer), &dwTransferred, NULL)) - dwErrCode = GetLastError(); - if(dwErrCode == ERROR_HANDLE_EOF) - dwErrCode = ERROR_SUCCESS; - if(dwTransferred == 0) - break; - - // If something has been actually read, write it - if(!FileStream_Write(pLocalFile, NULL, szBuffer, dwTransferred)) - dwErrCode = GetLastError(); - } - - // Close the files - if(hMpqFile != NULL) - SFileCloseFile(hMpqFile); - if(pLocalFile != NULL) - FileStream_Close(pLocalFile); - if(dwErrCode != ERROR_SUCCESS) - SetLastError(dwErrCode); - return (dwErrCode == ERROR_SUCCESS); -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/SFileFindFile.cpp b/app/jni/src/libultraship/extern/StormLib/src/SFileFindFile.cpp deleted file mode 100644 index 4de1022..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/SFileFindFile.cpp +++ /dev/null @@ -1,481 +0,0 @@ -/*****************************************************************************/ -/* SFileFindFile.cpp Copyright (c) Ladislav Zezula 2003 */ -/*---------------------------------------------------------------------------*/ -/* A module for file searching within MPQs */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 25.03.03 1.00 Lad The first version of SFileFindFile.cpp */ -/*****************************************************************************/ - -#define __STORMLIB_SELF__ -#include "StormLib.h" -#include "StormCommon.h" - -//----------------------------------------------------------------------------- -// Private structure used for file search (search handle) - -// Used by searching in MPQ archives -struct TMPQSearch -{ - TMPQArchive * ha; // Handle to MPQ, where the search runs - TFileEntry ** pSearchTable; // Table for files that have been already found - DWORD dwSearchTableItems; // Number of items in the search table - DWORD dwNextIndex; // Next file index to be checked - DWORD dwFlagMask; // For checking flag mask - char szSearchMask[1]; // Search mask (variable length) -}; - -//----------------------------------------------------------------------------- -// Local functions - -static TMPQSearch * IsValidSearchHandle(HANDLE hFind) -{ - TMPQSearch * hs = (TMPQSearch *)hFind; - - if(hs != NULL && IsValidMpqHandle(hs->ha)) - return hs; - - return NULL; -} - -bool SFileCheckWildCard(const char * szString, const char * szWildCard) -{ - const char * szWildCardPtr; - - for(;;) - { - // If there is '?' in the wildcard, we skip one char - while(szWildCard[0] == '?') - { - if(szString[0] == 0) - return false; - - szWildCard++; - szString++; - } - - // Handle '*' - szWildCardPtr = szWildCard; - if(szWildCardPtr[0] != 0) - { - if(szWildCardPtr[0] == '*') - { - while(szWildCardPtr[0] == '*') - szWildCardPtr++; - - if(szWildCardPtr[0] == 0) - return true; - - if(AsciiToUpperTable[szWildCardPtr[0]] == AsciiToUpperTable[szString[0]]) - { - if(SFileCheckWildCard(szString, szWildCardPtr)) - return true; - } - } - else - { - if(AsciiToUpperTable[szWildCardPtr[0]] != AsciiToUpperTable[szString[0]]) - return false; - - szWildCard = szWildCardPtr + 1; - } - - if(szString[0] == 0) - return false; - szString++; - } - else - { - return (szString[0] == 0) ? true : false; - } - } -} - -static DWORD GetSearchTableItems(TMPQArchive * ha) -{ - DWORD dwMergeItems = 0; - - // Loop over all patches - while(ha != NULL) - { - // Append the number of files - dwMergeItems += (ha->pHetTable != NULL) ? ha->pHetTable->dwEntryCount - : ha->pHeader->dwBlockTableSize; - // Move to the patched archive - ha = ha->haPatch; - } - - // Return the double size of number of items - return (dwMergeItems | 1); -} - -static bool FileWasFoundBefore( - TMPQArchive * ha, - TMPQSearch * hs, - TFileEntry * pFileEntry) -{ - TFileEntry * pEntry; - char * szRealFileName = pFileEntry->szFileName; - DWORD dwStartIndex; - DWORD dwNameHash; - DWORD dwIndex; - - if(hs->pSearchTable != NULL && szRealFileName != NULL) - { - // If we are in patch MPQ, we check if patch prefix matches - // and then trim the patch prefix - if(ha->pPatchPrefix != NULL) - { - // If the patch prefix doesn't fit, we pretend that the file - // was there before and it will be skipped - if(_strnicmp(szRealFileName, ha->pPatchPrefix->szPatchPrefix, ha->pPatchPrefix->nLength)) - return true; - - szRealFileName += ha->pPatchPrefix->nLength; - } - - // Calculate the hash to the table - dwNameHash = ha->pfnHashString(szRealFileName, MPQ_HASH_NAME_A); - dwStartIndex = dwIndex = (dwNameHash % hs->dwSearchTableItems); - - // The file might have been found before - // only if this is not the first MPQ being searched - if(ha->haBase != NULL) - { - // Enumerate all entries in the search table - for(;;) - { - // Get the file entry at that position - pEntry = hs->pSearchTable[dwIndex]; - if(pEntry == NULL) - break; - - if(pEntry->szFileName != NULL) - { - // Does the name match? - if(!_stricmp(pEntry->szFileName, szRealFileName)) - return true; - } - - // Move to the next entry - dwIndex = (dwIndex + 1) % hs->dwSearchTableItems; - if(dwIndex == dwStartIndex) - break; - } - } - - // Put the entry to the table for later use - hs->pSearchTable[dwIndex] = pFileEntry; - } - return false; -} - -static TFileEntry * FindPatchEntry(TMPQArchive * ha, TFileEntry * pFileEntry) -{ - TFileEntry * pPatchEntry = pFileEntry; - TFileEntry * pTempEntry; - char szFileName[MAX_PATH+1]; - - // Can't find patch entry for a file that doesn't have name - if(pFileEntry->szFileName != NULL && pFileEntry->szFileName[0] != 0) - { - // Go while there are patches - while(ha->haPatch != NULL) - { - // Move to the patch archive - ha = ha->haPatch; - szFileName[0] = 0; - - // Prepare the prefix for the file name - if(ha->pPatchPrefix && ha->pPatchPrefix->nLength) - StringCopy(szFileName, _countof(szFileName), ha->pPatchPrefix->szPatchPrefix); - StringCat(szFileName, _countof(szFileName), pFileEntry->szFileName); - - // Try to find the file there - pTempEntry = GetFileEntryExact(ha, szFileName, 0, NULL); - if(pTempEntry != NULL) - pPatchEntry = pTempEntry; - } - } - - // Return the found patch entry - return pPatchEntry; -} - -static bool DoMPQSearch_FileEntry( - TMPQSearch * hs, - SFILE_FIND_DATA * lpFindFileData, - TMPQArchive * ha, - TMPQHash * pHashEntry, - TFileEntry * pFileEntry) -{ - TFileEntry * pPatchEntry; - HANDLE hFile = NULL; - const char * szFileName; - size_t nPrefixLength = (ha->pPatchPrefix != NULL) ? ha->pPatchPrefix->nLength : 0; - DWORD dwBlockIndex; - char szNameBuff[MAX_PATH]; - - // Is it a file but not a patch file? - if((pFileEntry->dwFlags & hs->dwFlagMask) == MPQ_FILE_EXISTS) - { - // Ignore fake files which are not compressed but have size higher than the archive - if((pFileEntry->dwFlags & MPQ_FILE_COMPRESS_MASK) == 0 && (pFileEntry->dwFileSize > ha->FileSize)) - return false; - - // Now we have to check if this file was not enumerated before - if(!FileWasFoundBefore(ha, hs, pFileEntry)) - { -// if(pFileEntry != NULL && !_stricmp(pFileEntry->szFileName, "TriggerLibs\\NativeLib.galaxy")) -// DebugBreak(); - - // Find a patch to this file - // Note: This either succeeds or returns pFileEntry - pPatchEntry = FindPatchEntry(ha, pFileEntry); - - // Prepare the block index - dwBlockIndex = (DWORD)(pFileEntry - ha->pFileTable); - - // Get the file name. If it's not known, we will create pseudo-name - szFileName = pFileEntry->szFileName; - if(szFileName == NULL) - { - // Open the file by its pseudo-name. - StringCreatePseudoFileName(szNameBuff, _countof(szNameBuff), dwBlockIndex, "xxx"); - if(SFileOpenFileEx((HANDLE)hs->ha, szNameBuff, SFILE_OPEN_BASE_FILE, &hFile)) - { - SFileGetFileName(hFile, szNameBuff); - szFileName = szNameBuff; - SFileCloseFile(hFile); - } - } - - // If the file name is still NULL, we cannot include the file to search results - if(szFileName != NULL) - { - // Check the file name against the wildcard - if(SFileCheckWildCard(szFileName + nPrefixLength, hs->szSearchMask)) - { - // Fill the found entry. hash entry and block index are taken from the base MPQ - lpFindFileData->dwHashIndex = HASH_ENTRY_FREE; - lpFindFileData->dwBlockIndex = dwBlockIndex; - lpFindFileData->dwFileSize = pPatchEntry->dwFileSize; - lpFindFileData->dwFileFlags = pPatchEntry->dwFlags; - lpFindFileData->dwCompSize = pPatchEntry->dwCmpSize; - lpFindFileData->lcLocale = 0; // pPatchEntry->lcFileLocale; - - // Fill the filetime - lpFindFileData->dwFileTimeHi = (DWORD)(pPatchEntry->FileTime >> 32); - lpFindFileData->dwFileTimeLo = (DWORD)(pPatchEntry->FileTime); - - // Fill-in the entries from hash table entry, if given - if(pHashEntry != NULL) - { - lpFindFileData->dwHashIndex = (DWORD)(pHashEntry - ha->pHashTable); - lpFindFileData->lcLocale = SFILE_MAKE_LCID(pHashEntry->Locale, pHashEntry->Platform); - } - - // Fill the file name and plain file name - StringCopy(lpFindFileData->cFileName, _countof(lpFindFileData->cFileName), szFileName + nPrefixLength); - lpFindFileData->szPlainName = (char *)GetPlainFileName(lpFindFileData->cFileName); - return true; - } - } - } - } - - // Either not a valid item or was found before - return false; -} - -static DWORD DoMPQSearch_HashTable(TMPQSearch * hs, SFILE_FIND_DATA * lpFindFileData, TMPQArchive * ha) -{ - TMPQHash * pHashTableEnd = ha->pHashTable + ha->pHeader->dwHashTableSize; - TMPQHash * pHash; - - // Parse the file table - for(pHash = ha->pHashTable + hs->dwNextIndex; pHash < pHashTableEnd; pHash++) - { - // Increment the next index for subsequent search - hs->dwNextIndex++; - - // Does this hash table entry point to a proper block table entry? - if(IsValidHashEntry(ha, pHash)) - { - // Check if this file entry should be included in the search result - if(DoMPQSearch_FileEntry(hs, lpFindFileData, ha, pHash, ha->pFileTable + MPQ_BLOCK_INDEX(pHash))) - return ERROR_SUCCESS; - } - } - - // No more files - return ERROR_NO_MORE_FILES; -} - -static DWORD DoMPQSearch_FileTable(TMPQSearch * hs, SFILE_FIND_DATA * lpFindFileData, TMPQArchive * ha) -{ - TFileEntry * pFileTableEnd = ha->pFileTable + ha->dwFileTableSize; - TFileEntry * pFileEntry; - - // Parse the file table - for(pFileEntry = ha->pFileTable + hs->dwNextIndex; pFileEntry < pFileTableEnd; pFileEntry++) - { - // Increment the next index for subsequent search - hs->dwNextIndex++; - - // Check if this file entry should be included in the search result - if(DoMPQSearch_FileEntry(hs, lpFindFileData, ha, NULL, pFileEntry)) - return ERROR_SUCCESS; - } - - // No more files - return ERROR_NO_MORE_FILES; -} - -// Performs one MPQ search -static DWORD DoMPQSearch(TMPQSearch * hs, SFILE_FIND_DATA * lpFindFileData) -{ - TMPQArchive * ha = hs->ha; - DWORD dwErrCode; - - // Start searching with base MPQ - while(ha != NULL) - { - // If the archive has hash table, we need to use hash table - // in order to catch hash table index and file locale. - // Note: If multiple hash table entries, point to the same block entry, - // we need, to report them all - dwErrCode = (ha->pHashTable != NULL) ? DoMPQSearch_HashTable(hs, lpFindFileData, ha) - : DoMPQSearch_FileTable(hs, lpFindFileData, ha); - if(dwErrCode == ERROR_SUCCESS) - return dwErrCode; - - // If there is no more patches in the chain, stop it. - // This also keeps hs->ha non-NULL, which is required - // for freeing the handle later - if(ha->haPatch == NULL) - break; - - // Move to the next patch in the patch chain - hs->ha = ha = ha->haPatch; - hs->dwNextIndex = 0; - } - - // No more files found, return error - return ERROR_NO_MORE_FILES; -} - -static void FreeMPQSearch(TMPQSearch *& hs) -{ - if(hs != NULL) - { - if(hs->pSearchTable != NULL) - STORM_FREE(hs->pSearchTable); - STORM_FREE(hs); - hs = NULL; - } -} - -//----------------------------------------------------------------------------- -// Public functions - -HANDLE WINAPI SFileFindFirstFile(HANDLE hMpq, const char * szMask, SFILE_FIND_DATA * lpFindFileData, const TCHAR * szListFile) -{ - TMPQArchive * ha = (TMPQArchive *)hMpq; - TMPQSearch * hs = NULL; - size_t nSize = 0; - DWORD dwErrCode = ERROR_SUCCESS; - - // Check for the valid parameters - if(!IsValidMpqHandle(hMpq)) - dwErrCode = ERROR_INVALID_HANDLE; - if(szMask == NULL || lpFindFileData == NULL) - dwErrCode = ERROR_INVALID_PARAMETER; - - // Include the listfile into the MPQ's internal listfile - // Note that if the listfile name is NULL, do nothing because the - // internal listfile is always included. - if(dwErrCode == ERROR_SUCCESS && szListFile != NULL && *szListFile != 0) - dwErrCode = SFileAddListFile((HANDLE)ha, szListFile); - - // Allocate the structure for MPQ search - if(dwErrCode == ERROR_SUCCESS) - { - nSize = sizeof(TMPQSearch) + strlen(szMask) + 1; - if((hs = (TMPQSearch *)STORM_ALLOC(char, nSize)) == NULL) - dwErrCode = ERROR_NOT_ENOUGH_MEMORY; - } - - // Perform the first search - if(dwErrCode == ERROR_SUCCESS) - { - memset(hs, 0, sizeof(TMPQSearch)); - strcpy(hs->szSearchMask, szMask); - hs->dwFlagMask = MPQ_FILE_EXISTS; - hs->ha = ha; - - // If the archive is patched archive, we have to create a merge table - // to prevent files being repeated - if(ha->haPatch != NULL) - { - hs->dwSearchTableItems = GetSearchTableItems(ha); - hs->pSearchTable = STORM_ALLOC(TFileEntry *, hs->dwSearchTableItems); - hs->dwFlagMask = MPQ_FILE_EXISTS | MPQ_FILE_PATCH_FILE; - if(hs->pSearchTable != NULL) - memset(hs->pSearchTable, 0, hs->dwSearchTableItems * sizeof(TFileEntry *)); - else - dwErrCode = ERROR_NOT_ENOUGH_MEMORY; - } - } - - // Perform first item searching - if(dwErrCode == ERROR_SUCCESS) - { - dwErrCode = DoMPQSearch(hs, lpFindFileData); - } - - // Cleanup - if(dwErrCode != ERROR_SUCCESS) - { - FreeMPQSearch(hs); - SetLastError(dwErrCode); - } - - // Return the result value - return (HANDLE)hs; -} - -bool WINAPI SFileFindNextFile(HANDLE hFind, SFILE_FIND_DATA * lpFindFileData) -{ - TMPQSearch * hs = IsValidSearchHandle(hFind); - DWORD dwErrCode = ERROR_SUCCESS; - - // Check the parameters - if(hs == NULL) - dwErrCode = ERROR_INVALID_HANDLE; - if(lpFindFileData == NULL) - dwErrCode = ERROR_INVALID_PARAMETER; - - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = DoMPQSearch(hs, lpFindFileData); - - if(dwErrCode != ERROR_SUCCESS) - SetLastError(dwErrCode); - return (dwErrCode == ERROR_SUCCESS); -} - -bool WINAPI SFileFindClose(HANDLE hFind) -{ - TMPQSearch * hs = IsValidSearchHandle(hFind); - - // Check the parameters - if(hs == NULL) - { - SetLastError(ERROR_INVALID_HANDLE); - return false; - } - - FreeMPQSearch(hs); - return true; -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/SFileGetFileInfo.cpp b/app/jni/src/libultraship/extern/StormLib/src/SFileGetFileInfo.cpp deleted file mode 100644 index 77c86fd..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/SFileGetFileInfo.cpp +++ /dev/null @@ -1,609 +0,0 @@ -/*****************************************************************************/ -/* SFileGetFileInfo.cpp Copyright (c) Ladislav Zezula 2013 */ -/*---------------------------------------------------------------------------*/ -/* Description: */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 30.11.13 1.00 Lad The first version of SFileGetFileInfo.cpp */ -/*****************************************************************************/ - -#define __STORMLIB_SELF__ -#include "StormLib.h" -#include "StormCommon.h" - -//----------------------------------------------------------------------------- -// Local functions - -static DWORD GetMpqFileCount(TMPQArchive * ha) -{ - TFileEntry * pFileTableEnd; - TFileEntry * pFileEntry; - DWORD dwFileCount = 0; - - // Go through all open MPQs, including patches - while(ha != NULL) - { - // Only count files that are not patch files - pFileTableEnd = ha->pFileTable + ha->dwFileTableSize; - for(pFileEntry = ha->pFileTable; pFileEntry < pFileTableEnd; pFileEntry++) - { - // If the file is patch file and this is not primary archive, skip it - // BUGBUG: This errorneously counts non-patch files that are in both - // base MPQ and in patches, and increases the number of files by cca 50% - if((pFileEntry->dwFlags & (MPQ_FILE_EXISTS | MPQ_FILE_PATCH_FILE)) == MPQ_FILE_EXISTS) - dwFileCount++; - } - - // Move to the next patch archive - ha = ha->haPatch; - } - - return dwFileCount; -} - -static bool GetInfo_ReturdwErrCode(DWORD dwErrCode) -{ - SetLastError(dwErrCode); - return false; -} - -static bool GetInfo_BufferCheck(void * pvFileInfo, DWORD cbFileInfo, DWORD cbData, LPDWORD pcbLengthNeeded) -{ - // Give the length needed to store the info - if(pcbLengthNeeded != NULL) - pcbLengthNeeded[0] = cbData; - - // Check for sufficient buffer - if(cbData > cbFileInfo) - return GetInfo_ReturdwErrCode(ERROR_INSUFFICIENT_BUFFER); - - // If the buffer size is sufficient, check for valid user buffer - if(pvFileInfo == NULL) - return GetInfo_ReturdwErrCode(ERROR_INVALID_PARAMETER); - - // Buffers and sizes are OK, we are ready to proceed file copying - return true; -} - -static bool GetInfo(void * pvFileInfo, DWORD cbFileInfo, const void * pvData, DWORD cbData, LPDWORD pcbLengthNeeded) -{ - // Verify buffer pointer and buffer size - if(!GetInfo_BufferCheck(pvFileInfo, cbFileInfo, cbData, pcbLengthNeeded)) - return false; - - // Copy the data to the caller-supplied buffer - memcpy(pvFileInfo, pvData, cbData); - return true; -} - -static bool GetInfo_Allocated(void * pvFileInfo, DWORD cbFileInfo, void * pvData, DWORD cbData, LPDWORD pcbLengthNeeded) -{ - bool bResult; - - // Verify buffer pointer and buffer size - if((bResult = GetInfo_BufferCheck(pvFileInfo, cbFileInfo, cbData, pcbLengthNeeded)) != false) - memcpy(pvFileInfo, pvData, cbData); - - // Copy the data to the user buffer - STORM_FREE(pvData); - return bResult; -} - -static bool GetInfo_TablePointer(void * pvFileInfo, DWORD cbFileInfo, void * pvTablePointer, SFileInfoClass InfoClass, LPDWORD pcbLengthNeeded) -{ - // Verify buffer pointer and buffer size - if(!GetInfo_BufferCheck(pvFileInfo, cbFileInfo, sizeof(void *), pcbLengthNeeded)) - { - SFileFreeFileInfo(pvTablePointer, InfoClass); - return false; - } - - // The user buffer receives pointer to the table. - // When done, the caller needs to call SFileFreeFileInfo on it - *(void **)pvFileInfo = pvTablePointer; - return true; -} - -static bool GetInfo_ReadFromFile(void * pvFileInfo, DWORD cbFileInfo, TFileStream * pStream, ULONGLONG ByteOffset, DWORD cbData, LPDWORD pcbLengthNeeded) -{ - // Verify buffer pointer and buffer size - if(!GetInfo_BufferCheck(pvFileInfo, cbFileInfo, cbData, pcbLengthNeeded)) - return false; - - return FileStream_Read(pStream, &ByteOffset, pvFileInfo, cbData); -} - -static bool GetInfo_FileEntry(void * pvFileInfo, DWORD cbFileInfo, TFileEntry * pFileEntry, LPDWORD pcbLengthNeeded) -{ - LPBYTE pbFileInfo = (LPBYTE)pvFileInfo; - DWORD cbSrcFileInfo = sizeof(TFileEntry); - DWORD cbFileName = 1; - - // The file name belongs to the file entry - if(pFileEntry->szFileName) - cbFileName = (DWORD)strlen(pFileEntry->szFileName) + 1; - cbSrcFileInfo += cbFileName; - - // Verify buffer pointer and buffer size - if(!GetInfo_BufferCheck(pvFileInfo, cbFileInfo, cbSrcFileInfo, pcbLengthNeeded)) - return false; - - // Copy the file entry - memcpy(pbFileInfo, pFileEntry, sizeof(TFileEntry)); - pbFileInfo += sizeof(TFileEntry); - pbFileInfo[0] = 0; - - // Copy the file name - if(pFileEntry->szFileName) - memcpy(pbFileInfo, pFileEntry->szFileName, cbFileName); - return true; -} - -static bool GetInfo_PatchChain(TMPQFile * hf, void * pvFileInfo, DWORD cbFileInfo, LPDWORD pcbLengthNeeded) -{ - TMPQFile * hfTemp; - LPCTSTR szPatchName; - LPTSTR szFileInfo = (LPTSTR)pvFileInfo; - size_t cchCharsNeeded = 1; - size_t nLength; - - // Patch chain is only supported on MPQ files. Local files are not supported. - if(hf->pStream != NULL) - return GetInfo_ReturdwErrCode(ERROR_INVALID_PARAMETER); - - // Calculate the necessary length of the multi-string - for(hfTemp = hf; hfTemp != NULL; hfTemp = hfTemp->hfPatch) - cchCharsNeeded += _tcslen(FileStream_GetFileName(hfTemp->ha->pStream)) + 1; - - // Verify whether the caller gave us valid buffer with enough size - if(!GetInfo_BufferCheck(pvFileInfo, cbFileInfo, (DWORD)(cchCharsNeeded * sizeof(TCHAR)), pcbLengthNeeded)) - return false; - - // Copy each patch name - for(hfTemp = hf; hfTemp != NULL; hfTemp = hfTemp->hfPatch) - { - // Get the file name and its length - szPatchName = FileStream_GetFileName(hfTemp->ha->pStream); - nLength = _tcslen(szPatchName) + 1; - - // Copy the file name - memcpy(szFileInfo, szPatchName, nLength * sizeof(TCHAR)); - szFileInfo += nLength; - } - - // Make it multi-string - szFileInfo[0] = 0; - return true; -} - -//----------------------------------------------------------------------------- -// Retrieves an information about an archive or about a file within the archive -// -// hMpqOrFile - Handle to an MPQ archive or to a file -// InfoClass - Information to obtain -// pvFileInfo - Pointer to buffer to store the information -// cbFileInfo - Size of the buffer pointed by pvFileInfo -// pcbLengthNeeded - Receives number of bytes necessary to store the information - -bool WINAPI SFileGetFileInfo( - HANDLE hMpqOrFile, - SFileInfoClass InfoClass, - void * pvFileInfo, - DWORD cbFileInfo, - LPDWORD pcbLengthNeeded) -{ - MPQ_SIGNATURE_INFO SignatureInfo; - const TCHAR * szSrcFileInfo; - TMPQArchive * ha = NULL; - TFileEntry * pFileEntry = NULL; - TMPQHeader * pHeader = NULL; - ULONGLONG Int64Value = 0; - ULONGLONG ByteOffset; - TMPQFile * hf = NULL; - void * pvSrcFileInfo = NULL; - DWORD cbSrcFileInfo = 0; - DWORD dwInt32Value = 0; - - // Validate archive/file handle - if((int)InfoClass <= (int)SFileMpqFlags) - { - if((ha = IsValidMpqHandle(hMpqOrFile)) == NULL) - return GetInfo_ReturdwErrCode(ERROR_INVALID_HANDLE); - pHeader = ha->pHeader; - } - else - { - if((hf = IsValidFileHandle(hMpqOrFile)) == NULL) - return GetInfo_ReturdwErrCode(ERROR_INVALID_HANDLE); - pFileEntry = hf->pFileEntry; - } - - // Return info-class-specific data - switch(InfoClass) - { - case SFileMpqFileName: - szSrcFileInfo = FileStream_GetFileName(ha->pStream); - cbSrcFileInfo = (DWORD)((_tcslen(szSrcFileInfo) + 1) * sizeof(TCHAR)); - return GetInfo(pvFileInfo, cbFileInfo, szSrcFileInfo, cbSrcFileInfo, pcbLengthNeeded); - - case SFileMpqStreamBitmap: - return FileStream_GetBitmap(ha->pStream, pvFileInfo, cbFileInfo, pcbLengthNeeded); - - case SFileMpqUserDataOffset: - return GetInfo(pvFileInfo, cbFileInfo, &ha->UserDataPos, sizeof(ULONGLONG), pcbLengthNeeded); - - case SFileMpqUserDataHeader: - if(ha->pUserData == NULL) - return GetInfo_ReturdwErrCode(ERROR_INVALID_PARAMETER); - return GetInfo_ReadFromFile(pvFileInfo, cbFileInfo, ha->pStream, ha->UserDataPos, sizeof(TMPQUserData), pcbLengthNeeded); - - case SFileMpqUserData: - if(ha->pUserData == NULL) - return GetInfo_ReturdwErrCode(ERROR_INVALID_PARAMETER); - return GetInfo_ReadFromFile(pvFileInfo, cbFileInfo, ha->pStream, ha->UserDataPos + sizeof(TMPQUserData), ha->pUserData->dwHeaderOffs - sizeof(TMPQUserData), pcbLengthNeeded); - - case SFileMpqHeaderOffset: - return GetInfo(pvFileInfo, cbFileInfo, &ha->MpqPos, sizeof(ULONGLONG), pcbLengthNeeded); - - case SFileMpqHeaderSize: - return GetInfo(pvFileInfo, cbFileInfo, &pHeader->dwHeaderSize, sizeof(DWORD), pcbLengthNeeded); - - case SFileMpqHeader: - return GetInfo_ReadFromFile(pvFileInfo, cbFileInfo, ha->pStream, ha->MpqPos, pHeader->dwHeaderSize, pcbLengthNeeded); - - case SFileMpqHetTableOffset: - return GetInfo(pvFileInfo, cbFileInfo, &pHeader->HetTablePos64, sizeof(ULONGLONG), pcbLengthNeeded); - - case SFileMpqHetTableSize: - return GetInfo(pvFileInfo, cbFileInfo, &pHeader->HetTableSize64, sizeof(ULONGLONG), pcbLengthNeeded); - - case SFileMpqHetHeader: - pvSrcFileInfo = LoadExtTable(ha, pHeader->HetTablePos64, (size_t)pHeader->HetTableSize64, HET_TABLE_SIGNATURE, MPQ_KEY_HASH_TABLE); - if(pvSrcFileInfo == NULL) - return GetInfo_ReturdwErrCode(ERROR_FILE_NOT_FOUND); - return GetInfo_Allocated(pvFileInfo, cbFileInfo, pvSrcFileInfo, sizeof(TMPQHetHeader), pcbLengthNeeded); - - case SFileMpqHetTable: - if((pvSrcFileInfo = LoadHetTable(ha)) == NULL) - return GetInfo_ReturdwErrCode(ERROR_NOT_ENOUGH_MEMORY); - return GetInfo_TablePointer(pvFileInfo, cbFileInfo, pvSrcFileInfo, InfoClass, pcbLengthNeeded); - - case SFileMpqBetTableOffset: - return GetInfo(pvFileInfo, cbFileInfo, &pHeader->BetTablePos64, sizeof(ULONGLONG), pcbLengthNeeded); - - case SFileMpqBetTableSize: - return GetInfo(pvFileInfo, cbFileInfo, &pHeader->BetTableSize64, sizeof(ULONGLONG), pcbLengthNeeded); - - case SFileMpqBetHeader: - - // Retrieve the table and its size - pvSrcFileInfo = LoadExtTable(ha, pHeader->BetTablePos64, (size_t)pHeader->BetTableSize64, BET_TABLE_SIGNATURE, MPQ_KEY_BLOCK_TABLE); - if(pvSrcFileInfo == NULL) - return GetInfo_ReturdwErrCode(ERROR_FILE_NOT_FOUND); - cbSrcFileInfo = sizeof(TMPQBetHeader) + ((TMPQBetHeader *)pvSrcFileInfo)->dwFlagCount * sizeof(DWORD); - - // It is allowed for the caller to only require BET header - if(cbFileInfo == sizeof(TMPQBetHeader)) - cbSrcFileInfo = sizeof(TMPQBetHeader); - return GetInfo_Allocated(pvFileInfo, cbFileInfo, pvSrcFileInfo, cbSrcFileInfo, pcbLengthNeeded); - - case SFileMpqBetTable: - if((pvSrcFileInfo = LoadBetTable(ha)) == NULL) - return GetInfo_ReturdwErrCode(ERROR_NOT_ENOUGH_MEMORY); - return GetInfo_TablePointer(pvFileInfo, cbFileInfo, pvSrcFileInfo, InfoClass, pcbLengthNeeded); - - case SFileMpqHashTableOffset: - Int64Value = MAKE_OFFSET64(pHeader->wHashTablePosHi, pHeader->dwHashTablePos); - return GetInfo(pvFileInfo, cbFileInfo, &Int64Value, sizeof(ULONGLONG), pcbLengthNeeded); - - case SFileMpqHashTableSize64: - return GetInfo(pvFileInfo, cbFileInfo, &pHeader->HashTableSize64, sizeof(ULONGLONG), pcbLengthNeeded); - - case SFileMpqHashTableSize: - return GetInfo(pvFileInfo, cbFileInfo, &pHeader->dwHashTableSize, sizeof(DWORD), pcbLengthNeeded); - - case SFileMpqHashTable: - cbSrcFileInfo = pHeader->dwHashTableSize * sizeof(TMPQHash); - return GetInfo(pvFileInfo, cbFileInfo, ha->pHashTable, cbSrcFileInfo, pcbLengthNeeded); - - case SFileMpqBlockTableOffset: - Int64Value = MAKE_OFFSET64(pHeader->wBlockTablePosHi, pHeader->dwBlockTablePos); - return GetInfo(pvFileInfo, cbFileInfo, &Int64Value, sizeof(ULONGLONG), pcbLengthNeeded); - - case SFileMpqBlockTableSize64: - return GetInfo(pvFileInfo, cbFileInfo, &pHeader->BlockTableSize64, sizeof(ULONGLONG), pcbLengthNeeded); - - case SFileMpqBlockTableSize: - return GetInfo(pvFileInfo, cbFileInfo, &pHeader->dwBlockTableSize, sizeof(DWORD), pcbLengthNeeded); - - case SFileMpqBlockTable: - ByteOffset = FileOffsetFromMpqOffset(ha, MAKE_OFFSET64(pHeader->wBlockTablePosHi, pHeader->dwBlockTablePos)); - if(ByteOffset >= ha->FileSize) - return GetInfo_ReturdwErrCode(ERROR_FILE_NOT_FOUND); - cbSrcFileInfo = pHeader->dwBlockTableSize * sizeof(TMPQBlock); - pvSrcFileInfo = LoadBlockTable(ha, true); - return GetInfo_Allocated(pvFileInfo, cbFileInfo, pvSrcFileInfo, cbSrcFileInfo, pcbLengthNeeded); - - case SFileMpqHiBlockTableOffset: - return GetInfo(pvFileInfo, cbFileInfo, &pHeader->HiBlockTablePos64, sizeof(ULONGLONG), pcbLengthNeeded); - - case SFileMpqHiBlockTableSize64: - return GetInfo(pvFileInfo, cbFileInfo, &pHeader->HiBlockTableSize64, sizeof(ULONGLONG), pcbLengthNeeded); - - case SFileMpqHiBlockTable: - return GetInfo_ReturdwErrCode(ERROR_FILE_NOT_FOUND); - - case SFileMpqSignatures: - if(!QueryMpqSignatureInfo(ha, &SignatureInfo)) - return GetInfo_ReturdwErrCode(ERROR_FILE_NOT_FOUND); - return GetInfo(pvFileInfo, cbFileInfo, &SignatureInfo.SignatureTypes, sizeof(DWORD), pcbLengthNeeded); - - case SFileMpqStrongSignatureOffset: - if(QueryMpqSignatureInfo(ha, &SignatureInfo) == false || (SignatureInfo.SignatureTypes & SIGNATURE_TYPE_STRONG) == 0) - return GetInfo_ReturdwErrCode(ERROR_FILE_NOT_FOUND); - return GetInfo(pvFileInfo, cbFileInfo, &SignatureInfo.EndMpqData, sizeof(ULONGLONG), pcbLengthNeeded); - - case SFileMpqStrongSignatureSize: - if(QueryMpqSignatureInfo(ha, &SignatureInfo) == false || (SignatureInfo.SignatureTypes & SIGNATURE_TYPE_STRONG) == 0) - return GetInfo_ReturdwErrCode(ERROR_FILE_NOT_FOUND); - dwInt32Value = MPQ_STRONG_SIGNATURE_SIZE + 4; - return GetInfo(pvFileInfo, cbFileInfo, &dwInt32Value, sizeof(DWORD), pcbLengthNeeded); - - case SFileMpqStrongSignature: - if(QueryMpqSignatureInfo(ha, &SignatureInfo) == false || (SignatureInfo.SignatureTypes & SIGNATURE_TYPE_STRONG) == 0) - return GetInfo_ReturdwErrCode(ERROR_FILE_NOT_FOUND); - return GetInfo(pvFileInfo, cbFileInfo, SignatureInfo.Signature, MPQ_STRONG_SIGNATURE_SIZE + 4, pcbLengthNeeded); - - case SFileMpqArchiveSize64: - return GetInfo(pvFileInfo, cbFileInfo, &pHeader->ArchiveSize64, sizeof(ULONGLONG), pcbLengthNeeded); - - case SFileMpqArchiveSize: - return GetInfo(pvFileInfo, cbFileInfo, &pHeader->dwArchiveSize, sizeof(DWORD), pcbLengthNeeded); - - case SFileMpqMaxFileCount: - return GetInfo(pvFileInfo, cbFileInfo, &ha->dwMaxFileCount, sizeof(DWORD), pcbLengthNeeded); - - case SFileMpqFileTableSize: - return GetInfo(pvFileInfo, cbFileInfo, &ha->dwFileTableSize, sizeof(DWORD), pcbLengthNeeded); - - case SFileMpqSectorSize: - return GetInfo(pvFileInfo, cbFileInfo, &ha->dwSectorSize, sizeof(DWORD), pcbLengthNeeded); - - case SFileMpqNumberOfFiles: - dwInt32Value = GetMpqFileCount(ha); - return GetInfo(pvFileInfo, cbFileInfo, &dwInt32Value, sizeof(DWORD), pcbLengthNeeded); - - case SFileMpqRawChunkSize: - if(pHeader->dwRawChunkSize == 0) - return GetInfo_ReturdwErrCode(ERROR_FILE_NOT_FOUND); - return GetInfo(pvFileInfo, cbFileInfo, &pHeader->dwRawChunkSize, sizeof(DWORD), pcbLengthNeeded); - - case SFileMpqStreamFlags: - FileStream_GetFlags(ha->pStream, &dwInt32Value); - return GetInfo(pvFileInfo, cbFileInfo, &dwInt32Value, sizeof(DWORD), pcbLengthNeeded); - - case SFileMpqFlags: - return GetInfo(pvFileInfo, cbFileInfo, &ha->dwFlags, sizeof(DWORD), pcbLengthNeeded); - - case SFileInfoPatchChain: - return GetInfo_PatchChain(hf, pvFileInfo, cbFileInfo, pcbLengthNeeded); - - case SFileInfoFileEntry: - if(pFileEntry == NULL) - return GetInfo_ReturdwErrCode(ERROR_FILE_NOT_FOUND); - return GetInfo_FileEntry(pvFileInfo, cbFileInfo, pFileEntry, pcbLengthNeeded); - - case SFileInfoHashEntry: - return GetInfo(pvFileInfo, cbFileInfo, hf->pHashEntry, sizeof(TMPQHash), pcbLengthNeeded); - - case SFileInfoHashIndex: - return GetInfo(pvFileInfo, cbFileInfo, &hf->dwHashIndex, sizeof(DWORD), pcbLengthNeeded); - - case SFileInfoNameHash1: - return GetInfo(pvFileInfo, cbFileInfo, &hf->pHashEntry->dwName1, sizeof(DWORD), pcbLengthNeeded); - - case SFileInfoNameHash2: - return GetInfo(pvFileInfo, cbFileInfo, &hf->pHashEntry->dwName2, sizeof(DWORD), pcbLengthNeeded); - - case SFileInfoNameHash3: - return GetInfo(pvFileInfo, cbFileInfo, &pFileEntry->FileNameHash, sizeof(ULONGLONG), pcbLengthNeeded); - - case SFileInfoLocale: - dwInt32Value = SFILE_MAKE_LCID(hf->pHashEntry->Locale, hf->pHashEntry->Platform); - return GetInfo(pvFileInfo, cbFileInfo, &dwInt32Value, sizeof(DWORD), pcbLengthNeeded); - - case SFileInfoFileIndex: - dwInt32Value = (DWORD)(pFileEntry - hf->ha->pFileTable); - return GetInfo(pvFileInfo, cbFileInfo, &dwInt32Value, sizeof(DWORD), pcbLengthNeeded); - - case SFileInfoByteOffset: - return GetInfo(pvFileInfo, cbFileInfo, &pFileEntry->ByteOffset, sizeof(ULONGLONG), pcbLengthNeeded); - - case SFileInfoFileTime: - return GetInfo(pvFileInfo, cbFileInfo, &pFileEntry->FileTime, sizeof(ULONGLONG), pcbLengthNeeded); - - case SFileInfoFileSize: - return GetInfo(pvFileInfo, cbFileInfo, &pFileEntry->dwFileSize, sizeof(DWORD), pcbLengthNeeded); - - case SFileInfoCompressedSize: - return GetInfo(pvFileInfo, cbFileInfo, &pFileEntry->dwCmpSize, sizeof(DWORD), pcbLengthNeeded); - - case SFileInfoFlags: - return GetInfo(pvFileInfo, cbFileInfo, &pFileEntry->dwFlags, sizeof(DWORD), pcbLengthNeeded); - - case SFileInfoEncryptionKey: - return GetInfo(pvFileInfo, cbFileInfo, &hf->dwFileKey, sizeof(DWORD), pcbLengthNeeded); - - case SFileInfoEncryptionKeyRaw: - dwInt32Value = hf->dwFileKey; - if(pFileEntry->dwFlags & MPQ_FILE_FIX_KEY) - dwInt32Value = (dwInt32Value ^ pFileEntry->dwFileSize) - (DWORD)hf->MpqFilePos; - return GetInfo(pvFileInfo, cbFileInfo, &dwInt32Value, sizeof(DWORD), pcbLengthNeeded); - - case SFileInfoCRC32: - return GetInfo(pvFileInfo, cbFileInfo, &hf->pFileEntry->dwCrc32, sizeof(DWORD), pcbLengthNeeded); - default: - // Invalid info class - return GetInfo_ReturdwErrCode(ERROR_INVALID_PARAMETER); - } -} - -bool WINAPI SFileFreeFileInfo(void * pvFileInfo, SFileInfoClass InfoClass) -{ - switch(InfoClass) - { - case SFileMpqHetTable: - FreeHetTable((TMPQHetTable *)pvFileInfo); - return true; - - case SFileMpqBetTable: - FreeBetTable((TMPQBetTable *)pvFileInfo); - return true; - - default: - break; - } - - SetLastError(ERROR_INVALID_PARAMETER); - return false; -} - -//----------------------------------------------------------------------------- -// Tries to retrieve the file name - -struct TFileHeader2Ext -{ - DWORD dwOffset00Data; // Required data at offset 00 (32-bits) - DWORD dwOffset00Mask; // Mask for data at offset 00 (32 bits). 0 = data are ignored - DWORD dwOffset04Data; // Required data at offset 04 (32-bits) - DWORD dwOffset04Mask; // Mask for data at offset 04 (32 bits). 0 = data are ignored - const char * szExt; // Supplied extension, if the condition is true -}; - -static TFileHeader2Ext data2ext[] = -{ - {0x00005A4D, 0x0000FFFF, 0x00000000, 0x00000000, "exe"}, // EXE files - {0x00000006, 0xFFFFFFFF, 0x00000001, 0xFFFFFFFF, "dc6"}, // EXE files - {0x1A51504D, 0xFFFFFFFF, 0x00000000, 0x00000000, "mpq"}, // MPQ archive header ID ('MPQ\x1A') - {0x46464952, 0xFFFFFFFF, 0x00000000, 0x00000000, "wav"}, // WAVE header 'RIFF' - {0x324B4D53, 0xFFFFFFFF, 0x00000000, 0x00000000, "smk"}, // Old "Smacker Video" files 'SMK2' - {0x694B4942, 0xFFFFFFFF, 0x00000000, 0x00000000, "bik"}, // Bink video files (new) - {0x0801050A, 0xFFFFFFFF, 0x00000000, 0x00000000, "pcx"}, // PCX images used in Diablo I - {0x544E4F46, 0xFFFFFFFF, 0x00000000, 0x00000000, "fnt"}, // Font files used in Diablo II - {0x6D74683C, 0xFFFFFFFF, 0x00000000, 0x00000000, "html"}, // HTML 'ha->pFileTable), data2ext[i].szExt); - - // Save the pseudo-name in the file entry as well - AllocateFileName(hf->ha, pFileEntry, szPseudoName); - - // If the caller wants to copy the file name, do it - if(szFileName != NULL) - strcpy(szFileName, szPseudoName); - return ERROR_SUCCESS; - } - } - } - - return ERROR_CAN_NOT_COMPLETE; -} - -bool WINAPI SFileGetFileName(HANDLE hFile, char * szFileName) -{ - TMPQFile * hf = (TMPQFile *)hFile; // MPQ File handle - DWORD dwErrCode = ERROR_INVALID_HANDLE; - - // Check valid parameters - if(IsValidFileHandle(hFile)) - { - TFileEntry * pFileEntry = hf->pFileEntry; - - // For MPQ files, retrieve the file name from the file entry - if(hf->pStream == NULL) - { - if(pFileEntry != NULL) - { - // If the file name is not there yet, create a pseudo name - if(pFileEntry->szFileName == NULL) - dwErrCode = CreatePseudoFileName(hFile, pFileEntry, szFileName); - - // Copy the file name to the output buffer, if any - if(pFileEntry->szFileName && szFileName) - { - strcpy(szFileName, pFileEntry->szFileName); - dwErrCode = ERROR_SUCCESS; - } - } - } - - // For local files, copy the file name from the stream - else - { - if(szFileName != NULL) - { - const TCHAR * szStreamName = FileStream_GetFileName(hf->pStream); - StringCopy(szFileName, MAX_PATH, szStreamName); - } - dwErrCode = ERROR_SUCCESS; - } - } - - if(dwErrCode != ERROR_SUCCESS) - SetLastError(dwErrCode); - return (dwErrCode == ERROR_SUCCESS); -} - diff --git a/app/jni/src/libultraship/extern/StormLib/src/SFileListFile.cpp b/app/jni/src/libultraship/extern/StormLib/src/SFileListFile.cpp deleted file mode 100644 index 081f70c..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/SFileListFile.cpp +++ /dev/null @@ -1,704 +0,0 @@ -/*****************************************************************************/ -/* SListFile.cpp Copyright (c) Ladislav Zezula 2004 */ -/*---------------------------------------------------------------------------*/ -/* Description: */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 12.06.04 1.00 Lad The first version of SListFile.cpp */ -/*****************************************************************************/ - -#define __STORMLIB_SELF__ -#include "StormLib.h" -#include "StormCommon.h" -#include - -//----------------------------------------------------------------------------- -// Listfile entry structure - -#define CACHE_BUFFER_SIZE 0x1000 // Size of the cache buffer -#define MAX_LISTFILE_SIZE 0x8000000 // Maximum accepted listfile size is 128 MB - -union TListFileHandle -{ - TFileStream * pStream; // Opened local file - HANDLE hFile; // Opened MPQ file -}; - -struct TListFileCache -{ - char * szWildCard; // Self-relative pointer to file mask - LPBYTE pBegin; // The begin of the listfile cache - LPBYTE pPos; // Current position in the cache - LPBYTE pEnd; // The last character in the file cache - DWORD dwFlags; // Flags from TMPQArchive - -// char szWildCard[wildcard_length]; // Followed by the name mask (if any) -// char szListFile[listfile_length]; // Followed by the listfile (if any) -}; - -typedef bool (*LOAD_LISTFILE)(TListFileHandle * pHandle, void * pvBuffer, DWORD cbBuffer, LPDWORD pdwBytesRead); - -//----------------------------------------------------------------------------- -// Local functions (cache) - -// In SFileFindFile.cll -bool SFileCheckWildCard(const char * szString, const char * szWildCard); - -static char * CopyListLine(char * szListLine, const char * szFileName) -{ - // Copy the string - while(szFileName[0] != 0) - *szListLine++ = *szFileName++; - - // Append the end-of-line - *szListLine++ = 0x0D; - *szListLine++ = 0x0A; - return szListLine; -} - -static bool LoadListFile_Stream(TListFileHandle * pHandle, void * pvBuffer, DWORD cbBuffer, LPDWORD pdwBytesRead) -{ - ULONGLONG ByteOffset = 0; - bool bResult; - - bResult = FileStream_Read(pHandle->pStream, &ByteOffset, pvBuffer, cbBuffer); - if(bResult) - *pdwBytesRead = cbBuffer; - return bResult; -} - -static bool LoadListFile_MPQ(TListFileHandle * pHandle, void * pvBuffer, DWORD cbBuffer, LPDWORD pdwBytesRead) -{ - return SFileReadFile(pHandle->hFile, pvBuffer, cbBuffer, pdwBytesRead, NULL); -} - -static bool FreeListFileCache(TListFileCache * pCache) -{ - // Valid parameter check - if(pCache != NULL) - STORM_FREE(pCache); - return true; -} - -static TListFileCache * CreateListFileCache( - LOAD_LISTFILE PfnLoadFile, - TListFileHandle * pHandle, - const char * szWildCard, - DWORD dwFileSize, - DWORD dwMaxSize, - DWORD dwFlags) -{ - TListFileCache * pCache = NULL; - size_t cchWildCardAligned = 0; - size_t cchWildCard = 0; - DWORD dwBytesRead = 0; - - // Get the amount of bytes that need to be allocated - if(dwFileSize == 0 || dwFileSize > dwMaxSize) - return NULL; - - // Append buffer for name mask, if any - if(szWildCard != NULL) - { - cchWildCard = strlen(szWildCard) + 1; - cchWildCardAligned = (cchWildCard + 3) & 0xFFFFFFFC; - } - - // Allocate cache for one file block - pCache = (TListFileCache *)STORM_ALLOC(BYTE, sizeof(TListFileCache) + cchWildCardAligned + dwFileSize + 1); - if(pCache != NULL) - { - // Clear the entire structure - memset(pCache, 0, sizeof(TListFileCache) + cchWildCard); - pCache->dwFlags = dwFlags; - - // Shall we copy the mask? - if(cchWildCard != 0) - { - pCache->szWildCard = (char *)(pCache + 1); - memcpy(pCache->szWildCard, szWildCard, cchWildCard); - } - - // Fill-in the rest of the cache pointers - pCache->pBegin = (LPBYTE)(pCache + 1) + cchWildCardAligned; - - // Load the entire listfile to the cache - PfnLoadFile(pHandle, pCache->pBegin, dwFileSize, &dwBytesRead); - if(dwBytesRead != 0) - { - // Allocate pointers - pCache->pPos = pCache->pBegin; - pCache->pEnd = pCache->pBegin + dwBytesRead; - } - else - { - FreeListFileCache(pCache); - pCache = NULL; - } - } - - // Return the cache - return pCache; -} - -static TListFileCache * CreateListFileCache( - HANDLE hMpq, - const TCHAR * szListFile, - const char * szWildCard, - DWORD dwMaxSize, - DWORD dwFlags) -{ - TListFileCache * pCache = NULL; - TListFileHandle ListHandle = {NULL}; - - // Put default value to dwMaxSize - if(dwMaxSize == 0) - dwMaxSize = MAX_LISTFILE_SIZE; - - // Internal listfile: hMPQ must be non NULL and szListFile must be NULL. - // We load the MPQ::(listfile) file - if(hMpq != NULL && szListFile == NULL) - { - DWORD dwFileSize = 0; - - // Open the file from the MPQ - if(SFileOpenFileEx(hMpq, LISTFILE_NAME, 0, &ListHandle.hFile)) - { - // Get the file size and create the listfile cache - dwFileSize = SFileGetFileSize(ListHandle.hFile, NULL); - pCache = CreateListFileCache(LoadListFile_MPQ, &ListHandle, szWildCard, dwFileSize, dwMaxSize, dwFlags); - - // Close the MPQ file - SFileCloseFile(ListHandle.hFile); - } - - // Return the loaded cache - return pCache; - } - - // External listfile: hMpq must be NULL and szListFile must be non-NULL. - // We load the file using TFileStream - if(hMpq == NULL && szListFile != NULL) - { - ULONGLONG FileSize = 0; - - // Open the local file - ListHandle.pStream = FileStream_OpenFile(szListFile, STREAM_FLAG_READ_ONLY); - if(ListHandle.pStream != NULL) - { - // Verify the file size - FileStream_GetSize(ListHandle.pStream, &FileSize); - if(0 < FileSize && FileSize < dwMaxSize) - { - pCache = CreateListFileCache(LoadListFile_Stream, &ListHandle, szWildCard, (DWORD)FileSize, dwMaxSize, dwFlags); - } - - // Close the stream - FileStream_Close(ListHandle.pStream); - } - - // Return the loaded cache - return pCache; - } - - // This combination should never happen - SetLastError(ERROR_INVALID_PARAMETER); - assert(false); - return NULL; -} - -#ifdef _DEBUG -/* -TMPQNameCache * CreateNameCache(HANDLE hListFile, const char * szSearchMask) -{ - TMPQNameCache * pNameCache; - char * szCachePointer; - size_t cbToAllocate; - size_t nMaskLength = 1; - DWORD dwBytesRead = 0; - DWORD dwFileSize; - - // Get the size of the listfile. Ignore zero or too long ones - dwFileSize = SFileGetFileSize(hListFile, NULL); - if(dwFileSize == 0 || dwFileSize > MAX_LISTFILE_SIZE) - return NULL; - - // Get the length of the search mask - if(szSearchMask == NULL) - szSearchMask = "*"; - nMaskLength = strlen(szSearchMask) + 1; - - // Allocate the name cache - cbToAllocate = sizeof(TMPQNameCache) + nMaskLength + dwFileSize + 1; - pNameCache = (TMPQNameCache *)STORM_ALLOC(BYTE, cbToAllocate); - if(pNameCache != NULL) - { - // Initialize the name cache - memset(pNameCache, 0, sizeof(TMPQNameCache)); - pNameCache->TotalCacheSize = (DWORD)(nMaskLength + dwFileSize + 1); - szCachePointer = (char *)(pNameCache + 1); - - // Copy the search mask, if any - memcpy(szCachePointer, szSearchMask, nMaskLength); - pNameCache->FirstNameOffset = (DWORD)nMaskLength; - pNameCache->FreeSpaceOffset = (DWORD)nMaskLength; - - // Read the listfile itself - SFileSetFilePointer(hListFile, 0, NULL, FILE_BEGIN); - SFileReadFile(hListFile, szCachePointer + nMaskLength, dwFileSize, &dwBytesRead, NULL); - - // If nothing has been read from the listfile, clear the cache - if(dwBytesRead == 0) - { - STORM_FREE(pNameCache); - return NULL; - } - - // Move the free space offset - pNameCache->FreeSpaceOffset = pNameCache->FirstNameOffset + dwBytesRead + 1; - szCachePointer[nMaskLength + dwBytesRead] = 0; - } - - return pNameCache; -} - -static void FreeNameCache(TMPQNameCache * pNameCache) -{ - if(pNameCache != NULL) - STORM_FREE(pNameCache); - pNameCache = NULL; -} -*/ -#endif // _DEBUG - -static char * ReadListFileLine(TListFileCache * pCache, size_t * PtrLength) -{ - LPBYTE pbLineBegin; - LPBYTE pbLineEnd; - - // Skip newlines. Keep spaces and tabs, as they can be a legal part of the file name - while(pCache->pPos < pCache->pEnd && (pCache->pPos[0] == 0x0A || pCache->pPos[0] == 0x0D)) - pCache->pPos++; - - // Set the line begin and end - if(pCache->pPos >= pCache->pEnd) - return NULL; - pbLineBegin = pbLineEnd = pCache->pPos; - - // Find the end of the line - while(pCache->pPos < pCache->pEnd && pCache->pPos[0] != 0x0A && pCache->pPos[0] != 0x0D) - pCache->pPos++; - - // Remember the end of the line - pbLineEnd = pCache->pPos++; - pbLineEnd[0] = 0; - - // Give the line to the caller - if(PtrLength != NULL) - PtrLength[0] = (size_t)(pbLineEnd - pbLineBegin); - return (char *)pbLineBegin; -} - -static int STORMLIB_CDECL CompareFileNodes(const void * p1, const void * p2) -{ - char * szFileName1 = *(char **)p1; - char * szFileName2 = *(char **)p2; - - return _stricmp(szFileName1, szFileName2); -} - -static LPBYTE CreateListFile(TMPQArchive * ha, DWORD * pcbListFile) -{ - TFileEntry * pFileTableEnd = ha->pFileTable + ha->dwFileTableSize; - TFileEntry * pFileEntry; - char ** SortTable = NULL; - char * szListFile = NULL; - char * szListLine; - size_t nFileNodes = 0; - size_t cbListFile = 0; - size_t nIndex0; - size_t nIndex1; - - // Allocate the table for sorting listfile - SortTable = STORM_ALLOC(char*, ha->dwFileTableSize); - if(SortTable == NULL) - return NULL; - - // Construct the sort table - // Note: in MPQs with multiple locale versions of the same file, - // this code causes adding multiple listfile entries. - // They will get removed after the listfile sorting - for(pFileEntry = ha->pFileTable; pFileEntry < pFileTableEnd; pFileEntry++) - { - // Only take existing items - if((pFileEntry->dwFlags & MPQ_FILE_EXISTS) && pFileEntry->szFileName != NULL) - { - // Ignore pseudo-names and internal names - if(!IsPseudoFileName(pFileEntry->szFileName, NULL) && !IsInternalMpqFileName(pFileEntry->szFileName)) - { - SortTable[nFileNodes++] = pFileEntry->szFileName; - } - } - } - - // Remove duplicities - if(nFileNodes > 0) - { - // Sort the table - qsort(SortTable, nFileNodes, sizeof(char *), CompareFileNodes); - - // Count the 0-th item - cbListFile += strlen(SortTable[0]) + 2; - - // Walk through the items and only use the ones that are not duplicated - for(nIndex0 = 0, nIndex1 = 1; nIndex1 < nFileNodes; nIndex1++) - { - // If the next file node is different, we will include it to the result listfile - if(_stricmp(SortTable[nIndex1], SortTable[nIndex0]) != 0) - { - cbListFile += strlen(SortTable[nIndex1]) + 2; - nIndex0 = nIndex1; - } - } - - // Now allocate buffer for the entire listfile - szListFile = szListLine = STORM_ALLOC(char, cbListFile + 1); - if(szListFile != NULL) - { - // Copy the 0-th item - szListLine = CopyListLine(szListLine, SortTable[0]); - - // Walk through the items and only use the ones that are not duplicated - for(nIndex0 = 0, nIndex1 = 1; nIndex1 < nFileNodes; nIndex1++) - { - // If the next file node is different, we will include it to the result listfile - if(_stricmp(SortTable[nIndex1], SortTable[nIndex0]) != 0) - { - // Copy the listfile line - szListLine = CopyListLine(szListLine, SortTable[nIndex1]); - nIndex0 = nIndex1; - } - } - - // Sanity check - does the size match? - assert((size_t)(szListLine - szListFile) == cbListFile); - } - } - else - { - szListFile = STORM_ALLOC(char, 1); - cbListFile = 0; - } - - // Free the sort table - STORM_FREE(SortTable); - - // Give away the listfile - if(pcbListFile != NULL) - *pcbListFile = (DWORD)cbListFile; - return (LPBYTE)szListFile; -} - -//----------------------------------------------------------------------------- -// Local functions (listfile nodes) - -// Adds a name into the list of all names. For each locale in the MPQ, -// one entry will be created -// If the file name is already there, does nothing. -static DWORD SListFileCreateNodeForAllLocales(TMPQArchive * ha, const char * szFileName) -{ - TFileEntry * pFileEntry; - TMPQHash * pFirstHash; - TMPQHash * pHashEnd; - TMPQHash * pHash; - DWORD dwName1; - DWORD dwName2; - - // If we have HET table, use that one - if(ha->pHetTable != NULL) - { - pFileEntry = GetFileEntryLocale(ha, szFileName, 0); - if(pFileEntry != NULL) - { - // Allocate file name for the file entry - AllocateFileName(ha, pFileEntry, szFileName); - } - - return ERROR_SUCCESS; - } - - // If we have hash table, we use it - if(ha->pHashTable != NULL) - { - // Get the end of the hash table and both names - pHashEnd = ha->pHashTable + ha->pHeader->dwHashTableSize; - dwName1 = ha->pfnHashString(szFileName, MPQ_HASH_NAME_A); - dwName2 = ha->pfnHashString(szFileName, MPQ_HASH_NAME_B); - - // Some protectors set very high hash table size (0x00400000 items or more) - // in order to make this process very slow. We will ignore items - // in the hash table that would be beyond the end of the file. - // Example MPQ: MPQ_2022_v1_Sniper.scx - if(ha->dwFlags & MPQ_FLAG_HASH_TABLE_CUT) - pHashEnd = ha->pHashTable + (ha->dwRealHashTableSize / sizeof(TMPQHash)); - - // Go through the hash table and put the name in each item that has the same name pair - //for(pHash = ha->pHashTable; pHash < pHashEnd; pHash++) - //{ - // if(pHash->dwName1 == dwName1 && pHash->dwName2 == dwName2 && MPQ_BLOCK_INDEX(pHash) < ha->dwFileTableSize) - // { - // // Allocate file name for the file entry - // AllocateFileName(ha, ha->pFileTable + MPQ_BLOCK_INDEX(pHash), szFileName); - // } - //} - - // Go while we found something - pFirstHash = pHash = GetFirstHashEntry(ha, szFileName); - while(pHash != NULL) - { - // Allocate file name for the file entry - AllocateFileName(ha, ha->pFileTable + MPQ_BLOCK_INDEX(pHash), szFileName); - - // Now find the next language version of the file - pHash = GetNextHashEntry(ha, pFirstHash, pHash); - } - - return ERROR_SUCCESS; - } - - return ERROR_CAN_NOT_COMPLETE; -} - -// Saves the whole listfile to the MPQ -DWORD SListFileSaveToMpq(TMPQArchive * ha) -{ - TMPQFile * hf = NULL; - LPBYTE pbListFile; - DWORD cbListFile = 0; - DWORD dwErrCode = ERROR_SUCCESS; - - // Only save the listfile if we should do so - if(ha->dwFileFlags1 != 0) - { - // At this point, we expect to have at least one reserved entry in the file table - assert(ha->dwFlags & MPQ_FLAG_LISTFILE_NEW); - assert(ha->dwReservedFiles > 0); - - // Create the raw data that is to be written to (listfile) - // Note: Creating the raw data before the (listfile) has been created in the MPQ - // causes that the name of the listfile will not be included in the listfile itself. - // That is OK, because (listfile) in Blizzard MPQs does not contain it either. - pbListFile = CreateListFile(ha, &cbListFile); - if(pbListFile != NULL) - { - // Determine the real flags for (listfile) - if(ha->dwFileFlags1 == MPQ_FILE_DEFAULT_INTERNAL) - ha->dwFileFlags1 = GetDefaultSpecialFileFlags(cbListFile, ha->pHeader->wFormatVersion); - - // Create the listfile in the MPQ - dwErrCode = SFileAddFile_Init(ha, LISTFILE_NAME, - 0, - cbListFile, - LANG_NEUTRAL, - ha->dwFileFlags1 | MPQ_FILE_REPLACEEXISTING, - &hf); - - // Write the listfile raw data to it - if(dwErrCode == ERROR_SUCCESS) - { - // Write the content of the listfile to the MPQ - dwErrCode = SFileAddFile_Write(hf, pbListFile, cbListFile, MPQ_COMPRESSION_ZLIB); - SFileAddFile_Finish(hf); - } - - // Clear the listfile flags - ha->dwFlags &= ~(MPQ_FLAG_LISTFILE_NEW | MPQ_FLAG_LISTFILE_NONE); - ha->dwReservedFiles--; - - // Free the listfile buffer - STORM_FREE(pbListFile); - } - else - { - // If the (listfile) file would be empty, its OK - dwErrCode = (cbListFile == 0) ? ERROR_SUCCESS : ERROR_NOT_ENOUGH_MEMORY; - } - } - - return dwErrCode; -} - -static DWORD SFileAddArbitraryListFile( - TMPQArchive * ha, - HANDLE hMpq, - const TCHAR * szListFile, - DWORD dwMaxSize) -{ - TListFileCache * pCache = NULL; - - // Create the listfile cache for that file - pCache = CreateListFileCache(hMpq, szListFile, NULL, dwMaxSize, ha->dwFlags); - if(pCache != NULL) - { - char * szFileName; - size_t nLength = 0; - - // Get the next line - while((szFileName = ReadListFileLine(pCache, &nLength)) != NULL) - { - // Add the line to the MPQ - if(nLength != 0) - SListFileCreateNodeForAllLocales(ha, szFileName); - } - - // Delete the cache - FreeListFileCache(pCache); - } - - return (pCache != NULL) ? ERROR_SUCCESS : ERROR_FILE_CORRUPT; -} - -static DWORD SFileAddInternalListFile( - TMPQArchive * ha, - HANDLE hMpq) -{ - TMPQHash * pFirstHash; - TMPQHash * pHash; - LCID lcSaveLocale = g_lcFileLocale; - DWORD dwMaxSize = MAX_LISTFILE_SIZE; - DWORD dwErrCode = ERROR_SUCCESS; - - // If there is hash table, we need to support multiple listfiles - // with different locales (BrooDat.mpq) - if(ha->pHashTable != NULL) - { - // If the archive is a malformed map, ignore too large listfiles - if(ha->dwFlags & MPQ_FLAG_MALFORMED) - dwMaxSize = 0x40000; - - pFirstHash = pHash = GetFirstHashEntry(ha, LISTFILE_NAME); - while(dwErrCode == ERROR_SUCCESS && pHash != NULL) - { - // Set the prefered locale to that from list file - SFileSetLocale(SFILE_MAKE_LCID(pHash->Locale, pHash->Platform)); - - // Add that listfile - dwErrCode = SFileAddArbitraryListFile(ha, hMpq, NULL, dwMaxSize); - - // Move to the next hash - pHash = GetNextHashEntry(ha, pFirstHash, pHash); - } - - // Restore the original locale - SFileSetLocale(lcSaveLocale); - } - else - { - // Add the single listfile - dwErrCode = SFileAddArbitraryListFile(ha, hMpq, NULL, dwMaxSize); - } - - // Return the result of the operation - return dwErrCode; -} - -static bool DoListFileSearch(TListFileCache * pCache, SFILE_FIND_DATA * lpFindFileData) -{ - // Check for the valid search handle - if(pCache != NULL) - { - char * szFileName; - size_t nLength = 0; - - // Get the next line - while((szFileName = ReadListFileLine(pCache, &nLength)) != NULL) - { - // Check search mask - if(nLength != 0 && SFileCheckWildCard(szFileName, pCache->szWildCard)) - { - if(nLength >= sizeof(lpFindFileData->cFileName)) - nLength = sizeof(lpFindFileData->cFileName) - 1; - - memcpy(lpFindFileData->cFileName, szFileName, nLength); - lpFindFileData->cFileName[nLength] = 0; - return true; - } - } - } - - // No more files - memset(lpFindFileData, 0, sizeof(SFILE_FIND_DATA)); - SetLastError(ERROR_NO_MORE_FILES); - return false; -} - -//----------------------------------------------------------------------------- -// File functions - -// Adds a listfile into the MPQ archive. -DWORD WINAPI SFileAddListFile(HANDLE hMpq, const TCHAR * szListFile) -{ - TMPQArchive * ha = (TMPQArchive *)hMpq; - DWORD dwErrCode = ERROR_SUCCESS; - - // Add the listfile for each MPQ in the patch chain - while(ha != NULL) - { - if(szListFile != NULL) - dwErrCode = SFileAddArbitraryListFile(ha, NULL, szListFile, MAX_LISTFILE_SIZE); - else - dwErrCode = SFileAddInternalListFile(ha, hMpq); - - // Also, add three special files to the listfile: - // (listfile) itself, (attributes) and (signature) - SListFileCreateNodeForAllLocales(ha, LISTFILE_NAME); - SListFileCreateNodeForAllLocales(ha, SIGNATURE_NAME); - SListFileCreateNodeForAllLocales(ha, ATTRIBUTES_NAME); - - // Move to the next archive in the chain - ha = ha->haPatch; - } - - return dwErrCode; -} - -//----------------------------------------------------------------------------- -// Enumerating files in listfile - -HANDLE WINAPI SListFileFindFirstFile(HANDLE hMpq, const TCHAR * szListFile, const char * szMask, SFILE_FIND_DATA * lpFindFileData) -{ - TListFileCache * pCache = NULL; - - // Initialize the structure with zeros - memset(lpFindFileData, 0, sizeof(SFILE_FIND_DATA)); - - // Open the local/internal listfile - pCache = CreateListFileCache(hMpq, szListFile, szMask, 0, 0); - if(pCache != NULL) - { - if(!DoListFileSearch(pCache, lpFindFileData)) - { - memset(lpFindFileData, 0, sizeof(SFILE_FIND_DATA)); - SetLastError(ERROR_NO_MORE_FILES); - FreeListFileCache(pCache); - pCache = NULL; - } - } - - // Return the listfile cache as handle - return (HANDLE)pCache; -} - -bool WINAPI SListFileFindNextFile(HANDLE hFind, SFILE_FIND_DATA * lpFindFileData) -{ - return DoListFileSearch((TListFileCache *)hFind, lpFindFileData); -} - -bool WINAPI SListFileFindClose(HANDLE hFind) -{ - TListFileCache * pCache = (TListFileCache *)hFind; - - return FreeListFileCache(pCache); -} - diff --git a/app/jni/src/libultraship/extern/StormLib/src/SFileOpenArchive.cpp b/app/jni/src/libultraship/extern/StormLib/src/SFileOpenArchive.cpp deleted file mode 100644 index 16e2491..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/SFileOpenArchive.cpp +++ /dev/null @@ -1,692 +0,0 @@ -/*****************************************************************************/ -/* SFileOpenArchive.cpp Copyright Ladislav Zezula 1999 */ -/* */ -/* Author : Ladislav Zezula */ -/* E-mail : ladik@zezula.net */ -/* WWW : www.zezula.net */ -/*---------------------------------------------------------------------------*/ -/* Implementation of archive functions */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* xx.xx.xx 1.00 Lad Created */ -/* 19.11.03 1.01 Dan Big endian handling */ -/*****************************************************************************/ - -#define __STORMLIB_SELF__ -#include "StormLib.h" -#include "StormCommon.h" - -#define HEADER_SEARCH_BUFFER_SIZE 0x1000 - -//----------------------------------------------------------------------------- -// Local functions - -static MTYPE CheckMapType(LPCTSTR szFileName, LPBYTE pbHeaderBuffer, size_t cbHeaderBuffer) -{ - LPDWORD HeaderInt32 = (LPDWORD)pbHeaderBuffer; - LPCTSTR szExtension; - - // Don't do any checks if there is not at least 16 bytes - if(cbHeaderBuffer > 0x10) - { - DWORD DwordValue0 = BSWAP_INT32_UNSIGNED(HeaderInt32[0]); - DWORD DwordValue1 = BSWAP_INT32_UNSIGNED(HeaderInt32[1]); - DWORD DwordValue2 = BSWAP_INT32_UNSIGNED(HeaderInt32[2]); - DWORD DwordValue3 = BSWAP_INT32_UNSIGNED(HeaderInt32[3]); - - // Check maps by extension (Starcraft, Starcraft II). We must do this before - // checking actual data, because the "NP_Protect" protector places - // fake Warcraft III header into the Starcraft II maps - if((szExtension = _tcsrchr(szFileName, _T('.'))) != NULL) - { - // Check for Starcraft II maps by extension - if(!_tcsicmp(szExtension, _T(".s2ma")) || !_tcsicmp(szExtension, _T(".SC2Map")) || !_tcsicmp(szExtension, _T(".SC2Mod"))) - { - return MapTypeStarcraft2; - } - - // Check for Starcraft I maps by extension - if(!_tcsicmp(szExtension, _T(".scm")) || !_tcsicmp(szExtension, _T(".scx"))) - { - return MapTypeStarcraft; - } - } - - // Test for AVI files (Warcraft III cinematics) - 'RIFF', 'AVI ' or 'LIST' - if(DwordValue0 == 0x46464952 && DwordValue2 == 0x20495641 && DwordValue3 == 0x5453494C) - return MapTypeAviFile; - - // Check for Warcraft III maps - if(DwordValue0 == 0x57334D48 && DwordValue1 == 0x00000000) - return MapTypeWarcraft3; - } - - // MIX files are DLL files that contain MPQ in overlay. - // Only Warcraft III is able to load them, so we consider them Warcraft III maps - if(cbHeaderBuffer > 0x200 && pbHeaderBuffer[0] == 'M' && pbHeaderBuffer[1] == 'Z') - { - // Check the value of IMAGE_DOS_HEADER::e_lfanew at offset 0x3C - if(0 < HeaderInt32[0x0F] && HeaderInt32[0x0F] < 0x10000) - return MapTypeWarcraft3; - } - - // No special map type recognized - return MapTypeNotRecognized; -} - -static bool IsStarcraftBetaArchive(TMPQHeader * pHeader) -{ - // The archive must be version 1, with a standard header size - if(pHeader->dwID == ID_MPQ && pHeader->dwHeaderSize == MPQ_HEADER_SIZE_V1) - { - // Check for known archive sizes - return (pHeader->dwArchiveSize == 0x00028FB3 || // patch_rt.mpq - pHeader->dwArchiveSize == 0x0351853D || // StarDat.mpq - pHeader->dwArchiveSize == 0x0AEC8960); // INSTALL.exe - - } - return false; -} - -static TMPQUserData * IsValidMpqUserData(ULONGLONG ByteOffset, ULONGLONG FileSize, void * pvUserData) -{ - TMPQUserData * pUserData; - - // BSWAP the source data and copy them to our buffer - BSWAP_ARRAY32_UNSIGNED(pvUserData, sizeof(TMPQUserData)); - pUserData = (TMPQUserData *)pvUserData; - - // Check the sizes - if(pUserData->cbUserDataHeader <= pUserData->cbUserDataSize && pUserData->cbUserDataSize <= pUserData->dwHeaderOffs) - { - // Move to the position given by the userdata - ByteOffset += pUserData->dwHeaderOffs; - - // The MPQ header should be within range of the file size - if((ByteOffset + MPQ_HEADER_SIZE_V1) < FileSize) - { - // Note: We should verify if there is the MPQ header. - // However, the header could be at any position below that - // that is multiplier of 0x200 - return (TMPQUserData *)pvUserData; - } - } - - return NULL; -} - -// This function gets the right positions of the hash table and the block table. -static DWORD VerifyMpqTablePositions(TMPQArchive * ha, ULONGLONG FileSize) -{ - TMPQHeader * pHeader = ha->pHeader; - ULONGLONG ByteOffset; - //bool bMalformed = (ha->dwFlags & MPQ_FLAG_MALFORMED) ? true : false; - - // Check the begin of HET table - if(pHeader->HetTablePos64) - { - ByteOffset = ha->MpqPos + pHeader->HetTablePos64; - if(ByteOffset > FileSize) - return ERROR_BAD_FORMAT; - } - - // Check the begin of BET table - if(pHeader->BetTablePos64) - { - ByteOffset = ha->MpqPos + pHeader->BetTablePos64; - if(ByteOffset > FileSize) - return ERROR_BAD_FORMAT; - } - - // Check the begin of hash table - if(pHeader->wHashTablePosHi || pHeader->dwHashTablePos) - { - ByteOffset = FileOffsetFromMpqOffset(ha, MAKE_OFFSET64(pHeader->wHashTablePosHi, pHeader->dwHashTablePos)); - if(ByteOffset > FileSize) - return ERROR_BAD_FORMAT; - } - - // Check the begin of block table - if(pHeader->wBlockTablePosHi || pHeader->dwBlockTablePos) - { - ByteOffset = FileOffsetFromMpqOffset(ha, MAKE_OFFSET64(pHeader->wBlockTablePosHi, pHeader->dwBlockTablePos)); - if(ByteOffset > FileSize) - return ERROR_BAD_FORMAT; - } - - // Check the begin of hi-block table - //if(pHeader->HiBlockTablePos64 != 0) - //{ - // ByteOffset = ha->MpqPos + pHeader->HiBlockTablePos64; - // if(ByteOffset > FileSize) - // return ERROR_BAD_FORMAT; - //} - - // All OK. - return ERROR_SUCCESS; -} - -//----------------------------------------------------------------------------- -// Support for alternate markers. Call before opening an archive - -#define SFILE_MARKERS_MIN_SIZE (sizeof(DWORD) + sizeof(DWORD) + sizeof(const char *) + sizeof(const char *)) - -bool WINAPI SFileSetArchiveMarkers(PSFILE_MARKERS pMarkers) -{ - // Check structure minimum size - if(pMarkers == NULL || pMarkers->dwSize < SFILE_MARKERS_MIN_SIZE) - { - SetLastError(ERROR_INVALID_PARAMETER); - return false; - } - - // Make sure that the MPQ cryptography is initialized at this time - InitializeMpqCryptography(); - - // Remember the marker for MPQ header - if(pMarkers->dwSignature != 0) - g_dwMpqSignature = pMarkers->dwSignature; - - // Remember the encryption key for hash table - if(pMarkers->szHashTableKey != NULL) - g_dwHashTableKey = HashString(pMarkers->szHashTableKey, MPQ_HASH_FILE_KEY); - - // Remember the encryption key for block table - if(pMarkers->szBlockTableKey != NULL) - g_dwBlockTableKey = HashString(pMarkers->szBlockTableKey, MPQ_HASH_FILE_KEY); - - // Succeeded - return true; -} - -//----------------------------------------------------------------------------- -// SFileGetLocale and SFileSetLocale -// Set the locale for all newly opened files - -LCID WINAPI SFileGetLocale() -{ - return g_lcFileLocale; -} - -LCID WINAPI SFileSetLocale(LCID lcFileLocale) -{ - return (g_lcFileLocale = lcFileLocale); -} - -//----------------------------------------------------------------------------- -// SFileOpenArchive -// -// szFileName - MPQ archive file name to open -// dwPriority - When SFileOpenFileEx called, this contains the search priority for searched archives -// dwFlags - See MPQ_OPEN_XXX in StormLib.h -// phMpq - Pointer to store open archive handle - -bool WINAPI SFileOpenArchive( - const TCHAR * szMpqName, - DWORD dwPriority, - DWORD dwFlags, - HANDLE * phMpq) -{ - TMPQUserData * pUserData; - TFileStream * pStream = NULL; // Open file stream - TMPQArchive * ha = NULL; // Archive handle - TFileEntry * pFileEntry; - ULONGLONG FileSize = 0; // Size of the file - LPBYTE pbHeaderBuffer = NULL; // Buffer for searching MPQ header - DWORD dwStreamFlags = (dwFlags & STREAM_FLAGS_MASK); - MTYPE MapType = MapTypeNotChecked; - DWORD dwErrCode = ERROR_SUCCESS; - - // Verify the parameters - if(szMpqName == NULL || *szMpqName == 0 || phMpq == NULL) - { - SetLastError(ERROR_INVALID_PARAMETER); - return false; - } - - // One time initialization of MPQ cryptography - InitializeMpqCryptography(); - dwPriority = dwPriority; - - // If not forcing MPQ v 1.0, also use file bitmap - dwStreamFlags |= (dwFlags & MPQ_OPEN_FORCE_MPQ_V1) ? 0 : STREAM_FLAG_USE_BITMAP; - - // Open the MPQ archive file - pStream = FileStream_OpenFile(szMpqName, dwStreamFlags); - if(pStream == NULL) - return false; - - // Check the file size. There must be at least 0x20 bytes - if(dwErrCode == ERROR_SUCCESS) - { - FileStream_GetSize(pStream, &FileSize); - if(FileSize < MPQ_HEADER_SIZE_V1) - dwErrCode = ERROR_BAD_FORMAT; - } - - // Allocate the MPQhandle - if(dwErrCode == ERROR_SUCCESS) - { - if((ha = STORM_ALLOC(TMPQArchive, 1)) == NULL) - dwErrCode = ERROR_NOT_ENOUGH_MEMORY; - } - - // Allocate buffer for searching MPQ header - if(dwErrCode == ERROR_SUCCESS) - { - pbHeaderBuffer = STORM_ALLOC(BYTE, HEADER_SEARCH_BUFFER_SIZE); - if(pbHeaderBuffer == NULL) - dwErrCode = ERROR_NOT_ENOUGH_MEMORY; - } - - // Find the position of MPQ header - if(dwErrCode == ERROR_SUCCESS) - { - ULONGLONG ByteOffset = 0; - ULONGLONG EndOfSearch = FileSize; - DWORD dwStrmFlags = 0; - DWORD dwHeaderSize; - DWORD dwHeaderID; - bool bSearchComplete = false; - - memset(ha, 0, sizeof(TMPQArchive)); - ha->dwValidFileFlags = MPQ_FILE_VALID_FLAGS; - ha->pfnHashString = HashStringSlash; - ha->pStream = pStream; - pStream = NULL; - - // Set the archive read only if the stream is read-only - FileStream_GetFlags(ha->pStream, &dwStrmFlags); - ha->dwFlags |= (dwStrmFlags & STREAM_FLAG_READ_ONLY) ? MPQ_FLAG_READ_ONLY : 0; - - // Also remember if we shall check sector CRCs when reading file - ha->dwFlags |= (dwFlags & MPQ_OPEN_CHECK_SECTOR_CRC) ? MPQ_FLAG_CHECK_SECTOR_CRC : 0; - - // Also remember if this MPQ is a patch - ha->dwFlags |= (dwFlags & MPQ_OPEN_PATCH) ? MPQ_FLAG_PATCH : 0; - - // Limit the header searching to about 130 MB of data - if(EndOfSearch > 0x08000000) - EndOfSearch = 0x08000000; - if(FileSize < HEADER_SEARCH_BUFFER_SIZE) - memset(pbHeaderBuffer, 0, HEADER_SEARCH_BUFFER_SIZE); - - // Find the offset of MPQ header within the file - while(bSearchComplete == false && ByteOffset < EndOfSearch) - { - // Always read at least 0x1000 bytes for performance. - // This is what Storm.dll (2002) does. - DWORD dwBytesAvailable = HEADER_SEARCH_BUFFER_SIZE; - - // Cut the bytes available, if needed - if((FileSize - ByteOffset) < HEADER_SEARCH_BUFFER_SIZE) - dwBytesAvailable = (DWORD)(FileSize - ByteOffset); - - // Read the eventual MPQ header - if(!FileStream_Read(ha->pStream, &ByteOffset, pbHeaderBuffer, dwBytesAvailable)) - { - dwErrCode = GetLastError(); - break; - } - - // Check whether the file is AVI file or a Warcraft III/Starcraft II map - if(MapType == MapTypeNotChecked) - { - // Do nothing if the file is an AVI file - if((MapType = CheckMapType(szMpqName, pbHeaderBuffer, dwBytesAvailable)) == MapTypeAviFile) - { - dwErrCode = ERROR_AVI_FILE; - break; - } - } - - // Search the header buffer - for(DWORD dwInBufferOffset = 0; dwInBufferOffset < dwBytesAvailable; dwInBufferOffset += 0x200) - { - // Copy the data from the potential header buffer to the MPQ header - memcpy(ha->HeaderData, pbHeaderBuffer + dwInBufferOffset, sizeof(ha->HeaderData)); - - // If there is the MPQ user data, process it - // Note that Warcraft III does not check for user data, which is abused by many map protectors - dwHeaderID = BSWAP_INT32_UNSIGNED(ha->HeaderData[0]); - if(MapType != MapTypeWarcraft3 && (dwFlags & MPQ_OPEN_FORCE_MPQ_V1) == 0) - { - if(ha->pUserData == NULL && dwHeaderID == ID_MPQ_USERDATA) - { - // Verify if this looks like a valid user data - pUserData = IsValidMpqUserData(ByteOffset, FileSize, ha->HeaderData); - if(pUserData != NULL) - { - // Fill the user data header - ha->UserDataPos = ByteOffset; - ha->pUserData = &ha->UserData; - memcpy(ha->pUserData, pUserData, sizeof(TMPQUserData)); - - // Continue searching from that position - ByteOffset += ha->pUserData->dwHeaderOffs; - break; - } - } - } - - // There must be MPQ header signature. Note that STORM.dll from Warcraft III actually - // tests the MPQ header size. It must be at least 0x20 bytes in order to load it - // Abused by Spazzler Map protector. Note that the size check is not present - // in Storm.dll v 1.00, so Diablo I code would load the MPQ anyway. - dwHeaderSize = BSWAP_INT32_UNSIGNED(ha->HeaderData[1]); - if(dwHeaderID == g_dwMpqSignature && dwHeaderSize >= MPQ_HEADER_SIZE_V1) - { - // Now convert the header to version 4 - dwErrCode = ConvertMpqHeaderToFormat4(ha, ByteOffset, FileSize, dwFlags, MapType); - if(dwErrCode != ERROR_FAKE_MPQ_HEADER) - { - bSearchComplete = true; - break; - } - } - - // Check for MPK archives (Longwu Online - MPQ fork) - if(MapType == MapTypeNotRecognized && dwHeaderID == ID_MPK) - { - // Now convert the MPK header to MPQ Header version 4 - dwErrCode = ConvertMpkHeaderToFormat4(ha, FileSize, dwFlags); - bSearchComplete = true; - break; - } - - // If searching for the MPQ header is disabled, return an error - if(dwFlags & MPQ_OPEN_NO_HEADER_SEARCH) - { - dwErrCode = ERROR_NOT_SUPPORTED; - bSearchComplete = true; - break; - } - - // Move the pointers - ByteOffset += 0x200; - } - } - - // Did we identify one of the supported headers? - if(dwErrCode == ERROR_SUCCESS) - { - // Set the user data position to the MPQ header, if none - if(ha->pUserData == NULL) - ha->UserDataPos = ByteOffset; - - // Set the position of the MPQ header - ha->pHeader = (TMPQHeader *)ha->HeaderData; - ha->MpqPos = ByteOffset; - ha->FileSize = FileSize; - - // Sector size must be nonzero. - if(ByteOffset >= FileSize || ha->pHeader->wSectorSize == 0) - dwErrCode = ERROR_BAD_FORMAT; - } - } - - // Fix table positions according to format - if(dwErrCode == ERROR_SUCCESS) - { - // Dump the header -// DumpMpqHeader(ha->pHeader); - - // W3x Map Protectors use the fact that War3's Storm.dll ignores the MPQ user data, - // and ignores the MPQ format version as well. The trick is to - // fake MPQ format 2, with an improper hi-word position of hash table and block table - // We can overcome such protectors by forcing opening the archive as MPQ v 1.0 - if(dwFlags & MPQ_OPEN_FORCE_MPQ_V1) - { - ha->pHeader->wFormatVersion = MPQ_FORMAT_VERSION_1; - ha->pHeader->dwHeaderSize = MPQ_HEADER_SIZE_V1; - ha->dwFlags |= MPQ_FLAG_READ_ONLY; - ha->pUserData = NULL; - } - - // Anti-overflow. If the hash table size in the header is - // higher than 0x10000000, it would overflow in 32-bit version - // Observed in the malformed Warcraft III maps - // Example map: MPQ_2016_v1_ProtectedMap_TableSizeOverflow.w3x - ha->pHeader->dwBlockTableSize = (ha->pHeader->dwBlockTableSize & BLOCK_INDEX_MASK); - ha->pHeader->dwHashTableSize = (ha->pHeader->dwHashTableSize & BLOCK_INDEX_MASK); - - // Both MPQ_OPEN_NO_LISTFILE or MPQ_OPEN_NO_ATTRIBUTES trigger read only mode - if(dwFlags & (MPQ_OPEN_NO_LISTFILE | MPQ_OPEN_NO_ATTRIBUTES)) - ha->dwFlags |= MPQ_FLAG_READ_ONLY; - - // Check if the caller wants to force adding listfile - if(dwFlags & MPQ_OPEN_FORCE_LISTFILE) - ha->dwFlags |= MPQ_FLAG_LISTFILE_FORCE; - - // StarDat.mpq from Starcraft I BETA: Enable special compression types - if(IsStarcraftBetaArchive(ha->pHeader)) - ha->dwFlags |= MPQ_FLAG_STARCRAFT_BETA; - - // Remember whether whis is a map for Warcraft III - if(MapType == MapTypeWarcraft3) - { - ha->dwValidFileFlags = MPQ_FILE_VALID_FLAGS_W3X; - ha->dwFlags |= MPQ_FLAG_WAR3_MAP; - } - - // If this is starcraft map, set the flag mask - if(MapType == MapTypeStarcraft) - ha->dwValidFileFlags = MPQ_FILE_VALID_FLAGS_SCX; - - // Set the size of file sector - ha->dwSectorSize = (0x200 << ha->pHeader->wSectorSize); - - // Verify if any of the tables doesn't start beyond the end of the file - dwErrCode = VerifyMpqTablePositions(ha, FileSize); - } - - // Read the hash table. Ignore the result, as hash table is no longer required - // Read HET table. Ignore the result, as HET table is no longer required - if(dwErrCode == ERROR_SUCCESS) - { - dwErrCode = LoadAnyHashTable(ha); - } - - // Now, build the file table. It will be built by combining - // the block table, BET table, hi-block table, (attributes) and (listfile). - if(dwErrCode == ERROR_SUCCESS) - { - dwErrCode = BuildFileTable(ha); - } - - // Load the internal listfile and include it to the file table - if(dwErrCode == ERROR_SUCCESS && (dwFlags & MPQ_OPEN_NO_LISTFILE) == 0) - { - // Quick check for (listfile) - pFileEntry = GetFileEntryLocale(ha, LISTFILE_NAME, LANG_NEUTRAL); - if(pFileEntry != NULL) - { - // Ignore result of the operation. (listfile) is optional. - SFileAddListFile((HANDLE)ha, NULL); - ha->dwFileFlags1 = pFileEntry->dwFlags; - } - } - - // Load the "(attributes)" file and merge it to the file table - if(dwErrCode == ERROR_SUCCESS && (dwFlags & MPQ_OPEN_NO_ATTRIBUTES) == 0 && (ha->dwFlags & MPQ_FLAG_BLOCK_TABLE_CUT) == 0) - { - // Quick check for (attributes) - pFileEntry = GetFileEntryLocale(ha, ATTRIBUTES_NAME, LANG_NEUTRAL); - if(pFileEntry != NULL) - { - // Ignore result of the operation. (attributes) is optional. - SAttrLoadAttributes(ha); - ha->dwFileFlags2 = pFileEntry->dwFlags; - } - } - - // Remember whether the archive has weak signature. Only for MPQs format 1.0. - if(dwErrCode == ERROR_SUCCESS) - { - // Quick check for (signature) - pFileEntry = GetFileEntryLocale(ha, SIGNATURE_NAME, LANG_NEUTRAL); - if(pFileEntry != NULL) - { - // Just remember that the archive is weak-signed - assert((pFileEntry->dwFlags & MPQ_FILE_EXISTS) != 0); - ha->dwFileFlags3 = pFileEntry->dwFlags; - } - - // Finally, set the MPQ_FLAG_READ_ONLY if the MPQ was found malformed - ha->dwFlags |= (ha->dwFlags & MPQ_FLAG_MALFORMED) ? MPQ_FLAG_READ_ONLY : 0; - } - - // Cleanup and exit - if(dwErrCode != ERROR_SUCCESS) - { - FileStream_Close(pStream); - FreeArchiveHandle(ha); - SetLastError(dwErrCode); - ha = NULL; - } - - // Free the header buffer - if(pbHeaderBuffer != NULL) - STORM_FREE(pbHeaderBuffer); - if(phMpq != NULL) - *phMpq = ha; - return (dwErrCode == ERROR_SUCCESS); -} - -//----------------------------------------------------------------------------- -// bool WINAPI SFileSetDownloadCallback(HANDLE, SFILE_DOWNLOAD_CALLBACK, void *); -// -// Sets a callback that is called when content is downloaded from the master MPQ -// - -bool WINAPI SFileSetDownloadCallback(HANDLE hMpq, SFILE_DOWNLOAD_CALLBACK DownloadCB, void * pvUserData) -{ - TMPQArchive * ha = (TMPQArchive *)hMpq; - - // Do nothing if 'hMpq' is bad parameter - if(!IsValidMpqHandle(hMpq)) - { - SetLastError(ERROR_INVALID_HANDLE); - return false; - } - - return FileStream_SetCallback(ha->pStream, DownloadCB, pvUserData); -} - -//----------------------------------------------------------------------------- -// bool SFileFlushArchive(HANDLE hMpq) -// -// Saves all dirty data into MPQ archive. -// Has similar effect like SFileCloseArchive, but the archive is not closed. -// Use on clients who keep MPQ archive open even for write operations, -// and terminating without calling SFileCloseArchive might corrupt the archive. -// - -bool WINAPI SFileFlushArchive(HANDLE hMpq) -{ - TMPQArchive * ha; - DWORD dwResultError = ERROR_SUCCESS; - DWORD dwErrCode; - - // Do nothing if 'hMpq' is bad parameter - if((ha = IsValidMpqHandle(hMpq)) == NULL) - { - SetLastError(ERROR_INVALID_HANDLE); - return false; - } - - // Only if the MPQ was changed - if(ha->dwFlags & MPQ_FLAG_CHANGED) - { - // Indicate that we are saving MPQ internal structures - ha->dwFlags |= MPQ_FLAG_SAVING_TABLES; - - // Defragment the file table. This will allow us to put the internal files to the end - DefragmentFileTable(ha); - - // - // Create each internal file - // Note that the (signature) file is usually before (listfile) in the file table - // - - if(ha->dwFlags & MPQ_FLAG_SIGNATURE_NEW) - { - dwErrCode = SSignFileCreate(ha); - if(dwErrCode != ERROR_SUCCESS) - dwResultError = dwErrCode; - } - - if(ha->dwFlags & (MPQ_FLAG_LISTFILE_NEW | MPQ_FLAG_LISTFILE_FORCE)) - { - dwErrCode = SListFileSaveToMpq(ha); - if(dwErrCode != ERROR_SUCCESS) - dwResultError = dwErrCode; - } - - if(ha->dwFlags & MPQ_FLAG_ATTRIBUTES_NEW) - { - dwErrCode = SAttrFileSaveToMpq(ha); - if(dwErrCode != ERROR_SUCCESS) - dwResultError = dwErrCode; - } - - // Save HET table, BET table, hash table, block table, hi-block table - if(ha->dwFlags & MPQ_FLAG_CHANGED) - { - // Rebuild the HET table - if(ha->pHetTable != NULL) - RebuildHetTable(ha); - - // Save all MPQ tables first - dwErrCode = SaveMPQTables(ha); - if(dwErrCode != ERROR_SUCCESS) - dwResultError = dwErrCode; - - // If the archive has weak signature, we need to finish it - if(ha->dwFileFlags3 != 0) - { - dwErrCode = SSignFileFinish(ha); - if(dwErrCode != ERROR_SUCCESS) - dwResultError = dwErrCode; - } - } - - // We are no longer saving internal MPQ structures - ha->dwFlags &= ~MPQ_FLAG_SAVING_TABLES; - } - - // Return the error - if(dwResultError != ERROR_SUCCESS) - SetLastError(dwResultError); - return (dwResultError == ERROR_SUCCESS); -} - -//----------------------------------------------------------------------------- -// bool SFileCloseArchive(HANDLE hMpq); -// - -bool WINAPI SFileCloseArchive(HANDLE hMpq) -{ - TMPQArchive * ha = IsValidMpqHandle(hMpq); - bool bResult = false; - - // Only if the handle is valid - if(ha == NULL) - { - SetLastError(ERROR_INVALID_HANDLE); - return false; - } - - // Invalidate the add file callback so it won't be called - // when saving (listfile) and (attributes) - ha->pfnAddFileCB = NULL; - ha->pvAddFileUserData = NULL; - - // Flush all unsaved data to the storage - bResult = SFileFlushArchive(hMpq); - - // Free all memory used by MPQ archive - FreeArchiveHandle(ha); - return bResult; -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/SFileOpenFileEx.cpp b/app/jni/src/libultraship/extern/StormLib/src/SFileOpenFileEx.cpp deleted file mode 100644 index 5dc2dbf..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/SFileOpenFileEx.cpp +++ /dev/null @@ -1,418 +0,0 @@ -/*****************************************************************************/ -/* SFileOpenFileEx.cpp Copyright (c) Ladislav Zezula 2003 */ -/*---------------------------------------------------------------------------*/ -/* Description : */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* xx.xx.99 1.00 Lad The first version of SFileOpenFileEx.cpp */ -/*****************************************************************************/ - -#define __STORMLIB_SELF__ -#include "StormLib.h" -#include "StormCommon.h" - -/*****************************************************************************/ -/* Local functions */ -/*****************************************************************************/ - -static DWORD FindHashIndex(TMPQArchive * ha, DWORD dwFileIndex) -{ - TMPQHash * pHashTableEnd; - TMPQHash * pHash; - DWORD dwFirstIndex = HASH_ENTRY_FREE; - - // Should only be called if the archive has hash table - assert(ha->pHashTable != NULL); - - // Multiple hash table entries can point to the file table entry. - // We need to search all of them - pHashTableEnd = ha->pHashTable + ha->pHeader->dwHashTableSize; - for(pHash = ha->pHashTable; pHash < pHashTableEnd; pHash++) - { - if(MPQ_BLOCK_INDEX(pHash) == dwFileIndex) - { - // Duplicate hash entry found - if(dwFirstIndex != HASH_ENTRY_FREE) - return HASH_ENTRY_FREE; - dwFirstIndex = (DWORD)(pHash - ha->pHashTable); - } - } - - // Return the hash table entry index - return dwFirstIndex; -} - -static const char * GetPatchFileName(TMPQArchive * ha, const char * szFileName, char * szBuffer) -{ - TMPQNamePrefix * pPrefix; - - // Are there patches in the current MPQ? - if(ha->dwFlags & MPQ_FLAG_PATCH) - { - // The patch prefix must be already known here - assert(ha->pPatchPrefix != NULL); - pPrefix = ha->pPatchPrefix; - - // The patch name for "OldWorld\\XXX\\YYY" is "Base\\XXX\YYY" - // We need to remove the "OldWorld\\" prefix - if(!_strnicmp(szFileName, "OldWorld\\", 9)) - szFileName += 9; - - // Create the file name from the known patch entry - memcpy(szBuffer, pPrefix->szPatchPrefix, pPrefix->nLength); - strcpy(szBuffer + pPrefix->nLength, szFileName); - szFileName = szBuffer; - } - - return szFileName; -} - -static bool OpenLocalFile(const char * szFileName, HANDLE * PtrFile) -{ - TFileStream * pStream; - TMPQFile * hf = NULL; - TCHAR szFileNameT[MAX_PATH]; - - // Convert the file name to UNICODE (if needed) - StringCopy(szFileNameT, _countof(szFileNameT), szFileName); - - // Open the file and create the TMPQFile structure - pStream = FileStream_OpenFile(szFileNameT, STREAM_FLAG_READ_ONLY); - if(pStream != NULL) - { - // Allocate and initialize file handle - hf = CreateFileHandle(NULL, NULL); - if(hf != NULL) - { - hf->pStream = pStream; - *PtrFile = hf; - return true; - } - else - { - FileStream_Close(pStream); - SetLastError(ERROR_NOT_ENOUGH_MEMORY); - } - } - *PtrFile = NULL; - return false; -} - -bool OpenPatchedFile(HANDLE hMpq, const char * szFileName, HANDLE * PtrFile) -{ - TMPQArchive * haBase = NULL; - TMPQArchive * ha = (TMPQArchive *)hMpq; - TFileEntry * pFileEntry; - TMPQFile * hfPatch; // Pointer to patch file - TMPQFile * hfBase = NULL; // Pointer to base open file - TMPQFile * hf = NULL; - HANDLE hPatchFile; - char szNameBuffer[MAX_PATH]; - - // First of all, find the latest archive where the file is in base version - // (i.e. where the original, unpatched version of the file exists) - while(ha != NULL) - { - // If the file is there, then we remember the archive - pFileEntry = GetFileEntryExact(ha, GetPatchFileName(ha, szFileName, szNameBuffer), 0, NULL); - if(pFileEntry != NULL && (pFileEntry->dwFlags & MPQ_FILE_PATCH_FILE) == 0) - haBase = ha; - - // Move to the patch archive - ha = ha->haPatch; - } - - // If we couldn't find the base file in any of the patches, it doesn't exist - if((ha = haBase) != NULL) - { - // Now open the base file - if(SFileOpenFileEx((HANDLE)ha, GetPatchFileName(ha, szFileName, szNameBuffer), SFILE_OPEN_BASE_FILE, (HANDLE *)&hfBase)) - { - // The file must be a base file, i.e. without MPQ_FILE_PATCH_FILE - assert((hfBase->pFileEntry->dwFlags & MPQ_FILE_PATCH_FILE) == 0); - hf = hfBase; - - // Now open all patches and attach them on top of the base file - for(ha = ha->haPatch; ha != NULL; ha = ha->haPatch) - { - // Prepare the file name with a correct prefix - if(SFileOpenFileEx((HANDLE)ha, GetPatchFileName(ha, szFileName, szNameBuffer), SFILE_OPEN_BASE_FILE, &hPatchFile)) - { - // Remember the new version - hfPatch = (TMPQFile *)hPatchFile; - - // We should not find patch file - assert((hfPatch->pFileEntry->dwFlags & MPQ_FILE_PATCH_FILE) != 0); - - // Attach the patch to the base file - hf->hfPatch = hfPatch; - hf = hfPatch; - } - } - } - } - else - { - SetLastError(ERROR_FILE_NOT_FOUND); - } - - // Give the updated base MPQ - if(PtrFile != NULL) - *PtrFile = (HANDLE)hfBase; - return (hfBase != NULL); -} - -/*****************************************************************************/ -/* Public functions */ -/*****************************************************************************/ - -//----------------------------------------------------------------------------- -// SFileEnumLocales enums all locale versions within MPQ. -// Functions fills all available language identifiers on a file into the buffer -// pointed by PtrFileLocales. There must be enough entries to copy the localed, -// otherwise the function returns ERROR_INSUFFICIENT_BUFFER. - -DWORD WINAPI SFileEnumLocales( - HANDLE hMpq, - const char * szFileName, - LCID * PtrFileLocales, - LPDWORD PtrMaxLocales, - DWORD dwSearchScope) -{ - TMPQArchive * ha = (TMPQArchive *)hMpq; - TMPQHash * pFirstHash; - TMPQHash * pHash; - DWORD dwFileIndex = 0; - DWORD dwMaxLocales; - DWORD dwLocales = 0; - - // Test the parameters - if(!IsValidMpqHandle(hMpq)) - return ERROR_INVALID_HANDLE; - if(szFileName == NULL || *szFileName == 0) - return ERROR_INVALID_PARAMETER; - if(ha->pHashTable == NULL) - return ERROR_NOT_SUPPORTED; - if(PtrMaxLocales == NULL) - return ERROR_INVALID_PARAMETER; - if(IsPseudoFileName(szFileName, &dwFileIndex)) - return ERROR_INVALID_PARAMETER; - - // Keep compiler happy - dwMaxLocales = PtrMaxLocales[0]; - dwSearchScope = dwSearchScope; - - // Parse all files with that name - pFirstHash = pHash = GetFirstHashEntry(ha, szFileName); - while(pHash != NULL) - { - // Put the locales to the buffer - if(PtrFileLocales != NULL && dwLocales < dwMaxLocales) - *PtrFileLocales++ = SFILE_MAKE_LCID(pHash->Locale, pHash->Platform); - dwLocales++; - - // Get the next locale - pHash = GetNextHashEntry(ha, pFirstHash, pHash); - } - - // Give the caller the number of locales and return - PtrMaxLocales[0] = dwLocales; - return (dwLocales <= dwMaxLocales) ? ERROR_SUCCESS : ERROR_INSUFFICIENT_BUFFER; -} - -//----------------------------------------------------------------------------- -// SFileOpenFileEx -// -// hMpq - Handle of opened MPQ archive -// szFileName - Name of file to open -// dwSearchScope - Where to search -// PtrFile - Pointer to store opened file handle - -bool WINAPI SFileOpenFileEx(HANDLE hMpq, const char * szFileName, DWORD dwSearchScope, HANDLE * PtrFile) -{ - TMPQArchive * ha = IsValidMpqHandle(hMpq); - TFileEntry * pFileEntry = NULL; - TMPQFile * hf = NULL; - DWORD dwHashIndex = HASH_ENTRY_FREE; - DWORD dwFileIndex = 0; - DWORD dwErrCode = ERROR_SUCCESS; - bool bOpenByIndex = false; - - // Don't accept NULL pointer to file handle - if(szFileName == NULL || *szFileName == 0) - dwErrCode = ERROR_INVALID_PARAMETER; - - // When opening a file from MPQ, the handle must be valid - if(dwSearchScope != SFILE_OPEN_LOCAL_FILE && ha == NULL) - dwErrCode = ERROR_INVALID_HANDLE; - - // When not checking for existence, the pointer to file handle must be valid - if(dwSearchScope != SFILE_OPEN_CHECK_EXISTS && PtrFile == NULL) - dwErrCode = ERROR_INVALID_PARAMETER; - - // Prepare the file opening - if(dwErrCode == ERROR_SUCCESS) - { - switch(dwSearchScope) - { - case SFILE_OPEN_FROM_MPQ: - case SFILE_OPEN_BASE_FILE: - case SFILE_OPEN_CHECK_EXISTS: - - // If this MPQ has no patches, open the file from this MPQ directly - if(ha->haPatch == NULL || dwSearchScope == SFILE_OPEN_BASE_FILE) - { - pFileEntry = GetFileEntryLocale(ha, szFileName, g_lcFileLocale, &dwHashIndex); - } - - // If this MPQ is a patched archive, open the file as patched - else - { - return OpenPatchedFile(hMpq, szFileName, PtrFile); - } - break; - - case SFILE_OPEN_ANY_LOCALE: - - // This open option is reserved for opening MPQ internal listfile. - // No argument validation. Tries to open file with neutral locale first, - // then any other available. - pFileEntry = GetFileEntryLocale(ha, szFileName, 0, &dwHashIndex); - break; - - case SFILE_OPEN_LOCAL_FILE: - - // Open a local file - return OpenLocalFile(szFileName, PtrFile); - - default: - - // Don't accept any other value - dwErrCode = ERROR_INVALID_PARAMETER; - break; - } - } - - // Check whether the file really exists in the MPQ - if(dwErrCode == ERROR_SUCCESS) - { - // If we didn't find the file, try to open it using pseudo file name ("File - if (pFileEntry == NULL || (pFileEntry->dwFlags & MPQ_FILE_EXISTS) == 0) - { - // Check the pseudo-file name ("File00000001.ext") - if ((bOpenByIndex = IsPseudoFileName(szFileName, &dwFileIndex)) == true) - { - // Get the file entry for the file - if (dwFileIndex < ha->dwFileTableSize) - { - pFileEntry = ha->pFileTable + dwFileIndex; - } - } - - // Still not found? - if (pFileEntry == NULL) - { - dwErrCode = ERROR_FILE_NOT_FOUND; - } - } - - // Perform some checks of invalid files - if (pFileEntry != NULL) - { - // MPQ protectors use insanely amount of fake files, often with very high size. - // We won't open any files whose compressed size is bigger than archive size - // If the file is not compressed, its size cannot be bigger than archive size - if ((pFileEntry->dwFlags & MPQ_FILE_COMPRESS_MASK) == 0 && (pFileEntry->dwFileSize > ha->FileSize)) - { - dwErrCode = ERROR_FILE_CORRUPT; - pFileEntry = NULL; - } - - // Ignore unknown loading flags (example: MPQ_2016_v1_WME4_4.w3x) -// if(pFileEntry->dwFlags & ~MPQ_FILE_VALID_FLAGS) -// { -// dwErrCode = ERROR_NOT_SUPPORTED; -// pFileEntry = NULL; -// } - } - } - - // Did the caller just wanted to know if the file exists? - if(dwErrCode == ERROR_SUCCESS && dwSearchScope != SFILE_OPEN_CHECK_EXISTS) - { - // Allocate file handle - hf = CreateFileHandle(ha, pFileEntry); - if(hf != NULL) - { - // Get the hash index for the file - if(ha->pHashTable != NULL && dwHashIndex == HASH_ENTRY_FREE) - dwHashIndex = FindHashIndex(ha, dwFileIndex); - if(dwHashIndex != HASH_ENTRY_FREE) - hf->pHashEntry = ha->pHashTable + dwHashIndex; - hf->dwHashIndex = dwHashIndex; - - // If the MPQ has sector CRC enabled, enable if for the file - if(ha->dwFlags & MPQ_FLAG_CHECK_SECTOR_CRC) - hf->bCheckSectorCRCs = true; - - // If we know the real file name, copy it to the file entry - if(bOpenByIndex == false) - { - // If there is no file name yet, allocate it - AllocateFileName(ha, pFileEntry, szFileName); - - // If the file is encrypted, we should detect the file key - if(pFileEntry->dwFlags & MPQ_FILE_ENCRYPTED) - { - hf->dwFileKey = DecryptFileKey(szFileName, - pFileEntry->ByteOffset, - pFileEntry->dwFileSize, - pFileEntry->dwFlags); - } - } - } - else - { - dwErrCode = ERROR_NOT_ENOUGH_MEMORY; - } - } - - // Give the file entry - if(PtrFile != NULL) - PtrFile[0] = hf; - - // Return error code - if(dwErrCode != ERROR_SUCCESS) - SetLastError(dwErrCode); - return (dwErrCode == ERROR_SUCCESS); -} - -//----------------------------------------------------------------------------- -// SFileHasFile -// -// hMpq - Handle of opened MPQ archive -// szFileName - Name of file to look for - -bool WINAPI SFileHasFile(HANDLE hMpq, const char * szFileName) -{ - return SFileOpenFileEx(hMpq, szFileName, SFILE_OPEN_CHECK_EXISTS, NULL); -} - -//----------------------------------------------------------------------------- -// bool WINAPI SFileCloseFile(HANDLE hFile); - -bool WINAPI SFileCloseFile(HANDLE hFile) -{ - TMPQFile * hf = (TMPQFile *)hFile; - - if(!IsValidFileHandle(hFile)) - { - SetLastError(ERROR_INVALID_HANDLE); - return false; - } - - // Free the structure - FreeFileHandle(hf); - return true; -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/SFilePatchArchives.cpp b/app/jni/src/libultraship/extern/StormLib/src/SFilePatchArchives.cpp deleted file mode 100644 index e5fe32b..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/SFilePatchArchives.cpp +++ /dev/null @@ -1,1175 +0,0 @@ -/*****************************************************************************/ -/* SFilePatchArchives.cpp Copyright (c) Ladislav Zezula 2010 */ -/*---------------------------------------------------------------------------*/ -/* Description: */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 18.08.10 1.00 Lad The first version of SFilePatchArchives.cpp */ -/*****************************************************************************/ - -#define __STORMLIB_SELF__ -#include "StormLib.h" -#include "StormCommon.h" - -//----------------------------------------------------------------------------- -// Local structures - -#define MAX_SC2_PATCH_PREFIX 0x80 - -#define PATCH_SIGNATURE_HEADER 0x48435450 -#define PATCH_SIGNATURE_MD5 0x5f35444d -#define PATCH_SIGNATURE_XFRM 0x4d524658 - -#define SIZE_OF_XFRM_HEADER 0x0C - -// Header for incremental patch files -typedef struct _MPQ_PATCH_HEADER -{ - //-- PATCH header ----------------------------------- - DWORD dwSignature; // 'PTCH' - DWORD dwSizeOfPatchData; // Size of the entire patch (decompressed) - DWORD dwSizeBeforePatch; // Size of the file before patch - DWORD dwSizeAfterPatch; // Size of file after patch - - //-- MD5 block -------------------------------------- - DWORD dwMD5; // 'MD5_' - DWORD dwMd5BlockSize; // Size of the MD5 block, including the signature and size itself - BYTE md5_before_patch[0x10]; // MD5 of the original (unpached) file - BYTE md5_after_patch[0x10]; // MD5 of the patched file - - //-- XFRM block ------------------------------------- - DWORD dwXFRM; // 'XFRM' - DWORD dwXfrmBlockSize; // Size of the XFRM block, includes XFRM header and patch data - DWORD dwPatchType; // Type of patch ('BSD0' or 'COPY') - - // Followed by the patch data -} MPQ_PATCH_HEADER, *PMPQ_PATCH_HEADER; - -typedef struct _BLIZZARD_BSDIFF40_FILE -{ - ULONGLONG Signature; - ULONGLONG CtrlBlockSize; - ULONGLONG DataBlockSize; - ULONGLONG NewFileSize; -} BLIZZARD_BSDIFF40_FILE, *PBLIZZARD_BSDIFF40_FILE; - -typedef struct _BSDIFF_CTRL_BLOCK -{ - DWORD dwAddDataLength; - DWORD dwMovDataLength; - DWORD dwOldMoveLength; - -} BSDIFF_CTRL_BLOCK, *PBSDIFF_CTRL_BLOCK; - -typedef struct _LOCALIZED_MPQ_INFO -{ - const char * szNameTemplate; // Name template - size_t nLangOffset; // Offset of the language - size_t nLength; // Length of the name template -} LOCALIZED_MPQ_INFO, *PLOCALIZED_MPQ_INFO; - -//----------------------------------------------------------------------------- -// Local variables - -// 4-byte groups for all languages -static const char * LanguageList = "baseteenenUSenGBenCNenTWdeDEesESesMXfrFRitITkoKRptBRptPTruRUzhCNzhTW"; - -// List of localized MPQs for World of Warcraft -static LOCALIZED_MPQ_INFO LocaleMpqs_WoW[] = -{ - {"expansion1-locale-####", 18, 22}, - {"expansion1-speech-####", 18, 22}, - {"expansion2-locale-####", 18, 22}, - {"expansion2-speech-####", 18, 22}, - {"expansion3-locale-####", 18, 22}, - {"expansion3-speech-####", 18, 22}, - {"locale-####", 7, 11}, - {"speech-####", 7, 11}, - {NULL, 0, 0} -}; - -//----------------------------------------------------------------------------- -// Local functions - -static inline bool IsPatchMetadataFile(TFileEntry * pFileEntry) -{ - // The file must ave a name - if(pFileEntry->szFileName != NULL && (pFileEntry->dwFlags & MPQ_FILE_PATCH_FILE) == 0) - { - // The file must be small - if(0 < pFileEntry->dwFileSize && pFileEntry->dwFileSize < 0x40) - { - // Compare the plain name - return (_stricmp(GetPlainFileName(pFileEntry->szFileName), PATCH_METADATA_NAME) == 0); - } - } - - // Not a patch_metadata - return false; -} - -static void Decompress_RLE(LPBYTE pbDecompressed, DWORD cbDecompressed, LPBYTE pbCompressed, DWORD cbCompressed) -{ - LPBYTE pbDecompressedEnd = pbDecompressed + cbDecompressed; - LPBYTE pbCompressedEnd = pbCompressed + cbCompressed; - BYTE RepeatCount; - BYTE OneByte; - - // Cut the initial DWORD from the compressed chunk - pbCompressed += sizeof(DWORD); - - // Pre-fill decompressed buffer with zeros - memset(pbDecompressed, 0, cbDecompressed); - - // Unpack - while(pbCompressed < pbCompressedEnd && pbDecompressed < pbDecompressedEnd) - { - OneByte = *pbCompressed++; - - // Is it a repetition byte ? - if(OneByte & 0x80) - { - RepeatCount = (OneByte & 0x7F) + 1; - for(BYTE i = 0; i < RepeatCount; i++) - { - if(pbDecompressed == pbDecompressedEnd || pbCompressed == pbCompressedEnd) - break; - - *pbDecompressed++ = *pbCompressed++; - } - } - else - { - pbDecompressed += (OneByte + 1); - } - } -} - -static DWORD LoadFilePatch_COPY(TMPQFile * hf, PMPQ_PATCH_HEADER pFullPatch) -{ - DWORD cbBytesToRead = pFullPatch->dwSizeOfPatchData - sizeof(MPQ_PATCH_HEADER); - DWORD cbBytesRead = 0; - - // Simply load the rest of the patch - SFileReadFile((HANDLE)hf, (pFullPatch + 1), cbBytesToRead, &cbBytesRead, NULL); - return (cbBytesRead == cbBytesToRead) ? ERROR_SUCCESS : ERROR_FILE_CORRUPT; -} - -static DWORD LoadFilePatch_BSD0(TMPQFile * hf, PMPQ_PATCH_HEADER pFullPatch) -{ - LPBYTE pbDecompressed = (LPBYTE)(pFullPatch + 1); - LPBYTE pbCompressed = NULL; - DWORD cbDecompressed = 0; - DWORD cbCompressed = 0; - DWORD dwBytesRead = 0; - DWORD dwErrCode = ERROR_SUCCESS; - - // Calculate the size of compressed data - cbDecompressed = pFullPatch->dwSizeOfPatchData - sizeof(MPQ_PATCH_HEADER); - cbCompressed = pFullPatch->dwXfrmBlockSize - SIZE_OF_XFRM_HEADER; - - // Is that file compressed? - if(cbCompressed < cbDecompressed) - { - pbCompressed = STORM_ALLOC(BYTE, cbCompressed); - if(pbCompressed == NULL) - dwErrCode = ERROR_NOT_ENOUGH_MEMORY; - - // Read the compressed patch data - if(dwErrCode == ERROR_SUCCESS) - { - SFileReadFile((HANDLE)hf, pbCompressed, cbCompressed, &dwBytesRead, NULL); - if(dwBytesRead != cbCompressed) - dwErrCode = ERROR_FILE_CORRUPT; - } - - // Decompress the data - if(dwErrCode == ERROR_SUCCESS) - Decompress_RLE(pbDecompressed, cbDecompressed, pbCompressed, cbCompressed); - - if(pbCompressed != NULL) - STORM_FREE(pbCompressed); - } - else - { - SFileReadFile((HANDLE)hf, pbDecompressed, cbDecompressed, &dwBytesRead, NULL); - if(dwBytesRead != cbDecompressed) - dwErrCode = ERROR_FILE_CORRUPT; - } - - return dwErrCode; -} - -static DWORD ApplyFilePatch_COPY( - TMPQPatcher * pPatcher, - PMPQ_PATCH_HEADER pFullPatch, - LPBYTE pbTarget, - LPBYTE pbSource) -{ - // Sanity checks - assert(pPatcher->cbMaxFileData >= pPatcher->cbFileData); - pFullPatch = pFullPatch; - - // Copy the patch data as-is - memcpy(pbTarget, pbSource, pPatcher->cbFileData); - return ERROR_SUCCESS; -} - -static DWORD ApplyFilePatch_BSD0( - TMPQPatcher * pPatcher, - PMPQ_PATCH_HEADER pFullPatch, - LPBYTE pbTarget, - LPBYTE pbSource) -{ - PBLIZZARD_BSDIFF40_FILE pBsdiff; - PBSDIFF_CTRL_BLOCK pCtrlBlock; - LPBYTE pbPatchData = (LPBYTE)(pFullPatch + 1); - LPBYTE pDataBlock; - LPBYTE pExtraBlock; - LPBYTE pbOldData = pbSource; - LPBYTE pbNewData = pbTarget; - DWORD dwCombineSize; - DWORD dwNewOffset = 0; // Current position to patch - DWORD dwOldOffset = 0; // Current source position - DWORD dwNewSize; // Patched file size - DWORD dwOldSize = pPatcher->cbFileData; // File size before patch - - // Get pointer to the patch header - // Format of BSDIFF header corresponds to original BSDIFF, which is: - // 0000 8 bytes signature "BSDIFF40" - // 0008 8 bytes size of the control block - // 0010 8 bytes size of the data block - // 0018 8 bytes new size of the patched file - pBsdiff = (PBLIZZARD_BSDIFF40_FILE)pbPatchData; - pbPatchData += sizeof(BLIZZARD_BSDIFF40_FILE); - - // Get pointer to the 32-bit BSDIFF control block - // The control block follows immediately after the BSDIFF header - // and consists of three 32-bit integers - // 0000 4 bytes Length to copy from the BSDIFF data block the new file - // 0004 4 bytes Length to copy from the BSDIFF extra block - // 0008 4 bytes Size to increment source file offset - pCtrlBlock = (PBSDIFF_CTRL_BLOCK)pbPatchData; - pbPatchData += (size_t)BSWAP_INT64_UNSIGNED(pBsdiff->CtrlBlockSize); - - // Get the pointer to the data block - pDataBlock = (LPBYTE)pbPatchData; - pbPatchData += (size_t)BSWAP_INT64_UNSIGNED(pBsdiff->DataBlockSize); - - // Get the pointer to the extra block - pExtraBlock = (LPBYTE)pbPatchData; - dwNewSize = (DWORD)BSWAP_INT64_UNSIGNED(pBsdiff->NewFileSize); - - // Now patch the file - while(dwNewOffset < dwNewSize) - { - DWORD dwAddDataLength = BSWAP_INT32_UNSIGNED(pCtrlBlock->dwAddDataLength); - DWORD dwMovDataLength = BSWAP_INT32_UNSIGNED(pCtrlBlock->dwMovDataLength); - DWORD dwOldMoveLength = BSWAP_INT32_UNSIGNED(pCtrlBlock->dwOldMoveLength); - DWORD i; - - // Sanity check - if((dwNewOffset + dwAddDataLength) > dwNewSize) - return ERROR_FILE_CORRUPT; - - // Read the diff string to the target buffer - memcpy(pbNewData + dwNewOffset, pDataBlock, dwAddDataLength); - pDataBlock += dwAddDataLength; - - // Get the longest block that we can combine - dwCombineSize = ((dwOldOffset + dwAddDataLength) >= dwOldSize) ? (dwOldSize - dwOldOffset) : dwAddDataLength; - if((dwNewOffset + dwCombineSize) > dwNewSize || (dwNewOffset + dwCombineSize) < dwNewOffset) - return ERROR_FILE_CORRUPT; - - // Now combine the patch data with the original file - for(i = 0; i < dwCombineSize; i++) - pbNewData[dwNewOffset + i] = pbNewData[dwNewOffset + i] + pbOldData[dwOldOffset + i]; - - // Move the offsets - dwNewOffset += dwAddDataLength; - dwOldOffset += dwAddDataLength; - - // Sanity check - if((dwNewOffset + dwMovDataLength) > dwNewSize) - return ERROR_FILE_CORRUPT; - - // Copy the data from the extra block in BSDIFF patch - memcpy(pbNewData + dwNewOffset, pExtraBlock, dwMovDataLength); - pExtraBlock += dwMovDataLength; - dwNewOffset += dwMovDataLength; - - // Move the old offset - if(dwOldMoveLength & 0x80000000) - dwOldMoveLength = 0x80000000 - dwOldMoveLength; - dwOldOffset += dwOldMoveLength; - pCtrlBlock++; - } - - // The size after patch must match - if(dwNewOffset != pFullPatch->dwSizeAfterPatch) - return ERROR_FILE_CORRUPT; - - // Update the new data size - pPatcher->cbFileData = dwNewOffset; - return ERROR_SUCCESS; -} - -static PMPQ_PATCH_HEADER LoadFullFilePatch(TMPQFile * hf, MPQ_PATCH_HEADER & PatchHeader) -{ - PMPQ_PATCH_HEADER pFullPatch; - DWORD dwErrCode = ERROR_SUCCESS; - - // BSWAP the entire header, if needed - BSWAP_ARRAY32_UNSIGNED(&PatchHeader, sizeof(DWORD) * 6); - BSWAP_ARRAY32_UNSIGNED(&PatchHeader.dwXFRM, sizeof(DWORD) * 3); - - // Verify the signatures in the patch header - if(PatchHeader.dwSignature != PATCH_SIGNATURE_HEADER || PatchHeader.dwMD5 != PATCH_SIGNATURE_MD5 || PatchHeader.dwXFRM != PATCH_SIGNATURE_XFRM) - return NULL; - - // Allocate space for patch header and compressed data - pFullPatch = (PMPQ_PATCH_HEADER)STORM_ALLOC(BYTE, PatchHeader.dwSizeOfPatchData); - if(pFullPatch != NULL) - { - // Copy the patch header - memcpy(pFullPatch, &PatchHeader, sizeof(MPQ_PATCH_HEADER)); - - // Read the patch, depending on patch type - if(dwErrCode == ERROR_SUCCESS) - { - switch(PatchHeader.dwPatchType) - { - case 0x59504f43: // 'COPY' - dwErrCode = LoadFilePatch_COPY(hf, pFullPatch); - break; - - case 0x30445342: // 'BSD0' - dwErrCode = LoadFilePatch_BSD0(hf, pFullPatch); - break; - - default: - dwErrCode = ERROR_FILE_CORRUPT; - break; - } - } - - // If something failed, free the patch buffer - if(dwErrCode != ERROR_SUCCESS) - { - STORM_FREE(pFullPatch); - pFullPatch = NULL; - } - } - - // Give the result to the caller - return pFullPatch; -} - -static DWORD ApplyFilePatch( - TMPQPatcher * pPatcher, - PMPQ_PATCH_HEADER pFullPatch) -{ - LPBYTE pbSource = (pPatcher->nCounter & 0x1) ? pPatcher->pbFileData2 : pPatcher->pbFileData1; - LPBYTE pbTarget = (pPatcher->nCounter & 0x1) ? pPatcher->pbFileData1 : pPatcher->pbFileData2; - DWORD dwErrCode; - - // Sanity checks - assert(pFullPatch->dwSizeAfterPatch <= pPatcher->cbMaxFileData); - - // Apply the patch according to the type - switch(pFullPatch->dwPatchType) - { - case 0x59504f43: // 'COPY' - dwErrCode = ApplyFilePatch_COPY(pPatcher, pFullPatch, pbTarget, pbSource); - break; - - case 0x30445342: // 'BSD0' - dwErrCode = ApplyFilePatch_BSD0(pPatcher, pFullPatch, pbTarget, pbSource); - break; - - default: - dwErrCode = ERROR_FILE_CORRUPT; - break; - } - - // Verify MD5 after patch - if(dwErrCode == ERROR_SUCCESS && pFullPatch->dwSizeAfterPatch != 0) - { - // Verify the patched file - if(!VerifyDataBlockHash(pbTarget, pFullPatch->dwSizeAfterPatch, pFullPatch->md5_after_patch)) - dwErrCode = ERROR_FILE_CORRUPT; - - // Copy the MD5 of the new block - memcpy(pPatcher->this_md5, pFullPatch->md5_after_patch, MD5_DIGEST_SIZE); - } - - return dwErrCode; -} - -//----------------------------------------------------------------------------- -// Local functions (patch prefix matching) - -static bool CreatePatchPrefix(TMPQArchive * ha, const char * szFileName, size_t nLength) -{ - TMPQNamePrefix * pNewPrefix; - - // If the length of the patch prefix was not entered, find it - // Not that the patch prefix must always begin with backslash - if(szFileName != NULL && nLength == 0) - nLength = strlen(szFileName); - - // Create the patch prefix - pNewPrefix = (TMPQNamePrefix *)STORM_ALLOC(BYTE, sizeof(TMPQNamePrefix) + nLength + 1); - if(pNewPrefix != NULL) - { - // Fill the name prefix. Also add the backslash - if(szFileName && nLength) - { - memcpy(pNewPrefix->szPatchPrefix, szFileName, nLength); - if(pNewPrefix->szPatchPrefix[nLength - 1] != '\\') - pNewPrefix->szPatchPrefix[nLength++] = '\\'; - } - - // Terminate the string and fill the length - pNewPrefix->szPatchPrefix[nLength] = 0; - pNewPrefix->nLength = nLength; - } - - ha->pPatchPrefix = pNewPrefix; - return (pNewPrefix != NULL); -} - -static bool CheckAndCreatePatchPrefix(TMPQArchive * ha, const char * szPatchPrefix, size_t nLength) -{ - char szTempName[MAX_SC2_PATCH_PREFIX + 0x41]; - bool bResult = false; - - // Prepare the patch file name - if(nLength > MAX_SC2_PATCH_PREFIX) - return false; - - // Prepare the patched file name - memcpy(szTempName, szPatchPrefix, nLength); - memcpy(&szTempName[nLength], "\\(patch_metadata)", 18); - - // Verifywhether that file exists - if(GetFileEntryLocale(ha, szTempName, 0) != NULL) - bResult = CreatePatchPrefix(ha, szPatchPrefix, nLength); - - return bResult; -} - -static bool IsMatchingPatchFile( - TMPQArchive * ha, - const char * szFileName, - LPBYTE pbBaseFileMd5) -{ - MPQ_PATCH_HEADER PatchHeader = {0}; - HANDLE hFile = NULL; - DWORD dwTransferred = 0; - DWORD dwFlags = 0; - bool bResult = false; - - // Open the file and load the patch header - if(SFileOpenFileEx((HANDLE)ha, szFileName, SFILE_OPEN_BASE_FILE, &hFile)) - { - // Retrieve the flags. We need to know whether the file is a patch or not - SFileGetFileInfo(hFile, SFileInfoFlags, &dwFlags, sizeof(DWORD), &dwTransferred); - if(dwFlags & MPQ_FILE_PATCH_FILE) - { - // Load the patch header - SFileReadFile(hFile, &PatchHeader, sizeof(MPQ_PATCH_HEADER), &dwTransferred, NULL); - BSWAP_ARRAY32_UNSIGNED(&PatchHeader, sizeof(DWORD) * 6); - - // If the file contains an incremental patch, - // compare the "MD5 before patching" with the base file MD5 - if(dwTransferred == sizeof(MPQ_PATCH_HEADER) && PatchHeader.dwSignature == PATCH_SIGNATURE_HEADER) - bResult = (!memcmp(PatchHeader.md5_before_patch, pbBaseFileMd5, MD5_DIGEST_SIZE)); - } - else - { - // TODO: How to match it if it's not an incremental patch? - // Example: StarCraft II\Updates\enGB\s2-update-enGB-23258.MPQ: - // Mods\Core.SC2Mod\enGB.SC2Assets\StreamingBuckets.txt" - bResult = false; - } - - // Close the file - SFileCloseFile(hFile); - } - - return bResult; -} - -static const char * FindArchiveLanguage(TMPQArchive * ha, PLOCALIZED_MPQ_INFO pMpqInfo) -{ - TFileEntry * pFileEntry; - const char * szLanguage = LanguageList; - char szFileName[0x40]; - - // Iterate through all localized languages - while(pMpqInfo->szNameTemplate != NULL) - { - // Iterate through all languages - for(szLanguage = LanguageList; szLanguage[0] != 0; szLanguage += 4) - { - // Construct the file name - memcpy(szFileName, pMpqInfo->szNameTemplate, pMpqInfo->nLength); - szFileName[pMpqInfo->nLangOffset + 0] = szLanguage[0]; - szFileName[pMpqInfo->nLangOffset + 1] = szLanguage[1]; - szFileName[pMpqInfo->nLangOffset + 2] = szLanguage[2]; - szFileName[pMpqInfo->nLangOffset + 3] = szLanguage[3]; - - // Append the suffix - memcpy(szFileName + pMpqInfo->nLength, "-md5.lst", 9); - - // Check whether the name exists - pFileEntry = GetFileEntryLocale(ha, szFileName, 0); - if(pFileEntry != NULL) - return szLanguage; - } - - // Move to the next language name - pMpqInfo++; - } - - // Not found - return NULL; -} - -//----------------------------------------------------------------------------- -// Finding ratch prefix for an temporary build of WoW (Pre-Cataclysm) - -static bool FindPatchPrefix_WoW_13164_13623(TMPQArchive * haBase, TMPQArchive * haPatch) -{ - const char * szPatchPrefix; - char szNamePrefix[0x08]; - - // Try to find the language of the MPQ archive - szPatchPrefix = FindArchiveLanguage(haBase, LocaleMpqs_WoW); - if(szPatchPrefix == NULL) - szPatchPrefix = "Base"; - - // Format the patch prefix - szNamePrefix[0] = szPatchPrefix[0]; - szNamePrefix[1] = szPatchPrefix[1]; - szNamePrefix[2] = szPatchPrefix[2]; - szNamePrefix[3] = szPatchPrefix[3]; - szNamePrefix[4] = '\\'; - szNamePrefix[5] = 0; - return CreatePatchPrefix(haPatch, szNamePrefix, 5); -} - -//----------------------------------------------------------------------------- -// Finding patch prefix for Starcraft II (Pre-Legacy of the Void) - -// -// This method tries to match the patch by placement of the archive (in the game subdirectory) -// -// Archive Path: %GAME_DIR%\Mods\SwarmMulti.SC2Mod\Base.SC2Data -// Patch Prefix: Mods\SwarmMulti.SC2Mod\Base.SC2Data -// -// Archive Path: %ANY_DIR%\MPQ_2013_v4_Mods#Liberty.SC2Mod#enGB.SC2Data -// Patch Prefix: Mods\Liberty.SC2Mod\enGB.SC2Data -// - -static bool CheckPatchPrefix_SC2_ArchiveName( - TMPQArchive * haPatch, - const TCHAR * szPathPtr, - const TCHAR * szSeparator, - const TCHAR * szPathEnd, - const TCHAR * szExpectedString, - size_t cchExpectedString) -{ - char szPatchPrefix[MAX_SC2_PATCH_PREFIX+0x41]; - size_t nLength = 0; - bool bResult = false; - - // Check whether the length is equal to the length of the expected string - if((size_t)(szSeparator - szPathPtr) == cchExpectedString) - { - // Now check the string itself - if(!_tcsnicmp(szPathPtr, szExpectedString, szSeparator - szPathPtr)) - { - // Copy the name string - for(; szPathPtr < szPathEnd; szPathPtr++) - { - if(szPathPtr[0] != _T('/') && szPathPtr[0] != _T('#')) - szPatchPrefix[nLength++] = (char)szPathPtr[0]; - else - szPatchPrefix[nLength++] = '\\'; - } - - // Check and create the patch prefix - bResult = CheckAndCreatePatchPrefix(haPatch, szPatchPrefix, nLength); - } - } - - return bResult; -} - -static bool FindPatchPrefix_SC2_ArchiveName(TMPQArchive * haBase, TMPQArchive * haPatch) -{ - const TCHAR * szPathBegin = FileStream_GetFileName(haBase->pStream); - const TCHAR * szSeparator = NULL; - const TCHAR * szPathEnd = szPathBegin + _tcslen(szPathBegin); - const TCHAR * szPathPtr; - int nSlashCount = 0; - int nDotCount = 0; - - // Skip the part where the patch prefix would be too long - if((szPathEnd - szPathBegin) > MAX_SC2_PATCH_PREFIX) - szPathBegin = szPathEnd - MAX_SC2_PATCH_PREFIX; - - // Search for the file extension - for(szPathPtr = szPathEnd; szPathPtr > szPathBegin; szPathPtr--) - { - if(szPathPtr[0] == _T('.')) - { - nDotCount++; - break; - } - } - - // Search for the possible begin of the prefix name - for(/* NOTHING */; szPathPtr > szPathBegin; szPathPtr--) - { - // Check the slashes, backslashes and hashes - if(szPathPtr[0] == _T('\\') || szPathPtr[0] == _T('/') || szPathPtr[0] == _T('#')) - { - if(nDotCount == 0) - return false; - szSeparator = szPathPtr; - nSlashCount++; - } - - // Check the path parts - if(szSeparator != NULL && nSlashCount >= nDotCount) - { - if(CheckPatchPrefix_SC2_ArchiveName(haPatch, szPathPtr, szSeparator, szPathEnd, _T("Battle.net"), 10)) - return true; - if(CheckPatchPrefix_SC2_ArchiveName(haPatch, szPathPtr, szSeparator, szPathEnd, _T("Campaigns"), 9)) - return true; - if(CheckPatchPrefix_SC2_ArchiveName(haPatch, szPathPtr, szSeparator, szPathEnd, _T("Mods"), 4)) - return true; - } - } - - // Not matched, sorry - return false; -} - -// -// This method tries to read the patch prefix from a helper file -// -// Example -// ========================================================= -// MPQ File Name: MPQ_2013_v4_Base1.SC2Data -// Helper File : MPQ_2013_v4_Base1.SC2Data-PATCH -// File Contains: PatchPrefix=Mods\Core.SC2Mod\Base.SC2Data -// Patch Prefix : Mods\Core.SC2Mod\Base.SC2Data -// - -static bool ExtractPatchPrefixFromFile(const TCHAR * szHelperFile, char * szPatchPrefix, size_t nMaxChars, size_t * PtrLength) -{ - TFileStream * pStream; - ULONGLONG FileSize = 0; - size_t nLength; - char szFileData[MAX_PATH+1]; - bool bResult = false; - - pStream = FileStream_OpenFile(szHelperFile, STREAM_FLAG_READ_ONLY); - if(pStream != NULL) - { - // Retrieve and check the file size - FileStream_GetSize(pStream, &FileSize); - if(12 <= FileSize && FileSize < MAX_PATH) - { - // Read the entire file to memory - if(FileStream_Read(pStream, NULL, szFileData, (DWORD)FileSize)) - { - // Terminate the buffer with zero - szFileData[(DWORD)FileSize] = 0; - - // The file data must begin with the "PatchPrefix" variable - if(!_strnicmp(szFileData, "PatchPrefix", 11)) - { - char * szLinePtr = szFileData + 11; - char * szLineEnd; - - // Skip spaces or '=' - while(szLinePtr[0] == ' ' || szLinePtr[0] == '=') - szLinePtr++; - szLineEnd = szLinePtr; - - // Find the end - while(szLineEnd[0] != 0 && szLineEnd[0] != 0x0A && szLineEnd[0] != 0x0D) - szLineEnd++; - nLength = (size_t)(szLineEnd - szLinePtr); - - // Copy the variable - if(szLineEnd > szLinePtr && nLength <= nMaxChars) - { - memcpy(szPatchPrefix, szLinePtr, nLength); - szPatchPrefix[nLength] = 0; - PtrLength[0] = nLength; - bResult = true; - } - } - } - } - - // Close the stream - FileStream_Close(pStream); - } - - return bResult; -} - - -static bool FindPatchPrefix_SC2_HelperFile(TMPQArchive * haBase, TMPQArchive * haPatch) -{ - TCHAR szHelperFile[MAX_PATH+1]; - char szPatchPrefix[MAX_SC2_PATCH_PREFIX+0x41]; - size_t nLength = 0; - bool bResult = false; - - // Create the name of the patch helper file - _tcscpy(szHelperFile, FileStream_GetFileName(haBase->pStream)); - if(_tcslen(szHelperFile) + 6 > MAX_PATH) - return false; - _tcscat(szHelperFile, _T("-PATCH")); - - // Open the patch helper file and read the line - if(ExtractPatchPrefixFromFile(szHelperFile, szPatchPrefix, MAX_SC2_PATCH_PREFIX, &nLength)) - bResult = CheckAndCreatePatchPrefix(haPatch, szPatchPrefix, nLength); - - return bResult; -} - -// -// Find match in Starcraft II patch MPQs -// Match a LST file in the root directory if the MPQ with any of the file in subdirectories -// -// The problem: -// File in the base MPQ: enGB-md5.lst -// File in the patch MPQ: Campaigns\Liberty.SC2Campaign\enGB.SC2Assets\enGB-md5.lst -// Campaigns\Liberty.SC2Campaign\enGB.SC2Data\enGB-md5.lst -// Campaigns\LibertyStory.SC2Campaign\enGB.SC2Data\enGB-md5.lst -// Campaigns\LibertyStory.SC2Campaign\enGB.SC2Data\enGB-md5.lst Mods\Core.SC2Mod\enGB.SC2Assets\enGB-md5.lst -// Mods\Core.SC2Mod\enGB.SC2Data\enGB-md5.lst -// Mods\Liberty.SC2Mod\enGB.SC2Assets\enGB-md5.lst -// Mods\Liberty.SC2Mod\enGB.SC2Data\enGB-md5.lst -// Mods\LibertyMulti.SC2Mod\enGB.SC2Data\enGB-md5.lst -// -// Solution: -// We need to match the file by its MD5 -// - -static bool FindPatchPrefix_SC2_MatchFiles(TMPQArchive * haBase, TMPQArchive * haPatch, TFileEntry * pBaseEntry) -{ - TMPQNamePrefix * pPatchPrefix; - char * szPatchFileName; - char * szPlainName; - size_t cchWorkBuffer = 0x400; - bool bResult = false; - - // First-level patches: Find the same file within the patch archive - // and verify by MD5-before-patch - if(haBase->haPatch == NULL) - { - TFileEntry * pFileTableEnd = haPatch->pFileTable + haPatch->dwFileTableSize; - TFileEntry * pFileEntry; - - // Allocate working buffer for merging LST file - szPatchFileName = STORM_ALLOC(char, cchWorkBuffer); - if(szPatchFileName != NULL) - { - // Parse the entire file table - for(pFileEntry = haPatch->pFileTable; pFileEntry < pFileTableEnd; pFileEntry++) - { - // Look for "patch_metadata" file - if(IsPatchMetadataFile(pFileEntry)) - { - // Construct the name of the MD5 file - strcpy(szPatchFileName, pFileEntry->szFileName); - szPlainName = (char *)GetPlainFileName(szPatchFileName); - strcpy(szPlainName, pBaseEntry->szFileName); - - // Check for matching MD5 file - if(IsMatchingPatchFile(haPatch, szPatchFileName, pBaseEntry->md5)) - { - bResult = CreatePatchPrefix(haPatch, szPatchFileName, (size_t)(szPlainName - szPatchFileName)); - break; - } - } - } - - // Delete the merge buffer - STORM_FREE(szPatchFileName); - } - } - - // For second-level patches, just take the patch prefix from the lower level patch - else - { - // There must be at least two patches in the chain - assert(haBase->haPatch->pPatchPrefix != NULL); - pPatchPrefix = haBase->haPatch->pPatchPrefix; - - // Copy the patch prefix - bResult = CreatePatchPrefix(haPatch, - pPatchPrefix->szPatchPrefix, - pPatchPrefix->nLength); - } - - return bResult; -} - -// Note: pBaseEntry is the file entry of the base version of "StreamingBuckets.txt" -static bool FindPatchPrefix_SC2(TMPQArchive * haBase, TMPQArchive * haPatch, TFileEntry * pBaseEntry) -{ - // Method 1: Try it by the placement of the archive. - // Works when someone is opening an archive in the game (sub)directory - if(FindPatchPrefix_SC2_ArchiveName(haBase, haPatch)) - return true; - - // Method 2: Try to locate the Name.Ext-PATCH file and read the patch prefix from it - if(FindPatchPrefix_SC2_HelperFile(haBase, haPatch)) - return true; - - // Method 3: Try to pair any version of "StreamingBuckets.txt" from the patch MPQ - // with the "StreamingBuckets.txt" in the base MPQ. Does not always work - if(FindPatchPrefix_SC2_MatchFiles(haBase, haPatch, pBaseEntry)) - return true; - - return false; -} - -// -// Patch prefix is the path subdirectory where the patched files are within MPQ. -// -// Example 1: -// Main MPQ: locale-enGB.MPQ -// Patch MPQ: wow-update-12694.MPQ -// File in main MPQ: DBFilesClient\Achievement.dbc -// File in patch MPQ: enGB\DBFilesClient\Achievement.dbc -// Path prefix: enGB -// -// Example 2: -// Main MPQ: expansion1.MPQ -// Patch MPQ: wow-update-12694.MPQ -// File in main MPQ: DBFilesClient\Achievement.dbc -// File in patch MPQ: Base\DBFilesClient\Achievement.dbc -// Path prefix: Base -// -// Example 3: -// Main MPQ: %GAME%\Battle.net\Battle.net.MPQ -// Patch MPQ: s2-update-base-26147.MPQ -// File in main MPQ: Battle.net\i18n\deDE\String\CLIENT_ACHIEVEMENTS.xml -// File in patch MPQ: Battle.net\Battle.net.MPQ\Battle.net\i18n\deDE\String\CLIENT_ACHIEVEMENTS.xml -// Path prefix: Battle.net\Battle.net.MPQ -// -// Example 4: -// Main MPQ: %GAME%\Campaigns\Liberty.SC2Campaign\enGB.SC2Data -// *OR* %ANY_DIR%\%ANY_NAME%Campaigns#Liberty.SC2Campaign#enGB.SC2Data -// Patch MPQ: s2-update-enGB-23258.MPQ -// File in main MPQ: LocalizedData\GameHotkeys.txt -// File in patch MPQ: Campaigns\Liberty.SC2Campaign\enGB.SC2Data\LocalizedData\GameHotkeys.txt -// Patch Prefix: Campaigns\Liberty.SC2Campaign\enGB.SC2Data -// - -static bool FindPatchPrefix(TMPQArchive * haBase, TMPQArchive * haPatch, const char * szPatchPathPrefix) -{ - TFileEntry * pFileEntry; - - // If the patch prefix was explicitly entered, we use that one - if(szPatchPathPrefix != NULL) - return CreatePatchPrefix(haPatch, szPatchPathPrefix, 0); - - // Patches for World of Warcraft - they mostly do not use prefix. - // All patches that use patch prefix have the "base\\(patch_metadata) file present - if(GetFileEntryLocale(haPatch, "base\\" PATCH_METADATA_NAME, 0)) - return FindPatchPrefix_WoW_13164_13623(haBase, haPatch); - - // Updates for Starcraft II - // Match: LocalizedData\GameHotkeys.txt <==> Campaigns\Liberty.SC2Campaign\enGB.SC2Data\LocalizedData\GameHotkeys.txt - // All Starcraft II base archives seem to have the file "StreamingBuckets.txt" present - pFileEntry = GetFileEntryLocale(haBase, "StreamingBuckets.txt", 0); - if(pFileEntry != NULL) - return FindPatchPrefix_SC2(haBase, haPatch, pFileEntry); - - // Diablo III patch MPQs don't use patch prefix - // Hearthstone MPQs don't use patch prefix - CreatePatchPrefix(haPatch, NULL, 0); - return true; -} - -//----------------------------------------------------------------------------- -// Public functions (StormLib internals) - -bool IsIncrementalPatchFile(const void * pvData, DWORD cbData, LPDWORD pdwPatchedFileSize) -{ - PMPQ_PATCH_HEADER pPatchHeader = (PMPQ_PATCH_HEADER)pvData; - BLIZZARD_BSDIFF40_FILE DiffFile; - DWORD dwPatchType; - - if(cbData >= sizeof(MPQ_PATCH_HEADER) + sizeof(BLIZZARD_BSDIFF40_FILE)) - { - dwPatchType = BSWAP_INT32_UNSIGNED(pPatchHeader->dwPatchType); - if(dwPatchType == 0x30445342) - { - // Give the caller the patch file size - if(pdwPatchedFileSize != NULL) - { - Decompress_RLE((LPBYTE)&DiffFile, sizeof(BLIZZARD_BSDIFF40_FILE), (LPBYTE)(pPatchHeader + 1), sizeof(BLIZZARD_BSDIFF40_FILE)); - DiffFile.NewFileSize = BSWAP_INT64_UNSIGNED(DiffFile.NewFileSize); - *pdwPatchedFileSize = (DWORD)DiffFile.NewFileSize; - return true; - } - } - } - - return false; -} - -DWORD Patch_InitPatcher(TMPQPatcher * pPatcher, TMPQFile * hf) -{ - DWORD cbMaxFileData = 0; - - // Overflow check - if((cbMaxFileData + (DWORD)sizeof(MPQ_PATCH_HEADER)) < cbMaxFileData) - return ERROR_NOT_ENOUGH_MEMORY; - if(hf->hfPatch == NULL) - return ERROR_INVALID_PARAMETER; - - // Initialize the entire structure with zeros - memset(pPatcher, 0, sizeof(TMPQPatcher)); - - // Copy the MD5 of the current file - memcpy(pPatcher->this_md5, hf->pFileEntry->md5, MD5_DIGEST_SIZE); - - // Find out the biggest data size needed during the patching process - while(hf != NULL) - { - if(hf->pFileEntry->dwFileSize > cbMaxFileData) - cbMaxFileData = hf->pFileEntry->dwFileSize; - hf = hf->hfPatch; - } - - // Allocate primary and secondary buffer - pPatcher->pbFileData1 = STORM_ALLOC(BYTE, cbMaxFileData); - pPatcher->pbFileData2 = STORM_ALLOC(BYTE, cbMaxFileData); - if(!pPatcher->pbFileData1 || !pPatcher->pbFileData2) - return ERROR_NOT_ENOUGH_MEMORY; - - pPatcher->cbMaxFileData = cbMaxFileData; - return ERROR_SUCCESS; -} - -// -// Note: The patch may either be applied to the base file or to the previous version -// In Starcraft II, Mods\Core.SC2Mod\Base.SC2Data, file StreamingBuckets.txt: -// -// Base file MD5: 31376b0344b6df59ad009d4296125539 -// -// s2-update-base-23258: from 31376b0344b6df59ad009d4296125539 to 941a82683452e54bf024a8d491501824 -// s2-update-base-24540: from 31376b0344b6df59ad009d4296125539 to 941a82683452e54bf024a8d491501824 -// s2-update-base-26147: from 31376b0344b6df59ad009d4296125539 to d5d5253c762fac6b9761240288a0771a -// s2-update-base-28522: from 31376b0344b6df59ad009d4296125539 to 5a76c4b356920aab7afd22e0e1913d7a -// s2-update-base-30508: from 31376b0344b6df59ad009d4296125539 to 8cb0d4799893fe801cc78ae4488a3671 -// s2-update-base-32283: from 31376b0344b6df59ad009d4296125539 to 8cb0d4799893fe801cc78ae4488a3671 -// -// We don't keep all intermediate versions in memory, as it would cause massive -// memory usage during patching process. A prime example is the file -// DBFilesClient\\Item-Sparse.db2 from locale-enGB.MPQ (WoW 16965), which has -// 9 patches in a row, each requiring 70 MB memory (35 MB patch data + 35 MB work buffer) -// - -DWORD Patch_Process(TMPQPatcher * pPatcher, TMPQFile * hf) -{ - PMPQ_PATCH_HEADER pFullPatch; - MPQ_PATCH_HEADER PatchHeader1; - MPQ_PATCH_HEADER PatchHeader2 = {0}; - TMPQFile * hfBase = hf; - DWORD cbBytesRead = 0; - DWORD dwErrCode = ERROR_SUCCESS; - - // Move to the first patch - assert(hfBase->pbFileData == NULL); - assert(hfBase->cbFileData == 0); - hf = hf->hfPatch; - - // Read the header of the current patch - SFileReadFile((HANDLE)hf, &PatchHeader1, sizeof(MPQ_PATCH_HEADER), &cbBytesRead, NULL); - if(cbBytesRead != sizeof(MPQ_PATCH_HEADER)) - return ERROR_FILE_CORRUPT; - - // Perform the patching process - while(dwErrCode == ERROR_SUCCESS && hf != NULL) - { - // Try to read the next patch header. If the md5_before_patch - // still matches we go directly to the next one and repeat - while(hf->hfPatch != NULL) - { - // Attempt to read the patch header - SFileReadFile((HANDLE)hf->hfPatch, &PatchHeader2, sizeof(MPQ_PATCH_HEADER), &cbBytesRead, NULL); - if(cbBytesRead != sizeof(MPQ_PATCH_HEADER)) - return ERROR_FILE_CORRUPT; - - // Compare the md5_before_patch - if(memcmp(PatchHeader2.md5_before_patch, pPatcher->this_md5, MD5_DIGEST_SIZE)) - break; - - // Move one patch fuhrter - PatchHeader1 = PatchHeader2; - hf = hf->hfPatch; - } - - // Allocate memory for the patch data - pFullPatch = LoadFullFilePatch(hf, PatchHeader1); - if(pFullPatch != NULL) - { - // Apply the patch - dwErrCode = ApplyFilePatch(pPatcher, pFullPatch); - STORM_FREE(pFullPatch); - } - else - { - dwErrCode = ERROR_FILE_CORRUPT; - } - - // Move to the next patch - PatchHeader1 = PatchHeader2; - pPatcher->nCounter++; - hf = hf->hfPatch; - } - - // Put the result data to the file structure - if(dwErrCode == ERROR_SUCCESS) - { - // Swap the pointer to the file data structure - if(pPatcher->nCounter & 0x01) - { - hfBase->pbFileData = pPatcher->pbFileData2; - pPatcher->pbFileData2 = NULL; - } - else - { - hfBase->pbFileData = pPatcher->pbFileData1; - pPatcher->pbFileData1 = NULL; - } - - // Also supply the data size - hfBase->cbFileData = pPatcher->cbFileData; - } - - return ERROR_SUCCESS; -} - -void Patch_Finalize(TMPQPatcher * pPatcher) -{ - if(pPatcher != NULL) - { - if(pPatcher->pbFileData1 != NULL) - STORM_FREE(pPatcher->pbFileData1); - if(pPatcher->pbFileData2 != NULL) - STORM_FREE(pPatcher->pbFileData2); - - memset(pPatcher, 0, sizeof(TMPQPatcher)); - } -} - - -//----------------------------------------------------------------------------- -// Public functions - -bool WINAPI SFileOpenPatchArchive( - HANDLE hMpq, - const TCHAR * szPatchMpqName, - const char * szPatchPathPrefix, - DWORD dwFlags) -{ - TMPQArchive * haPatch; - TMPQArchive * ha = (TMPQArchive *)hMpq; - HANDLE hPatchMpq = NULL; - DWORD dwErrCode = ERROR_SUCCESS; - - // Keep compiler happy - dwFlags = dwFlags; - - // Verify input parameters - if(!IsValidMpqHandle(hMpq)) - dwErrCode = ERROR_INVALID_HANDLE; - if(szPatchMpqName == NULL || *szPatchMpqName == 0) - dwErrCode = ERROR_INVALID_PARAMETER; - - // - // We don't allow adding patches to archives that have been open for write - // - // Error scenario: - // - // 1) Open archive for writing - // 2) Modify or replace a file - // 3) Add patch archive to the opened MPQ - // 4) Read patched file - // 5) Now what ? - // - - if(dwErrCode == ERROR_SUCCESS) - { - if(!(ha->dwFlags & MPQ_FLAG_READ_ONLY)) - dwErrCode = ERROR_ACCESS_DENIED; - } - - // Open the archive like it is normal archive - if(dwErrCode == ERROR_SUCCESS) - { - if(SFileOpenArchive(szPatchMpqName, 0, MPQ_OPEN_READ_ONLY | MPQ_OPEN_PATCH, &hPatchMpq)) - { - // Cast the archive handle to structure pointer - haPatch = (TMPQArchive *)hPatchMpq; - - // We need to remember the proper patch prefix to match names of patched files - if(FindPatchPrefix(ha, (TMPQArchive *)hPatchMpq, szPatchPathPrefix)) - { - // Now add the patch archive to the list of patches to the original MPQ - while(ha != NULL) - { - if(ha->haPatch == NULL) - { - haPatch->haBase = ha; - ha->haPatch = haPatch; - return true; - } - - // Move to the next archive - ha = ha->haPatch; - } - } - - // Close the archive - SFileCloseArchive(hPatchMpq); - dwErrCode = ERROR_CANT_FIND_PATCH_PREFIX; - } - else - { - dwErrCode = GetLastError(); - } - } - - SetLastError(dwErrCode); - return false; -} - -bool WINAPI SFileIsPatchedArchive(HANDLE hMpq) -{ - TMPQArchive * ha = (TMPQArchive *)hMpq; - - // Verify input parameters - if(!IsValidMpqHandle(hMpq)) - return false; - - return (ha->haPatch != NULL); -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/SFileReadFile.cpp b/app/jni/src/libultraship/extern/StormLib/src/SFileReadFile.cpp deleted file mode 100644 index 8031ba7..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/SFileReadFile.cpp +++ /dev/null @@ -1,913 +0,0 @@ -/*****************************************************************************/ -/* SFileReadFile.cpp Copyright (c) Ladislav Zezula 2003 */ -/*---------------------------------------------------------------------------*/ -/* Description : */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* xx.xx.99 1.00 Lad The first version of SFileReadFile.cpp */ -/* 24.03.99 1.00 Lad Added the SFileGetFileInfo function */ -/*****************************************************************************/ - -#define __STORMLIB_SELF__ -#include "StormLib.h" -#include "StormCommon.h" - -//----------------------------------------------------------------------------- -// Local functions - -// hf - MPQ File handle. -// pbBuffer - Pointer to target buffer to store sectors. -// dwByteOffset - Position of sector in the file (relative to file begin) -// dwBytesToRead - Number of bytes to read. Must be multiplier of sector size. -// pdwBytesRead - Stored number of bytes loaded -static DWORD ReadMpqSectors(TMPQFile * hf, LPBYTE pbBuffer, DWORD dwByteOffset, DWORD dwBytesToRead, LPDWORD pdwBytesRead) -{ - ULONGLONG RawFilePos; - TMPQArchive * ha = hf->ha; - TFileEntry * pFileEntry = hf->pFileEntry; - LPBYTE pbRawSector = NULL; - LPBYTE pbOutSector = pbBuffer; - LPBYTE pbInSector = pbBuffer; - DWORD dwRawBytesToRead; - DWORD dwRawSectorOffset = dwByteOffset; - DWORD dwSectorsToRead = dwBytesToRead / ha->dwSectorSize; - DWORD dwSectorIndex = dwByteOffset / ha->dwSectorSize; - DWORD dwSectorsDone = 0; - DWORD dwBytesRead = 0; - DWORD dwErrCode = ERROR_SUCCESS; - - // Note that dwByteOffset must be aligned to size of one sector - // Note that dwBytesToRead must be a multiplier of one sector size - // This is local function, so we won't check if that's true. - // Note that files stored in single units are processed by a separate function - - // If there is not enough bytes remaining, cut dwBytesToRead - if((dwByteOffset + dwBytesToRead) > hf->dwDataSize) - dwBytesToRead = hf->dwDataSize - dwByteOffset; - dwRawBytesToRead = dwBytesToRead; - - // Perform all necessary work to do with compressed files - if(pFileEntry->dwFlags & MPQ_FILE_COMPRESS_MASK) - { - // If the sector positions are not loaded yet, do it - if(hf->SectorOffsets == NULL) - { - dwErrCode = AllocateSectorOffsets(hf, true); - if(dwErrCode != ERROR_SUCCESS || hf->SectorOffsets == NULL) - return dwErrCode; - } - - // If the sector checksums are not loaded yet, load them now. - if(hf->SectorChksums == NULL && (pFileEntry->dwFlags & MPQ_FILE_SECTOR_CRC) && hf->bLoadedSectorCRCs == false) - { - // - // Sector CRCs is plain crap feature. It is almost never present, - // often it's empty, or the end offset of sector CRCs is zero. - // We only try to load sector CRCs once, and regardless if it fails - // or not, we won't try that again for the given file. - // - - AllocateSectorChecksums(hf, true); - hf->bLoadedSectorCRCs = true; - } - - // TODO: If the raw data MD5s are not loaded yet, load them now - // Only do it if the MPQ is of format 4.0 -// if(ha->pHeader->wFormatVersion >= MPQ_FORMAT_VERSION_4 && ha->pHeader->dwRawChunkSize != 0) -// { -// dwErrCode = AllocateRawMD5s(hf, true); -// if(dwErrCode != ERROR_SUCCESS) -// return dwErrCode; -// } - - // Assign the temporary buffer as target for read operation - dwRawSectorOffset = hf->SectorOffsets[dwSectorIndex]; - dwRawBytesToRead = hf->SectorOffsets[dwSectorIndex + dwSectorsToRead] - dwRawSectorOffset; - - // If the file is compressed, also allocate secondary buffer - pbInSector = pbRawSector = STORM_ALLOC(BYTE, dwRawBytesToRead); - if(pbRawSector == NULL) - return ERROR_NOT_ENOUGH_MEMORY; - } - - // Calculate raw file offset where the sector(s) are stored. - RawFilePos = CalculateRawSectorOffset(hf, dwRawSectorOffset); - - // Set file pointer and read all required sectors - if(FileStream_Read(ha->pStream, &RawFilePos, pbInSector, dwRawBytesToRead)) - { - // Now we have to decrypt and decompress all file sectors that have been loaded - for(DWORD i = 0; i < dwSectorsToRead; i++) - { - DWORD dwRawBytesInThisSector = ha->dwSectorSize; - DWORD dwBytesInThisSector = ha->dwSectorSize; - DWORD dwIndex = dwSectorIndex + i; - - // If there is not enough bytes in the last sector, - // cut the number of bytes in this sector - if(dwRawBytesInThisSector > dwBytesToRead) - dwRawBytesInThisSector = dwBytesToRead; - if(dwBytesInThisSector > dwBytesToRead) - dwBytesInThisSector = dwBytesToRead; - - // If the file is compressed, we have to adjust the raw sector size - if(pFileEntry->dwFlags & MPQ_FILE_COMPRESS_MASK) - dwRawBytesInThisSector = hf->SectorOffsets[dwIndex + 1] - hf->SectorOffsets[dwIndex]; - - // If the file is encrypted, we have to decrypt the sector - if(pFileEntry->dwFlags & MPQ_FILE_ENCRYPTED) - { - BSWAP_ARRAY32_UNSIGNED(pbInSector, dwRawBytesInThisSector); - - // If we don't know the key, try to detect it by file content - if(hf->dwFileKey == 0) - { - hf->dwFileKey = DetectFileKeyByContent(pbInSector, dwBytesInThisSector, hf->dwDataSize); - if(hf->dwFileKey == 0) - { - dwErrCode = ERROR_UNKNOWN_FILE_KEY; - break; - } - } - - DecryptMpqBlock(pbInSector, dwRawBytesInThisSector, hf->dwFileKey + dwIndex); - BSWAP_ARRAY32_UNSIGNED(pbInSector, dwRawBytesInThisSector); - } - - // If the file has sector CRC check turned on, perform it - if(hf->bCheckSectorCRCs && hf->SectorChksums != NULL) - { - DWORD dwAdlerExpected = hf->SectorChksums[dwIndex]; - DWORD dwAdlerValue = 0; - - // We can only check sector CRC when it's not zero - // Neither can we check it if it's 0xFFFFFFFF. - if(dwAdlerExpected != 0 && dwAdlerExpected != 0xFFFFFFFF) - { - dwAdlerValue = adler32(0, pbInSector, dwRawBytesInThisSector); - if(dwAdlerValue != dwAdlerExpected) - { - dwErrCode = ERROR_CHECKSUM_ERROR; - break; - } - } - } - - // If the sector is really compressed, decompress it. - // WARNING : Some sectors may not be compressed, it can be determined only - // by comparing uncompressed and compressed size !!! - if(dwRawBytesInThisSector < dwBytesInThisSector) - { - if(dwRawBytesInThisSector != 0) - { - int cbOutSector = dwBytesInThisSector; - int cbInSector = dwRawBytesInThisSector; - int nResult = 0; - - // Is the file compressed by Blizzard's multiple compression ? - if(pFileEntry->dwFlags & MPQ_FILE_COMPRESS) - { - // Remember the last used compression - hf->dwCompression0 = pbInSector[0]; - - // Decompress the data - if(ha->pHeader->wFormatVersion >= MPQ_FORMAT_VERSION_2) - { - nResult = SCompDecompress2(pbOutSector, &cbOutSector, pbInSector, cbInSector); - } - else - { - if(ha->dwFlags & MPQ_FLAG_STARCRAFT_BETA) - nResult = SCompDecompress_SC1B(pbOutSector, &cbOutSector, pbInSector, cbInSector); - else - nResult = SCompDecompress(pbOutSector, &cbOutSector, pbInSector, cbInSector); - } - } - - // Is the file compressed by PKWARE Data Compression Library ? - else if(pFileEntry->dwFlags & MPQ_FILE_IMPLODE) - { - nResult = SCompExplode(pbOutSector, &cbOutSector, pbInSector, cbInSector); - } - - // Did the decompression fail ? - if(nResult == 0) - { - dwErrCode = ERROR_FILE_CORRUPT; - break; - } - } - else - { - memset(pbOutSector, 0, dwBytesInThisSector); - } - } - else - { - if(pbOutSector != pbInSector) - memcpy(pbOutSector, pbInSector, dwBytesInThisSector); - } - - // Move pointers - dwBytesToRead -= dwBytesInThisSector; - dwByteOffset += dwBytesInThisSector; - dwBytesRead += dwBytesInThisSector; - pbOutSector += dwBytesInThisSector; - pbInSector += dwRawBytesInThisSector; - dwSectorsDone++; - } - } - else - { - dwErrCode = GetLastError(); - } - - // Free all used buffers - if(pbRawSector != NULL) - STORM_FREE(pbRawSector); - - // Give the caller thenumber of bytes read - *pdwBytesRead = dwBytesRead; - return dwErrCode; -} - -static DWORD ReadMpqFileSingleUnit(TMPQFile * hf, void * pvBuffer, DWORD dwFilePos, DWORD dwToRead, LPDWORD pdwBytesRead) -{ - ULONGLONG RawFilePos = hf->RawFilePos; - TMPQArchive * ha = hf->ha; - TFileEntry * pFileEntry = hf->pFileEntry; - LPBYTE pbCompressed = NULL; - LPBYTE pbRawData; - DWORD dwErrCode = ERROR_SUCCESS; - - // If the file buffer is not allocated yet, do it. - if(hf->pbFileSector == NULL) - { - dwErrCode = AllocateSectorBuffer(hf); - if(dwErrCode != ERROR_SUCCESS || hf->pbFileSector == NULL) - return dwErrCode; - } - - // If the file is a patch file, adjust raw data offset - if(hf->pPatchInfo != NULL) - RawFilePos += hf->pPatchInfo->dwLength; - pbRawData = hf->pbFileSector; - - // If the file sector is not loaded yet, do it - if(hf->dwSectorOffs != 0) - { - // Is the file compressed? - if(pFileEntry->dwFlags & MPQ_FILE_COMPRESS_MASK) - { - // Allocate space for compressed data - pbCompressed = STORM_ALLOC(BYTE, pFileEntry->dwCmpSize); - if(pbCompressed == NULL) - return ERROR_NOT_ENOUGH_MEMORY; - pbRawData = pbCompressed; - } - - // Load the raw (compressed, encrypted) data - if(!FileStream_Read(ha->pStream, &RawFilePos, pbRawData, pFileEntry->dwCmpSize)) - { - STORM_FREE(pbCompressed); - return GetLastError(); - } - - // If the file is encrypted, we have to decrypt the data first - if(pFileEntry->dwFlags & MPQ_FILE_ENCRYPTED) - { - BSWAP_ARRAY32_UNSIGNED(pbRawData, pFileEntry->dwCmpSize); - DecryptMpqBlock(pbRawData, pFileEntry->dwCmpSize, hf->dwFileKey); - BSWAP_ARRAY32_UNSIGNED(pbRawData, pFileEntry->dwCmpSize); - } - - // If the file is compressed, we have to decompress it now - if(pFileEntry->dwFlags & MPQ_FILE_COMPRESS_MASK) - { - int cbOutBuffer = (int)hf->dwDataSize; - int cbInBuffer = (int)pFileEntry->dwCmpSize; - int nResult = 0; - - // - // If the file is an incremental patch, the size of compressed data - // is determined as pFileEntry->dwCmpSize - sizeof(TPatchInfo) - // - // In "wow-update-12694.MPQ" from Wow-Cataclysm BETA: - // - // File CmprSize DcmpSize DataSize Compressed? - // -------------------------------------- ---------- -------- -------- --------------- - // esES\DBFilesClient\LightSkyBox.dbc 0xBE->0xA2 0xBC 0xBC Yes - // deDE\DBFilesClient\MountCapability.dbc 0x93->0x77 0x77 0x77 No - // - - if(pFileEntry->dwFlags & MPQ_FILE_PATCH_FILE) - cbInBuffer = cbInBuffer - sizeof(TPatchInfo); - - // Is the file compressed by Blizzard's multiple compression ? - if(pFileEntry->dwFlags & MPQ_FILE_COMPRESS) - { - // Remember the last used compression - hf->dwCompression0 = pbRawData[0]; - - // Decompress the file - if(ha->pHeader->wFormatVersion >= MPQ_FORMAT_VERSION_2) - nResult = SCompDecompress2(hf->pbFileSector, &cbOutBuffer, pbRawData, cbInBuffer); - else - nResult = SCompDecompress(hf->pbFileSector, &cbOutBuffer, pbRawData, cbInBuffer); - } - - // Is the file compressed by PKWARE Data Compression Library ? - // Note: Single unit files compressed with IMPLODE are not supported by Blizzard - else if(pFileEntry->dwFlags & MPQ_FILE_IMPLODE) - nResult = SCompExplode(hf->pbFileSector, &cbOutBuffer, pbRawData, cbInBuffer); - - dwErrCode = (nResult != 0) ? ERROR_SUCCESS : ERROR_FILE_CORRUPT; - } - else - { - if(hf->pbFileSector != NULL && pbRawData != hf->pbFileSector) - memcpy(hf->pbFileSector, pbRawData, hf->dwDataSize); - } - - // Free the decompression buffer. - if(pbCompressed != NULL) - STORM_FREE(pbCompressed); - - // The file sector is now properly loaded - hf->dwSectorOffs = 0; - } - - // At this moment, we have the file loaded into the file buffer. - // Copy as much as the caller wants - if(dwErrCode == ERROR_SUCCESS && hf->dwSectorOffs == 0) - { - // File position is greater or equal to file size ? - if(dwFilePos >= hf->dwDataSize) - { - *pdwBytesRead = 0; - return ERROR_SUCCESS; - } - - // If not enough bytes remaining in the file, cut them - if((hf->dwDataSize - dwFilePos) < dwToRead) - dwToRead = (hf->dwDataSize - dwFilePos); - - // Copy the bytes - memcpy(pvBuffer, hf->pbFileSector + dwFilePos, dwToRead); - - // Give the number of bytes read - *pdwBytesRead = dwToRead; - } - - // An error, sorry - return dwErrCode; -} - -static DWORD ReadMpkFileSingleUnit(TMPQFile * hf, void * pvBuffer, DWORD dwFilePos, DWORD dwToRead, LPDWORD pdwBytesRead) -{ - ULONGLONG RawFilePos = hf->RawFilePos + 0x0C; // For some reason, MPK files start at position (hf->RawFilePos + 0x0C) - TMPQArchive * ha = hf->ha; - TFileEntry * pFileEntry = hf->pFileEntry; - LPBYTE pbCompressed = NULL; - LPBYTE pbRawData = hf->pbFileSector; - DWORD dwErrCode = ERROR_SUCCESS; - - // We do not support patch files in MPK archives - assert(hf->pPatchInfo == NULL); - - // If the file buffer is not allocated yet, do it. - if(hf->pbFileSector == NULL) - { - dwErrCode = AllocateSectorBuffer(hf); - if(dwErrCode != ERROR_SUCCESS || hf->pbFileSector == NULL) - return dwErrCode; - pbRawData = hf->pbFileSector; - } - - // If the file sector is not loaded yet, do it - if(hf->dwSectorOffs != 0) - { - // Is the file compressed? - if(pFileEntry->dwFlags & MPQ_FILE_COMPRESS_MASK) - { - // Allocate space for compressed data - pbCompressed = STORM_ALLOC(BYTE, pFileEntry->dwCmpSize); - if(pbCompressed == NULL) - return ERROR_NOT_ENOUGH_MEMORY; - pbRawData = pbCompressed; - } - - // Load the raw (compressed, encrypted) data - if(!FileStream_Read(ha->pStream, &RawFilePos, pbRawData, pFileEntry->dwCmpSize)) - { - STORM_FREE(pbCompressed); - return GetLastError(); - } - - // If the file is encrypted, we have to decrypt the data first - if(pFileEntry->dwFlags & MPQ_FILE_ENCRYPTED) - { - DecryptMpkTable(pbRawData, pFileEntry->dwCmpSize); - } - - // If the file is compressed, we have to decompress it now - if(pFileEntry->dwFlags & MPQ_FILE_COMPRESS_MASK) - { - int cbOutBuffer = (int)hf->dwDataSize; - - hf->dwCompression0 = pbRawData[0]; - if(!SCompDecompressMpk(hf->pbFileSector, &cbOutBuffer, pbRawData, (int)pFileEntry->dwCmpSize)) - dwErrCode = ERROR_FILE_CORRUPT; - } - else - { - if(pbRawData != hf->pbFileSector) - memcpy(hf->pbFileSector, pbRawData, hf->dwDataSize); - } - - // Free the decompression buffer. - if(pbCompressed != NULL) - STORM_FREE(pbCompressed); - - // The file sector is now properly loaded - hf->dwSectorOffs = 0; - } - - // At this moment, we have the file loaded into the file buffer. - // Copy as much as the caller wants - if(dwErrCode == ERROR_SUCCESS && hf->dwSectorOffs == 0) - { - // File position is greater or equal to file size ? - if(dwFilePos >= hf->dwDataSize) - { - *pdwBytesRead = 0; - return ERROR_SUCCESS; - } - - // If not enough bytes remaining in the file, cut them - if((hf->dwDataSize - dwFilePos) < dwToRead) - dwToRead = (hf->dwDataSize - dwFilePos); - - // Copy the bytes - memcpy(pvBuffer, hf->pbFileSector + dwFilePos, dwToRead); - - // Give the number of bytes read - *pdwBytesRead = dwToRead; - return ERROR_SUCCESS; - } - - // An error, sorry - return ERROR_CAN_NOT_COMPLETE; -} - - -static DWORD ReadMpqFileSectorFile(TMPQFile * hf, void * pvBuffer, DWORD dwFilePos, DWORD dwBytesToRead, LPDWORD pdwBytesRead) -{ - TMPQArchive * ha = hf->ha; - LPBYTE pbBuffer = (BYTE *)pvBuffer; - DWORD dwTotalBytesRead = 0; // Total bytes read in all three parts - DWORD dwSectorSizeMask = ha->dwSectorSize - 1; // Mask for block size, usually 0x0FFF - DWORD dwFileSectorPos; // File offset of the loaded sector - DWORD dwBytesRead; // Number of bytes read (temporary variable) - DWORD dwErrCode; - - // If the file position is at or beyond end of file, do nothing - if(dwFilePos >= hf->dwDataSize) - { - *pdwBytesRead = 0; - return ERROR_SUCCESS; - } - - // If not enough bytes in the file remaining, cut them - if(dwBytesToRead > (hf->dwDataSize - dwFilePos)) - dwBytesToRead = (hf->dwDataSize - dwFilePos); - - // Compute sector position in the file - dwFileSectorPos = dwFilePos & ~dwSectorSizeMask; // Position in the block - - // If the file sector buffer is not allocated yet, do it now - if(hf->pbFileSector == NULL) - { - dwErrCode = AllocateSectorBuffer(hf); - if(dwErrCode != ERROR_SUCCESS || hf->pbFileSector == NULL) - return dwErrCode; - } - - // Load the first (incomplete) file sector - if(dwFilePos & dwSectorSizeMask) - { - DWORD dwBytesInSector = ha->dwSectorSize; - DWORD dwBufferOffs = dwFilePos & dwSectorSizeMask; - DWORD dwToCopy; - - // Is the file sector already loaded ? - if(hf->dwSectorOffs != dwFileSectorPos) - { - // Load one MPQ sector into archive buffer - dwErrCode = ReadMpqSectors(hf, hf->pbFileSector, dwFileSectorPos, ha->dwSectorSize, &dwBytesInSector); - if(dwErrCode != ERROR_SUCCESS) - return dwErrCode; - - // Remember that the data loaded to the sector have new file offset - hf->dwSectorOffs = dwFileSectorPos; - } - else - { - if((dwFileSectorPos + dwBytesInSector) > hf->dwDataSize) - dwBytesInSector = hf->dwDataSize - dwFileSectorPos; - } - - // Copy the data from the offset in the loaded sector to the end of the sector - dwToCopy = dwBytesInSector - dwBufferOffs; - if(dwToCopy > dwBytesToRead) - dwToCopy = dwBytesToRead; - - // Copy data from sector buffer into target buffer - memcpy(pbBuffer, hf->pbFileSector + dwBufferOffs, dwToCopy); - - // Update pointers and byte counts - dwTotalBytesRead += dwToCopy; - dwFileSectorPos += dwBytesInSector; - pbBuffer += dwToCopy; - dwBytesToRead -= dwToCopy; - } - - // Load the whole ("middle") sectors only if there is at least one full sector to be read - if(dwBytesToRead >= ha->dwSectorSize) - { - DWORD dwBlockBytes = dwBytesToRead & ~dwSectorSizeMask; - - // Load all sectors to the output buffer - dwErrCode = ReadMpqSectors(hf, pbBuffer, dwFileSectorPos, dwBlockBytes, &dwBytesRead); - if(dwErrCode != ERROR_SUCCESS) - return dwErrCode; - - // Update pointers - dwTotalBytesRead += dwBytesRead; - dwFileSectorPos += dwBytesRead; - pbBuffer += dwBytesRead; - dwBytesToRead -= dwBytesRead; - } - - // Read the terminating sector - if(dwBytesToRead > 0) - { - DWORD dwToCopy = ha->dwSectorSize; - - // Is the file sector already loaded ? - if(hf->dwSectorOffs != dwFileSectorPos) - { - // Load one MPQ sector into archive buffer - dwErrCode = ReadMpqSectors(hf, hf->pbFileSector, dwFileSectorPos, ha->dwSectorSize, &dwBytesRead); - if(dwErrCode != ERROR_SUCCESS) - return dwErrCode; - - // Remember that the data loaded to the sector have new file offset - hf->dwSectorOffs = dwFileSectorPos; - } - - // Check number of bytes read - if(dwToCopy > dwBytesToRead) - dwToCopy = dwBytesToRead; - - // Copy the data from the cached last sector to the caller's buffer - memcpy(pbBuffer, hf->pbFileSector, dwToCopy); - - // Update pointers - dwTotalBytesRead += dwToCopy; - } - - // Store total number of bytes read to the caller - *pdwBytesRead = dwTotalBytesRead; - return ERROR_SUCCESS; -} - -static DWORD ReadMpqFilePatchFile(TMPQFile * hf, void * pvBuffer, DWORD dwFilePos, DWORD dwToRead, LPDWORD pdwBytesRead) -{ - TMPQPatcher Patcher; - DWORD dwBytesToRead = dwToRead; - DWORD dwBytesRead = 0; - DWORD dwErrCode = ERROR_SUCCESS; - - // Make sure that the patch file is loaded completely - if(dwErrCode == ERROR_SUCCESS && hf->pbFileData == NULL) - { - // Initialize patching process and allocate data - dwErrCode = Patch_InitPatcher(&Patcher, hf); - if(dwErrCode != ERROR_SUCCESS) - return dwErrCode; - - // Set the current data size - Patcher.cbFileData = hf->pFileEntry->dwFileSize; - - // Initialize the patcher object with initial file data - if(hf->pFileEntry->dwFlags & MPQ_FILE_SINGLE_UNIT) - dwErrCode = ReadMpqFileSingleUnit(hf, Patcher.pbFileData1, 0, Patcher.cbFileData, &dwBytesRead); - else - dwErrCode = ReadMpqFileSectorFile(hf, Patcher.pbFileData1, 0, Patcher.cbFileData, &dwBytesRead); - - // Perform the patching process - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = Patch_Process(&Patcher, hf); - - // Finalize the patcher structure - Patch_Finalize(&Patcher); - dwBytesRead = 0; - } - - // If there is something to read, do it - if(dwErrCode == ERROR_SUCCESS) - { - if(dwFilePos < hf->cbFileData) - { - // Make sure we don't copy more than file size - if((dwFilePos + dwToRead) > hf->cbFileData) - dwToRead = hf->cbFileData - dwFilePos; - - // Copy the appropriate amount of the file data to the caller's buffer - memcpy(pvBuffer, hf->pbFileData + dwFilePos, dwToRead); - dwBytesRead = dwToRead; - } - - // Set the proper error code - dwErrCode = (dwBytesRead == dwBytesToRead) ? ERROR_SUCCESS : ERROR_HANDLE_EOF; - } - - // Give the result to the caller - if(pdwBytesRead != NULL) - *pdwBytesRead = dwBytesRead; - return dwErrCode; -} - -static DWORD ReadMpqFileLocalFile(TMPQFile * hf, void * pvBuffer, DWORD dwFilePos, DWORD dwToRead, LPDWORD pdwBytesRead) -{ - ULONGLONG FilePosition1 = dwFilePos; - ULONGLONG FilePosition2; - DWORD dwBytesRead = 0; - DWORD dwErrCode = ERROR_SUCCESS; - - assert(hf->pStream != NULL); - - // Because stream I/O functions are designed to read - // "all or nothing", we compare file position before and after, - // and if they differ, we assume that number of bytes read - // is the difference between them - - if(!FileStream_Read(hf->pStream, &FilePosition1, pvBuffer, dwToRead)) - { - // If not all bytes have been read, then return the number of bytes read - if((dwErrCode = GetLastError()) == ERROR_HANDLE_EOF) - { - FileStream_GetPos(hf->pStream, &FilePosition2); - dwBytesRead = (DWORD)(FilePosition2 - FilePosition1); - } - } - else - { - dwBytesRead = dwToRead; - } - - *pdwBytesRead = dwBytesRead; - return dwErrCode; -} - -//----------------------------------------------------------------------------- -// SFileReadFile - -bool WINAPI SFileReadFile(HANDLE hFile, void * pvBuffer, DWORD dwToRead, LPDWORD pdwRead, LPOVERLAPPED lpOverlapped) -{ - TFileEntry * pFileEntry; - TMPQFile * hf; - DWORD dwBytesRead = 0; // Number of bytes read - DWORD dwErrCode = ERROR_SUCCESS; - - // Always zero the result - if(pdwRead != NULL) - *pdwRead = 0; - lpOverlapped = lpOverlapped; - - // Check valid parameters - if((hf = IsValidFileHandle(hFile)) == NULL) - { - SetLastError(ERROR_INVALID_HANDLE); - return false; - } - - if(pvBuffer == NULL) - { - SetLastError(ERROR_INVALID_PARAMETER); - return false; - } - - // If we didn't load the patch info yet, do it now - if(hf->pFileEntry != NULL && (hf->pFileEntry->dwFlags & MPQ_FILE_PATCH_FILE) && hf->pPatchInfo == NULL) - { - dwErrCode = AllocatePatchInfo(hf, true); - if(dwErrCode != ERROR_SUCCESS || hf->pPatchInfo == NULL) - { - SetLastError(dwErrCode); - return false; - } - } - - // Clear the last used compression - pFileEntry = hf->pFileEntry; - hf->dwCompression0 = 0; - - // If the file is local file, read the data directly from the stream - if(hf->pStream != NULL) - { - dwErrCode = ReadMpqFileLocalFile(hf, pvBuffer, hf->dwFilePos, dwToRead, &dwBytesRead); - } - - // If the file is a patch file, we have to read it special way - else if(hf->hfPatch != NULL && (pFileEntry->dwFlags & MPQ_FILE_PATCH_FILE) == 0) - { - dwErrCode = ReadMpqFilePatchFile(hf, pvBuffer, hf->dwFilePos, dwToRead, &dwBytesRead); - } - - // If the archive is a MPK archive, we need special way to read the file - else if(hf->ha->dwSubType == MPQ_SUBTYPE_MPK) - { - dwErrCode = ReadMpkFileSingleUnit(hf, pvBuffer, hf->dwFilePos, dwToRead, &dwBytesRead); - } - - // If the file is single unit file, redirect it to read file - else if(pFileEntry->dwFlags & MPQ_FILE_SINGLE_UNIT) - { - dwErrCode = ReadMpqFileSingleUnit(hf, pvBuffer, hf->dwFilePos, dwToRead, &dwBytesRead); - } - - // Otherwise read it as sector based MPQ file - else - { - dwErrCode = ReadMpqFileSectorFile(hf, pvBuffer, hf->dwFilePos, dwToRead, &dwBytesRead); - } - - // Increment the file position - hf->dwFilePos += dwBytesRead; - - // Give the caller the number of bytes read - if(pdwRead != NULL) - *pdwRead = dwBytesRead; - - // If the read operation succeeded, but not full number of bytes was read, - // set the last error to ERROR_HANDLE_EOF - if(dwErrCode == ERROR_SUCCESS && (dwBytesRead < dwToRead)) - dwErrCode = ERROR_HANDLE_EOF; - - // If something failed, set the last error value - if(dwErrCode != ERROR_SUCCESS) - SetLastError(dwErrCode); - return (dwErrCode == ERROR_SUCCESS); -} - -//----------------------------------------------------------------------------- -// SFileGetFileSize - -DWORD WINAPI SFileGetFileSize(HANDLE hFile, LPDWORD pdwFileSizeHigh) -{ - ULONGLONG FileSize; - TMPQFile * hf = (TMPQFile *)hFile; - - // Validate the file handle before we go on - if(IsValidFileHandle(hFile)) - { - // Make sure that the variable is initialized - FileSize = 0; - - // If the file is patched file, we have to get the size of the last version - if(hf->hfPatch != NULL) - { - // Walk through the entire patch chain, take the last version - while(hf != NULL) - { - // Get the size of the currently pointed version - FileSize = hf->pFileEntry->dwFileSize; - - // Move to the next patch file in the hierarchy - hf = hf->hfPatch; - } - } - else - { - // Is it a local file ? - if(hf->pStream != NULL) - { - FileStream_GetSize(hf->pStream, &FileSize); - } - else - { - FileSize = hf->dwDataSize; - } - } - - // If opened from archive, return file size - if(pdwFileSizeHigh != NULL) - *pdwFileSizeHigh = (DWORD)(FileSize >> 32); - return (DWORD)FileSize; - } - - SetLastError(ERROR_INVALID_HANDLE); - return SFILE_INVALID_SIZE; -} - -DWORD WINAPI SFileSetFilePointer(HANDLE hFile, LONG lFilePos, LONG * plFilePosHigh, DWORD dwMoveMethod) -{ - TMPQFile * hf = (TMPQFile *)hFile; - ULONGLONG OldPosition; - ULONGLONG NewPosition; - ULONGLONG FileSize; - ULONGLONG DeltaPos; - - // If the hFile is not a valid file handle, return an error. - if(!IsValidFileHandle(hFile)) - { - SetLastError(ERROR_INVALID_HANDLE); - return SFILE_INVALID_POS; - } - - // Retrieve the file size for handling the limits - if(hf->pStream != NULL) - { - FileStream_GetSize(hf->pStream, &FileSize); - } - else - { - FileSize = SFileGetFileSize(hFile, NULL); - } - - // Handle the NULL and non-NULL values of plFilePosHigh - // Non-NULL: The DeltaPos is combined from lFilePos and *lpFilePosHigh - // NULL: The DeltaPos is sign-extended value of lFilePos - DeltaPos = (plFilePosHigh != NULL) ? MAKE_OFFSET64(plFilePosHigh[0], lFilePos) : (ULONGLONG)(LONGLONG)lFilePos; - - // Get the relative point where to move from - switch(dwMoveMethod) - { - case FILE_BEGIN: - - // Move relative to the file begin. - OldPosition = 0; - break; - - case FILE_CURRENT: - - // Retrieve the current file position - if(hf->pStream != NULL) - { - FileStream_GetPos(hf->pStream, &OldPosition); - } - else - { - OldPosition = hf->dwFilePos; - } - break; - - case FILE_END: - - // Move relative to the end of the file - OldPosition = FileSize; - break; - - default: - SetLastError(ERROR_INVALID_PARAMETER); - return SFILE_INVALID_POS; - } - - // Calculate the new position - NewPosition = OldPosition + DeltaPos; - - // If moving backward, don't allow the new position go negative - if((LONGLONG)DeltaPos < 0) - { - if(NewPosition > FileSize) // Position is negative - { - SetLastError(ERROR_NEGATIVE_SEEK); - return SFILE_INVALID_POS; - } - } - - // If moving forward, don't allow the new position go past the end of the file - else - { - if(NewPosition > FileSize) - NewPosition = FileSize; - } - - // Now apply the file pointer to the file - if(hf->pStream != NULL) - { - if(!FileStream_Read(hf->pStream, &NewPosition, NULL, 0)) - return SFILE_INVALID_POS; - } - - // Also, store the new file position to the TMPQFile struct - hf->dwFilePos = (DWORD)NewPosition; - - // Return the new file position - if(plFilePosHigh != NULL) - *plFilePosHigh = (LONG)(NewPosition >> 32); - return (DWORD)NewPosition; -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/SFileVerify.cpp b/app/jni/src/libultraship/extern/StormLib/src/SFileVerify.cpp deleted file mode 100644 index 4465562..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/SFileVerify.cpp +++ /dev/null @@ -1,1054 +0,0 @@ -/*****************************************************************************/ -/* SFileVerify.cpp Copyright (c) Ladislav Zezula 2010 */ -/*---------------------------------------------------------------------------*/ -/* MPQ files and MPQ archives verification. */ -/* */ -/* The MPQ signature verification has been written by Jean-Francois Roy */ -/* and Justin Olbrantz (Quantam). */ -/* The MPQ public keys have been created by MPQKit, using OpenSSL library. */ -/* */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 04.05.10 1.00 Lad The first version of SFileVerify.cpp */ -/*****************************************************************************/ - -#define __STORMLIB_SELF__ -#include "StormLib.h" -#include "StormCommon.h" - -//----------------------------------------------------------------------------- -// Local defines - -#define MPQ_DIGEST_UNIT_SIZE 0x10000 - -//----------------------------------------------------------------------------- -// Known Blizzard public keys -// Created by Jean-Francois Roy using OpenSSL - -static const char * szBlizzardWeakPrivateKey = - "-----BEGIN PRIVATE KEY-----" - "MIIBOQIBAAJBAJJidwS/uILMBSO5DLGsBFknIXWWjQJe2kfdfEk3G/j66w4KkhZ1" - "V61Rt4zLaMVCYpDun7FLwRjkMDSepO1q2DcCAwEAAQJANtiztVDMJh2hE1hjPDKy" - "UmEJ9U/aN3gomuKOjbQbQ/bWWcM/WfhSVHmPqtqh/bQI2UXFr0rnXngeteZHLr/b" - "8QIhAMuWriSKGMACw18/rVVfUrThs915odKBH1Alr3vMVVzZAiEAuBHPSQkgwcb6" - "L4MWaiKuOzq08mSyNqPeN8oSy18q848CIHeMn+3s+eOmu7su1UYQl6yH7OrdBd1q" - "3UxfFNEJiAbhAiAqxdCyOxHGlbM7aS3DOg3cq5ayoN2cvtV7h1R4t8OmVwIgF+5z" - "/6vkzBUsZhd8Nwyis+MeQYH0rpFpMKdTlqmPF2Q=" - "-----END PRIVATE KEY-----"; - -static const char * szBlizzardWeakPublicKey = - "-----BEGIN PUBLIC KEY-----" - "MFwwDQYJKoZIhvcNAQEBBQADSwAwSAJBAJJidwS/uILMBSO5DLGsBFknIXWWjQJe" - "2kfdfEk3G/j66w4KkhZ1V61Rt4zLaMVCYpDun7FLwRjkMDSepO1q2DcCAwEAAQ==" - "-----END PUBLIC KEY-----"; - -static const char * szBlizzardStrongPublicKey = - "-----BEGIN PUBLIC KEY-----" - "MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAsQZ+ziT2h8h+J/iMQpgd" - "tH1HaJzOBE3agjU4yMPcrixaPOZoA4t8bwfey7qczfWywocYo3pleytFF+IuD4HD" - "Fl9OXN1SFyupSgMx1EGZlgbFAomnbq9MQJyMqQtMhRAjFgg4TndS7YNb+JMSAEKp" - "kXNqY28n/EVBHD5TsMuVCL579gIenbr61dI92DDEdy790IzIG0VKWLh/KOTcTJfm" - "Ds/7HQTkGouVW+WUsfekuqNQo7ND9DBnhLjLjptxeFE2AZqYcA1ao3S9LN3GL1tW" - "lVXFIX9c7fWqaVTQlZ2oNsI/ARVApOK3grNgqvwH6YoVYVXjNJEo5sQJsPsdV/hk" - "dwIDAQAB" - "-----END PUBLIC KEY-----"; - -static const char * szWarcraft3MapPublicKey = - "-----BEGIN PUBLIC KEY-----" - "MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA1BwklUUQ3UvjizOBRoF5" - "yyOVc7KD+oGOQH5i6eUk1yfs0luCC70kNucNrfqhmviywVtahRse1JtXCPrx2bd3" - "iN8Dx91fbkxjYIOGTsjYoHKTp0BbaFkJih776fcHgnFSb+7mJcDuJVvJOXxEH6w0" - "1vo6VtujCqj1arqbyoal+xtAaczF3us5cOEp45sR1zAWTn1+7omN7VWV4QqJPaDS" - "gBSESc0l1grO0i1VUSumayk7yBKIkb+LBvcG6WnYZHCi7VdLmaxER5m8oZfER66b" - "heHoiSQIZf9PAY6Guw2DT5BTc54j/AaLQAKf2qcRSgQLVo5kQaddF3rCpsXoB/74" - "6QIDAQAB" - "-----END PUBLIC KEY-----"; - -static const char * szWowPatchPublicKey = - "-----BEGIN PUBLIC KEY-----" - "MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAwOsMV0LagAWPEtEQM6b9" - "6FHFkUyGbbyda2/Dfc9dyl21E9QvX+Yw7qKRMAKPzA2TlQQLZKvXpnKXF/YIK5xa" - "5uwg9CEHCEAYolLG4xn0FUOE0E/0PuuytI0p0ICe6rk00PifZzTr8na2wI/l/GnQ" - "bvnIVF1ck6cslATpQJ5JJVMXzoFlUABS19WESw4MXuJAS3AbMhxNWdEhVv7eO51c" - "yGjRLy9QjogZODZTY0fSEksgBqQxNCoYVJYI/sF5K2flDsGqrIp0OdJ6teJlzg1Y" - "UjYnb6bKjlidXoHEXI2TgA/mD6O3XFIt08I9s3crOCTgICq7cgX35qrZiIVWZdRv" - "TwIDAQAB" - "-----END PUBLIC KEY-----"; - -static const char * szWowSurveyPublicKey = - "-----BEGIN PUBLIC KEY-----" - "MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAnIt1DR6nRyyKsy2qahHe" - "MKLtacatn/KxieHcwH87wLBxKy+jZ0gycTmJ7SaTdBAEMDs/V5IPIXEtoqYnid2c" - "63TmfGDU92oc3Ph1PWUZ2PWxBhT06HYxRdbrgHw9/I29pNPi/607x+lzPORITOgU" - "BR6MR8au8HsQP4bn4vkJNgnSgojh48/XQOB/cAln7As1neP61NmVimoLR4Bwi3zt" - "zfgrZaUpyeNCUrOYJmH09YIjbBySTtXOUidoPHjFrMsCWpr6xs8xbETbs7MJFL6a" - "vcUfTT67qfIZ9RsuKfnXJTIrV0kwDSjjuNXiPTmWAehSsiHIsrUXX5RNcwsSjClr" - "nQIDAQAB" - "-----END PUBLIC KEY-----"; - -static const char * szStarcraft2MapPublicKey = - "-----BEGIN PUBLIC KEY-----" - "MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAmk4GT8zb+ICC25a17KZB" - "q/ygKGJ2VSO6IT5PGHJlm1KfnHBA4B6SH3xMlJ4c6eG2k7QevZv+FOhjsAHubyWq" - "2VKqWbrIFKv2ILc2RfMn8J9EDVRxvcxh6slRrVL69D0w1tfVGjMiKq2Fym5yGoRT" - "E7CRgDqbAbXP9LBsCNWHiJLwfxMGzHbk8pIl9oia5pvM7ofZamSHchxlpy6xa4GJ" - "7xKN01YCNvklTL1D7uol3wkwcHc7vrF8QwuJizuA5bSg4poEGtH62BZOYi+UL/z0" - "31YK+k9CbQyM0X0pJoJoYz1TK+Y5J7vBnXCZtfcTYQ/ZzN6UcxTa57dJaiOlCh9z" - "nQIDAQAB" - "-----END PUBLIC KEY-----"; - -//----------------------------------------------------------------------------- -// Local functions - -static void memrev(unsigned char *buf, size_t count) -{ - unsigned char *r; - - for (r = buf + count - 1; buf < r; buf++, r--) - { - *buf ^= *r; - *r ^= *buf; - *buf ^= *r; - } -} - -static bool decode_base64_key(const char * szKeyBase64, rsa_key * key) -{ - unsigned char decoded_key[0x200]; - const char * szBase64Begin; - const char * szBase64End; - unsigned long decoded_length = sizeof(decoded_key); - unsigned long length; - - // Find out the begin of the BASE64 data - szBase64Begin = szKeyBase64 + strlen("-----BEGIN PUBLIC KEY-----"); - szBase64End = szBase64Begin + strlen(szBase64Begin) - strlen("-----END PUBLIC KEY-----"); - if(szBase64End[0] != '-') - return false; - - // decode the base64 string - length = (unsigned long)(szBase64End - szBase64Begin); - if(base64_decode((unsigned char *)szBase64Begin, length, decoded_key, &decoded_length) != CRYPT_OK) - return false; - - // Create RSA key - if(rsa_import(decoded_key, decoded_length, key) != CRYPT_OK) - return false; - - return true; -} - -static void GetPlainAnsiFileName( - const TCHAR * szFileName, - char * szPlainName) -{ - const TCHAR * szPlainNameT = GetPlainFileName(szFileName); - - // Convert the plain name to ANSI - while(*szPlainNameT != 0) - *szPlainName++ = (char)*szPlainNameT++; - *szPlainName = 0; -} - -// Calculate begin and end of the MPQ archive -static void CalculateArchiveRange( - TMPQArchive * ha, - PMPQ_SIGNATURE_INFO pSI) -{ - ULONGLONG TempPos = 0; - char szMapHeader[0x200]; - - // Get the MPQ begin - pSI->BeginMpqData = ha->MpqPos; - - // Warcraft III maps are signed from the map header to the end - if(FileStream_Read(ha->pStream, &TempPos, szMapHeader, sizeof(szMapHeader))) - { - // Is it a map header ? - if(szMapHeader[0] == 'H' && szMapHeader[1] == 'M' && szMapHeader[2] == '3' && szMapHeader[3] == 'W') - { - // We will have to hash since the map header - pSI->BeginMpqData = 0; - } - } - - // Get the MPQ data end. This is stored in the MPQ header - pSI->EndMpqData = ha->MpqPos + ha->pHeader->ArchiveSize64; - - // Get the size of the entire file - FileStream_GetSize(ha->pStream, &pSI->EndOfFile); -} - -static bool CalculateMpqHashMd5( - TMPQArchive * ha, - PMPQ_SIGNATURE_INFO pSI, - LPBYTE pMd5Digest) -{ - hash_state md5_state; - ULONGLONG BeginBuffer; - ULONGLONG EndBuffer; - LPBYTE pbDigestBuffer = NULL; - - // Allocate buffer for creating the MPQ digest. - pbDigestBuffer = STORM_ALLOC(BYTE, MPQ_DIGEST_UNIT_SIZE); - if(pbDigestBuffer == NULL) - return false; - - // Initialize the MD5 hash state - md5_init(&md5_state); - - // Set the byte offset of begin of the data - BeginBuffer = pSI->BeginMpqData; - - // Create the digest - for(;;) - { - ULONGLONG BytesRemaining; - LPBYTE pbSigBegin = NULL; - LPBYTE pbSigEnd = NULL; - DWORD dwToRead = MPQ_DIGEST_UNIT_SIZE; - - // Check the number of bytes remaining - BytesRemaining = pSI->EndMpqData - BeginBuffer; - if(BytesRemaining < MPQ_DIGEST_UNIT_SIZE) - dwToRead = (DWORD)BytesRemaining; - if(dwToRead == 0) - break; - - // Read the next chunk - if(!FileStream_Read(ha->pStream, &BeginBuffer, pbDigestBuffer, dwToRead)) - { - STORM_FREE(pbDigestBuffer); - return false; - } - - // Move the current byte offset - EndBuffer = BeginBuffer + dwToRead; - - // Check if the signature is within the loaded digest - if(BeginBuffer <= pSI->BeginExclude && pSI->BeginExclude < EndBuffer) - pbSigBegin = pbDigestBuffer + (size_t)(pSI->BeginExclude - BeginBuffer); - if(BeginBuffer <= pSI->EndExclude && pSI->EndExclude < EndBuffer) - pbSigEnd = pbDigestBuffer + (size_t)(pSI->EndExclude - BeginBuffer); - - // Zero the part that belongs to the signature - if(pbSigBegin != NULL || pbSigEnd != NULL) - { - if(pbSigBegin == NULL) - pbSigBegin = pbDigestBuffer; - if(pbSigEnd == NULL) - pbSigEnd = pbDigestBuffer + dwToRead; - - memset(pbSigBegin, 0, (pbSigEnd - pbSigBegin)); - } - - // Pass the buffer to the hashing function - md5_process(&md5_state, pbDigestBuffer, dwToRead); - - // Move pointers - BeginBuffer += dwToRead; - } - - // Finalize the MD5 hash - md5_done(&md5_state, pMd5Digest); - STORM_FREE(pbDigestBuffer); - return true; -} - -static void AddTailToSha1( - hash_state * psha1_state, - const char * szTail) -{ - unsigned char * pbTail = (unsigned char *)szTail; - unsigned char szUpperCase[0x200]; - unsigned long nLength = 0; - - // Convert the tail to uppercase - // Note that we don't need to terminate the string with zero - while(*pbTail != 0) - { - szUpperCase[nLength++] = AsciiToUpperTable[*pbTail++]; - } - - // Append the tail to the SHA1 - sha1_process(psha1_state, szUpperCase, nLength); -} - -static bool CalculateMpqHashSha1( - TMPQArchive * ha, - PMPQ_SIGNATURE_INFO pSI, - unsigned char * sha1_tail0, - unsigned char * sha1_tail1, - unsigned char * sha1_tail2) -{ - ULONGLONG BeginBuffer; - hash_state sha1_state_temp; - hash_state sha1_state; - LPBYTE pbDigestBuffer = NULL; - char szPlainName[MAX_PATH]; - - // Allocate buffer for creating the MPQ digest. - pbDigestBuffer = STORM_ALLOC(BYTE, MPQ_DIGEST_UNIT_SIZE); - if(pbDigestBuffer == NULL) - return false; - - // Initialize SHA1 state structure - sha1_init(&sha1_state); - - // Calculate begin of data to be hashed - BeginBuffer = pSI->BeginMpqData; - - // Create the digest - for(;;) - { - ULONGLONG BytesRemaining; - DWORD dwToRead = MPQ_DIGEST_UNIT_SIZE; - - // Check the number of bytes remaining - BytesRemaining = pSI->EndMpqData - BeginBuffer; - if(BytesRemaining < MPQ_DIGEST_UNIT_SIZE) - dwToRead = (DWORD)BytesRemaining; - if(dwToRead == 0) - break; - - // Read the next chunk - if(!FileStream_Read(ha->pStream, &BeginBuffer, pbDigestBuffer, dwToRead)) - { - STORM_FREE(pbDigestBuffer); - return false; - } - - // Pass the buffer to the hashing function - sha1_process(&sha1_state, pbDigestBuffer, dwToRead); - - // Move pointers - BeginBuffer += dwToRead; - } - - // Add all three known tails and generate three hashes - memcpy(&sha1_state_temp, &sha1_state, sizeof(hash_state)); - sha1_done(&sha1_state_temp, sha1_tail0); - - memcpy(&sha1_state_temp, &sha1_state, sizeof(hash_state)); - GetPlainAnsiFileName(FileStream_GetFileName(ha->pStream), szPlainName); - AddTailToSha1(&sha1_state_temp, szPlainName); - sha1_done(&sha1_state_temp, sha1_tail1); - - memcpy(&sha1_state_temp, &sha1_state, sizeof(hash_state)); - AddTailToSha1(&sha1_state_temp, "ARCHIVE"); - sha1_done(&sha1_state_temp, sha1_tail2); - - // Finalize the MD5 hash - STORM_FREE(pbDigestBuffer); - return true; -} - -static DWORD VerifyRawMpqData( - TMPQArchive * ha, - ULONGLONG ByteOffset, - DWORD dwDataSize) -{ - ULONGLONG DataOffset = ha->MpqPos + ByteOffset; - LPBYTE pbDataChunk; - LPBYTE pbMD5Array1; // Calculated MD5 array - LPBYTE pbMD5Array2; // MD5 array loaded from the MPQ - DWORD dwBytesInChunk; - DWORD dwChunkCount; - DWORD dwChunkSize = ha->pHeader->dwRawChunkSize; - DWORD dwMD5Size; - DWORD dwErrCode = ERROR_SUCCESS; - - // Don't verify zero-sized blocks - if(dwDataSize == 0) - return ERROR_SUCCESS; - - // Get the number of data chunks to calculate MD5 - assert(dwChunkSize != 0); - dwChunkCount = ((dwDataSize - 1) / dwChunkSize) + 1; - dwMD5Size = dwChunkCount * MD5_DIGEST_SIZE; - - // Allocate space for data chunk and for the MD5 array - pbDataChunk = STORM_ALLOC(BYTE, dwChunkSize); - if(pbDataChunk == NULL) - return ERROR_NOT_ENOUGH_MEMORY; - - // Allocate space for MD5 array - pbMD5Array1 = STORM_ALLOC(BYTE, dwMD5Size); - pbMD5Array2 = STORM_ALLOC(BYTE, dwMD5Size); - if(pbMD5Array1 == NULL || pbMD5Array2 == NULL) - dwErrCode = ERROR_NOT_ENOUGH_MEMORY; - - // Calculate MD5 of each data chunk - if(dwErrCode == ERROR_SUCCESS) - { - LPBYTE pbMD5 = pbMD5Array1; - - for(DWORD i = 0; i < dwChunkCount; i++) - { - // Get the number of bytes in the chunk - dwBytesInChunk = STORMLIB_MIN(dwChunkSize, dwDataSize); - - // Read the data chunk - if(!FileStream_Read(ha->pStream, &DataOffset, pbDataChunk, dwBytesInChunk)) - { - dwErrCode = ERROR_FILE_CORRUPT; - break; - } - - // Calculate MD5 - CalculateDataBlockHash(pbDataChunk, dwBytesInChunk, pbMD5); - - // Move pointers and offsets - DataOffset += dwBytesInChunk; - dwDataSize -= dwBytesInChunk; - pbMD5 += MD5_DIGEST_SIZE; - } - } - - // Read the MD5 array - if(dwErrCode == ERROR_SUCCESS) - { - // Read the array of MD5 - if(!FileStream_Read(ha->pStream, &DataOffset, pbMD5Array2, dwMD5Size)) - dwErrCode = GetLastError(); - } - - // Compare the array of MD5 - if(dwErrCode == ERROR_SUCCESS) - { - // Compare the MD5 - if(memcmp(pbMD5Array1, pbMD5Array2, dwMD5Size)) - dwErrCode = ERROR_FILE_CORRUPT; - } - - // Free memory and return result - if(pbMD5Array2 != NULL) - STORM_FREE(pbMD5Array2); - if(pbMD5Array1 != NULL) - STORM_FREE(pbMD5Array1); - if(pbDataChunk != NULL) - STORM_FREE(pbDataChunk); - return dwErrCode; -} - -static DWORD VerifyWeakSignature( - TMPQArchive * ha, - PMPQ_SIGNATURE_INFO pSI) -{ - BYTE RevSignature[MPQ_WEAK_SIGNATURE_SIZE]; - BYTE Md5Digest[MD5_DIGEST_SIZE]; - rsa_key key; - int hash_idx = find_hash("md5"); - int result = 0; - - // The signature might be zeroed out. In that case, we ignore it - if(!IsValidSignature(pSI->Signature)) - return ERROR_WEAK_SIGNATURE_OK; - - // Calculate hash of the entire archive, skipping the (signature) file - if(!CalculateMpqHashMd5(ha, pSI, Md5Digest)) - return ERROR_VERIFY_FAILED; - - // Import the Blizzard key in OpenSSL format - if(!decode_base64_key(szBlizzardWeakPublicKey, &key)) - return ERROR_VERIFY_FAILED; - - // Verify the signature - memcpy(RevSignature, &pSI->Signature[8], MPQ_WEAK_SIGNATURE_SIZE); - memrev(RevSignature, MPQ_WEAK_SIGNATURE_SIZE); - rsa_verify_hash_ex(RevSignature, MPQ_WEAK_SIGNATURE_SIZE, Md5Digest, sizeof(Md5Digest), LTC_LTC_PKCS_1_V1_5, hash_idx, 0, &result, &key); - rsa_free(&key); - - // Return the result - return result ? ERROR_WEAK_SIGNATURE_OK : ERROR_WEAK_SIGNATURE_ERROR; -} - -static DWORD VerifyStrongSignatureWithKey( - unsigned char * reversed_signature, - unsigned char * padded_digest, - const char * szPublicKey) -{ - rsa_key key; - int result = 0; - - // Import the Blizzard key in OpenSSL format - if(!decode_base64_key(szPublicKey, &key)) - { - assert(false); - return ERROR_VERIFY_FAILED; - } - - // Verify the signature - if(rsa_verify_simple(reversed_signature, MPQ_STRONG_SIGNATURE_SIZE, padded_digest, MPQ_STRONG_SIGNATURE_SIZE, &result, &key) != CRYPT_OK) - return ERROR_VERIFY_FAILED; - - // Free the key and return result - rsa_free(&key); - return result ? ERROR_STRONG_SIGNATURE_OK : ERROR_STRONG_SIGNATURE_ERROR; -} - -static DWORD VerifyStrongSignature( - TMPQArchive * ha, - PMPQ_SIGNATURE_INFO pSI) -{ - unsigned char reversed_signature[MPQ_STRONG_SIGNATURE_SIZE]; - unsigned char Sha1Digest_tail0[SHA1_DIGEST_SIZE]; - unsigned char Sha1Digest_tail1[SHA1_DIGEST_SIZE]; - unsigned char Sha1Digest_tail2[SHA1_DIGEST_SIZE]; - unsigned char padded_digest[MPQ_STRONG_SIGNATURE_SIZE]; - DWORD dwResult; - size_t digest_offset; - - // Calculate SHA1 hash of the archive - if(!CalculateMpqHashSha1(ha, pSI, Sha1Digest_tail0, Sha1Digest_tail1, Sha1Digest_tail2)) - return ERROR_VERIFY_FAILED; - - // Prepare the signature for decryption - memcpy(reversed_signature, &pSI->Signature[4], MPQ_STRONG_SIGNATURE_SIZE); - memrev(reversed_signature, MPQ_STRONG_SIGNATURE_SIZE); - - // Prepare the padded digest for comparison - digest_offset = sizeof(padded_digest) - SHA1_DIGEST_SIZE; - memset(padded_digest, 0xbb, digest_offset); - padded_digest[0] = 0x0b; - - // Try Blizzard Strong public key with no SHA1 tail - memcpy(padded_digest + digest_offset, Sha1Digest_tail0, SHA1_DIGEST_SIZE); - memrev(padded_digest + digest_offset, SHA1_DIGEST_SIZE); - dwResult = VerifyStrongSignatureWithKey(reversed_signature, padded_digest, szBlizzardStrongPublicKey); - if(dwResult == ERROR_STRONG_SIGNATURE_OK) - return dwResult; - - // Try War 3 map public key with plain file name as SHA1 tail - memcpy(padded_digest + digest_offset, Sha1Digest_tail1, SHA1_DIGEST_SIZE); - memrev(padded_digest + digest_offset, SHA1_DIGEST_SIZE); - dwResult = VerifyStrongSignatureWithKey(reversed_signature, padded_digest, szWarcraft3MapPublicKey); - if(dwResult == ERROR_STRONG_SIGNATURE_OK) - return dwResult; - - // Try WoW-TBC public key with "ARCHIVE" as SHA1 tail - memcpy(padded_digest + digest_offset, Sha1Digest_tail2, SHA1_DIGEST_SIZE); - memrev(padded_digest + digest_offset, SHA1_DIGEST_SIZE); - dwResult = VerifyStrongSignatureWithKey(reversed_signature, padded_digest, szWowPatchPublicKey); - if(dwResult == ERROR_STRONG_SIGNATURE_OK) - return dwResult; - - // Try Survey public key with no SHA1 tail - memcpy(padded_digest + digest_offset, Sha1Digest_tail0, SHA1_DIGEST_SIZE); - memrev(padded_digest + digest_offset, SHA1_DIGEST_SIZE); - dwResult = VerifyStrongSignatureWithKey(reversed_signature, padded_digest, szWowSurveyPublicKey); - if(dwResult == ERROR_STRONG_SIGNATURE_OK) - return dwResult; - - // Try Starcraft II public key with no SHA1 tail - memcpy(padded_digest + digest_offset, Sha1Digest_tail0, SHA1_DIGEST_SIZE); - memrev(padded_digest + digest_offset, SHA1_DIGEST_SIZE); - dwResult = VerifyStrongSignatureWithKey(reversed_signature, padded_digest, szStarcraft2MapPublicKey); - if(dwResult == ERROR_STRONG_SIGNATURE_OK) - return dwResult; - - return ERROR_STRONG_SIGNATURE_ERROR; -} - -static DWORD VerifyFile( - HANDLE hMpq, - const char * szFileName, - LPDWORD pdwCrc32, - char * pMD5, - DWORD dwFlags) -{ - hash_state md5_state; - unsigned char * pFileMd5; - unsigned char md5[MD5_DIGEST_SIZE]; - TFileEntry * pFileEntry; - TMPQFile * hf; - BYTE Buffer[0x1000]; - HANDLE hFile = NULL; - DWORD dwVerifyResult = 0; - DWORD dwTotalBytes = 0; - DWORD dwCrc32 = 0; - - // - // Note: When the MPQ is patched, it will - // automatically check the patched version of the file - // - - // Make sure the md5 is initialized - memset(md5, 0, sizeof(md5)); - - // If we have to verify raw data MD5, do it before file open - if(dwFlags & SFILE_VERIFY_RAW_MD5) - { - TMPQArchive * ha = (TMPQArchive *)hMpq; - - // Parse the base MPQ and all patches - while(ha != NULL) - { - // Does the archive have support for raw MD5? - if(ha->pHeader->dwRawChunkSize != 0) - { - // The file has raw MD5 if the archive supports it - dwVerifyResult |= VERIFY_FILE_HAS_RAW_MD5; - - // Find file entry for the file - pFileEntry = GetFileEntryLocale(ha, szFileName, g_lcFileLocale); - if(pFileEntry != NULL) - { - // If the file's raw MD5 doesn't match, don't bother with more checks - if(VerifyRawMpqData(ha, pFileEntry->ByteOffset, pFileEntry->dwCmpSize) != ERROR_SUCCESS) - return dwVerifyResult | VERIFY_FILE_RAW_MD5_ERROR; - } - } - - // Move to the next patch - ha = ha->haPatch; - } - } - - // Attempt to open the file - if(SFileOpenFileEx(hMpq, szFileName, SFILE_OPEN_FROM_MPQ, &hFile)) - { - // Get the file size - hf = (TMPQFile *)hFile; - pFileEntry = hf->pFileEntry; - dwTotalBytes = SFileGetFileSize(hFile, NULL); - - // Initialize the CRC32 and MD5 contexts - md5_init(&md5_state); - dwCrc32 = crc32(0, Z_NULL, 0); - - // Also turn on sector checksum verification - if(dwFlags & SFILE_VERIFY_SECTOR_CRC) - hf->bCheckSectorCRCs = true; - - // Go through entire file and update both CRC32 and MD5 - for(;;) - { - DWORD dwBytesRead = 0; - - // Read data from file - SFileReadFile(hFile, Buffer, sizeof(Buffer), &dwBytesRead, NULL); - if(dwBytesRead == 0) - { - if(GetLastError() == ERROR_CHECKSUM_ERROR) - dwVerifyResult |= VERIFY_FILE_SECTOR_CRC_ERROR; - break; - } - - // Update CRC32 value - if(dwFlags & SFILE_VERIFY_FILE_CRC) - dwCrc32 = crc32(dwCrc32, Buffer, dwBytesRead); - - // Update MD5 value - if(dwFlags & SFILE_VERIFY_FILE_MD5) - md5_process(&md5_state, Buffer, dwBytesRead); - - // Decrement the total size - dwTotalBytes -= dwBytesRead; - } - - // If the file has sector checksums, indicate it in the flags - if(dwFlags & SFILE_VERIFY_SECTOR_CRC) - { - if((hf->pFileEntry->dwFlags & MPQ_FILE_SECTOR_CRC) && hf->SectorChksums != NULL && hf->SectorChksums[0] != 0) - dwVerifyResult |= VERIFY_FILE_HAS_SECTOR_CRC; - } - - // Check if the entire file has been read - // No point in checking CRC32 and MD5 if not - // Skip checksum checks if the file has patches - if(dwTotalBytes == 0) - { - // Check CRC32 and MD5 only if there is no patches - if(hf->hfPatch == NULL) - { - // Check if the CRC32 matches. - if(dwFlags & SFILE_VERIFY_FILE_CRC) - { - // Only check the CRC32 if it is valid - if(pFileEntry->dwCrc32 != 0) - { - dwVerifyResult |= VERIFY_FILE_HAS_CHECKSUM; - if(dwCrc32 != pFileEntry->dwCrc32) - dwVerifyResult |= VERIFY_FILE_CHECKSUM_ERROR; - } - } - - // Check if MD5 matches - if(dwFlags & SFILE_VERIFY_FILE_MD5) - { - // Patch files have their MD5 saved in the patch info - pFileMd5 = (hf->pPatchInfo != NULL) ? hf->pPatchInfo->md5 : pFileEntry->md5; - md5_done(&md5_state, md5); - - // Only check the MD5 if it is valid - if(IsValidMD5(pFileMd5)) - { - dwVerifyResult |= VERIFY_FILE_HAS_MD5; - if(memcmp(md5, pFileMd5, MD5_DIGEST_SIZE)) - dwVerifyResult |= VERIFY_FILE_MD5_ERROR; - } - } - } - else - { - // Patched files are MD5-checked automatically - dwVerifyResult |= VERIFY_FILE_HAS_MD5; - } - } - else - { - dwVerifyResult |= VERIFY_READ_ERROR; - } - - SFileCloseFile(hFile); - } - else - { - // Remember that the file couldn't be open - dwVerifyResult |= VERIFY_OPEN_ERROR; - } - - // If the caller required CRC32 and/or MD5, give it to him - if(pdwCrc32 != NULL) - *pdwCrc32 = dwCrc32; - if(pMD5 != NULL) - memcpy(pMD5, md5, MD5_DIGEST_SIZE); - - return dwVerifyResult; -} - -// Used in SFileGetFileInfo -bool QueryMpqSignatureInfo( - TMPQArchive * ha, - PMPQ_SIGNATURE_INFO pSI) -{ - TFileEntry * pFileEntry; - ULONGLONG ExtraBytes; - DWORD dwFileSize; - - // Make sure it's all zeroed - memset(pSI, 0, sizeof(MPQ_SIGNATURE_INFO)); - - // Calculate the range of the MPQ - CalculateArchiveRange(ha, pSI); - - // If there is "(signature)" file in the MPQ, it has a weak signature - pFileEntry = GetFileEntryLocale(ha, SIGNATURE_NAME, LANG_NEUTRAL); - if(pFileEntry != NULL) - { - // Calculate the begin and end of the signature file itself - pSI->BeginExclude = ha->MpqPos + pFileEntry->ByteOffset; - pSI->EndExclude = pSI->BeginExclude + pFileEntry->dwCmpSize; - dwFileSize = (DWORD)(pSI->EndExclude - pSI->BeginExclude); - - // Does the signature have proper size? - if(dwFileSize == MPQ_SIGNATURE_FILE_SIZE) - { - // Read the weak signature - if(!FileStream_Read(ha->pStream, &pSI->BeginExclude, pSI->Signature, dwFileSize)) - return false; - - pSI->SignatureTypes |= SIGNATURE_TYPE_WEAK; - pSI->cbSignatureSize = dwFileSize; - return true; - } - } - - // If there is extra bytes beyond the end of the archive, - // it's the strong signature - ExtraBytes = pSI->EndOfFile - pSI->EndMpqData; - if(ExtraBytes >= (MPQ_STRONG_SIGNATURE_SIZE + 4)) - { - // Read the strong signature - if(!FileStream_Read(ha->pStream, &pSI->EndMpqData, pSI->Signature, (MPQ_STRONG_SIGNATURE_SIZE + 4))) - return false; - - // Check the signature header "NGIS" - if(pSI->Signature[0] != 'N' || pSI->Signature[1] != 'G' || pSI->Signature[2] != 'I' || pSI->Signature[3] != 'S') - return true; //Not a valid signature, but another filetype could've been appended so not always an error. - - pSI->SignatureTypes |= SIGNATURE_TYPE_STRONG; - return true; - } - - // Succeeded, but no known signature found - return true; -} - -//----------------------------------------------------------------------------- -// Support for weak signature - -DWORD SSignFileCreate(TMPQArchive * ha) -{ - TMPQFile * hf = NULL; - BYTE EmptySignature[MPQ_SIGNATURE_FILE_SIZE]; - DWORD dwErrCode = ERROR_SUCCESS; - - // Only save the signature if we should do so - if(ha->dwFileFlags3 != 0) - { - // The (signature) file must be non-encrypted and non-compressed - assert(ha->dwFlags & MPQ_FLAG_SIGNATURE_NEW); - assert(ha->dwFileFlags3 == MPQ_FILE_EXISTS); - assert(ha->dwReservedFiles > 0); - - // Create the (signature) file file in the MPQ - // Note that the file must not be compressed or encrypted - dwErrCode = SFileAddFile_Init(ha, SIGNATURE_NAME, - 0, - sizeof(EmptySignature), - LANG_NEUTRAL, - ha->dwFileFlags3 | MPQ_FILE_REPLACEEXISTING, - &hf); - - // Write the empty signature file to the archive - if(dwErrCode == ERROR_SUCCESS) - { - // Write the empty zeroed file to the MPQ - memset(EmptySignature, 0, sizeof(EmptySignature)); - dwErrCode = SFileAddFile_Write(hf, EmptySignature, (DWORD)sizeof(EmptySignature), 0); - SFileAddFile_Finish(hf); - - // Clear the invalid mark - ha->dwFlags &= ~(MPQ_FLAG_SIGNATURE_NEW | MPQ_FLAG_SIGNATURE_NONE); - ha->dwReservedFiles--; - } - } - - return dwErrCode; -} - -DWORD SSignFileFinish(TMPQArchive * ha) -{ - MPQ_SIGNATURE_INFO si; - unsigned long signature_len = MPQ_WEAK_SIGNATURE_SIZE; - BYTE WeakSignature[MPQ_SIGNATURE_FILE_SIZE]; - BYTE Md5Digest[MD5_DIGEST_SIZE]; - rsa_key key; - int hash_idx = find_hash("md5"); - - // Sanity checks - assert((ha->dwFlags & MPQ_FLAG_CHANGED) == 0); - assert(ha->dwFileFlags3 == MPQ_FILE_EXISTS); - - // Query the weak signature info - memset(&si, 0, sizeof(MPQ_SIGNATURE_INFO)); - if(!QueryMpqSignatureInfo(ha, &si)) - return ERROR_FILE_CORRUPT; - - // There must be exactly one signature - if(si.SignatureTypes != SIGNATURE_TYPE_WEAK) - return ERROR_FILE_CORRUPT; - - // Calculate MD5 of the entire archive - if(!CalculateMpqHashMd5(ha, &si, Md5Digest)) - return ERROR_VERIFY_FAILED; - - // Decode the private key - if(!decode_base64_key(szBlizzardWeakPrivateKey, &key)) - return ERROR_VERIFY_FAILED; - - // Sign the hash - memset(WeakSignature, 0, sizeof(WeakSignature)); - rsa_sign_hash_ex(Md5Digest, sizeof(Md5Digest), WeakSignature + 8, &signature_len, LTC_LTC_PKCS_1_V1_5, 0, 0, hash_idx, 0, &key); - memrev(WeakSignature + 8, MPQ_WEAK_SIGNATURE_SIZE); - rsa_free(&key); - - // Write the signature to the MPQ. Don't use SFile* functions, but write the hash directly - if(!FileStream_Write(ha->pStream, &si.BeginExclude, WeakSignature, MPQ_SIGNATURE_FILE_SIZE)) - return GetLastError(); - - return ERROR_SUCCESS; -} - -//----------------------------------------------------------------------------- -// Public (exported) functions - -bool WINAPI SFileGetFileChecksums(HANDLE hMpq, const char * szFileName, LPDWORD pdwCrc32, char * pMD5) -{ - DWORD dwVerifyResult; - DWORD dwVerifyFlags = 0; - - if(pdwCrc32 != NULL) - dwVerifyFlags |= SFILE_VERIFY_FILE_CRC; - if(pMD5 != NULL) - dwVerifyFlags |= SFILE_VERIFY_FILE_MD5; - - dwVerifyResult = VerifyFile(hMpq, - szFileName, - pdwCrc32, - pMD5, - dwVerifyFlags); - - // If verification failed, return zero - if(dwVerifyResult & VERIFY_FILE_ERROR_MASK) - { - SetLastError(ERROR_FILE_CORRUPT); - return false; - } - - return true; -} - - -DWORD WINAPI SFileVerifyFile(HANDLE hMpq, const char * szFileName, DWORD dwFlags) -{ - return VerifyFile(hMpq, - szFileName, - NULL, - NULL, - dwFlags); -} - -// Verifies raw data of the archive Only works for MPQs version 4 or newer -DWORD WINAPI SFileVerifyRawData(HANDLE hMpq, DWORD dwWhatToVerify, const char * szFileName) -{ - TMPQArchive * ha = (TMPQArchive *)hMpq; - TFileEntry * pFileEntry; - TMPQHeader * pHeader; - - // Verify input parameters - if(!IsValidMpqHandle(hMpq)) - return ERROR_INVALID_PARAMETER; - pHeader = ha->pHeader; - - // If the archive doesn't have raw data MD5, report it as OK - if(pHeader->dwRawChunkSize == 0) - return ERROR_SUCCESS; - - // If we have to verify MPQ header, do it - switch(dwWhatToVerify) - { - case SFILE_VERIFY_MPQ_HEADER: - - // Only if the header is of version 4 or newer - if(pHeader->dwHeaderSize >= (MPQ_HEADER_SIZE_V4 - MD5_DIGEST_SIZE)) - return VerifyRawMpqData(ha, 0, MPQ_HEADER_SIZE_V4 - MD5_DIGEST_SIZE); - return ERROR_SUCCESS; - - case SFILE_VERIFY_HET_TABLE: - - // Only if we have HET table - if(pHeader->HetTablePos64 && pHeader->HetTableSize64) - return VerifyRawMpqData(ha, pHeader->HetTablePos64, (DWORD)pHeader->HetTableSize64); - return ERROR_SUCCESS; - - case SFILE_VERIFY_BET_TABLE: - - // Only if we have BET table - if(pHeader->BetTablePos64 && pHeader->BetTableSize64) - return VerifyRawMpqData(ha, pHeader->BetTablePos64, (DWORD)pHeader->BetTableSize64); - return ERROR_SUCCESS; - - case SFILE_VERIFY_HASH_TABLE: - - // Hash table is not protected by MD5 - return ERROR_SUCCESS; - - case SFILE_VERIFY_BLOCK_TABLE: - - // Block table is not protected by MD5 - return ERROR_SUCCESS; - - case SFILE_VERIFY_HIBLOCK_TABLE: - - // It is unknown if the hi-block table is protected my MD5 or not. - return ERROR_SUCCESS; - - case SFILE_VERIFY_FILE: - - // Verify parameters - if(szFileName == NULL || *szFileName == 0) - return ERROR_INVALID_PARAMETER; - - // Get the offset of a file - pFileEntry = GetFileEntryLocale(ha, szFileName, g_lcFileLocale); - if(pFileEntry == NULL) - return ERROR_FILE_NOT_FOUND; - - return VerifyRawMpqData(ha, pFileEntry->ByteOffset, pFileEntry->dwCmpSize); - } - - return ERROR_INVALID_PARAMETER; -} - - -// Verifies the archive against the signature -DWORD WINAPI SFileVerifyArchive(HANDLE hMpq) -{ - MPQ_SIGNATURE_INFO si; - TMPQArchive * ha = (TMPQArchive *)hMpq; - - // Verify input parameters - if(!IsValidMpqHandle(hMpq)) - return ERROR_VERIFY_FAILED; - - // If the archive was modified, we need to flush it - if(ha->dwFlags & MPQ_FLAG_CHANGED) - SFileFlushArchive(hMpq); - - // Get the MPQ signature and signature type - memset(&si, 0, sizeof(MPQ_SIGNATURE_INFO)); - if(!QueryMpqSignatureInfo(ha, &si)) - return ERROR_VERIFY_FAILED; - - // If there is no signature - if(si.SignatureTypes == 0) - return ERROR_NO_SIGNATURE; - - // We haven't seen a MPQ with both signatures - assert(si.SignatureTypes == SIGNATURE_TYPE_WEAK || si.SignatureTypes == SIGNATURE_TYPE_STRONG); - - // Verify the strong signature, if present - if(si.SignatureTypes & SIGNATURE_TYPE_STRONG) - return VerifyStrongSignature(ha, &si); - - // Verify the weak signature, if present - if(si.SignatureTypes & SIGNATURE_TYPE_WEAK) - return VerifyWeakSignature(ha, &si); - - return ERROR_NO_SIGNATURE; -} - -// Verifies the archive against the signature -bool WINAPI SFileSignArchive(HANDLE hMpq, DWORD dwSignatureType) -{ - TMPQArchive * ha; - - // Verify the archive handle - ha = IsValidMpqHandle(hMpq); - if(ha == NULL) - { - SetLastError(ERROR_INVALID_PARAMETER); - return false; - } - - // We only support weak signature, and only for MPQs version 1.0 - if(dwSignatureType != SIGNATURE_TYPE_WEAK) - { - SetLastError(ERROR_INVALID_PARAMETER); - return false; - } - - // The archive must not be malformed and must not be read-only - if(ha->dwFlags & (MPQ_FLAG_READ_ONLY | MPQ_FLAG_MALFORMED)) - { - SetLastError(ERROR_ACCESS_DENIED); - return false; - } - - // If the signature is not there yet - if(ha->dwFileFlags3 == 0) - { - // Turn the signature on. The signature will - // be applied when the archive is closed - ha->dwFlags |= MPQ_FLAG_SIGNATURE_NEW | MPQ_FLAG_CHANGED; - ha->dwFileFlags3 = MPQ_FILE_EXISTS; - ha->dwReservedFiles++; - } - - return true; -} - diff --git a/app/jni/src/libultraship/extern/StormLib/src/StormCommon.h b/app/jni/src/libultraship/extern/StormLib/src/StormCommon.h deleted file mode 100644 index 48fd86f..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/StormCommon.h +++ /dev/null @@ -1,440 +0,0 @@ -/*****************************************************************************/ -/* SCommon.h Copyright (c) Ladislav Zezula 2003 */ -/*---------------------------------------------------------------------------*/ -/* Common functions for encryption/decryption from Storm.dll. Included by */ -/* SFile*** functions, do not include and do not use this file directly */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 24.03.03 1.00 Lad The first version of SFileCommon.h */ -/* 12.06.04 1.00 Lad Renamed to SCommon.h */ -/* 06.09.10 1.00 Lad Renamed to StormCommon.h */ -/*****************************************************************************/ - -#ifndef __STORMCOMMON_H__ -#define __STORMCOMMON_H__ - -//----------------------------------------------------------------------------- -// Compression support - -// Include functions from Pkware Data Compression Library -#include "pklib/pklib.h" - -// Include functions from Huffmann compression -#include "huffman/huff.h" - -// Include functions from IMA ADPCM compression -#include "adpcm/adpcm.h" - -// Include functions from SPARSE compression -#include "sparse/sparse.h" - -// Include functions from LZMA compression -#include "lzma/C/LzmaEnc.h" -#include "lzma/C/LzmaDec.h" - -// Include functions from zlib -#ifndef __SYS_ZLIB - #include "zlib/zlib.h" -#else - #include -#endif - -// Include functions from bzlib -#ifndef __SYS_BZLIB - #include "bzip2/bzlib.h" -#else - #include -#endif - -//----------------------------------------------------------------------------- -// Cryptography support - -// Headers from LibTomCrypt -#include "libtomcrypt/src/headers/tomcrypt.h" - -// For HashStringJenkins -#include "jenkins/lookup.h" - -//----------------------------------------------------------------------------- -// StormLib private defines - -#define ID_MPQ_FILE 0x46494c45 // Used internally for checking TMPQFile ('FILE') - -// Prevent problems with CRT "min" and "max" functions, -// as they are not defined on all platforms -#define STORMLIB_MIN(a, b) ((a < b) ? a : b) -#define STORMLIB_MAX(a, b) ((a > b) ? a : b) -#define STORMLIB_UNUSED(p) ((void)(p)) - -// Checks for data pointers aligned to 4-byte boundary -#define STORMLIB_DWORD_ALIGNED(ptr) (((size_t)(ptr) & 0x03) == 0) - -// Macro for building 64-bit file offset from two 32-bit -#define MAKE_OFFSET64(hi, lo) (((ULONGLONG)hi << 32) | (ULONGLONG)lo) - -//----------------------------------------------------------------------------- -// MTYPE definition - specifies what kind of MPQ is the map type - -typedef enum _MTYPE -{ - MapTypeNotChecked, // The map type was not checked yet - MapTypeNotRecognized, // The file does not seems to be a map - MapTypeAviFile, // The file is actually an AVI file (Warcraft III cinematics) - MapTypeStarcraft, // The file is a Starcraft map - MapTypeWarcraft3, // The file is a Warcraft III map - MapTypeStarcraft2 // The file is a Starcraft II map -} MTYPE, *PMTYPE; - -//----------------------------------------------------------------------------- -// MPQ signature information - -// Size of each signature type -#define MPQ_WEAK_SIGNATURE_SIZE 64 -#define MPQ_STRONG_SIGNATURE_SIZE 256 -#define MPQ_STRONG_SIGNATURE_ID 0x5349474E // ID of the strong signature ("NGIS") -#define MPQ_SIGNATURE_FILE_SIZE (MPQ_WEAK_SIGNATURE_SIZE + 8) - -// MPQ signature info -typedef struct _MPQ_SIGNATURE_INFO -{ - ULONGLONG BeginMpqData; // File offset where the hashing starts - ULONGLONG BeginExclude; // Begin of the excluded area (used for (signature) file) - ULONGLONG EndExclude; // End of the excluded area (used for (signature) file) - ULONGLONG EndMpqData; // File offset where the hashing ends - ULONGLONG EndOfFile; // Size of the entire file - BYTE Signature[MPQ_STRONG_SIGNATURE_SIZE + 0x10]; - DWORD cbSignatureSize; // Length of the signature - DWORD SignatureTypes; // See SIGNATURE_TYPE_XXX - -} MPQ_SIGNATURE_INFO, *PMPQ_SIGNATURE_INFO; - -//----------------------------------------------------------------------------- -// Memory management -// -// We use our own macros for allocating/freeing memory. If you want -// to redefine them, please keep the following rules: -// -// - The memory allocation must return NULL if not enough memory -// (i.e not to throw exception) -// - The allocating function does not need to fill the allocated buffer with zeros -// - Memory freeing function doesn't have to test the pointer to NULL -// - -//#if defined(_MSC_VER) && defined(_DEBUG) -// -//#define STORM_ALLOC(type, nitems) (type *)HeapAlloc(GetProcessHeap(), 0, ((nitems) * sizeof(type))) -//#define STORM_REALLOC(type, ptr, nitems) (type *)HeapReAlloc(GetProcessHeap(), 0, ptr, ((nitems) * sizeof(type))) -//#define STORM_FREE(ptr) HeapFree(GetProcessHeap(), 0, ptr) -// -//#else - -#define STORM_ALLOC(type, nitems) (type *)malloc((nitems) * sizeof(type)) -#define STORM_REALLOC(type, ptr, nitems) (type *)realloc(ptr, ((nitems) * sizeof(type))) -#define STORM_FREE(ptr) free(ptr) - -//#endif - -//----------------------------------------------------------------------------- -// StormLib internal global variables - -extern DWORD g_dwMpqSignature; // Marker for MPQ header -extern DWORD g_dwHashTableKey; // Key for hash table -extern DWORD g_dwBlockTableKey; // Key for block table -extern LCID g_lcFileLocale; // Preferred file locale and platform - -//----------------------------------------------------------------------------- -// Conversion to uppercase/lowercase (and "/" to "\") - -extern unsigned char AsciiToLowerTable[256]; -extern unsigned char AsciiToUpperTable[256]; - -//----------------------------------------------------------------------------- -// Safe string functions - -template -XCHAR * IntToString(XCHAR * szBuffer, size_t cchMaxChars, XINT nValue, size_t nDigitCount = 0) -{ - XCHAR * szBufferEnd = szBuffer + cchMaxChars - 1; - XCHAR szNumberRev[0x20]; - size_t nLength = 0; - - // Always put the first digit - szNumberRev[nLength++] = (XCHAR)(nValue % 10) + '0'; - nValue /= 10; - - // Continue as long as we have non-zero - while(nValue != 0) - { - szNumberRev[nLength++] = (XCHAR)(nValue % 10) + '0'; - nValue /= 10; - } - - // Fill zeros, if needed - while(szBuffer < szBufferEnd && nLength < nDigitCount) - { - *szBuffer++ = '0'; - nDigitCount--; - } - - // Fill the buffer - while(szBuffer < szBufferEnd && nLength > 0) - { - nLength--; - *szBuffer++ = szNumberRev[nLength]; - } - - // Terminate the number with zeros - szBuffer[0] = 0; - return szBuffer; -} - -char * StringCopy(char * szTarget, size_t cchTarget, const char * szSource); -void StringCat(char * szTarget, size_t cchTargetMax, const char * szSource); -void StringCreatePseudoFileName(char * szBuffer, size_t cchMaxChars, unsigned int nIndex, const char * szExtension); - -#ifdef _UNICODE -void StringCopy(TCHAR * szTarget, size_t cchTarget, const char * szSource); -void StringCopy(char * szTarget, size_t cchTarget, const TCHAR * szSource); -void StringCopy(TCHAR * szTarget, size_t cchTarget, const TCHAR * szSource); -void StringCat(TCHAR * szTarget, size_t cchTargetMax, const TCHAR * szSource); -#endif - -//----------------------------------------------------------------------------- -// Encryption and decryption functions - -#define MPQ_HASH_TABLE_INDEX 0x000 -#define MPQ_HASH_NAME_A 0x100 -#define MPQ_HASH_NAME_B 0x200 -#define MPQ_HASH_FILE_KEY 0x300 -#define MPQ_HASH_KEY2_MIX 0x400 - -DWORD HashString(const char * szFileName, DWORD dwHashType); -DWORD HashStringSlash(const char * szFileName, DWORD dwHashType); -DWORD HashStringLower(const char * szFileName, DWORD dwHashType); - -void InitializeMpqCryptography(); - -DWORD GetNearestPowerOfTwo(DWORD dwFileCount); - -bool IsPseudoFileName(const char * szFileName, LPDWORD pdwFileIndex); -ULONGLONG HashStringJenkins(const char * szFileName); - -DWORD GetDefaultSpecialFileFlags(DWORD dwFileSize, USHORT wFormatVersion); - -void EncryptMpqBlock(void * pvDataBlock, DWORD dwLength, DWORD dwKey); -void DecryptMpqBlock(void * pvDataBlock, DWORD dwLength, DWORD dwKey); - -DWORD DetectFileKeyBySectorSize(LPDWORD EncryptedData, DWORD dwSectorSize, DWORD dwSectorOffsLen); -DWORD DetectFileKeyByContent(void * pvEncryptedData, DWORD dwSectorSize, DWORD dwFileSize); -DWORD DecryptFileKey(const char * szFileName, ULONGLONG MpqPos, DWORD dwFileSize, DWORD dwFlags); - -bool IsValidMD5(LPBYTE pbMd5); -bool IsValidSignature(LPBYTE pbSignature); -bool VerifyDataBlockHash(void * pvDataBlock, DWORD cbDataBlock, LPBYTE expected_md5); -void CalculateDataBlockHash(void * pvDataBlock, DWORD cbDataBlock, LPBYTE md5_hash); - -//----------------------------------------------------------------------------- -// Handle validation functions - -TMPQArchive * IsValidMpqHandle(HANDLE hMpq); -TMPQFile * IsValidFileHandle(HANDLE hFile); - -//----------------------------------------------------------------------------- -// Support for MPQ file tables - -ULONGLONG FileOffsetFromMpqOffset(TMPQArchive * ha, ULONGLONG MpqOffset); -ULONGLONG CalculateRawSectorOffset(TMPQFile * hf, DWORD dwSectorOffset); - -DWORD ConvertMpqHeaderToFormat4(TMPQArchive * ha, ULONGLONG MpqOffset, ULONGLONG FileSize, DWORD dwFlags, MTYPE MapType); - -bool IsValidHashEntry(TMPQArchive * ha, TMPQHash * pHash); - -TMPQHash * FindFreeHashEntry(TMPQArchive * ha, DWORD dwStartIndex, DWORD dwName1, DWORD dwName2, LCID lcFileLocale); -TMPQHash * GetFirstHashEntry(TMPQArchive * ha, const char * szFileName); -TMPQHash * GetNextHashEntry(TMPQArchive * ha, TMPQHash * pFirstHash, TMPQHash * pPrevHash); -TMPQHash * AllocateHashEntry(TMPQArchive * ha, TFileEntry * pFileEntry, LCID lcFileLocale); - -TMPQExtHeader * LoadExtTable(TMPQArchive * ha, ULONGLONG ByteOffset, size_t Size, DWORD dwSignature, DWORD dwKey); -TMPQHetTable * LoadHetTable(TMPQArchive * ha); -TMPQBetTable * LoadBetTable(TMPQArchive * ha); - -TMPQBlock * LoadBlockTable(TMPQArchive * ha, bool bDontFixEntries = false); -TMPQBlock * TranslateBlockTable(TMPQArchive * ha, ULONGLONG * pcbTableSize, bool * pbNeedHiBlockTable); - -ULONGLONG FindFreeMpqSpace(TMPQArchive * ha); - -// Functions that load the HET and BET tables -DWORD CreateHashTable(TMPQArchive * ha, DWORD dwHashTableSize); -DWORD LoadAnyHashTable(TMPQArchive * ha); -DWORD BuildFileTable(TMPQArchive * ha); -DWORD DefragmentFileTable(TMPQArchive * ha); - -DWORD CreateFileTable(TMPQArchive * ha, DWORD dwFileTableSize); -DWORD RebuildHetTable(TMPQArchive * ha); -DWORD RebuildFileTable(TMPQArchive * ha, DWORD dwNewHashTableSize); -DWORD SaveMPQTables(TMPQArchive * ha); - -TMPQHetTable * CreateHetTable(DWORD dwEntryCount, DWORD dwTotalCount, DWORD dwHashBitSize, LPBYTE pbSrcData); -void FreeHetTable(TMPQHetTable * pHetTable); - -TMPQBetTable * CreateBetTable(DWORD dwMaxFileCount); -void FreeBetTable(TMPQBetTable * pBetTable); - -// Functions for finding files in the file table -TFileEntry * GetFileEntryLocale(TMPQArchive * ha, const char * szFileName, LCID lcFileLocale, LPDWORD PtrHashIndex = NULL); -TFileEntry * GetFileEntryExact(TMPQArchive * ha, const char * szFileName, LCID lcFileLocale, LPDWORD PtrHashIndex); - -// Allocates file name in the file entry -void AllocateFileName(TMPQArchive * ha, TFileEntry * pFileEntry, const char * szFileName); - -// Allocates new file entry in the MPQ tables. Reuses existing, if possible -TFileEntry * AllocateFileEntry(TMPQArchive * ha, const char * szFileName, LCID lcFileLocale, LPDWORD PtrHashIndex); -DWORD RenameFileEntry(TMPQArchive * ha, TMPQFile * hf, const char * szNewFileName); -DWORD DeleteFileEntry(TMPQArchive * ha, TMPQFile * hf); - -// Invalidates entries for (listfile) and (attributes) -void InvalidateInternalFiles(TMPQArchive * ha); - -// Retrieves information about the strong signature -bool QueryMpqSignatureInfo(TMPQArchive * ha, PMPQ_SIGNATURE_INFO pSignatureInfo); - -//----------------------------------------------------------------------------- -// Support for alternate file formats (SBaseSubTypes.cpp) - -DWORD ConvertSqpHeaderToFormat4(TMPQArchive * ha, ULONGLONG FileSize, DWORD dwFlags); -TMPQHash * LoadSqpHashTable(TMPQArchive * ha); -TMPQBlock * LoadSqpBlockTable(TMPQArchive * ha); - -DWORD ConvertMpkHeaderToFormat4(TMPQArchive * ha, ULONGLONG FileSize, DWORD dwFlags); -void DecryptMpkTable(void * pvMpkTable, size_t cbSize); -TMPQHash * LoadMpkHashTable(TMPQArchive * ha); -TMPQBlock * LoadMpkBlockTable(TMPQArchive * ha); -int SCompDecompressMpk(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer); - -//----------------------------------------------------------------------------- -// Common functions - MPQ File - -TMPQFile * CreateFileHandle(TMPQArchive * ha, TFileEntry * pFileEntry); -TMPQFile * CreateWritableHandle(TMPQArchive * ha, DWORD dwFileSize); -void * LoadMpqTable(TMPQArchive * ha, ULONGLONG ByteOffset, LPBYTE pbTableHash, DWORD dwCompressedSize, DWORD dwRealSize, DWORD dwKey, DWORD * PtrRealTableSize); -DWORD AllocateSectorBuffer(TMPQFile * hf); -DWORD AllocatePatchInfo(TMPQFile * hf, bool bLoadFromFile); -DWORD AllocateSectorOffsets(TMPQFile * hf, bool bLoadFromFile); -DWORD AllocateSectorChecksums(TMPQFile * hf, bool bLoadFromFile); -DWORD WritePatchInfo(TMPQFile * hf); -DWORD WriteSectorOffsets(TMPQFile * hf); -DWORD WriteSectorChecksums(TMPQFile * hf); -DWORD WriteMemDataMD5(TFileStream * pStream, ULONGLONG RawDataOffs, void * pvRawData, DWORD dwRawDataSize, DWORD dwChunkSize, LPDWORD pcbTotalSize); -DWORD WriteMpqDataMD5(TFileStream * pStream, ULONGLONG RawDataOffs, DWORD dwRawDataSize, DWORD dwChunkSize); -void FreeFileHandle(TMPQFile *& hf); -void FreeArchiveHandle(TMPQArchive *& ha); - -//----------------------------------------------------------------------------- -// Patch functions - -// Structure used for the patching process -typedef struct _TMPQPatcher -{ - BYTE this_md5[MD5_DIGEST_SIZE]; // MD5 of the current file state - LPBYTE pbFileData1; // Primary working buffer - LPBYTE pbFileData2; // Secondary working buffer - DWORD cbMaxFileData; // Maximum allowed size of the patch data - DWORD cbFileData; // Current size of the result data - DWORD nCounter; // Counter of the patch process - -} TMPQPatcher; - -bool IsIncrementalPatchFile(const void * pvData, DWORD cbData, LPDWORD pdwPatchedFileSize); -DWORD Patch_InitPatcher(TMPQPatcher * pPatcher, TMPQFile * hf); -DWORD Patch_Process(TMPQPatcher * pPatcher, TMPQFile * hf); -void Patch_Finalize(TMPQPatcher * pPatcher); - -//----------------------------------------------------------------------------- -// Utility functions - -bool IsInternalMpqFileName(const char * szFileName); - -template -const XCHAR * GetPlainFileName(const XCHAR * szFileName) -{ - const XCHAR * szPlainName = szFileName; - - while(*szFileName != 0) - { - if(*szFileName == '\\' || *szFileName == '/') - szPlainName = szFileName + 1; - szFileName++; - } - - return szPlainName; -} - -//----------------------------------------------------------------------------- -// Internal support for MPQ modifications - -DWORD SFileAddFile_Init( - TMPQArchive * ha, - const char * szArchivedName, - ULONGLONG ft, - DWORD dwFileSize, - LCID lcFileLocale, - DWORD dwFlags, - TMPQFile ** phf - ); - -DWORD SFileAddFile_Init( - TMPQArchive * ha, - TMPQFile * hfSrc, - TMPQFile ** phf - ); - -DWORD SFileAddFile_Write( - TMPQFile * hf, - const void * pvData, - DWORD dwSize, - DWORD dwCompression - ); - -DWORD SFileAddFile_Finish( - TMPQFile * hf - ); - -//----------------------------------------------------------------------------- -// Attributes support - -DWORD SAttrLoadAttributes(TMPQArchive * ha); -DWORD SAttrFileSaveToMpq(TMPQArchive * ha); - -//----------------------------------------------------------------------------- -// Listfile functions - -DWORD SListFileSaveToMpq(TMPQArchive * ha); - -//----------------------------------------------------------------------------- -// Weak signature support - -DWORD SSignFileCreate(TMPQArchive * ha); -DWORD SSignFileFinish(TMPQArchive * ha); - -//----------------------------------------------------------------------------- -// Dump data support - -#ifdef __STORMLIB_DUMP_DATA__ - -void DumpMpqHeader(TMPQHeader * pHeader); -void DumpHashTable(TMPQHash * pHashTable, DWORD dwHashTableSize); -void DumpHetAndBetTable(TMPQHetTable * pHetTable, TMPQBetTable * pBetTable); -void DumpFileTable(TFileEntry * pFileTable, DWORD dwFileTableSize); - -#else - -#define DumpMpqHeader(h) /* */ -#define DumpHashTable(t, s) /* */ -#define DumpHetAndBetTable(t, s) /* */ -#define DumpFileTable(t, s) /* */ - -#endif - -#endif // __STORMCOMMON_H__ - diff --git a/app/jni/src/libultraship/extern/StormLib/src/StormLib.exp b/app/jni/src/libultraship/extern/StormLib/src/StormLib.exp deleted file mode 100644 index bf370aa..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/StormLib.exp +++ /dev/null @@ -1,74 +0,0 @@ -# -# Export file for Mac OS X -# Copyright (c) 2009 Sam Wilkins -# swilkins1337@gmail.com -# - -_SFileSetLocale -_SFileGetLocale - -_SFileOpenArchive -_SFileCreateArchive -_SFileFlushArchive -_SFileCloseArchive - -_SFileAddListFile - -_SFileSetCompactCallback -_SFileCompactArchive - -_SFileGetMaxFileCount -_SFileSetMaxFileCount - -_SFileGetAttributes -_SFileSetAttributes -_SFileUpdateFileAttributes - -_SFileOpenPatchArchive -_SFileIsPatchedArchive - -_SFileOpenFileEx -_SFileGetFileSize -_SFileSetFilePointer -_SFileReadFile -_SFileCloseFile - -_SFileHasFile -_SFileGetFileName -_SFileGetFileInfo - -_SFileExtractFile - -_SFileVerifyFile -_SFileVerifyRawData -_SFileVerifyArchive - -_SFileFindFirstFile -_SFileFindNextFile -_SFileFindClose - -_SListFileFindFirstFile -_SListFileFindNextFile -_SListFileFindClose - -_SFileEnumLocales - -_SFileCreateFile -_SFileWriteFile -_SFileFinishFile -_SFileAddFileEx -_SFileAddFile -_SFileAddWave -_SFileRemoveFile -_SFileRenameFile -_SFileSetFileLocale -_SFileSetDataCompression -_SFileSetAddFileCallback - -_SCompImplode -_SCompExplode -_SCompCompress -_SCompDecompress - -_SetLastError -_GetLastError diff --git a/app/jni/src/libultraship/extern/StormLib/src/StormLib.h b/app/jni/src/libultraship/extern/StormLib/src/StormLib.h deleted file mode 100644 index 6cf8cc5..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/StormLib.h +++ /dev/null @@ -1,1150 +0,0 @@ -/*****************************************************************************/ -/* StormLib.h Copyright (c) Ladislav Zezula 1999-2017 */ -/*---------------------------------------------------------------------------*/ -/* StormLib library v 9.22 */ -/* */ -/* Author : Ladislav Zezula */ -/* E-mail : ladik@zezula.net */ -/* WWW : http://www.zezula.net */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* xx.xx.99 1.00 Lad Created */ -/* 24.03.03 2.50 Lad Version 2.50 */ -/* 02.04.03 3.00 Lad Version 3.00 with compression */ -/* 11.04.03 3.01 Lad Renamed to StormLib.h for compatibility with */ -/* original headers for Storm.dll */ -/* 10.05.03 3.02 Lad Added Pkware DCL compression */ -/* 26.05.03 4.00 Lad Completed all compressions */ -/* 18.06.03 4.01 Lad Added SFileSetFileLocale */ -/* Added SFileExtractFile */ -/* 26.07.03 4.02 Lad Implemented nameless rename and delete */ -/* 26.07.03 4.03 Lad Added support for protected MPQs */ -/* 28.08.03 4.10 Lad Fixed bugs that caused StormLib incorrectly work */ -/* with Diablo I savegames and with files having full */ -/* hash table */ -/* 08.12.03 4.11 DCH Fixed bug in reading file sector larger than 0x1000 */ -/* on certain files. */ -/* Fixed bug in AddFile with MPQ_FILE_REPLACEEXISTING */ -/* (Thanx Daniel Chiamarello, dchiamarello@madvawes.com)*/ -/* 21.12.03 4.50 Lad Completed port for Mac */ -/* Fixed bug in compacting (if fsize is mul of 0x1000) */ -/* Fixed bug in SCompCompress */ -/* 27.05.04 4.51 Lad Changed memory management from new/delete to our */ -/* own macros */ -/* 22.06.04 4.60 Lad Optimized search. Support for multiple listfiles. */ -/* 30.09.04 4.61 Lad Fixed some bugs (Aaargh !!!) */ -/* Correctly works if HashTableSize > BlockTableSize */ -/* 29.12.04 4.70 Lad Fixed compatibility problem with MPQs from WoW */ -/* 14.07.05 5.00 Lad Added the BZLIB compression support */ -/* Added suport of files stored as single unit */ -/* 17.04.06 5.01 Lad Converted to MS Visual Studio 8.0 */ -/* Fixed issue with protected Warcraft 3 protected maps */ -/* 15.05.06 5.02 Lad Fixed issue with WoW 1.10+ */ -/* 07.09.06 5.10 Lad Fixed processing files longer than 2GB */ -/* 22.11.06 6.00 Lad Support for MPQ archives V2 */ -/* 12.06.07 6.10 Lad Support for (attributes) file */ -/* 10.09.07 6.12 Lad Support for MPQs protected by corrupting hash table */ -/* 03.12.07 6.13 Lad Support for MPQs with hash tbl size > block tbl size */ -/* 07.04.08 6.20 Lad Added SFileFlushArchive */ -/* 09.04.08 Lad Removed FilePointer variable from MPQ handle */ -/* structure, as it caused more problems than benefits */ -/* 12.05.08 6.22 Lad Support for w3xMaster map protector */ -/* 05.10.08 6.23 Lad Support for protectors who set negative values in */ -/* the table of file blocks */ -/* 26.05.09 6.24 Lad Fixed search for multiple lang files with deleted */ -/* entries */ -/* 03.09.09 6.25 Lad Fixed decompression bug in huffmann decompression */ -/* 22.03.10 6.50 Lad New compressions in Starcraft II (LZMA, sparse) */ -/* Fixed compacting MPQs that contain single unit files */ -/* 26.04.10 7.00 Lad Major rewrite */ -/* 08.06.10 7.10 Lad Support for partial MPQs */ -/* 08.07.10 7.11 Lad Support for MPQs v 3.0 */ -/* 20.08.10 7.20 Lad Support for opening multiple MPQs in patch mode */ -/* 20.09.10 8.00 Lad MPQs v 4, HET and BET tables */ -/* 07.01.11 8.01 Lad Write support for MPQs v 3 and 4 */ -/* 15.09.11 8.04 Lad Bug fixes, testing for Diablo III MPQs */ -/* 26.04.12 8.10 Lad Support for data map, added SFileGetArchiveBitmap */ -/* 29.05.12 8.20 Lad C-only interface */ -/* 14.01.13 8.21 Lad ADPCM and Huffmann (de)compression refactored */ -/* 04.12.13 9.00 Lad Unit tests, bug fixes */ -/* 27.08.14 9.10 Lad Signing archives with weak digital signature */ -/* 25.11.14 9.11 Lad Fixed bug reading & creating HET table */ -/* 18.09.15 9.20 Lad Release 9.20 */ -/* 12.12.16 9.21 Lad Release 9.21 */ -/* 10.11.17 9.22 Lad Release 9.22 */ -/* 28.09.22 9.24 Lad lcLocale -> lcFileLocale, also contains platform */ -/*****************************************************************************/ - -#ifndef __STORMLIB_H__ -#define __STORMLIB_H__ - -#ifdef _MSC_VER -#pragma warning(disable:4668) // 'XXX' is not defined as a preprocessor macro, replacing with '0' for '#if/#elif' -#pragma warning(disable:4820) // 'XXX' : '2' bytes padding added after data member 'XXX::yyy' -#endif - -#include "StormPort.h" - -#ifdef __cplusplus -extern "C" { -#endif - -//----------------------------------------------------------------------------- -// Use the apropriate library -// -// The library type is encoded in the library name as the following -// StormLibXYZ.lib -// -// X - D for Debug version, R for Release version -// Y - A for ANSI version, U for Unicode version -// Z - S for static-linked CRT library, D for multithreaded DLL CRT library -// - -#if defined(__STORMLIB_SELF__) && !defined(STORMLIB_NO_AUTO_LINK) -#define STORMLIB_NO_AUTO_LINK // Define this if you don't want to link using pragmas when using msvc -#endif - -#if defined(_MSC_VER) && !defined(STORMLIB_NO_AUTO_LINK) - #ifndef WDK_BUILD - #ifdef _DEBUG // DEBUG VERSIONS - #ifndef _UNICODE - #ifdef _DLL - #pragma comment(lib, "StormLibDAD.lib") // Debug Ansi CRT-DLL version - #else - #pragma comment(lib, "StormLibDAS.lib") // Debug Ansi CRT-LIB version - #endif - #else - #ifdef _DLL - #pragma comment(lib, "StormLibDUD.lib") // Debug Unicode CRT-DLL version - #else - #pragma comment(lib, "StormLibDUS.lib") // Debug Unicode CRT-LIB version - #endif - #endif - #else // RELEASE VERSIONS - #ifndef _UNICODE - #ifdef _DLL - #pragma comment(lib, "StormLibRAD.lib") // Release Ansi CRT-DLL version - #else - #pragma comment(lib, "StormLibRAS.lib") // Release Ansi CRT-LIB version - #endif - #else - #ifdef _DLL - #pragma comment(lib, "StormLibRUD.lib") // Release Unicode CRT-DLL version - #else - #pragma comment(lib, "StormLibRUS.lib") // Release Unicode CRT-LIB version - #endif - #endif - #endif - #endif - -#endif - -//----------------------------------------------------------------------------- -// Defines - -#define STORMLIB_VERSION 0x0918 // Current version of StormLib (9.24) -#define STORMLIB_VERSION_STRING "9.24" // String version of StormLib version - -#define ID_MPQ 0x1A51504D // MPQ archive header ID ('MPQ\x1A') -#define ID_MPQ_USERDATA 0x1B51504D // MPQ userdata entry ('MPQ\x1B') -#define ID_MPK 0x1A4B504D // MPK archive header ID ('MPK\x1A') - -#define ERROR_AVI_FILE 10000 // Not a MPQ file, but an AVI file. -#define ERROR_UNKNOWN_FILE_KEY 10001 // Returned by SFileReadFile when can't find file key -#define ERROR_CHECKSUM_ERROR 10002 // Returned by SFileReadFile when sector CRC doesn't match -#define ERROR_INTERNAL_FILE 10003 // The given operation is not allowed on internal file -#define ERROR_BASE_FILE_MISSING 10004 // The file is present as incremental patch file, but base file is missing -#define ERROR_MARKED_FOR_DELETE 10005 // The file was marked as "deleted" in the MPQ -#define ERROR_FILE_INCOMPLETE 10006 // The required file part is missing -#define ERROR_UNKNOWN_FILE_NAMES 10007 // A name of at least one file is unknown -#define ERROR_CANT_FIND_PATCH_PREFIX 10008 // StormLib was unable to find patch prefix for the patches -#define ERROR_FAKE_MPQ_HEADER 10009 // The header at this position is fake header - -// Values for SFileCreateArchive -#define HASH_TABLE_SIZE_MIN 0x00000004 // Verified: If there is 1 file, hash table size is 4 -#define HASH_TABLE_SIZE_DEFAULT 0x00001000 // Default hash table size for empty MPQs -#define HASH_TABLE_SIZE_MAX 0x00080000 // Maximum acceptable hash table size - -#define HASH_ENTRY_DELETED 0xFFFFFFFE // Block index for deleted entry in the hash table -#define HASH_ENTRY_FREE 0xFFFFFFFF // Block index for free entry in the hash table - -#define HET_ENTRY_DELETED 0x80 // NameHash1 value for a deleted entry -#define HET_ENTRY_FREE 0x00 // NameHash1 value for free entry - -// Values for SFileOpenArchive -#define SFILE_OPEN_HARD_DISK_FILE 2 // Open the archive on HDD -#define SFILE_OPEN_CDROM_FILE 3 // Open the archive only if it is on CDROM - -// Values for SFileOpenFile -#define SFILE_OPEN_FROM_MPQ 0x00000000 // Open the file from the MPQ archive -#define SFILE_OPEN_CHECK_EXISTS 0xFFFFFFFC // Only check whether the file exists -#define SFILE_OPEN_BASE_FILE 0xFFFFFFFD // Reserved for StormLib internal use -#define SFILE_OPEN_ANY_LOCALE 0xFFFFFFFE // Reserved for StormLib internal use -#define SFILE_OPEN_LOCAL_FILE 0xFFFFFFFF // Open a local file - -// Flags for TMPQArchive::dwFlags. Used internally -#define MPQ_FLAG_READ_ONLY 0x00000001 // If set, the MPQ has been open for read-only access -#define MPQ_FLAG_CHANGED 0x00000002 // If set, the MPQ tables have been changed -#define MPQ_FLAG_MALFORMED 0x00000004 // Malformed data structure detected (W3M map protectors) -#define MPQ_FLAG_HASH_TABLE_CUT 0x00000008 // The hash table goes beyond EOF -#define MPQ_FLAG_BLOCK_TABLE_CUT 0x00000010 // The hash table goes beyond EOF -#define MPQ_FLAG_CHECK_SECTOR_CRC 0x00000020 // Checking sector CRC when reading files -#define MPQ_FLAG_SAVING_TABLES 0x00000040 // If set, we are saving MPQ internal files and MPQ tables -#define MPQ_FLAG_PATCH 0x00000080 // If set, this MPQ is a patch archive -#define MPQ_FLAG_WAR3_MAP 0x00000100 // If set, this MPQ is a Warcraft III map -#define MPQ_FLAG_STARCRAFT_BETA 0x00000200 // If set, this MPQ is StarDat.mpq from Starcraft I BETA -#define MPQ_FLAG_LISTFILE_NONE 0x00000400 // Set when no (listfile) was found in InvalidateInternalFiles -#define MPQ_FLAG_LISTFILE_NEW 0x00000800 // Set when (listfile) invalidated by InvalidateInternalFiles -#define MPQ_FLAG_LISTFILE_FORCE 0x00001000 // Save updated listfile on exit -#define MPQ_FLAG_ATTRIBUTES_NONE 0x00002000 // Set when no (attributes) was found in InvalidateInternalFiles -#define MPQ_FLAG_ATTRIBUTES_NEW 0x00004000 // Set when (attributes) invalidated by InvalidateInternalFiles -#define MPQ_FLAG_SIGNATURE_NONE 0x00008000 // Set when no (signature) was found in InvalidateInternalFiles -#define MPQ_FLAG_SIGNATURE_NEW 0x00010000 // Set when (signature) invalidated by InvalidateInternalFiles - -// Values for TMPQArchive::dwSubType -#define MPQ_SUBTYPE_MPQ 0x00000000 // The file is a MPQ file (Blizzard games) -#define MPQ_SUBTYPE_SQP 0x00000001 // The file is a SQP file (War of the Immortals) -#define MPQ_SUBTYPE_MPK 0x00000002 // The file is a MPK file (Longwu Online) - -// Return value for SFileGetFileSize and SFileSetFilePointer -#define SFILE_INVALID_SIZE 0xFFFFFFFF -#define SFILE_INVALID_POS 0xFFFFFFFF -#define SFILE_INVALID_ATTRIBUTES 0xFFFFFFFF - -// Flags for SFileAddFile -#define MPQ_FILE_IMPLODE 0x00000100 // Implode method (By PKWARE Data Compression Library) -#define MPQ_FILE_COMPRESS 0x00000200 // Compress methods (By multiple methods) -#define MPQ_FILE_ENCRYPTED 0x00010000 // Indicates whether file is encrypted -#define MPQ_FILE_FIX_KEY 0x00020000 // File decryption key has to be fixed -#define MPQ_FILE_PATCH_FILE 0x00100000 // The file is a patch file. Raw file data begin with TPatchInfo structure -#define MPQ_FILE_SINGLE_UNIT 0x01000000 // File is stored as a single unit, rather than split into sectors (Thx, Quantam) -#define MPQ_FILE_DELETE_MARKER 0x02000000 // File is a deletion marker. Used in MPQ patches, indicating that the file no longer exists. -#define MPQ_FILE_SECTOR_CRC 0x04000000 // File has checksums for each sector. - // Ignored if file is not compressed or imploded. -#define MPQ_FILE_SIGNATURE 0x10000000 // Present on STANDARD.SNP\(signature). The only occurence ever observed -#define MPQ_FILE_EXISTS 0x80000000 // Set if file exists, reset when the file was deleted -#define MPQ_FILE_REPLACEEXISTING 0x80000000 // Replace when the file exist (SFileAddFile) - -#define MPQ_FILE_COMPRESS_MASK 0x0000FF00 // Mask for a file being compressed - -#define MPQ_FILE_DEFAULT_INTERNAL 0xFFFFFFFF // Use default flags for internal files - -#define MPQ_FILE_VALID_FLAGS (MPQ_FILE_IMPLODE | \ - MPQ_FILE_COMPRESS | \ - MPQ_FILE_ENCRYPTED | \ - MPQ_FILE_FIX_KEY | \ - MPQ_FILE_PATCH_FILE | \ - MPQ_FILE_SINGLE_UNIT | \ - MPQ_FILE_DELETE_MARKER | \ - MPQ_FILE_SECTOR_CRC | \ - MPQ_FILE_SIGNATURE | \ - MPQ_FILE_EXISTS) - -#define MPQ_FILE_VALID_FLAGS_W3X (MPQ_FILE_IMPLODE | \ - MPQ_FILE_COMPRESS | \ - MPQ_FILE_ENCRYPTED | \ - MPQ_FILE_FIX_KEY | \ - MPQ_FILE_DELETE_MARKER | \ - MPQ_FILE_SECTOR_CRC | \ - MPQ_FILE_SIGNATURE | \ - MPQ_FILE_EXISTS) - -#define MPQ_FILE_VALID_FLAGS_SCX (MPQ_FILE_IMPLODE | \ - MPQ_FILE_COMPRESS | \ - MPQ_FILE_ENCRYPTED | \ - MPQ_FILE_FIX_KEY | \ - MPQ_FILE_EXISTS) - -// We need to mask out the upper 4 bits of the block table index. -// This is because it gets shifted out when calculating block table offset -// BlockTableOffset = pHash->dwBlockIndex << 0x04 -// Malformed MPQ maps may contain block indexes like 0x40000001 or 0xF0000023 -#define BLOCK_INDEX_MASK 0x0FFFFFFF -#define MPQ_BLOCK_INDEX(pHash) ((pHash)->dwBlockIndex & BLOCK_INDEX_MASK) - -// Compression types for multiple compressions -#define MPQ_COMPRESSION_HUFFMANN 0x01 // Huffmann compression (used on WAVE files only) -#define MPQ_COMPRESSION_ZLIB 0x02 // ZLIB compression -#define MPQ_COMPRESSION_PKWARE 0x08 // PKWARE DCL compression -#define MPQ_COMPRESSION_BZIP2 0x10 // BZIP2 compression (added in Warcraft III) -#define MPQ_COMPRESSION_SPARSE 0x20 // Sparse compression (added in Starcraft 2) -#define MPQ_COMPRESSION_ADPCM_MONO 0x40 // IMA ADPCM compression (mono) -#define MPQ_COMPRESSION_ADPCM_STEREO 0x80 // IMA ADPCM compression (stereo) -#define MPQ_COMPRESSION_LZMA 0x12 // LZMA compression. Added in Starcraft 2. This value is NOT a combination of flags. -#define MPQ_COMPRESSION_NEXT_SAME 0xFFFFFFFF // Same compression - -// Constants for SFileAddWave -#define MPQ_WAVE_QUALITY_HIGH 0 // Best quality, the worst compression -#define MPQ_WAVE_QUALITY_MEDIUM 1 // Medium quality, medium compression -#define MPQ_WAVE_QUALITY_LOW 2 // Low quality, the best compression - -// Signatures for HET and BET table -#define HET_TABLE_SIGNATURE 0x1A544548 // 'HET\x1a' -#define BET_TABLE_SIGNATURE 0x1A544542 // 'BET\x1a' - -// Decryption keys for MPQ tables -#define MPQ_KEY_HASH_TABLE 0xC3AF3770 // Obtained by HashString("(hash table)", MPQ_HASH_FILE_KEY) -#define MPQ_KEY_BLOCK_TABLE 0xEC83B3A3 // Obtained by HashString("(block table)", MPQ_HASH_FILE_KEY) - -#define LISTFILE_NAME "(listfile)" // Name of internal listfile -#define SIGNATURE_NAME "(signature)" // Name of internal signature -#define ATTRIBUTES_NAME "(attributes)" // Name of internal attributes file -#define PATCH_METADATA_NAME "(patch_metadata)" - -#define MPQ_FORMAT_VERSION_1 0 // Up to The Burning Crusade -#define MPQ_FORMAT_VERSION_2 1 // The Burning Crusade and newer -#define MPQ_FORMAT_VERSION_3 2 // WoW Cataclysm Beta -#define MPQ_FORMAT_VERSION_4 3 // WoW Cataclysm and newer - -// Flags for MPQ attributes -#define MPQ_ATTRIBUTE_CRC32 0x00000001 // The "(attributes)" contains CRC32 for each file -#define MPQ_ATTRIBUTE_FILETIME 0x00000002 // The "(attributes)" contains file time for each file -#define MPQ_ATTRIBUTE_MD5 0x00000004 // The "(attributes)" contains MD5 for each file -#define MPQ_ATTRIBUTE_PATCH_BIT 0x00000008 // The "(attributes)" contains a patch bit for each file -#define MPQ_ATTRIBUTE_ALL 0x0000000F // Summary mask - -#define MPQ_ATTRIBUTES_V1 100 // (attributes) format version 1.00 - -// Flags for SFileOpenArchive -#define BASE_PROVIDER_FILE 0x00000000 // Base data source is a file -#define BASE_PROVIDER_MAP 0x00000001 // Base data source is memory-mapped file -#define BASE_PROVIDER_HTTP 0x00000002 // Base data source is a file on web server -#define BASE_PROVIDER_MASK 0x0000000F // Mask for base provider value - -#define STREAM_PROVIDER_FLAT 0x00000000 // Stream is linear with no offset mapping -#define STREAM_PROVIDER_PARTIAL 0x00000010 // Stream is partial file (.part) -#define STREAM_PROVIDER_MPQE 0x00000020 // Stream is an encrypted MPQ -#define STREAM_PROVIDER_BLOCK4 0x00000030 // 0x4000 per block, text MD5 after each block, max 0x2000 blocks per file -#define STREAM_PROVIDER_MASK 0x000000F0 // Mask for stream provider value - -#define STREAM_FLAG_READ_ONLY 0x00000100 // Stream is read only -#define STREAM_FLAG_WRITE_SHARE 0x00000200 // Allow write sharing when open for write -#define STREAM_FLAG_USE_BITMAP 0x00000400 // If the file has a file bitmap, load it and use it -#define STREAM_OPTIONS_MASK 0x0000FF00 // Mask for stream options - -#define STREAM_PROVIDERS_MASK 0x000000FF // Mask to get stream providers -#define STREAM_FLAGS_MASK 0x0000FFFF // Mask for all stream flags (providers+options) - -#define MPQ_OPEN_NO_LISTFILE 0x00010000 // Don't load the internal listfile -#define MPQ_OPEN_NO_ATTRIBUTES 0x00020000 // Don't open the attributes -#define MPQ_OPEN_NO_HEADER_SEARCH 0x00040000 // Don't search for the MPQ header past the begin of the file -#define MPQ_OPEN_FORCE_MPQ_V1 0x00080000 // Always open the archive as MPQ v 1.00, ignore the "wFormatVersion" variable in the header -#define MPQ_OPEN_CHECK_SECTOR_CRC 0x00100000 // On files with MPQ_FILE_SECTOR_CRC, the CRC will be checked when reading file -#define MPQ_OPEN_PATCH 0x00200000 // This archive is a patch MPQ. Used internally. -#define MPQ_OPEN_FORCE_LISTFILE 0x00400000 // Force add listfile even if there is none at the moment of opening -#define MPQ_OPEN_READ_ONLY STREAM_FLAG_READ_ONLY - -// Flags for SFileCreateArchive -#define MPQ_CREATE_LISTFILE 0x00100000 // Also add the (listfile) file -#define MPQ_CREATE_ATTRIBUTES 0x00200000 // Also add the (attributes) file -#define MPQ_CREATE_SIGNATURE 0x00400000 // Also add the (signature) file -#define MPQ_CREATE_ARCHIVE_V1 0x00000000 // Creates archive of version 1 (size up to 4GB) -#define MPQ_CREATE_ARCHIVE_V2 0x01000000 // Creates archive of version 2 (larger than 4 GB) -#define MPQ_CREATE_ARCHIVE_V3 0x02000000 // Creates archive of version 3 -#define MPQ_CREATE_ARCHIVE_V4 0x03000000 // Creates archive of version 4 -#define MPQ_CREATE_ARCHIVE_VMASK 0x0F000000 // Mask for archive version - -#define FLAGS_TO_FORMAT_SHIFT 24 // (MPQ_CREATE_ARCHIVE_V4 >> FLAGS_TO_FORMAT_SHIFT) => MPQ_FORMAT_VERSION_4 - -// Flags for SFileVerifyFile -#define SFILE_VERIFY_SECTOR_CRC 0x00000001 // Verify sector checksum for the file, if available -#define SFILE_VERIFY_FILE_CRC 0x00000002 // Verify file CRC, if available -#define SFILE_VERIFY_FILE_MD5 0x00000004 // Verify file MD5, if available -#define SFILE_VERIFY_RAW_MD5 0x00000008 // Verify raw file MD5, if available -#define SFILE_VERIFY_ALL 0x0000000F // Verify every checksum possible - -// Return values for SFileVerifyFile -#define VERIFY_OPEN_ERROR 0x0001 // Failed to open the file -#define VERIFY_READ_ERROR 0x0002 // Failed to read all data from the file -#define VERIFY_FILE_HAS_SECTOR_CRC 0x0004 // File has sector CRC -#define VERIFY_FILE_SECTOR_CRC_ERROR 0x0008 // Sector CRC check failed -#define VERIFY_FILE_HAS_CHECKSUM 0x0010 // File has CRC32 -#define VERIFY_FILE_CHECKSUM_ERROR 0x0020 // CRC32 check failed -#define VERIFY_FILE_HAS_MD5 0x0040 // File has data MD5 -#define VERIFY_FILE_MD5_ERROR 0x0080 // MD5 check failed -#define VERIFY_FILE_HAS_RAW_MD5 0x0100 // File has raw data MD5 -#define VERIFY_FILE_RAW_MD5_ERROR 0x0200 // Raw MD5 check failed -#define VERIFY_FILE_ERROR_MASK (VERIFY_OPEN_ERROR | VERIFY_READ_ERROR | VERIFY_FILE_SECTOR_CRC_ERROR | VERIFY_FILE_CHECKSUM_ERROR | VERIFY_FILE_MD5_ERROR | VERIFY_FILE_RAW_MD5_ERROR) - -// Flags for SFileVerifyRawData (for MPQs version 4.0 or higher) -#define SFILE_VERIFY_MPQ_HEADER 0x0001 // Verify raw MPQ header -#define SFILE_VERIFY_HET_TABLE 0x0002 // Verify raw data of the HET table -#define SFILE_VERIFY_BET_TABLE 0x0003 // Verify raw data of the BET table -#define SFILE_VERIFY_HASH_TABLE 0x0004 // Verify raw data of the hash table -#define SFILE_VERIFY_BLOCK_TABLE 0x0005 // Verify raw data of the block table -#define SFILE_VERIFY_HIBLOCK_TABLE 0x0006 // Verify raw data of the hi-block table -#define SFILE_VERIFY_FILE 0x0007 // Verify raw data of a file - -// Signature types -#define SIGNATURE_TYPE_NONE 0x0000 // The archive has no signature in it -#define SIGNATURE_TYPE_WEAK 0x0001 // The archive has weak signature -#define SIGNATURE_TYPE_STRONG 0x0002 // The archive has strong signature - -// Return values for SFileVerifyArchive -#define ERROR_NO_SIGNATURE 0 // There is no signature in the MPQ -#define ERROR_VERIFY_FAILED 1 // There was an error during verifying signature (like no memory) -#define ERROR_WEAK_SIGNATURE_OK 2 // There is a weak signature and sign check passed -#define ERROR_WEAK_SIGNATURE_ERROR 3 // There is a weak signature but sign check failed -#define ERROR_STRONG_SIGNATURE_OK 4 // There is a strong signature and sign check passed -#define ERROR_STRONG_SIGNATURE_ERROR 5 // There is a strong signature but sign check failed - -#ifndef MD5_DIGEST_SIZE -#define MD5_DIGEST_SIZE 0x10 -#endif - -#ifndef SHA1_DIGEST_SIZE -#define SHA1_DIGEST_SIZE 0x14 // 160 bits -#endif - -#ifndef LANG_NEUTRAL -#define LANG_NEUTRAL 0x00 // Neutral locale -#endif - -// Pointer to hashing function -typedef DWORD (*HASH_STRING)(const char * szFileName, DWORD dwHashType); - -//----------------------------------------------------------------------------- -// File information classes for SFileGetFileInfo and SFileFreeFileInfo - -typedef enum _SFileInfoClass -{ - // Info classes for archives - SFileMpqFileName, // Name of the archive file (TCHAR []) - SFileMpqStreamBitmap, // Array of bits, each bit means availability of one block (BYTE []) - SFileMpqUserDataOffset, // Offset of the user data header (ULONGLONG) - SFileMpqUserDataHeader, // Raw (unfixed) user data header (TMPQUserData) - SFileMpqUserData, // MPQ USer data, without the header (BYTE []) - SFileMpqHeaderOffset, // Offset of the MPQ header (ULONGLONG) - SFileMpqHeaderSize, // Fixed size of the MPQ header - SFileMpqHeader, // Raw (unfixed) archive header (TMPQHeader) - SFileMpqHetTableOffset, // Offset of the HET table, relative to MPQ header (ULONGLONG) - SFileMpqHetTableSize, // Compressed size of the HET table (ULONGLONG) - SFileMpqHetHeader, // HET table header (TMPQHetHeader) - SFileMpqHetTable, // HET table as pointer. Must be freed using SFileFreeFileInfo - SFileMpqBetTableOffset, // Offset of the BET table, relative to MPQ header (ULONGLONG) - SFileMpqBetTableSize, // Compressed size of the BET table (ULONGLONG) - SFileMpqBetHeader, // BET table header, followed by the flags (TMPQBetHeader + DWORD[]) - SFileMpqBetTable, // BET table as pointer. Must be freed using SFileFreeFileInfo - SFileMpqHashTableOffset, // Hash table offset, relative to MPQ header (ULONGLONG) - SFileMpqHashTableSize64, // Compressed size of the hash table (ULONGLONG) - SFileMpqHashTableSize, // Size of the hash table, in entries (DWORD) - SFileMpqHashTable, // Raw (unfixed) hash table (TMPQBlock []) - SFileMpqBlockTableOffset, // Block table offset, relative to MPQ header (ULONGLONG) - SFileMpqBlockTableSize64, // Compressed size of the block table (ULONGLONG) - SFileMpqBlockTableSize, // Size of the block table, in entries (DWORD) - SFileMpqBlockTable, // Raw (unfixed) block table (TMPQBlock []) - SFileMpqHiBlockTableOffset, // Hi-block table offset, relative to MPQ header (ULONGLONG) - SFileMpqHiBlockTableSize64, // Compressed size of the hi-block table (ULONGLONG) - SFileMpqHiBlockTable, // The hi-block table (USHORT []) - SFileMpqSignatures, // Signatures present in the MPQ (DWORD) - SFileMpqStrongSignatureOffset, // Byte offset of the strong signature, relative to begin of the file (ULONGLONG) - SFileMpqStrongSignatureSize, // Size of the strong signature (DWORD) - SFileMpqStrongSignature, // The strong signature (BYTE []) - SFileMpqArchiveSize64, // Archive size from the header (ULONGLONG) - SFileMpqArchiveSize, // Archive size from the header (DWORD) - SFileMpqMaxFileCount, // Max number of files in the archive (DWORD) - SFileMpqFileTableSize, // Number of entries in the file table (DWORD) - SFileMpqSectorSize, // Sector size (DWORD) - SFileMpqNumberOfFiles, // Number of files (DWORD) - SFileMpqRawChunkSize, // Size of the raw data chunk for MD5 - SFileMpqStreamFlags, // Stream flags (DWORD) - SFileMpqFlags, // Nonzero if the MPQ is read only (DWORD) - - // Info classes for files - SFileInfoPatchChain, // Chain of patches where the file is (TCHAR []) - SFileInfoFileEntry, // The file entry for the file (TFileEntry) - SFileInfoHashEntry, // Hash table entry for the file (TMPQHash) - SFileInfoHashIndex, // Index of the hash table entry (DWORD) - SFileInfoNameHash1, // The first name hash in the hash table (DWORD) - SFileInfoNameHash2, // The second name hash in the hash table (DWORD) - SFileInfoNameHash3, // 64-bit file name hash for the HET/BET tables (ULONGLONG) - SFileInfoLocale, // File locale (DWORD) - SFileInfoFileIndex, // Block index (DWORD) - SFileInfoByteOffset, // File position in the archive (ULONGLONG) - SFileInfoFileTime, // File time (ULONGLONG) - SFileInfoFileSize, // Size of the file (DWORD) - SFileInfoCompressedSize, // Compressed file size (DWORD) - SFileInfoFlags, // File flags from (DWORD) - SFileInfoEncryptionKey, // File encryption key - SFileInfoEncryptionKeyRaw, // Unfixed value of the file key - SFileInfoCRC32, // CRC32 of the file -} SFileInfoClass; - -//----------------------------------------------------------------------------- -// Callback functions - -// Values for compact callback -#define CCB_CHECKING_FILES 1 // Checking archive (dwParam1 = current, dwParam2 = total) -#define CCB_CHECKING_HASH_TABLE 2 // Checking hash table (dwParam1 = current, dwParam2 = total) -#define CCB_COPYING_NON_MPQ_DATA 3 // Copying non-MPQ data: No params used -#define CCB_COMPACTING_FILES 4 // Compacting archive (dwParam1 = current, dwParam2 = total) -#define CCB_CLOSING_ARCHIVE 5 // Closing archive: No params used - -typedef void (WINAPI * SFILE_DOWNLOAD_CALLBACK)(void * pvUserData, ULONGLONG ByteOffset, DWORD dwTotalBytes); -typedef void (WINAPI * SFILE_ADDFILE_CALLBACK)(void * pvUserData, DWORD dwBytesWritten, DWORD dwTotalBytes, bool bFinalCall); -typedef void (WINAPI * SFILE_COMPACT_CALLBACK)(void * pvUserData, DWORD dwWorkType, ULONGLONG BytesProcessed, ULONGLONG TotalBytes); - -typedef struct TFileStream TFileStream; -typedef struct TMPQBits TMPQBits; - -//----------------------------------------------------------------------------- -// Structures related to MPQ format -// -// Note: All structures in this header file are supposed to remain private -// to StormLib. The structures may (and will) change over time, as the MPQ -// file format evolves. Programmers directly using these structures need to -// be aware of this. And the last, but not least, NEVER do any modifications -// to those structures directly, always use SFile* functions. -// - -#define MPQ_HEADER_SIZE_V1 0x20 -#define MPQ_HEADER_SIZE_V2 0x2C -#define MPQ_HEADER_SIZE_V3 0x44 -#define MPQ_HEADER_SIZE_V4 0xD0 -#define MPQ_HEADER_DWORDS (MPQ_HEADER_SIZE_V4 / 0x04) - -typedef struct _TMPQUserData -{ - // The ID_MPQ_USERDATA ('MPQ\x1B') signature - DWORD dwID; - - // Maximum size of the user data - DWORD cbUserDataSize; - - // Offset of the MPQ header, relative to the begin of this header - DWORD dwHeaderOffs; - - // Appears to be size of user data header (Starcraft II maps) - DWORD cbUserDataHeader; -} TMPQUserData; - -// MPQ file header -// -// We have to make sure that the header is packed OK. -// Reason: A 64-bit integer at the beginning of 3.0 part, -// which is offset 0x2C -#pragma pack(push, 1) -typedef struct _TMPQHeader -{ - // The ID_MPQ ('MPQ\x1A') signature - DWORD dwID; - - // Size of the archive header - DWORD dwHeaderSize; - - // 32-bit size of MPQ archive - // This field is deprecated in the Burning Crusade MoPaQ format, and the size of the archive - // is calculated as the size from the beginning of the archive to the end of the hash table, - // block table, or hi-block table (whichever is largest). - DWORD dwArchiveSize; - - // 0 = Format 1 (up to The Burning Crusade) - // 1 = Format 2 (The Burning Crusade and newer) - // 2 = Format 3 (WoW - Cataclysm beta or newer) - // 3 = Format 4 (WoW - Cataclysm beta or newer) - USHORT wFormatVersion; - - // Power of two exponent specifying the number of 512-byte disk sectors in each file sector - // in the archive. The size of each file sector in the archive is 512 * 2 ^ wSectorSize. - USHORT wSectorSize; - - // Offset to the beginning of the hash table, relative to the beginning of the archive. - DWORD dwHashTablePos; - - // Offset to the beginning of the block table, relative to the beginning of the archive. - DWORD dwBlockTablePos; - - // Number of entries in the hash table. Must be a power of two, and must be less than 2^16 for - // the original MoPaQ format, or less than 2^20 for the Burning Crusade format. - DWORD dwHashTableSize; - - // Number of entries in the block table - DWORD dwBlockTableSize; - - //-- MPQ HEADER v 2 ------------------------------------------- - - // Offset to the beginning of array of 16-bit high parts of file offsets. - ULONGLONG HiBlockTablePos64; - - // High 16 bits of the hash table offset for large archives. - USHORT wHashTablePosHi; - - // High 16 bits of the block table offset for large archives. - USHORT wBlockTablePosHi; - - //-- MPQ HEADER v 3 ------------------------------------------- - - // 64-bit version of the archive size - ULONGLONG ArchiveSize64; - - // 64-bit position of the BET table - ULONGLONG BetTablePos64; - - // 64-bit position of the HET table - ULONGLONG HetTablePos64; - - //-- MPQ HEADER v 4 ------------------------------------------- - - // Compressed size of the hash table - ULONGLONG HashTableSize64; - - // Compressed size of the block table - ULONGLONG BlockTableSize64; - - // Compressed size of the hi-block table - ULONGLONG HiBlockTableSize64; - - // Compressed size of the HET block - ULONGLONG HetTableSize64; - - // Compressed size of the BET block - ULONGLONG BetTableSize64; - - // Size of raw data chunk to calculate MD5. - // MD5 of each data chunk follows the raw file data. - DWORD dwRawChunkSize; - - // MD5 of MPQ tables - unsigned char MD5_BlockTable[MD5_DIGEST_SIZE]; // MD5 of the block table before decryption - unsigned char MD5_HashTable[MD5_DIGEST_SIZE]; // MD5 of the hash table before decryption - unsigned char MD5_HiBlockTable[MD5_DIGEST_SIZE]; // MD5 of the hi-block table - unsigned char MD5_BetTable[MD5_DIGEST_SIZE]; // MD5 of the BET table before decryption - unsigned char MD5_HetTable[MD5_DIGEST_SIZE]; // MD5 of the HET table before decryption - unsigned char MD5_MpqHeader[MD5_DIGEST_SIZE]; // MD5 of the MPQ header from signature to (including) MD5_HetTable -} TMPQHeader; -#pragma pack(pop) - -// Hash table entry. All files in the archive are searched by their hashes. -typedef struct _TMPQHash -{ - // The hash of the file path, using method A. - DWORD dwName1; - - // The hash of the file path, using method B. - DWORD dwName2; - -#ifdef STORMLIB_LITTLE_ENDIAN - - // The language of the file. This is a Windows LANGID data type, and uses the same values. - // 0 indicates the default language (American English), or that the file is language-neutral. - USHORT Locale; - - // The platform the file is used for. 0 indicates the default platform. - // No other values have been observed. - BYTE Platform; - BYTE Reserved; - -#else - - BYTE Reserved; - BYTE Platform; - USHORT Locale; - -#endif - - // If the hash table entry is valid, this is the index into the block table of the file. - // Otherwise, one of the following two values: - // - FFFFFFFFh: Hash table entry is empty, and has always been empty. - // Terminates searches for a given file. - // - FFFFFFFEh: Hash table entry is empty, but was valid at some point (a deleted file). - // Does not terminate searches for a given file. - DWORD dwBlockIndex; -} TMPQHash; - -// File description block contains informations about the file -typedef struct _TMPQBlock -{ - // Offset of the beginning of the file, relative to the beginning of the archive. - DWORD dwFilePos; - - // Compressed file size - DWORD dwCSize; - - // Only valid if the block is a file; otherwise meaningless, and should be 0. - // If the file is compressed, this is the size of the uncompressed file data. - DWORD dwFSize; - - // Flags for the file. See MPQ_FILE_XXXX constants - DWORD dwFlags; -} TMPQBlock; - -// Patch file information, preceding the sector offset table -typedef struct _TPatchInfo -{ - DWORD dwLength; // Length of patch info header, in bytes - DWORD dwFlags; // Flags. 0x80000000 = MD5 (?) - DWORD dwDataSize; // Uncompressed size of the patch file - BYTE md5[0x10]; // MD5 of the entire patch file after decompression - - // Followed by the sector table (variable length) -} TPatchInfo; - -// This is the combined file entry for maintaining file list in the MPQ. -// This structure is combined from block table, hi-block table, -// (attributes) file and from (listfile). -typedef struct _TFileEntry -{ - ULONGLONG FileNameHash; // Jenkins hash of the file name. Only used when the MPQ has BET table. - ULONGLONG ByteOffset; // Position of the file content in the MPQ, relative to the MPQ header - ULONGLONG FileTime; // FileTime from the (attributes) file. 0 if not present. - DWORD dwFileSize; // Decompressed size of the file - DWORD dwCmpSize; // Compressed size of the file (i.e., size of the file data in the MPQ) - DWORD dwFlags; // File flags (from block table) - DWORD dwCrc32; // CRC32 from (attributes) file. 0 if not present. - BYTE md5[MD5_DIGEST_SIZE]; // File MD5 from the (attributes) file. 0 if not present. - char * szFileName; // File name. NULL if not known. -} TFileEntry; - -// Common header for HET and BET tables -typedef struct _TMPQExtHeader -{ - DWORD dwSignature; // 'HET\x1A' or 'BET\x1A' - DWORD dwVersion; // Version. Seems to be always 1 - DWORD dwDataSize; // Size of the contained table - - // Followed by the table header - // Followed by the table data - -} TMPQExtHeader; - -// Structure for HET table header -typedef struct _TMPQHetHeader -{ - TMPQExtHeader ExtHdr; - - DWORD dwTableSize; // Size of the entire HET table, including HET_TABLE_HEADER (in bytes) - DWORD dwEntryCount; // Number of occupied entries in the HET table - DWORD dwTotalCount; // Total number of entries in the HET table - DWORD dwNameHashBitSize; // Size of the name hash entry (in bits) - DWORD dwIndexSizeTotal; // Total size of file index (in bits) - DWORD dwIndexSizeExtra; // Extra bits in the file index - DWORD dwIndexSize; // Effective size of the file index (in bits) - DWORD dwIndexTableSize; // Size of the block index subtable (in bytes) - -} TMPQHetHeader; - -// Structure for BET table header -typedef struct _TMPQBetHeader -{ - TMPQExtHeader ExtHdr; - - DWORD dwTableSize; // Size of the entire BET table, including the header (in bytes) - DWORD dwEntryCount; // Number of entries in the BET table. Must match HET_TABLE_HEADER::dwEntryCount - DWORD dwUnknown08; - DWORD dwTableEntrySize; // Size of one table entry (in bits) - DWORD dwBitIndex_FilePos; // Bit index of the file position (within the entry record) - DWORD dwBitIndex_FileSize; // Bit index of the file size (within the entry record) - DWORD dwBitIndex_CmpSize; // Bit index of the compressed size (within the entry record) - DWORD dwBitIndex_FlagIndex; // Bit index of the flag index (within the entry record) - DWORD dwBitIndex_Unknown; // Bit index of the ??? (within the entry record) - DWORD dwBitCount_FilePos; // Bit size of file position (in the entry record) - DWORD dwBitCount_FileSize; // Bit size of file size (in the entry record) - DWORD dwBitCount_CmpSize; // Bit size of compressed file size (in the entry record) - DWORD dwBitCount_FlagIndex; // Bit size of flags index (in the entry record) - DWORD dwBitCount_Unknown; // Bit size of ??? (in the entry record) - DWORD dwBitTotal_NameHash2; // Total bit size of the NameHash2 - DWORD dwBitExtra_NameHash2; // Extra bits in the NameHash2 - DWORD dwBitCount_NameHash2; // Effective size of NameHash2 (in bits) - DWORD dwNameHashArraySize; // Size of NameHash2 table, in bytes - DWORD dwFlagCount; // Number of flags in the following array - -} TMPQBetHeader; - -// Structure for parsed HET table -typedef struct _TMPQHetTable -{ - TMPQBits * pBetIndexes; // Bit array of FileIndex values - LPBYTE pNameHashes; // Array of NameHash1 values (NameHash1 = upper 8 bits of FileName hashe) - ULONGLONG AndMask64; // AND mask used for calculating file name hash - ULONGLONG OrMask64; // OR mask used for setting the highest bit of the file name hash - - DWORD dwEntryCount; // Number of occupied entries in the HET table - DWORD dwTotalCount; // Number of entries in both NameHash and FileIndex table - DWORD dwNameHashBitSize; // Size of the name hash entry (in bits) - DWORD dwIndexSizeTotal; // Total size of one entry in pBetIndexes (in bits) - DWORD dwIndexSizeExtra; // Extra bits in the entry in pBetIndexes - DWORD dwIndexSize; // Effective size of one entry in pBetIndexes (in bits) -} TMPQHetTable; - -// Structure for parsed BET table -typedef struct _TMPQBetTable -{ - TMPQBits * pNameHashes; // Array of NameHash2 entries (lower 24 bits of FileName hash) - TMPQBits * pFileTable; // Bit-based file table - LPDWORD pFileFlags; // Array of file flags - - DWORD dwTableEntrySize; // Size of one table entry, in bits - DWORD dwBitIndex_FilePos; // Bit index of the file position in the table entry - DWORD dwBitIndex_FileSize; // Bit index of the file size in the table entry - DWORD dwBitIndex_CmpSize; // Bit index of the compressed size in the table entry - DWORD dwBitIndex_FlagIndex; // Bit index of the flag index in the table entry - DWORD dwBitIndex_Unknown; // Bit index of ??? in the table entry - DWORD dwBitCount_FilePos; // Size of file offset (in bits) within table entry - DWORD dwBitCount_FileSize; // Size of file size (in bits) within table entry - DWORD dwBitCount_CmpSize; // Size of compressed file size (in bits) within table entry - DWORD dwBitCount_FlagIndex; // Size of flag index (in bits) within table entry - DWORD dwBitCount_Unknown; // Size of ??? (in bits) within table entry - DWORD dwBitTotal_NameHash2; // Total size of the NameHash2 - DWORD dwBitExtra_NameHash2; // Extra bits in the NameHash2 - DWORD dwBitCount_NameHash2; // Effective size of the NameHash2 - DWORD dwEntryCount; // Number of entries - DWORD dwFlagCount; // Number of file flags in pFileFlags -} TMPQBetTable; - -// Structure for patch prefix -typedef struct _TMPQNamePrefix -{ - size_t nLength; // Length of this patch prefix. Can be 0 - char szPatchPrefix[1]; // Patch name prefix (variable length). If not empty, it always starts with backslash. -} TMPQNamePrefix; - -// Structure for name cache -typedef struct _TMPQNameCache -{ - DWORD FirstNameOffset; // Offset of the first name in the name list (in bytes) - DWORD FreeSpaceOffset; // Offset of the first free byte in the name cache (in bytes) - DWORD TotalCacheSize; // Size, in bytes, of the cache. Includes wildcard - DWORD SearchOffset; // Used by SListFileFindFirstFile - - // Followed by search mask (ASCIIZ, '\0' if none) - // Followed by name cache (ANSI multistring) - -} TMPQNameCache; - -// Archive handle structure -typedef struct _TMPQArchive -{ - TFileStream * pStream; // Open stream for the MPQ - - ULONGLONG UserDataPos; // Position of user data (relative to the begin of the file) - ULONGLONG MpqPos; // MPQ header offset (relative to the begin of the file) - ULONGLONG FileSize; // Size of the file at the moment of file open - - struct _TMPQArchive * haPatch; // Pointer to patch archive, if any - struct _TMPQArchive * haBase; // Pointer to base ("previous version") archive, if any - TMPQNamePrefix * pPatchPrefix; // Patch prefix to precede names of patch files - - TMPQUserData * pUserData; // MPQ user data (NULL if not present in the file) - TMPQHeader * pHeader; // MPQ file header - TMPQHash * pHashTable; // Hash table - TMPQHetTable * pHetTable; // HET table - TFileEntry * pFileTable; // File table - HASH_STRING pfnHashString; // Hashing function that will convert the file name into hash - - TMPQUserData UserData; // MPQ user data. Valid only when ID_MPQ_USERDATA has been found - DWORD HeaderData[MPQ_HEADER_DWORDS]; // Storage for MPQ header - - DWORD dwHETBlockSize; - DWORD dwBETBlockSize; - DWORD dwMaxFileCount; // Maximum number of files in the MPQ. Also total size of the file table. - DWORD dwFileTableSize; // Current size of the file table, e.g. index of the entry past the last occupied one - DWORD dwReservedFiles; // Number of entries reserved for internal MPQ files (listfile, attributes) - DWORD dwSectorSize; // Default size of one file sector - DWORD dwFileFlags1; // Flags for (listfile) - DWORD dwFileFlags2; // Flags for (attributes) - DWORD dwFileFlags3; // Flags for (signature) - DWORD dwAttrFlags; // Flags for the (attributes) file, see MPQ_ATTRIBUTE_XXX - DWORD dwValidFileFlags; // Valid flags for the current MPQ - DWORD dwRealHashTableSize; // Real size of the hash table, if MPQ_FLAG_HASH_TABLE_CUT is zet in dwFlags - DWORD dwFlags; // See MPQ_FLAG_XXXXX - DWORD dwSubType; // See MPQ_SUBTYPE_XXX - - SFILE_ADDFILE_CALLBACK pfnAddFileCB; // Callback function for adding files - void * pvAddFileUserData; // User data thats passed to the callback - - SFILE_COMPACT_CALLBACK pfnCompactCB; // Callback function for compacting the archive - ULONGLONG CompactBytesProcessed; // Amount of bytes that have been processed during a particular compact call - ULONGLONG CompactTotalBytes; // Total amount of bytes to be compacted - void * pvCompactUserData; // User data thats passed to the callback - - // OTR - TFileEntry* lastFreeSpaceEntry; - bool useFreeSpaceOptimization; -} TMPQArchive; - -// File handle structure -typedef struct _TMPQFile -{ - TFileStream * pStream; // File stream. Only used on local files - TMPQArchive * ha; // Archive handle - TMPQHash * pHashEntry; // Pointer to hash table entry, if the file was open using hash table - TFileEntry * pFileEntry; // File entry for the file - ULONGLONG RawFilePos; // Offset in MPQ archive (relative to file begin) - ULONGLONG MpqFilePos; // Offset in MPQ archive (relative to MPQ header) - DWORD dwHashIndex; // Hash table index (0xFFFFFFFF if not used) - DWORD dwFileKey; // Decryption key - DWORD dwFilePos; // Current file position - DWORD dwMagic; // 'FILE' - - struct _TMPQFile * hfPatch; // Pointer to opened patch file - - TPatchInfo * pPatchInfo; // Patch info block, preceding the sector table - LPDWORD SectorOffsets; // Position of each file sector, relative to the begin of the file. Only for compressed files. - LPDWORD SectorChksums; // Array of sector checksums (either ADLER32 or MD5) values for each file sector - LPBYTE pbFileData; // Data of the file (single unit files, patched files) - DWORD cbFileData; // Size of file data - DWORD dwCompression0; // Compression that will be used on the first file sector - DWORD dwSectorCount; // Number of sectors in the file - DWORD dwPatchedFileSize; // Size of patched file. Used when saving patch file to the MPQ - DWORD dwDataSize; // Size of data in the file (on patch files, this differs from file size in block table entry) - - LPBYTE pbFileSector; // Last loaded file sector. For single unit files, entire file content - DWORD dwSectorOffs; // File position of currently loaded file sector - DWORD dwSectorSize; // Size of the file sector. For single unit files, this is equal to the file size - - void * hctx; // Hash state for MD5. Used when saving file to MPQ - DWORD dwCrc32; // CRC32 value, used when saving file to MPQ - - DWORD dwAddFileError; // Result of the "Add File" operations - - bool bLoadedSectorCRCs; // If true, we already tried to load sector CRCs - bool bCheckSectorCRCs; // If true, then SFileReadFile will check sector CRCs when reading the file - bool bIsWriteHandle; // If true, this handle has been created by SFileCreateFile -} TMPQFile; - -// Structure for SFileFindFirstFile and SFileFindNextFile -typedef struct _SFILE_FIND_DATA -{ - char cFileName[MAX_PATH]; // Full name of the found file - char * szPlainName; // Plain name of the found file - DWORD dwHashIndex; // Hash table index for the file (HAH_ENTRY_FREE if no hash table) - DWORD dwBlockIndex; // Block table index for the file - DWORD dwFileSize; // File size in bytes - DWORD dwFileFlags; // MPQ file flags - DWORD dwCompSize; // Compressed file size - DWORD dwFileTimeLo; // Low 32-bits of the file time (0 if not present) - DWORD dwFileTimeHi; // High 32-bits of the file time (0 if not present) - LCID lcLocale; // Compound of file locale (16 bits) and platform (8 bits) - -} SFILE_FIND_DATA, *PSFILE_FIND_DATA; - -typedef struct _SFILE_CREATE_MPQ -{ - DWORD cbSize; // Size of this structure, in bytes - DWORD dwMpqVersion; // Version of the MPQ to be created - void *pvUserData; // Reserved, must be NULL - DWORD cbUserData; // Reserved, must be 0 - DWORD dwStreamFlags; // Stream flags for creating the MPQ - DWORD dwFileFlags1; // File flags for (listfile). Use MPQ_FILE_DEFAULT_INTERNAL to set default flags - DWORD dwFileFlags2; // File flags for (attributes). Use MPQ_FILE_DEFAULT_INTERNAL to set default flags - DWORD dwFileFlags3; // File flags for (signature). Use MPQ_FILE_DEFAULT_INTERNAL to set default flags - DWORD dwAttrFlags; // Flags for the (attributes) file. If 0, no attributes will be created - DWORD dwSectorSize; // Sector size for compressed files - DWORD dwRawChunkSize; // Size of raw data chunk - DWORD dwMaxFileCount; // File limit for the MPQ - -} SFILE_CREATE_MPQ, *PSFILE_CREATE_MPQ; - -typedef struct _SFILE_MARKERS -{ - DWORD dwSize; // Size of this structure, in bytes - DWORD dwSignature; // Alternate MPQ header marker - const char * szHashTableKey; // Replacement for "(hash table)" - const char * szBlockTableKey; // Replacement for "(block table)" -} SFILE_MARKERS, *PSFILE_MARKERS; - -//----------------------------------------------------------------------------- -// TMPQBits support - functions - -void GetMPQBits(TMPQBits * pBits, unsigned int nBitPosition, unsigned int nBitLength, void * pvBuffer, int nResultByteSize); - -//----------------------------------------------------------------------------- -// Stream support - functions - -// Structure used by FileStream_GetBitmap -struct TStreamBitmap -{ - ULONGLONG StreamSize; // Size of the stream, in bytes - DWORD BitmapSize; // Size of the block map, in bytes - DWORD BlockCount; // Number of blocks in the stream - DWORD BlockSize; // Size of one block - DWORD IsComplete; // Nonzero if the file is complete - - // Followed by the BYTE array, each bit means availability of one block -}; - -// UNICODE versions of the file access functions -TFileStream * FileStream_CreateFile(const TCHAR * szFileName, DWORD dwStreamFlags); -TFileStream * FileStream_OpenFile(const TCHAR * szFileName, DWORD dwStreamFlags); -const TCHAR * FileStream_GetFileName(TFileStream * pStream); -size_t FileStream_Prefix(const TCHAR * szFileName, DWORD * pdwProvider); - -bool FileStream_SetCallback(TFileStream * pStream, SFILE_DOWNLOAD_CALLBACK pfnCallback, void * pvUserData); - -bool FileStream_GetBitmap(TFileStream * pStream, void * pvBitmap, DWORD cbBitmap, DWORD * pcbLengthNeeded); -bool FileStream_Read(TFileStream * pStream, ULONGLONG * pByteOffset, void * pvBuffer, DWORD dwBytesToRead); -bool FileStream_Write(TFileStream * pStream, ULONGLONG * pByteOffset, const void * pvBuffer, DWORD dwBytesToWrite); -bool FileStream_SetSize(TFileStream * pStream, ULONGLONG NewFileSize); -bool FileStream_GetSize(TFileStream * pStream, ULONGLONG * pFileSize); -bool FileStream_GetPos(TFileStream * pStream, ULONGLONG * pByteOffset); -bool FileStream_GetTime(TFileStream * pStream, ULONGLONG * pFT); -bool FileStream_GetFlags(TFileStream * pStream, LPDWORD pdwStreamFlags); -bool FileStream_Replace(TFileStream * pStream, TFileStream * pNewStream); -void FileStream_Close(TFileStream * pStream); - -//----------------------------------------------------------------------------- -// Functions prototypes for Storm.dll - -// Typedefs for functions exported by Storm.dll -typedef LCID (WINAPI * SFILESETLOCALE)(LCID); -typedef bool (WINAPI * SFILEOPENARCHIVE)(const char *, DWORD, DWORD, HANDLE *); -typedef bool (WINAPI * SFILECLOSEARCHIVE)(HANDLE); -typedef bool (WINAPI * SFILEOPENFILEEX)(HANDLE, const char *, DWORD, HANDLE *); -typedef bool (WINAPI * SFILECLOSEFILE)(HANDLE); -typedef DWORD (WINAPI * SFILEGETFILESIZE)(HANDLE, LPDWORD); -typedef DWORD (WINAPI * SFILESETFILEPOINTER)(HANDLE, LONG, LONG *, DWORD); -typedef bool (WINAPI * SFILEREADFILE)(HANDLE, void *, DWORD, LPDWORD, LPOVERLAPPED); - -//----------------------------------------------------------------------------- -// Functions for manipulation with StormLib global flags - -// Macros for making LCID from Locale and Platform -#define SFILE_MAKE_LCID(locale, platform) ((LCID)(USHORT)locale | (LCID)(BYTE)platform << 0x10) -#define SFILE_LOCALE(lcFileLocale) (USHORT)(lcFileLocale & 0xFFFF) -#define SFILE_PLATFORM(lcFileLocale) (BYTE)(lcFileLocale >> 0x10) - -// Alternate marker support. This is for MPQs masked as DLLs (*.asi), which -// patch Storm.dll at runtime. Call before SFileOpenArchive -bool WINAPI SFileSetArchiveMarkers(PSFILE_MARKERS pMarkers); - -// Call before SFileOpenFileEx -LCID WINAPI SFileGetLocale(); -LCID WINAPI SFileSetLocale(LCID lcFileLocale); - -//----------------------------------------------------------------------------- -// Functions for archive manipulation - -bool WINAPI SFileOpenArchive(const TCHAR * szMpqName, DWORD dwPriority, DWORD dwFlags, HANDLE * phMpq); -bool WINAPI SFileCreateArchive(const TCHAR * szMpqName, DWORD dwCreateFlags, DWORD dwMaxFileCount, HANDLE * phMpq); -bool WINAPI SFileCreateArchive2(const TCHAR * szMpqName, PSFILE_CREATE_MPQ pCreateInfo, HANDLE * phMpq); - -bool WINAPI SFileSetDownloadCallback(HANDLE hMpq, SFILE_DOWNLOAD_CALLBACK DownloadCB, void * pvUserData); -bool WINAPI SFileFlushArchive(HANDLE hMpq); -bool WINAPI SFileCloseArchive(HANDLE hMpq); - -// Adds another listfile into MPQ. The currently added listfile(s) remain, -// so you can use this API to combining more listfiles. -// Note that this function is internally called by SFileFindFirstFile -DWORD WINAPI SFileAddListFile(HANDLE hMpq, const TCHAR * szListFile); - -// Archive compacting -bool WINAPI SFileSetCompactCallback(HANDLE hMpq, SFILE_COMPACT_CALLBACK CompactCB, void * pvUserData); -bool WINAPI SFileCompactArchive(HANDLE hMpq, const TCHAR * szListFile, bool bReserved); - -// Changing the maximum file count -DWORD WINAPI SFileGetMaxFileCount(HANDLE hMpq); -bool WINAPI SFileSetMaxFileCount(HANDLE hMpq, DWORD dwMaxFileCount); - -// Changing (attributes) file -DWORD WINAPI SFileGetAttributes(HANDLE hMpq); -bool WINAPI SFileSetAttributes(HANDLE hMpq, DWORD dwFlags); -bool WINAPI SFileUpdateFileAttributes(HANDLE hMpq, const char * szFileName); - -//----------------------------------------------------------------------------- -// Functions for manipulation with patch archives - -bool WINAPI SFileOpenPatchArchive(HANDLE hMpq, const TCHAR * szPatchMpqName, const char * szPatchPathPrefix, DWORD dwFlags); -bool WINAPI SFileIsPatchedArchive(HANDLE hMpq); - -//----------------------------------------------------------------------------- -// Functions for file manipulation - -// Reading from MPQ file -bool WINAPI SFileHasFile(HANDLE hMpq, const char * szFileName); -bool WINAPI SFileOpenFileEx(HANDLE hMpq, const char * szFileName, DWORD dwSearchScope, HANDLE * phFile); -DWORD WINAPI SFileGetFileSize(HANDLE hFile, LPDWORD pdwFileSizeHigh); -DWORD WINAPI SFileSetFilePointer(HANDLE hFile, LONG lFilePos, LONG * plFilePosHigh, DWORD dwMoveMethod); -bool WINAPI SFileReadFile(HANDLE hFile, void * lpBuffer, DWORD dwToRead, LPDWORD pdwRead, LPOVERLAPPED lpOverlapped); -bool WINAPI SFileCloseFile(HANDLE hFile); - -// Retrieving info about a file in the archive -bool WINAPI SFileGetFileInfo(HANDLE hMpqOrFile, SFileInfoClass InfoClass, void * pvFileInfo, DWORD cbFileInfo, LPDWORD pcbLengthNeeded); -bool WINAPI SFileGetFileName(HANDLE hFile, char * szFileName); -bool WINAPI SFileFreeFileInfo(void * pvFileInfo, SFileInfoClass InfoClass); - -// High-level extract function -bool WINAPI SFileExtractFile(HANDLE hMpq, const char * szToExtract, const TCHAR * szExtracted, DWORD dwSearchScope); - -//----------------------------------------------------------------------------- -// Functions for file and archive verification - -// Generates file CRC32 -bool WINAPI SFileGetFileChecksums(HANDLE hMpq, const char * szFileName, LPDWORD pdwCrc32, char * pMD5); - -// Verifies file against its checksums stored in (attributes) attributes (depending on dwFlags). -// For dwFlags, use one or more of MPQ_ATTRIBUTE_MD5 -DWORD WINAPI SFileVerifyFile(HANDLE hMpq, const char * szFileName, DWORD dwFlags); - -// Verifies raw data of the archive. Only works for MPQs version 4 or newer -DWORD WINAPI SFileVerifyRawData(HANDLE hMpq, DWORD dwWhatToVerify, const char * szFileName); - -// Verifies the signature, if present -bool WINAPI SFileSignArchive(HANDLE hMpq, DWORD dwSignatureType); -DWORD WINAPI SFileVerifyArchive(HANDLE hMpq); - -//----------------------------------------------------------------------------- -// Functions for file searching - -HANDLE WINAPI SFileFindFirstFile(HANDLE hMpq, const char * szMask, SFILE_FIND_DATA * lpFindFileData, const TCHAR * szListFile); -bool WINAPI SFileFindNextFile(HANDLE hFind, SFILE_FIND_DATA * lpFindFileData); -bool WINAPI SFileFindClose(HANDLE hFind); - -HANDLE WINAPI SListFileFindFirstFile(HANDLE hMpq, const TCHAR * szListFile, const char * szMask, SFILE_FIND_DATA * lpFindFileData); -bool WINAPI SListFileFindNextFile(HANDLE hFind, SFILE_FIND_DATA * lpFindFileData); -bool WINAPI SListFileFindClose(HANDLE hFind); - -// Locale support -DWORD WINAPI SFileEnumLocales(HANDLE hMpq, const char * szFileName, LCID * PtrFileLocales, LPDWORD PtrMaxLocales, DWORD dwSearchScope); - -//----------------------------------------------------------------------------- -// Support for adding files to the MPQ - -bool WINAPI SFileCreateFile(HANDLE hMpq, const char * szArchivedName, ULONGLONG FileTime, DWORD dwFileSize, LCID lcFileLocale, DWORD dwFlags, HANDLE * phFile); -bool WINAPI SFileWriteFile(HANDLE hFile, const void * pvData, DWORD dwSize, DWORD dwCompression); -bool WINAPI SFileFinishFile(HANDLE hFile); - -bool WINAPI SFileAddFileEx(HANDLE hMpq, const TCHAR * szFileName, const char * szArchivedName, DWORD dwFlags, DWORD dwCompression, DWORD dwCompressionNext); -bool WINAPI SFileAddFile(HANDLE hMpq, const TCHAR * szFileName, const char * szArchivedName, DWORD dwFlags); -bool WINAPI SFileAddWave(HANDLE hMpq, const TCHAR * szFileName, const char * szArchivedName, DWORD dwFlags, DWORD dwQuality); -bool WINAPI SFileRemoveFile(HANDLE hMpq, const char * szFileName, DWORD dwSearchScope); -bool WINAPI SFileRenameFile(HANDLE hMpq, const char * szOldFileName, const char * szNewFileName); -bool WINAPI SFileSetFileLocale(HANDLE hFile, LCID lcNewLocale); -bool WINAPI SFileSetDataCompression(DWORD DataCompression); - -bool WINAPI SFileSetAddFileCallback(HANDLE hMpq, SFILE_ADDFILE_CALLBACK AddFileCB, void * pvUserData); - -//----------------------------------------------------------------------------- -// Compression and decompression - -int WINAPI SCompImplode (void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer); -int WINAPI SCompExplode (void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer); -int WINAPI SCompCompress (void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer, unsigned uCompressionMask, int nCmpType, int nCmpLevel); -int WINAPI SCompDecompress (void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer); -int WINAPI SCompDecompress2(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer); -int WINAPI SCompDecompress_SC1B(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer); - -//----------------------------------------------------------------------------- -// Non-Windows support for SetLastError/GetLastError - -#ifndef STORMLIB_WINDOWS - -void SetLastError(DWORD dwErrCode); -DWORD GetLastError(); - -#endif - -//----------------------------------------------------------------------------- -// Functions from Storm.dll. They use slightly different names for keeping -// possibility to use them together with StormLib (StormXXX instead of SFileXXX) - -#ifdef __LINK_STORM_DLL__ - #define STORM_ALTERNATE_NAMES // Force storm_dll.h to use alternate fnc names - #include "..\storm_dll\storm_dll.h" -#endif // __LINK_STORM_DLL__ - -#ifdef __cplusplus -} // extern "C" -#endif - -#endif // __STORMLIB_H__ diff --git a/app/jni/src/libultraship/extern/StormLib/src/StormPort.h b/app/jni/src/libultraship/extern/StormLib/src/StormPort.h deleted file mode 100644 index aa2c9f5..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/StormPort.h +++ /dev/null @@ -1,473 +0,0 @@ -/*****************************************************************************/ -/* StormPort.h Copyright (c) Marko Friedemann 2001 */ -/*---------------------------------------------------------------------------*/ -/* Portability module for the StormLib library. Contains a wrapper symbols */ -/* to make the compilation under Linux work */ -/* */ -/* Author: Marko Friedemann */ -/* Created at: Mon Jan 29 18:26:01 CEST 2001 */ -/* Computer: whiplash.flachland-chemnitz.de */ -/* System: Linux 2.4.0 on i686 */ -/* */ -/* Author: Sam Wilkins */ -/* System: Mac OS X and port to big endian processor */ -/* */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 29.01.01 1.00 Mar Created */ -/* 24.03.03 1.01 Lad Some cosmetic changes */ -/* 12.11.03 1.02 Dan Macintosh compatibility */ -/* 24.07.04 1.03 Sam Mac OS X compatibility */ -/* 22.11.06 1.04 Sam Mac OS X compatibility (for StormLib 6.0) */ -/* 31.12.06 1.05 XPinguin Full GNU/Linux compatibility */ -/* 17.10.12 1.05 Lad Moved error codes so they don't overlap with errno.h */ -/*****************************************************************************/ - -#ifndef __STORMPORT_H__ -#define __STORMPORT_H__ - -#ifndef __cplusplus - #define bool char - #define true 1 - #define false 0 -#endif - -//----------------------------------------------------------------------------- -// Defines for Windows - -#if !defined(STORMLIB_PLATFORM_DEFINED) && defined(_WIN32) - - // In MSVC 8.0, there are some functions declared as deprecated. - #if _MSC_VER >= 1400 - #define _CRT_SECURE_NO_DEPRECATE - #define _CRT_NON_CONFORMING_SWPRINTFS - #endif - - #include - #include - #include - #include - - // Suppress definitions of `min` and `max` macros by : - #define NOMINMAX 1 - #include - - #include - #define STORMLIB_LITTLE_ENDIAN - - #ifdef _WIN64 - #define STORMLIB_64BIT - #else - #define STORMLIB_32BIT - #endif - - #define STORMLIB_CDECL __cdecl - - #define STORMLIB_WINDOWS - #define STORMLIB_PLATFORM_DEFINED // The platform is known now - -#endif - -//----------------------------------------------------------------------------- -// Defines for Mac - -#if !defined(STORMLIB_PLATFORM_DEFINED) && defined(__APPLE__) // Mac BSD API - - // Macintosh - #include - #include - #include - #include - #include - #include - #include - #include - #include - #include - #include - - // Support for PowerPC on Max OS X - #if (__ppc__ == 1) || (__POWERPC__ == 1) || (_ARCH_PPC == 1) - #include - #include - #endif - - #define PKEXPORT - - #ifndef __SYS_ZLIB - #define __SYS_ZLIB - #endif - - #ifndef __SYS_BZLIB - #define __SYS_BZLIB - #endif - - #ifndef __BIG_ENDIAN__ - #define STORMLIB_LITTLE_ENDIAN - #endif - - #define STORMLIB_MAC - #define STORMLIB_HAS_MMAP // Indicate that we have mmap support - #define STORMLIB_PLATFORM_DEFINED // The platform is known now - -#endif - -//----------------------------------------------------------------------------- -// Defines for HAIKU platform - -#if !defined(STORMLIB_PLATFORM_DEFINED) && defined(__HAIKU__) - - #include - #include - #include - #include - #include - #include - #include - #include - #include - #include - #include - #include - #include - - #ifndef __BIG_ENDIAN__ - #define STORMLIB_LITTLE_ENDIAN - #endif - - #define STORMLIB_MAC // Use Mac compatible code - #define STORMLIB_HAIKU - #define STORMLIB_PLATFORM_DEFINED // The platform is known now - -#endif - -//----------------------------------------------------------------------------- -// Defines for AMIGA platform - -#if !defined(STORMLIB_PLATFORM_DEFINED) && defined(__AMIGA__) - - #include - #include - #include - #include - #include - #include - #include - #include - #include - #include - #include - #include - - #ifndef __BIG_ENDIAN__ - #define STORMLIB_LITTLE_ENDIAN - #endif - - #define STORMLIB_MAC // Use Mac compatible code - #define STORMLIB_AMIGA - #define STORMLIB_PLATFORM_DEFINED - -#endif - -//----------------------------------------------------------------------------- -// Defines for Switch platform - -#if !defined(STORMLIB_PLATFORM_DEFINED) && defined(__SWITCH__) - - #include - #include - #include - #include - #include - #include - #include - #include - #include - #include - #include - #include - #include - - #ifndef __BIG_ENDIAN__ - #define STORMLIB_LITTLE_ENDIAN - #endif - - #define STORMLIB_MAC // Use Mac compatible code - #define STORMLIB_SWITCH - #define STORMLIB_PLATFORM_DEFINED - -#endif - -//----------------------------------------------------------------------------- -// Defines for 3DS platform - -#if !defined(STORMLIB_PLATFORM_DEFINED) && defined(__3DS__) - - #include - #include - #include - #include - #include - #include - #include - #include - #include - #include - #include - #include - - #define STORMLIB_LITTLE_ENDIAN - - #define STORMLIB_MAC // Use Mac compatible code - #define STORMLIB_CTR - #define STORMLIB_PLATFORM_DEFINED - -#endif - -//----------------------------------------------------------------------------- -// Defines for Vita platform - -#if !defined(STORMLIB_PLATFORM_DEFINED) && defined(__vita__) - - #include - #include - #include - #include - #include - #include - #include - #include - #include - #include - #include - #include - #include - - #ifndef __BIG_ENDIAN__ - #define STORMLIB_LITTLE_ENDIAN - #endif - - #define STORMLIB_MAC // Use Mac compatible code - #define STORMLIB_VITA - #define STORMLIB_PLATFORM_DEFINED - -#endif - -//----------------------------------------------------------------------------- -// Defines for Wii U platform - -#if !defined(STORMLIB_PLATFORM_DEFINED) && defined(__WIIU__) - - #include - #include - #include - #include - #include - #include - #include - #include - #include - #include - #include - #include - #include - #include - - #undef STORMLIB_LITTLE_ENDIAN // Wii U is always big endian - - #define STORMLIB_MAC // Use Mac compatible code - #define STORMLIB_WIIU - #define STORMLIB_PLATFORM_DEFINED - -#endif - -//----------------------------------------------------------------------------- -// Assumption: If the platform is not defined, assume a Linux-like platform - -#if !defined(STORMLIB_PLATFORM_DEFINED) - - #include - #include - #include - #include - #include - #include - #include - #include - #include - #include - #include - #include - #include - - #ifndef __BIG_ENDIAN__ - #define STORMLIB_LITTLE_ENDIAN - #endif - - // Platforms with mmap support - #if defined(__linux__) || defined(__FreeBSD__) || defined(__NetBSD__) || defined(__OpenBSD__) || defined(__DragonFly__) - #include - #define STORMLIB_HAS_MMAP - #endif - - #define STORMLIB_LINUX - #define STORMLIB_PLATFORM_DEFINED - -#endif - -//----------------------------------------------------------------------------- -// Definition of Windows-specific types for non-Windows platforms - -#ifndef STORMLIB_WINDOWS - #if __LP64__ - #define STORMLIB_64BIT - #else - #define STORMLIB_32BIT - #endif - - // __cdecl meand nothing on non-Windows - #define STORMLIB_CDECL /* */ - - // Typedefs for ANSI C - typedef unsigned char BYTE; - typedef unsigned short USHORT; - typedef int LONG; - typedef unsigned int DWORD; - typedef unsigned long DWORD_PTR; - typedef long LONG_PTR; - typedef long INT_PTR; - typedef long long LONGLONG; - typedef unsigned long long ULONGLONG; - typedef void * HANDLE; - typedef void * LPOVERLAPPED; // Unsupported on Linux and Mac - typedef char TCHAR; - typedef unsigned int LCID; - typedef LONG * PLONG; - typedef DWORD * LPDWORD; - typedef BYTE * LPBYTE; - typedef const char * LPCTSTR; - typedef const char * LPCSTR; - typedef char * LPTSTR; - typedef char * LPSTR; - - #ifdef STORMLIB_32BIT - #define _LZMA_UINT32_IS_ULONG - #endif - - // Some Windows-specific defines - #ifndef MAX_PATH - #define MAX_PATH 1024 - #endif - - #define WINAPI - - #define FILE_BEGIN SEEK_SET - #define FILE_CURRENT SEEK_CUR - #define FILE_END SEEK_END - - #define _T(x) x - #define _tcslen strlen - #define _tcscpy strcpy - #define _tcscat strcat - #define _tcschr strchr - #define _tcsrchr strrchr - #define _tcsstr strstr - #define _tcsnicmp strncasecmp - #define _tprintf printf - #define _stprintf sprintf - #define _tremove remove - #define _tmain main - - #define _stricmp strcasecmp - #define _strnicmp strncasecmp - #define _tcsicmp strcasecmp - #define _tcsnicmp strncasecmp - -#endif // !STORMLIB_WINDOWS - -// 64-bit calls are supplied by "normal" calls on Mac -#if defined(STORMLIB_MAC) - #define stat64 stat - #define fstat64 fstat - #define lseek64 lseek - #define ftruncate64 ftruncate - #define off64_t off_t - #define O_LARGEFILE 0 -#endif - -// Platform-specific error codes for non-Windows platforms -#ifndef ERROR_SUCCESS - #define ERROR_SUCCESS 0 - #define ERROR_FILE_NOT_FOUND ENOENT - #define ERROR_ACCESS_DENIED EPERM - #define ERROR_INVALID_HANDLE EBADF - #define ERROR_NOT_ENOUGH_MEMORY ENOMEM - #define ERROR_NOT_SUPPORTED ENOTSUP - #define ERROR_INVALID_PARAMETER EINVAL - #define ERROR_NEGATIVE_SEEK ESPIPE - #define ERROR_DISK_FULL ENOSPC - #define ERROR_ALREADY_EXISTS EEXIST - #define ERROR_INSUFFICIENT_BUFFER ENOBUFS - #define ERROR_BAD_FORMAT 1000 // No such error code under Linux - #define ERROR_NO_MORE_FILES 1001 // No such error code under Linux - #define ERROR_HANDLE_EOF 1002 // No such error code under Linux - #define ERROR_CAN_NOT_COMPLETE 1003 // No such error code under Linux - #define ERROR_FILE_CORRUPT 1004 // No such error code under Linux -#endif - -// Macros that can sometimes be missing -#ifndef _countof - #define _countof(x) (sizeof(x) / sizeof(x[0])) -#endif - -//----------------------------------------------------------------------------- -// Swapping functions - -#ifdef STORMLIB_LITTLE_ENDIAN - #define BSWAP_INT16_UNSIGNED(a) (a) - #define BSWAP_INT16_SIGNED(a) (a) - #define BSWAP_INT32_UNSIGNED(a) (a) - #define BSWAP_INT32_SIGNED(a) (a) - #define BSWAP_INT64_SIGNED(a) (a) - #define BSWAP_INT64_UNSIGNED(a) (a) - #define BSWAP_ARRAY16_UNSIGNED(a,b) {} - #define BSWAP_ARRAY32_UNSIGNED(a,b) {} - #define BSWAP_ARRAY64_UNSIGNED(a,b) {} - #define BSWAP_PART_HEADER(a) {} - #define BSWAP_TMPQHEADER(a,b) {} - #define BSWAP_TMPKHEADER(a) {} -#else - -#ifdef __cplusplus - extern "C" { -#endif - int16_t SwapInt16(uint16_t); - uint16_t SwapUInt16(uint16_t); - int32_t SwapInt32(uint32_t); - uint32_t SwapUInt32(uint32_t); - int64_t SwapInt64(uint64_t); - uint64_t SwapUInt64(uint64_t); - void ConvertUInt16Buffer(void * ptr, size_t length); - void ConvertUInt32Buffer(void * ptr, size_t length); - void ConvertUInt64Buffer(void * ptr, size_t length); - void ConvertTMPQUserData(void *userData); - void ConvertTMPQHeader(void *header, uint16_t wPart); - void ConvertTMPKHeader(void *header); -#ifdef __cplusplus - } -#endif - #define BSWAP_INT16_SIGNED(a) SwapInt16((a)) - #define BSWAP_INT16_UNSIGNED(a) SwapUInt16((a)) - #define BSWAP_INT32_SIGNED(a) SwapInt32((a)) - #define BSWAP_INT32_UNSIGNED(a) SwapUInt32((a)) - #define BSWAP_INT64_SIGNED(a) SwapInt64((a)) - #define BSWAP_INT64_UNSIGNED(a) SwapUInt64((a)) - #define BSWAP_ARRAY16_UNSIGNED(a,b) ConvertUInt16Buffer((a),(b)) - #define BSWAP_ARRAY32_UNSIGNED(a,b) ConvertUInt32Buffer((a),(b)) - #define BSWAP_ARRAY64_UNSIGNED(a,b) ConvertUInt64Buffer((a),(b)) - #define BSWAP_TMPQHEADER(a,b) ConvertTMPQHeader((a),(b)) - #define BSWAP_TMPKHEADER(a) ConvertTMPKHeader((a)) -#endif - -#endif // __STORMPORT_H__ diff --git a/app/jni/src/libultraship/extern/StormLib/src/adpcm/adpcm.cpp b/app/jni/src/libultraship/extern/StormLib/src/adpcm/adpcm.cpp deleted file mode 100644 index 1725008..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/adpcm/adpcm.cpp +++ /dev/null @@ -1,539 +0,0 @@ -/*****************************************************************************/ -/* adpcm.cpp Copyright (c) Ladislav Zezula 2003 */ -/*---------------------------------------------------------------------------*/ -/* This module contains implementation of adpcm decompression method used by */ -/* Storm.dll to decompress WAVE files. Thanks to Tom Amigo for releasing */ -/* his sources. */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 11.03.03 1.00 Lad Splitted from Pkware.cpp */ -/* 20.05.03 2.00 Lad Added compression */ -/* 19.11.03 2.01 Dan Big endian handling */ -/* 10.01.13 3.00 Lad Refactored, beautified, documented :-) */ -/*****************************************************************************/ - -#include -#include - -#include "adpcm.h" - -//----------------------------------------------------------------------------- -// Tables necessary dor decompression - -static const int NextStepTable[] = -{ - -1, 0, -1, 4, -1, 2, -1, 6, - -1, 1, -1, 5, -1, 3, -1, 7, - -1, 1, -1, 5, -1, 3, -1, 7, - -1, 2, -1, 4, -1, 6, -1, 8 -}; - -static const int StepSizeTable[] = -{ - 7, 8, 9, 10, 11, 12, 13, 14, - 16, 17, 19, 21, 23, 25, 28, 31, - 34, 37, 41, 45, 50, 55, 60, 66, - 73, 80, 88, 97, 107, 118, 130, 143, - 157, 173, 190, 209, 230, 253, 279, 307, - 337, 371, 408, 449, 494, 544, 598, 658, - 724, 796, 876, 963, 1060, 1166, 1282, 1411, - 1552, 1707, 1878, 2066, 2272, 2499, 2749, 3024, - 3327, 3660, 4026, 4428, 4871, 5358, 5894, 6484, - 7132, 7845, 8630, 9493, 10442, 11487, 12635, 13899, - 15289, 16818, 18500, 20350, 22385, 24623, 27086, 29794, - 32767 -}; - -//----------------------------------------------------------------------------- -// Helper class for writing output ADPCM data - -class TADPCMStream -{ - public: - - TADPCMStream(void * pvBuffer, size_t cbBuffer) - { - pbBufferEnd = (unsigned char *)pvBuffer + cbBuffer; - pbBuffer = (unsigned char *)pvBuffer; - } - - bool ReadByteSample(unsigned char & ByteSample) - { - // Check if there is enough space in the buffer - if(pbBuffer >= pbBufferEnd) - return false; - - ByteSample = *pbBuffer++; - return true; - } - - bool WriteByteSample(unsigned char ByteSample) - { - // Check if there is enough space in the buffer - if(pbBuffer >= pbBufferEnd) - return false; - - *pbBuffer++ = ByteSample; - return true; - } - - bool ReadWordSample(short & OneSample) - { - // Check if we have enough space in the output buffer - if((size_t)(pbBufferEnd - pbBuffer) < sizeof(short)) - return false; - - // Write the sample - OneSample = pbBuffer[0] + (((short)pbBuffer[1]) << 0x08); - pbBuffer += sizeof(short); - return true; - } - - bool WriteWordSample(short OneSample) - { - // Check if we have enough space in the output buffer - if((size_t)(pbBufferEnd - pbBuffer) < sizeof(short)) - return false; - - // Write the sample - *pbBuffer++ = (unsigned char)(OneSample & 0xFF); - *pbBuffer++ = (unsigned char)(OneSample >> 0x08); - return true; - } - - int LengthProcessed(void * pvOutBuffer) - { - return (int)((unsigned char *)pbBuffer - (unsigned char *)pvOutBuffer); - } - - unsigned char * pbBufferEnd; - unsigned char * pbBuffer; -}; - -//---------------------------------------------------------------------------- -// Local functions - -static inline short GetNextStepIndex(int StepIndex, unsigned int EncodedSample) -{ - // Get the next step index - StepIndex = StepIndex + NextStepTable[EncodedSample & 0x1F]; - - // Don't make the step index overflow - if(StepIndex < 0) - StepIndex = 0; - else if(StepIndex > 88) - StepIndex = 88; - - return (short)StepIndex; -} - -static inline int UpdatePredictedSample(int PredictedSample, int EncodedSample, int Difference, int BitMask = 0x40) -{ - // Is the sign bit set? - if(EncodedSample & BitMask) - { - PredictedSample -= Difference; - if(PredictedSample <= -32768) - PredictedSample = -32768; - } - else - { - PredictedSample += Difference; - if(PredictedSample >= 32767) - PredictedSample = 32767; - } - - return PredictedSample; -} - -static inline int DecodeSample(int PredictedSample, int EncodedSample, int StepSize, int Difference) -{ - if(EncodedSample & 0x01) - Difference += (StepSize >> 0); - - if(EncodedSample & 0x02) - Difference += (StepSize >> 1); - - if(EncodedSample & 0x04) - Difference += (StepSize >> 2); - - if(EncodedSample & 0x08) - Difference += (StepSize >> 3); - - if(EncodedSample & 0x10) - Difference += (StepSize >> 4); - - if(EncodedSample & 0x20) - Difference += (StepSize >> 5); - - return UpdatePredictedSample(PredictedSample, EncodedSample, Difference); -} - -//---------------------------------------------------------------------------- -// Compression routine - -int CompressADPCM(void * pvOutBuffer, int cbOutBuffer, void * pvInBuffer, int cbInBuffer, int ChannelCount, int CompressionLevel) -{ - TADPCMStream os(pvOutBuffer, cbOutBuffer); // The output stream - TADPCMStream is(pvInBuffer, cbInBuffer); // The input stream - unsigned char BitShift = (unsigned char)(CompressionLevel - 1); - short PredictedSamples[MAX_ADPCM_CHANNEL_COUNT];// Predicted samples for each channel - short StepIndexes[MAX_ADPCM_CHANNEL_COUNT]; // Step indexes for each channel - short InputSample; // Input sample for the current channel - int TotalStepSize; - int ChannelIndex; - int AbsDifference; - int Difference; - int MaxBitMask; - int StepSize; - - // First byte in the output stream contains zero. The second one contains the compression level - os.WriteByteSample(0); - if(!os.WriteByteSample(BitShift)) - return 2; - - // Set the initial step index for each channel - PredictedSamples[0] = PredictedSamples[1] = 0; - StepIndexes[0] = StepIndexes[1] = INITIAL_ADPCM_STEP_INDEX; - - // Next, InitialSample value for each channel follows - for(int i = 0; i < ChannelCount; i++) - { - // Get the initial sample from the input stream - if(!is.ReadWordSample(InputSample)) - return os.LengthProcessed(pvOutBuffer); - - // Store the initial sample to our sample array - PredictedSamples[i] = InputSample; - - // Also store the loaded sample to the output stream - if(!os.WriteWordSample(InputSample)) - return os.LengthProcessed(pvOutBuffer); - } - - // Get the initial index - ChannelIndex = ChannelCount - 1; - - // Now keep reading the input data as long as there is something in the input buffer - while(is.ReadWordSample(InputSample)) - { - int EncodedSample = 0; - - // If we have two channels, we need to flip the channel index - ChannelIndex = (ChannelIndex + 1) % ChannelCount; - - // Get the difference from the previous sample. - // If the difference is negative, set the sign bit to the encoded sample - AbsDifference = InputSample - PredictedSamples[ChannelIndex]; - if(AbsDifference < 0) - { - AbsDifference = -AbsDifference; - EncodedSample |= 0x40; - } - - // If the difference is too low (higher that difference treshold), - // write a step index modifier marker - StepSize = StepSizeTable[StepIndexes[ChannelIndex]]; - if(AbsDifference < (StepSize >> CompressionLevel)) - { - if(StepIndexes[ChannelIndex] != 0) - StepIndexes[ChannelIndex]--; - - os.WriteByteSample(0x80); - } - else - { - // If the difference is too high, write marker that - // indicates increase in step size - while(AbsDifference > (StepSize << 1)) - { - if(StepIndexes[ChannelIndex] >= 0x58) - break; - - // Modify the step index - StepIndexes[ChannelIndex] += 8; - if(StepIndexes[ChannelIndex] > 0x58) - StepIndexes[ChannelIndex] = 0x58; - - // Write the "modify step index" marker - StepSize = StepSizeTable[StepIndexes[ChannelIndex]]; - os.WriteByteSample(0x81); - } - - // Get the limit bit value - MaxBitMask = (1 << (BitShift - 1)); - MaxBitMask = (MaxBitMask > 0x20) ? 0x20 : MaxBitMask; - Difference = StepSize >> BitShift; - TotalStepSize = 0; - - for(int BitVal = 0x01; BitVal <= MaxBitMask; BitVal <<= 1) - { - if((TotalStepSize + StepSize) <= AbsDifference) - { - TotalStepSize += StepSize; - EncodedSample |= BitVal; - } - StepSize >>= 1; - } - - PredictedSamples[ChannelIndex] = (short)UpdatePredictedSample(PredictedSamples[ChannelIndex], - EncodedSample, - Difference + TotalStepSize); - // Write the encoded sample to the output stream - if(!os.WriteByteSample((unsigned char)EncodedSample)) - break; - - // Calculates the step index to use for the next encode - StepIndexes[ChannelIndex] = GetNextStepIndex(StepIndexes[ChannelIndex], EncodedSample); - } - } - - return os.LengthProcessed(pvOutBuffer); -} - -//---------------------------------------------------------------------------- -// Decompression routine - -int DecompressADPCM(void * pvOutBuffer, int cbOutBuffer, void * pvInBuffer, int cbInBuffer, int ChannelCount) -{ - TADPCMStream os(pvOutBuffer, cbOutBuffer); // Output stream - TADPCMStream is(pvInBuffer, cbInBuffer); // Input stream - unsigned char EncodedSample; - unsigned char BitShift; - short PredictedSamples[MAX_ADPCM_CHANNEL_COUNT]; // Predicted sample for each channel - short StepIndexes[MAX_ADPCM_CHANNEL_COUNT]; // Predicted step index for each channel - int ChannelIndex; // Current channel index - - // Initialize the StepIndex for each channel - PredictedSamples[0] = PredictedSamples[1] = 0; - StepIndexes[0] = StepIndexes[1] = INITIAL_ADPCM_STEP_INDEX; - - // The first byte is always zero, the second one contains bit shift (compression level - 1) - is.ReadByteSample(BitShift); - is.ReadByteSample(BitShift); - - // Next, InitialSample value for each channel follows - for(int i = 0; i < ChannelCount; i++) - { - // Get the initial sample from the input stream - short InitialSample; - - // Attempt to read the initial sample - if(!is.ReadWordSample(InitialSample)) - return os.LengthProcessed(pvOutBuffer); - - // Store the initial sample to our sample array - PredictedSamples[i] = InitialSample; - - // Also store the loaded sample to the output stream - if(!os.WriteWordSample(InitialSample)) - return os.LengthProcessed(pvOutBuffer); - } - - // Get the initial index - ChannelIndex = ChannelCount - 1; - - // Keep reading as long as there is something in the input buffer - while(is.ReadByteSample(EncodedSample)) - { - // If we have two channels, we need to flip the channel index - ChannelIndex = (ChannelIndex + 1) % ChannelCount; - - if(EncodedSample == 0x80) - { - if(StepIndexes[ChannelIndex] != 0) - StepIndexes[ChannelIndex]--; - - if(!os.WriteWordSample(PredictedSamples[ChannelIndex])) - return os.LengthProcessed(pvOutBuffer); - } - else if(EncodedSample == 0x81) - { - // Modify the step index - StepIndexes[ChannelIndex] += 8; - if(StepIndexes[ChannelIndex] > 0x58) - StepIndexes[ChannelIndex] = 0x58; - - // Next pass, keep going on the same channel - ChannelIndex = (ChannelIndex + 1) % ChannelCount; - } - else - { - int StepIndex = StepIndexes[ChannelIndex]; - int StepSize = StepSizeTable[StepIndex]; - - // Encode one sample - PredictedSamples[ChannelIndex] = (short)DecodeSample(PredictedSamples[ChannelIndex], - EncodedSample, - StepSize, - StepSize >> BitShift); - - // Write the decoded sample to the output stream - if(!os.WriteWordSample(PredictedSamples[ChannelIndex])) - break; - - // Calculates the step index to use for the next encode - StepIndexes[ChannelIndex] = GetNextStepIndex(StepIndex, EncodedSample); - } - } - - // Return total bytes written since beginning of the output buffer - return os.LengthProcessed(pvOutBuffer); -} - -//----------------------------------------------------------------------------- -// ADPCM decompression present in Starcraft I BETA - -typedef struct _ADPCM_DATA -{ - const unsigned int * pValues; - int BitCount; - int field_8; - int field_C; - int field_10; - -} ADPCM_DATA, *PADPCM_DATA; - -static const unsigned int adpcm_values_2[] = {0x33, 0x66}; -static const unsigned int adpcm_values_3[] = {0x3A, 0x3A, 0x50, 0x70}; -static const unsigned int adpcm_values_4[] = {0x3A, 0x3A, 0x3A, 0x3A, 0x4D, 0x66, 0x80, 0x9A}; -static const unsigned int adpcm_values_6[] = -{ - 0x3A, 0x3A, 0x3A, 0x3A, 0x3A, 0x3A, 0x3A, 0x3A, 0x3A, 0x3A, 0x3A, 0x3A, 0x3A, 0x3A, 0x3A, 0x3A, - 0x46, 0x53, 0x60, 0x6D, 0x7A, 0x86, 0x93, 0xA0, 0xAD, 0xBA, 0xC6, 0xD3, 0xE0, 0xED, 0xFA, 0x106 -}; - -static const unsigned int * InitAdpcmData(PADPCM_DATA pData, unsigned char BitCount) -{ - switch(BitCount) - { - case 2: - pData->pValues = adpcm_values_2; - break; - - case 3: - pData->pValues = adpcm_values_3; - break; - - case 4: - pData->pValues = adpcm_values_4; - break; - - default: - pData->pValues = NULL; - break; - - case 6: - pData->pValues = adpcm_values_6; - break; - } - - pData->BitCount = BitCount; - pData->field_C = 0x20000; - pData->field_8 = 1 << BitCount; - pData->field_10 = (1 << BitCount) / 2; - return pData->pValues; -} - -int DecompressADPCM_SC1B(void * pvOutBuffer, int cbOutBuffer, void * pvInBuffer, int cbInBuffer, int ChannelCount) -{ - TADPCMStream os(pvOutBuffer, cbOutBuffer); // Output stream - TADPCMStream is(pvInBuffer, cbInBuffer); // Input stream - ADPCM_DATA AdpcmData; - int LowBitValues[MAX_ADPCM_CHANNEL_COUNT]; - int UpperBits[MAX_ADPCM_CHANNEL_COUNT]; - int BitMasks[MAX_ADPCM_CHANNEL_COUNT]; - int PredictedSamples[MAX_ADPCM_CHANNEL_COUNT]; - int ChannelIndex; - int ChannelIndexMax; - int OutputSample; - unsigned char BitCount; - unsigned char EncodedSample; - short InputValue16; - int reg_eax; - int Difference; - - // The first byte contains number of bits - if(!is.ReadByteSample(BitCount)) - return os.LengthProcessed(pvOutBuffer); - if(!InitAdpcmData(&AdpcmData, BitCount)) - return os.LengthProcessed(pvOutBuffer); - assert(AdpcmData.pValues != NULL); - - // Init bit values - for(int i = 0; i < ChannelCount; i++) - { - unsigned char OneByte; - - if(!is.ReadByteSample(OneByte)) - return os.LengthProcessed(pvOutBuffer); - LowBitValues[i] = OneByte & 0x01; - UpperBits[i] = OneByte >> 1; - } - - // - for(int i = 0; i < ChannelCount; i++) - { - if(!is.ReadWordSample(InputValue16)) - return os.LengthProcessed(pvOutBuffer); - BitMasks[i] = InputValue16 << AdpcmData.BitCount; - } - - // Next, InitialSample value for each channel follows - for(int i = 0; i < ChannelCount; i++) - { - if(!is.ReadWordSample(InputValue16)) - return os.LengthProcessed(pvOutBuffer); - - PredictedSamples[i] = InputValue16; - os.WriteWordSample(InputValue16); - } - - // Get the initial index - ChannelIndexMax = ChannelCount - 1; - ChannelIndex = 0; - - // Keep reading as long as there is something in the input buffer - while(is.ReadByteSample(EncodedSample)) - { - reg_eax = ((PredictedSamples[ChannelIndex] * 3) << 3) - PredictedSamples[ChannelIndex]; - PredictedSamples[ChannelIndex] = ((reg_eax * 10) + 0x80) >> 8; - - Difference = (((EncodedSample >> 1) + 1) * BitMasks[ChannelIndex] + AdpcmData.field_10) >> AdpcmData.BitCount; - - PredictedSamples[ChannelIndex] = UpdatePredictedSample(PredictedSamples[ChannelIndex], EncodedSample, Difference, 0x01); - - BitMasks[ChannelIndex] = (AdpcmData.pValues[EncodedSample >> 1] * BitMasks[ChannelIndex] + 0x80) >> 6; - if(BitMasks[ChannelIndex] < AdpcmData.field_8) - BitMasks[ChannelIndex] = AdpcmData.field_8; - - if(BitMasks[ChannelIndex] > AdpcmData.field_C) - BitMasks[ChannelIndex] = AdpcmData.field_C; - - reg_eax = (cbInBuffer - is.LengthProcessed(pvInBuffer)) >> ChannelIndexMax; - OutputSample = PredictedSamples[ChannelIndex]; - if(reg_eax < UpperBits[ChannelIndex]) - { - if(LowBitValues[ChannelIndex]) - { - OutputSample += (UpperBits[ChannelIndex] - reg_eax); - if(OutputSample > 32767) - OutputSample = 32767; - } - else - { - OutputSample += (reg_eax - UpperBits[ChannelIndex]); - if(OutputSample < -32768) - OutputSample = -32768; - } - } - - // Write the word sample and swap channel - os.WriteWordSample((short)(OutputSample)); - ChannelIndex = (ChannelIndex + 1) % ChannelCount; - } - - return os.LengthProcessed(pvOutBuffer); -} - diff --git a/app/jni/src/libultraship/extern/StormLib/src/adpcm/adpcm.h b/app/jni/src/libultraship/extern/StormLib/src/adpcm/adpcm.h deleted file mode 100644 index 22a8095..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/adpcm/adpcm.h +++ /dev/null @@ -1,27 +0,0 @@ -/*****************************************************************************/ -/* adpcm.h Copyright (c) Ladislav Zezula 2003 */ -/*---------------------------------------------------------------------------*/ -/* Header file for adpcm decompress functions */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 31.03.03 1.00 Lad The first version of adpcm.h */ -/*****************************************************************************/ - -#ifndef __ADPCM_H__ -#define __ADPCM_H__ - -//----------------------------------------------------------------------------- -// Defines - -#define MAX_ADPCM_CHANNEL_COUNT 2 -#define INITIAL_ADPCM_STEP_INDEX 0x2C - -//----------------------------------------------------------------------------- -// Public functions - -int CompressADPCM (void * pvOutBuffer, int dwOutLength, void * pvInBuffer, int dwInLength, int nCmpType, int ChannelCount); -int DecompressADPCM (void * pvOutBuffer, int dwOutLength, void * pvInBuffer, int dwInLength, int ChannelCount); -int DecompressADPCM_SC1B(void * pvOutBuffer, int cbOutBuffer, void * pvInBuffer, int cbInBuffer, int ChannelCount); - -#endif // __ADPCM_H__ diff --git a/app/jni/src/libultraship/extern/StormLib/src/bzip2/blocksort.c b/app/jni/src/libultraship/extern/StormLib/src/bzip2/blocksort.c deleted file mode 100644 index bd2dec1..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/bzip2/blocksort.c +++ /dev/null @@ -1,1094 +0,0 @@ - -/*-------------------------------------------------------------*/ -/*--- Block sorting machinery ---*/ -/*--- blocksort.c ---*/ -/*-------------------------------------------------------------*/ - -/* ------------------------------------------------------------------ - This file is part of bzip2/libbzip2, a program and library for - lossless, block-sorting data compression. - - bzip2/libbzip2 version 1.0.5 of 10 December 2007 - Copyright (C) 1996-2007 Julian Seward - - Please read the WARNING, DISCLAIMER and PATENTS sections in the - README file. - - This program is released under the terms of the license contained - in the file LICENSE. - ------------------------------------------------------------------ */ - - -#include "bzlib_private.h" - -/*---------------------------------------------*/ -/*--- Fallback O(N log(N)^2) sorting ---*/ -/*--- algorithm, for repetitive blocks ---*/ -/*---------------------------------------------*/ - -/*---------------------------------------------*/ -static -__inline__ -void fallbackSimpleSort ( UInt32* fmap, - UInt32* eclass, - Int32 lo, - Int32 hi ) -{ - Int32 i, j, tmp; - UInt32 ec_tmp; - - if (lo == hi) return; - - if (hi - lo > 3) { - for ( i = hi-4; i >= lo; i-- ) { - tmp = fmap[i]; - ec_tmp = eclass[tmp]; - for ( j = i+4; j <= hi && ec_tmp > eclass[fmap[j]]; j += 4 ) - fmap[j-4] = fmap[j]; - fmap[j-4] = tmp; - } - } - - for ( i = hi-1; i >= lo; i-- ) { - tmp = fmap[i]; - ec_tmp = eclass[tmp]; - for ( j = i+1; j <= hi && ec_tmp > eclass[fmap[j]]; j++ ) - fmap[j-1] = fmap[j]; - fmap[j-1] = tmp; - } -} - - -/*---------------------------------------------*/ -#define fswap(zz1, zz2) \ - { Int32 zztmp = zz1; zz1 = zz2; zz2 = zztmp; } - -#define fvswap(zzp1, zzp2, zzn) \ -{ \ - Int32 yyp1 = (zzp1); \ - Int32 yyp2 = (zzp2); \ - Int32 yyn = (zzn); \ - while (yyn > 0) { \ - fswap(fmap[yyp1], fmap[yyp2]); \ - yyp1++; yyp2++; yyn--; \ - } \ -} - - -#define fmin(a,b) ((a) < (b)) ? (a) : (b) - -#define fpush(lz,hz) { stackLo[sp] = lz; \ - stackHi[sp] = hz; \ - sp++; } - -#define fpop(lz,hz) { sp--; \ - lz = stackLo[sp]; \ - hz = stackHi[sp]; } - -#define FALLBACK_QSORT_SMALL_THRESH 10 -#define FALLBACK_QSORT_STACK_SIZE 100 - - -static -void fallbackQSort3 ( UInt32* fmap, - UInt32* eclass, - Int32 loSt, - Int32 hiSt ) -{ - Int32 unLo, unHi, ltLo, gtHi, n, m; - Int32 sp, lo, hi; - UInt32 med, r, r3; - Int32 stackLo[FALLBACK_QSORT_STACK_SIZE]; - Int32 stackHi[FALLBACK_QSORT_STACK_SIZE]; - - r = 0; - - sp = 0; - fpush ( loSt, hiSt ); - - while (sp > 0) { - - AssertH ( sp < FALLBACK_QSORT_STACK_SIZE - 1, 1004 ); - - fpop ( lo, hi ); - if (hi - lo < FALLBACK_QSORT_SMALL_THRESH) { - fallbackSimpleSort ( fmap, eclass, lo, hi ); - continue; - } - - /* Random partitioning. Median of 3 sometimes fails to - avoid bad cases. Median of 9 seems to help but - looks rather expensive. This too seems to work but - is cheaper. Guidance for the magic constants - 7621 and 32768 is taken from Sedgewick's algorithms - book, chapter 35. - */ - r = ((r * 7621) + 1) % 32768; - r3 = r % 3; - if (r3 == 0) med = eclass[fmap[lo]]; else - if (r3 == 1) med = eclass[fmap[(lo+hi)>>1]]; else - med = eclass[fmap[hi]]; - - unLo = ltLo = lo; - unHi = gtHi = hi; - - while (1) { - while (1) { - if (unLo > unHi) break; - n = (Int32)eclass[fmap[unLo]] - (Int32)med; - if (n == 0) { - fswap(fmap[unLo], fmap[ltLo]); - ltLo++; unLo++; - continue; - }; - if (n > 0) break; - unLo++; - } - while (1) { - if (unLo > unHi) break; - n = (Int32)eclass[fmap[unHi]] - (Int32)med; - if (n == 0) { - fswap(fmap[unHi], fmap[gtHi]); - gtHi--; unHi--; - continue; - }; - if (n < 0) break; - unHi--; - } - if (unLo > unHi) break; - fswap(fmap[unLo], fmap[unHi]); unLo++; unHi--; - } - - AssertD ( unHi == unLo-1, "fallbackQSort3(2)" ); - - if (gtHi < ltLo) continue; - - n = fmin(ltLo-lo, unLo-ltLo); fvswap(lo, unLo-n, n); - m = fmin(hi-gtHi, gtHi-unHi); fvswap(unLo, hi-m+1, m); - - n = lo + unLo - ltLo - 1; - m = hi - (gtHi - unHi) + 1; - - if (n - lo > hi - m) { - fpush ( lo, n ); - fpush ( m, hi ); - } else { - fpush ( m, hi ); - fpush ( lo, n ); - } - } -} - -#undef fmin -#undef fpush -#undef fpop -#undef fswap -#undef fvswap -#undef FALLBACK_QSORT_SMALL_THRESH -#undef FALLBACK_QSORT_STACK_SIZE - - -/*---------------------------------------------*/ -/* Pre: - nblock > 0 - eclass exists for [0 .. nblock-1] - ((UChar*)eclass) [0 .. nblock-1] holds block - ptr exists for [0 .. nblock-1] - - Post: - ((UChar*)eclass) [0 .. nblock-1] holds block - All other areas of eclass destroyed - fmap [0 .. nblock-1] holds sorted order - bhtab [ 0 .. 2+(nblock/32) ] destroyed -*/ - -#define SET_BH(zz) bhtab[(zz) >> 5] |= (1 << ((zz) & 31)) -#define CLEAR_BH(zz) bhtab[(zz) >> 5] &= ~(1 << ((zz) & 31)) -#define ISSET_BH(zz) (bhtab[(zz) >> 5] & (1 << ((zz) & 31))) -#define WORD_BH(zz) bhtab[(zz) >> 5] -#define UNALIGNED_BH(zz) ((zz) & 0x01f) - -static -void fallbackSort ( UInt32* fmap, - UInt32* eclass, - UInt32* bhtab, - Int32 nblock, - Int32 verb ) -{ - Int32 ftab[257]; - Int32 ftabCopy[256]; - Int32 H, i, j, k, l, r, cc, cc1; - Int32 nNotDone; - Int32 nBhtab; - UChar* eclass8 = (UChar*)eclass; - - /*-- - Initial 1-char radix sort to generate - initial fmap and initial BH bits. - --*/ - if (verb >= 4) - VPrintf0 ( " bucket sorting ...\n" ); - for (i = 0; i < 257; i++) ftab[i] = 0; - for (i = 0; i < nblock; i++) ftab[eclass8[i]]++; - for (i = 0; i < 256; i++) ftabCopy[i] = ftab[i]; - for (i = 1; i < 257; i++) ftab[i] += ftab[i-1]; - - for (i = 0; i < nblock; i++) { - j = eclass8[i]; - k = ftab[j] - 1; - ftab[j] = k; - fmap[k] = i; - } - - nBhtab = 2 + (nblock / 32); - for (i = 0; i < nBhtab; i++) bhtab[i] = 0; - for (i = 0; i < 256; i++) SET_BH(ftab[i]); - - /*-- - Inductively refine the buckets. Kind-of an - "exponential radix sort" (!), inspired by the - Manber-Myers suffix array construction algorithm. - --*/ - - /*-- set sentinel bits for block-end detection --*/ - for (i = 0; i < 32; i++) { - SET_BH(nblock + 2*i); - CLEAR_BH(nblock + 2*i + 1); - } - - /*-- the log(N) loop --*/ - H = 1; - while (1) { - - if (verb >= 4) - VPrintf1 ( " depth %6d has ", H ); - - j = 0; - for (i = 0; i < nblock; i++) { - if (ISSET_BH(i)) j = i; - k = fmap[i] - H; if (k < 0) k += nblock; - eclass[k] = j; - } - - nNotDone = 0; - r = -1; - while (1) { - - /*-- find the next non-singleton bucket --*/ - k = r + 1; - while (ISSET_BH(k) && UNALIGNED_BH(k)) k++; - if (ISSET_BH(k)) { - while (WORD_BH(k) == 0xffffffff) k += 32; - while (ISSET_BH(k)) k++; - } - l = k - 1; - if (l >= nblock) break; - while (!ISSET_BH(k) && UNALIGNED_BH(k)) k++; - if (!ISSET_BH(k)) { - while (WORD_BH(k) == 0x00000000) k += 32; - while (!ISSET_BH(k)) k++; - } - r = k - 1; - if (r >= nblock) break; - - /*-- now [l, r] bracket current bucket --*/ - if (r > l) { - nNotDone += (r - l + 1); - fallbackQSort3 ( fmap, eclass, l, r ); - - /*-- scan bucket and generate header bits-- */ - cc = -1; - for (i = l; i <= r; i++) { - cc1 = eclass[fmap[i]]; - if (cc != cc1) { SET_BH(i); cc = cc1; }; - } - } - } - - if (verb >= 4) - VPrintf1 ( "%6d unresolved strings\n", nNotDone ); - - H *= 2; - if (H > nblock || nNotDone == 0) break; - } - - /*-- - Reconstruct the original block in - eclass8 [0 .. nblock-1], since the - previous phase destroyed it. - --*/ - if (verb >= 4) - VPrintf0 ( " reconstructing block ...\n" ); - j = 0; - for (i = 0; i < nblock; i++) { - while (ftabCopy[j] == 0) j++; - ftabCopy[j]--; - eclass8[fmap[i]] = (UChar)j; - } - AssertH ( j < 256, 1005 ); -} - -#undef SET_BH -#undef CLEAR_BH -#undef ISSET_BH -#undef WORD_BH -#undef UNALIGNED_BH - - -/*---------------------------------------------*/ -/*--- The main, O(N^2 log(N)) sorting ---*/ -/*--- algorithm. Faster for "normal" ---*/ -/*--- non-repetitive blocks. ---*/ -/*---------------------------------------------*/ - -/*---------------------------------------------*/ -static -__inline__ -Bool mainGtU ( UInt32 i1, - UInt32 i2, - UChar* block, - UInt16* quadrant, - UInt32 nblock, - Int32* budget ) -{ - Int32 k; - UChar c1, c2; - UInt16 s1, s2; - - AssertD ( i1 != i2, "mainGtU" ); - /* 1 */ - c1 = block[i1]; c2 = block[i2]; - if (c1 != c2) return (c1 > c2); - i1++; i2++; - /* 2 */ - c1 = block[i1]; c2 = block[i2]; - if (c1 != c2) return (c1 > c2); - i1++; i2++; - /* 3 */ - c1 = block[i1]; c2 = block[i2]; - if (c1 != c2) return (c1 > c2); - i1++; i2++; - /* 4 */ - c1 = block[i1]; c2 = block[i2]; - if (c1 != c2) return (c1 > c2); - i1++; i2++; - /* 5 */ - c1 = block[i1]; c2 = block[i2]; - if (c1 != c2) return (c1 > c2); - i1++; i2++; - /* 6 */ - c1 = block[i1]; c2 = block[i2]; - if (c1 != c2) return (c1 > c2); - i1++; i2++; - /* 7 */ - c1 = block[i1]; c2 = block[i2]; - if (c1 != c2) return (c1 > c2); - i1++; i2++; - /* 8 */ - c1 = block[i1]; c2 = block[i2]; - if (c1 != c2) return (c1 > c2); - i1++; i2++; - /* 9 */ - c1 = block[i1]; c2 = block[i2]; - if (c1 != c2) return (c1 > c2); - i1++; i2++; - /* 10 */ - c1 = block[i1]; c2 = block[i2]; - if (c1 != c2) return (c1 > c2); - i1++; i2++; - /* 11 */ - c1 = block[i1]; c2 = block[i2]; - if (c1 != c2) return (c1 > c2); - i1++; i2++; - /* 12 */ - c1 = block[i1]; c2 = block[i2]; - if (c1 != c2) return (c1 > c2); - i1++; i2++; - - k = nblock + 8; - - do { - /* 1 */ - c1 = block[i1]; c2 = block[i2]; - if (c1 != c2) return (c1 > c2); - s1 = quadrant[i1]; s2 = quadrant[i2]; - if (s1 != s2) return (s1 > s2); - i1++; i2++; - /* 2 */ - c1 = block[i1]; c2 = block[i2]; - if (c1 != c2) return (c1 > c2); - s1 = quadrant[i1]; s2 = quadrant[i2]; - if (s1 != s2) return (s1 > s2); - i1++; i2++; - /* 3 */ - c1 = block[i1]; c2 = block[i2]; - if (c1 != c2) return (c1 > c2); - s1 = quadrant[i1]; s2 = quadrant[i2]; - if (s1 != s2) return (s1 > s2); - i1++; i2++; - /* 4 */ - c1 = block[i1]; c2 = block[i2]; - if (c1 != c2) return (c1 > c2); - s1 = quadrant[i1]; s2 = quadrant[i2]; - if (s1 != s2) return (s1 > s2); - i1++; i2++; - /* 5 */ - c1 = block[i1]; c2 = block[i2]; - if (c1 != c2) return (c1 > c2); - s1 = quadrant[i1]; s2 = quadrant[i2]; - if (s1 != s2) return (s1 > s2); - i1++; i2++; - /* 6 */ - c1 = block[i1]; c2 = block[i2]; - if (c1 != c2) return (c1 > c2); - s1 = quadrant[i1]; s2 = quadrant[i2]; - if (s1 != s2) return (s1 > s2); - i1++; i2++; - /* 7 */ - c1 = block[i1]; c2 = block[i2]; - if (c1 != c2) return (c1 > c2); - s1 = quadrant[i1]; s2 = quadrant[i2]; - if (s1 != s2) return (s1 > s2); - i1++; i2++; - /* 8 */ - c1 = block[i1]; c2 = block[i2]; - if (c1 != c2) return (c1 > c2); - s1 = quadrant[i1]; s2 = quadrant[i2]; - if (s1 != s2) return (s1 > s2); - i1++; i2++; - - if (i1 >= nblock) i1 -= nblock; - if (i2 >= nblock) i2 -= nblock; - - k -= 8; - (*budget)--; - } - while (k >= 0); - - return False; -} - - -/*---------------------------------------------*/ -/*-- - Knuth's increments seem to work better - than Incerpi-Sedgewick here. Possibly - because the number of elems to sort is - usually small, typically <= 20. ---*/ -static -Int32 incs[14] = { 1, 4, 13, 40, 121, 364, 1093, 3280, - 9841, 29524, 88573, 265720, - 797161, 2391484 }; - -static -void mainSimpleSort ( UInt32* ptr, - UChar* block, - UInt16* quadrant, - Int32 nblock, - Int32 lo, - Int32 hi, - Int32 d, - Int32* budget ) -{ - Int32 i, j, h, bigN, hp; - UInt32 v; - - bigN = hi - lo + 1; - if (bigN < 2) return; - - hp = 0; - while (incs[hp] < bigN) hp++; - hp--; - - for (; hp >= 0; hp--) { - h = incs[hp]; - - i = lo + h; - while (True) { - - /*-- copy 1 --*/ - if (i > hi) break; - v = ptr[i]; - j = i; - while ( mainGtU ( - ptr[j-h]+d, v+d, block, quadrant, nblock, budget - ) ) { - ptr[j] = ptr[j-h]; - j = j - h; - if (j <= (lo + h - 1)) break; - } - ptr[j] = v; - i++; - - /*-- copy 2 --*/ - if (i > hi) break; - v = ptr[i]; - j = i; - while ( mainGtU ( - ptr[j-h]+d, v+d, block, quadrant, nblock, budget - ) ) { - ptr[j] = ptr[j-h]; - j = j - h; - if (j <= (lo + h - 1)) break; - } - ptr[j] = v; - i++; - - /*-- copy 3 --*/ - if (i > hi) break; - v = ptr[i]; - j = i; - while ( mainGtU ( - ptr[j-h]+d, v+d, block, quadrant, nblock, budget - ) ) { - ptr[j] = ptr[j-h]; - j = j - h; - if (j <= (lo + h - 1)) break; - } - ptr[j] = v; - i++; - - if (*budget < 0) return; - } - } -} - - -/*---------------------------------------------*/ -/*-- - The following is an implementation of - an elegant 3-way quicksort for strings, - described in a paper "Fast Algorithms for - Sorting and Searching Strings", by Robert - Sedgewick and Jon L. Bentley. ---*/ - -#define mswap(zz1, zz2) \ - { Int32 zztmp = zz1; zz1 = zz2; zz2 = zztmp; } - -#define mvswap(zzp1, zzp2, zzn) \ -{ \ - Int32 yyp1 = (zzp1); \ - Int32 yyp2 = (zzp2); \ - Int32 yyn = (zzn); \ - while (yyn > 0) { \ - mswap(ptr[yyp1], ptr[yyp2]); \ - yyp1++; yyp2++; yyn--; \ - } \ -} - -static -__inline__ -UChar mmed3 ( UChar a, UChar b, UChar c ) -{ - UChar t; - if (a > b) { t = a; a = b; b = t; }; - if (b > c) { - b = c; - if (a > b) b = a; - } - return b; -} - -#define mmin(a,b) ((a) < (b)) ? (a) : (b) - -#define mpush(lz,hz,dz) { stackLo[sp] = lz; \ - stackHi[sp] = hz; \ - stackD [sp] = dz; \ - sp++; } - -#define mpop(lz,hz,dz) { sp--; \ - lz = stackLo[sp]; \ - hz = stackHi[sp]; \ - dz = stackD [sp]; } - - -#define mnextsize(az) (nextHi[az]-nextLo[az]) - -#define mnextswap(az,bz) \ - { Int32 tz; \ - tz = nextLo[az]; nextLo[az] = nextLo[bz]; nextLo[bz] = tz; \ - tz = nextHi[az]; nextHi[az] = nextHi[bz]; nextHi[bz] = tz; \ - tz = nextD [az]; nextD [az] = nextD [bz]; nextD [bz] = tz; } - - -#define MAIN_QSORT_SMALL_THRESH 20 -#define MAIN_QSORT_DEPTH_THRESH (BZ_N_RADIX + BZ_N_QSORT) -#define MAIN_QSORT_STACK_SIZE 100 - -static -void mainQSort3 ( UInt32* ptr, - UChar* block, - UInt16* quadrant, - Int32 nblock, - Int32 loSt, - Int32 hiSt, - Int32 dSt, - Int32* budget ) -{ - Int32 unLo, unHi, ltLo, gtHi, n, m, med; - Int32 sp, lo, hi, d; - - Int32 stackLo[MAIN_QSORT_STACK_SIZE]; - Int32 stackHi[MAIN_QSORT_STACK_SIZE]; - Int32 stackD [MAIN_QSORT_STACK_SIZE]; - - Int32 nextLo[3]; - Int32 nextHi[3]; - Int32 nextD [3]; - - sp = 0; - mpush ( loSt, hiSt, dSt ); - - while (sp > 0) { - - AssertH ( sp < MAIN_QSORT_STACK_SIZE - 2, 1001 ); - - mpop ( lo, hi, d ); - if (hi - lo < MAIN_QSORT_SMALL_THRESH || - d > MAIN_QSORT_DEPTH_THRESH) { - mainSimpleSort ( ptr, block, quadrant, nblock, lo, hi, d, budget ); - if (*budget < 0) return; - continue; - } - - med = (Int32) - mmed3 ( block[ptr[ lo ]+d], - block[ptr[ hi ]+d], - block[ptr[ (lo+hi)>>1 ]+d] ); - - unLo = ltLo = lo; - unHi = gtHi = hi; - - while (True) { - while (True) { - if (unLo > unHi) break; - n = ((Int32)block[ptr[unLo]+d]) - med; - if (n == 0) { - mswap(ptr[unLo], ptr[ltLo]); - ltLo++; unLo++; continue; - }; - if (n > 0) break; - unLo++; - } - while (True) { - if (unLo > unHi) break; - n = ((Int32)block[ptr[unHi]+d]) - med; - if (n == 0) { - mswap(ptr[unHi], ptr[gtHi]); - gtHi--; unHi--; continue; - }; - if (n < 0) break; - unHi--; - } - if (unLo > unHi) break; - mswap(ptr[unLo], ptr[unHi]); unLo++; unHi--; - } - - AssertD ( unHi == unLo-1, "mainQSort3(2)" ); - - if (gtHi < ltLo) { - mpush(lo, hi, d+1 ); - continue; - } - - n = mmin(ltLo-lo, unLo-ltLo); mvswap(lo, unLo-n, n); - m = mmin(hi-gtHi, gtHi-unHi); mvswap(unLo, hi-m+1, m); - - n = lo + unLo - ltLo - 1; - m = hi - (gtHi - unHi) + 1; - - nextLo[0] = lo; nextHi[0] = n; nextD[0] = d; - nextLo[1] = m; nextHi[1] = hi; nextD[1] = d; - nextLo[2] = n+1; nextHi[2] = m-1; nextD[2] = d+1; - - if (mnextsize(0) < mnextsize(1)) mnextswap(0,1); - if (mnextsize(1) < mnextsize(2)) mnextswap(1,2); - if (mnextsize(0) < mnextsize(1)) mnextswap(0,1); - - AssertD (mnextsize(0) >= mnextsize(1), "mainQSort3(8)" ); - AssertD (mnextsize(1) >= mnextsize(2), "mainQSort3(9)" ); - - mpush (nextLo[0], nextHi[0], nextD[0]); - mpush (nextLo[1], nextHi[1], nextD[1]); - mpush (nextLo[2], nextHi[2], nextD[2]); - } -} - -#undef mswap -#undef mvswap -#undef mpush -#undef mpop -#undef mmin -#undef mnextsize -#undef mnextswap -#undef MAIN_QSORT_SMALL_THRESH -#undef MAIN_QSORT_DEPTH_THRESH -#undef MAIN_QSORT_STACK_SIZE - - -/*---------------------------------------------*/ -/* Pre: - nblock > N_OVERSHOOT - block32 exists for [0 .. nblock-1 +N_OVERSHOOT] - ((UChar*)block32) [0 .. nblock-1] holds block - ptr exists for [0 .. nblock-1] - - Post: - ((UChar*)block32) [0 .. nblock-1] holds block - All other areas of block32 destroyed - ftab [0 .. 65536 ] destroyed - ptr [0 .. nblock-1] holds sorted order - if (*budget < 0), sorting was abandoned -*/ - -#define BIGFREQ(b) (ftab[((b)+1) << 8] - ftab[(b) << 8]) -#define SETMASK (1 << 21) -#define CLEARMASK (~(SETMASK)) - -static -void mainSort ( UInt32* ptr, - UChar* block, - UInt16* quadrant, - UInt32* ftab, - Int32 nblock, - Int32 verb, - Int32* budget ) -{ - Int32 i, j, k, ss, sb; - Int32 runningOrder[256]; - Bool bigDone[256]; - Int32 copyStart[256]; - Int32 copyEnd [256]; - UChar c1; - Int32 numQSorted; - UInt16 s; - if (verb >= 4) VPrintf0 ( " main sort initialise ...\n" ); - - /*-- set up the 2-byte frequency table --*/ - for (i = 65536; i >= 0; i--) ftab[i] = 0; - - j = block[0] << 8; - i = nblock-1; - for (; i >= 3; i -= 4) { - quadrant[i] = 0; - j = (j >> 8) | ( ((UInt16)block[i]) << 8); - ftab[j]++; - quadrant[i-1] = 0; - j = (j >> 8) | ( ((UInt16)block[i-1]) << 8); - ftab[j]++; - quadrant[i-2] = 0; - j = (j >> 8) | ( ((UInt16)block[i-2]) << 8); - ftab[j]++; - quadrant[i-3] = 0; - j = (j >> 8) | ( ((UInt16)block[i-3]) << 8); - ftab[j]++; - } - for (; i >= 0; i--) { - quadrant[i] = 0; - j = (j >> 8) | ( ((UInt16)block[i]) << 8); - ftab[j]++; - } - - /*-- (emphasises close relationship of block & quadrant) --*/ - for (i = 0; i < BZ_N_OVERSHOOT; i++) { - block [nblock+i] = block[i]; - quadrant[nblock+i] = 0; - } - - if (verb >= 4) VPrintf0 ( " bucket sorting ...\n" ); - - /*-- Complete the initial radix sort --*/ - for (i = 1; i <= 65536; i++) ftab[i] += ftab[i-1]; - - s = block[0] << 8; - i = nblock-1; - for (; i >= 3; i -= 4) { - s = (s >> 8) | (block[i] << 8); - j = ftab[s] -1; - ftab[s] = j; - ptr[j] = i; - s = (s >> 8) | (block[i-1] << 8); - j = ftab[s] -1; - ftab[s] = j; - ptr[j] = i-1; - s = (s >> 8) | (block[i-2] << 8); - j = ftab[s] -1; - ftab[s] = j; - ptr[j] = i-2; - s = (s >> 8) | (block[i-3] << 8); - j = ftab[s] -1; - ftab[s] = j; - ptr[j] = i-3; - } - for (; i >= 0; i--) { - s = (s >> 8) | (block[i] << 8); - j = ftab[s] -1; - ftab[s] = j; - ptr[j] = i; - } - - /*-- - Now ftab contains the first loc of every small bucket. - Calculate the running order, from smallest to largest - big bucket. - --*/ - for (i = 0; i <= 255; i++) { - bigDone [i] = False; - runningOrder[i] = i; - } - - { - Int32 vv; - Int32 h = 1; - do h = 3 * h + 1; while (h <= 256); - do { - h = h / 3; - for (i = h; i <= 255; i++) { - vv = runningOrder[i]; - j = i; - while ( BIGFREQ(runningOrder[j-h]) > BIGFREQ(vv) ) { - runningOrder[j] = runningOrder[j-h]; - j = j - h; - if (j <= (h - 1)) goto zero; - } - zero: - runningOrder[j] = vv; - } - } while (h != 1); - } - - /*-- - The main sorting loop. - --*/ - - numQSorted = 0; - - for (i = 0; i <= 255; i++) { - - /*-- - Process big buckets, starting with the least full. - Basically this is a 3-step process in which we call - mainQSort3 to sort the small buckets [ss, j], but - also make a big effort to avoid the calls if we can. - --*/ - ss = runningOrder[i]; - - /*-- - Step 1: - Complete the big bucket [ss] by quicksorting - any unsorted small buckets [ss, j], for j != ss. - Hopefully previous pointer-scanning phases have already - completed many of the small buckets [ss, j], so - we don't have to sort them at all. - --*/ - for (j = 0; j <= 255; j++) { - if (j != ss) { - sb = (ss << 8) + j; - if ( ! (ftab[sb] & SETMASK) ) { - Int32 lo = ftab[sb] & CLEARMASK; - Int32 hi = (ftab[sb+1] & CLEARMASK) - 1; - if (hi > lo) { - if (verb >= 4) - VPrintf4 ( " qsort [0x%x, 0x%x] " - "done %d this %d\n", - ss, j, numQSorted, hi - lo + 1 ); - mainQSort3 ( - ptr, block, quadrant, nblock, - lo, hi, BZ_N_RADIX, budget - ); - numQSorted += (hi - lo + 1); - if (*budget < 0) return; - } - } - ftab[sb] |= SETMASK; - } - } - - AssertH ( !bigDone[ss], 1006 ); - - /*-- - Step 2: - Now scan this big bucket [ss] so as to synthesise the - sorted order for small buckets [t, ss] for all t, - including, magically, the bucket [ss,ss] too. - This will avoid doing Real Work in subsequent Step 1's. - --*/ - { - for (j = 0; j <= 255; j++) { - copyStart[j] = ftab[(j << 8) + ss] & CLEARMASK; - copyEnd [j] = (ftab[(j << 8) + ss + 1] & CLEARMASK) - 1; - } - for (j = ftab[ss << 8] & CLEARMASK; j < copyStart[ss]; j++) { - k = ptr[j]-1; if (k < 0) k += nblock; - c1 = block[k]; - if (!bigDone[c1]) - ptr[ copyStart[c1]++ ] = k; - } - for (j = (ftab[(ss+1) << 8] & CLEARMASK) - 1; j > copyEnd[ss]; j--) { - k = ptr[j]-1; if (k < 0) k += nblock; - c1 = block[k]; - if (!bigDone[c1]) - ptr[ copyEnd[c1]-- ] = k; - } - } - - AssertH ( (copyStart[ss]-1 == copyEnd[ss]) - || - /* Extremely rare case missing in bzip2-1.0.0 and 1.0.1. - Necessity for this case is demonstrated by compressing - a sequence of approximately 48.5 million of character - 251; 1.0.0/1.0.1 will then die here. */ - (copyStart[ss] == 0 && copyEnd[ss] == nblock-1), - 1007 ) - - for (j = 0; j <= 255; j++) ftab[(j << 8) + ss] |= SETMASK; - - /*-- - Step 3: - The [ss] big bucket is now done. Record this fact, - and update the quadrant descriptors. Remember to - update quadrants in the overshoot area too, if - necessary. The "if (i < 255)" test merely skips - this updating for the last bucket processed, since - updating for the last bucket is pointless. - - The quadrant array provides a way to incrementally - cache sort orderings, as they appear, so as to - make subsequent comparisons in fullGtU() complete - faster. For repetitive blocks this makes a big - difference (but not big enough to be able to avoid - the fallback sorting mechanism, exponential radix sort). - - The precise meaning is: at all times: - - for 0 <= i < nblock and 0 <= j <= nblock - - if block[i] != block[j], - - then the relative values of quadrant[i] and - quadrant[j] are meaningless. - - else { - if quadrant[i] < quadrant[j] - then the string starting at i lexicographically - precedes the string starting at j - - else if quadrant[i] > quadrant[j] - then the string starting at j lexicographically - precedes the string starting at i - - else - the relative ordering of the strings starting - at i and j has not yet been determined. - } - --*/ - bigDone[ss] = True; - - if (i < 255) { - Int32 bbStart = ftab[ss << 8] & CLEARMASK; - Int32 bbSize = (ftab[(ss+1) << 8] & CLEARMASK) - bbStart; - Int32 shifts = 0; - - while ((bbSize >> shifts) > 65534) shifts++; - - for (j = bbSize-1; j >= 0; j--) { - Int32 a2update = ptr[bbStart + j]; - UInt16 qVal = (UInt16)(j >> shifts); - quadrant[a2update] = qVal; - if (a2update < BZ_N_OVERSHOOT) - quadrant[a2update + nblock] = qVal; - } - AssertH ( ((bbSize-1) >> shifts) <= 65535, 1002 ); - } - - } - - if (verb >= 4) - VPrintf3 ( " %d pointers, %d sorted, %d scanned\n", - nblock, numQSorted, nblock - numQSorted ); -} - -#undef BIGFREQ -#undef SETMASK -#undef CLEARMASK - - -/*---------------------------------------------*/ -/* Pre: - nblock > 0 - arr2 exists for [0 .. nblock-1 +N_OVERSHOOT] - ((UChar*)arr2) [0 .. nblock-1] holds block - arr1 exists for [0 .. nblock-1] - - Post: - ((UChar*)arr2) [0 .. nblock-1] holds block - All other areas of block destroyed - ftab [ 0 .. 65536 ] destroyed - arr1 [0 .. nblock-1] holds sorted order -*/ -void BZ2_blockSort ( EState* s ) -{ - UInt32* ptr = s->ptr; - UChar* block = s->block; - UInt32* ftab = s->ftab; - Int32 nblock = s->nblock; - Int32 verb = s->verbosity; - Int32 wfact = s->workFactor; - UInt16* quadrant; - Int32 budget; - Int32 budgetInit; - Int32 i; - - if (nblock < 10000) { - fallbackSort ( s->arr1, s->arr2, ftab, nblock, verb ); - } else { - /* Calculate the location for quadrant, remembering to get - the alignment right. Assumes that &(block[0]) is at least - 2-byte aligned -- this should be ok since block is really - the first section of arr2. - */ - i = nblock+BZ_N_OVERSHOOT; - if (i & 1) i++; - quadrant = (UInt16*)(&(block[i])); - - /* (wfact-1) / 3 puts the default-factor-30 - transition point at very roughly the same place as - with v0.1 and v0.9.0. - Not that it particularly matters any more, since the - resulting compressed stream is now the same regardless - of whether or not we use the main sort or fallback sort. - */ - if (wfact < 1 ) wfact = 1; - if (wfact > 100) wfact = 100; - budgetInit = nblock * ((wfact-1) / 3); - budget = budgetInit; - - mainSort ( ptr, block, quadrant, ftab, nblock, verb, &budget ); - if (verb >= 3) - VPrintf3 ( " %d work, %d block, ratio %5.2f\n", - budgetInit - budget, - nblock, - (float)(budgetInit - budget) / - (float)(nblock==0 ? 1 : nblock) ); - if (budget < 0) { - if (verb >= 2) - VPrintf0 ( " too repetitive; using fallback" - " sorting algorithm\n" ); - fallbackSort ( s->arr1, s->arr2, ftab, nblock, verb ); - } - } - - s->origPtr = -1; - for (i = 0; i < s->nblock; i++) - if (ptr[i] == 0) - { s->origPtr = i; break; }; - - AssertH( s->origPtr != -1, 1003 ); -} - - -/*-------------------------------------------------------------*/ -/*--- end blocksort.c ---*/ -/*-------------------------------------------------------------*/ diff --git a/app/jni/src/libultraship/extern/StormLib/src/bzip2/bzlib.c b/app/jni/src/libultraship/extern/StormLib/src/bzip2/bzlib.c deleted file mode 100644 index b98f3e5..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/bzip2/bzlib.c +++ /dev/null @@ -1,1573 +0,0 @@ - -/*-------------------------------------------------------------*/ -/*--- Library top-level functions. ---*/ -/*--- bzlib.c ---*/ -/*-------------------------------------------------------------*/ - -/* ------------------------------------------------------------------ - This file is part of bzip2/libbzip2, a program and library for - lossless, block-sorting data compression. - - bzip2/libbzip2 version 1.0.5 of 10 December 2007 - Copyright (C) 1996-2007 Julian Seward - - Please read the WARNING, DISCLAIMER and PATENTS sections in the - README file. - - This program is released under the terms of the license contained - in the file LICENSE. - ------------------------------------------------------------------ */ - -/* CHANGES - 0.9.0 -- original version. - 0.9.0a/b -- no changes in this file. - 0.9.0c -- made zero-length BZ_FLUSH work correctly in bzCompress(). - fixed bzWrite/bzRead to ignore zero-length requests. - fixed bzread to correctly handle read requests after EOF. - wrong parameter order in call to bzDecompressInit in - bzBuffToBuffDecompress. Fixed. -*/ - -#define _CRT_SECURE_NO_WARNINGS -#include "bzlib_private.h" - - -/*---------------------------------------------------*/ -/*--- Compression stuff ---*/ -/*---------------------------------------------------*/ - - -/*---------------------------------------------------*/ -#ifndef BZ_NO_STDIO -void BZ2_bz__AssertH__fail ( int errcode ) -{ - fprintf(stderr, - "\n\nbzip2/libbzip2: internal error number %d.\n" - "This is a bug in bzip2/libbzip2, %s.\n" - "Please report it to me at: jseward@bzip.org. If this happened\n" - "when you were using some program which uses libbzip2 as a\n" - "component, you should also report this bug to the author(s)\n" - "of that program. Please make an effort to report this bug;\n" - "timely and accurate bug reports eventually lead to higher\n" - "quality software. Thanks. Julian Seward, 10 December 2007.\n\n", - errcode, - BZ2_bzlibVersion() - ); - - if (errcode == 1007) { - fprintf(stderr, - "\n*** A special note about internal error number 1007 ***\n" - "\n" - "Experience suggests that a common cause of i.e. 1007\n" - "is unreliable memory or other hardware. The 1007 assertion\n" - "just happens to cross-check the results of huge numbers of\n" - "memory reads/writes, and so acts (unintendedly) as a stress\n" - "test of your memory system.\n" - "\n" - "I suggest the following: try compressing the file again,\n" - "possibly monitoring progress in detail with the -vv flag.\n" - "\n" - "* If the error cannot be reproduced, and/or happens at different\n" - " points in compression, you may have a flaky memory system.\n" - " Try a memory-test program. I have used Memtest86\n" - " (www.memtest86.com). At the time of writing it is free (GPLd).\n" - " Memtest86 tests memory much more thorougly than your BIOSs\n" - " power-on test, and may find failures that the BIOS doesn't.\n" - "\n" - "* If the error can be repeatably reproduced, this is a bug in\n" - " bzip2, and I would very much like to hear about it. Please\n" - " let me know, and, ideally, save a copy of the file causing the\n" - " problem -- without which I will be unable to investigate it.\n" - "\n" - ); - } - - exit(3); -} -#endif - - -/*---------------------------------------------------*/ -static -int bz_config_ok ( void ) -{ - if (sizeof(int) != 4) return 0; - if (sizeof(short) != 2) return 0; - if (sizeof(char) != 1) return 0; - return 1; -} - - -/*---------------------------------------------------*/ -static -void* default_bzalloc ( void* opaque, Int32 items, Int32 size ) -{ - void* v = malloc ( items * size ); - return v; -} - -static -void default_bzfree ( void* opaque, void* addr ) -{ - if (addr != NULL) free ( addr ); -} - - -/*---------------------------------------------------*/ -static -void prepare_new_block ( EState* s ) -{ - Int32 i; - s->nblock = 0; - s->numZ = 0; - s->state_out_pos = 0; - BZ_INITIALISE_CRC ( s->blockCRC ); - for (i = 0; i < 256; i++) s->inUse[i] = False; - s->blockNo++; -} - - -/*---------------------------------------------------*/ -static -void init_RL ( EState* s ) -{ - s->state_in_ch = 256; - s->state_in_len = 0; -} - - -static -Bool isempty_RL ( EState* s ) -{ - if (s->state_in_ch < 256 && s->state_in_len > 0) - return False; else - return True; -} - - -/*---------------------------------------------------*/ -int BZ_API(BZ2_bzCompressInit) - ( bz_stream* strm, - int blockSize100k, - int verbosity, - int workFactor ) -{ - Int32 n; - EState* s; - - if (!bz_config_ok()) return BZ_CONFIG_ERROR; - - if (strm == NULL || - blockSize100k < 1 || blockSize100k > 9 || - workFactor < 0 || workFactor > 250) - return BZ_PARAM_ERROR; - - if (workFactor == 0) workFactor = 30; - if (strm->bzalloc == NULL) strm->bzalloc = default_bzalloc; - if (strm->bzfree == NULL) strm->bzfree = default_bzfree; - - s = BZALLOC( sizeof(EState) ); - if (s == NULL) return BZ_MEM_ERROR; - s->strm = strm; - - s->arr1 = NULL; - s->arr2 = NULL; - s->ftab = NULL; - - n = 100000 * blockSize100k; - s->arr1 = BZALLOC( n * sizeof(UInt32) ); - s->arr2 = BZALLOC( (n+BZ_N_OVERSHOOT) * sizeof(UInt32) ); - s->ftab = BZALLOC( 65537 * sizeof(UInt32) ); - - if (s->arr1 == NULL || s->arr2 == NULL || s->ftab == NULL) { - if (s->arr1 != NULL) BZFREE(s->arr1); - if (s->arr2 != NULL) BZFREE(s->arr2); - if (s->ftab != NULL) BZFREE(s->ftab); - if (s != NULL) BZFREE(s); - return BZ_MEM_ERROR; - } - - s->blockNo = 0; - s->state = BZ_S_INPUT; - s->mode = BZ_M_RUNNING; - s->combinedCRC = 0; - s->blockSize100k = blockSize100k; - s->nblockMAX = 100000 * blockSize100k - 19; - s->verbosity = verbosity; - s->workFactor = workFactor; - - s->block = (UChar*)s->arr2; - s->mtfv = (UInt16*)s->arr1; - s->zbits = NULL; - s->ptr = (UInt32*)s->arr1; - - strm->state = s; - strm->total_in_lo32 = 0; - strm->total_in_hi32 = 0; - strm->total_out_lo32 = 0; - strm->total_out_hi32 = 0; - init_RL ( s ); - prepare_new_block ( s ); - return BZ_OK; -} - - -/*---------------------------------------------------*/ -static -void add_pair_to_block ( EState* s ) -{ - Int32 i; - UChar ch = (UChar)(s->state_in_ch); - for (i = 0; i < s->state_in_len; i++) { - BZ_UPDATE_CRC( s->blockCRC, ch ); - } - s->inUse[s->state_in_ch] = True; - switch (s->state_in_len) { - case 1: - s->block[s->nblock] = (UChar)ch; s->nblock++; - break; - case 2: - s->block[s->nblock] = (UChar)ch; s->nblock++; - s->block[s->nblock] = (UChar)ch; s->nblock++; - break; - case 3: - s->block[s->nblock] = (UChar)ch; s->nblock++; - s->block[s->nblock] = (UChar)ch; s->nblock++; - s->block[s->nblock] = (UChar)ch; s->nblock++; - break; - default: - s->inUse[s->state_in_len-4] = True; - s->block[s->nblock] = (UChar)ch; s->nblock++; - s->block[s->nblock] = (UChar)ch; s->nblock++; - s->block[s->nblock] = (UChar)ch; s->nblock++; - s->block[s->nblock] = (UChar)ch; s->nblock++; - s->block[s->nblock] = ((UChar)(s->state_in_len-4)); - s->nblock++; - break; - } -} - - -/*---------------------------------------------------*/ -static -void flush_RL ( EState* s ) -{ - if (s->state_in_ch < 256) add_pair_to_block ( s ); - init_RL ( s ); -} - - -/*---------------------------------------------------*/ -#define ADD_CHAR_TO_BLOCK(zs,zchh0) \ -{ \ - UInt32 zchh = (UInt32)(zchh0); \ - /*-- fast track the common case --*/ \ - if (zchh != zs->state_in_ch && \ - zs->state_in_len == 1) { \ - UChar ch = (UChar)(zs->state_in_ch); \ - BZ_UPDATE_CRC( zs->blockCRC, ch ); \ - zs->inUse[zs->state_in_ch] = True; \ - zs->block[zs->nblock] = (UChar)ch; \ - zs->nblock++; \ - zs->state_in_ch = zchh; \ - } \ - else \ - /*-- general, uncommon cases --*/ \ - if (zchh != zs->state_in_ch || \ - zs->state_in_len == 255) { \ - if (zs->state_in_ch < 256) \ - add_pair_to_block ( zs ); \ - zs->state_in_ch = zchh; \ - zs->state_in_len = 1; \ - } else { \ - zs->state_in_len++; \ - } \ -} - - -/*---------------------------------------------------*/ -static -Bool copy_input_until_stop ( EState* s ) -{ - Bool progress_in = False; - - if (s->mode == BZ_M_RUNNING) { - - /*-- fast track the common case --*/ - while (True) { - /*-- block full? --*/ - if (s->nblock >= s->nblockMAX) break; - /*-- no input? --*/ - if (s->strm->avail_in == 0) break; - progress_in = True; - ADD_CHAR_TO_BLOCK ( s, (UInt32)(*((UChar*)(s->strm->next_in))) ); - s->strm->next_in++; - s->strm->avail_in--; - s->strm->total_in_lo32++; - if (s->strm->total_in_lo32 == 0) s->strm->total_in_hi32++; - } - - } else { - - /*-- general, uncommon case --*/ - while (True) { - /*-- block full? --*/ - if (s->nblock >= s->nblockMAX) break; - /*-- no input? --*/ - if (s->strm->avail_in == 0) break; - /*-- flush/finish end? --*/ - if (s->avail_in_expect == 0) break; - progress_in = True; - ADD_CHAR_TO_BLOCK ( s, (UInt32)(*((UChar*)(s->strm->next_in))) ); - s->strm->next_in++; - s->strm->avail_in--; - s->strm->total_in_lo32++; - if (s->strm->total_in_lo32 == 0) s->strm->total_in_hi32++; - s->avail_in_expect--; - } - } - return progress_in; -} - - -/*---------------------------------------------------*/ -static -Bool copy_output_until_stop ( EState* s ) -{ - Bool progress_out = False; - - while (True) { - - /*-- no output space? --*/ - if (s->strm->avail_out == 0) break; - - /*-- block done? --*/ - if (s->state_out_pos >= s->numZ) break; - - progress_out = True; - *(s->strm->next_out) = s->zbits[s->state_out_pos]; - s->state_out_pos++; - s->strm->avail_out--; - s->strm->next_out++; - s->strm->total_out_lo32++; - if (s->strm->total_out_lo32 == 0) s->strm->total_out_hi32++; - } - - return progress_out; -} - - -/*---------------------------------------------------*/ -static -Bool handle_compress ( bz_stream* strm ) -{ - Bool progress_in = False; - Bool progress_out = False; - EState* s = strm->state; - - while (True) { - - if (s->state == BZ_S_OUTPUT) { - progress_out |= copy_output_until_stop ( s ); - if (s->state_out_pos < s->numZ) break; - if (s->mode == BZ_M_FINISHING && - s->avail_in_expect == 0 && - isempty_RL(s)) break; - prepare_new_block ( s ); - s->state = BZ_S_INPUT; - if (s->mode == BZ_M_FLUSHING && - s->avail_in_expect == 0 && - isempty_RL(s)) break; - } - - if (s->state == BZ_S_INPUT) { - progress_in |= copy_input_until_stop ( s ); - if (s->mode != BZ_M_RUNNING && s->avail_in_expect == 0) { - flush_RL ( s ); - BZ2_compressBlock ( s, (Bool)(s->mode == BZ_M_FINISHING) ); - s->state = BZ_S_OUTPUT; - } - else - if (s->nblock >= s->nblockMAX) { - BZ2_compressBlock ( s, False ); - s->state = BZ_S_OUTPUT; - } - else - if (s->strm->avail_in == 0) { - break; - } - } - - } - - return progress_in || progress_out; -} - - -/*---------------------------------------------------*/ -int BZ_API(BZ2_bzCompress) ( bz_stream *strm, int action ) -{ - Bool progress; - EState* s; - if (strm == NULL) return BZ_PARAM_ERROR; - s = strm->state; - if (s == NULL) return BZ_PARAM_ERROR; - if (s->strm != strm) return BZ_PARAM_ERROR; - - preswitch: - switch (s->mode) { - - case BZ_M_IDLE: - return BZ_SEQUENCE_ERROR; - - case BZ_M_RUNNING: - if (action == BZ_RUN) { - progress = handle_compress ( strm ); - return progress ? BZ_RUN_OK : BZ_PARAM_ERROR; - } - else - if (action == BZ_FLUSH) { - s->avail_in_expect = strm->avail_in; - s->mode = BZ_M_FLUSHING; - goto preswitch; - } - else - if (action == BZ_FINISH) { - s->avail_in_expect = strm->avail_in; - s->mode = BZ_M_FINISHING; - goto preswitch; - } - else - return BZ_PARAM_ERROR; - - case BZ_M_FLUSHING: - if (action != BZ_FLUSH) return BZ_SEQUENCE_ERROR; - if (s->avail_in_expect != s->strm->avail_in) - return BZ_SEQUENCE_ERROR; - progress = handle_compress ( strm ); - if (s->avail_in_expect > 0 || !isempty_RL(s) || - s->state_out_pos < s->numZ) return BZ_FLUSH_OK; - s->mode = BZ_M_RUNNING; - return BZ_RUN_OK; - - case BZ_M_FINISHING: - if (action != BZ_FINISH) return BZ_SEQUENCE_ERROR; - if (s->avail_in_expect != s->strm->avail_in) - return BZ_SEQUENCE_ERROR; - progress = handle_compress ( strm ); - if (!progress) return BZ_SEQUENCE_ERROR; - if (s->avail_in_expect > 0 || !isempty_RL(s) || - s->state_out_pos < s->numZ) return BZ_FINISH_OK; - s->mode = BZ_M_IDLE; - return BZ_STREAM_END; - } - return BZ_OK; /*--not reached--*/ -} - - -/*---------------------------------------------------*/ -int BZ_API(BZ2_bzCompressEnd) ( bz_stream *strm ) -{ - EState* s; - if (strm == NULL) return BZ_PARAM_ERROR; - s = strm->state; - if (s == NULL) return BZ_PARAM_ERROR; - if (s->strm != strm) return BZ_PARAM_ERROR; - - if (s->arr1 != NULL) BZFREE(s->arr1); - if (s->arr2 != NULL) BZFREE(s->arr2); - if (s->ftab != NULL) BZFREE(s->ftab); - BZFREE(strm->state); - - strm->state = NULL; - - return BZ_OK; -} - - -/*---------------------------------------------------*/ -/*--- Decompression stuff ---*/ -/*---------------------------------------------------*/ - -/*---------------------------------------------------*/ -int BZ_API(BZ2_bzDecompressInit) - ( bz_stream* strm, - int verbosity, - int small ) -{ - DState* s; - - if (!bz_config_ok()) return BZ_CONFIG_ERROR; - - if (strm == NULL) return BZ_PARAM_ERROR; - if (small != 0 && small != 1) return BZ_PARAM_ERROR; - if (verbosity < 0 || verbosity > 4) return BZ_PARAM_ERROR; - - if (strm->bzalloc == NULL) strm->bzalloc = default_bzalloc; - if (strm->bzfree == NULL) strm->bzfree = default_bzfree; - - s = BZALLOC( sizeof(DState) ); - if (s == NULL) return BZ_MEM_ERROR; - s->strm = strm; - strm->state = s; - s->state = BZ_X_MAGIC_1; - s->bsLive = 0; - s->bsBuff = 0; - s->calculatedCombinedCRC = 0; - strm->total_in_lo32 = 0; - strm->total_in_hi32 = 0; - strm->total_out_lo32 = 0; - strm->total_out_hi32 = 0; - s->smallDecompress = (Bool)small; - s->ll4 = NULL; - s->ll16 = NULL; - s->tt = NULL; - s->currBlockNo = 0; - s->verbosity = verbosity; - - return BZ_OK; -} - - -/*---------------------------------------------------*/ -/* Return True iff data corruption is discovered. - Returns False if there is no problem. -*/ -static -Bool unRLE_obuf_to_output_FAST ( DState* s ) -{ - UChar k1; - - if (s->blockRandomised) { - - while (True) { - /* try to finish existing run */ - while (True) { - if (s->strm->avail_out == 0) return False; - if (s->state_out_len == 0) break; - *( (UChar*)(s->strm->next_out) ) = s->state_out_ch; - BZ_UPDATE_CRC ( s->calculatedBlockCRC, s->state_out_ch ); - s->state_out_len--; - s->strm->next_out++; - s->strm->avail_out--; - s->strm->total_out_lo32++; - if (s->strm->total_out_lo32 == 0) s->strm->total_out_hi32++; - } - - /* can a new run be started? */ - if (s->nblock_used == s->save_nblock+1) return False; - - /* Only caused by corrupt data stream? */ - if (s->nblock_used > s->save_nblock+1) - return True; - - s->state_out_len = 1; - s->state_out_ch = s->k0; - BZ_GET_FAST(k1); BZ_RAND_UPD_MASK; - k1 ^= BZ_RAND_MASK; s->nblock_used++; - if (s->nblock_used == s->save_nblock+1) continue; - if (k1 != s->k0) { s->k0 = k1; continue; }; - - s->state_out_len = 2; - BZ_GET_FAST(k1); BZ_RAND_UPD_MASK; - k1 ^= BZ_RAND_MASK; s->nblock_used++; - if (s->nblock_used == s->save_nblock+1) continue; - if (k1 != s->k0) { s->k0 = k1; continue; }; - - s->state_out_len = 3; - BZ_GET_FAST(k1); BZ_RAND_UPD_MASK; - k1 ^= BZ_RAND_MASK; s->nblock_used++; - if (s->nblock_used == s->save_nblock+1) continue; - if (k1 != s->k0) { s->k0 = k1; continue; }; - - BZ_GET_FAST(k1); BZ_RAND_UPD_MASK; - k1 ^= BZ_RAND_MASK; s->nblock_used++; - s->state_out_len = ((Int32)k1) + 4; - BZ_GET_FAST(s->k0); BZ_RAND_UPD_MASK; - s->k0 ^= BZ_RAND_MASK; s->nblock_used++; - } - - } else { - - /* restore */ - UInt32 c_calculatedBlockCRC = s->calculatedBlockCRC; - UChar c_state_out_ch = s->state_out_ch; - Int32 c_state_out_len = s->state_out_len; - Int32 c_nblock_used = s->nblock_used; - Int32 c_k0 = s->k0; - UInt32* c_tt = s->tt; - UInt32 c_tPos = s->tPos; - char* cs_next_out = s->strm->next_out; - unsigned int cs_avail_out = s->strm->avail_out; - Int32 ro_blockSize100k = s->blockSize100k; - /* end restore */ - - UInt32 avail_out_INIT = cs_avail_out; - Int32 s_save_nblockPP = s->save_nblock+1; - unsigned int total_out_lo32_old; - - while (True) { - - /* try to finish existing run */ - if (c_state_out_len > 0) { - while (True) { - if (cs_avail_out == 0) goto return_notr; - if (c_state_out_len == 1) break; - *( (UChar*)(cs_next_out) ) = c_state_out_ch; - BZ_UPDATE_CRC ( c_calculatedBlockCRC, c_state_out_ch ); - c_state_out_len--; - cs_next_out++; - cs_avail_out--; - } - s_state_out_len_eq_one: - { - if (cs_avail_out == 0) { - c_state_out_len = 1; goto return_notr; - }; - *( (UChar*)(cs_next_out) ) = c_state_out_ch; - BZ_UPDATE_CRC ( c_calculatedBlockCRC, c_state_out_ch ); - cs_next_out++; - cs_avail_out--; - } - } - /* Only caused by corrupt data stream? */ - if (c_nblock_used > s_save_nblockPP) - return True; - - /* can a new run be started? */ - if (c_nblock_used == s_save_nblockPP) { - c_state_out_len = 0; goto return_notr; - }; - c_state_out_ch = c_k0; - BZ_GET_FAST_C(k1); c_nblock_used++; - if (k1 != c_k0) { - c_k0 = k1; goto s_state_out_len_eq_one; - }; - if (c_nblock_used == s_save_nblockPP) - goto s_state_out_len_eq_one; - - c_state_out_len = 2; - BZ_GET_FAST_C(k1); c_nblock_used++; - if (c_nblock_used == s_save_nblockPP) continue; - if (k1 != c_k0) { c_k0 = k1; continue; }; - - c_state_out_len = 3; - BZ_GET_FAST_C(k1); c_nblock_used++; - if (c_nblock_used == s_save_nblockPP) continue; - if (k1 != c_k0) { c_k0 = k1; continue; }; - - BZ_GET_FAST_C(k1); c_nblock_used++; - c_state_out_len = ((Int32)k1) + 4; - BZ_GET_FAST_C(c_k0); c_nblock_used++; - } - - return_notr: - total_out_lo32_old = s->strm->total_out_lo32; - s->strm->total_out_lo32 += (avail_out_INIT - cs_avail_out); - if (s->strm->total_out_lo32 < total_out_lo32_old) - s->strm->total_out_hi32++; - - /* save */ - s->calculatedBlockCRC = c_calculatedBlockCRC; - s->state_out_ch = c_state_out_ch; - s->state_out_len = c_state_out_len; - s->nblock_used = c_nblock_used; - s->k0 = c_k0; - s->tt = c_tt; - s->tPos = c_tPos; - s->strm->next_out = cs_next_out; - s->strm->avail_out = cs_avail_out; - /* end save */ - } - return False; -} - - - -/*---------------------------------------------------*/ -__inline__ Int32 BZ2_indexIntoF ( Int32 indx, Int32 *cftab ) -{ - Int32 nb, na, mid; - nb = 0; - na = 256; - do { - mid = (nb + na) >> 1; - if (indx >= cftab[mid]) nb = mid; else na = mid; - } - while (na - nb != 1); - return nb; -} - - -/*---------------------------------------------------*/ -/* Return True iff data corruption is discovered. - Returns False if there is no problem. -*/ -static -Bool unRLE_obuf_to_output_SMALL ( DState* s ) -{ - UChar k1; - - if (s->blockRandomised) { - - while (True) { - /* try to finish existing run */ - while (True) { - if (s->strm->avail_out == 0) return False; - if (s->state_out_len == 0) break; - *( (UChar*)(s->strm->next_out) ) = s->state_out_ch; - BZ_UPDATE_CRC ( s->calculatedBlockCRC, s->state_out_ch ); - s->state_out_len--; - s->strm->next_out++; - s->strm->avail_out--; - s->strm->total_out_lo32++; - if (s->strm->total_out_lo32 == 0) s->strm->total_out_hi32++; - } - - /* can a new run be started? */ - if (s->nblock_used == s->save_nblock+1) return False; - - /* Only caused by corrupt data stream? */ - if (s->nblock_used > s->save_nblock+1) - return True; - - s->state_out_len = 1; - s->state_out_ch = s->k0; - BZ_GET_SMALL(k1); BZ_RAND_UPD_MASK; - k1 ^= BZ_RAND_MASK; s->nblock_used++; - if (s->nblock_used == s->save_nblock+1) continue; - if (k1 != s->k0) { s->k0 = k1; continue; }; - - s->state_out_len = 2; - BZ_GET_SMALL(k1); BZ_RAND_UPD_MASK; - k1 ^= BZ_RAND_MASK; s->nblock_used++; - if (s->nblock_used == s->save_nblock+1) continue; - if (k1 != s->k0) { s->k0 = k1; continue; }; - - s->state_out_len = 3; - BZ_GET_SMALL(k1); BZ_RAND_UPD_MASK; - k1 ^= BZ_RAND_MASK; s->nblock_used++; - if (s->nblock_used == s->save_nblock+1) continue; - if (k1 != s->k0) { s->k0 = k1; continue; }; - - BZ_GET_SMALL(k1); BZ_RAND_UPD_MASK; - k1 ^= BZ_RAND_MASK; s->nblock_used++; - s->state_out_len = ((Int32)k1) + 4; - BZ_GET_SMALL(s->k0); BZ_RAND_UPD_MASK; - s->k0 ^= BZ_RAND_MASK; s->nblock_used++; - } - - } else { - - while (True) { - /* try to finish existing run */ - while (True) { - if (s->strm->avail_out == 0) return False; - if (s->state_out_len == 0) break; - *( (UChar*)(s->strm->next_out) ) = s->state_out_ch; - BZ_UPDATE_CRC ( s->calculatedBlockCRC, s->state_out_ch ); - s->state_out_len--; - s->strm->next_out++; - s->strm->avail_out--; - s->strm->total_out_lo32++; - if (s->strm->total_out_lo32 == 0) s->strm->total_out_hi32++; - } - - /* can a new run be started? */ - if (s->nblock_used == s->save_nblock+1) return False; - - /* Only caused by corrupt data stream? */ - if (s->nblock_used > s->save_nblock+1) - return True; - - s->state_out_len = 1; - s->state_out_ch = s->k0; - BZ_GET_SMALL(k1); s->nblock_used++; - if (s->nblock_used == s->save_nblock+1) continue; - if (k1 != s->k0) { s->k0 = k1; continue; }; - - s->state_out_len = 2; - BZ_GET_SMALL(k1); s->nblock_used++; - if (s->nblock_used == s->save_nblock+1) continue; - if (k1 != s->k0) { s->k0 = k1; continue; }; - - s->state_out_len = 3; - BZ_GET_SMALL(k1); s->nblock_used++; - if (s->nblock_used == s->save_nblock+1) continue; - if (k1 != s->k0) { s->k0 = k1; continue; }; - - BZ_GET_SMALL(k1); s->nblock_used++; - s->state_out_len = ((Int32)k1) + 4; - BZ_GET_SMALL(s->k0); s->nblock_used++; - } - - } -} - - -/*---------------------------------------------------*/ -int BZ_API(BZ2_bzDecompress) ( bz_stream *strm ) -{ - Bool corrupt; - DState* s; - if (strm == NULL) return BZ_PARAM_ERROR; - s = strm->state; - if (s == NULL) return BZ_PARAM_ERROR; - if (s->strm != strm) return BZ_PARAM_ERROR; - - while (True) { - if (s->state == BZ_X_IDLE) return BZ_SEQUENCE_ERROR; - if (s->state == BZ_X_OUTPUT) { - if (s->smallDecompress) - corrupt = unRLE_obuf_to_output_SMALL ( s ); else - corrupt = unRLE_obuf_to_output_FAST ( s ); - if (corrupt) return BZ_DATA_ERROR; - if (s->nblock_used == s->save_nblock+1 && s->state_out_len == 0) { - BZ_FINALISE_CRC ( s->calculatedBlockCRC ); - if (s->verbosity >= 3) - VPrintf2 ( " {0x%08x, 0x%08x}", s->storedBlockCRC, - s->calculatedBlockCRC ); - if (s->verbosity >= 2) VPrintf0 ( "]" ); - if (s->calculatedBlockCRC != s->storedBlockCRC) - return BZ_DATA_ERROR; - s->calculatedCombinedCRC - = (s->calculatedCombinedCRC << 1) | - (s->calculatedCombinedCRC >> 31); - s->calculatedCombinedCRC ^= s->calculatedBlockCRC; - s->state = BZ_X_BLKHDR_1; - } else { - return BZ_OK; - } - } - if (s->state >= BZ_X_MAGIC_1) { - Int32 r = BZ2_decompress ( s ); - if (r == BZ_STREAM_END) { - if (s->verbosity >= 3) - VPrintf2 ( "\n combined CRCs: stored = 0x%08x, computed = 0x%08x", - s->storedCombinedCRC, s->calculatedCombinedCRC ); - if (s->calculatedCombinedCRC != s->storedCombinedCRC) - return BZ_DATA_ERROR; - return r; - } - if (s->state != BZ_X_OUTPUT) return r; - } - } - - AssertH ( 0, 6001 ); - - return 0; /*NOTREACHED*/ -} - - -/*---------------------------------------------------*/ -int BZ_API(BZ2_bzDecompressEnd) ( bz_stream *strm ) -{ - DState* s; - if (strm == NULL) return BZ_PARAM_ERROR; - s = strm->state; - if (s == NULL) return BZ_PARAM_ERROR; - if (s->strm != strm) return BZ_PARAM_ERROR; - - if (s->tt != NULL) BZFREE(s->tt); - if (s->ll16 != NULL) BZFREE(s->ll16); - if (s->ll4 != NULL) BZFREE(s->ll4); - - BZFREE(strm->state); - strm->state = NULL; - - return BZ_OK; -} - - -#ifndef BZ_NO_STDIO -/*---------------------------------------------------*/ -/*--- File I/O stuff ---*/ -/*---------------------------------------------------*/ - -#define BZ_SETERR(eee) \ -{ \ - if (bzerror != NULL) *bzerror = eee; \ - if (bzf != NULL) bzf->lastErr = eee; \ -} - -typedef - struct { - FILE* handle; - Char buf[BZ_MAX_UNUSED]; - Int32 bufN; - Bool writing; - bz_stream strm; - Int32 lastErr; - Bool initialisedOk; - } - bzFile; - - -/*---------------------------------------------*/ -static Bool myfeof ( FILE* f ) -{ - Int32 c = fgetc ( f ); - if (c == EOF) return True; - ungetc ( c, f ); - return False; -} - - -/*---------------------------------------------------*/ -BZFILE* BZ_API(BZ2_bzWriteOpen) - ( int* bzerror, - FILE* f, - int blockSize100k, - int verbosity, - int workFactor ) -{ - Int32 ret; - bzFile* bzf = NULL; - - BZ_SETERR(BZ_OK); - - if (f == NULL || - (blockSize100k < 1 || blockSize100k > 9) || - (workFactor < 0 || workFactor > 250) || - (verbosity < 0 || verbosity > 4)) - { BZ_SETERR(BZ_PARAM_ERROR); return NULL; }; - - if (ferror(f)) - { BZ_SETERR(BZ_IO_ERROR); return NULL; }; - - bzf = malloc ( sizeof(bzFile) ); - if (bzf == NULL) - { BZ_SETERR(BZ_MEM_ERROR); return NULL; }; - - BZ_SETERR(BZ_OK); - bzf->initialisedOk = False; - bzf->bufN = 0; - bzf->handle = f; - bzf->writing = True; - bzf->strm.bzalloc = NULL; - bzf->strm.bzfree = NULL; - bzf->strm.opaque = NULL; - - if (workFactor == 0) workFactor = 30; - ret = BZ2_bzCompressInit ( &(bzf->strm), blockSize100k, - verbosity, workFactor ); - if (ret != BZ_OK) - { BZ_SETERR(ret); free(bzf); return NULL; }; - - bzf->strm.avail_in = 0; - bzf->initialisedOk = True; - return bzf; -} - - - -/*---------------------------------------------------*/ -void BZ_API(BZ2_bzWrite) - ( int* bzerror, - BZFILE* b, - void* buf, - int len ) -{ - Int32 n, n2, ret; - bzFile* bzf = (bzFile*)b; - - BZ_SETERR(BZ_OK); - if (bzf == NULL || buf == NULL || len < 0) - { BZ_SETERR(BZ_PARAM_ERROR); return; }; - if (!(bzf->writing)) - { BZ_SETERR(BZ_SEQUENCE_ERROR); return; }; - if (ferror(bzf->handle)) - { BZ_SETERR(BZ_IO_ERROR); return; }; - - if (len == 0) - { BZ_SETERR(BZ_OK); return; }; - - bzf->strm.avail_in = len; - bzf->strm.next_in = buf; - - while (True) { - bzf->strm.avail_out = BZ_MAX_UNUSED; - bzf->strm.next_out = bzf->buf; - ret = BZ2_bzCompress ( &(bzf->strm), BZ_RUN ); - if (ret != BZ_RUN_OK) - { BZ_SETERR(ret); return; }; - - if (bzf->strm.avail_out < BZ_MAX_UNUSED) { - n = BZ_MAX_UNUSED - bzf->strm.avail_out; - n2 = fwrite ( (void*)(bzf->buf), sizeof(UChar), - n, bzf->handle ); - if (n != n2 || ferror(bzf->handle)) - { BZ_SETERR(BZ_IO_ERROR); return; }; - } - - if (bzf->strm.avail_in == 0) - { BZ_SETERR(BZ_OK); return; }; - } -} - - -/*---------------------------------------------------*/ -void BZ_API(BZ2_bzWriteClose) - ( int* bzerror, - BZFILE* b, - int abandon, - unsigned int* nbytes_in, - unsigned int* nbytes_out ) -{ - BZ2_bzWriteClose64 ( bzerror, b, abandon, - nbytes_in, NULL, nbytes_out, NULL ); -} - - -void BZ_API(BZ2_bzWriteClose64) - ( int* bzerror, - BZFILE* b, - int abandon, - unsigned int* nbytes_in_lo32, - unsigned int* nbytes_in_hi32, - unsigned int* nbytes_out_lo32, - unsigned int* nbytes_out_hi32 ) -{ - Int32 n, n2, ret; - bzFile* bzf = (bzFile*)b; - - if (bzf == NULL) - { BZ_SETERR(BZ_OK); return; }; - if (!(bzf->writing)) - { BZ_SETERR(BZ_SEQUENCE_ERROR); return; }; - if (ferror(bzf->handle)) - { BZ_SETERR(BZ_IO_ERROR); return; }; - - if (nbytes_in_lo32 != NULL) *nbytes_in_lo32 = 0; - if (nbytes_in_hi32 != NULL) *nbytes_in_hi32 = 0; - if (nbytes_out_lo32 != NULL) *nbytes_out_lo32 = 0; - if (nbytes_out_hi32 != NULL) *nbytes_out_hi32 = 0; - - if ((!abandon) && bzf->lastErr == BZ_OK) { - while (True) { - bzf->strm.avail_out = BZ_MAX_UNUSED; - bzf->strm.next_out = bzf->buf; - ret = BZ2_bzCompress ( &(bzf->strm), BZ_FINISH ); - if (ret != BZ_FINISH_OK && ret != BZ_STREAM_END) - { BZ_SETERR(ret); return; }; - - if (bzf->strm.avail_out < BZ_MAX_UNUSED) { - n = BZ_MAX_UNUSED - bzf->strm.avail_out; - n2 = fwrite ( (void*)(bzf->buf), sizeof(UChar), - n, bzf->handle ); - if (n != n2 || ferror(bzf->handle)) - { BZ_SETERR(BZ_IO_ERROR); return; }; - } - - if (ret == BZ_STREAM_END) break; - } - } - - if ( !abandon && !ferror ( bzf->handle ) ) { - fflush ( bzf->handle ); - if (ferror(bzf->handle)) - { BZ_SETERR(BZ_IO_ERROR); return; }; - } - - if (nbytes_in_lo32 != NULL) - *nbytes_in_lo32 = bzf->strm.total_in_lo32; - if (nbytes_in_hi32 != NULL) - *nbytes_in_hi32 = bzf->strm.total_in_hi32; - if (nbytes_out_lo32 != NULL) - *nbytes_out_lo32 = bzf->strm.total_out_lo32; - if (nbytes_out_hi32 != NULL) - *nbytes_out_hi32 = bzf->strm.total_out_hi32; - - BZ_SETERR(BZ_OK); - BZ2_bzCompressEnd ( &(bzf->strm) ); - free ( bzf ); -} - - -/*---------------------------------------------------*/ -BZFILE* BZ_API(BZ2_bzReadOpen) - ( int* bzerror, - FILE* f, - int verbosity, - int small, - void* unused, - int nUnused ) -{ - bzFile* bzf = NULL; - int ret; - - BZ_SETERR(BZ_OK); - - if (f == NULL || - (small != 0 && small != 1) || - (verbosity < 0 || verbosity > 4) || - (unused == NULL && nUnused != 0) || - (unused != NULL && (nUnused < 0 || nUnused > BZ_MAX_UNUSED))) - { BZ_SETERR(BZ_PARAM_ERROR); return NULL; }; - - if (ferror(f)) - { BZ_SETERR(BZ_IO_ERROR); return NULL; }; - - bzf = malloc ( sizeof(bzFile) ); - if (bzf == NULL) - { BZ_SETERR(BZ_MEM_ERROR); return NULL; }; - - BZ_SETERR(BZ_OK); - - bzf->initialisedOk = False; - bzf->handle = f; - bzf->bufN = 0; - bzf->writing = False; - bzf->strm.bzalloc = NULL; - bzf->strm.bzfree = NULL; - bzf->strm.opaque = NULL; - - while (nUnused > 0) { - bzf->buf[bzf->bufN] = *((UChar*)(unused)); bzf->bufN++; - unused = ((void*)( 1 + ((UChar*)(unused)) )); - nUnused--; - } - - ret = BZ2_bzDecompressInit ( &(bzf->strm), verbosity, small ); - if (ret != BZ_OK) - { BZ_SETERR(ret); free(bzf); return NULL; }; - - bzf->strm.avail_in = bzf->bufN; - bzf->strm.next_in = bzf->buf; - - bzf->initialisedOk = True; - return bzf; -} - - -/*---------------------------------------------------*/ -void BZ_API(BZ2_bzReadClose) ( int *bzerror, BZFILE *b ) -{ - bzFile* bzf = (bzFile*)b; - - BZ_SETERR(BZ_OK); - if (bzf == NULL) - { BZ_SETERR(BZ_OK); return; }; - - if (bzf->writing) - { BZ_SETERR(BZ_SEQUENCE_ERROR); return; }; - - if (bzf->initialisedOk) - (void)BZ2_bzDecompressEnd ( &(bzf->strm) ); - free ( bzf ); -} - - -/*---------------------------------------------------*/ -int BZ_API(BZ2_bzRead) - ( int* bzerror, - BZFILE* b, - void* buf, - int len ) -{ - Int32 n, ret; - bzFile* bzf = (bzFile*)b; - - BZ_SETERR(BZ_OK); - - if (bzf == NULL || buf == NULL || len < 0) - { BZ_SETERR(BZ_PARAM_ERROR); return 0; }; - - if (bzf->writing) - { BZ_SETERR(BZ_SEQUENCE_ERROR); return 0; }; - - if (len == 0) - { BZ_SETERR(BZ_OK); return 0; }; - - bzf->strm.avail_out = len; - bzf->strm.next_out = buf; - - while (True) { - - if (ferror(bzf->handle)) - { BZ_SETERR(BZ_IO_ERROR); return 0; }; - - if (bzf->strm.avail_in == 0 && !myfeof(bzf->handle)) { - n = fread ( bzf->buf, sizeof(UChar), - BZ_MAX_UNUSED, bzf->handle ); - if (ferror(bzf->handle)) - { BZ_SETERR(BZ_IO_ERROR); return 0; }; - bzf->bufN = n; - bzf->strm.avail_in = bzf->bufN; - bzf->strm.next_in = bzf->buf; - } - - ret = BZ2_bzDecompress ( &(bzf->strm) ); - - if (ret != BZ_OK && ret != BZ_STREAM_END) - { BZ_SETERR(ret); return 0; }; - - if (ret == BZ_OK && myfeof(bzf->handle) && - bzf->strm.avail_in == 0 && bzf->strm.avail_out > 0) - { BZ_SETERR(BZ_UNEXPECTED_EOF); return 0; }; - - if (ret == BZ_STREAM_END) - { BZ_SETERR(BZ_STREAM_END); - return len - bzf->strm.avail_out; }; - if (bzf->strm.avail_out == 0) - { BZ_SETERR(BZ_OK); return len; }; - - } - - return 0; /*not reached*/ -} - - -/*---------------------------------------------------*/ -void BZ_API(BZ2_bzReadGetUnused) - ( int* bzerror, - BZFILE* b, - void** unused, - int* nUnused ) -{ - bzFile* bzf = (bzFile*)b; - if (bzf == NULL) - { BZ_SETERR(BZ_PARAM_ERROR); return; }; - if (bzf->lastErr != BZ_STREAM_END) - { BZ_SETERR(BZ_SEQUENCE_ERROR); return; }; - if (unused == NULL || nUnused == NULL) - { BZ_SETERR(BZ_PARAM_ERROR); return; }; - - BZ_SETERR(BZ_OK); - *nUnused = bzf->strm.avail_in; - *unused = bzf->strm.next_in; -} -#endif - - -/*---------------------------------------------------*/ -/*--- Misc convenience stuff ---*/ -/*---------------------------------------------------*/ - -/*---------------------------------------------------*/ -int BZ_API(BZ2_bzBuffToBuffCompress) - ( char* dest, - unsigned int* destLen, - char* source, - unsigned int sourceLen, - int blockSize100k, - int verbosity, - int workFactor ) -{ - bz_stream strm; - int ret; - - if (dest == NULL || destLen == NULL || - source == NULL || - blockSize100k < 1 || blockSize100k > 9 || - verbosity < 0 || verbosity > 4 || - workFactor < 0 || workFactor > 250) - return BZ_PARAM_ERROR; - - if (workFactor == 0) workFactor = 30; - strm.bzalloc = NULL; - strm.bzfree = NULL; - strm.opaque = NULL; - ret = BZ2_bzCompressInit ( &strm, blockSize100k, - verbosity, workFactor ); - if (ret != BZ_OK) return ret; - - strm.next_in = source; - strm.next_out = dest; - strm.avail_in = sourceLen; - strm.avail_out = *destLen; - - ret = BZ2_bzCompress ( &strm, BZ_FINISH ); - if (ret == BZ_FINISH_OK) goto output_overflow; - if (ret != BZ_STREAM_END) goto errhandler; - - /* normal termination */ - *destLen -= strm.avail_out; - BZ2_bzCompressEnd ( &strm ); - return BZ_OK; - - output_overflow: - BZ2_bzCompressEnd ( &strm ); - return BZ_OUTBUFF_FULL; - - errhandler: - BZ2_bzCompressEnd ( &strm ); - return ret; -} - - -/*---------------------------------------------------*/ -int BZ_API(BZ2_bzBuffToBuffDecompress) - ( char* dest, - unsigned int* destLen, - char* source, - unsigned int sourceLen, - int small, - int verbosity ) -{ - bz_stream strm; - int ret; - - if (dest == NULL || destLen == NULL || - source == NULL || - (small != 0 && small != 1) || - verbosity < 0 || verbosity > 4) - return BZ_PARAM_ERROR; - - strm.bzalloc = NULL; - strm.bzfree = NULL; - strm.opaque = NULL; - ret = BZ2_bzDecompressInit ( &strm, verbosity, small ); - if (ret != BZ_OK) return ret; - - strm.next_in = source; - strm.next_out = dest; - strm.avail_in = sourceLen; - strm.avail_out = *destLen; - - ret = BZ2_bzDecompress ( &strm ); - if (ret == BZ_OK) goto output_overflow_or_eof; - if (ret != BZ_STREAM_END) goto errhandler; - - /* normal termination */ - *destLen -= strm.avail_out; - BZ2_bzDecompressEnd ( &strm ); - return BZ_OK; - - output_overflow_or_eof: - if (strm.avail_out > 0) { - BZ2_bzDecompressEnd ( &strm ); - return BZ_UNEXPECTED_EOF; - } else { - BZ2_bzDecompressEnd ( &strm ); - return BZ_OUTBUFF_FULL; - }; - - errhandler: - BZ2_bzDecompressEnd ( &strm ); - return ret; -} - - -/*---------------------------------------------------*/ -/*-- - Code contributed by Yoshioka Tsuneo (tsuneo@rr.iij4u.or.jp) - to support better zlib compatibility. - This code is not _officially_ part of libbzip2 (yet); - I haven't tested it, documented it, or considered the - threading-safeness of it. - If this code breaks, please contact both Yoshioka and me. ---*/ -/*---------------------------------------------------*/ - -/*---------------------------------------------------*/ -/*-- - return version like "0.9.5d, 4-Sept-1999". ---*/ -const char * BZ_API(BZ2_bzlibVersion)(void) -{ - return BZ_VERSION; -} - - -#ifndef BZ_NO_STDIO -/*---------------------------------------------------*/ - -#if defined(_WIN32) || defined(OS2) || defined(MSDOS) -# include -# include -# define SET_BINARY_MODE(file) _setmode(_fileno(file),O_BINARY) -#else -# define SET_BINARY_MODE(file) -#endif -static -BZFILE * bzopen_or_bzdopen - ( const char *path, /* no use when bzdopen */ - int fd, /* no use when bzdopen */ - const char *mode, - int open_mode) /* bzopen: 0, bzdopen:1 */ -{ - int bzerr; - char unused[BZ_MAX_UNUSED]; - int blockSize100k = 9; - int writing = 0; - char mode2[10] = ""; - FILE *fp = NULL; - BZFILE *bzfp = NULL; - int verbosity = 0; - int workFactor = 30; - int smallMode = 0; - int nUnused = 0; - - if (mode == NULL) return NULL; - while (*mode) { - switch (*mode) { - case 'r': - writing = 0; break; - case 'w': - writing = 1; break; - case 's': - smallMode = 1; break; - default: - if (isdigit((int)(*mode))) { - blockSize100k = *mode-BZ_HDR_0; - } - } - mode++; - } - strcat(mode2, writing ? "w" : "r" ); - strcat(mode2,"b"); /* binary mode */ - - if (open_mode==0) { - if (path==NULL || strcmp(path,"")==0) { - fp = (writing ? stdout : stdin); - SET_BINARY_MODE(fp); - } else { - fp = fopen(path,mode2); - } - } else { -#ifdef BZ_STRICT_ANSI - fp = NULL; -#else - fp = _fdopen(fd,mode2); -#endif - } - if (fp == NULL) return NULL; - - if (writing) { - /* Guard against total chaos and anarchy -- JRS */ - if (blockSize100k < 1) blockSize100k = 1; - if (blockSize100k > 9) blockSize100k = 9; - bzfp = BZ2_bzWriteOpen(&bzerr,fp,blockSize100k, - verbosity,workFactor); - } else { - bzfp = BZ2_bzReadOpen(&bzerr,fp,verbosity,smallMode, - unused,nUnused); - } - if (bzfp == NULL) { - if (fp != stdin && fp != stdout) fclose(fp); - return NULL; - } - return bzfp; -} - - -/*---------------------------------------------------*/ -/*-- - open file for read or write. - ex) bzopen("file","w9") - case path="" or NULL => use stdin or stdout. ---*/ -BZFILE * BZ_API(BZ2_bzopen) - ( const char *path, - const char *mode ) -{ - return bzopen_or_bzdopen(path,-1,mode,/*bzopen*/0); -} - - -/*---------------------------------------------------*/ -BZFILE * BZ_API(BZ2_bzdopen) - ( int fd, - const char *mode ) -{ - return bzopen_or_bzdopen(NULL,fd,mode,/*bzdopen*/1); -} - - -/*---------------------------------------------------*/ -int BZ_API(BZ2_bzread) (BZFILE* b, void* buf, int len ) -{ - int bzerr, nread; - if (((bzFile*)b)->lastErr == BZ_STREAM_END) return 0; - nread = BZ2_bzRead(&bzerr,b,buf,len); - if (bzerr == BZ_OK || bzerr == BZ_STREAM_END) { - return nread; - } else { - return -1; - } -} - - -/*---------------------------------------------------*/ -int BZ_API(BZ2_bzwrite) (BZFILE* b, void* buf, int len ) -{ - int bzerr; - - BZ2_bzWrite(&bzerr,b,buf,len); - if(bzerr == BZ_OK){ - return len; - }else{ - return -1; - } -} - - -/*---------------------------------------------------*/ -int BZ_API(BZ2_bzflush) (BZFILE *b) -{ - /* do nothing now... */ - return 0; -} - - -/*---------------------------------------------------*/ -void BZ_API(BZ2_bzclose) (BZFILE* b) -{ - int bzerr; - FILE *fp; - - if (b==NULL) {return;} - fp = ((bzFile *)b)->handle; - if(((bzFile*)b)->writing){ - BZ2_bzWriteClose(&bzerr,b,0,NULL,NULL); - if(bzerr != BZ_OK){ - BZ2_bzWriteClose(NULL,b,1,NULL,NULL); - } - }else{ - BZ2_bzReadClose(&bzerr,b); - } - if(fp!=stdin && fp!=stdout){ - fclose(fp); - } -} - - -/*---------------------------------------------------*/ -/*-- - return last error code ---*/ -static const char *bzerrorstrings[] = { - "OK" - ,"SEQUENCE_ERROR" - ,"PARAM_ERROR" - ,"MEM_ERROR" - ,"DATA_ERROR" - ,"DATA_ERROR_MAGIC" - ,"IO_ERROR" - ,"UNEXPECTED_EOF" - ,"OUTBUFF_FULL" - ,"CONFIG_ERROR" - ,"???" /* for future */ - ,"???" /* for future */ - ,"???" /* for future */ - ,"???" /* for future */ - ,"???" /* for future */ - ,"???" /* for future */ -}; - - -const char * BZ_API(BZ2_bzerror) (BZFILE *b, int *errnum) -{ - int err = ((bzFile *)b)->lastErr; - - if(err>0) err = 0; - *errnum = err; - return bzerrorstrings[err*-1]; -} -#endif - - -/*-------------------------------------------------------------*/ -/*--- end bzlib.c ---*/ -/*-------------------------------------------------------------*/ diff --git a/app/jni/src/libultraship/extern/StormLib/src/bzip2/bzlib.h b/app/jni/src/libultraship/extern/StormLib/src/bzip2/bzlib.h deleted file mode 100644 index c5b75d6..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/bzip2/bzlib.h +++ /dev/null @@ -1,282 +0,0 @@ - -/*-------------------------------------------------------------*/ -/*--- Public header file for the library. ---*/ -/*--- bzlib.h ---*/ -/*-------------------------------------------------------------*/ - -/* ------------------------------------------------------------------ - This file is part of bzip2/libbzip2, a program and library for - lossless, block-sorting data compression. - - bzip2/libbzip2 version 1.0.5 of 10 December 2007 - Copyright (C) 1996-2007 Julian Seward - - Please read the WARNING, DISCLAIMER and PATENTS sections in the - README file. - - This program is released under the terms of the license contained - in the file LICENSE. - ------------------------------------------------------------------ */ - - -#ifndef _BZLIB_H -#define _BZLIB_H - -#ifdef __cplusplus -extern "C" { -#endif - -#define BZ_RUN 0 -#define BZ_FLUSH 1 -#define BZ_FINISH 2 - -#define BZ_OK 0 -#define BZ_RUN_OK 1 -#define BZ_FLUSH_OK 2 -#define BZ_FINISH_OK 3 -#define BZ_STREAM_END 4 -#define BZ_SEQUENCE_ERROR (-1) -#define BZ_PARAM_ERROR (-2) -#define BZ_MEM_ERROR (-3) -#define BZ_DATA_ERROR (-4) -#define BZ_DATA_ERROR_MAGIC (-5) -#define BZ_IO_ERROR (-6) -#define BZ_UNEXPECTED_EOF (-7) -#define BZ_OUTBUFF_FULL (-8) -#define BZ_CONFIG_ERROR (-9) - -typedef - struct { - char *next_in; - unsigned int avail_in; - unsigned int total_in_lo32; - unsigned int total_in_hi32; - - char *next_out; - unsigned int avail_out; - unsigned int total_out_lo32; - unsigned int total_out_hi32; - - void *state; - - void *(*bzalloc)(void *,int,int); - void (*bzfree)(void *,void *); - void *opaque; - } - bz_stream; - - -#ifndef BZ_IMPORT -#define BZ_EXPORT -#endif - -#ifndef BZ_NO_STDIO -/* Need a definitition for FILE */ -#include -#endif - -#ifdef _WIN32 -# include -# ifdef small - /* windows.h define small to char */ -# undef small -# endif -# ifdef BZ_EXPORT -# define BZ_API(func) WINAPI func -# define BZ_EXTERN extern -# else - /* import windows dll dynamically */ -# define BZ_API(func) (WINAPI * func) -# define BZ_EXTERN -# endif -#else -# define BZ_API(func) func -# define BZ_EXTERN extern -#endif - - -/*-- Core (low-level) library functions --*/ - -BZ_EXTERN int BZ_API(BZ2_bzCompressInit) ( - bz_stream* strm, - int blockSize100k, - int verbosity, - int workFactor - ); - -BZ_EXTERN int BZ_API(BZ2_bzCompress) ( - bz_stream* strm, - int action - ); - -BZ_EXTERN int BZ_API(BZ2_bzCompressEnd) ( - bz_stream* strm - ); - -BZ_EXTERN int BZ_API(BZ2_bzDecompressInit) ( - bz_stream *strm, - int verbosity, - int small - ); - -BZ_EXTERN int BZ_API(BZ2_bzDecompress) ( - bz_stream* strm - ); - -BZ_EXTERN int BZ_API(BZ2_bzDecompressEnd) ( - bz_stream *strm - ); - - - -/*-- High(er) level library functions --*/ - -#ifndef BZ_NO_STDIO -#define BZ_MAX_UNUSED 5000 - -typedef void BZFILE; - -BZ_EXTERN BZFILE* BZ_API(BZ2_bzReadOpen) ( - int* bzerror, - FILE* f, - int verbosity, - int small, - void* unused, - int nUnused - ); - -BZ_EXTERN void BZ_API(BZ2_bzReadClose) ( - int* bzerror, - BZFILE* b - ); - -BZ_EXTERN void BZ_API(BZ2_bzReadGetUnused) ( - int* bzerror, - BZFILE* b, - void** unused, - int* nUnused - ); - -BZ_EXTERN int BZ_API(BZ2_bzRead) ( - int* bzerror, - BZFILE* b, - void* buf, - int len - ); - -BZ_EXTERN BZFILE* BZ_API(BZ2_bzWriteOpen) ( - int* bzerror, - FILE* f, - int blockSize100k, - int verbosity, - int workFactor - ); - -BZ_EXTERN void BZ_API(BZ2_bzWrite) ( - int* bzerror, - BZFILE* b, - void* buf, - int len - ); - -BZ_EXTERN void BZ_API(BZ2_bzWriteClose) ( - int* bzerror, - BZFILE* b, - int abandon, - unsigned int* nbytes_in, - unsigned int* nbytes_out - ); - -BZ_EXTERN void BZ_API(BZ2_bzWriteClose64) ( - int* bzerror, - BZFILE* b, - int abandon, - unsigned int* nbytes_in_lo32, - unsigned int* nbytes_in_hi32, - unsigned int* nbytes_out_lo32, - unsigned int* nbytes_out_hi32 - ); -#endif - - -/*-- Utility functions --*/ - -BZ_EXTERN int BZ_API(BZ2_bzBuffToBuffCompress) ( - char* dest, - unsigned int* destLen, - char* source, - unsigned int sourceLen, - int blockSize100k, - int verbosity, - int workFactor - ); - -BZ_EXTERN int BZ_API(BZ2_bzBuffToBuffDecompress) ( - char* dest, - unsigned int* destLen, - char* source, - unsigned int sourceLen, - int small, - int verbosity - ); - - -/*-- - Code contributed by Yoshioka Tsuneo (tsuneo@rr.iij4u.or.jp) - to support better zlib compatibility. - This code is not _officially_ part of libbzip2 (yet); - I haven't tested it, documented it, or considered the - threading-safeness of it. - If this code breaks, please contact both Yoshioka and me. ---*/ - -BZ_EXTERN const char * BZ_API(BZ2_bzlibVersion) ( - void - ); - -#ifndef BZ_NO_STDIO -BZ_EXTERN BZFILE * BZ_API(BZ2_bzopen) ( - const char *path, - const char *mode - ); - -BZ_EXTERN BZFILE * BZ_API(BZ2_bzdopen) ( - int fd, - const char *mode - ); - -BZ_EXTERN int BZ_API(BZ2_bzread) ( - BZFILE* b, - void* buf, - int len - ); - -BZ_EXTERN int BZ_API(BZ2_bzwrite) ( - BZFILE* b, - void* buf, - int len - ); - -BZ_EXTERN int BZ_API(BZ2_bzflush) ( - BZFILE* b - ); - -BZ_EXTERN void BZ_API(BZ2_bzclose) ( - BZFILE* b - ); - -BZ_EXTERN const char * BZ_API(BZ2_bzerror) ( - BZFILE *b, - int *errnum - ); -#endif - -#ifdef __cplusplus -} -#endif - -#endif - -/*-------------------------------------------------------------*/ -/*--- end bzlib.h ---*/ -/*-------------------------------------------------------------*/ diff --git a/app/jni/src/libultraship/extern/StormLib/src/bzip2/bzlib_private.h b/app/jni/src/libultraship/extern/StormLib/src/bzip2/bzlib_private.h deleted file mode 100644 index 2342787..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/bzip2/bzlib_private.h +++ /dev/null @@ -1,509 +0,0 @@ - -/*-------------------------------------------------------------*/ -/*--- Private header file for the library. ---*/ -/*--- bzlib_private.h ---*/ -/*-------------------------------------------------------------*/ - -/* ------------------------------------------------------------------ - This file is part of bzip2/libbzip2, a program and library for - lossless, block-sorting data compression. - - bzip2/libbzip2 version 1.0.5 of 10 December 2007 - Copyright (C) 1996-2007 Julian Seward - - Please read the WARNING, DISCLAIMER and PATENTS sections in the - README file. - - This program is released under the terms of the license contained - in the file LICENSE. - ------------------------------------------------------------------ */ - - -#ifndef _BZLIB_PRIVATE_H -#define _BZLIB_PRIVATE_H - -#include - -#ifndef BZ_NO_STDIO -#include -#include -#include -#endif - -#include "bzlib.h" - - - -/*-- General stuff. --*/ - -#define BZ_VERSION "1.0.5, 10-Dec-2007" - -typedef char Char; -typedef unsigned char Bool; -typedef unsigned char UChar; -typedef int Int32; -typedef unsigned int UInt32; -typedef short Int16; -typedef unsigned short UInt16; - -#define True ((Bool)1) -#define False ((Bool)0) - -#ifndef __GNUC__ -#define __inline__ /* */ -#endif - -#ifndef BZ_NO_STDIO - -extern void BZ2_bz__AssertH__fail ( int errcode ); -#define AssertH(cond,errcode) \ - { if (!(cond)) BZ2_bz__AssertH__fail ( errcode ); } - -#if BZ_DEBUG -#define AssertD(cond,msg) \ - { if (!(cond)) { \ - fprintf ( stderr, \ - "\n\nlibbzip2(debug build): internal error\n\t%s\n", msg );\ - exit(1); \ - }} -#else -#define AssertD(cond,msg) /* */ -#endif - -#define VPrintf0(zf) \ - fprintf(stderr,zf) -#define VPrintf1(zf,za1) \ - fprintf(stderr,zf,za1) -#define VPrintf2(zf,za1,za2) \ - fprintf(stderr,zf,za1,za2) -#define VPrintf3(zf,za1,za2,za3) \ - fprintf(stderr,zf,za1,za2,za3) -#define VPrintf4(zf,za1,za2,za3,za4) \ - fprintf(stderr,zf,za1,za2,za3,za4) -#define VPrintf5(zf,za1,za2,za3,za4,za5) \ - fprintf(stderr,zf,za1,za2,za3,za4,za5) - -#else - -extern void bz_internal_error ( int errcode ); -#define AssertH(cond,errcode) \ - { if (!(cond)) bz_internal_error ( errcode ); } -#define AssertD(cond,msg) do { } while (0) -#define VPrintf0(zf) do { } while (0) -#define VPrintf1(zf,za1) do { } while (0) -#define VPrintf2(zf,za1,za2) do { } while (0) -#define VPrintf3(zf,za1,za2,za3) do { } while (0) -#define VPrintf4(zf,za1,za2,za3,za4) do { } while (0) -#define VPrintf5(zf,za1,za2,za3,za4,za5) do { } while (0) - -#endif - - -#define BZALLOC(nnn) (strm->bzalloc)(strm->opaque,(nnn),1) -#define BZFREE(ppp) (strm->bzfree)(strm->opaque,(ppp)) - - -/*-- Header bytes. --*/ - -#define BZ_HDR_B 0x42 /* 'B' */ -#define BZ_HDR_Z 0x5a /* 'Z' */ -#define BZ_HDR_h 0x68 /* 'h' */ -#define BZ_HDR_0 0x30 /* '0' */ - -/*-- Constants for the back end. --*/ - -#define BZ_MAX_ALPHA_SIZE 258 -#define BZ_MAX_CODE_LEN 23 - -#define BZ_RUNA 0 -#define BZ_RUNB 1 - -#define BZ_N_GROUPS 6 -#define BZ_G_SIZE 50 -#define BZ_N_ITERS 4 - -#define BZ_MAX_SELECTORS (2 + (900000 / BZ_G_SIZE)) - - - -/*-- Stuff for randomising repetitive blocks. --*/ - -extern Int32 BZ2_rNums[512]; - -#define BZ_RAND_DECLS \ - Int32 rNToGo; \ - Int32 rTPos \ - -#define BZ_RAND_INIT_MASK \ - s->rNToGo = 0; \ - s->rTPos = 0 \ - -#define BZ_RAND_MASK ((s->rNToGo == 1) ? 1 : 0) - -#define BZ_RAND_UPD_MASK \ - if (s->rNToGo == 0) { \ - s->rNToGo = BZ2_rNums[s->rTPos]; \ - s->rTPos++; \ - if (s->rTPos == 512) s->rTPos = 0; \ - } \ - s->rNToGo--; - - - -/*-- Stuff for doing CRCs. --*/ - -extern UInt32 BZ2_crc32Table[256]; - -#define BZ_INITIALISE_CRC(crcVar) \ -{ \ - crcVar = 0xffffffffL; \ -} - -#define BZ_FINALISE_CRC(crcVar) \ -{ \ - crcVar = ~(crcVar); \ -} - -#define BZ_UPDATE_CRC(crcVar,cha) \ -{ \ - crcVar = (crcVar << 8) ^ \ - BZ2_crc32Table[(crcVar >> 24) ^ \ - ((UChar)cha)]; \ -} - - - -/*-- States and modes for compression. --*/ - -#define BZ_M_IDLE 1 -#define BZ_M_RUNNING 2 -#define BZ_M_FLUSHING 3 -#define BZ_M_FINISHING 4 - -#define BZ_S_OUTPUT 1 -#define BZ_S_INPUT 2 - -#define BZ_N_RADIX 2 -#define BZ_N_QSORT 12 -#define BZ_N_SHELL 18 -#define BZ_N_OVERSHOOT (BZ_N_RADIX + BZ_N_QSORT + BZ_N_SHELL + 2) - - - - -/*-- Structure holding all the compression-side stuff. --*/ - -typedef - struct { - /* pointer back to the struct bz_stream */ - bz_stream* strm; - - /* mode this stream is in, and whether inputting */ - /* or outputting data */ - Int32 mode; - Int32 state; - - /* remembers avail_in when flush/finish requested */ - UInt32 avail_in_expect; - - /* for doing the block sorting */ - UInt32* arr1; - UInt32* arr2; - UInt32* ftab; - Int32 origPtr; - - /* aliases for arr1 and arr2 */ - UInt32* ptr; - UChar* block; - UInt16* mtfv; - UChar* zbits; - - /* for deciding when to use the fallback sorting algorithm */ - Int32 workFactor; - - /* run-length-encoding of the input */ - UInt32 state_in_ch; - Int32 state_in_len; - BZ_RAND_DECLS; - - /* input and output limits and current posns */ - Int32 nblock; - Int32 nblockMAX; - Int32 numZ; - Int32 state_out_pos; - - /* map of bytes used in block */ - Int32 nInUse; - Bool inUse[256]; - UChar unseqToSeq[256]; - - /* the buffer for bit stream creation */ - UInt32 bsBuff; - Int32 bsLive; - - /* block and combined CRCs */ - UInt32 blockCRC; - UInt32 combinedCRC; - - /* misc administratium */ - Int32 verbosity; - Int32 blockNo; - Int32 blockSize100k; - - /* stuff for coding the MTF values */ - Int32 nMTF; - Int32 mtfFreq [BZ_MAX_ALPHA_SIZE]; - UChar selector [BZ_MAX_SELECTORS]; - UChar selectorMtf[BZ_MAX_SELECTORS]; - - UChar len [BZ_N_GROUPS][BZ_MAX_ALPHA_SIZE]; - Int32 code [BZ_N_GROUPS][BZ_MAX_ALPHA_SIZE]; - Int32 rfreq [BZ_N_GROUPS][BZ_MAX_ALPHA_SIZE]; - /* second dimension: only 3 needed; 4 makes index calculations faster */ - UInt32 len_pack[BZ_MAX_ALPHA_SIZE][4]; - - } - EState; - - - -/*-- externs for compression. --*/ - -extern void -BZ2_blockSort ( EState* ); - -extern void -BZ2_compressBlock ( EState*, Bool ); - -extern void -BZ2_bsInitWrite ( EState* ); - -extern void -BZ2_hbAssignCodes ( Int32*, UChar*, Int32, Int32, Int32 ); - -extern void -BZ2_hbMakeCodeLengths ( UChar*, Int32*, Int32, Int32 ); - - - -/*-- states for decompression. --*/ - -#define BZ_X_IDLE 1 -#define BZ_X_OUTPUT 2 - -#define BZ_X_MAGIC_1 10 -#define BZ_X_MAGIC_2 11 -#define BZ_X_MAGIC_3 12 -#define BZ_X_MAGIC_4 13 -#define BZ_X_BLKHDR_1 14 -#define BZ_X_BLKHDR_2 15 -#define BZ_X_BLKHDR_3 16 -#define BZ_X_BLKHDR_4 17 -#define BZ_X_BLKHDR_5 18 -#define BZ_X_BLKHDR_6 19 -#define BZ_X_BCRC_1 20 -#define BZ_X_BCRC_2 21 -#define BZ_X_BCRC_3 22 -#define BZ_X_BCRC_4 23 -#define BZ_X_RANDBIT 24 -#define BZ_X_ORIGPTR_1 25 -#define BZ_X_ORIGPTR_2 26 -#define BZ_X_ORIGPTR_3 27 -#define BZ_X_MAPPING_1 28 -#define BZ_X_MAPPING_2 29 -#define BZ_X_SELECTOR_1 30 -#define BZ_X_SELECTOR_2 31 -#define BZ_X_SELECTOR_3 32 -#define BZ_X_CODING_1 33 -#define BZ_X_CODING_2 34 -#define BZ_X_CODING_3 35 -#define BZ_X_MTF_1 36 -#define BZ_X_MTF_2 37 -#define BZ_X_MTF_3 38 -#define BZ_X_MTF_4 39 -#define BZ_X_MTF_5 40 -#define BZ_X_MTF_6 41 -#define BZ_X_ENDHDR_2 42 -#define BZ_X_ENDHDR_3 43 -#define BZ_X_ENDHDR_4 44 -#define BZ_X_ENDHDR_5 45 -#define BZ_X_ENDHDR_6 46 -#define BZ_X_CCRC_1 47 -#define BZ_X_CCRC_2 48 -#define BZ_X_CCRC_3 49 -#define BZ_X_CCRC_4 50 - - - -/*-- Constants for the fast MTF decoder. --*/ - -#define MTFA_SIZE 4096 -#define MTFL_SIZE 16 - - - -/*-- Structure holding all the decompression-side stuff. --*/ - -typedef - struct { - /* pointer back to the struct bz_stream */ - bz_stream* strm; - - /* state indicator for this stream */ - Int32 state; - - /* for doing the final run-length decoding */ - UChar state_out_ch; - Int32 state_out_len; - Bool blockRandomised; - BZ_RAND_DECLS; - - /* the buffer for bit stream reading */ - UInt32 bsBuff; - Int32 bsLive; - - /* misc administratium */ - Int32 blockSize100k; - Bool smallDecompress; - Int32 currBlockNo; - Int32 verbosity; - - /* for undoing the Burrows-Wheeler transform */ - Int32 origPtr; - UInt32 tPos; - Int32 k0; - Int32 unzftab[256]; - Int32 nblock_used; - Int32 cftab[257]; - Int32 cftabCopy[257]; - - /* for undoing the Burrows-Wheeler transform (FAST) */ - UInt32 *tt; - - /* for undoing the Burrows-Wheeler transform (SMALL) */ - UInt16 *ll16; - UChar *ll4; - - /* stored and calculated CRCs */ - UInt32 storedBlockCRC; - UInt32 storedCombinedCRC; - UInt32 calculatedBlockCRC; - UInt32 calculatedCombinedCRC; - - /* map of bytes used in block */ - Int32 nInUse; - Bool inUse[256]; - Bool inUse16[16]; - UChar seqToUnseq[256]; - - /* for decoding the MTF values */ - UChar mtfa [MTFA_SIZE]; - Int32 mtfbase[256 / MTFL_SIZE]; - UChar selector [BZ_MAX_SELECTORS]; - UChar selectorMtf[BZ_MAX_SELECTORS]; - UChar len [BZ_N_GROUPS][BZ_MAX_ALPHA_SIZE]; - - Int32 limit [BZ_N_GROUPS][BZ_MAX_ALPHA_SIZE]; - Int32 base [BZ_N_GROUPS][BZ_MAX_ALPHA_SIZE]; - Int32 perm [BZ_N_GROUPS][BZ_MAX_ALPHA_SIZE]; - Int32 minLens[BZ_N_GROUPS]; - - /* save area for scalars in the main decompress code */ - Int32 save_i; - Int32 save_j; - Int32 save_t; - Int32 save_alphaSize; - Int32 save_nGroups; - Int32 save_nSelectors; - Int32 save_EOB; - Int32 save_groupNo; - Int32 save_groupPos; - Int32 save_nextSym; - Int32 save_nblockMAX; - Int32 save_nblock; - Int32 save_es; - Int32 save_N; - Int32 save_curr; - Int32 save_zt; - Int32 save_zn; - Int32 save_zvec; - Int32 save_zj; - Int32 save_gSel; - Int32 save_gMinlen; - Int32* save_gLimit; - Int32* save_gBase; - Int32* save_gPerm; - - } - DState; - - - -/*-- Macros for decompression. --*/ - -#define BZ_GET_FAST(cccc) \ - /* c_tPos is unsigned, hence test < 0 is pointless. */ \ - if (s->tPos >= (UInt32)100000 * (UInt32)s->blockSize100k) return True; \ - s->tPos = s->tt[s->tPos]; \ - cccc = (UChar)(s->tPos & 0xff); \ - s->tPos >>= 8; - -#define BZ_GET_FAST_C(cccc) \ - /* c_tPos is unsigned, hence test < 0 is pointless. */ \ - if (c_tPos >= (UInt32)100000 * (UInt32)ro_blockSize100k) return True; \ - c_tPos = c_tt[c_tPos]; \ - cccc = (UChar)(c_tPos & 0xff); \ - c_tPos >>= 8; - -#define SET_LL4(i,n) \ - { if (((i) & 0x1) == 0) \ - s->ll4[(i) >> 1] = (s->ll4[(i) >> 1] & 0xf0) | (n); else \ - s->ll4[(i) >> 1] = (s->ll4[(i) >> 1] & 0x0f) | ((n) << 4); \ - } - -#define GET_LL4(i) \ - ((((UInt32)(s->ll4[(i) >> 1])) >> (((i) << 2) & 0x4)) & 0xF) - -#define SET_LL(i,n) \ - { s->ll16[i] = (UInt16)(n & 0x0000ffff); \ - SET_LL4(i, n >> 16); \ - } - -#define GET_LL(i) \ - (((UInt32)s->ll16[i]) | (GET_LL4(i) << 16)) - -#define BZ_GET_SMALL(cccc) \ - /* c_tPos is unsigned, hence test < 0 is pointless. */ \ - if (s->tPos >= (UInt32)100000 * (UInt32)s->blockSize100k) return True; \ - cccc = BZ2_indexIntoF ( s->tPos, s->cftab ); \ - s->tPos = GET_LL(s->tPos); - - -/*-- externs for decompression. --*/ - -extern Int32 -BZ2_indexIntoF ( Int32, Int32* ); - -extern Int32 -BZ2_decompress ( DState* ); - -extern void -BZ2_hbCreateDecodeTables ( Int32*, Int32*, Int32*, UChar*, - Int32, Int32, Int32 ); - - -#endif - - -/*-- BZ_NO_STDIO seems to make NULL disappear on some platforms. --*/ - -#ifdef BZ_NO_STDIO -#ifndef NULL -#define NULL 0 -#endif -#endif - - -/*-------------------------------------------------------------*/ -/*--- end bzlib_private.h ---*/ -/*-------------------------------------------------------------*/ diff --git a/app/jni/src/libultraship/extern/StormLib/src/bzip2/compress.c b/app/jni/src/libultraship/extern/StormLib/src/bzip2/compress.c deleted file mode 100644 index 8c80a07..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/bzip2/compress.c +++ /dev/null @@ -1,672 +0,0 @@ - -/*-------------------------------------------------------------*/ -/*--- Compression machinery (not incl block sorting) ---*/ -/*--- compress.c ---*/ -/*-------------------------------------------------------------*/ - -/* ------------------------------------------------------------------ - This file is part of bzip2/libbzip2, a program and library for - lossless, block-sorting data compression. - - bzip2/libbzip2 version 1.0.5 of 10 December 2007 - Copyright (C) 1996-2007 Julian Seward - - Please read the WARNING, DISCLAIMER and PATENTS sections in the - README file. - - This program is released under the terms of the license contained - in the file LICENSE. - ------------------------------------------------------------------ */ - - -/* CHANGES - 0.9.0 -- original version. - 0.9.0a/b -- no changes in this file. - 0.9.0c -- changed setting of nGroups in sendMTFValues() - so as to do a bit better on small files -*/ - -#include "bzlib_private.h" - - -/*---------------------------------------------------*/ -/*--- Bit stream I/O ---*/ -/*---------------------------------------------------*/ - -/*---------------------------------------------------*/ -void BZ2_bsInitWrite ( EState* s ) -{ - s->bsLive = 0; - s->bsBuff = 0; -} - - -/*---------------------------------------------------*/ -static -void bsFinishWrite ( EState* s ) -{ - while (s->bsLive > 0) { - s->zbits[s->numZ] = (UChar)(s->bsBuff >> 24); - s->numZ++; - s->bsBuff <<= 8; - s->bsLive -= 8; - } -} - - -/*---------------------------------------------------*/ -#define bsNEEDW(nz) \ -{ \ - while (s->bsLive >= 8) { \ - s->zbits[s->numZ] \ - = (UChar)(s->bsBuff >> 24); \ - s->numZ++; \ - s->bsBuff <<= 8; \ - s->bsLive -= 8; \ - } \ -} - - -/*---------------------------------------------------*/ -static -__inline__ -void bsW ( EState* s, Int32 n, UInt32 v ) -{ - bsNEEDW ( n ); - s->bsBuff |= (v << (32 - s->bsLive - n)); - s->bsLive += n; -} - - -/*---------------------------------------------------*/ -static -void bsPutUInt32 ( EState* s, UInt32 u ) -{ - bsW ( s, 8, (u >> 24) & 0xffL ); - bsW ( s, 8, (u >> 16) & 0xffL ); - bsW ( s, 8, (u >> 8) & 0xffL ); - bsW ( s, 8, u & 0xffL ); -} - - -/*---------------------------------------------------*/ -static -void bsPutUChar ( EState* s, UChar c ) -{ - bsW( s, 8, (UInt32)c ); -} - - -/*---------------------------------------------------*/ -/*--- The back end proper ---*/ -/*---------------------------------------------------*/ - -/*---------------------------------------------------*/ -static -void makeMaps_e ( EState* s ) -{ - Int32 i; - s->nInUse = 0; - for (i = 0; i < 256; i++) - if (s->inUse[i]) { - s->unseqToSeq[i] = s->nInUse; - s->nInUse++; - } -} - - -/*---------------------------------------------------*/ -static -void generateMTFValues ( EState* s ) -{ - UChar yy[256]; - Int32 i, j; - Int32 zPend; - Int32 wr; - Int32 EOB; - - /* - After sorting (eg, here), - s->arr1 [ 0 .. s->nblock-1 ] holds sorted order, - and - ((UChar*)s->arr2) [ 0 .. s->nblock-1 ] - holds the original block data. - - The first thing to do is generate the MTF values, - and put them in - ((UInt16*)s->arr1) [ 0 .. s->nblock-1 ]. - Because there are strictly fewer or equal MTF values - than block values, ptr values in this area are overwritten - with MTF values only when they are no longer needed. - - The final compressed bitstream is generated into the - area starting at - (UChar*) (&((UChar*)s->arr2)[s->nblock]) - - These storage aliases are set up in bzCompressInit(), - except for the last one, which is arranged in - compressBlock(). - */ - UInt32* ptr = s->ptr; - UChar* block = s->block; - UInt16* mtfv = s->mtfv; - - makeMaps_e ( s ); - EOB = s->nInUse+1; - - for (i = 0; i <= EOB; i++) s->mtfFreq[i] = 0; - - wr = 0; - zPend = 0; - for (i = 0; i < s->nInUse; i++) yy[i] = (UChar) i; - - for (i = 0; i < s->nblock; i++) { - UChar ll_i; - AssertD ( wr <= i, "generateMTFValues(1)" ); - j = ptr[i]-1; if (j < 0) j += s->nblock; - ll_i = s->unseqToSeq[block[j]]; - AssertD ( ll_i < s->nInUse, "generateMTFValues(2a)" ); - - if (yy[0] == ll_i) { - zPend++; - } else { - - if (zPend > 0) { - zPend--; - while (True) { - if (zPend & 1) { - mtfv[wr] = BZ_RUNB; wr++; - s->mtfFreq[BZ_RUNB]++; - } else { - mtfv[wr] = BZ_RUNA; wr++; - s->mtfFreq[BZ_RUNA]++; - } - if (zPend < 2) break; - zPend = (zPend - 2) / 2; - }; - zPend = 0; - } - { - register UChar rtmp; - register UChar* ryy_j; - register UChar rll_i; - rtmp = yy[1]; - yy[1] = yy[0]; - ryy_j = &(yy[1]); - rll_i = ll_i; - while ( rll_i != rtmp ) { - register UChar rtmp2; - ryy_j++; - rtmp2 = rtmp; - rtmp = *ryy_j; - *ryy_j = rtmp2; - }; - yy[0] = rtmp; - j = ryy_j - &(yy[0]); - mtfv[wr] = j+1; wr++; s->mtfFreq[j+1]++; - } - - } - } - - if (zPend > 0) { - zPend--; - while (True) { - if (zPend & 1) { - mtfv[wr] = BZ_RUNB; wr++; - s->mtfFreq[BZ_RUNB]++; - } else { - mtfv[wr] = BZ_RUNA; wr++; - s->mtfFreq[BZ_RUNA]++; - } - if (zPend < 2) break; - zPend = (zPend - 2) / 2; - }; - zPend = 0; - } - - mtfv[wr] = EOB; wr++; s->mtfFreq[EOB]++; - - s->nMTF = wr; -} - - -/*---------------------------------------------------*/ -#define BZ_LESSER_ICOST 0 -#define BZ_GREATER_ICOST 15 - -static -void sendMTFValues ( EState* s ) -{ - Int32 v, t, i, j, gs, ge, totc, bt, bc, iter; - Int32 nSelectors, alphaSize, minLen, maxLen, selCtr; - Int32 nGroups, nBytes; - - /*-- - UChar len [BZ_N_GROUPS][BZ_MAX_ALPHA_SIZE]; - is a global since the decoder also needs it. - - Int32 code[BZ_N_GROUPS][BZ_MAX_ALPHA_SIZE]; - Int32 rfreq[BZ_N_GROUPS][BZ_MAX_ALPHA_SIZE]; - are also globals only used in this proc. - Made global to keep stack frame size small. - --*/ - - - UInt16 cost[BZ_N_GROUPS]; - Int32 fave[BZ_N_GROUPS]; - - UInt16* mtfv = s->mtfv; - - if (s->verbosity >= 3) - VPrintf3( " %d in block, %d after MTF & 1-2 coding, " - "%d+2 syms in use\n", - s->nblock, s->nMTF, s->nInUse ); - - alphaSize = s->nInUse+2; - for (t = 0; t < BZ_N_GROUPS; t++) - for (v = 0; v < alphaSize; v++) - s->len[t][v] = BZ_GREATER_ICOST; - - /*--- Decide how many coding tables to use ---*/ - AssertH ( s->nMTF > 0, 3001 ); - if (s->nMTF < 200) nGroups = 2; else - if (s->nMTF < 600) nGroups = 3; else - if (s->nMTF < 1200) nGroups = 4; else - if (s->nMTF < 2400) nGroups = 5; else - nGroups = 6; - - /*--- Generate an initial set of coding tables ---*/ - { - Int32 nPart, remF, tFreq, aFreq; - - nPart = nGroups; - remF = s->nMTF; - gs = 0; - while (nPart > 0) { - tFreq = remF / nPart; - ge = gs-1; - aFreq = 0; - while (aFreq < tFreq && ge < alphaSize-1) { - ge++; - aFreq += s->mtfFreq[ge]; - } - - if (ge > gs - && nPart != nGroups && nPart != 1 - && ((nGroups-nPart) % 2 == 1)) { - aFreq -= s->mtfFreq[ge]; - ge--; - } - - if (s->verbosity >= 3) - VPrintf5( " initial group %d, [%d .. %d], " - "has %d syms (%4.1f%%)\n", - nPart, gs, ge, aFreq, - (100.0 * (float)aFreq) / (float)(s->nMTF) ); - - for (v = 0; v < alphaSize; v++) - if (v >= gs && v <= ge) - s->len[nPart-1][v] = BZ_LESSER_ICOST; else - s->len[nPart-1][v] = BZ_GREATER_ICOST; - - nPart--; - gs = ge+1; - remF -= aFreq; - } - } - - /*--- - Iterate up to BZ_N_ITERS times to improve the tables. - ---*/ - for (iter = 0; iter < BZ_N_ITERS; iter++) { - - for (t = 0; t < nGroups; t++) fave[t] = 0; - - for (t = 0; t < nGroups; t++) - for (v = 0; v < alphaSize; v++) - s->rfreq[t][v] = 0; - - /*--- - Set up an auxiliary length table which is used to fast-track - the common case (nGroups == 6). - ---*/ - if (nGroups == 6) { - for (v = 0; v < alphaSize; v++) { - s->len_pack[v][0] = (s->len[1][v] << 16) | s->len[0][v]; - s->len_pack[v][1] = (s->len[3][v] << 16) | s->len[2][v]; - s->len_pack[v][2] = (s->len[5][v] << 16) | s->len[4][v]; - } - } - - nSelectors = 0; - totc = 0; - gs = 0; - while (True) { - - /*--- Set group start & end marks. --*/ - if (gs >= s->nMTF) break; - ge = gs + BZ_G_SIZE - 1; - if (ge >= s->nMTF) ge = s->nMTF-1; - - /*-- - Calculate the cost of this group as coded - by each of the coding tables. - --*/ - for (t = 0; t < nGroups; t++) cost[t] = 0; - - if (nGroups == 6 && 50 == ge-gs+1) { - /*--- fast track the common case ---*/ - register UInt32 cost01, cost23, cost45; - register UInt16 icv; - cost01 = cost23 = cost45 = 0; - -# define BZ_ITER(nn) \ - icv = mtfv[gs+(nn)]; \ - cost01 += s->len_pack[icv][0]; \ - cost23 += s->len_pack[icv][1]; \ - cost45 += s->len_pack[icv][2]; \ - - BZ_ITER(0); BZ_ITER(1); BZ_ITER(2); BZ_ITER(3); BZ_ITER(4); - BZ_ITER(5); BZ_ITER(6); BZ_ITER(7); BZ_ITER(8); BZ_ITER(9); - BZ_ITER(10); BZ_ITER(11); BZ_ITER(12); BZ_ITER(13); BZ_ITER(14); - BZ_ITER(15); BZ_ITER(16); BZ_ITER(17); BZ_ITER(18); BZ_ITER(19); - BZ_ITER(20); BZ_ITER(21); BZ_ITER(22); BZ_ITER(23); BZ_ITER(24); - BZ_ITER(25); BZ_ITER(26); BZ_ITER(27); BZ_ITER(28); BZ_ITER(29); - BZ_ITER(30); BZ_ITER(31); BZ_ITER(32); BZ_ITER(33); BZ_ITER(34); - BZ_ITER(35); BZ_ITER(36); BZ_ITER(37); BZ_ITER(38); BZ_ITER(39); - BZ_ITER(40); BZ_ITER(41); BZ_ITER(42); BZ_ITER(43); BZ_ITER(44); - BZ_ITER(45); BZ_ITER(46); BZ_ITER(47); BZ_ITER(48); BZ_ITER(49); - -# undef BZ_ITER - - cost[0] = cost01 & 0xffff; cost[1] = cost01 >> 16; - cost[2] = cost23 & 0xffff; cost[3] = cost23 >> 16; - cost[4] = cost45 & 0xffff; cost[5] = cost45 >> 16; - - } else { - /*--- slow version which correctly handles all situations ---*/ - for (i = gs; i <= ge; i++) { - UInt16 icv = mtfv[i]; - for (t = 0; t < nGroups; t++) cost[t] += s->len[t][icv]; - } - } - - /*-- - Find the coding table which is best for this group, - and record its identity in the selector table. - --*/ - bc = 999999999; bt = -1; - for (t = 0; t < nGroups; t++) - if (cost[t] < bc) { bc = cost[t]; bt = t; }; - totc += bc; - fave[bt]++; - s->selector[nSelectors] = bt; - nSelectors++; - - /*-- - Increment the symbol frequencies for the selected table. - --*/ - if (nGroups == 6 && 50 == ge-gs+1) { - /*--- fast track the common case ---*/ - -# define BZ_ITUR(nn) s->rfreq[bt][ mtfv[gs+(nn)] ]++ - - BZ_ITUR(0); BZ_ITUR(1); BZ_ITUR(2); BZ_ITUR(3); BZ_ITUR(4); - BZ_ITUR(5); BZ_ITUR(6); BZ_ITUR(7); BZ_ITUR(8); BZ_ITUR(9); - BZ_ITUR(10); BZ_ITUR(11); BZ_ITUR(12); BZ_ITUR(13); BZ_ITUR(14); - BZ_ITUR(15); BZ_ITUR(16); BZ_ITUR(17); BZ_ITUR(18); BZ_ITUR(19); - BZ_ITUR(20); BZ_ITUR(21); BZ_ITUR(22); BZ_ITUR(23); BZ_ITUR(24); - BZ_ITUR(25); BZ_ITUR(26); BZ_ITUR(27); BZ_ITUR(28); BZ_ITUR(29); - BZ_ITUR(30); BZ_ITUR(31); BZ_ITUR(32); BZ_ITUR(33); BZ_ITUR(34); - BZ_ITUR(35); BZ_ITUR(36); BZ_ITUR(37); BZ_ITUR(38); BZ_ITUR(39); - BZ_ITUR(40); BZ_ITUR(41); BZ_ITUR(42); BZ_ITUR(43); BZ_ITUR(44); - BZ_ITUR(45); BZ_ITUR(46); BZ_ITUR(47); BZ_ITUR(48); BZ_ITUR(49); - -# undef BZ_ITUR - - } else { - /*--- slow version which correctly handles all situations ---*/ - for (i = gs; i <= ge; i++) - s->rfreq[bt][ mtfv[i] ]++; - } - - gs = ge+1; - } - if (s->verbosity >= 3) { - VPrintf2 ( " pass %d: size is %d, grp uses are ", - iter+1, totc/8 ); - for (t = 0; t < nGroups; t++) - VPrintf1 ( "%d ", fave[t] ); - VPrintf0 ( "\n" ); - } - - /*-- - Recompute the tables based on the accumulated frequencies. - --*/ - /* maxLen was changed from 20 to 17 in bzip2-1.0.3. See - comment in huffman.c for details. */ - for (t = 0; t < nGroups; t++) - BZ2_hbMakeCodeLengths ( &(s->len[t][0]), &(s->rfreq[t][0]), - alphaSize, 17 /*20*/ ); - } - - - AssertH( nGroups < 8, 3002 ); - AssertH( nSelectors < 32768 && - nSelectors <= (2 + (900000 / BZ_G_SIZE)), - 3003 ); - - - /*--- Compute MTF values for the selectors. ---*/ - { - UChar pos[BZ_N_GROUPS], ll_i, tmp2, tmp; - for (i = 0; i < nGroups; i++) pos[i] = i; - for (i = 0; i < nSelectors; i++) { - ll_i = s->selector[i]; - j = 0; - tmp = pos[j]; - while ( ll_i != tmp ) { - j++; - tmp2 = tmp; - tmp = pos[j]; - pos[j] = tmp2; - }; - pos[0] = tmp; - s->selectorMtf[i] = j; - } - }; - - /*--- Assign actual codes for the tables. --*/ - for (t = 0; t < nGroups; t++) { - minLen = 32; - maxLen = 0; - for (i = 0; i < alphaSize; i++) { - if (s->len[t][i] > maxLen) maxLen = s->len[t][i]; - if (s->len[t][i] < minLen) minLen = s->len[t][i]; - } - AssertH ( !(maxLen > 17 /*20*/ ), 3004 ); - AssertH ( !(minLen < 1), 3005 ); - BZ2_hbAssignCodes ( &(s->code[t][0]), &(s->len[t][0]), - minLen, maxLen, alphaSize ); - } - - /*--- Transmit the mapping table. ---*/ - { - Bool inUse16[16]; - for (i = 0; i < 16; i++) { - inUse16[i] = False; - for (j = 0; j < 16; j++) - if (s->inUse[i * 16 + j]) inUse16[i] = True; - } - - nBytes = s->numZ; - for (i = 0; i < 16; i++) - if (inUse16[i]) bsW(s,1,1); else bsW(s,1,0); - - for (i = 0; i < 16; i++) - if (inUse16[i]) - for (j = 0; j < 16; j++) { - if (s->inUse[i * 16 + j]) bsW(s,1,1); else bsW(s,1,0); - } - - if (s->verbosity >= 3) - VPrintf1( " bytes: mapping %d, ", s->numZ-nBytes ); - } - - /*--- Now the selectors. ---*/ - nBytes = s->numZ; - bsW ( s, 3, nGroups ); - bsW ( s, 15, nSelectors ); - for (i = 0; i < nSelectors; i++) { - for (j = 0; j < s->selectorMtf[i]; j++) bsW(s,1,1); - bsW(s,1,0); - } - if (s->verbosity >= 3) - VPrintf1( "selectors %d, ", s->numZ-nBytes ); - - /*--- Now the coding tables. ---*/ - nBytes = s->numZ; - - for (t = 0; t < nGroups; t++) { - Int32 curr = s->len[t][0]; - bsW ( s, 5, curr ); - for (i = 0; i < alphaSize; i++) { - while (curr < s->len[t][i]) { bsW(s,2,2); curr++; /* 10 */ }; - while (curr > s->len[t][i]) { bsW(s,2,3); curr--; /* 11 */ }; - bsW ( s, 1, 0 ); - } - } - - if (s->verbosity >= 3) - VPrintf1 ( "code lengths %d, ", s->numZ-nBytes ); - - /*--- And finally, the block data proper ---*/ - nBytes = s->numZ; - selCtr = 0; - gs = 0; - while (True) { - if (gs >= s->nMTF) break; - ge = gs + BZ_G_SIZE - 1; - if (ge >= s->nMTF) ge = s->nMTF-1; - AssertH ( s->selector[selCtr] < nGroups, 3006 ); - - if (nGroups == 6 && 50 == ge-gs+1) { - /*--- fast track the common case ---*/ - UInt16 mtfv_i; - UChar* s_len_sel_selCtr - = &(s->len[s->selector[selCtr]][0]); - Int32* s_code_sel_selCtr - = &(s->code[s->selector[selCtr]][0]); - -# define BZ_ITAH(nn) \ - mtfv_i = mtfv[gs+(nn)]; \ - bsW ( s, \ - s_len_sel_selCtr[mtfv_i], \ - s_code_sel_selCtr[mtfv_i] ) - - BZ_ITAH(0); BZ_ITAH(1); BZ_ITAH(2); BZ_ITAH(3); BZ_ITAH(4); - BZ_ITAH(5); BZ_ITAH(6); BZ_ITAH(7); BZ_ITAH(8); BZ_ITAH(9); - BZ_ITAH(10); BZ_ITAH(11); BZ_ITAH(12); BZ_ITAH(13); BZ_ITAH(14); - BZ_ITAH(15); BZ_ITAH(16); BZ_ITAH(17); BZ_ITAH(18); BZ_ITAH(19); - BZ_ITAH(20); BZ_ITAH(21); BZ_ITAH(22); BZ_ITAH(23); BZ_ITAH(24); - BZ_ITAH(25); BZ_ITAH(26); BZ_ITAH(27); BZ_ITAH(28); BZ_ITAH(29); - BZ_ITAH(30); BZ_ITAH(31); BZ_ITAH(32); BZ_ITAH(33); BZ_ITAH(34); - BZ_ITAH(35); BZ_ITAH(36); BZ_ITAH(37); BZ_ITAH(38); BZ_ITAH(39); - BZ_ITAH(40); BZ_ITAH(41); BZ_ITAH(42); BZ_ITAH(43); BZ_ITAH(44); - BZ_ITAH(45); BZ_ITAH(46); BZ_ITAH(47); BZ_ITAH(48); BZ_ITAH(49); - -# undef BZ_ITAH - - } else { - /*--- slow version which correctly handles all situations ---*/ - for (i = gs; i <= ge; i++) { - bsW ( s, - s->len [s->selector[selCtr]] [mtfv[i]], - s->code [s->selector[selCtr]] [mtfv[i]] ); - } - } - - - gs = ge+1; - selCtr++; - } - AssertH( selCtr == nSelectors, 3007 ); - - if (s->verbosity >= 3) - VPrintf1( "codes %d\n", s->numZ-nBytes ); -} - - -/*---------------------------------------------------*/ -void BZ2_compressBlock ( EState* s, Bool is_last_block ) -{ - if (s->nblock > 0) { - - BZ_FINALISE_CRC ( s->blockCRC ); - s->combinedCRC = (s->combinedCRC << 1) | (s->combinedCRC >> 31); - s->combinedCRC ^= s->blockCRC; - if (s->blockNo > 1) s->numZ = 0; - - if (s->verbosity >= 2) - VPrintf4( " block %d: crc = 0x%08x, " - "combined CRC = 0x%08x, size = %d\n", - s->blockNo, s->blockCRC, s->combinedCRC, s->nblock ); - - BZ2_blockSort ( s ); - } - - s->zbits = (UChar*) (&((UChar*)s->arr2)[s->nblock]); - - /*-- If this is the first block, create the stream header. --*/ - if (s->blockNo == 1) { - BZ2_bsInitWrite ( s ); - bsPutUChar ( s, BZ_HDR_B ); - bsPutUChar ( s, BZ_HDR_Z ); - bsPutUChar ( s, BZ_HDR_h ); - bsPutUChar ( s, (UChar)(BZ_HDR_0 + s->blockSize100k) ); - } - - if (s->nblock > 0) { - - bsPutUChar ( s, 0x31 ); bsPutUChar ( s, 0x41 ); - bsPutUChar ( s, 0x59 ); bsPutUChar ( s, 0x26 ); - bsPutUChar ( s, 0x53 ); bsPutUChar ( s, 0x59 ); - - /*-- Now the block's CRC, so it is in a known place. --*/ - bsPutUInt32 ( s, s->blockCRC ); - - /*-- - Now a single bit indicating (non-)randomisation. - As of version 0.9.5, we use a better sorting algorithm - which makes randomisation unnecessary. So always set - the randomised bit to 'no'. Of course, the decoder - still needs to be able to handle randomised blocks - so as to maintain backwards compatibility with - older versions of bzip2. - --*/ - bsW(s,1,0); - - bsW ( s, 24, s->origPtr ); - generateMTFValues ( s ); - sendMTFValues ( s ); - } - - - /*-- If this is the last block, add the stream trailer. --*/ - if (is_last_block) { - - bsPutUChar ( s, 0x17 ); bsPutUChar ( s, 0x72 ); - bsPutUChar ( s, 0x45 ); bsPutUChar ( s, 0x38 ); - bsPutUChar ( s, 0x50 ); bsPutUChar ( s, 0x90 ); - bsPutUInt32 ( s, s->combinedCRC ); - if (s->verbosity >= 2) - VPrintf1( " final combined CRC = 0x%08x\n ", s->combinedCRC ); - bsFinishWrite ( s ); - } -} - - -/*-------------------------------------------------------------*/ -/*--- end compress.c ---*/ -/*-------------------------------------------------------------*/ diff --git a/app/jni/src/libultraship/extern/StormLib/src/bzip2/crctable.c b/app/jni/src/libultraship/extern/StormLib/src/bzip2/crctable.c deleted file mode 100644 index 215687b..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/bzip2/crctable.c +++ /dev/null @@ -1,104 +0,0 @@ - -/*-------------------------------------------------------------*/ -/*--- Table for doing CRCs ---*/ -/*--- crctable.c ---*/ -/*-------------------------------------------------------------*/ - -/* ------------------------------------------------------------------ - This file is part of bzip2/libbzip2, a program and library for - lossless, block-sorting data compression. - - bzip2/libbzip2 version 1.0.5 of 10 December 2007 - Copyright (C) 1996-2007 Julian Seward - - Please read the WARNING, DISCLAIMER and PATENTS sections in the - README file. - - This program is released under the terms of the license contained - in the file LICENSE. - ------------------------------------------------------------------ */ - - -#include "bzlib_private.h" - -/*-- - I think this is an implementation of the AUTODIN-II, - Ethernet & FDDI 32-bit CRC standard. Vaguely derived - from code by Rob Warnock, in Section 51 of the - comp.compression FAQ. ---*/ - -UInt32 BZ2_crc32Table[256] = { - - /*-- Ugly, innit? --*/ - - 0x00000000L, 0x04c11db7L, 0x09823b6eL, 0x0d4326d9L, - 0x130476dcL, 0x17c56b6bL, 0x1a864db2L, 0x1e475005L, - 0x2608edb8L, 0x22c9f00fL, 0x2f8ad6d6L, 0x2b4bcb61L, - 0x350c9b64L, 0x31cd86d3L, 0x3c8ea00aL, 0x384fbdbdL, - 0x4c11db70L, 0x48d0c6c7L, 0x4593e01eL, 0x4152fda9L, - 0x5f15adacL, 0x5bd4b01bL, 0x569796c2L, 0x52568b75L, - 0x6a1936c8L, 0x6ed82b7fL, 0x639b0da6L, 0x675a1011L, - 0x791d4014L, 0x7ddc5da3L, 0x709f7b7aL, 0x745e66cdL, - 0x9823b6e0L, 0x9ce2ab57L, 0x91a18d8eL, 0x95609039L, - 0x8b27c03cL, 0x8fe6dd8bL, 0x82a5fb52L, 0x8664e6e5L, - 0xbe2b5b58L, 0xbaea46efL, 0xb7a96036L, 0xb3687d81L, - 0xad2f2d84L, 0xa9ee3033L, 0xa4ad16eaL, 0xa06c0b5dL, - 0xd4326d90L, 0xd0f37027L, 0xddb056feL, 0xd9714b49L, - 0xc7361b4cL, 0xc3f706fbL, 0xceb42022L, 0xca753d95L, - 0xf23a8028L, 0xf6fb9d9fL, 0xfbb8bb46L, 0xff79a6f1L, - 0xe13ef6f4L, 0xe5ffeb43L, 0xe8bccd9aL, 0xec7dd02dL, - 0x34867077L, 0x30476dc0L, 0x3d044b19L, 0x39c556aeL, - 0x278206abL, 0x23431b1cL, 0x2e003dc5L, 0x2ac12072L, - 0x128e9dcfL, 0x164f8078L, 0x1b0ca6a1L, 0x1fcdbb16L, - 0x018aeb13L, 0x054bf6a4L, 0x0808d07dL, 0x0cc9cdcaL, - 0x7897ab07L, 0x7c56b6b0L, 0x71159069L, 0x75d48ddeL, - 0x6b93dddbL, 0x6f52c06cL, 0x6211e6b5L, 0x66d0fb02L, - 0x5e9f46bfL, 0x5a5e5b08L, 0x571d7dd1L, 0x53dc6066L, - 0x4d9b3063L, 0x495a2dd4L, 0x44190b0dL, 0x40d816baL, - 0xaca5c697L, 0xa864db20L, 0xa527fdf9L, 0xa1e6e04eL, - 0xbfa1b04bL, 0xbb60adfcL, 0xb6238b25L, 0xb2e29692L, - 0x8aad2b2fL, 0x8e6c3698L, 0x832f1041L, 0x87ee0df6L, - 0x99a95df3L, 0x9d684044L, 0x902b669dL, 0x94ea7b2aL, - 0xe0b41de7L, 0xe4750050L, 0xe9362689L, 0xedf73b3eL, - 0xf3b06b3bL, 0xf771768cL, 0xfa325055L, 0xfef34de2L, - 0xc6bcf05fL, 0xc27dede8L, 0xcf3ecb31L, 0xcbffd686L, - 0xd5b88683L, 0xd1799b34L, 0xdc3abdedL, 0xd8fba05aL, - 0x690ce0eeL, 0x6dcdfd59L, 0x608edb80L, 0x644fc637L, - 0x7a089632L, 0x7ec98b85L, 0x738aad5cL, 0x774bb0ebL, - 0x4f040d56L, 0x4bc510e1L, 0x46863638L, 0x42472b8fL, - 0x5c007b8aL, 0x58c1663dL, 0x558240e4L, 0x51435d53L, - 0x251d3b9eL, 0x21dc2629L, 0x2c9f00f0L, 0x285e1d47L, - 0x36194d42L, 0x32d850f5L, 0x3f9b762cL, 0x3b5a6b9bL, - 0x0315d626L, 0x07d4cb91L, 0x0a97ed48L, 0x0e56f0ffL, - 0x1011a0faL, 0x14d0bd4dL, 0x19939b94L, 0x1d528623L, - 0xf12f560eL, 0xf5ee4bb9L, 0xf8ad6d60L, 0xfc6c70d7L, - 0xe22b20d2L, 0xe6ea3d65L, 0xeba91bbcL, 0xef68060bL, - 0xd727bbb6L, 0xd3e6a601L, 0xdea580d8L, 0xda649d6fL, - 0xc423cd6aL, 0xc0e2d0ddL, 0xcda1f604L, 0xc960ebb3L, - 0xbd3e8d7eL, 0xb9ff90c9L, 0xb4bcb610L, 0xb07daba7L, - 0xae3afba2L, 0xaafbe615L, 0xa7b8c0ccL, 0xa379dd7bL, - 0x9b3660c6L, 0x9ff77d71L, 0x92b45ba8L, 0x9675461fL, - 0x8832161aL, 0x8cf30badL, 0x81b02d74L, 0x857130c3L, - 0x5d8a9099L, 0x594b8d2eL, 0x5408abf7L, 0x50c9b640L, - 0x4e8ee645L, 0x4a4ffbf2L, 0x470cdd2bL, 0x43cdc09cL, - 0x7b827d21L, 0x7f436096L, 0x7200464fL, 0x76c15bf8L, - 0x68860bfdL, 0x6c47164aL, 0x61043093L, 0x65c52d24L, - 0x119b4be9L, 0x155a565eL, 0x18197087L, 0x1cd86d30L, - 0x029f3d35L, 0x065e2082L, 0x0b1d065bL, 0x0fdc1becL, - 0x3793a651L, 0x3352bbe6L, 0x3e119d3fL, 0x3ad08088L, - 0x2497d08dL, 0x2056cd3aL, 0x2d15ebe3L, 0x29d4f654L, - 0xc5a92679L, 0xc1683bceL, 0xcc2b1d17L, 0xc8ea00a0L, - 0xd6ad50a5L, 0xd26c4d12L, 0xdf2f6bcbL, 0xdbee767cL, - 0xe3a1cbc1L, 0xe760d676L, 0xea23f0afL, 0xeee2ed18L, - 0xf0a5bd1dL, 0xf464a0aaL, 0xf9278673L, 0xfde69bc4L, - 0x89b8fd09L, 0x8d79e0beL, 0x803ac667L, 0x84fbdbd0L, - 0x9abc8bd5L, 0x9e7d9662L, 0x933eb0bbL, 0x97ffad0cL, - 0xafb010b1L, 0xab710d06L, 0xa6322bdfL, 0xa2f33668L, - 0xbcb4666dL, 0xb8757bdaL, 0xb5365d03L, 0xb1f740b4L -}; - - -/*-------------------------------------------------------------*/ -/*--- end crctable.c ---*/ -/*-------------------------------------------------------------*/ diff --git a/app/jni/src/libultraship/extern/StormLib/src/bzip2/decompress.c b/app/jni/src/libultraship/extern/StormLib/src/bzip2/decompress.c deleted file mode 100644 index bba5e0f..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/bzip2/decompress.c +++ /dev/null @@ -1,626 +0,0 @@ - -/*-------------------------------------------------------------*/ -/*--- Decompression machinery ---*/ -/*--- decompress.c ---*/ -/*-------------------------------------------------------------*/ - -/* ------------------------------------------------------------------ - This file is part of bzip2/libbzip2, a program and library for - lossless, block-sorting data compression. - - bzip2/libbzip2 version 1.0.5 of 10 December 2007 - Copyright (C) 1996-2007 Julian Seward - - Please read the WARNING, DISCLAIMER and PATENTS sections in the - README file. - - This program is released under the terms of the license contained - in the file LICENSE. - ------------------------------------------------------------------ */ - - -#include "bzlib_private.h" - - -/*---------------------------------------------------*/ -static -void makeMaps_d ( DState* s ) -{ - Int32 i; - s->nInUse = 0; - for (i = 0; i < 256; i++) - if (s->inUse[i]) { - s->seqToUnseq[s->nInUse] = i; - s->nInUse++; - } -} - - -/*---------------------------------------------------*/ -#define RETURN(rrr) \ - { retVal = rrr; goto save_state_and_return; }; - -#define GET_BITS(lll,vvv,nnn) \ - case lll: s->state = lll; \ - while (True) { \ - if (s->bsLive >= nnn) { \ - UInt32 v; \ - v = (s->bsBuff >> \ - (s->bsLive-nnn)) & ((1 << nnn)-1); \ - s->bsLive -= nnn; \ - vvv = v; \ - break; \ - } \ - if (s->strm->avail_in == 0) RETURN(BZ_OK); \ - s->bsBuff \ - = (s->bsBuff << 8) | \ - ((UInt32) \ - (*((UChar*)(s->strm->next_in)))); \ - s->bsLive += 8; \ - s->strm->next_in++; \ - s->strm->avail_in--; \ - s->strm->total_in_lo32++; \ - if (s->strm->total_in_lo32 == 0) \ - s->strm->total_in_hi32++; \ - } - -#define GET_UCHAR(lll,uuu) \ - GET_BITS(lll,uuu,8) - -#define GET_BIT(lll,uuu) \ - GET_BITS(lll,uuu,1) - -/*---------------------------------------------------*/ -#define GET_MTF_VAL(label1,label2,lval) \ -{ \ - if (groupPos == 0) { \ - groupNo++; \ - if (groupNo >= nSelectors) \ - RETURN(BZ_DATA_ERROR); \ - groupPos = BZ_G_SIZE; \ - gSel = s->selector[groupNo]; \ - gMinlen = s->minLens[gSel]; \ - gLimit = &(s->limit[gSel][0]); \ - gPerm = &(s->perm[gSel][0]); \ - gBase = &(s->base[gSel][0]); \ - } \ - groupPos--; \ - zn = gMinlen; \ - GET_BITS(label1, zvec, zn); \ - while (1) { \ - if (zn > 20 /* the longest code */) \ - RETURN(BZ_DATA_ERROR); \ - if (zvec <= gLimit[zn]) break; \ - zn++; \ - GET_BIT(label2, zj); \ - zvec = (zvec << 1) | zj; \ - }; \ - if (zvec - gBase[zn] < 0 \ - || zvec - gBase[zn] >= BZ_MAX_ALPHA_SIZE) \ - RETURN(BZ_DATA_ERROR); \ - lval = gPerm[zvec - gBase[zn]]; \ -} - - -/*---------------------------------------------------*/ -Int32 BZ2_decompress ( DState* s ) -{ - UChar uc; - Int32 retVal; - Int32 minLen, maxLen; - bz_stream* strm = s->strm; - - /* stuff that needs to be saved/restored */ - Int32 i; - Int32 j; - Int32 t; - Int32 alphaSize; - Int32 nGroups; - Int32 nSelectors; - Int32 EOB; - Int32 groupNo; - Int32 groupPos; - Int32 nextSym; - Int32 nblockMAX; - Int32 nblock; - Int32 es; - Int32 N; - Int32 curr; - Int32 zt; - Int32 zn; - Int32 zvec; - Int32 zj; - Int32 gSel; - Int32 gMinlen; - Int32* gLimit; - Int32* gBase; - Int32* gPerm; - - if (s->state == BZ_X_MAGIC_1) { - /*initialise the save area*/ - s->save_i = 0; - s->save_j = 0; - s->save_t = 0; - s->save_alphaSize = 0; - s->save_nGroups = 0; - s->save_nSelectors = 0; - s->save_EOB = 0; - s->save_groupNo = 0; - s->save_groupPos = 0; - s->save_nextSym = 0; - s->save_nblockMAX = 0; - s->save_nblock = 0; - s->save_es = 0; - s->save_N = 0; - s->save_curr = 0; - s->save_zt = 0; - s->save_zn = 0; - s->save_zvec = 0; - s->save_zj = 0; - s->save_gSel = 0; - s->save_gMinlen = 0; - s->save_gLimit = NULL; - s->save_gBase = NULL; - s->save_gPerm = NULL; - } - - /*restore from the save area*/ - i = s->save_i; - j = s->save_j; - t = s->save_t; - alphaSize = s->save_alphaSize; - nGroups = s->save_nGroups; - nSelectors = s->save_nSelectors; - EOB = s->save_EOB; - groupNo = s->save_groupNo; - groupPos = s->save_groupPos; - nextSym = s->save_nextSym; - nblockMAX = s->save_nblockMAX; - nblock = s->save_nblock; - es = s->save_es; - N = s->save_N; - curr = s->save_curr; - zt = s->save_zt; - zn = s->save_zn; - zvec = s->save_zvec; - zj = s->save_zj; - gSel = s->save_gSel; - gMinlen = s->save_gMinlen; - gLimit = s->save_gLimit; - gBase = s->save_gBase; - gPerm = s->save_gPerm; - - retVal = BZ_OK; - - switch (s->state) { - - GET_UCHAR(BZ_X_MAGIC_1, uc); - if (uc != BZ_HDR_B) RETURN(BZ_DATA_ERROR_MAGIC); - - GET_UCHAR(BZ_X_MAGIC_2, uc); - if (uc != BZ_HDR_Z) RETURN(BZ_DATA_ERROR_MAGIC); - - GET_UCHAR(BZ_X_MAGIC_3, uc) - if (uc != BZ_HDR_h) RETURN(BZ_DATA_ERROR_MAGIC); - - GET_BITS(BZ_X_MAGIC_4, s->blockSize100k, 8) - if (s->blockSize100k < (BZ_HDR_0 + 1) || - s->blockSize100k > (BZ_HDR_0 + 9)) RETURN(BZ_DATA_ERROR_MAGIC); - s->blockSize100k -= BZ_HDR_0; - - if (s->smallDecompress) { - s->ll16 = BZALLOC( s->blockSize100k * 100000 * sizeof(UInt16) ); - s->ll4 = BZALLOC( - ((1 + s->blockSize100k * 100000) >> 1) * sizeof(UChar) - ); - if (s->ll16 == NULL || s->ll4 == NULL) RETURN(BZ_MEM_ERROR); - } else { - s->tt = BZALLOC( s->blockSize100k * 100000 * sizeof(Int32) ); - if (s->tt == NULL) RETURN(BZ_MEM_ERROR); - } - - GET_UCHAR(BZ_X_BLKHDR_1, uc); - - if (uc == 0x17) goto endhdr_2; - if (uc != 0x31) RETURN(BZ_DATA_ERROR); - GET_UCHAR(BZ_X_BLKHDR_2, uc); - if (uc != 0x41) RETURN(BZ_DATA_ERROR); - GET_UCHAR(BZ_X_BLKHDR_3, uc); - if (uc != 0x59) RETURN(BZ_DATA_ERROR); - GET_UCHAR(BZ_X_BLKHDR_4, uc); - if (uc != 0x26) RETURN(BZ_DATA_ERROR); - GET_UCHAR(BZ_X_BLKHDR_5, uc); - if (uc != 0x53) RETURN(BZ_DATA_ERROR); - GET_UCHAR(BZ_X_BLKHDR_6, uc); - if (uc != 0x59) RETURN(BZ_DATA_ERROR); - - s->currBlockNo++; - if (s->verbosity >= 2) - VPrintf1 ( "\n [%d: huff+mtf ", s->currBlockNo ); - - s->storedBlockCRC = 0; - GET_UCHAR(BZ_X_BCRC_1, uc); - s->storedBlockCRC = (s->storedBlockCRC << 8) | ((UInt32)uc); - GET_UCHAR(BZ_X_BCRC_2, uc); - s->storedBlockCRC = (s->storedBlockCRC << 8) | ((UInt32)uc); - GET_UCHAR(BZ_X_BCRC_3, uc); - s->storedBlockCRC = (s->storedBlockCRC << 8) | ((UInt32)uc); - GET_UCHAR(BZ_X_BCRC_4, uc); - s->storedBlockCRC = (s->storedBlockCRC << 8) | ((UInt32)uc); - - GET_BITS(BZ_X_RANDBIT, s->blockRandomised, 1); - - s->origPtr = 0; - GET_UCHAR(BZ_X_ORIGPTR_1, uc); - s->origPtr = (s->origPtr << 8) | ((Int32)uc); - GET_UCHAR(BZ_X_ORIGPTR_2, uc); - s->origPtr = (s->origPtr << 8) | ((Int32)uc); - GET_UCHAR(BZ_X_ORIGPTR_3, uc); - s->origPtr = (s->origPtr << 8) | ((Int32)uc); - - if (s->origPtr < 0) - RETURN(BZ_DATA_ERROR); - if (s->origPtr > 10 + 100000*s->blockSize100k) - RETURN(BZ_DATA_ERROR); - - /*--- Receive the mapping table ---*/ - for (i = 0; i < 16; i++) { - GET_BIT(BZ_X_MAPPING_1, uc); - if (uc == 1) - s->inUse16[i] = True; else - s->inUse16[i] = False; - } - - for (i = 0; i < 256; i++) s->inUse[i] = False; - - for (i = 0; i < 16; i++) - if (s->inUse16[i]) - for (j = 0; j < 16; j++) { - GET_BIT(BZ_X_MAPPING_2, uc); - if (uc == 1) s->inUse[i * 16 + j] = True; - } - makeMaps_d ( s ); - if (s->nInUse == 0) RETURN(BZ_DATA_ERROR); - alphaSize = s->nInUse+2; - - /*--- Now the selectors ---*/ - GET_BITS(BZ_X_SELECTOR_1, nGroups, 3); - if (nGroups < 2 || nGroups > 6) RETURN(BZ_DATA_ERROR); - GET_BITS(BZ_X_SELECTOR_2, nSelectors, 15); - if (nSelectors < 1) RETURN(BZ_DATA_ERROR); - for (i = 0; i < nSelectors; i++) { - j = 0; - while (True) { - GET_BIT(BZ_X_SELECTOR_3, uc); - if (uc == 0) break; - j++; - if (j >= nGroups) RETURN(BZ_DATA_ERROR); - } - s->selectorMtf[i] = j; - } - - /*--- Undo the MTF values for the selectors. ---*/ - { - UChar pos[BZ_N_GROUPS], tmp, v; - for (v = 0; v < nGroups; v++) pos[v] = v; - - for (i = 0; i < nSelectors; i++) { - v = s->selectorMtf[i]; - tmp = pos[v]; - while (v > 0) { pos[v] = pos[v-1]; v--; } - pos[0] = tmp; - s->selector[i] = tmp; - } - } - - /*--- Now the coding tables ---*/ - for (t = 0; t < nGroups; t++) { - GET_BITS(BZ_X_CODING_1, curr, 5); - for (i = 0; i < alphaSize; i++) { - while (True) { - if (curr < 1 || curr > 20) RETURN(BZ_DATA_ERROR); - GET_BIT(BZ_X_CODING_2, uc); - if (uc == 0) break; - GET_BIT(BZ_X_CODING_3, uc); - if (uc == 0) curr++; else curr--; - } - s->len[t][i] = curr; - } - } - - /*--- Create the Huffman decoding tables ---*/ - for (t = 0; t < nGroups; t++) { - minLen = 32; - maxLen = 0; - for (i = 0; i < alphaSize; i++) { - if (s->len[t][i] > maxLen) maxLen = s->len[t][i]; - if (s->len[t][i] < minLen) minLen = s->len[t][i]; - } - BZ2_hbCreateDecodeTables ( - &(s->limit[t][0]), - &(s->base[t][0]), - &(s->perm[t][0]), - &(s->len[t][0]), - minLen, maxLen, alphaSize - ); - s->minLens[t] = minLen; - } - - /*--- Now the MTF values ---*/ - - EOB = s->nInUse+1; - nblockMAX = 100000 * s->blockSize100k; - groupNo = -1; - groupPos = 0; - - for (i = 0; i <= 255; i++) s->unzftab[i] = 0; - - /*-- MTF init --*/ - { - Int32 ii, jj, kk; - kk = MTFA_SIZE-1; - for (ii = 256 / MTFL_SIZE - 1; ii >= 0; ii--) { - for (jj = MTFL_SIZE-1; jj >= 0; jj--) { - s->mtfa[kk] = (UChar)(ii * MTFL_SIZE + jj); - kk--; - } - s->mtfbase[ii] = kk + 1; - } - } - /*-- end MTF init --*/ - - nblock = 0; - GET_MTF_VAL(BZ_X_MTF_1, BZ_X_MTF_2, nextSym); - - while (True) { - - if (nextSym == EOB) break; - - if (nextSym == BZ_RUNA || nextSym == BZ_RUNB) { - - es = -1; - N = 1; - do { - if (nextSym == BZ_RUNA) es = es + (0+1) * N; else - if (nextSym == BZ_RUNB) es = es + (1+1) * N; - N = N * 2; - GET_MTF_VAL(BZ_X_MTF_3, BZ_X_MTF_4, nextSym); - } - while (nextSym == BZ_RUNA || nextSym == BZ_RUNB); - - es++; - uc = s->seqToUnseq[ s->mtfa[s->mtfbase[0]] ]; - s->unzftab[uc] += es; - - if (s->smallDecompress) - while (es > 0) { - if (nblock >= nblockMAX) RETURN(BZ_DATA_ERROR); - s->ll16[nblock] = (UInt16)uc; - nblock++; - es--; - } - else - while (es > 0) { - if (nblock >= nblockMAX) RETURN(BZ_DATA_ERROR); - s->tt[nblock] = (UInt32)uc; - nblock++; - es--; - }; - - continue; - - } else { - - if (nblock >= nblockMAX) RETURN(BZ_DATA_ERROR); - - /*-- uc = MTF ( nextSym-1 ) --*/ - { - Int32 ii, jj, kk, pp, lno, off; - UInt32 nn; - nn = (UInt32)(nextSym - 1); - - if (nn < MTFL_SIZE) { - /* avoid general-case expense */ - pp = s->mtfbase[0]; - uc = s->mtfa[pp+nn]; - while (nn > 3) { - Int32 z = pp+nn; - s->mtfa[(z) ] = s->mtfa[(z)-1]; - s->mtfa[(z)-1] = s->mtfa[(z)-2]; - s->mtfa[(z)-2] = s->mtfa[(z)-3]; - s->mtfa[(z)-3] = s->mtfa[(z)-4]; - nn -= 4; - } - while (nn > 0) { - s->mtfa[(pp+nn)] = s->mtfa[(pp+nn)-1]; nn--; - }; - s->mtfa[pp] = uc; - } else { - /* general case */ - lno = nn / MTFL_SIZE; - off = nn % MTFL_SIZE; - pp = s->mtfbase[lno] + off; - uc = s->mtfa[pp]; - while (pp > s->mtfbase[lno]) { - s->mtfa[pp] = s->mtfa[pp-1]; pp--; - }; - s->mtfbase[lno]++; - while (lno > 0) { - s->mtfbase[lno]--; - s->mtfa[s->mtfbase[lno]] - = s->mtfa[s->mtfbase[lno-1] + MTFL_SIZE - 1]; - lno--; - } - s->mtfbase[0]--; - s->mtfa[s->mtfbase[0]] = uc; - if (s->mtfbase[0] == 0) { - kk = MTFA_SIZE-1; - for (ii = 256 / MTFL_SIZE-1; ii >= 0; ii--) { - for (jj = MTFL_SIZE-1; jj >= 0; jj--) { - s->mtfa[kk] = s->mtfa[s->mtfbase[ii] + jj]; - kk--; - } - s->mtfbase[ii] = kk + 1; - } - } - } - } - /*-- end uc = MTF ( nextSym-1 ) --*/ - - s->unzftab[s->seqToUnseq[uc]]++; - if (s->smallDecompress) - s->ll16[nblock] = (UInt16)(s->seqToUnseq[uc]); else - s->tt[nblock] = (UInt32)(s->seqToUnseq[uc]); - nblock++; - - GET_MTF_VAL(BZ_X_MTF_5, BZ_X_MTF_6, nextSym); - continue; - } - } - - /* Now we know what nblock is, we can do a better sanity - check on s->origPtr. - */ - if (s->origPtr < 0 || s->origPtr >= nblock) - RETURN(BZ_DATA_ERROR); - - /*-- Set up cftab to facilitate generation of T^(-1) --*/ - s->cftab[0] = 0; - for (i = 1; i <= 256; i++) s->cftab[i] = s->unzftab[i-1]; - for (i = 1; i <= 256; i++) s->cftab[i] += s->cftab[i-1]; - for (i = 0; i <= 256; i++) { - if (s->cftab[i] < 0 || s->cftab[i] > nblock) { - /* s->cftab[i] can legitimately be == nblock */ - RETURN(BZ_DATA_ERROR); - } - } - - s->state_out_len = 0; - s->state_out_ch = 0; - BZ_INITIALISE_CRC ( s->calculatedBlockCRC ); - s->state = BZ_X_OUTPUT; - if (s->verbosity >= 2) VPrintf0 ( "rt+rld" ); - - if (s->smallDecompress) { - - /*-- Make a copy of cftab, used in generation of T --*/ - for (i = 0; i <= 256; i++) s->cftabCopy[i] = s->cftab[i]; - - /*-- compute the T vector --*/ - for (i = 0; i < nblock; i++) { - uc = (UChar)(s->ll16[i]); - SET_LL(i, s->cftabCopy[uc]); - s->cftabCopy[uc]++; - } - - /*-- Compute T^(-1) by pointer reversal on T --*/ - i = s->origPtr; - j = GET_LL(i); - do { - Int32 tmp = GET_LL(j); - SET_LL(j, i); - i = j; - j = tmp; - } - while (i != s->origPtr); - - s->tPos = s->origPtr; - s->nblock_used = 0; - if (s->blockRandomised) { - BZ_RAND_INIT_MASK; - BZ_GET_SMALL(s->k0); s->nblock_used++; - BZ_RAND_UPD_MASK; s->k0 ^= BZ_RAND_MASK; - } else { - BZ_GET_SMALL(s->k0); s->nblock_used++; - } - - } else { - - /*-- compute the T^(-1) vector --*/ - for (i = 0; i < nblock; i++) { - uc = (UChar)(s->tt[i] & 0xff); - s->tt[s->cftab[uc]] |= (i << 8); - s->cftab[uc]++; - } - - s->tPos = s->tt[s->origPtr] >> 8; - s->nblock_used = 0; - if (s->blockRandomised) { - BZ_RAND_INIT_MASK; - BZ_GET_FAST(s->k0); s->nblock_used++; - BZ_RAND_UPD_MASK; s->k0 ^= BZ_RAND_MASK; - } else { - BZ_GET_FAST(s->k0); s->nblock_used++; - } - - } - - RETURN(BZ_OK); - - - - endhdr_2: - - GET_UCHAR(BZ_X_ENDHDR_2, uc); - if (uc != 0x72) RETURN(BZ_DATA_ERROR); - GET_UCHAR(BZ_X_ENDHDR_3, uc); - if (uc != 0x45) RETURN(BZ_DATA_ERROR); - GET_UCHAR(BZ_X_ENDHDR_4, uc); - if (uc != 0x38) RETURN(BZ_DATA_ERROR); - GET_UCHAR(BZ_X_ENDHDR_5, uc); - if (uc != 0x50) RETURN(BZ_DATA_ERROR); - GET_UCHAR(BZ_X_ENDHDR_6, uc); - if (uc != 0x90) RETURN(BZ_DATA_ERROR); - - s->storedCombinedCRC = 0; - GET_UCHAR(BZ_X_CCRC_1, uc); - s->storedCombinedCRC = (s->storedCombinedCRC << 8) | ((UInt32)uc); - GET_UCHAR(BZ_X_CCRC_2, uc); - s->storedCombinedCRC = (s->storedCombinedCRC << 8) | ((UInt32)uc); - GET_UCHAR(BZ_X_CCRC_3, uc); - s->storedCombinedCRC = (s->storedCombinedCRC << 8) | ((UInt32)uc); - GET_UCHAR(BZ_X_CCRC_4, uc); - s->storedCombinedCRC = (s->storedCombinedCRC << 8) | ((UInt32)uc); - - s->state = BZ_X_IDLE; - RETURN(BZ_STREAM_END); - - default: AssertH ( False, 4001 ); - } - - AssertH ( False, 4002 ); - - save_state_and_return: - - s->save_i = i; - s->save_j = j; - s->save_t = t; - s->save_alphaSize = alphaSize; - s->save_nGroups = nGroups; - s->save_nSelectors = nSelectors; - s->save_EOB = EOB; - s->save_groupNo = groupNo; - s->save_groupPos = groupPos; - s->save_nextSym = nextSym; - s->save_nblockMAX = nblockMAX; - s->save_nblock = nblock; - s->save_es = es; - s->save_N = N; - s->save_curr = curr; - s->save_zt = zt; - s->save_zn = zn; - s->save_zvec = zvec; - s->save_zj = zj; - s->save_gSel = gSel; - s->save_gMinlen = gMinlen; - s->save_gLimit = gLimit; - s->save_gBase = gBase; - s->save_gPerm = gPerm; - - return retVal; -} - - -/*-------------------------------------------------------------*/ -/*--- end decompress.c ---*/ -/*-------------------------------------------------------------*/ diff --git a/app/jni/src/libultraship/extern/StormLib/src/bzip2/huffman.c b/app/jni/src/libultraship/extern/StormLib/src/bzip2/huffman.c deleted file mode 100644 index 87e79e3..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/bzip2/huffman.c +++ /dev/null @@ -1,205 +0,0 @@ - -/*-------------------------------------------------------------*/ -/*--- Huffman coding low-level stuff ---*/ -/*--- huffman.c ---*/ -/*-------------------------------------------------------------*/ - -/* ------------------------------------------------------------------ - This file is part of bzip2/libbzip2, a program and library for - lossless, block-sorting data compression. - - bzip2/libbzip2 version 1.0.5 of 10 December 2007 - Copyright (C) 1996-2007 Julian Seward - - Please read the WARNING, DISCLAIMER and PATENTS sections in the - README file. - - This program is released under the terms of the license contained - in the file LICENSE. - ------------------------------------------------------------------ */ - - -#include "bzlib_private.h" - -/*---------------------------------------------------*/ -#define WEIGHTOF(zz0) ((zz0) & 0xffffff00) -#define DEPTHOF(zz1) ((zz1) & 0x000000ff) -#define MYMAX(zz2,zz3) ((zz2) > (zz3) ? (zz2) : (zz3)) - -#define ADDWEIGHTS(zw1,zw2) \ - (WEIGHTOF(zw1)+WEIGHTOF(zw2)) | \ - (1 + MYMAX(DEPTHOF(zw1),DEPTHOF(zw2))) - -#define UPHEAP(z) \ -{ \ - Int32 zz, tmp; \ - zz = z; tmp = heap[zz]; \ - while (weight[tmp] < weight[heap[zz >> 1]]) { \ - heap[zz] = heap[zz >> 1]; \ - zz >>= 1; \ - } \ - heap[zz] = tmp; \ -} - -#define DOWNHEAP(z) \ -{ \ - Int32 zz, yy, tmp; \ - zz = z; tmp = heap[zz]; \ - while (True) { \ - yy = zz << 1; \ - if (yy > nHeap) break; \ - if (yy < nHeap && \ - weight[heap[yy+1]] < weight[heap[yy]]) \ - yy++; \ - if (weight[tmp] < weight[heap[yy]]) break; \ - heap[zz] = heap[yy]; \ - zz = yy; \ - } \ - heap[zz] = tmp; \ -} - - -/*---------------------------------------------------*/ -void BZ2_hbMakeCodeLengths ( UChar *len, - Int32 *freq, - Int32 alphaSize, - Int32 maxLen ) -{ - /*-- - Nodes and heap entries run from 1. Entry 0 - for both the heap and nodes is a sentinel. - --*/ - Int32 nNodes, nHeap, n1, n2, i, j, k; - Bool tooLong; - - Int32 heap [ BZ_MAX_ALPHA_SIZE + 2 ]; - Int32 weight [ BZ_MAX_ALPHA_SIZE * 2 ]; - Int32 parent [ BZ_MAX_ALPHA_SIZE * 2 ]; - - for (i = 0; i < alphaSize; i++) - weight[i+1] = (freq[i] == 0 ? 1 : freq[i]) << 8; - - while (True) { - - nNodes = alphaSize; - nHeap = 0; - - heap[0] = 0; - weight[0] = 0; - parent[0] = -2; - - for (i = 1; i <= alphaSize; i++) { - parent[i] = -1; - nHeap++; - heap[nHeap] = i; - UPHEAP(nHeap); - } - - AssertH( nHeap < (BZ_MAX_ALPHA_SIZE+2), 2001 ); - - while (nHeap > 1) { - n1 = heap[1]; heap[1] = heap[nHeap]; nHeap--; DOWNHEAP(1); - n2 = heap[1]; heap[1] = heap[nHeap]; nHeap--; DOWNHEAP(1); - nNodes++; - parent[n1] = parent[n2] = nNodes; - weight[nNodes] = ADDWEIGHTS(weight[n1], weight[n2]); - parent[nNodes] = -1; - nHeap++; - heap[nHeap] = nNodes; - UPHEAP(nHeap); - } - - AssertH( nNodes < (BZ_MAX_ALPHA_SIZE * 2), 2002 ); - - tooLong = False; - for (i = 1; i <= alphaSize; i++) { - j = 0; - k = i; - while (parent[k] >= 0) { k = parent[k]; j++; } - len[i-1] = j; - if (j > maxLen) tooLong = True; - } - - if (! tooLong) break; - - /* 17 Oct 04: keep-going condition for the following loop used - to be 'i < alphaSize', which missed the last element, - theoretically leading to the possibility of the compressor - looping. However, this count-scaling step is only needed if - one of the generated Huffman code words is longer than - maxLen, which up to and including version 1.0.2 was 20 bits, - which is extremely unlikely. In version 1.0.3 maxLen was - changed to 17 bits, which has minimal effect on compression - ratio, but does mean this scaling step is used from time to - time, enough to verify that it works. - - This means that bzip2-1.0.3 and later will only produce - Huffman codes with a maximum length of 17 bits. However, in - order to preserve backwards compatibility with bitstreams - produced by versions pre-1.0.3, the decompressor must still - handle lengths of up to 20. */ - - for (i = 1; i <= alphaSize; i++) { - j = weight[i] >> 8; - j = 1 + (j / 2); - weight[i] = j << 8; - } - } -} - - -/*---------------------------------------------------*/ -void BZ2_hbAssignCodes ( Int32 *code, - UChar *length, - Int32 minLen, - Int32 maxLen, - Int32 alphaSize ) -{ - Int32 n, vec, i; - - vec = 0; - for (n = minLen; n <= maxLen; n++) { - for (i = 0; i < alphaSize; i++) - if (length[i] == n) { code[i] = vec; vec++; }; - vec <<= 1; - } -} - - -/*---------------------------------------------------*/ -void BZ2_hbCreateDecodeTables ( Int32 *limit, - Int32 *base, - Int32 *perm, - UChar *length, - Int32 minLen, - Int32 maxLen, - Int32 alphaSize ) -{ - Int32 pp, i, j, vec; - - pp = 0; - for (i = minLen; i <= maxLen; i++) - for (j = 0; j < alphaSize; j++) - if (length[j] == i) { perm[pp] = j; pp++; }; - - for (i = 0; i < BZ_MAX_CODE_LEN; i++) base[i] = 0; - for (i = 0; i < alphaSize; i++) base[length[i]+1]++; - - for (i = 1; i < BZ_MAX_CODE_LEN; i++) base[i] += base[i-1]; - - for (i = 0; i < BZ_MAX_CODE_LEN; i++) limit[i] = 0; - vec = 0; - - for (i = minLen; i <= maxLen; i++) { - vec += (base[i+1] - base[i]); - limit[i] = vec-1; - vec <<= 1; - } - for (i = minLen + 1; i <= maxLen; i++) - base[i] = ((limit[i-1] + 1) << 1) - base[i]; -} - - -/*-------------------------------------------------------------*/ -/*--- end huffman.c ---*/ -/*-------------------------------------------------------------*/ diff --git a/app/jni/src/libultraship/extern/StormLib/src/bzip2/randtable.c b/app/jni/src/libultraship/extern/StormLib/src/bzip2/randtable.c deleted file mode 100644 index 068b763..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/bzip2/randtable.c +++ /dev/null @@ -1,84 +0,0 @@ - -/*-------------------------------------------------------------*/ -/*--- Table for randomising repetitive blocks ---*/ -/*--- randtable.c ---*/ -/*-------------------------------------------------------------*/ - -/* ------------------------------------------------------------------ - This file is part of bzip2/libbzip2, a program and library for - lossless, block-sorting data compression. - - bzip2/libbzip2 version 1.0.5 of 10 December 2007 - Copyright (C) 1996-2007 Julian Seward - - Please read the WARNING, DISCLAIMER and PATENTS sections in the - README file. - - This program is released under the terms of the license contained - in the file LICENSE. - ------------------------------------------------------------------ */ - - -#include "bzlib_private.h" - - -/*---------------------------------------------*/ -Int32 BZ2_rNums[512] = { - 619, 720, 127, 481, 931, 816, 813, 233, 566, 247, - 985, 724, 205, 454, 863, 491, 741, 242, 949, 214, - 733, 859, 335, 708, 621, 574, 73, 654, 730, 472, - 419, 436, 278, 496, 867, 210, 399, 680, 480, 51, - 878, 465, 811, 169, 869, 675, 611, 697, 867, 561, - 862, 687, 507, 283, 482, 129, 807, 591, 733, 623, - 150, 238, 59, 379, 684, 877, 625, 169, 643, 105, - 170, 607, 520, 932, 727, 476, 693, 425, 174, 647, - 73, 122, 335, 530, 442, 853, 695, 249, 445, 515, - 909, 545, 703, 919, 874, 474, 882, 500, 594, 612, - 641, 801, 220, 162, 819, 984, 589, 513, 495, 799, - 161, 604, 958, 533, 221, 400, 386, 867, 600, 782, - 382, 596, 414, 171, 516, 375, 682, 485, 911, 276, - 98, 553, 163, 354, 666, 933, 424, 341, 533, 870, - 227, 730, 475, 186, 263, 647, 537, 686, 600, 224, - 469, 68, 770, 919, 190, 373, 294, 822, 808, 206, - 184, 943, 795, 384, 383, 461, 404, 758, 839, 887, - 715, 67, 618, 276, 204, 918, 873, 777, 604, 560, - 951, 160, 578, 722, 79, 804, 96, 409, 713, 940, - 652, 934, 970, 447, 318, 353, 859, 672, 112, 785, - 645, 863, 803, 350, 139, 93, 354, 99, 820, 908, - 609, 772, 154, 274, 580, 184, 79, 626, 630, 742, - 653, 282, 762, 623, 680, 81, 927, 626, 789, 125, - 411, 521, 938, 300, 821, 78, 343, 175, 128, 250, - 170, 774, 972, 275, 999, 639, 495, 78, 352, 126, - 857, 956, 358, 619, 580, 124, 737, 594, 701, 612, - 669, 112, 134, 694, 363, 992, 809, 743, 168, 974, - 944, 375, 748, 52, 600, 747, 642, 182, 862, 81, - 344, 805, 988, 739, 511, 655, 814, 334, 249, 515, - 897, 955, 664, 981, 649, 113, 974, 459, 893, 228, - 433, 837, 553, 268, 926, 240, 102, 654, 459, 51, - 686, 754, 806, 760, 493, 403, 415, 394, 687, 700, - 946, 670, 656, 610, 738, 392, 760, 799, 887, 653, - 978, 321, 576, 617, 626, 502, 894, 679, 243, 440, - 680, 879, 194, 572, 640, 724, 926, 56, 204, 700, - 707, 151, 457, 449, 797, 195, 791, 558, 945, 679, - 297, 59, 87, 824, 713, 663, 412, 693, 342, 606, - 134, 108, 571, 364, 631, 212, 174, 643, 304, 329, - 343, 97, 430, 751, 497, 314, 983, 374, 822, 928, - 140, 206, 73, 263, 980, 736, 876, 478, 430, 305, - 170, 514, 364, 692, 829, 82, 855, 953, 676, 246, - 369, 970, 294, 750, 807, 827, 150, 790, 288, 923, - 804, 378, 215, 828, 592, 281, 565, 555, 710, 82, - 896, 831, 547, 261, 524, 462, 293, 465, 502, 56, - 661, 821, 976, 991, 658, 869, 905, 758, 745, 193, - 768, 550, 608, 933, 378, 286, 215, 979, 792, 961, - 61, 688, 793, 644, 986, 403, 106, 366, 905, 644, - 372, 567, 466, 434, 645, 210, 389, 550, 919, 135, - 780, 773, 635, 389, 707, 100, 626, 958, 165, 504, - 920, 176, 193, 713, 857, 265, 203, 50, 668, 108, - 645, 990, 626, 197, 510, 357, 358, 850, 858, 364, - 936, 638 -}; - - -/*-------------------------------------------------------------*/ -/*--- end randtable.c ---*/ -/*-------------------------------------------------------------*/ diff --git a/app/jni/src/libultraship/extern/StormLib/src/huffman/huff.cpp b/app/jni/src/libultraship/extern/StormLib/src/huffman/huff.cpp deleted file mode 100644 index 6930354..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/huffman/huff.cpp +++ /dev/null @@ -1,892 +0,0 @@ -/*****************************************************************************/ -/* huffman.cpp Copyright (c) Ladislav Zezula 1998-2003 */ -/*---------------------------------------------------------------------------*/ -/* This module contains Huffmann (de)compression methods */ -/* */ -/* Authors : Ladislav Zezula (ladik@zezula.net) */ -/* ShadowFlare (BlakFlare@hotmail.com) */ -/* */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* xx.xx.xx 1.00 Lad The first version of dcmp.cpp */ -/* 03.05.03 1.00 Lad Added compression methods */ -/* 19.11.03 1.01 Dan Big endian handling */ -/* 08.12.03 2.01 Dan High-memory handling (> 0x80000000) */ -/* 09.01.13 3.00 Lad Refactored, beautified, documented :-) */ -/*****************************************************************************/ - -#include -#include - -#include "huff.h" - -//----------------------------------------------------------------------------- -// Table of byte-to-weight values - -// Table for (de)compression. Every compression type has 258 entries -static unsigned char ByteToWeight_00[] = -{ - 0x0A, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, - 0x00, 0x00 -}; - -// Data for compression type 0x01 -static unsigned char ByteToWeight_01[] = -{ - 0x54, 0x16, 0x16, 0x0D, 0x0C, 0x08, 0x06, 0x05, 0x06, 0x05, 0x06, 0x03, 0x04, 0x04, 0x03, 0x05, - 0x0E, 0x0B, 0x14, 0x13, 0x13, 0x09, 0x0B, 0x06, 0x05, 0x04, 0x03, 0x02, 0x03, 0x02, 0x02, 0x02, - 0x0D, 0x07, 0x09, 0x06, 0x06, 0x04, 0x03, 0x02, 0x04, 0x03, 0x03, 0x03, 0x03, 0x03, 0x02, 0x02, - 0x09, 0x06, 0x04, 0x04, 0x04, 0x04, 0x03, 0x02, 0x03, 0x02, 0x02, 0x02, 0x02, 0x03, 0x02, 0x04, - 0x08, 0x03, 0x04, 0x07, 0x09, 0x05, 0x03, 0x03, 0x03, 0x03, 0x02, 0x02, 0x02, 0x03, 0x02, 0x02, - 0x03, 0x02, 0x02, 0x02, 0x02, 0x02, 0x02, 0x02, 0x02, 0x01, 0x01, 0x01, 0x02, 0x01, 0x02, 0x02, - 0x06, 0x0A, 0x08, 0x08, 0x06, 0x07, 0x04, 0x03, 0x04, 0x04, 0x02, 0x02, 0x04, 0x02, 0x03, 0x03, - 0x04, 0x03, 0x07, 0x07, 0x09, 0x06, 0x04, 0x03, 0x03, 0x02, 0x01, 0x02, 0x02, 0x02, 0x02, 0x02, - 0x0A, 0x02, 0x02, 0x03, 0x02, 0x02, 0x01, 0x01, 0x02, 0x02, 0x02, 0x06, 0x03, 0x05, 0x02, 0x03, - 0x02, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x02, 0x03, 0x01, 0x01, 0x01, - 0x02, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x02, 0x04, 0x04, 0x04, 0x07, 0x09, 0x08, 0x0C, 0x02, - 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x02, 0x01, 0x01, 0x03, - 0x04, 0x01, 0x02, 0x04, 0x05, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x02, 0x01, 0x01, 0x01, - 0x04, 0x01, 0x01, 0x01, 0x01, 0x01, 0x02, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, - 0x02, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x03, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, - 0x02, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x02, 0x02, 0x01, 0x01, 0x02, 0x02, 0x02, 0x06, 0x4B, - 0x00, 0x00 -}; - -// Data for compression type 0x02 -static unsigned char ByteToWeight_02[] = -{ - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x27, 0x00, 0x00, 0x23, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0xFF, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x02, 0x02, 0x01, 0x01, 0x06, 0x0E, 0x10, 0x04, - 0x06, 0x08, 0x05, 0x04, 0x04, 0x03, 0x03, 0x02, 0x02, 0x03, 0x03, 0x01, 0x01, 0x02, 0x01, 0x01, - 0x01, 0x04, 0x02, 0x04, 0x02, 0x02, 0x02, 0x01, 0x01, 0x04, 0x01, 0x01, 0x02, 0x03, 0x03, 0x02, - 0x03, 0x01, 0x03, 0x06, 0x04, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x02, 0x01, 0x02, 0x01, 0x01, - 0x01, 0x29, 0x07, 0x16, 0x12, 0x40, 0x0A, 0x0A, 0x11, 0x25, 0x01, 0x03, 0x17, 0x10, 0x26, 0x2A, - 0x10, 0x01, 0x23, 0x23, 0x2F, 0x10, 0x06, 0x07, 0x02, 0x09, 0x01, 0x01, 0x01, 0x01, 0x01, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00 -}; - -// Data for compression type 0x03 -static unsigned char ByteToWeight_03[] = -{ - 0xFF, 0x0B, 0x07, 0x05, 0x0B, 0x02, 0x02, 0x02, 0x06, 0x02, 0x02, 0x01, 0x04, 0x02, 0x01, 0x03, - 0x09, 0x01, 0x01, 0x01, 0x03, 0x04, 0x01, 0x01, 0x02, 0x01, 0x01, 0x01, 0x02, 0x01, 0x01, 0x01, - 0x05, 0x01, 0x01, 0x01, 0x0D, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, - 0x02, 0x01, 0x01, 0x03, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x02, 0x01, 0x01, 0x01, 0x01, - 0x0A, 0x04, 0x02, 0x01, 0x06, 0x03, 0x02, 0x01, 0x01, 0x01, 0x01, 0x01, 0x03, 0x01, 0x01, 0x01, - 0x05, 0x02, 0x03, 0x04, 0x03, 0x03, 0x03, 0x02, 0x01, 0x01, 0x01, 0x02, 0x01, 0x02, 0x03, 0x03, - 0x01, 0x03, 0x01, 0x01, 0x02, 0x05, 0x01, 0x01, 0x04, 0x03, 0x05, 0x01, 0x03, 0x01, 0x03, 0x03, - 0x02, 0x01, 0x04, 0x03, 0x0A, 0x06, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, - 0x02, 0x02, 0x01, 0x0A, 0x02, 0x05, 0x01, 0x01, 0x02, 0x07, 0x02, 0x17, 0x01, 0x05, 0x01, 0x01, - 0x0E, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, - 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, - 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, - 0x06, 0x02, 0x01, 0x04, 0x05, 0x01, 0x01, 0x02, 0x01, 0x01, 0x01, 0x01, 0x02, 0x01, 0x01, 0x01, - 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, - 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x07, 0x01, 0x01, 0x02, 0x01, 0x01, 0x01, 0x01, - 0x02, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x02, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x11, - 0x00, 0x00 -}; - -// Data for compression type 0x04 -static unsigned char ByteToWeight_04[] = -{ - 0xFF, 0xFB, 0x98, 0x9A, 0x84, 0x85, 0x63, 0x64, 0x3E, 0x3E, 0x22, 0x22, 0x13, 0x13, 0x18, 0x17, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00 -}; - -// Data for compression type 0x05 -static unsigned char ByteToWeight_05[] = -{ - 0xFF, 0xF1, 0x9D, 0x9E, 0x9A, 0x9B, 0x9A, 0x97, 0x93, 0x93, 0x8C, 0x8E, 0x86, 0x88, 0x80, 0x82, - 0x7C, 0x7C, 0x72, 0x73, 0x69, 0x6B, 0x5F, 0x60, 0x55, 0x56, 0x4A, 0x4B, 0x40, 0x41, 0x37, 0x37, - 0x2F, 0x2F, 0x27, 0x27, 0x21, 0x21, 0x1B, 0x1C, 0x17, 0x17, 0x13, 0x13, 0x10, 0x10, 0x0D, 0x0D, - 0x0B, 0x0B, 0x09, 0x09, 0x08, 0x08, 0x07, 0x07, 0x06, 0x05, 0x05, 0x04, 0x04, 0x04, 0x19, 0x18, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00 -}; - - // Data for compression type 0x06 -static unsigned char ByteToWeight_06[] = -{ - 0xC3, 0xCB, 0xF5, 0x41, 0xFF, 0x7B, 0xF7, 0x21, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0xBF, 0xCC, 0xF2, 0x40, 0xFD, 0x7C, 0xF7, 0x22, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x7A, 0x46, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00 -}; - -// Data for compression type 0x07 -static unsigned char ByteToWeight_07[] = -{ - 0xC3, 0xD9, 0xEF, 0x3D, 0xF9, 0x7C, 0xE9, 0x1E, 0xFD, 0xAB, 0xF1, 0x2C, 0xFC, 0x5B, 0xFE, 0x17, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0xBD, 0xD9, 0xEC, 0x3D, 0xF5, 0x7D, 0xE8, 0x1D, 0xFB, 0xAE, 0xF0, 0x2C, 0xFB, 0x5C, 0xFF, 0x18, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x70, 0x6C, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00 -}; - -// Data for compression type 0x08 -static unsigned char ByteToWeight_08[] = -{ - 0xBA, 0xC5, 0xDA, 0x33, 0xE3, 0x6D, 0xD8, 0x18, 0xE5, 0x94, 0xDA, 0x23, 0xDF, 0x4A, 0xD1, 0x10, - 0xEE, 0xAF, 0xE4, 0x2C, 0xEA, 0x5A, 0xDE, 0x15, 0xF4, 0x87, 0xE9, 0x21, 0xF6, 0x43, 0xFC, 0x12, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0xB0, 0xC7, 0xD8, 0x33, 0xE3, 0x6B, 0xD6, 0x18, 0xE7, 0x95, 0xD8, 0x23, 0xDB, 0x49, 0xD0, 0x11, - 0xE9, 0xB2, 0xE2, 0x2B, 0xE8, 0x5C, 0xDD, 0x15, 0xF1, 0x87, 0xE7, 0x20, 0xF7, 0x44, 0xFF, 0x13, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x5F, 0x9E, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x00 -}; - -static unsigned char * WeightTables[0x09] = -{ - ByteToWeight_00, - ByteToWeight_01, - ByteToWeight_02, - ByteToWeight_03, - ByteToWeight_04, - ByteToWeight_05, - ByteToWeight_06, - ByteToWeight_07, - ByteToWeight_08 -}; - -//----------------------------------------------------------------------------- -// Debug/diagnostics - -#ifdef _DEBUG -void DumpHuffmannTree(THTreeItem * pItem) -{ - THTreeItem * pChildLo; // Item with the lower weight - THTreeItem * pChildHi; // Item with the higher weight - - // Get the lower-weight branch - pChildLo = pItem->pChildLo; - if(pChildLo != NULL) - { - // Get the higher-weight branch - pChildHi = pChildLo->pPrev; - - // Parse the lower-weight branch - DumpHuffmannTree(pChildHi); - DumpHuffmannTree(pChildLo); - } -} -#endif - -//----------------------------------------------------------------------------- -// TInputStream functions - -TInputStream::TInputStream(void * pvInBuffer, size_t cbInBuffer) -{ - pbInBufferEnd = (unsigned char *)pvInBuffer + cbInBuffer; - pbInBuffer = (unsigned char *)pvInBuffer; - BitBuffer = 0; - BitCount = 0; -} - -// Gets 7 bits from the stream. DOES NOT remove the bits from input stream -unsigned int TInputStream::Peek7Bits() -{ - unsigned int dwReloadByte = 0; - - // If there is not enough bits to get the value, - // we have to add 8 more bits from the input buffer - if(BitCount < 7) - { - dwReloadByte = *pbInBuffer++; - BitBuffer |= dwReloadByte << BitCount; - BitCount += 8; - } - - // Return the first available 7 bits. DO NOT remove them from the input stream - return (BitBuffer & 0x7F); -} - -// Gets one bit from input stream -unsigned int TInputStream::Get1Bit() -{ - unsigned int OneBit = 0; - - // Ensure that the input stream is reloaded, if there are no bits left - if(BitCount == 0) - { - // Refill the bit buffer - BitBuffer = *pbInBuffer++; - BitCount = 8; - } - - // Copy the bit from bit buffer to the variable - OneBit = (BitBuffer & 0x01); - BitBuffer >>= 1; - BitCount--; - - return OneBit; -} - -// Gets the whole byte from the input stream. -unsigned int TInputStream::Get8Bits() -{ - unsigned int dwReloadByte = 0; - unsigned int dwOneByte = 0; - - // If there is not enough bits to get the value, - // we have to add 8 more bits from the input buffer - if(BitCount < 8) - { - dwReloadByte = *pbInBuffer++; - BitBuffer |= dwReloadByte << BitCount; - BitCount += 8; - } - - // Return the lowest 8 its - dwOneByte = (BitBuffer & 0xFF); - BitBuffer >>= 8; - BitCount -= 8; - return dwOneByte; -} - -void TInputStream::SkipBits(unsigned int dwBitsToSkip) -{ - unsigned int dwReloadByte = 0; - - // If there is not enough bits in the buffer, - // we have to add 8 more bits from the input buffer - if(BitCount < dwBitsToSkip) - { - dwReloadByte = *pbInBuffer++; - BitBuffer |= dwReloadByte << BitCount; - BitCount += 8; - } - - // Skip the remaining bits - BitBuffer >>= dwBitsToSkip; - BitCount -= dwBitsToSkip; -} - -//----------------------------------------------------------------------------- -// TOutputStream functions - -TOutputStream::TOutputStream(void * pvOutBuffer, size_t cbOutLength) -{ - pbOutBufferEnd = (unsigned char *)pvOutBuffer + cbOutLength; - pbOutBuffer = (unsigned char *)pvOutBuffer; - BitBuffer = 0; - BitCount = 0; -} - -void TOutputStream::PutBits(unsigned int dwValue, unsigned int nBitCount) -{ - BitBuffer |= (dwValue << BitCount); - BitCount += nBitCount; - - // Flush completed bytes - while(BitCount >= 8) - { - if(pbOutBuffer < pbOutBufferEnd) - *pbOutBuffer++ = (unsigned char)BitBuffer; - - BitBuffer >>= 8; - BitCount -= 8; - } -} - -void TOutputStream::Flush() -{ - while(BitCount != 0) - { - if(pbOutBuffer < pbOutBufferEnd) - *pbOutBuffer++ = (unsigned char)BitBuffer; - - BitBuffer >>= 8; - BitCount -= ((BitCount > 8) ? 8 : BitCount); - } -} - -//----------------------------------------------------------------------------- -// Methods of the THTreeItem struct - -void THTreeItem::RemoveItem() -{ - if(pNext != NULL) - { - pPrev->pNext = pNext; - pNext->pPrev = pPrev; - pNext = pPrev = NULL; - } -} - -//----------------------------------------------------------------------------- -// THuffmannTree class functions - -THuffmannTree::THuffmannTree(bool bCompression) -{ - pFirst = pLast = LIST_HEAD(); - MinValidValue = 1; - ItemsUsed = 0; - bIsCmp0 = 0; - - memset(ItemsByByte, 0, sizeof(ItemsByByte)); - - // If we are going to decompress data, we need to invalidate all item links - // We do so by zeroing their ValidValue, so it becomes lower MinValidValue - if(bCompression == false) - { - memset(QuickLinks, 0, sizeof(QuickLinks)); - } -} - -THuffmannTree::~THuffmannTree() -{ - // Our Huffmann tree does not use any memory allocations, - // so we don't need to do eny code in the destructor -} - -void THuffmannTree::LinkTwoItems(THTreeItem * pItem1, THTreeItem * pItem2) -{ - pItem2->pNext = pItem1->pNext; - pItem2->pPrev = pItem1->pNext->pPrev; - pItem1->pNext->pPrev = pItem2; - pItem1->pNext = pItem2; -} - -// Inserts item into the tree (?) -void THuffmannTree::InsertItem(THTreeItem * pNewItem, TInsertPoint InsertPoint, THTreeItem * pInsertPoint) -{ - // Remove the item from the tree - pNewItem->RemoveItem(); - - if(pInsertPoint == NULL) - pInsertPoint = LIST_HEAD(); - - switch(InsertPoint) - { - case InsertAfter: - LinkTwoItems(pInsertPoint, pNewItem); - return; - - case InsertBefore: - pNewItem->pNext = pInsertPoint; // Set next item (or pointer to pointer to first item) - pNewItem->pPrev = pInsertPoint->pPrev; // Set prev item (or last item in the tree) - pInsertPoint->pPrev->pNext = pNewItem; - pInsertPoint->pPrev = pNewItem; // Set the next/last item - return; - } -} - -THTreeItem * THuffmannTree::FindHigherOrEqualItem(THTreeItem * pItem, unsigned int Weight) -{ - // Parse all existing items - if(pItem != NULL) - { - while(pItem != LIST_HEAD()) - { - if(pItem->Weight >= Weight) - return pItem; - - pItem = pItem->pPrev; - } - } - - // If not found, we just get the first item - return LIST_HEAD(); -} - -THTreeItem * THuffmannTree::CreateNewItem(unsigned int DecompressedValue, unsigned int Weight, TInsertPoint InsertPoint) -{ - THTreeItem * pNewItem = NULL; - - // Don't let the item buffer run out of space - if(ItemsUsed < HUFF_ITEM_COUNT) - { - // Allocate new item from the item pool - pNewItem = &ItemBuffer[ItemsUsed++]; - - // Insert this item to the top of the tree - InsertItem(pNewItem, InsertPoint, NULL); - - // Fill the rest of the item - pNewItem->DecompressedValue = DecompressedValue; - pNewItem->Weight = Weight; - pNewItem->pParent = NULL; - pNewItem->pChildLo = NULL; - } - - return pNewItem; -} - -unsigned int THuffmannTree::FixupItemPosByWeight(THTreeItem * pNewItem, unsigned int MaxWeight) -{ - THTreeItem * pHigherItem; - - if(pNewItem->Weight < MaxWeight) - { - // Find an item that has higher weight than this one - pHigherItem = FindHigherOrEqualItem(pLast, pNewItem->Weight); - - // Remove the item and put it to the new position - pNewItem->RemoveItem(); - LinkTwoItems(pHigherItem, pNewItem); - } - else - { - MaxWeight = pNewItem->Weight; - } - - // Return the (updated) maximum weight - return MaxWeight; -} - -// Builds Huffman tree. Called with the first 8 bits loaded from input stream -bool THuffmannTree::BuildTree(unsigned int CompressionType) -{ - THTreeItem * pNewItem; - THTreeItem * pChildLo; - THTreeItem * pChildHi; - unsigned char * WeightTable; - unsigned int MaxWeight; // [ESP+10] - The greatest character found in table - - // Clear all pointers in HTree item array - memset(ItemsByByte, 0, sizeof(ItemsByByte)); - MaxWeight = 0; - - // Ensure that the compression type is in range - if((CompressionType & 0x0F) > 0x08) - return false; - WeightTable = WeightTables[CompressionType & 0x0F]; - - // Build the linear list of entries that is sorted by byte weight - for(unsigned int i = 0; i < 0x100; i++) - { - // Skip all the bytes which are zero. - if(WeightTable[i] != 0) - { - // Create new tree item - ItemsByByte[i] = pNewItem = CreateNewItem(i, WeightTable[i], InsertAfter); - - // We need to put the item to the right place in the list - MaxWeight = FixupItemPosByWeight(pNewItem, MaxWeight); - } - } - - // Insert termination entries at the end of the list - ItemsByByte[0x100] = CreateNewItem(0x100, 1, InsertBefore); - ItemsByByte[0x101] = CreateNewItem(0x101, 1, InsertBefore); - - // Now we need to build the tree. We start at the last entry - // and go backwards to the first one - pChildLo = pLast; - - // Work as long as both children are valid - // pChildHi is child with higher weight, pChildLo is the one with lower weight - while(pChildLo != LIST_HEAD()) - { - // Also get and verify the higher-weight child - pChildHi = pChildLo->pPrev; - if(pChildHi == LIST_HEAD()) - break; - - // Create new parent item for the children - pNewItem = CreateNewItem(0, pChildHi->Weight + pChildLo->Weight, InsertAfter); - if(pNewItem == NULL) - return false; - - // Link both child items to their new parent - pChildLo->pParent = pNewItem; - pChildHi->pParent = pNewItem; - pNewItem->pChildLo = pChildLo; - - // Fixup the item's position by its weight - MaxWeight = FixupItemPosByWeight(pNewItem, MaxWeight); - - // Get the previous lower-weight child - pChildLo = pChildHi->pPrev; - } - - // Initialize the MinValidValue to 1, which invalidates all quick-link items - MinValidValue = 1; - return true; -} - -void THuffmannTree::IncWeightsAndRebalance(THTreeItem * pItem) -{ - THTreeItem * pHigherItem; // A previous item with greater or equal weight - THTreeItem * pChildHi; // The higher-weight child - THTreeItem * pChildLo; // The lower-weight child - THTreeItem * pParent; - - // Climb up the tree and increment weight of each tree item - for(; pItem != NULL; pItem = pItem->pParent) - { - // Increment the item's weight - pItem->Weight++; - - // Find a previous item with equal or greater weight, which is not equal to this item - pHigherItem = FindHigherOrEqualItem(pItem->pPrev, pItem->Weight); - pChildHi = pHigherItem->pNext; - - // If the item is not equal to the tree item, we need to rebalance the tree - if(pChildHi != pItem) - { - // Move the previous item to the RIGHT from the given item - pChildHi->RemoveItem(); - LinkTwoItems(pItem, pChildHi); - - // Move the given item AFTER the greater-weight tree item - pItem->RemoveItem(); - LinkTwoItems(pHigherItem, pItem); - - // We need to maintain the tree so that pChildHi->Weight is >= pChildLo->Weight. - // Rebalance the tree accordingly. - pChildLo = pChildHi->pParent->pChildLo; - pParent = pItem->pParent; - if(pParent->pChildLo == pItem) - pParent->pChildLo = pChildHi; - if(pChildLo == pChildHi) - pChildHi->pParent->pChildLo = pItem; - pParent = pItem->pParent; - pItem->pParent = pChildHi->pParent; - pChildHi->pParent = pParent; - - // Increment the global valid value. This invalidates all quick-link items. - MinValidValue++; - } - } -} - -bool THuffmannTree::InsertNewBranchAndRebalance(unsigned int Value1, unsigned int Value2) -{ - THTreeItem * pLastItem = pLast; - THTreeItem * pChildHi; - THTreeItem * pChildLo; - - // Create higher-weight child - pChildHi = CreateNewItem(Value1, pLastItem->Weight, InsertBefore); - if(pChildHi != NULL) - { - pChildHi->pParent = pLastItem; - ItemsByByte[Value1] = pChildHi; - - // Create lower-weight child - pChildLo = CreateNewItem(Value2, 0, InsertBefore); - if(pChildLo != NULL) - { - pChildLo->pParent = pLastItem; - pLastItem->pChildLo = pChildLo; - ItemsByByte[Value2] = pChildLo; - - IncWeightsAndRebalance(pChildLo); - return true; - } - } - - // No more space in the tree buffer - return false; -} - -void THuffmannTree::EncodeOneByte(TOutputStream * os, THTreeItem * pItem) -{ - THTreeItem * pParent = pItem->pParent; - unsigned int BitBuffer = 0; - unsigned int BitCount = 0; - - // Put 1's as long as there is parent - while(pParent != NULL) - { - // Fill the bit buffer - BitBuffer = (BitBuffer << 1) | ((pParent->pChildLo != pItem) ? 1 : 0); - BitCount++; - - // Move to the parent - pItem = pParent; - pParent = pParent->pParent; - } - - // Write the bits to the output stream - os->PutBits(BitBuffer, BitCount); -} - -unsigned int THuffmannTree::DecodeOneByte(TInputStream * is) -{ - THTreeItem * pItemLink = NULL; - THTreeItem * pItem; - unsigned int ItemLinkIndex; - unsigned int BitCount = 0; - - // Check for the end of the input stream - if(is->pbInBuffer >= is->pbInBufferEnd && is->BitCount < 7) - return 0x1FF; - - // Get the eventual quick-link index - ItemLinkIndex = is->Peek7Bits(); - - // Is the quick-link item valid? - if(QuickLinks[ItemLinkIndex].ValidValue > MinValidValue) - { - // If that item needs less than 7 bits, we can get decompressed value directly - if(QuickLinks[ItemLinkIndex].ValidBits <= 7) - { - is->SkipBits(QuickLinks[ItemLinkIndex].ValidBits); - return QuickLinks[ItemLinkIndex].DecompressedValue; - } - - // Otherwise we cannot get decompressed value directly - // but we can skip 7 levels of tree parsing - pItem = QuickLinks[ItemLinkIndex].pItem; - is->SkipBits(7); - } - else - { - // Just a sanity check - if(pFirst == LIST_HEAD()) - return 0x1FF; - - // We don't have the quick-link item, we need to parse the tree from its root - pItem = pFirst; - } - - // Step down the tree until we find a terminal item - while(pItem->pChildLo != NULL) - { - // If the next bit in the compressed stream is set, we get the higher-weight - // child. Otherwise, get the lower-weight child. - pItem = is->Get1Bit() ? pItem->pChildLo->pPrev : pItem->pChildLo; - BitCount++; - - // If the number of loaded bits reached 7, - // remember the current item for storing into quick-link item array - if(BitCount == 7) - pItemLink = pItem; - } - - // If we didn't get the item from the quick-link array, - // set the entry in it - if(QuickLinks[ItemLinkIndex].ValidValue < MinValidValue) - { - // If the current compressed byte was more than 7 bits, - // set a quick-link item with pointer to tree item - if(BitCount > 7) - { - QuickLinks[ItemLinkIndex].ValidValue = MinValidValue; - QuickLinks[ItemLinkIndex].ValidBits = BitCount; - QuickLinks[ItemLinkIndex].pItem = pItemLink; - } - else - { - // Limit the quick-decompress item to lower amount of bits - // Coverity fix 84457: (x >> 32) has undefined behavior - ItemLinkIndex = (BitCount != 0) ? ItemLinkIndex & (0xFFFFFFFF >> (32 - BitCount)) : 0; - while(ItemLinkIndex < LINK_ITEM_COUNT) - { - // Fill the quick-decompress item - QuickLinks[ItemLinkIndex].ValidValue = MinValidValue; - QuickLinks[ItemLinkIndex].ValidBits = BitCount; - QuickLinks[ItemLinkIndex].DecompressedValue = pItem->DecompressedValue; - - // Increment the index - ItemLinkIndex += (1 << BitCount); - } - } - } - - // Return the decompressed value from the found item - return pItem->DecompressedValue; -} - -unsigned int THuffmannTree::Compress(TOutputStream * os, void * pvInBuffer, int cbInBuffer, int CompressionType) -{ - unsigned char * pbInBufferEnd = (unsigned char *)pvInBuffer + cbInBuffer; - unsigned char * pbInBuffer = (unsigned char *)pvInBuffer; - unsigned char * pbOutBuff = os->pbOutBuffer; - unsigned char InputByte; - - if(!BuildTree(CompressionType)) - return 0; - bIsCmp0 = (CompressionType == 0); - - // Store the compression type into output buffer - os->PutBits(CompressionType, 8); - - // Process the entire input buffer - while(pbInBuffer < pbInBufferEnd) - { - // Get the (next) byte from the input buffer - InputByte = *pbInBuffer++; - - // Do we have an item for such input value? - if(ItemsByByte[InputByte] == NULL) - { - // Encode the relationship - EncodeOneByte(os, ItemsByByte[0x101]); - - // Store the loaded byte into output stream - os->PutBits(InputByte, 8); - - if(!InsertNewBranchAndRebalance(pLast->DecompressedValue, InputByte)) - return 0; - - if(bIsCmp0) - { - IncWeightsAndRebalance(ItemsByByte[InputByte]); - continue; - } - - IncWeightsAndRebalance(ItemsByByte[InputByte]); - } - else - { - EncodeOneByte(os, ItemsByByte[InputByte]); - } - - if(bIsCmp0) - { - IncWeightsAndRebalance(ItemsByByte[InputByte]); - } - } - - // Put the termination mark to the compressed stream - EncodeOneByte(os, ItemsByByte[0x100]); - - // Flush the remaining bits - os->Flush(); - return (unsigned int)(os->pbOutBuffer - pbOutBuff); -} - -// Decompression using Huffman tree (1500E450) -unsigned int THuffmannTree::Decompress(void * pvOutBuffer, unsigned int cbOutLength, TInputStream * is) -{ - unsigned char * pbOutBufferEnd = (unsigned char *)pvOutBuffer + cbOutLength; - unsigned char * pbOutBuffer = (unsigned char *)pvOutBuffer; - unsigned int DecompressedValue = 0; - unsigned int CompressionType = 0; - - // Test the output length. Must not be NULL. - if(cbOutLength == 0) - return 0; - - // Get the compression type from the input stream - CompressionType = is->Get8Bits(); - bIsCmp0 = (CompressionType == 0) ? 1 : 0; - - // Build the Huffman tree - if(!BuildTree(CompressionType)) - return 0; - - // Process the entire input buffer until end of the stream - while((DecompressedValue = DecodeOneByte(is)) != 0x100) - { - // Did an error occur? - if(DecompressedValue == 0x1FF) // An error occurred - return 0; - - // Huffman tree needs to be modified - if(DecompressedValue == 0x101) - { - // The decompressed byte is stored in the next 8 bits - DecompressedValue = is->Get8Bits(); - - if(!InsertNewBranchAndRebalance(pLast->DecompressedValue, DecompressedValue)) - return 0; - - if(bIsCmp0 == 0) - IncWeightsAndRebalance(ItemsByByte[DecompressedValue]); - } - - // A byte successfully decoded - store it in the output stream - *pbOutBuffer++ = (unsigned char)DecompressedValue; - if(pbOutBuffer >= pbOutBufferEnd) - break; - - if(bIsCmp0) - { - IncWeightsAndRebalance(ItemsByByte[DecompressedValue]); - } - } - - return (unsigned int)(pbOutBuffer - (unsigned char *)pvOutBuffer); -} - diff --git a/app/jni/src/libultraship/extern/StormLib/src/huffman/huff.h b/app/jni/src/libultraship/extern/StormLib/src/huffman/huff.h deleted file mode 100644 index b75acbb..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/huffman/huff.h +++ /dev/null @@ -1,143 +0,0 @@ -/*****************************************************************************/ -/* huffman.h Copyright (c) Ladislav Zezula 2003 */ -/*---------------------------------------------------------------------------*/ -/* Description : */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* xx.xx.xx 1.00 Lad The first version of huffman.h */ -/* 03.05.03 2.00 Lad Added compression */ -/* 08.12.03 2.01 Dan High-memory handling (> 0x80000000) */ -/*****************************************************************************/ - -#ifndef __HUFFMAN_H__ -#define __HUFFMAN_H__ - -//----------------------------------------------------------------------------- -// Defines - -#define HUFF_ITEM_COUNT 0x203 // Number of items in the item pool -#define LINK_ITEM_COUNT 0x80 // Maximum number of quick-link items - -//----------------------------------------------------------------------------- -// Structures and classes - -// Input stream for Huffmann decompression -class TInputStream -{ - public: - - TInputStream(void * pvInBuffer, size_t cbInBuffer); - unsigned int Get1Bit(); - unsigned int Peek7Bits(); - unsigned int Get8Bits(); - void SkipBits(unsigned int BitCount); - - unsigned char * pbInBufferEnd; // End position in the the input buffer - unsigned char * pbInBuffer; // Current position in the the input buffer - unsigned int BitBuffer; // Input bit buffer - unsigned int BitCount; // Number of bits remaining in 'dwBitBuff' -}; - - -// Output stream for Huffmann compression -class TOutputStream -{ - public: - - TOutputStream(void * pvOutBuffer, size_t cbOutLength); - void PutBits(unsigned int dwValue, unsigned int nBitCount); - void Flush(); - - unsigned char * pbOutBufferEnd; // End position in the output buffer - unsigned char * pbOutBuffer; // Current position in the output buffer - unsigned int BitBuffer; // Bit buffer - unsigned int BitCount; // Number of bits in the bit buffer -}; - -// A virtual tree item that represents the head of the item list -#define LIST_HEAD() ((THTreeItem *)(&pFirst)) - -enum TInsertPoint -{ - InsertAfter = 1, - InsertBefore = 2 -}; - -// Huffmann tree item -struct THTreeItem -{ - THTreeItem() { pPrev = pNext = NULL; DecompressedValue = 0; Weight = 0; pParent = pChildLo = NULL; } -// ~THTreeItem() { RemoveItem(); } - - void RemoveItem(); -// void RemoveEntry(); - - THTreeItem * pNext; // Pointer to lower-weight tree item - THTreeItem * pPrev; // Pointer to higher-weight item - unsigned int DecompressedValue; // 08 - Decompressed byte value (also index in the array) - unsigned int Weight; // 0C - Weight - THTreeItem * pParent; // 10 - Pointer to parent item (NULL if none) - THTreeItem * pChildLo; // 14 - Pointer to the child with lower-weight child ("left child") -}; - - -// Structure used for quick navigating in the huffmann tree. -// Allows skipping up to 7 bits in the compressed stream, thus -// decompressing a bit faster. Sometimes it can even get the decompressed -// byte directly. -struct TQuickLink -{ - unsigned int ValidValue; // If greater than THuffmannTree::MinValidValue, the entry is valid - unsigned int ValidBits; // Number of bits that are valid for this item link - union - { - THTreeItem * pItem; // Pointer to the item within the Huffmann tree - unsigned int DecompressedValue; // Value for direct decompression - }; -}; - - -// Structure for Huffman tree (Size 0x3674 bytes). Because I'm not expert -// for the decompression, I do not know actually if the class is really a Hufmann -// tree. If someone knows the decompression details, please let me know -class THuffmannTree -{ - public: - - THuffmannTree(bool bCompression); - ~THuffmannTree(); - - void LinkTwoItems(THTreeItem * pItem1, THTreeItem * pItem2); - void InsertItem(THTreeItem * item, TInsertPoint InsertPoint, THTreeItem * item2); - - THTreeItem * FindHigherOrEqualItem(THTreeItem * pItem, unsigned int Weight); - THTreeItem * CreateNewItem(unsigned int DecompressedValue, unsigned int Weight, TInsertPoint InsertPoint); - - unsigned int FixupItemPosByWeight(THTreeItem * pItem, unsigned int MaxWeight); - bool BuildTree(unsigned int CompressionType); - - void IncWeightsAndRebalance(THTreeItem * pItem); - bool InsertNewBranchAndRebalance(unsigned int Value1, unsigned int Value2); - - void EncodeOneByte(TOutputStream * os, THTreeItem * pItem); - unsigned int DecodeOneByte(TInputStream * is); - - unsigned int Compress(TOutputStream * os, void * pvInBuffer, int cbInBuffer, int nCmpType); - unsigned int Decompress(void * pvOutBuffer, unsigned int cbOutLength, TInputStream * is); - - THTreeItem ItemBuffer[HUFF_ITEM_COUNT]; // Buffer for tree items. No memory allocation is needed - unsigned int ItemsUsed; // Number of tree items used from ItemBuffer - - // Head of the linear item list - THTreeItem * pFirst; // Pointer to the highest weight item - THTreeItem * pLast; // Pointer to the lowest weight item - - THTreeItem * ItemsByByte[0x102]; // Array of item pointers, one for each possible byte value - TQuickLink QuickLinks[LINK_ITEM_COUNT]; // Array of quick-link items - - unsigned int MinValidValue; // A minimum value of TQDecompress::ValidValue to be considered valid - unsigned int bIsCmp0; // 1 if compression type 0 -}; - -#endif // __HUFFMAN_H__ diff --git a/app/jni/src/libultraship/extern/StormLib/src/jenkins/lookup.h b/app/jni/src/libultraship/extern/StormLib/src/jenkins/lookup.h deleted file mode 100644 index 54ccc97..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/jenkins/lookup.h +++ /dev/null @@ -1,24 +0,0 @@ -#ifndef __LOOKUP3_H__ -#define __LOOKUP3_H__ - -#ifdef WIN32 -typedef unsigned char uint8_t; -typedef unsigned short uint16_t; -typedef unsigned int uint32_t; -#else -#include /* defines uint32_t etc */ -#endif - -#ifdef __cplusplus -extern "C" -{ -#endif - -uint32_t hashlittle(const void *key, size_t length, uint32_t initval); -void hashlittle2(const void *key, size_t length, uint32_t *pc, uint32_t *pb); - -#ifdef __cplusplus -} -#endif - -#endif // __LOOKUP3_H__ diff --git a/app/jni/src/libultraship/extern/StormLib/src/jenkins/lookup3.c b/app/jni/src/libultraship/extern/StormLib/src/jenkins/lookup3.c deleted file mode 100644 index 6af56b4..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/jenkins/lookup3.c +++ /dev/null @@ -1,1003 +0,0 @@ -/* -------------------------------------------------------------------------------- -lookup3.c, by Bob Jenkins, May 2006, Public Domain. - -These are functions for producing 32-bit hashes for hash table lookup. -hashword(), hashlittle(), hashlittle2(), hashbig(), mix(), and final() -are externally useful functions. Routines to test the hash are included -if SELF_TEST is defined. You can use this free for any purpose. It's in -the public domain. It has no warranty. - -You probably want to use hashlittle(). hashlittle() and hashbig() -hash byte arrays. hashlittle() is is faster than hashbig() on -little-endian machines. Intel and AMD are little-endian machines. -On second thought, you probably want hashlittle2(), which is identical to -hashlittle() except it returns two 32-bit hashes for the price of one. -You could implement hashbig2() if you wanted but I haven't bothered here. - -If you want to find a hash of, say, exactly 7 integers, do - a = i1; b = i2; c = i3; - mix(a,b,c); - a += i4; b += i5; c += i6; - mix(a,b,c); - a += i7; - final(a,b,c); -then use c as the hash value. If you have a variable length array of -4-byte integers to hash, use hashword(). If you have a byte array (like -a character string), use hashlittle(). If you have several byte arrays, or -a mix of things, see the comments above hashlittle(). - -Why is this so big? I read 12 bytes at a time into 3 4-byte integers, -then mix those integers. This is fast (you can do a lot more thorough -mixing with 12*3 instructions on 3 integers than you can with 3 instructions -on 1 byte), but shoehorning those bytes into integers efficiently is messy. -------------------------------------------------------------------------------- -*/ -//#define SELF_TEST 1 - -#include /* defines printf for tests */ -#include /* defines time_t for timings in the test */ - -#ifdef linux -#include /* attempt to define endianness */ -#include /* attempt to define endianness */ -#endif - -#include "lookup.h" - -/* - * My best guess at if you are big-endian or little-endian. This may - * need adjustment. - */ -#if (defined(__BYTE_ORDER) && defined(__LITTLE_ENDIAN) && \ - __BYTE_ORDER == __LITTLE_ENDIAN) || \ - (defined(i386) || defined(__i386__) || defined(__i486__) || \ - defined(__i586__) || defined(__i686__) || defined(vax) || defined(MIPSEL)) -# define HASH_LITTLE_ENDIAN 1 -# define HASH_BIG_ENDIAN 0 -#elif (defined(__BYTE_ORDER) && defined(__BIG_ENDIAN) && \ - __BYTE_ORDER == __BIG_ENDIAN) || \ - (defined(sparc) || defined(POWERPC) || defined(mc68000) || defined(sel)) -# define HASH_LITTLE_ENDIAN 0 -# define HASH_BIG_ENDIAN 1 -#else -# define HASH_LITTLE_ENDIAN 0 -# define HASH_BIG_ENDIAN 0 -#endif - -#define hashsize(n) ((uint32_t)1<<(n)) -#define hashmask(n) (hashsize(n)-1) -#define rot(x,k) (((x)<<(k)) | ((x)>>(32-(k)))) - -/* -------------------------------------------------------------------------------- -mix -- mix 3 32-bit values reversibly. - -This is reversible, so any information in (a,b,c) before mix() is -still in (a,b,c) after mix(). - -If four pairs of (a,b,c) inputs are run through mix(), or through -mix() in reverse, there are at least 32 bits of the output that -are sometimes the same for one pair and different for another pair. -This was tested for: -* pairs that differed by one bit, by two bits, in any combination - of top bits of (a,b,c), or in any combination of bottom bits of - (a,b,c). -* "differ" is defined as +, -, ^, or ~^. For + and -, I transformed - the output delta to a Gray code (a^(a>>1)) so a string of 1's (as - is commonly produced by subtraction) look like a single 1-bit - difference. -* the base values were pseudorandom, all zero but one bit set, or - all zero plus a counter that starts at zero. - -Some k values for my "a-=c; a^=rot(c,k); c+=b;" arrangement that -satisfy this are - 4 6 8 16 19 4 - 9 15 3 18 27 15 - 14 9 3 7 17 3 -Well, "9 15 3 18 27 15" didn't quite get 32 bits diffing -for "differ" defined as + with a one-bit base and a two-bit delta. I -used http://burtleburtle.net/bob/hash/avalanche.html to choose -the operations, constants, and arrangements of the variables. - -This does not achieve avalanche. There are input bits of (a,b,c) -that fail to affect some output bits of (a,b,c), especially of a. The -most thoroughly mixed value is c, but it doesn't really even achieve -avalanche in c. - -This allows some parallelism. Read-after-writes are good at doubling -the number of bits affected, so the goal of mixing pulls in the opposite -direction as the goal of parallelism. I did what I could. Rotates -seem to cost as much as shifts on every machine I could lay my hands -on, and rotates are much kinder to the top and bottom bits, so I used -rotates. -------------------------------------------------------------------------------- -*/ -#define mix(a,b,c) \ -{ \ - a -= c; a ^= rot(c, 4); c += b; \ - b -= a; b ^= rot(a, 6); a += c; \ - c -= b; c ^= rot(b, 8); b += a; \ - a -= c; a ^= rot(c,16); c += b; \ - b -= a; b ^= rot(a,19); a += c; \ - c -= b; c ^= rot(b, 4); b += a; \ -} - -/* -------------------------------------------------------------------------------- -final -- final mixing of 3 32-bit values (a,b,c) into c - -Pairs of (a,b,c) values differing in only a few bits will usually -produce values of c that look totally different. This was tested for -* pairs that differed by one bit, by two bits, in any combination - of top bits of (a,b,c), or in any combination of bottom bits of - (a,b,c). -* "differ" is defined as +, -, ^, or ~^. For + and -, I transformed - the output delta to a Gray code (a^(a>>1)) so a string of 1's (as - is commonly produced by subtraction) look like a single 1-bit - difference. -* the base values were pseudorandom, all zero but one bit set, or - all zero plus a counter that starts at zero. - -These constants passed: - 14 11 25 16 4 14 24 - 12 14 25 16 4 14 24 -and these came close: - 4 8 15 26 3 22 24 - 10 8 15 26 3 22 24 - 11 8 15 26 3 22 24 -------------------------------------------------------------------------------- -*/ -#define final(a,b,c) \ -{ \ - c ^= b; c -= rot(b,14); \ - a ^= c; a -= rot(c,11); \ - b ^= a; b -= rot(a,25); \ - c ^= b; c -= rot(b,16); \ - a ^= c; a -= rot(c,4); \ - b ^= a; b -= rot(a,14); \ - c ^= b; c -= rot(b,24); \ -} - -/* --------------------------------------------------------------------- - This works on all machines. To be useful, it requires - -- that the key be an array of uint32_t's, and - -- that the length be the number of uint32_t's in the key - - The function hashword() is identical to hashlittle() on little-endian - machines, and identical to hashbig() on big-endian machines, - except that the length has to be measured in uint32_ts rather than in - bytes. hashlittle() is more complicated than hashword() only because - hashlittle() has to dance around fitting the key bytes into registers. --------------------------------------------------------------------- -*/ -uint32_t hashword( -const uint32_t *k, /* the key, an array of uint32_t values */ -size_t length, /* the length of the key, in uint32_ts */ -uint32_t initval) /* the previous hash, or an arbitrary value */ -{ - uint32_t a,b,c; - - /* Set up the internal state */ - a = b = c = 0xdeadbeef + (((uint32_t)length)<<2) + initval; - - /*------------------------------------------------- handle most of the key */ - while (length > 3) - { - a += k[0]; - b += k[1]; - c += k[2]; - mix(a,b,c); - length -= 3; - k += 3; - } - - /*------------------------------------------- handle the last 3 uint32_t's */ - switch(length) /* all the case statements fall through */ - { - case 3 : c+=k[2]; - case 2 : b+=k[1]; - case 1 : a+=k[0]; - final(a,b,c); - case 0: /* case 0: nothing left to add */ - break; - } - /*------------------------------------------------------ report the result */ - return c; -} - - -/* --------------------------------------------------------------------- -hashword2() -- same as hashword(), but take two seeds and return two -32-bit values. pc and pb must both be nonnull, and *pc and *pb must -both be initialized with seeds. If you pass in (*pb)==0, the output -(*pc) will be the same as the return value from hashword(). --------------------------------------------------------------------- -*/ -void hashword2 ( -const uint32_t *k, /* the key, an array of uint32_t values */ -size_t length, /* the length of the key, in uint32_ts */ -uint32_t *pc, /* IN: seed OUT: primary hash value */ -uint32_t *pb) /* IN: more seed OUT: secondary hash value */ -{ - uint32_t a,b,c; - - /* Set up the internal state */ - a = b = c = 0xdeadbeef + ((uint32_t)(length<<2)) + *pc; - c += *pb; - - /*------------------------------------------------- handle most of the key */ - while (length > 3) - { - a += k[0]; - b += k[1]; - c += k[2]; - mix(a,b,c); - length -= 3; - k += 3; - } - - /*------------------------------------------- handle the last 3 uint32_t's */ - switch(length) /* all the case statements fall through */ - { - case 3 : c+=k[2]; - case 2 : b+=k[1]; - case 1 : a+=k[0]; - final(a,b,c); - case 0: /* case 0: nothing left to add */ - break; - } - /*------------------------------------------------------ report the result */ - *pc=c; *pb=b; -} - - -/* -------------------------------------------------------------------------------- -hashlittle() -- hash a variable-length key into a 32-bit value - k : the key (the unaligned variable-length array of bytes) - length : the length of the key, counting by bytes - initval : can be any 4-byte value -Returns a 32-bit value. Every bit of the key affects every bit of -the return value. Two keys differing by one or two bits will have -totally different hash values. - -The best hash table sizes are powers of 2. There is no need to do -mod a prime (mod is sooo slow!). If you need less than 32 bits, -use a bitmask. For example, if you need only 10 bits, do - h = (h & hashmask(10)); -In which case, the hash table should have hashsize(10) elements. - -If you are hashing n strings (uint8_t **)k, do it like this: - for (i=0, h=0; i 12) - { - a += k[0]; - b += k[1]; - c += k[2]; - mix(a,b,c); - length -= 12; - k += 3; - } - - /*----------------------------- handle the last (probably partial) block */ - /* - * "k[2]&0xffffff" actually reads beyond the end of the string, but - * then masks off the part it's not allowed to read. Because the - * string is aligned, the masked-off tail is in the same word as the - * rest of the string. Every machine with memory protection I've seen - * does it on word boundaries, so is OK with this. But VALGRIND will - * still catch it and complain. The masking trick does make the hash - * noticably faster for short strings (like English words). - */ -#ifndef VALGRIND - - switch(length) - { - case 12: c+=k[2]; b+=k[1]; a+=k[0]; break; - case 11: c+=k[2]&0xffffff; b+=k[1]; a+=k[0]; break; - case 10: c+=k[2]&0xffff; b+=k[1]; a+=k[0]; break; - case 9 : c+=k[2]&0xff; b+=k[1]; a+=k[0]; break; - case 8 : b+=k[1]; a+=k[0]; break; - case 7 : b+=k[1]&0xffffff; a+=k[0]; break; - case 6 : b+=k[1]&0xffff; a+=k[0]; break; - case 5 : b+=k[1]&0xff; a+=k[0]; break; - case 4 : a+=k[0]; break; - case 3 : a+=k[0]&0xffffff; break; - case 2 : a+=k[0]&0xffff; break; - case 1 : a+=k[0]&0xff; break; - case 0 : return c; /* zero length strings require no mixing */ - } - -#else /* make valgrind happy */ - - k8 = (const uint8_t *)k; - switch(length) - { - case 12: c+=k[2]; b+=k[1]; a+=k[0]; break; - case 11: c+=((uint32_t)k8[10])<<16; /* fall through */ - case 10: c+=((uint32_t)k8[9])<<8; /* fall through */ - case 9 : c+=k8[8]; /* fall through */ - case 8 : b+=k[1]; a+=k[0]; break; - case 7 : b+=((uint32_t)k8[6])<<16; /* fall through */ - case 6 : b+=((uint32_t)k8[5])<<8; /* fall through */ - case 5 : b+=k8[4]; /* fall through */ - case 4 : a+=k[0]; break; - case 3 : a+=((uint32_t)k8[2])<<16; /* fall through */ - case 2 : a+=((uint32_t)k8[1])<<8; /* fall through */ - case 1 : a+=k8[0]; break; - case 0 : return c; - } - -#endif /* !valgrind */ - - } else if (HASH_LITTLE_ENDIAN && ((u.i & 0x1) == 0)) { - const uint16_t *k = (const uint16_t *)key; /* read 16-bit chunks */ - const uint8_t *k8; - - /*--------------- all but last block: aligned reads and different mixing */ - while (length > 12) - { - a += k[0] + (((uint32_t)k[1])<<16); - b += k[2] + (((uint32_t)k[3])<<16); - c += k[4] + (((uint32_t)k[5])<<16); - mix(a,b,c); - length -= 12; - k += 6; - } - - /*----------------------------- handle the last (probably partial) block */ - k8 = (const uint8_t *)k; - switch(length) - { - case 12: c+=k[4]+(((uint32_t)k[5])<<16); - b+=k[2]+(((uint32_t)k[3])<<16); - a+=k[0]+(((uint32_t)k[1])<<16); - break; - case 11: c+=((uint32_t)k8[10])<<16; /* fall through */ - case 10: c+=k[4]; - b+=k[2]+(((uint32_t)k[3])<<16); - a+=k[0]+(((uint32_t)k[1])<<16); - break; - case 9 : c+=k8[8]; /* fall through */ - case 8 : b+=k[2]+(((uint32_t)k[3])<<16); - a+=k[0]+(((uint32_t)k[1])<<16); - break; - case 7 : b+=((uint32_t)k8[6])<<16; /* fall through */ - case 6 : b+=k[2]; - a+=k[0]+(((uint32_t)k[1])<<16); - break; - case 5 : b+=k8[4]; /* fall through */ - case 4 : a+=k[0]+(((uint32_t)k[1])<<16); - break; - case 3 : a+=((uint32_t)k8[2])<<16; /* fall through */ - case 2 : a+=k[0]; - break; - case 1 : a+=k8[0]; - break; - case 0 : return c; /* zero length requires no mixing */ - } - - } else { /* need to read the key one byte at a time */ - const uint8_t *k = (const uint8_t *)key; - - /*--------------- all but the last block: affect some 32 bits of (a,b,c) */ - while (length > 12) - { - a += k[0]; - a += ((uint32_t)k[1])<<8; - a += ((uint32_t)k[2])<<16; - a += ((uint32_t)k[3])<<24; - b += k[4]; - b += ((uint32_t)k[5])<<8; - b += ((uint32_t)k[6])<<16; - b += ((uint32_t)k[7])<<24; - c += k[8]; - c += ((uint32_t)k[9])<<8; - c += ((uint32_t)k[10])<<16; - c += ((uint32_t)k[11])<<24; - mix(a,b,c); - length -= 12; - k += 12; - } - - /*-------------------------------- last block: affect all 32 bits of (c) */ - switch(length) /* all the case statements fall through */ - { - case 12: c+=((uint32_t)k[11])<<24; - case 11: c+=((uint32_t)k[10])<<16; - case 10: c+=((uint32_t)k[9])<<8; - case 9 : c+=k[8]; - case 8 : b+=((uint32_t)k[7])<<24; - case 7 : b+=((uint32_t)k[6])<<16; - case 6 : b+=((uint32_t)k[5])<<8; - case 5 : b+=k[4]; - case 4 : a+=((uint32_t)k[3])<<24; - case 3 : a+=((uint32_t)k[2])<<16; - case 2 : a+=((uint32_t)k[1])<<8; - case 1 : a+=k[0]; - break; - case 0 : return c; - } - } - - final(a,b,c); - return c; -} - - -/* - * hashlittle2: return 2 32-bit hash values - * - * This is identical to hashlittle(), except it returns two 32-bit hash - * values instead of just one. This is good enough for hash table - * lookup with 2^^64 buckets, or if you want a second hash if you're not - * happy with the first, or if you want a probably-unique 64-bit ID for - * the key. *pc is better mixed than *pb, so use *pc first. If you want - * a 64-bit value do something like "*pc + (((uint64_t)*pb)<<32)". - */ -void hashlittle2( - const void *key, /* the key to hash */ - size_t length, /* length of the key */ - uint32_t *pc, /* IN: primary initval, OUT: primary hash */ - uint32_t *pb) /* IN: secondary initval, OUT: secondary hash */ -{ - uint32_t a,b,c; /* internal state */ - union { const void *ptr; size_t i; } u; /* needed for Mac Powerbook G4 */ - - /* Set up the internal state */ - a = b = c = 0xdeadbeef + ((uint32_t)length) + *pc; - c += *pb; - - u.ptr = key; - if (HASH_LITTLE_ENDIAN && ((u.i & 0x3) == 0)) { - const uint32_t *k = (const uint32_t *)key; /* read 32-bit chunks */ - const uint8_t *k8; - - /*------ all but last block: aligned reads and affect 32 bits of (a,b,c) */ - while (length > 12) - { - a += k[0]; - b += k[1]; - c += k[2]; - mix(a,b,c); - length -= 12; - k += 3; - } - - /*----------------------------- handle the last (probably partial) block */ - /* - * "k[2]&0xffffff" actually reads beyond the end of the string, but - * then masks off the part it's not allowed to read. Because the - * string is aligned, the masked-off tail is in the same word as the - * rest of the string. Every machine with memory protection I've seen - * does it on word boundaries, so is OK with this. But VALGRIND will - * still catch it and complain. The masking trick does make the hash - * noticably faster for short strings (like English words). - */ -#ifndef VALGRIND - - switch(length) - { - case 12: c+=k[2]; b+=k[1]; a+=k[0]; break; - case 11: c+=k[2]&0xffffff; b+=k[1]; a+=k[0]; break; - case 10: c+=k[2]&0xffff; b+=k[1]; a+=k[0]; break; - case 9 : c+=k[2]&0xff; b+=k[1]; a+=k[0]; break; - case 8 : b+=k[1]; a+=k[0]; break; - case 7 : b+=k[1]&0xffffff; a+=k[0]; break; - case 6 : b+=k[1]&0xffff; a+=k[0]; break; - case 5 : b+=k[1]&0xff; a+=k[0]; break; - case 4 : a+=k[0]; break; - case 3 : a+=k[0]&0xffffff; break; - case 2 : a+=k[0]&0xffff; break; - case 1 : a+=k[0]&0xff; break; - case 0 : *pc=c; *pb=b; return; /* zero length strings require no mixing */ - } - -#else /* make valgrind happy */ - - k8 = (const uint8_t *)k; - switch(length) - { - case 12: c+=k[2]; b+=k[1]; a+=k[0]; break; - case 11: c+=((uint32_t)k8[10])<<16; /* fall through */ - case 10: c+=((uint32_t)k8[9])<<8; /* fall through */ - case 9 : c+=k8[8]; /* fall through */ - case 8 : b+=k[1]; a+=k[0]; break; - case 7 : b+=((uint32_t)k8[6])<<16; /* fall through */ - case 6 : b+=((uint32_t)k8[5])<<8; /* fall through */ - case 5 : b+=k8[4]; /* fall through */ - case 4 : a+=k[0]; break; - case 3 : a+=((uint32_t)k8[2])<<16; /* fall through */ - case 2 : a+=((uint32_t)k8[1])<<8; /* fall through */ - case 1 : a+=k8[0]; break; - case 0 : *pc=c; *pb=b; return; /* zero length strings require no mixing */ - } - -#endif /* !valgrind */ - - } else if (HASH_LITTLE_ENDIAN && ((u.i & 0x1) == 0)) { - const uint16_t *k = (const uint16_t *)key; /* read 16-bit chunks */ - const uint8_t *k8; - - /*--------------- all but last block: aligned reads and different mixing */ - while (length > 12) - { - a += k[0] + (((uint32_t)k[1])<<16); - b += k[2] + (((uint32_t)k[3])<<16); - c += k[4] + (((uint32_t)k[5])<<16); - mix(a,b,c); - length -= 12; - k += 6; - } - - /*----------------------------- handle the last (probably partial) block */ - k8 = (const uint8_t *)k; - switch(length) - { - case 12: c+=k[4]+(((uint32_t)k[5])<<16); - b+=k[2]+(((uint32_t)k[3])<<16); - a+=k[0]+(((uint32_t)k[1])<<16); - break; - case 11: c+=((uint32_t)k8[10])<<16; /* fall through */ - case 10: c+=k[4]; - b+=k[2]+(((uint32_t)k[3])<<16); - a+=k[0]+(((uint32_t)k[1])<<16); - break; - case 9 : c+=k8[8]; /* fall through */ - case 8 : b+=k[2]+(((uint32_t)k[3])<<16); - a+=k[0]+(((uint32_t)k[1])<<16); - break; - case 7 : b+=((uint32_t)k8[6])<<16; /* fall through */ - case 6 : b+=k[2]; - a+=k[0]+(((uint32_t)k[1])<<16); - break; - case 5 : b+=k8[4]; /* fall through */ - case 4 : a+=k[0]+(((uint32_t)k[1])<<16); - break; - case 3 : a+=((uint32_t)k8[2])<<16; /* fall through */ - case 2 : a+=k[0]; - break; - case 1 : a+=k8[0]; - break; - case 0 : *pc=c; *pb=b; return; /* zero length strings require no mixing */ - } - - } else { /* need to read the key one byte at a time */ - const uint8_t *k = (const uint8_t *)key; - - /*--------------- all but the last block: affect some 32 bits of (a,b,c) */ - while (length > 12) - { - a += k[0]; - a += ((uint32_t)k[1])<<8; - a += ((uint32_t)k[2])<<16; - a += ((uint32_t)k[3])<<24; - b += k[4]; - b += ((uint32_t)k[5])<<8; - b += ((uint32_t)k[6])<<16; - b += ((uint32_t)k[7])<<24; - c += k[8]; - c += ((uint32_t)k[9])<<8; - c += ((uint32_t)k[10])<<16; - c += ((uint32_t)k[11])<<24; - mix(a,b,c); - length -= 12; - k += 12; - } - - /*-------------------------------- last block: affect all 32 bits of (c) */ - switch(length) /* all the case statements fall through */ - { - case 12: c+=((uint32_t)k[11])<<24; - case 11: c+=((uint32_t)k[10])<<16; - case 10: c+=((uint32_t)k[9])<<8; - case 9 : c+=k[8]; - case 8 : b+=((uint32_t)k[7])<<24; - case 7 : b+=((uint32_t)k[6])<<16; - case 6 : b+=((uint32_t)k[5])<<8; - case 5 : b+=k[4]; - case 4 : a+=((uint32_t)k[3])<<24; - case 3 : a+=((uint32_t)k[2])<<16; - case 2 : a+=((uint32_t)k[1])<<8; - case 1 : a+=k[0]; - break; - case 0 : *pc=c; *pb=b; return; /* zero length strings require no mixing */ - } - } - - final(a,b,c); - *pc=c; *pb=b; -} - - - -/* - * hashbig(): - * This is the same as hashword() on big-endian machines. It is different - * from hashlittle() on all machines. hashbig() takes advantage of - * big-endian byte ordering. - */ -uint32_t hashbig( const void *key, size_t length, uint32_t initval) -{ - uint32_t a,b,c; - union { const void *ptr; size_t i; } u; /* to cast key to (size_t) happily */ - - /* Set up the internal state */ - a = b = c = 0xdeadbeef + ((uint32_t)length) + initval; - - u.ptr = key; - if (HASH_BIG_ENDIAN && ((u.i & 0x3) == 0)) { - const uint32_t *k = (const uint32_t *)key; /* read 32-bit chunks */ - const uint8_t *k8; - - /*------ all but last block: aligned reads and affect 32 bits of (a,b,c) */ - while (length > 12) - { - a += k[0]; - b += k[1]; - c += k[2]; - mix(a,b,c); - length -= 12; - k += 3; - } - - /*----------------------------- handle the last (probably partial) block */ - /* - * "k[2]<<8" actually reads beyond the end of the string, but - * then shifts out the part it's not allowed to read. Because the - * string is aligned, the illegal read is in the same word as the - * rest of the string. Every machine with memory protection I've seen - * does it on word boundaries, so is OK with this. But VALGRIND will - * still catch it and complain. The masking trick does make the hash - * noticably faster for short strings (like English words). - */ -#ifndef VALGRIND - - switch(length) - { - case 12: c+=k[2]; b+=k[1]; a+=k[0]; break; - case 11: c+=k[2]&0xffffff00; b+=k[1]; a+=k[0]; break; - case 10: c+=k[2]&0xffff0000; b+=k[1]; a+=k[0]; break; - case 9 : c+=k[2]&0xff000000; b+=k[1]; a+=k[0]; break; - case 8 : b+=k[1]; a+=k[0]; break; - case 7 : b+=k[1]&0xffffff00; a+=k[0]; break; - case 6 : b+=k[1]&0xffff0000; a+=k[0]; break; - case 5 : b+=k[1]&0xff000000; a+=k[0]; break; - case 4 : a+=k[0]; break; - case 3 : a+=k[0]&0xffffff00; break; - case 2 : a+=k[0]&0xffff0000; break; - case 1 : a+=k[0]&0xff000000; break; - case 0 : return c; /* zero length strings require no mixing */ - } - -#else /* make valgrind happy */ - - k8 = (const uint8_t *)k; - switch(length) /* all the case statements fall through */ - { - case 12: c+=k[2]; b+=k[1]; a+=k[0]; break; - case 11: c+=((uint32_t)k8[10])<<8; /* fall through */ - case 10: c+=((uint32_t)k8[9])<<16; /* fall through */ - case 9 : c+=((uint32_t)k8[8])<<24; /* fall through */ - case 8 : b+=k[1]; a+=k[0]; break; - case 7 : b+=((uint32_t)k8[6])<<8; /* fall through */ - case 6 : b+=((uint32_t)k8[5])<<16; /* fall through */ - case 5 : b+=((uint32_t)k8[4])<<24; /* fall through */ - case 4 : a+=k[0]; break; - case 3 : a+=((uint32_t)k8[2])<<8; /* fall through */ - case 2 : a+=((uint32_t)k8[1])<<16; /* fall through */ - case 1 : a+=((uint32_t)k8[0])<<24; break; - case 0 : return c; - } - -#endif /* !VALGRIND */ - - } else { /* need to read the key one byte at a time */ - const uint8_t *k = (const uint8_t *)key; - - /*--------------- all but the last block: affect some 32 bits of (a,b,c) */ - while (length > 12) - { - a += ((uint32_t)k[0])<<24; - a += ((uint32_t)k[1])<<16; - a += ((uint32_t)k[2])<<8; - a += ((uint32_t)k[3]); - b += ((uint32_t)k[4])<<24; - b += ((uint32_t)k[5])<<16; - b += ((uint32_t)k[6])<<8; - b += ((uint32_t)k[7]); - c += ((uint32_t)k[8])<<24; - c += ((uint32_t)k[9])<<16; - c += ((uint32_t)k[10])<<8; - c += ((uint32_t)k[11]); - mix(a,b,c); - length -= 12; - k += 12; - } - - /*-------------------------------- last block: affect all 32 bits of (c) */ - switch(length) /* all the case statements fall through */ - { - case 12: c+=k[11]; - case 11: c+=((uint32_t)k[10])<<8; - case 10: c+=((uint32_t)k[9])<<16; - case 9 : c+=((uint32_t)k[8])<<24; - case 8 : b+=k[7]; - case 7 : b+=((uint32_t)k[6])<<8; - case 6 : b+=((uint32_t)k[5])<<16; - case 5 : b+=((uint32_t)k[4])<<24; - case 4 : a+=k[3]; - case 3 : a+=((uint32_t)k[2])<<8; - case 2 : a+=((uint32_t)k[1])<<16; - case 1 : a+=((uint32_t)k[0])<<24; - break; - case 0 : return c; - } - } - - final(a,b,c); - return c; -} - - -#ifdef SELF_TEST - -/* used for timings */ -void driver1() -{ - uint8_t buf[256]; - uint32_t i; - uint32_t h=0; - time_t a,z; - - time(&a); - for (i=0; i<256; ++i) buf[i] = 'x'; - for (i=0; i<1; ++i) - { - h = hashlittle(&buf[0],1,h); - } - time(&z); - if (z-a > 0) printf("time %d %.8x\n", z-a, h); -} - -/* check that every input bit changes every output bit half the time */ -#define HASHSTATE 1 -#define HASHLEN 1 -#define MAXPAIR 60 -#define MAXLEN 70 -void driver2() -{ - uint8_t qa[MAXLEN+1], qb[MAXLEN+2], *a = &qa[0], *b = &qb[1]; - uint32_t c[HASHSTATE], d[HASHSTATE], i=0, j=0, k, l, m=0, z; - uint32_t e[HASHSTATE],f[HASHSTATE],g[HASHSTATE],h[HASHSTATE]; - uint32_t x[HASHSTATE],y[HASHSTATE]; - uint32_t hlen; - - printf("No more than %d trials should ever be needed \n",MAXPAIR/2); - for (hlen=0; hlen < MAXLEN; ++hlen) - { - z=0; - for (i=0; i>(8-j)); - c[0] = hashlittle(a, hlen, m); - b[i] ^= ((k+1)<>(8-j)); - d[0] = hashlittle(b, hlen, m); - /* check every bit is 1, 0, set, and not set at least once */ - for (l=0; lz) z=k; - if (k==MAXPAIR) - { - printf("Some bit didn't change: "); - printf("%.8x %.8x %.8x %.8x %.8x %.8x ", - e[0],f[0],g[0],h[0],x[0],y[0]); - printf("i %d j %d m %d len %d\n", i, j, m, hlen); - } - if (z==MAXPAIR) goto done; - } - } - } - done: - if (z < MAXPAIR) - { - printf("Mix success %2d bytes %2d initvals ",i,m); - printf("required %d trials\n", z/2); - } - } - printf("\n"); -} - -/* Check for reading beyond the end of the buffer and alignment problems */ -void driver3() -{ - uint8_t buf[MAXLEN+20], *b; - uint32_t len; - uint8_t q[] = "This is the time for all good men to come to the aid of their country..."; - uint32_t h; - uint8_t qq[] = "xThis is the time for all good men to come to the aid of their country..."; - uint32_t i; - uint8_t qqq[] = "xxThis is the time for all good men to come to the aid of their country..."; - uint32_t j; - uint8_t qqqq[] = "xxxThis is the time for all good men to come to the aid of their country..."; - uint32_t ref,x,y; - uint8_t *p; - - printf("Endianness. These lines should all be the same (for values filled in):\n"); - printf("%.8x %.8x %.8x\n", - hashword((const uint32_t *)q, (sizeof(q)-1)/4, 13), - hashword((const uint32_t *)q, (sizeof(q)-5)/4, 13), - hashword((const uint32_t *)q, (sizeof(q)-9)/4, 13)); - p = q; - printf("%.8x %.8x %.8x %.8x %.8x %.8x %.8x %.8x %.8x %.8x %.8x %.8x\n", - hashlittle(p, sizeof(q)-1, 13), hashlittle(p, sizeof(q)-2, 13), - hashlittle(p, sizeof(q)-3, 13), hashlittle(p, sizeof(q)-4, 13), - hashlittle(p, sizeof(q)-5, 13), hashlittle(p, sizeof(q)-6, 13), - hashlittle(p, sizeof(q)-7, 13), hashlittle(p, sizeof(q)-8, 13), - hashlittle(p, sizeof(q)-9, 13), hashlittle(p, sizeof(q)-10, 13), - hashlittle(p, sizeof(q)-11, 13), hashlittle(p, sizeof(q)-12, 13)); - p = &qq[1]; - printf("%.8x %.8x %.8x %.8x %.8x %.8x %.8x %.8x %.8x %.8x %.8x %.8x\n", - hashlittle(p, sizeof(q)-1, 13), hashlittle(p, sizeof(q)-2, 13), - hashlittle(p, sizeof(q)-3, 13), hashlittle(p, sizeof(q)-4, 13), - hashlittle(p, sizeof(q)-5, 13), hashlittle(p, sizeof(q)-6, 13), - hashlittle(p, sizeof(q)-7, 13), hashlittle(p, sizeof(q)-8, 13), - hashlittle(p, sizeof(q)-9, 13), hashlittle(p, sizeof(q)-10, 13), - hashlittle(p, sizeof(q)-11, 13), hashlittle(p, sizeof(q)-12, 13)); - p = &qqq[2]; - printf("%.8x %.8x %.8x %.8x %.8x %.8x %.8x %.8x %.8x %.8x %.8x %.8x\n", - hashlittle(p, sizeof(q)-1, 13), hashlittle(p, sizeof(q)-2, 13), - hashlittle(p, sizeof(q)-3, 13), hashlittle(p, sizeof(q)-4, 13), - hashlittle(p, sizeof(q)-5, 13), hashlittle(p, sizeof(q)-6, 13), - hashlittle(p, sizeof(q)-7, 13), hashlittle(p, sizeof(q)-8, 13), - hashlittle(p, sizeof(q)-9, 13), hashlittle(p, sizeof(q)-10, 13), - hashlittle(p, sizeof(q)-11, 13), hashlittle(p, sizeof(q)-12, 13)); - p = &qqqq[3]; - printf("%.8x %.8x %.8x %.8x %.8x %.8x %.8x %.8x %.8x %.8x %.8x %.8x\n", - hashlittle(p, sizeof(q)-1, 13), hashlittle(p, sizeof(q)-2, 13), - hashlittle(p, sizeof(q)-3, 13), hashlittle(p, sizeof(q)-4, 13), - hashlittle(p, sizeof(q)-5, 13), hashlittle(p, sizeof(q)-6, 13), - hashlittle(p, sizeof(q)-7, 13), hashlittle(p, sizeof(q)-8, 13), - hashlittle(p, sizeof(q)-9, 13), hashlittle(p, sizeof(q)-10, 13), - hashlittle(p, sizeof(q)-11, 13), hashlittle(p, sizeof(q)-12, 13)); - printf("\n"); - - /* check that hashlittle2 and hashlittle produce the same results */ - i=47; j=0; - hashlittle2(q, sizeof(q), &i, &j); - if (hashlittle(q, sizeof(q), 47) != i) - printf("hashlittle2 and hashlittle mismatch\n"); - - /* check that hashword2 and hashword produce the same results */ - len = 0xdeadbeef; - i=47, j=0; - hashword2(&len, 1, &i, &j); - if (hashword(&len, 1, 47) != i) - printf("hashword2 and hashword mismatch %x %x\n", - i, hashword(&len, 1, 47)); - - /* check hashlittle doesn't read before or after the ends of the string */ - for (h=0, b=buf+1; h<8; ++h, ++b) - { - for (i=0; imd5.state[0]; - b = md->md5.state[1]; - c = md->md5.state[2]; - d = md->md5.state[3]; - -#ifdef LTC_SMALL_CODE - for (i = 0; i < 16; ++i) { - FF(a,b,c,d,W[Worder[i]],Rorder[i],Korder[i]); - t = d; d = c; c = b; b = a; a = t; - } - - for (; i < 32; ++i) { - GG(a,b,c,d,W[Worder[i]],Rorder[i],Korder[i]); - t = d; d = c; c = b; b = a; a = t; - } - - for (; i < 48; ++i) { - HH(a,b,c,d,W[Worder[i]],Rorder[i],Korder[i]); - t = d; d = c; c = b; b = a; a = t; - } - - for (; i < 64; ++i) { - II(a,b,c,d,W[Worder[i]],Rorder[i],Korder[i]); - t = d; d = c; c = b; b = a; a = t; - } - -#else - FF(a,b,c,d,W[0],7,0xd76aa478UL) - FF(d,a,b,c,W[1],12,0xe8c7b756UL) - FF(c,d,a,b,W[2],17,0x242070dbUL) - FF(b,c,d,a,W[3],22,0xc1bdceeeUL) - FF(a,b,c,d,W[4],7,0xf57c0fafUL) - FF(d,a,b,c,W[5],12,0x4787c62aUL) - FF(c,d,a,b,W[6],17,0xa8304613UL) - FF(b,c,d,a,W[7],22,0xfd469501UL) - FF(a,b,c,d,W[8],7,0x698098d8UL) - FF(d,a,b,c,W[9],12,0x8b44f7afUL) - FF(c,d,a,b,W[10],17,0xffff5bb1UL) - FF(b,c,d,a,W[11],22,0x895cd7beUL) - FF(a,b,c,d,W[12],7,0x6b901122UL) - FF(d,a,b,c,W[13],12,0xfd987193UL) - FF(c,d,a,b,W[14],17,0xa679438eUL) - FF(b,c,d,a,W[15],22,0x49b40821UL) - GG(a,b,c,d,W[1],5,0xf61e2562UL) - GG(d,a,b,c,W[6],9,0xc040b340UL) - GG(c,d,a,b,W[11],14,0x265e5a51UL) - GG(b,c,d,a,W[0],20,0xe9b6c7aaUL) - GG(a,b,c,d,W[5],5,0xd62f105dUL) - GG(d,a,b,c,W[10],9,0x02441453UL) - GG(c,d,a,b,W[15],14,0xd8a1e681UL) - GG(b,c,d,a,W[4],20,0xe7d3fbc8UL) - GG(a,b,c,d,W[9],5,0x21e1cde6UL) - GG(d,a,b,c,W[14],9,0xc33707d6UL) - GG(c,d,a,b,W[3],14,0xf4d50d87UL) - GG(b,c,d,a,W[8],20,0x455a14edUL) - GG(a,b,c,d,W[13],5,0xa9e3e905UL) - GG(d,a,b,c,W[2],9,0xfcefa3f8UL) - GG(c,d,a,b,W[7],14,0x676f02d9UL) - GG(b,c,d,a,W[12],20,0x8d2a4c8aUL) - HH(a,b,c,d,W[5],4,0xfffa3942UL) - HH(d,a,b,c,W[8],11,0x8771f681UL) - HH(c,d,a,b,W[11],16,0x6d9d6122UL) - HH(b,c,d,a,W[14],23,0xfde5380cUL) - HH(a,b,c,d,W[1],4,0xa4beea44UL) - HH(d,a,b,c,W[4],11,0x4bdecfa9UL) - HH(c,d,a,b,W[7],16,0xf6bb4b60UL) - HH(b,c,d,a,W[10],23,0xbebfbc70UL) - HH(a,b,c,d,W[13],4,0x289b7ec6UL) - HH(d,a,b,c,W[0],11,0xeaa127faUL) - HH(c,d,a,b,W[3],16,0xd4ef3085UL) - HH(b,c,d,a,W[6],23,0x04881d05UL) - HH(a,b,c,d,W[9],4,0xd9d4d039UL) - HH(d,a,b,c,W[12],11,0xe6db99e5UL) - HH(c,d,a,b,W[15],16,0x1fa27cf8UL) - HH(b,c,d,a,W[2],23,0xc4ac5665UL) - II(a,b,c,d,W[0],6,0xf4292244UL) - II(d,a,b,c,W[7],10,0x432aff97UL) - II(c,d,a,b,W[14],15,0xab9423a7UL) - II(b,c,d,a,W[5],21,0xfc93a039UL) - II(a,b,c,d,W[12],6,0x655b59c3UL) - II(d,a,b,c,W[3],10,0x8f0ccc92UL) - II(c,d,a,b,W[10],15,0xffeff47dUL) - II(b,c,d,a,W[1],21,0x85845dd1UL) - II(a,b,c,d,W[8],6,0x6fa87e4fUL) - II(d,a,b,c,W[15],10,0xfe2ce6e0UL) - II(c,d,a,b,W[6],15,0xa3014314UL) - II(b,c,d,a,W[13],21,0x4e0811a1UL) - II(a,b,c,d,W[4],6,0xf7537e82UL) - II(d,a,b,c,W[11],10,0xbd3af235UL) - II(c,d,a,b,W[2],15,0x2ad7d2bbUL) - II(b,c,d,a,W[9],21,0xeb86d391UL) -#endif - - md->md5.state[0] = md->md5.state[0] + a; - md->md5.state[1] = md->md5.state[1] + b; - md->md5.state[2] = md->md5.state[2] + c; - md->md5.state[3] = md->md5.state[3] + d; - - return CRYPT_OK; -} - -#ifdef LTC_CLEAN_STACK -static int md5_compress(hash_state *md, unsigned char *buf) -{ - int err; - err = _md5_compress(md, buf); - burn_stack(sizeof(ulong32) * 21); - return err; -} -#endif - -/** - Initialize the hash state - @param md The hash state you wish to initialize - @return CRYPT_OK if successful -*/ -int md5_init(hash_state * md) -{ - LTC_ARGCHK(md != NULL); - md->md5.state[0] = 0x67452301UL; - md->md5.state[1] = 0xefcdab89UL; - md->md5.state[2] = 0x98badcfeUL; - md->md5.state[3] = 0x10325476UL; - md->md5.curlen = 0; - md->md5.length = 0; - return CRYPT_OK; -} - -/** - Process a block of memory though the hash - @param md The hash state - @param in The data to hash - @param inlen The length of the data (octets) - @return CRYPT_OK if successful -*/ -HASH_PROCESS(md5_process, md5_compress, md5, 64) - -/** - Terminate the hash to get the digest - @param md The hash state - @param out [out] The destination of the hash (16 bytes) - @return CRYPT_OK if successful -*/ -int md5_done(hash_state * md, unsigned char *out) -{ - int i; - - LTC_ARGCHK(md != NULL); - LTC_ARGCHK(out != NULL); - - if (md->md5.curlen >= sizeof(md->md5.buf)) { - return CRYPT_INVALID_ARG; - } - - - /* increase the length of the message */ - md->md5.length += md->md5.curlen * 8; - - /* append the '1' bit */ - md->md5.buf[md->md5.curlen++] = (unsigned char)0x80; - - /* if the length is currently above 56 bytes we append zeros - * then compress. Then we can fall back to padding zeros and length - * encoding like normal. - */ - if (md->md5.curlen > 56) { - while (md->md5.curlen < 64) { - md->md5.buf[md->md5.curlen++] = (unsigned char)0; - } - md5_compress(md, md->md5.buf); - md->md5.curlen = 0; - } - - /* pad upto 56 bytes of zeroes */ - while (md->md5.curlen < 56) { - md->md5.buf[md->md5.curlen++] = (unsigned char)0; - } - - /* store length */ - STORE64L(md->md5.length, md->md5.buf+56); - md5_compress(md, md->md5.buf); - - /* copy output */ - for (i = 0; i < 4; i++) { - STORE32L(md->md5.state[i], out+(4*i)); - } -#ifdef LTC_CLEAN_STACK - zeromem(md, sizeof(hash_state)); -#endif - return CRYPT_OK; -} - -/** - Self-test the hash - @return CRYPT_OK if successful, CRYPT_NOP if self-tests have been disabled -*/ -int md5_test(void) -{ - #ifndef LTC_TEST - return CRYPT_NOP; - #else - static const struct { - char *msg; - unsigned char hash[16]; - } tests[] = { - { "", - { 0xd4, 0x1d, 0x8c, 0xd9, 0x8f, 0x00, 0xb2, 0x04, - 0xe9, 0x80, 0x09, 0x98, 0xec, 0xf8, 0x42, 0x7e } }, - { "a", - {0x0c, 0xc1, 0x75, 0xb9, 0xc0, 0xf1, 0xb6, 0xa8, - 0x31, 0xc3, 0x99, 0xe2, 0x69, 0x77, 0x26, 0x61 } }, - { "abc", - { 0x90, 0x01, 0x50, 0x98, 0x3c, 0xd2, 0x4f, 0xb0, - 0xd6, 0x96, 0x3f, 0x7d, 0x28, 0xe1, 0x7f, 0x72 } }, - { "message digest", - { 0xf9, 0x6b, 0x69, 0x7d, 0x7c, 0xb7, 0x93, 0x8d, - 0x52, 0x5a, 0x2f, 0x31, 0xaa, 0xf1, 0x61, 0xd0 } }, - { "abcdefghijklmnopqrstuvwxyz", - { 0xc3, 0xfc, 0xd3, 0xd7, 0x61, 0x92, 0xe4, 0x00, - 0x7d, 0xfb, 0x49, 0x6c, 0xca, 0x67, 0xe1, 0x3b } }, - { "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789", - { 0xd1, 0x74, 0xab, 0x98, 0xd2, 0x77, 0xd9, 0xf5, - 0xa5, 0x61, 0x1c, 0x2c, 0x9f, 0x41, 0x9d, 0x9f } }, - { "12345678901234567890123456789012345678901234567890123456789012345678901234567890", - { 0x57, 0xed, 0xf4, 0xa2, 0x2b, 0xe3, 0xc9, 0x55, - 0xac, 0x49, 0xda, 0x2e, 0x21, 0x07, 0xb6, 0x7a } }, - { NULL, { 0 } } - }; - - int i; - unsigned char tmp[16]; - hash_state md; - - for (i = 0; tests[i].msg != NULL; i++) { - md5_init(&md); - md5_process(&md, (unsigned char *)tests[i].msg, (unsigned long)strlen(tests[i].msg)); - md5_done(&md, tmp); - if (XMEMCMP(tmp, tests[i].hash, 16) != 0) { - return CRYPT_FAIL_TESTVECTOR; - } - } - return CRYPT_OK; - #endif -} - -#endif - - - -/* $Source: /cvs/libtom/libtomcrypt/src/hashes/md5.c,v $ */ -/* $Revision: 1.10 $ */ -/* $Date: 2007/05/12 14:25:28 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/hashes/sha1.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/hashes/sha1.c deleted file mode 100644 index 409d095..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/hashes/sha1.c +++ /dev/null @@ -1,288 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../headers/tomcrypt.h" - -/** - @file sha1.c - LTC_SHA1 code by Tom St Denis -*/ - - -#ifdef LTC_SHA1 - -const struct ltc_hash_descriptor sha1_desc = -{ - "sha1", - 2, - 20, - 64, - - /* OID */ - { 1, 3, 14, 3, 2, 26, }, - 6, - - &sha1_init, - &sha1_process, - &sha1_done, - &sha1_test, - NULL -}; - -#define F0(x,y,z) (z ^ (x & (y ^ z))) -#define F1(x,y,z) (x ^ y ^ z) -#define F2(x,y,z) ((x & y) | (z & (x | y))) -#define F3(x,y,z) (x ^ y ^ z) - -#ifdef LTC_CLEAN_STACK -static int _sha1_compress(hash_state *md, unsigned char *buf) -#else -static int sha1_compress(hash_state *md, unsigned char *buf) -#endif -{ - ulong32 a,b,c,d,e,W[80],i; -#ifdef LTC_SMALL_CODE - ulong32 t; -#endif - - /* copy the state into 512-bits into W[0..15] */ - for (i = 0; i < 16; i++) { - LOAD32H(W[i], buf + (4*i)); - } - - /* copy state */ - a = md->sha1.state[0]; - b = md->sha1.state[1]; - c = md->sha1.state[2]; - d = md->sha1.state[3]; - e = md->sha1.state[4]; - - /* expand it */ - for (i = 16; i < 80; i++) { - W[i] = ROL(W[i-3] ^ W[i-8] ^ W[i-14] ^ W[i-16], 1); - } - - /* compress */ - /* round one */ - #define FF0(a,b,c,d,e,i) e = (ROLc(a, 5) + F0(b,c,d) + e + W[i] + 0x5a827999UL); b = ROLc(b, 30); - #define FF1(a,b,c,d,e,i) e = (ROLc(a, 5) + F1(b,c,d) + e + W[i] + 0x6ed9eba1UL); b = ROLc(b, 30); - #define FF2(a,b,c,d,e,i) e = (ROLc(a, 5) + F2(b,c,d) + e + W[i] + 0x8f1bbcdcUL); b = ROLc(b, 30); - #define FF3(a,b,c,d,e,i) e = (ROLc(a, 5) + F3(b,c,d) + e + W[i] + 0xca62c1d6UL); b = ROLc(b, 30); - -#ifdef LTC_SMALL_CODE - - for (i = 0; i < 20; ) { - FF0(a,b,c,d,e,i++); t = e; e = d; d = c; c = b; b = a; a = t; - } - - for (; i < 40; ) { - FF1(a,b,c,d,e,i++); t = e; e = d; d = c; c = b; b = a; a = t; - } - - for (; i < 60; ) { - FF2(a,b,c,d,e,i++); t = e; e = d; d = c; c = b; b = a; a = t; - } - - for (; i < 80; ) { - FF3(a,b,c,d,e,i++); t = e; e = d; d = c; c = b; b = a; a = t; - } - -#else - - for (i = 0; i < 20; ) { - FF0(a,b,c,d,e,i++); - FF0(e,a,b,c,d,i++); - FF0(d,e,a,b,c,i++); - FF0(c,d,e,a,b,i++); - FF0(b,c,d,e,a,i++); - } - - /* round two */ - for (; i < 40; ) { - FF1(a,b,c,d,e,i++); - FF1(e,a,b,c,d,i++); - FF1(d,e,a,b,c,i++); - FF1(c,d,e,a,b,i++); - FF1(b,c,d,e,a,i++); - } - - /* round three */ - for (; i < 60; ) { - FF2(a,b,c,d,e,i++); - FF2(e,a,b,c,d,i++); - FF2(d,e,a,b,c,i++); - FF2(c,d,e,a,b,i++); - FF2(b,c,d,e,a,i++); - } - - /* round four */ - for (; i < 80; ) { - FF3(a,b,c,d,e,i++); - FF3(e,a,b,c,d,i++); - FF3(d,e,a,b,c,i++); - FF3(c,d,e,a,b,i++); - FF3(b,c,d,e,a,i++); - } -#endif - - #undef FF0 - #undef FF1 - #undef FF2 - #undef FF3 - - /* store */ - md->sha1.state[0] = md->sha1.state[0] + a; - md->sha1.state[1] = md->sha1.state[1] + b; - md->sha1.state[2] = md->sha1.state[2] + c; - md->sha1.state[3] = md->sha1.state[3] + d; - md->sha1.state[4] = md->sha1.state[4] + e; - - return CRYPT_OK; -} - -#ifdef LTC_CLEAN_STACK -static int sha1_compress(hash_state *md, unsigned char *buf) -{ - int err; - err = _sha1_compress(md, buf); - burn_stack(sizeof(ulong32) * 87); - return err; -} -#endif - -/** - Initialize the hash state - @param md The hash state you wish to initialize - @return CRYPT_OK if successful -*/ -int sha1_init(hash_state * md) -{ - LTC_ARGCHK(md != NULL); - md->sha1.state[0] = 0x67452301UL; - md->sha1.state[1] = 0xefcdab89UL; - md->sha1.state[2] = 0x98badcfeUL; - md->sha1.state[3] = 0x10325476UL; - md->sha1.state[4] = 0xc3d2e1f0UL; - md->sha1.curlen = 0; - md->sha1.length = 0; - return CRYPT_OK; -} - -/** - Process a block of memory though the hash - @param md The hash state - @param in The data to hash - @param inlen The length of the data (octets) - @return CRYPT_OK if successful -*/ -HASH_PROCESS(sha1_process, sha1_compress, sha1, 64) - -/** - Terminate the hash to get the digest - @param md The hash state - @param out [out] The destination of the hash (20 bytes) - @return CRYPT_OK if successful -*/ -int sha1_done(hash_state * md, unsigned char *out) -{ - int i; - - LTC_ARGCHK(md != NULL); - LTC_ARGCHK(out != NULL); - - if (md->sha1.curlen >= sizeof(md->sha1.buf)) { - return CRYPT_INVALID_ARG; - } - - /* increase the length of the message */ - md->sha1.length += md->sha1.curlen * 8; - - /* append the '1' bit */ - md->sha1.buf[md->sha1.curlen++] = (unsigned char)0x80; - - /* if the length is currently above 56 bytes we append zeros - * then compress. Then we can fall back to padding zeros and length - * encoding like normal. - */ - if (md->sha1.curlen > 56) { - while (md->sha1.curlen < 64) { - md->sha1.buf[md->sha1.curlen++] = (unsigned char)0; - } - sha1_compress(md, md->sha1.buf); - md->sha1.curlen = 0; - } - - /* pad upto 56 bytes of zeroes */ - while (md->sha1.curlen < 56) { - md->sha1.buf[md->sha1.curlen++] = (unsigned char)0; - } - - /* store length */ - STORE64H(md->sha1.length, md->sha1.buf+56); - sha1_compress(md, md->sha1.buf); - - /* copy output */ - for (i = 0; i < 5; i++) { - STORE32H(md->sha1.state[i], out+(4*i)); - } -#ifdef LTC_CLEAN_STACK - zeromem(md, sizeof(hash_state)); -#endif - return CRYPT_OK; -} - -/** - Self-test the hash - @return CRYPT_OK if successful, CRYPT_NOP if self-tests have been disabled -*/ -int sha1_test(void) -{ - #ifndef LTC_TEST - return CRYPT_NOP; - #else - static const struct { - char *msg; - unsigned char hash[20]; - } tests[] = { - { "abc", - { 0xa9, 0x99, 0x3e, 0x36, 0x47, 0x06, 0x81, 0x6a, - 0xba, 0x3e, 0x25, 0x71, 0x78, 0x50, 0xc2, 0x6c, - 0x9c, 0xd0, 0xd8, 0x9d } - }, - { "abcdbcdecdefdefgefghfghighijhijkijkljklmklmnlmnomnopnopq", - { 0x84, 0x98, 0x3E, 0x44, 0x1C, 0x3B, 0xD2, 0x6E, - 0xBA, 0xAE, 0x4A, 0xA1, 0xF9, 0x51, 0x29, 0xE5, - 0xE5, 0x46, 0x70, 0xF1 } - } - }; - - int i; - unsigned char tmp[20]; - hash_state md; - - for (i = 0; i < (int)(sizeof(tests) / sizeof(tests[0])); i++) { - sha1_init(&md); - sha1_process(&md, (unsigned char*)tests[i].msg, (unsigned long)strlen(tests[i].msg)); - sha1_done(&md, tmp); - if (XMEMCMP(tmp, tests[i].hash, 20) != 0) { - return CRYPT_FAIL_TESTVECTOR; - } - } - return CRYPT_OK; - #endif -} - -#endif - - - -/* $Source: /cvs/libtom/libtomcrypt/src/hashes/sha1.c,v $ */ -/* $Revision: 1.10 $ */ -/* $Date: 2007/05/12 14:25:28 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt.h b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt.h deleted file mode 100644 index 7df3f5a..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt.h +++ /dev/null @@ -1,91 +0,0 @@ -#ifndef TOMCRYPT_H_ -#define TOMCRYPT_H_ -#include -#include -#include -#include -#include -#include -#include - -/* use configuration data */ -#include "tomcrypt_custom.h" - -#ifdef __cplusplus -extern "C" { -#endif - -/* version */ -#define CRYPT 0x0117 -#define SCRYPT "1.17" - -/* max size of either a cipher/hash block or symmetric key [largest of the two] */ -#define MAXBLOCKSIZE 128 - -/* descriptor table size */ -#define TAB_SIZE 32 - -#ifdef _MSC_VER -#pragma warning(disable: 4333) // der_encode_utf8_string.c(91) : warning C4333: '>>' : right shift by too large amount, data loss -#endif - -/* error codes [will be expanded in future releases] */ -enum { - CRYPT_OK=0, /* Result OK */ - CRYPT_ERROR, /* Generic Error */ - CRYPT_NOP, /* Not a failure but no operation was performed */ - - CRYPT_INVALID_KEYSIZE, /* Invalid key size given */ - CRYPT_INVALID_ROUNDS, /* Invalid number of rounds */ - CRYPT_FAIL_TESTVECTOR, /* Algorithm failed test vectors */ - - CRYPT_BUFFER_OVERFLOW, /* Not enough space for output */ - CRYPT_INVALID_PACKET, /* Invalid input packet given */ - - CRYPT_INVALID_PRNGSIZE, /* Invalid number of bits for a PRNG */ - CRYPT_ERROR_READPRNG, /* Could not read enough from PRNG */ - - CRYPT_INVALID_CIPHER, /* Invalid cipher specified */ - CRYPT_INVALID_HASH, /* Invalid hash specified */ - CRYPT_INVALID_PRNG, /* Invalid PRNG specified */ - - CRYPT_MEM, /* Out of memory */ - - CRYPT_PK_TYPE_MISMATCH, /* Not equivalent types of PK keys */ - CRYPT_PK_NOT_PRIVATE, /* Requires a private PK key */ - - CRYPT_INVALID_ARG, /* Generic invalid argument */ - CRYPT_FILE_NOTFOUND, /* File Not Found */ - - CRYPT_PK_INVALID_TYPE, /* Invalid type of PK key */ - CRYPT_PK_INVALID_SYSTEM,/* Invalid PK system specified */ - CRYPT_PK_DUP, /* Duplicate key already in key ring */ - CRYPT_PK_NOT_FOUND, /* Key not found in keyring */ - CRYPT_PK_INVALID_SIZE, /* Invalid size input for PK parameters */ - - CRYPT_INVALID_PRIME_SIZE,/* Invalid size of prime requested */ - CRYPT_PK_INVALID_PADDING /* Invalid padding on input */ -}; - -#include "tomcrypt_cfg.h" -#include "tomcrypt_macros.h" -#include "tomcrypt_cipher.h" -#include "tomcrypt_hash.h" -#include "tomcrypt_mac.h" -#include "tomcrypt_prng.h" -#include "tomcrypt_pk.h" -#include "tomcrypt_math.h" -#include "tomcrypt_misc.h" -#include "tomcrypt_argchk.h" -#include "tomcrypt_pkcs.h" - -#ifdef __cplusplus - } -#endif - -#endif /* TOMCRYPT_H_ */ - - -/* $Source: /cvs/libtom/libtomcrypt/src/headers/tomcrypt.h,v $ */ -/* $Revision: 1.21 $ */ -/* $Date: 2006/12/16 19:34:05 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_argchk.h b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_argchk.h deleted file mode 100644 index cfc93ad..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_argchk.h +++ /dev/null @@ -1,38 +0,0 @@ -/* Defines the LTC_ARGCHK macro used within the library */ -/* ARGTYPE is defined in mycrypt_cfg.h */ -#if ARGTYPE == 0 - -#include - -/* this is the default LibTomCrypt macro */ -void crypt_argchk(char *v, char *s, int d); -#define LTC_ARGCHK(x) if (!(x)) { crypt_argchk(#x, __FILE__, __LINE__); } -#define LTC_ARGCHKVD(x) LTC_ARGCHK(x) - -#elif ARGTYPE == 1 - -/* fatal type of error */ -#define LTC_ARGCHK(x) assert((x)) -#define LTC_ARGCHKVD(x) LTC_ARGCHK(x) - -#elif ARGTYPE == 2 - -#define LTC_ARGCHK(x) if (!(x)) { fprintf(stderr, "\nwarning: ARGCHK failed at %s:%d\n", __FILE__, __LINE__); } -#define LTC_ARGCHKVD(x) LTC_ARGCHK(x) - -#elif ARGTYPE == 3 - -#define LTC_ARGCHK(x) -#define LTC_ARGCHKVD(x) LTC_ARGCHK(x) - -#elif ARGTYPE == 4 - -#define LTC_ARGCHK(x) if (!(x)) return CRYPT_INVALID_ARG; -#define LTC_ARGCHKVD(x) if (!(x)) return; - -#endif - - -/* $Source: /cvs/libtom/libtomcrypt/src/headers/tomcrypt_argchk.h,v $ */ -/* $Revision: 1.5 $ */ -/* $Date: 2006/08/27 20:50:21 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_cfg.h b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_cfg.h deleted file mode 100644 index 335d55f..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_cfg.h +++ /dev/null @@ -1,144 +0,0 @@ -/* This is the build config file. - * - * With this you can setup what to inlcude/exclude automatically during any build. Just comment - * out the line that #define's the word for the thing you want to remove. phew! - */ - -#ifndef TOMCRYPT_CFG_H -#define TOMCRYPT_CFG_H - -#if defined(_WIN32) || defined(_MSC_VER) -#define LTC_CALL __cdecl -#else -#ifndef LTC_CALL - #define LTC_CALL -#endif -#endif - -#ifndef LTC_EXPORT -#define LTC_EXPORT -#endif - -/* certain platforms use macros for these, making the prototypes broken */ -#ifndef LTC_NO_PROTOTYPES - -/* you can change how memory allocation works ... */ -LTC_EXPORT void * LTC_CALL XMALLOC(size_t n); -LTC_EXPORT void * LTC_CALL XREALLOC(void *p, size_t n); -LTC_EXPORT void * LTC_CALL XCALLOC(size_t n, size_t s); -LTC_EXPORT void LTC_CALL XFREE(void *p); - -LTC_EXPORT void LTC_CALL XQSORT(void *base, size_t nmemb, size_t size, int(LTC_CALL * compar)(const void *, const void *)); - -/* change the clock function too */ -LTC_EXPORT clock_t LTC_CALL XCLOCK(void); -#endif // LTC_NO_PROTOTYPES - -/* various other functions */ -#ifndef LTC_NO_PROTOTYPES_MEMCPY -LTC_EXPORT void * LTC_CALL XMEMCPY(void *dest, const void *src, size_t n); -#endif - -#ifndef LTC_NO_PROTOTYPES_MEMCMP -LTC_EXPORT int LTC_CALL XMEMCMP(const void *s1, const void *s2, size_t n); -#endif - -#ifndef LTC_NO_PROTOTYPES_MEMSET -LTC_EXPORT void * LTC_CALL XMEMSET(void *s, int c, size_t n); -#endif - -#ifndef LTC_NO_PROTOTYPES_STRCMP -LTC_EXPORT int LTC_CALL XSTRCMP(const char *s1, const char *s2); -#endif - -/* type of argument checking, 0=default, 1=fatal and 2=error+continue, 3=nothing */ -#ifndef ARGTYPE - #define ARGTYPE 0 -#endif - -/* Controls endianess and size of registers. Leave uncommented to get platform neutral [slower] code - * - * Note: in order to use the optimized macros your platform must support unaligned 32 and 64 bit read/writes. - * The x86 platforms allow this but some others [ARM for instance] do not. On those platforms you **MUST** - * use the portable [slower] macros. - */ - -/* detect x86-32 machines somewhat */ -#if !defined(__STRICT_ANSI__) && (defined(INTEL_CC) || (defined(_MSC_VER) && defined(WIN32)) || (defined(__GNUC__) && (defined(__DJGPP__) || defined(__CYGWIN__) || defined(__MINGW32__) || defined(__i386__)))) - #define ENDIAN_LITTLE - #define ENDIAN_32BITWORD - #define LTC_FAST - #define LTC_FAST_TYPE unsigned long -#endif - -/* detects MIPS R5900 processors (PS2) */ -#if (defined(__R5900) || defined(R5900) || defined(__R5900__)) && (defined(_mips) || defined(__mips__) || defined(mips)) - #define ENDIAN_LITTLE - #define ENDIAN_64BITWORD -#endif - -/* detect amd64 */ -#if !defined(__STRICT_ANSI__) && defined(__x86_64__) - #define ENDIAN_LITTLE - #define ENDIAN_64BITWORD - #define LTC_FAST - #define LTC_FAST_TYPE unsigned long -#endif - -/* detect PPC32 */ -#if !defined(__STRICT_ANSI__) && defined(LTC_PPC32) - #define ENDIAN_BIG - #define ENDIAN_32BITWORD - #define LTC_FAST - #define LTC_FAST_TYPE unsigned long -#endif - -/* detect sparc and sparc64 */ -#if defined(__sparc__) - #define ENDIAN_BIG - #if defined(__arch64__) - #define ENDIAN_64BITWORD - #else - #define ENDIAN_32BITWORD - #endif -#endif - - -#ifdef LTC_NO_FAST - #ifdef LTC_FAST - #undef LTC_FAST - #endif -#endif - -/* No asm is a quick way to disable anything "not portable" */ -#ifdef LTC_NO_ASM - #undef ENDIAN_LITTLE - #undef ENDIAN_BIG - #undef ENDIAN_32BITWORD - #undef ENDIAN_64BITWORD - #undef LTC_FAST - #undef LTC_FAST_TYPE - #define LTC_NO_ROLC - #define LTC_NO_BSWAP -#endif - -/* #define ENDIAN_LITTLE */ -/* #define ENDIAN_BIG */ - -/* #define ENDIAN_32BITWORD */ -/* #define ENDIAN_64BITWORD */ - -#if (defined(ENDIAN_BIG) || defined(ENDIAN_LITTLE)) && !(defined(ENDIAN_32BITWORD) || defined(ENDIAN_64BITWORD)) - #error You must specify a word size as well as endianess in tomcrypt_cfg.h -#endif - -#if !(defined(ENDIAN_BIG) || defined(ENDIAN_LITTLE)) - #define ENDIAN_NEUTRAL -#endif - -#endif - - -/* $Source: /cvs/libtom/libtomcrypt/src/headers/tomcrypt_cfg.h,v $ */ -/* $Revision: 1.19 $ */ -/* $Date: 2006/12/04 02:19:48 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_cipher.h b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_cipher.h deleted file mode 100644 index bd740bf..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_cipher.h +++ /dev/null @@ -1,891 +0,0 @@ -/* ---- SYMMETRIC KEY STUFF ----- - * - * We put each of the ciphers scheduled keys in their own structs then we put all of - * the key formats in one union. This makes the function prototypes easier to use. - */ -#ifdef LTC_BLOWFISH -struct blowfish_key { - ulong32 S[4][256]; - ulong32 K[18]; -}; -#endif - -#ifdef LTC_RC5 -struct rc5_key { - int rounds; - ulong32 K[50]; -}; -#endif - -#ifdef LTC_RC6 -struct rc6_key { - ulong32 K[44]; -}; -#endif - -#ifdef LTC_SAFERP -struct saferp_key { - unsigned char K[33][16]; - long rounds; -}; -#endif - -#ifdef LTC_RIJNDAEL -struct rijndael_key { - ulong32 eK[60], dK[60]; - int Nr; -}; -#endif - -#ifdef LTC_KSEED -struct kseed_key { - ulong32 K[32], dK[32]; -}; -#endif - -#ifdef LTC_KASUMI -struct kasumi_key { - ulong32 KLi1[8], KLi2[8], - KOi1[8], KOi2[8], KOi3[8], - KIi1[8], KIi2[8], KIi3[8]; -}; -#endif - -#ifdef LTC_XTEA -struct xtea_key { - unsigned long A[32], B[32]; -}; -#endif - -#ifdef LTC_TWOFISH -#ifndef LTC_TWOFISH_SMALL - struct twofish_key { - ulong32 S[4][256], K[40]; - }; -#else - struct twofish_key { - ulong32 K[40]; - unsigned char S[32], start; - }; -#endif -#endif - -#ifdef LTC_SAFER -#define LTC_SAFER_K64_DEFAULT_NOF_ROUNDS 6 -#define LTC_SAFER_K128_DEFAULT_NOF_ROUNDS 10 -#define LTC_SAFER_SK64_DEFAULT_NOF_ROUNDS 8 -#define LTC_SAFER_SK128_DEFAULT_NOF_ROUNDS 10 -#define LTC_SAFER_MAX_NOF_ROUNDS 13 -#define LTC_SAFER_BLOCK_LEN 8 -#define LTC_SAFER_KEY_LEN (1 + LTC_SAFER_BLOCK_LEN * (1 + 2 * LTC_SAFER_MAX_NOF_ROUNDS)) -typedef unsigned char safer_block_t[LTC_SAFER_BLOCK_LEN]; -typedef unsigned char safer_key_t[LTC_SAFER_KEY_LEN]; -struct safer_key { safer_key_t key; }; -#endif - -#ifdef LTC_RC2 -struct rc2_key { unsigned xkey[64]; }; -#endif - -#ifdef LTC_DES -struct des_key { - ulong32 ek[32], dk[32]; -}; - -struct des3_key { - ulong32 ek[3][32], dk[3][32]; -}; -#endif - -#ifdef LTC_CAST5 -struct cast5_key { - ulong32 K[32], keylen; -}; -#endif - -#ifdef LTC_NOEKEON -struct noekeon_key { - ulong32 K[4], dK[4]; -}; -#endif - -#ifdef LTC_SKIPJACK -struct skipjack_key { - unsigned char key[10]; -}; -#endif - -#ifdef LTC_KHAZAD -struct khazad_key { - ulong64 roundKeyEnc[8 + 1]; - ulong64 roundKeyDec[8 + 1]; -}; -#endif - -#ifdef LTC_ANUBIS -struct anubis_key { - int keyBits; - int R; - ulong32 roundKeyEnc[18 + 1][4]; - ulong32 roundKeyDec[18 + 1][4]; -}; -#endif - -#ifdef LTC_MULTI2 -struct multi2_key { - int N; - ulong32 uk[8]; -}; -#endif - -typedef union Symmetric_key { -#ifdef LTC_DES - struct des_key des; - struct des3_key des3; -#endif -#ifdef LTC_RC2 - struct rc2_key rc2; -#endif -#ifdef LTC_SAFER - struct safer_key safer; -#endif -#ifdef LTC_TWOFISH - struct twofish_key twofish; -#endif -#ifdef LTC_BLOWFISH - struct blowfish_key blowfish; -#endif -#ifdef LTC_RC5 - struct rc5_key rc5; -#endif -#ifdef LTC_RC6 - struct rc6_key rc6; -#endif -#ifdef LTC_SAFERP - struct saferp_key saferp; -#endif -#ifdef LTC_RIJNDAEL - struct rijndael_key rijndael; -#endif -#ifdef LTC_XTEA - struct xtea_key xtea; -#endif -#ifdef LTC_CAST5 - struct cast5_key cast5; -#endif -#ifdef LTC_NOEKEON - struct noekeon_key noekeon; -#endif -#ifdef LTC_SKIPJACK - struct skipjack_key skipjack; -#endif -#ifdef LTC_KHAZAD - struct khazad_key khazad; -#endif -#ifdef LTC_ANUBIS - struct anubis_key anubis; -#endif -#ifdef LTC_KSEED - struct kseed_key kseed; -#endif -#ifdef LTC_KASUMI - struct kasumi_key kasumi; -#endif -#ifdef LTC_MULTI2 - struct multi2_key multi2; -#endif - void *data; -} symmetric_key; - -#ifdef LTC_ECB_MODE -/** A block cipher ECB structure */ -typedef struct { - /** The index of the cipher chosen */ - int cipher, - /** The block size of the given cipher */ - blocklen; - /** The scheduled key */ - symmetric_key key; -} symmetric_ECB; -#endif - -#ifdef LTC_CFB_MODE -/** A block cipher CFB structure */ -typedef struct { - /** The index of the cipher chosen */ - int cipher, - /** The block size of the given cipher */ - blocklen, - /** The padding offset */ - padlen; - /** The current IV */ - unsigned char IV[MAXBLOCKSIZE], - /** The pad used to encrypt/decrypt */ - pad[MAXBLOCKSIZE]; - /** The scheduled key */ - symmetric_key key; -} symmetric_CFB; -#endif - -#ifdef LTC_OFB_MODE -/** A block cipher OFB structure */ -typedef struct { - /** The index of the cipher chosen */ - int cipher, - /** The block size of the given cipher */ - blocklen, - /** The padding offset */ - padlen; - /** The current IV */ - unsigned char IV[MAXBLOCKSIZE]; - /** The scheduled key */ - symmetric_key key; -} symmetric_OFB; -#endif - -#ifdef LTC_CBC_MODE -/** A block cipher CBC structure */ -typedef struct { - /** The index of the cipher chosen */ - int cipher, - /** The block size of the given cipher */ - blocklen; - /** The current IV */ - unsigned char IV[MAXBLOCKSIZE]; - /** The scheduled key */ - symmetric_key key; -} symmetric_CBC; -#endif - - -#ifdef LTC_CTR_MODE -/** A block cipher CTR structure */ -typedef struct { - /** The index of the cipher chosen */ - int cipher, - /** The block size of the given cipher */ - blocklen, - /** The padding offset */ - padlen, - /** The mode (endianess) of the CTR, 0==little, 1==big */ - mode, - /** counter width */ - ctrlen; - - /** The counter */ - unsigned char ctr[MAXBLOCKSIZE], - /** The pad used to encrypt/decrypt */ - pad[MAXBLOCKSIZE]; - /** The scheduled key */ - symmetric_key key; -} symmetric_CTR; -#endif - - -#ifdef LTC_LRW_MODE -/** A LRW structure */ -typedef struct { - /** The index of the cipher chosen (must be a 128-bit block cipher) */ - int cipher; - - /** The current IV */ - unsigned char IV[16], - - /** the tweak key */ - tweak[16], - - /** The current pad, it's the product of the first 15 bytes against the tweak key */ - pad[16]; - - /** The scheduled symmetric key */ - symmetric_key key; - -#ifdef LRW_TABLES - /** The pre-computed multiplication table */ - unsigned char PC[16][256][16]; -#endif -} symmetric_LRW; -#endif - -#ifdef LTC_F8_MODE -/** A block cipher F8 structure */ -typedef struct { - /** The index of the cipher chosen */ - int cipher, - /** The block size of the given cipher */ - blocklen, - /** The padding offset */ - padlen; - /** The current IV */ - unsigned char IV[MAXBLOCKSIZE], - MIV[MAXBLOCKSIZE]; - /** Current block count */ - ulong32 blockcnt; - /** The scheduled key */ - symmetric_key key; -} symmetric_F8; -#endif - - -/** cipher descriptor table, last entry has "name == NULL" to mark the end of table */ -extern struct ltc_cipher_descriptor { - /** name of cipher */ - char *name; - /** internal ID */ - unsigned char ID; - /** min keysize (octets) */ - int min_key_length, - /** max keysize (octets) */ - max_key_length, - /** block size (octets) */ - block_length, - /** default number of rounds */ - default_rounds; - /** Setup the cipher - @param key The input symmetric key - @param keylen The length of the input key (octets) - @param num_rounds The requested number of rounds (0==default) - @param skey [out] The destination of the scheduled key - @return CRYPT_OK if successful - */ - int (*setup)(const unsigned char *key, int keylen, int num_rounds, symmetric_key *skey); - /** Encrypt a block - @param pt The plaintext - @param ct [out] The ciphertext - @param skey The scheduled key - @return CRYPT_OK if successful - */ - int (*ecb_encrypt)(const unsigned char *pt, unsigned char *ct, symmetric_key *skey); - /** Decrypt a block - @param ct The ciphertext - @param pt [out] The plaintext - @param skey The scheduled key - @return CRYPT_OK if successful - */ - int (*ecb_decrypt)(const unsigned char *ct, unsigned char *pt, symmetric_key *skey); - /** Test the block cipher - @return CRYPT_OK if successful, CRYPT_NOP if self-testing has been disabled - */ - int (*test)(void); - - /** Terminate the context - @param skey The scheduled key - */ - void (*done)(symmetric_key *skey); - - /** Determine a key size - @param keysize [in/out] The size of the key desired and the suggested size - @return CRYPT_OK if successful - */ - int (*keysize)(int *keysize); - -/** Accelerators **/ - /** Accelerated ECB encryption - @param pt Plaintext - @param ct Ciphertext - @param blocks The number of complete blocks to process - @param skey The scheduled key context - @return CRYPT_OK if successful - */ - int (*accel_ecb_encrypt)(const unsigned char *pt, unsigned char *ct, unsigned long blocks, symmetric_key *skey); - - /** Accelerated ECB decryption - @param pt Plaintext - @param ct Ciphertext - @param blocks The number of complete blocks to process - @param skey The scheduled key context - @return CRYPT_OK if successful - */ - int (*accel_ecb_decrypt)(const unsigned char *ct, unsigned char *pt, unsigned long blocks, symmetric_key *skey); - - /** Accelerated CBC encryption - @param pt Plaintext - @param ct Ciphertext - @param blocks The number of complete blocks to process - @param IV The initial value (input/output) - @param skey The scheduled key context - @return CRYPT_OK if successful - */ - int (*accel_cbc_encrypt)(const unsigned char *pt, unsigned char *ct, unsigned long blocks, unsigned char *IV, symmetric_key *skey); - - /** Accelerated CBC decryption - @param pt Plaintext - @param ct Ciphertext - @param blocks The number of complete blocks to process - @param IV The initial value (input/output) - @param skey The scheduled key context - @return CRYPT_OK if successful - */ - int (*accel_cbc_decrypt)(const unsigned char *ct, unsigned char *pt, unsigned long blocks, unsigned char *IV, symmetric_key *skey); - - /** Accelerated CTR encryption - @param pt Plaintext - @param ct Ciphertext - @param blocks The number of complete blocks to process - @param IV The initial value (input/output) - @param mode little or big endian counter (mode=0 or mode=1) - @param skey The scheduled key context - @return CRYPT_OK if successful - */ - int (*accel_ctr_encrypt)(const unsigned char *pt, unsigned char *ct, unsigned long blocks, unsigned char *IV, int mode, symmetric_key *skey); - - /** Accelerated LRW - @param pt Plaintext - @param ct Ciphertext - @param blocks The number of complete blocks to process - @param IV The initial value (input/output) - @param tweak The LRW tweak - @param skey The scheduled key context - @return CRYPT_OK if successful - */ - int (*accel_lrw_encrypt)(const unsigned char *pt, unsigned char *ct, unsigned long blocks, unsigned char *IV, const unsigned char *tweak, symmetric_key *skey); - - /** Accelerated LRW - @param ct Ciphertext - @param pt Plaintext - @param blocks The number of complete blocks to process - @param IV The initial value (input/output) - @param tweak The LRW tweak - @param skey The scheduled key context - @return CRYPT_OK if successful - */ - int (*accel_lrw_decrypt)(const unsigned char *ct, unsigned char *pt, unsigned long blocks, unsigned char *IV, const unsigned char *tweak, symmetric_key *skey); - - /** Accelerated CCM packet (one-shot) - @param key The secret key to use - @param keylen The length of the secret key (octets) - @param uskey A previously scheduled key [optional can be NULL] - @param nonce The session nonce [use once] - @param noncelen The length of the nonce - @param header The header for the session - @param headerlen The length of the header (octets) - @param pt [out] The plaintext - @param ptlen The length of the plaintext (octets) - @param ct [out] The ciphertext - @param tag [out] The destination tag - @param taglen [in/out] The max size and resulting size of the authentication tag - @param direction Encrypt or Decrypt direction (0 or 1) - @return CRYPT_OK if successful - */ - int (*accel_ccm_memory)( - const unsigned char *key, unsigned long keylen, - symmetric_key *uskey, - const unsigned char *nonce, unsigned long noncelen, - const unsigned char *header, unsigned long headerlen, - unsigned char *pt, unsigned long ptlen, - unsigned char *ct, - unsigned char *tag, unsigned long *taglen, - int direction); - - /** Accelerated GCM packet (one shot) - @param key The secret key - @param keylen The length of the secret key - @param IV The initial vector - @param IVlen The length of the initial vector - @param adata The additional authentication data (header) - @param adatalen The length of the adata - @param pt The plaintext - @param ptlen The length of the plaintext (ciphertext length is the same) - @param ct The ciphertext - @param tag [out] The MAC tag - @param taglen [in/out] The MAC tag length - @param direction Encrypt or Decrypt mode (GCM_ENCRYPT or GCM_DECRYPT) - @return CRYPT_OK on success - */ - int (*accel_gcm_memory)( - const unsigned char *key, unsigned long keylen, - const unsigned char *IV, unsigned long IVlen, - const unsigned char *adata, unsigned long adatalen, - unsigned char *pt, unsigned long ptlen, - unsigned char *ct, - unsigned char *tag, unsigned long *taglen, - int direction); - - /** Accelerated one shot LTC_OMAC - @param key The secret key - @param keylen The key length (octets) - @param in The message - @param inlen Length of message (octets) - @param out [out] Destination for tag - @param outlen [in/out] Initial and final size of out - @return CRYPT_OK on success - */ - int (*omac_memory)( - const unsigned char *key, unsigned long keylen, - const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen); - - /** Accelerated one shot XCBC - @param key The secret key - @param keylen The key length (octets) - @param in The message - @param inlen Length of message (octets) - @param out [out] Destination for tag - @param outlen [in/out] Initial and final size of out - @return CRYPT_OK on success - */ - int (*xcbc_memory)( - const unsigned char *key, unsigned long keylen, - const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen); - - /** Accelerated one shot F9 - @param key The secret key - @param keylen The key length (octets) - @param in The message - @param inlen Length of message (octets) - @param out [out] Destination for tag - @param outlen [in/out] Initial and final size of out - @return CRYPT_OK on success - @remark Requires manual padding - */ - int (*f9_memory)( - const unsigned char *key, unsigned long keylen, - const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen); -} cipher_descriptor[]; - -#ifdef LTC_BLOWFISH -int blowfish_setup(const unsigned char *key, int keylen, int num_rounds, symmetric_key *skey); -int blowfish_ecb_encrypt(const unsigned char *pt, unsigned char *ct, symmetric_key *skey); -int blowfish_ecb_decrypt(const unsigned char *ct, unsigned char *pt, symmetric_key *skey); -int blowfish_test(void); -void blowfish_done(symmetric_key *skey); -int blowfish_keysize(int *keysize); -extern const struct ltc_cipher_descriptor blowfish_desc; -#endif - -#ifdef LTC_RC5 -int rc5_setup(const unsigned char *key, int keylen, int num_rounds, symmetric_key *skey); -int rc5_ecb_encrypt(const unsigned char *pt, unsigned char *ct, symmetric_key *skey); -int rc5_ecb_decrypt(const unsigned char *ct, unsigned char *pt, symmetric_key *skey); -int rc5_test(void); -void rc5_done(symmetric_key *skey); -int rc5_keysize(int *keysize); -extern const struct ltc_cipher_descriptor rc5_desc; -#endif - -#ifdef LTC_RC6 -int rc6_setup(const unsigned char *key, int keylen, int num_rounds, symmetric_key *skey); -int rc6_ecb_encrypt(const unsigned char *pt, unsigned char *ct, symmetric_key *skey); -int rc6_ecb_decrypt(const unsigned char *ct, unsigned char *pt, symmetric_key *skey); -int rc6_test(void); -void rc6_done(symmetric_key *skey); -int rc6_keysize(int *keysize); -extern const struct ltc_cipher_descriptor rc6_desc; -#endif - -#ifdef LTC_RC2 -int rc2_setup(const unsigned char *key, int keylen, int num_rounds, symmetric_key *skey); -int rc2_ecb_encrypt(const unsigned char *pt, unsigned char *ct, symmetric_key *skey); -int rc2_ecb_decrypt(const unsigned char *ct, unsigned char *pt, symmetric_key *skey); -int rc2_test(void); -void rc2_done(symmetric_key *skey); -int rc2_keysize(int *keysize); -extern const struct ltc_cipher_descriptor rc2_desc; -#endif - -#ifdef LTC_SAFERP -int saferp_setup(const unsigned char *key, int keylen, int num_rounds, symmetric_key *skey); -int saferp_ecb_encrypt(const unsigned char *pt, unsigned char *ct, symmetric_key *skey); -int saferp_ecb_decrypt(const unsigned char *ct, unsigned char *pt, symmetric_key *skey); -int saferp_test(void); -void saferp_done(symmetric_key *skey); -int saferp_keysize(int *keysize); -extern const struct ltc_cipher_descriptor saferp_desc; -#endif - -#ifdef LTC_SAFER -int safer_k64_setup(const unsigned char *key, int keylen, int num_rounds, symmetric_key *skey); -int safer_sk64_setup(const unsigned char *key, int keylen, int num_rounds, symmetric_key *skey); -int safer_k128_setup(const unsigned char *key, int keylen, int num_rounds, symmetric_key *skey); -int safer_sk128_setup(const unsigned char *key, int keylen, int num_rounds, symmetric_key *skey); -int safer_ecb_encrypt(const unsigned char *pt, unsigned char *ct, symmetric_key *key); -int safer_ecb_decrypt(const unsigned char *ct, unsigned char *pt, symmetric_key *key); -int safer_k64_test(void); -int safer_sk64_test(void); -int safer_sk128_test(void); -void safer_done(symmetric_key *skey); -int safer_64_keysize(int *keysize); -int safer_128_keysize(int *keysize); -extern const struct ltc_cipher_descriptor safer_k64_desc, safer_k128_desc, safer_sk64_desc, safer_sk128_desc; -#endif - -#ifdef LTC_RIJNDAEL - -/* make aes an alias */ -#define aes_setup rijndael_setup -#define aes_ecb_encrypt rijndael_ecb_encrypt -#define aes_ecb_decrypt rijndael_ecb_decrypt -#define aes_test rijndael_test -#define aes_done rijndael_done -#define aes_keysize rijndael_keysize - -#define aes_enc_setup rijndael_enc_setup -#define aes_enc_ecb_encrypt rijndael_enc_ecb_encrypt -#define aes_enc_keysize rijndael_enc_keysize - -int rijndael_setup(const unsigned char *key, int keylen, int num_rounds, symmetric_key *skey); -int rijndael_ecb_encrypt(const unsigned char *pt, unsigned char *ct, symmetric_key *skey); -int rijndael_ecb_decrypt(const unsigned char *ct, unsigned char *pt, symmetric_key *skey); -int rijndael_test(void); -void rijndael_done(symmetric_key *skey); -int rijndael_keysize(int *keysize); -int rijndael_enc_setup(const unsigned char *key, int keylen, int num_rounds, symmetric_key *skey); -int rijndael_enc_ecb_encrypt(const unsigned char *pt, unsigned char *ct, symmetric_key *skey); -void rijndael_enc_done(symmetric_key *skey); -int rijndael_enc_keysize(int *keysize); -extern const struct ltc_cipher_descriptor rijndael_desc, aes_desc; -extern const struct ltc_cipher_descriptor rijndael_enc_desc, aes_enc_desc; -#endif - -#ifdef LTC_XTEA -int xtea_setup(const unsigned char *key, int keylen, int num_rounds, symmetric_key *skey); -int xtea_ecb_encrypt(const unsigned char *pt, unsigned char *ct, symmetric_key *skey); -int xtea_ecb_decrypt(const unsigned char *ct, unsigned char *pt, symmetric_key *skey); -int xtea_test(void); -void xtea_done(symmetric_key *skey); -int xtea_keysize(int *keysize); -extern const struct ltc_cipher_descriptor xtea_desc; -#endif - -#ifdef LTC_TWOFISH -int twofish_setup(const unsigned char *key, int keylen, int num_rounds, symmetric_key *skey); -int twofish_ecb_encrypt(const unsigned char *pt, unsigned char *ct, symmetric_key *skey); -int twofish_ecb_decrypt(const unsigned char *ct, unsigned char *pt, symmetric_key *skey); -int twofish_test(void); -void twofish_done(symmetric_key *skey); -int twofish_keysize(int *keysize); -extern const struct ltc_cipher_descriptor twofish_desc; -#endif - -#ifdef LTC_DES -int des_setup(const unsigned char *key, int keylen, int num_rounds, symmetric_key *skey); -int des_ecb_encrypt(const unsigned char *pt, unsigned char *ct, symmetric_key *skey); -int des_ecb_decrypt(const unsigned char *ct, unsigned char *pt, symmetric_key *skey); -int des_test(void); -void des_done(symmetric_key *skey); -int des_keysize(int *keysize); -int des3_setup(const unsigned char *key, int keylen, int num_rounds, symmetric_key *skey); -int des3_ecb_encrypt(const unsigned char *pt, unsigned char *ct, symmetric_key *skey); -int des3_ecb_decrypt(const unsigned char *ct, unsigned char *pt, symmetric_key *skey); -int des3_test(void); -void des3_done(symmetric_key *skey); -int des3_keysize(int *keysize); -extern const struct ltc_cipher_descriptor des_desc, des3_desc; -#endif - -#ifdef LTC_CAST5 -int cast5_setup(const unsigned char *key, int keylen, int num_rounds, symmetric_key *skey); -int cast5_ecb_encrypt(const unsigned char *pt, unsigned char *ct, symmetric_key *skey); -int cast5_ecb_decrypt(const unsigned char *ct, unsigned char *pt, symmetric_key *skey); -int cast5_test(void); -void cast5_done(symmetric_key *skey); -int cast5_keysize(int *keysize); -extern const struct ltc_cipher_descriptor cast5_desc; -#endif - -#ifdef LTC_NOEKEON -int noekeon_setup(const unsigned char *key, int keylen, int num_rounds, symmetric_key *skey); -int noekeon_ecb_encrypt(const unsigned char *pt, unsigned char *ct, symmetric_key *skey); -int noekeon_ecb_decrypt(const unsigned char *ct, unsigned char *pt, symmetric_key *skey); -int noekeon_test(void); -void noekeon_done(symmetric_key *skey); -int noekeon_keysize(int *keysize); -extern const struct ltc_cipher_descriptor noekeon_desc; -#endif - -#ifdef LTC_SKIPJACK -int skipjack_setup(const unsigned char *key, int keylen, int num_rounds, symmetric_key *skey); -int skipjack_ecb_encrypt(const unsigned char *pt, unsigned char *ct, symmetric_key *skey); -int skipjack_ecb_decrypt(const unsigned char *ct, unsigned char *pt, symmetric_key *skey); -int skipjack_test(void); -void skipjack_done(symmetric_key *skey); -int skipjack_keysize(int *keysize); -extern const struct ltc_cipher_descriptor skipjack_desc; -#endif - -#ifdef LTC_KHAZAD -int khazad_setup(const unsigned char *key, int keylen, int num_rounds, symmetric_key *skey); -int khazad_ecb_encrypt(const unsigned char *pt, unsigned char *ct, symmetric_key *skey); -int khazad_ecb_decrypt(const unsigned char *ct, unsigned char *pt, symmetric_key *skey); -int khazad_test(void); -void khazad_done(symmetric_key *skey); -int khazad_keysize(int *keysize); -extern const struct ltc_cipher_descriptor khazad_desc; -#endif - -#ifdef LTC_ANUBIS -int anubis_setup(const unsigned char *key, int keylen, int num_rounds, symmetric_key *skey); -int anubis_ecb_encrypt(const unsigned char *pt, unsigned char *ct, symmetric_key *skey); -int anubis_ecb_decrypt(const unsigned char *ct, unsigned char *pt, symmetric_key *skey); -int anubis_test(void); -void anubis_done(symmetric_key *skey); -int anubis_keysize(int *keysize); -extern const struct ltc_cipher_descriptor anubis_desc; -#endif - -#ifdef LTC_KSEED -int kseed_setup(const unsigned char *key, int keylen, int num_rounds, symmetric_key *skey); -int kseed_ecb_encrypt(const unsigned char *pt, unsigned char *ct, symmetric_key *skey); -int kseed_ecb_decrypt(const unsigned char *ct, unsigned char *pt, symmetric_key *skey); -int kseed_test(void); -void kseed_done(symmetric_key *skey); -int kseed_keysize(int *keysize); -extern const struct ltc_cipher_descriptor kseed_desc; -#endif - -#ifdef LTC_KASUMI -int kasumi_setup(const unsigned char *key, int keylen, int num_rounds, symmetric_key *skey); -int kasumi_ecb_encrypt(const unsigned char *pt, unsigned char *ct, symmetric_key *skey); -int kasumi_ecb_decrypt(const unsigned char *ct, unsigned char *pt, symmetric_key *skey); -int kasumi_test(void); -void kasumi_done(symmetric_key *skey); -int kasumi_keysize(int *keysize); -extern const struct ltc_cipher_descriptor kasumi_desc; -#endif - - -#ifdef LTC_MULTI2 -int multi2_setup(const unsigned char *key, int keylen, int num_rounds, symmetric_key *skey); -int multi2_ecb_encrypt(const unsigned char *pt, unsigned char *ct, symmetric_key *skey); -int multi2_ecb_decrypt(const unsigned char *ct, unsigned char *pt, symmetric_key *skey); -int multi2_test(void); -void multi2_done(symmetric_key *skey); -int multi2_keysize(int *keysize); -extern const struct ltc_cipher_descriptor multi2_desc; -#endif - -#ifdef LTC_ECB_MODE -int ecb_start(int cipher, const unsigned char *key, - int keylen, int num_rounds, symmetric_ECB *ecb); -int ecb_encrypt(const unsigned char *pt, unsigned char *ct, unsigned long len, symmetric_ECB *ecb); -int ecb_decrypt(const unsigned char *ct, unsigned char *pt, unsigned long len, symmetric_ECB *ecb); -int ecb_done(symmetric_ECB *ecb); -#endif - -#ifdef LTC_CFB_MODE -int cfb_start(int cipher, const unsigned char *IV, const unsigned char *key, - int keylen, int num_rounds, symmetric_CFB *cfb); -int cfb_encrypt(const unsigned char *pt, unsigned char *ct, unsigned long len, symmetric_CFB *cfb); -int cfb_decrypt(const unsigned char *ct, unsigned char *pt, unsigned long len, symmetric_CFB *cfb); -int cfb_getiv(unsigned char *IV, unsigned long *len, symmetric_CFB *cfb); -int cfb_setiv(const unsigned char *IV, unsigned long len, symmetric_CFB *cfb); -int cfb_done(symmetric_CFB *cfb); -#endif - -#ifdef LTC_OFB_MODE -int ofb_start(int cipher, const unsigned char *IV, const unsigned char *key, - int keylen, int num_rounds, symmetric_OFB *ofb); -int ofb_encrypt(const unsigned char *pt, unsigned char *ct, unsigned long len, symmetric_OFB *ofb); -int ofb_decrypt(const unsigned char *ct, unsigned char *pt, unsigned long len, symmetric_OFB *ofb); -int ofb_getiv(unsigned char *IV, unsigned long *len, symmetric_OFB *ofb); -int ofb_setiv(const unsigned char *IV, unsigned long len, symmetric_OFB *ofb); -int ofb_done(symmetric_OFB *ofb); -#endif - -#ifdef LTC_CBC_MODE -int cbc_start(int cipher, const unsigned char *IV, const unsigned char *key, - int keylen, int num_rounds, symmetric_CBC *cbc); -int cbc_encrypt(const unsigned char *pt, unsigned char *ct, unsigned long len, symmetric_CBC *cbc); -int cbc_decrypt(const unsigned char *ct, unsigned char *pt, unsigned long len, symmetric_CBC *cbc); -int cbc_getiv(unsigned char *IV, unsigned long *len, symmetric_CBC *cbc); -int cbc_setiv(const unsigned char *IV, unsigned long len, symmetric_CBC *cbc); -int cbc_done(symmetric_CBC *cbc); -#endif - -#ifdef LTC_CTR_MODE - -#define CTR_COUNTER_LITTLE_ENDIAN 0x0000 -#define CTR_COUNTER_BIG_ENDIAN 0x1000 -#define LTC_CTR_RFC3686 0x2000 - -int ctr_start( int cipher, - const unsigned char *IV, - const unsigned char *key, int keylen, - int num_rounds, int ctr_mode, - symmetric_CTR *ctr); -int ctr_encrypt(const unsigned char *pt, unsigned char *ct, unsigned long len, symmetric_CTR *ctr); -int ctr_decrypt(const unsigned char *ct, unsigned char *pt, unsigned long len, symmetric_CTR *ctr); -int ctr_getiv(unsigned char *IV, unsigned long *len, symmetric_CTR *ctr); -int ctr_setiv(const unsigned char *IV, unsigned long len, symmetric_CTR *ctr); -int ctr_done(symmetric_CTR *ctr); -int ctr_test(void); -#endif - -#ifdef LTC_LRW_MODE - -#define LRW_ENCRYPT 0 -#define LRW_DECRYPT 1 - -int lrw_start( int cipher, - const unsigned char *IV, - const unsigned char *key, int keylen, - const unsigned char *tweak, - int num_rounds, - symmetric_LRW *lrw); -int lrw_encrypt(const unsigned char *pt, unsigned char *ct, unsigned long len, symmetric_LRW *lrw); -int lrw_decrypt(const unsigned char *ct, unsigned char *pt, unsigned long len, symmetric_LRW *lrw); -int lrw_getiv(unsigned char *IV, unsigned long *len, symmetric_LRW *lrw); -int lrw_setiv(const unsigned char *IV, unsigned long len, symmetric_LRW *lrw); -int lrw_done(symmetric_LRW *lrw); -int lrw_test(void); - -/* don't call */ -int lrw_process(const unsigned char *pt, unsigned char *ct, unsigned long len, int mode, symmetric_LRW *lrw); -#endif - -#ifdef LTC_F8_MODE -int f8_start( int cipher, const unsigned char *IV, - const unsigned char *key, int keylen, - const unsigned char *salt_key, int skeylen, - int num_rounds, symmetric_F8 *f8); -int f8_encrypt(const unsigned char *pt, unsigned char *ct, unsigned long len, symmetric_F8 *f8); -int f8_decrypt(const unsigned char *ct, unsigned char *pt, unsigned long len, symmetric_F8 *f8); -int f8_getiv(unsigned char *IV, unsigned long *len, symmetric_F8 *f8); -int f8_setiv(const unsigned char *IV, unsigned long len, symmetric_F8 *f8); -int f8_done(symmetric_F8 *f8); -int f8_test_mode(void); -#endif - -#ifdef LTC_XTS_MODE -typedef struct { - symmetric_key key1, key2; - int cipher; -} symmetric_xts; - -int xts_start( int cipher, - const unsigned char *key1, - const unsigned char *key2, - unsigned long keylen, - int num_rounds, - symmetric_xts *xts); - -int xts_encrypt( - const unsigned char *pt, unsigned long ptlen, - unsigned char *ct, - const unsigned char *tweak, - symmetric_xts *xts); -int xts_decrypt( - const unsigned char *ct, unsigned long ptlen, - unsigned char *pt, - const unsigned char *tweak, - symmetric_xts *xts); - -void xts_done(symmetric_xts *xts); -int xts_test(void); -void xts_mult_x(unsigned char *I); -#endif - -int find_cipher(const char *name); -int find_cipher_any(const char *name, int blocklen, int keylen); -int find_cipher_id(unsigned char ID); -int register_cipher(const struct ltc_cipher_descriptor *cipher); -int unregister_cipher(const struct ltc_cipher_descriptor *cipher); -int cipher_is_valid(int idx); - -LTC_MUTEX_PROTO(ltc_cipher_mutex) - -/* $Source: /cvs/libtom/libtomcrypt/src/headers/tomcrypt_cipher.h,v $ */ -/* $Revision: 1.54 $ */ -/* $Date: 2007/05/12 14:37:41 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_custom.h b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_custom.h deleted file mode 100644 index 312a4c2..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_custom.h +++ /dev/null @@ -1,424 +0,0 @@ -#ifndef TOMCRYPT_CUSTOM_H_ -#define TOMCRYPT_CUSTOM_H_ - -#define LTC_NO_CIPHERS -#define LTC_NO_HASHES -#define LTC_NO_MACS -#define LTC_NO_PRNGS -#define LTC_NO_CURVES -#define LTC_NO_MODES -#define LTC_NO_PKCS -#define LTC_NO_ROLC - -#define LTC_SOURCE -#define LTC_SHA1 -#define LTC_MD5 -#define LTC_DER -#define LTC_RC4 - -#define USE_LTM -#define LTM_DESC - -/* macros for various libc functions you can change for embedded targets */ -#ifndef XMALLOC - #ifdef malloc - #define LTC_NO_PROTOTYPES - #endif -#define XMALLOC LibTomMalloc -#endif -#ifndef XREALLOC - #ifdef realloc - #define LTC_NO_PROTOTYPES - #endif -#define XREALLOC LibTomRealloc -#endif -#ifndef XCALLOC - #ifdef calloc - #define LTC_NO_PROTOTYPES - #endif -#define XCALLOC LibTomCalloc -#endif -#ifndef XFREE - #ifdef free - #define LTC_NO_PROTOTYPES - #endif -#define XFREE LibTomFree -#endif - -#ifndef XMEMSET - #ifdef memset - #define LTC_NO_PROTOTYPES_MEMSET - #endif -#define XMEMSET memset -#endif -#ifndef XMEMCPY - #ifdef memcpy - #define LTC_NO_PROTOTYPES_MEMCPY - #endif -#define XMEMCPY memcpy -#endif -#ifndef XMEMCMP - #ifdef memcmp - #define LTC_NO_PROTOTYPES_MEMCMP - #endif -#define XMEMCMP memcmp -#endif -#ifndef XSTRCMP - #ifdef strcmp - #define LTC_NO_PROTOTYPES_STRCMP - #endif -#define XSTRCMP strcmp -#endif - -#ifndef XCLOCK -#define XCLOCK LibTomClock -#endif -#ifndef XCLOCKS_PER_SEC -#define XCLOCKS_PER_SEC CLOCKS_PER_SEC -#endif - -#ifndef XQSORT - #ifdef qsort - #define LTC_NO_PROTOTYPES - #endif -#define XQSORT LibTomQsort -#endif - -/* Easy button? */ -#ifdef LTC_EASY - #define LTC_NO_CIPHERS - #define LTC_RIJNDAEL - #define LTC_BLOWFISH - #define LTC_DES - #define LTC_CAST5 - - #define LTC_NO_MODES - #define LTC_ECB_MODE - #define LTC_CBC_MODE - #define LTC_CTR_MODE - - #define LTC_NO_HASHES - #define LTC_SHA1 - #define LTC_SHA512 - #define LTC_SHA384 - #define LTC_SHA256 - #define LTC_SHA224 - - #define LTC_NO_MACS - #define LTC_HMAC - #define LTC_OMAC - #define LTC_CCM_MODE - - #define LTC_NO_PRNGS - #define LTC_SPRNG - #define LTC_YARROW - #define LTC_DEVRANDOM - #define TRY_URANDOM_FIRST - - #define LTC_NO_PK - #define LTC_MRSA - #define LTC_MECC -#endif - -/* Use small code where possible */ -/* #define LTC_SMALL_CODE */ - -/* Enable self-test test vector checking */ -#ifndef LTC_NO_TEST - #define LTC_TEST -#endif - -/* clean the stack of functions which put private information on stack */ -/* #define LTC_CLEAN_STACK */ - -/* disable all file related functions */ -/* #define LTC_NO_FILE */ - -/* disable all forms of ASM */ -/* #define LTC_NO_ASM */ - -/* disable FAST mode */ -/* #define LTC_NO_FAST */ - -/* disable BSWAP on x86 */ -/* #define LTC_NO_BSWAP */ - -/* ---> Symmetric Block Ciphers <--- */ -#ifndef LTC_NO_CIPHERS - -#define LTC_BLOWFISH -#define LTC_RC2 -#define LTC_RC5 -#define LTC_RC6 -#define LTC_SAFERP -#define LTC_RIJNDAEL -#define LTC_XTEA -/* _TABLES tells it to use tables during setup, _SMALL means to use the smaller scheduled key format - * (saves 4KB of ram), _ALL_TABLES enables all tables during setup */ -#define LTC_TWOFISH -#ifndef LTC_NO_TABLES - #define LTC_TWOFISH_TABLES - /* #define LTC_TWOFISH_ALL_TABLES */ -#else - #define LTC_TWOFISH_SMALL -#endif -/* #define LTC_TWOFISH_SMALL */ -/* LTC_DES includes EDE triple-LTC_DES */ -#define LTC_DES -#define LTC_CAST5 -#define LTC_NOEKEON -#define LTC_SKIPJACK -#define LTC_SAFER -#define LTC_KHAZAD -#define LTC_ANUBIS -#define LTC_ANUBIS_TWEAK -#define LTC_KSEED -#define LTC_KASUMI - -#endif /* LTC_NO_CIPHERS */ - - -/* ---> Block Cipher Modes of Operation <--- */ -#ifndef LTC_NO_MODES - -#define LTC_CFB_MODE -#define LTC_OFB_MODE -#define LTC_ECB_MODE -#define LTC_CBC_MODE -#define LTC_CTR_MODE - -/* F8 chaining mode */ -#define LTC_F8_MODE - -/* LRW mode */ -#define LTC_LRW_MODE -#ifndef LTC_NO_TABLES - /* like GCM mode this will enable 16 8x128 tables [64KB] that make - * seeking very fast. - */ - #define LRW_TABLES -#endif - -/* XTS mode */ -#define LTC_XTS_MODE - -#endif /* LTC_NO_MODES */ - -/* ---> One-Way Hash Functions <--- */ -#ifndef LTC_NO_HASHES - -#define LTC_CHC_HASH -#define LTC_WHIRLPOOL -#define LTC_SHA512 -#define LTC_SHA384 -#define LTC_SHA256 -#define LTC_SHA224 -#define LTC_TIGER -#define LTC_SHA1 -#define LTC_MD5 -#define LTC_MD4 -#define LTC_MD2 -#define LTC_RIPEMD128 -#define LTC_RIPEMD160 -#define LTC_RIPEMD256 -#define LTC_RIPEMD320 - -#endif /* LTC_NO_HASHES */ - -/* ---> MAC functions <--- */ -#ifndef LTC_NO_MACS - -#define LTC_HMAC -#define LTC_OMAC -#define LTC_PMAC -#define LTC_XCBC -#define LTC_F9_MODE -#define LTC_PELICAN - -#if defined(LTC_PELICAN) && !defined(LTC_RIJNDAEL) - #error Pelican-MAC requires LTC_RIJNDAEL -#endif - -/* ---> Encrypt + Authenticate Modes <--- */ - -#define LTC_EAX_MODE -#if defined(LTC_EAX_MODE) && !(defined(LTC_CTR_MODE) && defined(LTC_OMAC)) - #error LTC_EAX_MODE requires CTR and LTC_OMAC mode -#endif - -#define LTC_OCB_MODE -#define LTC_CCM_MODE -#define LTC_GCM_MODE - -/* Use 64KiB tables */ -#ifndef LTC_NO_TABLES - #define LTC_GCM_TABLES -#endif - -/* USE SSE2? requires GCC works on x86_32 and x86_64*/ -#ifdef LTC_GCM_TABLES -/* #define LTC_GCM_TABLES_SSE2 */ -#endif - -#endif /* LTC_NO_MACS */ - -/* Various tidbits of modern neatoness */ -#define LTC_BASE64 - -/* --> Pseudo Random Number Generators <--- */ -#ifndef LTC_NO_PRNGS - -/* Yarrow */ -#define LTC_YARROW -/* which descriptor of AES to use? */ -/* 0 = rijndael_enc 1 = aes_enc, 2 = rijndael [full], 3 = aes [full] */ -#define LTC_YARROW_AES 0 - -#if defined(LTC_YARROW) && !defined(LTC_CTR_MODE) - #error LTC_YARROW requires LTC_CTR_MODE chaining mode to be defined! -#endif - -/* a PRNG that simply reads from an available system source */ -#define LTC_SPRNG - -/* The LTC_RC4 stream cipher */ -#define LTC_RC4 - -/* Fortuna PRNG */ -#define LTC_FORTUNA -/* reseed every N calls to the read function */ -#define LTC_FORTUNA_WD 10 -/* number of pools (4..32) can save a bit of ram by lowering the count */ -#define LTC_FORTUNA_POOLS 32 - -/* Greg's LTC_SOBER128 PRNG ;-0 */ -#define LTC_SOBER128 - -/* the *nix style /dev/random device */ -#define LTC_DEVRANDOM -/* try /dev/urandom before trying /dev/random */ -#define TRY_URANDOM_FIRST - -#endif /* LTC_NO_PRNGS */ - -/* ---> math provider? <--- */ -#ifndef LTC_NO_MATH - -/* LibTomMath */ -#define LTM_LTC_DESC - -/* TomsFastMath */ -//#define TFM_LTC_DESC - -#endif /* LTC_NO_MATH */ - -/* ---> Public Key Crypto <--- */ -#ifndef LTC_NO_PK - -/* Include RSA support */ -#define LTC_MRSA - -/* Include Katja (a Rabin variant like RSA) */ -/* #define MKAT */ - -/* Digital Signature Algorithm */ -#define LTC_MDSA - -/* ECC */ -#define LTC_MECC - -/* use Shamir's trick for point mul (speeds up signature verification) */ -#define LTC_ECC_SHAMIR - -#if defined(TFM_LTC_DESC) && defined(LTC_MECC) - #define LTC_MECC_ACCEL -#endif - -/* do we want fixed point ECC */ -/* #define LTC_MECC_FP */ - -/* Timing Resistant? */ -/* #define LTC_ECC_TIMING_RESISTANT */ - -#endif /* LTC_NO_PK */ - -/* LTC_PKCS #1 (RSA) and #5 (Password Handling) stuff */ -#ifndef LTC_NO_PKCS - -#define LTC_PKCS_1 -#define LTC_PKCS_5 - -/* Include ASN.1 DER (required by DSA/RSA) */ -#define LTC_DER - -#endif /* LTC_NO_PKCS */ - -/* cleanup */ - -#ifdef LTC_MECC -/* Supported ECC Key Sizes */ -#ifndef LTC_NO_CURVES - #define ECC112 - #define ECC128 - #define ECC160 - #define ECC192 - #define ECC224 - #define ECC256 - #define ECC384 - #define ECC521 -#endif -#endif - -#if defined(LTC_MECC) || defined(LTC_MRSA) || defined(LTC_MDSA) || defined(MKATJA) - /* Include the MPI functionality? (required by the PK algorithms) */ - #define MPI -#endif - -#ifdef LTC_MRSA - #define LTC_PKCS_1 -#endif - -#if defined(LTC_DER) && !defined(MPI) - #error ASN.1 DER requires MPI functionality -#endif - -#if (defined(LTC_MDSA) || defined(LTC_MRSA) || defined(LTC_MECC) || defined(MKATJA)) && !defined(LTC_DER) - #error PK requires ASN.1 DER functionality, make sure LTC_DER is enabled -#endif - -/* THREAD management */ -#ifdef LTC_PTHREAD - -#include - -#define LTC_MUTEX_GLOBAL(x) pthread_mutex_t x = PTHREAD_MUTEX_INITIALIZER; -#define LTC_MUTEX_PROTO(x) extern pthread_mutex_t x; -#define LTC_MUTEX_TYPE(x) pthread_mutex_t x; -#define LTC_MUTEX_INIT(x) pthread_mutex_init(x, NULL); -#define LTC_MUTEX_LOCK(x) pthread_mutex_lock(x); -#define LTC_MUTEX_UNLOCK(x) pthread_mutex_unlock(x); - -#else - -/* default no functions */ -#define LTC_MUTEX_GLOBAL(x) -#define LTC_MUTEX_PROTO(x) -#define LTC_MUTEX_TYPE(x) -#define LTC_MUTEX_INIT(x) -#define LTC_MUTEX_LOCK(x) -#define LTC_MUTEX_UNLOCK(x) - -#endif - -/* Debuggers */ - -/* define this if you use Valgrind, note: it CHANGES the way SOBER-128 and LTC_RC4 work (see the code) */ -/* #define LTC_VALGRIND */ - -#endif - - - -/* $Source: /cvs/libtom/libtomcrypt/src/headers/tomcrypt_custom.h,v $ */ -/* $Revision: 1.73 $ */ -/* $Date: 2007/05/12 14:37:41 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_hash.h b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_hash.h deleted file mode 100644 index 18553eb..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_hash.h +++ /dev/null @@ -1,378 +0,0 @@ -/* ---- HASH FUNCTIONS ---- */ -#ifdef LTC_SHA512 -struct sha512_state { - ulong64 length, state[8]; - unsigned long curlen; - unsigned char buf[128]; -}; -#endif - -#ifdef LTC_SHA256 -struct sha256_state { - ulong64 length; - ulong32 state[8], curlen; - unsigned char buf[64]; -}; -#endif - -#ifdef LTC_SHA1 -struct sha1_state { - ulong64 length; - ulong32 state[5], curlen; - unsigned char buf[64]; -}; -#endif - -#ifdef LTC_MD5 -struct md5_state { - ulong64 length; - ulong32 state[4], curlen; - unsigned char buf[64]; -}; -#endif - -#ifdef LTC_MD4 -struct md4_state { - ulong64 length; - ulong32 state[4], curlen; - unsigned char buf[64]; -}; -#endif - -#ifdef LTC_TIGER -struct tiger_state { - ulong64 state[3], length; - unsigned long curlen; - unsigned char buf[64]; -}; -#endif - -#ifdef LTC_MD2 -struct md2_state { - unsigned char chksum[16], X[48], buf[16]; - unsigned long curlen; -}; -#endif - -#ifdef LTC_RIPEMD128 -struct rmd128_state { - ulong64 length; - unsigned char buf[64]; - ulong32 curlen, state[4]; -}; -#endif - -#ifdef LTC_RIPEMD160 -struct rmd160_state { - ulong64 length; - unsigned char buf[64]; - ulong32 curlen, state[5]; -}; -#endif - -#ifdef LTC_RIPEMD256 -struct rmd256_state { - ulong64 length; - unsigned char buf[64]; - ulong32 curlen, state[8]; -}; -#endif - -#ifdef LTC_RIPEMD320 -struct rmd320_state { - ulong64 length; - unsigned char buf[64]; - ulong32 curlen, state[10]; -}; -#endif - -#ifdef LTC_WHIRLPOOL -struct whirlpool_state { - ulong64 length, state[8]; - unsigned char buf[64]; - ulong32 curlen; -}; -#endif - -#ifdef LTC_CHC_HASH -struct chc_state { - ulong64 length; - unsigned char state[MAXBLOCKSIZE], buf[MAXBLOCKSIZE]; - ulong32 curlen; -}; -#endif - -typedef union Hash_state { -#ifdef LTC_CHC_HASH - struct chc_state chc; -#endif -#ifdef LTC_WHIRLPOOL - struct whirlpool_state whirlpool; -#endif -#ifdef LTC_SHA512 - struct sha512_state sha512; -#endif -#ifdef LTC_SHA256 - struct sha256_state sha256; -#endif -#ifdef LTC_SHA1 - struct sha1_state sha1; -#endif -#ifdef LTC_MD5 - struct md5_state md5; -#endif -#ifdef LTC_MD4 - struct md4_state md4; -#endif -#ifdef LTC_MD2 - struct md2_state md2; -#endif -#ifdef LTC_TIGER - struct tiger_state tiger; -#endif -#ifdef LTC_RIPEMD128 - struct rmd128_state rmd128; -#endif -#ifdef LTC_RIPEMD160 - struct rmd160_state rmd160; -#endif -#ifdef LTC_RIPEMD256 - struct rmd256_state rmd256; -#endif -#ifdef LTC_RIPEMD320 - struct rmd320_state rmd320; -#endif - void *data; -} hash_state; - -/** hash descriptor */ -extern struct ltc_hash_descriptor { - /** name of hash */ - char *name; - /** internal ID */ - unsigned char ID; - /** Size of digest in octets */ - unsigned long hashsize; - /** Input block size in octets */ - unsigned long blocksize; - /** ASN.1 OID */ - unsigned long OID[16]; - /** Length of DER encoding */ - unsigned long OIDlen; - - /** Init a hash state - @param hash The hash to initialize - @return CRYPT_OK if successful - */ - int (*init)(hash_state *hash); - /** Process a block of data - @param hash The hash state - @param in The data to hash - @param inlen The length of the data (octets) - @return CRYPT_OK if successful - */ - int (*process)(hash_state *hash, const unsigned char *in, unsigned long inlen); - /** Produce the digest and store it - @param hash The hash state - @param out [out] The destination of the digest - @return CRYPT_OK if successful - */ - int (*done)(hash_state *hash, unsigned char *out); - /** Self-test - @return CRYPT_OK if successful, CRYPT_NOP if self-tests have been disabled - */ - int (*test)(void); - - /* accelerated hmac callback: if you need to-do multiple packets just use the generic hmac_memory and provide a hash callback */ - int (*hmac_block)(const unsigned char *key, unsigned long keylen, - const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen); - -} hash_descriptor[]; - -#ifdef LTC_CHC_HASH -int chc_register(int cipher); -int chc_init(hash_state * md); -int chc_process(hash_state * md, const unsigned char *in, unsigned long inlen); -int chc_done(hash_state * md, unsigned char *hash); -int chc_test(void); -extern const struct ltc_hash_descriptor chc_desc; -#endif - -#ifdef LTC_WHIRLPOOL -int whirlpool_init(hash_state * md); -int whirlpool_process(hash_state * md, const unsigned char *in, unsigned long inlen); -int whirlpool_done(hash_state * md, unsigned char *hash); -int whirlpool_test(void); -extern const struct ltc_hash_descriptor whirlpool_desc; -#endif - -#ifdef LTC_SHA512 -int sha512_init(hash_state * md); -int sha512_process(hash_state * md, const unsigned char *in, unsigned long inlen); -int sha512_done(hash_state * md, unsigned char *hash); -int sha512_test(void); -extern const struct ltc_hash_descriptor sha512_desc; -#endif - -#ifdef LTC_SHA384 -#ifndef LTC_SHA512 - #error LTC_SHA512 is required for LTC_SHA384 -#endif -int sha384_init(hash_state * md); -#define sha384_process sha512_process -int sha384_done(hash_state * md, unsigned char *hash); -int sha384_test(void); -extern const struct ltc_hash_descriptor sha384_desc; -#endif - -#ifdef LTC_SHA256 -int sha256_init(hash_state * md); -int sha256_process(hash_state * md, const unsigned char *in, unsigned long inlen); -int sha256_done(hash_state * md, unsigned char *hash); -int sha256_test(void); -extern const struct ltc_hash_descriptor sha256_desc; - -#ifdef LTC_SHA224 -#ifndef LTC_SHA256 - #error LTC_SHA256 is required for LTC_SHA224 -#endif -int sha224_init(hash_state * md); -#define sha224_process sha256_process -int sha224_done(hash_state * md, unsigned char *hash); -int sha224_test(void); -extern const struct ltc_hash_descriptor sha224_desc; -#endif -#endif - -#ifdef LTC_SHA1 -int sha1_init(hash_state * md); -int sha1_process(hash_state * md, const unsigned char *in, unsigned long inlen); -int sha1_done(hash_state * md, unsigned char *hash); -int sha1_test(void); -extern const struct ltc_hash_descriptor sha1_desc; -#endif - -#ifdef LTC_MD5 -int md5_init(hash_state * md); -int md5_process(hash_state * md, const unsigned char *in, unsigned long inlen); -int md5_done(hash_state * md, unsigned char *hash); -int md5_test(void); -extern const struct ltc_hash_descriptor md5_desc; -#endif - -#ifdef LTC_MD4 -int md4_init(hash_state * md); -int md4_process(hash_state * md, const unsigned char *in, unsigned long inlen); -int md4_done(hash_state * md, unsigned char *hash); -int md4_test(void); -extern const struct ltc_hash_descriptor md4_desc; -#endif - -#ifdef LTC_MD2 -int md2_init(hash_state * md); -int md2_process(hash_state * md, const unsigned char *in, unsigned long inlen); -int md2_done(hash_state * md, unsigned char *hash); -int md2_test(void); -extern const struct ltc_hash_descriptor md2_desc; -#endif - -#ifdef LTC_TIGER -int tiger_init(hash_state * md); -int tiger_process(hash_state * md, const unsigned char *in, unsigned long inlen); -int tiger_done(hash_state * md, unsigned char *hash); -int tiger_test(void); -extern const struct ltc_hash_descriptor tiger_desc; -#endif - -#ifdef LTC_RIPEMD128 -int rmd128_init(hash_state * md); -int rmd128_process(hash_state * md, const unsigned char *in, unsigned long inlen); -int rmd128_done(hash_state * md, unsigned char *hash); -int rmd128_test(void); -extern const struct ltc_hash_descriptor rmd128_desc; -#endif - -#ifdef LTC_RIPEMD160 -int rmd160_init(hash_state * md); -int rmd160_process(hash_state * md, const unsigned char *in, unsigned long inlen); -int rmd160_done(hash_state * md, unsigned char *hash); -int rmd160_test(void); -extern const struct ltc_hash_descriptor rmd160_desc; -#endif - -#ifdef LTC_RIPEMD256 -int rmd256_init(hash_state * md); -int rmd256_process(hash_state * md, const unsigned char *in, unsigned long inlen); -int rmd256_done(hash_state * md, unsigned char *hash); -int rmd256_test(void); -extern const struct ltc_hash_descriptor rmd256_desc; -#endif - -#ifdef LTC_RIPEMD320 -int rmd320_init(hash_state * md); -int rmd320_process(hash_state * md, const unsigned char *in, unsigned long inlen); -int rmd320_done(hash_state * md, unsigned char *hash); -int rmd320_test(void); -extern const struct ltc_hash_descriptor rmd320_desc; -#endif - - -int find_hash(const char *name); -int find_hash_id(unsigned char ID); -int find_hash_oid(const unsigned long *ID, unsigned long IDlen); -int find_hash_any(const char *name, int digestlen); -int register_hash(const struct ltc_hash_descriptor *hash); -int unregister_hash(const struct ltc_hash_descriptor *hash); -int hash_is_valid(int idx); - -LTC_MUTEX_PROTO(ltc_hash_mutex) - -int hash_memory(int hash, - const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen); -int hash_memory_multi(int hash, unsigned char *out, unsigned long *outlen, - const unsigned char *in, unsigned long inlen, ...); -int hash_filehandle(int hash, FILE *in, unsigned char *out, unsigned long *outlen); -int hash_file(int hash, const char *fname, unsigned char *out, unsigned long *outlen); - -/* a simple macro for making hash "process" functions */ -#define HASH_PROCESS(func_name, compress_name, state_var, block_size) \ -int func_name (hash_state * md, const unsigned char *in, unsigned long inlen) \ -{ \ - unsigned long n; \ - int err; \ - LTC_ARGCHK(md != NULL); \ - LTC_ARGCHK(in != NULL); \ - if (md-> state_var .curlen > sizeof(md-> state_var .buf)) { \ - return CRYPT_INVALID_ARG; \ - } \ - while (inlen > 0) { \ - if (md-> state_var .curlen == 0 && inlen >= block_size) { \ - if ((err = compress_name (md, (unsigned char *)in)) != CRYPT_OK) { \ - return err; \ - } \ - md-> state_var .length += block_size * 8; \ - in += block_size; \ - inlen -= block_size; \ - } else { \ - n = MIN(inlen, (block_size - md-> state_var .curlen)); \ - memcpy(md-> state_var .buf + md-> state_var.curlen, in, (size_t)n); \ - md-> state_var .curlen += n; \ - in += n; \ - inlen -= n; \ - if (md-> state_var .curlen == block_size) { \ - if ((err = compress_name (md, md-> state_var .buf)) != CRYPT_OK) { \ - return err; \ - } \ - md-> state_var .length += 8*block_size; \ - md-> state_var .curlen = 0; \ - } \ - } \ - } \ - return CRYPT_OK; \ -} - -/* $Source: /cvs/libtom/libtomcrypt/src/headers/tomcrypt_hash.h,v $ */ -/* $Revision: 1.22 $ */ -/* $Date: 2007/05/12 14:32:35 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_mac.h b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_mac.h deleted file mode 100644 index 7ad9516..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_mac.h +++ /dev/null @@ -1,384 +0,0 @@ -#ifdef LTC_HMAC -typedef struct Hmac_state { - hash_state md; - int hash; - hash_state hashstate; - unsigned char *key; -} hmac_state; - -int hmac_init(hmac_state *hmac, int hash, const unsigned char *key, unsigned long keylen); -int hmac_process(hmac_state *hmac, const unsigned char *in, unsigned long inlen); -int hmac_done(hmac_state *hmac, unsigned char *out, unsigned long *outlen); -int hmac_test(void); -int hmac_memory(int hash, - const unsigned char *key, unsigned long keylen, - const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen); -int hmac_memory_multi(int hash, - const unsigned char *key, unsigned long keylen, - unsigned char *out, unsigned long *outlen, - const unsigned char *in, unsigned long inlen, ...); -int hmac_file(int hash, const char *fname, const unsigned char *key, - unsigned long keylen, - unsigned char *dst, unsigned long *dstlen); -#endif - -#ifdef LTC_OMAC - -typedef struct { - int cipher_idx, - buflen, - blklen; - unsigned char block[MAXBLOCKSIZE], - prev[MAXBLOCKSIZE], - Lu[2][MAXBLOCKSIZE]; - symmetric_key key; -} omac_state; - -int omac_init(omac_state *omac, int cipher, const unsigned char *key, unsigned long keylen); -int omac_process(omac_state *omac, const unsigned char *in, unsigned long inlen); -int omac_done(omac_state *omac, unsigned char *out, unsigned long *outlen); -int omac_memory(int cipher, - const unsigned char *key, unsigned long keylen, - const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen); -int omac_memory_multi(int cipher, - const unsigned char *key, unsigned long keylen, - unsigned char *out, unsigned long *outlen, - const unsigned char *in, unsigned long inlen, ...); -int omac_file(int cipher, - const unsigned char *key, unsigned long keylen, - const char *filename, - unsigned char *out, unsigned long *outlen); -int omac_test(void); -#endif /* LTC_OMAC */ - -#ifdef LTC_PMAC - -typedef struct { - unsigned char Ls[32][MAXBLOCKSIZE], /* L shifted by i bits to the left */ - Li[MAXBLOCKSIZE], /* value of Li [current value, we calc from previous recall] */ - Lr[MAXBLOCKSIZE], /* L * x^-1 */ - block[MAXBLOCKSIZE], /* currently accumulated block */ - checksum[MAXBLOCKSIZE]; /* current checksum */ - - symmetric_key key; /* scheduled key for cipher */ - unsigned long block_index; /* index # for current block */ - int cipher_idx, /* cipher idx */ - block_len, /* length of block */ - buflen; /* number of bytes in the buffer */ -} pmac_state; - -int pmac_init(pmac_state *pmac, int cipher, const unsigned char *key, unsigned long keylen); -int pmac_process(pmac_state *pmac, const unsigned char *in, unsigned long inlen); -int pmac_done(pmac_state *pmac, unsigned char *out, unsigned long *outlen); - -int pmac_memory(int cipher, - const unsigned char *key, unsigned long keylen, - const unsigned char *msg, unsigned long msglen, - unsigned char *out, unsigned long *outlen); - -int pmac_memory_multi(int cipher, - const unsigned char *key, unsigned long keylen, - unsigned char *out, unsigned long *outlen, - const unsigned char *in, unsigned long inlen, ...); - -int pmac_file(int cipher, - const unsigned char *key, unsigned long keylen, - const char *filename, - unsigned char *out, unsigned long *outlen); - -int pmac_test(void); - -/* internal functions */ -int pmac_ntz(unsigned long x); -void pmac_shift_xor(pmac_state *pmac); - -#endif /* PMAC */ - -#ifdef LTC_EAX_MODE - -#if !(defined(LTC_OMAC) && defined(LTC_CTR_MODE)) - #error LTC_EAX_MODE requires LTC_OMAC and CTR -#endif - -typedef struct { - unsigned char N[MAXBLOCKSIZE]; - symmetric_CTR ctr; - omac_state headeromac, ctomac; -} eax_state; - -int eax_init(eax_state *eax, int cipher, const unsigned char *key, unsigned long keylen, - const unsigned char *nonce, unsigned long noncelen, - const unsigned char *header, unsigned long headerlen); - -int eax_encrypt(eax_state *eax, const unsigned char *pt, unsigned char *ct, unsigned long length); -int eax_decrypt(eax_state *eax, const unsigned char *ct, unsigned char *pt, unsigned long length); -int eax_addheader(eax_state *eax, const unsigned char *header, unsigned long length); -int eax_done(eax_state *eax, unsigned char *tag, unsigned long *taglen); - -int eax_encrypt_authenticate_memory(int cipher, - const unsigned char *key, unsigned long keylen, - const unsigned char *nonce, unsigned long noncelen, - const unsigned char *header, unsigned long headerlen, - const unsigned char *pt, unsigned long ptlen, - unsigned char *ct, - unsigned char *tag, unsigned long *taglen); - -int eax_decrypt_verify_memory(int cipher, - const unsigned char *key, unsigned long keylen, - const unsigned char *nonce, unsigned long noncelen, - const unsigned char *header, unsigned long headerlen, - const unsigned char *ct, unsigned long ctlen, - unsigned char *pt, - unsigned char *tag, unsigned long taglen, - int *stat); - - int eax_test(void); -#endif /* EAX MODE */ - -#ifdef LTC_OCB_MODE -typedef struct { - unsigned char L[MAXBLOCKSIZE], /* L value */ - Ls[32][MAXBLOCKSIZE], /* L shifted by i bits to the left */ - Li[MAXBLOCKSIZE], /* value of Li [current value, we calc from previous recall] */ - Lr[MAXBLOCKSIZE], /* L * x^-1 */ - R[MAXBLOCKSIZE], /* R value */ - checksum[MAXBLOCKSIZE]; /* current checksum */ - - symmetric_key key; /* scheduled key for cipher */ - unsigned long block_index; /* index # for current block */ - int cipher, /* cipher idx */ - block_len; /* length of block */ -} ocb_state; - -int ocb_init(ocb_state *ocb, int cipher, - const unsigned char *key, unsigned long keylen, const unsigned char *nonce); - -int ocb_encrypt(ocb_state *ocb, const unsigned char *pt, unsigned char *ct); -int ocb_decrypt(ocb_state *ocb, const unsigned char *ct, unsigned char *pt); - -int ocb_done_encrypt(ocb_state *ocb, - const unsigned char *pt, unsigned long ptlen, - unsigned char *ct, - unsigned char *tag, unsigned long *taglen); - -int ocb_done_decrypt(ocb_state *ocb, - const unsigned char *ct, unsigned long ctlen, - unsigned char *pt, - const unsigned char *tag, unsigned long taglen, int *stat); - -int ocb_encrypt_authenticate_memory(int cipher, - const unsigned char *key, unsigned long keylen, - const unsigned char *nonce, - const unsigned char *pt, unsigned long ptlen, - unsigned char *ct, - unsigned char *tag, unsigned long *taglen); - -int ocb_decrypt_verify_memory(int cipher, - const unsigned char *key, unsigned long keylen, - const unsigned char *nonce, - const unsigned char *ct, unsigned long ctlen, - unsigned char *pt, - const unsigned char *tag, unsigned long taglen, - int *stat); - -int ocb_test(void); - -/* internal functions */ -void ocb_shift_xor(ocb_state *ocb, unsigned char *Z); -int ocb_ntz(unsigned long x); -int s_ocb_done(ocb_state *ocb, const unsigned char *pt, unsigned long ptlen, - unsigned char *ct, unsigned char *tag, unsigned long *taglen, int mode); - -#endif /* LTC_OCB_MODE */ - -#ifdef LTC_CCM_MODE - -#define CCM_ENCRYPT 0 -#define CCM_DECRYPT 1 - -int ccm_memory(int cipher, - const unsigned char *key, unsigned long keylen, - symmetric_key *uskey, - const unsigned char *nonce, unsigned long noncelen, - const unsigned char *header, unsigned long headerlen, - unsigned char *pt, unsigned long ptlen, - unsigned char *ct, - unsigned char *tag, unsigned long *taglen, - int direction); - -int ccm_test(void); - -#endif /* LTC_CCM_MODE */ - -#if defined(LRW_MODE) || defined(LTC_GCM_MODE) -void gcm_gf_mult(const unsigned char *a, const unsigned char *b, unsigned char *c); -#endif - - -/* table shared between GCM and LRW */ -#if defined(LTC_GCM_TABLES) || defined(LRW_TABLES) || ((defined(LTC_GCM_MODE) || defined(LTC_GCM_MODE)) && defined(LTC_FAST)) -extern const unsigned char gcm_shift_table[]; -#endif - -#ifdef LTC_GCM_MODE - -#define GCM_ENCRYPT 0 -#define GCM_DECRYPT 1 - -#define LTC_GCM_MODE_IV 0 -#define LTC_GCM_MODE_AAD 1 -#define LTC_GCM_MODE_TEXT 2 - -typedef struct { - symmetric_key K; - unsigned char H[16], /* multiplier */ - X[16], /* accumulator */ - Y[16], /* counter */ - Y_0[16], /* initial counter */ - buf[16]; /* buffer for stuff */ - - int cipher, /* which cipher */ - ivmode, /* Which mode is the IV in? */ - mode, /* mode the GCM code is in */ - buflen; /* length of data in buf */ - - ulong64 totlen, /* 64-bit counter used for IV and AAD */ - pttotlen; /* 64-bit counter for the PT */ - -#ifdef LTC_GCM_TABLES - unsigned char PC[16][256][16] /* 16 tables of 8x128 */ -#ifdef LTC_GCM_TABLES_SSE2 -__attribute__ ((aligned (16))) -#endif -; -#endif -} gcm_state; - -void gcm_mult_h(gcm_state *gcm, unsigned char *I); - -int gcm_init(gcm_state *gcm, int cipher, - const unsigned char *key, int keylen); - -int gcm_reset(gcm_state *gcm); - -int gcm_add_iv(gcm_state *gcm, - const unsigned char *IV, unsigned long IVlen); - -int gcm_add_aad(gcm_state *gcm, - const unsigned char *adata, unsigned long adatalen); - -int gcm_process(gcm_state *gcm, - unsigned char *pt, unsigned long ptlen, - unsigned char *ct, - int direction); - -int gcm_done(gcm_state *gcm, - unsigned char *tag, unsigned long *taglen); - -int gcm_memory( int cipher, - const unsigned char *key, unsigned long keylen, - const unsigned char *IV, unsigned long IVlen, - const unsigned char *adata, unsigned long adatalen, - unsigned char *pt, unsigned long ptlen, - unsigned char *ct, - unsigned char *tag, unsigned long *taglen, - int direction); -int gcm_test(void); - -#endif /* LTC_GCM_MODE */ - -#ifdef LTC_PELICAN - -typedef struct pelican_state -{ - symmetric_key K; - unsigned char state[16]; - int buflen; -} pelican_state; - -int pelican_init(pelican_state *pelmac, const unsigned char *key, unsigned long keylen); -int pelican_process(pelican_state *pelmac, const unsigned char *in, unsigned long inlen); -int pelican_done(pelican_state *pelmac, unsigned char *out); -int pelican_test(void); - -int pelican_memory(const unsigned char *key, unsigned long keylen, - const unsigned char *in, unsigned long inlen, - unsigned char *out); - -#endif - -#ifdef LTC_XCBC - -/* add this to "keylen" to xcbc_init to use a pure three-key XCBC MAC */ -#define LTC_XCBC_PURE 0x8000UL - -typedef struct { - unsigned char K[3][MAXBLOCKSIZE], - IV[MAXBLOCKSIZE]; - - symmetric_key key; - - int cipher, - buflen, - blocksize; -} xcbc_state; - -int xcbc_init(xcbc_state *xcbc, int cipher, const unsigned char *key, unsigned long keylen); -int xcbc_process(xcbc_state *xcbc, const unsigned char *in, unsigned long inlen); -int xcbc_done(xcbc_state *xcbc, unsigned char *out, unsigned long *outlen); -int xcbc_memory(int cipher, - const unsigned char *key, unsigned long keylen, - const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen); -int xcbc_memory_multi(int cipher, - const unsigned char *key, unsigned long keylen, - unsigned char *out, unsigned long *outlen, - const unsigned char *in, unsigned long inlen, ...); -int xcbc_file(int cipher, - const unsigned char *key, unsigned long keylen, - const char *filename, - unsigned char *out, unsigned long *outlen); -int xcbc_test(void); - -#endif - -#ifdef LTC_F9_MODE - -typedef struct { - unsigned char akey[MAXBLOCKSIZE], - ACC[MAXBLOCKSIZE], - IV[MAXBLOCKSIZE]; - - symmetric_key key; - - int cipher, - buflen, - keylen, - blocksize; -} f9_state; - -int f9_init(f9_state *f9, int cipher, const unsigned char *key, unsigned long keylen); -int f9_process(f9_state *f9, const unsigned char *in, unsigned long inlen); -int f9_done(f9_state *f9, unsigned char *out, unsigned long *outlen); -int f9_memory(int cipher, - const unsigned char *key, unsigned long keylen, - const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen); -int f9_memory_multi(int cipher, - const unsigned char *key, unsigned long keylen, - unsigned char *out, unsigned long *outlen, - const unsigned char *in, unsigned long inlen, ...); -int f9_file(int cipher, - const unsigned char *key, unsigned long keylen, - const char *filename, - unsigned char *out, unsigned long *outlen); -int f9_test(void); - -#endif - - -/* $Source: /cvs/libtom/libtomcrypt/src/headers/tomcrypt_mac.h,v $ */ -/* $Revision: 1.23 $ */ -/* $Date: 2007/05/12 14:37:41 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_macros.h b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_macros.h deleted file mode 100644 index 53bda9b..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_macros.h +++ /dev/null @@ -1,424 +0,0 @@ -/* fix for MSVC ...evil! */ -#ifdef _MSC_VER - #define CONST64(n) n ## ui64 - typedef unsigned __int64 ulong64; -#else - #define CONST64(n) n ## ULL - typedef unsigned long long ulong64; -#endif - -/* this is the "32-bit at least" data type - * Re-define it to suit your platform but it must be at least 32-bits - */ -#if defined(__x86_64__) || (defined(__sparc__) && defined(__arch64__)) - typedef unsigned ulong32; -#else - typedef unsigned long ulong32; -#endif - -/* ---- HELPER MACROS ---- */ -#ifdef ENDIAN_NEUTRAL - -#define STORE32L(x, y) \ - { (y)[3] = (unsigned char)(((x)>>24)&255); (y)[2] = (unsigned char)(((x)>>16)&255); \ - (y)[1] = (unsigned char)(((x)>>8)&255); (y)[0] = (unsigned char)((x)&255); } - -#define LOAD32L(x, y) \ - { x = ((unsigned long)((y)[3] & 255)<<24) | \ - ((unsigned long)((y)[2] & 255)<<16) | \ - ((unsigned long)((y)[1] & 255)<<8) | \ - ((unsigned long)((y)[0] & 255)); } - -#define STORE64L(x, y) \ - { (y)[7] = (unsigned char)(((x)>>56)&255); (y)[6] = (unsigned char)(((x)>>48)&255); \ - (y)[5] = (unsigned char)(((x)>>40)&255); (y)[4] = (unsigned char)(((x)>>32)&255); \ - (y)[3] = (unsigned char)(((x)>>24)&255); (y)[2] = (unsigned char)(((x)>>16)&255); \ - (y)[1] = (unsigned char)(((x)>>8)&255); (y)[0] = (unsigned char)((x)&255); } - -#define LOAD64L(x, y) \ - { x = (((ulong64)((y)[7] & 255))<<56)|(((ulong64)((y)[6] & 255))<<48)| \ - (((ulong64)((y)[5] & 255))<<40)|(((ulong64)((y)[4] & 255))<<32)| \ - (((ulong64)((y)[3] & 255))<<24)|(((ulong64)((y)[2] & 255))<<16)| \ - (((ulong64)((y)[1] & 255))<<8)|(((ulong64)((y)[0] & 255))); } - -#define STORE32H(x, y) \ - { (y)[0] = (unsigned char)(((x)>>24)&255); (y)[1] = (unsigned char)(((x)>>16)&255); \ - (y)[2] = (unsigned char)(((x)>>8)&255); (y)[3] = (unsigned char)((x)&255); } - -#define LOAD32H(x, y) \ - { x = ((unsigned long)((y)[0] & 255)<<24) | \ - ((unsigned long)((y)[1] & 255)<<16) | \ - ((unsigned long)((y)[2] & 255)<<8) | \ - ((unsigned long)((y)[3] & 255)); } - -#define STORE64H(x, y) \ - { (y)[0] = (unsigned char)(((x)>>56)&255); (y)[1] = (unsigned char)(((x)>>48)&255); \ - (y)[2] = (unsigned char)(((x)>>40)&255); (y)[3] = (unsigned char)(((x)>>32)&255); \ - (y)[4] = (unsigned char)(((x)>>24)&255); (y)[5] = (unsigned char)(((x)>>16)&255); \ - (y)[6] = (unsigned char)(((x)>>8)&255); (y)[7] = (unsigned char)((x)&255); } - -#define LOAD64H(x, y) \ - { x = (((ulong64)((y)[0] & 255))<<56)|(((ulong64)((y)[1] & 255))<<48) | \ - (((ulong64)((y)[2] & 255))<<40)|(((ulong64)((y)[3] & 255))<<32) | \ - (((ulong64)((y)[4] & 255))<<24)|(((ulong64)((y)[5] & 255))<<16) | \ - (((ulong64)((y)[6] & 255))<<8)|(((ulong64)((y)[7] & 255))); } - -#endif /* ENDIAN_NEUTRAL */ - -#ifdef ENDIAN_LITTLE - -#if !defined(LTC_NO_BSWAP) && (defined(INTEL_CC) || (defined(__GNUC__) && (defined(__DJGPP__) || defined(__CYGWIN__) || defined(__MINGW32__) || defined(__i386__) || defined(__x86_64__)))) - -#define STORE32H(x, y) \ -asm __volatile__ ( \ - "bswapl %0 \n\t" \ - "movl %0,(%1)\n\t" \ - "bswapl %0 \n\t" \ - ::"r"(x), "r"(y)); - -#define LOAD32H(x, y) \ -asm __volatile__ ( \ - "movl (%1),%0\n\t" \ - "bswapl %0\n\t" \ - :"=r"(x): "r"(y)); - -#else - -#define STORE32H(x, y) \ - { (y)[0] = (unsigned char)(((x)>>24)&255); (y)[1] = (unsigned char)(((x)>>16)&255); \ - (y)[2] = (unsigned char)(((x)>>8)&255); (y)[3] = (unsigned char)((x)&255); } - -#define LOAD32H(x, y) \ - { x = ((unsigned long)((y)[0] & 255)<<24) | \ - ((unsigned long)((y)[1] & 255)<<16) | \ - ((unsigned long)((y)[2] & 255)<<8) | \ - ((unsigned long)((y)[3] & 255)); } - -#endif - - -/* x86_64 processor */ -#if !defined(LTC_NO_BSWAP) && (defined(__GNUC__) && defined(__x86_64__)) - -#define STORE64H(x, y) \ -asm __volatile__ ( \ - "bswapq %0 \n\t" \ - "movq %0,(%1)\n\t" \ - "bswapq %0 \n\t" \ - ::"r"(x), "r"(y)); - -#define LOAD64H(x, y) \ -asm __volatile__ ( \ - "movq (%1),%0\n\t" \ - "bswapq %0\n\t" \ - :"=r"(x): "r"(y)); - -#else - -#define STORE64H(x, y) \ - { (y)[0] = (unsigned char)(((x)>>56)&255); (y)[1] = (unsigned char)(((x)>>48)&255); \ - (y)[2] = (unsigned char)(((x)>>40)&255); (y)[3] = (unsigned char)(((x)>>32)&255); \ - (y)[4] = (unsigned char)(((x)>>24)&255); (y)[5] = (unsigned char)(((x)>>16)&255); \ - (y)[6] = (unsigned char)(((x)>>8)&255); (y)[7] = (unsigned char)((x)&255); } - -#define LOAD64H(x, y) \ - { x = (((ulong64)((y)[0] & 255))<<56)|(((ulong64)((y)[1] & 255))<<48) | \ - (((ulong64)((y)[2] & 255))<<40)|(((ulong64)((y)[3] & 255))<<32) | \ - (((ulong64)((y)[4] & 255))<<24)|(((ulong64)((y)[5] & 255))<<16) | \ - (((ulong64)((y)[6] & 255))<<8)|(((ulong64)((y)[7] & 255))); } - -#endif - -#ifdef ENDIAN_32BITWORD - -#define STORE32L(x, y) \ - { ulong32 __t = (x); XMEMCPY(y, &__t, 4); } - -#define LOAD32L(x, y) \ - XMEMCPY(&(x), y, 4); - -#define STORE64L(x, y) \ - { (y)[7] = (unsigned char)(((x)>>56)&255); (y)[6] = (unsigned char)(((x)>>48)&255); \ - (y)[5] = (unsigned char)(((x)>>40)&255); (y)[4] = (unsigned char)(((x)>>32)&255); \ - (y)[3] = (unsigned char)(((x)>>24)&255); (y)[2] = (unsigned char)(((x)>>16)&255); \ - (y)[1] = (unsigned char)(((x)>>8)&255); (y)[0] = (unsigned char)((x)&255); } - -#define LOAD64L(x, y) \ - { x = (((ulong64)((y)[7] & 255))<<56)|(((ulong64)((y)[6] & 255))<<48)| \ - (((ulong64)((y)[5] & 255))<<40)|(((ulong64)((y)[4] & 255))<<32)| \ - (((ulong64)((y)[3] & 255))<<24)|(((ulong64)((y)[2] & 255))<<16)| \ - (((ulong64)((y)[1] & 255))<<8)|(((ulong64)((y)[0] & 255))); } - -#else /* 64-bit words then */ - -#define STORE32L(x, y) \ - { ulong32 __t = (x); XMEMCPY(y, &__t, 4); } - -#define LOAD32L(x, y) \ - { XMEMCPY(&(x), y, 4); x &= 0xFFFFFFFF; } - -#define STORE64L(x, y) \ - { ulong64 __t = (x); XMEMCPY(y, &__t, 8); } - -#define LOAD64L(x, y) \ - { XMEMCPY(&(x), y, 8); } - -#endif /* ENDIAN_64BITWORD */ - -#endif /* ENDIAN_LITTLE */ - -#ifdef ENDIAN_BIG -#define STORE32L(x, y) \ - { (y)[3] = (unsigned char)(((x)>>24)&255); (y)[2] = (unsigned char)(((x)>>16)&255); \ - (y)[1] = (unsigned char)(((x)>>8)&255); (y)[0] = (unsigned char)((x)&255); } - -#define LOAD32L(x, y) \ - { x = ((unsigned long)((y)[3] & 255)<<24) | \ - ((unsigned long)((y)[2] & 255)<<16) | \ - ((unsigned long)((y)[1] & 255)<<8) | \ - ((unsigned long)((y)[0] & 255)); } - -#define STORE64L(x, y) \ - { (y)[7] = (unsigned char)(((x)>>56)&255); (y)[6] = (unsigned char)(((x)>>48)&255); \ - (y)[5] = (unsigned char)(((x)>>40)&255); (y)[4] = (unsigned char)(((x)>>32)&255); \ - (y)[3] = (unsigned char)(((x)>>24)&255); (y)[2] = (unsigned char)(((x)>>16)&255); \ - (y)[1] = (unsigned char)(((x)>>8)&255); (y)[0] = (unsigned char)((x)&255); } - -#define LOAD64L(x, y) \ - { x = (((ulong64)((y)[7] & 255))<<56)|(((ulong64)((y)[6] & 255))<<48) | \ - (((ulong64)((y)[5] & 255))<<40)|(((ulong64)((y)[4] & 255))<<32) | \ - (((ulong64)((y)[3] & 255))<<24)|(((ulong64)((y)[2] & 255))<<16) | \ - (((ulong64)((y)[1] & 255))<<8)|(((ulong64)((y)[0] & 255))); } - -#ifdef ENDIAN_32BITWORD - -#define STORE32H(x, y) \ - { ulong32 __t = (x); XMEMCPY(y, &__t, 4); } - -#define LOAD32H(x, y) \ - XMEMCPY(&(x), y, 4); - -#define STORE64H(x, y) \ - { (y)[0] = (unsigned char)(((x)>>56)&255); (y)[1] = (unsigned char)(((x)>>48)&255); \ - (y)[2] = (unsigned char)(((x)>>40)&255); (y)[3] = (unsigned char)(((x)>>32)&255); \ - (y)[4] = (unsigned char)(((x)>>24)&255); (y)[5] = (unsigned char)(((x)>>16)&255); \ - (y)[6] = (unsigned char)(((x)>>8)&255); (y)[7] = (unsigned char)((x)&255); } - -#define LOAD64H(x, y) \ - { x = (((ulong64)((y)[0] & 255))<<56)|(((ulong64)((y)[1] & 255))<<48)| \ - (((ulong64)((y)[2] & 255))<<40)|(((ulong64)((y)[3] & 255))<<32)| \ - (((ulong64)((y)[4] & 255))<<24)|(((ulong64)((y)[5] & 255))<<16)| \ - (((ulong64)((y)[6] & 255))<<8)| (((ulong64)((y)[7] & 255))); } - -#else /* 64-bit words then */ - -#define STORE32H(x, y) \ - { ulong32 __t = (x); XMEMCPY(y, &__t, 4); } - -#define LOAD32H(x, y) \ - { XMEMCPY(&(x), y, 4); x &= 0xFFFFFFFF; } - -#define STORE64H(x, y) \ - { ulong64 __t = (x); XMEMCPY(y, &__t, 8); } - -#define LOAD64H(x, y) \ - { XMEMCPY(&(x), y, 8); } - -#endif /* ENDIAN_64BITWORD */ -#endif /* ENDIAN_BIG */ - -#define BSWAP(x) ( ((x>>24)&0x000000FFUL) | ((x<<24)&0xFF000000UL) | \ - ((x>>8)&0x0000FF00UL) | ((x<<8)&0x00FF0000UL) ) - - -/* 32-bit Rotates */ -#if defined(_MSC_VER) - -/* instrinsic rotate */ -#include -#pragma intrinsic(_lrotr,_lrotl) -#define ROR(x,n) _lrotr(x,n) -#define ROL(x,n) _lrotl(x,n) -#define RORc(x,n) _lrotr(x,n) -#define ROLc(x,n) _lrotl(x,n) - -#elif !defined(__STRICT_ANSI__) && defined(__GNUC__) && (defined(__i386__) || defined(__x86_64__)) && !defined(INTEL_CC) && !defined(LTC_NO_ASM) - -static inline unsigned ROL(unsigned word, int i) -{ - asm ("roll %%cl,%0" - :"=r" (word) - :"0" (word),"c" (i)); - return word; -} - -static inline unsigned ROR(unsigned word, int i) -{ - asm ("rorl %%cl,%0" - :"=r" (word) - :"0" (word),"c" (i)); - return word; -} - -#ifndef LTC_NO_ROLC - -static inline unsigned ROLc(unsigned word, const int i) -{ - asm ("roll %2,%0" - :"=r" (word) - :"0" (word),"I" (i)); - return word; -} - -static inline unsigned RORc(unsigned word, const int i) -{ - asm ("rorl %2,%0" - :"=r" (word) - :"0" (word),"I" (i)); - return word; -} - -#else - -#define ROLc ROL -#define RORc ROR - -#endif - -#elif !defined(__STRICT_ANSI__) && defined(LTC_PPC32) - -static inline unsigned ROL(unsigned word, int i) -{ - asm ("rotlw %0,%0,%2" - :"=r" (word) - :"0" (word),"r" (i)); - return word; -} - -static inline unsigned ROR(unsigned word, int i) -{ - asm ("rotlw %0,%0,%2" - :"=r" (word) - :"0" (word),"r" (32-i)); - return word; -} - -#ifndef LTC_NO_ROLC - -static inline unsigned ROLc(unsigned word, const int i) -{ - asm ("rotlwi %0,%0,%2" - :"=r" (word) - :"0" (word),"I" (i)); - return word; -} - -static inline unsigned RORc(unsigned word, const int i) -{ - asm ("rotrwi %0,%0,%2" - :"=r" (word) - :"0" (word),"I" (i)); - return word; -} - -#else - -#define ROLc ROL -#define RORc ROR - -#endif - - -#else - -/* rotates the hard way */ -#define ROL(x, y) ( (((unsigned long)(x)<<(unsigned long)((y)&31)) | (((unsigned long)(x)&0xFFFFFFFFUL)>>(unsigned long)(32-((y)&31)))) & 0xFFFFFFFFUL) -#define ROR(x, y) ( ((((unsigned long)(x)&0xFFFFFFFFUL)>>(unsigned long)((y)&31)) | ((unsigned long)(x)<<(unsigned long)(32-((y)&31)))) & 0xFFFFFFFFUL) -#define ROLc(x, y) ( (((unsigned long)(x)<<(unsigned long)((y)&31)) | (((unsigned long)(x)&0xFFFFFFFFUL)>>(unsigned long)(32-((y)&31)))) & 0xFFFFFFFFUL) -#define RORc(x, y) ( ((((unsigned long)(x)&0xFFFFFFFFUL)>>(unsigned long)((y)&31)) | ((unsigned long)(x)<<(unsigned long)(32-((y)&31)))) & 0xFFFFFFFFUL) - -#endif - - -/* 64-bit Rotates */ -#if !defined(__STRICT_ANSI__) && defined(__GNUC__) && defined(__x86_64__) && !defined(LTC_NO_ASM) - -static inline unsigned long ROL64(unsigned long word, int i) -{ - asm("rolq %%cl,%0" - :"=r" (word) - :"0" (word),"c" (i)); - return word; -} - -static inline unsigned long ROR64(unsigned long word, int i) -{ - asm("rorq %%cl,%0" - :"=r" (word) - :"0" (word),"c" (i)); - return word; -} - -#ifndef LTC_NO_ROLC - -static inline unsigned long ROL64c(unsigned long word, const int i) -{ - asm("rolq %2,%0" - :"=r" (word) - :"0" (word),"J" (i)); - return word; -} - -static inline unsigned long ROR64c(unsigned long word, const int i) -{ - asm("rorq %2,%0" - :"=r" (word) - :"0" (word),"J" (i)); - return word; -} - -#else /* LTC_NO_ROLC */ - -#define ROL64c ROL64 -#define ROR64c ROR64 - -#endif - -#else /* Not x86_64 */ - -#define ROL64(x, y) \ - ( (((x)<<((ulong64)(y)&63)) | \ - (((x)&CONST64(0xFFFFFFFFFFFFFFFF))>>((ulong64)64-((y)&63)))) & CONST64(0xFFFFFFFFFFFFFFFF)) - -#define ROR64(x, y) \ - ( ((((x)&CONST64(0xFFFFFFFFFFFFFFFF))>>((ulong64)(y)&CONST64(63))) | \ - ((x)<<((ulong64)(64-((y)&CONST64(63)))))) & CONST64(0xFFFFFFFFFFFFFFFF)) - -#define ROL64c(x, y) \ - ( (((x)<<((ulong64)(y)&63)) | \ - (((x)&CONST64(0xFFFFFFFFFFFFFFFF))>>((ulong64)64-((y)&63)))) & CONST64(0xFFFFFFFFFFFFFFFF)) - -#define ROR64c(x, y) \ - ( ((((x)&CONST64(0xFFFFFFFFFFFFFFFF))>>((ulong64)(y)&CONST64(63))) | \ - ((x)<<((ulong64)(64-((y)&CONST64(63)))))) & CONST64(0xFFFFFFFFFFFFFFFF)) - -#endif - -#ifndef MAX - #define MAX(x, y) ( ((x)>(y))?(x):(y) ) -#endif - -#ifndef MIN - #define MIN(x, y) ( ((x)<(y))?(x):(y) ) -#endif - -/* extract a byte portably */ -#ifdef _MSC_VER - #define byte(x, n) ((unsigned char)((x) >> (8 * (n)))) -#else - #define byte(x, n) (((x) >> (8 * (n))) & 255) -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/headers/tomcrypt_macros.h,v $ */ -/* $Revision: 1.15 $ */ -/* $Date: 2006/11/29 23:43:57 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_math.h b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_math.h deleted file mode 100644 index a05d7ff..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_math.h +++ /dev/null @@ -1,500 +0,0 @@ -/** math functions **/ - -#define LTC_MP_LT -1 -#define LTC_MP_EQ 0 -#define LTC_MP_GT 1 - -#define LTC_MP_NO 0 -#define LTC_MP_YES 1 - -#ifndef LTC_MECC - typedef void ecc_point; -#endif - -#ifndef LTC_MRSA - typedef void rsa_key; -#endif - -/** math descriptor */ -typedef struct { - /** Name of the math provider */ - char *name; - - /** Bits per digit, amount of bits must fit in an unsigned long */ - int bits_per_digit; - -/* ---- init/deinit functions ---- */ - - /** initialize a bignum - @param a The number to initialize - @return CRYPT_OK on success - */ - int (*init)(void **a); - - /** init copy - @param dst The number to initialize and write to - @param src The number to copy from - @return CRYPT_OK on success - */ - int (*init_copy)(void **dst, void *src); - - /** deinit - @param a The number to free - @return CRYPT_OK on success - */ - void (*deinit)(void *a); - -/* ---- data movement ---- */ - - /** negate - @param src The number to negate - @param dst The destination - @return CRYPT_OK on success - */ - int (*neg)(void *src, void *dst); - - /** copy - @param src The number to copy from - @param dst The number to write to - @return CRYPT_OK on success - */ - int (*copy)(void *src, void *dst); - -/* ---- trivial low level functions ---- */ - - /** set small constant - @param a Number to write to - @param n Source upto bits_per_digit (actually meant for very small constants) - @return CRYPT_OK on succcess - */ - int (*set_int)(void *a, unsigned long n); - - /** get small constant - @param a Number to read, only fetches upto bits_per_digit from the number - @return The lower bits_per_digit of the integer (unsigned) - */ - unsigned long (*get_int)(void *a); - - /** get digit n - @param a The number to read from - @param n The number of the digit to fetch - @return The bits_per_digit sized n'th digit of a - */ - unsigned long (*get_digit)(void *a, int n); - - /** Get the number of digits that represent the number - @param a The number to count - @return The number of digits used to represent the number - */ - int (*get_digit_count)(void *a); - - /** compare two integers - @param a The left side integer - @param b The right side integer - @return LTC_MP_LT if a < b, LTC_MP_GT if a > b and LTC_MP_EQ otherwise. (signed comparison) - */ - int (*compare)(void *a, void *b); - - /** compare against int - @param a The left side integer - @param b The right side integer (upto bits_per_digit) - @return LTC_MP_LT if a < b, LTC_MP_GT if a > b and LTC_MP_EQ otherwise. (signed comparison) - */ - int (*compare_d)(void *a, unsigned long n); - - /** Count the number of bits used to represent the integer - @param a The integer to count - @return The number of bits required to represent the integer - */ - int (*count_bits)(void * a); - - /** Count the number of LSB bits which are zero - @param a The integer to count - @return The number of contiguous zero LSB bits - */ - int (*count_lsb_bits)(void *a); - - /** Compute a power of two - @param a The integer to store the power in - @param n The power of two you want to store (a = 2^n) - @return CRYPT_OK on success - */ - int (*twoexpt)(void *a , int n); - -/* ---- radix conversions ---- */ - - /** read ascii string - @param a The integer to store into - @param str The string to read - @param radix The radix the integer has been represented in (2-64) - @return CRYPT_OK on success - */ - int (*read_radix)(void *a, const char *str, int radix); - - /** write number to string - @param a The integer to store - @param str The destination for the string - @param radix The radix the integer is to be represented in (2-64) - @return CRYPT_OK on success - */ - int (*write_radix)(void *a, char *str, int radix); - - /** get size as unsigned char string - @param a The integer to get the size (when stored in array of octets) - @return The length of the integer - */ - unsigned long (*unsigned_size)(void *a); - - /** store an integer as an array of octets - @param src The integer to store - @param dst The buffer to store the integer in - @return CRYPT_OK on success - */ - int (*unsigned_write)(void *src, unsigned char *dst); - - /** read an array of octets and store as integer - @param dst The integer to load - @param src The array of octets - @param len The number of octets - @return CRYPT_OK on success - */ - int (*unsigned_read)(void *dst, unsigned char *src, unsigned long len); - -/* ---- basic math ---- */ - - /** add two integers - @param a The first source integer - @param b The second source integer - @param c The destination of "a + b" - @return CRYPT_OK on success - */ - int (*add)(void *a, void *b, void *c); - - - /** add two integers - @param a The first source integer - @param b The second source integer (single digit of upto bits_per_digit in length) - @param c The destination of "a + b" - @return CRYPT_OK on success - */ - int (*addi)(void *a, unsigned long b, void *c); - - /** subtract two integers - @param a The first source integer - @param b The second source integer - @param c The destination of "a - b" - @return CRYPT_OK on success - */ - int (*sub)(void *a, void *b, void *c); - - /** subtract two integers - @param a The first source integer - @param b The second source integer (single digit of upto bits_per_digit in length) - @param c The destination of "a - b" - @return CRYPT_OK on success - */ - int (*subi)(void *a, unsigned long b, void *c); - - /** multiply two integers - @param a The first source integer - @param b The second source integer (single digit of upto bits_per_digit in length) - @param c The destination of "a * b" - @return CRYPT_OK on success - */ - int (*mul)(void *a, void *b, void *c); - - /** multiply two integers - @param a The first source integer - @param b The second source integer (single digit of upto bits_per_digit in length) - @param c The destination of "a * b" - @return CRYPT_OK on success - */ - int (*muli)(void *a, unsigned long b, void *c); - - /** Square an integer - @param a The integer to square - @param b The destination - @return CRYPT_OK on success - */ - int (*sqr)(void *a, void *b); - - /** Divide an integer - @param a The dividend - @param b The divisor - @param c The quotient (can be NULL to signify don't care) - @param d The remainder (can be NULL to signify don't care) - @return CRYPT_OK on success - */ - int (*mpdiv)(void *a, void *b, void *c, void *d); - - /** divide by two - @param a The integer to divide (shift right) - @param b The destination - @return CRYPT_OK on success - */ - int (*div_2)(void *a, void *b); - - /** Get remainder (small value) - @param a The integer to reduce - @param b The modulus (upto bits_per_digit in length) - @param c The destination for the residue - @return CRYPT_OK on success - */ - int (*modi)(void *a, unsigned long b, unsigned long *c); - - /** gcd - @param a The first integer - @param b The second integer - @param c The destination for (a, b) - @return CRYPT_OK on success - */ - int (*gcd)(void *a, void *b, void *c); - - /** lcm - @param a The first integer - @param b The second integer - @param c The destination for [a, b] - @return CRYPT_OK on success - */ - int (*lcm)(void *a, void *b, void *c); - - /** Modular multiplication - @param a The first source - @param b The second source - @param c The modulus - @param d The destination (a*b mod c) - @return CRYPT_OK on success - */ - int (*mulmod)(void *a, void *b, void *c, void *d); - - /** Modular squaring - @param a The first source - @param b The modulus - @param c The destination (a*a mod b) - @return CRYPT_OK on success - */ - int (*sqrmod)(void *a, void *b, void *c); - - /** Modular inversion - @param a The value to invert - @param b The modulus - @param c The destination (1/a mod b) - @return CRYPT_OK on success - */ - int (*invmod)(void *, void *, void *); - -/* ---- reduction ---- */ - - /** setup montgomery - @param a The modulus - @param b The destination for the reduction digit - @return CRYPT_OK on success - */ - int (*montgomery_setup)(void *a, void **b); - - /** get normalization value - @param a The destination for the normalization value - @param b The modulus - @return CRYPT_OK on success - */ - int (*montgomery_normalization)(void *a, void *b); - - /** reduce a number - @param a The number [and dest] to reduce - @param b The modulus - @param c The value "b" from montgomery_setup() - @return CRYPT_OK on success - */ - int (*montgomery_reduce)(void *a, void *b, void *c); - - /** clean up (frees memory) - @param a The value "b" from montgomery_setup() - @return CRYPT_OK on success - */ - void (*montgomery_deinit)(void *a); - -/* ---- exponentiation ---- */ - - /** Modular exponentiation - @param a The base integer - @param b The power (can be negative) integer - @param c The modulus integer - @param d The destination - @return CRYPT_OK on success - */ - int (*exptmod)(void *a, void *b, void *c, void *d); - - /** Primality testing - @param a The integer to test - @param b The destination of the result (FP_YES if prime) - @return CRYPT_OK on success - */ - int (*isprime)(void *a, int *b); - -/* ---- (optional) ecc point math ---- */ - - /** ECC GF(p) point multiplication (from the NIST curves) - @param k The integer to multiply the point by - @param G The point to multiply - @param R The destination for kG - @param modulus The modulus for the field - @param map Boolean indicated whether to map back to affine or not (can be ignored if you work in affine only) - @return CRYPT_OK on success - */ - int (*ecc_ptmul)(void *k, ecc_point *G, ecc_point *R, void *modulus, int map); - - /** ECC GF(p) point addition - @param P The first point - @param Q The second point - @param R The destination of P + Q - @param modulus The modulus - @param mp The "b" value from montgomery_setup() - @return CRYPT_OK on success - */ - int (*ecc_ptadd)(ecc_point *P, ecc_point *Q, ecc_point *R, void *modulus, void *mp); - - /** ECC GF(p) point double - @param P The first point - @param R The destination of 2P - @param modulus The modulus - @param mp The "b" value from montgomery_setup() - @return CRYPT_OK on success - */ - int (*ecc_ptdbl)(ecc_point *P, ecc_point *R, void *modulus, void *mp); - - /** ECC mapping from projective to affine, currently uses (x,y,z) => (x/z^2, y/z^3, 1) - @param P The point to map - @param modulus The modulus - @param mp The "b" value from montgomery_setup() - @return CRYPT_OK on success - @remark The mapping can be different but keep in mind a ecc_point only has three - integers (x,y,z) so if you use a different mapping you have to make it fit. - */ - int (*ecc_map)(ecc_point *P, void *modulus, void *mp); - - /** Computes kA*A + kB*B = C using Shamir's Trick - @param A First point to multiply - @param kA What to multiple A by - @param B Second point to multiply - @param kB What to multiple B by - @param C [out] Destination point (can overlap with A or B - @param modulus Modulus for curve - @return CRYPT_OK on success - */ - int (*ecc_mul2add)(ecc_point *A, void *kA, - ecc_point *B, void *kB, - ecc_point *C, - void *modulus); - -/* ---- (optional) rsa optimized math (for internal CRT) ---- */ - - /** RSA Key Generation - @param prng An active PRNG state - @param wprng The index of the PRNG desired - @param size The size of the modulus (key size) desired (octets) - @param e The "e" value (public key). e==65537 is a good choice - @param key [out] Destination of a newly created private key pair - @return CRYPT_OK if successful, upon error all allocated ram is freed - */ - int (*rsa_keygen)(prng_state *prng, int wprng, int size, long e, rsa_key *key); - - - /** RSA exponentiation - @param in The octet array representing the base - @param inlen The length of the input - @param out The destination (to be stored in an octet array format) - @param outlen The length of the output buffer and the resulting size (zero padded to the size of the modulus) - @param which PK_PUBLIC for public RSA and PK_PRIVATE for private RSA - @param key The RSA key to use - @return CRYPT_OK on success - */ - int (*rsa_me)(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen, int which, - rsa_key *key); -} ltc_math_descriptor; - -extern ltc_math_descriptor ltc_mp; - -int ltc_init_multi(void **a, ...); -void ltc_deinit_multi(void *a, ...); - -#ifdef LTM_DESC -extern const ltc_math_descriptor ltm_desc; -#endif - -#ifdef TFM_DESC -extern const ltc_math_descriptor tfm_desc; -#endif - -#ifdef GMP_DESC -extern const ltc_math_descriptor gmp_desc; -#endif - -#if !defined(DESC_DEF_ONLY) && defined(LTC_SOURCE) - -#define MP_DIGIT_BIT ltc_mp.bits_per_digit - -/* some handy macros */ -#define mp_init(a) ltc_mp.init(a) -#define mp_init_multi ltc_init_multi -#define mp_clear(a) ltc_mp.deinit(a) -#define mp_clear_multi ltc_deinit_multi -#define mp_init_copy(a, b) ltc_mp.init_copy(a, b) - -#define mp_neg(a, b) ltc_mp.neg(a, b) -#define mp_copy(a, b) ltc_mp.copy(a, b) - -#define mp_set(a, b) ltc_mp.set_int(a, b) -#define mp_set_int(a, b) ltc_mp.set_int(a, b) -#define mp_get_int(a) ltc_mp.get_int(a) -#define mp_get_digit(a, n) ltc_mp.get_digit(a, n) -#define mp_get_digit_count(a) ltc_mp.get_digit_count(a) -#define mp_cmp(a, b) ltc_mp.compare(a, b) -#define mp_cmp_d(a, b) ltc_mp.compare_d(a, b) -#define mp_count_bits(a) ltc_mp.count_bits(a) -#define mp_cnt_lsb(a) ltc_mp.count_lsb_bits(a) -#define mp_2expt(a, b) ltc_mp.twoexpt(a, b) - -#define mp_read_radix(a, b, c) ltc_mp.read_radix(a, b, c) -#define mp_toradix(a, b, c) ltc_mp.write_radix(a, b, c) -#define mp_unsigned_bin_size(a) ltc_mp.unsigned_size(a) -#define mp_to_unsigned_bin(a, b) ltc_mp.unsigned_write(a, b) -#define mp_read_unsigned_bin(a, b, c) ltc_mp.unsigned_read(a, b, c) - -#define mp_add(a, b, c) ltc_mp.add(a, b, c) -#define mp_add_d(a, b, c) ltc_mp.addi(a, b, c) -#define mp_sub(a, b, c) ltc_mp.sub(a, b, c) -#define mp_sub_d(a, b, c) ltc_mp.subi(a, b, c) -#define mp_mul(a, b, c) ltc_mp.mul(a, b, c) -#define mp_mul_d(a, b, c) ltc_mp.muli(a, b, c) -#define mp_sqr(a, b) ltc_mp.sqr(a, b) -#define mp_div(a, b, c, d) ltc_mp.mpdiv(a, b, c, d) -#define mp_div_2(a, b) ltc_mp.div_2(a, b) -#define mp_mod(a, b, c) ltc_mp.mpdiv(a, b, NULL, c) -#define mp_mod_d(a, b, c) ltc_mp.modi(a, b, c) -#define mp_gcd(a, b, c) ltc_mp.gcd(a, b, c) -#define mp_lcm(a, b, c) ltc_mp.lcm(a, b, c) - -#define mp_mulmod(a, b, c, d) ltc_mp.mulmod(a, b, c, d) -#define mp_sqrmod(a, b, c) ltc_mp.sqrmod(a, b, c) -#define mp_invmod(a, b, c) ltc_mp.invmod(a, b, c) - -#define mp_montgomery_setup(a, b) ltc_mp.montgomery_setup(a, b) -#define mp_montgomery_normalization(a, b) ltc_mp.montgomery_normalization(a, b) -#define mp_montgomery_reduce(a, b, c) ltc_mp.montgomery_reduce(a, b, c) -#define mp_montgomery_free(a) ltc_mp.montgomery_deinit(a) - -#define mp_exptmod(a,b,c,d) ltc_mp.exptmod(a,b,c,d) -#define mp_prime_is_prime(a, b, c) ltc_mp.isprime(a, c) - -#define mp_iszero(a) (mp_cmp_d(a, 0) == LTC_MP_EQ ? LTC_MP_YES : LTC_MP_NO) -#define mp_isodd(a) (mp_get_digit_count(a) > 0 ? (mp_get_digit(a, 0) & 1 ? LTC_MP_YES : LTC_MP_NO) : LTC_MP_NO) -#define mp_exch(a, b) do { void *ABC__tmp = a; a = b; b = ABC__tmp; } while(0); - -#define mp_tohex(a, b) mp_toradix(a, b, 16) - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/headers/tomcrypt_math.h,v $ */ -/* $Revision: 1.44 $ */ -/* $Date: 2007/05/12 14:32:35 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_misc.h b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_misc.h deleted file mode 100644 index f5384ca..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_misc.h +++ /dev/null @@ -1,23 +0,0 @@ -/* ---- LTC_BASE64 Routines ---- */ -#ifdef LTC_BASE64 -int base64_encode(const unsigned char *in, unsigned long len, - unsigned char *out, unsigned long *outlen); - -int base64_decode(const unsigned char *in, unsigned long len, - unsigned char *out, unsigned long *outlen); -#endif - -/* ---- MEM routines ---- */ -void zeromem(void *dst, size_t len); -void burn_stack(unsigned long len); - -const char *error_to_string(int err); - -extern const char *crypt_build_settings; - -/* ---- HMM ---- */ -int crypt_fsa(void *mp, ...); - -/* $Source: /cvs/libtom/libtomcrypt/src/headers/tomcrypt_misc.h,v $ */ -/* $Revision: 1.5 $ */ -/* $Date: 2007/05/12 14:32:35 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_pk.h b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_pk.h deleted file mode 100644 index b5f277a..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_pk.h +++ /dev/null @@ -1,558 +0,0 @@ -/* ---- NUMBER THEORY ---- */ - -enum { - PK_PUBLIC=0, - PK_PRIVATE=1 -}; - -int rand_prime(void *N, long len, prng_state *prng, int wprng); - -/* ---- RSA ---- */ -#ifdef LTC_MRSA - -/* Min and Max RSA key sizes (in bits) */ -#define MIN_RSA_SIZE 1024 -#define MAX_RSA_SIZE 4096 - -/** RSA LTC_PKCS style key */ -typedef struct Rsa_key { - /** Type of key, PK_PRIVATE or PK_PUBLIC */ - int type; - /** The public exponent */ - void *e; - /** The private exponent */ - void *d; - /** The modulus */ - void *N; - /** The p factor of N */ - void *p; - /** The q factor of N */ - void *q; - /** The 1/q mod p CRT param */ - void *qP; - /** The d mod (p - 1) CRT param */ - void *dP; - /** The d mod (q - 1) CRT param */ - void *dQ; -} rsa_key; - -int rsa_make_key(prng_state *prng, int wprng, int size, long e, rsa_key *key); - -int rsa_exptmod(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen, int which, - rsa_key *key); - -void rsa_free(rsa_key *key); - -/* These use LTC_PKCS #1 v2.0 padding */ -#define rsa_encrypt_key(_in, _inlen, _out, _outlen, _lparam, _lparamlen, _prng, _prng_idx, _hash_idx, _key) \ - rsa_encrypt_key_ex(_in, _inlen, _out, _outlen, _lparam, _lparamlen, _prng, _prng_idx, _hash_idx, LTC_LTC_PKCS_1_OAEP, _key) - -#define rsa_decrypt_key(_in, _inlen, _out, _outlen, _lparam, _lparamlen, _hash_idx, _stat, _key) \ - rsa_decrypt_key_ex(_in, _inlen, _out, _outlen, _lparam, _lparamlen, _hash_idx, LTC_LTC_PKCS_1_OAEP, _stat, _key) - -#define rsa_sign_hash(_in, _inlen, _out, _outlen, _prng, _prng_idx, _hash_idx, _saltlen, _key) \ - rsa_sign_hash_ex(_in, _inlen, _out, _outlen, LTC_LTC_PKCS_1_PSS, _prng, _prng_idx, _hash_idx, _saltlen, _key) - -#define rsa_verify_hash(_sig, _siglen, _hash, _hashlen, _hash_idx, _saltlen, _stat, _key) \ - rsa_verify_hash_ex(_sig, _siglen, _hash, _hashlen, LTC_LTC_PKCS_1_PSS, _hash_idx, _saltlen, _stat, _key) - -/* These can be switched between LTC_PKCS #1 v2.x and LTC_PKCS #1 v1.5 paddings */ -int rsa_encrypt_key_ex(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen, - const unsigned char *lparam, unsigned long lparamlen, - prng_state *prng, int prng_idx, int hash_idx, int padding, rsa_key *key); - -int rsa_decrypt_key_ex(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen, - const unsigned char *lparam, unsigned long lparamlen, - int hash_idx, int padding, - int *stat, rsa_key *key); - -int rsa_sign_hash_ex(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen, - int padding, - prng_state *prng, int prng_idx, - int hash_idx, unsigned long saltlen, - rsa_key *key); - -int rsa_verify_hash_ex(const unsigned char *sig, unsigned long siglen, - const unsigned char *hash, unsigned long hashlen, - int padding, - int hash_idx, unsigned long saltlen, - int *stat, rsa_key *key); - -/* LTC_PKCS #1 import/export */ -int rsa_export(unsigned char *out, unsigned long *outlen, int type, rsa_key *key); -int rsa_import(const unsigned char *in, unsigned long inlen, rsa_key *key); - -/* Ladik: Added for verifying Blizzard strong signature verification */ -int rsa_verify_simple(const unsigned char *sig, unsigned long siglen, - const unsigned char *hash, unsigned long hashlen, - int *stat, - rsa_key *key); - -#endif - -/* ---- Katja ---- */ -#ifdef MKAT - -/* Min and Max KAT key sizes (in bits) */ -#define MIN_KAT_SIZE 1024 -#define MAX_KAT_SIZE 4096 - -/** Katja LTC_PKCS style key */ -typedef struct KAT_key { - /** Type of key, PK_PRIVATE or PK_PUBLIC */ - int type; - /** The private exponent */ - void *d; - /** The modulus */ - void *N; - /** The p factor of N */ - void *p; - /** The q factor of N */ - void *q; - /** The 1/q mod p CRT param */ - void *qP; - /** The d mod (p - 1) CRT param */ - void *dP; - /** The d mod (q - 1) CRT param */ - void *dQ; - /** The pq param */ - void *pq; -} katja_key; - -int katja_make_key(prng_state *prng, int wprng, int size, katja_key *key); - -int katja_exptmod(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen, int which, - katja_key *key); - -void katja_free(katja_key *key); - -/* These use LTC_PKCS #1 v2.0 padding */ -int katja_encrypt_key(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen, - const unsigned char *lparam, unsigned long lparamlen, - prng_state *prng, int prng_idx, int hash_idx, katja_key *key); - -int katja_decrypt_key(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen, - const unsigned char *lparam, unsigned long lparamlen, - int hash_idx, int *stat, - katja_key *key); - -/* LTC_PKCS #1 import/export */ -int katja_export(unsigned char *out, unsigned long *outlen, int type, katja_key *key); -int katja_import(const unsigned char *in, unsigned long inlen, katja_key *key); - -#endif - -/* ---- ECC Routines ---- */ -#ifdef LTC_MECC - -/* size of our temp buffers for exported keys */ -#define ECC_BUF_SIZE 256 - -/* max private key size */ -#define ECC_MAXSIZE 66 - -/** Structure defines a NIST GF(p) curve */ -typedef struct { - /** The size of the curve in octets */ - int size; - - /** name of curve */ - char *name; - - /** The prime that defines the field the curve is in (encoded in hex) */ - char *prime; - - /** The fields B param (hex) */ - char *B; - - /** The order of the curve (hex) */ - char *order; - - /** The x co-ordinate of the base point on the curve (hex) */ - char *Gx; - - /** The y co-ordinate of the base point on the curve (hex) */ - char *Gy; -} ltc_ecc_set_type; - -/** A point on a ECC curve, stored in Jacbobian format such that (x,y,z) => (x/z^2, y/z^3, 1) when interpretted as affine */ -typedef struct { - /** The x co-ordinate */ - void *x; - - /** The y co-ordinate */ - void *y; - - /** The z co-ordinate */ - void *z; -} ecc_point; - -/** An ECC key */ -typedef struct { - /** Type of key, PK_PRIVATE or PK_PUBLIC */ - int type; - - /** Index into the ltc_ecc_sets[] for the parameters of this curve; if -1, then this key is using user supplied curve in dp */ - int idx; - - /** pointer to domain parameters; either points to NIST curves (identified by idx >= 0) or user supplied curve */ - const ltc_ecc_set_type *dp; - - /** The public key */ - ecc_point pubkey; - - /** The private key */ - void *k; -} ecc_key; - -/** the ECC params provided */ -extern const ltc_ecc_set_type ltc_ecc_sets[]; - -int ecc_test(void); -void ecc_sizes(int *low, int *high); -int ecc_get_size(ecc_key *key); - -int ecc_make_key(prng_state *prng, int wprng, int keysize, ecc_key *key); -int ecc_make_key_ex(prng_state *prng, int wprng, ecc_key *key, const ltc_ecc_set_type *dp); -void ecc_free(ecc_key *key); - -int ecc_export(unsigned char *out, unsigned long *outlen, int type, ecc_key *key); -int ecc_import(const unsigned char *in, unsigned long inlen, ecc_key *key); -int ecc_import_ex(const unsigned char *in, unsigned long inlen, ecc_key *key, const ltc_ecc_set_type *dp); - -int ecc_ansi_x963_export(ecc_key *key, unsigned char *out, unsigned long *outlen); -int ecc_ansi_x963_import(const unsigned char *in, unsigned long inlen, ecc_key *key); -int ecc_ansi_x963_import_ex(const unsigned char *in, unsigned long inlen, ecc_key *key, ltc_ecc_set_type *dp); - -int ecc_shared_secret(ecc_key *private_key, ecc_key *public_key, - unsigned char *out, unsigned long *outlen); - -int ecc_encrypt_key(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen, - prng_state *prng, int wprng, int hash, - ecc_key *key); - -int ecc_decrypt_key(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen, - ecc_key *key); - -int ecc_sign_hash(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen, - prng_state *prng, int wprng, ecc_key *key); - -int ecc_verify_hash(const unsigned char *sig, unsigned long siglen, - const unsigned char *hash, unsigned long hashlen, - int *stat, ecc_key *key); - -/* low level functions */ -ecc_point *ltc_ecc_new_point(void); -void ltc_ecc_del_point(ecc_point *p); -int ltc_ecc_is_valid_idx(int n); - -/* point ops (mp == montgomery digit) */ -#if !defined(LTC_MECC_ACCEL) || defined(LTM_LTC_DESC) || defined(GMP_LTC_DESC) -/* R = 2P */ -int ltc_ecc_projective_dbl_point(ecc_point *P, ecc_point *R, void *modulus, void *mp); - -/* R = P + Q */ -int ltc_ecc_projective_add_point(ecc_point *P, ecc_point *Q, ecc_point *R, void *modulus, void *mp); -#endif - -#if defined(LTC_MECC_FP) -/* optimized point multiplication using fixed point cache (HAC algorithm 14.117) */ -int ltc_ecc_fp_mulmod(void *k, ecc_point *G, ecc_point *R, void *modulus, int map); - -/* functions for saving/loading/freeing/adding to fixed point cache */ -int ltc_ecc_fp_save_state(unsigned char **out, unsigned long *outlen); -int ltc_ecc_fp_restore_state(unsigned char *in, unsigned long inlen); -void ltc_ecc_fp_free(void); -int ltc_ecc_fp_add_point(ecc_point *g, void *modulus, int lock); - -/* lock/unlock all points currently in fixed point cache */ -void ltc_ecc_fp_tablelock(int lock); -#endif - -/* R = kG */ -int ltc_ecc_mulmod(void *k, ecc_point *G, ecc_point *R, void *modulus, int map); - -#ifdef LTC_ECC_SHAMIR -/* kA*A + kB*B = C */ -int ltc_ecc_mul2add(ecc_point *A, void *kA, - ecc_point *B, void *kB, - ecc_point *C, - void *modulus); - -#ifdef LTC_MECC_FP -/* Shamir's trick with optimized point multiplication using fixed point cache */ -int ltc_ecc_fp_mul2add(ecc_point *A, void *kA, - ecc_point *B, void *kB, - ecc_point *C, void *modulus); -#endif - -#endif - - -/* map P to affine from projective */ -int ltc_ecc_map(ecc_point *P, void *modulus, void *mp); - -#endif - -#ifdef LTC_MDSA - -/* Max diff between group and modulus size in bytes */ -#define LTC_MDSA_DELTA 512 - -/* Max DSA group size in bytes (default allows 4k-bit groups) */ -#define LTC_MDSA_MAX_GROUP 512 - -/** DSA key structure */ -typedef struct { - /** The key type, PK_PRIVATE or PK_PUBLIC */ - int type; - - /** The order of the sub-group used in octets */ - int qord; - - /** The generator */ - void *g; - - /** The prime used to generate the sub-group */ - void *q; - - /** The large prime that generats the field the contains the sub-group */ - void *p; - - /** The private key */ - void *x; - - /** The public key */ - void *y; -} dsa_key; - -int dsa_make_key(prng_state *prng, int wprng, int group_size, int modulus_size, dsa_key *key); -void dsa_free(dsa_key *key); - -int dsa_sign_hash_raw(const unsigned char *in, unsigned long inlen, - void *r, void *s, - prng_state *prng, int wprng, dsa_key *key); - -int dsa_sign_hash(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen, - prng_state *prng, int wprng, dsa_key *key); - -int dsa_verify_hash_raw( void *r, void *s, - const unsigned char *hash, unsigned long hashlen, - int *stat, dsa_key *key); - -int dsa_verify_hash(const unsigned char *sig, unsigned long siglen, - const unsigned char *hash, unsigned long hashlen, - int *stat, dsa_key *key); - -int dsa_encrypt_key(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen, - prng_state *prng, int wprng, int hash, - dsa_key *key); - -int dsa_decrypt_key(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen, - dsa_key *key); - -int dsa_import(const unsigned char *in, unsigned long inlen, dsa_key *key); -int dsa_export(unsigned char *out, unsigned long *outlen, int type, dsa_key *key); -int dsa_verify_key(dsa_key *key, int *stat); - -int dsa_shared_secret(void *private_key, void *base, - dsa_key *public_key, - unsigned char *out, unsigned long *outlen); -#endif - -#ifdef LTC_DER -/* DER handling */ - -enum { - LTC_ASN1_EOL, - LTC_ASN1_BOOLEAN, - LTC_ASN1_INTEGER, - LTC_ASN1_SHORT_INTEGER, - LTC_ASN1_BIT_STRING, - LTC_ASN1_OCTET_STRING, - LTC_ASN1_NULL, - LTC_ASN1_OBJECT_IDENTIFIER, - LTC_ASN1_IA5_STRING, - LTC_ASN1_PRINTABLE_STRING, - LTC_ASN1_UTF8_STRING, - LTC_ASN1_UTCTIME, - LTC_ASN1_CHOICE, - LTC_ASN1_SEQUENCE, - LTC_ASN1_SET, - LTC_ASN1_SETOF -}; - -/** A LTC ASN.1 list type */ -typedef struct ltc_asn1_list_ { - /** The LTC ASN.1 enumerated type identifier */ - int type; - /** The data to encode or place for decoding */ - void *data; - /** The size of the input or resulting output */ - unsigned long size; - /** The used flag, this is used by the CHOICE ASN.1 type to indicate which choice was made */ - int used; - /** prev/next entry in the list */ - struct ltc_asn1_list_ *prev, *next, *child, *parent; -} ltc_asn1_list; - -#define LTC_SET_ASN1(list, index, Type, Data, Size) \ - do { \ - int LTC_MACRO_temp = (index); \ - ltc_asn1_list *LTC_MACRO_list = (list); \ - LTC_MACRO_list[LTC_MACRO_temp].type = (Type); \ - LTC_MACRO_list[LTC_MACRO_temp].data = (void*)(Data); \ - LTC_MACRO_list[LTC_MACRO_temp].size = (Size); \ - LTC_MACRO_list[LTC_MACRO_temp].used = 0; \ - } while (0); - -/* SEQUENCE */ -int der_encode_sequence_ex(ltc_asn1_list *list, unsigned long inlen, - unsigned char *out, unsigned long *outlen, int type_of); - -#define der_encode_sequence(list, inlen, out, outlen) der_encode_sequence_ex(list, inlen, out, outlen, LTC_ASN1_SEQUENCE) - -int der_decode_sequence_ex(const unsigned char *in, unsigned long inlen, - ltc_asn1_list *list, unsigned long outlen, int ordered); - -#define der_decode_sequence(in, inlen, list, outlen) der_decode_sequence_ex(in, inlen, list, outlen, 1) - -int der_length_sequence(ltc_asn1_list *list, unsigned long inlen, - unsigned long *outlen); - -/* SET */ -#define der_decode_set(in, inlen, list, outlen) der_decode_sequence_ex(in, inlen, list, outlen, 0) -#define der_length_set der_length_sequence -int der_encode_set(ltc_asn1_list *list, unsigned long inlen, - unsigned char *out, unsigned long *outlen); - -int der_encode_setof(ltc_asn1_list *list, unsigned long inlen, - unsigned char *out, unsigned long *outlen); - -/* VA list handy helpers with triplets of */ -int der_encode_sequence_multi(unsigned char *out, unsigned long *outlen, ...); -int der_decode_sequence_multi(const unsigned char *in, unsigned long inlen, ...); - -/* FLEXI DECODER handle unknown list decoder */ -int der_decode_sequence_flexi(const unsigned char *in, unsigned long *inlen, ltc_asn1_list **out); -void der_free_sequence_flexi(ltc_asn1_list *list); -void der_sequence_free(ltc_asn1_list *in); - -/* BOOLEAN */ -int der_length_boolean(unsigned long *outlen); -int der_encode_boolean(int in, - unsigned char *out, unsigned long *outlen); -int der_decode_boolean(const unsigned char *in, unsigned long inlen, - int *out); -/* INTEGER */ -int der_encode_integer(void *num, unsigned char *out, unsigned long *outlen); -int der_decode_integer(const unsigned char *in, unsigned long inlen, void *num); -int der_length_integer(void *num, unsigned long *len); - -/* INTEGER -- handy for 0..2^32-1 values */ -int der_decode_short_integer(const unsigned char *in, unsigned long inlen, unsigned long *num); -int der_encode_short_integer(unsigned long num, unsigned char *out, unsigned long *outlen); -int der_length_short_integer(unsigned long num, unsigned long *outlen); - -/* BIT STRING */ -int der_encode_bit_string(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen); -int der_decode_bit_string(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen); -int der_length_bit_string(unsigned long nbits, unsigned long *outlen); - -/* OCTET STRING */ -int der_encode_octet_string(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen); -int der_decode_octet_string(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen); -int der_length_octet_string(unsigned long noctets, unsigned long *outlen); - -/* OBJECT IDENTIFIER */ -int der_encode_object_identifier(unsigned long *words, unsigned long nwords, - unsigned char *out, unsigned long *outlen); -int der_decode_object_identifier(const unsigned char *in, unsigned long inlen, - unsigned long *words, unsigned long *outlen); -int der_length_object_identifier(unsigned long *words, unsigned long nwords, unsigned long *outlen); -unsigned long der_object_identifier_bits(unsigned long x); - -/* IA5 STRING */ -int der_encode_ia5_string(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen); -int der_decode_ia5_string(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen); -int der_length_ia5_string(const unsigned char *octets, unsigned long noctets, unsigned long *outlen); - -int der_ia5_char_encode(int c); -int der_ia5_value_decode(int v); - -/* Printable STRING */ -int der_encode_printable_string(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen); -int der_decode_printable_string(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen); -int der_length_printable_string(const unsigned char *octets, unsigned long noctets, unsigned long *outlen); - -int der_printable_char_encode(int c); -int der_printable_value_decode(int v); - -/* UTF-8 */ -#if (defined(SIZE_MAX) || __STDC_VERSION__ >= 199901L || defined(WCHAR_MAX) || defined(_WCHAR_T) || defined(_WCHAR_T_DEFINED) || defined (__WCHAR_TYPE__)) && !defined(LTC_NO_WCHAR) -#include -#else -typedef ulong32 wchar_t; -#endif - -int der_encode_utf8_string(const wchar_t *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen); - -int der_decode_utf8_string(const unsigned char *in, unsigned long inlen, - wchar_t *out, unsigned long *outlen); -unsigned long der_utf8_charsize(const wchar_t c); -int der_length_utf8_string(const wchar_t *in, unsigned long noctets, unsigned long *outlen); - - -/* CHOICE */ -int der_decode_choice(const unsigned char *in, unsigned long *inlen, - ltc_asn1_list *list, unsigned long outlen); - -/* UTCTime */ -typedef struct { - unsigned YY, /* year */ - MM, /* month */ - DD, /* day */ - hh, /* hour */ - mm, /* minute */ - ss, /* second */ - off_dir, /* timezone offset direction 0 == +, 1 == - */ - off_hh, /* timezone offset hours */ - off_mm; /* timezone offset minutes */ -} ltc_utctime; - -int der_encode_utctime(ltc_utctime *utctime, - unsigned char *out, unsigned long *outlen); - -int der_decode_utctime(const unsigned char *in, unsigned long *inlen, - ltc_utctime *out); - -int der_length_utctime(ltc_utctime *utctime, unsigned long *outlen); - - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/headers/tomcrypt_pk.h,v $ */ -/* $Revision: 1.81 $ */ -/* $Date: 2007/05/12 14:32:35 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_pkcs.h b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_pkcs.h deleted file mode 100644 index 84fb82a..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_pkcs.h +++ /dev/null @@ -1,89 +0,0 @@ -/* LTC_PKCS Header Info */ - -/* ===> LTC_PKCS #1 -- RSA Cryptography <=== */ -#ifdef LTC_PKCS_1 - -enum ltc_pkcs_1_v1_5_blocks -{ - LTC_LTC_PKCS_1_EMSA = 1, /* Block type 1 (LTC_PKCS #1 v1.5 signature padding) */ - LTC_LTC_PKCS_1_EME = 2 /* Block type 2 (LTC_PKCS #1 v1.5 encryption padding) */ -}; - -enum ltc_pkcs_1_paddings -{ - LTC_LTC_PKCS_1_V1_5 = 1, /* LTC_PKCS #1 v1.5 padding (\sa ltc_pkcs_1_v1_5_blocks) */ - LTC_LTC_PKCS_1_OAEP = 2, /* LTC_PKCS #1 v2.0 encryption padding */ - LTC_LTC_PKCS_1_PSS = 3 /* LTC_PKCS #1 v2.1 signature padding */ -}; - -int pkcs_1_mgf1( int hash_idx, - const unsigned char *seed, unsigned long seedlen, - unsigned char *mask, unsigned long masklen); - -int pkcs_1_i2osp(void *n, unsigned long modulus_len, unsigned char *out); -int pkcs_1_os2ip(void *n, unsigned char *in, unsigned long inlen); - -/* *** v1.5 padding */ -int pkcs_1_v1_5_encode(const unsigned char *msg, - unsigned long msglen, - int block_type, - unsigned long modulus_bitlen, - prng_state *prng, - int prng_idx, - unsigned char *out, - unsigned long *outlen); - -int pkcs_1_v1_5_decode(const unsigned char *msg, - unsigned long msglen, - int block_type, - unsigned long modulus_bitlen, - unsigned char *out, - unsigned long *outlen, - int *is_valid); - -/* *** v2.1 padding */ -int pkcs_1_oaep_encode(const unsigned char *msg, unsigned long msglen, - const unsigned char *lparam, unsigned long lparamlen, - unsigned long modulus_bitlen, prng_state *prng, - int prng_idx, int hash_idx, - unsigned char *out, unsigned long *outlen); - -int pkcs_1_oaep_decode(const unsigned char *msg, unsigned long msglen, - const unsigned char *lparam, unsigned long lparamlen, - unsigned long modulus_bitlen, int hash_idx, - unsigned char *out, unsigned long *outlen, - int *res); - -int pkcs_1_pss_encode(const unsigned char *msghash, unsigned long msghashlen, - unsigned long saltlen, prng_state *prng, - int prng_idx, int hash_idx, - unsigned long modulus_bitlen, - unsigned char *out, unsigned long *outlen); - -int pkcs_1_pss_decode(const unsigned char *msghash, unsigned long msghashlen, - const unsigned char *sig, unsigned long siglen, - unsigned long saltlen, int hash_idx, - unsigned long modulus_bitlen, int *res); - -#endif /* LTC_PKCS_1 */ - -/* ===> LTC_PKCS #5 -- Password Based Cryptography <=== */ -#ifdef LTC_PKCS_5 - -/* Algorithm #1 (old) */ -int pkcs_5_alg1(const unsigned char *password, unsigned long password_len, - const unsigned char *salt, - int iteration_count, int hash_idx, - unsigned char *out, unsigned long *outlen); - -/* Algorithm #2 (new) */ -int pkcs_5_alg2(const unsigned char *password, unsigned long password_len, - const unsigned char *salt, unsigned long salt_len, - int iteration_count, int hash_idx, - unsigned char *out, unsigned long *outlen); - -#endif /* LTC_PKCS_5 */ - -/* $Source: /cvs/libtom/libtomcrypt/src/headers/tomcrypt_pkcs.h,v $ */ -/* $Revision: 1.8 $ */ -/* $Date: 2007/05/12 14:32:35 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_prng.h b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_prng.h deleted file mode 100644 index f3e3e55..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/headers/tomcrypt_prng.h +++ /dev/null @@ -1,199 +0,0 @@ -/* ---- PRNG Stuff ---- */ -#ifdef LTC_YARROW -struct yarrow_prng { - int cipher, hash; - unsigned char pool[MAXBLOCKSIZE]; - symmetric_CTR ctr; - LTC_MUTEX_TYPE(prng_lock) -}; -#endif - -#ifdef LTC_RC4 -struct rc4_prng { - int x, y; - unsigned char buf[256]; -}; -#endif - -#ifdef LTC_FORTUNA -struct fortuna_prng { - hash_state pool[LTC_FORTUNA_POOLS]; /* the pools */ - - symmetric_key skey; - - unsigned char K[32], /* the current key */ - IV[16]; /* IV for CTR mode */ - - unsigned long pool_idx, /* current pool we will add to */ - pool0_len, /* length of 0'th pool */ - wd; - - ulong64 reset_cnt; /* number of times we have reset */ - LTC_MUTEX_TYPE(prng_lock) -}; -#endif - -#ifdef LTC_SOBER128 -struct sober128_prng { - ulong32 R[17], /* Working storage for the shift register */ - initR[17], /* saved register contents */ - konst, /* key dependent constant */ - sbuf; /* partial word encryption buffer */ - - int nbuf, /* number of part-word stream bits buffered */ - flag, /* first add_entropy call or not? */ - set; /* did we call add_entropy to set key? */ - -}; -#endif - -typedef union Prng_state { - char dummy[1]; -#ifdef LTC_YARROW - struct yarrow_prng yarrow; -#endif -#ifdef LTC_RC4 - struct rc4_prng rc4; -#endif -#ifdef LTC_FORTUNA - struct fortuna_prng fortuna; -#endif -#ifdef LTC_SOBER128 - struct sober128_prng sober128; -#endif -} prng_state; - -/** PRNG descriptor */ -extern struct ltc_prng_descriptor { - /** Name of the PRNG */ - char *name; - /** size in bytes of exported state */ - int export_size; - /** Start a PRNG state - @param prng [out] The state to initialize - @return CRYPT_OK if successful - */ - int (*start)(prng_state *prng); - /** Add entropy to the PRNG - @param in The entropy - @param inlen Length of the entropy (octets)\ - @param prng The PRNG state - @return CRYPT_OK if successful - */ - int (*add_entropy)(const unsigned char *in, unsigned long inlen, prng_state *prng); - /** Ready a PRNG state to read from - @param prng The PRNG state to ready - @return CRYPT_OK if successful - */ - int (*ready)(prng_state *prng); - /** Read from the PRNG - @param out [out] Where to store the data - @param outlen Length of data desired (octets) - @param prng The PRNG state to read from - @return Number of octets read - */ - unsigned long (*read)(unsigned char *out, unsigned long outlen, prng_state *prng); - /** Terminate a PRNG state - @param prng The PRNG state to terminate - @return CRYPT_OK if successful - */ - int (*done)(prng_state *prng); - /** Export a PRNG state - @param out [out] The destination for the state - @param outlen [in/out] The max size and resulting size of the PRNG state - @param prng The PRNG to export - @return CRYPT_OK if successful - */ - int (*pexport)(unsigned char *out, unsigned long *outlen, prng_state *prng); - /** Import a PRNG state - @param in The data to import - @param inlen The length of the data to import (octets) - @param prng The PRNG to initialize/import - @return CRYPT_OK if successful - */ - int (*pimport)(const unsigned char *in, unsigned long inlen, prng_state *prng); - /** Self-test the PRNG - @return CRYPT_OK if successful, CRYPT_NOP if self-testing has been disabled - */ - int (*test)(void); -} prng_descriptor[]; - -#ifdef LTC_YARROW -int yarrow_start(prng_state *prng); -int yarrow_add_entropy(const unsigned char *in, unsigned long inlen, prng_state *prng); -int yarrow_ready(prng_state *prng); -unsigned long yarrow_read(unsigned char *out, unsigned long outlen, prng_state *prng); -int yarrow_done(prng_state *prng); -int yarrow_export(unsigned char *out, unsigned long *outlen, prng_state *prng); -int yarrow_import(const unsigned char *in, unsigned long inlen, prng_state *prng); -int yarrow_test(void); -extern const struct ltc_prng_descriptor yarrow_desc; -#endif - -#ifdef LTC_FORTUNA -int fortuna_start(prng_state *prng); -int fortuna_add_entropy(const unsigned char *in, unsigned long inlen, prng_state *prng); -int fortuna_ready(prng_state *prng); -unsigned long fortuna_read(unsigned char *out, unsigned long outlen, prng_state *prng); -int fortuna_done(prng_state *prng); -int fortuna_export(unsigned char *out, unsigned long *outlen, prng_state *prng); -int fortuna_import(const unsigned char *in, unsigned long inlen, prng_state *prng); -int fortuna_test(void); -extern const struct ltc_prng_descriptor fortuna_desc; -#endif - -#ifdef LTC_RC4 -int rc4_start(prng_state *prng); -int rc4_add_entropy(const unsigned char *in, unsigned long inlen, prng_state *prng); -int rc4_ready(prng_state *prng); -unsigned long rc4_read(unsigned char *out, unsigned long outlen, prng_state *prng); -int rc4_done(prng_state *prng); -int rc4_export(unsigned char *out, unsigned long *outlen, prng_state *prng); -int rc4_import(const unsigned char *in, unsigned long inlen, prng_state *prng); -int rc4_test(void); -extern const struct ltc_prng_descriptor rc4_desc; -#endif - -#ifdef LTC_SPRNG -int sprng_start(prng_state *prng); -int sprng_add_entropy(const unsigned char *in, unsigned long inlen, prng_state *prng); -int sprng_ready(prng_state *prng); -unsigned long sprng_read(unsigned char *out, unsigned long outlen, prng_state *prng); -int sprng_done(prng_state *prng); -int sprng_export(unsigned char *out, unsigned long *outlen, prng_state *prng); -int sprng_import(const unsigned char *in, unsigned long inlen, prng_state *prng); -int sprng_test(void); -extern const struct ltc_prng_descriptor sprng_desc; -#endif - -#ifdef LTC_SOBER128 -int sober128_start(prng_state *prng); -int sober128_add_entropy(const unsigned char *in, unsigned long inlen, prng_state *prng); -int sober128_ready(prng_state *prng); -unsigned long sober128_read(unsigned char *out, unsigned long outlen, prng_state *prng); -int sober128_done(prng_state *prng); -int sober128_export(unsigned char *out, unsigned long *outlen, prng_state *prng); -int sober128_import(const unsigned char *in, unsigned long inlen, prng_state *prng); -int sober128_test(void); -extern const struct ltc_prng_descriptor sober128_desc; -#endif - -int find_prng(const char *name); -int register_prng(const struct ltc_prng_descriptor *prng); -int unregister_prng(const struct ltc_prng_descriptor *prng); -int prng_is_valid(int idx); -LTC_MUTEX_PROTO(ltc_prng_mutex) - -/* Slow RNG you **might** be able to use to seed a PRNG with. Be careful as this - * might not work on all platforms as planned - */ -unsigned long rng_get_bytes(unsigned char *out, - unsigned long outlen, - void (*callback)(void)); - -int rng_make_prng(int bits, int wprng, prng_state *prng, void (*callback)(void)); - - -/* $Source: /cvs/libtom/libtomcrypt/src/headers/tomcrypt_prng.h,v $ */ -/* $Revision: 1.9 $ */ -/* $Date: 2007/05/12 14:32:35 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/math/ltm_desc.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/math/ltm_desc.c deleted file mode 100644 index 25dc0b3..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/math/ltm_desc.c +++ /dev/null @@ -1,483 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -#define DESC_DEF_ONLY -#include "../headers/tomcrypt.h" - -#ifdef LTM_DESC - -#include "../../../libtommath/tommath.h" - -static const struct { - int mpi_code, ltc_code; -} mpi_to_ltc_codes[] = { - { MP_OKAY , CRYPT_OK}, - { MP_MEM , CRYPT_MEM}, - { MP_VAL , CRYPT_INVALID_ARG}, -}; - -/** - Convert a MPI error to a LTC error (Possibly the most powerful function ever! Oh wait... no) - @param err The error to convert - @return The equivalent LTC error code or CRYPT_ERROR if none found -*/ -static int mpi_to_ltc_error(int err) -{ - int x; - - for (x = 0; x < (int)(sizeof(mpi_to_ltc_codes)/sizeof(mpi_to_ltc_codes[0])); x++) { - if (err == mpi_to_ltc_codes[x].mpi_code) { - return mpi_to_ltc_codes[x].ltc_code; - } - } - return CRYPT_ERROR; -} - -static int init(void **a) -{ - int err; - - LTC_ARGCHK(a != NULL); - - *a = XCALLOC(1, sizeof(mp_int)); - if (*a == NULL) { - return CRYPT_MEM; - } - - if ((err = mpi_to_ltc_error(mp_init(*a))) != CRYPT_OK) { - XFREE(*a); - } - return err; -} - -static void deinit(void *a) -{ - LTC_ARGCHKVD(a != NULL); - mp_clear(a); - XFREE(a); -} - -static int neg(void *a, void *b) -{ - LTC_ARGCHK(a != NULL); - LTC_ARGCHK(b != NULL); - return mpi_to_ltc_error(mp_neg(a, b)); -} - -static int copy(void *a, void *b) -{ - LTC_ARGCHK(a != NULL); - LTC_ARGCHK(b != NULL); - return mpi_to_ltc_error(mp_copy(a, b)); -} - -static int init_copy(void **a, void *b) -{ - if (init(a) != CRYPT_OK) { - return CRYPT_MEM; - } - return copy(b, *a); -} - -/* ---- trivial ---- */ -static int set_int(void *a, unsigned long b) -{ - LTC_ARGCHK(a != NULL); - return mpi_to_ltc_error(mp_set_int(a, b)); -} - -static unsigned long get_int(void *a) -{ - LTC_ARGCHK(a != NULL); - return mp_get_int(a); -} - -static unsigned long get_digit(void *a, int n) -{ - mp_int *A; - LTC_ARGCHK(a != NULL); - A = a; - return (n >= A->used || n < 0) ? 0 : A->dp[n]; -} - -static int get_digit_count(void *a) -{ - mp_int *A; - LTC_ARGCHK(a != NULL); - A = a; - return A->used; -} - -static int compare(void *a, void *b) -{ - int ret; - LTC_ARGCHK(a != NULL); - LTC_ARGCHK(b != NULL); - ret = mp_cmp(a, b); - switch (ret) { - case MP_LT: return LTC_MP_LT; - case MP_EQ: return LTC_MP_EQ; - case MP_GT: return LTC_MP_GT; - } - return 0; -} - -static int compare_d(void *a, unsigned long b) -{ - int ret; - LTC_ARGCHK(a != NULL); - ret = mp_cmp_d(a, b); - switch (ret) { - case MP_LT: return LTC_MP_LT; - case MP_EQ: return LTC_MP_EQ; - case MP_GT: return LTC_MP_GT; - } - return 0; -} - -static int count_bits(void *a) -{ - LTC_ARGCHK(a != NULL); - return mp_count_bits(a); -} - -static int count_lsb_bits(void *a) -{ - LTC_ARGCHK(a != NULL); - return mp_cnt_lsb(a); -} - - -static int twoexpt(void *a, int n) -{ - LTC_ARGCHK(a != NULL); - return mpi_to_ltc_error(mp_2expt(a, n)); -} - -/* ---- conversions ---- */ - -/* read ascii string */ -static int read_radix(void *a, const char *b, int radix) -{ - LTC_ARGCHK(a != NULL); - LTC_ARGCHK(b != NULL); - return mpi_to_ltc_error(mp_read_radix(a, b, radix)); -} - -/* write one */ -static int write_radix(void *a, char *b, int radix) -{ - LTC_ARGCHK(a != NULL); - LTC_ARGCHK(b != NULL); - return mpi_to_ltc_error(mp_toradix(a, b, radix)); -} - -/* get size as unsigned char string */ -static unsigned long unsigned_size(void *a) -{ - LTC_ARGCHK(a != NULL); - return mp_unsigned_bin_size(a); -} - -/* store */ -static int unsigned_write(void *a, unsigned char *b) -{ - LTC_ARGCHK(a != NULL); - LTC_ARGCHK(b != NULL); - return mpi_to_ltc_error(mp_to_unsigned_bin(a, b)); -} - -/* read */ -static int unsigned_read(void *a, unsigned char *b, unsigned long len) -{ - LTC_ARGCHK(a != NULL); - LTC_ARGCHK(b != NULL); - return mpi_to_ltc_error(mp_read_unsigned_bin(a, b, len)); -} - -/* add */ -static int add(void *a, void *b, void *c) -{ - LTC_ARGCHK(a != NULL); - LTC_ARGCHK(b != NULL); - LTC_ARGCHK(c != NULL); - return mpi_to_ltc_error(mp_add(a, b, c)); -} - -static int addi(void *a, unsigned long b, void *c) -{ - LTC_ARGCHK(a != NULL); - LTC_ARGCHK(c != NULL); - return mpi_to_ltc_error(mp_add_d(a, b, c)); -} - -/* sub */ -static int sub(void *a, void *b, void *c) -{ - LTC_ARGCHK(a != NULL); - LTC_ARGCHK(b != NULL); - LTC_ARGCHK(c != NULL); - return mpi_to_ltc_error(mp_sub(a, b, c)); -} - -static int subi(void *a, unsigned long b, void *c) -{ - LTC_ARGCHK(a != NULL); - LTC_ARGCHK(c != NULL); - return mpi_to_ltc_error(mp_sub_d(a, b, c)); -} - -/* mul */ -static int mul(void *a, void *b, void *c) -{ - LTC_ARGCHK(a != NULL); - LTC_ARGCHK(b != NULL); - LTC_ARGCHK(c != NULL); - return mpi_to_ltc_error(mp_mul(a, b, c)); -} - -static int muli(void *a, unsigned long b, void *c) -{ - LTC_ARGCHK(a != NULL); - LTC_ARGCHK(c != NULL); - return mpi_to_ltc_error(mp_mul_d(a, b, c)); -} - -/* sqr */ -static int sqr(void *a, void *b) -{ - LTC_ARGCHK(a != NULL); - LTC_ARGCHK(b != NULL); - return mpi_to_ltc_error(mp_sqr(a, b)); -} - -/* div */ -static int divide(void *a, void *b, void *c, void *d) -{ - LTC_ARGCHK(a != NULL); - LTC_ARGCHK(b != NULL); - return mpi_to_ltc_error(mp_div(a, b, c, d)); -} - -static int div_2(void *a, void *b) -{ - LTC_ARGCHK(a != NULL); - LTC_ARGCHK(b != NULL); - return mpi_to_ltc_error(mp_div_2(a, b)); -} - -/* modi */ -static int modi(void *a, unsigned long b, unsigned long *c) -{ - mp_digit tmp; - int err; - - LTC_ARGCHK(a != NULL); - LTC_ARGCHK(c != NULL); - - if ((err = mpi_to_ltc_error(mp_mod_d(a, b, &tmp))) != CRYPT_OK) { - return err; - } - *c = tmp; - return CRYPT_OK; -} - -/* gcd */ -static int gcd(void *a, void *b, void *c) -{ - LTC_ARGCHK(a != NULL); - LTC_ARGCHK(b != NULL); - LTC_ARGCHK(c != NULL); - return mpi_to_ltc_error(mp_gcd(a, b, c)); -} - -/* lcm */ -static int lcm(void *a, void *b, void *c) -{ - LTC_ARGCHK(a != NULL); - LTC_ARGCHK(b != NULL); - LTC_ARGCHK(c != NULL); - return mpi_to_ltc_error(mp_lcm(a, b, c)); -} - -static int mulmod(void *a, void *b, void *c, void *d) -{ - LTC_ARGCHK(a != NULL); - LTC_ARGCHK(b != NULL); - LTC_ARGCHK(c != NULL); - LTC_ARGCHK(d != NULL); - return mpi_to_ltc_error(mp_mulmod(a,b,c,d)); -} - -static int sqrmod(void *a, void *b, void *c) -{ - LTC_ARGCHK(a != NULL); - LTC_ARGCHK(b != NULL); - LTC_ARGCHK(c != NULL); - return mpi_to_ltc_error(mp_sqrmod(a,b,c)); -} - -/* invmod */ -static int invmod(void *a, void *b, void *c) -{ - LTC_ARGCHK(a != NULL); - LTC_ARGCHK(b != NULL); - LTC_ARGCHK(c != NULL); - return mpi_to_ltc_error(mp_invmod(a, b, c)); -} - -/* setup */ -static int montgomery_setup(void *a, void **b) -{ - int err; - LTC_ARGCHK(a != NULL); - LTC_ARGCHK(b != NULL); - *b = XCALLOC(1, sizeof(mp_digit)); - if (*b == NULL) { - return CRYPT_MEM; - } - if ((err = mpi_to_ltc_error(mp_montgomery_setup(a, (mp_digit *)*b))) != CRYPT_OK) { - XFREE(*b); - } - return err; -} - -/* get normalization value */ -static int montgomery_normalization(void *a, void *b) -{ - LTC_ARGCHK(a != NULL); - LTC_ARGCHK(b != NULL); - return mpi_to_ltc_error(mp_montgomery_calc_normalization(a, b)); -} - -/* reduce */ -static int montgomery_reduce(void *a, void *b, void *c) -{ - LTC_ARGCHK(a != NULL); - LTC_ARGCHK(b != NULL); - LTC_ARGCHK(c != NULL); - return mpi_to_ltc_error(mp_montgomery_reduce(a, b, *((mp_digit *)c))); -} - -/* clean up */ -static void montgomery_deinit(void *a) -{ - XFREE(a); -} - -static int exptmod(void *a, void *b, void *c, void *d) -{ - LTC_ARGCHK(a != NULL); - LTC_ARGCHK(b != NULL); - LTC_ARGCHK(c != NULL); - LTC_ARGCHK(d != NULL); - return mpi_to_ltc_error(mp_exptmod(a,b,c,d)); -} - -static int isprime(void *a, int *b) -{ - int err; - LTC_ARGCHK(a != NULL); - LTC_ARGCHK(b != NULL); - err = mpi_to_ltc_error(mp_prime_is_prime(a, 8, b)); - *b = (*b == MP_YES) ? LTC_MP_YES : LTC_MP_NO; - return err; -} - -const ltc_math_descriptor ltm_desc = { - - "LibTomMath", - (int)DIGIT_BIT, - - &init, - &init_copy, - &deinit, - - &neg, - ©, - - &set_int, - &get_int, - &get_digit, - &get_digit_count, - &compare, - &compare_d, - &count_bits, - &count_lsb_bits, - &twoexpt, - - &read_radix, - &write_radix, - &unsigned_size, - &unsigned_write, - &unsigned_read, - - &add, - &addi, - &sub, - &subi, - &mul, - &muli, - &sqr, - ÷, - &div_2, - &modi, - &gcd, - &lcm, - - &mulmod, - &sqrmod, - &invmod, - - &montgomery_setup, - &montgomery_normalization, - &montgomery_reduce, - &montgomery_deinit, - - &exptmod, - &isprime, - -#ifdef LTC_MECC -#ifdef LTC_MECC_FP - <c_ecc_fp_mulmod, -#else - <c_ecc_mulmod, -#endif - <c_ecc_projective_add_point, - <c_ecc_projective_dbl_point, - <c_ecc_map, -#ifdef LTC_ECC_SHAMIR -#ifdef LTC_MECC_FP - <c_ecc_fp_mul2add, -#else - <c_ecc_mul2add, -#endif /* LTC_MECC_FP */ -#else - NULL, -#endif /* LTC_ECC_SHAMIR */ -#else - NULL, NULL, NULL, NULL, NULL, -#endif /* LTC_MECC */ - -#ifdef LTC_MRSA - &rsa_make_key, - &rsa_exptmod, -#else - NULL, NULL -#endif -}; - - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/math/ltm_desc.c,v $ */ -/* $Revision: 1.31 $ */ -/* $Date: 2007/05/12 14:32:35 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/math/multi.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/math/multi.c deleted file mode 100644 index 7d40040..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/math/multi.c +++ /dev/null @@ -1,61 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../headers/tomcrypt.h" - -#ifdef MPI -#include - -int ltc_init_multi(void **a, ...) -{ - void **cur = a; - int np = 0; - va_list args; - - va_start(args, a); - while (cur != NULL) { - if (mp_init(cur) != CRYPT_OK) { - /* failed */ - va_list clean_list; - - va_start(clean_list, a); - cur = a; - while (np--) { - mp_clear(*cur); - cur = va_arg(clean_list, void**); - } - va_end(clean_list); - return CRYPT_MEM; - } - ++np; - cur = va_arg(args, void**); - } - va_end(args); - return CRYPT_OK; -} - -void ltc_deinit_multi(void *a, ...) -{ - void *cur = a; - va_list args; - - va_start(args, a); - while (cur != NULL) { - mp_clear(cur); - cur = va_arg(args, void *); - } - va_end(args); -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/math/multi.c,v $ */ -/* $Revision: 1.6 $ */ -/* $Date: 2006/12/28 01:27:23 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/math/rand_prime.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/math/rand_prime.c deleted file mode 100644 index 913fa95..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/math/rand_prime.c +++ /dev/null @@ -1,87 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../headers/tomcrypt.h" - -/** - @file rand_prime.c - Generate a random prime, Tom St Denis -*/ - -#define USE_BBS 1 - -int rand_prime(void *N, long len, prng_state *prng, int wprng) -{ - int err, res, type; - unsigned char *buf; - - LTC_ARGCHK(N != NULL); - - /* get type */ - if (len < 0) { - type = USE_BBS; - len = -len; - } else { - type = 0; - } - - /* allow sizes between 2 and 512 bytes for a prime size */ - if (len < 2 || len > 512) { - return CRYPT_INVALID_PRIME_SIZE; - } - - /* valid PRNG? Better be! */ - if ((err = prng_is_valid(wprng)) != CRYPT_OK) { - return err; - } - - /* allocate buffer to work with */ - buf = XCALLOC(1, len); - if (buf == NULL) { - return CRYPT_MEM; - } - - do { - /* generate value */ - if (prng_descriptor[wprng].read(buf, len, prng) != (unsigned long)len) { - XFREE(buf); - return CRYPT_ERROR_READPRNG; - } - - /* munge bits */ - buf[0] |= 0x80 | 0x40; - buf[len-1] |= 0x01 | ((type & USE_BBS) ? 0x02 : 0x00); - - /* load value */ - if ((err = mp_read_unsigned_bin(N, buf, len)) != CRYPT_OK) { - XFREE(buf); - return err; - } - - /* test */ - if ((err = mp_prime_is_prime(N, 8, &res)) != CRYPT_OK) { - XFREE(buf); - return err; - } - } while (res == LTC_MP_NO); - -#ifdef LTC_CLEAN_STACK - zeromem(buf, len); -#endif - - XFREE(buf); - return CRYPT_OK; -} - - - -/* $Source: /cvs/libtom/libtomcrypt/src/math/rand_prime.c,v $ */ -/* $Revision: 1.7 $ */ -/* $Date: 2006/12/28 01:27:23 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/base64_decode.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/base64_decode.c deleted file mode 100644 index 3d13393..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/base64_decode.c +++ /dev/null @@ -1,104 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../headers/tomcrypt.h" - -/** - @file base64_decode.c - Compliant base64 code donated by Wayne Scott (wscott@bitmover.com) -*/ - - -#ifdef LTC_BASE64 - -static const unsigned char map[256] = { -255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, -255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, -255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, -255, 255, 255, 255, 255, 255, 255, 62, 255, 255, 255, 63, - 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 255, 255, -255, 254, 255, 255, 255, 0, 1, 2, 3, 4, 5, 6, - 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, - 19, 20, 21, 22, 23, 24, 25, 255, 255, 255, 255, 255, -255, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, - 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, - 49, 50, 51, 255, 255, 255, 255, 255, 255, 255, 255, 255, -255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, -255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, -255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, -255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, -255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, -255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, -255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, -255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, -255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, -255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, -255, 255, 255, 255 }; - -/** - base64 decode a block of memory - @param in The base64 data to decode - @param inlen The length of the base64 data - @param out [out] The destination of the binary decoded data - @param outlen [in/out] The max size and resulting size of the decoded data - @return CRYPT_OK if successful -*/ -int base64_decode(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen) -{ - unsigned long t, x, y, z; - unsigned char c; - int g; - - LTC_ARGCHK(in != NULL); - LTC_ARGCHK(out != NULL); - LTC_ARGCHK(outlen != NULL); - - g = 3; - for (x = y = z = t = 0; x < inlen; x++) { - c = map[in[x]&0xFF]; - if (c == 255) continue; - /* the final = symbols are read and used to trim the remaining bytes */ - if (c == 254) { - c = 0; - /* prevent g < 0 which would potentially allow an overflow later */ - if (--g < 0) { - return CRYPT_INVALID_PACKET; - } - } else if (g != 3) { - /* we only allow = to be at the end */ - return CRYPT_INVALID_PACKET; - } - - t = (t<<6)|c; - - if (++y == 4) { - if (z + g > *outlen) { - return CRYPT_BUFFER_OVERFLOW; - } - out[z++] = (unsigned char)((t>>16)&255); - if (g > 1) out[z++] = (unsigned char)((t>>8)&255); - if (g > 2) out[z++] = (unsigned char)(t&255); - y = t = 0; - } - } - if (y != 0) { - return CRYPT_INVALID_PACKET; - } - *outlen = z; - return CRYPT_OK; -} - -#endif - - -/* $Source: /cvs/libtom/libtomcrypt/src/misc/base64/base64_decode.c,v $ */ -/* $Revision: 1.6 $ */ -/* $Date: 2007/05/12 14:32:35 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_argchk.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_argchk.c deleted file mode 100644 index 537516d..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_argchk.c +++ /dev/null @@ -1,30 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../headers/tomcrypt.h" -#include - -/** - @file crypt_argchk.c - Perform argument checking, Tom St Denis -*/ - -#if (ARGTYPE == 0) -void crypt_argchk(char *v, char *s, int d) -{ - fprintf(stderr, "LTC_ARGCHK '%s' failure on line %d of file %s\n", - v, d, s); - (void)raise(SIGABRT); -} -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/misc/crypt/crypt_argchk.c,v $ */ -/* $Revision: 1.5 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_find_hash.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_find_hash.c deleted file mode 100644 index fef2d8c..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_find_hash.c +++ /dev/null @@ -1,40 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../headers/tomcrypt.h" - -/** - @file crypt_find_hash.c - Find a hash, Tom St Denis -*/ - -/** - Find a registered hash by name - @param name The name of the hash to look for - @return >= 0 if found, -1 if not present -*/ -int find_hash(const char *name) -{ - int x; - LTC_ARGCHK(name != NULL); - LTC_MUTEX_LOCK(<c_hash_mutex); - for (x = 0; x < TAB_SIZE; x++) { - if (hash_descriptor[x].name != NULL && XSTRCMP(hash_descriptor[x].name, name) == 0) { - LTC_MUTEX_UNLOCK(<c_hash_mutex); - return x; - } - } - LTC_MUTEX_UNLOCK(<c_hash_mutex); - return -1; -} - -/* $Source: /cvs/libtom/libtomcrypt/src/misc/crypt/crypt_find_hash.c,v $ */ -/* $Revision: 1.7 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_find_prng.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_find_prng.c deleted file mode 100644 index fafbb0e..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_find_prng.c +++ /dev/null @@ -1,41 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../headers/tomcrypt.h" - -/** - @file crypt_find_prng.c - Find a PRNG, Tom St Denis -*/ - -/** - Find a registered PRNG by name - @param name The name of the PRNG to look for - @return >= 0 if found, -1 if not present -*/ -int find_prng(const char *name) -{ - int x; - LTC_ARGCHK(name != NULL); - LTC_MUTEX_LOCK(<c_prng_mutex); - for (x = 0; x < TAB_SIZE; x++) { - if ((prng_descriptor[x].name != NULL) && XSTRCMP(prng_descriptor[x].name, name) == 0) { - LTC_MUTEX_UNLOCK(<c_prng_mutex); - return x; - } - } - LTC_MUTEX_UNLOCK(<c_prng_mutex); - return -1; -} - - -/* $Source: /cvs/libtom/libtomcrypt/src/misc/crypt/crypt_find_prng.c,v $ */ -/* $Revision: 1.7 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_hash_descriptor.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_hash_descriptor.c deleted file mode 100644 index 5925fd2..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_hash_descriptor.c +++ /dev/null @@ -1,27 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../headers/tomcrypt.h" - -/** - @file crypt_hash_descriptor.c - Stores the hash descriptor table, Tom St Denis -*/ - -struct ltc_hash_descriptor hash_descriptor[TAB_SIZE] = { -{ NULL, 0, 0, 0, { 0 }, 0, NULL, NULL, NULL, NULL, NULL } -}; - -LTC_MUTEX_GLOBAL(ltc_hash_mutex) - - -/* $Source: /cvs/libtom/libtomcrypt/src/misc/crypt/crypt_hash_descriptor.c,v $ */ -/* $Revision: 1.10 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_hash_is_valid.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_hash_is_valid.c deleted file mode 100644 index 8ed5105..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_hash_is_valid.c +++ /dev/null @@ -1,36 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../headers/tomcrypt.h" - -/** - @file crypt_hash_is_valid.c - Determine if hash is valid, Tom St Denis -*/ - -/* - Test if a hash index is valid - @param idx The index of the hash to search for - @return CRYPT_OK if valid -*/ -int hash_is_valid(int idx) -{ - LTC_MUTEX_LOCK(<c_hash_mutex); - if (idx < 0 || idx >= TAB_SIZE || hash_descriptor[idx].name == NULL) { - LTC_MUTEX_UNLOCK(<c_hash_mutex); - return CRYPT_INVALID_HASH; - } - LTC_MUTEX_UNLOCK(<c_hash_mutex); - return CRYPT_OK; -} - -/* $Source: /cvs/libtom/libtomcrypt/src/misc/crypt/crypt_hash_is_valid.c,v $ */ -/* $Revision: 1.6 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_libc.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_libc.c deleted file mode 100644 index 3457a52..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_libc.c +++ /dev/null @@ -1,43 +0,0 @@ -/*****************************************************************************/ -/* crypt_libc.c Copyright (c) Ladislav Zezula 2010 */ -/*---------------------------------------------------------------------------*/ -/* Description: */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 05.05.10 1.00 Lad The first version of crypt_libc.c */ -/*****************************************************************************/ - -// LibTomCrypt header -#include -#include "../headers/tomcrypt.h" - -LTC_EXPORT void * LTC_CALL LibTomMalloc(size_t n) -{ - return malloc(n); -} - -LTC_EXPORT void * LTC_CALL LibTomCalloc(size_t n, size_t s) -{ - return calloc(n, s); -} - -LTC_EXPORT void * LTC_CALL LibTomRealloc(void *p, size_t n) -{ - return realloc(p, n); -} - -LTC_EXPORT void LTC_CALL LibTomFree(void * p) -{ - free(p); -} - -LTC_EXPORT clock_t LTC_CALL LibTomClock(void) -{ - return clock(); -} - -LTC_EXPORT void LTC_CALL LibTomQsort(void *base, size_t nmemb, size_t size, int(LTC_CALL * compar)(const void *, const void *)) -{ - qsort(base, nmemb, size, compar); -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_ltc_mp_descriptor.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_ltc_mp_descriptor.c deleted file mode 100644 index c02a96f..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_ltc_mp_descriptor.c +++ /dev/null @@ -1,13 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../headers/tomcrypt.h" - -ltc_math_descriptor ltc_mp = {0}; diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_prng_descriptor.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_prng_descriptor.c deleted file mode 100644 index c5b39e0..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_prng_descriptor.c +++ /dev/null @@ -1,26 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../headers/tomcrypt.h" - -/** - @file crypt_prng_descriptor.c - Stores the PRNG descriptors, Tom St Denis -*/ -struct ltc_prng_descriptor prng_descriptor[TAB_SIZE] = { -{ NULL, 0, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL } -}; - -LTC_MUTEX_GLOBAL(ltc_prng_mutex) - - -/* $Source: /cvs/libtom/libtomcrypt/src/misc/crypt/crypt_prng_descriptor.c,v $ */ -/* $Revision: 1.8 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_prng_is_valid.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_prng_is_valid.c deleted file mode 100644 index d38fd3a..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_prng_is_valid.c +++ /dev/null @@ -1,36 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../headers/tomcrypt.h" - -/** - @file crypt_prng_is_valid.c - Determine if PRNG is valid, Tom St Denis -*/ - -/* - Test if a PRNG index is valid - @param idx The index of the PRNG to search for - @return CRYPT_OK if valid -*/ -int prng_is_valid(int idx) -{ - LTC_MUTEX_LOCK(<c_prng_mutex); - if (idx < 0 || idx >= TAB_SIZE || prng_descriptor[idx].name == NULL) { - LTC_MUTEX_UNLOCK(<c_prng_mutex); - return CRYPT_INVALID_PRNG; - } - LTC_MUTEX_UNLOCK(<c_prng_mutex); - return CRYPT_OK; -} - -/* $Source: /cvs/libtom/libtomcrypt/src/misc/crypt/crypt_prng_is_valid.c,v $ */ -/* $Revision: 1.6 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_register_hash.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_register_hash.c deleted file mode 100644 index 1730091..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_register_hash.c +++ /dev/null @@ -1,54 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../headers/tomcrypt.h" - -/** - @file crypt_register_hash.c - Register a HASH, Tom St Denis -*/ - -/** - Register a hash with the descriptor table - @param hash The hash you wish to register - @return value >= 0 if successfully added (or already present), -1 if unsuccessful -*/ -int register_hash(const struct ltc_hash_descriptor *hash) -{ - int x; - - LTC_ARGCHK(hash != NULL); - - /* is it already registered? */ - LTC_MUTEX_LOCK(<c_hash_mutex); - for (x = 0; x < TAB_SIZE; x++) { - if (XMEMCMP(&hash_descriptor[x], hash, sizeof(struct ltc_hash_descriptor)) == 0) { - LTC_MUTEX_UNLOCK(<c_hash_mutex); - return x; - } - } - - /* find a blank spot */ - for (x = 0; x < TAB_SIZE; x++) { - if (hash_descriptor[x].name == NULL) { - XMEMCPY(&hash_descriptor[x], hash, sizeof(struct ltc_hash_descriptor)); - LTC_MUTEX_UNLOCK(<c_hash_mutex); - return x; - } - } - - /* no spot */ - LTC_MUTEX_UNLOCK(<c_hash_mutex); - return -1; -} - -/* $Source: /cvs/libtom/libtomcrypt/src/misc/crypt/crypt_register_hash.c,v $ */ -/* $Revision: 1.7 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_register_prng.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_register_prng.c deleted file mode 100644 index 29fc9bd..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/crypt_register_prng.c +++ /dev/null @@ -1,54 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../headers/tomcrypt.h" - -/** - @file crypt_register_prng.c - Register a PRNG, Tom St Denis -*/ - -/** - Register a PRNG with the descriptor table - @param prng The PRNG you wish to register - @return value >= 0 if successfully added (or already present), -1 if unsuccessful -*/ -int register_prng(const struct ltc_prng_descriptor *prng) -{ - int x; - - LTC_ARGCHK(prng != NULL); - - /* is it already registered? */ - LTC_MUTEX_LOCK(<c_prng_mutex); - for (x = 0; x < TAB_SIZE; x++) { - if (XMEMCMP(&prng_descriptor[x], prng, sizeof(struct ltc_prng_descriptor)) == 0) { - LTC_MUTEX_UNLOCK(<c_prng_mutex); - return x; - } - } - - /* find a blank spot */ - for (x = 0; x < TAB_SIZE; x++) { - if (prng_descriptor[x].name == NULL) { - XMEMCPY(&prng_descriptor[x], prng, sizeof(struct ltc_prng_descriptor)); - LTC_MUTEX_UNLOCK(<c_prng_mutex); - return x; - } - } - - /* no spot */ - LTC_MUTEX_UNLOCK(<c_prng_mutex); - return -1; -} - -/* $Source: /cvs/libtom/libtomcrypt/src/misc/crypt/crypt_register_prng.c,v $ */ -/* $Revision: 1.8 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/zeromem.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/zeromem.c deleted file mode 100644 index faa0efa..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/misc/zeromem.c +++ /dev/null @@ -1,34 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../headers/tomcrypt.h" - -/** - @file zeromem.c - Zero a block of memory, Tom St Denis -*/ - -/** - Zero a block of memory - @param out The destination of the area to zero - @param outlen The length of the area to zero (octets) -*/ -void zeromem(void *out, size_t outlen) -{ - unsigned char *mem = out; - LTC_ARGCHKVD(out != NULL); - while (outlen-- > 0) { - *mem++ = 0; - } -} - -/* $Source: /cvs/libtom/libtomcrypt/src/misc/zeromem.c,v $ */ -/* $Revision: 1.7 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_bit_string.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_bit_string.c deleted file mode 100644 index e536867..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_bit_string.c +++ /dev/null @@ -1,102 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_decode_bit_string.c - ASN.1 DER, encode a BIT STRING, Tom St Denis -*/ - - -#ifdef LTC_DER - -/** - Store a BIT STRING - @param in The DER encoded BIT STRING - @param inlen The size of the DER BIT STRING - @param out [out] The array of bits stored (one per char) - @param outlen [in/out] The number of bits stored - @return CRYPT_OK if successful -*/ -int der_decode_bit_string(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen) -{ - unsigned long dlen, blen, x, y; - - LTC_ARGCHK(in != NULL); - LTC_ARGCHK(out != NULL); - LTC_ARGCHK(outlen != NULL); - - /* packet must be at least 4 bytes */ - if (inlen < 4) { - return CRYPT_INVALID_ARG; - } - - /* check for 0x03 */ - if ((in[0]&0x1F) != 0x03) { - return CRYPT_INVALID_PACKET; - } - - /* offset in the data */ - x = 1; - - /* get the length of the data */ - if (in[x] & 0x80) { - /* long format get number of length bytes */ - y = in[x++] & 0x7F; - - /* invalid if 0 or > 2 */ - if (y == 0 || y > 2) { - return CRYPT_INVALID_PACKET; - } - - /* read the data len */ - dlen = 0; - while (y--) { - dlen = (dlen << 8) | (unsigned long)in[x++]; - } - } else { - /* short format */ - dlen = in[x++] & 0x7F; - } - - /* is the data len too long or too short? */ - if ((dlen == 0) || (dlen + x > inlen)) { - return CRYPT_INVALID_PACKET; - } - - /* get padding count */ - blen = ((dlen - 1) << 3) - (in[x++] & 7); - - /* too many bits? */ - if (blen > *outlen) { - *outlen = blen; - return CRYPT_BUFFER_OVERFLOW; - } - - /* decode/store the bits */ - for (y = 0; y < blen; y++) { - out[y] = (in[x] & (1 << (7 - (y & 7)))) ? 1 : 0; - if ((y & 7) == 7) { - ++x; - } - } - - /* we done */ - *outlen = blen; - return CRYPT_OK; -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/bit/der_decode_bit_string.c,v $ */ -/* $Revision: 1.5 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_boolean.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_boolean.c deleted file mode 100644 index 617d4e8..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_boolean.c +++ /dev/null @@ -1,47 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_decode_boolean.c - ASN.1 DER, decode a BOOLEAN, Tom St Denis -*/ - - -#ifdef LTC_DER - -/** - Read a BOOLEAN - @param in The destination for the DER encoded BOOLEAN - @param inlen The size of the DER BOOLEAN - @param out [out] The boolean to decode - @return CRYPT_OK if successful -*/ -int der_decode_boolean(const unsigned char *in, unsigned long inlen, - int *out) -{ - LTC_ARGCHK(in != NULL); - LTC_ARGCHK(out != NULL); - - if (inlen != 3 || in[0] != 0x01 || in[1] != 0x01 || (in[2] != 0x00 && in[2] != 0xFF)) { - return CRYPT_INVALID_ARG; - } - - *out = (in[2]==0xFF) ? 1 : 0; - - return CRYPT_OK; -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/boolean/der_decode_boolean.c,v $ */ -/* $Revision: 1.2 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_choice.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_choice.c deleted file mode 100644 index 44a0891..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_choice.c +++ /dev/null @@ -1,182 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_decode_choice.c - ASN.1 DER, decode a CHOICE, Tom St Denis -*/ - -#ifdef LTC_DER - -/** - Decode a CHOICE - @param in The DER encoded input - @param inlen [in/out] The size of the input and resulting size of read type - @param list The list of items to decode - @param outlen The number of items in the list - @return CRYPT_OK on success -*/ -int der_decode_choice(const unsigned char *in, unsigned long *inlen, - ltc_asn1_list *list, unsigned long outlen) -{ - unsigned long size, x, z; - void *data; - - LTC_ARGCHK(in != NULL); - LTC_ARGCHK(inlen != NULL); - LTC_ARGCHK(list != NULL); - - /* get blk size */ - if (*inlen < 2) { - return CRYPT_INVALID_PACKET; - } - - /* set all of the "used" flags to zero */ - for (x = 0; x < outlen; x++) { - list[x].used = 0; - } - - /* now scan until we have a winner */ - for (x = 0; x < outlen; x++) { - size = list[x].size; - data = list[x].data; - - switch (list[x].type) { - case LTC_ASN1_INTEGER: - if (der_decode_integer(in, *inlen, data) == CRYPT_OK) { - if (der_length_integer(data, &z) == CRYPT_OK) { - list[x].used = 1; - *inlen = z; - return CRYPT_OK; - } - } - break; - - case LTC_ASN1_SHORT_INTEGER: - if (der_decode_short_integer(in, *inlen, data) == CRYPT_OK) { - if (der_length_short_integer(size, &z) == CRYPT_OK) { - list[x].used = 1; - *inlen = z; - return CRYPT_OK; - } - } - break; - - case LTC_ASN1_BIT_STRING: - if (der_decode_bit_string(in, *inlen, data, &size) == CRYPT_OK) { - if (der_length_bit_string(size, &z) == CRYPT_OK) { - list[x].used = 1; - list[x].size = size; - *inlen = z; - return CRYPT_OK; - } - } - break; - - case LTC_ASN1_OCTET_STRING: - if (der_decode_octet_string(in, *inlen, data, &size) == CRYPT_OK) { - if (der_length_octet_string(size, &z) == CRYPT_OK) { - list[x].used = 1; - list[x].size = size; - *inlen = z; - return CRYPT_OK; - } - } - break; - - case LTC_ASN1_NULL: - if (*inlen == 2 && in[x] == 0x05 && in[x+1] == 0x00) { - *inlen = 2; - list[x].used = 1; - return CRYPT_OK; - } - break; - - case LTC_ASN1_OBJECT_IDENTIFIER: - if (der_decode_object_identifier(in, *inlen, data, &size) == CRYPT_OK) { - if (der_length_object_identifier(data, size, &z) == CRYPT_OK) { - list[x].used = 1; - list[x].size = size; - *inlen = z; - return CRYPT_OK; - } - } - break; - - case LTC_ASN1_IA5_STRING: - if (der_decode_ia5_string(in, *inlen, data, &size) == CRYPT_OK) { - if (der_length_ia5_string(data, size, &z) == CRYPT_OK) { - list[x].used = 1; - list[x].size = size; - *inlen = z; - return CRYPT_OK; - } - } - break; - - - case LTC_ASN1_PRINTABLE_STRING: - if (der_decode_printable_string(in, *inlen, data, &size) == CRYPT_OK) { - if (der_length_printable_string(data, size, &z) == CRYPT_OK) { - list[x].used = 1; - list[x].size = size; - *inlen = z; - return CRYPT_OK; - } - } - break; - - case LTC_ASN1_UTF8_STRING: - if (der_decode_utf8_string(in, *inlen, data, &size) == CRYPT_OK) { - if (der_length_utf8_string(data, size, &z) == CRYPT_OK) { - list[x].used = 1; - list[x].size = size; - *inlen = z; - return CRYPT_OK; - } - } - break; - - case LTC_ASN1_UTCTIME: - z = *inlen; - if (der_decode_utctime(in, &z, data) == CRYPT_OK) { - list[x].used = 1; - *inlen = z; - return CRYPT_OK; - } - break; - - case LTC_ASN1_SET: - case LTC_ASN1_SETOF: - case LTC_ASN1_SEQUENCE: - if (der_decode_sequence(in, *inlen, data, size) == CRYPT_OK) { - if (der_length_sequence(data, size, &z) == CRYPT_OK) { - list[x].used = 1; - *inlen = z; - return CRYPT_OK; - } - } - break; - - default: - return CRYPT_INVALID_ARG; - } - } - - return CRYPT_INVALID_PACKET; -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/choice/der_decode_choice.c,v $ */ -/* $Revision: 1.9 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_ia5_string.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_ia5_string.c deleted file mode 100644 index f2e073b..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_ia5_string.c +++ /dev/null @@ -1,96 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_decode_ia5_string.c - ASN.1 DER, encode a IA5 STRING, Tom St Denis -*/ - - -#ifdef LTC_DER - -/** - Store a IA5 STRING - @param in The DER encoded IA5 STRING - @param inlen The size of the DER IA5 STRING - @param out [out] The array of octets stored (one per char) - @param outlen [in/out] The number of octets stored - @return CRYPT_OK if successful -*/ -int der_decode_ia5_string(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen) -{ - unsigned long x, y, len; - int t; - - LTC_ARGCHK(in != NULL); - LTC_ARGCHK(out != NULL); - LTC_ARGCHK(outlen != NULL); - - /* must have header at least */ - if (inlen < 2) { - return CRYPT_INVALID_PACKET; - } - - /* check for 0x16 */ - if ((in[0] & 0x1F) != 0x16) { - return CRYPT_INVALID_PACKET; - } - x = 1; - - /* decode the length */ - if (in[x] & 0x80) { - /* valid # of bytes in length are 1,2,3 */ - y = in[x] & 0x7F; - if ((y == 0) || (y > 3) || ((x + y) > inlen)) { - return CRYPT_INVALID_PACKET; - } - - /* read the length in */ - len = 0; - ++x; - while (y--) { - len = (len << 8) | in[x++]; - } - } else { - len = in[x++] & 0x7F; - } - - /* is it too long? */ - if (len > *outlen) { - *outlen = len; - return CRYPT_BUFFER_OVERFLOW; - } - - if (len + x > inlen) { - return CRYPT_INVALID_PACKET; - } - - /* read the data */ - for (y = 0; y < len; y++) { - t = der_ia5_value_decode(in[x++]); - if (t == -1) { - return CRYPT_INVALID_ARG; - } - out[y] = t; - } - - *outlen = y; - - return CRYPT_OK; -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/ia5/der_decode_ia5_string.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_integer.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_integer.c deleted file mode 100644 index cca2745..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_integer.c +++ /dev/null @@ -1,110 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_decode_integer.c - ASN.1 DER, decode an integer, Tom St Denis -*/ - - -#ifdef LTC_DER - -/** - Read a mp_int integer - @param in The DER encoded data - @param inlen Size of DER encoded data - @param num The first mp_int to decode - @return CRYPT_OK if successful -*/ -int der_decode_integer(const unsigned char *in, unsigned long inlen, void *num) -{ - unsigned long x, y, z; - int err; - - LTC_ARGCHK(num != NULL); - LTC_ARGCHK(in != NULL); - - /* min DER INTEGER is 0x02 01 00 == 0 */ - if (inlen < (1 + 1 + 1)) { - return CRYPT_INVALID_PACKET; - } - - /* ok expect 0x02 when we AND with 0001 1111 [1F] */ - x = 0; - if ((in[x++] & 0x1F) != 0x02) { - return CRYPT_INVALID_PACKET; - } - - /* now decode the len stuff */ - z = in[x++]; - - if ((z & 0x80) == 0x00) { - /* short form */ - - /* will it overflow? */ - if (x + z > inlen) { - return CRYPT_INVALID_PACKET; - } - - /* no so read it */ - if ((err = mp_read_unsigned_bin(num, (unsigned char *)in + x, z)) != CRYPT_OK) { - return err; - } - } else { - /* long form */ - z &= 0x7F; - - /* will number of length bytes overflow? (or > 4) */ - if (((x + z) > inlen) || (z > 4) || (z == 0)) { - return CRYPT_INVALID_PACKET; - } - - /* now read it in */ - y = 0; - while (z--) { - y = ((unsigned long)(in[x++])) | (y << 8); - } - - /* now will reading y bytes overrun? */ - if ((x + y) > inlen) { - return CRYPT_INVALID_PACKET; - } - - /* no so read it */ - if ((err = mp_read_unsigned_bin(num, (unsigned char *)in + x, y)) != CRYPT_OK) { - return err; - } - } - - /* see if it's negative */ - if (in[x] & 0x80) { - void *tmp; - if (mp_init(&tmp) != CRYPT_OK) { - return CRYPT_MEM; - } - - if (mp_2expt(tmp, mp_count_bits(num)) != CRYPT_OK || mp_sub(num, tmp, num) != CRYPT_OK) { - mp_clear(tmp); - return CRYPT_MEM; - } - mp_clear(tmp); - } - - return CRYPT_OK; - -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/integer/der_decode_integer.c,v $ */ -/* $Revision: 1.5 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_object_identifier.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_object_identifier.c deleted file mode 100644 index e7baae8..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_object_identifier.c +++ /dev/null @@ -1,99 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_decode_object_identifier.c - ASN.1 DER, Decode Object Identifier, Tom St Denis -*/ - -#ifdef LTC_DER -/** - Decode OID data and store the array of integers in words - @param in The OID DER encoded data - @param inlen The length of the OID data - @param words [out] The destination of the OID words - @param outlen [in/out] The number of OID words - @return CRYPT_OK if successful -*/ -int der_decode_object_identifier(const unsigned char *in, unsigned long inlen, - unsigned long *words, unsigned long *outlen) -{ - unsigned long x, y, t, len; - - LTC_ARGCHK(in != NULL); - LTC_ARGCHK(words != NULL); - LTC_ARGCHK(outlen != NULL); - - /* header is at least 3 bytes */ - if (inlen < 3) { - return CRYPT_INVALID_PACKET; - } - - /* must be room for at least two words */ - if (*outlen < 2) { - return CRYPT_BUFFER_OVERFLOW; - } - - /* decode the packet header */ - x = 0; - if ((in[x++] & 0x1F) != 0x06) { - return CRYPT_INVALID_PACKET; - } - - /* get the length */ - if (in[x] < 128) { - len = in[x++]; - } else { - if (in[x] < 0x81 || in[x] > 0x82) { - return CRYPT_INVALID_PACKET; - } - y = in[x++] & 0x7F; - len = 0; - while (y--) { - len = (len << 8) | (unsigned long)in[x++]; - } - } - - if (len < 1 || (len + x) > inlen) { - return CRYPT_INVALID_PACKET; - } - - /* decode words */ - y = 0; - t = 0; - while (len--) { - t = (t << 7) | (in[x] & 0x7F); - if (!(in[x++] & 0x80)) { - /* store t */ - if (y >= *outlen) { - return CRYPT_BUFFER_OVERFLOW; - } - if (y == 0) { - words[0] = t / 40; - words[1] = t % 40; - y = 2; - } else { - words[y++] = t; - } - t = 0; - } - } - - *outlen = y; - return CRYPT_OK; -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/object_identifier/der_decode_object_identifier.c,v $ */ -/* $Revision: 1.6 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_octet_string.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_octet_string.c deleted file mode 100644 index 523d0ba..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_octet_string.c +++ /dev/null @@ -1,91 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_decode_octet_string.c - ASN.1 DER, encode a OCTET STRING, Tom St Denis -*/ - - -#ifdef LTC_DER - -/** - Store a OCTET STRING - @param in The DER encoded OCTET STRING - @param inlen The size of the DER OCTET STRING - @param out [out] The array of octets stored (one per char) - @param outlen [in/out] The number of octets stored - @return CRYPT_OK if successful -*/ -int der_decode_octet_string(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen) -{ - unsigned long x, y, len; - - LTC_ARGCHK(in != NULL); - LTC_ARGCHK(out != NULL); - LTC_ARGCHK(outlen != NULL); - - /* must have header at least */ - if (inlen < 2) { - return CRYPT_INVALID_PACKET; - } - - /* check for 0x04 */ - if ((in[0] & 0x1F) != 0x04) { - return CRYPT_INVALID_PACKET; - } - x = 1; - - /* decode the length */ - if (in[x] & 0x80) { - /* valid # of bytes in length are 1,2,3 */ - y = in[x] & 0x7F; - if ((y == 0) || (y > 3) || ((x + y) > inlen)) { - return CRYPT_INVALID_PACKET; - } - - /* read the length in */ - len = 0; - ++x; - while (y--) { - len = (len << 8) | in[x++]; - } - } else { - len = in[x++] & 0x7F; - } - - /* is it too long? */ - if (len > *outlen) { - *outlen = len; - return CRYPT_BUFFER_OVERFLOW; - } - - if (len + x > inlen) { - return CRYPT_INVALID_PACKET; - } - - /* read the data */ - for (y = 0; y < len; y++) { - out[y] = in[x++]; - } - - *outlen = y; - - return CRYPT_OK; -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/octet/der_decode_octet_string.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_printable_string.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_printable_string.c deleted file mode 100644 index f832593..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_printable_string.c +++ /dev/null @@ -1,96 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_decode_printable_string.c - ASN.1 DER, encode a printable STRING, Tom St Denis -*/ - - -#ifdef LTC_DER - -/** - Store a printable STRING - @param in The DER encoded printable STRING - @param inlen The size of the DER printable STRING - @param out [out] The array of octets stored (one per char) - @param outlen [in/out] The number of octets stored - @return CRYPT_OK if successful -*/ -int der_decode_printable_string(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen) -{ - unsigned long x, y, len; - int t; - - LTC_ARGCHK(in != NULL); - LTC_ARGCHK(out != NULL); - LTC_ARGCHK(outlen != NULL); - - /* must have header at least */ - if (inlen < 2) { - return CRYPT_INVALID_PACKET; - } - - /* check for 0x13 */ - if ((in[0] & 0x1F) != 0x13) { - return CRYPT_INVALID_PACKET; - } - x = 1; - - /* decode the length */ - if (in[x] & 0x80) { - /* valid # of bytes in length are 1,2,3 */ - y = in[x] & 0x7F; - if ((y == 0) || (y > 3) || ((x + y) > inlen)) { - return CRYPT_INVALID_PACKET; - } - - /* read the length in */ - len = 0; - ++x; - while (y--) { - len = (len << 8) | in[x++]; - } - } else { - len = in[x++] & 0x7F; - } - - /* is it too long? */ - if (len > *outlen) { - *outlen = len; - return CRYPT_BUFFER_OVERFLOW; - } - - if (len + x > inlen) { - return CRYPT_INVALID_PACKET; - } - - /* read the data */ - for (y = 0; y < len; y++) { - t = der_printable_value_decode(in[x++]); - if (t == -1) { - return CRYPT_INVALID_ARG; - } - out[y] = t; - } - - *outlen = y; - - return CRYPT_OK; -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/printable_string/der_decode_printable_string.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_sequence_ex.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_sequence_ex.c deleted file mode 100644 index 9b00f61..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_sequence_ex.c +++ /dev/null @@ -1,287 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" -#include - - -/** - @file der_decode_sequence_ex.c - ASN.1 DER, decode a SEQUENCE, Tom St Denis -*/ - -#ifdef LTC_DER - -/** - Decode a SEQUENCE - @param in The DER encoded input - @param inlen The size of the input - @param list The list of items to decode - @param outlen The number of items in the list - @param ordered Search an unordeded or ordered list - @return CRYPT_OK on success -*/ -int der_decode_sequence_ex(const unsigned char *in, unsigned long inlen, - ltc_asn1_list *list, unsigned long outlen, int ordered) -{ - int err, type; - unsigned long size, x, y, z, i, blksize; - void *data; - - LTC_ARGCHK(in != NULL); - LTC_ARGCHK(list != NULL); - - /* get blk size */ - if (inlen < 2) { - return CRYPT_INVALID_PACKET; - } - - /* sequence type? We allow 0x30 SEQUENCE and 0x31 SET since fundamentally they're the same structure */ - x = 0; - if (in[x] != 0x30 && in[x] != 0x31) { - return CRYPT_INVALID_PACKET; - } - ++x; - - if (in[x] < 128) { - blksize = in[x++]; - } else if (in[x] & 0x80) { - if (in[x] < 0x81 || in[x] > 0x83) { - return CRYPT_INVALID_PACKET; - } - y = in[x++] & 0x7F; - - /* would reading the len bytes overrun? */ - if (x + y > inlen) { - return CRYPT_INVALID_PACKET; - } - - /* read len */ - blksize = 0; - while (y--) { - blksize = (blksize << 8) | (unsigned long)in[x++]; - } - } - - /* would this blksize overflow? */ - if (x + blksize > inlen) { - return CRYPT_INVALID_PACKET; - } - - /* mark all as unused */ - for (i = 0; i < outlen; i++) { - list[i].used = 0; - } - - /* ok read data */ - inlen = blksize; - for (i = 0; i < outlen; i++) { - z = 0; - type = list[i].type; - size = list[i].size; - data = list[i].data; - if (!ordered && list[i].used == 1) { continue; } - - if (type == LTC_ASN1_EOL) { - break; - } - - switch (type) { - case LTC_ASN1_BOOLEAN: - z = inlen; - if ((err = der_decode_boolean(in + x, z, ((int *)data))) != CRYPT_OK) { - goto LBL_ERR; - } - if ((err = der_length_boolean(&z)) != CRYPT_OK) { - goto LBL_ERR; - } - break; - - case LTC_ASN1_INTEGER: - z = inlen; - if ((err = der_decode_integer(in + x, z, data)) != CRYPT_OK) { - if (!ordered) { continue; } - goto LBL_ERR; - } - if ((err = der_length_integer(data, &z)) != CRYPT_OK) { - goto LBL_ERR; - } - break; - - case LTC_ASN1_SHORT_INTEGER: - z = inlen; - if ((err = der_decode_short_integer(in + x, z, data)) != CRYPT_OK) { - if (!ordered) { continue; } - goto LBL_ERR; - } - if ((err = der_length_short_integer(((unsigned long*)data)[0], &z)) != CRYPT_OK) { - goto LBL_ERR; - } - - break; - - case LTC_ASN1_BIT_STRING: - z = inlen; - if ((err = der_decode_bit_string(in + x, z, data, &size)) != CRYPT_OK) { - if (!ordered) { continue; } - goto LBL_ERR; - } - list[i].size = size; - if ((err = der_length_bit_string(size, &z)) != CRYPT_OK) { - goto LBL_ERR; - } - break; - - case LTC_ASN1_OCTET_STRING: - z = inlen; - if ((err = der_decode_octet_string(in + x, z, data, &size)) != CRYPT_OK) { - if (!ordered) { continue; } - goto LBL_ERR; - } - list[i].size = size; - if ((err = der_length_octet_string(size, &z)) != CRYPT_OK) { - goto LBL_ERR; - } - break; - - case LTC_ASN1_NULL: - if (inlen < 2 || in[x] != 0x05 || in[x+1] != 0x00) { - if (!ordered) { continue; } - err = CRYPT_INVALID_PACKET; - goto LBL_ERR; - } - z = 2; - break; - - case LTC_ASN1_OBJECT_IDENTIFIER: - z = inlen; - if ((err = der_decode_object_identifier(in + x, z, data, &size)) != CRYPT_OK) { - if (!ordered) { continue; } - goto LBL_ERR; - } - list[i].size = size; - if ((err = der_length_object_identifier(data, size, &z)) != CRYPT_OK) { - goto LBL_ERR; - } - break; - - case LTC_ASN1_IA5_STRING: - z = inlen; - if ((err = der_decode_ia5_string(in + x, z, data, &size)) != CRYPT_OK) { - if (!ordered) { continue; } - goto LBL_ERR; - } - list[i].size = size; - if ((err = der_length_ia5_string(data, size, &z)) != CRYPT_OK) { - goto LBL_ERR; - } - break; - - - case LTC_ASN1_PRINTABLE_STRING: - z = inlen; - if ((err = der_decode_printable_string(in + x, z, data, &size)) != CRYPT_OK) { - if (!ordered) { continue; } - goto LBL_ERR; - } - list[i].size = size; - if ((err = der_length_printable_string(data, size, &z)) != CRYPT_OK) { - goto LBL_ERR; - } - break; - - case LTC_ASN1_UTF8_STRING: - z = inlen; - if ((err = der_decode_utf8_string(in + x, z, data, &size)) != CRYPT_OK) { - if (!ordered) { continue; } - goto LBL_ERR; - } - list[i].size = size; - if ((err = der_length_utf8_string(data, size, &z)) != CRYPT_OK) { - goto LBL_ERR; - } - break; - - case LTC_ASN1_UTCTIME: - z = inlen; - if ((err = der_decode_utctime(in + x, &z, data)) != CRYPT_OK) { - if (!ordered) { continue; } - goto LBL_ERR; - } - break; - - case LTC_ASN1_SET: - z = inlen; - if ((err = der_decode_set(in + x, z, data, size)) != CRYPT_OK) { - if (!ordered) { continue; } - goto LBL_ERR; - } - if ((err = der_length_sequence(data, size, &z)) != CRYPT_OK) { - goto LBL_ERR; - } - break; - - case LTC_ASN1_SETOF: - case LTC_ASN1_SEQUENCE: - /* detect if we have the right type */ - if ((type == LTC_ASN1_SETOF && (in[x] & 0x3F) != 0x31) || (type == LTC_ASN1_SEQUENCE && (in[x] & 0x3F) != 0x30)) { - err = CRYPT_INVALID_PACKET; - goto LBL_ERR; - } - - z = inlen; - if ((err = der_decode_sequence(in + x, z, data, size)) != CRYPT_OK) { - if (!ordered) { continue; } - goto LBL_ERR; - } - if ((err = der_length_sequence(data, size, &z)) != CRYPT_OK) { - goto LBL_ERR; - } - break; - - - case LTC_ASN1_CHOICE: - z = inlen; - if ((err = der_decode_choice(in + x, &z, data, size)) != CRYPT_OK) { - if (!ordered) { continue; } - goto LBL_ERR; - } - break; - - default: - err = CRYPT_INVALID_ARG; - goto LBL_ERR; - } - x += z; - inlen -= z; - list[i].used = 1; - if (!ordered) { - /* restart the decoder */ - i = -1; - } - } - - for (i = 0; i < outlen; i++) { - if (list[i].used == 0) { - err = CRYPT_INVALID_PACKET; - goto LBL_ERR; - } - } - err = CRYPT_OK; - -LBL_ERR: - return err; -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/sequence/der_decode_sequence_ex.c,v $ */ -/* $Revision: 1.16 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_sequence_flexi.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_sequence_flexi.c deleted file mode 100644 index 9c648bc..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_sequence_flexi.c +++ /dev/null @@ -1,386 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_decode_sequence_flexi.c - ASN.1 DER, decode an array of ASN.1 types with a flexi parser, Tom St Denis -*/ - -#ifdef LTC_DER - -static unsigned long fetch_length(const unsigned char *in, unsigned long inlen) -{ - unsigned long x, y, z; - - y = 0; - - /* skip type and read len */ - if (inlen < 2) { - return 0xFFFFFFFF; - } - ++in; ++y; - - /* read len */ - x = *in++; ++y; - - /* <128 means literal */ - if (x < 128) { - return x+y; - } - x &= 0x7F; /* the lower 7 bits are the length of the length */ - inlen -= 2; - - /* len means len of len! */ - if (x == 0 || x > 4 || x > inlen) { - return 0xFFFFFFFF; - } - - y += x; - z = 0; - while (x--) { - z = (z<<8) | ((unsigned long)*in); - ++in; - } - return z+y; -} - -/** - ASN.1 DER Flexi(ble) decoder will decode arbitrary DER packets and create a linked list of the decoded elements. - @param in The input buffer - @param inlen [in/out] The length of the input buffer and on output the amount of decoded data - @param out [out] A pointer to the linked list - @return CRYPT_OK on success. -*/ -int der_decode_sequence_flexi(const unsigned char *in, unsigned long *inlen, ltc_asn1_list **out) -{ - ltc_asn1_list *l; - unsigned long err, type, len, totlen, x, y; - void *realloc_tmp; - - LTC_ARGCHK(in != NULL); - LTC_ARGCHK(inlen != NULL); - LTC_ARGCHK(out != NULL); - - l = NULL; - totlen = 0; - - /* scan the input and and get lengths and what not */ - while (*inlen) { - /* read the type byte */ - type = *in; - - /* fetch length */ - len = fetch_length(in, *inlen); - if (len > *inlen) { - err = CRYPT_INVALID_PACKET; - goto error; - } - - /* alloc new link */ - if (l == NULL) { - l = XCALLOC(1, sizeof(*l)); - if (l == NULL) { - err = CRYPT_MEM; - goto error; - } - } else { - l->next = XCALLOC(1, sizeof(*l)); - if (l->next == NULL) { - err = CRYPT_MEM; - goto error; - } - l->next->prev = l; - l = l->next; - } - - /* now switch on type */ - switch (type) { - case 0x01: /* BOOLEAN */ - l->type = LTC_ASN1_BOOLEAN; - l->size = 1; - l->data = XCALLOC(1, sizeof(int)); - - if ((err = der_decode_boolean(in, *inlen, l->data)) != CRYPT_OK) { - goto error; - } - - if ((err = der_length_boolean(&len)) != CRYPT_OK) { - goto error; - } - break; - - case 0x02: /* INTEGER */ - /* init field */ - l->type = LTC_ASN1_INTEGER; - l->size = 1; - if ((err = mp_init(&l->data)) != CRYPT_OK) { - goto error; - } - - /* decode field */ - if ((err = der_decode_integer(in, *inlen, l->data)) != CRYPT_OK) { - goto error; - } - - /* calc length of object */ - if ((err = der_length_integer(l->data, &len)) != CRYPT_OK) { - goto error; - } - break; - - case 0x03: /* BIT */ - /* init field */ - l->type = LTC_ASN1_BIT_STRING; - l->size = len * 8; /* *8 because we store decoded bits one per char and they are encoded 8 per char. */ - - if ((l->data = XCALLOC(1, l->size)) == NULL) { - err = CRYPT_MEM; - goto error; - } - - if ((err = der_decode_bit_string(in, *inlen, l->data, &l->size)) != CRYPT_OK) { - goto error; - } - - if ((err = der_length_bit_string(l->size, &len)) != CRYPT_OK) { - goto error; - } - break; - - case 0x04: /* OCTET */ - - /* init field */ - l->type = LTC_ASN1_OCTET_STRING; - l->size = len; - - if ((l->data = XCALLOC(1, l->size)) == NULL) { - err = CRYPT_MEM; - goto error; - } - - if ((err = der_decode_octet_string(in, *inlen, l->data, &l->size)) != CRYPT_OK) { - goto error; - } - - if ((err = der_length_octet_string(l->size, &len)) != CRYPT_OK) { - goto error; - } - break; - - case 0x05: /* NULL */ - - /* valid NULL is 0x05 0x00 */ - if (in[0] != 0x05 || in[1] != 0x00) { - err = CRYPT_INVALID_PACKET; - goto error; - } - - /* simple to store ;-) */ - l->type = LTC_ASN1_NULL; - l->data = NULL; - l->size = 0; - len = 2; - - break; - - case 0x06: /* OID */ - - /* init field */ - l->type = LTC_ASN1_OBJECT_IDENTIFIER; - l->size = len; - - if ((l->data = XCALLOC(len, sizeof(unsigned long))) == NULL) { - err = CRYPT_MEM; - goto error; - } - - if ((err = der_decode_object_identifier(in, *inlen, l->data, &l->size)) != CRYPT_OK) { - goto error; - } - - if ((err = der_length_object_identifier(l->data, l->size, &len)) != CRYPT_OK) { - goto error; - } - - /* resize it to save a bunch of mem */ - if ((realloc_tmp = XREALLOC(l->data, l->size * sizeof(unsigned long))) == NULL) { - /* out of heap but this is not an error */ - break; - } - l->data = realloc_tmp; - break; - - case 0x0C: /* UTF8 */ - - /* init field */ - l->type = LTC_ASN1_UTF8_STRING; - l->size = len; - - if ((l->data = XCALLOC(sizeof(wchar_t), l->size)) == NULL) { - err = CRYPT_MEM; - goto error; - } - - if ((err = der_decode_utf8_string(in, *inlen, l->data, &l->size)) != CRYPT_OK) { - goto error; - } - - if ((err = der_length_utf8_string(l->data, l->size, &len)) != CRYPT_OK) { - goto error; - } - break; - - case 0x13: /* PRINTABLE */ - - /* init field */ - l->type = LTC_ASN1_PRINTABLE_STRING; - l->size = len; - - if ((l->data = XCALLOC(1, l->size)) == NULL) { - err = CRYPT_MEM; - goto error; - } - - if ((err = der_decode_printable_string(in, *inlen, l->data, &l->size)) != CRYPT_OK) { - goto error; - } - - if ((err = der_length_printable_string(l->data, l->size, &len)) != CRYPT_OK) { - goto error; - } - break; - - case 0x16: /* IA5 */ - - /* init field */ - l->type = LTC_ASN1_IA5_STRING; - l->size = len; - - if ((l->data = XCALLOC(1, l->size)) == NULL) { - err = CRYPT_MEM; - goto error; - } - - if ((err = der_decode_ia5_string(in, *inlen, l->data, &l->size)) != CRYPT_OK) { - goto error; - } - - if ((err = der_length_ia5_string(l->data, l->size, &len)) != CRYPT_OK) { - goto error; - } - break; - - case 0x17: /* UTC TIME */ - - /* init field */ - l->type = LTC_ASN1_UTCTIME; - l->size = 1; - - if ((l->data = XCALLOC(1, sizeof(ltc_utctime))) == NULL) { - err = CRYPT_MEM; - goto error; - } - - len = *inlen; - if ((err = der_decode_utctime(in, &len, l->data)) != CRYPT_OK) { - goto error; - } - - if ((err = der_length_utctime(l->data, &len)) != CRYPT_OK) { - goto error; - } - break; - - case 0x30: /* SEQUENCE */ - case 0x31: /* SET */ - - /* init field */ - l->type = (type == 0x30) ? LTC_ASN1_SEQUENCE : LTC_ASN1_SET; - - /* we have to decode the SEQUENCE header and get it's length */ - - /* move past type */ - ++in; --(*inlen); - - /* read length byte */ - x = *in++; --(*inlen); - - /* smallest SEQUENCE/SET header */ - y = 2; - - /* now if it's > 127 the next bytes are the length of the length */ - if (x > 128) { - x &= 0x7F; - in += x; - *inlen -= x; - - /* update sequence header len */ - y += x; - } - - /* Sequence elements go as child */ - len = len - y; - if ((err = der_decode_sequence_flexi(in, &len, &(l->child))) != CRYPT_OK) { - goto error; - } - - /* len update */ - totlen += y; - - /* link them up y0 */ - l->child->parent = l; - - break; - default: - /* invalid byte ... this is a soft error */ - /* remove link */ - l = l->prev; - XFREE(l->next); - l->next = NULL; - goto outside; - } - - /* advance pointers */ - totlen += len; - in += len; - *inlen -= len; - } - -outside: - - /* rewind l please */ - while (l->prev != NULL || l->parent != NULL) { - if (l->parent != NULL) { - l = l->parent; - } else { - l = l->prev; - } - } - - /* return */ - *out = l; - *inlen = totlen; - return CRYPT_OK; - -error: - /* free list */ - der_sequence_free(l); - - return err; -} - -#endif - - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/sequence/der_decode_sequence_flexi.c,v $ */ -/* $Revision: 1.26 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_sequence_multi.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_sequence_multi.c deleted file mode 100644 index ff633df..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_sequence_multi.c +++ /dev/null @@ -1,139 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" -#include - - -/** - @file der_decode_sequence_multi.c - ASN.1 DER, decode a SEQUENCE, Tom St Denis -*/ - -#ifdef LTC_DER - -/** - Decode a SEQUENCE type using a VA list - @param in Input buffer - @param inlen Length of input in octets - @remark <...> is of the form (int, unsigned long, void*) - @return CRYPT_OK on success -*/ -int der_decode_sequence_multi(const unsigned char *in, unsigned long inlen, ...) -{ - int err, type; - unsigned long size, x; - void *data; - va_list args; - ltc_asn1_list *list; - - LTC_ARGCHK(in != NULL); - - /* get size of output that will be required */ - va_start(args, inlen); - x = 0; - for (;;) { - type = va_arg(args, int); - size = va_arg(args, unsigned long); - data = va_arg(args, void*); - - if (type == LTC_ASN1_EOL) { - break; - } - - switch (type) { - case LTC_ASN1_BOOLEAN: - case LTC_ASN1_INTEGER: - case LTC_ASN1_SHORT_INTEGER: - case LTC_ASN1_BIT_STRING: - case LTC_ASN1_OCTET_STRING: - case LTC_ASN1_NULL: - case LTC_ASN1_OBJECT_IDENTIFIER: - case LTC_ASN1_IA5_STRING: - case LTC_ASN1_PRINTABLE_STRING: - case LTC_ASN1_UTF8_STRING: - case LTC_ASN1_UTCTIME: - case LTC_ASN1_SET: - case LTC_ASN1_SETOF: - case LTC_ASN1_SEQUENCE: - case LTC_ASN1_CHOICE: - ++x; - break; - - default: - va_end(args); - return CRYPT_INVALID_ARG; - } - } - va_end(args); - - /* allocate structure for x elements */ - if (x == 0) { - return CRYPT_NOP; - } - - list = XCALLOC(sizeof(*list), x); - if (list == NULL) { - return CRYPT_MEM; - } - - /* fill in the structure */ - va_start(args, inlen); - x = 0; - for (;;) { - type = va_arg(args, int); - size = va_arg(args, unsigned long); - data = va_arg(args, void*); - - if (type == LTC_ASN1_EOL) { - break; - } - - switch (type) { - case LTC_ASN1_BOOLEAN: - case LTC_ASN1_INTEGER: - case LTC_ASN1_SHORT_INTEGER: - case LTC_ASN1_BIT_STRING: - case LTC_ASN1_OCTET_STRING: - case LTC_ASN1_NULL: - case LTC_ASN1_OBJECT_IDENTIFIER: - case LTC_ASN1_IA5_STRING: - case LTC_ASN1_PRINTABLE_STRING: - case LTC_ASN1_UTF8_STRING: - case LTC_ASN1_UTCTIME: - case LTC_ASN1_SEQUENCE: - case LTC_ASN1_SET: - case LTC_ASN1_SETOF: - case LTC_ASN1_CHOICE: - list[x].type = type; - list[x].size = size; - list[x++].data = data; - break; - - default: - va_end(args); - err = CRYPT_INVALID_ARG; - goto LBL_ERR; - } - } - va_end(args); - - err = der_decode_sequence(in, inlen, list, x); -LBL_ERR: - XFREE(list); - return err; -} - -#endif - - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/sequence/der_decode_sequence_multi.c,v $ */ -/* $Revision: 1.13 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_short_integer.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_short_integer.c deleted file mode 100644 index 907e4e1..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_short_integer.c +++ /dev/null @@ -1,68 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_decode_short_integer.c - ASN.1 DER, decode an integer, Tom St Denis -*/ - - -#ifdef LTC_DER - -/** - Read a short integer - @param in The DER encoded data - @param inlen Size of data - @param num [out] The integer to decode - @return CRYPT_OK if successful -*/ -int der_decode_short_integer(const unsigned char *in, unsigned long inlen, unsigned long *num) -{ - unsigned long len, x, y; - - LTC_ARGCHK(num != NULL); - LTC_ARGCHK(in != NULL); - - /* check length */ - if (inlen < 2) { - return CRYPT_INVALID_PACKET; - } - - /* check header */ - x = 0; - if ((in[x++] & 0x1F) != 0x02) { - return CRYPT_INVALID_PACKET; - } - - /* get the packet len */ - len = in[x++]; - - if (x + len > inlen) { - return CRYPT_INVALID_PACKET; - } - - /* read number */ - y = 0; - while (len--) { - y = (y<<8) | (unsigned long)in[x++]; - } - *num = y; - - return CRYPT_OK; - -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/short_integer/der_decode_short_integer.c,v $ */ -/* $Revision: 1.7 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_utctime.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_utctime.c deleted file mode 100644 index 7f3f0d7..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_utctime.c +++ /dev/null @@ -1,127 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_decode_utctime.c - ASN.1 DER, decode a UTCTIME, Tom St Denis -*/ - -#ifdef LTC_DER - -static int char_to_int(unsigned char x) -{ - switch (x) { - case '0': return 0; - case '1': return 1; - case '2': return 2; - case '3': return 3; - case '4': return 4; - case '5': return 5; - case '6': return 6; - case '7': return 7; - case '8': return 8; - case '9': return 9; - } - return 100; -} - -#define DECODE_V(y, max) \ - y = char_to_int(buf[x])*10 + char_to_int(buf[x+1]); \ - if (y >= max) return CRYPT_INVALID_PACKET; \ - x += 2; - -/** - Decodes a UTC time structure in DER format (reads all 6 valid encoding formats) - @param in Input buffer - @param inlen Length of input buffer in octets - @param out [out] Destination of UTC time structure - @return CRYPT_OK if successful -*/ -int der_decode_utctime(const unsigned char *in, unsigned long *inlen, - ltc_utctime *out) -{ - unsigned char buf[32]; - unsigned long x; - int y; - - LTC_ARGCHK(in != NULL); - LTC_ARGCHK(inlen != NULL); - LTC_ARGCHK(out != NULL); - - /* check header */ - if (*inlen < 2UL || (in[1] >= sizeof(buf)) || ((in[1] + 2UL) > *inlen)) { - return CRYPT_INVALID_PACKET; - } - - /* decode the string */ - for (x = 0; x < in[1]; x++) { - y = der_ia5_value_decode(in[x+2]); - if (y == -1) { - return CRYPT_INVALID_PACKET; - } - buf[x] = y; - } - *inlen = 2 + x; - - - /* possible encodings are -YYMMDDhhmmZ -YYMMDDhhmm+hh'mm' -YYMMDDhhmm-hh'mm' -YYMMDDhhmmssZ -YYMMDDhhmmss+hh'mm' -YYMMDDhhmmss-hh'mm' - - So let's do a trivial decode upto [including] mm - */ - - x = 0; - DECODE_V(out->YY, 100); - DECODE_V(out->MM, 13); - DECODE_V(out->DD, 32); - DECODE_V(out->hh, 24); - DECODE_V(out->mm, 60); - - /* clear timezone and seconds info */ - out->off_dir = out->off_hh = out->off_mm = out->ss = 0; - - /* now is it Z, +, - or 0-9 */ - if (buf[x] == 'Z') { - return CRYPT_OK; - } else if (buf[x] == '+' || buf[x] == '-') { - out->off_dir = (buf[x++] == '+') ? 0 : 1; - DECODE_V(out->off_hh, 24); - DECODE_V(out->off_mm, 60); - return CRYPT_OK; - } - - /* decode seconds */ - DECODE_V(out->ss, 60); - - /* now is it Z, +, - */ - if (buf[x] == 'Z') { - return CRYPT_OK; - } else if (buf[x] == '+' || buf[x] == '-') { - out->off_dir = (buf[x++] == '+') ? 0 : 1; - DECODE_V(out->off_hh, 24); - DECODE_V(out->off_mm, 60); - return CRYPT_OK; - } else { - return CRYPT_INVALID_PACKET; - } -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/utctime/der_decode_utctime.c,v $ */ -/* $Revision: 1.9 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_utf8_string.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_utf8_string.c deleted file mode 100644 index 898d6cd..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_decode_utf8_string.c +++ /dev/null @@ -1,111 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_decode_utf8_string.c - ASN.1 DER, encode a UTF8 STRING, Tom St Denis -*/ - - -#ifdef LTC_DER - -/** - Store a UTF8 STRING - @param in The DER encoded UTF8 STRING - @param inlen The size of the DER UTF8 STRING - @param out [out] The array of utf8s stored (one per char) - @param outlen [in/out] The number of utf8s stored - @return CRYPT_OK if successful -*/ -int der_decode_utf8_string(const unsigned char *in, unsigned long inlen, - wchar_t *out, unsigned long *outlen) -{ - wchar_t tmp; - unsigned long x, y, z, len; - - LTC_ARGCHK(in != NULL); - LTC_ARGCHK(out != NULL); - LTC_ARGCHK(outlen != NULL); - - /* must have header at least */ - if (inlen < 2) { - return CRYPT_INVALID_PACKET; - } - - /* check for 0x0C */ - if ((in[0] & 0x1F) != 0x0C) { - return CRYPT_INVALID_PACKET; - } - x = 1; - - /* decode the length */ - if (in[x] & 0x80) { - /* valid # of bytes in length are 1,2,3 */ - y = in[x] & 0x7F; - if ((y == 0) || (y > 3) || ((x + y) > inlen)) { - return CRYPT_INVALID_PACKET; - } - - /* read the length in */ - len = 0; - ++x; - while (y--) { - len = (len << 8) | in[x++]; - } - } else { - len = in[x++] & 0x7F; - } - - if (len + x > inlen) { - return CRYPT_INVALID_PACKET; - } - - /* proceed to decode */ - for (y = 0; x < inlen; ) { - /* get first byte */ - tmp = in[x++]; - - /* count number of bytes */ - for (z = 0; (tmp & 0x80) && (z <= 4); z++, tmp = (tmp << 1) & 0xFF); - - if (z > 4 || (x + (z - 1) > inlen)) { - return CRYPT_INVALID_PACKET; - } - - /* decode, grab upper bits */ - tmp >>= z; - - /* grab remaining bytes */ - if (z > 1) { --z; } - while (z-- != 0) { - if ((in[x] & 0xC0) != 0x80) { - return CRYPT_INVALID_PACKET; - } - tmp = (tmp << 6) | ((wchar_t)in[x++] & 0x3F); - } - - if (y > *outlen) { - *outlen = y; - return CRYPT_BUFFER_OVERFLOW; - } - out[y++] = tmp; - } - *outlen = y; - - return CRYPT_OK; -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/utf8/der_decode_utf8_string.c,v $ */ -/* $Revision: 1.8 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_bit_string.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_bit_string.c deleted file mode 100644 index ca29c58..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_bit_string.c +++ /dev/null @@ -1,89 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_encode_bit_string.c - ASN.1 DER, encode a BIT STRING, Tom St Denis -*/ - - -#ifdef LTC_DER - -/** - Store a BIT STRING - @param in The array of bits to store (one per char) - @param inlen The number of bits tostore - @param out [out] The destination for the DER encoded BIT STRING - @param outlen [in/out] The max size and resulting size of the DER BIT STRING - @return CRYPT_OK if successful -*/ -int der_encode_bit_string(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen) -{ - unsigned long len, x, y; - unsigned char buf; - int err; - - LTC_ARGCHK(in != NULL); - LTC_ARGCHK(out != NULL); - LTC_ARGCHK(outlen != NULL); - - /* avoid overflows */ - if ((err = der_length_bit_string(inlen, &len)) != CRYPT_OK) { - return err; - } - - if (len > *outlen) { - *outlen = len; - return CRYPT_BUFFER_OVERFLOW; - } - - /* store header (include bit padding count in length) */ - x = 0; - y = (inlen >> 3) + ((inlen&7) ? 1 : 0) + 1; - - out[x++] = 0x03; - if (y < 128) { - out[x++] = (unsigned char)y; - } else if (y < 256) { - out[x++] = 0x81; - out[x++] = (unsigned char)y; - } else if (y < 65536) { - out[x++] = 0x82; - out[x++] = (unsigned char)((y>>8)&255); - out[x++] = (unsigned char)(y&255); - } - - /* store number of zero padding bits */ - out[x++] = (unsigned char)((8 - inlen) & 7); - - /* store the bits in big endian format */ - for (y = buf = 0; y < inlen; y++) { - buf |= (in[y] ? 1 : 0) << (7 - (y & 7)); - if ((y & 7) == 7) { - out[x++] = buf; - buf = 0; - } - } - /* store last byte */ - if (inlen & 7) { - out[x++] = buf; - } - *outlen = x; - return CRYPT_OK; -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/bit/der_encode_bit_string.c,v $ */ -/* $Revision: 1.5 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_boolean.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_boolean.c deleted file mode 100644 index ded2731..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_boolean.c +++ /dev/null @@ -1,51 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_encode_boolean.c - ASN.1 DER, encode a BOOLEAN, Tom St Denis -*/ - - -#ifdef LTC_DER - -/** - Store a BOOLEAN - @param in The boolean to encode - @param out [out] The destination for the DER encoded BOOLEAN - @param outlen [in/out] The max size and resulting size of the DER BOOLEAN - @return CRYPT_OK if successful -*/ -int der_encode_boolean(int in, - unsigned char *out, unsigned long *outlen) -{ - LTC_ARGCHK(outlen != NULL); - LTC_ARGCHK(out != NULL); - - if (*outlen < 3) { - *outlen = 3; - return CRYPT_BUFFER_OVERFLOW; - } - - *outlen = 3; - out[0] = 0x01; - out[1] = 0x01; - out[2] = in ? 0xFF : 0x00; - - return CRYPT_OK; -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/boolean/der_encode_boolean.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_ia5_string.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_ia5_string.c deleted file mode 100644 index 30d3f43..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_ia5_string.c +++ /dev/null @@ -1,85 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_encode_ia5_string.c - ASN.1 DER, encode a IA5 STRING, Tom St Denis -*/ - -#ifdef LTC_DER - -/** - Store an IA5 STRING - @param in The array of IA5 to store (one per char) - @param inlen The number of IA5 to store - @param out [out] The destination for the DER encoded IA5 STRING - @param outlen [in/out] The max size and resulting size of the DER IA5 STRING - @return CRYPT_OK if successful -*/ -int der_encode_ia5_string(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen) -{ - unsigned long x, y, len; - int err; - - LTC_ARGCHK(in != NULL); - LTC_ARGCHK(out != NULL); - LTC_ARGCHK(outlen != NULL); - - /* get the size */ - if ((err = der_length_ia5_string(in, inlen, &len)) != CRYPT_OK) { - return err; - } - - /* too big? */ - if (len > *outlen) { - *outlen = len; - return CRYPT_BUFFER_OVERFLOW; - } - - /* encode the header+len */ - x = 0; - out[x++] = 0x16; - if (inlen < 128) { - out[x++] = (unsigned char)inlen; - } else if (inlen < 256) { - out[x++] = 0x81; - out[x++] = (unsigned char)inlen; - } else if (inlen < 65536UL) { - out[x++] = 0x82; - out[x++] = (unsigned char)((inlen>>8)&255); - out[x++] = (unsigned char)(inlen&255); - } else if (inlen < 16777216UL) { - out[x++] = 0x83; - out[x++] = (unsigned char)((inlen>>16)&255); - out[x++] = (unsigned char)((inlen>>8)&255); - out[x++] = (unsigned char)(inlen&255); - } else { - return CRYPT_INVALID_ARG; - } - - /* store octets */ - for (y = 0; y < inlen; y++) { - out[x++] = der_ia5_char_encode(in[y]); - } - - /* retun length */ - *outlen = x; - - return CRYPT_OK; -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/ia5/der_encode_ia5_string.c,v $ */ -/* $Revision: 1.5 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_integer.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_integer.c deleted file mode 100644 index 4137a94..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_integer.c +++ /dev/null @@ -1,130 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_encode_integer.c - ASN.1 DER, encode an integer, Tom St Denis -*/ - - -#ifdef LTC_DER - -/* Exports a positive bignum as DER format (upto 2^32 bytes in size) */ -/** - Store a mp_int integer - @param num The first mp_int to encode - @param out [out] The destination for the DER encoded integers - @param outlen [in/out] The max size and resulting size of the DER encoded integers - @return CRYPT_OK if successful -*/ -int der_encode_integer(void *num, unsigned char *out, unsigned long *outlen) -{ - unsigned long tmplen, y; - int err, leading_zero; - - LTC_ARGCHK(num != NULL); - LTC_ARGCHK(out != NULL); - LTC_ARGCHK(outlen != NULL); - - /* find out how big this will be */ - if ((err = der_length_integer(num, &tmplen)) != CRYPT_OK) { - return err; - } - - if (*outlen < tmplen) { - *outlen = tmplen; - return CRYPT_BUFFER_OVERFLOW; - } - - if (mp_cmp_d(num, 0) != LTC_MP_LT) { - /* we only need a leading zero if the msb of the first byte is one */ - if ((mp_count_bits(num) & 7) == 0 || mp_iszero(num) == LTC_MP_YES) { - leading_zero = 1; - } else { - leading_zero = 0; - } - - /* get length of num in bytes (plus 1 since we force the msbyte to zero) */ - y = mp_unsigned_bin_size(num) + leading_zero; - } else { - leading_zero = 0; - y = mp_count_bits(num); - y = y + (8 - (y & 7)); - y = y >> 3; - if (((mp_cnt_lsb(num)+1)==mp_count_bits(num)) && ((mp_count_bits(num)&7)==0)) --y; - } - - /* now store initial data */ - *out++ = 0x02; - if (y < 128) { - /* short form */ - *out++ = (unsigned char)y; - } else if (y < 256) { - *out++ = 0x81; - *out++ = (unsigned char)y; - } else if (y < 65536UL) { - *out++ = 0x82; - *out++ = (unsigned char)((y>>8)&255); - *out++ = (unsigned char)y; - } else if (y < 16777216UL) { - *out++ = 0x83; - *out++ = (unsigned char)((y>>16)&255); - *out++ = (unsigned char)((y>>8)&255); - *out++ = (unsigned char)y; - } else { - return CRYPT_INVALID_ARG; - } - - /* now store msbyte of zero if num is non-zero */ - if (leading_zero) { - *out++ = 0x00; - } - - /* if it's not zero store it as big endian */ - if (mp_cmp_d(num, 0) == LTC_MP_GT) { - /* now store the mpint */ - if ((err = mp_to_unsigned_bin(num, out)) != CRYPT_OK) { - return err; - } - } else if (mp_iszero(num) != LTC_MP_YES) { - void *tmp; - - /* negative */ - if (mp_init(&tmp) != CRYPT_OK) { - return CRYPT_MEM; - } - - /* 2^roundup and subtract */ - y = mp_count_bits(num); - y = y + (8 - (y & 7)); - if (((mp_cnt_lsb(num)+1)==mp_count_bits(num)) && ((mp_count_bits(num)&7)==0)) y -= 8; - if (mp_2expt(tmp, y) != CRYPT_OK || mp_add(tmp, num, tmp) != CRYPT_OK) { - mp_clear(tmp); - return CRYPT_MEM; - } - if ((err = mp_to_unsigned_bin(tmp, out)) != CRYPT_OK) { - mp_clear(tmp); - return err; - } - mp_clear(tmp); - } - - /* we good */ - *outlen = tmplen; - return CRYPT_OK; -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/integer/der_encode_integer.c,v $ */ -/* $Revision: 1.9 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_object_identifier.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_object_identifier.c deleted file mode 100644 index 68e2162..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_object_identifier.c +++ /dev/null @@ -1,111 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_encode_object_identifier.c - ASN.1 DER, Encode Object Identifier, Tom St Denis -*/ - -#ifdef LTC_DER -/** - Encode an OID - @param words The words to encode (upto 32-bits each) - @param nwords The number of words in the OID - @param out [out] Destination of OID data - @param outlen [in/out] The max and resulting size of the OID - @return CRYPT_OK if successful -*/ -int der_encode_object_identifier(unsigned long *words, unsigned long nwords, - unsigned char *out, unsigned long *outlen) -{ - unsigned long i, x, y, z, t, mask, wordbuf; - int err; - - LTC_ARGCHK(words != NULL); - LTC_ARGCHK(out != NULL); - LTC_ARGCHK(outlen != NULL); - - /* check length */ - if ((err = der_length_object_identifier(words, nwords, &x)) != CRYPT_OK) { - return err; - } - if (x > *outlen) { - *outlen = x; - return CRYPT_BUFFER_OVERFLOW; - } - - /* compute length to store OID data */ - z = 0; - wordbuf = words[0] * 40 + words[1]; - for (y = 1; y < nwords; y++) { - t = der_object_identifier_bits(wordbuf); - z += t/7 + ((t%7) ? 1 : 0) + (wordbuf == 0 ? 1 : 0); - if (y < nwords - 1) { - wordbuf = words[y + 1]; - } - } - - /* store header + length */ - x = 0; - out[x++] = 0x06; - if (z < 128) { - out[x++] = (unsigned char)z; - } else if (z < 256) { - out[x++] = 0x81; - out[x++] = (unsigned char)z; - } else if (z < 65536UL) { - out[x++] = 0x82; - out[x++] = (unsigned char)((z>>8)&255); - out[x++] = (unsigned char)(z&255); - } else { - return CRYPT_INVALID_ARG; - } - - /* store first byte */ - wordbuf = words[0] * 40 + words[1]; - for (i = 1; i < nwords; i++) { - /* store 7 bit words in little endian */ - t = wordbuf & 0xFFFFFFFF; - if (t) { - y = x; - mask = 0; - while (t) { - out[x++] = (unsigned char)((t & 0x7F) | mask); - t >>= 7; - mask |= 0x80; /* upper bit is set on all but the last byte */ - } - /* now swap bytes y...x-1 */ - z = x - 1; - while (y < z) { - t = out[y]; out[y] = out[z]; out[z] = (unsigned char)t; - ++y; - --z; - } - } else { - /* zero word */ - out[x++] = 0x00; - } - - if (i < nwords - 1) { - wordbuf = words[i + 1]; - } - } - - *outlen = x; - return CRYPT_OK; -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/object_identifier/der_encode_object_identifier.c,v $ */ -/* $Revision: 1.7 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_octet_string.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_octet_string.c deleted file mode 100644 index b3ee7f4..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_octet_string.c +++ /dev/null @@ -1,86 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_encode_octet_string.c - ASN.1 DER, encode a OCTET STRING, Tom St Denis -*/ - - -#ifdef LTC_DER - -/** - Store an OCTET STRING - @param in The array of OCTETS to store (one per char) - @param inlen The number of OCTETS to store - @param out [out] The destination for the DER encoded OCTET STRING - @param outlen [in/out] The max size and resulting size of the DER OCTET STRING - @return CRYPT_OK if successful -*/ -int der_encode_octet_string(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen) -{ - unsigned long x, y, len; - int err; - - LTC_ARGCHK(in != NULL); - LTC_ARGCHK(out != NULL); - LTC_ARGCHK(outlen != NULL); - - /* get the size */ - if ((err = der_length_octet_string(inlen, &len)) != CRYPT_OK) { - return err; - } - - /* too big? */ - if (len > *outlen) { - *outlen = len; - return CRYPT_BUFFER_OVERFLOW; - } - - /* encode the header+len */ - x = 0; - out[x++] = 0x04; - if (inlen < 128) { - out[x++] = (unsigned char)inlen; - } else if (inlen < 256) { - out[x++] = 0x81; - out[x++] = (unsigned char)inlen; - } else if (inlen < 65536UL) { - out[x++] = 0x82; - out[x++] = (unsigned char)((inlen>>8)&255); - out[x++] = (unsigned char)(inlen&255); - } else if (inlen < 16777216UL) { - out[x++] = 0x83; - out[x++] = (unsigned char)((inlen>>16)&255); - out[x++] = (unsigned char)((inlen>>8)&255); - out[x++] = (unsigned char)(inlen&255); - } else { - return CRYPT_INVALID_ARG; - } - - /* store octets */ - for (y = 0; y < inlen; y++) { - out[x++] = in[y]; - } - - /* retun length */ - *outlen = x; - - return CRYPT_OK; -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/octet/der_encode_octet_string.c,v $ */ -/* $Revision: 1.5 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_printable_string.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_printable_string.c deleted file mode 100644 index a1dab5f..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_printable_string.c +++ /dev/null @@ -1,85 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_encode_printable_string.c - ASN.1 DER, encode a printable STRING, Tom St Denis -*/ - -#ifdef LTC_DER - -/** - Store an printable STRING - @param in The array of printable to store (one per char) - @param inlen The number of printable to store - @param out [out] The destination for the DER encoded printable STRING - @param outlen [in/out] The max size and resulting size of the DER printable STRING - @return CRYPT_OK if successful -*/ -int der_encode_printable_string(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen) -{ - unsigned long x, y, len; - int err; - - LTC_ARGCHK(in != NULL); - LTC_ARGCHK(out != NULL); - LTC_ARGCHK(outlen != NULL); - - /* get the size */ - if ((err = der_length_printable_string(in, inlen, &len)) != CRYPT_OK) { - return err; - } - - /* too big? */ - if (len > *outlen) { - *outlen = len; - return CRYPT_BUFFER_OVERFLOW; - } - - /* encode the header+len */ - x = 0; - out[x++] = 0x13; - if (inlen < 128) { - out[x++] = (unsigned char)inlen; - } else if (inlen < 256) { - out[x++] = 0x81; - out[x++] = (unsigned char)inlen; - } else if (inlen < 65536UL) { - out[x++] = 0x82; - out[x++] = (unsigned char)((inlen>>8)&255); - out[x++] = (unsigned char)(inlen&255); - } else if (inlen < 16777216UL) { - out[x++] = 0x83; - out[x++] = (unsigned char)((inlen>>16)&255); - out[x++] = (unsigned char)((inlen>>8)&255); - out[x++] = (unsigned char)(inlen&255); - } else { - return CRYPT_INVALID_ARG; - } - - /* store octets */ - for (y = 0; y < inlen; y++) { - out[x++] = der_printable_char_encode(in[y]); - } - - /* retun length */ - *outlen = x; - - return CRYPT_OK; -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/printable_string/der_encode_printable_string.c,v $ */ -/* $Revision: 1.5 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_sequence_ex.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_sequence_ex.c deleted file mode 100644 index 3df19cf..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_sequence_ex.c +++ /dev/null @@ -1,335 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" -#include - - -/** - @file der_encode_sequence_ex.c - ASN.1 DER, encode a SEQUENCE, Tom St Denis -*/ - -#ifdef LTC_DER - -/** - Encode a SEQUENCE - @param list The list of items to encode - @param inlen The number of items in the list - @param out [out] The destination - @param outlen [in/out] The size of the output - @param type_of LTC_ASN1_SEQUENCE or LTC_ASN1_SET/LTC_ASN1_SETOF - @return CRYPT_OK on success -*/ -int der_encode_sequence_ex(ltc_asn1_list *list, unsigned long inlen, - unsigned char *out, unsigned long *outlen, int type_of) -{ - int err, type; - unsigned long size, x, y, z, i; - void *data; - - LTC_ARGCHK(list != NULL); - LTC_ARGCHK(out != NULL); - LTC_ARGCHK(outlen != NULL); - - /* get size of output that will be required */ - y = 0; - for (i = 0; i < inlen; i++) { - type = list[i].type; - size = list[i].size; - data = list[i].data; - - if (type == LTC_ASN1_EOL) { - break; - } - - switch (type) { - case LTC_ASN1_BOOLEAN: - if ((err = der_length_boolean(&x)) != CRYPT_OK) { - goto LBL_ERR; - } - y += x; - break; - - case LTC_ASN1_INTEGER: - if ((err = der_length_integer(data, &x)) != CRYPT_OK) { - goto LBL_ERR; - } - y += x; - break; - - case LTC_ASN1_SHORT_INTEGER: - if ((err = der_length_short_integer(*((unsigned long*)data), &x)) != CRYPT_OK) { - goto LBL_ERR; - } - y += x; - break; - - case LTC_ASN1_BIT_STRING: - if ((err = der_length_bit_string(size, &x)) != CRYPT_OK) { - goto LBL_ERR; - } - y += x; - break; - - case LTC_ASN1_OCTET_STRING: - if ((err = der_length_octet_string(size, &x)) != CRYPT_OK) { - goto LBL_ERR; - } - y += x; - break; - - case LTC_ASN1_NULL: - y += 2; - break; - - case LTC_ASN1_OBJECT_IDENTIFIER: - if ((err = der_length_object_identifier(data, size, &x)) != CRYPT_OK) { - goto LBL_ERR; - } - y += x; - break; - - case LTC_ASN1_IA5_STRING: - if ((err = der_length_ia5_string(data, size, &x)) != CRYPT_OK) { - goto LBL_ERR; - } - y += x; - break; - - case LTC_ASN1_PRINTABLE_STRING: - if ((err = der_length_printable_string(data, size, &x)) != CRYPT_OK) { - goto LBL_ERR; - } - y += x; - break; - - case LTC_ASN1_UTF8_STRING: - if ((err = der_length_utf8_string(data, size, &x)) != CRYPT_OK) { - goto LBL_ERR; - } - y += x; - break; - - case LTC_ASN1_UTCTIME: - if ((err = der_length_utctime(data, &x)) != CRYPT_OK) { - goto LBL_ERR; - } - y += x; - break; - - case LTC_ASN1_SET: - case LTC_ASN1_SETOF: - case LTC_ASN1_SEQUENCE: - if ((err = der_length_sequence(data, size, &x)) != CRYPT_OK) { - goto LBL_ERR; - } - y += x; - break; - - default: - err = CRYPT_INVALID_ARG; - goto LBL_ERR; - } - } - - /* calc header size */ - z = y; - if (y < 128) { - y += 2; - } else if (y < 256) { - /* 0x30 0x81 LL */ - y += 3; - } else if (y < 65536UL) { - /* 0x30 0x82 LL LL */ - y += 4; - } else if (y < 16777216UL) { - /* 0x30 0x83 LL LL LL */ - y += 5; - } else { - err = CRYPT_INVALID_ARG; - goto LBL_ERR; - } - - /* too big ? */ - if (*outlen < y) { - *outlen = y; - err = CRYPT_BUFFER_OVERFLOW; - goto LBL_ERR; - } - - /* store header */ - x = 0; - out[x++] = (type_of == LTC_ASN1_SEQUENCE) ? 0x30 : 0x31; - - if (z < 128) { - out[x++] = (unsigned char)z; - } else if (z < 256) { - out[x++] = 0x81; - out[x++] = (unsigned char)z; - } else if (z < 65536UL) { - out[x++] = 0x82; - out[x++] = (unsigned char)((z>>8UL)&255); - out[x++] = (unsigned char)(z&255); - } else if (z < 16777216UL) { - out[x++] = 0x83; - out[x++] = (unsigned char)((z>>16UL)&255); - out[x++] = (unsigned char)((z>>8UL)&255); - out[x++] = (unsigned char)(z&255); - } - - /* store data */ - *outlen -= x; - for (i = 0; i < inlen; i++) { - type = list[i].type; - size = list[i].size; - data = list[i].data; - - if (type == LTC_ASN1_EOL) { - break; - } - - switch (type) { - case LTC_ASN1_BOOLEAN: - z = *outlen; - if ((err = der_encode_boolean(*((int *)data), out + x, &z)) != CRYPT_OK) { - goto LBL_ERR; - } - x += z; - *outlen -= z; - break; - - case LTC_ASN1_INTEGER: - z = *outlen; - if ((err = der_encode_integer(data, out + x, &z)) != CRYPT_OK) { - goto LBL_ERR; - } - x += z; - *outlen -= z; - break; - - case LTC_ASN1_SHORT_INTEGER: - z = *outlen; - if ((err = der_encode_short_integer(*((unsigned long*)data), out + x, &z)) != CRYPT_OK) { - goto LBL_ERR; - } - x += z; - *outlen -= z; - break; - - case LTC_ASN1_BIT_STRING: - z = *outlen; - if ((err = der_encode_bit_string(data, size, out + x, &z)) != CRYPT_OK) { - goto LBL_ERR; - } - x += z; - *outlen -= z; - break; - - case LTC_ASN1_OCTET_STRING: - z = *outlen; - if ((err = der_encode_octet_string(data, size, out + x, &z)) != CRYPT_OK) { - goto LBL_ERR; - } - x += z; - *outlen -= z; - break; - - case LTC_ASN1_NULL: - out[x++] = 0x05; - out[x++] = 0x00; - *outlen -= 2; - break; - - case LTC_ASN1_OBJECT_IDENTIFIER: - z = *outlen; - if ((err = der_encode_object_identifier(data, size, out + x, &z)) != CRYPT_OK) { - goto LBL_ERR; - } - x += z; - *outlen -= z; - break; - - case LTC_ASN1_IA5_STRING: - z = *outlen; - if ((err = der_encode_ia5_string(data, size, out + x, &z)) != CRYPT_OK) { - goto LBL_ERR; - } - x += z; - *outlen -= z; - break; - - case LTC_ASN1_PRINTABLE_STRING: - z = *outlen; - if ((err = der_encode_printable_string(data, size, out + x, &z)) != CRYPT_OK) { - goto LBL_ERR; - } - x += z; - *outlen -= z; - break; - - case LTC_ASN1_UTF8_STRING: - z = *outlen; - if ((err = der_encode_utf8_string(data, size, out + x, &z)) != CRYPT_OK) { - goto LBL_ERR; - } - x += z; - *outlen -= z; - break; - - case LTC_ASN1_UTCTIME: - z = *outlen; - if ((err = der_encode_utctime(data, out + x, &z)) != CRYPT_OK) { - goto LBL_ERR; - } - x += z; - *outlen -= z; - break; - - case LTC_ASN1_SET: - z = *outlen; - if ((err = der_encode_set(data, size, out + x, &z)) != CRYPT_OK) { - goto LBL_ERR; - } - x += z; - *outlen -= z; - break; - - case LTC_ASN1_SETOF: - z = *outlen; - if ((err = der_encode_setof(data, size, out + x, &z)) != CRYPT_OK) { - goto LBL_ERR; - } - x += z; - *outlen -= z; - break; - - case LTC_ASN1_SEQUENCE: - z = *outlen; - if ((err = der_encode_sequence_ex(data, size, out + x, &z, type)) != CRYPT_OK) { - goto LBL_ERR; - } - x += z; - *outlen -= z; - break; - - default: - err = CRYPT_INVALID_ARG; - goto LBL_ERR; - } - } - *outlen = x; - err = CRYPT_OK; - -LBL_ERR: - return err; -} - -#endif diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_sequence_multi.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_sequence_multi.c deleted file mode 100644 index 782f042..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_sequence_multi.c +++ /dev/null @@ -1,138 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" -#include - - -/** - @file der_encode_sequence_multi.c - ASN.1 DER, encode a SEQUENCE, Tom St Denis -*/ - -#ifdef LTC_DER - -/** - Encode a SEQUENCE type using a VA list - @param out [out] Destination for data - @param outlen [in/out] Length of buffer and resulting length of output - @remark <...> is of the form (int, unsigned long, void*) - @return CRYPT_OK on success -*/ -int der_encode_sequence_multi(unsigned char *out, unsigned long *outlen, ...) -{ - int err, type; - unsigned long size, x; - void *data; - va_list args; - ltc_asn1_list *list; - - LTC_ARGCHK(out != NULL); - LTC_ARGCHK(outlen != NULL); - - /* get size of output that will be required */ - va_start(args, outlen); - x = 0; - for (;;) { - type = va_arg(args, int); - size = va_arg(args, unsigned long); - data = va_arg(args, void*); - - if (type == LTC_ASN1_EOL) { - break; - } - - switch (type) { - case LTC_ASN1_BOOLEAN: - case LTC_ASN1_INTEGER: - case LTC_ASN1_SHORT_INTEGER: - case LTC_ASN1_BIT_STRING: - case LTC_ASN1_OCTET_STRING: - case LTC_ASN1_NULL: - case LTC_ASN1_OBJECT_IDENTIFIER: - case LTC_ASN1_IA5_STRING: - case LTC_ASN1_PRINTABLE_STRING: - case LTC_ASN1_UTF8_STRING: - case LTC_ASN1_UTCTIME: - case LTC_ASN1_SEQUENCE: - case LTC_ASN1_SET: - case LTC_ASN1_SETOF: - ++x; - break; - - default: - va_end(args); - return CRYPT_INVALID_ARG; - } - } - va_end(args); - - /* allocate structure for x elements */ - if (x == 0) { - return CRYPT_NOP; - } - - list = XCALLOC(sizeof(*list), x); - if (list == NULL) { - return CRYPT_MEM; - } - - /* fill in the structure */ - va_start(args, outlen); - x = 0; - for (;;) { - type = va_arg(args, int); - size = va_arg(args, unsigned long); - data = va_arg(args, void*); - - if (type == LTC_ASN1_EOL) { - break; - } - - switch (type) { - case LTC_ASN1_BOOLEAN: - case LTC_ASN1_INTEGER: - case LTC_ASN1_SHORT_INTEGER: - case LTC_ASN1_BIT_STRING: - case LTC_ASN1_OCTET_STRING: - case LTC_ASN1_NULL: - case LTC_ASN1_OBJECT_IDENTIFIER: - case LTC_ASN1_IA5_STRING: - case LTC_ASN1_PRINTABLE_STRING: - case LTC_ASN1_UTF8_STRING: - case LTC_ASN1_UTCTIME: - case LTC_ASN1_SEQUENCE: - case LTC_ASN1_SET: - case LTC_ASN1_SETOF: - list[x].type = type; - list[x].size = size; - list[x++].data = data; - break; - - default: - va_end(args); - err = CRYPT_INVALID_ARG; - goto LBL_ERR; - } - } - va_end(args); - - err = der_encode_sequence(list, x, out, outlen); -LBL_ERR: - XFREE(list); - return err; -} - -#endif - - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/sequence/der_encode_sequence_multi.c,v $ */ -/* $Revision: 1.12 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_set.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_set.c deleted file mode 100644 index 25d247d..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_set.c +++ /dev/null @@ -1,103 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_encode_set.c - ASN.1 DER, Encode a SET, Tom St Denis -*/ - -#ifdef LTC_DER - -/* LTC define to ASN.1 TAG */ -static int ltc_to_asn1(int v) -{ - switch (v) { - case LTC_ASN1_BOOLEAN: return 0x01; - case LTC_ASN1_INTEGER: - case LTC_ASN1_SHORT_INTEGER: return 0x02; - case LTC_ASN1_BIT_STRING: return 0x03; - case LTC_ASN1_OCTET_STRING: return 0x04; - case LTC_ASN1_NULL: return 0x05; - case LTC_ASN1_OBJECT_IDENTIFIER: return 0x06; - case LTC_ASN1_UTF8_STRING: return 0x0C; - case LTC_ASN1_PRINTABLE_STRING: return 0x13; - case LTC_ASN1_IA5_STRING: return 0x16; - case LTC_ASN1_UTCTIME: return 0x17; - case LTC_ASN1_SEQUENCE: return 0x30; - case LTC_ASN1_SET: - case LTC_ASN1_SETOF: return 0x31; - default: return -1; - } -} - - -static int LTC_CALL qsort_helper1(const void *a, const void *b) -{ - ltc_asn1_list *A = (ltc_asn1_list *)a, *B = (ltc_asn1_list *)b; - int r; - - r = ltc_to_asn1(A->type) - ltc_to_asn1(B->type); - - /* for QSORT the order is UNDEFINED if they are "equal" which means it is NOT DETERMINISTIC. So we force it to be :-) */ - if (r == 0) { - /* their order in the original list now determines the position */ - return A->used - B->used; - } else { - return r; - } -} - -/* - Encode a SET type - @param list The list of items to encode - @param inlen The number of items in the list - @param out [out] The destination - @param outlen [in/out] The size of the output - @return CRYPT_OK on success -*/ -int der_encode_set(ltc_asn1_list *list, unsigned long inlen, - unsigned char *out, unsigned long *outlen) -{ - ltc_asn1_list *copy; - unsigned long x; - int err; - - /* make copy of list */ - copy = XCALLOC(inlen, sizeof(*copy)); - if (copy == NULL) { - return CRYPT_MEM; - } - - /* fill in used member with index so we can fully sort it */ - for (x = 0; x < inlen; x++) { - copy[x] = list[x]; - copy[x].used = x; - } - - /* sort it by the "type" field */ - XQSORT(copy, inlen, sizeof(*copy), &qsort_helper1); - - /* call der_encode_sequence_ex() */ - err = der_encode_sequence_ex(copy, inlen, out, outlen, LTC_ASN1_SET); - - /* free list */ - XFREE(copy); - - return err; -} - - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/set/der_encode_set.c,v $ */ -/* $Revision: 1.12 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_setof.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_setof.c deleted file mode 100644 index 0987cab..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_setof.c +++ /dev/null @@ -1,162 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_encode_setof.c - ASN.1 DER, Encode SET OF, Tom St Denis -*/ - -#ifdef LTC_DER - -struct edge { - unsigned char *start; - unsigned long size; -}; - -static int LTC_CALL qsort_helper2(const void *a, const void *b) -{ - struct edge *A = (struct edge *)a, *B = (struct edge *)b; - int r; - unsigned long x; - - /* compare min length */ - r = XMEMCMP(A->start, B->start, MIN(A->size, B->size)); - - if (r == 0 && A->size != B->size) { - if (A->size > B->size) { - for (x = B->size; x < A->size; x++) { - if (A->start[x]) { - return 1; - } - } - } else { - for (x = A->size; x < B->size; x++) { - if (B->start[x]) { - return -1; - } - } - } - } - - return r; -} - -/** - Encode a SETOF stucture - @param list The list of items to encode - @param inlen The number of items in the list - @param out [out] The destination - @param outlen [in/out] The size of the output - @return CRYPT_OK on success -*/ -int der_encode_setof(ltc_asn1_list *list, unsigned long inlen, - unsigned char *out, unsigned long *outlen) -{ - unsigned long x, y, z, hdrlen; - int err; - struct edge *edges; - unsigned char *ptr, *buf; - - /* check that they're all the same type */ - for (x = 1; x < inlen; x++) { - if (list[x].type != list[x-1].type) { - return CRYPT_INVALID_ARG; - } - } - - /* alloc buffer to store copy of output */ - buf = XCALLOC(1, *outlen); - if (buf == NULL) { - return CRYPT_MEM; - } - - /* encode list */ - if ((err = der_encode_sequence_ex(list, inlen, buf, outlen, LTC_ASN1_SETOF)) != CRYPT_OK) { - XFREE(buf); - return err; - } - - /* allocate edges */ - edges = XCALLOC(inlen, sizeof(*edges)); - if (edges == NULL) { - XFREE(buf); - return CRYPT_MEM; - } - - /* skip header */ - ptr = buf + 1; - - /* now skip length data */ - x = *ptr++; - if (x >= 0x80) { - ptr += (x & 0x7F); - } - - /* get the size of the static header */ - hdrlen = (unsigned long)((size_t)ptr - (size_t)buf); - - - /* scan for edges */ - x = 0; - while (ptr < (buf + *outlen)) { - /* store start */ - edges[x].start = ptr; - - /* skip type */ - z = 1; - - /* parse length */ - y = ptr[z++]; - if (y < 128) { - edges[x].size = y; - } else { - y &= 0x7F; - edges[x].size = 0; - while (y--) { - edges[x].size = (edges[x].size << 8) | ((unsigned long)ptr[z++]); - } - } - - /* skip content */ - edges[x].size += z; - ptr += edges[x].size; - ++x; - } - - /* sort based on contents (using edges) */ - XQSORT(edges, inlen, sizeof(*edges), &qsort_helper2); - - /* copy static header */ - XMEMCPY(out, buf, hdrlen); - - /* copy+sort using edges+indecies to output from buffer */ - for (y = hdrlen, x = 0; x < inlen; x++) { - XMEMCPY(out+y, edges[x].start, edges[x].size); - y += edges[x].size; - } - -#ifdef LTC_CLEAN_STACK - zeromem(buf, *outlen); -#endif - - /* free buffers */ - XFREE(edges); - XFREE(buf); - - return CRYPT_OK; -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/set/der_encode_setof.c,v $ */ -/* $Revision: 1.12 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_short_integer.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_short_integer.c deleted file mode 100644 index 9b167d0..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_short_integer.c +++ /dev/null @@ -1,97 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_encode_short_integer.c - ASN.1 DER, encode an integer, Tom St Denis -*/ - - -#ifdef LTC_DER - -/** - Store a short integer in the range (0,2^32-1) - @param num The integer to encode - @param out [out] The destination for the DER encoded integers - @param outlen [in/out] The max size and resulting size of the DER encoded integers - @return CRYPT_OK if successful -*/ -int der_encode_short_integer(unsigned long num, unsigned char *out, unsigned long *outlen) -{ - unsigned long len, x, y, z; - int err; - - LTC_ARGCHK(out != NULL); - LTC_ARGCHK(outlen != NULL); - - /* force to 32 bits */ - num &= 0xFFFFFFFFUL; - - /* find out how big this will be */ - if ((err = der_length_short_integer(num, &len)) != CRYPT_OK) { - return err; - } - - if (*outlen < len) { - *outlen = len; - return CRYPT_BUFFER_OVERFLOW; - } - - /* get len of output */ - z = 0; - y = num; - while (y) { - ++z; - y >>= 8; - } - - /* handle zero */ - if (z == 0) { - z = 1; - } - - /* see if msb is set */ - z += (num&(1UL<<((z<<3) - 1))) ? 1 : 0; - - /* adjust the number so the msB is non-zero */ - for (x = 0; (z <= 4) && (x < (4 - z)); x++) { - num <<= 8; - } - - /* store header */ - x = 0; - out[x++] = 0x02; - out[x++] = (unsigned char)z; - - /* if 31st bit is set output a leading zero and decrement count */ - if (z == 5) { - out[x++] = 0; - --z; - } - - /* store values */ - for (y = 0; y < z; y++) { - out[x++] = (unsigned char)((num >> 24) & 0xFF); - num <<= 8; - } - - /* we good */ - *outlen = x; - - return CRYPT_OK; -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/short_integer/der_encode_short_integer.c,v $ */ -/* $Revision: 1.8 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_utctime.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_utctime.c deleted file mode 100644 index 167a2b4..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_utctime.c +++ /dev/null @@ -1,83 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_encode_utctime.c - ASN.1 DER, encode a UTCTIME, Tom St Denis -*/ - -#ifdef LTC_DER - -static const char *baseten = "0123456789"; - -#define STORE_V(y) \ - out[x++] = der_ia5_char_encode(baseten[(y/10) % 10]); \ - out[x++] = der_ia5_char_encode(baseten[y % 10]); - -/** - Encodes a UTC time structure in DER format - @param utctime The UTC time structure to encode - @param out The destination of the DER encoding of the UTC time structure - @param outlen [in/out] The length of the DER encoding - @return CRYPT_OK if successful -*/ -int der_encode_utctime(ltc_utctime *utctime, - unsigned char *out, unsigned long *outlen) -{ - unsigned long x, tmplen; - int err; - - LTC_ARGCHK(utctime != NULL); - LTC_ARGCHK(out != NULL); - LTC_ARGCHK(outlen != NULL); - - if ((err = der_length_utctime(utctime, &tmplen)) != CRYPT_OK) { - return err; - } - if (tmplen > *outlen) { - *outlen = tmplen; - return CRYPT_BUFFER_OVERFLOW; - } - - /* store header */ - out[0] = 0x17; - - /* store values */ - x = 2; - STORE_V(utctime->YY); - STORE_V(utctime->MM); - STORE_V(utctime->DD); - STORE_V(utctime->hh); - STORE_V(utctime->mm); - STORE_V(utctime->ss); - - if (utctime->off_mm || utctime->off_hh) { - out[x++] = der_ia5_char_encode(utctime->off_dir ? '-' : '+'); - STORE_V(utctime->off_hh); - STORE_V(utctime->off_mm); - } else { - out[x++] = der_ia5_char_encode('Z'); - } - - /* store length */ - out[1] = (unsigned char)(x - 2); - - /* all good let's return */ - *outlen = x; - return CRYPT_OK; -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/utctime/der_encode_utctime.c,v $ */ -/* $Revision: 1.10 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_utf8_string.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_utf8_string.c deleted file mode 100644 index 84d8d06..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_encode_utf8_string.c +++ /dev/null @@ -1,105 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_encode_utf8_string.c - ASN.1 DER, encode a UTF8 STRING, Tom St Denis -*/ - - -#ifdef LTC_DER - -/** - Store an UTF8 STRING - @param in The array of UTF8 to store (one per wchar_t) - @param inlen The number of UTF8 to store - @param out [out] The destination for the DER encoded UTF8 STRING - @param outlen [in/out] The max size and resulting size of the DER UTF8 STRING - @return CRYPT_OK if successful -*/ -int der_encode_utf8_string(const wchar_t *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen) -{ - unsigned long x, y, len; - - LTC_ARGCHK(in != NULL); - LTC_ARGCHK(out != NULL); - LTC_ARGCHK(outlen != NULL); - - /* get the size */ - for (x = len = 0; x < inlen; x++) { - if (in[x] < 0 || in[x] > 0x1FFFF) { - return CRYPT_INVALID_ARG; - } - len += der_utf8_charsize(in[x]); - } - - if (len < 128) { - y = 2 + len; - } else if (len < 256) { - y = 3 + len; - } else if (len < 65536UL) { - y = 4 + len; - } else if (len < 16777216UL) { - y = 5 + len; - } else { - return CRYPT_INVALID_ARG; - } - - /* too big? */ - if (y > *outlen) { - *outlen = len; - return CRYPT_BUFFER_OVERFLOW; - } - - /* encode the header+len */ - x = 0; - out[x++] = 0x0C; - if (len < 128) { - out[x++] = (unsigned char)len; - } else if (len < 256) { - out[x++] = 0x81; - out[x++] = (unsigned char)len; - } else if (len < 65536UL) { - out[x++] = 0x82; - out[x++] = (unsigned char)((len>>8)&255); - out[x++] = (unsigned char)(len&255); - } else if (len < 16777216UL) { - out[x++] = 0x83; - out[x++] = (unsigned char)((len>>16)&255); - out[x++] = (unsigned char)((len>>8)&255); - out[x++] = (unsigned char)(len&255); - } else { - return CRYPT_INVALID_ARG; - } - - /* store UTF8 */ - for (y = 0; y < inlen; y++) { - switch (der_utf8_charsize(in[y])) { - case 1: out[x++] = (unsigned char)in[y]; break; - case 2: out[x++] = 0xC0 | ((in[y] >> 6) & 0x1F); out[x++] = 0x80 | (in[y] & 0x3F); break; - case 3: out[x++] = 0xE0 | ((in[y] >> 12) & 0x0F); out[x++] = 0x80 | ((in[y] >> 6) & 0x3F); out[x++] = 0x80 | (in[y] & 0x3F); break; - case 4: out[x++] = 0xF0 | ((in[y] >> 18) & 0x07); out[x++] = 0x80 | ((in[y] >> 12) & 0x3F); out[x++] = 0x80 | ((in[y] >> 6) & 0x3F); out[x++] = 0x80 | (in[y] & 0x3F); break; - } - } - - /* retun length */ - *outlen = x; - - return CRYPT_OK; -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/utf8/der_encode_utf8_string.c,v $ */ -/* $Revision: 1.9 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_bit_string.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_bit_string.c deleted file mode 100644 index 2bffa3b..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_bit_string.c +++ /dev/null @@ -1,54 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_length_bit_string.c - ASN.1 DER, get length of BIT STRING, Tom St Denis -*/ - -#ifdef LTC_DER -/** - Gets length of DER encoding of BIT STRING - @param nbits The number of bits in the string to encode - @param outlen [out] The length of the DER encoding for the given string - @return CRYPT_OK if successful -*/ -int der_length_bit_string(unsigned long nbits, unsigned long *outlen) -{ - unsigned long nbytes; - LTC_ARGCHK(outlen != NULL); - - /* get the number of the bytes */ - nbytes = (nbits >> 3) + ((nbits & 7) ? 1 : 0) + 1; - - if (nbytes < 128) { - /* 03 LL PP DD DD DD ... */ - *outlen = 2 + nbytes; - } else if (nbytes < 256) { - /* 03 81 LL PP DD DD DD ... */ - *outlen = 3 + nbytes; - } else if (nbytes < 65536) { - /* 03 82 LL LL PP DD DD DD ... */ - *outlen = 4 + nbytes; - } else { - return CRYPT_INVALID_ARG; - } - - return CRYPT_OK; -} - -#endif - - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/bit/der_length_bit_string.c,v $ */ -/* $Revision: 1.3 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_boolean.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_boolean.c deleted file mode 100644 index e34ce5c..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_boolean.c +++ /dev/null @@ -1,35 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_length_boolean.c - ASN.1 DER, get length of a BOOLEAN, Tom St Denis -*/ - -#ifdef LTC_DER -/** - Gets length of DER encoding of a BOOLEAN - @param outlen [out] The length of the DER encoding - @return CRYPT_OK if successful -*/ -int der_length_boolean(unsigned long *outlen) -{ - LTC_ARGCHK(outlen != NULL); - *outlen = 3; - return CRYPT_OK; -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/boolean/der_length_boolean.c,v $ */ -/* $Revision: 1.3 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_ia5_string.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_ia5_string.c deleted file mode 100644 index 473bc79..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_ia5_string.c +++ /dev/null @@ -1,194 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_length_ia5_string.c - ASN.1 DER, get length of IA5 STRING, Tom St Denis -*/ - -#ifdef LTC_DER - -static const struct { - int code, value; -} ia5_table[] = { -{ '\0', 0 }, -{ '\a', 7 }, -{ '\b', 8 }, -{ '\t', 9 }, -{ '\n', 10 }, -{ '\f', 12 }, -{ '\r', 13 }, -{ ' ', 32 }, -{ '!', 33 }, -{ '"', 34 }, -{ '#', 35 }, -{ '$', 36 }, -{ '%', 37 }, -{ '&', 38 }, -{ '\'', 39 }, -{ '(', 40 }, -{ ')', 41 }, -{ '*', 42 }, -{ '+', 43 }, -{ ',', 44 }, -{ '-', 45 }, -{ '.', 46 }, -{ '/', 47 }, -{ '0', 48 }, -{ '1', 49 }, -{ '2', 50 }, -{ '3', 51 }, -{ '4', 52 }, -{ '5', 53 }, -{ '6', 54 }, -{ '7', 55 }, -{ '8', 56 }, -{ '9', 57 }, -{ ':', 58 }, -{ ';', 59 }, -{ '<', 60 }, -{ '=', 61 }, -{ '>', 62 }, -{ '?', 63 }, -{ '@', 64 }, -{ 'A', 65 }, -{ 'B', 66 }, -{ 'C', 67 }, -{ 'D', 68 }, -{ 'E', 69 }, -{ 'F', 70 }, -{ 'G', 71 }, -{ 'H', 72 }, -{ 'I', 73 }, -{ 'J', 74 }, -{ 'K', 75 }, -{ 'L', 76 }, -{ 'M', 77 }, -{ 'N', 78 }, -{ 'O', 79 }, -{ 'P', 80 }, -{ 'Q', 81 }, -{ 'R', 82 }, -{ 'S', 83 }, -{ 'T', 84 }, -{ 'U', 85 }, -{ 'V', 86 }, -{ 'W', 87 }, -{ 'X', 88 }, -{ 'Y', 89 }, -{ 'Z', 90 }, -{ '[', 91 }, -{ '\\', 92 }, -{ ']', 93 }, -{ '^', 94 }, -{ '_', 95 }, -{ '`', 96 }, -{ 'a', 97 }, -{ 'b', 98 }, -{ 'c', 99 }, -{ 'd', 100 }, -{ 'e', 101 }, -{ 'f', 102 }, -{ 'g', 103 }, -{ 'h', 104 }, -{ 'i', 105 }, -{ 'j', 106 }, -{ 'k', 107 }, -{ 'l', 108 }, -{ 'm', 109 }, -{ 'n', 110 }, -{ 'o', 111 }, -{ 'p', 112 }, -{ 'q', 113 }, -{ 'r', 114 }, -{ 's', 115 }, -{ 't', 116 }, -{ 'u', 117 }, -{ 'v', 118 }, -{ 'w', 119 }, -{ 'x', 120 }, -{ 'y', 121 }, -{ 'z', 122 }, -{ '{', 123 }, -{ '|', 124 }, -{ '}', 125 }, -{ '~', 126 } -}; - -int der_ia5_char_encode(int c) -{ - int x; - for (x = 0; x < (int)(sizeof(ia5_table)/sizeof(ia5_table[0])); x++) { - if (ia5_table[x].code == c) { - return ia5_table[x].value; - } - } - return -1; -} - -int der_ia5_value_decode(int v) -{ - int x; - for (x = 0; x < (int)(sizeof(ia5_table)/sizeof(ia5_table[0])); x++) { - if (ia5_table[x].value == v) { - return ia5_table[x].code; - } - } - return -1; -} - -/** - Gets length of DER encoding of IA5 STRING - @param octets The values you want to encode - @param noctets The number of octets in the string to encode - @param outlen [out] The length of the DER encoding for the given string - @return CRYPT_OK if successful -*/ -int der_length_ia5_string(const unsigned char *octets, unsigned long noctets, unsigned long *outlen) -{ - unsigned long x; - - LTC_ARGCHK(outlen != NULL); - LTC_ARGCHK(octets != NULL); - - /* scan string for validity */ - for (x = 0; x < noctets; x++) { - if (der_ia5_char_encode(octets[x]) == -1) { - return CRYPT_INVALID_ARG; - } - } - - if (noctets < 128) { - /* 16 LL DD DD DD ... */ - *outlen = 2 + noctets; - } else if (noctets < 256) { - /* 16 81 LL DD DD DD ... */ - *outlen = 3 + noctets; - } else if (noctets < 65536UL) { - /* 16 82 LL LL DD DD DD ... */ - *outlen = 4 + noctets; - } else if (noctets < 16777216UL) { - /* 16 83 LL LL LL DD DD DD ... */ - *outlen = 5 + noctets; - } else { - return CRYPT_INVALID_ARG; - } - - return CRYPT_OK; -} - -#endif - - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/ia5/der_length_ia5_string.c,v $ */ -/* $Revision: 1.3 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_integer.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_integer.c deleted file mode 100644 index 540d205..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_integer.c +++ /dev/null @@ -1,82 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_length_integer.c - ASN.1 DER, get length of encoding, Tom St Denis -*/ - - -#ifdef LTC_DER -/** - Gets length of DER encoding of num - @param num The int to get the size of - @param outlen [out] The length of the DER encoding for the given integer - @return CRYPT_OK if successful -*/ -int der_length_integer(void *num, unsigned long *outlen) -{ - unsigned long z, len; - int leading_zero; - - LTC_ARGCHK(num != NULL); - LTC_ARGCHK(outlen != NULL); - - if (mp_cmp_d(num, 0) != LTC_MP_LT) { - /* positive */ - - /* we only need a leading zero if the msb of the first byte is one */ - if ((mp_count_bits(num) & 7) == 0 || mp_iszero(num) == LTC_MP_YES) { - leading_zero = 1; - } else { - leading_zero = 0; - } - - /* size for bignum */ - z = len = leading_zero + mp_unsigned_bin_size(num); - } else { - /* it's negative */ - /* find power of 2 that is a multiple of eight and greater than count bits */ - leading_zero = 0; - z = mp_count_bits(num); - z = z + (8 - (z & 7)); - if (((mp_cnt_lsb(num)+1)==mp_count_bits(num)) && ((mp_count_bits(num)&7)==0)) --z; - len = z = z >> 3; - } - - /* now we need a length */ - if (z < 128) { - /* short form */ - ++len; - } else { - /* long form (relies on z != 0), assumes length bytes < 128 */ - ++len; - - while (z) { - ++len; - z >>= 8; - } - } - - /* we need a 0x02 to indicate it's INTEGER */ - ++len; - - /* return length */ - *outlen = len; - return CRYPT_OK; -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/integer/der_length_integer.c,v $ */ -/* $Revision: 1.5 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_object_identifier.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_object_identifier.c deleted file mode 100644 index 94c326f..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_object_identifier.c +++ /dev/null @@ -1,89 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_length_object_identifier.c - ASN.1 DER, get length of Object Identifier, Tom St Denis -*/ - -#ifdef LTC_DER - -unsigned long der_object_identifier_bits(unsigned long x) -{ - unsigned long c; - x &= 0xFFFFFFFF; - c = 0; - while (x) { - ++c; - x >>= 1; - } - return c; -} - - -/** - Gets length of DER encoding of Object Identifier - @param nwords The number of OID words - @param words The actual OID words to get the size of - @param outlen [out] The length of the DER encoding for the given string - @return CRYPT_OK if successful -*/ -int der_length_object_identifier(unsigned long *words, unsigned long nwords, unsigned long *outlen) -{ - unsigned long y, z, t, wordbuf; - - LTC_ARGCHK(words != NULL); - LTC_ARGCHK(outlen != NULL); - - - /* must be >= 2 words */ - if (nwords < 2) { - return CRYPT_INVALID_ARG; - } - - /* word1 = 0,1,2,3 and word2 0..39 */ - if (words[0] > 3 || (words[0] < 2 && words[1] > 39)) { - return CRYPT_INVALID_ARG; - } - - /* leading word is the first two */ - z = 0; - wordbuf = words[0] * 40 + words[1]; - for (y = 1; y < nwords; y++) { - t = der_object_identifier_bits(wordbuf); - z += t/7 + ((t%7) ? 1 : 0) + (wordbuf == 0 ? 1 : 0); - if (y < nwords - 1) { - /* grab next word */ - wordbuf = words[y+1]; - } - } - - /* now depending on the length our length encoding changes */ - if (z < 128) { - z += 2; - } else if (z < 256) { - z += 3; - } else if (z < 65536UL) { - z += 4; - } else { - return CRYPT_INVALID_ARG; - } - - *outlen = z; - return CRYPT_OK; -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/object_identifier/der_length_object_identifier.c,v $ */ -/* $Revision: 1.5 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_octet_string.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_octet_string.c deleted file mode 100644 index acd4053..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_octet_string.c +++ /dev/null @@ -1,53 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_length_octet_string.c - ASN.1 DER, get length of OCTET STRING, Tom St Denis -*/ - -#ifdef LTC_DER -/** - Gets length of DER encoding of OCTET STRING - @param noctets The number of octets in the string to encode - @param outlen [out] The length of the DER encoding for the given string - @return CRYPT_OK if successful -*/ -int der_length_octet_string(unsigned long noctets, unsigned long *outlen) -{ - LTC_ARGCHK(outlen != NULL); - - if (noctets < 128) { - /* 04 LL DD DD DD ... */ - *outlen = 2 + noctets; - } else if (noctets < 256) { - /* 04 81 LL DD DD DD ... */ - *outlen = 3 + noctets; - } else if (noctets < 65536UL) { - /* 04 82 LL LL DD DD DD ... */ - *outlen = 4 + noctets; - } else if (noctets < 16777216UL) { - /* 04 83 LL LL LL DD DD DD ... */ - *outlen = 5 + noctets; - } else { - return CRYPT_INVALID_ARG; - } - - return CRYPT_OK; -} - -#endif - - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/octet/der_length_octet_string.c,v $ */ -/* $Revision: 1.3 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_printable_string.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_printable_string.c deleted file mode 100644 index ef1ed0e..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_printable_string.c +++ /dev/null @@ -1,166 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_length_printable_string.c - ASN.1 DER, get length of Printable STRING, Tom St Denis -*/ - -#ifdef LTC_DER - -static const struct { - int code, value; -} printable_table[] = { -{ ' ', 32 }, -{ '\'', 39 }, -{ '(', 40 }, -{ ')', 41 }, -{ '+', 43 }, -{ ',', 44 }, -{ '-', 45 }, -{ '.', 46 }, -{ '/', 47 }, -{ '0', 48 }, -{ '1', 49 }, -{ '2', 50 }, -{ '3', 51 }, -{ '4', 52 }, -{ '5', 53 }, -{ '6', 54 }, -{ '7', 55 }, -{ '8', 56 }, -{ '9', 57 }, -{ ':', 58 }, -{ '=', 61 }, -{ '?', 63 }, -{ 'A', 65 }, -{ 'B', 66 }, -{ 'C', 67 }, -{ 'D', 68 }, -{ 'E', 69 }, -{ 'F', 70 }, -{ 'G', 71 }, -{ 'H', 72 }, -{ 'I', 73 }, -{ 'J', 74 }, -{ 'K', 75 }, -{ 'L', 76 }, -{ 'M', 77 }, -{ 'N', 78 }, -{ 'O', 79 }, -{ 'P', 80 }, -{ 'Q', 81 }, -{ 'R', 82 }, -{ 'S', 83 }, -{ 'T', 84 }, -{ 'U', 85 }, -{ 'V', 86 }, -{ 'W', 87 }, -{ 'X', 88 }, -{ 'Y', 89 }, -{ 'Z', 90 }, -{ 'a', 97 }, -{ 'b', 98 }, -{ 'c', 99 }, -{ 'd', 100 }, -{ 'e', 101 }, -{ 'f', 102 }, -{ 'g', 103 }, -{ 'h', 104 }, -{ 'i', 105 }, -{ 'j', 106 }, -{ 'k', 107 }, -{ 'l', 108 }, -{ 'm', 109 }, -{ 'n', 110 }, -{ 'o', 111 }, -{ 'p', 112 }, -{ 'q', 113 }, -{ 'r', 114 }, -{ 's', 115 }, -{ 't', 116 }, -{ 'u', 117 }, -{ 'v', 118 }, -{ 'w', 119 }, -{ 'x', 120 }, -{ 'y', 121 }, -{ 'z', 122 }, -}; - -int der_printable_char_encode(int c) -{ - int x; - for (x = 0; x < (int)(sizeof(printable_table)/sizeof(printable_table[0])); x++) { - if (printable_table[x].code == c) { - return printable_table[x].value; - } - } - return -1; -} - -int der_printable_value_decode(int v) -{ - int x; - for (x = 0; x < (int)(sizeof(printable_table)/sizeof(printable_table[0])); x++) { - if (printable_table[x].value == v) { - return printable_table[x].code; - } - } - return -1; -} - -/** - Gets length of DER encoding of Printable STRING - @param octets The values you want to encode - @param noctets The number of octets in the string to encode - @param outlen [out] The length of the DER encoding for the given string - @return CRYPT_OK if successful -*/ -int der_length_printable_string(const unsigned char *octets, unsigned long noctets, unsigned long *outlen) -{ - unsigned long x; - - LTC_ARGCHK(outlen != NULL); - LTC_ARGCHK(octets != NULL); - - /* scan string for validity */ - for (x = 0; x < noctets; x++) { - if (der_printable_char_encode(octets[x]) == -1) { - return CRYPT_INVALID_ARG; - } - } - - if (noctets < 128) { - /* 16 LL DD DD DD ... */ - *outlen = 2 + noctets; - } else if (noctets < 256) { - /* 16 81 LL DD DD DD ... */ - *outlen = 3 + noctets; - } else if (noctets < 65536UL) { - /* 16 82 LL LL DD DD DD ... */ - *outlen = 4 + noctets; - } else if (noctets < 16777216UL) { - /* 16 83 LL LL LL DD DD DD ... */ - *outlen = 5 + noctets; - } else { - return CRYPT_INVALID_ARG; - } - - return CRYPT_OK; -} - -#endif - - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/printable_string/der_length_printable_string.c,v $ */ -/* $Revision: 1.3 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_sequence.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_sequence.c deleted file mode 100644 index e75ed7e..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_sequence.c +++ /dev/null @@ -1,169 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_length_sequence.c - ASN.1 DER, length a SEQUENCE, Tom St Denis -*/ - -#ifdef LTC_DER - -/** - Get the length of a DER sequence - @param list The sequences of items in the SEQUENCE - @param inlen The number of items - @param outlen [out] The length required in octets to store it - @return CRYPT_OK on success -*/ -int der_length_sequence(ltc_asn1_list *list, unsigned long inlen, - unsigned long *outlen) -{ - int err, type; - unsigned long size, x, y, z, i; - void *data; - - LTC_ARGCHK(list != NULL); - LTC_ARGCHK(outlen != NULL); - - /* get size of output that will be required */ - y = 0; - for (i = 0; i < inlen; i++) { - type = list[i].type; - size = list[i].size; - data = list[i].data; - - if (type == LTC_ASN1_EOL) { - break; - } - - switch (type) { - case LTC_ASN1_BOOLEAN: - if ((err = der_length_boolean(&x)) != CRYPT_OK) { - goto LBL_ERR; - } - y += x; - break; - - case LTC_ASN1_INTEGER: - if ((err = der_length_integer(data, &x)) != CRYPT_OK) { - goto LBL_ERR; - } - y += x; - break; - - case LTC_ASN1_SHORT_INTEGER: - if ((err = der_length_short_integer(*((unsigned long *)data), &x)) != CRYPT_OK) { - goto LBL_ERR; - } - y += x; - break; - - case LTC_ASN1_BIT_STRING: - if ((err = der_length_bit_string(size, &x)) != CRYPT_OK) { - goto LBL_ERR; - } - y += x; - break; - - case LTC_ASN1_OCTET_STRING: - if ((err = der_length_octet_string(size, &x)) != CRYPT_OK) { - goto LBL_ERR; - } - y += x; - break; - - case LTC_ASN1_NULL: - y += 2; - break; - - case LTC_ASN1_OBJECT_IDENTIFIER: - if ((err = der_length_object_identifier(data, size, &x)) != CRYPT_OK) { - goto LBL_ERR; - } - y += x; - break; - - case LTC_ASN1_IA5_STRING: - if ((err = der_length_ia5_string(data, size, &x)) != CRYPT_OK) { - goto LBL_ERR; - } - y += x; - break; - - case LTC_ASN1_PRINTABLE_STRING: - if ((err = der_length_printable_string(data, size, &x)) != CRYPT_OK) { - goto LBL_ERR; - } - y += x; - break; - - case LTC_ASN1_UTCTIME: - if ((err = der_length_utctime(data, &x)) != CRYPT_OK) { - goto LBL_ERR; - } - y += x; - break; - - case LTC_ASN1_UTF8_STRING: - if ((err = der_length_utf8_string(data, size, &x)) != CRYPT_OK) { - goto LBL_ERR; - } - y += x; - break; - - case LTC_ASN1_SET: - case LTC_ASN1_SETOF: - case LTC_ASN1_SEQUENCE: - if ((err = der_length_sequence(data, size, &x)) != CRYPT_OK) { - goto LBL_ERR; - } - y += x; - break; - - - default: - err = CRYPT_INVALID_ARG; - goto LBL_ERR; - } - } - - /* calc header size */ - z = y; - if (y < 128) { - y += 2; - } else if (y < 256) { - /* 0x30 0x81 LL */ - y += 3; - } else if (y < 65536UL) { - /* 0x30 0x82 LL LL */ - y += 4; - } else if (y < 16777216UL) { - /* 0x30 0x83 LL LL LL */ - y += 5; - } else { - err = CRYPT_INVALID_ARG; - goto LBL_ERR; - } - - /* store size */ - *outlen = y; - err = CRYPT_OK; - -LBL_ERR: - return err; -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/sequence/der_length_sequence.c,v $ */ -/* $Revision: 1.14 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_short_integer.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_short_integer.c deleted file mode 100644 index afa6dd0..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_short_integer.c +++ /dev/null @@ -1,70 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_length_short_integer.c - ASN.1 DER, get length of encoding, Tom St Denis -*/ - - -#ifdef LTC_DER -/** - Gets length of DER encoding of num - @param num The integer to get the size of - @param outlen [out] The length of the DER encoding for the given integer - @return CRYPT_OK if successful -*/ -int der_length_short_integer(unsigned long num, unsigned long *outlen) -{ - unsigned long z, y, len; - - LTC_ARGCHK(outlen != NULL); - - /* force to 32 bits */ - num &= 0xFFFFFFFFUL; - - /* get the number of bytes */ - z = 0; - y = num; - while (y) { - ++z; - y >>= 8; - } - - /* handle zero */ - if (z == 0) { - z = 1; - } - - /* we need a 0x02 to indicate it's INTEGER */ - len = 1; - - /* length byte */ - ++len; - - /* bytes in value */ - len += z; - - /* see if msb is set */ - len += (num&(1UL<<((z<<3) - 1))) ? 1 : 0; - - /* return length */ - *outlen = len; - - return CRYPT_OK; -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/short_integer/der_length_short_integer.c,v $ */ -/* $Revision: 1.6 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_utctime.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_utctime.c deleted file mode 100644 index 1296bab..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_utctime.c +++ /dev/null @@ -1,46 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_length_utctime.c - ASN.1 DER, get length of UTCTIME, Tom St Denis -*/ - -#ifdef LTC_DER - -/** - Gets length of DER encoding of UTCTIME - @param utctime The UTC time structure to get the size of - @param outlen [out] The length of the DER encoding - @return CRYPT_OK if successful -*/ -int der_length_utctime(ltc_utctime *utctime, unsigned long *outlen) -{ - LTC_ARGCHK(outlen != NULL); - LTC_ARGCHK(utctime != NULL); - - if (utctime->off_hh == 0 && utctime->off_mm == 0) { - /* we encode as YYMMDDhhmmssZ */ - *outlen = 2 + 13; - } else { - /* we encode as YYMMDDhhmmss{+|-}hh'mm' */ - *outlen = 2 + 17; - } - - return CRYPT_OK; -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/utctime/der_length_utctime.c,v $ */ -/* $Revision: 1.5 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_utf8_string.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_utf8_string.c deleted file mode 100644 index 514db84..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_length_utf8_string.c +++ /dev/null @@ -1,83 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_length_utf8_string.c - ASN.1 DER, get length of UTF8 STRING, Tom St Denis -*/ - -#ifdef LTC_DER - -/** Return the size in bytes of a UTF-8 character - @param c The UTF-8 character to measure - @return The size in bytes -*/ -unsigned long der_utf8_charsize(const wchar_t c) -{ - if (c <= 0x7F) { - return 1; - } else if (c <= 0x7FF) { - return 2; - } else if (c <= 0xFFFF) { - return 3; - } else { - return 4; - } -} - -/** - Gets length of DER encoding of UTF8 STRING - @param in The characters to measure the length of - @param noctets The number of octets in the string to encode - @param outlen [out] The length of the DER encoding for the given string - @return CRYPT_OK if successful -*/ -int der_length_utf8_string(const wchar_t *in, unsigned long noctets, unsigned long *outlen) -{ - unsigned long x, len; - - LTC_ARGCHK(in != NULL); - LTC_ARGCHK(outlen != NULL); - - len = 0; - for (x = 0; x < noctets; x++) { - if (in[x] < 0 || in[x] > 0x10FFFF) { - return CRYPT_INVALID_ARG; - } - len += der_utf8_charsize(in[x]); - } - - if (len < 128) { - /* 0C LL DD DD DD ... */ - *outlen = 2 + len; - } else if (len < 256) { - /* 0C 81 LL DD DD DD ... */ - *outlen = 3 + len; - } else if (len < 65536UL) { - /* 0C 82 LL LL DD DD DD ... */ - *outlen = 4 + len; - } else if (len < 16777216UL) { - /* 0C 83 LL LL LL DD DD DD ... */ - *outlen = 5 + len; - } else { - return CRYPT_INVALID_ARG; - } - - return CRYPT_OK; -} - -#endif - - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/utf8/der_length_utf8_string.c,v $ */ -/* $Revision: 1.6 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_sequence_free.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_sequence_free.c deleted file mode 100644 index 4887215..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/asn1/der_sequence_free.c +++ /dev/null @@ -1,65 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file der_sequence_free.c - ASN.1 DER, free's a structure allocated by der_decode_sequence_flexi(), Tom St Denis -*/ - -#ifdef LTC_DER - -/** - Free memory allocated by der_decode_sequence_flexi() - @param in The list to free -*/ -void der_sequence_free(ltc_asn1_list *in) -{ - ltc_asn1_list *l; - - /* walk to the start of the chain */ - while (in->prev != NULL || in->parent != NULL) { - if (in->parent != NULL) { - in = in->parent; - } else { - in = in->prev; - } - } - - /* now walk the list and free stuff */ - while (in != NULL) { - /* is there a child? */ - if (in->child) { - /* disconnect */ - in->child->parent = NULL; - der_sequence_free(in->child); - } - - switch (in->type) { - case LTC_ASN1_SET: - case LTC_ASN1_SETOF: - case LTC_ASN1_SEQUENCE: break; - case LTC_ASN1_INTEGER : if (in->data != NULL) { mp_clear(in->data); } break; - default : if (in->data != NULL) { XFREE(in->data); } - } - - /* move to next and free current */ - l = in->next; - free(in); - in = l; - } -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/asn1/der/sequence/der_sequence_free.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:27:24 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/ecc/ltc_ecc_map.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/ecc/ltc_ecc_map.c deleted file mode 100644 index 5a1324c..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/ecc/ltc_ecc_map.c +++ /dev/null @@ -1,76 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* Implements ECC over Z/pZ for curve y^2 = x^3 - 3x + b - * - * All curves taken from NIST recommendation paper of July 1999 - * Available at http://csrc.nist.gov/cryptval/dss.htm - */ -#include "../../headers/tomcrypt.h" - -/** - @file ltc_ecc_map.c - ECC Crypto, Tom St Denis -*/ - -#ifdef LTC_MECC - -/** - Map a projective jacbobian point back to affine space - @param P [in/out] The point to map - @param modulus The modulus of the field the ECC curve is in - @param mp The "b" value from montgomery_setup() - @return CRYPT_OK on success -*/ -int ltc_ecc_map(ecc_point *P, void *modulus, void *mp) -{ - void *t1, *t2; - int err; - - LTC_ARGCHK(P != NULL); - LTC_ARGCHK(modulus != NULL); - LTC_ARGCHK(mp != NULL); - - if ((err = mp_init_multi(&t1, &t2, NULL)) != CRYPT_OK) { - return CRYPT_MEM; - } - - /* first map z back to normal */ - if ((err = mp_montgomery_reduce(P->z, modulus, mp)) != CRYPT_OK) { goto done; } - - /* get 1/z */ - if ((err = mp_invmod(P->z, modulus, t1)) != CRYPT_OK) { goto done; } - - /* get 1/z^2 and 1/z^3 */ - if ((err = mp_sqr(t1, t2)) != CRYPT_OK) { goto done; } - if ((err = mp_mod(t2, modulus, t2)) != CRYPT_OK) { goto done; } - if ((err = mp_mul(t1, t2, t1)) != CRYPT_OK) { goto done; } - if ((err = mp_mod(t1, modulus, t1)) != CRYPT_OK) { goto done; } - - /* multiply against x/y */ - if ((err = mp_mul(P->x, t2, P->x)) != CRYPT_OK) { goto done; } - if ((err = mp_montgomery_reduce(P->x, modulus, mp)) != CRYPT_OK) { goto done; } - if ((err = mp_mul(P->y, t1, P->y)) != CRYPT_OK) { goto done; } - if ((err = mp_montgomery_reduce(P->y, modulus, mp)) != CRYPT_OK) { goto done; } - if ((err = mp_set(P->z, 1)) != CRYPT_OK) { goto done; } - - err = CRYPT_OK; -done: - mp_clear_multi(t1, t2, NULL); - return err; -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/ecc/ltc_ecc_map.c,v $ */ -/* $Revision: 1.7 $ */ -/* $Date: 2007/05/12 14:32:35 $ */ - diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/ecc/ltc_ecc_mul2add.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/ecc/ltc_ecc_mul2add.c deleted file mode 100644 index 2c468ea..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/ecc/ltc_ecc_mul2add.c +++ /dev/null @@ -1,207 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* Implements ECC over Z/pZ for curve y^2 = x^3 - 3x + b - * - * All curves taken from NIST recommendation paper of July 1999 - * Available at http://csrc.nist.gov/cryptval/dss.htm - */ -#include "../../headers/tomcrypt.h" - -/** - @file ltc_ecc_mul2add.c - ECC Crypto, Shamir's Trick, Tom St Denis -*/ - -#ifdef LTC_MECC - -#ifdef LTC_ECC_SHAMIR - -/** Computes kA*A + kB*B = C using Shamir's Trick - @param A First point to multiply - @param kA What to multiple A by - @param B Second point to multiply - @param kB What to multiple B by - @param C [out] Destination point (can overlap with A or B - @param modulus Modulus for curve - @return CRYPT_OK on success -*/ -int ltc_ecc_mul2add(ecc_point *A, void *kA, - ecc_point *B, void *kB, - ecc_point *C, - void *modulus) -{ - ecc_point *precomp[16]; - unsigned bitbufA, bitbufB, lenA, lenB, len, x, y, nA, nB, nibble; - unsigned char *tA, *tB; - int err, first; - void *mp, *mu; - - /* argchks */ - LTC_ARGCHK(A != NULL); - LTC_ARGCHK(B != NULL); - LTC_ARGCHK(C != NULL); - LTC_ARGCHK(kA != NULL); - LTC_ARGCHK(kB != NULL); - LTC_ARGCHK(modulus != NULL); - - /* allocate memory */ - tA = XCALLOC(1, ECC_BUF_SIZE); - if (tA == NULL) { - return CRYPT_MEM; - } - tB = XCALLOC(1, ECC_BUF_SIZE); - if (tB == NULL) { - XFREE(tA); - return CRYPT_MEM; - } - - /* get sizes */ - lenA = mp_unsigned_bin_size(kA); - lenB = mp_unsigned_bin_size(kB); - len = MAX(lenA, lenB); - - /* sanity check */ - if ((lenA > ECC_BUF_SIZE) || (lenB > ECC_BUF_SIZE)) { - err = CRYPT_INVALID_ARG; - goto ERR_T; - } - - /* extract and justify kA */ - mp_to_unsigned_bin(kA, (len - lenA) + tA); - - /* extract and justify kB */ - mp_to_unsigned_bin(kB, (len - lenB) + tB); - - /* allocate the table */ - for (x = 0; x < 16; x++) { - precomp[x] = ltc_ecc_new_point(); - if (precomp[x] == NULL) { - for (y = 0; y < x; ++y) { - ltc_ecc_del_point(precomp[y]); - } - err = CRYPT_MEM; - goto ERR_T; - } - } - - /* init montgomery reduction */ - if ((err = mp_montgomery_setup(modulus, &mp)) != CRYPT_OK) { - goto ERR_P; - } - if ((err = mp_init(&mu)) != CRYPT_OK) { - goto ERR_MP; - } - if ((err = mp_montgomery_normalization(mu, modulus)) != CRYPT_OK) { - goto ERR_MU; - } - - /* copy ones ... */ - if ((err = mp_mulmod(A->x, mu, modulus, precomp[1]->x)) != CRYPT_OK) { goto ERR_MU; } - if ((err = mp_mulmod(A->y, mu, modulus, precomp[1]->y)) != CRYPT_OK) { goto ERR_MU; } - if ((err = mp_mulmod(A->z, mu, modulus, precomp[1]->z)) != CRYPT_OK) { goto ERR_MU; } - - if ((err = mp_mulmod(B->x, mu, modulus, precomp[1<<2]->x)) != CRYPT_OK) { goto ERR_MU; } - if ((err = mp_mulmod(B->y, mu, modulus, precomp[1<<2]->y)) != CRYPT_OK) { goto ERR_MU; } - if ((err = mp_mulmod(B->z, mu, modulus, precomp[1<<2]->z)) != CRYPT_OK) { goto ERR_MU; } - - /* precomp [i,0](A + B) table */ - if ((err = ltc_mp.ecc_ptdbl(precomp[1], precomp[2], modulus, mp)) != CRYPT_OK) { goto ERR_MU; } - if ((err = ltc_mp.ecc_ptadd(precomp[1], precomp[2], precomp[3], modulus, mp)) != CRYPT_OK) { goto ERR_MU; } - - /* precomp [0,i](A + B) table */ - if ((err = ltc_mp.ecc_ptdbl(precomp[1<<2], precomp[2<<2], modulus, mp)) != CRYPT_OK) { goto ERR_MU; } - if ((err = ltc_mp.ecc_ptadd(precomp[1<<2], precomp[2<<2], precomp[3<<2], modulus, mp)) != CRYPT_OK) { goto ERR_MU; } - - /* precomp [i,j](A + B) table (i != 0, j != 0) */ - for (x = 1; x < 4; x++) { - for (y = 1; y < 4; y++) { - if ((err = ltc_mp.ecc_ptadd(precomp[x], precomp[(y<<2)], precomp[x+(y<<2)], modulus, mp)) != CRYPT_OK) { goto ERR_MU; } - } - } - - nibble = 3; - first = 1; - bitbufA = tA[0]; - bitbufB = tB[0]; - - /* for every byte of the multiplicands */ - for (x = -1;; ) { - /* grab a nibble */ - if (++nibble == 4) { - ++x; if (x == len) break; - bitbufA = tA[x]; - bitbufB = tB[x]; - nibble = 0; - } - - /* extract two bits from both, shift/update */ - nA = (bitbufA >> 6) & 0x03; - nB = (bitbufB >> 6) & 0x03; - bitbufA = (bitbufA << 2) & 0xFF; - bitbufB = (bitbufB << 2) & 0xFF; - - /* if both zero, if first, continue */ - if ((nA == 0) && (nB == 0) && (first == 1)) { - continue; - } - - /* double twice, only if this isn't the first */ - if (first == 0) { - /* double twice */ - if ((err = ltc_mp.ecc_ptdbl(C, C, modulus, mp)) != CRYPT_OK) { goto ERR_MU; } - if ((err = ltc_mp.ecc_ptdbl(C, C, modulus, mp)) != CRYPT_OK) { goto ERR_MU; } - } - - /* if not both zero */ - if ((nA != 0) || (nB != 0)) { - if (first == 1) { - /* if first, copy from table */ - first = 0; - if ((err = mp_copy(precomp[nA + (nB<<2)]->x, C->x)) != CRYPT_OK) { goto ERR_MU; } - if ((err = mp_copy(precomp[nA + (nB<<2)]->y, C->y)) != CRYPT_OK) { goto ERR_MU; } - if ((err = mp_copy(precomp[nA + (nB<<2)]->z, C->z)) != CRYPT_OK) { goto ERR_MU; } - } else { - /* if not first, add from table */ - if ((err = ltc_mp.ecc_ptadd(C, precomp[nA + (nB<<2)], C, modulus, mp)) != CRYPT_OK) { goto ERR_MU; } - } - } - } - - /* reduce to affine */ - err = ltc_ecc_map(C, modulus, mp); - - /* clean up */ -ERR_MU: - mp_clear(mu); -ERR_MP: - mp_montgomery_free(mp); -ERR_P: - for (x = 0; x < 16; x++) { - ltc_ecc_del_point(precomp[x]); - } -ERR_T: -#ifdef LTC_CLEAN_STACK - zeromem(tA, ECC_BUF_SIZE); - zeromem(tB, ECC_BUF_SIZE); -#endif - XFREE(tA); - XFREE(tB); - - return err; -} - -#endif -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/ecc/ltc_ecc_mul2add.c,v $ */ -/* $Revision: 1.8 $ */ -/* $Date: 2007/05/12 14:32:35 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/ecc/ltc_ecc_mulmod.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/ecc/ltc_ecc_mulmod.c deleted file mode 100644 index f9d0cad..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/ecc/ltc_ecc_mulmod.c +++ /dev/null @@ -1,222 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* Implements ECC over Z/pZ for curve y^2 = x^3 - 3x + b - * - * All curves taken from NIST recommendation paper of July 1999 - * Available at http://csrc.nist.gov/cryptval/dss.htm - */ -#include "../../headers/tomcrypt.h" - -/** - @file ltc_ecc_mulmod.c - ECC Crypto, Tom St Denis -*/ - -#ifdef LTC_MECC -#ifndef LTC_ECC_TIMING_RESISTANT - -/* size of sliding window, don't change this! */ -#define WINSIZE 4 - -/** - Perform a point multiplication - @param k The scalar to multiply by - @param G The base point - @param R [out] Destination for kG - @param modulus The modulus of the field the ECC curve is in - @param map Boolean whether to map back to affine or not (1==map, 0 == leave in projective) - @return CRYPT_OK on success -*/ -int ltc_ecc_mulmod(void *k, ecc_point *G, ecc_point *R, void *modulus, int map) -{ - ecc_point *tG, *M[8]; - int i, j, err; - void *mu, *mp; - unsigned long buf; - int first, bitbuf, bitcpy, bitcnt, mode, digidx; - - LTC_ARGCHK(k != NULL); - LTC_ARGCHK(G != NULL); - LTC_ARGCHK(R != NULL); - LTC_ARGCHK(modulus != NULL); - - /* init montgomery reduction */ - if ((err = mp_montgomery_setup(modulus, &mp)) != CRYPT_OK) { - return err; - } - if ((err = mp_init(&mu)) != CRYPT_OK) { - mp_montgomery_free(mp); - return err; - } - if ((err = mp_montgomery_normalization(mu, modulus)) != CRYPT_OK) { - mp_montgomery_free(mp); - mp_clear(mu); - return err; - } - - /* alloc ram for window temps */ - for (i = 0; i < 8; i++) { - M[i] = ltc_ecc_new_point(); - if (M[i] == NULL) { - for (j = 0; j < i; j++) { - ltc_ecc_del_point(M[j]); - } - mp_montgomery_free(mp); - mp_clear(mu); - return CRYPT_MEM; - } - } - - /* make a copy of G incase R==G */ - tG = ltc_ecc_new_point(); - if (tG == NULL) { err = CRYPT_MEM; goto done; } - - /* tG = G and convert to montgomery */ - if (mp_cmp_d(mu, 1) == LTC_MP_EQ) { - if ((err = mp_copy(G->x, tG->x)) != CRYPT_OK) { goto done; } - if ((err = mp_copy(G->y, tG->y)) != CRYPT_OK) { goto done; } - if ((err = mp_copy(G->z, tG->z)) != CRYPT_OK) { goto done; } - } else { - if ((err = mp_mulmod(G->x, mu, modulus, tG->x)) != CRYPT_OK) { goto done; } - if ((err = mp_mulmod(G->y, mu, modulus, tG->y)) != CRYPT_OK) { goto done; } - if ((err = mp_mulmod(G->z, mu, modulus, tG->z)) != CRYPT_OK) { goto done; } - } - mp_clear(mu); - mu = NULL; - - /* calc the M tab, which holds kG for k==8..15 */ - /* M[0] == 8G */ - if ((err = ltc_mp.ecc_ptdbl(tG, M[0], modulus, mp)) != CRYPT_OK) { goto done; } - if ((err = ltc_mp.ecc_ptdbl(M[0], M[0], modulus, mp)) != CRYPT_OK) { goto done; } - if ((err = ltc_mp.ecc_ptdbl(M[0], M[0], modulus, mp)) != CRYPT_OK) { goto done; } - - /* now find (8+k)G for k=1..7 */ - for (j = 9; j < 16; j++) { - if ((err = ltc_mp.ecc_ptadd(M[j-9], tG, M[j-8], modulus, mp)) != CRYPT_OK) { goto done; } - } - - /* setup sliding window */ - mode = 0; - bitcnt = 1; - buf = 0; - digidx = mp_get_digit_count(k) - 1; - bitcpy = bitbuf = 0; - first = 1; - - /* perform ops */ - for (;;) { - /* grab next digit as required */ - if (--bitcnt == 0) { - if (digidx == -1) { - break; - } - buf = mp_get_digit(k, digidx); - bitcnt = (int) ltc_mp.bits_per_digit; - --digidx; - } - - /* grab the next msb from the ltiplicand */ - i = (buf >> (ltc_mp.bits_per_digit - 1)) & 1; - buf <<= 1; - - /* skip leading zero bits */ - if (mode == 0 && i == 0) { - continue; - } - - /* if the bit is zero and mode == 1 then we double */ - if (mode == 1 && i == 0) { - if ((err = ltc_mp.ecc_ptdbl(R, R, modulus, mp)) != CRYPT_OK) { goto done; } - continue; - } - - /* else we add it to the window */ - bitbuf |= (i << (WINSIZE - ++bitcpy)); - mode = 2; - - if (bitcpy == WINSIZE) { - /* if this is the first window we do a simple copy */ - if (first == 1) { - /* R = kG [k = first window] */ - if ((err = mp_copy(M[bitbuf-8]->x, R->x)) != CRYPT_OK) { goto done; } - if ((err = mp_copy(M[bitbuf-8]->y, R->y)) != CRYPT_OK) { goto done; } - if ((err = mp_copy(M[bitbuf-8]->z, R->z)) != CRYPT_OK) { goto done; } - first = 0; - } else { - /* normal window */ - /* ok window is filled so double as required and add */ - /* double first */ - for (j = 0; j < WINSIZE; j++) { - if ((err = ltc_mp.ecc_ptdbl(R, R, modulus, mp)) != CRYPT_OK) { goto done; } - } - - /* then add, bitbuf will be 8..15 [8..2^WINSIZE] guaranteed */ - if ((err = ltc_mp.ecc_ptadd(R, M[bitbuf-8], R, modulus, mp)) != CRYPT_OK) { goto done; } - } - /* empty window and reset */ - bitcpy = bitbuf = 0; - mode = 1; - } - } - - /* if bits remain then double/add */ - if (mode == 2 && bitcpy > 0) { - /* double then add */ - for (j = 0; j < bitcpy; j++) { - /* only double if we have had at least one add first */ - if (first == 0) { - if ((err = ltc_mp.ecc_ptdbl(R, R, modulus, mp)) != CRYPT_OK) { goto done; } - } - - bitbuf <<= 1; - if ((bitbuf & (1 << WINSIZE)) != 0) { - if (first == 1){ - /* first add, so copy */ - if ((err = mp_copy(tG->x, R->x)) != CRYPT_OK) { goto done; } - if ((err = mp_copy(tG->y, R->y)) != CRYPT_OK) { goto done; } - if ((err = mp_copy(tG->z, R->z)) != CRYPT_OK) { goto done; } - first = 0; - } else { - /* then add */ - if ((err = ltc_mp.ecc_ptadd(R, tG, R, modulus, mp)) != CRYPT_OK) { goto done; } - } - } - } - } - - /* map R back from projective space */ - if (map) { - err = ltc_ecc_map(R, modulus, mp); - } else { - err = CRYPT_OK; - } -done: - if (mu != NULL) { - mp_clear(mu); - } - mp_montgomery_free(mp); - ltc_ecc_del_point(tG); - for (i = 0; i < 8; i++) { - ltc_ecc_del_point(M[i]); - } - return err; -} - -#endif - -#undef WINSIZE - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/ecc/ltc_ecc_mulmod.c,v $ */ -/* $Revision: 1.26 $ */ -/* $Date: 2007/05/12 14:32:35 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/ecc/ltc_ecc_points.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/ecc/ltc_ecc_points.c deleted file mode 100644 index f5a4acb..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/ecc/ltc_ecc_points.c +++ /dev/null @@ -1,60 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* Implements ECC over Z/pZ for curve y^2 = x^3 - 3x + b - * - * All curves taken from NIST recommendation paper of July 1999 - * Available at http://csrc.nist.gov/cryptval/dss.htm - */ -#include "../../headers/tomcrypt.h" - -/** - @file ltc_ecc_points.c - ECC Crypto, Tom St Denis -*/ - -#ifdef LTC_MECC - -/** - Allocate a new ECC point - @return A newly allocated point or NULL on error -*/ -ecc_point *ltc_ecc_new_point(void) -{ - ecc_point *p; - p = XCALLOC(1, sizeof(*p)); - if (p == NULL) { - return NULL; - } - if (mp_init_multi(&p->x, &p->y, &p->z, NULL) != CRYPT_OK) { - XFREE(p); - return NULL; - } - return p; -} - -/** Free an ECC point from memory - @param p The point to free -*/ -void ltc_ecc_del_point(ecc_point *p) -{ - /* prevents free'ing null arguments */ - if (p != NULL) { - mp_clear_multi(p->x, p->y, p->z, NULL); /* note: p->z may be NULL but that's ok with this function anyways */ - XFREE(p); - } -} - -#endif -/* $Source: /cvs/libtom/libtomcrypt/src/pk/ecc/ltc_ecc_points.c,v $ */ -/* $Revision: 1.7 $ */ -/* $Date: 2007/05/12 14:32:35 $ */ - diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/ecc/ltc_ecc_projective_add_point.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/ecc/ltc_ecc_projective_add_point.c deleted file mode 100644 index b4416fc..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/ecc/ltc_ecc_projective_add_point.c +++ /dev/null @@ -1,196 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* Implements ECC over Z/pZ for curve y^2 = x^3 - 3x + b - * - * All curves taken from NIST recommendation paper of July 1999 - * Available at http://csrc.nist.gov/cryptval/dss.htm - */ -#include "../../headers/tomcrypt.h" - -/** - @file ltc_ecc_projective_add_point.c - ECC Crypto, Tom St Denis -*/ - -#if defined(LTC_MECC) && (!defined(LTC_MECC_ACCEL) || defined(LTM_LTC_DESC)) - -/** - Add two ECC points - @param P The point to add - @param Q The point to add - @param R [out] The destination of the double - @param modulus The modulus of the field the ECC curve is in - @param mp The "b" value from montgomery_setup() - @return CRYPT_OK on success -*/ -int ltc_ecc_projective_add_point(ecc_point *P, ecc_point *Q, ecc_point *R, void *modulus, void *mp) -{ - void *t1, *t2, *x, *y, *z; - int err; - - LTC_ARGCHK(P != NULL); - LTC_ARGCHK(Q != NULL); - LTC_ARGCHK(R != NULL); - LTC_ARGCHK(modulus != NULL); - LTC_ARGCHK(mp != NULL); - - if ((err = mp_init_multi(&t1, &t2, &x, &y, &z, NULL)) != CRYPT_OK) { - return err; - } - - /* should we dbl instead? */ - if ((err = mp_sub(modulus, Q->y, t1)) != CRYPT_OK) { goto done; } - - if ( (mp_cmp(P->x, Q->x) == LTC_MP_EQ) && - (Q->z != NULL && mp_cmp(P->z, Q->z) == LTC_MP_EQ) && - (mp_cmp(P->y, Q->y) == LTC_MP_EQ || mp_cmp(P->y, t1) == LTC_MP_EQ)) { - mp_clear_multi(t1, t2, x, y, z, NULL); - return ltc_ecc_projective_dbl_point(P, R, modulus, mp); - } - - if ((err = mp_copy(P->x, x)) != CRYPT_OK) { goto done; } - if ((err = mp_copy(P->y, y)) != CRYPT_OK) { goto done; } - if ((err = mp_copy(P->z, z)) != CRYPT_OK) { goto done; } - - /* if Z is one then these are no-operations */ - if (Q->z != NULL) { - /* T1 = Z' * Z' */ - if ((err = mp_sqr(Q->z, t1)) != CRYPT_OK) { goto done; } - if ((err = mp_montgomery_reduce(t1, modulus, mp)) != CRYPT_OK) { goto done; } - /* X = X * T1 */ - if ((err = mp_mul(t1, x, x)) != CRYPT_OK) { goto done; } - if ((err = mp_montgomery_reduce(x, modulus, mp)) != CRYPT_OK) { goto done; } - /* T1 = Z' * T1 */ - if ((err = mp_mul(Q->z, t1, t1)) != CRYPT_OK) { goto done; } - if ((err = mp_montgomery_reduce(t1, modulus, mp)) != CRYPT_OK) { goto done; } - /* Y = Y * T1 */ - if ((err = mp_mul(t1, y, y)) != CRYPT_OK) { goto done; } - if ((err = mp_montgomery_reduce(y, modulus, mp)) != CRYPT_OK) { goto done; } - } - - /* T1 = Z*Z */ - if ((err = mp_sqr(z, t1)) != CRYPT_OK) { goto done; } - if ((err = mp_montgomery_reduce(t1, modulus, mp)) != CRYPT_OK) { goto done; } - /* T2 = X' * T1 */ - if ((err = mp_mul(Q->x, t1, t2)) != CRYPT_OK) { goto done; } - if ((err = mp_montgomery_reduce(t2, modulus, mp)) != CRYPT_OK) { goto done; } - /* T1 = Z * T1 */ - if ((err = mp_mul(z, t1, t1)) != CRYPT_OK) { goto done; } - if ((err = mp_montgomery_reduce(t1, modulus, mp)) != CRYPT_OK) { goto done; } - /* T1 = Y' * T1 */ - if ((err = mp_mul(Q->y, t1, t1)) != CRYPT_OK) { goto done; } - if ((err = mp_montgomery_reduce(t1, modulus, mp)) != CRYPT_OK) { goto done; } - - /* Y = Y - T1 */ - if ((err = mp_sub(y, t1, y)) != CRYPT_OK) { goto done; } - if (mp_cmp_d(y, 0) == LTC_MP_LT) { - if ((err = mp_add(y, modulus, y)) != CRYPT_OK) { goto done; } - } - /* T1 = 2T1 */ - if ((err = mp_add(t1, t1, t1)) != CRYPT_OK) { goto done; } - if (mp_cmp(t1, modulus) != LTC_MP_LT) { - if ((err = mp_sub(t1, modulus, t1)) != CRYPT_OK) { goto done; } - } - /* T1 = Y + T1 */ - if ((err = mp_add(t1, y, t1)) != CRYPT_OK) { goto done; } - if (mp_cmp(t1, modulus) != LTC_MP_LT) { - if ((err = mp_sub(t1, modulus, t1)) != CRYPT_OK) { goto done; } - } - /* X = X - T2 */ - if ((err = mp_sub(x, t2, x)) != CRYPT_OK) { goto done; } - if (mp_cmp_d(x, 0) == LTC_MP_LT) { - if ((err = mp_add(x, modulus, x)) != CRYPT_OK) { goto done; } - } - /* T2 = 2T2 */ - if ((err = mp_add(t2, t2, t2)) != CRYPT_OK) { goto done; } - if (mp_cmp(t2, modulus) != LTC_MP_LT) { - if ((err = mp_sub(t2, modulus, t2)) != CRYPT_OK) { goto done; } - } - /* T2 = X + T2 */ - if ((err = mp_add(t2, x, t2)) != CRYPT_OK) { goto done; } - if (mp_cmp(t2, modulus) != LTC_MP_LT) { - if ((err = mp_sub(t2, modulus, t2)) != CRYPT_OK) { goto done; } - } - - /* if Z' != 1 */ - if (Q->z != NULL) { - /* Z = Z * Z' */ - if ((err = mp_mul(z, Q->z, z)) != CRYPT_OK) { goto done; } - if ((err = mp_montgomery_reduce(z, modulus, mp)) != CRYPT_OK) { goto done; } - } - - /* Z = Z * X */ - if ((err = mp_mul(z, x, z)) != CRYPT_OK) { goto done; } - if ((err = mp_montgomery_reduce(z, modulus, mp)) != CRYPT_OK) { goto done; } - - /* T1 = T1 * X */ - if ((err = mp_mul(t1, x, t1)) != CRYPT_OK) { goto done; } - if ((err = mp_montgomery_reduce(t1, modulus, mp)) != CRYPT_OK) { goto done; } - /* X = X * X */ - if ((err = mp_sqr(x, x)) != CRYPT_OK) { goto done; } - if ((err = mp_montgomery_reduce(x, modulus, mp)) != CRYPT_OK) { goto done; } - /* T2 = T2 * x */ - if ((err = mp_mul(t2, x, t2)) != CRYPT_OK) { goto done; } - if ((err = mp_montgomery_reduce(t2, modulus, mp)) != CRYPT_OK) { goto done; } - /* T1 = T1 * X */ - if ((err = mp_mul(t1, x, t1)) != CRYPT_OK) { goto done; } - if ((err = mp_montgomery_reduce(t1, modulus, mp)) != CRYPT_OK) { goto done; } - - /* X = Y*Y */ - if ((err = mp_sqr(y, x)) != CRYPT_OK) { goto done; } - if ((err = mp_montgomery_reduce(x, modulus, mp)) != CRYPT_OK) { goto done; } - /* X = X - T2 */ - if ((err = mp_sub(x, t2, x)) != CRYPT_OK) { goto done; } - if (mp_cmp_d(x, 0) == LTC_MP_LT) { - if ((err = mp_add(x, modulus, x)) != CRYPT_OK) { goto done; } - } - - /* T2 = T2 - X */ - if ((err = mp_sub(t2, x, t2)) != CRYPT_OK) { goto done; } - if (mp_cmp_d(t2, 0) == LTC_MP_LT) { - if ((err = mp_add(t2, modulus, t2)) != CRYPT_OK) { goto done; } - } - /* T2 = T2 - X */ - if ((err = mp_sub(t2, x, t2)) != CRYPT_OK) { goto done; } - if (mp_cmp_d(t2, 0) == LTC_MP_LT) { - if ((err = mp_add(t2, modulus, t2)) != CRYPT_OK) { goto done; } - } - /* T2 = T2 * Y */ - if ((err = mp_mul(t2, y, t2)) != CRYPT_OK) { goto done; } - if ((err = mp_montgomery_reduce(t2, modulus, mp)) != CRYPT_OK) { goto done; } - /* Y = T2 - T1 */ - if ((err = mp_sub(t2, t1, y)) != CRYPT_OK) { goto done; } - if (mp_cmp_d(y, 0) == LTC_MP_LT) { - if ((err = mp_add(y, modulus, y)) != CRYPT_OK) { goto done; } - } - /* Y = Y/2 */ - if (mp_isodd(y)) { - if ((err = mp_add(y, modulus, y)) != CRYPT_OK) { goto done; } - } - if ((err = mp_div_2(y, y)) != CRYPT_OK) { goto done; } - - if ((err = mp_copy(x, R->x)) != CRYPT_OK) { goto done; } - if ((err = mp_copy(y, R->y)) != CRYPT_OK) { goto done; } - if ((err = mp_copy(z, R->z)) != CRYPT_OK) { goto done; } - - err = CRYPT_OK; -done: - mp_clear_multi(t1, t2, x, y, z, NULL); - return err; -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/ecc/ltc_ecc_projective_add_point.c,v $ */ -/* $Revision: 1.16 $ */ -/* $Date: 2007/05/12 14:32:35 $ */ - diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/ecc/ltc_ecc_projective_dbl_point.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/ecc/ltc_ecc_projective_dbl_point.c deleted file mode 100644 index b990e0a..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/ecc/ltc_ecc_projective_dbl_point.c +++ /dev/null @@ -1,147 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* Implements ECC over Z/pZ for curve y^2 = x^3 - 3x + b - * - * All curves taken from NIST recommendation paper of July 1999 - * Available at http://csrc.nist.gov/cryptval/dss.htm - */ -#include "../../headers/tomcrypt.h" - -/** - @file ltc_ecc_projective_dbl_point.c - ECC Crypto, Tom St Denis -*/ - -#if defined(LTC_MECC) && (!defined(LTC_MECC_ACCEL) || defined(LTM_LTC_DESC)) - -/** - Double an ECC point - @param P The point to double - @param R [out] The destination of the double - @param modulus The modulus of the field the ECC curve is in - @param mp The "b" value from montgomery_setup() - @return CRYPT_OK on success -*/ -int ltc_ecc_projective_dbl_point(ecc_point *P, ecc_point *R, void *modulus, void *mp) -{ - void *t1, *t2; - int err; - - LTC_ARGCHK(P != NULL); - LTC_ARGCHK(R != NULL); - LTC_ARGCHK(modulus != NULL); - LTC_ARGCHK(mp != NULL); - - if ((err = mp_init_multi(&t1, &t2, NULL)) != CRYPT_OK) { - return err; - } - - if (P != R) { - if ((err = mp_copy(P->x, R->x)) != CRYPT_OK) { goto done; } - if ((err = mp_copy(P->y, R->y)) != CRYPT_OK) { goto done; } - if ((err = mp_copy(P->z, R->z)) != CRYPT_OK) { goto done; } - } - - /* t1 = Z * Z */ - if ((err = mp_sqr(R->z, t1)) != CRYPT_OK) { goto done; } - if ((err = mp_montgomery_reduce(t1, modulus, mp)) != CRYPT_OK) { goto done; } - /* Z = Y * Z */ - if ((err = mp_mul(R->z, R->y, R->z)) != CRYPT_OK) { goto done; } - if ((err = mp_montgomery_reduce(R->z, modulus, mp)) != CRYPT_OK) { goto done; } - /* Z = 2Z */ - if ((err = mp_add(R->z, R->z, R->z)) != CRYPT_OK) { goto done; } - if (mp_cmp(R->z, modulus) != LTC_MP_LT) { - if ((err = mp_sub(R->z, modulus, R->z)) != CRYPT_OK) { goto done; } - } - - /* T2 = X - T1 */ - if ((err = mp_sub(R->x, t1, t2)) != CRYPT_OK) { goto done; } - if (mp_cmp_d(t2, 0) == LTC_MP_LT) { - if ((err = mp_add(t2, modulus, t2)) != CRYPT_OK) { goto done; } - } - /* T1 = X + T1 */ - if ((err = mp_add(t1, R->x, t1)) != CRYPT_OK) { goto done; } - if (mp_cmp(t1, modulus) != LTC_MP_LT) { - if ((err = mp_sub(t1, modulus, t1)) != CRYPT_OK) { goto done; } - } - /* T2 = T1 * T2 */ - if ((err = mp_mul(t1, t2, t2)) != CRYPT_OK) { goto done; } - if ((err = mp_montgomery_reduce(t2, modulus, mp)) != CRYPT_OK) { goto done; } - /* T1 = 2T2 */ - if ((err = mp_add(t2, t2, t1)) != CRYPT_OK) { goto done; } - if (mp_cmp(t1, modulus) != LTC_MP_LT) { - if ((err = mp_sub(t1, modulus, t1)) != CRYPT_OK) { goto done; } - } - /* T1 = T1 + T2 */ - if ((err = mp_add(t1, t2, t1)) != CRYPT_OK) { goto done; } - if (mp_cmp(t1, modulus) != LTC_MP_LT) { - if ((err = mp_sub(t1, modulus, t1)) != CRYPT_OK) { goto done; } - } - - /* Y = 2Y */ - if ((err = mp_add(R->y, R->y, R->y)) != CRYPT_OK) { goto done; } - if (mp_cmp(R->y, modulus) != LTC_MP_LT) { - if ((err = mp_sub(R->y, modulus, R->y)) != CRYPT_OK) { goto done; } - } - /* Y = Y * Y */ - if ((err = mp_sqr(R->y, R->y)) != CRYPT_OK) { goto done; } - if ((err = mp_montgomery_reduce(R->y, modulus, mp)) != CRYPT_OK) { goto done; } - /* T2 = Y * Y */ - if ((err = mp_sqr(R->y, t2)) != CRYPT_OK) { goto done; } - if ((err = mp_montgomery_reduce(t2, modulus, mp)) != CRYPT_OK) { goto done; } - /* T2 = T2/2 */ - if (mp_isodd(t2)) { - if ((err = mp_add(t2, modulus, t2)) != CRYPT_OK) { goto done; } - } - if ((err = mp_div_2(t2, t2)) != CRYPT_OK) { goto done; } - /* Y = Y * X */ - if ((err = mp_mul(R->y, R->x, R->y)) != CRYPT_OK) { goto done; } - if ((err = mp_montgomery_reduce(R->y, modulus, mp)) != CRYPT_OK) { goto done; } - - /* X = T1 * T1 */ - if ((err = mp_sqr(t1, R->x)) != CRYPT_OK) { goto done; } - if ((err = mp_montgomery_reduce(R->x, modulus, mp)) != CRYPT_OK) { goto done; } - /* X = X - Y */ - if ((err = mp_sub(R->x, R->y, R->x)) != CRYPT_OK) { goto done; } - if (mp_cmp_d(R->x, 0) == LTC_MP_LT) { - if ((err = mp_add(R->x, modulus, R->x)) != CRYPT_OK) { goto done; } - } - /* X = X - Y */ - if ((err = mp_sub(R->x, R->y, R->x)) != CRYPT_OK) { goto done; } - if (mp_cmp_d(R->x, 0) == LTC_MP_LT) { - if ((err = mp_add(R->x, modulus, R->x)) != CRYPT_OK) { goto done; } - } - - /* Y = Y - X */ - if ((err = mp_sub(R->y, R->x, R->y)) != CRYPT_OK) { goto done; } - if (mp_cmp_d(R->y, 0) == LTC_MP_LT) { - if ((err = mp_add(R->y, modulus, R->y)) != CRYPT_OK) { goto done; } - } - /* Y = Y * T1 */ - if ((err = mp_mul(R->y, t1, R->y)) != CRYPT_OK) { goto done; } - if ((err = mp_montgomery_reduce(R->y, modulus, mp)) != CRYPT_OK) { goto done; } - /* Y = Y - T2 */ - if ((err = mp_sub(R->y, t2, R->y)) != CRYPT_OK) { goto done; } - if (mp_cmp_d(R->y, 0) == LTC_MP_LT) { - if ((err = mp_add(R->y, modulus, R->y)) != CRYPT_OK) { goto done; } - } - - err = CRYPT_OK; -done: - mp_clear_multi(t1, t2, NULL); - return err; -} -#endif -/* $Source: /cvs/libtom/libtomcrypt/src/pk/ecc/ltc_ecc_projective_dbl_point.c,v $ */ -/* $Revision: 1.11 $ */ -/* $Date: 2007/05/12 14:32:35 $ */ - diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/pkcs1/pkcs_1_mgf1.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/pkcs1/pkcs_1_mgf1.c deleted file mode 100644 index e8f6418..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/pkcs1/pkcs_1_mgf1.c +++ /dev/null @@ -1,108 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file pkcs_1_mgf1.c - The Mask Generation Function (MGF1) for LTC_PKCS #1, Tom St Denis -*/ - -#ifdef LTC_PKCS_1 - -/** - Perform LTC_PKCS #1 MGF1 (internal) - @param seed The seed for MGF1 - @param seedlen The length of the seed - @param hash_idx The index of the hash desired - @param mask [out] The destination - @param masklen The length of the mask desired - @return CRYPT_OK if successful -*/ -int pkcs_1_mgf1(int hash_idx, - const unsigned char *seed, unsigned long seedlen, - unsigned char *mask, unsigned long masklen) -{ - unsigned long hLen, x; - ulong32 counter; - int err; - hash_state *md; - unsigned char *buf; - - LTC_ARGCHK(seed != NULL); - LTC_ARGCHK(mask != NULL); - - /* ensure valid hash */ - if ((err = hash_is_valid(hash_idx)) != CRYPT_OK) { - return err; - } - - /* get hash output size */ - hLen = hash_descriptor[hash_idx].hashsize; - - /* allocate memory */ - md = XMALLOC(sizeof(hash_state)); - buf = XMALLOC(hLen); - if (md == NULL || buf == NULL) { - if (md != NULL) { - XFREE(md); - } - if (buf != NULL) { - XFREE(buf); - } - return CRYPT_MEM; - } - - /* start counter */ - counter = 0; - - while (masklen > 0) { - /* handle counter */ - STORE32H(counter, buf); - ++counter; - - /* get hash of seed || counter */ - if ((err = hash_descriptor[hash_idx].init(md)) != CRYPT_OK) { - goto LBL_ERR; - } - if ((err = hash_descriptor[hash_idx].process(md, seed, seedlen)) != CRYPT_OK) { - goto LBL_ERR; - } - if ((err = hash_descriptor[hash_idx].process(md, buf, 4)) != CRYPT_OK) { - goto LBL_ERR; - } - if ((err = hash_descriptor[hash_idx].done(md, buf)) != CRYPT_OK) { - goto LBL_ERR; - } - - /* store it */ - for (x = 0; x < hLen && masklen > 0; x++, masklen--) { - *mask++ = buf[x]; - } - } - - err = CRYPT_OK; -LBL_ERR: -#ifdef LTC_CLEAN_STACK - zeromem(buf, hLen); - zeromem(md, sizeof(hash_state)); -#endif - - XFREE(buf); - XFREE(md); - - return err; -} - -#endif /* LTC_PKCS_1 */ - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/pkcs1/pkcs_1_mgf1.c,v $ */ -/* $Revision: 1.8 $ */ -/* $Date: 2007/05/12 14:32:35 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/pkcs1/pkcs_1_oaep_decode.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/pkcs1/pkcs_1_oaep_decode.c deleted file mode 100644 index 709ab8a..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/pkcs1/pkcs_1_oaep_decode.c +++ /dev/null @@ -1,189 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file pkcs_1_oaep_decode.c - OAEP Padding for LTC_PKCS #1, Tom St Denis -*/ - -#ifdef LTC_PKCS_1 - -/** - LTC_PKCS #1 v2.00 OAEP decode - @param msg The encoded data to decode - @param msglen The length of the encoded data (octets) - @param lparam The session or system data (can be NULL) - @param lparamlen The length of the lparam - @param modulus_bitlen The bit length of the RSA modulus - @param hash_idx The index of the hash desired - @param out [out] Destination of decoding - @param outlen [in/out] The max size and resulting size of the decoding - @param res [out] Result of decoding, 1==valid, 0==invalid - @return CRYPT_OK if successful (even if invalid) -*/ -int pkcs_1_oaep_decode(const unsigned char *msg, unsigned long msglen, - const unsigned char *lparam, unsigned long lparamlen, - unsigned long modulus_bitlen, int hash_idx, - unsigned char *out, unsigned long *outlen, - int *res) -{ - unsigned char *DB, *seed, *mask; - unsigned long hLen, x, y, modulus_len; - int err; - - LTC_ARGCHK(msg != NULL); - LTC_ARGCHK(out != NULL); - LTC_ARGCHK(outlen != NULL); - LTC_ARGCHK(res != NULL); - - /* default to invalid packet */ - *res = 0; - - /* test valid hash */ - if ((err = hash_is_valid(hash_idx)) != CRYPT_OK) { - return err; - } - hLen = hash_descriptor[hash_idx].hashsize; - modulus_len = (modulus_bitlen >> 3) + (modulus_bitlen & 7 ? 1 : 0); - - /* test hash/message size */ - if ((2*hLen >= (modulus_len - 2)) || (msglen != modulus_len)) { - return CRYPT_PK_INVALID_SIZE; - } - - /* allocate ram for DB/mask/salt of size modulus_len */ - DB = XMALLOC(modulus_len); - mask = XMALLOC(modulus_len); - seed = XMALLOC(hLen); - if (DB == NULL || mask == NULL || seed == NULL) { - if (DB != NULL) { - XFREE(DB); - } - if (mask != NULL) { - XFREE(mask); - } - if (seed != NULL) { - XFREE(seed); - } - return CRYPT_MEM; - } - - /* ok so it's now in the form - - 0x00 || maskedseed || maskedDB - - 1 || hLen || modulus_len - hLen - 1 - - */ - - /* must have leading 0x00 byte */ - if (msg[0] != 0x00) { - err = CRYPT_OK; - goto LBL_ERR; - } - - /* now read the masked seed */ - x = 1; - XMEMCPY(seed, msg + x, hLen); - x += hLen; - - /* now read the masked DB */ - XMEMCPY(DB, msg + x, modulus_len - hLen - 1); - x += modulus_len - hLen - 1; - - /* compute MGF1 of maskedDB (hLen) */ - if ((err = pkcs_1_mgf1(hash_idx, DB, modulus_len - hLen - 1, mask, hLen)) != CRYPT_OK) { - goto LBL_ERR; - } - - /* XOR against seed */ - for (y = 0; y < hLen; y++) { - seed[y] ^= mask[y]; - } - - /* compute MGF1 of seed (k - hlen - 1) */ - if ((err = pkcs_1_mgf1(hash_idx, seed, hLen, mask, modulus_len - hLen - 1)) != CRYPT_OK) { - goto LBL_ERR; - } - - /* xor against DB */ - for (y = 0; y < (modulus_len - hLen - 1); y++) { - DB[y] ^= mask[y]; - } - - /* now DB == lhash || PS || 0x01 || M, PS == k - mlen - 2hlen - 2 zeroes */ - - /* compute lhash and store it in seed [reuse temps!] */ - x = modulus_len; - if (lparam != NULL) { - if ((err = hash_memory(hash_idx, lparam, lparamlen, seed, &x)) != CRYPT_OK) { - goto LBL_ERR; - } - } else { - /* can't pass hash_memory a NULL so use DB with zero length */ - if ((err = hash_memory(hash_idx, DB, 0, seed, &x)) != CRYPT_OK) { - goto LBL_ERR; - } - } - - /* compare the lhash'es */ - if (XMEMCMP(seed, DB, hLen) != 0) { - err = CRYPT_OK; - goto LBL_ERR; - } - - /* now zeroes before a 0x01 */ - for (x = hLen; x < (modulus_len - hLen - 1) && DB[x] == 0x00; x++) { - /* step... */ - } - - /* error out if wasn't 0x01 */ - if (x == (modulus_len - hLen - 1) || DB[x] != 0x01) { - err = CRYPT_INVALID_PACKET; - goto LBL_ERR; - } - - /* rest is the message (and skip 0x01) */ - if ((modulus_len - hLen - 1 - ++x) > *outlen) { - *outlen = modulus_len - hLen - 1 - x; - err = CRYPT_BUFFER_OVERFLOW; - goto LBL_ERR; - } - - /* copy message */ - *outlen = modulus_len - hLen - 1 - x; - XMEMCPY(out, DB + x, modulus_len - hLen - 1 - x); - x += modulus_len - hLen - 1; - - /* valid packet */ - *res = 1; - - err = CRYPT_OK; -LBL_ERR: -#ifdef LTC_CLEAN_STACK - zeromem(DB, modulus_len); - zeromem(seed, hLen); - zeromem(mask, modulus_len); -#endif - - XFREE(seed); - XFREE(mask); - XFREE(DB); - - return err; -} - -#endif /* LTC_PKCS_1 */ - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/pkcs1/pkcs_1_oaep_decode.c,v $ */ -/* $Revision: 1.13 $ */ -/* $Date: 2007/05/12 14:32:35 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/pkcs1/pkcs_1_pss_decode.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/pkcs1/pkcs_1_pss_decode.c deleted file mode 100644 index c3a7211..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/pkcs1/pkcs_1_pss_decode.c +++ /dev/null @@ -1,177 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file pkcs_1_pss_decode.c - LTC_PKCS #1 PSS Signature Padding, Tom St Denis -*/ - -#ifdef LTC_PKCS_1 - -/** - LTC_PKCS #1 v2.00 PSS decode - @param msghash The hash to verify - @param msghashlen The length of the hash (octets) - @param sig The signature data (encoded data) - @param siglen The length of the signature data (octets) - @param saltlen The length of the salt used (octets) - @param hash_idx The index of the hash desired - @param modulus_bitlen The bit length of the RSA modulus - @param res [out] The result of the comparison, 1==valid, 0==invalid - @return CRYPT_OK if successful (even if the comparison failed) -*/ -int pkcs_1_pss_decode(const unsigned char *msghash, unsigned long msghashlen, - const unsigned char *sig, unsigned long siglen, - unsigned long saltlen, int hash_idx, - unsigned long modulus_bitlen, int *res) -{ - unsigned char *DB, *mask, *salt, *hash; - unsigned long x, y, hLen, modulus_len; - int err; - hash_state md; - - LTC_ARGCHK(msghash != NULL); - LTC_ARGCHK(res != NULL); - - /* default to invalid */ - *res = 0; - - /* ensure hash is valid */ - if ((err = hash_is_valid(hash_idx)) != CRYPT_OK) { - return err; - } - - hLen = hash_descriptor[hash_idx].hashsize; - modulus_len = (modulus_bitlen>>3) + (modulus_bitlen & 7 ? 1 : 0); - - /* check sizes */ - if ((saltlen > modulus_len) || - (modulus_len < hLen + saltlen + 2) || (siglen != modulus_len)) { - return CRYPT_PK_INVALID_SIZE; - } - - /* allocate ram for DB/mask/salt/hash of size modulus_len */ - DB = XMALLOC(modulus_len); - mask = XMALLOC(modulus_len); - salt = XMALLOC(modulus_len); - hash = XMALLOC(modulus_len); - if (DB == NULL || mask == NULL || salt == NULL || hash == NULL) { - if (DB != NULL) { - XFREE(DB); - } - if (mask != NULL) { - XFREE(mask); - } - if (salt != NULL) { - XFREE(salt); - } - if (hash != NULL) { - XFREE(hash); - } - return CRYPT_MEM; - } - - /* ensure the 0xBC byte */ - if (sig[siglen-1] != 0xBC) { - err = CRYPT_INVALID_PACKET; - goto LBL_ERR; - } - - /* copy out the DB */ - x = 0; - XMEMCPY(DB, sig + x, modulus_len - hLen - 1); - x += modulus_len - hLen - 1; - - /* copy out the hash */ - XMEMCPY(hash, sig + x, hLen); - x += hLen; - - /* check the MSB */ - if ((sig[0] & ~(0xFF >> ((modulus_len<<3) - (modulus_bitlen-1)))) != 0) { - err = CRYPT_INVALID_PACKET; - goto LBL_ERR; - } - - /* generate mask of length modulus_len - hLen - 1 from hash */ - if ((err = pkcs_1_mgf1(hash_idx, hash, hLen, mask, modulus_len - hLen - 1)) != CRYPT_OK) { - goto LBL_ERR; - } - - /* xor against DB */ - for (y = 0; y < (modulus_len - hLen - 1); y++) { - DB[y] ^= mask[y]; - } - - /* now clear the first byte [make sure smaller than modulus] */ - DB[0] &= 0xFF >> ((modulus_len<<3) - (modulus_bitlen-1)); - - /* DB = PS || 0x01 || salt, PS == modulus_len - saltlen - hLen - 2 zero bytes */ - - /* check for zeroes and 0x01 */ - for (x = 0; x < modulus_len - saltlen - hLen - 2; x++) { - if (DB[x] != 0x00) { - err = CRYPT_INVALID_PACKET; - goto LBL_ERR; - } - } - - /* check for the 0x01 */ - if (DB[x++] != 0x01) { - err = CRYPT_INVALID_PACKET; - goto LBL_ERR; - } - - /* M = (eight) 0x00 || msghash || salt, mask = H(M) */ - if ((err = hash_descriptor[hash_idx].init(&md)) != CRYPT_OK) { - goto LBL_ERR; - } - zeromem(mask, 8); - if ((err = hash_descriptor[hash_idx].process(&md, mask, 8)) != CRYPT_OK) { - goto LBL_ERR; - } - if ((err = hash_descriptor[hash_idx].process(&md, msghash, msghashlen)) != CRYPT_OK) { - goto LBL_ERR; - } - if ((err = hash_descriptor[hash_idx].process(&md, DB+x, saltlen)) != CRYPT_OK) { - goto LBL_ERR; - } - if ((err = hash_descriptor[hash_idx].done(&md, mask)) != CRYPT_OK) { - goto LBL_ERR; - } - - /* mask == hash means valid signature */ - if (XMEMCMP(mask, hash, hLen) == 0) { - *res = 1; - } - - err = CRYPT_OK; -LBL_ERR: -#ifdef LTC_CLEAN_STACK - zeromem(DB, modulus_len); - zeromem(mask, modulus_len); - zeromem(salt, modulus_len); - zeromem(hash, modulus_len); -#endif - - XFREE(hash); - XFREE(salt); - XFREE(mask); - XFREE(DB); - - return err; -} - -#endif /* LTC_PKCS_1 */ - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/pkcs1/pkcs_1_pss_decode.c,v $ */ -/* $Revision: 1.11 $ */ -/* $Date: 2007/05/12 14:32:35 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/pkcs1/pkcs_1_pss_encode.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/pkcs1/pkcs_1_pss_encode.c deleted file mode 100644 index 68d5e86..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/pkcs1/pkcs_1_pss_encode.c +++ /dev/null @@ -1,175 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file pkcs_1_pss_encode.c - LTC_PKCS #1 PSS Signature Padding, Tom St Denis -*/ - -#ifdef LTC_PKCS_1 - -/** - LTC_PKCS #1 v2.00 Signature Encoding - @param msghash The hash to encode - @param msghashlen The length of the hash (octets) - @param saltlen The length of the salt desired (octets) - @param prng An active PRNG context - @param prng_idx The index of the PRNG desired - @param hash_idx The index of the hash desired - @param modulus_bitlen The bit length of the RSA modulus - @param out [out] The destination of the encoding - @param outlen [in/out] The max size and resulting size of the encoded data - @return CRYPT_OK if successful -*/ -int pkcs_1_pss_encode(const unsigned char *msghash, unsigned long msghashlen, - unsigned long saltlen, prng_state *prng, - int prng_idx, int hash_idx, - unsigned long modulus_bitlen, - unsigned char *out, unsigned long *outlen) -{ - unsigned char *DB, *mask, *salt, *hash; - unsigned long x, y, hLen, modulus_len; - int err; - hash_state md; - - LTC_ARGCHK(msghash != NULL); - LTC_ARGCHK(out != NULL); - LTC_ARGCHK(outlen != NULL); - - /* ensure hash and PRNG are valid */ - if ((err = hash_is_valid(hash_idx)) != CRYPT_OK) { - return err; - } - if ((err = prng_is_valid(prng_idx)) != CRYPT_OK) { - return err; - } - - hLen = hash_descriptor[hash_idx].hashsize; - modulus_len = (modulus_bitlen>>3) + (modulus_bitlen & 7 ? 1 : 0); - - /* check sizes */ - if ((saltlen > modulus_len) || (modulus_len < hLen + saltlen + 2)) { - return CRYPT_PK_INVALID_SIZE; - } - - /* allocate ram for DB/mask/salt/hash of size modulus_len */ - DB = XMALLOC(modulus_len); - mask = XMALLOC(modulus_len); - salt = XMALLOC(modulus_len); - hash = XMALLOC(modulus_len); - if (DB == NULL || mask == NULL || salt == NULL || hash == NULL) { - if (DB != NULL) { - XFREE(DB); - } - if (mask != NULL) { - XFREE(mask); - } - if (salt != NULL) { - XFREE(salt); - } - if (hash != NULL) { - XFREE(hash); - } - return CRYPT_MEM; - } - - - /* generate random salt */ - if (saltlen > 0) { - if (prng_descriptor[prng_idx].read(salt, saltlen, prng) != saltlen) { - err = CRYPT_ERROR_READPRNG; - goto LBL_ERR; - } - } - - /* M = (eight) 0x00 || msghash || salt, hash = H(M) */ - if ((err = hash_descriptor[hash_idx].init(&md)) != CRYPT_OK) { - goto LBL_ERR; - } - zeromem(DB, 8); - if ((err = hash_descriptor[hash_idx].process(&md, DB, 8)) != CRYPT_OK) { - goto LBL_ERR; - } - if ((err = hash_descriptor[hash_idx].process(&md, msghash, msghashlen)) != CRYPT_OK) { - goto LBL_ERR; - } - if ((err = hash_descriptor[hash_idx].process(&md, salt, saltlen)) != CRYPT_OK) { - goto LBL_ERR; - } - if ((err = hash_descriptor[hash_idx].done(&md, hash)) != CRYPT_OK) { - goto LBL_ERR; - } - - /* generate DB = PS || 0x01 || salt, PS == modulus_len - saltlen - hLen - 2 zero bytes */ - x = 0; - XMEMSET(DB + x, 0, modulus_len - saltlen - hLen - 2); - x += modulus_len - saltlen - hLen - 2; - DB[x++] = 0x01; - XMEMCPY(DB + x, salt, saltlen); - x += saltlen; - - /* generate mask of length modulus_len - hLen - 1 from hash */ - if ((err = pkcs_1_mgf1(hash_idx, hash, hLen, mask, modulus_len - hLen - 1)) != CRYPT_OK) { - goto LBL_ERR; - } - - /* xor against DB */ - for (y = 0; y < (modulus_len - hLen - 1); y++) { - DB[y] ^= mask[y]; - } - - /* output is DB || hash || 0xBC */ - if (*outlen < modulus_len) { - *outlen = modulus_len; - err = CRYPT_BUFFER_OVERFLOW; - goto LBL_ERR; - } - - /* DB len = modulus_len - hLen - 1 */ - y = 0; - XMEMCPY(out + y, DB, modulus_len - hLen - 1); - y += modulus_len - hLen - 1; - - /* hash */ - XMEMCPY(out + y, hash, hLen); - y += hLen; - - /* 0xBC */ - out[y] = 0xBC; - - /* now clear the 8*modulus_len - modulus_bitlen most significant bits */ - out[0] &= 0xFF >> ((modulus_len<<3) - (modulus_bitlen-1)); - - /* store output size */ - *outlen = modulus_len; - err = CRYPT_OK; -LBL_ERR: -#ifdef LTC_CLEAN_STACK - zeromem(DB, modulus_len); - zeromem(mask, modulus_len); - zeromem(salt, modulus_len); - zeromem(hash, modulus_len); -#endif - - XFREE(hash); - XFREE(salt); - XFREE(mask); - XFREE(DB); - - return err; -} - -#endif /* LTC_PKCS_1 */ - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/pkcs1/pkcs_1_pss_encode.c,v $ */ -/* $Revision: 1.9 $ */ -/* $Date: 2007/05/12 14:32:35 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/pkcs1/pkcs_1_v1_5_decode.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/pkcs1/pkcs_1_v1_5_decode.c deleted file mode 100644 index 7c3711c..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/pkcs1/pkcs_1_v1_5_decode.c +++ /dev/null @@ -1,110 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** @file pkcs_1_v1_5_decode.c - * - * LTC_PKCS #1 v1.5 Padding. (Andreas Lange) - */ - -#ifdef LTC_PKCS_1 - -/** @brief LTC_PKCS #1 v1.5 decode. - * - * @param msg The encoded data to decode - * @param msglen The length of the encoded data (octets) - * @param block_type Block type to use in padding (\sa ltc_pkcs_1_v1_5_blocks) - * @param modulus_bitlen The bit length of the RSA modulus - * @param out [out] Destination of decoding - * @param outlen [in/out] The max size and resulting size of the decoding - * @param is_valid [out] Boolean whether the padding was valid - * - * @return CRYPT_OK if successful (even if invalid) - */ -int pkcs_1_v1_5_decode(const unsigned char *msg, - unsigned long msglen, - int block_type, - unsigned long modulus_bitlen, - unsigned char *out, - unsigned long *outlen, - int *is_valid) -{ - unsigned long modulus_len, ps_len, i; - int result; - - /* default to invalid packet */ - *is_valid = 0; - - modulus_len = (modulus_bitlen >> 3) + (modulus_bitlen & 7 ? 1 : 0); - - /* test message size */ - - if ((msglen > modulus_len) || (modulus_len < 11)) { - return CRYPT_PK_INVALID_SIZE; - } - - /* separate encoded message */ - - if ((msg[0] != 0x00) || (msg[1] != (unsigned char)block_type)) { - result = CRYPT_INVALID_PACKET; - goto bail; - } - - if (block_type == LTC_LTC_PKCS_1_EME) { - for (i = 2; i < modulus_len; i++) { - /* separator */ - if (msg[i] == 0x00) { break; } - } - ps_len = i++ - 2; - - if ((i >= modulus_len) || (ps_len < 8)) { - /* There was no octet with hexadecimal value 0x00 to separate ps from m, - * or the length of ps is less than 8 octets. - */ - result = CRYPT_INVALID_PACKET; - goto bail; - } - } else { - for (i = 2; i < modulus_len - 1; i++) { - if (msg[i] != 0xFF) { break; } - } - - /* separator check */ - if (msg[i] != 0) { - /* There was no octet with hexadecimal value 0x00 to separate ps from m. */ - result = CRYPT_INVALID_PACKET; - goto bail; - } - - ps_len = i - 2; - } - - if (*outlen < (msglen - (2 + ps_len + 1))) { - *outlen = msglen - (2 + ps_len + 1); - result = CRYPT_BUFFER_OVERFLOW; - goto bail; - } - - *outlen = (msglen - (2 + ps_len + 1)); - XMEMCPY(out, &msg[2 + ps_len + 1], *outlen); - - /* valid packet */ - *is_valid = 1; - result = CRYPT_OK; -bail: - return result; -} /* pkcs_1_v1_5_decode */ - -#endif /* #ifdef LTC_PKCS_1 */ - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/pkcs1/pkcs_1_v1_5_decode.c,v $ */ -/* $Revision: 1.7 $ */ -/* $Date: 2007/05/12 14:32:35 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/pkcs1/pkcs_1_v1_5_encode.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/pkcs1/pkcs_1_v1_5_encode.c deleted file mode 100644 index 4342919..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/pkcs1/pkcs_1_v1_5_encode.c +++ /dev/null @@ -1,111 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/*! \file pkcs_1_v1_5_encode.c - * - * LTC_PKCS #1 v1.5 Padding (Andreas Lange) - */ - -#ifdef LTC_PKCS_1 - -/*! \brief LTC_PKCS #1 v1.5 encode. - * - * \param msg The data to encode - * \param msglen The length of the data to encode (octets) - * \param block_type Block type to use in padding (\sa ltc_pkcs_1_v1_5_blocks) - * \param modulus_bitlen The bit length of the RSA modulus - * \param prng An active PRNG state (only for LTC_LTC_PKCS_1_EME) - * \param prng_idx The index of the PRNG desired (only for LTC_LTC_PKCS_1_EME) - * \param out [out] The destination for the encoded data - * \param outlen [in/out] The max size and resulting size of the encoded data - * - * \return CRYPT_OK if successful - */ -int pkcs_1_v1_5_encode(const unsigned char *msg, - unsigned long msglen, - int block_type, - unsigned long modulus_bitlen, - prng_state *prng, - int prng_idx, - unsigned char *out, - unsigned long *outlen) -{ - unsigned long modulus_len, ps_len, i; - unsigned char *ps; - int result; - - /* valid block_type? */ - if ((block_type != LTC_LTC_PKCS_1_EMSA) && - (block_type != LTC_LTC_PKCS_1_EME)) { - return CRYPT_PK_INVALID_PADDING; - } - - if (block_type == LTC_LTC_PKCS_1_EME) { /* encryption padding, we need a valid PRNG */ - if ((result = prng_is_valid(prng_idx)) != CRYPT_OK) { - return result; - } - } - - modulus_len = (modulus_bitlen >> 3) + (modulus_bitlen & 7 ? 1 : 0); - - /* test message size */ - if ((msglen + 11) > modulus_len) { - return CRYPT_PK_INVALID_SIZE; - } - - if (*outlen < modulus_len) { - *outlen = modulus_len; - result = CRYPT_BUFFER_OVERFLOW; - goto bail; - } - - /* generate an octets string PS */ - ps = &out[2]; - ps_len = modulus_len - msglen - 3; - - if (block_type == LTC_LTC_PKCS_1_EME) { - /* now choose a random ps */ - if (prng_descriptor[prng_idx].read(ps, ps_len, prng) != ps_len) { - result = CRYPT_ERROR_READPRNG; - goto bail; - } - - /* transform zero bytes (if any) to non-zero random bytes */ - for (i = 0; i < ps_len; i++) { - while (ps[i] == 0) { - if (prng_descriptor[prng_idx].read(&ps[i], 1, prng) != 1) { - result = CRYPT_ERROR_READPRNG; - goto bail; - } - } - } - } else { - XMEMSET(ps, 0xFF, ps_len); - } - - /* create string of length modulus_len */ - out[0] = 0x00; - out[1] = (unsigned char)block_type; /* block_type 1 or 2 */ - out[2 + ps_len] = 0x00; - XMEMCPY(&out[2 + ps_len + 1], msg, msglen); - *outlen = modulus_len; - - result = CRYPT_OK; -bail: - return result; -} /* pkcs_1_v1_5_encode */ - -#endif /* #ifdef LTC_PKCS_1 */ - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/pkcs1/pkcs_1_v1_5_encode.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2007/05/12 14:32:35 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/rsa/rsa_exptmod.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/rsa/rsa_exptmod.c deleted file mode 100644 index ba44106..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/rsa/rsa_exptmod.c +++ /dev/null @@ -1,113 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file rsa_exptmod.c - RSA LTC_PKCS exptmod, Tom St Denis -*/ - -#ifdef LTC_MRSA - -/** - Compute an RSA modular exponentiation - @param in The input data to send into RSA - @param inlen The length of the input (octets) - @param out [out] The destination - @param outlen [in/out] The max size and resulting size of the output - @param which Which exponent to use, e.g. PK_PRIVATE or PK_PUBLIC - @param key The RSA key to use - @return CRYPT_OK if successful -*/ -int rsa_exptmod(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen, int which, - rsa_key *key) -{ - void *tmp, *tmpa, *tmpb; - unsigned long x; - int err; - - LTC_ARGCHK(in != NULL); - LTC_ARGCHK(out != NULL); - LTC_ARGCHK(outlen != NULL); - LTC_ARGCHK(key != NULL); - - /* is the key of the right type for the operation? */ - if (which == PK_PRIVATE && (key->type != PK_PRIVATE)) { - return CRYPT_PK_NOT_PRIVATE; - } - - /* must be a private or public operation */ - if (which != PK_PRIVATE && which != PK_PUBLIC) { - return CRYPT_PK_INVALID_TYPE; - } - - /* init and copy into tmp */ - if ((err = mp_init_multi(&tmp, &tmpa, &tmpb, NULL)) != CRYPT_OK) { return err; } - if ((err = mp_read_unsigned_bin(tmp, (unsigned char *)in, (int)inlen)) != CRYPT_OK) { goto error; } - - /* sanity check on the input */ - if (mp_cmp(key->N, tmp) == LTC_MP_LT) { - err = CRYPT_PK_INVALID_SIZE; - goto error; - } - - /* are we using the private exponent and is the key optimized? */ - if (which == PK_PRIVATE) { - /* tmpa = tmp^dP mod p */ - if ((err = mp_exptmod(tmp, key->dP, key->p, tmpa)) != CRYPT_OK) { goto error; } - - /* tmpb = tmp^dQ mod q */ - if ((err = mp_exptmod(tmp, key->dQ, key->q, tmpb)) != CRYPT_OK) { goto error; } - - /* tmp = (tmpa - tmpb) * qInv (mod p) */ - if ((err = mp_sub(tmpa, tmpb, tmp)) != CRYPT_OK) { goto error; } - if ((err = mp_mulmod(tmp, key->qP, key->p, tmp)) != CRYPT_OK) { goto error; } - - /* tmp = tmpb + q * tmp */ - if ((err = mp_mul(tmp, key->q, tmp)) != CRYPT_OK) { goto error; } - if ((err = mp_add(tmp, tmpb, tmp)) != CRYPT_OK) { goto error; } - } else { - /* exptmod it */ - if ((err = mp_exptmod(tmp, key->e, key->N, tmp)) != CRYPT_OK) { goto error; } - } - - /* read it back */ - x = (unsigned long)mp_unsigned_bin_size(key->N); - if (x > *outlen) { - *outlen = x; - err = CRYPT_BUFFER_OVERFLOW; - goto error; - } - - /* this should never happen ... */ - if (mp_unsigned_bin_size(tmp) > mp_unsigned_bin_size(key->N)) { - err = CRYPT_ERROR; - goto error; - } - *outlen = x; - - /* convert it */ - zeromem(out, x); - if ((err = mp_to_unsigned_bin(tmp, out+(x-mp_unsigned_bin_size(tmp)))) != CRYPT_OK) { goto error; } - - /* clean up and return */ - err = CRYPT_OK; -error: - mp_clear_multi(tmp, tmpa, tmpb, NULL); - return err; -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/rsa/rsa_exptmod.c,v $ */ -/* $Revision: 1.18 $ */ -/* $Date: 2007/05/12 14:32:35 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/rsa/rsa_free.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/rsa/rsa_free.c deleted file mode 100644 index a10ed59..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/rsa/rsa_free.c +++ /dev/null @@ -1,34 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file rsa_free.c - Free an RSA key, Tom St Denis -*/ - -#ifdef LTC_MRSA - -/** - Free an RSA key from memory - @param key The RSA key to free -*/ -void rsa_free(rsa_key *key) -{ - LTC_ARGCHKVD(key != NULL); - mp_clear_multi(key->e, key->d, key->N, key->dQ, key->dP, key->qP, key->p, key->q, NULL); -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/rsa/rsa_free.c,v $ */ -/* $Revision: 1.10 $ */ -/* $Date: 2007/05/12 14:32:35 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/rsa/rsa_import.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/rsa/rsa_import.c deleted file mode 100644 index 6254fd7..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/rsa/rsa_import.c +++ /dev/null @@ -1,143 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file rsa_import.c - Import a LTC_PKCS RSA key, Tom St Denis -*/ - -#ifdef LTC_MRSA - -/** - Import an RSAPublicKey or RSAPrivateKey [two-prime only, only support >= 1024-bit keys, defined in LTC_PKCS #1 v2.1] - @param in The packet to import from - @param inlen It's length (octets) - @param key [out] Destination for newly imported key - @return CRYPT_OK if successful, upon error allocated memory is freed -*/ -int rsa_import(const unsigned char *in, unsigned long inlen, rsa_key *key) -{ - int err; - void *zero; - unsigned char *tmpbuf; - unsigned long t, x, y, z, tmpoid[16]; - ltc_asn1_list ssl_pubkey_hashoid[2]; - ltc_asn1_list ssl_pubkey[2]; - - LTC_ARGCHK(in != NULL); - LTC_ARGCHK(key != NULL); - LTC_ARGCHK(ltc_mp.name != NULL); - - /* init key */ - if ((err = mp_init_multi(&key->e, &key->d, &key->N, &key->dQ, - &key->dP, &key->qP, &key->p, &key->q, NULL)) != CRYPT_OK) { - return err; - } - - /* see if the OpenSSL DER format RSA public key will work */ - tmpbuf = XCALLOC(1, MAX_RSA_SIZE*8); - if (tmpbuf == NULL) { - err = CRYPT_MEM; - goto LBL_ERR; - } - - /* this includes the internal hash ID and optional params (NULL in this case) */ - LTC_SET_ASN1(ssl_pubkey_hashoid, 0, LTC_ASN1_OBJECT_IDENTIFIER, tmpoid, sizeof(tmpoid)/sizeof(tmpoid[0])); - LTC_SET_ASN1(ssl_pubkey_hashoid, 1, LTC_ASN1_NULL, NULL, 0); - - /* the actual format of the SSL DER key is odd, it stores a RSAPublicKey in a **BIT** string ... so we have to extract it - then proceed to convert bit to octet - */ - LTC_SET_ASN1(ssl_pubkey, 0, LTC_ASN1_SEQUENCE, &ssl_pubkey_hashoid, 2); - LTC_SET_ASN1(ssl_pubkey, 1, LTC_ASN1_BIT_STRING, tmpbuf, MAX_RSA_SIZE*8); - - if (der_decode_sequence(in, inlen, - ssl_pubkey, 2UL) == CRYPT_OK) { - - /* ok now we have to reassemble the BIT STRING to an OCTET STRING. Thanks OpenSSL... */ - for (t = y = z = x = 0; x < ssl_pubkey[1].size; x++) { - y = (y << 1) | tmpbuf[x]; - if (++z == 8) { - tmpbuf[t++] = (unsigned char)y; - y = 0; - z = 0; - } - } - - /* now it should be SEQUENCE { INTEGER, INTEGER } */ - if ((err = der_decode_sequence_multi(tmpbuf, t, - LTC_ASN1_INTEGER, 1UL, key->N, - LTC_ASN1_INTEGER, 1UL, key->e, - LTC_ASN1_EOL, 0UL, NULL)) != CRYPT_OK) { - XFREE(tmpbuf); - goto LBL_ERR; - } - XFREE(tmpbuf); - key->type = PK_PUBLIC; - return CRYPT_OK; - } - XFREE(tmpbuf); - - /* not SSL public key, try to match against LTC_PKCS #1 standards */ - if ((err = der_decode_sequence_multi(in, inlen, - LTC_ASN1_INTEGER, 1UL, key->N, - LTC_ASN1_EOL, 0UL, NULL)) != CRYPT_OK) { - goto LBL_ERR; - } - - if (mp_cmp_d(key->N, 0) == LTC_MP_EQ) { - if ((err = mp_init(&zero)) != CRYPT_OK) { - goto LBL_ERR; - } - /* it's a private key */ - if ((err = der_decode_sequence_multi(in, inlen, - LTC_ASN1_INTEGER, 1UL, zero, - LTC_ASN1_INTEGER, 1UL, key->N, - LTC_ASN1_INTEGER, 1UL, key->e, - LTC_ASN1_INTEGER, 1UL, key->d, - LTC_ASN1_INTEGER, 1UL, key->p, - LTC_ASN1_INTEGER, 1UL, key->q, - LTC_ASN1_INTEGER, 1UL, key->dP, - LTC_ASN1_INTEGER, 1UL, key->dQ, - LTC_ASN1_INTEGER, 1UL, key->qP, - LTC_ASN1_EOL, 0UL, NULL)) != CRYPT_OK) { - mp_clear(zero); - goto LBL_ERR; - } - mp_clear(zero); - key->type = PK_PRIVATE; - } else if (mp_cmp_d(key->N, 1) == LTC_MP_EQ) { - /* we don't support multi-prime RSA */ - err = CRYPT_PK_INVALID_TYPE; - goto LBL_ERR; - } else { - /* it's a public key and we lack e */ - if ((err = der_decode_sequence_multi(in, inlen, - LTC_ASN1_INTEGER, 1UL, key->N, - LTC_ASN1_INTEGER, 1UL, key->e, - LTC_ASN1_EOL, 0UL, NULL)) != CRYPT_OK) { - goto LBL_ERR; - } - key->type = PK_PUBLIC; - } - return CRYPT_OK; -LBL_ERR: - mp_clear_multi(key->d, key->e, key->N, key->dQ, key->dP, key->qP, key->p, key->q, NULL); - return err; -} - -#endif /* LTC_MRSA */ - - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/rsa/rsa_import.c,v $ */ -/* $Revision: 1.23 $ */ -/* $Date: 2007/05/12 14:32:35 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/rsa/rsa_make_key.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/rsa/rsa_make_key.c deleted file mode 100644 index bd37b4a..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/rsa/rsa_make_key.c +++ /dev/null @@ -1,112 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file rsa_make_key.c - RSA key generation, Tom St Denis -*/ - -#ifdef LTC_MRSA - -/** - Create an RSA key - @param prng An active PRNG state - @param wprng The index of the PRNG desired - @param size The size of the modulus (key size) desired (octets) - @param e The "e" value (public key). e==65537 is a good choice - @param key [out] Destination of a newly created private key pair - @return CRYPT_OK if successful, upon error all allocated ram is freed -*/ -int rsa_make_key(prng_state *prng, int wprng, int size, long e, rsa_key *key) -{ - void *p, *q, *tmp1, *tmp2, *tmp3; - int err; - - LTC_ARGCHK(ltc_mp.name != NULL); - LTC_ARGCHK(key != NULL); - - if ((size < (MIN_RSA_SIZE/8)) || (size > (MAX_RSA_SIZE/8))) { - return CRYPT_INVALID_KEYSIZE; - } - - if ((e < 3) || ((e & 1) == 0)) { - return CRYPT_INVALID_ARG; - } - - if ((err = prng_is_valid(wprng)) != CRYPT_OK) { - return err; - } - - if ((err = mp_init_multi(&p, &q, &tmp1, &tmp2, &tmp3, NULL)) != CRYPT_OK) { - return err; - } - - /* make primes p and q (optimization provided by Wayne Scott) */ - if ((err = mp_set_int(tmp3, e)) != CRYPT_OK) { goto errkey; } /* tmp3 = e */ - - /* make prime "p" */ - do { - if ((err = rand_prime( p, size/2, prng, wprng)) != CRYPT_OK) { goto errkey; } - if ((err = mp_sub_d( p, 1, tmp1)) != CRYPT_OK) { goto errkey; } /* tmp1 = p-1 */ - if ((err = mp_gcd( tmp1, tmp3, tmp2)) != CRYPT_OK) { goto errkey; } /* tmp2 = gcd(p-1, e) */ - } while (mp_cmp_d( tmp2, 1) != 0); /* while e divides p-1 */ - - /* make prime "q" */ - do { - if ((err = rand_prime( q, size/2, prng, wprng)) != CRYPT_OK) { goto errkey; } - if ((err = mp_sub_d( q, 1, tmp1)) != CRYPT_OK) { goto errkey; } /* tmp1 = q-1 */ - if ((err = mp_gcd( tmp1, tmp3, tmp2)) != CRYPT_OK) { goto errkey; } /* tmp2 = gcd(q-1, e) */ - } while (mp_cmp_d( tmp2, 1) != 0); /* while e divides q-1 */ - - /* tmp1 = lcm(p-1, q-1) */ - if ((err = mp_sub_d( p, 1, tmp2)) != CRYPT_OK) { goto errkey; } /* tmp2 = p-1 */ - /* tmp1 = q-1 (previous do/while loop) */ - if ((err = mp_lcm( tmp1, tmp2, tmp1)) != CRYPT_OK) { goto errkey; } /* tmp1 = lcm(p-1, q-1) */ - - /* make key */ - if ((err = mp_init_multi(&key->e, &key->d, &key->N, &key->dQ, &key->dP, &key->qP, &key->p, &key->q, NULL)) != CRYPT_OK) { - goto errkey; - } - - if ((err = mp_set_int( key->e, e)) != CRYPT_OK) { goto errkey; } /* key->e = e */ - if ((err = mp_invmod( key->e, tmp1, key->d)) != CRYPT_OK) { goto errkey; } /* key->d = 1/e mod lcm(p-1,q-1) */ - if ((err = mp_mul( p, q, key->N)) != CRYPT_OK) { goto errkey; } /* key->N = pq */ - - /* optimize for CRT now */ - /* find d mod q-1 and d mod p-1 */ - if ((err = mp_sub_d( p, 1, tmp1)) != CRYPT_OK) { goto errkey; } /* tmp1 = q-1 */ - if ((err = mp_sub_d( q, 1, tmp2)) != CRYPT_OK) { goto errkey; } /* tmp2 = p-1 */ - if ((err = mp_mod( key->d, tmp1, key->dP)) != CRYPT_OK) { goto errkey; } /* dP = d mod p-1 */ - if ((err = mp_mod( key->d, tmp2, key->dQ)) != CRYPT_OK) { goto errkey; } /* dQ = d mod q-1 */ - if ((err = mp_invmod( q, p, key->qP)) != CRYPT_OK) { goto errkey; } /* qP = 1/q mod p */ - - if ((err = mp_copy( p, key->p)) != CRYPT_OK) { goto errkey; } - if ((err = mp_copy( q, key->q)) != CRYPT_OK) { goto errkey; } - - /* set key type (in this case it's CRT optimized) */ - key->type = PK_PRIVATE; - - /* return ok and free temps */ - err = CRYPT_OK; - goto cleanup; -errkey: - mp_clear_multi(key->d, key->e, key->N, key->dQ, key->dP, key->qP, key->p, key->q, NULL); -cleanup: - mp_clear_multi(tmp3, tmp2, tmp1, p, q, NULL); - return err; -} - -#endif - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/rsa/rsa_make_key.c,v $ */ -/* $Revision: 1.16 $ */ -/* $Date: 2007/05/12 14:32:35 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/rsa/rsa_sign_hash.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/rsa/rsa_sign_hash.c deleted file mode 100644 index 49fb858..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/rsa/rsa_sign_hash.c +++ /dev/null @@ -1,134 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file rsa_sign_hash.c - RSA LTC_PKCS #1 v1.5 and v2 PSS sign hash, Tom St Denis and Andreas Lange -*/ - -#ifdef LTC_MRSA - -/** - LTC_PKCS #1 pad then sign - @param in The hash to sign - @param inlen The length of the hash to sign (octets) - @param out [out] The signature - @param outlen [in/out] The max size and resulting size of the signature - @param padding Type of padding (LTC_LTC_PKCS_1_PSS or LTC_LTC_PKCS_1_V1_5) - @param prng An active PRNG state - @param prng_idx The index of the PRNG desired - @param hash_idx The index of the hash desired - @param saltlen The length of the salt desired (octets) - @param key The private RSA key to use - @return CRYPT_OK if successful -*/ -int rsa_sign_hash_ex(const unsigned char *in, unsigned long inlen, - unsigned char *out, unsigned long *outlen, - int padding, - prng_state *prng, int prng_idx, - int hash_idx, unsigned long saltlen, - rsa_key *key) -{ - unsigned long modulus_bitlen, modulus_bytelen, x, y; - int err; - - LTC_ARGCHK(in != NULL); - LTC_ARGCHK(out != NULL); - LTC_ARGCHK(outlen != NULL); - LTC_ARGCHK(key != NULL); - - /* valid padding? */ - if ((padding != LTC_LTC_PKCS_1_V1_5) && (padding != LTC_LTC_PKCS_1_PSS)) { - return CRYPT_PK_INVALID_PADDING; - } - - if (padding == LTC_LTC_PKCS_1_PSS) { - /* valid prng and hash ? */ - if ((err = prng_is_valid(prng_idx)) != CRYPT_OK) { - return err; - } - if ((err = hash_is_valid(hash_idx)) != CRYPT_OK) { - return err; - } - } - - /* get modulus len in bits */ - modulus_bitlen = mp_count_bits((key->N)); - - /* outlen must be at least the size of the modulus */ - modulus_bytelen = mp_unsigned_bin_size((key->N)); - if (modulus_bytelen > *outlen) { - *outlen = modulus_bytelen; - return CRYPT_BUFFER_OVERFLOW; - } - - if (padding == LTC_LTC_PKCS_1_PSS) { - /* PSS pad the key */ - x = *outlen; - if ((err = pkcs_1_pss_encode(in, inlen, saltlen, prng, prng_idx, - hash_idx, modulus_bitlen, out, &x)) != CRYPT_OK) { - return err; - } - } else { - /* LTC_PKCS #1 v1.5 pad the hash */ - unsigned char *tmpin; - ltc_asn1_list digestinfo[2], siginfo[2]; - - /* not all hashes have OIDs... so sad */ - if (hash_descriptor[hash_idx].OIDlen == 0) { - return CRYPT_INVALID_ARG; - } - - /* construct the SEQUENCE - SEQUENCE { - SEQUENCE {hashoid OID - blah NULL - } - hash OCTET STRING - } - */ - LTC_SET_ASN1(digestinfo, 0, LTC_ASN1_OBJECT_IDENTIFIER, hash_descriptor[hash_idx].OID, hash_descriptor[hash_idx].OIDlen); - LTC_SET_ASN1(digestinfo, 1, LTC_ASN1_NULL, NULL, 0); - LTC_SET_ASN1(siginfo, 0, LTC_ASN1_SEQUENCE, digestinfo, 2); - LTC_SET_ASN1(siginfo, 1, LTC_ASN1_OCTET_STRING, in, inlen); - - /* allocate memory for the encoding */ - y = mp_unsigned_bin_size(key->N); - tmpin = XMALLOC(y); - if (tmpin == NULL) { - return CRYPT_MEM; - } - - if ((err = der_encode_sequence(siginfo, 2, tmpin, &y)) != CRYPT_OK) { - XFREE(tmpin); - return err; - } - - x = *outlen; - if ((err = pkcs_1_v1_5_encode(tmpin, y, LTC_LTC_PKCS_1_EMSA, - modulus_bitlen, NULL, 0, - out, &x)) != CRYPT_OK) { - XFREE(tmpin); - return err; - } - XFREE(tmpin); - } - - /* RSA encode it */ - return ltc_mp.rsa_me(out, x, out, outlen, PK_PRIVATE, key); -} - -#endif /* LTC_MRSA */ - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/rsa/rsa_sign_hash.c,v $ */ -/* $Revision: 1.11 $ */ -/* $Date: 2007/05/12 14:32:35 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/rsa/rsa_verify_hash.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/rsa/rsa_verify_hash.c deleted file mode 100644 index 103ae2f..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/rsa/rsa_verify_hash.c +++ /dev/null @@ -1,167 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file rsa_verify_hash.c - RSA LTC_PKCS #1 v1.5 or v2 PSS signature verification, Tom St Denis and Andreas Lange -*/ - -#ifdef LTC_MRSA - -/** - LTC_PKCS #1 de-sign then v1.5 or PSS depad - @param sig The signature data - @param siglen The length of the signature data (octets) - @param hash The hash of the message that was signed - @param hashlen The length of the hash of the message that was signed (octets) - @param padding Type of padding (LTC_LTC_PKCS_1_PSS or LTC_LTC_PKCS_1_V1_5) - @param hash_idx The index of the desired hash - @param saltlen The length of the salt used during signature - @param stat [out] The result of the signature comparison, 1==valid, 0==invalid - @param key The public RSA key corresponding to the key that performed the signature - @return CRYPT_OK on success (even if the signature is invalid) -*/ -int rsa_verify_hash_ex(const unsigned char *sig, unsigned long siglen, - const unsigned char *hash, unsigned long hashlen, - int padding, - int hash_idx, unsigned long saltlen, - int *stat, rsa_key *key) -{ - unsigned long modulus_bitlen, modulus_bytelen, x; - int err; - unsigned char *tmpbuf; - - LTC_ARGCHK(hash != NULL); - LTC_ARGCHK(sig != NULL); - LTC_ARGCHK(stat != NULL); - LTC_ARGCHK(key != NULL); - - /* default to invalid */ - *stat = 0; - - /* valid padding? */ - - if ((padding != LTC_LTC_PKCS_1_V1_5) && - (padding != LTC_LTC_PKCS_1_PSS)) { - return CRYPT_PK_INVALID_PADDING; - } - - if (padding == LTC_LTC_PKCS_1_PSS) { - /* valid hash ? */ - if ((err = hash_is_valid(hash_idx)) != CRYPT_OK) { - return err; - } - } - - /* get modulus len in bits */ - modulus_bitlen = mp_count_bits( (key->N)); - - /* outlen must be at least the size of the modulus */ - modulus_bytelen = mp_unsigned_bin_size( (key->N)); - if (modulus_bytelen != siglen) { - return CRYPT_INVALID_PACKET; - } - - /* allocate temp buffer for decoded sig */ - tmpbuf = XMALLOC(siglen); - if (tmpbuf == NULL) { - return CRYPT_MEM; - } - - /* RSA decode it */ - x = siglen; - if ((err = ltc_mp.rsa_me(sig, siglen, tmpbuf, &x, PK_PUBLIC, key)) != CRYPT_OK) { - XFREE(tmpbuf); - return err; - } - - /* make sure the output is the right size */ - if (x != siglen) { - XFREE(tmpbuf); - return CRYPT_INVALID_PACKET; - } - - if (padding == LTC_LTC_PKCS_1_PSS) { - /* PSS decode and verify it */ - err = pkcs_1_pss_decode(hash, hashlen, tmpbuf, x, saltlen, hash_idx, modulus_bitlen, stat); - } else { - /* LTC_PKCS #1 v1.5 decode it */ - unsigned char *out; - unsigned long outlen, loid[16]; - int decoded; - ltc_asn1_list digestinfo[2], siginfo[2]; - - /* not all hashes have OIDs... so sad */ - if (hash_descriptor[hash_idx].OIDlen == 0) { - err = CRYPT_INVALID_ARG; - goto bail_2; - } - - /* allocate temp buffer for decoded hash */ - outlen = ((modulus_bitlen >> 3) + (modulus_bitlen & 7 ? 1 : 0)) - 3; - out = XMALLOC(outlen); - if (out == NULL) { - err = CRYPT_MEM; - goto bail_2; - } - - if ((err = pkcs_1_v1_5_decode(tmpbuf, x, LTC_LTC_PKCS_1_EMSA, modulus_bitlen, out, &outlen, &decoded)) != CRYPT_OK) { - XFREE(out); - goto bail_2; - } - - /* now we must decode out[0...outlen-1] using ASN.1, test the OID and then test the hash */ - /* construct the SEQUENCE - SEQUENCE { - SEQUENCE {hashoid OID - blah NULL - } - hash OCTET STRING - } - */ - LTC_SET_ASN1(digestinfo, 0, LTC_ASN1_OBJECT_IDENTIFIER, loid, sizeof(loid)/sizeof(loid[0])); - LTC_SET_ASN1(digestinfo, 1, LTC_ASN1_NULL, NULL, 0); - LTC_SET_ASN1(siginfo, 0, LTC_ASN1_SEQUENCE, digestinfo, 2); - LTC_SET_ASN1(siginfo, 1, LTC_ASN1_OCTET_STRING, tmpbuf, siglen); - - if ((err = der_decode_sequence(out, outlen, siginfo, 2)) != CRYPT_OK) { - XFREE(out); - goto bail_2; - } - - /* test OID */ - if ((digestinfo[0].size == hash_descriptor[hash_idx].OIDlen) && - (XMEMCMP(digestinfo[0].data, hash_descriptor[hash_idx].OID, sizeof(unsigned long) * hash_descriptor[hash_idx].OIDlen) == 0) && - (siginfo[1].size == hashlen) && - (XMEMCMP(siginfo[1].data, hash, hashlen) == 0)) { - *stat = 1; - } - -#ifdef LTC_CLEAN_STACK - zeromem(out, outlen); -#endif - XFREE(out); - } - -bail_2: -#ifdef LTC_CLEAN_STACK - zeromem(tmpbuf, siglen); -#endif - XFREE(tmpbuf); - return err; -} - -#endif /* LTC_MRSA */ - -/* $Source: /cvs/libtom/libtomcrypt/src/pk/rsa/rsa_verify_hash.c,v $ */ -/* $Revision: 1.13 $ */ -/* $Date: 2007/05/12 14:32:35 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/rsa/rsa_verify_simple.c b/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/rsa/rsa_verify_simple.c deleted file mode 100644 index 6d8888c..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtomcrypt/src/pk/rsa/rsa_verify_simple.c +++ /dev/null @@ -1,87 +0,0 @@ -/* LibTomCrypt, modular cryptographic library -- Tom St Denis - * - * LibTomCrypt is a library that provides various cryptographic - * algorithms in a highly modular and flexible manner. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include "../../headers/tomcrypt.h" - -/** - @file rsa_verify_simple.c - Created by Ladislav Zezula (zezula@volny.cz) as modification - for Blizzard strong signature verification -*/ - -#ifdef LTC_MRSA - -/** - Simple RSA decryption - @param sig The signature data - @param siglen The length of the signature data (octets) - @param hash The hash of the message that was signed - @param hashlen The length of the hash of the message that was signed (octets) - @param stat [out] The result of the signature comparison, 1==valid, 0==invalid - @param key The public RSA key corresponding - @return Error code -*/ -int rsa_verify_simple(const unsigned char *sig, unsigned long siglen, - const unsigned char *hash, unsigned long hashlen, - int *stat, - rsa_key *key) -{ - unsigned long modulus_bitlen, modulus_bytelen, x; - unsigned char *tmpbuf; - int err; - - LTC_ARGCHK(sig != NULL); - LTC_ARGCHK(hash != NULL); - LTC_ARGCHK(stat != NULL); - LTC_ARGCHK(key != NULL); - - /* default to invalid */ - *stat = 0; - - /* get modulus len in bits */ - modulus_bitlen = mp_count_bits( (key->N)); - - /* outlen must be at least the size of the modulus */ - modulus_bytelen = mp_unsigned_bin_size( (key->N)); - if (modulus_bytelen != siglen) { - return CRYPT_INVALID_PACKET; - } - - /* allocate temp buffer for decoded sig */ - tmpbuf = XMALLOC(siglen); - if (tmpbuf == NULL) { - return CRYPT_MEM; - } - - /* RSA decode it */ - x = siglen; - if ((err = ltc_mp.rsa_me(sig, siglen, tmpbuf, &x, PK_PUBLIC, key)) != CRYPT_OK) { - XFREE(tmpbuf); - return err; - } - - /* make sure the output is the right size */ - if (x != siglen) { - XFREE(tmpbuf); - return CRYPT_INVALID_PACKET; - } - - /* compare the decrypted signature with the given hash */ - if(x == hashlen && XMEMCMP(tmpbuf, hash, hashlen) == 0) - *stat = 1; - -#ifdef LTC_CLEAN_STACK - zeromem(tmpbuf, siglen); -#endif - XFREE(tmpbuf); - return CRYPT_OK; -} - -#endif /* LTC_MRSA */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_fast_mp_invmod.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_fast_mp_invmod.c deleted file mode 100644 index 597d7a9..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_fast_mp_invmod.c +++ /dev/null @@ -1,148 +0,0 @@ -#include "tommath.h" -#ifdef BN_FAST_MP_INVMOD_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* computes the modular inverse via binary extended euclidean algorithm, - * that is c = 1/a mod b - * - * Based on slow invmod except this is optimized for the case where b is - * odd as per HAC Note 14.64 on pp. 610 - */ -int fast_mp_invmod (mp_int * a, mp_int * b, mp_int * c) -{ - mp_int x, y, u, v, B, D; - int res, neg; - - /* 2. [modified] b must be odd */ - if (mp_iseven (b) == 1) { - return MP_VAL; - } - - /* init all our temps */ - if ((res = mp_init_multi(&x, &y, &u, &v, &B, &D, NULL)) != MP_OKAY) { - return res; - } - - /* x == modulus, y == value to invert */ - if ((res = mp_copy (b, &x)) != MP_OKAY) { - goto LBL_ERR; - } - - /* we need y = |a| */ - if ((res = mp_mod (a, b, &y)) != MP_OKAY) { - goto LBL_ERR; - } - - /* 3. u=x, v=y, A=1, B=0, C=0,D=1 */ - if ((res = mp_copy (&x, &u)) != MP_OKAY) { - goto LBL_ERR; - } - if ((res = mp_copy (&y, &v)) != MP_OKAY) { - goto LBL_ERR; - } - mp_set (&D, 1); - -top: - /* 4. while u is even do */ - while (mp_iseven (&u) == 1) { - /* 4.1 u = u/2 */ - if ((res = mp_div_2 (&u, &u)) != MP_OKAY) { - goto LBL_ERR; - } - /* 4.2 if B is odd then */ - if (mp_isodd (&B) == 1) { - if ((res = mp_sub (&B, &x, &B)) != MP_OKAY) { - goto LBL_ERR; - } - } - /* B = B/2 */ - if ((res = mp_div_2 (&B, &B)) != MP_OKAY) { - goto LBL_ERR; - } - } - - /* 5. while v is even do */ - while (mp_iseven (&v) == 1) { - /* 5.1 v = v/2 */ - if ((res = mp_div_2 (&v, &v)) != MP_OKAY) { - goto LBL_ERR; - } - /* 5.2 if D is odd then */ - if (mp_isodd (&D) == 1) { - /* D = (D-x)/2 */ - if ((res = mp_sub (&D, &x, &D)) != MP_OKAY) { - goto LBL_ERR; - } - } - /* D = D/2 */ - if ((res = mp_div_2 (&D, &D)) != MP_OKAY) { - goto LBL_ERR; - } - } - - /* 6. if u >= v then */ - if (mp_cmp (&u, &v) != MP_LT) { - /* u = u - v, B = B - D */ - if ((res = mp_sub (&u, &v, &u)) != MP_OKAY) { - goto LBL_ERR; - } - - if ((res = mp_sub (&B, &D, &B)) != MP_OKAY) { - goto LBL_ERR; - } - } else { - /* v - v - u, D = D - B */ - if ((res = mp_sub (&v, &u, &v)) != MP_OKAY) { - goto LBL_ERR; - } - - if ((res = mp_sub (&D, &B, &D)) != MP_OKAY) { - goto LBL_ERR; - } - } - - /* if not zero goto step 4 */ - if (mp_iszero (&u) == 0) { - goto top; - } - - /* now a = C, b = D, gcd == g*v */ - - /* if v != 1 then there is no inverse */ - if (mp_cmp_d (&v, 1) != MP_EQ) { - res = MP_VAL; - goto LBL_ERR; - } - - /* b is now the inverse */ - neg = a->sign; - while (D.sign == MP_NEG) { - if ((res = mp_add (&D, b, &D)) != MP_OKAY) { - goto LBL_ERR; - } - } - mp_exch (&D, c); - c->sign = neg; - res = MP_OKAY; - -LBL_ERR:mp_clear_multi (&x, &y, &u, &v, &B, &D, NULL); - return res; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_fast_mp_invmod.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_fast_mp_montgomery_reduce.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_fast_mp_montgomery_reduce.c deleted file mode 100644 index 65eed7d..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_fast_mp_montgomery_reduce.c +++ /dev/null @@ -1,172 +0,0 @@ -#include "tommath.h" -#ifdef BN_FAST_MP_MONTGOMERY_REDUCE_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* computes xR**-1 == x (mod N) via Montgomery Reduction - * - * This is an optimized implementation of montgomery_reduce - * which uses the comba method to quickly calculate the columns of the - * reduction. - * - * Based on Algorithm 14.32 on pp.601 of HAC. -*/ -int fast_mp_montgomery_reduce (mp_int * x, mp_int * n, mp_digit rho) -{ - int ix, res, olduse; - mp_word W[MP_WARRAY]; - - /* get old used count */ - olduse = x->used; - - /* grow a as required */ - if (x->alloc < n->used + 1) { - if ((res = mp_grow (x, n->used + 1)) != MP_OKAY) { - return res; - } - } - - /* first we have to get the digits of the input into - * an array of double precision words W[...] - */ - { - register mp_word *_W; - register mp_digit *tmpx; - - /* alias for the W[] array */ - _W = W; - - /* alias for the digits of x*/ - tmpx = x->dp; - - /* copy the digits of a into W[0..a->used-1] */ - for (ix = 0; ix < x->used; ix++) { - *_W++ = *tmpx++; - } - - /* zero the high words of W[a->used..m->used*2] */ - for (; ix < n->used * 2 + 1; ix++) { - *_W++ = 0; - } - } - - /* now we proceed to zero successive digits - * from the least significant upwards - */ - for (ix = 0; ix < n->used; ix++) { - /* mu = ai * m' mod b - * - * We avoid a double precision multiplication (which isn't required) - * by casting the value down to a mp_digit. Note this requires - * that W[ix-1] have the carry cleared (see after the inner loop) - */ - register mp_digit mu; - mu = (mp_digit) (((W[ix] & MP_MASK) * rho) & MP_MASK); - - /* a = a + mu * m * b**i - * - * This is computed in place and on the fly. The multiplication - * by b**i is handled by offseting which columns the results - * are added to. - * - * Note the comba method normally doesn't handle carries in the - * inner loop In this case we fix the carry from the previous - * column since the Montgomery reduction requires digits of the - * result (so far) [see above] to work. This is - * handled by fixing up one carry after the inner loop. The - * carry fixups are done in order so after these loops the - * first m->used words of W[] have the carries fixed - */ - { - register int iy; - register mp_digit *tmpn; - register mp_word *_W; - - /* alias for the digits of the modulus */ - tmpn = n->dp; - - /* Alias for the columns set by an offset of ix */ - _W = W + ix; - - /* inner loop */ - for (iy = 0; iy < n->used; iy++) { - *_W++ += ((mp_word)mu) * ((mp_word)*tmpn++); - } - } - - /* now fix carry for next digit, W[ix+1] */ - W[ix + 1] += W[ix] >> ((mp_word) DIGIT_BIT); - } - - /* now we have to propagate the carries and - * shift the words downward [all those least - * significant digits we zeroed]. - */ - { - register mp_digit *tmpx; - register mp_word *_W, *_W1; - - /* nox fix rest of carries */ - - /* alias for current word */ - _W1 = W + ix; - - /* alias for next word, where the carry goes */ - _W = W + ++ix; - - for (; ix <= n->used * 2 + 1; ix++) { - *_W++ += *_W1++ >> ((mp_word) DIGIT_BIT); - } - - /* copy out, A = A/b**n - * - * The result is A/b**n but instead of converting from an - * array of mp_word to mp_digit than calling mp_rshd - * we just copy them in the right order - */ - - /* alias for destination word */ - tmpx = x->dp; - - /* alias for shifted double precision result */ - _W = W + n->used; - - for (ix = 0; ix < n->used + 1; ix++) { - *tmpx++ = (mp_digit)(*_W++ & ((mp_word) MP_MASK)); - } - - /* zero oldused digits, if the input a was larger than - * m->used+1 we'll have to clear the digits - */ - for (; ix < olduse; ix++) { - *tmpx++ = 0; - } - } - - /* set the max used and clamp */ - x->used = n->used + 1; - mp_clamp (x); - - /* if A >= m then A = A - m */ - if (mp_cmp_mag (x, n) != MP_LT) { - return s_mp_sub (x, n, x); - } - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_fast_mp_montgomery_reduce.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_fast_s_mp_mul_digs.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_fast_s_mp_mul_digs.c deleted file mode 100644 index df83f89..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_fast_s_mp_mul_digs.c +++ /dev/null @@ -1,107 +0,0 @@ -#include "tommath.h" -#ifdef BN_FAST_S_MP_MUL_DIGS_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* Fast (comba) multiplier - * - * This is the fast column-array [comba] multiplier. It is - * designed to compute the columns of the product first - * then handle the carries afterwards. This has the effect - * of making the nested loops that compute the columns very - * simple and schedulable on super-scalar processors. - * - * This has been modified to produce a variable number of - * digits of output so if say only a half-product is required - * you don't have to compute the upper half (a feature - * required for fast Barrett reduction). - * - * Based on Algorithm 14.12 on pp.595 of HAC. - * - */ -int fast_s_mp_mul_digs (mp_int * a, mp_int * b, mp_int * c, int digs) -{ - int olduse, res, pa, ix, iz; - mp_digit W[MP_WARRAY]; - register mp_word _W; - - /* grow the destination as required */ - if (c->alloc < digs) { - if ((res = mp_grow (c, digs)) != MP_OKAY) { - return res; - } - } - - /* number of output digits to produce */ - pa = MIN(digs, a->used + b->used); - - /* clear the carry */ - _W = 0; - for (ix = 0; ix < pa; ix++) { - int tx, ty; - int iy; - mp_digit *tmpx, *tmpy; - - /* get offsets into the two bignums */ - ty = MIN(b->used-1, ix); - tx = ix - ty; - - /* setup temp aliases */ - tmpx = a->dp + tx; - tmpy = b->dp + ty; - - /* this is the number of times the loop will iterrate, essentially - while (tx++ < a->used && ty-- >= 0) { ... } - */ - iy = MIN(a->used-tx, ty+1); - - /* execute loop */ - for (iz = 0; iz < iy; ++iz) { - _W += ((mp_word)*tmpx++)*((mp_word)*tmpy--); - - } - - /* store term */ - W[ix] = ((mp_digit)_W) & MP_MASK; - - /* make next carry */ - _W = _W >> ((mp_word)DIGIT_BIT); - } - - /* setup dest */ - olduse = c->used; - c->used = pa; - - { - register mp_digit *tmpc; - tmpc = c->dp; - for (ix = 0; ix < pa+1; ix++) { - /* now extract the previous digit [below the carry] */ - *tmpc++ = W[ix]; - } - - /* clear unused digits [that existed in the old copy of c] */ - for (; ix < olduse; ix++) { - *tmpc++ = 0; - } - } - mp_clamp (c); - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_fast_s_mp_mul_digs.c,v $ */ -/* $Revision: 1.8 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_fast_s_mp_mul_high_digs.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_fast_s_mp_mul_high_digs.c deleted file mode 100644 index 6866aab..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_fast_s_mp_mul_high_digs.c +++ /dev/null @@ -1,98 +0,0 @@ -#include "tommath.h" -#ifdef BN_FAST_S_MP_MUL_HIGH_DIGS_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* this is a modified version of fast_s_mul_digs that only produces - * output digits *above* digs. See the comments for fast_s_mul_digs - * to see how it works. - * - * This is used in the Barrett reduction since for one of the multiplications - * only the higher digits were needed. This essentially halves the work. - * - * Based on Algorithm 14.12 on pp.595 of HAC. - */ -int fast_s_mp_mul_high_digs (mp_int * a, mp_int * b, mp_int * c, int digs) -{ - int olduse, res, pa, ix, iz; - mp_digit W[MP_WARRAY]; - mp_word _W; - - /* grow the destination as required */ - pa = a->used + b->used; - if (c->alloc < pa) { - if ((res = mp_grow (c, pa)) != MP_OKAY) { - return res; - } - } - - /* number of output digits to produce */ - pa = a->used + b->used; - _W = 0; - for (ix = digs; ix < pa; ix++) { - int tx, ty, iy; - mp_digit *tmpx, *tmpy; - - /* get offsets into the two bignums */ - ty = MIN(b->used-1, ix); - tx = ix - ty; - - /* setup temp aliases */ - tmpx = a->dp + tx; - tmpy = b->dp + ty; - - /* this is the number of times the loop will iterrate, essentially its - while (tx++ < a->used && ty-- >= 0) { ... } - */ - iy = MIN(a->used-tx, ty+1); - - /* execute loop */ - for (iz = 0; iz < iy; iz++) { - _W += ((mp_word)*tmpx++)*((mp_word)*tmpy--); - } - - /* store term */ - W[ix] = ((mp_digit)_W) & MP_MASK; - - /* make next carry */ - _W = _W >> ((mp_word)DIGIT_BIT); - } - - /* setup dest */ - olduse = c->used; - c->used = pa; - - { - register mp_digit *tmpc; - - tmpc = c->dp + digs; - for (ix = digs; ix < pa; ix++) { - /* now extract the previous digit [below the carry] */ - *tmpc++ = W[ix]; - } - - /* clear unused digits [that existed in the old copy of c] */ - for (; ix < olduse; ix++) { - *tmpc++ = 0; - } - } - mp_clamp (c); - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_fast_s_mp_mul_high_digs.c,v $ */ -/* $Revision: 1.6 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_fast_s_mp_sqr.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_fast_s_mp_sqr.c deleted file mode 100644 index 5f9d58c..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_fast_s_mp_sqr.c +++ /dev/null @@ -1,114 +0,0 @@ -#include "tommath.h" -#ifdef BN_FAST_S_MP_SQR_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* the jist of squaring... - * you do like mult except the offset of the tmpx [one that - * starts closer to zero] can't equal the offset of tmpy. - * So basically you set up iy like before then you min it with - * (ty-tx) so that it never happens. You double all those - * you add in the inner loop - -After that loop you do the squares and add them in. -*/ - -int fast_s_mp_sqr (mp_int * a, mp_int * b) -{ - int olduse, res, pa, ix, iz; - mp_digit W[MP_WARRAY], *tmpx; - mp_word W1; - - /* grow the destination as required */ - pa = a->used + a->used; - if (b->alloc < pa) { - if ((res = mp_grow (b, pa)) != MP_OKAY) { - return res; - } - } - - /* number of output digits to produce */ - W1 = 0; - for (ix = 0; ix < pa; ix++) { - int tx, ty, iy; - mp_word _W; - mp_digit *tmpy; - - /* clear counter */ - _W = 0; - - /* get offsets into the two bignums */ - ty = MIN(a->used-1, ix); - tx = ix - ty; - - /* setup temp aliases */ - tmpx = a->dp + tx; - tmpy = a->dp + ty; - - /* this is the number of times the loop will iterrate, essentially - while (tx++ < a->used && ty-- >= 0) { ... } - */ - iy = MIN(a->used-tx, ty+1); - - /* now for squaring tx can never equal ty - * we halve the distance since they approach at a rate of 2x - * and we have to round because odd cases need to be executed - */ - iy = MIN(iy, (ty-tx+1)>>1); - - /* execute loop */ - for (iz = 0; iz < iy; iz++) { - _W += ((mp_word)*tmpx++)*((mp_word)*tmpy--); - } - - /* double the inner product and add carry */ - _W = _W + _W + W1; - - /* even columns have the square term in them */ - if ((ix&1) == 0) { - _W += ((mp_word)a->dp[ix>>1])*((mp_word)a->dp[ix>>1]); - } - - /* store it */ - W[ix] = (mp_digit)(_W & MP_MASK); - - /* make next carry */ - W1 = _W >> ((mp_word)DIGIT_BIT); - } - - /* setup dest */ - olduse = b->used; - b->used = a->used+a->used; - - { - mp_digit *tmpb; - tmpb = b->dp; - for (ix = 0; ix < pa; ix++) { - *tmpb++ = W[ix] & MP_MASK; - } - - /* clear unused digits [that existed in the old copy of c] */ - for (; ix < olduse; ix++) { - *tmpb++ = 0; - } - } - mp_clamp (b); - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_fast_s_mp_sqr.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_2expt.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_2expt.c deleted file mode 100644 index f899eae..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_2expt.c +++ /dev/null @@ -1,48 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_2EXPT_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* computes a = 2**b - * - * Simple algorithm which zeroes the int, grows it then just sets one bit - * as required. - */ -int -mp_2expt (mp_int * a, int b) -{ - int res; - - /* zero a as per default */ - mp_zero (a); - - /* grow a to accomodate the single bit */ - if ((res = mp_grow (a, b / DIGIT_BIT + 1)) != MP_OKAY) { - return res; - } - - /* set the used count of where the bit will go */ - a->used = b / DIGIT_BIT + 1; - - /* put the single bit in its place */ - a->dp[b / DIGIT_BIT] = ((mp_digit)1) << (b % DIGIT_BIT); - - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_2expt.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_abs.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_abs.c deleted file mode 100644 index 14f3a7e..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_abs.c +++ /dev/null @@ -1,43 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_ABS_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* b = |a| - * - * Simple function copies the input and fixes the sign to positive - */ -int -mp_abs (mp_int * a, mp_int * b) -{ - int res; - - /* copy a to b */ - if (a != b) { - if ((res = mp_copy (a, b)) != MP_OKAY) { - return res; - } - } - - /* force the sign of b to positive */ - b->sign = MP_ZPOS; - - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_abs.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_add.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_add.c deleted file mode 100644 index b368b21..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_add.c +++ /dev/null @@ -1,53 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_ADD_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* high level addition (handles signs) */ -int mp_add (mp_int * a, mp_int * b, mp_int * c) -{ - int sa, sb, res; - - /* get sign of both inputs */ - sa = a->sign; - sb = b->sign; - - /* handle two cases, not four */ - if (sa == sb) { - /* both positive or both negative */ - /* add their magnitudes, copy the sign */ - c->sign = sa; - res = s_mp_add (a, b, c); - } else { - /* one positive, the other negative */ - /* subtract the one with the greater magnitude from */ - /* the one of the lesser magnitude. The result gets */ - /* the sign of the one with the greater magnitude. */ - if (mp_cmp_mag (a, b) == MP_LT) { - c->sign = sb; - res = s_mp_sub (b, a, c); - } else { - c->sign = sa; - res = s_mp_sub (a, b, c); - } - } - return res; -} - -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_add.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_add_d.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_add_d.c deleted file mode 100644 index c147554..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_add_d.c +++ /dev/null @@ -1,112 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_ADD_D_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* single digit addition */ -int -mp_add_d (mp_int * a, mp_digit b, mp_int * c) -{ - int res, ix, oldused; - mp_digit *tmpa, *tmpc, mu; - - /* grow c as required */ - if (c->alloc < a->used + 1) { - if ((res = mp_grow(c, a->used + 1)) != MP_OKAY) { - return res; - } - } - - /* if a is negative and |a| >= b, call c = |a| - b */ - if (a->sign == MP_NEG && (a->used > 1 || a->dp[0] >= b)) { - /* temporarily fix sign of a */ - a->sign = MP_ZPOS; - - /* c = |a| - b */ - res = mp_sub_d(a, b, c); - - /* fix sign */ - a->sign = c->sign = MP_NEG; - - /* clamp */ - mp_clamp(c); - - return res; - } - - /* old number of used digits in c */ - oldused = c->used; - - /* sign always positive */ - c->sign = MP_ZPOS; - - /* source alias */ - tmpa = a->dp; - - /* destination alias */ - tmpc = c->dp; - - /* if a is positive */ - if (a->sign == MP_ZPOS) { - /* add digit, after this we're propagating - * the carry. - */ - *tmpc = *tmpa++ + b; - mu = *tmpc >> DIGIT_BIT; - *tmpc++ &= MP_MASK; - - /* now handle rest of the digits */ - for (ix = 1; ix < a->used; ix++) { - *tmpc = *tmpa++ + mu; - mu = *tmpc >> DIGIT_BIT; - *tmpc++ &= MP_MASK; - } - /* set final carry */ - ix++; - *tmpc++ = mu; - - /* setup size */ - c->used = a->used + 1; - } else { - /* a was negative and |a| < b */ - c->used = 1; - - /* the result is a single digit */ - if (a->used == 1) { - *tmpc++ = b - a->dp[0]; - } else { - *tmpc++ = b; - } - - /* setup count so the clearing of oldused - * can fall through correctly - */ - ix = 1; - } - - /* now zero to oldused */ - while (ix++ < oldused) { - *tmpc++ = 0; - } - mp_clamp(c); - - return MP_OKAY; -} - -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_add_d.c,v $ */ -/* $Revision: 1.5 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_addmod.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_addmod.c deleted file mode 100644 index 0a21f62..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_addmod.c +++ /dev/null @@ -1,41 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_ADDMOD_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* d = a + b (mod c) */ -int -mp_addmod (mp_int * a, mp_int * b, mp_int * c, mp_int * d) -{ - int res; - mp_int t; - - if ((res = mp_init (&t)) != MP_OKAY) { - return res; - } - - if ((res = mp_add (a, b, &t)) != MP_OKAY) { - mp_clear (&t); - return res; - } - res = mp_mod (&t, c, d); - mp_clear (&t); - return res; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_addmod.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_and.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_and.c deleted file mode 100644 index 6b7afc1..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_and.c +++ /dev/null @@ -1,57 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_AND_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* AND two ints together */ -int -mp_and (mp_int * a, mp_int * b, mp_int * c) -{ - int res, ix, px; - mp_int t, *x; - - if (a->used > b->used) { - if ((res = mp_init_copy (&t, a)) != MP_OKAY) { - return res; - } - px = b->used; - x = b; - } else { - if ((res = mp_init_copy (&t, b)) != MP_OKAY) { - return res; - } - px = a->used; - x = a; - } - - for (ix = 0; ix < px; ix++) { - t.dp[ix] &= x->dp[ix]; - } - - /* zero digits above the last from the smallest mp_int */ - for (; ix < t.used; ix++) { - t.dp[ix] = 0; - } - - mp_clamp (&t); - mp_exch (c, &t); - mp_clear (&t); - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_and.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_clamp.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_clamp.c deleted file mode 100644 index d3cc21c..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_clamp.c +++ /dev/null @@ -1,44 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_CLAMP_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* trim unused digits - * - * This is used to ensure that leading zero digits are - * trimed and the leading "used" digit will be non-zero - * Typically very fast. Also fixes the sign if there - * are no more leading digits - */ -void -mp_clamp (mp_int * a) -{ - /* decrease used while the most significant digit is - * zero. - */ - while (a->used > 0 && a->dp[a->used - 1] == 0) { - --(a->used); - } - - /* reset the sign flag if used == 0 */ - if (a->used == 0) { - a->sign = MP_ZPOS; - } -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_clamp.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_clear.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_clear.c deleted file mode 100644 index 7644c38..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_clear.c +++ /dev/null @@ -1,44 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_CLEAR_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* clear one (frees) */ -void -mp_clear (mp_int * a) -{ - int i; - - /* only do anything if a hasn't been freed previously */ - if (a->dp != NULL) { - /* first zero the digits */ - for (i = 0; i < a->used; i++) { - a->dp[i] = 0; - } - - /* free ram */ - XFREE(a->dp); - - /* reset members to make debugging easier */ - a->dp = NULL; - a->alloc = a->used = 0; - a->sign = MP_ZPOS; - } -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_clear.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_clear_multi.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_clear_multi.c deleted file mode 100644 index a107624..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_clear_multi.c +++ /dev/null @@ -1,34 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_CLEAR_MULTI_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include - -void mp_clear_multi(mp_int *mp, ...) -{ - mp_int* next_mp = mp; - va_list args; - va_start(args, mp); - while (next_mp != NULL) { - mp_clear(next_mp); - next_mp = va_arg(args, mp_int*); - } - va_end(args); -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_clear_multi.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_cmp.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_cmp.c deleted file mode 100644 index 761d2b0..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_cmp.c +++ /dev/null @@ -1,43 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_CMP_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* compare two ints (signed)*/ -int -mp_cmp (mp_int * a, mp_int * b) -{ - /* compare based on sign */ - if (a->sign != b->sign) { - if (a->sign == MP_NEG) { - return MP_LT; - } else { - return MP_GT; - } - } - - /* compare digits */ - if (a->sign == MP_NEG) { - /* if negative compare opposite direction */ - return mp_cmp_mag(b, a); - } else { - return mp_cmp_mag(a, b); - } -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_cmp.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_cmp_d.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_cmp_d.c deleted file mode 100644 index 420dfd3..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_cmp_d.c +++ /dev/null @@ -1,44 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_CMP_D_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* compare a digit */ -int mp_cmp_d(mp_int * a, mp_digit b) -{ - /* compare based on sign */ - if (a->sign == MP_NEG) { - return MP_LT; - } - - /* compare based on magnitude */ - if (a->used > 1) { - return MP_GT; - } - - /* compare the only digit of a to b */ - if (a->dp[0] > b) { - return MP_GT; - } else if (a->dp[0] < b) { - return MP_LT; - } else { - return MP_EQ; - } -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_cmp_d.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_cmp_mag.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_cmp_mag.c deleted file mode 100644 index 92565a3..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_cmp_mag.c +++ /dev/null @@ -1,55 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_CMP_MAG_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* compare maginitude of two ints (unsigned) */ -int mp_cmp_mag (mp_int * a, mp_int * b) -{ - int n; - mp_digit *tmpa, *tmpb; - - /* compare based on # of non-zero digits */ - if (a->used > b->used) { - return MP_GT; - } - - if (a->used < b->used) { - return MP_LT; - } - - /* alias for a */ - tmpa = a->dp + (a->used - 1); - - /* alias for b */ - tmpb = b->dp + (a->used - 1); - - /* compare based on digits */ - for (n = 0; n < a->used; ++n, --tmpa, --tmpb) { - if (*tmpa > *tmpb) { - return MP_GT; - } - - if (*tmpa < *tmpb) { - return MP_LT; - } - } - return MP_EQ; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_cmp_mag.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_cnt_lsb.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_cnt_lsb.c deleted file mode 100644 index 6040661..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_cnt_lsb.c +++ /dev/null @@ -1,53 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_CNT_LSB_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -static const int lnz[16] = { - 4, 0, 1, 0, 2, 0, 1, 0, 3, 0, 1, 0, 2, 0, 1, 0 -}; - -/* Counts the number of lsbs which are zero before the first zero bit */ -int mp_cnt_lsb(mp_int *a) -{ - int x; - mp_digit q, qq; - - /* easy out */ - if (mp_iszero(a) == 1) { - return 0; - } - - /* scan lower digits until non-zero */ - for (x = 0; x < a->used && a->dp[x] == 0; x++); - q = a->dp[x]; - x *= DIGIT_BIT; - - /* now scan this digit until a 1 is found */ - if ((q & 1) == 0) { - do { - qq = q & 15; - x += lnz[qq]; - q >>= 4; - } while (qq == 0); - } - return x; -} - -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_cnt_lsb.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_copy.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_copy.c deleted file mode 100644 index 7828592..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_copy.c +++ /dev/null @@ -1,68 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_COPY_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* copy, b = a */ -int -mp_copy (mp_int * a, mp_int * b) -{ - int res, n; - - /* if dst == src do nothing */ - if (a == b) { - return MP_OKAY; - } - - /* grow dest */ - if (b->alloc < a->used) { - if ((res = mp_grow (b, a->used)) != MP_OKAY) { - return res; - } - } - - /* zero b and copy the parameters over */ - { - register mp_digit *tmpa, *tmpb; - - /* pointer aliases */ - - /* source */ - tmpa = a->dp; - - /* destination */ - tmpb = b->dp; - - /* copy all the digits */ - for (n = 0; n < a->used; n++) { - *tmpb++ = *tmpa++; - } - - /* clear high digits */ - for (; n < b->used; n++) { - *tmpb++ = 0; - } - } - - /* copy used count and sign */ - b->used = a->used; - b->sign = a->sign; - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_copy.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_count_bits.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_count_bits.c deleted file mode 100644 index 9d8640f..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_count_bits.c +++ /dev/null @@ -1,45 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_COUNT_BITS_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* returns the number of bits in an int */ -int -mp_count_bits (mp_int * a) -{ - int r; - mp_digit q; - - /* shortcut */ - if (a->used == 0) { - return 0; - } - - /* get number of digits and add that */ - r = (a->used - 1) * DIGIT_BIT; - - /* take the last digit and count the bits in it */ - q = a->dp[a->used - 1]; - while (q > ((mp_digit) 0)) { - ++r; - q >>= ((mp_digit) 1); - } - return r; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_count_bits.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_div.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_div.c deleted file mode 100644 index 3004a3e..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_div.c +++ /dev/null @@ -1,292 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_DIV_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -#ifdef BN_MP_DIV_SMALL - -/* slower bit-bang division... also smaller */ -int mp_div(mp_int * a, mp_int * b, mp_int * c, mp_int * d) -{ - mp_int ta, tb, tq, q; - int res, n, n2; - - /* is divisor zero ? */ - if (mp_iszero (b) == 1) { - return MP_VAL; - } - - /* if a < b then q=0, r = a */ - if (mp_cmp_mag (a, b) == MP_LT) { - if (d != NULL) { - res = mp_copy (a, d); - } else { - res = MP_OKAY; - } - if (c != NULL) { - mp_zero (c); - } - return res; - } - - /* init our temps */ - if ((res = mp_init_multi(&ta, &tb, &tq, &q, NULL) != MP_OKAY)) { - return res; - } - - - mp_set(&tq, 1); - n = mp_count_bits(a) - mp_count_bits(b); - if (((res = mp_abs(a, &ta)) != MP_OKAY) || - ((res = mp_abs(b, &tb)) != MP_OKAY) || - ((res = mp_mul_2d(&tb, n, &tb)) != MP_OKAY) || - ((res = mp_mul_2d(&tq, n, &tq)) != MP_OKAY)) { - goto LBL_ERR; - } - - while (n-- >= 0) { - if (mp_cmp(&tb, &ta) != MP_GT) { - if (((res = mp_sub(&ta, &tb, &ta)) != MP_OKAY) || - ((res = mp_add(&q, &tq, &q)) != MP_OKAY)) { - goto LBL_ERR; - } - } - if (((res = mp_div_2d(&tb, 1, &tb, NULL)) != MP_OKAY) || - ((res = mp_div_2d(&tq, 1, &tq, NULL)) != MP_OKAY)) { - goto LBL_ERR; - } - } - - /* now q == quotient and ta == remainder */ - n = a->sign; - n2 = (a->sign == b->sign ? MP_ZPOS : MP_NEG); - if (c != NULL) { - mp_exch(c, &q); - c->sign = (mp_iszero(c) == MP_YES) ? MP_ZPOS : n2; - } - if (d != NULL) { - mp_exch(d, &ta); - d->sign = (mp_iszero(d) == MP_YES) ? MP_ZPOS : n; - } -LBL_ERR: - mp_clear_multi(&ta, &tb, &tq, &q, NULL); - return res; -} - -#else - -/* integer signed division. - * c*b + d == a [e.g. a/b, c=quotient, d=remainder] - * HAC pp.598 Algorithm 14.20 - * - * Note that the description in HAC is horribly - * incomplete. For example, it doesn't consider - * the case where digits are removed from 'x' in - * the inner loop. It also doesn't consider the - * case that y has fewer than three digits, etc.. - * - * The overall algorithm is as described as - * 14.20 from HAC but fixed to treat these cases. -*/ -int mp_div (mp_int * a, mp_int * b, mp_int * c, mp_int * d) -{ - mp_int q, x, y, t1, t2; - int res, n, t, i, norm, neg; - - /* is divisor zero ? */ - if (mp_iszero (b) == 1) { - return MP_VAL; - } - - /* if a < b then q=0, r = a */ - if (mp_cmp_mag (a, b) == MP_LT) { - if (d != NULL) { - res = mp_copy (a, d); - } else { - res = MP_OKAY; - } - if (c != NULL) { - mp_zero (c); - } - return res; - } - - if ((res = mp_init_size (&q, a->used + 2)) != MP_OKAY) { - return res; - } - q.used = a->used + 2; - - if ((res = mp_init (&t1)) != MP_OKAY) { - goto LBL_Q; - } - - if ((res = mp_init (&t2)) != MP_OKAY) { - goto LBL_T1; - } - - if ((res = mp_init_copy (&x, a)) != MP_OKAY) { - goto LBL_T2; - } - - if ((res = mp_init_copy (&y, b)) != MP_OKAY) { - goto LBL_X; - } - - /* fix the sign */ - neg = (a->sign == b->sign) ? MP_ZPOS : MP_NEG; - x.sign = y.sign = MP_ZPOS; - - /* normalize both x and y, ensure that y >= b/2, [b == 2**DIGIT_BIT] */ - norm = mp_count_bits(&y) % DIGIT_BIT; - if (norm < (int)(DIGIT_BIT-1)) { - norm = (DIGIT_BIT-1) - norm; - if ((res = mp_mul_2d (&x, norm, &x)) != MP_OKAY) { - goto LBL_Y; - } - if ((res = mp_mul_2d (&y, norm, &y)) != MP_OKAY) { - goto LBL_Y; - } - } else { - norm = 0; - } - - /* note hac does 0 based, so if used==5 then its 0,1,2,3,4, e.g. use 4 */ - n = x.used - 1; - t = y.used - 1; - - /* while (x >= y*b**n-t) do { q[n-t] += 1; x -= y*b**{n-t} } */ - if ((res = mp_lshd (&y, n - t)) != MP_OKAY) { /* y = y*b**{n-t} */ - goto LBL_Y; - } - - while (mp_cmp (&x, &y) != MP_LT) { - ++(q.dp[n - t]); - if ((res = mp_sub (&x, &y, &x)) != MP_OKAY) { - goto LBL_Y; - } - } - - /* reset y by shifting it back down */ - mp_rshd (&y, n - t); - - /* step 3. for i from n down to (t + 1) */ - for (i = n; i >= (t + 1); i--) { - if (i > x.used) { - continue; - } - - /* step 3.1 if xi == yt then set q{i-t-1} to b-1, - * otherwise set q{i-t-1} to (xi*b + x{i-1})/yt */ - if (x.dp[i] == y.dp[t]) { - q.dp[i - t - 1] = ((((mp_digit)1) << DIGIT_BIT) - 1); - } else { - mp_word tmp; - tmp = ((mp_word) x.dp[i]) << ((mp_word) DIGIT_BIT); - tmp |= ((mp_word) x.dp[i - 1]); - tmp /= ((mp_word) y.dp[t]); - if (tmp > (mp_word) MP_MASK) - tmp = MP_MASK; - q.dp[i - t - 1] = (mp_digit) (tmp & (mp_word) (MP_MASK)); - } - - /* while (q{i-t-1} * (yt * b + y{t-1})) > - xi * b**2 + xi-1 * b + xi-2 - - do q{i-t-1} -= 1; - */ - q.dp[i - t - 1] = (q.dp[i - t - 1] + 1) & MP_MASK; - do { - q.dp[i - t - 1] = (q.dp[i - t - 1] - 1) & MP_MASK; - - /* find left hand */ - mp_zero (&t1); - t1.dp[0] = (t - 1 < 0) ? 0 : y.dp[t - 1]; - t1.dp[1] = y.dp[t]; - t1.used = 2; - if ((res = mp_mul_d (&t1, q.dp[i - t - 1], &t1)) != MP_OKAY) { - goto LBL_Y; - } - - /* find right hand */ - t2.dp[0] = (i - 2 < 0) ? 0 : x.dp[i - 2]; - t2.dp[1] = (i - 1 < 0) ? 0 : x.dp[i - 1]; - t2.dp[2] = x.dp[i]; - t2.used = 3; - } while (mp_cmp_mag(&t1, &t2) == MP_GT); - - /* step 3.3 x = x - q{i-t-1} * y * b**{i-t-1} */ - if ((res = mp_mul_d (&y, q.dp[i - t - 1], &t1)) != MP_OKAY) { - goto LBL_Y; - } - - if ((res = mp_lshd (&t1, i - t - 1)) != MP_OKAY) { - goto LBL_Y; - } - - if ((res = mp_sub (&x, &t1, &x)) != MP_OKAY) { - goto LBL_Y; - } - - /* if x < 0 then { x = x + y*b**{i-t-1}; q{i-t-1} -= 1; } */ - if (x.sign == MP_NEG) { - if ((res = mp_copy (&y, &t1)) != MP_OKAY) { - goto LBL_Y; - } - if ((res = mp_lshd (&t1, i - t - 1)) != MP_OKAY) { - goto LBL_Y; - } - if ((res = mp_add (&x, &t1, &x)) != MP_OKAY) { - goto LBL_Y; - } - - q.dp[i - t - 1] = (q.dp[i - t - 1] - 1UL) & MP_MASK; - } - } - - /* now q is the quotient and x is the remainder - * [which we have to normalize] - */ - - /* get sign before writing to c */ - x.sign = x.used == 0 ? MP_ZPOS : a->sign; - - if (c != NULL) { - mp_clamp (&q); - mp_exch (&q, c); - c->sign = neg; - } - - if (d != NULL) { - mp_div_2d (&x, norm, &x, NULL); - mp_exch (&x, d); - } - - res = MP_OKAY; - -LBL_Y:mp_clear (&y); -LBL_X:mp_clear (&x); -LBL_T2:mp_clear (&t2); -LBL_T1:mp_clear (&t1); -LBL_Q:mp_clear (&q); - return res; -} - -#endif - -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_div.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_div_2.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_div_2.c deleted file mode 100644 index f3b9d16..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_div_2.c +++ /dev/null @@ -1,68 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_DIV_2_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* b = a/2 */ -int mp_div_2(mp_int * a, mp_int * b) -{ - int x, res, oldused; - - /* copy */ - if (b->alloc < a->used) { - if ((res = mp_grow (b, a->used)) != MP_OKAY) { - return res; - } - } - - oldused = b->used; - b->used = a->used; - { - register mp_digit r, rr, *tmpa, *tmpb; - - /* source alias */ - tmpa = a->dp + b->used - 1; - - /* dest alias */ - tmpb = b->dp + b->used - 1; - - /* carry */ - r = 0; - for (x = b->used - 1; x >= 0; x--) { - /* get the carry for the next iteration */ - rr = *tmpa & 1; - - /* shift the current digit, add in carry and store */ - *tmpb-- = (*tmpa-- >> 1) | (r << (DIGIT_BIT - 1)); - - /* forward carry to next iteration */ - r = rr; - } - - /* zero excess digits */ - tmpb = b->dp + b->used; - for (x = b->used; x < oldused; x++) { - *tmpb++ = 0; - } - } - b->sign = a->sign; - mp_clamp (b); - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_div_2.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_div_2d.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_div_2d.c deleted file mode 100644 index 861ea23..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_div_2d.c +++ /dev/null @@ -1,97 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_DIV_2D_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* shift right by a certain bit count (store quotient in c, optional remainder in d) */ -int mp_div_2d (mp_int * a, int b, mp_int * c, mp_int * d) -{ - mp_digit D, r, rr; - int x, res; - mp_int t; - - - /* if the shift count is <= 0 then we do no work */ - if (b <= 0) { - res = mp_copy (a, c); - if (d != NULL) { - mp_zero (d); - } - return res; - } - - if ((res = mp_init (&t)) != MP_OKAY) { - return res; - } - - /* get the remainder */ - if (d != NULL) { - if ((res = mp_mod_2d (a, b, &t)) != MP_OKAY) { - mp_clear (&t); - return res; - } - } - - /* copy */ - if ((res = mp_copy (a, c)) != MP_OKAY) { - mp_clear (&t); - return res; - } - - /* shift by as many digits in the bit count */ - if (b >= (int)DIGIT_BIT) { - mp_rshd (c, b / DIGIT_BIT); - } - - /* shift any bit count < DIGIT_BIT */ - D = (mp_digit) (b % DIGIT_BIT); - if (D != 0) { - register mp_digit *tmpc, mask, shift; - - /* mask */ - mask = (((mp_digit)1) << D) - 1; - - /* shift for lsb */ - shift = DIGIT_BIT - D; - - /* alias */ - tmpc = c->dp + (c->used - 1); - - /* carry */ - r = 0; - for (x = c->used - 1; x >= 0; x--) { - /* get the lower bits of this word in a temp */ - rr = *tmpc & mask; - - /* shift the current word and mix in the carry bits from the previous word */ - *tmpc = (*tmpc >> D) | (r << shift); - --tmpc; - - /* set the carry to the carry bits of the current word found above */ - r = rr; - } - } - mp_clamp (c); - if (d != NULL) { - mp_exch (&t, d); - } - mp_clear (&t); - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_div_2d.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_div_3.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_div_3.c deleted file mode 100644 index 4fc08fc..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_div_3.c +++ /dev/null @@ -1,79 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_DIV_3_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* divide by three (based on routine from MPI and the GMP manual) */ -int -mp_div_3 (mp_int * a, mp_int *c, mp_digit * d) -{ - mp_int q; - mp_word w, t; - mp_digit b; - int res, ix; - - /* b = 2**DIGIT_BIT / 3 */ - b = (((mp_word)1) << ((mp_word)DIGIT_BIT)) / ((mp_word)3); - - if ((res = mp_init_size(&q, a->used)) != MP_OKAY) { - return res; - } - - q.used = a->used; - q.sign = a->sign; - w = 0; - for (ix = a->used - 1; ix >= 0; ix--) { - w = (w << ((mp_word)DIGIT_BIT)) | ((mp_word)a->dp[ix]); - - if (w >= 3) { - /* multiply w by [1/3] */ - t = (w * ((mp_word)b)) >> ((mp_word)DIGIT_BIT); - - /* now subtract 3 * [w/3] from w, to get the remainder */ - w -= t+t+t; - - /* fixup the remainder as required since - * the optimization is not exact. - */ - while (w >= 3) { - t += 1; - w -= 3; - } - } else { - t = 0; - } - q.dp[ix] = (mp_digit)t; - } - - /* [optional] store the remainder */ - if (d != NULL) { - *d = (mp_digit)w; - } - - /* [optional] store the quotient */ - if (c != NULL) { - mp_clamp(&q); - mp_exch(&q, c); - } - mp_clear(&q); - - return res; -} - -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_div_3.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_div_d.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_div_d.c deleted file mode 100644 index c0318a4..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_div_d.c +++ /dev/null @@ -1,115 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_DIV_D_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -static int s_is_power_of_two(mp_digit b, int *p) -{ - int x; - - /* fast return if no power of two */ - if ((b==0) || (b & (b-1))) { - return 0; - } - - for (x = 0; x < DIGIT_BIT; x++) { - if (b == (((mp_digit)1)<dp[0] & ((((mp_digit)1)<used)) != MP_OKAY) { - return res; - } - - q.used = a->used; - q.sign = a->sign; - w = 0; - for (ix = a->used - 1; ix >= 0; ix--) { - w = (w << ((mp_word)DIGIT_BIT)) | ((mp_word)a->dp[ix]); - - if (w >= b) { - t = (mp_digit)(w / b); - w -= ((mp_word)t) * ((mp_word)b); - } else { - t = 0; - } - q.dp[ix] = (mp_digit)t; - } - - if (d != NULL) { - *d = (mp_digit)w; - } - - if (c != NULL) { - mp_clamp(&q); - mp_exch(&q, c); - } - mp_clear(&q); - - return res; -} - -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_div_d.c,v $ */ -/* $Revision: 1.5 $ */ -/* $Date: 2007/01/09 04:44:32 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_dr_is_modulus.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_dr_is_modulus.c deleted file mode 100644 index 22ba5df..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_dr_is_modulus.c +++ /dev/null @@ -1,43 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_DR_IS_MODULUS_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* determines if a number is a valid DR modulus */ -int mp_dr_is_modulus(mp_int *a) -{ - int ix; - - /* must be at least two digits */ - if (a->used < 2) { - return 0; - } - - /* must be of the form b**k - a [a <= b] so all - * but the first digit must be equal to -1 (mod b). - */ - for (ix = 1; ix < a->used; ix++) { - if (a->dp[ix] != MP_MASK) { - return 0; - } - } - return 1; -} - -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_dr_is_modulus.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_dr_reduce.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_dr_reduce.c deleted file mode 100644 index 0afac94..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_dr_reduce.c +++ /dev/null @@ -1,94 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_DR_REDUCE_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* reduce "x" in place modulo "n" using the Diminished Radix algorithm. - * - * Based on algorithm from the paper - * - * "Generating Efficient Primes for Discrete Log Cryptosystems" - * Chae Hoon Lim, Pil Joong Lee, - * POSTECH Information Research Laboratories - * - * The modulus must be of a special format [see manual] - * - * Has been modified to use algorithm 7.10 from the LTM book instead - * - * Input x must be in the range 0 <= x <= (n-1)**2 - */ -int -mp_dr_reduce (mp_int * x, mp_int * n, mp_digit k) -{ - int err, i, m; - mp_word r; - mp_digit mu, *tmpx1, *tmpx2; - - /* m = digits in modulus */ - m = n->used; - - /* ensure that "x" has at least 2m digits */ - if (x->alloc < m + m) { - if ((err = mp_grow (x, m + m)) != MP_OKAY) { - return err; - } - } - -/* top of loop, this is where the code resumes if - * another reduction pass is required. - */ -top: - /* aliases for digits */ - /* alias for lower half of x */ - tmpx1 = x->dp; - - /* alias for upper half of x, or x/B**m */ - tmpx2 = x->dp + m; - - /* set carry to zero */ - mu = 0; - - /* compute (x mod B**m) + k * [x/B**m] inline and inplace */ - for (i = 0; i < m; i++) { - r = ((mp_word)*tmpx2++) * ((mp_word)k) + *tmpx1 + mu; - *tmpx1++ = (mp_digit)(r & MP_MASK); - mu = (mp_digit)(r >> ((mp_word)DIGIT_BIT)); - } - - /* set final carry */ - *tmpx1++ = mu; - - /* zero words above m */ - for (i = m + 1; i < x->used; i++) { - *tmpx1++ = 0; - } - - /* clamp, sub and return */ - mp_clamp (x); - - /* if x >= n then subtract and reduce again - * Each successive "recursion" makes the input smaller and smaller. - */ - if (mp_cmp_mag (x, n) != MP_LT) { - s_mp_sub(x, n, x); - goto top; - } - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_dr_reduce.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_dr_setup.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_dr_setup.c deleted file mode 100644 index a5152f7..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_dr_setup.c +++ /dev/null @@ -1,32 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_DR_SETUP_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* determines the setup value */ -void mp_dr_setup(mp_int *a, mp_digit *d) -{ - /* the casts are required if DIGIT_BIT is one less than - * the number of bits in a mp_digit [e.g. DIGIT_BIT==31] - */ - *d = (mp_digit)((((mp_word)1) << ((mp_word)DIGIT_BIT)) - - ((mp_word)a->dp[0])); -} - -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_dr_setup.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_exch.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_exch.c deleted file mode 100644 index e5ec7f5..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_exch.c +++ /dev/null @@ -1,34 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_EXCH_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* swap the elements of two integers, for cases where you can't simply swap the - * mp_int pointers around - */ -void -mp_exch (mp_int * a, mp_int * b) -{ - mp_int t; - - t = *a; - *a = *b; - *b = t; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_exch.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_expt_d.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_expt_d.c deleted file mode 100644 index 7bf371c..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_expt_d.c +++ /dev/null @@ -1,57 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_EXPT_D_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* calculate c = a**b using a square-multiply algorithm */ -int mp_expt_d (mp_int * a, mp_digit b, mp_int * c) -{ - int res, x; - mp_int g; - - if ((res = mp_init_copy (&g, a)) != MP_OKAY) { - return res; - } - - /* set initial result */ - mp_set (c, 1); - - for (x = 0; x < (int) DIGIT_BIT; x++) { - /* square */ - if ((res = mp_sqr (c, c)) != MP_OKAY) { - mp_clear (&g); - return res; - } - - /* if the bit is set multiply */ - if ((b & (mp_digit) (((mp_digit)1) << (DIGIT_BIT - 1))) != 0) { - if ((res = mp_mul (c, &g, c)) != MP_OKAY) { - mp_clear (&g); - return res; - } - } - - /* shift to next bit */ - b <<= 1; - } - - mp_clear (&g); - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_expt_d.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_exptmod.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_exptmod.c deleted file mode 100644 index 27c46ea..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_exptmod.c +++ /dev/null @@ -1,112 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_EXPTMOD_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - - -/* this is a shell function that calls either the normal or Montgomery - * exptmod functions. Originally the call to the montgomery code was - * embedded in the normal function but that wasted alot of stack space - * for nothing (since 99% of the time the Montgomery code would be called) - */ -int mp_exptmod (mp_int * G, mp_int * X, mp_int * P, mp_int * Y) -{ - int dr; - - /* modulus P must be positive */ - if (P->sign == MP_NEG) { - return MP_VAL; - } - - /* if exponent X is negative we have to recurse */ - if (X->sign == MP_NEG) { -#ifdef BN_MP_INVMOD_C - mp_int tmpG, tmpX; - int err; - - /* first compute 1/G mod P */ - if ((err = mp_init(&tmpG)) != MP_OKAY) { - return err; - } - if ((err = mp_invmod(G, P, &tmpG)) != MP_OKAY) { - mp_clear(&tmpG); - return err; - } - - /* now get |X| */ - if ((err = mp_init(&tmpX)) != MP_OKAY) { - mp_clear(&tmpG); - return err; - } - if ((err = mp_abs(X, &tmpX)) != MP_OKAY) { - mp_clear_multi(&tmpG, &tmpX, NULL); - return err; - } - - /* and now compute (1/G)**|X| instead of G**X [X < 0] */ - err = mp_exptmod(&tmpG, &tmpX, P, Y); - mp_clear_multi(&tmpG, &tmpX, NULL); - return err; -#else - /* no invmod */ - return MP_VAL; -#endif - } - -/* modified diminished radix reduction */ -#if defined(BN_MP_REDUCE_IS_2K_L_C) && defined(BN_MP_REDUCE_2K_L_C) && defined(BN_S_MP_EXPTMOD_C) - if (mp_reduce_is_2k_l(P) == MP_YES) { - return s_mp_exptmod(G, X, P, Y, 1); - } -#endif - -#ifdef BN_MP_DR_IS_MODULUS_C - /* is it a DR modulus? */ - dr = mp_dr_is_modulus(P); -#else - /* default to no */ - dr = 0; -#endif - -#ifdef BN_MP_REDUCE_IS_2K_C - /* if not, is it a unrestricted DR modulus? */ - if (dr == 0) { - dr = mp_reduce_is_2k(P) << 1; - } -#endif - - /* if the modulus is odd or dr != 0 use the montgomery method */ -#ifdef BN_MP_EXPTMOD_FAST_C - if (mp_isodd (P) == 1 || dr != 0) { - return mp_exptmod_fast (G, X, P, Y, dr); - } else { -#endif -#ifdef BN_S_MP_EXPTMOD_C - /* otherwise use the generic Barrett reduction technique */ - return s_mp_exptmod (G, X, P, Y, 0); -#else - /* no exptmod for evens */ - return MP_VAL; -#endif -#ifdef BN_MP_EXPTMOD_FAST_C - } -#endif -} - -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_exptmod.c,v $ */ -/* $Revision: 1.5 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_exptmod_fast.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_exptmod_fast.c deleted file mode 100644 index 31205d4..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_exptmod_fast.c +++ /dev/null @@ -1,321 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_EXPTMOD_FAST_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* computes Y == G**X mod P, HAC pp.616, Algorithm 14.85 - * - * Uses a left-to-right k-ary sliding window to compute the modular exponentiation. - * The value of k changes based on the size of the exponent. - * - * Uses Montgomery or Diminished Radix reduction [whichever appropriate] - */ - -#ifdef MP_LOW_MEM - #define TAB_SIZE 32 -#else - #define TAB_SIZE 256 -#endif - -int mp_exptmod_fast (mp_int * G, mp_int * X, mp_int * P, mp_int * Y, int redmode) -{ - mp_int M[TAB_SIZE], res; - mp_digit buf, mp; - int err, bitbuf, bitcpy, bitcnt, mode, digidx, x, y, winsize; - - /* use a pointer to the reduction algorithm. This allows us to use - * one of many reduction algorithms without modding the guts of - * the code with if statements everywhere. - */ - int (*redux)(mp_int*,mp_int*,mp_digit); - - /* find window size */ - x = mp_count_bits (X); - if (x <= 7) { - winsize = 2; - } else if (x <= 36) { - winsize = 3; - } else if (x <= 140) { - winsize = 4; - } else if (x <= 450) { - winsize = 5; - } else if (x <= 1303) { - winsize = 6; - } else if (x <= 3529) { - winsize = 7; - } else { - winsize = 8; - } - -#ifdef MP_LOW_MEM - if (winsize > 5) { - winsize = 5; - } -#endif - - /* init M array */ - /* init first cell */ - if ((err = mp_init(&M[1])) != MP_OKAY) { - return err; - } - - /* now init the second half of the array */ - for (x = 1<<(winsize-1); x < (1 << winsize); x++) { - if ((err = mp_init(&M[x])) != MP_OKAY) { - for (y = 1<<(winsize-1); y < x; y++) { - mp_clear (&M[y]); - } - mp_clear(&M[1]); - return err; - } - } - - /* determine and setup reduction code */ - if (redmode == 0) { -#ifdef BN_MP_MONTGOMERY_SETUP_C - /* now setup montgomery */ - if ((err = mp_montgomery_setup (P, &mp)) != MP_OKAY) { - goto LBL_M; - } -#else - err = MP_VAL; - goto LBL_M; -#endif - - /* automatically pick the comba one if available (saves quite a few calls/ifs) */ -#ifdef BN_FAST_MP_MONTGOMERY_REDUCE_C - if (((P->used * 2 + 1) < MP_WARRAY) && - P->used < (1 << ((CHAR_BIT * sizeof (mp_word)) - (2 * DIGIT_BIT)))) { - redux = fast_mp_montgomery_reduce; - } else -#endif - { -#ifdef BN_MP_MONTGOMERY_REDUCE_C - /* use slower baseline Montgomery method */ - redux = mp_montgomery_reduce; -#else - err = MP_VAL; - goto LBL_M; -#endif - } - } else if (redmode == 1) { -#if defined(BN_MP_DR_SETUP_C) && defined(BN_MP_DR_REDUCE_C) - /* setup DR reduction for moduli of the form B**k - b */ - mp_dr_setup(P, &mp); - redux = mp_dr_reduce; -#else - err = MP_VAL; - goto LBL_M; -#endif - } else { -#if defined(BN_MP_REDUCE_2K_SETUP_C) && defined(BN_MP_REDUCE_2K_C) - /* setup DR reduction for moduli of the form 2**k - b */ - if ((err = mp_reduce_2k_setup(P, &mp)) != MP_OKAY) { - goto LBL_M; - } - redux = mp_reduce_2k; -#else - err = MP_VAL; - goto LBL_M; -#endif - } - - /* setup result */ - if ((err = mp_init (&res)) != MP_OKAY) { - goto LBL_M; - } - - /* create M table - * - - * - * The first half of the table is not computed though accept for M[0] and M[1] - */ - - if (redmode == 0) { -#ifdef BN_MP_MONTGOMERY_CALC_NORMALIZATION_C - /* now we need R mod m */ - if ((err = mp_montgomery_calc_normalization (&res, P)) != MP_OKAY) { - goto LBL_RES; - } -#else - err = MP_VAL; - goto LBL_RES; -#endif - - /* now set M[1] to G * R mod m */ - if ((err = mp_mulmod (G, &res, P, &M[1])) != MP_OKAY) { - goto LBL_RES; - } - } else { - mp_set(&res, 1); - if ((err = mp_mod(G, P, &M[1])) != MP_OKAY) { - goto LBL_RES; - } - } - - /* compute the value at M[1<<(winsize-1)] by squaring M[1] (winsize-1) times */ - if ((err = mp_copy (&M[1], &M[1 << (winsize - 1)])) != MP_OKAY) { - goto LBL_RES; - } - - for (x = 0; x < (winsize - 1); x++) { - if ((err = mp_sqr (&M[1 << (winsize - 1)], &M[1 << (winsize - 1)])) != MP_OKAY) { - goto LBL_RES; - } - if ((err = redux (&M[1 << (winsize - 1)], P, mp)) != MP_OKAY) { - goto LBL_RES; - } - } - - /* create upper table */ - for (x = (1 << (winsize - 1)) + 1; x < (1 << winsize); x++) { - if ((err = mp_mul (&M[x - 1], &M[1], &M[x])) != MP_OKAY) { - goto LBL_RES; - } - if ((err = redux (&M[x], P, mp)) != MP_OKAY) { - goto LBL_RES; - } - } - - /* set initial mode and bit cnt */ - mode = 0; - bitcnt = 1; - buf = 0; - digidx = X->used - 1; - bitcpy = 0; - bitbuf = 0; - - for (;;) { - /* grab next digit as required */ - if (--bitcnt == 0) { - /* if digidx == -1 we are out of digits so break */ - if (digidx == -1) { - break; - } - /* read next digit and reset bitcnt */ - buf = X->dp[digidx--]; - bitcnt = (int)DIGIT_BIT; - } - - /* grab the next msb from the exponent */ - y = (mp_digit)(buf >> (DIGIT_BIT - 1)) & 1; - buf <<= (mp_digit)1; - - /* if the bit is zero and mode == 0 then we ignore it - * These represent the leading zero bits before the first 1 bit - * in the exponent. Technically this opt is not required but it - * does lower the # of trivial squaring/reductions used - */ - if (mode == 0 && y == 0) { - continue; - } - - /* if the bit is zero and mode == 1 then we square */ - if (mode == 1 && y == 0) { - if ((err = mp_sqr (&res, &res)) != MP_OKAY) { - goto LBL_RES; - } - if ((err = redux (&res, P, mp)) != MP_OKAY) { - goto LBL_RES; - } - continue; - } - - /* else we add it to the window */ - bitbuf |= (y << (winsize - ++bitcpy)); - mode = 2; - - if (bitcpy == winsize) { - /* ok window is filled so square as required and multiply */ - /* square first */ - for (x = 0; x < winsize; x++) { - if ((err = mp_sqr (&res, &res)) != MP_OKAY) { - goto LBL_RES; - } - if ((err = redux (&res, P, mp)) != MP_OKAY) { - goto LBL_RES; - } - } - - /* then multiply */ - if ((err = mp_mul (&res, &M[bitbuf], &res)) != MP_OKAY) { - goto LBL_RES; - } - if ((err = redux (&res, P, mp)) != MP_OKAY) { - goto LBL_RES; - } - - /* empty window and reset */ - bitcpy = 0; - bitbuf = 0; - mode = 1; - } - } - - /* if bits remain then square/multiply */ - if (mode == 2 && bitcpy > 0) { - /* square then multiply if the bit is set */ - for (x = 0; x < bitcpy; x++) { - if ((err = mp_sqr (&res, &res)) != MP_OKAY) { - goto LBL_RES; - } - if ((err = redux (&res, P, mp)) != MP_OKAY) { - goto LBL_RES; - } - - /* get next bit of the window */ - bitbuf <<= 1; - if ((bitbuf & (1 << winsize)) != 0) { - /* then multiply */ - if ((err = mp_mul (&res, &M[1], &res)) != MP_OKAY) { - goto LBL_RES; - } - if ((err = redux (&res, P, mp)) != MP_OKAY) { - goto LBL_RES; - } - } - } - } - - if (redmode == 0) { - /* fixup result if Montgomery reduction is used - * recall that any value in a Montgomery system is - * actually multiplied by R mod n. So we have - * to reduce one more time to cancel out the factor - * of R. - */ - if ((err = redux(&res, P, mp)) != MP_OKAY) { - goto LBL_RES; - } - } - - /* swap res with Y */ - mp_exch (&res, Y); - err = MP_OKAY; -LBL_RES:mp_clear (&res); -LBL_M: - mp_clear(&M[1]); - for (x = 1<<(winsize-1); x < (1 << winsize); x++) { - mp_clear (&M[x]); - } - return err; -} -#endif - - -/* $Source: /cvs/libtom/libtommath/bn_mp_exptmod_fast.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_exteuclid.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_exteuclid.c deleted file mode 100644 index 9881d6e..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_exteuclid.c +++ /dev/null @@ -1,82 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_EXTEUCLID_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* Extended euclidean algorithm of (a, b) produces - a*u1 + b*u2 = u3 - */ -int mp_exteuclid(mp_int *a, mp_int *b, mp_int *U1, mp_int *U2, mp_int *U3) -{ - mp_int u1,u2,u3,v1,v2,v3,t1,t2,t3,q,tmp; - int err; - - if ((err = mp_init_multi(&u1, &u2, &u3, &v1, &v2, &v3, &t1, &t2, &t3, &q, &tmp, NULL)) != MP_OKAY) { - return err; - } - - /* initialize, (u1,u2,u3) = (1,0,a) */ - mp_set(&u1, 1); - if ((err = mp_copy(a, &u3)) != MP_OKAY) { goto _ERR; } - - /* initialize, (v1,v2,v3) = (0,1,b) */ - mp_set(&v2, 1); - if ((err = mp_copy(b, &v3)) != MP_OKAY) { goto _ERR; } - - /* loop while v3 != 0 */ - while (mp_iszero(&v3) == MP_NO) { - /* q = u3/v3 */ - if ((err = mp_div(&u3, &v3, &q, NULL)) != MP_OKAY) { goto _ERR; } - - /* (t1,t2,t3) = (u1,u2,u3) - (v1,v2,v3)q */ - if ((err = mp_mul(&v1, &q, &tmp)) != MP_OKAY) { goto _ERR; } - if ((err = mp_sub(&u1, &tmp, &t1)) != MP_OKAY) { goto _ERR; } - if ((err = mp_mul(&v2, &q, &tmp)) != MP_OKAY) { goto _ERR; } - if ((err = mp_sub(&u2, &tmp, &t2)) != MP_OKAY) { goto _ERR; } - if ((err = mp_mul(&v3, &q, &tmp)) != MP_OKAY) { goto _ERR; } - if ((err = mp_sub(&u3, &tmp, &t3)) != MP_OKAY) { goto _ERR; } - - /* (u1,u2,u3) = (v1,v2,v3) */ - if ((err = mp_copy(&v1, &u1)) != MP_OKAY) { goto _ERR; } - if ((err = mp_copy(&v2, &u2)) != MP_OKAY) { goto _ERR; } - if ((err = mp_copy(&v3, &u3)) != MP_OKAY) { goto _ERR; } - - /* (v1,v2,v3) = (t1,t2,t3) */ - if ((err = mp_copy(&t1, &v1)) != MP_OKAY) { goto _ERR; } - if ((err = mp_copy(&t2, &v2)) != MP_OKAY) { goto _ERR; } - if ((err = mp_copy(&t3, &v3)) != MP_OKAY) { goto _ERR; } - } - - /* make sure U3 >= 0 */ - if (u3.sign == MP_NEG) { - mp_neg(&u1, &u1); - mp_neg(&u2, &u2); - mp_neg(&u3, &u3); - } - - /* copy result out */ - if (U1 != NULL) { mp_exch(U1, &u1); } - if (U2 != NULL) { mp_exch(U2, &u2); } - if (U3 != NULL) { mp_exch(U3, &u3); } - - err = MP_OKAY; -_ERR: mp_clear_multi(&u1, &u2, &u3, &v1, &v2, &v3, &t1, &t2, &t3, &q, &tmp, NULL); - return err; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_exteuclid.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_fread.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_fread.c deleted file mode 100644 index 2976b30..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_fread.c +++ /dev/null @@ -1,67 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_FREAD_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* read a bigint from a file stream in ASCII */ -int mp_fread(mp_int *a, int radix, FILE *stream) -{ - int err, ch, neg, y; - - /* clear a */ - mp_zero(a); - - /* if first digit is - then set negative */ - ch = fgetc(stream); - if (ch == '-') { - neg = MP_NEG; - ch = fgetc(stream); - } else { - neg = MP_ZPOS; - } - - for (;;) { - /* find y in the radix map */ - for (y = 0; y < radix; y++) { - if (mp_s_rmap[y] == ch) { - break; - } - } - if (y == radix) { - break; - } - - /* shift up and add */ - if ((err = mp_mul_d(a, radix, a)) != MP_OKAY) { - return err; - } - if ((err = mp_add_d(a, y, a)) != MP_OKAY) { - return err; - } - - ch = fgetc(stream); - } - if (mp_cmp_d(a, 0) != MP_EQ) { - a->sign = neg; - } - - return MP_OKAY; -} - -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_fread.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_fwrite.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_fwrite.c deleted file mode 100644 index 6782b2e..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_fwrite.c +++ /dev/null @@ -1,52 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_FWRITE_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -int mp_fwrite(mp_int *a, int radix, FILE *stream) -{ - char *buf; - int err, len, x; - - if ((err = mp_radix_size(a, radix, &len)) != MP_OKAY) { - return err; - } - - buf = OPT_CAST(char) XMALLOC (len); - if (buf == NULL) { - return MP_MEM; - } - - if ((err = mp_toradix(a, buf, radix)) != MP_OKAY) { - XFREE (buf); - return err; - } - - for (x = 0; x < len; x++) { - if (fputc(buf[x], stream) == EOF) { - XFREE (buf); - return MP_VAL; - } - } - - XFREE (buf); - return MP_OKAY; -} - -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_fwrite.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_gcd.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_gcd.c deleted file mode 100644 index ce980eb..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_gcd.c +++ /dev/null @@ -1,105 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_GCD_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* Greatest Common Divisor using the binary method */ -int mp_gcd (mp_int * a, mp_int * b, mp_int * c) -{ - mp_int u, v; - int k, u_lsb, v_lsb, res; - - /* either zero than gcd is the largest */ - if (mp_iszero (a) == MP_YES) { - return mp_abs (b, c); - } - if (mp_iszero (b) == MP_YES) { - return mp_abs (a, c); - } - - /* get copies of a and b we can modify */ - if ((res = mp_init_copy (&u, a)) != MP_OKAY) { - return res; - } - - if ((res = mp_init_copy (&v, b)) != MP_OKAY) { - goto LBL_U; - } - - /* must be positive for the remainder of the algorithm */ - u.sign = v.sign = MP_ZPOS; - - /* B1. Find the common power of two for u and v */ - u_lsb = mp_cnt_lsb(&u); - v_lsb = mp_cnt_lsb(&v); - k = MIN(u_lsb, v_lsb); - - if (k > 0) { - /* divide the power of two out */ - if ((res = mp_div_2d(&u, k, &u, NULL)) != MP_OKAY) { - goto LBL_V; - } - - if ((res = mp_div_2d(&v, k, &v, NULL)) != MP_OKAY) { - goto LBL_V; - } - } - - /* divide any remaining factors of two out */ - if (u_lsb != k) { - if ((res = mp_div_2d(&u, u_lsb - k, &u, NULL)) != MP_OKAY) { - goto LBL_V; - } - } - - if (v_lsb != k) { - if ((res = mp_div_2d(&v, v_lsb - k, &v, NULL)) != MP_OKAY) { - goto LBL_V; - } - } - - while (mp_iszero(&v) == 0) { - /* make sure v is the largest */ - if (mp_cmp_mag(&u, &v) == MP_GT) { - /* swap u and v to make sure v is >= u */ - mp_exch(&u, &v); - } - - /* subtract smallest from largest */ - if ((res = s_mp_sub(&v, &u, &v)) != MP_OKAY) { - goto LBL_V; - } - - /* Divide out all factors of two */ - if ((res = mp_div_2d(&v, mp_cnt_lsb(&v), &v, NULL)) != MP_OKAY) { - goto LBL_V; - } - } - - /* multiply by 2**k which we divided out at the beginning */ - if ((res = mp_mul_2d (&u, k, c)) != MP_OKAY) { - goto LBL_V; - } - c->sign = MP_ZPOS; - res = MP_OKAY; -LBL_V:mp_clear (&u); -LBL_U:mp_clear (&v); - return res; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_gcd.c,v $ */ -/* $Revision: 1.5 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_get_int.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_get_int.c deleted file mode 100644 index d9c76d0..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_get_int.c +++ /dev/null @@ -1,45 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_GET_INT_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* get the lower 32-bits of an mp_int */ -unsigned long mp_get_int(mp_int * a) -{ - int i; - unsigned long res; - - if (a->used == 0) { - return 0; - } - - /* get number of digits of the lsb we have to read */ - i = MIN(a->used,(int)((sizeof(unsigned long)*CHAR_BIT+DIGIT_BIT-1)/DIGIT_BIT))-1; - - /* get most significant digit of result */ - res = DIGIT(a,i); - - while (--i >= 0) { - res = (res << DIGIT_BIT) | DIGIT(a,i); - } - - /* force result to 32-bits always so it is consistent on non 32-bit platforms */ - return res & 0xFFFFFFFFUL; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_get_int.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_grow.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_grow.c deleted file mode 100644 index a05dad7..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_grow.c +++ /dev/null @@ -1,57 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_GROW_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* grow as required */ -int mp_grow (mp_int * a, int size) -{ - int i; - mp_digit *tmp; - - /* if the alloc size is smaller alloc more ram */ - if (a->alloc < size) { - /* ensure there are always at least MP_PREC digits extra on top */ - size += (MP_PREC * 2) - (size % MP_PREC); - - /* reallocate the array a->dp - * - * We store the return in a temporary variable - * in case the operation failed we don't want - * to overwrite the dp member of a. - */ - tmp = OPT_CAST(mp_digit) XREALLOC (a->dp, sizeof (mp_digit) * size); - if (tmp == NULL) { - /* reallocation failed but "a" is still valid [can be freed] */ - return MP_MEM; - } - - /* reallocation succeeded so set a->dp */ - a->dp = tmp; - - /* zero excess digits */ - i = a->alloc; - a->alloc = size; - for (; i < a->alloc; i++) { - a->dp[i] = 0; - } - } - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_grow.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_init.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_init.c deleted file mode 100644 index 107d98b..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_init.c +++ /dev/null @@ -1,46 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_INIT_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* init a new mp_int */ -int mp_init (mp_int * a) -{ - int i; - - /* allocate memory required and clear it */ - a->dp = OPT_CAST(mp_digit) XMALLOC (sizeof (mp_digit) * MP_PREC); - if (a->dp == NULL) { - return MP_MEM; - } - - /* set the digits to zero */ - for (i = 0; i < MP_PREC; i++) { - a->dp[i] = 0; - } - - /* set the used to zero, allocated digits to the default precision - * and sign to positive */ - a->used = 0; - a->alloc = MP_PREC; - a->sign = MP_ZPOS; - - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_init.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_init_copy.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_init_copy.c deleted file mode 100644 index 3ca1186..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_init_copy.c +++ /dev/null @@ -1,32 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_INIT_COPY_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* creates "a" then copies b into it */ -int mp_init_copy (mp_int * a, mp_int * b) -{ - int res; - - if ((res = mp_init (a)) != MP_OKAY) { - return res; - } - return mp_copy (b, a); -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_init_copy.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_init_multi.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_init_multi.c deleted file mode 100644 index 4f6f367..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_init_multi.c +++ /dev/null @@ -1,59 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_INIT_MULTI_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#include - -int mp_init_multi(mp_int *mp, ...) -{ - mp_err res = MP_OKAY; /* Assume ok until proven otherwise */ - int n = 0; /* Number of ok inits */ - mp_int* cur_arg = mp; - va_list args; - - va_start(args, mp); /* init args to next argument from caller */ - while (cur_arg != NULL) { - if (mp_init(cur_arg) != MP_OKAY) { - /* Oops - error! Back-track and mp_clear what we already - succeeded in init-ing, then return error. - */ - va_list clean_args; - - /* end the current list */ - va_end(args); - - /* now start cleaning up */ - cur_arg = mp; - va_start(clean_args, mp); - while (n--) { - mp_clear(cur_arg); - cur_arg = va_arg(clean_args, mp_int*); - } - va_end(clean_args); - res = MP_MEM; - break; - } - n++; - cur_arg = va_arg(args, mp_int*); - } - va_end(args); - return res; /* Assumed ok, if error flagged above. */ -} - -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_init_multi.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_init_set.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_init_set.c deleted file mode 100644 index 853323f..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_init_set.c +++ /dev/null @@ -1,32 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_INIT_SET_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* initialize and set a digit */ -int mp_init_set (mp_int * a, mp_digit b) -{ - int err; - if ((err = mp_init(a)) != MP_OKAY) { - return err; - } - mp_set(a, b); - return err; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_init_set.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_init_set_int.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_init_set_int.c deleted file mode 100644 index b2f8727..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_init_set_int.c +++ /dev/null @@ -1,31 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_INIT_SET_INT_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* initialize and set a digit */ -int mp_init_set_int (mp_int * a, unsigned long b) -{ - int err; - if ((err = mp_init(a)) != MP_OKAY) { - return err; - } - return mp_set_int(a, b); -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_init_set_int.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_init_size.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_init_size.c deleted file mode 100644 index 17b8d9f..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_init_size.c +++ /dev/null @@ -1,48 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_INIT_SIZE_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* init an mp_init for a given size */ -int mp_init_size (mp_int * a, int size) -{ - int x; - - /* pad size so there are always extra digits */ - size += (MP_PREC * 2) - (size % MP_PREC); - - /* alloc mem */ - a->dp = OPT_CAST(mp_digit) XMALLOC (sizeof (mp_digit) * size); - if (a->dp == NULL) { - return MP_MEM; - } - - /* set the members */ - a->used = 0; - a->alloc = size; - a->sign = MP_ZPOS; - - /* zero the digits */ - for (x = 0; x < size; x++) { - a->dp[x] = 0; - } - - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_init_size.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_invmod.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_invmod.c deleted file mode 100644 index 038e584..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_invmod.c +++ /dev/null @@ -1,43 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_INVMOD_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* hac 14.61, pp608 */ -int mp_invmod (mp_int * a, mp_int * b, mp_int * c) -{ - /* b cannot be negative */ - if (b->sign == MP_NEG || mp_iszero(b) == 1) { - return MP_VAL; - } - -#ifdef BN_FAST_MP_INVMOD_C - /* if the modulus is odd we can use a faster routine instead */ - if (mp_isodd (b) == 1) { - return fast_mp_invmod (a, b, c); - } -#endif - -#ifdef BN_MP_INVMOD_SLOW_C - return mp_invmod_slow(a, b, c); -#endif - - return MP_VAL; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_invmod.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_invmod_slow.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_invmod_slow.c deleted file mode 100644 index 3792a4c..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_invmod_slow.c +++ /dev/null @@ -1,175 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_INVMOD_SLOW_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* hac 14.61, pp608 */ -int mp_invmod_slow (mp_int * a, mp_int * b, mp_int * c) -{ - mp_int x, y, u, v, A, B, C, D; - int res; - - /* b cannot be negative */ - if (b->sign == MP_NEG || mp_iszero(b) == 1) { - return MP_VAL; - } - - /* init temps */ - if ((res = mp_init_multi(&x, &y, &u, &v, - &A, &B, &C, &D, NULL)) != MP_OKAY) { - return res; - } - - /* x = a, y = b */ - if ((res = mp_mod(a, b, &x)) != MP_OKAY) { - goto LBL_ERR; - } - if ((res = mp_copy (b, &y)) != MP_OKAY) { - goto LBL_ERR; - } - - /* 2. [modified] if x,y are both even then return an error! */ - if (mp_iseven (&x) == 1 && mp_iseven (&y) == 1) { - res = MP_VAL; - goto LBL_ERR; - } - - /* 3. u=x, v=y, A=1, B=0, C=0,D=1 */ - if ((res = mp_copy (&x, &u)) != MP_OKAY) { - goto LBL_ERR; - } - if ((res = mp_copy (&y, &v)) != MP_OKAY) { - goto LBL_ERR; - } - mp_set (&A, 1); - mp_set (&D, 1); - -top: - /* 4. while u is even do */ - while (mp_iseven (&u) == 1) { - /* 4.1 u = u/2 */ - if ((res = mp_div_2 (&u, &u)) != MP_OKAY) { - goto LBL_ERR; - } - /* 4.2 if A or B is odd then */ - if (mp_isodd (&A) == 1 || mp_isodd (&B) == 1) { - /* A = (A+y)/2, B = (B-x)/2 */ - if ((res = mp_add (&A, &y, &A)) != MP_OKAY) { - goto LBL_ERR; - } - if ((res = mp_sub (&B, &x, &B)) != MP_OKAY) { - goto LBL_ERR; - } - } - /* A = A/2, B = B/2 */ - if ((res = mp_div_2 (&A, &A)) != MP_OKAY) { - goto LBL_ERR; - } - if ((res = mp_div_2 (&B, &B)) != MP_OKAY) { - goto LBL_ERR; - } - } - - /* 5. while v is even do */ - while (mp_iseven (&v) == 1) { - /* 5.1 v = v/2 */ - if ((res = mp_div_2 (&v, &v)) != MP_OKAY) { - goto LBL_ERR; - } - /* 5.2 if C or D is odd then */ - if (mp_isodd (&C) == 1 || mp_isodd (&D) == 1) { - /* C = (C+y)/2, D = (D-x)/2 */ - if ((res = mp_add (&C, &y, &C)) != MP_OKAY) { - goto LBL_ERR; - } - if ((res = mp_sub (&D, &x, &D)) != MP_OKAY) { - goto LBL_ERR; - } - } - /* C = C/2, D = D/2 */ - if ((res = mp_div_2 (&C, &C)) != MP_OKAY) { - goto LBL_ERR; - } - if ((res = mp_div_2 (&D, &D)) != MP_OKAY) { - goto LBL_ERR; - } - } - - /* 6. if u >= v then */ - if (mp_cmp (&u, &v) != MP_LT) { - /* u = u - v, A = A - C, B = B - D */ - if ((res = mp_sub (&u, &v, &u)) != MP_OKAY) { - goto LBL_ERR; - } - - if ((res = mp_sub (&A, &C, &A)) != MP_OKAY) { - goto LBL_ERR; - } - - if ((res = mp_sub (&B, &D, &B)) != MP_OKAY) { - goto LBL_ERR; - } - } else { - /* v - v - u, C = C - A, D = D - B */ - if ((res = mp_sub (&v, &u, &v)) != MP_OKAY) { - goto LBL_ERR; - } - - if ((res = mp_sub (&C, &A, &C)) != MP_OKAY) { - goto LBL_ERR; - } - - if ((res = mp_sub (&D, &B, &D)) != MP_OKAY) { - goto LBL_ERR; - } - } - - /* if not zero goto step 4 */ - if (mp_iszero (&u) == 0) - goto top; - - /* now a = C, b = D, gcd == g*v */ - - /* if v != 1 then there is no inverse */ - if (mp_cmp_d (&v, 1) != MP_EQ) { - res = MP_VAL; - goto LBL_ERR; - } - - /* if its too low */ - while (mp_cmp_d(&C, 0) == MP_LT) { - if ((res = mp_add(&C, b, &C)) != MP_OKAY) { - goto LBL_ERR; - } - } - - /* too big */ - while (mp_cmp_mag(&C, b) != MP_LT) { - if ((res = mp_sub(&C, b, &C)) != MP_OKAY) { - goto LBL_ERR; - } - } - - /* C is now the inverse */ - mp_exch (&C, c); - res = MP_OKAY; -LBL_ERR:mp_clear_multi (&x, &y, &u, &v, &A, &B, &C, &D, NULL); - return res; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_invmod_slow.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_is_square.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_is_square.c deleted file mode 100644 index 5d2fa07..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_is_square.c +++ /dev/null @@ -1,109 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_IS_SQUARE_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* Check if remainders are possible squares - fast exclude non-squares */ -static const char rem_128[128] = { - 0, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, - 0, 0, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, - 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, - 1, 0, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, - 0, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, - 1, 0, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, - 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, - 1, 0, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1 -}; - -static const char rem_105[105] = { - 0, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, - 0, 0, 1, 1, 1, 1, 0, 1, 1, 1, 0, 1, 1, 1, 1, - 0, 1, 1, 1, 1, 1, 0, 1, 1, 0, 1, 1, 1, 1, 1, - 1, 0, 1, 1, 0, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, - 0, 1, 1, 1, 0, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, - 1, 1, 1, 1, 0, 1, 0, 1, 1, 0, 0, 1, 1, 1, 1, - 1, 0, 1, 1, 1, 1, 1, 1, 1, 0, 0, 1, 1, 1, 1 -}; - -/* Store non-zero to ret if arg is square, and zero if not */ -int mp_is_square(mp_int *arg,int *ret) -{ - int res; - mp_digit c; - mp_int t; - unsigned long r; - - /* Default to Non-square :) */ - *ret = MP_NO; - - if (arg->sign == MP_NEG) { - return MP_VAL; - } - - /* digits used? (TSD) */ - if (arg->used == 0) { - return MP_OKAY; - } - - /* First check mod 128 (suppose that DIGIT_BIT is at least 7) */ - if (rem_128[127 & DIGIT(arg,0)] == 1) { - return MP_OKAY; - } - - /* Next check mod 105 (3*5*7) */ - if ((res = mp_mod_d(arg,105,&c)) != MP_OKAY) { - return res; - } - if (rem_105[c] == 1) { - return MP_OKAY; - } - - - if ((res = mp_init_set_int(&t,11L*13L*17L*19L*23L*29L*31L)) != MP_OKAY) { - return res; - } - if ((res = mp_mod(arg,&t,&t)) != MP_OKAY) { - goto ERR; - } - r = mp_get_int(&t); - /* Check for other prime modules, note it's not an ERROR but we must - * free "t" so the easiest way is to goto ERR. We know that res - * is already equal to MP_OKAY from the mp_mod call - */ - if ( (1L<<(r%11)) & 0x5C4L ) goto ERR; - if ( (1L<<(r%13)) & 0x9E4L ) goto ERR; - if ( (1L<<(r%17)) & 0x5CE8L ) goto ERR; - if ( (1L<<(r%19)) & 0x4F50CL ) goto ERR; - if ( (1L<<(r%23)) & 0x7ACCA0L ) goto ERR; - if ( (1L<<(r%29)) & 0xC2EDD0CL ) goto ERR; - if ( (1L<<(r%31)) & 0x6DE2B848L ) goto ERR; - - /* Final check - is sqr(sqrt(arg)) == arg ? */ - if ((res = mp_sqrt(arg,&t)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_sqr(&t,&t)) != MP_OKAY) { - goto ERR; - } - - *ret = (mp_cmp_mag(&t,arg) == MP_EQ) ? MP_YES : MP_NO; -ERR:mp_clear(&t); - return res; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_is_square.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_jacobi.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_jacobi.c deleted file mode 100644 index c70b946..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_jacobi.c +++ /dev/null @@ -1,105 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_JACOBI_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* computes the jacobi c = (a | n) (or Legendre if n is prime) - * HAC pp. 73 Algorithm 2.149 - */ -int mp_jacobi (mp_int * a, mp_int * p, int *c) -{ - mp_int a1, p1; - int k, s, r, res; - mp_digit residue; - - /* if p <= 0 return MP_VAL */ - if (mp_cmp_d(p, 0) != MP_GT) { - return MP_VAL; - } - - /* step 1. if a == 0, return 0 */ - if (mp_iszero (a) == 1) { - *c = 0; - return MP_OKAY; - } - - /* step 2. if a == 1, return 1 */ - if (mp_cmp_d (a, 1) == MP_EQ) { - *c = 1; - return MP_OKAY; - } - - /* default */ - s = 0; - - /* step 3. write a = a1 * 2**k */ - if ((res = mp_init_copy (&a1, a)) != MP_OKAY) { - return res; - } - - if ((res = mp_init (&p1)) != MP_OKAY) { - goto LBL_A1; - } - - /* divide out larger power of two */ - k = mp_cnt_lsb(&a1); - if ((res = mp_div_2d(&a1, k, &a1, NULL)) != MP_OKAY) { - goto LBL_P1; - } - - /* step 4. if e is even set s=1 */ - if ((k & 1) == 0) { - s = 1; - } else { - /* else set s=1 if p = 1/7 (mod 8) or s=-1 if p = 3/5 (mod 8) */ - residue = p->dp[0] & 7; - - if (residue == 1 || residue == 7) { - s = 1; - } else if (residue == 3 || residue == 5) { - s = -1; - } - } - - /* step 5. if p == 3 (mod 4) *and* a1 == 3 (mod 4) then s = -s */ - if ( ((p->dp[0] & 3) == 3) && ((a1.dp[0] & 3) == 3)) { - s = -s; - } - - /* if a1 == 1 we're done */ - if (mp_cmp_d (&a1, 1) == MP_EQ) { - *c = s; - } else { - /* n1 = n mod a1 */ - if ((res = mp_mod (p, &a1, &p1)) != MP_OKAY) { - goto LBL_P1; - } - if ((res = mp_jacobi (&p1, &a1, &r)) != MP_OKAY) { - goto LBL_P1; - } - *c = s * r; - } - - /* done */ - res = MP_OKAY; -LBL_P1:mp_clear (&p1); -LBL_A1:mp_clear (&a1); - return res; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_jacobi.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_karatsuba_mul.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_karatsuba_mul.c deleted file mode 100644 index b15ec24..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_karatsuba_mul.c +++ /dev/null @@ -1,167 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_KARATSUBA_MUL_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* c = |a| * |b| using Karatsuba Multiplication using - * three half size multiplications - * - * Let B represent the radix [e.g. 2**DIGIT_BIT] and - * let n represent half of the number of digits in - * the min(a,b) - * - * a = a1 * B**n + a0 - * b = b1 * B**n + b0 - * - * Then, a * b => - a1b1 * B**2n + ((a1 + a0)(b1 + b0) - (a0b0 + a1b1)) * B + a0b0 - * - * Note that a1b1 and a0b0 are used twice and only need to be - * computed once. So in total three half size (half # of - * digit) multiplications are performed, a0b0, a1b1 and - * (a1+b1)(a0+b0) - * - * Note that a multiplication of half the digits requires - * 1/4th the number of single precision multiplications so in - * total after one call 25% of the single precision multiplications - * are saved. Note also that the call to mp_mul can end up back - * in this function if the a0, a1, b0, or b1 are above the threshold. - * This is known as divide-and-conquer and leads to the famous - * O(N**lg(3)) or O(N**1.584) work which is asymptopically lower than - * the standard O(N**2) that the baseline/comba methods use. - * Generally though the overhead of this method doesn't pay off - * until a certain size (N ~ 80) is reached. - */ -int mp_karatsuba_mul (mp_int * a, mp_int * b, mp_int * c) -{ - mp_int x0, x1, y0, y1, t1, x0y0, x1y1; - int B, err; - - /* default the return code to an error */ - err = MP_MEM; - - /* min # of digits */ - B = MIN (a->used, b->used); - - /* now divide in two */ - B = B >> 1; - - /* init copy all the temps */ - if (mp_init_size (&x0, B) != MP_OKAY) - goto ERR; - if (mp_init_size (&x1, a->used - B) != MP_OKAY) - goto X0; - if (mp_init_size (&y0, B) != MP_OKAY) - goto X1; - if (mp_init_size (&y1, b->used - B) != MP_OKAY) - goto Y0; - - /* init temps */ - if (mp_init_size (&t1, B * 2) != MP_OKAY) - goto Y1; - if (mp_init_size (&x0y0, B * 2) != MP_OKAY) - goto T1; - if (mp_init_size (&x1y1, B * 2) != MP_OKAY) - goto X0Y0; - - /* now shift the digits */ - x0.used = y0.used = B; - x1.used = a->used - B; - y1.used = b->used - B; - - { - register int x; - register mp_digit *tmpa, *tmpb, *tmpx, *tmpy; - - /* we copy the digits directly instead of using higher level functions - * since we also need to shift the digits - */ - tmpa = a->dp; - tmpb = b->dp; - - tmpx = x0.dp; - tmpy = y0.dp; - for (x = 0; x < B; x++) { - *tmpx++ = *tmpa++; - *tmpy++ = *tmpb++; - } - - tmpx = x1.dp; - for (x = B; x < a->used; x++) { - *tmpx++ = *tmpa++; - } - - tmpy = y1.dp; - for (x = B; x < b->used; x++) { - *tmpy++ = *tmpb++; - } - } - - /* only need to clamp the lower words since by definition the - * upper words x1/y1 must have a known number of digits - */ - mp_clamp (&x0); - mp_clamp (&y0); - - /* now calc the products x0y0 and x1y1 */ - /* after this x0 is no longer required, free temp [x0==t2]! */ - if (mp_mul (&x0, &y0, &x0y0) != MP_OKAY) - goto X1Y1; /* x0y0 = x0*y0 */ - if (mp_mul (&x1, &y1, &x1y1) != MP_OKAY) - goto X1Y1; /* x1y1 = x1*y1 */ - - /* now calc x1+x0 and y1+y0 */ - if (s_mp_add (&x1, &x0, &t1) != MP_OKAY) - goto X1Y1; /* t1 = x1 - x0 */ - if (s_mp_add (&y1, &y0, &x0) != MP_OKAY) - goto X1Y1; /* t2 = y1 - y0 */ - if (mp_mul (&t1, &x0, &t1) != MP_OKAY) - goto X1Y1; /* t1 = (x1 + x0) * (y1 + y0) */ - - /* add x0y0 */ - if (mp_add (&x0y0, &x1y1, &x0) != MP_OKAY) - goto X1Y1; /* t2 = x0y0 + x1y1 */ - if (s_mp_sub (&t1, &x0, &t1) != MP_OKAY) - goto X1Y1; /* t1 = (x1+x0)*(y1+y0) - (x1y1 + x0y0) */ - - /* shift by B */ - if (mp_lshd (&t1, B) != MP_OKAY) - goto X1Y1; /* t1 = (x0y0 + x1y1 - (x1-x0)*(y1-y0))<used; - - /* now divide in two */ - B = B >> 1; - - /* init copy all the temps */ - if (mp_init_size (&x0, B) != MP_OKAY) - goto ERR; - if (mp_init_size (&x1, a->used - B) != MP_OKAY) - goto X0; - - /* init temps */ - if (mp_init_size (&t1, a->used * 2) != MP_OKAY) - goto X1; - if (mp_init_size (&t2, a->used * 2) != MP_OKAY) - goto T1; - if (mp_init_size (&x0x0, B * 2) != MP_OKAY) - goto T2; - if (mp_init_size (&x1x1, (a->used - B) * 2) != MP_OKAY) - goto X0X0; - - { - register int x; - register mp_digit *dst, *src; - - src = a->dp; - - /* now shift the digits */ - dst = x0.dp; - for (x = 0; x < B; x++) { - *dst++ = *src++; - } - - dst = x1.dp; - for (x = B; x < a->used; x++) { - *dst++ = *src++; - } - } - - x0.used = B; - x1.used = a->used - B; - - mp_clamp (&x0); - - /* now calc the products x0*x0 and x1*x1 */ - if (mp_sqr (&x0, &x0x0) != MP_OKAY) - goto X1X1; /* x0x0 = x0*x0 */ - if (mp_sqr (&x1, &x1x1) != MP_OKAY) - goto X1X1; /* x1x1 = x1*x1 */ - - /* now calc (x1+x0)**2 */ - if (s_mp_add (&x1, &x0, &t1) != MP_OKAY) - goto X1X1; /* t1 = x1 - x0 */ - if (mp_sqr (&t1, &t1) != MP_OKAY) - goto X1X1; /* t1 = (x1 - x0) * (x1 - x0) */ - - /* add x0y0 */ - if (s_mp_add (&x0x0, &x1x1, &t2) != MP_OKAY) - goto X1X1; /* t2 = x0x0 + x1x1 */ - if (s_mp_sub (&t1, &t2, &t1) != MP_OKAY) - goto X1X1; /* t1 = (x1+x0)**2 - (x0x0 + x1x1) */ - - /* shift by B */ - if (mp_lshd (&t1, B) != MP_OKAY) - goto X1X1; /* t1 = (x0x0 + x1x1 - (x1-x0)*(x1-x0))<sign = MP_ZPOS; - -LBL_T: - mp_clear_multi (&t1, &t2, NULL); - return res; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_lcm.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_lshd.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_lshd.c deleted file mode 100644 index ffb0def..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_lshd.c +++ /dev/null @@ -1,67 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_LSHD_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* shift left a certain amount of digits */ -int mp_lshd (mp_int * a, int b) -{ - int x, res; - - /* if its less than zero return */ - if (b <= 0) { - return MP_OKAY; - } - - /* grow to fit the new digits */ - if (a->alloc < a->used + b) { - if ((res = mp_grow (a, a->used + b)) != MP_OKAY) { - return res; - } - } - - { - register mp_digit *top, *bottom; - - /* increment the used by the shift amount then copy upwards */ - a->used += b; - - /* top */ - top = a->dp + a->used - 1; - - /* base */ - bottom = a->dp + a->used - 1 - b; - - /* much like mp_rshd this is implemented using a sliding window - * except the window goes the otherway around. Copying from - * the bottom to the top. see bn_mp_rshd.c for more info. - */ - for (x = a->used - 1; x >= b; x--) { - *top-- = *bottom--; - } - - /* zero the lower digits */ - top = a->dp; - for (x = 0; x < b; x++) { - *top++ = 0; - } - } - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_lshd.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_mod.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_mod.c deleted file mode 100644 index b24c71f..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_mod.c +++ /dev/null @@ -1,48 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_MOD_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* c = a mod b, 0 <= c < b */ -int -mp_mod (mp_int * a, mp_int * b, mp_int * c) -{ - mp_int t; - int res; - - if ((res = mp_init (&t)) != MP_OKAY) { - return res; - } - - if ((res = mp_div (a, b, NULL, &t)) != MP_OKAY) { - mp_clear (&t); - return res; - } - - if (t.sign != b->sign) { - res = mp_add (b, &t, c); - } else { - res = MP_OKAY; - mp_exch (&t, c); - } - - mp_clear (&t); - return res; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_mod.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_mod_2d.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_mod_2d.c deleted file mode 100644 index a54a024..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_mod_2d.c +++ /dev/null @@ -1,55 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_MOD_2D_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* calc a value mod 2**b */ -int -mp_mod_2d (mp_int * a, int b, mp_int * c) -{ - int x, res; - - /* if b is <= 0 then zero the int */ - if (b <= 0) { - mp_zero (c); - return MP_OKAY; - } - - /* if the modulus is larger than the value than return */ - if (b >= (int) (a->used * DIGIT_BIT)) { - res = mp_copy (a, c); - return res; - } - - /* copy */ - if ((res = mp_copy (a, c)) != MP_OKAY) { - return res; - } - - /* zero digits above the last digit of the modulus */ - for (x = (b / DIGIT_BIT) + ((b % DIGIT_BIT) == 0 ? 0 : 1); x < c->used; x++) { - c->dp[x] = 0; - } - /* clear the digit that is not completely outside/inside the modulus */ - c->dp[b / DIGIT_BIT] &= - (mp_digit) ((((mp_digit) 1) << (((mp_digit) b) % DIGIT_BIT)) - ((mp_digit) 1)); - mp_clamp (c); - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_mod_2d.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_mod_d.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_mod_d.c deleted file mode 100644 index 59886e7..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_mod_d.c +++ /dev/null @@ -1,27 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_MOD_D_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -int -mp_mod_d (mp_int * a, mp_digit b, mp_digit * c) -{ - return mp_div_d(a, b, NULL, c); -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_mod_d.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_montgomery_calc_normalization.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_montgomery_calc_normalization.c deleted file mode 100644 index fdefcbd..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_montgomery_calc_normalization.c +++ /dev/null @@ -1,59 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_MONTGOMERY_CALC_NORMALIZATION_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* - * shifts with subtractions when the result is greater than b. - * - * The method is slightly modified to shift B unconditionally upto just under - * the leading bit of b. This saves alot of multiple precision shifting. - */ -int mp_montgomery_calc_normalization (mp_int * a, mp_int * b) -{ - int x, bits, res; - - /* how many bits of last digit does b use */ - bits = mp_count_bits (b) % DIGIT_BIT; - - if (b->used > 1) { - if ((res = mp_2expt (a, (b->used - 1) * DIGIT_BIT + bits - 1)) != MP_OKAY) { - return res; - } - } else { - mp_set(a, 1); - bits = 1; - } - - - /* now compute C = A * B mod b */ - for (x = bits - 1; x < (int)DIGIT_BIT; x++) { - if ((res = mp_mul_2 (a, a)) != MP_OKAY) { - return res; - } - if (mp_cmp_mag (a, b) != MP_LT) { - if ((res = s_mp_sub (a, b, a)) != MP_OKAY) { - return res; - } - } - } - - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_montgomery_calc_normalization.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_montgomery_reduce.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_montgomery_reduce.c deleted file mode 100644 index 173848e..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_montgomery_reduce.c +++ /dev/null @@ -1,118 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_MONTGOMERY_REDUCE_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* computes xR**-1 == x (mod N) via Montgomery Reduction */ -int -mp_montgomery_reduce (mp_int * x, mp_int * n, mp_digit rho) -{ - int ix, res, digs; - mp_digit mu; - - /* can the fast reduction [comba] method be used? - * - * Note that unlike in mul you're safely allowed *less* - * than the available columns [255 per default] since carries - * are fixed up in the inner loop. - */ - digs = n->used * 2 + 1; - if ((digs < MP_WARRAY) && - n->used < - (1 << ((CHAR_BIT * sizeof (mp_word)) - (2 * DIGIT_BIT)))) { - return fast_mp_montgomery_reduce (x, n, rho); - } - - /* grow the input as required */ - if (x->alloc < digs) { - if ((res = mp_grow (x, digs)) != MP_OKAY) { - return res; - } - } - x->used = digs; - - for (ix = 0; ix < n->used; ix++) { - /* mu = ai * rho mod b - * - * The value of rho must be precalculated via - * montgomery_setup() such that - * it equals -1/n0 mod b this allows the - * following inner loop to reduce the - * input one digit at a time - */ - mu = (mp_digit) (((mp_word)x->dp[ix]) * ((mp_word)rho) & MP_MASK); - - /* a = a + mu * m * b**i */ - { - register int iy; - register mp_digit *tmpn, *tmpx, u; - register mp_word r; - - /* alias for digits of the modulus */ - tmpn = n->dp; - - /* alias for the digits of x [the input] */ - tmpx = x->dp + ix; - - /* set the carry to zero */ - u = 0; - - /* Multiply and add in place */ - for (iy = 0; iy < n->used; iy++) { - /* compute product and sum */ - r = ((mp_word)mu) * ((mp_word)*tmpn++) + - ((mp_word) u) + ((mp_word) * tmpx); - - /* get carry */ - u = (mp_digit)(r >> ((mp_word) DIGIT_BIT)); - - /* fix digit */ - *tmpx++ = (mp_digit)(r & ((mp_word) MP_MASK)); - } - /* At this point the ix'th digit of x should be zero */ - - - /* propagate carries upwards as required*/ - while (u) { - *tmpx += u; - u = *tmpx >> DIGIT_BIT; - *tmpx++ &= MP_MASK; - } - } - } - - /* at this point the n.used'th least - * significant digits of x are all zero - * which means we can shift x to the - * right by n.used digits and the - * residue is unchanged. - */ - - /* x = x/b**n.used */ - mp_clamp(x); - mp_rshd (x, n->used); - - /* if x >= n then x = x - n */ - if (mp_cmp_mag (x, n) != MP_LT) { - return s_mp_sub (x, n, x); - } - - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_montgomery_reduce.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_montgomery_setup.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_montgomery_setup.c deleted file mode 100644 index 6f27732..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_montgomery_setup.c +++ /dev/null @@ -1,59 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_MONTGOMERY_SETUP_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* setups the montgomery reduction stuff */ -int -mp_montgomery_setup (mp_int * n, mp_digit * rho) -{ - mp_digit x, b; - -/* fast inversion mod 2**k - * - * Based on the fact that - * - * XA = 1 (mod 2**n) => (X(2-XA)) A = 1 (mod 2**2n) - * => 2*X*A - X*X*A*A = 1 - * => 2*(1) - (1) = 1 - */ - b = n->dp[0]; - - if ((b & 1) == 0) { - return MP_VAL; - } - - x = (((b + 2) & 4) << 1) + b; /* here x*a==1 mod 2**4 */ - x *= 2 - b * x; /* here x*a==1 mod 2**8 */ -#if !defined(MP_8BIT) - x *= 2 - b * x; /* here x*a==1 mod 2**16 */ -#endif -#if defined(MP_64BIT) || !(defined(MP_8BIT) || defined(MP_16BIT)) - x *= 2 - b * x; /* here x*a==1 mod 2**32 */ -#endif -#ifdef MP_64BIT - x *= 2 - b * x; /* here x*a==1 mod 2**64 */ -#endif - - /* rho = -1/m mod b */ - *rho = (unsigned long)(((mp_word)1 << ((mp_word) DIGIT_BIT)) - x) & MP_MASK; - - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_montgomery_setup.c,v $ */ -/* $Revision: 1.5 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_mul.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_mul.c deleted file mode 100644 index a1315da..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_mul.c +++ /dev/null @@ -1,66 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_MUL_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* high level multiplication (handles sign) */ -int mp_mul (mp_int * a, mp_int * b, mp_int * c) -{ - int res, neg; - neg = (a->sign == b->sign) ? MP_ZPOS : MP_NEG; - - /* use Toom-Cook? */ -#ifdef BN_MP_TOOM_MUL_C - if (MIN (a->used, b->used) >= TOOM_MUL_CUTOFF) { - res = mp_toom_mul(a, b, c); - } else -#endif -#ifdef BN_MP_KARATSUBA_MUL_C - /* use Karatsuba? */ - if (MIN (a->used, b->used) >= KARATSUBA_MUL_CUTOFF) { - res = mp_karatsuba_mul (a, b, c); - } else -#endif - { - /* can we use the fast multiplier? - * - * The fast multiplier can be used if the output will - * have less than MP_WARRAY digits and the number of - * digits won't affect carry propagation - */ - int digs = a->used + b->used + 1; - -#ifdef BN_FAST_S_MP_MUL_DIGS_C - if ((digs < MP_WARRAY) && - MIN(a->used, b->used) <= - (1 << ((CHAR_BIT * sizeof (mp_word)) - (2 * DIGIT_BIT)))) { - res = fast_s_mp_mul_digs (a, b, c, digs); - } else -#endif -#ifdef BN_S_MP_MUL_DIGS_C - res = s_mp_mul (a, b, c); /* uses s_mp_mul_digs */ -#else - res = MP_VAL; -#endif - - } - c->sign = (c->used > 0) ? neg : MP_ZPOS; - return res; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_mul.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_mul_2.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_mul_2.c deleted file mode 100644 index 3315744..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_mul_2.c +++ /dev/null @@ -1,82 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_MUL_2_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* b = a*2 */ -int mp_mul_2(mp_int * a, mp_int * b) -{ - int x, res, oldused; - - /* grow to accomodate result */ - if (b->alloc < a->used + 1) { - if ((res = mp_grow (b, a->used + 1)) != MP_OKAY) { - return res; - } - } - - oldused = b->used; - b->used = a->used; - - { - register mp_digit r, rr, *tmpa, *tmpb; - - /* alias for source */ - tmpa = a->dp; - - /* alias for dest */ - tmpb = b->dp; - - /* carry */ - r = 0; - for (x = 0; x < a->used; x++) { - - /* get what will be the *next* carry bit from the - * MSB of the current digit - */ - rr = *tmpa >> ((mp_digit)(DIGIT_BIT - 1)); - - /* now shift up this digit, add in the carry [from the previous] */ - *tmpb++ = ((*tmpa++ << ((mp_digit)1)) | r) & MP_MASK; - - /* copy the carry that would be from the source - * digit into the next iteration - */ - r = rr; - } - - /* new leading digit? */ - if (r != 0) { - /* add a MSB which is always 1 at this point */ - *tmpb = 1; - ++(b->used); - } - - /* now zero any excess digits on the destination - * that we didn't write to - */ - tmpb = b->dp + b->used; - for (x = b->used; x < oldused; x++) { - *tmpb++ = 0; - } - } - b->sign = a->sign; - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_mul_2.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_mul_2d.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_mul_2d.c deleted file mode 100644 index c636c17..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_mul_2d.c +++ /dev/null @@ -1,85 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_MUL_2D_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* shift left by a certain bit count */ -int mp_mul_2d (mp_int * a, int b, mp_int * c) -{ - mp_digit d; - int res; - - /* copy */ - if (a != c) { - if ((res = mp_copy (a, c)) != MP_OKAY) { - return res; - } - } - - if (c->alloc < (int)(c->used + b/DIGIT_BIT + 1)) { - if ((res = mp_grow (c, c->used + b / DIGIT_BIT + 1)) != MP_OKAY) { - return res; - } - } - - /* shift by as many digits in the bit count */ - if (b >= (int)DIGIT_BIT) { - if ((res = mp_lshd (c, b / DIGIT_BIT)) != MP_OKAY) { - return res; - } - } - - /* shift any bit count < DIGIT_BIT */ - d = (mp_digit) (b % DIGIT_BIT); - if (d != 0) { - register mp_digit *tmpc, shift, mask, r, rr; - register int x; - - /* bitmask for carries */ - mask = (((mp_digit)1) << d) - 1; - - /* shift for msbs */ - shift = DIGIT_BIT - d; - - /* alias */ - tmpc = c->dp; - - /* carry */ - r = 0; - for (x = 0; x < c->used; x++) { - /* get the higher bits of the current word */ - rr = (*tmpc >> shift) & mask; - - /* shift the current word and OR in the carry */ - *tmpc = ((*tmpc << d) | r) & MP_MASK; - ++tmpc; - - /* set the carry to the carry bits of the current word */ - r = rr; - } - - /* set final carry */ - if (r != 0) { - c->dp[(c->used)++] = r; - } - } - mp_clamp (c); - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_mul_2d.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_mul_d.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_mul_d.c deleted file mode 100644 index a36a76b..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_mul_d.c +++ /dev/null @@ -1,79 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_MUL_D_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* multiply by a digit */ -int -mp_mul_d (mp_int * a, mp_digit b, mp_int * c) -{ - mp_digit u, *tmpa, *tmpc; - mp_word r; - int ix, res, olduse; - - /* make sure c is big enough to hold a*b */ - if (c->alloc < a->used + 1) { - if ((res = mp_grow (c, a->used + 1)) != MP_OKAY) { - return res; - } - } - - /* get the original destinations used count */ - olduse = c->used; - - /* set the sign */ - c->sign = a->sign; - - /* alias for a->dp [source] */ - tmpa = a->dp; - - /* alias for c->dp [dest] */ - tmpc = c->dp; - - /* zero carry */ - u = 0; - - /* compute columns */ - for (ix = 0; ix < a->used; ix++) { - /* compute product and carry sum for this term */ - r = ((mp_word) u) + ((mp_word)*tmpa++) * ((mp_word)b); - - /* mask off higher bits to get a single digit */ - *tmpc++ = (mp_digit) (r & ((mp_word) MP_MASK)); - - /* send carry into next iteration */ - u = (mp_digit) (r >> ((mp_word) DIGIT_BIT)); - } - - /* store final carry [if any] and increment ix offset */ - *tmpc++ = u; - ++ix; - - /* now zero digits above the top */ - while (ix++ < olduse) { - *tmpc++ = 0; - } - - /* set used count */ - c->used = a->used + 1; - mp_clamp(c); - - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_mul_d.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_mulmod.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_mulmod.c deleted file mode 100644 index 8ec98bb..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_mulmod.c +++ /dev/null @@ -1,40 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_MULMOD_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* d = a * b (mod c) */ -int mp_mulmod (mp_int * a, mp_int * b, mp_int * c, mp_int * d) -{ - int res; - mp_int t; - - if ((res = mp_init (&t)) != MP_OKAY) { - return res; - } - - if ((res = mp_mul (a, b, &t)) != MP_OKAY) { - mp_clear (&t); - return res; - } - res = mp_mod (&t, c, d); - mp_clear (&t); - return res; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_mulmod.c,v $ */ -/* $Revision: 1.5 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_n_root.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_n_root.c deleted file mode 100644 index f188f52..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_n_root.c +++ /dev/null @@ -1,132 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_N_ROOT_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* find the n'th root of an integer - * - * Result found such that (c)**b <= a and (c+1)**b > a - * - * This algorithm uses Newton's approximation - * x[i+1] = x[i] - f(x[i])/f'(x[i]) - * which will find the root in log(N) time where - * each step involves a fair bit. This is not meant to - * find huge roots [square and cube, etc]. - */ -int mp_n_root (mp_int * a, mp_digit b, mp_int * c) -{ - mp_int t1, t2, t3; - int res, neg; - - /* input must be positive if b is even */ - if ((b & 1) == 0 && a->sign == MP_NEG) { - return MP_VAL; - } - - if ((res = mp_init (&t1)) != MP_OKAY) { - return res; - } - - if ((res = mp_init (&t2)) != MP_OKAY) { - goto LBL_T1; - } - - if ((res = mp_init (&t3)) != MP_OKAY) { - goto LBL_T2; - } - - /* if a is negative fudge the sign but keep track */ - neg = a->sign; - a->sign = MP_ZPOS; - - /* t2 = 2 */ - mp_set (&t2, 2); - - do { - /* t1 = t2 */ - if ((res = mp_copy (&t2, &t1)) != MP_OKAY) { - goto LBL_T3; - } - - /* t2 = t1 - ((t1**b - a) / (b * t1**(b-1))) */ - - /* t3 = t1**(b-1) */ - if ((res = mp_expt_d (&t1, b - 1, &t3)) != MP_OKAY) { - goto LBL_T3; - } - - /* numerator */ - /* t2 = t1**b */ - if ((res = mp_mul (&t3, &t1, &t2)) != MP_OKAY) { - goto LBL_T3; - } - - /* t2 = t1**b - a */ - if ((res = mp_sub (&t2, a, &t2)) != MP_OKAY) { - goto LBL_T3; - } - - /* denominator */ - /* t3 = t1**(b-1) * b */ - if ((res = mp_mul_d (&t3, b, &t3)) != MP_OKAY) { - goto LBL_T3; - } - - /* t3 = (t1**b - a)/(b * t1**(b-1)) */ - if ((res = mp_div (&t2, &t3, &t3, NULL)) != MP_OKAY) { - goto LBL_T3; - } - - if ((res = mp_sub (&t1, &t3, &t2)) != MP_OKAY) { - goto LBL_T3; - } - } while (mp_cmp (&t1, &t2) != MP_EQ); - - /* result can be off by a few so check */ - for (;;) { - if ((res = mp_expt_d (&t1, b, &t2)) != MP_OKAY) { - goto LBL_T3; - } - - if (mp_cmp (&t2, a) == MP_GT) { - if ((res = mp_sub_d (&t1, 1, &t1)) != MP_OKAY) { - goto LBL_T3; - } - } else { - break; - } - } - - /* reset the sign of a first */ - a->sign = neg; - - /* set the result */ - mp_exch (&t1, c); - - /* set the sign of the result */ - c->sign = neg; - - res = MP_OKAY; - -LBL_T3:mp_clear (&t3); -LBL_T2:mp_clear (&t2); -LBL_T1:mp_clear (&t1); - return res; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_n_root.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_neg.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_neg.c deleted file mode 100644 index 87a8b50..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_neg.c +++ /dev/null @@ -1,40 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_NEG_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* b = -a */ -int mp_neg (mp_int * a, mp_int * b) -{ - int res; - if (a != b) { - if ((res = mp_copy (a, b)) != MP_OKAY) { - return res; - } - } - - if (mp_iszero(b) != MP_YES) { - b->sign = (a->sign == MP_ZPOS) ? MP_NEG : MP_ZPOS; - } else { - b->sign = MP_ZPOS; - } - - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_neg.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_or.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_or.c deleted file mode 100644 index 12601ea..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_or.c +++ /dev/null @@ -1,50 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_OR_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* OR two ints together */ -int mp_or (mp_int * a, mp_int * b, mp_int * c) -{ - int res, ix, px; - mp_int t, *x; - - if (a->used > b->used) { - if ((res = mp_init_copy (&t, a)) != MP_OKAY) { - return res; - } - px = b->used; - x = b; - } else { - if ((res = mp_init_copy (&t, b)) != MP_OKAY) { - return res; - } - px = a->used; - x = a; - } - - for (ix = 0; ix < px; ix++) { - t.dp[ix] |= x->dp[ix]; - } - mp_clamp (&t); - mp_exch (c, &t); - mp_clear (&t); - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_or.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_prime_fermat.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_prime_fermat.c deleted file mode 100644 index 297e13c..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_prime_fermat.c +++ /dev/null @@ -1,62 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_PRIME_FERMAT_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* performs one Fermat test. - * - * If "a" were prime then b**a == b (mod a) since the order of - * the multiplicative sub-group would be phi(a) = a-1. That means - * it would be the same as b**(a mod (a-1)) == b**1 == b (mod a). - * - * Sets result to 1 if the congruence holds, or zero otherwise. - */ -int mp_prime_fermat (mp_int * a, mp_int * b, int *result) -{ - mp_int t; - int err; - - /* default to composite */ - *result = MP_NO; - - /* ensure b > 1 */ - if (mp_cmp_d(b, 1) != MP_GT) { - return MP_VAL; - } - - /* init t */ - if ((err = mp_init (&t)) != MP_OKAY) { - return err; - } - - /* compute t = b**a mod a */ - if ((err = mp_exptmod (b, a, a, &t)) != MP_OKAY) { - goto LBL_T; - } - - /* is it equal to b? */ - if (mp_cmp (&t, b) == MP_EQ) { - *result = MP_YES; - } - - err = MP_OKAY; -LBL_T:mp_clear (&t); - return err; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_prime_fermat.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_prime_is_divisible.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_prime_is_divisible.c deleted file mode 100644 index 0ae6498..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_prime_is_divisible.c +++ /dev/null @@ -1,50 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_PRIME_IS_DIVISIBLE_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* determines if an integers is divisible by one - * of the first PRIME_SIZE primes or not - * - * sets result to 0 if not, 1 if yes - */ -int mp_prime_is_divisible (mp_int * a, int *result) -{ - int err, ix; - mp_digit res; - - /* default to not */ - *result = MP_NO; - - for (ix = 0; ix < PRIME_SIZE; ix++) { - /* what is a mod LBL_prime_tab[ix] */ - if ((err = mp_mod_d (a, ltm_prime_tab[ix], &res)) != MP_OKAY) { - return err; - } - - /* is the residue zero? */ - if (res == 0) { - *result = MP_YES; - return MP_OKAY; - } - } - - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_prime_is_divisible.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_prime_is_prime.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_prime_is_prime.c deleted file mode 100644 index 0e1e94b..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_prime_is_prime.c +++ /dev/null @@ -1,83 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_PRIME_IS_PRIME_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* performs a variable number of rounds of Miller-Rabin - * - * Probability of error after t rounds is no more than - - * - * Sets result to 1 if probably prime, 0 otherwise - */ -int mp_prime_is_prime (mp_int * a, int t, int *result) -{ - mp_int b; - int ix, err, res; - - /* default to no */ - *result = MP_NO; - - /* valid value of t? */ - if (t <= 0 || t > PRIME_SIZE) { - return MP_VAL; - } - - /* is the input equal to one of the primes in the table? */ - for (ix = 0; ix < PRIME_SIZE; ix++) { - if (mp_cmp_d(a, ltm_prime_tab[ix]) == MP_EQ) { - *result = 1; - return MP_OKAY; - } - } - - /* first perform trial division */ - if ((err = mp_prime_is_divisible (a, &res)) != MP_OKAY) { - return err; - } - - /* return if it was trivially divisible */ - if (res == MP_YES) { - return MP_OKAY; - } - - /* now perform the miller-rabin rounds */ - if ((err = mp_init (&b)) != MP_OKAY) { - return err; - } - - for (ix = 0; ix < t; ix++) { - /* set the prime */ - mp_set (&b, ltm_prime_tab[ix]); - - if ((err = mp_prime_miller_rabin (a, &b, &res)) != MP_OKAY) { - goto LBL_B; - } - - if (res == MP_NO) { - goto LBL_B; - } - } - - /* passed the test */ - *result = MP_YES; -LBL_B:mp_clear (&b); - return err; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_prime_is_prime.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_prime_miller_rabin.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_prime_miller_rabin.c deleted file mode 100644 index 47385bc..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_prime_miller_rabin.c +++ /dev/null @@ -1,103 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_PRIME_MILLER_RABIN_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* Miller-Rabin test of "a" to the base of "b" as described in - * HAC pp. 139 Algorithm 4.24 - * - * Sets result to 0 if definitely composite or 1 if probably prime. - * Randomly the chance of error is no more than 1/4 and often - * very much lower. - */ -int mp_prime_miller_rabin (mp_int * a, mp_int * b, int *result) -{ - mp_int n1, y, r; - int s, j, err; - - /* default */ - *result = MP_NO; - - /* ensure b > 1 */ - if (mp_cmp_d(b, 1) != MP_GT) { - return MP_VAL; - } - - /* get n1 = a - 1 */ - if ((err = mp_init_copy (&n1, a)) != MP_OKAY) { - return err; - } - if ((err = mp_sub_d (&n1, 1, &n1)) != MP_OKAY) { - goto LBL_N1; - } - - /* set 2**s * r = n1 */ - if ((err = mp_init_copy (&r, &n1)) != MP_OKAY) { - goto LBL_N1; - } - - /* count the number of least significant bits - * which are zero - */ - s = mp_cnt_lsb(&r); - - /* now divide n - 1 by 2**s */ - if ((err = mp_div_2d (&r, s, &r, NULL)) != MP_OKAY) { - goto LBL_R; - } - - /* compute y = b**r mod a */ - if ((err = mp_init (&y)) != MP_OKAY) { - goto LBL_R; - } - if ((err = mp_exptmod (b, &r, a, &y)) != MP_OKAY) { - goto LBL_Y; - } - - /* if y != 1 and y != n1 do */ - if (mp_cmp_d (&y, 1) != MP_EQ && mp_cmp (&y, &n1) != MP_EQ) { - j = 1; - /* while j <= s-1 and y != n1 */ - while ((j <= (s - 1)) && mp_cmp (&y, &n1) != MP_EQ) { - if ((err = mp_sqrmod (&y, a, &y)) != MP_OKAY) { - goto LBL_Y; - } - - /* if y == 1 then composite */ - if (mp_cmp_d (&y, 1) == MP_EQ) { - goto LBL_Y; - } - - ++j; - } - - /* if y != n1 then composite */ - if (mp_cmp (&y, &n1) != MP_EQ) { - goto LBL_Y; - } - } - - /* probably prime now */ - *result = MP_YES; -LBL_Y:mp_clear (&y); -LBL_R:mp_clear (&r); -LBL_N1:mp_clear (&n1); - return err; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_prime_miller_rabin.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_prime_next_prime.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_prime_next_prime.c deleted file mode 100644 index 833992b..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_prime_next_prime.c +++ /dev/null @@ -1,170 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_PRIME_NEXT_PRIME_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* finds the next prime after the number "a" using "t" trials - * of Miller-Rabin. - * - * bbs_style = 1 means the prime must be congruent to 3 mod 4 - */ -int mp_prime_next_prime(mp_int *a, int t, int bbs_style) -{ - int err, res, x, y; - mp_digit res_tab[PRIME_SIZE], step, kstep; - mp_int b; - - /* ensure t is valid */ - if (t <= 0 || t > PRIME_SIZE) { - return MP_VAL; - } - - /* force positive */ - a->sign = MP_ZPOS; - - /* simple algo if a is less than the largest prime in the table */ - if (mp_cmp_d(a, ltm_prime_tab[PRIME_SIZE-1]) == MP_LT) { - /* find which prime it is bigger than */ - for (x = PRIME_SIZE - 2; x >= 0; x--) { - if (mp_cmp_d(a, ltm_prime_tab[x]) != MP_LT) { - if (bbs_style == 1) { - /* ok we found a prime smaller or - * equal [so the next is larger] - * - * however, the prime must be - * congruent to 3 mod 4 - */ - if ((ltm_prime_tab[x + 1] & 3) != 3) { - /* scan upwards for a prime congruent to 3 mod 4 */ - for (y = x + 1; y < PRIME_SIZE; y++) { - if ((ltm_prime_tab[y] & 3) == 3) { - mp_set(a, ltm_prime_tab[y]); - return MP_OKAY; - } - } - } - } else { - mp_set(a, ltm_prime_tab[x + 1]); - return MP_OKAY; - } - } - } - /* at this point a maybe 1 */ - if (mp_cmp_d(a, 1) == MP_EQ) { - mp_set(a, 2); - return MP_OKAY; - } - /* fall through to the sieve */ - } - - /* generate a prime congruent to 3 mod 4 or 1/3 mod 4? */ - if (bbs_style == 1) { - kstep = 4; - } else { - kstep = 2; - } - - /* at this point we will use a combination of a sieve and Miller-Rabin */ - - if (bbs_style == 1) { - /* if a mod 4 != 3 subtract the correct value to make it so */ - if ((a->dp[0] & 3) != 3) { - if ((err = mp_sub_d(a, (a->dp[0] & 3) + 1, a)) != MP_OKAY) { return err; }; - } - } else { - if (mp_iseven(a) == 1) { - /* force odd */ - if ((err = mp_sub_d(a, 1, a)) != MP_OKAY) { - return err; - } - } - } - - /* generate the restable */ - for (x = 1; x < PRIME_SIZE; x++) { - if ((err = mp_mod_d(a, ltm_prime_tab[x], res_tab + x)) != MP_OKAY) { - return err; - } - } - - /* init temp used for Miller-Rabin Testing */ - if ((err = mp_init(&b)) != MP_OKAY) { - return err; - } - - for (;;) { - /* skip to the next non-trivially divisible candidate */ - step = 0; - do { - /* y == 1 if any residue was zero [e.g. cannot be prime] */ - y = 0; - - /* increase step to next candidate */ - step += kstep; - - /* compute the new residue without using division */ - for (x = 1; x < PRIME_SIZE; x++) { - /* add the step to each residue */ - res_tab[x] += kstep; - - /* subtract the modulus [instead of using division] */ - if (res_tab[x] >= ltm_prime_tab[x]) { - res_tab[x] -= ltm_prime_tab[x]; - } - - /* set flag if zero */ - if (res_tab[x] == 0) { - y = 1; - } - } - } while (y == 1 && step < ((((mp_digit)1)<= ((((mp_digit)1)< size) { - return (x == 0) ? sizes[0].t : sizes[x - 1].t; - } - } - return sizes[x-1].t + 1; -} - - -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_prime_rabin_miller_trials.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_prime_random_ex.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_prime_random_ex.c deleted file mode 100644 index 4eec3f6..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_prime_random_ex.c +++ /dev/null @@ -1,125 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_PRIME_RANDOM_EX_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* makes a truly random prime of a given size (bits), - * - * Flags are as follows: - * - * LTM_PRIME_BBS - make prime congruent to 3 mod 4 - * LTM_PRIME_SAFE - make sure (p-1)/2 is prime as well (implies LTM_PRIME_BBS) - * LTM_PRIME_2MSB_OFF - make the 2nd highest bit zero - * LTM_PRIME_2MSB_ON - make the 2nd highest bit one - * - * You have to supply a callback which fills in a buffer with random bytes. "dat" is a parameter you can - * have passed to the callback (e.g. a state or something). This function doesn't use "dat" itself - * so it can be NULL - * - */ - -/* This is possibly the mother of all prime generation functions, muahahahahaha! */ -int mp_prime_random_ex(mp_int *a, int t, int size, int flags, ltm_prime_callback cb, void *dat) -{ - unsigned char *tmp, maskAND, maskOR_msb, maskOR_lsb; - int res, err, bsize, maskOR_msb_offset; - - /* sanity check the input */ - if (size <= 1 || t <= 0) { - return MP_VAL; - } - - /* LTM_PRIME_SAFE implies LTM_PRIME_BBS */ - if (flags & LTM_PRIME_SAFE) { - flags |= LTM_PRIME_BBS; - } - - /* calc the byte size */ - bsize = (size>>3) + ((size&7)?1:0); - - /* we need a buffer of bsize bytes */ - tmp = OPT_CAST(unsigned char) XMALLOC(bsize); - if (tmp == NULL) { - return MP_MEM; - } - - /* calc the maskAND value for the MSbyte*/ - maskAND = ((size&7) == 0) ? 0xFF : (0xFF >> (8 - (size & 7))); - - /* calc the maskOR_msb */ - maskOR_msb = 0; - maskOR_msb_offset = ((size & 7) == 1) ? 1 : 0; - if (flags & LTM_PRIME_2MSB_ON) { - maskOR_msb |= 0x80 >> ((9 - size) & 7); - } - - /* get the maskOR_lsb */ - maskOR_lsb = 1; - if (flags & LTM_PRIME_BBS) { - maskOR_lsb |= 3; - } - - do { - /* read the bytes */ - if (cb(tmp, bsize, dat) != bsize) { - err = MP_VAL; - goto error; - } - - /* work over the MSbyte */ - tmp[0] &= maskAND; - tmp[0] |= 1 << ((size - 1) & 7); - - /* mix in the maskORs */ - tmp[maskOR_msb_offset] |= maskOR_msb; - tmp[bsize-1] |= maskOR_lsb; - - /* read it in */ - if ((err = mp_read_unsigned_bin(a, tmp, bsize)) != MP_OKAY) { goto error; } - - /* is it prime? */ - if ((err = mp_prime_is_prime(a, t, &res)) != MP_OKAY) { goto error; } - if (res == MP_NO) { - continue; - } - - if (flags & LTM_PRIME_SAFE) { - /* see if (a-1)/2 is prime */ - if ((err = mp_sub_d(a, 1, a)) != MP_OKAY) { goto error; } - if ((err = mp_div_2(a, a)) != MP_OKAY) { goto error; } - - /* is it prime? */ - if ((err = mp_prime_is_prime(a, t, &res)) != MP_OKAY) { goto error; } - } - } while (res == MP_NO); - - if (flags & LTM_PRIME_SAFE) { - /* restore a to the original value */ - if ((err = mp_mul_2(a, a)) != MP_OKAY) { goto error; } - if ((err = mp_add_d(a, 1, a)) != MP_OKAY) { goto error; } - } - - err = MP_OKAY; -error: - XFREE(tmp); - return err; -} - - -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_prime_random_ex.c,v $ */ -/* $Revision: 1.5 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_radix_size.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_radix_size.c deleted file mode 100644 index 2378f1f..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_radix_size.c +++ /dev/null @@ -1,78 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_RADIX_SIZE_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* returns size of ASCII reprensentation */ -int mp_radix_size (mp_int * a, int radix, int *size) -{ - int res, digs; - mp_int t; - mp_digit d; - - *size = 0; - - /* special case for binary */ - if (radix == 2) { - *size = mp_count_bits (a) + (a->sign == MP_NEG ? 1 : 0) + 1; - return MP_OKAY; - } - - /* make sure the radix is in range */ - if (radix < 2 || radix > 64) { - return MP_VAL; - } - - if (mp_iszero(a) == MP_YES) { - *size = 2; - return MP_OKAY; - } - - /* digs is the digit count */ - digs = 0; - - /* if it's negative add one for the sign */ - if (a->sign == MP_NEG) { - ++digs; - } - - /* init a copy of the input */ - if ((res = mp_init_copy (&t, a)) != MP_OKAY) { - return res; - } - - /* force temp to positive */ - t.sign = MP_ZPOS; - - /* fetch out all of the digits */ - while (mp_iszero (&t) == MP_NO) { - if ((res = mp_div_d (&t, (mp_digit) radix, &t, &d)) != MP_OKAY) { - mp_clear (&t); - return res; - } - ++digs; - } - mp_clear (&t); - - /* return digs + 1, the 1 is for the NULL byte that would be required. */ - *size = digs + 1; - return MP_OKAY; -} - -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_radix_size.c,v $ */ -/* $Revision: 1.5 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_radix_smap.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_radix_smap.c deleted file mode 100644 index 5cbe952..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_radix_smap.c +++ /dev/null @@ -1,24 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_RADIX_SMAP_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* chars used in radix conversions */ -const char *mp_s_rmap = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz+/"; -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_radix_smap.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_rand.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_rand.c deleted file mode 100644 index e124178..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_rand.c +++ /dev/null @@ -1,55 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_RAND_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* makes a pseudo-random int of a given size */ -int -mp_rand (mp_int * a, int digits) -{ - int res; - mp_digit d; - - mp_zero (a); - if (digits <= 0) { - return MP_OKAY; - } - - /* first place a random non-zero digit */ - do { - d = ((mp_digit) abs (rand ())) & MP_MASK; - } while (d == 0); - - if ((res = mp_add_d (a, d, a)) != MP_OKAY) { - return res; - } - - while (--digits > 0) { - if ((res = mp_lshd (a, 1)) != MP_OKAY) { - return res; - } - - if ((res = mp_add_d (a, ((mp_digit) abs (rand ())), a)) != MP_OKAY) { - return res; - } - } - - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_rand.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_read_radix.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_read_radix.c deleted file mode 100644 index 6869668..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_read_radix.c +++ /dev/null @@ -1,85 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_READ_RADIX_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* read a string [ASCII] in a given radix */ -int mp_read_radix (mp_int * a, const char *str, int radix) -{ - int y, res, neg; - char ch; - - /* zero the digit bignum */ - mp_zero(a); - - /* make sure the radix is ok */ - if (radix < 2 || radix > 64) { - return MP_VAL; - } - - /* if the leading digit is a - * minus set the sign to negative. - */ - if (*str == '-') { - ++str; - neg = MP_NEG; - } else { - neg = MP_ZPOS; - } - - /* set the integer to the default of zero */ - mp_zero (a); - - /* process each digit of the string */ - while (*str) { - /* if the radix < 36 the conversion is case insensitive - * this allows numbers like 1AB and 1ab to represent the same value - * [e.g. in hex] - */ - ch = (char) ((radix < 36) ? toupper (*str) : *str); - for (y = 0; y < 64; y++) { - if (ch == mp_s_rmap[y]) { - break; - } - } - - /* if the char was found in the map - * and is less than the given radix add it - * to the number, otherwise exit the loop. - */ - if (y < radix) { - if ((res = mp_mul_d (a, (mp_digit) radix, a)) != MP_OKAY) { - return res; - } - if ((res = mp_add_d (a, (mp_digit) y, a)) != MP_OKAY) { - return res; - } - } else { - break; - } - ++str; - } - - /* set the sign only if a != 0 */ - if (mp_iszero(a) != 1) { - a->sign = neg; - } - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_read_radix.c,v $ */ -/* $Revision: 1.5 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_read_signed_bin.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_read_signed_bin.c deleted file mode 100644 index e9a780c..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_read_signed_bin.c +++ /dev/null @@ -1,41 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_READ_SIGNED_BIN_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* read signed bin, big endian, first byte is 0==positive or 1==negative */ -int mp_read_signed_bin (mp_int * a, const unsigned char *b, int c) -{ - int res; - - /* read magnitude */ - if ((res = mp_read_unsigned_bin (a, b + 1, c - 1)) != MP_OKAY) { - return res; - } - - /* first byte is 0 for positive, non-zero for negative */ - if (b[0] == 0) { - a->sign = MP_ZPOS; - } else { - a->sign = MP_NEG; - } - - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_read_signed_bin.c,v $ */ -/* $Revision: 1.5 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_read_unsigned_bin.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_read_unsigned_bin.c deleted file mode 100644 index 7d35370..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_read_unsigned_bin.c +++ /dev/null @@ -1,55 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_READ_UNSIGNED_BIN_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* reads a unsigned char array, assumes the msb is stored first [big endian] */ -int mp_read_unsigned_bin (mp_int * a, const unsigned char *b, int c) -{ - int res; - - /* make sure there are at least two digits */ - if (a->alloc < 2) { - if ((res = mp_grow(a, 2)) != MP_OKAY) { - return res; - } - } - - /* zero the int */ - mp_zero (a); - - /* read the bytes in */ - while (c-- > 0) { - if ((res = mp_mul_2d (a, 8, a)) != MP_OKAY) { - return res; - } - -#ifndef MP_8BIT - a->dp[0] |= *b++; - a->used += 1; -#else - a->dp[0] = (*b & MP_MASK); - a->dp[1] |= ((*b++ >> 7U) & 1); - a->used += 2; -#endif - } - mp_clamp (a); - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_read_unsigned_bin.c,v $ */ -/* $Revision: 1.5 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_reduce.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_reduce.c deleted file mode 100644 index 3a6bb5a..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_reduce.c +++ /dev/null @@ -1,100 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_REDUCE_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* reduces x mod m, assumes 0 < x < m**2, mu is - * precomputed via mp_reduce_setup. - * From HAC pp.604 Algorithm 14.42 - */ -int mp_reduce (mp_int * x, mp_int * m, mp_int * mu) -{ - mp_int q; - int res, um = m->used; - - /* q = x */ - if ((res = mp_init_copy (&q, x)) != MP_OKAY) { - return res; - } - - /* q1 = x / b**(k-1) */ - mp_rshd (&q, um - 1); - - /* according to HAC this optimization is ok */ - if (((unsigned long) um) > (((mp_digit)1) << (DIGIT_BIT - 1))) { - if ((res = mp_mul (&q, mu, &q)) != MP_OKAY) { - goto CLEANUP; - } - } else { -#ifdef BN_S_MP_MUL_HIGH_DIGS_C - if ((res = s_mp_mul_high_digs (&q, mu, &q, um)) != MP_OKAY) { - goto CLEANUP; - } -#elif defined(BN_FAST_S_MP_MUL_HIGH_DIGS_C) - if ((res = fast_s_mp_mul_high_digs (&q, mu, &q, um)) != MP_OKAY) { - goto CLEANUP; - } -#else - { - res = MP_VAL; - goto CLEANUP; - } -#endif - } - - /* q3 = q2 / b**(k+1) */ - mp_rshd (&q, um + 1); - - /* x = x mod b**(k+1), quick (no division) */ - if ((res = mp_mod_2d (x, DIGIT_BIT * (um + 1), x)) != MP_OKAY) { - goto CLEANUP; - } - - /* q = q * m mod b**(k+1), quick (no division) */ - if ((res = s_mp_mul_digs (&q, m, &q, um + 1)) != MP_OKAY) { - goto CLEANUP; - } - - /* x = x - q */ - if ((res = mp_sub (x, &q, x)) != MP_OKAY) { - goto CLEANUP; - } - - /* If x < 0, add b**(k+1) to it */ - if (mp_cmp_d (x, 0) == MP_LT) { - mp_set (&q, 1); - if ((res = mp_lshd (&q, um + 1)) != MP_OKAY) - goto CLEANUP; - if ((res = mp_add (x, &q, x)) != MP_OKAY) - goto CLEANUP; - } - - /* Back off if it's too big */ - while (mp_cmp (x, m) != MP_LT) { - if ((res = s_mp_sub (x, m, x)) != MP_OKAY) { - goto CLEANUP; - } - } - -CLEANUP: - mp_clear (&q); - - return res; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_reduce.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_reduce_2k.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_reduce_2k.c deleted file mode 100644 index 3191d82..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_reduce_2k.c +++ /dev/null @@ -1,61 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_REDUCE_2K_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* reduces a modulo n where n is of the form 2**p - d */ -int mp_reduce_2k(mp_int *a, mp_int *n, mp_digit d) -{ - mp_int q; - int p, res; - - if ((res = mp_init(&q)) != MP_OKAY) { - return res; - } - - p = mp_count_bits(n); -top: - /* q = a/2**p, a = a mod 2**p */ - if ((res = mp_div_2d(a, p, &q, a)) != MP_OKAY) { - goto ERR; - } - - if (d != 1) { - /* q = q * d */ - if ((res = mp_mul_d(&q, d, &q)) != MP_OKAY) { - goto ERR; - } - } - - /* a = a + q */ - if ((res = s_mp_add(a, &q, a)) != MP_OKAY) { - goto ERR; - } - - if (mp_cmp_mag(a, n) != MP_LT) { - s_mp_sub(a, n, a); - goto top; - } - -ERR: - mp_clear(&q); - return res; -} - -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_reduce_2k.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_reduce_2k_l.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_reduce_2k_l.c deleted file mode 100644 index 49b7e34..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_reduce_2k_l.c +++ /dev/null @@ -1,62 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_REDUCE_2K_L_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* reduces a modulo n where n is of the form 2**p - d - This differs from reduce_2k since "d" can be larger - than a single digit. -*/ -int mp_reduce_2k_l(mp_int *a, mp_int *n, mp_int *d) -{ - mp_int q; - int p, res; - - if ((res = mp_init(&q)) != MP_OKAY) { - return res; - } - - p = mp_count_bits(n); -top: - /* q = a/2**p, a = a mod 2**p */ - if ((res = mp_div_2d(a, p, &q, a)) != MP_OKAY) { - goto ERR; - } - - /* q = q * d */ - if ((res = mp_mul(&q, d, &q)) != MP_OKAY) { - goto ERR; - } - - /* a = a + q */ - if ((res = s_mp_add(a, &q, a)) != MP_OKAY) { - goto ERR; - } - - if (mp_cmp_mag(a, n) != MP_LT) { - s_mp_sub(a, n, a); - goto top; - } - -ERR: - mp_clear(&q); - return res; -} - -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_reduce_2k_l.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_reduce_2k_setup.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_reduce_2k_setup.c deleted file mode 100644 index aa3b3ba..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_reduce_2k_setup.c +++ /dev/null @@ -1,47 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_REDUCE_2K_SETUP_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* determines the setup value */ -int mp_reduce_2k_setup(mp_int *a, mp_digit *d) -{ - int res, p; - mp_int tmp; - - if ((res = mp_init(&tmp)) != MP_OKAY) { - return res; - } - - p = mp_count_bits(a); - if ((res = mp_2expt(&tmp, p)) != MP_OKAY) { - mp_clear(&tmp); - return res; - } - - if ((res = s_mp_sub(&tmp, a, &tmp)) != MP_OKAY) { - mp_clear(&tmp); - return res; - } - - *d = tmp.dp[0]; - mp_clear(&tmp); - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_reduce_2k_setup.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_reduce_2k_setup_l.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_reduce_2k_setup_l.c deleted file mode 100644 index 4eca870..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_reduce_2k_setup_l.c +++ /dev/null @@ -1,44 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_REDUCE_2K_SETUP_L_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* determines the setup value */ -int mp_reduce_2k_setup_l(mp_int *a, mp_int *d) -{ - int res; - mp_int tmp; - - if ((res = mp_init(&tmp)) != MP_OKAY) { - return res; - } - - if ((res = mp_2expt(&tmp, mp_count_bits(a))) != MP_OKAY) { - goto ERR; - } - - if ((res = s_mp_sub(&tmp, a, d)) != MP_OKAY) { - goto ERR; - } - -ERR: - mp_clear(&tmp); - return res; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_reduce_2k_setup_l.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_reduce_is_2k.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_reduce_is_2k.c deleted file mode 100644 index b9ede97..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_reduce_is_2k.c +++ /dev/null @@ -1,52 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_REDUCE_IS_2K_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* determines if mp_reduce_2k can be used */ -int mp_reduce_is_2k(mp_int *a) -{ - int ix, iy, iw; - mp_digit iz; - - if (a->used == 0) { - return MP_NO; - } else if (a->used == 1) { - return MP_YES; - } else if (a->used > 1) { - iy = mp_count_bits(a); - iz = 1; - iw = 1; - - /* Test every bit from the second digit up, must be 1 */ - for (ix = DIGIT_BIT; ix < iy; ix++) { - if ((a->dp[iw] & iz) == 0) { - return MP_NO; - } - iz <<= 1; - if (iz > (mp_digit)MP_MASK) { - ++iw; - iz = 1; - } - } - } - return MP_YES; -} - -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_reduce_is_2k.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_reduce_is_2k_l.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_reduce_is_2k_l.c deleted file mode 100644 index 787875f..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_reduce_is_2k_l.c +++ /dev/null @@ -1,44 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_REDUCE_IS_2K_L_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* determines if reduce_2k_l can be used */ -int mp_reduce_is_2k_l(mp_int *a) -{ - int ix, iy; - - if (a->used == 0) { - return MP_NO; - } else if (a->used == 1) { - return MP_YES; - } else if (a->used > 1) { - /* if more than half of the digits are -1 we're sold */ - for (iy = ix = 0; ix < a->used; ix++) { - if (a->dp[ix] == MP_MASK) { - ++iy; - } - } - return (iy >= (a->used/2)) ? MP_YES : MP_NO; - - } - return MP_NO; -} - -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_reduce_is_2k_l.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_reduce_setup.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_reduce_setup.c deleted file mode 100644 index 00e0a62..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_reduce_setup.c +++ /dev/null @@ -1,34 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_REDUCE_SETUP_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* pre-calculate the value required for Barrett reduction - * For a given modulus "b" it calulates the value required in "a" - */ -int mp_reduce_setup (mp_int * a, mp_int * b) -{ - int res; - - if ((res = mp_2expt (a, b->used * 2 * DIGIT_BIT)) != MP_OKAY) { - return res; - } - return mp_div (a, b, a, NULL); -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_reduce_setup.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_rshd.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_rshd.c deleted file mode 100644 index eac6721..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_rshd.c +++ /dev/null @@ -1,72 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_RSHD_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* shift right a certain amount of digits */ -void mp_rshd (mp_int * a, int b) -{ - int x; - - /* if b <= 0 then ignore it */ - if (b <= 0) { - return; - } - - /* if b > used then simply zero it and return */ - if (a->used <= b) { - mp_zero (a); - return; - } - - { - register mp_digit *bottom, *top; - - /* shift the digits down */ - - /* bottom */ - bottom = a->dp; - - /* top [offset into digits] */ - top = a->dp + b; - - /* this is implemented as a sliding window where - * the window is b-digits long and digits from - * the top of the window are copied to the bottom - * - * e.g. - - b-2 | b-1 | b0 | b1 | b2 | ... | bb | ----> - /\ | ----> - \-------------------/ ----> - */ - for (x = 0; x < (a->used - b); x++) { - *bottom++ = *top++; - } - - /* zero the top digits */ - for (; x < a->used; x++) { - *bottom++ = 0; - } - } - - /* remove excess digits */ - a->used -= b; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_rshd.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_set.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_set.c deleted file mode 100644 index d76d5bb..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_set.c +++ /dev/null @@ -1,29 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_SET_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* set to a digit */ -void mp_set (mp_int * a, mp_digit b) -{ - mp_zero (a); - a->dp[0] = b & MP_MASK; - a->used = (a->dp[0] != 0) ? 1 : 0; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_set.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_set_int.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_set_int.c deleted file mode 100644 index 68cf0e3..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_set_int.c +++ /dev/null @@ -1,48 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_SET_INT_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* set a 32-bit const */ -int mp_set_int (mp_int * a, unsigned long b) -{ - int x, res; - - mp_zero (a); - - /* set four bits at a time */ - for (x = 0; x < 8; x++) { - /* shift the number up four bits */ - if ((res = mp_mul_2d (a, 4, a)) != MP_OKAY) { - return res; - } - - /* OR in the top four bits of the source */ - a->dp[0] |= (b >> 28) & 15; - - /* shift the source up to the next four bits */ - b <<= 4; - - /* ensure that digits are not clamped off */ - a->used += 1; - } - mp_clamp (a); - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_set_int.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_shrink.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_shrink.c deleted file mode 100644 index 54920d1..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_shrink.c +++ /dev/null @@ -1,35 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_SHRINK_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* shrink a bignum */ -int mp_shrink (mp_int * a) -{ - mp_digit *tmp; - if (a->alloc != a->used && a->used > 0) { - if ((tmp = OPT_CAST(mp_digit) XREALLOC (a->dp, sizeof (mp_digit) * a->used)) == NULL) { - return MP_MEM; - } - a->dp = tmp; - a->alloc = a->used; - } - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_shrink.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_signed_bin_size.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_signed_bin_size.c deleted file mode 100644 index b9492a5..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_signed_bin_size.c +++ /dev/null @@ -1,27 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_SIGNED_BIN_SIZE_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* get the size for an signed equivalent */ -int mp_signed_bin_size (mp_int * a) -{ - return 1 + mp_unsigned_bin_size (a); -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_signed_bin_size.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_sqr.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_sqr.c deleted file mode 100644 index c10fa6f..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_sqr.c +++ /dev/null @@ -1,58 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_SQR_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* computes b = a*a */ -int -mp_sqr (mp_int * a, mp_int * b) -{ - int res; - -#ifdef BN_MP_TOOM_SQR_C - /* use Toom-Cook? */ - if (a->used >= TOOM_SQR_CUTOFF) { - res = mp_toom_sqr(a, b); - /* Karatsuba? */ - } else -#endif -#ifdef BN_MP_KARATSUBA_SQR_C -if (a->used >= KARATSUBA_SQR_CUTOFF) { - res = mp_karatsuba_sqr (a, b); - } else -#endif - { -#ifdef BN_FAST_S_MP_SQR_C - /* can we use the fast comba multiplier? */ - if ((a->used * 2 + 1) < MP_WARRAY && - a->used < - (1 << (sizeof(mp_word) * CHAR_BIT - 2*DIGIT_BIT - 1))) { - res = fast_s_mp_sqr (a, b); - } else -#endif -#ifdef BN_S_MP_SQR_C - res = s_mp_sqr (a, b); -#else - res = MP_VAL; -#endif - } - b->sign = MP_ZPOS; - return res; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_sqr.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_sqrmod.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_sqrmod.c deleted file mode 100644 index 5f4b2f3..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_sqrmod.c +++ /dev/null @@ -1,41 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_SQRMOD_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* c = a * a (mod b) */ -int -mp_sqrmod (mp_int * a, mp_int * b, mp_int * c) -{ - int res; - mp_int t; - - if ((res = mp_init (&t)) != MP_OKAY) { - return res; - } - - if ((res = mp_sqr (a, &t)) != MP_OKAY) { - mp_clear (&t); - return res; - } - res = mp_mod (&t, b, c); - mp_clear (&t); - return res; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_sqrmod.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_sqrt.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_sqrt.c deleted file mode 100644 index e15ba98..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_sqrt.c +++ /dev/null @@ -1,81 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_SQRT_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* this function is less generic than mp_n_root, simpler and faster */ -int mp_sqrt(mp_int *arg, mp_int *ret) -{ - int res; - mp_int t1,t2; - - /* must be positive */ - if (arg->sign == MP_NEG) { - return MP_VAL; - } - - /* easy out */ - if (mp_iszero(arg) == MP_YES) { - mp_zero(ret); - return MP_OKAY; - } - - if ((res = mp_init_copy(&t1, arg)) != MP_OKAY) { - return res; - } - - if ((res = mp_init(&t2)) != MP_OKAY) { - goto E2; - } - - /* First approx. (not very bad for large arg) */ - mp_rshd (&t1,t1.used/2); - - /* t1 > 0 */ - if ((res = mp_div(arg,&t1,&t2,NULL)) != MP_OKAY) { - goto E1; - } - if ((res = mp_add(&t1,&t2,&t1)) != MP_OKAY) { - goto E1; - } - if ((res = mp_div_2(&t1,&t1)) != MP_OKAY) { - goto E1; - } - /* And now t1 > sqrt(arg) */ - do { - if ((res = mp_div(arg,&t1,&t2,NULL)) != MP_OKAY) { - goto E1; - } - if ((res = mp_add(&t1,&t2,&t1)) != MP_OKAY) { - goto E1; - } - if ((res = mp_div_2(&t1,&t1)) != MP_OKAY) { - goto E1; - } - /* t1 >= sqrt(arg) >= t2 at this point */ - } while (mp_cmp_mag(&t1,&t2) == MP_GT); - - mp_exch(&t1,ret); - -E1: mp_clear(&t2); -E2: mp_clear(&t1); - return res; -} - -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_sqrt.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_sub.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_sub.c deleted file mode 100644 index 6e72138..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_sub.c +++ /dev/null @@ -1,59 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_SUB_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* high level subtraction (handles signs) */ -int -mp_sub (mp_int * a, mp_int * b, mp_int * c) -{ - int sa, sb, res; - - sa = a->sign; - sb = b->sign; - - if (sa != sb) { - /* subtract a negative from a positive, OR */ - /* subtract a positive from a negative. */ - /* In either case, ADD their magnitudes, */ - /* and use the sign of the first number. */ - c->sign = sa; - res = s_mp_add (a, b, c); - } else { - /* subtract a positive from a positive, OR */ - /* subtract a negative from a negative. */ - /* First, take the difference between their */ - /* magnitudes, then... */ - if (mp_cmp_mag (a, b) != MP_LT) { - /* Copy the sign from the first */ - c->sign = sa; - /* The first has a larger or equal magnitude */ - res = s_mp_sub (a, b, c); - } else { - /* The result has the *opposite* sign from */ - /* the first number. */ - c->sign = (sa == MP_ZPOS) ? MP_NEG : MP_ZPOS; - /* The second has a larger magnitude */ - res = s_mp_sub (b, a, c); - } - } - return res; -} - -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_sub.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_sub_d.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_sub_d.c deleted file mode 100644 index aa08e31..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_sub_d.c +++ /dev/null @@ -1,93 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_SUB_D_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* single digit subtraction */ -int -mp_sub_d (mp_int * a, mp_digit b, mp_int * c) -{ - mp_digit *tmpa, *tmpc, mu; - int res, ix, oldused; - - /* grow c as required */ - if (c->alloc < a->used + 1) { - if ((res = mp_grow(c, a->used + 1)) != MP_OKAY) { - return res; - } - } - - /* if a is negative just do an unsigned - * addition [with fudged signs] - */ - if (a->sign == MP_NEG) { - a->sign = MP_ZPOS; - res = mp_add_d(a, b, c); - a->sign = c->sign = MP_NEG; - - /* clamp */ - mp_clamp(c); - - return res; - } - - /* setup regs */ - oldused = c->used; - tmpa = a->dp; - tmpc = c->dp; - - /* if a <= b simply fix the single digit */ - if ((a->used == 1 && a->dp[0] <= b) || a->used == 0) { - if (a->used == 1) { - *tmpc++ = b - *tmpa; - } else { - *tmpc++ = b; - } - ix = 1; - - /* negative/1digit */ - c->sign = MP_NEG; - c->used = 1; - } else { - /* positive/size */ - c->sign = MP_ZPOS; - c->used = a->used; - - /* subtract first digit */ - *tmpc = *tmpa++ - b; - mu = *tmpc >> (sizeof(mp_digit) * CHAR_BIT - 1); - *tmpc++ &= MP_MASK; - - /* handle rest of the digits */ - for (ix = 1; ix < a->used; ix++) { - *tmpc = *tmpa++ - mu; - mu = *tmpc >> (sizeof(mp_digit) * CHAR_BIT - 1); - *tmpc++ &= MP_MASK; - } - } - - /* zero excess digits */ - while (ix++ < oldused) { - *tmpc++ = 0; - } - mp_clamp(c); - return MP_OKAY; -} - -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_sub_d.c,v $ */ -/* $Revision: 1.6 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_submod.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_submod.c deleted file mode 100644 index 6617ff4..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_submod.c +++ /dev/null @@ -1,42 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_SUBMOD_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* d = a - b (mod c) */ -int -mp_submod (mp_int * a, mp_int * b, mp_int * c, mp_int * d) -{ - int res; - mp_int t; - - - if ((res = mp_init (&t)) != MP_OKAY) { - return res; - } - - if ((res = mp_sub (a, b, &t)) != MP_OKAY) { - mp_clear (&t); - return res; - } - res = mp_mod (&t, c, d); - mp_clear (&t); - return res; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_submod.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_to_signed_bin.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_to_signed_bin.c deleted file mode 100644 index 154f64b..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_to_signed_bin.c +++ /dev/null @@ -1,33 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_TO_SIGNED_BIN_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* store in signed [big endian] format */ -int mp_to_signed_bin (mp_int * a, unsigned char *b) -{ - int res; - - if ((res = mp_to_unsigned_bin (a, b + 1)) != MP_OKAY) { - return res; - } - b[0] = (unsigned char) ((a->sign == MP_ZPOS) ? 0 : 1); - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_to_signed_bin.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_to_signed_bin_n.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_to_signed_bin_n.c deleted file mode 100644 index e119c38..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_to_signed_bin_n.c +++ /dev/null @@ -1,31 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_TO_SIGNED_BIN_N_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* store in signed [big endian] format */ -int mp_to_signed_bin_n (mp_int * a, unsigned char *b, unsigned long *outlen) -{ - if (*outlen < (unsigned long)mp_signed_bin_size(a)) { - return MP_VAL; - } - *outlen = mp_signed_bin_size(a); - return mp_to_signed_bin(a, b); -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_to_signed_bin_n.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_to_unsigned_bin.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_to_unsigned_bin.c deleted file mode 100644 index ce69e5b..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_to_unsigned_bin.c +++ /dev/null @@ -1,48 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_TO_UNSIGNED_BIN_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* store in unsigned [big endian] format */ -int mp_to_unsigned_bin (mp_int * a, unsigned char *b) -{ - int x, res; - mp_int t; - - if ((res = mp_init_copy (&t, a)) != MP_OKAY) { - return res; - } - - x = 0; - while (mp_iszero (&t) == 0) { -#ifndef MP_8BIT - b[x++] = (unsigned char) (t.dp[0] & 255); -#else - b[x++] = (unsigned char) (t.dp[0] | ((t.dp[1] & 0x01) << 7)); -#endif - if ((res = mp_div_2d (&t, 8, &t, NULL)) != MP_OKAY) { - mp_clear (&t); - return res; - } - } - bn_reverse (b, x); - mp_clear (&t); - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_to_unsigned_bin.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_to_unsigned_bin_n.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_to_unsigned_bin_n.c deleted file mode 100644 index dfa27c4..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_to_unsigned_bin_n.c +++ /dev/null @@ -1,31 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_TO_UNSIGNED_BIN_N_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* store in unsigned [big endian] format */ -int mp_to_unsigned_bin_n (mp_int * a, unsigned char *b, unsigned long *outlen) -{ - if (*outlen < (unsigned long)mp_unsigned_bin_size(a)) { - return MP_VAL; - } - *outlen = mp_unsigned_bin_size(a); - return mp_to_unsigned_bin(a, b); -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_to_unsigned_bin_n.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_toom_mul.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_toom_mul.c deleted file mode 100644 index e48c6b3..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_toom_mul.c +++ /dev/null @@ -1,284 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_TOOM_MUL_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* multiplication using the Toom-Cook 3-way algorithm - * - * Much more complicated than Karatsuba but has a lower - * asymptotic running time of O(N**1.464). This algorithm is - * only particularly useful on VERY large inputs - * (we're talking 1000s of digits here...). -*/ -int mp_toom_mul(mp_int *a, mp_int *b, mp_int *c) -{ - mp_int w0, w1, w2, w3, w4, tmp1, tmp2, a0, a1, a2, b0, b1, b2; - int res, B; - - /* init temps */ - if ((res = mp_init_multi(&w0, &w1, &w2, &w3, &w4, - &a0, &a1, &a2, &b0, &b1, - &b2, &tmp1, &tmp2, NULL)) != MP_OKAY) { - return res; - } - - /* B */ - B = MIN(a->used, b->used) / 3; - - /* a = a2 * B**2 + a1 * B + a0 */ - if ((res = mp_mod_2d(a, DIGIT_BIT * B, &a0)) != MP_OKAY) { - goto ERR; - } - - if ((res = mp_copy(a, &a1)) != MP_OKAY) { - goto ERR; - } - mp_rshd(&a1, B); - mp_mod_2d(&a1, DIGIT_BIT * B, &a1); - - if ((res = mp_copy(a, &a2)) != MP_OKAY) { - goto ERR; - } - mp_rshd(&a2, B*2); - - /* b = b2 * B**2 + b1 * B + b0 */ - if ((res = mp_mod_2d(b, DIGIT_BIT * B, &b0)) != MP_OKAY) { - goto ERR; - } - - if ((res = mp_copy(b, &b1)) != MP_OKAY) { - goto ERR; - } - mp_rshd(&b1, B); - mp_mod_2d(&b1, DIGIT_BIT * B, &b1); - - if ((res = mp_copy(b, &b2)) != MP_OKAY) { - goto ERR; - } - mp_rshd(&b2, B*2); - - /* w0 = a0*b0 */ - if ((res = mp_mul(&a0, &b0, &w0)) != MP_OKAY) { - goto ERR; - } - - /* w4 = a2 * b2 */ - if ((res = mp_mul(&a2, &b2, &w4)) != MP_OKAY) { - goto ERR; - } - - /* w1 = (a2 + 2(a1 + 2a0))(b2 + 2(b1 + 2b0)) */ - if ((res = mp_mul_2(&a0, &tmp1)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_add(&tmp1, &a1, &tmp1)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_mul_2(&tmp1, &tmp1)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_add(&tmp1, &a2, &tmp1)) != MP_OKAY) { - goto ERR; - } - - if ((res = mp_mul_2(&b0, &tmp2)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_add(&tmp2, &b1, &tmp2)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_mul_2(&tmp2, &tmp2)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_add(&tmp2, &b2, &tmp2)) != MP_OKAY) { - goto ERR; - } - - if ((res = mp_mul(&tmp1, &tmp2, &w1)) != MP_OKAY) { - goto ERR; - } - - /* w3 = (a0 + 2(a1 + 2a2))(b0 + 2(b1 + 2b2)) */ - if ((res = mp_mul_2(&a2, &tmp1)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_add(&tmp1, &a1, &tmp1)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_mul_2(&tmp1, &tmp1)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_add(&tmp1, &a0, &tmp1)) != MP_OKAY) { - goto ERR; - } - - if ((res = mp_mul_2(&b2, &tmp2)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_add(&tmp2, &b1, &tmp2)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_mul_2(&tmp2, &tmp2)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_add(&tmp2, &b0, &tmp2)) != MP_OKAY) { - goto ERR; - } - - if ((res = mp_mul(&tmp1, &tmp2, &w3)) != MP_OKAY) { - goto ERR; - } - - - /* w2 = (a2 + a1 + a0)(b2 + b1 + b0) */ - if ((res = mp_add(&a2, &a1, &tmp1)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_add(&tmp1, &a0, &tmp1)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_add(&b2, &b1, &tmp2)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_add(&tmp2, &b0, &tmp2)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_mul(&tmp1, &tmp2, &w2)) != MP_OKAY) { - goto ERR; - } - - /* now solve the matrix - - 0 0 0 0 1 - 1 2 4 8 16 - 1 1 1 1 1 - 16 8 4 2 1 - 1 0 0 0 0 - - using 12 subtractions, 4 shifts, - 2 small divisions and 1 small multiplication - */ - - /* r1 - r4 */ - if ((res = mp_sub(&w1, &w4, &w1)) != MP_OKAY) { - goto ERR; - } - /* r3 - r0 */ - if ((res = mp_sub(&w3, &w0, &w3)) != MP_OKAY) { - goto ERR; - } - /* r1/2 */ - if ((res = mp_div_2(&w1, &w1)) != MP_OKAY) { - goto ERR; - } - /* r3/2 */ - if ((res = mp_div_2(&w3, &w3)) != MP_OKAY) { - goto ERR; - } - /* r2 - r0 - r4 */ - if ((res = mp_sub(&w2, &w0, &w2)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_sub(&w2, &w4, &w2)) != MP_OKAY) { - goto ERR; - } - /* r1 - r2 */ - if ((res = mp_sub(&w1, &w2, &w1)) != MP_OKAY) { - goto ERR; - } - /* r3 - r2 */ - if ((res = mp_sub(&w3, &w2, &w3)) != MP_OKAY) { - goto ERR; - } - /* r1 - 8r0 */ - if ((res = mp_mul_2d(&w0, 3, &tmp1)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_sub(&w1, &tmp1, &w1)) != MP_OKAY) { - goto ERR; - } - /* r3 - 8r4 */ - if ((res = mp_mul_2d(&w4, 3, &tmp1)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_sub(&w3, &tmp1, &w3)) != MP_OKAY) { - goto ERR; - } - /* 3r2 - r1 - r3 */ - if ((res = mp_mul_d(&w2, 3, &w2)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_sub(&w2, &w1, &w2)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_sub(&w2, &w3, &w2)) != MP_OKAY) { - goto ERR; - } - /* r1 - r2 */ - if ((res = mp_sub(&w1, &w2, &w1)) != MP_OKAY) { - goto ERR; - } - /* r3 - r2 */ - if ((res = mp_sub(&w3, &w2, &w3)) != MP_OKAY) { - goto ERR; - } - /* r1/3 */ - if ((res = mp_div_3(&w1, &w1, NULL)) != MP_OKAY) { - goto ERR; - } - /* r3/3 */ - if ((res = mp_div_3(&w3, &w3, NULL)) != MP_OKAY) { - goto ERR; - } - - /* at this point shift W[n] by B*n */ - if ((res = mp_lshd(&w1, 1*B)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_lshd(&w2, 2*B)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_lshd(&w3, 3*B)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_lshd(&w4, 4*B)) != MP_OKAY) { - goto ERR; - } - - if ((res = mp_add(&w0, &w1, c)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_add(&w2, &w3, &tmp1)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_add(&w4, &tmp1, &tmp1)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_add(&tmp1, c, c)) != MP_OKAY) { - goto ERR; - } - -ERR: - mp_clear_multi(&w0, &w1, &w2, &w3, &w4, - &a0, &a1, &a2, &b0, &b1, - &b2, &tmp1, &tmp2, NULL); - return res; -} - -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_toom_mul.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_toom_sqr.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_toom_sqr.c deleted file mode 100644 index fd8bc67..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_toom_sqr.c +++ /dev/null @@ -1,226 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_TOOM_SQR_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* squaring using Toom-Cook 3-way algorithm */ -int -mp_toom_sqr(mp_int *a, mp_int *b) -{ - mp_int w0, w1, w2, w3, w4, tmp1, a0, a1, a2; - int res, B; - - /* init temps */ - if ((res = mp_init_multi(&w0, &w1, &w2, &w3, &w4, &a0, &a1, &a2, &tmp1, NULL)) != MP_OKAY) { - return res; - } - - /* B */ - B = a->used / 3; - - /* a = a2 * B**2 + a1 * B + a0 */ - if ((res = mp_mod_2d(a, DIGIT_BIT * B, &a0)) != MP_OKAY) { - goto ERR; - } - - if ((res = mp_copy(a, &a1)) != MP_OKAY) { - goto ERR; - } - mp_rshd(&a1, B); - mp_mod_2d(&a1, DIGIT_BIT * B, &a1); - - if ((res = mp_copy(a, &a2)) != MP_OKAY) { - goto ERR; - } - mp_rshd(&a2, B*2); - - /* w0 = a0*a0 */ - if ((res = mp_sqr(&a0, &w0)) != MP_OKAY) { - goto ERR; - } - - /* w4 = a2 * a2 */ - if ((res = mp_sqr(&a2, &w4)) != MP_OKAY) { - goto ERR; - } - - /* w1 = (a2 + 2(a1 + 2a0))**2 */ - if ((res = mp_mul_2(&a0, &tmp1)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_add(&tmp1, &a1, &tmp1)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_mul_2(&tmp1, &tmp1)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_add(&tmp1, &a2, &tmp1)) != MP_OKAY) { - goto ERR; - } - - if ((res = mp_sqr(&tmp1, &w1)) != MP_OKAY) { - goto ERR; - } - - /* w3 = (a0 + 2(a1 + 2a2))**2 */ - if ((res = mp_mul_2(&a2, &tmp1)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_add(&tmp1, &a1, &tmp1)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_mul_2(&tmp1, &tmp1)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_add(&tmp1, &a0, &tmp1)) != MP_OKAY) { - goto ERR; - } - - if ((res = mp_sqr(&tmp1, &w3)) != MP_OKAY) { - goto ERR; - } - - - /* w2 = (a2 + a1 + a0)**2 */ - if ((res = mp_add(&a2, &a1, &tmp1)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_add(&tmp1, &a0, &tmp1)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_sqr(&tmp1, &w2)) != MP_OKAY) { - goto ERR; - } - - /* now solve the matrix - - 0 0 0 0 1 - 1 2 4 8 16 - 1 1 1 1 1 - 16 8 4 2 1 - 1 0 0 0 0 - - using 12 subtractions, 4 shifts, 2 small divisions and 1 small multiplication. - */ - - /* r1 - r4 */ - if ((res = mp_sub(&w1, &w4, &w1)) != MP_OKAY) { - goto ERR; - } - /* r3 - r0 */ - if ((res = mp_sub(&w3, &w0, &w3)) != MP_OKAY) { - goto ERR; - } - /* r1/2 */ - if ((res = mp_div_2(&w1, &w1)) != MP_OKAY) { - goto ERR; - } - /* r3/2 */ - if ((res = mp_div_2(&w3, &w3)) != MP_OKAY) { - goto ERR; - } - /* r2 - r0 - r4 */ - if ((res = mp_sub(&w2, &w0, &w2)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_sub(&w2, &w4, &w2)) != MP_OKAY) { - goto ERR; - } - /* r1 - r2 */ - if ((res = mp_sub(&w1, &w2, &w1)) != MP_OKAY) { - goto ERR; - } - /* r3 - r2 */ - if ((res = mp_sub(&w3, &w2, &w3)) != MP_OKAY) { - goto ERR; - } - /* r1 - 8r0 */ - if ((res = mp_mul_2d(&w0, 3, &tmp1)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_sub(&w1, &tmp1, &w1)) != MP_OKAY) { - goto ERR; - } - /* r3 - 8r4 */ - if ((res = mp_mul_2d(&w4, 3, &tmp1)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_sub(&w3, &tmp1, &w3)) != MP_OKAY) { - goto ERR; - } - /* 3r2 - r1 - r3 */ - if ((res = mp_mul_d(&w2, 3, &w2)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_sub(&w2, &w1, &w2)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_sub(&w2, &w3, &w2)) != MP_OKAY) { - goto ERR; - } - /* r1 - r2 */ - if ((res = mp_sub(&w1, &w2, &w1)) != MP_OKAY) { - goto ERR; - } - /* r3 - r2 */ - if ((res = mp_sub(&w3, &w2, &w3)) != MP_OKAY) { - goto ERR; - } - /* r1/3 */ - if ((res = mp_div_3(&w1, &w1, NULL)) != MP_OKAY) { - goto ERR; - } - /* r3/3 */ - if ((res = mp_div_3(&w3, &w3, NULL)) != MP_OKAY) { - goto ERR; - } - - /* at this point shift W[n] by B*n */ - if ((res = mp_lshd(&w1, 1*B)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_lshd(&w2, 2*B)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_lshd(&w3, 3*B)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_lshd(&w4, 4*B)) != MP_OKAY) { - goto ERR; - } - - if ((res = mp_add(&w0, &w1, b)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_add(&w2, &w3, &tmp1)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_add(&w4, &tmp1, &tmp1)) != MP_OKAY) { - goto ERR; - } - if ((res = mp_add(&tmp1, b, b)) != MP_OKAY) { - goto ERR; - } - -ERR: - mp_clear_multi(&w0, &w1, &w2, &w3, &w4, &a0, &a1, &a2, &tmp1, NULL); - return res; -} - -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_toom_sqr.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_toradix.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_toradix.c deleted file mode 100644 index 539abe9..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_toradix.c +++ /dev/null @@ -1,75 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_TORADIX_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* stores a bignum as a ASCII string in a given radix (2..64) */ -int mp_toradix (mp_int * a, char *str, int radix) -{ - int res, digs; - mp_int t; - mp_digit d; - char *_s = str; - - /* check range of the radix */ - if (radix < 2 || radix > 64) { - return MP_VAL; - } - - /* quick out if its zero */ - if (mp_iszero(a) == 1) { - *str++ = '0'; - *str = '\0'; - return MP_OKAY; - } - - if ((res = mp_init_copy (&t, a)) != MP_OKAY) { - return res; - } - - /* if it is negative output a - */ - if (t.sign == MP_NEG) { - ++_s; - *str++ = '-'; - t.sign = MP_ZPOS; - } - - digs = 0; - while (mp_iszero (&t) == 0) { - if ((res = mp_div_d (&t, (mp_digit) radix, &t, &d)) != MP_OKAY) { - mp_clear (&t); - return res; - } - *str++ = mp_s_rmap[d]; - ++digs; - } - - /* reverse the digits of the string. In this case _s points - * to the first digit [exluding the sign] of the number] - */ - bn_reverse ((unsigned char *)_s, digs); - - /* append a NULL so the string is properly terminated */ - *str = '\0'; - - mp_clear (&t); - return MP_OKAY; -} - -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_toradix.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_toradix_n.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_toradix_n.c deleted file mode 100644 index 0322f8d..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_toradix_n.c +++ /dev/null @@ -1,88 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_TORADIX_N_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* stores a bignum as a ASCII string in a given radix (2..64) - * - * Stores upto maxlen-1 chars and always a NULL byte - */ -int mp_toradix_n(mp_int * a, char *str, int radix, int maxlen) -{ - int res, digs; - mp_int t; - mp_digit d; - char *_s = str; - - /* check range of the maxlen, radix */ - if (maxlen < 2 || radix < 2 || radix > 64) { - return MP_VAL; - } - - /* quick out if its zero */ - if (mp_iszero(a) == MP_YES) { - *str++ = '0'; - *str = '\0'; - return MP_OKAY; - } - - if ((res = mp_init_copy (&t, a)) != MP_OKAY) { - return res; - } - - /* if it is negative output a - */ - if (t.sign == MP_NEG) { - /* we have to reverse our digits later... but not the - sign!! */ - ++_s; - - /* store the flag and mark the number as positive */ - *str++ = '-'; - t.sign = MP_ZPOS; - - /* subtract a char */ - --maxlen; - } - - digs = 0; - while (mp_iszero (&t) == 0) { - if (--maxlen < 1) { - /* no more room */ - break; - } - if ((res = mp_div_d (&t, (mp_digit) radix, &t, &d)) != MP_OKAY) { - mp_clear (&t); - return res; - } - *str++ = mp_s_rmap[d]; - ++digs; - } - - /* reverse the digits of the string. In this case _s points - * to the first digit [exluding the sign] of the number - */ - bn_reverse ((unsigned char *)_s, digs); - - /* append a NULL so the string is properly terminated */ - *str = '\0'; - - mp_clear (&t); - return MP_OKAY; -} - -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_toradix_n.c,v $ */ -/* $Revision: 1.5 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_unsigned_bin_size.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_unsigned_bin_size.c deleted file mode 100644 index 88f3e92..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_unsigned_bin_size.c +++ /dev/null @@ -1,28 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_UNSIGNED_BIN_SIZE_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* get the size for an unsigned equivalent */ -int mp_unsigned_bin_size (mp_int * a) -{ - int size = mp_count_bits (a); - return (size / 8 + ((size & 7) != 0 ? 1 : 0)); -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_unsigned_bin_size.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_xor.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_xor.c deleted file mode 100644 index bf0446e..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_xor.c +++ /dev/null @@ -1,51 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_XOR_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* XOR two ints together */ -int -mp_xor (mp_int * a, mp_int * b, mp_int * c) -{ - int res, ix, px; - mp_int t, *x; - - if (a->used > b->used) { - if ((res = mp_init_copy (&t, a)) != MP_OKAY) { - return res; - } - px = b->used; - x = b; - } else { - if ((res = mp_init_copy (&t, b)) != MP_OKAY) { - return res; - } - px = a->used; - x = a; - } - - for (ix = 0; ix < px; ix++) { - t.dp[ix] ^= x->dp[ix]; - } - mp_clamp (&t); - mp_exch (c, &t); - mp_clear (&t); - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_xor.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_zero.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_zero.c deleted file mode 100644 index f21db5e..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_mp_zero.c +++ /dev/null @@ -1,36 +0,0 @@ -#include "tommath.h" -#ifdef BN_MP_ZERO_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* set to zero */ -void mp_zero (mp_int * a) -{ - int n; - mp_digit *tmp; - - a->sign = MP_ZPOS; - a->used = 0; - - tmp = a->dp; - for (n = 0; n < a->alloc; n++) { - *tmp++ = 0; - } -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_mp_zero.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_prime_tab.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_prime_tab.c deleted file mode 100644 index 7d306dd..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_prime_tab.c +++ /dev/null @@ -1,61 +0,0 @@ -#include "tommath.h" -#ifdef BN_PRIME_TAB_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -const mp_digit ltm_prime_tab[] = { - 0x0002, 0x0003, 0x0005, 0x0007, 0x000B, 0x000D, 0x0011, 0x0013, - 0x0017, 0x001D, 0x001F, 0x0025, 0x0029, 0x002B, 0x002F, 0x0035, - 0x003B, 0x003D, 0x0043, 0x0047, 0x0049, 0x004F, 0x0053, 0x0059, - 0x0061, 0x0065, 0x0067, 0x006B, 0x006D, 0x0071, 0x007F, -#ifndef MP_8BIT - 0x0083, - 0x0089, 0x008B, 0x0095, 0x0097, 0x009D, 0x00A3, 0x00A7, 0x00AD, - 0x00B3, 0x00B5, 0x00BF, 0x00C1, 0x00C5, 0x00C7, 0x00D3, 0x00DF, - 0x00E3, 0x00E5, 0x00E9, 0x00EF, 0x00F1, 0x00FB, 0x0101, 0x0107, - 0x010D, 0x010F, 0x0115, 0x0119, 0x011B, 0x0125, 0x0133, 0x0137, - - 0x0139, 0x013D, 0x014B, 0x0151, 0x015B, 0x015D, 0x0161, 0x0167, - 0x016F, 0x0175, 0x017B, 0x017F, 0x0185, 0x018D, 0x0191, 0x0199, - 0x01A3, 0x01A5, 0x01AF, 0x01B1, 0x01B7, 0x01BB, 0x01C1, 0x01C9, - 0x01CD, 0x01CF, 0x01D3, 0x01DF, 0x01E7, 0x01EB, 0x01F3, 0x01F7, - 0x01FD, 0x0209, 0x020B, 0x021D, 0x0223, 0x022D, 0x0233, 0x0239, - 0x023B, 0x0241, 0x024B, 0x0251, 0x0257, 0x0259, 0x025F, 0x0265, - 0x0269, 0x026B, 0x0277, 0x0281, 0x0283, 0x0287, 0x028D, 0x0293, - 0x0295, 0x02A1, 0x02A5, 0x02AB, 0x02B3, 0x02BD, 0x02C5, 0x02CF, - - 0x02D7, 0x02DD, 0x02E3, 0x02E7, 0x02EF, 0x02F5, 0x02F9, 0x0301, - 0x0305, 0x0313, 0x031D, 0x0329, 0x032B, 0x0335, 0x0337, 0x033B, - 0x033D, 0x0347, 0x0355, 0x0359, 0x035B, 0x035F, 0x036D, 0x0371, - 0x0373, 0x0377, 0x038B, 0x038F, 0x0397, 0x03A1, 0x03A9, 0x03AD, - 0x03B3, 0x03B9, 0x03C7, 0x03CB, 0x03D1, 0x03D7, 0x03DF, 0x03E5, - 0x03F1, 0x03F5, 0x03FB, 0x03FD, 0x0407, 0x0409, 0x040F, 0x0419, - 0x041B, 0x0425, 0x0427, 0x042D, 0x043F, 0x0443, 0x0445, 0x0449, - 0x044F, 0x0455, 0x045D, 0x0463, 0x0469, 0x047F, 0x0481, 0x048B, - - 0x0493, 0x049D, 0x04A3, 0x04A9, 0x04B1, 0x04BD, 0x04C1, 0x04C7, - 0x04CD, 0x04CF, 0x04D5, 0x04E1, 0x04EB, 0x04FD, 0x04FF, 0x0503, - 0x0509, 0x050B, 0x0511, 0x0515, 0x0517, 0x051B, 0x0527, 0x0529, - 0x052F, 0x0551, 0x0557, 0x055D, 0x0565, 0x0577, 0x0581, 0x058F, - 0x0593, 0x0595, 0x0599, 0x059F, 0x05A7, 0x05AB, 0x05AD, 0x05B3, - 0x05BF, 0x05C9, 0x05CB, 0x05CF, 0x05D1, 0x05D5, 0x05DB, 0x05E7, - 0x05F3, 0x05FB, 0x0607, 0x060D, 0x0611, 0x0617, 0x061F, 0x0623, - 0x062B, 0x062F, 0x063D, 0x0641, 0x0647, 0x0649, 0x064D, 0x0653 -#endif -}; -#endif - -/* $Source: /cvs/libtom/libtommath/bn_prime_tab.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_reverse.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_reverse.c deleted file mode 100644 index d4a919a..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_reverse.c +++ /dev/null @@ -1,39 +0,0 @@ -#include "tommath.h" -#ifdef BN_REVERSE_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* reverse an array, used for radix code */ -void -bn_reverse (unsigned char *s, int len) -{ - int ix, iy; - unsigned char t; - - ix = 0; - iy = len - 1; - while (ix < iy) { - t = s[ix]; - s[ix] = s[iy]; - s[iy] = t; - ++ix; - --iy; - } -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_reverse.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_s_mp_add.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_s_mp_add.c deleted file mode 100644 index 5ea9c6d..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_s_mp_add.c +++ /dev/null @@ -1,109 +0,0 @@ -#include "tommath.h" -#ifdef BN_S_MP_ADD_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* low level addition, based on HAC pp.594, Algorithm 14.7 */ -int -s_mp_add (mp_int * a, mp_int * b, mp_int * c) -{ - mp_int *x; - int olduse, res, min, max; - - /* find sizes, we let |a| <= |b| which means we have to sort - * them. "x" will point to the input with the most digits - */ - if (a->used > b->used) { - min = b->used; - max = a->used; - x = a; - } else { - min = a->used; - max = b->used; - x = b; - } - - /* init result */ - if (c->alloc < max + 1) { - if ((res = mp_grow (c, max + 1)) != MP_OKAY) { - return res; - } - } - - /* get old used digit count and set new one */ - olduse = c->used; - c->used = max + 1; - - { - register mp_digit u, *tmpa, *tmpb, *tmpc; - register int i; - - /* alias for digit pointers */ - - /* first input */ - tmpa = a->dp; - - /* second input */ - tmpb = b->dp; - - /* destination */ - tmpc = c->dp; - - /* zero the carry */ - u = 0; - for (i = 0; i < min; i++) { - /* Compute the sum at one digit, T[i] = A[i] + B[i] + U */ - *tmpc = *tmpa++ + *tmpb++ + u; - - /* U = carry bit of T[i] */ - u = *tmpc >> ((mp_digit)DIGIT_BIT); - - /* take away carry bit from T[i] */ - *tmpc++ &= MP_MASK; - } - - /* now copy higher words if any, that is in A+B - * if A or B has more digits add those in - */ - if (min != max) { - for (; i < max; i++) { - /* T[i] = X[i] + U */ - *tmpc = x->dp[i] + u; - - /* U = carry bit of T[i] */ - u = *tmpc >> ((mp_digit)DIGIT_BIT); - - /* take away carry bit from T[i] */ - *tmpc++ &= MP_MASK; - } - } - - /* add carry */ - *tmpc++ = u; - - /* clear digits above oldused */ - for (i = c->used; i < olduse; i++) { - *tmpc++ = 0; - } - } - - mp_clamp (c); - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_s_mp_add.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_s_mp_exptmod.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_s_mp_exptmod.c deleted file mode 100644 index 9fb2da8..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_s_mp_exptmod.c +++ /dev/null @@ -1,252 +0,0 @@ -#include "tommath.h" -#ifdef BN_S_MP_EXPTMOD_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ -#ifdef MP_LOW_MEM - #define TAB_SIZE 32 -#else - #define TAB_SIZE 256 -#endif - -int s_mp_exptmod (mp_int * G, mp_int * X, mp_int * P, mp_int * Y, int redmode) -{ - mp_int M[TAB_SIZE], res, mu; - mp_digit buf; - int err, bitbuf, bitcpy, bitcnt, mode, digidx, x, y, winsize; - int (*redux)(mp_int*,mp_int*,mp_int*); - - /* find window size */ - x = mp_count_bits (X); - if (x <= 7) { - winsize = 2; - } else if (x <= 36) { - winsize = 3; - } else if (x <= 140) { - winsize = 4; - } else if (x <= 450) { - winsize = 5; - } else if (x <= 1303) { - winsize = 6; - } else if (x <= 3529) { - winsize = 7; - } else { - winsize = 8; - } - -#ifdef MP_LOW_MEM - if (winsize > 5) { - winsize = 5; - } -#endif - - /* init M array */ - /* init first cell */ - if ((err = mp_init(&M[1])) != MP_OKAY) { - return err; - } - - /* now init the second half of the array */ - for (x = 1<<(winsize-1); x < (1 << winsize); x++) { - if ((err = mp_init(&M[x])) != MP_OKAY) { - for (y = 1<<(winsize-1); y < x; y++) { - mp_clear (&M[y]); - } - mp_clear(&M[1]); - return err; - } - } - - /* create mu, used for Barrett reduction */ - if ((err = mp_init (&mu)) != MP_OKAY) { - goto LBL_M; - } - - if (redmode == 0) { - if ((err = mp_reduce_setup (&mu, P)) != MP_OKAY) { - goto LBL_MU; - } - redux = mp_reduce; - } else { - if ((err = mp_reduce_2k_setup_l (P, &mu)) != MP_OKAY) { - goto LBL_MU; - } - redux = mp_reduce_2k_l; - } - - /* create M table - * - * The M table contains powers of the base, - * e.g. M[x] = G**x mod P - * - * The first half of the table is not - * computed though accept for M[0] and M[1] - */ - if ((err = mp_mod (G, P, &M[1])) != MP_OKAY) { - goto LBL_MU; - } - - /* compute the value at M[1<<(winsize-1)] by squaring - * M[1] (winsize-1) times - */ - if ((err = mp_copy (&M[1], &M[1 << (winsize - 1)])) != MP_OKAY) { - goto LBL_MU; - } - - for (x = 0; x < (winsize - 1); x++) { - /* square it */ - if ((err = mp_sqr (&M[1 << (winsize - 1)], - &M[1 << (winsize - 1)])) != MP_OKAY) { - goto LBL_MU; - } - - /* reduce modulo P */ - if ((err = redux (&M[1 << (winsize - 1)], P, &mu)) != MP_OKAY) { - goto LBL_MU; - } - } - - /* create upper table, that is M[x] = M[x-1] * M[1] (mod P) - * for x = (2**(winsize - 1) + 1) to (2**winsize - 1) - */ - for (x = (1 << (winsize - 1)) + 1; x < (1 << winsize); x++) { - if ((err = mp_mul (&M[x - 1], &M[1], &M[x])) != MP_OKAY) { - goto LBL_MU; - } - if ((err = redux (&M[x], P, &mu)) != MP_OKAY) { - goto LBL_MU; - } - } - - /* setup result */ - if ((err = mp_init (&res)) != MP_OKAY) { - goto LBL_MU; - } - mp_set (&res, 1); - - /* set initial mode and bit cnt */ - mode = 0; - bitcnt = 1; - buf = 0; - digidx = X->used - 1; - bitcpy = 0; - bitbuf = 0; - - for (;;) { - /* grab next digit as required */ - if (--bitcnt == 0) { - /* if digidx == -1 we are out of digits */ - if (digidx == -1) { - break; - } - /* read next digit and reset the bitcnt */ - buf = X->dp[digidx--]; - bitcnt = (int) DIGIT_BIT; - } - - /* grab the next msb from the exponent */ - y = (buf >> (mp_digit)(DIGIT_BIT - 1)) & 1; - buf <<= (mp_digit)1; - - /* if the bit is zero and mode == 0 then we ignore it - * These represent the leading zero bits before the first 1 bit - * in the exponent. Technically this opt is not required but it - * does lower the # of trivial squaring/reductions used - */ - if (mode == 0 && y == 0) { - continue; - } - - /* if the bit is zero and mode == 1 then we square */ - if (mode == 1 && y == 0) { - if ((err = mp_sqr (&res, &res)) != MP_OKAY) { - goto LBL_RES; - } - if ((err = redux (&res, P, &mu)) != MP_OKAY) { - goto LBL_RES; - } - continue; - } - - /* else we add it to the window */ - bitbuf |= (y << (winsize - ++bitcpy)); - mode = 2; - - if (bitcpy == winsize) { - /* ok window is filled so square as required and multiply */ - /* square first */ - for (x = 0; x < winsize; x++) { - if ((err = mp_sqr (&res, &res)) != MP_OKAY) { - goto LBL_RES; - } - if ((err = redux (&res, P, &mu)) != MP_OKAY) { - goto LBL_RES; - } - } - - /* then multiply */ - if ((err = mp_mul (&res, &M[bitbuf], &res)) != MP_OKAY) { - goto LBL_RES; - } - if ((err = redux (&res, P, &mu)) != MP_OKAY) { - goto LBL_RES; - } - - /* empty window and reset */ - bitcpy = 0; - bitbuf = 0; - mode = 1; - } - } - - /* if bits remain then square/multiply */ - if (mode == 2 && bitcpy > 0) { - /* square then multiply if the bit is set */ - for (x = 0; x < bitcpy; x++) { - if ((err = mp_sqr (&res, &res)) != MP_OKAY) { - goto LBL_RES; - } - if ((err = redux (&res, P, &mu)) != MP_OKAY) { - goto LBL_RES; - } - - bitbuf <<= 1; - if ((bitbuf & (1 << winsize)) != 0) { - /* then multiply */ - if ((err = mp_mul (&res, &M[1], &res)) != MP_OKAY) { - goto LBL_RES; - } - if ((err = redux (&res, P, &mu)) != MP_OKAY) { - goto LBL_RES; - } - } - } - } - - mp_exch (&res, Y); - err = MP_OKAY; -LBL_RES:mp_clear (&res); -LBL_MU:mp_clear (&mu); -LBL_M: - mp_clear(&M[1]); - for (x = 1<<(winsize-1); x < (1 << winsize); x++) { - mp_clear (&M[x]); - } - return err; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_s_mp_exptmod.c,v $ */ -/* $Revision: 1.5 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_s_mp_mul_digs.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_s_mp_mul_digs.c deleted file mode 100644 index f04dacf..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_s_mp_mul_digs.c +++ /dev/null @@ -1,90 +0,0 @@ -#include "tommath.h" -#ifdef BN_S_MP_MUL_DIGS_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* multiplies |a| * |b| and only computes upto digs digits of result - * HAC pp. 595, Algorithm 14.12 Modified so you can control how - * many digits of output are created. - */ -int s_mp_mul_digs (mp_int * a, mp_int * b, mp_int * c, int digs) -{ - mp_int t; - int res, pa, pb, ix, iy; - mp_digit u; - mp_word r; - mp_digit tmpx, *tmpt, *tmpy; - - /* can we use the fast multiplier? */ - if (((digs) < MP_WARRAY) && - MIN (a->used, b->used) < - (1 << ((CHAR_BIT * sizeof (mp_word)) - (2 * DIGIT_BIT)))) { - return fast_s_mp_mul_digs (a, b, c, digs); - } - - if ((res = mp_init_size (&t, digs)) != MP_OKAY) { - return res; - } - t.used = digs; - - /* compute the digits of the product directly */ - pa = a->used; - for (ix = 0; ix < pa; ix++) { - /* set the carry to zero */ - u = 0; - - /* limit ourselves to making digs digits of output */ - pb = MIN (b->used, digs - ix); - - /* setup some aliases */ - /* copy of the digit from a used within the nested loop */ - tmpx = a->dp[ix]; - - /* an alias for the destination shifted ix places */ - tmpt = t.dp + ix; - - /* an alias for the digits of b */ - tmpy = b->dp; - - /* compute the columns of the output and propagate the carry */ - for (iy = 0; iy < pb; iy++) { - /* compute the column as a mp_word */ - r = ((mp_word)*tmpt) + - ((mp_word)tmpx) * ((mp_word)*tmpy++) + - ((mp_word) u); - - /* the new column is the lower part of the result */ - *tmpt++ = (mp_digit) (r & ((mp_word) MP_MASK)); - - /* get the carry word from the result */ - u = (mp_digit) (r >> ((mp_word) DIGIT_BIT)); - } - /* set carry if it is placed below digs */ - if (ix + iy < digs) { - *tmpt = u; - } - } - - mp_clamp (&t); - mp_exch (&t, c); - - mp_clear (&t); - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_s_mp_mul_digs.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_s_mp_mul_high_digs.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_s_mp_mul_high_digs.c deleted file mode 100644 index b1d0199..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_s_mp_mul_high_digs.c +++ /dev/null @@ -1,81 +0,0 @@ -#include "tommath.h" -#ifdef BN_S_MP_MUL_HIGH_DIGS_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* multiplies |a| * |b| and does not compute the lower digs digits - * [meant to get the higher part of the product] - */ -int -s_mp_mul_high_digs (mp_int * a, mp_int * b, mp_int * c, int digs) -{ - mp_int t; - int res, pa, pb, ix, iy; - mp_digit u; - mp_word r; - mp_digit tmpx, *tmpt, *tmpy; - - /* can we use the fast multiplier? */ -#ifdef BN_FAST_S_MP_MUL_HIGH_DIGS_C - if (((a->used + b->used + 1) < MP_WARRAY) - && MIN (a->used, b->used) < (1 << ((CHAR_BIT * sizeof (mp_word)) - (2 * DIGIT_BIT)))) { - return fast_s_mp_mul_high_digs (a, b, c, digs); - } -#endif - - if ((res = mp_init_size (&t, a->used + b->used + 1)) != MP_OKAY) { - return res; - } - t.used = a->used + b->used + 1; - - pa = a->used; - pb = b->used; - for (ix = 0; ix < pa; ix++) { - /* clear the carry */ - u = 0; - - /* left hand side of A[ix] * B[iy] */ - tmpx = a->dp[ix]; - - /* alias to the address of where the digits will be stored */ - tmpt = &(t.dp[digs]); - - /* alias for where to read the right hand side from */ - tmpy = b->dp + (digs - ix); - - for (iy = digs - ix; iy < pb; iy++) { - /* calculate the double precision result */ - r = ((mp_word)*tmpt) + - ((mp_word)tmpx) * ((mp_word)*tmpy++) + - ((mp_word) u); - - /* get the lower part */ - *tmpt++ = (mp_digit) (r & ((mp_word) MP_MASK)); - - /* carry the carry */ - u = (mp_digit) (r >> ((mp_word) DIGIT_BIT)); - } - *tmpt = u; - } - mp_clamp (&t); - mp_exch (&t, c); - mp_clear (&t); - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_s_mp_mul_high_digs.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_s_mp_sqr.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_s_mp_sqr.c deleted file mode 100644 index c1e994e..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_s_mp_sqr.c +++ /dev/null @@ -1,84 +0,0 @@ -#include "tommath.h" -#ifdef BN_S_MP_SQR_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* low level squaring, b = a*a, HAC pp.596-597, Algorithm 14.16 */ -int s_mp_sqr (mp_int * a, mp_int * b) -{ - mp_int t; - int res, ix, iy, pa; - mp_word r; - mp_digit u, tmpx, *tmpt; - - pa = a->used; - if ((res = mp_init_size (&t, 2*pa + 1)) != MP_OKAY) { - return res; - } - - /* default used is maximum possible size */ - t.used = 2*pa + 1; - - for (ix = 0; ix < pa; ix++) { - /* first calculate the digit at 2*ix */ - /* calculate double precision result */ - r = ((mp_word) t.dp[2*ix]) + - ((mp_word)a->dp[ix])*((mp_word)a->dp[ix]); - - /* store lower part in result */ - t.dp[ix+ix] = (mp_digit) (r & ((mp_word) MP_MASK)); - - /* get the carry */ - u = (mp_digit)(r >> ((mp_word) DIGIT_BIT)); - - /* left hand side of A[ix] * A[iy] */ - tmpx = a->dp[ix]; - - /* alias for where to store the results */ - tmpt = t.dp + (2*ix + 1); - - for (iy = ix + 1; iy < pa; iy++) { - /* first calculate the product */ - r = ((mp_word)tmpx) * ((mp_word)a->dp[iy]); - - /* now calculate the double precision result, note we use - * addition instead of *2 since it's easier to optimize - */ - r = ((mp_word) *tmpt) + r + r + ((mp_word) u); - - /* store lower part */ - *tmpt++ = (mp_digit) (r & ((mp_word) MP_MASK)); - - /* get carry */ - u = (mp_digit)(r >> ((mp_word) DIGIT_BIT)); - } - /* propagate upwards */ - while (u != ((mp_digit) 0)) { - r = ((mp_word) *tmpt) + ((mp_word) u); - *tmpt++ = (mp_digit) (r & ((mp_word) MP_MASK)); - u = (mp_digit)(r >> ((mp_word) DIGIT_BIT)); - } - } - - mp_clamp (&t); - mp_exch (&t, b); - mp_clear (&t); - return MP_OKAY; -} -#endif - -/* $Source: /cvs/libtom/libtommath/bn_s_mp_sqr.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_s_mp_sub.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_s_mp_sub.c deleted file mode 100644 index 0ae91cc..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bn_s_mp_sub.c +++ /dev/null @@ -1,89 +0,0 @@ -#include "tommath.h" -#ifdef BN_S_MP_SUB_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* low level subtraction (assumes |a| > |b|), HAC pp.595 Algorithm 14.9 */ -int -s_mp_sub (mp_int * a, mp_int * b, mp_int * c) -{ - int olduse, res, min, max; - - /* find sizes */ - min = b->used; - max = a->used; - - /* init result */ - if (c->alloc < max) { - if ((res = mp_grow (c, max)) != MP_OKAY) { - return res; - } - } - olduse = c->used; - c->used = max; - - { - register mp_digit u, *tmpa, *tmpb, *tmpc; - register int i; - - /* alias for digit pointers */ - tmpa = a->dp; - tmpb = b->dp; - tmpc = c->dp; - - /* set carry to zero */ - u = 0; - for (i = 0; i < min; i++) { - /* T[i] = A[i] - B[i] - U */ - *tmpc = *tmpa++ - *tmpb++ - u; - - /* U = carry bit of T[i] - * Note this saves performing an AND operation since - * if a carry does occur it will propagate all the way to the - * MSB. As a result a single shift is enough to get the carry - */ - u = *tmpc >> ((mp_digit)(CHAR_BIT * sizeof (mp_digit) - 1)); - - /* Clear carry from T[i] */ - *tmpc++ &= MP_MASK; - } - - /* now copy higher words if any, e.g. if A has more digits than B */ - for (; i < max; i++) { - /* T[i] = A[i] - U */ - *tmpc = *tmpa++ - u; - - /* U = carry bit of T[i] */ - u = *tmpc >> ((mp_digit)(CHAR_BIT * sizeof (mp_digit) - 1)); - - /* Clear carry from T[i] */ - *tmpc++ &= MP_MASK; - } - - /* clear digits above used (since we may not have grown result above) */ - for (i = c->used; i < olduse; i++) { - *tmpc++ = 0; - } - } - - mp_clamp (c); - return MP_OKAY; -} - -#endif - -/* $Source: /cvs/libtom/libtommath/bn_s_mp_sub.c,v $ */ -/* $Revision: 1.4 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bncore.c b/app/jni/src/libultraship/extern/StormLib/src/libtommath/bncore.c deleted file mode 100644 index ad7347f..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/bncore.c +++ /dev/null @@ -1,36 +0,0 @@ -#include "tommath.h" -#ifdef BNCORE_C -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://libtom.org - */ - -/* Known optimal configurations - - CPU /Compiler /MUL CUTOFF/SQR CUTOFF -------------------------------------------------------------- - Intel P4 Northwood /GCC v3.4.1 / 88/ 128/LTM 0.32 ;-) - AMD Athlon64 /GCC v3.4.4 / 80/ 120/LTM 0.35 - -*/ - -int KARATSUBA_MUL_CUTOFF = 80, /* Min. number of digits before Karatsuba multiplication is used. */ - KARATSUBA_SQR_CUTOFF = 120, /* Min. number of digits before Karatsuba squaring is used. */ - - TOOM_MUL_CUTOFF = 350, /* no optimal values of these are known yet so set em high */ - TOOM_SQR_CUTOFF = 400; -#endif - -/* $Source: /cvs/libtom/libtommath/bncore.c,v $ */ -/* $Revision: 1.5 $ */ -/* $Date: 2006/12/28 01:25:13 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/tommath.h b/app/jni/src/libultraship/extern/StormLib/src/libtommath/tommath.h deleted file mode 100644 index 1ead3d0..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/tommath.h +++ /dev/null @@ -1,584 +0,0 @@ -/* LibTomMath, multiple-precision integer library -- Tom St Denis - * - * LibTomMath is a library that provides multiple-precision - * integer arithmetic as well as number theoretic functionality. - * - * The library was designed directly after the MPI library by - * Michael Fromberger but has been written from scratch with - * additional optimizations in place. - * - * The library is free for all purposes without any express - * guarantee it works. - * - * Tom St Denis, tomstdenis@gmail.com, http://math.libtomcrypt.com - */ -#ifndef BN_H_ -#define BN_H_ - -#include -#include -#include -#include -#include - -#include "tommath_class.h" - -#ifndef MIN - #define MIN(x,y) ((x)<(y)?(x):(y)) -#endif - -#ifndef MAX - #define MAX(x,y) ((x)>(y)?(x):(y)) -#endif - -#ifdef __cplusplus -extern "C" { - -/* C++ compilers don't like assigning void * to mp_digit * */ -#define OPT_CAST(x) (x *) - -#else - -/* C on the other hand doesn't care */ -#define OPT_CAST(x) - -#endif - - -/* detect 64-bit mode if possible */ -#if defined(__x86_64__) - #if !(defined(MP_64BIT) && defined(MP_16BIT) && defined(MP_8BIT)) - #define MP_64BIT - #endif -#endif - -/* some default configurations. - * - * A "mp_digit" must be able to hold DIGIT_BIT + 1 bits - * A "mp_word" must be able to hold 2*DIGIT_BIT + 1 bits - * - * At the very least a mp_digit must be able to hold 7 bits - * [any size beyond that is ok provided it doesn't overflow the data type] - */ -#ifdef MP_8BIT - typedef unsigned char mp_digit; - typedef unsigned short mp_word; -#elif defined(MP_16BIT) - typedef unsigned short mp_digit; - typedef unsigned long mp_word; -#elif defined(MP_64BIT) - /* for GCC only on supported platforms */ -#ifndef CRYPT - typedef unsigned long long ulong64; - typedef signed long long long64; -#endif - - typedef unsigned long mp_digit; - typedef unsigned long mp_word __attribute__ ((mode(TI))); - - #define DIGIT_BIT 60 -#else - /* this is the default case, 28-bit digits */ - - /* this is to make porting into LibTomCrypt easier :-) */ -#ifndef CRYPT - #if defined(_MSC_VER) || defined(__BORLANDC__) - typedef unsigned __int64 ulong64; - typedef signed __int64 long64; - #else - typedef unsigned long long ulong64; - typedef signed long long long64; - #endif -#endif - - typedef unsigned long mp_digit; - typedef ulong64 mp_word; - -#ifdef MP_31BIT - /* this is an extension that uses 31-bit digits */ - #define DIGIT_BIT 31 -#else - /* default case is 28-bit digits, defines MP_28BIT as a handy macro to test */ - #define DIGIT_BIT 28 - #define MP_28BIT -#endif -#endif - -/* define heap macros */ -#ifndef CRYPT - /* default to libc stuff */ - #ifndef XMALLOC - #define XMALLOC malloc - #define XFREE free - #define XREALLOC realloc - #define XCALLOC calloc - #else - /* prototypes for our heap functions */ - extern void *XMALLOC(size_t n); - extern void *XREALLOC(void *p, size_t n); - extern void *XCALLOC(size_t n, size_t s); - extern void XFREE(void *p); - #endif -#endif - - -/* otherwise the bits per digit is calculated automatically from the size of a mp_digit */ -#ifndef DIGIT_BIT - #define DIGIT_BIT ((int)((CHAR_BIT * sizeof(mp_digit) - 1))) /* bits per digit */ -#endif - -#define MP_DIGIT_BIT DIGIT_BIT -#define MP_MASK ((((mp_digit)1)<<((mp_digit)DIGIT_BIT))-((mp_digit)1)) -#define MP_DIGIT_MAX MP_MASK - -/* equalities */ -#define MP_LT -1 /* less than */ -#define MP_EQ 0 /* equal to */ -#define MP_GT 1 /* greater than */ - -#define MP_ZPOS 0 /* positive integer */ -#define MP_NEG 1 /* negative */ - -#define MP_OKAY 0 /* ok result */ -#define MP_MEM -2 /* out of mem */ -#define MP_VAL -3 /* invalid input */ -#define MP_RANGE MP_VAL - -#define MP_YES 1 /* yes response */ -#define MP_NO 0 /* no response */ - -/* Primality generation flags */ -#define LTM_PRIME_BBS 0x0001 /* BBS style prime */ -#define LTM_PRIME_SAFE 0x0002 /* Safe prime (p-1)/2 == prime */ -#define LTM_PRIME_2MSB_ON 0x0008 /* force 2nd MSB to 1 */ - -typedef int mp_err; - -/* you'll have to tune these... */ -extern int KARATSUBA_MUL_CUTOFF, - KARATSUBA_SQR_CUTOFF, - TOOM_MUL_CUTOFF, - TOOM_SQR_CUTOFF; - -/* define this to use lower memory usage routines (exptmods mostly) */ -/* #define MP_LOW_MEM */ - -/* default precision */ -#ifndef MP_PREC - #ifndef MP_LOW_MEM - #define MP_PREC 32 /* default digits of precision */ - #else - #define MP_PREC 8 /* default digits of precision */ - #endif -#endif - -/* size of comba arrays, should be at least 2 * 2**(BITS_PER_WORD - BITS_PER_DIGIT*2) */ -#define MP_WARRAY (1 << (sizeof(mp_word) * CHAR_BIT - 2 * DIGIT_BIT + 1)) - -/* the infamous mp_int structure */ -typedef struct { - int used, alloc, sign; - mp_digit *dp; -} mp_int; - -/* callback for mp_prime_random, should fill dst with random bytes and return how many read [upto len] */ -typedef int ltm_prime_callback(unsigned char *dst, int len, void *dat); - - -#define USED(m) ((m)->used) -#define DIGIT(m,k) ((m)->dp[(k)]) -#define SIGN(m) ((m)->sign) - -/* error code to char* string */ -char *mp_error_to_string(int code); - -/* ---> init and deinit bignum functions <--- */ -/* init a bignum */ -int mp_init(mp_int *a); - -/* free a bignum */ -void mp_clear(mp_int *a); - -/* init a null terminated series of arguments */ -int mp_init_multi(mp_int *mp, ...); - -/* clear a null terminated series of arguments */ -void mp_clear_multi(mp_int *mp, ...); - -/* exchange two ints */ -void mp_exch(mp_int *a, mp_int *b); - -/* shrink ram required for a bignum */ -int mp_shrink(mp_int *a); - -/* grow an int to a given size */ -int mp_grow(mp_int *a, int size); - -/* init to a given number of digits */ -int mp_init_size(mp_int *a, int size); - -/* ---> Basic Manipulations <--- */ -#define mp_iszero(a) (((a)->used == 0) ? MP_YES : MP_NO) -#define mp_iseven(a) (((a)->used > 0 && (((a)->dp[0] & 1) == 0)) ? MP_YES : MP_NO) -#define mp_isodd(a) (((a)->used > 0 && (((a)->dp[0] & 1) == 1)) ? MP_YES : MP_NO) - -/* set to zero */ -void mp_zero(mp_int *a); - -/* set to a digit */ -void mp_set(mp_int *a, mp_digit b); - -/* set a 32-bit const */ -int mp_set_int(mp_int *a, unsigned long b); - -/* get a 32-bit value */ -unsigned long mp_get_int(mp_int * a); - -/* initialize and set a digit */ -int mp_init_set (mp_int * a, mp_digit b); - -/* initialize and set 32-bit value */ -int mp_init_set_int (mp_int * a, unsigned long b); - -/* copy, b = a */ -int mp_copy(mp_int *a, mp_int *b); - -/* inits and copies, a = b */ -int mp_init_copy(mp_int *a, mp_int *b); - -/* trim unused digits */ -void mp_clamp(mp_int *a); - -/* ---> digit manipulation <--- */ - -/* right shift by "b" digits */ -void mp_rshd(mp_int *a, int b); - -/* left shift by "b" digits */ -int mp_lshd(mp_int *a, int b); - -/* c = a / 2**b */ -int mp_div_2d(mp_int *a, int b, mp_int *c, mp_int *d); - -/* b = a/2 */ -int mp_div_2(mp_int *a, mp_int *b); - -/* c = a * 2**b */ -int mp_mul_2d(mp_int *a, int b, mp_int *c); - -/* b = a*2 */ -int mp_mul_2(mp_int *a, mp_int *b); - -/* c = a mod 2**d */ -int mp_mod_2d(mp_int *a, int b, mp_int *c); - -/* computes a = 2**b */ -int mp_2expt(mp_int *a, int b); - -/* Counts the number of lsbs which are zero before the first zero bit */ -int mp_cnt_lsb(mp_int *a); - -/* I Love Earth! */ - -/* makes a pseudo-random int of a given size */ -int mp_rand(mp_int *a, int digits); - -/* ---> binary operations <--- */ -/* c = a XOR b */ -int mp_xor(mp_int *a, mp_int *b, mp_int *c); - -/* c = a OR b */ -int mp_or(mp_int *a, mp_int *b, mp_int *c); - -/* c = a AND b */ -int mp_and(mp_int *a, mp_int *b, mp_int *c); - -/* ---> Basic arithmetic <--- */ - -/* b = -a */ -int mp_neg(mp_int *a, mp_int *b); - -/* b = |a| */ -int mp_abs(mp_int *a, mp_int *b); - -/* compare a to b */ -int mp_cmp(mp_int *a, mp_int *b); - -/* compare |a| to |b| */ -int mp_cmp_mag(mp_int *a, mp_int *b); - -/* c = a + b */ -int mp_add(mp_int *a, mp_int *b, mp_int *c); - -/* c = a - b */ -int mp_sub(mp_int *a, mp_int *b, mp_int *c); - -/* c = a * b */ -int mp_mul(mp_int *a, mp_int *b, mp_int *c); - -/* b = a*a */ -int mp_sqr(mp_int *a, mp_int *b); - -/* a/b => cb + d == a */ -int mp_div(mp_int *a, mp_int *b, mp_int *c, mp_int *d); - -/* c = a mod b, 0 <= c < b */ -int mp_mod(mp_int *a, mp_int *b, mp_int *c); - -/* ---> single digit functions <--- */ - -/* compare against a single digit */ -int mp_cmp_d(mp_int *a, mp_digit b); - -/* c = a + b */ -int mp_add_d(mp_int *a, mp_digit b, mp_int *c); - -/* c = a - b */ -int mp_sub_d(mp_int *a, mp_digit b, mp_int *c); - -/* c = a * b */ -int mp_mul_d(mp_int *a, mp_digit b, mp_int *c); - -/* a/b => cb + d == a */ -int mp_div_d(mp_int *a, mp_digit b, mp_int *c, mp_digit *d); - -/* a/3 => 3c + d == a */ -int mp_div_3(mp_int *a, mp_int *c, mp_digit *d); - -/* c = a**b */ -int mp_expt_d(mp_int *a, mp_digit b, mp_int *c); - -/* c = a mod b, 0 <= c < b */ -int mp_mod_d(mp_int *a, mp_digit b, mp_digit *c); - -/* ---> number theory <--- */ - -/* d = a + b (mod c) */ -int mp_addmod(mp_int *a, mp_int *b, mp_int *c, mp_int *d); - -/* d = a - b (mod c) */ -int mp_submod(mp_int *a, mp_int *b, mp_int *c, mp_int *d); - -/* d = a * b (mod c) */ -int mp_mulmod(mp_int *a, mp_int *b, mp_int *c, mp_int *d); - -/* c = a * a (mod b) */ -int mp_sqrmod(mp_int *a, mp_int *b, mp_int *c); - -/* c = 1/a (mod b) */ -int mp_invmod(mp_int *a, mp_int *b, mp_int *c); - -/* c = (a, b) */ -int mp_gcd(mp_int *a, mp_int *b, mp_int *c); - -/* produces value such that U1*a + U2*b = U3 */ -int mp_exteuclid(mp_int *a, mp_int *b, mp_int *U1, mp_int *U2, mp_int *U3); - -/* c = [a, b] or (a*b)/(a, b) */ -int mp_lcm(mp_int *a, mp_int *b, mp_int *c); - -/* finds one of the b'th root of a, such that |c|**b <= |a| - * - * returns error if a < 0 and b is even - */ -int mp_n_root(mp_int *a, mp_digit b, mp_int *c); - -/* special sqrt algo */ -int mp_sqrt(mp_int *arg, mp_int *ret); - -/* is number a square? */ -int mp_is_square(mp_int *arg, int *ret); - -/* computes the jacobi c = (a | n) (or Legendre if b is prime) */ -int mp_jacobi(mp_int *a, mp_int *n, int *c); - -/* used to setup the Barrett reduction for a given modulus b */ -int mp_reduce_setup(mp_int *a, mp_int *b); - -/* Barrett Reduction, computes a (mod b) with a precomputed value c - * - * Assumes that 0 < a <= b*b, note if 0 > a > -(b*b) then you can merely - * compute the reduction as -1 * mp_reduce(mp_abs(a)) [pseudo code]. - */ -int mp_reduce(mp_int *a, mp_int *b, mp_int *c); - -/* setups the montgomery reduction */ -int mp_montgomery_setup(mp_int *a, mp_digit *mp); - -/* computes a = B**n mod b without division or multiplication useful for - * normalizing numbers in a Montgomery system. - */ -int mp_montgomery_calc_normalization(mp_int *a, mp_int *b); - -/* computes x/R == x (mod N) via Montgomery Reduction */ -int mp_montgomery_reduce(mp_int *a, mp_int *m, mp_digit mp); - -/* returns 1 if a is a valid DR modulus */ -int mp_dr_is_modulus(mp_int *a); - -/* sets the value of "d" required for mp_dr_reduce */ -void mp_dr_setup(mp_int *a, mp_digit *d); - -/* reduces a modulo b using the Diminished Radix method */ -int mp_dr_reduce(mp_int *a, mp_int *b, mp_digit mp); - -/* returns true if a can be reduced with mp_reduce_2k */ -int mp_reduce_is_2k(mp_int *a); - -/* determines k value for 2k reduction */ -int mp_reduce_2k_setup(mp_int *a, mp_digit *d); - -/* reduces a modulo b where b is of the form 2**p - k [0 <= a] */ -int mp_reduce_2k(mp_int *a, mp_int *n, mp_digit d); - -/* returns true if a can be reduced with mp_reduce_2k_l */ -int mp_reduce_is_2k_l(mp_int *a); - -/* determines k value for 2k reduction */ -int mp_reduce_2k_setup_l(mp_int *a, mp_int *d); - -/* reduces a modulo b where b is of the form 2**p - k [0 <= a] */ -int mp_reduce_2k_l(mp_int *a, mp_int *n, mp_int *d); - -/* d = a**b (mod c) */ -int mp_exptmod(mp_int *a, mp_int *b, mp_int *c, mp_int *d); - -/* ---> Primes <--- */ - -/* number of primes */ -#ifdef MP_8BIT - #define PRIME_SIZE 31 -#else - #define PRIME_SIZE 256 -#endif - -/* table of first PRIME_SIZE primes */ -extern const mp_digit ltm_prime_tab[]; - -/* result=1 if a is divisible by one of the first PRIME_SIZE primes */ -int mp_prime_is_divisible(mp_int *a, int *result); - -/* performs one Fermat test of "a" using base "b". - * Sets result to 0 if composite or 1 if probable prime - */ -int mp_prime_fermat(mp_int *a, mp_int *b, int *result); - -/* performs one Miller-Rabin test of "a" using base "b". - * Sets result to 0 if composite or 1 if probable prime - */ -int mp_prime_miller_rabin(mp_int *a, mp_int *b, int *result); - -/* This gives [for a given bit size] the number of trials required - * such that Miller-Rabin gives a prob of failure lower than 2^-96 - */ -int mp_prime_rabin_miller_trials(int size); - -/* performs t rounds of Miller-Rabin on "a" using the first - * t prime bases. Also performs an initial sieve of trial - * division. Determines if "a" is prime with probability - * of error no more than (1/4)**t. - * - * Sets result to 1 if probably prime, 0 otherwise - */ -int mp_prime_is_prime(mp_int *a, int t, int *result); - -/* finds the next prime after the number "a" using "t" trials - * of Miller-Rabin. - * - * bbs_style = 1 means the prime must be congruent to 3 mod 4 - */ -int mp_prime_next_prime(mp_int *a, int t, int bbs_style); - -/* makes a truly random prime of a given size (bytes), - * call with bbs = 1 if you want it to be congruent to 3 mod 4 - * - * You have to supply a callback which fills in a buffer with random bytes. "dat" is a parameter you can - * have passed to the callback (e.g. a state or something). This function doesn't use "dat" itself - * so it can be NULL - * - * The prime generated will be larger than 2^(8*size). - */ -#define mp_prime_random(a, t, size, bbs, cb, dat) mp_prime_random_ex(a, t, ((size) * 8) + 1, (bbs==1)?LTM_PRIME_BBS:0, cb, dat) - -/* makes a truly random prime of a given size (bits), - * - * Flags are as follows: - * - * LTM_PRIME_BBS - make prime congruent to 3 mod 4 - * LTM_PRIME_SAFE - make sure (p-1)/2 is prime as well (implies LTM_PRIME_BBS) - * LTM_PRIME_2MSB_OFF - make the 2nd highest bit zero - * LTM_PRIME_2MSB_ON - make the 2nd highest bit one - * - * You have to supply a callback which fills in a buffer with random bytes. "dat" is a parameter you can - * have passed to the callback (e.g. a state or something). This function doesn't use "dat" itself - * so it can be NULL - * - */ -int mp_prime_random_ex(mp_int *a, int t, int size, int flags, ltm_prime_callback cb, void *dat); - -/* ---> radix conversion <--- */ -int mp_count_bits(mp_int *a); - -int mp_unsigned_bin_size(mp_int *a); -int mp_read_unsigned_bin(mp_int *a, const unsigned char *b, int c); -int mp_to_unsigned_bin(mp_int *a, unsigned char *b); -int mp_to_unsigned_bin_n (mp_int * a, unsigned char *b, unsigned long *outlen); - -int mp_signed_bin_size(mp_int *a); -int mp_read_signed_bin(mp_int *a, const unsigned char *b, int c); -int mp_to_signed_bin(mp_int *a, unsigned char *b); -int mp_to_signed_bin_n (mp_int * a, unsigned char *b, unsigned long *outlen); - -int mp_read_radix(mp_int *a, const char *str, int radix); -int mp_toradix(mp_int *a, char *str, int radix); -int mp_toradix_n(mp_int * a, char *str, int radix, int maxlen); -int mp_radix_size(mp_int *a, int radix, int *size); - -int mp_fread(mp_int *a, int radix, FILE *stream); -int mp_fwrite(mp_int *a, int radix, FILE *stream); - -#define mp_read_raw(mp, str, len) mp_read_signed_bin((mp), (str), (len)) -#define mp_raw_size(mp) mp_signed_bin_size(mp) -#define mp_toraw(mp, str) mp_to_signed_bin((mp), (str)) -#define mp_read_mag(mp, str, len) mp_read_unsigned_bin((mp), (str), (len)) -#define mp_mag_size(mp) mp_unsigned_bin_size(mp) -#define mp_tomag(mp, str) mp_to_unsigned_bin((mp), (str)) - -#define mp_tobinary(M, S) mp_toradix((M), (S), 2) -#define mp_tooctal(M, S) mp_toradix((M), (S), 8) -#define mp_todecimal(M, S) mp_toradix((M), (S), 10) -#define mp_tohex(M, S) mp_toradix((M), (S), 16) - -/* lowlevel functions, do not call! */ -int s_mp_add(mp_int *a, mp_int *b, mp_int *c); -int s_mp_sub(mp_int *a, mp_int *b, mp_int *c); -#define s_mp_mul(a, b, c) s_mp_mul_digs(a, b, c, (a)->used + (b)->used + 1) -int fast_s_mp_mul_digs(mp_int *a, mp_int *b, mp_int *c, int digs); -int s_mp_mul_digs(mp_int *a, mp_int *b, mp_int *c, int digs); -int fast_s_mp_mul_high_digs(mp_int *a, mp_int *b, mp_int *c, int digs); -int s_mp_mul_high_digs(mp_int *a, mp_int *b, mp_int *c, int digs); -int fast_s_mp_sqr(mp_int *a, mp_int *b); -int s_mp_sqr(mp_int *a, mp_int *b); -int mp_karatsuba_mul(mp_int *a, mp_int *b, mp_int *c); -int mp_toom_mul(mp_int *a, mp_int *b, mp_int *c); -int mp_karatsuba_sqr(mp_int *a, mp_int *b); -int mp_toom_sqr(mp_int *a, mp_int *b); -int fast_mp_invmod(mp_int *a, mp_int *b, mp_int *c); -int mp_invmod_slow (mp_int * a, mp_int * b, mp_int * c); -int fast_mp_montgomery_reduce(mp_int *a, mp_int *m, mp_digit mp); -int mp_exptmod_fast(mp_int *G, mp_int *X, mp_int *P, mp_int *Y, int mode); -int s_mp_exptmod (mp_int * G, mp_int * X, mp_int * P, mp_int * Y, int mode); -void bn_reverse(unsigned char *s, int len); - -extern const char *mp_s_rmap; - -#ifdef __cplusplus - } -#endif - -#endif - - -/* $Source: /cvs/libtom/libtommath/tommath.h,v $ */ -/* $Revision: 1.8 $ */ -/* $Date: 2006/03/31 14:18:44 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/tommath_class.h b/app/jni/src/libultraship/extern/StormLib/src/libtommath/tommath_class.h deleted file mode 100644 index 18d1553..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/tommath_class.h +++ /dev/null @@ -1,999 +0,0 @@ -#if !(defined(LTM1) && defined(LTM2) && defined(LTM3)) -#if defined(LTM2) -#define LTM3 -#endif -#if defined(LTM1) -#define LTM2 -#endif -#define LTM1 - -#if defined(LTM_ALL) -#define BN_ERROR_C -#define BN_FAST_MP_INVMOD_C -#define BN_FAST_MP_MONTGOMERY_REDUCE_C -#define BN_FAST_S_MP_MUL_DIGS_C -#define BN_FAST_S_MP_MUL_HIGH_DIGS_C -#define BN_FAST_S_MP_SQR_C -#define BN_MP_2EXPT_C -#define BN_MP_ABS_C -#define BN_MP_ADD_C -#define BN_MP_ADD_D_C -#define BN_MP_ADDMOD_C -#define BN_MP_AND_C -#define BN_MP_CLAMP_C -#define BN_MP_CLEAR_C -#define BN_MP_CLEAR_MULTI_C -#define BN_MP_CMP_C -#define BN_MP_CMP_D_C -#define BN_MP_CMP_MAG_C -#define BN_MP_CNT_LSB_C -#define BN_MP_COPY_C -#define BN_MP_COUNT_BITS_C -#define BN_MP_DIV_C -#define BN_MP_DIV_2_C -#define BN_MP_DIV_2D_C -#define BN_MP_DIV_3_C -#define BN_MP_DIV_D_C -#define BN_MP_DR_IS_MODULUS_C -#define BN_MP_DR_REDUCE_C -#define BN_MP_DR_SETUP_C -#define BN_MP_EXCH_C -#define BN_MP_EXPT_D_C -#define BN_MP_EXPTMOD_C -#define BN_MP_EXPTMOD_FAST_C -#define BN_MP_EXTEUCLID_C -#define BN_MP_FREAD_C -#define BN_MP_FWRITE_C -#define BN_MP_GCD_C -#define BN_MP_GET_INT_C -#define BN_MP_GROW_C -#define BN_MP_INIT_C -#define BN_MP_INIT_COPY_C -#define BN_MP_INIT_MULTI_C -#define BN_MP_INIT_SET_C -#define BN_MP_INIT_SET_INT_C -#define BN_MP_INIT_SIZE_C -#define BN_MP_INVMOD_C -#define BN_MP_INVMOD_SLOW_C -#define BN_MP_IS_SQUARE_C -#define BN_MP_JACOBI_C -#define BN_MP_KARATSUBA_MUL_C -#define BN_MP_KARATSUBA_SQR_C -#define BN_MP_LCM_C -#define BN_MP_LSHD_C -#define BN_MP_MOD_C -#define BN_MP_MOD_2D_C -#define BN_MP_MOD_D_C -#define BN_MP_MONTGOMERY_CALC_NORMALIZATION_C -#define BN_MP_MONTGOMERY_REDUCE_C -#define BN_MP_MONTGOMERY_SETUP_C -#define BN_MP_MUL_C -#define BN_MP_MUL_2_C -#define BN_MP_MUL_2D_C -#define BN_MP_MUL_D_C -#define BN_MP_MULMOD_C -#define BN_MP_N_ROOT_C -#define BN_MP_NEG_C -#define BN_MP_OR_C -#define BN_MP_PRIME_FERMAT_C -#define BN_MP_PRIME_IS_DIVISIBLE_C -#define BN_MP_PRIME_IS_PRIME_C -#define BN_MP_PRIME_MILLER_RABIN_C -#define BN_MP_PRIME_NEXT_PRIME_C -#define BN_MP_PRIME_RABIN_MILLER_TRIALS_C -#define BN_MP_PRIME_RANDOM_EX_C -#define BN_MP_RADIX_SIZE_C -#define BN_MP_RADIX_SMAP_C -#define BN_MP_RAND_C -#define BN_MP_READ_RADIX_C -#define BN_MP_READ_SIGNED_BIN_C -#define BN_MP_READ_UNSIGNED_BIN_C -#define BN_MP_REDUCE_C -#define BN_MP_REDUCE_2K_C -#define BN_MP_REDUCE_2K_L_C -#define BN_MP_REDUCE_2K_SETUP_C -#define BN_MP_REDUCE_2K_SETUP_L_C -#define BN_MP_REDUCE_IS_2K_C -#define BN_MP_REDUCE_IS_2K_L_C -#define BN_MP_REDUCE_SETUP_C -#define BN_MP_RSHD_C -#define BN_MP_SET_C -#define BN_MP_SET_INT_C -#define BN_MP_SHRINK_C -#define BN_MP_SIGNED_BIN_SIZE_C -#define BN_MP_SQR_C -#define BN_MP_SQRMOD_C -#define BN_MP_SQRT_C -#define BN_MP_SUB_C -#define BN_MP_SUB_D_C -#define BN_MP_SUBMOD_C -#define BN_MP_TO_SIGNED_BIN_C -#define BN_MP_TO_SIGNED_BIN_N_C -#define BN_MP_TO_UNSIGNED_BIN_C -#define BN_MP_TO_UNSIGNED_BIN_N_C -#define BN_MP_TOOM_MUL_C -#define BN_MP_TOOM_SQR_C -#define BN_MP_TORADIX_C -#define BN_MP_TORADIX_N_C -#define BN_MP_UNSIGNED_BIN_SIZE_C -#define BN_MP_XOR_C -#define BN_MP_ZERO_C -#define BN_PRIME_TAB_C -#define BN_REVERSE_C -#define BN_S_MP_ADD_C -#define BN_S_MP_EXPTMOD_C -#define BN_S_MP_MUL_DIGS_C -#define BN_S_MP_MUL_HIGH_DIGS_C -#define BN_S_MP_SQR_C -#define BN_S_MP_SUB_C -#define BNCORE_C -#endif - -#if defined(BN_ERROR_C) - #define BN_MP_ERROR_TO_STRING_C -#endif - -#if defined(BN_FAST_MP_INVMOD_C) - #define BN_MP_ISEVEN_C - #define BN_MP_INIT_MULTI_C - #define BN_MP_COPY_C - #define BN_MP_MOD_C - #define BN_MP_SET_C - #define BN_MP_DIV_2_C - #define BN_MP_ISODD_C - #define BN_MP_SUB_C - #define BN_MP_CMP_C - #define BN_MP_ISZERO_C - #define BN_MP_CMP_D_C - #define BN_MP_ADD_C - #define BN_MP_EXCH_C - #define BN_MP_CLEAR_MULTI_C -#endif - -#if defined(BN_FAST_MP_MONTGOMERY_REDUCE_C) - #define BN_MP_GROW_C - #define BN_MP_RSHD_C - #define BN_MP_CLAMP_C - #define BN_MP_CMP_MAG_C - #define BN_S_MP_SUB_C -#endif - -#if defined(BN_FAST_S_MP_MUL_DIGS_C) - #define BN_MP_GROW_C - #define BN_MP_CLAMP_C -#endif - -#if defined(BN_FAST_S_MP_MUL_HIGH_DIGS_C) - #define BN_MP_GROW_C - #define BN_MP_CLAMP_C -#endif - -#if defined(BN_FAST_S_MP_SQR_C) - #define BN_MP_GROW_C - #define BN_MP_CLAMP_C -#endif - -#if defined(BN_MP_2EXPT_C) - #define BN_MP_ZERO_C - #define BN_MP_GROW_C -#endif - -#if defined(BN_MP_ABS_C) - #define BN_MP_COPY_C -#endif - -#if defined(BN_MP_ADD_C) - #define BN_S_MP_ADD_C - #define BN_MP_CMP_MAG_C - #define BN_S_MP_SUB_C -#endif - -#if defined(BN_MP_ADD_D_C) - #define BN_MP_GROW_C - #define BN_MP_SUB_D_C - #define BN_MP_CLAMP_C -#endif - -#if defined(BN_MP_ADDMOD_C) - #define BN_MP_INIT_C - #define BN_MP_ADD_C - #define BN_MP_CLEAR_C - #define BN_MP_MOD_C -#endif - -#if defined(BN_MP_AND_C) - #define BN_MP_INIT_COPY_C - #define BN_MP_CLAMP_C - #define BN_MP_EXCH_C - #define BN_MP_CLEAR_C -#endif - -#if defined(BN_MP_CLAMP_C) -#endif - -#if defined(BN_MP_CLEAR_C) -#endif - -#if defined(BN_MP_CLEAR_MULTI_C) - #define BN_MP_CLEAR_C -#endif - -#if defined(BN_MP_CMP_C) - #define BN_MP_CMP_MAG_C -#endif - -#if defined(BN_MP_CMP_D_C) -#endif - -#if defined(BN_MP_CMP_MAG_C) -#endif - -#if defined(BN_MP_CNT_LSB_C) - #define BN_MP_ISZERO_C -#endif - -#if defined(BN_MP_COPY_C) - #define BN_MP_GROW_C -#endif - -#if defined(BN_MP_COUNT_BITS_C) -#endif - -#if defined(BN_MP_DIV_C) - #define BN_MP_ISZERO_C - #define BN_MP_CMP_MAG_C - #define BN_MP_COPY_C - #define BN_MP_ZERO_C - #define BN_MP_INIT_MULTI_C - #define BN_MP_SET_C - #define BN_MP_COUNT_BITS_C - #define BN_MP_ABS_C - #define BN_MP_MUL_2D_C - #define BN_MP_CMP_C - #define BN_MP_SUB_C - #define BN_MP_ADD_C - #define BN_MP_DIV_2D_C - #define BN_MP_EXCH_C - #define BN_MP_CLEAR_MULTI_C - #define BN_MP_INIT_SIZE_C - #define BN_MP_INIT_C - #define BN_MP_INIT_COPY_C - #define BN_MP_LSHD_C - #define BN_MP_RSHD_C - #define BN_MP_MUL_D_C - #define BN_MP_CLAMP_C - #define BN_MP_CLEAR_C -#endif - -#if defined(BN_MP_DIV_2_C) - #define BN_MP_GROW_C - #define BN_MP_CLAMP_C -#endif - -#if defined(BN_MP_DIV_2D_C) - #define BN_MP_COPY_C - #define BN_MP_ZERO_C - #define BN_MP_INIT_C - #define BN_MP_MOD_2D_C - #define BN_MP_CLEAR_C - #define BN_MP_RSHD_C - #define BN_MP_CLAMP_C - #define BN_MP_EXCH_C -#endif - -#if defined(BN_MP_DIV_3_C) - #define BN_MP_INIT_SIZE_C - #define BN_MP_CLAMP_C - #define BN_MP_EXCH_C - #define BN_MP_CLEAR_C -#endif - -#if defined(BN_MP_DIV_D_C) - #define BN_MP_ISZERO_C - #define BN_MP_COPY_C - #define BN_MP_DIV_2D_C - #define BN_MP_DIV_3_C - #define BN_MP_INIT_SIZE_C - #define BN_MP_CLAMP_C - #define BN_MP_EXCH_C - #define BN_MP_CLEAR_C -#endif - -#if defined(BN_MP_DR_IS_MODULUS_C) -#endif - -#if defined(BN_MP_DR_REDUCE_C) - #define BN_MP_GROW_C - #define BN_MP_CLAMP_C - #define BN_MP_CMP_MAG_C - #define BN_S_MP_SUB_C -#endif - -#if defined(BN_MP_DR_SETUP_C) -#endif - -#if defined(BN_MP_EXCH_C) -#endif - -#if defined(BN_MP_EXPT_D_C) - #define BN_MP_INIT_COPY_C - #define BN_MP_SET_C - #define BN_MP_SQR_C - #define BN_MP_CLEAR_C - #define BN_MP_MUL_C -#endif - -#if defined(BN_MP_EXPTMOD_C) - #define BN_MP_INIT_C - #define BN_MP_INVMOD_C - #define BN_MP_CLEAR_C - #define BN_MP_ABS_C - #define BN_MP_CLEAR_MULTI_C - #define BN_MP_REDUCE_IS_2K_L_C - #define BN_S_MP_EXPTMOD_C - #define BN_MP_DR_IS_MODULUS_C - #define BN_MP_REDUCE_IS_2K_C - #define BN_MP_ISODD_C - #define BN_MP_EXPTMOD_FAST_C -#endif - -#if defined(BN_MP_EXPTMOD_FAST_C) - #define BN_MP_COUNT_BITS_C - #define BN_MP_INIT_C - #define BN_MP_CLEAR_C - #define BN_MP_MONTGOMERY_SETUP_C - #define BN_FAST_MP_MONTGOMERY_REDUCE_C - #define BN_MP_MONTGOMERY_REDUCE_C - #define BN_MP_DR_SETUP_C - #define BN_MP_DR_REDUCE_C - #define BN_MP_REDUCE_2K_SETUP_C - #define BN_MP_REDUCE_2K_C - #define BN_MP_MONTGOMERY_CALC_NORMALIZATION_C - #define BN_MP_MULMOD_C - #define BN_MP_SET_C - #define BN_MP_MOD_C - #define BN_MP_COPY_C - #define BN_MP_SQR_C - #define BN_MP_MUL_C - #define BN_MP_EXCH_C -#endif - -#if defined(BN_MP_EXTEUCLID_C) - #define BN_MP_INIT_MULTI_C - #define BN_MP_SET_C - #define BN_MP_COPY_C - #define BN_MP_ISZERO_C - #define BN_MP_DIV_C - #define BN_MP_MUL_C - #define BN_MP_SUB_C - #define BN_MP_NEG_C - #define BN_MP_EXCH_C - #define BN_MP_CLEAR_MULTI_C -#endif - -#if defined(BN_MP_FREAD_C) - #define BN_MP_ZERO_C - #define BN_MP_S_RMAP_C - #define BN_MP_MUL_D_C - #define BN_MP_ADD_D_C - #define BN_MP_CMP_D_C -#endif - -#if defined(BN_MP_FWRITE_C) - #define BN_MP_RADIX_SIZE_C - #define BN_MP_TORADIX_C -#endif - -#if defined(BN_MP_GCD_C) - #define BN_MP_ISZERO_C - #define BN_MP_ABS_C - #define BN_MP_ZERO_C - #define BN_MP_INIT_COPY_C - #define BN_MP_CNT_LSB_C - #define BN_MP_DIV_2D_C - #define BN_MP_CMP_MAG_C - #define BN_MP_EXCH_C - #define BN_S_MP_SUB_C - #define BN_MP_MUL_2D_C - #define BN_MP_CLEAR_C -#endif - -#if defined(BN_MP_GET_INT_C) -#endif - -#if defined(BN_MP_GROW_C) -#endif - -#if defined(BN_MP_INIT_C) -#endif - -#if defined(BN_MP_INIT_COPY_C) - #define BN_MP_COPY_C -#endif - -#if defined(BN_MP_INIT_MULTI_C) - #define BN_MP_ERR_C - #define BN_MP_INIT_C - #define BN_MP_CLEAR_C -#endif - -#if defined(BN_MP_INIT_SET_C) - #define BN_MP_INIT_C - #define BN_MP_SET_C -#endif - -#if defined(BN_MP_INIT_SET_INT_C) - #define BN_MP_INIT_C - #define BN_MP_SET_INT_C -#endif - -#if defined(BN_MP_INIT_SIZE_C) - #define BN_MP_INIT_C -#endif - -#if defined(BN_MP_INVMOD_C) - #define BN_MP_ISZERO_C - #define BN_MP_ISODD_C - #define BN_FAST_MP_INVMOD_C - #define BN_MP_INVMOD_SLOW_C -#endif - -#if defined(BN_MP_INVMOD_SLOW_C) - #define BN_MP_ISZERO_C - #define BN_MP_INIT_MULTI_C - #define BN_MP_MOD_C - #define BN_MP_COPY_C - #define BN_MP_ISEVEN_C - #define BN_MP_SET_C - #define BN_MP_DIV_2_C - #define BN_MP_ISODD_C - #define BN_MP_ADD_C - #define BN_MP_SUB_C - #define BN_MP_CMP_C - #define BN_MP_CMP_D_C - #define BN_MP_CMP_MAG_C - #define BN_MP_EXCH_C - #define BN_MP_CLEAR_MULTI_C -#endif - -#if defined(BN_MP_IS_SQUARE_C) - #define BN_MP_MOD_D_C - #define BN_MP_INIT_SET_INT_C - #define BN_MP_MOD_C - #define BN_MP_GET_INT_C - #define BN_MP_SQRT_C - #define BN_MP_SQR_C - #define BN_MP_CMP_MAG_C - #define BN_MP_CLEAR_C -#endif - -#if defined(BN_MP_JACOBI_C) - #define BN_MP_CMP_D_C - #define BN_MP_ISZERO_C - #define BN_MP_INIT_COPY_C - #define BN_MP_CNT_LSB_C - #define BN_MP_DIV_2D_C - #define BN_MP_MOD_C - #define BN_MP_CLEAR_C -#endif - -#if defined(BN_MP_KARATSUBA_MUL_C) - #define BN_MP_MUL_C - #define BN_MP_INIT_SIZE_C - #define BN_MP_CLAMP_C - #define BN_MP_SUB_C - #define BN_MP_ADD_C - #define BN_MP_LSHD_C - #define BN_MP_CLEAR_C -#endif - -#if defined(BN_MP_KARATSUBA_SQR_C) - #define BN_MP_INIT_SIZE_C - #define BN_MP_CLAMP_C - #define BN_MP_SQR_C - #define BN_MP_SUB_C - #define BN_S_MP_ADD_C - #define BN_MP_LSHD_C - #define BN_MP_ADD_C - #define BN_MP_CLEAR_C -#endif - -#if defined(BN_MP_LCM_C) - #define BN_MP_INIT_MULTI_C - #define BN_MP_GCD_C - #define BN_MP_CMP_MAG_C - #define BN_MP_DIV_C - #define BN_MP_MUL_C - #define BN_MP_CLEAR_MULTI_C -#endif - -#if defined(BN_MP_LSHD_C) - #define BN_MP_GROW_C - #define BN_MP_RSHD_C -#endif - -#if defined(BN_MP_MOD_C) - #define BN_MP_INIT_C - #define BN_MP_DIV_C - #define BN_MP_CLEAR_C - #define BN_MP_ADD_C - #define BN_MP_EXCH_C -#endif - -#if defined(BN_MP_MOD_2D_C) - #define BN_MP_ZERO_C - #define BN_MP_COPY_C - #define BN_MP_CLAMP_C -#endif - -#if defined(BN_MP_MOD_D_C) - #define BN_MP_DIV_D_C -#endif - -#if defined(BN_MP_MONTGOMERY_CALC_NORMALIZATION_C) - #define BN_MP_COUNT_BITS_C - #define BN_MP_2EXPT_C - #define BN_MP_SET_C - #define BN_MP_MUL_2_C - #define BN_MP_CMP_MAG_C - #define BN_S_MP_SUB_C -#endif - -#if defined(BN_MP_MONTGOMERY_REDUCE_C) - #define BN_FAST_MP_MONTGOMERY_REDUCE_C - #define BN_MP_GROW_C - #define BN_MP_CLAMP_C - #define BN_MP_RSHD_C - #define BN_MP_CMP_MAG_C - #define BN_S_MP_SUB_C -#endif - -#if defined(BN_MP_MONTGOMERY_SETUP_C) -#endif - -#if defined(BN_MP_MUL_C) - #define BN_MP_TOOM_MUL_C - #define BN_MP_KARATSUBA_MUL_C - #define BN_FAST_S_MP_MUL_DIGS_C - #define BN_S_MP_MUL_C - #define BN_S_MP_MUL_DIGS_C -#endif - -#if defined(BN_MP_MUL_2_C) - #define BN_MP_GROW_C -#endif - -#if defined(BN_MP_MUL_2D_C) - #define BN_MP_COPY_C - #define BN_MP_GROW_C - #define BN_MP_LSHD_C - #define BN_MP_CLAMP_C -#endif - -#if defined(BN_MP_MUL_D_C) - #define BN_MP_GROW_C - #define BN_MP_CLAMP_C -#endif - -#if defined(BN_MP_MULMOD_C) - #define BN_MP_INIT_C - #define BN_MP_MUL_C - #define BN_MP_CLEAR_C - #define BN_MP_MOD_C -#endif - -#if defined(BN_MP_N_ROOT_C) - #define BN_MP_INIT_C - #define BN_MP_SET_C - #define BN_MP_COPY_C - #define BN_MP_EXPT_D_C - #define BN_MP_MUL_C - #define BN_MP_SUB_C - #define BN_MP_MUL_D_C - #define BN_MP_DIV_C - #define BN_MP_CMP_C - #define BN_MP_SUB_D_C - #define BN_MP_EXCH_C - #define BN_MP_CLEAR_C -#endif - -#if defined(BN_MP_NEG_C) - #define BN_MP_COPY_C - #define BN_MP_ISZERO_C -#endif - -#if defined(BN_MP_OR_C) - #define BN_MP_INIT_COPY_C - #define BN_MP_CLAMP_C - #define BN_MP_EXCH_C - #define BN_MP_CLEAR_C -#endif - -#if defined(BN_MP_PRIME_FERMAT_C) - #define BN_MP_CMP_D_C - #define BN_MP_INIT_C - #define BN_MP_EXPTMOD_C - #define BN_MP_CMP_C - #define BN_MP_CLEAR_C -#endif - -#if defined(BN_MP_PRIME_IS_DIVISIBLE_C) - #define BN_MP_MOD_D_C -#endif - -#if defined(BN_MP_PRIME_IS_PRIME_C) - #define BN_MP_CMP_D_C - #define BN_MP_PRIME_IS_DIVISIBLE_C - #define BN_MP_INIT_C - #define BN_MP_SET_C - #define BN_MP_PRIME_MILLER_RABIN_C - #define BN_MP_CLEAR_C -#endif - -#if defined(BN_MP_PRIME_MILLER_RABIN_C) - #define BN_MP_CMP_D_C - #define BN_MP_INIT_COPY_C - #define BN_MP_SUB_D_C - #define BN_MP_CNT_LSB_C - #define BN_MP_DIV_2D_C - #define BN_MP_EXPTMOD_C - #define BN_MP_CMP_C - #define BN_MP_SQRMOD_C - #define BN_MP_CLEAR_C -#endif - -#if defined(BN_MP_PRIME_NEXT_PRIME_C) - #define BN_MP_CMP_D_C - #define BN_MP_SET_C - #define BN_MP_SUB_D_C - #define BN_MP_ISEVEN_C - #define BN_MP_MOD_D_C - #define BN_MP_INIT_C - #define BN_MP_ADD_D_C - #define BN_MP_PRIME_MILLER_RABIN_C - #define BN_MP_CLEAR_C -#endif - -#if defined(BN_MP_PRIME_RABIN_MILLER_TRIALS_C) -#endif - -#if defined(BN_MP_PRIME_RANDOM_EX_C) - #define BN_MP_READ_UNSIGNED_BIN_C - #define BN_MP_PRIME_IS_PRIME_C - #define BN_MP_SUB_D_C - #define BN_MP_DIV_2_C - #define BN_MP_MUL_2_C - #define BN_MP_ADD_D_C -#endif - -#if defined(BN_MP_RADIX_SIZE_C) - #define BN_MP_COUNT_BITS_C - #define BN_MP_INIT_COPY_C - #define BN_MP_ISZERO_C - #define BN_MP_DIV_D_C - #define BN_MP_CLEAR_C -#endif - -#if defined(BN_MP_RADIX_SMAP_C) - #define BN_MP_S_RMAP_C -#endif - -#if defined(BN_MP_RAND_C) - #define BN_MP_ZERO_C - #define BN_MP_ADD_D_C - #define BN_MP_LSHD_C -#endif - -#if defined(BN_MP_READ_RADIX_C) - #define BN_MP_ZERO_C - #define BN_MP_S_RMAP_C - #define BN_MP_RADIX_SMAP_C - #define BN_MP_MUL_D_C - #define BN_MP_ADD_D_C - #define BN_MP_ISZERO_C -#endif - -#if defined(BN_MP_READ_SIGNED_BIN_C) - #define BN_MP_READ_UNSIGNED_BIN_C -#endif - -#if defined(BN_MP_READ_UNSIGNED_BIN_C) - #define BN_MP_GROW_C - #define BN_MP_ZERO_C - #define BN_MP_MUL_2D_C - #define BN_MP_CLAMP_C -#endif - -#if defined(BN_MP_REDUCE_C) - #define BN_MP_REDUCE_SETUP_C - #define BN_MP_INIT_COPY_C - #define BN_MP_RSHD_C - #define BN_MP_MUL_C - #define BN_S_MP_MUL_HIGH_DIGS_C - #define BN_FAST_S_MP_MUL_HIGH_DIGS_C - #define BN_MP_MOD_2D_C - #define BN_S_MP_MUL_DIGS_C - #define BN_MP_SUB_C - #define BN_MP_CMP_D_C - #define BN_MP_SET_C - #define BN_MP_LSHD_C - #define BN_MP_ADD_C - #define BN_MP_CMP_C - #define BN_S_MP_SUB_C - #define BN_MP_CLEAR_C -#endif - -#if defined(BN_MP_REDUCE_2K_C) - #define BN_MP_INIT_C - #define BN_MP_COUNT_BITS_C - #define BN_MP_DIV_2D_C - #define BN_MP_MUL_D_C - #define BN_S_MP_ADD_C - #define BN_MP_CMP_MAG_C - #define BN_S_MP_SUB_C - #define BN_MP_CLEAR_C -#endif - -#if defined(BN_MP_REDUCE_2K_L_C) - #define BN_MP_INIT_C - #define BN_MP_COUNT_BITS_C - #define BN_MP_DIV_2D_C - #define BN_MP_MUL_C - #define BN_S_MP_ADD_C - #define BN_MP_CMP_MAG_C - #define BN_S_MP_SUB_C - #define BN_MP_CLEAR_C -#endif - -#if defined(BN_MP_REDUCE_2K_SETUP_C) - #define BN_MP_INIT_C - #define BN_MP_COUNT_BITS_C - #define BN_MP_2EXPT_C - #define BN_MP_CLEAR_C - #define BN_S_MP_SUB_C -#endif - -#if defined(BN_MP_REDUCE_2K_SETUP_L_C) - #define BN_MP_INIT_C - #define BN_MP_2EXPT_C - #define BN_MP_COUNT_BITS_C - #define BN_S_MP_SUB_C - #define BN_MP_CLEAR_C -#endif - -#if defined(BN_MP_REDUCE_IS_2K_C) - #define BN_MP_REDUCE_2K_C - #define BN_MP_COUNT_BITS_C -#endif - -#if defined(BN_MP_REDUCE_IS_2K_L_C) -#endif - -#if defined(BN_MP_REDUCE_SETUP_C) - #define BN_MP_2EXPT_C - #define BN_MP_DIV_C -#endif - -#if defined(BN_MP_RSHD_C) - #define BN_MP_ZERO_C -#endif - -#if defined(BN_MP_SET_C) - #define BN_MP_ZERO_C -#endif - -#if defined(BN_MP_SET_INT_C) - #define BN_MP_ZERO_C - #define BN_MP_MUL_2D_C - #define BN_MP_CLAMP_C -#endif - -#if defined(BN_MP_SHRINK_C) -#endif - -#if defined(BN_MP_SIGNED_BIN_SIZE_C) - #define BN_MP_UNSIGNED_BIN_SIZE_C -#endif - -#if defined(BN_MP_SQR_C) - #define BN_MP_TOOM_SQR_C - #define BN_MP_KARATSUBA_SQR_C - #define BN_FAST_S_MP_SQR_C - #define BN_S_MP_SQR_C -#endif - -#if defined(BN_MP_SQRMOD_C) - #define BN_MP_INIT_C - #define BN_MP_SQR_C - #define BN_MP_CLEAR_C - #define BN_MP_MOD_C -#endif - -#if defined(BN_MP_SQRT_C) - #define BN_MP_N_ROOT_C - #define BN_MP_ISZERO_C - #define BN_MP_ZERO_C - #define BN_MP_INIT_COPY_C - #define BN_MP_RSHD_C - #define BN_MP_DIV_C - #define BN_MP_ADD_C - #define BN_MP_DIV_2_C - #define BN_MP_CMP_MAG_C - #define BN_MP_EXCH_C - #define BN_MP_CLEAR_C -#endif - -#if defined(BN_MP_SUB_C) - #define BN_S_MP_ADD_C - #define BN_MP_CMP_MAG_C - #define BN_S_MP_SUB_C -#endif - -#if defined(BN_MP_SUB_D_C) - #define BN_MP_GROW_C - #define BN_MP_ADD_D_C - #define BN_MP_CLAMP_C -#endif - -#if defined(BN_MP_SUBMOD_C) - #define BN_MP_INIT_C - #define BN_MP_SUB_C - #define BN_MP_CLEAR_C - #define BN_MP_MOD_C -#endif - -#if defined(BN_MP_TO_SIGNED_BIN_C) - #define BN_MP_TO_UNSIGNED_BIN_C -#endif - -#if defined(BN_MP_TO_SIGNED_BIN_N_C) - #define BN_MP_SIGNED_BIN_SIZE_C - #define BN_MP_TO_SIGNED_BIN_C -#endif - -#if defined(BN_MP_TO_UNSIGNED_BIN_C) - #define BN_MP_INIT_COPY_C - #define BN_MP_ISZERO_C - #define BN_MP_DIV_2D_C - #define BN_MP_CLEAR_C -#endif - -#if defined(BN_MP_TO_UNSIGNED_BIN_N_C) - #define BN_MP_UNSIGNED_BIN_SIZE_C - #define BN_MP_TO_UNSIGNED_BIN_C -#endif - -#if defined(BN_MP_TOOM_MUL_C) - #define BN_MP_INIT_MULTI_C - #define BN_MP_MOD_2D_C - #define BN_MP_COPY_C - #define BN_MP_RSHD_C - #define BN_MP_MUL_C - #define BN_MP_MUL_2_C - #define BN_MP_ADD_C - #define BN_MP_SUB_C - #define BN_MP_DIV_2_C - #define BN_MP_MUL_2D_C - #define BN_MP_MUL_D_C - #define BN_MP_DIV_3_C - #define BN_MP_LSHD_C - #define BN_MP_CLEAR_MULTI_C -#endif - -#if defined(BN_MP_TOOM_SQR_C) - #define BN_MP_INIT_MULTI_C - #define BN_MP_MOD_2D_C - #define BN_MP_COPY_C - #define BN_MP_RSHD_C - #define BN_MP_SQR_C - #define BN_MP_MUL_2_C - #define BN_MP_ADD_C - #define BN_MP_SUB_C - #define BN_MP_DIV_2_C - #define BN_MP_MUL_2D_C - #define BN_MP_MUL_D_C - #define BN_MP_DIV_3_C - #define BN_MP_LSHD_C - #define BN_MP_CLEAR_MULTI_C -#endif - -#if defined(BN_MP_TORADIX_C) - #define BN_MP_ISZERO_C - #define BN_MP_INIT_COPY_C - #define BN_MP_DIV_D_C - #define BN_MP_CLEAR_C - #define BN_MP_S_RMAP_C -#endif - -#if defined(BN_MP_TORADIX_N_C) - #define BN_MP_ISZERO_C - #define BN_MP_INIT_COPY_C - #define BN_MP_DIV_D_C - #define BN_MP_CLEAR_C - #define BN_MP_S_RMAP_C -#endif - -#if defined(BN_MP_UNSIGNED_BIN_SIZE_C) - #define BN_MP_COUNT_BITS_C -#endif - -#if defined(BN_MP_XOR_C) - #define BN_MP_INIT_COPY_C - #define BN_MP_CLAMP_C - #define BN_MP_EXCH_C - #define BN_MP_CLEAR_C -#endif - -#if defined(BN_MP_ZERO_C) -#endif - -#if defined(BN_PRIME_TAB_C) -#endif - -#if defined(BN_REVERSE_C) -#endif - -#if defined(BN_S_MP_ADD_C) - #define BN_MP_GROW_C - #define BN_MP_CLAMP_C -#endif - -#if defined(BN_S_MP_EXPTMOD_C) - #define BN_MP_COUNT_BITS_C - #define BN_MP_INIT_C - #define BN_MP_CLEAR_C - #define BN_MP_REDUCE_SETUP_C - #define BN_MP_REDUCE_C - #define BN_MP_REDUCE_2K_SETUP_L_C - #define BN_MP_REDUCE_2K_L_C - #define BN_MP_MOD_C - #define BN_MP_COPY_C - #define BN_MP_SQR_C - #define BN_MP_MUL_C - #define BN_MP_SET_C - #define BN_MP_EXCH_C -#endif - -#if defined(BN_S_MP_MUL_DIGS_C) - #define BN_FAST_S_MP_MUL_DIGS_C - #define BN_MP_INIT_SIZE_C - #define BN_MP_CLAMP_C - #define BN_MP_EXCH_C - #define BN_MP_CLEAR_C -#endif - -#if defined(BN_S_MP_MUL_HIGH_DIGS_C) - #define BN_FAST_S_MP_MUL_HIGH_DIGS_C - #define BN_MP_INIT_SIZE_C - #define BN_MP_CLAMP_C - #define BN_MP_EXCH_C - #define BN_MP_CLEAR_C -#endif - -#if defined(BN_S_MP_SQR_C) - #define BN_MP_INIT_SIZE_C - #define BN_MP_CLAMP_C - #define BN_MP_EXCH_C - #define BN_MP_CLEAR_C -#endif - -#if defined(BN_S_MP_SUB_C) - #define BN_MP_GROW_C - #define BN_MP_CLAMP_C -#endif - -#if defined(BNCORE_C) -#endif - -#ifdef LTM3 -#define LTM_LAST -#endif -#include "tommath_superclass.h" -#include "tommath_class.h" -#else -#define LTM_LAST -#endif - -/* $Source: /cvs/libtom/libtommath/tommath_class.h,v $ */ -/* $Revision: 1.3 $ */ -/* $Date: 2005/07/28 11:59:32 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/libtommath/tommath_superclass.h b/app/jni/src/libultraship/extern/StormLib/src/libtommath/tommath_superclass.h deleted file mode 100644 index 2fdebe6..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/libtommath/tommath_superclass.h +++ /dev/null @@ -1,76 +0,0 @@ -/* super class file for PK algos */ - -/* default ... include all MPI */ -#define LTM_ALL - -/* RSA only (does not support DH/DSA/ECC) */ -/* #define SC_RSA_1 */ - -/* For reference.... On an Athlon64 optimizing for speed... - - LTM's mpi.o with all functions [striped] is 142KiB in size. - -*/ - -/* Works for RSA only, mpi.o is 68KiB */ -#ifdef SC_RSA_1 - #define BN_MP_SHRINK_C - #define BN_MP_LCM_C - #define BN_MP_PRIME_RANDOM_EX_C - #define BN_MP_INVMOD_C - #define BN_MP_GCD_C - #define BN_MP_MOD_C - #define BN_MP_MULMOD_C - #define BN_MP_ADDMOD_C - #define BN_MP_EXPTMOD_C - #define BN_MP_SET_INT_C - #define BN_MP_INIT_MULTI_C - #define BN_MP_CLEAR_MULTI_C - #define BN_MP_UNSIGNED_BIN_SIZE_C - #define BN_MP_TO_UNSIGNED_BIN_C - #define BN_MP_MOD_D_C - #define BN_MP_PRIME_RABIN_MILLER_TRIALS_C - #define BN_REVERSE_C - #define BN_PRIME_TAB_C - - /* other modifiers */ - #define BN_MP_DIV_SMALL /* Slower division, not critical */ - - /* here we are on the last pass so we turn things off. The functions classes are still there - * but we remove them specifically from the build. This also invokes tweaks in functions - * like removing support for even moduli, etc... - */ -#ifdef LTM_LAST - #undef BN_MP_TOOM_MUL_C - #undef BN_MP_TOOM_SQR_C - #undef BN_MP_KARATSUBA_MUL_C - #undef BN_MP_KARATSUBA_SQR_C - #undef BN_MP_REDUCE_C - #undef BN_MP_REDUCE_SETUP_C - #undef BN_MP_DR_IS_MODULUS_C - #undef BN_MP_DR_SETUP_C - #undef BN_MP_DR_REDUCE_C - #undef BN_MP_REDUCE_IS_2K_C - #undef BN_MP_REDUCE_2K_SETUP_C - #undef BN_MP_REDUCE_2K_C - #undef BN_S_MP_EXPTMOD_C - #undef BN_MP_DIV_3_C - #undef BN_S_MP_MUL_HIGH_DIGS_C - #undef BN_FAST_S_MP_MUL_HIGH_DIGS_C - #undef BN_FAST_MP_INVMOD_C - - /* To safely undefine these you have to make sure your RSA key won't exceed the Comba threshold - * which is roughly 255 digits [7140 bits for 32-bit machines, 15300 bits for 64-bit machines] - * which means roughly speaking you can handle upto 2536-bit RSA keys with these defined without - * trouble. - */ - #undef BN_S_MP_MUL_DIGS_C - #undef BN_S_MP_SQR_C - #undef BN_MP_MONTGOMERY_REDUCE_C -#endif - -#endif - -/* $Source: /cvs/libtom/libtommath/tommath_superclass.h,v $ */ -/* $Revision: 1.3 $ */ -/* $Date: 2005/05/14 13:29:17 $ */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/lzma/C/LzFind.c b/app/jni/src/libultraship/extern/StormLib/src/lzma/C/LzFind.c deleted file mode 100644 index e3ecb05..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/lzma/C/LzFind.c +++ /dev/null @@ -1,761 +0,0 @@ -/* LzFind.c -- Match finder for LZ algorithms -2009-04-22 : Igor Pavlov : Public domain */ - -#include - -#include "LzFind.h" -#include "LzHash.h" - -#define kEmptyHashValue 0 -#define kMaxValForNormalize ((UInt32)0xFFFFFFFF) -#define kNormalizeStepMin (1 << 10) /* it must be power of 2 */ -#define kNormalizeMask (~(kNormalizeStepMin - 1)) -#define kMaxHistorySize ((UInt32)3 << 30) - -#define kStartMaxLen 3 - -static void LzInWindow_Free(CMatchFinder *p, ISzAlloc *alloc) -{ - if (!p->directInput) - { - alloc->Free(alloc, p->bufferBase); - p->bufferBase = 0; - } -} - -/* keepSizeBefore + keepSizeAfter + keepSizeReserv must be < 4G) */ - -static int LzInWindow_Create(CMatchFinder *p, UInt32 keepSizeReserv, ISzAlloc *alloc) -{ - UInt32 blockSize = p->keepSizeBefore + p->keepSizeAfter + keepSizeReserv; - if (p->directInput) - { - p->blockSize = blockSize; - return 1; - } - if (p->bufferBase == 0 || p->blockSize != blockSize) - { - LzInWindow_Free(p, alloc); - p->blockSize = blockSize; - p->bufferBase = (Byte *)alloc->Alloc(alloc, (size_t)blockSize); - } - return (p->bufferBase != 0); -} - -Byte *MatchFinder_GetPointerToCurrentPos(CMatchFinder *p) { return p->buffer; } -Byte MatchFinder_GetIndexByte(CMatchFinder *p, Int32 index) { return p->buffer[index]; } - -UInt32 MatchFinder_GetNumAvailableBytes(CMatchFinder *p) { return p->streamPos - p->pos; } - -void MatchFinder_ReduceOffsets(CMatchFinder *p, UInt32 subValue) -{ - p->posLimit -= subValue; - p->pos -= subValue; - p->streamPos -= subValue; -} - -static void MatchFinder_ReadBlock(CMatchFinder *p) -{ - if (p->streamEndWasReached || p->result != SZ_OK) - return; - if (p->directInput) - { - UInt32 curSize = 0xFFFFFFFF - p->streamPos; - if (curSize > p->directInputRem) - curSize = (UInt32)p->directInputRem; - p->directInputRem -= curSize; - p->streamPos += curSize; - if (p->directInputRem == 0) - p->streamEndWasReached = 1; - return; - } - for (;;) - { - Byte *dest = p->buffer + (p->streamPos - p->pos); - size_t size = (p->bufferBase + p->blockSize - dest); - if (size == 0) - return; - p->result = p->stream->Read(p->stream, dest, &size); - if (p->result != SZ_OK) - return; - if (size == 0) - { - p->streamEndWasReached = 1; - return; - } - p->streamPos += (UInt32)size; - if (p->streamPos - p->pos > p->keepSizeAfter) - return; - } -} - -void MatchFinder_MoveBlock(CMatchFinder *p) -{ - memmove(p->bufferBase, - p->buffer - p->keepSizeBefore, - (size_t)(p->streamPos - p->pos + p->keepSizeBefore)); - p->buffer = p->bufferBase + p->keepSizeBefore; -} - -int MatchFinder_NeedMove(CMatchFinder *p) -{ - if (p->directInput) - return 0; - /* if (p->streamEndWasReached) return 0; */ - return ((size_t)(p->bufferBase + p->blockSize - p->buffer) <= p->keepSizeAfter); -} - -void MatchFinder_ReadIfRequired(CMatchFinder *p) -{ - if (p->streamEndWasReached) - return; - if (p->keepSizeAfter >= p->streamPos - p->pos) - MatchFinder_ReadBlock(p); -} - -static void MatchFinder_CheckAndMoveAndRead(CMatchFinder *p) -{ - if (MatchFinder_NeedMove(p)) - MatchFinder_MoveBlock(p); - MatchFinder_ReadBlock(p); -} - -static void MatchFinder_SetDefaultSettings(CMatchFinder *p) -{ - p->cutValue = 32; - p->btMode = 1; - p->numHashBytes = 4; - p->bigHash = 0; -} - -#define kCrcPoly 0xEDB88320 - -void MatchFinder_Construct(CMatchFinder *p) -{ - UInt32 i; - p->bufferBase = 0; - p->directInput = 0; - p->hash = 0; - MatchFinder_SetDefaultSettings(p); - - for (i = 0; i < 256; i++) - { - UInt32 r = i; - int j; - for (j = 0; j < 8; j++) - r = (r >> 1) ^ (kCrcPoly & ~((r & 1) - 1)); - p->crc[i] = r; - } -} - -static void MatchFinder_FreeThisClassMemory(CMatchFinder *p, ISzAlloc *alloc) -{ - alloc->Free(alloc, p->hash); - p->hash = 0; -} - -void MatchFinder_Free(CMatchFinder *p, ISzAlloc *alloc) -{ - MatchFinder_FreeThisClassMemory(p, alloc); - LzInWindow_Free(p, alloc); -} - -static CLzRef* AllocRefs(UInt32 num, ISzAlloc *alloc) -{ - size_t sizeInBytes = (size_t)num * sizeof(CLzRef); - if (sizeInBytes / sizeof(CLzRef) != num) - return 0; - return (CLzRef *)alloc->Alloc(alloc, sizeInBytes); -} - -int MatchFinder_Create(CMatchFinder *p, UInt32 historySize, - UInt32 keepAddBufferBefore, UInt32 matchMaxLen, UInt32 keepAddBufferAfter, - ISzAlloc *alloc) -{ - UInt32 sizeReserv; - if (historySize > kMaxHistorySize) - { - MatchFinder_Free(p, alloc); - return 0; - } - sizeReserv = historySize >> 1; - if (historySize > ((UInt32)2 << 30)) - sizeReserv = historySize >> 2; - sizeReserv += (keepAddBufferBefore + matchMaxLen + keepAddBufferAfter) / 2 + (1 << 19); - - p->keepSizeBefore = historySize + keepAddBufferBefore + 1; - p->keepSizeAfter = matchMaxLen + keepAddBufferAfter; - /* we need one additional byte, since we use MoveBlock after pos++ and before dictionary using */ - if (LzInWindow_Create(p, sizeReserv, alloc)) - { - UInt32 newCyclicBufferSize = historySize + 1; - UInt32 hs; - p->matchMaxLen = matchMaxLen; - { - p->fixedHashSize = 0; - if (p->numHashBytes == 2) - hs = (1 << 16) - 1; - else - { - hs = historySize - 1; - hs |= (hs >> 1); - hs |= (hs >> 2); - hs |= (hs >> 4); - hs |= (hs >> 8); - hs >>= 1; - hs |= 0xFFFF; /* don't change it! It's required for Deflate */ - if (hs > (1 << 24)) - { - if (p->numHashBytes == 3) - hs = (1 << 24) - 1; - else - hs >>= 1; - } - } - p->hashMask = hs; - hs++; - if (p->numHashBytes > 2) p->fixedHashSize += kHash2Size; - if (p->numHashBytes > 3) p->fixedHashSize += kHash3Size; - if (p->numHashBytes > 4) p->fixedHashSize += kHash4Size; - hs += p->fixedHashSize; - } - - { - UInt32 prevSize = p->hashSizeSum + p->numSons; - UInt32 newSize; - p->historySize = historySize; - p->hashSizeSum = hs; - p->cyclicBufferSize = newCyclicBufferSize; - p->numSons = (p->btMode ? newCyclicBufferSize * 2 : newCyclicBufferSize); - newSize = p->hashSizeSum + p->numSons; - if (p->hash != 0 && prevSize == newSize) - return 1; - MatchFinder_FreeThisClassMemory(p, alloc); - p->hash = AllocRefs(newSize, alloc); - if (p->hash != 0) - { - p->son = p->hash + p->hashSizeSum; - return 1; - } - } - } - MatchFinder_Free(p, alloc); - return 0; -} - -static void MatchFinder_SetLimits(CMatchFinder *p) -{ - UInt32 limit = kMaxValForNormalize - p->pos; - UInt32 limit2 = p->cyclicBufferSize - p->cyclicBufferPos; - if (limit2 < limit) - limit = limit2; - limit2 = p->streamPos - p->pos; - if (limit2 <= p->keepSizeAfter) - { - if (limit2 > 0) - limit2 = 1; - } - else - limit2 -= p->keepSizeAfter; - if (limit2 < limit) - limit = limit2; - { - UInt32 lenLimit = p->streamPos - p->pos; - if (lenLimit > p->matchMaxLen) - lenLimit = p->matchMaxLen; - p->lenLimit = lenLimit; - } - p->posLimit = p->pos + limit; -} - -void MatchFinder_Init(CMatchFinder *p) -{ - UInt32 i; - for (i = 0; i < p->hashSizeSum; i++) - p->hash[i] = kEmptyHashValue; - p->cyclicBufferPos = 0; - p->buffer = p->bufferBase; - p->pos = p->streamPos = p->cyclicBufferSize; - p->result = SZ_OK; - p->streamEndWasReached = 0; - MatchFinder_ReadBlock(p); - MatchFinder_SetLimits(p); -} - -static UInt32 MatchFinder_GetSubValue(CMatchFinder *p) -{ - return (p->pos - p->historySize - 1) & kNormalizeMask; -} - -void MatchFinder_Normalize3(UInt32 subValue, CLzRef *items, UInt32 numItems) -{ - UInt32 i; - for (i = 0; i < numItems; i++) - { - UInt32 value = items[i]; - if (value <= subValue) - value = kEmptyHashValue; - else - value -= subValue; - items[i] = value; - } -} - -static void MatchFinder_Normalize(CMatchFinder *p) -{ - UInt32 subValue = MatchFinder_GetSubValue(p); - MatchFinder_Normalize3(subValue, p->hash, p->hashSizeSum + p->numSons); - MatchFinder_ReduceOffsets(p, subValue); -} - -static void MatchFinder_CheckLimits(CMatchFinder *p) -{ - if (p->pos == kMaxValForNormalize) - MatchFinder_Normalize(p); - if (!p->streamEndWasReached && p->keepSizeAfter == p->streamPos - p->pos) - MatchFinder_CheckAndMoveAndRead(p); - if (p->cyclicBufferPos == p->cyclicBufferSize) - p->cyclicBufferPos = 0; - MatchFinder_SetLimits(p); -} - -static UInt32 * Hc_GetMatchesSpec(UInt32 lenLimit, UInt32 curMatch, UInt32 pos, const Byte *cur, CLzRef *son, - UInt32 _cyclicBufferPos, UInt32 _cyclicBufferSize, UInt32 cutValue, - UInt32 *distances, UInt32 maxLen) -{ - son[_cyclicBufferPos] = curMatch; - for (;;) - { - UInt32 delta = pos - curMatch; - if (cutValue-- == 0 || delta >= _cyclicBufferSize) - return distances; - { - const Byte *pb = cur - delta; - curMatch = son[_cyclicBufferPos - delta + ((delta > _cyclicBufferPos) ? _cyclicBufferSize : 0)]; - if (pb[maxLen] == cur[maxLen] && *pb == *cur) - { - UInt32 len = 0; - while (++len != lenLimit) - if (pb[len] != cur[len]) - break; - if (maxLen < len) - { - *distances++ = maxLen = len; - *distances++ = delta - 1; - if (len == lenLimit) - return distances; - } - } - } - } -} - -UInt32 * GetMatchesSpec1(UInt32 lenLimit, UInt32 curMatch, UInt32 pos, const Byte *cur, CLzRef *son, - UInt32 _cyclicBufferPos, UInt32 _cyclicBufferSize, UInt32 cutValue, - UInt32 *distances, UInt32 maxLen) -{ - CLzRef *ptr0 = son + (_cyclicBufferPos << 1) + 1; - CLzRef *ptr1 = son + (_cyclicBufferPos << 1); - UInt32 len0 = 0, len1 = 0; - for (;;) - { - UInt32 delta = pos - curMatch; - if (cutValue-- == 0 || delta >= _cyclicBufferSize) - { - *ptr0 = *ptr1 = kEmptyHashValue; - return distances; - } - { - CLzRef *pair = son + ((_cyclicBufferPos - delta + ((delta > _cyclicBufferPos) ? _cyclicBufferSize : 0)) << 1); - const Byte *pb = cur - delta; - UInt32 len = (len0 < len1 ? len0 : len1); - if (pb[len] == cur[len]) - { - if (++len != lenLimit && pb[len] == cur[len]) - while (++len != lenLimit) - if (pb[len] != cur[len]) - break; - if (maxLen < len) - { - *distances++ = maxLen = len; - *distances++ = delta - 1; - if (len == lenLimit) - { - *ptr1 = pair[0]; - *ptr0 = pair[1]; - return distances; - } - } - } - if (pb[len] < cur[len]) - { - *ptr1 = curMatch; - ptr1 = pair + 1; - curMatch = *ptr1; - len1 = len; - } - else - { - *ptr0 = curMatch; - ptr0 = pair; - curMatch = *ptr0; - len0 = len; - } - } - } -} - -static void SkipMatchesSpec(UInt32 lenLimit, UInt32 curMatch, UInt32 pos, const Byte *cur, CLzRef *son, - UInt32 _cyclicBufferPos, UInt32 _cyclicBufferSize, UInt32 cutValue) -{ - CLzRef *ptr0 = son + (_cyclicBufferPos << 1) + 1; - CLzRef *ptr1 = son + (_cyclicBufferPos << 1); - UInt32 len0 = 0, len1 = 0; - for (;;) - { - UInt32 delta = pos - curMatch; - if (cutValue-- == 0 || delta >= _cyclicBufferSize) - { - *ptr0 = *ptr1 = kEmptyHashValue; - return; - } - { - CLzRef *pair = son + ((_cyclicBufferPos - delta + ((delta > _cyclicBufferPos) ? _cyclicBufferSize : 0)) << 1); - const Byte *pb = cur - delta; - UInt32 len = (len0 < len1 ? len0 : len1); - if (pb[len] == cur[len]) - { - while (++len != lenLimit) - if (pb[len] != cur[len]) - break; - { - if (len == lenLimit) - { - *ptr1 = pair[0]; - *ptr0 = pair[1]; - return; - } - } - } - if (pb[len] < cur[len]) - { - *ptr1 = curMatch; - ptr1 = pair + 1; - curMatch = *ptr1; - len1 = len; - } - else - { - *ptr0 = curMatch; - ptr0 = pair; - curMatch = *ptr0; - len0 = len; - } - } - } -} - -#define MOVE_POS \ - ++p->cyclicBufferPos; \ - p->buffer++; \ - if (++p->pos == p->posLimit) MatchFinder_CheckLimits(p); - -#define MOVE_POS_RET MOVE_POS return offset; - -static void MatchFinder_MovePos(CMatchFinder *p) { MOVE_POS; } - -#define GET_MATCHES_HEADER2(minLen, ret_op) \ - UInt32 lenLimit; UInt32 hashValue; const Byte *cur; UInt32 curMatch; \ - lenLimit = p->lenLimit; { if (lenLimit < minLen) { MatchFinder_MovePos(p); ret_op; }} \ - cur = p->buffer; - -#define GET_MATCHES_HEADER(minLen) GET_MATCHES_HEADER2(minLen, return 0) -#define SKIP_HEADER(minLen) GET_MATCHES_HEADER2(minLen, continue) - -#define MF_PARAMS(p) p->pos, p->buffer, p->son, p->cyclicBufferPos, p->cyclicBufferSize, p->cutValue - -#define GET_MATCHES_FOOTER(offset, maxLen) \ - offset = (UInt32)(GetMatchesSpec1(lenLimit, curMatch, MF_PARAMS(p), \ - distances + offset, maxLen) - distances); MOVE_POS_RET; - -#define SKIP_FOOTER \ - SkipMatchesSpec(lenLimit, curMatch, MF_PARAMS(p)); MOVE_POS; - -static UInt32 Bt2_MatchFinder_GetMatches(CMatchFinder *p, UInt32 *distances) -{ - UInt32 offset; - GET_MATCHES_HEADER(2) - HASH2_CALC; - curMatch = p->hash[hashValue]; - p->hash[hashValue] = p->pos; - offset = 0; - GET_MATCHES_FOOTER(offset, 1) -} - -UInt32 Bt3Zip_MatchFinder_GetMatches(CMatchFinder *p, UInt32 *distances) -{ - UInt32 offset; - GET_MATCHES_HEADER(3) - HASH_ZIP_CALC; - curMatch = p->hash[hashValue]; - p->hash[hashValue] = p->pos; - offset = 0; - GET_MATCHES_FOOTER(offset, 2) -} - -static UInt32 Bt3_MatchFinder_GetMatches(CMatchFinder *p, UInt32 *distances) -{ - UInt32 hash2Value, delta2, maxLen, offset; - GET_MATCHES_HEADER(3) - - HASH3_CALC; - - delta2 = p->pos - p->hash[hash2Value]; - curMatch = p->hash[kFix3HashSize + hashValue]; - - p->hash[hash2Value] = - p->hash[kFix3HashSize + hashValue] = p->pos; - - - maxLen = 2; - offset = 0; - if (delta2 < p->cyclicBufferSize && *(cur - delta2) == *cur) - { - for (; maxLen != lenLimit; maxLen++) - if (cur[(ptrdiff_t)maxLen - delta2] != cur[maxLen]) - break; - distances[0] = maxLen; - distances[1] = delta2 - 1; - offset = 2; - if (maxLen == lenLimit) - { - SkipMatchesSpec(lenLimit, curMatch, MF_PARAMS(p)); - MOVE_POS_RET; - } - } - GET_MATCHES_FOOTER(offset, maxLen) -} - -static UInt32 Bt4_MatchFinder_GetMatches(CMatchFinder *p, UInt32 *distances) -{ - UInt32 hash2Value, hash3Value, delta2, delta3, maxLen, offset; - GET_MATCHES_HEADER(4) - - HASH4_CALC; - - delta2 = p->pos - p->hash[ hash2Value]; - delta3 = p->pos - p->hash[kFix3HashSize + hash3Value]; - curMatch = p->hash[kFix4HashSize + hashValue]; - - p->hash[ hash2Value] = - p->hash[kFix3HashSize + hash3Value] = - p->hash[kFix4HashSize + hashValue] = p->pos; - - maxLen = 1; - offset = 0; - if (delta2 < p->cyclicBufferSize && *(cur - delta2) == *cur) - { - distances[0] = maxLen = 2; - distances[1] = delta2 - 1; - offset = 2; - } - if (delta2 != delta3 && delta3 < p->cyclicBufferSize && *(cur - delta3) == *cur) - { - maxLen = 3; - distances[offset + 1] = delta3 - 1; - offset += 2; - delta2 = delta3; - } - if (offset != 0) - { - for (; maxLen != lenLimit; maxLen++) - if (cur[(ptrdiff_t)maxLen - delta2] != cur[maxLen]) - break; - distances[offset - 2] = maxLen; - if (maxLen == lenLimit) - { - SkipMatchesSpec(lenLimit, curMatch, MF_PARAMS(p)); - MOVE_POS_RET; - } - } - if (maxLen < 3) - maxLen = 3; - GET_MATCHES_FOOTER(offset, maxLen) -} - -static UInt32 Hc4_MatchFinder_GetMatches(CMatchFinder *p, UInt32 *distances) -{ - UInt32 hash2Value, hash3Value, delta2, delta3, maxLen, offset; - GET_MATCHES_HEADER(4) - - HASH4_CALC; - - delta2 = p->pos - p->hash[ hash2Value]; - delta3 = p->pos - p->hash[kFix3HashSize + hash3Value]; - curMatch = p->hash[kFix4HashSize + hashValue]; - - p->hash[ hash2Value] = - p->hash[kFix3HashSize + hash3Value] = - p->hash[kFix4HashSize + hashValue] = p->pos; - - maxLen = 1; - offset = 0; - if (delta2 < p->cyclicBufferSize && *(cur - delta2) == *cur) - { - distances[0] = maxLen = 2; - distances[1] = delta2 - 1; - offset = 2; - } - if (delta2 != delta3 && delta3 < p->cyclicBufferSize && *(cur - delta3) == *cur) - { - maxLen = 3; - distances[offset + 1] = delta3 - 1; - offset += 2; - delta2 = delta3; - } - if (offset != 0) - { - for (; maxLen != lenLimit; maxLen++) - if (cur[(ptrdiff_t)maxLen - delta2] != cur[maxLen]) - break; - distances[offset - 2] = maxLen; - if (maxLen == lenLimit) - { - p->son[p->cyclicBufferPos] = curMatch; - MOVE_POS_RET; - } - } - if (maxLen < 3) - maxLen = 3; - offset = (UInt32)(Hc_GetMatchesSpec(lenLimit, curMatch, MF_PARAMS(p), - distances + offset, maxLen) - (distances)); - MOVE_POS_RET -} - -UInt32 Hc3Zip_MatchFinder_GetMatches(CMatchFinder *p, UInt32 *distances) -{ - UInt32 offset; - GET_MATCHES_HEADER(3) - HASH_ZIP_CALC; - curMatch = p->hash[hashValue]; - p->hash[hashValue] = p->pos; - offset = (UInt32)(Hc_GetMatchesSpec(lenLimit, curMatch, MF_PARAMS(p), - distances, 2) - (distances)); - MOVE_POS_RET -} - -static void Bt2_MatchFinder_Skip(CMatchFinder *p, UInt32 num) -{ - do - { - SKIP_HEADER(2) - HASH2_CALC; - curMatch = p->hash[hashValue]; - p->hash[hashValue] = p->pos; - SKIP_FOOTER - } - while (--num != 0); -} - -void Bt3Zip_MatchFinder_Skip(CMatchFinder *p, UInt32 num) -{ - do - { - SKIP_HEADER(3) - HASH_ZIP_CALC; - curMatch = p->hash[hashValue]; - p->hash[hashValue] = p->pos; - SKIP_FOOTER - } - while (--num != 0); -} - -static void Bt3_MatchFinder_Skip(CMatchFinder *p, UInt32 num) -{ - do - { - UInt32 hash2Value; - SKIP_HEADER(3) - HASH3_CALC; - curMatch = p->hash[kFix3HashSize + hashValue]; - p->hash[hash2Value] = - p->hash[kFix3HashSize + hashValue] = p->pos; - SKIP_FOOTER - } - while (--num != 0); -} - -static void Bt4_MatchFinder_Skip(CMatchFinder *p, UInt32 num) -{ - do - { - UInt32 hash2Value, hash3Value; - SKIP_HEADER(4) - HASH4_CALC; - curMatch = p->hash[kFix4HashSize + hashValue]; - p->hash[ hash2Value] = - p->hash[kFix3HashSize + hash3Value] = p->pos; - p->hash[kFix4HashSize + hashValue] = p->pos; - SKIP_FOOTER - } - while (--num != 0); -} - -static void Hc4_MatchFinder_Skip(CMatchFinder *p, UInt32 num) -{ - do - { - UInt32 hash2Value, hash3Value; - SKIP_HEADER(4) - HASH4_CALC; - curMatch = p->hash[kFix4HashSize + hashValue]; - p->hash[ hash2Value] = - p->hash[kFix3HashSize + hash3Value] = - p->hash[kFix4HashSize + hashValue] = p->pos; - p->son[p->cyclicBufferPos] = curMatch; - MOVE_POS - } - while (--num != 0); -} - -void Hc3Zip_MatchFinder_Skip(CMatchFinder *p, UInt32 num) -{ - do - { - SKIP_HEADER(3) - HASH_ZIP_CALC; - curMatch = p->hash[hashValue]; - p->hash[hashValue] = p->pos; - p->son[p->cyclicBufferPos] = curMatch; - MOVE_POS - } - while (--num != 0); -} - -void MatchFinder_CreateVTable(CMatchFinder *p, IMatchFinder *vTable) -{ - vTable->Init = (Mf_Init_Func)MatchFinder_Init; - vTable->GetIndexByte = (Mf_GetIndexByte_Func)MatchFinder_GetIndexByte; - vTable->GetNumAvailableBytes = (Mf_GetNumAvailableBytes_Func)MatchFinder_GetNumAvailableBytes; - vTable->GetPointerToCurrentPos = (Mf_GetPointerToCurrentPos_Func)MatchFinder_GetPointerToCurrentPos; - if (!p->btMode) - { - vTable->GetMatches = (Mf_GetMatches_Func)Hc4_MatchFinder_GetMatches; - vTable->Skip = (Mf_Skip_Func)Hc4_MatchFinder_Skip; - } - else if (p->numHashBytes == 2) - { - vTable->GetMatches = (Mf_GetMatches_Func)Bt2_MatchFinder_GetMatches; - vTable->Skip = (Mf_Skip_Func)Bt2_MatchFinder_Skip; - } - else if (p->numHashBytes == 3) - { - vTable->GetMatches = (Mf_GetMatches_Func)Bt3_MatchFinder_GetMatches; - vTable->Skip = (Mf_Skip_Func)Bt3_MatchFinder_Skip; - } - else - { - vTable->GetMatches = (Mf_GetMatches_Func)Bt4_MatchFinder_GetMatches; - vTable->Skip = (Mf_Skip_Func)Bt4_MatchFinder_Skip; - } -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/lzma/C/LzFind.h b/app/jni/src/libultraship/extern/StormLib/src/lzma/C/LzFind.h deleted file mode 100644 index 010c4b9..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/lzma/C/LzFind.h +++ /dev/null @@ -1,115 +0,0 @@ -/* LzFind.h -- Match finder for LZ algorithms -2009-04-22 : Igor Pavlov : Public domain */ - -#ifndef __LZ_FIND_H -#define __LZ_FIND_H - -#include "Types.h" - -#ifdef __cplusplus -extern "C" { -#endif - -typedef UInt32 CLzRef; - -typedef struct _CMatchFinder -{ - Byte *buffer; - UInt32 pos; - UInt32 posLimit; - UInt32 streamPos; - UInt32 lenLimit; - - UInt32 cyclicBufferPos; - UInt32 cyclicBufferSize; /* it must be = (historySize + 1) */ - - UInt32 matchMaxLen; - CLzRef *hash; - CLzRef *son; - UInt32 hashMask; - UInt32 cutValue; - - Byte *bufferBase; - ISeqInStream *stream; - int streamEndWasReached; - - UInt32 blockSize; - UInt32 keepSizeBefore; - UInt32 keepSizeAfter; - - UInt32 numHashBytes; - int directInput; - size_t directInputRem; - int btMode; - int bigHash; - UInt32 historySize; - UInt32 fixedHashSize; - UInt32 hashSizeSum; - UInt32 numSons; - SRes result; - UInt32 crc[256]; -} CMatchFinder; - -#define Inline_MatchFinder_GetPointerToCurrentPos(p) ((p)->buffer) -#define Inline_MatchFinder_GetIndexByte(p, index) ((p)->buffer[(Int32)(index)]) - -#define Inline_MatchFinder_GetNumAvailableBytes(p) ((p)->streamPos - (p)->pos) - -int MatchFinder_NeedMove(CMatchFinder *p); -Byte *MatchFinder_GetPointerToCurrentPos(CMatchFinder *p); -void MatchFinder_MoveBlock(CMatchFinder *p); -void MatchFinder_ReadIfRequired(CMatchFinder *p); - -void MatchFinder_Construct(CMatchFinder *p); - -/* Conditions: - historySize <= 3 GB - keepAddBufferBefore + matchMaxLen + keepAddBufferAfter < 511MB -*/ -int MatchFinder_Create(CMatchFinder *p, UInt32 historySize, - UInt32 keepAddBufferBefore, UInt32 matchMaxLen, UInt32 keepAddBufferAfter, - ISzAlloc *alloc); -void MatchFinder_Free(CMatchFinder *p, ISzAlloc *alloc); -void MatchFinder_Normalize3(UInt32 subValue, CLzRef *items, UInt32 numItems); -void MatchFinder_ReduceOffsets(CMatchFinder *p, UInt32 subValue); - -UInt32 * GetMatchesSpec1(UInt32 lenLimit, UInt32 curMatch, UInt32 pos, const Byte *buffer, CLzRef *son, - UInt32 _cyclicBufferPos, UInt32 _cyclicBufferSize, UInt32 _cutValue, - UInt32 *distances, UInt32 maxLen); - -/* -Conditions: - Mf_GetNumAvailableBytes_Func must be called before each Mf_GetMatchLen_Func. - Mf_GetPointerToCurrentPos_Func's result must be used only before any other function -*/ - -typedef void (*Mf_Init_Func)(void *object); -typedef Byte (*Mf_GetIndexByte_Func)(void *object, Int32 index); -typedef UInt32 (*Mf_GetNumAvailableBytes_Func)(void *object); -typedef const Byte * (*Mf_GetPointerToCurrentPos_Func)(void *object); -typedef UInt32 (*Mf_GetMatches_Func)(void *object, UInt32 *distances); -typedef void (*Mf_Skip_Func)(void *object, UInt32); - -typedef struct _IMatchFinder -{ - Mf_Init_Func Init; - Mf_GetIndexByte_Func GetIndexByte; - Mf_GetNumAvailableBytes_Func GetNumAvailableBytes; - Mf_GetPointerToCurrentPos_Func GetPointerToCurrentPos; - Mf_GetMatches_Func GetMatches; - Mf_Skip_Func Skip; -} IMatchFinder; - -void MatchFinder_CreateVTable(CMatchFinder *p, IMatchFinder *vTable); - -void MatchFinder_Init(CMatchFinder *p); -UInt32 Bt3Zip_MatchFinder_GetMatches(CMatchFinder *p, UInt32 *distances); -UInt32 Hc3Zip_MatchFinder_GetMatches(CMatchFinder *p, UInt32 *distances); -void Bt3Zip_MatchFinder_Skip(CMatchFinder *p, UInt32 num); -void Hc3Zip_MatchFinder_Skip(CMatchFinder *p, UInt32 num); - -#ifdef __cplusplus -} -#endif - -#endif diff --git a/app/jni/src/libultraship/extern/StormLib/src/lzma/C/LzFindMt.c b/app/jni/src/libultraship/extern/StormLib/src/lzma/C/LzFindMt.c deleted file mode 100644 index aa41ed9..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/lzma/C/LzFindMt.c +++ /dev/null @@ -1,793 +0,0 @@ -/* LzFindMt.c -- multithreaded Match finder for LZ algorithms -2009-09-20 : Igor Pavlov : Public domain */ - -#include "LzHash.h" - -#include "LzFindMt.h" - -void MtSync_Construct(CMtSync *p) -{ - p->wasCreated = False; - p->csWasInitialized = False; - p->csWasEntered = False; - Thread_Construct(&p->thread); - Event_Construct(&p->canStart); - Event_Construct(&p->wasStarted); - Event_Construct(&p->wasStopped); - Semaphore_Construct(&p->freeSemaphore); - Semaphore_Construct(&p->filledSemaphore); -} - -void MtSync_GetNextBlock(CMtSync *p) -{ - if (p->needStart) - { - p->numProcessedBlocks = 1; - p->needStart = False; - p->stopWriting = False; - p->exit = False; - Event_Reset(&p->wasStarted); - Event_Reset(&p->wasStopped); - - Event_Set(&p->canStart); - Event_Wait(&p->wasStarted); - } - else - { - CriticalSection_Leave(&p->cs); - p->csWasEntered = False; - p->numProcessedBlocks++; - Semaphore_Release1(&p->freeSemaphore); - } - Semaphore_Wait(&p->filledSemaphore); - CriticalSection_Enter(&p->cs); - p->csWasEntered = True; -} - -/* MtSync_StopWriting must be called if Writing was started */ - -void MtSync_StopWriting(CMtSync *p) -{ - UInt32 myNumBlocks = p->numProcessedBlocks; - if (!Thread_WasCreated(&p->thread) || p->needStart) - return; - p->stopWriting = True; - if (p->csWasEntered) - { - CriticalSection_Leave(&p->cs); - p->csWasEntered = False; - } - Semaphore_Release1(&p->freeSemaphore); - - Event_Wait(&p->wasStopped); - - while (myNumBlocks++ != p->numProcessedBlocks) - { - Semaphore_Wait(&p->filledSemaphore); - Semaphore_Release1(&p->freeSemaphore); - } - p->needStart = True; -} - -void MtSync_Destruct(CMtSync *p) -{ - if (Thread_WasCreated(&p->thread)) - { - MtSync_StopWriting(p); - p->exit = True; - if (p->needStart) - Event_Set(&p->canStart); - Thread_Wait(&p->thread); - Thread_Close(&p->thread); - } - if (p->csWasInitialized) - { - CriticalSection_Delete(&p->cs); - p->csWasInitialized = False; - } - - Event_Close(&p->canStart); - Event_Close(&p->wasStarted); - Event_Close(&p->wasStopped); - Semaphore_Close(&p->freeSemaphore); - Semaphore_Close(&p->filledSemaphore); - - p->wasCreated = False; -} - -#define RINOK_THREAD(x) { if ((x) != 0) return SZ_ERROR_THREAD; } - -static SRes MtSync_Create2(CMtSync *p, unsigned (MY_STD_CALL *startAddress)(void *), void *obj, UInt32 numBlocks) -{ - if (p->wasCreated) - return SZ_OK; - - RINOK_THREAD(CriticalSection_Init(&p->cs)); - p->csWasInitialized = True; - - RINOK_THREAD(AutoResetEvent_CreateNotSignaled(&p->canStart)); - RINOK_THREAD(AutoResetEvent_CreateNotSignaled(&p->wasStarted)); - RINOK_THREAD(AutoResetEvent_CreateNotSignaled(&p->wasStopped)); - - RINOK_THREAD(Semaphore_Create(&p->freeSemaphore, numBlocks, numBlocks)); - RINOK_THREAD(Semaphore_Create(&p->filledSemaphore, 0, numBlocks)); - - p->needStart = True; - - RINOK_THREAD(Thread_Create(&p->thread, startAddress, obj)); - p->wasCreated = True; - return SZ_OK; -} - -static SRes MtSync_Create(CMtSync *p, unsigned (MY_STD_CALL *startAddress)(void *), void *obj, UInt32 numBlocks) -{ - SRes res = MtSync_Create2(p, startAddress, obj, numBlocks); - if (res != SZ_OK) - MtSync_Destruct(p); - return res; -} - -void MtSync_Init(CMtSync *p) { p->needStart = True; } - -#define kMtMaxValForNormalize 0xFFFFFFFF - -#define DEF_GetHeads2(name, v, action) \ -static void GetHeads ## name(const Byte *p, UInt32 pos, \ -UInt32 *hash, UInt32 hashMask, UInt32 *heads, UInt32 numHeads, const UInt32 *crc) \ -{ action; for (; numHeads != 0; numHeads--) { \ -const UInt32 value = (v); p++; *heads++ = pos - hash[value]; hash[value] = pos++; } } - -#define DEF_GetHeads(name, v) DEF_GetHeads2(name, v, ;) - -DEF_GetHeads2(2, (p[0] | ((UInt32)p[1] << 8)), hashMask = hashMask; crc = crc; ) -DEF_GetHeads(3, (crc[p[0]] ^ p[1] ^ ((UInt32)p[2] << 8)) & hashMask) -DEF_GetHeads(4, (crc[p[0]] ^ p[1] ^ ((UInt32)p[2] << 8) ^ (crc[p[3]] << 5)) & hashMask) -DEF_GetHeads(4b, (crc[p[0]] ^ p[1] ^ ((UInt32)p[2] << 8) ^ ((UInt32)p[3] << 16)) & hashMask) -/* DEF_GetHeads(5, (crc[p[0]] ^ p[1] ^ ((UInt32)p[2] << 8) ^ (crc[p[3]] << 5) ^ (crc[p[4]] << 3)) & hashMask) */ - -void HashThreadFunc(CMatchFinderMt *mt) -{ - CMtSync *p = &mt->hashSync; - for (;;) - { - UInt32 numProcessedBlocks = 0; - Event_Wait(&p->canStart); - Event_Set(&p->wasStarted); - for (;;) - { - if (p->exit) - return; - if (p->stopWriting) - { - p->numProcessedBlocks = numProcessedBlocks; - Event_Set(&p->wasStopped); - break; - } - - { - CMatchFinder *mf = mt->MatchFinder; - if (MatchFinder_NeedMove(mf)) - { - CriticalSection_Enter(&mt->btSync.cs); - CriticalSection_Enter(&mt->hashSync.cs); - { - const Byte *beforePtr = MatchFinder_GetPointerToCurrentPos(mf); - const Byte *afterPtr; - MatchFinder_MoveBlock(mf); - afterPtr = MatchFinder_GetPointerToCurrentPos(mf); - mt->pointerToCurPos -= beforePtr - afterPtr; - mt->buffer -= beforePtr - afterPtr; - } - CriticalSection_Leave(&mt->btSync.cs); - CriticalSection_Leave(&mt->hashSync.cs); - continue; - } - - Semaphore_Wait(&p->freeSemaphore); - - MatchFinder_ReadIfRequired(mf); - if (mf->pos > (kMtMaxValForNormalize - kMtHashBlockSize)) - { - UInt32 subValue = (mf->pos - mf->historySize - 1); - MatchFinder_ReduceOffsets(mf, subValue); - MatchFinder_Normalize3(subValue, mf->hash + mf->fixedHashSize, mf->hashMask + 1); - } - { - UInt32 *heads = mt->hashBuf + ((numProcessedBlocks++) & kMtHashNumBlocksMask) * kMtHashBlockSize; - UInt32 num = mf->streamPos - mf->pos; - heads[0] = 2; - heads[1] = num; - if (num >= mf->numHashBytes) - { - num = num - mf->numHashBytes + 1; - if (num > kMtHashBlockSize - 2) - num = kMtHashBlockSize - 2; - mt->GetHeadsFunc(mf->buffer, mf->pos, mf->hash + mf->fixedHashSize, mf->hashMask, heads + 2, num, mf->crc); - heads[0] += num; - } - mf->pos += num; - mf->buffer += num; - } - } - - Semaphore_Release1(&p->filledSemaphore); - } - } -} - -void MatchFinderMt_GetNextBlock_Hash(CMatchFinderMt *p) -{ - MtSync_GetNextBlock(&p->hashSync); - p->hashBufPosLimit = p->hashBufPos = ((p->hashSync.numProcessedBlocks - 1) & kMtHashNumBlocksMask) * kMtHashBlockSize; - p->hashBufPosLimit += p->hashBuf[p->hashBufPos++]; - p->hashNumAvail = p->hashBuf[p->hashBufPos++]; -} - -#define kEmptyHashValue 0 - -/* #define MFMT_GM_INLINE */ - -#ifdef MFMT_GM_INLINE - -#define NO_INLINE MY_FAST_CALL - -Int32 NO_INLINE GetMatchesSpecN(UInt32 lenLimit, UInt32 pos, const Byte *cur, CLzRef *son, - UInt32 _cyclicBufferPos, UInt32 _cyclicBufferSize, UInt32 _cutValue, - UInt32 *_distances, UInt32 _maxLen, const UInt32 *hash, Int32 limit, UInt32 size, UInt32 *posRes) -{ - do - { - UInt32 *distances = _distances + 1; - UInt32 curMatch = pos - *hash++; - - CLzRef *ptr0 = son + (_cyclicBufferPos << 1) + 1; - CLzRef *ptr1 = son + (_cyclicBufferPos << 1); - UInt32 len0 = 0, len1 = 0; - UInt32 cutValue = _cutValue; - UInt32 maxLen = _maxLen; - for (;;) - { - UInt32 delta = pos - curMatch; - if (cutValue-- == 0 || delta >= _cyclicBufferSize) - { - *ptr0 = *ptr1 = kEmptyHashValue; - break; - } - { - CLzRef *pair = son + ((_cyclicBufferPos - delta + ((delta > _cyclicBufferPos) ? _cyclicBufferSize : 0)) << 1); - const Byte *pb = cur - delta; - UInt32 len = (len0 < len1 ? len0 : len1); - if (pb[len] == cur[len]) - { - if (++len != lenLimit && pb[len] == cur[len]) - while (++len != lenLimit) - if (pb[len] != cur[len]) - break; - if (maxLen < len) - { - *distances++ = maxLen = len; - *distances++ = delta - 1; - if (len == lenLimit) - { - *ptr1 = pair[0]; - *ptr0 = pair[1]; - break; - } - } - } - if (pb[len] < cur[len]) - { - *ptr1 = curMatch; - ptr1 = pair + 1; - curMatch = *ptr1; - len1 = len; - } - else - { - *ptr0 = curMatch; - ptr0 = pair; - curMatch = *ptr0; - len0 = len; - } - } - } - pos++; - _cyclicBufferPos++; - cur++; - { - UInt32 num = (UInt32)(distances - _distances); - *_distances = num - 1; - _distances += num; - limit -= num; - } - } - while (limit > 0 && --size != 0); - *posRes = pos; - return limit; -} - -#endif - -void BtGetMatches(CMatchFinderMt *p, UInt32 *distances) -{ - UInt32 numProcessed = 0; - UInt32 curPos = 2; - UInt32 limit = kMtBtBlockSize - (p->matchMaxLen * 2); - distances[1] = p->hashNumAvail; - while (curPos < limit) - { - if (p->hashBufPos == p->hashBufPosLimit) - { - MatchFinderMt_GetNextBlock_Hash(p); - distances[1] = numProcessed + p->hashNumAvail; - if (p->hashNumAvail >= p->numHashBytes) - continue; - for (; p->hashNumAvail != 0; p->hashNumAvail--) - distances[curPos++] = 0; - break; - } - { - UInt32 size = p->hashBufPosLimit - p->hashBufPos; - UInt32 lenLimit = p->matchMaxLen; - UInt32 pos = p->pos; - UInt32 cyclicBufferPos = p->cyclicBufferPos; - if (lenLimit >= p->hashNumAvail) - lenLimit = p->hashNumAvail; - { - UInt32 size2 = p->hashNumAvail - lenLimit + 1; - if (size2 < size) - size = size2; - size2 = p->cyclicBufferSize - cyclicBufferPos; - if (size2 < size) - size = size2; - } - #ifndef MFMT_GM_INLINE - while (curPos < limit && size-- != 0) - { - UInt32 *startDistances = distances + curPos; - UInt32 num = (UInt32)(GetMatchesSpec1(lenLimit, pos - p->hashBuf[p->hashBufPos++], - pos, p->buffer, p->son, cyclicBufferPos, p->cyclicBufferSize, p->cutValue, - startDistances + 1, p->numHashBytes - 1) - startDistances); - *startDistances = num - 1; - curPos += num; - cyclicBufferPos++; - pos++; - p->buffer++; - } - #else - { - UInt32 posRes; - curPos = limit - GetMatchesSpecN(lenLimit, pos, p->buffer, p->son, cyclicBufferPos, p->cyclicBufferSize, p->cutValue, - distances + curPos, p->numHashBytes - 1, p->hashBuf + p->hashBufPos, (Int32)(limit - curPos) , size, &posRes); - p->hashBufPos += posRes - pos; - cyclicBufferPos += posRes - pos; - p->buffer += posRes - pos; - pos = posRes; - } - #endif - - numProcessed += pos - p->pos; - p->hashNumAvail -= pos - p->pos; - p->pos = pos; - if (cyclicBufferPos == p->cyclicBufferSize) - cyclicBufferPos = 0; - p->cyclicBufferPos = cyclicBufferPos; - } - } - distances[0] = curPos; -} - -void BtFillBlock(CMatchFinderMt *p, UInt32 globalBlockIndex) -{ - CMtSync *sync = &p->hashSync; - if (!sync->needStart) - { - CriticalSection_Enter(&sync->cs); - sync->csWasEntered = True; - } - - BtGetMatches(p, p->btBuf + (globalBlockIndex & kMtBtNumBlocksMask) * kMtBtBlockSize); - - if (p->pos > kMtMaxValForNormalize - kMtBtBlockSize) - { - UInt32 subValue = p->pos - p->cyclicBufferSize; - MatchFinder_Normalize3(subValue, p->son, p->cyclicBufferSize * 2); - p->pos -= subValue; - } - - if (!sync->needStart) - { - CriticalSection_Leave(&sync->cs); - sync->csWasEntered = False; - } -} - -void BtThreadFunc(CMatchFinderMt *mt) -{ - CMtSync *p = &mt->btSync; - for (;;) - { - UInt32 blockIndex = 0; - Event_Wait(&p->canStart); - Event_Set(&p->wasStarted); - for (;;) - { - if (p->exit) - return; - if (p->stopWriting) - { - p->numProcessedBlocks = blockIndex; - MtSync_StopWriting(&mt->hashSync); - Event_Set(&p->wasStopped); - break; - } - Semaphore_Wait(&p->freeSemaphore); - BtFillBlock(mt, blockIndex++); - Semaphore_Release1(&p->filledSemaphore); - } - } -} - -void MatchFinderMt_Construct(CMatchFinderMt *p) -{ - p->hashBuf = 0; - MtSync_Construct(&p->hashSync); - MtSync_Construct(&p->btSync); -} - -void MatchFinderMt_FreeMem(CMatchFinderMt *p, ISzAlloc *alloc) -{ - alloc->Free(alloc, p->hashBuf); - p->hashBuf = 0; -} - -void MatchFinderMt_Destruct(CMatchFinderMt *p, ISzAlloc *alloc) -{ - MtSync_Destruct(&p->hashSync); - MtSync_Destruct(&p->btSync); - MatchFinderMt_FreeMem(p, alloc); -} - -#define kHashBufferSize (kMtHashBlockSize * kMtHashNumBlocks) -#define kBtBufferSize (kMtBtBlockSize * kMtBtNumBlocks) - -static unsigned MY_STD_CALL HashThreadFunc2(void *p) { HashThreadFunc((CMatchFinderMt *)p); return 0; } -static unsigned MY_STD_CALL BtThreadFunc2(void *p) -{ - Byte allocaDummy[0x180]; - int i = 0; - for (i = 0; i < 16; i++) - allocaDummy[i] = (Byte)i; - BtThreadFunc((CMatchFinderMt *)p); - return 0; -} - -SRes MatchFinderMt_Create(CMatchFinderMt *p, UInt32 historySize, UInt32 keepAddBufferBefore, - UInt32 matchMaxLen, UInt32 keepAddBufferAfter, ISzAlloc *alloc) -{ - CMatchFinder *mf = p->MatchFinder; - p->historySize = historySize; - if (kMtBtBlockSize <= matchMaxLen * 4) - return SZ_ERROR_PARAM; - if (p->hashBuf == 0) - { - p->hashBuf = (UInt32 *)alloc->Alloc(alloc, (kHashBufferSize + kBtBufferSize) * sizeof(UInt32)); - if (p->hashBuf == 0) - return SZ_ERROR_MEM; - p->btBuf = p->hashBuf + kHashBufferSize; - } - keepAddBufferBefore += (kHashBufferSize + kBtBufferSize); - keepAddBufferAfter += kMtHashBlockSize; - if (!MatchFinder_Create(mf, historySize, keepAddBufferBefore, matchMaxLen, keepAddBufferAfter, alloc)) - return SZ_ERROR_MEM; - - RINOK(MtSync_Create(&p->hashSync, HashThreadFunc2, p, kMtHashNumBlocks)); - RINOK(MtSync_Create(&p->btSync, BtThreadFunc2, p, kMtBtNumBlocks)); - return SZ_OK; -} - -/* Call it after ReleaseStream / SetStream */ -void MatchFinderMt_Init(CMatchFinderMt *p) -{ - CMatchFinder *mf = p->MatchFinder; - p->btBufPos = p->btBufPosLimit = 0; - p->hashBufPos = p->hashBufPosLimit = 0; - MatchFinder_Init(mf); - p->pointerToCurPos = MatchFinder_GetPointerToCurrentPos(mf); - p->btNumAvailBytes = 0; - p->lzPos = p->historySize + 1; - - p->hash = mf->hash; - p->fixedHashSize = mf->fixedHashSize; - p->crc = mf->crc; - - p->son = mf->son; - p->matchMaxLen = mf->matchMaxLen; - p->numHashBytes = mf->numHashBytes; - p->pos = mf->pos; - p->buffer = mf->buffer; - p->cyclicBufferPos = mf->cyclicBufferPos; - p->cyclicBufferSize = mf->cyclicBufferSize; - p->cutValue = mf->cutValue; -} - -/* ReleaseStream is required to finish multithreading */ -void MatchFinderMt_ReleaseStream(CMatchFinderMt *p) -{ - MtSync_StopWriting(&p->btSync); - /* p->MatchFinder->ReleaseStream(); */ -} - -void MatchFinderMt_Normalize(CMatchFinderMt *p) -{ - MatchFinder_Normalize3(p->lzPos - p->historySize - 1, p->hash, p->fixedHashSize); - p->lzPos = p->historySize + 1; -} - -void MatchFinderMt_GetNextBlock_Bt(CMatchFinderMt *p) -{ - UInt32 blockIndex; - MtSync_GetNextBlock(&p->btSync); - blockIndex = ((p->btSync.numProcessedBlocks - 1) & kMtBtNumBlocksMask); - p->btBufPosLimit = p->btBufPos = blockIndex * kMtBtBlockSize; - p->btBufPosLimit += p->btBuf[p->btBufPos++]; - p->btNumAvailBytes = p->btBuf[p->btBufPos++]; - if (p->lzPos >= kMtMaxValForNormalize - kMtBtBlockSize) - MatchFinderMt_Normalize(p); -} - -const Byte * MatchFinderMt_GetPointerToCurrentPos(CMatchFinderMt *p) -{ - return p->pointerToCurPos; -} - -#define GET_NEXT_BLOCK_IF_REQUIRED if (p->btBufPos == p->btBufPosLimit) MatchFinderMt_GetNextBlock_Bt(p); - -UInt32 MatchFinderMt_GetNumAvailableBytes(CMatchFinderMt *p) -{ - GET_NEXT_BLOCK_IF_REQUIRED; - return p->btNumAvailBytes; -} - -Byte MatchFinderMt_GetIndexByte(CMatchFinderMt *p, Int32 index) -{ - return p->pointerToCurPos[index]; -} - -UInt32 * MixMatches2(CMatchFinderMt *p, UInt32 matchMinPos, UInt32 *distances) -{ - UInt32 hash2Value, curMatch2; - UInt32 *hash = p->hash; - const Byte *cur = p->pointerToCurPos; - UInt32 lzPos = p->lzPos; - MT_HASH2_CALC - - curMatch2 = hash[hash2Value]; - hash[hash2Value] = lzPos; - - if (curMatch2 >= matchMinPos) - if (cur[(ptrdiff_t)curMatch2 - lzPos] == cur[0]) - { - *distances++ = 2; - *distances++ = lzPos - curMatch2 - 1; - } - return distances; -} - -UInt32 * MixMatches3(CMatchFinderMt *p, UInt32 matchMinPos, UInt32 *distances) -{ - UInt32 hash2Value, hash3Value, curMatch2, curMatch3; - UInt32 *hash = p->hash; - const Byte *cur = p->pointerToCurPos; - UInt32 lzPos = p->lzPos; - MT_HASH3_CALC - - curMatch2 = hash[ hash2Value]; - curMatch3 = hash[kFix3HashSize + hash3Value]; - - hash[ hash2Value] = - hash[kFix3HashSize + hash3Value] = - lzPos; - - if (curMatch2 >= matchMinPos && cur[(ptrdiff_t)curMatch2 - lzPos] == cur[0]) - { - distances[1] = lzPos - curMatch2 - 1; - if (cur[(ptrdiff_t)curMatch2 - lzPos + 2] == cur[2]) - { - distances[0] = 3; - return distances + 2; - } - distances[0] = 2; - distances += 2; - } - if (curMatch3 >= matchMinPos && cur[(ptrdiff_t)curMatch3 - lzPos] == cur[0]) - { - *distances++ = 3; - *distances++ = lzPos - curMatch3 - 1; - } - return distances; -} - -/* -UInt32 *MixMatches4(CMatchFinderMt *p, UInt32 matchMinPos, UInt32 *distances) -{ - UInt32 hash2Value, hash3Value, hash4Value, curMatch2, curMatch3, curMatch4; - UInt32 *hash = p->hash; - const Byte *cur = p->pointerToCurPos; - UInt32 lzPos = p->lzPos; - MT_HASH4_CALC - - curMatch2 = hash[ hash2Value]; - curMatch3 = hash[kFix3HashSize + hash3Value]; - curMatch4 = hash[kFix4HashSize + hash4Value]; - - hash[ hash2Value] = - hash[kFix3HashSize + hash3Value] = - hash[kFix4HashSize + hash4Value] = - lzPos; - - if (curMatch2 >= matchMinPos && cur[(ptrdiff_t)curMatch2 - lzPos] == cur[0]) - { - distances[1] = lzPos - curMatch2 - 1; - if (cur[(ptrdiff_t)curMatch2 - lzPos + 2] == cur[2]) - { - distances[0] = (cur[(ptrdiff_t)curMatch2 - lzPos + 3] == cur[3]) ? 4 : 3; - return distances + 2; - } - distances[0] = 2; - distances += 2; - } - if (curMatch3 >= matchMinPos && cur[(ptrdiff_t)curMatch3 - lzPos] == cur[0]) - { - distances[1] = lzPos - curMatch3 - 1; - if (cur[(ptrdiff_t)curMatch3 - lzPos + 3] == cur[3]) - { - distances[0] = 4; - return distances + 2; - } - distances[0] = 3; - distances += 2; - } - - if (curMatch4 >= matchMinPos) - if ( - cur[(ptrdiff_t)curMatch4 - lzPos] == cur[0] && - cur[(ptrdiff_t)curMatch4 - lzPos + 3] == cur[3] - ) - { - *distances++ = 4; - *distances++ = lzPos - curMatch4 - 1; - } - return distances; -} -*/ - -#define INCREASE_LZ_POS p->lzPos++; p->pointerToCurPos++; - -UInt32 MatchFinderMt2_GetMatches(CMatchFinderMt *p, UInt32 *distances) -{ - const UInt32 *btBuf = p->btBuf + p->btBufPos; - UInt32 len = *btBuf++; - p->btBufPos += 1 + len; - p->btNumAvailBytes--; - { - UInt32 i; - for (i = 0; i < len; i += 2) - { - *distances++ = *btBuf++; - *distances++ = *btBuf++; - } - } - INCREASE_LZ_POS - return len; -} - -UInt32 MatchFinderMt_GetMatches(CMatchFinderMt *p, UInt32 *distances) -{ - const UInt32 *btBuf = p->btBuf + p->btBufPos; - UInt32 len = *btBuf++; - p->btBufPos += 1 + len; - - if (len == 0) - { - if (p->btNumAvailBytes-- >= 4) - len = (UInt32)(p->MixMatchesFunc(p, p->lzPos - p->historySize, distances) - (distances)); - } - else - { - /* Condition: there are matches in btBuf with length < p->numHashBytes */ - UInt32 *distances2; - p->btNumAvailBytes--; - distances2 = p->MixMatchesFunc(p, p->lzPos - btBuf[1], distances); - do - { - *distances2++ = *btBuf++; - *distances2++ = *btBuf++; - } - while ((len -= 2) != 0); - len = (UInt32)(distances2 - (distances)); - } - INCREASE_LZ_POS - return len; -} - -#define SKIP_HEADER2_MT do { GET_NEXT_BLOCK_IF_REQUIRED -#define SKIP_HEADER_MT(n) SKIP_HEADER2_MT if (p->btNumAvailBytes-- >= (n)) { const Byte *cur = p->pointerToCurPos; UInt32 *hash = p->hash; -#define SKIP_FOOTER_MT } INCREASE_LZ_POS p->btBufPos += p->btBuf[p->btBufPos] + 1; } while (--num != 0); - -void MatchFinderMt0_Skip(CMatchFinderMt *p, UInt32 num) -{ - SKIP_HEADER2_MT { p->btNumAvailBytes--; - SKIP_FOOTER_MT -} - -void MatchFinderMt2_Skip(CMatchFinderMt *p, UInt32 num) -{ - SKIP_HEADER_MT(2) - UInt32 hash2Value; - MT_HASH2_CALC - hash[hash2Value] = p->lzPos; - SKIP_FOOTER_MT -} - -void MatchFinderMt3_Skip(CMatchFinderMt *p, UInt32 num) -{ - SKIP_HEADER_MT(3) - UInt32 hash2Value, hash3Value; - MT_HASH3_CALC - hash[kFix3HashSize + hash3Value] = - hash[ hash2Value] = - p->lzPos; - SKIP_FOOTER_MT -} - -/* -void MatchFinderMt4_Skip(CMatchFinderMt *p, UInt32 num) -{ - SKIP_HEADER_MT(4) - UInt32 hash2Value, hash3Value, hash4Value; - MT_HASH4_CALC - hash[kFix4HashSize + hash4Value] = - hash[kFix3HashSize + hash3Value] = - hash[ hash2Value] = - p->lzPos; - SKIP_FOOTER_MT -} -*/ - -void MatchFinderMt_CreateVTable(CMatchFinderMt *p, IMatchFinder *vTable) -{ - vTable->Init = (Mf_Init_Func)MatchFinderMt_Init; - vTable->GetIndexByte = (Mf_GetIndexByte_Func)MatchFinderMt_GetIndexByte; - vTable->GetNumAvailableBytes = (Mf_GetNumAvailableBytes_Func)MatchFinderMt_GetNumAvailableBytes; - vTable->GetPointerToCurrentPos = (Mf_GetPointerToCurrentPos_Func)MatchFinderMt_GetPointerToCurrentPos; - vTable->GetMatches = (Mf_GetMatches_Func)MatchFinderMt_GetMatches; - switch(p->MatchFinder->numHashBytes) - { - case 2: - p->GetHeadsFunc = GetHeads2; - p->MixMatchesFunc = (Mf_Mix_Matches)0; - vTable->Skip = (Mf_Skip_Func)MatchFinderMt0_Skip; - vTable->GetMatches = (Mf_GetMatches_Func)MatchFinderMt2_GetMatches; - break; - case 3: - p->GetHeadsFunc = GetHeads3; - p->MixMatchesFunc = (Mf_Mix_Matches)MixMatches2; - vTable->Skip = (Mf_Skip_Func)MatchFinderMt2_Skip; - break; - default: - /* case 4: */ - p->GetHeadsFunc = p->MatchFinder->bigHash ? GetHeads4b : GetHeads4; - /* p->GetHeadsFunc = GetHeads4; */ - p->MixMatchesFunc = (Mf_Mix_Matches)MixMatches3; - vTable->Skip = (Mf_Skip_Func)MatchFinderMt3_Skip; - break; - /* - default: - p->GetHeadsFunc = GetHeads5; - p->MixMatchesFunc = (Mf_Mix_Matches)MixMatches4; - vTable->Skip = (Mf_Skip_Func)MatchFinderMt4_Skip; - break; - */ - } -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/lzma/C/LzFindMt.h b/app/jni/src/libultraship/extern/StormLib/src/lzma/C/LzFindMt.h deleted file mode 100644 index b985af5..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/lzma/C/LzFindMt.h +++ /dev/null @@ -1,105 +0,0 @@ -/* LzFindMt.h -- multithreaded Match finder for LZ algorithms -2009-02-07 : Igor Pavlov : Public domain */ - -#ifndef __LZ_FIND_MT_H -#define __LZ_FIND_MT_H - -#include "LzFind.h" -#include "Threads.h" - -#ifdef __cplusplus -extern "C" { -#endif - -#define kMtHashBlockSize (1 << 13) -#define kMtHashNumBlocks (1 << 3) -#define kMtHashNumBlocksMask (kMtHashNumBlocks - 1) - -#define kMtBtBlockSize (1 << 14) -#define kMtBtNumBlocks (1 << 6) -#define kMtBtNumBlocksMask (kMtBtNumBlocks - 1) - -typedef struct _CMtSync -{ - Bool wasCreated; - Bool needStart; - Bool exit; - Bool stopWriting; - - CThread thread; - CAutoResetEvent canStart; - CAutoResetEvent wasStarted; - CAutoResetEvent wasStopped; - CSemaphore freeSemaphore; - CSemaphore filledSemaphore; - Bool csWasInitialized; - Bool csWasEntered; - CCriticalSection cs; - UInt32 numProcessedBlocks; -} CMtSync; - -typedef UInt32 * (*Mf_Mix_Matches)(void *p, UInt32 matchMinPos, UInt32 *distances); - -/* kMtCacheLineDummy must be >= size_of_CPU_cache_line */ -#define kMtCacheLineDummy 128 - -typedef void (*Mf_GetHeads)(const Byte *buffer, UInt32 pos, - UInt32 *hash, UInt32 hashMask, UInt32 *heads, UInt32 numHeads, const UInt32 *crc); - -typedef struct _CMatchFinderMt -{ - /* LZ */ - const Byte *pointerToCurPos; - UInt32 *btBuf; - UInt32 btBufPos; - UInt32 btBufPosLimit; - UInt32 lzPos; - UInt32 btNumAvailBytes; - - UInt32 *hash; - UInt32 fixedHashSize; - UInt32 historySize; - const UInt32 *crc; - - Mf_Mix_Matches MixMatchesFunc; - - /* LZ + BT */ - CMtSync btSync; - Byte btDummy[kMtCacheLineDummy]; - - /* BT */ - UInt32 *hashBuf; - UInt32 hashBufPos; - UInt32 hashBufPosLimit; - UInt32 hashNumAvail; - - CLzRef *son; - UInt32 matchMaxLen; - UInt32 numHashBytes; - UInt32 pos; - Byte *buffer; - UInt32 cyclicBufferPos; - UInt32 cyclicBufferSize; /* it must be historySize + 1 */ - UInt32 cutValue; - - /* BT + Hash */ - CMtSync hashSync; - /* Byte hashDummy[kMtCacheLineDummy]; */ - - /* Hash */ - Mf_GetHeads GetHeadsFunc; - CMatchFinder *MatchFinder; -} CMatchFinderMt; - -void MatchFinderMt_Construct(CMatchFinderMt *p); -void MatchFinderMt_Destruct(CMatchFinderMt *p, ISzAlloc *alloc); -SRes MatchFinderMt_Create(CMatchFinderMt *p, UInt32 historySize, UInt32 keepAddBufferBefore, - UInt32 matchMaxLen, UInt32 keepAddBufferAfter, ISzAlloc *alloc); -void MatchFinderMt_CreateVTable(CMatchFinderMt *p, IMatchFinder *vTable); -void MatchFinderMt_ReleaseStream(CMatchFinderMt *p); - -#ifdef __cplusplus -} -#endif - -#endif diff --git a/app/jni/src/libultraship/extern/StormLib/src/lzma/C/LzHash.h b/app/jni/src/libultraship/extern/StormLib/src/lzma/C/LzHash.h deleted file mode 100644 index f3e8996..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/lzma/C/LzHash.h +++ /dev/null @@ -1,54 +0,0 @@ -/* LzHash.h -- HASH functions for LZ algorithms -2009-02-07 : Igor Pavlov : Public domain */ - -#ifndef __LZ_HASH_H -#define __LZ_HASH_H - -#define kHash2Size (1 << 10) -#define kHash3Size (1 << 16) -#define kHash4Size (1 << 20) - -#define kFix3HashSize (kHash2Size) -#define kFix4HashSize (kHash2Size + kHash3Size) -#define kFix5HashSize (kHash2Size + kHash3Size + kHash4Size) - -#define HASH2_CALC hashValue = cur[0] | ((UInt32)cur[1] << 8); - -#define HASH3_CALC { \ - UInt32 temp = p->crc[cur[0]] ^ cur[1]; \ - hash2Value = temp & (kHash2Size - 1); \ - hashValue = (temp ^ ((UInt32)cur[2] << 8)) & p->hashMask; } - -#define HASH4_CALC { \ - UInt32 temp = p->crc[cur[0]] ^ cur[1]; \ - hash2Value = temp & (kHash2Size - 1); \ - hash3Value = (temp ^ ((UInt32)cur[2] << 8)) & (kHash3Size - 1); \ - hashValue = (temp ^ ((UInt32)cur[2] << 8) ^ (p->crc[cur[3]] << 5)) & p->hashMask; } - -#define HASH5_CALC { \ - UInt32 temp = p->crc[cur[0]] ^ cur[1]; \ - hash2Value = temp & (kHash2Size - 1); \ - hash3Value = (temp ^ ((UInt32)cur[2] << 8)) & (kHash3Size - 1); \ - hash4Value = (temp ^ ((UInt32)cur[2] << 8) ^ (p->crc[cur[3]] << 5)); \ - hashValue = (hash4Value ^ (p->crc[cur[4]] << 3)) & p->hashMask; \ - hash4Value &= (kHash4Size - 1); } - -/* #define HASH_ZIP_CALC hashValue = ((cur[0] | ((UInt32)cur[1] << 8)) ^ p->crc[cur[2]]) & 0xFFFF; */ -#define HASH_ZIP_CALC hashValue = ((cur[2] | ((UInt32)cur[0] << 8)) ^ p->crc[cur[1]]) & 0xFFFF; - - -#define MT_HASH2_CALC \ - hash2Value = (p->crc[cur[0]] ^ cur[1]) & (kHash2Size - 1); - -#define MT_HASH3_CALC { \ - UInt32 temp = p->crc[cur[0]] ^ cur[1]; \ - hash2Value = temp & (kHash2Size - 1); \ - hash3Value = (temp ^ ((UInt32)cur[2] << 8)) & (kHash3Size - 1); } - -#define MT_HASH4_CALC { \ - UInt32 temp = p->crc[cur[0]] ^ cur[1]; \ - hash2Value = temp & (kHash2Size - 1); \ - hash3Value = (temp ^ ((UInt32)cur[2] << 8)) & (kHash3Size - 1); \ - hash4Value = (temp ^ ((UInt32)cur[2] << 8) ^ (p->crc[cur[3]] << 5)) & (kHash4Size - 1); } - -#endif diff --git a/app/jni/src/libultraship/extern/StormLib/src/lzma/C/LzmaDec.c b/app/jni/src/libultraship/extern/StormLib/src/lzma/C/LzmaDec.c deleted file mode 100644 index 2036761..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/lzma/C/LzmaDec.c +++ /dev/null @@ -1,999 +0,0 @@ -/* LzmaDec.c -- LZMA Decoder -2009-09-20 : Igor Pavlov : Public domain */ - -#include "LzmaDec.h" - -#include - -#define kNumTopBits 24 -#define kTopValue ((UInt32)1 << kNumTopBits) - -#define kNumBitModelTotalBits 11 -#define kBitModelTotal (1 << kNumBitModelTotalBits) -#define kNumMoveBits 5 - -#define RC_INIT_SIZE 5 - -#define NORMALIZE if (range < kTopValue) { range <<= 8; code = (code << 8) | (*buf++); } - -#define IF_BIT_0(p) ttt = *(p); NORMALIZE; bound = (range >> kNumBitModelTotalBits) * ttt; if (code < bound) -#define UPDATE_0(p) range = bound; *(p) = (CLzmaProb)(ttt + ((kBitModelTotal - ttt) >> kNumMoveBits)); -#define UPDATE_1(p) range -= bound; code -= bound; *(p) = (CLzmaProb)(ttt - (ttt >> kNumMoveBits)); -#define GET_BIT2(p, i, A0, A1) IF_BIT_0(p) \ - { UPDATE_0(p); i = (i + i); A0; } else \ - { UPDATE_1(p); i = (i + i) + 1; A1; } -#define GET_BIT(p, i) GET_BIT2(p, i, ; , ;) - -#define TREE_GET_BIT(probs, i) { GET_BIT((probs + i), i); } -#define TREE_DECODE(probs, limit, i) \ - { i = 1; do { TREE_GET_BIT(probs, i); } while (i < limit); i -= limit; } - -/* #define _LZMA_SIZE_OPT */ - -#ifdef _LZMA_SIZE_OPT -#define TREE_6_DECODE(probs, i) TREE_DECODE(probs, (1 << 6), i) -#else -#define TREE_6_DECODE(probs, i) \ - { i = 1; \ - TREE_GET_BIT(probs, i); \ - TREE_GET_BIT(probs, i); \ - TREE_GET_BIT(probs, i); \ - TREE_GET_BIT(probs, i); \ - TREE_GET_BIT(probs, i); \ - TREE_GET_BIT(probs, i); \ - i -= 0x40; } -#endif - -#define NORMALIZE_CHECK if (range < kTopValue) { if (buf >= bufLimit) return DUMMY_ERROR; range <<= 8; code = (code << 8) | (*buf++); } - -#define IF_BIT_0_CHECK(p) ttt = *(p); NORMALIZE_CHECK; bound = (range >> kNumBitModelTotalBits) * ttt; if (code < bound) -#define UPDATE_0_CHECK range = bound; -#define UPDATE_1_CHECK range -= bound; code -= bound; -#define GET_BIT2_CHECK(p, i, A0, A1) IF_BIT_0_CHECK(p) \ - { UPDATE_0_CHECK; i = (i + i); A0; } else \ - { UPDATE_1_CHECK; i = (i + i) + 1; A1; } -#define GET_BIT_CHECK(p, i) GET_BIT2_CHECK(p, i, ; , ;) -#define TREE_DECODE_CHECK(probs, limit, i) \ - { i = 1; do { GET_BIT_CHECK(probs + i, i) } while (i < limit); i -= limit; } - - -#define kNumPosBitsMax 4 -#define kNumPosStatesMax (1 << kNumPosBitsMax) - -#define kLenNumLowBits 3 -#define kLenNumLowSymbols (1 << kLenNumLowBits) -#define kLenNumMidBits 3 -#define kLenNumMidSymbols (1 << kLenNumMidBits) -#define kLenNumHighBits 8 -#define kLenNumHighSymbols (1 << kLenNumHighBits) - -#define LenChoice 0 -#define LenChoice2 (LenChoice + 1) -#define LenLow (LenChoice2 + 1) -#define LenMid (LenLow + (kNumPosStatesMax << kLenNumLowBits)) -#define LenHigh (LenMid + (kNumPosStatesMax << kLenNumMidBits)) -#define kNumLenProbs (LenHigh + kLenNumHighSymbols) - - -#define kNumStates 12 -#define kNumLitStates 7 - -#define kStartPosModelIndex 4 -#define kEndPosModelIndex 14 -#define kNumFullDistances (1 << (kEndPosModelIndex >> 1)) - -#define kNumPosSlotBits 6 -#define kNumLenToPosStates 4 - -#define kNumAlignBits 4 -#define kAlignTableSize (1 << kNumAlignBits) - -#define kMatchMinLen 2 -#define kMatchSpecLenStart (kMatchMinLen + kLenNumLowSymbols + kLenNumMidSymbols + kLenNumHighSymbols) - -#define IsMatch 0 -#define IsRep (IsMatch + (kNumStates << kNumPosBitsMax)) -#define IsRepG0 (IsRep + kNumStates) -#define IsRepG1 (IsRepG0 + kNumStates) -#define IsRepG2 (IsRepG1 + kNumStates) -#define IsRep0Long (IsRepG2 + kNumStates) -#define PosSlot (IsRep0Long + (kNumStates << kNumPosBitsMax)) -#define SpecPos (PosSlot + (kNumLenToPosStates << kNumPosSlotBits)) -#define Align (SpecPos + kNumFullDistances - kEndPosModelIndex) -#define LenCoder (Align + kAlignTableSize) -#define RepLenCoder (LenCoder + kNumLenProbs) -#define Literal (RepLenCoder + kNumLenProbs) - -#define LZMA_BASE_SIZE 1846 -#define LZMA_LIT_SIZE 768 - -#define LzmaProps_GetNumProbs(p) ((UInt32)LZMA_BASE_SIZE + (LZMA_LIT_SIZE << ((p)->lc + (p)->lp))) - -#if Literal != LZMA_BASE_SIZE -StopCompilingDueBUG -#endif - -#define LZMA_DIC_MIN (1 << 12) - -/* First LZMA-symbol is always decoded. -And it decodes new LZMA-symbols while (buf < bufLimit), but "buf" is without last normalization -Out: - Result: - SZ_OK - OK - SZ_ERROR_DATA - Error - p->remainLen: - < kMatchSpecLenStart : normal remain - = kMatchSpecLenStart : finished - = kMatchSpecLenStart + 1 : Flush marker - = kMatchSpecLenStart + 2 : State Init Marker -*/ - -static int MY_FAST_CALL LzmaDec_DecodeReal(CLzmaDec *p, SizeT limit, const Byte *bufLimit) -{ - CLzmaProb *probs = p->probs; - - unsigned state = p->state; - UInt32 rep0 = p->reps[0], rep1 = p->reps[1], rep2 = p->reps[2], rep3 = p->reps[3]; - unsigned pbMask = ((unsigned)1 << (p->prop.pb)) - 1; - unsigned lpMask = ((unsigned)1 << (p->prop.lp)) - 1; - unsigned lc = p->prop.lc; - - Byte *dic = p->dic; - SizeT dicBufSize = p->dicBufSize; - SizeT dicPos = p->dicPos; - - UInt32 processedPos = p->processedPos; - UInt32 checkDicSize = p->checkDicSize; - unsigned len = 0; - - const Byte *buf = p->buf; - UInt32 range = p->range; - UInt32 code = p->code; - - do - { - CLzmaProb *prob; - UInt32 bound; - unsigned ttt; - unsigned posState = processedPos & pbMask; - - prob = probs + IsMatch + (state << kNumPosBitsMax) + posState; - IF_BIT_0(prob) - { - unsigned symbol; - UPDATE_0(prob); - prob = probs + Literal; - if (checkDicSize != 0 || processedPos != 0) - prob += (LZMA_LIT_SIZE * (((processedPos & lpMask) << lc) + - (dic[(dicPos == 0 ? dicBufSize : dicPos) - 1] >> (8 - lc)))); - - if (state < kNumLitStates) - { - state -= (state < 4) ? state : 3; - symbol = 1; - do { GET_BIT(prob + symbol, symbol) } while (symbol < 0x100); - } - else - { - unsigned matchByte = p->dic[(dicPos - rep0) + ((dicPos < rep0) ? dicBufSize : 0)]; - unsigned offs = 0x100; - state -= (state < 10) ? 3 : 6; - symbol = 1; - do - { - unsigned bit; - CLzmaProb *probLit; - matchByte <<= 1; - bit = (matchByte & offs); - probLit = prob + offs + bit + symbol; - GET_BIT2(probLit, symbol, offs &= ~bit, offs &= bit) - } - while (symbol < 0x100); - } - dic[dicPos++] = (Byte)symbol; - processedPos++; - continue; - } - else - { - UPDATE_1(prob); - prob = probs + IsRep + state; - IF_BIT_0(prob) - { - UPDATE_0(prob); - state += kNumStates; - prob = probs + LenCoder; - } - else - { - UPDATE_1(prob); - if (checkDicSize == 0 && processedPos == 0) - return SZ_ERROR_DATA; - prob = probs + IsRepG0 + state; - IF_BIT_0(prob) - { - UPDATE_0(prob); - prob = probs + IsRep0Long + (state << kNumPosBitsMax) + posState; - IF_BIT_0(prob) - { - UPDATE_0(prob); - dic[dicPos] = dic[(dicPos - rep0) + ((dicPos < rep0) ? dicBufSize : 0)]; - dicPos++; - processedPos++; - state = state < kNumLitStates ? 9 : 11; - continue; - } - UPDATE_1(prob); - } - else - { - UInt32 distance; - UPDATE_1(prob); - prob = probs + IsRepG1 + state; - IF_BIT_0(prob) - { - UPDATE_0(prob); - distance = rep1; - } - else - { - UPDATE_1(prob); - prob = probs + IsRepG2 + state; - IF_BIT_0(prob) - { - UPDATE_0(prob); - distance = rep2; - } - else - { - UPDATE_1(prob); - distance = rep3; - rep3 = rep2; - } - rep2 = rep1; - } - rep1 = rep0; - rep0 = distance; - } - state = state < kNumLitStates ? 8 : 11; - prob = probs + RepLenCoder; - } - { - unsigned limit, offset; - CLzmaProb *probLen = prob + LenChoice; - IF_BIT_0(probLen) - { - UPDATE_0(probLen); - probLen = prob + LenLow + (posState << kLenNumLowBits); - offset = 0; - limit = (1 << kLenNumLowBits); - } - else - { - UPDATE_1(probLen); - probLen = prob + LenChoice2; - IF_BIT_0(probLen) - { - UPDATE_0(probLen); - probLen = prob + LenMid + (posState << kLenNumMidBits); - offset = kLenNumLowSymbols; - limit = (1 << kLenNumMidBits); - } - else - { - UPDATE_1(probLen); - probLen = prob + LenHigh; - offset = kLenNumLowSymbols + kLenNumMidSymbols; - limit = (1 << kLenNumHighBits); - } - } - TREE_DECODE(probLen, limit, len); - len += offset; - } - - if (state >= kNumStates) - { - UInt32 distance; - prob = probs + PosSlot + - ((len < kNumLenToPosStates ? len : kNumLenToPosStates - 1) << kNumPosSlotBits); - TREE_6_DECODE(prob, distance); - if (distance >= kStartPosModelIndex) - { - unsigned posSlot = (unsigned)distance; - int numDirectBits = (int)(((distance >> 1) - 1)); - distance = (2 | (distance & 1)); - if (posSlot < kEndPosModelIndex) - { - distance <<= numDirectBits; - prob = probs + SpecPos + distance - posSlot - 1; - { - UInt32 mask = 1; - unsigned i = 1; - do - { - GET_BIT2(prob + i, i, ; , distance |= mask); - mask <<= 1; - } - while (--numDirectBits != 0); - } - } - else - { - numDirectBits -= kNumAlignBits; - do - { - NORMALIZE - range >>= 1; - - { - UInt32 t; - code -= range; - t = (0 - ((UInt32)code >> 31)); /* (UInt32)((Int32)code >> 31) */ - distance = (distance << 1) + (t + 1); - code += range & t; - } - /* - distance <<= 1; - if (code >= range) - { - code -= range; - distance |= 1; - } - */ - } - while (--numDirectBits != 0); - prob = probs + Align; - distance <<= kNumAlignBits; - { - unsigned i = 1; - GET_BIT2(prob + i, i, ; , distance |= 1); - GET_BIT2(prob + i, i, ; , distance |= 2); - GET_BIT2(prob + i, i, ; , distance |= 4); - GET_BIT2(prob + i, i, ; , distance |= 8); - } - if (distance == (UInt32)0xFFFFFFFF) - { - len += kMatchSpecLenStart; - state -= kNumStates; - break; - } - } - } - rep3 = rep2; - rep2 = rep1; - rep1 = rep0; - rep0 = distance + 1; - if (checkDicSize == 0) - { - if (distance >= processedPos) - return SZ_ERROR_DATA; - } - else if (distance >= checkDicSize) - return SZ_ERROR_DATA; - state = (state < kNumStates + kNumLitStates) ? kNumLitStates : kNumLitStates + 3; - } - - len += kMatchMinLen; - - if (limit == dicPos) - return SZ_ERROR_DATA; - { - SizeT rem = limit - dicPos; - unsigned curLen = ((rem < len) ? (unsigned)rem : len); - SizeT pos = (dicPos - rep0) + ((dicPos < rep0) ? dicBufSize : 0); - - processedPos += curLen; - - len -= curLen; - if (pos + curLen <= dicBufSize) - { - Byte *dest = dic + dicPos; - ptrdiff_t src = (ptrdiff_t)pos - (ptrdiff_t)dicPos; - const Byte *lim = dest + curLen; - dicPos += curLen; - do - *(dest) = (Byte)*(dest + src); - while (++dest != lim); - } - else - { - do - { - dic[dicPos++] = dic[pos]; - if (++pos == dicBufSize) - pos = 0; - } - while (--curLen != 0); - } - } - } - } - while (dicPos < limit && buf < bufLimit); - NORMALIZE; - p->buf = buf; - p->range = range; - p->code = code; - p->remainLen = len; - p->dicPos = dicPos; - p->processedPos = processedPos; - p->reps[0] = rep0; - p->reps[1] = rep1; - p->reps[2] = rep2; - p->reps[3] = rep3; - p->state = state; - - return SZ_OK; -} - -static void MY_FAST_CALL LzmaDec_WriteRem(CLzmaDec *p, SizeT limit) -{ - if (p->remainLen != 0 && p->remainLen < kMatchSpecLenStart) - { - Byte *dic = p->dic; - SizeT dicPos = p->dicPos; - SizeT dicBufSize = p->dicBufSize; - unsigned len = p->remainLen; - UInt32 rep0 = p->reps[0]; - if (limit - dicPos < len) - len = (unsigned)(limit - dicPos); - - if (p->checkDicSize == 0 && p->prop.dicSize - p->processedPos <= len) - p->checkDicSize = p->prop.dicSize; - - p->processedPos += len; - p->remainLen -= len; - while (len-- != 0) - { - dic[dicPos] = dic[(dicPos - rep0) + ((dicPos < rep0) ? dicBufSize : 0)]; - dicPos++; - } - p->dicPos = dicPos; - } -} - -static int MY_FAST_CALL LzmaDec_DecodeReal2(CLzmaDec *p, SizeT limit, const Byte *bufLimit) -{ - do - { - SizeT limit2 = limit; - if (p->checkDicSize == 0) - { - UInt32 rem = p->prop.dicSize - p->processedPos; - if (limit - p->dicPos > rem) - limit2 = p->dicPos + rem; - } - RINOK(LzmaDec_DecodeReal(p, limit2, bufLimit)); - if (p->processedPos >= p->prop.dicSize) - p->checkDicSize = p->prop.dicSize; - LzmaDec_WriteRem(p, limit); - } - while (p->dicPos < limit && p->buf < bufLimit && p->remainLen < kMatchSpecLenStart); - - if (p->remainLen > kMatchSpecLenStart) - { - p->remainLen = kMatchSpecLenStart; - } - return 0; -} - -typedef enum -{ - DUMMY_ERROR, /* unexpected end of input stream */ - DUMMY_LIT, - DUMMY_MATCH, - DUMMY_REP -} ELzmaDummy; - -static ELzmaDummy LzmaDec_TryDummy(const CLzmaDec *p, const Byte *buf, SizeT inSize) -{ - UInt32 range = p->range; - UInt32 code = p->code; - const Byte *bufLimit = buf + inSize; - CLzmaProb *probs = p->probs; - unsigned state = p->state; - ELzmaDummy res; - - { - CLzmaProb *prob; - UInt32 bound; - unsigned ttt; - unsigned posState = (p->processedPos) & ((1 << p->prop.pb) - 1); - - prob = probs + IsMatch + (state << kNumPosBitsMax) + posState; - IF_BIT_0_CHECK(prob) - { - UPDATE_0_CHECK - - /* if (bufLimit - buf >= 7) return DUMMY_LIT; */ - - prob = probs + Literal; - if (p->checkDicSize != 0 || p->processedPos != 0) - prob += (LZMA_LIT_SIZE * - ((((p->processedPos) & ((1 << (p->prop.lp)) - 1)) << p->prop.lc) + - (p->dic[(p->dicPos == 0 ? p->dicBufSize : p->dicPos) - 1] >> (8 - p->prop.lc)))); - - if (state < kNumLitStates) - { - unsigned symbol = 1; - do { GET_BIT_CHECK(prob + symbol, symbol) } while (symbol < 0x100); - } - else - { - unsigned matchByte = p->dic[p->dicPos - p->reps[0] + - ((p->dicPos < p->reps[0]) ? p->dicBufSize : 0)]; - unsigned offs = 0x100; - unsigned symbol = 1; - do - { - unsigned bit; - CLzmaProb *probLit; - matchByte <<= 1; - bit = (matchByte & offs); - probLit = prob + offs + bit + symbol; - GET_BIT2_CHECK(probLit, symbol, offs &= ~bit, offs &= bit) - } - while (symbol < 0x100); - } - res = DUMMY_LIT; - } - else - { - unsigned len; - UPDATE_1_CHECK; - - prob = probs + IsRep + state; - IF_BIT_0_CHECK(prob) - { - UPDATE_0_CHECK; - state = 0; - prob = probs + LenCoder; - res = DUMMY_MATCH; - } - else - { - UPDATE_1_CHECK; - res = DUMMY_REP; - prob = probs + IsRepG0 + state; - IF_BIT_0_CHECK(prob) - { - UPDATE_0_CHECK; - prob = probs + IsRep0Long + (state << kNumPosBitsMax) + posState; - IF_BIT_0_CHECK(prob) - { - UPDATE_0_CHECK; - NORMALIZE_CHECK; - return DUMMY_REP; - } - else - { - UPDATE_1_CHECK; - } - } - else - { - UPDATE_1_CHECK; - prob = probs + IsRepG1 + state; - IF_BIT_0_CHECK(prob) - { - UPDATE_0_CHECK; - } - else - { - UPDATE_1_CHECK; - prob = probs + IsRepG2 + state; - IF_BIT_0_CHECK(prob) - { - UPDATE_0_CHECK; - } - else - { - UPDATE_1_CHECK; - } - } - } - state = kNumStates; - prob = probs + RepLenCoder; - } - { - unsigned limit, offset; - CLzmaProb *probLen = prob + LenChoice; - IF_BIT_0_CHECK(probLen) - { - UPDATE_0_CHECK; - probLen = prob + LenLow + (posState << kLenNumLowBits); - offset = 0; - limit = 1 << kLenNumLowBits; - } - else - { - UPDATE_1_CHECK; - probLen = prob + LenChoice2; - IF_BIT_0_CHECK(probLen) - { - UPDATE_0_CHECK; - probLen = prob + LenMid + (posState << kLenNumMidBits); - offset = kLenNumLowSymbols; - limit = 1 << kLenNumMidBits; - } - else - { - UPDATE_1_CHECK; - probLen = prob + LenHigh; - offset = kLenNumLowSymbols + kLenNumMidSymbols; - limit = 1 << kLenNumHighBits; - } - } - TREE_DECODE_CHECK(probLen, limit, len); - len += offset; - } - - if (state < 4) - { - unsigned posSlot; - prob = probs + PosSlot + - ((len < kNumLenToPosStates ? len : kNumLenToPosStates - 1) << - kNumPosSlotBits); - TREE_DECODE_CHECK(prob, 1 << kNumPosSlotBits, posSlot); - if (posSlot >= kStartPosModelIndex) - { - int numDirectBits = ((posSlot >> 1) - 1); - - /* if (bufLimit - buf >= 8) return DUMMY_MATCH; */ - - if (posSlot < kEndPosModelIndex) - { - prob = probs + SpecPos + ((2 | (posSlot & 1)) << numDirectBits) - posSlot - 1; - } - else - { - numDirectBits -= kNumAlignBits; - do - { - NORMALIZE_CHECK - range >>= 1; - code -= range & (((code - range) >> 31) - 1); - /* if (code >= range) code -= range; */ - } - while (--numDirectBits != 0); - prob = probs + Align; - numDirectBits = kNumAlignBits; - } - { - unsigned i = 1; - do - { - GET_BIT_CHECK(prob + i, i); - } - while (--numDirectBits != 0); - } - } - } - } - } - NORMALIZE_CHECK; - return res; -} - - -static void LzmaDec_InitRc(CLzmaDec *p, const Byte *data) -{ - p->code = ((UInt32)data[1] << 24) | ((UInt32)data[2] << 16) | ((UInt32)data[3] << 8) | ((UInt32)data[4]); - p->range = 0xFFFFFFFF; - p->needFlush = 0; -} - -void LzmaDec_InitDicAndState(CLzmaDec *p, Bool initDic, Bool initState) -{ - p->needFlush = 1; - p->remainLen = 0; - p->tempBufSize = 0; - - if (initDic) - { - p->processedPos = 0; - p->checkDicSize = 0; - p->needInitState = 1; - } - if (initState) - p->needInitState = 1; -} - -void LzmaDec_Init(CLzmaDec *p) -{ - p->dicPos = 0; - LzmaDec_InitDicAndState(p, True, True); -} - -static void LzmaDec_InitStateReal(CLzmaDec *p) -{ - UInt32 numProbs = Literal + ((UInt32)LZMA_LIT_SIZE << (p->prop.lc + p->prop.lp)); - UInt32 i; - CLzmaProb *probs = p->probs; - for (i = 0; i < numProbs; i++) - probs[i] = kBitModelTotal >> 1; - p->reps[0] = p->reps[1] = p->reps[2] = p->reps[3] = 1; - p->state = 0; - p->needInitState = 0; -} - -SRes LzmaDec_DecodeToDic(CLzmaDec *p, SizeT dicLimit, const Byte *src, SizeT *srcLen, - ELzmaFinishMode finishMode, ELzmaStatus *status) -{ - SizeT inSize = *srcLen; - (*srcLen) = 0; - LzmaDec_WriteRem(p, dicLimit); - - *status = LZMA_STATUS_NOT_SPECIFIED; - - while (p->remainLen != kMatchSpecLenStart) - { - int checkEndMarkNow; - - if (p->needFlush != 0) - { - for (; inSize > 0 && p->tempBufSize < RC_INIT_SIZE; (*srcLen)++, inSize--) - p->tempBuf[p->tempBufSize++] = *src++; - if (p->tempBufSize < RC_INIT_SIZE) - { - *status = LZMA_STATUS_NEEDS_MORE_INPUT; - return SZ_OK; - } - if (p->tempBuf[0] != 0) - return SZ_ERROR_DATA; - - LzmaDec_InitRc(p, p->tempBuf); - p->tempBufSize = 0; - } - - checkEndMarkNow = 0; - if (p->dicPos >= dicLimit) - { - if (p->remainLen == 0 && p->code == 0) - { - *status = LZMA_STATUS_MAYBE_FINISHED_WITHOUT_MARK; - return SZ_OK; - } - if (finishMode == LZMA_FINISH_ANY) - { - *status = LZMA_STATUS_NOT_FINISHED; - return SZ_OK; - } - if (p->remainLen != 0) - { - *status = LZMA_STATUS_NOT_FINISHED; - return SZ_ERROR_DATA; - } - checkEndMarkNow = 1; - } - - if (p->needInitState) - LzmaDec_InitStateReal(p); - - if (p->tempBufSize == 0) - { - SizeT processed; - const Byte *bufLimit; - if (inSize < LZMA_REQUIRED_INPUT_MAX || checkEndMarkNow) - { - int dummyRes = LzmaDec_TryDummy(p, src, inSize); - if (dummyRes == DUMMY_ERROR) - { - memcpy(p->tempBuf, src, inSize); - p->tempBufSize = (unsigned)inSize; - (*srcLen) += inSize; - *status = LZMA_STATUS_NEEDS_MORE_INPUT; - return SZ_OK; - } - if (checkEndMarkNow && dummyRes != DUMMY_MATCH) - { - *status = LZMA_STATUS_NOT_FINISHED; - return SZ_ERROR_DATA; - } - bufLimit = src; - } - else - bufLimit = src + inSize - LZMA_REQUIRED_INPUT_MAX; - p->buf = src; - if (LzmaDec_DecodeReal2(p, dicLimit, bufLimit) != 0) - return SZ_ERROR_DATA; - processed = (SizeT)(p->buf - src); - (*srcLen) += processed; - src += processed; - inSize -= processed; - } - else - { - unsigned rem = p->tempBufSize, lookAhead = 0; - while (rem < LZMA_REQUIRED_INPUT_MAX && lookAhead < inSize) - p->tempBuf[rem++] = src[lookAhead++]; - p->tempBufSize = rem; - if (rem < LZMA_REQUIRED_INPUT_MAX || checkEndMarkNow) - { - int dummyRes = LzmaDec_TryDummy(p, p->tempBuf, rem); - if (dummyRes == DUMMY_ERROR) - { - (*srcLen) += lookAhead; - *status = LZMA_STATUS_NEEDS_MORE_INPUT; - return SZ_OK; - } - if (checkEndMarkNow && dummyRes != DUMMY_MATCH) - { - *status = LZMA_STATUS_NOT_FINISHED; - return SZ_ERROR_DATA; - } - } - p->buf = p->tempBuf; - if (LzmaDec_DecodeReal2(p, dicLimit, p->buf) != 0) - return SZ_ERROR_DATA; - lookAhead -= (rem - (unsigned)(p->buf - p->tempBuf)); - (*srcLen) += lookAhead; - src += lookAhead; - inSize -= lookAhead; - p->tempBufSize = 0; - } - } - if (p->code == 0) - *status = LZMA_STATUS_FINISHED_WITH_MARK; - return (p->code == 0) ? SZ_OK : SZ_ERROR_DATA; -} - -SRes LzmaDec_DecodeToBuf(CLzmaDec *p, Byte *dest, SizeT *destLen, const Byte *src, SizeT *srcLen, ELzmaFinishMode finishMode, ELzmaStatus *status) -{ - SizeT outSize = *destLen; - SizeT inSize = *srcLen; - *srcLen = *destLen = 0; - for (;;) - { - SizeT inSizeCur = inSize, outSizeCur, dicPos; - ELzmaFinishMode curFinishMode; - SRes res; - if (p->dicPos == p->dicBufSize) - p->dicPos = 0; - dicPos = p->dicPos; - if (outSize > p->dicBufSize - dicPos) - { - outSizeCur = p->dicBufSize; - curFinishMode = LZMA_FINISH_ANY; - } - else - { - outSizeCur = dicPos + outSize; - curFinishMode = finishMode; - } - - res = LzmaDec_DecodeToDic(p, outSizeCur, src, &inSizeCur, curFinishMode, status); - src += inSizeCur; - inSize -= inSizeCur; - *srcLen += inSizeCur; - outSizeCur = p->dicPos - dicPos; - memcpy(dest, p->dic + dicPos, outSizeCur); - dest += outSizeCur; - outSize -= outSizeCur; - *destLen += outSizeCur; - if (res != 0) - return res; - if (outSizeCur == 0 || outSize == 0) - return SZ_OK; - } -} - -void LzmaDec_FreeProbs(CLzmaDec *p, ISzAlloc *alloc) -{ - alloc->Free(alloc, p->probs); - p->probs = 0; -} - -static void LzmaDec_FreeDict(CLzmaDec *p, ISzAlloc *alloc) -{ - alloc->Free(alloc, p->dic); - p->dic = 0; -} - -void LzmaDec_Free(CLzmaDec *p, ISzAlloc *alloc) -{ - LzmaDec_FreeProbs(p, alloc); - LzmaDec_FreeDict(p, alloc); -} - -SRes LzmaProps_Decode(CLzmaProps *p, const Byte *data, unsigned size) -{ - UInt32 dicSize; - Byte d; - - if (size < LZMA_PROPS_SIZE) - return SZ_ERROR_UNSUPPORTED; - else - dicSize = data[1] | ((UInt32)data[2] << 8) | ((UInt32)data[3] << 16) | ((UInt32)data[4] << 24); - - if (dicSize < LZMA_DIC_MIN) - dicSize = LZMA_DIC_MIN; - p->dicSize = dicSize; - - d = data[0]; - if (d >= (9 * 5 * 5)) - return SZ_ERROR_UNSUPPORTED; - - p->lc = d % 9; - d /= 9; - p->pb = d / 5; - p->lp = d % 5; - - return SZ_OK; -} - -static SRes LzmaDec_AllocateProbs2(CLzmaDec *p, const CLzmaProps *propNew, ISzAlloc *alloc) -{ - UInt32 numProbs = LzmaProps_GetNumProbs(propNew); - if (p->probs == 0 || numProbs != p->numProbs) - { - LzmaDec_FreeProbs(p, alloc); - p->probs = (CLzmaProb *)alloc->Alloc(alloc, numProbs * sizeof(CLzmaProb)); - p->numProbs = numProbs; - if (p->probs == 0) - return SZ_ERROR_MEM; - } - return SZ_OK; -} - -SRes LzmaDec_AllocateProbs(CLzmaDec *p, const Byte *props, unsigned propsSize, ISzAlloc *alloc) -{ - CLzmaProps propNew; - RINOK(LzmaProps_Decode(&propNew, props, propsSize)); - RINOK(LzmaDec_AllocateProbs2(p, &propNew, alloc)); - p->prop = propNew; - return SZ_OK; -} - -SRes LzmaDec_Allocate(CLzmaDec *p, const Byte *props, unsigned propsSize, ISzAlloc *alloc) -{ - CLzmaProps propNew; - SizeT dicBufSize; - RINOK(LzmaProps_Decode(&propNew, props, propsSize)); - RINOK(LzmaDec_AllocateProbs2(p, &propNew, alloc)); - dicBufSize = propNew.dicSize; - if (p->dic == 0 || dicBufSize != p->dicBufSize) - { - LzmaDec_FreeDict(p, alloc); - p->dic = (Byte *)alloc->Alloc(alloc, dicBufSize); - if (p->dic == 0) - { - LzmaDec_FreeProbs(p, alloc); - return SZ_ERROR_MEM; - } - } - p->dicBufSize = dicBufSize; - p->prop = propNew; - return SZ_OK; -} - -SRes LzmaDecode(Byte *dest, SizeT *destLen, const Byte *src, SizeT *srcLen, - const Byte *propData, unsigned propSize, ELzmaFinishMode finishMode, - ELzmaStatus *status, ISzAlloc *alloc) -{ - CLzmaDec p; - SRes res; - SizeT inSize = *srcLen; - SizeT outSize = *destLen; - *srcLen = *destLen = 0; - if (inSize < RC_INIT_SIZE) - return SZ_ERROR_INPUT_EOF; - - LzmaDec_Construct(&p); - res = LzmaDec_AllocateProbs(&p, propData, propSize, alloc); - if (res != 0) - return res; - p.dic = dest; - p.dicBufSize = outSize; - - LzmaDec_Init(&p); - - *srcLen = inSize; - res = LzmaDec_DecodeToDic(&p, outSize, src, srcLen, finishMode, status); - - if (res == SZ_OK && *status == LZMA_STATUS_NEEDS_MORE_INPUT) - res = SZ_ERROR_INPUT_EOF; - - (*destLen) = p.dicPos; - LzmaDec_FreeProbs(&p, alloc); - return res; -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/lzma/C/LzmaDec.h b/app/jni/src/libultraship/extern/StormLib/src/lzma/C/LzmaDec.h deleted file mode 100644 index bf7f084..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/lzma/C/LzmaDec.h +++ /dev/null @@ -1,231 +0,0 @@ -/* LzmaDec.h -- LZMA Decoder -2009-02-07 : Igor Pavlov : Public domain */ - -#ifndef __LZMA_DEC_H -#define __LZMA_DEC_H - -#include "Types.h" - -#ifdef __cplusplus -extern "C" { -#endif - -/* #define _LZMA_PROB32 */ -/* _LZMA_PROB32 can increase the speed on some CPUs, - but memory usage for CLzmaDec::probs will be doubled in that case */ - -#ifdef _LZMA_PROB32 -#define CLzmaProb UInt32 -#else -#define CLzmaProb UInt16 -#endif - - -/* ---------- LZMA Properties ---------- */ - -#define LZMA_PROPS_SIZE 5 - -typedef struct _CLzmaProps -{ - unsigned lc, lp, pb; - UInt32 dicSize; -} CLzmaProps; - -/* LzmaProps_Decode - decodes properties -Returns: - SZ_OK - SZ_ERROR_UNSUPPORTED - Unsupported properties -*/ - -SRes LzmaProps_Decode(CLzmaProps *p, const Byte *data, unsigned size); - - -/* ---------- LZMA Decoder state ---------- */ - -/* LZMA_REQUIRED_INPUT_MAX = number of required input bytes for worst case. - Num bits = log2((2^11 / 31) ^ 22) + 26 < 134 + 26 = 160; */ - -#define LZMA_REQUIRED_INPUT_MAX 20 - -typedef struct -{ - CLzmaProps prop; - CLzmaProb *probs; - Byte *dic; - const Byte *buf; - UInt32 range, code; - SizeT dicPos; - SizeT dicBufSize; - UInt32 processedPos; - UInt32 checkDicSize; - unsigned state; - UInt32 reps[4]; - unsigned remainLen; - int needFlush; - int needInitState; - UInt32 numProbs; - unsigned tempBufSize; - Byte tempBuf[LZMA_REQUIRED_INPUT_MAX]; -} CLzmaDec; - -#define LzmaDec_Construct(p) { (p)->dic = 0; (p)->probs = 0; } - -void LzmaDec_Init(CLzmaDec *p); - -/* There are two types of LZMA streams: - 0) Stream with end mark. That end mark adds about 6 bytes to compressed size. - 1) Stream without end mark. You must know exact uncompressed size to decompress such stream. */ - -typedef enum -{ - LZMA_FINISH_ANY, /* finish at any point */ - LZMA_FINISH_END /* block must be finished at the end */ -} ELzmaFinishMode; - -/* ELzmaFinishMode has meaning only if the decoding reaches output limit !!! - - You must use LZMA_FINISH_END, when you know that current output buffer - covers last bytes of block. In other cases you must use LZMA_FINISH_ANY. - - If LZMA decoder sees end marker before reaching output limit, it returns SZ_OK, - and output value of destLen will be less than output buffer size limit. - You can check status result also. - - You can use multiple checks to test data integrity after full decompression: - 1) Check Result and "status" variable. - 2) Check that output(destLen) = uncompressedSize, if you know real uncompressedSize. - 3) Check that output(srcLen) = compressedSize, if you know real compressedSize. - You must use correct finish mode in that case. */ - -typedef enum -{ - LZMA_STATUS_NOT_SPECIFIED, /* use main error code instead */ - LZMA_STATUS_FINISHED_WITH_MARK, /* stream was finished with end mark. */ - LZMA_STATUS_NOT_FINISHED, /* stream was not finished */ - LZMA_STATUS_NEEDS_MORE_INPUT, /* you must provide more input bytes */ - LZMA_STATUS_MAYBE_FINISHED_WITHOUT_MARK /* there is probability that stream was finished without end mark */ -} ELzmaStatus; - -/* ELzmaStatus is used only as output value for function call */ - - -/* ---------- Interfaces ---------- */ - -/* There are 3 levels of interfaces: - 1) Dictionary Interface - 2) Buffer Interface - 3) One Call Interface - You can select any of these interfaces, but don't mix functions from different - groups for same object. */ - - -/* There are two variants to allocate state for Dictionary Interface: - 1) LzmaDec_Allocate / LzmaDec_Free - 2) LzmaDec_AllocateProbs / LzmaDec_FreeProbs - You can use variant 2, if you set dictionary buffer manually. - For Buffer Interface you must always use variant 1. - -LzmaDec_Allocate* can return: - SZ_OK - SZ_ERROR_MEM - Memory allocation error - SZ_ERROR_UNSUPPORTED - Unsupported properties -*/ - -SRes LzmaDec_AllocateProbs(CLzmaDec *p, const Byte *props, unsigned propsSize, ISzAlloc *alloc); -void LzmaDec_FreeProbs(CLzmaDec *p, ISzAlloc *alloc); - -SRes LzmaDec_Allocate(CLzmaDec *state, const Byte *prop, unsigned propsSize, ISzAlloc *alloc); -void LzmaDec_Free(CLzmaDec *state, ISzAlloc *alloc); - -/* ---------- Dictionary Interface ---------- */ - -/* You can use it, if you want to eliminate the overhead for data copying from - dictionary to some other external buffer. - You must work with CLzmaDec variables directly in this interface. - - STEPS: - LzmaDec_Constr() - LzmaDec_Allocate() - for (each new stream) - { - LzmaDec_Init() - while (it needs more decompression) - { - LzmaDec_DecodeToDic() - use data from CLzmaDec::dic and update CLzmaDec::dicPos - } - } - LzmaDec_Free() -*/ - -/* LzmaDec_DecodeToDic - - The decoding to internal dictionary buffer (CLzmaDec::dic). - You must manually update CLzmaDec::dicPos, if it reaches CLzmaDec::dicBufSize !!! - -finishMode: - It has meaning only if the decoding reaches output limit (dicLimit). - LZMA_FINISH_ANY - Decode just dicLimit bytes. - LZMA_FINISH_END - Stream must be finished after dicLimit. - -Returns: - SZ_OK - status: - LZMA_STATUS_FINISHED_WITH_MARK - LZMA_STATUS_NOT_FINISHED - LZMA_STATUS_NEEDS_MORE_INPUT - LZMA_STATUS_MAYBE_FINISHED_WITHOUT_MARK - SZ_ERROR_DATA - Data error -*/ - -SRes LzmaDec_DecodeToDic(CLzmaDec *p, SizeT dicLimit, - const Byte *src, SizeT *srcLen, ELzmaFinishMode finishMode, ELzmaStatus *status); - - -/* ---------- Buffer Interface ---------- */ - -/* It's zlib-like interface. - See LzmaDec_DecodeToDic description for information about STEPS and return results, - but you must use LzmaDec_DecodeToBuf instead of LzmaDec_DecodeToDic and you don't need - to work with CLzmaDec variables manually. - -finishMode: - It has meaning only if the decoding reaches output limit (*destLen). - LZMA_FINISH_ANY - Decode just destLen bytes. - LZMA_FINISH_END - Stream must be finished after (*destLen). -*/ - -SRes LzmaDec_DecodeToBuf(CLzmaDec *p, Byte *dest, SizeT *destLen, - const Byte *src, SizeT *srcLen, ELzmaFinishMode finishMode, ELzmaStatus *status); - - -/* ---------- One Call Interface ---------- */ - -/* LzmaDecode - -finishMode: - It has meaning only if the decoding reaches output limit (*destLen). - LZMA_FINISH_ANY - Decode just destLen bytes. - LZMA_FINISH_END - Stream must be finished after (*destLen). - -Returns: - SZ_OK - status: - LZMA_STATUS_FINISHED_WITH_MARK - LZMA_STATUS_NOT_FINISHED - LZMA_STATUS_MAYBE_FINISHED_WITHOUT_MARK - SZ_ERROR_DATA - Data error - SZ_ERROR_MEM - Memory allocation error - SZ_ERROR_UNSUPPORTED - Unsupported properties - SZ_ERROR_INPUT_EOF - It needs more bytes in input buffer (src). -*/ - -SRes LzmaDecode(Byte *dest, SizeT *destLen, const Byte *src, SizeT *srcLen, - const Byte *propData, unsigned propSize, ELzmaFinishMode finishMode, - ELzmaStatus *status, ISzAlloc *alloc); - -#ifdef __cplusplus -} -#endif - -#endif diff --git a/app/jni/src/libultraship/extern/StormLib/src/lzma/C/LzmaEnc.c b/app/jni/src/libultraship/extern/StormLib/src/lzma/C/LzmaEnc.c deleted file mode 100644 index 169d4f4..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/lzma/C/LzmaEnc.c +++ /dev/null @@ -1,2268 +0,0 @@ -/* LzmaEnc.c -- LZMA Encoder -2009-11-24 : Igor Pavlov : Public domain */ - -#include - -/* #define SHOW_STAT */ -/* #define SHOW_STAT2 */ - -#if defined(SHOW_STAT) || defined(SHOW_STAT2) -#include -#endif - -#include "LzmaEnc.h" - -#include "LzFind.h" -#ifndef _7ZIP_ST -#include "LzFindMt.h" -#endif - -#ifdef SHOW_STAT -static int ttt = 0; -#endif - -#define kBlockSizeMax ((1 << LZMA_NUM_BLOCK_SIZE_BITS) - 1) - -#define kBlockSize (9 << 10) -#define kUnpackBlockSize (1 << 18) -#define kMatchArraySize (1 << 21) -#define kMatchRecordMaxSize ((LZMA_MATCH_LEN_MAX * 2 + 3) * LZMA_MATCH_LEN_MAX) - -#define kNumMaxDirectBits (31) - -#define kNumTopBits 24 -#define kTopValue ((UInt32)1 << kNumTopBits) - -#define kNumBitModelTotalBits 11 -#define kBitModelTotal (1 << kNumBitModelTotalBits) -#define kNumMoveBits 5 -#define kProbInitValue (kBitModelTotal >> 1) - -#define kNumMoveReducingBits 4 -#define kNumBitPriceShiftBits 4 -#define kBitPrice (1 << kNumBitPriceShiftBits) - -void LzmaEncProps_Init(CLzmaEncProps *p) -{ - p->level = 5; - p->dictSize = p->mc = 0; - p->lc = p->lp = p->pb = p->algo = p->fb = p->btMode = p->numHashBytes = p->numThreads = -1; - p->writeEndMark = 0; -} - -void LzmaEncProps_Normalize(CLzmaEncProps *p) -{ - int level = p->level; - if (level < 0) level = 5; - p->level = level; - if (p->dictSize == 0) p->dictSize = (level <= 5 ? (1 << (level * 2 + 14)) : (level == 6 ? (1 << 25) : (1 << 26))); - if (p->lc < 0) p->lc = 3; - if (p->lp < 0) p->lp = 0; - if (p->pb < 0) p->pb = 2; - if (p->algo < 0) p->algo = (level < 5 ? 0 : 1); - if (p->fb < 0) p->fb = (level < 7 ? 32 : 64); - if (p->btMode < 0) p->btMode = (p->algo == 0 ? 0 : 1); - if (p->numHashBytes < 0) p->numHashBytes = 4; - if (p->mc == 0) p->mc = (16 + (p->fb >> 1)) >> (p->btMode ? 0 : 1); - if (p->numThreads < 0) - p->numThreads = - #ifndef _7ZIP_ST - ((p->btMode && p->algo) ? 2 : 1); - #else - 1; - #endif -} - -UInt32 LzmaEncProps_GetDictSize(const CLzmaEncProps *props2) -{ - CLzmaEncProps props = *props2; - LzmaEncProps_Normalize(&props); - return props.dictSize; -} - -/* #define LZMA_LOG_BSR */ -/* Define it for Intel's CPU */ - - -#ifdef LZMA_LOG_BSR - -#define kDicLogSizeMaxCompress 30 - -#define BSR2_RET(pos, res) { unsigned long i; _BitScanReverse(&i, (pos)); res = (i + i) + ((pos >> (i - 1)) & 1); } - -UInt32 GetPosSlot1(UInt32 pos) -{ - UInt32 res; - BSR2_RET(pos, res); - return res; -} -#define GetPosSlot2(pos, res) { BSR2_RET(pos, res); } -#define GetPosSlot(pos, res) { if (pos < 2) res = pos; else BSR2_RET(pos, res); } - -#else - -#define kNumLogBits (9 + (int)sizeof(size_t) / 2) -#define kDicLogSizeMaxCompress ((kNumLogBits - 1) * 2 + 7) - -void LzmaEnc_FastPosInit(Byte *g_FastPos) -{ - int c = 2, slotFast; - g_FastPos[0] = 0; - g_FastPos[1] = 1; - - for (slotFast = 2; slotFast < kNumLogBits * 2; slotFast++) - { - UInt32 k = (1 << ((slotFast >> 1) - 1)); - UInt32 j; - for (j = 0; j < k; j++, c++) - g_FastPos[c] = (Byte)slotFast; - } -} - -#define BSR2_RET(pos, res) { UInt32 i = 6 + ((kNumLogBits - 1) & \ - (0 - (((((UInt32)1 << (kNumLogBits + 6)) - 1) - pos) >> 31))); \ - res = p->g_FastPos[pos >> i] + (i * 2); } -/* -#define BSR2_RET(pos, res) { res = (pos < (1 << (kNumLogBits + 6))) ? \ - p->g_FastPos[pos >> 6] + 12 : \ - p->g_FastPos[pos >> (6 + kNumLogBits - 1)] + (6 + (kNumLogBits - 1)) * 2; } -*/ - -#define GetPosSlot1(pos) p->g_FastPos[pos] -#define GetPosSlot2(pos, res) { BSR2_RET(pos, res); } -#define GetPosSlot(pos, res) { if (pos < kNumFullDistances) res = p->g_FastPos[pos]; else BSR2_RET(pos, res); } - -#endif - - -#define LZMA_NUM_REPS 4 - -typedef unsigned CState; - -typedef struct -{ - UInt32 price; - - CState state; - int prev1IsChar; - int prev2; - - UInt32 posPrev2; - UInt32 backPrev2; - - UInt32 posPrev; - UInt32 backPrev; - UInt32 backs[LZMA_NUM_REPS]; -} COptimal; - -#define kNumOpts (1 << 12) - -#define kNumLenToPosStates 4 -#define kNumPosSlotBits 6 -#define kDicLogSizeMin 0 -#define kDicLogSizeMax 32 -#define kDistTableSizeMax (kDicLogSizeMax * 2) - - -#define kNumAlignBits 4 -#define kAlignTableSize (1 << kNumAlignBits) -#define kAlignMask (kAlignTableSize - 1) - -#define kStartPosModelIndex 4 -#define kEndPosModelIndex 14 -#define kNumPosModels (kEndPosModelIndex - kStartPosModelIndex) - -#define kNumFullDistances (1 << (kEndPosModelIndex >> 1)) - -#ifdef _LZMA_PROB32 -#define CLzmaProb UInt32 -#else -#define CLzmaProb UInt16 -#endif - -#define LZMA_PB_MAX 4 -#define LZMA_LC_MAX 8 -#define LZMA_LP_MAX 4 - -#define LZMA_NUM_PB_STATES_MAX (1 << LZMA_PB_MAX) - - -#define kLenNumLowBits 3 -#define kLenNumLowSymbols (1 << kLenNumLowBits) -#define kLenNumMidBits 3 -#define kLenNumMidSymbols (1 << kLenNumMidBits) -#define kLenNumHighBits 8 -#define kLenNumHighSymbols (1 << kLenNumHighBits) - -#define kLenNumSymbolsTotal (kLenNumLowSymbols + kLenNumMidSymbols + kLenNumHighSymbols) - -#define LZMA_MATCH_LEN_MIN 2 -#define LZMA_MATCH_LEN_MAX (LZMA_MATCH_LEN_MIN + kLenNumSymbolsTotal - 1) - -#define kNumStates 12 - -typedef struct -{ - CLzmaProb choice; - CLzmaProb choice2; - CLzmaProb low[LZMA_NUM_PB_STATES_MAX << kLenNumLowBits]; - CLzmaProb mid[LZMA_NUM_PB_STATES_MAX << kLenNumMidBits]; - CLzmaProb high[kLenNumHighSymbols]; -} CLenEnc; - -typedef struct -{ - CLenEnc p; - UInt32 prices[LZMA_NUM_PB_STATES_MAX][kLenNumSymbolsTotal]; - UInt32 tableSize; - UInt32 counters[LZMA_NUM_PB_STATES_MAX]; -} CLenPriceEnc; - -typedef struct -{ - UInt32 range; - Byte cache; - UInt64 low; - UInt64 cacheSize; - Byte *buf; - Byte *bufLim; - Byte *bufBase; - ISeqOutStream *outStream; - UInt64 processed; - SRes res; -} CRangeEnc; - -typedef struct -{ - CLzmaProb *litProbs; - - CLzmaProb isMatch[kNumStates][LZMA_NUM_PB_STATES_MAX]; - CLzmaProb isRep[kNumStates]; - CLzmaProb isRepG0[kNumStates]; - CLzmaProb isRepG1[kNumStates]; - CLzmaProb isRepG2[kNumStates]; - CLzmaProb isRep0Long[kNumStates][LZMA_NUM_PB_STATES_MAX]; - - CLzmaProb posSlotEncoder[kNumLenToPosStates][1 << kNumPosSlotBits]; - CLzmaProb posEncoders[kNumFullDistances - kEndPosModelIndex]; - CLzmaProb posAlignEncoder[1 << kNumAlignBits]; - - CLenPriceEnc lenEnc; - CLenPriceEnc repLenEnc; - - UInt32 reps[LZMA_NUM_REPS]; - UInt32 state; -} CSaveState; - -typedef struct -{ - IMatchFinder matchFinder; - void *matchFinderObj; - - #ifndef _7ZIP_ST - Bool mtMode; - CMatchFinderMt matchFinderMt; - #endif - - CMatchFinder matchFinderBase; - - #ifndef _7ZIP_ST - Byte pad[128]; - #endif - - UInt32 optimumEndIndex; - UInt32 optimumCurrentIndex; - - UInt32 longestMatchLength; - UInt32 numPairs; - UInt32 numAvail; - COptimal opt[kNumOpts]; - - #ifndef LZMA_LOG_BSR - Byte g_FastPos[1 << kNumLogBits]; - #endif - - UInt32 ProbPrices[kBitModelTotal >> kNumMoveReducingBits]; - UInt32 matches[LZMA_MATCH_LEN_MAX * 2 + 2 + 1]; - UInt32 numFastBytes; - UInt32 additionalOffset; - UInt32 reps[LZMA_NUM_REPS]; - UInt32 state; - - UInt32 posSlotPrices[kNumLenToPosStates][kDistTableSizeMax]; - UInt32 distancesPrices[kNumLenToPosStates][kNumFullDistances]; - UInt32 alignPrices[kAlignTableSize]; - UInt32 alignPriceCount; - - UInt32 distTableSize; - - unsigned lc, lp, pb; - unsigned lpMask, pbMask; - - CLzmaProb *litProbs; - - CLzmaProb isMatch[kNumStates][LZMA_NUM_PB_STATES_MAX]; - CLzmaProb isRep[kNumStates]; - CLzmaProb isRepG0[kNumStates]; - CLzmaProb isRepG1[kNumStates]; - CLzmaProb isRepG2[kNumStates]; - CLzmaProb isRep0Long[kNumStates][LZMA_NUM_PB_STATES_MAX]; - - CLzmaProb posSlotEncoder[kNumLenToPosStates][1 << kNumPosSlotBits]; - CLzmaProb posEncoders[kNumFullDistances - kEndPosModelIndex]; - CLzmaProb posAlignEncoder[1 << kNumAlignBits]; - - CLenPriceEnc lenEnc; - CLenPriceEnc repLenEnc; - - unsigned lclp; - - Bool fastMode; - - CRangeEnc rc; - - Bool writeEndMark; - UInt64 nowPos64; - UInt32 matchPriceCount; - Bool finished; - Bool multiThread; - - SRes result; - UInt32 dictSize; - UInt32 matchFinderCycles; - - int needInit; - - CSaveState saveState; -} CLzmaEnc; - -void LzmaEnc_SaveState(CLzmaEncHandle pp) -{ - CLzmaEnc *p = (CLzmaEnc *)pp; - CSaveState *dest = &p->saveState; - int i; - dest->lenEnc = p->lenEnc; - dest->repLenEnc = p->repLenEnc; - dest->state = p->state; - - for (i = 0; i < kNumStates; i++) - { - memcpy(dest->isMatch[i], p->isMatch[i], sizeof(p->isMatch[i])); - memcpy(dest->isRep0Long[i], p->isRep0Long[i], sizeof(p->isRep0Long[i])); - } - for (i = 0; i < kNumLenToPosStates; i++) - memcpy(dest->posSlotEncoder[i], p->posSlotEncoder[i], sizeof(p->posSlotEncoder[i])); - memcpy(dest->isRep, p->isRep, sizeof(p->isRep)); - memcpy(dest->isRepG0, p->isRepG0, sizeof(p->isRepG0)); - memcpy(dest->isRepG1, p->isRepG1, sizeof(p->isRepG1)); - memcpy(dest->isRepG2, p->isRepG2, sizeof(p->isRepG2)); - memcpy(dest->posEncoders, p->posEncoders, sizeof(p->posEncoders)); - memcpy(dest->posAlignEncoder, p->posAlignEncoder, sizeof(p->posAlignEncoder)); - memcpy(dest->reps, p->reps, sizeof(p->reps)); - memcpy(dest->litProbs, p->litProbs, (0x300 << p->lclp) * sizeof(CLzmaProb)); -} - -void LzmaEnc_RestoreState(CLzmaEncHandle pp) -{ - CLzmaEnc *dest = (CLzmaEnc *)pp; - const CSaveState *p = &dest->saveState; - int i; - dest->lenEnc = p->lenEnc; - dest->repLenEnc = p->repLenEnc; - dest->state = p->state; - - for (i = 0; i < kNumStates; i++) - { - memcpy(dest->isMatch[i], p->isMatch[i], sizeof(p->isMatch[i])); - memcpy(dest->isRep0Long[i], p->isRep0Long[i], sizeof(p->isRep0Long[i])); - } - for (i = 0; i < kNumLenToPosStates; i++) - memcpy(dest->posSlotEncoder[i], p->posSlotEncoder[i], sizeof(p->posSlotEncoder[i])); - memcpy(dest->isRep, p->isRep, sizeof(p->isRep)); - memcpy(dest->isRepG0, p->isRepG0, sizeof(p->isRepG0)); - memcpy(dest->isRepG1, p->isRepG1, sizeof(p->isRepG1)); - memcpy(dest->isRepG2, p->isRepG2, sizeof(p->isRepG2)); - memcpy(dest->posEncoders, p->posEncoders, sizeof(p->posEncoders)); - memcpy(dest->posAlignEncoder, p->posAlignEncoder, sizeof(p->posAlignEncoder)); - memcpy(dest->reps, p->reps, sizeof(p->reps)); - memcpy(dest->litProbs, p->litProbs, (0x300 << dest->lclp) * sizeof(CLzmaProb)); -} - -SRes LzmaEnc_SetProps(CLzmaEncHandle pp, const CLzmaEncProps *props2) -{ - CLzmaEnc *p = (CLzmaEnc *)pp; - CLzmaEncProps props = *props2; - LzmaEncProps_Normalize(&props); - - if (props.lc > LZMA_LC_MAX || props.lp > LZMA_LP_MAX || props.pb > LZMA_PB_MAX || - props.dictSize > (1 << kDicLogSizeMaxCompress) || props.dictSize > (1 << 30)) - return SZ_ERROR_PARAM; - p->dictSize = props.dictSize; - p->matchFinderCycles = props.mc; - { - unsigned fb = props.fb; - if (fb < 5) - fb = 5; - if (fb > LZMA_MATCH_LEN_MAX) - fb = LZMA_MATCH_LEN_MAX; - p->numFastBytes = fb; - } - p->lc = props.lc; - p->lp = props.lp; - p->pb = props.pb; - p->fastMode = (props.algo == 0); - p->matchFinderBase.btMode = props.btMode; - { - UInt32 numHashBytes = 4; - if (props.btMode) - { - if (props.numHashBytes < 2) - numHashBytes = 2; - else if (props.numHashBytes < 4) - numHashBytes = props.numHashBytes; - } - p->matchFinderBase.numHashBytes = numHashBytes; - } - - p->matchFinderBase.cutValue = props.mc; - - p->writeEndMark = props.writeEndMark; - - #ifndef _7ZIP_ST - /* - if (newMultiThread != _multiThread) - { - ReleaseMatchFinder(); - _multiThread = newMultiThread; - } - */ - p->multiThread = (props.numThreads > 1); - #endif - - return SZ_OK; -} - -static const int kLiteralNextStates[kNumStates] = {0, 0, 0, 0, 1, 2, 3, 4, 5, 6, 4, 5}; -static const int kMatchNextStates[kNumStates] = {7, 7, 7, 7, 7, 7, 7, 10, 10, 10, 10, 10}; -static const int kRepNextStates[kNumStates] = {8, 8, 8, 8, 8, 8, 8, 11, 11, 11, 11, 11}; -static const int kShortRepNextStates[kNumStates]= {9, 9, 9, 9, 9, 9, 9, 11, 11, 11, 11, 11}; - -#define IsCharState(s) ((s) < 7) - -#define GetLenToPosState(len) (((len) < kNumLenToPosStates + 1) ? (len) - 2 : kNumLenToPosStates - 1) - -#define kInfinityPrice (1 << 30) - -static void RangeEnc_Construct(CRangeEnc *p) -{ - p->outStream = 0; - p->bufBase = 0; -} - -#define RangeEnc_GetProcessed(p) ((p)->processed + ((p)->buf - (p)->bufBase) + (p)->cacheSize) - -#define RC_BUF_SIZE (1 << 16) -static int RangeEnc_Alloc(CRangeEnc *p, ISzAlloc *alloc) -{ - if (p->bufBase == 0) - { - p->bufBase = (Byte *)alloc->Alloc(alloc, RC_BUF_SIZE); - if (p->bufBase == 0) - return 0; - p->bufLim = p->bufBase + RC_BUF_SIZE; - } - return 1; -} - -static void RangeEnc_Free(CRangeEnc *p, ISzAlloc *alloc) -{ - alloc->Free(alloc, p->bufBase); - p->bufBase = 0; -} - -static void RangeEnc_Init(CRangeEnc *p) -{ - /* Stream.Init(); */ - p->low = 0; - p->range = 0xFFFFFFFF; - p->cacheSize = 1; - p->cache = 0; - - p->buf = p->bufBase; - - p->processed = 0; - p->res = SZ_OK; -} - -static void RangeEnc_FlushStream(CRangeEnc *p) -{ - size_t num; - if (p->res != SZ_OK) - return; - num = p->buf - p->bufBase; - if (num != p->outStream->Write(p->outStream, p->bufBase, num)) - p->res = SZ_ERROR_WRITE; - p->processed += num; - p->buf = p->bufBase; -} - -static void MY_FAST_CALL RangeEnc_ShiftLow(CRangeEnc *p) -{ - if ((UInt32)p->low < (UInt32)0xFF000000 || (int)(p->low >> 32) != 0) - { - Byte temp = p->cache; - do - { - Byte *buf = p->buf; - *buf++ = (Byte)(temp + (Byte)(p->low >> 32)); - p->buf = buf; - if (buf == p->bufLim) - RangeEnc_FlushStream(p); - temp = 0xFF; - } - while (--p->cacheSize != 0); - p->cache = (Byte)((UInt32)p->low >> 24); - } - p->cacheSize++; - p->low = (UInt32)p->low << 8; -} - -static void RangeEnc_FlushData(CRangeEnc *p) -{ - int i; - for (i = 0; i < 5; i++) - RangeEnc_ShiftLow(p); -} - -static void RangeEnc_EncodeDirectBits(CRangeEnc *p, UInt32 value, int numBits) -{ - do - { - p->range >>= 1; - p->low += p->range & (0 - ((value >> --numBits) & 1)); - if (p->range < kTopValue) - { - p->range <<= 8; - RangeEnc_ShiftLow(p); - } - } - while (numBits != 0); -} - -static void RangeEnc_EncodeBit(CRangeEnc *p, CLzmaProb *prob, UInt32 symbol) -{ - UInt32 ttt = *prob; - UInt32 newBound = (p->range >> kNumBitModelTotalBits) * ttt; - if (symbol == 0) - { - p->range = newBound; - ttt += (kBitModelTotal - ttt) >> kNumMoveBits; - } - else - { - p->low += newBound; - p->range -= newBound; - ttt -= ttt >> kNumMoveBits; - } - *prob = (CLzmaProb)ttt; - if (p->range < kTopValue) - { - p->range <<= 8; - RangeEnc_ShiftLow(p); - } -} - -static void LitEnc_Encode(CRangeEnc *p, CLzmaProb *probs, UInt32 symbol) -{ - symbol |= 0x100; - do - { - RangeEnc_EncodeBit(p, probs + (symbol >> 8), (symbol >> 7) & 1); - symbol <<= 1; - } - while (symbol < 0x10000); -} - -static void LitEnc_EncodeMatched(CRangeEnc *p, CLzmaProb *probs, UInt32 symbol, UInt32 matchByte) -{ - UInt32 offs = 0x100; - symbol |= 0x100; - do - { - matchByte <<= 1; - RangeEnc_EncodeBit(p, probs + (offs + (matchByte & offs) + (symbol >> 8)), (symbol >> 7) & 1); - symbol <<= 1; - offs &= ~(matchByte ^ symbol); - } - while (symbol < 0x10000); -} - -void LzmaEnc_InitPriceTables(UInt32 *ProbPrices) -{ - UInt32 i; - for (i = (1 << kNumMoveReducingBits) / 2; i < kBitModelTotal; i += (1 << kNumMoveReducingBits)) - { - const int kCyclesBits = kNumBitPriceShiftBits; - UInt32 w = i; - UInt32 bitCount = 0; - int j; - for (j = 0; j < kCyclesBits; j++) - { - w = w * w; - bitCount <<= 1; - while (w >= ((UInt32)1 << 16)) - { - w >>= 1; - bitCount++; - } - } - ProbPrices[i >> kNumMoveReducingBits] = ((kNumBitModelTotalBits << kCyclesBits) - 15 - bitCount); - } -} - - -#define GET_PRICE(prob, symbol) \ - p->ProbPrices[((prob) ^ (((-(int)(symbol))) & (kBitModelTotal - 1))) >> kNumMoveReducingBits]; - -#define GET_PRICEa(prob, symbol) \ - ProbPrices[((prob) ^ ((-((int)(symbol))) & (kBitModelTotal - 1))) >> kNumMoveReducingBits]; - -#define GET_PRICE_0(prob) p->ProbPrices[(prob) >> kNumMoveReducingBits] -#define GET_PRICE_1(prob) p->ProbPrices[((prob) ^ (kBitModelTotal - 1)) >> kNumMoveReducingBits] - -#define GET_PRICE_0a(prob) ProbPrices[(prob) >> kNumMoveReducingBits] -#define GET_PRICE_1a(prob) ProbPrices[((prob) ^ (kBitModelTotal - 1)) >> kNumMoveReducingBits] - -static UInt32 LitEnc_GetPrice(const CLzmaProb *probs, UInt32 symbol, UInt32 *ProbPrices) -{ - UInt32 price = 0; - symbol |= 0x100; - do - { - price += GET_PRICEa(probs[symbol >> 8], (symbol >> 7) & 1); - symbol <<= 1; - } - while (symbol < 0x10000); - return price; -} - -static UInt32 LitEnc_GetPriceMatched(const CLzmaProb *probs, UInt32 symbol, UInt32 matchByte, UInt32 *ProbPrices) -{ - UInt32 price = 0; - UInt32 offs = 0x100; - symbol |= 0x100; - do - { - matchByte <<= 1; - price += GET_PRICEa(probs[offs + (matchByte & offs) + (symbol >> 8)], (symbol >> 7) & 1); - symbol <<= 1; - offs &= ~(matchByte ^ symbol); - } - while (symbol < 0x10000); - return price; -} - - -static void RcTree_Encode(CRangeEnc *rc, CLzmaProb *probs, int numBitLevels, UInt32 symbol) -{ - UInt32 m = 1; - int i; - for (i = numBitLevels; i != 0;) - { - UInt32 bit; - i--; - bit = (symbol >> i) & 1; - RangeEnc_EncodeBit(rc, probs + m, bit); - m = (m << 1) | bit; - } -} - -static void RcTree_ReverseEncode(CRangeEnc *rc, CLzmaProb *probs, int numBitLevels, UInt32 symbol) -{ - UInt32 m = 1; - int i; - for (i = 0; i < numBitLevels; i++) - { - UInt32 bit = symbol & 1; - RangeEnc_EncodeBit(rc, probs + m, bit); - m = (m << 1) | bit; - symbol >>= 1; - } -} - -static UInt32 RcTree_GetPrice(const CLzmaProb *probs, int numBitLevels, UInt32 symbol, UInt32 *ProbPrices) -{ - UInt32 price = 0; - symbol |= (1 << numBitLevels); - while (symbol != 1) - { - price += GET_PRICEa(probs[symbol >> 1], symbol & 1); - symbol >>= 1; - } - return price; -} - -static UInt32 RcTree_ReverseGetPrice(const CLzmaProb *probs, int numBitLevels, UInt32 symbol, UInt32 *ProbPrices) -{ - UInt32 price = 0; - UInt32 m = 1; - int i; - for (i = numBitLevels; i != 0; i--) - { - UInt32 bit = symbol & 1; - symbol >>= 1; - price += GET_PRICEa(probs[m], bit); - m = (m << 1) | bit; - } - return price; -} - - -static void LenEnc_Init(CLenEnc *p) -{ - unsigned i; - p->choice = p->choice2 = kProbInitValue; - for (i = 0; i < (LZMA_NUM_PB_STATES_MAX << kLenNumLowBits); i++) - p->low[i] = kProbInitValue; - for (i = 0; i < (LZMA_NUM_PB_STATES_MAX << kLenNumMidBits); i++) - p->mid[i] = kProbInitValue; - for (i = 0; i < kLenNumHighSymbols; i++) - p->high[i] = kProbInitValue; -} - -static void LenEnc_Encode(CLenEnc *p, CRangeEnc *rc, UInt32 symbol, UInt32 posState) -{ - if (symbol < kLenNumLowSymbols) - { - RangeEnc_EncodeBit(rc, &p->choice, 0); - RcTree_Encode(rc, p->low + (posState << kLenNumLowBits), kLenNumLowBits, symbol); - } - else - { - RangeEnc_EncodeBit(rc, &p->choice, 1); - if (symbol < kLenNumLowSymbols + kLenNumMidSymbols) - { - RangeEnc_EncodeBit(rc, &p->choice2, 0); - RcTree_Encode(rc, p->mid + (posState << kLenNumMidBits), kLenNumMidBits, symbol - kLenNumLowSymbols); - } - else - { - RangeEnc_EncodeBit(rc, &p->choice2, 1); - RcTree_Encode(rc, p->high, kLenNumHighBits, symbol - kLenNumLowSymbols - kLenNumMidSymbols); - } - } -} - -static void LenEnc_SetPrices(CLenEnc *p, UInt32 posState, UInt32 numSymbols, UInt32 *prices, UInt32 *ProbPrices) -{ - UInt32 a0 = GET_PRICE_0a(p->choice); - UInt32 a1 = GET_PRICE_1a(p->choice); - UInt32 b0 = a1 + GET_PRICE_0a(p->choice2); - UInt32 b1 = a1 + GET_PRICE_1a(p->choice2); - UInt32 i = 0; - for (i = 0; i < kLenNumLowSymbols; i++) - { - if (i >= numSymbols) - return; - prices[i] = a0 + RcTree_GetPrice(p->low + (posState << kLenNumLowBits), kLenNumLowBits, i, ProbPrices); - } - for (; i < kLenNumLowSymbols + kLenNumMidSymbols; i++) - { - if (i >= numSymbols) - return; - prices[i] = b0 + RcTree_GetPrice(p->mid + (posState << kLenNumMidBits), kLenNumMidBits, i - kLenNumLowSymbols, ProbPrices); - } - for (; i < numSymbols; i++) - prices[i] = b1 + RcTree_GetPrice(p->high, kLenNumHighBits, i - kLenNumLowSymbols - kLenNumMidSymbols, ProbPrices); -} - -static void MY_FAST_CALL LenPriceEnc_UpdateTable(CLenPriceEnc *p, UInt32 posState, UInt32 *ProbPrices) -{ - LenEnc_SetPrices(&p->p, posState, p->tableSize, p->prices[posState], ProbPrices); - p->counters[posState] = p->tableSize; -} - -static void LenPriceEnc_UpdateTables(CLenPriceEnc *p, UInt32 numPosStates, UInt32 *ProbPrices) -{ - UInt32 posState; - for (posState = 0; posState < numPosStates; posState++) - LenPriceEnc_UpdateTable(p, posState, ProbPrices); -} - -static void LenEnc_Encode2(CLenPriceEnc *p, CRangeEnc *rc, UInt32 symbol, UInt32 posState, Bool updatePrice, UInt32 *ProbPrices) -{ - LenEnc_Encode(&p->p, rc, symbol, posState); - if (updatePrice) - if (--p->counters[posState] == 0) - LenPriceEnc_UpdateTable(p, posState, ProbPrices); -} - - - - -static void MovePos(CLzmaEnc *p, UInt32 num) -{ - #ifdef SHOW_STAT - ttt += num; - printf("\n MovePos %d", num); - #endif - if (num != 0) - { - p->additionalOffset += num; - p->matchFinder.Skip(p->matchFinderObj, num); - } -} - -static UInt32 ReadMatchDistances(CLzmaEnc *p, UInt32 *numDistancePairsRes) -{ - UInt32 lenRes = 0, numPairs; - p->numAvail = p->matchFinder.GetNumAvailableBytes(p->matchFinderObj); - numPairs = p->matchFinder.GetMatches(p->matchFinderObj, p->matches); - #ifdef SHOW_STAT - printf("\n i = %d numPairs = %d ", ttt, numPairs / 2); - ttt++; - { - UInt32 i; - for (i = 0; i < numPairs; i += 2) - printf("%2d %6d | ", p->matches[i], p->matches[i + 1]); - } - #endif - if (numPairs > 0) - { - lenRes = p->matches[numPairs - 2]; - if (lenRes == p->numFastBytes) - { - const Byte *pby = p->matchFinder.GetPointerToCurrentPos(p->matchFinderObj) - 1; - UInt32 distance = p->matches[numPairs - 1] + 1; - UInt32 numAvail = p->numAvail; - if (numAvail > LZMA_MATCH_LEN_MAX) - numAvail = LZMA_MATCH_LEN_MAX; - { - const Byte *pby2 = pby - distance; - for (; lenRes < numAvail && pby[lenRes] == pby2[lenRes]; lenRes++); - } - } - } - p->additionalOffset++; - *numDistancePairsRes = numPairs; - return lenRes; -} - - -#define MakeAsChar(p) (p)->backPrev = (UInt32)(-1); (p)->prev1IsChar = False; -#define MakeAsShortRep(p) (p)->backPrev = 0; (p)->prev1IsChar = False; -#define IsShortRep(p) ((p)->backPrev == 0) - -static UInt32 GetRepLen1Price(CLzmaEnc *p, UInt32 state, UInt32 posState) -{ - return - GET_PRICE_0(p->isRepG0[state]) + - GET_PRICE_0(p->isRep0Long[state][posState]); -} - -static UInt32 GetPureRepPrice(CLzmaEnc *p, UInt32 repIndex, UInt32 state, UInt32 posState) -{ - UInt32 price; - if (repIndex == 0) - { - price = GET_PRICE_0(p->isRepG0[state]); - price += GET_PRICE_1(p->isRep0Long[state][posState]); - } - else - { - price = GET_PRICE_1(p->isRepG0[state]); - if (repIndex == 1) - price += GET_PRICE_0(p->isRepG1[state]); - else - { - price += GET_PRICE_1(p->isRepG1[state]); - price += GET_PRICE(p->isRepG2[state], repIndex - 2); - } - } - return price; -} - -static UInt32 GetRepPrice(CLzmaEnc *p, UInt32 repIndex, UInt32 len, UInt32 state, UInt32 posState) -{ - return p->repLenEnc.prices[posState][len - LZMA_MATCH_LEN_MIN] + - GetPureRepPrice(p, repIndex, state, posState); -} - -static UInt32 Backward(CLzmaEnc *p, UInt32 *backRes, UInt32 cur) -{ - UInt32 posMem = p->opt[cur].posPrev; - UInt32 backMem = p->opt[cur].backPrev; - p->optimumEndIndex = cur; - do - { - if (p->opt[cur].prev1IsChar) - { - MakeAsChar(&p->opt[posMem]) - p->opt[posMem].posPrev = posMem - 1; - if (p->opt[cur].prev2) - { - p->opt[posMem - 1].prev1IsChar = False; - p->opt[posMem - 1].posPrev = p->opt[cur].posPrev2; - p->opt[posMem - 1].backPrev = p->opt[cur].backPrev2; - } - } - { - UInt32 posPrev = posMem; - UInt32 backCur = backMem; - - backMem = p->opt[posPrev].backPrev; - posMem = p->opt[posPrev].posPrev; - - p->opt[posPrev].backPrev = backCur; - p->opt[posPrev].posPrev = cur; - cur = posPrev; - } - } - while (cur != 0); - *backRes = p->opt[0].backPrev; - p->optimumCurrentIndex = p->opt[0].posPrev; - return p->optimumCurrentIndex; -} - -#define LIT_PROBS(pos, prevByte) (p->litProbs + ((((pos) & p->lpMask) << p->lc) + ((prevByte) >> (8 - p->lc))) * 0x300) - -static UInt32 GetOptimum(CLzmaEnc *p, UInt32 position, UInt32 *backRes) -{ - UInt32 numAvail, mainLen, numPairs, repMaxIndex, i, posState, lenEnd, len, cur; - UInt32 matchPrice, repMatchPrice, normalMatchPrice; - UInt32 reps[LZMA_NUM_REPS], repLens[LZMA_NUM_REPS]; - UInt32 *matches; - const Byte *data; - Byte curByte, matchByte; - if (p->optimumEndIndex != p->optimumCurrentIndex) - { - const COptimal *opt = &p->opt[p->optimumCurrentIndex]; - UInt32 lenRes = opt->posPrev - p->optimumCurrentIndex; - *backRes = opt->backPrev; - p->optimumCurrentIndex = opt->posPrev; - return lenRes; - } - p->optimumCurrentIndex = p->optimumEndIndex = 0; - - if (p->additionalOffset == 0) - mainLen = ReadMatchDistances(p, &numPairs); - else - { - mainLen = p->longestMatchLength; - numPairs = p->numPairs; - } - - numAvail = p->numAvail; - if (numAvail < 2) - { - *backRes = (UInt32)(-1); - return 1; - } - if (numAvail > LZMA_MATCH_LEN_MAX) - numAvail = LZMA_MATCH_LEN_MAX; - - data = p->matchFinder.GetPointerToCurrentPos(p->matchFinderObj) - 1; - repMaxIndex = 0; - for (i = 0; i < LZMA_NUM_REPS; i++) - { - UInt32 lenTest; - const Byte *data2; - reps[i] = p->reps[i]; - data2 = data - (reps[i] + 1); - if (data[0] != data2[0] || data[1] != data2[1]) - { - repLens[i] = 0; - continue; - } - for (lenTest = 2; lenTest < numAvail && data[lenTest] == data2[lenTest]; lenTest++); - repLens[i] = lenTest; - if (lenTest > repLens[repMaxIndex]) - repMaxIndex = i; - } - if (repLens[repMaxIndex] >= p->numFastBytes) - { - UInt32 lenRes; - *backRes = repMaxIndex; - lenRes = repLens[repMaxIndex]; - MovePos(p, lenRes - 1); - return lenRes; - } - - matches = p->matches; - if (mainLen >= p->numFastBytes) - { - *backRes = matches[numPairs - 1] + LZMA_NUM_REPS; - MovePos(p, mainLen - 1); - return mainLen; - } - curByte = *data; - matchByte = *(data - (reps[0] + 1)); - - if (mainLen < 2 && curByte != matchByte && repLens[repMaxIndex] < 2) - { - *backRes = (UInt32)-1; - return 1; - } - - p->opt[0].state = (CState)p->state; - - posState = (position & p->pbMask); - - { - const CLzmaProb *probs = LIT_PROBS(position, *(data - 1)); - p->opt[1].price = GET_PRICE_0(p->isMatch[p->state][posState]) + - (!IsCharState(p->state) ? - LitEnc_GetPriceMatched(probs, curByte, matchByte, p->ProbPrices) : - LitEnc_GetPrice(probs, curByte, p->ProbPrices)); - } - - MakeAsChar(&p->opt[1]); - - matchPrice = GET_PRICE_1(p->isMatch[p->state][posState]); - repMatchPrice = matchPrice + GET_PRICE_1(p->isRep[p->state]); - - if (matchByte == curByte) - { - UInt32 shortRepPrice = repMatchPrice + GetRepLen1Price(p, p->state, posState); - if (shortRepPrice < p->opt[1].price) - { - p->opt[1].price = shortRepPrice; - MakeAsShortRep(&p->opt[1]); - } - } - lenEnd = ((mainLen >= repLens[repMaxIndex]) ? mainLen : repLens[repMaxIndex]); - - if (lenEnd < 2) - { - *backRes = p->opt[1].backPrev; - return 1; - } - - p->opt[1].posPrev = 0; - for (i = 0; i < LZMA_NUM_REPS; i++) - p->opt[0].backs[i] = reps[i]; - - len = lenEnd; - do - p->opt[len--].price = kInfinityPrice; - while (len >= 2); - - for (i = 0; i < LZMA_NUM_REPS; i++) - { - UInt32 repLen = repLens[i]; - UInt32 price; - if (repLen < 2) - continue; - price = repMatchPrice + GetPureRepPrice(p, i, p->state, posState); - do - { - UInt32 curAndLenPrice = price + p->repLenEnc.prices[posState][repLen - 2]; - COptimal *opt = &p->opt[repLen]; - if (curAndLenPrice < opt->price) - { - opt->price = curAndLenPrice; - opt->posPrev = 0; - opt->backPrev = i; - opt->prev1IsChar = False; - } - } - while (--repLen >= 2); - } - - normalMatchPrice = matchPrice + GET_PRICE_0(p->isRep[p->state]); - - len = ((repLens[0] >= 2) ? repLens[0] + 1 : 2); - if (len <= mainLen) - { - UInt32 offs = 0; - while (len > matches[offs]) - offs += 2; - for (; ; len++) - { - COptimal *opt; - UInt32 distance = matches[offs + 1]; - - UInt32 curAndLenPrice = normalMatchPrice + p->lenEnc.prices[posState][len - LZMA_MATCH_LEN_MIN]; - UInt32 lenToPosState = GetLenToPosState(len); - if (distance < kNumFullDistances) - curAndLenPrice += p->distancesPrices[lenToPosState][distance]; - else - { - UInt32 slot; - GetPosSlot2(distance, slot); - curAndLenPrice += p->alignPrices[distance & kAlignMask] + p->posSlotPrices[lenToPosState][slot]; - } - opt = &p->opt[len]; - if (curAndLenPrice < opt->price) - { - opt->price = curAndLenPrice; - opt->posPrev = 0; - opt->backPrev = distance + LZMA_NUM_REPS; - opt->prev1IsChar = False; - } - if (len == matches[offs]) - { - offs += 2; - if (offs == numPairs) - break; - } - } - } - - cur = 0; - - #ifdef SHOW_STAT2 - if (position >= 0) - { - unsigned i; - printf("\n pos = %4X", position); - for (i = cur; i <= lenEnd; i++) - printf("\nprice[%4X] = %d", position - cur + i, p->opt[i].price); - } - #endif - - for (;;) - { - UInt32 numAvailFull, newLen, numPairs, posPrev, state, posState, startLen; - UInt32 curPrice, curAnd1Price, matchPrice, repMatchPrice; - Bool nextIsChar; - Byte curByte, matchByte; - const Byte *data; - COptimal *curOpt; - COptimal *nextOpt; - - cur++; - if (cur == lenEnd) - return Backward(p, backRes, cur); - - newLen = ReadMatchDistances(p, &numPairs); - if (newLen >= p->numFastBytes) - { - p->numPairs = numPairs; - p->longestMatchLength = newLen; - return Backward(p, backRes, cur); - } - position++; - curOpt = &p->opt[cur]; - posPrev = curOpt->posPrev; - if (curOpt->prev1IsChar) - { - posPrev--; - if (curOpt->prev2) - { - state = p->opt[curOpt->posPrev2].state; - if (curOpt->backPrev2 < LZMA_NUM_REPS) - state = kRepNextStates[state]; - else - state = kMatchNextStates[state]; - } - else - state = p->opt[posPrev].state; - state = kLiteralNextStates[state]; - } - else - state = p->opt[posPrev].state; - if (posPrev == cur - 1) - { - if (IsShortRep(curOpt)) - state = kShortRepNextStates[state]; - else - state = kLiteralNextStates[state]; - } - else - { - UInt32 pos; - const COptimal *prevOpt; - if (curOpt->prev1IsChar && curOpt->prev2) - { - posPrev = curOpt->posPrev2; - pos = curOpt->backPrev2; - state = kRepNextStates[state]; - } - else - { - pos = curOpt->backPrev; - if (pos < LZMA_NUM_REPS) - state = kRepNextStates[state]; - else - state = kMatchNextStates[state]; - } - prevOpt = &p->opt[posPrev]; - if (pos < LZMA_NUM_REPS) - { - UInt32 i; - reps[0] = prevOpt->backs[pos]; - for (i = 1; i <= pos; i++) - reps[i] = prevOpt->backs[i - 1]; - for (; i < LZMA_NUM_REPS; i++) - reps[i] = prevOpt->backs[i]; - } - else - { - UInt32 i; - reps[0] = (pos - LZMA_NUM_REPS); - for (i = 1; i < LZMA_NUM_REPS; i++) - reps[i] = prevOpt->backs[i - 1]; - } - } - curOpt->state = (CState)state; - - curOpt->backs[0] = reps[0]; - curOpt->backs[1] = reps[1]; - curOpt->backs[2] = reps[2]; - curOpt->backs[3] = reps[3]; - - curPrice = curOpt->price; - nextIsChar = False; - data = p->matchFinder.GetPointerToCurrentPos(p->matchFinderObj) - 1; - curByte = *data; - matchByte = *(data - (reps[0] + 1)); - - posState = (position & p->pbMask); - - curAnd1Price = curPrice + GET_PRICE_0(p->isMatch[state][posState]); - { - const CLzmaProb *probs = LIT_PROBS(position, *(data - 1)); - curAnd1Price += - (!IsCharState(state) ? - LitEnc_GetPriceMatched(probs, curByte, matchByte, p->ProbPrices) : - LitEnc_GetPrice(probs, curByte, p->ProbPrices)); - } - - nextOpt = &p->opt[cur + 1]; - - if (curAnd1Price < nextOpt->price) - { - nextOpt->price = curAnd1Price; - nextOpt->posPrev = cur; - MakeAsChar(nextOpt); - nextIsChar = True; - } - - matchPrice = curPrice + GET_PRICE_1(p->isMatch[state][posState]); - repMatchPrice = matchPrice + GET_PRICE_1(p->isRep[state]); - - if (matchByte == curByte && !(nextOpt->posPrev < cur && nextOpt->backPrev == 0)) - { - UInt32 shortRepPrice = repMatchPrice + GetRepLen1Price(p, state, posState); - if (shortRepPrice <= nextOpt->price) - { - nextOpt->price = shortRepPrice; - nextOpt->posPrev = cur; - MakeAsShortRep(nextOpt); - nextIsChar = True; - } - } - numAvailFull = p->numAvail; - { - UInt32 temp = kNumOpts - 1 - cur; - if (temp < numAvailFull) - numAvailFull = temp; - } - - if (numAvailFull < 2) - continue; - numAvail = (numAvailFull <= p->numFastBytes ? numAvailFull : p->numFastBytes); - - if (!nextIsChar && matchByte != curByte) /* speed optimization */ - { - /* try Literal + rep0 */ - UInt32 temp; - UInt32 lenTest2; - const Byte *data2 = data - (reps[0] + 1); - UInt32 limit = p->numFastBytes + 1; - if (limit > numAvailFull) - limit = numAvailFull; - - for (temp = 1; temp < limit && data[temp] == data2[temp]; temp++); - lenTest2 = temp - 1; - if (lenTest2 >= 2) - { - UInt32 state2 = kLiteralNextStates[state]; - UInt32 posStateNext = (position + 1) & p->pbMask; - UInt32 nextRepMatchPrice = curAnd1Price + - GET_PRICE_1(p->isMatch[state2][posStateNext]) + - GET_PRICE_1(p->isRep[state2]); - /* for (; lenTest2 >= 2; lenTest2--) */ - { - UInt32 curAndLenPrice; - COptimal *opt; - UInt32 offset = cur + 1 + lenTest2; - while (lenEnd < offset) - p->opt[++lenEnd].price = kInfinityPrice; - curAndLenPrice = nextRepMatchPrice + GetRepPrice(p, 0, lenTest2, state2, posStateNext); - opt = &p->opt[offset]; - if (curAndLenPrice < opt->price) - { - opt->price = curAndLenPrice; - opt->posPrev = cur + 1; - opt->backPrev = 0; - opt->prev1IsChar = True; - opt->prev2 = False; - } - } - } - } - - startLen = 2; /* speed optimization */ - { - UInt32 repIndex; - for (repIndex = 0; repIndex < LZMA_NUM_REPS; repIndex++) - { - UInt32 lenTest; - UInt32 lenTestTemp; - UInt32 price; - const Byte *data2 = data - (reps[repIndex] + 1); - if (data[0] != data2[0] || data[1] != data2[1]) - continue; - for (lenTest = 2; lenTest < numAvail && data[lenTest] == data2[lenTest]; lenTest++); - while (lenEnd < cur + lenTest) - p->opt[++lenEnd].price = kInfinityPrice; - lenTestTemp = lenTest; - price = repMatchPrice + GetPureRepPrice(p, repIndex, state, posState); - do - { - UInt32 curAndLenPrice = price + p->repLenEnc.prices[posState][lenTest - 2]; - COptimal *opt = &p->opt[cur + lenTest]; - if (curAndLenPrice < opt->price) - { - opt->price = curAndLenPrice; - opt->posPrev = cur; - opt->backPrev = repIndex; - opt->prev1IsChar = False; - } - } - while (--lenTest >= 2); - lenTest = lenTestTemp; - - if (repIndex == 0) - startLen = lenTest + 1; - - /* if (_maxMode) */ - { - UInt32 lenTest2 = lenTest + 1; - UInt32 limit = lenTest2 + p->numFastBytes; - UInt32 nextRepMatchPrice; - if (limit > numAvailFull) - limit = numAvailFull; - for (; lenTest2 < limit && data[lenTest2] == data2[lenTest2]; lenTest2++); - lenTest2 -= lenTest + 1; - if (lenTest2 >= 2) - { - UInt32 state2 = kRepNextStates[state]; - UInt32 posStateNext = (position + lenTest) & p->pbMask; - UInt32 curAndLenCharPrice = - price + p->repLenEnc.prices[posState][lenTest - 2] + - GET_PRICE_0(p->isMatch[state2][posStateNext]) + - LitEnc_GetPriceMatched(LIT_PROBS(position + lenTest, data[lenTest - 1]), - data[lenTest], data2[lenTest], p->ProbPrices); - state2 = kLiteralNextStates[state2]; - posStateNext = (position + lenTest + 1) & p->pbMask; - nextRepMatchPrice = curAndLenCharPrice + - GET_PRICE_1(p->isMatch[state2][posStateNext]) + - GET_PRICE_1(p->isRep[state2]); - - /* for (; lenTest2 >= 2; lenTest2--) */ - { - UInt32 curAndLenPrice; - COptimal *opt; - UInt32 offset = cur + lenTest + 1 + lenTest2; - while (lenEnd < offset) - p->opt[++lenEnd].price = kInfinityPrice; - curAndLenPrice = nextRepMatchPrice + GetRepPrice(p, 0, lenTest2, state2, posStateNext); - opt = &p->opt[offset]; - if (curAndLenPrice < opt->price) - { - opt->price = curAndLenPrice; - opt->posPrev = cur + lenTest + 1; - opt->backPrev = 0; - opt->prev1IsChar = True; - opt->prev2 = True; - opt->posPrev2 = cur; - opt->backPrev2 = repIndex; - } - } - } - } - } - } - /* for (UInt32 lenTest = 2; lenTest <= newLen; lenTest++) */ - if (newLen > numAvail) - { - newLen = numAvail; - for (numPairs = 0; newLen > matches[numPairs]; numPairs += 2); - matches[numPairs] = newLen; - numPairs += 2; - } - if (newLen >= startLen) - { - UInt32 normalMatchPrice = matchPrice + GET_PRICE_0(p->isRep[state]); - UInt32 offs, curBack, posSlot; - UInt32 lenTest; - while (lenEnd < cur + newLen) - p->opt[++lenEnd].price = kInfinityPrice; - - offs = 0; - while (startLen > matches[offs]) - offs += 2; - curBack = matches[offs + 1]; - GetPosSlot2(curBack, posSlot); - for (lenTest = /*2*/ startLen; ; lenTest++) - { - UInt32 curAndLenPrice = normalMatchPrice + p->lenEnc.prices[posState][lenTest - LZMA_MATCH_LEN_MIN]; - UInt32 lenToPosState = GetLenToPosState(lenTest); - COptimal *opt; - if (curBack < kNumFullDistances) - curAndLenPrice += p->distancesPrices[lenToPosState][curBack]; - else - curAndLenPrice += p->posSlotPrices[lenToPosState][posSlot] + p->alignPrices[curBack & kAlignMask]; - - opt = &p->opt[cur + lenTest]; - if (curAndLenPrice < opt->price) - { - opt->price = curAndLenPrice; - opt->posPrev = cur; - opt->backPrev = curBack + LZMA_NUM_REPS; - opt->prev1IsChar = False; - } - - if (/*_maxMode && */lenTest == matches[offs]) - { - /* Try Match + Literal + Rep0 */ - const Byte *data2 = data - (curBack + 1); - UInt32 lenTest2 = lenTest + 1; - UInt32 limit = lenTest2 + p->numFastBytes; - UInt32 nextRepMatchPrice; - if (limit > numAvailFull) - limit = numAvailFull; - for (; lenTest2 < limit && data[lenTest2] == data2[lenTest2]; lenTest2++); - lenTest2 -= lenTest + 1; - if (lenTest2 >= 2) - { - UInt32 state2 = kMatchNextStates[state]; - UInt32 posStateNext = (position + lenTest) & p->pbMask; - UInt32 curAndLenCharPrice = curAndLenPrice + - GET_PRICE_0(p->isMatch[state2][posStateNext]) + - LitEnc_GetPriceMatched(LIT_PROBS(position + lenTest, data[lenTest - 1]), - data[lenTest], data2[lenTest], p->ProbPrices); - state2 = kLiteralNextStates[state2]; - posStateNext = (posStateNext + 1) & p->pbMask; - nextRepMatchPrice = curAndLenCharPrice + - GET_PRICE_1(p->isMatch[state2][posStateNext]) + - GET_PRICE_1(p->isRep[state2]); - - /* for (; lenTest2 >= 2; lenTest2--) */ - { - UInt32 offset = cur + lenTest + 1 + lenTest2; - UInt32 curAndLenPrice; - COptimal *opt; - while (lenEnd < offset) - p->opt[++lenEnd].price = kInfinityPrice; - curAndLenPrice = nextRepMatchPrice + GetRepPrice(p, 0, lenTest2, state2, posStateNext); - opt = &p->opt[offset]; - if (curAndLenPrice < opt->price) - { - opt->price = curAndLenPrice; - opt->posPrev = cur + lenTest + 1; - opt->backPrev = 0; - opt->prev1IsChar = True; - opt->prev2 = True; - opt->posPrev2 = cur; - opt->backPrev2 = curBack + LZMA_NUM_REPS; - } - } - } - offs += 2; - if (offs == numPairs) - break; - curBack = matches[offs + 1]; - if (curBack >= kNumFullDistances) - GetPosSlot2(curBack, posSlot); - } - } - } - } -} - -#define ChangePair(smallDist, bigDist) (((bigDist) >> 7) > (smallDist)) - -static UInt32 GetOptimumFast(CLzmaEnc *p, UInt32 *backRes) -{ - UInt32 numAvail, mainLen, mainDist, numPairs, repIndex, repLen, i; - const Byte *data; - const UInt32 *matches; - - if (p->additionalOffset == 0) - mainLen = ReadMatchDistances(p, &numPairs); - else - { - mainLen = p->longestMatchLength; - numPairs = p->numPairs; - } - - numAvail = p->numAvail; - *backRes = (UInt32)-1; - if (numAvail < 2) - return 1; - if (numAvail > LZMA_MATCH_LEN_MAX) - numAvail = LZMA_MATCH_LEN_MAX; - data = p->matchFinder.GetPointerToCurrentPos(p->matchFinderObj) - 1; - - repLen = repIndex = 0; - for (i = 0; i < LZMA_NUM_REPS; i++) - { - UInt32 len; - const Byte *data2 = data - (p->reps[i] + 1); - if (data[0] != data2[0] || data[1] != data2[1]) - continue; - for (len = 2; len < numAvail && data[len] == data2[len]; len++); - if (len >= p->numFastBytes) - { - *backRes = i; - MovePos(p, len - 1); - return len; - } - if (len > repLen) - { - repIndex = i; - repLen = len; - } - } - - matches = p->matches; - if (mainLen >= p->numFastBytes) - { - *backRes = matches[numPairs - 1] + LZMA_NUM_REPS; - MovePos(p, mainLen - 1); - return mainLen; - } - - mainDist = 0; /* for GCC */ - if (mainLen >= 2) - { - mainDist = matches[numPairs - 1]; - while (numPairs > 2 && mainLen == matches[numPairs - 4] + 1) - { - if (!ChangePair(matches[numPairs - 3], mainDist)) - break; - numPairs -= 2; - mainLen = matches[numPairs - 2]; - mainDist = matches[numPairs - 1]; - } - if (mainLen == 2 && mainDist >= 0x80) - mainLen = 1; - } - - if (repLen >= 2 && ( - (repLen + 1 >= mainLen) || - (repLen + 2 >= mainLen && mainDist >= (1 << 9)) || - (repLen + 3 >= mainLen && mainDist >= (1 << 15)))) - { - *backRes = repIndex; - MovePos(p, repLen - 1); - return repLen; - } - - if (mainLen < 2 || numAvail <= 2) - return 1; - - p->longestMatchLength = ReadMatchDistances(p, &p->numPairs); - if (p->longestMatchLength >= 2) - { - UInt32 newDistance = matches[p->numPairs - 1]; - if ((p->longestMatchLength >= mainLen && newDistance < mainDist) || - (p->longestMatchLength == mainLen + 1 && !ChangePair(mainDist, newDistance)) || - (p->longestMatchLength > mainLen + 1) || - (p->longestMatchLength + 1 >= mainLen && mainLen >= 3 && ChangePair(newDistance, mainDist))) - return 1; - } - - data = p->matchFinder.GetPointerToCurrentPos(p->matchFinderObj) - 1; - for (i = 0; i < LZMA_NUM_REPS; i++) - { - UInt32 len, limit; - const Byte *data2 = data - (p->reps[i] + 1); - if (data[0] != data2[0] || data[1] != data2[1]) - continue; - limit = mainLen - 1; - for (len = 2; len < limit && data[len] == data2[len]; len++); - if (len >= limit) - return 1; - } - *backRes = mainDist + LZMA_NUM_REPS; - MovePos(p, mainLen - 2); - return mainLen; -} - -static void WriteEndMarker(CLzmaEnc *p, UInt32 posState) -{ - UInt32 len; - RangeEnc_EncodeBit(&p->rc, &p->isMatch[p->state][posState], 1); - RangeEnc_EncodeBit(&p->rc, &p->isRep[p->state], 0); - p->state = kMatchNextStates[p->state]; - len = LZMA_MATCH_LEN_MIN; - LenEnc_Encode2(&p->lenEnc, &p->rc, len - LZMA_MATCH_LEN_MIN, posState, !p->fastMode, p->ProbPrices); - RcTree_Encode(&p->rc, p->posSlotEncoder[GetLenToPosState(len)], kNumPosSlotBits, (1 << kNumPosSlotBits) - 1); - RangeEnc_EncodeDirectBits(&p->rc, (((UInt32)1 << 30) - 1) >> kNumAlignBits, 30 - kNumAlignBits); - RcTree_ReverseEncode(&p->rc, p->posAlignEncoder, kNumAlignBits, kAlignMask); -} - -static SRes CheckErrors(CLzmaEnc *p) -{ - if (p->result != SZ_OK) - return p->result; - if (p->rc.res != SZ_OK) - p->result = SZ_ERROR_WRITE; - if (p->matchFinderBase.result != SZ_OK) - p->result = SZ_ERROR_READ; - if (p->result != SZ_OK) - p->finished = True; - return p->result; -} - -static SRes Flush(CLzmaEnc *p, UInt32 nowPos) -{ - /* ReleaseMFStream(); */ - p->finished = True; - if (p->writeEndMark) - WriteEndMarker(p, nowPos & p->pbMask); - RangeEnc_FlushData(&p->rc); - RangeEnc_FlushStream(&p->rc); - return CheckErrors(p); -} - -static void FillAlignPrices(CLzmaEnc *p) -{ - UInt32 i; - for (i = 0; i < kAlignTableSize; i++) - p->alignPrices[i] = RcTree_ReverseGetPrice(p->posAlignEncoder, kNumAlignBits, i, p->ProbPrices); - p->alignPriceCount = 0; -} - -static void FillDistancesPrices(CLzmaEnc *p) -{ - UInt32 tempPrices[kNumFullDistances]; - UInt32 i, lenToPosState; - for (i = kStartPosModelIndex; i < kNumFullDistances; i++) - { - UInt32 posSlot = GetPosSlot1(i); - UInt32 footerBits = ((posSlot >> 1) - 1); - UInt32 base = ((2 | (posSlot & 1)) << footerBits); - tempPrices[i] = RcTree_ReverseGetPrice(p->posEncoders + base - posSlot - 1, footerBits, i - base, p->ProbPrices); - } - - for (lenToPosState = 0; lenToPosState < kNumLenToPosStates; lenToPosState++) - { - UInt32 posSlot; - const CLzmaProb *encoder = p->posSlotEncoder[lenToPosState]; - UInt32 *posSlotPrices = p->posSlotPrices[lenToPosState]; - for (posSlot = 0; posSlot < p->distTableSize; posSlot++) - posSlotPrices[posSlot] = RcTree_GetPrice(encoder, kNumPosSlotBits, posSlot, p->ProbPrices); - for (posSlot = kEndPosModelIndex; posSlot < p->distTableSize; posSlot++) - posSlotPrices[posSlot] += ((((posSlot >> 1) - 1) - kNumAlignBits) << kNumBitPriceShiftBits); - - { - UInt32 *distancesPrices = p->distancesPrices[lenToPosState]; - UInt32 i; - for (i = 0; i < kStartPosModelIndex; i++) - distancesPrices[i] = posSlotPrices[i]; - for (; i < kNumFullDistances; i++) - distancesPrices[i] = posSlotPrices[GetPosSlot1(i)] + tempPrices[i]; - } - } - p->matchPriceCount = 0; -} - -void LzmaEnc_Construct(CLzmaEnc *p) -{ - RangeEnc_Construct(&p->rc); - MatchFinder_Construct(&p->matchFinderBase); - #ifndef _7ZIP_ST - MatchFinderMt_Construct(&p->matchFinderMt); - p->matchFinderMt.MatchFinder = &p->matchFinderBase; - #endif - - { - CLzmaEncProps props; - LzmaEncProps_Init(&props); - LzmaEnc_SetProps(p, &props); - } - - #ifndef LZMA_LOG_BSR - LzmaEnc_FastPosInit(p->g_FastPos); - #endif - - LzmaEnc_InitPriceTables(p->ProbPrices); - p->litProbs = 0; - p->saveState.litProbs = 0; -} - -CLzmaEncHandle LzmaEnc_Create(ISzAlloc *alloc) -{ - void *p; - p = alloc->Alloc(alloc, sizeof(CLzmaEnc)); - if (p != 0) - LzmaEnc_Construct((CLzmaEnc *)p); - return p; -} - -void LzmaEnc_FreeLits(CLzmaEnc *p, ISzAlloc *alloc) -{ - alloc->Free(alloc, p->litProbs); - alloc->Free(alloc, p->saveState.litProbs); - p->litProbs = 0; - p->saveState.litProbs = 0; -} - -void LzmaEnc_Destruct(CLzmaEnc *p, ISzAlloc *alloc, ISzAlloc *allocBig) -{ - #ifndef _7ZIP_ST - MatchFinderMt_Destruct(&p->matchFinderMt, allocBig); - #endif - MatchFinder_Free(&p->matchFinderBase, allocBig); - LzmaEnc_FreeLits(p, alloc); - RangeEnc_Free(&p->rc, alloc); -} - -void LzmaEnc_Destroy(CLzmaEncHandle p, ISzAlloc *alloc, ISzAlloc *allocBig) -{ - LzmaEnc_Destruct((CLzmaEnc *)p, alloc, allocBig); - alloc->Free(alloc, p); -} - -static SRes LzmaEnc_CodeOneBlock(CLzmaEnc *p, Bool useLimits, UInt32 maxPackSize, UInt32 maxUnpackSize) -{ - UInt32 nowPos32, startPos32; - if (p->needInit) - { - p->matchFinder.Init(p->matchFinderObj); - p->needInit = 0; - } - - if (p->finished) - return p->result; - RINOK(CheckErrors(p)); - - nowPos32 = (UInt32)p->nowPos64; - startPos32 = nowPos32; - - if (p->nowPos64 == 0) - { - UInt32 numPairs; - Byte curByte; - if (p->matchFinder.GetNumAvailableBytes(p->matchFinderObj) == 0) - return Flush(p, nowPos32); - ReadMatchDistances(p, &numPairs); - RangeEnc_EncodeBit(&p->rc, &p->isMatch[p->state][0], 0); - p->state = kLiteralNextStates[p->state]; - curByte = p->matchFinder.GetIndexByte(p->matchFinderObj, 0 - p->additionalOffset); - LitEnc_Encode(&p->rc, p->litProbs, curByte); - p->additionalOffset--; - nowPos32++; - } - - if (p->matchFinder.GetNumAvailableBytes(p->matchFinderObj) != 0) - for (;;) - { - UInt32 pos, len, posState; - - if (p->fastMode) - len = GetOptimumFast(p, &pos); - else - len = GetOptimum(p, nowPos32, &pos); - - #ifdef SHOW_STAT2 - printf("\n pos = %4X, len = %d pos = %d", nowPos32, len, pos); - #endif - - posState = nowPos32 & p->pbMask; - if (len == 1 && pos == (UInt32)-1) - { - Byte curByte; - CLzmaProb *probs; - const Byte *data; - - RangeEnc_EncodeBit(&p->rc, &p->isMatch[p->state][posState], 0); - data = p->matchFinder.GetPointerToCurrentPos(p->matchFinderObj) - p->additionalOffset; - curByte = *data; - probs = LIT_PROBS(nowPos32, *(data - 1)); - if (IsCharState(p->state)) - LitEnc_Encode(&p->rc, probs, curByte); - else - LitEnc_EncodeMatched(&p->rc, probs, curByte, *(data - p->reps[0] - 1)); - p->state = kLiteralNextStates[p->state]; - } - else - { - RangeEnc_EncodeBit(&p->rc, &p->isMatch[p->state][posState], 1); - if (pos < LZMA_NUM_REPS) - { - RangeEnc_EncodeBit(&p->rc, &p->isRep[p->state], 1); - if (pos == 0) - { - RangeEnc_EncodeBit(&p->rc, &p->isRepG0[p->state], 0); - RangeEnc_EncodeBit(&p->rc, &p->isRep0Long[p->state][posState], ((len == 1) ? 0 : 1)); - } - else - { - UInt32 distance = p->reps[pos]; - RangeEnc_EncodeBit(&p->rc, &p->isRepG0[p->state], 1); - if (pos == 1) - RangeEnc_EncodeBit(&p->rc, &p->isRepG1[p->state], 0); - else - { - RangeEnc_EncodeBit(&p->rc, &p->isRepG1[p->state], 1); - RangeEnc_EncodeBit(&p->rc, &p->isRepG2[p->state], pos - 2); - if (pos == 3) - p->reps[3] = p->reps[2]; - p->reps[2] = p->reps[1]; - } - p->reps[1] = p->reps[0]; - p->reps[0] = distance; - } - if (len == 1) - p->state = kShortRepNextStates[p->state]; - else - { - LenEnc_Encode2(&p->repLenEnc, &p->rc, len - LZMA_MATCH_LEN_MIN, posState, !p->fastMode, p->ProbPrices); - p->state = kRepNextStates[p->state]; - } - } - else - { - UInt32 posSlot; - RangeEnc_EncodeBit(&p->rc, &p->isRep[p->state], 0); - p->state = kMatchNextStates[p->state]; - LenEnc_Encode2(&p->lenEnc, &p->rc, len - LZMA_MATCH_LEN_MIN, posState, !p->fastMode, p->ProbPrices); - pos -= LZMA_NUM_REPS; - GetPosSlot(pos, posSlot); - RcTree_Encode(&p->rc, p->posSlotEncoder[GetLenToPosState(len)], kNumPosSlotBits, posSlot); - - if (posSlot >= kStartPosModelIndex) - { - UInt32 footerBits = ((posSlot >> 1) - 1); - UInt32 base = ((2 | (posSlot & 1)) << footerBits); - UInt32 posReduced = pos - base; - - if (posSlot < kEndPosModelIndex) - RcTree_ReverseEncode(&p->rc, p->posEncoders + base - posSlot - 1, footerBits, posReduced); - else - { - RangeEnc_EncodeDirectBits(&p->rc, posReduced >> kNumAlignBits, footerBits - kNumAlignBits); - RcTree_ReverseEncode(&p->rc, p->posAlignEncoder, kNumAlignBits, posReduced & kAlignMask); - p->alignPriceCount++; - } - } - p->reps[3] = p->reps[2]; - p->reps[2] = p->reps[1]; - p->reps[1] = p->reps[0]; - p->reps[0] = pos; - p->matchPriceCount++; - } - } - p->additionalOffset -= len; - nowPos32 += len; - if (p->additionalOffset == 0) - { - UInt32 processed; - if (!p->fastMode) - { - if (p->matchPriceCount >= (1 << 7)) - FillDistancesPrices(p); - if (p->alignPriceCount >= kAlignTableSize) - FillAlignPrices(p); - } - if (p->matchFinder.GetNumAvailableBytes(p->matchFinderObj) == 0) - break; - processed = nowPos32 - startPos32; - if (useLimits) - { - if (processed + kNumOpts + 300 >= maxUnpackSize || - RangeEnc_GetProcessed(&p->rc) + kNumOpts * 2 >= maxPackSize) - break; - } - else if (processed >= (1 << 15)) - { - p->nowPos64 += nowPos32 - startPos32; - return CheckErrors(p); - } - } - } - p->nowPos64 += nowPos32 - startPos32; - return Flush(p, nowPos32); -} - -#define kBigHashDicLimit ((UInt32)1 << 24) - -static SRes LzmaEnc_Alloc(CLzmaEnc *p, UInt32 keepWindowSize, ISzAlloc *alloc, ISzAlloc *allocBig) -{ - UInt32 beforeSize = kNumOpts; - Bool btMode; - if (!RangeEnc_Alloc(&p->rc, alloc)) - return SZ_ERROR_MEM; - btMode = (p->matchFinderBase.btMode != 0); - #ifndef _7ZIP_ST - p->mtMode = (p->multiThread && !p->fastMode && btMode); - #endif - - { - unsigned lclp = p->lc + p->lp; - if (p->litProbs == 0 || p->saveState.litProbs == 0 || p->lclp != lclp) - { - LzmaEnc_FreeLits(p, alloc); - p->litProbs = (CLzmaProb *)alloc->Alloc(alloc, (0x300 << lclp) * sizeof(CLzmaProb)); - p->saveState.litProbs = (CLzmaProb *)alloc->Alloc(alloc, (0x300 << lclp) * sizeof(CLzmaProb)); - if (p->litProbs == 0 || p->saveState.litProbs == 0) - { - LzmaEnc_FreeLits(p, alloc); - return SZ_ERROR_MEM; - } - p->lclp = lclp; - } - } - - p->matchFinderBase.bigHash = (p->dictSize > kBigHashDicLimit); - - if (beforeSize + p->dictSize < keepWindowSize) - beforeSize = keepWindowSize - p->dictSize; - - #ifndef _7ZIP_ST - if (p->mtMode) - { - RINOK(MatchFinderMt_Create(&p->matchFinderMt, p->dictSize, beforeSize, p->numFastBytes, LZMA_MATCH_LEN_MAX, allocBig)); - p->matchFinderObj = &p->matchFinderMt; - MatchFinderMt_CreateVTable(&p->matchFinderMt, &p->matchFinder); - } - else - #endif - { - if (!MatchFinder_Create(&p->matchFinderBase, p->dictSize, beforeSize, p->numFastBytes, LZMA_MATCH_LEN_MAX, allocBig)) - return SZ_ERROR_MEM; - p->matchFinderObj = &p->matchFinderBase; - MatchFinder_CreateVTable(&p->matchFinderBase, &p->matchFinder); - } - return SZ_OK; -} - -void LzmaEnc_Init(CLzmaEnc *p) -{ - UInt32 i; - p->state = 0; - for (i = 0 ; i < LZMA_NUM_REPS; i++) - p->reps[i] = 0; - - RangeEnc_Init(&p->rc); - - - for (i = 0; i < kNumStates; i++) - { - UInt32 j; - for (j = 0; j < LZMA_NUM_PB_STATES_MAX; j++) - { - p->isMatch[i][j] = kProbInitValue; - p->isRep0Long[i][j] = kProbInitValue; - } - p->isRep[i] = kProbInitValue; - p->isRepG0[i] = kProbInitValue; - p->isRepG1[i] = kProbInitValue; - p->isRepG2[i] = kProbInitValue; - } - - { - UInt32 num = 0x300 << (p->lp + p->lc); - for (i = 0; i < num; i++) - p->litProbs[i] = kProbInitValue; - } - - { - for (i = 0; i < kNumLenToPosStates; i++) - { - CLzmaProb *probs = p->posSlotEncoder[i]; - UInt32 j; - for (j = 0; j < (1 << kNumPosSlotBits); j++) - probs[j] = kProbInitValue; - } - } - { - for (i = 0; i < kNumFullDistances - kEndPosModelIndex; i++) - p->posEncoders[i] = kProbInitValue; - } - - LenEnc_Init(&p->lenEnc.p); - LenEnc_Init(&p->repLenEnc.p); - - for (i = 0; i < (1 << kNumAlignBits); i++) - p->posAlignEncoder[i] = kProbInitValue; - - p->optimumEndIndex = 0; - p->optimumCurrentIndex = 0; - p->additionalOffset = 0; - - p->pbMask = (1 << p->pb) - 1; - p->lpMask = (1 << p->lp) - 1; -} - -void LzmaEnc_InitPrices(CLzmaEnc *p) -{ - if (!p->fastMode) - { - FillDistancesPrices(p); - FillAlignPrices(p); - } - - p->lenEnc.tableSize = - p->repLenEnc.tableSize = - p->numFastBytes + 1 - LZMA_MATCH_LEN_MIN; - LenPriceEnc_UpdateTables(&p->lenEnc, 1 << p->pb, p->ProbPrices); - LenPriceEnc_UpdateTables(&p->repLenEnc, 1 << p->pb, p->ProbPrices); -} - -static SRes LzmaEnc_AllocAndInit(CLzmaEnc *p, UInt32 keepWindowSize, ISzAlloc *alloc, ISzAlloc *allocBig) -{ - UInt32 i; - for (i = 0; i < (UInt32)kDicLogSizeMaxCompress; i++) - if (p->dictSize <= ((UInt32)1 << i)) - break; - p->distTableSize = i * 2; - - p->finished = False; - p->result = SZ_OK; - RINOK(LzmaEnc_Alloc(p, keepWindowSize, alloc, allocBig)); - LzmaEnc_Init(p); - LzmaEnc_InitPrices(p); - p->nowPos64 = 0; - return SZ_OK; -} - -static SRes LzmaEnc_Prepare(CLzmaEncHandle pp, ISeqOutStream *outStream, ISeqInStream *inStream, - ISzAlloc *alloc, ISzAlloc *allocBig) -{ - CLzmaEnc *p = (CLzmaEnc *)pp; - p->matchFinderBase.stream = inStream; - p->needInit = 1; - p->rc.outStream = outStream; - return LzmaEnc_AllocAndInit(p, 0, alloc, allocBig); -} - -SRes LzmaEnc_PrepareForLzma2(CLzmaEncHandle pp, - ISeqInStream *inStream, UInt32 keepWindowSize, - ISzAlloc *alloc, ISzAlloc *allocBig) -{ - CLzmaEnc *p = (CLzmaEnc *)pp; - p->matchFinderBase.stream = inStream; - p->needInit = 1; - return LzmaEnc_AllocAndInit(p, keepWindowSize, alloc, allocBig); -} - -static void LzmaEnc_SetInputBuf(CLzmaEnc *p, const Byte *src, SizeT srcLen) -{ - p->matchFinderBase.directInput = 1; - p->matchFinderBase.bufferBase = (Byte *)src; - p->matchFinderBase.directInputRem = srcLen; -} - -SRes LzmaEnc_MemPrepare(CLzmaEncHandle pp, const Byte *src, SizeT srcLen, - UInt32 keepWindowSize, ISzAlloc *alloc, ISzAlloc *allocBig) -{ - CLzmaEnc *p = (CLzmaEnc *)pp; - LzmaEnc_SetInputBuf(p, src, srcLen); - p->needInit = 1; - - return LzmaEnc_AllocAndInit(p, keepWindowSize, alloc, allocBig); -} - -void LzmaEnc_Finish(CLzmaEncHandle pp) -{ - #ifndef _7ZIP_ST - CLzmaEnc *p = (CLzmaEnc *)pp; - if (p->mtMode) - MatchFinderMt_ReleaseStream(&p->matchFinderMt); - #else - pp = pp; - #endif -} - -typedef struct -{ - ISeqOutStream funcTable; - Byte *data; - SizeT rem; - Bool overflow; -} CSeqOutStreamBuf; - -static size_t MyWrite(void *pp, const void *data, size_t size) -{ - CSeqOutStreamBuf *p = (CSeqOutStreamBuf *)pp; - if (p->rem < size) - { - size = p->rem; - p->overflow = True; - } - memcpy(p->data, data, size); - p->rem -= size; - p->data += size; - return size; -} - - -UInt32 LzmaEnc_GetNumAvailableBytes(CLzmaEncHandle pp) -{ - const CLzmaEnc *p = (CLzmaEnc *)pp; - return p->matchFinder.GetNumAvailableBytes(p->matchFinderObj); -} - -const Byte *LzmaEnc_GetCurBuf(CLzmaEncHandle pp) -{ - const CLzmaEnc *p = (CLzmaEnc *)pp; - return p->matchFinder.GetPointerToCurrentPos(p->matchFinderObj) - p->additionalOffset; -} - -SRes LzmaEnc_CodeOneMemBlock(CLzmaEncHandle pp, Bool reInit, - Byte *dest, size_t *destLen, UInt32 desiredPackSize, UInt32 *unpackSize) -{ - CLzmaEnc *p = (CLzmaEnc *)pp; - UInt64 nowPos64; - SRes res; - CSeqOutStreamBuf outStream; - - outStream.funcTable.Write = MyWrite; - outStream.data = dest; - outStream.rem = *destLen; - outStream.overflow = False; - - p->writeEndMark = False; - p->finished = False; - p->result = SZ_OK; - - if (reInit) - LzmaEnc_Init(p); - LzmaEnc_InitPrices(p); - nowPos64 = p->nowPos64; - RangeEnc_Init(&p->rc); - p->rc.outStream = &outStream.funcTable; - - res = LzmaEnc_CodeOneBlock(p, True, desiredPackSize, *unpackSize); - - *unpackSize = (UInt32)(p->nowPos64 - nowPos64); - *destLen -= outStream.rem; - if (outStream.overflow) - return SZ_ERROR_OUTPUT_EOF; - - return res; -} - -static SRes LzmaEnc_Encode2(CLzmaEnc *p, ICompressProgress *progress) -{ - SRes res = SZ_OK; - - #ifndef _7ZIP_ST - Byte allocaDummy[0x300]; - int i = 0; - for (i = 0; i < 16; i++) - allocaDummy[i] = (Byte)i; - #endif - - for (;;) - { - res = LzmaEnc_CodeOneBlock(p, False, 0, 0); - if (res != SZ_OK || p->finished != 0) - break; - if (progress != 0) - { - res = progress->Progress(progress, p->nowPos64, RangeEnc_GetProcessed(&p->rc)); - if (res != SZ_OK) - { - res = SZ_ERROR_PROGRESS; - break; - } - } - } - LzmaEnc_Finish(p); - return res; -} - -SRes LzmaEnc_Encode(CLzmaEncHandle pp, ISeqOutStream *outStream, ISeqInStream *inStream, ICompressProgress *progress, - ISzAlloc *alloc, ISzAlloc *allocBig) -{ - RINOK(LzmaEnc_Prepare(pp, outStream, inStream, alloc, allocBig)); - return LzmaEnc_Encode2((CLzmaEnc *)pp, progress); -} - -SRes LzmaEnc_WriteProperties(CLzmaEncHandle pp, Byte *props, SizeT *size) -{ - CLzmaEnc *p = (CLzmaEnc *)pp; - int i; - UInt32 dictSize = p->dictSize; - if (*size < LZMA_PROPS_SIZE) - return SZ_ERROR_PARAM; - *size = LZMA_PROPS_SIZE; - props[0] = (Byte)((p->pb * 5 + p->lp) * 9 + p->lc); - - for (i = 11; i <= 30; i++) - { - if (dictSize <= ((UInt32)2 << i)) - { - dictSize = (2 << i); - break; - } - if (dictSize <= ((UInt32)3 << i)) - { - dictSize = (3 << i); - break; - } - } - - for (i = 0; i < 4; i++) - props[1 + i] = (Byte)(dictSize >> (8 * i)); - return SZ_OK; -} - -SRes LzmaEnc_MemEncode(CLzmaEncHandle pp, Byte *dest, SizeT *destLen, const Byte *src, SizeT srcLen, - int writeEndMark, ICompressProgress *progress, ISzAlloc *alloc, ISzAlloc *allocBig) -{ - SRes res; - CLzmaEnc *p = (CLzmaEnc *)pp; - - CSeqOutStreamBuf outStream; - - LzmaEnc_SetInputBuf(p, src, srcLen); - - outStream.funcTable.Write = MyWrite; - outStream.data = dest; - outStream.rem = *destLen; - outStream.overflow = False; - - p->writeEndMark = writeEndMark; - - p->rc.outStream = &outStream.funcTable; - res = LzmaEnc_MemPrepare(pp, src, srcLen, 0, alloc, allocBig); - if (res == SZ_OK) - res = LzmaEnc_Encode2(p, progress); - - *destLen -= outStream.rem; - if (outStream.overflow) - return SZ_ERROR_OUTPUT_EOF; - return res; -} - -SRes LzmaEncode(Byte *dest, SizeT *destLen, const Byte *src, SizeT srcLen, - const CLzmaEncProps *props, Byte *propsEncoded, SizeT *propsSize, int writeEndMark, - ICompressProgress *progress, ISzAlloc *alloc, ISzAlloc *allocBig) -{ - CLzmaEnc *p = (CLzmaEnc *)LzmaEnc_Create(alloc); - SRes res; - if (p == 0) - return SZ_ERROR_MEM; - - res = LzmaEnc_SetProps(p, props); - if (res == SZ_OK) - { - res = LzmaEnc_WriteProperties(p, propsEncoded, propsSize); - if (res == SZ_OK) - res = LzmaEnc_MemEncode(p, dest, destLen, src, srcLen, - writeEndMark, progress, alloc, allocBig); - } - - LzmaEnc_Destroy(p, alloc, allocBig); - return res; -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/lzma/C/LzmaEnc.h b/app/jni/src/libultraship/extern/StormLib/src/lzma/C/LzmaEnc.h deleted file mode 100644 index 200d60e..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/lzma/C/LzmaEnc.h +++ /dev/null @@ -1,80 +0,0 @@ -/* LzmaEnc.h -- LZMA Encoder -2009-02-07 : Igor Pavlov : Public domain */ - -#ifndef __LZMA_ENC_H -#define __LZMA_ENC_H - -#include "Types.h" - -#ifdef __cplusplus -extern "C" { -#endif - -#define LZMA_PROPS_SIZE 5 - -typedef struct _CLzmaEncProps -{ - int level; /* 0 <= level <= 9 */ - UInt32 dictSize; /* (1 << 12) <= dictSize <= (1 << 27) for 32-bit version - (1 << 12) <= dictSize <= (1 << 30) for 64-bit version - default = (1 << 24) */ - int lc; /* 0 <= lc <= 8, default = 3 */ - int lp; /* 0 <= lp <= 4, default = 0 */ - int pb; /* 0 <= pb <= 4, default = 2 */ - int algo; /* 0 - fast, 1 - normal, default = 1 */ - int fb; /* 5 <= fb <= 273, default = 32 */ - int btMode; /* 0 - hashChain Mode, 1 - binTree mode - normal, default = 1 */ - int numHashBytes; /* 2, 3 or 4, default = 4 */ - UInt32 mc; /* 1 <= mc <= (1 << 30), default = 32 */ - unsigned writeEndMark; /* 0 - do not write EOPM, 1 - write EOPM, default = 0 */ - int numThreads; /* 1 or 2, default = 2 */ -} CLzmaEncProps; - -void LzmaEncProps_Init(CLzmaEncProps *p); -void LzmaEncProps_Normalize(CLzmaEncProps *p); -UInt32 LzmaEncProps_GetDictSize(const CLzmaEncProps *props2); - - -/* ---------- CLzmaEncHandle Interface ---------- */ - -/* LzmaEnc_* functions can return the following exit codes: -Returns: - SZ_OK - OK - SZ_ERROR_MEM - Memory allocation error - SZ_ERROR_PARAM - Incorrect paramater in props - SZ_ERROR_WRITE - Write callback error. - SZ_ERROR_PROGRESS - some break from progress callback - SZ_ERROR_THREAD - errors in multithreading functions (only for Mt version) -*/ - -typedef void * CLzmaEncHandle; - -CLzmaEncHandle LzmaEnc_Create(ISzAlloc *alloc); -void LzmaEnc_Destroy(CLzmaEncHandle p, ISzAlloc *alloc, ISzAlloc *allocBig); -SRes LzmaEnc_SetProps(CLzmaEncHandle p, const CLzmaEncProps *props); -SRes LzmaEnc_WriteProperties(CLzmaEncHandle p, Byte *properties, SizeT *size); -SRes LzmaEnc_Encode(CLzmaEncHandle p, ISeqOutStream *outStream, ISeqInStream *inStream, - ICompressProgress *progress, ISzAlloc *alloc, ISzAlloc *allocBig); -SRes LzmaEnc_MemEncode(CLzmaEncHandle p, Byte *dest, SizeT *destLen, const Byte *src, SizeT srcLen, - int writeEndMark, ICompressProgress *progress, ISzAlloc *alloc, ISzAlloc *allocBig); - -/* ---------- One Call Interface ---------- */ - -/* LzmaEncode -Return code: - SZ_OK - OK - SZ_ERROR_MEM - Memory allocation error - SZ_ERROR_PARAM - Incorrect paramater - SZ_ERROR_OUTPUT_EOF - output buffer overflow - SZ_ERROR_THREAD - errors in multithreading functions (only for Mt version) -*/ - -SRes LzmaEncode(Byte *dest, SizeT *destLen, const Byte *src, SizeT srcLen, - const CLzmaEncProps *props, Byte *propsEncoded, SizeT *propsSize, int writeEndMark, - ICompressProgress *progress, ISzAlloc *alloc, ISzAlloc *allocBig); - -#ifdef __cplusplus -} -#endif - -#endif diff --git a/app/jni/src/libultraship/extern/StormLib/src/lzma/C/Threads.c b/app/jni/src/libultraship/extern/StormLib/src/lzma/C/Threads.c deleted file mode 100644 index 7af1da2..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/lzma/C/Threads.c +++ /dev/null @@ -1,84 +0,0 @@ -/* Threads.c -- multithreading library -2009-09-20 : Igor Pavlov : Public domain */ - -#ifndef _WIN32_WCE -#include -#endif - -#include "Threads.h" - -static WRes GetError() -{ - DWORD res = GetLastError(); - return (res) ? (WRes)(res) : 1; -} - -WRes HandleToWRes(HANDLE h) { return (h != 0) ? 0 : GetError(); } -WRes BOOLToWRes(BOOL v) { return v ? 0 : GetError(); } - -WRes HandlePtr_Close(HANDLE *p) -{ - if (*p != NULL) - if (!CloseHandle(*p)) - return GetError(); - *p = NULL; - return 0; -} - -WRes Handle_WaitObject(HANDLE h) { return (WRes)WaitForSingleObject(h, INFINITE); } - -WRes Thread_Create(CThread *p, THREAD_FUNC_TYPE func, LPVOID param) -{ - unsigned threadId; /* Windows Me/98/95: threadId parameter may not be NULL in _beginthreadex/CreateThread functions */ - *p = - #ifdef UNDER_CE - CreateThread(0, 0, func, param, 0, &threadId); - #else - (HANDLE)_beginthreadex(NULL, 0, func, param, 0, &threadId); - #endif - /* maybe we must use errno here, but probably GetLastError() is also OK. */ - return HandleToWRes(*p); -} - -WRes Event_Create(CEvent *p, BOOL manualReset, int signaled) -{ - *p = CreateEvent(NULL, manualReset, (signaled ? TRUE : FALSE), NULL); - return HandleToWRes(*p); -} - -WRes Event_Set(CEvent *p) { return BOOLToWRes(SetEvent(*p)); } -WRes Event_Reset(CEvent *p) { return BOOLToWRes(ResetEvent(*p)); } - -WRes ManualResetEvent_Create(CManualResetEvent *p, int signaled) { return Event_Create(p, TRUE, signaled); } -WRes AutoResetEvent_Create(CAutoResetEvent *p, int signaled) { return Event_Create(p, FALSE, signaled); } -WRes ManualResetEvent_CreateNotSignaled(CManualResetEvent *p) { return ManualResetEvent_Create(p, 0); } -WRes AutoResetEvent_CreateNotSignaled(CAutoResetEvent *p) { return AutoResetEvent_Create(p, 0); } - - -WRes Semaphore_Create(CSemaphore *p, UInt32 initCount, UInt32 maxCount) -{ - *p = CreateSemaphore(NULL, (LONG)initCount, (LONG)maxCount, NULL); - return HandleToWRes(*p); -} - -static WRes Semaphore_Release(CSemaphore *p, LONG releaseCount, LONG *previousCount) - { return BOOLToWRes(ReleaseSemaphore(*p, releaseCount, previousCount)); } -WRes Semaphore_ReleaseN(CSemaphore *p, UInt32 num) - { return Semaphore_Release(p, (LONG)num, NULL); } -WRes Semaphore_Release1(CSemaphore *p) { return Semaphore_ReleaseN(p, 1); } - -WRes CriticalSection_Init(CCriticalSection *p) -{ - /* InitializeCriticalSection can raise only STATUS_NO_MEMORY exception */ - #ifdef _MSC_VER - __try - #endif - { - InitializeCriticalSection(p); - /* InitializeCriticalSectionAndSpinCount(p, 0); */ - } - #ifdef _MSC_VER - __except (EXCEPTION_EXECUTE_HANDLER) { return 1; } - #endif - return 0; -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/lzma/C/Threads.h b/app/jni/src/libultraship/extern/StormLib/src/lzma/C/Threads.h deleted file mode 100644 index d0ddd80..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/lzma/C/Threads.h +++ /dev/null @@ -1,59 +0,0 @@ -/* Threads.h -- multithreading library -2009-03-27 : Igor Pavlov : Public domain */ - -#ifndef __7Z_THREADS_H -#define __7Z_THREADS_H - -#include "Types.h" - -#ifdef __cplusplus -extern "C" { -#endif - -WRes HandlePtr_Close(HANDLE *h); -WRes Handle_WaitObject(HANDLE h); - -typedef HANDLE CThread; -#define Thread_Construct(p) *(p) = NULL -#define Thread_WasCreated(p) (*(p) != NULL) -#define Thread_Close(p) HandlePtr_Close(p) -#define Thread_Wait(p) Handle_WaitObject(*(p)) -typedef unsigned THREAD_FUNC_RET_TYPE; -#define THREAD_FUNC_CALL_TYPE MY_STD_CALL -#define THREAD_FUNC_DECL THREAD_FUNC_RET_TYPE THREAD_FUNC_CALL_TYPE -typedef THREAD_FUNC_RET_TYPE (THREAD_FUNC_CALL_TYPE * THREAD_FUNC_TYPE)(void *); -WRes Thread_Create(CThread *p, THREAD_FUNC_TYPE func, LPVOID param); - -typedef HANDLE CEvent; -typedef CEvent CAutoResetEvent; -typedef CEvent CManualResetEvent; -#define Event_Construct(p) *(p) = NULL -#define Event_IsCreated(p) (*(p) != NULL) -#define Event_Close(p) HandlePtr_Close(p) -#define Event_Wait(p) Handle_WaitObject(*(p)) -WRes Event_Set(CEvent *p); -WRes Event_Reset(CEvent *p); -WRes ManualResetEvent_Create(CManualResetEvent *p, int signaled); -WRes ManualResetEvent_CreateNotSignaled(CManualResetEvent *p); -WRes AutoResetEvent_Create(CAutoResetEvent *p, int signaled); -WRes AutoResetEvent_CreateNotSignaled(CAutoResetEvent *p); - -typedef HANDLE CSemaphore; -#define Semaphore_Construct(p) (*p) = NULL -#define Semaphore_Close(p) HandlePtr_Close(p) -#define Semaphore_Wait(p) Handle_WaitObject(*(p)) -WRes Semaphore_Create(CSemaphore *p, UInt32 initCount, UInt32 maxCount); -WRes Semaphore_ReleaseN(CSemaphore *p, UInt32 num); -WRes Semaphore_Release1(CSemaphore *p); - -typedef CRITICAL_SECTION CCriticalSection; -WRes CriticalSection_Init(CCriticalSection *p); -#define CriticalSection_Delete(p) DeleteCriticalSection(p) -#define CriticalSection_Enter(p) EnterCriticalSection(p) -#define CriticalSection_Leave(p) LeaveCriticalSection(p) - -#ifdef __cplusplus -} -#endif - -#endif diff --git a/app/jni/src/libultraship/extern/StormLib/src/lzma/C/Types.h b/app/jni/src/libultraship/extern/StormLib/src/lzma/C/Types.h deleted file mode 100644 index 0526cb4..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/lzma/C/Types.h +++ /dev/null @@ -1,236 +0,0 @@ -/* Types.h -- Basic types -2010-03-11 : Igor Pavlov : Public domain */ - -#ifndef __7Z_TYPES_H -#define __7Z_TYPES_H - -#include - -#ifdef _WIN32 -#include -#endif - -#ifndef EXTERN_C_BEGIN -#ifdef __cplusplus -#define EXTERN_C_BEGIN extern "C" { -#define EXTERN_C_END } -#else -#define EXTERN_C_BEGIN -#define EXTERN_C_END -#endif -#endif - -EXTERN_C_BEGIN - -#define SZ_OK 0 - -#define SZ_ERROR_DATA 1 -#define SZ_ERROR_MEM 2 -#define SZ_ERROR_CRC 3 -#define SZ_ERROR_UNSUPPORTED 4 -#define SZ_ERROR_PARAM 5 -#define SZ_ERROR_INPUT_EOF 6 -#define SZ_ERROR_OUTPUT_EOF 7 -#define SZ_ERROR_READ 8 -#define SZ_ERROR_WRITE 9 -#define SZ_ERROR_PROGRESS 10 -#define SZ_ERROR_FAIL 11 -#define SZ_ERROR_THREAD 12 - -#define SZ_ERROR_ARCHIVE 16 -#define SZ_ERROR_NO_ARCHIVE 17 - -typedef int SRes; - -#ifdef _WIN32 -typedef DWORD WRes; -#else -typedef int WRes; -#endif - -#ifndef RINOK -#define RINOK(x) { int __result__ = (x); if (__result__ != 0) return __result__; } -#endif - -typedef unsigned char Byte; -typedef short Int16; -typedef unsigned short UInt16; - -#ifdef _LZMA_UINT32_IS_ULONG -typedef long Int32; -typedef unsigned long UInt32; -#else -typedef int Int32; -typedef unsigned int UInt32; -#endif - -#ifdef _SZ_NO_INT_64 - -/* define _SZ_NO_INT_64, if your compiler doesn't support 64-bit integers. - NOTES: Some code will work incorrectly in that case! */ - -typedef long Int64; -typedef unsigned long UInt64; - -#else - -#if defined(_MSC_VER) || defined(__BORLANDC__) -typedef __int64 Int64; -typedef unsigned __int64 UInt64; -#else -typedef long long int Int64; -typedef unsigned long long int UInt64; -#endif - -#endif - -#ifdef _LZMA_NO_SYSTEM_SIZE_T -typedef UInt32 SizeT; -#else -typedef size_t SizeT; -#endif - -typedef int Bool; -#define True 1 -#define False 0 - - -#ifdef _WIN32 -#define MY_STD_CALL __stdcall -#else -#define MY_STD_CALL -#endif - -#ifdef _MSC_VER - -#if _MSC_VER >= 1300 -#define MY_NO_INLINE __declspec(noinline) -#else -#define MY_NO_INLINE -#endif - -#define MY_CDECL __cdecl -#define MY_FAST_CALL __fastcall - -#else - -#define MY_CDECL -#define MY_FAST_CALL - -#endif - - -/* The following interfaces use first parameter as pointer to structure */ - -typedef struct -{ - Byte (*Read)(void *p); /* reads one byte, returns 0 in case of EOF or error */ -} IByteIn; - -typedef struct -{ - void (*Write)(void *p, Byte b); -} IByteOut; - -typedef struct -{ - SRes (*Read)(void *p, void *buf, size_t *size); - /* if (input(*size) != 0 && output(*size) == 0) means end_of_stream. - (output(*size) < input(*size)) is allowed */ -} ISeqInStream; - -/* it can return SZ_ERROR_INPUT_EOF */ -SRes SeqInStream_Read(ISeqInStream *stream, void *buf, size_t size); -SRes SeqInStream_Read2(ISeqInStream *stream, void *buf, size_t size, SRes errorType); -SRes SeqInStream_ReadByte(ISeqInStream *stream, Byte *buf); - -typedef struct -{ - size_t (*Write)(void *p, const void *buf, size_t size); - /* Returns: result - the number of actually written bytes. - (result < size) means error */ -} ISeqOutStream; - -typedef enum -{ - SZ_SEEK_SET = 0, - SZ_SEEK_CUR = 1, - SZ_SEEK_END = 2 -} ESzSeek; - -typedef struct -{ - SRes (*Read)(void *p, void *buf, size_t *size); /* same as ISeqInStream::Read */ - SRes (*Seek)(void *p, Int64 *pos, ESzSeek origin); -} ISeekInStream; - -typedef struct -{ - SRes (*Look)(void *p, const void **buf, size_t *size); - /* if (input(*size) != 0 && output(*size) == 0) means end_of_stream. - (output(*size) > input(*size)) is not allowed - (output(*size) < input(*size)) is allowed */ - SRes (*Skip)(void *p, size_t offset); - /* offset must be <= output(*size) of Look */ - - SRes (*Read)(void *p, void *buf, size_t *size); - /* reads directly (without buffer). It's same as ISeqInStream::Read */ - SRes (*Seek)(void *p, Int64 *pos, ESzSeek origin); -} ILookInStream; - -SRes LookInStream_LookRead(ILookInStream *stream, void *buf, size_t *size); -SRes LookInStream_SeekTo(ILookInStream *stream, UInt64 offset); - -/* reads via ILookInStream::Read */ -SRes LookInStream_Read2(ILookInStream *stream, void *buf, size_t size, SRes errorType); -SRes LookInStream_Read(ILookInStream *stream, void *buf, size_t size); - -#define LookToRead_BUF_SIZE (1 << 14) - -typedef struct -{ - ILookInStream s; - ISeekInStream *realStream; - size_t pos; - size_t size; - Byte buf[LookToRead_BUF_SIZE]; -} CLookToRead; - -void LookToRead_CreateVTable(CLookToRead *p, int lookahead); -void LookToRead_Init(CLookToRead *p); - -typedef struct -{ - ISeqInStream s; - ILookInStream *realStream; -} CSecToLook; - -void SecToLook_CreateVTable(CSecToLook *p); - -typedef struct -{ - ISeqInStream s; - ILookInStream *realStream; -} CSecToRead; - -void SecToRead_CreateVTable(CSecToRead *p); - -typedef struct -{ - SRes (*Progress)(void *p, UInt64 inSize, UInt64 outSize); - /* Returns: result. (result != SZ_OK) means break. - Value (UInt64)(Int64)-1 for size means unknown value. */ -} ICompressProgress; - -typedef struct -{ - void *(*Alloc)(void *p, size_t size); - void (*Free)(void *p, void *address); /* address can be 0 */ -} ISzAlloc; - -#define IAlloc_Alloc(p, size) (p)->Alloc((p), size) -#define IAlloc_Free(p, a) (p)->Free((p), a) - -EXTERN_C_END - -#endif diff --git a/app/jni/src/libultraship/extern/StormLib/src/lzma/info.txt b/app/jni/src/libultraship/extern/StormLib/src/lzma/info.txt deleted file mode 100644 index 4cee86e..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/lzma/info.txt +++ /dev/null @@ -1 +0,0 @@ -Taken from LZMA SDK v 9.11 \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/src/pklib/crc32.c b/app/jni/src/libultraship/extern/StormLib/src/pklib/crc32.c deleted file mode 100644 index cd47b1d..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/pklib/crc32.c +++ /dev/null @@ -1,66 +0,0 @@ -/*****************************************************************************/ -/* crc32.c Copyright (c) Ladislav Zezula 2003 */ -/*---------------------------------------------------------------------------*/ -/* Pkware Data Compression Library Version 1.11 */ -/* Dissassembled method crc32 - cdecl version */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 09.04.03 1.00 Lad The first version of crc32.c */ -/* 02.05.03 1.00 Lad Stress test done */ -/*****************************************************************************/ - -#include "pklib.h" - -static unsigned long crc_table[] = -{ - 0x00000000, 0x77073096, 0xEE0E612C, 0x990951BA, 0x076DC419, 0x706AF48F, 0xE963A535, 0x9E6495A3, - 0x0EDB8832, 0x79DCB8A4, 0xE0D5E91E, 0x97D2D988, 0x09B64C2B, 0x7EB17CBD, 0xE7B82D07, 0x90BF1D91, - 0x1DB71064, 0x6AB020F2, 0xF3B97148, 0x84BE41DE, 0x1ADAD47D, 0x6DDDE4EB, 0xF4D4B551, 0x83D385C7, - 0x136C9856, 0x646BA8C0, 0xFD62F97A, 0x8A65C9EC, 0x14015C4F, 0x63066CD9, 0xFA0F3D63, 0x8D080DF5, - 0x3B6E20C8, 0x4C69105E, 0xD56041E4, 0xA2677172, 0x3C03E4D1, 0x4B04D447, 0xD20D85FD, 0xA50AB56B, - 0x35B5A8FA, 0x42B2986C, 0xDBBBC9D6, 0xACBCF940, 0x32D86CE3, 0x45DF5C75, 0xDCD60DCF, 0xABD13D59, - 0x26D930AC, 0x51DE003A, 0xC8D75180, 0xBFD06116, 0x21B4F4B5, 0x56B3C423, 0xCFBA9599, 0xB8BDA50F, - 0x2802B89E, 0x5F058808, 0xC60CD9B2, 0xB10BE924, 0x2F6F7C87, 0x58684C11, 0xC1611DAB, 0xB6662D3D, - 0x76DC4190, 0x01DB7106, 0x98D220BC, 0xEFD5102A, 0x71B18589, 0x06B6B51F, 0x9FBFE4A5, 0xE8B8D433, - 0x7807C9A2, 0x0F00F934, 0x9609A88E, 0xE10E9818, 0x7F6A0DBB, 0x086D3D2D, 0x91646C97, 0xE6635C01, - 0x6B6B51F4, 0x1C6C6162, 0x856530D8, 0xF262004E, 0x6C0695ED, 0x1B01A57B, 0x8208F4C1, 0xF50FC457, - 0x65B0D9C6, 0x12B7E950, 0x8BBEB8EA, 0xFCB9887C, 0x62DD1DDF, 0x15DA2D49, 0x8CD37CF3, 0xFBD44C65, - 0x4DB26158, 0x3AB551CE, 0xA3BC0074, 0xD4BB30E2, 0x4ADFA541, 0x3DD895D7, 0xA4D1C46D, 0xD3D6F4FB, - 0x4369E96A, 0x346ED9FC, 0xAD678846, 0xDA60B8D0, 0x44042D73, 0x33031DE5, 0xAA0A4C5F, 0xDD0D7CC9, - 0x5005713C, 0x270241AA, 0xBE0B1010, 0xC90C2086, 0x5768B525, 0x206F85B3, 0xB966D409, 0xCE61E49F, - 0x5EDEF90E, 0x29D9C998, 0xB0D09822, 0xC7D7A8B4, 0x59B33D17, 0x2EB40D81, 0xB7BD5C3B, 0xC0BA6CAD, - 0xEDB88320, 0x9ABFB3B6, 0x03B6E20C, 0x74B1D29A, 0xEAD54739, 0x9DD277AF, 0x04DB2615, 0x73DC1683, - 0xE3630B12, 0x94643B84, 0x0D6D6A3E, 0x7A6A5AA8, 0xE40ECF0B, 0x9309FF9D, 0x0A00AE27, 0x7D079EB1, - 0xF00F9344, 0x8708A3D2, 0x1E01F268, 0x6906C2FE, 0xF762575D, 0x806567CB, 0x196C3671, 0x6E6B06E7, - 0xFED41B76, 0x89D32BE0, 0x10DA7A5A, 0x67DD4ACC, 0xF9B9DF6F, 0x8EBEEFF9, 0x17B7BE43, 0x60B08ED5, - 0xD6D6A3E8, 0xA1D1937E, 0x38D8C2C4, 0x4FDFF252, 0xD1BB67F1, 0xA6BC5767, 0x3FB506DD, 0x48B2364B, - 0xD80D2BDA, 0xAF0A1B4C, 0x36034AF6, 0x41047A60, 0xDF60EFC3, 0xA867DF55, 0x316E8EEF, 0x4669BE79, - 0xCB61B38C, 0xBC66831A, 0x256FD2A0, 0x5268E236, 0xCC0C7795, 0xBB0B4703, 0x220216B9, 0x5505262F, - 0xC5BA3BBE, 0xB2BD0B28, 0x2BB45A92, 0x5CB36A04, 0xC2D7FFA7, 0xB5D0CF31, 0x2CD99E8B, 0x5BDEAE1D, - 0x9B64C2B0, 0xEC63F226, 0x756AA39C, 0x026D930A, 0x9C0906A9, 0xEB0E363F, 0x72076785, 0x05005713, - 0x95BF4A82, 0xE2B87A14, 0x7BB12BAE, 0x0CB61B38, 0x92D28E9B, 0xE5D5BE0D, 0x7CDCEFB7, 0x0BDBDF21, - 0x86D3D2D4, 0xF1D4E242, 0x68DDB3F8, 0x1FDA836E, 0x81BE16CD, 0xF6B9265B, 0x6FB077E1, 0x18B74777, - 0x88085AE6, 0xFF0F6A70, 0x66063BCA, 0x11010B5C, 0x8F659EFF, 0xF862AE69, 0x616BFFD3, 0x166CCF45, - 0xA00AE278, 0xD70DD2EE, 0x4E048354, 0x3903B3C2, 0xA7672661, 0xD06016F7, 0x4969474D, 0x3E6E77DB, - 0xAED16A4A, 0xD9D65ADC, 0x40DF0B66, 0x37D83BF0, 0xA9BCAE53, 0xDEBB9EC5, 0x47B2CF7F, 0x30B5FFE9, - 0xBDBDF21C, 0xCABAC28A, 0x53B39330, 0x24B4A3A6, 0xBAD03605, 0xCDD70693, 0x54DE5729, 0x23D967BF, - 0xB3667A2E, 0xC4614AB8, 0x5D681B02, 0x2A6F2B94, 0xB40BBE37, 0xC30C8EA1, 0x5A05DF1B, 0x2D02EF8D -}; - - -unsigned long PKEXPORT crc32_pklib(char * buffer, unsigned int * psize, unsigned long * old_crc) -{ - unsigned int size = *psize; - unsigned long ch; - unsigned long crc_value = *old_crc; - - while(size-- != 0) - { - ch = *buffer++ ^ (char)crc_value; - crc_value >>= 8; - - crc_value = crc_table[ch & 0x0FF] ^ crc_value; - } - return crc_value; -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/pklib/explode.c b/app/jni/src/libultraship/extern/StormLib/src/pklib/explode.c deleted file mode 100644 index 35210fb..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/pklib/explode.c +++ /dev/null @@ -1,521 +0,0 @@ -/*****************************************************************************/ -/* explode.c Copyright (c) Ladislav Zezula 2003 */ -/*---------------------------------------------------------------------------*/ -/* Implode function of PKWARE Data Compression library */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 11.03.03 1.00 Lad Splitted from Pkware.cpp */ -/* 08.04.03 1.01 Lad Renamed to explode.c to be compatible with pklib */ -/* 02.05.03 1.01 Lad Stress test done */ -/* 22.04.10 1.01 Lad Documented */ -/*****************************************************************************/ - -#include -#include - -#include "pklib.h" - -#define PKDCL_OK 0 -#define PKDCL_STREAM_END 1 // All data from the input stream is read -#define PKDCL_NEED_DICT 2 // Need more data (dictionary) -#define PKDCL_CONTINUE 10 // Internal flag, not returned to user -#define PKDCL_GET_INPUT 11 // Internal flag, not returned to user - -char CopyrightPkware[] = "PKWARE Data Compression Library for Win32\r\n" - "Copyright 1989-1995 PKWARE Inc. All Rights Reserved\r\n" - "Patent No. 5,051,745\r\n" - "PKWARE Data Compression Library Reg. U.S. Pat. and Tm. Off.\r\n" - "Version 1.11\r\n"; - -//----------------------------------------------------------------------------- -// Tables - -const unsigned char DistBits[0x40] = -{ - 0x02, 0x04, 0x04, 0x05, 0x05, 0x05, 0x05, 0x06, 0x06, 0x06, 0x06, 0x06, 0x06, 0x06, 0x06, 0x06, - 0x06, 0x06, 0x06, 0x06, 0x06, 0x06, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, - 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, - 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08 -}; - -const unsigned char DistCode[0x40] = -{ - 0x03, 0x0D, 0x05, 0x19, 0x09, 0x11, 0x01, 0x3E, 0x1E, 0x2E, 0x0E, 0x36, 0x16, 0x26, 0x06, 0x3A, - 0x1A, 0x2A, 0x0A, 0x32, 0x12, 0x22, 0x42, 0x02, 0x7C, 0x3C, 0x5C, 0x1C, 0x6C, 0x2C, 0x4C, 0x0C, - 0x74, 0x34, 0x54, 0x14, 0x64, 0x24, 0x44, 0x04, 0x78, 0x38, 0x58, 0x18, 0x68, 0x28, 0x48, 0x08, - 0xF0, 0x70, 0xB0, 0x30, 0xD0, 0x50, 0x90, 0x10, 0xE0, 0x60, 0xA0, 0x20, 0xC0, 0x40, 0x80, 0x00 -}; - -const unsigned char ExLenBits[0x10] = -{ - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08 -}; - -const unsigned short LenBase[0x10] = -{ - 0x0000, 0x0001, 0x0002, 0x0003, 0x0004, 0x0005, 0x0006, 0x0007, - 0x0008, 0x000A, 0x000E, 0x0016, 0x0026, 0x0046, 0x0086, 0x0106 -}; - -const unsigned char LenBits[0x10] = -{ - 0x03, 0x02, 0x03, 0x03, 0x04, 0x04, 0x04, 0x05, 0x05, 0x05, 0x05, 0x06, 0x06, 0x06, 0x07, 0x07 -}; - -const unsigned char LenCode[0x10] = -{ - 0x05, 0x03, 0x01, 0x06, 0x0A, 0x02, 0x0C, 0x14, 0x04, 0x18, 0x08, 0x30, 0x10, 0x20, 0x40, 0x00 -}; - -const unsigned char ChBitsAsc[0x100] = -{ - 0x0B, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x08, 0x07, 0x0C, 0x0C, 0x07, 0x0C, 0x0C, - 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0D, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, - 0x04, 0x0A, 0x08, 0x0C, 0x0A, 0x0C, 0x0A, 0x08, 0x07, 0x07, 0x08, 0x09, 0x07, 0x06, 0x07, 0x08, - 0x07, 0x06, 0x07, 0x07, 0x07, 0x07, 0x08, 0x07, 0x07, 0x08, 0x08, 0x0C, 0x0B, 0x07, 0x09, 0x0B, - 0x0C, 0x06, 0x07, 0x06, 0x06, 0x05, 0x07, 0x08, 0x08, 0x06, 0x0B, 0x09, 0x06, 0x07, 0x06, 0x06, - 0x07, 0x0B, 0x06, 0x06, 0x06, 0x07, 0x09, 0x08, 0x09, 0x09, 0x0B, 0x08, 0x0B, 0x09, 0x0C, 0x08, - 0x0C, 0x05, 0x06, 0x06, 0x06, 0x05, 0x06, 0x06, 0x06, 0x05, 0x0B, 0x07, 0x05, 0x06, 0x05, 0x05, - 0x06, 0x0A, 0x05, 0x05, 0x05, 0x05, 0x08, 0x07, 0x08, 0x08, 0x0A, 0x0B, 0x0B, 0x0C, 0x0C, 0x0C, - 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, - 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, - 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, - 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, - 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, - 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, 0x0C, - 0x0D, 0x0C, 0x0D, 0x0D, 0x0D, 0x0C, 0x0D, 0x0D, 0x0D, 0x0C, 0x0D, 0x0D, 0x0D, 0x0D, 0x0C, 0x0D, - 0x0D, 0x0D, 0x0C, 0x0C, 0x0C, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D, 0x0D -}; - -const unsigned short ChCodeAsc[0x100] = -{ - 0x0490, 0x0FE0, 0x07E0, 0x0BE0, 0x03E0, 0x0DE0, 0x05E0, 0x09E0, - 0x01E0, 0x00B8, 0x0062, 0x0EE0, 0x06E0, 0x0022, 0x0AE0, 0x02E0, - 0x0CE0, 0x04E0, 0x08E0, 0x00E0, 0x0F60, 0x0760, 0x0B60, 0x0360, - 0x0D60, 0x0560, 0x1240, 0x0960, 0x0160, 0x0E60, 0x0660, 0x0A60, - 0x000F, 0x0250, 0x0038, 0x0260, 0x0050, 0x0C60, 0x0390, 0x00D8, - 0x0042, 0x0002, 0x0058, 0x01B0, 0x007C, 0x0029, 0x003C, 0x0098, - 0x005C, 0x0009, 0x001C, 0x006C, 0x002C, 0x004C, 0x0018, 0x000C, - 0x0074, 0x00E8, 0x0068, 0x0460, 0x0090, 0x0034, 0x00B0, 0x0710, - 0x0860, 0x0031, 0x0054, 0x0011, 0x0021, 0x0017, 0x0014, 0x00A8, - 0x0028, 0x0001, 0x0310, 0x0130, 0x003E, 0x0064, 0x001E, 0x002E, - 0x0024, 0x0510, 0x000E, 0x0036, 0x0016, 0x0044, 0x0030, 0x00C8, - 0x01D0, 0x00D0, 0x0110, 0x0048, 0x0610, 0x0150, 0x0060, 0x0088, - 0x0FA0, 0x0007, 0x0026, 0x0006, 0x003A, 0x001B, 0x001A, 0x002A, - 0x000A, 0x000B, 0x0210, 0x0004, 0x0013, 0x0032, 0x0003, 0x001D, - 0x0012, 0x0190, 0x000D, 0x0015, 0x0005, 0x0019, 0x0008, 0x0078, - 0x00F0, 0x0070, 0x0290, 0x0410, 0x0010, 0x07A0, 0x0BA0, 0x03A0, - 0x0240, 0x1C40, 0x0C40, 0x1440, 0x0440, 0x1840, 0x0840, 0x1040, - 0x0040, 0x1F80, 0x0F80, 0x1780, 0x0780, 0x1B80, 0x0B80, 0x1380, - 0x0380, 0x1D80, 0x0D80, 0x1580, 0x0580, 0x1980, 0x0980, 0x1180, - 0x0180, 0x1E80, 0x0E80, 0x1680, 0x0680, 0x1A80, 0x0A80, 0x1280, - 0x0280, 0x1C80, 0x0C80, 0x1480, 0x0480, 0x1880, 0x0880, 0x1080, - 0x0080, 0x1F00, 0x0F00, 0x1700, 0x0700, 0x1B00, 0x0B00, 0x1300, - 0x0DA0, 0x05A0, 0x09A0, 0x01A0, 0x0EA0, 0x06A0, 0x0AA0, 0x02A0, - 0x0CA0, 0x04A0, 0x08A0, 0x00A0, 0x0F20, 0x0720, 0x0B20, 0x0320, - 0x0D20, 0x0520, 0x0920, 0x0120, 0x0E20, 0x0620, 0x0A20, 0x0220, - 0x0C20, 0x0420, 0x0820, 0x0020, 0x0FC0, 0x07C0, 0x0BC0, 0x03C0, - 0x0DC0, 0x05C0, 0x09C0, 0x01C0, 0x0EC0, 0x06C0, 0x0AC0, 0x02C0, - 0x0CC0, 0x04C0, 0x08C0, 0x00C0, 0x0F40, 0x0740, 0x0B40, 0x0340, - 0x0300, 0x0D40, 0x1D00, 0x0D00, 0x1500, 0x0540, 0x0500, 0x1900, - 0x0900, 0x0940, 0x1100, 0x0100, 0x1E00, 0x0E00, 0x0140, 0x1600, - 0x0600, 0x1A00, 0x0E40, 0x0640, 0x0A40, 0x0A00, 0x1200, 0x0200, - 0x1C00, 0x0C00, 0x1400, 0x0400, 0x1800, 0x0800, 0x1000, 0x0000 -}; - -//----------------------------------------------------------------------------- -// Local functions - -static void GenDecodeTabs( - unsigned char * positions, // [out] Table of positions - const unsigned char * start_indexes, // [in] Table of start indexes - const unsigned char * length_bits, // [in] Table of lengths. Each length is stored as number of bits - size_t elements) // [in] Number of elements in start_indexes and length_bits -{ - unsigned int index; - unsigned int length; - size_t i; - - for(i = 0; i < elements; i++) - { - length = 1 << length_bits[i]; // Get the length in bytes - - for(index = start_indexes[i]; index < 0x100; index += length) - { - positions[index] = (unsigned char)i; - } - } -} - -static void GenAscTabs(TDcmpStruct * pWork) -{ - const unsigned short * pChCodeAsc = &ChCodeAsc[0xFF]; - unsigned int acc, add; - unsigned short count; - - for(count = 0x00FF; pChCodeAsc >= ChCodeAsc; pChCodeAsc--, count--) - { - unsigned char * pChBitsAsc = pWork->ChBitsAsc + count; - unsigned char bits_asc = *pChBitsAsc; - - if(bits_asc <= 8) - { - add = (1 << bits_asc); - acc = *pChCodeAsc; - - do - { - pWork->offs2C34[acc] = (unsigned char)count; - acc += add; - } - while(acc < 0x100); - } - else if((acc = (*pChCodeAsc & 0xFF)) != 0) - { - pWork->offs2C34[acc] = 0xFF; - - if(*pChCodeAsc & 0x3F) - { - bits_asc -= 4; - *pChBitsAsc = bits_asc; - - add = (1 << bits_asc); - acc = *pChCodeAsc >> 4; - do - { - pWork->offs2D34[acc] = (unsigned char)count; - acc += add; - } - while(acc < 0x100); - } - else - { - bits_asc -= 6; - *pChBitsAsc = bits_asc; - - add = (1 << bits_asc); - acc = *pChCodeAsc >> 6; - do - { - pWork->offs2E34[acc] = (unsigned char)count; - acc += add; - } - while(acc < 0x80); - } - } - else - { - bits_asc -= 8; - *pChBitsAsc = bits_asc; - - add = (1 << bits_asc); - acc = *pChCodeAsc >> 8; - do - { - pWork->offs2EB4[acc] = (unsigned char)count; - acc += add; - } - while(acc < 0x100); - } - } -} - -//----------------------------------------------------------------------------- -// Removes given number of bits in the bit buffer. New bits are reloaded from -// the input buffer, if needed. -// Returns: PKDCL_OK: Operation was successful -// PKDCL_STREAM_END: There are no more bits in the input buffer - -static int WasteBits(TDcmpStruct * pWork, unsigned int nBits) -{ - // If number of bits required is less than number of (bits in the buffer) ? - if(nBits <= pWork->extra_bits) - { - pWork->extra_bits -= nBits; - pWork->bit_buff >>= nBits; - return PKDCL_OK; - } - - // Load input buffer if necessary - pWork->bit_buff >>= pWork->extra_bits; - if(pWork->in_pos == pWork->in_bytes) - { - pWork->in_pos = sizeof(pWork->in_buff); - if((pWork->in_bytes = pWork->read_buf((char *)pWork->in_buff, &pWork->in_pos, pWork->param)) == 0) - return PKDCL_STREAM_END; - pWork->in_pos = 0; - } - - // Update bit buffer - pWork->bit_buff |= (pWork->in_buff[pWork->in_pos++] << 8); - pWork->bit_buff >>= (nBits - pWork->extra_bits); - pWork->extra_bits = (pWork->extra_bits - nBits) + 8; - return PKDCL_OK; -} - -//----------------------------------------------------------------------------- -// Decodes next literal from the input (compressed) data. -// Returns : 0x000: One byte 0x00 -// 0x001: One byte 0x01 -// ... -// 0x0FF: One byte 0xFF -// 0x100: Repetition, length of 0x02 bytes -// 0x101: Repetition, length of 0x03 bytes -// ... -// 0x304: Repetition, length of 0x206 bytes -// 0x305: End of stream -// 0x306: Error - -static unsigned int DecodeLit(TDcmpStruct * pWork) -{ - unsigned int extra_length_bits; // Number of bits of extra literal length - unsigned int length_code; // Length code - unsigned int value; - - // Test the current bit in byte buffer. If is not set, simply return the next 8 bits. - if(pWork->bit_buff & 1) - { - // Remove one bit from the input data - if(WasteBits(pWork, 1)) - return 0x306; - - // The next 8 bits hold the index to the length code table - length_code = pWork->LengthCodes[pWork->bit_buff & 0xFF]; - - // Remove the apropriate number of bits - if(WasteBits(pWork, pWork->LenBits[length_code])) - return 0x306; - - // Are there some extra bits for the obtained length code ? - if((extra_length_bits = pWork->ExLenBits[length_code]) != 0) - { - unsigned int extra_length = pWork->bit_buff & ((1 << extra_length_bits) - 1); - - if(WasteBits(pWork, extra_length_bits)) - { - if((length_code + extra_length) != 0x10E) - return 0x306; - } - length_code = pWork->LenBase[length_code] + extra_length; - } - - // In order to distinguish uncompressed byte from repetition length, - // we have to add 0x100 to the length. - return length_code + 0x100; - } - - // Remove one bit from the input data - if(WasteBits(pWork, 1)) - return 0x306; - - // If the binary compression type, read 8 bits and return them as one byte. - if(pWork->ctype == CMP_BINARY) - { - unsigned int uncompressed_byte = pWork->bit_buff & 0xFF; - - if(WasteBits(pWork, 8)) - return 0x306; - return uncompressed_byte; - } - - // When ASCII compression ... - if(pWork->bit_buff & 0xFF) - { - value = pWork->offs2C34[pWork->bit_buff & 0xFF]; - - if(value == 0xFF) - { - if(pWork->bit_buff & 0x3F) - { - if(WasteBits(pWork, 4)) - return 0x306; - - value = pWork->offs2D34[pWork->bit_buff & 0xFF]; - } - else - { - if(WasteBits(pWork, 6)) - return 0x306; - - value = pWork->offs2E34[pWork->bit_buff & 0x7F]; - } - } - } - else - { - if(WasteBits(pWork, 8)) - return 0x306; - - value = pWork->offs2EB4[pWork->bit_buff & 0xFF]; - } - - return WasteBits(pWork, pWork->ChBitsAsc[value]) ? 0x306 : value; -} - -//----------------------------------------------------------------------------- -// Decodes the distance of the repetition, backwards relative to the -// current output buffer position - -static unsigned int DecodeDist(TDcmpStruct * pWork, unsigned int rep_length) -{ - unsigned int dist_pos_code; // Distance position code - unsigned int dist_pos_bits; // Number of bits of distance position - unsigned int distance; // Distance position - - // Next 2-8 bits in the input buffer is the distance position code - dist_pos_code = pWork->DistPosCodes[pWork->bit_buff & 0xFF]; - dist_pos_bits = pWork->DistBits[dist_pos_code]; - if(WasteBits(pWork, dist_pos_bits)) - return 0; - - if(rep_length == 2) - { - // If the repetition is only 2 bytes length, - // then take 2 bits from the stream in order to get the distance - distance = (dist_pos_code << 2) | (pWork->bit_buff & 0x03); - if(WasteBits(pWork, 2)) - return 0; - } - else - { - // If the repetition is more than 2 bytes length, - // then take "dsize_bits" bits in order to get the distance - distance = (dist_pos_code << pWork->dsize_bits) | (pWork->bit_buff & pWork->dsize_mask); - if(WasteBits(pWork, pWork->dsize_bits)) - return 0; - } - return distance + 1; -} - -static unsigned int Expand(TDcmpStruct * pWork) -{ - unsigned int next_literal; // Literal decoded from the compressed data - unsigned int result; // Value to be returned - unsigned int copyBytes; // Number of bytes to copy to the output buffer - - pWork->outputPos = 0x1000; // Initialize output buffer position - - // Decode the next literal from the input data. - // The returned literal can either be an uncompressed byte (next_literal < 0x100) - // or an encoded length of the repeating byte sequence that - // is to be copied to the current buffer position - while((result = next_literal = DecodeLit(pWork)) < 0x305) - { - // If the literal is greater than 0x100, it holds length - // of repeating byte sequence - // literal of 0x100 means repeating sequence of 0x2 bytes - // literal of 0x101 means repeating sequence of 0x3 bytes - // ... - // literal of 0x305 means repeating sequence of 0x207 bytes - if(next_literal >= 0x100) - { - unsigned char * source; - unsigned char * target; - unsigned int rep_length; // Length of the repetition, in bytes - unsigned int minus_dist; // Backward distance to the repetition, relative to the current buffer position - - // Get the length of the repeating sequence. - // Note that the repeating block may overlap the current output position, - // for example if there was a sequence of equal bytes - rep_length = next_literal - 0xFE; - - // Get backward distance to the repetition - if((minus_dist = DecodeDist(pWork, rep_length)) == 0) - { - result = 0x306; - break; - } - - // Target and source pointer - target = &pWork->out_buff[pWork->outputPos]; - source = target - minus_dist; - - // Update buffer output position - pWork->outputPos += rep_length; - - // Copy the repeating sequence - while(rep_length-- > 0) - *target++ = *source++; - } - else - { - pWork->out_buff[pWork->outputPos++] = (unsigned char)next_literal; - } - - // Flush the output buffer, if number of extracted bytes has reached the end - if(pWork->outputPos >= 0x2000) - { - // Copy decompressed data into user buffer - copyBytes = 0x1000; - pWork->write_buf((char *)&pWork->out_buff[0x1000], ©Bytes, pWork->param); - - // Now copy the decompressed data to the first half of the buffer. - // This is needed because the decompression might reuse them as repetitions. - // Note that if the output buffer overflowed previously, the extra decompressed bytes - // are stored in "out_buff_overflow", and they will now be - // within decompressed part of the output buffer. - memmove(pWork->out_buff, &pWork->out_buff[0x1000], pWork->outputPos - 0x1000); - pWork->outputPos -= 0x1000; - } - } - - // Flush any remaining decompressed bytes - copyBytes = pWork->outputPos - 0x1000; - pWork->write_buf((char *)&pWork->out_buff[0x1000], ©Bytes, pWork->param); - return result; -} - - -//----------------------------------------------------------------------------- -// Main exploding function. - -unsigned int PKEXPORT explode( - unsigned int (*read_buf)(char *buf, unsigned int *size, void *param), - void (*write_buf)(char *buf, unsigned int *size, void *param), - char *work_buf, - void *param) -{ - TDcmpStruct * pWork = (TDcmpStruct *)work_buf; - - // Initialize work struct and load compressed data - pWork->read_buf = read_buf; - pWork->write_buf = write_buf; - pWork->param = param; - pWork->in_pos = sizeof(pWork->in_buff); - pWork->in_bytes = pWork->read_buf((char *)pWork->in_buff, &pWork->in_pos, pWork->param); - if(pWork->in_bytes <= 4) - return CMP_BAD_DATA; - - pWork->ctype = pWork->in_buff[0]; // Get the compression type (CMP_BINARY or CMP_ASCII) - pWork->dsize_bits = pWork->in_buff[1]; // Get the dictionary size - pWork->bit_buff = pWork->in_buff[2]; // Initialize 16-bit bit buffer - pWork->extra_bits = 0; // Extra (over 8) bits - pWork->in_pos = 3; // Position in input buffer - - // Test for the valid dictionary size - if(4 > pWork->dsize_bits || pWork->dsize_bits > 6) - return CMP_INVALID_DICTSIZE; - - pWork->dsize_mask = 0xFFFF >> (0x10 - pWork->dsize_bits); // Shifted by 'sar' instruction - - if(pWork->ctype != CMP_BINARY) - { - if(pWork->ctype != CMP_ASCII) - return CMP_INVALID_MODE; - - memcpy(pWork->ChBitsAsc, ChBitsAsc, sizeof(pWork->ChBitsAsc)); - GenAscTabs(pWork); - } - - memcpy(pWork->LenBits, LenBits, sizeof(pWork->LenBits)); - GenDecodeTabs(pWork->LengthCodes, LenCode, LenBits, sizeof(LenBits)); - memcpy(pWork->ExLenBits, ExLenBits, sizeof(pWork->ExLenBits)); - memcpy(pWork->LenBase, LenBase, sizeof(pWork->LenBase)); - memcpy(pWork->DistBits, DistBits, sizeof(pWork->DistBits)); - GenDecodeTabs(pWork->DistPosCodes, DistCode, DistBits, sizeof(DistBits)); - if(Expand(pWork) != 0x306) - return CMP_NO_ERROR; - - return CMP_ABORT; -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/pklib/implode.c b/app/jni/src/libultraship/extern/StormLib/src/pklib/implode.c deleted file mode 100644 index 96baf98..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/pklib/implode.c +++ /dev/null @@ -1,674 +0,0 @@ -/*****************************************************************************/ -/* implode.c Copyright (c) Ladislav Zezula 2003 */ -/*---------------------------------------------------------------------------*/ -/* Implode function of PKWARE Data Compression library */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 11.04.03 1.00 Lad First version of implode.c */ -/* 02.05.03 1.00 Lad Stress test done */ -/* 22.04.10 1.01 Lad Documented */ -/*****************************************************************************/ - -#include -#include -#include - -#include "pklib.h" - -#if ((1200 < _MSC_VER) && (_MSC_VER < 1400)) -#pragma optimize("", off) // Fucking Microsoft VS.NET 2003 compiler !!! (_MSC_VER=1310) -#endif - -//----------------------------------------------------------------------------- -// Defines - -#define MAX_REP_LENGTH 0x204 // The longest allowed repetition - -//----------------------------------------------------------------------------- -// Macros - -// Macro for calculating hash of the current byte pair. -// Note that most exact byte pair hash would be buffer[0] + buffer[1] << 0x08, -// but even this way gives nice indication of equal byte pairs, with significantly -// smaller size of the array that holds numbers of those hashes -#define BYTE_PAIR_HASH(buffer) ((buffer[0] * 4) + (buffer[1] * 5)) - -//----------------------------------------------------------------------------- -// Local functions - -// Builds the "hash_to_index" table and "pair_hash_offsets" table. -// Every element of "hash_to_index" will contain lowest index to the -// "pair_hash_offsets" table, effectively giving offset of the first -// occurence of the given PAIR_HASH in the input data. -static void SortBuffer(TCmpStruct * pWork, unsigned char * buffer_begin, unsigned char * buffer_end) -{ - unsigned short * phash_to_index; - unsigned char * buffer_ptr; - unsigned short total_sum = 0; - unsigned long byte_pair_hash; // Hash value of the byte pair - unsigned short byte_pair_offs; // Offset of the byte pair, relative to "work_buff" - - // Zero the entire "phash_to_index" table - memset(pWork->phash_to_index, 0, sizeof(pWork->phash_to_index)); - - // Step 1: Count amount of each PAIR_HASH in the input buffer - // The table will look like this: - // offs 0x000: Number of occurences of PAIR_HASH 0 - // offs 0x001: Number of occurences of PAIR_HASH 1 - // ... - // offs 0x8F7: Number of occurences of PAIR_HASH 0x8F7 (the highest hash value) - for(buffer_ptr = buffer_begin; buffer_ptr < buffer_end; buffer_ptr++) - pWork->phash_to_index[BYTE_PAIR_HASH(buffer_ptr)]++; - - // Step 2: Convert the table to the array of PAIR_HASH amounts. - // Each element contains count of PAIR_HASHes that is less or equal - // to element index - // The table will look like this: - // offs 0x000: Number of occurences of PAIR_HASH 0 or lower - // offs 0x001: Number of occurences of PAIR_HASH 1 or lower - // ... - // offs 0x8F7: Number of occurences of PAIR_HASH 0x8F7 or lower - for(phash_to_index = pWork->phash_to_index; phash_to_index < &pWork->phash_to_index_end; phash_to_index++) - { - total_sum = total_sum + phash_to_index[0]; - phash_to_index[0] = total_sum; - } - - // Step 3: Convert the table to the array of indexes. - // Now, each element contains index to the first occurence of given PAIR_HASH - for(buffer_end--; buffer_end >= buffer_begin; buffer_end--) - { - byte_pair_hash = BYTE_PAIR_HASH(buffer_end); - byte_pair_offs = (unsigned short)(buffer_end - pWork->work_buff); - - pWork->phash_to_index[byte_pair_hash]--; - pWork->phash_offs[pWork->phash_to_index[byte_pair_hash]] = byte_pair_offs; - } -} - -static void FlushBuf(TCmpStruct * pWork) -{ - unsigned char save_ch1; - unsigned char save_ch2; - unsigned int size = 0x800; - - pWork->write_buf(pWork->out_buff, &size, pWork->param); - - save_ch1 = pWork->out_buff[0x800]; - save_ch2 = pWork->out_buff[pWork->out_bytes]; - pWork->out_bytes -= 0x800; - - memset(pWork->out_buff, 0, sizeof(pWork->out_buff)); - - if(pWork->out_bytes != 0) - pWork->out_buff[0] = save_ch1; - if(pWork->out_bits != 0) - pWork->out_buff[pWork->out_bytes] = save_ch2; -} - -static void OutputBits(TCmpStruct * pWork, unsigned int nbits, unsigned long bit_buff) -{ - unsigned int out_bits; - - // If more than 8 bits to output, do recursion - if(nbits > 8) - { - OutputBits(pWork, 8, bit_buff); - bit_buff >>= 8; - nbits -= 8; - } - - // Add bits to the last out byte in out_buff; - out_bits = pWork->out_bits; - pWork->out_buff[pWork->out_bytes] |= (unsigned char)(bit_buff << out_bits); - pWork->out_bits += nbits; - - // If 8 or more bits, increment number of bytes - if(pWork->out_bits > 8) - { - pWork->out_bytes++; - bit_buff >>= (8 - out_bits); - - pWork->out_buff[pWork->out_bytes] = (unsigned char)bit_buff; - pWork->out_bits &= 7; - } - else - { - pWork->out_bits &= 7; - if(pWork->out_bits == 0) - pWork->out_bytes++; - } - - // If there is enough compressed bytes, flush them - if(pWork->out_bytes >= 0x800) - FlushBuf(pWork); -} - -// This function searches for a repetition -// (a previous occurence of the current byte sequence) -// Returns length of the repetition, and stores the backward distance -// to pWork structure. -static unsigned int FindRep(TCmpStruct * pWork, unsigned char * input_data) -{ - unsigned short * phash_to_index; // Pointer into pWork->phash_to_index table - unsigned short * phash_offs; // Pointer to the table containing offsets of each PAIR_HASH - unsigned char * repetition_limit; // An eventual repetition must be at position below this pointer - unsigned char * prev_repetition; // Pointer to the previous occurence of the current PAIR_HASH - unsigned char * prev_rep_end; // End of the previous repetition - unsigned char * input_data_ptr; - unsigned short phash_offs_index; // Index to the table with PAIR_HASH positions - unsigned short min_phash_offs; // The lowest allowed hash offset - unsigned short offs_in_rep; // Offset within found repetition - unsigned int equal_byte_count; // Number of bytes that are equal to the previous occurence - unsigned int rep_length = 1; // Length of the found repetition - unsigned int rep_length2; // Secondary repetition - unsigned char pre_last_byte; // Last but one byte from a repetion - unsigned short di_val; - - // Calculate the previous position of the PAIR_HASH - phash_to_index = pWork->phash_to_index + BYTE_PAIR_HASH(input_data); - min_phash_offs = (unsigned short)((input_data - pWork->work_buff) - pWork->dsize_bytes + 1); - phash_offs_index = phash_to_index[0]; - - // If the PAIR_HASH offset is below the limit, find a next one - phash_offs = pWork->phash_offs + phash_offs_index; - if(*phash_offs < min_phash_offs) - { - while(*phash_offs < min_phash_offs) - { - phash_offs_index++; - phash_offs++; - } - *phash_to_index = phash_offs_index; - } - - // Get the first location of the PAIR_HASH, - // and thus the first eventual location of byte repetition - phash_offs = pWork->phash_offs + phash_offs_index; - prev_repetition = pWork->work_buff + phash_offs[0]; - repetition_limit = input_data - 1; - - // If the current PAIR_HASH was not encountered before, - // we haven't found a repetition. - if(prev_repetition >= repetition_limit) - return 0; - - // We have found a match of a PAIR_HASH. Now we have to make sure - // that it is also a byte match, because PAIR_HASH is not unique. - // We compare the bytes and count the length of the repetition - input_data_ptr = input_data; - for(;;) - { - // If the first byte of the repetition and the so-far-last byte - // of the repetition are equal, we will compare the blocks. - if(*input_data_ptr == *prev_repetition && input_data_ptr[rep_length-1] == prev_repetition[rep_length-1]) - { - // Skip the current byte - prev_repetition++; - input_data_ptr++; - equal_byte_count = 2; - - // Now count how many more bytes are equal - while(equal_byte_count < MAX_REP_LENGTH) - { - prev_repetition++; - input_data_ptr++; - - // Are the bytes different ? - if(*prev_repetition != *input_data_ptr) - break; - - equal_byte_count++; - } - - // If we found a repetition of at least the same length, take it. - // If there are multiple repetitions in the input buffer, this will - // make sure that we find the most recent one, which in turn allows - // us to store backward length in less amount of bits - input_data_ptr = input_data; - if(equal_byte_count >= rep_length) - { - // Calculate the backward distance of the repetition. - // Note that the distance is stored as decremented by 1 - pWork->distance = (unsigned int)(input_data - prev_repetition + equal_byte_count - 1); - - // Repetitions longer than 10 bytes will be stored in more bits, - // so they need a bit different handling - if((rep_length = equal_byte_count) > 10) - break; - } - } - - // Move forward in the table of PAIR_HASH repetitions. - // There might be a more recent occurence of the same repetition. - phash_offs_index++; - phash_offs++; - prev_repetition = pWork->work_buff + phash_offs[0]; - - // If the next repetition is beyond the minimum allowed repetition, we are done. - if(prev_repetition >= repetition_limit) - { - // A repetition must have at least 2 bytes, otherwise it's not worth it - return (rep_length >= 2) ? rep_length : 0; - } - } - - // If the repetition has max length of 0x204 bytes, we can't go any fuhrter - if(equal_byte_count == MAX_REP_LENGTH) - { - pWork->distance--; - return equal_byte_count; - } - - // Check for possibility of a repetition that occurs at more recent position - phash_offs = pWork->phash_offs + phash_offs_index; - if(pWork->work_buff + phash_offs[1] >= repetition_limit) - return rep_length; - - // - // The following part checks if there isn't a longer repetition at - // a latter offset, that would lead to better compression. - // - // Example of data that can trigger this optimization: - // - // "EEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEQQQQQQQQQQQQ" - // "XYZ" - // "EEEEEEEEEEEEEEEEQQQQQQQQQQQQ"; - // - // Description of data in this buffer - // [0x00] Single byte "E" - // [0x01] Single byte "E" - // [0x02] Repeat 0x1E bytes from [0x00] - // [0x20] Single byte "X" - // [0x21] Single byte "Y" - // [0x22] Single byte "Z" - // [0x23] 17 possible previous repetitions of length at least 0x10 bytes: - // - Repetition of 0x10 bytes from [0x00] "EEEEEEEEEEEEEEEE" - // - Repetition of 0x10 bytes from [0x01] "EEEEEEEEEEEEEEEE" - // - Repetition of 0x10 bytes from [0x02] "EEEEEEEEEEEEEEEE" - // ... - // - Repetition of 0x10 bytes from [0x0F] "EEEEEEEEEEEEEEEE" - // - Repetition of 0x1C bytes from [0x10] "EEEEEEEEEEEEEEEEQQQQQQQQQQQQ" - // The last repetition is the best one. - // - - pWork->offs09BC[0] = USHRT_MAX; - pWork->offs09BC[1] = 0x0000; - di_val = 0; - - // Note: I failed to figure out what does the table "offs09BC" mean. - // If anyone has an idea, let me know to zezula_at_volny_dot_cz - for(offs_in_rep = 1; offs_in_rep < rep_length; ) - { - if(input_data[offs_in_rep] != input_data[di_val]) - { - di_val = pWork->offs09BC[di_val]; - if(di_val != USHRT_MAX) - continue; - } - pWork->offs09BC[++offs_in_rep] = ++di_val; - } - - // - // Now go through all the repetitions from the first found one - // to the current input data, and check if any of them migh be - // a start of a greater sequence match. - // - - prev_repetition = pWork->work_buff + phash_offs[0]; - prev_rep_end = prev_repetition + rep_length; - rep_length2 = rep_length; - - for(;;) - { - rep_length2 = pWork->offs09BC[rep_length2]; - if(rep_length2 == USHRT_MAX) - rep_length2 = 0; - - // Get the pointer to the previous repetition - phash_offs = pWork->phash_offs + phash_offs_index; - - // Skip those repetitions that don't reach the end - // of the first found repetition - do - { - phash_offs++; - phash_offs_index++; - prev_repetition = pWork->work_buff + *phash_offs; - if(prev_repetition >= repetition_limit) - return rep_length; - } - while(prev_repetition + rep_length2 < prev_rep_end); - - // Verify if the last but one byte from the repetition matches - // the last but one byte from the input data. - // If not, find a next repetition - pre_last_byte = input_data[rep_length - 2]; - if(pre_last_byte == prev_repetition[rep_length - 2]) - { - // If the new repetition reaches beyond the end - // of previously found repetition, reset the repetition length to zero. - if(prev_repetition + rep_length2 != prev_rep_end) - { - prev_rep_end = prev_repetition; - rep_length2 = 0; - } - } - else - { - phash_offs = pWork->phash_offs + phash_offs_index; - do - { - phash_offs++; - phash_offs_index++; - prev_repetition = pWork->work_buff + *phash_offs; - if(prev_repetition >= repetition_limit) - return rep_length; - } - while(prev_repetition[rep_length - 2] != pre_last_byte || prev_repetition[0] != input_data[0]); - - // Reset the length of the repetition to 2 bytes only - prev_rep_end = prev_repetition + 2; - rep_length2 = 2; - } - - // Find out how many more characters are equal to the first repetition. - while(*prev_rep_end == input_data[rep_length2]) - { - if(++rep_length2 >= 0x204) - break; - prev_rep_end++; - } - - // Is the newly found repetion at least as long as the previous one ? - if(rep_length2 >= rep_length) - { - // Calculate the distance of the new repetition - pWork->distance = (unsigned int)(input_data - prev_repetition - 1); - if((rep_length = rep_length2) == 0x204) - return rep_length; - - // Update the additional elements in the "offs09BC" table - // to reflect new rep length - while(offs_in_rep < rep_length2) - { - if(input_data[offs_in_rep] != input_data[di_val]) - { - di_val = pWork->offs09BC[di_val]; - if(di_val != USHRT_MAX) - continue; - } - pWork->offs09BC[++offs_in_rep] = ++di_val; - } - } - } -} - -static void WriteCmpData(TCmpStruct * pWork) -{ - unsigned char * input_data_end; // Pointer to the end of the input data - unsigned char * input_data = pWork->work_buff + pWork->dsize_bytes + 0x204; - unsigned int input_data_ended = 0; // If 1, then all data from the input stream have been already loaded - unsigned int save_rep_length; // Saved length of current repetition - unsigned int save_distance = 0; // Saved distance of current repetition - unsigned int rep_length; // Length of the found repetition - unsigned int phase = 0; // - - // Store the compression type and dictionary size - pWork->out_buff[0] = (char)pWork->ctype; - pWork->out_buff[1] = (char)pWork->dsize_bits; - pWork->out_bytes = 2; - - // Reset output buffer to zero - memset(&pWork->out_buff[2], 0, sizeof(pWork->out_buff) - 2); - pWork->out_bits = 0; - - while(input_data_ended == 0) - { - unsigned int bytes_to_load = 0x1000; - int total_loaded = 0; - int bytes_loaded; - - // Load the bytes from the input stream, up to 0x1000 bytes - while(bytes_to_load != 0) - { - bytes_loaded = pWork->read_buf((char *)pWork->work_buff + pWork->dsize_bytes + 0x204 + total_loaded, - &bytes_to_load, - pWork->param); - if(bytes_loaded == 0) - { - if(total_loaded == 0 && phase == 0) - goto __Exit; - input_data_ended = 1; - break; - } - else - { - bytes_to_load -= bytes_loaded; - total_loaded += bytes_loaded; - } - } - - input_data_end = pWork->work_buff + pWork->dsize_bytes + total_loaded; - if(input_data_ended) - input_data_end += 0x204; - - // - // Warning: The end of the buffer passed to "SortBuffer" is actually 2 bytes beyond - // valid data. It is questionable if this is actually a bug or not, - // but it might cause the compressed data output to be dependent on random bytes - // that are in the buffer. - // To prevent that, the calling application must always zero the compression - // buffer before passing it to "implode" - // - - // Search the PAIR_HASHes of the loaded blocks. Also, include - // previously compressed data, if any. - switch(phase) - { - case 0: - SortBuffer(pWork, input_data, input_data_end + 1); - phase++; - if(pWork->dsize_bytes != 0x1000) - phase++; - break; - - case 1: - SortBuffer(pWork, input_data - pWork->dsize_bytes + 0x204, input_data_end + 1); - phase++; - break; - - default: - SortBuffer(pWork, input_data - pWork->dsize_bytes, input_data_end + 1); - break; - } - - // Perform the compression of the current block - while(input_data < input_data_end) - { - // Find if the current byte sequence wasn't there before. - rep_length = FindRep(pWork, input_data); - while(rep_length != 0) - { - // If we found repetition of 2 bytes, that is 0x100 or fuhrter back, - // don't bother. Storing the distance of 0x100 bytes would actually - // take more space than storing the 2 bytes as-is. - if(rep_length == 2 && pWork->distance >= 0x100) - break; - - // When we are at the end of the input data, we cannot allow - // the repetition to go past the end of the input data. - if(input_data_ended && input_data + rep_length > input_data_end) - { - // Shorten the repetition length so that it only covers valid data - rep_length = (unsigned long)(input_data_end - input_data); - if(rep_length < 2) - break; - - // If we got repetition of 2 bytes, that is 0x100 or more backward, don't bother - if(rep_length == 2 && pWork->distance >= 0x100) - break; - goto __FlushRepetition; - } - - if(rep_length >= 8 || input_data + 1 >= input_data_end) - goto __FlushRepetition; - - // Try to find better repetition 1 byte later. - // Example: "ARROCKFORT" "AROCKFORT" - // When "input_data" points to the second string, FindRep - // returns the occurence of "AR". But there is longer repetition "ROCKFORT", - // beginning 1 byte after. - save_rep_length = rep_length; - save_distance = pWork->distance; - rep_length = FindRep(pWork, input_data + 1); - - // Only use the new repetition if it's length is greater than the previous one - if(rep_length > save_rep_length) - { - // If the new repetition if only 1 byte better - // and the previous distance is less than 0x80 bytes, use the previous repetition - if(rep_length > save_rep_length + 1 || save_distance > 0x80) - { - // Flush one byte, so that input_data will point to the secondary repetition - OutputBits(pWork, pWork->nChBits[*input_data], pWork->nChCodes[*input_data]); - input_data++; - continue; - } - } - - // Revert to the previous repetition - rep_length = save_rep_length; - pWork->distance = save_distance; - - __FlushRepetition: - - OutputBits(pWork, pWork->nChBits[rep_length + 0xFE], pWork->nChCodes[rep_length + 0xFE]); - if(rep_length == 2) - { - OutputBits(pWork, pWork->dist_bits[pWork->distance >> 2], - pWork->dist_codes[pWork->distance >> 2]); - OutputBits(pWork, 2, pWork->distance & 3); - } - else - { - OutputBits(pWork, pWork->dist_bits[pWork->distance >> pWork->dsize_bits], - pWork->dist_codes[pWork->distance >> pWork->dsize_bits]); - OutputBits(pWork, pWork->dsize_bits, pWork->dsize_mask & pWork->distance); - } - - // Move the begin of the input data by the length of the repetition - input_data += rep_length; - goto _00402252; - } - - // If there was no previous repetition for the current position in the input data, - // just output the 9-bit literal for the one character - OutputBits(pWork, pWork->nChBits[*input_data], pWork->nChCodes[*input_data]); - input_data++; -_00402252:; - } - - if(input_data_ended == 0) - { - input_data -= 0x1000; - memmove(pWork->work_buff, pWork->work_buff + 0x1000, pWork->dsize_bytes + 0x204); - } - } - -__Exit: - - // Write the termination literal - OutputBits(pWork, pWork->nChBits[0x305], pWork->nChCodes[0x305]); - if(pWork->out_bits != 0) - pWork->out_bytes++; - pWork->write_buf(pWork->out_buff, &pWork->out_bytes, pWork->param); - return; -} - -//----------------------------------------------------------------------------- -// Main imploding function - -unsigned int PKEXPORT implode( - unsigned int (*read_buf)(char *buf, unsigned int *size, void *param), - void (*write_buf)(char *buf, unsigned int *size, void *param), - char *work_buf, - void *param, - unsigned int *type, - unsigned int *dsize) -{ - TCmpStruct * pWork = (TCmpStruct *)work_buf; - unsigned int nCount; - unsigned int i; - int nCount2; - - // Fill the work buffer information - pWork->read_buf = read_buf; - pWork->write_buf = write_buf; - pWork->dsize_bytes = *dsize; - pWork->ctype = *type; - pWork->param = param; - pWork->dsize_bits = 4; - pWork->dsize_mask = 0x0F; - - // Test dictionary size - switch(*dsize) - { - case CMP_IMPLODE_DICT_SIZE3: // 0x1000 bytes - pWork->dsize_bits++; - pWork->dsize_mask |= 0x20; - // No break here !!! - - case CMP_IMPLODE_DICT_SIZE2: // 0x800 bytes - pWork->dsize_bits++; - pWork->dsize_mask |= 0x10; - // No break here !!! - - case CMP_IMPLODE_DICT_SIZE1: // 0x400 - break; - - default: - return CMP_INVALID_DICTSIZE; - } - - // Test the compression type - switch(*type) - { - case CMP_BINARY: // We will compress data with binary compression type - for(nCount = 0; nCount < 0x100; nCount++) - { - pWork->nChBits[nCount] = 9; - pWork->nChCodes[nCount] = nCount * 2; - } - break; - - - case CMP_ASCII: // We will compress data with ASCII compression type - for(nCount = 0; nCount < 0x100; nCount++) - { - pWork->nChBits[nCount] = (unsigned char )(ChBitsAsc[nCount] + 1); - pWork->nChCodes[nCount] = (unsigned short)(ChCodeAsc[nCount] * 2); - } - break; - - default: - return CMP_INVALID_MODE; - } - - for(i = 0; i < 0x10; i++) - { - for(nCount2 = 0; nCount2 < (1 << ExLenBits[i]); nCount2++) - { - pWork->nChBits[nCount] = (unsigned char)(ExLenBits[i] + LenBits[i] + 1); - pWork->nChCodes[nCount] = (unsigned short)((nCount2 << (LenBits[i] + 1)) | ((LenCode[i] & 0xFFFF00FF) * 2) | 1); - nCount++; - } - } - - // Copy the distance codes and distance bits and perform the compression - memcpy(&pWork->dist_codes, DistCode, sizeof(DistCode)); - memcpy(&pWork->dist_bits, DistBits, sizeof(DistBits)); - WriteCmpData(pWork); - return CMP_NO_ERROR; -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/pklib/pklib.h b/app/jni/src/libultraship/extern/StormLib/src/pklib/pklib.h deleted file mode 100644 index c1e328d..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/pklib/pklib.h +++ /dev/null @@ -1,158 +0,0 @@ -/*****************************************************************************/ -/* pklib.h Copyright (c) Ladislav Zezula 2003 */ -/*---------------------------------------------------------------------------*/ -/* Header file for PKWARE Data Compression Library */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 31.03.03 1.00 Lad The first version of pkware.h */ -/*****************************************************************************/ - -#ifndef __PKLIB_H__ -#define __PKLIB_H__ - -//----------------------------------------------------------------------------- -// Defines - -#define CMP_BINARY 0 // Binary compression -#define CMP_ASCII 1 // Ascii compression - -#define CMP_NO_ERROR 0 -#define CMP_INVALID_DICTSIZE 1 -#define CMP_INVALID_MODE 2 -#define CMP_BAD_DATA 3 -#define CMP_ABORT 4 - -#define CMP_IMPLODE_DICT_SIZE1 1024 // Dictionary size of 1024 -#define CMP_IMPLODE_DICT_SIZE2 2048 // Dictionary size of 2048 -#define CMP_IMPLODE_DICT_SIZE3 4096 // Dictionary size of 4096 - -//----------------------------------------------------------------------------- -// Define calling convention - -#ifndef PKEXPORT -#ifdef WIN32 -#define PKEXPORT __cdecl // Use for normal __cdecl calling -#else -#define PKEXPORT -#endif -#endif - -//----------------------------------------------------------------------------- -// Internal structures - -// Compression structure -typedef struct -{ - unsigned int distance; // 0000: Backward distance of the currently found repetition, decreased by 1 - unsigned int out_bytes; // 0004: # bytes available in out_buff - unsigned int out_bits; // 0008: # of bits available in the last out byte - unsigned int dsize_bits; // 000C: Number of bits needed for dictionary size. 4 = 0x400, 5 = 0x800, 6 = 0x1000 - unsigned int dsize_mask; // 0010: Bit mask for dictionary. 0x0F = 0x400, 0x1F = 0x800, 0x3F = 0x1000 - unsigned int ctype; // 0014: Compression type (CMP_ASCII or CMP_BINARY) - unsigned int dsize_bytes; // 0018: Dictionary size in bytes - unsigned char dist_bits[0x40]; // 001C: Distance bits - unsigned char dist_codes[0x40]; // 005C: Distance codes - unsigned char nChBits[0x306]; // 009C: Table of literal bit lengths to be put to the output stream - unsigned short nChCodes[0x306]; // 03A2: Table of literal codes to be put to the output stream - unsigned short offs09AE; // 09AE: - - void * param; // 09B0: User parameter - unsigned int (*read_buf)(char *buf, unsigned int *size, void *param); // 9B4 - void (*write_buf)(char *buf, unsigned int *size, void *param); // 9B8 - - unsigned short offs09BC[0x204]; // 09BC: - unsigned long offs0DC4; // 0DC4: - unsigned short phash_to_index[0x900]; // 0DC8: Array of indexes (one for each PAIR_HASH) to the "pair_hash_offsets" table - unsigned short phash_to_index_end; // 1FC8: End marker for "phash_to_index" table - char out_buff[0x802]; // 1FCA: Compressed data - unsigned char work_buff[0x2204]; // 27CC: Work buffer - // + DICT_OFFSET => Dictionary - // + UNCMP_OFFSET => Uncompressed data - unsigned short phash_offs[0x2204]; // 49D0: Table of offsets for each PAIR_HASH -} TCmpStruct; - -#define CMP_BUFFER_SIZE sizeof(TCmpStruct) // Size of compression structure. - // Defined as 36312 in pkware header file - - -// Decompression structure -typedef struct -{ - unsigned long offs0000; // 0000 - unsigned long ctype; // 0004: Compression type (CMP_BINARY or CMP_ASCII) - unsigned long outputPos; // 0008: Position in output buffer - unsigned long dsize_bits; // 000C: Dict size (4, 5, 6 for 0x400, 0x800, 0x1000) - unsigned long dsize_mask; // 0010: Dict size bitmask (0x0F, 0x1F, 0x3F for 0x400, 0x800, 0x1000) - unsigned long bit_buff; // 0014: 16-bit buffer for processing input data - unsigned long extra_bits; // 0018: Number of extra (above 8) bits in bit buffer - unsigned int in_pos; // 001C: Position in in_buff - unsigned long in_bytes; // 0020: Number of bytes in input buffer - void * param; // 0024: Custom parameter - unsigned int (*read_buf)(char *buf, unsigned int *size, void *param); // Pointer to function that reads data from the input stream - void (*write_buf)(char *buf, unsigned int *size, void *param);// Pointer to function that writes data to the output stream - - unsigned char out_buff[0x2204]; // 0030: Output circle buffer. - // 0x0000 - 0x0FFF: Previous uncompressed data, kept for repetitions - // 0x1000 - 0x1FFF: Currently decompressed data - // 0x2000 - 0x2203: Reserve space for the longest possible repetition - unsigned char in_buff[0x800]; // 2234: Buffer for data to be decompressed - unsigned char DistPosCodes[0x100]; // 2A34: Table of distance position codes - unsigned char LengthCodes[0x100]; // 2B34: Table of length codes - unsigned char offs2C34[0x100]; // 2C34: Buffer for - unsigned char offs2D34[0x100]; // 2D34: Buffer for - unsigned char offs2E34[0x80]; // 2E34: Buffer for - unsigned char offs2EB4[0x100]; // 2EB4: Buffer for - unsigned char ChBitsAsc[0x100]; // 2FB4: Buffer for - unsigned char DistBits[0x40]; // 30B4: Numbers of bytes to skip copied block length - unsigned char LenBits[0x10]; // 30F4: Numbers of bits for skip copied block length - unsigned char ExLenBits[0x10]; // 3104: Number of valid bits for copied block - unsigned short LenBase[0x10]; // 3114: Buffer for -} TDcmpStruct; - -#define EXP_BUFFER_SIZE sizeof(TDcmpStruct) // Size of decompression structure - // Defined as 12596 in pkware headers - -//----------------------------------------------------------------------------- -// Tables (in explode.c) - -extern const unsigned char DistBits[0x40]; -extern const unsigned char DistCode[0x40]; -extern const unsigned char ExLenBits[0x10]; -extern const unsigned short LenBase[0x10]; -extern const unsigned char LenBits[0x10]; -extern const unsigned char LenCode[0x10]; -extern const unsigned char ChBitsAsc[0x100]; -extern const unsigned short ChCodeAsc[0x100]; - -//----------------------------------------------------------------------------- -// Public functions - -#ifdef __cplusplus - extern "C" { -#endif - -unsigned int PKEXPORT implode( - unsigned int (*read_buf)(char *buf, unsigned int *size, void *param), - void (*write_buf)(char *buf, unsigned int *size, void *param), - char *work_buf, - void *param, - unsigned int *type, - unsigned int *dsize); - - -unsigned int PKEXPORT explode( - unsigned int (*read_buf)(char *buf, unsigned int *size, void *param), - void (*write_buf)(char *buf, unsigned int *size, void *param), - char *work_buf, - void *param); - -// The original name "crc32" was changed to "crc32pk" due -// to compatibility with zlib -unsigned long PKEXPORT crc32_pklib(char *buffer, unsigned int *size, unsigned long *old_crc); - -#ifdef __cplusplus - } // End of 'extern "C"' declaration -#endif - -#endif // __PKLIB_H__ diff --git a/app/jni/src/libultraship/extern/StormLib/src/resource.h b/app/jni/src/libultraship/extern/StormLib/src/resource.h deleted file mode 100644 index 8821947..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/resource.h +++ /dev/null @@ -1,15 +0,0 @@ -//{{NO_DEPENDENCIES}} -// Microsoft Visual C++ generated include file. -// Used by DllMain.rc -// - -// Next default values for new objects -// -#ifdef APSTUDIO_INVOKED -#ifndef APSTUDIO_READONLY_SYMBOLS -#define _APS_NEXT_RESOURCE_VALUE 101 -#define _APS_NEXT_COMMAND_VALUE 40001 -#define _APS_NEXT_CONTROL_VALUE 1000 -#define _APS_NEXT_SYMED_VALUE 101 -#endif -#endif diff --git a/app/jni/src/libultraship/extern/StormLib/src/sparse/sparse.cpp b/app/jni/src/libultraship/extern/StormLib/src/sparse/sparse.cpp deleted file mode 100644 index 6d1b621..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/sparse/sparse.cpp +++ /dev/null @@ -1,282 +0,0 @@ -/*****************************************************************************/ -/* huffman.cpp Copyright (c) Ladislav Zezula 1998-2003 */ -/*---------------------------------------------------------------------------*/ -/* This module contains Huffmann (de)compression methods */ -/* */ -/* Authors : Ladislav Zezula (ladik.zezula.net) */ -/* ShadowFlare (BlakFlare@hotmail.com) */ -/* */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* xx.xx.xx 1.00 Lad The first version of dcmp.cpp */ -/* 03.05.03 1.00 Lad Added compression methods */ -/* 19.11.03 1.01 Dan Big endian handling */ -/* 08.12.03 2.01 Dan High-memory handling (> 0x80000000) */ -/*****************************************************************************/ - -#include -#include - -#include "sparse.h" - -//----------------------------------------------------------------------------- -// Public functions - -void CompressSparse(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer) -{ - unsigned char * pbOutBufferEnd = (unsigned char *)pvOutBuffer + *pcbOutBuffer; - unsigned char * pbInBufferEnd = (unsigned char *)pvInBuffer + cbInBuffer; - unsigned char * pbLastNonZero = (unsigned char *)pvInBuffer; - unsigned char * pbOutBuffer0 = (unsigned char *)pvOutBuffer; - unsigned char * pbInBuffPtr = (unsigned char *)pvInBuffer; - unsigned char * pbOutBuffer = (unsigned char *)pvOutBuffer; - unsigned char * pbInBuffer = (unsigned char *)pvInBuffer; - size_t NumberOfNonZeros; - size_t NumberOfZeros; - - // There must be at least 4 bytes of free space in the output buffer now - if((pbInBuffer + 4) >= pbInBufferEnd) - return; - - // Put the original data length (in little endian) - *pbOutBuffer++ = (unsigned char)(cbInBuffer >> 0x18); - *pbOutBuffer++ = (unsigned char)(cbInBuffer >> 0x10); - *pbOutBuffer++ = (unsigned char)(cbInBuffer >> 0x08); - *pbOutBuffer++ = (unsigned char)(cbInBuffer >> 0x00); - - // If there is at least 3 bytes in the input buffer, do this loop - while(pbInBuffer < (pbInBufferEnd - 3)) - { - // Reset the zero count and frontal pointer - pbLastNonZero = pbInBuffer; - pbInBuffPtr = pbInBuffer; - NumberOfZeros = 0; - - if(pbInBuffPtr < pbInBufferEnd) - { - do - { - // Count number of zeros - if(*pbInBuffPtr == 0) - { - NumberOfZeros++; - } - else - { - // Were there at least 3 zeros before? If yes, we need to flush the data - if(NumberOfZeros >= 3) - break; - pbLastNonZero = pbInBuffPtr + 1; - NumberOfZeros = 0; - } - } - while(++pbInBuffPtr < pbInBufferEnd); - } - - // Get number of nonzeros that we found so far and flush them - NumberOfNonZeros = pbLastNonZero - pbInBuffer; - if(NumberOfNonZeros != 0) - { - // Process blocks that are longer than 0x81 nonzero bytes - while(NumberOfNonZeros > 0x81) - { - // Verify if we still have enough space in output buffer - if((pbOutBuffer + 0x81) >= pbOutBufferEnd) - return; - - // Put marker that means "0x80 of nonzeros" - *pbOutBuffer++ = 0xFF; - memcpy(pbOutBuffer, pbInBuffer, 0x80); - - // Adjust counter of nonzeros and both pointers - NumberOfNonZeros -= 0x80; - pbOutBuffer += 0x80; - pbInBuffer += 0x80; - } - - // BUGBUG: The following code will be triggered if the NumberOfNonZeros - // was 0x81 before. It will copy just one byte. This seems like a bug to me, - // but since I want StormLib to be exact like Blizzard code is, I will keep - // it that way here - if(NumberOfNonZeros > 0x80) - { - // Verify if we still have enough space in output buffer - if((pbOutBuffer + 2) >= pbOutBufferEnd) - return; - - // Put marker that means "1 nonzero byte" - *pbOutBuffer++ = 0x80; - memcpy(pbOutBuffer, pbInBuffer, 1); - - // Adjust counter of nonzeros and both pointers - NumberOfNonZeros--; - pbOutBuffer++; - pbInBuffer++; - } - - // If there is 1 nonzero or more, put the block - if(NumberOfNonZeros >= 0x01) - { - // Verify if we still have enough space in output buffer - if((pbOutBuffer + NumberOfNonZeros + 1) >= pbOutBufferEnd) - return; - - // Put marker that means "Several nonzero bytes" - *pbOutBuffer++ = (unsigned char)(0x80 | (NumberOfNonZeros - 1)); - memcpy(pbOutBuffer, pbInBuffer, NumberOfNonZeros); - - // Adjust pointers - pbOutBuffer += NumberOfNonZeros; - pbInBuffer += NumberOfNonZeros; - } - } - - // Now flush all zero bytes - while(NumberOfZeros > 0x85) - { - // Do we have at least 2 bytes in the output buffer ? - if((pbOutBuffer + 1) >= pbOutBufferEnd) - return; - - // Put marker that means "0x82 zeros" - *pbOutBuffer++ = 0x7F; - - // Adjust zero counter and input pointer - NumberOfZeros -= 0x82; - pbInBuffer += 0x82; - } - - // If we got more than 0x82 zeros, flush 3 of them now - if(NumberOfZeros > 0x82) - { - // Do we have at least 2 bytes in the output buffer ? - if((pbOutBuffer + 1) >= pbOutBufferEnd) - return; - - // Put marker that means "0x03 zeros" - *pbOutBuffer++ = 0; - - // Adjust zero counter and input pointer - NumberOfZeros -= 0x03; - pbInBuffer += 0x03; - } - - // Is there at least three zeros ? - if(NumberOfZeros >= 3) - { - // Do we have at least 2 bytes in the output buffer ? - if((pbOutBuffer + 1) >= pbOutBufferEnd) - return; - - // Put marker that means "Several zeros" - *pbOutBuffer++ = (unsigned char)(NumberOfZeros - 3); - - // Adjust pointer - pbInBuffer += NumberOfZeros; - } - } - - // Flush last three bytes - if(pbInBuffer < pbInBufferEnd) - { - pbInBuffPtr = pbInBuffer; - - for(;;) - { - if(*pbInBuffPtr++ != 0) - { - // Get number of bytes remaining - NumberOfNonZeros = (pbInBufferEnd - pbInBuffer); - - // Not enough space in the output buffer ==> exit - if((pbOutBuffer + NumberOfNonZeros + 1) >= pbOutBufferEnd) - return; - - // Terminate with a marker that means "0x80 of nonzeros" - *pbOutBuffer++ = 0xFF; - memcpy(pbOutBuffer, pbInBuffer, NumberOfNonZeros); - - // Adjust pointer - pbOutBuffer += NumberOfNonZeros; - break; - } - else - { - // Is there are more chars in the input buffer - if(pbInBuffPtr < pbInBufferEnd) - continue; - - // If the compression will not compress it by even 1 byte, do nothing - if((pbOutBuffer + 1) >= pbOutBufferEnd) - return; - - // Terminate with a chunk that means "0x82 of zeros" - *pbOutBuffer++ = 0x7F; - break; - } - } - } - - // Out the length of the output buffer - *pcbOutBuffer = (int)(pbOutBuffer - pbOutBuffer0); -} - -int DecompressSparse(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer) -{ - unsigned char * pbInBufferEnd = (unsigned char *)pvInBuffer + cbInBuffer; - unsigned char * pbOutBuffer = (unsigned char *)pvOutBuffer; - unsigned char * pbInBuffer = (unsigned char *)pvInBuffer; - unsigned int cbChunkSize; - unsigned int cbOutBuffer = 0; - unsigned int OneByte; - - // Don't decompress anything that is shorter than 5 bytes - if(cbInBuffer < 5) - return 0; - - // Get the 32-bits from the input stream - OneByte = *pbInBuffer++; - cbOutBuffer |= (OneByte << 0x18); - OneByte = *pbInBuffer++; - cbOutBuffer |= (OneByte << 0x10); - OneByte = *pbInBuffer++; - cbOutBuffer |= (OneByte << 0x08); - OneByte = *pbInBuffer++; - cbOutBuffer |= (OneByte << 0x00); - - // Verify the size of the stream against the output buffer size - if(cbOutBuffer > (unsigned int)*pcbOutBuffer) - return 0; - - // Put the output size to the buffer - *pcbOutBuffer = cbOutBuffer; - - // Process the input buffer - while(pbInBuffer < pbInBufferEnd) - { - // Get (next) byte from the stream - OneByte = *pbInBuffer++; - - // If highest bit, it means that that normal data follow - if(OneByte & 0x80) - { - cbChunkSize = (OneByte & 0x7F) + 1; - cbChunkSize = (cbChunkSize < cbOutBuffer) ? cbChunkSize : cbOutBuffer; - memcpy(pbOutBuffer, pbInBuffer, cbChunkSize); - pbInBuffer += cbChunkSize; - } - else - { - cbChunkSize = (OneByte & 0x7F) + 3; - cbChunkSize = (cbChunkSize < cbOutBuffer) ? cbChunkSize : cbOutBuffer; - memset(pbOutBuffer, 0, cbChunkSize); - } - - // Increment output buffer pointer - pbOutBuffer += cbChunkSize; - cbOutBuffer -= cbChunkSize; - } - - return 1; -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/sparse/sparse.h b/app/jni/src/libultraship/extern/StormLib/src/sparse/sparse.h deleted file mode 100644 index 12f62b5..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/sparse/sparse.h +++ /dev/null @@ -1,17 +0,0 @@ -/*****************************************************************************/ -/* sparse.h Copyright (c) Ladislav Zezula 2010 */ -/*---------------------------------------------------------------------------*/ -/* implementation of Sparse compression, used in Starcraft II */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 05.03.10 1.00 Lad The first version of sparse.h */ -/*****************************************************************************/ - -#ifndef __SPARSE_H__ -#define __SPARSE_H__ - -void CompressSparse(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer); -int DecompressSparse(void * pvOutBuffer, int * pcbOutBuffer, void * pvInBuffer, int cbInBuffer); - -#endif // __SPARSE_H__ diff --git a/app/jni/src/libultraship/extern/StormLib/src/wdk/sources-cpp.cpp b/app/jni/src/libultraship/extern/StormLib/src/wdk/sources-cpp.cpp deleted file mode 100644 index f289975..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/wdk/sources-cpp.cpp +++ /dev/null @@ -1,26 +0,0 @@ -// This is a source file for WDK build of StormLib -// It is copied to the root folder during the build process - -#include "src\adpcm\adpcm.cpp" -#include "src\huffman\huff.cpp" -#include "src\sparse\sparse.cpp" - -#include "src\FileStream.cpp" -#include "src\SBaseCommon.cpp" -#include "src\SBaseDumpData.cpp" -#include "src\SBaseFileTable.cpp" -#include "src\SBaseSubTypes.cpp" -#include "src\SCompression.cpp" -#include "src\SFileAddFile.cpp" -#include "src\SFileAttributes.cpp" -#include "src\SFileCompactArchive.cpp" -#include "src\SFileCreateArchive.cpp" -#include "src\SFileExtractFile.cpp" -#include "src\SFileFindFile.cpp" -#include "src\SFileGetFileInfo.cpp" -#include "src\SFileListFile.cpp" -#include "src\SFileOpenArchive.cpp" -#include "src\SFileOpenFileEx.cpp" -#include "src\SFilePatchArchives.cpp" -#include "src\SFileReadFile.cpp" -#include "src\SFileVerify.cpp" diff --git a/app/jni/src/libultraship/extern/StormLib/src/wdk/sources-wdk-bzip2.c b/app/jni/src/libultraship/extern/StormLib/src/wdk/sources-wdk-bzip2.c deleted file mode 100644 index 74cf92a..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/wdk/sources-wdk-bzip2.c +++ /dev/null @@ -1,13 +0,0 @@ -// This is a source file for WDK build of StormLib -// It is copied to the root folder during the build process - -#pragma warning(disable: 4242) // '=' : conversion from 'Int32' to 'UChar', possible loss of data -#pragma warning(disable: 4244) // '=' : conversion from '__int64' to 'Int32', possible loss of data - -#include "src\bzip2\blocksort.c" -#include "src\bzip2\bzlib.c" -#include "src\bzip2\compress.c" -#include "src\bzip2\crctable.c" -#include "src\bzip2\decompress.c" -#include "src\bzip2\huffman.c" -#include "src\bzip2\randtable.c" diff --git a/app/jni/src/libultraship/extern/StormLib/src/wdk/sources-wdk-ltc.c b/app/jni/src/libultraship/extern/StormLib/src/wdk/sources-wdk-ltc.c deleted file mode 100644 index 7a7f90c..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/wdk/sources-wdk-ltc.c +++ /dev/null @@ -1,4 +0,0 @@ -// This is a source file for WDK build of StormLib -// It is copied to the root folder during the build process - -#include "src\libtomcrypt\src\math\ltm_desc.c" diff --git a/app/jni/src/libultraship/extern/StormLib/src/wdk/sources-wdk-lzma.c b/app/jni/src/libultraship/extern/StormLib/src/wdk/sources-wdk-lzma.c deleted file mode 100644 index 1fe46ee..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/wdk/sources-wdk-lzma.c +++ /dev/null @@ -1,8 +0,0 @@ -// This is a source file for WDK build of StormLib -// It is copied to the root folder during the build process - -#include "src\lzma\C\LzFind.c" -#include "src\lzma\C\LzFindMt.c" -#include "src\lzma\C\LzmaDec.c" -#include "src\lzma\C\LzmaEnc.c" -#include "src\lzma\C\Threads.c" diff --git a/app/jni/src/libultraship/extern/StormLib/src/wdk/sources-wdk-misc.c b/app/jni/src/libultraship/extern/StormLib/src/wdk/sources-wdk-misc.c deleted file mode 100644 index d1c36f0..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/wdk/sources-wdk-misc.c +++ /dev/null @@ -1,6 +0,0 @@ -// This is a source file for WDK build of StormLib -// It is copied to the root folder during the build process - -#include "src\jenkins\lookup3.c" -#include "src\pklib\explode.c" -#include "src\pklib\implode.c" diff --git a/app/jni/src/libultraship/extern/StormLib/src/wdk/sources-wdk-tomcrypt.c b/app/jni/src/libultraship/extern/StormLib/src/wdk/sources-wdk-tomcrypt.c deleted file mode 100644 index 60453d6..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/wdk/sources-wdk-tomcrypt.c +++ /dev/null @@ -1,82 +0,0 @@ -// This is a source file for WDK build of StormLib -// It is copied to the root folder during the build process - -#pragma warning(disable:4242) // der_decode_ia5_string.c(84) : warning C4242: '=' : conversion from 'int' to 'unsigned char', possible loss of data - -#include "src\libtomcrypt\src\hashes\hash_memory.c" -#include "src\libtomcrypt\src\hashes\md5.c" -#include "src\libtomcrypt\src\hashes\sha1.c" -#include "src\libtomcrypt\src\math\multi.c" -#include "src\libtomcrypt\src\math\rand_prime.c" -#include "src\libtomcrypt\src\misc\base64_decode.c" -#include "src\libtomcrypt\src\misc\crypt_argchk.c" -#include "src\libtomcrypt\src\misc\crypt_find_hash.c" -#include "src\libtomcrypt\src\misc\crypt_find_prng.c" -#include "src\libtomcrypt\src\misc\crypt_hash_descriptor.c" -#include "src\libtomcrypt\src\misc\crypt_hash_is_valid.c" -#include "src\libtomcrypt\src\misc\crypt_libc.c" -#include "src\libtomcrypt\src\misc\crypt_ltc_mp_descriptor.c" -#include "src\libtomcrypt\src\misc\crypt_prng_descriptor.c" -#include "src\libtomcrypt\src\misc\crypt_prng_is_valid.c" -#include "src\libtomcrypt\src\misc\crypt_register_hash.c" -#include "src\libtomcrypt\src\misc\crypt_register_prng.c" -#include "src\libtomcrypt\src\misc\zeromem.c" -#include "src\libtomcrypt\src\pk\asn1\der_decode_bit_string.c" -#include "src\libtomcrypt\src\pk\asn1\der_decode_boolean.c" -#include "src\libtomcrypt\src\pk\asn1\der_decode_choice.c" -#include "src\libtomcrypt\src\pk\asn1\der_decode_ia5_string.c" -#include "src\libtomcrypt\src\pk\asn1\der_decode_integer.c" -#include "src\libtomcrypt\src\pk\asn1\der_decode_object_identifier.c" -#include "src\libtomcrypt\src\pk\asn1\der_decode_octet_string.c" -#include "src\libtomcrypt\src\pk\asn1\der_decode_printable_string.c" -#include "src\libtomcrypt\src\pk\asn1\der_decode_sequence_ex.c" -#include "src\libtomcrypt\src\pk\asn1\der_decode_sequence_flexi.c" -#include "src\libtomcrypt\src\pk\asn1\der_decode_sequence_multi.c" -#include "src\libtomcrypt\src\pk\asn1\der_decode_short_integer.c" -#include "src\libtomcrypt\src\pk\asn1\der_decode_utctime.c" -#include "src\libtomcrypt\src\pk\asn1\der_decode_utf8_string.c" -#include "src\libtomcrypt\src\pk\asn1\der_encode_bit_string.c" -#include "src\libtomcrypt\src\pk\asn1\der_encode_boolean.c" -#include "src\libtomcrypt\src\pk\asn1\der_encode_ia5_string.c" -#include "src\libtomcrypt\src\pk\asn1\der_encode_integer.c" -#include "src\libtomcrypt\src\pk\asn1\der_encode_object_identifier.c" -#include "src\libtomcrypt\src\pk\asn1\der_encode_octet_string.c" -#include "src\libtomcrypt\src\pk\asn1\der_encode_printable_string.c" -#include "src\libtomcrypt\src\pk\asn1\der_encode_sequence_ex.c" -#include "src\libtomcrypt\src\pk\asn1\der_encode_sequence_multi.c" -#include "src\libtomcrypt\src\pk\asn1\der_encode_set.c" -#include "src\libtomcrypt\src\pk\asn1\der_encode_setof.c" -#include "src\libtomcrypt\src\pk\asn1\der_encode_short_integer.c" -#include "src\libtomcrypt\src\pk\asn1\der_encode_utctime.c" -#include "src\libtomcrypt\src\pk\asn1\der_encode_utf8_string.c" -#include "src\libtomcrypt\src\pk\asn1\der_length_bit_string.c" -#include "src\libtomcrypt\src\pk\asn1\der_length_boolean.c" -#include "src\libtomcrypt\src\pk\asn1\der_length_ia5_string.c" -#include "src\libtomcrypt\src\pk\asn1\der_length_integer.c" -#include "src\libtomcrypt\src\pk\asn1\der_length_object_identifier.c" -#include "src\libtomcrypt\src\pk\asn1\der_length_octet_string.c" -#include "src\libtomcrypt\src\pk\asn1\der_length_printable_string.c" -#include "src\libtomcrypt\src\pk\asn1\der_length_sequence.c" -#include "src\libtomcrypt\src\pk\asn1\der_length_short_integer.c" -#include "src\libtomcrypt\src\pk\asn1\der_length_utctime.c" -#include "src\libtomcrypt\src\pk\asn1\der_length_utf8_string.c" -#include "src\libtomcrypt\src\pk\asn1\der_sequence_free.c" -#include "src\libtomcrypt\src\pk\ecc\ltc_ecc_map.c" -#include "src\libtomcrypt\src\pk\ecc\ltc_ecc_mul2add.c" -#include "src\libtomcrypt\src\pk\ecc\ltc_ecc_mulmod.c" -#include "src\libtomcrypt\src\pk\ecc\ltc_ecc_points.c" -#include "src\libtomcrypt\src\pk\ecc\ltc_ecc_projective_add_point.c" -#include "src\libtomcrypt\src\pk\ecc\ltc_ecc_projective_dbl_point.c" -#include "src\libtomcrypt\src\pk\pkcs1\pkcs_1_mgf1.c" -#include "src\libtomcrypt\src\pk\pkcs1\pkcs_1_oaep_decode.c" -#include "src\libtomcrypt\src\pk\pkcs1\pkcs_1_pss_decode.c" -#include "src\libtomcrypt\src\pk\pkcs1\pkcs_1_pss_encode.c" -#include "src\libtomcrypt\src\pk\pkcs1\pkcs_1_v1_5_decode.c" -#include "src\libtomcrypt\src\pk\pkcs1\pkcs_1_v1_5_encode.c" -#include "src\libtomcrypt\src\pk\rsa\rsa_exptmod.c" -#include "src\libtomcrypt\src\pk\rsa\rsa_free.c" -#include "src\libtomcrypt\src\pk\rsa\rsa_import.c" -#include "src\libtomcrypt\src\pk\rsa\rsa_make_key.c" -#include "src\libtomcrypt\src\pk\rsa\rsa_sign_hash.c" -#include "src\libtomcrypt\src\pk\rsa\rsa_verify_hash.c" -#include "src\libtomcrypt\src\pk\rsa\rsa_verify_simple.c" diff --git a/app/jni/src/libultraship/extern/StormLib/src/wdk/sources-wdk-tommath.c b/app/jni/src/libultraship/extern/StormLib/src/wdk/sources-wdk-tommath.c deleted file mode 100644 index 78e86a2..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/wdk/sources-wdk-tommath.c +++ /dev/null @@ -1,124 +0,0 @@ -// This is a source file for WDK build of StormLib -// It is copied to the root folder during the build process - -#pragma warning(disable:4334) // warning C4334: '<<' : result of 32-bit shift implicitly converted to 64 bits (was 64-bit shift intended?) - -#include "src\libtommath\bn_fast_mp_invmod.c" -#include "src\libtommath\bn_fast_mp_montgomery_reduce.c" -#include "src\libtommath\bn_fast_s_mp_mul_digs.c" -#include "src\libtommath\bn_fast_s_mp_mul_high_digs.c" -#include "src\libtommath\bn_fast_s_mp_sqr.c" -#include "src\libtommath\bn_mp_2expt.c" -#include "src\libtommath\bn_mp_abs.c" -#include "src\libtommath\bn_mp_add.c" -#include "src\libtommath\bn_mp_add_d.c" -#include "src\libtommath\bn_mp_addmod.c" -#include "src\libtommath\bn_mp_and.c" -#include "src\libtommath\bn_mp_clamp.c" -#include "src\libtommath\bn_mp_clear.c" -#include "src\libtommath\bn_mp_clear_multi.c" -#include "src\libtommath\bn_mp_cmp.c" -#include "src\libtommath\bn_mp_cmp_d.c" -#include "src\libtommath\bn_mp_cmp_mag.c" -#include "src\libtommath\bn_mp_cnt_lsb.c" -#include "src\libtommath\bn_mp_copy.c" -#include "src\libtommath\bn_mp_count_bits.c" -#include "src\libtommath\bn_mp_div.c" -#include "src\libtommath\bn_mp_div_2.c" -#include "src\libtommath\bn_mp_div_2d.c" -#include "src\libtommath\bn_mp_div_3.c" -#include "src\libtommath\bn_mp_div_d.c" -#include "src\libtommath\bn_mp_dr_is_modulus.c" -#include "src\libtommath\bn_mp_dr_reduce.c" -#include "src\libtommath\bn_mp_dr_setup.c" -#include "src\libtommath\bn_mp_exch.c" -#include "src\libtommath\bn_mp_expt_d.c" -#include "src\libtommath\bn_mp_exptmod.c" -#include "src\libtommath\bn_mp_exptmod_fast.c" -#include "src\libtommath\bn_mp_exteuclid.c" -#include "src\libtommath\bn_mp_fread.c" -#include "src\libtommath\bn_mp_fwrite.c" -#include "src\libtommath\bn_mp_gcd.c" -#include "src\libtommath\bn_mp_get_int.c" -#include "src\libtommath\bn_mp_grow.c" -#include "src\libtommath\bn_mp_init.c" -#include "src\libtommath\bn_mp_init_copy.c" -#include "src\libtommath\bn_mp_init_multi.c" -#include "src\libtommath\bn_mp_init_set.c" -#include "src\libtommath\bn_mp_init_set_int.c" -#include "src\libtommath\bn_mp_init_size.c" -#include "src\libtommath\bn_mp_invmod.c" -#include "src\libtommath\bn_mp_invmod_slow.c" -#include "src\libtommath\bn_mp_is_square.c" -#include "src\libtommath\bn_mp_jacobi.c" -#include "src\libtommath\bn_mp_karatsuba_mul.c" -#include "src\libtommath\bn_mp_karatsuba_sqr.c" -#include "src\libtommath\bn_mp_lcm.c" -#include "src\libtommath\bn_mp_lshd.c" -#include "src\libtommath\bn_mp_mod.c" -#include "src\libtommath\bn_mp_mod_2d.c" -#include "src\libtommath\bn_mp_mod_d.c" -#include "src\libtommath\bn_mp_montgomery_calc_normalization.c" -#include "src\libtommath\bn_mp_montgomery_reduce.c" -#include "src\libtommath\bn_mp_montgomery_setup.c" -#include "src\libtommath\bn_mp_mul.c" -#include "src\libtommath\bn_mp_mul_2.c" -#include "src\libtommath\bn_mp_mul_2d.c" -#include "src\libtommath\bn_mp_mul_d.c" -#include "src\libtommath\bn_mp_mulmod.c" -#include "src\libtommath\bn_mp_n_root.c" -#include "src\libtommath\bn_mp_neg.c" -#include "src\libtommath\bn_mp_or.c" -#include "src\libtommath\bn_mp_prime_fermat.c" -#include "src\libtommath\bn_mp_prime_is_divisible.c" -#include "src\libtommath\bn_mp_prime_is_prime.c" -#include "src\libtommath\bn_mp_prime_miller_rabin.c" -#include "src\libtommath\bn_mp_prime_next_prime.c" -#include "src\libtommath\bn_mp_prime_rabin_miller_trials.c" -#include "src\libtommath\bn_mp_prime_random_ex.c" -#include "src\libtommath\bn_mp_radix_size.c" -#include "src\libtommath\bn_mp_radix_smap.c" -#include "src\libtommath\bn_mp_rand.c" -#include "src\libtommath\bn_mp_read_radix.c" -#include "src\libtommath\bn_mp_read_signed_bin.c" -#include "src\libtommath\bn_mp_read_unsigned_bin.c" -#include "src\libtommath\bn_mp_reduce.c" -#include "src\libtommath\bn_mp_reduce_2k.c" -#include "src\libtommath\bn_mp_reduce_2k_l.c" -#include "src\libtommath\bn_mp_reduce_2k_setup.c" -#include "src\libtommath\bn_mp_reduce_2k_setup_l.c" -#include "src\libtommath\bn_mp_reduce_is_2k.c" -#include "src\libtommath\bn_mp_reduce_is_2k_l.c" -#include "src\libtommath\bn_mp_reduce_setup.c" -#include "src\libtommath\bn_mp_rshd.c" -#include "src\libtommath\bn_mp_set.c" -#include "src\libtommath\bn_mp_set_int.c" -#include "src\libtommath\bn_mp_shrink.c" -#include "src\libtommath\bn_mp_signed_bin_size.c" -#include "src\libtommath\bn_mp_sqr.c" -#include "src\libtommath\bn_mp_sqrmod.c" -#include "src\libtommath\bn_mp_sqrt.c" -#include "src\libtommath\bn_mp_sub.c" -#include "src\libtommath\bn_mp_sub_d.c" -#include "src\libtommath\bn_mp_submod.c" -#include "src\libtommath\bn_mp_to_signed_bin.c" -#include "src\libtommath\bn_mp_to_signed_bin_n.c" -#include "src\libtommath\bn_mp_to_unsigned_bin.c" -#include "src\libtommath\bn_mp_to_unsigned_bin_n.c" -#include "src\libtommath\bn_mp_toom_mul.c" -#include "src\libtommath\bn_mp_toom_sqr.c" -#include "src\libtommath\bn_mp_toradix.c" -#include "src\libtommath\bn_mp_toradix_n.c" -#include "src\libtommath\bn_mp_unsigned_bin_size.c" -#include "src\libtommath\bn_mp_xor.c" -#include "src\libtommath\bn_mp_zero.c" -#include "src\libtommath\bn_prime_tab.c" -#include "src\libtommath\bn_reverse.c" -#include "src\libtommath\bn_s_mp_add.c" -#include "src\libtommath\bn_s_mp_exptmod.c" -#include "src\libtommath\bn_s_mp_mul_digs.c" -#include "src\libtommath\bn_s_mp_mul_high_digs.c" -#include "src\libtommath\bn_s_mp_sqr.c" -#include "src\libtommath\bn_s_mp_sub.c" -#include "src\libtommath\bncore.c" - diff --git a/app/jni/src/libultraship/extern/StormLib/src/wdk/sources-wdk-zlib.c b/app/jni/src/libultraship/extern/StormLib/src/wdk/sources-wdk-zlib.c deleted file mode 100644 index 2455a9a..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/wdk/sources-wdk-zlib.c +++ /dev/null @@ -1,21 +0,0 @@ -// This is a source file for WDK build of StormLib -// It is copied to the root folder during the build process - -#pragma warning(disable:4242) // deflate.c(1693) : warning C4242: '=' : conversion from 'unsigned int' to 'Bytef', possible loss of data - -#define NO_DUMMY_DECL -#define NO_GZIP -#include "src\zlib\adler32.c" -#undef DO1 -#undef DO8 -#undef MIN -#include "src\zlib\compress.c" -#include "src\zlib\crc32.c" -#include "src\zlib\deflate.c" -#include "src\zlib\trees.c" -#include "src\zlib\zutil.c" - -#undef COPY // Conflicting definition -#include "src\zlib\inflate.c" -#include "src\zlib\inffast.c" -#include "src\zlib\inftrees.c" diff --git a/app/jni/src/libultraship/extern/StormLib/src/zlib/adler32.c b/app/jni/src/libultraship/extern/StormLib/src/zlib/adler32.c deleted file mode 100644 index 65ad6a5..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/zlib/adler32.c +++ /dev/null @@ -1,169 +0,0 @@ -/* adler32.c -- compute the Adler-32 checksum of a data stream - * Copyright (C) 1995-2007 Mark Adler - * For conditions of distribution and use, see copyright notice in zlib.h - */ - -/* @(#) $Id$ */ - -#include "zutil.h" - -#define local static - -local uLong adler32_combine_(uLong adler1, uLong adler2, z_off64_t len2); - -#define BASE 65521UL /* largest prime smaller than 65536 */ -#define NMAX 5552 -/* NMAX is the largest n such that 255n(n+1)/2 + (n+1)(BASE-1) <= 2^32-1 */ - -#define DO1(buf,i) {adler += (buf)[i]; sum2 += adler;} -#define DO2(buf,i) DO1(buf,i); DO1(buf,i+1); -#define DO4(buf,i) DO2(buf,i); DO2(buf,i+2); -#define DO8(buf,i) DO4(buf,i); DO4(buf,i+4); -#define DO16(buf) DO8(buf,0); DO8(buf,8); - -/* use NO_DIVIDE if your processor does not do division in hardware */ -#ifdef NO_DIVIDE -# define MOD(a) \ - do { \ - if (a >= (BASE << 16)) a -= (BASE << 16); \ - if (a >= (BASE << 15)) a -= (BASE << 15); \ - if (a >= (BASE << 14)) a -= (BASE << 14); \ - if (a >= (BASE << 13)) a -= (BASE << 13); \ - if (a >= (BASE << 12)) a -= (BASE << 12); \ - if (a >= (BASE << 11)) a -= (BASE << 11); \ - if (a >= (BASE << 10)) a -= (BASE << 10); \ - if (a >= (BASE << 9)) a -= (BASE << 9); \ - if (a >= (BASE << 8)) a -= (BASE << 8); \ - if (a >= (BASE << 7)) a -= (BASE << 7); \ - if (a >= (BASE << 6)) a -= (BASE << 6); \ - if (a >= (BASE << 5)) a -= (BASE << 5); \ - if (a >= (BASE << 4)) a -= (BASE << 4); \ - if (a >= (BASE << 3)) a -= (BASE << 3); \ - if (a >= (BASE << 2)) a -= (BASE << 2); \ - if (a >= (BASE << 1)) a -= (BASE << 1); \ - if (a >= BASE) a -= BASE; \ - } while (0) -# define MOD4(a) \ - do { \ - if (a >= (BASE << 4)) a -= (BASE << 4); \ - if (a >= (BASE << 3)) a -= (BASE << 3); \ - if (a >= (BASE << 2)) a -= (BASE << 2); \ - if (a >= (BASE << 1)) a -= (BASE << 1); \ - if (a >= BASE) a -= BASE; \ - } while (0) -#else -# define MOD(a) a %= BASE -# define MOD4(a) a %= BASE -#endif - -/* ========================================================================= */ -uLong ZEXPORT adler32(adler, buf, len) - uLong adler; - const Bytef *buf; - uInt len; -{ - unsigned long sum2; - unsigned n; - - /* split Adler-32 into component sums */ - sum2 = (adler >> 16) & 0xffff; - adler &= 0xffff; - - /* in case user likes doing a byte at a time, keep it fast */ - if (len == 1) { - adler += buf[0]; - if (adler >= BASE) - adler -= BASE; - sum2 += adler; - if (sum2 >= BASE) - sum2 -= BASE; - return adler | (sum2 << 16); - } - - /* initial Adler-32 value (deferred check for len == 1 speed) */ - if (buf == Z_NULL) - return 1L; - - /* in case short lengths are provided, keep it somewhat fast */ - if (len < 16) { - while (len--) { - adler += *buf++; - sum2 += adler; - } - if (adler >= BASE) - adler -= BASE; - MOD4(sum2); /* only added so many BASE's */ - return adler | (sum2 << 16); - } - - /* do length NMAX blocks -- requires just one modulo operation */ - while (len >= NMAX) { - len -= NMAX; - n = NMAX / 16; /* NMAX is divisible by 16 */ - do { - DO16(buf); /* 16 sums unrolled */ - buf += 16; - } while (--n); - MOD(adler); - MOD(sum2); - } - - /* do remaining bytes (less than NMAX, still just one modulo) */ - if (len) { /* avoid modulos if none remaining */ - while (len >= 16) { - len -= 16; - DO16(buf); - buf += 16; - } - while (len--) { - adler += *buf++; - sum2 += adler; - } - MOD(adler); - MOD(sum2); - } - - /* return recombined sums */ - return adler | (sum2 << 16); -} - -/* ========================================================================= */ -local uLong adler32_combine_(adler1, adler2, len2) - uLong adler1; - uLong adler2; - z_off64_t len2; -{ - unsigned long sum1; - unsigned long sum2; - unsigned rem; - - /* the derivation of this formula is left as an exercise for the reader */ - rem = (unsigned)(len2 % BASE); - sum1 = adler1 & 0xffff; - sum2 = rem * sum1; - MOD(sum2); - sum1 += (adler2 & 0xffff) + BASE - 1; - sum2 += ((adler1 >> 16) & 0xffff) + ((adler2 >> 16) & 0xffff) + BASE - rem; - if (sum1 >= BASE) sum1 -= BASE; - if (sum1 >= BASE) sum1 -= BASE; - if (sum2 >= (BASE << 1)) sum2 -= (BASE << 1); - if (sum2 >= BASE) sum2 -= BASE; - return sum1 | (sum2 << 16); -} - -/* ========================================================================= */ -uLong ZEXPORT adler32_combine(adler1, adler2, len2) - uLong adler1; - uLong adler2; - z_off_t len2; -{ - return adler32_combine_(adler1, adler2, len2); -} - -uLong ZEXPORT adler32_combine64(adler1, adler2, len2) - uLong adler1; - uLong adler2; - z_off64_t len2; -{ - return adler32_combine_(adler1, adler2, len2); -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/zlib/compress.c b/app/jni/src/libultraship/extern/StormLib/src/zlib/compress.c deleted file mode 100644 index ea4dfbe..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/zlib/compress.c +++ /dev/null @@ -1,80 +0,0 @@ -/* compress.c -- compress a memory buffer - * Copyright (C) 1995-2005 Jean-loup Gailly. - * For conditions of distribution and use, see copyright notice in zlib.h - */ - -/* @(#) $Id$ */ - -#define ZLIB_INTERNAL -#include "zlib.h" - -/* =========================================================================== - Compresses the source buffer into the destination buffer. The level - parameter has the same meaning as in deflateInit. sourceLen is the byte - length of the source buffer. Upon entry, destLen is the total size of the - destination buffer, which must be at least 0.1% larger than sourceLen plus - 12 bytes. Upon exit, destLen is the actual size of the compressed buffer. - - compress2 returns Z_OK if success, Z_MEM_ERROR if there was not enough - memory, Z_BUF_ERROR if there was not enough room in the output buffer, - Z_STREAM_ERROR if the level parameter is invalid. -*/ -int ZEXPORT compress2 (dest, destLen, source, sourceLen, level) - Bytef *dest; - uLongf *destLen; - const Bytef *source; - uLong sourceLen; - int level; -{ - z_stream stream; - int err; - - stream.next_in = (Bytef*)source; - stream.avail_in = (uInt)sourceLen; -#ifdef MAXSEG_64K - /* Check for source > 64K on 16-bit machine: */ - if ((uLong)stream.avail_in != sourceLen) return Z_BUF_ERROR; -#endif - stream.next_out = dest; - stream.avail_out = (uInt)*destLen; - if ((uLong)stream.avail_out != *destLen) return Z_BUF_ERROR; - - stream.zalloc = (alloc_func)0; - stream.zfree = (free_func)0; - stream.opaque = (voidpf)0; - - err = deflateInit(&stream, level); - if (err != Z_OK) return err; - - err = deflate(&stream, Z_FINISH); - if (err != Z_STREAM_END) { - deflateEnd(&stream); - return err == Z_OK ? Z_BUF_ERROR : err; - } - *destLen = stream.total_out; - - err = deflateEnd(&stream); - return err; -} - -/* =========================================================================== - */ -int ZEXPORT compress (dest, destLen, source, sourceLen) - Bytef *dest; - uLongf *destLen; - const Bytef *source; - uLong sourceLen; -{ - return compress2(dest, destLen, source, sourceLen, Z_DEFAULT_COMPRESSION); -} - -/* =========================================================================== - If the default memLevel or windowBits for deflateInit() is changed, then - this function needs to be updated. - */ -uLong ZEXPORT compressBound (sourceLen) - uLong sourceLen; -{ - return sourceLen + (sourceLen >> 12) + (sourceLen >> 14) + - (sourceLen >> 25) + 13; -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/zlib/compress_zlib.c b/app/jni/src/libultraship/extern/StormLib/src/zlib/compress_zlib.c deleted file mode 100644 index 46e5061..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/zlib/compress_zlib.c +++ /dev/null @@ -1,5 +0,0 @@ -// Some compilers (e.g. Visual Studio 2012) don't like the name conflict between -// zlib\compress.c and bzip2\compress.c. This file is plain wrapper for compress.c -// in order to create obj file with a different name. - -#include "compress.c" diff --git a/app/jni/src/libultraship/extern/StormLib/src/zlib/crc32.c b/app/jni/src/libultraship/extern/StormLib/src/zlib/crc32.c deleted file mode 100644 index 91be372..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/zlib/crc32.c +++ /dev/null @@ -1,442 +0,0 @@ -/* crc32.c -- compute the CRC-32 of a data stream - * Copyright (C) 1995-2006, 2010 Mark Adler - * For conditions of distribution and use, see copyright notice in zlib.h - * - * Thanks to Rodney Brown for his contribution of faster - * CRC methods: exclusive-oring 32 bits of data at a time, and pre-computing - * tables for updating the shift register in one step with three exclusive-ors - * instead of four steps with four exclusive-ors. This results in about a - * factor of two increase in speed on a Power PC G4 (PPC7455) using gcc -O3. - */ - -/* @(#) $Id$ */ - -/* - Note on the use of DYNAMIC_CRC_TABLE: there is no mutex or semaphore - protection on the static variables used to control the first-use generation - of the crc tables. Therefore, if you #define DYNAMIC_CRC_TABLE, you should - first call get_crc_table() to initialize the tables before allowing more than - one thread to use crc32(). - */ - -#ifdef MAKECRCH -# include -# ifndef DYNAMIC_CRC_TABLE -# define DYNAMIC_CRC_TABLE -# endif /* !DYNAMIC_CRC_TABLE */ -#endif /* MAKECRCH */ - -#include "zutil.h" /* for STDC and FAR definitions */ - -#define local static - -/* Find a four-byte integer type for crc32_little() and crc32_big(). */ -#ifndef NOBYFOUR -# ifdef STDC /* need ANSI C limits.h to determine sizes */ -# include -# define BYFOUR -# if (UINT_MAX == 0xffffffffUL) - typedef unsigned int u4; -# else -# if (ULONG_MAX == 0xffffffffUL) - typedef unsigned long u4; -# else -# if (USHRT_MAX == 0xffffffffUL) - typedef unsigned short u4; -# else -# undef BYFOUR /* can't find a four-byte integer type! */ -# endif -# endif -# endif -# endif /* STDC */ -#endif /* !NOBYFOUR */ - -/* Definitions for doing the crc four data bytes at a time. */ -#ifdef BYFOUR -# define REV(w) ((((w)>>24)&0xff)+(((w)>>8)&0xff00)+ \ - (((w)&0xff00)<<8)+(((w)&0xff)<<24)) - local unsigned long crc32_little OF((unsigned long, - const unsigned char FAR *, unsigned)); - local unsigned long crc32_big OF((unsigned long, - const unsigned char FAR *, unsigned)); -# define TBLS 8 -#else -# define TBLS 1 -#endif /* BYFOUR */ - -/* Local functions for crc concatenation */ -local unsigned long gf2_matrix_times OF((unsigned long *mat, - unsigned long vec)); -local void gf2_matrix_square OF((unsigned long *square, unsigned long *mat)); -local uLong crc32_combine_(uLong crc1, uLong crc2, z_off64_t len2); - - -#ifdef DYNAMIC_CRC_TABLE - -local volatile int crc_table_empty = 1; -local unsigned long FAR crc_table[TBLS][256]; -local void make_crc_table OF((void)); -#ifdef MAKECRCH - local void write_table OF((FILE *, const unsigned long FAR *)); -#endif /* MAKECRCH */ -/* - Generate tables for a byte-wise 32-bit CRC calculation on the polynomial: - x^32+x^26+x^23+x^22+x^16+x^12+x^11+x^10+x^8+x^7+x^5+x^4+x^2+x+1. - - Polynomials over GF(2) are represented in binary, one bit per coefficient, - with the lowest powers in the most significant bit. Then adding polynomials - is just exclusive-or, and multiplying a polynomial by x is a right shift by - one. If we call the above polynomial p, and represent a byte as the - polynomial q, also with the lowest power in the most significant bit (so the - byte 0xb1 is the polynomial x^7+x^3+x+1), then the CRC is (q*x^32) mod p, - where a mod b means the remainder after dividing a by b. - - This calculation is done using the shift-register method of multiplying and - taking the remainder. The register is initialized to zero, and for each - incoming bit, x^32 is added mod p to the register if the bit is a one (where - x^32 mod p is p+x^32 = x^26+...+1), and the register is multiplied mod p by - x (which is shifting right by one and adding x^32 mod p if the bit shifted - out is a one). We start with the highest power (least significant bit) of - q and repeat for all eight bits of q. - - The first table is simply the CRC of all possible eight bit values. This is - all the information needed to generate CRCs on data a byte at a time for all - combinations of CRC register values and incoming bytes. The remaining tables - allow for word-at-a-time CRC calculation for both big-endian and little- - endian machines, where a word is four bytes. -*/ -local void make_crc_table() -{ - unsigned long c; - int n, k; - unsigned long poly; /* polynomial exclusive-or pattern */ - /* terms of polynomial defining this crc (except x^32): */ - static volatile int first = 1; /* flag to limit concurrent making */ - static const unsigned char p[] = {0,1,2,4,5,7,8,10,11,12,16,22,23,26}; - - /* See if another task is already doing this (not thread-safe, but better - than nothing -- significantly reduces duration of vulnerability in - case the advice about DYNAMIC_CRC_TABLE is ignored) */ - if (first) { - first = 0; - - /* make exclusive-or pattern from polynomial (0xedb88320UL) */ - poly = 0UL; - for (n = 0; n < sizeof(p)/sizeof(unsigned char); n++) - poly |= 1UL << (31 - p[n]); - - /* generate a crc for every 8-bit value */ - for (n = 0; n < 256; n++) { - c = (unsigned long)n; - for (k = 0; k < 8; k++) - c = c & 1 ? poly ^ (c >> 1) : c >> 1; - crc_table[0][n] = c; - } - -#ifdef BYFOUR - /* generate crc for each value followed by one, two, and three zeros, - and then the byte reversal of those as well as the first table */ - for (n = 0; n < 256; n++) { - c = crc_table[0][n]; - crc_table[4][n] = REV(c); - for (k = 1; k < 4; k++) { - c = crc_table[0][c & 0xff] ^ (c >> 8); - crc_table[k][n] = c; - crc_table[k + 4][n] = REV(c); - } - } -#endif /* BYFOUR */ - - crc_table_empty = 0; - } - else { /* not first */ - /* wait for the other guy to finish (not efficient, but rare) */ - while (crc_table_empty) - ; - } - -#ifdef MAKECRCH - /* write out CRC tables to crc32.h */ - { - FILE *out; - - out = fopen("crc32.h", "w"); - if (out == NULL) return; - fprintf(out, "/* crc32.h -- tables for rapid CRC calculation\n"); - fprintf(out, " * Generated automatically by crc32.c\n */\n\n"); - fprintf(out, "local const unsigned long FAR "); - fprintf(out, "crc_table[TBLS][256] =\n{\n {\n"); - write_table(out, crc_table[0]); -# ifdef BYFOUR - fprintf(out, "#ifdef BYFOUR\n"); - for (k = 1; k < 8; k++) { - fprintf(out, " },\n {\n"); - write_table(out, crc_table[k]); - } - fprintf(out, "#endif\n"); -# endif /* BYFOUR */ - fprintf(out, " }\n};\n"); - fclose(out); - } -#endif /* MAKECRCH */ -} - -#ifdef MAKECRCH -local void write_table(out, table) - FILE *out; - const unsigned long FAR *table; -{ - int n; - - for (n = 0; n < 256; n++) - fprintf(out, "%s0x%08lxUL%s", n % 5 ? "" : " ", table[n], - n == 255 ? "\n" : (n % 5 == 4 ? ",\n" : ", ")); -} -#endif /* MAKECRCH */ - -#else /* !DYNAMIC_CRC_TABLE */ -/* ======================================================================== - * Tables of CRC-32s of all single-byte values, made by make_crc_table(). - */ -#include "crc32.h" -#endif /* DYNAMIC_CRC_TABLE */ - -/* ========================================================================= - * This function can be used by asm versions of crc32() - */ -const unsigned long FAR * ZEXPORT get_crc_table() -{ -#ifdef DYNAMIC_CRC_TABLE - if (crc_table_empty) - make_crc_table(); -#endif /* DYNAMIC_CRC_TABLE */ - return (const unsigned long FAR *)crc_table; -} - -/* ========================================================================= */ -#define DO1 crc = crc_table[0][((int)crc ^ (*buf++)) & 0xff] ^ (crc >> 8) -#define DO8 DO1; DO1; DO1; DO1; DO1; DO1; DO1; DO1 - -/* ========================================================================= */ -unsigned long ZEXPORT crc32(crc, buf, len) - unsigned long crc; - const unsigned char FAR *buf; - uInt len; -{ - if (buf == Z_NULL) return 0UL; - -#ifdef DYNAMIC_CRC_TABLE - if (crc_table_empty) - make_crc_table(); -#endif /* DYNAMIC_CRC_TABLE */ - -#ifdef BYFOUR - if (sizeof(void *) == sizeof(ptrdiff_t)) { - u4 endian; - - endian = 1; - if (*((unsigned char *)(&endian))) - return crc32_little(crc, buf, len); - else - return crc32_big(crc, buf, len); - } -#endif /* BYFOUR */ - crc = crc ^ 0xffffffffUL; - while (len >= 8) { - DO8; - len -= 8; - } - if (len) do { - DO1; - } while (--len); - return crc ^ 0xffffffffUL; -} - -#ifdef BYFOUR - -/* ========================================================================= */ -#define DOLIT4 c ^= *buf4++; \ - c = crc_table[3][c & 0xff] ^ crc_table[2][(c >> 8) & 0xff] ^ \ - crc_table[1][(c >> 16) & 0xff] ^ crc_table[0][c >> 24] -#define DOLIT32 DOLIT4; DOLIT4; DOLIT4; DOLIT4; DOLIT4; DOLIT4; DOLIT4; DOLIT4 - -/* ========================================================================= */ -local unsigned long crc32_little(crc, buf, len) - unsigned long crc; - const unsigned char FAR *buf; - unsigned len; -{ - register u4 c; - register const u4 FAR *buf4; - - c = (u4)crc; - c = ~c; - while (len && ((ptrdiff_t)buf & 3)) { - c = crc_table[0][(c ^ *buf++) & 0xff] ^ (c >> 8); - len--; - } - - buf4 = (const u4 FAR *)(const void FAR *)buf; - while (len >= 32) { - DOLIT32; - len -= 32; - } - while (len >= 4) { - DOLIT4; - len -= 4; - } - buf = (const unsigned char FAR *)buf4; - - if (len) do { - c = crc_table[0][(c ^ *buf++) & 0xff] ^ (c >> 8); - } while (--len); - c = ~c; - return (unsigned long)c; -} - -/* ========================================================================= */ -#define DOBIG4 c ^= *++buf4; \ - c = crc_table[4][c & 0xff] ^ crc_table[5][(c >> 8) & 0xff] ^ \ - crc_table[6][(c >> 16) & 0xff] ^ crc_table[7][c >> 24] -#define DOBIG32 DOBIG4; DOBIG4; DOBIG4; DOBIG4; DOBIG4; DOBIG4; DOBIG4; DOBIG4 - -/* ========================================================================= */ -local unsigned long crc32_big(crc, buf, len) - unsigned long crc; - const unsigned char FAR *buf; - unsigned len; -{ - register u4 c; - register const u4 FAR *buf4; - - c = REV((u4)crc); - c = ~c; - while (len && ((ptrdiff_t)buf & 3)) { - c = crc_table[4][(c >> 24) ^ *buf++] ^ (c << 8); - len--; - } - - buf4 = (const u4 FAR *)(const void FAR *)buf; - buf4--; - while (len >= 32) { - DOBIG32; - len -= 32; - } - while (len >= 4) { - DOBIG4; - len -= 4; - } - buf4++; - buf = (const unsigned char FAR *)buf4; - - if (len) do { - c = crc_table[4][(c >> 24) ^ *buf++] ^ (c << 8); - } while (--len); - c = ~c; - return (unsigned long)(REV(c)); -} - -#endif /* BYFOUR */ - -#define GF2_DIM 32 /* dimension of GF(2) vectors (length of CRC) */ - -/* ========================================================================= */ -local unsigned long gf2_matrix_times(mat, vec) - unsigned long *mat; - unsigned long vec; -{ - unsigned long sum; - - sum = 0; - while (vec) { - if (vec & 1) - sum ^= *mat; - vec >>= 1; - mat++; - } - return sum; -} - -/* ========================================================================= */ -local void gf2_matrix_square(square, mat) - unsigned long *square; - unsigned long *mat; -{ - int n; - - for (n = 0; n < GF2_DIM; n++) - square[n] = gf2_matrix_times(mat, mat[n]); -} - -/* ========================================================================= */ -local uLong crc32_combine_(crc1, crc2, len2) - uLong crc1; - uLong crc2; - z_off64_t len2; -{ - int n; - unsigned long row; - unsigned long even[GF2_DIM]; /* even-power-of-two zeros operator */ - unsigned long odd[GF2_DIM]; /* odd-power-of-two zeros operator */ - - /* degenerate case (also disallow negative lengths) */ - if (len2 <= 0) - return crc1; - - /* put operator for one zero bit in odd */ - odd[0] = 0xedb88320UL; /* CRC-32 polynomial */ - row = 1; - for (n = 1; n < GF2_DIM; n++) { - odd[n] = row; - row <<= 1; - } - - /* put operator for two zero bits in even */ - gf2_matrix_square(even, odd); - - /* put operator for four zero bits in odd */ - gf2_matrix_square(odd, even); - - /* apply len2 zeros to crc1 (first square will put the operator for one - zero byte, eight zero bits, in even) */ - do { - /* apply zeros operator for this bit of len2 */ - gf2_matrix_square(even, odd); - if (len2 & 1) - crc1 = gf2_matrix_times(even, crc1); - len2 >>= 1; - - /* if no more bits set, then done */ - if (len2 == 0) - break; - - /* another iteration of the loop with odd and even swapped */ - gf2_matrix_square(odd, even); - if (len2 & 1) - crc1 = gf2_matrix_times(odd, crc1); - len2 >>= 1; - - /* if no more bits set, then done */ - } while (len2 != 0); - - /* return combined crc */ - crc1 ^= crc2; - return crc1; -} - -/* ========================================================================= */ -uLong ZEXPORT crc32_combine(crc1, crc2, len2) - uLong crc1; - uLong crc2; - z_off_t len2; -{ - return crc32_combine_(crc1, crc2, len2); -} - -uLong ZEXPORT crc32_combine64(crc1, crc2, len2) - uLong crc1; - uLong crc2; - z_off64_t len2; -{ - return crc32_combine_(crc1, crc2, len2); -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/zlib/crc32.h b/app/jni/src/libultraship/extern/StormLib/src/zlib/crc32.h deleted file mode 100644 index 8053b61..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/zlib/crc32.h +++ /dev/null @@ -1,441 +0,0 @@ -/* crc32.h -- tables for rapid CRC calculation - * Generated automatically by crc32.c - */ - -local const unsigned long FAR crc_table[TBLS][256] = -{ - { - 0x00000000UL, 0x77073096UL, 0xee0e612cUL, 0x990951baUL, 0x076dc419UL, - 0x706af48fUL, 0xe963a535UL, 0x9e6495a3UL, 0x0edb8832UL, 0x79dcb8a4UL, - 0xe0d5e91eUL, 0x97d2d988UL, 0x09b64c2bUL, 0x7eb17cbdUL, 0xe7b82d07UL, - 0x90bf1d91UL, 0x1db71064UL, 0x6ab020f2UL, 0xf3b97148UL, 0x84be41deUL, - 0x1adad47dUL, 0x6ddde4ebUL, 0xf4d4b551UL, 0x83d385c7UL, 0x136c9856UL, - 0x646ba8c0UL, 0xfd62f97aUL, 0x8a65c9ecUL, 0x14015c4fUL, 0x63066cd9UL, - 0xfa0f3d63UL, 0x8d080df5UL, 0x3b6e20c8UL, 0x4c69105eUL, 0xd56041e4UL, - 0xa2677172UL, 0x3c03e4d1UL, 0x4b04d447UL, 0xd20d85fdUL, 0xa50ab56bUL, - 0x35b5a8faUL, 0x42b2986cUL, 0xdbbbc9d6UL, 0xacbcf940UL, 0x32d86ce3UL, - 0x45df5c75UL, 0xdcd60dcfUL, 0xabd13d59UL, 0x26d930acUL, 0x51de003aUL, - 0xc8d75180UL, 0xbfd06116UL, 0x21b4f4b5UL, 0x56b3c423UL, 0xcfba9599UL, - 0xb8bda50fUL, 0x2802b89eUL, 0x5f058808UL, 0xc60cd9b2UL, 0xb10be924UL, - 0x2f6f7c87UL, 0x58684c11UL, 0xc1611dabUL, 0xb6662d3dUL, 0x76dc4190UL, - 0x01db7106UL, 0x98d220bcUL, 0xefd5102aUL, 0x71b18589UL, 0x06b6b51fUL, - 0x9fbfe4a5UL, 0xe8b8d433UL, 0x7807c9a2UL, 0x0f00f934UL, 0x9609a88eUL, - 0xe10e9818UL, 0x7f6a0dbbUL, 0x086d3d2dUL, 0x91646c97UL, 0xe6635c01UL, - 0x6b6b51f4UL, 0x1c6c6162UL, 0x856530d8UL, 0xf262004eUL, 0x6c0695edUL, - 0x1b01a57bUL, 0x8208f4c1UL, 0xf50fc457UL, 0x65b0d9c6UL, 0x12b7e950UL, - 0x8bbeb8eaUL, 0xfcb9887cUL, 0x62dd1ddfUL, 0x15da2d49UL, 0x8cd37cf3UL, - 0xfbd44c65UL, 0x4db26158UL, 0x3ab551ceUL, 0xa3bc0074UL, 0xd4bb30e2UL, - 0x4adfa541UL, 0x3dd895d7UL, 0xa4d1c46dUL, 0xd3d6f4fbUL, 0x4369e96aUL, - 0x346ed9fcUL, 0xad678846UL, 0xda60b8d0UL, 0x44042d73UL, 0x33031de5UL, - 0xaa0a4c5fUL, 0xdd0d7cc9UL, 0x5005713cUL, 0x270241aaUL, 0xbe0b1010UL, - 0xc90c2086UL, 0x5768b525UL, 0x206f85b3UL, 0xb966d409UL, 0xce61e49fUL, - 0x5edef90eUL, 0x29d9c998UL, 0xb0d09822UL, 0xc7d7a8b4UL, 0x59b33d17UL, - 0x2eb40d81UL, 0xb7bd5c3bUL, 0xc0ba6cadUL, 0xedb88320UL, 0x9abfb3b6UL, - 0x03b6e20cUL, 0x74b1d29aUL, 0xead54739UL, 0x9dd277afUL, 0x04db2615UL, - 0x73dc1683UL, 0xe3630b12UL, 0x94643b84UL, 0x0d6d6a3eUL, 0x7a6a5aa8UL, - 0xe40ecf0bUL, 0x9309ff9dUL, 0x0a00ae27UL, 0x7d079eb1UL, 0xf00f9344UL, - 0x8708a3d2UL, 0x1e01f268UL, 0x6906c2feUL, 0xf762575dUL, 0x806567cbUL, - 0x196c3671UL, 0x6e6b06e7UL, 0xfed41b76UL, 0x89d32be0UL, 0x10da7a5aUL, - 0x67dd4accUL, 0xf9b9df6fUL, 0x8ebeeff9UL, 0x17b7be43UL, 0x60b08ed5UL, - 0xd6d6a3e8UL, 0xa1d1937eUL, 0x38d8c2c4UL, 0x4fdff252UL, 0xd1bb67f1UL, - 0xa6bc5767UL, 0x3fb506ddUL, 0x48b2364bUL, 0xd80d2bdaUL, 0xaf0a1b4cUL, - 0x36034af6UL, 0x41047a60UL, 0xdf60efc3UL, 0xa867df55UL, 0x316e8eefUL, - 0x4669be79UL, 0xcb61b38cUL, 0xbc66831aUL, 0x256fd2a0UL, 0x5268e236UL, - 0xcc0c7795UL, 0xbb0b4703UL, 0x220216b9UL, 0x5505262fUL, 0xc5ba3bbeUL, - 0xb2bd0b28UL, 0x2bb45a92UL, 0x5cb36a04UL, 0xc2d7ffa7UL, 0xb5d0cf31UL, - 0x2cd99e8bUL, 0x5bdeae1dUL, 0x9b64c2b0UL, 0xec63f226UL, 0x756aa39cUL, - 0x026d930aUL, 0x9c0906a9UL, 0xeb0e363fUL, 0x72076785UL, 0x05005713UL, - 0x95bf4a82UL, 0xe2b87a14UL, 0x7bb12baeUL, 0x0cb61b38UL, 0x92d28e9bUL, - 0xe5d5be0dUL, 0x7cdcefb7UL, 0x0bdbdf21UL, 0x86d3d2d4UL, 0xf1d4e242UL, - 0x68ddb3f8UL, 0x1fda836eUL, 0x81be16cdUL, 0xf6b9265bUL, 0x6fb077e1UL, - 0x18b74777UL, 0x88085ae6UL, 0xff0f6a70UL, 0x66063bcaUL, 0x11010b5cUL, - 0x8f659effUL, 0xf862ae69UL, 0x616bffd3UL, 0x166ccf45UL, 0xa00ae278UL, - 0xd70dd2eeUL, 0x4e048354UL, 0x3903b3c2UL, 0xa7672661UL, 0xd06016f7UL, - 0x4969474dUL, 0x3e6e77dbUL, 0xaed16a4aUL, 0xd9d65adcUL, 0x40df0b66UL, - 0x37d83bf0UL, 0xa9bcae53UL, 0xdebb9ec5UL, 0x47b2cf7fUL, 0x30b5ffe9UL, - 0xbdbdf21cUL, 0xcabac28aUL, 0x53b39330UL, 0x24b4a3a6UL, 0xbad03605UL, - 0xcdd70693UL, 0x54de5729UL, 0x23d967bfUL, 0xb3667a2eUL, 0xc4614ab8UL, - 0x5d681b02UL, 0x2a6f2b94UL, 0xb40bbe37UL, 0xc30c8ea1UL, 0x5a05df1bUL, - 0x2d02ef8dUL -#ifdef BYFOUR - }, - { - 0x00000000UL, 0x191b3141UL, 0x32366282UL, 0x2b2d53c3UL, 0x646cc504UL, - 0x7d77f445UL, 0x565aa786UL, 0x4f4196c7UL, 0xc8d98a08UL, 0xd1c2bb49UL, - 0xfaefe88aUL, 0xe3f4d9cbUL, 0xacb54f0cUL, 0xb5ae7e4dUL, 0x9e832d8eUL, - 0x87981ccfUL, 0x4ac21251UL, 0x53d92310UL, 0x78f470d3UL, 0x61ef4192UL, - 0x2eaed755UL, 0x37b5e614UL, 0x1c98b5d7UL, 0x05838496UL, 0x821b9859UL, - 0x9b00a918UL, 0xb02dfadbUL, 0xa936cb9aUL, 0xe6775d5dUL, 0xff6c6c1cUL, - 0xd4413fdfUL, 0xcd5a0e9eUL, 0x958424a2UL, 0x8c9f15e3UL, 0xa7b24620UL, - 0xbea97761UL, 0xf1e8e1a6UL, 0xe8f3d0e7UL, 0xc3de8324UL, 0xdac5b265UL, - 0x5d5daeaaUL, 0x44469febUL, 0x6f6bcc28UL, 0x7670fd69UL, 0x39316baeUL, - 0x202a5aefUL, 0x0b07092cUL, 0x121c386dUL, 0xdf4636f3UL, 0xc65d07b2UL, - 0xed705471UL, 0xf46b6530UL, 0xbb2af3f7UL, 0xa231c2b6UL, 0x891c9175UL, - 0x9007a034UL, 0x179fbcfbUL, 0x0e848dbaUL, 0x25a9de79UL, 0x3cb2ef38UL, - 0x73f379ffUL, 0x6ae848beUL, 0x41c51b7dUL, 0x58de2a3cUL, 0xf0794f05UL, - 0xe9627e44UL, 0xc24f2d87UL, 0xdb541cc6UL, 0x94158a01UL, 0x8d0ebb40UL, - 0xa623e883UL, 0xbf38d9c2UL, 0x38a0c50dUL, 0x21bbf44cUL, 0x0a96a78fUL, - 0x138d96ceUL, 0x5ccc0009UL, 0x45d73148UL, 0x6efa628bUL, 0x77e153caUL, - 0xbabb5d54UL, 0xa3a06c15UL, 0x888d3fd6UL, 0x91960e97UL, 0xded79850UL, - 0xc7cca911UL, 0xece1fad2UL, 0xf5facb93UL, 0x7262d75cUL, 0x6b79e61dUL, - 0x4054b5deUL, 0x594f849fUL, 0x160e1258UL, 0x0f152319UL, 0x243870daUL, - 0x3d23419bUL, 0x65fd6ba7UL, 0x7ce65ae6UL, 0x57cb0925UL, 0x4ed03864UL, - 0x0191aea3UL, 0x188a9fe2UL, 0x33a7cc21UL, 0x2abcfd60UL, 0xad24e1afUL, - 0xb43fd0eeUL, 0x9f12832dUL, 0x8609b26cUL, 0xc94824abUL, 0xd05315eaUL, - 0xfb7e4629UL, 0xe2657768UL, 0x2f3f79f6UL, 0x362448b7UL, 0x1d091b74UL, - 0x04122a35UL, 0x4b53bcf2UL, 0x52488db3UL, 0x7965de70UL, 0x607eef31UL, - 0xe7e6f3feUL, 0xfefdc2bfUL, 0xd5d0917cUL, 0xcccba03dUL, 0x838a36faUL, - 0x9a9107bbUL, 0xb1bc5478UL, 0xa8a76539UL, 0x3b83984bUL, 0x2298a90aUL, - 0x09b5fac9UL, 0x10aecb88UL, 0x5fef5d4fUL, 0x46f46c0eUL, 0x6dd93fcdUL, - 0x74c20e8cUL, 0xf35a1243UL, 0xea412302UL, 0xc16c70c1UL, 0xd8774180UL, - 0x9736d747UL, 0x8e2de606UL, 0xa500b5c5UL, 0xbc1b8484UL, 0x71418a1aUL, - 0x685abb5bUL, 0x4377e898UL, 0x5a6cd9d9UL, 0x152d4f1eUL, 0x0c367e5fUL, - 0x271b2d9cUL, 0x3e001cddUL, 0xb9980012UL, 0xa0833153UL, 0x8bae6290UL, - 0x92b553d1UL, 0xddf4c516UL, 0xc4eff457UL, 0xefc2a794UL, 0xf6d996d5UL, - 0xae07bce9UL, 0xb71c8da8UL, 0x9c31de6bUL, 0x852aef2aUL, 0xca6b79edUL, - 0xd37048acUL, 0xf85d1b6fUL, 0xe1462a2eUL, 0x66de36e1UL, 0x7fc507a0UL, - 0x54e85463UL, 0x4df36522UL, 0x02b2f3e5UL, 0x1ba9c2a4UL, 0x30849167UL, - 0x299fa026UL, 0xe4c5aeb8UL, 0xfdde9ff9UL, 0xd6f3cc3aUL, 0xcfe8fd7bUL, - 0x80a96bbcUL, 0x99b25afdUL, 0xb29f093eUL, 0xab84387fUL, 0x2c1c24b0UL, - 0x350715f1UL, 0x1e2a4632UL, 0x07317773UL, 0x4870e1b4UL, 0x516bd0f5UL, - 0x7a468336UL, 0x635db277UL, 0xcbfad74eUL, 0xd2e1e60fUL, 0xf9ccb5ccUL, - 0xe0d7848dUL, 0xaf96124aUL, 0xb68d230bUL, 0x9da070c8UL, 0x84bb4189UL, - 0x03235d46UL, 0x1a386c07UL, 0x31153fc4UL, 0x280e0e85UL, 0x674f9842UL, - 0x7e54a903UL, 0x5579fac0UL, 0x4c62cb81UL, 0x8138c51fUL, 0x9823f45eUL, - 0xb30ea79dUL, 0xaa1596dcUL, 0xe554001bUL, 0xfc4f315aUL, 0xd7626299UL, - 0xce7953d8UL, 0x49e14f17UL, 0x50fa7e56UL, 0x7bd72d95UL, 0x62cc1cd4UL, - 0x2d8d8a13UL, 0x3496bb52UL, 0x1fbbe891UL, 0x06a0d9d0UL, 0x5e7ef3ecUL, - 0x4765c2adUL, 0x6c48916eUL, 0x7553a02fUL, 0x3a1236e8UL, 0x230907a9UL, - 0x0824546aUL, 0x113f652bUL, 0x96a779e4UL, 0x8fbc48a5UL, 0xa4911b66UL, - 0xbd8a2a27UL, 0xf2cbbce0UL, 0xebd08da1UL, 0xc0fdde62UL, 0xd9e6ef23UL, - 0x14bce1bdUL, 0x0da7d0fcUL, 0x268a833fUL, 0x3f91b27eUL, 0x70d024b9UL, - 0x69cb15f8UL, 0x42e6463bUL, 0x5bfd777aUL, 0xdc656bb5UL, 0xc57e5af4UL, - 0xee530937UL, 0xf7483876UL, 0xb809aeb1UL, 0xa1129ff0UL, 0x8a3fcc33UL, - 0x9324fd72UL - }, - { - 0x00000000UL, 0x01c26a37UL, 0x0384d46eUL, 0x0246be59UL, 0x0709a8dcUL, - 0x06cbc2ebUL, 0x048d7cb2UL, 0x054f1685UL, 0x0e1351b8UL, 0x0fd13b8fUL, - 0x0d9785d6UL, 0x0c55efe1UL, 0x091af964UL, 0x08d89353UL, 0x0a9e2d0aUL, - 0x0b5c473dUL, 0x1c26a370UL, 0x1de4c947UL, 0x1fa2771eUL, 0x1e601d29UL, - 0x1b2f0bacUL, 0x1aed619bUL, 0x18abdfc2UL, 0x1969b5f5UL, 0x1235f2c8UL, - 0x13f798ffUL, 0x11b126a6UL, 0x10734c91UL, 0x153c5a14UL, 0x14fe3023UL, - 0x16b88e7aUL, 0x177ae44dUL, 0x384d46e0UL, 0x398f2cd7UL, 0x3bc9928eUL, - 0x3a0bf8b9UL, 0x3f44ee3cUL, 0x3e86840bUL, 0x3cc03a52UL, 0x3d025065UL, - 0x365e1758UL, 0x379c7d6fUL, 0x35dac336UL, 0x3418a901UL, 0x3157bf84UL, - 0x3095d5b3UL, 0x32d36beaUL, 0x331101ddUL, 0x246be590UL, 0x25a98fa7UL, - 0x27ef31feUL, 0x262d5bc9UL, 0x23624d4cUL, 0x22a0277bUL, 0x20e69922UL, - 0x2124f315UL, 0x2a78b428UL, 0x2bbade1fUL, 0x29fc6046UL, 0x283e0a71UL, - 0x2d711cf4UL, 0x2cb376c3UL, 0x2ef5c89aUL, 0x2f37a2adUL, 0x709a8dc0UL, - 0x7158e7f7UL, 0x731e59aeUL, 0x72dc3399UL, 0x7793251cUL, 0x76514f2bUL, - 0x7417f172UL, 0x75d59b45UL, 0x7e89dc78UL, 0x7f4bb64fUL, 0x7d0d0816UL, - 0x7ccf6221UL, 0x798074a4UL, 0x78421e93UL, 0x7a04a0caUL, 0x7bc6cafdUL, - 0x6cbc2eb0UL, 0x6d7e4487UL, 0x6f38fadeUL, 0x6efa90e9UL, 0x6bb5866cUL, - 0x6a77ec5bUL, 0x68315202UL, 0x69f33835UL, 0x62af7f08UL, 0x636d153fUL, - 0x612bab66UL, 0x60e9c151UL, 0x65a6d7d4UL, 0x6464bde3UL, 0x662203baUL, - 0x67e0698dUL, 0x48d7cb20UL, 0x4915a117UL, 0x4b531f4eUL, 0x4a917579UL, - 0x4fde63fcUL, 0x4e1c09cbUL, 0x4c5ab792UL, 0x4d98dda5UL, 0x46c49a98UL, - 0x4706f0afUL, 0x45404ef6UL, 0x448224c1UL, 0x41cd3244UL, 0x400f5873UL, - 0x4249e62aUL, 0x438b8c1dUL, 0x54f16850UL, 0x55330267UL, 0x5775bc3eUL, - 0x56b7d609UL, 0x53f8c08cUL, 0x523aaabbUL, 0x507c14e2UL, 0x51be7ed5UL, - 0x5ae239e8UL, 0x5b2053dfUL, 0x5966ed86UL, 0x58a487b1UL, 0x5deb9134UL, - 0x5c29fb03UL, 0x5e6f455aUL, 0x5fad2f6dUL, 0xe1351b80UL, 0xe0f771b7UL, - 0xe2b1cfeeUL, 0xe373a5d9UL, 0xe63cb35cUL, 0xe7fed96bUL, 0xe5b86732UL, - 0xe47a0d05UL, 0xef264a38UL, 0xeee4200fUL, 0xeca29e56UL, 0xed60f461UL, - 0xe82fe2e4UL, 0xe9ed88d3UL, 0xebab368aUL, 0xea695cbdUL, 0xfd13b8f0UL, - 0xfcd1d2c7UL, 0xfe976c9eUL, 0xff5506a9UL, 0xfa1a102cUL, 0xfbd87a1bUL, - 0xf99ec442UL, 0xf85cae75UL, 0xf300e948UL, 0xf2c2837fUL, 0xf0843d26UL, - 0xf1465711UL, 0xf4094194UL, 0xf5cb2ba3UL, 0xf78d95faUL, 0xf64fffcdUL, - 0xd9785d60UL, 0xd8ba3757UL, 0xdafc890eUL, 0xdb3ee339UL, 0xde71f5bcUL, - 0xdfb39f8bUL, 0xddf521d2UL, 0xdc374be5UL, 0xd76b0cd8UL, 0xd6a966efUL, - 0xd4efd8b6UL, 0xd52db281UL, 0xd062a404UL, 0xd1a0ce33UL, 0xd3e6706aUL, - 0xd2241a5dUL, 0xc55efe10UL, 0xc49c9427UL, 0xc6da2a7eUL, 0xc7184049UL, - 0xc25756ccUL, 0xc3953cfbUL, 0xc1d382a2UL, 0xc011e895UL, 0xcb4dafa8UL, - 0xca8fc59fUL, 0xc8c97bc6UL, 0xc90b11f1UL, 0xcc440774UL, 0xcd866d43UL, - 0xcfc0d31aUL, 0xce02b92dUL, 0x91af9640UL, 0x906dfc77UL, 0x922b422eUL, - 0x93e92819UL, 0x96a63e9cUL, 0x976454abUL, 0x9522eaf2UL, 0x94e080c5UL, - 0x9fbcc7f8UL, 0x9e7eadcfUL, 0x9c381396UL, 0x9dfa79a1UL, 0x98b56f24UL, - 0x99770513UL, 0x9b31bb4aUL, 0x9af3d17dUL, 0x8d893530UL, 0x8c4b5f07UL, - 0x8e0de15eUL, 0x8fcf8b69UL, 0x8a809decUL, 0x8b42f7dbUL, 0x89044982UL, - 0x88c623b5UL, 0x839a6488UL, 0x82580ebfUL, 0x801eb0e6UL, 0x81dcdad1UL, - 0x8493cc54UL, 0x8551a663UL, 0x8717183aUL, 0x86d5720dUL, 0xa9e2d0a0UL, - 0xa820ba97UL, 0xaa6604ceUL, 0xaba46ef9UL, 0xaeeb787cUL, 0xaf29124bUL, - 0xad6fac12UL, 0xacadc625UL, 0xa7f18118UL, 0xa633eb2fUL, 0xa4755576UL, - 0xa5b73f41UL, 0xa0f829c4UL, 0xa13a43f3UL, 0xa37cfdaaUL, 0xa2be979dUL, - 0xb5c473d0UL, 0xb40619e7UL, 0xb640a7beUL, 0xb782cd89UL, 0xb2cddb0cUL, - 0xb30fb13bUL, 0xb1490f62UL, 0xb08b6555UL, 0xbbd72268UL, 0xba15485fUL, - 0xb853f606UL, 0xb9919c31UL, 0xbcde8ab4UL, 0xbd1ce083UL, 0xbf5a5edaUL, - 0xbe9834edUL - }, - { - 0x00000000UL, 0xb8bc6765UL, 0xaa09c88bUL, 0x12b5afeeUL, 0x8f629757UL, - 0x37def032UL, 0x256b5fdcUL, 0x9dd738b9UL, 0xc5b428efUL, 0x7d084f8aUL, - 0x6fbde064UL, 0xd7018701UL, 0x4ad6bfb8UL, 0xf26ad8ddUL, 0xe0df7733UL, - 0x58631056UL, 0x5019579fUL, 0xe8a530faUL, 0xfa109f14UL, 0x42acf871UL, - 0xdf7bc0c8UL, 0x67c7a7adUL, 0x75720843UL, 0xcdce6f26UL, 0x95ad7f70UL, - 0x2d111815UL, 0x3fa4b7fbUL, 0x8718d09eUL, 0x1acfe827UL, 0xa2738f42UL, - 0xb0c620acUL, 0x087a47c9UL, 0xa032af3eUL, 0x188ec85bUL, 0x0a3b67b5UL, - 0xb28700d0UL, 0x2f503869UL, 0x97ec5f0cUL, 0x8559f0e2UL, 0x3de59787UL, - 0x658687d1UL, 0xdd3ae0b4UL, 0xcf8f4f5aUL, 0x7733283fUL, 0xeae41086UL, - 0x525877e3UL, 0x40edd80dUL, 0xf851bf68UL, 0xf02bf8a1UL, 0x48979fc4UL, - 0x5a22302aUL, 0xe29e574fUL, 0x7f496ff6UL, 0xc7f50893UL, 0xd540a77dUL, - 0x6dfcc018UL, 0x359fd04eUL, 0x8d23b72bUL, 0x9f9618c5UL, 0x272a7fa0UL, - 0xbafd4719UL, 0x0241207cUL, 0x10f48f92UL, 0xa848e8f7UL, 0x9b14583dUL, - 0x23a83f58UL, 0x311d90b6UL, 0x89a1f7d3UL, 0x1476cf6aUL, 0xaccaa80fUL, - 0xbe7f07e1UL, 0x06c36084UL, 0x5ea070d2UL, 0xe61c17b7UL, 0xf4a9b859UL, - 0x4c15df3cUL, 0xd1c2e785UL, 0x697e80e0UL, 0x7bcb2f0eUL, 0xc377486bUL, - 0xcb0d0fa2UL, 0x73b168c7UL, 0x6104c729UL, 0xd9b8a04cUL, 0x446f98f5UL, - 0xfcd3ff90UL, 0xee66507eUL, 0x56da371bUL, 0x0eb9274dUL, 0xb6054028UL, - 0xa4b0efc6UL, 0x1c0c88a3UL, 0x81dbb01aUL, 0x3967d77fUL, 0x2bd27891UL, - 0x936e1ff4UL, 0x3b26f703UL, 0x839a9066UL, 0x912f3f88UL, 0x299358edUL, - 0xb4446054UL, 0x0cf80731UL, 0x1e4da8dfUL, 0xa6f1cfbaUL, 0xfe92dfecUL, - 0x462eb889UL, 0x549b1767UL, 0xec277002UL, 0x71f048bbUL, 0xc94c2fdeUL, - 0xdbf98030UL, 0x6345e755UL, 0x6b3fa09cUL, 0xd383c7f9UL, 0xc1366817UL, - 0x798a0f72UL, 0xe45d37cbUL, 0x5ce150aeUL, 0x4e54ff40UL, 0xf6e89825UL, - 0xae8b8873UL, 0x1637ef16UL, 0x048240f8UL, 0xbc3e279dUL, 0x21e91f24UL, - 0x99557841UL, 0x8be0d7afUL, 0x335cb0caUL, 0xed59b63bUL, 0x55e5d15eUL, - 0x47507eb0UL, 0xffec19d5UL, 0x623b216cUL, 0xda874609UL, 0xc832e9e7UL, - 0x708e8e82UL, 0x28ed9ed4UL, 0x9051f9b1UL, 0x82e4565fUL, 0x3a58313aUL, - 0xa78f0983UL, 0x1f336ee6UL, 0x0d86c108UL, 0xb53aa66dUL, 0xbd40e1a4UL, - 0x05fc86c1UL, 0x1749292fUL, 0xaff54e4aUL, 0x322276f3UL, 0x8a9e1196UL, - 0x982bbe78UL, 0x2097d91dUL, 0x78f4c94bUL, 0xc048ae2eUL, 0xd2fd01c0UL, - 0x6a4166a5UL, 0xf7965e1cUL, 0x4f2a3979UL, 0x5d9f9697UL, 0xe523f1f2UL, - 0x4d6b1905UL, 0xf5d77e60UL, 0xe762d18eUL, 0x5fdeb6ebUL, 0xc2098e52UL, - 0x7ab5e937UL, 0x680046d9UL, 0xd0bc21bcUL, 0x88df31eaUL, 0x3063568fUL, - 0x22d6f961UL, 0x9a6a9e04UL, 0x07bda6bdUL, 0xbf01c1d8UL, 0xadb46e36UL, - 0x15080953UL, 0x1d724e9aUL, 0xa5ce29ffUL, 0xb77b8611UL, 0x0fc7e174UL, - 0x9210d9cdUL, 0x2aacbea8UL, 0x38191146UL, 0x80a57623UL, 0xd8c66675UL, - 0x607a0110UL, 0x72cfaefeUL, 0xca73c99bUL, 0x57a4f122UL, 0xef189647UL, - 0xfdad39a9UL, 0x45115eccUL, 0x764dee06UL, 0xcef18963UL, 0xdc44268dUL, - 0x64f841e8UL, 0xf92f7951UL, 0x41931e34UL, 0x5326b1daUL, 0xeb9ad6bfUL, - 0xb3f9c6e9UL, 0x0b45a18cUL, 0x19f00e62UL, 0xa14c6907UL, 0x3c9b51beUL, - 0x842736dbUL, 0x96929935UL, 0x2e2efe50UL, 0x2654b999UL, 0x9ee8defcUL, - 0x8c5d7112UL, 0x34e11677UL, 0xa9362eceUL, 0x118a49abUL, 0x033fe645UL, - 0xbb838120UL, 0xe3e09176UL, 0x5b5cf613UL, 0x49e959fdUL, 0xf1553e98UL, - 0x6c820621UL, 0xd43e6144UL, 0xc68bceaaUL, 0x7e37a9cfUL, 0xd67f4138UL, - 0x6ec3265dUL, 0x7c7689b3UL, 0xc4caeed6UL, 0x591dd66fUL, 0xe1a1b10aUL, - 0xf3141ee4UL, 0x4ba87981UL, 0x13cb69d7UL, 0xab770eb2UL, 0xb9c2a15cUL, - 0x017ec639UL, 0x9ca9fe80UL, 0x241599e5UL, 0x36a0360bUL, 0x8e1c516eUL, - 0x866616a7UL, 0x3eda71c2UL, 0x2c6fde2cUL, 0x94d3b949UL, 0x090481f0UL, - 0xb1b8e695UL, 0xa30d497bUL, 0x1bb12e1eUL, 0x43d23e48UL, 0xfb6e592dUL, - 0xe9dbf6c3UL, 0x516791a6UL, 0xccb0a91fUL, 0x740cce7aUL, 0x66b96194UL, - 0xde0506f1UL - }, - { - 0x00000000UL, 0x96300777UL, 0x2c610eeeUL, 0xba510999UL, 0x19c46d07UL, - 0x8ff46a70UL, 0x35a563e9UL, 0xa395649eUL, 0x3288db0eUL, 0xa4b8dc79UL, - 0x1ee9d5e0UL, 0x88d9d297UL, 0x2b4cb609UL, 0xbd7cb17eUL, 0x072db8e7UL, - 0x911dbf90UL, 0x6410b71dUL, 0xf220b06aUL, 0x4871b9f3UL, 0xde41be84UL, - 0x7dd4da1aUL, 0xebe4dd6dUL, 0x51b5d4f4UL, 0xc785d383UL, 0x56986c13UL, - 0xc0a86b64UL, 0x7af962fdUL, 0xecc9658aUL, 0x4f5c0114UL, 0xd96c0663UL, - 0x633d0ffaUL, 0xf50d088dUL, 0xc8206e3bUL, 0x5e10694cUL, 0xe44160d5UL, - 0x727167a2UL, 0xd1e4033cUL, 0x47d4044bUL, 0xfd850dd2UL, 0x6bb50aa5UL, - 0xfaa8b535UL, 0x6c98b242UL, 0xd6c9bbdbUL, 0x40f9bcacUL, 0xe36cd832UL, - 0x755cdf45UL, 0xcf0dd6dcUL, 0x593dd1abUL, 0xac30d926UL, 0x3a00de51UL, - 0x8051d7c8UL, 0x1661d0bfUL, 0xb5f4b421UL, 0x23c4b356UL, 0x9995bacfUL, - 0x0fa5bdb8UL, 0x9eb80228UL, 0x0888055fUL, 0xb2d90cc6UL, 0x24e90bb1UL, - 0x877c6f2fUL, 0x114c6858UL, 0xab1d61c1UL, 0x3d2d66b6UL, 0x9041dc76UL, - 0x0671db01UL, 0xbc20d298UL, 0x2a10d5efUL, 0x8985b171UL, 0x1fb5b606UL, - 0xa5e4bf9fUL, 0x33d4b8e8UL, 0xa2c90778UL, 0x34f9000fUL, 0x8ea80996UL, - 0x18980ee1UL, 0xbb0d6a7fUL, 0x2d3d6d08UL, 0x976c6491UL, 0x015c63e6UL, - 0xf4516b6bUL, 0x62616c1cUL, 0xd8306585UL, 0x4e0062f2UL, 0xed95066cUL, - 0x7ba5011bUL, 0xc1f40882UL, 0x57c40ff5UL, 0xc6d9b065UL, 0x50e9b712UL, - 0xeab8be8bUL, 0x7c88b9fcUL, 0xdf1ddd62UL, 0x492dda15UL, 0xf37cd38cUL, - 0x654cd4fbUL, 0x5861b24dUL, 0xce51b53aUL, 0x7400bca3UL, 0xe230bbd4UL, - 0x41a5df4aUL, 0xd795d83dUL, 0x6dc4d1a4UL, 0xfbf4d6d3UL, 0x6ae96943UL, - 0xfcd96e34UL, 0x468867adUL, 0xd0b860daUL, 0x732d0444UL, 0xe51d0333UL, - 0x5f4c0aaaUL, 0xc97c0dddUL, 0x3c710550UL, 0xaa410227UL, 0x10100bbeUL, - 0x86200cc9UL, 0x25b56857UL, 0xb3856f20UL, 0x09d466b9UL, 0x9fe461ceUL, - 0x0ef9de5eUL, 0x98c9d929UL, 0x2298d0b0UL, 0xb4a8d7c7UL, 0x173db359UL, - 0x810db42eUL, 0x3b5cbdb7UL, 0xad6cbac0UL, 0x2083b8edUL, 0xb6b3bf9aUL, - 0x0ce2b603UL, 0x9ad2b174UL, 0x3947d5eaUL, 0xaf77d29dUL, 0x1526db04UL, - 0x8316dc73UL, 0x120b63e3UL, 0x843b6494UL, 0x3e6a6d0dUL, 0xa85a6a7aUL, - 0x0bcf0ee4UL, 0x9dff0993UL, 0x27ae000aUL, 0xb19e077dUL, 0x44930ff0UL, - 0xd2a30887UL, 0x68f2011eUL, 0xfec20669UL, 0x5d5762f7UL, 0xcb676580UL, - 0x71366c19UL, 0xe7066b6eUL, 0x761bd4feUL, 0xe02bd389UL, 0x5a7ada10UL, - 0xcc4add67UL, 0x6fdfb9f9UL, 0xf9efbe8eUL, 0x43beb717UL, 0xd58eb060UL, - 0xe8a3d6d6UL, 0x7e93d1a1UL, 0xc4c2d838UL, 0x52f2df4fUL, 0xf167bbd1UL, - 0x6757bca6UL, 0xdd06b53fUL, 0x4b36b248UL, 0xda2b0dd8UL, 0x4c1b0aafUL, - 0xf64a0336UL, 0x607a0441UL, 0xc3ef60dfUL, 0x55df67a8UL, 0xef8e6e31UL, - 0x79be6946UL, 0x8cb361cbUL, 0x1a8366bcUL, 0xa0d26f25UL, 0x36e26852UL, - 0x95770cccUL, 0x03470bbbUL, 0xb9160222UL, 0x2f260555UL, 0xbe3bbac5UL, - 0x280bbdb2UL, 0x925ab42bUL, 0x046ab35cUL, 0xa7ffd7c2UL, 0x31cfd0b5UL, - 0x8b9ed92cUL, 0x1daede5bUL, 0xb0c2649bUL, 0x26f263ecUL, 0x9ca36a75UL, - 0x0a936d02UL, 0xa906099cUL, 0x3f360eebUL, 0x85670772UL, 0x13570005UL, - 0x824abf95UL, 0x147ab8e2UL, 0xae2bb17bUL, 0x381bb60cUL, 0x9b8ed292UL, - 0x0dbed5e5UL, 0xb7efdc7cUL, 0x21dfdb0bUL, 0xd4d2d386UL, 0x42e2d4f1UL, - 0xf8b3dd68UL, 0x6e83da1fUL, 0xcd16be81UL, 0x5b26b9f6UL, 0xe177b06fUL, - 0x7747b718UL, 0xe65a0888UL, 0x706a0fffUL, 0xca3b0666UL, 0x5c0b0111UL, - 0xff9e658fUL, 0x69ae62f8UL, 0xd3ff6b61UL, 0x45cf6c16UL, 0x78e20aa0UL, - 0xeed20dd7UL, 0x5483044eUL, 0xc2b30339UL, 0x612667a7UL, 0xf71660d0UL, - 0x4d476949UL, 0xdb776e3eUL, 0x4a6ad1aeUL, 0xdc5ad6d9UL, 0x660bdf40UL, - 0xf03bd837UL, 0x53aebca9UL, 0xc59ebbdeUL, 0x7fcfb247UL, 0xe9ffb530UL, - 0x1cf2bdbdUL, 0x8ac2bacaUL, 0x3093b353UL, 0xa6a3b424UL, 0x0536d0baUL, - 0x9306d7cdUL, 0x2957de54UL, 0xbf67d923UL, 0x2e7a66b3UL, 0xb84a61c4UL, - 0x021b685dUL, 0x942b6f2aUL, 0x37be0bb4UL, 0xa18e0cc3UL, 0x1bdf055aUL, - 0x8def022dUL - }, - { - 0x00000000UL, 0x41311b19UL, 0x82623632UL, 0xc3532d2bUL, 0x04c56c64UL, - 0x45f4777dUL, 0x86a75a56UL, 0xc796414fUL, 0x088ad9c8UL, 0x49bbc2d1UL, - 0x8ae8effaUL, 0xcbd9f4e3UL, 0x0c4fb5acUL, 0x4d7eaeb5UL, 0x8e2d839eUL, - 0xcf1c9887UL, 0x5112c24aUL, 0x1023d953UL, 0xd370f478UL, 0x9241ef61UL, - 0x55d7ae2eUL, 0x14e6b537UL, 0xd7b5981cUL, 0x96848305UL, 0x59981b82UL, - 0x18a9009bUL, 0xdbfa2db0UL, 0x9acb36a9UL, 0x5d5d77e6UL, 0x1c6c6cffUL, - 0xdf3f41d4UL, 0x9e0e5acdUL, 0xa2248495UL, 0xe3159f8cUL, 0x2046b2a7UL, - 0x6177a9beUL, 0xa6e1e8f1UL, 0xe7d0f3e8UL, 0x2483dec3UL, 0x65b2c5daUL, - 0xaaae5d5dUL, 0xeb9f4644UL, 0x28cc6b6fUL, 0x69fd7076UL, 0xae6b3139UL, - 0xef5a2a20UL, 0x2c09070bUL, 0x6d381c12UL, 0xf33646dfUL, 0xb2075dc6UL, - 0x715470edUL, 0x30656bf4UL, 0xf7f32abbUL, 0xb6c231a2UL, 0x75911c89UL, - 0x34a00790UL, 0xfbbc9f17UL, 0xba8d840eUL, 0x79dea925UL, 0x38efb23cUL, - 0xff79f373UL, 0xbe48e86aUL, 0x7d1bc541UL, 0x3c2ade58UL, 0x054f79f0UL, - 0x447e62e9UL, 0x872d4fc2UL, 0xc61c54dbUL, 0x018a1594UL, 0x40bb0e8dUL, - 0x83e823a6UL, 0xc2d938bfUL, 0x0dc5a038UL, 0x4cf4bb21UL, 0x8fa7960aUL, - 0xce968d13UL, 0x0900cc5cUL, 0x4831d745UL, 0x8b62fa6eUL, 0xca53e177UL, - 0x545dbbbaUL, 0x156ca0a3UL, 0xd63f8d88UL, 0x970e9691UL, 0x5098d7deUL, - 0x11a9ccc7UL, 0xd2fae1ecUL, 0x93cbfaf5UL, 0x5cd76272UL, 0x1de6796bUL, - 0xdeb55440UL, 0x9f844f59UL, 0x58120e16UL, 0x1923150fUL, 0xda703824UL, - 0x9b41233dUL, 0xa76bfd65UL, 0xe65ae67cUL, 0x2509cb57UL, 0x6438d04eUL, - 0xa3ae9101UL, 0xe29f8a18UL, 0x21cca733UL, 0x60fdbc2aUL, 0xafe124adUL, - 0xeed03fb4UL, 0x2d83129fUL, 0x6cb20986UL, 0xab2448c9UL, 0xea1553d0UL, - 0x29467efbUL, 0x687765e2UL, 0xf6793f2fUL, 0xb7482436UL, 0x741b091dUL, - 0x352a1204UL, 0xf2bc534bUL, 0xb38d4852UL, 0x70de6579UL, 0x31ef7e60UL, - 0xfef3e6e7UL, 0xbfc2fdfeUL, 0x7c91d0d5UL, 0x3da0cbccUL, 0xfa368a83UL, - 0xbb07919aUL, 0x7854bcb1UL, 0x3965a7a8UL, 0x4b98833bUL, 0x0aa99822UL, - 0xc9fab509UL, 0x88cbae10UL, 0x4f5def5fUL, 0x0e6cf446UL, 0xcd3fd96dUL, - 0x8c0ec274UL, 0x43125af3UL, 0x022341eaUL, 0xc1706cc1UL, 0x804177d8UL, - 0x47d73697UL, 0x06e62d8eUL, 0xc5b500a5UL, 0x84841bbcUL, 0x1a8a4171UL, - 0x5bbb5a68UL, 0x98e87743UL, 0xd9d96c5aUL, 0x1e4f2d15UL, 0x5f7e360cUL, - 0x9c2d1b27UL, 0xdd1c003eUL, 0x120098b9UL, 0x533183a0UL, 0x9062ae8bUL, - 0xd153b592UL, 0x16c5f4ddUL, 0x57f4efc4UL, 0x94a7c2efUL, 0xd596d9f6UL, - 0xe9bc07aeUL, 0xa88d1cb7UL, 0x6bde319cUL, 0x2aef2a85UL, 0xed796bcaUL, - 0xac4870d3UL, 0x6f1b5df8UL, 0x2e2a46e1UL, 0xe136de66UL, 0xa007c57fUL, - 0x6354e854UL, 0x2265f34dUL, 0xe5f3b202UL, 0xa4c2a91bUL, 0x67918430UL, - 0x26a09f29UL, 0xb8aec5e4UL, 0xf99fdefdUL, 0x3accf3d6UL, 0x7bfde8cfUL, - 0xbc6ba980UL, 0xfd5ab299UL, 0x3e099fb2UL, 0x7f3884abUL, 0xb0241c2cUL, - 0xf1150735UL, 0x32462a1eUL, 0x73773107UL, 0xb4e17048UL, 0xf5d06b51UL, - 0x3683467aUL, 0x77b25d63UL, 0x4ed7facbUL, 0x0fe6e1d2UL, 0xccb5ccf9UL, - 0x8d84d7e0UL, 0x4a1296afUL, 0x0b238db6UL, 0xc870a09dUL, 0x8941bb84UL, - 0x465d2303UL, 0x076c381aUL, 0xc43f1531UL, 0x850e0e28UL, 0x42984f67UL, - 0x03a9547eUL, 0xc0fa7955UL, 0x81cb624cUL, 0x1fc53881UL, 0x5ef42398UL, - 0x9da70eb3UL, 0xdc9615aaUL, 0x1b0054e5UL, 0x5a314ffcUL, 0x996262d7UL, - 0xd85379ceUL, 0x174fe149UL, 0x567efa50UL, 0x952dd77bUL, 0xd41ccc62UL, - 0x138a8d2dUL, 0x52bb9634UL, 0x91e8bb1fUL, 0xd0d9a006UL, 0xecf37e5eUL, - 0xadc26547UL, 0x6e91486cUL, 0x2fa05375UL, 0xe836123aUL, 0xa9070923UL, - 0x6a542408UL, 0x2b653f11UL, 0xe479a796UL, 0xa548bc8fUL, 0x661b91a4UL, - 0x272a8abdUL, 0xe0bccbf2UL, 0xa18dd0ebUL, 0x62defdc0UL, 0x23efe6d9UL, - 0xbde1bc14UL, 0xfcd0a70dUL, 0x3f838a26UL, 0x7eb2913fUL, 0xb924d070UL, - 0xf815cb69UL, 0x3b46e642UL, 0x7a77fd5bUL, 0xb56b65dcUL, 0xf45a7ec5UL, - 0x370953eeUL, 0x763848f7UL, 0xb1ae09b8UL, 0xf09f12a1UL, 0x33cc3f8aUL, - 0x72fd2493UL - }, - { - 0x00000000UL, 0x376ac201UL, 0x6ed48403UL, 0x59be4602UL, 0xdca80907UL, - 0xebc2cb06UL, 0xb27c8d04UL, 0x85164f05UL, 0xb851130eUL, 0x8f3bd10fUL, - 0xd685970dUL, 0xe1ef550cUL, 0x64f91a09UL, 0x5393d808UL, 0x0a2d9e0aUL, - 0x3d475c0bUL, 0x70a3261cUL, 0x47c9e41dUL, 0x1e77a21fUL, 0x291d601eUL, - 0xac0b2f1bUL, 0x9b61ed1aUL, 0xc2dfab18UL, 0xf5b56919UL, 0xc8f23512UL, - 0xff98f713UL, 0xa626b111UL, 0x914c7310UL, 0x145a3c15UL, 0x2330fe14UL, - 0x7a8eb816UL, 0x4de47a17UL, 0xe0464d38UL, 0xd72c8f39UL, 0x8e92c93bUL, - 0xb9f80b3aUL, 0x3cee443fUL, 0x0b84863eUL, 0x523ac03cUL, 0x6550023dUL, - 0x58175e36UL, 0x6f7d9c37UL, 0x36c3da35UL, 0x01a91834UL, 0x84bf5731UL, - 0xb3d59530UL, 0xea6bd332UL, 0xdd011133UL, 0x90e56b24UL, 0xa78fa925UL, - 0xfe31ef27UL, 0xc95b2d26UL, 0x4c4d6223UL, 0x7b27a022UL, 0x2299e620UL, - 0x15f32421UL, 0x28b4782aUL, 0x1fdeba2bUL, 0x4660fc29UL, 0x710a3e28UL, - 0xf41c712dUL, 0xc376b32cUL, 0x9ac8f52eUL, 0xada2372fUL, 0xc08d9a70UL, - 0xf7e75871UL, 0xae591e73UL, 0x9933dc72UL, 0x1c259377UL, 0x2b4f5176UL, - 0x72f11774UL, 0x459bd575UL, 0x78dc897eUL, 0x4fb64b7fUL, 0x16080d7dUL, - 0x2162cf7cUL, 0xa4748079UL, 0x931e4278UL, 0xcaa0047aUL, 0xfdcac67bUL, - 0xb02ebc6cUL, 0x87447e6dUL, 0xdefa386fUL, 0xe990fa6eUL, 0x6c86b56bUL, - 0x5bec776aUL, 0x02523168UL, 0x3538f369UL, 0x087faf62UL, 0x3f156d63UL, - 0x66ab2b61UL, 0x51c1e960UL, 0xd4d7a665UL, 0xe3bd6464UL, 0xba032266UL, - 0x8d69e067UL, 0x20cbd748UL, 0x17a11549UL, 0x4e1f534bUL, 0x7975914aUL, - 0xfc63de4fUL, 0xcb091c4eUL, 0x92b75a4cUL, 0xa5dd984dUL, 0x989ac446UL, - 0xaff00647UL, 0xf64e4045UL, 0xc1248244UL, 0x4432cd41UL, 0x73580f40UL, - 0x2ae64942UL, 0x1d8c8b43UL, 0x5068f154UL, 0x67023355UL, 0x3ebc7557UL, - 0x09d6b756UL, 0x8cc0f853UL, 0xbbaa3a52UL, 0xe2147c50UL, 0xd57ebe51UL, - 0xe839e25aUL, 0xdf53205bUL, 0x86ed6659UL, 0xb187a458UL, 0x3491eb5dUL, - 0x03fb295cUL, 0x5a456f5eUL, 0x6d2fad5fUL, 0x801b35e1UL, 0xb771f7e0UL, - 0xeecfb1e2UL, 0xd9a573e3UL, 0x5cb33ce6UL, 0x6bd9fee7UL, 0x3267b8e5UL, - 0x050d7ae4UL, 0x384a26efUL, 0x0f20e4eeUL, 0x569ea2ecUL, 0x61f460edUL, - 0xe4e22fe8UL, 0xd388ede9UL, 0x8a36abebUL, 0xbd5c69eaUL, 0xf0b813fdUL, - 0xc7d2d1fcUL, 0x9e6c97feUL, 0xa90655ffUL, 0x2c101afaUL, 0x1b7ad8fbUL, - 0x42c49ef9UL, 0x75ae5cf8UL, 0x48e900f3UL, 0x7f83c2f2UL, 0x263d84f0UL, - 0x115746f1UL, 0x944109f4UL, 0xa32bcbf5UL, 0xfa958df7UL, 0xcdff4ff6UL, - 0x605d78d9UL, 0x5737bad8UL, 0x0e89fcdaUL, 0x39e33edbUL, 0xbcf571deUL, - 0x8b9fb3dfUL, 0xd221f5ddUL, 0xe54b37dcUL, 0xd80c6bd7UL, 0xef66a9d6UL, - 0xb6d8efd4UL, 0x81b22dd5UL, 0x04a462d0UL, 0x33cea0d1UL, 0x6a70e6d3UL, - 0x5d1a24d2UL, 0x10fe5ec5UL, 0x27949cc4UL, 0x7e2adac6UL, 0x494018c7UL, - 0xcc5657c2UL, 0xfb3c95c3UL, 0xa282d3c1UL, 0x95e811c0UL, 0xa8af4dcbUL, - 0x9fc58fcaUL, 0xc67bc9c8UL, 0xf1110bc9UL, 0x740744ccUL, 0x436d86cdUL, - 0x1ad3c0cfUL, 0x2db902ceUL, 0x4096af91UL, 0x77fc6d90UL, 0x2e422b92UL, - 0x1928e993UL, 0x9c3ea696UL, 0xab546497UL, 0xf2ea2295UL, 0xc580e094UL, - 0xf8c7bc9fUL, 0xcfad7e9eUL, 0x9613389cUL, 0xa179fa9dUL, 0x246fb598UL, - 0x13057799UL, 0x4abb319bUL, 0x7dd1f39aUL, 0x3035898dUL, 0x075f4b8cUL, - 0x5ee10d8eUL, 0x698bcf8fUL, 0xec9d808aUL, 0xdbf7428bUL, 0x82490489UL, - 0xb523c688UL, 0x88649a83UL, 0xbf0e5882UL, 0xe6b01e80UL, 0xd1dadc81UL, - 0x54cc9384UL, 0x63a65185UL, 0x3a181787UL, 0x0d72d586UL, 0xa0d0e2a9UL, - 0x97ba20a8UL, 0xce0466aaUL, 0xf96ea4abUL, 0x7c78ebaeUL, 0x4b1229afUL, - 0x12ac6fadUL, 0x25c6adacUL, 0x1881f1a7UL, 0x2feb33a6UL, 0x765575a4UL, - 0x413fb7a5UL, 0xc429f8a0UL, 0xf3433aa1UL, 0xaafd7ca3UL, 0x9d97bea2UL, - 0xd073c4b5UL, 0xe71906b4UL, 0xbea740b6UL, 0x89cd82b7UL, 0x0cdbcdb2UL, - 0x3bb10fb3UL, 0x620f49b1UL, 0x55658bb0UL, 0x6822d7bbUL, 0x5f4815baUL, - 0x06f653b8UL, 0x319c91b9UL, 0xb48adebcUL, 0x83e01cbdUL, 0xda5e5abfUL, - 0xed3498beUL - }, - { - 0x00000000UL, 0x6567bcb8UL, 0x8bc809aaUL, 0xeeafb512UL, 0x5797628fUL, - 0x32f0de37UL, 0xdc5f6b25UL, 0xb938d79dUL, 0xef28b4c5UL, 0x8a4f087dUL, - 0x64e0bd6fUL, 0x018701d7UL, 0xb8bfd64aUL, 0xddd86af2UL, 0x3377dfe0UL, - 0x56106358UL, 0x9f571950UL, 0xfa30a5e8UL, 0x149f10faUL, 0x71f8ac42UL, - 0xc8c07bdfUL, 0xada7c767UL, 0x43087275UL, 0x266fcecdUL, 0x707fad95UL, - 0x1518112dUL, 0xfbb7a43fUL, 0x9ed01887UL, 0x27e8cf1aUL, 0x428f73a2UL, - 0xac20c6b0UL, 0xc9477a08UL, 0x3eaf32a0UL, 0x5bc88e18UL, 0xb5673b0aUL, - 0xd00087b2UL, 0x6938502fUL, 0x0c5fec97UL, 0xe2f05985UL, 0x8797e53dUL, - 0xd1878665UL, 0xb4e03addUL, 0x5a4f8fcfUL, 0x3f283377UL, 0x8610e4eaUL, - 0xe3775852UL, 0x0dd8ed40UL, 0x68bf51f8UL, 0xa1f82bf0UL, 0xc49f9748UL, - 0x2a30225aUL, 0x4f579ee2UL, 0xf66f497fUL, 0x9308f5c7UL, 0x7da740d5UL, - 0x18c0fc6dUL, 0x4ed09f35UL, 0x2bb7238dUL, 0xc518969fUL, 0xa07f2a27UL, - 0x1947fdbaUL, 0x7c204102UL, 0x928ff410UL, 0xf7e848a8UL, 0x3d58149bUL, - 0x583fa823UL, 0xb6901d31UL, 0xd3f7a189UL, 0x6acf7614UL, 0x0fa8caacUL, - 0xe1077fbeUL, 0x8460c306UL, 0xd270a05eUL, 0xb7171ce6UL, 0x59b8a9f4UL, - 0x3cdf154cUL, 0x85e7c2d1UL, 0xe0807e69UL, 0x0e2fcb7bUL, 0x6b4877c3UL, - 0xa20f0dcbUL, 0xc768b173UL, 0x29c70461UL, 0x4ca0b8d9UL, 0xf5986f44UL, - 0x90ffd3fcUL, 0x7e5066eeUL, 0x1b37da56UL, 0x4d27b90eUL, 0x284005b6UL, - 0xc6efb0a4UL, 0xa3880c1cUL, 0x1ab0db81UL, 0x7fd76739UL, 0x9178d22bUL, - 0xf41f6e93UL, 0x03f7263bUL, 0x66909a83UL, 0x883f2f91UL, 0xed589329UL, - 0x546044b4UL, 0x3107f80cUL, 0xdfa84d1eUL, 0xbacff1a6UL, 0xecdf92feUL, - 0x89b82e46UL, 0x67179b54UL, 0x027027ecUL, 0xbb48f071UL, 0xde2f4cc9UL, - 0x3080f9dbUL, 0x55e74563UL, 0x9ca03f6bUL, 0xf9c783d3UL, 0x176836c1UL, - 0x720f8a79UL, 0xcb375de4UL, 0xae50e15cUL, 0x40ff544eUL, 0x2598e8f6UL, - 0x73888baeUL, 0x16ef3716UL, 0xf8408204UL, 0x9d273ebcUL, 0x241fe921UL, - 0x41785599UL, 0xafd7e08bUL, 0xcab05c33UL, 0x3bb659edUL, 0x5ed1e555UL, - 0xb07e5047UL, 0xd519ecffUL, 0x6c213b62UL, 0x094687daUL, 0xe7e932c8UL, - 0x828e8e70UL, 0xd49eed28UL, 0xb1f95190UL, 0x5f56e482UL, 0x3a31583aUL, - 0x83098fa7UL, 0xe66e331fUL, 0x08c1860dUL, 0x6da63ab5UL, 0xa4e140bdUL, - 0xc186fc05UL, 0x2f294917UL, 0x4a4ef5afUL, 0xf3762232UL, 0x96119e8aUL, - 0x78be2b98UL, 0x1dd99720UL, 0x4bc9f478UL, 0x2eae48c0UL, 0xc001fdd2UL, - 0xa566416aUL, 0x1c5e96f7UL, 0x79392a4fUL, 0x97969f5dUL, 0xf2f123e5UL, - 0x05196b4dUL, 0x607ed7f5UL, 0x8ed162e7UL, 0xebb6de5fUL, 0x528e09c2UL, - 0x37e9b57aUL, 0xd9460068UL, 0xbc21bcd0UL, 0xea31df88UL, 0x8f566330UL, - 0x61f9d622UL, 0x049e6a9aUL, 0xbda6bd07UL, 0xd8c101bfUL, 0x366eb4adUL, - 0x53090815UL, 0x9a4e721dUL, 0xff29cea5UL, 0x11867bb7UL, 0x74e1c70fUL, - 0xcdd91092UL, 0xa8beac2aUL, 0x46111938UL, 0x2376a580UL, 0x7566c6d8UL, - 0x10017a60UL, 0xfeaecf72UL, 0x9bc973caUL, 0x22f1a457UL, 0x479618efUL, - 0xa939adfdUL, 0xcc5e1145UL, 0x06ee4d76UL, 0x6389f1ceUL, 0x8d2644dcUL, - 0xe841f864UL, 0x51792ff9UL, 0x341e9341UL, 0xdab12653UL, 0xbfd69aebUL, - 0xe9c6f9b3UL, 0x8ca1450bUL, 0x620ef019UL, 0x07694ca1UL, 0xbe519b3cUL, - 0xdb362784UL, 0x35999296UL, 0x50fe2e2eUL, 0x99b95426UL, 0xfcdee89eUL, - 0x12715d8cUL, 0x7716e134UL, 0xce2e36a9UL, 0xab498a11UL, 0x45e63f03UL, - 0x208183bbUL, 0x7691e0e3UL, 0x13f65c5bUL, 0xfd59e949UL, 0x983e55f1UL, - 0x2106826cUL, 0x44613ed4UL, 0xaace8bc6UL, 0xcfa9377eUL, 0x38417fd6UL, - 0x5d26c36eUL, 0xb389767cUL, 0xd6eecac4UL, 0x6fd61d59UL, 0x0ab1a1e1UL, - 0xe41e14f3UL, 0x8179a84bUL, 0xd769cb13UL, 0xb20e77abUL, 0x5ca1c2b9UL, - 0x39c67e01UL, 0x80fea99cUL, 0xe5991524UL, 0x0b36a036UL, 0x6e511c8eUL, - 0xa7166686UL, 0xc271da3eUL, 0x2cde6f2cUL, 0x49b9d394UL, 0xf0810409UL, - 0x95e6b8b1UL, 0x7b490da3UL, 0x1e2eb11bUL, 0x483ed243UL, 0x2d596efbUL, - 0xc3f6dbe9UL, 0xa6916751UL, 0x1fa9b0ccUL, 0x7ace0c74UL, 0x9461b966UL, - 0xf10605deUL -#endif - } -}; diff --git a/app/jni/src/libultraship/extern/StormLib/src/zlib/deflate.c b/app/jni/src/libultraship/extern/StormLib/src/zlib/deflate.c deleted file mode 100644 index 5c4022f..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/zlib/deflate.c +++ /dev/null @@ -1,1834 +0,0 @@ -/* deflate.c -- compress data using the deflation algorithm - * Copyright (C) 1995-2010 Jean-loup Gailly and Mark Adler - * For conditions of distribution and use, see copyright notice in zlib.h - */ - -/* - * ALGORITHM - * - * The "deflation" process depends on being able to identify portions - * of the input text which are identical to earlier input (within a - * sliding window trailing behind the input currently being processed). - * - * The most straightforward technique turns out to be the fastest for - * most input files: try all possible matches and select the longest. - * The key feature of this algorithm is that insertions into the string - * dictionary are very simple and thus fast, and deletions are avoided - * completely. Insertions are performed at each input character, whereas - * string matches are performed only when the previous match ends. So it - * is preferable to spend more time in matches to allow very fast string - * insertions and avoid deletions. The matching algorithm for small - * strings is inspired from that of Rabin & Karp. A brute force approach - * is used to find longer strings when a small match has been found. - * A similar algorithm is used in comic (by Jan-Mark Wams) and freeze - * (by Leonid Broukhis). - * A previous version of this file used a more sophisticated algorithm - * (by Fiala and Greene) which is guaranteed to run in linear amortized - * time, but has a larger average cost, uses more memory and is patented. - * However the F&G algorithm may be faster for some highly redundant - * files if the parameter max_chain_length (described below) is too large. - * - * ACKNOWLEDGEMENTS - * - * The idea of lazy evaluation of matches is due to Jan-Mark Wams, and - * I found it in 'freeze' written by Leonid Broukhis. - * Thanks to many people for bug reports and testing. - * - * REFERENCES - * - * Deutsch, L.P.,"DEFLATE Compressed Data Format Specification". - * Available in http://www.ietf.org/rfc/rfc1951.txt - * - * A description of the Rabin and Karp algorithm is given in the book - * "Algorithms" by R. Sedgewick, Addison-Wesley, p252. - * - * Fiala,E.R., and Greene,D.H. - * Data Compression with Finite Windows, Comm.ACM, 32,4 (1989) 490-595 - * - */ - -/* @(#) $Id$ */ - -#include "deflate.h" - -const char deflate_copyright[] = - " deflate 1.2.5 Copyright 1995-2010 Jean-loup Gailly and Mark Adler "; -/* - If you use the zlib library in a product, an acknowledgment is welcome - in the documentation of your product. If for some reason you cannot - include such an acknowledgment, I would appreciate that you keep this - copyright string in the executable of your product. - */ - -/* =========================================================================== - * Function prototypes. - */ -typedef enum { - need_more, /* block not completed, need more input or more output */ - block_done, /* block flush performed */ - finish_started, /* finish started, need only more output at next deflate */ - finish_done /* finish done, accept no more input or output */ -} block_state; - -typedef block_state (*compress_func) OF((deflate_state *s, int flush)); -/* Compression function. Returns the block state after the call. */ - -local void fill_window OF((deflate_state *s)); -local block_state deflate_stored OF((deflate_state *s, int flush)); -local block_state deflate_fast OF((deflate_state *s, int flush)); -#ifndef FASTEST -local block_state deflate_slow OF((deflate_state *s, int flush)); -#endif -local block_state deflate_rle OF((deflate_state *s, int flush)); -local block_state deflate_huff OF((deflate_state *s, int flush)); -local void lm_init OF((deflate_state *s)); -local void putShortMSB OF((deflate_state *s, uInt b)); -local void flush_pending OF((z_streamp strm)); -local int read_buf OF((z_streamp strm, Bytef *buf, unsigned size)); -#ifdef ASMV - void match_init OF((void)); /* asm code initialization */ - uInt longest_match OF((deflate_state *s, IPos cur_match)); -#else -local uInt longest_match OF((deflate_state *s, IPos cur_match)); -#endif - -#ifdef DEBUG -local void check_match OF((deflate_state *s, IPos start, IPos match, - int length)); -#endif - -/* =========================================================================== - * Local data - */ - -#define NIL 0 -/* Tail of hash chains */ - -#ifndef TOO_FAR -# define TOO_FAR 4096 -#endif -/* Matches of length 3 are discarded if their distance exceeds TOO_FAR */ - -/* Values for max_lazy_match, good_match and max_chain_length, depending on - * the desired pack level (0..9). The values given below have been tuned to - * exclude worst case performance for pathological files. Better values may be - * found for specific files. - */ -typedef struct config_s { - ush good_length; /* reduce lazy search above this match length */ - ush max_lazy; /* do not perform lazy search above this match length */ - ush nice_length; /* quit search above this match length */ - ush max_chain; - compress_func func; -} config; - -#ifdef FASTEST -local const config configuration_table[2] = { -/* good lazy nice chain */ -/* 0 */ {0, 0, 0, 0, deflate_stored}, /* store only */ -/* 1 */ {4, 4, 8, 4, deflate_fast}}; /* max speed, no lazy matches */ -#else -local const config configuration_table[10] = { -/* good lazy nice chain */ -/* 0 */ {0, 0, 0, 0, deflate_stored}, /* store only */ -/* 1 */ {4, 4, 8, 4, deflate_fast}, /* max speed, no lazy matches */ -/* 2 */ {4, 5, 16, 8, deflate_fast}, -/* 3 */ {4, 6, 32, 32, deflate_fast}, - -/* 4 */ {4, 4, 16, 16, deflate_slow}, /* lazy matches */ -/* 5 */ {8, 16, 32, 32, deflate_slow}, -/* 6 */ {8, 16, 128, 128, deflate_slow}, -/* 7 */ {8, 32, 128, 256, deflate_slow}, -/* 8 */ {32, 128, 258, 1024, deflate_slow}, -/* 9 */ {32, 258, 258, 4096, deflate_slow}}; /* max compression */ -#endif - -/* Note: the deflate() code requires max_lazy >= MIN_MATCH and max_chain >= 4 - * For deflate_fast() (levels <= 3) good is ignored and lazy has a different - * meaning. - */ - -#define EQUAL 0 -/* result of memcmp for equal strings */ - -#ifndef NO_DUMMY_DECL -struct static_tree_desc_s {int dummy;}; /* for buggy compilers */ -#endif - -/* =========================================================================== - * Update a hash value with the given input byte - * IN assertion: all calls to to UPDATE_HASH are made with consecutive - * input characters, so that a running hash key can be computed from the - * previous key instead of complete recalculation each time. - */ -#define UPDATE_HASH(s,h,c) (h = (((h)<hash_shift) ^ (c)) & s->hash_mask) - - -/* =========================================================================== - * Insert string str in the dictionary and set match_head to the previous head - * of the hash chain (the most recent string with same hash key). Return - * the previous length of the hash chain. - * If this file is compiled with -DFASTEST, the compression level is forced - * to 1, and no hash chains are maintained. - * IN assertion: all calls to to INSERT_STRING are made with consecutive - * input characters and the first MIN_MATCH bytes of str are valid - * (except for the last MIN_MATCH-1 bytes of the input file). - */ -#ifdef FASTEST -#define INSERT_STRING(s, str, match_head) \ - (UPDATE_HASH(s, s->ins_h, s->window[(str) + (MIN_MATCH-1)]), \ - match_head = s->head[s->ins_h], \ - s->head[s->ins_h] = (Pos)(str)) -#else -#define INSERT_STRING(s, str, match_head) \ - (UPDATE_HASH(s, s->ins_h, s->window[(str) + (MIN_MATCH-1)]), \ - match_head = s->prev[(str) & s->w_mask] = s->head[s->ins_h], \ - s->head[s->ins_h] = (Pos)(str)) -#endif - -/* =========================================================================== - * Initialize the hash table (avoiding 64K overflow for 16 bit systems). - * prev[] will be initialized on the fly. - */ -#define CLEAR_HASH(s) \ - s->head[s->hash_size-1] = NIL; \ - zmemzero((Bytef *)s->head, (unsigned)(s->hash_size-1)*sizeof(*s->head)); - -/* ========================================================================= */ -int ZEXPORT deflateInit_(strm, level, version, stream_size) - z_streamp strm; - int level; - const char *version; - int stream_size; -{ - return deflateInit2_(strm, level, Z_DEFLATED, MAX_WBITS, DEF_MEM_LEVEL, - Z_DEFAULT_STRATEGY, version, stream_size); - /* To do: ignore strm->next_in if we use it as window */ -} - -/* ========================================================================= */ -int ZEXPORT deflateInit2_(strm, level, method, windowBits, memLevel, strategy, - version, stream_size) - z_streamp strm; - int level; - int method; - int windowBits; - int memLevel; - int strategy; - const char *version; - int stream_size; -{ - deflate_state *s; - int wrap = 1; - static const char my_version[] = ZLIB_VERSION; - - ushf *overlay; - /* We overlay pending_buf and d_buf+l_buf. This works since the average - * output size for (length,distance) codes is <= 24 bits. - */ - - if (version == Z_NULL || version[0] != my_version[0] || - stream_size != sizeof(z_stream)) { - return Z_VERSION_ERROR; - } - if (strm == Z_NULL) return Z_STREAM_ERROR; - - strm->msg = Z_NULL; - if (strm->zalloc == (alloc_func)0) { - strm->zalloc = zcalloc; - strm->opaque = (voidpf)0; - } - if (strm->zfree == (free_func)0) strm->zfree = zcfree; - -#ifdef FASTEST - if (level != 0) level = 1; -#else - if (level == Z_DEFAULT_COMPRESSION) level = 6; -#endif - - if (windowBits < 0) { /* suppress zlib wrapper */ - wrap = 0; - windowBits = -windowBits; - } -#ifdef GZIP - else if (windowBits > 15) { - wrap = 2; /* write gzip wrapper instead */ - windowBits -= 16; - } -#endif - if (memLevel < 1 || memLevel > MAX_MEM_LEVEL || method != Z_DEFLATED || - windowBits < 8 || windowBits > 15 || level < 0 || level > 9 || - strategy < 0 || strategy > Z_FIXED) { - return Z_STREAM_ERROR; - } - if (windowBits == 8) windowBits = 9; /* until 256-byte window bug fixed */ - s = (deflate_state *) ZALLOC(strm, 1, sizeof(deflate_state)); - if (s == Z_NULL) return Z_MEM_ERROR; - strm->state = (struct internal_state FAR *)s; - s->strm = strm; - - s->wrap = wrap; - s->gzhead = Z_NULL; - s->w_bits = windowBits; - s->w_size = 1 << s->w_bits; - s->w_mask = s->w_size - 1; - - s->hash_bits = memLevel + 7; - s->hash_size = 1 << s->hash_bits; - s->hash_mask = s->hash_size - 1; - s->hash_shift = ((s->hash_bits+MIN_MATCH-1)/MIN_MATCH); - - s->window = (Bytef *) ZALLOC(strm, s->w_size, 2*sizeof(Byte)); - s->prev = (Posf *) ZALLOC(strm, s->w_size, sizeof(Pos)); - s->head = (Posf *) ZALLOC(strm, s->hash_size, sizeof(Pos)); - - s->high_water = 0; /* nothing written to s->window yet */ - - s->lit_bufsize = 1 << (memLevel + 6); /* 16K elements by default */ - - overlay = (ushf *) ZALLOC(strm, s->lit_bufsize, sizeof(ush)+2); - s->pending_buf = (uchf *) overlay; - s->pending_buf_size = (ulg)s->lit_bufsize * (sizeof(ush)+2L); - - if (s->window == Z_NULL || s->prev == Z_NULL || s->head == Z_NULL || - s->pending_buf == Z_NULL) { - s->status = FINISH_STATE; - strm->msg = (char*)ERR_MSG(Z_MEM_ERROR); - deflateEnd (strm); - return Z_MEM_ERROR; - } - s->d_buf = overlay + s->lit_bufsize/sizeof(ush); - s->l_buf = s->pending_buf + (1+sizeof(ush))*s->lit_bufsize; - - s->level = level; - s->strategy = strategy; - s->method = (Byte)method; - - return deflateReset(strm); -} - -/* ========================================================================= */ -int ZEXPORT deflateSetDictionary (strm, dictionary, dictLength) - z_streamp strm; - const Bytef *dictionary; - uInt dictLength; -{ - deflate_state *s; - uInt length = dictLength; - uInt n; - IPos hash_head = 0; - - if (strm == Z_NULL || strm->state == Z_NULL || dictionary == Z_NULL || - strm->state->wrap == 2 || - (strm->state->wrap == 1 && strm->state->status != INIT_STATE)) - return Z_STREAM_ERROR; - - s = strm->state; - if (s->wrap) - strm->adler = adler32(strm->adler, dictionary, dictLength); - - if (length < MIN_MATCH) return Z_OK; - if (length > s->w_size) { - length = s->w_size; - dictionary += dictLength - length; /* use the tail of the dictionary */ - } - zmemcpy(s->window, dictionary, length); - s->strstart = length; - s->block_start = (long)length; - - /* Insert all strings in the hash table (except for the last two bytes). - * s->lookahead stays null, so s->ins_h will be recomputed at the next - * call of fill_window. - */ - s->ins_h = s->window[0]; - UPDATE_HASH(s, s->ins_h, s->window[1]); - for (n = 0; n <= length - MIN_MATCH; n++) { - INSERT_STRING(s, n, hash_head); - } - if (hash_head) hash_head = 0; /* to make compiler happy */ - return Z_OK; -} - -/* ========================================================================= */ -int ZEXPORT deflateReset (strm) - z_streamp strm; -{ - deflate_state *s; - - if (strm == Z_NULL || strm->state == Z_NULL || - strm->zalloc == (alloc_func)0 || strm->zfree == (free_func)0) { - return Z_STREAM_ERROR; - } - - strm->total_in = strm->total_out = 0; - strm->msg = Z_NULL; /* use zfree if we ever allocate msg dynamically */ - strm->data_type = Z_UNKNOWN; - - s = (deflate_state *)strm->state; - s->pending = 0; - s->pending_out = s->pending_buf; - - if (s->wrap < 0) { - s->wrap = -s->wrap; /* was made negative by deflate(..., Z_FINISH); */ - } - s->status = s->wrap ? INIT_STATE : BUSY_STATE; - strm->adler = -#ifdef GZIP - s->wrap == 2 ? crc32(0L, Z_NULL, 0) : -#endif - adler32(0L, Z_NULL, 0); - s->last_flush = Z_NO_FLUSH; - - _tr_init(s); - lm_init(s); - - return Z_OK; -} - -/* ========================================================================= */ -int ZEXPORT deflateSetHeader (strm, head) - z_streamp strm; - gz_headerp head; -{ - if (strm == Z_NULL || strm->state == Z_NULL) return Z_STREAM_ERROR; - if (strm->state->wrap != 2) return Z_STREAM_ERROR; - strm->state->gzhead = head; - return Z_OK; -} - -/* ========================================================================= */ -int ZEXPORT deflatePrime (strm, bits, value) - z_streamp strm; - int bits; - int value; -{ - if (strm == Z_NULL || strm->state == Z_NULL) return Z_STREAM_ERROR; - strm->state->bi_valid = bits; - strm->state->bi_buf = (ush)(value & ((1 << bits) - 1)); - return Z_OK; -} - -/* ========================================================================= */ -int ZEXPORT deflateParams(strm, level, strategy) - z_streamp strm; - int level; - int strategy; -{ - deflate_state *s; - compress_func func; - int err = Z_OK; - - if (strm == Z_NULL || strm->state == Z_NULL) return Z_STREAM_ERROR; - s = strm->state; - -#ifdef FASTEST - if (level != 0) level = 1; -#else - if (level == Z_DEFAULT_COMPRESSION) level = 6; -#endif - if (level < 0 || level > 9 || strategy < 0 || strategy > Z_FIXED) { - return Z_STREAM_ERROR; - } - func = configuration_table[s->level].func; - - if ((strategy != s->strategy || func != configuration_table[level].func) && - strm->total_in != 0) { - /* Flush the last buffer: */ - err = deflate(strm, Z_BLOCK); - } - if (s->level != level) { - s->level = level; - s->max_lazy_match = configuration_table[level].max_lazy; - s->good_match = configuration_table[level].good_length; - s->nice_match = configuration_table[level].nice_length; - s->max_chain_length = configuration_table[level].max_chain; - } - s->strategy = strategy; - return err; -} - -/* ========================================================================= */ -int ZEXPORT deflateTune(strm, good_length, max_lazy, nice_length, max_chain) - z_streamp strm; - int good_length; - int max_lazy; - int nice_length; - int max_chain; -{ - deflate_state *s; - - if (strm == Z_NULL || strm->state == Z_NULL) return Z_STREAM_ERROR; - s = strm->state; - s->good_match = good_length; - s->max_lazy_match = max_lazy; - s->nice_match = nice_length; - s->max_chain_length = max_chain; - return Z_OK; -} - -/* ========================================================================= - * For the default windowBits of 15 and memLevel of 8, this function returns - * a close to exact, as well as small, upper bound on the compressed size. - * They are coded as constants here for a reason--if the #define's are - * changed, then this function needs to be changed as well. The return - * value for 15 and 8 only works for those exact settings. - * - * For any setting other than those defaults for windowBits and memLevel, - * the value returned is a conservative worst case for the maximum expansion - * resulting from using fixed blocks instead of stored blocks, which deflate - * can emit on compressed data for some combinations of the parameters. - * - * This function could be more sophisticated to provide closer upper bounds for - * every combination of windowBits and memLevel. But even the conservative - * upper bound of about 14% expansion does not seem onerous for output buffer - * allocation. - */ -uLong ZEXPORT deflateBound(strm, sourceLen) - z_streamp strm; - uLong sourceLen; -{ - deflate_state *s; - uLong complen, wraplen; - Bytef *str; - - /* conservative upper bound for compressed data */ - complen = sourceLen + - ((sourceLen + 7) >> 3) + ((sourceLen + 63) >> 6) + 5; - - /* if can't get parameters, return conservative bound plus zlib wrapper */ - if (strm == Z_NULL || strm->state == Z_NULL) - return complen + 6; - - /* compute wrapper length */ - s = strm->state; - switch (s->wrap) { - case 0: /* raw deflate */ - wraplen = 0; - break; - case 1: /* zlib wrapper */ - wraplen = 6 + (s->strstart ? 4 : 0); - break; - case 2: /* gzip wrapper */ - wraplen = 18; - if (s->gzhead != Z_NULL) { /* user-supplied gzip header */ - if (s->gzhead->extra != Z_NULL) - wraplen += 2 + s->gzhead->extra_len; - str = s->gzhead->name; - if (str != Z_NULL) - do { - wraplen++; - } while (*str++); - str = s->gzhead->comment; - if (str != Z_NULL) - do { - wraplen++; - } while (*str++); - if (s->gzhead->hcrc) - wraplen += 2; - } - break; - default: /* for compiler happiness */ - wraplen = 6; - } - - /* if not default parameters, return conservative bound */ - if (s->w_bits != 15 || s->hash_bits != 8 + 7) - return complen + wraplen; - - /* default settings: return tight bound for that case */ - return sourceLen + (sourceLen >> 12) + (sourceLen >> 14) + - (sourceLen >> 25) + 13 - 6 + wraplen; -} - -/* ========================================================================= - * Put a short in the pending buffer. The 16-bit value is put in MSB order. - * IN assertion: the stream state is correct and there is enough room in - * pending_buf. - */ -local void putShortMSB (s, b) - deflate_state *s; - uInt b; -{ - put_byte(s, (Byte)(b >> 8)); - put_byte(s, (Byte)(b & 0xff)); -} - -/* ========================================================================= - * Flush as much pending output as possible. All deflate() output goes - * through this function so some applications may wish to modify it - * to avoid allocating a large strm->next_out buffer and copying into it. - * (See also read_buf()). - */ -local void flush_pending(strm) - z_streamp strm; -{ - unsigned len = strm->state->pending; - - if (len > strm->avail_out) len = strm->avail_out; - if (len == 0) return; - - zmemcpy(strm->next_out, strm->state->pending_out, len); - strm->next_out += len; - strm->state->pending_out += len; - strm->total_out += len; - strm->avail_out -= len; - strm->state->pending -= len; - if (strm->state->pending == 0) { - strm->state->pending_out = strm->state->pending_buf; - } -} - -/* ========================================================================= */ -int ZEXPORT deflate (strm, flush) - z_streamp strm; - int flush; -{ - int old_flush; /* value of flush param for previous deflate call */ - deflate_state *s; - - if (strm == Z_NULL || strm->state == Z_NULL || - flush > Z_BLOCK || flush < 0) { - return Z_STREAM_ERROR; - } - s = strm->state; - - if (strm->next_out == Z_NULL || - (strm->next_in == Z_NULL && strm->avail_in != 0) || - (s->status == FINISH_STATE && flush != Z_FINISH)) { - ERR_RETURN(strm, Z_STREAM_ERROR); - } - if (strm->avail_out == 0) ERR_RETURN(strm, Z_BUF_ERROR); - - s->strm = strm; /* just in case */ - old_flush = s->last_flush; - s->last_flush = flush; - - /* Write the header */ - if (s->status == INIT_STATE) { -#ifdef GZIP - if (s->wrap == 2) { - strm->adler = crc32(0L, Z_NULL, 0); - put_byte(s, 31); - put_byte(s, 139); - put_byte(s, 8); - if (s->gzhead == Z_NULL) { - put_byte(s, 0); - put_byte(s, 0); - put_byte(s, 0); - put_byte(s, 0); - put_byte(s, 0); - put_byte(s, s->level == 9 ? 2 : - (s->strategy >= Z_HUFFMAN_ONLY || s->level < 2 ? - 4 : 0)); - put_byte(s, OS_CODE); - s->status = BUSY_STATE; - } - else { - put_byte(s, (s->gzhead->text ? 1 : 0) + - (s->gzhead->hcrc ? 2 : 0) + - (s->gzhead->extra == Z_NULL ? 0 : 4) + - (s->gzhead->name == Z_NULL ? 0 : 8) + - (s->gzhead->comment == Z_NULL ? 0 : 16) - ); - put_byte(s, (Byte)(s->gzhead->time & 0xff)); - put_byte(s, (Byte)((s->gzhead->time >> 8) & 0xff)); - put_byte(s, (Byte)((s->gzhead->time >> 16) & 0xff)); - put_byte(s, (Byte)((s->gzhead->time >> 24) & 0xff)); - put_byte(s, s->level == 9 ? 2 : - (s->strategy >= Z_HUFFMAN_ONLY || s->level < 2 ? - 4 : 0)); - put_byte(s, s->gzhead->os & 0xff); - if (s->gzhead->extra != Z_NULL) { - put_byte(s, s->gzhead->extra_len & 0xff); - put_byte(s, (s->gzhead->extra_len >> 8) & 0xff); - } - if (s->gzhead->hcrc) - strm->adler = crc32(strm->adler, s->pending_buf, - s->pending); - s->gzindex = 0; - s->status = EXTRA_STATE; - } - } - else -#endif - { - uInt header = (Z_DEFLATED + ((s->w_bits-8)<<4)) << 8; - uInt level_flags; - - if (s->strategy >= Z_HUFFMAN_ONLY || s->level < 2) - level_flags = 0; - else if (s->level < 6) - level_flags = 1; - else if (s->level == 6) - level_flags = 2; - else - level_flags = 3; - header |= (level_flags << 6); - if (s->strstart != 0) header |= PRESET_DICT; - header += 31 - (header % 31); - - s->status = BUSY_STATE; - putShortMSB(s, header); - - /* Save the adler32 of the preset dictionary: */ - if (s->strstart != 0) { - putShortMSB(s, (uInt)(strm->adler >> 16)); - putShortMSB(s, (uInt)(strm->adler & 0xffff)); - } - strm->adler = adler32(0L, Z_NULL, 0); - } - } -#ifdef GZIP - if (s->status == EXTRA_STATE) { - if (s->gzhead->extra != Z_NULL) { - uInt beg = s->pending; /* start of bytes to update crc */ - - while (s->gzindex < (s->gzhead->extra_len & 0xffff)) { - if (s->pending == s->pending_buf_size) { - if (s->gzhead->hcrc && s->pending > beg) - strm->adler = crc32(strm->adler, s->pending_buf + beg, - s->pending - beg); - flush_pending(strm); - beg = s->pending; - if (s->pending == s->pending_buf_size) - break; - } - put_byte(s, s->gzhead->extra[s->gzindex]); - s->gzindex++; - } - if (s->gzhead->hcrc && s->pending > beg) - strm->adler = crc32(strm->adler, s->pending_buf + beg, - s->pending - beg); - if (s->gzindex == s->gzhead->extra_len) { - s->gzindex = 0; - s->status = NAME_STATE; - } - } - else - s->status = NAME_STATE; - } - if (s->status == NAME_STATE) { - if (s->gzhead->name != Z_NULL) { - uInt beg = s->pending; /* start of bytes to update crc */ - int val; - - do { - if (s->pending == s->pending_buf_size) { - if (s->gzhead->hcrc && s->pending > beg) - strm->adler = crc32(strm->adler, s->pending_buf + beg, - s->pending - beg); - flush_pending(strm); - beg = s->pending; - if (s->pending == s->pending_buf_size) { - val = 1; - break; - } - } - val = s->gzhead->name[s->gzindex++]; - put_byte(s, val); - } while (val != 0); - if (s->gzhead->hcrc && s->pending > beg) - strm->adler = crc32(strm->adler, s->pending_buf + beg, - s->pending - beg); - if (val == 0) { - s->gzindex = 0; - s->status = COMMENT_STATE; - } - } - else - s->status = COMMENT_STATE; - } - if (s->status == COMMENT_STATE) { - if (s->gzhead->comment != Z_NULL) { - uInt beg = s->pending; /* start of bytes to update crc */ - int val; - - do { - if (s->pending == s->pending_buf_size) { - if (s->gzhead->hcrc && s->pending > beg) - strm->adler = crc32(strm->adler, s->pending_buf + beg, - s->pending - beg); - flush_pending(strm); - beg = s->pending; - if (s->pending == s->pending_buf_size) { - val = 1; - break; - } - } - val = s->gzhead->comment[s->gzindex++]; - put_byte(s, val); - } while (val != 0); - if (s->gzhead->hcrc && s->pending > beg) - strm->adler = crc32(strm->adler, s->pending_buf + beg, - s->pending - beg); - if (val == 0) - s->status = HCRC_STATE; - } - else - s->status = HCRC_STATE; - } - if (s->status == HCRC_STATE) { - if (s->gzhead->hcrc) { - if (s->pending + 2 > s->pending_buf_size) - flush_pending(strm); - if (s->pending + 2 <= s->pending_buf_size) { - put_byte(s, (Byte)(strm->adler & 0xff)); - put_byte(s, (Byte)((strm->adler >> 8) & 0xff)); - strm->adler = crc32(0L, Z_NULL, 0); - s->status = BUSY_STATE; - } - } - else - s->status = BUSY_STATE; - } -#endif - - /* Flush as much pending output as possible */ - if (s->pending != 0) { - flush_pending(strm); - if (strm->avail_out == 0) { - /* Since avail_out is 0, deflate will be called again with - * more output space, but possibly with both pending and - * avail_in equal to zero. There won't be anything to do, - * but this is not an error situation so make sure we - * return OK instead of BUF_ERROR at next call of deflate: - */ - s->last_flush = -1; - return Z_OK; - } - - /* Make sure there is something to do and avoid duplicate consecutive - * flushes. For repeated and useless calls with Z_FINISH, we keep - * returning Z_STREAM_END instead of Z_BUF_ERROR. - */ - } else if (strm->avail_in == 0 && flush <= old_flush && - flush != Z_FINISH) { - ERR_RETURN(strm, Z_BUF_ERROR); - } - - /* User must not provide more input after the first FINISH: */ - if (s->status == FINISH_STATE && strm->avail_in != 0) { - ERR_RETURN(strm, Z_BUF_ERROR); - } - - /* Start a new block or continue the current one. - */ - if (strm->avail_in != 0 || s->lookahead != 0 || - (flush != Z_NO_FLUSH && s->status != FINISH_STATE)) { - block_state bstate; - - bstate = s->strategy == Z_HUFFMAN_ONLY ? deflate_huff(s, flush) : - (s->strategy == Z_RLE ? deflate_rle(s, flush) : - (*(configuration_table[s->level].func))(s, flush)); - - if (bstate == finish_started || bstate == finish_done) { - s->status = FINISH_STATE; - } - if (bstate == need_more || bstate == finish_started) { - if (strm->avail_out == 0) { - s->last_flush = -1; /* avoid BUF_ERROR next call, see above */ - } - return Z_OK; - /* If flush != Z_NO_FLUSH && avail_out == 0, the next call - * of deflate should use the same flush parameter to make sure - * that the flush is complete. So we don't have to output an - * empty block here, this will be done at next call. This also - * ensures that for a very small output buffer, we emit at most - * one empty block. - */ - } - if (bstate == block_done) { - if (flush == Z_PARTIAL_FLUSH) { - _tr_align(s); - } else if (flush != Z_BLOCK) { /* FULL_FLUSH or SYNC_FLUSH */ - _tr_stored_block(s, (char*)0, 0L, 0); - /* For a full flush, this empty block will be recognized - * as a special marker by inflate_sync(). - */ - if (flush == Z_FULL_FLUSH) { - CLEAR_HASH(s); /* forget history */ - if (s->lookahead == 0) { - s->strstart = 0; - s->block_start = 0L; - } - } - } - flush_pending(strm); - if (strm->avail_out == 0) { - s->last_flush = -1; /* avoid BUF_ERROR at next call, see above */ - return Z_OK; - } - } - } - Assert(strm->avail_out > 0, "bug2"); - - if (flush != Z_FINISH) return Z_OK; - if (s->wrap <= 0) return Z_STREAM_END; - - /* Write the trailer */ -#ifdef GZIP - if (s->wrap == 2) { - put_byte(s, (Byte)(strm->adler & 0xff)); - put_byte(s, (Byte)((strm->adler >> 8) & 0xff)); - put_byte(s, (Byte)((strm->adler >> 16) & 0xff)); - put_byte(s, (Byte)((strm->adler >> 24) & 0xff)); - put_byte(s, (Byte)(strm->total_in & 0xff)); - put_byte(s, (Byte)((strm->total_in >> 8) & 0xff)); - put_byte(s, (Byte)((strm->total_in >> 16) & 0xff)); - put_byte(s, (Byte)((strm->total_in >> 24) & 0xff)); - } - else -#endif - { - putShortMSB(s, (uInt)(strm->adler >> 16)); - putShortMSB(s, (uInt)(strm->adler & 0xffff)); - } - flush_pending(strm); - /* If avail_out is zero, the application will call deflate again - * to flush the rest. - */ - if (s->wrap > 0) s->wrap = -s->wrap; /* write the trailer only once! */ - return s->pending != 0 ? Z_OK : Z_STREAM_END; -} - -/* ========================================================================= */ -int ZEXPORT deflateEnd (strm) - z_streamp strm; -{ - int status; - - if (strm == Z_NULL || strm->state == Z_NULL) return Z_STREAM_ERROR; - - status = strm->state->status; - if (status != INIT_STATE && - status != EXTRA_STATE && - status != NAME_STATE && - status != COMMENT_STATE && - status != HCRC_STATE && - status != BUSY_STATE && - status != FINISH_STATE) { - return Z_STREAM_ERROR; - } - - /* Deallocate in reverse order of allocations: */ - TRY_FREE(strm, strm->state->pending_buf); - TRY_FREE(strm, strm->state->head); - TRY_FREE(strm, strm->state->prev); - TRY_FREE(strm, strm->state->window); - - ZFREE(strm, strm->state); - strm->state = Z_NULL; - - return status == BUSY_STATE ? Z_DATA_ERROR : Z_OK; -} - -/* ========================================================================= - * Copy the source state to the destination state. - * To simplify the source, this is not supported for 16-bit MSDOS (which - * doesn't have enough memory anyway to duplicate compression states). - */ -int ZEXPORT deflateCopy (dest, source) - z_streamp dest; - z_streamp source; -{ -#ifdef MAXSEG_64K - return Z_STREAM_ERROR; -#else - deflate_state *ds; - deflate_state *ss; - ushf *overlay; - - - if (source == Z_NULL || dest == Z_NULL || source->state == Z_NULL) { - return Z_STREAM_ERROR; - } - - ss = source->state; - - zmemcpy(dest, source, sizeof(z_stream)); - - ds = (deflate_state *) ZALLOC(dest, 1, sizeof(deflate_state)); - if (ds == Z_NULL) return Z_MEM_ERROR; - dest->state = (struct internal_state FAR *) ds; - zmemcpy(ds, ss, sizeof(deflate_state)); - ds->strm = dest; - - ds->window = (Bytef *) ZALLOC(dest, ds->w_size, 2*sizeof(Byte)); - ds->prev = (Posf *) ZALLOC(dest, ds->w_size, sizeof(Pos)); - ds->head = (Posf *) ZALLOC(dest, ds->hash_size, sizeof(Pos)); - overlay = (ushf *) ZALLOC(dest, ds->lit_bufsize, sizeof(ush)+2); - ds->pending_buf = (uchf *) overlay; - - if (ds->window == Z_NULL || ds->prev == Z_NULL || ds->head == Z_NULL || - ds->pending_buf == Z_NULL) { - deflateEnd (dest); - return Z_MEM_ERROR; - } - /* following zmemcpy do not work for 16-bit MSDOS */ - zmemcpy(ds->window, ss->window, ds->w_size * 2 * sizeof(Byte)); - zmemcpy(ds->prev, ss->prev, ds->w_size * sizeof(Pos)); - zmemcpy(ds->head, ss->head, ds->hash_size * sizeof(Pos)); - zmemcpy(ds->pending_buf, ss->pending_buf, (uInt)ds->pending_buf_size); - - ds->pending_out = ds->pending_buf + (ss->pending_out - ss->pending_buf); - ds->d_buf = overlay + ds->lit_bufsize/sizeof(ush); - ds->l_buf = ds->pending_buf + (1+sizeof(ush))*ds->lit_bufsize; - - ds->l_desc.dyn_tree = ds->dyn_ltree; - ds->d_desc.dyn_tree = ds->dyn_dtree; - ds->bl_desc.dyn_tree = ds->bl_tree; - - return Z_OK; -#endif /* MAXSEG_64K */ -} - -/* =========================================================================== - * Read a new buffer from the current input stream, update the adler32 - * and total number of bytes read. All deflate() input goes through - * this function so some applications may wish to modify it to avoid - * allocating a large strm->next_in buffer and copying from it. - * (See also flush_pending()). - */ -local int read_buf(strm, buf, size) - z_streamp strm; - Bytef *buf; - unsigned size; -{ - unsigned len = strm->avail_in; - - if (len > size) len = size; - if (len == 0) return 0; - - strm->avail_in -= len; - - if (strm->state->wrap == 1) { - strm->adler = adler32(strm->adler, strm->next_in, len); - } -#ifdef GZIP - else if (strm->state->wrap == 2) { - strm->adler = crc32(strm->adler, strm->next_in, len); - } -#endif - zmemcpy(buf, strm->next_in, len); - strm->next_in += len; - strm->total_in += len; - - return (int)len; -} - -/* =========================================================================== - * Initialize the "longest match" routines for a new zlib stream - */ -local void lm_init (s) - deflate_state *s; -{ - s->window_size = (ulg)2L*s->w_size; - - CLEAR_HASH(s); - - /* Set the default configuration parameters: - */ - s->max_lazy_match = configuration_table[s->level].max_lazy; - s->good_match = configuration_table[s->level].good_length; - s->nice_match = configuration_table[s->level].nice_length; - s->max_chain_length = configuration_table[s->level].max_chain; - - s->strstart = 0; - s->block_start = 0L; - s->lookahead = 0; - s->match_length = s->prev_length = MIN_MATCH-1; - s->match_available = 0; - s->ins_h = 0; -#ifndef FASTEST -#ifdef ASMV - match_init(); /* initialize the asm code */ -#endif -#endif -} - -#ifndef FASTEST -/* =========================================================================== - * Set match_start to the longest match starting at the given string and - * return its length. Matches shorter or equal to prev_length are discarded, - * in which case the result is equal to prev_length and match_start is - * garbage. - * IN assertions: cur_match is the head of the hash chain for the current - * string (strstart) and its distance is <= MAX_DIST, and prev_length >= 1 - * OUT assertion: the match length is not greater than s->lookahead. - */ -#ifndef ASMV -/* For 80x86 and 680x0, an optimized version will be provided in match.asm or - * match.S. The code will be functionally equivalent. - */ -local uInt longest_match(s, cur_match) - deflate_state *s; - IPos cur_match; /* current match */ -{ - unsigned chain_length = s->max_chain_length;/* max hash chain length */ - register Bytef *scan = s->window + s->strstart; /* current string */ - register Bytef *match; /* matched string */ - register int len; /* length of current match */ - int best_len = s->prev_length; /* best match length so far */ - int nice_match = s->nice_match; /* stop if match long enough */ - IPos limit = s->strstart > (IPos)MAX_DIST(s) ? - s->strstart - (IPos)MAX_DIST(s) : NIL; - /* Stop when cur_match becomes <= limit. To simplify the code, - * we prevent matches with the string of window index 0. - */ - Posf *prev = s->prev; - uInt wmask = s->w_mask; - -#ifdef UNALIGNED_OK - /* Compare two bytes at a time. Note: this is not always beneficial. - * Try with and without -DUNALIGNED_OK to check. - */ - register Bytef *strend = s->window + s->strstart + MAX_MATCH - 1; - register ush scan_start = *(ushf*)scan; - register ush scan_end = *(ushf*)(scan+best_len-1); -#else - register Bytef *strend = s->window + s->strstart + MAX_MATCH; - register Byte scan_end1 = scan[best_len-1]; - register Byte scan_end = scan[best_len]; -#endif - - /* The code is optimized for HASH_BITS >= 8 and MAX_MATCH-2 multiple of 16. - * It is easy to get rid of this optimization if necessary. - */ - Assert(s->hash_bits >= 8 && MAX_MATCH == 258, "Code too clever"); - - /* Do not waste too much time if we already have a good match: */ - if (s->prev_length >= s->good_match) { - chain_length >>= 2; - } - /* Do not look for matches beyond the end of the input. This is necessary - * to make deflate deterministic. - */ - if ((uInt)nice_match > s->lookahead) nice_match = s->lookahead; - - Assert((ulg)s->strstart <= s->window_size-MIN_LOOKAHEAD, "need lookahead"); - - do { - Assert(cur_match < s->strstart, "no future"); - match = s->window + cur_match; - - /* Skip to next match if the match length cannot increase - * or if the match length is less than 2. Note that the checks below - * for insufficient lookahead only occur occasionally for performance - * reasons. Therefore uninitialized memory will be accessed, and - * conditional jumps will be made that depend on those values. - * However the length of the match is limited to the lookahead, so - * the output of deflate is not affected by the uninitialized values. - */ -#if (defined(UNALIGNED_OK) && MAX_MATCH == 258) - /* This code assumes sizeof(unsigned short) == 2. Do not use - * UNALIGNED_OK if your compiler uses a different size. - */ - if (*(ushf*)(match+best_len-1) != scan_end || - *(ushf*)match != scan_start) continue; - - /* It is not necessary to compare scan[2] and match[2] since they are - * always equal when the other bytes match, given that the hash keys - * are equal and that HASH_BITS >= 8. Compare 2 bytes at a time at - * strstart+3, +5, ... up to strstart+257. We check for insufficient - * lookahead only every 4th comparison; the 128th check will be made - * at strstart+257. If MAX_MATCH-2 is not a multiple of 8, it is - * necessary to put more guard bytes at the end of the window, or - * to check more often for insufficient lookahead. - */ - Assert(scan[2] == match[2], "scan[2]?"); - scan++, match++; - do { - } while (*(ushf*)(scan+=2) == *(ushf*)(match+=2) && - *(ushf*)(scan+=2) == *(ushf*)(match+=2) && - *(ushf*)(scan+=2) == *(ushf*)(match+=2) && - *(ushf*)(scan+=2) == *(ushf*)(match+=2) && - scan < strend); - /* The funny "do {}" generates better code on most compilers */ - - /* Here, scan <= window+strstart+257 */ - Assert(scan <= s->window+(unsigned)(s->window_size-1), "wild scan"); - if (*scan == *match) scan++; - - len = (MAX_MATCH - 1) - (int)(strend-scan); - scan = strend - (MAX_MATCH-1); - -#else /* UNALIGNED_OK */ - - if (match[best_len] != scan_end || - match[best_len-1] != scan_end1 || - *match != *scan || - *++match != scan[1]) continue; - - /* The check at best_len-1 can be removed because it will be made - * again later. (This heuristic is not always a win.) - * It is not necessary to compare scan[2] and match[2] since they - * are always equal when the other bytes match, given that - * the hash keys are equal and that HASH_BITS >= 8. - */ - scan += 2, match++; - Assert(*scan == *match, "match[2]?"); - - /* We check for insufficient lookahead only every 8th comparison; - * the 256th check will be made at strstart+258. - */ - do { - } while (*++scan == *++match && *++scan == *++match && - *++scan == *++match && *++scan == *++match && - *++scan == *++match && *++scan == *++match && - *++scan == *++match && *++scan == *++match && - scan < strend); - - Assert(scan <= s->window+(unsigned)(s->window_size-1), "wild scan"); - - len = MAX_MATCH - (int)(strend - scan); - scan = strend - MAX_MATCH; - -#endif /* UNALIGNED_OK */ - - if (len > best_len) { - s->match_start = cur_match; - best_len = len; - if (len >= nice_match) break; -#ifdef UNALIGNED_OK - scan_end = *(ushf*)(scan+best_len-1); -#else - scan_end1 = scan[best_len-1]; - scan_end = scan[best_len]; -#endif - } - } while ((cur_match = prev[cur_match & wmask]) > limit - && --chain_length != 0); - - if ((uInt)best_len <= s->lookahead) return (uInt)best_len; - return s->lookahead; -} -#endif /* ASMV */ - -#else /* FASTEST */ - -/* --------------------------------------------------------------------------- - * Optimized version for FASTEST only - */ -local uInt longest_match(s, cur_match) - deflate_state *s; - IPos cur_match; /* current match */ -{ - register Bytef *scan = s->window + s->strstart; /* current string */ - register Bytef *match; /* matched string */ - register int len; /* length of current match */ - register Bytef *strend = s->window + s->strstart + MAX_MATCH; - - /* The code is optimized for HASH_BITS >= 8 and MAX_MATCH-2 multiple of 16. - * It is easy to get rid of this optimization if necessary. - */ - Assert(s->hash_bits >= 8 && MAX_MATCH == 258, "Code too clever"); - - Assert((ulg)s->strstart <= s->window_size-MIN_LOOKAHEAD, "need lookahead"); - - Assert(cur_match < s->strstart, "no future"); - - match = s->window + cur_match; - - /* Return failure if the match length is less than 2: - */ - if (match[0] != scan[0] || match[1] != scan[1]) return MIN_MATCH-1; - - /* The check at best_len-1 can be removed because it will be made - * again later. (This heuristic is not always a win.) - * It is not necessary to compare scan[2] and match[2] since they - * are always equal when the other bytes match, given that - * the hash keys are equal and that HASH_BITS >= 8. - */ - scan += 2, match += 2; - Assert(*scan == *match, "match[2]?"); - - /* We check for insufficient lookahead only every 8th comparison; - * the 256th check will be made at strstart+258. - */ - do { - } while (*++scan == *++match && *++scan == *++match && - *++scan == *++match && *++scan == *++match && - *++scan == *++match && *++scan == *++match && - *++scan == *++match && *++scan == *++match && - scan < strend); - - Assert(scan <= s->window+(unsigned)(s->window_size-1), "wild scan"); - - len = MAX_MATCH - (int)(strend - scan); - - if (len < MIN_MATCH) return MIN_MATCH - 1; - - s->match_start = cur_match; - return (uInt)len <= s->lookahead ? (uInt)len : s->lookahead; -} - -#endif /* FASTEST */ - -#ifdef DEBUG -/* =========================================================================== - * Check that the match at match_start is indeed a match. - */ -local void check_match(s, start, match, length) - deflate_state *s; - IPos start, match; - int length; -{ - /* check that the match is indeed a match */ - if (zmemcmp(s->window + match, - s->window + start, length) != EQUAL) { - fprintf(stderr, " start %u, match %u, length %d\n", - start, match, length); - do { - fprintf(stderr, "%c%c", s->window[match++], s->window[start++]); - } while (--length != 0); - z_error("invalid match"); - } - if (z_verbose > 1) { - fprintf(stderr,"\\[%d,%d]", start-match, length); - do { putc(s->window[start++], stderr); } while (--length != 0); - } -} -#else -# define check_match(s, start, match, length) -#endif /* DEBUG */ - -/* =========================================================================== - * Fill the window when the lookahead becomes insufficient. - * Updates strstart and lookahead. - * - * IN assertion: lookahead < MIN_LOOKAHEAD - * OUT assertions: strstart <= window_size-MIN_LOOKAHEAD - * At least one byte has been read, or avail_in == 0; reads are - * performed for at least two bytes (required for the zip translate_eol - * option -- not supported here). - */ -local void fill_window(s) - deflate_state *s; -{ - register unsigned n, m; - register Posf *p; - unsigned more; /* Amount of free space at the end of the window. */ - uInt wsize = s->w_size; - - do { - more = (unsigned)(s->window_size -(ulg)s->lookahead -(ulg)s->strstart); - - /* Deal with !@#$% 64K limit: */ - if (sizeof(int) <= 2) { - if (more == 0 && s->strstart == 0 && s->lookahead == 0) { - more = wsize; - - } else if (more == (unsigned)(-1)) { - /* Very unlikely, but possible on 16 bit machine if - * strstart == 0 && lookahead == 1 (input done a byte at time) - */ - more--; - } - } - - /* If the window is almost full and there is insufficient lookahead, - * move the upper half to the lower one to make room in the upper half. - */ - if (s->strstart >= wsize+MAX_DIST(s)) { - - zmemcpy(s->window, s->window+wsize, (unsigned)wsize); - s->match_start -= wsize; - s->strstart -= wsize; /* we now have strstart >= MAX_DIST */ - s->block_start -= (long) wsize; - - /* Slide the hash table (could be avoided with 32 bit values - at the expense of memory usage). We slide even when level == 0 - to keep the hash table consistent if we switch back to level > 0 - later. (Using level 0 permanently is not an optimal usage of - zlib, so we don't care about this pathological case.) - */ - n = s->hash_size; - p = &s->head[n]; - do { - m = *--p; - *p = (Pos)(m >= wsize ? m-wsize : NIL); - } while (--n); - - n = wsize; -#ifndef FASTEST - p = &s->prev[n]; - do { - m = *--p; - *p = (Pos)(m >= wsize ? m-wsize : NIL); - /* If n is not on any hash chain, prev[n] is garbage but - * its value will never be used. - */ - } while (--n); -#endif - more += wsize; - } - if (s->strm->avail_in == 0) return; - - /* If there was no sliding: - * strstart <= WSIZE+MAX_DIST-1 && lookahead <= MIN_LOOKAHEAD - 1 && - * more == window_size - lookahead - strstart - * => more >= window_size - (MIN_LOOKAHEAD-1 + WSIZE + MAX_DIST-1) - * => more >= window_size - 2*WSIZE + 2 - * In the BIG_MEM or MMAP case (not yet supported), - * window_size == input_size + MIN_LOOKAHEAD && - * strstart + s->lookahead <= input_size => more >= MIN_LOOKAHEAD. - * Otherwise, window_size == 2*WSIZE so more >= 2. - * If there was sliding, more >= WSIZE. So in all cases, more >= 2. - */ - Assert(more >= 2, "more < 2"); - - n = read_buf(s->strm, s->window + s->strstart + s->lookahead, more); - s->lookahead += n; - - /* Initialize the hash value now that we have some input: */ - if (s->lookahead >= MIN_MATCH) { - s->ins_h = s->window[s->strstart]; - UPDATE_HASH(s, s->ins_h, s->window[s->strstart+1]); -#if MIN_MATCH != 3 - Call UPDATE_HASH() MIN_MATCH-3 more times -#endif - } - /* If the whole input has less than MIN_MATCH bytes, ins_h is garbage, - * but this is not important since only literal bytes will be emitted. - */ - - } while (s->lookahead < MIN_LOOKAHEAD && s->strm->avail_in != 0); - - /* If the WIN_INIT bytes after the end of the current data have never been - * written, then zero those bytes in order to avoid memory check reports of - * the use of uninitialized (or uninitialised as Julian writes) bytes by - * the longest match routines. Update the high water mark for the next - * time through here. WIN_INIT is set to MAX_MATCH since the longest match - * routines allow scanning to strstart + MAX_MATCH, ignoring lookahead. - */ - if (s->high_water < s->window_size) { - ulg curr = s->strstart + (ulg)(s->lookahead); - ulg init; - - if (s->high_water < curr) { - /* Previous high water mark below current data -- zero WIN_INIT - * bytes or up to end of window, whichever is less. - */ - init = s->window_size - curr; - if (init > WIN_INIT) - init = WIN_INIT; - zmemzero(s->window + curr, (unsigned)init); - s->high_water = curr + init; - } - else if (s->high_water < (ulg)curr + WIN_INIT) { - /* High water mark at or above current data, but below current data - * plus WIN_INIT -- zero out to current data plus WIN_INIT, or up - * to end of window, whichever is less. - */ - init = (ulg)curr + WIN_INIT - s->high_water; - if (init > s->window_size - s->high_water) - init = s->window_size - s->high_water; - zmemzero(s->window + s->high_water, (unsigned)init); - s->high_water += init; - } - } -} - -/* =========================================================================== - * Flush the current block, with given end-of-file flag. - * IN assertion: strstart is set to the end of the current match. - */ -#define FLUSH_BLOCK_ONLY(s, last) { \ - _tr_flush_block(s, (s->block_start >= 0L ? \ - (charf *)&s->window[(unsigned)s->block_start] : \ - (charf *)Z_NULL), \ - (ulg)((long)s->strstart - s->block_start), \ - (last)); \ - s->block_start = s->strstart; \ - flush_pending(s->strm); \ - Tracev((stderr,"[FLUSH]")); \ -} - -/* Same but force premature exit if necessary. */ -#define FLUSH_BLOCK(s, last) { \ - FLUSH_BLOCK_ONLY(s, last); \ - if (s->strm->avail_out == 0) return (last) ? finish_started : need_more; \ -} - -/* =========================================================================== - * Copy without compression as much as possible from the input stream, return - * the current block state. - * This function does not insert new strings in the dictionary since - * uncompressible data is probably not useful. This function is used - * only for the level=0 compression option. - * NOTE: this function should be optimized to avoid extra copying from - * window to pending_buf. - */ -local block_state deflate_stored(s, flush) - deflate_state *s; - int flush; -{ - /* Stored blocks are limited to 0xffff bytes, pending_buf is limited - * to pending_buf_size, and each stored block has a 5 byte header: - */ - ulg max_block_size = 0xffff; - ulg max_start; - - if (max_block_size > s->pending_buf_size - 5) { - max_block_size = s->pending_buf_size - 5; - } - - /* Copy as much as possible from input to output: */ - for (;;) { - /* Fill the window as much as possible: */ - if (s->lookahead <= 1) { - - Assert(s->strstart < s->w_size+MAX_DIST(s) || - s->block_start >= (long)s->w_size, "slide too late"); - - fill_window(s); - if (s->lookahead == 0 && flush == Z_NO_FLUSH) return need_more; - - if (s->lookahead == 0) break; /* flush the current block */ - } - Assert(s->block_start >= 0L, "block gone"); - - s->strstart += s->lookahead; - s->lookahead = 0; - - /* Emit a stored block if pending_buf will be full: */ - max_start = s->block_start + max_block_size; - if (s->strstart == 0 || (ulg)s->strstart >= max_start) { - /* strstart == 0 is possible when wraparound on 16-bit machine */ - s->lookahead = (uInt)(s->strstart - max_start); - s->strstart = (uInt)max_start; - FLUSH_BLOCK(s, 0); - } - /* Flush if we may have to slide, otherwise block_start may become - * negative and the data will be gone: - */ - if (s->strstart - (uInt)s->block_start >= MAX_DIST(s)) { - FLUSH_BLOCK(s, 0); - } - } - FLUSH_BLOCK(s, flush == Z_FINISH); - return flush == Z_FINISH ? finish_done : block_done; -} - -/* =========================================================================== - * Compress as much as possible from the input stream, return the current - * block state. - * This function does not perform lazy evaluation of matches and inserts - * new strings in the dictionary only for unmatched strings or for short - * matches. It is used only for the fast compression options. - */ -local block_state deflate_fast(s, flush) - deflate_state *s; - int flush; -{ - IPos hash_head; /* head of the hash chain */ - int bflush; /* set if current block must be flushed */ - - for (;;) { - /* Make sure that we always have enough lookahead, except - * at the end of the input file. We need MAX_MATCH bytes - * for the next match, plus MIN_MATCH bytes to insert the - * string following the next match. - */ - if (s->lookahead < MIN_LOOKAHEAD) { - fill_window(s); - if (s->lookahead < MIN_LOOKAHEAD && flush == Z_NO_FLUSH) { - return need_more; - } - if (s->lookahead == 0) break; /* flush the current block */ - } - - /* Insert the string window[strstart .. strstart+2] in the - * dictionary, and set hash_head to the head of the hash chain: - */ - hash_head = NIL; - if (s->lookahead >= MIN_MATCH) { - INSERT_STRING(s, s->strstart, hash_head); - } - - /* Find the longest match, discarding those <= prev_length. - * At this point we have always match_length < MIN_MATCH - */ - if (hash_head != NIL && s->strstart - hash_head <= MAX_DIST(s)) { - /* To simplify the code, we prevent matches with the string - * of window index 0 (in particular we have to avoid a match - * of the string with itself at the start of the input file). - */ - s->match_length = longest_match (s, hash_head); - /* longest_match() sets match_start */ - } - if (s->match_length >= MIN_MATCH) { - check_match(s, s->strstart, s->match_start, s->match_length); - - _tr_tally_dist(s, s->strstart - s->match_start, - s->match_length - MIN_MATCH, bflush); - - s->lookahead -= s->match_length; - - /* Insert new strings in the hash table only if the match length - * is not too large. This saves time but degrades compression. - */ -#ifndef FASTEST - if (s->match_length <= s->max_insert_length && - s->lookahead >= MIN_MATCH) { - s->match_length--; /* string at strstart already in table */ - do { - s->strstart++; - INSERT_STRING(s, s->strstart, hash_head); - /* strstart never exceeds WSIZE-MAX_MATCH, so there are - * always MIN_MATCH bytes ahead. - */ - } while (--s->match_length != 0); - s->strstart++; - } else -#endif - { - s->strstart += s->match_length; - s->match_length = 0; - s->ins_h = s->window[s->strstart]; - UPDATE_HASH(s, s->ins_h, s->window[s->strstart+1]); -#if MIN_MATCH != 3 - Call UPDATE_HASH() MIN_MATCH-3 more times -#endif - /* If lookahead < MIN_MATCH, ins_h is garbage, but it does not - * matter since it will be recomputed at next deflate call. - */ - } - } else { - /* No match, output a literal byte */ - Tracevv((stderr,"%c", s->window[s->strstart])); - _tr_tally_lit (s, s->window[s->strstart], bflush); - s->lookahead--; - s->strstart++; - } - if (bflush) FLUSH_BLOCK(s, 0); - } - FLUSH_BLOCK(s, flush == Z_FINISH); - return flush == Z_FINISH ? finish_done : block_done; -} - -#ifndef FASTEST -/* =========================================================================== - * Same as above, but achieves better compression. We use a lazy - * evaluation for matches: a match is finally adopted only if there is - * no better match at the next window position. - */ -local block_state deflate_slow(s, flush) - deflate_state *s; - int flush; -{ - IPos hash_head; /* head of hash chain */ - int bflush; /* set if current block must be flushed */ - - /* Process the input block. */ - for (;;) { - /* Make sure that we always have enough lookahead, except - * at the end of the input file. We need MAX_MATCH bytes - * for the next match, plus MIN_MATCH bytes to insert the - * string following the next match. - */ - if (s->lookahead < MIN_LOOKAHEAD) { - fill_window(s); - if (s->lookahead < MIN_LOOKAHEAD && flush == Z_NO_FLUSH) { - return need_more; - } - if (s->lookahead == 0) break; /* flush the current block */ - } - - /* Insert the string window[strstart .. strstart+2] in the - * dictionary, and set hash_head to the head of the hash chain: - */ - hash_head = NIL; - if (s->lookahead >= MIN_MATCH) { - INSERT_STRING(s, s->strstart, hash_head); - } - - /* Find the longest match, discarding those <= prev_length. - */ - s->prev_length = s->match_length, s->prev_match = s->match_start; - s->match_length = MIN_MATCH-1; - - if (hash_head != NIL && s->prev_length < s->max_lazy_match && - s->strstart - hash_head <= MAX_DIST(s)) { - /* To simplify the code, we prevent matches with the string - * of window index 0 (in particular we have to avoid a match - * of the string with itself at the start of the input file). - */ - s->match_length = longest_match (s, hash_head); - /* longest_match() sets match_start */ - - if (s->match_length <= 5 && (s->strategy == Z_FILTERED -#if TOO_FAR <= 32767 - || (s->match_length == MIN_MATCH && - s->strstart - s->match_start > TOO_FAR) -#endif - )) { - - /* If prev_match is also MIN_MATCH, match_start is garbage - * but we will ignore the current match anyway. - */ - s->match_length = MIN_MATCH-1; - } - } - /* If there was a match at the previous step and the current - * match is not better, output the previous match: - */ - if (s->prev_length >= MIN_MATCH && s->match_length <= s->prev_length) { - uInt max_insert = s->strstart + s->lookahead - MIN_MATCH; - /* Do not insert strings in hash table beyond this. */ - - check_match(s, s->strstart-1, s->prev_match, s->prev_length); - - _tr_tally_dist(s, s->strstart -1 - s->prev_match, - s->prev_length - MIN_MATCH, bflush); - - /* Insert in hash table all strings up to the end of the match. - * strstart-1 and strstart are already inserted. If there is not - * enough lookahead, the last two strings are not inserted in - * the hash table. - */ - s->lookahead -= s->prev_length-1; - s->prev_length -= 2; - do { - if (++s->strstart <= max_insert) { - INSERT_STRING(s, s->strstart, hash_head); - } - } while (--s->prev_length != 0); - s->match_available = 0; - s->match_length = MIN_MATCH-1; - s->strstart++; - - if (bflush) FLUSH_BLOCK(s, 0); - - } else if (s->match_available) { - /* If there was no match at the previous position, output a - * single literal. If there was a match but the current match - * is longer, truncate the previous match to a single literal. - */ - Tracevv((stderr,"%c", s->window[s->strstart-1])); - _tr_tally_lit(s, s->window[s->strstart-1], bflush); - if (bflush) { - FLUSH_BLOCK_ONLY(s, 0); - } - s->strstart++; - s->lookahead--; - if (s->strm->avail_out == 0) return need_more; - } else { - /* There is no previous match to compare with, wait for - * the next step to decide. - */ - s->match_available = 1; - s->strstart++; - s->lookahead--; - } - } - Assert (flush != Z_NO_FLUSH, "no flush?"); - if (s->match_available) { - Tracevv((stderr,"%c", s->window[s->strstart-1])); - _tr_tally_lit(s, s->window[s->strstart-1], bflush); - s->match_available = 0; - } - FLUSH_BLOCK(s, flush == Z_FINISH); - return flush == Z_FINISH ? finish_done : block_done; -} -#endif /* FASTEST */ - -/* =========================================================================== - * For Z_RLE, simply look for runs of bytes, generate matches only of distance - * one. Do not maintain a hash table. (It will be regenerated if this run of - * deflate switches away from Z_RLE.) - */ -local block_state deflate_rle(s, flush) - deflate_state *s; - int flush; -{ - int bflush; /* set if current block must be flushed */ - uInt prev; /* byte at distance one to match */ - Bytef *scan, *strend; /* scan goes up to strend for length of run */ - - for (;;) { - /* Make sure that we always have enough lookahead, except - * at the end of the input file. We need MAX_MATCH bytes - * for the longest encodable run. - */ - if (s->lookahead < MAX_MATCH) { - fill_window(s); - if (s->lookahead < MAX_MATCH && flush == Z_NO_FLUSH) { - return need_more; - } - if (s->lookahead == 0) break; /* flush the current block */ - } - - /* See how many times the previous byte repeats */ - s->match_length = 0; - if (s->lookahead >= MIN_MATCH && s->strstart > 0) { - scan = s->window + s->strstart - 1; - prev = *scan; - if (prev == *++scan && prev == *++scan && prev == *++scan) { - strend = s->window + s->strstart + MAX_MATCH; - do { - } while (prev == *++scan && prev == *++scan && - prev == *++scan && prev == *++scan && - prev == *++scan && prev == *++scan && - prev == *++scan && prev == *++scan && - scan < strend); - s->match_length = MAX_MATCH - (int)(strend - scan); - if (s->match_length > s->lookahead) - s->match_length = s->lookahead; - } - } - - /* Emit match if have run of MIN_MATCH or longer, else emit literal */ - if (s->match_length >= MIN_MATCH) { - check_match(s, s->strstart, s->strstart - 1, s->match_length); - - _tr_tally_dist(s, 1, s->match_length - MIN_MATCH, bflush); - - s->lookahead -= s->match_length; - s->strstart += s->match_length; - s->match_length = 0; - } else { - /* No match, output a literal byte */ - Tracevv((stderr,"%c", s->window[s->strstart])); - _tr_tally_lit (s, s->window[s->strstart], bflush); - s->lookahead--; - s->strstart++; - } - if (bflush) FLUSH_BLOCK(s, 0); - } - FLUSH_BLOCK(s, flush == Z_FINISH); - return flush == Z_FINISH ? finish_done : block_done; -} - -/* =========================================================================== - * For Z_HUFFMAN_ONLY, do not look for matches. Do not maintain a hash table. - * (It will be regenerated if this run of deflate switches away from Huffman.) - */ -local block_state deflate_huff(s, flush) - deflate_state *s; - int flush; -{ - int bflush; /* set if current block must be flushed */ - - for (;;) { - /* Make sure that we have a literal to write. */ - if (s->lookahead == 0) { - fill_window(s); - if (s->lookahead == 0) { - if (flush == Z_NO_FLUSH) - return need_more; - break; /* flush the current block */ - } - } - - /* Output a literal byte */ - s->match_length = 0; - Tracevv((stderr,"%c", s->window[s->strstart])); - _tr_tally_lit (s, s->window[s->strstart], bflush); - s->lookahead--; - s->strstart++; - if (bflush) FLUSH_BLOCK(s, 0); - } - FLUSH_BLOCK(s, flush == Z_FINISH); - return flush == Z_FINISH ? finish_done : block_done; -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/zlib/deflate.h b/app/jni/src/libultraship/extern/StormLib/src/zlib/deflate.h deleted file mode 100644 index cbf0d1e..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/zlib/deflate.h +++ /dev/null @@ -1,342 +0,0 @@ -/* deflate.h -- internal compression state - * Copyright (C) 1995-2010 Jean-loup Gailly - * For conditions of distribution and use, see copyright notice in zlib.h - */ - -/* WARNING: this file should *not* be used by applications. It is - part of the implementation of the compression library and is - subject to change. Applications should only use zlib.h. - */ - -/* @(#) $Id$ */ - -#ifndef DEFLATE_H -#define DEFLATE_H - -#include "zutil.h" - -/* define NO_GZIP when compiling if you want to disable gzip header and - trailer creation by deflate(). NO_GZIP would be used to avoid linking in - the crc code when it is not needed. For shared libraries, gzip encoding - should be left enabled. */ -#ifndef NO_GZIP -# define GZIP -#endif - -/* =========================================================================== - * Internal compression state. - */ - -#define LENGTH_CODES 29 -/* number of length codes, not counting the special END_BLOCK code */ - -#define LITERALS 256 -/* number of literal bytes 0..255 */ - -#define L_CODES (LITERALS+1+LENGTH_CODES) -/* number of Literal or Length codes, including the END_BLOCK code */ - -#define D_CODES 30 -/* number of distance codes */ - -#define BL_CODES 19 -/* number of codes used to transfer the bit lengths */ - -#define HEAP_SIZE (2*L_CODES+1) -/* maximum heap size */ - -#define MAX_BITS 15 -/* All codes must not exceed MAX_BITS bits */ - -#define INIT_STATE 42 -#define EXTRA_STATE 69 -#define NAME_STATE 73 -#define COMMENT_STATE 91 -#define HCRC_STATE 103 -#define BUSY_STATE 113 -#define FINISH_STATE 666 -/* Stream status */ - - -/* Data structure describing a single value and its code string. */ -typedef struct ct_data_s { - union { - ush freq; /* frequency count */ - ush code; /* bit string */ - } fc; - union { - ush dad; /* father node in Huffman tree */ - ush len; /* length of bit string */ - } dl; -} FAR ct_data; - -#define Freq fc.freq -#define Code fc.code -#define Dad dl.dad -#define Len dl.len - -typedef struct static_tree_desc_s static_tree_desc; - -typedef struct tree_desc_s { - ct_data *dyn_tree; /* the dynamic tree */ - int max_code; /* largest code with non zero frequency */ - static_tree_desc *stat_desc; /* the corresponding static tree */ -} FAR tree_desc; - -typedef ush Pos; -typedef Pos FAR Posf; -typedef unsigned IPos; - -/* A Pos is an index in the character window. We use short instead of int to - * save space in the various tables. IPos is used only for parameter passing. - */ - -typedef struct internal_state { - z_streamp strm; /* pointer back to this zlib stream */ - int status; /* as the name implies */ - Bytef *pending_buf; /* output still pending */ - ulg pending_buf_size; /* size of pending_buf */ - Bytef *pending_out; /* next pending byte to output to the stream */ - uInt pending; /* nb of bytes in the pending buffer */ - int wrap; /* bit 0 true for zlib, bit 1 true for gzip */ - gz_headerp gzhead; /* gzip header information to write */ - uInt gzindex; /* where in extra, name, or comment */ - Byte method; /* STORED (for zip only) or DEFLATED */ - int last_flush; /* value of flush param for previous deflate call */ - - /* used by deflate.c: */ - - uInt w_size; /* LZ77 window size (32K by default) */ - uInt w_bits; /* log2(w_size) (8..16) */ - uInt w_mask; /* w_size - 1 */ - - Bytef *window; - /* Sliding window. Input bytes are read into the second half of the window, - * and move to the first half later to keep a dictionary of at least wSize - * bytes. With this organization, matches are limited to a distance of - * wSize-MAX_MATCH bytes, but this ensures that IO is always - * performed with a length multiple of the block size. Also, it limits - * the window size to 64K, which is quite useful on MSDOS. - * To do: use the user input buffer as sliding window. - */ - - ulg window_size; - /* Actual size of window: 2*wSize, except when the user input buffer - * is directly used as sliding window. - */ - - Posf *prev; - /* Link to older string with same hash index. To limit the size of this - * array to 64K, this link is maintained only for the last 32K strings. - * An index in this array is thus a window index modulo 32K. - */ - - Posf *head; /* Heads of the hash chains or NIL. */ - - uInt ins_h; /* hash index of string to be inserted */ - uInt hash_size; /* number of elements in hash table */ - uInt hash_bits; /* log2(hash_size) */ - uInt hash_mask; /* hash_size-1 */ - - uInt hash_shift; - /* Number of bits by which ins_h must be shifted at each input - * step. It must be such that after MIN_MATCH steps, the oldest - * byte no longer takes part in the hash key, that is: - * hash_shift * MIN_MATCH >= hash_bits - */ - - long block_start; - /* Window position at the beginning of the current output block. Gets - * negative when the window is moved backwards. - */ - - uInt match_length; /* length of best match */ - IPos prev_match; /* previous match */ - int match_available; /* set if previous match exists */ - uInt strstart; /* start of string to insert */ - uInt match_start; /* start of matching string */ - uInt lookahead; /* number of valid bytes ahead in window */ - - uInt prev_length; - /* Length of the best match at previous step. Matches not greater than this - * are discarded. This is used in the lazy match evaluation. - */ - - uInt max_chain_length; - /* To speed up deflation, hash chains are never searched beyond this - * length. A higher limit improves compression ratio but degrades the - * speed. - */ - - uInt max_lazy_match; - /* Attempt to find a better match only when the current match is strictly - * smaller than this value. This mechanism is used only for compression - * levels >= 4. - */ -# define max_insert_length max_lazy_match - /* Insert new strings in the hash table only if the match length is not - * greater than this length. This saves time but degrades compression. - * max_insert_length is used only for compression levels <= 3. - */ - - int level; /* compression level (1..9) */ - int strategy; /* favor or force Huffman coding*/ - - uInt good_match; - /* Use a faster search when the previous match is longer than this */ - - int nice_match; /* Stop searching when current match exceeds this */ - - /* used by trees.c: */ - /* Didn't use ct_data typedef below to supress compiler warning */ - struct ct_data_s dyn_ltree[HEAP_SIZE]; /* literal and length tree */ - struct ct_data_s dyn_dtree[2*D_CODES+1]; /* distance tree */ - struct ct_data_s bl_tree[2*BL_CODES+1]; /* Huffman tree for bit lengths */ - - struct tree_desc_s l_desc; /* desc. for literal tree */ - struct tree_desc_s d_desc; /* desc. for distance tree */ - struct tree_desc_s bl_desc; /* desc. for bit length tree */ - - ush bl_count[MAX_BITS+1]; - /* number of codes at each bit length for an optimal tree */ - - int heap[2*L_CODES+1]; /* heap used to build the Huffman trees */ - int heap_len; /* number of elements in the heap */ - int heap_max; /* element of largest frequency */ - /* The sons of heap[n] are heap[2*n] and heap[2*n+1]. heap[0] is not used. - * The same heap array is used to build all trees. - */ - - uch depth[2*L_CODES+1]; - /* Depth of each subtree used as tie breaker for trees of equal frequency - */ - - uchf *l_buf; /* buffer for literals or lengths */ - - uInt lit_bufsize; - /* Size of match buffer for literals/lengths. There are 4 reasons for - * limiting lit_bufsize to 64K: - * - frequencies can be kept in 16 bit counters - * - if compression is not successful for the first block, all input - * data is still in the window so we can still emit a stored block even - * when input comes from standard input. (This can also be done for - * all blocks if lit_bufsize is not greater than 32K.) - * - if compression is not successful for a file smaller than 64K, we can - * even emit a stored file instead of a stored block (saving 5 bytes). - * This is applicable only for zip (not gzip or zlib). - * - creating new Huffman trees less frequently may not provide fast - * adaptation to changes in the input data statistics. (Take for - * example a binary file with poorly compressible code followed by - * a highly compressible string table.) Smaller buffer sizes give - * fast adaptation but have of course the overhead of transmitting - * trees more frequently. - * - I can't count above 4 - */ - - uInt last_lit; /* running index in l_buf */ - - ushf *d_buf; - /* Buffer for distances. To simplify the code, d_buf and l_buf have - * the same number of elements. To use different lengths, an extra flag - * array would be necessary. - */ - - ulg opt_len; /* bit length of current block with optimal trees */ - ulg static_len; /* bit length of current block with static trees */ - uInt matches; /* number of string matches in current block */ - int last_eob_len; /* bit length of EOB code for last block */ - -#ifdef DEBUG - ulg compressed_len; /* total bit length of compressed file mod 2^32 */ - ulg bits_sent; /* bit length of compressed data sent mod 2^32 */ -#endif - - ush bi_buf; - /* Output buffer. bits are inserted starting at the bottom (least - * significant bits). - */ - int bi_valid; - /* Number of valid bits in bi_buf. All bits above the last valid bit - * are always zero. - */ - - ulg high_water; - /* High water mark offset in window for initialized bytes -- bytes above - * this are set to zero in order to avoid memory check warnings when - * longest match routines access bytes past the input. This is then - * updated to the new high water mark. - */ - -} FAR deflate_state; - -/* Output a byte on the stream. - * IN assertion: there is enough room in pending_buf. - */ -#define put_byte(s, c) {s->pending_buf[s->pending++] = (c);} - - -#define MIN_LOOKAHEAD (MAX_MATCH+MIN_MATCH+1) -/* Minimum amount of lookahead, except at the end of the input file. - * See deflate.c for comments about the MIN_MATCH+1. - */ - -#define MAX_DIST(s) ((s)->w_size-MIN_LOOKAHEAD) -/* In order to simplify the code, particularly on 16 bit machines, match - * distances are limited to MAX_DIST instead of WSIZE. - */ - -#define WIN_INIT MAX_MATCH -/* Number of bytes after end of data in window to initialize in order to avoid - memory checker errors from longest match routines */ - - /* in trees.c */ -void ZLIB_INTERNAL _tr_init OF((deflate_state *s)); -int ZLIB_INTERNAL _tr_tally OF((deflate_state *s, unsigned dist, unsigned lc)); -void ZLIB_INTERNAL _tr_flush_block OF((deflate_state *s, charf *buf, - ulg stored_len, int last)); -void ZLIB_INTERNAL _tr_align OF((deflate_state *s)); -void ZLIB_INTERNAL _tr_stored_block OF((deflate_state *s, charf *buf, - ulg stored_len, int last)); - -#define d_code(dist) \ - ((dist) < 256 ? _dist_code[dist] : _dist_code[256+((dist)>>7)]) -/* Mapping from a distance to a distance code. dist is the distance - 1 and - * must not have side effects. _dist_code[256] and _dist_code[257] are never - * used. - */ - -#ifndef DEBUG -/* Inline versions of _tr_tally for speed: */ - -#if defined(GEN_TREES_H) || !defined(STDC) - extern uch ZLIB_INTERNAL _length_code[]; - extern uch ZLIB_INTERNAL _dist_code[]; -#else - extern const uch ZLIB_INTERNAL _length_code[]; - extern const uch ZLIB_INTERNAL _dist_code[]; -#endif - -# define _tr_tally_lit(s, c, flush) \ - { uch cc = (c); \ - s->d_buf[s->last_lit] = 0; \ - s->l_buf[s->last_lit++] = cc; \ - s->dyn_ltree[cc].Freq++; \ - flush = (s->last_lit == s->lit_bufsize-1); \ - } -# define _tr_tally_dist(s, distance, length, flush) \ - { uch len = (length); \ - ush dist = (distance); \ - s->d_buf[s->last_lit] = dist; \ - s->l_buf[s->last_lit++] = len; \ - dist--; \ - s->dyn_ltree[_length_code[len]+LITERALS+1].Freq++; \ - s->dyn_dtree[d_code(dist)].Freq++; \ - flush = (s->last_lit == s->lit_bufsize-1); \ - } -#else -# define _tr_tally_lit(s, c, flush) flush = _tr_tally(s, 0, c) -# define _tr_tally_dist(s, distance, length, flush) \ - flush = _tr_tally(s, distance, length) -#endif - -#endif /* DEFLATE_H */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/zlib/gzguts.h b/app/jni/src/libultraship/extern/StormLib/src/zlib/gzguts.h deleted file mode 100644 index 990a4d2..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/zlib/gzguts.h +++ /dev/null @@ -1,218 +0,0 @@ -/* gzguts.h -- zlib internal header definitions for gz* operations - * Copyright (C) 2004, 2005, 2010, 2011, 2012, 2013, 2016 Mark Adler - * For conditions of distribution and use, see copyright notice in zlib.h - */ - -#ifdef _LARGEFILE64_SOURCE -# ifndef _LARGEFILE_SOURCE -# define _LARGEFILE_SOURCE 1 -# endif -# ifdef _FILE_OFFSET_BITS -# undef _FILE_OFFSET_BITS -# endif -#endif - -#ifdef HAVE_HIDDEN -# define ZLIB_INTERNAL __attribute__((visibility ("hidden"))) -#else -# define ZLIB_INTERNAL -#endif - -#include -#include "zlib.h" -#ifdef STDC -# include -# include -# include -#endif - -#ifndef _POSIX_SOURCE -# define _POSIX_SOURCE -#endif -#include - -#ifdef _WIN32 -# include -#endif - -#if defined(__TURBOC__) || defined(_MSC_VER) || defined(_WIN32) -# include -#endif - -#if defined(_WIN32) || defined(__CYGWIN__) -# define WIDECHAR -#endif - -#ifdef WINAPI_FAMILY -# define open _open -# define read _read -# define write _write -# define close _close -#endif - -#ifdef NO_DEFLATE /* for compatibility with old definition */ -# define NO_GZCOMPRESS -#endif - -#if defined(STDC99) || (defined(__TURBOC__) && __TURBOC__ >= 0x550) -# ifndef HAVE_VSNPRINTF -# define HAVE_VSNPRINTF -# endif -#endif - -#if defined(__CYGWIN__) -# ifndef HAVE_VSNPRINTF -# define HAVE_VSNPRINTF -# endif -#endif - -#if defined(MSDOS) && defined(__BORLANDC__) && (BORLANDC > 0x410) -# ifndef HAVE_VSNPRINTF -# define HAVE_VSNPRINTF -# endif -#endif - -#ifndef HAVE_VSNPRINTF -# ifdef MSDOS -/* vsnprintf may exist on some MS-DOS compilers (DJGPP?), - but for now we just assume it doesn't. */ -# define NO_vsnprintf -# endif -# ifdef __TURBOC__ -# define NO_vsnprintf -# endif -# ifdef WIN32 -/* In Win32, vsnprintf is available as the "non-ANSI" _vsnprintf. */ -# if !defined(vsnprintf) && !defined(NO_vsnprintf) -# if !defined(_MSC_VER) || ( defined(_MSC_VER) && _MSC_VER < 1500 ) -# define vsnprintf _vsnprintf -# endif -# endif -# endif -# ifdef __SASC -# define NO_vsnprintf -# endif -# ifdef VMS -# define NO_vsnprintf -# endif -# ifdef __OS400__ -# define NO_vsnprintf -# endif -# ifdef __MVS__ -# define NO_vsnprintf -# endif -#endif - -/* unlike snprintf (which is required in C99), _snprintf does not guarantee - null termination of the result -- however this is only used in gzlib.c where - the result is assured to fit in the space provided */ -#if defined(_MSC_VER) && _MSC_VER < 1900 -# define snprintf _snprintf -#endif - -#ifndef local -# define local static -#endif -/* since "static" is used to mean two completely different things in C, we - define "local" for the non-static meaning of "static", for readability - (compile with -Dlocal if your debugger can't find static symbols) */ - -/* gz* functions always use library allocation functions */ -#ifndef STDC - extern voidp malloc OF((uInt size)); - extern void free OF((voidpf ptr)); -#endif - -/* get errno and strerror definition */ -#if defined UNDER_CE -# include -# define zstrerror() gz_strwinerror((DWORD)GetLastError()) -#else -# ifndef NO_STRERROR -# include -# define zstrerror() strerror(errno) -# else -# define zstrerror() "stdio error (consult errno)" -# endif -#endif - -/* provide prototypes for these when building zlib without LFS */ -#if !defined(_LARGEFILE64_SOURCE) || _LFS64_LARGEFILE-0 == 0 - ZEXTERN gzFile ZEXPORT gzopen64 OF((const char *, const char *)); - ZEXTERN z_off64_t ZEXPORT gzseek64 OF((gzFile, z_off64_t, int)); - ZEXTERN z_off64_t ZEXPORT gztell64 OF((gzFile)); - ZEXTERN z_off64_t ZEXPORT gzoffset64 OF((gzFile)); -#endif - -/* default memLevel */ -#if MAX_MEM_LEVEL >= 8 -# define DEF_MEM_LEVEL 8 -#else -# define DEF_MEM_LEVEL MAX_MEM_LEVEL -#endif - -/* default i/o buffer size -- double this for output when reading (this and - twice this must be able to fit in an unsigned type) */ -#define GZBUFSIZE 8192 - -/* gzip modes, also provide a little integrity check on the passed structure */ -#define GZ_NONE 0 -#define GZ_READ 7247 -#define GZ_WRITE 31153 -#define GZ_APPEND 1 /* mode set to GZ_WRITE after the file is opened */ - -/* values for gz_state how */ -#define LOOK 0 /* look for a gzip header */ -#define COPY 1 /* copy input directly */ -#define GZIP 2 /* decompress a gzip stream */ - -/* internal gzip file state data structure */ -typedef struct { - /* exposed contents for gzgetc() macro */ - struct gzFile_s x; /* "x" for exposed */ - /* x.have: number of bytes available at x.next */ - /* x.next: next output data to deliver or write */ - /* x.pos: current position in uncompressed data */ - /* used for both reading and writing */ - int mode; /* see gzip modes above */ - int fd; /* file descriptor */ - char *path; /* path or fd for error messages */ - unsigned size; /* buffer size, zero if not allocated yet */ - unsigned want; /* requested buffer size, default is GZBUFSIZE */ - unsigned char *in; /* input buffer (double-sized when writing) */ - unsigned char *out; /* output buffer (double-sized when reading) */ - int direct; /* 0 if processing gzip, 1 if transparent */ - /* just for reading */ - int how; /* 0: get header, 1: copy, 2: decompress */ - z_off64_t start; /* where the gzip data started, for rewinding */ - int eof; /* true if end of input file reached */ - int past; /* true if read requested past end */ - /* just for writing */ - int level; /* compression level */ - int strategy; /* compression strategy */ - /* seek request */ - z_off64_t skip; /* amount to skip (already rewound if backwards) */ - int seek; /* true if seek request pending */ - /* error information */ - int err; /* error code */ - char *msg; /* error message */ - /* zlib inflate or deflate stream */ - z_stream strm; /* stream structure in-place (not a pointer) */ -} gz_state; -typedef gz_state FAR *gz_statep; - -/* shared functions */ -void ZLIB_INTERNAL gz_error OF((gz_statep, int, const char *)); -#if defined UNDER_CE -char ZLIB_INTERNAL *gz_strwinerror OF((DWORD error)); -#endif - -/* GT_OFF(x), where x is an unsigned value, is true if x > maximum z_off64_t - value -- needed when comparing unsigned to z_off64_t, which is signed - (possible z_off64_t types off_t, off64_t, and long are all signed) */ -#ifdef INT_MAX -# define GT_OFF(x) (sizeof(int) == sizeof(z_off64_t) && (x) > INT_MAX) -#else -unsigned ZLIB_INTERNAL gz_intmax OF((void)); -# define GT_OFF(x) (sizeof(int) == sizeof(z_off64_t) && (x) > gz_intmax()) -#endif diff --git a/app/jni/src/libultraship/extern/StormLib/src/zlib/inffast.c b/app/jni/src/libultraship/extern/StormLib/src/zlib/inffast.c deleted file mode 100644 index 2f1d60b..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/zlib/inffast.c +++ /dev/null @@ -1,340 +0,0 @@ -/* inffast.c -- fast decoding - * Copyright (C) 1995-2008, 2010 Mark Adler - * For conditions of distribution and use, see copyright notice in zlib.h - */ - -#include "zutil.h" -#include "inftrees.h" -#include "inflate.h" -#include "inffast.h" - -#ifndef ASMINF - -/* Allow machine dependent optimization for post-increment or pre-increment. - Based on testing to date, - Pre-increment preferred for: - - PowerPC G3 (Adler) - - MIPS R5000 (Randers-Pehrson) - Post-increment preferred for: - - none - No measurable difference: - - Pentium III (Anderson) - - M68060 (Nikl) - */ -#ifdef POSTINC -# define OFF 0 -# define PUP(a) *(a)++ -#else -# define OFF 1 -# define PUP(a) *++(a) -#endif - -/* - Decode literal, length, and distance codes and write out the resulting - literal and match bytes until either not enough input or output is - available, an end-of-block is encountered, or a data error is encountered. - When large enough input and output buffers are supplied to inflate(), for - example, a 16K input buffer and a 64K output buffer, more than 95% of the - inflate execution time is spent in this routine. - - Entry assumptions: - - state->mode == LEN - strm->avail_in >= 6 - strm->avail_out >= 258 - start >= strm->avail_out - state->bits < 8 - - On return, state->mode is one of: - - LEN -- ran out of enough output space or enough available input - TYPE -- reached end of block code, inflate() to interpret next block - BAD -- error in block data - - Notes: - - - The maximum input bits used by a length/distance pair is 15 bits for the - length code, 5 bits for the length extra, 15 bits for the distance code, - and 13 bits for the distance extra. This totals 48 bits, or six bytes. - Therefore if strm->avail_in >= 6, then there is enough input to avoid - checking for available input while decoding. - - - The maximum bytes that a single length/distance pair can output is 258 - bytes, which is the maximum length that can be coded. inflate_fast() - requires strm->avail_out >= 258 for each loop to avoid checking for - output space. - */ -void ZLIB_INTERNAL inflate_fast(strm, start) -z_streamp strm; -unsigned start; /* inflate()'s starting value for strm->avail_out */ -{ - struct inflate_state FAR *state; - unsigned char FAR *in; /* local strm->next_in */ - unsigned char FAR *last; /* while in < last, enough input available */ - unsigned char FAR *out; /* local strm->next_out */ - unsigned char FAR *beg; /* inflate()'s initial strm->next_out */ - unsigned char FAR *end; /* while out < end, enough space available */ -#ifdef INFLATE_STRICT - unsigned dmax; /* maximum distance from zlib header */ -#endif - unsigned wsize; /* window size or zero if not using window */ - unsigned whave; /* valid bytes in the window */ - unsigned wnext; /* window write index */ - unsigned char FAR *window; /* allocated sliding window, if wsize != 0 */ - unsigned long hold; /* local strm->hold */ - unsigned bits; /* local strm->bits */ - code const FAR *lcode; /* local strm->lencode */ - code const FAR *dcode; /* local strm->distcode */ - unsigned lmask; /* mask for first level of length codes */ - unsigned dmask; /* mask for first level of distance codes */ - code here; /* retrieved table entry */ - unsigned op; /* code bits, operation, extra bits, or */ - /* window position, window bytes to copy */ - unsigned len; /* match length, unused bytes */ - unsigned dist; /* match distance */ - unsigned char FAR *from; /* where to copy match from */ - - /* copy state to local variables */ - state = (struct inflate_state FAR *)strm->state; - in = strm->next_in - OFF; - last = in + (strm->avail_in - 5); - out = strm->next_out - OFF; - beg = out - (start - strm->avail_out); - end = out + (strm->avail_out - 257); -#ifdef INFLATE_STRICT - dmax = state->dmax; -#endif - wsize = state->wsize; - whave = state->whave; - wnext = state->wnext; - window = state->window; - hold = state->hold; - bits = state->bits; - lcode = state->lencode; - dcode = state->distcode; - lmask = (1U << state->lenbits) - 1; - dmask = (1U << state->distbits) - 1; - - /* decode literals and length/distances until end-of-block or not enough - input data or output space */ - do { - if (bits < 15) { - hold += (unsigned long)(PUP(in)) << bits; - bits += 8; - hold += (unsigned long)(PUP(in)) << bits; - bits += 8; - } - here = lcode[hold & lmask]; - dolen: - op = (unsigned)(here.bits); - hold >>= op; - bits -= op; - op = (unsigned)(here.op); - if (op == 0) { /* literal */ - Tracevv((stderr, here.val >= 0x20 && here.val < 0x7f ? - "inflate: literal '%c'\n" : - "inflate: literal 0x%02x\n", here.val)); - PUP(out) = (unsigned char)(here.val); - } - else if (op & 16) { /* length base */ - len = (unsigned)(here.val); - op &= 15; /* number of extra bits */ - if (op) { - if (bits < op) { - hold += (unsigned long)(PUP(in)) << bits; - bits += 8; - } - len += (unsigned)hold & ((1U << op) - 1); - hold >>= op; - bits -= op; - } - Tracevv((stderr, "inflate: length %u\n", len)); - if (bits < 15) { - hold += (unsigned long)(PUP(in)) << bits; - bits += 8; - hold += (unsigned long)(PUP(in)) << bits; - bits += 8; - } - here = dcode[hold & dmask]; - dodist: - op = (unsigned)(here.bits); - hold >>= op; - bits -= op; - op = (unsigned)(here.op); - if (op & 16) { /* distance base */ - dist = (unsigned)(here.val); - op &= 15; /* number of extra bits */ - if (bits < op) { - hold += (unsigned long)(PUP(in)) << bits; - bits += 8; - if (bits < op) { - hold += (unsigned long)(PUP(in)) << bits; - bits += 8; - } - } - dist += (unsigned)hold & ((1U << op) - 1); -#ifdef INFLATE_STRICT - if (dist > dmax) { - strm->msg = (char *)"invalid distance too far back"; - state->mode = BAD; - break; - } -#endif - hold >>= op; - bits -= op; - Tracevv((stderr, "inflate: distance %u\n", dist)); - op = (unsigned)(out - beg); /* max distance in output */ - if (dist > op) { /* see if copy from window */ - op = dist - op; /* distance back in window */ - if (op > whave) { - if (state->sane) { - strm->msg = - (char *)"invalid distance too far back"; - state->mode = BAD; - break; - } -#ifdef INFLATE_ALLOW_INVALID_DISTANCE_TOOFAR_ARRR - if (len <= op - whave) { - do { - PUP(out) = 0; - } while (--len); - continue; - } - len -= op - whave; - do { - PUP(out) = 0; - } while (--op > whave); - if (op == 0) { - from = out - dist; - do { - PUP(out) = PUP(from); - } while (--len); - continue; - } -#endif - } - from = window - OFF; - if (wnext == 0) { /* very common case */ - from += wsize - op; - if (op < len) { /* some from window */ - len -= op; - do { - PUP(out) = PUP(from); - } while (--op); - from = out - dist; /* rest from output */ - } - } - else if (wnext < op) { /* wrap around window */ - from += wsize + wnext - op; - op -= wnext; - if (op < len) { /* some from end of window */ - len -= op; - do { - PUP(out) = PUP(from); - } while (--op); - from = window - OFF; - if (wnext < len) { /* some from start of window */ - op = wnext; - len -= op; - do { - PUP(out) = PUP(from); - } while (--op); - from = out - dist; /* rest from output */ - } - } - } - else { /* contiguous in window */ - from += wnext - op; - if (op < len) { /* some from window */ - len -= op; - do { - PUP(out) = PUP(from); - } while (--op); - from = out - dist; /* rest from output */ - } - } - while (len > 2) { - PUP(out) = PUP(from); - PUP(out) = PUP(from); - PUP(out) = PUP(from); - len -= 3; - } - if (len) { - PUP(out) = PUP(from); - if (len > 1) - PUP(out) = PUP(from); - } - } - else { - from = out - dist; /* copy direct from output */ - do { /* minimum length is three */ - PUP(out) = PUP(from); - PUP(out) = PUP(from); - PUP(out) = PUP(from); - len -= 3; - } while (len > 2); - if (len) { - PUP(out) = PUP(from); - if (len > 1) - PUP(out) = PUP(from); - } - } - } - else if ((op & 64) == 0) { /* 2nd level distance code */ - here = dcode[here.val + (hold & ((1U << op) - 1))]; - goto dodist; - } - else { - strm->msg = (char *)"invalid distance code"; - state->mode = BAD; - break; - } - } - else if ((op & 64) == 0) { /* 2nd level length code */ - here = lcode[here.val + (hold & ((1U << op) - 1))]; - goto dolen; - } - else if (op & 32) { /* end-of-block */ - Tracevv((stderr, "inflate: end of block\n")); - state->mode = TYPE; - break; - } - else { - strm->msg = (char *)"invalid literal/length code"; - state->mode = BAD; - break; - } - } while (in < last && out < end); - - /* return unused bytes (on entry, bits < 8, so in won't go too far back) */ - len = bits >> 3; - in -= len; - bits -= len << 3; - hold &= (1U << bits) - 1; - - /* update state and return */ - strm->next_in = in + OFF; - strm->next_out = out + OFF; - strm->avail_in = (unsigned)(in < last ? 5 + (last - in) : 5 - (in - last)); - strm->avail_out = (unsigned)(out < end ? - 257 + (end - out) : 257 - (out - end)); - state->hold = hold; - state->bits = bits; - return; -} - -/* - inflate_fast() speedups that turned out slower (on a PowerPC G3 750CXe): - - Using bit fields for code structure - - Different op definition to avoid & for extra bits (do & for table bits) - - Three separate decoding do-loops for direct, window, and wnext == 0 - - Special case for distance > 1 copies to do overlapped load and store copy - - Explicit branch predictions (based on measured branch probabilities) - - Deferring match copy and interspersed it with decoding subsequent codes - - Swapping literal/length else - - Swapping window/direct else - - Larger unrolled copy loops (three is about right) - - Moving len -= 3 statement into middle of loop - */ - -#endif /* !ASMINF */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/zlib/inffast.h b/app/jni/src/libultraship/extern/StormLib/src/zlib/inffast.h deleted file mode 100644 index e5c1aa4..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/zlib/inffast.h +++ /dev/null @@ -1,11 +0,0 @@ -/* inffast.h -- header to use inffast.c - * Copyright (C) 1995-2003, 2010 Mark Adler - * For conditions of distribution and use, see copyright notice in zlib.h - */ - -/* WARNING: this file should *not* be used by applications. It is - part of the implementation of the compression library and is - subject to change. Applications should only use zlib.h. - */ - -void ZLIB_INTERNAL inflate_fast OF((z_streamp strm, unsigned start)); diff --git a/app/jni/src/libultraship/extern/StormLib/src/zlib/inffixed.h b/app/jni/src/libultraship/extern/StormLib/src/zlib/inffixed.h deleted file mode 100644 index 75ed4b5..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/zlib/inffixed.h +++ /dev/null @@ -1,94 +0,0 @@ - /* inffixed.h -- table for decoding fixed codes - * Generated automatically by makefixed(). - */ - - /* WARNING: this file should *not* be used by applications. It - is part of the implementation of the compression library and - is subject to change. Applications should only use zlib.h. - */ - - static const code lenfix[512] = { - {96,7,0},{0,8,80},{0,8,16},{20,8,115},{18,7,31},{0,8,112},{0,8,48}, - {0,9,192},{16,7,10},{0,8,96},{0,8,32},{0,9,160},{0,8,0},{0,8,128}, - {0,8,64},{0,9,224},{16,7,6},{0,8,88},{0,8,24},{0,9,144},{19,7,59}, - {0,8,120},{0,8,56},{0,9,208},{17,7,17},{0,8,104},{0,8,40},{0,9,176}, - {0,8,8},{0,8,136},{0,8,72},{0,9,240},{16,7,4},{0,8,84},{0,8,20}, - {21,8,227},{19,7,43},{0,8,116},{0,8,52},{0,9,200},{17,7,13},{0,8,100}, - {0,8,36},{0,9,168},{0,8,4},{0,8,132},{0,8,68},{0,9,232},{16,7,8}, - {0,8,92},{0,8,28},{0,9,152},{20,7,83},{0,8,124},{0,8,60},{0,9,216}, - {18,7,23},{0,8,108},{0,8,44},{0,9,184},{0,8,12},{0,8,140},{0,8,76}, - {0,9,248},{16,7,3},{0,8,82},{0,8,18},{21,8,163},{19,7,35},{0,8,114}, - {0,8,50},{0,9,196},{17,7,11},{0,8,98},{0,8,34},{0,9,164},{0,8,2}, - {0,8,130},{0,8,66},{0,9,228},{16,7,7},{0,8,90},{0,8,26},{0,9,148}, - {20,7,67},{0,8,122},{0,8,58},{0,9,212},{18,7,19},{0,8,106},{0,8,42}, - {0,9,180},{0,8,10},{0,8,138},{0,8,74},{0,9,244},{16,7,5},{0,8,86}, - {0,8,22},{64,8,0},{19,7,51},{0,8,118},{0,8,54},{0,9,204},{17,7,15}, - {0,8,102},{0,8,38},{0,9,172},{0,8,6},{0,8,134},{0,8,70},{0,9,236}, - {16,7,9},{0,8,94},{0,8,30},{0,9,156},{20,7,99},{0,8,126},{0,8,62}, - {0,9,220},{18,7,27},{0,8,110},{0,8,46},{0,9,188},{0,8,14},{0,8,142}, - {0,8,78},{0,9,252},{96,7,0},{0,8,81},{0,8,17},{21,8,131},{18,7,31}, - {0,8,113},{0,8,49},{0,9,194},{16,7,10},{0,8,97},{0,8,33},{0,9,162}, - {0,8,1},{0,8,129},{0,8,65},{0,9,226},{16,7,6},{0,8,89},{0,8,25}, - {0,9,146},{19,7,59},{0,8,121},{0,8,57},{0,9,210},{17,7,17},{0,8,105}, - {0,8,41},{0,9,178},{0,8,9},{0,8,137},{0,8,73},{0,9,242},{16,7,4}, - {0,8,85},{0,8,21},{16,8,258},{19,7,43},{0,8,117},{0,8,53},{0,9,202}, - {17,7,13},{0,8,101},{0,8,37},{0,9,170},{0,8,5},{0,8,133},{0,8,69}, - {0,9,234},{16,7,8},{0,8,93},{0,8,29},{0,9,154},{20,7,83},{0,8,125}, - {0,8,61},{0,9,218},{18,7,23},{0,8,109},{0,8,45},{0,9,186},{0,8,13}, - {0,8,141},{0,8,77},{0,9,250},{16,7,3},{0,8,83},{0,8,19},{21,8,195}, - {19,7,35},{0,8,115},{0,8,51},{0,9,198},{17,7,11},{0,8,99},{0,8,35}, - {0,9,166},{0,8,3},{0,8,131},{0,8,67},{0,9,230},{16,7,7},{0,8,91}, - {0,8,27},{0,9,150},{20,7,67},{0,8,123},{0,8,59},{0,9,214},{18,7,19}, - {0,8,107},{0,8,43},{0,9,182},{0,8,11},{0,8,139},{0,8,75},{0,9,246}, - {16,7,5},{0,8,87},{0,8,23},{64,8,0},{19,7,51},{0,8,119},{0,8,55}, - {0,9,206},{17,7,15},{0,8,103},{0,8,39},{0,9,174},{0,8,7},{0,8,135}, - {0,8,71},{0,9,238},{16,7,9},{0,8,95},{0,8,31},{0,9,158},{20,7,99}, - {0,8,127},{0,8,63},{0,9,222},{18,7,27},{0,8,111},{0,8,47},{0,9,190}, - {0,8,15},{0,8,143},{0,8,79},{0,9,254},{96,7,0},{0,8,80},{0,8,16}, - {20,8,115},{18,7,31},{0,8,112},{0,8,48},{0,9,193},{16,7,10},{0,8,96}, - {0,8,32},{0,9,161},{0,8,0},{0,8,128},{0,8,64},{0,9,225},{16,7,6}, - {0,8,88},{0,8,24},{0,9,145},{19,7,59},{0,8,120},{0,8,56},{0,9,209}, - {17,7,17},{0,8,104},{0,8,40},{0,9,177},{0,8,8},{0,8,136},{0,8,72}, - {0,9,241},{16,7,4},{0,8,84},{0,8,20},{21,8,227},{19,7,43},{0,8,116}, - {0,8,52},{0,9,201},{17,7,13},{0,8,100},{0,8,36},{0,9,169},{0,8,4}, - {0,8,132},{0,8,68},{0,9,233},{16,7,8},{0,8,92},{0,8,28},{0,9,153}, - {20,7,83},{0,8,124},{0,8,60},{0,9,217},{18,7,23},{0,8,108},{0,8,44}, - {0,9,185},{0,8,12},{0,8,140},{0,8,76},{0,9,249},{16,7,3},{0,8,82}, - {0,8,18},{21,8,163},{19,7,35},{0,8,114},{0,8,50},{0,9,197},{17,7,11}, - {0,8,98},{0,8,34},{0,9,165},{0,8,2},{0,8,130},{0,8,66},{0,9,229}, - {16,7,7},{0,8,90},{0,8,26},{0,9,149},{20,7,67},{0,8,122},{0,8,58}, - {0,9,213},{18,7,19},{0,8,106},{0,8,42},{0,9,181},{0,8,10},{0,8,138}, - {0,8,74},{0,9,245},{16,7,5},{0,8,86},{0,8,22},{64,8,0},{19,7,51}, - {0,8,118},{0,8,54},{0,9,205},{17,7,15},{0,8,102},{0,8,38},{0,9,173}, - {0,8,6},{0,8,134},{0,8,70},{0,9,237},{16,7,9},{0,8,94},{0,8,30}, - {0,9,157},{20,7,99},{0,8,126},{0,8,62},{0,9,221},{18,7,27},{0,8,110}, - {0,8,46},{0,9,189},{0,8,14},{0,8,142},{0,8,78},{0,9,253},{96,7,0}, - {0,8,81},{0,8,17},{21,8,131},{18,7,31},{0,8,113},{0,8,49},{0,9,195}, - {16,7,10},{0,8,97},{0,8,33},{0,9,163},{0,8,1},{0,8,129},{0,8,65}, - {0,9,227},{16,7,6},{0,8,89},{0,8,25},{0,9,147},{19,7,59},{0,8,121}, - {0,8,57},{0,9,211},{17,7,17},{0,8,105},{0,8,41},{0,9,179},{0,8,9}, - {0,8,137},{0,8,73},{0,9,243},{16,7,4},{0,8,85},{0,8,21},{16,8,258}, - {19,7,43},{0,8,117},{0,8,53},{0,9,203},{17,7,13},{0,8,101},{0,8,37}, - {0,9,171},{0,8,5},{0,8,133},{0,8,69},{0,9,235},{16,7,8},{0,8,93}, - {0,8,29},{0,9,155},{20,7,83},{0,8,125},{0,8,61},{0,9,219},{18,7,23}, - {0,8,109},{0,8,45},{0,9,187},{0,8,13},{0,8,141},{0,8,77},{0,9,251}, - {16,7,3},{0,8,83},{0,8,19},{21,8,195},{19,7,35},{0,8,115},{0,8,51}, - {0,9,199},{17,7,11},{0,8,99},{0,8,35},{0,9,167},{0,8,3},{0,8,131}, - {0,8,67},{0,9,231},{16,7,7},{0,8,91},{0,8,27},{0,9,151},{20,7,67}, - {0,8,123},{0,8,59},{0,9,215},{18,7,19},{0,8,107},{0,8,43},{0,9,183}, - {0,8,11},{0,8,139},{0,8,75},{0,9,247},{16,7,5},{0,8,87},{0,8,23}, - {64,8,0},{19,7,51},{0,8,119},{0,8,55},{0,9,207},{17,7,15},{0,8,103}, - {0,8,39},{0,9,175},{0,8,7},{0,8,135},{0,8,71},{0,9,239},{16,7,9}, - {0,8,95},{0,8,31},{0,9,159},{20,7,99},{0,8,127},{0,8,63},{0,9,223}, - {18,7,27},{0,8,111},{0,8,47},{0,9,191},{0,8,15},{0,8,143},{0,8,79}, - {0,9,255} - }; - - static const code distfix[32] = { - {16,5,1},{23,5,257},{19,5,17},{27,5,4097},{17,5,5},{25,5,1025}, - {21,5,65},{29,5,16385},{16,5,3},{24,5,513},{20,5,33},{28,5,8193}, - {18,5,9},{26,5,2049},{22,5,129},{64,5,0},{16,5,2},{23,5,385}, - {19,5,25},{27,5,6145},{17,5,7},{25,5,1537},{21,5,97},{29,5,24577}, - {16,5,4},{24,5,769},{20,5,49},{28,5,12289},{18,5,13},{26,5,3073}, - {22,5,193},{64,5,0} - }; diff --git a/app/jni/src/libultraship/extern/StormLib/src/zlib/inflate.c b/app/jni/src/libultraship/extern/StormLib/src/zlib/inflate.c deleted file mode 100644 index a8431ab..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/zlib/inflate.c +++ /dev/null @@ -1,1480 +0,0 @@ -/* inflate.c -- zlib decompression - * Copyright (C) 1995-2010 Mark Adler - * For conditions of distribution and use, see copyright notice in zlib.h - */ - -/* - * Change history: - * - * 1.2.beta0 24 Nov 2002 - * - First version -- complete rewrite of inflate to simplify code, avoid - * creation of window when not needed, minimize use of window when it is - * needed, make inffast.c even faster, implement gzip decoding, and to - * improve code readability and style over the previous zlib inflate code - * - * 1.2.beta1 25 Nov 2002 - * - Use pointers for available input and output checking in inffast.c - * - Remove input and output counters in inffast.c - * - Change inffast.c entry and loop from avail_in >= 7 to >= 6 - * - Remove unnecessary second byte pull from length extra in inffast.c - * - Unroll direct copy to three copies per loop in inffast.c - * - * 1.2.beta2 4 Dec 2002 - * - Change external routine names to reduce potential conflicts - * - Correct filename to inffixed.h for fixed tables in inflate.c - * - Make hbuf[] unsigned char to match parameter type in inflate.c - * - Change strm->next_out[-state->offset] to *(strm->next_out - state->offset) - * to avoid negation problem on Alphas (64 bit) in inflate.c - * - * 1.2.beta3 22 Dec 2002 - * - Add comments on state->bits assertion in inffast.c - * - Add comments on op field in inftrees.h - * - Fix bug in reuse of allocated window after inflateReset() - * - Remove bit fields--back to byte structure for speed - * - Remove distance extra == 0 check in inflate_fast()--only helps for lengths - * - Change post-increments to pre-increments in inflate_fast(), PPC biased? - * - Add compile time option, POSTINC, to use post-increments instead (Intel?) - * - Make MATCH copy in inflate() much faster for when inflate_fast() not used - * - Use local copies of stream next and avail values, as well as local bit - * buffer and bit count in inflate()--for speed when inflate_fast() not used - * - * 1.2.beta4 1 Jan 2003 - * - Split ptr - 257 statements in inflate_table() to avoid compiler warnings - * - Move a comment on output buffer sizes from inffast.c to inflate.c - * - Add comments in inffast.c to introduce the inflate_fast() routine - * - Rearrange window copies in inflate_fast() for speed and simplification - * - Unroll last copy for window match in inflate_fast() - * - Use local copies of window variables in inflate_fast() for speed - * - Pull out common wnext == 0 case for speed in inflate_fast() - * - Make op and len in inflate_fast() unsigned for consistency - * - Add FAR to lcode and dcode declarations in inflate_fast() - * - Simplified bad distance check in inflate_fast() - * - Added inflateBackInit(), inflateBack(), and inflateBackEnd() in new - * source file infback.c to provide a call-back interface to inflate for - * programs like gzip and unzip -- uses window as output buffer to avoid - * window copying - * - * 1.2.beta5 1 Jan 2003 - * - Improved inflateBack() interface to allow the caller to provide initial - * input in strm. - * - Fixed stored blocks bug in inflateBack() - * - * 1.2.beta6 4 Jan 2003 - * - Added comments in inffast.c on effectiveness of POSTINC - * - Typecasting all around to reduce compiler warnings - * - Changed loops from while (1) or do {} while (1) to for (;;), again to - * make compilers happy - * - Changed type of window in inflateBackInit() to unsigned char * - * - * 1.2.beta7 27 Jan 2003 - * - Changed many types to unsigned or unsigned short to avoid warnings - * - Added inflateCopy() function - * - * 1.2.0 9 Mar 2003 - * - Changed inflateBack() interface to provide separate opaque descriptors - * for the in() and out() functions - * - Changed inflateBack() argument and in_func typedef to swap the length - * and buffer address return values for the input function - * - Check next_in and next_out for Z_NULL on entry to inflate() - * - * The history for versions after 1.2.0 are in ChangeLog in zlib distribution. - */ - -#include "zutil.h" -#include "inftrees.h" -#include "inflate.h" -#include "inffast.h" - -#ifdef MAKEFIXED -# ifndef BUILDFIXED -# define BUILDFIXED -# endif -#endif - -/* function prototypes */ -local void fixedtables OF((struct inflate_state FAR *state)); -local int updatewindow OF((z_streamp strm, unsigned out)); -#ifdef BUILDFIXED - void makefixed OF((void)); -#endif -local unsigned syncsearch OF((unsigned FAR *have, unsigned char FAR *buf, - unsigned len)); - -int ZEXPORT inflateReset(strm) -z_streamp strm; -{ - struct inflate_state FAR *state; - - if (strm == Z_NULL || strm->state == Z_NULL) return Z_STREAM_ERROR; - state = (struct inflate_state FAR *)strm->state; - strm->total_in = strm->total_out = state->total = 0; - strm->msg = Z_NULL; - strm->adler = 1; /* to support ill-conceived Java test suite */ - state->mode = HEAD; - state->last = 0; - state->havedict = 0; - state->dmax = 32768U; - state->head = Z_NULL; - state->wsize = 0; - state->whave = 0; - state->wnext = 0; - state->hold = 0; - state->bits = 0; - state->lencode = state->distcode = state->next = state->codes; - state->sane = 1; - state->back = -1; - Tracev((stderr, "inflate: reset\n")); - return Z_OK; -} - -int ZEXPORT inflateReset2(strm, windowBits) -z_streamp strm; -int windowBits; -{ - int wrap; - struct inflate_state FAR *state; - - /* get the state */ - if (strm == Z_NULL || strm->state == Z_NULL) return Z_STREAM_ERROR; - state = (struct inflate_state FAR *)strm->state; - - /* extract wrap request from windowBits parameter */ - if (windowBits < 0) { - wrap = 0; - windowBits = -windowBits; - } - else { - wrap = (windowBits >> 4) + 1; -#ifdef GUNZIP - if (windowBits < 48) - windowBits &= 15; -#endif - } - - /* set number of window bits, free window if different */ - if (windowBits && (windowBits < 8 || windowBits > 15)) - return Z_STREAM_ERROR; - if (state->window != Z_NULL && state->wbits != (unsigned)windowBits) { - ZFREE(strm, state->window); - state->window = Z_NULL; - } - - /* update state and reset the rest of it */ - state->wrap = wrap; - state->wbits = (unsigned)windowBits; - return inflateReset(strm); -} - -int ZEXPORT inflateInit2_(strm, windowBits, version, stream_size) -z_streamp strm; -int windowBits; -const char *version; -int stream_size; -{ - int ret; - struct inflate_state FAR *state; - - if (version == Z_NULL || version[0] != ZLIB_VERSION[0] || - stream_size != (int)(sizeof(z_stream))) - return Z_VERSION_ERROR; - if (strm == Z_NULL) return Z_STREAM_ERROR; - strm->msg = Z_NULL; /* in case we return an error */ - if (strm->zalloc == (alloc_func)0) { - strm->zalloc = zcalloc; - strm->opaque = (voidpf)0; - } - if (strm->zfree == (free_func)0) strm->zfree = zcfree; - state = (struct inflate_state FAR *) - ZALLOC(strm, 1, sizeof(struct inflate_state)); - if (state == Z_NULL) return Z_MEM_ERROR; - Tracev((stderr, "inflate: allocated\n")); - strm->state = (struct internal_state FAR *)state; - state->window = Z_NULL; - ret = inflateReset2(strm, windowBits); - if (ret != Z_OK) { - ZFREE(strm, state); - strm->state = Z_NULL; - } - return ret; -} - -int ZEXPORT inflateInit_(strm, version, stream_size) -z_streamp strm; -const char *version; -int stream_size; -{ - return inflateInit2_(strm, DEF_WBITS, version, stream_size); -} - -int ZEXPORT inflatePrime(strm, bits, value) -z_streamp strm; -int bits; -int value; -{ - struct inflate_state FAR *state; - - if (strm == Z_NULL || strm->state == Z_NULL) return Z_STREAM_ERROR; - state = (struct inflate_state FAR *)strm->state; - if (bits < 0) { - state->hold = 0; - state->bits = 0; - return Z_OK; - } - if (bits > 16 || state->bits + bits > 32) return Z_STREAM_ERROR; - value &= (1L << bits) - 1; - state->hold += value << state->bits; - state->bits += bits; - return Z_OK; -} - -/* - Return state with length and distance decoding tables and index sizes set to - fixed code decoding. Normally this returns fixed tables from inffixed.h. - If BUILDFIXED is defined, then instead this routine builds the tables the - first time it's called, and returns those tables the first time and - thereafter. This reduces the size of the code by about 2K bytes, in - exchange for a little execution time. However, BUILDFIXED should not be - used for threaded applications, since the rewriting of the tables and virgin - may not be thread-safe. - */ -local void fixedtables(state) -struct inflate_state FAR *state; -{ -#ifdef BUILDFIXED - static int virgin = 1; - static code *lenfix, *distfix; - static code fixed[544]; - - /* build fixed huffman tables if first call (may not be thread safe) */ - if (virgin) { - unsigned sym, bits; - static code *next; - - /* literal/length table */ - sym = 0; - while (sym < 144) state->lens[sym++] = 8; - while (sym < 256) state->lens[sym++] = 9; - while (sym < 280) state->lens[sym++] = 7; - while (sym < 288) state->lens[sym++] = 8; - next = fixed; - lenfix = next; - bits = 9; - inflate_table(LENS, state->lens, 288, &(next), &(bits), state->work); - - /* distance table */ - sym = 0; - while (sym < 32) state->lens[sym++] = 5; - distfix = next; - bits = 5; - inflate_table(DISTS, state->lens, 32, &(next), &(bits), state->work); - - /* do this just once */ - virgin = 0; - } -#else /* !BUILDFIXED */ -# include "inffixed.h" -#endif /* BUILDFIXED */ - state->lencode = lenfix; - state->lenbits = 9; - state->distcode = distfix; - state->distbits = 5; -} - -#ifdef MAKEFIXED -#include - -/* - Write out the inffixed.h that is #include'd above. Defining MAKEFIXED also - defines BUILDFIXED, so the tables are built on the fly. makefixed() writes - those tables to stdout, which would be piped to inffixed.h. A small program - can simply call makefixed to do this: - - void makefixed(void); - - int main(void) - { - makefixed(); - return 0; - } - - Then that can be linked with zlib built with MAKEFIXED defined and run: - - a.out > inffixed.h - */ -void makefixed() -{ - unsigned low, size; - struct inflate_state state; - - fixedtables(&state); - puts(" /* inffixed.h -- table for decoding fixed codes"); - puts(" * Generated automatically by makefixed()."); - puts(" */"); - puts(""); - puts(" /* WARNING: this file should *not* be used by applications."); - puts(" It is part of the implementation of this library and is"); - puts(" subject to change. Applications should only use zlib.h."); - puts(" */"); - puts(""); - size = 1U << 9; - printf(" static const code lenfix[%u] = {", size); - low = 0; - for (;;) { - if ((low % 7) == 0) printf("\n "); - printf("{%u,%u,%d}", state.lencode[low].op, state.lencode[low].bits, - state.lencode[low].val); - if (++low == size) break; - putchar(','); - } - puts("\n };"); - size = 1U << 5; - printf("\n static const code distfix[%u] = {", size); - low = 0; - for (;;) { - if ((low % 6) == 0) printf("\n "); - printf("{%u,%u,%d}", state.distcode[low].op, state.distcode[low].bits, - state.distcode[low].val); - if (++low == size) break; - putchar(','); - } - puts("\n };"); -} -#endif /* MAKEFIXED */ - -/* - Update the window with the last wsize (normally 32K) bytes written before - returning. If window does not exist yet, create it. This is only called - when a window is already in use, or when output has been written during this - inflate call, but the end of the deflate stream has not been reached yet. - It is also called to create a window for dictionary data when a dictionary - is loaded. - - Providing output buffers larger than 32K to inflate() should provide a speed - advantage, since only the last 32K of output is copied to the sliding window - upon return from inflate(), and since all distances after the first 32K of - output will fall in the output data, making match copies simpler and faster. - The advantage may be dependent on the size of the processor's data caches. - */ -local int updatewindow(strm, out) -z_streamp strm; -unsigned out; -{ - struct inflate_state FAR *state; - unsigned copy, dist; - - state = (struct inflate_state FAR *)strm->state; - - /* if it hasn't been done already, allocate space for the window */ - if (state->window == Z_NULL) { - state->window = (unsigned char FAR *) - ZALLOC(strm, 1U << state->wbits, - sizeof(unsigned char)); - if (state->window == Z_NULL) return 1; - } - - /* if window not in use yet, initialize */ - if (state->wsize == 0) { - state->wsize = 1U << state->wbits; - state->wnext = 0; - state->whave = 0; - } - - /* copy state->wsize or less output bytes into the circular window */ - copy = out - strm->avail_out; - if (copy >= state->wsize) { - zmemcpy(state->window, strm->next_out - state->wsize, state->wsize); - state->wnext = 0; - state->whave = state->wsize; - } - else { - dist = state->wsize - state->wnext; - if (dist > copy) dist = copy; - zmemcpy(state->window + state->wnext, strm->next_out - copy, dist); - copy -= dist; - if (copy) { - zmemcpy(state->window, strm->next_out - copy, copy); - state->wnext = copy; - state->whave = state->wsize; - } - else { - state->wnext += dist; - if (state->wnext == state->wsize) state->wnext = 0; - if (state->whave < state->wsize) state->whave += dist; - } - } - return 0; -} - -/* Macros for inflate(): */ - -/* check function to use adler32() for zlib or crc32() for gzip */ -#ifdef GUNZIP -# define UPDATE(check, buf, len) \ - (state->flags ? crc32(check, buf, len) : adler32(check, buf, len)) -#else -# define UPDATE(check, buf, len) adler32(check, buf, len) -#endif - -/* check macros for header crc */ -#ifdef GUNZIP -# define CRC2(check, word) \ - do { \ - hbuf[0] = (unsigned char)(word); \ - hbuf[1] = (unsigned char)((word) >> 8); \ - check = crc32(check, hbuf, 2); \ - } while (0) - -# define CRC4(check, word) \ - do { \ - hbuf[0] = (unsigned char)(word); \ - hbuf[1] = (unsigned char)((word) >> 8); \ - hbuf[2] = (unsigned char)((word) >> 16); \ - hbuf[3] = (unsigned char)((word) >> 24); \ - check = crc32(check, hbuf, 4); \ - } while (0) -#endif - -/* Load registers with state in inflate() for speed */ -#define LOAD() \ - do { \ - put = strm->next_out; \ - left = strm->avail_out; \ - next = strm->next_in; \ - have = strm->avail_in; \ - hold = state->hold; \ - bits = state->bits; \ - } while (0) - -/* Restore state from registers in inflate() */ -#define RESTORE() \ - do { \ - strm->next_out = put; \ - strm->avail_out = left; \ - strm->next_in = next; \ - strm->avail_in = have; \ - state->hold = hold; \ - state->bits = bits; \ - } while (0) - -/* Clear the input bit accumulator */ -#define INITBITS() \ - do { \ - hold = 0; \ - bits = 0; \ - } while (0) - -/* Get a byte of input into the bit accumulator, or return from inflate() - if there is no input available. */ -#define PULLBYTE() \ - do { \ - if (have == 0) goto inf_leave; \ - have--; \ - hold += (unsigned long)(*next++) << bits; \ - bits += 8; \ - } while (0) - -/* Assure that there are at least n bits in the bit accumulator. If there is - not enough available input to do that, then return from inflate(). */ -#define NEEDBITS(n) \ - do { \ - while (bits < (unsigned)(n)) \ - PULLBYTE(); \ - } while (0) - -/* Return the low n bits of the bit accumulator (n < 16) */ -#define BITS(n) \ - ((unsigned)hold & ((1U << (n)) - 1)) - -/* Remove n bits from the bit accumulator */ -#define DROPBITS(n) \ - do { \ - hold >>= (n); \ - bits -= (unsigned)(n); \ - } while (0) - -/* Remove zero to seven bits as needed to go to a byte boundary */ -#define BYTEBITS() \ - do { \ - hold >>= bits & 7; \ - bits -= bits & 7; \ - } while (0) - -/* Reverse the bytes in a 32-bit value */ -#define REVERSE(q) \ - ((((q) >> 24) & 0xff) + (((q) >> 8) & 0xff00) + \ - (((q) & 0xff00) << 8) + (((q) & 0xff) << 24)) - -/* - inflate() uses a state machine to process as much input data and generate as - much output data as possible before returning. The state machine is - structured roughly as follows: - - for (;;) switch (state) { - ... - case STATEn: - if (not enough input data or output space to make progress) - return; - ... make progress ... - state = STATEm; - break; - ... - } - - so when inflate() is called again, the same case is attempted again, and - if the appropriate resources are provided, the machine proceeds to the - next state. The NEEDBITS() macro is usually the way the state evaluates - whether it can proceed or should return. NEEDBITS() does the return if - the requested bits are not available. The typical use of the BITS macros - is: - - NEEDBITS(n); - ... do something with BITS(n) ... - DROPBITS(n); - - where NEEDBITS(n) either returns from inflate() if there isn't enough - input left to load n bits into the accumulator, or it continues. BITS(n) - gives the low n bits in the accumulator. When done, DROPBITS(n) drops - the low n bits off the accumulator. INITBITS() clears the accumulator - and sets the number of available bits to zero. BYTEBITS() discards just - enough bits to put the accumulator on a byte boundary. After BYTEBITS() - and a NEEDBITS(8), then BITS(8) would return the next byte in the stream. - - NEEDBITS(n) uses PULLBYTE() to get an available byte of input, or to return - if there is no input available. The decoding of variable length codes uses - PULLBYTE() directly in order to pull just enough bytes to decode the next - code, and no more. - - Some states loop until they get enough input, making sure that enough - state information is maintained to continue the loop where it left off - if NEEDBITS() returns in the loop. For example, want, need, and keep - would all have to actually be part of the saved state in case NEEDBITS() - returns: - - case STATEw: - while (want < need) { - NEEDBITS(n); - keep[want++] = BITS(n); - DROPBITS(n); - } - state = STATEx; - case STATEx: - - As shown above, if the next state is also the next case, then the break - is omitted. - - A state may also return if there is not enough output space available to - complete that state. Those states are copying stored data, writing a - literal byte, and copying a matching string. - - When returning, a "goto inf_leave" is used to update the total counters, - update the check value, and determine whether any progress has been made - during that inflate() call in order to return the proper return code. - Progress is defined as a change in either strm->avail_in or strm->avail_out. - When there is a window, goto inf_leave will update the window with the last - output written. If a goto inf_leave occurs in the middle of decompression - and there is no window currently, goto inf_leave will create one and copy - output to the window for the next call of inflate(). - - In this implementation, the flush parameter of inflate() only affects the - return code (per zlib.h). inflate() always writes as much as possible to - strm->next_out, given the space available and the provided input--the effect - documented in zlib.h of Z_SYNC_FLUSH. Furthermore, inflate() always defers - the allocation of and copying into a sliding window until necessary, which - provides the effect documented in zlib.h for Z_FINISH when the entire input - stream available. So the only thing the flush parameter actually does is: - when flush is set to Z_FINISH, inflate() cannot return Z_OK. Instead it - will return Z_BUF_ERROR if it has not reached the end of the stream. - */ - -int ZEXPORT inflate(strm, flush) -z_streamp strm; -int flush; -{ - struct inflate_state FAR *state; - unsigned char FAR *next; /* next input */ - unsigned char FAR *put; /* next output */ - unsigned have, left; /* available input and output */ - unsigned long hold; /* bit buffer */ - unsigned bits; /* bits in bit buffer */ - unsigned in, out; /* save starting available input and output */ - unsigned copy; /* number of stored or match bytes to copy */ - unsigned char FAR *from; /* where to copy match bytes from */ - code here; /* current decoding table entry */ - code last; /* parent table entry */ - unsigned len; /* length to copy for repeats, bits to drop */ - int ret; /* return code */ -#ifdef GUNZIP - unsigned char hbuf[4]; /* buffer for gzip header crc calculation */ -#endif - static const unsigned short order[19] = /* permutation of code lengths */ - {16, 17, 18, 0, 8, 7, 9, 6, 10, 5, 11, 4, 12, 3, 13, 2, 14, 1, 15}; - - if (strm == Z_NULL || strm->state == Z_NULL || strm->next_out == Z_NULL || - (strm->next_in == Z_NULL && strm->avail_in != 0)) - return Z_STREAM_ERROR; - - state = (struct inflate_state FAR *)strm->state; - if (state->mode == TYPE) state->mode = TYPEDO; /* skip check */ - LOAD(); - in = have; - out = left; - ret = Z_OK; - for (;;) - switch (state->mode) { - case HEAD: - if (state->wrap == 0) { - state->mode = TYPEDO; - break; - } - NEEDBITS(16); -#ifdef GUNZIP - if ((state->wrap & 2) && hold == 0x8b1f) { /* gzip header */ - state->check = crc32(0L, Z_NULL, 0); - CRC2(state->check, hold); - INITBITS(); - state->mode = FLAGS; - break; - } - state->flags = 0; /* expect zlib header */ - if (state->head != Z_NULL) - state->head->done = -1; - if (!(state->wrap & 1) || /* check if zlib header allowed */ -#else - if ( -#endif - ((BITS(8) << 8) + (hold >> 8)) % 31) { - strm->msg = (char *)"incorrect header check"; - state->mode = BAD; - break; - } - if (BITS(4) != Z_DEFLATED) { - strm->msg = (char *)"unknown compression method"; - state->mode = BAD; - break; - } - DROPBITS(4); - len = BITS(4) + 8; - if (state->wbits == 0) - state->wbits = len; - else if (len > state->wbits) { - strm->msg = (char *)"invalid window size"; - state->mode = BAD; - break; - } - state->dmax = 1U << len; - Tracev((stderr, "inflate: zlib header ok\n")); - strm->adler = state->check = adler32(0L, Z_NULL, 0); - state->mode = hold & 0x200 ? DICTID : TYPE; - INITBITS(); - break; -#ifdef GUNZIP - case FLAGS: - NEEDBITS(16); - state->flags = (int)(hold); - if ((state->flags & 0xff) != Z_DEFLATED) { - strm->msg = (char *)"unknown compression method"; - state->mode = BAD; - break; - } - if (state->flags & 0xe000) { - strm->msg = (char *)"unknown header flags set"; - state->mode = BAD; - break; - } - if (state->head != Z_NULL) - state->head->text = (int)((hold >> 8) & 1); - if (state->flags & 0x0200) CRC2(state->check, hold); - INITBITS(); - state->mode = TIME; - case TIME: - NEEDBITS(32); - if (state->head != Z_NULL) - state->head->time = hold; - if (state->flags & 0x0200) CRC4(state->check, hold); - INITBITS(); - state->mode = OS; - case OS: - NEEDBITS(16); - if (state->head != Z_NULL) { - state->head->xflags = (int)(hold & 0xff); - state->head->os = (int)(hold >> 8); - } - if (state->flags & 0x0200) CRC2(state->check, hold); - INITBITS(); - state->mode = EXLEN; - case EXLEN: - if (state->flags & 0x0400) { - NEEDBITS(16); - state->length = (unsigned)(hold); - if (state->head != Z_NULL) - state->head->extra_len = (unsigned)hold; - if (state->flags & 0x0200) CRC2(state->check, hold); - INITBITS(); - } - else if (state->head != Z_NULL) - state->head->extra = Z_NULL; - state->mode = EXTRA; - case EXTRA: - if (state->flags & 0x0400) { - copy = state->length; - if (copy > have) copy = have; - if (copy) { - if (state->head != Z_NULL && - state->head->extra != Z_NULL) { - len = state->head->extra_len - state->length; - zmemcpy(state->head->extra + len, next, - len + copy > state->head->extra_max ? - state->head->extra_max - len : copy); - } - if (state->flags & 0x0200) - state->check = crc32(state->check, next, copy); - have -= copy; - next += copy; - state->length -= copy; - } - if (state->length) goto inf_leave; - } - state->length = 0; - state->mode = NAME; - case NAME: - if (state->flags & 0x0800) { - if (have == 0) goto inf_leave; - copy = 0; - do { - len = (unsigned)(next[copy++]); - if (state->head != Z_NULL && - state->head->name != Z_NULL && - state->length < state->head->name_max) - state->head->name[state->length++] = len; - } while (len && copy < have); - if (state->flags & 0x0200) - state->check = crc32(state->check, next, copy); - have -= copy; - next += copy; - if (len) goto inf_leave; - } - else if (state->head != Z_NULL) - state->head->name = Z_NULL; - state->length = 0; - state->mode = COMMENT; - case COMMENT: - if (state->flags & 0x1000) { - if (have == 0) goto inf_leave; - copy = 0; - do { - len = (unsigned)(next[copy++]); - if (state->head != Z_NULL && - state->head->comment != Z_NULL && - state->length < state->head->comm_max) - state->head->comment[state->length++] = len; - } while (len && copy < have); - if (state->flags & 0x0200) - state->check = crc32(state->check, next, copy); - have -= copy; - next += copy; - if (len) goto inf_leave; - } - else if (state->head != Z_NULL) - state->head->comment = Z_NULL; - state->mode = HCRC; - case HCRC: - if (state->flags & 0x0200) { - NEEDBITS(16); - if (hold != (state->check & 0xffff)) { - strm->msg = (char *)"header crc mismatch"; - state->mode = BAD; - break; - } - INITBITS(); - } - if (state->head != Z_NULL) { - state->head->hcrc = (int)((state->flags >> 9) & 1); - state->head->done = 1; - } - strm->adler = state->check = crc32(0L, Z_NULL, 0); - state->mode = TYPE; - break; -#endif - case DICTID: - NEEDBITS(32); - strm->adler = state->check = REVERSE(hold); - INITBITS(); - state->mode = DICT; - case DICT: - if (state->havedict == 0) { - RESTORE(); - return Z_NEED_DICT; - } - strm->adler = state->check = adler32(0L, Z_NULL, 0); - state->mode = TYPE; - case TYPE: - if (flush == Z_BLOCK || flush == Z_TREES) goto inf_leave; - case TYPEDO: - if (state->last) { - BYTEBITS(); - state->mode = CHECK; - break; - } - NEEDBITS(3); - state->last = BITS(1); - DROPBITS(1); - switch (BITS(2)) { - case 0: /* stored block */ - Tracev((stderr, "inflate: stored block%s\n", - state->last ? " (last)" : "")); - state->mode = STORED; - break; - case 1: /* fixed block */ - fixedtables(state); - Tracev((stderr, "inflate: fixed codes block%s\n", - state->last ? " (last)" : "")); - state->mode = LEN_; /* decode codes */ - if (flush == Z_TREES) { - DROPBITS(2); - goto inf_leave; - } - break; - case 2: /* dynamic block */ - Tracev((stderr, "inflate: dynamic codes block%s\n", - state->last ? " (last)" : "")); - state->mode = TABLE; - break; - case 3: - strm->msg = (char *)"invalid block type"; - state->mode = BAD; - } - DROPBITS(2); - break; - case STORED: - BYTEBITS(); /* go to byte boundary */ - NEEDBITS(32); - if ((hold & 0xffff) != ((hold >> 16) ^ 0xffff)) { - strm->msg = (char *)"invalid stored block lengths"; - state->mode = BAD; - break; - } - state->length = (unsigned)hold & 0xffff; - Tracev((stderr, "inflate: stored length %u\n", - state->length)); - INITBITS(); - state->mode = COPY_; - if (flush == Z_TREES) goto inf_leave; - case COPY_: - state->mode = COPY; - case COPY: - copy = state->length; - if (copy) { - if (copy > have) copy = have; - if (copy > left) copy = left; - if (copy == 0) goto inf_leave; - zmemcpy(put, next, copy); - have -= copy; - next += copy; - left -= copy; - put += copy; - state->length -= copy; - break; - } - Tracev((stderr, "inflate: stored end\n")); - state->mode = TYPE; - break; - case TABLE: - NEEDBITS(14); - state->nlen = BITS(5) + 257; - DROPBITS(5); - state->ndist = BITS(5) + 1; - DROPBITS(5); - state->ncode = BITS(4) + 4; - DROPBITS(4); -#ifndef PKZIP_BUG_WORKAROUND - if (state->nlen > 286 || state->ndist > 30) { - strm->msg = (char *)"too many length or distance symbols"; - state->mode = BAD; - break; - } -#endif - Tracev((stderr, "inflate: table sizes ok\n")); - state->have = 0; - state->mode = LENLENS; - case LENLENS: - while (state->have < state->ncode) { - NEEDBITS(3); - state->lens[order[state->have++]] = (unsigned short)BITS(3); - DROPBITS(3); - } - while (state->have < 19) - state->lens[order[state->have++]] = 0; - state->next = state->codes; - state->lencode = (code const FAR *)(state->next); - state->lenbits = 7; - ret = inflate_table(CODES, state->lens, 19, &(state->next), - &(state->lenbits), state->work); - if (ret) { - strm->msg = (char *)"invalid code lengths set"; - state->mode = BAD; - break; - } - Tracev((stderr, "inflate: code lengths ok\n")); - state->have = 0; - state->mode = CODELENS; - case CODELENS: - while (state->have < state->nlen + state->ndist) { - for (;;) { - here = state->lencode[BITS(state->lenbits)]; - if ((unsigned)(here.bits) <= bits) break; - PULLBYTE(); - } - if (here.val < 16) { - NEEDBITS(here.bits); - DROPBITS(here.bits); - state->lens[state->have++] = here.val; - } - else { - if (here.val == 16) { - NEEDBITS(here.bits + 2); - DROPBITS(here.bits); - if (state->have == 0) { - strm->msg = (char *)"invalid bit length repeat"; - state->mode = BAD; - break; - } - len = state->lens[state->have - 1]; - copy = 3 + BITS(2); - DROPBITS(2); - } - else if (here.val == 17) { - NEEDBITS(here.bits + 3); - DROPBITS(here.bits); - len = 0; - copy = 3 + BITS(3); - DROPBITS(3); - } - else { - NEEDBITS(here.bits + 7); - DROPBITS(here.bits); - len = 0; - copy = 11 + BITS(7); - DROPBITS(7); - } - if (state->have + copy > state->nlen + state->ndist) { - strm->msg = (char *)"invalid bit length repeat"; - state->mode = BAD; - break; - } - while (copy--) - state->lens[state->have++] = (unsigned short)len; - } - } - - /* handle error breaks in while */ - if (state->mode == BAD) break; - - /* check for end-of-block code (better have one) */ - if (state->lens[256] == 0) { - strm->msg = (char *)"invalid code -- missing end-of-block"; - state->mode = BAD; - break; - } - - /* build code tables -- note: do not change the lenbits or distbits - values here (9 and 6) without reading the comments in inftrees.h - concerning the ENOUGH constants, which depend on those values */ - state->next = state->codes; - state->lencode = (code const FAR *)(state->next); - state->lenbits = 9; - ret = inflate_table(LENS, state->lens, state->nlen, &(state->next), - &(state->lenbits), state->work); - if (ret) { - strm->msg = (char *)"invalid literal/lengths set"; - state->mode = BAD; - break; - } - state->distcode = (code const FAR *)(state->next); - state->distbits = 6; - ret = inflate_table(DISTS, state->lens + state->nlen, state->ndist, - &(state->next), &(state->distbits), state->work); - if (ret) { - strm->msg = (char *)"invalid distances set"; - state->mode = BAD; - break; - } - Tracev((stderr, "inflate: codes ok\n")); - state->mode = LEN_; - if (flush == Z_TREES) goto inf_leave; - case LEN_: - state->mode = LEN; - case LEN: - if (have >= 6 && left >= 258) { - RESTORE(); - inflate_fast(strm, out); - LOAD(); - if (state->mode == TYPE) - state->back = -1; - break; - } - state->back = 0; - for (;;) { - here = state->lencode[BITS(state->lenbits)]; - if ((unsigned)(here.bits) <= bits) break; - PULLBYTE(); - } - if (here.op && (here.op & 0xf0) == 0) { - last = here; - for (;;) { - here = state->lencode[last.val + - (BITS(last.bits + last.op) >> last.bits)]; - if ((unsigned)(last.bits + here.bits) <= bits) break; - PULLBYTE(); - } - DROPBITS(last.bits); - state->back += last.bits; - } - DROPBITS(here.bits); - state->back += here.bits; - state->length = (unsigned)here.val; - if ((int)(here.op) == 0) { - Tracevv((stderr, here.val >= 0x20 && here.val < 0x7f ? - "inflate: literal '%c'\n" : - "inflate: literal 0x%02x\n", here.val)); - state->mode = LIT; - break; - } - if (here.op & 32) { - Tracevv((stderr, "inflate: end of block\n")); - state->back = -1; - state->mode = TYPE; - break; - } - if (here.op & 64) { - strm->msg = (char *)"invalid literal/length code"; - state->mode = BAD; - break; - } - state->extra = (unsigned)(here.op) & 15; - state->mode = LENEXT; - case LENEXT: - if (state->extra) { - NEEDBITS(state->extra); - state->length += BITS(state->extra); - DROPBITS(state->extra); - state->back += state->extra; - } - Tracevv((stderr, "inflate: length %u\n", state->length)); - state->was = state->length; - state->mode = DIST; - case DIST: - for (;;) { - here = state->distcode[BITS(state->distbits)]; - if ((unsigned)(here.bits) <= bits) break; - PULLBYTE(); - } - if ((here.op & 0xf0) == 0) { - last = here; - for (;;) { - here = state->distcode[last.val + - (BITS(last.bits + last.op) >> last.bits)]; - if ((unsigned)(last.bits + here.bits) <= bits) break; - PULLBYTE(); - } - DROPBITS(last.bits); - state->back += last.bits; - } - DROPBITS(here.bits); - state->back += here.bits; - if (here.op & 64) { - strm->msg = (char *)"invalid distance code"; - state->mode = BAD; - break; - } - state->offset = (unsigned)here.val; - state->extra = (unsigned)(here.op) & 15; - state->mode = DISTEXT; - case DISTEXT: - if (state->extra) { - NEEDBITS(state->extra); - state->offset += BITS(state->extra); - DROPBITS(state->extra); - state->back += state->extra; - } -#ifdef INFLATE_STRICT - if (state->offset > state->dmax) { - strm->msg = (char *)"invalid distance too far back"; - state->mode = BAD; - break; - } -#endif - Tracevv((stderr, "inflate: distance %u\n", state->offset)); - state->mode = MATCH; - case MATCH: - if (left == 0) goto inf_leave; - copy = out - left; - if (state->offset > copy) { /* copy from window */ - copy = state->offset - copy; - if (copy > state->whave) { - if (state->sane) { - strm->msg = (char *)"invalid distance too far back"; - state->mode = BAD; - break; - } -#ifdef INFLATE_ALLOW_INVALID_DISTANCE_TOOFAR_ARRR - Trace((stderr, "inflate.c too far\n")); - copy -= state->whave; - if (copy > state->length) copy = state->length; - if (copy > left) copy = left; - left -= copy; - state->length -= copy; - do { - *put++ = 0; - } while (--copy); - if (state->length == 0) state->mode = LEN; - break; -#endif - } - if (copy > state->wnext) { - copy -= state->wnext; - from = state->window + (state->wsize - copy); - } - else - from = state->window + (state->wnext - copy); - if (copy > state->length) copy = state->length; - } - else { /* copy from output */ - from = put - state->offset; - copy = state->length; - } - if (copy > left) copy = left; - left -= copy; - state->length -= copy; - do { - *put++ = *from++; - } while (--copy); - if (state->length == 0) state->mode = LEN; - break; - case LIT: - if (left == 0) goto inf_leave; - *put++ = (unsigned char)(state->length); - left--; - state->mode = LEN; - break; - case CHECK: - if (state->wrap) { - NEEDBITS(32); - out -= left; - strm->total_out += out; - state->total += out; - if (out) - strm->adler = state->check = - UPDATE(state->check, put - out, out); - out = left; - if (( -#ifdef GUNZIP - state->flags ? hold : -#endif - REVERSE(hold)) != state->check) { - strm->msg = (char *)"incorrect data check"; - state->mode = BAD; - break; - } - INITBITS(); - Tracev((stderr, "inflate: check matches trailer\n")); - } -#ifdef GUNZIP - state->mode = LENGTH; - case LENGTH: - if (state->wrap && state->flags) { - NEEDBITS(32); - if (hold != (state->total & 0xffffffffUL)) { - strm->msg = (char *)"incorrect length check"; - state->mode = BAD; - break; - } - INITBITS(); - Tracev((stderr, "inflate: length matches trailer\n")); - } -#endif - state->mode = DONE; - case DONE: - ret = Z_STREAM_END; - goto inf_leave; - case BAD: - ret = Z_DATA_ERROR; - goto inf_leave; - case MEM: - return Z_MEM_ERROR; - case SYNC: - default: - return Z_STREAM_ERROR; - } - - /* - Return from inflate(), updating the total counts and the check value. - If there was no progress during the inflate() call, return a buffer - error. Call updatewindow() to create and/or update the window state. - Note: a memory error from inflate() is non-recoverable. - */ - inf_leave: - RESTORE(); - if (state->wsize || (state->mode < CHECK && out != strm->avail_out)) - if (updatewindow(strm, out)) { - state->mode = MEM; - return Z_MEM_ERROR; - } - in -= strm->avail_in; - out -= strm->avail_out; - strm->total_in += in; - strm->total_out += out; - state->total += out; - if (state->wrap && out) - strm->adler = state->check = - UPDATE(state->check, strm->next_out - out, out); - strm->data_type = state->bits + (state->last ? 64 : 0) + - (state->mode == TYPE ? 128 : 0) + - (state->mode == LEN_ || state->mode == COPY_ ? 256 : 0); - if (((in == 0 && out == 0) || flush == Z_FINISH) && ret == Z_OK) - ret = Z_BUF_ERROR; - return ret; -} - -int ZEXPORT inflateEnd(strm) -z_streamp strm; -{ - struct inflate_state FAR *state; - if (strm == Z_NULL || strm->state == Z_NULL || strm->zfree == (free_func)0) - return Z_STREAM_ERROR; - state = (struct inflate_state FAR *)strm->state; - if (state->window != Z_NULL) ZFREE(strm, state->window); - ZFREE(strm, strm->state); - strm->state = Z_NULL; - Tracev((stderr, "inflate: end\n")); - return Z_OK; -} - -int ZEXPORT inflateSetDictionary(strm, dictionary, dictLength) -z_streamp strm; -const Bytef *dictionary; -uInt dictLength; -{ - struct inflate_state FAR *state; - unsigned long id; - - /* check state */ - if (strm == Z_NULL || strm->state == Z_NULL) return Z_STREAM_ERROR; - state = (struct inflate_state FAR *)strm->state; - if (state->wrap != 0 && state->mode != DICT) - return Z_STREAM_ERROR; - - /* check for correct dictionary id */ - if (state->mode == DICT) { - id = adler32(0L, Z_NULL, 0); - id = adler32(id, dictionary, dictLength); - if (id != state->check) - return Z_DATA_ERROR; - } - - /* copy dictionary to window */ - if (updatewindow(strm, strm->avail_out)) { - state->mode = MEM; - return Z_MEM_ERROR; - } - if (dictLength > state->wsize) { - zmemcpy(state->window, dictionary + dictLength - state->wsize, - state->wsize); - state->whave = state->wsize; - } - else { - zmemcpy(state->window + state->wsize - dictLength, dictionary, - dictLength); - state->whave = dictLength; - } - state->havedict = 1; - Tracev((stderr, "inflate: dictionary set\n")); - return Z_OK; -} - -int ZEXPORT inflateGetHeader(strm, head) -z_streamp strm; -gz_headerp head; -{ - struct inflate_state FAR *state; - - /* check state */ - if (strm == Z_NULL || strm->state == Z_NULL) return Z_STREAM_ERROR; - state = (struct inflate_state FAR *)strm->state; - if ((state->wrap & 2) == 0) return Z_STREAM_ERROR; - - /* save header structure */ - state->head = head; - head->done = 0; - return Z_OK; -} - -/* - Search buf[0..len-1] for the pattern: 0, 0, 0xff, 0xff. Return when found - or when out of input. When called, *have is the number of pattern bytes - found in order so far, in 0..3. On return *have is updated to the new - state. If on return *have equals four, then the pattern was found and the - return value is how many bytes were read including the last byte of the - pattern. If *have is less than four, then the pattern has not been found - yet and the return value is len. In the latter case, syncsearch() can be - called again with more data and the *have state. *have is initialized to - zero for the first call. - */ -local unsigned syncsearch(have, buf, len) -unsigned FAR *have; -unsigned char FAR *buf; -unsigned len; -{ - unsigned got; - unsigned next; - - got = *have; - next = 0; - while (next < len && got < 4) { - if ((int)(buf[next]) == (got < 2 ? 0 : 0xff)) - got++; - else if (buf[next]) - got = 0; - else - got = 4 - got; - next++; - } - *have = got; - return next; -} - -int ZEXPORT inflateSync(strm) -z_streamp strm; -{ - unsigned len; /* number of bytes to look at or looked at */ - unsigned long in, out; /* temporary to save total_in and total_out */ - unsigned char buf[4]; /* to restore bit buffer to byte string */ - struct inflate_state FAR *state; - - /* check parameters */ - if (strm == Z_NULL || strm->state == Z_NULL) return Z_STREAM_ERROR; - state = (struct inflate_state FAR *)strm->state; - if (strm->avail_in == 0 && state->bits < 8) return Z_BUF_ERROR; - - /* if first time, start search in bit buffer */ - if (state->mode != SYNC) { - state->mode = SYNC; - state->hold <<= state->bits & 7; - state->bits -= state->bits & 7; - len = 0; - while (state->bits >= 8) { - buf[len++] = (unsigned char)(state->hold); - state->hold >>= 8; - state->bits -= 8; - } - state->have = 0; - syncsearch(&(state->have), buf, len); - } - - /* search available input */ - len = syncsearch(&(state->have), strm->next_in, strm->avail_in); - strm->avail_in -= len; - strm->next_in += len; - strm->total_in += len; - - /* return no joy or set up to restart inflate() on a new block */ - if (state->have != 4) return Z_DATA_ERROR; - in = strm->total_in; out = strm->total_out; - inflateReset(strm); - strm->total_in = in; strm->total_out = out; - state->mode = TYPE; - return Z_OK; -} - -/* - Returns true if inflate is currently at the end of a block generated by - Z_SYNC_FLUSH or Z_FULL_FLUSH. This function is used by one PPP - implementation to provide an additional safety check. PPP uses - Z_SYNC_FLUSH but removes the length bytes of the resulting empty stored - block. When decompressing, PPP checks that at the end of input packet, - inflate is waiting for these length bytes. - */ -int ZEXPORT inflateSyncPoint(strm) -z_streamp strm; -{ - struct inflate_state FAR *state; - - if (strm == Z_NULL || strm->state == Z_NULL) return Z_STREAM_ERROR; - state = (struct inflate_state FAR *)strm->state; - return state->mode == STORED && state->bits == 0; -} - -int ZEXPORT inflateCopy(dest, source) -z_streamp dest; -z_streamp source; -{ - struct inflate_state FAR *state; - struct inflate_state FAR *copy; - unsigned char FAR *window; - unsigned wsize; - - /* check input */ - if (dest == Z_NULL || source == Z_NULL || source->state == Z_NULL || - source->zalloc == (alloc_func)0 || source->zfree == (free_func)0) - return Z_STREAM_ERROR; - state = (struct inflate_state FAR *)source->state; - - /* allocate space */ - copy = (struct inflate_state FAR *) - ZALLOC(source, 1, sizeof(struct inflate_state)); - if (copy == Z_NULL) return Z_MEM_ERROR; - window = Z_NULL; - if (state->window != Z_NULL) { - window = (unsigned char FAR *) - ZALLOC(source, 1U << state->wbits, sizeof(unsigned char)); - if (window == Z_NULL) { - ZFREE(source, copy); - return Z_MEM_ERROR; - } - } - - /* copy state */ - zmemcpy(dest, source, sizeof(z_stream)); - zmemcpy(copy, state, sizeof(struct inflate_state)); - if (state->lencode >= state->codes && - state->lencode <= state->codes + ENOUGH - 1) { - copy->lencode = copy->codes + (state->lencode - state->codes); - copy->distcode = copy->codes + (state->distcode - state->codes); - } - copy->next = copy->codes + (state->next - state->codes); - if (window != Z_NULL) { - wsize = 1U << state->wbits; - zmemcpy(window, state->window, wsize); - } - copy->window = window; - dest->state = (struct internal_state FAR *)copy; - return Z_OK; -} - -int ZEXPORT inflateUndermine(strm, subvert) -z_streamp strm; -int subvert; -{ - struct inflate_state FAR *state; - - if (strm == Z_NULL || strm->state == Z_NULL) return Z_STREAM_ERROR; - state = (struct inflate_state FAR *)strm->state; - state->sane = !subvert; -#ifdef INFLATE_ALLOW_INVALID_DISTANCE_TOOFAR_ARRR - return Z_OK; -#else - state->sane = 1; - return Z_DATA_ERROR; -#endif -} - -long ZEXPORT inflateMark(strm) -z_streamp strm; -{ - struct inflate_state FAR *state; - - if (strm == Z_NULL || strm->state == Z_NULL) return -1L << 16; - state = (struct inflate_state FAR *)strm->state; - return ((long)(state->back) << 16) + - (state->mode == COPY ? state->length : - (state->mode == MATCH ? state->was - state->length : 0)); -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/zlib/inflate.h b/app/jni/src/libultraship/extern/StormLib/src/zlib/inflate.h deleted file mode 100644 index eaef3dc..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/zlib/inflate.h +++ /dev/null @@ -1,130 +0,0 @@ -/* inflate.h -- internal inflate state definition - * Copyright (C) 1995-2016 Mark Adler - * For conditions of distribution and use, see copyright notice in zlib.h - */ - -/* WARNING: this file should *not* be used by applications. It is - part of the implementation of the compression library and is - subject to change. Applications should only use zlib.h. - */ - -#ifndef __INFLATE_H_ -#define __INFLATE_H_ - -/* define NO_GZIP when compiling if you want to disable gzip header and - trailer decoding by inflate(). NO_GZIP would be used to avoid linking in - the crc code when it is not needed. For shared libraries, gzip decoding - should be left enabled. */ -#ifndef NO_GZIP -# define GUNZIP -#endif - -/* Possible inflate modes between inflate() calls */ -typedef enum { - HEAD = 16180, /* i: waiting for magic header */ - FLAGS, /* i: waiting for method and flags (gzip) */ - TIME, /* i: waiting for modification time (gzip) */ - OS, /* i: waiting for extra flags and operating system (gzip) */ - EXLEN, /* i: waiting for extra length (gzip) */ - EXTRA, /* i: waiting for extra bytes (gzip) */ - NAME, /* i: waiting for end of file name (gzip) */ - COMMENT, /* i: waiting for end of comment (gzip) */ - HCRC, /* i: waiting for header crc (gzip) */ - DICTID, /* i: waiting for dictionary check value */ - DICT, /* waiting for inflateSetDictionary() call */ - TYPE, /* i: waiting for type bits, including last-flag bit */ - TYPEDO, /* i: same, but skip check to exit inflate on new block */ - STORED, /* i: waiting for stored size (length and complement) */ - COPY_, /* i/o: same as COPY below, but only first time in */ - COPY, /* i/o: waiting for input or output to copy stored block */ - TABLE, /* i: waiting for dynamic block table lengths */ - LENLENS, /* i: waiting for code length code lengths */ - CODELENS, /* i: waiting for length/lit and distance code lengths */ - LEN_, /* i: same as LEN below, but only first time in */ - LEN, /* i: waiting for length/lit/eob code */ - LENEXT, /* i: waiting for length extra bits */ - DIST, /* i: waiting for distance code */ - DISTEXT, /* i: waiting for distance extra bits */ - MATCH, /* o: waiting for output space to copy string */ - LIT, /* o: waiting for output space to write literal */ - CHECK, /* i: waiting for 32-bit check value */ - LENGTH, /* i: waiting for 32-bit length (gzip) */ - DONE, /* finished check, done -- remain here until reset */ - BAD, /* got a data error -- remain here until reset */ - MEM, /* got an inflate() memory error -- remain here until reset */ - SYNC /* looking for synchronization bytes to restart inflate() */ -} inflate_mode; - -/* - State transitions between above modes - - - (most modes can go to BAD or MEM on error -- not shown for clarity) - - Process header: - HEAD -> (gzip) or (zlib) or (raw) - (gzip) -> FLAGS -> TIME -> OS -> EXLEN -> EXTRA -> NAME -> COMMENT -> - HCRC -> TYPE - (zlib) -> DICTID or TYPE - DICTID -> DICT -> TYPE - (raw) -> TYPEDO - Read deflate blocks: - TYPE -> TYPEDO -> STORED or TABLE or LEN_ or CHECK - STORED -> COPY_ -> COPY -> TYPE - TABLE -> LENLENS -> CODELENS -> LEN_ - LEN_ -> LEN - Read deflate codes in fixed or dynamic block: - LEN -> LENEXT or LIT or TYPE - LENEXT -> DIST -> DISTEXT -> MATCH -> LEN - LIT -> LEN - Process trailer: - CHECK -> LENGTH -> DONE - */ - -/* State maintained between inflate() calls -- approximately 7K bytes, not - including the allocated sliding window, which is up to 32K bytes. */ -struct inflate_state { - z_streamp strm; /* pointer back to this zlib stream */ - inflate_mode mode; /* current inflate mode */ - int last; /* true if processing last block */ - int wrap; /* bit 0 true for zlib, bit 1 true for gzip, - bit 2 true to validate check value */ - int havedict; /* true if dictionary provided */ - int flags; /* gzip header method and flags (0 if zlib) */ - unsigned dmax; /* zlib header max distance (INFLATE_STRICT) */ - unsigned long check; /* protected copy of check value */ - unsigned long total; /* protected copy of output count */ - gz_headerp head; /* where to save gzip header information */ - /* sliding window */ - unsigned wbits; /* log base 2 of requested window size */ - unsigned wsize; /* window size or zero if not using window */ - unsigned whave; /* valid bytes in the window */ - unsigned wnext; /* window write index */ - unsigned char FAR *window; /* allocated sliding window, if needed */ - /* bit accumulator */ - unsigned long hold; /* input bit accumulator */ - unsigned bits; /* number of bits in "in" */ - /* for string and stored block copying */ - unsigned length; /* literal or length of data to copy */ - unsigned offset; /* distance back to copy string from */ - /* for table and code decoding */ - unsigned extra; /* extra bits needed */ - /* fixed and dynamic code tables */ - code const FAR *lencode; /* starting table for length/literal codes */ - code const FAR *distcode; /* starting table for distance codes */ - unsigned lenbits; /* index bits for lencode */ - unsigned distbits; /* index bits for distcode */ - /* dynamic table building */ - unsigned ncode; /* number of code length code lengths */ - unsigned nlen; /* number of length code lengths */ - unsigned ndist; /* number of distance code lengths */ - unsigned have; /* number of code lengths in lens[] */ - code FAR *next; /* next available space in codes[] */ - unsigned short lens[320]; /* temporary storage for code lengths */ - unsigned short work[288]; /* work area for code table building */ - code codes[ENOUGH]; /* space for code tables */ - int sane; /* if false, allow invalid distance too far */ - int back; /* bits back of last unprocessed length/lit */ - unsigned was; /* initial length of match */ -}; - -#endif __INFLATE_H_ diff --git a/app/jni/src/libultraship/extern/StormLib/src/zlib/inftrees.c b/app/jni/src/libultraship/extern/StormLib/src/zlib/inftrees.c deleted file mode 100644 index 11e9c52..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/zlib/inftrees.c +++ /dev/null @@ -1,330 +0,0 @@ -/* inftrees.c -- generate Huffman trees for efficient decoding - * Copyright (C) 1995-2010 Mark Adler - * For conditions of distribution and use, see copyright notice in zlib.h - */ - -#include "zutil.h" -#include "inftrees.h" - -#define MAXBITS 15 - -const char inflate_copyright[] = - " inflate 1.2.5 Copyright 1995-2010 Mark Adler "; -/* - If you use the zlib library in a product, an acknowledgment is welcome - in the documentation of your product. If for some reason you cannot - include such an acknowledgment, I would appreciate that you keep this - copyright string in the executable of your product. - */ - -/* - Build a set of tables to decode the provided canonical Huffman code. - The code lengths are lens[0..codes-1]. The result starts at *table, - whose indices are 0..2^bits-1. work is a writable array of at least - lens shorts, which is used as a work area. type is the type of code - to be generated, CODES, LENS, or DISTS. On return, zero is success, - -1 is an invalid code, and +1 means that ENOUGH isn't enough. table - on return points to the next available entry's address. bits is the - requested root table index bits, and on return it is the actual root - table index bits. It will differ if the request is greater than the - longest code or if it is less than the shortest code. - */ -int ZLIB_INTERNAL inflate_table(type, lens, codes, table, bits, work) -codetype type; -unsigned short FAR *lens; -unsigned codes; -code FAR * FAR *table; -unsigned FAR *bits; -unsigned short FAR *work; -{ - unsigned len; /* a code's length in bits */ - unsigned sym; /* index of code symbols */ - unsigned min, max; /* minimum and maximum code lengths */ - unsigned root; /* number of index bits for root table */ - unsigned curr; /* number of index bits for current table */ - unsigned drop; /* code bits to drop for sub-table */ - int left; /* number of prefix codes available */ - unsigned used; /* code entries in table used */ - unsigned huff; /* Huffman code */ - unsigned incr; /* for incrementing code, index */ - unsigned fill; /* index for replicating entries */ - unsigned low; /* low bits for current root entry */ - unsigned mask; /* mask for low root bits */ - code here; /* table entry for duplication */ - code FAR *next; /* next available space in table */ - const unsigned short FAR *base; /* base value table to use */ - const unsigned short FAR *extra; /* extra bits table to use */ - int end; /* use base and extra for symbol > end */ - unsigned short count[MAXBITS+1]; /* number of codes of each length */ - unsigned short offs[MAXBITS+1]; /* offsets in table for each length */ - static const unsigned short lbase[31] = { /* Length codes 257..285 base */ - 3, 4, 5, 6, 7, 8, 9, 10, 11, 13, 15, 17, 19, 23, 27, 31, - 35, 43, 51, 59, 67, 83, 99, 115, 131, 163, 195, 227, 258, 0, 0}; - static const unsigned short lext[31] = { /* Length codes 257..285 extra */ - 16, 16, 16, 16, 16, 16, 16, 16, 17, 17, 17, 17, 18, 18, 18, 18, - 19, 19, 19, 19, 20, 20, 20, 20, 21, 21, 21, 21, 16, 73, 195}; - static const unsigned short dbase[32] = { /* Distance codes 0..29 base */ - 1, 2, 3, 4, 5, 7, 9, 13, 17, 25, 33, 49, 65, 97, 129, 193, - 257, 385, 513, 769, 1025, 1537, 2049, 3073, 4097, 6145, - 8193, 12289, 16385, 24577, 0, 0}; - static const unsigned short dext[32] = { /* Distance codes 0..29 extra */ - 16, 16, 16, 16, 17, 17, 18, 18, 19, 19, 20, 20, 21, 21, 22, 22, - 23, 23, 24, 24, 25, 25, 26, 26, 27, 27, - 28, 28, 29, 29, 64, 64}; - - /* - Process a set of code lengths to create a canonical Huffman code. The - code lengths are lens[0..codes-1]. Each length corresponds to the - symbols 0..codes-1. The Huffman code is generated by first sorting the - symbols by length from short to long, and retaining the symbol order - for codes with equal lengths. Then the code starts with all zero bits - for the first code of the shortest length, and the codes are integer - increments for the same length, and zeros are appended as the length - increases. For the deflate format, these bits are stored backwards - from their more natural integer increment ordering, and so when the - decoding tables are built in the large loop below, the integer codes - are incremented backwards. - - This routine assumes, but does not check, that all of the entries in - lens[] are in the range 0..MAXBITS. The caller must assure this. - 1..MAXBITS is interpreted as that code length. zero means that that - symbol does not occur in this code. - - The codes are sorted by computing a count of codes for each length, - creating from that a table of starting indices for each length in the - sorted table, and then entering the symbols in order in the sorted - table. The sorted table is work[], with that space being provided by - the caller. - - The length counts are used for other purposes as well, i.e. finding - the minimum and maximum length codes, determining if there are any - codes at all, checking for a valid set of lengths, and looking ahead - at length counts to determine sub-table sizes when building the - decoding tables. - */ - - /* accumulate lengths for codes (assumes lens[] all in 0..MAXBITS) */ - for (len = 0; len <= MAXBITS; len++) - count[len] = 0; - for (sym = 0; sym < codes; sym++) - count[lens[sym]]++; - - /* bound code lengths, force root to be within code lengths */ - root = *bits; - for (max = MAXBITS; max >= 1; max--) - if (count[max] != 0) break; - if (root > max) root = max; - if (max == 0) { /* no symbols to code at all */ - here.op = (unsigned char)64; /* invalid code marker */ - here.bits = (unsigned char)1; - here.val = (unsigned short)0; - *(*table)++ = here; /* make a table to force an error */ - *(*table)++ = here; - *bits = 1; - return 0; /* no symbols, but wait for decoding to report error */ - } - for (min = 1; min < max; min++) - if (count[min] != 0) break; - if (root < min) root = min; - - /* check for an over-subscribed or incomplete set of lengths */ - left = 1; - for (len = 1; len <= MAXBITS; len++) { - left <<= 1; - left -= count[len]; - if (left < 0) return -1; /* over-subscribed */ - } - if (left > 0 && (type == CODES || max != 1)) - return -1; /* incomplete set */ - - /* generate offsets into symbol table for each length for sorting */ - offs[1] = 0; - for (len = 1; len < MAXBITS; len++) - offs[len + 1] = offs[len] + count[len]; - - /* sort symbols by length, by symbol order within each length */ - for (sym = 0; sym < codes; sym++) - if (lens[sym] != 0) work[offs[lens[sym]]++] = (unsigned short)sym; - - /* - Create and fill in decoding tables. In this loop, the table being - filled is at next and has curr index bits. The code being used is huff - with length len. That code is converted to an index by dropping drop - bits off of the bottom. For codes where len is less than drop + curr, - those top drop + curr - len bits are incremented through all values to - fill the table with replicated entries. - - root is the number of index bits for the root table. When len exceeds - root, sub-tables are created pointed to by the root entry with an index - of the low root bits of huff. This is saved in low to check for when a - new sub-table should be started. drop is zero when the root table is - being filled, and drop is root when sub-tables are being filled. - - When a new sub-table is needed, it is necessary to look ahead in the - code lengths to determine what size sub-table is needed. The length - counts are used for this, and so count[] is decremented as codes are - entered in the tables. - - used keeps track of how many table entries have been allocated from the - provided *table space. It is checked for LENS and DIST tables against - the constants ENOUGH_LENS and ENOUGH_DISTS to guard against changes in - the initial root table size constants. See the comments in inftrees.h - for more information. - - sym increments through all symbols, and the loop terminates when - all codes of length max, i.e. all codes, have been processed. This - routine permits incomplete codes, so another loop after this one fills - in the rest of the decoding tables with invalid code markers. - */ - - /* set up for code type */ - switch (type) { - case CODES: - base = extra = work; /* dummy value--not used */ - end = 19; - break; - case LENS: - base = lbase; - base -= 257; - extra = lext; - extra -= 257; - end = 256; - break; - default: /* DISTS */ - base = dbase; - extra = dext; - end = -1; - } - - /* initialize state for loop */ - huff = 0; /* starting code */ - sym = 0; /* starting code symbol */ - len = min; /* starting code length */ - next = *table; /* current table to fill in */ - curr = root; /* current table index bits */ - drop = 0; /* current bits to drop from code for index */ - low = (unsigned)(-1); /* trigger new sub-table when len > root */ - used = 1U << root; /* use root table entries */ - mask = used - 1; /* mask for comparing low */ - - /* check available table space */ - if ((type == LENS && used >= ENOUGH_LENS) || - (type == DISTS && used >= ENOUGH_DISTS)) - return 1; - - /* process all codes and make table entries */ - for (;;) { - /* create table entry */ - here.bits = (unsigned char)(len - drop); - if ((int)(work[sym]) < end) { - here.op = (unsigned char)0; - here.val = work[sym]; - } - else if ((int)(work[sym]) > end) { - here.op = (unsigned char)(extra[work[sym]]); - here.val = base[work[sym]]; - } - else { - here.op = (unsigned char)(32 + 64); /* end of block */ - here.val = 0; - } - - /* replicate for those indices with low len bits equal to huff */ - incr = 1U << (len - drop); - fill = 1U << curr; - min = fill; /* save offset to next table */ - do { - fill -= incr; - next[(huff >> drop) + fill] = here; - } while (fill != 0); - - /* backwards increment the len-bit code huff */ - incr = 1U << (len - 1); - while (huff & incr) - incr >>= 1; - if (incr != 0) { - huff &= incr - 1; - huff += incr; - } - else - huff = 0; - - /* go to next symbol, update count, len */ - sym++; - if (--(count[len]) == 0) { - if (len == max) break; - len = lens[work[sym]]; - } - - /* create new sub-table if needed */ - if (len > root && (huff & mask) != low) { - /* if first time, transition to sub-tables */ - if (drop == 0) - drop = root; - - /* increment past last table */ - next += min; /* here min is 1 << curr */ - - /* determine length of next table */ - curr = len - drop; - left = (int)(1 << curr); - while (curr + drop < max) { - left -= count[curr + drop]; - if (left <= 0) break; - curr++; - left <<= 1; - } - - /* check for enough space */ - used += 1U << curr; - if ((type == LENS && used >= ENOUGH_LENS) || - (type == DISTS && used >= ENOUGH_DISTS)) - return 1; - - /* point entry in root table to sub-table */ - low = huff & mask; - (*table)[low].op = (unsigned char)curr; - (*table)[low].bits = (unsigned char)root; - (*table)[low].val = (unsigned short)(next - *table); - } - } - - /* - Fill in rest of table for incomplete codes. This loop is similar to the - loop above in incrementing huff for table indices. It is assumed that - len is equal to curr + drop, so there is no loop needed to increment - through high index bits. When the current sub-table is filled, the loop - drops back to the root table to fill in any remaining entries there. - */ - here.op = (unsigned char)64; /* invalid code marker */ - here.bits = (unsigned char)(len - drop); - here.val = (unsigned short)0; - while (huff != 0) { - /* when done with sub-table, drop back to root table */ - if (drop != 0 && (huff & mask) != low) { - drop = 0; - len = root; - next = *table; - here.bits = (unsigned char)len; - } - - /* put invalid code marker in table */ - next[huff >> drop] = here; - - /* backwards increment the len-bit code huff */ - incr = 1U << (len - 1); - while (huff & incr) - incr >>= 1; - if (incr != 0) { - huff &= incr - 1; - huff += incr; - } - else - huff = 0; - } - - /* set return parameters */ - *table += used; - *bits = root; - return 0; -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/zlib/inftrees.h b/app/jni/src/libultraship/extern/StormLib/src/zlib/inftrees.h deleted file mode 100644 index 14429f3..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/zlib/inftrees.h +++ /dev/null @@ -1,67 +0,0 @@ -/* inftrees.h -- header to use inftrees.c - * Copyright (C) 1995-2005, 2010 Mark Adler - * For conditions of distribution and use, see copyright notice in zlib.h - */ - -/* WARNING: this file should *not* be used by applications. It is - part of the implementation of the compression library and is - subject to change. Applications should only use zlib.h. - */ - -#ifndef __INFTREES_H_ -#define __INFTREES_H_ - -/* Structure for decoding tables. Each entry provides either the - information needed to do the operation requested by the code that - indexed that table entry, or it provides a pointer to another - table that indexes more bits of the code. op indicates whether - the entry is a pointer to another table, a literal, a length or - distance, an end-of-block, or an invalid code. For a table - pointer, the low four bits of op is the number of index bits of - that table. For a length or distance, the low four bits of op - is the number of extra bits to get after the code. bits is - the number of bits in this code or part of the code to drop off - of the bit buffer. val is the actual byte to output in the case - of a literal, the base length or distance, or the offset from - the current table to the next table. Each entry is four bytes. */ -typedef struct { - unsigned char op; /* operation, extra bits, table bits */ - unsigned char bits; /* bits in this part of the code */ - unsigned short val; /* offset in table or code value */ -} code; - -/* op values as set by inflate_table(): - 00000000 - literal - 0000tttt - table link, tttt != 0 is the number of table index bits - 0001eeee - length or distance, eeee is the number of extra bits - 01100000 - end of block - 01000000 - invalid code - */ - -/* Maximum size of the dynamic table. The maximum number of code structures is - 1444, which is the sum of 852 for literal/length codes and 592 for distance - codes. These values were found by exhaustive searches using the program - examples/enough.c found in the zlib distribtution. The arguments to that - program are the number of symbols, the initial root table size, and the - maximum bit length of a code. "enough 286 9 15" for literal/length codes - returns returns 852, and "enough 30 6 15" for distance codes returns 592. - The initial root table size (9 or 6) is found in the fifth argument of the - inflate_table() calls in inflate.c and infback.c. If the root table size is - changed, then these maximum sizes would be need to be recalculated and - updated. */ -#define ENOUGH_LENS 852 -#define ENOUGH_DISTS 592 -#define ENOUGH (ENOUGH_LENS+ENOUGH_DISTS) - -/* Type of code to build for inflate_table() */ -typedef enum { - CODES, - LENS, - DISTS -} codetype; - -int ZLIB_INTERNAL inflate_table OF((codetype type, unsigned short FAR *lens, - unsigned codes, code FAR * FAR *table, - unsigned FAR *bits, unsigned short FAR *work)); - -#endif // __INFTREES_H_ diff --git a/app/jni/src/libultraship/extern/StormLib/src/zlib/trees.c b/app/jni/src/libultraship/extern/StormLib/src/zlib/trees.c deleted file mode 100644 index 56e9bb1..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/zlib/trees.c +++ /dev/null @@ -1,1244 +0,0 @@ -/* trees.c -- output deflated data using Huffman coding - * Copyright (C) 1995-2010 Jean-loup Gailly - * detect_data_type() function provided freely by Cosmin Truta, 2006 - * For conditions of distribution and use, see copyright notice in zlib.h - */ - -/* - * ALGORITHM - * - * The "deflation" process uses several Huffman trees. The more - * common source values are represented by shorter bit sequences. - * - * Each code tree is stored in a compressed form which is itself - * a Huffman encoding of the lengths of all the code strings (in - * ascending order by source values). The actual code strings are - * reconstructed from the lengths in the inflate process, as described - * in the deflate specification. - * - * REFERENCES - * - * Deutsch, L.P.,"'Deflate' Compressed Data Format Specification". - * Available in ftp.uu.net:/pub/archiving/zip/doc/deflate-1.1.doc - * - * Storer, James A. - * Data Compression: Methods and Theory, pp. 49-50. - * Computer Science Press, 1988. ISBN 0-7167-8156-5. - * - * Sedgewick, R. - * Algorithms, p290. - * Addison-Wesley, 1983. ISBN 0-201-06672-6. - */ - -/* @(#) $Id$ */ - -/* #define GEN_TREES_H */ - -#include "deflate.h" - -#ifdef DEBUG -# include -#endif - -/* =========================================================================== - * Constants - */ - -#define MAX_BL_BITS 7 -/* Bit length codes must not exceed MAX_BL_BITS bits */ - -#define END_BLOCK 256 -/* end of block literal code */ - -#define REP_3_6 16 -/* repeat previous bit length 3-6 times (2 bits of repeat count) */ - -#define REPZ_3_10 17 -/* repeat a zero length 3-10 times (3 bits of repeat count) */ - -#define REPZ_11_138 18 -/* repeat a zero length 11-138 times (7 bits of repeat count) */ - -local const int extra_lbits[LENGTH_CODES] /* extra bits for each length code */ - = {0,0,0,0,0,0,0,0,1,1,1,1,2,2,2,2,3,3,3,3,4,4,4,4,5,5,5,5,0}; - -local const int extra_dbits[D_CODES] /* extra bits for each distance code */ - = {0,0,0,0,1,1,2,2,3,3,4,4,5,5,6,6,7,7,8,8,9,9,10,10,11,11,12,12,13,13}; - -local const int extra_blbits[BL_CODES]/* extra bits for each bit length code */ - = {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,3,7}; - -local const uch bl_order[BL_CODES] - = {16,17,18,0,8,7,9,6,10,5,11,4,12,3,13,2,14,1,15}; -/* The lengths of the bit length codes are sent in order of decreasing - * probability, to avoid transmitting the lengths for unused bit length codes. - */ - -#define Buf_size (8 * 2*sizeof(char)) -/* Number of bits used within bi_buf. (bi_buf might be implemented on - * more than 16 bits on some systems.) - */ - -/* =========================================================================== - * Local data. These are initialized only once. - */ - -#define DIST_CODE_LEN 512 /* see definition of array dist_code below */ - -#if defined(GEN_TREES_H) || !defined(STDC) -/* non ANSI compilers may not accept trees.h */ - -local ct_data static_ltree[L_CODES+2]; -/* The static literal tree. Since the bit lengths are imposed, there is no - * need for the L_CODES extra codes used during heap construction. However - * The codes 286 and 287 are needed to build a canonical tree (see _tr_init - * below). - */ - -local ct_data static_dtree[D_CODES]; -/* The static distance tree. (Actually a trivial tree since all codes use - * 5 bits.) - */ - -uch _dist_code[DIST_CODE_LEN]; -/* Distance codes. The first 256 values correspond to the distances - * 3 .. 258, the last 256 values correspond to the top 8 bits of - * the 15 bit distances. - */ - -uch _length_code[MAX_MATCH-MIN_MATCH+1]; -/* length code for each normalized match length (0 == MIN_MATCH) */ - -local int base_length[LENGTH_CODES]; -/* First normalized length for each code (0 = MIN_MATCH) */ - -local int base_dist[D_CODES]; -/* First normalized distance for each code (0 = distance of 1) */ - -#else -# include "trees.h" -#endif /* GEN_TREES_H */ - -struct static_tree_desc_s { - const ct_data *static_tree; /* static tree or NULL */ - const intf *extra_bits; /* extra bits for each code or NULL */ - int extra_base; /* base index for extra_bits */ - int elems; /* max number of elements in the tree */ - int max_length; /* max bit length for the codes */ -}; - -local static_tree_desc static_l_desc = -{static_ltree, extra_lbits, LITERALS+1, L_CODES, MAX_BITS}; - -local static_tree_desc static_d_desc = -{static_dtree, extra_dbits, 0, D_CODES, MAX_BITS}; - -local static_tree_desc static_bl_desc = -{(const ct_data *)0, extra_blbits, 0, BL_CODES, MAX_BL_BITS}; - -/* =========================================================================== - * Local (static) routines in this file. - */ - -local void tr_static_init OF((void)); -local void init_block OF((deflate_state *s)); -local void pqdownheap OF((deflate_state *s, ct_data *tree, int k)); -local void gen_bitlen OF((deflate_state *s, tree_desc *desc)); -local void gen_codes OF((ct_data *tree, int max_code, ushf *bl_count)); -local void build_tree OF((deflate_state *s, tree_desc *desc)); -local void scan_tree OF((deflate_state *s, ct_data *tree, int max_code)); -local void send_tree OF((deflate_state *s, ct_data *tree, int max_code)); -local int build_bl_tree OF((deflate_state *s)); -local void send_all_trees OF((deflate_state *s, int lcodes, int dcodes, - int blcodes)); -local void compress_block OF((deflate_state *s, ct_data *ltree, - ct_data *dtree)); -local int detect_data_type OF((deflate_state *s)); -local unsigned bi_reverse OF((unsigned value, int length)); -local void bi_windup OF((deflate_state *s)); -local void bi_flush OF((deflate_state *s)); -local void copy_block OF((deflate_state *s, charf *buf, unsigned len, - int header)); - -#ifdef GEN_TREES_H -local void gen_trees_header OF((void)); -#endif - -#ifndef DEBUG -# define send_code(s, c, tree) send_bits(s, tree[c].Code, tree[c].Len) - /* Send a code of the given tree. c and tree must not have side effects */ - -#else /* DEBUG */ -# define send_code(s, c, tree) \ - { if (z_verbose>2) fprintf(stderr,"\ncd %3d ",(c)); \ - send_bits(s, tree[c].Code, tree[c].Len); } -#endif - -/* =========================================================================== - * Output a short LSB first on the stream. - * IN assertion: there is enough room in pendingBuf. - */ -#define put_short(s, w) { \ - put_byte(s, (uch)((w) & 0xff)); \ - put_byte(s, (uch)((ush)(w) >> 8)); \ -} - -/* =========================================================================== - * Send a value on a given number of bits. - * IN assertion: length <= 16 and value fits in length bits. - */ -#ifdef DEBUG -local void send_bits OF((deflate_state *s, int value, int length)); - -local void send_bits(s, value, length) - deflate_state *s; - int value; /* value to send */ - int length; /* number of bits */ -{ - Tracevv((stderr," l %2d v %4x ", length, value)); - Assert(length > 0 && length <= 15, "invalid length"); - s->bits_sent += (ulg)length; - - /* If not enough room in bi_buf, use (valid) bits from bi_buf and - * (16 - bi_valid) bits from value, leaving (width - (16-bi_valid)) - * unused bits in value. - */ - if (s->bi_valid > (int)Buf_size - length) { - s->bi_buf |= (ush)value << s->bi_valid; - put_short(s, s->bi_buf); - s->bi_buf = (ush)value >> (Buf_size - s->bi_valid); - s->bi_valid += length - Buf_size; - } else { - s->bi_buf |= (ush)value << s->bi_valid; - s->bi_valid += length; - } -} -#else /* !DEBUG */ - -#define send_bits(s, value, length) \ -{ int len = length;\ - if (s->bi_valid > (int)Buf_size - len) {\ - int val = value;\ - s->bi_buf |= (ush)val << s->bi_valid;\ - put_short(s, s->bi_buf);\ - s->bi_buf = (ush)val >> (Buf_size - s->bi_valid);\ - s->bi_valid += len - Buf_size;\ - } else {\ - s->bi_buf |= (ush)(value) << s->bi_valid;\ - s->bi_valid += len;\ - }\ -} -#endif /* DEBUG */ - - -/* the arguments must not have side effects */ - -/* =========================================================================== - * Initialize the various 'constant' tables. - */ -local void tr_static_init() -{ -#if defined(GEN_TREES_H) || !defined(STDC) - static int static_init_done = 0; - int n; /* iterates over tree elements */ - int bits; /* bit counter */ - int length; /* length value */ - int code; /* code value */ - int dist; /* distance index */ - ush bl_count[MAX_BITS+1]; - /* number of codes at each bit length for an optimal tree */ - - if (static_init_done) return; - - /* For some embedded targets, global variables are not initialized: */ -#ifdef NO_INIT_GLOBAL_POINTERS - static_l_desc.static_tree = static_ltree; - static_l_desc.extra_bits = extra_lbits; - static_d_desc.static_tree = static_dtree; - static_d_desc.extra_bits = extra_dbits; - static_bl_desc.extra_bits = extra_blbits; -#endif - - /* Initialize the mapping length (0..255) -> length code (0..28) */ - length = 0; - for (code = 0; code < LENGTH_CODES-1; code++) { - base_length[code] = length; - for (n = 0; n < (1< dist code (0..29) */ - dist = 0; - for (code = 0 ; code < 16; code++) { - base_dist[code] = dist; - for (n = 0; n < (1<>= 7; /* from now on, all distances are divided by 128 */ - for ( ; code < D_CODES; code++) { - base_dist[code] = dist << 7; - for (n = 0; n < (1<<(extra_dbits[code]-7)); n++) { - _dist_code[256 + dist++] = (uch)code; - } - } - Assert (dist == 256, "tr_static_init: 256+dist != 512"); - - /* Construct the codes of the static literal tree */ - for (bits = 0; bits <= MAX_BITS; bits++) bl_count[bits] = 0; - n = 0; - while (n <= 143) static_ltree[n++].Len = 8, bl_count[8]++; - while (n <= 255) static_ltree[n++].Len = 9, bl_count[9]++; - while (n <= 279) static_ltree[n++].Len = 7, bl_count[7]++; - while (n <= 287) static_ltree[n++].Len = 8, bl_count[8]++; - /* Codes 286 and 287 do not exist, but we must include them in the - * tree construction to get a canonical Huffman tree (longest code - * all ones) - */ - gen_codes((ct_data *)static_ltree, L_CODES+1, bl_count); - - /* The static distance tree is trivial: */ - for (n = 0; n < D_CODES; n++) { - static_dtree[n].Len = 5; - static_dtree[n].Code = bi_reverse((unsigned)n, 5); - } - static_init_done = 1; - -# ifdef GEN_TREES_H - gen_trees_header(); -# endif -#endif /* defined(GEN_TREES_H) || !defined(STDC) */ -} - -/* =========================================================================== - * Genererate the file trees.h describing the static trees. - */ -#ifdef GEN_TREES_H -# ifndef DEBUG -# include -# endif - -# define SEPARATOR(i, last, width) \ - ((i) == (last)? "\n};\n\n" : \ - ((i) % (width) == (width)-1 ? ",\n" : ", ")) - -void gen_trees_header() -{ - FILE *header = fopen("trees.h", "w"); - int i; - - Assert (header != NULL, "Can't open trees.h"); - fprintf(header, - "/* header created automatically with -DGEN_TREES_H */\n\n"); - - fprintf(header, "local const ct_data static_ltree[L_CODES+2] = {\n"); - for (i = 0; i < L_CODES+2; i++) { - fprintf(header, "{{%3u},{%3u}}%s", static_ltree[i].Code, - static_ltree[i].Len, SEPARATOR(i, L_CODES+1, 5)); - } - - fprintf(header, "local const ct_data static_dtree[D_CODES] = {\n"); - for (i = 0; i < D_CODES; i++) { - fprintf(header, "{{%2u},{%2u}}%s", static_dtree[i].Code, - static_dtree[i].Len, SEPARATOR(i, D_CODES-1, 5)); - } - - fprintf(header, "const uch ZLIB_INTERNAL _dist_code[DIST_CODE_LEN] = {\n"); - for (i = 0; i < DIST_CODE_LEN; i++) { - fprintf(header, "%2u%s", _dist_code[i], - SEPARATOR(i, DIST_CODE_LEN-1, 20)); - } - - fprintf(header, - "const uch ZLIB_INTERNAL _length_code[MAX_MATCH-MIN_MATCH+1]= {\n"); - for (i = 0; i < MAX_MATCH-MIN_MATCH+1; i++) { - fprintf(header, "%2u%s", _length_code[i], - SEPARATOR(i, MAX_MATCH-MIN_MATCH, 20)); - } - - fprintf(header, "local const int base_length[LENGTH_CODES] = {\n"); - for (i = 0; i < LENGTH_CODES; i++) { - fprintf(header, "%1u%s", base_length[i], - SEPARATOR(i, LENGTH_CODES-1, 20)); - } - - fprintf(header, "local const int base_dist[D_CODES] = {\n"); - for (i = 0; i < D_CODES; i++) { - fprintf(header, "%5u%s", base_dist[i], - SEPARATOR(i, D_CODES-1, 10)); - } - - fclose(header); -} -#endif /* GEN_TREES_H */ - -/* =========================================================================== - * Initialize the tree data structures for a new zlib stream. - */ -void ZLIB_INTERNAL _tr_init(s) - deflate_state *s; -{ - tr_static_init(); - - s->l_desc.dyn_tree = s->dyn_ltree; - s->l_desc.stat_desc = &static_l_desc; - - s->d_desc.dyn_tree = s->dyn_dtree; - s->d_desc.stat_desc = &static_d_desc; - - s->bl_desc.dyn_tree = s->bl_tree; - s->bl_desc.stat_desc = &static_bl_desc; - - s->bi_buf = 0; - s->bi_valid = 0; - s->last_eob_len = 8; /* enough lookahead for inflate */ -#ifdef DEBUG - s->compressed_len = 0L; - s->bits_sent = 0L; -#endif - - /* Initialize the first block of the first file: */ - init_block(s); -} - -/* =========================================================================== - * Initialize a new block. - */ -local void init_block(s) - deflate_state *s; -{ - int n; /* iterates over tree elements */ - - /* Initialize the trees. */ - for (n = 0; n < L_CODES; n++) s->dyn_ltree[n].Freq = 0; - for (n = 0; n < D_CODES; n++) s->dyn_dtree[n].Freq = 0; - for (n = 0; n < BL_CODES; n++) s->bl_tree[n].Freq = 0; - - s->dyn_ltree[END_BLOCK].Freq = 1; - s->opt_len = s->static_len = 0L; - s->last_lit = s->matches = 0; -} - -#define SMALLEST 1 -/* Index within the heap array of least frequent node in the Huffman tree */ - - -/* =========================================================================== - * Remove the smallest element from the heap and recreate the heap with - * one less element. Updates heap and heap_len. - */ -#define pqremove(s, tree, top) \ -{\ - top = s->heap[SMALLEST]; \ - s->heap[SMALLEST] = s->heap[s->heap_len--]; \ - pqdownheap(s, tree, SMALLEST); \ -} - -/* =========================================================================== - * Compares to subtrees, using the tree depth as tie breaker when - * the subtrees have equal frequency. This minimizes the worst case length. - */ -#define smaller(tree, n, m, depth) \ - (tree[n].Freq < tree[m].Freq || \ - (tree[n].Freq == tree[m].Freq && depth[n] <= depth[m])) - -/* =========================================================================== - * Restore the heap property by moving down the tree starting at node k, - * exchanging a node with the smallest of its two sons if necessary, stopping - * when the heap property is re-established (each father smaller than its - * two sons). - */ -local void pqdownheap(s, tree, k) - deflate_state *s; - ct_data *tree; /* the tree to restore */ - int k; /* node to move down */ -{ - int v = s->heap[k]; - int j = k << 1; /* left son of k */ - while (j <= s->heap_len) { - /* Set j to the smallest of the two sons: */ - if (j < s->heap_len && - smaller(tree, s->heap[j+1], s->heap[j], s->depth)) { - j++; - } - /* Exit if v is smaller than both sons */ - if (smaller(tree, v, s->heap[j], s->depth)) break; - - /* Exchange v with the smallest son */ - s->heap[k] = s->heap[j]; k = j; - - /* And continue down the tree, setting j to the left son of k */ - j <<= 1; - } - s->heap[k] = v; -} - -/* =========================================================================== - * Compute the optimal bit lengths for a tree and update the total bit length - * for the current block. - * IN assertion: the fields freq and dad are set, heap[heap_max] and - * above are the tree nodes sorted by increasing frequency. - * OUT assertions: the field len is set to the optimal bit length, the - * array bl_count contains the frequencies for each bit length. - * The length opt_len is updated; static_len is also updated if stree is - * not null. - */ -local void gen_bitlen(s, desc) - deflate_state *s; - tree_desc *desc; /* the tree descriptor */ -{ - ct_data *tree = desc->dyn_tree; - int max_code = desc->max_code; - const ct_data *stree = desc->stat_desc->static_tree; - const intf *extra = desc->stat_desc->extra_bits; - int base = desc->stat_desc->extra_base; - int max_length = desc->stat_desc->max_length; - int h; /* heap index */ - int n, m; /* iterate over the tree elements */ - int bits; /* bit length */ - int xbits; /* extra bits */ - ush f; /* frequency */ - int overflow = 0; /* number of elements with bit length too large */ - - for (bits = 0; bits <= MAX_BITS; bits++) s->bl_count[bits] = 0; - - /* In a first pass, compute the optimal bit lengths (which may - * overflow in the case of the bit length tree). - */ - tree[s->heap[s->heap_max]].Len = 0; /* root of the heap */ - - for (h = s->heap_max+1; h < HEAP_SIZE; h++) { - n = s->heap[h]; - bits = tree[tree[n].Dad].Len + 1; - if (bits > max_length) bits = max_length, overflow++; - tree[n].Len = (ush)bits; - /* We overwrite tree[n].Dad which is no longer needed */ - - if (n > max_code) continue; /* not a leaf node */ - - s->bl_count[bits]++; - xbits = 0; - if (n >= base) xbits = extra[n-base]; - f = tree[n].Freq; - s->opt_len += (ulg)f * (bits + xbits); - if (stree) s->static_len += (ulg)f * (stree[n].Len + xbits); - } - if (overflow == 0) return; - - Trace((stderr,"\nbit length overflow\n")); - /* This happens for example on obj2 and pic of the Calgary corpus */ - - /* Find the first bit length which could increase: */ - do { - bits = max_length-1; - while (s->bl_count[bits] == 0) bits--; - s->bl_count[bits]--; /* move one leaf down the tree */ - s->bl_count[bits+1] += 2; /* move one overflow item as its brother */ - s->bl_count[max_length]--; - /* The brother of the overflow item also moves one step up, - * but this does not affect bl_count[max_length] - */ - overflow -= 2; - } while (overflow > 0); - - /* Now recompute all bit lengths, scanning in increasing frequency. - * h is still equal to HEAP_SIZE. (It is simpler to reconstruct all - * lengths instead of fixing only the wrong ones. This idea is taken - * from 'ar' written by Haruhiko Okumura.) - */ - for (bits = max_length; bits != 0; bits--) { - n = s->bl_count[bits]; - while (n != 0) { - m = s->heap[--h]; - if (m > max_code) continue; - if ((unsigned) tree[m].Len != (unsigned) bits) { - Trace((stderr,"code %d bits %d->%d\n", m, tree[m].Len, bits)); - s->opt_len += ((long)bits - (long)tree[m].Len) - *(long)tree[m].Freq; - tree[m].Len = (ush)bits; - } - n--; - } - } -} - -/* =========================================================================== - * Generate the codes for a given tree and bit counts (which need not be - * optimal). - * IN assertion: the array bl_count contains the bit length statistics for - * the given tree and the field len is set for all tree elements. - * OUT assertion: the field code is set for all tree elements of non - * zero code length. - */ -local void gen_codes (tree, max_code, bl_count) - ct_data *tree; /* the tree to decorate */ - int max_code; /* largest code with non zero frequency */ - ushf *bl_count; /* number of codes at each bit length */ -{ - ush next_code[MAX_BITS+1]; /* next code value for each bit length */ - ush code = 0; /* running code value */ - int bits; /* bit index */ - int n; /* code index */ - - /* The distribution counts are first used to generate the code values - * without bit reversal. - */ - for (bits = 1; bits <= MAX_BITS; bits++) { - next_code[bits] = code = (code + bl_count[bits-1]) << 1; - } - /* Check that the bit counts in bl_count are consistent. The last code - * must be all ones. - */ - Assert (code + bl_count[MAX_BITS]-1 == (1<dyn_tree; - const ct_data *stree = desc->stat_desc->static_tree; - int elems = desc->stat_desc->elems; - int n, m; /* iterate over heap elements */ - int max_code = -1; /* largest code with non zero frequency */ - int node; /* new node being created */ - - /* Construct the initial heap, with least frequent element in - * heap[SMALLEST]. The sons of heap[n] are heap[2*n] and heap[2*n+1]. - * heap[0] is not used. - */ - s->heap_len = 0, s->heap_max = HEAP_SIZE; - - for (n = 0; n < elems; n++) { - if (tree[n].Freq != 0) { - s->heap[++(s->heap_len)] = max_code = n; - s->depth[n] = 0; - } else { - tree[n].Len = 0; - } - } - - /* The pkzip format requires that at least one distance code exists, - * and that at least one bit should be sent even if there is only one - * possible code. So to avoid special checks later on we force at least - * two codes of non zero frequency. - */ - while (s->heap_len < 2) { - node = s->heap[++(s->heap_len)] = (max_code < 2 ? ++max_code : 0); - tree[node].Freq = 1; - s->depth[node] = 0; - s->opt_len--; if (stree) s->static_len -= stree[node].Len; - /* node is 0 or 1 so it does not have extra bits */ - } - desc->max_code = max_code; - - /* The elements heap[heap_len/2+1 .. heap_len] are leaves of the tree, - * establish sub-heaps of increasing lengths: - */ - for (n = s->heap_len/2; n >= 1; n--) pqdownheap(s, tree, n); - - /* Construct the Huffman tree by repeatedly combining the least two - * frequent nodes. - */ - node = elems; /* next internal node of the tree */ - do { - pqremove(s, tree, n); /* n = node of least frequency */ - m = s->heap[SMALLEST]; /* m = node of next least frequency */ - - s->heap[--(s->heap_max)] = n; /* keep the nodes sorted by frequency */ - s->heap[--(s->heap_max)] = m; - - /* Create a new node father of n and m */ - tree[node].Freq = tree[n].Freq + tree[m].Freq; - s->depth[node] = (uch)((s->depth[n] >= s->depth[m] ? - s->depth[n] : s->depth[m]) + 1); - tree[n].Dad = tree[m].Dad = (ush)node; -#ifdef DUMP_BL_TREE - if (tree == s->bl_tree) { - fprintf(stderr,"\nnode %d(%d), sons %d(%d) %d(%d)", - node, tree[node].Freq, n, tree[n].Freq, m, tree[m].Freq); - } -#endif - /* and insert the new node in the heap */ - s->heap[SMALLEST] = node++; - pqdownheap(s, tree, SMALLEST); - - } while (s->heap_len >= 2); - - s->heap[--(s->heap_max)] = s->heap[SMALLEST]; - - /* At this point, the fields freq and dad are set. We can now - * generate the bit lengths. - */ - gen_bitlen(s, (tree_desc *)desc); - - /* The field len is now set, we can generate the bit codes */ - gen_codes ((ct_data *)tree, max_code, s->bl_count); -} - -/* =========================================================================== - * Scan a literal or distance tree to determine the frequencies of the codes - * in the bit length tree. - */ -local void scan_tree (s, tree, max_code) - deflate_state *s; - ct_data *tree; /* the tree to be scanned */ - int max_code; /* and its largest code of non zero frequency */ -{ - int n; /* iterates over all tree elements */ - int prevlen = -1; /* last emitted length */ - int curlen; /* length of current code */ - int nextlen = tree[0].Len; /* length of next code */ - int count = 0; /* repeat count of the current code */ - int max_count = 7; /* max repeat count */ - int min_count = 4; /* min repeat count */ - - if (nextlen == 0) max_count = 138, min_count = 3; - tree[max_code+1].Len = (ush)0xffff; /* guard */ - - for (n = 0; n <= max_code; n++) { - curlen = nextlen; nextlen = tree[n+1].Len; - if (++count < max_count && curlen == nextlen) { - continue; - } else if (count < min_count) { - s->bl_tree[curlen].Freq += count; - } else if (curlen != 0) { - if (curlen != prevlen) s->bl_tree[curlen].Freq++; - s->bl_tree[REP_3_6].Freq++; - } else if (count <= 10) { - s->bl_tree[REPZ_3_10].Freq++; - } else { - s->bl_tree[REPZ_11_138].Freq++; - } - count = 0; prevlen = curlen; - if (nextlen == 0) { - max_count = 138, min_count = 3; - } else if (curlen == nextlen) { - max_count = 6, min_count = 3; - } else { - max_count = 7, min_count = 4; - } - } -} - -/* =========================================================================== - * Send a literal or distance tree in compressed form, using the codes in - * bl_tree. - */ -local void send_tree (s, tree, max_code) - deflate_state *s; - ct_data *tree; /* the tree to be scanned */ - int max_code; /* and its largest code of non zero frequency */ -{ - int n; /* iterates over all tree elements */ - int prevlen = -1; /* last emitted length */ - int curlen; /* length of current code */ - int nextlen = tree[0].Len; /* length of next code */ - int count = 0; /* repeat count of the current code */ - int max_count = 7; /* max repeat count */ - int min_count = 4; /* min repeat count */ - - /* tree[max_code+1].Len = -1; */ /* guard already set */ - if (nextlen == 0) max_count = 138, min_count = 3; - - for (n = 0; n <= max_code; n++) { - curlen = nextlen; nextlen = tree[n+1].Len; - if (++count < max_count && curlen == nextlen) { - continue; - } else if (count < min_count) { - do { send_code(s, curlen, s->bl_tree); } while (--count != 0); - - } else if (curlen != 0) { - if (curlen != prevlen) { - send_code(s, curlen, s->bl_tree); count--; - } - Assert(count >= 3 && count <= 6, " 3_6?"); - send_code(s, REP_3_6, s->bl_tree); send_bits(s, count-3, 2); - - } else if (count <= 10) { - send_code(s, REPZ_3_10, s->bl_tree); send_bits(s, count-3, 3); - - } else { - send_code(s, REPZ_11_138, s->bl_tree); send_bits(s, count-11, 7); - } - count = 0; prevlen = curlen; - if (nextlen == 0) { - max_count = 138, min_count = 3; - } else if (curlen == nextlen) { - max_count = 6, min_count = 3; - } else { - max_count = 7, min_count = 4; - } - } -} - -/* =========================================================================== - * Construct the Huffman tree for the bit lengths and return the index in - * bl_order of the last bit length code to send. - */ -local int build_bl_tree(s) - deflate_state *s; -{ - int max_blindex; /* index of last bit length code of non zero freq */ - - /* Determine the bit length frequencies for literal and distance trees */ - scan_tree(s, (ct_data *)s->dyn_ltree, s->l_desc.max_code); - scan_tree(s, (ct_data *)s->dyn_dtree, s->d_desc.max_code); - - /* Build the bit length tree: */ - build_tree(s, (tree_desc *)(&(s->bl_desc))); - /* opt_len now includes the length of the tree representations, except - * the lengths of the bit lengths codes and the 5+5+4 bits for the counts. - */ - - /* Determine the number of bit length codes to send. The pkzip format - * requires that at least 4 bit length codes be sent. (appnote.txt says - * 3 but the actual value used is 4.) - */ - for (max_blindex = BL_CODES-1; max_blindex >= 3; max_blindex--) { - if (s->bl_tree[bl_order[max_blindex]].Len != 0) break; - } - /* Update opt_len to include the bit length tree and counts */ - s->opt_len += 3*(max_blindex+1) + 5+5+4; - Tracev((stderr, "\ndyn trees: dyn %ld, stat %ld", - s->opt_len, s->static_len)); - - return max_blindex; -} - -/* =========================================================================== - * Send the header for a block using dynamic Huffman trees: the counts, the - * lengths of the bit length codes, the literal tree and the distance tree. - * IN assertion: lcodes >= 257, dcodes >= 1, blcodes >= 4. - */ -local void send_all_trees(s, lcodes, dcodes, blcodes) - deflate_state *s; - int lcodes, dcodes, blcodes; /* number of codes for each tree */ -{ - int rank; /* index in bl_order */ - - Assert (lcodes >= 257 && dcodes >= 1 && blcodes >= 4, "not enough codes"); - Assert (lcodes <= L_CODES && dcodes <= D_CODES && blcodes <= BL_CODES, - "too many codes"); - Tracev((stderr, "\nbl counts: ")); - send_bits(s, lcodes-257, 5); /* not +255 as stated in appnote.txt */ - send_bits(s, dcodes-1, 5); - send_bits(s, blcodes-4, 4); /* not -3 as stated in appnote.txt */ - for (rank = 0; rank < blcodes; rank++) { - Tracev((stderr, "\nbl code %2d ", bl_order[rank])); - send_bits(s, s->bl_tree[bl_order[rank]].Len, 3); - } - Tracev((stderr, "\nbl tree: sent %ld", s->bits_sent)); - - send_tree(s, (ct_data *)s->dyn_ltree, lcodes-1); /* literal tree */ - Tracev((stderr, "\nlit tree: sent %ld", s->bits_sent)); - - send_tree(s, (ct_data *)s->dyn_dtree, dcodes-1); /* distance tree */ - Tracev((stderr, "\ndist tree: sent %ld", s->bits_sent)); -} - -/* =========================================================================== - * Send a stored block - */ -void ZLIB_INTERNAL _tr_stored_block(s, buf, stored_len, last) - deflate_state *s; - charf *buf; /* input block */ - ulg stored_len; /* length of input block */ - int last; /* one if this is the last block for a file */ -{ - send_bits(s, (STORED_BLOCK<<1)+last, 3); /* send block type */ -#ifdef DEBUG - s->compressed_len = (s->compressed_len + 3 + 7) & (ulg)~7L; - s->compressed_len += (stored_len + 4) << 3; -#endif - copy_block(s, buf, (unsigned)stored_len, 1); /* with header */ -} - -/* =========================================================================== - * Send one empty static block to give enough lookahead for inflate. - * This takes 10 bits, of which 7 may remain in the bit buffer. - * The current inflate code requires 9 bits of lookahead. If the - * last two codes for the previous block (real code plus EOB) were coded - * on 5 bits or less, inflate may have only 5+3 bits of lookahead to decode - * the last real code. In this case we send two empty static blocks instead - * of one. (There are no problems if the previous block is stored or fixed.) - * To simplify the code, we assume the worst case of last real code encoded - * on one bit only. - */ -void ZLIB_INTERNAL _tr_align(s) - deflate_state *s; -{ - send_bits(s, STATIC_TREES<<1, 3); - send_code(s, END_BLOCK, static_ltree); -#ifdef DEBUG - s->compressed_len += 10L; /* 3 for block type, 7 for EOB */ -#endif - bi_flush(s); - /* Of the 10 bits for the empty block, we have already sent - * (10 - bi_valid) bits. The lookahead for the last real code (before - * the EOB of the previous block) was thus at least one plus the length - * of the EOB plus what we have just sent of the empty static block. - */ - if (1 + s->last_eob_len + 10 - s->bi_valid < 9) { - send_bits(s, STATIC_TREES<<1, 3); - send_code(s, END_BLOCK, static_ltree); -#ifdef DEBUG - s->compressed_len += 10L; -#endif - bi_flush(s); - } - s->last_eob_len = 7; -} - -/* =========================================================================== - * Determine the best encoding for the current block: dynamic trees, static - * trees or store, and output the encoded block to the zip file. - */ -void ZLIB_INTERNAL _tr_flush_block(s, buf, stored_len, last) - deflate_state *s; - charf *buf; /* input block, or NULL if too old */ - ulg stored_len; /* length of input block */ - int last; /* one if this is the last block for a file */ -{ - ulg opt_lenb, static_lenb; /* opt_len and static_len in bytes */ - int max_blindex = 0; /* index of last bit length code of non zero freq */ - - /* Build the Huffman trees unless a stored block is forced */ - if (s->level > 0) { - - /* Check if the file is binary or text */ - if (s->strm->data_type == Z_UNKNOWN) - s->strm->data_type = detect_data_type(s); - - /* Construct the literal and distance trees */ - build_tree(s, (tree_desc *)(&(s->l_desc))); - Tracev((stderr, "\nlit data: dyn %ld, stat %ld", s->opt_len, - s->static_len)); - - build_tree(s, (tree_desc *)(&(s->d_desc))); - Tracev((stderr, "\ndist data: dyn %ld, stat %ld", s->opt_len, - s->static_len)); - /* At this point, opt_len and static_len are the total bit lengths of - * the compressed block data, excluding the tree representations. - */ - - /* Build the bit length tree for the above two trees, and get the index - * in bl_order of the last bit length code to send. - */ - max_blindex = build_bl_tree(s); - - /* Determine the best encoding. Compute the block lengths in bytes. */ - opt_lenb = (s->opt_len+3+7)>>3; - static_lenb = (s->static_len+3+7)>>3; - - Tracev((stderr, "\nopt %lu(%lu) stat %lu(%lu) stored %lu lit %u ", - opt_lenb, s->opt_len, static_lenb, s->static_len, stored_len, - s->last_lit)); - - if (static_lenb <= opt_lenb) opt_lenb = static_lenb; - - } else { - Assert(buf != (char*)0, "lost buf"); - opt_lenb = static_lenb = stored_len + 5; /* force a stored block */ - } - -#ifdef FORCE_STORED - if (buf != (char*)0) { /* force stored block */ -#else - if (stored_len+4 <= opt_lenb && buf != (char*)0) { - /* 4: two words for the lengths */ -#endif - /* The test buf != NULL is only necessary if LIT_BUFSIZE > WSIZE. - * Otherwise we can't have processed more than WSIZE input bytes since - * the last block flush, because compression would have been - * successful. If LIT_BUFSIZE <= WSIZE, it is never too late to - * transform a block into a stored block. - */ - _tr_stored_block(s, buf, stored_len, last); - -#ifdef FORCE_STATIC - } else if (static_lenb >= 0) { /* force static trees */ -#else - } else if (s->strategy == Z_FIXED || static_lenb == opt_lenb) { -#endif - send_bits(s, (STATIC_TREES<<1)+last, 3); - compress_block(s, (ct_data *)static_ltree, (ct_data *)static_dtree); -#ifdef DEBUG - s->compressed_len += 3 + s->static_len; -#endif - } else { - send_bits(s, (DYN_TREES<<1)+last, 3); - send_all_trees(s, s->l_desc.max_code+1, s->d_desc.max_code+1, - max_blindex+1); - compress_block(s, (ct_data *)s->dyn_ltree, (ct_data *)s->dyn_dtree); -#ifdef DEBUG - s->compressed_len += 3 + s->opt_len; -#endif - } - Assert (s->compressed_len == s->bits_sent, "bad compressed size"); - /* The above check is made mod 2^32, for files larger than 512 MB - * and uLong implemented on 32 bits. - */ - init_block(s); - - if (last) { - bi_windup(s); -#ifdef DEBUG - s->compressed_len += 7; /* align on byte boundary */ -#endif - } - Tracev((stderr,"\ncomprlen %lu(%lu) ", s->compressed_len>>3, - s->compressed_len-7*last)); -} - -/* =========================================================================== - * Save the match info and tally the frequency counts. Return true if - * the current block must be flushed. - */ -int ZLIB_INTERNAL _tr_tally (s, dist, lc) - deflate_state *s; - unsigned dist; /* distance of matched string */ - unsigned lc; /* match length-MIN_MATCH or unmatched char (if dist==0) */ -{ - s->d_buf[s->last_lit] = (ush)dist; - s->l_buf[s->last_lit++] = (uch)lc; - if (dist == 0) { - /* lc is the unmatched char */ - s->dyn_ltree[lc].Freq++; - } else { - s->matches++; - /* Here, lc is the match length - MIN_MATCH */ - dist--; /* dist = match distance - 1 */ - Assert((ush)dist < (ush)MAX_DIST(s) && - (ush)lc <= (ush)(MAX_MATCH-MIN_MATCH) && - (ush)d_code(dist) < (ush)D_CODES, "_tr_tally: bad match"); - - s->dyn_ltree[_length_code[lc]+LITERALS+1].Freq++; - s->dyn_dtree[d_code(dist)].Freq++; - } - -#ifdef TRUNCATE_BLOCK - /* Try to guess if it is profitable to stop the current block here */ - if ((s->last_lit & 0x1fff) == 0 && s->level > 2) { - /* Compute an upper bound for the compressed length */ - ulg out_length = (ulg)s->last_lit*8L; - ulg in_length = (ulg)((long)s->strstart - s->block_start); - int dcode; - for (dcode = 0; dcode < D_CODES; dcode++) { - out_length += (ulg)s->dyn_dtree[dcode].Freq * - (5L+extra_dbits[dcode]); - } - out_length >>= 3; - Tracev((stderr,"\nlast_lit %u, in %ld, out ~%ld(%ld%%) ", - s->last_lit, in_length, out_length, - 100L - out_length*100L/in_length)); - if (s->matches < s->last_lit/2 && out_length < in_length/2) return 1; - } -#endif - return (s->last_lit == s->lit_bufsize-1); - /* We avoid equality with lit_bufsize because of wraparound at 64K - * on 16 bit machines and because stored blocks are restricted to - * 64K-1 bytes. - */ -} - -/* =========================================================================== - * Send the block data compressed using the given Huffman trees - */ -local void compress_block(s, ltree, dtree) - deflate_state *s; - ct_data *ltree; /* literal tree */ - ct_data *dtree; /* distance tree */ -{ - unsigned dist; /* distance of matched string */ - int lc; /* match length or unmatched char (if dist == 0) */ - unsigned lx = 0; /* running index in l_buf */ - unsigned code; /* the code to send */ - int extra; /* number of extra bits to send */ - - if (s->last_lit != 0) do { - dist = s->d_buf[lx]; - lc = s->l_buf[lx++]; - if (dist == 0) { - send_code(s, lc, ltree); /* send a literal byte */ - Tracecv(isgraph(lc), (stderr," '%c' ", lc)); - } else { - /* Here, lc is the match length - MIN_MATCH */ - code = _length_code[lc]; - send_code(s, code+LITERALS+1, ltree); /* send the length code */ - extra = extra_lbits[code]; - if (extra != 0) { - lc -= base_length[code]; - send_bits(s, lc, extra); /* send the extra length bits */ - } - dist--; /* dist is now the match distance - 1 */ - code = d_code(dist); - Assert (code < D_CODES, "bad d_code"); - - send_code(s, code, dtree); /* send the distance code */ - extra = extra_dbits[code]; - if (extra != 0) { - dist -= base_dist[code]; - send_bits(s, dist, extra); /* send the extra distance bits */ - } - } /* literal or match pair ? */ - - /* Check that the overlay between pending_buf and d_buf+l_buf is ok: */ - Assert((uInt)(s->pending) < s->lit_bufsize + 2*lx, - "pendingBuf overflow"); - - } while (lx < s->last_lit); - - send_code(s, END_BLOCK, ltree); - s->last_eob_len = ltree[END_BLOCK].Len; -} - -/* =========================================================================== - * Check if the data type is TEXT or BINARY, using the following algorithm: - * - TEXT if the two conditions below are satisfied: - * a) There are no non-portable control characters belonging to the - * "black list" (0..6, 14..25, 28..31). - * b) There is at least one printable character belonging to the - * "white list" (9 {TAB}, 10 {LF}, 13 {CR}, 32..255). - * - BINARY otherwise. - * - The following partially-portable control characters form a - * "gray list" that is ignored in this detection algorithm: - * (7 {BEL}, 8 {BS}, 11 {VT}, 12 {FF}, 26 {SUB}, 27 {ESC}). - * IN assertion: the fields Freq of dyn_ltree are set. - */ -local int detect_data_type(s) - deflate_state *s; -{ - /* black_mask is the bit mask of black-listed bytes - * set bits 0..6, 14..25, and 28..31 - * 0xf3ffc07f = binary 11110011111111111100000001111111 - */ - unsigned long black_mask = 0xf3ffc07fUL; - int n; - - /* Check for non-textual ("black-listed") bytes. */ - for (n = 0; n <= 31; n++, black_mask >>= 1) - if ((black_mask & 1) && (s->dyn_ltree[n].Freq != 0)) - return Z_BINARY; - - /* Check for textual ("white-listed") bytes. */ - if (s->dyn_ltree[9].Freq != 0 || s->dyn_ltree[10].Freq != 0 - || s->dyn_ltree[13].Freq != 0) - return Z_TEXT; - for (n = 32; n < LITERALS; n++) - if (s->dyn_ltree[n].Freq != 0) - return Z_TEXT; - - /* There are no "black-listed" or "white-listed" bytes: - * this stream either is empty or has tolerated ("gray-listed") bytes only. - */ - return Z_BINARY; -} - -/* =========================================================================== - * Reverse the first len bits of a code, using straightforward code (a faster - * method would use a table) - * IN assertion: 1 <= len <= 15 - */ -local unsigned bi_reverse(code, len) - unsigned code; /* the value to invert */ - int len; /* its bit length */ -{ - register unsigned res = 0; - do { - res |= code & 1; - code >>= 1, res <<= 1; - } while (--len > 0); - return res >> 1; -} - -/* =========================================================================== - * Flush the bit buffer, keeping at most 7 bits in it. - */ -local void bi_flush(s) - deflate_state *s; -{ - if (s->bi_valid == 16) { - put_short(s, s->bi_buf); - s->bi_buf = 0; - s->bi_valid = 0; - } else if (s->bi_valid >= 8) { - put_byte(s, (Byte)s->bi_buf); - s->bi_buf >>= 8; - s->bi_valid -= 8; - } -} - -/* =========================================================================== - * Flush the bit buffer and align the output on a byte boundary - */ -local void bi_windup(s) - deflate_state *s; -{ - if (s->bi_valid > 8) { - put_short(s, s->bi_buf); - } else if (s->bi_valid > 0) { - put_byte(s, (Byte)s->bi_buf); - } - s->bi_buf = 0; - s->bi_valid = 0; -#ifdef DEBUG - s->bits_sent = (s->bits_sent+7) & ~7; -#endif -} - -/* =========================================================================== - * Copy a stored block, storing first the length and its - * one's complement if requested. - */ -local void copy_block(s, buf, len, header) - deflate_state *s; - charf *buf; /* the input data */ - unsigned len; /* its length */ - int header; /* true if block header must be written */ -{ - bi_windup(s); /* align on byte boundary */ - s->last_eob_len = 8; /* enough lookahead for inflate */ - - if (header) { - put_short(s, (ush)len); - put_short(s, (ush)~len); -#ifdef DEBUG - s->bits_sent += 2*16; -#endif - } -#ifdef DEBUG - s->bits_sent += (ulg)len<<3; -#endif - while (len--) { - put_byte(s, *buf++); - } -} diff --git a/app/jni/src/libultraship/extern/StormLib/src/zlib/trees.h b/app/jni/src/libultraship/extern/StormLib/src/zlib/trees.h deleted file mode 100644 index d35639d..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/zlib/trees.h +++ /dev/null @@ -1,128 +0,0 @@ -/* header created automatically with -DGEN_TREES_H */ - -local const ct_data static_ltree[L_CODES+2] = { -{{ 12},{ 8}}, {{140},{ 8}}, {{ 76},{ 8}}, {{204},{ 8}}, {{ 44},{ 8}}, -{{172},{ 8}}, {{108},{ 8}}, {{236},{ 8}}, {{ 28},{ 8}}, {{156},{ 8}}, -{{ 92},{ 8}}, {{220},{ 8}}, {{ 60},{ 8}}, {{188},{ 8}}, {{124},{ 8}}, -{{252},{ 8}}, {{ 2},{ 8}}, {{130},{ 8}}, {{ 66},{ 8}}, {{194},{ 8}}, -{{ 34},{ 8}}, {{162},{ 8}}, {{ 98},{ 8}}, {{226},{ 8}}, {{ 18},{ 8}}, -{{146},{ 8}}, {{ 82},{ 8}}, {{210},{ 8}}, {{ 50},{ 8}}, {{178},{ 8}}, -{{114},{ 8}}, {{242},{ 8}}, {{ 10},{ 8}}, {{138},{ 8}}, {{ 74},{ 8}}, -{{202},{ 8}}, {{ 42},{ 8}}, {{170},{ 8}}, {{106},{ 8}}, {{234},{ 8}}, -{{ 26},{ 8}}, {{154},{ 8}}, {{ 90},{ 8}}, {{218},{ 8}}, {{ 58},{ 8}}, -{{186},{ 8}}, {{122},{ 8}}, {{250},{ 8}}, {{ 6},{ 8}}, {{134},{ 8}}, -{{ 70},{ 8}}, {{198},{ 8}}, {{ 38},{ 8}}, {{166},{ 8}}, {{102},{ 8}}, -{{230},{ 8}}, {{ 22},{ 8}}, {{150},{ 8}}, {{ 86},{ 8}}, {{214},{ 8}}, -{{ 54},{ 8}}, {{182},{ 8}}, {{118},{ 8}}, {{246},{ 8}}, {{ 14},{ 8}}, -{{142},{ 8}}, {{ 78},{ 8}}, {{206},{ 8}}, {{ 46},{ 8}}, {{174},{ 8}}, -{{110},{ 8}}, {{238},{ 8}}, {{ 30},{ 8}}, {{158},{ 8}}, {{ 94},{ 8}}, -{{222},{ 8}}, {{ 62},{ 8}}, {{190},{ 8}}, {{126},{ 8}}, {{254},{ 8}}, -{{ 1},{ 8}}, {{129},{ 8}}, {{ 65},{ 8}}, {{193},{ 8}}, {{ 33},{ 8}}, -{{161},{ 8}}, {{ 97},{ 8}}, {{225},{ 8}}, {{ 17},{ 8}}, {{145},{ 8}}, -{{ 81},{ 8}}, {{209},{ 8}}, {{ 49},{ 8}}, {{177},{ 8}}, {{113},{ 8}}, -{{241},{ 8}}, {{ 9},{ 8}}, {{137},{ 8}}, {{ 73},{ 8}}, {{201},{ 8}}, -{{ 41},{ 8}}, {{169},{ 8}}, {{105},{ 8}}, {{233},{ 8}}, {{ 25},{ 8}}, -{{153},{ 8}}, {{ 89},{ 8}}, {{217},{ 8}}, {{ 57},{ 8}}, {{185},{ 8}}, -{{121},{ 8}}, {{249},{ 8}}, {{ 5},{ 8}}, {{133},{ 8}}, {{ 69},{ 8}}, -{{197},{ 8}}, {{ 37},{ 8}}, {{165},{ 8}}, {{101},{ 8}}, {{229},{ 8}}, -{{ 21},{ 8}}, {{149},{ 8}}, {{ 85},{ 8}}, {{213},{ 8}}, {{ 53},{ 8}}, -{{181},{ 8}}, {{117},{ 8}}, {{245},{ 8}}, {{ 13},{ 8}}, {{141},{ 8}}, -{{ 77},{ 8}}, {{205},{ 8}}, {{ 45},{ 8}}, {{173},{ 8}}, {{109},{ 8}}, -{{237},{ 8}}, {{ 29},{ 8}}, {{157},{ 8}}, {{ 93},{ 8}}, {{221},{ 8}}, -{{ 61},{ 8}}, {{189},{ 8}}, {{125},{ 8}}, {{253},{ 8}}, {{ 19},{ 9}}, -{{275},{ 9}}, {{147},{ 9}}, {{403},{ 9}}, {{ 83},{ 9}}, {{339},{ 9}}, -{{211},{ 9}}, {{467},{ 9}}, {{ 51},{ 9}}, {{307},{ 9}}, {{179},{ 9}}, -{{435},{ 9}}, {{115},{ 9}}, {{371},{ 9}}, {{243},{ 9}}, {{499},{ 9}}, -{{ 11},{ 9}}, {{267},{ 9}}, {{139},{ 9}}, {{395},{ 9}}, {{ 75},{ 9}}, -{{331},{ 9}}, {{203},{ 9}}, {{459},{ 9}}, {{ 43},{ 9}}, {{299},{ 9}}, -{{171},{ 9}}, {{427},{ 9}}, {{107},{ 9}}, {{363},{ 9}}, {{235},{ 9}}, -{{491},{ 9}}, {{ 27},{ 9}}, {{283},{ 9}}, {{155},{ 9}}, {{411},{ 9}}, -{{ 91},{ 9}}, {{347},{ 9}}, {{219},{ 9}}, {{475},{ 9}}, {{ 59},{ 9}}, -{{315},{ 9}}, {{187},{ 9}}, {{443},{ 9}}, {{123},{ 9}}, {{379},{ 9}}, -{{251},{ 9}}, {{507},{ 9}}, {{ 7},{ 9}}, {{263},{ 9}}, {{135},{ 9}}, -{{391},{ 9}}, {{ 71},{ 9}}, {{327},{ 9}}, {{199},{ 9}}, {{455},{ 9}}, -{{ 39},{ 9}}, {{295},{ 9}}, {{167},{ 9}}, {{423},{ 9}}, {{103},{ 9}}, -{{359},{ 9}}, {{231},{ 9}}, {{487},{ 9}}, {{ 23},{ 9}}, {{279},{ 9}}, -{{151},{ 9}}, {{407},{ 9}}, {{ 87},{ 9}}, {{343},{ 9}}, {{215},{ 9}}, -{{471},{ 9}}, {{ 55},{ 9}}, {{311},{ 9}}, {{183},{ 9}}, {{439},{ 9}}, -{{119},{ 9}}, {{375},{ 9}}, {{247},{ 9}}, {{503},{ 9}}, {{ 15},{ 9}}, -{{271},{ 9}}, {{143},{ 9}}, {{399},{ 9}}, {{ 79},{ 9}}, {{335},{ 9}}, -{{207},{ 9}}, {{463},{ 9}}, {{ 47},{ 9}}, {{303},{ 9}}, {{175},{ 9}}, -{{431},{ 9}}, {{111},{ 9}}, {{367},{ 9}}, {{239},{ 9}}, {{495},{ 9}}, -{{ 31},{ 9}}, {{287},{ 9}}, {{159},{ 9}}, {{415},{ 9}}, {{ 95},{ 9}}, -{{351},{ 9}}, {{223},{ 9}}, {{479},{ 9}}, {{ 63},{ 9}}, {{319},{ 9}}, -{{191},{ 9}}, {{447},{ 9}}, {{127},{ 9}}, {{383},{ 9}}, {{255},{ 9}}, -{{511},{ 9}}, {{ 0},{ 7}}, {{ 64},{ 7}}, {{ 32},{ 7}}, {{ 96},{ 7}}, -{{ 16},{ 7}}, {{ 80},{ 7}}, {{ 48},{ 7}}, {{112},{ 7}}, {{ 8},{ 7}}, -{{ 72},{ 7}}, {{ 40},{ 7}}, {{104},{ 7}}, {{ 24},{ 7}}, {{ 88},{ 7}}, -{{ 56},{ 7}}, {{120},{ 7}}, {{ 4},{ 7}}, {{ 68},{ 7}}, {{ 36},{ 7}}, -{{100},{ 7}}, {{ 20},{ 7}}, {{ 84},{ 7}}, {{ 52},{ 7}}, {{116},{ 7}}, -{{ 3},{ 8}}, {{131},{ 8}}, {{ 67},{ 8}}, {{195},{ 8}}, {{ 35},{ 8}}, -{{163},{ 8}}, {{ 99},{ 8}}, {{227},{ 8}} -}; - -local const ct_data static_dtree[D_CODES] = { -{{ 0},{ 5}}, {{16},{ 5}}, {{ 8},{ 5}}, {{24},{ 5}}, {{ 4},{ 5}}, -{{20},{ 5}}, {{12},{ 5}}, {{28},{ 5}}, {{ 2},{ 5}}, {{18},{ 5}}, -{{10},{ 5}}, {{26},{ 5}}, {{ 6},{ 5}}, {{22},{ 5}}, {{14},{ 5}}, -{{30},{ 5}}, {{ 1},{ 5}}, {{17},{ 5}}, {{ 9},{ 5}}, {{25},{ 5}}, -{{ 5},{ 5}}, {{21},{ 5}}, {{13},{ 5}}, {{29},{ 5}}, {{ 3},{ 5}}, -{{19},{ 5}}, {{11},{ 5}}, {{27},{ 5}}, {{ 7},{ 5}}, {{23},{ 5}} -}; - -const uch ZLIB_INTERNAL _dist_code[DIST_CODE_LEN] = { - 0, 1, 2, 3, 4, 4, 5, 5, 6, 6, 6, 6, 7, 7, 7, 7, 8, 8, 8, 8, - 8, 8, 8, 8, 9, 9, 9, 9, 9, 9, 9, 9, 10, 10, 10, 10, 10, 10, 10, 10, -10, 10, 10, 10, 10, 10, 10, 10, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, -11, 11, 11, 11, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, -12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 13, 13, 13, 13, -13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, -13, 13, 13, 13, 13, 13, 13, 13, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, -14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, -14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, -14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 15, 15, 15, 15, 15, 15, 15, 15, -15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, -15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, -15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 0, 0, 16, 17, -18, 18, 19, 19, 20, 20, 20, 20, 21, 21, 21, 21, 22, 22, 22, 22, 22, 22, 22, 22, -23, 23, 23, 23, 23, 23, 23, 23, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, -24, 24, 24, 24, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, -26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, -26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 27, 27, 27, 27, 27, 27, 27, 27, -27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, -27, 27, 27, 27, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, -28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, -28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, -28, 28, 28, 28, 28, 28, 28, 28, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, -29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, -29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, -29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29 -}; - -const uch ZLIB_INTERNAL _length_code[MAX_MATCH-MIN_MATCH+1]= { - 0, 1, 2, 3, 4, 5, 6, 7, 8, 8, 9, 9, 10, 10, 11, 11, 12, 12, 12, 12, -13, 13, 13, 13, 14, 14, 14, 14, 15, 15, 15, 15, 16, 16, 16, 16, 16, 16, 16, 16, -17, 17, 17, 17, 17, 17, 17, 17, 18, 18, 18, 18, 18, 18, 18, 18, 19, 19, 19, 19, -19, 19, 19, 19, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, -21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 22, 22, 22, 22, -22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 23, 23, 23, 23, 23, 23, 23, 23, -23, 23, 23, 23, 23, 23, 23, 23, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, -24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, -25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, -25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 25, 26, 26, 26, 26, 26, 26, 26, 26, -26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, -26, 26, 26, 26, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, -27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 27, 28 -}; - -local const int base_length[LENGTH_CODES] = { -0, 1, 2, 3, 4, 5, 6, 7, 8, 10, 12, 14, 16, 20, 24, 28, 32, 40, 48, 56, -64, 80, 96, 112, 128, 160, 192, 224, 0 -}; - -local const int base_dist[D_CODES] = { - 0, 1, 2, 3, 4, 6, 8, 12, 16, 24, - 32, 48, 64, 96, 128, 192, 256, 384, 512, 768, - 1024, 1536, 2048, 3072, 4096, 6144, 8192, 12288, 16384, 24576 -}; - diff --git a/app/jni/src/libultraship/extern/StormLib/src/zlib/zconf.h b/app/jni/src/libultraship/extern/StormLib/src/zlib/zconf.h deleted file mode 100644 index 02ce56c..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/zlib/zconf.h +++ /dev/null @@ -1,428 +0,0 @@ -/* zconf.h -- configuration of the zlib compression library - * Copyright (C) 1995-2010 Jean-loup Gailly. - * For conditions of distribution and use, see copyright notice in zlib.h - */ - -/* @(#) $Id$ */ - -#ifndef ZCONF_H -#define ZCONF_H - -/* - * If you *really* need a unique prefix for all types and library functions, - * compile with -DZ_PREFIX. The "standard" zlib should be compiled without it. - * Even better than compiling with -DZ_PREFIX would be to use configure to set - * this permanently in zconf.h using "./configure --zprefix". - */ -#ifdef Z_PREFIX /* may be set to #if 1 by ./configure */ - -/* all linked symbols */ -# define _dist_code z__dist_code -# define _length_code z__length_code -# define _tr_align z__tr_align -# define _tr_flush_block z__tr_flush_block -# define _tr_init z__tr_init -# define _tr_stored_block z__tr_stored_block -# define _tr_tally z__tr_tally -# define adler32 z_adler32 -# define adler32_combine z_adler32_combine -# define adler32_combine64 z_adler32_combine64 -# define compress z_compress -# define compress2 z_compress2 -# define compressBound z_compressBound -# define crc32 z_crc32 -# define crc32_combine z_crc32_combine -# define crc32_combine64 z_crc32_combine64 -# define deflate z_deflate -# define deflateBound z_deflateBound -# define deflateCopy z_deflateCopy -# define deflateEnd z_deflateEnd -# define deflateInit2_ z_deflateInit2_ -# define deflateInit_ z_deflateInit_ -# define deflateParams z_deflateParams -# define deflatePrime z_deflatePrime -# define deflateReset z_deflateReset -# define deflateSetDictionary z_deflateSetDictionary -# define deflateSetHeader z_deflateSetHeader -# define deflateTune z_deflateTune -# define deflate_copyright z_deflate_copyright -# define get_crc_table z_get_crc_table -# define gz_error z_gz_error -# define gz_intmax z_gz_intmax -# define gz_strwinerror z_gz_strwinerror -# define gzbuffer z_gzbuffer -# define gzclearerr z_gzclearerr -# define gzclose z_gzclose -# define gzclose_r z_gzclose_r -# define gzclose_w z_gzclose_w -# define gzdirect z_gzdirect -# define gzdopen z_gzdopen -# define gzeof z_gzeof -# define gzerror z_gzerror -# define gzflush z_gzflush -# define gzgetc z_gzgetc -# define gzgets z_gzgets -# define gzoffset z_gzoffset -# define gzoffset64 z_gzoffset64 -# define gzopen z_gzopen -# define gzopen64 z_gzopen64 -# define gzprintf z_gzprintf -# define gzputc z_gzputc -# define gzputs z_gzputs -# define gzread z_gzread -# define gzrewind z_gzrewind -# define gzseek z_gzseek -# define gzseek64 z_gzseek64 -# define gzsetparams z_gzsetparams -# define gztell z_gztell -# define gztell64 z_gztell64 -# define gzungetc z_gzungetc -# define gzwrite z_gzwrite -# define inflate z_inflate -# define inflateBack z_inflateBack -# define inflateBackEnd z_inflateBackEnd -# define inflateBackInit_ z_inflateBackInit_ -# define inflateCopy z_inflateCopy -# define inflateEnd z_inflateEnd -# define inflateGetHeader z_inflateGetHeader -# define inflateInit2_ z_inflateInit2_ -# define inflateInit_ z_inflateInit_ -# define inflateMark z_inflateMark -# define inflatePrime z_inflatePrime -# define inflateReset z_inflateReset -# define inflateReset2 z_inflateReset2 -# define inflateSetDictionary z_inflateSetDictionary -# define inflateSync z_inflateSync -# define inflateSyncPoint z_inflateSyncPoint -# define inflateUndermine z_inflateUndermine -# define inflate_copyright z_inflate_copyright -# define inflate_fast z_inflate_fast -# define inflate_table z_inflate_table -# define uncompress z_uncompress -# define zError z_zError -# define zcalloc z_zcalloc -# define zcfree z_zcfree -# define zlibCompileFlags z_zlibCompileFlags -# define zlibVersion z_zlibVersion - -/* all zlib typedefs in zlib.h and zconf.h */ -# define Byte z_Byte -# define Bytef z_Bytef -# define alloc_func z_alloc_func -# define charf z_charf -# define free_func z_free_func -# define gzFile z_gzFile -# define gz_header z_gz_header -# define gz_headerp z_gz_headerp -# define in_func z_in_func -# define intf z_intf -# define out_func z_out_func -# define uInt z_uInt -# define uIntf z_uIntf -# define uLong z_uLong -# define uLongf z_uLongf -# define voidp z_voidp -# define voidpc z_voidpc -# define voidpf z_voidpf - -/* all zlib structs in zlib.h and zconf.h */ -# define gz_header_s z_gz_header_s -# define internal_state z_internal_state - -#endif - -#if defined(__MSDOS__) && !defined(MSDOS) -# define MSDOS -#endif -#if (defined(OS_2) || defined(__OS2__)) && !defined(OS2) -# define OS2 -#endif -#if defined(_WINDOWS) && !defined(WINDOWS) -# define WINDOWS -#endif -#if defined(_WIN32) || defined(_WIN32_WCE) || defined(__WIN32__) -# ifndef WIN32 -# define WIN32 -# endif -#endif -#if (defined(MSDOS) || defined(OS2) || defined(WINDOWS)) && !defined(WIN32) -# if !defined(__GNUC__) && !defined(__FLAT__) && !defined(__386__) -# ifndef SYS16BIT -# define SYS16BIT -# endif -# endif -#endif - -/* - * Compile with -DMAXSEG_64K if the alloc function cannot allocate more - * than 64k bytes at a time (needed on systems with 16-bit int). - */ -#ifdef SYS16BIT -# define MAXSEG_64K -#endif -#ifdef MSDOS -# define UNALIGNED_OK -#endif - -#ifdef __STDC_VERSION__ -# ifndef STDC -# define STDC -# endif -# if __STDC_VERSION__ >= 199901L -# ifndef STDC99 -# define STDC99 -# endif -# endif -#endif -#if !defined(STDC) && (defined(__STDC__) || defined(__cplusplus)) -# define STDC -#endif -#if !defined(STDC) && (defined(__GNUC__) || defined(__BORLANDC__)) -# define STDC -#endif -#if !defined(STDC) && (defined(MSDOS) || defined(WINDOWS) || defined(WIN32)) -# define STDC -#endif -#if !defined(STDC) && (defined(OS2) || defined(__HOS_AIX__)) -# define STDC -#endif - -#if defined(__OS400__) && !defined(STDC) /* iSeries (formerly AS/400). */ -# define STDC -#endif - -#ifndef STDC -# ifndef const /* cannot use !defined(STDC) && !defined(const) on Mac */ -# define const /* note: need a more gentle solution here */ -# endif -#endif - -/* Some Mac compilers merge all .h files incorrectly: */ -#if defined(__MWERKS__)||defined(applec)||defined(THINK_C)||defined(__SC__) -# define NO_DUMMY_DECL -#endif - -/* Maximum value for memLevel in deflateInit2 */ -#ifndef MAX_MEM_LEVEL -# ifdef MAXSEG_64K -# define MAX_MEM_LEVEL 8 -# else -# define MAX_MEM_LEVEL 9 -# endif -#endif - -/* Maximum value for windowBits in deflateInit2 and inflateInit2. - * WARNING: reducing MAX_WBITS makes minigzip unable to extract .gz files - * created by gzip. (Files created by minigzip can still be extracted by - * gzip.) - */ -#ifndef MAX_WBITS -# define MAX_WBITS 15 /* 32K LZ77 window */ -#endif - -/* The memory requirements for deflate are (in bytes): - (1 << (windowBits+2)) + (1 << (memLevel+9)) - that is: 128K for windowBits=15 + 128K for memLevel = 8 (default values) - plus a few kilobytes for small objects. For example, if you want to reduce - the default memory requirements from 256K to 128K, compile with - make CFLAGS="-O -DMAX_WBITS=14 -DMAX_MEM_LEVEL=7" - Of course this will generally degrade compression (there's no free lunch). - - The memory requirements for inflate are (in bytes) 1 << windowBits - that is, 32K for windowBits=15 (default value) plus a few kilobytes - for small objects. -*/ - - /* Type declarations */ - -#ifndef OF /* function prototypes */ -# ifdef STDC -# define OF(args) args -# else -# define OF(args) () -# endif -#endif - -/* The following definitions for FAR are needed only for MSDOS mixed - * model programming (small or medium model with some far allocations). - * This was tested only with MSC; for other MSDOS compilers you may have - * to define NO_MEMCPY in zutil.h. If you don't need the mixed model, - * just define FAR to be empty. - */ -#ifdef SYS16BIT -# if defined(M_I86SM) || defined(M_I86MM) - /* MSC small or medium model */ -# define SMALL_MEDIUM -# ifdef _MSC_VER -# define FAR _far -# else -# define FAR far -# endif -# endif -# if (defined(__SMALL__) || defined(__MEDIUM__)) - /* Turbo C small or medium model */ -# define SMALL_MEDIUM -# ifdef __BORLANDC__ -# define FAR _far -# else -# define FAR far -# endif -# endif -#endif - -#if defined(WINDOWS) || defined(WIN32) - /* If building or using zlib as a DLL, define ZLIB_DLL. - * This is not mandatory, but it offers a little performance increase. - */ -# ifdef ZLIB_DLL -# if defined(WIN32) && (!defined(__BORLANDC__) || (__BORLANDC__ >= 0x500)) -# ifdef ZLIB_INTERNAL -# define ZEXTERN extern __declspec(dllexport) -# else -# define ZEXTERN extern __declspec(dllimport) -# endif -# endif -# endif /* ZLIB_DLL */ - /* If building or using zlib with the WINAPI/WINAPIV calling convention, - * define ZLIB_WINAPI. - * Caution: the standard ZLIB1.DLL is NOT compiled using ZLIB_WINAPI. - */ -# ifdef ZLIB_WINAPI -# ifdef FAR -# undef FAR -# endif -# include - /* No need for _export, use ZLIB.DEF instead. */ - /* For complete Windows compatibility, use WINAPI, not __stdcall. */ -# define ZEXPORT WINAPI -# ifdef WIN32 -# define ZEXPORTVA WINAPIV -# else -# define ZEXPORTVA FAR CDECL -# endif -# endif -#endif - -#if defined (__BEOS__) -# ifdef ZLIB_DLL -# ifdef ZLIB_INTERNAL -# define ZEXPORT __declspec(dllexport) -# define ZEXPORTVA __declspec(dllexport) -# else -# define ZEXPORT __declspec(dllimport) -# define ZEXPORTVA __declspec(dllimport) -# endif -# endif -#endif - -#ifndef ZEXTERN -# define ZEXTERN extern -#endif -#ifndef ZEXPORT -# define ZEXPORT -#endif -#ifndef ZEXPORTVA -# define ZEXPORTVA -#endif - -#ifndef FAR -# define FAR -#endif - -#if !defined(__MACTYPES__) -typedef unsigned char Byte; /* 8 bits */ -#endif -typedef unsigned int uInt; /* 16 bits or more */ -typedef unsigned long uLong; /* 32 bits or more */ - -#ifdef SMALL_MEDIUM - /* Borland C/C++ and some old MSC versions ignore FAR inside typedef */ -# define Bytef Byte FAR -#else - typedef Byte FAR Bytef; -#endif -typedef char FAR charf; -typedef int FAR intf; -typedef uInt FAR uIntf; -typedef uLong FAR uLongf; - -#ifdef STDC - typedef void const *voidpc; - typedef void FAR *voidpf; - typedef void *voidp; -#else - typedef Byte const *voidpc; - typedef Byte FAR *voidpf; - typedef Byte *voidp; -#endif - -#ifdef HAVE_UNISTD_H /* may be set to #if 1 by ./configure */ -# define Z_HAVE_UNISTD_H -#endif - -#ifdef STDC -# include /* for off_t */ -#endif - -/* a little trick to accommodate both "#define _LARGEFILE64_SOURCE" and - * "#define _LARGEFILE64_SOURCE 1" as requesting 64-bit operations, (even - * though the former does not conform to the LFS document), but considering - * both "#undef _LARGEFILE64_SOURCE" and "#define _LARGEFILE64_SOURCE 0" as - * equivalently requesting no 64-bit operations - */ -#if -_LARGEFILE64_SOURCE - -1 == 1 -# undef _LARGEFILE64_SOURCE -#endif - -#if defined(Z_HAVE_UNISTD_H) || defined(_LARGEFILE64_SOURCE) -# include /* for SEEK_* and off_t */ -# ifdef VMS -# include /* for off_t */ -# endif -# ifndef z_off_t -# define z_off_t off_t -# endif -#endif - -#ifndef SEEK_SET -# define SEEK_SET 0 /* Seek from beginning of file. */ -# define SEEK_CUR 1 /* Seek from current position. */ -# define SEEK_END 2 /* Set file pointer to EOF plus "offset" */ -#endif - -#ifndef z_off_t -# define z_off_t long -#endif - -#if defined(_LARGEFILE64_SOURCE) && _LFS64_LARGEFILE-0 -# define z_off64_t off64_t -#else -# define z_off64_t z_off_t -#endif - -#if defined(__OS400__) -# define NO_vsnprintf -#endif - -#if defined(__MVS__) -# define NO_vsnprintf -#endif - -/* MVS linker does not support external names larger than 8 bytes */ -#if defined(__MVS__) - #pragma map(deflateInit_,"DEIN") - #pragma map(deflateInit2_,"DEIN2") - #pragma map(deflateEnd,"DEEND") - #pragma map(deflateBound,"DEBND") - #pragma map(inflateInit_,"ININ") - #pragma map(inflateInit2_,"ININ2") - #pragma map(inflateEnd,"INEND") - #pragma map(inflateSync,"INSY") - #pragma map(inflateSetDictionary,"INSEDI") - #pragma map(compressBound,"CMBND") - #pragma map(inflate_table,"INTABL") - #pragma map(inflate_fast,"INFA") - #pragma map(inflate_copyright,"INCOPY") -#endif - -#endif /* ZCONF_H */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/zlib/zlib.h b/app/jni/src/libultraship/extern/StormLib/src/zlib/zlib.h deleted file mode 100644 index bfbba83..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/zlib/zlib.h +++ /dev/null @@ -1,1613 +0,0 @@ -/* zlib.h -- interface of the 'zlib' general purpose compression library - version 1.2.5, April 19th, 2010 - - Copyright (C) 1995-2010 Jean-loup Gailly and Mark Adler - - 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. - - Jean-loup Gailly Mark Adler - jloup@gzip.org madler@alumni.caltech.edu - - - The data format used by the zlib library is described by RFCs (Request for - Comments) 1950 to 1952 in the files http://www.ietf.org/rfc/rfc1950.txt - (zlib format), rfc1951.txt (deflate format) and rfc1952.txt (gzip format). -*/ - -#ifndef ZLIB_H -#define ZLIB_H - -#include "zconf.h" - -#ifdef __cplusplus -extern "C" { -#endif - -#define ZLIB_VERSION "1.2.5" -#define ZLIB_VERNUM 0x1250 -#define ZLIB_VER_MAJOR 1 -#define ZLIB_VER_MINOR 2 -#define ZLIB_VER_REVISION 5 -#define ZLIB_VER_SUBREVISION 0 - -/* - The 'zlib' compression library provides in-memory compression and - decompression functions, including integrity checks of the uncompressed data. - This version of the library supports only one compression method (deflation) - but other algorithms will be added later and will have the same stream - interface. - - Compression can be done in a single step if the buffers are large enough, - or can be done by repeated calls of the compression function. In the latter - case, the application must provide more input and/or consume the output - (providing more output space) before each call. - - The compressed data format used by default by the in-memory functions is - the zlib format, which is a zlib wrapper documented in RFC 1950, wrapped - around a deflate stream, which is itself documented in RFC 1951. - - The library also supports reading and writing files in gzip (.gz) format - with an interface similar to that of stdio using the functions that start - with "gz". The gzip format is different from the zlib format. gzip is a - gzip wrapper, documented in RFC 1952, wrapped around a deflate stream. - - This library can optionally read and write gzip streams in memory as well. - - The zlib format was designed to be compact and fast for use in memory - and on communications channels. The gzip format was designed for single- - file compression on file systems, has a larger header than zlib to maintain - directory information, and uses a different, slower check method than zlib. - - The library does not install any signal handler. The decoder checks - the consistency of the compressed data, so the library should never crash - even in case of corrupted input. -*/ - -typedef voidpf (*alloc_func) OF((voidpf opaque, uInt items, uInt size)); -typedef void (*free_func) OF((voidpf opaque, voidpf address)); - -struct internal_state; - -typedef struct z_stream_s { - Bytef *next_in; /* next input byte */ - uInt avail_in; /* number of bytes available at next_in */ - uLong total_in; /* total nb of input bytes read so far */ - - Bytef *next_out; /* next output byte should be put there */ - uInt avail_out; /* remaining free space at next_out */ - uLong total_out; /* total nb of bytes output so far */ - - char *msg; /* last error message, NULL if no error */ - struct internal_state FAR *state; /* not visible by applications */ - - alloc_func zalloc; /* used to allocate the internal state */ - free_func zfree; /* used to free the internal state */ - voidpf opaque; /* private data object passed to zalloc and zfree */ - - int data_type; /* best guess about the data type: binary or text */ - uLong adler; /* adler32 value of the uncompressed data */ - uLong reserved; /* reserved for future use */ -} z_stream; - -typedef z_stream FAR *z_streamp; - -/* - gzip header information passed to and from zlib routines. See RFC 1952 - for more details on the meanings of these fields. -*/ -typedef struct gz_header_s { - int text; /* true if compressed data believed to be text */ - uLong time; /* modification time */ - int xflags; /* extra flags (not used when writing a gzip file) */ - int os; /* operating system */ - Bytef *extra; /* pointer to extra field or Z_NULL if none */ - uInt extra_len; /* extra field length (valid if extra != Z_NULL) */ - uInt extra_max; /* space at extra (only when reading header) */ - Bytef *name; /* pointer to zero-terminated file name or Z_NULL */ - uInt name_max; /* space at name (only when reading header) */ - Bytef *comment; /* pointer to zero-terminated comment or Z_NULL */ - uInt comm_max; /* space at comment (only when reading header) */ - int hcrc; /* true if there was or will be a header crc */ - int done; /* true when done reading gzip header (not used - when writing a gzip file) */ -} gz_header; - -typedef gz_header FAR *gz_headerp; - -/* - The application must update next_in and avail_in when avail_in has dropped - to zero. It must update next_out and avail_out when avail_out has dropped - to zero. The application must initialize zalloc, zfree and opaque before - calling the init function. All other fields are set by the compression - library and must not be updated by the application. - - The opaque value provided by the application will be passed as the first - parameter for calls of zalloc and zfree. This can be useful for custom - memory management. The compression library attaches no meaning to the - opaque value. - - zalloc must return Z_NULL if there is not enough memory for the object. - If zlib is used in a multi-threaded application, zalloc and zfree must be - thread safe. - - On 16-bit systems, the functions zalloc and zfree must be able to allocate - exactly 65536 bytes, but will not be required to allocate more than this if - the symbol MAXSEG_64K is defined (see zconf.h). WARNING: On MSDOS, pointers - returned by zalloc for objects of exactly 65536 bytes *must* have their - offset normalized to zero. The default allocation function provided by this - library ensures this (see zutil.c). To reduce memory requirements and avoid - any allocation of 64K objects, at the expense of compression ratio, compile - the library with -DMAX_WBITS=14 (see zconf.h). - - The fields total_in and total_out can be used for statistics or progress - reports. After compression, total_in holds the total size of the - uncompressed data and may be saved for use in the decompressor (particularly - if the decompressor wants to decompress everything in a single step). -*/ - - /* constants */ - -#define Z_NO_FLUSH 0 -#define Z_PARTIAL_FLUSH 1 -#define Z_SYNC_FLUSH 2 -#define Z_FULL_FLUSH 3 -#define Z_FINISH 4 -#define Z_BLOCK 5 -#define Z_TREES 6 -/* Allowed flush values; see deflate() and inflate() below for details */ - -#define Z_OK 0 -#define Z_STREAM_END 1 -#define Z_NEED_DICT 2 -#define Z_ERRNO (-1) -#define Z_STREAM_ERROR (-2) -#define Z_DATA_ERROR (-3) -#define Z_MEM_ERROR (-4) -#define Z_BUF_ERROR (-5) -#define Z_VERSION_ERROR (-6) -/* Return codes for the compression/decompression functions. Negative values - * are errors, positive values are used for special but normal events. - */ - -#define Z_NO_COMPRESSION 0 -#define Z_BEST_SPEED 1 -#define Z_BEST_COMPRESSION 9 -#define Z_DEFAULT_COMPRESSION (-1) -/* compression levels */ - -#define Z_FILTERED 1 -#define Z_HUFFMAN_ONLY 2 -#define Z_RLE 3 -#define Z_FIXED 4 -#define Z_DEFAULT_STRATEGY 0 -/* compression strategy; see deflateInit2() below for details */ - -#define Z_BINARY 0 -#define Z_TEXT 1 -#define Z_ASCII Z_TEXT /* for compatibility with 1.2.2 and earlier */ -#define Z_UNKNOWN 2 -/* Possible values of the data_type field (though see inflate()) */ - -#define Z_DEFLATED 8 -/* The deflate compression method (the only one supported in this version) */ - -#define Z_NULL 0 /* for initializing zalloc, zfree, opaque */ - -#define zlib_version zlibVersion() -/* for compatibility with versions < 1.0.2 */ - - - /* basic functions */ - -ZEXTERN const char * ZEXPORT zlibVersion OF((void)); -/* The application can compare zlibVersion and ZLIB_VERSION for consistency. - If the first character differs, the library code actually used is not - compatible with the zlib.h header file used by the application. This check - is automatically made by deflateInit and inflateInit. - */ - -/* -ZEXTERN int ZEXPORT deflateInit OF((z_streamp strm, int level)); - - Initializes the internal stream state for compression. The fields - zalloc, zfree and opaque must be initialized before by the caller. If - zalloc and zfree are set to Z_NULL, deflateInit updates them to use default - allocation functions. - - The compression level must be Z_DEFAULT_COMPRESSION, or between 0 and 9: - 1 gives best speed, 9 gives best compression, 0 gives no compression at all - (the input data is simply copied a block at a time). Z_DEFAULT_COMPRESSION - requests a default compromise between speed and compression (currently - equivalent to level 6). - - deflateInit returns Z_OK if success, Z_MEM_ERROR if there was not enough - memory, Z_STREAM_ERROR if level is not a valid compression level, or - Z_VERSION_ERROR if the zlib library version (zlib_version) is incompatible - with the version assumed by the caller (ZLIB_VERSION). msg is set to null - if there is no error message. deflateInit does not perform any compression: - this will be done by deflate(). -*/ - - -ZEXTERN int ZEXPORT deflate OF((z_streamp strm, int flush)); -/* - deflate compresses as much data as possible, and stops when the input - buffer becomes empty or the output buffer becomes full. It may introduce - some output latency (reading input without producing any output) except when - forced to flush. - - The detailed semantics are as follows. deflate performs one or both of the - following actions: - - - Compress more input starting at next_in and update next_in and avail_in - accordingly. If not all input can be processed (because there is not - enough room in the output buffer), next_in and avail_in are updated and - processing will resume at this point for the next call of deflate(). - - - Provide more output starting at next_out and update next_out and avail_out - accordingly. This action is forced if the parameter flush is non zero. - Forcing flush frequently degrades the compression ratio, so this parameter - should be set only when necessary (in interactive applications). Some - output may be provided even if flush is not set. - - Before the call of deflate(), the application should ensure that at least - one of the actions is possible, by providing more input and/or consuming more - output, and updating avail_in or avail_out accordingly; avail_out should - never be zero before the call. The application can consume the compressed - output when it wants, for example when the output buffer is full (avail_out - == 0), or after each call of deflate(). If deflate returns Z_OK and with - zero avail_out, it must be called again after making room in the output - buffer because there might be more output pending. - - Normally the parameter flush is set to Z_NO_FLUSH, which allows deflate to - decide how much data to accumulate before producing output, in order to - maximize compression. - - If the parameter flush is set to Z_SYNC_FLUSH, all pending output is - flushed to the output buffer and the output is aligned on a byte boundary, so - that the decompressor can get all input data available so far. (In - particular avail_in is zero after the call if enough output space has been - provided before the call.) Flushing may degrade compression for some - compression algorithms and so it should be used only when necessary. This - completes the current deflate block and follows it with an empty stored block - that is three bits plus filler bits to the next byte, followed by four bytes - (00 00 ff ff). - - If flush is set to Z_PARTIAL_FLUSH, all pending output is flushed to the - output buffer, but the output is not aligned to a byte boundary. All of the - input data so far will be available to the decompressor, as for Z_SYNC_FLUSH. - This completes the current deflate block and follows it with an empty fixed - codes block that is 10 bits long. This assures that enough bytes are output - in order for the decompressor to finish the block before the empty fixed code - block. - - If flush is set to Z_BLOCK, a deflate block is completed and emitted, as - for Z_SYNC_FLUSH, but the output is not aligned on a byte boundary, and up to - seven bits of the current block are held to be written as the next byte after - the next deflate block is completed. In this case, the decompressor may not - be provided enough bits at this point in order to complete decompression of - the data provided so far to the compressor. It may need to wait for the next - block to be emitted. This is for advanced applications that need to control - the emission of deflate blocks. - - If flush is set to Z_FULL_FLUSH, all output is flushed as with - Z_SYNC_FLUSH, and the compression state is reset so that decompression can - restart from this point if previous compressed data has been damaged or if - random access is desired. Using Z_FULL_FLUSH too often can seriously degrade - compression. - - If deflate returns with avail_out == 0, this function must be called again - with the same value of the flush parameter and more output space (updated - avail_out), until the flush is complete (deflate returns with non-zero - avail_out). In the case of a Z_FULL_FLUSH or Z_SYNC_FLUSH, make sure that - avail_out is greater than six to avoid repeated flush markers due to - avail_out == 0 on return. - - If the parameter flush is set to Z_FINISH, pending input is processed, - pending output is flushed and deflate returns with Z_STREAM_END if there was - enough output space; if deflate returns with Z_OK, this function must be - called again with Z_FINISH and more output space (updated avail_out) but no - more input data, until it returns with Z_STREAM_END or an error. After - deflate has returned Z_STREAM_END, the only possible operations on the stream - are deflateReset or deflateEnd. - - Z_FINISH can be used immediately after deflateInit if all the compression - is to be done in a single step. In this case, avail_out must be at least the - value returned by deflateBound (see below). If deflate does not return - Z_STREAM_END, then it must be called again as described above. - - deflate() sets strm->adler to the adler32 checksum of all input read - so far (that is, total_in bytes). - - deflate() may update strm->data_type if it can make a good guess about - the input data type (Z_BINARY or Z_TEXT). In doubt, the data is considered - binary. This field is only for information purposes and does not affect the - compression algorithm in any manner. - - deflate() returns Z_OK if some progress has been made (more input - processed or more output produced), Z_STREAM_END if all input has been - consumed and all output has been produced (only when flush is set to - Z_FINISH), Z_STREAM_ERROR if the stream state was inconsistent (for example - if next_in or next_out was Z_NULL), Z_BUF_ERROR if no progress is possible - (for example avail_in or avail_out was zero). Note that Z_BUF_ERROR is not - fatal, and deflate() can be called again with more input and more output - space to continue compressing. -*/ - - -ZEXTERN int ZEXPORT deflateEnd OF((z_streamp strm)); -/* - All dynamically allocated data structures for this stream are freed. - This function discards any unprocessed input and does not flush any pending - output. - - deflateEnd returns Z_OK if success, Z_STREAM_ERROR if the - stream state was inconsistent, Z_DATA_ERROR if the stream was freed - prematurely (some input or output was discarded). In the error case, msg - may be set but then points to a static string (which must not be - deallocated). -*/ - - -/* -ZEXTERN int ZEXPORT inflateInit OF((z_streamp strm)); - - Initializes the internal stream state for decompression. The fields - next_in, avail_in, zalloc, zfree and opaque must be initialized before by - the caller. If next_in is not Z_NULL and avail_in is large enough (the - exact value depends on the compression method), inflateInit determines the - compression method from the zlib header and allocates all data structures - accordingly; otherwise the allocation will be deferred to the first call of - inflate. If zalloc and zfree are set to Z_NULL, inflateInit updates them to - use default allocation functions. - - inflateInit returns Z_OK if success, Z_MEM_ERROR if there was not enough - memory, Z_VERSION_ERROR if the zlib library version is incompatible with the - version assumed by the caller, or Z_STREAM_ERROR if the parameters are - invalid, such as a null pointer to the structure. msg is set to null if - there is no error message. inflateInit does not perform any decompression - apart from possibly reading the zlib header if present: actual decompression - will be done by inflate(). (So next_in and avail_in may be modified, but - next_out and avail_out are unused and unchanged.) The current implementation - of inflateInit() does not process any header information -- that is deferred - until inflate() is called. -*/ - - -ZEXTERN int ZEXPORT inflate OF((z_streamp strm, int flush)); -/* - inflate decompresses as much data as possible, and stops when the input - buffer becomes empty or the output buffer becomes full. It may introduce - some output latency (reading input without producing any output) except when - forced to flush. - - The detailed semantics are as follows. inflate performs one or both of the - following actions: - - - Decompress more input starting at next_in and update next_in and avail_in - accordingly. If not all input can be processed (because there is not - enough room in the output buffer), next_in is updated and processing will - resume at this point for the next call of inflate(). - - - Provide more output starting at next_out and update next_out and avail_out - accordingly. inflate() provides as much output as possible, until there is - no more input data or no more space in the output buffer (see below about - the flush parameter). - - Before the call of inflate(), the application should ensure that at least - one of the actions is possible, by providing more input and/or consuming more - output, and updating the next_* and avail_* values accordingly. The - application can consume the uncompressed output when it wants, for example - when the output buffer is full (avail_out == 0), or after each call of - inflate(). If inflate returns Z_OK and with zero avail_out, it must be - called again after making room in the output buffer because there might be - more output pending. - - The flush parameter of inflate() can be Z_NO_FLUSH, Z_SYNC_FLUSH, Z_FINISH, - Z_BLOCK, or Z_TREES. Z_SYNC_FLUSH requests that inflate() flush as much - output as possible to the output buffer. Z_BLOCK requests that inflate() - stop if and when it gets to the next deflate block boundary. When decoding - the zlib or gzip format, this will cause inflate() to return immediately - after the header and before the first block. When doing a raw inflate, - inflate() will go ahead and process the first block, and will return when it - gets to the end of that block, or when it runs out of data. - - The Z_BLOCK option assists in appending to or combining deflate streams. - Also to assist in this, on return inflate() will set strm->data_type to the - number of unused bits in the last byte taken from strm->next_in, plus 64 if - inflate() is currently decoding the last block in the deflate stream, plus - 128 if inflate() returned immediately after decoding an end-of-block code or - decoding the complete header up to just before the first byte of the deflate - stream. The end-of-block will not be indicated until all of the uncompressed - data from that block has been written to strm->next_out. The number of - unused bits may in general be greater than seven, except when bit 7 of - data_type is set, in which case the number of unused bits will be less than - eight. data_type is set as noted here every time inflate() returns for all - flush options, and so can be used to determine the amount of currently - consumed input in bits. - - The Z_TREES option behaves as Z_BLOCK does, but it also returns when the - end of each deflate block header is reached, before any actual data in that - block is decoded. This allows the caller to determine the length of the - deflate block header for later use in random access within a deflate block. - 256 is added to the value of strm->data_type when inflate() returns - immediately after reaching the end of the deflate block header. - - inflate() should normally be called until it returns Z_STREAM_END or an - error. However if all decompression is to be performed in a single step (a - single call of inflate), the parameter flush should be set to Z_FINISH. In - this case all pending input is processed and all pending output is flushed; - avail_out must be large enough to hold all the uncompressed data. (The size - of the uncompressed data may have been saved by the compressor for this - purpose.) The next operation on this stream must be inflateEnd to deallocate - the decompression state. The use of Z_FINISH is never required, but can be - used to inform inflate that a faster approach may be used for the single - inflate() call. - - In this implementation, inflate() always flushes as much output as - possible to the output buffer, and always uses the faster approach on the - first call. So the only effect of the flush parameter in this implementation - is on the return value of inflate(), as noted below, or when it returns early - because Z_BLOCK or Z_TREES is used. - - If a preset dictionary is needed after this call (see inflateSetDictionary - below), inflate sets strm->adler to the adler32 checksum of the dictionary - chosen by the compressor and returns Z_NEED_DICT; otherwise it sets - strm->adler to the adler32 checksum of all output produced so far (that is, - total_out bytes) and returns Z_OK, Z_STREAM_END or an error code as described - below. At the end of the stream, inflate() checks that its computed adler32 - checksum is equal to that saved by the compressor and returns Z_STREAM_END - only if the checksum is correct. - - inflate() can decompress and check either zlib-wrapped or gzip-wrapped - deflate data. The header type is detected automatically, if requested when - initializing with inflateInit2(). Any information contained in the gzip - header is not retained, so applications that need that information should - instead use raw inflate, see inflateInit2() below, or inflateBack() and - perform their own processing of the gzip header and trailer. - - inflate() returns Z_OK if some progress has been made (more input processed - or more output produced), Z_STREAM_END if the end of the compressed data has - been reached and all uncompressed output has been produced, Z_NEED_DICT if a - preset dictionary is needed at this point, Z_DATA_ERROR if the input data was - corrupted (input stream not conforming to the zlib format or incorrect check - value), Z_STREAM_ERROR if the stream structure was inconsistent (for example - next_in or next_out was Z_NULL), Z_MEM_ERROR if there was not enough memory, - Z_BUF_ERROR if no progress is possible or if there was not enough room in the - output buffer when Z_FINISH is used. Note that Z_BUF_ERROR is not fatal, and - inflate() can be called again with more input and more output space to - continue decompressing. If Z_DATA_ERROR is returned, the application may - then call inflateSync() to look for a good compression block if a partial - recovery of the data is desired. -*/ - - -ZEXTERN int ZEXPORT inflateEnd OF((z_streamp strm)); -/* - All dynamically allocated data structures for this stream are freed. - This function discards any unprocessed input and does not flush any pending - output. - - inflateEnd returns Z_OK if success, Z_STREAM_ERROR if the stream state - was inconsistent. In the error case, msg may be set but then points to a - static string (which must not be deallocated). -*/ - - - /* Advanced functions */ - -/* - The following functions are needed only in some special applications. -*/ - -/* -ZEXTERN int ZEXPORT deflateInit2 OF((z_streamp strm, - int level, - int method, - int windowBits, - int memLevel, - int strategy)); - - This is another version of deflateInit with more compression options. The - fields next_in, zalloc, zfree and opaque must be initialized before by the - caller. - - The method parameter is the compression method. It must be Z_DEFLATED in - this version of the library. - - The windowBits parameter is the base two logarithm of the window size - (the size of the history buffer). It should be in the range 8..15 for this - version of the library. Larger values of this parameter result in better - compression at the expense of memory usage. The default value is 15 if - deflateInit is used instead. - - windowBits can also be -8..-15 for raw deflate. In this case, -windowBits - determines the window size. deflate() will then generate raw deflate data - with no zlib header or trailer, and will not compute an adler32 check value. - - windowBits can also be greater than 15 for optional gzip encoding. Add - 16 to windowBits to write a simple gzip header and trailer around the - compressed data instead of a zlib wrapper. The gzip header will have no - file name, no extra data, no comment, no modification time (set to zero), no - header crc, and the operating system will be set to 255 (unknown). If a - gzip stream is being written, strm->adler is a crc32 instead of an adler32. - - The memLevel parameter specifies how much memory should be allocated - for the internal compression state. memLevel=1 uses minimum memory but is - slow and reduces compression ratio; memLevel=9 uses maximum memory for - optimal speed. The default value is 8. See zconf.h for total memory usage - as a function of windowBits and memLevel. - - The strategy parameter is used to tune the compression algorithm. Use the - value Z_DEFAULT_STRATEGY for normal data, Z_FILTERED for data produced by a - filter (or predictor), Z_HUFFMAN_ONLY to force Huffman encoding only (no - string match), or Z_RLE to limit match distances to one (run-length - encoding). Filtered data consists mostly of small values with a somewhat - random distribution. In this case, the compression algorithm is tuned to - compress them better. The effect of Z_FILTERED is to force more Huffman - coding and less string matching; it is somewhat intermediate between - Z_DEFAULT_STRATEGY and Z_HUFFMAN_ONLY. Z_RLE is designed to be almost as - fast as Z_HUFFMAN_ONLY, but give better compression for PNG image data. The - strategy parameter only affects the compression ratio but not the - correctness of the compressed output even if it is not set appropriately. - Z_FIXED prevents the use of dynamic Huffman codes, allowing for a simpler - decoder for special applications. - - deflateInit2 returns Z_OK if success, Z_MEM_ERROR if there was not enough - memory, Z_STREAM_ERROR if any parameter is invalid (such as an invalid - method), or Z_VERSION_ERROR if the zlib library version (zlib_version) is - incompatible with the version assumed by the caller (ZLIB_VERSION). msg is - set to null if there is no error message. deflateInit2 does not perform any - compression: this will be done by deflate(). -*/ - -ZEXTERN int ZEXPORT deflateSetDictionary OF((z_streamp strm, - const Bytef *dictionary, - uInt dictLength)); -/* - Initializes the compression dictionary from the given byte sequence - without producing any compressed output. This function must be called - immediately after deflateInit, deflateInit2 or deflateReset, before any call - of deflate. The compressor and decompressor must use exactly the same - dictionary (see inflateSetDictionary). - - The dictionary should consist of strings (byte sequences) that are likely - to be encountered later in the data to be compressed, with the most commonly - used strings preferably put towards the end of the dictionary. Using a - dictionary is most useful when the data to be compressed is short and can be - predicted with good accuracy; the data can then be compressed better than - with the default empty dictionary. - - Depending on the size of the compression data structures selected by - deflateInit or deflateInit2, a part of the dictionary may in effect be - discarded, for example if the dictionary is larger than the window size - provided in deflateInit or deflateInit2. Thus the strings most likely to be - useful should be put at the end of the dictionary, not at the front. In - addition, the current implementation of deflate will use at most the window - size minus 262 bytes of the provided dictionary. - - Upon return of this function, strm->adler is set to the adler32 value - of the dictionary; the decompressor may later use this value to determine - which dictionary has been used by the compressor. (The adler32 value - applies to the whole dictionary even if only a subset of the dictionary is - actually used by the compressor.) If a raw deflate was requested, then the - adler32 value is not computed and strm->adler is not set. - - deflateSetDictionary returns Z_OK if success, or Z_STREAM_ERROR if a - parameter is invalid (e.g. dictionary being Z_NULL) or the stream state is - inconsistent (for example if deflate has already been called for this stream - or if the compression method is bsort). deflateSetDictionary does not - perform any compression: this will be done by deflate(). -*/ - -ZEXTERN int ZEXPORT deflateCopy OF((z_streamp dest, - z_streamp source)); -/* - Sets the destination stream as a complete copy of the source stream. - - This function can be useful when several compression strategies will be - tried, for example when there are several ways of pre-processing the input - data with a filter. The streams that will be discarded should then be freed - by calling deflateEnd. Note that deflateCopy duplicates the internal - compression state which can be quite large, so this strategy is slow and can - consume lots of memory. - - deflateCopy returns Z_OK if success, Z_MEM_ERROR if there was not - enough memory, Z_STREAM_ERROR if the source stream state was inconsistent - (such as zalloc being Z_NULL). msg is left unchanged in both source and - destination. -*/ - -ZEXTERN int ZEXPORT deflateReset OF((z_streamp strm)); -/* - This function is equivalent to deflateEnd followed by deflateInit, - but does not free and reallocate all the internal compression state. The - stream will keep the same compression level and any other attributes that - may have been set by deflateInit2. - - deflateReset returns Z_OK if success, or Z_STREAM_ERROR if the source - stream state was inconsistent (such as zalloc or state being Z_NULL). -*/ - -ZEXTERN int ZEXPORT deflateParams OF((z_streamp strm, - int level, - int strategy)); -/* - Dynamically update the compression level and compression strategy. The - interpretation of level and strategy is as in deflateInit2. This can be - used to switch between compression and straight copy of the input data, or - to switch to a different kind of input data requiring a different strategy. - If the compression level is changed, the input available so far is - compressed with the old level (and may be flushed); the new level will take - effect only at the next call of deflate(). - - Before the call of deflateParams, the stream state must be set as for - a call of deflate(), since the currently available input may have to be - compressed and flushed. In particular, strm->avail_out must be non-zero. - - deflateParams returns Z_OK if success, Z_STREAM_ERROR if the source - stream state was inconsistent or if a parameter was invalid, Z_BUF_ERROR if - strm->avail_out was zero. -*/ - -ZEXTERN int ZEXPORT deflateTune OF((z_streamp strm, - int good_length, - int max_lazy, - int nice_length, - int max_chain)); -/* - Fine tune deflate's internal compression parameters. This should only be - used by someone who understands the algorithm used by zlib's deflate for - searching for the best matching string, and even then only by the most - fanatic optimizer trying to squeeze out the last compressed bit for their - specific input data. Read the deflate.c source code for the meaning of the - max_lazy, good_length, nice_length, and max_chain parameters. - - deflateTune() can be called after deflateInit() or deflateInit2(), and - returns Z_OK on success, or Z_STREAM_ERROR for an invalid deflate stream. - */ - -ZEXTERN uLong ZEXPORT deflateBound OF((z_streamp strm, - uLong sourceLen)); -/* - deflateBound() returns an upper bound on the compressed size after - deflation of sourceLen bytes. It must be called after deflateInit() or - deflateInit2(), and after deflateSetHeader(), if used. This would be used - to allocate an output buffer for deflation in a single pass, and so would be - called before deflate(). -*/ - -ZEXTERN int ZEXPORT deflatePrime OF((z_streamp strm, - int bits, - int value)); -/* - deflatePrime() inserts bits in the deflate output stream. The intent - is that this function is used to start off the deflate output with the bits - leftover from a previous deflate stream when appending to it. As such, this - function can only be used for raw deflate, and must be used before the first - deflate() call after a deflateInit2() or deflateReset(). bits must be less - than or equal to 16, and that many of the least significant bits of value - will be inserted in the output. - - deflatePrime returns Z_OK if success, or Z_STREAM_ERROR if the source - stream state was inconsistent. -*/ - -ZEXTERN int ZEXPORT deflateSetHeader OF((z_streamp strm, - gz_headerp head)); -/* - deflateSetHeader() provides gzip header information for when a gzip - stream is requested by deflateInit2(). deflateSetHeader() may be called - after deflateInit2() or deflateReset() and before the first call of - deflate(). The text, time, os, extra field, name, and comment information - in the provided gz_header structure are written to the gzip header (xflag is - ignored -- the extra flags are set according to the compression level). The - caller must assure that, if not Z_NULL, name and comment are terminated with - a zero byte, and that if extra is not Z_NULL, that extra_len bytes are - available there. If hcrc is true, a gzip header crc is included. Note that - the current versions of the command-line version of gzip (up through version - 1.3.x) do not support header crc's, and will report that it is a "multi-part - gzip file" and give up. - - If deflateSetHeader is not used, the default gzip header has text false, - the time set to zero, and os set to 255, with no extra, name, or comment - fields. The gzip header is returned to the default state by deflateReset(). - - deflateSetHeader returns Z_OK if success, or Z_STREAM_ERROR if the source - stream state was inconsistent. -*/ - -/* -ZEXTERN int ZEXPORT inflateInit2 OF((z_streamp strm, - int windowBits)); - - This is another version of inflateInit with an extra parameter. The - fields next_in, avail_in, zalloc, zfree and opaque must be initialized - before by the caller. - - The windowBits parameter is the base two logarithm of the maximum window - size (the size of the history buffer). It should be in the range 8..15 for - this version of the library. The default value is 15 if inflateInit is used - instead. windowBits must be greater than or equal to the windowBits value - provided to deflateInit2() while compressing, or it must be equal to 15 if - deflateInit2() was not used. If a compressed stream with a larger window - size is given as input, inflate() will return with the error code - Z_DATA_ERROR instead of trying to allocate a larger window. - - windowBits can also be zero to request that inflate use the window size in - the zlib header of the compressed stream. - - windowBits can also be -8..-15 for raw inflate. In this case, -windowBits - determines the window size. inflate() will then process raw deflate data, - not looking for a zlib or gzip header, not generating a check value, and not - looking for any check values for comparison at the end of the stream. This - is for use with other formats that use the deflate compressed data format - such as zip. Those formats provide their own check values. If a custom - format is developed using the raw deflate format for compressed data, it is - recommended that a check value such as an adler32 or a crc32 be applied to - the uncompressed data as is done in the zlib, gzip, and zip formats. For - most applications, the zlib format should be used as is. Note that comments - above on the use in deflateInit2() applies to the magnitude of windowBits. - - windowBits can also be greater than 15 for optional gzip decoding. Add - 32 to windowBits to enable zlib and gzip decoding with automatic header - detection, or add 16 to decode only the gzip format (the zlib format will - return a Z_DATA_ERROR). If a gzip stream is being decoded, strm->adler is a - crc32 instead of an adler32. - - inflateInit2 returns Z_OK if success, Z_MEM_ERROR if there was not enough - memory, Z_VERSION_ERROR if the zlib library version is incompatible with the - version assumed by the caller, or Z_STREAM_ERROR if the parameters are - invalid, such as a null pointer to the structure. msg is set to null if - there is no error message. inflateInit2 does not perform any decompression - apart from possibly reading the zlib header if present: actual decompression - will be done by inflate(). (So next_in and avail_in may be modified, but - next_out and avail_out are unused and unchanged.) The current implementation - of inflateInit2() does not process any header information -- that is - deferred until inflate() is called. -*/ - -ZEXTERN int ZEXPORT inflateSetDictionary OF((z_streamp strm, - const Bytef *dictionary, - uInt dictLength)); -/* - Initializes the decompression dictionary from the given uncompressed byte - sequence. This function must be called immediately after a call of inflate, - if that call returned Z_NEED_DICT. The dictionary chosen by the compressor - can be determined from the adler32 value returned by that call of inflate. - The compressor and decompressor must use exactly the same dictionary (see - deflateSetDictionary). For raw inflate, this function can be called - immediately after inflateInit2() or inflateReset() and before any call of - inflate() to set the dictionary. The application must insure that the - dictionary that was used for compression is provided. - - inflateSetDictionary returns Z_OK if success, Z_STREAM_ERROR if a - parameter is invalid (e.g. dictionary being Z_NULL) or the stream state is - inconsistent, Z_DATA_ERROR if the given dictionary doesn't match the - expected one (incorrect adler32 value). inflateSetDictionary does not - perform any decompression: this will be done by subsequent calls of - inflate(). -*/ - -ZEXTERN int ZEXPORT inflateSync OF((z_streamp strm)); -/* - Skips invalid compressed data until a full flush point (see above the - description of deflate with Z_FULL_FLUSH) can be found, or until all - available input is skipped. No output is provided. - - inflateSync returns Z_OK if a full flush point has been found, Z_BUF_ERROR - if no more input was provided, Z_DATA_ERROR if no flush point has been - found, or Z_STREAM_ERROR if the stream structure was inconsistent. In the - success case, the application may save the current current value of total_in - which indicates where valid compressed data was found. In the error case, - the application may repeatedly call inflateSync, providing more input each - time, until success or end of the input data. -*/ - -ZEXTERN int ZEXPORT inflateCopy OF((z_streamp dest, - z_streamp source)); -/* - Sets the destination stream as a complete copy of the source stream. - - This function can be useful when randomly accessing a large stream. The - first pass through the stream can periodically record the inflate state, - allowing restarting inflate at those points when randomly accessing the - stream. - - inflateCopy returns Z_OK if success, Z_MEM_ERROR if there was not - enough memory, Z_STREAM_ERROR if the source stream state was inconsistent - (such as zalloc being Z_NULL). msg is left unchanged in both source and - destination. -*/ - -ZEXTERN int ZEXPORT inflateReset OF((z_streamp strm)); -/* - This function is equivalent to inflateEnd followed by inflateInit, - but does not free and reallocate all the internal decompression state. The - stream will keep attributes that may have been set by inflateInit2. - - inflateReset returns Z_OK if success, or Z_STREAM_ERROR if the source - stream state was inconsistent (such as zalloc or state being Z_NULL). -*/ - -ZEXTERN int ZEXPORT inflateReset2 OF((z_streamp strm, - int windowBits)); -/* - This function is the same as inflateReset, but it also permits changing - the wrap and window size requests. The windowBits parameter is interpreted - the same as it is for inflateInit2. - - inflateReset2 returns Z_OK if success, or Z_STREAM_ERROR if the source - stream state was inconsistent (such as zalloc or state being Z_NULL), or if - the windowBits parameter is invalid. -*/ - -ZEXTERN int ZEXPORT inflatePrime OF((z_streamp strm, - int bits, - int value)); -/* - This function inserts bits in the inflate input stream. The intent is - that this function is used to start inflating at a bit position in the - middle of a byte. The provided bits will be used before any bytes are used - from next_in. This function should only be used with raw inflate, and - should be used before the first inflate() call after inflateInit2() or - inflateReset(). bits must be less than or equal to 16, and that many of the - least significant bits of value will be inserted in the input. - - If bits is negative, then the input stream bit buffer is emptied. Then - inflatePrime() can be called again to put bits in the buffer. This is used - to clear out bits leftover after feeding inflate a block description prior - to feeding inflate codes. - - inflatePrime returns Z_OK if success, or Z_STREAM_ERROR if the source - stream state was inconsistent. -*/ - -ZEXTERN long ZEXPORT inflateMark OF((z_streamp strm)); -/* - This function returns two values, one in the lower 16 bits of the return - value, and the other in the remaining upper bits, obtained by shifting the - return value down 16 bits. If the upper value is -1 and the lower value is - zero, then inflate() is currently decoding information outside of a block. - If the upper value is -1 and the lower value is non-zero, then inflate is in - the middle of a stored block, with the lower value equaling the number of - bytes from the input remaining to copy. If the upper value is not -1, then - it is the number of bits back from the current bit position in the input of - the code (literal or length/distance pair) currently being processed. In - that case the lower value is the number of bytes already emitted for that - code. - - A code is being processed if inflate is waiting for more input to complete - decoding of the code, or if it has completed decoding but is waiting for - more output space to write the literal or match data. - - inflateMark() is used to mark locations in the input data for random - access, which may be at bit positions, and to note those cases where the - output of a code may span boundaries of random access blocks. The current - location in the input stream can be determined from avail_in and data_type - as noted in the description for the Z_BLOCK flush parameter for inflate. - - inflateMark returns the value noted above or -1 << 16 if the provided - source stream state was inconsistent. -*/ - -ZEXTERN int ZEXPORT inflateGetHeader OF((z_streamp strm, - gz_headerp head)); -/* - inflateGetHeader() requests that gzip header information be stored in the - provided gz_header structure. inflateGetHeader() may be called after - inflateInit2() or inflateReset(), and before the first call of inflate(). - As inflate() processes the gzip stream, head->done is zero until the header - is completed, at which time head->done is set to one. If a zlib stream is - being decoded, then head->done is set to -1 to indicate that there will be - no gzip header information forthcoming. Note that Z_BLOCK or Z_TREES can be - used to force inflate() to return immediately after header processing is - complete and before any actual data is decompressed. - - The text, time, xflags, and os fields are filled in with the gzip header - contents. hcrc is set to true if there is a header CRC. (The header CRC - was valid if done is set to one.) If extra is not Z_NULL, then extra_max - contains the maximum number of bytes to write to extra. Once done is true, - extra_len contains the actual extra field length, and extra contains the - extra field, or that field truncated if extra_max is less than extra_len. - If name is not Z_NULL, then up to name_max characters are written there, - terminated with a zero unless the length is greater than name_max. If - comment is not Z_NULL, then up to comm_max characters are written there, - terminated with a zero unless the length is greater than comm_max. When any - of extra, name, or comment are not Z_NULL and the respective field is not - present in the header, then that field is set to Z_NULL to signal its - absence. This allows the use of deflateSetHeader() with the returned - structure to duplicate the header. However if those fields are set to - allocated memory, then the application will need to save those pointers - elsewhere so that they can be eventually freed. - - If inflateGetHeader is not used, then the header information is simply - discarded. The header is always checked for validity, including the header - CRC if present. inflateReset() will reset the process to discard the header - information. The application would need to call inflateGetHeader() again to - retrieve the header from the next gzip stream. - - inflateGetHeader returns Z_OK if success, or Z_STREAM_ERROR if the source - stream state was inconsistent. -*/ - -/* -ZEXTERN int ZEXPORT inflateBackInit OF((z_streamp strm, int windowBits, - unsigned char FAR *window)); - - Initialize the internal stream state for decompression using inflateBack() - calls. The fields zalloc, zfree and opaque in strm must be initialized - before the call. If zalloc and zfree are Z_NULL, then the default library- - derived memory allocation routines are used. windowBits is the base two - logarithm of the window size, in the range 8..15. window is a caller - supplied buffer of that size. Except for special applications where it is - assured that deflate was used with small window sizes, windowBits must be 15 - and a 32K byte window must be supplied to be able to decompress general - deflate streams. - - See inflateBack() for the usage of these routines. - - inflateBackInit will return Z_OK on success, Z_STREAM_ERROR if any of - the paramaters are invalid, Z_MEM_ERROR if the internal state could not be - allocated, or Z_VERSION_ERROR if the version of the library does not match - the version of the header file. -*/ - -typedef unsigned (*in_func) OF((void FAR *, unsigned char FAR * FAR *)); -typedef int (*out_func) OF((void FAR *, unsigned char FAR *, unsigned)); - -ZEXTERN int ZEXPORT inflateBack OF((z_streamp strm, - in_func in, void FAR *in_desc, - out_func out, void FAR *out_desc)); -/* - inflateBack() does a raw inflate with a single call using a call-back - interface for input and output. This is more efficient than inflate() for - file i/o applications in that it avoids copying between the output and the - sliding window by simply making the window itself the output buffer. This - function trusts the application to not change the output buffer passed by - the output function, at least until inflateBack() returns. - - inflateBackInit() must be called first to allocate the internal state - and to initialize the state with the user-provided window buffer. - inflateBack() may then be used multiple times to inflate a complete, raw - deflate stream with each call. inflateBackEnd() is then called to free the - allocated state. - - A raw deflate stream is one with no zlib or gzip header or trailer. - This routine would normally be used in a utility that reads zip or gzip - files and writes out uncompressed files. The utility would decode the - header and process the trailer on its own, hence this routine expects only - the raw deflate stream to decompress. This is different from the normal - behavior of inflate(), which expects either a zlib or gzip header and - trailer around the deflate stream. - - inflateBack() uses two subroutines supplied by the caller that are then - called by inflateBack() for input and output. inflateBack() calls those - routines until it reads a complete deflate stream and writes out all of the - uncompressed data, or until it encounters an error. The function's - parameters and return types are defined above in the in_func and out_func - typedefs. inflateBack() will call in(in_desc, &buf) which should return the - number of bytes of provided input, and a pointer to that input in buf. If - there is no input available, in() must return zero--buf is ignored in that - case--and inflateBack() will return a buffer error. inflateBack() will call - out(out_desc, buf, len) to write the uncompressed data buf[0..len-1]. out() - should return zero on success, or non-zero on failure. If out() returns - non-zero, inflateBack() will return with an error. Neither in() nor out() - are permitted to change the contents of the window provided to - inflateBackInit(), which is also the buffer that out() uses to write from. - The length written by out() will be at most the window size. Any non-zero - amount of input may be provided by in(). - - For convenience, inflateBack() can be provided input on the first call by - setting strm->next_in and strm->avail_in. If that input is exhausted, then - in() will be called. Therefore strm->next_in must be initialized before - calling inflateBack(). If strm->next_in is Z_NULL, then in() will be called - immediately for input. If strm->next_in is not Z_NULL, then strm->avail_in - must also be initialized, and then if strm->avail_in is not zero, input will - initially be taken from strm->next_in[0 .. strm->avail_in - 1]. - - The in_desc and out_desc parameters of inflateBack() is passed as the - first parameter of in() and out() respectively when they are called. These - descriptors can be optionally used to pass any information that the caller- - supplied in() and out() functions need to do their job. - - On return, inflateBack() will set strm->next_in and strm->avail_in to - pass back any unused input that was provided by the last in() call. The - return values of inflateBack() can be Z_STREAM_END on success, Z_BUF_ERROR - if in() or out() returned an error, Z_DATA_ERROR if there was a format error - in the deflate stream (in which case strm->msg is set to indicate the nature - of the error), or Z_STREAM_ERROR if the stream was not properly initialized. - In the case of Z_BUF_ERROR, an input or output error can be distinguished - using strm->next_in which will be Z_NULL only if in() returned an error. If - strm->next_in is not Z_NULL, then the Z_BUF_ERROR was due to out() returning - non-zero. (in() will always be called before out(), so strm->next_in is - assured to be defined if out() returns non-zero.) Note that inflateBack() - cannot return Z_OK. -*/ - -ZEXTERN int ZEXPORT inflateBackEnd OF((z_streamp strm)); -/* - All memory allocated by inflateBackInit() is freed. - - inflateBackEnd() returns Z_OK on success, or Z_STREAM_ERROR if the stream - state was inconsistent. -*/ - -ZEXTERN uLong ZEXPORT zlibCompileFlags OF((void)); -/* Return flags indicating compile-time options. - - Type sizes, two bits each, 00 = 16 bits, 01 = 32, 10 = 64, 11 = other: - 1.0: size of uInt - 3.2: size of uLong - 5.4: size of voidpf (pointer) - 7.6: size of z_off_t - - Compiler, assembler, and debug options: - 8: DEBUG - 9: ASMV or ASMINF -- use ASM code - 10: ZLIB_WINAPI -- exported functions use the WINAPI calling convention - 11: 0 (reserved) - - One-time table building (smaller code, but not thread-safe if true): - 12: BUILDFIXED -- build static block decoding tables when needed - 13: DYNAMIC_CRC_TABLE -- build CRC calculation tables when needed - 14,15: 0 (reserved) - - Library content (indicates missing functionality): - 16: NO_GZCOMPRESS -- gz* functions cannot compress (to avoid linking - deflate code when not needed) - 17: NO_GZIP -- deflate can't write gzip streams, and inflate can't detect - and decode gzip streams (to avoid linking crc code) - 18-19: 0 (reserved) - - Operation variations (changes in library functionality): - 20: PKZIP_BUG_WORKAROUND -- slightly more permissive inflate - 21: FASTEST -- deflate algorithm with only one, lowest compression level - 22,23: 0 (reserved) - - The sprintf variant used by gzprintf (zero is best): - 24: 0 = vs*, 1 = s* -- 1 means limited to 20 arguments after the format - 25: 0 = *nprintf, 1 = *printf -- 1 means gzprintf() not secure! - 26: 0 = returns value, 1 = void -- 1 means inferred string length returned - - Remainder: - 27-31: 0 (reserved) - */ - - - /* utility functions */ - -/* - The following utility functions are implemented on top of the basic - stream-oriented functions. To simplify the interface, some default options - are assumed (compression level and memory usage, standard memory allocation - functions). The source code of these utility functions can be modified if - you need special options. -*/ - -ZEXTERN int ZEXPORT compress OF((Bytef *dest, uLongf *destLen, - const Bytef *source, uLong sourceLen)); -/* - Compresses the source buffer into the destination buffer. sourceLen is - the byte length of the source buffer. Upon entry, destLen is the total size - of the destination buffer, which must be at least the value returned by - compressBound(sourceLen). Upon exit, destLen is the actual size of the - compressed buffer. - - compress returns Z_OK if success, Z_MEM_ERROR if there was not - enough memory, Z_BUF_ERROR if there was not enough room in the output - buffer. -*/ - -ZEXTERN int ZEXPORT compress2 OF((Bytef *dest, uLongf *destLen, - const Bytef *source, uLong sourceLen, - int level)); -/* - Compresses the source buffer into the destination buffer. The level - parameter has the same meaning as in deflateInit. sourceLen is the byte - length of the source buffer. Upon entry, destLen is the total size of the - destination buffer, which must be at least the value returned by - compressBound(sourceLen). Upon exit, destLen is the actual size of the - compressed buffer. - - compress2 returns Z_OK if success, Z_MEM_ERROR if there was not enough - memory, Z_BUF_ERROR if there was not enough room in the output buffer, - Z_STREAM_ERROR if the level parameter is invalid. -*/ - -ZEXTERN uLong ZEXPORT compressBound OF((uLong sourceLen)); -/* - compressBound() returns an upper bound on the compressed size after - compress() or compress2() on sourceLen bytes. It would be used before a - compress() or compress2() call to allocate the destination buffer. -*/ - -ZEXTERN int ZEXPORT uncompress OF((Bytef *dest, uLongf *destLen, - const Bytef *source, uLong sourceLen)); -/* - Decompresses the source buffer into the destination buffer. sourceLen is - the byte length of the source buffer. Upon entry, destLen is the total size - of the destination buffer, which must be large enough to hold the entire - uncompressed data. (The size of the uncompressed data must have been saved - previously by the compressor and transmitted to the decompressor by some - mechanism outside the scope of this compression library.) Upon exit, destLen - is the actual size of the uncompressed buffer. - - uncompress returns Z_OK if success, Z_MEM_ERROR if there was not - enough memory, Z_BUF_ERROR if there was not enough room in the output - buffer, or Z_DATA_ERROR if the input data was corrupted or incomplete. -*/ - - - /* gzip file access functions */ - -/* - This library supports reading and writing files in gzip (.gz) format with - an interface similar to that of stdio, using the functions that start with - "gz". The gzip format is different from the zlib format. gzip is a gzip - wrapper, documented in RFC 1952, wrapped around a deflate stream. -*/ - -typedef voidp gzFile; /* opaque gzip file descriptor */ - -/* -ZEXTERN gzFile ZEXPORT gzopen OF((const char *path, const char *mode)); - - Opens a gzip (.gz) file for reading or writing. The mode parameter is as - in fopen ("rb" or "wb") but can also include a compression level ("wb9") or - a strategy: 'f' for filtered data as in "wb6f", 'h' for Huffman-only - compression as in "wb1h", 'R' for run-length encoding as in "wb1R", or 'F' - for fixed code compression as in "wb9F". (See the description of - deflateInit2 for more information about the strategy parameter.) Also "a" - can be used instead of "w" to request that the gzip stream that will be - written be appended to the file. "+" will result in an error, since reading - and writing to the same gzip file is not supported. - - gzopen can be used to read a file which is not in gzip format; in this - case gzread will directly read from the file without decompression. - - gzopen returns NULL if the file could not be opened, if there was - insufficient memory to allocate the gzFile state, or if an invalid mode was - specified (an 'r', 'w', or 'a' was not provided, or '+' was provided). - errno can be checked to determine if the reason gzopen failed was that the - file could not be opened. -*/ - -ZEXTERN gzFile ZEXPORT gzdopen OF((int fd, const char *mode)); -/* - gzdopen associates a gzFile with the file descriptor fd. File descriptors - are obtained from calls like open, dup, creat, pipe or fileno (if the file - has been previously opened with fopen). The mode parameter is as in gzopen. - - The next call of gzclose on the returned gzFile will also close the file - descriptor fd, just like fclose(fdopen(fd, mode)) closes the file descriptor - fd. If you want to keep fd open, use fd = dup(fd_keep); gz = gzdopen(fd, - mode);. The duplicated descriptor should be saved to avoid a leak, since - gzdopen does not close fd if it fails. - - gzdopen returns NULL if there was insufficient memory to allocate the - gzFile state, if an invalid mode was specified (an 'r', 'w', or 'a' was not - provided, or '+' was provided), or if fd is -1. The file descriptor is not - used until the next gz* read, write, seek, or close operation, so gzdopen - will not detect if fd is invalid (unless fd is -1). -*/ - -ZEXTERN int ZEXPORT gzbuffer OF((gzFile file, unsigned size)); -/* - Set the internal buffer size used by this library's functions. The - default buffer size is 8192 bytes. This function must be called after - gzopen() or gzdopen(), and before any other calls that read or write the - file. The buffer memory allocation is always deferred to the first read or - write. Two buffers are allocated, either both of the specified size when - writing, or one of the specified size and the other twice that size when - reading. A larger buffer size of, for example, 64K or 128K bytes will - noticeably increase the speed of decompression (reading). - - The new buffer size also affects the maximum length for gzprintf(). - - gzbuffer() returns 0 on success, or -1 on failure, such as being called - too late. -*/ - -ZEXTERN int ZEXPORT gzsetparams OF((gzFile file, int level, int strategy)); -/* - Dynamically update the compression level or strategy. See the description - of deflateInit2 for the meaning of these parameters. - - gzsetparams returns Z_OK if success, or Z_STREAM_ERROR if the file was not - opened for writing. -*/ - -ZEXTERN int ZEXPORT gzread OF((gzFile file, voidp buf, unsigned len)); -/* - Reads the given number of uncompressed bytes from the compressed file. If - the input file was not in gzip format, gzread copies the given number of - bytes into the buffer. - - After reaching the end of a gzip stream in the input, gzread will continue - to read, looking for another gzip stream, or failing that, reading the rest - of the input file directly without decompression. The entire input file - will be read if gzread is called until it returns less than the requested - len. - - gzread returns the number of uncompressed bytes actually read, less than - len for end of file, or -1 for error. -*/ - -ZEXTERN int ZEXPORT gzwrite OF((gzFile file, - voidpc buf, unsigned len)); -/* - Writes the given number of uncompressed bytes into the compressed file. - gzwrite returns the number of uncompressed bytes written or 0 in case of - error. -*/ - -ZEXTERN int ZEXPORTVA gzprintf OF((gzFile file, const char *format, ...)); -/* - Converts, formats, and writes the arguments to the compressed file under - control of the format string, as in fprintf. gzprintf returns the number of - uncompressed bytes actually written, or 0 in case of error. The number of - uncompressed bytes written is limited to 8191, or one less than the buffer - size given to gzbuffer(). The caller should assure that this limit is not - exceeded. If it is exceeded, then gzprintf() will return an error (0) with - nothing written. In this case, there may also be a buffer overflow with - unpredictable consequences, which is possible only if zlib was compiled with - the insecure functions sprintf() or vsprintf() because the secure snprintf() - or vsnprintf() functions were not available. This can be determined using - zlibCompileFlags(). -*/ - -ZEXTERN int ZEXPORT gzputs OF((gzFile file, const char *s)); -/* - Writes the given null-terminated string to the compressed file, excluding - the terminating null character. - - gzputs returns the number of characters written, or -1 in case of error. -*/ - -ZEXTERN char * ZEXPORT gzgets OF((gzFile file, char *buf, int len)); -/* - Reads bytes from the compressed file until len-1 characters are read, or a - newline character is read and transferred to buf, or an end-of-file - condition is encountered. If any characters are read or if len == 1, the - string is terminated with a null character. If no characters are read due - to an end-of-file or len < 1, then the buffer is left untouched. - - gzgets returns buf which is a null-terminated string, or it returns NULL - for end-of-file or in case of error. If there was an error, the contents at - buf are indeterminate. -*/ - -ZEXTERN int ZEXPORT gzputc OF((gzFile file, int c)); -/* - Writes c, converted to an unsigned char, into the compressed file. gzputc - returns the value that was written, or -1 in case of error. -*/ - -ZEXTERN int ZEXPORT gzgetc OF((gzFile file)); -/* - Reads one byte from the compressed file. gzgetc returns this byte or -1 - in case of end of file or error. -*/ - -ZEXTERN int ZEXPORT gzungetc OF((int c, gzFile file)); -/* - Push one character back onto the stream to be read as the first character - on the next read. At least one character of push-back is allowed. - gzungetc() returns the character pushed, or -1 on failure. gzungetc() will - fail if c is -1, and may fail if a character has been pushed but not read - yet. If gzungetc is used immediately after gzopen or gzdopen, at least the - output buffer size of pushed characters is allowed. (See gzbuffer above.) - The pushed character will be discarded if the stream is repositioned with - gzseek() or gzrewind(). -*/ - -ZEXTERN int ZEXPORT gzflush OF((gzFile file, int flush)); -/* - Flushes all pending output into the compressed file. The parameter flush - is as in the deflate() function. The return value is the zlib error number - (see function gzerror below). gzflush is only permitted when writing. - - If the flush parameter is Z_FINISH, the remaining data is written and the - gzip stream is completed in the output. If gzwrite() is called again, a new - gzip stream will be started in the output. gzread() is able to read such - concatented gzip streams. - - gzflush should be called only when strictly necessary because it will - degrade compression if called too often. -*/ - -/* -ZEXTERN z_off_t ZEXPORT gzseek OF((gzFile file, - z_off_t offset, int whence)); - - Sets the starting position for the next gzread or gzwrite on the given - compressed file. The offset represents a number of bytes in the - uncompressed data stream. The whence parameter is defined as in lseek(2); - the value SEEK_END is not supported. - - If the file is opened for reading, this function is emulated but can be - extremely slow. If the file is opened for writing, only forward seeks are - supported; gzseek then compresses a sequence of zeroes up to the new - starting position. - - gzseek returns the resulting offset location as measured in bytes from - the beginning of the uncompressed stream, or -1 in case of error, in - particular if the file is opened for writing and the new starting position - would be before the current position. -*/ - -ZEXTERN int ZEXPORT gzrewind OF((gzFile file)); -/* - Rewinds the given file. This function is supported only for reading. - - gzrewind(file) is equivalent to (int)gzseek(file, 0L, SEEK_SET) -*/ - -/* -ZEXTERN z_off_t ZEXPORT gztell OF((gzFile file)); - - Returns the starting position for the next gzread or gzwrite on the given - compressed file. This position represents a number of bytes in the - uncompressed data stream, and is zero when starting, even if appending or - reading a gzip stream from the middle of a file using gzdopen(). - - gztell(file) is equivalent to gzseek(file, 0L, SEEK_CUR) -*/ - -/* -ZEXTERN z_off_t ZEXPORT gzoffset OF((gzFile file)); - - Returns the current offset in the file being read or written. This offset - includes the count of bytes that precede the gzip stream, for example when - appending or when using gzdopen() for reading. When reading, the offset - does not include as yet unused buffered input. This information can be used - for a progress indicator. On error, gzoffset() returns -1. -*/ - -ZEXTERN int ZEXPORT gzeof OF((gzFile file)); -/* - Returns true (1) if the end-of-file indicator has been set while reading, - false (0) otherwise. Note that the end-of-file indicator is set only if the - read tried to go past the end of the input, but came up short. Therefore, - just like feof(), gzeof() may return false even if there is no more data to - read, in the event that the last read request was for the exact number of - bytes remaining in the input file. This will happen if the input file size - is an exact multiple of the buffer size. - - If gzeof() returns true, then the read functions will return no more data, - unless the end-of-file indicator is reset by gzclearerr() and the input file - has grown since the previous end of file was detected. -*/ - -ZEXTERN int ZEXPORT gzdirect OF((gzFile file)); -/* - Returns true (1) if file is being copied directly while reading, or false - (0) if file is a gzip stream being decompressed. This state can change from - false to true while reading the input file if the end of a gzip stream is - reached, but is followed by data that is not another gzip stream. - - If the input file is empty, gzdirect() will return true, since the input - does not contain a gzip stream. - - If gzdirect() is used immediately after gzopen() or gzdopen() it will - cause buffers to be allocated to allow reading the file to determine if it - is a gzip file. Therefore if gzbuffer() is used, it should be called before - gzdirect(). -*/ - -ZEXTERN int ZEXPORT gzclose OF((gzFile file)); -/* - Flushes all pending output if necessary, closes the compressed file and - deallocates the (de)compression state. Note that once file is closed, you - cannot call gzerror with file, since its structures have been deallocated. - gzclose must not be called more than once on the same file, just as free - must not be called more than once on the same allocation. - - gzclose will return Z_STREAM_ERROR if file is not valid, Z_ERRNO on a - file operation error, or Z_OK on success. -*/ - -ZEXTERN int ZEXPORT gzclose_r OF((gzFile file)); -ZEXTERN int ZEXPORT gzclose_w OF((gzFile file)); -/* - Same as gzclose(), but gzclose_r() is only for use when reading, and - gzclose_w() is only for use when writing or appending. The advantage to - using these instead of gzclose() is that they avoid linking in zlib - compression or decompression code that is not used when only reading or only - writing respectively. If gzclose() is used, then both compression and - decompression code will be included the application when linking to a static - zlib library. -*/ - -ZEXTERN const char * ZEXPORT gzerror OF((gzFile file, int *errnum)); -/* - Returns the error message for the last error which occurred on the given - compressed file. errnum is set to zlib error number. If an error occurred - in the file system and not in the compression library, errnum is set to - Z_ERRNO and the application may consult errno to get the exact error code. - - The application must not modify the returned string. Future calls to - this function may invalidate the previously returned string. If file is - closed, then the string previously returned by gzerror will no longer be - available. - - gzerror() should be used to distinguish errors from end-of-file for those - functions above that do not distinguish those cases in their return values. -*/ - -ZEXTERN void ZEXPORT gzclearerr OF((gzFile file)); -/* - Clears the error and end-of-file flags for file. This is analogous to the - clearerr() function in stdio. This is useful for continuing to read a gzip - file that is being written concurrently. -*/ - - - /* checksum functions */ - -/* - These functions are not related to compression but are exported - anyway because they might be useful in applications using the compression - library. -*/ - -ZEXTERN uLong ZEXPORT adler32 OF((uLong adler, const Bytef *buf, uInt len)); -/* - Update a running Adler-32 checksum with the bytes buf[0..len-1] and - return the updated checksum. If buf is Z_NULL, this function returns the - required initial value for the checksum. - - An Adler-32 checksum is almost as reliable as a CRC32 but can be computed - much faster. - - Usage example: - - uLong adler = adler32(0L, Z_NULL, 0); - - while (read_buffer(buffer, length) != EOF) { - adler = adler32(adler, buffer, length); - } - if (adler != original_adler) error(); -*/ - -/* -ZEXTERN uLong ZEXPORT adler32_combine OF((uLong adler1, uLong adler2, - z_off_t len2)); - - Combine two Adler-32 checksums into one. For two sequences of bytes, seq1 - and seq2 with lengths len1 and len2, Adler-32 checksums were calculated for - each, adler1 and adler2. adler32_combine() returns the Adler-32 checksum of - seq1 and seq2 concatenated, requiring only adler1, adler2, and len2. -*/ - -ZEXTERN uLong ZEXPORT crc32 OF((uLong crc, const Bytef *buf, uInt len)); -/* - Update a running CRC-32 with the bytes buf[0..len-1] and return the - updated CRC-32. If buf is Z_NULL, this function returns the required - initial value for the for the crc. Pre- and post-conditioning (one's - complement) is performed within this function so it shouldn't be done by the - application. - - Usage example: - - uLong crc = crc32(0L, Z_NULL, 0); - - while (read_buffer(buffer, length) != EOF) { - crc = crc32(crc, buffer, length); - } - if (crc != original_crc) error(); -*/ - -/* -ZEXTERN uLong ZEXPORT crc32_combine OF((uLong crc1, uLong crc2, z_off_t len2)); - - Combine two CRC-32 check values into one. For two sequences of bytes, - seq1 and seq2 with lengths len1 and len2, CRC-32 check values were - calculated for each, crc1 and crc2. crc32_combine() returns the CRC-32 - check value of seq1 and seq2 concatenated, requiring only crc1, crc2, and - len2. -*/ - - - /* various hacks, don't look :) */ - -/* deflateInit and inflateInit are macros to allow checking the zlib version - * and the compiler's view of z_stream: - */ -ZEXTERN int ZEXPORT deflateInit_ OF((z_streamp strm, int level, - const char *version, int stream_size)); -ZEXTERN int ZEXPORT inflateInit_ OF((z_streamp strm, - const char *version, int stream_size)); -ZEXTERN int ZEXPORT deflateInit2_ OF((z_streamp strm, int level, int method, - int windowBits, int memLevel, - int strategy, const char *version, - int stream_size)); -ZEXTERN int ZEXPORT inflateInit2_ OF((z_streamp strm, int windowBits, - const char *version, int stream_size)); -ZEXTERN int ZEXPORT inflateBackInit_ OF((z_streamp strm, int windowBits, - unsigned char FAR *window, - const char *version, - int stream_size)); -#define deflateInit(strm, level) \ - deflateInit_((strm), (level), ZLIB_VERSION, sizeof(z_stream)) -#define inflateInit(strm) \ - inflateInit_((strm), ZLIB_VERSION, sizeof(z_stream)) -#define deflateInit2(strm, level, method, windowBits, memLevel, strategy) \ - deflateInit2_((strm),(level),(method),(windowBits),(memLevel),\ - (strategy), ZLIB_VERSION, sizeof(z_stream)) -#define inflateInit2(strm, windowBits) \ - inflateInit2_((strm), (windowBits), ZLIB_VERSION, sizeof(z_stream)) -#define inflateBackInit(strm, windowBits, window) \ - inflateBackInit_((strm), (windowBits), (window), \ - ZLIB_VERSION, sizeof(z_stream)) - -/* provide 64-bit offset functions if _LARGEFILE64_SOURCE defined, and/or - * change the regular functions to 64 bits if _FILE_OFFSET_BITS is 64 (if - * both are true, the application gets the *64 functions, and the regular - * functions are changed to 64 bits) -- in case these are set on systems - * without large file support, _LFS64_LARGEFILE must also be true - */ -#if defined(_LARGEFILE64_SOURCE) && _LFS64_LARGEFILE-0 - ZEXTERN gzFile ZEXPORT gzopen64 OF((const char *, const char *)); - ZEXTERN z_off64_t ZEXPORT gzseek64 OF((gzFile, z_off64_t, int)); - ZEXTERN z_off64_t ZEXPORT gztell64 OF((gzFile)); - ZEXTERN z_off64_t ZEXPORT gzoffset64 OF((gzFile)); - ZEXTERN uLong ZEXPORT adler32_combine64 OF((uLong, uLong, z_off64_t)); - ZEXTERN uLong ZEXPORT crc32_combine64 OF((uLong, uLong, z_off64_t)); -#endif - -#if !defined(ZLIB_INTERNAL) && _FILE_OFFSET_BITS-0 == 64 && _LFS64_LARGEFILE-0 -# define gzopen gzopen64 -# define gzseek gzseek64 -# define gztell gztell64 -# define gzoffset gzoffset64 -# define adler32_combine adler32_combine64 -# define crc32_combine crc32_combine64 -# ifdef _LARGEFILE64_SOURCE - ZEXTERN gzFile ZEXPORT gzopen64 OF((const char *, const char *)); - ZEXTERN z_off_t ZEXPORT gzseek64 OF((gzFile, z_off_t, int)); - ZEXTERN z_off_t ZEXPORT gztell64 OF((gzFile)); - ZEXTERN z_off_t ZEXPORT gzoffset64 OF((gzFile)); - ZEXTERN uLong ZEXPORT adler32_combine64 OF((uLong, uLong, z_off_t)); - ZEXTERN uLong ZEXPORT crc32_combine64 OF((uLong, uLong, z_off_t)); -# endif -#else - ZEXTERN gzFile ZEXPORT gzopen OF((const char *, const char *)); - ZEXTERN z_off_t ZEXPORT gzseek OF((gzFile, z_off_t, int)); - ZEXTERN z_off_t ZEXPORT gztell OF((gzFile)); - ZEXTERN z_off_t ZEXPORT gzoffset OF((gzFile)); - ZEXTERN uLong ZEXPORT adler32_combine OF((uLong, uLong, z_off_t)); - ZEXTERN uLong ZEXPORT crc32_combine OF((uLong, uLong, z_off_t)); -#endif - -/* hack for buggy compilers */ -#if !defined(ZUTIL_H) && !defined(NO_DUMMY_DECL) - struct internal_state {int dummy;}; -#endif - -/* undocumented functions */ -ZEXTERN const char * ZEXPORT zError OF((int)); -ZEXTERN int ZEXPORT inflateSyncPoint OF((z_streamp)); -ZEXTERN const uLongf * ZEXPORT get_crc_table OF((void)); -ZEXTERN int ZEXPORT inflateUndermine OF((z_streamp, int)); - -#ifdef __cplusplus -} -#endif - -#endif /* ZLIB_H */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/zlib/zutil.c b/app/jni/src/libultraship/extern/StormLib/src/zlib/zutil.c deleted file mode 100644 index 898ed34..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/zlib/zutil.c +++ /dev/null @@ -1,318 +0,0 @@ -/* zutil.c -- target dependent utility functions for the compression library - * Copyright (C) 1995-2005, 2010 Jean-loup Gailly. - * For conditions of distribution and use, see copyright notice in zlib.h - */ - -/* @(#) $Id$ */ - -#include "zutil.h" - -#ifndef NO_DUMMY_DECL -struct internal_state {int dummy;}; /* for buggy compilers */ -#endif - -const char * const z_errmsg[10] = { -"need dictionary", /* Z_NEED_DICT 2 */ -"stream end", /* Z_STREAM_END 1 */ -"", /* Z_OK 0 */ -"file error", /* Z_ERRNO (-1) */ -"stream error", /* Z_STREAM_ERROR (-2) */ -"data error", /* Z_DATA_ERROR (-3) */ -"insufficient memory", /* Z_MEM_ERROR (-4) */ -"buffer error", /* Z_BUF_ERROR (-5) */ -"incompatible version",/* Z_VERSION_ERROR (-6) */ -""}; - - -const char * ZEXPORT zlibVersion() -{ - return ZLIB_VERSION; -} - -uLong ZEXPORT zlibCompileFlags() -{ - uLong flags; - - flags = 0; - switch ((int)(sizeof(uInt))) { - case 2: break; - case 4: flags += 1; break; - case 8: flags += 2; break; - default: flags += 3; - } - switch ((int)(sizeof(uLong))) { - case 2: break; - case 4: flags += 1 << 2; break; - case 8: flags += 2 << 2; break; - default: flags += 3 << 2; - } - switch ((int)(sizeof(voidpf))) { - case 2: break; - case 4: flags += 1 << 4; break; - case 8: flags += 2 << 4; break; - default: flags += 3 << 4; - } - switch ((int)(sizeof(z_off_t))) { - case 2: break; - case 4: flags += 1 << 6; break; - case 8: flags += 2 << 6; break; - default: flags += 3 << 6; - } -#ifdef DEBUG - flags += 1 << 8; -#endif -#if defined(ASMV) || defined(ASMINF) - flags += 1 << 9; -#endif -#ifdef ZLIB_WINAPI - flags += 1 << 10; -#endif -#ifdef BUILDFIXED - flags += 1 << 12; -#endif -#ifdef DYNAMIC_CRC_TABLE - flags += 1 << 13; -#endif -#ifdef NO_GZCOMPRESS - flags += 1L << 16; -#endif -#ifdef NO_GZIP - flags += 1L << 17; -#endif -#ifdef PKZIP_BUG_WORKAROUND - flags += 1L << 20; -#endif -#ifdef FASTEST - flags += 1L << 21; -#endif -#ifdef STDC -# ifdef NO_vsnprintf - flags += 1L << 25; -# ifdef HAS_vsprintf_void - flags += 1L << 26; -# endif -# else -# ifdef HAS_vsnprintf_void - flags += 1L << 26; -# endif -# endif -#else - flags += 1L << 24; -# ifdef NO_snprintf - flags += 1L << 25; -# ifdef HAS_sprintf_void - flags += 1L << 26; -# endif -# else -# ifdef HAS_snprintf_void - flags += 1L << 26; -# endif -# endif -#endif - return flags; -} - -#ifdef DEBUG - -# ifndef verbose -# define verbose 0 -# endif -int ZLIB_INTERNAL z_verbose = verbose; - -void ZLIB_INTERNAL z_error (m) - char *m; -{ - fprintf(stderr, "%s\n", m); - exit(1); -} -#endif - -/* exported to allow conversion of error code to string for compress() and - * uncompress() - */ -const char * ZEXPORT zError(err) - int err; -{ - return ERR_MSG(err); -} - -#if defined(_WIN32_WCE) - /* The Microsoft C Run-Time Library for Windows CE doesn't have - * errno. We define it as a global variable to simplify porting. - * Its value is always 0 and should not be used. - */ - int errno = 0; -#endif - -#ifndef HAVE_MEMCPY - -void ZLIB_INTERNAL zmemcpy(dest, source, len) - Bytef* dest; - const Bytef* source; - uInt len; -{ - if (len == 0) return; - do { - *dest++ = *source++; /* ??? to be unrolled */ - } while (--len != 0); -} - -int ZLIB_INTERNAL zmemcmp(s1, s2, len) - const Bytef* s1; - const Bytef* s2; - uInt len; -{ - uInt j; - - for (j = 0; j < len; j++) { - if (s1[j] != s2[j]) return 2*(s1[j] > s2[j])-1; - } - return 0; -} - -void ZLIB_INTERNAL zmemzero(dest, len) - Bytef* dest; - uInt len; -{ - if (len == 0) return; - do { - *dest++ = 0; /* ??? to be unrolled */ - } while (--len != 0); -} -#endif - - -#ifdef SYS16BIT - -#ifdef __TURBOC__ -/* Turbo C in 16-bit mode */ - -# define MY_ZCALLOC - -/* Turbo C malloc() does not allow dynamic allocation of 64K bytes - * and farmalloc(64K) returns a pointer with an offset of 8, so we - * must fix the pointer. Warning: the pointer must be put back to its - * original form in order to free it, use zcfree(). - */ - -#define MAX_PTR 10 -/* 10*64K = 640K */ - -local int next_ptr = 0; - -typedef struct ptr_table_s { - voidpf org_ptr; - voidpf new_ptr; -} ptr_table; - -local ptr_table table[MAX_PTR]; -/* This table is used to remember the original form of pointers - * to large buffers (64K). Such pointers are normalized with a zero offset. - * Since MSDOS is not a preemptive multitasking OS, this table is not - * protected from concurrent access. This hack doesn't work anyway on - * a protected system like OS/2. Use Microsoft C instead. - */ - -voidpf ZLIB_INTERNAL zcalloc (voidpf opaque, unsigned items, unsigned size) -{ - voidpf buf = opaque; /* just to make some compilers happy */ - ulg bsize = (ulg)items*size; - - /* If we allocate less than 65520 bytes, we assume that farmalloc - * will return a usable pointer which doesn't have to be normalized. - */ - if (bsize < 65520L) { - buf = farmalloc(bsize); - if (*(ush*)&buf != 0) return buf; - } else { - buf = farmalloc(bsize + 16L); - } - if (buf == NULL || next_ptr >= MAX_PTR) return NULL; - table[next_ptr].org_ptr = buf; - - /* Normalize the pointer to seg:0 */ - *((ush*)&buf+1) += ((ush)((uch*)buf-0) + 15) >> 4; - *(ush*)&buf = 0; - table[next_ptr++].new_ptr = buf; - return buf; -} - -void ZLIB_INTERNAL zcfree (voidpf opaque, voidpf ptr) -{ - int n; - if (*(ush*)&ptr != 0) { /* object < 64K */ - farfree(ptr); - return; - } - /* Find the original pointer */ - for (n = 0; n < next_ptr; n++) { - if (ptr != table[n].new_ptr) continue; - - farfree(table[n].org_ptr); - while (++n < next_ptr) { - table[n-1] = table[n]; - } - next_ptr--; - return; - } - ptr = opaque; /* just to make some compilers happy */ - Assert(0, "zcfree: ptr not found"); -} - -#endif /* __TURBOC__ */ - - -#ifdef M_I86 -/* Microsoft C in 16-bit mode */ - -# define MY_ZCALLOC - -#if (!defined(_MSC_VER) || (_MSC_VER <= 600)) -# define _halloc halloc -# define _hfree hfree -#endif - -voidpf ZLIB_INTERNAL zcalloc (voidpf opaque, uInt items, uInt size) -{ - if (opaque) opaque = 0; /* to make compiler happy */ - return _halloc((long)items, size); -} - -void ZLIB_INTERNAL zcfree (voidpf opaque, voidpf ptr) -{ - if (opaque) opaque = 0; /* to make compiler happy */ - _hfree(ptr); -} - -#endif /* M_I86 */ - -#endif /* SYS16BIT */ - - -#ifndef MY_ZCALLOC /* Any system without a special alloc function */ - -#ifndef STDC -extern voidp malloc OF((uInt size)); -extern voidp calloc OF((uInt items, uInt size)); -extern void free OF((voidpf ptr)); -#endif - -voidpf ZLIB_INTERNAL zcalloc (opaque, items, size) - voidpf opaque; - unsigned items; - unsigned size; -{ - if (opaque) items += size - size; /* make compiler happy */ - return sizeof(uInt) > 2 ? (voidpf)malloc(items * size) : - (voidpf)calloc(items, size); -} - -void ZLIB_INTERNAL zcfree (opaque, ptr) - voidpf opaque; - voidpf ptr; -{ - free(ptr); - if (opaque) return; /* make compiler happy */ -} - -#endif /* MY_ZCALLOC */ diff --git a/app/jni/src/libultraship/extern/StormLib/src/zlib/zutil.h b/app/jni/src/libultraship/extern/StormLib/src/zlib/zutil.h deleted file mode 100644 index 258fa88..0000000 --- a/app/jni/src/libultraship/extern/StormLib/src/zlib/zutil.h +++ /dev/null @@ -1,274 +0,0 @@ -/* zutil.h -- internal interface and configuration of the compression library - * Copyright (C) 1995-2010 Jean-loup Gailly. - * For conditions of distribution and use, see copyright notice in zlib.h - */ - -/* WARNING: this file should *not* be used by applications. It is - part of the implementation of the compression library and is - subject to change. Applications should only use zlib.h. - */ - -/* @(#) $Id$ */ - -#ifndef ZUTIL_H -#define ZUTIL_H - -#if ((__GNUC__-0) * 10 + __GNUC_MINOR__-0 >= 33) && !defined(NO_VIZ) -# define ZLIB_INTERNAL __attribute__((visibility ("hidden"))) -#else -# define ZLIB_INTERNAL -#endif - -#include "zlib.h" - -#ifdef STDC -# if !(defined(_WIN32_WCE) && defined(_MSC_VER)) -# include -# endif -# include -# include -#endif - -#ifndef local -# define local static -#endif -/* compile with -Dlocal if your debugger can't find static symbols */ - -typedef unsigned char uch; -typedef uch FAR uchf; -typedef unsigned short ush; -typedef ush FAR ushf; -typedef unsigned long ulg; - -extern const char * const z_errmsg[10]; /* indexed by 2-zlib_error */ -/* (size given to avoid silly warnings with Visual C++) */ - -#define ERR_MSG(err) z_errmsg[Z_NEED_DICT-(err)] - -#define ERR_RETURN(strm,err) \ - return (strm->msg = (char*)ERR_MSG(err), (err)) -/* To be used only when the state is known to be valid */ - - /* common constants */ - -#ifndef DEF_WBITS -# define DEF_WBITS MAX_WBITS -#endif -/* default windowBits for decompression. MAX_WBITS is for compression only */ - -#if MAX_MEM_LEVEL >= 8 -# define DEF_MEM_LEVEL 8 -#else -# define DEF_MEM_LEVEL MAX_MEM_LEVEL -#endif -/* default memLevel */ - -#define STORED_BLOCK 0 -#define STATIC_TREES 1 -#define DYN_TREES 2 -/* The three kinds of block type */ - -#define MIN_MATCH 3 -#define MAX_MATCH 258 -/* The minimum and maximum match lengths */ - -#define PRESET_DICT 0x20 /* preset dictionary flag in zlib header */ - - /* target dependencies */ - -#if defined(MSDOS) || (defined(WINDOWS) && !defined(WIN32)) -# define OS_CODE 0x00 -# if defined(__TURBOC__) || defined(__BORLANDC__) -# if (__STDC__ == 1) && (defined(__LARGE__) || defined(__COMPACT__)) - /* Allow compilation with ANSI keywords only enabled */ - void _Cdecl farfree( void *block ); - void *_Cdecl farmalloc( unsigned long nbytes ); -# else -# include -# endif -# else /* MSC or DJGPP */ -# include -# endif -#endif - -#ifdef AMIGA -# define OS_CODE 0x01 -#endif - -#if defined(VAXC) || defined(VMS) -# define OS_CODE 0x02 -# define F_OPEN(name, mode) \ - fopen((name), (mode), "mbc=60", "ctx=stm", "rfm=fix", "mrs=512") -#endif - -#if defined(ATARI) || defined(atarist) -# define OS_CODE 0x05 -#endif - -#ifdef OS2 -# define OS_CODE 0x06 -# ifdef M_I86 -# include -# endif -#endif - -#if defined(MACOS) || defined(TARGET_OS_MAC) -# define OS_CODE 0x07 -# if defined(__MWERKS__) && __dest_os != __be_os && __dest_os != __win32_os -# include /* for fdopen */ -# else -# ifndef fdopen -# define fdopen(fd,mode) NULL /* No fdopen() */ -# endif -# endif -#endif - -#ifdef TOPS20 -# define OS_CODE 0x0a -#endif - -#ifdef WIN32 -# ifndef __CYGWIN__ /* Cygwin is Unix, not Win32 */ -# define OS_CODE 0x0b -# endif -#endif - -#ifdef __50SERIES /* Prime/PRIMOS */ -# define OS_CODE 0x0f -#endif - -#if defined(_BEOS_) || defined(RISCOS) -# define fdopen(fd,mode) NULL /* No fdopen() */ -#endif - -#if (defined(_MSC_VER) && (_MSC_VER > 600)) && !defined __INTERIX -# if defined(_WIN32_WCE) -# define fdopen(fd,mode) NULL /* No fdopen() */ -# ifndef _PTRDIFF_T_DEFINED - typedef int ptrdiff_t; -# define _PTRDIFF_T_DEFINED -# endif -# else -# define fdopen(fd,type) _fdopen(fd,type) -# endif -#endif - -#if defined(__BORLANDC__) - #pragma warn -8004 - #pragma warn -8008 - #pragma warn -8066 -#endif - -/* provide prototypes for these when building zlib without LFS */ -#if !defined(_LARGEFILE64_SOURCE) || _LFS64_LARGEFILE-0 == 0 - ZEXTERN uLong ZEXPORT adler32_combine64 OF((uLong, uLong, z_off_t)); - ZEXTERN uLong ZEXPORT crc32_combine64 OF((uLong, uLong, z_off_t)); -#endif - - /* common defaults */ - -#ifndef OS_CODE -# define OS_CODE 0x03 /* assume Unix */ -#endif - -#ifndef F_OPEN -# define F_OPEN(name, mode) fopen((name), (mode)) -#endif - - /* functions */ - -#if defined(STDC99) || (defined(__TURBOC__) && __TURBOC__ >= 0x550) -# ifndef HAVE_VSNPRINTF -# define HAVE_VSNPRINTF -# endif -#endif -#if defined(__CYGWIN__) -# ifndef HAVE_VSNPRINTF -# define HAVE_VSNPRINTF -# endif -#endif -#ifndef HAVE_VSNPRINTF -# ifdef MSDOS - /* vsnprintf may exist on some MS-DOS compilers (DJGPP?), - but for now we just assume it doesn't. */ -# define NO_vsnprintf -# endif -# ifdef __TURBOC__ -# define NO_vsnprintf -# endif -# ifdef WIN32 - /* In Win32, vsnprintf is available as the "non-ANSI" _vsnprintf. */ -# if !defined(vsnprintf) && !defined(NO_vsnprintf) -# if !defined(_MSC_VER) || ( defined(_MSC_VER) && _MSC_VER < 1500 ) -# define vsnprintf _vsnprintf -# endif -# endif -# endif -# ifdef __SASC -# define NO_vsnprintf -# endif -#endif -#ifdef VMS -# define NO_vsnprintf -#endif - -#if defined(pyr) -# define NO_MEMCPY -#endif -#if defined(SMALL_MEDIUM) && !defined(_MSC_VER) && !defined(__SC__) - /* Use our own functions for small and medium model with MSC <= 5.0. - * You may have to use the same strategy for Borland C (untested). - * The __SC__ check is for Symantec. - */ -# define NO_MEMCPY -#endif -#if defined(STDC) && !defined(HAVE_MEMCPY) && !defined(NO_MEMCPY) -# define HAVE_MEMCPY -#endif -#ifdef HAVE_MEMCPY -# ifdef SMALL_MEDIUM /* MSDOS small or medium model */ -# define zmemcpy _fmemcpy -# define zmemcmp _fmemcmp -# define zmemzero(dest, len) _fmemset(dest, 0, len) -# else -# define zmemcpy memcpy -# define zmemcmp memcmp -# define zmemzero(dest, len) memset(dest, 0, len) -# endif -#else - void ZLIB_INTERNAL zmemcpy OF((Bytef* dest, const Bytef* source, uInt len)); - int ZLIB_INTERNAL zmemcmp OF((const Bytef* s1, const Bytef* s2, uInt len)); - void ZLIB_INTERNAL zmemzero OF((Bytef* dest, uInt len)); -#endif - -/* Diagnostic functions */ -#ifdef DEBUG -# include - extern int ZLIB_INTERNAL z_verbose; - extern void ZLIB_INTERNAL z_error OF((char *m)); -# define Assert(cond,msg) {if(!(cond)) z_error(msg);} -# define Trace(x) {if (z_verbose>=0) fprintf x ;} -# define Tracev(x) {if (z_verbose>0) fprintf x ;} -# define Tracevv(x) {if (z_verbose>1) fprintf x ;} -# define Tracec(c,x) {if (z_verbose>0 && (c)) fprintf x ;} -# define Tracecv(c,x) {if (z_verbose>1 && (c)) fprintf x ;} -#else -# define Assert(cond,msg) -# define Trace(x) -# define Tracev(x) -# define Tracevv(x) -# define Tracec(c,x) -# define Tracecv(c,x) -#endif - - -voidpf ZLIB_INTERNAL zcalloc OF((voidpf opaque, unsigned items, - unsigned size)); -void ZLIB_INTERNAL zcfree OF((voidpf opaque, voidpf ptr)); - -#define ZALLOC(strm, items, size) \ - (*((strm)->zalloc))((strm)->opaque, (items), (size)) -#define ZFREE(strm, addr) (*((strm)->zfree))((strm)->opaque, (voidpf)(addr)) -#define TRY_FREE(s, p) {if (p) ZFREE(s, p);} - -#endif /* ZUTIL_H */ diff --git a/app/jni/src/libultraship/extern/StormLib/storm_dll/storm.cpp b/app/jni/src/libultraship/extern/StormLib/storm_dll/storm.cpp deleted file mode 100644 index 814f7c8..0000000 --- a/app/jni/src/libultraship/extern/StormLib/storm_dll/storm.cpp +++ /dev/null @@ -1,117 +0,0 @@ -/*****************************************************************************/ -/* Storm.cpp Copyright (c) Ladislav Zezula 2003 */ -/*---------------------------------------------------------------------------*/ -/* This is just a dummy module for building import library for Storm.dll */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 11.04.03 1.00 Lad The first version of Storm.cpp */ -/*****************************************************************************/ - -#include - -#define BUILDING_STORM_CPP -#define STORM_ALTERNATE_NAMES -#include "storm.h" - -BOOL WINAPI SFILE(OpenArchive)(LPCSTR lpFileName, DWORD dwPriority, DWORD dwFlags, HANDLE *hMPQ) -{ - SetLastError(ERROR_CALL_NOT_IMPLEMENTED); - return FALSE; -} - -BOOL WINAPI SFILE(CloseArchive)(HANDLE hMPQ) -{ - SetLastError(ERROR_CALL_NOT_IMPLEMENTED); - return FALSE; -} - -BOOL WINAPI SFILE(GetArchiveName)(HANDLE hMPQ, LPCSTR lpBuffer, DWORD dwBufferLength) -{ - SetLastError(ERROR_CALL_NOT_IMPLEMENTED); - return FALSE; -} - -BOOL WINAPI SFILE(OpenFile)(LPCSTR lpFileName, HANDLE *hFile) -{ - SetLastError(ERROR_CALL_NOT_IMPLEMENTED); - return FALSE; -} - -BOOL WINAPI SFILE(OpenFileEx)(HANDLE hMPQ, LPCSTR lpFileName, DWORD dwSearchScope, HANDLE *hFile) -{ - SetLastError(ERROR_CALL_NOT_IMPLEMENTED); - return FALSE; -} - -BOOL WINAPI SFILE(CloseFile)(HANDLE hFile) -{ - SetLastError(ERROR_CALL_NOT_IMPLEMENTED); - return FALSE; -} - -DWORD WINAPI SFILE(GetFileSize)(HANDLE hFile, LPDWORD lpFileSizeHigh) -{ - SetLastError(ERROR_CALL_NOT_IMPLEMENTED); - return FALSE; -} - -BOOL WINAPI SFILE(GetFileArchive)(HANDLE hFile, HANDLE *hMPQ) -{ - SetLastError(ERROR_CALL_NOT_IMPLEMENTED); - return FALSE; -} - -BOOL WINAPI SFILE(GetFileName)(HANDLE hFile, LPCSTR lpBuffer, DWORD dwBufferLength) -{ - SetLastError(ERROR_CALL_NOT_IMPLEMENTED); - return FALSE; -} - -DWORD WINAPI SFILE(SetFilePointer)(HANDLE hFile, long lDistanceToMove, PLONG lplDistanceToMoveHigh, DWORD dwMoveMethod) -{ - SetLastError(ERROR_CALL_NOT_IMPLEMENTED); - return FALSE; -} - -BOOL WINAPI SFILE(ReadFile)(HANDLE hFile,LPVOID lpBuffer,DWORD nNumberOfBytesToRead,LPDWORD lpNumberOfBytesRead,LPOVERLAPPED lpOverlapped) -{ - SetLastError(ERROR_CALL_NOT_IMPLEMENTED); - return FALSE; -} - -LCID WINAPI SFILE(SetLocale)(LCID nNewLocale) -{ - SetLastError(ERROR_CALL_NOT_IMPLEMENTED); - return FALSE; -} - -BOOL WINAPI SFILE(GetBasePath)(LPCSTR lpBuffer, DWORD dwBufferLength) -{ - SetLastError(ERROR_CALL_NOT_IMPLEMENTED); - return FALSE; -} - -BOOL WINAPI SFILE(SetBasePath)(LPCSTR lpNewBasePath) -{ - SetLastError(ERROR_CALL_NOT_IMPLEMENTED); - return FALSE; -} - -BOOL WINAPI SFILE(Destroy)() -{ - SetLastError(ERROR_CALL_NOT_IMPLEMENTED); - return FALSE; -} - -BOOL WINAPI SCOMP(Compress)(char * pbOutBuffer, int * pdwOutLength, char * pbInBuffer, int dwInLength, int uCmp, int uCmpType, int nCmpLevel) -{ - SetLastError(ERROR_CALL_NOT_IMPLEMENTED); - return FALSE; -} - -BOOL WINAPI SCOMP(Decompress)(char * pbOutBuffer, int * pdwOutLength, char * pbInBuffer, int dwInLength) -{ - SetLastError(ERROR_CALL_NOT_IMPLEMENTED); - return FALSE; -} diff --git a/app/jni/src/libultraship/extern/StormLib/storm_dll/storm.def b/app/jni/src/libultraship/extern/StormLib/storm_dll/storm.def deleted file mode 100644 index 8de88f5..0000000 --- a/app/jni/src/libultraship/extern/StormLib/storm_dll/storm.def +++ /dev/null @@ -1,25 +0,0 @@ -; Storm definition file with alternate Storm.dll names -LIBRARY "Storm" - -EXPORTS - StormCloseArchive @252 ; 0x0FC - StormCloseFile @253 ; 0x0FD - StormDestroy @262 ; 0x106 - StormGetFileArchive @264 ; 0x108 - StormGetFileSize @265 ; 0x109 - StormOpenArchive @266 ; 0x10A - StormOpenFile @267 ; 0x10B - StormOpenFileEx @268 ; 0x10C - StormReadFile @269 ; 0x10D - StormSetBasePath @270 ; 0x10E - StormSetFilePointer @271 ; 0x10F - StormSetLocale @272 ; 0x110 - StormGetBasePath @273 ; 0x111 - StormGetArchiveName @275 ; 0x113 - StormGetFileName @276 ; 0x114 - -; StormSetLastError @465 ; 0x - - StormCompress @551 ; 0x227 - StormDecompress @552 ; 0x228 - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/storm_dll/storm.h b/app/jni/src/libultraship/extern/StormLib/storm_dll/storm.h deleted file mode 100644 index 75681b8..0000000 --- a/app/jni/src/libultraship/extern/StormLib/storm_dll/storm.h +++ /dev/null @@ -1,65 +0,0 @@ -/*****************************************************************************/ -/* Storm.h Copyright Justin Olbrantz(Quantam) 2000 */ -/*---------------------------------------------------------------------------*/ -/* Storm Interface Library v1.0 for Windows */ -/* */ -/* Author : Justin Olbrantz(Quantam) */ -/* E-mail : omega@dragonfire.net */ -/* WWW : www.campaigncreations.com/starcraft/mpq2k/inside_mopaq/ */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* xx.xx.00 1.00 Qua The first version of Storm.h */ -/* 11.04.03 1.00 Lad Added some functions */ -/*****************************************************************************/ - -#ifndef __STORM_H__ -#define __STORM_H__ - -// We need the Windows data types for the Storm prototypes -#include - -// Sometimes is necessary to change the function names so they -// will not conflict with other MPQ tools. -#ifdef STORM_ALTERNATE_NAMES - #define SFILE(Name) Storm##Name - #define SCOMP(Name) Storm##Name -#else - #define SFILE(Name) SFile##Name - #define SCOMP(Name) SComp##Name -#endif - -// Make sure the functions are exported as C functions -#ifdef __cplusplus -extern "C" { -#endif - -// Storm file function prototypes -BOOL WINAPI SFILE(OpenArchive)(LPCSTR lpFileName, DWORD dwPriority, DWORD dwFlags, HANDLE *hMPQ); -BOOL WINAPI SFILE(CloseArchive)(HANDLE hMPQ); -BOOL WINAPI SFILE(GetArchiveName)(HANDLE hMPQ, LPCSTR lpBuffer, DWORD dwBufferLength); -BOOL WINAPI SFILE(OpenFile)(LPCSTR lpFileName, HANDLE *hFile); -BOOL WINAPI SFILE(OpenFileEx)(HANDLE hMPQ, LPCSTR lpFileName, DWORD dwSearchScope, HANDLE *hFile); -BOOL WINAPI SFILE(CloseFile)(HANDLE hFile); -DWORD WINAPI SFILE(GetFileSize)(HANDLE hFile, LPDWORD lpFileSizeHigh); -BOOL WINAPI SFILE(GetFileArchive)(HANDLE hFile, HANDLE *hMPQ); -BOOL WINAPI SFILE(GetFileName)(HANDLE hFile, LPCSTR lpBuffer, DWORD dwBufferLength); -DWORD WINAPI SFILE(SetFilePointer)(HANDLE hFile, long lDistanceToMove, PLONG lplDistanceToMoveHigh, DWORD dwMoveMethod); -BOOL WINAPI SFILE(ReadFile)(HANDLE hFile, LPVOID lpBuffer, DWORD nNumberOfBytesToRead, LPDWORD lpNumberOfBytesRead, LPOVERLAPPED lpOverlapped); -LCID WINAPI SFILE(SetLocale)(LCID nNewLocale); -BOOL WINAPI SFILE(GetBasePath)(LPCSTR lpBuffer, DWORD dwBufferLength); -BOOL WINAPI SFILE(SetBasePath)(LPCSTR lpNewBasePath); - -// Storm (de)compression functions -BOOL WINAPI SCOMP(Compress) (char * pbOutBuffer, int * pdwOutLength, char * pbInBuffer, int dwInLength, int uCmp, int uCmpType, int nCmpLevel); -BOOL WINAPI SCOMP(Decompress)(char * pbOutBuffer, int * pdwOutLength, char * pbInBuffer, int dwInLength); - -#ifdef __cplusplus -} -#endif - -#if defined(_MSC_VER) && !defined(BUILDING_STORM_CPP) -#pragma comment(lib, "Storm.lib") // Force linking Storm.lib and thus Storm.dll -#endif - -#endif // __STORM_H__ diff --git a/app/jni/src/libultraship/extern/StormLib/storm_dll/storm.vcxproj b/app/jni/src/libultraship/extern/StormLib/storm_dll/storm.vcxproj deleted file mode 100644 index ac64fd5..0000000 --- a/app/jni/src/libultraship/extern/StormLib/storm_dll/storm.vcxproj +++ /dev/null @@ -1,197 +0,0 @@ - - - - - Debug - Win32 - - - Debug - x64 - - - Release - Win32 - - - Release - x64 - - - - {BD600973-C6FA-4CE3-8821-67F6418B7F9C} - storm - Win32Proj - 10.0 - - - - DynamicLibrary - v142 - Unicode - true - - - DynamicLibrary - v142 - Unicode - - - DynamicLibrary - v142 - Unicode - true - - - DynamicLibrary - v142 - Unicode - - - - - - - - - - - - - - - - - - - <_ProjectFileVersion>16.0.31829.152 - - - .\bin\dll\$(Platform)\$(Configuration)\ - .\bin\dll\$(Platform)\$(Configuration)\ - true - false - - - .\bin\dll\$(Platform)\$(Configuration)\ - .\bin\dll\$(Platform)\$(Configuration)\ - true - false - - - .\bin\dll\$(Platform)\$(Configuration)\ - .\bin\dll\$(Platform)\$(Configuration)\ - false - false - - - .\bin\dll\$(Platform)\$(Configuration)\ - .\bin\dll\$(Platform)\$(Configuration)\ - false - false - - - - Disabled - WIN32;_DEBUG;_WINDOWS;_USRDLL;storm_EXPORTS;%(PreprocessorDefinitions) - EnableFastChecks - MultiThreaded - - Level3 - EditAndContinue - - - $(OutDir)storm.dll - .\storm.def - true - Windows - 0x15000000 - - MachineX86 - false - - - - - X64 - - - Disabled - WIN32;_DEBUG;_WINDOWS;_USRDLL;storm_EXPORTS;%(PreprocessorDefinitions) - EnableFastChecks - MultiThreadedDebugDLL - - Level3 - ProgramDatabase - - - $(OutDir)storm.dll - .\storm.def - true - Windows - - - - MachineX64 - false - - - - - WIN32;NDEBUG;_WINDOWS;_USRDLL;storm_EXPORTS;%(PreprocessorDefinitions) - MultiThreaded - - Level3 - ProgramDatabase - - - $(OutDir)storm.dll - .\storm.def - true - Windows - true - true - 0x15000000 - - MachineX86 - false - - - - - X64 - - - WIN32;NDEBUG;_WINDOWS;_USRDLL;storm_EXPORTS;%(PreprocessorDefinitions) - MultiThreadedDLL - - Level3 - ProgramDatabase - - - $(OutDir)storm.dll - .\storm.def - true - Windows - true - true - - - - MachineX64 - false - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/storm_dll/storm.vcxproj.filters b/app/jni/src/libultraship/extern/StormLib/storm_dll/storm.vcxproj.filters deleted file mode 100644 index c10e805..0000000 --- a/app/jni/src/libultraship/extern/StormLib/storm_dll/storm.vcxproj.filters +++ /dev/null @@ -1,28 +0,0 @@ - - - - - {4FC737F1-C7A5-4376-A066-2A32D752A2FF} - cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx - - - {93995380-89BD-4b04-88EB-625FBE52EBFB} - h;hpp;hxx;hm;inl;inc;xsd - - - - - Source Files - - - - - Source Files - - - - - Header Files - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/storm_dll/storm_test.cpp b/app/jni/src/libultraship/extern/StormLib/storm_dll/storm_test.cpp deleted file mode 100644 index 0ac2c67..0000000 --- a/app/jni/src/libultraship/extern/StormLib/storm_dll/storm_test.cpp +++ /dev/null @@ -1,233 +0,0 @@ -/*****************************************************************************/ -/* Storm_test.cpp Copyright (c) Ladislav Zezula 2014 */ -/*---------------------------------------------------------------------------*/ -/* Test module for storm.dll (original Blizzard MPQ dynalic library */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 24.08.14 1.00 Lad The first version of Storm_test.cpp */ -/*****************************************************************************/ - -#define _CRT_NON_CONFORMING_SWPRINTFS -#define _CRT_SECURE_NO_DEPRECATE -#include -#include - -#ifdef _MSC_VER -#include -#endif - -#define STORM_ALTERNATE_NAMES // Use Storm* prefix for functions -#include "storm.h" // Header file for Storm.dll - -//----------------------------------------------------------------------------- -// List of files - -const char * IntToHexChar = "0123456789ABCDEF"; - -LPCSTR ListFile[] = -{ - "music\\tdefeat.wav", - "setupdat\\inst.vis", - "setupdat\\audio\\mouseover.wav", - "files\\font\\font12.fnt", - "music\\zvict.wav", - "files\\readme.txt", - "music\\zerg2.wav", - "music\\zerg1.wav", - "setupdat\\inst_regs.ins", - "files\\font\\font50.fnt", - "files\\msv2all.vxp", - "setupdat\\scr_options.vis", - "setupdat\\font\\font16x.fnt", - "setupdat\\setup.vis", - "maps\\128x128_wasteland4.scm", - "setupdat\\scr_main.vis", - "music\\pvict.wav", - "music\\zdefeat.wav", - "files\\font\\font16x.fnt", - "setupdat\\nt\\comctl32.dll", - "setupdat\\debug.ins", - "setupdat\\inst.ins", - "music\\pdefeat.wav", - "files\\smackw32.dll", - "music\\tvict.wav", - "setupdat\\optvox.vis", - "setupdat\\gen\\maps.lst", - "files\\font\\font8.fnt", - "files\\mvoice.vxp", - "files\\font\\font14.fnt", - "files\\battle.snp", - "files\\storm.dll", - "maps\\128x128_ash4.scm", - "files\\font\\font32.fnt", - "setupdat\\normal.ins", - "files\\font\\font16.fnt", - "setupdat\\mainplay.vis", - "setupdat\\gendefs.ins", - "setupdat\\audio\\installermusic.wav", - "setupdat\\templates.ins", - "music\\terran1.wav", - "maps\\96x96_ash4.scm", - "setupdat\\defaults.vis", - "music\\prdyroom.wav", - "setupdat\\scr_blizzard.vis", - "setupdat\\scr_isp.vis", - "setupdat\\95\\comctl32.dll", - "files\\font\\font10.fnt", - "files\\local.dll", - "music\\terran3.wav", - "music\\terran2.wav", - "setupdat\\audio\\battlenetclick.wav", - "music\\zrdyroom.wav", - "setupdat\\starunin.exe", - "files\\vct32150.dll", - "maps\\96x96_wasteland4.scm", - "setupdat\\inst_sys.ins", - "music\\zerg3.wav", - "setupdat\\license.txt", - "music\\protoss2.wav", - "files\\starcraft.exe", - "music\\trdyroom.wav", - "maps\\96x96_space4.scm", - "files\\vfonts.vxp", - "setupdat\\installed.ins", - "music\\protoss1.wav", - "files\\stardat.mpq", - "setupdat\\font\\font16.fnt", - "smk\\starintr.smk", - "files\\vadagc.vxp", - "setupdat\\strings.ins", - "music\\title.wav", - "setupdat\\font\\font32.fnt", - "setupdat\\inst_files.ins", - "setupdat\\images\\install.pcx", - "files\\report bugs.url", - "setupdat\\single.ins", - "maps\\128x128_space4.scm", - "setupdat\\audio\\mousedown.wav", - NULL -}; - -//----------------------------------------------------------------------------- -// Main - -static void CalculateMD5(LPBYTE md5_digest, LPBYTE pbData, DWORD cbData) -{ - HCRYPTPROV hCryptProv = NULL; - HCRYPTHASH hCryptHash = NULL; - - if(CryptAcquireContext(&hCryptProv, NULL, NULL, PROV_RSA_FULL, CRYPT_VERIFYCONTEXT)) - { - if(CryptCreateHash(hCryptProv, CALG_MD5, NULL, 0, &hCryptHash)) - { - DWORD dwHashLen = 0x10; - - CryptHashData(hCryptHash, pbData, cbData, 0); - CryptGetHashParam(hCryptHash, HP_HASHVAL, md5_digest, &dwHashLen, 0); - CryptDestroyHash(hCryptHash); - } - - CryptReleaseContext(hCryptProv, 0); - } -} - -template -DWORD BinaryToString(XCHAR * szBuffer, size_t cchBuffer, LPCVOID pvBinary, size_t cbBinary) -{ - LPCBYTE pbBinary = (LPCBYTE)pvBinary; - - // The size of the string must be enough to hold the binary + EOS - if(cchBuffer < ((cbBinary * 2) + 1)) - return ERROR_INSUFFICIENT_BUFFER; - - // Convert the string to the array of MD5 - // Copy the blob data as text - for(size_t i = 0; i < cbBinary; i++) - { - *szBuffer++ = IntToHexChar[pbBinary[0] >> 0x04]; - *szBuffer++ = IntToHexChar[pbBinary[0] & 0x0F]; - pbBinary++; - } - - // Terminate the string - *szBuffer = 0; - return ERROR_SUCCESS; -} - - -int main(int argc, char * argv[]) -{ - LPCSTR szArchiveName; - LPCSTR szFileName; - LPCSTR szFormat; - HANDLE hMpq = NULL; - HANDLE hFile = NULL; - LPBYTE pbBuffer = NULL; - DWORD dwBytesRead = 0; - DWORD dwFileSize = 0; - BOOL bResult; - BYTE md5_digest[0x10]; - char md5_string[0x40]; - - // Check parameters - if(argc != 3) - { - printf("Error: Missing MPQ or file name\n"); - return 3; - } - - // Get both arguments - SetLastError(ERROR_SUCCESS); - szArchiveName = argv[1]; - szFileName = argv[2]; - - // Break for kernel debugger - //__debugbreak(); - - // Put Storm.dll to the current folder before running this - //printf("[*] Opening archive '%s' ...\n", szArchiveName); - if(StormOpenArchive(szArchiveName, 0, 0, &hMpq)) - { - for(size_t i = 0; ListFile[i] != NULL; i++) - { - //printf("[*] Opening file '%s' ...\n", ListFile[i]); - if(StormOpenFileEx(hMpq, ListFile[i], 0, &hFile)) - { - //printf("[*] Retrieving file size ... "); - dwFileSize = StormGetFileSize(hFile, NULL); - szFormat = (dwFileSize == INVALID_FILE_SIZE) ? ("(invalid)\n") : ("(%u bytes)\n"); - //printf(szFormat, dwFileSize); - - // Allocate the buffer for the entire file - //printf("[*] Allocating buffer ...\n"); - if((pbBuffer = new BYTE[dwFileSize]) != NULL) - { - //printf("[*] Moving to begin of the file ...\n"); - StormSetFilePointer(hFile, 0, NULL, FILE_BEGIN); - - //printf("[*] Reading file ... "); - bResult = StormReadFile(hFile, pbBuffer, dwFileSize, &dwBytesRead, NULL); - szFormat = (bResult != FALSE && dwBytesRead == dwFileSize) ? ("(OK)\n") : ("(error %u)\n"); - //printf(szFormat, GetLastError()); - - //printf("[*] Calculating MD5 ... "); - CalculateMD5(md5_digest, pbBuffer, dwFileSize); - BinaryToString(md5_string, _countof(md5_string), md5_digest, sizeof(md5_digest)); - printf("%s *%s\n", md5_string, ListFile[i]); - - delete[] pbBuffer; - } - - //printf("[*] Closing file ...\n"); - StormCloseFile(hFile); - } - } - - //printf("[*] Closing archive ...\n"); - StormCloseArchive(hMpq); - } - - //printf("Done.\n\n"); - return 0; -} diff --git a/app/jni/src/libultraship/extern/StormLib/storm_dll/storm_test.vcxproj b/app/jni/src/libultraship/extern/StormLib/storm_dll/storm_test.vcxproj deleted file mode 100644 index 48058ff..0000000 --- a/app/jni/src/libultraship/extern/StormLib/storm_dll/storm_test.vcxproj +++ /dev/null @@ -1,202 +0,0 @@ - - - - - Debug - Win32 - - - Debug - x64 - - - Release - Win32 - - - Release - x64 - - - - {5B0E680A-EC4E-402E-AE0D-18ADD2DC6EBE} - storm_test - Win32Proj - 10.0 - - - - Application - v142 - MultiByte - - - Application - v142 - MultiByte - - - Application - v142 - MultiByte - - - Application - v142 - MultiByte - - - - - - - - - - - - - - - - - - - - - - - <_ProjectFileVersion>16.0.31829.152 - - - .\bin\$(Platform)\$(Configuration)\ - .\bin\$(Platform)\$(Configuration)\ - true - - - .\bin\$(Platform)\$(Configuration)\ - .\bin\$(Platform)\$(Configuration)\ - true - - - .\bin\$(Platform)\$(Configuration)\ - .\bin\$(Platform)\$(Configuration)\ - false - - - .\bin\$(Platform)\$(Configuration)\ - .\bin\$(Platform)\$(Configuration)\ - false - - - - Disabled - ../aaa/inc;exif;%(AdditionalIncludeDirectories) - WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions) - EnableFastChecks - MultiThreadedDebug - - Level4 - EditAndContinue - - - $(OutDir)storm_test.exe - .\bin\dll\Win32\Release;%(AdditionalLibraryDirectories) - true - $(OutDir)storm_test.pdb - Console - false - - MachineX86 - false - - - - - X64 - - - Disabled - ../aaa/inc;%(AdditionalIncludeDirectories) - WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions) - EnableFastChecks - MultiThreadedDebug - - Level4 - ProgramDatabase - - - $(OutDir)storm_test.exe - .\bin\dll\x64\Release;%(AdditionalLibraryDirectories) - true - $(OutDir)storm_test.pdb - Console - false - - MachineX64 - false - - - - - ../aaa/inc;%(AdditionalIncludeDirectories) - WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions) - MultiThreaded - - Level4 - ProgramDatabase - - - $(OutDir)storm_test.exe - .\bin\dll\Win32\Release;%(AdditionalLibraryDirectories) - true - Console - true - true - false - - MachineX86 - false - - - - - - - - X64 - - - ../aaa/inc;%(AdditionalIncludeDirectories) - WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions) - MultiThreaded - - Level4 - ProgramDatabase - - - $(OutDir)storm_test.exe - .\bin\dll\x64\Release;%(AdditionalLibraryDirectories) - true - Console - true - true - false - - MachineX64 - false - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/storm_dll/storm_test.vcxproj.filters b/app/jni/src/libultraship/extern/StormLib/storm_dll/storm_test.vcxproj.filters deleted file mode 100644 index 3345f52..0000000 --- a/app/jni/src/libultraship/extern/StormLib/storm_dll/storm_test.vcxproj.filters +++ /dev/null @@ -1,22 +0,0 @@ - - - - - {4FC737F1-C7A5-4376-A066-2A32D752A2FF} - cpp;c;cxx;def;odl;idl;hpj;bat;asm;asmx - - - {10b55df7-950e-4099-ab74-ee928278fc62} - - - - - Source Files - - - - - Header Files - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StormLib/storm_dll/storm_vs19.sln b/app/jni/src/libultraship/extern/StormLib/storm_dll/storm_vs19.sln deleted file mode 100644 index b658180..0000000 --- a/app/jni/src/libultraship/extern/StormLib/storm_dll/storm_vs19.sln +++ /dev/null @@ -1,43 +0,0 @@ -Microsoft Visual Studio Solution File, Format Version 12.00 -# Visual Studio Version 16 -VisualStudioVersion = 16.0.31911.196 -MinimumVisualStudioVersion = 10.0.40219.1 -Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "storm", "storm.vcxproj", "{BD600973-C6FA-4CE3-8821-67F6418B7F9C}" -EndProject -Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "storm_test", "storm_test.vcxproj", "{5B0E680A-EC4E-402E-AE0D-18ADD2DC6EBE}" - ProjectSection(ProjectDependencies) = postProject - {BD600973-C6FA-4CE3-8821-67F6418B7F9C} = {BD600973-C6FA-4CE3-8821-67F6418B7F9C} - EndProjectSection -EndProject -Global - GlobalSection(SolutionConfigurationPlatforms) = preSolution - Debug|Win32 = Debug|Win32 - Debug|x64 = Debug|x64 - Release|Win32 = Release|Win32 - Release|x64 = Release|x64 - EndGlobalSection - GlobalSection(ProjectConfigurationPlatforms) = postSolution - {BD600973-C6FA-4CE3-8821-67F6418B7F9C}.Debug|Win32.ActiveCfg = Debug|Win32 - {BD600973-C6FA-4CE3-8821-67F6418B7F9C}.Debug|Win32.Build.0 = Debug|Win32 - {BD600973-C6FA-4CE3-8821-67F6418B7F9C}.Debug|x64.ActiveCfg = Debug|x64 - {BD600973-C6FA-4CE3-8821-67F6418B7F9C}.Debug|x64.Build.0 = Debug|x64 - {BD600973-C6FA-4CE3-8821-67F6418B7F9C}.Release|Win32.ActiveCfg = Release|Win32 - {BD600973-C6FA-4CE3-8821-67F6418B7F9C}.Release|Win32.Build.0 = Release|Win32 - {BD600973-C6FA-4CE3-8821-67F6418B7F9C}.Release|x64.ActiveCfg = Release|x64 - {BD600973-C6FA-4CE3-8821-67F6418B7F9C}.Release|x64.Build.0 = Release|x64 - {5B0E680A-EC4E-402E-AE0D-18ADD2DC6EBE}.Debug|Win32.ActiveCfg = Debug|Win32 - {5B0E680A-EC4E-402E-AE0D-18ADD2DC6EBE}.Debug|Win32.Build.0 = Debug|Win32 - {5B0E680A-EC4E-402E-AE0D-18ADD2DC6EBE}.Debug|x64.ActiveCfg = Debug|x64 - {5B0E680A-EC4E-402E-AE0D-18ADD2DC6EBE}.Debug|x64.Build.0 = Debug|x64 - {5B0E680A-EC4E-402E-AE0D-18ADD2DC6EBE}.Release|Win32.ActiveCfg = Release|Win32 - {5B0E680A-EC4E-402E-AE0D-18ADD2DC6EBE}.Release|Win32.Build.0 = Release|Win32 - {5B0E680A-EC4E-402E-AE0D-18ADD2DC6EBE}.Release|x64.ActiveCfg = Release|x64 - {5B0E680A-EC4E-402E-AE0D-18ADD2DC6EBE}.Release|x64.Build.0 = Release|x64 - EndGlobalSection - GlobalSection(SolutionProperties) = preSolution - HideSolutionNode = FALSE - EndGlobalSection - GlobalSection(ExtensibilityGlobals) = postSolution - SolutionGuid = {ADD59899-BF23-49D6-9CAA-479813B6604A} - EndGlobalSection -EndGlobal diff --git a/app/jni/src/libultraship/extern/StormLib/test/Readme.txt b/app/jni/src/libultraship/extern/StormLib/test/Readme.txt deleted file mode 100644 index 19bdf53..0000000 --- a/app/jni/src/libultraship/extern/StormLib/test/Readme.txt +++ /dev/null @@ -1,90 +0,0 @@ -Testing MPQ set for StormLib test suite -======================================= - -The path to the directory could be anywhere. Path to this directory -is set on a command line. If there is no command line argument passed, -one of the hard-coded paths is used. - -The testing directory must contain the following files: - -Path File Size -------------------------------------------------- ----------- -patches\wow-update-13164.MPQ 480 028 668 // Original patch files from WoW -patches\wow-update-13205.MPQ 8 814 -patches\wow-update-13287.MPQ 333 363 917 -patches\wow-update-13329.MPQ 159 285 434 -patches\wow-update-13596.MPQ 148 022 182 -patches\wow-update-13623.MPQ 11 561 -patches\wow-update-base-13914.MPQ 293 580 556 -patches\wow-update-base-14007.MPQ 262 906 -patches\wow-update-base-14333.MPQ 368 972 365 -patches\wow-update-base-14480.MPQ 75 897 -patches\wow-update-base-14545.MPQ 1 224 415 -patches\wow-update-base-14946.MPQ 749 246 163 -patches\wow-update-base-15005.MPQ 7 121 223 -patches\wow-update-base-15050.MPQ 4 497 -patches\wow-update-enGB-16016.MPQ 17 117 318 -patches\wow-update-enGB-16048.MPQ 78 180 -patches\wow-update-enGB-16057.MPQ 4 072 -patches\wow-update-enGB-16309.MPQ 28 187 877 -patches\wow-update-enGB-16357.MPQ 3 621 -patches\wow-update-enGB-16516.MPQ 42 934 402 -patches\wow-update-enGB-16650.MPQ 426 683 -patches\wow-update-enGB-16844.MPQ 18 366 460 -patches\wow-update-enGB-16965.MPQ 305 202 -patches\wow-update-oldworld-13154.MPQ 54 068 663 -patches\wow-update-oldworld-13286.MPQ 2 328 773 - -AddFile.bin 0 // Just an empty file -AddFile.exe 432 640 // An arbitraty binary file -AddFile.wav 311 340 // An arbitrary WAVE file -ListFile_Blizzard.txt 3 904 784 // Listfile for Blizzard games (pre-WoW) -ListFile_WarOfTheImmortals.txt 3 904 858 // Listfile for War of the Immortals game -MPQ_1997_v1_Diablo1_DIABDAT.MPQ 517 501 282 // Originally DIABDAT.MPQ from Diablo I -MPQ_1997_v1_Diablo1_DIABDAT.sha 206 -MPQ_1997_v1_Diablo1_single_0.sha 201 // Single player savegame from Diablo I -MPQ_1997_v1_Diablo1_single_0.sv 98 980 -MPQ_1999_v1_WeakSignature.exe 1 031 826 // War2Patch_202.exe from Warcraft II Bnet Edition -MPQ_1999_v1_WeakSignature.sha 260 -MPQ_2002_v1_BlockTableCut.MPQ 27 498 436 // Cut file War3Patch.mpq from Warcraft III -MPQ_2002_v1_BlockTableCut.sha 250 -MPQ_2002_v1_ProtectedMap_HashTable_FakeValid.sha 1 067 -MPQ_2002_v1_ProtectedMap_HashTable_FakeValid.w3x 1 089 638 // Protected Warcraft III map -MPQ_2002_v1_ProtectedMap_InvalidMpqFormat.sha 507 -MPQ_2002_v1_ProtectedMap_InvalidMpqFormat.w3x 2 429 195 // Protected Warcraft III map -MPQ_2002_v1_ProtectedMap_InvalidUserData.sha 293 -MPQ_2002_v1_ProtectedMap_InvalidUserData.w3x 596 486 // Protected Warcraft III map -MPQ_2002_v1_StrongSignature.sha 250 -MPQ_2002_v1_StrongSignature.w3m 306 818 // (10)DustwallowKeys.w3m from Warcraft III -MPQ_2009_v2_WoW_patch.MPQ.part 31 396 380 // patch.MPQ.part from trial WoW build 10958 -MPQ_2009_v2_WoW_patch.MPQ.sha 226 -MPQ_2010_v2_HashTableCompressed.MPQ.part 14 546 972 // interface.MPQ.part from WoW build 10958 -MPQ_2010_v2_HashTableCompressed.MPQ.sha 277 -MPQ_2010_v2_HasUserData.s2ma 1 972 177 // (4) - AI - Kulas Ravine (1x).s2ma from Starcraft II Beta -MPQ_2010_v2_HasUserData.sha 261 -MPQ_2010_v3_expansion-locale-frFR.MPQ 2 980 489 // expansion-locale-frFR.MPQ from WoW 12911 -MPQ_2010_v3_expansion-locale-frFR.sha 274 -MPQ_2011_v2_EncryptedMpq.MPQE 41 631 764 // Installer UI 2 esES.MPQE from Starcraft II Installer (build 15404) -MPQ_2011_v2_EncryptedMpq.sha 255 -MPQ_2011_v4_InvalidHetEntryCount.MPQ 206 164 // An invalid MPQ created by a previous Stormlib version -MPQ_2011_v4_InvalidHetEntryCount.sha 312 -MPQ_2012_v2_EmptyMpq.MPQ 44 // Empty MPQ (Cache from WoW 11723) -MPQ_2012_v2_EmptyMpq.sha 212 -MPQ_2012_v4_OldWorld.MPQ 1 854 547 587 // OldWorld.MPQ from WoW 12911 -MPQ_2012_v4_OldWorld.sha 270 -MPQ_2013_v4_EmptyMpq.MPQ 208 // Empty MPQ created by StormLib -MPQ_2013_v4_EmptyMpq.sha 183 -MPQ_2013_v4_expansion1.MPQ 1 426 926 736 // expansion1.MPQ from WoW build 17538 -MPQ_2013_v4_expansion1.sha 221 -MPQ_2013_v4_locale-enGB.MPQ 446 491 866 // locale-enGB.MPQ from WoW build 16965 -MPQ_2013_v4_locale-enGB.sha 273 -MPQ_2013_v4_patch-base-16357.MPQ 249 // patch-base-16357.MPQ from WoW build 17538 -MPQ_2013_v4_patch-base-16357.sha 229 -MPQ_2013_v4_SC2_EmptyMap.SC2Map 25 058 // Custom Starcraft II Map -MPQ_2013_v4_SC2_EmptyMap.sha 243 -MPQ_2013_v4_world.MPQ 2 617 175 835 // world.MPQ from WoW build 12911 -MPQ_2013_v4_world.sha 252 -MPx_2013_v1_LongwuOnline.mpk 2 146 549 // Scp.mpk from Longwu Online -MPx_2013_v1_LongwuOnline.sha 277 -MPx_2013_v1_WarOfTheImmortals.sha 248 -MPx_2013_v1_WarOfTheImmortals.sqp 56 775 675 // Modified Other.sqp from War of the Immortals diff --git a/app/jni/src/libultraship/extern/StormLib/test/StormTest.cpp b/app/jni/src/libultraship/extern/StormLib/test/StormTest.cpp deleted file mode 100644 index e7a2434..0000000 --- a/app/jni/src/libultraship/extern/StormLib/test/StormTest.cpp +++ /dev/null @@ -1,4693 +0,0 @@ -/*****************************************************************************/ -/* StormTest.cpp Copyright (c) Ladislav Zezula 2003 */ -/*---------------------------------------------------------------------------*/ -/* Test module for StormLib */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 25.03.03 1.00 Lad The first version of StormTest.cpp */ -/*****************************************************************************/ - -#define _CRT_NON_CONFORMING_SWPRINTFS -#define _CRT_SECURE_NO_DEPRECATE -#define __INCLUDE_CRYPTOGRAPHY__ -#define __STORMLIB_SELF__ // Don't use StormLib.lib -#include - -#ifdef _MSC_VER -#include -#endif - -#include "../src/StormLib.h" -#include "../src/StormCommon.h" - -#include "TLogHelper.cpp" // Helper class for showing test results - -#ifdef _MSC_VER -#pragma warning(disable: 4505) // 'XXX' : unreferenced local function has been removed -#pragma comment(lib, "winmm.lib") -#endif - -#ifndef STORMLIB_WINDOWS -#include -#endif - -//------------------------------------------------------------------------------ -// Local structures - -#define TFLG_COUNT_HASH 0x01000000 // There is file count in the lower 24-bits, then hash -#define TFLG_FILE_LOCALE 0x02000000 // The process is expected to fail -#define TFLG_WILL_FAIL 0x04000000 // The process is expected to fail -#define TFLG_VALUE_MASK 0x00FFFFFF // Mask for integer value -#define TEST_DATA(hash, num) (num | TFLG_COUNT_HASH), hash - -#define ERROR_UNDETERMINED_RESULT 0xC000FFFF - -typedef DWORD(*FIND_FILE_CALLBACK)(LPCTSTR szFullPath); - -typedef struct _TEST_INFO -{ - LPCTSTR szMpqName1; - LPCTSTR szMpqName2; - DWORD dwFlags; - const void * param1; - const void * param2; -} TEST_INFO, *PTEST_INFO; - -typedef struct _LINE_INFO -{ - LONG nLinePos; - DWORD nLineLen; - const char * szLine; -} LINE_INFO, *PLINE_INFO; - -//------------------------------------------------------------------------------ -// Local variables - -#ifdef STORMLIB_WINDOWS -#define WORK_PATH_ROOT _T("\\Multimedia\\MPQs") -static const TCHAR szListFileDir[] = { '1', '9', '9', '5', ' ', '-', ' ', 'T', 'e', 's', 't', ' ', 'M', 'P', 'Q', 's', '\\', 'l', 'i', 's', 't', 'f', 'i', 'l', 'e', 's', '-', (TCHAR)0x65B0, (TCHAR)0x5EFA, (TCHAR)0x6587, (TCHAR)0x4EF6, (TCHAR)0x5939, 0 }; -#endif - -#ifdef STORMLIB_LINUX -#define WORK_PATH_ROOT "/media/ladik/CascStorages/MPQs" -static const TCHAR szListFileDir[] = { '1', '9', '9', '5', ' ', '-', ' ', 'T', 'e', 's', 't', ' ', 'M', 'P', 'Q', 's', '\\', 'l', 'i', 's', 't', 'f', 'i', 'l', 'e', 's', '-', (TCHAR)0xe6, (TCHAR)0x96, (TCHAR)0xB0, (TCHAR)0xE5, (TCHAR)0xBB, (TCHAR)0xBA, (TCHAR)0xE6, (TCHAR)0x96, (TCHAR)0x87, (TCHAR)0xE4, (TCHAR)0xBB, (TCHAR)0xB6, (TCHAR)0xE5, (TCHAR)0xA4, (TCHAR)0xB9, 0 }; -#endif - -#ifdef STORMLIB_MAC -#define WORK_PATH_ROOT "/home/sam/StormLib/test" -static const TCHAR szListFileDir[] = { '1', '9', '9', '5', ' ', '-', ' ', 'T', 'e', 's', 't', ' ', 'M', 'P', 'Q', 's', '\\', 'l', 'i', 's', 't', 'f', 'i', 'l', 'e', 's', '-', (TCHAR)0xe6, (TCHAR)0x96, (TCHAR)0xB0, (TCHAR)0xE5, (TCHAR)0xBB, (TCHAR)0xBA, (TCHAR)0xE6, (TCHAR)0x96, (TCHAR)0x87, (TCHAR)0xE4, (TCHAR)0xBB, (TCHAR)0xB6, (TCHAR)0xE5, (TCHAR)0xA4, (TCHAR)0xB9, 0 }; -#endif - -#ifdef STORMLIB_HAIKU -#define WORK_PATH_ROOT "~/StormLib/test" -static const TCHAR szListFileDir[] = { '1', '9', '9', '5', ' ', '-', ' ', 'T', 'e', 's', 't', ' ', 'M', 'P', 'Q', 's', '\\', 'l', 'i', 's', 't', 'f', 'i', 'l', 'e', 's', '-', (TCHAR)0xe6, (TCHAR)0x96, (TCHAR)0xB0, (TCHAR)0xE5, (TCHAR)0xBB, (TCHAR)0xBA, (TCHAR)0xE6, (TCHAR)0x96, (TCHAR)0x87, (TCHAR)0xE4, (TCHAR)0xBB, (TCHAR)0xB6, (TCHAR)0xE5, (TCHAR)0xA4, (TCHAR)0xB9, 0 }; -#endif - -// Global for the work MPQ -static LPCTSTR szMpqSubDir = _T("1995 - Test MPQs"); -static LPCTSTR szMpqPatchDir = _T("1995 - Test MPQs\\patches"); -static LPCSTR IntToHexChar = "0123456789abcdef"; - -//----------------------------------------------------------------------------- -// Testing data - -static DWORD AddFlags[] = -{ -// Compression Encryption Fixed key Single Unit Sector CRC - 0 | 0 | 0 | 0 | 0, - 0 | MPQ_FILE_ENCRYPTED | 0 | 0 | 0, - 0 | MPQ_FILE_ENCRYPTED | MPQ_FILE_FIX_KEY | 0 | 0, - 0 | 0 | 0 | MPQ_FILE_SINGLE_UNIT | 0, - 0 | MPQ_FILE_ENCRYPTED | 0 | MPQ_FILE_SINGLE_UNIT | 0, - 0 | MPQ_FILE_ENCRYPTED | MPQ_FILE_FIX_KEY | MPQ_FILE_SINGLE_UNIT | 0, - MPQ_FILE_IMPLODE | 0 | 0 | 0 | 0, - MPQ_FILE_IMPLODE | MPQ_FILE_ENCRYPTED | 0 | 0 | 0, - MPQ_FILE_IMPLODE | MPQ_FILE_ENCRYPTED | MPQ_FILE_FIX_KEY | 0 | 0, - MPQ_FILE_IMPLODE | 0 | 0 | MPQ_FILE_SINGLE_UNIT | 0, - MPQ_FILE_IMPLODE | MPQ_FILE_ENCRYPTED | 0 | MPQ_FILE_SINGLE_UNIT | 0, - MPQ_FILE_IMPLODE | MPQ_FILE_ENCRYPTED | MPQ_FILE_FIX_KEY | MPQ_FILE_SINGLE_UNIT | 0, - MPQ_FILE_IMPLODE | 0 | 0 | 0 | MPQ_FILE_SECTOR_CRC, - MPQ_FILE_IMPLODE | MPQ_FILE_ENCRYPTED | 0 | 0 | MPQ_FILE_SECTOR_CRC, - MPQ_FILE_IMPLODE | MPQ_FILE_ENCRYPTED | MPQ_FILE_FIX_KEY | 0 | MPQ_FILE_SECTOR_CRC, - MPQ_FILE_COMPRESS | 0 | 0 | 0 | 0, - MPQ_FILE_COMPRESS | MPQ_FILE_ENCRYPTED | 0 | 0 | 0, - MPQ_FILE_COMPRESS | MPQ_FILE_ENCRYPTED | MPQ_FILE_FIX_KEY | 0 | 0, - MPQ_FILE_COMPRESS | 0 | 0 | MPQ_FILE_SINGLE_UNIT | 0, - MPQ_FILE_COMPRESS | MPQ_FILE_ENCRYPTED | 0 | MPQ_FILE_SINGLE_UNIT | 0, - MPQ_FILE_COMPRESS | MPQ_FILE_ENCRYPTED | MPQ_FILE_FIX_KEY | MPQ_FILE_SINGLE_UNIT | 0, - MPQ_FILE_COMPRESS | 0 | 0 | 0 | MPQ_FILE_SECTOR_CRC, - MPQ_FILE_COMPRESS | MPQ_FILE_ENCRYPTED | 0 | 0 | MPQ_FILE_SECTOR_CRC, - MPQ_FILE_COMPRESS | MPQ_FILE_ENCRYPTED | MPQ_FILE_FIX_KEY | 0 | MPQ_FILE_SECTOR_CRC, - 0xFFFFFFFF -}; - -static DWORD WaveCompressions[] = -{ - MPQ_COMPRESSION_ADPCM_MONO | MPQ_COMPRESSION_HUFFMANN, - MPQ_COMPRESSION_ADPCM_STEREO | MPQ_COMPRESSION_HUFFMANN, - MPQ_COMPRESSION_PKWARE, - MPQ_COMPRESSION_ZLIB, - MPQ_COMPRESSION_BZIP2 -}; - -static const wchar_t szUnicodeName1[] = { // Czech - 0x010C, 0x0065, 0x0073, 0x006B, 0x00FD, _T('.'), _T('m'), _T('p'), _T('q'), 0 -}; - -static const wchar_t szUnicodeName2[] = { // Russian - 0x0420, 0x0443, 0x0441, 0x0441, 0x043A, 0x0438, 0x0439, _T('.'), _T('m'), _T('p'), _T('q'), 0 -}; - -static const wchar_t szUnicodeName3[] = { // Greek - 0x03B5, 0x03BB, 0x03BB, 0x03B7, 0x03BD, 0x03B9, 0x03BA, 0x03AC, _T('.'), _T('m'), _T('p'), _T('q'), 0 -}; - -static const wchar_t szUnicodeName4[] = { // Chinese - 0x65E5, 0x672C, 0x8A9E, _T('.'), _T('m'), _T('p'), _T('q'), 0 -}; - -static const wchar_t szUnicodeName5[] = { // Japanese - 0x7B80, 0x4F53, 0x4E2D, 0x6587, _T('.'), _T('m'), _T('p'), _T('q'), 0 -}; - -static const wchar_t szUnicodeName6[] = { // Arabic - 0x0627, 0x0644, 0x0639, 0x0639, 0x0631, 0x0628, 0x064A, 0x0629, _T('.'), _T('m'), _T('p'), _T('q'), 0 -}; - -static SFILE_MARKERS MpqMarkers[] = -{ - {sizeof(SFILE_MARKERS), ID_MPQ, "(hash table)", "(block table)"}, - {sizeof(SFILE_MARKERS), 'XHSC', "(cash table)", "(clock table)"} -}; - -static LPCTSTR PatchList_StarCraft[] = -{ - _T("MPQ_1998_v1_StarCraft.mpq"), - _T("s1-1998-BroodWar.mpq"), - NULL -}; - -static LPCTSTR PatchList_WoW_OldWorld13286[] = -{ - _T("MPQ_2012_v4_OldWorld.MPQ"), - _T("wow-update-oldworld-13154.MPQ"), - _T("wow-update-oldworld-13286.MPQ"), - NULL -}; - -static LPCTSTR PatchList_WoW_15050[] = -{ - _T("MPQ_2013_v4_world.MPQ"), - _T("wow-update-13164.MPQ"), - _T("wow-update-13205.MPQ"), - _T("wow-update-13287.MPQ"), - _T("wow-update-13329.MPQ"), - _T("wow-update-13596.MPQ"), - _T("wow-update-13623.MPQ"), - _T("wow-update-base-13914.MPQ"), - _T("wow-update-base-14007.MPQ"), - _T("wow-update-base-14333.MPQ"), - _T("wow-update-base-14480.MPQ"), - _T("wow-update-base-14545.MPQ"), - _T("wow-update-base-14946.MPQ"), - _T("wow-update-base-15005.MPQ"), - _T("wow-update-base-15050.MPQ"), - NULL -}; - -static LPCTSTR PatchList_WoW_16965[] = -{ - _T("MPQ_2013_v4_locale-enGB.MPQ"), - _T("wow-update-enGB-16016.MPQ"), - _T("wow-update-enGB-16048.MPQ"), - _T("wow-update-enGB-16057.MPQ"), - _T("wow-update-enGB-16309.MPQ"), - _T("wow-update-enGB-16357.MPQ"), - _T("wow-update-enGB-16516.MPQ"), - _T("wow-update-enGB-16650.MPQ"), - _T("wow-update-enGB-16844.MPQ"), - _T("wow-update-enGB-16965.MPQ"), - NULL -}; - -static LPCTSTR PatchList_SC2_32283[] = -{ - _T("MPQ_2013_v4_Base1.SC2Data"), - _T("s2-update-base-23258.MPQ"), - _T("s2-update-base-24540.MPQ"), - _T("s2-update-base-26147.MPQ"), - _T("s2-update-base-28522.MPQ"), - _T("s2-update-base-30508.MPQ"), - _T("s2-update-base-32283.MPQ"), - NULL -}; - -static LPCTSTR PatchList_SC2_34644[] = -{ - _T("MPQ_2013_v4_Base1.SC2Data"), - _T("s2-update-base-23258.MPQ"), - _T("s2-update-base-24540.MPQ"), - _T("s2-update-base-26147.MPQ"), - _T("s2-update-base-28522.MPQ"), - _T("s2-update-base-32384.MPQ"), - _T("s2-update-base-34644.MPQ"), - NULL -}; - -static LPCTSTR PatchList_SC2_34644_Maps[] = -{ - _T("MPQ_2013_v4_Base3.SC2Maps"), - _T("s2-update-base-23258.MPQ"), - _T("s2-update-base-24540.MPQ"), - _T("s2-update-base-26147.MPQ"), - _T("s2-update-base-28522.MPQ"), - _T("s2-update-base-32384.MPQ"), - _T("s2-update-base-34644.MPQ"), - NULL -}; - -static LPCTSTR PatchList_SC2_32283_enGB[] = -{ - _T("MPQ_2013_v4_Mods#Core.SC2Mod#enGB.SC2Assets"), - _T("s2-update-enGB-23258.MPQ"), - _T("s2-update-enGB-24540.MPQ"), - _T("s2-update-enGB-26147.MPQ"), - _T("s2-update-enGB-28522.MPQ"), - _T("s2-update-enGB-30508.MPQ"), - _T("s2-update-enGB-32283.MPQ"), - NULL -}; - -static LPCTSTR PatchList_SC2_36281_enGB[] = -{ - _T("MPQ_2013_v4_Mods#Liberty.SC2Mod#enGB.SC2Data"), - _T("s2-update-enGB-23258.MPQ"), - _T("s2-update-enGB-24540.MPQ"), - _T("s2-update-enGB-26147.MPQ"), - _T("s2-update-enGB-28522.MPQ"), - _T("s2-update-enGB-32384.MPQ"), - _T("s2-update-enGB-34644.MPQ"), - _T("s2-update-enGB-36281.MPQ"), - NULL -}; - -static LPCTSTR PatchList_HS_3604_enGB[] = -{ - _T("MPQ_2014_v4_base-Win.MPQ"), - _T("hs-0-3604-Win-final.MPQ"), - NULL -}; - -static LPCTSTR PatchList_HS_6898_enGB[] = -{ - _T("MPQ_2014_v4_base-Win.MPQ"), - _T("hs-0-5314-Win-final.MPQ"), - _T("hs-5314-5435-Win-final.MPQ"), - _T("hs-5435-5506-Win-final.MPQ"), - _T("hs-5506-5834-Win-final.MPQ"), - _T("hs-5834-6024-Win-final.MPQ"), - _T("hs-6024-6141-Win-final.MPQ"), - _T("hs-6141-6187-Win-final.MPQ"), - _T("hs-6187-6284-Win-final.MPQ"), - _T("hs-6284-6485-Win-final.MPQ"), - _T("hs-6485-6898-Win-final.MPQ"), - NULL -}; - -//----------------------------------------------------------------------------- -// Local file functions - -// Definition of the path separator -#ifdef STORMLIB_WINDOWS -static LPCTSTR g_szPathSeparator = _T("\\"); -static const TCHAR PATH_SEPARATOR = _T('\\'); // Path separator for Windows platforms -#else -static LPCSTR g_szPathSeparator = "/"; -static const TCHAR PATH_SEPARATOR = '/'; // Path separator for Non-Windows platforms -#endif - -// This must be the directory where our test MPQs are stored. -// We also expect a subdirectory named -static TCHAR szMpqDirectory[MAX_PATH+1]; -size_t cchMpqDirectory = 0; - -template -static bool IsFullPath(const XCHAR * szFileName) -{ -#ifdef STORMLIB_WINDOWS - if(('A' <= szFileName[0] && szFileName[0] <= 'Z') || ('a' <= szFileName[0] && szFileName[0] <= 'z')) - { - return (szFileName[1] == ':' && szFileName[2] == PATH_SEPARATOR); - } -#endif - - szFileName = szFileName; - return false; -} - -static bool IsMpqExtension(LPCTSTR szFileName) -{ - LPCTSTR szExtension = _tcsrchr(szFileName, '.'); - - if(szExtension != NULL) - { - if(!_tcsicmp(szExtension, _T(".mpq"))) - return true; - if(!_tcsicmp(szExtension, _T(".w3m"))) - return true; - if(!_tcsicmp(szExtension, _T(".w3x"))) - return true; - if(!_tcsicmp(szExtension, _T(".asi"))) - return true; - if(!_tcsicmp(szExtension, _T(".mpqe"))) - return true; - if(!_tcsicmp(szExtension, _T(".part"))) - return true; - if(!_tcsicmp(szExtension, _T(".sv"))) - return true; - if(!_tcsicmp(szExtension, _T(".s2ma"))) - return true; - if(!_tcsicmp(szExtension, _T(".SC2Map"))) - return true; - if(!_tcsicmp(szExtension, _T(".SC2Mod"))) - return true; - if(!_tcsicmp(szExtension, _T(".SC2Replay"))) - return true; - if(!_tcsicmp(szExtension, _T(".0"))) // .MPQ.0 - return true; -// if(!_tcsicmp(szExtension, ".link")) -// return true; - } - - return false; -} - -// Converts binary array to string. -// The caller must ensure that the buffer has at least ((cbBinary * 2) + 1) characters -template -xchar * StringFromBinary(LPBYTE pbBinary, size_t cbBinary, xchar * szBuffer) -{ - xchar * szSaveBuffer = szBuffer; - - // Verify the binary pointer - if(pbBinary && cbBinary) - { - // Convert the bytes to string array - for(size_t i = 0; i < cbBinary; i++) - { - *szBuffer++ = IntToHexChar[pbBinary[i] >> 0x04]; - *szBuffer++ = IntToHexChar[pbBinary[i] & 0x0F]; - } - } - - // Terminate the string - *szBuffer = 0; - return szSaveBuffer; -} - -static void AddStringBeforeExtension(char * szBuffer, LPCSTR szFileName, LPCSTR szExtraString) -{ - LPCSTR szExtension; - size_t nLength; - - // Get the extension - szExtension = strrchr(szFileName, '.'); - if(szExtension == NULL) - szExtension = szFileName + strlen(szFileName); - nLength = (size_t)(szExtension - szFileName); - - // Copy the part before extension - memcpy(szBuffer, szFileName, nLength); - szFileName += nLength; - szBuffer += nLength; - - // Append the extra data - if(szExtraString != NULL) - strcpy(szBuffer, szExtraString); - - // Append the rest of the file name - strcat(szBuffer, szFileName); -} - -static bool CompareBlocks(LPBYTE pbBlock1, LPBYTE pbBlock2, DWORD dwLength, DWORD * pdwDifference) -{ - for(DWORD i = 0; i < dwLength; i++) - { - if(pbBlock1[i] != pbBlock2[i]) - { - pdwDifference[0] = i; - return false; - } - } - - return true; -} - -static int GetPathSeparatorCount(LPCSTR szPath) -{ - int nSeparatorCount = 0; - - while(szPath[0] != 0) - { - if(szPath[0] == '\\' || szPath[0] == '/') - nSeparatorCount++; - szPath++; - } - - return nSeparatorCount; -} - -template -static const XCHAR * FindNextPathPart(const XCHAR * szPath, size_t nPartCount) -{ - const XCHAR * szPathPart = szPath; - - while(szPath[0] != 0 && nPartCount > 0) - { - // Is there path separator? - if(szPath[0] == '\\' || szPath[0] == '/') - { - szPathPart = szPath + 1; - nPartCount--; - } - - // Move to the next letter - szPath++; - } - - return szPathPart; -} - -template -size_t StringLength(const XCHAR * szString) -{ - size_t nLength; - - for(nLength = 0; szString[nLength] != 0; nLength++); - - return nLength; -} - -template -static const XCHAR * GetShortPlainName(const XCHAR * szFileName) -{ - const XCHAR * szPlainName = FindNextPathPart(szFileName, 1000); - const XCHAR * szPlainEnd = szFileName + StringLength(szFileName); - - // If the name is still too long, cut it - if((szPlainEnd - szPlainName) > 50) - szPlainName = szPlainEnd - 50; - - return szPlainName; -} - -static void CopyPathPart(char * szBuffer, LPCSTR szPath) -{ - while(szPath[0] != 0) - { - szBuffer[0] = (szPath[0] == '\\' || szPath[0] == '/') ? '/' : szPath[0]; - szBuffer++; - szPath++; - } - - *szBuffer = 0; -} - -static bool CopyStringAndVerifyConversion( - LPCTSTR szFoundFile, - TCHAR * szBufferT, - char * szBufferA, - size_t cchMaxChars) -{ - // Convert the TCHAR name to ANSI name - StringCopy(szBufferA, cchMaxChars, szFoundFile); - StringCopy(szBufferT, cchMaxChars, szBufferA); - - // Compare both TCHAR strings - return (_tcsicmp(szBufferT, szFoundFile) == 0) ? true : false; -} - -static size_t ConvertSha1ToText(const unsigned char * sha1_digest, TCHAR * szSha1Text) -{ - LPCSTR szTable = "0123456789abcdef"; - - for(size_t i = 0; i < SHA1_DIGEST_SIZE; i++) - { - *szSha1Text++ = szTable[(sha1_digest[0] >> 0x04)]; - *szSha1Text++ = szTable[(sha1_digest[0] & 0x0F)]; - sha1_digest++; - } - - *szSha1Text = 0; - return (SHA1_DIGEST_SIZE * 2); -} - -static void CreateFullPathName(TCHAR * szBuffer, size_t cchBuffer, LPCTSTR szSubDir, LPCTSTR szNamePart1, LPCTSTR szNamePart2 = NULL) -{ - TCHAR * szSaveBuffer = szBuffer; - size_t nPrefixLength = 0; - size_t nLength; - DWORD dwProvider = 0; - bool bIsFullPath = false; - char chSeparator = PATH_SEPARATOR; - - // Pre-initialize the buffer - szBuffer[0] = 0; - - // Determine the path prefix - if(szNamePart1 != NULL) - { - nPrefixLength = FileStream_Prefix(szNamePart1, &dwProvider); - if((dwProvider & BASE_PROVIDER_MASK) == BASE_PROVIDER_HTTP) - { - bIsFullPath = true; - chSeparator = '/'; - } - else - bIsFullPath = IsFullPath(szNamePart1 + nPrefixLength); - } - - // Copy the MPQ prefix, if any - if(nPrefixLength > 0) - { - StringCat(szBuffer, cchBuffer, szNamePart1); - szBuffer[nPrefixLength] = 0; - szSaveBuffer += nPrefixLength; - szNamePart1 += nPrefixLength; - } - - // If the given name is not a full path, copy the MPQ directory - if(bIsFullPath == false) - { - // Copy the master MPQ directory - StringCat(szBuffer, cchBuffer, szMpqDirectory); - - // Append the subdirectory, if any - if(szSubDir != NULL && (nLength = _tcslen(szSubDir)) != 0) - { - // No leading or trailing separator are allowed - assert(szSubDir[0] != '/' && szSubDir[0] != '\\'); - assert(szSubDir[nLength - 1] != '/' && szSubDir[nLength - 1] != '\\'); - - // Append the subdirectory - StringCat(szBuffer, cchBuffer, g_szPathSeparator); - StringCat(szBuffer, cchBuffer, szSubDir); - } - } - - // Copy the file name, if any - if(szNamePart1 != NULL && (nLength = _tcslen(szNamePart1)) != 0) - { - // Path separators are not allowed in the name part - assert(szNamePart1[0] != '\\' && szNamePart1[0] != '/'); - assert(szNamePart1[nLength - 1] != '/' && szNamePart1[nLength - 1] != '\\'); - - // Append file path separator and the name part - if(bIsFullPath == false) - StringCat(szBuffer, cchBuffer, g_szPathSeparator); - StringCat(szBuffer, cchBuffer, szNamePart1); - } - - // Append the second part of the name - if(szNamePart2 != NULL && (nLength = _tcslen(szNamePart2)) != 0) - { - // Copy the file name - StringCat(szBuffer, cchBuffer, szNamePart2); - } - - // Normalize the path separators - for(; szSaveBuffer[0] != 0; szSaveBuffer++) - { - szSaveBuffer[0] = (szSaveBuffer[0] != '/' && szSaveBuffer[0] != '\\') ? szSaveBuffer[0] : chSeparator; - } -} - -#ifdef _UNICODE -static void CreateFullPathName(char * szBuffer, size_t cchBuffer, LPCTSTR szSubDir, LPCTSTR szNamePart1, LPCTSTR szNamePart2 = NULL) -{ - TCHAR szFullPathT[MAX_PATH]; - - CreateFullPathName(szFullPathT, _countof(szFullPathT), szSubDir, szNamePart1, szNamePart2); - StringCopy(szBuffer, cchBuffer, szFullPathT); -} -#endif - -static DWORD CalculateFileSha1(TLogHelper * pLogger, LPCTSTR szFullPath, TCHAR * szFileSha1) -{ - TFileStream * pStream; - unsigned char sha1_digest[SHA1_DIGEST_SIZE]; - LPCTSTR szShortPlainName = GetShortPlainName(szFullPath); - hash_state sha1_state; - ULONGLONG ByteOffset = 0; - ULONGLONG FileSize = 0; - BYTE * pbFileBlock; - DWORD cbBytesToRead; - DWORD cbFileBlock = 0x100000; - DWORD dwErrCode = ERROR_SUCCESS; - - // Notify the user - pLogger->PrintProgress(_T("Hashing file %s"), szShortPlainName); - szFileSha1[0] = 0; - - // Open the file to be verified - pStream = FileStream_OpenFile(szFullPath, STREAM_FLAG_READ_ONLY); - if(pStream != NULL) - { - // Retrieve the size of the file - FileStream_GetSize(pStream, &FileSize); - - // Allocate the buffer for loading file parts - pbFileBlock = STORM_ALLOC(BYTE, cbFileBlock); - if(pbFileBlock != NULL) - { - // Initialize SHA1 calculation - sha1_init(&sha1_state); - - // Calculate the SHA1 of the file - while(ByteOffset < FileSize) - { - // Notify the user - pLogger->PrintProgress(_T("Hashing file %s (%I64u of %I64u)"), szShortPlainName, ByteOffset, FileSize); - - // Load the file block - cbBytesToRead = ((FileSize - ByteOffset) > cbFileBlock) ? cbFileBlock : (DWORD)(FileSize - ByteOffset); - if(!FileStream_Read(pStream, &ByteOffset, pbFileBlock, cbBytesToRead)) - { - dwErrCode = GetLastError(); - break; - } - - // Add to SHA1 - sha1_process(&sha1_state, pbFileBlock, cbBytesToRead); - ByteOffset += cbBytesToRead; - } - - // Notify the user - pLogger->PrintProgress(_T("Hashing file %s (%I64u of %I64u)"), szShortPlainName, ByteOffset, FileSize); - - // Finalize SHA1 - sha1_done(&sha1_state, sha1_digest); - - // Convert the SHA1 to ANSI text - ConvertSha1ToText(sha1_digest, szFileSha1); - STORM_FREE(pbFileBlock); - } - - FileStream_Close(pStream); - } - - // If we calculated something, return OK - if(dwErrCode == ERROR_SUCCESS && szFileSha1[0] == 0) - dwErrCode = ERROR_CAN_NOT_COMPLETE; - return dwErrCode; -} - -//----------------------------------------------------------------------------- -// Directory search - -static HANDLE InitDirectorySearch(LPCTSTR szDirectory) -{ -#ifdef STORMLIB_WINDOWS - - WIN32_FIND_DATA wf; - HANDLE hFind; - TCHAR szSearchMask[MAX_PATH]; - - // Construct the directory mask - _stprintf(szSearchMask, _T("%s\\*"), szDirectory); - - // Perform the search - hFind = FindFirstFile(szSearchMask, &wf); - return (hFind != INVALID_HANDLE_VALUE) ? hFind : NULL; - -#endif - -#if defined(STORMLIB_LINUX) || defined(STORMLIB_MAC) - - // Keep compilers happy - return (HANDLE)opendir(szDirectory); - -#endif -} - -static bool SearchDirectory(HANDLE hFind, TCHAR * szDirEntry, size_t cchDirEntry, bool & IsDirectory) -{ -#ifdef STORMLIB_WINDOWS - - WIN32_FIND_DATA wf; - TCHAR szDirEntryT[MAX_PATH]; - char szDirEntryA[MAX_PATH]; - - __SearchNextEntry: - - // Search for the hnext entry. - if(FindNextFile(hFind, &wf)) - { - // Verify if the directory entry is an UNICODE name that would be destroyed - // by Unicode->ANSI->Unicode conversion - if(CopyStringAndVerifyConversion(wf.cFileName, szDirEntryT, szDirEntryA, _countof(szDirEntryA)) == false) - goto __SearchNextEntry; - - IsDirectory = (wf.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) ? true : false; - StringCopy(szDirEntry, cchDirEntry, wf.cFileName); - return true; - } - - return false; - -#endif - -#if defined(STORMLIB_LINUX) || defined(STORMLIB_MAC) - - struct dirent * directory_entry; - - directory_entry = readdir((DIR *)hFind); - if(directory_entry != NULL) - { - IsDirectory = (directory_entry->d_type == DT_DIR) ? true : false; - strcpy(szDirEntry, directory_entry->d_name); - return true; - } - - return false; - -#endif -} - -static void FreeDirectorySearch(HANDLE hFind) -{ -#ifdef STORMLIB_WINDOWS - FindClose(hFind); -#endif - -#if defined(STORMLIB_LINUX) || defined(STORMLIB_MAC) - closedir((DIR *)hFind); -#endif -} - -static DWORD FindFilesInternal(FIND_FILE_CALLBACK pfnTest, TCHAR * szDirectory) -{ - TCHAR * szPlainName; - HANDLE hFind; - size_t nLength; - TCHAR szDirEntry[MAX_PATH]; - bool IsDirectory = false; - DWORD dwErrCode = ERROR_SUCCESS; - - if(szDirectory != NULL) - { - // Initiate directory search - hFind = InitDirectorySearch(szDirectory); - if(hFind != NULL) - { - // Append slash at the end of the directory name - nLength = _tcslen(szDirectory); - szDirectory[nLength++] = PATH_SEPARATOR; - szPlainName = szDirectory + nLength; - - // Skip the first entry, since it's always "." or ".." - while(SearchDirectory(hFind, szDirEntry, _countof(szDirEntry), IsDirectory) && dwErrCode == ERROR_SUCCESS) - { - // Copy the directory entry name to both names - _tcscpy(szPlainName, szDirEntry); - - // Found a directory? - if(IsDirectory) - { - if(szDirEntry[0] != '.') - { - dwErrCode = FindFilesInternal(pfnTest, szDirectory); - } - } - else - { - if(pfnTest != NULL) - { - dwErrCode = pfnTest(szDirectory); - } - } - } - - FreeDirectorySearch(hFind); - } - } - - // Free the path buffer, if any - return dwErrCode; -} - -static DWORD FindFiles(FIND_FILE_CALLBACK pfnFindFile, LPCTSTR szSubDirectory) -{ - TCHAR szWorkBuff[MAX_PATH]; - - CreateFullPathName(szWorkBuff, _countof(szWorkBuff), szSubDirectory, NULL); - return FindFilesInternal(pfnFindFile, szWorkBuff); -} - -static DWORD InitializeMpqDirectory(TCHAR * argv[], int argc) -{ - TLogHelper Logger("InitWorkDir"); - TFileStream * pStream; - TCHAR szFullPath[MAX_PATH]; - LPCTSTR szWhereFrom = _T("default"); - LPCTSTR szDirName = WORK_PATH_ROOT; - - // Retrieve the first argument - if(argc > 1 && argv[1] != NULL) - { - // Check if it's a directory - pStream = FileStream_OpenFile(argv[1], STREAM_FLAG_READ_ONLY); - if(pStream == NULL) - { - szWhereFrom = _T("command line"); - szDirName = argv[1]; - } - else - { - FileStream_Close(pStream); - } - } - - // Copy the name of the MPQ directory. - StringCopy(szMpqDirectory, _countof(szMpqDirectory), szDirName); - cchMpqDirectory = _tcslen(szMpqDirectory); - - // Cut trailing slashes and/or backslashes - while((cchMpqDirectory > 0) && (szMpqDirectory[cchMpqDirectory - 1] == '/' || szMpqDirectory[cchMpqDirectory - 1] == '\\')) - cchMpqDirectory--; - szMpqDirectory[cchMpqDirectory] = 0; - - // Print the work directory info - Logger.PrintMessage(_T("Work directory %s (%s)"), szMpqDirectory, szWhereFrom); - - // Verify if the work MPQ directory is writable - CreateFullPathName(szFullPath, _countof(szFullPath), NULL, _T("TestFile.bin")); - pStream = FileStream_CreateFile(szFullPath, 0); - if(pStream == NULL) - return Logger.PrintError(_T("MPQ subdirectory doesn't exist or is not writable")); - - // Close the stream - FileStream_Close(pStream); - _tremove(szFullPath); - - // Verify if the working directory exists and if there is a subdirectory with the file name - CreateFullPathName(szFullPath, _countof(szFullPath), szListFileDir, _T("ListFile_Blizzard.txt")); - pStream = FileStream_OpenFile(szFullPath, STREAM_FLAG_READ_ONLY); - if(pStream == NULL) - return Logger.PrintError(_T("The main listfile (%s) was not found. Check your paths"), GetShortPlainName(szFullPath)); - - // Close the stream - FileStream_Close(pStream); - return ERROR_SUCCESS; -} - -static DWORD GetFilePatchCount(TLogHelper * pLogger, HANDLE hMpq, LPCSTR szFileName) -{ - TCHAR * szPatchName; - HANDLE hFile; - TCHAR szPatchChain[0x400]; - DWORD dwErrCode = ERROR_SUCCESS; - int nPatchCount = 0; - - // Open the MPQ file - if(SFileOpenFileEx(hMpq, szFileName, 0, &hFile)) - { - // Notify the user - pLogger->PrintProgress("Verifying patch chain for %s ...", GetShortPlainName(szFileName)); - - // Query the patch chain - if(!SFileGetFileInfo(hFile, SFileInfoPatchChain, szPatchChain, sizeof(szPatchChain), NULL)) - dwErrCode = pLogger->PrintError("Failed to retrieve the patch chain on %s", szFileName); - - // Is there anything at all in the patch chain? - if(dwErrCode == ERROR_SUCCESS && szPatchChain[0] == 0) - { - pLogger->PrintError("The patch chain for %s is empty", szFileName); - dwErrCode = ERROR_FILE_CORRUPT; - } - - // Now calculate the number of patches - if(dwErrCode == ERROR_SUCCESS) - { - // Get the pointer to the patch - szPatchName = szPatchChain; - - // Skip the base name - for(;;) - { - // Skip the current name - szPatchName = szPatchName + _tcslen(szPatchName) + 1; - if(szPatchName[0] == 0) - break; - - // Increment number of patches - nPatchCount++; - } - } - - SFileCloseFile(hFile); - } - else - { - pLogger->PrintError("Open failed: %s", szFileName); - } - - return nPatchCount; -} - -static DWORD VerifyFilePatchCount(TLogHelper * pLogger, HANDLE hMpq, LPCSTR szFileName, DWORD dwExpectedPatchCount) -{ - DWORD dwPatchCount = 0; - - // Retrieve the patch count - pLogger->PrintProgress(_T("Verifying patch count for %s ..."), szFileName); - dwPatchCount = GetFilePatchCount(pLogger, hMpq, szFileName); - - // Check if there are any patches at all - if(dwExpectedPatchCount != 0 && dwPatchCount == 0) - { - pLogger->PrintMessage("There are no patches for %s", szFileName); - return ERROR_FILE_CORRUPT; - } - - // Check if the number of patches fits - if(dwPatchCount != dwExpectedPatchCount) - { - pLogger->PrintMessage("Unexpected number of patches for %s", szFileName); - return ERROR_FILE_CORRUPT; - } - - return ERROR_SUCCESS; -} - -static DWORD CreateEmptyFile(TLogHelper * pLogger, LPCTSTR szPlainName, ULONGLONG FileSize, TCHAR * szBuffer) -{ - TFileStream * pStream; - TCHAR szFullPath[MAX_PATH]; - - // Notify the user - pLogger->PrintProgress(_T("Creating empty file %s ..."), szPlainName); - - // Construct the full path and crete the file - CreateFullPathName(szFullPath, _countof(szFullPath), NULL, szPlainName); - pStream = FileStream_CreateFile(szFullPath, STREAM_PROVIDER_FLAT | BASE_PROVIDER_FILE); - if(pStream == NULL) - return pLogger->PrintError(_T("Failed to create file %s"), szBuffer); - - // Write the required size - FileStream_SetSize(pStream, FileSize); - FileStream_Close(pStream); - - // Give the caller the full file name - if(szBuffer != NULL) - _tcscpy(szBuffer, szFullPath); - return ERROR_SUCCESS; -} - -static DWORD VerifyFilePosition( - TLogHelper * pLogger, - TFileStream * pStream, - ULONGLONG ExpectedPosition) -{ - ULONGLONG ByteOffset = 0; - DWORD dwErrCode = ERROR_SUCCESS; - - // Retrieve the file position - if(FileStream_GetPos(pStream, &ByteOffset)) - { - if(ByteOffset != ExpectedPosition) - { - pLogger->PrintMessage(_T("The file position is different than expected (expected: ") I64u_t _T(", current: ") I64u_t, ExpectedPosition, ByteOffset); - dwErrCode = ERROR_FILE_CORRUPT; - } - } - else - { - dwErrCode = pLogger->PrintError(_T("Failed to retrieve the file offset")); - } - - return dwErrCode; -} - -static DWORD VerifyFileMpqHeader(TLogHelper * pLogger, TFileStream * pStream, ULONGLONG * pByteOffset) -{ - TMPQHeader Header; - DWORD dwErrCode = ERROR_SUCCESS; - - memset(&Header, 0xFE, sizeof(TMPQHeader)); - if(FileStream_Read(pStream, pByteOffset, &Header, sizeof(TMPQHeader))) - { - if(Header.dwID != g_dwMpqSignature) - { - pLogger->PrintMessage(_T("Read error - the data is not a MPQ header")); - dwErrCode = ERROR_FILE_CORRUPT; - } - } - else - { - dwErrCode = pLogger->PrintError(_T("Failed to read the MPQ header")); - } - - return dwErrCode; -} - -static DWORD WriteMpqUserDataHeader( - TLogHelper * pLogger, - TFileStream * pStream, - ULONGLONG ByteOffset, - DWORD dwByteCount) -{ - TMPQUserData UserData; - DWORD dwErrCode = ERROR_SUCCESS; - - // Notify the user - pLogger->PrintProgress("Writing user data header..."); - - // Fill the user data header - UserData.dwID = ID_MPQ_USERDATA; - UserData.cbUserDataSize = dwByteCount; - UserData.dwHeaderOffs = (dwByteCount + sizeof(TMPQUserData)); - UserData.cbUserDataHeader = dwByteCount / 2; - if(!FileStream_Write(pStream, &ByteOffset, &UserData, sizeof(TMPQUserData))) - dwErrCode = GetLastError(); - return dwErrCode; -} - -static DWORD WriteFileData( - TLogHelper * pLogger, - TFileStream * pStream, - ULONGLONG ByteOffset, - ULONGLONG ByteCount) -{ - ULONGLONG SaveByteCount = ByteCount; - ULONGLONG BytesWritten = 0; - LPBYTE pbDataBuffer; - DWORD cbDataBuffer = 0x10000; - DWORD dwErrCode = ERROR_SUCCESS; - - // Write some data - pbDataBuffer = new BYTE[cbDataBuffer]; - if(pbDataBuffer != NULL) - { - memset(pbDataBuffer, 0, cbDataBuffer); - strcpy((char *)pbDataBuffer, "This is a test data written to a file."); - - // Perform the write - while(ByteCount > 0) - { - DWORD cbToWrite = (ByteCount > cbDataBuffer) ? cbDataBuffer : (DWORD)ByteCount; - - // Notify the user - pLogger->PrintProgress("Writing file data (%I64u of %I64u) ...", BytesWritten, SaveByteCount); - - // Write the data - if(!FileStream_Write(pStream, &ByteOffset, pbDataBuffer, cbToWrite)) - { - dwErrCode = GetLastError(); - break; - } - - BytesWritten += cbToWrite; - ByteOffset += cbToWrite; - ByteCount -= cbToWrite; - } - - delete [] pbDataBuffer; - } - return dwErrCode; -} - -static DWORD CopyFileData( - TLogHelper * pLogger, - TFileStream * pStream1, - TFileStream * pStream2, - ULONGLONG ByteOffset, - ULONGLONG ByteCount) -{ - ULONGLONG BytesCopied = 0; - ULONGLONG EndOffset = ByteOffset + ByteCount; - LPBYTE pbCopyBuffer; - DWORD BytesToRead; - DWORD BlockLength = 0x100000; - DWORD dwErrCode = ERROR_SUCCESS; - - // Allocate copy buffer - pbCopyBuffer = STORM_ALLOC(BYTE, BlockLength); - if(pbCopyBuffer != NULL) - { - while(ByteOffset < EndOffset) - { - // Read source - BytesToRead = ((EndOffset - ByteOffset) > BlockLength) ? BlockLength : (DWORD)(EndOffset - ByteOffset); - if(!FileStream_Read(pStream1, &ByteOffset, pbCopyBuffer, BytesToRead)) - { - dwErrCode = GetLastError(); - break; - } - - // Write to the destination file - if(!FileStream_Write(pStream2, NULL, pbCopyBuffer, BytesToRead)) - { - dwErrCode = GetLastError(); - break; - } - - // Increment the byte counts - BytesCopied += BytesToRead; - ByteOffset += BytesToRead; - - // Notify the user - pLogger->PrintProgress("Copying (%I64u of %I64u complete) ...", BytesCopied, ByteCount); - } - - STORM_FREE(pbCopyBuffer); - } - - return dwErrCode; -} - -// Support function for copying file -static DWORD CreateFileCopy( - TLogHelper * pLogger, - LPCTSTR szPlainName, - LPCTSTR szFileCopy, - TCHAR * szBuffer = NULL, - size_t cchBuffer = 0, - ULONGLONG PreMpqDataSize = 0, - ULONGLONG UserDataSize = 0) -{ - TFileStream * pStream1; // Source file - TFileStream * pStream2; // Target file - ULONGLONG ByteOffset = 0; - ULONGLONG FileSize = 0; - TCHAR szFileName1[MAX_PATH]; - TCHAR szFileName2[MAX_PATH]; - DWORD dwErrCode = ERROR_SUCCESS; - - // Notify the user - szPlainName += FileStream_Prefix(szPlainName, NULL); - pLogger->PrintProgress(_T("Creating copy of %s ..."), szPlainName); - - // Construct both file names. Check if they are not the same - CreateFullPathName(szFileName1, _countof(szFileName1), szMpqSubDir, szPlainName); - CreateFullPathName(szFileName2, _countof(szFileName2), NULL, szFileCopy + FileStream_Prefix(szFileCopy, NULL)); - if(!_tcsicmp(szFileName1, szFileName2)) - { - pLogger->PrintError("Failed to create copy of MPQ (the copy name is the same like the original name)"); - return ERROR_CAN_NOT_COMPLETE; - } - - // Open the source file - pStream1 = FileStream_OpenFile(szFileName1, STREAM_FLAG_READ_ONLY); - if(pStream1 == NULL) - { - pLogger->PrintError(_T("Failed to open the source file %s"), szFileName1); - return ERROR_CAN_NOT_COMPLETE; - } - - // Create the destination file - pStream2 = FileStream_CreateFile(szFileName2, 0); - if(pStream2 != NULL) - { - // If we should write some pre-MPQ data to the target file, do it - if(PreMpqDataSize != 0) - { - dwErrCode = WriteFileData(pLogger, pStream2, ByteOffset, PreMpqDataSize); - ByteOffset += PreMpqDataSize; - } - - // If we should write some MPQ user data, write the header first - if(UserDataSize != 0) - { - dwErrCode = WriteMpqUserDataHeader(pLogger, pStream2, ByteOffset, (DWORD)UserDataSize); - ByteOffset += sizeof(TMPQUserData); - - dwErrCode = WriteFileData(pLogger, pStream2, ByteOffset, UserDataSize); - ByteOffset += UserDataSize; - } - - // Copy the file data from the source file to the destination file - FileStream_GetSize(pStream1, &FileSize); - if(FileSize != 0) - { - dwErrCode = CopyFileData(pLogger, pStream1, pStream2, 0, FileSize); - ByteOffset += FileSize; - } - FileStream_Close(pStream2); - } - - // Close the source file - FileStream_Close(pStream1); - - // Create the full file name of the target file, including prefix - if(szBuffer && cchBuffer) - CreateFullPathName(szBuffer, cchBuffer, NULL, szFileCopy); - - // Report error, if any - if(dwErrCode != ERROR_SUCCESS) - pLogger->PrintError("Failed to create copy of MPQ"); - return dwErrCode; -} - -static DWORD CreateMasterAndMirrorPaths( - TLogHelper * pLogger, - TCHAR * szMirrorPath, - TCHAR * szMasterPath, - LPCTSTR szMirrorName, - LPCTSTR szMasterName, - bool bCopyMirrorFile) -{ - TCHAR szCopyPath[MAX_PATH]; - DWORD dwErrCode = ERROR_SUCCESS; - - // Always delete the mirror file - CreateFullPathName(szMasterPath, MAX_PATH, szMpqSubDir, szMasterName); - CreateFullPathName(szCopyPath, _countof(szCopyPath), NULL, szMirrorName); - _tremove(szCopyPath + FileStream_Prefix(szCopyPath, NULL)); - - // Copy the mirrored file from the source to the work directory - if(bCopyMirrorFile) - dwErrCode = CreateFileCopy(pLogger, szMirrorName, szMirrorName); - - // Create the mirror*master path - if(dwErrCode == ERROR_SUCCESS) - _stprintf(szMirrorPath, _T("%s*%s"), szCopyPath, szMasterPath); - - return dwErrCode; -} - -static void WINAPI AddFileCallback(void * pvUserData, DWORD dwBytesWritten, DWORD dwTotalBytes, bool bFinalCall) -{ - TLogHelper * pLogger = (TLogHelper *)pvUserData; - - // Keep compiler happy - bFinalCall = bFinalCall; - - pLogger->PrintProgress("Adding file (%s) (%u of %u) (%u of %u) ...", pLogger->UserString, - pLogger->UserCount, - pLogger->UserTotal, - dwBytesWritten, - dwTotalBytes); -} - -static void WINAPI CompactCallback(void * pvUserData, DWORD dwWork, ULONGLONG BytesDone, ULONGLONG TotalBytes) -{ - TLogHelper * pLogger = (TLogHelper *)pvUserData; - LPCSTR szWork = NULL; - - switch(dwWork) - { - case CCB_CHECKING_FILES: - szWork = "Checking files in archive"; - break; - - case CCB_CHECKING_HASH_TABLE: - szWork = "Checking hash table"; - break; - - case CCB_COPYING_NON_MPQ_DATA: - szWork = "Copying non-MPQ data"; - break; - - case CCB_COMPACTING_FILES: - szWork = "Compacting files"; - break; - - case CCB_CLOSING_ARCHIVE: - szWork = "Closing archive"; - break; - } - - if(szWork != NULL) - { - if(pLogger != NULL) - pLogger->PrintProgress("%s (%I64u of %I64u) ...", szWork, BytesDone, TotalBytes); - else - printf("%s (" I64u_a " of " I64u_a ") ... \r", szWork, BytesDone, TotalBytes); - } -} - -//----------------------------------------------------------------------------- -// MPQ file utilities - -#define SEARCH_FLAG_LOAD_FILES 0x00000001 // Test function should load all files in the MPQ -#define SEARCH_FLAG_HASH_FILES 0x00000002 // Test function should load all files in the MPQ -#define SEARCH_FLAG_PLAY_WAVES 0x00000004 // Play extracted WAVE files -#define SEARCH_FLAG_MOST_PATCHED 0x00000008 // Find the most patched file -#define SEARCH_FLAG_IGNORE_ERRORS 0x00000010 // Ignore files that failed to open - -struct TFileData -{ - DWORD dwBlockIndex; - DWORD dwFileSize; - DWORD dwFlags; - DWORD dwCrc32; - BYTE FileData[1]; -}; - -static bool CheckIfFileIsPresent(TLogHelper * pLogger, HANDLE hMpq, LPCSTR szFileName, bool bShouldExist) -{ - HANDLE hFile = NULL; - - if(SFileOpenFileEx(hMpq, szFileName, 0, &hFile)) - { - if(bShouldExist == false) - pLogger->PrintMessage("The file %s is present, but it should not be", szFileName); - SFileCloseFile(hFile); - return true; - } - else - { - if(bShouldExist) - pLogger->PrintMessage("The file %s is not present, but it should be", szFileName); - return false; - } -} - -static TFileData * LoadLocalFile(TLogHelper * pLogger, LPCTSTR szFileName, bool bMustSucceed) -{ - TFileStream * pStream; - TFileData * pFileData = NULL; - ULONGLONG FileSize = 0; - size_t nAllocateBytes; - - // Notify the user - if(pLogger != NULL) - pLogger->PrintProgress("Loading local file ..."); - - // Attempt to open the file - pStream = FileStream_OpenFile(szFileName, STREAM_FLAG_READ_ONLY); - if(pStream == NULL) - { - if(pLogger != NULL && bMustSucceed == true) - pLogger->PrintError(_T("Open failed: %s"), szFileName); - return NULL; - } - - // Verify the size - FileStream_GetSize(pStream, &FileSize); - if((FileSize >> 0x20) == 0) - { - // Allocate space for the file - nAllocateBytes = sizeof(TFileData) + (size_t)FileSize; - pFileData = (TFileData *)STORM_ALLOC(BYTE, nAllocateBytes); - if(pFileData != NULL) - { - // Make sure it;s properly zeroed - memset(pFileData, 0, nAllocateBytes); - pFileData->dwFileSize = (DWORD)FileSize; - - // Load to memory - if(!FileStream_Read(pStream, NULL, pFileData->FileData, pFileData->dwFileSize)) - { - STORM_FREE(pFileData); - pFileData = NULL; - } - } - } - - FileStream_Close(pStream); - return pFileData; -} - -static DWORD LoadLocalFileMD5(TLogHelper * pLogger, LPCTSTR szFileFullName, LPBYTE md5_file_local) -{ - TFileData * pFileData; - - // Load the local file to memory - if((pFileData = LoadLocalFile(pLogger, szFileFullName, true)) == NULL) - { - return pLogger->PrintError(_T("The file \"%s\" could not be loaded"), szFileFullName); - } - - // Calculate the hash - CalculateDataBlockHash(pFileData->FileData, pFileData->dwFileSize, md5_file_local); - STORM_FREE(pFileData); - return ERROR_SUCCESS; -} - -static TFileData * LoadMpqFile(TLogHelper * pLogger, HANDLE hMpq, LPCSTR szFileName, LCID lcFileLocale = 0, bool bIgnoreOpedwErrCodes = false) -{ - TFileData * pFileData = NULL; - HANDLE hFile; - DWORD dwFileSizeHi = 0xCCCCCCCC; - DWORD dwFileSizeLo = 0; - DWORD dwBytesRead; - DWORD dwCrc32 = 0; - DWORD dwErrCode = ERROR_SUCCESS; - - // Notify the user that we are loading a file from MPQ - pLogger->PrintProgress("Loading file %s ...", GetShortPlainName(szFileName)); - -#if defined(_MSC_VER) && defined(_DEBUG) -// if(!_stricmp(szFileName, "File00000687.xxx")) -// __debugbreak(); -#endif - - // Make sure that we open the proper locale file - SFileSetLocale(lcFileLocale); - - // Open the file from MPQ - if(SFileOpenFileEx(hMpq, szFileName, 0, &hFile)) - { - // Get the CRC32 of the file - SFileGetFileInfo(hFile, SFileInfoCRC32, &dwCrc32, sizeof(dwCrc32), NULL); - - // Get the size of the file - if(dwErrCode == ERROR_SUCCESS) - { - dwFileSizeLo = SFileGetFileSize(hFile, &dwFileSizeHi); - if(dwFileSizeLo == SFILE_INVALID_SIZE || dwFileSizeHi != 0) - dwErrCode = pLogger->PrintError("Failed to query the file size"); - } - - // Spazzler protector: Creates fake files with size of 0x7FFFE7CA - if(dwErrCode == ERROR_SUCCESS && dwFileSizeLo > 0x1FFFFFFF) - { - dwErrCode = ERROR_FILE_CORRUPT; - } - - // Allocate buffer for the file content - if(dwErrCode == ERROR_SUCCESS) - { - pFileData = (TFileData *)STORM_ALLOC(BYTE, sizeof(TFileData) + dwFileSizeLo); - if(pFileData == NULL) - { - pLogger->PrintError("Failed to allocate buffer for the file content"); - dwErrCode = ERROR_NOT_ENOUGH_MEMORY; - } - } - - // get the file index of the MPQ file - if(dwErrCode == ERROR_SUCCESS) - { - // Store the file size - memset(pFileData, 0, sizeof(TFileData) + dwFileSizeLo); - pFileData->dwFileSize = dwFileSizeLo; - pFileData->dwCrc32 = dwCrc32; - - // Retrieve the block index and file flags - if(!SFileGetFileInfo(hFile, SFileInfoFileIndex, &pFileData->dwBlockIndex, sizeof(DWORD), NULL)) - dwErrCode = pLogger->PrintError("Failed retrieve the file index of %s", szFileName); - if(!SFileGetFileInfo(hFile, SFileInfoFlags, &pFileData->dwFlags, sizeof(DWORD), NULL)) - dwErrCode = pLogger->PrintError("Failed retrieve the file flags of %s", szFileName); - } - - // Load the entire file - if(dwErrCode == ERROR_SUCCESS) - { - //if(!_stricmp(szFileName, "File00000687.xxx")) - // __debugbreak(); - - // Read the file data - SFileReadFile(hFile, pFileData->FileData, dwFileSizeLo, &dwBytesRead, NULL); - if(dwBytesRead != dwFileSizeLo) - dwErrCode = ERROR_FILE_CORRUPT; - } - - // If failed, free the buffer - if(dwErrCode != ERROR_SUCCESS) - { - SetLastError(dwErrCode); - if(pFileData != NULL) - STORM_FREE(pFileData); - pFileData = NULL; - } - - SFileCloseFile(hFile); - } - else - { - if(bIgnoreOpedwErrCodes == false) - { - dwErrCode = pLogger->PrintError("Open failed: %s", szFileName); - } - } - - // Return what we got - return pFileData; -} - -static DWORD LoadMpqFileMD5(TLogHelper * pLogger, HANDLE hMpq, LPCSTR szArchivedName, LPBYTE md5_file_in_mpq1) -{ - TFileData * pFileData; - - // Load the MPQ to memory - if((pFileData = LoadMpqFile(pLogger, hMpq, szArchivedName)) == NULL) - return pLogger->PrintError("The file \"%s\" is not in the archive", szArchivedName); - - // Calculate hash - CalculateDataBlockHash(pFileData->FileData, pFileData->dwFileSize, md5_file_in_mpq1); - STORM_FREE(pFileData); - return ERROR_SUCCESS; -} - -static DWORD CompareTwoLocalFilesRR( - TLogHelper * pLogger, - TFileStream * pStream1, // Master file - TFileStream * pStream2, // Mirror file - int nIterations) // Number of iterations -{ - ULONGLONG RandomNumber = 0x12345678; // We need pseudo-random number that will repeat each run of the program - ULONGLONG RandomSeed; - ULONGLONG ByteOffset; - ULONGLONG FileSize1 = 1; - ULONGLONG FileSize2 = 2; - DWORD BytesToRead; - DWORD Difference; - LPBYTE pbBuffer1; - LPBYTE pbBuffer2; - DWORD cbBuffer = 0x100000; - DWORD dwErrCode = ERROR_SUCCESS; - - // Compare file sizes - FileStream_GetSize(pStream1, &FileSize1); - FileStream_GetSize(pStream2, &FileSize2); - if(FileSize1 != FileSize2) - { - pLogger->PrintMessage("The files have different size"); - return ERROR_CAN_NOT_COMPLETE; - } - - // Allocate both buffers - pbBuffer1 = STORM_ALLOC(BYTE, cbBuffer); - pbBuffer2 = STORM_ALLOC(BYTE, cbBuffer); - if(pbBuffer1 && pbBuffer2) - { - // Perform many random reads - for(int i = 0; i < nIterations; i++) - { - // Generate psudo-random offsrt and data size - ByteOffset = (RandomNumber % FileSize1); - BytesToRead = (DWORD)(RandomNumber % cbBuffer); - - // Show the progress message - pLogger->PrintProgress("Comparing file: Offset: " I64u_a ", Length: %u", ByteOffset, BytesToRead); - - // Only perform read if the byte offset is below - if(ByteOffset < FileSize1) - { - if((ByteOffset + BytesToRead) > FileSize1) - BytesToRead = (DWORD)(FileSize1 - ByteOffset); - - memset(pbBuffer1, 0xEE, cbBuffer); - memset(pbBuffer2, 0xAA, cbBuffer); - - FileStream_Read(pStream1, &ByteOffset, pbBuffer1, BytesToRead); - FileStream_Read(pStream2, &ByteOffset, pbBuffer2, BytesToRead); - - if(!CompareBlocks(pbBuffer1, pbBuffer2, BytesToRead, &Difference)) - { - pLogger->PrintMessage("Difference at %u (Offset " I64X_a ", Length %X)", Difference, ByteOffset, BytesToRead); - dwErrCode = ERROR_FILE_CORRUPT; - break; - } - - // Shuffle the random number - memcpy(&RandomSeed, pbBuffer1, sizeof(RandomSeed)); - RandomNumber = ((RandomNumber >> 0x11) | (RandomNumber << 0x29)) ^ (RandomNumber + RandomSeed); - } - } - } - - // Free both buffers - if(pbBuffer2 != NULL) - STORM_FREE(pbBuffer2); - if(pbBuffer1 != NULL) - STORM_FREE(pbBuffer1); - return dwErrCode; -} - -static bool CompareTwoFiles(TLogHelper * pLogger, TFileData * pFileData1, TFileData * pFileData2) -{ - // Compare the file size - if(pFileData1->dwFileSize != pFileData2->dwFileSize) - { - pLogger->PrintErrorVa(_T("The files have different size (%u vs %u)"), pFileData1->dwFileSize, pFileData2->dwFileSize); - SetLastError(ERROR_FILE_CORRUPT); - return false; - } - - // Compare the files - for(DWORD i = 0; i < pFileData1->dwFileSize; i++) - { - if(pFileData1->FileData[i] != pFileData2->FileData[i]) - { - pLogger->PrintErrorVa(_T("Files are different at offset %08X"), i); - SetLastError(ERROR_FILE_CORRUPT); - return false; - } - } - - // The files are identical - return true; -} - -static DWORD SearchArchive( - TLogHelper * pLogger, - HANDLE hMpq, - DWORD dwSearchFlags = 0, - DWORD * pdwFileCount = NULL, - LPBYTE pbFileHash = NULL) -{ - SFILE_FIND_DATA sf; - TFileData * pFileData; - HANDLE hFind; - DWORD dwFileCount = 0; - hash_state md5state; - TCHAR szListFile[MAX_PATH] = _T(""); - char szMostPatched[MAX_PATH] = ""; - DWORD dwErrCode = ERROR_SUCCESS; - bool bIgnoreOpedwErrCodes = (dwSearchFlags & SEARCH_FLAG_IGNORE_ERRORS) ? true : false; - bool bFound = true; - int nMaxPatchCount = 0; - int nPatchCount = 0; - - // Construct the full name of the listfile - CreateFullPathName(szListFile, _countof(szListFile), szListFileDir, _T("ListFile_Blizzard.txt")); - - // Prepare hashing - md5_init(&md5state); - - // Initiate the MPQ search - pLogger->PrintProgress("Searching the archive (initializing) ..."); - hFind = SFileFindFirstFile(hMpq, "*", &sf, szListFile); - if(hFind == NULL) - { - dwErrCode = GetLastError(); - dwErrCode = (dwErrCode == ERROR_NO_MORE_FILES) ? ERROR_SUCCESS : dwErrCode; - return dwErrCode; - } - - // Perform the search - pLogger->PrintProgress("Searching the archive ..."); - while(bFound == true) - { - // Increment number of files - dwFileCount++; - - if(dwSearchFlags & SEARCH_FLAG_MOST_PATCHED) - { - // Load the patch count - nPatchCount = GetFilePatchCount(pLogger, hMpq, sf.cFileName); - - // Check if it's greater than maximum - if(nPatchCount > nMaxPatchCount) - { - strcpy(szMostPatched, sf.cFileName); - nMaxPatchCount = nPatchCount; - } - } - - // Load the file to memory, if required - if(dwSearchFlags & SEARCH_FLAG_LOAD_FILES) - { - // Load the entire file to the MPQ - pFileData = LoadMpqFile(pLogger, hMpq, sf.cFileName, sf.lcLocale, bIgnoreOpedwErrCodes); - if(pFileData != NULL) - { - // Hash the file data, if needed - if((dwSearchFlags & SEARCH_FLAG_HASH_FILES) && !IsInternalMpqFileName(sf.cFileName)) - md5_process(&md5state, pFileData->FileData, pFileData->dwFileSize); - - // Play sound files, if required - if((dwSearchFlags & SEARCH_FLAG_PLAY_WAVES) && strstr(sf.cFileName, ".wav") != NULL) - { -#ifdef _MSC_VER - pLogger->PrintProgress("Playing sound %s", sf.cFileName); - PlaySound((LPCTSTR)pFileData->FileData, NULL, SND_MEMORY); -#endif - } - - // Debug: Show CRC32 of each file in order to debug differences - //pFileData->dwCrc32 = crc32(0, pFileData->FileData, pFileData->dwFileSize); - //printf("%08x: %s \n", pFileData->dwCrc32, sf.cFileName); - - // Free the loaded file data - STORM_FREE(pFileData); - } - } - - bFound = SFileFindNextFile(hFind, &sf); - } - SFileFindClose(hFind); - - // Give the file count, if required - if(pdwFileCount != NULL) - pdwFileCount[0] = dwFileCount; - - // Give the hash, if required - if(pbFileHash != NULL && (dwSearchFlags & SEARCH_FLAG_HASH_FILES)) - md5_done(&md5state, pbFileHash); - - return dwErrCode; -} - -static DWORD CreateNewArchive(TLogHelper * pLogger, LPCTSTR szPlainName, DWORD dwCreateFlags, DWORD dwMaxFileCount, HANDLE * phMpq) -{ - HANDLE hMpq = NULL; - TCHAR szMpqName[MAX_PATH]; - TCHAR szFullPath[MAX_PATH]; - - // Make sure that the MPQ is deleted - CreateFullPathName(szFullPath, _countof(szFullPath), NULL, szPlainName); - _tremove(szFullPath); - - // Create the new MPQ - StringCopy(szMpqName, _countof(szMpqName), szFullPath); - if(!SFileCreateArchive(szMpqName, dwCreateFlags, dwMaxFileCount, &hMpq)) - return pLogger->PrintError(_T("Failed to create archive %s"), szMpqName); - - // Shall we close it right away? - if(phMpq == NULL) - SFileCloseArchive(hMpq); - else - *phMpq = hMpq; - - return ERROR_SUCCESS; -} - -static DWORD CreateNewArchive_V2(TLogHelper * pLogger, LPCTSTR szPlainName, DWORD dwCreateFlags, DWORD dwMaxFileCount, HANDLE * phMpq) -{ - SFILE_CREATE_MPQ CreateInfo; - HANDLE hMpq = NULL; - TCHAR szMpqName[MAX_PATH]; - TCHAR szFullPath[MAX_PATH]; - - // Make sure that the MPQ is deleted - CreateFullPathName(szFullPath, _countof(szFullPath), NULL, szPlainName); - StringCopy(szMpqName, _countof(szMpqName), szFullPath); - _tremove(szFullPath); - - // Fill the create structure - memset(&CreateInfo, 0, sizeof(SFILE_CREATE_MPQ)); - CreateInfo.cbSize = sizeof(SFILE_CREATE_MPQ); - CreateInfo.dwMpqVersion = (dwCreateFlags & MPQ_CREATE_ARCHIVE_VMASK) >> FLAGS_TO_FORMAT_SHIFT; - CreateInfo.dwStreamFlags = STREAM_PROVIDER_FLAT | BASE_PROVIDER_FILE; -// CreateInfo.dwFileFlags1 = (dwCreateFlags & MPQ_CREATE_LISTFILE) ? MPQ_FILE_EXISTS : 0; -// CreateInfo.dwFileFlags2 = (dwCreateFlags & MPQ_CREATE_ATTRIBUTES) ? MPQ_FILE_EXISTS : 0; - CreateInfo.dwFileFlags1 = (dwCreateFlags & MPQ_CREATE_LISTFILE) ? MPQ_FILE_DEFAULT_INTERNAL : 0; - CreateInfo.dwFileFlags2 = (dwCreateFlags & MPQ_CREATE_ATTRIBUTES) ? MPQ_FILE_DEFAULT_INTERNAL : 0; - CreateInfo.dwFileFlags3 = (dwCreateFlags & MPQ_CREATE_SIGNATURE) ? MPQ_FILE_DEFAULT_INTERNAL : 0; - CreateInfo.dwAttrFlags = (dwCreateFlags & MPQ_CREATE_ATTRIBUTES) ? (MPQ_ATTRIBUTE_CRC32 | MPQ_ATTRIBUTE_FILETIME | MPQ_ATTRIBUTE_MD5) : 0; - CreateInfo.dwSectorSize = (CreateInfo.dwMpqVersion >= MPQ_FORMAT_VERSION_3) ? 0x4000 : 0x1000; - CreateInfo.dwRawChunkSize = (CreateInfo.dwMpqVersion >= MPQ_FORMAT_VERSION_4) ? 0x4000 : 0; - CreateInfo.dwMaxFileCount = dwMaxFileCount; - - // Create the new MPQ - if(!SFileCreateArchive2(szMpqName, &CreateInfo, &hMpq)) - return pLogger->PrintError(_T("Failed to create archive %s"), szMpqName); - - // Shall we close it right away? - if(phMpq == NULL) - SFileCloseArchive(hMpq); - else - *phMpq = hMpq; - - return ERROR_SUCCESS; -} - -// Creates new archive with UNICODE name. Adds prefix to the name -static DWORD CreateNewArchiveU(TLogHelper * pLogger, const wchar_t * szPlainName, DWORD dwCreateFlags, DWORD dwMaxFileCount) -{ -#ifdef _UNICODE - HANDLE hMpq = NULL; - TCHAR szMpqName[MAX_PATH+1]; - TCHAR szFullPath[MAX_PATH]; - - // Construct the full UNICODE name - CreateFullPathName(szFullPath, _countof(szFullPath), NULL, _T("StormLibTest_")); - StringCopy(szMpqName, _countof(szMpqName), szFullPath); - StringCat(szMpqName, _countof(szMpqName), szPlainName); - - // Make sure that the MPQ is deleted - _tremove(szMpqName); - - // Create the archive - pLogger->PrintProgress("Creating new archive with UNICODE name ..."); - if(!SFileCreateArchive(szMpqName, dwCreateFlags, dwMaxFileCount, &hMpq)) - return pLogger->PrintError(_T("Failed to create archive %s"), szMpqName); - - SFileCloseArchive(hMpq); -#else - pLogger = pLogger; - szPlainName = szPlainName; - dwCreateFlags = dwCreateFlags; - dwMaxFileCount = dwMaxFileCount; -#endif - return ERROR_SUCCESS; -} - -static DWORD OpenExistingArchive(TLogHelper * pLogger, LPCTSTR szFullPath, DWORD dwFlags, HANDLE * phMpq) -{ - HANDLE hMpq = NULL; - size_t nMarkerIndex; - DWORD dwErrCode = ERROR_SUCCESS; - - // Is it an encrypted MPQ ? - if(_tcsstr(szFullPath, _T(".MPQE")) != NULL) - dwFlags |= STREAM_PROVIDER_MPQE; - if(_tcsstr(szFullPath, _T(".MPQ.part")) != NULL) - dwFlags |= STREAM_PROVIDER_PARTIAL; - if(_tcsstr(szFullPath, _T(".mpq.part")) != NULL) - dwFlags |= STREAM_PROVIDER_PARTIAL; - if(_tcsstr(szFullPath, _T(".MPQ.0")) != NULL) - dwFlags |= STREAM_PROVIDER_BLOCK4; - - // Handle ASI files properly - nMarkerIndex = (_tcsstr(szFullPath, _T(".asi")) != NULL) ? 1 : 0; - SFileSetArchiveMarkers(&MpqMarkers[nMarkerIndex]); - - // Open the copied archive - pLogger->PrintProgress(_T("Opening archive %s ..."), GetShortPlainName(szFullPath)); - if(!SFileOpenArchive(szFullPath, 0, dwFlags, &hMpq)) - { - switch(dwErrCode = GetLastError()) - { -// case ERROR_BAD_FORMAT: // If the error is ERROR_BAD_FORMAT, try to open with MPQ_OPEN_FORCE_MPQ_V1 -// bReopenResult = SFileOpenArchive(szMpqName, 0, dwFlags | MPQ_OPEN_FORCE_MPQ_V1, &hMpq); -// dwErrCode = (bReopenResult == false) ? GetLastError() : ERROR_SUCCESS; -// break; - - case ERROR_AVI_FILE: // Ignore the error if it's an AVI file or if the file is incomplete - case ERROR_FILE_INCOMPLETE: - return dwErrCode; - } - - // Show the open error to the user - return pLogger->PrintError(_T("Failed to open archive %s"), szFullPath); - } - - // Store the archive handle or close the archive - if(phMpq == NULL) - SFileCloseArchive(hMpq); - else - *phMpq = hMpq; - return dwErrCode; -} - -static DWORD OpenPatchArchive(TLogHelper * pLogger, HANDLE hMpq, LPCTSTR szFullPath) -{ - TCHAR szPatchName[MAX_PATH]; - DWORD dwErrCode = ERROR_SUCCESS; - - pLogger->PrintProgress(_T("Adding patch %s ..."), GetShortPlainName(szFullPath)); - StringCopy(szPatchName, _countof(szPatchName), szFullPath); - if(!SFileOpenPatchArchive(hMpq, szPatchName, NULL, 0)) - dwErrCode = pLogger->PrintError(_T("Failed to add patch %s ..."), szFullPath); - - return dwErrCode; -} - -static DWORD OpenExistingArchiveWithCopy(TLogHelper * pLogger, LPCTSTR szFileName, LPCTSTR szCopyName, HANDLE * phMpq) -{ - DWORD dwFlags = 0; - TCHAR szFullPath[MAX_PATH]; - DWORD dwErrCode = ERROR_SUCCESS; - - // We expect MPQ directory to be already prepared by InitializeMpqDirectory - assert(szMpqDirectory[0] != 0); - - // At least one name must be entered - assert(szFileName != NULL || szCopyName != NULL); - - // If both names entered, create a copy - if(szFileName != NULL && szCopyName != NULL) - { - dwErrCode = CreateFileCopy(pLogger, szFileName, szCopyName, szFullPath, _countof(szFullPath)); - if(dwErrCode != ERROR_SUCCESS) - return dwErrCode; - } - - // If only source name entered, open it for read-only access - else if(szFileName != NULL && szCopyName == NULL) - { - CreateFullPathName(szFullPath, _countof(szFullPath), szMpqSubDir, szFileName); - dwFlags |= MPQ_OPEN_READ_ONLY; - } - - // If only target name entered, open it directly - else if(szFileName == NULL && szCopyName != NULL) - { - CreateFullPathName(szFullPath, _countof(szFullPath), NULL, szCopyName); - } - - // Open the archive - return OpenExistingArchive(pLogger, szFullPath, dwFlags, phMpq); -} - -static DWORD OpenPatchedArchive(TLogHelper * pLogger, HANDLE * phMpq, LPCTSTR PatchList[]) -{ - HANDLE hMpq = NULL; - TCHAR szFullPath[MAX_PATH]; - DWORD dwErrCode = ERROR_SUCCESS; - - // The first file is expected to be valid - assert(PatchList[0] != NULL); - - // Open the primary MPQ - CreateFullPathName(szFullPath, _countof(szFullPath), szMpqSubDir, PatchList[0]); - dwErrCode = OpenExistingArchive(pLogger, szFullPath, MPQ_OPEN_READ_ONLY, &hMpq); - - // Add all patches - if(dwErrCode == ERROR_SUCCESS) - { - for(size_t i = 1; PatchList[i] != NULL; i++) - { - CreateFullPathName(szFullPath, _countof(szFullPath), szMpqPatchDir, PatchList[i]); - dwErrCode = OpenPatchArchive(pLogger, hMpq, szFullPath); - if(dwErrCode != ERROR_SUCCESS) - break; - } - } - - // If anything failed, close the MPQ handle - if(dwErrCode != ERROR_SUCCESS) - { - SFileCloseArchive(hMpq); - hMpq = NULL; - } - - // Give the archive handle to the caller - if(phMpq != NULL) - *phMpq = hMpq; - return dwErrCode; -} - -static DWORD AddFileToMpq( - TLogHelper * pLogger, - HANDLE hMpq, - LPCSTR szFileName, - LPCSTR szFileData, - DWORD dwFlags = 0, - DWORD dwCompression = 0, - DWORD dwExpectedError = ERROR_SUCCESS) -{ - HANDLE hFile = NULL; - DWORD dwFileSize = (DWORD)strlen(szFileData); - DWORD dwErrCode = ERROR_SUCCESS; - - // Notify the user - pLogger->PrintProgress("Adding file %s ...", szFileName); - - // Get the default flags - if(dwFlags == 0) - dwFlags = MPQ_FILE_COMPRESS | MPQ_FILE_ENCRYPTED; - if(dwCompression == 0) - dwCompression = MPQ_COMPRESSION_ZLIB; - - // Create the file within the MPQ - if(SFileCreateFile(hMpq, szFileName, 0, dwFileSize, 0, dwFlags, &hFile)) - { - // Write the file - if(!SFileWriteFile(hFile, szFileData, dwFileSize, dwCompression)) - dwErrCode = pLogger->PrintError("Failed to write data to the MPQ"); - SFileCloseFile(hFile); - } - else - { - dwErrCode = GetLastError(); - } - - // Check the expected error code - if(dwExpectedError != ERROR_UNDETERMINED_RESULT && dwErrCode != dwExpectedError) - return pLogger->PrintError("Unexpected result from SFileCreateFile(%s)", szFileName); - return dwErrCode; -} - -static DWORD AddLocalFileToMpq( - TLogHelper * pLogger, - HANDLE hMpq, - LPCSTR szArchivedName, - LPCTSTR szFileFullName, - DWORD dwFlags = 0, - DWORD dwCompression = 0, - bool bMustSucceed = false) -{ - TCHAR szFileName[MAX_PATH]; - DWORD dwVerifyResult; - - // Notify the user - pLogger->PrintProgress("Adding file %s (%u of %u)...", GetShortPlainName(szFileFullName), pLogger->UserCount, pLogger->UserTotal); - pLogger->UserString = szArchivedName; - - // Get the default flags - if(dwFlags == 0) - dwFlags = MPQ_FILE_COMPRESS | MPQ_FILE_ENCRYPTED; - if(dwCompression == 0) - dwCompression = MPQ_COMPRESSION_ZLIB; - - // Set the notification callback - SFileSetAddFileCallback(hMpq, AddFileCallback, pLogger); - - // Add the file to the MPQ - StringCopy(szFileName, _countof(szFileName), szFileFullName); - if(!SFileAddFileEx(hMpq, szFileName, szArchivedName, dwFlags, dwCompression, MPQ_COMPRESSION_NEXT_SAME)) - { - if(bMustSucceed) - return pLogger->PrintError("Failed to add the file %s", szArchivedName); - return GetLastError(); - } - - // Verify the file unless it was lossy compression - if((dwCompression & (MPQ_COMPRESSION_ADPCM_MONO | MPQ_COMPRESSION_ADPCM_STEREO)) == 0) - { - // Notify the user - pLogger->PrintProgress("Verifying file %s (%u of %u) ...", szArchivedName, pLogger->UserCount, pLogger->UserTotal); - - // Perform the verification - dwVerifyResult = SFileVerifyFile(hMpq, szArchivedName, MPQ_ATTRIBUTE_CRC32 | MPQ_ATTRIBUTE_MD5); - if(dwVerifyResult & (VERIFY_OPEN_ERROR | VERIFY_READ_ERROR | VERIFY_FILE_SECTOR_CRC_ERROR | VERIFY_FILE_CHECKSUM_ERROR | VERIFY_FILE_MD5_ERROR)) - return pLogger->PrintError("CRC error on %s", szArchivedName); - } - - return ERROR_SUCCESS; -} - -static DWORD RenameMpqFile(TLogHelper * pLogger, HANDLE hMpq, LPCSTR szOldFileName, LPCSTR szNewFileName, DWORD dwExpectedError) -{ - DWORD dwErrCode = ERROR_SUCCESS; - - // Notify the user - pLogger->PrintProgress("Renaming %s to %s ...", szOldFileName, szNewFileName); - - // Perform the deletion - if(!SFileRenameFile(hMpq, szOldFileName, szNewFileName)) - dwErrCode = GetLastError(); - - if(dwErrCode != dwExpectedError) - return pLogger->PrintErrorVa("Unexpected result from SFileRenameFile(%s -> %s)", szOldFileName, szNewFileName); - return ERROR_SUCCESS; -} - -static DWORD RemoveMpqFile(TLogHelper * pLogger, HANDLE hMpq, LPCSTR szFileName, DWORD dwExpectedError) -{ - DWORD dwErrCode = ERROR_SUCCESS; - - // Notify the user - pLogger->PrintProgress("Removing file %s ...", szFileName); - - // Perform the deletion - if(!SFileRemoveFile(hMpq, szFileName, 0)) - dwErrCode = GetLastError(); - - if(dwErrCode != dwExpectedError) - return pLogger->PrintError("Unexpected result from SFileRemoveFile(%s)", szFileName); - return ERROR_SUCCESS; -} - -static ULONGLONG SFileGetFilePointer(HANDLE hFile) -{ - LONG FilePosHi = 0; - DWORD FilePosLo; - - FilePosLo = SFileSetFilePointer(hFile, 0, &FilePosHi, FILE_CURRENT); - return MAKE_OFFSET64(FilePosHi, FilePosLo); -} - -//----------------------------------------------------------------------------- -// Tests - -static DWORD TestSetFilePointer( - HANDLE hFile, - LONGLONG DeltaPos, - ULONGLONG ExpectedPos, - DWORD dwMoveMethod, - bool bUseFilePosHigh, - DWORD dwErrCode) -{ - ULONGLONG NewPos = 0; - LONG DeltaPosHi = (LONG)(DeltaPos >> 32); - LONG DeltaPosLo = (LONG)(DeltaPos); - - // If there was an error before, do nothing - if(dwErrCode == ERROR_SUCCESS) - { - SFileSetFilePointer(hFile, DeltaPosLo, bUseFilePosHigh ? &DeltaPosHi : NULL, dwMoveMethod); - NewPos = SFileGetFilePointer(hFile); - if(NewPos != ExpectedPos) - dwErrCode = ERROR_HANDLE_EOF; - } - - return dwErrCode; -} - -static DWORD TestSetFilePointers(HANDLE hFile, bool bUseFilePosHigh) -{ - LONGLONG FileSize; - DWORD dwErrCode = ERROR_SUCCESS; - - // We expect the file to be at least 2 pages long - FileSize = SFileGetFileSize(hFile, NULL); - if(FileSize < 0x2000) - return ERROR_NOT_SUPPORTED; - - // Move 0x20 bytes from the beginning. Expected new pos is 0x20 - dwErrCode = TestSetFilePointer(hFile, 0x20, 0x20, FILE_BEGIN, bUseFilePosHigh, dwErrCode); - - // Move 0x20 bytes from the current position. Expected new pos is 0x20 - dwErrCode = TestSetFilePointer(hFile, 0x20, 0x40, FILE_CURRENT, bUseFilePosHigh, dwErrCode); - - // Move 0x40 bytes back. Because the offset can't be moved to negative position, it will be zero - dwErrCode = TestSetFilePointer(hFile, -64, 0x00, FILE_CURRENT, bUseFilePosHigh, dwErrCode); - - // Move 0x40 bytes before the end of the file - dwErrCode = TestSetFilePointer(hFile, -64, FileSize-64, FILE_END, bUseFilePosHigh, dwErrCode); - - // Move 0x80 bytes forward. Should be at end of file - dwErrCode = TestSetFilePointer(hFile, 0x80, FileSize, FILE_CURRENT, bUseFilePosHigh, dwErrCode); - - return dwErrCode; -} - - -static void TestGetFileInfo( - TLogHelper * pLogger, - HANDLE hMpqOrFile, - SFileInfoClass InfoClass, - void * pvFileInfo, - DWORD cbFileInfo, - DWORD * pcbLengthNeeded, - bool bExpectedResult, - DWORD dwExpectedErrCode) -{ - DWORD dwErrCode = ERROR_SUCCESS; - bool bResult; - - // Call the get file info - bResult = SFileGetFileInfo(hMpqOrFile, InfoClass, pvFileInfo, cbFileInfo, pcbLengthNeeded); - if(!bResult) - dwErrCode = GetLastError(); - - if(bResult != bExpectedResult) - pLogger->PrintMessage("Different result of SFileGetFileInfo."); - if(dwErrCode != dwExpectedErrCode) - pLogger->PrintMessage("Different error from SFileGetFileInfo (expected %u, returned %u)", dwExpectedErrCode, dwErrCode); -} - -// StormLib is able to open local files (as well as the original Storm.dll) -// I want to keep this for occasional use - -static LINE_INFO Lines[] = -{ - {0x000, 18, "accountbilling.url"}, - {0x013, 45, "alternate/character/goblin/male/goblinmale.m2"}, - {0x9ab, 54, "alternate/character/goblin/male/goblinmale0186-00.anim"} -}; - -static DWORD TestOnLocalListFile_Read(TLogHelper & Logger, HANDLE hFile) -{ - for(size_t i = 0; i < _countof(Lines); i++) - { - DWORD dwBytesRead = 0; - char szFileLine[0x100] = {0}; - - SFileSetFilePointer(hFile, Lines[i].nLinePos, NULL, FILE_BEGIN); - SFileReadFile(hFile, szFileLine, Lines[i].nLineLen, &dwBytesRead, NULL); - - if(dwBytesRead != Lines[i].nLineLen) - { - Logger.PrintMessage("Line %u length mismatch", i); - return false; - } - - if(strcmp(szFileLine, Lines[i].szLine)) - { - Logger.PrintMessage("Line %u content mismatch", i); - return false; - } - } - - return true; -} - -static DWORD TestOnLocalListFile(LPCTSTR szPlainName) -{ - TLogHelper Logger("LocalListFile", szPlainName); - SFILE_FIND_DATA sf; - HANDLE hFile; - HANDLE hFind; - DWORD dwFileSizeHi = 0; - DWORD dwFileSizeLo = 0; - TCHAR szFullPath[MAX_PATH]; - char szFileName1[MAX_PATH]; - char szFileName2[MAX_PATH]; - int nFileCount = 0; - - // Get the full name of the local file - CreateFullPathName(szFileName1, _countof(szFileName1), szMpqSubDir, szPlainName); - - // Test opening the local file - if(SFileOpenFileEx(NULL, szFileName1, SFILE_OPEN_LOCAL_FILE, &hFile)) - { - // Retrieve the file name. It must match the name under which the file was open - if(FileStream_Prefix(szPlainName, NULL) == 0) - { - SFileGetFileName(hFile, szFileName2); - if(strcmp(szFileName2, szFileName1)) - Logger.PrintMessage("The retrieved name does not match the open name"); - } - - // Retrieve the file size - dwFileSizeLo = SFileGetFileSize(hFile, &dwFileSizeHi); - if(dwFileSizeHi != 0 || dwFileSizeLo != 0x04385a4e) - Logger.PrintMessage("Local file size mismatch"); - - // Read few lines, check their content - TestOnLocalListFile_Read(Logger, hFile); - SFileCloseFile(hFile); - } - else - return Logger.PrintError("Failed to open local listfile"); - - // We need unicode listfile name - StringCopy(szFullPath, _countof(szFullPath), szFileName1); - - // Start searching in the listfile - hFind = SListFileFindFirstFile(NULL, szFullPath, "*", &sf); - if(hFind != NULL) - { - for(;;) - { - Logger.PrintProgress("Found file (%04u): %s", nFileCount++, GetShortPlainName(sf.cFileName)); - if(!SListFileFindNextFile(hFind, &sf)) - break; - } - - SListFileFindClose(hFind); - } - else - return Logger.PrintError("Failed to search local listfile"); - - return ERROR_SUCCESS; -} - -static void WINAPI TestReadFile_DownloadCallback( - void * UserData, - ULONGLONG ByteOffset, - DWORD DataLength) -{ - TLogHelper * pLogger = (TLogHelper *)UserData; - - if(ByteOffset != 0 && DataLength != 0) - pLogger->PrintProgress("Downloading data (offset: " I64X_a ", length: %X)", ByteOffset, DataLength); - else - pLogger->PrintProgress("Download complete."); -} - -// Open a file stream with mirroring a master file -static DWORD TestReadFile_MasterMirror(LPCTSTR szMirrorName, LPCTSTR szMasterName, bool bCopyMirrorFile) -{ - TFileStream * pStream1; // Master file - TFileStream * pStream2; // Mirror file - TLogHelper Logger("OpenMirrorFile", szMirrorName); - TCHAR szMirrorPath[MAX_PATH + MAX_PATH]; - TCHAR szMasterPath[MAX_PATH]; - DWORD dwProvider = 0; - int nIterations = 0x10000; - DWORD dwErrCode; - - // Retrieve the provider - FileStream_Prefix(szMasterName, &dwProvider); - -#ifndef STORMLIB_WINDOWS - if((dwProvider & BASE_PROVIDER_MASK) == BASE_PROVIDER_HTTP) - return ERROR_SUCCESS; -#endif - - // Create copy of the file to serve as mirror, keep master there - dwErrCode = CreateMasterAndMirrorPaths(&Logger, szMirrorPath, szMasterPath, szMirrorName, szMasterName, bCopyMirrorFile); - if(dwErrCode == ERROR_SUCCESS) - { - // Open both master and mirror file - pStream1 = FileStream_OpenFile(szMasterPath, STREAM_FLAG_READ_ONLY); - pStream2 = FileStream_OpenFile(szMirrorPath, STREAM_FLAG_READ_ONLY | STREAM_FLAG_USE_BITMAP); - if(pStream1 && pStream2) - { - // For internet based files, we limit the number of operations - if((dwProvider & BASE_PROVIDER_MASK) == BASE_PROVIDER_HTTP) - nIterations = 0x80; - - FileStream_SetCallback(pStream2, TestReadFile_DownloadCallback, &Logger); - dwErrCode = CompareTwoLocalFilesRR(&Logger, pStream1, pStream2, nIterations); - } - - if(pStream2 != NULL) - FileStream_Close(pStream2); - if(pStream1 != NULL) - FileStream_Close(pStream1); - } - - return dwErrCode; -} - -// Test of the TFileStream object -static DWORD TestFileStreamOperations(LPCTSTR szPlainName, DWORD dwStreamFlags) -{ - TFileStream * pStream = NULL; - TLogHelper Logger("FileStreamTest", szPlainName); - ULONGLONG ByteOffset; - ULONGLONG FileSize = 0; - TCHAR szFullPath[MAX_PATH]; - DWORD dwRequiredFlags = 0; - BYTE Buffer[0x10]; - DWORD dwErrCode = ERROR_SUCCESS; - - // Copy the file so we won't screw up - if((dwStreamFlags & STREAM_PROVIDER_MASK) == STREAM_PROVIDER_BLOCK4) - CreateFullPathName(szFullPath, _countof(szFullPath), szMpqSubDir, szPlainName); - else - dwErrCode = CreateFileCopy(&Logger, szPlainName, szPlainName, szFullPath, _countof(szFullPath)); - - // Open the file stream - if(dwErrCode == ERROR_SUCCESS) - { - pStream = FileStream_OpenFile(szFullPath, dwStreamFlags); - if(pStream == NULL) - return Logger.PrintError(_T("Open failed: %s"), szFullPath); - } - - // Get the size of the file stream - if(dwErrCode == ERROR_SUCCESS) - { - if(!FileStream_GetFlags(pStream, &dwStreamFlags)) - dwErrCode = Logger.PrintError("Failed to retrieve the stream flags"); - - if(!FileStream_GetSize(pStream, &FileSize)) - dwErrCode = Logger.PrintError("Failed to retrieve the file size"); - - // Any other stream except STREAM_PROVIDER_FLAT | BASE_PROVIDER_FILE should be read-only - if((dwStreamFlags & STREAM_PROVIDERS_MASK) != (STREAM_PROVIDER_FLAT | BASE_PROVIDER_FILE)) - dwRequiredFlags |= STREAM_FLAG_READ_ONLY; -// if(pStream->BlockPresent) -// dwRequiredFlags |= STREAM_FLAG_READ_ONLY; - - // Check the flags there - if((dwStreamFlags & dwRequiredFlags) != dwRequiredFlags) - { - Logger.PrintMessage("The stream should be read-only but it isn't"); - dwErrCode = ERROR_FILE_CORRUPT; - } - } - - // After successful open, the stream position must be zero - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = VerifyFilePosition(&Logger, pStream, 0); - - // Read the MPQ header from the current file offset. - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = VerifyFileMpqHeader(&Logger, pStream, NULL); - - // After successful open, the stream position must sizeof(TMPQHeader) - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = VerifyFilePosition(&Logger, pStream, sizeof(TMPQHeader)); - - // Now try to read the MPQ header from the offset 0 - if(dwErrCode == ERROR_SUCCESS) - { - ByteOffset = 0; - dwErrCode = VerifyFileMpqHeader(&Logger, pStream, &ByteOffset); - } - - // After successful open, the stream position must sizeof(TMPQHeader) - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = VerifyFilePosition(&Logger, pStream, sizeof(TMPQHeader)); - - // Try a write operation - if(dwErrCode == ERROR_SUCCESS) - { - bool bExpectedResult = (dwStreamFlags & STREAM_FLAG_READ_ONLY) ? false : true; - bool bResult; - - // Attempt to write to the file - ByteOffset = 0; - bResult = FileStream_Write(pStream, &ByteOffset, Buffer, sizeof(Buffer)); - - // If the result is not expected - if(bResult != bExpectedResult) - { - Logger.PrintMessage("FileStream_Write result is different than expected"); - dwErrCode = ERROR_FILE_CORRUPT; - } - } - - // Move the position 9 bytes from the end and try to read 10 bytes. - // This must fail, because stream reading functions are "all or nothing" - if(dwErrCode == ERROR_SUCCESS) - { - ByteOffset = FileSize - 9; - if(FileStream_Read(pStream, &ByteOffset, Buffer, 10)) - { - Logger.PrintMessage("FileStream_Read succeeded, but it shouldn't"); - dwErrCode = ERROR_FILE_CORRUPT; - } - } - - // Try again with 9 bytes. This must succeed, unless the file block is not available - if(dwErrCode == ERROR_SUCCESS) - { - ByteOffset = FileSize - 9; - if(!FileStream_Read(pStream, &ByteOffset, Buffer, 9)) - { - Logger.PrintMessage("FileStream_Read from the end of the file failed"); - dwErrCode = ERROR_FILE_CORRUPT; - } - } - - // Verify file position - it must be at the end of the file - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = VerifyFilePosition(&Logger, pStream, FileSize); - - // Close the stream - if(pStream != NULL) - FileStream_Close(pStream); - return dwErrCode; -} - -static DWORD TestArchive_LoadFiles(TLogHelper * pLogger, HANDLE hMpq, bool bIgnoreOpedwErrCodes, ...) -{ - TFileData * pFileData; - const char * szFileName; - va_list argList; - DWORD dwErrCode = ERROR_SUCCESS; - - va_start(argList, bIgnoreOpedwErrCodes); - while((szFileName = va_arg(argList, const char *)) != NULL) - { - if(SFileHasFile(hMpq, szFileName)) - { - pFileData = LoadMpqFile(pLogger, hMpq, szFileName); - if(pFileData == NULL && bIgnoreOpedwErrCodes == false) - { - pLogger->PrintError("Error loading the file %s", szFileName); - dwErrCode = ERROR_FILE_CORRUPT; - break; - } - else - { - STORM_FREE(pFileData); - pFileData = NULL; - } - } - } - va_end(argList); - - return dwErrCode; -} - -static DWORD TestArchive_SetPos(HANDLE hMpq, const char * szFileName) -{ - HANDLE hFile = NULL; - DWORD dwErrCode = ERROR_SUCCESS; - - if(SFileOpenFileEx(hMpq, szFileName, 0, &hFile)) - { - // First, use the SFileSetFilePointer WITHOUT the high-dword position - dwErrCode = TestSetFilePointers(hFile, false); - - // First, use the SFileSetFilePointer WITH the high-dword position - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestSetFilePointers(hFile, true); - - // Close the file - SFileCloseFile(hFile); - } - - return dwErrCode; -} - -static DWORD TestArchive( - LPCTSTR szPlainName, // Plain name of the MPQ - LPCTSTR szListFile, // Listfile name (NULL if none) - DWORD dwFlags, // Flags - LPCSTR szParam1, - LPCSTR szParam2) -{ - TFileData * FileDataList[2] = {NULL}; - TLogHelper Logger("TestMpq", szPlainName); - LPCSTR FileNameList[2] = {NULL}; - LPCSTR szExpectedMD5 = NULL; - HANDLE hMpq = NULL; - DWORD dwFileCount = 0; - DWORD dwSearchFlags = 0; - DWORD dwErrCode; - DWORD dwCrc32 = 0; - DWORD dwExpectedFileCount = 0; - DWORD dwMpqFlags = 0; - TCHAR szFullName[MAX_PATH]; - LCID lcFileLocale = 0; - BYTE ObtainedMD5[MD5_DIGEST_SIZE] = {0}; - bool bIgnoreOpedwErrCodes = false; - - // If the file is a partial MPQ, don't load all files - if(_tcsstr(szPlainName, _T(".MPQ.part")) == NULL) - dwSearchFlags |= SEARCH_FLAG_LOAD_FILES; - - // If the MPQ is a protected MPQ, do different tests - if(dwFlags & TFLG_COUNT_HASH) - { - if((szExpectedMD5 = szParam1) != NULL) - dwSearchFlags |= SEARCH_FLAG_HASH_FILES; - dwExpectedFileCount = (dwFlags & TFLG_VALUE_MASK); - szParam1 = NULL; - } - - // If locale entered - if(dwFlags & TFLG_FILE_LOCALE) - { - lcFileLocale = (LCID)(dwFlags & TFLG_VALUE_MASK); - } - - // Put all file names into list - FileNameList[0] = szParam1; - FileNameList[1] = szParam2; - - // Copy the archive so we won't fuck up the original one - dwErrCode = OpenExistingArchiveWithCopy(&Logger, szPlainName, NULL, &hMpq); - while(dwErrCode == ERROR_SUCCESS) - { - // Check for malformed MPQs - SFileGetFileInfo(hMpq, SFileMpqFlags, &dwMpqFlags, sizeof(dwMpqFlags), NULL); - if(dwMpqFlags & MPQ_FLAG_MALFORMED) - { - dwSearchFlags |= SEARCH_FLAG_IGNORE_ERRORS; - bIgnoreOpedwErrCodes = true; - } - - // If the listfile was given, add it to the MPQ - if(szListFile && szListFile[0]) - { - Logger.PrintProgress(_T("Adding listfile %s ..."), szListFile); - CreateFullPathName(szFullName, _countof(szFullName), szListFileDir, szListFile); - if((dwErrCode = SFileAddListFile(hMpq, szFullName)) != ERROR_SUCCESS) - Logger.PrintMessage("Failed to add the listfile to the MPQ"); - } - - // Attempt to open the (listfile), (attributes), (signature) - dwErrCode = TestArchive_LoadFiles(&Logger, hMpq, bIgnoreOpedwErrCodes, LISTFILE_NAME, ATTRIBUTES_NAME, SIGNATURE_NAME, NULL); - if(dwErrCode != ERROR_SUCCESS) - break; - - // For every file name given, load it and check its CRC - for(size_t i = 0; i < _countof(FileNameList); i++) - { - TFileData * pFileData; - LPCSTR szFileName = FileNameList[i]; - - if(szFileName && szFileName[0]) - { - // Test setting position - dwErrCode = TestArchive_SetPos(hMpq, szFileName); - if(dwErrCode != ERROR_SUCCESS) - break; - - // Load the entire file 1 - FileDataList[i] = pFileData = LoadMpqFile(&Logger, hMpq, szFileName, lcFileLocale); - if(pFileData == NULL) - { - dwErrCode = Logger.PrintError("Failed to load the file %s", szFileName); - break; - } - - // Check the CRC of file1, if available - if(pFileData->dwCrc32) - { - // Compare the CRC32, if available - dwCrc32 = crc32(0, (Bytef *)pFileData->FileData, (uInt)pFileData->dwFileSize); - if(dwCrc32 != pFileData->dwCrc32) - Logger.PrintError("Warning: CRC32 error on %s", szFileName); - } - -#ifdef _DEBUG -/* - FILE * fp = fopen("e:\\out_file.wav", "wb"); - if(fp) - { - fwrite(pFileData->FileData, 1, pFileData->dwFileSize, fp); - fclose(fp); - } -*/ -#endif - } - } - - // If two files were given, compare them - if(FileDataList[0] && FileDataList[1]) - { - // Compare both files - if(!CompareTwoFiles(&Logger, FileDataList[0], FileDataList[1])) - { - dwErrCode = Logger.PrintError("The file has different size/content of files"); - break; - } - } - - // Search the archive - dwErrCode = SearchArchive(&Logger, hMpq, dwSearchFlags, &dwFileCount, ObtainedMD5); - - // Shall we check the file count and overall MD5? - if(dwFlags & TFLG_COUNT_HASH) - { - if(dwFileCount != dwExpectedFileCount) - { - Logger.PrintMessage("File count mismatch(expected: %u, found: %u)", dwExpectedFileCount, dwFileCount); - dwErrCode = ERROR_CAN_NOT_COMPLETE; - } - } - - // Shall we check overall MD5? - if(szExpectedMD5 && szExpectedMD5[0]) - { - char szObtainedMD5[0x40]; - - StringFromBinary(ObtainedMD5, MD5_DIGEST_SIZE, szObtainedMD5); - if(_stricmp(szObtainedMD5, szExpectedMD5)) - { - Logger.PrintMessage("Extracted files MD5 mismatch (expected: %s, obtained: %s)", szExpectedMD5, szObtainedMD5); - dwErrCode = ERROR_CAN_NOT_COMPLETE; - } - } - break; - } - - // Common cleanup - if(FileDataList[1] != NULL) - STORM_FREE(FileDataList[1]); - if(FileDataList[0] != NULL) - STORM_FREE(FileDataList[0]); - if(hMpq != NULL) - SFileCloseArchive(hMpq); - return Logger.PrintVerdict(dwErrCode); -} - -// Open an empty archive (found in WoW cache - it's just a header) -static DWORD TestOpenArchive_WillFail(LPCTSTR szPlainName) -{ - TLogHelper Logger("FailMpqTest", szPlainName); - HANDLE hMpq = NULL; - TCHAR szMpqName[MAX_PATH]; - char szFullPath[MAX_PATH]; - - // Create the full path name for the archive - CreateFullPathName(szFullPath, _countof(szFullPath), szMpqSubDir, szPlainName); - StringCopy(szMpqName, _countof(szFullPath), szFullPath); - - // Try to open the archive. It is expected to fail - Logger.PrintProgress("Opening archive %s", szPlainName); - if(!SFileOpenArchive(szMpqName, 0, MPQ_OPEN_READ_ONLY, &hMpq)) - return ERROR_SUCCESS; - - Logger.PrintError(_T("Archive %s succeeded to open, even if it should not."), szPlainName); - SFileCloseArchive(hMpq); - return ERROR_CAN_NOT_COMPLETE; -} - -static DWORD TestOpenArchive_Corrupt(LPCTSTR szPlainName) -{ - TLogHelper Logger("OpenCorruptMpqTest", szPlainName); - HANDLE hMpq = NULL; - TCHAR szFullPath[MAX_PATH]; - - // Copy the archive so we won't fuck up the original one - CreateFullPathName(szFullPath, _countof(szFullPath), szMpqSubDir, szPlainName); - if(SFileOpenArchive(szFullPath, 0, STREAM_FLAG_READ_ONLY, &hMpq)) - { - SFileCloseArchive(hMpq); - Logger.PrintMessage(_T("Opening archive %s succeeded, but it shouldn't"), szFullPath); - return ERROR_CAN_NOT_COMPLETE; - } - - return ERROR_SUCCESS; -} - - -// Opens a patched MPQ archive -static DWORD TestArchive_Patched(LPCTSTR PatchList[], LPCSTR szPatchedFile, DWORD dwFlags) -{ - TLogHelper Logger("PatchedMPQ", PatchList[0]); - HANDLE hMpq; - HANDLE hFile; - BYTE Buffer[0x100]; - DWORD dwExpectedPatchCount = (dwFlags & TFLG_VALUE_MASK); - DWORD dwFileCount = 0; - DWORD BytesRead = 0; - DWORD dwErrCode; - bool bExpectedToFail = (dwFlags & TFLG_WILL_FAIL) ? true : false; - - // Open a patched MPQ archive - dwErrCode = OpenPatchedArchive(&Logger, &hMpq, PatchList); - if(dwErrCode == ERROR_SUCCESS) - { - // Check patch count - if(szPatchedFile != NULL) - dwErrCode = VerifyFilePatchCount(&Logger, hMpq, szPatchedFile, dwExpectedPatchCount); - - // Try to open and read the file - if(dwErrCode == ERROR_SUCCESS) - { - if(SFileOpenFileEx(hMpq, szPatchedFile, 0, &hFile)) - { - SFileReadFile(hFile, Buffer, sizeof(Buffer), &BytesRead, NULL); - SFileCloseFile(hFile); - } - } - - // Search the archive and load every file - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = SearchArchive(&Logger, hMpq, SEARCH_FLAG_LOAD_FILES | SEARCH_FLAG_IGNORE_ERRORS, &dwFileCount); - - // Close the archive - SFileCloseArchive(hMpq); - } - - // Clear the error if patch prefix was not found - if(dwErrCode == ERROR_CANT_FIND_PATCH_PREFIX && bExpectedToFail) - dwErrCode = ERROR_SUCCESS; - return dwErrCode; -} - -// Open an archive for read-only access -static DWORD TestOpenArchive_ReadOnly(LPCTSTR szPlainName, bool bReadOnly) -{ - TLogHelper Logger("ReadOnlyTest", szPlainName); - LPCTSTR szCopyName; - HANDLE hMpq = NULL; - TCHAR szFullPath[MAX_PATH]; - DWORD dwFlags = bReadOnly ? MPQ_OPEN_READ_ONLY : 0;; - int nExpectedError; - DWORD dwErrCode; - - // Copy the fiel so we wont screw up something - szCopyName = bReadOnly ? _T("StormLibTest_ReadOnly.mpq") : _T("StormLibTest_ReadWrite.mpq"); - dwErrCode = CreateFileCopy(&Logger, szPlainName, szCopyName, szFullPath, _countof(szFullPath)); - - // Now open the archive for read-only access - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = OpenExistingArchive(&Logger, szFullPath, dwFlags, &hMpq); - - // Now try to add a file. This must fail if the MPQ is read only - if(dwErrCode == ERROR_SUCCESS) - { - nExpectedError = (bReadOnly) ? ERROR_ACCESS_DENIED : ERROR_SUCCESS; - AddFileToMpq(&Logger, hMpq, "AddedFile.txt", "This is an added file.", MPQ_FILE_COMPRESS | MPQ_FILE_ENCRYPTED, 0, nExpectedError); - } - - // Now try to rename a file in the MPQ. This must only succeed if the MPQ is not read only - if(dwErrCode == ERROR_SUCCESS) - { - nExpectedError = (bReadOnly) ? ERROR_ACCESS_DENIED : ERROR_SUCCESS; - RenameMpqFile(&Logger, hMpq, "spawn.mpq", "spawn-renamed.mpq", nExpectedError); - } - - // Now try to delete a file in the MPQ. This must only succeed if the MPQ is not read only - if(dwErrCode == ERROR_SUCCESS) - { - nExpectedError = (bReadOnly) ? ERROR_ACCESS_DENIED : ERROR_SUCCESS; - RemoveMpqFile(&Logger, hMpq, "spawn-renamed.mpq", nExpectedError); - } - - // Close the archive - if(hMpq != NULL) - SFileCloseArchive(hMpq); - return dwErrCode; -} - -static DWORD TestOpenArchive_GetFileInfo(LPCTSTR szPlainName1, LPCTSTR szPlainName4) -{ - TLogHelper Logger("GetFileInfoTest", szPlainName1, szPlainName4); - HANDLE hFile; - HANDLE hMpq4; - HANDLE hMpq1; - DWORD cbLength; - BYTE DataBuff[0x400]; - DWORD dwErrCode1; - DWORD dwErrCode4; - - // Copy the archive so we won't fuck up the original one - dwErrCode1 = OpenExistingArchiveWithCopy(&Logger, szPlainName1, NULL, &hMpq1); - dwErrCode4 = OpenExistingArchiveWithCopy(&Logger, szPlainName4, NULL, &hMpq4); - if(dwErrCode1 == ERROR_SUCCESS && dwErrCode4 == ERROR_SUCCESS) - { - // Invalid handle - expected (false, ERROR_INVALID_HANDLE) - TestGetFileInfo(&Logger, NULL, SFileMpqBetHeader, NULL, 0, NULL, false, ERROR_INVALID_HANDLE); - - // Valid handle but invalid value of file info class (false, ERROR_INVALID_PARAMETER) - TestGetFileInfo(&Logger, NULL, (SFileInfoClass)0xFFF, NULL, 0, NULL, false, ERROR_INVALID_HANDLE); - - // Invalid archive handle and file info class is for file (false, ERROR_INVALID_HANDLE) - TestGetFileInfo(&Logger, NULL, SFileInfoNameHash1, NULL, 0, NULL, false, ERROR_INVALID_HANDLE); - - // Valid handle and all parameters NULL - // Returns (true, ERROR_SUCCESS), if BET table is present, otherwise (false, ERROR_FILE_NOT_FOUND) - TestGetFileInfo(&Logger, hMpq1, SFileMpqBetHeader, NULL, 0, NULL, false, ERROR_FILE_NOT_FOUND); - TestGetFileInfo(&Logger, hMpq4, SFileMpqBetHeader, NULL, 0, NULL, false, ERROR_INSUFFICIENT_BUFFER); - - // Now try to retrieve the required size of the BET table header - TestGetFileInfo(&Logger, hMpq4, SFileMpqBetHeader, NULL, 0, &cbLength, false, ERROR_INSUFFICIENT_BUFFER); - - // When we call SFileInfo with buffer = NULL and nonzero buffer size, it is ignored - TestGetFileInfo(&Logger, hMpq4, SFileMpqBetHeader, NULL, 3, &cbLength, false, ERROR_INSUFFICIENT_BUFFER); - - // When we call SFileInfo with buffer != NULL and nonzero buffer size, it should return error - TestGetFileInfo(&Logger, hMpq4, SFileMpqBetHeader, DataBuff, 3, &cbLength, false, ERROR_INSUFFICIENT_BUFFER); - - // Request for bet table header should also succeed if we want header only - TestGetFileInfo(&Logger, hMpq4, SFileMpqBetHeader, DataBuff, sizeof(TMPQBetHeader), &cbLength, true, ERROR_SUCCESS); - - // Request for bet table header should also succeed if we want header+flag table only - TestGetFileInfo(&Logger, hMpq4, SFileMpqBetHeader, DataBuff, sizeof(DataBuff), &cbLength, true, ERROR_SUCCESS); - - // Try to retrieve strong signature from the MPQ - TestGetFileInfo(&Logger, hMpq1, SFileMpqStrongSignature, NULL, 0, NULL, false, ERROR_INSUFFICIENT_BUFFER); - TestGetFileInfo(&Logger, hMpq4, SFileMpqStrongSignature, NULL, 0, NULL, false, ERROR_FILE_NOT_FOUND); - - // Strong signature is returned including the signature ID - TestGetFileInfo(&Logger, hMpq1, SFileMpqStrongSignature, NULL, 0, &cbLength, false, ERROR_INSUFFICIENT_BUFFER); - assert(cbLength == MPQ_STRONG_SIGNATURE_SIZE + 4); - - // Retrieve the signature - TestGetFileInfo(&Logger, hMpq1, SFileMpqStrongSignature, DataBuff, sizeof(DataBuff), &cbLength, true, ERROR_SUCCESS); - assert(memcmp(DataBuff, "NGIS", 4) == 0); - - // Check SFileGetFileInfo on - if(SFileOpenFileEx(hMpq4, LISTFILE_NAME, 0, &hFile)) - { - // Valid parameters but the handle should be file handle - TestGetFileInfo(&Logger, hMpq4, SFileInfoFileTime, DataBuff, sizeof(DataBuff), &cbLength, false, ERROR_INVALID_HANDLE); - - // Valid parameters - TestGetFileInfo(&Logger, hFile, SFileInfoFileTime, DataBuff, sizeof(DataBuff), &cbLength, true, ERROR_SUCCESS); - - SFileCloseFile(hFile); - } - } - - if(hMpq4 != NULL) - SFileCloseArchive(hMpq4); - if(hMpq1 != NULL) - SFileCloseArchive(hMpq1); - return ERROR_SUCCESS; -} - -static DWORD TestOpenArchive_MasterMirror(LPCTSTR szMirrorName, LPCTSTR szMasterName, LPCSTR szFileToExtract, bool bCopyMirrorFile) -{ - TFileData * pFileData; - TLogHelper Logger("OpenServerMirror", szMirrorName); - HANDLE hFile = NULL; - HANDLE hMpq = NULL; - DWORD dwVerifyResult; - TCHAR szMirrorPath[MAX_PATH + MAX_PATH]; // Combined name - TCHAR szMasterPath[MAX_PATH]; // Original (server) name - DWORD dwErrCode; - - // Create both paths - dwErrCode = CreateMasterAndMirrorPaths(&Logger, szMirrorPath, szMasterPath, szMirrorName, szMasterName, bCopyMirrorFile); - - // Now open both archives as local-server pair - if(dwErrCode == ERROR_SUCCESS) - { - dwErrCode = OpenExistingArchive(&Logger, szMirrorPath, 0, &hMpq); - } - - // The MPQ must be read-only. Writing to mirrored MPQ is not allowed - if(dwErrCode == ERROR_SUCCESS) - { - if(SFileCreateFile(hMpq, "AddedFile.bin", 0, 0x10, 0, MPQ_FILE_COMPRESS, &hFile)) - { - SFileCloseFile(hFile); - Logger.PrintMessage("The archive is writable, although it should not be"); - dwErrCode = ERROR_FILE_CORRUPT; - } - } - - // Verify the file - if(dwErrCode == ERROR_SUCCESS && szFileToExtract != NULL) - { - dwVerifyResult = SFileVerifyFile(hMpq, szFileToExtract, SFILE_VERIFY_ALL); - if(dwVerifyResult & VERIFY_FILE_ERROR_MASK) - { - Logger.PrintMessage("File verification failed"); - dwErrCode = ERROR_FILE_CORRUPT; - } - } - - // Load the file to memory - if(dwErrCode == ERROR_SUCCESS && szFileToExtract) - { - pFileData = LoadMpqFile(&Logger, hMpq, szFileToExtract); - if(pFileData != NULL) - STORM_FREE(pFileData); - } - - if(hMpq != NULL) - SFileCloseArchive(hMpq); - return dwErrCode; -} - - -static DWORD TestOpenArchive_VerifySignature(LPCTSTR szPlainName, LPCTSTR szOriginalName) -{ - TLogHelper Logger("VerifySignatureTest", szPlainName); - HANDLE hMpq; - DWORD dwSignatures = 0; - DWORD dwErrCode = ERROR_SUCCESS; - int nVerifyError; - - // We need original name for the signature check - dwErrCode = OpenExistingArchiveWithCopy(&Logger, szPlainName, szOriginalName, &hMpq); - if(dwErrCode == ERROR_SUCCESS) - { - // Query the signature types - Logger.PrintProgress("Retrieving signatures ..."); - TestGetFileInfo(&Logger, hMpq, SFileMpqSignatures, &dwSignatures, sizeof(DWORD), NULL, true, ERROR_SUCCESS); - - // Verify any of the present signatures - Logger.PrintProgress("Verifying archive signature ..."); - nVerifyError = SFileVerifyArchive(hMpq); - - // Verify the result - if((dwSignatures & SIGNATURE_TYPE_STRONG) && (nVerifyError != ERROR_STRONG_SIGNATURE_OK)) - { - Logger.PrintMessage("Strong signature verification error"); - dwErrCode = ERROR_FILE_CORRUPT; - } - - // Verify the result - if((dwSignatures & SIGNATURE_TYPE_WEAK) && (nVerifyError != ERROR_WEAK_SIGNATURE_OK)) - { - Logger.PrintMessage("Weak signature verification error"); - dwErrCode = ERROR_FILE_CORRUPT; - } - - SFileCloseArchive(hMpq); - } - return dwErrCode; -} - -static DWORD TestOpenArchive_ModifySigned(LPCTSTR szPlainName, LPCTSTR szOriginalName) -{ - TLogHelper Logger("ModifySignedTest", szPlainName); - HANDLE hMpq = NULL; - int nVerifyError; - DWORD dwErrCode = ERROR_SUCCESS; - - // We need original name for the signature check - dwErrCode = OpenExistingArchiveWithCopy(&Logger, szPlainName, szOriginalName, &hMpq); - if(dwErrCode == ERROR_SUCCESS) - { - // Verify the weak signature - Logger.PrintProgress("Verifying archive signature ..."); - nVerifyError = SFileVerifyArchive(hMpq); - - // Check the result signature - if(nVerifyError != ERROR_WEAK_SIGNATURE_OK) - { - Logger.PrintMessage("Weak signature verification error"); - dwErrCode = ERROR_FILE_CORRUPT; - } - } - - // Add a file and verify the signature again - if(dwErrCode == ERROR_SUCCESS) - { - // Verify any of the present signatures - Logger.PrintProgress("Modifying signed archive ..."); - dwErrCode = AddFileToMpq(&Logger, hMpq, "AddedFile01.txt", "This is a file added to signed MPQ", 0, 0, ERROR_SUCCESS); - } - - // Verify the signature again - if(dwErrCode == ERROR_SUCCESS) - { - // Verify the weak signature - Logger.PrintProgress("Verifying archive signature ..."); - nVerifyError = SFileVerifyArchive(hMpq); - - // Check the result signature - if(nVerifyError != ERROR_WEAK_SIGNATURE_OK) - { - Logger.PrintMessage("Weak signature verification error"); - dwErrCode = ERROR_FILE_CORRUPT; - } - } - - // Close the MPQ - if(hMpq != NULL) - SFileCloseArchive(hMpq); - return dwErrCode; -} - -static DWORD TestOpenArchive_SignExisting(LPCTSTR szPlainName) -{ - TLogHelper Logger("SignExistingMpq", szPlainName); - HANDLE hMpq = NULL; - int nVerifyError; - DWORD dwErrCode = ERROR_SUCCESS; - - // We need original name for the signature check - dwErrCode = OpenExistingArchiveWithCopy(&Logger, szPlainName, szPlainName, &hMpq); - if(dwErrCode == ERROR_SUCCESS) - { - // Verify the weak signature - Logger.PrintProgress("Verifying archive signature ..."); - nVerifyError = SFileVerifyArchive(hMpq); - - // Check the result signature - if(nVerifyError != ERROR_NO_SIGNATURE) - { - Logger.PrintMessage("There already is a signature in the MPQ"); - dwErrCode = ERROR_FILE_CORRUPT; - } - } - - // Add a file and verify the signature again - if(dwErrCode == ERROR_SUCCESS) - { - // Verify any of the present signatures - Logger.PrintProgress("Signing the MPQ ..."); - if(!SFileSignArchive(hMpq, SIGNATURE_TYPE_WEAK)) - { - Logger.PrintMessage("Failed to create archive signature"); - dwErrCode = ERROR_FILE_CORRUPT; - } - } - - // Verify the signature again - if(dwErrCode == ERROR_SUCCESS) - { - // Verify the weak signature - Logger.PrintProgress("Verifying archive signature ..."); - nVerifyError = SFileVerifyArchive(hMpq); - - // Check the result signature - if(nVerifyError != ERROR_WEAK_SIGNATURE_OK) - { - Logger.PrintMessage("Weak signature verification error"); - dwErrCode = ERROR_FILE_CORRUPT; - } - } - - // Close the MPQ - if(hMpq != NULL) - SFileCloseArchive(hMpq); - return dwErrCode; -} - -static DWORD TestOpenArchive_CompactArchive(LPCTSTR szPlainName, LPCTSTR szCopyName, bool bAddUserData) -{ - TLogHelper Logger("CompactMpqTest", szPlainName); - ULONGLONG PreMpqDataSize = (bAddUserData) ? 0x400 : 0; - ULONGLONG UserDataSize = (bAddUserData) ? 0x531 : 0; - HANDLE hMpq; - DWORD dwFileCount1 = 0; - DWORD dwFileCount2 = 0; - TCHAR szFullPath[MAX_PATH]; - BYTE FileHash1[MD5_DIGEST_SIZE]; - BYTE FileHash2[MD5_DIGEST_SIZE]; - DWORD dwErrCode; - - // Create copy of the archive, with interleaving some user data - dwErrCode = CreateFileCopy(&Logger, szPlainName, szCopyName, szFullPath, _countof(szFullPath), PreMpqDataSize, UserDataSize); - - // Open the archive and load some files - if(dwErrCode == ERROR_SUCCESS) - { - // Open the archive - dwErrCode = OpenExistingArchive(&Logger, szFullPath, 0, &hMpq); - if(dwErrCode != ERROR_SUCCESS) - return dwErrCode; - - // Verify presence of (listfile) and (attributes) - CheckIfFileIsPresent(&Logger, hMpq, LISTFILE_NAME, true); - CheckIfFileIsPresent(&Logger, hMpq, ATTRIBUTES_NAME, true); - - // Search the archive and load every file - dwErrCode = SearchArchive(&Logger, hMpq, SEARCH_FLAG_LOAD_FILES | SEARCH_FLAG_HASH_FILES, &dwFileCount1, FileHash1); - SFileCloseArchive(hMpq); - } - - // Try to compact the MPQ - if(dwErrCode == ERROR_SUCCESS) - { - // Open the archive again - dwErrCode = OpenExistingArchive(&Logger, szFullPath, 0, &hMpq); - if(dwErrCode != ERROR_SUCCESS) - return dwErrCode; - - // Compact the archive - Logger.PrintProgress("Compacting archive %s ...", GetShortPlainName(szFullPath)); - if(!SFileSetCompactCallback(hMpq, CompactCallback, &Logger)) - dwErrCode = Logger.PrintError(_T("Failed to compact archive %s"), szFullPath); - - SFileCompactArchive(hMpq, NULL, false); - SFileCloseArchive(hMpq); - } - - // Open the archive and load some files - if(dwErrCode == ERROR_SUCCESS) - { - // Open the archive - dwErrCode = OpenExistingArchive(&Logger, szFullPath, 0, &hMpq); - if(dwErrCode != ERROR_SUCCESS) - return dwErrCode; - - // Verify presence of (listfile) and (attributes) - CheckIfFileIsPresent(&Logger, hMpq, LISTFILE_NAME, true); - CheckIfFileIsPresent(&Logger, hMpq, ATTRIBUTES_NAME, true); - - // Search the archive and load every file - dwErrCode = SearchArchive(&Logger, hMpq, SEARCH_FLAG_LOAD_FILES | SEARCH_FLAG_HASH_FILES, &dwFileCount2, FileHash2); - SFileCloseArchive(hMpq); - } - - // Compare the file counts and their hashes - if(dwErrCode == ERROR_SUCCESS) - { - if(dwFileCount2 != dwFileCount1) - Logger.PrintMessage("Different file count after compacting archive: %u vs %u", dwFileCount2, dwFileCount1); - - if(memcmp(FileHash2, FileHash1, MD5_DIGEST_SIZE)) - Logger.PrintMessage("Different file hash after compacting archive"); - } - - return dwErrCode; -} - -static DWORD ForEachFile_VerifyFileChecksum(LPCTSTR szFullPath) -{ - TFileData * pFileData; - TCHAR * szExtension; - TCHAR szShaFileName[MAX_PATH+1]; - TCHAR szSha1Text[0x40]; - char szSha1TextA[0x40]; - DWORD dwErrCode = ERROR_SUCCESS; - - // Try to load the file with the SHA extension - StringCopy(szShaFileName, _countof(szShaFileName), szFullPath); - szExtension = _tcsrchr(szShaFileName, '.'); - if(szExtension == NULL) - return ERROR_SUCCESS; - - // Skip .SHA and .TXT files - if(!_tcsicmp(szExtension, _T(".sha")) || !_tcsicmp(szExtension, _T(".txt"))) - return ERROR_SUCCESS; - - // Load the local file to memory - _tcscpy(szExtension, _T(".sha")); - pFileData = LoadLocalFile(NULL, szShaFileName, false); - if(pFileData != NULL) - { - TLogHelper Logger("VerifyFileHash"); - - // Calculate SHA1 of the entire file - dwErrCode = CalculateFileSha1(&Logger, szFullPath, szSha1Text); - if(dwErrCode == ERROR_SUCCESS) - { - // Compare with what we loaded from the file - if(pFileData->dwFileSize >= (SHA1_DIGEST_SIZE * 2)) - { - // Compare the SHA1 - StringCopy(szSha1TextA, _countof(szSha1TextA), szSha1Text); - if(_strnicmp(szSha1TextA, (char *)pFileData->FileData, (SHA1_DIGEST_SIZE * 2))) - { - SetLastError(dwErrCode = ERROR_FILE_CORRUPT); - Logger.PrintError(_T("File CRC check failed: %s"), szFullPath); - } - } - } - - STORM_FREE(pFileData); - } - - return dwErrCode; -} - -// Opens a found archive -static DWORD ForEachFile_OpenArchive(LPCTSTR szFullPath) -{ - HANDLE hMpq = NULL; - DWORD dwFileCount = 0; - DWORD dwErrCode = ERROR_SUCCESS; - - // Check if it's a MPQ file type - if(IsMpqExtension(szFullPath)) - { - TLogHelper Logger("OpenEachMpqTest", GetShortPlainName(szFullPath)); - - // Open the MPQ name - dwErrCode = OpenExistingArchive(&Logger, szFullPath, 0, &hMpq); - if(dwErrCode == ERROR_AVI_FILE || dwErrCode == ERROR_FILE_CORRUPT || dwErrCode == ERROR_BAD_FORMAT) - return ERROR_SUCCESS; - - // Search the archive and load every file - if(dwErrCode == ERROR_SUCCESS) - { - dwErrCode = SearchArchive(&Logger, hMpq, 0, &dwFileCount); - SFileCloseArchive(hMpq); - } - - // Show warning if no files found - if(dwFileCount == 0) - { - Logger.PrintMessage("Warning: no files in the archive"); - } - } - - // Correct some errors - if(dwErrCode == ERROR_FILE_CORRUPT || dwErrCode == ERROR_FILE_INCOMPLETE) - return ERROR_SUCCESS; - return dwErrCode; -} - -// Adding a file to MPQ that had size of the file table equal -// or greater than hash table, but has free entries -static DWORD TestAddFile_FullTable(LPCTSTR szFullMpqName) -{ - TLogHelper Logger("FullMpqTest", szFullMpqName); - LPCSTR szFileName = "AddedFile001.txt"; - LPCSTR szFileData = "0123456789ABCDEF"; - HANDLE hMpq = NULL; - DWORD dwErrCode = ERROR_SUCCESS; - - // Copy the archive so we won't fuck up the original one - dwErrCode = OpenExistingArchiveWithCopy(&Logger, szFullMpqName, szFullMpqName, &hMpq); - if(dwErrCode == ERROR_SUCCESS) - { - // Attempt to add a file - dwErrCode = AddFileToMpq(&Logger, hMpq, szFileName, szFileData, MPQ_FILE_IMPLODE, MPQ_COMPRESSION_PKWARE, ERROR_SUCCESS); - SFileCloseArchive(hMpq); - } - - return dwErrCode; -} - -// Adding a file to MPQ that had no (listfile) and no (attributes). -// We expect that neither of these will be present after the archive is closed -static DWORD TestAddFile_ListFileTest(LPCTSTR szSourceMpq, bool bShouldHaveListFile, bool bShouldHaveAttributes) -{ - TLogHelper Logger("ListFileTest", szSourceMpq); - TFileData * pFileData = NULL; - LPCTSTR szBackupMpq = bShouldHaveListFile ? _T("StormLibTest_HasListFile.mpq") : _T("StormLibTest_NoListFile.mpq"); - LPCSTR szFileName = "AddedFile001.txt"; - LPCSTR szFileData = "0123456789ABCDEF"; - HANDLE hMpq = NULL; - DWORD dwFileSize = (DWORD)strlen(szFileData); - DWORD dwErrCode = ERROR_SUCCESS; - - // Copy the archive so we won't fuck up the original one - dwErrCode = OpenExistingArchiveWithCopy(&Logger, szSourceMpq, szBackupMpq, &hMpq); - - // Add a file - if(dwErrCode == ERROR_SUCCESS) - { - // Now add a file - dwErrCode = AddFileToMpq(&Logger, hMpq, szFileName, szFileData, MPQ_FILE_IMPLODE, MPQ_COMPRESSION_PKWARE); - SFileCloseArchive(hMpq); - hMpq = NULL; - } - - // Now reopen the archive - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = OpenExistingArchiveWithCopy(&Logger, NULL, szBackupMpq, &hMpq); - - // Now the file has been written and the MPQ has been saved. - // We Reopen the MPQ and check if there is no (listfile) nor (attributes). - if(dwErrCode == ERROR_SUCCESS) - { - // Verify presence of (listfile) and (attributes) - CheckIfFileIsPresent(&Logger, hMpq, LISTFILE_NAME, bShouldHaveListFile); - CheckIfFileIsPresent(&Logger, hMpq, ATTRIBUTES_NAME, bShouldHaveAttributes); - - // Try to open the file that we recently added - pFileData = LoadMpqFile(&Logger, hMpq, szFileName); - if(pFileData != NULL) - { - // Verify if the file size matches - if(pFileData->dwFileSize == dwFileSize) - { - // Verify if the file data match - if(memcmp(pFileData->FileData, szFileData, dwFileSize)) - { - Logger.PrintError("The data of the added file does not match"); - dwErrCode = ERROR_FILE_CORRUPT; - } - } - else - { - Logger.PrintError("The size of the added file does not match"); - dwErrCode = ERROR_FILE_CORRUPT; - } - - // Delete the file data - STORM_FREE(pFileData); - } - else - { - dwErrCode = Logger.PrintError("Failed to open the file previously added"); - } - } - - // Close the MPQ archive - if(hMpq != NULL) - SFileCloseArchive(hMpq); - return dwErrCode; -} -/* -static DWORD TestCreateArchive_Deprotect(LPCSTR szPlainName) -{ - TLogHelper Logger("DeprotectTest", szPlainName); - HANDLE hMpq1 = NULL; - HANDLE hMpq2 = NULL; - char szMpqName1[MAX_PATH]; - char szMpqName2[MAX_PATH]; - BYTE FileHash1[MD5_DIGEST_SIZE]; - BYTE FileHash2[MD5_DIGEST_SIZE]; - DWORD dwFileCount1 = 0; - DWORD dwFileCount2 = 0; - DWORD dwTestFlags = SEARCH_FLAG_LOAD_FILES | SEARCH_FLAG_HASH_FILES; - DWORD dwErrCode = ERROR_SUCCESS; - - // First copy: The original (untouched) file - if(dwErrCode == ERROR_SUCCESS) - { - AddStringBeforeExtension(szMpqName1, szPlainName, "_original"); - dwErrCode = OpenExistingArchiveWithCopy(&Logger, szPlainName, szMpqName1, &hMpq1); - if(dwErrCode != ERROR_SUCCESS) - Logger.PrintMessage("Open failed: %s", szMpqName1); - } - - // Second copy: Will be deprotected - if(dwErrCode == ERROR_SUCCESS) - { - AddStringBeforeExtension(szMpqName2, szPlainName, "_deprotected"); - dwErrCode = OpenExistingArchiveWithCopy(&Logger, szPlainName, szMpqName2, &hMpq2); - if(dwErrCode != ERROR_SUCCESS) - Logger.PrintMessage("Open failed: %s", szMpqName2); - } - - // Deprotect the second map - if(dwErrCode == ERROR_SUCCESS) - { - SFileSetCompactCallback(hMpq2, CompactCallback, &Logger); - if(!SFileCompactArchive(hMpq2, NULL, false)) - dwErrCode = Logger.PrintError("Failed to deprotect archive %s", szMpqName2); - } - - // Calculate number of files and compare their hash (archive 1) - if(dwErrCode == ERROR_SUCCESS) - { - memset(FileHash1, 0, sizeof(FileHash1)); - dwErrCode = SearchArchive(&Logger, hMpq1, dwTestFlags, &dwFileCount1, FileHash1); - } - - // Calculate number of files and compare their hash (archive 2) - if(dwErrCode == ERROR_SUCCESS) - { - memset(FileHash1, 0, sizeof(FileHash2)); - dwErrCode = SearchArchive(&Logger, hMpq2, dwTestFlags, &dwFileCount2, FileHash2); - } - - if(dwErrCode == ERROR_SUCCESS) - { - if(dwFileCount1 != dwFileCount2) - Logger.PrintMessage("Different file count (%u in %s; %u in %s)", dwFileCount1, szMpqName1, dwFileCount2, szMpqName2); - if(memcmp(FileHash1, FileHash2, MD5_DIGEST_SIZE)) - Logger.PrintMessage("Different file hash (%s vs %s)", szMpqName1, szMpqName2); - } - - // Close both MPQs - if(hMpq2 != NULL) - SFileCloseArchive(hMpq2); - if(hMpq1 != NULL) - SFileCloseArchive(hMpq1); - return dwErrCode; -} -*/ - -static DWORD TestCreateArchive_EmptyMpq(LPCTSTR szPlainName, DWORD dwCreateFlags) -{ - TLogHelper Logger("CreateEmptyMpq", szPlainName); - HANDLE hMpq = NULL; - DWORD dwFileCount = 0; - DWORD dwErrCode; - - // Create the full path name - dwErrCode = CreateNewArchive(&Logger, szPlainName, dwCreateFlags, 0, &hMpq); - if(dwErrCode == ERROR_SUCCESS) - { - SearchArchive(&Logger, hMpq); - SFileCloseArchive(hMpq); - } - - // Reopen the empty MPQ - if(dwErrCode == ERROR_SUCCESS) - { - dwErrCode = OpenExistingArchiveWithCopy(&Logger, NULL, szPlainName, &hMpq); - if(dwErrCode == ERROR_SUCCESS) - { - SFileGetFileInfo(hMpq, SFileMpqNumberOfFiles, &dwFileCount, sizeof(dwFileCount), NULL); - - CheckIfFileIsPresent(&Logger, hMpq, "File00000000.xxx", false); - CheckIfFileIsPresent(&Logger, hMpq, LISTFILE_NAME, false); - SearchArchive(&Logger, hMpq); - SFileCloseArchive(hMpq); - } - } - - return dwErrCode; -} - -static DWORD TestCreateArchive_TestGaps(LPCTSTR szPlainName) -{ - TLogHelper Logger("CreateGapsTest", szPlainName); - ULONGLONG ByteOffset1 = 0xFFFFFFFF; - ULONGLONG ByteOffset2 = 0xEEEEEEEE; - HANDLE hMpq = NULL; - HANDLE hFile = NULL; - TCHAR szFullPath[MAX_PATH]; - DWORD dwErrCode = ERROR_SUCCESS; - - // Create new MPQ - dwErrCode = CreateNewArchive_V2(&Logger, szPlainName, MPQ_CREATE_LISTFILE | MPQ_CREATE_ATTRIBUTES | MPQ_FORMAT_VERSION_4, 4000, &hMpq); - if(dwErrCode == ERROR_SUCCESS) - { - // Add one file and flush the archive - dwErrCode = AddFileToMpq(&Logger, hMpq, "AddedFile01.txt", "This is the file data.", MPQ_FILE_COMPRESS); - SFileCloseArchive(hMpq); - hMpq = NULL; - } - - // Reopen the MPQ and add another file. - // The new file must be added to the position of the (listfile) - if(dwErrCode == ERROR_SUCCESS) - { - CreateFullPathName(szFullPath, _countof(szFullPath), NULL, szPlainName); - dwErrCode = OpenExistingArchive(&Logger, szFullPath, 0, &hMpq); - if(dwErrCode == ERROR_SUCCESS) - { - // Retrieve the position of the (listfile) - if(SFileOpenFileEx(hMpq, LISTFILE_NAME, 0, &hFile)) - { - SFileGetFileInfo(hFile, SFileInfoByteOffset, &ByteOffset1, sizeof(ULONGLONG), NULL); - SFileCloseFile(hFile); - } - else - dwErrCode = GetLastError(); - } - } - - // Add another file and check its position. It must be at the position of the former listfile - if(dwErrCode == ERROR_SUCCESS) - { - LPCSTR szAddedFile = "AddedFile02.txt"; - - // Add another file - dwErrCode = AddFileToMpq(&Logger, hMpq, szAddedFile, "This is the second added file.", MPQ_FILE_COMPRESS); - - // Retrieve the position of the (listfile) - if(SFileOpenFileEx(hMpq, szAddedFile, 0, &hFile)) - { - SFileGetFileInfo(hFile, SFileInfoByteOffset, &ByteOffset2, sizeof(ULONGLONG), NULL); - SFileCloseFile(hFile); - } - else - dwErrCode = GetLastError(); - } - - // Now check the positions - if(dwErrCode == ERROR_SUCCESS) - { - if(ByteOffset1 != ByteOffset2) - { - Logger.PrintError("The added file was not written to the position of (listfile)"); - dwErrCode = ERROR_FILE_CORRUPT; - } - } - - // Close the archive if needed - if(hMpq != NULL) - SFileCloseArchive(hMpq); - return dwErrCode; -} - -static DWORD TestCreateArchive_NonStdNames(LPCTSTR szPlainName) -{ - TLogHelper Logger("NonStdNamesTest", szPlainName); - HANDLE hMpq = NULL; - DWORD dwErrCode = ERROR_SUCCESS; - - // Create new MPQ - dwErrCode = CreateNewArchive(&Logger, szPlainName, MPQ_CREATE_LISTFILE | MPQ_CREATE_ATTRIBUTES | MPQ_FORMAT_VERSION_1, 4000, &hMpq); - if(dwErrCode == ERROR_SUCCESS) - { - // Add few files and close the archive - AddFileToMpq(&Logger, hMpq, "AddedFile000.txt", "This is the file data 000.", MPQ_FILE_COMPRESS); - AddFileToMpq(&Logger, hMpq, "\\/\\/\\/\\AddedFile001.txt", "This is the file data 001.", MPQ_FILE_COMPRESS); - AddFileToMpq(&Logger, hMpq, "\\\\\\\\\\\\\\\\", "This is the file data 002.", MPQ_FILE_COMPRESS); - AddFileToMpq(&Logger, hMpq, "////////////////", "This is the file data 003.", MPQ_FILE_COMPRESS); - AddFileToMpq(&Logger, hMpq, "//\\//\\//\\//\\", "This is the file data 004.", MPQ_FILE_COMPRESS); - AddFileToMpq(&Logger, hMpq, "................", "This is the file data 005.", MPQ_FILE_COMPRESS); - AddFileToMpq(&Logger, hMpq, "//****//****//****//****.***", "This is the file data 006.", MPQ_FILE_COMPRESS); - AddFileToMpq(&Logger, hMpq, "//*??*//*??*//*??*//?**?.?*?", "This is the file data 007.", MPQ_FILE_COMPRESS); - AddFileToMpq(&Logger, hMpq, "\\/\\/File.txt", "This is the file data 008.", MPQ_FILE_COMPRESS); - AddFileToMpq(&Logger, hMpq, "\\/\\/File.txt..", "This is the file data 009.", MPQ_FILE_COMPRESS); - AddFileToMpq(&Logger, hMpq, "Dir1\\Dir2\\Dir3\\File.txt..", "This is the file data 010.", MPQ_FILE_COMPRESS); - AddFileToMpq(&Logger, hMpq, "\\Dir1\\Dir2\\Dir3\\File.txt..", "This is the file data 011.", MPQ_FILE_COMPRESS); - AddFileToMpq(&Logger, hMpq, "\\\\Dir1\\\\Dir2\\\\Dir3\\\\File.txt..", "This is the file data 012.", MPQ_FILE_COMPRESS); - AddFileToMpq(&Logger, hMpq, "/Dir1/Dir2/Dir3/File.txt..", "This is the file data 013.", MPQ_FILE_COMPRESS); - AddFileToMpq(&Logger, hMpq, "////Dir1////Dir2////Dir3////File.txt..", "This is the file data 014.", MPQ_FILE_COMPRESS); - AddFileToMpq(&Logger, hMpq, "\\//\\Dir1\\//\\Dir2\\//\\File.txt..", "This is the file data 015.", MPQ_FILE_COMPRESS); - AddFileToMpq(&Logger, hMpq, "\x10\x11\x12\x13\\\x14\x15\x16\x17\\\x18\x19\x1a\x1b\\\x1c\x1D\x1E\x1F.txt", "This is the file data 016.", MPQ_FILE_COMPRESS); - AddFileToMpq(&Logger, hMpq, "\x09\x20\x09\x20\\\x20\x09\x20\x09\\\x09\x20\x09\x20\\\x20\x09\x20\x09.txt", "This is the file data 017.", MPQ_FILE_COMPRESS); - AddFileToMpq(&Logger, hMpq, "\x80\x91\xA2\xB3\\\xC4\xD5\xE6\xF7\\\x80\x91\xA2\xB3.txt", "This is the file data 018.", MPQ_FILE_COMPRESS); - AddFileToMpq(&Logger, hMpq, "Dir1\x20\x09\x20\\Dir2\x20\x09\x20\\File.txt\x09\x09\x20\x2e", "This is the file data 019.", MPQ_FILE_COMPRESS); - AddFileToMpq(&Logger, hMpq, "Dir1\x20\x09\x20\\Dir2\x20\x09\x20\\\x09\x20\x2e\x09\x20\x2e", "This is the file data 020.", MPQ_FILE_COMPRESS); - - SFileCloseArchive(hMpq); - } - - return ERROR_SUCCESS; -} - -static DWORD TestCreateArchive_Signed(LPCTSTR szPlainName, bool bSignAtCreate) -{ - TLogHelper Logger("CreateSignedMpq", szPlainName); - HANDLE hMpq = NULL; - DWORD dwCreateFlags = MPQ_CREATE_LISTFILE | MPQ_CREATE_ATTRIBUTES | MPQ_FORMAT_VERSION_1; - DWORD dwSignatures = 0; - DWORD nVerifyError = 0; - DWORD dwErrCode = ERROR_SUCCESS; - - // Method 1: Create the archive as signed - if(bSignAtCreate) - dwCreateFlags |= MPQ_CREATE_SIGNATURE; - - // Create new MPQ - dwErrCode = CreateNewArchive_V2(&Logger, szPlainName, dwCreateFlags, 4000, &hMpq); - if(dwErrCode == ERROR_SUCCESS) - { - // Add one file and flush the archive - dwErrCode = AddFileToMpq(&Logger, hMpq, "AddedFile01.txt", "This is the file data.", MPQ_FILE_COMPRESS); - } - - // Sign the archive with weak signature - if(dwErrCode == ERROR_SUCCESS) - { - if(!SFileSignArchive(hMpq, SIGNATURE_TYPE_WEAK)) - dwErrCode = ERROR_SUCCESS; - } - - // Reopen the MPQ and add another file. - // The new file must be added to the position of the (listfile) - if(dwErrCode == ERROR_SUCCESS) - { - // Query the signature types - Logger.PrintProgress("Retrieving signatures ..."); - TestGetFileInfo(&Logger, hMpq, SFileMpqSignatures, &dwSignatures, sizeof(DWORD), NULL, true, ERROR_SUCCESS); - - // Verify any of the present signatures - Logger.PrintProgress("Verifying archive signature ..."); - nVerifyError = SFileVerifyArchive(hMpq); - - // Verify the result - if((dwSignatures != SIGNATURE_TYPE_WEAK) && (nVerifyError != ERROR_WEAK_SIGNATURE_OK)) - { - Logger.PrintMessage("Weak signature verification error"); - dwErrCode = ERROR_FILE_CORRUPT; - } - } - - // Close the archive - if(hMpq != NULL) - SFileCloseArchive(hMpq); - return dwErrCode; -} - -static DWORD TestCreateArchive_MpqEditor(LPCTSTR szPlainName, LPCSTR szFileName) -{ - TLogHelper Logger("CreateMpqEditor", szPlainName); - HANDLE hMpq = NULL; - DWORD dwErrCode = ERROR_SUCCESS; - - // Create new MPQ - dwErrCode = CreateNewArchive_V2(&Logger, szPlainName, MPQ_CREATE_LISTFILE | MPQ_CREATE_ATTRIBUTES, 4000, &hMpq); - if(dwErrCode == ERROR_SUCCESS) - { - // Flush the archive first - SFileFlushArchive(hMpq); - - // Add one file - dwErrCode = AddFileToMpq(&Logger, hMpq, szFileName, "This is the file data.", MPQ_FILE_COMPRESS); - - // Flush the archive again - SFileFlushArchive(hMpq); - SFileCloseArchive(hMpq); - } - else - { - dwErrCode = GetLastError(); - } - - return dwErrCode; -} - -static DWORD TestCreateArchive_FillArchive(LPCTSTR szPlainName, DWORD dwCreateFlags) -{ - TLogHelper Logger("CreateFullMpq", szPlainName); - LPCSTR szFileData = "TestCreateArchive_FillArchive: Testing file data"; - char szFileName[MAX_PATH]; - HANDLE hMpq = NULL; - DWORD dwMaxFileCount = 6; - DWORD dwCompression = MPQ_COMPRESSION_ZLIB; - DWORD dwFlags = MPQ_FILE_ENCRYPTED | MPQ_FILE_COMPRESS; - DWORD dwErrCode; - - // - // Note that StormLib will round the maxfile count - // up to hash table size (nearest power of two) - // - if((dwCreateFlags & MPQ_CREATE_LISTFILE) == 0) - dwMaxFileCount++; - if((dwCreateFlags & MPQ_CREATE_ATTRIBUTES) == 0) - dwMaxFileCount++; - - // Create the new MPQ archive - dwErrCode = CreateNewArchive_V2(&Logger, szPlainName, dwCreateFlags, dwMaxFileCount, &hMpq); - if(dwErrCode == ERROR_SUCCESS) - { - // Flush the archive first - SFileFlushArchive(hMpq); - - // Add all files - for(unsigned int i = 0; i < dwMaxFileCount; i++) - { - sprintf(szFileName, "AddedFile%03u.txt", i); - dwErrCode = AddFileToMpq(&Logger, hMpq, szFileName, szFileData, dwFlags, dwCompression); - if(dwErrCode != ERROR_SUCCESS) - break; - } - - // Flush the archive again - SFileFlushArchive(hMpq); - } - - // Now the MPQ should be full. It must not be possible to add another file - if(dwErrCode == ERROR_SUCCESS) - { - dwErrCode = AddFileToMpq(&Logger, hMpq, "ShouldNotBeHere.txt", szFileData, MPQ_FILE_COMPRESS, MPQ_COMPRESSION_ZLIB, ERROR_DISK_FULL); - assert(dwErrCode != ERROR_SUCCESS); - dwErrCode = ERROR_SUCCESS; - } - - // Close the archive to enforce saving all tables - if(hMpq != NULL) - SFileCloseArchive(hMpq); - hMpq = NULL; - - // Reopen the archive again - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = OpenExistingArchiveWithCopy(&Logger, NULL, szPlainName, &hMpq); - - // The archive should still be full - if(dwErrCode == ERROR_SUCCESS) - { - CheckIfFileIsPresent(&Logger, hMpq, LISTFILE_NAME, (dwCreateFlags & MPQ_CREATE_LISTFILE) ? true : false); - CheckIfFileIsPresent(&Logger, hMpq, ATTRIBUTES_NAME, (dwCreateFlags & MPQ_CREATE_ATTRIBUTES) ? true : false); - dwErrCode = AddFileToMpq(&Logger, hMpq, "ShouldNotBeHere.txt", szFileData, MPQ_FILE_COMPRESS, MPQ_COMPRESSION_ZLIB, ERROR_DISK_FULL); - assert(dwErrCode != ERROR_SUCCESS); - dwErrCode = ERROR_SUCCESS; - } - - // The (listfile) and (attributes) must be present - if(dwErrCode == ERROR_SUCCESS) - { - CheckIfFileIsPresent(&Logger, hMpq, LISTFILE_NAME, (dwCreateFlags & MPQ_CREATE_LISTFILE) ? true : false); - CheckIfFileIsPresent(&Logger, hMpq, ATTRIBUTES_NAME, (dwCreateFlags & MPQ_CREATE_ATTRIBUTES) ? true : false); - dwErrCode = RemoveMpqFile(&Logger, hMpq, szFileName, ERROR_SUCCESS); - } - - // Now add the file again. This time, it should be possible OK - if(dwErrCode == ERROR_SUCCESS) - { - dwErrCode = AddFileToMpq(&Logger, hMpq, szFileName, szFileData, dwFlags, dwCompression, ERROR_SUCCESS); - assert(dwErrCode == ERROR_SUCCESS); - } - - // Now add the file again. This time, it should fail - if(dwErrCode == ERROR_SUCCESS) - { - dwErrCode = AddFileToMpq(&Logger, hMpq, szFileName, szFileData, dwFlags, dwCompression, ERROR_ALREADY_EXISTS); - assert(dwErrCode != ERROR_SUCCESS); - dwErrCode = ERROR_SUCCESS; - } - - // Now add the file again. This time, it should fail - if(dwErrCode == ERROR_SUCCESS) - { - dwErrCode = AddFileToMpq(&Logger, hMpq, "ShouldNotBeHere.txt", szFileData, dwFlags, dwCompression, ERROR_DISK_FULL); - assert(dwErrCode != ERROR_SUCCESS); - dwErrCode = ERROR_SUCCESS; - } - - // Close the archive and return - if(hMpq != NULL) - SFileCloseArchive(hMpq); - hMpq = NULL; - - // Reopen the archive for the third time to verify that both internal files are there - if(dwErrCode == ERROR_SUCCESS) - { - dwErrCode = OpenExistingArchiveWithCopy(&Logger, NULL, szPlainName, &hMpq); - if(dwErrCode == ERROR_SUCCESS) - { - CheckIfFileIsPresent(&Logger, hMpq, LISTFILE_NAME, (dwCreateFlags & MPQ_CREATE_LISTFILE) ? true : false); - CheckIfFileIsPresent(&Logger, hMpq, ATTRIBUTES_NAME, (dwCreateFlags & MPQ_CREATE_ATTRIBUTES) ? true : false); - SFileCloseArchive(hMpq); - } - } - - return dwErrCode; -} - -static DWORD TestCreateArchive_IncMaxFileCount(LPCTSTR szPlainName) -{ - TLogHelper Logger("IncMaxFileCount", szPlainName); - LPCSTR szFileData = "TestCreateArchive_IncMaxFileCount: Testing file data"; - char szFileName[MAX_PATH]; - HANDLE hMpq = NULL; - DWORD dwMaxFileCount = 1; - DWORD dwErrCode; - - // Create the new MPQ - dwErrCode = CreateNewArchive(&Logger, szPlainName, MPQ_CREATE_ARCHIVE_V4 | MPQ_CREATE_LISTFILE | MPQ_CREATE_ATTRIBUTES, dwMaxFileCount, &hMpq); - - // Now add exactly one file - if(dwErrCode == ERROR_SUCCESS) - { - dwErrCode = AddFileToMpq(&Logger, hMpq, "AddFile_base.txt", szFileData); - SFileFlushArchive(hMpq); - SFileCloseArchive(hMpq); - } - - // Now add 10 files. Each time we cannot add the file due to archive being full, - // we increment the max file count - if(dwErrCode == ERROR_SUCCESS) - { - for(unsigned int i = 0; i < 10; i++) - { - // Open the archive again - dwErrCode = OpenExistingArchiveWithCopy(&Logger, NULL, szPlainName, &hMpq); - if(dwErrCode != ERROR_SUCCESS) - break; - - // Add one file - sprintf(szFileName, "AddFile_%04u.txt", i); - dwErrCode = AddFileToMpq(&Logger, hMpq, szFileName, szFileData, 0, 0, ERROR_UNDETERMINED_RESULT); - if(dwErrCode != ERROR_SUCCESS) - { - // Increment the max file count by one - dwMaxFileCount = SFileGetMaxFileCount(hMpq) + 1; - Logger.PrintProgress("Increasing max file count to %u ...", dwMaxFileCount); - SFileSetMaxFileCount(hMpq, dwMaxFileCount); - - // Attempt to create the file again - dwErrCode = AddFileToMpq(&Logger, hMpq, szFileName, szFileData, 0, 0, ERROR_SUCCESS); - } - - // Compact the archive and close it - SFileSetCompactCallback(hMpq, CompactCallback, &Logger); - SFileCompactArchive(hMpq, NULL, false); - SFileCloseArchive(hMpq); - if(dwErrCode != ERROR_SUCCESS) - break; - } - } - - return dwErrCode; -} - -static DWORD TestCreateArchive_UnicodeNames() -{ - TLogHelper Logger("MpqUnicodeName"); - DWORD dwCreateFlags = MPQ_CREATE_LISTFILE | MPQ_CREATE_ATTRIBUTES; - DWORD dwErrCode = ERROR_SUCCESS; - - dwErrCode = CreateNewArchiveU(&Logger, szUnicodeName1, dwCreateFlags | MPQ_CREATE_ARCHIVE_V1, 15); - if(dwErrCode != ERROR_SUCCESS) - return dwErrCode; - - dwErrCode = CreateNewArchiveU(&Logger, szUnicodeName2, dwCreateFlags | MPQ_CREATE_ARCHIVE_V2, 58); - if(dwErrCode != ERROR_SUCCESS) - return dwErrCode; - - dwErrCode = CreateNewArchiveU(&Logger, szUnicodeName3, dwCreateFlags | MPQ_CREATE_ARCHIVE_V3, 15874); - if(dwErrCode != ERROR_SUCCESS) - return dwErrCode; - - dwErrCode = CreateNewArchiveU(&Logger, szUnicodeName4, dwCreateFlags | MPQ_CREATE_ARCHIVE_V4, 87541); - if(dwErrCode != ERROR_SUCCESS) - return dwErrCode; - - dwErrCode = CreateNewArchiveU(&Logger, szUnicodeName5, dwCreateFlags | MPQ_CREATE_ARCHIVE_V3, 87541); - if(dwErrCode != ERROR_SUCCESS) - return dwErrCode; - - dwErrCode = CreateNewArchiveU(&Logger, szUnicodeName5, dwCreateFlags | MPQ_CREATE_ARCHIVE_V2, 87541); - if(dwErrCode != ERROR_SUCCESS) - return dwErrCode; - - return dwErrCode; -} - -static DWORD TestCreateArchive_FileFlagTest(LPCTSTR szPlainName) -{ - TLogHelper Logger("FileFlagTest", szPlainName); - HANDLE hMpq = NULL; // Handle of created archive - TCHAR szFileName1[MAX_PATH]; - TCHAR szFileName2[MAX_PATH]; - TCHAR szFullPath[MAX_PATH]; - LPCSTR szMiddleFile = "FileTest_10.exe"; - LCID LocaleIDs[] = {0x000, 0x405, 0x406, 0x407}; - char szArchivedName[MAX_PATH]; - DWORD dwMaxFileCount = 0; - DWORD dwFileCount = 0; - DWORD dwErrCode; - - // Create paths for local file to be added - CreateFullPathName(szFileName1, _countof(szFileName1), szMpqSubDir, _T("AddFile.exe")); - CreateFullPathName(szFileName2, _countof(szFileName2), szMpqSubDir, _T("AddFile.bin")); - - // Create an empty file that will serve as holder for the MPQ - dwErrCode = CreateEmptyFile(&Logger, szPlainName, 0x100000, szFullPath); - - // Create new MPQ archive over that file - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = CreateNewArchive(&Logger, szPlainName, MPQ_CREATE_ARCHIVE_V1 | MPQ_CREATE_LISTFILE | MPQ_CREATE_ATTRIBUTES, 17, &hMpq); - - // Add the same file multiple times - if(dwErrCode == ERROR_SUCCESS) - { - dwMaxFileCount = SFileGetMaxFileCount(hMpq); - for(size_t i = 0; AddFlags[i] != 0xFFFFFFFF; i++) - { - sprintf(szArchivedName, "FileTest_%02u.exe", (unsigned int)i); - dwErrCode = AddLocalFileToMpq(&Logger, hMpq, szArchivedName, szFileName1, AddFlags[i], 0); - if(dwErrCode != ERROR_SUCCESS) - break; - - dwFileCount++; - } - } - - // Delete a file in the middle of the file table - if(dwErrCode == ERROR_SUCCESS) - { - Logger.PrintProgress("Removing file %s ...", szMiddleFile); - dwErrCode = RemoveMpqFile(&Logger, hMpq, szMiddleFile, ERROR_SUCCESS); - dwFileCount--; - } - - // Add one more file - if(dwErrCode == ERROR_SUCCESS) - { - dwErrCode = AddLocalFileToMpq(&Logger, hMpq, "FileTest_xx.exe", szFileName1); - dwFileCount++; - } - - // Try to decrement max file count. This must succeed - if(dwErrCode == ERROR_SUCCESS) - { - Logger.PrintProgress("Attempting to decrement max file count ..."); - if(SFileSetMaxFileCount(hMpq, 5)) - dwErrCode = Logger.PrintError("Max file count decremented, even if it should fail"); - } - - // Add ZeroSize.txt several times under a different locale - if(dwErrCode == ERROR_SUCCESS) - { - for(size_t i = 0; i < _countof(LocaleIDs); i++) - { - bool bMustSucceed = ((dwFileCount + 2) < dwMaxFileCount); - - SFileSetLocale(LocaleIDs[i]); - dwErrCode = AddLocalFileToMpq(&Logger, hMpq, "ZeroSize_1.txt", szFileName2); - if(dwErrCode != ERROR_SUCCESS) - { - if(bMustSucceed == false) - dwErrCode = ERROR_SUCCESS; - break; - } - - dwFileCount++; - } - } - - // Add ZeroSize.txt again several times under a different locale - if(dwErrCode == ERROR_SUCCESS) - { - for(size_t i = 0; LocaleIDs[i] != 0xFFFF; i++) - { - bool bMustSucceed = ((dwFileCount + 2) < dwMaxFileCount); - - SFileSetLocale(LocaleIDs[i]); - dwErrCode = AddLocalFileToMpq(&Logger, hMpq, "ZeroSize_2.txt", szFileName2, 0, 0, bMustSucceed); - if(dwErrCode != ERROR_SUCCESS) - { - if(bMustSucceed == false) - dwErrCode = ERROR_SUCCESS; - break; - } - - dwFileCount++; - } - } - - // Verify how many files did we add to the MPQ - if(dwErrCode == ERROR_SUCCESS) - { - if(dwFileCount + 2 != dwMaxFileCount) - { - Logger.PrintErrorVa("Number of files added to MPQ was unexpected (expected %u, added %u)", dwFileCount, dwMaxFileCount - 2); - dwErrCode = ERROR_FILE_CORRUPT; - } - } - - // Test rename function - if(dwErrCode == ERROR_SUCCESS) - { - Logger.PrintProgress("Testing rename files ..."); - SFileSetLocale(LANG_NEUTRAL); - if(!SFileRenameFile(hMpq, "FileTest_08.exe", "FileTest_08a.exe")) - dwErrCode = Logger.PrintError("Failed to rename the file"); - } - - if(dwErrCode == ERROR_SUCCESS) - { - if(!SFileRenameFile(hMpq, "FileTest_08a.exe", "FileTest_08.exe")) - dwErrCode = Logger.PrintError("Failed to rename the file"); - } - - if(dwErrCode == ERROR_SUCCESS) - { - if(SFileRenameFile(hMpq, "FileTest_10.exe", "FileTest_10a.exe")) - { - Logger.PrintError("Rename test succeeded even if it shouldn't"); - dwErrCode = ERROR_FILE_CORRUPT; - } - } - - if(dwErrCode == ERROR_SUCCESS) - { - if(SFileRenameFile(hMpq, "FileTest_10a.exe", "FileTest_10.exe")) - { - Logger.PrintError("Rename test succeeded even if it shouldn't"); - dwErrCode = ERROR_FILE_CORRUPT; - } - } - - // Close the archive - if(hMpq != NULL) - SFileCloseArchive(hMpq); - hMpq = NULL; - - // Try to reopen the archive - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = OpenExistingArchive(&Logger, szFullPath, 0, NULL); - return dwErrCode; -} - -static DWORD TestCreateArchive_WaveCompressionsTest(LPCTSTR szPlainName, LPCTSTR szWaveFile) -{ - TLogHelper Logger("CompressionsTest", szPlainName); - HANDLE hMpq = NULL; // Handle of created archive - TCHAR szFileName[MAX_PATH]; // Source file to be added - char szArchivedName[MAX_PATH]; - DWORD dwCmprCount = sizeof(WaveCompressions) / sizeof(DWORD); - DWORD dwAddedFiles = 0; - DWORD dwFoundFiles = 0; - DWORD dwErrCode; - - // Create paths for local file to be added - CreateFullPathName(szFileName, _countof(szFileName), szMpqSubDir, szWaveFile); - - // Create new archive - dwErrCode = CreateNewArchive(&Logger, szPlainName, MPQ_CREATE_ARCHIVE_V1 | MPQ_CREATE_LISTFILE | MPQ_CREATE_ATTRIBUTES, 0x40, &hMpq); - - // Add the same file multiple times - if(dwErrCode == ERROR_SUCCESS) - { - Logger.UserTotal = dwCmprCount; - for(unsigned int i = 0; i < dwCmprCount; i++) - { - sprintf(szArchivedName, "WaveFile_%02u.wav", i + 1); - dwErrCode = AddLocalFileToMpq(&Logger, hMpq, szArchivedName, szFileName, MPQ_FILE_COMPRESS | MPQ_FILE_ENCRYPTED | MPQ_FILE_SECTOR_CRC, WaveCompressions[i]); - if(dwErrCode != ERROR_SUCCESS) - break; - - Logger.UserCount++; - dwAddedFiles++; - } - - SFileCloseArchive(hMpq); - } - - // Reopen the archive extract each WAVE file and try to play it - if(dwErrCode == ERROR_SUCCESS) - { - dwErrCode = OpenExistingArchiveWithCopy(&Logger, NULL, szPlainName, &hMpq); - if(dwErrCode == ERROR_SUCCESS) - { - SearchArchive(&Logger, hMpq, SEARCH_FLAG_LOAD_FILES | SEARCH_FLAG_PLAY_WAVES, &dwFoundFiles, NULL); - SFileCloseArchive(hMpq); - } - - // Check if the number of found files is the same like the number of added files - // DOn;t forget that there will be (listfile) and (attributes) - if(dwFoundFiles != (dwAddedFiles + 2)) - { - Logger.PrintError("Number of found files does not match number of added files."); - dwErrCode = ERROR_FILE_CORRUPT; - } - } - - return dwErrCode; -} - -static DWORD TestCreateArchive_ListFilePos(LPCTSTR szPlainName) -{ - TFileData * pFileData; - LPCSTR szReaddedFile = "AddedFile_##.txt"; - LPCSTR szFileMask = "AddedFile_%02u.txt"; - TLogHelper Logger("ListFilePos", szPlainName); - HANDLE hMpq = NULL; // Handle of created archive - char szArchivedName[MAX_PATH]; - DWORD dwMaxFileCount = 0x0E; - DWORD dwFileCount = 0; - size_t i; - DWORD dwErrCode; - - // Create a new archive with the limit of 0x20 files - dwErrCode = CreateNewArchive(&Logger, szPlainName, MPQ_CREATE_ARCHIVE_V4 | MPQ_CREATE_LISTFILE | MPQ_CREATE_ATTRIBUTES, dwMaxFileCount, &hMpq); - - // Add maximum files files - if(dwErrCode == ERROR_SUCCESS) - { - for(i = 0; i < dwMaxFileCount; i++) - { - sprintf(szArchivedName, szFileMask, i); - dwErrCode = AddFileToMpq(&Logger, hMpq, szArchivedName, "This is a text data.", 0, 0, ERROR_SUCCESS); - if(dwErrCode != ERROR_SUCCESS) - break; - - dwFileCount++; - } - } - - // Delete few middle files - if(dwErrCode == ERROR_SUCCESS) - { - for(i = 0; i < (dwMaxFileCount / 2); i++) - { - sprintf(szArchivedName, szFileMask, i); - dwErrCode = RemoveMpqFile(&Logger, hMpq, szArchivedName, ERROR_SUCCESS); - if(dwErrCode != ERROR_SUCCESS) - break; - - dwFileCount--; - } - } - - // Close the archive - if(hMpq != NULL) - SFileCloseArchive(hMpq); - hMpq = NULL; - - // Reopen the archive to catch any asserts - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = OpenExistingArchiveWithCopy(&Logger, NULL, szPlainName, &hMpq); - - // Check that (listfile) is at the end - if(dwErrCode == ERROR_SUCCESS) - { - pFileData = LoadMpqFile(&Logger, hMpq, LISTFILE_NAME); - if(pFileData != NULL) - { - if(pFileData->dwBlockIndex < dwFileCount) - Logger.PrintMessage("Unexpected file index of %s", LISTFILE_NAME); - STORM_FREE(pFileData); - } - - pFileData = LoadMpqFile(&Logger, hMpq, ATTRIBUTES_NAME); - if(pFileData != NULL) - { - if(pFileData->dwBlockIndex <= dwFileCount) - Logger.PrintMessage("Unexpected file index of %s", ATTRIBUTES_NAME); - STORM_FREE(pFileData); - } - - // Add new file to the archive. It should be added to the last position - dwErrCode = AddFileToMpq(&Logger, hMpq, szReaddedFile, "This is a re-added file.", 0, 0, ERROR_SUCCESS); - if(dwErrCode == ERROR_SUCCESS) - { - // Force update of the tables - SFileFlushArchive(hMpq); - - // Load the file - pFileData = LoadMpqFile(&Logger, hMpq, szReaddedFile); - if(pFileData != NULL) - { - if(pFileData->dwBlockIndex != dwFileCount) - Logger.PrintMessage("Unexpected file index of %s", szReaddedFile); - STORM_FREE(pFileData); - } - } - - SFileCloseArchive(hMpq); - } - - return dwErrCode; -} - -static DWORD TestCreateArchive_BigArchive(LPCTSTR szPlainName) -{ - TLogHelper Logger("BigMpqTest", szPlainName); - HANDLE hMpq = NULL; // Handle of created archive - TCHAR szLocalFileName[MAX_PATH]; - char szArchivedName[MAX_PATH]; - DWORD dwMaxFileCount = 0x20; - DWORD dwAddedCount = 0; - size_t i; - DWORD dwErrCode; - - // Create a new archive with the limit of 0x20 files - dwErrCode = CreateNewArchive(&Logger, szPlainName, MPQ_CREATE_ARCHIVE_V3 | MPQ_CREATE_LISTFILE | MPQ_CREATE_ATTRIBUTES, dwMaxFileCount, &hMpq); - if(dwErrCode == ERROR_SUCCESS) - { - LPCSTR szFileMask = "AddedFile_%02u.txt"; - - // Now add few really big files - CreateFullPathName(szLocalFileName, _countof(szLocalFileName), szMpqSubDir, _T("MPQ_1997_v1_Diablo1_DIABDAT.MPQ")); - Logger.UserTotal = (dwMaxFileCount / 2); - - for(i = 0; i < dwMaxFileCount / 2; i++) - { - sprintf(szArchivedName, szFileMask, i + 1); - dwErrCode = AddLocalFileToMpq(&Logger, hMpq, szArchivedName, szLocalFileName, 0, 0, true); - if(dwErrCode != ERROR_SUCCESS) - break; - - Logger.UserCount++; - dwAddedCount++; - } - } - - // Close the archive - if(hMpq != NULL) - SFileCloseArchive(hMpq); - hMpq = NULL; - - // Reopen the archive to catch any asserts - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = OpenExistingArchiveWithCopy(&Logger, NULL, szPlainName, &hMpq); - - // Check that (listfile) is at the end - if(dwErrCode == ERROR_SUCCESS) - { - CheckIfFileIsPresent(&Logger, hMpq, LISTFILE_NAME, true); - CheckIfFileIsPresent(&Logger, hMpq, ATTRIBUTES_NAME, true); - - SFileCloseArchive(hMpq); - } - - return dwErrCode; -} - -// "MPQ_2014_v4_Heroes_Replay.MPQ", "AddFile-replay.message.events" -static DWORD TestModifyArchive_ReplaceFile(LPCTSTR szMpqPlainName, LPCTSTR szFilePlainName) -{ - TLogHelper Logger("ModifyTest", szMpqPlainName); - HANDLE hMpq = NULL; - TCHAR szFileFullName[MAX_PATH]; - TCHAR szMpqFullName[MAX_PATH]; - char szArchivedName[MAX_PATH]; - size_t nOffset = 0; - DWORD dwErrCode; - BYTE md5_file_in_mpq1[MD5_DIGEST_SIZE]; - BYTE md5_file_in_mpq2[MD5_DIGEST_SIZE]; - BYTE md5_file_in_mpq3[MD5_DIGEST_SIZE]; - BYTE md5_file_local[MD5_DIGEST_SIZE]; - - // Get the name of archived file as plain text - if(!_tcsnicmp(szFilePlainName, _T("AddFile-"), 8)) - nOffset = 8; - StringCopy(szArchivedName, _countof(szArchivedName), szFilePlainName + nOffset); - - // Get the full path of the archive and local file - CreateFullPathName(szFileFullName, _countof(szFileFullName), szMpqSubDir, szFilePlainName); - CreateFullPathName(szMpqFullName, _countof(szMpqFullName), NULL, szMpqPlainName); - - // Open an existing archive - dwErrCode = OpenExistingArchiveWithCopy(&Logger, szMpqPlainName, szMpqPlainName, &hMpq); - - // Open the file, load to memory, calculate hash - if(dwErrCode == ERROR_SUCCESS) - { - dwErrCode = LoadMpqFileMD5(&Logger, hMpq, szArchivedName, md5_file_in_mpq1); - } - - // Open the local file, calculate hash - if(dwErrCode == ERROR_SUCCESS) - { - dwErrCode = LoadLocalFileMD5(&Logger, szFileFullName, md5_file_local); - } - - // Add the given file - if(dwErrCode == ERROR_SUCCESS) - { - // Add the file to MPQ - dwErrCode = AddLocalFileToMpq(&Logger, hMpq, - szArchivedName, - szFileFullName, - MPQ_FILE_REPLACEEXISTING | MPQ_FILE_COMPRESS | MPQ_FILE_SINGLE_UNIT, - MPQ_COMPRESSION_ZLIB, - true); - } - - // Load the file from the MPQ again and compare both MD5's - if(dwErrCode == ERROR_SUCCESS) - { - // Load the file from the MPQ again - dwErrCode = LoadMpqFileMD5(&Logger, hMpq, szArchivedName, md5_file_in_mpq2); - if(dwErrCode == ERROR_SUCCESS) - { - // New MPQ file must be different from the old one - if(!memcmp(md5_file_in_mpq2, md5_file_in_mpq1, MD5_DIGEST_SIZE)) - { - Logger.PrintError("Data mismatch after adding the file \"%s\"", szArchivedName); - dwErrCode = ERROR_CHECKSUM_ERROR; - } - - // New MPQ file must be identical to the local one - if(memcmp(md5_file_in_mpq2, md5_file_local, MD5_DIGEST_SIZE)) - { - Logger.PrintError("Data mismatch after adding the file \"%s\"", szArchivedName); - dwErrCode = ERROR_CHECKSUM_ERROR; - } - } - } - - // Compact the MPQ - if(dwErrCode == ERROR_SUCCESS) - { - // Compact the archive - Logger.PrintProgress("Compacting archive %s ...", szMpqPlainName); - if(!SFileSetCompactCallback(hMpq, CompactCallback, &Logger)) - dwErrCode = Logger.PrintError(_T("Failed to compact archive %s"), szMpqPlainName); - - // Some test archives (like MPQ_2022_v1_v4.329.w3x) can't be compacted. - // For that reason, we ignore the result of SFileCompactArchive(). - SFileCompactArchive(hMpq, NULL, 0); - SFileCloseArchive(hMpq); - } - - // Try to open the archive again. Ignore the previous errors - if(dwErrCode == ERROR_SUCCESS) - { - dwErrCode = OpenExistingArchive(&Logger, szMpqFullName, 0, &hMpq); - if(dwErrCode == ERROR_SUCCESS) - { - // Load the file from the MPQ again - dwErrCode = LoadMpqFileMD5(&Logger, hMpq, szArchivedName, md5_file_in_mpq3); - if(dwErrCode == ERROR_SUCCESS) - { - // New MPQ file must be the same like the local one - if(memcmp(md5_file_in_mpq3, md5_file_local, MD5_DIGEST_SIZE)) - { - Logger.PrintError("Data mismatch after adding the file \"%s\"", szArchivedName); - dwErrCode = ERROR_CHECKSUM_ERROR; - } - } - - SFileCloseArchive(hMpq); - } - } - - return dwErrCode; -} - -//----------------------------------------------------------------------------- -// Tables - -static LPCTSTR Bliz = _T("ListFile_Blizzard.txt"); -static LPCTSTR WotI = _T("ListFile_WarOfTheImmortals.txt"); - -static const TEST_INFO TestList_StreamOps[] = -{ - {_T("MPQ_2013_v4_alternate-original.MPQ"), NULL, 0}, - {_T("MPQ_2013_v4_alternate-original.MPQ"), NULL, STREAM_FLAG_READ_ONLY}, - {_T("MPQ_2013_v4_alternate-complete.MPQ"), NULL, STREAM_FLAG_USE_BITMAP}, - {_T("part-file://MPQ_2009_v2_WoW_patch.MPQ.part"), NULL, 0}, - {_T("blk4-file://streaming/model.MPQ.0"), NULL, STREAM_PROVIDER_BLOCK4}, - {_T("mpqe-file://MPQ_2011_v2_EncryptedMpq.MPQE"), NULL, STREAM_PROVIDER_MPQE} -}; - -static const TEST_INFO TestList_MasterMirror[] = -{ - {_T("part-file://MPQ_2009_v1_patch-created.MPQ.part"), _T("MPQ_2009_v1_patch-original.MPQ"), 0}, - {_T("part-file://MPQ_2009_v1_patch-partial.MPQ.part"), _T("MPQ_2009_v1_patch-original.MPQ"), 1}, - {_T("part-file://MPQ_2009_v1_patch-complete.MPQ.part"), _T("MPQ_2009_v1_patch-original.MPQ"), 1}, - {_T("MPQ_2013_v4_alternate-created.MPQ"), _T("MPQ_2013_v4_alternate-original.MPQ"), 0}, - {_T("MPQ_2013_v4_alternate-incomplete.MPQ"), _T("MPQ_2013_v4_alternate-incomplete.MPQ"), 1}, - {_T("MPQ_2013_v4_alternate-complete.MPQ"), _T("MPQ_2013_v4_alternate-original.MPQ"), 1}, - - // Takes hell a lot of time!!! -// {_T("MPQ_2013_v4_alternate-downloaded.MPQ"), _T("http://www.zezula.net\\mpqs\\alternate.zip"), 0} -}; - -static const TEST_INFO Test_Mpqs[] = -{ - // Correct or damaged archives - {_T("MPQ_1997_v1_Diablo1_DIABDAT.MPQ"), NULL, 0, "music\\dintro.wav", "File00000023.xxx"}, - {_T("MPQ_1997_v1_patch_rt_SC1B.mpq"), NULL, TEST_DATA("43fe7d362955be68a708486e399576a7", 10)}, // From Starcraft 1 BETA - {_T("MPQ_1997_v1_StarDat_SC1B.mpq"), NULL, TEST_DATA("0094b23f28cfff7386071ef3bd19a577", 2468)}, // From Starcraft 1 BETA - {_T("MPQ_1997_v1_INSTALL_SC1B.EXE_"), NULL, TEST_DATA("3248460c89bb6f8e3b8fc3e08de7ffbb", 79)}, // From Starcraft 1 BETA - {_T("MPQ_2016_v1_D2XP_IX86_1xx_114a.mpq"), NULL, TEST_DATA("255d87a62f3c9518f72cf723a1818946", 221), "waitingroombkgd.dc6"}, // Update MPQ from Diablo II (patch 2016) - {_T("MPQ_2018_v1_icon_error.w3m"), NULL, TEST_DATA("fcefa25fb50c391e8714f2562d1e10ff", 19), "file00000002.blp"}, - {_T("MPQ_1997_v1_Diablo1_STANDARD.SNP"), Bliz, TEST_DATA("5ef18ef9a26b5704d8d46a344d976c89", 2)}, // File whose archive's (signature) file has flags = 0x90000000 - {_T("MPQ_2012_v2_EmptyMpq.MPQ"), NULL, TEST_DATA("00000000000000000000000000000000", 0)}, // Empty archive (found in WoW cache - it's just a header) - {_T("MPQ_2013_v4_EmptyMpq.MPQ"), NULL, TEST_DATA("00000000000000000000000000000000", 0)}, // Empty archive (created artificially - it's just a header) - {_T("MPQ_2013_v4_patch-base-16357.MPQ"), NULL, TEST_DATA("d41d8cd98f00b204e9800998ecf8427e", 1)}, // Empty archive (found in WoW cache - it's just a header) - {_T("MPQ_2011_v4_InvalidHetEntryCount.MPQ"), NULL, TEST_DATA("be4b49ecc3942d1957249f9da0021659", 6)}, // Empty archive (with invalid HET entry count) - {_T("MPQ_2002_v1_BlockTableCut.MPQ"), NULL, TEST_DATA("a9499ab74d939303d8cda7c397c36275", 287)}, // Truncated archive - {_T("MPQ_2010_v2_HasUserData.s2ma"), NULL, TEST_DATA("feff9e2c86db716b6ff5ffc906181200", 52)}, // MPQ that actually has user data - {_T("MPQ_2014_v1_AttributesOneEntryLess.w3x"), NULL, TEST_DATA("90451b7052eb0f1d6f4bf69b2daff7f5", 116)}, // Warcraft III map whose "(attributes)" file has (BlockTableSize-1) entries - {_T("MPQ_2020_v1_AHF04patch.mix"), NULL, TEST_DATA("d3c6aac48bc12813ef5ce4ad113e58bf", 2891)}, // MIX file - {_T("MPQ_2010_v3_expansion-locale-frFR.MPQ"), NULL, TEST_DATA("0c8fc921466f07421a281a05fad08b01", 53)}, // MPQ archive v 3.0 (the only one I know) - {_T("mpqe-file://MPQ_2011_v2_EncryptedMpq.MPQE"), NULL, TEST_DATA("10e4dcdbe95b7ad731c563ec6b71bc16", 82)}, // Encrypted archive from Starcraft II installer - {_T("MPx_2013_v1_LongwuOnline.mpk"), NULL, TEST_DATA("548f7db88284097f7e94c95a08c5bc24", 469)}, // MPK archive from Longwu online - {_T("MPx_2013_v1_WarOfTheImmortals.sqp"), WotI, TEST_DATA("a048f37f7c6162a96253d8081722b6d9", 9396)}, // SQP archive from War of the Immortals - {_T("part-file://MPQ_2010_v2_HashTableCompressed.MPQ.part"),0, TEST_DATA("d41d8cd98f00b204e9800998ecf8427e", 14263)}, // Partial MPQ with compressed hash table - {_T("blk4-file://streaming/model.MPQ.0"), NULL, TEST_DATA("e06b00efb2fc7e7469dd8b3b859ae15d", 39914)}, // Archive that is merged with multiple files - - // Protected archives - {_T("MPQ_2002_v1_ProtectedMap_InvalidUserData.w3x"), NULL, TEST_DATA("b900364cc134a51ddeca21a13697c3ca", 79)}, - {_T("MPQ_2002_v1_ProtectedMap_InvalidMpqFormat.w3x"), NULL, TEST_DATA("db67e894da9de618a1cdf86d02d315ff", 117)}, - {_T("MPQ_2002_v1_ProtectedMap_Spazzler.w3x"), NULL, TEST_DATA("72d7963aa799a7fb4117c55b7beabaf9", 470)}, // Warcraft III map locked by the Spazzler protector - {_T("MPQ_2014_v1_ProtectedMap_Spazzler2.w3x"), NULL, TEST_DATA("72d7963aa799a7fb4117c55b7beabaf9", 470)}, // Warcraft III map locked by the Spazzler protector - {_T("MPQ_2014_v1_ProtectedMap_Spazzler3.w3x"), NULL, TEST_DATA("e55aad2dd33cf68b372ca8e30dcb78a7", 130)}, // Warcraft III map locked by the Spazzler protector - {_T("MPQ_2002_v1_ProtectedMap_BOBA.w3m"), NULL, TEST_DATA("7b725d87e07a2173c42fe2314b95fa6c", 17)}, // Warcraft III map locked by the BOBA protector - {_T("MPQ_2015_v1_ProtectedMap_KangTooJee.w3x"), NULL, TEST_DATA("44111a3edf7645bc44bb1afd3a813576", 1715)}, - {_T("MPQ_2015_v1_ProtectedMap_Somj2hM16.w3x"), NULL, TEST_DATA("b411f9a51a6e9a9a509150c8d66ba359", 92)}, - {_T("MPQ_2015_v1_ProtectedMap_Spazy.w3x"), NULL, TEST_DATA("6e491bd055511435dcb4d9c8baed0516", 4089)}, // Warcraft III map locked by Spazy protector - {_T("MPQ_2015_v1_MessListFile.mpq"), NULL, TEST_DATA("15e25d5be124d8ad71519f967997efc2", 8)}, - {_T("MPQ_2016_v1_ProtectedMap_TableSizeOverflow.w3x"), NULL, TEST_DATA("ad81b43cbd37bbfa27e4bed4c17e6a81", 176)}, - {_T("MPQ_2016_v1_ProtectedMap_HashOffsIsZero.w3x"), NULL, TEST_DATA("d6e712c275a26dc51f16b3a02f6187df", 228)}, - {_T("MPQ_2016_v1_ProtectedMap_Somj2.w3x"), NULL, TEST_DATA("457cdbf97a9ca41cfe8ea130dafaa0bb", 21)}, // Something like Somj 2.0 - {_T("MPQ_2016_v1_WME4_4.w3x"), NULL, TEST_DATA("7ec2f4d0f3982d8b12d88bc08ef0c1fb", 640)}, // Protector from China (2016-05-27) - {_T("MPQ_2016_v1_SP_(4)Adrenaline.w3x"), NULL, TEST_DATA("b6f6d56f4f8aaef04c2c4b1f08881a8b", 16)}, - {_T("MPQ_2016_v1_ProtectedMap_1.4.w3x"), NULL, TEST_DATA("3c7908b29d3feac9ec952282390a242d", 5027)}, - {_T("MPQ_2016_v1_KoreanFile.w3m"), NULL, TEST_DATA("805d1f75712472a81c6df27b2a71f946", 18)}, - {_T("MPQ_2017_v1_Eden_RPG_S2_2.5J.w3x"), NULL, TEST_DATA("cbe1fd7ed5ed2fc005fba9beafcefe40", 16334)}, // Protected by PG1.11.973 - {_T("MPQ_2017_v1_BigDummyFiles.w3x"), NULL, TEST_DATA("f4d2ee9d85d2c4107e0b2d00ff302dd7", 9086)}, - {_T("MPQ_2017_v1_TildeInFileName.mpq"), NULL, TEST_DATA("f203e3979247a4dbf7f3828695ac810c", 5)}, - {_T("MPQ_2018_v1_EWIX_v8_7.w3x"), NULL, TEST_DATA("12c0f4e15c7361b7c13acd37a181d83b", 857), "BlueCrystal.mdx"}, - {_T("MPQ_2020_v4_FakeMpqHeaders.SC2Mod"), NULL, TEST_DATA("f45392f6523250c943990a017c230b41", 24)}, // Archive that has two fake headers before the real one - {_T("MPQ_2020_v4_NP_Protect_1.s2ma"), NULL, TEST_DATA("1a1ea40ac1165bcdb4f2e434edfc7636", 21)}, // SC2 map that is protected by the NP_Protect - {_T("MPQ_2020_v4_NP_Protect_2.s2ma"), NULL, TEST_DATA("7d1a379da8bd966da1f4fa6e4646049b", 55)}, // SC2 map that is protected by the NP_Protect - {_T("MPQ_2015_v1_flem1.w3x"), NULL, TEST_DATA("1c4c13e627658c473e84d94371e31f37", 20)}, - {_T("MPQ_2002_v1_ProtectedMap_HashTable_FakeValid.w3x"), NULL, TEST_DATA("5250975ed917375fc6540d7be436d4de", 114)}, - {_T("MPQ_2021_v1_CantExtractCHK.scx"), NULL, TEST_DATA("055fd548a789c910d9dd37472ecc1e66", 28)}, - {_T("MPQ_2022_v1_Sniper.scx"), NULL, TEST_DATA("2e955271b70b79344ad85b698f6ce9d8", 64)}, // Multiple items in hash table for staredit\scenario.chk (locale=0, platform=0) - {_T("MPQ_2022_v1_OcOc_Bound_2.scx"), NULL, TEST_DATA("25cad16a2fb4e883767a1f512fc1dce7", 16)}, - - // ASI plugins - {_T("MPQ_2020_v1_HS0.1.asi"), NULL, TEST_DATA("50cba7460a6e6d270804fb9776a7ec4f", 6022)}, - {_T("MPQ_2022_v1_hs0.8.asi"), NULL, TEST_DATA("6a40f733428001805bfe6e107ca9aec1", 11352)}, // Items in hash table have platform = 0xFF - {_T("MPQ_2022_v1_MoeMoeMod.asi"), NULL, TEST_DATA("89b923c7cde06de48815844a5bbb0ec4", 2578)}, -}; - -static const TEST_INFO Patched_Mpqs[] = -{ - {NULL, NULL, 0, PatchList_StarCraft, "music\\terran1.wav"}, - {NULL, NULL, 2, PatchList_WoW_OldWorld13286, "OldWorld\\World\\Model.blob"}, - {NULL, NULL, 8, PatchList_WoW_15050, "World\\Model.blob"}, - {NULL, NULL, 0, PatchList_WoW_16965, "DBFilesClient\\BattlePetNPCTeamMember.db2"}, - {NULL, NULL, 6, PatchList_SC2_32283, "TriggerLibs\\natives.galaxy"}, - {NULL, NULL, 2, PatchList_SC2_34644, "TriggerLibs\\GameData\\GameData.galaxy"}, - {NULL, NULL, 3, PatchList_SC2_34644_Maps, "Maps\\Campaign\\THorner03.SC2Map\\BankList.xml"}, - {NULL, NULL, TFLG_WILL_FAIL, PatchList_SC2_32283_enGB, "Assets\\Textures\\startupimage.dds"}, - {NULL, NULL, 6, PatchList_SC2_36281_enGB, "LocalizedData\\GameHotkeys.txt"}, - {NULL, NULL, 1, PatchList_HS_3604_enGB, "Hearthstone.exe"}, - {NULL, NULL, 10, PatchList_HS_6898_enGB, "Hearthstone_Data\\Managed\\Assembly-Csharp.dll"} -}; - -//----------------------------------------------------------------------------- -// Main - -int _tmain(int argc, TCHAR * argv[]) -{ - DWORD dwErrCode = ERROR_SUCCESS; - -#if defined(_MSC_VER) && defined(_DEBUG) - _CrtSetDbgFlag(_CRTDBG_ALLOC_MEM_DF | _CRTDBG_LEAK_CHECK_DF); -#endif // defined(_MSC_VER) && defined(_DEBUG) - - // Initialize storage and mix the random number generator - printf("==== Test Suite for StormLib version %s ====\n", STORMLIB_VERSION_STRING); - dwErrCode = InitializeMpqDirectory(argv, argc); - - // - // Test-open MPQs from the command line. They must be plain name - // and must be placed in the Test-MPQs folder - // - - for(int i = 2; i < argc; i++) - { - TestArchive(argv[i], Bliz, 0, "sound\\zerg\\advisor\\zaderr05.wav", NULL); - } - - // - // Tests on a local listfile - // - - if(dwErrCode == ERROR_SUCCESS) - { - TestOnLocalListFile(_T("FLAT-MAP:ListFile_Blizzard.txt")); - dwErrCode = TestOnLocalListFile(_T("ListFile_Blizzard.txt")); - } - - // - // Test file stream operations - // - - if(dwErrCode == ERROR_SUCCESS) - { - for(size_t i = 0; i < _countof(TestList_StreamOps); i++) - { - dwErrCode = TestFileStreamOperations(TestList_StreamOps[i].szMpqName1, TestList_StreamOps[i].dwFlags); - if(dwErrCode != ERROR_SUCCESS) - break; - } - } - - // - // Test master-mirror reading operations - // - - if(dwErrCode == ERROR_SUCCESS) - { - for(size_t i = 0; i < _countof(TestList_MasterMirror); i++) - { - dwErrCode = TestReadFile_MasterMirror(TestList_MasterMirror[i].szMpqName1, - TestList_MasterMirror[i].szMpqName2, - TestList_MasterMirror[i].dwFlags != 0); - if(dwErrCode != ERROR_SUCCESS) - break; - } - } - - // - // Test opening various archives - correct, damaged, protected - // - - if(dwErrCode == ERROR_SUCCESS) - { - for(size_t i = 0; i < _countof(Test_Mpqs); i++) - { - // Ignore the error code here; we want to see results of all opens - dwErrCode = TestArchive(Test_Mpqs[i].szMpqName1, // Plain archive name - Test_Mpqs[i].szMpqName2, // List file (NULL if none) - Test_Mpqs[i].dwFlags, // What exactly to do - (LPCSTR)Test_Mpqs[i].param1, // The 1st parameter - (LPCSTR)Test_Mpqs[i].param2); // The 2nd parameter - dwErrCode = ERROR_SUCCESS; - } - } - - // - // Test opening patched archives - correct, damaged, protected - // - - if(dwErrCode == ERROR_SUCCESS) - { - for(size_t i = 0; i < _countof(Patched_Mpqs); i++) - { - LPCTSTR * PatchList = (LPCTSTR *)Patched_Mpqs[i].param1; - LPCSTR szFileName = (LPCSTR)Patched_Mpqs[i].param2; - - // Ignore the error code here; we want to see results of all opens - dwErrCode = TestArchive_Patched(PatchList, // List of patches - szFileName, // Name of a file - Patched_Mpqs[i].dwFlags); - dwErrCode = ERROR_SUCCESS; - } - } - - // Veryfy SHA1 of each MPQ that we have in the list - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = FindFiles(ForEachFile_VerifyFileChecksum, szMpqSubDir); - - // Open every MPQ that we have in the storage - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = FindFiles(ForEachFile_OpenArchive, NULL); - - // Open the multi-file archive with wrong prefix to see how StormLib deals with it - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestOpenArchive_WillFail(_T("flat-file://streaming/model.MPQ.0")); - - // Test on an archive that has been invalidated by extending an old valid MPQ - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestOpenArchive_Corrupt(_T("MPQ_2013_vX_Battle.net.MPQ")); - - // Check the opening archive for read-only - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestOpenArchive_ReadOnly(_T("MPQ_1997_v1_Diablo1_DIABDAT.MPQ"), true); - - // Check the opening archive for read-only - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestOpenArchive_ReadOnly(_T("MPQ_1997_v1_Diablo1_DIABDAT.MPQ"), false); - - // Check the SFileGetFileInfo function - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestOpenArchive_GetFileInfo(_T("MPQ_2002_v1_StrongSignature.w3m"), _T("MPQ_2013_v4_SC2_EmptyMap.SC2Map")); - - // Check archive signature - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestOpenArchive_VerifySignature(_T("MPQ_1997_v1_Diablo1_STANDARD.SNP"), _T("STANDARD.SNP")); - - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestOpenArchive_VerifySignature(_T("MPQ_1999_v1_WeakSignature.exe"), _T("War2Patch_202.exe")); - - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestOpenArchive_VerifySignature(_T("MPQ_2003_v1_WeakSignatureEmpty.exe"), _T("WoW-1.2.3.4211-enUS-patch.exe")); - - // Check archive signature - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestOpenArchive_VerifySignature(_T("MPQ_2002_v1_StrongSignature.w3m"), _T("(10)DustwallowKeys.w3m")); - - // Compact the archive - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestOpenArchive_CompactArchive(_T("MPQ_2010_v3_expansion-locale-frFR.MPQ"), _T("StormLibTest_CraftedMpq1_v3.mpq"), true); - - // Compact the archive - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestOpenArchive_CompactArchive(_T("MPQ_2016_v1_00000.pak"), _T("MPQ_2016_v1_00000.pak"), false); - - // Open a MPQ (add custom user data to it) - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestOpenArchive_CompactArchive(_T("MPQ_2013_v4_SC2_EmptyMap.SC2Map"), _T("StormLibTest_CraftedMpq2_v4.mpq"), true); - - // Open a MPQ (add custom user data to it) - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestOpenArchive_CompactArchive(_T("MPQ_2013_v4_expansion1.MPQ"), _T("StormLibTest_CraftedMpq3_v4.mpq"), true); - - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestAddFile_FullTable(_T("MPQ_2014_v1_out1.w3x")); - - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestAddFile_FullTable(_T("MPQ_2014_v1_out2.w3x")); - - // Test modifying file with no (listfile) and no (attributes) - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestAddFile_ListFileTest(_T("MPQ_1997_v1_Diablo1_DIABDAT.MPQ"), false, false); - - // Test modifying an archive that contains (listfile) and (attributes) - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestAddFile_ListFileTest(_T("MPQ_2013_v4_SC2_EmptyMap.SC2Map"), true, true); - - // Create an empty archive v2 - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestCreateArchive_EmptyMpq(_T("StormLibTest_EmptyMpq_v2.mpq"), MPQ_CREATE_ARCHIVE_V2 | MPQ_CREATE_LISTFILE | MPQ_CREATE_ATTRIBUTES); - - // Create an empty archive v4 - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestCreateArchive_EmptyMpq(_T("StormLibTest_EmptyMpq_v4.mpq"), MPQ_CREATE_ARCHIVE_V4 | MPQ_CREATE_LISTFILE | MPQ_CREATE_ATTRIBUTES); - - // Test creating of an archive the same way like MPQ Editor does - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestCreateArchive_TestGaps(_T("StormLibTest_GapsTest.mpq")); - - // Test creating of an archive with non standard file names - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestCreateArchive_NonStdNames(_T("StormLibTest_NonStdNames.mpq")); - - // Sign an existing non-signed archive - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestOpenArchive_SignExisting(_T("MPQ_1998_v1_StarDat.mpq")); - - // Open a signed archive, add a file and verify the signature - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestOpenArchive_ModifySigned(_T("MPQ_1999_v1_WeakSignature.exe"), _T("War2Patch_202.exe")); - - // Create new archive and sign it - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestCreateArchive_Signed(_T("MPQ_1999_v1_WeakSigned1.mpq"), true); - - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestCreateArchive_Signed(_T("MPQ_1999_v1_WeakSigned2.mpq"), false); - - // Test creating of an archive the same way like MPQ Editor does - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestCreateArchive_MpqEditor(_T("StormLibTest_MpqEditorTest.mpq"), "AddedFile.exe"); - - // Create an archive and fill it with files up to the max file count - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestCreateArchive_FillArchive(_T("StormLibTest_FileTableFull.mpq"), 0); - - // Create an archive and fill it with files up to the max file count - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestCreateArchive_FillArchive(_T("StormLibTest_FileTableFull.mpq"), MPQ_CREATE_LISTFILE); - - // Create an archive and fill it with files up to the max file count - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestCreateArchive_FillArchive(_T("StormLibTest_FileTableFull.mpq"), MPQ_CREATE_ATTRIBUTES); - - // Create an archive and fill it with files up to the max file count - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestCreateArchive_FillArchive(_T("StormLibTest_FileTableFull.mpq"), MPQ_CREATE_ATTRIBUTES | MPQ_CREATE_LISTFILE); - - // Create an archive, and increment max file count several times - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestCreateArchive_IncMaxFileCount(_T("StormLibTest_IncMaxFileCount.mpq")); - - // Create a MPQ archive with UNICODE names - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestCreateArchive_UnicodeNames(); - - // Create a MPQ file, add files with various flags - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestCreateArchive_FileFlagTest(_T("StormLibTest_FileFlagTest.mpq")); - - // Create a MPQ file, add a mono-WAVE file with various compressions - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestCreateArchive_WaveCompressionsTest(_T("StormLibTest_AddWaveMonoTest.mpq"), _T("AddFile-Mono.wav")); - - // Create a MPQ file, add a mono-WAVE with 8 bits per sample file with various compressions - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestCreateArchive_WaveCompressionsTest(_T("StormLibTest_AddWaveMonoBadTest.mpq"), _T("AddFile-MonoBad.wav")); - - // Create a MPQ file, add a stereo-WAVE file with various compressions - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestCreateArchive_WaveCompressionsTest(_T("StormLibTest_AddWaveStereoTest.mpq"), _T("AddFile-Stereo.wav")); - - // Check if the listfile is always created at the end of the file table in the archive - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestCreateArchive_ListFilePos(_T("StormLibTest_ListFilePos.mpq")); - - // Open a MPQ (add custom user data to it) - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestCreateArchive_BigArchive(_T("StormLibTest_BigArchive_v4.mpq")); - - // Test replacing a file with zero size file - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestModifyArchive_ReplaceFile(_T("MPQ_2014_v4_Base.StormReplay"), _T("AddFile-replay.message.events")); - - if(dwErrCode == ERROR_SUCCESS) - dwErrCode = TestModifyArchive_ReplaceFile(_T("MPQ_2022_v1_v4.329.w3x"), _T("AddFile-war3map.j")); - -#ifdef _MSC_VER - _CrtDumpMemoryLeaks(); -#endif // _MSC_VER - - return dwErrCode; -} diff --git a/app/jni/src/libultraship/extern/StormLib/test/TLogHelper.cpp b/app/jni/src/libultraship/extern/StormLib/test/TLogHelper.cpp deleted file mode 100644 index 3a82368..0000000 --- a/app/jni/src/libultraship/extern/StormLib/test/TLogHelper.cpp +++ /dev/null @@ -1,462 +0,0 @@ -/*****************************************************************************/ -/* TLogHelper.cpp Copyright (c) Ladislav Zezula 2013 */ -/*---------------------------------------------------------------------------*/ -/* Helper class for reporting StormLib tests */ -/* This file should be included directly from StormTest.cpp using #include */ -/*---------------------------------------------------------------------------*/ -/* Date Ver Who Comment */ -/* -------- ---- --- ------- */ -/* 26.11.13 1.00 Lad The first version of TLogHelper.cpp */ -/*****************************************************************************/ - -//----------------------------------------------------------------------------- -// Definition of the TLogHelper class - -class TLogHelper -{ - public: - - TLogHelper(const char * szNewMainTitle = NULL, const TCHAR * szNewSubTitle1 = NULL, const TCHAR * szNewSubTitle2 = NULL); - ~TLogHelper(); - -#if defined(UNICODE) || defined(UNICODE) - // TCHAR-based functions. They are only needed on UNICODE builds. - // On ANSI builds is TCHAR = char, so we don't need them at all - int PrintWithClreol(const TCHAR * szFormat, va_list argList, bool bPrintPrefix, bool bPrintLastError, bool bPrintEndOfLine); - void PrintProgress(const TCHAR * szFormat, ...); - void PrintMessage(const TCHAR * szFormat, ...); - int PrintErrorVa(const TCHAR * szFormat, ...); - int PrintError(const TCHAR * szFormat, const TCHAR * szFileName = NULL); -#endif // defined(UNICODE) || defined(UNICODE) - - // ANSI functions - DWORD PrintWithClreol(const char * szFormat, va_list argList, bool bPrintPrefix, bool bPrintLastError, bool bPrintEndOfLine); - void PrintProgress(const char * szFormat, ...); - void PrintMessage(const char * szFormat, ...); - DWORD PrintErrorVa(const char * szFormat, ...); - DWORD PrintError(const char * szFormat, const char * szFileName = NULL); - - // Print final verdict - DWORD PrintVerdict(DWORD dwErrCode = ERROR_SUCCESS); - - const char * UserString; - unsigned int UserCount; - unsigned int UserTotal; - bool bDontPrintResult; - - protected: - -#if defined(UNICODE) || defined(UNICODE) - TCHAR * CopyFormatCharacter(TCHAR * szBuffer, const TCHAR *& szFormat); -#endif - char * CopyFormatCharacter(char * szBuffer, const char *& szFormat); - int GetConsoleWidth(); - - const char * szMainTitle; // Title of the text (usually name) - const TCHAR * szSubTitle1; // Title of the text (can be name of the tested file) - const TCHAR * szSubTitle2; // Title of the text (can be name of the tested file) - size_t nTextLength; // Length of the previous progress message - bool bMessagePrinted; -}; - -//----------------------------------------------------------------------------- -// String replacements for format strings - -#ifdef _MSC_VER -#define I64u_t _T("%I64u") -#define I64u_a "%I64u" -#define I64X_t _T("%I64X") -#define I64X_a "%I64X" -#else -#define I64u_t _T("%llu") -#define I64u_a "%llu" -#define I64X_t _T("%llX") -#define I64X_a "%llX" -#endif - -//----------------------------------------------------------------------------- -// Constructor and destructor - - -TLogHelper::TLogHelper(const char * szNewMainTitle, const TCHAR * szNewSubTitle1, const TCHAR * szNewSubTitle2) -{ - TCHAR szMainTitleT[0x80]; - - UserString = ""; - UserCount = 1; - UserTotal = 1; - - // Fill the test line structure - szMainTitle = szNewMainTitle; - szSubTitle1 = szNewSubTitle1; - szSubTitle2 = szNewSubTitle2; - nTextLength = 0; - bMessagePrinted = false; - bDontPrintResult = false; - - // Copy the UNICODE main title - StringCopy(szMainTitleT, _countof(szMainTitleT), szMainTitle); - - // Print the initial information - if(szMainTitle != NULL) - { - if(szSubTitle1 != NULL && szSubTitle2 != NULL) - _tprintf(_T("Running %s (%s+%s) ..."), szMainTitleT, szSubTitle1, szSubTitle2); - else if(szSubTitle1 != NULL) - _tprintf(_T("Running %s (%s) ..."), szMainTitleT, szSubTitle1); - else - _tprintf(_T("Running %s ..."), szMainTitleT); - } -} - -TLogHelper::~TLogHelper() -{ - // Print a verdict, if no verdict was printed yet - if(bMessagePrinted == false) - { - PrintVerdict(ERROR_SUCCESS); - } - -#if defined(_MSC_VER) && defined(_DEBUG) - if(_CrtDumpMemoryLeaks()) - { - PrintMessage(_T("Memory leak(s) detected.\n")); - } -#endif // _MSC_VER -} - -//----------------------------------------------------------------------------- -// TCHAR-based functions. They are only needed on UNICODE builds. -// On ANSI builds is TCHAR = char, so we don't need them at all - -#if defined(UNICODE) || defined(UNICODE) -int TLogHelper::PrintWithClreol(const TCHAR * szFormat, va_list argList, bool bPrintPrefix, bool bPrintLastError, bool bPrintEndOfLine) -{ - TCHAR szFormatBuff[0x200]; - TCHAR szMessage[0x200]; - TCHAR * szBuffer = szFormatBuff; - int nRemainingWidth; - int nConsoleWidth = GetConsoleWidth(); - int nLength = 0; - int nError = GetLastError(); - - // Always start the buffer with '\r' - *szBuffer++ = '\r'; - - // Print the prefix, if needed - if(szMainTitle != NULL && bPrintPrefix) - { - while(szMainTitle[nLength] != 0) - *szBuffer++ = szMainTitle[nLength++]; - - *szBuffer++ = ':'; - *szBuffer++ = ' '; - } - - // Copy the message format itself. Replace %s with "%s", unless it's (%s) - if(szFormat != NULL) - { - while(szFormat[0] != 0) - { - szBuffer = CopyFormatCharacter(szBuffer, szFormat); - } - } - - // Append the last error - if(bPrintLastError) - { - nLength = _stprintf(szBuffer, _T(" (error code: %u)"), nError); - szBuffer += nLength; - } - - // Create the result string - szBuffer[0] = 0; - nLength = _vstprintf(szMessage, szFormatBuff, argList); - szBuffer = szMessage + nLength; - - // Shall we pad the string? - if(nLength < nConsoleWidth) - { - // Calculate the remaining width - nRemainingWidth = nConsoleWidth - nLength - 1; - - // Pad the string with spaces to fill it up to the end of the line - for(int i = 0; i < nRemainingWidth; i++) - *szBuffer++ = 0x20; - } - - // Put the newline, if requested - *szBuffer++ = bPrintEndOfLine ? '\n' : 0; - *szBuffer = 0; - - // Remember if we printed a message - if(bPrintEndOfLine) - bMessagePrinted = true; - - // Spit out the text in one single printf - _tprintf(_T("%s"), szMessage); - return nError; -} - -void TLogHelper::PrintProgress(const TCHAR * szFormat, ...) -{ - va_list argList; - - va_start(argList, szFormat); - PrintWithClreol(szFormat, argList, true, false, false); - va_end(argList); -} - -void TLogHelper::PrintMessage(const TCHAR * szFormat, ...) -{ - va_list argList; - - va_start(argList, szFormat); - PrintWithClreol(szFormat, argList, true, false, true); - va_end(argList); -} - -int TLogHelper::PrintErrorVa(const TCHAR * szFormat, ...) -{ - va_list argList; - int nResult; - - va_start(argList, szFormat); - nResult = PrintWithClreol(szFormat, argList, true, true, true); - va_end(argList); - - return nResult; -} - -int TLogHelper::PrintError(const TCHAR * szFormat, const TCHAR * szFileName) -{ - return PrintErrorVa(szFormat, szFileName); -} -#endif // defined(UNICODE) || defined(UNICODE) - -//----------------------------------------------------------------------------- -// ANSI functions - -DWORD TLogHelper::PrintWithClreol(const char * szFormat, va_list argList, bool bPrintPrefix, bool bPrintLastError, bool bPrintEndOfLine) -{ - char szFormatBuff[0x200]; - char szMessage[0x200]; - char * szBuffer = szFormatBuff; - int nRemainingWidth; - int nConsoleWidth = GetConsoleWidth(); - int nLength = 0; - DWORD dwErrCode = GetLastError(); - - // Always start the buffer with '\r' - *szBuffer++ = '\r'; - - // Print the prefix, if needed - if(szMainTitle != NULL && bPrintPrefix) - { - while(szMainTitle[nLength] != 0) - *szBuffer++ = (char)szMainTitle[nLength++]; - - *szBuffer++ = ':'; - *szBuffer++ = ' '; - } - - // Copy the message format itself. Replace %s with "%s", unless it's (%s) - if(szFormat != NULL) - { - while(szFormat[0] != 0) - { - szBuffer = CopyFormatCharacter(szBuffer, szFormat); - } - } - - // Append the last error - if(bPrintLastError) - { - nLength = sprintf(szBuffer, " (error code: %u)", dwErrCode); - szBuffer += nLength; - } - - // Create the result string - szBuffer[0] = 0; - nLength = vsprintf(szMessage, szFormatBuff, argList); - - // Shall we pad the string? - szBuffer = szMessage + nLength; - if(nLength < nConsoleWidth) - { - // Calculate the remaining width - nRemainingWidth = nConsoleWidth - nLength - 1; - - // Pad the string with spaces to fill it up to the end of the line - for(int i = 0; i < nRemainingWidth; i++) - *szBuffer++ = 0x20; - } - - // Put the newline, if requested - *szBuffer++ = bPrintEndOfLine ? '\n' : '\r'; - *szBuffer = 0; - - // Remember if we printed a message - if(bPrintEndOfLine) - bMessagePrinted = true; - - // Spit out the text in one single printf - printf("%s", szMessage); - return dwErrCode; -} - -void TLogHelper::PrintProgress(const char * szFormat, ...) -{ - va_list argList; - - va_start(argList, szFormat); - PrintWithClreol(szFormat, argList, true, false, false); - va_end(argList); -} - -void TLogHelper::PrintMessage(const char * szFormat, ...) -{ - va_list argList; - - va_start(argList, szFormat); - PrintWithClreol(szFormat, argList, true, false, true); - va_end(argList); -} - -DWORD TLogHelper::PrintErrorVa(const char * szFormat, ...) -{ - va_list argList; - DWORD dwErrCode; - - va_start(argList, szFormat); - dwErrCode = PrintWithClreol(szFormat, argList, true, true, true); - va_end(argList); - - return dwErrCode; -} - -DWORD TLogHelper::PrintError(const char * szFormat, const char * szFileName) -{ - return PrintErrorVa(szFormat, szFileName); -} - -//----------------------------------------------------------------------------- -// Print final verdict - -DWORD TLogHelper::PrintVerdict(DWORD dwErrCode) -{ - LPCTSTR szSaveSubTitle1 = szSubTitle1; - LPCTSTR szSaveSubTitle2 = szSubTitle2; - TCHAR szSaveMainTitle[0x80]; - - // Set both to NULL so they won't be printed - StringCopy(szSaveMainTitle, _countof(szSaveMainTitle), szMainTitle); - szSubTitle1 = NULL; - szSubTitle2 = NULL; - szMainTitle = NULL; - - // Print the final information - if(szSaveMainTitle[0] != 0) - { - if(bDontPrintResult == false) - { - LPCTSTR szVerdict = (dwErrCode == ERROR_SUCCESS) ? _T("succeeded") : _T("failed"); - - if(szSaveSubTitle1 != NULL && szSaveSubTitle2 != NULL) - PrintMessage(_T("%s (%s+%s) %s."), szSaveMainTitle, szSaveSubTitle1, szSaveSubTitle2, szVerdict); - else if(szSaveSubTitle1 != NULL) - PrintMessage(_T("%s (%s) %s."), szSaveMainTitle, szSaveSubTitle1, szVerdict); - else - PrintMessage(_T("%s %s."), szSaveMainTitle, szVerdict); - } - else - { - PrintProgress(" "); - printf("\r"); - } - } - - // Return the error code so the caller can pass it fuhrter - return dwErrCode; -} - -//----------------------------------------------------------------------------- -// Protected functions - -#ifdef _UNICODE -TCHAR * TLogHelper::CopyFormatCharacter(TCHAR * szBuffer, const TCHAR *& szFormat) -{ -// static LPCTSTR szStringFormat = _T("\"%s\""); - static LPCTSTR szStringFormat = _T("%s"); - static LPCTSTR szUint64Format = I64u_t; - - // String format - if(szFormat[0] == '%') - { - if(szFormat[1] == 's') - { - _tcscpy(szBuffer, szStringFormat); - szFormat += 2; - return szBuffer + _tcslen(szStringFormat); - } - - // Replace %I64u with the proper platform-dependent suffix - if(szFormat[1] == 'I' && szFormat[2] == '6' && szFormat[3] == '4' && szFormat[4] == 'u') - { - _tcscpy(szBuffer, szUint64Format); - szFormat += 5; - return szBuffer + _tcslen(szUint64Format); - } - } - - // Copy the character as-is - *szBuffer++ = *szFormat++; - return szBuffer; -} -#endif - -char * TLogHelper::CopyFormatCharacter(char * szBuffer, const char *& szFormat) -{ - static const char * szStringFormat = "\"%s\""; - static const char * szUint64Format = I64u_a; - - // String format - if(szFormat[0] == '%') - { - if(szFormat[1] == 's') - { - strcpy(szBuffer, szStringFormat); - szFormat += 2; - return szBuffer + strlen(szStringFormat); - } - - // Replace %I64u with the proper platform-dependent suffix - if(szFormat[1] == 'I' && szFormat[2] == '6' && szFormat[3] == '4' && szFormat[4] == 'u') - { - strcpy(szBuffer, szUint64Format); - szFormat += 5; - return szBuffer + strlen(szUint64Format); - } - } - - // Copy the character as-is - *szBuffer++ = *szFormat++; - return szBuffer; -} - -int TLogHelper::GetConsoleWidth() -{ -#ifdef STORMLIB_WINDOWS - - CONSOLE_SCREEN_BUFFER_INFO ScreenInfo; - GetConsoleScreenBufferInfo(GetStdHandle(STD_OUTPUT_HANDLE), &ScreenInfo); - return (int)(ScreenInfo.srWindow.Right - ScreenInfo.srWindow.Left); - -#else - - // On non-Windows platforms, we assume that width of the console line - // is 80 characters - return 120; - -#endif -} diff --git a/app/jni/src/libultraship/extern/StormLib/test/stormlib-test.txt b/app/jni/src/libultraship/extern/StormLib/test/stormlib-test.txt deleted file mode 100644 index 947a387..0000000 --- a/app/jni/src/libultraship/extern/StormLib/test/stormlib-test.txt +++ /dev/null @@ -1,2351 +0,0 @@ -Microsoft Windows [Version 10.0.19044.2006] -(c) Microsoft Corporation. All rights reserved. - -E:\Ladik\AppDir\StormLib\bin\StormLib_test\x64\Release>StormLib_test.exe -==== Test Suite for StormLib version 9.24 ==== -InitWorkDir: Work directory \Multimedia\MPQs (default) -LocalListFile (FLAT-MAP:ListFile_Blizzard.txt) succeeded. -LocalListFile (ListFile_Blizzard.txt) succeeded. -FileStreamTest (MPQ_2013_v4_alternate-original.MPQ) succeeded. -FileStreamTest (MPQ_2013_v4_alternate-original.MPQ) succeeded. -FileStreamTest (MPQ_2013_v4_alternate-complete.MPQ) succeeded. -FileStreamTest (part-file://MPQ_2009_v2_WoW_patch.MPQ.part) succeeded. -FileStreamTest (blk4-file://streaming/model.MPQ.0) succeeded. -FileStreamTest (mpqe-file://MPQ_2011_v2_EncryptedMpq.MPQE) succeeded. -OpenMirrorFile (part-file://MPQ_2009_v1_patch-created.MPQ.part) succeeded. -OpenMirrorFile (part-file://MPQ_2009_v1_patch-partial.MPQ.part) succeeded. -OpenMirrorFile (part-file://MPQ_2009_v1_patch-complete.MPQ.part) succeeded. -OpenMirrorFile (MPQ_2013_v4_alternate-created.MPQ) succeeded. -OpenMirrorFile (MPQ_2013_v4_alternate-incomplete.MPQ) succeeded. -OpenMirrorFile (MPQ_2013_v4_alternate-complete.MPQ) succeeded. -TestMpq (MPQ_1997_v1_Diablo1_DIABDAT.MPQ) succeeded. -TestMpq (MPQ_1997_v1_patch_rt_SC1B.mpq) succeeded. -TestMpq (MPQ_1997_v1_StarDat_SC1B.mpq) succeeded. -TestMpq (MPQ_1997_v1_INSTALL_SC1B.EXE_) succeeded. -TestMpq (MPQ_2016_v1_D2XP_IX86_1xx_114a.mpq) succeeded. -TestMpq (MPQ_2018_v1_icon_error.w3m) succeeded. -TestMpq (MPQ_1997_v1_Diablo1_STANDARD.SNP) succeeded. -TestMpq (MPQ_2012_v2_EmptyMpq.MPQ) succeeded. -TestMpq (MPQ_2013_v4_EmptyMpq.MPQ) succeeded. -TestMpq (MPQ_2013_v4_patch-base-16357.MPQ) succeeded. -TestMpq (MPQ_2011_v4_InvalidHetEntryCount.MPQ) succeeded. -TestMpq (MPQ_2002_v1_BlockTableCut.MPQ) succeeded. -TestMpq (MPQ_2010_v2_HasUserData.s2ma) succeeded. -TestMpq (MPQ_2014_v1_AttributesOneEntryLess.w3x) succeeded. -TestMpq (MPQ_2020_v1_AHF04patch.mix) succeeded. -TestMpq (MPQ_2010_v3_expansion-locale-frFR.MPQ) succeeded. -TestMpq (mpqe-file://MPQ_2011_v2_EncryptedMpq.MPQE) succeeded. -TestMpq (MPx_2013_v1_LongwuOnline.mpk) succeeded. -TestMpq (MPx_2013_v1_WarOfTheImmortals.sqp) succeeded. -TestMpq (part-file://MPQ_2010_v2_HashTableCompressed.MPQ.part) succeeded. -TestMpq (blk4-file://streaming/model.MPQ.0) succeeded. -TestMpq (MPQ_2002_v1_ProtectedMap_InvalidUserData.w3x) succeeded. -TestMpq (MPQ_2002_v1_ProtectedMap_InvalidMpqFormat.w3x) succeeded. -TestMpq (MPQ_2002_v1_ProtectedMap_Spazzler.w3x) succeeded. -TestMpq (MPQ_2014_v1_ProtectedMap_Spazzler2.w3x) succeeded. -TestMpq (MPQ_2014_v1_ProtectedMap_Spazzler3.w3x) succeeded. -TestMpq (MPQ_2002_v1_ProtectedMap_BOBA.w3m) succeeded. -TestMpq (MPQ_2015_v1_ProtectedMap_KangTooJee.w3x) succeeded. -TestMpq (MPQ_2015_v1_ProtectedMap_Somj2hM16.w3x) succeeded. -TestMpq (MPQ_2015_v1_ProtectedMap_Spazy.w3x) succeeded. -TestMpq (MPQ_2015_v1_MessListFile.mpq) succeeded. -TestMpq (MPQ_2016_v1_ProtectedMap_TableSizeOverflow.w3x) succeeded. -TestMpq (MPQ_2016_v1_ProtectedMap_HashOffsIsZero.w3x) succeeded. -TestMpq (MPQ_2016_v1_ProtectedMap_Somj2.w3x) succeeded. -TestMpq (MPQ_2016_v1_WME4_4.w3x) succeeded. -TestMpq (MPQ_2016_v1_SP_(4)Adrenaline.w3x) succeeded. -TestMpq (MPQ_2016_v1_ProtectedMap_1.4.w3x) succeeded. -TestMpq (MPQ_2016_v1_KoreanFile.w3m) succeeded. -TestMpq (MPQ_2017_v1_Eden_RPG_S2_2.5J.w3x) succeeded. -TestMpq (MPQ_2017_v1_BigDummyFiles.w3x) succeeded. -TestMpq (MPQ_2017_v1_TildeInFileName.mpq) succeeded. -TestMpq (MPQ_2018_v1_EWIX_v8_7.w3x) succeeded. -TestMpq (MPQ_2020_v4_FakeMpqHeaders.SC2Mod) succeeded. -TestMpq (MPQ_2020_v4_NP_Protect_1.s2ma) succeeded. -TestMpq (MPQ_2020_v4_NP_Protect_2.s2ma) succeeded. -TestMpq (MPQ_2015_v1_flem1.w3x) succeeded. -TestMpq (MPQ_2002_v1_ProtectedMap_HashTable_FakeValid.w3x) succeeded. -TestMpq (MPQ_2021_v1_CantExtractCHK.scx) succeeded. -TestMpq (MPQ_2022_v1_Sniper.scx) succeeded. -TestMpq (MPQ_2022_v1_OcOc_Bound_2.scx) succeeded. -TestMpq (MPQ_2020_v1_HS0.1.asi) succeeded. -TestMpq (MPQ_2022_v1_hs0.8.asi) succeeded. -TestMpq (MPQ_2022_v1_MoeMoeMod.asi) succeeded. -PatchedMPQ (MPQ_1998_v1_StarCraft.mpq) succeeded. -PatchedMPQ (MPQ_2012_v4_OldWorld.MPQ) succeeded. -PatchedMPQ (MPQ_2013_v4_world.MPQ) succeeded. -PatchedMPQ (MPQ_2013_v4_locale-enGB.MPQ) succeeded. -PatchedMPQ (MPQ_2013_v4_Base1.SC2Data) succeeded. -PatchedMPQ (MPQ_2013_v4_Base1.SC2Data) succeeded. -PatchedMPQ (MPQ_2013_v4_Base3.SC2Maps) succeeded. -PatchedMPQ (MPQ_2013_v4_Mods#Core.SC2Mod#enGB.SC2Assets) succeeded. -PatchedMPQ (MPQ_2013_v4_Mods#Liberty.SC2Mod#enGB.SC2Data) succeeded. -PatchedMPQ (MPQ_2014_v4_base-Win.MPQ) succeeded. -PatchedMPQ (MPQ_2014_v4_base-Win.MPQ) succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -VerifyFileHash succeeded. -OpenEachMpqTest ((10)DustwallowKeys.w3m) succeeded. -OpenEachMpqTest (MPQ_1997_v1_Diablo1_DIABDAT.MPQ) succeeded. -OpenEachMpqTest (MPQ_1997_v1_Diablo1_single_0.sv) succeeded. -OpenEachMpqTest (MPQ_1997_v1_patch_rt_SC1B.mpq) succeeded. -OpenEachMpqTest (MPQ_1997_v1_StarDat.mpq) succeeded. -OpenEachMpqTest (MPQ_1997_v1_StarDat_SC1B.mpq) succeeded. -OpenEachMpqTest (MPQ_1998_v1_StarCraft.mpq) succeeded. -OpenEachMpqTest (MPQ_1998_v1_StarDat.mpq) succeeded. -OpenEachMpqTest (MPQ_2002_v1_BlockTableCut.MPQ) succeeded. -OpenEachMpqTest (MPQ_2002_v1_ProtectedMap_BOBA.w3m) succeeded. -OpenEachMpqTest (MPQ_2002_v1_ProtectedMap_HashTable_FakeValid.w3x) succeeded. -OpenEachMpqTest (MPQ_2002_v1_ProtectedMap_InvalidMpqFormat.w3x) succeeded. -OpenEachMpqTest (MPQ_2002_v1_ProtectedMap_InvalidUserData.w3x) succeeded. -OpenEachMpqTest (MPQ_2002_v1_ProtectedMap_Spazzler.w3x) succeeded. -OpenEachMpqTest (MPQ_2002_v1_StrongSignature.w3m) succeeded. -OpenEachMpqTest (MPQ_2009_v1_patch-complete.MPQ.part) succeeded. -OpenEachMpqTest (MPQ_2009_v1_patch-original.MPQ) succeeded. -OpenEachMpqTest (MPQ_2009_v1_patch-partial.MPQ.part) succeeded. -OpenEachMpqTest (MPQ_2009_v2_WoW_patch.MPQ.part) succeeded. -OpenEachMpqTest (MPQ_2010_v2_HashTableCompressed.MPQ.part) succeeded. -OpenEachMpqTest (MPQ_2010_v2_HasUserData.s2ma) succeeded. -OpenEachMpqTest (MPQ_2010_v3_expansion-locale-frFR.MPQ) succeeded. -OpenEachMpqTest (MPQ_2011_v2_EncryptedMpq.MPQE) succeeded. -OpenEachMpqTest (MPQ_2011_v4_InvalidHetEntryCount.MPQ) succeeded. -OpenEachMpqTest: Warning: no files in the archive -OpenEachMpqTest (MPQ_2012_v4_OldWorld.MPQ) succeeded. -OpenEachMpqTest (MPQ_2013_v4_alternate-complete.MPQ) succeeded. -OpenEachMpqTest (MPQ_2013_v4_alternate-downloaded.MPQ) succeeded. -OpenEachMpqTest (MPQ_2013_v4_alternate-incomplete.MPQ) succeeded. -OpenEachMpqTest (MPQ_2013_v4_alternate-original.MPQ) succeeded. -OpenEachMpqTest: Warning: no files in the archive -OpenEachMpqTest (MPQ_2013_v4_expansion1.MPQ) succeeded. -OpenEachMpqTest (MPQ_2013_v4_locale-enGB.MPQ) succeeded. -OpenEachMpqTest (MPQ_2013_v4_patch-base-16357.MPQ) succeeded. -OpenEachMpqTest (MPQ_2013_v4_SC2_EmptyMap.SC2Map) succeeded. -OpenEachMpqTest (MPQ_2013_v4_world.MPQ) succeeded. -OpenEachMpqTest: Warning: no files in the archive -OpenEachMpqTest (MPQ_2014_v1_AttributesOneEntryLess.w3x) succeeded. -OpenEachMpqTest (MPQ_2014_v1_CompactTest.w3x) succeeded. -OpenEachMpqTest (MPQ_2014_v1_out1.w3x) succeeded. -OpenEachMpqTest (MPQ_2014_v1_out2.w3x) succeeded. -OpenEachMpqTest (MPQ_2014_v1_ProtectedMap_Spazzler2.w3x) succeeded. -OpenEachMpqTest (MPQ_2014_v1_ProtectedMap_Spazzler3.w3x) succeeded. -OpenEachMpqTest (MPQ_2014_v4_base-Win.MPQ) succeeded. -OpenEachMpqTest (MPQ_2015_v1_flem1.w3x) succeeded. -OpenEachMpqTest (MPQ_2015_v1_MessListFile.mpq) succeeded. -OpenEachMpqTest (MPQ_2015_v1_ProtectedMap_KangTooJee.w3x) succeeded. -OpenEachMpqTest (MPQ_2015_v1_ProtectedMap_Somj2hM16.w3x) succeeded. -OpenEachMpqTest (MPQ_2015_v1_ProtectedMap_Spazy.w3x) succeeded. -OpenEachMpqTest (MPQ_2016_v1_AnotherProtectedMap.w3x) succeeded. -OpenEachMpqTest (MPQ_2016_v1_D2XP_IX86_1xx_114a.mpq) succeeded. -OpenEachMpqTest (MPQ_2016_v1_DeathWing_ORPG_v.1.45a.w3x) succeeded. -OpenEachMpqTest (MPQ_2016_v1_KoreanFile.w3m) succeeded. -OpenEachMpqTest (MPQ_2016_v1_ProtectedMap123.w3x) succeeded. -OpenEachMpqTest (MPQ_2016_v1_ProtectedMap_1.4.w3x) succeeded. -OpenEachMpqTest (MPQ_2016_v1_ProtectedMap_HashOffsIsZero.w3x) succeeded. -OpenEachMpqTest (MPQ_2016_v1_ProtectedMap_Somj2.w3x) succeeded. -OpenEachMpqTest (MPQ_2016_v1_ProtectedMap_TableSizeOverflow.w3x) succeeded. -OpenEachMpqTest (MPQ_2016_v1_SP_(4)Adrenaline.w3x) succeeded. -OpenEachMpqTest (MPQ_2016_v1_WME4_4.w3x) succeeded. -OpenEachMpqTest (MPQ_2017_v1_BigDummyFiles.w3x) succeeded. -OpenEachMpqTest (MPQ_2017_v1_Eden_RPG_S2_2.5J.w3x) succeeded. -OpenEachMpqTest (MPQ_2017_v1_TildeInFileName.mpq) succeeded. -OpenEachMpqTest (MPQ_2018_v1_EWIX_v8_7.w3x) succeeded. -OpenEachMpqTest (MPQ_2018_v1_icon_error.w3m) succeeded. -OpenEachMpqTest (MPQ_2020_v1_HS0.1.asi) succeeded. -OpenEachMpqTest (MPQ_2020_v4_FakeMpqHeaders.SC2Mod) succeeded. -OpenEachMpqTest (MPQ_2020_v4_NP_Protect_1.s2ma) succeeded. -OpenEachMpqTest (MPQ_2020_v4_NP_Protect_2.s2ma) succeeded. -OpenEachMpqTest (MPQ_2020_v4_NP_Protect_3.s2ma) succeeded. -OpenEachMpqTest (MPQ_2020_v4_NP_Protect_4.s2ma) succeeded. -OpenEachMpqTest (MPQ_2020_v4_ThreeFakeHeaders.s2ma) succeeded. -OpenEachMpqTest (MPQ_2021_v1_CrossLinkedFiles.w3x) succeeded. -OpenEachMpqTest (MPQ_2021_v4_BzipError.SC2Replay) succeeded. -OpenEachMpqTest (MPQ_2022_v1_hs0.8.asi) succeeded. -OpenEachMpqTest (MPQ_2022_v1_MoeMoeMod.asi) succeeded. -OpenEachMpqTest (MPQ_2022_v1_v4.329.w3x) succeeded. -OpenEachMpqTest (hs-0-3604-Win-final.MPQ) succeeded. -OpenEachMpqTest (hs-0-5314-Win-final.MPQ) succeeded. -OpenEachMpqTest (hs-5314-5435-Win-final.MPQ) succeeded. -OpenEachMpqTest (hs-5435-5506-Win-final.MPQ) succeeded. -OpenEachMpqTest (hs-5506-5834-Win-final.MPQ) succeeded. -OpenEachMpqTest (hs-5834-6024-Win-final.MPQ) succeeded. -OpenEachMpqTest (hs-6024-6141-Win-final.MPQ) succeeded. -OpenEachMpqTest (hs-6141-6187-Win-final.MPQ) succeeded. -OpenEachMpqTest (hs-6187-6284-Win-final.MPQ) succeeded. -OpenEachMpqTest (hs-6284-6485-Win-final.MPQ) succeeded. -OpenEachMpqTest (hs-6485-6898-Win-final.MPQ) succeeded. -OpenEachMpqTest (s1-1998-BroodWar.mpq) succeeded. -OpenEachMpqTest (s2-update-base-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-base-24540.MPQ) succeeded. -OpenEachMpqTest (s2-update-base-26147.MPQ) succeeded. -OpenEachMpqTest (s2-update-base-28522.MPQ) succeeded. -OpenEachMpqTest (s2-update-base-30508.MPQ) succeeded. -OpenEachMpqTest (s2-update-base-32283.MPQ) succeeded. -OpenEachMpqTest (s2-update-base-32384.MPQ) succeeded. -OpenEachMpqTest (s2-update-base-34644.MPQ) succeeded. -OpenEachMpqTest (s2-update-enGB-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-enGB-24540.MPQ) succeeded. -OpenEachMpqTest (s2-update-enGB-26147.MPQ) succeeded. -OpenEachMpqTest (s2-update-enGB-28522.MPQ) succeeded. -OpenEachMpqTest (s2-update-enGB-30508.MPQ) succeeded. -OpenEachMpqTest (s2-update-enGB-32283.MPQ) succeeded. -OpenEachMpqTest (s2-update-enGB-32384.MPQ) succeeded. -OpenEachMpqTest (s2-update-enGB-34644.MPQ) succeeded. -OpenEachMpqTest (s2-update-enGB-36281.MPQ) succeeded. -OpenEachMpqTest (wow-update-13164.MPQ) succeeded. -OpenEachMpqTest (wow-update-13205.MPQ) succeeded. -OpenEachMpqTest (wow-update-13287.MPQ) succeeded. -OpenEachMpqTest (wow-update-13329.MPQ) succeeded. -OpenEachMpqTest (wow-update-13596.MPQ) succeeded. -OpenEachMpqTest (wow-update-13623.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-13914.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-14007.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-14333.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-14480.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-14545.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-14946.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-15005.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-15050.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16016.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16048.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16057.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16309.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16357.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16516.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16650.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16844.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16965.MPQ) succeeded. -OpenEachMpqTest (wow-update-oldworld-13154.MPQ) succeeded. -OpenEachMpqTest (wow-update-oldworld-13286.MPQ) succeeded. -OpenEachMpqTest (model.MPQ.0) succeeded. -OpenEachMpqTest (DIABDAT.mpq) succeeded. -OpenEachMpqTest (single_0.sv) succeeded. -OpenEachMpqTest (DIABDAT.MPQ) succeeded. -OpenEachMpqTest (hellfire.mpq) succeeded. -OpenEachMpqTest (hfmonk.mpq) succeeded. -OpenEachMpqTest (hfmusic.mpq) succeeded. -OpenEachMpqTest (hfvoice.mpq) succeeded. -OpenEachMpqTest (gs.mpq) succeeded. -OpenEachMpqTest (imp.mpq) succeeded. -OpenEachMpqTest (pic.mpq) succeeded. -OpenEachMpqTest (sndfx.mpq) succeeded. -OpenEachMpqTest (special.mpq) succeeded. -OpenEachMpqTest (patch_rt.mpq) succeeded. -OpenEachMpqTest (StarDat.mpq) succeeded. -OpenEachMpqTest (BrooDat.mpq) succeeded. -OpenEachMpqTest (BroodWar.mpq) succeeded. -OpenEachMpqTest (Patch_rt.mpq) succeeded. -OpenEachMpqTest (StarCraft.mpq) succeeded. -OpenEachMpqTest (StarDat.mpq) succeeded. -OpenEachMpqTest (StardatSW.mpq) succeeded. -OpenEachMpqTest (StarDat_BETA.mpq) succeeded. -OpenEachMpqTest (War2Dat.mpq) succeeded. -OpenEachMpqTest (War2Patch.mpq) succeeded. -OpenEachMpqTest (d2char.mpq) succeeded. -OpenEachMpqTest (d2data.mpq) succeeded. -OpenEachMpqTest (d2exp.mpq) succeeded. -OpenEachMpqTest (d2music.mpq) succeeded. -OpenEachMpqTest (d2sfx.mpq) succeeded. -OpenEachMpqTest (d2speech.mpq) succeeded. -OpenEachMpqTest (d2video.mpq) succeeded. -OpenEachMpqTest (D2XMUSIC.MPQ) succeeded. -OpenEachMpqTest (d2xtalk.mpq) succeeded. -OpenEachMpqTest (d2xvideo.mpq) succeeded. -OpenEachMpqTest (Patch_D2.mpq) succeeded. -OpenEachMpqTest (setup.mpq) succeeded. -OpenEachMpqTest (HumanEd.mpq) succeeded. -OpenEachMpqTest ((10)DustwallowKeys.w3m) succeeded. -OpenEachMpqTest ((10)RagingStream.w3x) succeeded. -OpenEachMpqTest ((4)aaaa.w3x) succeeded. -OpenEachMpqTest (a_tvse_x_1_2_f.w3x) succeeded. -OpenEachMpqTest (Shopping_Maul_ USA 9.10.7.w3x) succeeded. -OpenEachMpqTest (siverrpg_1.9_ver.w3x) succeeded. -OpenEachMpqTest (ACGExternal0.2.asi) succeeded. -OpenEachMpqTest (grandparty.asi) succeeded. -OpenEachMpqTest (HS0.1.asi) succeeded. -OpenEachMpqTest (HS0.5.asi) succeeded. -OpenEachMpqTest (Patch_War3x.mpq) succeeded. -OpenEachMpqTest (Patch_War3_Low.mpq) succeeded. -OpenEachMpqTest (Patch_War3_Med.mpq) succeeded. -OpenEachMpqTest (War3.mpq) succeeded. -OpenEachMpqTest (War3Patch.mpq) succeeded. -OpenEachMpqTest (War3x.mpq) succeeded. -OpenEachMpqTest (War3xlocal.mpq) succeeded. -OpenEachMpqTest (dbc.MPQ) succeeded. -OpenEachMpqTest (fonts.MPQ) succeeded. -OpenEachMpqTest (interface.MPQ) succeeded. -OpenEachMpqTest (misc.MPQ) succeeded. -OpenEachMpqTest (model.MPQ) succeeded. -OpenEachMpqTest (sound.MPQ) succeeded. -OpenEachMpqTest (speech.MPQ) succeeded. -OpenEachMpqTest (texture.MPQ) succeeded. -OpenEachMpqTest (TheramoreDocks.wmo.MPQ) succeeded. -OpenEachMpqTest (Azeroth.wdl.MPQ) succeeded. -OpenEachMpqTest (Azeroth.wdt.MPQ) succeeded. -OpenEachMpqTest (Blackfathom.wdl.MPQ) succeeded. -OpenEachMpqTest (Blackfathom.wdt.MPQ) succeeded. -OpenEachMpqTest (Collin.wdl.MPQ) succeeded. -OpenEachMpqTest (Collin.wdt.MPQ) succeeded. -OpenEachMpqTest (DeadminesInstance.wdl.MPQ) succeeded. -OpenEachMpqTest (DeadminesInstance.wdt.MPQ) succeeded. -OpenEachMpqTest (GnomeragonInstance.wdl.MPQ) succeeded. -OpenEachMpqTest (GnomeragonInstance.wdt.MPQ) succeeded. -OpenEachMpqTest (Kalidar.wdl.MPQ) succeeded. -OpenEachMpqTest (Kalidar.wdt.MPQ) succeeded. -OpenEachMpqTest (Kalimdor.wdl.MPQ) succeeded. -OpenEachMpqTest (Kalimdor.wdt.MPQ) succeeded. -OpenEachMpqTest (Monastery.wdl.MPQ) succeeded. -OpenEachMpqTest (Monastery.wdt.MPQ) succeeded. -OpenEachMpqTest (PVPZone01.wdl.MPQ) succeeded. -OpenEachMpqTest (PVPZone01.wdt.MPQ) succeeded. -OpenEachMpqTest (PVPZone02.wdl.MPQ) succeeded. -OpenEachMpqTest (PVPZone02.wdt.MPQ) succeeded. -OpenEachMpqTest (RazorfenDowns.wdl.MPQ) succeeded. -OpenEachMpqTest (RazorfenDowns.wdt.MPQ) succeeded. -OpenEachMpqTest (RazorfenKraulInstance.wdl.MPQ) succeeded. -OpenEachMpqTest (RazorfenKraulInstance.wdt.MPQ) succeeded. -OpenEachMpqTest (Shadowfang.wdl.MPQ) succeeded. -OpenEachMpqTest (Shadowfang.wdt.MPQ) succeeded. -OpenEachMpqTest (StormwindJail.wdl.MPQ) succeeded. -OpenEachMpqTest (StormwindJail.wdt.MPQ) succeeded. -OpenEachMpqTest (StormwindPrison.wdl.MPQ) succeeded. -OpenEachMpqTest (StormwindPrison.wdt.MPQ) succeeded. -OpenEachMpqTest (SunkenTemple.wdl.MPQ) succeeded. -OpenEachMpqTest (SunkenTemple.wdt.MPQ) succeeded. -OpenEachMpqTest (test.wdl.MPQ) succeeded. -OpenEachMpqTest (test.wdt.MPQ) succeeded. -OpenEachMpqTest (Uldaman.wdl.MPQ) succeeded. -OpenEachMpqTest (Uldaman.wdt.MPQ) succeeded. -OpenEachMpqTest (UnderMine.wdl.MPQ) succeeded. -OpenEachMpqTest (UnderMine.wdt.MPQ) succeeded. -OpenEachMpqTest (WailingCaverns.wdl.MPQ) succeeded. -OpenEachMpqTest (WailingCaverns.wdt.MPQ) succeeded. -OpenEachMpqTest (AltarOfStorms.wmo.MPQ) succeeded. -OpenEachMpqTest (Big_Keep.wmo.MPQ) succeeded. -OpenEachMpqTest (castle01.wmo.MPQ) succeeded. -OpenEachMpqTest (Chapel.wmo.MPQ) succeeded. -OpenEachMpqTest (DuskwoodChapel.wmo.MPQ) succeeded. -OpenEachMpqTest (RedridgeChapel.wmo.MPQ) succeeded. -OpenEachMpqTest (DuskwoodAbandoned_Barn.wmo.MPQ) succeeded. -OpenEachMpqTest (DuskwoodAbandoned_Blacksmith.wmo.MPQ) succeeded. -OpenEachMpqTest (DuskwoodAbandoned_HumanTwoStory.wmo.MPQ) succeeded. -OpenEachMpqTest (DuskwoodAbandoned_human_farm.wmo.MPQ) succeeded. -OpenEachMpqTest (DuskwoodAbandoned_Inn.wmo.MPQ) succeeded. -OpenEachMpqTest (DuskwoodAbandoned_lumbermill.wmo.MPQ) succeeded. -OpenEachMpqTest (DuskwoodAbandoned_TownHall_NoWall.wmo.MPQ) succeeded. -OpenEachMpqTest (Duskwood_Barn.wmo.MPQ) succeeded. -OpenEachMpqTest (duskwood_barracks.wmo.MPQ) succeeded. -OpenEachMpqTest (Duskwood_Blacksmith.wmo.MPQ) succeeded. -OpenEachMpqTest (Duskwood_HumanTwoStory.wmo.MPQ) succeeded. -OpenEachMpqTest (Duskwood_human_farm.wmo.MPQ) succeeded. -OpenEachMpqTest (DuskwoodFarmHouseburnt.wmo.MPQ) succeeded. -OpenEachMpqTest (Duskwood_Inn.wmo.MPQ) succeeded. -OpenEachMpqTest (Duskwood_lumbermill.wmo.MPQ) succeeded. -OpenEachMpqTest (Duskwood_MageTower.wmo.MPQ) succeeded. -OpenEachMpqTest (Duskwood_Stable.wmo.MPQ) succeeded. -OpenEachMpqTest (Duskwood_TownHall.wmo.MPQ) succeeded. -OpenEachMpqTest (Duskwood_TownHall_NoWall.wmo.MPQ) succeeded. -OpenEachMpqTest (GnomeHut.wmo.MPQ) succeeded. -OpenEachMpqTest (GnomeHutTwoStory.wmo.MPQ) succeeded. -OpenEachMpqTest (goldshireblacksmith.wmo.MPQ) succeeded. -OpenEachMpqTest (GoldshireInn.wmo.MPQ) succeeded. -OpenEachMpqTest (GriffonAviary.wmo.MPQ) succeeded. -OpenEachMpqTest (GuardTower.wmo.MPQ) succeeded. -OpenEachMpqTest (RuinedHumanGuardTower01.wmo.MPQ) succeeded. -OpenEachMpqTest (HumanTwoStory.wmo.MPQ) succeeded. -OpenEachMpqTest (barn.wmo.MPQ) succeeded. -OpenEachMpqTest (silo.wmo.MPQ) succeeded. -OpenEachMpqTest (Human_Barracks.wmo.MPQ) succeeded. -OpenEachMpqTest (farm.wmo.MPQ) succeeded. -OpenEachMpqTest (farmtest.wmo.MPQ) succeeded. -OpenEachMpqTest (Gate01.wmo.MPQ) succeeded. -OpenEachMpqTest (Gate02.wmo.MPQ) succeeded. -OpenEachMpqTest (Gate03.wmo.MPQ) succeeded. -OpenEachMpqTest (GateRuined01.wmo.MPQ) succeeded. -OpenEachMpqTest (GateRuined02.wmo.MPQ) succeeded. -OpenEachMpqTest (KeepBridge01.wmo.MPQ) succeeded. -OpenEachMpqTest (LowWallPost01.wmo.MPQ) succeeded. -OpenEachMpqTest (WallPiece01.wmo.MPQ) succeeded. -OpenEachMpqTest (WallPiece02.wmo.MPQ) succeeded. -OpenEachMpqTest (WallPiece03.wmo.MPQ) succeeded. -OpenEachMpqTest (WallPiece04.wmo.MPQ) succeeded. -OpenEachMpqTest (WallPiece05.wmo.MPQ) succeeded. -OpenEachMpqTest (WallPieceRuin01.wmo.MPQ) succeeded. -OpenEachMpqTest (WallPieceRuin02.wmo.MPQ) succeeded. -OpenEachMpqTest (WallPieceRuin03.wmo.MPQ) succeeded. -OpenEachMpqTest (WallPieceRuin04.wmo.MPQ) succeeded. -OpenEachMpqTest (WallPieceStairs01.wmo.MPQ) succeeded. -OpenEachMpqTest (WallPost01.wmo.MPQ) succeeded. -OpenEachMpqTest (WallPost02.wmo.MPQ) succeeded. -OpenEachMpqTest (WallPostRuined01.wmo.MPQ) succeeded. -OpenEachMpqTest (WallPostTunnel01.wmo.MPQ) succeeded. -OpenEachMpqTest (lumbermill.wmo.MPQ) succeeded. -OpenEachMpqTest (magetower.wmo.MPQ) succeeded. -OpenEachMpqTest (Moonbrook_Blacksmith.wmo.MPQ) succeeded. -OpenEachMpqTest (Moonbrook_HumanTwoStory.wmo.MPQ) succeeded. -OpenEachMpqTest (Moonbrook_human_farm.wmo.MPQ) succeeded. -OpenEachMpqTest (Moonbrook_Inn.wmo.MPQ) succeeded. -OpenEachMpqTest (Moonbrook_TownHall_NoWall.wmo.MPQ) succeeded. -OpenEachMpqTest (NSabbey.wmo.MPQ) succeeded. -OpenEachMpqTest (OilPlatform.wmo.MPQ) succeeded. -OpenEachMpqTest (OilPlatformSmall.wmo.MPQ) succeeded. -OpenEachMpqTest (oil_platform.wmo.MPQ) succeeded. -OpenEachMpqTest (PrisonGuardTower.wmo.MPQ) succeeded. -OpenEachMpqTest (prisonHQ.wmo.MPQ) succeeded. -OpenEachMpqTest (prisonLonghouse.wmo.MPQ) succeeded. -OpenEachMpqTest (PrisonOubliette.wmo.MPQ) succeeded. -OpenEachMpqTest (PrisonOublietteTunnel.wmo.MPQ) succeeded. -OpenEachMpqTest (RedRidge_Barn.wmo.MPQ) succeeded. -OpenEachMpqTest (redridge_barracks.wmo.MPQ) succeeded. -OpenEachMpqTest (RedRidge_Blacksmith.wmo.MPQ) succeeded. -OpenEachMpqTest (RedRidge_HumanTwoStory.wmo.MPQ) succeeded. -OpenEachMpqTest (RedRidge_human_farm.wmo.MPQ) succeeded. -OpenEachMpqTest (RedRidge_Inn.wmo.MPQ) succeeded. -OpenEachMpqTest (RedRidge_lumbermill.wmo.MPQ) succeeded. -OpenEachMpqTest (RedRidge_MageTower.wmo.MPQ) succeeded. -OpenEachMpqTest (RedRidge_Stable.wmo.MPQ) succeeded. -OpenEachMpqTest (RedRidge_TownHall.wmo.MPQ) succeeded. -OpenEachMpqTest (RedRidge_TownHall_NoWall.wmo.MPQ) succeeded. -OpenEachMpqTest (Scarlet_Monestary.wmo.MPQ) succeeded. -OpenEachMpqTest (stable.wmo.MPQ) succeeded. -OpenEachMpqTest (Stormwind.wmo.MPQ) succeeded. -OpenEachMpqTest (BootyBay.wmo.MPQ) succeeded. -OpenEachMpqTest (BootyBayPlank.wmo.MPQ) succeeded. -OpenEachMpqTest (BootyBay_house1.wmo.MPQ) succeeded. -OpenEachMpqTest (BootyBay_house2.wmo.MPQ) succeeded. -OpenEachMpqTest (BootyBay_railing.wmo.MPQ) succeeded. -OpenEachMpqTest (BootyBay_warehouse.wmo.MPQ) succeeded. -OpenEachMpqTest (ratchet_dock.wmo.MPQ) succeeded. -OpenEachMpqTest (TownHall.wmo.MPQ) succeeded. -OpenEachMpqTest (TownHall_NoWall.wmo.MPQ) succeeded. -OpenEachMpqTest (Westfall_Barn.wmo.MPQ) succeeded. -OpenEachMpqTest (westfall_barracks.wmo.MPQ) succeeded. -OpenEachMpqTest (Westfall_Blacksmith.wmo.MPQ) succeeded. -OpenEachMpqTest (Westfall_GuardTower.wmo.MPQ) succeeded. -OpenEachMpqTest (Westfall_HumanTwoStory.wmo.MPQ) succeeded. -OpenEachMpqTest (Westfall_human_farm.wmo.MPQ) succeeded. -OpenEachMpqTest (WestFallFarmHouseburnt.wmo.MPQ) succeeded. -OpenEachMpqTest (Westfall_Inn.wmo.MPQ) succeeded. -OpenEachMpqTest (Westfall_lumbermill.wmo.MPQ) succeeded. -OpenEachMpqTest (Westfall_MageTower.wmo.MPQ) succeeded. -OpenEachMpqTest (Westfall_Stable.wmo.MPQ) succeeded. -OpenEachMpqTest (Westfall_TownHall.wmo.MPQ) succeeded. -OpenEachMpqTest (Westfall_TownHall_NoWall.wmo.MPQ) succeeded. -OpenEachMpqTest (DuskWorldTree.wmo.MPQ) succeeded. -OpenEachMpqTest (WorldTree.wmo.MPQ) succeeded. -OpenEachMpqTest (TrollZiggurat.wmo.MPQ) succeeded. -OpenEachMpqTest (ZulGurubRuins01.wmo.MPQ) succeeded. -OpenEachMpqTest (AllianceShrine.wmo.MPQ) succeeded. -OpenEachMpqTest (DuskwoodChasmBridge.wmo.MPQ) succeeded. -OpenEachMpqTest (DuskwoodCoveredBridge.wmo.MPQ) succeeded. -OpenEachMpqTest (abbeygate01.wmo.MPQ) succeeded. -OpenEachMpqTest (abbeygate02.wmo.MPQ) succeeded. -OpenEachMpqTest (ElwynnLakeBridge.wmo.MPQ) succeeded. -OpenEachMpqTest (ElwynnFootbridge.wmo.MPQ) succeeded. -OpenEachMpqTest (ElwynnLionBridge.wmo.MPQ) succeeded. -OpenEachMpqTest (HeroBridge.wmo.MPQ) succeeded. -OpenEachMpqTest (HeroGate.wmo.MPQ) succeeded. -OpenEachMpqTest (ElwynnWideBridge.wmo.MPQ) succeeded. -OpenEachMpqTest (HordeShrine.wmo.MPQ) succeeded. -OpenEachMpqTest (IronFootbridge.wmo.MPQ) succeeded. -OpenEachMpqTest (IronforgeRopeBridge01.wmo.MPQ) succeeded. -OpenEachMpqTest (IronStonebridge.wmo.MPQ) succeeded. -OpenEachMpqTest (RedridgeDamagedBridge.wmo.MPQ) succeeded. -OpenEachMpqTest (RedRidgeDocks01.wmo.MPQ) succeeded. -OpenEachMpqTest (RedRidgeDocks02.wmo.MPQ) succeeded. -OpenEachMpqTest (RedRidgeDocks03.wmo.MPQ) succeeded. -OpenEachMpqTest (RedRidgeFootbridge.wmo.MPQ) succeeded. -OpenEachMpqTest (OilRefinery.wmo.MPQ) succeeded. -OpenEachMpqTest (RopeBridge.wmo.MPQ) succeeded. -OpenEachMpqTest (StrangleRuinStair.wmo.MPQ) succeeded. -OpenEachMpqTest (StrangleGladiatorArena.wmo.MPQ) succeeded. -OpenEachMpqTest (StrangleArenaGate01.wmo.MPQ) succeeded. -OpenEachMpqTest (StranglethornRuins01.wmo.MPQ) succeeded. -OpenEachMpqTest (StranglethornRuins02.wmo.MPQ) succeeded. -OpenEachMpqTest (StranglethornRuins04.wmo.MPQ) succeeded. -OpenEachMpqTest (StranglethornRuins11.wmo.MPQ) succeeded. -OpenEachMpqTest (StranglethornRuins12.wmo.MPQ) succeeded. -OpenEachMpqTest (StranglethornRuins13.wmo.MPQ) succeeded. -OpenEachMpqTest (StranglethornRuins16.wmo.MPQ) succeeded. -OpenEachMpqTest (BridgeStranglethorn.wmo.MPQ) succeeded. -OpenEachMpqTest (SwampBridge01.wmo.MPQ) succeeded. -OpenEachMpqTest (SwampDock01.wmo.MPQ) succeeded. -OpenEachMpqTest (HumanBoatHouse.wmo.MPQ) succeeded. -OpenEachMpqTest (WestFallGrainSilo01.wmo.MPQ) succeeded. -OpenEachMpqTest (WetlandsHumanDock01.wmo.MPQ) succeeded. -OpenEachMpqTest (WetlandsBustedWagon.wmo.MPQ) succeeded. -OpenEachMpqTest (cameron.wmo.MPQ) succeeded. -OpenEachMpqTest (Blackrock.wmo.MPQ) succeeded. -OpenEachMpqTest (Blackrock2.wmo.MPQ) succeeded. -OpenEachMpqTest (AZ_Deadmines_A.wmo.MPQ) succeeded. -OpenEachMpqTest (AZ_Deadmines_B.wmo.MPQ) succeeded. -OpenEachMpqTest (AZ_Deadmines_C.wmo.MPQ) succeeded. -OpenEachMpqTest (AZ_Deadmines_D.wmo.MPQ) succeeded. -OpenEachMpqTest (Karazhan.wmo.MPQ) succeeded. -OpenEachMpqTest (StormwindJail.wmo.MPQ) succeeded. -OpenEachMpqTest (StormwindPrison.wmo.MPQ) succeeded. -OpenEachMpqTest (Ahn_Qiraj.wmo.MPQ) succeeded. -OpenEachMpqTest (Ahn_Qirajwall01.wmo.MPQ) succeeded. -OpenEachMpqTest (Ahn_Qirajwall02.wmo.MPQ) succeeded. -OpenEachMpqTest (Ahn_Qirajwall03.wmo.MPQ) succeeded. -OpenEachMpqTest (Blackfathom.wmo.MPQ) succeeded. -OpenEachMpqTest (Blackfathom_instance.wmo.MPQ) succeeded. -OpenEachMpqTest (RazorfenDowns.wmo.MPQ) succeeded. -OpenEachMpqTest (RazorfenDowns_instance.wmo.MPQ) succeeded. -OpenEachMpqTest (RazorfenKraul.wmo.MPQ) succeeded. -OpenEachMpqTest (RazorfenKraul_instance.wmo.MPQ) succeeded. -OpenEachMpqTest (wailingcaverns.wmo.MPQ) succeeded. -OpenEachMpqTest (wailingcaverns_instance.wmo.MPQ) succeeded. -OpenEachMpqTest (KZ_Gnomeragon.wmo.MPQ) succeeded. -OpenEachMpqTest (KZ_Gnomeragon_Instance.wmo.MPQ) succeeded. -OpenEachMpqTest (KZ_Uldaman.wmo.MPQ) succeeded. -OpenEachMpqTest (KZ_Uldaman_A.wmo.MPQ) succeeded. -OpenEachMpqTest (KZ_Uldaman_B.wmo.MPQ) succeeded. -OpenEachMpqTest (LD_ShadowFang.wmo.MPQ) succeeded. -OpenEachMpqTest (LD_ShadowFangInterior.wmo.MPQ) succeeded. -OpenEachMpqTest (Stratholme.wmo.MPQ) succeeded. -OpenEachMpqTest (AlgazGate.wmo.MPQ) succeeded. -OpenEachMpqTest (AnimalDen.wmo.MPQ) succeeded. -OpenEachMpqTest (Anvilmarpass.wmo.MPQ) succeeded. -OpenEachMpqTest (BarrowDens.wmo.MPQ) succeeded. -OpenEachMpqTest (CorruptBarrowDens.wmo.MPQ) succeeded. -OpenEachMpqTest (BarrowDensOneRm.wmo.MPQ) succeeded. -OpenEachMpqTest (CorruptBarrowDensOneRoom.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_IceDen.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_JungleDen.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_MushroomDen.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_TrollDen.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_TrollDen_Warm.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_WarmDen.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_CaveTunnel01.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_StoneAshen_Tunnel.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_WarmCaveTunnel01.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_Crypt.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_CryptOneRm.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_CryptSchool.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_CryptSimpleEnt.wmo.MPQ) succeeded. -OpenEachMpqTest (LargeTunnel.wmo.MPQ) succeeded. -OpenEachMpqTest (MediumTunnel.wmo.MPQ) succeeded. -OpenEachMpqTest (MediumTunnel_Snow.wmo.MPQ) succeeded. -OpenEachMpqTest (SmallTunnel.wmo.MPQ) succeeded. -OpenEachMpqTest (SmallTunnel_Snow.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_FishingHoleIce.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_Goldmine.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_Goldmine_1Room.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_Goldmine_variantA.wmo.MPQ) succeeded. -OpenEachMpqTest (exterior_arch.wmo.MPQ) succeeded. -OpenEachMpqTest (exterior_piece01.wmo.MPQ) succeeded. -OpenEachMpqTest (exterior_piece02.wmo.MPQ) succeeded. -OpenEachMpqTest (exterior_piece03.wmo.MPQ) succeeded. -OpenEachMpqTest (exterior_piece04.wmo.MPQ) succeeded. -OpenEachMpqTest (exterior_piece05.wmo.MPQ) succeeded. -OpenEachMpqTest (mini-hive_A.wmo.MPQ) succeeded. -OpenEachMpqTest (mini-hive_B.wmo.MPQ) succeeded. -OpenEachMpqTest (mini-hive_C.wmo.MPQ) succeeded. -OpenEachMpqTest (mini-hive_D.wmo.MPQ) succeeded. -OpenEachMpqTest (mini-hive_E.wmo.MPQ) succeeded. -OpenEachMpqTest (mini-hive_F.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_Hordemine.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_Hordemine1Room.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_Icecave.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_Icecave_Medium.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_Junglecave.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_Junglecave_Medium.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_Mountaincave_Medium.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_Mushroomcave.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_Underwatercave_Medium.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_Warmcave.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_Warmcave_Medium.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_Brogremound.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_Brogremound1Room.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_Grogremound.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_Grogremound1Room.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_Ogremound.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_Ogremound1Room.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_Ogremound_Medium.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_Snogremound.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_Snogremound1Room.wmo.MPQ) succeeded. -OpenEachMpqTest (Pirateship.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_RuinedFortress.wmo.MPQ) succeeded. -OpenEachMpqTest (Ruinedkeep.wmo.MPQ) succeeded. -OpenEachMpqTest (Shipwreck_A.wmo.MPQ) succeeded. -OpenEachMpqTest (Shipwreck_B.wmo.MPQ) succeeded. -OpenEachMpqTest (Shipwreck_C.wmo.MPQ) succeeded. -OpenEachMpqTest (Shipwreck_D.wmo.MPQ) succeeded. -OpenEachMpqTest (Transport_Shipwreck.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_Spidermine.wmo.MPQ) succeeded. -OpenEachMpqTest (MD_Spidermine_nokobolds.wmo.MPQ) succeeded. -OpenEachMpqTest (Scarlet_Monestary_Interior.wmo.MPQ) succeeded. -OpenEachMpqTest (AZ_SunkenTemple.wmo.MPQ) succeeded. -OpenEachMpqTest (AZ_SunkenTemple_Instance.wmo.MPQ) succeeded. -OpenEachMpqTest (SunkenTemple.wmo.MPQ) succeeded. -OpenEachMpqTest (collintest.wmo.MPQ) succeeded. -OpenEachMpqTest (missingwmo.wmo.MPQ) succeeded. -OpenEachMpqTest (test.wmo.MPQ) succeeded. -OpenEachMpqTest (ThousandNeedlesElevator.wmo.MPQ) succeeded. -OpenEachMpqTest (AZRClassicalElfRuin01.wmo.MPQ) succeeded. -OpenEachMpqTest (AZRClassicalElfRuin02.wmo.MPQ) succeeded. -OpenEachMpqTest (AZRClassicalElfRuin03.wmo.MPQ) succeeded. -OpenEachMpqTest (AZRClassicalElfRuin04.wmo.MPQ) succeeded. -OpenEachMpqTest (AZRClassicalElfRuin05.wmo.MPQ) succeeded. -OpenEachMpqTest (AZRClassicalElfRuin06.wmo.MPQ) succeeded. -OpenEachMpqTest (AZRClassicalElfRuin07.wmo.MPQ) succeeded. -OpenEachMpqTest (AZRClassicalElfRuin08.wmo.MPQ) succeeded. -OpenEachMpqTest (AZRClassicalElfRuin09.wmo.MPQ) succeeded. -OpenEachMpqTest (AZRClassicalElfRuin10.wmo.MPQ) succeeded. -OpenEachMpqTest (ClassicalElfRuin01.wmo.MPQ) succeeded. -OpenEachMpqTest (ClassicalElfRuin02.wmo.MPQ) succeeded. -OpenEachMpqTest (ClassicalElfRuin03.wmo.MPQ) succeeded. -OpenEachMpqTest (ClassicalElfRuin04.wmo.MPQ) succeeded. -OpenEachMpqTest (ClassicalElfRuin05.wmo.MPQ) succeeded. -OpenEachMpqTest (ClassicalElfRuin06.wmo.MPQ) succeeded. -OpenEachMpqTest (ClassicalElfRuin07.wmo.MPQ) succeeded. -OpenEachMpqTest (ClassicalElfRuin08.wmo.MPQ) succeeded. -OpenEachMpqTest (ClassicalElfTemple.wmo.MPQ) succeeded. -OpenEachMpqTest (ClassicalElfTemple2.wmo.MPQ) succeeded. -OpenEachMpqTest (GoblinHut.wmo.MPQ) succeeded. -OpenEachMpqTest (GoblinLab.wmo.MPQ) succeeded. -OpenEachMpqTest (NagaPagoda01.wmo.MPQ) succeeded. -OpenEachMpqTest (DSNightElf2Story.wmo.MPQ) succeeded. -OpenEachMpqTest (NightElf2Story.wmo.MPQ) succeeded. -OpenEachMpqTest (NightElfAbbey.wmo.MPQ) succeeded. -OpenEachMpqTest (DSNightElfDruidTower.wmo.MPQ) succeeded. -OpenEachMpqTest (NightElfDruidTower.wmo.MPQ) succeeded. -OpenEachMpqTest (DSNightElfHuntersLodge.wmo.MPQ) succeeded. -OpenEachMpqTest (NightElfHuntersLodge.wmo.MPQ) succeeded. -OpenEachMpqTest (DSNightElfInn.wmo.MPQ) succeeded. -OpenEachMpqTest (NightElfInn.wmo.MPQ) succeeded. -OpenEachMpqTest (DSNightElfMoonWell.wmo.MPQ) succeeded. -OpenEachMpqTest (DSNightElfMoonWellOrnate.wmo.MPQ) succeeded. -OpenEachMpqTest (GiantMoonwell.wmo.MPQ) succeeded. -OpenEachMpqTest (NightElfMoonWell.wmo.MPQ) succeeded. -OpenEachMpqTest (NightElfMoonWellOrnate.wmo.MPQ) succeeded. -OpenEachMpqTest (DSNightElfSmallHouse.wmo.MPQ) succeeded. -OpenEachMpqTest (NightElfSmallHouse.wmo.MPQ) succeeded. -OpenEachMpqTest (southGate.wmo.MPQ) succeeded. -OpenEachMpqTest (AbandonedOrcBarracks.wmo.MPQ) succeeded. -OpenEachMpqTest (BlackrockOrcBarracks.wmo.MPQ) succeeded. -OpenEachMpqTest (OrcBarracks.wmo.MPQ) succeeded. -OpenEachMpqTest (SwampOrcBarracks.wmo.MPQ) succeeded. -OpenEachMpqTest (AbandonedOrcBlacksmith.wmo.MPQ) succeeded. -OpenEachMpqTest (BlackrockOrcBlacksmith.wmo.MPQ) succeeded. -OpenEachMpqTest (orcblacksmith.wmo.MPQ) succeeded. -OpenEachMpqTest (SwampOrcBlacksmith.wmo.MPQ) succeeded. -OpenEachMpqTest (BlackrockOrcFortress.wmo.MPQ) succeeded. -OpenEachMpqTest (OrcFortress.wmo.MPQ) succeeded. -OpenEachMpqTest (SwampOrcFortress.wmo.MPQ) succeeded. -OpenEachMpqTest (AbandonedOrcGreatHall.wmo.MPQ) succeeded. -OpenEachMpqTest (BlackrockOrcGreatHall.wmo.MPQ) succeeded. -OpenEachMpqTest (OrcGreatHall.wmo.MPQ) succeeded. -OpenEachMpqTest (SwampOrcGreatHall.wmo.MPQ) succeeded. -OpenEachMpqTest (AbandonedOrcKennel.wmo.MPQ) succeeded. -OpenEachMpqTest (BlackrockOrcKennel.wmo.MPQ) succeeded. -OpenEachMpqTest (OrcKennel.wmo.MPQ) succeeded. -OpenEachMpqTest (SwampOrcKennel.wmo.MPQ) succeeded. -OpenEachMpqTest (abandonedOrcMageTower.wmo.MPQ) succeeded. -OpenEachMpqTest (BlackrockOrcMageTower.wmo.MPQ) succeeded. -OpenEachMpqTest (OrcMageTower.wmo.MPQ) succeeded. -OpenEachMpqTest (SwampOrcMageTower.wmo.MPQ) succeeded. -OpenEachMpqTest (AbandonedOrcMedium.wmo.MPQ) succeeded. -OpenEachMpqTest (BlackrockOrcMedium.wmo.MPQ) succeeded. -OpenEachMpqTest (OrcMedium.wmo.MPQ) succeeded. -OpenEachMpqTest (SwampOrcMedium.wmo.MPQ) succeeded. -OpenEachMpqTest (AbandonedOrcTower.wmo.MPQ) succeeded. -OpenEachMpqTest (BlackrockOrcTower.wmo.MPQ) succeeded. -OpenEachMpqTest (OrcTower.wmo.MPQ) succeeded. -OpenEachMpqTest (SwampOrcTower.wmo.MPQ) succeeded. -OpenEachMpqTest (Bighouse.wmo.MPQ) succeeded. -OpenEachMpqTest (Hut.wmo.MPQ) succeeded. -OpenEachMpqTest (Ladder.wmo.MPQ) succeeded. -OpenEachMpqTest (Wallhut.wmo.MPQ) succeeded. -OpenEachMpqTest (Wallhut2.wmo.MPQ) succeeded. -OpenEachMpqTest (TanarisRuins01.wmo.MPQ) succeeded. -OpenEachMpqTest (TanarisRuins02.wmo.MPQ) succeeded. -OpenEachMpqTest (TanarisRuins03.wmo.MPQ) succeeded. -OpenEachMpqTest (TanarisRuins04.wmo.MPQ) succeeded. -OpenEachMpqTest (TanarisRuins05.wmo.MPQ) succeeded. -OpenEachMpqTest (TanarisRuins06.wmo.MPQ) succeeded. -OpenEachMpqTest (TanarisRuins07.wmo.MPQ) succeeded. -OpenEachMpqTest (TanarisRuins09.wmo.MPQ) succeeded. -OpenEachMpqTest (TanarisRuins11.wmo.MPQ) succeeded. -OpenEachMpqTest (TanarisRuins12.wmo.MPQ) succeeded. -OpenEachMpqTest (TanarisRuins13.wmo.MPQ) succeeded. -OpenEachMpqTest (TanarisRuins14.wmo.MPQ) succeeded. -OpenEachMpqTest (TaurenDruidTent.wmo.MPQ) succeeded. -OpenEachMpqTest (TaurenHunterTent.wmo.MPQ) succeeded. -OpenEachMpqTest (TaurenChickenHut.wmo.MPQ) succeeded. -OpenEachMpqTest (TaurenHutA.wmo.MPQ) succeeded. -OpenEachMpqTest (TaurenHutB.wmo.MPQ) succeeded. -OpenEachMpqTest (TaurenHutBig.wmo.MPQ) succeeded. -OpenEachMpqTest (TaurenHutC.wmo.MPQ) succeeded. -OpenEachMpqTest (TaurenHutD.wmo.MPQ) succeeded. -OpenEachMpqTest (TaurenTallHut.wmo.MPQ) succeeded. -OpenEachMpqTest (TaurenTepee.wmo.MPQ) succeeded. -OpenEachMpqTest (TaurenLonghouse.wmo.MPQ) succeeded. -OpenEachMpqTest (TaurenShamanTent.wmo.MPQ) succeeded. -OpenEachMpqTest (Trollbridge.wmo.MPQ) succeeded. -OpenEachMpqTest (AbandonedTrollBurrow.wmo.MPQ) succeeded. -OpenEachMpqTest (BlackrockTrollBurrow.wmo.MPQ) succeeded. -OpenEachMpqTest (SwampTrollBurrow.wmo.MPQ) succeeded. -OpenEachMpqTest (TrollBurrow.wmo.MPQ) succeeded. -OpenEachMpqTest (troll_hotel01.wmo.MPQ) succeeded. -OpenEachMpqTest (troll_hotel_burn01.wmo.MPQ) succeeded. -OpenEachMpqTest (trollhut01.wmo.MPQ) succeeded. -OpenEachMpqTest (trollhutSmall01.wmo.MPQ) succeeded. -OpenEachMpqTest (trollhut_burn01.wmo.MPQ) succeeded. -OpenEachMpqTest (WyvernNest.wmo.MPQ) succeeded. -OpenEachMpqTest (DarkshoreBridge01.wmo.MPQ) succeeded. -OpenEachMpqTest (DarkshoreBridge02.wmo.MPQ) succeeded. -OpenEachMpqTest (DarkshoreBridge03.wmo.MPQ) succeeded. -OpenEachMpqTest (DarkshoreBridge04.wmo.MPQ) succeeded. -OpenEachMpqTest (DarkshoreDocks01.wmo.MPQ) succeeded. -OpenEachMpqTest (DarkshoreDocks02.wmo.MPQ) succeeded. -OpenEachMpqTest (DarkshoreDocks03.wmo.MPQ) succeeded. -OpenEachMpqTest (DarkshoreDocksAberdeen.wmo.MPQ) succeeded. -OpenEachMpqTest (DarkshoreDocksCurve.wmo.MPQ) succeeded. -OpenEachMpqTest (GiantSeaTurtle01.wmo.MPQ) succeeded. -OpenEachMpqTest (GiantSeaTurtle02.wmo.MPQ) succeeded. -OpenEachMpqTest (SnakeSpineGiantArch.wmo.MPQ) succeeded. -OpenEachMpqTest (DurotarBridge01.wmo.MPQ) succeeded. -OpenEachMpqTest (DurotarRootedRock03.wmo.MPQ) succeeded. -OpenEachMpqTest (DurotarGate.wmo.MPQ) succeeded. -OpenEachMpqTest (CrashedZippelin.wmo.MPQ) succeeded. -OpenEachMpqTest (DustWallowFootbridge.wmo.MPQ) succeeded. -OpenEachMpqTest (FeralasStoneBridge01.wmo.MPQ) succeeded. -OpenEachMpqTest (KalidarBridge01.wmo.MPQ) succeeded. -OpenEachMpqTest (KalidarDock01.wmo.MPQ) succeeded. -OpenEachMpqTest (KalidarTreeBranch.wmo.MPQ) succeeded. -OpenEachMpqTest (MoongladeBridge.wmo.MPQ) succeeded. -OpenEachMpqTest (CentaurTent02.wmo.MPQ) succeeded. -OpenEachMpqTest (CentaurTent03.wmo.MPQ) succeeded. -OpenEachMpqTest (Crossroadsbridge.wmo.MPQ) succeeded. -OpenEachMpqTest (TaurenBridge01.wmo.MPQ) succeeded. -OpenEachMpqTest (TaurenTent01.wmo.MPQ) succeeded. -OpenEachMpqTest (Orcbridge.wmo.MPQ) succeeded. -OpenEachMpqTest (LandingPad01.wmo.MPQ) succeeded. -OpenEachMpqTest (MonsterLogMachine_01.wmo.MPQ) succeeded. -OpenEachMpqTest (StonetalonWheelPlatform.wmo.MPQ) succeeded. -OpenEachMpqTest (TrollTentSand01.wmo.MPQ) succeeded. -OpenEachMpqTest (1000NeedlesBridge.wmo.MPQ) succeeded. -OpenEachMpqTest (Darnassis.wmo.MPQ) succeeded. -OpenEachMpqTest (Ogrimmar.wmo.MPQ) succeeded. -OpenEachMpqTest (DruidMesaA.wmo.MPQ) succeeded. -OpenEachMpqTest (DruidMesaB.wmo.MPQ) succeeded. -OpenEachMpqTest (GiantTotem.wmo.MPQ) succeeded. -OpenEachMpqTest (LowerMesaA.wmo.MPQ) succeeded. -OpenEachMpqTest (LowerMesaB.wmo.MPQ) succeeded. -OpenEachMpqTest (LowerMesaC.wmo.MPQ) succeeded. -OpenEachMpqTest (LowerMesaD.wmo.MPQ) succeeded. -OpenEachMpqTest (LowerMesaE.wmo.MPQ) succeeded. -OpenEachMpqTest (LowerMesaF.wmo.MPQ) succeeded. -OpenEachMpqTest (MidMesaA.wmo.MPQ) succeeded. -OpenEachMpqTest (MidMesaB.wmo.MPQ) succeeded. -OpenEachMpqTest (MidMesaC.wmo.MPQ) succeeded. -OpenEachMpqTest (MidMesaD.wmo.MPQ) succeeded. -OpenEachMpqTest (ShamanMesa.wmo.MPQ) succeeded. -OpenEachMpqTest (UndeadCave.wmo.MPQ) succeeded. -OpenEachMpqTest (UpperMesaA.wmo.MPQ) succeeded. -OpenEachMpqTest (UpperMesaB.wmo.MPQ) succeeded. -OpenEachMpqTest (UpperMesaC.wmo.MPQ) succeeded. -OpenEachMpqTest (UpperMesaD.wmo.MPQ) succeeded. -OpenEachMpqTest (UpperMesaE.wmo.MPQ) succeeded. -OpenEachMpqTest (WarriorMesaA.wmo.MPQ) succeeded. -OpenEachMpqTest (WarriorMesaB.wmo.MPQ) succeeded. -OpenEachMpqTest (AnvilMar.wmo.MPQ) succeeded. -OpenEachMpqTest (mud_hovel.wmo.MPQ) succeeded. -OpenEachMpqTest (hovel_machine.wmo.MPQ) succeeded. -OpenEachMpqTest (snow_hovel.wmo.MPQ) succeeded. -OpenEachMpqTest (mud_2story.wmo.MPQ) succeeded. -OpenEachMpqTest (snow_2story.wmo.MPQ) succeeded. -OpenEachMpqTest (snow_dwarfbarracks.wmo.MPQ) succeeded. -OpenEachMpqTest (wet_dwarfbarracks.wmo.MPQ) succeeded. -OpenEachMpqTest (snow_blacksmith.wmo.MPQ) succeeded. -OpenEachMpqTest (wetland_blacksmith.wmo.MPQ) succeeded. -OpenEachMpqTest (Dwarven_GriffonAviary.wmo.MPQ) succeeded. -OpenEachMpqTest (Dwarven_GuardTower.wmo.MPQ) succeeded. -OpenEachMpqTest (Dwarven_SnowStable.wmo.MPQ) succeeded. -OpenEachMpqTest (Dwarven_SnowTower.wmo.MPQ) succeeded. -OpenEachMpqTest (Dwarven_Stable.wmo.MPQ) succeeded. -OpenEachMpqTest (Snow_Tavern.wmo.MPQ) succeeded. -OpenEachMpqTest (wet_Tavern.wmo.MPQ) succeeded. -OpenEachMpqTest (GreatWall_Gate.wmo.MPQ) succeeded. -OpenEachMpqTest (GreatWall_tower_01.wmo.MPQ) succeeded. -OpenEachMpqTest (GreatWall_tower_02.wmo.MPQ) succeeded. -OpenEachMpqTest (GreatWall_wall_01.wmo.MPQ) succeeded. -OpenEachMpqTest (GreatWall_wall_02.wmo.MPQ) succeeded. -OpenEachMpqTest (GreatWall_wall_03.wmo.MPQ) succeeded. -OpenEachMpqTest (GreatWall_wall_04.wmo.MPQ) succeeded. -OpenEachMpqTest (ThandolSpan.wmo.MPQ) succeeded. -OpenEachMpqTest (Wetlands_GrimBatol.wmo.MPQ) succeeded. -OpenEachMpqTest (ironforge.wmo.MPQ) succeeded. -OpenEachMpqTest (DwarvenDam01.wmo.MPQ) succeeded. -OpenEachMpqTest (DwarvenDock01.wmo.MPQ) succeeded. -OpenEachMpqTest (DwarvenSentinel01.wmo.MPQ) succeeded. -OpenEachMpqTest (DwarvenSentinel02.wmo.MPQ) succeeded. -OpenEachMpqTest (ExcavationPlatform01.wmo.MPQ) succeeded. -OpenEachMpqTest (ExcavationPlatform02.wmo.MPQ) succeeded. -OpenEachMpqTest (ExcavationPlatform03.wmo.MPQ) succeeded. -OpenEachMpqTest (NetherguardWall.wmo.MPQ) succeeded. -OpenEachMpqTest (GreenHouse01.wmo.MPQ) succeeded. -OpenEachMpqTest (Cathedral.wmo.MPQ) succeeded. -OpenEachMpqTest (SlaughterHouse.wmo.MPQ) succeeded. -OpenEachMpqTest (UndeadZiggurat.wmo.MPQ) succeeded. -OpenEachMpqTest (UtherShrine.wmo.MPQ) succeeded. -OpenEachMpqTest (BridgeBigWhite.wmo.MPQ) succeeded. -OpenEachMpqTest (ArathiStoneBridge01.wmo.MPQ) succeeded. -OpenEachMpqTest (ArathiStoneBridge02.wmo.MPQ) succeeded. -OpenEachMpqTest (ChimneyTop.wmo.MPQ) succeeded. -OpenEachMpqTest (HuRuinedBuildingsBig01.wmo.MPQ) succeeded. -OpenEachMpqTest (HuRuinedBuildingsBig02.wmo.MPQ) succeeded. -OpenEachMpqTest (HuRuinedBuildingsBig03.wmo.MPQ) succeeded. -OpenEachMpqTest (HuRuinedBuildingsMed01.wmo.MPQ) succeeded. -OpenEachMpqTest (HuRuinedBuildingsMed02.wmo.MPQ) succeeded. -OpenEachMpqTest (HuRuinedBuildingsSmall01.wmo.MPQ) succeeded. -OpenEachMpqTest (HuRuinedBuildingsSmall02.wmo.MPQ) succeeded. -OpenEachMpqTest (WreckedBuildingHCorner01.wmo.MPQ) succeeded. -OpenEachMpqTest (WreckedBuildingHCorner02.wmo.MPQ) succeeded. -OpenEachMpqTest (PlaguelandsBridge.wmo.MPQ) succeeded. -OpenEachMpqTest (Undercity.wmo.MPQ) succeeded. -OpenEachMpqTest (Undercitywall01.wmo.MPQ) succeeded. -OpenEachMpqTest (Undercity_test01.wmo.MPQ) succeeded. -OpenEachMpqTest (HumanLevelOneTest.wmo.MPQ) succeeded. -OpenEachMpqTest (HumanLevelThreeTest.wmo.MPQ) succeeded. -OpenEachMpqTest (transportship_A.wmo.MPQ) succeeded. -OpenEachMpqTest (base.MPQ) succeeded. -OpenEachMpqTest (dbc.MPQ) succeeded. -OpenEachMpqTest (fonts.MPQ) succeeded. -OpenEachMpqTest (interface.MPQ) succeeded. -OpenEachMpqTest (misc.MPQ) succeeded. -OpenEachMpqTest (model.MPQ) succeeded. -OpenEachMpqTest (sound.MPQ) succeeded. -OpenEachMpqTest (speech.MPQ) succeeded. -OpenEachMpqTest (terrain.MPQ) succeeded. -OpenEachMpqTest (texture.MPQ) succeeded. -OpenEachMpqTest (wmo.MPQ) succeeded. -OpenEachMpqTest (base.MPQ) succeeded. -OpenEachMpqTest (dbc.MPQ) succeeded. -OpenEachMpqTest (fonts.MPQ) succeeded. -OpenEachMpqTest (interface.MPQ) succeeded. -OpenEachMpqTest (misc.MPQ) succeeded. -OpenEachMpqTest (model.MPQ) succeeded. -OpenEachMpqTest (sound.MPQ) succeeded. -OpenEachMpqTest (speech.MPQ) succeeded. -OpenEachMpqTest (terrain.MPQ) succeeded. -OpenEachMpqTest (texture.MPQ) succeeded. -OpenEachMpqTest (wmo.MPQ) succeeded. -OpenEachMpqTest (base.MPQ) succeeded. -OpenEachMpqTest (dbc.MPQ) succeeded. -OpenEachMpqTest (expansion.MPQ) succeeded. -OpenEachMpqTest (expansionLoc.MPQ) succeeded. -OpenEachMpqTest (fonts.MPQ) succeeded. -OpenEachMpqTest (interface.MPQ) succeeded. -OpenEachMpqTest (misc.MPQ) succeeded. -OpenEachMpqTest (model.MPQ) succeeded. -OpenEachMpqTest (patch.MPQ) succeeded. -OpenEachMpqTest (sound.MPQ) succeeded. -OpenEachMpqTest (speech.MPQ) succeeded. -OpenEachMpqTest (terrain.MPQ) succeeded. -OpenEachMpqTest (texture.MPQ) succeeded. -OpenEachMpqTest (wmo.MPQ) succeeded. -OpenEachMpqTest (backup-enGB.MPQ) succeeded. -OpenEachMpqTest (base-enGB.MPQ) succeeded. -OpenEachMpqTest (common.MPQ) succeeded. -OpenEachMpqTest (expansion-locale-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion.MPQ) succeeded. -OpenEachMpqTest (locale-enGB.MPQ) succeeded. -OpenEachMpqTest (speech-enGB.MPQ) succeeded. -OpenEachMpqTest (common.MPQ) succeeded. -OpenEachMpqTest (backup-enGB.MPQ) succeeded. -OpenEachMpqTest (base-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion-locale-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (locale-enGB.MPQ) succeeded. -OpenEachMpqTest (speech-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion.MPQ) succeeded. -OpenEachMpqTest (Installer Tome.mpq) succeeded. -OpenEachMpqTest (common-2.MPQ) succeeded. -OpenEachMpqTest (common.MPQ) succeeded. -OpenEachMpqTest (base-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion-locale-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (lichking-locale-enGB.MPQ) succeeded. -OpenEachMpqTest (lichking-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (locale-enGB.MPQ) succeeded. -OpenEachMpqTest (speech-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion.MPQ) succeeded. -OpenEachMpqTest (lichking.MPQ) succeeded. -OpenEachMpqTest (installer tome.mpq.part) succeeded. -OpenEachMpqTest (movies.mpq.part) succeeded. -OpenEachMpqTest (dbc.MPQ.0) succeeded. -OpenEachMpqTest (fonts.MPQ.0) succeeded. -OpenEachMpqTest (interface.MPQ.0) succeeded. -OpenEachMpqTest (misc.MPQ.0) succeeded. -OpenEachMpqTest (model.MPQ.0) succeeded. -OpenEachMpqTest (patch.MPQ) succeeded. -OpenEachMpqTest (sound.MPQ.0) succeeded. -OpenEachMpqTest (speech.MPQ.0) succeeded. -OpenEachMpqTest (streaming.MPQ.0) succeeded. -OpenEachMpqTest (streamingloc.MPQ.0) succeeded. -OpenEachMpqTest (terrain.MPQ.0) succeeded. -OpenEachMpqTest (texture.MPQ.0) succeeded. -OpenEachMpqTest (wmo.MPQ.0) succeeded. -OpenEachMpqTest (dbc.MPQ.part) succeeded. -OpenEachMpqTest (locale-enGB.MPQ) succeeded. -OpenEachMpqTest (fonts.MPQ.part) succeeded. -OpenEachMpqTest (interface.MPQ.part) succeeded. -OpenEachMpqTest (misc.MPQ.part) succeeded. -OpenEachMpqTest (model.MPQ.part) succeeded. -OpenEachMpqTest (patch.MPQ.part) succeeded. -OpenEachMpqTest (sound.MPQ.part) succeeded. -OpenEachMpqTest (speech.MPQ.part) succeeded. -OpenEachMpqTest (streaming.MPQ.part) succeeded. -OpenEachMpqTest (streamingloc.MPQ.part) succeeded. -OpenEachMpqTest (terrain.MPQ.part) succeeded. -OpenEachMpqTest (texture.MPQ.part) succeeded. -OpenEachMpqTest (wmo.MPQ.part) succeeded. -OpenEachMpqTest (WoW-3.3.0.10958-4.0.0.12911-EU-Stage-1.mpq) succeeded. -OpenEachMpqTest (dbc.MPQ.part) succeeded. -OpenEachMpqTest (locale-enGB.MPQ) succeeded. -OpenEachMpqTest (fonts.MPQ.part) succeeded. -OpenEachMpqTest (interface.MPQ.part) succeeded. -OpenEachMpqTest (misc.MPQ.part) succeeded. -OpenEachMpqTest (model.MPQ.part) succeeded. -OpenEachMpqTest (patch.MPQ.part) succeeded. -OpenEachMpqTest (sound.MPQ.part) succeeded. -OpenEachMpqTest: Failed to open archive \Multimedia\MPQs\2004 - WoW\11403\Data\SoundCache.MPQ (error code: 11) -OpenEachMpqTest (speech.MPQ.part) succeeded. -OpenEachMpqTest (streaming.MPQ.part) succeeded. -OpenEachMpqTest (streamingloc.MPQ.part) succeeded. -OpenEachMpqTest (terrain.MPQ.part) succeeded. -OpenEachMpqTest (texture.MPQ.part) succeeded. -OpenEachMpqTest (wmo.MPQ.part) succeeded. -OpenEachMpqTest (Installer Tome 2.mpq.part) succeeded. -OpenEachMpqTest: Failed to open archive \Multimedia\MPQs\2004 - WoW\11927\Installer Tome.mpq.1.part (error code: 11) -OpenEachMpqTest (Installer Tome.mpq.part) succeeded. -OpenEachMpqTest (expansion-locale-frFR.MPQ) succeeded. -OpenEachMpqTest (art.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (locale-enGB.MPQ) succeeded. -OpenEachMpqTest (speech-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion1.MPQ) succeeded. -OpenEachMpqTest (expansion2.MPQ) succeeded. -OpenEachMpqTest (expansion3.MPQ) succeeded. -OpenEachMpqTest (sound.MPQ) succeeded. -OpenEachMpqTest (world.MPQ) succeeded. -OpenEachMpqTest (wow-update-12694.MPQ) succeeded. -OpenEachMpqTest (wow-update-12759.MPQ) succeeded. -OpenEachMpqTest (wow-update-12803.MPQ) succeeded. -OpenEachMpqTest (wow-update-12857.MPQ) succeeded. -OpenEachMpqTest (wow-update-12942.MPQ) succeeded. -OpenEachMpqTest (wow-update-12984.MPQ) succeeded. -OpenEachMpqTest (wow-update-13066.MPQ) succeeded. -OpenEachMpqTest (wow-update-13117.MPQ) succeeded. -OpenEachMpqTest (wow-update-13183.MPQ) succeeded. -OpenEachMpqTest (wow-update-13189.MPQ) succeeded. -OpenEachMpqTest (wow-update-13195.MPQ) succeeded. -OpenEachMpqTest (wow-update-13202.MPQ) succeeded. -OpenEachMpqTest (wow-update-13221.MPQ) succeeded. -OpenEachMpqTest (wow-update-13241.MPQ) succeeded. -OpenEachMpqTest (wow-update-13277.MPQ) succeeded. -OpenEachMpqTest (wow-update-13316.MPQ) succeeded. -OpenEachMpqTest (wow-12635-OSX-final.MPQ) succeeded. -OpenEachMpqTest (wow-12635-Win-final.MPQ) succeeded. -OpenEachMpqTest (wow-12694-OSX-final.MPQ) succeeded. -OpenEachMpqTest (wow-12694-Win-final.MPQ) succeeded. -OpenEachMpqTest (wow-12759-OSX-final.MPQ) succeeded. -OpenEachMpqTest (wow-12759-Win-final.MPQ) succeeded. -OpenEachMpqTest (base-OSX.MPQ) succeeded. -OpenEachMpqTest (base-Win.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (locale-enGB.MPQ) succeeded. -OpenEachMpqTest (OldWorld-enGB.MPQ) succeeded. -OpenEachMpqTest (speech-enGB.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-13623.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-13914.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-14007.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-14333.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-14480.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-14545.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-14946.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-15005.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-15050.MPQ) succeeded. -OpenEachMpqTest (locale-enGB.MPQ) succeeded. -OpenEachMpqTest (speech-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion1.MPQ) succeeded. -OpenEachMpqTest (expansion2.MPQ) succeeded. -OpenEachMpqTest (expansion3.MPQ) succeeded. -OpenEachMpqTest (OldWorld.MPQ) succeeded. -OpenEachMpqTest (sound.MPQ) succeeded. -OpenEachMpqTest (world.MPQ) succeeded. -OpenEachMpqTest (wow-update-13164.MPQ) succeeded. -OpenEachMpqTest (wow-update-13205.MPQ) succeeded. -OpenEachMpqTest (wow-update-13287.MPQ) succeeded. -OpenEachMpqTest (wow-update-13329.MPQ) succeeded. -OpenEachMpqTest (wow-update-13596.MPQ) succeeded. -OpenEachMpqTest (wow-update-13623.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-13914.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-14007.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-14333.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-14480.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-14545.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-14946.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-15005.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-15050.MPQ) succeeded. -OpenEachMpqTest (wow-update-oldworld-13154.MPQ) succeeded. -OpenEachMpqTest (wow-update-oldworld-13286.MPQ) succeeded. -OpenEachMpqTest (wow-update-12941.MPQ) succeeded. -OpenEachMpqTest (wow-update-12984.MPQ) succeeded. -OpenEachMpqTest (SoundCache-patch-13154.MPQ) succeeded. -OpenEachMpqTest (SoundCache-patch-13164.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-13417.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-13449.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-13482.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-13529.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-13561.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-13596.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-13682.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-13698.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-13707.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-13726.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-13750.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-13793.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-13812.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-13850.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-13875.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-13914.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-14002.MPQ) succeeded. -OpenEachMpqTest (locale-zhCN.MPQ) succeeded. -OpenEachMpqTest (alternate.MPQ) succeeded. -OpenEachMpqTest (art.MPQ) succeeded. -OpenEachMpqTest (base-OSX.MPQ) succeeded. -OpenEachMpqTest (base-Win.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-deDE.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-deDE.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-deDE.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-deDE.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-deDE.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-deDE.MPQ) succeeded. -OpenEachMpqTest (locale-deDE.MPQ) succeeded. -OpenEachMpqTest (OldWorld-deDE.MPQ) succeeded. -OpenEachMpqTest (speech-deDE.MPQ) succeeded. -OpenEachMpqTest (wow-update-deDE-15211.MPQ) succeeded. -OpenEachMpqTest (wow-update-deDE-15354.MPQ) succeeded. -OpenEachMpqTest (wow-update-deDE-15595.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-enCN.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-enCN.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-enCN.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-enCN.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-enCN.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-enCN.MPQ) succeeded. -OpenEachMpqTest (locale-enCN.MPQ) succeeded. -OpenEachMpqTest (speech-enCN.MPQ) succeeded. -OpenEachMpqTest (wow-update-enCN-15211.MPQ) succeeded. -OpenEachMpqTest (wow-update-enCN-15354.MPQ) succeeded. -OpenEachMpqTest (wow-update-enCN-15595.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (locale-enGB.MPQ) succeeded. -OpenEachMpqTest (OldWorld-enGB.MPQ) succeeded. -OpenEachMpqTest (speech-enGB.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-15211.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-15354.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-15595.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-enTW.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-enTW.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-enTW.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-enTW.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-enTW.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-enTW.MPQ) succeeded. -OpenEachMpqTest (locale-enTW.MPQ) succeeded. -OpenEachMpqTest (OldWorld-enTW.MPQ) succeeded. -OpenEachMpqTest (speech-enTW.MPQ) succeeded. -OpenEachMpqTest (wow-update-enTW-15211.MPQ) succeeded. -OpenEachMpqTest (wow-update-enTW-15354.MPQ) succeeded. -OpenEachMpqTest (wow-update-enTW-15595.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-enUS.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-enUS.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-enUS.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-enUS.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-enUS.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-enUS.MPQ) succeeded. -OpenEachMpqTest (locale-enUS.MPQ) succeeded. -OpenEachMpqTest (OldWorld-enUS.MPQ) succeeded. -OpenEachMpqTest (speech-enUS.MPQ) succeeded. -OpenEachMpqTest (wow-update-enUS-15211.MPQ) succeeded. -OpenEachMpqTest (wow-update-enUS-15354.MPQ) succeeded. -OpenEachMpqTest (wow-update-enUS-15595.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-esES.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-esES.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-esES.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-esES.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-esES.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-esES.MPQ) succeeded. -OpenEachMpqTest (locale-esES.MPQ) succeeded. -OpenEachMpqTest (OldWorld-esES.MPQ) succeeded. -OpenEachMpqTest (speech-esES.MPQ) succeeded. -OpenEachMpqTest (wow-update-esES-15211.MPQ) succeeded. -OpenEachMpqTest (wow-update-esES-15354.MPQ) succeeded. -OpenEachMpqTest (wow-update-esES-15595.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-esMX.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-esMX.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-esMX.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-esMX.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-esMX.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-esMX.MPQ) succeeded. -OpenEachMpqTest (locale-esMX.MPQ) succeeded. -OpenEachMpqTest (OldWorld-esMX.MPQ) succeeded. -OpenEachMpqTest (speech-esMX.MPQ) succeeded. -OpenEachMpqTest (wow-update-esMX-15211.MPQ) succeeded. -OpenEachMpqTest (wow-update-esMX-15354.MPQ) succeeded. -OpenEachMpqTest (wow-update-esMX-15595.MPQ) succeeded. -OpenEachMpqTest (expansion1.MPQ) succeeded. -OpenEachMpqTest (expansion2.MPQ) succeeded. -OpenEachMpqTest (expansion3.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-frFR.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-frFR.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-frFR.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-frFR.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-frFR.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-frFR.MPQ) succeeded. -OpenEachMpqTest (locale-frFR.MPQ) succeeded. -OpenEachMpqTest (OldWorld-frFR.MPQ) succeeded. -OpenEachMpqTest (speech-frFR.MPQ) succeeded. -OpenEachMpqTest (wow-update-frFR-15211.MPQ) succeeded. -OpenEachMpqTest (wow-update-frFR-15354.MPQ) succeeded. -OpenEachMpqTest (wow-update-frFR-15595.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-koKR.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-koKR.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-koKR.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-koKR.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-koKR.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-koKR.MPQ) succeeded. -OpenEachMpqTest (locale-koKR.MPQ) succeeded. -OpenEachMpqTest (OldWorld-koKR.MPQ) succeeded. -OpenEachMpqTest (speech-koKR.MPQ) succeeded. -OpenEachMpqTest (wow-update-koKR-15211.MPQ) succeeded. -OpenEachMpqTest (wow-update-koKR-15354.MPQ) succeeded. -OpenEachMpqTest (wow-update-koKR-15595.MPQ) succeeded. -OpenEachMpqTest (MigrationContent_base1.MPQ) succeeded. -OpenEachMpqTest (MigrationContent_base2.MPQ) succeeded. -OpenEachMpqTest (OldWorld.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-ptBR.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-ptBR.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-ptBR.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-ptBR.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-ptBR.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-ptBR.MPQ) succeeded. -OpenEachMpqTest (locale-ptBR.MPQ) succeeded. -OpenEachMpqTest (speech-ptBR.MPQ) succeeded. -OpenEachMpqTest (wow-update-ptBR-15211.MPQ) succeeded. -OpenEachMpqTest (wow-update-ptBR-15354.MPQ) succeeded. -OpenEachMpqTest (wow-update-ptBR-15595.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-ptPT.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-ptPT.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-ptPT.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-ptPT.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-ptPT.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-ptPT.MPQ) succeeded. -OpenEachMpqTest (locale-ptPT.MPQ) succeeded. -OpenEachMpqTest (speech-ptPT.MPQ) succeeded. -OpenEachMpqTest (wow-update-ptPT-15211.MPQ) succeeded. -OpenEachMpqTest (wow-update-ptPT-15354.MPQ) succeeded. -OpenEachMpqTest (wow-update-ptPT-15595.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-ruRU.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-ruRU.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-ruRU.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-ruRU.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-ruRU.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-ruRU.MPQ) succeeded. -OpenEachMpqTest (locale-ruRU.MPQ) succeeded. -OpenEachMpqTest (OldWorld-ruRU.MPQ) succeeded. -OpenEachMpqTest (speech-ruRU.MPQ) succeeded. -OpenEachMpqTest (wow-update-ruRU-15211.MPQ) succeeded. -OpenEachMpqTest (wow-update-ruRU-15354.MPQ) succeeded. -OpenEachMpqTest (wow-update-ruRU-15595.MPQ) succeeded. -OpenEachMpqTest (sound.MPQ) succeeded. -OpenEachMpqTest (world.MPQ) succeeded. -OpenEachMpqTest (world2.MPQ) succeeded. -OpenEachMpqTest (wow-0-15595-OSX-final.MPQ) succeeded. -OpenEachMpqTest (wow-0-15595-Win-final.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-15211.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-15354.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-15595.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-zhCN.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-zhCN.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-zhCN.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-zhCN.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-zhCN.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-zhCN.MPQ) succeeded. -OpenEachMpqTest (locale-zhCN.MPQ) succeeded. -OpenEachMpqTest (speech-zhCN.MPQ) succeeded. -OpenEachMpqTest (wow-update-zhCN-15211.MPQ) succeeded. -OpenEachMpqTest (wow-update-zhCN-15354.MPQ) succeeded. -OpenEachMpqTest (wow-update-zhCN-15595.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-zhTW.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-zhTW.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-zhTW.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-zhTW.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-zhTW.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-zhTW.MPQ) succeeded. -OpenEachMpqTest (locale-zhTW.MPQ) succeeded. -OpenEachMpqTest (OldWorld-zhTW.MPQ) succeeded. -OpenEachMpqTest (speech-zhTW.MPQ) succeeded. -OpenEachMpqTest (wow-update-zhTW-15211.MPQ) succeeded. -OpenEachMpqTest (wow-update-zhTW-15354.MPQ) succeeded. -OpenEachMpqTest (wow-update-zhTW-15595.MPQ) succeeded. -OpenEachMpqTest (wow-0-15211-OSX-final.MPQ) succeeded. -OpenEachMpqTest (wow-0-15211-Win-final.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (SoundCache-patch-15508.MPQ) succeeded. -OpenEachMpqTest (alternate.MPQ) succeeded. -OpenEachMpqTest (Base-Win.mpq) succeeded. -OpenEachMpqTest (expansion1-locale-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion4-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (locale-enGB.MPQ) succeeded. -OpenEachMpqTest (patch-enGB.MPQ) succeeded. -OpenEachMpqTest (speech-enGB.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-15508.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-15544.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-15589.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-enUS.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-enUS.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-enUS.MPQ) succeeded. -OpenEachMpqTest (expansion4-speech-enUS.MPQ) succeeded. -OpenEachMpqTest (locale-enUS.MPQ) succeeded. -OpenEachMpqTest (patch-enUS.MPQ) succeeded. -OpenEachMpqTest (speech-enUS.MPQ) succeeded. -OpenEachMpqTest (wow-update-enUS-15508.MPQ) succeeded. -OpenEachMpqTest (wow-update-enUS-15544.MPQ) succeeded. -OpenEachMpqTest (wow-update-enUS-15589.MPQ) succeeded. -OpenEachMpqTest (expansion1.MPQ) succeeded. -OpenEachMpqTest (expansion2.MPQ) succeeded. -OpenEachMpqTest (expansion3.MPQ) succeeded. -OpenEachMpqTest (expansion4.MPQ) succeeded. -OpenEachMpqTest (interface.MPQ) succeeded. -OpenEachMpqTest (itemtexture.MPQ) succeeded. -OpenEachMpqTest (misc.MPQ) succeeded. -OpenEachMpqTest (model.MPQ) succeeded. -OpenEachMpqTest (sound.MPQ) succeeded. -OpenEachMpqTest (texture.MPQ) succeeded. -OpenEachMpqTest (wow-0-15508-OSX-final.MPQ) succeeded. -OpenEachMpqTest (wow-0-15508-Win-final.MPQ) succeeded. -OpenEachMpqTest (wow-0-15544-OSX-final.MPQ) succeeded. -OpenEachMpqTest (wow-0-15589-OSX-final.MPQ) succeeded. -OpenEachMpqTest (wow-0-15589-Win-final.MPQ) succeeded. -OpenEachMpqTest (world.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-15508.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-15544.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-15589.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-15851.MPQ) succeeded. -OpenEachMpqTest (wow-update-enUS-15851.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-15851.MPQ) succeeded. -OpenEachMpqTest (alternate.MPQ) succeeded. -OpenEachMpqTest (art.MPQ) succeeded. -OpenEachMpqTest (base-OSX.MPQ) succeeded. -OpenEachMpqTest (base-Win.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-deDE.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-deDE.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-deDE.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-deDE.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-deDE.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-deDE.MPQ) succeeded. -OpenEachMpqTest (expansion4-speech-deDE.MPQ) succeeded. -OpenEachMpqTest (locale-deDE.MPQ) succeeded. -OpenEachMpqTest (OldWorld-deDE.MPQ) succeeded. -OpenEachMpqTest (speech-deDE.MPQ) succeeded. -OpenEachMpqTest (wow-update-deDE-16016.MPQ) succeeded. -OpenEachMpqTest (wow-update-deDE-16048.MPQ) succeeded. -OpenEachMpqTest (wow-update-deDE-16057.MPQ) succeeded. -OpenEachMpqTest (wow-update-deDE-16309.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-enCN.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-enCN.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-enCN.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-enCN.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-enCN.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-enCN.MPQ) succeeded. -OpenEachMpqTest (expansion4-speech-enCN.MPQ) succeeded. -OpenEachMpqTest (locale-enCN.MPQ) succeeded. -OpenEachMpqTest (OldWorld-enCN.MPQ) succeeded. -OpenEachMpqTest (speech-enCN.MPQ) succeeded. -OpenEachMpqTest (wow-update-enCN-16016.MPQ) succeeded. -OpenEachMpqTest (wow-update-enCN-16048.MPQ) succeeded. -OpenEachMpqTest (wow-update-enCN-16057.MPQ) succeeded. -OpenEachMpqTest (wow-update-enCN-16309.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion4-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (locale-enGB.MPQ) succeeded. -OpenEachMpqTest (OldWorld-enGB.MPQ) succeeded. -OpenEachMpqTest (speech-enGB.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16016.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16048.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16057.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16309.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-enTW.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-enTW.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-enTW.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-enTW.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-enTW.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-enTW.MPQ) succeeded. -OpenEachMpqTest (expansion4-speech-enTW.MPQ) succeeded. -OpenEachMpqTest (locale-enTW.MPQ) succeeded. -OpenEachMpqTest (OldWorld-enTW.MPQ) succeeded. -OpenEachMpqTest (speech-enTW.MPQ) succeeded. -OpenEachMpqTest (wow-update-enTW-16016.MPQ) succeeded. -OpenEachMpqTest (wow-update-enTW-16048.MPQ) succeeded. -OpenEachMpqTest (wow-update-enTW-16057.MPQ) succeeded. -OpenEachMpqTest (wow-update-enTW-16309.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-enUS.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-enUS.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-enUS.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-enUS.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-enUS.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-enUS.MPQ) succeeded. -OpenEachMpqTest (expansion4-speech-enUS.MPQ) succeeded. -OpenEachMpqTest (locale-enUS.MPQ) succeeded. -OpenEachMpqTest (OldWorld-enUS.MPQ) succeeded. -OpenEachMpqTest (speech-enUS.MPQ) succeeded. -OpenEachMpqTest (wow-update-enUS-16016.MPQ) succeeded. -OpenEachMpqTest (wow-update-enUS-16048.MPQ) succeeded. -OpenEachMpqTest (wow-update-enUS-16057.MPQ) succeeded. -OpenEachMpqTest (wow-update-enUS-16309.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-esES.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-esES.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-esES.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-esES.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-esES.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-esES.MPQ) succeeded. -OpenEachMpqTest (expansion4-speech-esES.MPQ) succeeded. -OpenEachMpqTest (locale-esES.MPQ) succeeded. -OpenEachMpqTest (OldWorld-esES.MPQ) succeeded. -OpenEachMpqTest (speech-esES.MPQ) succeeded. -OpenEachMpqTest (wow-update-esES-16016.MPQ) succeeded. -OpenEachMpqTest (wow-update-esES-16048.MPQ) succeeded. -OpenEachMpqTest (wow-update-esES-16057.MPQ) succeeded. -OpenEachMpqTest (wow-update-esES-16309.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-esMX.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-esMX.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-esMX.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-esMX.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-esMX.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-esMX.MPQ) succeeded. -OpenEachMpqTest (expansion4-speech-esMX.MPQ) succeeded. -OpenEachMpqTest (locale-esMX.MPQ) succeeded. -OpenEachMpqTest (OldWorld-esMX.MPQ) succeeded. -OpenEachMpqTest (speech-esMX.MPQ) succeeded. -OpenEachMpqTest (wow-update-esMX-16016.MPQ) succeeded. -OpenEachMpqTest (wow-update-esMX-16048.MPQ) succeeded. -OpenEachMpqTest (wow-update-esMX-16057.MPQ) succeeded. -OpenEachMpqTest (wow-update-esMX-16309.MPQ) succeeded. -OpenEachMpqTest (expansion1.MPQ) succeeded. -OpenEachMpqTest (expansion2.MPQ) succeeded. -OpenEachMpqTest (expansion3.MPQ) succeeded. -OpenEachMpqTest (expansion4.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-frFR.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-frFR.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-frFR.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-frFR.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-frFR.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-frFR.MPQ) succeeded. -OpenEachMpqTest (expansion4-speech-frFR.MPQ) succeeded. -OpenEachMpqTest (locale-frFR.MPQ) succeeded. -OpenEachMpqTest (OldWorld-frFR.MPQ) succeeded. -OpenEachMpqTest (speech-frFR.MPQ) succeeded. -OpenEachMpqTest (wow-update-frFR-16016.MPQ) succeeded. -OpenEachMpqTest (wow-update-frFR-16048.MPQ) succeeded. -OpenEachMpqTest (wow-update-frFR-16057.MPQ) succeeded. -OpenEachMpqTest (wow-update-frFR-16309.MPQ) succeeded. -OpenEachMpqTest (interface.MPQ) succeeded. -OpenEachMpqTest (itemtexture.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-itIT.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-itIT.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-itIT.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-itIT.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-itIT.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-itIT.MPQ) succeeded. -OpenEachMpqTest (expansion4-speech-itIT.MPQ) succeeded. -OpenEachMpqTest (locale-itIT.MPQ) succeeded. -OpenEachMpqTest (OldWorld-itIT.MPQ) succeeded. -OpenEachMpqTest (speech-itIT.MPQ) succeeded. -OpenEachMpqTest (wow-update-itIT-16016.MPQ) succeeded. -OpenEachMpqTest (wow-update-itIT-16048.MPQ) succeeded. -OpenEachMpqTest (wow-update-itIT-16057.MPQ) succeeded. -OpenEachMpqTest (wow-update-itIT-16309.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-koKR.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-koKR.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-koKR.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-koKR.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-koKR.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-koKR.MPQ) succeeded. -OpenEachMpqTest (expansion4-speech-koKR.MPQ) succeeded. -OpenEachMpqTest (locale-koKR.MPQ) succeeded. -OpenEachMpqTest (OldWorld-koKR.MPQ) succeeded. -OpenEachMpqTest (speech-koKR.MPQ) succeeded. -OpenEachMpqTest (wow-update-koKR-16016.MPQ) succeeded. -OpenEachMpqTest (wow-update-koKR-16048.MPQ) succeeded. -OpenEachMpqTest (wow-update-koKR-16057.MPQ) succeeded. -OpenEachMpqTest (wow-update-koKR-16309.MPQ) succeeded. -OpenEachMpqTest (misc.MPQ) succeeded. -OpenEachMpqTest (model.MPQ) succeeded. -OpenEachMpqTest (OldWorld.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-ptBR.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-ptBR.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-ptBR.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-ptBR.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-ptBR.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-ptBR.MPQ) succeeded. -OpenEachMpqTest (expansion4-speech-ptBR.MPQ) succeeded. -OpenEachMpqTest (locale-ptBR.MPQ) succeeded. -OpenEachMpqTest (OldWorld-ptBR.MPQ) succeeded. -OpenEachMpqTest (speech-ptBR.MPQ) succeeded. -OpenEachMpqTest (wow-update-ptBR-16016.MPQ) succeeded. -OpenEachMpqTest (wow-update-ptBR-16048.MPQ) succeeded. -OpenEachMpqTest (wow-update-ptBR-16057.MPQ) succeeded. -OpenEachMpqTest (wow-update-ptBR-16309.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-ptPT.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-ptPT.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-ptPT.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-ptPT.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-ptPT.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-ptPT.MPQ) succeeded. -OpenEachMpqTest (expansion4-speech-ptPT.MPQ) succeeded. -OpenEachMpqTest (locale-ptPT.MPQ) succeeded. -OpenEachMpqTest (OldWorld-ptPT.MPQ) succeeded. -OpenEachMpqTest (speech-ptPT.MPQ) succeeded. -OpenEachMpqTest (wow-update-ptPT-16016.MPQ) succeeded. -OpenEachMpqTest (wow-update-ptPT-16048.MPQ) succeeded. -OpenEachMpqTest (wow-update-ptPT-16057.MPQ) succeeded. -OpenEachMpqTest (wow-update-ptPT-16309.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-ruRU.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-ruRU.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-ruRU.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-ruRU.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-ruRU.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-ruRU.MPQ) succeeded. -OpenEachMpqTest (expansion4-speech-ruRU.MPQ) succeeded. -OpenEachMpqTest (locale-ruRU.MPQ) succeeded. -OpenEachMpqTest (OldWorld-ruRU.MPQ) succeeded. -OpenEachMpqTest (speech-ruRU.MPQ) succeeded. -OpenEachMpqTest (wow-update-ruRU-16016.MPQ) succeeded. -OpenEachMpqTest (wow-update-ruRU-16048.MPQ) succeeded. -OpenEachMpqTest (wow-update-ruRU-16057.MPQ) succeeded. -OpenEachMpqTest (wow-update-ruRU-16309.MPQ) succeeded. -OpenEachMpqTest (sound.MPQ) succeeded. -OpenEachMpqTest (texture.MPQ) succeeded. -OpenEachMpqTest (world.MPQ) succeeded. -OpenEachMpqTest (world2.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-16016.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-16048.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-16057.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-16309.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-zhCN.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-zhCN.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-zhCN.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-zhCN.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-zhCN.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-zhCN.MPQ) succeeded. -OpenEachMpqTest (expansion4-speech-zhCN.MPQ) succeeded. -OpenEachMpqTest (locale-zhCN.MPQ) succeeded. -OpenEachMpqTest (OldWorld-zhCN.MPQ) succeeded. -OpenEachMpqTest (speech-zhCN.MPQ) succeeded. -OpenEachMpqTest (wow-update-zhCN-16016.MPQ) succeeded. -OpenEachMpqTest (wow-update-zhCN-16048.MPQ) succeeded. -OpenEachMpqTest (wow-update-zhCN-16057.MPQ) succeeded. -OpenEachMpqTest (wow-update-zhCN-16309.MPQ) succeeded. -OpenEachMpqTest (expansion1-locale-zhTW.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-zhTW.MPQ) succeeded. -OpenEachMpqTest (expansion2-locale-zhTW.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-zhTW.MPQ) succeeded. -OpenEachMpqTest (expansion3-locale-zhTW.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-zhTW.MPQ) succeeded. -OpenEachMpqTest (expansion4-speech-zhTW.MPQ) succeeded. -OpenEachMpqTest (locale-zhTW.MPQ) succeeded. -OpenEachMpqTest (OldWorld-zhTW.MPQ) succeeded. -OpenEachMpqTest (speech-zhTW.MPQ) succeeded. -OpenEachMpqTest (wow-update-zhTW-16016.MPQ) succeeded. -OpenEachMpqTest (wow-update-zhTW-16048.MPQ) succeeded. -OpenEachMpqTest (wow-update-zhTW-16057.MPQ) succeeded. -OpenEachMpqTest (wow-update-zhTW-16309.MPQ) succeeded. -OpenEachMpqTest (wow-0-16309-OSX-final.MPQ) succeeded. -OpenEachMpqTest (wow-0-16309-Win-final.MPQ) succeeded. -OpenEachMpqTest (alternate.MPQ) succeeded. -OpenEachMpqTest (Base-Win.mpq) succeeded. -OpenEachMpqTest (expansion1-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion4-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (locale-enGB.MPQ) succeeded. -OpenEachMpqTest (speech-enGB.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16016.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16048.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16057.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16309.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16357.MPQ) succeeded. -OpenEachMpqTest (locale-enUS.MPQ) succeeded. -OpenEachMpqTest (speech-enUS.MPQ) succeeded. -OpenEachMpqTest (wow-update-enUS-16016.MPQ) succeeded. -OpenEachMpqTest (wow-update-enUS-16048.MPQ) succeeded. -OpenEachMpqTest (wow-update-enUS-16057.MPQ) succeeded. -OpenEachMpqTest (expansion1.MPQ) succeeded. -OpenEachMpqTest (expansion2.MPQ) succeeded. -OpenEachMpqTest (expansion3.MPQ) succeeded. -OpenEachMpqTest (expansion4.MPQ) succeeded. -OpenEachMpqTest (interface.MPQ) succeeded. -OpenEachMpqTest (itemtexture.MPQ) succeeded. -OpenEachMpqTest (misc.MPQ) succeeded. -OpenEachMpqTest (model.MPQ) succeeded. -OpenEachMpqTest (SetupWin.mpq) succeeded. -OpenEachMpqTest (sound.MPQ) succeeded. -OpenEachMpqTest (texture.MPQ) succeeded. -OpenEachMpqTest (world.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-16016.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-16048.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-16057.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-16309.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-16357.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-16516.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-16650.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-16844.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-16965.MPQ) succeeded. -OpenEachMpqTest (base-Win.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16516.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16650.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16844.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16965.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-17116.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-17266.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-17325.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-17345.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-17538.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-17645.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-17116.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-17266.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-17325.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-17345.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-17538.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-17645.MPQ) succeeded. -OpenEachMpqTest (SetupWin.mpq) succeeded. -OpenEachMpqTest (base-Win.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-16016.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-16048.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-16057.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-16309.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-16357.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-16516.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-16650.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-16844.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-16965.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-17116.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-17266.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-17325.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-17345.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-17538.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-17645.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-17688.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-17898.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-18273.MPQ) succeeded. -OpenEachMpqTest (patch-base-16016.MPQ) succeeded. -OpenEachMpqTest (patch-base-16048.MPQ) succeeded. -OpenEachMpqTest (patch-base-16057.MPQ) succeeded. -OpenEachMpqTest (patch-base-16309.MPQ) succeeded. -OpenEachMpqTest (patch-base-16357.MPQ) succeeded. -OpenEachMpqTest (patch-base-16516.MPQ) succeeded. -OpenEachMpqTest (patch-base-16650.MPQ) succeeded. -OpenEachMpqTest (patch-base-16844.MPQ) succeeded. -OpenEachMpqTest (patch-base-16965.MPQ) succeeded. -OpenEachMpqTest (patch-base-17116.MPQ) succeeded. -OpenEachMpqTest (patch-base-17266.MPQ) succeeded. -OpenEachMpqTest (patch-base-17325.MPQ) succeeded. -OpenEachMpqTest (patch-base-17345.MPQ) succeeded. -OpenEachMpqTest (patch-base-17538.MPQ) succeeded. -OpenEachMpqTest (patch-base-17645.MPQ) succeeded. -OpenEachMpqTest (patch-base-17688.MPQ) succeeded. -OpenEachMpqTest (patch-base-17898.MPQ) succeeded. -OpenEachMpqTest (patch-base-18273.MPQ) succeeded. -OpenEachMpqTest (expansion1-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion2-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion3-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (expansion4-speech-enGB.MPQ) succeeded. -OpenEachMpqTest (locale-enGB.MPQ) succeeded. -OpenEachMpqTest (speech-enGB.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16016.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16048.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16057.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16309.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16357.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16516.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16650.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16844.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-16965.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-17116.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-17266.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-17325.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-17345.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-17538.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-17645.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-17688.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-17898.MPQ) succeeded. -OpenEachMpqTest (wow-update-enGB-18273.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-17116.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-17266.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-17325.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-17345.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-17538.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-17645.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-17688.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-17898.MPQ) succeeded. -OpenEachMpqTest (wow-update-base-18273.MPQ) succeeded. -OpenEachMpqTest (SetupWin.mpq) succeeded. -OpenEachMpqTest (Bel'shir Wildlands1.0.SC2Map) succeeded. -OpenEachMpqTest (CubDefensev09.SC2Map) succeeded. -OpenEachMpqTest (Hell_TD_v0.17.SC2Map) succeeded. -OpenEachMpqTest (Magma Mayham.SC2Map) succeeded. -OpenEachMpqTest (Test map - published (locked).SC2Map) succeeded. -OpenEachMpqTest (Test map - published (unlocked).SC2Map) succeeded. -OpenEachMpqTest (TiddaoTest01.SC2Map) succeeded. -OpenEachMpqTest (Tya's Zerg Defense (unprotected).SC2Map) succeeded. -OpenEachMpqTest (Tya's Zerg Defense.SC2Map) succeeded. -OpenEachMpqTest (Zenith.SC2MAP) succeeded. -OpenEachMpqTest (zone_control_belshir.SC2Map) succeeded. -OpenEachMpqTest ((12)(SB) - Shakuras Plateau (Money Map).s2ma) succeeded. -OpenEachMpqTest ((12)(SB) - Shakuras Plateau (Money Map)_orig.s2ma) succeeded. -OpenEachMpqTest ((2) - AI - Blistering Sands.s2ma) succeeded. -OpenEachMpqTest ((2) - AI - Desert Oasis.s2ma) succeeded. -OpenEachMpqTest ((2) - AI - Scrap Station.s2ma) succeeded. -OpenEachMpqTest ((2) - AI - Steppes of War.s2ma) succeeded. -OpenEachMpqTest ((4) - AI - Kulas Ravine (1x).s2ma) succeeded. -OpenEachMpqTest ((4) - AI - Kulas Ravine (3x).s2ma) succeeded. -OpenEachMpqTest ((4) - AI - Lost Temple (1x).s2ma) succeeded. -OpenEachMpqTest ((4) - AI - Lost Temple (3x).s2ma) succeeded. -OpenEachMpqTest ((4) - AI - Metalopolis (1x).s2ma) succeeded. -OpenEachMpqTest ((4) - AI - Metalopolis (3x).s2ma) succeeded. -OpenEachMpqTest ((4) - AI - Shakuras Plateau (1x).s2ma) succeeded. -OpenEachMpqTest ((4) - AI - Shakuras Plateau (3x).s2ma) succeeded. -OpenEachMpqTest ((4) - AI - Twilight Fortress (1x).s2ma) succeeded. -OpenEachMpqTest ((4) - AI - Twilight Fortress (3x).s2ma) succeeded. -OpenEachMpqTest (Battle.net.MPQ) succeeded. -OpenEachMpqTest (LOST_v1.SC2Map) succeeded. -OpenEachMpqTest (Backup.MPQ) succeeded. -OpenEachMpqTest (Base.MPQ) succeeded. -OpenEachMpqTest (Installer Tome 1.MPQE) succeeded. -OpenEachMpqTest (Installer UI 1.MPQ) succeeded. -OpenEachMpqTest (Installer UI 2.MPQE) succeeded. -OpenEachMpqTest (Installer UI 2 deDE.MPQE) succeeded. -OpenEachMpqTest (Installer UI 2 enGB.MPQE) succeeded. -OpenEachMpqTest (Installer UI 2 enSG.MPQE) succeeded. -OpenEachMpqTest (Installer UI 2 enUS.MPQE) succeeded. -OpenEachMpqTest (Installer UI 2 esES.MPQE) succeeded. -OpenEachMpqTest (Installer UI 2 esMX.MPQE) succeeded. -OpenEachMpqTest (Installer UI 2 frFR.MPQE) succeeded. -OpenEachMpqTest (Installer UI 2 itIT.MPQE) succeeded. -OpenEachMpqTest (Installer UI 2 plPL.MPQE) succeeded. -OpenEachMpqTest (Installer UI 2 ptBR.MPQE) succeeded. -OpenEachMpqTest (Installer UI 2 ruRU.MPQE) succeeded. -OpenEachMpqTest (Installer UI 2 zhTW.MPQE) succeeded. -OpenEachMpqTest (Battle.net-patch.MPQ) succeeded. -OpenEachMpqTest (Battle.net.MPQ) succeeded. -OpenEachMpqTest (Challenges.SC2Mod) succeeded. -OpenEachMpqTest (Backup.MPQ) succeeded. -OpenEachMpqTest (Base.MPQ) succeeded. -OpenEachMpqTest (Battle.net.MPQ) succeeded. -OpenEachMpqTest (Challenges.SC2Mod) succeeded. -OpenEachMpqTest (Base-OSX.mpq) succeeded. -OpenEachMpqTest (Base-Win.mpq) succeeded. -OpenEachMpqTest (Battle.net.MPQ) succeeded. -OpenEachMpqTest (Test map.SC2Map) succeeded. -OpenEachMpqTest (Challenges.SC2Mod) succeeded. -OpenEachMpqTest (Base-Win.mpq) succeeded. -OpenEachMpqTest (SetupWin.mpq) succeeded. -OpenEachMpqTest (s2-update-base-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-base-24540.MPQ) succeeded. -OpenEachMpqTest (patch-base-23258.MPQ) succeeded. -OpenEachMpqTest (patch-base-24540.MPQ) succeeded. -OpenEachMpqTest (patch-deDE-23258.MPQ) succeeded. -OpenEachMpqTest (patch-deDE-24540.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-23258.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-24540.MPQ) succeeded. -OpenEachMpqTest (patch-enUS-23258.MPQ) succeeded. -OpenEachMpqTest (patch-enUS-24540.MPQ) succeeded. -OpenEachMpqTest (patch-esES-23258.MPQ) succeeded. -OpenEachMpqTest (patch-esES-24540.MPQ) succeeded. -OpenEachMpqTest (patch-esMX-23258.MPQ) succeeded. -OpenEachMpqTest (patch-esMX-24540.MPQ) succeeded. -OpenEachMpqTest (patch-frFR-23258.MPQ) succeeded. -OpenEachMpqTest (patch-frFR-24540.MPQ) succeeded. -OpenEachMpqTest (patch-itIT-23258.MPQ) succeeded. -OpenEachMpqTest (patch-itIT-24540.MPQ) succeeded. -OpenEachMpqTest (patch-koKR-23258.MPQ) succeeded. -OpenEachMpqTest (patch-koKR-24540.MPQ) succeeded. -OpenEachMpqTest (patch-plPL-23258.MPQ) succeeded. -OpenEachMpqTest (patch-plPL-24540.MPQ) succeeded. -OpenEachMpqTest (patch-ptBR-23258.MPQ) succeeded. -OpenEachMpqTest (patch-ptBR-24540.MPQ) succeeded. -OpenEachMpqTest (patch-ruRU-23258.MPQ) succeeded. -OpenEachMpqTest (patch-ruRU-24540.MPQ) succeeded. -OpenEachMpqTest (patch-zhCN-23258.MPQ) succeeded. -OpenEachMpqTest (patch-zhCN-24540.MPQ) succeeded. -OpenEachMpqTest (patch-zhTW-23258.MPQ) succeeded. -OpenEachMpqTest (patch-zhTW-24540.MPQ) succeeded. -OpenEachMpqTest (s2-update-deDE-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-deDE-24540.MPQ) succeeded. -OpenEachMpqTest (s2-update-enGB-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-enGB-24540.MPQ) succeeded. -OpenEachMpqTest (s2-update-enUS-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-enUS-24540.MPQ) succeeded. -OpenEachMpqTest (s2-update-esES-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-esES-24540.MPQ) succeeded. -OpenEachMpqTest (s2-update-esMX-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-esMX-24540.MPQ) succeeded. -OpenEachMpqTest (s2-update-frFR-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-frFR-24540.MPQ) succeeded. -OpenEachMpqTest (s2-update-itIT-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-itIT-24540.MPQ) succeeded. -OpenEachMpqTest (s2-update-koKR-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-koKR-24540.MPQ) succeeded. -OpenEachMpqTest (s2-update-plPL-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-plPL-24540.MPQ) succeeded. -OpenEachMpqTest (s2-update-ptBR-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-ptBR-24540.MPQ) succeeded. -OpenEachMpqTest (s2-update-ruRU-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-ruRU-24540.MPQ) succeeded. -OpenEachMpqTest (s2-0-24540-Win-final.MPQ) succeeded. -OpenEachMpqTest (SC2_HotS_20_BGDL_Base.MPQE) succeeded. -OpenEachMpqTest (SC2_HotS_20_BGDL_Base1.MPQE) succeeded. -OpenEachMpqTest (SC2_HotS_20_BGDL_deDE.MPQE) succeeded. -OpenEachMpqTest (SC2_HotS_20_BGDL_enGB.MPQE) succeeded. -OpenEachMpqTest (SC2_HotS_20_BGDL_enUS.MPQE) succeeded. -OpenEachMpqTest (SC2_HotS_20_BGDL_esES.MPQE) succeeded. -OpenEachMpqTest (SC2_HotS_20_BGDL_esMX.MPQE) succeeded. -OpenEachMpqTest (SC2_HotS_20_BGDL_frFR.MPQE) succeeded. -OpenEachMpqTest (SC2_HotS_20_BGDL_itIT.MPQE) succeeded. -OpenEachMpqTest (SC2_HotS_20_BGDL_koKR.MPQE) succeeded. -OpenEachMpqTest (SC2_HotS_20_BGDL_plPL.MPQE) succeeded. -OpenEachMpqTest (SC2_HotS_20_BGDL_ptBR.MPQE) succeeded. -OpenEachMpqTest (SC2_HotS_20_BGDL_ruRU.MPQE) succeeded. -OpenEachMpqTest (SC2_HotS_20_BGDL_zhTW.MPQE) succeeded. -OpenEachMpqTest (MigrationContent_base1.MPQ) succeeded. -OpenEachMpqTest (MigrationContent_deDE.MPQ) succeeded. -OpenEachMpqTest (MigrationContent_enGB.MPQ) succeeded. -OpenEachMpqTest (MigrationContent_enUS.MPQ) succeeded. -OpenEachMpqTest (MigrationContent_esES.MPQ) succeeded. -OpenEachMpqTest (MigrationContent_esMX.MPQ) succeeded. -OpenEachMpqTest (MigrationContent_frFR.MPQ) succeeded. -OpenEachMpqTest (MigrationContent_itIT.MPQ) succeeded. -OpenEachMpqTest (MigrationContent_koKR.MPQ) succeeded. -OpenEachMpqTest (MigrationContent_plPL.MPQ) succeeded. -OpenEachMpqTest (MigrationContent_ptBR.MPQ) succeeded. -OpenEachMpqTest (MigrationContent_ruRU.MPQ) succeeded. -OpenEachMpqTest (MigrationContent_zhCN.MPQ) succeeded. -OpenEachMpqTest (MigrationContent_zhTW.MPQ) succeeded. -OpenEachMpqTest (s2-update-zhCN-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-zhCN-24540.MPQ) succeeded. -OpenEachMpqTest (s2-update-zhTW-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-zhTW-24540.MPQ) succeeded. -OpenEachMpqTest (Battle.net.MPQ) succeeded. -OpenEachMpqTest (Challenges.SC2Mod) succeeded. -OpenEachMpqTest (Base-Win.mpq) succeeded. -OpenEachMpqTest (SetupWin.mpq) succeeded. -OpenEachMpqTest (s2-update-base-24764.MPQ) succeeded. -OpenEachMpqTest (s2-update-enUS-24764.MPQ) succeeded. -OpenEachMpqTest (s2-0-24764-Win-final.MPQ) succeeded. -OpenEachMpqTest: Warning: no files in the archive -OpenEachMpqTest: Warning: no files in the archive -OpenEachMpqTest: Failed to open archive \Multimedia\MPQs\2010 - Starcraft II\25092\Updates\base\s2-update-base-24540.MPQ (error code: 1392) -OpenEachMpqTest: Failed to open archive \Multimedia\MPQs\2010 - Starcraft II\25092\Updates\base\s2-update-base-25092.MPQ (error code: 1392) -OpenEachMpqTest (patch-base-23258.MPQ) succeeded. -OpenEachMpqTest (patch-base-24540.MPQ) succeeded. -OpenEachMpqTest (patch-deDE-23258.MPQ) succeeded. -OpenEachMpqTest (patch-deDE-24540.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-23258.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-24540.MPQ) succeeded. -OpenEachMpqTest (patch-enUS-23258.MPQ) succeeded. -OpenEachMpqTest (patch-enUS-24540.MPQ) succeeded. -OpenEachMpqTest (patch-esES-23258.MPQ) succeeded. -OpenEachMpqTest (patch-esES-24540.MPQ) succeeded. -OpenEachMpqTest (patch-esMX-23258.MPQ) succeeded. -OpenEachMpqTest (patch-esMX-24540.MPQ) succeeded. -OpenEachMpqTest (patch-frFR-23258.MPQ) succeeded. -OpenEachMpqTest (patch-frFR-24540.MPQ) succeeded. -OpenEachMpqTest (patch-itIT-23258.MPQ) succeeded. -OpenEachMpqTest (patch-itIT-24540.MPQ) succeeded. -OpenEachMpqTest (patch-koKR-23258.MPQ) succeeded. -OpenEachMpqTest (patch-koKR-24540.MPQ) succeeded. -OpenEachMpqTest (patch-plPL-23258.MPQ) succeeded. -OpenEachMpqTest (patch-plPL-24540.MPQ) succeeded. -OpenEachMpqTest (patch-ptBR-23258.MPQ) succeeded. -OpenEachMpqTest (patch-ptBR-24540.MPQ) succeeded. -OpenEachMpqTest (patch-ruRU-23258.MPQ) succeeded. -OpenEachMpqTest (patch-ruRU-24540.MPQ) succeeded. -OpenEachMpqTest (patch-zhCN-23258.MPQ) succeeded. -OpenEachMpqTest (patch-zhCN-24540.MPQ) succeeded. -OpenEachMpqTest (patch-zhTW-23258.MPQ) succeeded. -OpenEachMpqTest (patch-zhTW-24540.MPQ) succeeded. -OpenEachMpqTest (s2-update-deDE-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-deDE-24540.MPQ) succeeded. -OpenEachMpqTest: Warning: no files in the archive -OpenEachMpqTest: Warning: no files in the archive -OpenEachMpqTest (s2-update-enUS-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-enUS-24540.MPQ) succeeded. -OpenEachMpqTest (s2-update-esES-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-esES-24540.MPQ) succeeded. -OpenEachMpqTest (s2-update-esMX-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-esMX-24540.MPQ) succeeded. -OpenEachMpqTest (s2-update-frFR-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-frFR-24540.MPQ) succeeded. -OpenEachMpqTest (s2-update-itIT-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-itIT-24540.MPQ) succeeded. -OpenEachMpqTest (s2-update-koKR-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-koKR-24540.MPQ) succeeded. -OpenEachMpqTest (s2-update-plPL-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-plPL-24540.MPQ) succeeded. -OpenEachMpqTest (s2-update-ptBR-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-ptBR-24540.MPQ) succeeded. -OpenEachMpqTest (s2-update-ruRU-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-ruRU-24540.MPQ) succeeded. -OpenEachMpqTest (s2-0-24540-Win-final.MPQ) succeeded. -OpenEachMpqTest: Warning: no files in the archive -OpenEachMpqTest (SC2_HotS_20_BGDL_Base.MPQE) succeeded. -OpenEachMpqTest (SC2_HotS_20_BGDL_Base1.MPQE) succeeded. -OpenEachMpqTest (SC2_HotS_20_BGDL_deDE.MPQE) succeeded. -OpenEachMpqTest (SC2_HotS_20_BGDL_enGB.MPQE) succeeded. -OpenEachMpqTest (SC2_HotS_20_BGDL_enUS.MPQE) succeeded. -OpenEachMpqTest (SC2_HotS_20_BGDL_esES.MPQE) succeeded. -OpenEachMpqTest (SC2_HotS_20_BGDL_esMX.MPQE) succeeded. -OpenEachMpqTest (SC2_HotS_20_BGDL_frFR.MPQE) succeeded. -OpenEachMpqTest (SC2_HotS_20_BGDL_itIT.MPQE) succeeded. -OpenEachMpqTest (SC2_HotS_20_BGDL_koKR.MPQE) succeeded. -OpenEachMpqTest (SC2_HotS_20_BGDL_plPL.MPQE) succeeded. -OpenEachMpqTest (SC2_HotS_20_BGDL_ptBR.MPQE) succeeded. -OpenEachMpqTest (SC2_HotS_20_BGDL_ruRU.MPQE) succeeded. -OpenEachMpqTest (SC2_HotS_20_BGDL_zhTW.MPQE) succeeded. -OpenEachMpqTest (MigrationContent_base1.MPQ) succeeded. -OpenEachMpqTest (MigrationContent_deDE.MPQ) succeeded. -OpenEachMpqTest (MigrationContent_enGB.MPQ) succeeded. -OpenEachMpqTest (MigrationContent_enUS.MPQ) succeeded. -OpenEachMpqTest (MigrationContent_esES.MPQ) succeeded. -OpenEachMpqTest (MigrationContent_esMX.MPQ) succeeded. -OpenEachMpqTest (MigrationContent_frFR.MPQ) succeeded. -OpenEachMpqTest (MigrationContent_itIT.MPQ) succeeded. -OpenEachMpqTest (MigrationContent_koKR.MPQ) succeeded. -OpenEachMpqTest (MigrationContent_plPL.MPQ) succeeded. -OpenEachMpqTest (MigrationContent_ptBR.MPQ) succeeded. -OpenEachMpqTest (MigrationContent_ruRU.MPQ) succeeded. -OpenEachMpqTest (MigrationContent_zhCN.MPQ) succeeded. -OpenEachMpqTest (MigrationContent_zhTW.MPQ) succeeded. -OpenEachMpqTest (s2-update-zhCN-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-zhCN-24540.MPQ) succeeded. -OpenEachMpqTest (s2-update-zhTW-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-zhTW-24540.MPQ) succeeded. -OpenEachMpqTest (Battle.net.MPQ) succeeded. -OpenEachMpqTest (SwarmStoryUtil.SC2Mod) succeeded. -OpenEachMpqTest (Challenges.SC2Mod) succeeded. -OpenEachMpqTest (Base-Win.mpq) succeeded. -OpenEachMpqTest (SetupWin.mpq) succeeded. -OpenEachMpqTest (s2-update-base-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-base-24540.MPQ) succeeded. -OpenEachMpqTest (s2-update-base-25293.MPQ) succeeded. -OpenEachMpqTest (s2-update-base-26147.MPQ) succeeded. -OpenEachMpqTest (s2-update-base-26825.MPQ) succeeded. -OpenEachMpqTest (patch-base-25293.MPQ) succeeded. -OpenEachMpqTest (patch-base-26147.MPQ) succeeded. -OpenEachMpqTest (patch-base-26825.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-26147.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-26825.MPQ) succeeded. -OpenEachMpqTest (s2-update-enGB-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-enGB-24540.MPQ) succeeded. -OpenEachMpqTest (s2-update-enGB-26147.MPQ) succeeded. -OpenEachMpqTest (s2-update-enGB-26825.MPQ) succeeded. -OpenEachMpqTest (s2-0-26825-Win-final.MPQ) succeeded. -OpenEachMpqTest (Battle.net.MPQ) succeeded. -OpenEachMpqTest (SwarmStoryUtil.SC2Mod) succeeded. -OpenEachMpqTest (Challenges.SC2Mod) succeeded. -OpenEachMpqTest (Base-Win.mpq) succeeded. -OpenEachMpqTest (SetupWin.mpq) succeeded. -OpenEachMpqTest (s2-update-base-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-base-24540.MPQ) succeeded. -OpenEachMpqTest (s2-update-base-26147.MPQ) succeeded. -OpenEachMpqTest (s2-update-base-28522.MPQ) succeeded. -OpenEachMpqTest (s2-update-base-32384.MPQ) succeeded. -OpenEachMpqTest (s2-update-base-34644.MPQ) succeeded. -OpenEachMpqTest (patch-base-26147.MPQ) succeeded. -OpenEachMpqTest (patch-base-28522.MPQ) succeeded. -OpenEachMpqTest (patch-base-32384.MPQ) succeeded. -OpenEachMpqTest (patch-base-34644.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-26147.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-28522.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-32384.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-34644.MPQ) succeeded. -OpenEachMpqTest (s2-update-enGB-23258.MPQ) succeeded. -OpenEachMpqTest (s2-update-enGB-24540.MPQ) succeeded. -OpenEachMpqTest (s2-update-enGB-26147.MPQ) succeeded. -OpenEachMpqTest (s2-update-enGB-28522.MPQ) succeeded. -OpenEachMpqTest (s2-update-enGB-32384.MPQ) succeeded. -OpenEachMpqTest (s2-update-enGB-34644.MPQ) succeeded. -OpenEachMpqTest (s2-0-34644-Win-final.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-7170.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-7200.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-7318.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-7338.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-7447.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-7728.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-7841.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-7931.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-8059.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-8101.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-8296.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-8350.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-8392.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-8610.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-8815.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-8896.MPQ) succeeded. -OpenEachMpqTest (base-Win.mpq) succeeded. -OpenEachMpqTest (patch-base-7170.MPQ) succeeded. -OpenEachMpqTest (patch-base-7200.MPQ) succeeded. -OpenEachMpqTest (patch-base-7318.MPQ) succeeded. -OpenEachMpqTest (patch-base-7338.MPQ) succeeded. -OpenEachMpqTest (patch-base-7447.MPQ) succeeded. -OpenEachMpqTest (patch-base-7728.MPQ) succeeded. -OpenEachMpqTest (patch-base-7841.MPQ) succeeded. -OpenEachMpqTest (patch-base-7931.MPQ) succeeded. -OpenEachMpqTest (patch-base-8059.MPQ) succeeded. -OpenEachMpqTest (patch-base-8101.MPQ) succeeded. -OpenEachMpqTest (patch-base-8296.MPQ) succeeded. -OpenEachMpqTest (patch-base-8350.MPQ) succeeded. -OpenEachMpqTest (patch-base-8392.MPQ) succeeded. -OpenEachMpqTest (patch-base-8610.MPQ) succeeded. -OpenEachMpqTest (patch-base-8815.MPQ) succeeded. -OpenEachMpqTest (patch-base-8896.MPQ) succeeded. -OpenEachMpqTest (patch-enUS-7170.MPQ) succeeded. -OpenEachMpqTest (patch-enUS-7200.MPQ) succeeded. -OpenEachMpqTest (patch-enUS-7318.MPQ) succeeded. -OpenEachMpqTest (patch-enUS-7338.MPQ) succeeded. -OpenEachMpqTest (patch-enUS-7447.MPQ) succeeded. -OpenEachMpqTest (patch-enUS-7728.MPQ) succeeded. -OpenEachMpqTest (patch-enUS-7841.MPQ) succeeded. -OpenEachMpqTest (patch-enUS-7931.MPQ) succeeded. -OpenEachMpqTest (patch-enUS-8059.MPQ) succeeded. -OpenEachMpqTest (patch-enUS-8296.MPQ) succeeded. -OpenEachMpqTest (patch-enUS-8392.MPQ) succeeded. -OpenEachMpqTest (patch-enUS-8610.MPQ) succeeded. -OpenEachMpqTest (patch-enUS-8815.MPQ) succeeded. -OpenEachMpqTest (patch-enUS-8896.MPQ) succeeded. -OpenEachMpqTest (patch-Win-7200.MPQ) succeeded. -OpenEachMpqTest (patch-Win-7318.MPQ) succeeded. -OpenEachMpqTest (patch-Win-7338.MPQ) succeeded. -OpenEachMpqTest (patch-Win-7447.MPQ) succeeded. -OpenEachMpqTest (patch-Win-7728.MPQ) succeeded. -OpenEachMpqTest (patch-Win-7841.MPQ) succeeded. -OpenEachMpqTest (patch-Win-7931.MPQ) succeeded. -OpenEachMpqTest (patch-Win-8059.MPQ) succeeded. -OpenEachMpqTest (patch-Win-8101.MPQ) succeeded. -OpenEachMpqTest (patch-Win-8296.MPQ) succeeded. -OpenEachMpqTest (patch-Win-8350.MPQ) succeeded. -OpenEachMpqTest (patch-Win-8392.MPQ) succeeded. -OpenEachMpqTest (patch-Win-8610.MPQ) succeeded. -OpenEachMpqTest (patch-Win-8815.MPQ) succeeded. -OpenEachMpqTest (patch-Win-8896.MPQ) succeeded. -OpenEachMpqTest (ClientData.mpq) succeeded. -OpenEachMpqTest (CoreData.mpq) succeeded. -OpenEachMpqTest (d3-update-enUS-7170.MPQ) succeeded. -OpenEachMpqTest (d3-update-enUS-7200.MPQ) succeeded. -OpenEachMpqTest (d3-update-enUS-7318.MPQ) succeeded. -OpenEachMpqTest (d3-update-enUS-7338.MPQ) succeeded. -OpenEachMpqTest (d3-update-enUS-7447.MPQ) succeeded. -OpenEachMpqTest (d3-update-enUS-7728.MPQ) succeeded. -OpenEachMpqTest (d3-update-enUS-7841.MPQ) succeeded. -OpenEachMpqTest (d3-update-enUS-7931.MPQ) succeeded. -OpenEachMpqTest (d3-update-enUS-8059.MPQ) succeeded. -OpenEachMpqTest (d3-update-enUS-8296.MPQ) succeeded. -OpenEachMpqTest (d3-update-enUS-8392.MPQ) succeeded. -OpenEachMpqTest (d3-update-enUS-8610.MPQ) succeeded. -OpenEachMpqTest (d3-update-enUS-8815.MPQ) succeeded. -OpenEachMpqTest (d3-update-enUS-8896.MPQ) succeeded. -OpenEachMpqTest (enUS_Audio.mpq) succeeded. -OpenEachMpqTest (enUS_Cutscene.mpq) succeeded. -OpenEachMpqTest (enUS_Text.mpq) succeeded. -OpenEachMpqTest (HLSLShaders.mpq) succeeded. -OpenEachMpqTest (patch.MPQ) succeeded. -OpenEachMpqTest (Sound.mpq) succeeded. -OpenEachMpqTest (Texture.mpq) succeeded. -OpenEachMpqTest (d3-update-Win-7200.MPQ) succeeded. -OpenEachMpqTest (d3-update-Win-7318.MPQ) succeeded. -OpenEachMpqTest (d3-update-Win-7338.MPQ) succeeded. -OpenEachMpqTest (d3-update-Win-7447.MPQ) succeeded. -OpenEachMpqTest (d3-update-Win-7728.MPQ) succeeded. -OpenEachMpqTest (d3-update-Win-7841.MPQ) succeeded. -OpenEachMpqTest (d3-update-Win-7931.MPQ) succeeded. -OpenEachMpqTest (d3-update-Win-8059.MPQ) succeeded. -OpenEachMpqTest (d3-update-Win-8101.MPQ) succeeded. -OpenEachMpqTest (d3-update-Win-8296.MPQ) succeeded. -OpenEachMpqTest (d3-update-Win-8350.MPQ) succeeded. -OpenEachMpqTest (d3-update-Win-8392.MPQ) succeeded. -OpenEachMpqTest (d3-update-Win-8610.MPQ) succeeded. -OpenEachMpqTest (d3-update-Win-8815.MPQ) succeeded. -OpenEachMpqTest (d3-update-Win-8896.MPQ) succeeded. -OpenEachMpqTest (Installer Tome 1 deDE.MPQE) succeeded. -OpenEachMpqTest (Installer Tome 1 enGB.MPQE) succeeded. -OpenEachMpqTest (Installer Tome 1 enSG.MPQE) succeeded. -OpenEachMpqTest (Installer Tome 1 enUS.MPQE) succeeded. -OpenEachMpqTest (Installer Tome 1 esES.MPQE) succeeded. -OpenEachMpqTest (Installer Tome 1 esMX.MPQE) succeeded. -OpenEachMpqTest (Installer Tome 1 frFR.MPQE) succeeded. -OpenEachMpqTest (Installer Tome 1 itIT.MPQE) succeeded. -OpenEachMpqTest (Installer Tome 1 koKR.MPQE) succeeded. -OpenEachMpqTest (Installer Tome 1 plPL.MPQE) succeeded. -OpenEachMpqTest (Installer Tome 1 ptBR.MPQE) succeeded. -OpenEachMpqTest (Installer Tome 1 ruRU.MPQE) succeeded. -OpenEachMpqTest (Installer Tome 1 zhTW.MPQE) succeeded. -OpenEachMpqTest (d3-update-base-10057.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-10235.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-10485.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-11327.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-12480.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-12811.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-13300.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-13644.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-9558.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-9749.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-9858.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-9950.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-9991.MPQ) succeeded. -OpenEachMpqTest (base-Win.mpq) succeeded. -OpenEachMpqTest (patch-base-10057.MPQ) succeeded. -OpenEachMpqTest (patch-base-10235.MPQ) succeeded. -OpenEachMpqTest (patch-base-10485.MPQ) succeeded. -OpenEachMpqTest (patch-base-11327.MPQ) succeeded. -OpenEachMpqTest (patch-base-12480.MPQ) succeeded. -OpenEachMpqTest (patch-base-12811.MPQ) succeeded. -OpenEachMpqTest (patch-base-13300.MPQ) succeeded. -OpenEachMpqTest (patch-base-13644.MPQ) succeeded. -OpenEachMpqTest (patch-base-9558.MPQ) succeeded. -OpenEachMpqTest (patch-base-9749.MPQ) succeeded. -OpenEachMpqTest (patch-base-9858.MPQ) succeeded. -OpenEachMpqTest (patch-base-9950.MPQ) succeeded. -OpenEachMpqTest (patch-base-9991.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-10057.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-10485.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-11327.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-12480.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-13300.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-9558.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-9749.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-9858.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-9950.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-9991.MPQ) succeeded. -OpenEachMpqTest (patch-Win-10057.MPQ) succeeded. -OpenEachMpqTest (patch-Win-11327.MPQ) succeeded. -OpenEachMpqTest (patch-Win-12480.MPQ) succeeded. -OpenEachMpqTest (patch-Win-9558.MPQ) succeeded. -OpenEachMpqTest (ClientData.mpq) succeeded. -OpenEachMpqTest (CoreData.mpq) succeeded. -OpenEachMpqTest (d3-update-enGB-10057.MPQ) succeeded. -OpenEachMpqTest (d3-update-enGB-10485.MPQ) succeeded. -OpenEachMpqTest (d3-update-enGB-11327.MPQ) succeeded. -OpenEachMpqTest (d3-update-enGB-12480.MPQ) succeeded. -OpenEachMpqTest (d3-update-enGB-13300.MPQ) succeeded. -OpenEachMpqTest (d3-update-enGB-9558.MPQ) succeeded. -OpenEachMpqTest (d3-update-enGB-9749.MPQ) succeeded. -OpenEachMpqTest (d3-update-enGB-9858.MPQ) succeeded. -OpenEachMpqTest (d3-update-enGB-9950.MPQ) succeeded. -OpenEachMpqTest (d3-update-enGB-9991.MPQ) succeeded. -OpenEachMpqTest (enGB_Audio.mpq) succeeded. -OpenEachMpqTest (enGB_Cutscene.mpq) succeeded. -OpenEachMpqTest (enGB_Text.mpq) succeeded. -OpenEachMpqTest (HLSLShaders.mpq) succeeded. -OpenEachMpqTest (Sound.mpq) succeeded. -OpenEachMpqTest (Texture.mpq) succeeded. -OpenEachMpqTest (d3-update-Win-10057.MPQ) succeeded. -OpenEachMpqTest (d3-update-Win-11327.MPQ) succeeded. -OpenEachMpqTest (d3-update-Win-12480.MPQ) succeeded. -OpenEachMpqTest (d3-update-Win-9558.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-14633.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-15295.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-16416.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-16603.MPQ) succeeded. -OpenEachMpqTest (patch-base-14633.MPQ) succeeded. -OpenEachMpqTest (patch-base-15295.MPQ) succeeded. -OpenEachMpqTest (patch-base-16416.MPQ) succeeded. -OpenEachMpqTest (patch-base-16603.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-14633.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-16416.MPQ) succeeded. -OpenEachMpqTest (patch-Win-16416.MPQ) succeeded. -OpenEachMpqTest (d3-update-enGB-14633.MPQ) succeeded. -OpenEachMpqTest (d3-update-enGB-16416.MPQ) succeeded. -OpenEachMpqTest (d3-update-Win-16416.MPQ) succeeded. -OpenEachMpqTest (SetupWin.mpq) succeeded. -OpenEachMpqTest (d3-update-base-21876.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-22044.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-22274.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-22427.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-23119.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-23920.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-24017.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-24641.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-26451.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-27255.MPQ) succeeded. -OpenEachMpqTest (d3-update-base-28709.MPQ) succeeded. -OpenEachMpqTest (base-Win.mpq) succeeded. -OpenEachMpqTest (patch-base-21876.MPQ) succeeded. -OpenEachMpqTest (patch-base-22044.MPQ) succeeded. -OpenEachMpqTest (patch-base-22274.MPQ) succeeded. -OpenEachMpqTest (patch-base-22427.MPQ) succeeded. -OpenEachMpqTest (patch-base-23119.MPQ) succeeded. -OpenEachMpqTest (patch-base-23920.MPQ) succeeded. -OpenEachMpqTest (patch-base-24017.MPQ) succeeded. -OpenEachMpqTest (patch-base-24641.MPQ) succeeded. -OpenEachMpqTest (patch-base-26451.MPQ) succeeded. -OpenEachMpqTest (patch-base-27255.MPQ) succeeded. -OpenEachMpqTest (patch-base-28709.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-21876.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-22044.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-22274.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-22427.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-23119.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-23920.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-24641.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-26451.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-27255.MPQ) succeeded. -OpenEachMpqTest (patch-enGB-28709.MPQ) succeeded. -OpenEachMpqTest (patch-Win-21876.MPQ) succeeded. -OpenEachMpqTest (patch-Win-22044.MPQ) succeeded. -OpenEachMpqTest (patch-Win-23119.MPQ) succeeded. -OpenEachMpqTest (patch-Win-23920.MPQ) succeeded. -OpenEachMpqTest (patch-Win-26451.MPQ) succeeded. -OpenEachMpqTest (patch-Win-27255.MPQ) succeeded. -OpenEachMpqTest (patch-Win-28709.MPQ) succeeded. -OpenEachMpqTest (ClientData.mpq) succeeded. -OpenEachMpqTest (CoreData.mpq) succeeded. -OpenEachMpqTest (d3-update-enGB-21876.MPQ) succeeded. -OpenEachMpqTest (d3-update-enGB-22044.MPQ) succeeded. -OpenEachMpqTest (d3-update-enGB-22274.MPQ) succeeded. -OpenEachMpqTest (d3-update-enGB-22427.MPQ) succeeded. -OpenEachMpqTest (d3-update-enGB-23119.MPQ) succeeded. -OpenEachMpqTest (d3-update-enGB-23920.MPQ) succeeded. -OpenEachMpqTest (d3-update-enGB-24641.MPQ) succeeded. -OpenEachMpqTest (d3-update-enGB-26451.MPQ) succeeded. -OpenEachMpqTest (d3-update-enGB-27255.MPQ) succeeded. -OpenEachMpqTest (d3-update-enGB-28709.MPQ) succeeded. -OpenEachMpqTest (enGB_Audio.mpq) succeeded. -OpenEachMpqTest (enGB_Cutscene.mpq) succeeded. -OpenEachMpqTest (enGB_Text.mpq) succeeded. -OpenEachMpqTest (HLSLShaders.mpq) succeeded. -OpenEachMpqTest (Sound.mpq) succeeded. -OpenEachMpqTest (Texture.mpq) succeeded. -OpenEachMpqTest (d3-update-Win-21876.MPQ) succeeded. -OpenEachMpqTest (d3-update-Win-22044.MPQ) succeeded. -OpenEachMpqTest (d3-update-Win-23119.MPQ) succeeded. -OpenEachMpqTest (d3-update-Win-23920.MPQ) succeeded. -OpenEachMpqTest (d3-update-Win-26451.MPQ) succeeded. -OpenEachMpqTest (d3-update-Win-27255.MPQ) succeeded. -OpenEachMpqTest (d3-update-Win-28709.MPQ) succeeded. -OpenEachMpqTest (SetupWin.mpq) succeeded. -OpenEachMpqTest (Installer Tome 1.MPQ) succeeded. -OpenEachMpqTest (base-Win.MPQ) succeeded. -OpenEachMpqTest (SetupWin.mpq) succeeded. -OpenEachMpqTest (base-Win.MPQ) succeeded. -OpenEachMpqTest (SetupWin.mpq) succeeded. -OpenEachMpqTest (hs-0-5314-Win-final.MPQ) succeeded. -OpenEachMpqTest (hs-5314-5435-Win-final.MPQ) succeeded. -OpenEachMpqTest (hs-5435-5506-Win-final.MPQ) succeeded. -OpenEachMpqTest (hs-5506-5834-Win-final.MPQ) succeeded. -OpenEachMpqTest (hs-5834-6024-Win-final.MPQ) succeeded. -OpenEachMpqTest (hs-6024-6141-Win-final.MPQ) succeeded. -OpenEachMpqTest (hs-6141-6187-Win-final.MPQ) succeeded. -OpenEachMpqTest (hs-6187-6284-Win-final.MPQ) succeeded. -OpenEachMpqTest (hs-6284-6485-Win-final.MPQ) succeeded. -OpenEachMpqTest (hs-6485-6898-Win-final.MPQ) succeeded. -OpenEachMpqTest (MPQ_1998_v1_StarDat.mpq) succeeded. -OpenEachMpqTest (MPQ_1999_v1_WeakSigned1.mpq) succeeded. -OpenEachMpqTest (MPQ_1999_v1_WeakSigned2.mpq) succeeded. -OpenEachMpqTest (MPQ_2009_v1_patch-complete.MPQ.part) succeeded. -OpenEachMpqTest (MPQ_2009_v1_patch-created.MPQ.part) succeeded. -OpenEachMpqTest (MPQ_2009_v1_patch-partial.MPQ.part) succeeded. -OpenEachMpqTest (MPQ_2009_v2_WoW_patch.MPQ.part) succeeded. -OpenEachMpqTest (MPQ_2011_v2_EncryptedMpq.MPQE) succeeded. -OpenEachMpqTest (MPQ_2013_v4_alternate-complete.MPQ) succeeded. -OpenEachMpqTest (MPQ_2013_v4_alternate-created.MPQ) succeeded. -OpenEachMpqTest (MPQ_2013_v4_alternate-incomplete.MPQ) succeeded. -OpenEachMpqTest (MPQ_2013_v4_alternate-original.MPQ) succeeded. -OpenEachMpqTest (MPQ_2014_v1_out1.w3x) succeeded. -OpenEachMpqTest (MPQ_2014_v1_out2.w3x) succeeded. -OpenEachMpqTest (MPQ_2022_v1_v4.329.w3x) succeeded. -OpenEachMpqTest (StormLibTest_AddWaveMonoBadTest.mpq) succeeded. -OpenEachMpqTest (StormLibTest_AddWaveMonoTest.mpq) succeeded. -OpenEachMpqTest (StormLibTest_AddWaveStereoTest.mpq) succeeded. -OpenEachMpqTest (StormLibTest_BigArchive_v4.mpq) succeeded. -OpenEachMpqTest (StormLibTest_CraftedMpq1_v3.mpq) succeeded. -OpenEachMpqTest (StormLibTest_CraftedMpq2_v4.mpq) succeeded. -OpenEachMpqTest (StormLibTest_CraftedMpq3_v4.mpq) succeeded. -OpenEachMpqTest: Warning: no files in the archive -OpenEachMpqTest: Warning: no files in the archive -OpenEachMpqTest (StormLibTest_FileFlagTest.mpq) succeeded. -OpenEachMpqTest (StormLibTest_FileTableFull.mpq) succeeded. -OpenEachMpqTest (StormLibTest_GapsTest.mpq) succeeded. -OpenEachMpqTest (StormLibTest_HasListFile.mpq) succeeded. -OpenEachMpqTest (StormLibTest_IncMaxFileCount.mpq) succeeded. -OpenEachMpqTest (StormLibTest_ListFilePos.mpq) succeeded. -OpenEachMpqTest (StormLibTest_MpqEditorTest.mpq) succeeded. -OpenEachMpqTest (StormLibTest_NoListFile.mpq) succeeded. -OpenEachMpqTest (StormLibTest_NonStdNames.mpq) succeeded. -OpenEachMpqTest (StormLibTest_ReadOnly.mpq) succeeded. -OpenEachMpqTest (StormLibTest_ReadWrite.mpq) succeeded. -OpenEachMpqTest (File00000003.mpq) succeeded. -FailMpqTest (flat-file://streaming/model.MPQ.0) succeeded. -OpenCorruptMpqTest (MPQ_2013_vX_Battle.net.MPQ) succeeded. -ReadOnlyTest (MPQ_1997_v1_Diablo1_DIABDAT.MPQ) succeeded. -ReadOnlyTest (MPQ_1997_v1_Diablo1_DIABDAT.MPQ) succeeded. -GetFileInfoTest (MPQ_2002_v1_StrongSignature.w3m+MPQ_2013_v4_SC2_EmptyMap.SC2Map) succeeded. -VerifySignatureTest (MPQ_1997_v1_Diablo1_STANDARD.SNP) succeeded. -VerifySignatureTest (MPQ_1999_v1_WeakSignature.exe) succeeded. -VerifySignatureTest (MPQ_2003_v1_WeakSignatureEmpty.exe) succeeded. -VerifySignatureTest (MPQ_2002_v1_StrongSignature.w3m) succeeded. -CompactMpqTest (MPQ_2010_v3_expansion-locale-frFR.MPQ) succeeded. -CompactMpqTest: The file "(attributes)" is not present, but it should be -CompactMpqTest: The file "(attributes)" is not present, but it should be -CompactMpqTest (MPQ_2013_v4_SC2_EmptyMap.SC2Map) succeeded. -CompactMpqTest (MPQ_2013_v4_expansion1.MPQ) succeeded. -FullMpqTest (MPQ_2014_v1_out1.w3x) succeeded. -FullMpqTest (MPQ_2014_v1_out2.w3x) succeeded. -ListFileTest (MPQ_1997_v1_Diablo1_DIABDAT.MPQ) succeeded. -ListFileTest (MPQ_2013_v4_SC2_EmptyMap.SC2Map) succeeded. -CreateEmptyMpq: The file "File00000000.xxx" is present, but it should not be -CreateEmptyMpq: The file "File00000000.xxx" is present, but it should not be -CreateGapsTest (StormLibTest_GapsTest.mpq) succeeded. -NonStdNamesTest: Adding file " \ \ \ .txt" ... NonStdNamesTest: Adding file "Dir1 \Dir2 \File.txt ." ... NonStdNamesTest: Adding file "Dir1 \Dir2 \ . ." ... NonStdNamesTest (StormLibTest_NonStdNames.mpq) succeeded. -SignExistingMpq (MPQ_1998_v1_StarDat.mpq) succeeded. -ModifySignedTest (MPQ_1999_v1_WeakSignature.exe) succeeded. -CreateSignedMpq (MPQ_1999_v1_WeakSigned1.mpq) succeeded. -CreateSignedMpq (MPQ_1999_v1_WeakSigned2.mpq) succeeded. -CreateMpqEditor (StormLibTest_MpqEditorTest.mpq) succeeded. -CreateFullMpq (StormLibTest_FileTableFull.mpq) succeeded. -CreateFullMpq (StormLibTest_FileTableFull.mpq) succeeded. -CreateFullMpq (StormLibTest_FileTableFull.mpq) succeeded. -CreateFullMpq (StormLibTest_FileTableFull.mpq) succeeded. -IncMaxFileCount (StormLibTest_IncMaxFileCount.mpq) succeeded. -MpqUnicodeName succeeded. -FileFlagTest (StormLibTest_FileFlagTest.mpq) succeeded. -CompressionsTest (StormLibTest_AddWaveMonoTest.mpq) succeeded. -CompressionsTest (StormLibTest_AddWaveMonoBadTest.mpq) succeeded. -CompressionsTest (StormLibTest_AddWaveStereoTest.mpq) succeeded. -ListFilePos (StormLibTest_ListFilePos.mpq) succeeded. -BigMpqTest (StormLibTest_BigArchive_v4.mpq) succeeded. -ModifyTest (MPQ_2014_v4_Base.StormReplay) succeeded. -ModifyTest (MPQ_2022_v1_v4.329.w3x) succeeded. - -E:\Ladik\AppDir\StormLib\bin\StormLib_test\x64\Release> \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StrHash64/StrHash64.cpp b/app/jni/src/libultraship/extern/StrHash64/StrHash64.cpp deleted file mode 100644 index fd96d61..0000000 --- a/app/jni/src/libultraship/extern/StrHash64/StrHash64.cpp +++ /dev/null @@ -1,250 +0,0 @@ - /* - * Below are the various copyright notices from the original source. - * - * - * The source has be substationally modified: - * 1. Unneeded code has been deleted. - * 2. The code was converted from C++ to C. - * 3. Routines optimized for hashing were added. - */ - /////////////////////////////////////////////////////////////////////////////////// - // - // Copyright (c) 2006 Anton Samokhvalov - // - // 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. - // - /////////////////////////////////////////////////////////////////////////////////// - /* - [To some parts of this code] - */ - /* - Copyright (C) 1995-2004 Jean-loup Gailly and Mark Adler - 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. - Jean-loup Gailly Mark Adler - jloup@gzip.org madler@alumni.caltech.edu - */ - /* - [To some parts of this code] - */ - /* - Copyright (c) 2003, Dominik Reichl - All rights reserved. - LICENSE TERMS - 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 ReichlSoft nor the names of its contributors may be used - to endorse or promote products derived from this software without specific - prior written permission. - DISCLAIMER - 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 - -#define u8 uint8_t -#define u16 uint16_t -#define u32 uint32_t -#define u64 uint64_t -#define unint uint32_t - -#define INITIAL_CRC64 0xffffffffffffffffULL - -#define CONST64(n) n##ull -static const u64 CRC64_Table[256] = { - CONST64(0x0000000000000000), CONST64(0x42f0e1eba9ea3693), - CONST64(0x85e1c3d753d46d26), CONST64(0xc711223cfa3e5bb5), - CONST64(0x493366450e42ecdf), CONST64(0x0bc387aea7a8da4c), - CONST64(0xccd2a5925d9681f9), CONST64(0x8e224479f47cb76a), - CONST64(0x9266cc8a1c85d9be), CONST64(0xd0962d61b56fef2d), - CONST64(0x17870f5d4f51b498), CONST64(0x5577eeb6e6bb820b), - CONST64(0xdb55aacf12c73561), CONST64(0x99a54b24bb2d03f2), - CONST64(0x5eb4691841135847), CONST64(0x1c4488f3e8f96ed4), - CONST64(0x663d78ff90e185ef), CONST64(0x24cd9914390bb37c), - CONST64(0xe3dcbb28c335e8c9), CONST64(0xa12c5ac36adfde5a), - CONST64(0x2f0e1eba9ea36930), CONST64(0x6dfeff5137495fa3), - CONST64(0xaaefdd6dcd770416), CONST64(0xe81f3c86649d3285), - CONST64(0xf45bb4758c645c51), CONST64(0xb6ab559e258e6ac2), - CONST64(0x71ba77a2dfb03177), CONST64(0x334a9649765a07e4), - CONST64(0xbd68d2308226b08e), CONST64(0xff9833db2bcc861d), - CONST64(0x388911e7d1f2dda8), CONST64(0x7a79f00c7818eb3b), - CONST64(0xcc7af1ff21c30bde), CONST64(0x8e8a101488293d4d), - CONST64(0x499b3228721766f8), CONST64(0x0b6bd3c3dbfd506b), - CONST64(0x854997ba2f81e701), CONST64(0xc7b97651866bd192), - CONST64(0x00a8546d7c558a27), CONST64(0x4258b586d5bfbcb4), - CONST64(0x5e1c3d753d46d260), CONST64(0x1cecdc9e94ace4f3), - CONST64(0xdbfdfea26e92bf46), CONST64(0x990d1f49c77889d5), - CONST64(0x172f5b3033043ebf), CONST64(0x55dfbadb9aee082c), - CONST64(0x92ce98e760d05399), CONST64(0xd03e790cc93a650a), - CONST64(0xaa478900b1228e31), CONST64(0xe8b768eb18c8b8a2), - CONST64(0x2fa64ad7e2f6e317), CONST64(0x6d56ab3c4b1cd584), - CONST64(0xe374ef45bf6062ee), CONST64(0xa1840eae168a547d), - CONST64(0x66952c92ecb40fc8), CONST64(0x2465cd79455e395b), - CONST64(0x3821458aada7578f), CONST64(0x7ad1a461044d611c), - CONST64(0xbdc0865dfe733aa9), CONST64(0xff3067b657990c3a), - CONST64(0x711223cfa3e5bb50), CONST64(0x33e2c2240a0f8dc3), - CONST64(0xf4f3e018f031d676), CONST64(0xb60301f359dbe0e5), - CONST64(0xda050215ea6c212f), CONST64(0x98f5e3fe438617bc), - CONST64(0x5fe4c1c2b9b84c09), CONST64(0x1d14202910527a9a), - CONST64(0x93366450e42ecdf0), CONST64(0xd1c685bb4dc4fb63), - CONST64(0x16d7a787b7faa0d6), CONST64(0x5427466c1e109645), - CONST64(0x4863ce9ff6e9f891), CONST64(0x0a932f745f03ce02), - CONST64(0xcd820d48a53d95b7), CONST64(0x8f72eca30cd7a324), - CONST64(0x0150a8daf8ab144e), CONST64(0x43a04931514122dd), - CONST64(0x84b16b0dab7f7968), CONST64(0xc6418ae602954ffb), - CONST64(0xbc387aea7a8da4c0), CONST64(0xfec89b01d3679253), - CONST64(0x39d9b93d2959c9e6), CONST64(0x7b2958d680b3ff75), - CONST64(0xf50b1caf74cf481f), CONST64(0xb7fbfd44dd257e8c), - CONST64(0x70eadf78271b2539), CONST64(0x321a3e938ef113aa), - CONST64(0x2e5eb66066087d7e), CONST64(0x6cae578bcfe24bed), - CONST64(0xabbf75b735dc1058), CONST64(0xe94f945c9c3626cb), - CONST64(0x676dd025684a91a1), CONST64(0x259d31cec1a0a732), - CONST64(0xe28c13f23b9efc87), CONST64(0xa07cf2199274ca14), - CONST64(0x167ff3eacbaf2af1), CONST64(0x548f120162451c62), - CONST64(0x939e303d987b47d7), CONST64(0xd16ed1d631917144), - CONST64(0x5f4c95afc5edc62e), CONST64(0x1dbc74446c07f0bd), - CONST64(0xdaad56789639ab08), CONST64(0x985db7933fd39d9b), - CONST64(0x84193f60d72af34f), CONST64(0xc6e9de8b7ec0c5dc), - CONST64(0x01f8fcb784fe9e69), CONST64(0x43081d5c2d14a8fa), - CONST64(0xcd2a5925d9681f90), CONST64(0x8fdab8ce70822903), - CONST64(0x48cb9af28abc72b6), CONST64(0x0a3b7b1923564425), - CONST64(0x70428b155b4eaf1e), CONST64(0x32b26afef2a4998d), - CONST64(0xf5a348c2089ac238), CONST64(0xb753a929a170f4ab), - CONST64(0x3971ed50550c43c1), CONST64(0x7b810cbbfce67552), - CONST64(0xbc902e8706d82ee7), CONST64(0xfe60cf6caf321874), - CONST64(0xe224479f47cb76a0), CONST64(0xa0d4a674ee214033), - CONST64(0x67c58448141f1b86), CONST64(0x253565a3bdf52d15), - CONST64(0xab1721da49899a7f), CONST64(0xe9e7c031e063acec), - CONST64(0x2ef6e20d1a5df759), CONST64(0x6c0603e6b3b7c1ca), - CONST64(0xf6fae5c07d3274cd), CONST64(0xb40a042bd4d8425e), - CONST64(0x731b26172ee619eb), CONST64(0x31ebc7fc870c2f78), - CONST64(0xbfc9838573709812), CONST64(0xfd39626eda9aae81), - CONST64(0x3a28405220a4f534), CONST64(0x78d8a1b9894ec3a7), - CONST64(0x649c294a61b7ad73), CONST64(0x266cc8a1c85d9be0), - CONST64(0xe17dea9d3263c055), CONST64(0xa38d0b769b89f6c6), - CONST64(0x2daf4f0f6ff541ac), CONST64(0x6f5faee4c61f773f), - CONST64(0xa84e8cd83c212c8a), CONST64(0xeabe6d3395cb1a19), - CONST64(0x90c79d3fedd3f122), CONST64(0xd2377cd44439c7b1), - CONST64(0x15265ee8be079c04), CONST64(0x57d6bf0317edaa97), - CONST64(0xd9f4fb7ae3911dfd), CONST64(0x9b041a914a7b2b6e), - CONST64(0x5c1538adb04570db), CONST64(0x1ee5d94619af4648), - CONST64(0x02a151b5f156289c), CONST64(0x4051b05e58bc1e0f), - CONST64(0x87409262a28245ba), CONST64(0xc5b073890b687329), - CONST64(0x4b9237f0ff14c443), CONST64(0x0962d61b56fef2d0), - CONST64(0xce73f427acc0a965), CONST64(0x8c8315cc052a9ff6), - CONST64(0x3a80143f5cf17f13), CONST64(0x7870f5d4f51b4980), - CONST64(0xbf61d7e80f251235), CONST64(0xfd913603a6cf24a6), - CONST64(0x73b3727a52b393cc), CONST64(0x31439391fb59a55f), - CONST64(0xf652b1ad0167feea), CONST64(0xb4a25046a88dc879), - CONST64(0xa8e6d8b54074a6ad), CONST64(0xea16395ee99e903e), - CONST64(0x2d071b6213a0cb8b), CONST64(0x6ff7fa89ba4afd18), - CONST64(0xe1d5bef04e364a72), CONST64(0xa3255f1be7dc7ce1), - CONST64(0x64347d271de22754), CONST64(0x26c49cccb40811c7), - CONST64(0x5cbd6cc0cc10fafc), CONST64(0x1e4d8d2b65facc6f), - CONST64(0xd95caf179fc497da), CONST64(0x9bac4efc362ea149), - CONST64(0x158e0a85c2521623), CONST64(0x577eeb6e6bb820b0), - CONST64(0x906fc95291867b05), CONST64(0xd29f28b9386c4d96), - CONST64(0xcedba04ad0952342), CONST64(0x8c2b41a1797f15d1), - CONST64(0x4b3a639d83414e64), CONST64(0x09ca82762aab78f7), - CONST64(0x87e8c60fded7cf9d), CONST64(0xc51827e4773df90e), - CONST64(0x020905d88d03a2bb), CONST64(0x40f9e43324e99428), - CONST64(0x2cffe7d5975e55e2), CONST64(0x6e0f063e3eb46371), - CONST64(0xa91e2402c48a38c4), CONST64(0xebeec5e96d600e57), - CONST64(0x65cc8190991cb93d), CONST64(0x273c607b30f68fae), - CONST64(0xe02d4247cac8d41b), CONST64(0xa2dda3ac6322e288), - CONST64(0xbe992b5f8bdb8c5c), CONST64(0xfc69cab42231bacf), - CONST64(0x3b78e888d80fe17a), CONST64(0x7988096371e5d7e9), - CONST64(0xf7aa4d1a85996083), CONST64(0xb55aacf12c735610), - CONST64(0x724b8ecdd64d0da5), CONST64(0x30bb6f267fa73b36), - CONST64(0x4ac29f2a07bfd00d), CONST64(0x08327ec1ae55e69e), - CONST64(0xcf235cfd546bbd2b), CONST64(0x8dd3bd16fd818bb8), - CONST64(0x03f1f96f09fd3cd2), CONST64(0x41011884a0170a41), - CONST64(0x86103ab85a2951f4), CONST64(0xc4e0db53f3c36767), - CONST64(0xd8a453a01b3a09b3), CONST64(0x9a54b24bb2d03f20), - CONST64(0x5d45907748ee6495), CONST64(0x1fb5719ce1045206), - CONST64(0x919735e51578e56c), CONST64(0xd367d40ebc92d3ff), - CONST64(0x1476f63246ac884a), CONST64(0x568617d9ef46bed9), - CONST64(0xe085162ab69d5e3c), CONST64(0xa275f7c11f7768af), - CONST64(0x6564d5fde549331a), CONST64(0x279434164ca30589), - CONST64(0xa9b6706fb8dfb2e3), CONST64(0xeb46918411358470), - CONST64(0x2c57b3b8eb0bdfc5), CONST64(0x6ea7525342e1e956), - CONST64(0x72e3daa0aa188782), CONST64(0x30133b4b03f2b111), - CONST64(0xf7021977f9cceaa4), CONST64(0xb5f2f89c5026dc37), - CONST64(0x3bd0bce5a45a6b5d), CONST64(0x79205d0e0db05dce), - CONST64(0xbe317f32f78e067b), CONST64(0xfcc19ed95e6430e8), - CONST64(0x86b86ed5267cdbd3), CONST64(0xc4488f3e8f96ed40), - CONST64(0x0359ad0275a8b6f5), CONST64(0x41a94ce9dc428066), - CONST64(0xcf8b0890283e370c), CONST64(0x8d7be97b81d4019f), - CONST64(0x4a6acb477bea5a2a), CONST64(0x089a2aacd2006cb9), - CONST64(0x14dea25f3af9026d), CONST64(0x562e43b4931334fe), - CONST64(0x913f6188692d6f4b), CONST64(0xd3cf8063c0c759d8), - CONST64(0x5dedc41a34bbeeb2), CONST64(0x1f1d25f19d51d821), - CONST64(0xd80c07cd676f8394), CONST64(0x9afce626ce85b507) -}; - -uint64_t update_crc64(const void* buf, unint len, u64 crc) -{ - const u8* b = (const u8*)buf; - unint i; - for (i = 0; i < len; i++) { - crc = CRC64_Table[(u8)(crc >> 56) ^ *b++] ^ (crc << 8); - } - return ~crc; -} - -u64 crc64(const void* buf, unint len) -{ - return update_crc64(buf, len, INITIAL_CRC64); -} - -u64 CRC64(const char* t) -{ - u64 crc = INITIAL_CRC64; - const u8* s = (const u8*)t; - while (*s) { - crc = CRC64_Table[(u8)(crc >> 56) ^ *s++] ^ (crc << 8); - } - return crc; -} \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/StrHash64/StrHash64.h b/app/jni/src/libultraship/extern/StrHash64/StrHash64.h deleted file mode 100644 index d8cc8ff..0000000 --- a/app/jni/src/libultraship/extern/StrHash64/StrHash64.h +++ /dev/null @@ -1,93 +0,0 @@ -#pragma once - -/* - * Below are the various copyright notices from the original source. - * - * - * The source has be substationally modified: - * 1. Unneeded code has been deleted. - * 2. The code was converted from C++ to C. - * 3. Routines optimized for hashing were added. - */ - /////////////////////////////////////////////////////////////////////////////////// - // - // Copyright (c) 2006 Anton Samokhvalov - // - // 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. - // - /////////////////////////////////////////////////////////////////////////////////// - /* - [To some parts of this code] - */ - /* - Copyright (C) 1995-2004 Jean-loup Gailly and Mark Adler - 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. - Jean-loup Gailly Mark Adler - jloup@gzip.org madler@alumni.caltech.edu - */ - /* - [To some parts of this code] - */ - /* - Copyright (c) 2003, Dominik Reichl - All rights reserved. - LICENSE TERMS - 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 ReichlSoft nor the names of its contributors may be used - to endorse or promote products derived from this software without specific - prior written permission. - DISCLAIMER - 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 - -#define INITIAL_CRC64 0xffffffffffffffffULL - -extern uint64_t update_crc64(const void* buf, uint32_t len, uint64_t crc); -extern uint64_t crc64(const void* buf, uint32_t len); -extern uint64_t CRC64(const char* t); \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ZAPDUtils/CMakeLists.txt b/app/jni/src/libultraship/extern/ZAPDUtils/CMakeLists.txt deleted file mode 100644 index baf868f..0000000 --- a/app/jni/src/libultraship/extern/ZAPDUtils/CMakeLists.txt +++ /dev/null @@ -1,194 +0,0 @@ -set(PROJECT_NAME ZAPDUtils) - -################################################################################ -# Source groups -################################################################################ -set(Source_Files__Utils - "Utils/StringHelper.cpp" - "Utils/MemoryStream.cpp" - "Utils/BinaryWriter.cpp" -) -source_group("Source Files\\Utils" FILES ${Source_Files__Utils}) - -################################################################################ -# Target -################################################################################ -add_library(${PROJECT_NAME} STATIC) -set_property(TARGET ${PROJECT_NAME} PROPERTY CXX_STANDARD 20) - -target_sources(${PROJECT_NAME} PRIVATE ${Source_Files__Utils}) - -target_include_directories(${PROJECT_NAME} PUBLIC - $ - $ - PRIVATE ${CMAKE_CURRENT_SOURCE_DIR} -) - -target_link_libraries(${PROJECT_NAME} PRIVATE tinyxml2) - -if (CMAKE_SYSTEM_NAME STREQUAL "Windows") -use_props(${PROJECT_NAME} "${CMAKE_CONFIGURATION_TYPES}" "${DEFAULT_CXX_PROPS}") -endif() - -set(ROOT_NAMESPACE ZAPDUtils) - -if (CMAKE_SYSTEM_NAME STREQUAL "Windows") - set_target_properties(${PROJECT_NAME} PROPERTIES - VS_GLOBAL_KEYWORD "Win32Proj" - ) - if("${CMAKE_VS_PLATFORM_NAME}" STREQUAL "x64") - set_target_properties(${PROJECT_NAME} PROPERTIES - INTERPROCEDURAL_OPTIMIZATION_RELEASE "TRUE" - ) - elseif("${CMAKE_VS_PLATFORM_NAME}" STREQUAL "Win32") - set_target_properties(${PROJECT_NAME} PROPERTIES - INTERPROCEDURAL_OPTIMIZATION_RELEASE "TRUE" - ) - endif() -endif() -################################################################################ -# MSVC runtime library -################################################################################ -if (CMAKE_SYSTEM_NAME STREQUAL "Windows") - get_property(MSVC_RUNTIME_LIBRARY_DEFAULT TARGET ${PROJECT_NAME} PROPERTY MSVC_RUNTIME_LIBRARY) - if("${CMAKE_VS_PLATFORM_NAME}" MATCHES "x64") - string(CONCAT "MSVC_RUNTIME_LIBRARY_STR" - $<$: - MultiThreadedDebug - > - $<$: - MultiThreaded - > - $<$,$>>:${MSVC_RUNTIME_LIBRARY_DEFAULT}> - ) - elseif("${CMAKE_VS_PLATFORM_NAME}" STREQUAL "Win32") - string(CONCAT "MSVC_RUNTIME_LIBRARY_STR" - MultiThreaded - ) - endif() - set_target_properties(${PROJECT_NAME} PROPERTIES MSVC_RUNTIME_LIBRARY ${MSVC_RUNTIME_LIBRARY_STR}) -endif() -################################################################################ -# Compile definitions -################################################################################ -if (CMAKE_SYSTEM_NAME STREQUAL "Windows") - if("${CMAKE_VS_PLATFORM_NAME}" STREQUAL "x64") - target_compile_definitions(${PROJECT_NAME} PRIVATE - "$<$:" - "_DEBUG;" - "_MBCS" - ">" - "$<$:" - "NDEBUG;" - "UNICODE;" - "_UNICODE" - ">" - "_CONSOLE;" - "_CRT_SECURE_NO_WARNINGS" - STORMLIB_NO_AUTO_LINK - ) - elseif("${CMAKE_VS_PLATFORM_NAME}" STREQUAL "Win32") - target_compile_definitions(${PROJECT_NAME} PRIVATE - "$<$:" - "_DEBUG" - ">" - "$<$:" - "NDEBUG" - ">" - "WIN32;" - "_CONSOLE;" - "_CRT_SECURE_NO_WARNINGS;" - "UNICODE;" - "_UNICODE" - STORMLIB_NO_AUTO_LINK - ) - endif() -endif() - -if ("${CMAKE_CXX_COMPILER_ID}" MATCHES "GNU|Clang|AppleClang") - target_compile_definitions(${PROJECT_NAME} PRIVATE - "$<$:" - "_DEBUG" - ">" - "$<$:" - "NDEBUG" - ">" - "_CONSOLE;" - "_CRT_SECURE_NO_WARNINGS;" - "UNICODE;" - "_UNICODE" - ) -endif() - -################################################################################ -# Compile and link options -################################################################################ -if(MSVC) - if("${CMAKE_VS_PLATFORM_NAME}" STREQUAL "x64") - target_compile_options(${PROJECT_NAME} PRIVATE - $<$: - /Oi; - /Gy - > - /permissive-; - /MP; - /sdl; - /W3; - ${DEFAULT_CXX_DEBUG_INFORMATION_FORMAT}; - ${DEFAULT_CXX_EXCEPTION_HANDLING} - ) - elseif("${CMAKE_VS_PLATFORM_NAME}" STREQUAL "Win32") - target_compile_options(${PROJECT_NAME} PRIVATE - $<$: - /O2; - /Ot - > - $<$: - /Gy - > - /permissive-; - /MP; - /Oi; - /sdl; - /W3; - ${DEFAULT_CXX_DEBUG_INFORMATION_FORMAT}; - ${DEFAULT_CXX_EXCEPTION_HANDLING} - ) - endif() - if("${CMAKE_VS_PLATFORM_NAME}" STREQUAL "x64") - target_link_options(${PROJECT_NAME} PRIVATE - $<$: - /OPT:REF; - /OPT:ICF - > - /SUBSYSTEM:CONSOLE - ) - elseif("${CMAKE_VS_PLATFORM_NAME}" STREQUAL "Win32") - target_link_options(${PROJECT_NAME} PRIVATE - $<$: - /OPT:REF; - /OPT:ICF - > - /SUBSYSTEM:CONSOLE - ) - endif() -endif() - -if ("${CMAKE_CXX_COMPILER_ID}" MATCHES "GNU|Clang|AppleClang") - target_compile_options(${PROJECT_NAME} PRIVATE - -Wall -Wextra -Wno-error - -Wno-unused-parameter - -Wno-unused-function - -Wno-unused-variable - -Wno-missing-field-initializers - -Wno-parentheses - -Wno-narrowing - $<$:-Wno-deprecated-enum-enum-conversion> - ) -endif() -################################################################################ -# Dependencies -################################################################################ -# Link with other targets. - - diff --git a/app/jni/src/libultraship/extern/ZAPDUtils/Color3b.h b/app/jni/src/libultraship/extern/ZAPDUtils/Color3b.h deleted file mode 100644 index 507c099..0000000 --- a/app/jni/src/libultraship/extern/ZAPDUtils/Color3b.h +++ /dev/null @@ -1,21 +0,0 @@ -#pragma once - -#include - -struct Color3b -{ - uint8_t r, g, b; - - Color3b() - { - r = 0; - g = 0; - b = 0; - }; - Color3b(uint8_t nR, uint8_t nG, uint8_t nB) - { - r = nR; - g = nG; - b = nB; - }; -}; \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ZAPDUtils/StrHash.h b/app/jni/src/libultraship/extern/ZAPDUtils/StrHash.h deleted file mode 100644 index c611bdd..0000000 --- a/app/jni/src/libultraship/extern/ZAPDUtils/StrHash.h +++ /dev/null @@ -1,51 +0,0 @@ -#pragma once - -#include -#include -#include - -typedef uint32_t strhash; - -[[maybe_unused]] static strhash CRC32B(unsigned char* message, int32_t size) -{ - int32_t byte = 0, crc = 0; - int32_t mask = 0; - - crc = 0xFFFFFFFF; - - for (int32_t i = 0; i < size; i++) - { - byte = message[i]; - crc = crc ^ byte; - - for (int32_t j = 7; j >= 0; j--) - { - mask = -(crc & 1); - crc = (crc >> 1) ^ (0xEDB88320 & mask); - } - } - - return ~(uint32_t)(crc); -} - -[[maybe_unused]] constexpr static strhash CRC32BCT(const char* message, int32_t size) -{ - int32_t byte = 0, crc = 0; - int32_t mask = 0; - - crc = 0xFFFFFFFF; - - for (int32_t i = 0; i < size; i++) - { - byte = message[i]; - crc = crc ^ byte; - - for (int32_t j = 7; j >= 0; j--) - { - mask = -(crc & 1); - crc = (crc >> 1) ^ (0xEDB88320 & mask); - } - } - - return ~(uint32_t)(crc); -} \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ZAPDUtils/Utils/BinaryReader.cpp b/app/jni/src/libultraship/extern/ZAPDUtils/Utils/BinaryReader.cpp deleted file mode 100644 index 092124a..0000000 --- a/app/jni/src/libultraship/extern/ZAPDUtils/Utils/BinaryReader.cpp +++ /dev/null @@ -1,203 +0,0 @@ -#include "BinaryReader.h" -#include -#include -#include "Stream.h" - -BinaryReader::BinaryReader(Stream* nStream) -{ - stream.reset(nStream); -} - -BinaryReader::BinaryReader(std::shared_ptr nStream) -{ - stream = nStream; -} - -void BinaryReader::Close() -{ - stream->Close(); -} - -void BinaryReader::SetEndianness(Endianness endianness) -{ - this->endianness = endianness; -} - -Endianness BinaryReader::GetEndianness() const -{ - return endianness; -} - -void BinaryReader::Seek(uint32_t offset, SeekOffsetType seekType) -{ - stream->Seek(offset, seekType); -} - -uint32_t BinaryReader::GetBaseAddress() -{ - return stream->GetBaseAddress(); -} - -void BinaryReader::Read(int32_t length) -{ - stream->Read(length); -} - -void BinaryReader::Read(char* buffer, int32_t length) -{ - stream->Read(buffer, length); -} - -char BinaryReader::ReadChar() -{ - return (char)stream->ReadByte(); -} - -int8_t BinaryReader::ReadByte() -{ - return stream->ReadByte(); -} - -uint8_t BinaryReader::ReadUByte() -{ - return (uint8_t)stream->ReadByte(); -} - -int16_t BinaryReader::ReadInt16() -{ - int16_t result = 0; - - stream->Read((char*)&result, sizeof(int16_t)); - - if (endianness != Endianness::Native) - result = BSWAP16(result); - - return result; -} - -int32_t BinaryReader::ReadInt32() -{ - int32_t result = 0; - - stream->Read((char*)&result, sizeof(int32_t)); - - if (endianness != Endianness::Native) - result = BSWAP32(result); - - return result; -} - -uint16_t BinaryReader::ReadUInt16() -{ - uint16_t result = 0; - - stream->Read((char*)&result, sizeof(uint16_t)); - - if (endianness != Endianness::Native) - result = BSWAP16(result); - - return result; -} - -uint32_t BinaryReader::ReadUInt32() -{ - uint32_t result = 0; - - stream->Read((char*)&result, sizeof(uint32_t)); - - if (endianness != Endianness::Native) - result = BSWAP32(result); - - return result; -} - -uint64_t BinaryReader::ReadUInt64() -{ - uint64_t result = 0; - - stream->Read((char*)&result, sizeof(uint64_t)); - - if (endianness != Endianness::Native) - result = BSWAP64(result); - - return result; -} - -float BinaryReader::ReadSingle() -{ - float result = NAN; - - stream->Read((char*)&result, sizeof(float)); - - if (endianness != Endianness::Native) - { - float tmp; - char* dst = (char*)&tmp; - char* src = (char*)&result; - dst[3] = src[0]; dst[2] = src[1]; dst[1] = src[2]; dst[0] = src[3]; - result = tmp; - } - - if (std::isnan(result)) - throw std::runtime_error("BinaryReader::ReadSingle(): Error reading stream"); - - return result; -} - -double BinaryReader::ReadDouble() -{ - double result = NAN; - - stream->Read((char*)&result, sizeof(double)); - - if (endianness != Endianness::Native) - { - double tmp; - char* dst = (char*)&tmp; - char* src = (char*)&result; - dst[7] = src[0]; dst[6] = src[1]; dst[5] = src[2]; dst[4] = src[3]; - dst[3] = src[4]; dst[2] = src[5]; dst[1] = src[6]; dst[0] = src[7]; - result = tmp; - } - - if (std::isnan(result)) - throw std::runtime_error("BinaryReader::ReadDouble(): Error reading stream"); - - return result; -} - -Vec3f BinaryReader::ReadVec3f() -{ - return Vec3f(); -} - -Vec3s BinaryReader::ReadVec3s() -{ - return Vec3s(0, 0, 0); -} - -Vec3s BinaryReader::ReadVec3b() -{ - return Vec3s(0, 0, 0); -} - -Vec2f BinaryReader::ReadVec2f() -{ - return Vec2f(); -} - -Color3b BinaryReader::ReadColor3b() -{ - return Color3b(); -} - -std::string BinaryReader::ReadString() -{ - std::string res; - int numChars = ReadInt32(); - - for (int i = 0; i < numChars; i++) - res += ReadChar(); - - return res; -} \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ZAPDUtils/Utils/BinaryReader.h b/app/jni/src/libultraship/extern/ZAPDUtils/Utils/BinaryReader.h deleted file mode 100644 index 0b18351..0000000 --- a/app/jni/src/libultraship/extern/ZAPDUtils/Utils/BinaryReader.h +++ /dev/null @@ -1,50 +0,0 @@ -#pragma once - -#include -#include -#include -#include -#include "../Color3b.h" -#include "../Vec2f.h" -#include "../Vec3f.h" -#include "../Vec3s.h" -#include "BitConverter.h" -#include "Stream.h" - -class BinaryReader -{ -public: - BinaryReader(Stream* nStream); - BinaryReader(std::shared_ptr nStream); - - void Close(); - - void SetEndianness(Endianness endianness); - Endianness GetEndianness() const; - - void Seek(uint32_t offset, SeekOffsetType seekType); - uint32_t GetBaseAddress(); - - void Read(int32_t length); - void Read(char* buffer, int32_t length); - char ReadChar(); - int8_t ReadByte(); - int16_t ReadInt16(); - int32_t ReadInt32(); - uint8_t ReadUByte(); - uint16_t ReadUInt16(); - uint32_t ReadUInt32(); - uint64_t ReadUInt64(); - float ReadSingle(); - double ReadDouble(); - Vec3f ReadVec3f(); - Vec3s ReadVec3s(); - Vec3s ReadVec3b(); - Vec2f ReadVec2f(); - Color3b ReadColor3b(); - std::string ReadString(); - -protected: - std::shared_ptr stream; - Endianness endianness = Endianness::Native; -}; \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ZAPDUtils/Utils/BinaryWriter.cpp b/app/jni/src/libultraship/extern/ZAPDUtils/Utils/BinaryWriter.cpp deleted file mode 100644 index 34bcad0..0000000 --- a/app/jni/src/libultraship/extern/ZAPDUtils/Utils/BinaryWriter.cpp +++ /dev/null @@ -1,148 +0,0 @@ -#include "BinaryWriter.h" - -BinaryWriter::BinaryWriter(Stream* nStream) -{ - stream.reset(nStream); -} - -BinaryWriter::BinaryWriter(std::shared_ptr nStream) -{ - stream = nStream; -} - -void BinaryWriter::SetEndianness(Endianness endianness) -{ - this->endianness = endianness; -} - -void BinaryWriter::Close() -{ - stream->Close(); -} - -std::shared_ptr BinaryWriter::GetStream() -{ - return stream; -} - -uint64_t BinaryWriter::GetBaseAddress() -{ - return stream->GetBaseAddress(); -} - -uint64_t BinaryWriter::GetLength() -{ - return stream->GetLength(); -} - -void BinaryWriter::Seek(int32_t offset, SeekOffsetType seekType) -{ - stream->Seek(offset, seekType); -} - -void BinaryWriter::Write(int8_t value) -{ - stream->Write((char*)&value, sizeof(int8_t)); -} - -void BinaryWriter::Write(uint8_t value) -{ - stream->Write((char*)&value, sizeof(uint8_t)); -} - -void BinaryWriter::Write(int16_t value) -{ - if (endianness != Endianness::Native) - value = BSWAP16(value); - - stream->Write((char*)&value, sizeof(int16_t)); -} - -void BinaryWriter::Write(uint16_t value) -{ - if (endianness != Endianness::Native) - value = BSWAP16(value); - - stream->Write((char*)&value, sizeof(uint16_t)); -} - -void BinaryWriter::Write(int32_t value) -{ - if (endianness != Endianness::Native) - value = BSWAP32(value); - - stream->Write((char*)&value, sizeof(int32_t)); -} - -void BinaryWriter::Write(int32_t valueA, int32_t valueB) -{ - Write(valueA); - Write(valueB); -} - -void BinaryWriter::Write(uint32_t value) -{ - if (endianness != Endianness::Native) - value = BSWAP32(value); - - stream->Write((char*)&value, sizeof(uint32_t)); -} - -void BinaryWriter::Write(int64_t value) -{ - if (endianness != Endianness::Native) - value = BSWAP64(value); - - stream->Write((char*)&value, sizeof(int64_t)); -} - -void BinaryWriter::Write(uint64_t value) -{ - if (endianness != Endianness::Native) - value = BSWAP64(value); - - stream->Write((char*)&value, sizeof(uint64_t)); -} - -void BinaryWriter::Write(float value) -{ - if (endianness != Endianness::Native) - { - float tmp; - char* dst = (char*)&tmp; - char* src = (char*)&value; - dst[3] = src[0]; dst[2] = src[1]; dst[1] = src[2]; dst[0] = src[3]; - value = tmp; - } - - stream->Write((char*)&value, sizeof(float)); -} - -void BinaryWriter::Write(double value) -{ - if (endianness != Endianness::Native) - { - double tmp; - char* dst = (char*)&tmp; - char* src = (char*)&value; - dst[7] = src[0]; dst[6] = src[1]; dst[5] = src[2]; dst[4] = src[3]; - dst[3] = src[4]; dst[2] = src[5]; dst[1] = src[6]; dst[0] = src[7]; - value = tmp; - } - - stream->Write((char*)&value, sizeof(double)); -} - -void BinaryWriter::Write(const std::string& str) -{ - int strLen = str.size(); - Write(strLen); - - for (char c : str) - stream->WriteByte(c); -} - -void BinaryWriter::Write(char* srcBuffer, size_t length) -{ - stream->Write(srcBuffer, length); -} diff --git a/app/jni/src/libultraship/extern/ZAPDUtils/Utils/BinaryWriter.h b/app/jni/src/libultraship/extern/ZAPDUtils/Utils/BinaryWriter.h deleted file mode 100644 index 67c8fcd..0000000 --- a/app/jni/src/libultraship/extern/ZAPDUtils/Utils/BinaryWriter.h +++ /dev/null @@ -1,41 +0,0 @@ -#pragma once - -#include -#include -#include -#include -#include "BitConverter.h" -#include "Stream.h" - -class BinaryWriter -{ -public: - BinaryWriter(Stream* nStream); - BinaryWriter(std::shared_ptr nStream); - - void SetEndianness(Endianness endianness); - - std::shared_ptr GetStream(); - uint64_t GetBaseAddress(); - uint64_t GetLength(); - void Seek(int32_t offset, SeekOffsetType seekType); - void Close(); - - void Write(int8_t value); - void Write(uint8_t value); - void Write(int16_t value); - void Write(uint16_t value); - void Write(int32_t value); - void Write(int32_t valueA, int32_t valueB); - void Write(uint32_t value); - void Write(int64_t value); - void Write(uint64_t value); - void Write(float value); - void Write(double value); - void Write(const std::string& str); - void Write(char* srcBuffer, size_t length); - -protected: - std::shared_ptr stream; - Endianness endianness = Endianness::Native; -}; \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ZAPDUtils/Utils/BitConverter.h b/app/jni/src/libultraship/extern/ZAPDUtils/Utils/BitConverter.h deleted file mode 100644 index 46845fe..0000000 --- a/app/jni/src/libultraship/extern/ZAPDUtils/Utils/BitConverter.h +++ /dev/null @@ -1,209 +0,0 @@ -#pragma once - -#include -#include -#include -#include - -#ifdef _MSC_VER -#define BSWAP16 _byteswap_ushort -#define BSWAP32 _byteswap_ulong -#define BSWAP64 _byteswap_uint64 -#else -#define BSWAP16 __builtin_bswap16 -#define BSWAP32 __builtin_bswap32 -#define BSWAP64 __builtin_bswap64 -#endif - -enum class Endianness -{ - Little = 0, - Big = 1, - -#if (defined(__BYTE_ORDER__) && (__BYTE_ORDER__ == __ORDER_BIG_ENDIAN__)) || defined(__BIG_ENDIAN__) - Native = Big, -#else - Native = Little, -#endif -}; - -class BitConverter -{ -public: - static inline int8_t ToInt8BE(const uint8_t* data, int32_t offset) - { - return (uint8_t)data[offset + 0]; - } - - static inline int8_t ToInt8BE(const std::vector& data, int32_t offset) - { - return (uint8_t)data[offset + 0]; - } - - static inline uint8_t ToUInt8BE(const uint8_t* data, int32_t offset) - { - return (uint8_t)data[offset + 0]; - } - - static inline uint8_t ToUInt8BE(const std::vector& data, int32_t offset) - { - return (uint8_t)data[offset + 0]; - } - - static inline int16_t ToInt16BE(const uint8_t* data, int32_t offset) - { - return ((uint16_t)data[offset + 0] << 8) + (uint16_t)data[offset + 1]; - } - - static inline int16_t ToInt16BE(const std::vector& data, int32_t offset) - { - return ((uint16_t)data[offset + 0] << 8) + (uint16_t)data[offset + 1]; - } - - static inline uint16_t ToUInt16BE(const uint8_t* data, int32_t offset) - { - return ((uint16_t)data[offset + 0] << 8) + (uint16_t)data[offset + 1]; - } - - static inline uint16_t ToUInt16BE(const std::vector& data, int32_t offset) - { - return ((uint16_t)data[offset + 0] << 8) + (uint16_t)data[offset + 1]; - } - - static inline int32_t ToInt32BE(const uint8_t* data, int32_t offset) - { - return ((uint32_t)data[offset + 0] << 24) + ((uint32_t)data[offset + 1] << 16) + - ((uint32_t)data[offset + 2] << 8) + (uint32_t)data[offset + 3]; - } - - static inline int32_t ToInt32BE(const std::vector& data, int32_t offset) - { - return ((uint32_t)data[offset + 0] << 24) + ((uint32_t)data[offset + 1] << 16) + - ((uint32_t)data[offset + 2] << 8) + (uint32_t)data[offset + 3]; - } - - static inline uint32_t ToUInt32BE(const uint8_t* data, int32_t offset) - { - return ((uint32_t)data[offset + 0] << 24) + ((uint32_t)data[offset + 1] << 16) + - ((uint32_t)data[offset + 2] << 8) + (uint32_t)data[offset + 3]; - } - - static inline uint32_t ToUInt32BE(const std::vector& data, int32_t offset) - { - return ((uint32_t)data[offset + 0] << 24) + ((uint32_t)data[offset + 1] << 16) + - ((uint32_t)data[offset + 2] << 8) + (uint32_t)data[offset + 3]; - } - - static inline int64_t ToInt64BE(const uint8_t* data, int32_t offset) - { - return ((uint64_t)data[offset + 0] << 56) + ((uint64_t)data[offset + 1] << 48) + - ((uint64_t)data[offset + 2] << 40) + ((uint64_t)data[offset + 3] << 32) + - ((uint64_t)data[offset + 4] << 24) + ((uint64_t)data[offset + 5] << 16) + - ((uint64_t)data[offset + 6] << 8) + ((uint64_t)data[offset + 7]); - } - - static inline int64_t ToInt64BE(const std::vector& data, int32_t offset) - { - return ((uint64_t)data[offset + 0] << 56) + ((uint64_t)data[offset + 1] << 48) + - ((uint64_t)data[offset + 2] << 40) + ((uint64_t)data[offset + 3] << 32) + - ((uint64_t)data[offset + 4] << 24) + ((uint64_t)data[offset + 5] << 16) + - ((uint64_t)data[offset + 6] << 8) + ((uint64_t)data[offset + 7]); - } - - static inline uint64_t ToUInt64BE(const uint8_t* data, int32_t offset) - { - return ((uint64_t)data[offset + 0] << 56) + ((uint64_t)data[offset + 1] << 48) + - ((uint64_t)data[offset + 2] << 40) + ((uint64_t)data[offset + 3] << 32) + - ((uint64_t)data[offset + 4] << 24) + ((uint64_t)data[offset + 5] << 16) + - ((uint64_t)data[offset + 6] << 8) + ((uint64_t)data[offset + 7]); - } - - static inline uint64_t ToUInt64BE(const std::vector& data, int32_t offset) - { - return ((uint64_t)data[offset + 0] << 56) + ((uint64_t)data[offset + 1] << 48) + - ((uint64_t)data[offset + 2] << 40) + ((uint64_t)data[offset + 3] << 32) + - ((uint64_t)data[offset + 4] << 24) + ((uint64_t)data[offset + 5] << 16) + - ((uint64_t)data[offset + 6] << 8) + ((uint64_t)data[offset + 7]); - } - - static inline float ToFloatBE(const uint8_t* data, int32_t offset) - { - float value; - uint32_t floatData = ((uint32_t)data[offset + 0] << 24) + - ((uint32_t)data[offset + 1] << 16) + - ((uint32_t)data[offset + 2] << 8) + (uint32_t)data[offset + 3]; - static_assert(sizeof(uint32_t) == sizeof(float), "expected 32-bit float"); - std::memcpy(&value, &floatData, sizeof(value)); - return value; - } - - static inline float ToFloatBE(const std::vector& data, int32_t offset) - { - float value; - uint32_t floatData = ((uint32_t)data[offset + 0] << 24) + - ((uint32_t)data[offset + 1] << 16) + - ((uint32_t)data[offset + 2] << 8) + (uint32_t)data[offset + 3]; - static_assert(sizeof(uint32_t) == sizeof(float), "expected 32-bit float"); - std::memcpy(&value, &floatData, sizeof(value)); - return value; - } - - static inline double ToDoubleBE(const uint8_t* data, int32_t offset) - { - double value; - uint64_t floatData = - ((uint64_t)data[offset + 0] << 56) + ((uint64_t)data[offset + 1] << 48) + - ((uint64_t)data[offset + 2] << 40) + ((uint64_t)data[offset + 3] << 32) + - ((uint64_t)data[offset + 4] << 24) + ((uint64_t)data[offset + 5] << 16) + - ((uint64_t)data[offset + 6] << 8) + ((uint64_t)data[offset + 7]); - static_assert(sizeof(uint64_t) == sizeof(double), "expected 64-bit double"); - // Checks if the float format on the platform the ZAPD binary is running on supports the - // same float format as the object file. - static_assert(std::numeric_limits::is_iec559, - "expected IEC559 floats on host machine"); - std::memcpy(&value, &floatData, sizeof(value)); - return value; - } - - static inline double ToDoubleBE(const std::vector& data, int32_t offset) - { - double value; - uint64_t floatData = - ((uint64_t)data[offset + 0] << 56) + ((uint64_t)data[offset + 1] << 48) + - ((uint64_t)data[offset + 2] << 40) + ((uint64_t)data[offset + 3] << 32) + - ((uint64_t)data[offset + 4] << 24) + ((uint64_t)data[offset + 5] << 16) + - ((uint64_t)data[offset + 6] << 8) + ((uint64_t)data[offset + 7]); - static_assert(sizeof(uint64_t) == sizeof(double), "expected 64-bit double"); - // Checks if the float format on the platform the ZAPD binary is running on supports the - // same float format as the object file. - static_assert(std::numeric_limits::is_iec559, - "expected IEC559 doubles on host machine"); - std::memcpy(&value, &floatData, sizeof(value)); - return value; - } - - // Rewrites the rom data in-place to be in BigEndian/z64 format - static inline void RomToBigEndian(uint8_t* rom, size_t romSize) { - if (romSize <= 0) { - return; - } - - // Use the first byte to determine byte order - uint8_t firstByte = rom[0]; - - switch (firstByte) { - case 0x37: // v64 - for (int32_t pos = 0; pos < (romSize / 2); pos++) { - ((uint16_t*)rom)[pos] = ToUInt16BE(rom, pos * 2); - } - break; - case 0x40: // n64 - for (int32_t pos = 0; pos < (romSize / 4); pos++) { - ((uint32_t*)rom)[pos] = ToUInt32BE(rom, pos * 4); - } - break; - case 0x80: // z64 - break; // Already BE, no need to swap - } - } -}; diff --git a/app/jni/src/libultraship/extern/ZAPDUtils/Utils/Directory.h b/app/jni/src/libultraship/extern/ZAPDUtils/Utils/Directory.h deleted file mode 100644 index ea792d8..0000000 --- a/app/jni/src/libultraship/extern/ZAPDUtils/Utils/Directory.h +++ /dev/null @@ -1,60 +0,0 @@ -#pragma once - -#include -#include -#include "StringHelper.h" -#include - -#if __has_include() -#include -namespace fs = std::filesystem; -#else -#include -namespace fs = std::experimental::filesystem; -#endif - -#undef GetCurrentDirectory -#undef CreateDirectory - -class Directory -{ -public: - #ifndef PATH_HACK - static std::string GetCurrentDirectory() { return fs::current_path().string(); } - #endif - - static bool Exists(const fs::path& path) { return fs::exists(path); } - - // Stupid hack because of Windows.h - static void MakeDirectory(const std::string& path) - { - CreateDirectory(path); - } - - static void CreateDirectory(const std::string& path) - { - try - { - fs::create_directories(path); - } - catch (...) - { - } - } - - static std::vector ListFiles(const std::string& dir) - { - std::vector lst; - - if (Exists(dir)) - { - for (auto& p : fs::recursive_directory_iterator(dir)) - { - if (!p.is_directory()) - lst.push_back(p.path().generic_string()); - } - } - - return lst; - } -}; diff --git a/app/jni/src/libultraship/extern/ZAPDUtils/Utils/DiskFile.h b/app/jni/src/libultraship/extern/ZAPDUtils/Utils/DiskFile.h deleted file mode 100644 index 74962a0..0000000 --- a/app/jni/src/libultraship/extern/ZAPDUtils/Utils/DiskFile.h +++ /dev/null @@ -1,87 +0,0 @@ -#pragma once - -#include -#include -#include -#include -#include -#include "Path.h" -#include "Utils/StringHelper.h" -#include "Utils/Directory.h" - - -class DiskFile -{ -public: - static bool Exists(const fs::path& filePath) - { - std::ifstream file(filePath, std::ios::in | std::ios::binary | std::ios::ate); - return file.good(); - } - - static std::vector ReadAllBytes(const fs::path& filePath) - { - std::ifstream file(filePath, std::ios::in | std::ios::binary | std::ios::ate); - - if (!file) - return std::vector(); - - int32_t fileSize = (int32_t)file.tellg(); - file.seekg(0); - char* data = new char[fileSize]; - file.read(data, fileSize); - std::vector result = std::vector(data, data + fileSize); - delete[] data; - - return result; - }; - - static std::string ReadAllText(const fs::path& filePath) - { - std::ifstream file(filePath, std::ios::in | std::ios::binary | std::ios::ate); - int32_t fileSize = (int32_t)file.tellg(); - file.seekg(0); - char* data = new char[fileSize + 1]; - memset(data, 0, fileSize + 1); - file.read(data, fileSize); - std::string str = std::string((const char*)data); - delete[] data; - - return str; - }; - - static std::vector ReadAllLines(const fs::path& filePath) - { - std::string text = ReadAllText(filePath); - std::vector lines = StringHelper::Split(text, "\n"); - - return lines; - }; - - static void WriteAllBytes(const fs::path& filePath, const std::vector& data) - { - std::ofstream file(filePath, std::ios::binary); - file.write((char*)data.data(), data.size()); - }; - - static void WriteAllBytes(const std::string& filePath, const std::vector& data) - { - if (!Directory::Exists(Path::GetDirectoryName(filePath))) - Directory::MakeDirectory(Path::GetDirectoryName(filePath).string()); - - std::ofstream file(filePath, std::ios::binary); - file.write((char*)data.data(), data.size()); - }; - - static void WriteAllBytes(const std::string& filePath, const char* data, int dataSize) - { - std::ofstream file(filePath, std::ios::binary); - file.write((char*)data, dataSize); - }; - - static void WriteAllText(const fs::path& filePath, const std::string& text) - { - std::ofstream file(filePath, std::ios::out); - file.write(text.c_str(), text.size()); - } -}; diff --git a/app/jni/src/libultraship/extern/ZAPDUtils/Utils/MemoryStream.cpp b/app/jni/src/libultraship/extern/ZAPDUtils/Utils/MemoryStream.cpp deleted file mode 100644 index 1c70c00..0000000 --- a/app/jni/src/libultraship/extern/ZAPDUtils/Utils/MemoryStream.cpp +++ /dev/null @@ -1,97 +0,0 @@ -#include "MemoryStream.h" -#include - -#ifndef _MSC_VER -#define memcpy_s(dest, destSize, source, sourceSize) memcpy(dest, source, destSize) -#endif - -MemoryStream::MemoryStream() -{ - buffer = std::vector(); - //buffer.reserve(1024 * 16); - bufferSize = 0; - baseAddress = 0; -} - -MemoryStream::MemoryStream(char* nBuffer, size_t nBufferSize) : MemoryStream() -{ - buffer = std::vector(nBuffer, nBuffer + nBufferSize); - bufferSize = nBufferSize; - baseAddress = 0; -} - -MemoryStream::~MemoryStream() -{ -} - -uint64_t MemoryStream::GetLength() -{ - return buffer.size(); -} - -void MemoryStream::Seek(int32_t offset, SeekOffsetType seekType) -{ - if (seekType == SeekOffsetType::Start) - baseAddress = offset; - else if (seekType == SeekOffsetType::Current) - baseAddress += offset; - else if (seekType == SeekOffsetType::End) - baseAddress = bufferSize - 1 - offset; -} - -std::unique_ptr MemoryStream::Read(size_t length) -{ - std::unique_ptr result = std::make_unique(length); - - memcpy_s(result.get(), length, &buffer[baseAddress], length); - baseAddress += length; - - return result; -} - -void MemoryStream::Read(const char* dest, size_t length) -{ - memcpy_s((void*)dest, length, &buffer[baseAddress], length); - baseAddress += length; -} - -int8_t MemoryStream::ReadByte() -{ - return buffer[baseAddress++]; -} - -void MemoryStream::Write(char* srcBuffer, size_t length) -{ - if (baseAddress + length >= buffer.size()) - { - buffer.resize(baseAddress + length); - bufferSize += length; - } - - memcpy_s(&buffer[baseAddress], length, srcBuffer, length); - baseAddress += length; -} - -void MemoryStream::WriteByte(int8_t value) -{ - if (baseAddress >= buffer.size()) - { - buffer.resize(baseAddress + 1); - bufferSize = baseAddress; - } - - buffer[baseAddress++] = value; -} - -std::vector MemoryStream::ToVector() -{ - return buffer; -} - -void MemoryStream::Flush() -{ -} - -void MemoryStream::Close() -{ -} \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ZAPDUtils/Utils/MemoryStream.h b/app/jni/src/libultraship/extern/ZAPDUtils/Utils/MemoryStream.h deleted file mode 100644 index 5a17bb0..0000000 --- a/app/jni/src/libultraship/extern/ZAPDUtils/Utils/MemoryStream.h +++ /dev/null @@ -1,33 +0,0 @@ -#pragma once - -#include -#include -#include "Stream.h" - -class MemoryStream : public Stream -{ -public: - MemoryStream(); - MemoryStream(char* nBuffer, size_t nBufferSize); - ~MemoryStream(); - - uint64_t GetLength() override; - - void Seek(int32_t offset, SeekOffsetType seekType) override; - - std::unique_ptr Read(size_t length) override; - void Read(const char* dest, size_t length) override; - int8_t ReadByte() override; - - void Write(char* srcBuffer, size_t length) override; - void WriteByte(int8_t value) override; - - std::vector ToVector(); - - void Flush() override; - void Close() override; - -protected: - std::vector buffer; - std::size_t bufferSize; -}; \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ZAPDUtils/Utils/Path.h b/app/jni/src/libultraship/extern/ZAPDUtils/Utils/Path.h deleted file mode 100644 index 0f7ef27..0000000 --- a/app/jni/src/libultraship/extern/ZAPDUtils/Utils/Path.h +++ /dev/null @@ -1,50 +0,0 @@ -#pragma once - -#include -#include -#include "Utils/StringHelper.h" - -#if __has_include() -#include -namespace fs = std::filesystem; -#else -#include -namespace fs = std::experimental::filesystem; -#endif - -class Path -{ -public: - static std::string GetFileName(const fs::path& input) - { - // https://en.cppreference.com/w/cpp/filesystem/path/filename - return input.filename().string(); - }; - - static std::string GetFileNameWithoutExtension(const fs::path& input) - { - // https://en.cppreference.com/w/cpp/filesystem/path/stem - return input.stem().string(); - }; - - static std::string GetFileNameExtension(const std::string& input) - { - return input.substr(input.find_last_of("."), input.length()); - }; - - static fs::path GetPath(const std::string& input) - { - std::vector split = StringHelper::Split(input, "/"); - fs::path output; - - for (std::string str : split) - { - if (str.find_last_of(".") == std::string::npos) - output /= str; - } - - return output; - }; - - static fs::path GetDirectoryName(const fs::path& path) { return path.parent_path(); }; -}; diff --git a/app/jni/src/libultraship/extern/ZAPDUtils/Utils/Stream.h b/app/jni/src/libultraship/extern/ZAPDUtils/Utils/Stream.h deleted file mode 100644 index e72d794..0000000 --- a/app/jni/src/libultraship/extern/ZAPDUtils/Utils/Stream.h +++ /dev/null @@ -1,34 +0,0 @@ -#pragma once - -#include -#include - -enum class SeekOffsetType -{ - Start, - Current, - End -}; - -class Stream -{ -public: - virtual ~Stream() = default; - virtual uint64_t GetLength() = 0; - uint64_t GetBaseAddress() { return baseAddress; } - - virtual void Seek(int32_t offset, SeekOffsetType seekType) = 0; - - virtual std::unique_ptr Read(size_t length) = 0; - virtual void Read(const char* dest, size_t length) = 0; - virtual int8_t ReadByte() = 0; - - virtual void Write(char* destBuffer, size_t length) = 0; - virtual void WriteByte(int8_t value) = 0; - - virtual void Flush() = 0; - virtual void Close() = 0; - -protected: - uint64_t baseAddress; -}; \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ZAPDUtils/Utils/StringHelper.cpp b/app/jni/src/libultraship/extern/ZAPDUtils/Utils/StringHelper.cpp deleted file mode 100644 index c55580e..0000000 --- a/app/jni/src/libultraship/extern/ZAPDUtils/Utils/StringHelper.cpp +++ /dev/null @@ -1,191 +0,0 @@ -#include "StringHelper.h" - -#if (_MSC_VER) -#pragma optimize("2", on) -#define _CRT_SECURE_NO_WARNINGS -#endif - -#ifndef _MSC_VER -#define vsprintf_s vsprintf -#endif - -std::vector StringHelper::Split(std::string s, const std::string& delimiter) -{ - size_t pos_start = 0, pos_end, delim_len = delimiter.length(); - std::string token; - std::vector res; - - while ((pos_end = s.find(delimiter, pos_start)) != std::string::npos) { - token = s.substr(pos_start, pos_end - pos_start); - pos_start = pos_end + delim_len; - res.push_back(token); - } - - res.push_back(s.substr(pos_start)); - return res; -} - -std::vector StringHelper::Split(std::string_view s, const std::string& delimiter) -{ - size_t pos_start = 0, pos_end, delim_len = delimiter.length(); - std::string_view token; - std::vector res; - - while ((pos_end = s.find(delimiter, pos_start)) != std::string_view::npos) - { - token = s.substr(pos_start, pos_end - pos_start); - pos_start = pos_end + delim_len; - res.push_back(token); - } - - res.push_back(s.substr(pos_start)); - return res; -} - -std::string StringHelper::Strip(std::string s, const std::string& delimiter) -{ - size_t pos = 0; - std::string token; - - while ((pos = s.find(delimiter)) != std::string::npos) - { - token = s.substr(0, pos); - s.erase(pos, pos + delimiter.length()); - } - - return s; -} - -std::string StringHelper::Replace(std::string str, const std::string& from, - const std::string& to) -{ - size_t start_pos = str.find(from); - - while (start_pos != std::string::npos) - { - str.replace(start_pos, from.length(), to); - start_pos = str.find(from); - } - - return str; -} - -void StringHelper::ReplaceOriginal(std::string& str, const std::string& from, const std::string& to) -{ - size_t start_pos = str.find(from); - - while (start_pos != std::string::npos) - { - str.replace(start_pos, from.length(), to); - start_pos = str.find(from); - } -} - -bool StringHelper::StartsWith(const std::string& s, const std::string& input) -{ -#if __cplusplus >= 202002L - return s.starts_with(input.c_str()); -#else - return s.rfind(input, 0) == 0; -#endif -} - -bool StringHelper::Contains(const std::string& s, const std::string& input) -{ - return s.find(input) != std::string::npos; -} - -bool StringHelper::EndsWith(const std::string& s, const std::string& input) -{ - size_t inputLen = strlen(input.c_str()); - return s.rfind(input) == (s.size() - inputLen); -} - -std::string StringHelper::Sprintf(const char* format, ...) -{ - char buffer[32768]; - // char buffer[2048]; - std::string output; - va_list va; - - va_start(va, format); - vsprintf_s(buffer, format, va); - va_end(va); - - output = buffer; - return output; -} - -std::string StringHelper::Implode(std::vector& elements, - const char* const separator) -{ - return ""; - - // return std::accumulate(std::begin(elements), std::end(elements), std::string(), - //[separator](std::string& ss, std::string& s) { - // return ss.empty() ? s : ss + separator + s; - //}); -} - -int64_t StringHelper::StrToL(const std::string& str, int32_t base) -{ - return std::strtoull(str.c_str(), nullptr, base); -} - -std::string StringHelper::BoolStr(bool b) -{ - return b ? "true" : "false"; -} - -bool StringHelper::HasOnlyDigits(const std::string& str) -{ - return std::all_of(str.begin(), str.end(), ::isdigit); -} - -// Validate a hex string based on the c89 standard -// https://www.gnu.org/software/gnu-c-manual/gnu-c-manual.html#Integer-Constants -bool StringHelper::IsValidHex(std::string_view str) -{ - if (str.length() < 3) - { - return false; - } - if (str[0] == '0' && (str[1] == 'x' || str[1] == 'X')) - { - return std::all_of(str.begin() + 2, str.end(), ::isxdigit); - } - return false; -} - - -bool StringHelper::IsValidHex(const std::string& str) -{ - return IsValidHex(std::string_view(str.c_str())); -} - -bool StringHelper::IsValidOffset(std::string_view str) -{ - if (str.length() == 1) - { - // 0 is a valid offset - return isdigit(str[0]); - } - return IsValidHex(str); -} - -bool StringHelper::IsValidOffset(const std::string& str) -{ - if (str.length() == 1) - { - // 0 is a valid offset - return isdigit(str[0]); - } - return IsValidHex(str); -} - - -bool StringHelper::IEquals(const std::string& a, const std::string& b) -{ - return std::equal(a.begin(), a.end(), b.begin(), b.end(), - [](char a, char b) { return tolower(a) == tolower(b); }); -} diff --git a/app/jni/src/libultraship/extern/ZAPDUtils/Utils/StringHelper.h b/app/jni/src/libultraship/extern/ZAPDUtils/Utils/StringHelper.h deleted file mode 100644 index 0fc58d3..0000000 --- a/app/jni/src/libultraship/extern/ZAPDUtils/Utils/StringHelper.h +++ /dev/null @@ -1,33 +0,0 @@ -#pragma once - -#include -#include -#include -#include -#include -#include -#include -#include - -class StringHelper -{ -public: - static std::vector Split(std::string s, const std::string& delimiter); - static std::vector Split(std::string_view s, const std::string& delimiter); - static std::string Strip(std::string s, const std::string& delimiter); - static std::string Replace(std::string str, const std::string& from, const std::string& to); - static void ReplaceOriginal(std::string& str, const std::string& from, const std::string& to); - static bool StartsWith(const std::string& s, const std::string& input); - static bool Contains(const std::string& s, const std::string& input); - static bool EndsWith(const std::string& s, const std::string& input); - static std::string Sprintf(const char* format, ...); - static std::string Implode(std::vector& elements, const char* const separator); - static int64_t StrToL(const std::string& str, int32_t base = 10); - static std::string BoolStr(bool b); - static bool HasOnlyDigits(const std::string& str); - static bool IsValidHex(std::string_view str); - static bool IsValidHex(const std::string& str); - static bool IsValidOffset(std::string_view str); - static bool IsValidOffset(const std::string& str); - static bool IEquals(const std::string& a, const std::string& b); -}; \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ZAPDUtils/Utils/vt.h b/app/jni/src/libultraship/extern/ZAPDUtils/Utils/vt.h deleted file mode 100644 index 23f4244..0000000 --- a/app/jni/src/libultraship/extern/ZAPDUtils/Utils/vt.h +++ /dev/null @@ -1,45 +0,0 @@ -#ifndef VT_H -#define VT_H - -// clang-format off -#define VT_COLOR_BLACK 0 -#define VT_COLOR_RED 1 -#define VT_COLOR_GREEN 2 -#define VT_COLOR_YELLOW 3 -#define VT_COLOR_BLUE 4 -#define VT_COLOR_PURPLE 5 -#define VT_COLOR_CYAN 6 -#define VT_COLOR_WHITE 7 -#define VT_COLOR_LIGHTGRAY 8 -#define VT_COLOR_DARKGRAY 9 - -#define VT_COLOR_FOREGROUND 3 -#define VT_COLOR_BACKGROUND 4 -// clang-format on - -#define VT_COLOR_EXPAND0(type, color) #type #color -#define VT_COLOR_EXPAND1(type, color) VT_COLOR_EXPAND0(type, color) -#define VT_COLOR(type, color) VT_COLOR_EXPAND1(VT_COLOR_##type, VT_COLOR_##color) - -#define VT_ESC "\x1b" -#define VT_CSI "[" -#define VT_CUP(x, y) VT_ESC VT_CSI y ";" x "H" -#define VT_ED(n) VT_ESC VT_CSI #n "J" -#define VT_SGR(n) VT_ESC VT_CSI n "m" - -// Add more macros if necessary -#define VT_COL(back, fore) VT_SGR(VT_COLOR(BACKGROUND, back) ";" VT_COLOR(FOREGROUND, fore)) -#define VT_FGCOL(color) VT_SGR(VT_COLOR(FOREGROUND, color)) -#define VT_BGCOL(color) VT_SGR(VT_COLOR(BACKGROUND, color)) - -// Bold -#define VT_BOLD "1" - -// Bold color support -#define VT_BOLD_FGCOL(color) VT_SGR(VT_BOLD ";" VT_COLOR(FOREGROUND, color)) -#define VT_BOLD_BGCOL(color) VT_SGR(VT_BOLD ";" VT_COLOR(BACKGROUND, color)) - -#define VT_RST VT_SGR("") -#define VT_CLS VT_ED(2) - -#endif diff --git a/app/jni/src/libultraship/extern/ZAPDUtils/Vec2f.h b/app/jni/src/libultraship/extern/ZAPDUtils/Vec2f.h deleted file mode 100644 index f157eab..0000000 --- a/app/jni/src/libultraship/extern/ZAPDUtils/Vec2f.h +++ /dev/null @@ -1,19 +0,0 @@ -#pragma once - -#include - -namespace ZAPDUtils { - -struct Vec2f { - float x, y; - - Vec2f() { - x = 0; - y = 0; - }; - Vec2f(float nX, float nY) { - x = nX; - y = nY; - }; -}; -} // namespace ZAPDUtils \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ZAPDUtils/Vec3f.h b/app/jni/src/libultraship/extern/ZAPDUtils/Vec3f.h deleted file mode 100644 index 104676a..0000000 --- a/app/jni/src/libultraship/extern/ZAPDUtils/Vec3f.h +++ /dev/null @@ -1,19 +0,0 @@ -#pragma once - -namespace ZAPDUtils { - -struct Vec3f { - float x, y, z; - - Vec3f() { - x = 0; - y = 0; - z = 0; - }; - Vec3f(float nX, float nY, float nZ) { - x = nX; - y = nY; - z = nZ; - }; -}; -} // namespace ZAPDUtils \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ZAPDUtils/Vec3s.h b/app/jni/src/libultraship/extern/ZAPDUtils/Vec3s.h deleted file mode 100644 index 358602c..0000000 --- a/app/jni/src/libultraship/extern/ZAPDUtils/Vec3s.h +++ /dev/null @@ -1,21 +0,0 @@ -#pragma once - -#include - -namespace ZAPDUtils { - -struct Vec3s { - int16_t x, y, z; - - Vec3s() { - x = 0; - y = 0; - z = 0; - }; - Vec3s(int16_t nX, int16_t nY, int16_t nZ) { - x = nX; - y = nY; - z = nZ; - }; -}; -} // namespace ZAPDUtils \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ZAPDUtils/ZAPDUtils.vcxproj b/app/jni/src/libultraship/extern/ZAPDUtils/ZAPDUtils.vcxproj deleted file mode 100644 index 23ae268..0000000 --- a/app/jni/src/libultraship/extern/ZAPDUtils/ZAPDUtils.vcxproj +++ /dev/null @@ -1,192 +0,0 @@ - - - - - Debug - Win32 - - - Release - Win32 - - - Debug - x64 - - - Release - x64 - - - - 16.0 - Win32Proj - {a2e01c3e-d647-45d1-9788-043debc1a908} - ZAPDUtils - 10.0 - - - - StaticLibrary - false - v142 - Unicode - - - StaticLibrary - false - v142 - true - Unicode - - - StaticLibrary - false - v142 - MultiByte - - - StaticLibrary - false - v142 - true - Unicode - - - - - - - - - - - - - - - - - - - - - true - MinimumRecommendedRules.ruleset - - - - - false - MinimumRecommendedRules.ruleset - - - - - true - MinimumRecommendedRules.ruleset - - - - - false - MinimumRecommendedRules.ruleset - - - - - - Level3 - true - WIN32;_DEBUG;_CONSOLE;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions) - true - MultiThreaded - true - MaxSpeed - Speed - Default - true - - - Console - true - - - - - Level3 - true - true - true - WIN32;NDEBUG;_CONSOLE;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions) - true - MultiThreaded - true - - - Console - true - true - true - - - - - Level3 - true - _DEBUG;_CONSOLE;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions) - true - MultiThreaded - Default - true - - - Console - true - - - - - Level3 - true - true - true - NDEBUG;_CONSOLE;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions) - true - MultiThreaded - true - - - Console - true - true - true - - - - - - - - - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/ZAPDUtils/ZAPDUtils.vcxproj.filters b/app/jni/src/libultraship/extern/ZAPDUtils/ZAPDUtils.vcxproj.filters deleted file mode 100644 index 3c46d19..0000000 --- a/app/jni/src/libultraship/extern/ZAPDUtils/ZAPDUtils.vcxproj.filters +++ /dev/null @@ -1,87 +0,0 @@ - - - - - {93995380-89BD-4b04-88EB-625FBE52EBFB} - h;hh;hpp;hxx;h++;hm;inl;inc;ipp;xsd - - - {67DA6AB6-F800-4c08-8B7A-83BB121AAD01} - rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms - - - {d8c2c1e7-b065-4b0f-86a2-46ab46eedc0b} - - - {4FC737F1-C7A5-4376-A066-2A32D752A2FF} - cpp;c;cc;cxx;c++;cppm;ixx;def;odl;idl;hpj;bat;asm;asmx - - - {e047919d-7186-49ca-b115-e48fbb5c8743} - - - {3de9dd46-0dfd-4d48-9f20-9f24e5b80fe0} - - - - - Header Files\Utils - - - Header Files\Utils - - - Header Files\Utils - - - Header Files\Utils - - - Header Files\Utils - - - Header Files\Utils - - - Header Files\Utils - - - Header Files\Utils - - - Header Files - - - Header Files\Utils - - - Header Files - - - Header Files - - - Header Files - - - Header Files - - - - - Source Files\Utils - - - Source Files\Utils - - - Source Files\Utils - - - Source Files\Libraries - - - Source Files\Utils - - - \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/dr_libs/mp3.h b/app/jni/src/libultraship/extern/dr_libs/mp3.h deleted file mode 100644 index 3319132..0000000 --- a/app/jni/src/libultraship/extern/dr_libs/mp3.h +++ /dev/null @@ -1,4826 +0,0 @@ -/* -MP3 audio decoder. Choice of public domain or MIT-0. See license statements at the end of this file. -dr_mp3 - v0.6.33 - 2022-04-10 - -David Reid - mackron@gmail.com - -GitHub: https://github.com/mackron/dr_libs - -Based on minimp3 (https://github.com/lieff/minimp3) which is where the real work was done. See the bottom of this file for differences between minimp3 and dr_mp3. -*/ - -/* -RELEASE NOTES - VERSION 0.6 -=========================== -Version 0.6 includes breaking changes with the configuration of decoders. The ability to customize the number of output channels and the sample rate has been -removed. You must now use the channel count and sample rate reported by the MP3 stream itself, and all channel and sample rate conversion must be done -yourself. - - -Changes to Initialization -------------------------- -Previously, `drmp3_init()`, etc. took a pointer to a `drmp3_config` object that allowed you to customize the output channels and sample rate. This has been -removed. If you need the old behaviour you will need to convert the data yourself or just not upgrade. The following APIs have changed. - - `drmp3_init()` - `drmp3_init_memory()` - `drmp3_init_file()` - - -Miscellaneous Changes ---------------------- -Support for loading a file from a `wchar_t` string has been added via the `drmp3_init_file_w()` API. -*/ - -/* -Introducation -============= -dr_mp3 is a single file library. To use it, do something like the following in one .c file. - - ```c - #define DR_MP3_IMPLEMENTATION - #include "dr_mp3.h" - ``` - -You can then #include this file in other parts of the program as you would with any other header file. To decode audio data, do something like the following: - - ```c - drmp3 mp3; - if (!drmp3_init_file(&mp3, "MySong.mp3", NULL)) { - // Failed to open file - } - - ... - - drmp3_uint64 framesRead = drmp3_read_pcm_frames_f32(pMP3, framesToRead, pFrames); - ``` - -The drmp3 object is transparent so you can get access to the channel count and sample rate like so: - - ``` - drmp3_uint32 channels = mp3.channels; - drmp3_uint32 sampleRate = mp3.sampleRate; - ``` - -The example above initializes a decoder from a file, but you can also initialize it from a block of memory and read and seek callbacks with -`drmp3_init_memory()` and `drmp3_init()` respectively. - -You do not need to do any annoying memory management when reading PCM frames - this is all managed internally. You can request any number of PCM frames in each -call to `drmp3_read_pcm_frames_f32()` and it will return as many PCM frames as it can, up to the requested amount. - -You can also decode an entire file in one go with `drmp3_open_and_read_pcm_frames_f32()`, `drmp3_open_memory_and_read_pcm_frames_f32()` and -`drmp3_open_file_and_read_pcm_frames_f32()`. - - -Build Options -============= -#define these options before including this file. - -#define DR_MP3_NO_STDIO - Disable drmp3_init_file(), etc. - -#define DR_MP3_NO_SIMD - Disable SIMD optimizations. -*/ - -#ifndef dr_mp3_h -#define dr_mp3_h - -#ifdef __cplusplus -extern "C" { -#endif - -#define DRMP3_STRINGIFY(x) #x -#define DRMP3_XSTRINGIFY(x) DRMP3_STRINGIFY(x) - -#define DRMP3_VERSION_MAJOR 0 -#define DRMP3_VERSION_MINOR 6 -#define DRMP3_VERSION_REVISION 33 -#define DRMP3_VERSION_STRING DRMP3_XSTRINGIFY(DRMP3_VERSION_MAJOR) "." DRMP3_XSTRINGIFY(DRMP3_VERSION_MINOR) "." DRMP3_XSTRINGIFY(DRMP3_VERSION_REVISION) - -#include /* For size_t. */ - - /* Sized types. */ - typedef signed char drmp3_int8; - typedef unsigned char drmp3_uint8; - typedef signed short drmp3_int16; - typedef unsigned short drmp3_uint16; - typedef signed int drmp3_int32; - typedef unsigned int drmp3_uint32; -#if defined(_MSC_VER) && !defined(__clang__) - typedef signed __int64 drmp3_int64; - typedef unsigned __int64 drmp3_uint64; -#else -#if defined(__clang__) || (defined(__GNUC__) && (__GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 6))) -#pragma GCC diagnostic push -#pragma GCC diagnostic ignored "-Wlong-long" -#if defined(__clang__) -#pragma GCC diagnostic ignored "-Wc++11-long-long" -#endif -#endif - typedef signed long long drmp3_int64; - typedef unsigned long long drmp3_uint64; -#if defined(__clang__) || (defined(__GNUC__) && (__GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 6))) -#pragma GCC diagnostic pop -#endif -#endif -#if defined(__LP64__) || defined(_WIN64) || (defined(__x86_64__) && !defined(__ILP32__)) || defined(_M_X64) || defined(__ia64) || defined (_M_IA64) || defined(__aarch64__) || defined(_M_ARM64) || defined(__powerpc64__) - typedef drmp3_uint64 drmp3_uintptr; -#else - typedef drmp3_uint32 drmp3_uintptr; -#endif - typedef drmp3_uint8 drmp3_bool8; - typedef drmp3_uint32 drmp3_bool32; -#define DRMP3_TRUE 1 -#define DRMP3_FALSE 0 - -#if !defined(DRMP3_API) -#if defined(DRMP3_DLL) -#if defined(_WIN32) -#define DRMP3_DLL_IMPORT __declspec(dllimport) -#define DRMP3_DLL_EXPORT __declspec(dllexport) -#define DRMP3_DLL_PRIVATE static -#else -#if defined(__GNUC__) && __GNUC__ >= 4 -#define DRMP3_DLL_IMPORT __attribute__((visibility("default"))) -#define DRMP3_DLL_EXPORT __attribute__((visibility("default"))) -#define DRMP3_DLL_PRIVATE __attribute__((visibility("hidden"))) -#else -#define DRMP3_DLL_IMPORT -#define DRMP3_DLL_EXPORT -#define DRMP3_DLL_PRIVATE static -#endif -#endif - -#if defined(DR_MP3_IMPLEMENTATION) || defined(DRMP3_IMPLEMENTATION) -#define DRMP3_API DRMP3_DLL_EXPORT -#else -#define DRMP3_API DRMP3_DLL_IMPORT -#endif -#define DRMP3_PRIVATE DRMP3_DLL_PRIVATE -#else -#define DRMP3_API extern -#define DRMP3_PRIVATE static -#endif -#endif - - typedef drmp3_int32 drmp3_result; -#define DRMP3_SUCCESS 0 -#define DRMP3_ERROR -1 /* A generic error. */ -#define DRMP3_INVALID_ARGS -2 -#define DRMP3_INVALID_OPERATION -3 -#define DRMP3_OUT_OF_MEMORY -4 -#define DRMP3_OUT_OF_RANGE -5 -#define DRMP3_ACCESS_DENIED -6 -#define DRMP3_DOES_NOT_EXIST -7 -#define DRMP3_ALREADY_EXISTS -8 -#define DRMP3_TOO_MANY_OPEN_FILES -9 -#define DRMP3_INVALID_FILE -10 -#define DRMP3_TOO_BIG -11 -#define DRMP3_PATH_TOO_LONG -12 -#define DRMP3_NAME_TOO_LONG -13 -#define DRMP3_NOT_DIRECTORY -14 -#define DRMP3_IS_DIRECTORY -15 -#define DRMP3_DIRECTORY_NOT_EMPTY -16 -#define DRMP3_END_OF_FILE -17 -#define DRMP3_NO_SPACE -18 -#define DRMP3_BUSY -19 -#define DRMP3_IO_ERROR -20 -#define DRMP3_INTERRUPT -21 -#define DRMP3_UNAVAILABLE -22 -#define DRMP3_ALREADY_IN_USE -23 -#define DRMP3_BAD_ADDRESS -24 -#define DRMP3_BAD_SEEK -25 -#define DRMP3_BAD_PIPE -26 -#define DRMP3_DEADLOCK -27 -#define DRMP3_TOO_MANY_LINKS -28 -#define DRMP3_NOT_IMPLEMENTED -29 -#define DRMP3_NO_MESSAGE -30 -#define DRMP3_BAD_MESSAGE -31 -#define DRMP3_NO_DATA_AVAILABLE -32 -#define DRMP3_INVALID_DATA -33 -#define DRMP3_TIMEOUT -34 -#define DRMP3_NO_NETWORK -35 -#define DRMP3_NOT_UNIQUE -36 -#define DRMP3_NOT_SOCKET -37 -#define DRMP3_NO_ADDRESS -38 -#define DRMP3_BAD_PROTOCOL -39 -#define DRMP3_PROTOCOL_UNAVAILABLE -40 -#define DRMP3_PROTOCOL_NOT_SUPPORTED -41 -#define DRMP3_PROTOCOL_FAMILY_NOT_SUPPORTED -42 -#define DRMP3_ADDRESS_FAMILY_NOT_SUPPORTED -43 -#define DRMP3_SOCKET_NOT_SUPPORTED -44 -#define DRMP3_CONNECTION_RESET -45 -#define DRMP3_ALREADY_CONNECTED -46 -#define DRMP3_NOT_CONNECTED -47 -#define DRMP3_CONNECTION_REFUSED -48 -#define DRMP3_NO_HOST -49 -#define DRMP3_IN_PROGRESS -50 -#define DRMP3_CANCELLED -51 -#define DRMP3_MEMORY_ALREADY_MAPPED -52 -#define DRMP3_AT_END -53 - - -#define DRMP3_MAX_PCM_FRAMES_PER_MP3_FRAME 1152 -#define DRMP3_MAX_SAMPLES_PER_FRAME (DRMP3_MAX_PCM_FRAMES_PER_MP3_FRAME*2) - -#ifdef _MSC_VER -#define DRMP3_INLINE __forceinline -#elif defined(__GNUC__) - /* - I've had a bug report where GCC is emitting warnings about functions possibly not being inlineable. This warning happens when - the __attribute__((always_inline)) attribute is defined without an "inline" statement. I think therefore there must be some - case where "__inline__" is not always defined, thus the compiler emitting these warnings. When using -std=c89 or -ansi on the - command line, we cannot use the "inline" keyword and instead need to use "__inline__". In an attempt to work around this issue - I am using "__inline__" only when we're compiling in strict ANSI mode. - */ -#if defined(__STRICT_ANSI__) -#define DRMP3_GNUC_INLINE_HINT __inline__ -#else -#define DRMP3_GNUC_INLINE_HINT inline -#endif - -#if (__GNUC__ > 3 || (__GNUC__ == 3 && __GNUC_MINOR__ >= 2)) || defined(__clang__) -#define DRMP3_INLINE DRMP3_GNUC_INLINE_HINT __attribute__((always_inline)) -#else -#define DRMP3_INLINE DRMP3_GNUC_INLINE_HINT -#endif -#elif defined(__WATCOMC__) -#define DRMP3_INLINE __inline -#else -#define DRMP3_INLINE -#endif - - - DRMP3_API void drmp3_version(drmp3_uint32* pMajor, drmp3_uint32* pMinor, drmp3_uint32* pRevision); - DRMP3_API const char* drmp3_version_string(void); - - - /* - Low Level Push API - ================== - */ - typedef struct - { - int frame_bytes, channels, hz, layer, bitrate_kbps; - } drmp3dec_frame_info; - - typedef struct - { - float mdct_overlap[2][9 * 32], qmf_state[15 * 2 * 32]; - int reserv, free_format_bytes; - drmp3_uint8 header[4], reserv_buf[511]; - } drmp3dec; - - /* Initializes a low level decoder. */ - DRMP3_API void drmp3dec_init(drmp3dec* dec); - - /* Reads a frame from a low level decoder. */ - DRMP3_API int drmp3dec_decode_frame(drmp3dec* dec, const drmp3_uint8* mp3, int mp3_bytes, void* pcm, drmp3dec_frame_info* info); - - /* Helper for converting between f32 and s16. */ - DRMP3_API void drmp3dec_f32_to_s16(const float* in, drmp3_int16* out, size_t num_samples); - - - - /* - Main API (Pull API) - =================== - */ - typedef enum - { - drmp3_seek_origin_start, - drmp3_seek_origin_current - } drmp3_seek_origin; - - typedef struct - { - drmp3_uint64 seekPosInBytes; /* Points to the first byte of an MP3 frame. */ - drmp3_uint64 pcmFrameIndex; /* The index of the PCM frame this seek point targets. */ - drmp3_uint16 mp3FramesToDiscard; /* The number of whole MP3 frames to be discarded before pcmFramesToDiscard. */ - drmp3_uint16 pcmFramesToDiscard; /* The number of leading samples to read and discard. These are discarded after mp3FramesToDiscard. */ - } drmp3_seek_point; - - /* - Callback for when data is read. Return value is the number of bytes actually read. - - pUserData [in] The user data that was passed to drmp3_init(), drmp3_open() and family. - pBufferOut [out] The output buffer. - bytesToRead [in] The number of bytes to read. - - Returns the number of bytes actually read. - - A return value of less than bytesToRead indicates the end of the stream. Do _not_ return from this callback until - either the entire bytesToRead is filled or you have reached the end of the stream. - */ - typedef size_t(*drmp3_read_proc)(void* pUserData, void* pBufferOut, size_t bytesToRead); - - /* - Callback for when data needs to be seeked. - - pUserData [in] The user data that was passed to drmp3_init(), drmp3_open() and family. - offset [in] The number of bytes to move, relative to the origin. Will never be negative. - origin [in] The origin of the seek - the current position or the start of the stream. - - Returns whether or not the seek was successful. - - Whether or not it is relative to the beginning or current position is determined by the "origin" parameter which - will be either drmp3_seek_origin_start or drmp3_seek_origin_current. - */ - typedef drmp3_bool32(*drmp3_seek_proc)(void* pUserData, int offset, drmp3_seek_origin origin); - - typedef struct - { - void* pUserData; - void* (*onMalloc)(size_t sz, void* pUserData); - void* (*onRealloc)(void* p, size_t sz, void* pUserData); - void (*onFree)(void* p, void* pUserData); - } drmp3_allocation_callbacks; - - typedef struct - { - drmp3_uint32 channels; - drmp3_uint32 sampleRate; - } drmp3_config; - - typedef struct - { - drmp3dec decoder; - drmp3dec_frame_info frameInfo; - drmp3_uint32 channels; - drmp3_uint32 sampleRate; - drmp3_read_proc onRead; - drmp3_seek_proc onSeek; - void* pUserData; - drmp3_allocation_callbacks allocationCallbacks; - drmp3_uint32 mp3FrameChannels; /* The number of channels in the currently loaded MP3 frame. Internal use only. */ - drmp3_uint32 mp3FrameSampleRate; /* The sample rate of the currently loaded MP3 frame. Internal use only. */ - drmp3_uint32 pcmFramesConsumedInMP3Frame; - drmp3_uint32 pcmFramesRemainingInMP3Frame; - drmp3_uint8 pcmFrames[sizeof(float) * DRMP3_MAX_SAMPLES_PER_FRAME]; /* <-- Multipled by sizeof(float) to ensure there's enough room for DR_MP3_FLOAT_OUTPUT. */ - drmp3_uint64 currentPCMFrame; /* The current PCM frame, globally, based on the output sample rate. Mainly used for seeking. */ - drmp3_uint64 streamCursor; /* The current byte the decoder is sitting on in the raw stream. */ - drmp3_seek_point* pSeekPoints; /* NULL by default. Set with drmp3_bind_seek_table(). Memory is owned by the client. dr_mp3 will never attempt to free this pointer. */ - drmp3_uint32 seekPointCount; /* The number of items in pSeekPoints. When set to 0 assumes to no seek table. Defaults to zero. */ - size_t dataSize; - size_t dataCapacity; - size_t dataConsumed; - drmp3_uint8* pData; - drmp3_bool32 atEnd : 1; - struct - { - const drmp3_uint8* pData; - size_t dataSize; - size_t currentReadPos; - } memory; /* Only used for decoders that were opened against a block of memory. */ - } drmp3; - - /* - Initializes an MP3 decoder. - - onRead [in] The function to call when data needs to be read from the client. - onSeek [in] The function to call when the read position of the client data needs to move. - pUserData [in, optional] A pointer to application defined data that will be passed to onRead and onSeek. - - Returns true if successful; false otherwise. - - Close the loader with drmp3_uninit(). - - See also: drmp3_init_file(), drmp3_init_memory(), drmp3_uninit() - */ - DRMP3_API drmp3_bool32 drmp3_init(drmp3* pMP3, drmp3_read_proc onRead, drmp3_seek_proc onSeek, void* pUserData, const drmp3_allocation_callbacks* pAllocationCallbacks); - - /* - Initializes an MP3 decoder from a block of memory. - - This does not create a copy of the data. It is up to the application to ensure the buffer remains valid for - the lifetime of the drmp3 object. - - The buffer should contain the contents of the entire MP3 file. - */ - DRMP3_API drmp3_bool32 drmp3_init_memory(drmp3* pMP3, const void* pData, size_t dataSize, const drmp3_allocation_callbacks* pAllocationCallbacks); - -#ifndef DR_MP3_NO_STDIO - /* - Initializes an MP3 decoder from a file. - - This holds the internal FILE object until drmp3_uninit() is called. Keep this in mind if you're caching drmp3 - objects because the operating system may restrict the number of file handles an application can have open at - any given time. - */ - DRMP3_API drmp3_bool32 drmp3_init_file(drmp3* pMP3, const char* pFilePath, const drmp3_allocation_callbacks* pAllocationCallbacks); - DRMP3_API drmp3_bool32 drmp3_init_file_w(drmp3* pMP3, const wchar_t* pFilePath, const drmp3_allocation_callbacks* pAllocationCallbacks); -#endif - - /* - Uninitializes an MP3 decoder. - */ - DRMP3_API void drmp3_uninit(drmp3* pMP3); - - /* - Reads PCM frames as interleaved 32-bit IEEE floating point PCM. - - Note that framesToRead specifies the number of PCM frames to read, _not_ the number of MP3 frames. - */ - DRMP3_API drmp3_uint64 drmp3_read_pcm_frames_f32(drmp3* pMP3, drmp3_uint64 framesToRead, float* pBufferOut); - - /* - Reads PCM frames as interleaved signed 16-bit integer PCM. - - Note that framesToRead specifies the number of PCM frames to read, _not_ the number of MP3 frames. - */ - DRMP3_API drmp3_uint64 drmp3_read_pcm_frames_s16(drmp3* pMP3, drmp3_uint64 framesToRead, drmp3_int16* pBufferOut); - - /* - Seeks to a specific frame. - - Note that this is _not_ an MP3 frame, but rather a PCM frame. - */ - DRMP3_API drmp3_bool32 drmp3_seek_to_pcm_frame(drmp3* pMP3, drmp3_uint64 frameIndex); - - /* - Calculates the total number of PCM frames in the MP3 stream. Cannot be used for infinite streams such as internet - radio. Runs in linear time. Returns 0 on error. - */ - DRMP3_API drmp3_uint64 drmp3_get_pcm_frame_count(drmp3* pMP3); - - /* - Calculates the total number of MP3 frames in the MP3 stream. Cannot be used for infinite streams such as internet - radio. Runs in linear time. Returns 0 on error. - */ - DRMP3_API drmp3_uint64 drmp3_get_mp3_frame_count(drmp3* pMP3); - - /* - Calculates the total number of MP3 and PCM frames in the MP3 stream. Cannot be used for infinite streams such as internet - radio. Runs in linear time. Returns 0 on error. - - This is equivalent to calling drmp3_get_mp3_frame_count() and drmp3_get_pcm_frame_count() except that it's more efficient. - */ - DRMP3_API drmp3_bool32 drmp3_get_mp3_and_pcm_frame_count(drmp3* pMP3, drmp3_uint64* pMP3FrameCount, drmp3_uint64* pPCMFrameCount); - - /* - Calculates the seekpoints based on PCM frames. This is slow. - - pSeekpoint count is a pointer to a uint32 containing the seekpoint count. On input it contains the desired count. - On output it contains the actual count. The reason for this design is that the client may request too many - seekpoints, in which case dr_mp3 will return a corrected count. - - Note that seektable seeking is not quite sample exact when the MP3 stream contains inconsistent sample rates. - */ - DRMP3_API drmp3_bool32 drmp3_calculate_seek_points(drmp3* pMP3, drmp3_uint32* pSeekPointCount, drmp3_seek_point* pSeekPoints); - - /* - Binds a seek table to the decoder. - - This does _not_ make a copy of pSeekPoints - it only references it. It is up to the application to ensure this - remains valid while it is bound to the decoder. - - Use drmp3_calculate_seek_points() to calculate the seek points. - */ - DRMP3_API drmp3_bool32 drmp3_bind_seek_table(drmp3* pMP3, drmp3_uint32 seekPointCount, drmp3_seek_point* pSeekPoints); - - - /* - Opens an decodes an entire MP3 stream as a single operation. - - On output pConfig will receive the channel count and sample rate of the stream. - - Free the returned pointer with drmp3_free(). - */ - DRMP3_API float* drmp3_open_and_read_pcm_frames_f32(drmp3_read_proc onRead, drmp3_seek_proc onSeek, void* pUserData, drmp3_config* pConfig, drmp3_uint64* pTotalFrameCount, const drmp3_allocation_callbacks* pAllocationCallbacks); - DRMP3_API drmp3_int16* drmp3_open_and_read_pcm_frames_s16(drmp3_read_proc onRead, drmp3_seek_proc onSeek, void* pUserData, drmp3_config* pConfig, drmp3_uint64* pTotalFrameCount, const drmp3_allocation_callbacks* pAllocationCallbacks); - - DRMP3_API float* drmp3_open_memory_and_read_pcm_frames_f32(const void* pData, size_t dataSize, drmp3_config* pConfig, drmp3_uint64* pTotalFrameCount, const drmp3_allocation_callbacks* pAllocationCallbacks); - DRMP3_API drmp3_int16* drmp3_open_memory_and_read_pcm_frames_s16(const void* pData, size_t dataSize, drmp3_config* pConfig, drmp3_uint64* pTotalFrameCount, const drmp3_allocation_callbacks* pAllocationCallbacks); - -#ifndef DR_MP3_NO_STDIO - DRMP3_API float* drmp3_open_file_and_read_pcm_frames_f32(const char* filePath, drmp3_config* pConfig, drmp3_uint64* pTotalFrameCount, const drmp3_allocation_callbacks* pAllocationCallbacks); - DRMP3_API drmp3_int16* drmp3_open_file_and_read_pcm_frames_s16(const char* filePath, drmp3_config* pConfig, drmp3_uint64* pTotalFrameCount, const drmp3_allocation_callbacks* pAllocationCallbacks); -#endif - - /* - Allocates a block of memory on the heap. - */ - DRMP3_API void* drmp3_malloc(size_t sz, const drmp3_allocation_callbacks* pAllocationCallbacks); - - /* - Frees any memory that was allocated by a public drmp3 API. - */ - DRMP3_API void drmp3_free(void* p, const drmp3_allocation_callbacks* pAllocationCallbacks); - -#ifdef __cplusplus -} -#endif -#endif /* dr_mp3_h */ - - -/************************************************************************************************************************************************************ - ************************************************************************************************************************************************************ - - IMPLEMENTATION - - ************************************************************************************************************************************************************ - ************************************************************************************************************************************************************/ -#if defined(DR_MP3_IMPLEMENTATION) || defined(DRMP3_IMPLEMENTATION) -#ifndef dr_mp3_c -#define dr_mp3_c - -#include -#include -#include /* For INT_MAX */ - -DRMP3_API void drmp3_version(drmp3_uint32* pMajor, drmp3_uint32* pMinor, drmp3_uint32* pRevision) -{ - if (pMajor) { - *pMajor = DRMP3_VERSION_MAJOR; - } - - if (pMinor) { - *pMinor = DRMP3_VERSION_MINOR; - } - - if (pRevision) { - *pRevision = DRMP3_VERSION_REVISION; - } -} - -DRMP3_API const char* drmp3_version_string(void) -{ - return DRMP3_VERSION_STRING; -} - -/* Disable SIMD when compiling with TCC for now. */ -#if defined(__TINYC__) -#define DR_MP3_NO_SIMD -#endif - -#define DRMP3_OFFSET_PTR(p, offset) ((void*)((drmp3_uint8*)(p) + (offset))) - -#define DRMP3_MAX_FREE_FORMAT_FRAME_SIZE 2304 /* more than ISO spec's */ -#ifndef DRMP3_MAX_FRAME_SYNC_MATCHES -#define DRMP3_MAX_FRAME_SYNC_MATCHES 10 -#endif - -#define DRMP3_MAX_L3_FRAME_PAYLOAD_BYTES DRMP3_MAX_FREE_FORMAT_FRAME_SIZE /* MUST be >= 320000/8/32000*1152 = 1440 */ - -#define DRMP3_MAX_BITRESERVOIR_BYTES 511 -#define DRMP3_SHORT_BLOCK_TYPE 2 -#define DRMP3_STOP_BLOCK_TYPE 3 -#define DRMP3_MODE_MONO 3 -#define DRMP3_MODE_JOINT_STEREO 1 -#define DRMP3_HDR_SIZE 4 -#define DRMP3_HDR_IS_MONO(h) (((h[3]) & 0xC0) == 0xC0) -#define DRMP3_HDR_IS_MS_STEREO(h) (((h[3]) & 0xE0) == 0x60) -#define DRMP3_HDR_IS_FREE_FORMAT(h) (((h[2]) & 0xF0) == 0) -#define DRMP3_HDR_IS_CRC(h) (!((h[1]) & 1)) -#define DRMP3_HDR_TEST_PADDING(h) ((h[2]) & 0x2) -#define DRMP3_HDR_TEST_MPEG1(h) ((h[1]) & 0x8) -#define DRMP3_HDR_TEST_NOT_MPEG25(h) ((h[1]) & 0x10) -#define DRMP3_HDR_TEST_I_STEREO(h) ((h[3]) & 0x10) -#define DRMP3_HDR_TEST_MS_STEREO(h) ((h[3]) & 0x20) -#define DRMP3_HDR_GET_STEREO_MODE(h) (((h[3]) >> 6) & 3) -#define DRMP3_HDR_GET_STEREO_MODE_EXT(h) (((h[3]) >> 4) & 3) -#define DRMP3_HDR_GET_LAYER(h) (((h[1]) >> 1) & 3) -#define DRMP3_HDR_GET_BITRATE(h) ((h[2]) >> 4) -#define DRMP3_HDR_GET_SAMPLE_RATE(h) (((h[2]) >> 2) & 3) -#define DRMP3_HDR_GET_MY_SAMPLE_RATE(h) (DRMP3_HDR_GET_SAMPLE_RATE(h) + (((h[1] >> 3) & 1) + ((h[1] >> 4) & 1))*3) -#define DRMP3_HDR_IS_FRAME_576(h) ((h[1] & 14) == 2) -#define DRMP3_HDR_IS_LAYER_1(h) ((h[1] & 6) == 6) - -#define DRMP3_BITS_DEQUANTIZER_OUT -1 -#define DRMP3_MAX_SCF (255 + DRMP3_BITS_DEQUANTIZER_OUT*4 - 210) -#define DRMP3_MAX_SCFI ((DRMP3_MAX_SCF + 3) & ~3) - -#define DRMP3_MIN(a, b) ((a) > (b) ? (b) : (a)) -#define DRMP3_MAX(a, b) ((a) < (b) ? (b) : (a)) - -#if !defined(DR_MP3_NO_SIMD) - -#if !defined(DR_MP3_ONLY_SIMD) && (defined(_M_X64) || defined(__x86_64__) || defined(__aarch64__) || defined(_M_ARM64)) -/* x64 always have SSE2, arm64 always have neon, no need for generic code */ -#define DR_MP3_ONLY_SIMD -#endif - -#if ((defined(_MSC_VER) && _MSC_VER >= 1400) && (defined(_M_IX86) || defined(_M_X64))) || ((defined(__i386__) || defined(__x86_64__)) && defined(__SSE2__)) -#if defined(_MSC_VER) -#include -#endif -#include -#define DRMP3_HAVE_SSE 1 -#define DRMP3_HAVE_SIMD 1 -#define DRMP3_VSTORE _mm_storeu_ps -#define DRMP3_VLD _mm_loadu_ps -#define DRMP3_VSET _mm_set1_ps -#define DRMP3_VADD _mm_add_ps -#define DRMP3_VSUB _mm_sub_ps -#define DRMP3_VMUL _mm_mul_ps -#define DRMP3_VMAC(a, x, y) _mm_add_ps(a, _mm_mul_ps(x, y)) -#define DRMP3_VMSB(a, x, y) _mm_sub_ps(a, _mm_mul_ps(x, y)) -#define DRMP3_VMUL_S(x, s) _mm_mul_ps(x, _mm_set1_ps(s)) -#define DRMP3_VREV(x) _mm_shuffle_ps(x, x, _MM_SHUFFLE(0, 1, 2, 3)) -typedef __m128 drmp3_f4; -#if defined(_MSC_VER) || defined(DR_MP3_ONLY_SIMD) -#define drmp3_cpuid __cpuid -#else -static __inline__ __attribute__((always_inline)) void drmp3_cpuid(int CPUInfo[], const int InfoType) -{ -#if defined(__PIC__) - __asm__ __volatile__( -#if defined(__x86_64__) - "push %%rbx\n" - "cpuid\n" - "xchgl %%ebx, %1\n" - "pop %%rbx\n" -#else - "xchgl %%ebx, %1\n" - "cpuid\n" - "xchgl %%ebx, %1\n" -#endif - : "=a" (CPUInfo[0]), "=r" (CPUInfo[1]), "=c" (CPUInfo[2]), "=d" (CPUInfo[3]) - : "a" (InfoType)); -#else - __asm__ __volatile__( - "cpuid" - : "=a" (CPUInfo[0]), "=b" (CPUInfo[1]), "=c" (CPUInfo[2]), "=d" (CPUInfo[3]) - : "a" (InfoType)); -#endif -} -#endif -static int drmp3_have_simd(void) -{ -#ifdef DR_MP3_ONLY_SIMD - return 1; -#else - static int g_have_simd; - int CPUInfo[4]; -#ifdef MINIMP3_TEST - static int g_counter; - if (g_counter++ > 100) - return 0; -#endif - if (g_have_simd) - goto end; - drmp3_cpuid(CPUInfo, 0); - if (CPUInfo[0] > 0) - { - drmp3_cpuid(CPUInfo, 1); - g_have_simd = (CPUInfo[3] & (1 << 26)) + 1; /* SSE2 */ - return g_have_simd - 1; - } - -end: - return g_have_simd - 1; -#endif -} -#elif defined(__ARM_NEON) || defined(__aarch64__) || defined(_M_ARM64) -#include -#define DRMP3_HAVE_SSE 0 -#define DRMP3_HAVE_SIMD 1 -#define DRMP3_VSTORE vst1q_f32 -#define DRMP3_VLD vld1q_f32 -#define DRMP3_VSET vmovq_n_f32 -#define DRMP3_VADD vaddq_f32 -#define DRMP3_VSUB vsubq_f32 -#define DRMP3_VMUL vmulq_f32 -#define DRMP3_VMAC(a, x, y) vmlaq_f32(a, x, y) -#define DRMP3_VMSB(a, x, y) vmlsq_f32(a, x, y) -#define DRMP3_VMUL_S(x, s) vmulq_f32(x, vmovq_n_f32(s)) -#define DRMP3_VREV(x) vcombine_f32(vget_high_f32(vrev64q_f32(x)), vget_low_f32(vrev64q_f32(x))) -typedef float32x4_t drmp3_f4; -static int drmp3_have_simd(void) -{ /* TODO: detect neon for !DR_MP3_ONLY_SIMD */ - return 1; -} -#else -#define DRMP3_HAVE_SSE 0 -#define DRMP3_HAVE_SIMD 0 -#ifdef DR_MP3_ONLY_SIMD -#error DR_MP3_ONLY_SIMD used, but SSE/NEON not enabled -#endif -#endif - -#else - -#define DRMP3_HAVE_SIMD 0 - -#endif - -#if defined(__ARM_ARCH) && (__ARM_ARCH >= 6) && !defined(__aarch64__) && !defined(_M_ARM64) -#define DRMP3_HAVE_ARMV6 1 -static __inline__ __attribute__((always_inline)) drmp3_int32 drmp3_clip_int16_arm(drmp3_int32 a) -{ - drmp3_int32 x = 0; - __asm__("ssat %0, #16, %1" : "=r"(x) : "r"(a)); - return x; -} -#else -#define DRMP3_HAVE_ARMV6 0 -#endif - - -/* Standard library stuff. */ -#ifndef DRMP3_ASSERT -#include -#define DRMP3_ASSERT(expression) assert(expression) -#endif -#ifndef DRMP3_COPY_MEMORY -#define DRMP3_COPY_MEMORY(dst, src, sz) memcpy((dst), (src), (sz)) -#endif -#ifndef DRMP3_MOVE_MEMORY -#define DRMP3_MOVE_MEMORY(dst, src, sz) memmove((dst), (src), (sz)) -#endif -#ifndef DRMP3_ZERO_MEMORY -#define DRMP3_ZERO_MEMORY(p, sz) memset((p), 0, (sz)) -#endif -#define DRMP3_ZERO_OBJECT(p) DRMP3_ZERO_MEMORY((p), sizeof(*(p))) -#ifndef DRMP3_MALLOC -#define DRMP3_MALLOC(sz) malloc((sz)) -#endif -#ifndef DRMP3_REALLOC -#define DRMP3_REALLOC(p, sz) realloc((p), (sz)) -#endif -#ifndef DRMP3_FREE -#define DRMP3_FREE(p) free((p)) -#endif - -typedef struct -{ - const drmp3_uint8* buf; - int pos, limit; -} drmp3_bs; - -typedef struct -{ - float scf[3 * 64]; - drmp3_uint8 total_bands, stereo_bands, bitalloc[64], scfcod[64]; -} drmp3_L12_scale_info; - -typedef struct -{ - drmp3_uint8 tab_offset, code_tab_width, band_count; -} drmp3_L12_subband_alloc; - -typedef struct -{ - const drmp3_uint8* sfbtab; - drmp3_uint16 part_23_length, big_values, scalefac_compress; - drmp3_uint8 global_gain, block_type, mixed_block_flag, n_long_sfb, n_short_sfb; - drmp3_uint8 table_select[3], region_count[3], subblock_gain[3]; - drmp3_uint8 preflag, scalefac_scale, count1_table, scfsi; -} drmp3_L3_gr_info; - -typedef struct -{ - drmp3_bs bs; - drmp3_uint8 maindata[DRMP3_MAX_BITRESERVOIR_BYTES + DRMP3_MAX_L3_FRAME_PAYLOAD_BYTES]; - drmp3_L3_gr_info gr_info[4]; - float grbuf[2][576], scf[40], syn[18 + 15][2 * 32]; - drmp3_uint8 ist_pos[2][39]; -} drmp3dec_scratch; - -static void drmp3_bs_init(drmp3_bs* bs, const drmp3_uint8* data, int bytes) -{ - bs->buf = data; - bs->pos = 0; - bs->limit = bytes * 8; -} - -static drmp3_uint32 drmp3_bs_get_bits(drmp3_bs* bs, int n) -{ - drmp3_uint32 next, cache = 0, s = bs->pos & 7; - int shl = n + s; - const drmp3_uint8* p = bs->buf + (bs->pos >> 3); - if ((bs->pos += n) > bs->limit) - return 0; - next = *p++ & (255 >> s); - while ((shl -= 8) > 0) - { - cache |= next << shl; - next = *p++; - } - return cache | (next >> -shl); -} - -static int drmp3_hdr_valid(const drmp3_uint8* h) -{ - return h[0] == 0xff && - ((h[1] & 0xF0) == 0xf0 || (h[1] & 0xFE) == 0xe2) && - (DRMP3_HDR_GET_LAYER(h) != 0) && - (DRMP3_HDR_GET_BITRATE(h) != 15) && - (DRMP3_HDR_GET_SAMPLE_RATE(h) != 3); -} - -static int drmp3_hdr_compare(const drmp3_uint8* h1, const drmp3_uint8* h2) -{ - return drmp3_hdr_valid(h2) && - ((h1[1] ^ h2[1]) & 0xFE) == 0 && - ((h1[2] ^ h2[2]) & 0x0C) == 0 && - !(DRMP3_HDR_IS_FREE_FORMAT(h1) ^ DRMP3_HDR_IS_FREE_FORMAT(h2)); -} - -static unsigned drmp3_hdr_bitrate_kbps(const drmp3_uint8* h) -{ - static const drmp3_uint8 halfrate[2][3][15] = { - { { 0,4,8,12,16,20,24,28,32,40,48,56,64,72,80 }, { 0,4,8,12,16,20,24,28,32,40,48,56,64,72,80 }, { 0,16,24,28,32,40,48,56,64,72,80,88,96,112,128 } }, - { { 0,16,20,24,28,32,40,48,56,64,80,96,112,128,160 }, { 0,16,24,28,32,40,48,56,64,80,96,112,128,160,192 }, { 0,16,32,48,64,80,96,112,128,144,160,176,192,208,224 } }, - }; - return 2 * halfrate[!!DRMP3_HDR_TEST_MPEG1(h)][DRMP3_HDR_GET_LAYER(h) - 1][DRMP3_HDR_GET_BITRATE(h)]; -} - -static unsigned drmp3_hdr_sample_rate_hz(const drmp3_uint8* h) -{ - static const unsigned g_hz[3] = { 44100, 48000, 32000 }; - return g_hz[DRMP3_HDR_GET_SAMPLE_RATE(h)] >> (int)!DRMP3_HDR_TEST_MPEG1(h) >> (int)!DRMP3_HDR_TEST_NOT_MPEG25(h); -} - -static unsigned drmp3_hdr_frame_samples(const drmp3_uint8* h) -{ - return DRMP3_HDR_IS_LAYER_1(h) ? 384 : (1152 >> (int)DRMP3_HDR_IS_FRAME_576(h)); -} - -static int drmp3_hdr_frame_bytes(const drmp3_uint8* h, int free_format_size) -{ - int frame_bytes = drmp3_hdr_frame_samples(h) * drmp3_hdr_bitrate_kbps(h) * 125 / drmp3_hdr_sample_rate_hz(h); - if (DRMP3_HDR_IS_LAYER_1(h)) - { - frame_bytes &= ~3; /* slot align */ - } - return frame_bytes ? frame_bytes : free_format_size; -} - -static int drmp3_hdr_padding(const drmp3_uint8* h) -{ - return DRMP3_HDR_TEST_PADDING(h) ? (DRMP3_HDR_IS_LAYER_1(h) ? 4 : 1) : 0; -} - -#ifndef DR_MP3_ONLY_MP3 -static const drmp3_L12_subband_alloc* drmp3_L12_subband_alloc_table(const drmp3_uint8* hdr, drmp3_L12_scale_info* sci) -{ - const drmp3_L12_subband_alloc* alloc; - int mode = DRMP3_HDR_GET_STEREO_MODE(hdr); - int nbands, stereo_bands = (mode == DRMP3_MODE_MONO) ? 0 : (mode == DRMP3_MODE_JOINT_STEREO) ? (DRMP3_HDR_GET_STEREO_MODE_EXT(hdr) << 2) + 4 : 32; - - if (DRMP3_HDR_IS_LAYER_1(hdr)) - { - static const drmp3_L12_subband_alloc g_alloc_L1[] = { { 76, 4, 32 } }; - alloc = g_alloc_L1; - nbands = 32; - } - else if (!DRMP3_HDR_TEST_MPEG1(hdr)) - { - static const drmp3_L12_subband_alloc g_alloc_L2M2[] = { { 60, 4, 4 }, { 44, 3, 7 }, { 44, 2, 19 } }; - alloc = g_alloc_L2M2; - nbands = 30; - } - else - { - static const drmp3_L12_subband_alloc g_alloc_L2M1[] = { { 0, 4, 3 }, { 16, 4, 8 }, { 32, 3, 12 }, { 40, 2, 7 } }; - int sample_rate_idx = DRMP3_HDR_GET_SAMPLE_RATE(hdr); - unsigned kbps = drmp3_hdr_bitrate_kbps(hdr) >> (int)(mode != DRMP3_MODE_MONO); - if (!kbps) /* free-format */ - { - kbps = 192; - } - - alloc = g_alloc_L2M1; - nbands = 27; - if (kbps < 56) - { - static const drmp3_L12_subband_alloc g_alloc_L2M1_lowrate[] = { { 44, 4, 2 }, { 44, 3, 10 } }; - alloc = g_alloc_L2M1_lowrate; - nbands = sample_rate_idx == 2 ? 12 : 8; - } - else if (kbps >= 96 && sample_rate_idx != 1) - { - nbands = 30; - } - } - - sci->total_bands = (drmp3_uint8)nbands; - sci->stereo_bands = (drmp3_uint8)DRMP3_MIN(stereo_bands, nbands); - - return alloc; -} - -static void drmp3_L12_read_scalefactors(drmp3_bs* bs, drmp3_uint8* pba, drmp3_uint8* scfcod, int bands, float* scf) -{ - static const float g_deq_L12[18 * 3] = { -#define DRMP3_DQ(x) 9.53674316e-07f/x, 7.56931807e-07f/x, 6.00777173e-07f/x - DRMP3_DQ(3),DRMP3_DQ(7),DRMP3_DQ(15),DRMP3_DQ(31),DRMP3_DQ(63),DRMP3_DQ(127),DRMP3_DQ(255),DRMP3_DQ(511),DRMP3_DQ(1023),DRMP3_DQ(2047),DRMP3_DQ(4095),DRMP3_DQ(8191),DRMP3_DQ(16383),DRMP3_DQ(32767),DRMP3_DQ(65535),DRMP3_DQ(3),DRMP3_DQ(5),DRMP3_DQ(9) - }; - int i, m; - for (i = 0; i < bands; i++) - { - float s = 0; - int ba = *pba++; - int mask = ba ? 4 + ((19 >> scfcod[i]) & 3) : 0; - for (m = 4; m; m >>= 1) - { - if (mask & m) - { - int b = drmp3_bs_get_bits(bs, 6); - s = g_deq_L12[ba * 3 - 6 + b % 3] * (int)(1 << 21 >> b / 3); - } - *scf++ = s; - } - } -} - -static void drmp3_L12_read_scale_info(const drmp3_uint8* hdr, drmp3_bs* bs, drmp3_L12_scale_info* sci) -{ - static const drmp3_uint8 g_bitalloc_code_tab[] = { - 0,17, 3, 4, 5,6,7, 8,9,10,11,12,13,14,15,16, - 0,17,18, 3,19,4,5, 6,7, 8, 9,10,11,12,13,16, - 0,17,18, 3,19,4,5,16, - 0,17,18,16, - 0,17,18,19, 4,5,6, 7,8, 9,10,11,12,13,14,15, - 0,17,18, 3,19,4,5, 6,7, 8, 9,10,11,12,13,14, - 0, 2, 3, 4, 5,6,7, 8,9,10,11,12,13,14,15,16 - }; - const drmp3_L12_subband_alloc* subband_alloc = drmp3_L12_subband_alloc_table(hdr, sci); - - int i, k = 0, ba_bits = 0; - const drmp3_uint8* ba_code_tab = g_bitalloc_code_tab; - - for (i = 0; i < sci->total_bands; i++) - { - drmp3_uint8 ba; - if (i == k) - { - k += subband_alloc->band_count; - ba_bits = subband_alloc->code_tab_width; - ba_code_tab = g_bitalloc_code_tab + subband_alloc->tab_offset; - subband_alloc++; - } - ba = ba_code_tab[drmp3_bs_get_bits(bs, ba_bits)]; - sci->bitalloc[2 * i] = ba; - if (i < sci->stereo_bands) - { - ba = ba_code_tab[drmp3_bs_get_bits(bs, ba_bits)]; - } - sci->bitalloc[2 * i + 1] = sci->stereo_bands ? ba : 0; - } - - for (i = 0; i < 2 * sci->total_bands; i++) - { - sci->scfcod[i] = (drmp3_uint8)(sci->bitalloc[i] ? DRMP3_HDR_IS_LAYER_1(hdr) ? 2 : drmp3_bs_get_bits(bs, 2) : 6); - } - - drmp3_L12_read_scalefactors(bs, sci->bitalloc, sci->scfcod, sci->total_bands * 2, sci->scf); - - for (i = sci->stereo_bands; i < sci->total_bands; i++) - { - sci->bitalloc[2 * i + 1] = 0; - } -} - -static int drmp3_L12_dequantize_granule(float* grbuf, drmp3_bs* bs, drmp3_L12_scale_info* sci, int group_size) -{ - int i, j, k, choff = 576; - for (j = 0; j < 4; j++) - { - float* dst = grbuf + group_size * j; - for (i = 0; i < 2 * sci->total_bands; i++) - { - int ba = sci->bitalloc[i]; - if (ba != 0) - { - if (ba < 17) - { - int half = (1 << (ba - 1)) - 1; - for (k = 0; k < group_size; k++) - { - dst[k] = (float)((int)drmp3_bs_get_bits(bs, ba) - half); - } - } - else - { - unsigned mod = (2 << (ba - 17)) + 1; /* 3, 5, 9 */ - unsigned code = drmp3_bs_get_bits(bs, mod + 2 - (mod >> 3)); /* 5, 7, 10 */ - for (k = 0; k < group_size; k++, code /= mod) - { - dst[k] = (float)((int)(code % mod - mod / 2)); - } - } - } - dst += choff; - choff = 18 - choff; - } - } - return group_size * 4; -} - -static void drmp3_L12_apply_scf_384(drmp3_L12_scale_info* sci, const float* scf, float* dst) -{ - int i, k; - DRMP3_COPY_MEMORY(dst + 576 + sci->stereo_bands * 18, dst + sci->stereo_bands * 18, (sci->total_bands - sci->stereo_bands) * 18 * sizeof(float)); - for (i = 0; i < sci->total_bands; i++, dst += 18, scf += 6) - { - for (k = 0; k < 12; k++) - { - dst[k + 0] *= scf[0]; - dst[k + 576] *= scf[3]; - } - } -} -#endif - -static int drmp3_L3_read_side_info(drmp3_bs* bs, drmp3_L3_gr_info* gr, const drmp3_uint8* hdr) -{ - static const drmp3_uint8 g_scf_long[8][23] = { - { 6,6,6,6,6,6,8,10,12,14,16,20,24,28,32,38,46,52,60,68,58,54,0 }, - { 12,12,12,12,12,12,16,20,24,28,32,40,48,56,64,76,90,2,2,2,2,2,0 }, - { 6,6,6,6,6,6,8,10,12,14,16,20,24,28,32,38,46,52,60,68,58,54,0 }, - { 6,6,6,6,6,6,8,10,12,14,16,18,22,26,32,38,46,54,62,70,76,36,0 }, - { 6,6,6,6,6,6,8,10,12,14,16,20,24,28,32,38,46,52,60,68,58,54,0 }, - { 4,4,4,4,4,4,6,6,8,8,10,12,16,20,24,28,34,42,50,54,76,158,0 }, - { 4,4,4,4,4,4,6,6,6,8,10,12,16,18,22,28,34,40,46,54,54,192,0 }, - { 4,4,4,4,4,4,6,6,8,10,12,16,20,24,30,38,46,56,68,84,102,26,0 } - }; - static const drmp3_uint8 g_scf_short[8][40] = { - { 4,4,4,4,4,4,4,4,4,6,6,6,8,8,8,10,10,10,12,12,12,14,14,14,18,18,18,24,24,24,30,30,30,40,40,40,18,18,18,0 }, - { 8,8,8,8,8,8,8,8,8,12,12,12,16,16,16,20,20,20,24,24,24,28,28,28,36,36,36,2,2,2,2,2,2,2,2,2,26,26,26,0 }, - { 4,4,4,4,4,4,4,4,4,6,6,6,6,6,6,8,8,8,10,10,10,14,14,14,18,18,18,26,26,26,32,32,32,42,42,42,18,18,18,0 }, - { 4,4,4,4,4,4,4,4,4,6,6,6,8,8,8,10,10,10,12,12,12,14,14,14,18,18,18,24,24,24,32,32,32,44,44,44,12,12,12,0 }, - { 4,4,4,4,4,4,4,4,4,6,6,6,8,8,8,10,10,10,12,12,12,14,14,14,18,18,18,24,24,24,30,30,30,40,40,40,18,18,18,0 }, - { 4,4,4,4,4,4,4,4,4,4,4,4,6,6,6,8,8,8,10,10,10,12,12,12,14,14,14,18,18,18,22,22,22,30,30,30,56,56,56,0 }, - { 4,4,4,4,4,4,4,4,4,4,4,4,6,6,6,6,6,6,10,10,10,12,12,12,14,14,14,16,16,16,20,20,20,26,26,26,66,66,66,0 }, - { 4,4,4,4,4,4,4,4,4,4,4,4,6,6,6,8,8,8,12,12,12,16,16,16,20,20,20,26,26,26,34,34,34,42,42,42,12,12,12,0 } - }; - static const drmp3_uint8 g_scf_mixed[8][40] = { - { 6,6,6,6,6,6,6,6,6,8,8,8,10,10,10,12,12,12,14,14,14,18,18,18,24,24,24,30,30,30,40,40,40,18,18,18,0 }, - { 12,12,12,4,4,4,8,8,8,12,12,12,16,16,16,20,20,20,24,24,24,28,28,28,36,36,36,2,2,2,2,2,2,2,2,2,26,26,26,0 }, - { 6,6,6,6,6,6,6,6,6,6,6,6,8,8,8,10,10,10,14,14,14,18,18,18,26,26,26,32,32,32,42,42,42,18,18,18,0 }, - { 6,6,6,6,6,6,6,6,6,8,8,8,10,10,10,12,12,12,14,14,14,18,18,18,24,24,24,32,32,32,44,44,44,12,12,12,0 }, - { 6,6,6,6,6,6,6,6,6,8,8,8,10,10,10,12,12,12,14,14,14,18,18,18,24,24,24,30,30,30,40,40,40,18,18,18,0 }, - { 4,4,4,4,4,4,6,6,4,4,4,6,6,6,8,8,8,10,10,10,12,12,12,14,14,14,18,18,18,22,22,22,30,30,30,56,56,56,0 }, - { 4,4,4,4,4,4,6,6,4,4,4,6,6,6,6,6,6,10,10,10,12,12,12,14,14,14,16,16,16,20,20,20,26,26,26,66,66,66,0 }, - { 4,4,4,4,4,4,6,6,4,4,4,6,6,6,8,8,8,12,12,12,16,16,16,20,20,20,26,26,26,34,34,34,42,42,42,12,12,12,0 } - }; - - unsigned tables, scfsi = 0; - int main_data_begin, part_23_sum = 0; - int gr_count = DRMP3_HDR_IS_MONO(hdr) ? 1 : 2; - int sr_idx = DRMP3_HDR_GET_MY_SAMPLE_RATE(hdr); sr_idx -= (sr_idx != 0); - - if (DRMP3_HDR_TEST_MPEG1(hdr)) - { - gr_count *= 2; - main_data_begin = drmp3_bs_get_bits(bs, 9); - scfsi = drmp3_bs_get_bits(bs, 7 + gr_count); - } - else - { - main_data_begin = drmp3_bs_get_bits(bs, 8 + gr_count) >> gr_count; - } - - do - { - if (DRMP3_HDR_IS_MONO(hdr)) - { - scfsi <<= 4; - } - gr->part_23_length = (drmp3_uint16)drmp3_bs_get_bits(bs, 12); - part_23_sum += gr->part_23_length; - gr->big_values = (drmp3_uint16)drmp3_bs_get_bits(bs, 9); - if (gr->big_values > 288) - { - return -1; - } - gr->global_gain = (drmp3_uint8)drmp3_bs_get_bits(bs, 8); - gr->scalefac_compress = (drmp3_uint16)drmp3_bs_get_bits(bs, DRMP3_HDR_TEST_MPEG1(hdr) ? 4 : 9); - gr->sfbtab = g_scf_long[sr_idx]; - gr->n_long_sfb = 22; - gr->n_short_sfb = 0; - if (drmp3_bs_get_bits(bs, 1)) - { - gr->block_type = (drmp3_uint8)drmp3_bs_get_bits(bs, 2); - if (!gr->block_type) - { - return -1; - } - gr->mixed_block_flag = (drmp3_uint8)drmp3_bs_get_bits(bs, 1); - gr->region_count[0] = 7; - gr->region_count[1] = 255; - if (gr->block_type == DRMP3_SHORT_BLOCK_TYPE) - { - scfsi &= 0x0F0F; - if (!gr->mixed_block_flag) - { - gr->region_count[0] = 8; - gr->sfbtab = g_scf_short[sr_idx]; - gr->n_long_sfb = 0; - gr->n_short_sfb = 39; - } - else - { - gr->sfbtab = g_scf_mixed[sr_idx]; - gr->n_long_sfb = DRMP3_HDR_TEST_MPEG1(hdr) ? 8 : 6; - gr->n_short_sfb = 30; - } - } - tables = drmp3_bs_get_bits(bs, 10); - tables <<= 5; - gr->subblock_gain[0] = (drmp3_uint8)drmp3_bs_get_bits(bs, 3); - gr->subblock_gain[1] = (drmp3_uint8)drmp3_bs_get_bits(bs, 3); - gr->subblock_gain[2] = (drmp3_uint8)drmp3_bs_get_bits(bs, 3); - } - else - { - gr->block_type = 0; - gr->mixed_block_flag = 0; - tables = drmp3_bs_get_bits(bs, 15); - gr->region_count[0] = (drmp3_uint8)drmp3_bs_get_bits(bs, 4); - gr->region_count[1] = (drmp3_uint8)drmp3_bs_get_bits(bs, 3); - gr->region_count[2] = 255; - } - gr->table_select[0] = (drmp3_uint8)(tables >> 10); - gr->table_select[1] = (drmp3_uint8)((tables >> 5) & 31); - gr->table_select[2] = (drmp3_uint8)((tables) & 31); - gr->preflag = (drmp3_uint8)(DRMP3_HDR_TEST_MPEG1(hdr) ? drmp3_bs_get_bits(bs, 1) : (gr->scalefac_compress >= 500)); - gr->scalefac_scale = (drmp3_uint8)drmp3_bs_get_bits(bs, 1); - gr->count1_table = (drmp3_uint8)drmp3_bs_get_bits(bs, 1); - gr->scfsi = (drmp3_uint8)((scfsi >> 12) & 15); - scfsi <<= 4; - gr++; - } while (--gr_count); - - if (part_23_sum + bs->pos > bs->limit + main_data_begin * 8) - { - return -1; - } - - return main_data_begin; -} - -static void drmp3_L3_read_scalefactors(drmp3_uint8* scf, drmp3_uint8* ist_pos, const drmp3_uint8* scf_size, const drmp3_uint8* scf_count, drmp3_bs* bitbuf, int scfsi) -{ - int i, k; - for (i = 0; i < 4 && scf_count[i]; i++, scfsi *= 2) - { - int cnt = scf_count[i]; - if (scfsi & 8) - { - DRMP3_COPY_MEMORY(scf, ist_pos, cnt); - } - else - { - int bits = scf_size[i]; - if (!bits) - { - DRMP3_ZERO_MEMORY(scf, cnt); - DRMP3_ZERO_MEMORY(ist_pos, cnt); - } - else - { - int max_scf = (scfsi < 0) ? (1 << bits) - 1 : -1; - for (k = 0; k < cnt; k++) - { - int s = drmp3_bs_get_bits(bitbuf, bits); - ist_pos[k] = (drmp3_uint8)(s == max_scf ? -1 : s); - scf[k] = (drmp3_uint8)s; - } - } - } - ist_pos += cnt; - scf += cnt; - } - scf[0] = scf[1] = scf[2] = 0; -} - -static float drmp3_L3_ldexp_q2(float y, int exp_q2) -{ - static const float g_expfrac[4] = { 9.31322575e-10f,7.83145814e-10f,6.58544508e-10f,5.53767716e-10f }; - int e; - do - { - e = DRMP3_MIN(30 * 4, exp_q2); - y *= g_expfrac[e & 3] * (1 << 30 >> (e >> 2)); - } while ((exp_q2 -= e) > 0); - return y; -} - -static void drmp3_L3_decode_scalefactors(const drmp3_uint8* hdr, drmp3_uint8* ist_pos, drmp3_bs* bs, const drmp3_L3_gr_info* gr, float* scf, int ch) -{ - static const drmp3_uint8 g_scf_partitions[3][28] = { - { 6,5,5, 5,6,5,5,5,6,5, 7,3,11,10,0,0, 7, 7, 7,0, 6, 6,6,3, 8, 8,5,0 }, - { 8,9,6,12,6,9,9,9,6,9,12,6,15,18,0,0, 6,15,12,0, 6,12,9,6, 6,18,9,0 }, - { 9,9,6,12,9,9,9,9,9,9,12,6,18,18,0,0,12,12,12,0,12, 9,9,6,15,12,9,0 } - }; - const drmp3_uint8* scf_partition = g_scf_partitions[!!gr->n_short_sfb + !gr->n_long_sfb]; - drmp3_uint8 scf_size[4], iscf[40]; - int i, scf_shift = gr->scalefac_scale + 1, gain_exp, scfsi = gr->scfsi; - float gain; - - if (DRMP3_HDR_TEST_MPEG1(hdr)) - { - static const drmp3_uint8 g_scfc_decode[16] = { 0,1,2,3, 12,5,6,7, 9,10,11,13, 14,15,18,19 }; - int part = g_scfc_decode[gr->scalefac_compress]; - scf_size[1] = scf_size[0] = (drmp3_uint8)(part >> 2); - scf_size[3] = scf_size[2] = (drmp3_uint8)(part & 3); - } - else - { - static const drmp3_uint8 g_mod[6 * 4] = { 5,5,4,4,5,5,4,1,4,3,1,1,5,6,6,1,4,4,4,1,4,3,1,1 }; - int k, modprod, sfc, ist = DRMP3_HDR_TEST_I_STEREO(hdr) && ch; - sfc = gr->scalefac_compress >> ist; - for (k = ist * 3 * 4; sfc >= 0; sfc -= modprod, k += 4) - { - for (modprod = 1, i = 3; i >= 0; i--) - { - scf_size[i] = (drmp3_uint8)(sfc / modprod % g_mod[k + i]); - modprod *= g_mod[k + i]; - } - } - scf_partition += k; - scfsi = -16; - } - drmp3_L3_read_scalefactors(iscf, ist_pos, scf_size, scf_partition, bs, scfsi); - - if (gr->n_short_sfb) - { - int sh = 3 - scf_shift; - for (i = 0; i < gr->n_short_sfb; i += 3) - { - iscf[gr->n_long_sfb + i + 0] = (drmp3_uint8)(iscf[gr->n_long_sfb + i + 0] + (gr->subblock_gain[0] << sh)); - iscf[gr->n_long_sfb + i + 1] = (drmp3_uint8)(iscf[gr->n_long_sfb + i + 1] + (gr->subblock_gain[1] << sh)); - iscf[gr->n_long_sfb + i + 2] = (drmp3_uint8)(iscf[gr->n_long_sfb + i + 2] + (gr->subblock_gain[2] << sh)); - } - } - else if (gr->preflag) - { - static const drmp3_uint8 g_preamp[10] = { 1,1,1,1,2,2,3,3,3,2 }; - for (i = 0; i < 10; i++) - { - iscf[11 + i] = (drmp3_uint8)(iscf[11 + i] + g_preamp[i]); - } - } - - gain_exp = gr->global_gain + DRMP3_BITS_DEQUANTIZER_OUT * 4 - 210 - (DRMP3_HDR_IS_MS_STEREO(hdr) ? 2 : 0); - gain = drmp3_L3_ldexp_q2(1 << (DRMP3_MAX_SCFI / 4), DRMP3_MAX_SCFI - gain_exp); - for (i = 0; i < (int)(gr->n_long_sfb + gr->n_short_sfb); i++) - { - scf[i] = drmp3_L3_ldexp_q2(gain, iscf[i] << scf_shift); - } -} - -static const float g_drmp3_pow43[129 + 16] = { - 0,-1,-2.519842f,-4.326749f,-6.349604f,-8.549880f,-10.902724f,-13.390518f,-16.000000f,-18.720754f,-21.544347f,-24.463781f,-27.473142f,-30.567351f,-33.741992f,-36.993181f, - 0,1,2.519842f,4.326749f,6.349604f,8.549880f,10.902724f,13.390518f,16.000000f,18.720754f,21.544347f,24.463781f,27.473142f,30.567351f,33.741992f,36.993181f,40.317474f,43.711787f,47.173345f,50.699631f,54.288352f,57.937408f,61.644865f,65.408941f,69.227979f,73.100443f,77.024898f,81.000000f,85.024491f,89.097188f,93.216975f,97.382800f,101.593667f,105.848633f,110.146801f,114.487321f,118.869381f,123.292209f,127.755065f,132.257246f,136.798076f,141.376907f,145.993119f,150.646117f,155.335327f,160.060199f,164.820202f,169.614826f,174.443577f,179.305980f,184.201575f,189.129918f,194.090580f,199.083145f,204.107210f,209.162385f,214.248292f,219.364564f,224.510845f,229.686789f,234.892058f,240.126328f,245.389280f,250.680604f,256.000000f,261.347174f,266.721841f,272.123723f,277.552547f,283.008049f,288.489971f,293.998060f,299.532071f,305.091761f,310.676898f,316.287249f,321.922592f,327.582707f,333.267377f,338.976394f,344.709550f,350.466646f,356.247482f,362.051866f,367.879608f,373.730522f,379.604427f,385.501143f,391.420496f,397.362314f,403.326427f,409.312672f,415.320884f,421.350905f,427.402579f,433.475750f,439.570269f,445.685987f,451.822757f,457.980436f,464.158883f,470.357960f,476.577530f,482.817459f,489.077615f,495.357868f,501.658090f,507.978156f,514.317941f,520.677324f,527.056184f,533.454404f,539.871867f,546.308458f,552.764065f,559.238575f,565.731879f,572.243870f,578.774440f,585.323483f,591.890898f,598.476581f,605.080431f,611.702349f,618.342238f,625.000000f,631.675540f,638.368763f,645.079578f -}; - -static float drmp3_L3_pow_43(int x) -{ - float frac; - int sign, mult = 256; - - if (x < 129) - { - return g_drmp3_pow43[16 + x]; - } - - if (x < 1024) - { - mult = 16; - x <<= 3; - } - - sign = 2 * x & 64; - frac = (float)((x & 63) - sign) / ((x & ~63) + sign); - return g_drmp3_pow43[16 + ((x + sign) >> 6)] * (1.f + frac * ((4.f / 3) + frac * (2.f / 9))) * mult; -} - -static void drmp3_L3_huffman(float* dst, drmp3_bs* bs, const drmp3_L3_gr_info* gr_info, const float* scf, int layer3gr_limit) -{ - static const drmp3_int16 tabs[] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 785,785,785,785,784,784,784,784,513,513,513,513,513,513,513,513,256,256,256,256,256,256,256,256,256,256,256,256,256,256,256,256, - -255,1313,1298,1282,785,785,785,785,784,784,784,784,769,769,769,769,256,256,256,256,256,256,256,256,256,256,256,256,256,256,256,256,290,288, - -255,1313,1298,1282,769,769,769,769,529,529,529,529,529,529,529,529,528,528,528,528,528,528,528,528,512,512,512,512,512,512,512,512,290,288, - -253,-318,-351,-367,785,785,785,785,784,784,784,784,769,769,769,769,256,256,256,256,256,256,256,256,256,256,256,256,256,256,256,256,819,818,547,547,275,275,275,275,561,560,515,546,289,274,288,258, - -254,-287,1329,1299,1314,1312,1057,1057,1042,1042,1026,1026,784,784,784,784,529,529,529,529,529,529,529,529,769,769,769,769,768,768,768,768,563,560,306,306,291,259, - -252,-413,-477,-542,1298,-575,1041,1041,784,784,784,784,769,769,769,769,256,256,256,256,256,256,256,256,256,256,256,256,256,256,256,256,-383,-399,1107,1092,1106,1061,849,849,789,789,1104,1091,773,773,1076,1075,341,340,325,309,834,804,577,577,532,532,516,516,832,818,803,816,561,561,531,531,515,546,289,289,288,258, - -252,-429,-493,-559,1057,1057,1042,1042,529,529,529,529,529,529,529,529,784,784,784,784,769,769,769,769,512,512,512,512,512,512,512,512,-382,1077,-415,1106,1061,1104,849,849,789,789,1091,1076,1029,1075,834,834,597,581,340,340,339,324,804,833,532,532,832,772,818,803,817,787,816,771,290,290,290,290,288,258, - -253,-349,-414,-447,-463,1329,1299,-479,1314,1312,1057,1057,1042,1042,1026,1026,785,785,785,785,784,784,784,784,769,769,769,769,768,768,768,768,-319,851,821,-335,836,850,805,849,341,340,325,336,533,533,579,579,564,564,773,832,578,548,563,516,321,276,306,291,304,259, - -251,-572,-733,-830,-863,-879,1041,1041,784,784,784,784,769,769,769,769,256,256,256,256,256,256,256,256,256,256,256,256,256,256,256,256,-511,-527,-543,1396,1351,1381,1366,1395,1335,1380,-559,1334,1138,1138,1063,1063,1350,1392,1031,1031,1062,1062,1364,1363,1120,1120,1333,1348,881,881,881,881,375,374,359,373,343,358,341,325,791,791,1123,1122,-703,1105,1045,-719,865,865,790,790,774,774,1104,1029,338,293,323,308,-799,-815,833,788,772,818,803,816,322,292,307,320,561,531,515,546,289,274,288,258, - -251,-525,-605,-685,-765,-831,-846,1298,1057,1057,1312,1282,785,785,785,785,784,784,784,784,769,769,769,769,512,512,512,512,512,512,512,512,1399,1398,1383,1367,1382,1396,1351,-511,1381,1366,1139,1139,1079,1079,1124,1124,1364,1349,1363,1333,882,882,882,882,807,807,807,807,1094,1094,1136,1136,373,341,535,535,881,775,867,822,774,-591,324,338,-671,849,550,550,866,864,609,609,293,336,534,534,789,835,773,-751,834,804,308,307,833,788,832,772,562,562,547,547,305,275,560,515,290,290, - -252,-397,-477,-557,-622,-653,-719,-735,-750,1329,1299,1314,1057,1057,1042,1042,1312,1282,1024,1024,785,785,785,785,784,784,784,784,769,769,769,769,-383,1127,1141,1111,1126,1140,1095,1110,869,869,883,883,1079,1109,882,882,375,374,807,868,838,881,791,-463,867,822,368,263,852,837,836,-543,610,610,550,550,352,336,534,534,865,774,851,821,850,805,593,533,579,564,773,832,578,578,548,548,577,577,307,276,306,291,516,560,259,259, - -250,-2107,-2507,-2764,-2909,-2974,-3007,-3023,1041,1041,1040,1040,769,769,769,769,256,256,256,256,256,256,256,256,256,256,256,256,256,256,256,256,-767,-1052,-1213,-1277,-1358,-1405,-1469,-1535,-1550,-1582,-1614,-1647,-1662,-1694,-1726,-1759,-1774,-1807,-1822,-1854,-1886,1565,-1919,-1935,-1951,-1967,1731,1730,1580,1717,-1983,1729,1564,-1999,1548,-2015,-2031,1715,1595,-2047,1714,-2063,1610,-2079,1609,-2095,1323,1323,1457,1457,1307,1307,1712,1547,1641,1700,1699,1594,1685,1625,1442,1442,1322,1322,-780,-973,-910,1279,1278,1277,1262,1276,1261,1275,1215,1260,1229,-959,974,974,989,989,-943,735,478,478,495,463,506,414,-1039,1003,958,1017,927,942,987,957,431,476,1272,1167,1228,-1183,1256,-1199,895,895,941,941,1242,1227,1212,1135,1014,1014,490,489,503,487,910,1013,985,925,863,894,970,955,1012,847,-1343,831,755,755,984,909,428,366,754,559,-1391,752,486,457,924,997,698,698,983,893,740,740,908,877,739,739,667,667,953,938,497,287,271,271,683,606,590,712,726,574,302,302,738,736,481,286,526,725,605,711,636,724,696,651,589,681,666,710,364,467,573,695,466,466,301,465,379,379,709,604,665,679,316,316,634,633,436,436,464,269,424,394,452,332,438,363,347,408,393,448,331,422,362,407,392,421,346,406,391,376,375,359,1441,1306,-2367,1290,-2383,1337,-2399,-2415,1426,1321,-2431,1411,1336,-2447,-2463,-2479,1169,1169,1049,1049,1424,1289,1412,1352,1319,-2495,1154,1154,1064,1064,1153,1153,416,390,360,404,403,389,344,374,373,343,358,372,327,357,342,311,356,326,1395,1394,1137,1137,1047,1047,1365,1392,1287,1379,1334,1364,1349,1378,1318,1363,792,792,792,792,1152,1152,1032,1032,1121,1121,1046,1046,1120,1120,1030,1030,-2895,1106,1061,1104,849,849,789,789,1091,1076,1029,1090,1060,1075,833,833,309,324,532,532,832,772,818,803,561,561,531,560,515,546,289,274,288,258, - -250,-1179,-1579,-1836,-1996,-2124,-2253,-2333,-2413,-2477,-2542,-2574,-2607,-2622,-2655,1314,1313,1298,1312,1282,785,785,785,785,1040,1040,1025,1025,768,768,768,768,-766,-798,-830,-862,-895,-911,-927,-943,-959,-975,-991,-1007,-1023,-1039,-1055,-1070,1724,1647,-1103,-1119,1631,1767,1662,1738,1708,1723,-1135,1780,1615,1779,1599,1677,1646,1778,1583,-1151,1777,1567,1737,1692,1765,1722,1707,1630,1751,1661,1764,1614,1736,1676,1763,1750,1645,1598,1721,1691,1762,1706,1582,1761,1566,-1167,1749,1629,767,766,751,765,494,494,735,764,719,749,734,763,447,447,748,718,477,506,431,491,446,476,461,505,415,430,475,445,504,399,460,489,414,503,383,474,429,459,502,502,746,752,488,398,501,473,413,472,486,271,480,270,-1439,-1455,1357,-1471,-1487,-1503,1341,1325,-1519,1489,1463,1403,1309,-1535,1372,1448,1418,1476,1356,1462,1387,-1551,1475,1340,1447,1402,1386,-1567,1068,1068,1474,1461,455,380,468,440,395,425,410,454,364,467,466,464,453,269,409,448,268,432,1371,1473,1432,1417,1308,1460,1355,1446,1459,1431,1083,1083,1401,1416,1458,1445,1067,1067,1370,1457,1051,1051,1291,1430,1385,1444,1354,1415,1400,1443,1082,1082,1173,1113,1186,1066,1185,1050,-1967,1158,1128,1172,1097,1171,1081,-1983,1157,1112,416,266,375,400,1170,1142,1127,1065,793,793,1169,1033,1156,1096,1141,1111,1155,1080,1126,1140,898,898,808,808,897,897,792,792,1095,1152,1032,1125,1110,1139,1079,1124,882,807,838,881,853,791,-2319,867,368,263,822,852,837,866,806,865,-2399,851,352,262,534,534,821,836,594,594,549,549,593,593,533,533,848,773,579,579,564,578,548,563,276,276,577,576,306,291,516,560,305,305,275,259, - -251,-892,-2058,-2620,-2828,-2957,-3023,-3039,1041,1041,1040,1040,769,769,769,769,256,256,256,256,256,256,256,256,256,256,256,256,256,256,256,256,-511,-527,-543,-559,1530,-575,-591,1528,1527,1407,1526,1391,1023,1023,1023,1023,1525,1375,1268,1268,1103,1103,1087,1087,1039,1039,1523,-604,815,815,815,815,510,495,509,479,508,463,507,447,431,505,415,399,-734,-782,1262,-815,1259,1244,-831,1258,1228,-847,-863,1196,-879,1253,987,987,748,-767,493,493,462,477,414,414,686,669,478,446,461,445,474,429,487,458,412,471,1266,1264,1009,1009,799,799,-1019,-1276,-1452,-1581,-1677,-1757,-1821,-1886,-1933,-1997,1257,1257,1483,1468,1512,1422,1497,1406,1467,1496,1421,1510,1134,1134,1225,1225,1466,1451,1374,1405,1252,1252,1358,1480,1164,1164,1251,1251,1238,1238,1389,1465,-1407,1054,1101,-1423,1207,-1439,830,830,1248,1038,1237,1117,1223,1148,1236,1208,411,426,395,410,379,269,1193,1222,1132,1235,1221,1116,976,976,1192,1162,1177,1220,1131,1191,963,963,-1647,961,780,-1663,558,558,994,993,437,408,393,407,829,978,813,797,947,-1743,721,721,377,392,844,950,828,890,706,706,812,859,796,960,948,843,934,874,571,571,-1919,690,555,689,421,346,539,539,944,779,918,873,932,842,903,888,570,570,931,917,674,674,-2575,1562,-2591,1609,-2607,1654,1322,1322,1441,1441,1696,1546,1683,1593,1669,1624,1426,1426,1321,1321,1639,1680,1425,1425,1305,1305,1545,1668,1608,1623,1667,1592,1638,1666,1320,1320,1652,1607,1409,1409,1304,1304,1288,1288,1664,1637,1395,1395,1335,1335,1622,1636,1394,1394,1319,1319,1606,1621,1392,1392,1137,1137,1137,1137,345,390,360,375,404,373,1047,-2751,-2767,-2783,1062,1121,1046,-2799,1077,-2815,1106,1061,789,789,1105,1104,263,355,310,340,325,354,352,262,339,324,1091,1076,1029,1090,1060,1075,833,833,788,788,1088,1028,818,818,803,803,561,561,531,531,816,771,546,546,289,274,288,258, - -253,-317,-381,-446,-478,-509,1279,1279,-811,-1179,-1451,-1756,-1900,-2028,-2189,-2253,-2333,-2414,-2445,-2511,-2526,1313,1298,-2559,1041,1041,1040,1040,1025,1025,1024,1024,1022,1007,1021,991,1020,975,1019,959,687,687,1018,1017,671,671,655,655,1016,1015,639,639,758,758,623,623,757,607,756,591,755,575,754,559,543,543,1009,783,-575,-621,-685,-749,496,-590,750,749,734,748,974,989,1003,958,988,973,1002,942,987,957,972,1001,926,986,941,971,956,1000,910,985,925,999,894,970,-1071,-1087,-1102,1390,-1135,1436,1509,1451,1374,-1151,1405,1358,1480,1420,-1167,1507,1494,1389,1342,1465,1435,1450,1326,1505,1310,1493,1373,1479,1404,1492,1464,1419,428,443,472,397,736,526,464,464,486,457,442,471,484,482,1357,1449,1434,1478,1388,1491,1341,1490,1325,1489,1463,1403,1309,1477,1372,1448,1418,1433,1476,1356,1462,1387,-1439,1475,1340,1447,1402,1474,1324,1461,1371,1473,269,448,1432,1417,1308,1460,-1711,1459,-1727,1441,1099,1099,1446,1386,1431,1401,-1743,1289,1083,1083,1160,1160,1458,1445,1067,1067,1370,1457,1307,1430,1129,1129,1098,1098,268,432,267,416,266,400,-1887,1144,1187,1082,1173,1113,1186,1066,1050,1158,1128,1143,1172,1097,1171,1081,420,391,1157,1112,1170,1142,1127,1065,1169,1049,1156,1096,1141,1111,1155,1080,1126,1154,1064,1153,1140,1095,1048,-2159,1125,1110,1137,-2175,823,823,1139,1138,807,807,384,264,368,263,868,838,853,791,867,822,852,837,866,806,865,790,-2319,851,821,836,352,262,850,805,849,-2399,533,533,835,820,336,261,578,548,563,577,532,532,832,772,562,562,547,547,305,275,560,515,290,290,288,258 }; - static const drmp3_uint8 tab32[] = { 130,162,193,209,44,28,76,140,9,9,9,9,9,9,9,9,190,254,222,238,126,94,157,157,109,61,173,205 }; - static const drmp3_uint8 tab33[] = { 252,236,220,204,188,172,156,140,124,108,92,76,60,44,28,12 }; - static const drmp3_int16 tabindex[2 * 16] = { 0,32,64,98,0,132,180,218,292,364,426,538,648,746,0,1126,1460,1460,1460,1460,1460,1460,1460,1460,1842,1842,1842,1842,1842,1842,1842,1842 }; - static const drmp3_uint8 g_linbits[] = { 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,2,3,4,6,8,10,13,4,5,6,7,8,9,11,13 }; - -#define DRMP3_PEEK_BITS(n) (bs_cache >> (32 - n)) -#define DRMP3_FLUSH_BITS(n) { bs_cache <<= (n); bs_sh += (n); } -#define DRMP3_CHECK_BITS while (bs_sh >= 0) { bs_cache |= (drmp3_uint32)*bs_next_ptr++ << bs_sh; bs_sh -= 8; } -#define DRMP3_BSPOS ((bs_next_ptr - bs->buf)*8 - 24 + bs_sh) - - float one = 0.0f; - int ireg = 0, big_val_cnt = gr_info->big_values; - const drmp3_uint8* sfb = gr_info->sfbtab; - const drmp3_uint8* bs_next_ptr = bs->buf + bs->pos / 8; - drmp3_uint32 bs_cache = (((bs_next_ptr[0] * 256u + bs_next_ptr[1]) * 256u + bs_next_ptr[2]) * 256u + bs_next_ptr[3]) << (bs->pos & 7); - int pairs_to_decode, np, bs_sh = (bs->pos & 7) - 8; - bs_next_ptr += 4; - - while (big_val_cnt > 0) - { - int tab_num = gr_info->table_select[ireg]; - int sfb_cnt = gr_info->region_count[ireg++]; - const drmp3_int16* codebook = tabs + tabindex[tab_num]; - int linbits = g_linbits[tab_num]; - if (linbits) - { - do - { - np = *sfb++ / 2; - pairs_to_decode = DRMP3_MIN(big_val_cnt, np); - one = *scf++; - do - { - int j, w = 5; - int leaf = codebook[DRMP3_PEEK_BITS(w)]; - while (leaf < 0) - { - DRMP3_FLUSH_BITS(w); - w = leaf & 7; - leaf = codebook[DRMP3_PEEK_BITS(w) - (leaf >> 3)]; - } - DRMP3_FLUSH_BITS(leaf >> 8); - - for (j = 0; j < 2; j++, dst++, leaf >>= 4) - { - int lsb = leaf & 0x0F; - if (lsb == 15) - { - lsb += DRMP3_PEEK_BITS(linbits); - DRMP3_FLUSH_BITS(linbits); - DRMP3_CHECK_BITS; - *dst = one * drmp3_L3_pow_43(lsb) * ((drmp3_int32)bs_cache < 0 ? -1 : 1); - } - else - { - *dst = g_drmp3_pow43[16 + lsb - 16 * (bs_cache >> 31)] * one; - } - DRMP3_FLUSH_BITS(lsb ? 1 : 0); - } - DRMP3_CHECK_BITS; - } while (--pairs_to_decode); - } while ((big_val_cnt -= np) > 0 && --sfb_cnt >= 0); - } - else - { - do - { - np = *sfb++ / 2; - pairs_to_decode = DRMP3_MIN(big_val_cnt, np); - one = *scf++; - do - { - int j, w = 5; - int leaf = codebook[DRMP3_PEEK_BITS(w)]; - while (leaf < 0) - { - DRMP3_FLUSH_BITS(w); - w = leaf & 7; - leaf = codebook[DRMP3_PEEK_BITS(w) - (leaf >> 3)]; - } - DRMP3_FLUSH_BITS(leaf >> 8); - - for (j = 0; j < 2; j++, dst++, leaf >>= 4) - { - int lsb = leaf & 0x0F; - *dst = g_drmp3_pow43[16 + lsb - 16 * (bs_cache >> 31)] * one; - DRMP3_FLUSH_BITS(lsb ? 1 : 0); - } - DRMP3_CHECK_BITS; - } while (--pairs_to_decode); - } while ((big_val_cnt -= np) > 0 && --sfb_cnt >= 0); - } - } - - for (np = 1 - big_val_cnt;; dst += 4) - { - const drmp3_uint8* codebook_count1 = (gr_info->count1_table) ? tab33 : tab32; - int leaf = codebook_count1[DRMP3_PEEK_BITS(4)]; - if (!(leaf & 8)) - { - leaf = codebook_count1[(leaf >> 3) + (bs_cache << 4 >> (32 - (leaf & 3)))]; - } - DRMP3_FLUSH_BITS(leaf & 7); - if (DRMP3_BSPOS > layer3gr_limit) - { - break; - } -#define DRMP3_RELOAD_SCALEFACTOR if (!--np) { np = *sfb++/2; if (!np) break; one = *scf++; } -#define DRMP3_DEQ_COUNT1(s) if (leaf & (128 >> s)) { dst[s] = ((drmp3_int32)bs_cache < 0) ? -one : one; DRMP3_FLUSH_BITS(1) } - DRMP3_RELOAD_SCALEFACTOR; - DRMP3_DEQ_COUNT1(0); - DRMP3_DEQ_COUNT1(1); - DRMP3_RELOAD_SCALEFACTOR; - DRMP3_DEQ_COUNT1(2); - DRMP3_DEQ_COUNT1(3); - DRMP3_CHECK_BITS; - } - - bs->pos = layer3gr_limit; -} - -static void drmp3_L3_midside_stereo(float* left, int n) -{ - int i = 0; - float* right = left + 576; -#if DRMP3_HAVE_SIMD - if (drmp3_have_simd()) - { - for (; i < n - 3; i += 4) - { - drmp3_f4 vl = DRMP3_VLD(left + i); - drmp3_f4 vr = DRMP3_VLD(right + i); - DRMP3_VSTORE(left + i, DRMP3_VADD(vl, vr)); - DRMP3_VSTORE(right + i, DRMP3_VSUB(vl, vr)); - } -#ifdef __GNUC__ - /* Workaround for spurious -Waggressive-loop-optimizations warning from gcc. - * For more info see: https://github.com/lieff/minimp3/issues/88 - */ - if (__builtin_constant_p(n % 4 == 0) && n % 4 == 0) - return; -#endif - } -#endif - for (; i < n; i++) - { - float a = left[i]; - float b = right[i]; - left[i] = a + b; - right[i] = a - b; - } -} - -static void drmp3_L3_intensity_stereo_band(float* left, int n, float kl, float kr) -{ - int i; - for (i = 0; i < n; i++) - { - left[i + 576] = left[i] * kr; - left[i] = left[i] * kl; - } -} - -static void drmp3_L3_stereo_top_band(const float* right, const drmp3_uint8* sfb, int nbands, int max_band[3]) -{ - int i, k; - - max_band[0] = max_band[1] = max_band[2] = -1; - - for (i = 0; i < nbands; i++) - { - for (k = 0; k < sfb[i]; k += 2) - { - if (right[k] != 0 || right[k + 1] != 0) - { - max_band[i % 3] = i; - break; - } - } - right += sfb[i]; - } -} - -static void drmp3_L3_stereo_process(float* left, const drmp3_uint8* ist_pos, const drmp3_uint8* sfb, const drmp3_uint8* hdr, int max_band[3], int mpeg2_sh) -{ - static const float g_pan[7 * 2] = { 0,1,0.21132487f,0.78867513f,0.36602540f,0.63397460f,0.5f,0.5f,0.63397460f,0.36602540f,0.78867513f,0.21132487f,1,0 }; - unsigned i, max_pos = DRMP3_HDR_TEST_MPEG1(hdr) ? 7 : 64; - - for (i = 0; sfb[i]; i++) - { - unsigned ipos = ist_pos[i]; - if ((int)i > max_band[i % 3] && ipos < max_pos) - { - float kl, kr, s = DRMP3_HDR_TEST_MS_STEREO(hdr) ? 1.41421356f : 1; - if (DRMP3_HDR_TEST_MPEG1(hdr)) - { - kl = g_pan[2 * ipos]; - kr = g_pan[2 * ipos + 1]; - } - else - { - kl = 1; - kr = drmp3_L3_ldexp_q2(1, (ipos + 1) >> 1 << mpeg2_sh); - if (ipos & 1) - { - kl = kr; - kr = 1; - } - } - drmp3_L3_intensity_stereo_band(left, sfb[i], kl * s, kr * s); - } - else if (DRMP3_HDR_TEST_MS_STEREO(hdr)) - { - drmp3_L3_midside_stereo(left, sfb[i]); - } - left += sfb[i]; - } -} - -static void drmp3_L3_intensity_stereo(float* left, drmp3_uint8* ist_pos, const drmp3_L3_gr_info* gr, const drmp3_uint8* hdr) -{ - int max_band[3], n_sfb = gr->n_long_sfb + gr->n_short_sfb; - int i, max_blocks = gr->n_short_sfb ? 3 : 1; - - drmp3_L3_stereo_top_band(left + 576, gr->sfbtab, n_sfb, max_band); - if (gr->n_long_sfb) - { - max_band[0] = max_band[1] = max_band[2] = DRMP3_MAX(DRMP3_MAX(max_band[0], max_band[1]), max_band[2]); - } - for (i = 0; i < max_blocks; i++) - { - int default_pos = DRMP3_HDR_TEST_MPEG1(hdr) ? 3 : 0; - int itop = n_sfb - max_blocks + i; - int prev = itop - max_blocks; - ist_pos[itop] = (drmp3_uint8)(max_band[i] >= prev ? default_pos : ist_pos[prev]); - } - drmp3_L3_stereo_process(left, ist_pos, gr->sfbtab, hdr, max_band, gr[1].scalefac_compress & 1); -} - -static void drmp3_L3_reorder(float* grbuf, float* scratch, const drmp3_uint8* sfb) -{ - int i, len; - float* src = grbuf, * dst = scratch; - - for (; 0 != (len = *sfb); sfb += 3, src += 2 * len) - { - for (i = 0; i < len; i++, src++) - { - *dst++ = src[0 * len]; - *dst++ = src[1 * len]; - *dst++ = src[2 * len]; - } - } - DRMP3_COPY_MEMORY(grbuf, scratch, (dst - scratch) * sizeof(float)); -} - -static void drmp3_L3_antialias(float* grbuf, int nbands) -{ - static const float g_aa[2][8] = { - {0.85749293f,0.88174200f,0.94962865f,0.98331459f,0.99551782f,0.99916056f,0.99989920f,0.99999316f}, - {0.51449576f,0.47173197f,0.31337745f,0.18191320f,0.09457419f,0.04096558f,0.01419856f,0.00369997f} - }; - - for (; nbands > 0; nbands--, grbuf += 18) - { - int i = 0; -#if DRMP3_HAVE_SIMD - if (drmp3_have_simd()) for (; i < 8; i += 4) - { - drmp3_f4 vu = DRMP3_VLD(grbuf + 18 + i); - drmp3_f4 vd = DRMP3_VLD(grbuf + 14 - i); - drmp3_f4 vc0 = DRMP3_VLD(g_aa[0] + i); - drmp3_f4 vc1 = DRMP3_VLD(g_aa[1] + i); - vd = DRMP3_VREV(vd); - DRMP3_VSTORE(grbuf + 18 + i, DRMP3_VSUB(DRMP3_VMUL(vu, vc0), DRMP3_VMUL(vd, vc1))); - vd = DRMP3_VADD(DRMP3_VMUL(vu, vc1), DRMP3_VMUL(vd, vc0)); - DRMP3_VSTORE(grbuf + 14 - i, DRMP3_VREV(vd)); - } -#endif -#ifndef DR_MP3_ONLY_SIMD - for (; i < 8; i++) - { - float u = grbuf[18 + i]; - float d = grbuf[17 - i]; - grbuf[18 + i] = u * g_aa[0][i] - d * g_aa[1][i]; - grbuf[17 - i] = u * g_aa[1][i] + d * g_aa[0][i]; - } -#endif - } -} - -static void drmp3_L3_dct3_9(float* y) -{ - float s0, s1, s2, s3, s4, s5, s6, s7, s8, t0, t2, t4; - - s0 = y[0]; s2 = y[2]; s4 = y[4]; s6 = y[6]; s8 = y[8]; - t0 = s0 + s6 * 0.5f; - s0 -= s6; - t4 = (s4 + s2) * 0.93969262f; - t2 = (s8 + s2) * 0.76604444f; - s6 = (s4 - s8) * 0.17364818f; - s4 += s8 - s2; - - s2 = s0 - s4 * 0.5f; - y[4] = s4 + s0; - s8 = t0 - t2 + s6; - s0 = t0 - t4 + t2; - s4 = t0 + t4 - s6; - - s1 = y[1]; s3 = y[3]; s5 = y[5]; s7 = y[7]; - - s3 *= 0.86602540f; - t0 = (s5 + s1) * 0.98480775f; - t4 = (s5 - s7) * 0.34202014f; - t2 = (s1 + s7) * 0.64278761f; - s1 = (s1 - s5 - s7) * 0.86602540f; - - s5 = t0 - s3 - t2; - s7 = t4 - s3 - t0; - s3 = t4 + s3 - t2; - - y[0] = s4 - s7; - y[1] = s2 + s1; - y[2] = s0 - s3; - y[3] = s8 + s5; - y[5] = s8 - s5; - y[6] = s0 + s3; - y[7] = s2 - s1; - y[8] = s4 + s7; -} - -static void drmp3_L3_imdct36(float* grbuf, float* overlap, const float* window, int nbands) -{ - int i, j; - static const float g_twid9[18] = { - 0.73727734f,0.79335334f,0.84339145f,0.88701083f,0.92387953f,0.95371695f,0.97629601f,0.99144486f,0.99904822f,0.67559021f,0.60876143f,0.53729961f,0.46174861f,0.38268343f,0.30070580f,0.21643961f,0.13052619f,0.04361938f - }; - - for (j = 0; j < nbands; j++, grbuf += 18, overlap += 9) - { - float co[9], si[9]; - co[0] = -grbuf[0]; - si[0] = grbuf[17]; - for (i = 0; i < 4; i++) - { - si[8 - 2 * i] = grbuf[4 * i + 1] - grbuf[4 * i + 2]; - co[1 + 2 * i] = grbuf[4 * i + 1] + grbuf[4 * i + 2]; - si[7 - 2 * i] = grbuf[4 * i + 4] - grbuf[4 * i + 3]; - co[2 + 2 * i] = -(grbuf[4 * i + 3] + grbuf[4 * i + 4]); - } - drmp3_L3_dct3_9(co); - drmp3_L3_dct3_9(si); - - si[1] = -si[1]; - si[3] = -si[3]; - si[5] = -si[5]; - si[7] = -si[7]; - - i = 0; - -#if DRMP3_HAVE_SIMD - if (drmp3_have_simd()) for (; i < 8; i += 4) - { - drmp3_f4 vovl = DRMP3_VLD(overlap + i); - drmp3_f4 vc = DRMP3_VLD(co + i); - drmp3_f4 vs = DRMP3_VLD(si + i); - drmp3_f4 vr0 = DRMP3_VLD(g_twid9 + i); - drmp3_f4 vr1 = DRMP3_VLD(g_twid9 + 9 + i); - drmp3_f4 vw0 = DRMP3_VLD(window + i); - drmp3_f4 vw1 = DRMP3_VLD(window + 9 + i); - drmp3_f4 vsum = DRMP3_VADD(DRMP3_VMUL(vc, vr1), DRMP3_VMUL(vs, vr0)); - DRMP3_VSTORE(overlap + i, DRMP3_VSUB(DRMP3_VMUL(vc, vr0), DRMP3_VMUL(vs, vr1))); - DRMP3_VSTORE(grbuf + i, DRMP3_VSUB(DRMP3_VMUL(vovl, vw0), DRMP3_VMUL(vsum, vw1))); - vsum = DRMP3_VADD(DRMP3_VMUL(vovl, vw1), DRMP3_VMUL(vsum, vw0)); - DRMP3_VSTORE(grbuf + 14 - i, DRMP3_VREV(vsum)); - } -#endif - for (; i < 9; i++) - { - float ovl = overlap[i]; - float sum = co[i] * g_twid9[9 + i] + si[i] * g_twid9[0 + i]; - overlap[i] = co[i] * g_twid9[0 + i] - si[i] * g_twid9[9 + i]; - grbuf[i] = ovl * window[0 + i] - sum * window[9 + i]; - grbuf[17 - i] = ovl * window[9 + i] + sum * window[0 + i]; - } - } -} - -static void drmp3_L3_idct3(float x0, float x1, float x2, float* dst) -{ - float m1 = x1 * 0.86602540f; - float a1 = x0 - x2 * 0.5f; - dst[1] = x0 + x2; - dst[0] = a1 + m1; - dst[2] = a1 - m1; -} - -static void drmp3_L3_imdct12(float* x, float* dst, float* overlap) -{ - static const float g_twid3[6] = { 0.79335334f,0.92387953f,0.99144486f, 0.60876143f,0.38268343f,0.13052619f }; - float co[3], si[3]; - int i; - - drmp3_L3_idct3(-x[0], x[6] + x[3], x[12] + x[9], co); - drmp3_L3_idct3(x[15], x[12] - x[9], x[6] - x[3], si); - si[1] = -si[1]; - - for (i = 0; i < 3; i++) - { - float ovl = overlap[i]; - float sum = co[i] * g_twid3[3 + i] + si[i] * g_twid3[0 + i]; - overlap[i] = co[i] * g_twid3[0 + i] - si[i] * g_twid3[3 + i]; - dst[i] = ovl * g_twid3[2 - i] - sum * g_twid3[5 - i]; - dst[5 - i] = ovl * g_twid3[5 - i] + sum * g_twid3[2 - i]; - } -} - -static void drmp3_L3_imdct_short(float* grbuf, float* overlap, int nbands) -{ - for (; nbands > 0; nbands--, overlap += 9, grbuf += 18) - { - float tmp[18]; - DRMP3_COPY_MEMORY(tmp, grbuf, sizeof(tmp)); - DRMP3_COPY_MEMORY(grbuf, overlap, 6 * sizeof(float)); - drmp3_L3_imdct12(tmp, grbuf + 6, overlap + 6); - drmp3_L3_imdct12(tmp + 1, grbuf + 12, overlap + 6); - drmp3_L3_imdct12(tmp + 2, overlap, overlap + 6); - } -} - -static void drmp3_L3_change_sign(float* grbuf) -{ - int b, i; - for (b = 0, grbuf += 18; b < 32; b += 2, grbuf += 36) - for (i = 1; i < 18; i += 2) - grbuf[i] = -grbuf[i]; -} - -static void drmp3_L3_imdct_gr(float* grbuf, float* overlap, unsigned block_type, unsigned n_long_bands) -{ - static const float g_mdct_window[2][18] = { - { 0.99904822f,0.99144486f,0.97629601f,0.95371695f,0.92387953f,0.88701083f,0.84339145f,0.79335334f,0.73727734f,0.04361938f,0.13052619f,0.21643961f,0.30070580f,0.38268343f,0.46174861f,0.53729961f,0.60876143f,0.67559021f }, - { 1,1,1,1,1,1,0.99144486f,0.92387953f,0.79335334f,0,0,0,0,0,0,0.13052619f,0.38268343f,0.60876143f } - }; - if (n_long_bands) - { - drmp3_L3_imdct36(grbuf, overlap, g_mdct_window[0], n_long_bands); - grbuf += 18 * n_long_bands; - overlap += 9 * n_long_bands; - } - if (block_type == DRMP3_SHORT_BLOCK_TYPE) - drmp3_L3_imdct_short(grbuf, overlap, 32 - n_long_bands); - else - drmp3_L3_imdct36(grbuf, overlap, g_mdct_window[block_type == DRMP3_STOP_BLOCK_TYPE], 32 - n_long_bands); -} - -static void drmp3_L3_save_reservoir(drmp3dec* h, drmp3dec_scratch* s) -{ - int pos = (s->bs.pos + 7) / 8u; - int remains = s->bs.limit / 8u - pos; - if (remains > DRMP3_MAX_BITRESERVOIR_BYTES) - { - pos += remains - DRMP3_MAX_BITRESERVOIR_BYTES; - remains = DRMP3_MAX_BITRESERVOIR_BYTES; - } - if (remains > 0) - { - DRMP3_MOVE_MEMORY(h->reserv_buf, s->maindata + pos, remains); - } - h->reserv = remains; -} - -static int drmp3_L3_restore_reservoir(drmp3dec* h, drmp3_bs* bs, drmp3dec_scratch* s, int main_data_begin) -{ - int frame_bytes = (bs->limit - bs->pos) / 8; - int bytes_have = DRMP3_MIN(h->reserv, main_data_begin); - DRMP3_COPY_MEMORY(s->maindata, h->reserv_buf + DRMP3_MAX(0, h->reserv - main_data_begin), DRMP3_MIN(h->reserv, main_data_begin)); - DRMP3_COPY_MEMORY(s->maindata + bytes_have, bs->buf + bs->pos / 8, frame_bytes); - drmp3_bs_init(&s->bs, s->maindata, bytes_have + frame_bytes); - return h->reserv >= main_data_begin; -} - -static void drmp3_L3_decode(drmp3dec* h, drmp3dec_scratch* s, drmp3_L3_gr_info* gr_info, int nch) -{ - int ch; - - for (ch = 0; ch < nch; ch++) - { - int layer3gr_limit = s->bs.pos + gr_info[ch].part_23_length; - drmp3_L3_decode_scalefactors(h->header, s->ist_pos[ch], &s->bs, gr_info + ch, s->scf, ch); - drmp3_L3_huffman(s->grbuf[ch], &s->bs, gr_info + ch, s->scf, layer3gr_limit); - } - - if (DRMP3_HDR_TEST_I_STEREO(h->header)) - { - drmp3_L3_intensity_stereo(s->grbuf[0], s->ist_pos[1], gr_info, h->header); - } - else if (DRMP3_HDR_IS_MS_STEREO(h->header)) - { - drmp3_L3_midside_stereo(s->grbuf[0], 576); - } - - for (ch = 0; ch < nch; ch++, gr_info++) - { - int aa_bands = 31; - int n_long_bands = (gr_info->mixed_block_flag ? 2 : 0) << (int)(DRMP3_HDR_GET_MY_SAMPLE_RATE(h->header) == 2); - - if (gr_info->n_short_sfb) - { - aa_bands = n_long_bands - 1; - drmp3_L3_reorder(s->grbuf[ch] + n_long_bands * 18, s->syn[0], gr_info->sfbtab + gr_info->n_long_sfb); - } - - drmp3_L3_antialias(s->grbuf[ch], aa_bands); - drmp3_L3_imdct_gr(s->grbuf[ch], h->mdct_overlap[ch], gr_info->block_type, n_long_bands); - drmp3_L3_change_sign(s->grbuf[ch]); - } -} - -static void drmp3d_DCT_II(float* grbuf, int n) -{ - static const float g_sec[24] = { - 10.19000816f,0.50060302f,0.50241929f,3.40760851f,0.50547093f,0.52249861f,2.05778098f,0.51544732f,0.56694406f,1.48416460f,0.53104258f,0.64682180f,1.16943991f,0.55310392f,0.78815460f,0.97256821f,0.58293498f,1.06067765f,0.83934963f,0.62250412f,1.72244716f,0.74453628f,0.67480832f,5.10114861f - }; - int i, k = 0; -#if DRMP3_HAVE_SIMD - if (drmp3_have_simd()) for (; k < n; k += 4) - { - drmp3_f4 t[4][8], * x; - float* y = grbuf + k; - - for (x = t[0], i = 0; i < 8; i++, x++) - { - drmp3_f4 x0 = DRMP3_VLD(&y[i * 18]); - drmp3_f4 x1 = DRMP3_VLD(&y[(15 - i) * 18]); - drmp3_f4 x2 = DRMP3_VLD(&y[(16 + i) * 18]); - drmp3_f4 x3 = DRMP3_VLD(&y[(31 - i) * 18]); - drmp3_f4 t0 = DRMP3_VADD(x0, x3); - drmp3_f4 t1 = DRMP3_VADD(x1, x2); - drmp3_f4 t2 = DRMP3_VMUL_S(DRMP3_VSUB(x1, x2), g_sec[3 * i + 0]); - drmp3_f4 t3 = DRMP3_VMUL_S(DRMP3_VSUB(x0, x3), g_sec[3 * i + 1]); - x[0] = DRMP3_VADD(t0, t1); - x[8] = DRMP3_VMUL_S(DRMP3_VSUB(t0, t1), g_sec[3 * i + 2]); - x[16] = DRMP3_VADD(t3, t2); - x[24] = DRMP3_VMUL_S(DRMP3_VSUB(t3, t2), g_sec[3 * i + 2]); - } - for (x = t[0], i = 0; i < 4; i++, x += 8) - { - drmp3_f4 x0 = x[0], x1 = x[1], x2 = x[2], x3 = x[3], x4 = x[4], x5 = x[5], x6 = x[6], x7 = x[7], xt; - xt = DRMP3_VSUB(x0, x7); x0 = DRMP3_VADD(x0, x7); - x7 = DRMP3_VSUB(x1, x6); x1 = DRMP3_VADD(x1, x6); - x6 = DRMP3_VSUB(x2, x5); x2 = DRMP3_VADD(x2, x5); - x5 = DRMP3_VSUB(x3, x4); x3 = DRMP3_VADD(x3, x4); - x4 = DRMP3_VSUB(x0, x3); x0 = DRMP3_VADD(x0, x3); - x3 = DRMP3_VSUB(x1, x2); x1 = DRMP3_VADD(x1, x2); - x[0] = DRMP3_VADD(x0, x1); - x[4] = DRMP3_VMUL_S(DRMP3_VSUB(x0, x1), 0.70710677f); - x5 = DRMP3_VADD(x5, x6); - x6 = DRMP3_VMUL_S(DRMP3_VADD(x6, x7), 0.70710677f); - x7 = DRMP3_VADD(x7, xt); - x3 = DRMP3_VMUL_S(DRMP3_VADD(x3, x4), 0.70710677f); - x5 = DRMP3_VSUB(x5, DRMP3_VMUL_S(x7, 0.198912367f)); /* rotate by PI/8 */ - x7 = DRMP3_VADD(x7, DRMP3_VMUL_S(x5, 0.382683432f)); - x5 = DRMP3_VSUB(x5, DRMP3_VMUL_S(x7, 0.198912367f)); - x0 = DRMP3_VSUB(xt, x6); xt = DRMP3_VADD(xt, x6); - x[1] = DRMP3_VMUL_S(DRMP3_VADD(xt, x7), 0.50979561f); - x[2] = DRMP3_VMUL_S(DRMP3_VADD(x4, x3), 0.54119611f); - x[3] = DRMP3_VMUL_S(DRMP3_VSUB(x0, x5), 0.60134488f); - x[5] = DRMP3_VMUL_S(DRMP3_VADD(x0, x5), 0.89997619f); - x[6] = DRMP3_VMUL_S(DRMP3_VSUB(x4, x3), 1.30656302f); - x[7] = DRMP3_VMUL_S(DRMP3_VSUB(xt, x7), 2.56291556f); - } - - if (k > n - 3) - { -#if DRMP3_HAVE_SSE -#define DRMP3_VSAVE2(i, v) _mm_storel_pi((__m64 *)(void*)&y[i*18], v) -#else -#define DRMP3_VSAVE2(i, v) vst1_f32((float32_t *)&y[i*18], vget_low_f32(v)) -#endif - for (i = 0; i < 7; i++, y += 4 * 18) - { - drmp3_f4 s = DRMP3_VADD(t[3][i], t[3][i + 1]); - DRMP3_VSAVE2(0, t[0][i]); - DRMP3_VSAVE2(1, DRMP3_VADD(t[2][i], s)); - DRMP3_VSAVE2(2, DRMP3_VADD(t[1][i], t[1][i + 1])); - DRMP3_VSAVE2(3, DRMP3_VADD(t[2][1 + i], s)); - } - DRMP3_VSAVE2(0, t[0][7]); - DRMP3_VSAVE2(1, DRMP3_VADD(t[2][7], t[3][7])); - DRMP3_VSAVE2(2, t[1][7]); - DRMP3_VSAVE2(3, t[3][7]); - } - else - { -#define DRMP3_VSAVE4(i, v) DRMP3_VSTORE(&y[i*18], v) - for (i = 0; i < 7; i++, y += 4 * 18) - { - drmp3_f4 s = DRMP3_VADD(t[3][i], t[3][i + 1]); - DRMP3_VSAVE4(0, t[0][i]); - DRMP3_VSAVE4(1, DRMP3_VADD(t[2][i], s)); - DRMP3_VSAVE4(2, DRMP3_VADD(t[1][i], t[1][i + 1])); - DRMP3_VSAVE4(3, DRMP3_VADD(t[2][1 + i], s)); - } - DRMP3_VSAVE4(0, t[0][7]); - DRMP3_VSAVE4(1, DRMP3_VADD(t[2][7], t[3][7])); - DRMP3_VSAVE4(2, t[1][7]); - DRMP3_VSAVE4(3, t[3][7]); - } - } - else -#endif -#ifdef DR_MP3_ONLY_SIMD - { - } /* for HAVE_SIMD=1, MINIMP3_ONLY_SIMD=1 case we do not need non-intrinsic "else" branch */ -#else - for (; k < n; k++) - { - float t[4][8], * x, * y = grbuf + k; - - for (x = t[0], i = 0; i < 8; i++, x++) - { - float x0 = y[i * 18]; - float x1 = y[(15 - i) * 18]; - float x2 = y[(16 + i) * 18]; - float x3 = y[(31 - i) * 18]; - float t0 = x0 + x3; - float t1 = x1 + x2; - float t2 = (x1 - x2) * g_sec[3 * i + 0]; - float t3 = (x0 - x3) * g_sec[3 * i + 1]; - x[0] = t0 + t1; - x[8] = (t0 - t1) * g_sec[3 * i + 2]; - x[16] = t3 + t2; - x[24] = (t3 - t2) * g_sec[3 * i + 2]; - } - for (x = t[0], i = 0; i < 4; i++, x += 8) - { - float x0 = x[0], x1 = x[1], x2 = x[2], x3 = x[3], x4 = x[4], x5 = x[5], x6 = x[6], x7 = x[7], xt; - xt = x0 - x7; x0 += x7; - x7 = x1 - x6; x1 += x6; - x6 = x2 - x5; x2 += x5; - x5 = x3 - x4; x3 += x4; - x4 = x0 - x3; x0 += x3; - x3 = x1 - x2; x1 += x2; - x[0] = x0 + x1; - x[4] = (x0 - x1) * 0.70710677f; - x5 = x5 + x6; - x6 = (x6 + x7) * 0.70710677f; - x7 = x7 + xt; - x3 = (x3 + x4) * 0.70710677f; - x5 -= x7 * 0.198912367f; /* rotate by PI/8 */ - x7 += x5 * 0.382683432f; - x5 -= x7 * 0.198912367f; - x0 = xt - x6; xt += x6; - x[1] = (xt + x7) * 0.50979561f; - x[2] = (x4 + x3) * 0.54119611f; - x[3] = (x0 - x5) * 0.60134488f; - x[5] = (x0 + x5) * 0.89997619f; - x[6] = (x4 - x3) * 1.30656302f; - x[7] = (xt - x7) * 2.56291556f; - - } - for (i = 0; i < 7; i++, y += 4 * 18) - { - y[0 * 18] = t[0][i]; - y[1 * 18] = t[2][i] + t[3][i] + t[3][i + 1]; - y[2 * 18] = t[1][i] + t[1][i + 1]; - y[3 * 18] = t[2][i + 1] + t[3][i] + t[3][i + 1]; - } - y[0 * 18] = t[0][7]; - y[1 * 18] = t[2][7] + t[3][7]; - y[2 * 18] = t[1][7]; - y[3 * 18] = t[3][7]; - } -#endif -} - -#ifndef DR_MP3_FLOAT_OUTPUT -typedef drmp3_int16 drmp3d_sample_t; - -static drmp3_int16 drmp3d_scale_pcm(float sample) -{ - drmp3_int16 s; -#if DRMP3_HAVE_ARMV6 - drmp3_int32 s32 = (drmp3_int32)(sample + .5f); - s32 -= (s32 < 0); - s = (drmp3_int16)drmp3_clip_int16_arm(s32); -#else - if (sample >= 32766.5) return (drmp3_int16)32767; - if (sample <= -32767.5) return (drmp3_int16)-32768; - s = (drmp3_int16)(sample + .5f); - s -= (s < 0); /* away from zero, to be compliant */ -#endif - return s; -} -#else -typedef float drmp3d_sample_t; - -static float drmp3d_scale_pcm(float sample) -{ - return sample * (1.f / 32768.f); -} -#endif - -static void drmp3d_synth_pair(drmp3d_sample_t* pcm, int nch, const float* z) -{ - float a; - a = (z[14 * 64] - z[0]) * 29; - a += (z[1 * 64] + z[13 * 64]) * 213; - a += (z[12 * 64] - z[2 * 64]) * 459; - a += (z[3 * 64] + z[11 * 64]) * 2037; - a += (z[10 * 64] - z[4 * 64]) * 5153; - a += (z[5 * 64] + z[9 * 64]) * 6574; - a += (z[8 * 64] - z[6 * 64]) * 37489; - a += z[7 * 64] * 75038; - pcm[0] = drmp3d_scale_pcm(a); - - z += 2; - a = z[14 * 64] * 104; - a += z[12 * 64] * 1567; - a += z[10 * 64] * 9727; - a += z[8 * 64] * 64019; - a += z[6 * 64] * -9975; - a += z[4 * 64] * -45; - a += z[2 * 64] * 146; - a += z[0 * 64] * -5; - pcm[16 * nch] = drmp3d_scale_pcm(a); -} - -static void drmp3d_synth(float* xl, drmp3d_sample_t* dstl, int nch, float* lins) -{ - int i; - float* xr = xl + 576 * (nch - 1); - drmp3d_sample_t* dstr = dstl + (nch - 1); - - static const float g_win[] = { - -1,26,-31,208,218,401,-519,2063,2000,4788,-5517,7134,5959,35640,-39336,74992, - -1,24,-35,202,222,347,-581,2080,1952,4425,-5879,7640,5288,33791,-41176,74856, - -1,21,-38,196,225,294,-645,2087,1893,4063,-6237,8092,4561,31947,-43006,74630, - -1,19,-41,190,227,244,-711,2085,1822,3705,-6589,8492,3776,30112,-44821,74313, - -1,17,-45,183,228,197,-779,2075,1739,3351,-6935,8840,2935,28289,-46617,73908, - -1,16,-49,176,228,153,-848,2057,1644,3004,-7271,9139,2037,26482,-48390,73415, - -2,14,-53,169,227,111,-919,2032,1535,2663,-7597,9389,1082,24694,-50137,72835, - -2,13,-58,161,224,72,-991,2001,1414,2330,-7910,9592,70,22929,-51853,72169, - -2,11,-63,154,221,36,-1064,1962,1280,2006,-8209,9750,-998,21189,-53534,71420, - -2,10,-68,147,215,2,-1137,1919,1131,1692,-8491,9863,-2122,19478,-55178,70590, - -3,9,-73,139,208,-29,-1210,1870,970,1388,-8755,9935,-3300,17799,-56778,69679, - -3,8,-79,132,200,-57,-1283,1817,794,1095,-8998,9966,-4533,16155,-58333,68692, - -4,7,-85,125,189,-83,-1356,1759,605,814,-9219,9959,-5818,14548,-59838,67629, - -4,7,-91,117,177,-106,-1428,1698,402,545,-9416,9916,-7154,12980,-61289,66494, - -5,6,-97,111,163,-127,-1498,1634,185,288,-9585,9838,-8540,11455,-62684,65290 - }; - float* zlin = lins + 15 * 64; - const float* w = g_win; - - zlin[4 * 15] = xl[18 * 16]; - zlin[4 * 15 + 1] = xr[18 * 16]; - zlin[4 * 15 + 2] = xl[0]; - zlin[4 * 15 + 3] = xr[0]; - - zlin[4 * 31] = xl[1 + 18 * 16]; - zlin[4 * 31 + 1] = xr[1 + 18 * 16]; - zlin[4 * 31 + 2] = xl[1]; - zlin[4 * 31 + 3] = xr[1]; - - drmp3d_synth_pair(dstr, nch, lins + 4 * 15 + 1); - drmp3d_synth_pair(dstr + 32 * nch, nch, lins + 4 * 15 + 64 + 1); - drmp3d_synth_pair(dstl, nch, lins + 4 * 15); - drmp3d_synth_pair(dstl + 32 * nch, nch, lins + 4 * 15 + 64); - -#if DRMP3_HAVE_SIMD - if (drmp3_have_simd()) for (i = 14; i >= 0; i--) - { -#define DRMP3_VLOAD(k) drmp3_f4 w0 = DRMP3_VSET(*w++); drmp3_f4 w1 = DRMP3_VSET(*w++); drmp3_f4 vz = DRMP3_VLD(&zlin[4*i - 64*k]); drmp3_f4 vy = DRMP3_VLD(&zlin[4*i - 64*(15 - k)]); -#define DRMP3_V0(k) { DRMP3_VLOAD(k) b = DRMP3_VADD(DRMP3_VMUL(vz, w1), DRMP3_VMUL(vy, w0)) ; a = DRMP3_VSUB(DRMP3_VMUL(vz, w0), DRMP3_VMUL(vy, w1)); } -#define DRMP3_V1(k) { DRMP3_VLOAD(k) b = DRMP3_VADD(b, DRMP3_VADD(DRMP3_VMUL(vz, w1), DRMP3_VMUL(vy, w0))); a = DRMP3_VADD(a, DRMP3_VSUB(DRMP3_VMUL(vz, w0), DRMP3_VMUL(vy, w1))); } -#define DRMP3_V2(k) { DRMP3_VLOAD(k) b = DRMP3_VADD(b, DRMP3_VADD(DRMP3_VMUL(vz, w1), DRMP3_VMUL(vy, w0))); a = DRMP3_VADD(a, DRMP3_VSUB(DRMP3_VMUL(vy, w1), DRMP3_VMUL(vz, w0))); } - drmp3_f4 a, b; - zlin[4 * i] = xl[18 * (31 - i)]; - zlin[4 * i + 1] = xr[18 * (31 - i)]; - zlin[4 * i + 2] = xl[1 + 18 * (31 - i)]; - zlin[4 * i + 3] = xr[1 + 18 * (31 - i)]; - zlin[4 * i + 64] = xl[1 + 18 * (1 + i)]; - zlin[4 * i + 64 + 1] = xr[1 + 18 * (1 + i)]; - zlin[4 * i - 64 + 2] = xl[18 * (1 + i)]; - zlin[4 * i - 64 + 3] = xr[18 * (1 + i)]; - - DRMP3_V0(0) DRMP3_V2(1) DRMP3_V1(2) DRMP3_V2(3) DRMP3_V1(4) DRMP3_V2(5) DRMP3_V1(6) DRMP3_V2(7) - - { -#ifndef DR_MP3_FLOAT_OUTPUT -#if DRMP3_HAVE_SSE - static const drmp3_f4 g_max = { 32767.0f, 32767.0f, 32767.0f, 32767.0f }; - static const drmp3_f4 g_min = { -32768.0f, -32768.0f, -32768.0f, -32768.0f }; - __m128i pcm8 = _mm_packs_epi32(_mm_cvtps_epi32(_mm_max_ps(_mm_min_ps(a, g_max), g_min)), - _mm_cvtps_epi32(_mm_max_ps(_mm_min_ps(b, g_max), g_min))); - dstr[(15 - i) * nch] = (drmp3_int16)_mm_extract_epi16(pcm8, 1); - dstr[(17 + i) * nch] = (drmp3_int16)_mm_extract_epi16(pcm8, 5); - dstl[(15 - i) * nch] = (drmp3_int16)_mm_extract_epi16(pcm8, 0); - dstl[(17 + i) * nch] = (drmp3_int16)_mm_extract_epi16(pcm8, 4); - dstr[(47 - i) * nch] = (drmp3_int16)_mm_extract_epi16(pcm8, 3); - dstr[(49 + i) * nch] = (drmp3_int16)_mm_extract_epi16(pcm8, 7); - dstl[(47 - i) * nch] = (drmp3_int16)_mm_extract_epi16(pcm8, 2); - dstl[(49 + i) * nch] = (drmp3_int16)_mm_extract_epi16(pcm8, 6); -#else - int16x4_t pcma, pcmb; - a = DRMP3_VADD(a, DRMP3_VSET(0.5f)); - b = DRMP3_VADD(b, DRMP3_VSET(0.5f)); - pcma = vqmovn_s32(vqaddq_s32(vcvtq_s32_f32(a), vreinterpretq_s32_u32(vcltq_f32(a, DRMP3_VSET(0))))); - pcmb = vqmovn_s32(vqaddq_s32(vcvtq_s32_f32(b), vreinterpretq_s32_u32(vcltq_f32(b, DRMP3_VSET(0))))); - vst1_lane_s16(dstr + (15 - i) * nch, pcma, 1); - vst1_lane_s16(dstr + (17 + i) * nch, pcmb, 1); - vst1_lane_s16(dstl + (15 - i) * nch, pcma, 0); - vst1_lane_s16(dstl + (17 + i) * nch, pcmb, 0); - vst1_lane_s16(dstr + (47 - i) * nch, pcma, 3); - vst1_lane_s16(dstr + (49 + i) * nch, pcmb, 3); - vst1_lane_s16(dstl + (47 - i) * nch, pcma, 2); - vst1_lane_s16(dstl + (49 + i) * nch, pcmb, 2); -#endif -#else -#if DRMP3_HAVE_SSE - static const drmp3_f4 g_scale = { 1.0f / 32768.0f, 1.0f / 32768.0f, 1.0f / 32768.0f, 1.0f / 32768.0f }; -#else - const drmp3_f4 g_scale = vdupq_n_f32(1.0f / 32768.0f); -#endif - a = DRMP3_VMUL(a, g_scale); - b = DRMP3_VMUL(b, g_scale); -#if DRMP3_HAVE_SSE - _mm_store_ss(dstr + (15 - i) * nch, _mm_shuffle_ps(a, a, _MM_SHUFFLE(1, 1, 1, 1))); - _mm_store_ss(dstr + (17 + i) * nch, _mm_shuffle_ps(b, b, _MM_SHUFFLE(1, 1, 1, 1))); - _mm_store_ss(dstl + (15 - i) * nch, _mm_shuffle_ps(a, a, _MM_SHUFFLE(0, 0, 0, 0))); - _mm_store_ss(dstl + (17 + i) * nch, _mm_shuffle_ps(b, b, _MM_SHUFFLE(0, 0, 0, 0))); - _mm_store_ss(dstr + (47 - i) * nch, _mm_shuffle_ps(a, a, _MM_SHUFFLE(3, 3, 3, 3))); - _mm_store_ss(dstr + (49 + i) * nch, _mm_shuffle_ps(b, b, _MM_SHUFFLE(3, 3, 3, 3))); - _mm_store_ss(dstl + (47 - i) * nch, _mm_shuffle_ps(a, a, _MM_SHUFFLE(2, 2, 2, 2))); - _mm_store_ss(dstl + (49 + i) * nch, _mm_shuffle_ps(b, b, _MM_SHUFFLE(2, 2, 2, 2))); -#else - vst1q_lane_f32(dstr + (15 - i) * nch, a, 1); - vst1q_lane_f32(dstr + (17 + i) * nch, b, 1); - vst1q_lane_f32(dstl + (15 - i) * nch, a, 0); - vst1q_lane_f32(dstl + (17 + i) * nch, b, 0); - vst1q_lane_f32(dstr + (47 - i) * nch, a, 3); - vst1q_lane_f32(dstr + (49 + i) * nch, b, 3); - vst1q_lane_f32(dstl + (47 - i) * nch, a, 2); - vst1q_lane_f32(dstl + (49 + i) * nch, b, 2); -#endif -#endif /* DR_MP3_FLOAT_OUTPUT */ - } - } - else -#endif -#ifdef DR_MP3_ONLY_SIMD - { - } /* for HAVE_SIMD=1, MINIMP3_ONLY_SIMD=1 case we do not need non-intrinsic "else" branch */ -#else - for (i = 14; i >= 0; i--) - { -#define DRMP3_LOAD(k) float w0 = *w++; float w1 = *w++; float *vz = &zlin[4*i - k*64]; float *vy = &zlin[4*i - (15 - k)*64]; -#define DRMP3_S0(k) { int j; DRMP3_LOAD(k); for (j = 0; j < 4; j++) b[j] = vz[j]*w1 + vy[j]*w0, a[j] = vz[j]*w0 - vy[j]*w1; } -#define DRMP3_S1(k) { int j; DRMP3_LOAD(k); for (j = 0; j < 4; j++) b[j] += vz[j]*w1 + vy[j]*w0, a[j] += vz[j]*w0 - vy[j]*w1; } -#define DRMP3_S2(k) { int j; DRMP3_LOAD(k); for (j = 0; j < 4; j++) b[j] += vz[j]*w1 + vy[j]*w0, a[j] += vy[j]*w1 - vz[j]*w0; } - float a[4], b[4]; - - zlin[4 * i] = xl[18 * (31 - i)]; - zlin[4 * i + 1] = xr[18 * (31 - i)]; - zlin[4 * i + 2] = xl[1 + 18 * (31 - i)]; - zlin[4 * i + 3] = xr[1 + 18 * (31 - i)]; - zlin[4 * (i + 16)] = xl[1 + 18 * (1 + i)]; - zlin[4 * (i + 16) + 1] = xr[1 + 18 * (1 + i)]; - zlin[4 * (i - 16) + 2] = xl[18 * (1 + i)]; - zlin[4 * (i - 16) + 3] = xr[18 * (1 + i)]; - - DRMP3_S0(0) DRMP3_S2(1) DRMP3_S1(2) DRMP3_S2(3) DRMP3_S1(4) DRMP3_S2(5) DRMP3_S1(6) DRMP3_S2(7) - - dstr[(15 - i) * nch] = drmp3d_scale_pcm(a[1]); - dstr[(17 + i) * nch] = drmp3d_scale_pcm(b[1]); - dstl[(15 - i) * nch] = drmp3d_scale_pcm(a[0]); - dstl[(17 + i) * nch] = drmp3d_scale_pcm(b[0]); - dstr[(47 - i) * nch] = drmp3d_scale_pcm(a[3]); - dstr[(49 + i) * nch] = drmp3d_scale_pcm(b[3]); - dstl[(47 - i) * nch] = drmp3d_scale_pcm(a[2]); - dstl[(49 + i) * nch] = drmp3d_scale_pcm(b[2]); - } -#endif -} - -static void drmp3d_synth_granule(float* qmf_state, float* grbuf, int nbands, int nch, drmp3d_sample_t* pcm, float* lins) -{ - int i; - for (i = 0; i < nch; i++) - { - drmp3d_DCT_II(grbuf + 576 * i, nbands); - } - - DRMP3_COPY_MEMORY(lins, qmf_state, sizeof(float) * 15 * 64); - - for (i = 0; i < nbands; i += 2) - { - drmp3d_synth(grbuf + i, pcm + 32 * nch * i, nch, lins + i * 64); - } -#ifndef DR_MP3_NONSTANDARD_BUT_LOGICAL - if (nch == 1) - { - for (i = 0; i < 15 * 64; i += 2) - { - qmf_state[i] = lins[nbands * 64 + i]; - } - } - else -#endif - { - DRMP3_COPY_MEMORY(qmf_state, lins + nbands * 64, sizeof(float) * 15 * 64); - } -} - -static int drmp3d_match_frame(const drmp3_uint8* hdr, int mp3_bytes, int frame_bytes) -{ - int i, nmatch; - for (i = 0, nmatch = 0; nmatch < DRMP3_MAX_FRAME_SYNC_MATCHES; nmatch++) - { - i += drmp3_hdr_frame_bytes(hdr + i, frame_bytes) + drmp3_hdr_padding(hdr + i); - if (i + DRMP3_HDR_SIZE > mp3_bytes) - return nmatch > 0; - if (!drmp3_hdr_compare(hdr, hdr + i)) - return 0; - } - return 1; -} - -static int drmp3d_find_frame(const drmp3_uint8* mp3, int mp3_bytes, int* free_format_bytes, int* ptr_frame_bytes) -{ - int i, k; - for (i = 0; i < mp3_bytes - DRMP3_HDR_SIZE; i++, mp3++) - { - if (drmp3_hdr_valid(mp3)) - { - int frame_bytes = drmp3_hdr_frame_bytes(mp3, *free_format_bytes); - int frame_and_padding = frame_bytes + drmp3_hdr_padding(mp3); - - for (k = DRMP3_HDR_SIZE; !frame_bytes && k < DRMP3_MAX_FREE_FORMAT_FRAME_SIZE && i + 2 * k < mp3_bytes - DRMP3_HDR_SIZE; k++) - { - if (drmp3_hdr_compare(mp3, mp3 + k)) - { - int fb = k - drmp3_hdr_padding(mp3); - int nextfb = fb + drmp3_hdr_padding(mp3 + k); - if (i + k + nextfb + DRMP3_HDR_SIZE > mp3_bytes || !drmp3_hdr_compare(mp3, mp3 + k + nextfb)) - continue; - frame_and_padding = k; - frame_bytes = fb; - *free_format_bytes = fb; - } - } - - if ((frame_bytes && i + frame_and_padding <= mp3_bytes && - drmp3d_match_frame(mp3, mp3_bytes - i, frame_bytes)) || - (!i && frame_and_padding == mp3_bytes)) - { - *ptr_frame_bytes = frame_and_padding; - return i; - } - *free_format_bytes = 0; - } - } - *ptr_frame_bytes = 0; - return mp3_bytes; -} - -DRMP3_API void drmp3dec_init(drmp3dec* dec) -{ - dec->header[0] = 0; -} - -DRMP3_API int drmp3dec_decode_frame(drmp3dec* dec, const drmp3_uint8* mp3, int mp3_bytes, void* pcm, drmp3dec_frame_info* info) -{ - int i = 0, igr, frame_size = 0, success = 1; - const drmp3_uint8* hdr; - drmp3_bs bs_frame[1]; - drmp3dec_scratch scratch; - - if (mp3_bytes > 4 && dec->header[0] == 0xff && drmp3_hdr_compare(dec->header, mp3)) - { - frame_size = drmp3_hdr_frame_bytes(mp3, dec->free_format_bytes) + drmp3_hdr_padding(mp3); - if (frame_size != mp3_bytes && (frame_size + DRMP3_HDR_SIZE > mp3_bytes || !drmp3_hdr_compare(mp3, mp3 + frame_size))) - { - frame_size = 0; - } - } - if (!frame_size) - { - DRMP3_ZERO_MEMORY(dec, sizeof(drmp3dec)); - i = drmp3d_find_frame(mp3, mp3_bytes, &dec->free_format_bytes, &frame_size); - if (!frame_size || i + frame_size > mp3_bytes) - { - info->frame_bytes = i; - return 0; - } - } - - hdr = mp3 + i; - DRMP3_COPY_MEMORY(dec->header, hdr, DRMP3_HDR_SIZE); - info->frame_bytes = i + frame_size; - info->channels = DRMP3_HDR_IS_MONO(hdr) ? 1 : 2; - info->hz = drmp3_hdr_sample_rate_hz(hdr); - info->layer = 4 - DRMP3_HDR_GET_LAYER(hdr); - info->bitrate_kbps = drmp3_hdr_bitrate_kbps(hdr); - - drmp3_bs_init(bs_frame, hdr + DRMP3_HDR_SIZE, frame_size - DRMP3_HDR_SIZE); - if (DRMP3_HDR_IS_CRC(hdr)) - { - drmp3_bs_get_bits(bs_frame, 16); - } - - if (info->layer == 3) - { - int main_data_begin = drmp3_L3_read_side_info(bs_frame, scratch.gr_info, hdr); - if (main_data_begin < 0 || bs_frame->pos > bs_frame->limit) - { - drmp3dec_init(dec); - return 0; - } - success = drmp3_L3_restore_reservoir(dec, bs_frame, &scratch, main_data_begin); - if (success && pcm != NULL) - { - for (igr = 0; igr < (DRMP3_HDR_TEST_MPEG1(hdr) ? 2 : 1); igr++, pcm = DRMP3_OFFSET_PTR(pcm, sizeof(drmp3d_sample_t) * 576 * info->channels)) - { - DRMP3_ZERO_MEMORY(scratch.grbuf[0], 576 * 2 * sizeof(float)); - drmp3_L3_decode(dec, &scratch, scratch.gr_info + igr * info->channels, info->channels); - drmp3d_synth_granule(dec->qmf_state, scratch.grbuf[0], 18, info->channels, (drmp3d_sample_t*)pcm, scratch.syn[0]); - } - } - drmp3_L3_save_reservoir(dec, &scratch); - } - else - { -#ifdef DR_MP3_ONLY_MP3 - return 0; -#else - drmp3_L12_scale_info sci[1]; - - if (pcm == NULL) { - return drmp3_hdr_frame_samples(hdr); - } - - drmp3_L12_read_scale_info(hdr, bs_frame, sci); - - DRMP3_ZERO_MEMORY(scratch.grbuf[0], 576 * 2 * sizeof(float)); - for (i = 0, igr = 0; igr < 3; igr++) - { - if (12 == (i += drmp3_L12_dequantize_granule(scratch.grbuf[0] + i, bs_frame, sci, info->layer | 1))) - { - i = 0; - drmp3_L12_apply_scf_384(sci, sci->scf + igr, scratch.grbuf[0]); - drmp3d_synth_granule(dec->qmf_state, scratch.grbuf[0], 12, info->channels, (drmp3d_sample_t*)pcm, scratch.syn[0]); - DRMP3_ZERO_MEMORY(scratch.grbuf[0], 576 * 2 * sizeof(float)); - pcm = DRMP3_OFFSET_PTR(pcm, sizeof(drmp3d_sample_t) * 384 * info->channels); - } - if (bs_frame->pos > bs_frame->limit) - { - drmp3dec_init(dec); - return 0; - } - } -#endif - } - - return success * drmp3_hdr_frame_samples(dec->header); -} - -DRMP3_API void drmp3dec_f32_to_s16(const float* in, drmp3_int16* out, size_t num_samples) -{ - size_t i = 0; -#if DRMP3_HAVE_SIMD - size_t aligned_count = num_samples & ~7; - for (; i < aligned_count; i += 8) - { - drmp3_f4 scale = DRMP3_VSET(32768.0f); - drmp3_f4 a = DRMP3_VMUL(DRMP3_VLD(&in[i]), scale); - drmp3_f4 b = DRMP3_VMUL(DRMP3_VLD(&in[i + 4]), scale); -#if DRMP3_HAVE_SSE - drmp3_f4 s16max = DRMP3_VSET(32767.0f); - drmp3_f4 s16min = DRMP3_VSET(-32768.0f); - __m128i pcm8 = _mm_packs_epi32(_mm_cvtps_epi32(_mm_max_ps(_mm_min_ps(a, s16max), s16min)), - _mm_cvtps_epi32(_mm_max_ps(_mm_min_ps(b, s16max), s16min))); - out[i] = (drmp3_int16)_mm_extract_epi16(pcm8, 0); - out[i + 1] = (drmp3_int16)_mm_extract_epi16(pcm8, 1); - out[i + 2] = (drmp3_int16)_mm_extract_epi16(pcm8, 2); - out[i + 3] = (drmp3_int16)_mm_extract_epi16(pcm8, 3); - out[i + 4] = (drmp3_int16)_mm_extract_epi16(pcm8, 4); - out[i + 5] = (drmp3_int16)_mm_extract_epi16(pcm8, 5); - out[i + 6] = (drmp3_int16)_mm_extract_epi16(pcm8, 6); - out[i + 7] = (drmp3_int16)_mm_extract_epi16(pcm8, 7); -#else - int16x4_t pcma, pcmb; - a = DRMP3_VADD(a, DRMP3_VSET(0.5f)); - b = DRMP3_VADD(b, DRMP3_VSET(0.5f)); - pcma = vqmovn_s32(vqaddq_s32(vcvtq_s32_f32(a), vreinterpretq_s32_u32(vcltq_f32(a, DRMP3_VSET(0))))); - pcmb = vqmovn_s32(vqaddq_s32(vcvtq_s32_f32(b), vreinterpretq_s32_u32(vcltq_f32(b, DRMP3_VSET(0))))); - vst1_lane_s16(out + i, pcma, 0); - vst1_lane_s16(out + i + 1, pcma, 1); - vst1_lane_s16(out + i + 2, pcma, 2); - vst1_lane_s16(out + i + 3, pcma, 3); - vst1_lane_s16(out + i + 4, pcmb, 0); - vst1_lane_s16(out + i + 5, pcmb, 1); - vst1_lane_s16(out + i + 6, pcmb, 2); - vst1_lane_s16(out + i + 7, pcmb, 3); -#endif - } -#endif - for (; i < num_samples; i++) - { - float sample = in[i] * 32768.0f; - if (sample >= 32766.5) - out[i] = (drmp3_int16)32767; - else if (sample <= -32767.5) - out[i] = (drmp3_int16)-32768; - else - { - short s = (drmp3_int16)(sample + .5f); - s -= (s < 0); /* away from zero, to be compliant */ - out[i] = s; - } - } -} - - - -/************************************************************************************************************************************************************ - - Main Public API - - ************************************************************************************************************************************************************/ -#if defined(SIZE_MAX) -#define DRMP3_SIZE_MAX SIZE_MAX -#else -#if defined(_WIN64) || defined(_LP64) || defined(__LP64__) -#define DRMP3_SIZE_MAX ((drmp3_uint64)0xFFFFFFFFFFFFFFFF) -#else -#define DRMP3_SIZE_MAX 0xFFFFFFFF -#endif -#endif - - /* Options. */ -#ifndef DRMP3_SEEK_LEADING_MP3_FRAMES -#define DRMP3_SEEK_LEADING_MP3_FRAMES 2 -#endif - -#define DRMP3_MIN_DATA_CHUNK_SIZE 16384 - -/* The size in bytes of each chunk of data to read from the MP3 stream. minimp3 recommends at least 16K, but in an attempt to reduce data movement I'm making this slightly larger. */ -#ifndef DRMP3_DATA_CHUNK_SIZE -#define DRMP3_DATA_CHUNK_SIZE DRMP3_MIN_DATA_CHUNK_SIZE*4 -#endif - - -#define DRMP3_COUNTOF(x) (sizeof(x) / sizeof(x[0])) -#define DRMP3_CLAMP(x, lo, hi) (DRMP3_MAX(lo, DRMP3_MIN(x, hi))) - -#ifndef DRMP3_PI_D -#define DRMP3_PI_D 3.14159265358979323846264 -#endif - -#define DRMP3_DEFAULT_RESAMPLER_LPF_ORDER 2 - -static DRMP3_INLINE float drmp3_mix_f32(float x, float y, float a) -{ - return x * (1 - a) + y * a; -} -static DRMP3_INLINE float drmp3_mix_f32_fast(float x, float y, float a) -{ - float r0 = (y - x); - float r1 = r0 * a; - return x + r1; - /*return x + (y - x)*a;*/ -} - - -/* -Greatest common factor using Euclid's algorithm iteratively. -*/ -static DRMP3_INLINE drmp3_uint32 drmp3_gcf_u32(drmp3_uint32 a, drmp3_uint32 b) -{ - for (;;) { - if (b == 0) { - break; - } - else { - drmp3_uint32 t = a; - a = b; - b = t % a; - } - } - - return a; -} - - -static void* drmp3__malloc_default(size_t sz, void* pUserData) -{ - (void)pUserData; - return DRMP3_MALLOC(sz); -} - -static void* drmp3__realloc_default(void* p, size_t sz, void* pUserData) -{ - (void)pUserData; - return DRMP3_REALLOC(p, sz); -} - -static void drmp3__free_default(void* p, void* pUserData) -{ - (void)pUserData; - DRMP3_FREE(p); -} - - -static void* drmp3__malloc_from_callbacks(size_t sz, const drmp3_allocation_callbacks* pAllocationCallbacks) -{ - if (pAllocationCallbacks == NULL) { - return NULL; - } - - if (pAllocationCallbacks->onMalloc != NULL) { - return pAllocationCallbacks->onMalloc(sz, pAllocationCallbacks->pUserData); - } - - /* Try using realloc(). */ - if (pAllocationCallbacks->onRealloc != NULL) { - return pAllocationCallbacks->onRealloc(NULL, sz, pAllocationCallbacks->pUserData); - } - - return NULL; -} - -static void* drmp3__realloc_from_callbacks(void* p, size_t szNew, size_t szOld, const drmp3_allocation_callbacks* pAllocationCallbacks) -{ - if (pAllocationCallbacks == NULL) { - return NULL; - } - - if (pAllocationCallbacks->onRealloc != NULL) { - return pAllocationCallbacks->onRealloc(p, szNew, pAllocationCallbacks->pUserData); - } - - /* Try emulating realloc() in terms of malloc()/free(). */ - if (pAllocationCallbacks->onMalloc != NULL && pAllocationCallbacks->onFree != NULL) { - void* p2; - - p2 = pAllocationCallbacks->onMalloc(szNew, pAllocationCallbacks->pUserData); - if (p2 == NULL) { - return NULL; - } - - if (p != NULL) { - DRMP3_COPY_MEMORY(p2, p, szOld); - pAllocationCallbacks->onFree(p, pAllocationCallbacks->pUserData); - } - - return p2; - } - - return NULL; -} - -static void drmp3__free_from_callbacks(void* p, const drmp3_allocation_callbacks* pAllocationCallbacks) -{ - if (p == NULL || pAllocationCallbacks == NULL) { - return; - } - - if (pAllocationCallbacks->onFree != NULL) { - pAllocationCallbacks->onFree(p, pAllocationCallbacks->pUserData); - } -} - - -static drmp3_allocation_callbacks drmp3_copy_allocation_callbacks_or_defaults(const drmp3_allocation_callbacks* pAllocationCallbacks) -{ - if (pAllocationCallbacks != NULL) { - /* Copy. */ - return *pAllocationCallbacks; - } - else { - /* Defaults. */ - drmp3_allocation_callbacks allocationCallbacks; - allocationCallbacks.pUserData = NULL; - allocationCallbacks.onMalloc = drmp3__malloc_default; - allocationCallbacks.onRealloc = drmp3__realloc_default; - allocationCallbacks.onFree = drmp3__free_default; - return allocationCallbacks; - } -} - - - -static size_t drmp3__on_read(drmp3* pMP3, void* pBufferOut, size_t bytesToRead) -{ - size_t bytesRead = pMP3->onRead(pMP3->pUserData, pBufferOut, bytesToRead); - pMP3->streamCursor += bytesRead; - return bytesRead; -} - -static drmp3_bool32 drmp3__on_seek(drmp3* pMP3, int offset, drmp3_seek_origin origin) -{ - DRMP3_ASSERT(offset >= 0); - - if (!pMP3->onSeek(pMP3->pUserData, offset, origin)) { - return DRMP3_FALSE; - } - - if (origin == drmp3_seek_origin_start) { - pMP3->streamCursor = (drmp3_uint64)offset; - } - else { - pMP3->streamCursor += offset; - } - - return DRMP3_TRUE; -} - -static drmp3_bool32 drmp3__on_seek_64(drmp3* pMP3, drmp3_uint64 offset, drmp3_seek_origin origin) -{ - if (offset <= 0x7FFFFFFF) { - return drmp3__on_seek(pMP3, (int)offset, origin); - } - - - /* Getting here "offset" is too large for a 32-bit integer. We just keep seeking forward until we hit the offset. */ - if (!drmp3__on_seek(pMP3, 0x7FFFFFFF, drmp3_seek_origin_start)) { - return DRMP3_FALSE; - } - - offset -= 0x7FFFFFFF; - while (offset > 0) { - if (offset <= 0x7FFFFFFF) { - if (!drmp3__on_seek(pMP3, (int)offset, drmp3_seek_origin_current)) { - return DRMP3_FALSE; - } - offset = 0; - } - else { - if (!drmp3__on_seek(pMP3, 0x7FFFFFFF, drmp3_seek_origin_current)) { - return DRMP3_FALSE; - } - offset -= 0x7FFFFFFF; - } - } - - return DRMP3_TRUE; -} - - -static drmp3_uint32 drmp3_decode_next_frame_ex__callbacks(drmp3* pMP3, drmp3d_sample_t* pPCMFrames) -{ - drmp3_uint32 pcmFramesRead = 0; - - DRMP3_ASSERT(pMP3 != NULL); - DRMP3_ASSERT(pMP3->onRead != NULL); - - if (pMP3->atEnd) { - return 0; - } - - for (;;) { - drmp3dec_frame_info info; - - /* minimp3 recommends doing data submission in chunks of at least 16K. If we don't have at least 16K bytes available, get more. */ - if (pMP3->dataSize < DRMP3_MIN_DATA_CHUNK_SIZE) { - size_t bytesRead; - - /* First we need to move the data down. */ - if (pMP3->pData != NULL) { - DRMP3_MOVE_MEMORY(pMP3->pData, pMP3->pData + pMP3->dataConsumed, pMP3->dataSize); - } - - pMP3->dataConsumed = 0; - - if (pMP3->dataCapacity < DRMP3_DATA_CHUNK_SIZE) { - drmp3_uint8* pNewData; - size_t newDataCap; - - newDataCap = DRMP3_DATA_CHUNK_SIZE; - - pNewData = (drmp3_uint8*)drmp3__realloc_from_callbacks(pMP3->pData, newDataCap, pMP3->dataCapacity, &pMP3->allocationCallbacks); - if (pNewData == NULL) { - return 0; /* Out of memory. */ - } - - pMP3->pData = pNewData; - pMP3->dataCapacity = newDataCap; - } - - bytesRead = drmp3__on_read(pMP3, pMP3->pData + pMP3->dataSize, (pMP3->dataCapacity - pMP3->dataSize)); - if (bytesRead == 0) { - if (pMP3->dataSize == 0) { - pMP3->atEnd = DRMP3_TRUE; - return 0; /* No data. */ - } - } - - pMP3->dataSize += bytesRead; - } - - if (pMP3->dataSize > INT_MAX) { - pMP3->atEnd = DRMP3_TRUE; - return 0; /* File too big. */ - } - - DRMP3_ASSERT(pMP3->pData != NULL); - DRMP3_ASSERT(pMP3->dataCapacity > 0); - - pcmFramesRead = drmp3dec_decode_frame(&pMP3->decoder, pMP3->pData + pMP3->dataConsumed, (int)pMP3->dataSize, pPCMFrames, &info); /* <-- Safe size_t -> int conversion thanks to the check above. */ - - /* Consume the data. */ - if (info.frame_bytes > 0) { - pMP3->dataConsumed += (size_t)info.frame_bytes; - pMP3->dataSize -= (size_t)info.frame_bytes; - } - - /* pcmFramesRead will be equal to 0 if decoding failed. If it is zero and info.frame_bytes > 0 then we have successfully decoded the frame. */ - if (pcmFramesRead > 0) { - pcmFramesRead = drmp3_hdr_frame_samples(pMP3->decoder.header); - pMP3->pcmFramesConsumedInMP3Frame = 0; - pMP3->pcmFramesRemainingInMP3Frame = pcmFramesRead; - pMP3->mp3FrameChannels = info.channels; - pMP3->mp3FrameSampleRate = info.hz; - break; - } - else if (info.frame_bytes == 0) { - /* Need more data. minimp3 recommends doing data submission in 16K chunks. */ - size_t bytesRead; - - /* First we need to move the data down. */ - DRMP3_MOVE_MEMORY(pMP3->pData, pMP3->pData + pMP3->dataConsumed, pMP3->dataSize); - pMP3->dataConsumed = 0; - - if (pMP3->dataCapacity == pMP3->dataSize) { - /* No room. Expand. */ - drmp3_uint8* pNewData; - size_t newDataCap; - - newDataCap = pMP3->dataCapacity + DRMP3_DATA_CHUNK_SIZE; - - pNewData = (drmp3_uint8*)drmp3__realloc_from_callbacks(pMP3->pData, newDataCap, pMP3->dataCapacity, &pMP3->allocationCallbacks); - if (pNewData == NULL) { - return 0; /* Out of memory. */ - } - - pMP3->pData = pNewData; - pMP3->dataCapacity = newDataCap; - } - - /* Fill in a chunk. */ - bytesRead = drmp3__on_read(pMP3, pMP3->pData + pMP3->dataSize, (pMP3->dataCapacity - pMP3->dataSize)); - if (bytesRead == 0) { - pMP3->atEnd = DRMP3_TRUE; - return 0; /* Error reading more data. */ - } - - pMP3->dataSize += bytesRead; - } - }; - - return pcmFramesRead; -} - -static drmp3_uint32 drmp3_decode_next_frame_ex__memory(drmp3* pMP3, drmp3d_sample_t* pPCMFrames) -{ - drmp3_uint32 pcmFramesRead = 0; - drmp3dec_frame_info info; - - DRMP3_ASSERT(pMP3 != NULL); - DRMP3_ASSERT(pMP3->memory.pData != NULL); - - if (pMP3->atEnd) { - return 0; - } - - for (;;) { - pcmFramesRead = drmp3dec_decode_frame(&pMP3->decoder, pMP3->memory.pData + pMP3->memory.currentReadPos, (int)(pMP3->memory.dataSize - pMP3->memory.currentReadPos), pPCMFrames, &info); - if (pcmFramesRead > 0) { - pcmFramesRead = drmp3_hdr_frame_samples(pMP3->decoder.header); - pMP3->pcmFramesConsumedInMP3Frame = 0; - pMP3->pcmFramesRemainingInMP3Frame = pcmFramesRead; - pMP3->mp3FrameChannels = info.channels; - pMP3->mp3FrameSampleRate = info.hz; - break; - } - else if (info.frame_bytes > 0) { - /* No frames were read, but it looks like we skipped past one. Read the next MP3 frame. */ - pMP3->memory.currentReadPos += (size_t)info.frame_bytes; - } - else { - /* Nothing at all was read. Abort. */ - break; - } - } - - /* Consume the data. */ - pMP3->memory.currentReadPos += (size_t)info.frame_bytes; - - return pcmFramesRead; -} - -static drmp3_uint32 drmp3_decode_next_frame_ex(drmp3* pMP3, drmp3d_sample_t* pPCMFrames) -{ - if (pMP3->memory.pData != NULL && pMP3->memory.dataSize > 0) { - return drmp3_decode_next_frame_ex__memory(pMP3, pPCMFrames); - } - else { - return drmp3_decode_next_frame_ex__callbacks(pMP3, pPCMFrames); - } -} - -static drmp3_uint32 drmp3_decode_next_frame(drmp3* pMP3) -{ - DRMP3_ASSERT(pMP3 != NULL); - return drmp3_decode_next_frame_ex(pMP3, (drmp3d_sample_t*)pMP3->pcmFrames); -} - -#if 0 -static drmp3_uint32 drmp3_seek_next_frame(drmp3* pMP3) -{ - drmp3_uint32 pcmFrameCount; - - DRMP3_ASSERT(pMP3 != NULL); - - pcmFrameCount = drmp3_decode_next_frame_ex(pMP3, NULL); - if (pcmFrameCount == 0) { - return 0; - } - - /* We have essentially just skipped past the frame, so just set the remaining samples to 0. */ - pMP3->currentPCMFrame += pcmFrameCount; - pMP3->pcmFramesConsumedInMP3Frame = pcmFrameCount; - pMP3->pcmFramesRemainingInMP3Frame = 0; - - return pcmFrameCount; -} -#endif - -static drmp3_bool32 drmp3_init_internal(drmp3* pMP3, drmp3_read_proc onRead, drmp3_seek_proc onSeek, void* pUserData, const drmp3_allocation_callbacks* pAllocationCallbacks) -{ - DRMP3_ASSERT(pMP3 != NULL); - DRMP3_ASSERT(onRead != NULL); - - /* This function assumes the output object has already been reset to 0. Do not do that here, otherwise things will break. */ - drmp3dec_init(&pMP3->decoder); - - pMP3->onRead = onRead; - pMP3->onSeek = onSeek; - pMP3->pUserData = pUserData; - pMP3->allocationCallbacks = drmp3_copy_allocation_callbacks_or_defaults(pAllocationCallbacks); - - if (pMP3->allocationCallbacks.onFree == NULL || (pMP3->allocationCallbacks.onMalloc == NULL && pMP3->allocationCallbacks.onRealloc == NULL)) { - return DRMP3_FALSE; /* Invalid allocation callbacks. */ - } - - /* Decode the first frame to confirm that it is indeed a valid MP3 stream. */ - if (drmp3_decode_next_frame(pMP3) == 0) { - drmp3__free_from_callbacks(pMP3->pData, &pMP3->allocationCallbacks); /* The call above may have allocated memory. Need to make sure it's freed before aborting. */ - return DRMP3_FALSE; /* Not a valid MP3 stream. */ - } - - pMP3->channels = pMP3->mp3FrameChannels; - pMP3->sampleRate = pMP3->mp3FrameSampleRate; - - return DRMP3_TRUE; -} - -DRMP3_API drmp3_bool32 drmp3_init(drmp3* pMP3, drmp3_read_proc onRead, drmp3_seek_proc onSeek, void* pUserData, const drmp3_allocation_callbacks* pAllocationCallbacks) -{ - if (pMP3 == NULL || onRead == NULL) { - return DRMP3_FALSE; - } - - DRMP3_ZERO_OBJECT(pMP3); - return drmp3_init_internal(pMP3, onRead, onSeek, pUserData, pAllocationCallbacks); -} - - -static size_t drmp3__on_read_memory(void* pUserData, void* pBufferOut, size_t bytesToRead) -{ - drmp3* pMP3 = (drmp3*)pUserData; - size_t bytesRemaining; - - DRMP3_ASSERT(pMP3 != NULL); - DRMP3_ASSERT(pMP3->memory.dataSize >= pMP3->memory.currentReadPos); - - bytesRemaining = pMP3->memory.dataSize - pMP3->memory.currentReadPos; - if (bytesToRead > bytesRemaining) { - bytesToRead = bytesRemaining; - } - - if (bytesToRead > 0) { - DRMP3_COPY_MEMORY(pBufferOut, pMP3->memory.pData + pMP3->memory.currentReadPos, bytesToRead); - pMP3->memory.currentReadPos += bytesToRead; - } - - return bytesToRead; -} - -static drmp3_bool32 drmp3__on_seek_memory(void* pUserData, int byteOffset, drmp3_seek_origin origin) -{ - drmp3* pMP3 = (drmp3*)pUserData; - - DRMP3_ASSERT(pMP3 != NULL); - - if (origin == drmp3_seek_origin_current) { - if (byteOffset > 0) { - if (pMP3->memory.currentReadPos + byteOffset > pMP3->memory.dataSize) { - byteOffset = (int)(pMP3->memory.dataSize - pMP3->memory.currentReadPos); /* Trying to seek too far forward. */ - } - } - else { - if (pMP3->memory.currentReadPos < (size_t)-byteOffset) { - byteOffset = -(int)pMP3->memory.currentReadPos; /* Trying to seek too far backwards. */ - } - } - - /* This will never underflow thanks to the clamps above. */ - pMP3->memory.currentReadPos += byteOffset; - } - else { - if ((drmp3_uint32)byteOffset <= pMP3->memory.dataSize) { - pMP3->memory.currentReadPos = byteOffset; - } - else { - pMP3->memory.currentReadPos = pMP3->memory.dataSize; /* Trying to seek too far forward. */ - } - } - - return DRMP3_TRUE; -} - -DRMP3_API drmp3_bool32 drmp3_init_memory(drmp3* pMP3, const void* pData, size_t dataSize, const drmp3_allocation_callbacks* pAllocationCallbacks) -{ - if (pMP3 == NULL) { - return DRMP3_FALSE; - } - - DRMP3_ZERO_OBJECT(pMP3); - - if (pData == NULL || dataSize == 0) { - return DRMP3_FALSE; - } - - pMP3->memory.pData = (const drmp3_uint8*)pData; - pMP3->memory.dataSize = dataSize; - pMP3->memory.currentReadPos = 0; - - return drmp3_init_internal(pMP3, drmp3__on_read_memory, drmp3__on_seek_memory, pMP3, pAllocationCallbacks); -} - - -#ifndef DR_MP3_NO_STDIO -#include -#include /* For wcslen(), wcsrtombs() */ - -/* drmp3_result_from_errno() is only used inside DR_MP3_NO_STDIO for now. Move this out if it's ever used elsewhere. */ -#include -static drmp3_result drmp3_result_from_errno(int e) -{ - switch (e) - { - case 0: return DRMP3_SUCCESS; -#ifdef EPERM - case EPERM: return DRMP3_INVALID_OPERATION; -#endif -#ifdef ENOENT - case ENOENT: return DRMP3_DOES_NOT_EXIST; -#endif -#ifdef ESRCH - case ESRCH: return DRMP3_DOES_NOT_EXIST; -#endif -#ifdef EINTR - case EINTR: return DRMP3_INTERRUPT; -#endif -#ifdef EIO - case EIO: return DRMP3_IO_ERROR; -#endif -#ifdef ENXIO - case ENXIO: return DRMP3_DOES_NOT_EXIST; -#endif -#ifdef E2BIG - case E2BIG: return DRMP3_INVALID_ARGS; -#endif -#ifdef ENOEXEC - case ENOEXEC: return DRMP3_INVALID_FILE; -#endif -#ifdef EBADF - case EBADF: return DRMP3_INVALID_FILE; -#endif -#ifdef ECHILD - case ECHILD: return DRMP3_ERROR; -#endif -#ifdef EAGAIN - case EAGAIN: return DRMP3_UNAVAILABLE; -#endif -#ifdef ENOMEM - case ENOMEM: return DRMP3_OUT_OF_MEMORY; -#endif -#ifdef EACCES - case EACCES: return DRMP3_ACCESS_DENIED; -#endif -#ifdef EFAULT - case EFAULT: return DRMP3_BAD_ADDRESS; -#endif -#ifdef ENOTBLK - case ENOTBLK: return DRMP3_ERROR; -#endif -#ifdef EBUSY - case EBUSY: return DRMP3_BUSY; -#endif -#ifdef EEXIST - case EEXIST: return DRMP3_ALREADY_EXISTS; -#endif -#ifdef EXDEV - case EXDEV: return DRMP3_ERROR; -#endif -#ifdef ENODEV - case ENODEV: return DRMP3_DOES_NOT_EXIST; -#endif -#ifdef ENOTDIR - case ENOTDIR: return DRMP3_NOT_DIRECTORY; -#endif -#ifdef EISDIR - case EISDIR: return DRMP3_IS_DIRECTORY; -#endif -#ifdef EINVAL - case EINVAL: return DRMP3_INVALID_ARGS; -#endif -#ifdef ENFILE - case ENFILE: return DRMP3_TOO_MANY_OPEN_FILES; -#endif -#ifdef EMFILE - case EMFILE: return DRMP3_TOO_MANY_OPEN_FILES; -#endif -#ifdef ENOTTY - case ENOTTY: return DRMP3_INVALID_OPERATION; -#endif -#ifdef ETXTBSY - case ETXTBSY: return DRMP3_BUSY; -#endif -#ifdef EFBIG - case EFBIG: return DRMP3_TOO_BIG; -#endif -#ifdef ENOSPC - case ENOSPC: return DRMP3_NO_SPACE; -#endif -#ifdef ESPIPE - case ESPIPE: return DRMP3_BAD_SEEK; -#endif -#ifdef EROFS - case EROFS: return DRMP3_ACCESS_DENIED; -#endif -#ifdef EMLINK - case EMLINK: return DRMP3_TOO_MANY_LINKS; -#endif -#ifdef EPIPE - case EPIPE: return DRMP3_BAD_PIPE; -#endif -#ifdef EDOM - case EDOM: return DRMP3_OUT_OF_RANGE; -#endif -#ifdef ERANGE - case ERANGE: return DRMP3_OUT_OF_RANGE; -#endif -#ifdef EDEADLK - case EDEADLK: return DRMP3_DEADLOCK; -#endif -#ifdef ENAMETOOLONG - case ENAMETOOLONG: return DRMP3_PATH_TOO_LONG; -#endif -#ifdef ENOLCK - case ENOLCK: return DRMP3_ERROR; -#endif -#ifdef ENOSYS - case ENOSYS: return DRMP3_NOT_IMPLEMENTED; -#endif -#ifdef ENOTEMPTY - case ENOTEMPTY: return DRMP3_DIRECTORY_NOT_EMPTY; -#endif -#ifdef ELOOP - case ELOOP: return DRMP3_TOO_MANY_LINKS; -#endif -#ifdef ENOMSG - case ENOMSG: return DRMP3_NO_MESSAGE; -#endif -#ifdef EIDRM - case EIDRM: return DRMP3_ERROR; -#endif -#ifdef ECHRNG - case ECHRNG: return DRMP3_ERROR; -#endif -#ifdef EL2NSYNC - case EL2NSYNC: return DRMP3_ERROR; -#endif -#ifdef EL3HLT - case EL3HLT: return DRMP3_ERROR; -#endif -#ifdef EL3RST - case EL3RST: return DRMP3_ERROR; -#endif -#ifdef ELNRNG - case ELNRNG: return DRMP3_OUT_OF_RANGE; -#endif -#ifdef EUNATCH - case EUNATCH: return DRMP3_ERROR; -#endif -#ifdef ENOCSI - case ENOCSI: return DRMP3_ERROR; -#endif -#ifdef EL2HLT - case EL2HLT: return DRMP3_ERROR; -#endif -#ifdef EBADE - case EBADE: return DRMP3_ERROR; -#endif -#ifdef EBADR - case EBADR: return DRMP3_ERROR; -#endif -#ifdef EXFULL - case EXFULL: return DRMP3_ERROR; -#endif -#ifdef ENOANO - case ENOANO: return DRMP3_ERROR; -#endif -#ifdef EBADRQC - case EBADRQC: return DRMP3_ERROR; -#endif -#ifdef EBADSLT - case EBADSLT: return DRMP3_ERROR; -#endif -#ifdef EBFONT - case EBFONT: return DRMP3_INVALID_FILE; -#endif -#ifdef ENOSTR - case ENOSTR: return DRMP3_ERROR; -#endif -#ifdef ENODATA - case ENODATA: return DRMP3_NO_DATA_AVAILABLE; -#endif -#ifdef ETIME - case ETIME: return DRMP3_TIMEOUT; -#endif -#ifdef ENOSR - case ENOSR: return DRMP3_NO_DATA_AVAILABLE; -#endif -#ifdef ENONET - case ENONET: return DRMP3_NO_NETWORK; -#endif -#ifdef ENOPKG - case ENOPKG: return DRMP3_ERROR; -#endif -#ifdef EREMOTE - case EREMOTE: return DRMP3_ERROR; -#endif -#ifdef ENOLINK - case ENOLINK: return DRMP3_ERROR; -#endif -#ifdef EADV - case EADV: return DRMP3_ERROR; -#endif -#ifdef ESRMNT - case ESRMNT: return DRMP3_ERROR; -#endif -#ifdef ECOMM - case ECOMM: return DRMP3_ERROR; -#endif -#ifdef EPROTO - case EPROTO: return DRMP3_ERROR; -#endif -#ifdef EMULTIHOP - case EMULTIHOP: return DRMP3_ERROR; -#endif -#ifdef EDOTDOT - case EDOTDOT: return DRMP3_ERROR; -#endif -#ifdef EBADMSG - case EBADMSG: return DRMP3_BAD_MESSAGE; -#endif -#ifdef EOVERFLOW - case EOVERFLOW: return DRMP3_TOO_BIG; -#endif -#ifdef ENOTUNIQ - case ENOTUNIQ: return DRMP3_NOT_UNIQUE; -#endif -#ifdef EBADFD - case EBADFD: return DRMP3_ERROR; -#endif -#ifdef EREMCHG - case EREMCHG: return DRMP3_ERROR; -#endif -#ifdef ELIBACC - case ELIBACC: return DRMP3_ACCESS_DENIED; -#endif -#ifdef ELIBBAD - case ELIBBAD: return DRMP3_INVALID_FILE; -#endif -#ifdef ELIBSCN - case ELIBSCN: return DRMP3_INVALID_FILE; -#endif -#ifdef ELIBMAX - case ELIBMAX: return DRMP3_ERROR; -#endif -#ifdef ELIBEXEC - case ELIBEXEC: return DRMP3_ERROR; -#endif -#ifdef EILSEQ - case EILSEQ: return DRMP3_INVALID_DATA; -#endif -#ifdef ERESTART - case ERESTART: return DRMP3_ERROR; -#endif -#ifdef ESTRPIPE - case ESTRPIPE: return DRMP3_ERROR; -#endif -#ifdef EUSERS - case EUSERS: return DRMP3_ERROR; -#endif -#ifdef ENOTSOCK - case ENOTSOCK: return DRMP3_NOT_SOCKET; -#endif -#ifdef EDESTADDRREQ - case EDESTADDRREQ: return DRMP3_NO_ADDRESS; -#endif -#ifdef EMSGSIZE - case EMSGSIZE: return DRMP3_TOO_BIG; -#endif -#ifdef EPROTOTYPE - case EPROTOTYPE: return DRMP3_BAD_PROTOCOL; -#endif -#ifdef ENOPROTOOPT - case ENOPROTOOPT: return DRMP3_PROTOCOL_UNAVAILABLE; -#endif -#ifdef EPROTONOSUPPORT - case EPROTONOSUPPORT: return DRMP3_PROTOCOL_NOT_SUPPORTED; -#endif -#ifdef ESOCKTNOSUPPORT - case ESOCKTNOSUPPORT: return DRMP3_SOCKET_NOT_SUPPORTED; -#endif -#ifdef EOPNOTSUPP - case EOPNOTSUPP: return DRMP3_INVALID_OPERATION; -#endif -#ifdef EPFNOSUPPORT - case EPFNOSUPPORT: return DRMP3_PROTOCOL_FAMILY_NOT_SUPPORTED; -#endif -#ifdef EAFNOSUPPORT - case EAFNOSUPPORT: return DRMP3_ADDRESS_FAMILY_NOT_SUPPORTED; -#endif -#ifdef EADDRINUSE - case EADDRINUSE: return DRMP3_ALREADY_IN_USE; -#endif -#ifdef EADDRNOTAVAIL - case EADDRNOTAVAIL: return DRMP3_ERROR; -#endif -#ifdef ENETDOWN - case ENETDOWN: return DRMP3_NO_NETWORK; -#endif -#ifdef ENETUNREACH - case ENETUNREACH: return DRMP3_NO_NETWORK; -#endif -#ifdef ENETRESET - case ENETRESET: return DRMP3_NO_NETWORK; -#endif -#ifdef ECONNABORTED - case ECONNABORTED: return DRMP3_NO_NETWORK; -#endif -#ifdef ECONNRESET - case ECONNRESET: return DRMP3_CONNECTION_RESET; -#endif -#ifdef ENOBUFS - case ENOBUFS: return DRMP3_NO_SPACE; -#endif -#ifdef EISCONN - case EISCONN: return DRMP3_ALREADY_CONNECTED; -#endif -#ifdef ENOTCONN - case ENOTCONN: return DRMP3_NOT_CONNECTED; -#endif -#ifdef ESHUTDOWN - case ESHUTDOWN: return DRMP3_ERROR; -#endif -#ifdef ETOOMANYREFS - case ETOOMANYREFS: return DRMP3_ERROR; -#endif -#ifdef ETIMEDOUT - case ETIMEDOUT: return DRMP3_TIMEOUT; -#endif -#ifdef ECONNREFUSED - case ECONNREFUSED: return DRMP3_CONNECTION_REFUSED; -#endif -#ifdef EHOSTDOWN - case EHOSTDOWN: return DRMP3_NO_HOST; -#endif -#ifdef EHOSTUNREACH - case EHOSTUNREACH: return DRMP3_NO_HOST; -#endif -#ifdef EALREADY - case EALREADY: return DRMP3_IN_PROGRESS; -#endif -#ifdef EINPROGRESS - case EINPROGRESS: return DRMP3_IN_PROGRESS; -#endif -#ifdef ESTALE - case ESTALE: return DRMP3_INVALID_FILE; -#endif -#ifdef EUCLEAN - case EUCLEAN: return DRMP3_ERROR; -#endif -#ifdef ENOTNAM - case ENOTNAM: return DRMP3_ERROR; -#endif -#ifdef ENAVAIL - case ENAVAIL: return DRMP3_ERROR; -#endif -#ifdef EISNAM - case EISNAM: return DRMP3_ERROR; -#endif -#ifdef EREMOTEIO - case EREMOTEIO: return DRMP3_IO_ERROR; -#endif -#ifdef EDQUOT - case EDQUOT: return DRMP3_NO_SPACE; -#endif -#ifdef ENOMEDIUM - case ENOMEDIUM: return DRMP3_DOES_NOT_EXIST; -#endif -#ifdef EMEDIUMTYPE - case EMEDIUMTYPE: return DRMP3_ERROR; -#endif -#ifdef ECANCELED - case ECANCELED: return DRMP3_CANCELLED; -#endif -#ifdef ENOKEY - case ENOKEY: return DRMP3_ERROR; -#endif -#ifdef EKEYEXPIRED - case EKEYEXPIRED: return DRMP3_ERROR; -#endif -#ifdef EKEYREVOKED - case EKEYREVOKED: return DRMP3_ERROR; -#endif -#ifdef EKEYREJECTED - case EKEYREJECTED: return DRMP3_ERROR; -#endif -#ifdef EOWNERDEAD - case EOWNERDEAD: return DRMP3_ERROR; -#endif -#ifdef ENOTRECOVERABLE - case ENOTRECOVERABLE: return DRMP3_ERROR; -#endif -#ifdef ERFKILL - case ERFKILL: return DRMP3_ERROR; -#endif -#ifdef EHWPOISON - case EHWPOISON: return DRMP3_ERROR; -#endif - default: return DRMP3_ERROR; - } -} - -static drmp3_result drmp3_fopen(FILE** ppFile, const char* pFilePath, const char* pOpenMode) -{ -#if defined(_MSC_VER) && _MSC_VER >= 1400 - errno_t err; -#endif - - if (ppFile != NULL) { - *ppFile = NULL; /* Safety. */ - } - - if (pFilePath == NULL || pOpenMode == NULL || ppFile == NULL) { - return DRMP3_INVALID_ARGS; - } - -#if defined(_MSC_VER) && _MSC_VER >= 1400 - err = fopen_s(ppFile, pFilePath, pOpenMode); - if (err != 0) { - return drmp3_result_from_errno(err); - } -#else -#if defined(_WIN32) || defined(__APPLE__) - *ppFile = fopen(pFilePath, pOpenMode); -#else -#if defined(_FILE_OFFSET_BITS) && _FILE_OFFSET_BITS == 64 && defined(_LARGEFILE64_SOURCE) - *ppFile = fopen64(pFilePath, pOpenMode); -#else - * ppFile = fopen(pFilePath, pOpenMode); -#endif -#endif - if (*ppFile == NULL) { - drmp3_result result = drmp3_result_from_errno(errno); - if (result == DRMP3_SUCCESS) { - result = DRMP3_ERROR; /* Just a safety check to make sure we never ever return success when pFile == NULL. */ - } - - return result; - } -#endif - - return DRMP3_SUCCESS; -} - -/* -_wfopen() isn't always available in all compilation environments. - - * Windows only. - * MSVC seems to support it universally as far back as VC6 from what I can tell (haven't checked further back). - * MinGW-64 (both 32- and 64-bit) seems to support it. - * MinGW wraps it in !defined(__STRICT_ANSI__). - * OpenWatcom wraps it in !defined(_NO_EXT_KEYS). - -This can be reviewed as compatibility issues arise. The preference is to use _wfopen_s() and _wfopen() as opposed to the wcsrtombs() -fallback, so if you notice your compiler not detecting this properly I'm happy to look at adding support. -*/ -#if defined(_WIN32) -#if defined(_MSC_VER) || defined(__MINGW64__) || (!defined(__STRICT_ANSI__) && !defined(_NO_EXT_KEYS)) -#define DRMP3_HAS_WFOPEN -#endif -#endif - -static drmp3_result drmp3_wfopen(FILE** ppFile, const wchar_t* pFilePath, const wchar_t* pOpenMode, const drmp3_allocation_callbacks* pAllocationCallbacks) -{ - if (ppFile != NULL) { - *ppFile = NULL; /* Safety. */ - } - - if (pFilePath == NULL || pOpenMode == NULL || ppFile == NULL) { - return DRMP3_INVALID_ARGS; - } - -#if defined(DRMP3_HAS_WFOPEN) - { - /* Use _wfopen() on Windows. */ -#if defined(_MSC_VER) && _MSC_VER >= 1400 - errno_t err = _wfopen_s(ppFile, pFilePath, pOpenMode); - if (err != 0) { - return drmp3_result_from_errno(err); - } -#else - * ppFile = _wfopen(pFilePath, pOpenMode); - if (*ppFile == NULL) { - return drmp3_result_from_errno(errno); - } -#endif - (void)pAllocationCallbacks; - } -#else - /* - Use fopen() on anything other than Windows. Requires a conversion. This is annoying because fopen() is locale specific. The only real way I can - think of to do this is with wcsrtombs(). Note that wcstombs() is apparently not thread-safe because it uses a static global mbstate_t object for - maintaining state. I've checked this with -std=c89 and it works, but if somebody get's a compiler error I'll look into improving compatibility. - */ - { - mbstate_t mbs; - size_t lenMB; - const wchar_t* pFilePathTemp = pFilePath; - char* pFilePathMB = NULL; - char pOpenModeMB[32] = { 0 }; - - /* Get the length first. */ - DRMP3_ZERO_OBJECT(&mbs); - lenMB = wcsrtombs(NULL, &pFilePathTemp, 0, &mbs); - if (lenMB == (size_t)-1) { - return drmp3_result_from_errno(errno); - } - - pFilePathMB = (char*)drmp3__malloc_from_callbacks(lenMB + 1, pAllocationCallbacks); - if (pFilePathMB == NULL) { - return DRMP3_OUT_OF_MEMORY; - } - - pFilePathTemp = pFilePath; - DRMP3_ZERO_OBJECT(&mbs); - wcsrtombs(pFilePathMB, &pFilePathTemp, lenMB + 1, &mbs); - - /* The open mode should always consist of ASCII characters so we should be able to do a trivial conversion. */ - { - size_t i = 0; - for (;;) { - if (pOpenMode[i] == 0) { - pOpenModeMB[i] = '\0'; - break; - } - - pOpenModeMB[i] = (char)pOpenMode[i]; - i += 1; - } - } - - *ppFile = fopen(pFilePathMB, pOpenModeMB); - - drmp3__free_from_callbacks(pFilePathMB, pAllocationCallbacks); - } - - if (*ppFile == NULL) { - return DRMP3_ERROR; - } -#endif - - return DRMP3_SUCCESS; -} - - - -static size_t drmp3__on_read_stdio(void* pUserData, void* pBufferOut, size_t bytesToRead) -{ - return fread(pBufferOut, 1, bytesToRead, (FILE*)pUserData); -} - -static drmp3_bool32 drmp3__on_seek_stdio(void* pUserData, int offset, drmp3_seek_origin origin) -{ - return fseek((FILE*)pUserData, offset, (origin == drmp3_seek_origin_current) ? SEEK_CUR : SEEK_SET) == 0; -} - -DRMP3_API drmp3_bool32 drmp3_init_file(drmp3* pMP3, const char* pFilePath, const drmp3_allocation_callbacks* pAllocationCallbacks) -{ - drmp3_bool32 result; - FILE* pFile; - - if (drmp3_fopen(&pFile, pFilePath, "rb") != DRMP3_SUCCESS) { - return DRMP3_FALSE; - } - - result = drmp3_init(pMP3, drmp3__on_read_stdio, drmp3__on_seek_stdio, (void*)pFile, pAllocationCallbacks); - if (result != DRMP3_TRUE) { - fclose(pFile); - return result; - } - - return DRMP3_TRUE; -} - -DRMP3_API drmp3_bool32 drmp3_init_file_w(drmp3* pMP3, const wchar_t* pFilePath, const drmp3_allocation_callbacks* pAllocationCallbacks) -{ - drmp3_bool32 result; - FILE* pFile; - - if (drmp3_wfopen(&pFile, pFilePath, L"rb", pAllocationCallbacks) != DRMP3_SUCCESS) { - return DRMP3_FALSE; - } - - result = drmp3_init(pMP3, drmp3__on_read_stdio, drmp3__on_seek_stdio, (void*)pFile, pAllocationCallbacks); - if (result != DRMP3_TRUE) { - fclose(pFile); - return result; - } - - return DRMP3_TRUE; -} -#endif - -DRMP3_API void drmp3_uninit(drmp3* pMP3) -{ - if (pMP3 == NULL) { - return; - } - -#ifndef DR_MP3_NO_STDIO - if (pMP3->onRead == drmp3__on_read_stdio) { - FILE* pFile = (FILE*)pMP3->pUserData; - if (pFile != NULL) { - fclose(pFile); - pMP3->pUserData = NULL; /* Make sure the file handle is cleared to NULL to we don't attempt to close it a second time. */ - } - } -#endif - - drmp3__free_from_callbacks(pMP3->pData, &pMP3->allocationCallbacks); -} - -#if defined(DR_MP3_FLOAT_OUTPUT) -static void drmp3_f32_to_s16(drmp3_int16* dst, const float* src, drmp3_uint64 sampleCount) -{ - drmp3_uint64 i; - drmp3_uint64 i4; - drmp3_uint64 sampleCount4; - - /* Unrolled. */ - i = 0; - sampleCount4 = sampleCount >> 2; - for (i4 = 0; i4 < sampleCount4; i4 += 1) { - float x0 = src[i + 0]; - float x1 = src[i + 1]; - float x2 = src[i + 2]; - float x3 = src[i + 3]; - - x0 = ((x0 < -1) ? -1 : ((x0 > 1) ? 1 : x0)); - x1 = ((x1 < -1) ? -1 : ((x1 > 1) ? 1 : x1)); - x2 = ((x2 < -1) ? -1 : ((x2 > 1) ? 1 : x2)); - x3 = ((x3 < -1) ? -1 : ((x3 > 1) ? 1 : x3)); - - x0 = x0 * 32767.0f; - x1 = x1 * 32767.0f; - x2 = x2 * 32767.0f; - x3 = x3 * 32767.0f; - - dst[i + 0] = (drmp3_int16)x0; - dst[i + 1] = (drmp3_int16)x1; - dst[i + 2] = (drmp3_int16)x2; - dst[i + 3] = (drmp3_int16)x3; - - i += 4; - } - - /* Leftover. */ - for (; i < sampleCount; i += 1) { - float x = src[i]; - x = ((x < -1) ? -1 : ((x > 1) ? 1 : x)); /* clip */ - x = x * 32767.0f; /* -1..1 to -32767..32767 */ - - dst[i] = (drmp3_int16)x; - } -} -#endif - -#if !defined(DR_MP3_FLOAT_OUTPUT) -static void drmp3_s16_to_f32(float* dst, const drmp3_int16* src, drmp3_uint64 sampleCount) -{ - drmp3_uint64 i; - for (i = 0; i < sampleCount; i += 1) { - float x = (float)src[i]; - x = x * 0.000030517578125f; /* -32768..32767 to -1..0.999969482421875 */ - dst[i] = x; - } -} -#endif - - -static drmp3_uint64 drmp3_read_pcm_frames_raw(drmp3* pMP3, drmp3_uint64 framesToRead, void* pBufferOut) -{ - drmp3_uint64 totalFramesRead = 0; - - DRMP3_ASSERT(pMP3 != NULL); - DRMP3_ASSERT(pMP3->onRead != NULL); - - while (framesToRead > 0) { - drmp3_uint32 framesToConsume = (drmp3_uint32)DRMP3_MIN(pMP3->pcmFramesRemainingInMP3Frame, framesToRead); - if (pBufferOut != NULL) { -#if defined(DR_MP3_FLOAT_OUTPUT) - /* f32 */ - float* pFramesOutF32 = (float*)DRMP3_OFFSET_PTR(pBufferOut, sizeof(float) * totalFramesRead * pMP3->channels); - float* pFramesInF32 = (float*)DRMP3_OFFSET_PTR(&pMP3->pcmFrames[0], sizeof(float) * pMP3->pcmFramesConsumedInMP3Frame * pMP3->mp3FrameChannels); - DRMP3_COPY_MEMORY(pFramesOutF32, pFramesInF32, sizeof(float) * framesToConsume * pMP3->channels); -#else - /* s16 */ - drmp3_int16* pFramesOutS16 = (drmp3_int16*)DRMP3_OFFSET_PTR(pBufferOut, sizeof(drmp3_int16) * totalFramesRead * pMP3->channels); - drmp3_int16* pFramesInS16 = (drmp3_int16*)DRMP3_OFFSET_PTR(&pMP3->pcmFrames[0], sizeof(drmp3_int16) * pMP3->pcmFramesConsumedInMP3Frame * pMP3->mp3FrameChannels); - DRMP3_COPY_MEMORY(pFramesOutS16, pFramesInS16, sizeof(drmp3_int16) * framesToConsume * pMP3->channels); -#endif - } - - pMP3->currentPCMFrame += framesToConsume; - pMP3->pcmFramesConsumedInMP3Frame += framesToConsume; - pMP3->pcmFramesRemainingInMP3Frame -= framesToConsume; - totalFramesRead += framesToConsume; - framesToRead -= framesToConsume; - - if (framesToRead == 0) { - break; - } - - DRMP3_ASSERT(pMP3->pcmFramesRemainingInMP3Frame == 0); - - /* - At this point we have exhausted our in-memory buffer so we need to re-fill. Note that the sample rate may have changed - at this point which means we'll also need to update our sample rate conversion pipeline. - */ - if (drmp3_decode_next_frame(pMP3) == 0) { - break; - } - } - - return totalFramesRead; -} - - -DRMP3_API drmp3_uint64 drmp3_read_pcm_frames_f32(drmp3* pMP3, drmp3_uint64 framesToRead, float* pBufferOut) -{ - if (pMP3 == NULL || pMP3->onRead == NULL) { - return 0; - } - -#if defined(DR_MP3_FLOAT_OUTPUT) - /* Fast path. No conversion required. */ - return drmp3_read_pcm_frames_raw(pMP3, framesToRead, pBufferOut); -#else - /* Slow path. Convert from s16 to f32. */ - { - drmp3_int16 pTempS16[8192]; - drmp3_uint64 totalPCMFramesRead = 0; - - while (totalPCMFramesRead < framesToRead) { - drmp3_uint64 framesJustRead; - drmp3_uint64 framesRemaining = framesToRead - totalPCMFramesRead; - drmp3_uint64 framesToReadNow = DRMP3_COUNTOF(pTempS16) / pMP3->channels; - if (framesToReadNow > framesRemaining) { - framesToReadNow = framesRemaining; - } - - framesJustRead = drmp3_read_pcm_frames_raw(pMP3, framesToReadNow, pTempS16); - if (framesJustRead == 0) { - break; - } - - drmp3_s16_to_f32((float*)DRMP3_OFFSET_PTR(pBufferOut, sizeof(float) * totalPCMFramesRead * pMP3->channels), pTempS16, framesJustRead * pMP3->channels); - totalPCMFramesRead += framesJustRead; - } - - return totalPCMFramesRead; - } -#endif -} - -DRMP3_API drmp3_uint64 drmp3_read_pcm_frames_s16(drmp3* pMP3, drmp3_uint64 framesToRead, drmp3_int16* pBufferOut) -{ - if (pMP3 == NULL || pMP3->onRead == NULL) { - return 0; - } - -#if !defined(DR_MP3_FLOAT_OUTPUT) - /* Fast path. No conversion required. */ - return drmp3_read_pcm_frames_raw(pMP3, framesToRead, pBufferOut); -#else - /* Slow path. Convert from f32 to s16. */ - { - float pTempF32[4096]; - drmp3_uint64 totalPCMFramesRead = 0; - - while (totalPCMFramesRead < framesToRead) { - drmp3_uint64 framesJustRead; - drmp3_uint64 framesRemaining = framesToRead - totalPCMFramesRead; - drmp3_uint64 framesToReadNow = DRMP3_COUNTOF(pTempF32) / pMP3->channels; - if (framesToReadNow > framesRemaining) { - framesToReadNow = framesRemaining; - } - - framesJustRead = drmp3_read_pcm_frames_raw(pMP3, framesToReadNow, pTempF32); - if (framesJustRead == 0) { - break; - } - - drmp3_f32_to_s16((drmp3_int16*)DRMP3_OFFSET_PTR(pBufferOut, sizeof(drmp3_int16) * totalPCMFramesRead * pMP3->channels), pTempF32, framesJustRead * pMP3->channels); - totalPCMFramesRead += framesJustRead; - } - - return totalPCMFramesRead; - } -#endif -} - -static void drmp3_reset(drmp3* pMP3) -{ - DRMP3_ASSERT(pMP3 != NULL); - - pMP3->pcmFramesConsumedInMP3Frame = 0; - pMP3->pcmFramesRemainingInMP3Frame = 0; - pMP3->currentPCMFrame = 0; - pMP3->dataSize = 0; - pMP3->atEnd = DRMP3_FALSE; - drmp3dec_init(&pMP3->decoder); -} - -static drmp3_bool32 drmp3_seek_to_start_of_stream(drmp3* pMP3) -{ - DRMP3_ASSERT(pMP3 != NULL); - DRMP3_ASSERT(pMP3->onSeek != NULL); - - /* Seek to the start of the stream to begin with. */ - if (!drmp3__on_seek(pMP3, 0, drmp3_seek_origin_start)) { - return DRMP3_FALSE; - } - - /* Clear any cached data. */ - drmp3_reset(pMP3); - return DRMP3_TRUE; -} - - -static drmp3_bool32 drmp3_seek_forward_by_pcm_frames__brute_force(drmp3* pMP3, drmp3_uint64 frameOffset) -{ - drmp3_uint64 framesRead; - - /* - Just using a dumb read-and-discard for now. What would be nice is to parse only the header of the MP3 frame, and then skip over leading - frames without spending the time doing a full decode. I cannot see an easy way to do this in minimp3, however, so it may involve some - kind of manual processing. - */ -#if defined(DR_MP3_FLOAT_OUTPUT) - framesRead = drmp3_read_pcm_frames_f32(pMP3, frameOffset, NULL); -#else - framesRead = drmp3_read_pcm_frames_s16(pMP3, frameOffset, NULL); -#endif - if (framesRead != frameOffset) { - return DRMP3_FALSE; - } - - return DRMP3_TRUE; -} - -static drmp3_bool32 drmp3_seek_to_pcm_frame__brute_force(drmp3* pMP3, drmp3_uint64 frameIndex) -{ - DRMP3_ASSERT(pMP3 != NULL); - - if (frameIndex == pMP3->currentPCMFrame) { - return DRMP3_TRUE; - } - - /* - If we're moving foward we just read from where we're at. Otherwise we need to move back to the start of - the stream and read from the beginning. - */ - if (frameIndex < pMP3->currentPCMFrame) { - /* Moving backward. Move to the start of the stream and then move forward. */ - if (!drmp3_seek_to_start_of_stream(pMP3)) { - return DRMP3_FALSE; - } - } - - DRMP3_ASSERT(frameIndex >= pMP3->currentPCMFrame); - return drmp3_seek_forward_by_pcm_frames__brute_force(pMP3, (frameIndex - pMP3->currentPCMFrame)); -} - -static drmp3_bool32 drmp3_find_closest_seek_point(drmp3* pMP3, drmp3_uint64 frameIndex, drmp3_uint32* pSeekPointIndex) -{ - drmp3_uint32 iSeekPoint; - - DRMP3_ASSERT(pSeekPointIndex != NULL); - - *pSeekPointIndex = 0; - - if (frameIndex < pMP3->pSeekPoints[0].pcmFrameIndex) { - return DRMP3_FALSE; - } - - /* Linear search for simplicity to begin with while I'm getting this thing working. Once it's all working change this to a binary search. */ - for (iSeekPoint = 0; iSeekPoint < pMP3->seekPointCount; ++iSeekPoint) { - if (pMP3->pSeekPoints[iSeekPoint].pcmFrameIndex > frameIndex) { - break; /* Found it. */ - } - - *pSeekPointIndex = iSeekPoint; - } - - return DRMP3_TRUE; -} - -static drmp3_bool32 drmp3_seek_to_pcm_frame__seek_table(drmp3* pMP3, drmp3_uint64 frameIndex) -{ - drmp3_seek_point seekPoint; - drmp3_uint32 priorSeekPointIndex; - drmp3_uint16 iMP3Frame; - drmp3_uint64 leftoverFrames; - - DRMP3_ASSERT(pMP3 != NULL); - DRMP3_ASSERT(pMP3->pSeekPoints != NULL); - DRMP3_ASSERT(pMP3->seekPointCount > 0); - - /* If there is no prior seekpoint it means the target PCM frame comes before the first seek point. Just assume a seekpoint at the start of the file in this case. */ - if (drmp3_find_closest_seek_point(pMP3, frameIndex, &priorSeekPointIndex)) { - seekPoint = pMP3->pSeekPoints[priorSeekPointIndex]; - } - else { - seekPoint.seekPosInBytes = 0; - seekPoint.pcmFrameIndex = 0; - seekPoint.mp3FramesToDiscard = 0; - seekPoint.pcmFramesToDiscard = 0; - } - - /* First thing to do is seek to the first byte of the relevant MP3 frame. */ - if (!drmp3__on_seek_64(pMP3, seekPoint.seekPosInBytes, drmp3_seek_origin_start)) { - return DRMP3_FALSE; /* Failed to seek. */ - } - - /* Clear any cached data. */ - drmp3_reset(pMP3); - - /* Whole MP3 frames need to be discarded first. */ - for (iMP3Frame = 0; iMP3Frame < seekPoint.mp3FramesToDiscard; ++iMP3Frame) { - drmp3_uint32 pcmFramesRead; - drmp3d_sample_t* pPCMFrames; - - /* Pass in non-null for the last frame because we want to ensure the sample rate converter is preloaded correctly. */ - pPCMFrames = NULL; - if (iMP3Frame == seekPoint.mp3FramesToDiscard - 1) { - pPCMFrames = (drmp3d_sample_t*)pMP3->pcmFrames; - } - - /* We first need to decode the next frame. */ - pcmFramesRead = drmp3_decode_next_frame_ex(pMP3, pPCMFrames); - if (pcmFramesRead == 0) { - return DRMP3_FALSE; - } - } - - /* We seeked to an MP3 frame in the raw stream so we need to make sure the current PCM frame is set correctly. */ - pMP3->currentPCMFrame = seekPoint.pcmFrameIndex - seekPoint.pcmFramesToDiscard; - - /* - Now at this point we can follow the same process as the brute force technique where we just skip over unnecessary MP3 frames and then - read-and-discard at least 2 whole MP3 frames. - */ - leftoverFrames = frameIndex - pMP3->currentPCMFrame; - return drmp3_seek_forward_by_pcm_frames__brute_force(pMP3, leftoverFrames); -} - -DRMP3_API drmp3_bool32 drmp3_seek_to_pcm_frame(drmp3* pMP3, drmp3_uint64 frameIndex) -{ - if (pMP3 == NULL || pMP3->onSeek == NULL) { - return DRMP3_FALSE; - } - - if (frameIndex == 0) { - return drmp3_seek_to_start_of_stream(pMP3); - } - - /* Use the seek table if we have one. */ - if (pMP3->pSeekPoints != NULL && pMP3->seekPointCount > 0) { - return drmp3_seek_to_pcm_frame__seek_table(pMP3, frameIndex); - } - else { - return drmp3_seek_to_pcm_frame__brute_force(pMP3, frameIndex); - } -} - -DRMP3_API drmp3_bool32 drmp3_get_mp3_and_pcm_frame_count(drmp3* pMP3, drmp3_uint64* pMP3FrameCount, drmp3_uint64* pPCMFrameCount) -{ - drmp3_uint64 currentPCMFrame; - drmp3_uint64 totalPCMFrameCount; - drmp3_uint64 totalMP3FrameCount; - - if (pMP3 == NULL) { - return DRMP3_FALSE; - } - - /* - The way this works is we move back to the start of the stream, iterate over each MP3 frame and calculate the frame count based - on our output sample rate, the seek back to the PCM frame we were sitting on before calling this function. - */ - - /* The stream must support seeking for this to work. */ - if (pMP3->onSeek == NULL) { - return DRMP3_FALSE; - } - - /* We'll need to seek back to where we were, so grab the PCM frame we're currently sitting on so we can restore later. */ - currentPCMFrame = pMP3->currentPCMFrame; - - if (!drmp3_seek_to_start_of_stream(pMP3)) { - return DRMP3_FALSE; - } - - totalPCMFrameCount = 0; - totalMP3FrameCount = 0; - - for (;;) { - drmp3_uint32 pcmFramesInCurrentMP3Frame; - - pcmFramesInCurrentMP3Frame = drmp3_decode_next_frame_ex(pMP3, NULL); - if (pcmFramesInCurrentMP3Frame == 0) { - break; - } - - totalPCMFrameCount += pcmFramesInCurrentMP3Frame; - totalMP3FrameCount += 1; - } - - /* Finally, we need to seek back to where we were. */ - if (!drmp3_seek_to_start_of_stream(pMP3)) { - return DRMP3_FALSE; - } - - if (!drmp3_seek_to_pcm_frame(pMP3, currentPCMFrame)) { - return DRMP3_FALSE; - } - - if (pMP3FrameCount != NULL) { - *pMP3FrameCount = totalMP3FrameCount; - } - if (pPCMFrameCount != NULL) { - *pPCMFrameCount = totalPCMFrameCount; - } - - return DRMP3_TRUE; -} - -DRMP3_API drmp3_uint64 drmp3_get_pcm_frame_count(drmp3* pMP3) -{ - drmp3_uint64 totalPCMFrameCount; - if (!drmp3_get_mp3_and_pcm_frame_count(pMP3, NULL, &totalPCMFrameCount)) { - return 0; - } - - return totalPCMFrameCount; -} - -DRMP3_API drmp3_uint64 drmp3_get_mp3_frame_count(drmp3* pMP3) -{ - drmp3_uint64 totalMP3FrameCount; - if (!drmp3_get_mp3_and_pcm_frame_count(pMP3, &totalMP3FrameCount, NULL)) { - return 0; - } - - return totalMP3FrameCount; -} - -static void drmp3__accumulate_running_pcm_frame_count(drmp3* pMP3, drmp3_uint32 pcmFrameCountIn, drmp3_uint64* pRunningPCMFrameCount, float* pRunningPCMFrameCountFractionalPart) -{ - float srcRatio; - float pcmFrameCountOutF; - drmp3_uint32 pcmFrameCountOut; - - srcRatio = (float)pMP3->mp3FrameSampleRate / (float)pMP3->sampleRate; - DRMP3_ASSERT(srcRatio > 0); - - pcmFrameCountOutF = *pRunningPCMFrameCountFractionalPart + (pcmFrameCountIn / srcRatio); - pcmFrameCountOut = (drmp3_uint32)pcmFrameCountOutF; - *pRunningPCMFrameCountFractionalPart = pcmFrameCountOutF - pcmFrameCountOut; - *pRunningPCMFrameCount += pcmFrameCountOut; -} - -typedef struct -{ - drmp3_uint64 bytePos; - drmp3_uint64 pcmFrameIndex; /* <-- After sample rate conversion. */ -} drmp3__seeking_mp3_frame_info; - -DRMP3_API drmp3_bool32 drmp3_calculate_seek_points(drmp3* pMP3, drmp3_uint32* pSeekPointCount, drmp3_seek_point* pSeekPoints) -{ - drmp3_uint32 seekPointCount; - drmp3_uint64 currentPCMFrame; - drmp3_uint64 totalMP3FrameCount; - drmp3_uint64 totalPCMFrameCount; - - if (pMP3 == NULL || pSeekPointCount == NULL || pSeekPoints == NULL) { - return DRMP3_FALSE; /* Invalid args. */ - } - - seekPointCount = *pSeekPointCount; - if (seekPointCount == 0) { - return DRMP3_FALSE; /* The client has requested no seek points. Consider this to be invalid arguments since the client has probably not intended this. */ - } - - /* We'll need to seek back to the current sample after calculating the seekpoints so we need to go ahead and grab the current location at the top. */ - currentPCMFrame = pMP3->currentPCMFrame; - - /* We never do more than the total number of MP3 frames and we limit it to 32-bits. */ - if (!drmp3_get_mp3_and_pcm_frame_count(pMP3, &totalMP3FrameCount, &totalPCMFrameCount)) { - return DRMP3_FALSE; - } - - /* If there's less than DRMP3_SEEK_LEADING_MP3_FRAMES+1 frames we just report 1 seek point which will be the very start of the stream. */ - if (totalMP3FrameCount < DRMP3_SEEK_LEADING_MP3_FRAMES + 1) { - seekPointCount = 1; - pSeekPoints[0].seekPosInBytes = 0; - pSeekPoints[0].pcmFrameIndex = 0; - pSeekPoints[0].mp3FramesToDiscard = 0; - pSeekPoints[0].pcmFramesToDiscard = 0; - } - else { - drmp3_uint64 pcmFramesBetweenSeekPoints; - drmp3__seeking_mp3_frame_info mp3FrameInfo[DRMP3_SEEK_LEADING_MP3_FRAMES + 1]; - drmp3_uint64 runningPCMFrameCount = 0; - float runningPCMFrameCountFractionalPart = 0; - drmp3_uint64 nextTargetPCMFrame; - drmp3_uint32 iMP3Frame; - drmp3_uint32 iSeekPoint; - - if (seekPointCount > totalMP3FrameCount - 1) { - seekPointCount = (drmp3_uint32)totalMP3FrameCount - 1; - } - - pcmFramesBetweenSeekPoints = totalPCMFrameCount / (seekPointCount + 1); - - /* - Here is where we actually calculate the seek points. We need to start by moving the start of the stream. We then enumerate over each - MP3 frame. - */ - if (!drmp3_seek_to_start_of_stream(pMP3)) { - return DRMP3_FALSE; - } - - /* - We need to cache the byte positions of the previous MP3 frames. As a new MP3 frame is iterated, we cycle the byte positions in this - array. The value in the first item in this array is the byte position that will be reported in the next seek point. - */ - - /* We need to initialize the array of MP3 byte positions for the leading MP3 frames. */ - for (iMP3Frame = 0; iMP3Frame < DRMP3_SEEK_LEADING_MP3_FRAMES + 1; ++iMP3Frame) { - drmp3_uint32 pcmFramesInCurrentMP3FrameIn; - - /* The byte position of the next frame will be the stream's cursor position, minus whatever is sitting in the buffer. */ - DRMP3_ASSERT(pMP3->streamCursor >= pMP3->dataSize); - mp3FrameInfo[iMP3Frame].bytePos = pMP3->streamCursor - pMP3->dataSize; - mp3FrameInfo[iMP3Frame].pcmFrameIndex = runningPCMFrameCount; - - /* We need to get information about this frame so we can know how many samples it contained. */ - pcmFramesInCurrentMP3FrameIn = drmp3_decode_next_frame_ex(pMP3, NULL); - if (pcmFramesInCurrentMP3FrameIn == 0) { - return DRMP3_FALSE; /* This should never happen. */ - } - - drmp3__accumulate_running_pcm_frame_count(pMP3, pcmFramesInCurrentMP3FrameIn, &runningPCMFrameCount, &runningPCMFrameCountFractionalPart); - } - - /* - At this point we will have extracted the byte positions of the leading MP3 frames. We can now start iterating over each seek point and - calculate them. - */ - nextTargetPCMFrame = 0; - for (iSeekPoint = 0; iSeekPoint < seekPointCount; ++iSeekPoint) { - nextTargetPCMFrame += pcmFramesBetweenSeekPoints; - - for (;;) { - if (nextTargetPCMFrame < runningPCMFrameCount) { - /* The next seek point is in the current MP3 frame. */ - pSeekPoints[iSeekPoint].seekPosInBytes = mp3FrameInfo[0].bytePos; - pSeekPoints[iSeekPoint].pcmFrameIndex = nextTargetPCMFrame; - pSeekPoints[iSeekPoint].mp3FramesToDiscard = DRMP3_SEEK_LEADING_MP3_FRAMES; - pSeekPoints[iSeekPoint].pcmFramesToDiscard = (drmp3_uint16)(nextTargetPCMFrame - mp3FrameInfo[DRMP3_SEEK_LEADING_MP3_FRAMES - 1].pcmFrameIndex); - break; - } - else { - size_t i; - drmp3_uint32 pcmFramesInCurrentMP3FrameIn; - - /* - The next seek point is not in the current MP3 frame, so continue on to the next one. The first thing to do is cycle the cached - MP3 frame info. - */ - for (i = 0; i < DRMP3_COUNTOF(mp3FrameInfo) - 1; ++i) { - mp3FrameInfo[i] = mp3FrameInfo[i + 1]; - } - - /* Cache previous MP3 frame info. */ - mp3FrameInfo[DRMP3_COUNTOF(mp3FrameInfo) - 1].bytePos = pMP3->streamCursor - pMP3->dataSize; - mp3FrameInfo[DRMP3_COUNTOF(mp3FrameInfo) - 1].pcmFrameIndex = runningPCMFrameCount; - - /* - Go to the next MP3 frame. This shouldn't ever fail, but just in case it does we just set the seek point and break. If it happens, it - should only ever do it for the last seek point. - */ - pcmFramesInCurrentMP3FrameIn = drmp3_decode_next_frame_ex(pMP3, NULL); - if (pcmFramesInCurrentMP3FrameIn == 0) { - pSeekPoints[iSeekPoint].seekPosInBytes = mp3FrameInfo[0].bytePos; - pSeekPoints[iSeekPoint].pcmFrameIndex = nextTargetPCMFrame; - pSeekPoints[iSeekPoint].mp3FramesToDiscard = DRMP3_SEEK_LEADING_MP3_FRAMES; - pSeekPoints[iSeekPoint].pcmFramesToDiscard = (drmp3_uint16)(nextTargetPCMFrame - mp3FrameInfo[DRMP3_SEEK_LEADING_MP3_FRAMES - 1].pcmFrameIndex); - break; - } - - drmp3__accumulate_running_pcm_frame_count(pMP3, pcmFramesInCurrentMP3FrameIn, &runningPCMFrameCount, &runningPCMFrameCountFractionalPart); - } - } - } - - /* Finally, we need to seek back to where we were. */ - if (!drmp3_seek_to_start_of_stream(pMP3)) { - return DRMP3_FALSE; - } - if (!drmp3_seek_to_pcm_frame(pMP3, currentPCMFrame)) { - return DRMP3_FALSE; - } - } - - *pSeekPointCount = seekPointCount; - return DRMP3_TRUE; -} - -DRMP3_API drmp3_bool32 drmp3_bind_seek_table(drmp3* pMP3, drmp3_uint32 seekPointCount, drmp3_seek_point* pSeekPoints) -{ - if (pMP3 == NULL) { - return DRMP3_FALSE; - } - - if (seekPointCount == 0 || pSeekPoints == NULL) { - /* Unbinding. */ - pMP3->seekPointCount = 0; - pMP3->pSeekPoints = NULL; - } - else { - /* Binding. */ - pMP3->seekPointCount = seekPointCount; - pMP3->pSeekPoints = pSeekPoints; - } - - return DRMP3_TRUE; -} - - -static float* drmp3__full_read_and_close_f32(drmp3* pMP3, drmp3_config* pConfig, drmp3_uint64* pTotalFrameCount) -{ - drmp3_uint64 totalFramesRead = 0; - drmp3_uint64 framesCapacity = 0; - float* pFrames = NULL; - float temp[4096]; - - DRMP3_ASSERT(pMP3 != NULL); - - for (;;) { - drmp3_uint64 framesToReadRightNow = DRMP3_COUNTOF(temp) / pMP3->channels; - drmp3_uint64 framesJustRead = drmp3_read_pcm_frames_f32(pMP3, framesToReadRightNow, temp); - if (framesJustRead == 0) { - break; - } - - /* Reallocate the output buffer if there's not enough room. */ - if (framesCapacity < totalFramesRead + framesJustRead) { - drmp3_uint64 oldFramesBufferSize; - drmp3_uint64 newFramesBufferSize; - drmp3_uint64 newFramesCap; - float* pNewFrames; - - newFramesCap = framesCapacity * 2; - if (newFramesCap < totalFramesRead + framesJustRead) { - newFramesCap = totalFramesRead + framesJustRead; - } - - oldFramesBufferSize = framesCapacity * pMP3->channels * sizeof(float); - newFramesBufferSize = newFramesCap * pMP3->channels * sizeof(float); - if (newFramesBufferSize > (drmp3_uint64)DRMP3_SIZE_MAX) { - break; - } - - pNewFrames = (float*)drmp3__realloc_from_callbacks(pFrames, (size_t)newFramesBufferSize, (size_t)oldFramesBufferSize, &pMP3->allocationCallbacks); - if (pNewFrames == NULL) { - drmp3__free_from_callbacks(pFrames, &pMP3->allocationCallbacks); - break; - } - - pFrames = pNewFrames; - framesCapacity = newFramesCap; - } - - DRMP3_COPY_MEMORY(pFrames + totalFramesRead * pMP3->channels, temp, (size_t)(framesJustRead * pMP3->channels * sizeof(float))); - totalFramesRead += framesJustRead; - - /* If the number of frames we asked for is less that what we actually read it means we've reached the end. */ - if (framesJustRead != framesToReadRightNow) { - break; - } - } - - if (pConfig != NULL) { - pConfig->channels = pMP3->channels; - pConfig->sampleRate = pMP3->sampleRate; - } - - drmp3_uninit(pMP3); - - if (pTotalFrameCount) { - *pTotalFrameCount = totalFramesRead; - } - - return pFrames; -} - -static drmp3_int16* drmp3__full_read_and_close_s16(drmp3* pMP3, drmp3_config* pConfig, drmp3_uint64* pTotalFrameCount) -{ - drmp3_uint64 totalFramesRead = 0; - drmp3_uint64 framesCapacity = 0; - drmp3_int16* pFrames = NULL; - drmp3_int16 temp[4096]; - - DRMP3_ASSERT(pMP3 != NULL); - - for (;;) { - drmp3_uint64 framesToReadRightNow = DRMP3_COUNTOF(temp) / pMP3->channels; - drmp3_uint64 framesJustRead = drmp3_read_pcm_frames_s16(pMP3, framesToReadRightNow, temp); - if (framesJustRead == 0) { - break; - } - - /* Reallocate the output buffer if there's not enough room. */ - if (framesCapacity < totalFramesRead + framesJustRead) { - drmp3_uint64 newFramesBufferSize; - drmp3_uint64 oldFramesBufferSize; - drmp3_uint64 newFramesCap; - drmp3_int16* pNewFrames; - - newFramesCap = framesCapacity * 2; - if (newFramesCap < totalFramesRead + framesJustRead) { - newFramesCap = totalFramesRead + framesJustRead; - } - - oldFramesBufferSize = framesCapacity * pMP3->channels * sizeof(drmp3_int16); - newFramesBufferSize = newFramesCap * pMP3->channels * sizeof(drmp3_int16); - if (newFramesBufferSize > (drmp3_uint64)DRMP3_SIZE_MAX) { - break; - } - - pNewFrames = (drmp3_int16*)drmp3__realloc_from_callbacks(pFrames, (size_t)newFramesBufferSize, (size_t)oldFramesBufferSize, &pMP3->allocationCallbacks); - if (pNewFrames == NULL) { - drmp3__free_from_callbacks(pFrames, &pMP3->allocationCallbacks); - break; - } - - pFrames = pNewFrames; - framesCapacity = newFramesCap; - } - - DRMP3_COPY_MEMORY(pFrames + totalFramesRead * pMP3->channels, temp, (size_t)(framesJustRead * pMP3->channels * sizeof(drmp3_int16))); - totalFramesRead += framesJustRead; - - /* If the number of frames we asked for is less that what we actually read it means we've reached the end. */ - if (framesJustRead != framesToReadRightNow) { - break; - } - } - - if (pConfig != NULL) { - pConfig->channels = pMP3->channels; - pConfig->sampleRate = pMP3->sampleRate; - } - - drmp3_uninit(pMP3); - - if (pTotalFrameCount) { - *pTotalFrameCount = totalFramesRead; - } - - return pFrames; -} - - -DRMP3_API float* drmp3_open_and_read_pcm_frames_f32(drmp3_read_proc onRead, drmp3_seek_proc onSeek, void* pUserData, drmp3_config* pConfig, drmp3_uint64* pTotalFrameCount, const drmp3_allocation_callbacks* pAllocationCallbacks) -{ - drmp3 mp3; - if (!drmp3_init(&mp3, onRead, onSeek, pUserData, pAllocationCallbacks)) { - return NULL; - } - - return drmp3__full_read_and_close_f32(&mp3, pConfig, pTotalFrameCount); -} - -DRMP3_API drmp3_int16* drmp3_open_and_read_pcm_frames_s16(drmp3_read_proc onRead, drmp3_seek_proc onSeek, void* pUserData, drmp3_config* pConfig, drmp3_uint64* pTotalFrameCount, const drmp3_allocation_callbacks* pAllocationCallbacks) -{ - drmp3 mp3; - if (!drmp3_init(&mp3, onRead, onSeek, pUserData, pAllocationCallbacks)) { - return NULL; - } - - return drmp3__full_read_and_close_s16(&mp3, pConfig, pTotalFrameCount); -} - - -DRMP3_API float* drmp3_open_memory_and_read_pcm_frames_f32(const void* pData, size_t dataSize, drmp3_config* pConfig, drmp3_uint64* pTotalFrameCount, const drmp3_allocation_callbacks* pAllocationCallbacks) -{ - drmp3 mp3; - if (!drmp3_init_memory(&mp3, pData, dataSize, pAllocationCallbacks)) { - return NULL; - } - - return drmp3__full_read_and_close_f32(&mp3, pConfig, pTotalFrameCount); -} - -DRMP3_API drmp3_int16* drmp3_open_memory_and_read_pcm_frames_s16(const void* pData, size_t dataSize, drmp3_config* pConfig, drmp3_uint64* pTotalFrameCount, const drmp3_allocation_callbacks* pAllocationCallbacks) -{ - drmp3 mp3; - if (!drmp3_init_memory(&mp3, pData, dataSize, pAllocationCallbacks)) { - return NULL; - } - - return drmp3__full_read_and_close_s16(&mp3, pConfig, pTotalFrameCount); -} - - -#ifndef DR_MP3_NO_STDIO -DRMP3_API float* drmp3_open_file_and_read_pcm_frames_f32(const char* filePath, drmp3_config* pConfig, drmp3_uint64* pTotalFrameCount, const drmp3_allocation_callbacks* pAllocationCallbacks) -{ - drmp3 mp3; - if (!drmp3_init_file(&mp3, filePath, pAllocationCallbacks)) { - return NULL; - } - - return drmp3__full_read_and_close_f32(&mp3, pConfig, pTotalFrameCount); -} - -DRMP3_API drmp3_int16* drmp3_open_file_and_read_pcm_frames_s16(const char* filePath, drmp3_config* pConfig, drmp3_uint64* pTotalFrameCount, const drmp3_allocation_callbacks* pAllocationCallbacks) -{ - drmp3 mp3; - if (!drmp3_init_file(&mp3, filePath, pAllocationCallbacks)) { - return NULL; - } - - return drmp3__full_read_and_close_s16(&mp3, pConfig, pTotalFrameCount); -} -#endif - -DRMP3_API void* drmp3_malloc(size_t sz, const drmp3_allocation_callbacks* pAllocationCallbacks) -{ - if (pAllocationCallbacks != NULL) { - return drmp3__malloc_from_callbacks(sz, pAllocationCallbacks); - } - else { - return drmp3__malloc_default(sz, NULL); - } -} - -DRMP3_API void drmp3_free(void* p, const drmp3_allocation_callbacks* pAllocationCallbacks) -{ - if (pAllocationCallbacks != NULL) { - drmp3__free_from_callbacks(p, pAllocationCallbacks); - } - else { - drmp3__free_default(p, NULL); - } -} - -#endif /* dr_mp3_c */ -#endif /*DR_MP3_IMPLEMENTATION*/ - -/* -DIFFERENCES BETWEEN minimp3 AND dr_mp3 -====================================== -- First, keep in mind that minimp3 (https://github.com/lieff/minimp3) is where all the real work was done. All of the - code relating to the actual decoding remains mostly unmodified, apart from some namespacing changes. -- dr_mp3 adds a pulling style API which allows you to deliver raw data via callbacks. So, rather than pushing data - to the decoder, the decoder _pulls_ data from your callbacks. -- In addition to callbacks, a decoder can be initialized from a block of memory and a file. -- The dr_mp3 pull API reads PCM frames rather than whole MP3 frames. -- dr_mp3 adds convenience APIs for opening and decoding entire files in one go. -- dr_mp3 is fully namespaced, including the implementation section, which is more suitable when compiling projects - as a single translation unit (aka unity builds). At the time of writing this, a unity build is not possible when - using minimp3 in conjunction with stb_vorbis. dr_mp3 addresses this. -*/ - -/* -RELEASE NOTES - v0.5.0 -======================= -Version 0.5.0 has breaking API changes. - -Improved Client-Defined Memory Allocation ------------------------------------------ -The main change with this release is the addition of a more flexible way of implementing custom memory allocation routines. The -existing system of DRMP3_MALLOC, DRMP3_REALLOC and DRMP3_FREE are still in place and will be used by default when no custom -allocation callbacks are specified. - -To use the new system, you pass in a pointer to a drmp3_allocation_callbacks object to drmp3_init() and family, like this: - - void* my_malloc(size_t sz, void* pUserData) - { - return malloc(sz); - } - void* my_realloc(void* p, size_t sz, void* pUserData) - { - return realloc(p, sz); - } - void my_free(void* p, void* pUserData) - { - free(p); - } - - ... - - drmp3_allocation_callbacks allocationCallbacks; - allocationCallbacks.pUserData = &myData; - allocationCallbacks.onMalloc = my_malloc; - allocationCallbacks.onRealloc = my_realloc; - allocationCallbacks.onFree = my_free; - drmp3_init_file(&mp3, "my_file.mp3", NULL, &allocationCallbacks); - -The advantage of this new system is that it allows you to specify user data which will be passed in to the allocation routines. - -Passing in null for the allocation callbacks object will cause dr_mp3 to use defaults which is the same as DRMP3_MALLOC, -DRMP3_REALLOC and DRMP3_FREE and the equivalent of how it worked in previous versions. - -Every API that opens a drmp3 object now takes this extra parameter. These include the following: - - drmp3_init() - drmp3_init_file() - drmp3_init_memory() - drmp3_open_and_read_pcm_frames_f32() - drmp3_open_and_read_pcm_frames_s16() - drmp3_open_memory_and_read_pcm_frames_f32() - drmp3_open_memory_and_read_pcm_frames_s16() - drmp3_open_file_and_read_pcm_frames_f32() - drmp3_open_file_and_read_pcm_frames_s16() - -Renamed APIs ------------- -The following APIs have been renamed for consistency with other dr_* libraries and to make it clear that they return PCM frame -counts rather than sample counts. - - drmp3_open_and_read_f32() -> drmp3_open_and_read_pcm_frames_f32() - drmp3_open_and_read_s16() -> drmp3_open_and_read_pcm_frames_s16() - drmp3_open_memory_and_read_f32() -> drmp3_open_memory_and_read_pcm_frames_f32() - drmp3_open_memory_and_read_s16() -> drmp3_open_memory_and_read_pcm_frames_s16() - drmp3_open_file_and_read_f32() -> drmp3_open_file_and_read_pcm_frames_f32() - drmp3_open_file_and_read_s16() -> drmp3_open_file_and_read_pcm_frames_s16() -*/ - -/* -REVISION HISTORY -================ -v0.6.33 - 2022-04-10 - - Fix compilation error with the MSVC ARM64 build. - - Fix compilation error on older versions of GCC. - - Remove some unused functions. - -v0.6.32 - 2021-12-11 - - Fix a warning with Clang. - -v0.6.31 - 2021-08-22 - - Fix a bug when loading from memory. - -v0.6.30 - 2021-08-16 - - Silence some warnings. - - Replace memory operations with DRMP3_* macros. - -v0.6.29 - 2021-08-08 - - Bring up to date with minimp3. - -v0.6.28 - 2021-07-31 - - Fix platform detection for ARM64. - - Fix a compilation error with C89. - -v0.6.27 - 2021-02-21 - - Fix a warning due to referencing _MSC_VER when it is undefined. - -v0.6.26 - 2021-01-31 - - Bring up to date with minimp3. - -v0.6.25 - 2020-12-26 - - Remove DRMP3_DEFAULT_CHANNELS and DRMP3_DEFAULT_SAMPLE_RATE which are leftovers from some removed APIs. - -v0.6.24 - 2020-12-07 - - Fix a typo in version date for 0.6.23. - -v0.6.23 - 2020-12-03 - - Fix an error where a file can be closed twice when initialization of the decoder fails. - -v0.6.22 - 2020-12-02 - - Fix an error where it's possible for a file handle to be left open when initialization of the decoder fails. - -v0.6.21 - 2020-11-28 - - Bring up to date with minimp3. - -v0.6.20 - 2020-11-21 - - Fix compilation with OpenWatcom. - -v0.6.19 - 2020-11-13 - - Minor code clean up. - -v0.6.18 - 2020-11-01 - - Improve compiler support for older versions of GCC. - -v0.6.17 - 2020-09-28 - - Bring up to date with minimp3. - -v0.6.16 - 2020-08-02 - - Simplify sized types. - -v0.6.15 - 2020-07-25 - - Fix a compilation warning. - -v0.6.14 - 2020-07-23 - - Fix undefined behaviour with memmove(). - -v0.6.13 - 2020-07-06 - - Fix a bug when converting from s16 to f32 in drmp3_read_pcm_frames_f32(). - -v0.6.12 - 2020-06-23 - - Add include guard for the implementation section. - -v0.6.11 - 2020-05-26 - - Fix use of uninitialized variable error. - -v0.6.10 - 2020-05-16 - - Add compile-time and run-time version querying. - - DRMP3_VERSION_MINOR - - DRMP3_VERSION_MAJOR - - DRMP3_VERSION_REVISION - - DRMP3_VERSION_STRING - - drmp3_version() - - drmp3_version_string() - -v0.6.9 - 2020-04-30 - - Change the `pcm` parameter of drmp3dec_decode_frame() to a `const drmp3_uint8*` for consistency with internal APIs. - -v0.6.8 - 2020-04-26 - - Optimizations to decoding when initializing from memory. - -v0.6.7 - 2020-04-25 - - Fix a compilation error with DR_MP3_NO_STDIO - - Optimization to decoding by reducing some data movement. - -v0.6.6 - 2020-04-23 - - Fix a minor bug with the running PCM frame counter. - -v0.6.5 - 2020-04-19 - - Fix compilation error on ARM builds. - -v0.6.4 - 2020-04-19 - - Bring up to date with changes to minimp3. - -v0.6.3 - 2020-04-13 - - Fix some pedantic warnings. - -v0.6.2 - 2020-04-10 - - Fix a crash in drmp3_open_*_and_read_pcm_frames_*() if the output config object is NULL. - -v0.6.1 - 2020-04-05 - - Fix warnings. - -v0.6.0 - 2020-04-04 - - API CHANGE: Remove the pConfig parameter from the following APIs: - - drmp3_init() - - drmp3_init_memory() - - drmp3_init_file() - - Add drmp3_init_file_w() for opening a file from a wchar_t encoded path. - -v0.5.6 - 2020-02-12 - - Bring up to date with minimp3. - -v0.5.5 - 2020-01-29 - - Fix a memory allocation bug in high level s16 decoding APIs. - -v0.5.4 - 2019-12-02 - - Fix a possible null pointer dereference when using custom memory allocators for realloc(). - -v0.5.3 - 2019-11-14 - - Fix typos in documentation. - -v0.5.2 - 2019-11-02 - - Bring up to date with minimp3. - -v0.5.1 - 2019-10-08 - - Fix a warning with GCC. - -v0.5.0 - 2019-10-07 - - API CHANGE: Add support for user defined memory allocation routines. This system allows the program to specify their own memory allocation - routines with a user data pointer for client-specific contextual data. This adds an extra parameter to the end of the following APIs: - - drmp3_init() - - drmp3_init_file() - - drmp3_init_memory() - - drmp3_open_and_read_pcm_frames_f32() - - drmp3_open_and_read_pcm_frames_s16() - - drmp3_open_memory_and_read_pcm_frames_f32() - - drmp3_open_memory_and_read_pcm_frames_s16() - - drmp3_open_file_and_read_pcm_frames_f32() - - drmp3_open_file_and_read_pcm_frames_s16() - - API CHANGE: Renamed the following APIs: - - drmp3_open_and_read_f32() -> drmp3_open_and_read_pcm_frames_f32() - - drmp3_open_and_read_s16() -> drmp3_open_and_read_pcm_frames_s16() - - drmp3_open_memory_and_read_f32() -> drmp3_open_memory_and_read_pcm_frames_f32() - - drmp3_open_memory_and_read_s16() -> drmp3_open_memory_and_read_pcm_frames_s16() - - drmp3_open_file_and_read_f32() -> drmp3_open_file_and_read_pcm_frames_f32() - - drmp3_open_file_and_read_s16() -> drmp3_open_file_and_read_pcm_frames_s16() - -v0.4.7 - 2019-07-28 - - Fix a compiler error. - -v0.4.6 - 2019-06-14 - - Fix a compiler error. - -v0.4.5 - 2019-06-06 - - Bring up to date with minimp3. - -v0.4.4 - 2019-05-06 - - Fixes to the VC6 build. - -v0.4.3 - 2019-05-05 - - Use the channel count and/or sample rate of the first MP3 frame instead of DRMP3_DEFAULT_CHANNELS and - DRMP3_DEFAULT_SAMPLE_RATE when they are set to 0. To use the old behaviour, just set the relevant property to - DRMP3_DEFAULT_CHANNELS or DRMP3_DEFAULT_SAMPLE_RATE. - - Add s16 reading APIs - - drmp3_read_pcm_frames_s16 - - drmp3_open_memory_and_read_pcm_frames_s16 - - drmp3_open_and_read_pcm_frames_s16 - - drmp3_open_file_and_read_pcm_frames_s16 - - Add drmp3_get_mp3_and_pcm_frame_count() to the public header section. - - Add support for C89. - - Change license to choice of public domain or MIT-0. - -v0.4.2 - 2019-02-21 - - Fix a warning. - -v0.4.1 - 2018-12-30 - - Fix a warning. - -v0.4.0 - 2018-12-16 - - API CHANGE: Rename some APIs: - - drmp3_read_f32 -> to drmp3_read_pcm_frames_f32 - - drmp3_seek_to_frame -> drmp3_seek_to_pcm_frame - - drmp3_open_and_decode_f32 -> drmp3_open_and_read_pcm_frames_f32 - - drmp3_open_and_decode_memory_f32 -> drmp3_open_memory_and_read_pcm_frames_f32 - - drmp3_open_and_decode_file_f32 -> drmp3_open_file_and_read_pcm_frames_f32 - - Add drmp3_get_pcm_frame_count(). - - Add drmp3_get_mp3_frame_count(). - - Improve seeking performance. - -v0.3.2 - 2018-09-11 - - Fix a couple of memory leaks. - - Bring up to date with minimp3. - -v0.3.1 - 2018-08-25 - - Fix C++ build. - -v0.3.0 - 2018-08-25 - - Bring up to date with minimp3. This has a minor API change: the "pcm" parameter of drmp3dec_decode_frame() has - been changed from short* to void* because it can now output both s16 and f32 samples, depending on whether or - not the DR_MP3_FLOAT_OUTPUT option is set. - -v0.2.11 - 2018-08-08 - - Fix a bug where the last part of a file is not read. - -v0.2.10 - 2018-08-07 - - Improve 64-bit detection. - -v0.2.9 - 2018-08-05 - - Fix C++ build on older versions of GCC. - - Bring up to date with minimp3. - -v0.2.8 - 2018-08-02 - - Fix compilation errors with older versions of GCC. - -v0.2.7 - 2018-07-13 - - Bring up to date with minimp3. - -v0.2.6 - 2018-07-12 - - Bring up to date with minimp3. - -v0.2.5 - 2018-06-22 - - Bring up to date with minimp3. - -v0.2.4 - 2018-05-12 - - Bring up to date with minimp3. - -v0.2.3 - 2018-04-29 - - Fix TCC build. - -v0.2.2 - 2018-04-28 - - Fix bug when opening a decoder from memory. - -v0.2.1 - 2018-04-27 - - Efficiency improvements when the decoder reaches the end of the stream. - -v0.2 - 2018-04-21 - - Bring up to date with minimp3. - - Start using major.minor.revision versioning. - -v0.1d - 2018-03-30 - - Bring up to date with minimp3. - -v0.1c - 2018-03-11 - - Fix C++ build error. - -v0.1b - 2018-03-07 - - Bring up to date with minimp3. - -v0.1a - 2018-02-28 - - Fix compilation error on GCC/Clang. - - Fix some warnings. - -v0.1 - 2018-02-xx - - Initial versioned release. -*/ - -/* -This software is available as a choice of the following licenses. Choose -whichever you prefer. - -=============================================================================== -ALTERNATIVE 1 - Public Domain (www.unlicense.org) -=============================================================================== -This is free and unencumbered software released into the public domain. - -Anyone is free to copy, modify, publish, use, compile, sell, or distribute this -software, either in source code form or as a compiled binary, for any purpose, -commercial or non-commercial, and by any means. - -In jurisdictions that recognize copyright laws, the author or authors of this -software dedicate any and all copyright interest in the software to the public -domain. We make this dedication for the benefit of the public at large and to -the detriment of our heirs and successors. We intend this dedication to be an -overt act of relinquishment in perpetuity of all present and future rights to -this software under copyright law. - -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 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. - -For more information, please refer to - -=============================================================================== -ALTERNATIVE 2 - MIT No Attribution -=============================================================================== -Copyright 2020 David Reid - -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. - -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. -*/ - -/* - https://github.com/lieff/minimp3 - To the extent possible under law, the author(s) have dedicated all copyright and related and neighboring rights to this software to the public domain worldwide. - This software is distributed without any warranty. - See . -*/ \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/dr_libs/wav.h b/app/jni/src/libultraship/extern/dr_libs/wav.h deleted file mode 100644 index 517c6f6..0000000 --- a/app/jni/src/libultraship/extern/dr_libs/wav.h +++ /dev/null @@ -1,8418 +0,0 @@ -/* -WAV audio loader and writer. Choice of public domain or MIT-0. See license statements at the end of this file. -dr_wav - v0.13.6 - 2022-04-10 - -David Reid - mackron@gmail.com - -GitHub: https://github.com/mackron/dr_libs -*/ - -/* -Introduction -============ -This is a single file library. To use it, do something like the following in one .c file. - - ```c - #define DR_WAV_IMPLEMENTATION - #include "dr_wav.h" - ``` - -You can then #include this file in other parts of the program as you would with any other header file. Do something like the following to read audio data: - - ```c - drwav wav; - if (!drwav_init_file(&wav, "my_song.wav", NULL)) { - // Error opening WAV file. - } - - drwav_int32* pDecodedInterleavedPCMFrames = malloc(wav.totalPCMFrameCount * wav.channels * sizeof(drwav_int32)); - size_t numberOfSamplesActuallyDecoded = drwav_read_pcm_frames_s32(&wav, wav.totalPCMFrameCount, pDecodedInterleavedPCMFrames); - - ... - - drwav_uninit(&wav); - ``` - -If you just want to quickly open and read the audio data in a single operation you can do something like this: - - ```c - unsigned int channels; - unsigned int sampleRate; - drwav_uint64 totalPCMFrameCount; - float* pSampleData = drwav_open_file_and_read_pcm_frames_f32("my_song.wav", &channels, &sampleRate, &totalPCMFrameCount, NULL); - if (pSampleData == NULL) { - // Error opening and reading WAV file. - } - - ... - - drwav_free(pSampleData, NULL); - ``` - -The examples above use versions of the API that convert the audio data to a consistent format (32-bit signed PCM, in this case), but you can still output the -audio data in its internal format (see notes below for supported formats): - - ```c - size_t framesRead = drwav_read_pcm_frames(&wav, wav.totalPCMFrameCount, pDecodedInterleavedPCMFrames); - ``` - -You can also read the raw bytes of audio data, which could be useful if dr_wav does not have native support for a particular data format: - - ```c - size_t bytesRead = drwav_read_raw(&wav, bytesToRead, pRawDataBuffer); - ``` - -dr_wav can also be used to output WAV files. This does not currently support compressed formats. To use this, look at `drwav_init_write()`, -`drwav_init_file_write()`, etc. Use `drwav_write_pcm_frames()` to write samples, or `drwav_write_raw()` to write raw data in the "data" chunk. - - ```c - drwav_data_format format; - format.container = drwav_container_riff; // <-- drwav_container_riff = normal WAV files, drwav_container_w64 = Sony Wave64. - format.format = DR_WAVE_FORMAT_PCM; // <-- Any of the DR_WAVE_FORMAT_* codes. - format.channels = 2; - format.sampleRate = 44100; - format.bitsPerSample = 16; - drwav_init_file_write(&wav, "data/recording.wav", &format, NULL); - - ... - - drwav_uint64 framesWritten = drwav_write_pcm_frames(pWav, frameCount, pSamples); - ``` - -dr_wav has seamless support the Sony Wave64 format. The decoder will automatically detect it and it should Just Work without any manual intervention. - - -Build Options -============= -#define these options before including this file. - -#define DR_WAV_NO_CONVERSION_API - Disables conversion APIs such as `drwav_read_pcm_frames_f32()` and `drwav_s16_to_f32()`. - -#define DR_WAV_NO_STDIO - Disables APIs that initialize a decoder from a file such as `drwav_init_file()`, `drwav_init_file_write()`, etc. - - - -Notes -===== -- Samples are always interleaved. -- The default read function does not do any data conversion. Use `drwav_read_pcm_frames_f32()`, `drwav_read_pcm_frames_s32()` and `drwav_read_pcm_frames_s16()` - to read and convert audio data to 32-bit floating point, signed 32-bit integer and signed 16-bit integer samples respectively. Tested and supported internal - formats include the following: - - Unsigned 8-bit PCM - - Signed 12-bit PCM - - Signed 16-bit PCM - - Signed 24-bit PCM - - Signed 32-bit PCM - - IEEE 32-bit floating point - - IEEE 64-bit floating point - - A-law and u-law - - Microsoft ADPCM - - IMA ADPCM (DVI, format code 0x11) -- dr_wav will try to read the WAV file as best it can, even if it's not strictly conformant to the WAV format. -*/ - -#ifndef dr_wav_h -#define dr_wav_h - -#ifdef __cplusplus -extern "C" { -#endif - -#define DRWAV_STRINGIFY(x) #x -#define DRWAV_XSTRINGIFY(x) DRWAV_STRINGIFY(x) - -#define DRWAV_VERSION_MAJOR 0 -#define DRWAV_VERSION_MINOR 13 -#define DRWAV_VERSION_REVISION 6 -#define DRWAV_VERSION_STRING DRWAV_XSTRINGIFY(DRWAV_VERSION_MAJOR) "." DRWAV_XSTRINGIFY(DRWAV_VERSION_MINOR) "." DRWAV_XSTRINGIFY(DRWAV_VERSION_REVISION) - -#include /* For size_t. */ - - /* Sized types. */ - typedef signed char drwav_int8; - typedef unsigned char drwav_uint8; - typedef signed short drwav_int16; - typedef unsigned short drwav_uint16; - typedef signed int drwav_int32; - typedef unsigned int drwav_uint32; -#if defined(_MSC_VER) && !defined(__clang__) - typedef signed __int64 drwav_int64; - typedef unsigned __int64 drwav_uint64; -#else -#if defined(__clang__) || (defined(__GNUC__) && (__GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 6))) -#pragma GCC diagnostic push -#pragma GCC diagnostic ignored "-Wlong-long" -#if defined(__clang__) -#pragma GCC diagnostic ignored "-Wc++11-long-long" -#endif -#endif - typedef signed long long drwav_int64; - typedef unsigned long long drwav_uint64; -#if defined(__clang__) || (defined(__GNUC__) && (__GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 6))) -#pragma GCC diagnostic pop -#endif -#endif -#if defined(__LP64__) || defined(_WIN64) || (defined(__x86_64__) && !defined(__ILP32__)) || defined(_M_X64) || defined(__ia64) || defined (_M_IA64) || defined(__aarch64__) || defined(_M_ARM64) || defined(__powerpc64__) - typedef drwav_uint64 drwav_uintptr; -#else - typedef drwav_uint32 drwav_uintptr; -#endif - typedef drwav_uint8 drwav_bool8; - typedef drwav_uint32 drwav_bool32; -#define DRWAV_TRUE 1 -#define DRWAV_FALSE 0 - -#if !defined(DRWAV_API) -#if defined(DRWAV_DLL) -#if defined(_WIN32) -#define DRWAV_DLL_IMPORT __declspec(dllimport) -#define DRWAV_DLL_EXPORT __declspec(dllexport) -#define DRWAV_DLL_PRIVATE static -#else -#if defined(__GNUC__) && __GNUC__ >= 4 -#define DRWAV_DLL_IMPORT __attribute__((visibility("default"))) -#define DRWAV_DLL_EXPORT __attribute__((visibility("default"))) -#define DRWAV_DLL_PRIVATE __attribute__((visibility("hidden"))) -#else -#define DRWAV_DLL_IMPORT -#define DRWAV_DLL_EXPORT -#define DRWAV_DLL_PRIVATE static -#endif -#endif - -#if defined(DR_WAV_IMPLEMENTATION) || defined(DRWAV_IMPLEMENTATION) -#define DRWAV_API DRWAV_DLL_EXPORT -#else -#define DRWAV_API DRWAV_DLL_IMPORT -#endif -#define DRWAV_PRIVATE DRWAV_DLL_PRIVATE -#else -#define DRWAV_API extern -#define DRWAV_PRIVATE static -#endif -#endif - - typedef drwav_int32 drwav_result; -#define DRWAV_SUCCESS 0 -#define DRWAV_ERROR -1 /* A generic error. */ -#define DRWAV_INVALID_ARGS -2 -#define DRWAV_INVALID_OPERATION -3 -#define DRWAV_OUT_OF_MEMORY -4 -#define DRWAV_OUT_OF_RANGE -5 -#define DRWAV_ACCESS_DENIED -6 -#define DRWAV_DOES_NOT_EXIST -7 -#define DRWAV_ALREADY_EXISTS -8 -#define DRWAV_TOO_MANY_OPEN_FILES -9 -#define DRWAV_INVALID_FILE -10 -#define DRWAV_TOO_BIG -11 -#define DRWAV_PATH_TOO_LONG -12 -#define DRWAV_NAME_TOO_LONG -13 -#define DRWAV_NOT_DIRECTORY -14 -#define DRWAV_IS_DIRECTORY -15 -#define DRWAV_DIRECTORY_NOT_EMPTY -16 -#define DRWAV_END_OF_FILE -17 -#define DRWAV_NO_SPACE -18 -#define DRWAV_BUSY -19 -#define DRWAV_IO_ERROR -20 -#define DRWAV_INTERRUPT -21 -#define DRWAV_UNAVAILABLE -22 -#define DRWAV_ALREADY_IN_USE -23 -#define DRWAV_BAD_ADDRESS -24 -#define DRWAV_BAD_SEEK -25 -#define DRWAV_BAD_PIPE -26 -#define DRWAV_DEADLOCK -27 -#define DRWAV_TOO_MANY_LINKS -28 -#define DRWAV_NOT_IMPLEMENTED -29 -#define DRWAV_NO_MESSAGE -30 -#define DRWAV_BAD_MESSAGE -31 -#define DRWAV_NO_DATA_AVAILABLE -32 -#define DRWAV_INVALID_DATA -33 -#define DRWAV_TIMEOUT -34 -#define DRWAV_NO_NETWORK -35 -#define DRWAV_NOT_UNIQUE -36 -#define DRWAV_NOT_SOCKET -37 -#define DRWAV_NO_ADDRESS -38 -#define DRWAV_BAD_PROTOCOL -39 -#define DRWAV_PROTOCOL_UNAVAILABLE -40 -#define DRWAV_PROTOCOL_NOT_SUPPORTED -41 -#define DRWAV_PROTOCOL_FAMILY_NOT_SUPPORTED -42 -#define DRWAV_ADDRESS_FAMILY_NOT_SUPPORTED -43 -#define DRWAV_SOCKET_NOT_SUPPORTED -44 -#define DRWAV_CONNECTION_RESET -45 -#define DRWAV_ALREADY_CONNECTED -46 -#define DRWAV_NOT_CONNECTED -47 -#define DRWAV_CONNECTION_REFUSED -48 -#define DRWAV_NO_HOST -49 -#define DRWAV_IN_PROGRESS -50 -#define DRWAV_CANCELLED -51 -#define DRWAV_MEMORY_ALREADY_MAPPED -52 -#define DRWAV_AT_END -53 - - /* Common data formats. */ -#define DR_WAVE_FORMAT_PCM 0x1 -#define DR_WAVE_FORMAT_ADPCM 0x2 -#define DR_WAVE_FORMAT_IEEE_FLOAT 0x3 -#define DR_WAVE_FORMAT_ALAW 0x6 -#define DR_WAVE_FORMAT_MULAW 0x7 -#define DR_WAVE_FORMAT_DVI_ADPCM 0x11 -#define DR_WAVE_FORMAT_EXTENSIBLE 0xFFFE - -/* Flags to pass into drwav_init_ex(), etc. */ -#define DRWAV_SEQUENTIAL 0x00000001 - - DRWAV_API void drwav_version(drwav_uint32* pMajor, drwav_uint32* pMinor, drwav_uint32* pRevision); - DRWAV_API const char* drwav_version_string(void); - - typedef enum - { - drwav_seek_origin_start, - drwav_seek_origin_current - } drwav_seek_origin; - - typedef enum - { - drwav_container_riff, - drwav_container_w64, - drwav_container_rf64 - } drwav_container; - - typedef struct - { - union - { - drwav_uint8 fourcc[4]; - drwav_uint8 guid[16]; - } id; - - /* The size in bytes of the chunk. */ - drwav_uint64 sizeInBytes; - - /* - RIFF = 2 byte alignment. - W64 = 8 byte alignment. - */ - unsigned int paddingSize; - } drwav_chunk_header; - - typedef struct - { - /* - The format tag exactly as specified in the wave file's "fmt" chunk. This can be used by applications - that require support for data formats not natively supported by dr_wav. - */ - drwav_uint16 formatTag; - - /* The number of channels making up the audio data. When this is set to 1 it is mono, 2 is stereo, etc. */ - drwav_uint16 channels; - - /* The sample rate. Usually set to something like 44100. */ - drwav_uint32 sampleRate; - - /* Average bytes per second. You probably don't need this, but it's left here for informational purposes. */ - drwav_uint32 avgBytesPerSec; - - /* Block align. This is equal to the number of channels * bytes per sample. */ - drwav_uint16 blockAlign; - - /* Bits per sample. */ - drwav_uint16 bitsPerSample; - - /* The size of the extended data. Only used internally for validation, but left here for informational purposes. */ - drwav_uint16 extendedSize; - - /* - The number of valid bits per sample. When is equal to WAVE_FORMAT_EXTENSIBLE, - is always rounded up to the nearest multiple of 8. This variable contains information about exactly how - many bits are valid per sample. Mainly used for informational purposes. - */ - drwav_uint16 validBitsPerSample; - - /* The channel mask. Not used at the moment. */ - drwav_uint32 channelMask; - - /* The sub-format, exactly as specified by the wave file. */ - drwav_uint8 subFormat[16]; - } drwav_fmt; - - DRWAV_API drwav_uint16 drwav_fmt_get_format(const drwav_fmt* pFMT); - - - /* - Callback for when data is read. Return value is the number of bytes actually read. - - pUserData [in] The user data that was passed to drwav_init() and family. - pBufferOut [out] The output buffer. - bytesToRead [in] The number of bytes to read. - - Returns the number of bytes actually read. - - A return value of less than bytesToRead indicates the end of the stream. Do _not_ return from this callback until - either the entire bytesToRead is filled or you have reached the end of the stream. - */ - typedef size_t(*drwav_read_proc)(void* pUserData, void* pBufferOut, size_t bytesToRead); - - /* - Callback for when data is written. Returns value is the number of bytes actually written. - - pUserData [in] The user data that was passed to drwav_init_write() and family. - pData [out] A pointer to the data to write. - bytesToWrite [in] The number of bytes to write. - - Returns the number of bytes actually written. - - If the return value differs from bytesToWrite, it indicates an error. - */ - typedef size_t(*drwav_write_proc)(void* pUserData, const void* pData, size_t bytesToWrite); - - /* - Callback for when data needs to be seeked. - - pUserData [in] The user data that was passed to drwav_init() and family. - offset [in] The number of bytes to move, relative to the origin. Will never be negative. - origin [in] The origin of the seek - the current position or the start of the stream. - - Returns whether or not the seek was successful. - - Whether or not it is relative to the beginning or current position is determined by the "origin" parameter which will be either drwav_seek_origin_start or - drwav_seek_origin_current. - */ - typedef drwav_bool32(*drwav_seek_proc)(void* pUserData, int offset, drwav_seek_origin origin); - - /* - Callback for when drwav_init_ex() finds a chunk. - - pChunkUserData [in] The user data that was passed to the pChunkUserData parameter of drwav_init_ex() and family. - onRead [in] A pointer to the function to call when reading. - onSeek [in] A pointer to the function to call when seeking. - pReadSeekUserData [in] The user data that was passed to the pReadSeekUserData parameter of drwav_init_ex() and family. - pChunkHeader [in] A pointer to an object containing basic header information about the chunk. Use this to identify the chunk. - container [in] Whether or not the WAV file is a RIFF or Wave64 container. If you're unsure of the difference, assume RIFF. - pFMT [in] A pointer to the object containing the contents of the "fmt" chunk. - - Returns the number of bytes read + seeked. - - To read data from the chunk, call onRead(), passing in pReadSeekUserData as the first parameter. Do the same for seeking with onSeek(). The return value must - be the total number of bytes you have read _plus_ seeked. - - Use the `container` argument to discriminate the fields in `pChunkHeader->id`. If the container is `drwav_container_riff` or `drwav_container_rf64` you should - use `id.fourcc`, otherwise you should use `id.guid`. - - The `pFMT` parameter can be used to determine the data format of the wave file. Use `drwav_fmt_get_format()` to get the sample format, which will be one of the - `DR_WAVE_FORMAT_*` identifiers. - - The read pointer will be sitting on the first byte after the chunk's header. You must not attempt to read beyond the boundary of the chunk. - */ - typedef drwav_uint64(*drwav_chunk_proc)(void* pChunkUserData, drwav_read_proc onRead, drwav_seek_proc onSeek, void* pReadSeekUserData, const drwav_chunk_header* pChunkHeader, drwav_container container, const drwav_fmt* pFMT); - - typedef struct - { - void* pUserData; - void* (*onMalloc)(size_t sz, void* pUserData); - void* (*onRealloc)(void* p, size_t sz, void* pUserData); - void (*onFree)(void* p, void* pUserData); - } drwav_allocation_callbacks; - - /* Structure for internal use. Only used for loaders opened with drwav_init_memory(). */ - typedef struct - { - const drwav_uint8* data; - size_t dataSize; - size_t currentReadPos; - } drwav__memory_stream; - - /* Structure for internal use. Only used for writers opened with drwav_init_memory_write(). */ - typedef struct - { - void** ppData; - size_t* pDataSize; - size_t dataSize; - size_t dataCapacity; - size_t currentWritePos; - } drwav__memory_stream_write; - - typedef struct - { - drwav_container container; /* RIFF, W64. */ - drwav_uint32 format; /* DR_WAVE_FORMAT_* */ - drwav_uint32 channels; - drwav_uint32 sampleRate; - drwav_uint32 bitsPerSample; - } drwav_data_format; - - typedef enum - { - drwav_metadata_type_none = 0, - - /* - Unknown simply means a chunk that drwav does not handle specifically. You can still ask to - receive these chunks as metadata objects. It is then up to you to interpret the chunk's data. - You can also write unknown metadata to a wav file. Be careful writing unknown chunks if you - have also edited the audio data. The unknown chunks could represent offsets/sizes that no - longer correctly correspond to the audio data. - */ - drwav_metadata_type_unknown = 1 << 0, - - /* Only 1 of each of these metadata items are allowed in a wav file. */ - drwav_metadata_type_smpl = 1 << 1, - drwav_metadata_type_inst = 1 << 2, - drwav_metadata_type_cue = 1 << 3, - drwav_metadata_type_acid = 1 << 4, - drwav_metadata_type_bext = 1 << 5, - - /* - Wav files often have a LIST chunk. This is a chunk that contains a set of subchunks. For this - higher-level metadata API, we don't make a distinction between a regular chunk and a LIST - subchunk. Instead, they are all just 'metadata' items. - - There can be multiple of these metadata items in a wav file. - */ - drwav_metadata_type_list_label = 1 << 6, - drwav_metadata_type_list_note = 1 << 7, - drwav_metadata_type_list_labelled_cue_region = 1 << 8, - - drwav_metadata_type_list_info_software = 1 << 9, - drwav_metadata_type_list_info_copyright = 1 << 10, - drwav_metadata_type_list_info_title = 1 << 11, - drwav_metadata_type_list_info_artist = 1 << 12, - drwav_metadata_type_list_info_comment = 1 << 13, - drwav_metadata_type_list_info_date = 1 << 14, - drwav_metadata_type_list_info_genre = 1 << 15, - drwav_metadata_type_list_info_album = 1 << 16, - drwav_metadata_type_list_info_tracknumber = 1 << 17, - - /* Other type constants for convenience. */ - drwav_metadata_type_list_all_info_strings = drwav_metadata_type_list_info_software - | drwav_metadata_type_list_info_copyright - | drwav_metadata_type_list_info_title - | drwav_metadata_type_list_info_artist - | drwav_metadata_type_list_info_comment - | drwav_metadata_type_list_info_date - | drwav_metadata_type_list_info_genre - | drwav_metadata_type_list_info_album - | drwav_metadata_type_list_info_tracknumber, - - drwav_metadata_type_list_all_adtl = drwav_metadata_type_list_label - | drwav_metadata_type_list_note - | drwav_metadata_type_list_labelled_cue_region, - - drwav_metadata_type_all = -2, /*0xFFFFFFFF & ~drwav_metadata_type_unknown,*/ - drwav_metadata_type_all_including_unknown = -1 /*0xFFFFFFFF,*/ - } drwav_metadata_type; - - /* - Sampler Metadata - - The sampler chunk contains information about how a sound should be played in the context of a whole - audio production, and when used in a sampler. See https://en.wikipedia.org/wiki/Sample-based_synthesis. - */ - typedef enum - { - drwav_smpl_loop_type_forward = 0, - drwav_smpl_loop_type_pingpong = 1, - drwav_smpl_loop_type_backward = 2 - } drwav_smpl_loop_type; - - typedef struct - { - /* The ID of the associated cue point, see drwav_cue and drwav_cue_point. As with all cue point IDs, this can correspond to a label chunk to give this loop a name, see drwav_list_label_or_note. */ - drwav_uint32 cuePointId; - - /* See drwav_smpl_loop_type. */ - drwav_uint32 type; - - /* The byte offset of the first sample to be played in the loop. */ - drwav_uint32 firstSampleByteOffset; - - /* The byte offset into the audio data of the last sample to be played in the loop. */ - drwav_uint32 lastSampleByteOffset; - - /* A value to represent that playback should occur at a point between samples. This value ranges from 0 to UINT32_MAX. Where a value of 0 means no fraction, and a value of (UINT32_MAX / 2) would mean half a sample. */ - drwav_uint32 sampleFraction; - - /* Number of times to play the loop. 0 means loop infinitely. */ - drwav_uint32 playCount; - } drwav_smpl_loop; - - typedef struct - { - /* IDs for a particular MIDI manufacturer. 0 if not used. */ - drwav_uint32 manufacturerId; - drwav_uint32 productId; - - /* The period of 1 sample in nanoseconds. */ - drwav_uint32 samplePeriodNanoseconds; - - /* The MIDI root note of this file. 0 to 127. */ - drwav_uint32 midiUnityNote; - - /* The fraction of a semitone up from the given MIDI note. This is a value from 0 to UINT32_MAX, where 0 means no change and (UINT32_MAX / 2) is half a semitone (AKA 50 cents). */ - drwav_uint32 midiPitchFraction; - - /* Data relating to SMPTE standards which are used for syncing audio and video. 0 if not used. */ - drwav_uint32 smpteFormat; - drwav_uint32 smpteOffset; - - /* drwav_smpl_loop loops. */ - drwav_uint32 sampleLoopCount; - - /* Optional sampler-specific data. */ - drwav_uint32 samplerSpecificDataSizeInBytes; - - drwav_smpl_loop* pLoops; - drwav_uint8* pSamplerSpecificData; - } drwav_smpl; - - /* - Instrument Metadata - - The inst metadata contains data about how a sound should be played as part of an instrument. This - commonly read by samplers. See https://en.wikipedia.org/wiki/Sample-based_synthesis. - */ - typedef struct - { - drwav_int8 midiUnityNote; /* The root note of the audio as a MIDI note number. 0 to 127. */ - drwav_int8 fineTuneCents; /* -50 to +50 */ - drwav_int8 gainDecibels; /* -64 to +64 */ - drwav_int8 lowNote; /* 0 to 127 */ - drwav_int8 highNote; /* 0 to 127 */ - drwav_int8 lowVelocity; /* 1 to 127 */ - drwav_int8 highVelocity; /* 1 to 127 */ - } drwav_inst; - - /* - Cue Metadata - - Cue points are markers at specific points in the audio. They often come with an associated piece of - drwav_list_label_or_note metadata which contains the text for the marker. - */ - typedef struct - { - /* Unique identification value. */ - drwav_uint32 id; - - /* Set to 0. This is only relevant if there is a 'playlist' chunk - which is not supported by dr_wav. */ - drwav_uint32 playOrderPosition; - - /* Should always be "data". This represents the fourcc value of the chunk that this cue point corresponds to. dr_wav only supports a single data chunk so this should always be "data". */ - drwav_uint8 dataChunkId[4]; - - /* Set to 0. This is only relevant if there is a wave list chunk. dr_wav, like lots of readers/writers, do not support this. */ - drwav_uint32 chunkStart; - - /* Set to 0 for uncompressed formats. Else the last byte in compressed wave data where decompression can begin to find the value of the corresponding sample value. */ - drwav_uint32 blockStart; - - /* For uncompressed formats this is the byte offset of the cue point into the audio data. For compressed formats this is relative to the block specified with blockStart. */ - drwav_uint32 sampleByteOffset; - } drwav_cue_point; - - typedef struct - { - drwav_uint32 cuePointCount; - drwav_cue_point* pCuePoints; - } drwav_cue; - - /* - Acid Metadata - - This chunk contains some information about the time signature and the tempo of the audio. - */ - typedef enum - { - drwav_acid_flag_one_shot = 1, /* If this is not set, then it is a loop instead of a one-shot. */ - drwav_acid_flag_root_note_set = 2, - drwav_acid_flag_stretch = 4, - drwav_acid_flag_disk_based = 8, - drwav_acid_flag_acidizer = 16 /* Not sure what this means. */ - } drwav_acid_flag; - - typedef struct - { - /* A bit-field, see drwav_acid_flag. */ - drwav_uint32 flags; - - /* Valid if flags contains drwav_acid_flag_root_note_set. It represents the MIDI root note the file - a value from 0 to 127. */ - drwav_uint16 midiUnityNote; - - /* Reserved values that should probably be ignored. reserved1 seems to often be 128 and reserved2 is 0. */ - drwav_uint16 reserved1; - float reserved2; - - /* Number of beats. */ - drwav_uint32 numBeats; - - /* The time signature of the audio. */ - drwav_uint16 meterDenominator; - drwav_uint16 meterNumerator; - - /* Beats per minute of the track. Setting a value of 0 suggests that there is no tempo. */ - float tempo; - } drwav_acid; - - /* - Cue Label or Note metadata - - These are 2 different types of metadata, but they have the exact same format. Labels tend to be the - more common and represent a short name for a cue point. Notes might be used to represent a longer - comment. - */ - typedef struct - { - /* The ID of a cue point that this label or note corresponds to. */ - drwav_uint32 cuePointId; - - /* Size of the string not including any null terminator. */ - drwav_uint32 stringLength; - - /* The string. The *init_with_metadata functions null terminate this for convenience. */ - char* pString; - } drwav_list_label_or_note; - - /* - BEXT metadata, also known as Broadcast Wave Format (BWF) - - This metadata adds some extra description to an audio file. You must check the version field to - determine if the UMID or the loudness fields are valid. - */ - typedef struct - { - /* - These top 3 fields, and the umid field are actually defined in the standard as a statically - sized buffers. In order to reduce the size of this struct (and therefore the union in the - metadata struct), we instead store these as pointers. - */ - char* pDescription; /* Can be NULL or a null-terminated string, must be <= 256 characters. */ - char* pOriginatorName; /* Can be NULL or a null-terminated string, must be <= 32 characters. */ - char* pOriginatorReference; /* Can be NULL or a null-terminated string, must be <= 32 characters. */ - char pOriginationDate[10]; /* ASCII "yyyy:mm:dd". */ - char pOriginationTime[8]; /* ASCII "hh:mm:ss". */ - drwav_uint64 timeReference; /* First sample count since midnight. */ - drwav_uint16 version; /* Version of the BWF, check this to see if the fields below are valid. */ - - /* - Unrestricted ASCII characters containing a collection of strings terminated by CR/LF. Each - string shall contain a description of a coding process applied to the audio data. - */ - char* pCodingHistory; - drwav_uint32 codingHistorySize; - - /* Fields below this point are only valid if the version is 1 or above. */ - drwav_uint8* pUMID; /* Exactly 64 bytes of SMPTE UMID */ - - /* Fields below this point are only valid if the version is 2 or above. */ - drwav_uint16 loudnessValue; /* Integrated Loudness Value of the file in LUFS (multiplied by 100). */ - drwav_uint16 loudnessRange; /* Loudness Range of the file in LU (multiplied by 100). */ - drwav_uint16 maxTruePeakLevel; /* Maximum True Peak Level of the file expressed as dBTP (multiplied by 100). */ - drwav_uint16 maxMomentaryLoudness; /* Highest value of the Momentary Loudness Level of the file in LUFS (multiplied by 100). */ - drwav_uint16 maxShortTermLoudness; /* Highest value of the Short-Term Loudness Level of the file in LUFS (multiplied by 100). */ - } drwav_bext; - - /* - Info Text Metadata - - There a many different types of information text that can be saved in this format. This is where - things like the album name, the artists, the year it was produced, etc are saved. See - drwav_metadata_type for the full list of types that dr_wav supports. - */ - typedef struct - { - /* Size of the string not including any null terminator. */ - drwav_uint32 stringLength; - - /* The string. The *init_with_metadata functions null terminate this for convenience. */ - char* pString; - } drwav_list_info_text; - - /* - Labelled Cue Region Metadata - - The labelled cue region metadata is used to associate some region of audio with text. The region - starts at a cue point, and extends for the given number of samples. - */ - typedef struct - { - /* The ID of a cue point that this object corresponds to. */ - drwav_uint32 cuePointId; - - /* The number of samples from the cue point forwards that should be considered this region */ - drwav_uint32 sampleLength; - - /* Four characters used to say what the purpose of this region is. */ - drwav_uint8 purposeId[4]; - - /* Unsure of the exact meanings of these. It appears to be acceptable to set them all to 0. */ - drwav_uint16 country; - drwav_uint16 language; - drwav_uint16 dialect; - drwav_uint16 codePage; - - /* Size of the string not including any null terminator. */ - drwav_uint32 stringLength; - - /* The string. The *init_with_metadata functions null terminate this for convenience. */ - char* pString; - } drwav_list_labelled_cue_region; - - /* - Unknown Metadata - - This chunk just represents a type of chunk that dr_wav does not understand. - - Unknown metadata has a location attached to it. This is because wav files can have a LIST chunk - that contains subchunks. These LIST chunks can be one of two types. An adtl list, or an INFO - list. This enum is used to specify the location of a chunk that dr_wav currently doesn't support. - */ - typedef enum - { - drwav_metadata_location_invalid, - drwav_metadata_location_top_level, - drwav_metadata_location_inside_info_list, - drwav_metadata_location_inside_adtl_list - } drwav_metadata_location; - - typedef struct - { - drwav_uint8 id[4]; - drwav_metadata_location chunkLocation; - drwav_uint32 dataSizeInBytes; - drwav_uint8* pData; - } drwav_unknown_metadata; - - /* - Metadata is saved as a union of all the supported types. - */ - typedef struct - { - /* Determines which item in the union is valid. */ - drwav_metadata_type type; - - union - { - drwav_cue cue; - drwav_smpl smpl; - drwav_acid acid; - drwav_inst inst; - drwav_bext bext; - drwav_list_label_or_note labelOrNote; /* List label or list note. */ - drwav_list_labelled_cue_region labelledCueRegion; - drwav_list_info_text infoText; /* Any of the list info types. */ - drwav_unknown_metadata unknown; - } data; - } drwav_metadata; - - typedef struct - { - /* A pointer to the function to call when more data is needed. */ - drwav_read_proc onRead; - - /* A pointer to the function to call when data needs to be written. Only used when the drwav object is opened in write mode. */ - drwav_write_proc onWrite; - - /* A pointer to the function to call when the wav file needs to be seeked. */ - drwav_seek_proc onSeek; - - /* The user data to pass to callbacks. */ - void* pUserData; - - /* Allocation callbacks. */ - drwav_allocation_callbacks allocationCallbacks; - - - /* Whether or not the WAV file is formatted as a standard RIFF file or W64. */ - drwav_container container; - - - /* Structure containing format information exactly as specified by the wav file. */ - drwav_fmt fmt; - - /* The sample rate. Will be set to something like 44100. */ - drwav_uint32 sampleRate; - - /* The number of channels. This will be set to 1 for monaural streams, 2 for stereo, etc. */ - drwav_uint16 channels; - - /* The bits per sample. Will be set to something like 16, 24, etc. */ - drwav_uint16 bitsPerSample; - - /* Equal to fmt.formatTag, or the value specified by fmt.subFormat if fmt.formatTag is equal to 65534 (WAVE_FORMAT_EXTENSIBLE). */ - drwav_uint16 translatedFormatTag; - - /* The total number of PCM frames making up the audio data. */ - drwav_uint64 totalPCMFrameCount; - - - /* The size in bytes of the data chunk. */ - drwav_uint64 dataChunkDataSize; - - /* The position in the stream of the first data byte of the data chunk. This is used for seeking. */ - drwav_uint64 dataChunkDataPos; - - /* The number of bytes remaining in the data chunk. */ - drwav_uint64 bytesRemaining; - - /* The current read position in PCM frames. */ - drwav_uint64 readCursorInPCMFrames; - - - /* - Only used in sequential write mode. Keeps track of the desired size of the "data" chunk at the point of initialization time. Always - set to 0 for non-sequential writes and when the drwav object is opened in read mode. Used for validation. - */ - drwav_uint64 dataChunkDataSizeTargetWrite; - - /* Keeps track of whether or not the wav writer was initialized in sequential mode. */ - drwav_bool32 isSequentialWrite; - - - /* A bit-field of drwav_metadata_type values, only bits set in this variable are parsed and saved */ - drwav_metadata_type allowedMetadataTypes; - - /* A array of metadata. This is valid after the *init_with_metadata call returns. It will be valid until drwav_uninit() is called. You can take ownership of this data with drwav_take_ownership_of_metadata(). */ - drwav_metadata* pMetadata; - drwav_uint32 metadataCount; - - - /* A hack to avoid a DRWAV_MALLOC() when opening a decoder with drwav_init_memory(). */ - drwav__memory_stream memoryStream; - drwav__memory_stream_write memoryStreamWrite; - - - /* Microsoft ADPCM specific data. */ - struct - { - drwav_uint32 bytesRemainingInBlock; - drwav_uint16 predictor[2]; - drwav_int32 delta[2]; - drwav_int32 cachedFrames[4]; /* Samples are stored in this cache during decoding. */ - drwav_uint32 cachedFrameCount; - drwav_int32 prevFrames[2][2]; /* The previous 2 samples for each channel (2 channels at most). */ - } msadpcm; - - /* IMA ADPCM specific data. */ - struct - { - drwav_uint32 bytesRemainingInBlock; - drwav_int32 predictor[2]; - drwav_int32 stepIndex[2]; - drwav_int32 cachedFrames[16]; /* Samples are stored in this cache during decoding. */ - drwav_uint32 cachedFrameCount; - } ima; - } drwav; - - - /* - Initializes a pre-allocated drwav object for reading. - - pWav [out] A pointer to the drwav object being initialized. - onRead [in] The function to call when data needs to be read from the client. - onSeek [in] The function to call when the read position of the client data needs to move. - onChunk [in, optional] The function to call when a chunk is enumerated at initialized time. - pUserData, pReadSeekUserData [in, optional] A pointer to application defined data that will be passed to onRead and onSeek. - pChunkUserData [in, optional] A pointer to application defined data that will be passed to onChunk. - flags [in, optional] A set of flags for controlling how things are loaded. - - Returns true if successful; false otherwise. - - Close the loader with drwav_uninit(). - - This is the lowest level function for initializing a WAV file. You can also use drwav_init_file() and drwav_init_memory() - to open the stream from a file or from a block of memory respectively. - - Possible values for flags: - DRWAV_SEQUENTIAL: Never perform a backwards seek while loading. This disables the chunk callback and will cause this function - to return as soon as the data chunk is found. Any chunks after the data chunk will be ignored. - - drwav_init() is equivalent to "drwav_init_ex(pWav, onRead, onSeek, NULL, pUserData, NULL, 0);". - - The onChunk callback is not called for the WAVE or FMT chunks. The contents of the FMT chunk can be read from pWav->fmt - after the function returns. - - See also: drwav_init_file(), drwav_init_memory(), drwav_uninit() - */ - DRWAV_API drwav_bool32 drwav_init(drwav* pWav, drwav_read_proc onRead, drwav_seek_proc onSeek, void* pUserData, const drwav_allocation_callbacks* pAllocationCallbacks); - DRWAV_API drwav_bool32 drwav_init_ex(drwav* pWav, drwav_read_proc onRead, drwav_seek_proc onSeek, drwav_chunk_proc onChunk, void* pReadSeekUserData, void* pChunkUserData, drwav_uint32 flags, const drwav_allocation_callbacks* pAllocationCallbacks); - DRWAV_API drwav_bool32 drwav_init_with_metadata(drwav* pWav, drwav_read_proc onRead, drwav_seek_proc onSeek, void* pUserData, drwav_uint32 flags, const drwav_allocation_callbacks* pAllocationCallbacks); - - /* - Initializes a pre-allocated drwav object for writing. - - onWrite [in] The function to call when data needs to be written. - onSeek [in] The function to call when the write position needs to move. - pUserData [in, optional] A pointer to application defined data that will be passed to onWrite and onSeek. - metadata, numMetadata [in, optional] An array of metadata objects that should be written to the file. The array is not edited. You are responsible for this metadata memory and it must maintain valid until drwav_uninit() is called. - - Returns true if successful; false otherwise. - - Close the writer with drwav_uninit(). - - This is the lowest level function for initializing a WAV file. You can also use drwav_init_file_write() and drwav_init_memory_write() - to open the stream from a file or from a block of memory respectively. - - If the total sample count is known, you can use drwav_init_write_sequential(). This avoids the need for dr_wav to perform - a post-processing step for storing the total sample count and the size of the data chunk which requires a backwards seek. - - See also: drwav_init_file_write(), drwav_init_memory_write(), drwav_uninit() - */ - DRWAV_API drwav_bool32 drwav_init_write(drwav* pWav, const drwav_data_format* pFormat, drwav_write_proc onWrite, drwav_seek_proc onSeek, void* pUserData, const drwav_allocation_callbacks* pAllocationCallbacks); - DRWAV_API drwav_bool32 drwav_init_write_sequential(drwav* pWav, const drwav_data_format* pFormat, drwav_uint64 totalSampleCount, drwav_write_proc onWrite, void* pUserData, const drwav_allocation_callbacks* pAllocationCallbacks); - DRWAV_API drwav_bool32 drwav_init_write_sequential_pcm_frames(drwav* pWav, const drwav_data_format* pFormat, drwav_uint64 totalPCMFrameCount, drwav_write_proc onWrite, void* pUserData, const drwav_allocation_callbacks* pAllocationCallbacks); - DRWAV_API drwav_bool32 drwav_init_write_with_metadata(drwav* pWav, const drwav_data_format* pFormat, drwav_write_proc onWrite, drwav_seek_proc onSeek, void* pUserData, const drwav_allocation_callbacks* pAllocationCallbacks, drwav_metadata* pMetadata, drwav_uint32 metadataCount); - - /* - Utility function to determine the target size of the entire data to be written (including all headers and chunks). - - Returns the target size in bytes. - - The metadata argument can be NULL meaning no metadata exists. - - Useful if the application needs to know the size to allocate. - - Only writing to the RIFF chunk and one data chunk is currently supported. - - See also: drwav_init_write(), drwav_init_file_write(), drwav_init_memory_write() - */ - DRWAV_API drwav_uint64 drwav_target_write_size_bytes(const drwav_data_format* pFormat, drwav_uint64 totalFrameCount, drwav_metadata* pMetadata, drwav_uint32 metadataCount); - - /* - Take ownership of the metadata objects that were allocated via one of the init_with_metadata() function calls. The init_with_metdata functions perform a single heap allocation for this metadata. - - Useful if you want the data to persist beyond the lifetime of the drwav object. - - You must free the data returned from this function using drwav_free(). - */ - DRWAV_API drwav_metadata* drwav_take_ownership_of_metadata(drwav* pWav); - - /* - Uninitializes the given drwav object. - - Use this only for objects initialized with drwav_init*() functions (drwav_init(), drwav_init_ex(), drwav_init_write(), drwav_init_write_sequential()). - */ - DRWAV_API drwav_result drwav_uninit(drwav* pWav); - - - /* - Reads raw audio data. - - This is the lowest level function for reading audio data. It simply reads the given number of - bytes of the raw internal sample data. - - Consider using drwav_read_pcm_frames_s16(), drwav_read_pcm_frames_s32() or drwav_read_pcm_frames_f32() for - reading sample data in a consistent format. - - pBufferOut can be NULL in which case a seek will be performed. - - Returns the number of bytes actually read. - */ - DRWAV_API size_t drwav_read_raw(drwav* pWav, size_t bytesToRead, void* pBufferOut); - - /* - Reads up to the specified number of PCM frames from the WAV file. - - The output data will be in the file's internal format, converted to native-endian byte order. Use - drwav_read_pcm_frames_s16/f32/s32() to read data in a specific format. - - If the return value is less than it means the end of the file has been reached or - you have requested more PCM frames than can possibly fit in the output buffer. - - This function will only work when sample data is of a fixed size and uncompressed. If you are - using a compressed format consider using drwav_read_raw() or drwav_read_pcm_frames_s16/s32/f32(). - - pBufferOut can be NULL in which case a seek will be performed. - */ - DRWAV_API drwav_uint64 drwav_read_pcm_frames(drwav* pWav, drwav_uint64 framesToRead, void* pBufferOut); - DRWAV_API drwav_uint64 drwav_read_pcm_frames_le(drwav* pWav, drwav_uint64 framesToRead, void* pBufferOut); - DRWAV_API drwav_uint64 drwav_read_pcm_frames_be(drwav* pWav, drwav_uint64 framesToRead, void* pBufferOut); - - /* - Seeks to the given PCM frame. - - Returns true if successful; false otherwise. - */ - DRWAV_API drwav_bool32 drwav_seek_to_pcm_frame(drwav* pWav, drwav_uint64 targetFrameIndex); - - /* - Retrieves the current read position in pcm frames. - */ - DRWAV_API drwav_result drwav_get_cursor_in_pcm_frames(drwav* pWav, drwav_uint64* pCursor); - - /* - Retrieves the length of the file. - */ - DRWAV_API drwav_result drwav_get_length_in_pcm_frames(drwav* pWav, drwav_uint64* pLength); - - - /* - Writes raw audio data. - - Returns the number of bytes actually written. If this differs from bytesToWrite, it indicates an error. - */ - DRWAV_API size_t drwav_write_raw(drwav* pWav, size_t bytesToWrite, const void* pData); - - /* - Writes PCM frames. - - Returns the number of PCM frames written. - - Input samples need to be in native-endian byte order. On big-endian architectures the input data will be converted to - little-endian. Use drwav_write_raw() to write raw audio data without performing any conversion. - */ - DRWAV_API drwav_uint64 drwav_write_pcm_frames(drwav* pWav, drwav_uint64 framesToWrite, const void* pData); - DRWAV_API drwav_uint64 drwav_write_pcm_frames_le(drwav* pWav, drwav_uint64 framesToWrite, const void* pData); - DRWAV_API drwav_uint64 drwav_write_pcm_frames_be(drwav* pWav, drwav_uint64 framesToWrite, const void* pData); - - /* Conversion Utilities */ -#ifndef DR_WAV_NO_CONVERSION_API - -/* -Reads a chunk of audio data and converts it to signed 16-bit PCM samples. - -pBufferOut can be NULL in which case a seek will be performed. - -Returns the number of PCM frames actually read. - -If the return value is less than it means the end of the file has been reached. -*/ - DRWAV_API drwav_uint64 drwav_read_pcm_frames_s16(drwav* pWav, drwav_uint64 framesToRead, drwav_int16* pBufferOut); - DRWAV_API drwav_uint64 drwav_read_pcm_frames_s16le(drwav* pWav, drwav_uint64 framesToRead, drwav_int16* pBufferOut); - DRWAV_API drwav_uint64 drwav_read_pcm_frames_s16be(drwav* pWav, drwav_uint64 framesToRead, drwav_int16* pBufferOut); - - /* Low-level function for converting unsigned 8-bit PCM samples to signed 16-bit PCM samples. */ - DRWAV_API void drwav_u8_to_s16(drwav_int16* pOut, const drwav_uint8* pIn, size_t sampleCount); - - /* Low-level function for converting signed 24-bit PCM samples to signed 16-bit PCM samples. */ - DRWAV_API void drwav_s24_to_s16(drwav_int16* pOut, const drwav_uint8* pIn, size_t sampleCount); - - /* Low-level function for converting signed 32-bit PCM samples to signed 16-bit PCM samples. */ - DRWAV_API void drwav_s32_to_s16(drwav_int16* pOut, const drwav_int32* pIn, size_t sampleCount); - - /* Low-level function for converting IEEE 32-bit floating point samples to signed 16-bit PCM samples. */ - DRWAV_API void drwav_f32_to_s16(drwav_int16* pOut, const float* pIn, size_t sampleCount); - - /* Low-level function for converting IEEE 64-bit floating point samples to signed 16-bit PCM samples. */ - DRWAV_API void drwav_f64_to_s16(drwav_int16* pOut, const double* pIn, size_t sampleCount); - - /* Low-level function for converting A-law samples to signed 16-bit PCM samples. */ - DRWAV_API void drwav_alaw_to_s16(drwav_int16* pOut, const drwav_uint8* pIn, size_t sampleCount); - - /* Low-level function for converting u-law samples to signed 16-bit PCM samples. */ - DRWAV_API void drwav_mulaw_to_s16(drwav_int16* pOut, const drwav_uint8* pIn, size_t sampleCount); - - - /* - Reads a chunk of audio data and converts it to IEEE 32-bit floating point samples. - - pBufferOut can be NULL in which case a seek will be performed. - - Returns the number of PCM frames actually read. - - If the return value is less than it means the end of the file has been reached. - */ - DRWAV_API drwav_uint64 drwav_read_pcm_frames_f32(drwav* pWav, drwav_uint64 framesToRead, float* pBufferOut); - DRWAV_API drwav_uint64 drwav_read_pcm_frames_f32le(drwav* pWav, drwav_uint64 framesToRead, float* pBufferOut); - DRWAV_API drwav_uint64 drwav_read_pcm_frames_f32be(drwav* pWav, drwav_uint64 framesToRead, float* pBufferOut); - - /* Low-level function for converting unsigned 8-bit PCM samples to IEEE 32-bit floating point samples. */ - DRWAV_API void drwav_u8_to_f32(float* pOut, const drwav_uint8* pIn, size_t sampleCount); - - /* Low-level function for converting signed 16-bit PCM samples to IEEE 32-bit floating point samples. */ - DRWAV_API void drwav_s16_to_f32(float* pOut, const drwav_int16* pIn, size_t sampleCount); - - /* Low-level function for converting signed 24-bit PCM samples to IEEE 32-bit floating point samples. */ - DRWAV_API void drwav_s24_to_f32(float* pOut, const drwav_uint8* pIn, size_t sampleCount); - - /* Low-level function for converting signed 32-bit PCM samples to IEEE 32-bit floating point samples. */ - DRWAV_API void drwav_s32_to_f32(float* pOut, const drwav_int32* pIn, size_t sampleCount); - - /* Low-level function for converting IEEE 64-bit floating point samples to IEEE 32-bit floating point samples. */ - DRWAV_API void drwav_f64_to_f32(float* pOut, const double* pIn, size_t sampleCount); - - /* Low-level function for converting A-law samples to IEEE 32-bit floating point samples. */ - DRWAV_API void drwav_alaw_to_f32(float* pOut, const drwav_uint8* pIn, size_t sampleCount); - - /* Low-level function for converting u-law samples to IEEE 32-bit floating point samples. */ - DRWAV_API void drwav_mulaw_to_f32(float* pOut, const drwav_uint8* pIn, size_t sampleCount); - - - /* - Reads a chunk of audio data and converts it to signed 32-bit PCM samples. - - pBufferOut can be NULL in which case a seek will be performed. - - Returns the number of PCM frames actually read. - - If the return value is less than it means the end of the file has been reached. - */ - DRWAV_API drwav_uint64 drwav_read_pcm_frames_s32(drwav* pWav, drwav_uint64 framesToRead, drwav_int32* pBufferOut); - DRWAV_API drwav_uint64 drwav_read_pcm_frames_s32le(drwav* pWav, drwav_uint64 framesToRead, drwav_int32* pBufferOut); - DRWAV_API drwav_uint64 drwav_read_pcm_frames_s32be(drwav* pWav, drwav_uint64 framesToRead, drwav_int32* pBufferOut); - - /* Low-level function for converting unsigned 8-bit PCM samples to signed 32-bit PCM samples. */ - DRWAV_API void drwav_u8_to_s32(drwav_int32* pOut, const drwav_uint8* pIn, size_t sampleCount); - - /* Low-level function for converting signed 16-bit PCM samples to signed 32-bit PCM samples. */ - DRWAV_API void drwav_s16_to_s32(drwav_int32* pOut, const drwav_int16* pIn, size_t sampleCount); - - /* Low-level function for converting signed 24-bit PCM samples to signed 32-bit PCM samples. */ - DRWAV_API void drwav_s24_to_s32(drwav_int32* pOut, const drwav_uint8* pIn, size_t sampleCount); - - /* Low-level function for converting IEEE 32-bit floating point samples to signed 32-bit PCM samples. */ - DRWAV_API void drwav_f32_to_s32(drwav_int32* pOut, const float* pIn, size_t sampleCount); - - /* Low-level function for converting IEEE 64-bit floating point samples to signed 32-bit PCM samples. */ - DRWAV_API void drwav_f64_to_s32(drwav_int32* pOut, const double* pIn, size_t sampleCount); - - /* Low-level function for converting A-law samples to signed 32-bit PCM samples. */ - DRWAV_API void drwav_alaw_to_s32(drwav_int32* pOut, const drwav_uint8* pIn, size_t sampleCount); - - /* Low-level function for converting u-law samples to signed 32-bit PCM samples. */ - DRWAV_API void drwav_mulaw_to_s32(drwav_int32* pOut, const drwav_uint8* pIn, size_t sampleCount); - -#endif /* DR_WAV_NO_CONVERSION_API */ - - - /* High-Level Convenience Helpers */ - -#ifndef DR_WAV_NO_STDIO -/* -Helper for initializing a wave file for reading using stdio. - -This holds the internal FILE object until drwav_uninit() is called. Keep this in mind if you're caching drwav -objects because the operating system may restrict the number of file handles an application can have open at -any given time. -*/ - DRWAV_API drwav_bool32 drwav_init_file(drwav* pWav, const char* filename, const drwav_allocation_callbacks* pAllocationCallbacks); - DRWAV_API drwav_bool32 drwav_init_file_ex(drwav* pWav, const char* filename, drwav_chunk_proc onChunk, void* pChunkUserData, drwav_uint32 flags, const drwav_allocation_callbacks* pAllocationCallbacks); - DRWAV_API drwav_bool32 drwav_init_file_w(drwav* pWav, const wchar_t* filename, const drwav_allocation_callbacks* pAllocationCallbacks); - DRWAV_API drwav_bool32 drwav_init_file_ex_w(drwav* pWav, const wchar_t* filename, drwav_chunk_proc onChunk, void* pChunkUserData, drwav_uint32 flags, const drwav_allocation_callbacks* pAllocationCallbacks); - DRWAV_API drwav_bool32 drwav_init_file_with_metadata(drwav* pWav, const char* filename, drwav_uint32 flags, const drwav_allocation_callbacks* pAllocationCallbacks); - DRWAV_API drwav_bool32 drwav_init_file_with_metadata_w(drwav* pWav, const wchar_t* filename, drwav_uint32 flags, const drwav_allocation_callbacks* pAllocationCallbacks); - - - /* - Helper for initializing a wave file for writing using stdio. - - This holds the internal FILE object until drwav_uninit() is called. Keep this in mind if you're caching drwav - objects because the operating system may restrict the number of file handles an application can have open at - any given time. - */ - DRWAV_API drwav_bool32 drwav_init_file_write(drwav* pWav, const char* filename, const drwav_data_format* pFormat, const drwav_allocation_callbacks* pAllocationCallbacks); - DRWAV_API drwav_bool32 drwav_init_file_write_sequential(drwav* pWav, const char* filename, const drwav_data_format* pFormat, drwav_uint64 totalSampleCount, const drwav_allocation_callbacks* pAllocationCallbacks); - DRWAV_API drwav_bool32 drwav_init_file_write_sequential_pcm_frames(drwav* pWav, const char* filename, const drwav_data_format* pFormat, drwav_uint64 totalPCMFrameCount, const drwav_allocation_callbacks* pAllocationCallbacks); - DRWAV_API drwav_bool32 drwav_init_file_write_w(drwav* pWav, const wchar_t* filename, const drwav_data_format* pFormat, const drwav_allocation_callbacks* pAllocationCallbacks); - DRWAV_API drwav_bool32 drwav_init_file_write_sequential_w(drwav* pWav, const wchar_t* filename, const drwav_data_format* pFormat, drwav_uint64 totalSampleCount, const drwav_allocation_callbacks* pAllocationCallbacks); - DRWAV_API drwav_bool32 drwav_init_file_write_sequential_pcm_frames_w(drwav* pWav, const wchar_t* filename, const drwav_data_format* pFormat, drwav_uint64 totalPCMFrameCount, const drwav_allocation_callbacks* pAllocationCallbacks); -#endif /* DR_WAV_NO_STDIO */ - - /* - Helper for initializing a loader from a pre-allocated memory buffer. - - This does not create a copy of the data. It is up to the application to ensure the buffer remains valid for - the lifetime of the drwav object. - - The buffer should contain the contents of the entire wave file, not just the sample data. - */ - DRWAV_API drwav_bool32 drwav_init_memory(drwav* pWav, const void* data, size_t dataSize, const drwav_allocation_callbacks* pAllocationCallbacks); - DRWAV_API drwav_bool32 drwav_init_memory_ex(drwav* pWav, const void* data, size_t dataSize, drwav_chunk_proc onChunk, void* pChunkUserData, drwav_uint32 flags, const drwav_allocation_callbacks* pAllocationCallbacks); - DRWAV_API drwav_bool32 drwav_init_memory_with_metadata(drwav* pWav, const void* data, size_t dataSize, drwav_uint32 flags, const drwav_allocation_callbacks* pAllocationCallbacks); - - /* - Helper for initializing a writer which outputs data to a memory buffer. - - dr_wav will manage the memory allocations, however it is up to the caller to free the data with drwav_free(). - - The buffer will remain allocated even after drwav_uninit() is called. The buffer should not be considered valid - until after drwav_uninit() has been called. - */ - DRWAV_API drwav_bool32 drwav_init_memory_write(drwav* pWav, void** ppData, size_t* pDataSize, const drwav_data_format* pFormat, const drwav_allocation_callbacks* pAllocationCallbacks); - DRWAV_API drwav_bool32 drwav_init_memory_write_sequential(drwav* pWav, void** ppData, size_t* pDataSize, const drwav_data_format* pFormat, drwav_uint64 totalSampleCount, const drwav_allocation_callbacks* pAllocationCallbacks); - DRWAV_API drwav_bool32 drwav_init_memory_write_sequential_pcm_frames(drwav* pWav, void** ppData, size_t* pDataSize, const drwav_data_format* pFormat, drwav_uint64 totalPCMFrameCount, const drwav_allocation_callbacks* pAllocationCallbacks); - - -#ifndef DR_WAV_NO_CONVERSION_API - /* - Opens and reads an entire wav file in a single operation. - - The return value is a heap-allocated buffer containing the audio data. Use drwav_free() to free the buffer. - */ - DRWAV_API drwav_int16* drwav_open_and_read_pcm_frames_s16(drwav_read_proc onRead, drwav_seek_proc onSeek, void* pUserData, unsigned int* channelsOut, unsigned int* sampleRateOut, drwav_uint64* totalFrameCountOut, const drwav_allocation_callbacks* pAllocationCallbacks); - DRWAV_API float* drwav_open_and_read_pcm_frames_f32(drwav_read_proc onRead, drwav_seek_proc onSeek, void* pUserData, unsigned int* channelsOut, unsigned int* sampleRateOut, drwav_uint64* totalFrameCountOut, const drwav_allocation_callbacks* pAllocationCallbacks); - DRWAV_API drwav_int32* drwav_open_and_read_pcm_frames_s32(drwav_read_proc onRead, drwav_seek_proc onSeek, void* pUserData, unsigned int* channelsOut, unsigned int* sampleRateOut, drwav_uint64* totalFrameCountOut, const drwav_allocation_callbacks* pAllocationCallbacks); -#ifndef DR_WAV_NO_STDIO - /* - Opens and decodes an entire wav file in a single operation. - - The return value is a heap-allocated buffer containing the audio data. Use drwav_free() to free the buffer. - */ - DRWAV_API drwav_int16* drwav_open_file_and_read_pcm_frames_s16(const char* filename, unsigned int* channelsOut, unsigned int* sampleRateOut, drwav_uint64* totalFrameCountOut, const drwav_allocation_callbacks* pAllocationCallbacks); - DRWAV_API float* drwav_open_file_and_read_pcm_frames_f32(const char* filename, unsigned int* channelsOut, unsigned int* sampleRateOut, drwav_uint64* totalFrameCountOut, const drwav_allocation_callbacks* pAllocationCallbacks); - DRWAV_API drwav_int32* drwav_open_file_and_read_pcm_frames_s32(const char* filename, unsigned int* channelsOut, unsigned int* sampleRateOut, drwav_uint64* totalFrameCountOut, const drwav_allocation_callbacks* pAllocationCallbacks); - DRWAV_API drwav_int16* drwav_open_file_and_read_pcm_frames_s16_w(const wchar_t* filename, unsigned int* channelsOut, unsigned int* sampleRateOut, drwav_uint64* totalFrameCountOut, const drwav_allocation_callbacks* pAllocationCallbacks); - DRWAV_API float* drwav_open_file_and_read_pcm_frames_f32_w(const wchar_t* filename, unsigned int* channelsOut, unsigned int* sampleRateOut, drwav_uint64* totalFrameCountOut, const drwav_allocation_callbacks* pAllocationCallbacks); - DRWAV_API drwav_int32* drwav_open_file_and_read_pcm_frames_s32_w(const wchar_t* filename, unsigned int* channelsOut, unsigned int* sampleRateOut, drwav_uint64* totalFrameCountOut, const drwav_allocation_callbacks* pAllocationCallbacks); -#endif - /* - Opens and decodes an entire wav file from a block of memory in a single operation. - - The return value is a heap-allocated buffer containing the audio data. Use drwav_free() to free the buffer. - */ - DRWAV_API drwav_int16* drwav_open_memory_and_read_pcm_frames_s16(const void* data, size_t dataSize, unsigned int* channelsOut, unsigned int* sampleRateOut, drwav_uint64* totalFrameCountOut, const drwav_allocation_callbacks* pAllocationCallbacks); - DRWAV_API float* drwav_open_memory_and_read_pcm_frames_f32(const void* data, size_t dataSize, unsigned int* channelsOut, unsigned int* sampleRateOut, drwav_uint64* totalFrameCountOut, const drwav_allocation_callbacks* pAllocationCallbacks); - DRWAV_API drwav_int32* drwav_open_memory_and_read_pcm_frames_s32(const void* data, size_t dataSize, unsigned int* channelsOut, unsigned int* sampleRateOut, drwav_uint64* totalFrameCountOut, const drwav_allocation_callbacks* pAllocationCallbacks); -#endif - - /* Frees data that was allocated internally by dr_wav. */ - DRWAV_API void drwav_free(void* p, const drwav_allocation_callbacks* pAllocationCallbacks); - - /* Converts bytes from a wav stream to a sized type of native endian. */ - DRWAV_API drwav_uint16 drwav_bytes_to_u16(const drwav_uint8* data); - DRWAV_API drwav_int16 drwav_bytes_to_s16(const drwav_uint8* data); - DRWAV_API drwav_uint32 drwav_bytes_to_u32(const drwav_uint8* data); - DRWAV_API drwav_int32 drwav_bytes_to_s32(const drwav_uint8* data); - DRWAV_API drwav_uint64 drwav_bytes_to_u64(const drwav_uint8* data); - DRWAV_API drwav_int64 drwav_bytes_to_s64(const drwav_uint8* data); - DRWAV_API float drwav_bytes_to_f32(const drwav_uint8* data); - - /* Compares a GUID for the purpose of checking the type of a Wave64 chunk. */ - DRWAV_API drwav_bool32 drwav_guid_equal(const drwav_uint8 a[16], const drwav_uint8 b[16]); - - /* Compares a four-character-code for the purpose of checking the type of a RIFF chunk. */ - DRWAV_API drwav_bool32 drwav_fourcc_equal(const drwav_uint8* a, const char* b); - -#ifdef __cplusplus -} -#endif -#endif /* dr_wav_h */ - - -/************************************************************************************************************************************************************ - ************************************************************************************************************************************************************ - - IMPLEMENTATION - - ************************************************************************************************************************************************************ - ************************************************************************************************************************************************************/ -#if defined(DR_WAV_IMPLEMENTATION) || defined(DRWAV_IMPLEMENTATION) -#ifndef dr_wav_c -#define dr_wav_c - -#include -#include -#include /* For INT_MAX */ - -#ifndef DR_WAV_NO_STDIO -#include -#include -#endif - - /* Standard library stuff. */ -#ifndef DRWAV_ASSERT -#include -#define DRWAV_ASSERT(expression) assert(expression) -#endif -#ifndef DRWAV_MALLOC -#define DRWAV_MALLOC(sz) malloc((sz)) -#endif -#ifndef DRWAV_REALLOC -#define DRWAV_REALLOC(p, sz) realloc((p), (sz)) -#endif -#ifndef DRWAV_FREE -#define DRWAV_FREE(p) free((p)) -#endif -#ifndef DRWAV_COPY_MEMORY -#define DRWAV_COPY_MEMORY(dst, src, sz) memcpy((dst), (src), (sz)) -#endif -#ifndef DRWAV_ZERO_MEMORY -#define DRWAV_ZERO_MEMORY(p, sz) memset((p), 0, (sz)) -#endif -#ifndef DRWAV_ZERO_OBJECT -#define DRWAV_ZERO_OBJECT(p) DRWAV_ZERO_MEMORY((p), sizeof(*p)) -#endif - -#define drwav_countof(x) (sizeof(x) / sizeof(x[0])) -#define drwav_align(x, a) ((((x) + (a) - 1) / (a)) * (a)) -#define drwav_min(a, b) (((a) < (b)) ? (a) : (b)) -#define drwav_max(a, b) (((a) > (b)) ? (a) : (b)) -#define drwav_clamp(x, lo, hi) (drwav_max((lo), drwav_min((hi), (x)))) -#define drwav_offset_ptr(p, offset) (((drwav_uint8*)(p)) + (offset)) - -#define DRWAV_MAX_SIMD_VECTOR_SIZE 64 /* 64 for AVX-512 in the future. */ - -/* CPU architecture. */ -#if defined(__x86_64__) || defined(_M_X64) -#define DRWAV_X64 -#elif defined(__i386) || defined(_M_IX86) -#define DRWAV_X86 -#elif defined(__arm__) || defined(_M_ARM) -#define DRWAV_ARM -#endif - -#ifdef _MSC_VER -#define DRWAV_INLINE __forceinline -#elif defined(__GNUC__) - /* - I've had a bug report where GCC is emitting warnings about functions possibly not being inlineable. This warning happens when - the __attribute__((always_inline)) attribute is defined without an "inline" statement. I think therefore there must be some - case where "__inline__" is not always defined, thus the compiler emitting these warnings. When using -std=c89 or -ansi on the - command line, we cannot use the "inline" keyword and instead need to use "__inline__". In an attempt to work around this issue - I am using "__inline__" only when we're compiling in strict ANSI mode. - */ -#if defined(__STRICT_ANSI__) -#define DRWAV_GNUC_INLINE_HINT __inline__ -#else -#define DRWAV_GNUC_INLINE_HINT inline -#endif - -#if (__GNUC__ > 3 || (__GNUC__ == 3 && __GNUC_MINOR__ >= 2)) || defined(__clang__) -#define DRWAV_INLINE DRWAV_GNUC_INLINE_HINT __attribute__((always_inline)) -#else -#define DRWAV_INLINE DRWAV_GNUC_INLINE_HINT -#endif -#elif defined(__WATCOMC__) -#define DRWAV_INLINE __inline -#else -#define DRWAV_INLINE -#endif - -#if defined(SIZE_MAX) -#define DRWAV_SIZE_MAX SIZE_MAX -#else -#if defined(_WIN64) || defined(_LP64) || defined(__LP64__) -#define DRWAV_SIZE_MAX ((drwav_uint64)0xFFFFFFFFFFFFFFFF) -#else -#define DRWAV_SIZE_MAX 0xFFFFFFFF -#endif -#endif - -#if defined(_MSC_VER) && _MSC_VER >= 1400 -#define DRWAV_HAS_BYTESWAP16_INTRINSIC -#define DRWAV_HAS_BYTESWAP32_INTRINSIC -#define DRWAV_HAS_BYTESWAP64_INTRINSIC -#elif defined(__clang__) -#if defined(__has_builtin) -#if __has_builtin(__builtin_bswap16) -#define DRWAV_HAS_BYTESWAP16_INTRINSIC -#endif -#if __has_builtin(__builtin_bswap32) -#define DRWAV_HAS_BYTESWAP32_INTRINSIC -#endif -#if __has_builtin(__builtin_bswap64) -#define DRWAV_HAS_BYTESWAP64_INTRINSIC -#endif -#endif -#elif defined(__GNUC__) -#if ((__GNUC__ > 4) || (__GNUC__ == 4 && __GNUC_MINOR__ >= 3)) -#define DRWAV_HAS_BYTESWAP32_INTRINSIC -#define DRWAV_HAS_BYTESWAP64_INTRINSIC -#endif -#if ((__GNUC__ > 4) || (__GNUC__ == 4 && __GNUC_MINOR__ >= 8)) -#define DRWAV_HAS_BYTESWAP16_INTRINSIC -#endif -#endif - -DRWAV_API void drwav_version(drwav_uint32* pMajor, drwav_uint32* pMinor, drwav_uint32* pRevision) -{ - if (pMajor) { - *pMajor = DRWAV_VERSION_MAJOR; - } - - if (pMinor) { - *pMinor = DRWAV_VERSION_MINOR; - } - - if (pRevision) { - *pRevision = DRWAV_VERSION_REVISION; - } -} - -DRWAV_API const char* drwav_version_string(void) -{ - return DRWAV_VERSION_STRING; -} - -/* -These limits are used for basic validation when initializing the decoder. If you exceed these limits, first of all: what on Earth are -you doing?! (Let me know, I'd be curious!) Second, you can adjust these by #define-ing them before the dr_wav implementation. -*/ -#ifndef DRWAV_MAX_SAMPLE_RATE -#define DRWAV_MAX_SAMPLE_RATE 384000 -#endif -#ifndef DRWAV_MAX_CHANNELS -#define DRWAV_MAX_CHANNELS 256 -#endif -#ifndef DRWAV_MAX_BITS_PER_SAMPLE -#define DRWAV_MAX_BITS_PER_SAMPLE 64 -#endif - -static const drwav_uint8 drwavGUID_W64_RIFF[16] = { 0x72,0x69,0x66,0x66, 0x2E,0x91, 0xCF,0x11, 0xA5,0xD6, 0x28,0xDB,0x04,0xC1,0x00,0x00 }; /* 66666972-912E-11CF-A5D6-28DB04C10000 */ -static const drwav_uint8 drwavGUID_W64_WAVE[16] = { 0x77,0x61,0x76,0x65, 0xF3,0xAC, 0xD3,0x11, 0x8C,0xD1, 0x00,0xC0,0x4F,0x8E,0xDB,0x8A }; /* 65766177-ACF3-11D3-8CD1-00C04F8EDB8A */ -/*static const drwav_uint8 drwavGUID_W64_JUNK[16] = {0x6A,0x75,0x6E,0x6B, 0xF3,0xAC, 0xD3,0x11, 0x8C,0xD1, 0x00,0xC0,0x4F,0x8E,0xDB,0x8A};*/ /* 6B6E756A-ACF3-11D3-8CD1-00C04F8EDB8A */ -static const drwav_uint8 drwavGUID_W64_FMT[16] = { 0x66,0x6D,0x74,0x20, 0xF3,0xAC, 0xD3,0x11, 0x8C,0xD1, 0x00,0xC0,0x4F,0x8E,0xDB,0x8A }; /* 20746D66-ACF3-11D3-8CD1-00C04F8EDB8A */ -static const drwav_uint8 drwavGUID_W64_FACT[16] = { 0x66,0x61,0x63,0x74, 0xF3,0xAC, 0xD3,0x11, 0x8C,0xD1, 0x00,0xC0,0x4F,0x8E,0xDB,0x8A }; /* 74636166-ACF3-11D3-8CD1-00C04F8EDB8A */ -static const drwav_uint8 drwavGUID_W64_DATA[16] = { 0x64,0x61,0x74,0x61, 0xF3,0xAC, 0xD3,0x11, 0x8C,0xD1, 0x00,0xC0,0x4F,0x8E,0xDB,0x8A }; /* 61746164-ACF3-11D3-8CD1-00C04F8EDB8A */ -/*static const drwav_uint8 drwavGUID_W64_SMPL[16] = {0x73,0x6D,0x70,0x6C, 0xF3,0xAC, 0xD3,0x11, 0x8C,0xD1, 0x00,0xC0,0x4F,0x8E,0xDB,0x8A};*/ /* 6C706D73-ACF3-11D3-8CD1-00C04F8EDB8A */ - - -static DRWAV_INLINE int drwav__is_little_endian(void) -{ -#if defined(DRWAV_X86) || defined(DRWAV_X64) - return DRWAV_TRUE; -#elif defined(__BYTE_ORDER) && defined(__LITTLE_ENDIAN) && __BYTE_ORDER == __LITTLE_ENDIAN - return DRWAV_TRUE; -#else - int n = 1; - return (*(char*)&n) == 1; -#endif -} - - -static DRWAV_INLINE void drwav_bytes_to_guid(const drwav_uint8* data, drwav_uint8* guid) -{ - int i; - for (i = 0; i < 16; ++i) { - guid[i] = data[i]; - } -} - - -static DRWAV_INLINE drwav_uint16 drwav__bswap16(drwav_uint16 n) -{ -#ifdef DRWAV_HAS_BYTESWAP16_INTRINSIC -#if defined(_MSC_VER) - return _byteswap_ushort(n); -#elif defined(__GNUC__) || defined(__clang__) - return __builtin_bswap16(n); -#else -#error "This compiler does not support the byte swap intrinsic." -#endif -#else - return ((n & 0xFF00) >> 8) | - ((n & 0x00FF) << 8); -#endif -} - -static DRWAV_INLINE drwav_uint32 drwav__bswap32(drwav_uint32 n) -{ -#ifdef DRWAV_HAS_BYTESWAP32_INTRINSIC -#if defined(_MSC_VER) - return _byteswap_ulong(n); -#elif defined(__GNUC__) || defined(__clang__) -#if defined(DRWAV_ARM) && (defined(__ARM_ARCH) && __ARM_ARCH >= 6) && !defined(DRWAV_64BIT) /* <-- 64-bit inline assembly has not been tested, so disabling for now. */ - /* Inline assembly optimized implementation for ARM. In my testing, GCC does not generate optimized code with __builtin_bswap32(). */ - drwav_uint32 r; - __asm__ __volatile__( -#if defined(DRWAV_64BIT) - "rev %w[out], %w[in]" : [out] "=r"(r) : [in] "r"(n) /* <-- This is untested. If someone in the community could test this, that would be appreciated! */ -#else - "rev %[out], %[in]" : [out] "=r"(r) : [in] "r"(n) -#endif - ); - return r; -#else - return __builtin_bswap32(n); -#endif -#else -#error "This compiler does not support the byte swap intrinsic." -#endif -#else - return ((n & 0xFF000000) >> 24) | - ((n & 0x00FF0000) >> 8) | - ((n & 0x0000FF00) << 8) | - ((n & 0x000000FF) << 24); -#endif -} - -static DRWAV_INLINE drwav_uint64 drwav__bswap64(drwav_uint64 n) -{ -#ifdef DRWAV_HAS_BYTESWAP64_INTRINSIC -#if defined(_MSC_VER) - return _byteswap_uint64(n); -#elif defined(__GNUC__) || defined(__clang__) - return __builtin_bswap64(n); -#else -#error "This compiler does not support the byte swap intrinsic." -#endif -#else - /* Weird "<< 32" bitshift is required for C89 because it doesn't support 64-bit constants. Should be optimized out by a good compiler. */ - return ((n & ((drwav_uint64)0xFF000000 << 32)) >> 56) | - ((n & ((drwav_uint64)0x00FF0000 << 32)) >> 40) | - ((n & ((drwav_uint64)0x0000FF00 << 32)) >> 24) | - ((n & ((drwav_uint64)0x000000FF << 32)) >> 8) | - ((n & ((drwav_uint64)0xFF000000)) << 8) | - ((n & ((drwav_uint64)0x00FF0000)) << 24) | - ((n & ((drwav_uint64)0x0000FF00)) << 40) | - ((n & ((drwav_uint64)0x000000FF)) << 56); -#endif -} - - -static DRWAV_INLINE drwav_int16 drwav__bswap_s16(drwav_int16 n) -{ - return (drwav_int16)drwav__bswap16((drwav_uint16)n); -} - -static DRWAV_INLINE void drwav__bswap_samples_s16(drwav_int16* pSamples, drwav_uint64 sampleCount) -{ - drwav_uint64 iSample; - for (iSample = 0; iSample < sampleCount; iSample += 1) { - pSamples[iSample] = drwav__bswap_s16(pSamples[iSample]); - } -} - - -static DRWAV_INLINE void drwav__bswap_s24(drwav_uint8* p) -{ - drwav_uint8 t; - t = p[0]; - p[0] = p[2]; - p[2] = t; -} - -static DRWAV_INLINE void drwav__bswap_samples_s24(drwav_uint8* pSamples, drwav_uint64 sampleCount) -{ - drwav_uint64 iSample; - for (iSample = 0; iSample < sampleCount; iSample += 1) { - drwav_uint8* pSample = pSamples + (iSample * 3); - drwav__bswap_s24(pSample); - } -} - - -static DRWAV_INLINE drwav_int32 drwav__bswap_s32(drwav_int32 n) -{ - return (drwav_int32)drwav__bswap32((drwav_uint32)n); -} - -static DRWAV_INLINE void drwav__bswap_samples_s32(drwav_int32* pSamples, drwav_uint64 sampleCount) -{ - drwav_uint64 iSample; - for (iSample = 0; iSample < sampleCount; iSample += 1) { - pSamples[iSample] = drwav__bswap_s32(pSamples[iSample]); - } -} - - -static DRWAV_INLINE float drwav__bswap_f32(float n) -{ - union { - drwav_uint32 i; - float f; - } x; - x.f = n; - x.i = drwav__bswap32(x.i); - - return x.f; -} - -static DRWAV_INLINE void drwav__bswap_samples_f32(float* pSamples, drwav_uint64 sampleCount) -{ - drwav_uint64 iSample; - for (iSample = 0; iSample < sampleCount; iSample += 1) { - pSamples[iSample] = drwav__bswap_f32(pSamples[iSample]); - } -} - - -static DRWAV_INLINE double drwav__bswap_f64(double n) -{ - union { - drwav_uint64 i; - double f; - } x; - x.f = n; - x.i = drwav__bswap64(x.i); - - return x.f; -} - -static DRWAV_INLINE void drwav__bswap_samples_f64(double* pSamples, drwav_uint64 sampleCount) -{ - drwav_uint64 iSample; - for (iSample = 0; iSample < sampleCount; iSample += 1) { - pSamples[iSample] = drwav__bswap_f64(pSamples[iSample]); - } -} - - -static DRWAV_INLINE void drwav__bswap_samples_pcm(void* pSamples, drwav_uint64 sampleCount, drwav_uint32 bytesPerSample) -{ - /* Assumes integer PCM. Floating point PCM is done in drwav__bswap_samples_ieee(). */ - switch (bytesPerSample) - { - case 1: /* u8 */ - { - /* no-op. */ - } break; - case 2: /* s16, s12 (loosely packed) */ - { - drwav__bswap_samples_s16((drwav_int16*)pSamples, sampleCount); - } break; - case 3: /* s24 */ - { - drwav__bswap_samples_s24((drwav_uint8*)pSamples, sampleCount); - } break; - case 4: /* s32 */ - { - drwav__bswap_samples_s32((drwav_int32*)pSamples, sampleCount); - } break; - default: - { - /* Unsupported format. */ - DRWAV_ASSERT(DRWAV_FALSE); - } break; - } -} - -static DRWAV_INLINE void drwav__bswap_samples_ieee(void* pSamples, drwav_uint64 sampleCount, drwav_uint32 bytesPerSample) -{ - switch (bytesPerSample) - { -#if 0 /* Contributions welcome for f16 support. */ - case 2: /* f16 */ - { - drwav__bswap_samples_f16((drwav_float16*)pSamples, sampleCount); - } break; -#endif - case 4: /* f32 */ - { - drwav__bswap_samples_f32((float*)pSamples, sampleCount); - } break; - case 8: /* f64 */ - { - drwav__bswap_samples_f64((double*)pSamples, sampleCount); - } break; - default: - { - /* Unsupported format. */ - DRWAV_ASSERT(DRWAV_FALSE); - } break; - } -} - -static DRWAV_INLINE void drwav__bswap_samples(void* pSamples, drwav_uint64 sampleCount, drwav_uint32 bytesPerSample, drwav_uint16 format) -{ - switch (format) - { - case DR_WAVE_FORMAT_PCM: - { - drwav__bswap_samples_pcm(pSamples, sampleCount, bytesPerSample); - } break; - - case DR_WAVE_FORMAT_IEEE_FLOAT: - { - drwav__bswap_samples_ieee(pSamples, sampleCount, bytesPerSample); - } break; - - case DR_WAVE_FORMAT_ALAW: - case DR_WAVE_FORMAT_MULAW: - { - drwav__bswap_samples_s16((drwav_int16*)pSamples, sampleCount); - } break; - - case DR_WAVE_FORMAT_ADPCM: - case DR_WAVE_FORMAT_DVI_ADPCM: - default: - { - /* Unsupported format. */ - DRWAV_ASSERT(DRWAV_FALSE); - } break; - } -} - - -DRWAV_PRIVATE void* drwav__malloc_default(size_t sz, void* pUserData) -{ - (void)pUserData; - return DRWAV_MALLOC(sz); -} - -DRWAV_PRIVATE void* drwav__realloc_default(void* p, size_t sz, void* pUserData) -{ - (void)pUserData; - return DRWAV_REALLOC(p, sz); -} - -DRWAV_PRIVATE void drwav__free_default(void* p, void* pUserData) -{ - (void)pUserData; - DRWAV_FREE(p); -} - - -DRWAV_PRIVATE void* drwav__malloc_from_callbacks(size_t sz, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - if (pAllocationCallbacks == NULL) { - return NULL; - } - - if (pAllocationCallbacks->onMalloc != NULL) { - return pAllocationCallbacks->onMalloc(sz, pAllocationCallbacks->pUserData); - } - - /* Try using realloc(). */ - if (pAllocationCallbacks->onRealloc != NULL) { - return pAllocationCallbacks->onRealloc(NULL, sz, pAllocationCallbacks->pUserData); - } - - return NULL; -} - -DRWAV_PRIVATE void* drwav__realloc_from_callbacks(void* p, size_t szNew, size_t szOld, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - if (pAllocationCallbacks == NULL) { - return NULL; - } - - if (pAllocationCallbacks->onRealloc != NULL) { - return pAllocationCallbacks->onRealloc(p, szNew, pAllocationCallbacks->pUserData); - } - - /* Try emulating realloc() in terms of malloc()/free(). */ - if (pAllocationCallbacks->onMalloc != NULL && pAllocationCallbacks->onFree != NULL) { - void* p2; - - p2 = pAllocationCallbacks->onMalloc(szNew, pAllocationCallbacks->pUserData); - if (p2 == NULL) { - return NULL; - } - - if (p != NULL) { - DRWAV_COPY_MEMORY(p2, p, szOld); - pAllocationCallbacks->onFree(p, pAllocationCallbacks->pUserData); - } - - return p2; - } - - return NULL; -} - -DRWAV_PRIVATE void drwav__free_from_callbacks(void* p, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - if (p == NULL || pAllocationCallbacks == NULL) { - return; - } - - if (pAllocationCallbacks->onFree != NULL) { - pAllocationCallbacks->onFree(p, pAllocationCallbacks->pUserData); - } -} - - -DRWAV_PRIVATE drwav_allocation_callbacks drwav_copy_allocation_callbacks_or_defaults(const drwav_allocation_callbacks* pAllocationCallbacks) -{ - if (pAllocationCallbacks != NULL) { - /* Copy. */ - return *pAllocationCallbacks; - } - else { - /* Defaults. */ - drwav_allocation_callbacks allocationCallbacks; - allocationCallbacks.pUserData = NULL; - allocationCallbacks.onMalloc = drwav__malloc_default; - allocationCallbacks.onRealloc = drwav__realloc_default; - allocationCallbacks.onFree = drwav__free_default; - return allocationCallbacks; - } -} - - -static DRWAV_INLINE drwav_bool32 drwav__is_compressed_format_tag(drwav_uint16 formatTag) -{ - return - formatTag == DR_WAVE_FORMAT_ADPCM || - formatTag == DR_WAVE_FORMAT_DVI_ADPCM; -} - -DRWAV_PRIVATE unsigned int drwav__chunk_padding_size_riff(drwav_uint64 chunkSize) -{ - return (unsigned int)(chunkSize % 2); -} - -DRWAV_PRIVATE unsigned int drwav__chunk_padding_size_w64(drwav_uint64 chunkSize) -{ - return (unsigned int)(chunkSize % 8); -} - -DRWAV_PRIVATE drwav_uint64 drwav_read_pcm_frames_s16__msadpcm(drwav* pWav, drwav_uint64 samplesToRead, drwav_int16* pBufferOut); -DRWAV_PRIVATE drwav_uint64 drwav_read_pcm_frames_s16__ima(drwav* pWav, drwav_uint64 samplesToRead, drwav_int16* pBufferOut); -DRWAV_PRIVATE drwav_bool32 drwav_init_write__internal(drwav* pWav, const drwav_data_format* pFormat, drwav_uint64 totalSampleCount); - -DRWAV_PRIVATE drwav_result drwav__read_chunk_header(drwav_read_proc onRead, void* pUserData, drwav_container container, drwav_uint64* pRunningBytesReadOut, drwav_chunk_header* pHeaderOut) -{ - if (container == drwav_container_riff || container == drwav_container_rf64) { - drwav_uint8 sizeInBytes[4]; - - if (onRead(pUserData, pHeaderOut->id.fourcc, 4) != 4) { - return DRWAV_AT_END; - } - - if (onRead(pUserData, sizeInBytes, 4) != 4) { - return DRWAV_INVALID_FILE; - } - - pHeaderOut->sizeInBytes = drwav_bytes_to_u32(sizeInBytes); - pHeaderOut->paddingSize = drwav__chunk_padding_size_riff(pHeaderOut->sizeInBytes); - *pRunningBytesReadOut += 8; - } - else { - drwav_uint8 sizeInBytes[8]; - - if (onRead(pUserData, pHeaderOut->id.guid, 16) != 16) { - return DRWAV_AT_END; - } - - if (onRead(pUserData, sizeInBytes, 8) != 8) { - return DRWAV_INVALID_FILE; - } - - pHeaderOut->sizeInBytes = drwav_bytes_to_u64(sizeInBytes) - 24; /* <-- Subtract 24 because w64 includes the size of the header. */ - pHeaderOut->paddingSize = drwav__chunk_padding_size_w64(pHeaderOut->sizeInBytes); - *pRunningBytesReadOut += 24; - } - - return DRWAV_SUCCESS; -} - -DRWAV_PRIVATE drwav_bool32 drwav__seek_forward(drwav_seek_proc onSeek, drwav_uint64 offset, void* pUserData) -{ - drwav_uint64 bytesRemainingToSeek = offset; - while (bytesRemainingToSeek > 0) { - if (bytesRemainingToSeek > 0x7FFFFFFF) { - if (!onSeek(pUserData, 0x7FFFFFFF, drwav_seek_origin_current)) { - return DRWAV_FALSE; - } - bytesRemainingToSeek -= 0x7FFFFFFF; - } - else { - if (!onSeek(pUserData, (int)bytesRemainingToSeek, drwav_seek_origin_current)) { - return DRWAV_FALSE; - } - bytesRemainingToSeek = 0; - } - } - - return DRWAV_TRUE; -} - -DRWAV_PRIVATE drwav_bool32 drwav__seek_from_start(drwav_seek_proc onSeek, drwav_uint64 offset, void* pUserData) -{ - if (offset <= 0x7FFFFFFF) { - return onSeek(pUserData, (int)offset, drwav_seek_origin_start); - } - - /* Larger than 32-bit seek. */ - if (!onSeek(pUserData, 0x7FFFFFFF, drwav_seek_origin_start)) { - return DRWAV_FALSE; - } - offset -= 0x7FFFFFFF; - - for (;;) { - if (offset <= 0x7FFFFFFF) { - return onSeek(pUserData, (int)offset, drwav_seek_origin_current); - } - - if (!onSeek(pUserData, 0x7FFFFFFF, drwav_seek_origin_current)) { - return DRWAV_FALSE; - } - offset -= 0x7FFFFFFF; - } - - /* Should never get here. */ - /*return DRWAV_TRUE; */ -} - - -DRWAV_PRIVATE drwav_bool32 drwav__read_fmt(drwav_read_proc onRead, drwav_seek_proc onSeek, void* pUserData, drwav_container container, drwav_uint64* pRunningBytesReadOut, drwav_fmt* fmtOut) -{ - drwav_chunk_header header; - drwav_uint8 fmt[16]; - - if (drwav__read_chunk_header(onRead, pUserData, container, pRunningBytesReadOut, &header) != DRWAV_SUCCESS) { - return DRWAV_FALSE; - } - - - /* Skip non-fmt chunks. */ - while (((container == drwav_container_riff || container == drwav_container_rf64) && !drwav_fourcc_equal(header.id.fourcc, "fmt ")) || (container == drwav_container_w64 && !drwav_guid_equal(header.id.guid, drwavGUID_W64_FMT))) { - if (!drwav__seek_forward(onSeek, header.sizeInBytes + header.paddingSize, pUserData)) { - return DRWAV_FALSE; - } - *pRunningBytesReadOut += header.sizeInBytes + header.paddingSize; - - /* Try the next header. */ - if (drwav__read_chunk_header(onRead, pUserData, container, pRunningBytesReadOut, &header) != DRWAV_SUCCESS) { - return DRWAV_FALSE; - } - } - - - /* Validation. */ - if (container == drwav_container_riff || container == drwav_container_rf64) { - if (!drwav_fourcc_equal(header.id.fourcc, "fmt ")) { - return DRWAV_FALSE; - } - } - else { - if (!drwav_guid_equal(header.id.guid, drwavGUID_W64_FMT)) { - return DRWAV_FALSE; - } - } - - - if (onRead(pUserData, fmt, sizeof(fmt)) != sizeof(fmt)) { - return DRWAV_FALSE; - } - *pRunningBytesReadOut += sizeof(fmt); - - fmtOut->formatTag = drwav_bytes_to_u16(fmt + 0); - fmtOut->channels = drwav_bytes_to_u16(fmt + 2); - fmtOut->sampleRate = drwav_bytes_to_u32(fmt + 4); - fmtOut->avgBytesPerSec = drwav_bytes_to_u32(fmt + 8); - fmtOut->blockAlign = drwav_bytes_to_u16(fmt + 12); - fmtOut->bitsPerSample = drwav_bytes_to_u16(fmt + 14); - - fmtOut->extendedSize = 0; - fmtOut->validBitsPerSample = 0; - fmtOut->channelMask = 0; - DRWAV_ZERO_MEMORY(fmtOut->subFormat, sizeof(fmtOut->subFormat)); - - if (header.sizeInBytes > 16) { - drwav_uint8 fmt_cbSize[2]; - int bytesReadSoFar = 0; - - if (onRead(pUserData, fmt_cbSize, sizeof(fmt_cbSize)) != sizeof(fmt_cbSize)) { - return DRWAV_FALSE; /* Expecting more data. */ - } - *pRunningBytesReadOut += sizeof(fmt_cbSize); - - bytesReadSoFar = 18; - - fmtOut->extendedSize = drwav_bytes_to_u16(fmt_cbSize); - if (fmtOut->extendedSize > 0) { - /* Simple validation. */ - if (fmtOut->formatTag == DR_WAVE_FORMAT_EXTENSIBLE) { - if (fmtOut->extendedSize != 22) { - return DRWAV_FALSE; - } - } - - if (fmtOut->formatTag == DR_WAVE_FORMAT_EXTENSIBLE) { - drwav_uint8 fmtext[22]; - if (onRead(pUserData, fmtext, fmtOut->extendedSize) != fmtOut->extendedSize) { - return DRWAV_FALSE; /* Expecting more data. */ - } - - fmtOut->validBitsPerSample = drwav_bytes_to_u16(fmtext + 0); - fmtOut->channelMask = drwav_bytes_to_u32(fmtext + 2); - drwav_bytes_to_guid(fmtext + 6, fmtOut->subFormat); - } - else { - if (!onSeek(pUserData, fmtOut->extendedSize, drwav_seek_origin_current)) { - return DRWAV_FALSE; - } - } - *pRunningBytesReadOut += fmtOut->extendedSize; - - bytesReadSoFar += fmtOut->extendedSize; - } - - /* Seek past any leftover bytes. For w64 the leftover will be defined based on the chunk size. */ - if (!onSeek(pUserData, (int)(header.sizeInBytes - bytesReadSoFar), drwav_seek_origin_current)) { - return DRWAV_FALSE; - } - *pRunningBytesReadOut += (header.sizeInBytes - bytesReadSoFar); - } - - if (header.paddingSize > 0) { - if (!onSeek(pUserData, header.paddingSize, drwav_seek_origin_current)) { - return DRWAV_FALSE; - } - *pRunningBytesReadOut += header.paddingSize; - } - - return DRWAV_TRUE; -} - - -DRWAV_PRIVATE size_t drwav__on_read(drwav_read_proc onRead, void* pUserData, void* pBufferOut, size_t bytesToRead, drwav_uint64* pCursor) -{ - size_t bytesRead; - - DRWAV_ASSERT(onRead != NULL); - DRWAV_ASSERT(pCursor != NULL); - - bytesRead = onRead(pUserData, pBufferOut, bytesToRead); - *pCursor += bytesRead; - return bytesRead; -} - -#if 0 -DRWAV_PRIVATE drwav_bool32 drwav__on_seek(drwav_seek_proc onSeek, void* pUserData, int offset, drwav_seek_origin origin, drwav_uint64* pCursor) -{ - DRWAV_ASSERT(onSeek != NULL); - DRWAV_ASSERT(pCursor != NULL); - - if (!onSeek(pUserData, offset, origin)) { - return DRWAV_FALSE; - } - - if (origin == drwav_seek_origin_start) { - *pCursor = offset; - } - else { - *pCursor += offset; - } - - return DRWAV_TRUE; -} -#endif - - -#define DRWAV_SMPL_BYTES 36 -#define DRWAV_SMPL_LOOP_BYTES 24 -#define DRWAV_INST_BYTES 7 -#define DRWAV_ACID_BYTES 24 -#define DRWAV_CUE_BYTES 4 -#define DRWAV_BEXT_BYTES 602 -#define DRWAV_BEXT_DESCRIPTION_BYTES 256 -#define DRWAV_BEXT_ORIGINATOR_NAME_BYTES 32 -#define DRWAV_BEXT_ORIGINATOR_REF_BYTES 32 -#define DRWAV_BEXT_RESERVED_BYTES 180 -#define DRWAV_BEXT_UMID_BYTES 64 -#define DRWAV_CUE_POINT_BYTES 24 -#define DRWAV_LIST_LABEL_OR_NOTE_BYTES 4 -#define DRWAV_LIST_LABELLED_TEXT_BYTES 20 - -#define DRWAV_METADATA_ALIGNMENT 8 - -typedef enum -{ - drwav__metadata_parser_stage_count, - drwav__metadata_parser_stage_read -} drwav__metadata_parser_stage; - -typedef struct -{ - drwav_read_proc onRead; - drwav_seek_proc onSeek; - void* pReadSeekUserData; - drwav__metadata_parser_stage stage; - drwav_metadata* pMetadata; - drwav_uint32 metadataCount; - drwav_uint8* pData; - drwav_uint8* pDataCursor; - drwav_uint64 metadataCursor; - drwav_uint64 extraCapacity; -} drwav__metadata_parser; - -DRWAV_PRIVATE size_t drwav__metadata_memory_capacity(drwav__metadata_parser* pParser) -{ - drwav_uint64 cap = sizeof(drwav_metadata) * (drwav_uint64)pParser->metadataCount + pParser->extraCapacity; - if (cap > DRWAV_SIZE_MAX) { - return 0; /* Too big. */ - } - - return (size_t)cap; /* Safe cast thanks to the check above. */ -} - -DRWAV_PRIVATE drwav_uint8* drwav__metadata_get_memory(drwav__metadata_parser* pParser, size_t size, size_t align) -{ - drwav_uint8* pResult; - - if (align) { - drwav_uintptr modulo = (drwav_uintptr)pParser->pDataCursor % align; - if (modulo != 0) { - pParser->pDataCursor += align - modulo; - } - } - - pResult = pParser->pDataCursor; - - /* - Getting to the point where this function is called means there should always be memory - available. Out of memory checks should have been done at an earlier stage. - */ - DRWAV_ASSERT((pResult + size) <= (pParser->pData + drwav__metadata_memory_capacity(pParser))); - - pParser->pDataCursor += size; - return pResult; -} - -DRWAV_PRIVATE void drwav__metadata_request_extra_memory_for_stage_2(drwav__metadata_parser* pParser, size_t bytes, size_t align) -{ - size_t extra = bytes + (align ? (align - 1) : 0); - pParser->extraCapacity += extra; -} - -DRWAV_PRIVATE drwav_result drwav__metadata_alloc(drwav__metadata_parser* pParser, drwav_allocation_callbacks* pAllocationCallbacks) -{ - if (pParser->extraCapacity != 0 || pParser->metadataCount != 0) { - pAllocationCallbacks->onFree(pParser->pData, pAllocationCallbacks->pUserData); - - pParser->pData = (drwav_uint8*)pAllocationCallbacks->onMalloc(drwav__metadata_memory_capacity(pParser), pAllocationCallbacks->pUserData); - pParser->pDataCursor = pParser->pData; - - if (pParser->pData == NULL) { - return DRWAV_OUT_OF_MEMORY; - } - - /* - We don't need to worry about specifying an alignment here because malloc always returns something - of suitable alignment. This also means than pParser->pMetadata is all that we need to store in order - for us to free when we are done. - */ - pParser->pMetadata = (drwav_metadata*)drwav__metadata_get_memory(pParser, sizeof(drwav_metadata) * pParser->metadataCount, 1); - pParser->metadataCursor = 0; - } - - return DRWAV_SUCCESS; -} - -DRWAV_PRIVATE size_t drwav__metadata_parser_read(drwav__metadata_parser* pParser, void* pBufferOut, size_t bytesToRead, drwav_uint64* pCursor) -{ - if (pCursor != NULL) { - return drwav__on_read(pParser->onRead, pParser->pReadSeekUserData, pBufferOut, bytesToRead, pCursor); - } - else { - return pParser->onRead(pParser->pReadSeekUserData, pBufferOut, bytesToRead); - } -} - -DRWAV_PRIVATE drwav_uint64 drwav__read_smpl_to_metadata_obj(drwav__metadata_parser* pParser, const drwav_chunk_header* pChunkHeader, drwav_metadata* pMetadata) -{ - drwav_uint8 smplHeaderData[DRWAV_SMPL_BYTES]; - drwav_uint64 totalBytesRead = 0; - size_t bytesJustRead = drwav__metadata_parser_read(pParser, smplHeaderData, sizeof(smplHeaderData), &totalBytesRead); - - DRWAV_ASSERT(pParser->stage == drwav__metadata_parser_stage_read); - DRWAV_ASSERT(pChunkHeader != NULL); - - if (bytesJustRead == sizeof(smplHeaderData)) { - drwav_uint32 iSampleLoop; - - pMetadata->type = drwav_metadata_type_smpl; - pMetadata->data.smpl.manufacturerId = drwav_bytes_to_u32(smplHeaderData + 0); - pMetadata->data.smpl.productId = drwav_bytes_to_u32(smplHeaderData + 4); - pMetadata->data.smpl.samplePeriodNanoseconds = drwav_bytes_to_u32(smplHeaderData + 8); - pMetadata->data.smpl.midiUnityNote = drwav_bytes_to_u32(smplHeaderData + 12); - pMetadata->data.smpl.midiPitchFraction = drwav_bytes_to_u32(smplHeaderData + 16); - pMetadata->data.smpl.smpteFormat = drwav_bytes_to_u32(smplHeaderData + 20); - pMetadata->data.smpl.smpteOffset = drwav_bytes_to_u32(smplHeaderData + 24); - pMetadata->data.smpl.sampleLoopCount = drwav_bytes_to_u32(smplHeaderData + 28); - pMetadata->data.smpl.samplerSpecificDataSizeInBytes = drwav_bytes_to_u32(smplHeaderData + 32); - - /* - The loop count needs to be validated against the size of the chunk for safety so we don't - attempt to read over the boundary of the chunk. - */ - if (pMetadata->data.smpl.sampleLoopCount == (pChunkHeader->sizeInBytes - DRWAV_SMPL_BYTES) / DRWAV_SMPL_LOOP_BYTES) { - pMetadata->data.smpl.pLoops = (drwav_smpl_loop*)drwav__metadata_get_memory(pParser, sizeof(drwav_smpl_loop) * pMetadata->data.smpl.sampleLoopCount, DRWAV_METADATA_ALIGNMENT); - - for (iSampleLoop = 0; iSampleLoop < pMetadata->data.smpl.sampleLoopCount; ++iSampleLoop) { - drwav_uint8 smplLoopData[DRWAV_SMPL_LOOP_BYTES]; - bytesJustRead = drwav__metadata_parser_read(pParser, smplLoopData, sizeof(smplLoopData), &totalBytesRead); - - if (bytesJustRead == sizeof(smplLoopData)) { - pMetadata->data.smpl.pLoops[iSampleLoop].cuePointId = drwav_bytes_to_u32(smplLoopData + 0); - pMetadata->data.smpl.pLoops[iSampleLoop].type = drwav_bytes_to_u32(smplLoopData + 4); - pMetadata->data.smpl.pLoops[iSampleLoop].firstSampleByteOffset = drwav_bytes_to_u32(smplLoopData + 8); - pMetadata->data.smpl.pLoops[iSampleLoop].lastSampleByteOffset = drwav_bytes_to_u32(smplLoopData + 12); - pMetadata->data.smpl.pLoops[iSampleLoop].sampleFraction = drwav_bytes_to_u32(smplLoopData + 16); - pMetadata->data.smpl.pLoops[iSampleLoop].playCount = drwav_bytes_to_u32(smplLoopData + 20); - } - else { - break; - } - } - - if (pMetadata->data.smpl.samplerSpecificDataSizeInBytes > 0) { - pMetadata->data.smpl.pSamplerSpecificData = drwav__metadata_get_memory(pParser, pMetadata->data.smpl.samplerSpecificDataSizeInBytes, 1); - DRWAV_ASSERT(pMetadata->data.smpl.pSamplerSpecificData != NULL); - - drwav__metadata_parser_read(pParser, pMetadata->data.smpl.pSamplerSpecificData, pMetadata->data.smpl.samplerSpecificDataSizeInBytes, &totalBytesRead); - } - } - } - - return totalBytesRead; -} - -DRWAV_PRIVATE drwav_uint64 drwav__read_cue_to_metadata_obj(drwav__metadata_parser* pParser, const drwav_chunk_header* pChunkHeader, drwav_metadata* pMetadata) -{ - drwav_uint8 cueHeaderSectionData[DRWAV_CUE_BYTES]; - drwav_uint64 totalBytesRead = 0; - size_t bytesJustRead = drwav__metadata_parser_read(pParser, cueHeaderSectionData, sizeof(cueHeaderSectionData), &totalBytesRead); - - DRWAV_ASSERT(pParser->stage == drwav__metadata_parser_stage_read); - - if (bytesJustRead == sizeof(cueHeaderSectionData)) { - pMetadata->type = drwav_metadata_type_cue; - pMetadata->data.cue.cuePointCount = drwav_bytes_to_u32(cueHeaderSectionData); - - /* - We need to validate the cue point count against the size of the chunk so we don't read - beyond the chunk. - */ - if (pMetadata->data.cue.cuePointCount == (pChunkHeader->sizeInBytes - DRWAV_CUE_BYTES) / DRWAV_CUE_POINT_BYTES) { - pMetadata->data.cue.pCuePoints = (drwav_cue_point*)drwav__metadata_get_memory(pParser, sizeof(drwav_cue_point) * pMetadata->data.cue.cuePointCount, DRWAV_METADATA_ALIGNMENT); - DRWAV_ASSERT(pMetadata->data.cue.pCuePoints != NULL); - - if (pMetadata->data.cue.cuePointCount > 0) { - drwav_uint32 iCuePoint; - - for (iCuePoint = 0; iCuePoint < pMetadata->data.cue.cuePointCount; ++iCuePoint) { - drwav_uint8 cuePointData[DRWAV_CUE_POINT_BYTES]; - bytesJustRead = drwav__metadata_parser_read(pParser, cuePointData, sizeof(cuePointData), &totalBytesRead); - - if (bytesJustRead == sizeof(cuePointData)) { - pMetadata->data.cue.pCuePoints[iCuePoint].id = drwav_bytes_to_u32(cuePointData + 0); - pMetadata->data.cue.pCuePoints[iCuePoint].playOrderPosition = drwav_bytes_to_u32(cuePointData + 4); - pMetadata->data.cue.pCuePoints[iCuePoint].dataChunkId[0] = cuePointData[8]; - pMetadata->data.cue.pCuePoints[iCuePoint].dataChunkId[1] = cuePointData[9]; - pMetadata->data.cue.pCuePoints[iCuePoint].dataChunkId[2] = cuePointData[10]; - pMetadata->data.cue.pCuePoints[iCuePoint].dataChunkId[3] = cuePointData[11]; - pMetadata->data.cue.pCuePoints[iCuePoint].chunkStart = drwav_bytes_to_u32(cuePointData + 12); - pMetadata->data.cue.pCuePoints[iCuePoint].blockStart = drwav_bytes_to_u32(cuePointData + 16); - pMetadata->data.cue.pCuePoints[iCuePoint].sampleByteOffset = drwav_bytes_to_u32(cuePointData + 20); - } - else { - break; - } - } - } - } - } - - return totalBytesRead; -} - -DRWAV_PRIVATE drwav_uint64 drwav__read_inst_to_metadata_obj(drwav__metadata_parser* pParser, drwav_metadata* pMetadata) -{ - drwav_uint8 instData[DRWAV_INST_BYTES]; - drwav_uint64 bytesRead = drwav__metadata_parser_read(pParser, instData, sizeof(instData), NULL); - - DRWAV_ASSERT(pParser->stage == drwav__metadata_parser_stage_read); - - if (bytesRead == sizeof(instData)) { - pMetadata->type = drwav_metadata_type_inst; - pMetadata->data.inst.midiUnityNote = (drwav_int8)instData[0]; - pMetadata->data.inst.fineTuneCents = (drwav_int8)instData[1]; - pMetadata->data.inst.gainDecibels = (drwav_int8)instData[2]; - pMetadata->data.inst.lowNote = (drwav_int8)instData[3]; - pMetadata->data.inst.highNote = (drwav_int8)instData[4]; - pMetadata->data.inst.lowVelocity = (drwav_int8)instData[5]; - pMetadata->data.inst.highVelocity = (drwav_int8)instData[6]; - } - - return bytesRead; -} - -DRWAV_PRIVATE drwav_uint64 drwav__read_acid_to_metadata_obj(drwav__metadata_parser* pParser, drwav_metadata* pMetadata) -{ - drwav_uint8 acidData[DRWAV_ACID_BYTES]; - drwav_uint64 bytesRead = drwav__metadata_parser_read(pParser, acidData, sizeof(acidData), NULL); - - DRWAV_ASSERT(pParser->stage == drwav__metadata_parser_stage_read); - - if (bytesRead == sizeof(acidData)) { - pMetadata->type = drwav_metadata_type_acid; - pMetadata->data.acid.flags = drwav_bytes_to_u32(acidData + 0); - pMetadata->data.acid.midiUnityNote = drwav_bytes_to_u16(acidData + 4); - pMetadata->data.acid.reserved1 = drwav_bytes_to_u16(acidData + 6); - pMetadata->data.acid.reserved2 = drwav_bytes_to_f32(acidData + 8); - pMetadata->data.acid.numBeats = drwav_bytes_to_u32(acidData + 12); - pMetadata->data.acid.meterDenominator = drwav_bytes_to_u16(acidData + 16); - pMetadata->data.acid.meterNumerator = drwav_bytes_to_u16(acidData + 18); - pMetadata->data.acid.tempo = drwav_bytes_to_f32(acidData + 20); - } - - return bytesRead; -} - -DRWAV_PRIVATE size_t drwav__strlen(const char* str) -{ - size_t result = 0; - - while (*str++) { - result += 1; - } - - return result; -} - -DRWAV_PRIVATE size_t drwav__strlen_clamped(const char* str, size_t maxToRead) -{ - size_t result = 0; - - while (*str++ && result < maxToRead) { - result += 1; - } - - return result; -} - -DRWAV_PRIVATE char* drwav__metadata_copy_string(drwav__metadata_parser* pParser, const char* str, size_t maxToRead) -{ - size_t len = drwav__strlen_clamped(str, maxToRead); - - if (len) { - char* result = (char*)drwav__metadata_get_memory(pParser, len + 1, 1); - DRWAV_ASSERT(result != NULL); - - DRWAV_COPY_MEMORY(result, str, len); - result[len] = '\0'; - - return result; - } - else { - return NULL; - } -} - -typedef struct -{ - const void* pBuffer; - size_t sizeInBytes; - size_t cursor; -} drwav_buffer_reader; - -DRWAV_PRIVATE drwav_result drwav_buffer_reader_init(const void* pBuffer, size_t sizeInBytes, drwav_buffer_reader* pReader) -{ - DRWAV_ASSERT(pBuffer != NULL); - DRWAV_ASSERT(pReader != NULL); - - DRWAV_ZERO_OBJECT(pReader); - - pReader->pBuffer = pBuffer; - pReader->sizeInBytes = sizeInBytes; - pReader->cursor = 0; - - return DRWAV_SUCCESS; -} - -DRWAV_PRIVATE const void* drwav_buffer_reader_ptr(const drwav_buffer_reader* pReader) -{ - DRWAV_ASSERT(pReader != NULL); - - return drwav_offset_ptr(pReader->pBuffer, pReader->cursor); -} - -DRWAV_PRIVATE drwav_result drwav_buffer_reader_seek(drwav_buffer_reader* pReader, size_t bytesToSeek) -{ - DRWAV_ASSERT(pReader != NULL); - - if (pReader->cursor + bytesToSeek > pReader->sizeInBytes) { - return DRWAV_BAD_SEEK; /* Seeking too far forward. */ - } - - pReader->cursor += bytesToSeek; - - return DRWAV_SUCCESS; -} - -DRWAV_PRIVATE drwav_result drwav_buffer_reader_read(drwav_buffer_reader* pReader, void* pDst, size_t bytesToRead, size_t* pBytesRead) -{ - drwav_result result = DRWAV_SUCCESS; - size_t bytesRemaining; - - DRWAV_ASSERT(pReader != NULL); - - if (pBytesRead != NULL) { - *pBytesRead = 0; - } - - bytesRemaining = (pReader->sizeInBytes - pReader->cursor); - if (bytesToRead > bytesRemaining) { - bytesToRead = bytesRemaining; - } - - if (pDst == NULL) { - /* Seek. */ - result = drwav_buffer_reader_seek(pReader, bytesToRead); - } - else { - /* Read. */ - DRWAV_COPY_MEMORY(pDst, drwav_buffer_reader_ptr(pReader), bytesToRead); - pReader->cursor += bytesToRead; - } - - DRWAV_ASSERT(pReader->cursor <= pReader->sizeInBytes); - - if (result == DRWAV_SUCCESS) { - if (pBytesRead != NULL) { - *pBytesRead = bytesToRead; - } - } - - return DRWAV_SUCCESS; -} - -DRWAV_PRIVATE drwav_result drwav_buffer_reader_read_u16(drwav_buffer_reader* pReader, drwav_uint16* pDst) -{ - drwav_result result; - size_t bytesRead; - drwav_uint8 data[2]; - - DRWAV_ASSERT(pReader != NULL); - DRWAV_ASSERT(pDst != NULL); - - *pDst = 0; /* Safety. */ - - result = drwav_buffer_reader_read(pReader, data, sizeof(*pDst), &bytesRead); - if (result != DRWAV_SUCCESS || bytesRead != sizeof(*pDst)) { - return result; - } - - *pDst = drwav_bytes_to_u16(data); - - return DRWAV_SUCCESS; -} - -DRWAV_PRIVATE drwav_result drwav_buffer_reader_read_u32(drwav_buffer_reader* pReader, drwav_uint32* pDst) -{ - drwav_result result; - size_t bytesRead; - drwav_uint8 data[4]; - - DRWAV_ASSERT(pReader != NULL); - DRWAV_ASSERT(pDst != NULL); - - *pDst = 0; /* Safety. */ - - result = drwav_buffer_reader_read(pReader, data, sizeof(*pDst), &bytesRead); - if (result != DRWAV_SUCCESS || bytesRead != sizeof(*pDst)) { - return result; - } - - *pDst = drwav_bytes_to_u32(data); - - return DRWAV_SUCCESS; -} - - - -DRWAV_PRIVATE drwav_uint64 drwav__read_bext_to_metadata_obj(drwav__metadata_parser* pParser, drwav_metadata* pMetadata, drwav_uint64 chunkSize) -{ - drwav_uint8 bextData[DRWAV_BEXT_BYTES]; - size_t bytesRead = drwav__metadata_parser_read(pParser, bextData, sizeof(bextData), NULL); - - DRWAV_ASSERT(pParser->stage == drwav__metadata_parser_stage_read); - - if (bytesRead == sizeof(bextData)) { - drwav_buffer_reader reader; - drwav_uint32 timeReferenceLow; - drwav_uint32 timeReferenceHigh; - size_t extraBytes; - - pMetadata->type = drwav_metadata_type_bext; - - if (drwav_buffer_reader_init(bextData, bytesRead, &reader) == DRWAV_SUCCESS) { - pMetadata->data.bext.pDescription = drwav__metadata_copy_string(pParser, (const char*)drwav_buffer_reader_ptr(&reader), DRWAV_BEXT_DESCRIPTION_BYTES); - drwav_buffer_reader_seek(&reader, DRWAV_BEXT_DESCRIPTION_BYTES); - - pMetadata->data.bext.pOriginatorName = drwav__metadata_copy_string(pParser, (const char*)drwav_buffer_reader_ptr(&reader), DRWAV_BEXT_ORIGINATOR_NAME_BYTES); - drwav_buffer_reader_seek(&reader, DRWAV_BEXT_ORIGINATOR_NAME_BYTES); - - pMetadata->data.bext.pOriginatorReference = drwav__metadata_copy_string(pParser, (const char*)drwav_buffer_reader_ptr(&reader), DRWAV_BEXT_ORIGINATOR_REF_BYTES); - drwav_buffer_reader_seek(&reader, DRWAV_BEXT_ORIGINATOR_REF_BYTES); - - drwav_buffer_reader_read(&reader, pMetadata->data.bext.pOriginationDate, sizeof(pMetadata->data.bext.pOriginationDate), NULL); - drwav_buffer_reader_read(&reader, pMetadata->data.bext.pOriginationTime, sizeof(pMetadata->data.bext.pOriginationTime), NULL); - - drwav_buffer_reader_read_u32(&reader, &timeReferenceLow); - drwav_buffer_reader_read_u32(&reader, &timeReferenceHigh); - pMetadata->data.bext.timeReference = ((drwav_uint64)timeReferenceHigh << 32) + timeReferenceLow; - - drwav_buffer_reader_read_u16(&reader, &pMetadata->data.bext.version); - - pMetadata->data.bext.pUMID = drwav__metadata_get_memory(pParser, DRWAV_BEXT_UMID_BYTES, 1); - drwav_buffer_reader_read(&reader, pMetadata->data.bext.pUMID, DRWAV_BEXT_UMID_BYTES, NULL); - - drwav_buffer_reader_read_u16(&reader, &pMetadata->data.bext.loudnessValue); - drwav_buffer_reader_read_u16(&reader, &pMetadata->data.bext.loudnessRange); - drwav_buffer_reader_read_u16(&reader, &pMetadata->data.bext.maxTruePeakLevel); - drwav_buffer_reader_read_u16(&reader, &pMetadata->data.bext.maxMomentaryLoudness); - drwav_buffer_reader_read_u16(&reader, &pMetadata->data.bext.maxShortTermLoudness); - - DRWAV_ASSERT((drwav_offset_ptr(drwav_buffer_reader_ptr(&reader), DRWAV_BEXT_RESERVED_BYTES)) == (bextData + DRWAV_BEXT_BYTES)); - - extraBytes = (size_t)(chunkSize - DRWAV_BEXT_BYTES); - if (extraBytes > 0) { - pMetadata->data.bext.pCodingHistory = (char*)drwav__metadata_get_memory(pParser, extraBytes + 1, 1); - DRWAV_ASSERT(pMetadata->data.bext.pCodingHistory != NULL); - - bytesRead += drwav__metadata_parser_read(pParser, pMetadata->data.bext.pCodingHistory, extraBytes, NULL); - pMetadata->data.bext.codingHistorySize = (drwav_uint32)drwav__strlen(pMetadata->data.bext.pCodingHistory); - } - else { - pMetadata->data.bext.pCodingHistory = NULL; - pMetadata->data.bext.codingHistorySize = 0; - } - } - } - - return bytesRead; -} - -DRWAV_PRIVATE drwav_uint64 drwav__read_list_label_or_note_to_metadata_obj(drwav__metadata_parser* pParser, drwav_metadata* pMetadata, drwav_uint64 chunkSize, drwav_metadata_type type) -{ - drwav_uint8 cueIDBuffer[DRWAV_LIST_LABEL_OR_NOTE_BYTES]; - drwav_uint64 totalBytesRead = 0; - size_t bytesJustRead = drwav__metadata_parser_read(pParser, cueIDBuffer, sizeof(cueIDBuffer), &totalBytesRead); - - DRWAV_ASSERT(pParser->stage == drwav__metadata_parser_stage_read); - - if (bytesJustRead == sizeof(cueIDBuffer)) { - drwav_uint32 sizeIncludingNullTerminator; - - pMetadata->type = type; - pMetadata->data.labelOrNote.cuePointId = drwav_bytes_to_u32(cueIDBuffer); - - sizeIncludingNullTerminator = (drwav_uint32)chunkSize - DRWAV_LIST_LABEL_OR_NOTE_BYTES; - if (sizeIncludingNullTerminator > 0) { - pMetadata->data.labelOrNote.stringLength = sizeIncludingNullTerminator - 1; - pMetadata->data.labelOrNote.pString = (char*)drwav__metadata_get_memory(pParser, sizeIncludingNullTerminator, 1); - DRWAV_ASSERT(pMetadata->data.labelOrNote.pString != NULL); - - drwav__metadata_parser_read(pParser, pMetadata->data.labelOrNote.pString, sizeIncludingNullTerminator, &totalBytesRead); - } - else { - pMetadata->data.labelOrNote.stringLength = 0; - pMetadata->data.labelOrNote.pString = NULL; - } - } - - return totalBytesRead; -} - -DRWAV_PRIVATE drwav_uint64 drwav__read_list_labelled_cue_region_to_metadata_obj(drwav__metadata_parser* pParser, drwav_metadata* pMetadata, drwav_uint64 chunkSize) -{ - drwav_uint8 buffer[DRWAV_LIST_LABELLED_TEXT_BYTES]; - drwav_uint64 totalBytesRead = 0; - size_t bytesJustRead = drwav__metadata_parser_read(pParser, buffer, sizeof(buffer), &totalBytesRead); - - DRWAV_ASSERT(pParser->stage == drwav__metadata_parser_stage_read); - - if (bytesJustRead == sizeof(buffer)) { - drwav_uint32 sizeIncludingNullTerminator; - - pMetadata->type = drwav_metadata_type_list_labelled_cue_region; - pMetadata->data.labelledCueRegion.cuePointId = drwav_bytes_to_u32(buffer + 0); - pMetadata->data.labelledCueRegion.sampleLength = drwav_bytes_to_u32(buffer + 4); - pMetadata->data.labelledCueRegion.purposeId[0] = buffer[8]; - pMetadata->data.labelledCueRegion.purposeId[1] = buffer[9]; - pMetadata->data.labelledCueRegion.purposeId[2] = buffer[10]; - pMetadata->data.labelledCueRegion.purposeId[3] = buffer[11]; - pMetadata->data.labelledCueRegion.country = drwav_bytes_to_u16(buffer + 12); - pMetadata->data.labelledCueRegion.language = drwav_bytes_to_u16(buffer + 14); - pMetadata->data.labelledCueRegion.dialect = drwav_bytes_to_u16(buffer + 16); - pMetadata->data.labelledCueRegion.codePage = drwav_bytes_to_u16(buffer + 18); - - sizeIncludingNullTerminator = (drwav_uint32)chunkSize - DRWAV_LIST_LABELLED_TEXT_BYTES; - if (sizeIncludingNullTerminator > 0) { - pMetadata->data.labelledCueRegion.stringLength = sizeIncludingNullTerminator - 1; - pMetadata->data.labelledCueRegion.pString = (char*)drwav__metadata_get_memory(pParser, sizeIncludingNullTerminator, 1); - DRWAV_ASSERT(pMetadata->data.labelledCueRegion.pString != NULL); - - drwav__metadata_parser_read(pParser, pMetadata->data.labelledCueRegion.pString, sizeIncludingNullTerminator, &totalBytesRead); - } - else { - pMetadata->data.labelledCueRegion.stringLength = 0; - pMetadata->data.labelledCueRegion.pString = NULL; - } - } - - return totalBytesRead; -} - -DRWAV_PRIVATE drwav_uint64 drwav__metadata_process_info_text_chunk(drwav__metadata_parser* pParser, drwav_uint64 chunkSize, drwav_metadata_type type) -{ - drwav_uint64 bytesRead = 0; - drwav_uint32 stringSizeWithNullTerminator = (drwav_uint32)chunkSize; - - if (pParser->stage == drwav__metadata_parser_stage_count) { - pParser->metadataCount += 1; - drwav__metadata_request_extra_memory_for_stage_2(pParser, stringSizeWithNullTerminator, 1); - } - else { - drwav_metadata* pMetadata = &pParser->pMetadata[pParser->metadataCursor]; - pMetadata->type = type; - if (stringSizeWithNullTerminator > 0) { - pMetadata->data.infoText.stringLength = stringSizeWithNullTerminator - 1; - pMetadata->data.infoText.pString = (char*)drwav__metadata_get_memory(pParser, stringSizeWithNullTerminator, 1); - DRWAV_ASSERT(pMetadata->data.infoText.pString != NULL); - - bytesRead = drwav__metadata_parser_read(pParser, pMetadata->data.infoText.pString, (size_t)stringSizeWithNullTerminator, NULL); - if (bytesRead == chunkSize) { - pParser->metadataCursor += 1; - } - else { - /* Failed to parse. */ - } - } - else { - pMetadata->data.infoText.stringLength = 0; - pMetadata->data.infoText.pString = NULL; - pParser->metadataCursor += 1; - } - } - - return bytesRead; -} - -DRWAV_PRIVATE drwav_uint64 drwav__metadata_process_unknown_chunk(drwav__metadata_parser* pParser, const drwav_uint8* pChunkId, drwav_uint64 chunkSize, drwav_metadata_location location) -{ - drwav_uint64 bytesRead = 0; - - if (location == drwav_metadata_location_invalid) { - return 0; - } - - if (drwav_fourcc_equal(pChunkId, "data") || drwav_fourcc_equal(pChunkId, "fmt") || drwav_fourcc_equal(pChunkId, "fact")) { - return 0; - } - - if (pParser->stage == drwav__metadata_parser_stage_count) { - pParser->metadataCount += 1; - drwav__metadata_request_extra_memory_for_stage_2(pParser, (size_t)chunkSize, 1); - } - else { - drwav_metadata* pMetadata = &pParser->pMetadata[pParser->metadataCursor]; - pMetadata->type = drwav_metadata_type_unknown; - pMetadata->data.unknown.chunkLocation = location; - pMetadata->data.unknown.id[0] = pChunkId[0]; - pMetadata->data.unknown.id[1] = pChunkId[1]; - pMetadata->data.unknown.id[2] = pChunkId[2]; - pMetadata->data.unknown.id[3] = pChunkId[3]; - pMetadata->data.unknown.dataSizeInBytes = (drwav_uint32)chunkSize; - pMetadata->data.unknown.pData = (drwav_uint8*)drwav__metadata_get_memory(pParser, (size_t)chunkSize, 1); - DRWAV_ASSERT(pMetadata->data.unknown.pData != NULL); - - bytesRead = drwav__metadata_parser_read(pParser, pMetadata->data.unknown.pData, pMetadata->data.unknown.dataSizeInBytes, NULL); - if (bytesRead == pMetadata->data.unknown.dataSizeInBytes) { - pParser->metadataCursor += 1; - } - else { - /* Failed to read. */ - } - } - - return bytesRead; -} - -DRWAV_PRIVATE drwav_bool32 drwav__chunk_matches(drwav_metadata_type allowedMetadataTypes, const drwav_uint8* pChunkID, drwav_metadata_type type, const char* pID) -{ - return (allowedMetadataTypes & type) && drwav_fourcc_equal(pChunkID, pID); -} - -DRWAV_PRIVATE drwav_uint64 drwav__metadata_process_chunk(drwav__metadata_parser* pParser, const drwav_chunk_header* pChunkHeader, drwav_metadata_type allowedMetadataTypes) -{ - const drwav_uint8* pChunkID = pChunkHeader->id.fourcc; - drwav_uint64 bytesRead = 0; - - if (drwav__chunk_matches(allowedMetadataTypes, pChunkID, drwav_metadata_type_smpl, "smpl")) { - if (pChunkHeader->sizeInBytes >= DRWAV_SMPL_BYTES) { - if (pParser->stage == drwav__metadata_parser_stage_count) { - drwav_uint8 buffer[4]; - size_t bytesJustRead; - - if (!pParser->onSeek(pParser->pReadSeekUserData, 28, drwav_seek_origin_current)) { - return bytesRead; - } - bytesRead += 28; - - bytesJustRead = drwav__metadata_parser_read(pParser, buffer, sizeof(buffer), &bytesRead); - if (bytesJustRead == sizeof(buffer)) { - drwav_uint32 loopCount = drwav_bytes_to_u32(buffer); - drwav_uint64 calculatedLoopCount; - - /* The loop count must be validated against the size of the chunk. */ - calculatedLoopCount = (pChunkHeader->sizeInBytes - DRWAV_SMPL_BYTES) / DRWAV_SMPL_LOOP_BYTES; - if (calculatedLoopCount == loopCount) { - bytesJustRead = drwav__metadata_parser_read(pParser, buffer, sizeof(buffer), &bytesRead); - if (bytesJustRead == sizeof(buffer)) { - drwav_uint32 samplerSpecificDataSizeInBytes = drwav_bytes_to_u32(buffer); - - pParser->metadataCount += 1; - drwav__metadata_request_extra_memory_for_stage_2(pParser, sizeof(drwav_smpl_loop) * loopCount, DRWAV_METADATA_ALIGNMENT); - drwav__metadata_request_extra_memory_for_stage_2(pParser, samplerSpecificDataSizeInBytes, 1); - } - } - else { - /* Loop count in header does not match the size of the chunk. */ - } - } - } - else { - bytesRead = drwav__read_smpl_to_metadata_obj(pParser, pChunkHeader, &pParser->pMetadata[pParser->metadataCursor]); - if (bytesRead == pChunkHeader->sizeInBytes) { - pParser->metadataCursor += 1; - } - else { - /* Failed to parse. */ - } - } - } - else { - /* Incorrectly formed chunk. */ - } - } - else if (drwav__chunk_matches(allowedMetadataTypes, pChunkID, drwav_metadata_type_inst, "inst")) { - if (pChunkHeader->sizeInBytes == DRWAV_INST_BYTES) { - if (pParser->stage == drwav__metadata_parser_stage_count) { - pParser->metadataCount += 1; - } - else { - bytesRead = drwav__read_inst_to_metadata_obj(pParser, &pParser->pMetadata[pParser->metadataCursor]); - if (bytesRead == pChunkHeader->sizeInBytes) { - pParser->metadataCursor += 1; - } - else { - /* Failed to parse. */ - } - } - } - else { - /* Incorrectly formed chunk. */ - } - } - else if (drwav__chunk_matches(allowedMetadataTypes, pChunkID, drwav_metadata_type_acid, "acid")) { - if (pChunkHeader->sizeInBytes == DRWAV_ACID_BYTES) { - if (pParser->stage == drwav__metadata_parser_stage_count) { - pParser->metadataCount += 1; - } - else { - bytesRead = drwav__read_acid_to_metadata_obj(pParser, &pParser->pMetadata[pParser->metadataCursor]); - if (bytesRead == pChunkHeader->sizeInBytes) { - pParser->metadataCursor += 1; - } - else { - /* Failed to parse. */ - } - } - } - else { - /* Incorrectly formed chunk. */ - } - } - else if (drwav__chunk_matches(allowedMetadataTypes, pChunkID, drwav_metadata_type_cue, "cue ")) { - if (pChunkHeader->sizeInBytes >= DRWAV_CUE_BYTES) { - if (pParser->stage == drwav__metadata_parser_stage_count) { - size_t cueCount; - - pParser->metadataCount += 1; - cueCount = (size_t)(pChunkHeader->sizeInBytes - DRWAV_CUE_BYTES) / DRWAV_CUE_POINT_BYTES; - drwav__metadata_request_extra_memory_for_stage_2(pParser, sizeof(drwav_cue_point) * cueCount, DRWAV_METADATA_ALIGNMENT); - } - else { - bytesRead = drwav__read_cue_to_metadata_obj(pParser, pChunkHeader, &pParser->pMetadata[pParser->metadataCursor]); - if (bytesRead == pChunkHeader->sizeInBytes) { - pParser->metadataCursor += 1; - } - else { - /* Failed to parse. */ - } - } - } - else { - /* Incorrectly formed chunk. */ - } - } - else if (drwav__chunk_matches(allowedMetadataTypes, pChunkID, drwav_metadata_type_bext, "bext")) { - if (pChunkHeader->sizeInBytes >= DRWAV_BEXT_BYTES) { - if (pParser->stage == drwav__metadata_parser_stage_count) { - /* The description field is the largest one in a bext chunk, so that is the max size of this temporary buffer. */ - char buffer[DRWAV_BEXT_DESCRIPTION_BYTES + 1]; - size_t allocSizeNeeded = DRWAV_BEXT_UMID_BYTES; /* We know we will need SMPTE umid size. */ - size_t bytesJustRead; - - buffer[DRWAV_BEXT_DESCRIPTION_BYTES] = '\0'; - bytesJustRead = drwav__metadata_parser_read(pParser, buffer, DRWAV_BEXT_DESCRIPTION_BYTES, &bytesRead); - if (bytesJustRead != DRWAV_BEXT_DESCRIPTION_BYTES) { - return bytesRead; - } - allocSizeNeeded += drwav__strlen(buffer) + 1; - - buffer[DRWAV_BEXT_ORIGINATOR_NAME_BYTES] = '\0'; - bytesJustRead = drwav__metadata_parser_read(pParser, buffer, DRWAV_BEXT_ORIGINATOR_NAME_BYTES, &bytesRead); - if (bytesJustRead != DRWAV_BEXT_ORIGINATOR_NAME_BYTES) { - return bytesRead; - } - allocSizeNeeded += drwav__strlen(buffer) + 1; - - buffer[DRWAV_BEXT_ORIGINATOR_REF_BYTES] = '\0'; - bytesJustRead = drwav__metadata_parser_read(pParser, buffer, DRWAV_BEXT_ORIGINATOR_REF_BYTES, &bytesRead); - if (bytesJustRead != DRWAV_BEXT_ORIGINATOR_REF_BYTES) { - return bytesRead; - } - allocSizeNeeded += drwav__strlen(buffer) + 1; - allocSizeNeeded += (size_t)pChunkHeader->sizeInBytes - DRWAV_BEXT_BYTES; /* Coding history. */ - - drwav__metadata_request_extra_memory_for_stage_2(pParser, allocSizeNeeded, 1); - - pParser->metadataCount += 1; - } - else { - bytesRead = drwav__read_bext_to_metadata_obj(pParser, &pParser->pMetadata[pParser->metadataCursor], pChunkHeader->sizeInBytes); - if (bytesRead == pChunkHeader->sizeInBytes) { - pParser->metadataCursor += 1; - } - else { - /* Failed to parse. */ - } - } - } - else { - /* Incorrectly formed chunk. */ - } - } - else if (drwav_fourcc_equal(pChunkID, "LIST") || drwav_fourcc_equal(pChunkID, "list")) { - drwav_metadata_location listType = drwav_metadata_location_invalid; - while (bytesRead < pChunkHeader->sizeInBytes) { - drwav_uint8 subchunkId[4]; - drwav_uint8 subchunkSizeBuffer[4]; - drwav_uint64 subchunkDataSize; - drwav_uint64 subchunkBytesRead = 0; - drwav_uint64 bytesJustRead = drwav__metadata_parser_read(pParser, subchunkId, sizeof(subchunkId), &bytesRead); - if (bytesJustRead != sizeof(subchunkId)) { - break; - } - - /* - The first thing in a list chunk should be "adtl" or "INFO". - - - adtl means this list is a Associated Data List Chunk and will contain labels, notes - or labelled cue regions. - - INFO means this list is an Info List Chunk containing info text chunks such as IPRD - which would specifies the album of this wav file. - - No data follows the adtl or INFO id so we just make note of what type this list is and - continue. - */ - if (drwav_fourcc_equal(subchunkId, "adtl")) { - listType = drwav_metadata_location_inside_adtl_list; - continue; - } - else if (drwav_fourcc_equal(subchunkId, "INFO")) { - listType = drwav_metadata_location_inside_info_list; - continue; - } - - bytesJustRead = drwav__metadata_parser_read(pParser, subchunkSizeBuffer, sizeof(subchunkSizeBuffer), &bytesRead); - if (bytesJustRead != sizeof(subchunkSizeBuffer)) { - break; - } - subchunkDataSize = drwav_bytes_to_u32(subchunkSizeBuffer); - - if (drwav__chunk_matches(allowedMetadataTypes, subchunkId, drwav_metadata_type_list_label, "labl") || drwav__chunk_matches(allowedMetadataTypes, subchunkId, drwav_metadata_type_list_note, "note")) { - if (subchunkDataSize >= DRWAV_LIST_LABEL_OR_NOTE_BYTES) { - drwav_uint64 stringSizeWithNullTerm = subchunkDataSize - DRWAV_LIST_LABEL_OR_NOTE_BYTES; - if (pParser->stage == drwav__metadata_parser_stage_count) { - pParser->metadataCount += 1; - drwav__metadata_request_extra_memory_for_stage_2(pParser, (size_t)stringSizeWithNullTerm, 1); - } - else { - subchunkBytesRead = drwav__read_list_label_or_note_to_metadata_obj(pParser, &pParser->pMetadata[pParser->metadataCursor], subchunkDataSize, drwav_fourcc_equal(subchunkId, "labl") ? drwav_metadata_type_list_label : drwav_metadata_type_list_note); - if (subchunkBytesRead == subchunkDataSize) { - pParser->metadataCursor += 1; - } - else { - /* Failed to parse. */ - } - } - } - else { - /* Incorrectly formed chunk. */ - } - } - else if (drwav__chunk_matches(allowedMetadataTypes, subchunkId, drwav_metadata_type_list_labelled_cue_region, "ltxt")) { - if (subchunkDataSize >= DRWAV_LIST_LABELLED_TEXT_BYTES) { - drwav_uint64 stringSizeWithNullTerminator = subchunkDataSize - DRWAV_LIST_LABELLED_TEXT_BYTES; - if (pParser->stage == drwav__metadata_parser_stage_count) { - pParser->metadataCount += 1; - drwav__metadata_request_extra_memory_for_stage_2(pParser, (size_t)stringSizeWithNullTerminator, 1); - } - else { - subchunkBytesRead = drwav__read_list_labelled_cue_region_to_metadata_obj(pParser, &pParser->pMetadata[pParser->metadataCursor], subchunkDataSize); - if (subchunkBytesRead == subchunkDataSize) { - pParser->metadataCursor += 1; - } - else { - /* Failed to parse. */ - } - } - } - else { - /* Incorrectly formed chunk. */ - } - } - else if (drwav__chunk_matches(allowedMetadataTypes, subchunkId, drwav_metadata_type_list_info_software, "ISFT")) { - subchunkBytesRead = drwav__metadata_process_info_text_chunk(pParser, subchunkDataSize, drwav_metadata_type_list_info_software); - } - else if (drwav__chunk_matches(allowedMetadataTypes, subchunkId, drwav_metadata_type_list_info_copyright, "ICOP")) { - subchunkBytesRead = drwav__metadata_process_info_text_chunk(pParser, subchunkDataSize, drwav_metadata_type_list_info_copyright); - } - else if (drwav__chunk_matches(allowedMetadataTypes, subchunkId, drwav_metadata_type_list_info_title, "INAM")) { - subchunkBytesRead = drwav__metadata_process_info_text_chunk(pParser, subchunkDataSize, drwav_metadata_type_list_info_title); - } - else if (drwav__chunk_matches(allowedMetadataTypes, subchunkId, drwav_metadata_type_list_info_artist, "IART")) { - subchunkBytesRead = drwav__metadata_process_info_text_chunk(pParser, subchunkDataSize, drwav_metadata_type_list_info_artist); - } - else if (drwav__chunk_matches(allowedMetadataTypes, subchunkId, drwav_metadata_type_list_info_comment, "ICMT")) { - subchunkBytesRead = drwav__metadata_process_info_text_chunk(pParser, subchunkDataSize, drwav_metadata_type_list_info_comment); - } - else if (drwav__chunk_matches(allowedMetadataTypes, subchunkId, drwav_metadata_type_list_info_date, "ICRD")) { - subchunkBytesRead = drwav__metadata_process_info_text_chunk(pParser, subchunkDataSize, drwav_metadata_type_list_info_date); - } - else if (drwav__chunk_matches(allowedMetadataTypes, subchunkId, drwav_metadata_type_list_info_genre, "IGNR")) { - subchunkBytesRead = drwav__metadata_process_info_text_chunk(pParser, subchunkDataSize, drwav_metadata_type_list_info_genre); - } - else if (drwav__chunk_matches(allowedMetadataTypes, subchunkId, drwav_metadata_type_list_info_album, "IPRD")) { - subchunkBytesRead = drwav__metadata_process_info_text_chunk(pParser, subchunkDataSize, drwav_metadata_type_list_info_album); - } - else if (drwav__chunk_matches(allowedMetadataTypes, subchunkId, drwav_metadata_type_list_info_tracknumber, "ITRK")) { - subchunkBytesRead = drwav__metadata_process_info_text_chunk(pParser, subchunkDataSize, drwav_metadata_type_list_info_tracknumber); - } - else if ((allowedMetadataTypes & drwav_metadata_type_unknown) != 0) { - subchunkBytesRead = drwav__metadata_process_unknown_chunk(pParser, subchunkId, subchunkDataSize, listType); - } - - bytesRead += subchunkBytesRead; - DRWAV_ASSERT(subchunkBytesRead <= subchunkDataSize); - - if (subchunkBytesRead < subchunkDataSize) { - drwav_uint64 bytesToSeek = subchunkDataSize - subchunkBytesRead; - - if (!pParser->onSeek(pParser->pReadSeekUserData, (int)bytesToSeek, drwav_seek_origin_current)) { - break; - } - bytesRead += bytesToSeek; - } - - if ((subchunkDataSize % 2) == 1) { - if (!pParser->onSeek(pParser->pReadSeekUserData, 1, drwav_seek_origin_current)) { - break; - } - bytesRead += 1; - } - } - } - else if ((allowedMetadataTypes & drwav_metadata_type_unknown) != 0) { - bytesRead = drwav__metadata_process_unknown_chunk(pParser, pChunkID, pChunkHeader->sizeInBytes, drwav_metadata_location_top_level); - } - - return bytesRead; -} - - -DRWAV_PRIVATE drwav_uint32 drwav_get_bytes_per_pcm_frame(drwav* pWav) -{ - drwav_uint32 bytesPerFrame; - - /* - The bytes per frame is a bit ambiguous. It can be either be based on the bits per sample, or the block align. The way I'm doing it here - is that if the bits per sample is a multiple of 8, use floor(bitsPerSample*channels/8), otherwise fall back to the block align. - */ - if ((pWav->bitsPerSample & 0x7) == 0) { - /* Bits per sample is a multiple of 8. */ - bytesPerFrame = (pWav->bitsPerSample * pWav->fmt.channels) >> 3; - } - else { - bytesPerFrame = pWav->fmt.blockAlign; - } - - /* Validation for known formats. a-law and mu-law should be 1 byte per channel. If it's not, it's not decodable. */ - if (pWav->translatedFormatTag == DR_WAVE_FORMAT_ALAW || pWav->translatedFormatTag == DR_WAVE_FORMAT_MULAW) { - if (bytesPerFrame != pWav->fmt.channels) { - return 0; /* Invalid file. */ - } - } - - return bytesPerFrame; -} - -DRWAV_API drwav_uint16 drwav_fmt_get_format(const drwav_fmt* pFMT) -{ - if (pFMT == NULL) { - return 0; - } - - if (pFMT->formatTag != DR_WAVE_FORMAT_EXTENSIBLE) { - return pFMT->formatTag; - } - else { - return drwav_bytes_to_u16(pFMT->subFormat); /* Only the first two bytes are required. */ - } -} - -DRWAV_PRIVATE drwav_bool32 drwav_preinit(drwav* pWav, drwav_read_proc onRead, drwav_seek_proc onSeek, void* pReadSeekUserData, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - if (pWav == NULL || onRead == NULL || onSeek == NULL) { - return DRWAV_FALSE; - } - - DRWAV_ZERO_MEMORY(pWav, sizeof(*pWav)); - pWav->onRead = onRead; - pWav->onSeek = onSeek; - pWav->pUserData = pReadSeekUserData; - pWav->allocationCallbacks = drwav_copy_allocation_callbacks_or_defaults(pAllocationCallbacks); - - if (pWav->allocationCallbacks.onFree == NULL || (pWav->allocationCallbacks.onMalloc == NULL && pWav->allocationCallbacks.onRealloc == NULL)) { - return DRWAV_FALSE; /* Invalid allocation callbacks. */ - } - - return DRWAV_TRUE; -} - -DRWAV_PRIVATE drwav_bool32 drwav_init__internal(drwav* pWav, drwav_chunk_proc onChunk, void* pChunkUserData, drwav_uint32 flags) -{ - /* This function assumes drwav_preinit() has been called beforehand. */ - - drwav_uint64 cursor; /* <-- Keeps track of the byte position so we can seek to specific locations. */ - drwav_bool32 sequential; - drwav_uint8 riff[4]; - drwav_fmt fmt; - unsigned short translatedFormatTag; - drwav_bool32 foundDataChunk; - drwav_uint64 dataChunkSize = 0; /* <-- Important! Don't explicitly set this to 0 anywhere else. Calculation of the size of the data chunk is performed in different paths depending on the container. */ - drwav_uint64 sampleCountFromFactChunk = 0; /* Same as dataChunkSize - make sure this is the only place this is initialized to 0. */ - drwav_uint64 chunkSize; - drwav__metadata_parser metadataParser; - - cursor = 0; - sequential = (flags & DRWAV_SEQUENTIAL) != 0; - - /* The first 4 bytes should be the RIFF identifier. */ - if (drwav__on_read(pWav->onRead, pWav->pUserData, riff, sizeof(riff), &cursor) != sizeof(riff)) { - return DRWAV_FALSE; - } - - /* - The first 4 bytes can be used to identify the container. For RIFF files it will start with "RIFF" and for - w64 it will start with "riff". - */ - if (drwav_fourcc_equal(riff, "RIFF")) { - pWav->container = drwav_container_riff; - } - else if (drwav_fourcc_equal(riff, "riff")) { - int i; - drwav_uint8 riff2[12]; - - pWav->container = drwav_container_w64; - - /* Check the rest of the GUID for validity. */ - if (drwav__on_read(pWav->onRead, pWav->pUserData, riff2, sizeof(riff2), &cursor) != sizeof(riff2)) { - return DRWAV_FALSE; - } - - for (i = 0; i < 12; ++i) { - if (riff2[i] != drwavGUID_W64_RIFF[i + 4]) { - return DRWAV_FALSE; - } - } - } - else if (drwav_fourcc_equal(riff, "RF64")) { - pWav->container = drwav_container_rf64; - } - else { - return DRWAV_FALSE; /* Unknown or unsupported container. */ - } - - - if (pWav->container == drwav_container_riff || pWav->container == drwav_container_rf64) { - drwav_uint8 chunkSizeBytes[4]; - drwav_uint8 wave[4]; - - /* RIFF/WAVE */ - if (drwav__on_read(pWav->onRead, pWav->pUserData, chunkSizeBytes, sizeof(chunkSizeBytes), &cursor) != sizeof(chunkSizeBytes)) { - return DRWAV_FALSE; - } - - if (pWav->container == drwav_container_riff) { - if (drwav_bytes_to_u32(chunkSizeBytes) < 36) { - return DRWAV_FALSE; /* Chunk size should always be at least 36 bytes. */ - } - } - else { - if (drwav_bytes_to_u32(chunkSizeBytes) != 0xFFFFFFFF) { - return DRWAV_FALSE; /* Chunk size should always be set to -1/0xFFFFFFFF for RF64. The actual size is retrieved later. */ - } - } - - if (drwav__on_read(pWav->onRead, pWav->pUserData, wave, sizeof(wave), &cursor) != sizeof(wave)) { - return DRWAV_FALSE; - } - - if (!drwav_fourcc_equal(wave, "WAVE")) { - return DRWAV_FALSE; /* Expecting "WAVE". */ - } - } - else { - drwav_uint8 chunkSizeBytes[8]; - drwav_uint8 wave[16]; - - /* W64 */ - if (drwav__on_read(pWav->onRead, pWav->pUserData, chunkSizeBytes, sizeof(chunkSizeBytes), &cursor) != sizeof(chunkSizeBytes)) { - return DRWAV_FALSE; - } - - if (drwav_bytes_to_u64(chunkSizeBytes) < 80) { - return DRWAV_FALSE; - } - - if (drwav__on_read(pWav->onRead, pWav->pUserData, wave, sizeof(wave), &cursor) != sizeof(wave)) { - return DRWAV_FALSE; - } - - if (!drwav_guid_equal(wave, drwavGUID_W64_WAVE)) { - return DRWAV_FALSE; - } - } - - - /* For RF64, the "ds64" chunk must come next, before the "fmt " chunk. */ - if (pWav->container == drwav_container_rf64) { - drwav_uint8 sizeBytes[8]; - drwav_uint64 bytesRemainingInChunk; - drwav_chunk_header header; - drwav_result result = drwav__read_chunk_header(pWav->onRead, pWav->pUserData, pWav->container, &cursor, &header); - if (result != DRWAV_SUCCESS) { - return DRWAV_FALSE; - } - - if (!drwav_fourcc_equal(header.id.fourcc, "ds64")) { - return DRWAV_FALSE; /* Expecting "ds64". */ - } - - bytesRemainingInChunk = header.sizeInBytes + header.paddingSize; - - /* We don't care about the size of the RIFF chunk - skip it. */ - if (!drwav__seek_forward(pWav->onSeek, 8, pWav->pUserData)) { - return DRWAV_FALSE; - } - bytesRemainingInChunk -= 8; - cursor += 8; - - - /* Next 8 bytes is the size of the "data" chunk. */ - if (drwav__on_read(pWav->onRead, pWav->pUserData, sizeBytes, sizeof(sizeBytes), &cursor) != sizeof(sizeBytes)) { - return DRWAV_FALSE; - } - bytesRemainingInChunk -= 8; - dataChunkSize = drwav_bytes_to_u64(sizeBytes); - - - /* Next 8 bytes is the same count which we would usually derived from the FACT chunk if it was available. */ - if (drwav__on_read(pWav->onRead, pWav->pUserData, sizeBytes, sizeof(sizeBytes), &cursor) != sizeof(sizeBytes)) { - return DRWAV_FALSE; - } - bytesRemainingInChunk -= 8; - sampleCountFromFactChunk = drwav_bytes_to_u64(sizeBytes); - - - /* Skip over everything else. */ - if (!drwav__seek_forward(pWav->onSeek, bytesRemainingInChunk, pWav->pUserData)) { - return DRWAV_FALSE; - } - cursor += bytesRemainingInChunk; - } - - - /* The next bytes should be the "fmt " chunk. */ - if (!drwav__read_fmt(pWav->onRead, pWav->onSeek, pWav->pUserData, pWav->container, &cursor, &fmt)) { - return DRWAV_FALSE; /* Failed to read the "fmt " chunk. */ - } - - /* Basic validation. */ - if ((fmt.sampleRate == 0 || fmt.sampleRate > DRWAV_MAX_SAMPLE_RATE) || - (fmt.channels == 0 || fmt.channels > DRWAV_MAX_CHANNELS) || - (fmt.bitsPerSample == 0 || fmt.bitsPerSample > DRWAV_MAX_BITS_PER_SAMPLE) || - fmt.blockAlign == 0) { - return DRWAV_FALSE; /* Probably an invalid WAV file. */ - } - - - /* Translate the internal format. */ - translatedFormatTag = fmt.formatTag; - if (translatedFormatTag == DR_WAVE_FORMAT_EXTENSIBLE) { - translatedFormatTag = drwav_bytes_to_u16(fmt.subFormat + 0); - } - - DRWAV_ZERO_MEMORY(&metadataParser, sizeof(metadataParser)); - - /* Not tested on W64. */ - if (!sequential && pWav->allowedMetadataTypes != drwav_metadata_type_none && (pWav->container == drwav_container_riff || pWav->container == drwav_container_rf64)) { - drwav_uint64 cursorForMetadata = cursor; - - metadataParser.onRead = pWav->onRead; - metadataParser.onSeek = pWav->onSeek; - metadataParser.pReadSeekUserData = pWav->pUserData; - metadataParser.stage = drwav__metadata_parser_stage_count; - - for (;;) { - drwav_result result; - drwav_uint64 bytesRead; - drwav_uint64 remainingBytes; - drwav_chunk_header header; - - result = drwav__read_chunk_header(pWav->onRead, pWav->pUserData, pWav->container, &cursorForMetadata, &header); - if (result != DRWAV_SUCCESS) { - break; - } - - bytesRead = drwav__metadata_process_chunk(&metadataParser, &header, pWav->allowedMetadataTypes); - DRWAV_ASSERT(bytesRead <= header.sizeInBytes); - - remainingBytes = header.sizeInBytes - bytesRead + header.paddingSize; - if (!drwav__seek_forward(pWav->onSeek, remainingBytes, pWav->pUserData)) { - break; - } - cursorForMetadata += remainingBytes; - } - - if (!drwav__seek_from_start(pWav->onSeek, cursor, pWav->pUserData)) { - return DRWAV_FALSE; - } - - drwav__metadata_alloc(&metadataParser, &pWav->allocationCallbacks); - metadataParser.stage = drwav__metadata_parser_stage_read; - } - - /* - We need to enumerate over each chunk for two reasons: - 1) The "data" chunk may not be the next one - 2) We may want to report each chunk back to the client - - In order to correctly report each chunk back to the client we will need to keep looping until the end of the file. - */ - foundDataChunk = DRWAV_FALSE; - - /* The next chunk we care about is the "data" chunk. This is not necessarily the next chunk so we'll need to loop. */ - for (;;) { - drwav_chunk_header header; - drwav_result result = drwav__read_chunk_header(pWav->onRead, pWav->pUserData, pWav->container, &cursor, &header); - if (result != DRWAV_SUCCESS) { - if (!foundDataChunk) { - return DRWAV_FALSE; - } - else { - break; /* Probably at the end of the file. Get out of the loop. */ - } - } - - /* Tell the client about this chunk. */ - if (!sequential && onChunk != NULL) { - drwav_uint64 callbackBytesRead = onChunk(pChunkUserData, pWav->onRead, pWav->onSeek, pWav->pUserData, &header, pWav->container, &fmt); - - /* - dr_wav may need to read the contents of the chunk, so we now need to seek back to the position before - we called the callback. - */ - if (callbackBytesRead > 0) { - if (!drwav__seek_from_start(pWav->onSeek, cursor, pWav->pUserData)) { - return DRWAV_FALSE; - } - } - } - - if (!sequential && pWav->allowedMetadataTypes != drwav_metadata_type_none && (pWav->container == drwav_container_riff || pWav->container == drwav_container_rf64)) { - drwav_uint64 bytesRead = drwav__metadata_process_chunk(&metadataParser, &header, pWav->allowedMetadataTypes); - - if (bytesRead > 0) { - if (!drwav__seek_from_start(pWav->onSeek, cursor, pWav->pUserData)) { - return DRWAV_FALSE; - } - } - } - - - if (!foundDataChunk) { - pWav->dataChunkDataPos = cursor; - } - - chunkSize = header.sizeInBytes; - if (pWav->container == drwav_container_riff || pWav->container == drwav_container_rf64) { - if (drwav_fourcc_equal(header.id.fourcc, "data")) { - foundDataChunk = DRWAV_TRUE; - if (pWav->container != drwav_container_rf64) { /* The data chunk size for RF64 will always be set to 0xFFFFFFFF here. It was set to it's true value earlier. */ - dataChunkSize = chunkSize; - } - } - } - else { - if (drwav_guid_equal(header.id.guid, drwavGUID_W64_DATA)) { - foundDataChunk = DRWAV_TRUE; - dataChunkSize = chunkSize; - } - } - - /* - If at this point we have found the data chunk and we're running in sequential mode, we need to break out of this loop. The reason for - this is that we would otherwise require a backwards seek which sequential mode forbids. - */ - if (foundDataChunk && sequential) { - break; - } - - /* Optional. Get the total sample count from the FACT chunk. This is useful for compressed formats. */ - if (pWav->container == drwav_container_riff) { - if (drwav_fourcc_equal(header.id.fourcc, "fact")) { - drwav_uint32 sampleCount; - if (drwav__on_read(pWav->onRead, pWav->pUserData, &sampleCount, 4, &cursor) != 4) { - return DRWAV_FALSE; - } - chunkSize -= 4; - - if (!foundDataChunk) { - pWav->dataChunkDataPos = cursor; - } - - /* - The sample count in the "fact" chunk is either unreliable, or I'm not understanding it properly. For now I am only enabling this - for Microsoft ADPCM formats. - */ - if (pWav->translatedFormatTag == DR_WAVE_FORMAT_ADPCM) { - sampleCountFromFactChunk = sampleCount; - } - else { - sampleCountFromFactChunk = 0; - } - } - } - else if (pWav->container == drwav_container_w64) { - if (drwav_guid_equal(header.id.guid, drwavGUID_W64_FACT)) { - if (drwav__on_read(pWav->onRead, pWav->pUserData, &sampleCountFromFactChunk, 8, &cursor) != 8) { - return DRWAV_FALSE; - } - chunkSize -= 8; - - if (!foundDataChunk) { - pWav->dataChunkDataPos = cursor; - } - } - } - else if (pWav->container == drwav_container_rf64) { - /* We retrieved the sample count from the ds64 chunk earlier so no need to do that here. */ - } - - /* Make sure we seek past the padding. */ - chunkSize += header.paddingSize; - if (!drwav__seek_forward(pWav->onSeek, chunkSize, pWav->pUserData)) { - break; - } - cursor += chunkSize; - - if (!foundDataChunk) { - pWav->dataChunkDataPos = cursor; - } - } - - pWav->pMetadata = metadataParser.pMetadata; - pWav->metadataCount = metadataParser.metadataCount; - - /* If we haven't found a data chunk, return an error. */ - if (!foundDataChunk) { - return DRWAV_FALSE; - } - - /* We may have moved passed the data chunk. If so we need to move back. If running in sequential mode we can assume we are already sitting on the data chunk. */ - if (!sequential) { - if (!drwav__seek_from_start(pWav->onSeek, pWav->dataChunkDataPos, pWav->pUserData)) { - return DRWAV_FALSE; - } - cursor = pWav->dataChunkDataPos; - } - - - /* At this point we should be sitting on the first byte of the raw audio data. */ - - pWav->fmt = fmt; - pWav->sampleRate = fmt.sampleRate; - pWav->channels = fmt.channels; - pWav->bitsPerSample = fmt.bitsPerSample; - pWav->bytesRemaining = dataChunkSize; - pWav->translatedFormatTag = translatedFormatTag; - pWav->dataChunkDataSize = dataChunkSize; - - if (sampleCountFromFactChunk != 0) { - pWav->totalPCMFrameCount = sampleCountFromFactChunk; - } - else { - drwav_uint32 bytesPerFrame = drwav_get_bytes_per_pcm_frame(pWav); - if (bytesPerFrame == 0) { - return DRWAV_FALSE; /* Invalid file. */ - } - - pWav->totalPCMFrameCount = dataChunkSize / bytesPerFrame; - - if (pWav->translatedFormatTag == DR_WAVE_FORMAT_ADPCM) { - drwav_uint64 totalBlockHeaderSizeInBytes; - drwav_uint64 blockCount = dataChunkSize / fmt.blockAlign; - - /* Make sure any trailing partial block is accounted for. */ - if ((blockCount * fmt.blockAlign) < dataChunkSize) { - blockCount += 1; - } - - /* We decode two samples per byte. There will be blockCount headers in the data chunk. This is enough to know how to calculate the total PCM frame count. */ - totalBlockHeaderSizeInBytes = blockCount * (6 * fmt.channels); - pWav->totalPCMFrameCount = ((dataChunkSize - totalBlockHeaderSizeInBytes) * 2) / fmt.channels; - } - if (pWav->translatedFormatTag == DR_WAVE_FORMAT_DVI_ADPCM) { - drwav_uint64 totalBlockHeaderSizeInBytes; - drwav_uint64 blockCount = dataChunkSize / fmt.blockAlign; - - /* Make sure any trailing partial block is accounted for. */ - if ((blockCount * fmt.blockAlign) < dataChunkSize) { - blockCount += 1; - } - - /* We decode two samples per byte. There will be blockCount headers in the data chunk. This is enough to know how to calculate the total PCM frame count. */ - totalBlockHeaderSizeInBytes = blockCount * (4 * fmt.channels); - pWav->totalPCMFrameCount = ((dataChunkSize - totalBlockHeaderSizeInBytes) * 2) / fmt.channels; - - /* The header includes a decoded sample for each channel which acts as the initial predictor sample. */ - pWav->totalPCMFrameCount += blockCount; - } - } - - /* Some formats only support a certain number of channels. */ - if (pWav->translatedFormatTag == DR_WAVE_FORMAT_ADPCM || pWav->translatedFormatTag == DR_WAVE_FORMAT_DVI_ADPCM) { - if (pWav->channels > 2) { - return DRWAV_FALSE; - } - } - - /* The number of bytes per frame must be known. If not, it's an invalid file and not decodable. */ - if (drwav_get_bytes_per_pcm_frame(pWav) == 0) { - return DRWAV_FALSE; - } - -#ifdef DR_WAV_LIBSNDFILE_COMPAT - /* - I use libsndfile as a benchmark for testing, however in the version I'm using (from the Windows installer on the libsndfile website), - it appears the total sample count libsndfile uses for MS-ADPCM is incorrect. It would seem they are computing the total sample count - from the number of blocks, however this results in the inclusion of extra silent samples at the end of the last block. The correct - way to know the total sample count is to inspect the "fact" chunk, which should always be present for compressed formats, and should - always include the sample count. This little block of code below is only used to emulate the libsndfile logic so I can properly run my - correctness tests against libsndfile, and is disabled by default. - */ - if (pWav->translatedFormatTag == DR_WAVE_FORMAT_ADPCM) { - drwav_uint64 blockCount = dataChunkSize / fmt.blockAlign; - pWav->totalPCMFrameCount = (((blockCount * (fmt.blockAlign - (6 * pWav->channels))) * 2)) / fmt.channels; /* x2 because two samples per byte. */ - } - if (pWav->translatedFormatTag == DR_WAVE_FORMAT_DVI_ADPCM) { - drwav_uint64 blockCount = dataChunkSize / fmt.blockAlign; - pWav->totalPCMFrameCount = (((blockCount * (fmt.blockAlign - (4 * pWav->channels))) * 2) + (blockCount * pWav->channels)) / fmt.channels; - } -#endif - - return DRWAV_TRUE; -} - -DRWAV_API drwav_bool32 drwav_init(drwav* pWav, drwav_read_proc onRead, drwav_seek_proc onSeek, void* pUserData, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - return drwav_init_ex(pWav, onRead, onSeek, NULL, pUserData, NULL, 0, pAllocationCallbacks); -} - -DRWAV_API drwav_bool32 drwav_init_ex(drwav* pWav, drwav_read_proc onRead, drwav_seek_proc onSeek, drwav_chunk_proc onChunk, void* pReadSeekUserData, void* pChunkUserData, drwav_uint32 flags, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - if (!drwav_preinit(pWav, onRead, onSeek, pReadSeekUserData, pAllocationCallbacks)) { - return DRWAV_FALSE; - } - - return drwav_init__internal(pWav, onChunk, pChunkUserData, flags); -} - -DRWAV_API drwav_bool32 drwav_init_with_metadata(drwav* pWav, drwav_read_proc onRead, drwav_seek_proc onSeek, void* pUserData, drwav_uint32 flags, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - if (!drwav_preinit(pWav, onRead, onSeek, pUserData, pAllocationCallbacks)) { - return DRWAV_FALSE; - } - - pWav->allowedMetadataTypes = drwav_metadata_type_all_including_unknown; /* <-- Needs to be set to tell drwav_init_ex() that we need to process metadata. */ - return drwav_init__internal(pWav, NULL, NULL, flags); -} - -DRWAV_API drwav_metadata* drwav_take_ownership_of_metadata(drwav* pWav) -{ - drwav_metadata* result = pWav->pMetadata; - - pWav->pMetadata = NULL; - pWav->metadataCount = 0; - - return result; -} - - -DRWAV_PRIVATE size_t drwav__write(drwav* pWav, const void* pData, size_t dataSize) -{ - DRWAV_ASSERT(pWav != NULL); - DRWAV_ASSERT(pWav->onWrite != NULL); - - /* Generic write. Assumes no byte reordering required. */ - return pWav->onWrite(pWav->pUserData, pData, dataSize); -} - -DRWAV_PRIVATE size_t drwav__write_byte(drwav* pWav, drwav_uint8 byte) -{ - DRWAV_ASSERT(pWav != NULL); - DRWAV_ASSERT(pWav->onWrite != NULL); - - return pWav->onWrite(pWav->pUserData, &byte, 1); -} - -DRWAV_PRIVATE size_t drwav__write_u16ne_to_le(drwav* pWav, drwav_uint16 value) -{ - DRWAV_ASSERT(pWav != NULL); - DRWAV_ASSERT(pWav->onWrite != NULL); - - if (!drwav__is_little_endian()) { - value = drwav__bswap16(value); - } - - return drwav__write(pWav, &value, 2); -} - -DRWAV_PRIVATE size_t drwav__write_u32ne_to_le(drwav* pWav, drwav_uint32 value) -{ - DRWAV_ASSERT(pWav != NULL); - DRWAV_ASSERT(pWav->onWrite != NULL); - - if (!drwav__is_little_endian()) { - value = drwav__bswap32(value); - } - - return drwav__write(pWav, &value, 4); -} - -DRWAV_PRIVATE size_t drwav__write_u64ne_to_le(drwav* pWav, drwav_uint64 value) -{ - DRWAV_ASSERT(pWav != NULL); - DRWAV_ASSERT(pWav->onWrite != NULL); - - if (!drwav__is_little_endian()) { - value = drwav__bswap64(value); - } - - return drwav__write(pWav, &value, 8); -} - -DRWAV_PRIVATE size_t drwav__write_f32ne_to_le(drwav* pWav, float value) -{ - union { - drwav_uint32 u32; - float f32; - } u; - - DRWAV_ASSERT(pWav != NULL); - DRWAV_ASSERT(pWav->onWrite != NULL); - - u.f32 = value; - - if (!drwav__is_little_endian()) { - u.u32 = drwav__bswap32(u.u32); - } - - return drwav__write(pWav, &u.u32, 4); -} - -DRWAV_PRIVATE size_t drwav__write_or_count(drwav* pWav, const void* pData, size_t dataSize) -{ - if (pWav == NULL) { - return dataSize; - } - - return drwav__write(pWav, pData, dataSize); -} - -DRWAV_PRIVATE size_t drwav__write_or_count_byte(drwav* pWav, drwav_uint8 byte) -{ - if (pWav == NULL) { - return 1; - } - - return drwav__write_byte(pWav, byte); -} - -DRWAV_PRIVATE size_t drwav__write_or_count_u16ne_to_le(drwav* pWav, drwav_uint16 value) -{ - if (pWav == NULL) { - return 2; - } - - return drwav__write_u16ne_to_le(pWav, value); -} - -DRWAV_PRIVATE size_t drwav__write_or_count_u32ne_to_le(drwav* pWav, drwav_uint32 value) -{ - if (pWav == NULL) { - return 4; - } - - return drwav__write_u32ne_to_le(pWav, value); -} - -#if 0 /* Unused for now. */ -DRWAV_PRIVATE size_t drwav__write_or_count_u64ne_to_le(drwav* pWav, drwav_uint64 value) -{ - if (pWav == NULL) { - return 8; - } - - return drwav__write_u64ne_to_le(pWav, value); -} -#endif - -DRWAV_PRIVATE size_t drwav__write_or_count_f32ne_to_le(drwav* pWav, float value) -{ - if (pWav == NULL) { - return 4; - } - - return drwav__write_f32ne_to_le(pWav, value); -} - -DRWAV_PRIVATE size_t drwav__write_or_count_string_to_fixed_size_buf(drwav* pWav, char* str, size_t bufFixedSize) -{ - size_t len; - - if (pWav == NULL) { - return bufFixedSize; - } - - len = drwav__strlen_clamped(str, bufFixedSize); - drwav__write_or_count(pWav, str, len); - - if (len < bufFixedSize) { - size_t i; - for (i = 0; i < bufFixedSize - len; ++i) { - drwav__write_byte(pWav, 0); - } - } - - return bufFixedSize; -} - - -/* pWav can be NULL meaning just count the bytes that would be written. */ -DRWAV_PRIVATE size_t drwav__write_or_count_metadata(drwav* pWav, drwav_metadata* pMetadatas, drwav_uint32 metadataCount) -{ - size_t bytesWritten = 0; - drwav_bool32 hasListAdtl = DRWAV_FALSE; - drwav_bool32 hasListInfo = DRWAV_FALSE; - drwav_uint32 iMetadata; - - if (pMetadatas == NULL || metadataCount == 0) { - return 0; - } - - for (iMetadata = 0; iMetadata < metadataCount; ++iMetadata) { - drwav_metadata* pMetadata = &pMetadatas[iMetadata]; - drwav_uint32 chunkSize = 0; - - if ((pMetadata->type & drwav_metadata_type_list_all_info_strings) || (pMetadata->type == drwav_metadata_type_unknown && pMetadata->data.unknown.chunkLocation == drwav_metadata_location_inside_info_list)) { - hasListInfo = DRWAV_TRUE; - } - - if ((pMetadata->type & drwav_metadata_type_list_all_adtl) || (pMetadata->type == drwav_metadata_type_unknown && pMetadata->data.unknown.chunkLocation == drwav_metadata_location_inside_adtl_list)) { - hasListAdtl = DRWAV_TRUE; - } - - switch (pMetadata->type) { - case drwav_metadata_type_smpl: - { - drwav_uint32 iLoop; - - chunkSize = DRWAV_SMPL_BYTES + DRWAV_SMPL_LOOP_BYTES * pMetadata->data.smpl.sampleLoopCount + pMetadata->data.smpl.samplerSpecificDataSizeInBytes; - - bytesWritten += drwav__write_or_count(pWav, "smpl", 4); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, chunkSize); - - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, pMetadata->data.smpl.manufacturerId); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, pMetadata->data.smpl.productId); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, pMetadata->data.smpl.samplePeriodNanoseconds); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, pMetadata->data.smpl.midiUnityNote); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, pMetadata->data.smpl.midiPitchFraction); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, pMetadata->data.smpl.smpteFormat); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, pMetadata->data.smpl.smpteOffset); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, pMetadata->data.smpl.sampleLoopCount); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, pMetadata->data.smpl.samplerSpecificDataSizeInBytes); - - for (iLoop = 0; iLoop < pMetadata->data.smpl.sampleLoopCount; ++iLoop) { - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, pMetadata->data.smpl.pLoops[iLoop].cuePointId); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, pMetadata->data.smpl.pLoops[iLoop].type); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, pMetadata->data.smpl.pLoops[iLoop].firstSampleByteOffset); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, pMetadata->data.smpl.pLoops[iLoop].lastSampleByteOffset); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, pMetadata->data.smpl.pLoops[iLoop].sampleFraction); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, pMetadata->data.smpl.pLoops[iLoop].playCount); - } - - if (pMetadata->data.smpl.samplerSpecificDataSizeInBytes > 0) { - bytesWritten += drwav__write(pWav, pMetadata->data.smpl.pSamplerSpecificData, pMetadata->data.smpl.samplerSpecificDataSizeInBytes); - } - } break; - - case drwav_metadata_type_inst: - { - chunkSize = DRWAV_INST_BYTES; - - bytesWritten += drwav__write_or_count(pWav, "inst", 4); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, chunkSize); - bytesWritten += drwav__write_or_count(pWav, &pMetadata->data.inst.midiUnityNote, 1); - bytesWritten += drwav__write_or_count(pWav, &pMetadata->data.inst.fineTuneCents, 1); - bytesWritten += drwav__write_or_count(pWav, &pMetadata->data.inst.gainDecibels, 1); - bytesWritten += drwav__write_or_count(pWav, &pMetadata->data.inst.lowNote, 1); - bytesWritten += drwav__write_or_count(pWav, &pMetadata->data.inst.highNote, 1); - bytesWritten += drwav__write_or_count(pWav, &pMetadata->data.inst.lowVelocity, 1); - bytesWritten += drwav__write_or_count(pWav, &pMetadata->data.inst.highVelocity, 1); - } break; - - case drwav_metadata_type_cue: - { - drwav_uint32 iCuePoint; - - chunkSize = DRWAV_CUE_BYTES + DRWAV_CUE_POINT_BYTES * pMetadata->data.cue.cuePointCount; - - bytesWritten += drwav__write_or_count(pWav, "cue ", 4); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, chunkSize); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, pMetadata->data.cue.cuePointCount); - for (iCuePoint = 0; iCuePoint < pMetadata->data.cue.cuePointCount; ++iCuePoint) { - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, pMetadata->data.cue.pCuePoints[iCuePoint].id); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, pMetadata->data.cue.pCuePoints[iCuePoint].playOrderPosition); - bytesWritten += drwav__write_or_count(pWav, pMetadata->data.cue.pCuePoints[iCuePoint].dataChunkId, 4); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, pMetadata->data.cue.pCuePoints[iCuePoint].chunkStart); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, pMetadata->data.cue.pCuePoints[iCuePoint].blockStart); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, pMetadata->data.cue.pCuePoints[iCuePoint].sampleByteOffset); - } - } break; - - case drwav_metadata_type_acid: - { - chunkSize = DRWAV_ACID_BYTES; - - bytesWritten += drwav__write_or_count(pWav, "acid", 4); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, chunkSize); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, pMetadata->data.acid.flags); - bytesWritten += drwav__write_or_count_u16ne_to_le(pWav, pMetadata->data.acid.midiUnityNote); - bytesWritten += drwav__write_or_count_u16ne_to_le(pWav, pMetadata->data.acid.reserved1); - bytesWritten += drwav__write_or_count_f32ne_to_le(pWav, pMetadata->data.acid.reserved2); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, pMetadata->data.acid.numBeats); - bytesWritten += drwav__write_or_count_u16ne_to_le(pWav, pMetadata->data.acid.meterDenominator); - bytesWritten += drwav__write_or_count_u16ne_to_le(pWav, pMetadata->data.acid.meterNumerator); - bytesWritten += drwav__write_or_count_f32ne_to_le(pWav, pMetadata->data.acid.tempo); - } break; - - case drwav_metadata_type_bext: - { - char reservedBuf[DRWAV_BEXT_RESERVED_BYTES]; - drwav_uint32 timeReferenceLow; - drwav_uint32 timeReferenceHigh; - - chunkSize = DRWAV_BEXT_BYTES + pMetadata->data.bext.codingHistorySize; - - bytesWritten += drwav__write_or_count(pWav, "bext", 4); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, chunkSize); - - bytesWritten += drwav__write_or_count_string_to_fixed_size_buf(pWav, pMetadata->data.bext.pDescription, DRWAV_BEXT_DESCRIPTION_BYTES); - bytesWritten += drwav__write_or_count_string_to_fixed_size_buf(pWav, pMetadata->data.bext.pOriginatorName, DRWAV_BEXT_ORIGINATOR_NAME_BYTES); - bytesWritten += drwav__write_or_count_string_to_fixed_size_buf(pWav, pMetadata->data.bext.pOriginatorReference, DRWAV_BEXT_ORIGINATOR_REF_BYTES); - bytesWritten += drwav__write_or_count(pWav, pMetadata->data.bext.pOriginationDate, sizeof(pMetadata->data.bext.pOriginationDate)); - bytesWritten += drwav__write_or_count(pWav, pMetadata->data.bext.pOriginationTime, sizeof(pMetadata->data.bext.pOriginationTime)); - - timeReferenceLow = (drwav_uint32)(pMetadata->data.bext.timeReference & 0xFFFFFFFF); - timeReferenceHigh = (drwav_uint32)(pMetadata->data.bext.timeReference >> 32); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, timeReferenceLow); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, timeReferenceHigh); - - bytesWritten += drwav__write_or_count_u16ne_to_le(pWav, pMetadata->data.bext.version); - bytesWritten += drwav__write_or_count(pWav, pMetadata->data.bext.pUMID, DRWAV_BEXT_UMID_BYTES); - bytesWritten += drwav__write_or_count_u16ne_to_le(pWav, pMetadata->data.bext.loudnessValue); - bytesWritten += drwav__write_or_count_u16ne_to_le(pWav, pMetadata->data.bext.loudnessRange); - bytesWritten += drwav__write_or_count_u16ne_to_le(pWav, pMetadata->data.bext.maxTruePeakLevel); - bytesWritten += drwav__write_or_count_u16ne_to_le(pWav, pMetadata->data.bext.maxMomentaryLoudness); - bytesWritten += drwav__write_or_count_u16ne_to_le(pWav, pMetadata->data.bext.maxShortTermLoudness); - - DRWAV_ZERO_MEMORY(reservedBuf, sizeof(reservedBuf)); - bytesWritten += drwav__write_or_count(pWav, reservedBuf, sizeof(reservedBuf)); - - if (pMetadata->data.bext.codingHistorySize > 0) { - bytesWritten += drwav__write_or_count(pWav, pMetadata->data.bext.pCodingHistory, pMetadata->data.bext.codingHistorySize); - } - } break; - - case drwav_metadata_type_unknown: - { - if (pMetadata->data.unknown.chunkLocation == drwav_metadata_location_top_level) { - chunkSize = pMetadata->data.unknown.dataSizeInBytes; - - bytesWritten += drwav__write_or_count(pWav, pMetadata->data.unknown.id, 4); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, chunkSize); - bytesWritten += drwav__write_or_count(pWav, pMetadata->data.unknown.pData, pMetadata->data.unknown.dataSizeInBytes); - } - } break; - - default: break; - } - if ((chunkSize % 2) != 0) { - bytesWritten += drwav__write_or_count_byte(pWav, 0); - } - } - - if (hasListInfo) { - drwav_uint32 chunkSize = 4; /* Start with 4 bytes for "INFO". */ - for (iMetadata = 0; iMetadata < metadataCount; ++iMetadata) { - drwav_metadata* pMetadata = &pMetadatas[iMetadata]; - - if ((pMetadata->type & drwav_metadata_type_list_all_info_strings)) { - chunkSize += 8; /* For id and string size. */ - chunkSize += pMetadata->data.infoText.stringLength + 1; /* Include null terminator. */ - } - else if (pMetadata->type == drwav_metadata_type_unknown && pMetadata->data.unknown.chunkLocation == drwav_metadata_location_inside_info_list) { - chunkSize += 8; /* For id string size. */ - chunkSize += pMetadata->data.unknown.dataSizeInBytes; - } - - if ((chunkSize % 2) != 0) { - chunkSize += 1; - } - } - - bytesWritten += drwav__write_or_count(pWav, "LIST", 4); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, chunkSize); - bytesWritten += drwav__write_or_count(pWav, "INFO", 4); - - for (iMetadata = 0; iMetadata < metadataCount; ++iMetadata) { - drwav_metadata* pMetadata = &pMetadatas[iMetadata]; - drwav_uint32 subchunkSize = 0; - - if (pMetadata->type & drwav_metadata_type_list_all_info_strings) { - const char* pID = NULL; - - switch (pMetadata->type) { - case drwav_metadata_type_list_info_software: pID = "ISFT"; break; - case drwav_metadata_type_list_info_copyright: pID = "ICOP"; break; - case drwav_metadata_type_list_info_title: pID = "INAM"; break; - case drwav_metadata_type_list_info_artist: pID = "IART"; break; - case drwav_metadata_type_list_info_comment: pID = "ICMT"; break; - case drwav_metadata_type_list_info_date: pID = "ICRD"; break; - case drwav_metadata_type_list_info_genre: pID = "IGNR"; break; - case drwav_metadata_type_list_info_album: pID = "IPRD"; break; - case drwav_metadata_type_list_info_tracknumber: pID = "ITRK"; break; - default: break; - } - - DRWAV_ASSERT(pID != NULL); - - if (pMetadata->data.infoText.stringLength) { - subchunkSize = pMetadata->data.infoText.stringLength + 1; - bytesWritten += drwav__write_or_count(pWav, pID, 4); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, subchunkSize); - bytesWritten += drwav__write_or_count(pWav, pMetadata->data.infoText.pString, pMetadata->data.infoText.stringLength); - bytesWritten += drwav__write_or_count_byte(pWav, '\0'); - } - } - else if (pMetadata->type == drwav_metadata_type_unknown && pMetadata->data.unknown.chunkLocation == drwav_metadata_location_inside_info_list) { - if (pMetadata->data.unknown.dataSizeInBytes) { - subchunkSize = pMetadata->data.unknown.dataSizeInBytes; - - bytesWritten += drwav__write_or_count(pWav, pMetadata->data.unknown.id, 4); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, pMetadata->data.unknown.dataSizeInBytes); - bytesWritten += drwav__write_or_count(pWav, pMetadata->data.unknown.pData, subchunkSize); - } - } - - if ((subchunkSize % 2) != 0) { - bytesWritten += drwav__write_or_count_byte(pWav, 0); - } - } - } - - if (hasListAdtl) { - drwav_uint32 chunkSize = 4; /* start with 4 bytes for "adtl" */ - - for (iMetadata = 0; iMetadata < metadataCount; ++iMetadata) { - drwav_metadata* pMetadata = &pMetadatas[iMetadata]; - - switch (pMetadata->type) - { - case drwav_metadata_type_list_label: - case drwav_metadata_type_list_note: - { - chunkSize += 8; /* for id and chunk size */ - chunkSize += DRWAV_LIST_LABEL_OR_NOTE_BYTES; - - if (pMetadata->data.labelOrNote.stringLength > 0) { - chunkSize += pMetadata->data.labelOrNote.stringLength + 1; - } - } break; - - case drwav_metadata_type_list_labelled_cue_region: - { - chunkSize += 8; /* for id and chunk size */ - chunkSize += DRWAV_LIST_LABELLED_TEXT_BYTES; - - if (pMetadata->data.labelledCueRegion.stringLength > 0) { - chunkSize += pMetadata->data.labelledCueRegion.stringLength + 1; - } - } break; - - case drwav_metadata_type_unknown: - { - if (pMetadata->data.unknown.chunkLocation == drwav_metadata_location_inside_adtl_list) { - chunkSize += 8; /* for id and chunk size */ - chunkSize += pMetadata->data.unknown.dataSizeInBytes; - } - } break; - - default: break; - } - - if ((chunkSize % 2) != 0) { - chunkSize += 1; - } - } - - bytesWritten += drwav__write_or_count(pWav, "LIST", 4); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, chunkSize); - bytesWritten += drwav__write_or_count(pWav, "adtl", 4); - - for (iMetadata = 0; iMetadata < metadataCount; ++iMetadata) { - drwav_metadata* pMetadata = &pMetadatas[iMetadata]; - drwav_uint32 subchunkSize = 0; - - switch (pMetadata->type) - { - case drwav_metadata_type_list_label: - case drwav_metadata_type_list_note: - { - if (pMetadata->data.labelOrNote.stringLength > 0) { - const char* pID = NULL; - - if (pMetadata->type == drwav_metadata_type_list_label) { - pID = "labl"; - } - else if (pMetadata->type == drwav_metadata_type_list_note) { - pID = "note"; - } - - DRWAV_ASSERT(pID != NULL); - DRWAV_ASSERT(pMetadata->data.labelOrNote.pString != NULL); - - subchunkSize = DRWAV_LIST_LABEL_OR_NOTE_BYTES; - - bytesWritten += drwav__write_or_count(pWav, pID, 4); - subchunkSize += pMetadata->data.labelOrNote.stringLength + 1; - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, subchunkSize); - - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, pMetadata->data.labelOrNote.cuePointId); - bytesWritten += drwav__write_or_count(pWav, pMetadata->data.labelOrNote.pString, pMetadata->data.labelOrNote.stringLength); - bytesWritten += drwav__write_or_count_byte(pWav, '\0'); - } - } break; - - case drwav_metadata_type_list_labelled_cue_region: - { - subchunkSize = DRWAV_LIST_LABELLED_TEXT_BYTES; - - bytesWritten += drwav__write_or_count(pWav, "ltxt", 4); - if (pMetadata->data.labelledCueRegion.stringLength > 0) { - subchunkSize += pMetadata->data.labelledCueRegion.stringLength + 1; - } - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, subchunkSize); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, pMetadata->data.labelledCueRegion.cuePointId); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, pMetadata->data.labelledCueRegion.sampleLength); - bytesWritten += drwav__write_or_count(pWav, pMetadata->data.labelledCueRegion.purposeId, 4); - bytesWritten += drwav__write_or_count_u16ne_to_le(pWav, pMetadata->data.labelledCueRegion.country); - bytesWritten += drwav__write_or_count_u16ne_to_le(pWav, pMetadata->data.labelledCueRegion.language); - bytesWritten += drwav__write_or_count_u16ne_to_le(pWav, pMetadata->data.labelledCueRegion.dialect); - bytesWritten += drwav__write_or_count_u16ne_to_le(pWav, pMetadata->data.labelledCueRegion.codePage); - - if (pMetadata->data.labelledCueRegion.stringLength > 0) { - DRWAV_ASSERT(pMetadata->data.labelledCueRegion.pString != NULL); - - bytesWritten += drwav__write_or_count(pWav, pMetadata->data.labelledCueRegion.pString, pMetadata->data.labelledCueRegion.stringLength); - bytesWritten += drwav__write_or_count_byte(pWav, '\0'); - } - } break; - - case drwav_metadata_type_unknown: - { - if (pMetadata->data.unknown.chunkLocation == drwav_metadata_location_inside_adtl_list) { - subchunkSize = pMetadata->data.unknown.dataSizeInBytes; - - DRWAV_ASSERT(pMetadata->data.unknown.pData != NULL); - bytesWritten += drwav__write_or_count(pWav, pMetadata->data.unknown.id, 4); - bytesWritten += drwav__write_or_count_u32ne_to_le(pWav, subchunkSize); - bytesWritten += drwav__write_or_count(pWav, pMetadata->data.unknown.pData, subchunkSize); - } - } break; - - default: break; - } - - if ((subchunkSize % 2) != 0) { - bytesWritten += drwav__write_or_count_byte(pWav, 0); - } - } - } - - DRWAV_ASSERT((bytesWritten % 2) == 0); - - return bytesWritten; -} - -DRWAV_PRIVATE drwav_uint32 drwav__riff_chunk_size_riff(drwav_uint64 dataChunkSize, drwav_metadata* pMetadata, drwav_uint32 metadataCount) -{ - drwav_uint64 chunkSize = 4 + 24 + (drwav_uint64)drwav__write_or_count_metadata(NULL, pMetadata, metadataCount) + 8 + dataChunkSize + drwav__chunk_padding_size_riff(dataChunkSize); /* 4 = "WAVE". 24 = "fmt " chunk. 8 = "data" + u32 data size. */ - if (chunkSize > 0xFFFFFFFFUL) { - chunkSize = 0xFFFFFFFFUL; - } - - return (drwav_uint32)chunkSize; /* Safe cast due to the clamp above. */ -} - -DRWAV_PRIVATE drwav_uint32 drwav__data_chunk_size_riff(drwav_uint64 dataChunkSize) -{ - if (dataChunkSize <= 0xFFFFFFFFUL) { - return (drwav_uint32)dataChunkSize; - } - else { - return 0xFFFFFFFFUL; - } -} - -DRWAV_PRIVATE drwav_uint64 drwav__riff_chunk_size_w64(drwav_uint64 dataChunkSize) -{ - drwav_uint64 dataSubchunkPaddingSize = drwav__chunk_padding_size_w64(dataChunkSize); - - return 80 + 24 + dataChunkSize + dataSubchunkPaddingSize; /* +24 because W64 includes the size of the GUID and size fields. */ -} - -DRWAV_PRIVATE drwav_uint64 drwav__data_chunk_size_w64(drwav_uint64 dataChunkSize) -{ - return 24 + dataChunkSize; /* +24 because W64 includes the size of the GUID and size fields. */ -} - -DRWAV_PRIVATE drwav_uint64 drwav__riff_chunk_size_rf64(drwav_uint64 dataChunkSize, drwav_metadata* metadata, drwav_uint32 numMetadata) -{ - drwav_uint64 chunkSize = 4 + 36 + 24 + (drwav_uint64)drwav__write_or_count_metadata(NULL, metadata, numMetadata) + 8 + dataChunkSize + drwav__chunk_padding_size_riff(dataChunkSize); /* 4 = "WAVE". 36 = "ds64" chunk. 24 = "fmt " chunk. 8 = "data" + u32 data size. */ - if (chunkSize > 0xFFFFFFFFUL) { - chunkSize = 0xFFFFFFFFUL; - } - - return chunkSize; -} - -DRWAV_PRIVATE drwav_uint64 drwav__data_chunk_size_rf64(drwav_uint64 dataChunkSize) -{ - return dataChunkSize; -} - - - -DRWAV_PRIVATE drwav_bool32 drwav_preinit_write(drwav* pWav, const drwav_data_format* pFormat, drwav_bool32 isSequential, drwav_write_proc onWrite, drwav_seek_proc onSeek, void* pUserData, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - if (pWav == NULL || onWrite == NULL) { - return DRWAV_FALSE; - } - - if (!isSequential && onSeek == NULL) { - return DRWAV_FALSE; /* <-- onSeek is required when in non-sequential mode. */ - } - - /* Not currently supporting compressed formats. Will need to add support for the "fact" chunk before we enable this. */ - if (pFormat->format == DR_WAVE_FORMAT_EXTENSIBLE) { - return DRWAV_FALSE; - } - if (pFormat->format == DR_WAVE_FORMAT_ADPCM || pFormat->format == DR_WAVE_FORMAT_DVI_ADPCM) { - return DRWAV_FALSE; - } - - DRWAV_ZERO_MEMORY(pWav, sizeof(*pWav)); - pWav->onWrite = onWrite; - pWav->onSeek = onSeek; - pWav->pUserData = pUserData; - pWav->allocationCallbacks = drwav_copy_allocation_callbacks_or_defaults(pAllocationCallbacks); - - if (pWav->allocationCallbacks.onFree == NULL || (pWav->allocationCallbacks.onMalloc == NULL && pWav->allocationCallbacks.onRealloc == NULL)) { - return DRWAV_FALSE; /* Invalid allocation callbacks. */ - } - - pWav->fmt.formatTag = (drwav_uint16)pFormat->format; - pWav->fmt.channels = (drwav_uint16)pFormat->channels; - pWav->fmt.sampleRate = pFormat->sampleRate; - pWav->fmt.avgBytesPerSec = (drwav_uint32)((pFormat->bitsPerSample * pFormat->sampleRate * pFormat->channels) / 8); - pWav->fmt.blockAlign = (drwav_uint16)((pFormat->channels * pFormat->bitsPerSample) / 8); - pWav->fmt.bitsPerSample = (drwav_uint16)pFormat->bitsPerSample; - pWav->fmt.extendedSize = 0; - pWav->isSequentialWrite = isSequential; - - return DRWAV_TRUE; -} - - -DRWAV_PRIVATE drwav_bool32 drwav_init_write__internal(drwav* pWav, const drwav_data_format* pFormat, drwav_uint64 totalSampleCount) -{ - /* The function assumes drwav_preinit_write() was called beforehand. */ - - size_t runningPos = 0; - drwav_uint64 initialDataChunkSize = 0; - drwav_uint64 chunkSizeFMT; - - /* - The initial values for the "RIFF" and "data" chunks depends on whether or not we are initializing in sequential mode or not. In - sequential mode we set this to its final values straight away since they can be calculated from the total sample count. In non- - sequential mode we initialize it all to zero and fill it out in drwav_uninit() using a backwards seek. - */ - if (pWav->isSequentialWrite) { - initialDataChunkSize = (totalSampleCount * pWav->fmt.bitsPerSample) / 8; - - /* - The RIFF container has a limit on the number of samples. drwav is not allowing this. There's no practical limits for Wave64 - so for the sake of simplicity I'm not doing any validation for that. - */ - if (pFormat->container == drwav_container_riff) { - if (initialDataChunkSize > (0xFFFFFFFFUL - 36)) { - return DRWAV_FALSE; /* Not enough room to store every sample. */ - } - } - } - - pWav->dataChunkDataSizeTargetWrite = initialDataChunkSize; - - - /* "RIFF" chunk. */ - if (pFormat->container == drwav_container_riff) { - drwav_uint32 chunkSizeRIFF = 28 + (drwav_uint32)initialDataChunkSize; /* +28 = "WAVE" + [sizeof "fmt " chunk] */ - runningPos += drwav__write(pWav, "RIFF", 4); - runningPos += drwav__write_u32ne_to_le(pWav, chunkSizeRIFF); - runningPos += drwav__write(pWav, "WAVE", 4); - } - else if (pFormat->container == drwav_container_w64) { - drwav_uint64 chunkSizeRIFF = 80 + 24 + initialDataChunkSize; /* +24 because W64 includes the size of the GUID and size fields. */ - runningPos += drwav__write(pWav, drwavGUID_W64_RIFF, 16); - runningPos += drwav__write_u64ne_to_le(pWav, chunkSizeRIFF); - runningPos += drwav__write(pWav, drwavGUID_W64_WAVE, 16); - } - else if (pFormat->container == drwav_container_rf64) { - runningPos += drwav__write(pWav, "RF64", 4); - runningPos += drwav__write_u32ne_to_le(pWav, 0xFFFFFFFF); /* Always 0xFFFFFFFF for RF64. Set to a proper value in the "ds64" chunk. */ - runningPos += drwav__write(pWav, "WAVE", 4); - } - - - /* "ds64" chunk (RF64 only). */ - if (pFormat->container == drwav_container_rf64) { - drwav_uint32 initialds64ChunkSize = 28; /* 28 = [Size of RIFF (8 bytes)] + [Size of DATA (8 bytes)] + [Sample Count (8 bytes)] + [Table Length (4 bytes)]. Table length always set to 0. */ - drwav_uint64 initialRiffChunkSize = 8 + initialds64ChunkSize + initialDataChunkSize; /* +8 for the ds64 header. */ - - runningPos += drwav__write(pWav, "ds64", 4); - runningPos += drwav__write_u32ne_to_le(pWav, initialds64ChunkSize); /* Size of ds64. */ - runningPos += drwav__write_u64ne_to_le(pWav, initialRiffChunkSize); /* Size of RIFF. Set to true value at the end. */ - runningPos += drwav__write_u64ne_to_le(pWav, initialDataChunkSize); /* Size of DATA. Set to true value at the end. */ - runningPos += drwav__write_u64ne_to_le(pWav, totalSampleCount); /* Sample count. */ - runningPos += drwav__write_u32ne_to_le(pWav, 0); /* Table length. Always set to zero in our case since we're not doing any other chunks than "DATA". */ - } - - - /* "fmt " chunk. */ - if (pFormat->container == drwav_container_riff || pFormat->container == drwav_container_rf64) { - chunkSizeFMT = 16; - runningPos += drwav__write(pWav, "fmt ", 4); - runningPos += drwav__write_u32ne_to_le(pWav, (drwav_uint32)chunkSizeFMT); - } - else if (pFormat->container == drwav_container_w64) { - chunkSizeFMT = 40; - runningPos += drwav__write(pWav, drwavGUID_W64_FMT, 16); - runningPos += drwav__write_u64ne_to_le(pWav, chunkSizeFMT); - } - - runningPos += drwav__write_u16ne_to_le(pWav, pWav->fmt.formatTag); - runningPos += drwav__write_u16ne_to_le(pWav, pWav->fmt.channels); - runningPos += drwav__write_u32ne_to_le(pWav, pWav->fmt.sampleRate); - runningPos += drwav__write_u32ne_to_le(pWav, pWav->fmt.avgBytesPerSec); - runningPos += drwav__write_u16ne_to_le(pWav, pWav->fmt.blockAlign); - runningPos += drwav__write_u16ne_to_le(pWav, pWav->fmt.bitsPerSample); - - /* TODO: is a 'fact' chunk required for DR_WAVE_FORMAT_IEEE_FLOAT? */ - - if (!pWav->isSequentialWrite && pWav->pMetadata != NULL && pWav->metadataCount > 0 && (pFormat->container == drwav_container_riff || pFormat->container == drwav_container_rf64)) { - runningPos += drwav__write_or_count_metadata(pWav, pWav->pMetadata, pWav->metadataCount); - } - - pWav->dataChunkDataPos = runningPos; - - /* "data" chunk. */ - if (pFormat->container == drwav_container_riff) { - drwav_uint32 chunkSizeDATA = (drwav_uint32)initialDataChunkSize; - runningPos += drwav__write(pWav, "data", 4); - runningPos += drwav__write_u32ne_to_le(pWav, chunkSizeDATA); - } - else if (pFormat->container == drwav_container_w64) { - drwav_uint64 chunkSizeDATA = 24 + initialDataChunkSize; /* +24 because W64 includes the size of the GUID and size fields. */ - runningPos += drwav__write(pWav, drwavGUID_W64_DATA, 16); - runningPos += drwav__write_u64ne_to_le(pWav, chunkSizeDATA); - } - else if (pFormat->container == drwav_container_rf64) { - runningPos += drwav__write(pWav, "data", 4); - runningPos += drwav__write_u32ne_to_le(pWav, 0xFFFFFFFF); /* Always set to 0xFFFFFFFF for RF64. The true size of the data chunk is specified in the ds64 chunk. */ - } - - /* Set some properties for the client's convenience. */ - pWav->container = pFormat->container; - pWav->channels = (drwav_uint16)pFormat->channels; - pWav->sampleRate = pFormat->sampleRate; - pWav->bitsPerSample = (drwav_uint16)pFormat->bitsPerSample; - pWav->translatedFormatTag = (drwav_uint16)pFormat->format; - pWav->dataChunkDataPos = runningPos; - - return DRWAV_TRUE; -} - - -DRWAV_API drwav_bool32 drwav_init_write(drwav* pWav, const drwav_data_format* pFormat, drwav_write_proc onWrite, drwav_seek_proc onSeek, void* pUserData, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - if (!drwav_preinit_write(pWav, pFormat, DRWAV_FALSE, onWrite, onSeek, pUserData, pAllocationCallbacks)) { - return DRWAV_FALSE; - } - - return drwav_init_write__internal(pWav, pFormat, 0); /* DRWAV_FALSE = Not Sequential */ -} - -DRWAV_API drwav_bool32 drwav_init_write_sequential(drwav* pWav, const drwav_data_format* pFormat, drwav_uint64 totalSampleCount, drwav_write_proc onWrite, void* pUserData, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - if (!drwav_preinit_write(pWav, pFormat, DRWAV_TRUE, onWrite, NULL, pUserData, pAllocationCallbacks)) { - return DRWAV_FALSE; - } - - return drwav_init_write__internal(pWav, pFormat, totalSampleCount); /* DRWAV_TRUE = Sequential */ -} - -DRWAV_API drwav_bool32 drwav_init_write_sequential_pcm_frames(drwav* pWav, const drwav_data_format* pFormat, drwav_uint64 totalPCMFrameCount, drwav_write_proc onWrite, void* pUserData, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - if (pFormat == NULL) { - return DRWAV_FALSE; - } - - return drwav_init_write_sequential(pWav, pFormat, totalPCMFrameCount * pFormat->channels, onWrite, pUserData, pAllocationCallbacks); -} - -DRWAV_API drwav_bool32 drwav_init_write_with_metadata(drwav* pWav, const drwav_data_format* pFormat, drwav_write_proc onWrite, drwav_seek_proc onSeek, void* pUserData, const drwav_allocation_callbacks* pAllocationCallbacks, drwav_metadata* pMetadata, drwav_uint32 metadataCount) -{ - if (!drwav_preinit_write(pWav, pFormat, DRWAV_FALSE, onWrite, onSeek, pUserData, pAllocationCallbacks)) { - return DRWAV_FALSE; - } - - pWav->pMetadata = pMetadata; - pWav->metadataCount = metadataCount; - - return drwav_init_write__internal(pWav, pFormat, 0); -} - - -DRWAV_API drwav_uint64 drwav_target_write_size_bytes(const drwav_data_format* pFormat, drwav_uint64 totalFrameCount, drwav_metadata* pMetadata, drwav_uint32 metadataCount) -{ - /* Casting totalFrameCount to drwav_int64 for VC6 compatibility. No issues in practice because nobody is going to exhaust the whole 63 bits. */ - drwav_uint64 targetDataSizeBytes = (drwav_uint64)((drwav_int64)totalFrameCount * pFormat->channels * pFormat->bitsPerSample / 8.0); - drwav_uint64 riffChunkSizeBytes; - drwav_uint64 fileSizeBytes = 0; - - if (pFormat->container == drwav_container_riff) { - riffChunkSizeBytes = drwav__riff_chunk_size_riff(targetDataSizeBytes, pMetadata, metadataCount); - fileSizeBytes = (8 + riffChunkSizeBytes); /* +8 because WAV doesn't include the size of the ChunkID and ChunkSize fields. */ - } - else if (pFormat->container == drwav_container_w64) { - riffChunkSizeBytes = drwav__riff_chunk_size_w64(targetDataSizeBytes); - fileSizeBytes = riffChunkSizeBytes; - } - else if (pFormat->container == drwav_container_rf64) { - riffChunkSizeBytes = drwav__riff_chunk_size_rf64(targetDataSizeBytes, pMetadata, metadataCount); - fileSizeBytes = (8 + riffChunkSizeBytes); /* +8 because WAV doesn't include the size of the ChunkID and ChunkSize fields. */ - } - - return fileSizeBytes; -} - - -#ifndef DR_WAV_NO_STDIO - -/* drwav_result_from_errno() is only used for fopen() and wfopen() so putting it inside DR_WAV_NO_STDIO for now. If something else needs this later we can move it out. */ -#include -DRWAV_PRIVATE drwav_result drwav_result_from_errno(int e) -{ - switch (e) - { - case 0: return DRWAV_SUCCESS; -#ifdef EPERM - case EPERM: return DRWAV_INVALID_OPERATION; -#endif -#ifdef ENOENT - case ENOENT: return DRWAV_DOES_NOT_EXIST; -#endif -#ifdef ESRCH - case ESRCH: return DRWAV_DOES_NOT_EXIST; -#endif -#ifdef EINTR - case EINTR: return DRWAV_INTERRUPT; -#endif -#ifdef EIO - case EIO: return DRWAV_IO_ERROR; -#endif -#ifdef ENXIO - case ENXIO: return DRWAV_DOES_NOT_EXIST; -#endif -#ifdef E2BIG - case E2BIG: return DRWAV_INVALID_ARGS; -#endif -#ifdef ENOEXEC - case ENOEXEC: return DRWAV_INVALID_FILE; -#endif -#ifdef EBADF - case EBADF: return DRWAV_INVALID_FILE; -#endif -#ifdef ECHILD - case ECHILD: return DRWAV_ERROR; -#endif -#ifdef EAGAIN - case EAGAIN: return DRWAV_UNAVAILABLE; -#endif -#ifdef ENOMEM - case ENOMEM: return DRWAV_OUT_OF_MEMORY; -#endif -#ifdef EACCES - case EACCES: return DRWAV_ACCESS_DENIED; -#endif -#ifdef EFAULT - case EFAULT: return DRWAV_BAD_ADDRESS; -#endif -#ifdef ENOTBLK - case ENOTBLK: return DRWAV_ERROR; -#endif -#ifdef EBUSY - case EBUSY: return DRWAV_BUSY; -#endif -#ifdef EEXIST - case EEXIST: return DRWAV_ALREADY_EXISTS; -#endif -#ifdef EXDEV - case EXDEV: return DRWAV_ERROR; -#endif -#ifdef ENODEV - case ENODEV: return DRWAV_DOES_NOT_EXIST; -#endif -#ifdef ENOTDIR - case ENOTDIR: return DRWAV_NOT_DIRECTORY; -#endif -#ifdef EISDIR - case EISDIR: return DRWAV_IS_DIRECTORY; -#endif -#ifdef EINVAL - case EINVAL: return DRWAV_INVALID_ARGS; -#endif -#ifdef ENFILE - case ENFILE: return DRWAV_TOO_MANY_OPEN_FILES; -#endif -#ifdef EMFILE - case EMFILE: return DRWAV_TOO_MANY_OPEN_FILES; -#endif -#ifdef ENOTTY - case ENOTTY: return DRWAV_INVALID_OPERATION; -#endif -#ifdef ETXTBSY - case ETXTBSY: return DRWAV_BUSY; -#endif -#ifdef EFBIG - case EFBIG: return DRWAV_TOO_BIG; -#endif -#ifdef ENOSPC - case ENOSPC: return DRWAV_NO_SPACE; -#endif -#ifdef ESPIPE - case ESPIPE: return DRWAV_BAD_SEEK; -#endif -#ifdef EROFS - case EROFS: return DRWAV_ACCESS_DENIED; -#endif -#ifdef EMLINK - case EMLINK: return DRWAV_TOO_MANY_LINKS; -#endif -#ifdef EPIPE - case EPIPE: return DRWAV_BAD_PIPE; -#endif -#ifdef EDOM - case EDOM: return DRWAV_OUT_OF_RANGE; -#endif -#ifdef ERANGE - case ERANGE: return DRWAV_OUT_OF_RANGE; -#endif -#ifdef EDEADLK - case EDEADLK: return DRWAV_DEADLOCK; -#endif -#ifdef ENAMETOOLONG - case ENAMETOOLONG: return DRWAV_PATH_TOO_LONG; -#endif -#ifdef ENOLCK - case ENOLCK: return DRWAV_ERROR; -#endif -#ifdef ENOSYS - case ENOSYS: return DRWAV_NOT_IMPLEMENTED; -#endif -#ifdef ENOTEMPTY - case ENOTEMPTY: return DRWAV_DIRECTORY_NOT_EMPTY; -#endif -#ifdef ELOOP - case ELOOP: return DRWAV_TOO_MANY_LINKS; -#endif -#ifdef ENOMSG - case ENOMSG: return DRWAV_NO_MESSAGE; -#endif -#ifdef EIDRM - case EIDRM: return DRWAV_ERROR; -#endif -#ifdef ECHRNG - case ECHRNG: return DRWAV_ERROR; -#endif -#ifdef EL2NSYNC - case EL2NSYNC: return DRWAV_ERROR; -#endif -#ifdef EL3HLT - case EL3HLT: return DRWAV_ERROR; -#endif -#ifdef EL3RST - case EL3RST: return DRWAV_ERROR; -#endif -#ifdef ELNRNG - case ELNRNG: return DRWAV_OUT_OF_RANGE; -#endif -#ifdef EUNATCH - case EUNATCH: return DRWAV_ERROR; -#endif -#ifdef ENOCSI - case ENOCSI: return DRWAV_ERROR; -#endif -#ifdef EL2HLT - case EL2HLT: return DRWAV_ERROR; -#endif -#ifdef EBADE - case EBADE: return DRWAV_ERROR; -#endif -#ifdef EBADR - case EBADR: return DRWAV_ERROR; -#endif -#ifdef EXFULL - case EXFULL: return DRWAV_ERROR; -#endif -#ifdef ENOANO - case ENOANO: return DRWAV_ERROR; -#endif -#ifdef EBADRQC - case EBADRQC: return DRWAV_ERROR; -#endif -#ifdef EBADSLT - case EBADSLT: return DRWAV_ERROR; -#endif -#ifdef EBFONT - case EBFONT: return DRWAV_INVALID_FILE; -#endif -#ifdef ENOSTR - case ENOSTR: return DRWAV_ERROR; -#endif -#ifdef ENODATA - case ENODATA: return DRWAV_NO_DATA_AVAILABLE; -#endif -#ifdef ETIME - case ETIME: return DRWAV_TIMEOUT; -#endif -#ifdef ENOSR - case ENOSR: return DRWAV_NO_DATA_AVAILABLE; -#endif -#ifdef ENONET - case ENONET: return DRWAV_NO_NETWORK; -#endif -#ifdef ENOPKG - case ENOPKG: return DRWAV_ERROR; -#endif -#ifdef EREMOTE - case EREMOTE: return DRWAV_ERROR; -#endif -#ifdef ENOLINK - case ENOLINK: return DRWAV_ERROR; -#endif -#ifdef EADV - case EADV: return DRWAV_ERROR; -#endif -#ifdef ESRMNT - case ESRMNT: return DRWAV_ERROR; -#endif -#ifdef ECOMM - case ECOMM: return DRWAV_ERROR; -#endif -#ifdef EPROTO - case EPROTO: return DRWAV_ERROR; -#endif -#ifdef EMULTIHOP - case EMULTIHOP: return DRWAV_ERROR; -#endif -#ifdef EDOTDOT - case EDOTDOT: return DRWAV_ERROR; -#endif -#ifdef EBADMSG - case EBADMSG: return DRWAV_BAD_MESSAGE; -#endif -#ifdef EOVERFLOW - case EOVERFLOW: return DRWAV_TOO_BIG; -#endif -#ifdef ENOTUNIQ - case ENOTUNIQ: return DRWAV_NOT_UNIQUE; -#endif -#ifdef EBADFD - case EBADFD: return DRWAV_ERROR; -#endif -#ifdef EREMCHG - case EREMCHG: return DRWAV_ERROR; -#endif -#ifdef ELIBACC - case ELIBACC: return DRWAV_ACCESS_DENIED; -#endif -#ifdef ELIBBAD - case ELIBBAD: return DRWAV_INVALID_FILE; -#endif -#ifdef ELIBSCN - case ELIBSCN: return DRWAV_INVALID_FILE; -#endif -#ifdef ELIBMAX - case ELIBMAX: return DRWAV_ERROR; -#endif -#ifdef ELIBEXEC - case ELIBEXEC: return DRWAV_ERROR; -#endif -#ifdef EILSEQ - case EILSEQ: return DRWAV_INVALID_DATA; -#endif -#ifdef ERESTART - case ERESTART: return DRWAV_ERROR; -#endif -#ifdef ESTRPIPE - case ESTRPIPE: return DRWAV_ERROR; -#endif -#ifdef EUSERS - case EUSERS: return DRWAV_ERROR; -#endif -#ifdef ENOTSOCK - case ENOTSOCK: return DRWAV_NOT_SOCKET; -#endif -#ifdef EDESTADDRREQ - case EDESTADDRREQ: return DRWAV_NO_ADDRESS; -#endif -#ifdef EMSGSIZE - case EMSGSIZE: return DRWAV_TOO_BIG; -#endif -#ifdef EPROTOTYPE - case EPROTOTYPE: return DRWAV_BAD_PROTOCOL; -#endif -#ifdef ENOPROTOOPT - case ENOPROTOOPT: return DRWAV_PROTOCOL_UNAVAILABLE; -#endif -#ifdef EPROTONOSUPPORT - case EPROTONOSUPPORT: return DRWAV_PROTOCOL_NOT_SUPPORTED; -#endif -#ifdef ESOCKTNOSUPPORT - case ESOCKTNOSUPPORT: return DRWAV_SOCKET_NOT_SUPPORTED; -#endif -#ifdef EOPNOTSUPP - case EOPNOTSUPP: return DRWAV_INVALID_OPERATION; -#endif -#ifdef EPFNOSUPPORT - case EPFNOSUPPORT: return DRWAV_PROTOCOL_FAMILY_NOT_SUPPORTED; -#endif -#ifdef EAFNOSUPPORT - case EAFNOSUPPORT: return DRWAV_ADDRESS_FAMILY_NOT_SUPPORTED; -#endif -#ifdef EADDRINUSE - case EADDRINUSE: return DRWAV_ALREADY_IN_USE; -#endif -#ifdef EADDRNOTAVAIL - case EADDRNOTAVAIL: return DRWAV_ERROR; -#endif -#ifdef ENETDOWN - case ENETDOWN: return DRWAV_NO_NETWORK; -#endif -#ifdef ENETUNREACH - case ENETUNREACH: return DRWAV_NO_NETWORK; -#endif -#ifdef ENETRESET - case ENETRESET: return DRWAV_NO_NETWORK; -#endif -#ifdef ECONNABORTED - case ECONNABORTED: return DRWAV_NO_NETWORK; -#endif -#ifdef ECONNRESET - case ECONNRESET: return DRWAV_CONNECTION_RESET; -#endif -#ifdef ENOBUFS - case ENOBUFS: return DRWAV_NO_SPACE; -#endif -#ifdef EISCONN - case EISCONN: return DRWAV_ALREADY_CONNECTED; -#endif -#ifdef ENOTCONN - case ENOTCONN: return DRWAV_NOT_CONNECTED; -#endif -#ifdef ESHUTDOWN - case ESHUTDOWN: return DRWAV_ERROR; -#endif -#ifdef ETOOMANYREFS - case ETOOMANYREFS: return DRWAV_ERROR; -#endif -#ifdef ETIMEDOUT - case ETIMEDOUT: return DRWAV_TIMEOUT; -#endif -#ifdef ECONNREFUSED - case ECONNREFUSED: return DRWAV_CONNECTION_REFUSED; -#endif -#ifdef EHOSTDOWN - case EHOSTDOWN: return DRWAV_NO_HOST; -#endif -#ifdef EHOSTUNREACH - case EHOSTUNREACH: return DRWAV_NO_HOST; -#endif -#ifdef EALREADY - case EALREADY: return DRWAV_IN_PROGRESS; -#endif -#ifdef EINPROGRESS - case EINPROGRESS: return DRWAV_IN_PROGRESS; -#endif -#ifdef ESTALE - case ESTALE: return DRWAV_INVALID_FILE; -#endif -#ifdef EUCLEAN - case EUCLEAN: return DRWAV_ERROR; -#endif -#ifdef ENOTNAM - case ENOTNAM: return DRWAV_ERROR; -#endif -#ifdef ENAVAIL - case ENAVAIL: return DRWAV_ERROR; -#endif -#ifdef EISNAM - case EISNAM: return DRWAV_ERROR; -#endif -#ifdef EREMOTEIO - case EREMOTEIO: return DRWAV_IO_ERROR; -#endif -#ifdef EDQUOT - case EDQUOT: return DRWAV_NO_SPACE; -#endif -#ifdef ENOMEDIUM - case ENOMEDIUM: return DRWAV_DOES_NOT_EXIST; -#endif -#ifdef EMEDIUMTYPE - case EMEDIUMTYPE: return DRWAV_ERROR; -#endif -#ifdef ECANCELED - case ECANCELED: return DRWAV_CANCELLED; -#endif -#ifdef ENOKEY - case ENOKEY: return DRWAV_ERROR; -#endif -#ifdef EKEYEXPIRED - case EKEYEXPIRED: return DRWAV_ERROR; -#endif -#ifdef EKEYREVOKED - case EKEYREVOKED: return DRWAV_ERROR; -#endif -#ifdef EKEYREJECTED - case EKEYREJECTED: return DRWAV_ERROR; -#endif -#ifdef EOWNERDEAD - case EOWNERDEAD: return DRWAV_ERROR; -#endif -#ifdef ENOTRECOVERABLE - case ENOTRECOVERABLE: return DRWAV_ERROR; -#endif -#ifdef ERFKILL - case ERFKILL: return DRWAV_ERROR; -#endif -#ifdef EHWPOISON - case EHWPOISON: return DRWAV_ERROR; -#endif - default: return DRWAV_ERROR; - } -} - -DRWAV_PRIVATE drwav_result drwav_fopen(FILE** ppFile, const char* pFilePath, const char* pOpenMode) -{ -#if defined(_MSC_VER) && _MSC_VER >= 1400 - errno_t err; -#endif - - if (ppFile != NULL) { - *ppFile = NULL; /* Safety. */ - } - - if (pFilePath == NULL || pOpenMode == NULL || ppFile == NULL) { - return DRWAV_INVALID_ARGS; - } - -#if defined(_MSC_VER) && _MSC_VER >= 1400 - err = fopen_s(ppFile, pFilePath, pOpenMode); - if (err != 0) { - return drwav_result_from_errno(err); - } -#else -#if defined(_WIN32) || defined(__APPLE__) - *ppFile = fopen(pFilePath, pOpenMode); -#else -#if defined(_FILE_OFFSET_BITS) && _FILE_OFFSET_BITS == 64 && defined(_LARGEFILE64_SOURCE) - *ppFile = fopen64(pFilePath, pOpenMode); -#else - * ppFile = fopen(pFilePath, pOpenMode); -#endif -#endif - if (*ppFile == NULL) { - drwav_result result = drwav_result_from_errno(errno); - if (result == DRWAV_SUCCESS) { - result = DRWAV_ERROR; /* Just a safety check to make sure we never ever return success when pFile == NULL. */ - } - - return result; - } -#endif - - return DRWAV_SUCCESS; -} - -/* -_wfopen() isn't always available in all compilation environments. - - * Windows only. - * MSVC seems to support it universally as far back as VC6 from what I can tell (haven't checked further back). - * MinGW-64 (both 32- and 64-bit) seems to support it. - * MinGW wraps it in !defined(__STRICT_ANSI__). - * OpenWatcom wraps it in !defined(_NO_EXT_KEYS). - -This can be reviewed as compatibility issues arise. The preference is to use _wfopen_s() and _wfopen() as opposed to the wcsrtombs() -fallback, so if you notice your compiler not detecting this properly I'm happy to look at adding support. -*/ -#if defined(_WIN32) -#if defined(_MSC_VER) || defined(__MINGW64__) || (!defined(__STRICT_ANSI__) && !defined(_NO_EXT_KEYS)) -#define DRWAV_HAS_WFOPEN -#endif -#endif - -DRWAV_PRIVATE drwav_result drwav_wfopen(FILE** ppFile, const wchar_t* pFilePath, const wchar_t* pOpenMode, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - if (ppFile != NULL) { - *ppFile = NULL; /* Safety. */ - } - - if (pFilePath == NULL || pOpenMode == NULL || ppFile == NULL) { - return DRWAV_INVALID_ARGS; - } - -#if defined(DRWAV_HAS_WFOPEN) - { - /* Use _wfopen() on Windows. */ -#if defined(_MSC_VER) && _MSC_VER >= 1400 - errno_t err = _wfopen_s(ppFile, pFilePath, pOpenMode); - if (err != 0) { - return drwav_result_from_errno(err); - } -#else - * ppFile = _wfopen(pFilePath, pOpenMode); - if (*ppFile == NULL) { - return drwav_result_from_errno(errno); - } -#endif - (void)pAllocationCallbacks; - } -#else - /* - Use fopen() on anything other than Windows. Requires a conversion. This is annoying because fopen() is locale specific. The only real way I can - think of to do this is with wcsrtombs(). Note that wcstombs() is apparently not thread-safe because it uses a static global mbstate_t object for - maintaining state. I've checked this with -std=c89 and it works, but if somebody get's a compiler error I'll look into improving compatibility. - */ - { - mbstate_t mbs; - size_t lenMB; - const wchar_t* pFilePathTemp = pFilePath; - char* pFilePathMB = NULL; - char pOpenModeMB[32] = { 0 }; - - /* Get the length first. */ - DRWAV_ZERO_OBJECT(&mbs); - lenMB = wcsrtombs(NULL, &pFilePathTemp, 0, &mbs); - if (lenMB == (size_t)-1) { - return drwav_result_from_errno(errno); - } - - pFilePathMB = (char*)drwav__malloc_from_callbacks(lenMB + 1, pAllocationCallbacks); - if (pFilePathMB == NULL) { - return DRWAV_OUT_OF_MEMORY; - } - - pFilePathTemp = pFilePath; - DRWAV_ZERO_OBJECT(&mbs); - wcsrtombs(pFilePathMB, &pFilePathTemp, lenMB + 1, &mbs); - - /* The open mode should always consist of ASCII characters so we should be able to do a trivial conversion. */ - { - size_t i = 0; - for (;;) { - if (pOpenMode[i] == 0) { - pOpenModeMB[i] = '\0'; - break; - } - - pOpenModeMB[i] = (char)pOpenMode[i]; - i += 1; - } - } - - *ppFile = fopen(pFilePathMB, pOpenModeMB); - - drwav__free_from_callbacks(pFilePathMB, pAllocationCallbacks); - } - - if (*ppFile == NULL) { - return DRWAV_ERROR; - } -#endif - - return DRWAV_SUCCESS; -} - - -DRWAV_PRIVATE size_t drwav__on_read_stdio(void* pUserData, void* pBufferOut, size_t bytesToRead) -{ - return fread(pBufferOut, 1, bytesToRead, (FILE*)pUserData); -} - -DRWAV_PRIVATE size_t drwav__on_write_stdio(void* pUserData, const void* pData, size_t bytesToWrite) -{ - return fwrite(pData, 1, bytesToWrite, (FILE*)pUserData); -} - -DRWAV_PRIVATE drwav_bool32 drwav__on_seek_stdio(void* pUserData, int offset, drwav_seek_origin origin) -{ - return fseek((FILE*)pUserData, offset, (origin == drwav_seek_origin_current) ? SEEK_CUR : SEEK_SET) == 0; -} - -DRWAV_API drwav_bool32 drwav_init_file(drwav* pWav, const char* filename, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - return drwav_init_file_ex(pWav, filename, NULL, NULL, 0, pAllocationCallbacks); -} - - -DRWAV_PRIVATE drwav_bool32 drwav_init_file__internal_FILE(drwav* pWav, FILE* pFile, drwav_chunk_proc onChunk, void* pChunkUserData, drwav_uint32 flags, drwav_metadata_type allowedMetadataTypes, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - drwav_bool32 result; - - result = drwav_preinit(pWav, drwav__on_read_stdio, drwav__on_seek_stdio, (void*)pFile, pAllocationCallbacks); - if (result != DRWAV_TRUE) { - fclose(pFile); - return result; - } - - pWav->allowedMetadataTypes = allowedMetadataTypes; - - result = drwav_init__internal(pWav, onChunk, pChunkUserData, flags); - if (result != DRWAV_TRUE) { - fclose(pFile); - return result; - } - - return DRWAV_TRUE; -} - -DRWAV_API drwav_bool32 drwav_init_file_ex(drwav* pWav, const char* filename, drwav_chunk_proc onChunk, void* pChunkUserData, drwav_uint32 flags, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - FILE* pFile; - if (drwav_fopen(&pFile, filename, "rb") != DRWAV_SUCCESS) { - return DRWAV_FALSE; - } - - /* This takes ownership of the FILE* object. */ - return drwav_init_file__internal_FILE(pWav, pFile, onChunk, pChunkUserData, flags, drwav_metadata_type_none, pAllocationCallbacks); -} - -DRWAV_API drwav_bool32 drwav_init_file_w(drwav* pWav, const wchar_t* filename, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - return drwav_init_file_ex_w(pWav, filename, NULL, NULL, 0, pAllocationCallbacks); -} - -DRWAV_API drwav_bool32 drwav_init_file_ex_w(drwav* pWav, const wchar_t* filename, drwav_chunk_proc onChunk, void* pChunkUserData, drwav_uint32 flags, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - FILE* pFile; - if (drwav_wfopen(&pFile, filename, L"rb", pAllocationCallbacks) != DRWAV_SUCCESS) { - return DRWAV_FALSE; - } - - /* This takes ownership of the FILE* object. */ - return drwav_init_file__internal_FILE(pWav, pFile, onChunk, pChunkUserData, flags, drwav_metadata_type_none, pAllocationCallbacks); -} - -DRWAV_API drwav_bool32 drwav_init_file_with_metadata(drwav* pWav, const char* filename, drwav_uint32 flags, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - FILE* pFile; - if (drwav_fopen(&pFile, filename, "rb") != DRWAV_SUCCESS) { - return DRWAV_FALSE; - } - - /* This takes ownership of the FILE* object. */ - return drwav_init_file__internal_FILE(pWav, pFile, NULL, NULL, flags, drwav_metadata_type_all_including_unknown, pAllocationCallbacks); -} - -DRWAV_API drwav_bool32 drwav_init_file_with_metadata_w(drwav* pWav, const wchar_t* filename, drwav_uint32 flags, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - FILE* pFile; - if (drwav_wfopen(&pFile, filename, L"rb", pAllocationCallbacks) != DRWAV_SUCCESS) { - return DRWAV_FALSE; - } - - /* This takes ownership of the FILE* object. */ - return drwav_init_file__internal_FILE(pWav, pFile, NULL, NULL, flags, drwav_metadata_type_all_including_unknown, pAllocationCallbacks); -} - - -DRWAV_PRIVATE drwav_bool32 drwav_init_file_write__internal_FILE(drwav* pWav, FILE* pFile, const drwav_data_format* pFormat, drwav_uint64 totalSampleCount, drwav_bool32 isSequential, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - drwav_bool32 result; - - result = drwav_preinit_write(pWav, pFormat, isSequential, drwav__on_write_stdio, drwav__on_seek_stdio, (void*)pFile, pAllocationCallbacks); - if (result != DRWAV_TRUE) { - fclose(pFile); - return result; - } - - result = drwav_init_write__internal(pWav, pFormat, totalSampleCount); - if (result != DRWAV_TRUE) { - fclose(pFile); - return result; - } - - return DRWAV_TRUE; -} - -DRWAV_PRIVATE drwav_bool32 drwav_init_file_write__internal(drwav* pWav, const char* filename, const drwav_data_format* pFormat, drwav_uint64 totalSampleCount, drwav_bool32 isSequential, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - FILE* pFile; - if (drwav_fopen(&pFile, filename, "wb") != DRWAV_SUCCESS) { - return DRWAV_FALSE; - } - - /* This takes ownership of the FILE* object. */ - return drwav_init_file_write__internal_FILE(pWav, pFile, pFormat, totalSampleCount, isSequential, pAllocationCallbacks); -} - -DRWAV_PRIVATE drwav_bool32 drwav_init_file_write_w__internal(drwav* pWav, const wchar_t* filename, const drwav_data_format* pFormat, drwav_uint64 totalSampleCount, drwav_bool32 isSequential, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - FILE* pFile; - if (drwav_wfopen(&pFile, filename, L"wb", pAllocationCallbacks) != DRWAV_SUCCESS) { - return DRWAV_FALSE; - } - - /* This takes ownership of the FILE* object. */ - return drwav_init_file_write__internal_FILE(pWav, pFile, pFormat, totalSampleCount, isSequential, pAllocationCallbacks); -} - -DRWAV_API drwav_bool32 drwav_init_file_write(drwav* pWav, const char* filename, const drwav_data_format* pFormat, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - return drwav_init_file_write__internal(pWav, filename, pFormat, 0, DRWAV_FALSE, pAllocationCallbacks); -} - -DRWAV_API drwav_bool32 drwav_init_file_write_sequential(drwav* pWav, const char* filename, const drwav_data_format* pFormat, drwav_uint64 totalSampleCount, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - return drwav_init_file_write__internal(pWav, filename, pFormat, totalSampleCount, DRWAV_TRUE, pAllocationCallbacks); -} - -DRWAV_API drwav_bool32 drwav_init_file_write_sequential_pcm_frames(drwav* pWav, const char* filename, const drwav_data_format* pFormat, drwav_uint64 totalPCMFrameCount, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - if (pFormat == NULL) { - return DRWAV_FALSE; - } - - return drwav_init_file_write_sequential(pWav, filename, pFormat, totalPCMFrameCount * pFormat->channels, pAllocationCallbacks); -} - -DRWAV_API drwav_bool32 drwav_init_file_write_w(drwav* pWav, const wchar_t* filename, const drwav_data_format* pFormat, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - return drwav_init_file_write_w__internal(pWav, filename, pFormat, 0, DRWAV_FALSE, pAllocationCallbacks); -} - -DRWAV_API drwav_bool32 drwav_init_file_write_sequential_w(drwav* pWav, const wchar_t* filename, const drwav_data_format* pFormat, drwav_uint64 totalSampleCount, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - return drwav_init_file_write_w__internal(pWav, filename, pFormat, totalSampleCount, DRWAV_TRUE, pAllocationCallbacks); -} - -DRWAV_API drwav_bool32 drwav_init_file_write_sequential_pcm_frames_w(drwav* pWav, const wchar_t* filename, const drwav_data_format* pFormat, drwav_uint64 totalPCMFrameCount, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - if (pFormat == NULL) { - return DRWAV_FALSE; - } - - return drwav_init_file_write_sequential_w(pWav, filename, pFormat, totalPCMFrameCount * pFormat->channels, pAllocationCallbacks); -} -#endif /* DR_WAV_NO_STDIO */ - - -DRWAV_PRIVATE size_t drwav__on_read_memory(void* pUserData, void* pBufferOut, size_t bytesToRead) -{ - drwav* pWav = (drwav*)pUserData; - size_t bytesRemaining; - - DRWAV_ASSERT(pWav != NULL); - DRWAV_ASSERT(pWav->memoryStream.dataSize >= pWav->memoryStream.currentReadPos); - - bytesRemaining = pWav->memoryStream.dataSize - pWav->memoryStream.currentReadPos; - if (bytesToRead > bytesRemaining) { - bytesToRead = bytesRemaining; - } - - if (bytesToRead > 0) { - DRWAV_COPY_MEMORY(pBufferOut, pWav->memoryStream.data + pWav->memoryStream.currentReadPos, bytesToRead); - pWav->memoryStream.currentReadPos += bytesToRead; - } - - return bytesToRead; -} - -DRWAV_PRIVATE drwav_bool32 drwav__on_seek_memory(void* pUserData, int offset, drwav_seek_origin origin) -{ - drwav* pWav = (drwav*)pUserData; - DRWAV_ASSERT(pWav != NULL); - - if (origin == drwav_seek_origin_current) { - if (offset > 0) { - if (pWav->memoryStream.currentReadPos + offset > pWav->memoryStream.dataSize) { - return DRWAV_FALSE; /* Trying to seek too far forward. */ - } - } - else { - if (pWav->memoryStream.currentReadPos < (size_t)-offset) { - return DRWAV_FALSE; /* Trying to seek too far backwards. */ - } - } - - /* This will never underflow thanks to the clamps above. */ - pWav->memoryStream.currentReadPos += offset; - } - else { - if ((drwav_uint32)offset <= pWav->memoryStream.dataSize) { - pWav->memoryStream.currentReadPos = offset; - } - else { - return DRWAV_FALSE; /* Trying to seek too far forward. */ - } - } - - return DRWAV_TRUE; -} - -DRWAV_PRIVATE size_t drwav__on_write_memory(void* pUserData, const void* pDataIn, size_t bytesToWrite) -{ - drwav* pWav = (drwav*)pUserData; - size_t bytesRemaining; - - DRWAV_ASSERT(pWav != NULL); - DRWAV_ASSERT(pWav->memoryStreamWrite.dataCapacity >= pWav->memoryStreamWrite.currentWritePos); - - bytesRemaining = pWav->memoryStreamWrite.dataCapacity - pWav->memoryStreamWrite.currentWritePos; - if (bytesRemaining < bytesToWrite) { - /* Need to reallocate. */ - void* pNewData; - size_t newDataCapacity = (pWav->memoryStreamWrite.dataCapacity == 0) ? 256 : pWav->memoryStreamWrite.dataCapacity * 2; - - /* If doubling wasn't enough, just make it the minimum required size to write the data. */ - if ((newDataCapacity - pWav->memoryStreamWrite.currentWritePos) < bytesToWrite) { - newDataCapacity = pWav->memoryStreamWrite.currentWritePos + bytesToWrite; - } - - pNewData = drwav__realloc_from_callbacks(*pWav->memoryStreamWrite.ppData, newDataCapacity, pWav->memoryStreamWrite.dataCapacity, &pWav->allocationCallbacks); - if (pNewData == NULL) { - return 0; - } - - *pWav->memoryStreamWrite.ppData = pNewData; - pWav->memoryStreamWrite.dataCapacity = newDataCapacity; - } - - DRWAV_COPY_MEMORY(((drwav_uint8*)(*pWav->memoryStreamWrite.ppData)) + pWav->memoryStreamWrite.currentWritePos, pDataIn, bytesToWrite); - - pWav->memoryStreamWrite.currentWritePos += bytesToWrite; - if (pWav->memoryStreamWrite.dataSize < pWav->memoryStreamWrite.currentWritePos) { - pWav->memoryStreamWrite.dataSize = pWav->memoryStreamWrite.currentWritePos; - } - - *pWav->memoryStreamWrite.pDataSize = pWav->memoryStreamWrite.dataSize; - - return bytesToWrite; -} - -DRWAV_PRIVATE drwav_bool32 drwav__on_seek_memory_write(void* pUserData, int offset, drwav_seek_origin origin) -{ - drwav* pWav = (drwav*)pUserData; - DRWAV_ASSERT(pWav != NULL); - - if (origin == drwav_seek_origin_current) { - if (offset > 0) { - if (pWav->memoryStreamWrite.currentWritePos + offset > pWav->memoryStreamWrite.dataSize) { - offset = (int)(pWav->memoryStreamWrite.dataSize - pWav->memoryStreamWrite.currentWritePos); /* Trying to seek too far forward. */ - } - } - else { - if (pWav->memoryStreamWrite.currentWritePos < (size_t)-offset) { - offset = -(int)pWav->memoryStreamWrite.currentWritePos; /* Trying to seek too far backwards. */ - } - } - - /* This will never underflow thanks to the clamps above. */ - pWav->memoryStreamWrite.currentWritePos += offset; - } - else { - if ((drwav_uint32)offset <= pWav->memoryStreamWrite.dataSize) { - pWav->memoryStreamWrite.currentWritePos = offset; - } - else { - pWav->memoryStreamWrite.currentWritePos = pWav->memoryStreamWrite.dataSize; /* Trying to seek too far forward. */ - } - } - - return DRWAV_TRUE; -} - -DRWAV_API drwav_bool32 drwav_init_memory(drwav* pWav, const void* data, size_t dataSize, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - return drwav_init_memory_ex(pWav, data, dataSize, NULL, NULL, 0, pAllocationCallbacks); -} - -DRWAV_API drwav_bool32 drwav_init_memory_ex(drwav* pWav, const void* data, size_t dataSize, drwav_chunk_proc onChunk, void* pChunkUserData, drwav_uint32 flags, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - if (data == NULL || dataSize == 0) { - return DRWAV_FALSE; - } - - if (!drwav_preinit(pWav, drwav__on_read_memory, drwav__on_seek_memory, pWav, pAllocationCallbacks)) { - return DRWAV_FALSE; - } - - pWav->memoryStream.data = (const drwav_uint8*)data; - pWav->memoryStream.dataSize = dataSize; - pWav->memoryStream.currentReadPos = 0; - - return drwav_init__internal(pWav, onChunk, pChunkUserData, flags); -} - -DRWAV_API drwav_bool32 drwav_init_memory_with_metadata(drwav* pWav, const void* data, size_t dataSize, drwav_uint32 flags, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - if (data == NULL || dataSize == 0) { - return DRWAV_FALSE; - } - - if (!drwav_preinit(pWav, drwav__on_read_memory, drwav__on_seek_memory, pWav, pAllocationCallbacks)) { - return DRWAV_FALSE; - } - - pWav->memoryStream.data = (const drwav_uint8*)data; - pWav->memoryStream.dataSize = dataSize; - pWav->memoryStream.currentReadPos = 0; - - pWav->allowedMetadataTypes = drwav_metadata_type_all_including_unknown; - - return drwav_init__internal(pWav, NULL, NULL, flags); -} - - -DRWAV_PRIVATE drwav_bool32 drwav_init_memory_write__internal(drwav* pWav, void** ppData, size_t* pDataSize, const drwav_data_format* pFormat, drwav_uint64 totalSampleCount, drwav_bool32 isSequential, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - if (ppData == NULL || pDataSize == NULL) { - return DRWAV_FALSE; - } - - *ppData = NULL; /* Important because we're using realloc()! */ - *pDataSize = 0; - - if (!drwav_preinit_write(pWav, pFormat, isSequential, drwav__on_write_memory, drwav__on_seek_memory_write, pWav, pAllocationCallbacks)) { - return DRWAV_FALSE; - } - - pWav->memoryStreamWrite.ppData = ppData; - pWav->memoryStreamWrite.pDataSize = pDataSize; - pWav->memoryStreamWrite.dataSize = 0; - pWav->memoryStreamWrite.dataCapacity = 0; - pWav->memoryStreamWrite.currentWritePos = 0; - - return drwav_init_write__internal(pWav, pFormat, totalSampleCount); -} - -DRWAV_API drwav_bool32 drwav_init_memory_write(drwav* pWav, void** ppData, size_t* pDataSize, const drwav_data_format* pFormat, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - return drwav_init_memory_write__internal(pWav, ppData, pDataSize, pFormat, 0, DRWAV_FALSE, pAllocationCallbacks); -} - -DRWAV_API drwav_bool32 drwav_init_memory_write_sequential(drwav* pWav, void** ppData, size_t* pDataSize, const drwav_data_format* pFormat, drwav_uint64 totalSampleCount, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - return drwav_init_memory_write__internal(pWav, ppData, pDataSize, pFormat, totalSampleCount, DRWAV_TRUE, pAllocationCallbacks); -} - -DRWAV_API drwav_bool32 drwav_init_memory_write_sequential_pcm_frames(drwav* pWav, void** ppData, size_t* pDataSize, const drwav_data_format* pFormat, drwav_uint64 totalPCMFrameCount, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - if (pFormat == NULL) { - return DRWAV_FALSE; - } - - return drwav_init_memory_write_sequential(pWav, ppData, pDataSize, pFormat, totalPCMFrameCount * pFormat->channels, pAllocationCallbacks); -} - - - -DRWAV_API drwav_result drwav_uninit(drwav* pWav) -{ - drwav_result result = DRWAV_SUCCESS; - - if (pWav == NULL) { - return DRWAV_INVALID_ARGS; - } - - /* - If the drwav object was opened in write mode we'll need to finalize a few things: - - Make sure the "data" chunk is aligned to 16-bits for RIFF containers, or 64 bits for W64 containers. - - Set the size of the "data" chunk. - */ - if (pWav->onWrite != NULL) { - drwav_uint32 paddingSize = 0; - - /* Padding. Do not adjust pWav->dataChunkDataSize - this should not include the padding. */ - if (pWav->container == drwav_container_riff || pWav->container == drwav_container_rf64) { - paddingSize = drwav__chunk_padding_size_riff(pWav->dataChunkDataSize); - } - else { - paddingSize = drwav__chunk_padding_size_w64(pWav->dataChunkDataSize); - } - - if (paddingSize > 0) { - drwav_uint64 paddingData = 0; - drwav__write(pWav, &paddingData, paddingSize); /* Byte order does not matter for this. */ - } - - /* - Chunk sizes. When using sequential mode, these will have been filled in at initialization time. We only need - to do this when using non-sequential mode. - */ - if (pWav->onSeek && !pWav->isSequentialWrite) { - if (pWav->container == drwav_container_riff) { - /* The "RIFF" chunk size. */ - if (pWav->onSeek(pWav->pUserData, 4, drwav_seek_origin_start)) { - drwav_uint32 riffChunkSize = drwav__riff_chunk_size_riff(pWav->dataChunkDataSize, pWav->pMetadata, pWav->metadataCount); - drwav__write_u32ne_to_le(pWav, riffChunkSize); - } - - /* The "data" chunk size. */ - if (pWav->onSeek(pWav->pUserData, (int)pWav->dataChunkDataPos - 4, drwav_seek_origin_start)) { - drwav_uint32 dataChunkSize = drwav__data_chunk_size_riff(pWav->dataChunkDataSize); - drwav__write_u32ne_to_le(pWav, dataChunkSize); - } - } - else if (pWav->container == drwav_container_w64) { - /* The "RIFF" chunk size. */ - if (pWav->onSeek(pWav->pUserData, 16, drwav_seek_origin_start)) { - drwav_uint64 riffChunkSize = drwav__riff_chunk_size_w64(pWav->dataChunkDataSize); - drwav__write_u64ne_to_le(pWav, riffChunkSize); - } - - /* The "data" chunk size. */ - if (pWav->onSeek(pWav->pUserData, (int)pWav->dataChunkDataPos - 8, drwav_seek_origin_start)) { - drwav_uint64 dataChunkSize = drwav__data_chunk_size_w64(pWav->dataChunkDataSize); - drwav__write_u64ne_to_le(pWav, dataChunkSize); - } - } - else if (pWav->container == drwav_container_rf64) { - /* We only need to update the ds64 chunk. The "RIFF" and "data" chunks always have their sizes set to 0xFFFFFFFF for RF64. */ - int ds64BodyPos = 12 + 8; - - /* The "RIFF" chunk size. */ - if (pWav->onSeek(pWav->pUserData, ds64BodyPos + 0, drwav_seek_origin_start)) { - drwav_uint64 riffChunkSize = drwav__riff_chunk_size_rf64(pWav->dataChunkDataSize, pWav->pMetadata, pWav->metadataCount); - drwav__write_u64ne_to_le(pWav, riffChunkSize); - } - - /* The "data" chunk size. */ - if (pWav->onSeek(pWav->pUserData, ds64BodyPos + 8, drwav_seek_origin_start)) { - drwav_uint64 dataChunkSize = drwav__data_chunk_size_rf64(pWav->dataChunkDataSize); - drwav__write_u64ne_to_le(pWav, dataChunkSize); - } - } - } - - /* Validation for sequential mode. */ - if (pWav->isSequentialWrite) { - if (pWav->dataChunkDataSize != pWav->dataChunkDataSizeTargetWrite) { - result = DRWAV_INVALID_FILE; - } - } - } - else { - if (pWav->pMetadata != NULL) { - pWav->allocationCallbacks.onFree(pWav->pMetadata, pWav->allocationCallbacks.pUserData); - } - } - -#ifndef DR_WAV_NO_STDIO - /* - If we opened the file with drwav_open_file() we will want to close the file handle. We can know whether or not drwav_open_file() - was used by looking at the onRead and onSeek callbacks. - */ - if (pWav->onRead == drwav__on_read_stdio || pWav->onWrite == drwav__on_write_stdio) { - fclose((FILE*)pWav->pUserData); - } -#endif - - return result; -} - - - -DRWAV_API size_t drwav_read_raw(drwav* pWav, size_t bytesToRead, void* pBufferOut) -{ - size_t bytesRead; - drwav_uint32 bytesPerFrame; - - if (pWav == NULL || bytesToRead == 0) { - return 0; /* Invalid args. */ - } - - if (bytesToRead > pWav->bytesRemaining) { - bytesToRead = (size_t)pWav->bytesRemaining; - } - - if (bytesToRead == 0) { - return 0; /* At end. */ - } - - bytesPerFrame = drwav_get_bytes_per_pcm_frame(pWav); - if (bytesPerFrame == 0) { - return 0; /* Could not determine the bytes per frame. */ - } - - if (pBufferOut != NULL) { - bytesRead = pWav->onRead(pWav->pUserData, pBufferOut, bytesToRead); - } - else { - /* We need to seek. If we fail, we need to read-and-discard to make sure we get a good byte count. */ - bytesRead = 0; - while (bytesRead < bytesToRead) { - size_t bytesToSeek = (bytesToRead - bytesRead); - if (bytesToSeek > 0x7FFFFFFF) { - bytesToSeek = 0x7FFFFFFF; - } - - if (pWav->onSeek(pWav->pUserData, (int)bytesToSeek, drwav_seek_origin_current) == DRWAV_FALSE) { - break; - } - - bytesRead += bytesToSeek; - } - - /* When we get here we may need to read-and-discard some data. */ - while (bytesRead < bytesToRead) { - drwav_uint8 buffer[4096]; - size_t bytesSeeked; - size_t bytesToSeek = (bytesToRead - bytesRead); - if (bytesToSeek > sizeof(buffer)) { - bytesToSeek = sizeof(buffer); - } - - bytesSeeked = pWav->onRead(pWav->pUserData, buffer, bytesToSeek); - bytesRead += bytesSeeked; - - if (bytesSeeked < bytesToSeek) { - break; /* Reached the end. */ - } - } - } - - pWav->readCursorInPCMFrames += bytesRead / bytesPerFrame; - - pWav->bytesRemaining -= bytesRead; - return bytesRead; -} - - - -DRWAV_API drwav_uint64 drwav_read_pcm_frames_le(drwav* pWav, drwav_uint64 framesToRead, void* pBufferOut) -{ - drwav_uint32 bytesPerFrame; - drwav_uint64 bytesToRead; /* Intentionally uint64 instead of size_t so we can do a check that we're not reading too much on 32-bit builds. */ - - if (pWav == NULL || framesToRead == 0) { - return 0; - } - - /* Cannot use this function for compressed formats. */ - if (drwav__is_compressed_format_tag(pWav->translatedFormatTag)) { - return 0; - } - - bytesPerFrame = drwav_get_bytes_per_pcm_frame(pWav); - if (bytesPerFrame == 0) { - return 0; - } - - /* Don't try to read more samples than can potentially fit in the output buffer. */ - bytesToRead = framesToRead * bytesPerFrame; - if (bytesToRead > DRWAV_SIZE_MAX) { - bytesToRead = (DRWAV_SIZE_MAX / bytesPerFrame) * bytesPerFrame; /* Round the number of bytes to read to a clean frame boundary. */ - } - - /* - Doing an explicit check here just to make it clear that we don't want to be attempt to read anything if there's no bytes to read. There - *could* be a time where it evaluates to 0 due to overflowing. - */ - if (bytesToRead == 0) { - return 0; - } - - return drwav_read_raw(pWav, (size_t)bytesToRead, pBufferOut) / bytesPerFrame; -} - -DRWAV_API drwav_uint64 drwav_read_pcm_frames_be(drwav* pWav, drwav_uint64 framesToRead, void* pBufferOut) -{ - drwav_uint64 framesRead = drwav_read_pcm_frames_le(pWav, framesToRead, pBufferOut); - - if (pBufferOut != NULL) { - drwav_uint32 bytesPerFrame = drwav_get_bytes_per_pcm_frame(pWav); - if (bytesPerFrame == 0) { - return 0; /* Could not get the bytes per frame which means bytes per sample cannot be determined and we don't know how to byte swap. */ - } - - drwav__bswap_samples(pBufferOut, framesRead * pWav->channels, bytesPerFrame / pWav->channels, pWav->translatedFormatTag); - } - - return framesRead; -} - -DRWAV_API drwav_uint64 drwav_read_pcm_frames(drwav* pWav, drwav_uint64 framesToRead, void* pBufferOut) -{ - if (drwav__is_little_endian()) { - return drwav_read_pcm_frames_le(pWav, framesToRead, pBufferOut); - } - else { - return drwav_read_pcm_frames_be(pWav, framesToRead, pBufferOut); - } -} - - - -DRWAV_PRIVATE drwav_bool32 drwav_seek_to_first_pcm_frame(drwav* pWav) -{ - if (pWav->onWrite != NULL) { - return DRWAV_FALSE; /* No seeking in write mode. */ - } - - if (!pWav->onSeek(pWav->pUserData, (int)pWav->dataChunkDataPos, drwav_seek_origin_start)) { - return DRWAV_FALSE; - } - - if (drwav__is_compressed_format_tag(pWav->translatedFormatTag)) { - /* Cached data needs to be cleared for compressed formats. */ - if (pWav->translatedFormatTag == DR_WAVE_FORMAT_ADPCM) { - DRWAV_ZERO_OBJECT(&pWav->msadpcm); - } - else if (pWav->translatedFormatTag == DR_WAVE_FORMAT_DVI_ADPCM) { - DRWAV_ZERO_OBJECT(&pWav->ima); - } - else { - DRWAV_ASSERT(DRWAV_FALSE); /* If this assertion is triggered it means I've implemented a new compressed format but forgot to add a branch for it here. */ - } - } - - pWav->readCursorInPCMFrames = 0; - pWav->bytesRemaining = pWav->dataChunkDataSize; - - return DRWAV_TRUE; -} - -DRWAV_API drwav_bool32 drwav_seek_to_pcm_frame(drwav* pWav, drwav_uint64 targetFrameIndex) -{ - /* Seeking should be compatible with wave files > 2GB. */ - - if (pWav == NULL || pWav->onSeek == NULL) { - return DRWAV_FALSE; - } - - /* No seeking in write mode. */ - if (pWav->onWrite != NULL) { - return DRWAV_FALSE; - } - - /* If there are no samples, just return DRWAV_TRUE without doing anything. */ - if (pWav->totalPCMFrameCount == 0) { - return DRWAV_TRUE; - } - - /* Make sure the sample is clamped. */ - if (targetFrameIndex > pWav->totalPCMFrameCount) { - targetFrameIndex = pWav->totalPCMFrameCount; - } - - /* - For compressed formats we just use a slow generic seek. If we are seeking forward we just seek forward. If we are going backwards we need - to seek back to the start. - */ - if (drwav__is_compressed_format_tag(pWav->translatedFormatTag)) { - /* TODO: This can be optimized. */ - - /* - If we're seeking forward it's simple - just keep reading samples until we hit the sample we're requesting. If we're seeking backwards, - we first need to seek back to the start and then just do the same thing as a forward seek. - */ - if (targetFrameIndex < pWav->readCursorInPCMFrames) { - if (!drwav_seek_to_first_pcm_frame(pWav)) { - return DRWAV_FALSE; - } - } - - if (targetFrameIndex > pWav->readCursorInPCMFrames) { - drwav_uint64 offsetInFrames = targetFrameIndex - pWav->readCursorInPCMFrames; - - drwav_int16 devnull[2048]; - while (offsetInFrames > 0) { - drwav_uint64 framesRead = 0; - drwav_uint64 framesToRead = offsetInFrames; - if (framesToRead > drwav_countof(devnull) / pWav->channels) { - framesToRead = drwav_countof(devnull) / pWav->channels; - } - - if (pWav->translatedFormatTag == DR_WAVE_FORMAT_ADPCM) { - framesRead = drwav_read_pcm_frames_s16__msadpcm(pWav, framesToRead, devnull); - } - else if (pWav->translatedFormatTag == DR_WAVE_FORMAT_DVI_ADPCM) { - framesRead = drwav_read_pcm_frames_s16__ima(pWav, framesToRead, devnull); - } - else { - DRWAV_ASSERT(DRWAV_FALSE); /* If this assertion is triggered it means I've implemented a new compressed format but forgot to add a branch for it here. */ - } - - if (framesRead != framesToRead) { - return DRWAV_FALSE; - } - - offsetInFrames -= framesRead; - } - } - } - else { - drwav_uint64 totalSizeInBytes; - drwav_uint64 currentBytePos; - drwav_uint64 targetBytePos; - drwav_uint64 offset; - drwav_uint32 bytesPerFrame; - - bytesPerFrame = drwav_get_bytes_per_pcm_frame(pWav); - if (bytesPerFrame == 0) { - return DRWAV_FALSE; /* Not able to calculate offset. */ - } - - totalSizeInBytes = pWav->totalPCMFrameCount * bytesPerFrame; - DRWAV_ASSERT(totalSizeInBytes >= pWav->bytesRemaining); - - currentBytePos = totalSizeInBytes - pWav->bytesRemaining; - targetBytePos = targetFrameIndex * bytesPerFrame; - - if (currentBytePos < targetBytePos) { - /* Offset forwards. */ - offset = (targetBytePos - currentBytePos); - } - else { - /* Offset backwards. */ - if (!drwav_seek_to_first_pcm_frame(pWav)) { - return DRWAV_FALSE; - } - offset = targetBytePos; - } - - while (offset > 0) { - int offset32 = ((offset > INT_MAX) ? INT_MAX : (int)offset); - if (!pWav->onSeek(pWav->pUserData, offset32, drwav_seek_origin_current)) { - return DRWAV_FALSE; - } - - pWav->readCursorInPCMFrames += offset32 / bytesPerFrame; - pWav->bytesRemaining -= offset32; - offset -= offset32; - } - } - - return DRWAV_TRUE; -} - -DRWAV_API drwav_result drwav_get_cursor_in_pcm_frames(drwav* pWav, drwav_uint64* pCursor) -{ - if (pCursor == NULL) { - return DRWAV_INVALID_ARGS; - } - - *pCursor = 0; /* Safety. */ - - if (pWav == NULL) { - return DRWAV_INVALID_ARGS; - } - - *pCursor = pWav->readCursorInPCMFrames; - - return DRWAV_SUCCESS; -} - -DRWAV_API drwav_result drwav_get_length_in_pcm_frames(drwav* pWav, drwav_uint64* pLength) -{ - if (pLength == NULL) { - return DRWAV_INVALID_ARGS; - } - - *pLength = 0; /* Safety. */ - - if (pWav == NULL) { - return DRWAV_INVALID_ARGS; - } - - *pLength = pWav->totalPCMFrameCount; - - return DRWAV_SUCCESS; -} - - -DRWAV_API size_t drwav_write_raw(drwav* pWav, size_t bytesToWrite, const void* pData) -{ - size_t bytesWritten; - - if (pWav == NULL || bytesToWrite == 0 || pData == NULL) { - return 0; - } - - bytesWritten = pWav->onWrite(pWav->pUserData, pData, bytesToWrite); - pWav->dataChunkDataSize += bytesWritten; - - return bytesWritten; -} - -DRWAV_API drwav_uint64 drwav_write_pcm_frames_le(drwav* pWav, drwav_uint64 framesToWrite, const void* pData) -{ - drwav_uint64 bytesToWrite; - drwav_uint64 bytesWritten; - const drwav_uint8* pRunningData; - - if (pWav == NULL || framesToWrite == 0 || pData == NULL) { - return 0; - } - - bytesToWrite = ((framesToWrite * pWav->channels * pWav->bitsPerSample) / 8); - if (bytesToWrite > DRWAV_SIZE_MAX) { - return 0; - } - - bytesWritten = 0; - pRunningData = (const drwav_uint8*)pData; - - while (bytesToWrite > 0) { - size_t bytesJustWritten; - drwav_uint64 bytesToWriteThisIteration; - - bytesToWriteThisIteration = bytesToWrite; - DRWAV_ASSERT(bytesToWriteThisIteration <= DRWAV_SIZE_MAX); /* <-- This is checked above. */ - - bytesJustWritten = drwav_write_raw(pWav, (size_t)bytesToWriteThisIteration, pRunningData); - if (bytesJustWritten == 0) { - break; - } - - bytesToWrite -= bytesJustWritten; - bytesWritten += bytesJustWritten; - pRunningData += bytesJustWritten; - } - - return (bytesWritten * 8) / pWav->bitsPerSample / pWav->channels; -} - -DRWAV_API drwav_uint64 drwav_write_pcm_frames_be(drwav* pWav, drwav_uint64 framesToWrite, const void* pData) -{ - drwav_uint64 bytesToWrite; - drwav_uint64 bytesWritten; - drwav_uint32 bytesPerSample; - const drwav_uint8* pRunningData; - - if (pWav == NULL || framesToWrite == 0 || pData == NULL) { - return 0; - } - - bytesToWrite = ((framesToWrite * pWav->channels * pWav->bitsPerSample) / 8); - if (bytesToWrite > DRWAV_SIZE_MAX) { - return 0; - } - - bytesWritten = 0; - pRunningData = (const drwav_uint8*)pData; - - bytesPerSample = drwav_get_bytes_per_pcm_frame(pWav) / pWav->channels; - if (bytesPerSample == 0) { - return 0; /* Cannot determine bytes per sample, or bytes per sample is less than one byte. */ - } - - while (bytesToWrite > 0) { - drwav_uint8 temp[4096]; - drwav_uint32 sampleCount; - size_t bytesJustWritten; - drwav_uint64 bytesToWriteThisIteration; - - bytesToWriteThisIteration = bytesToWrite; - DRWAV_ASSERT(bytesToWriteThisIteration <= DRWAV_SIZE_MAX); /* <-- This is checked above. */ - - /* - WAV files are always little-endian. We need to byte swap on big-endian architectures. Since our input buffer is read-only we need - to use an intermediary buffer for the conversion. - */ - sampleCount = sizeof(temp) / bytesPerSample; - - if (bytesToWriteThisIteration > ((drwav_uint64)sampleCount) * bytesPerSample) { - bytesToWriteThisIteration = ((drwav_uint64)sampleCount) * bytesPerSample; - } - - DRWAV_COPY_MEMORY(temp, pRunningData, (size_t)bytesToWriteThisIteration); - drwav__bswap_samples(temp, sampleCount, bytesPerSample, pWav->translatedFormatTag); - - bytesJustWritten = drwav_write_raw(pWav, (size_t)bytesToWriteThisIteration, temp); - if (bytesJustWritten == 0) { - break; - } - - bytesToWrite -= bytesJustWritten; - bytesWritten += bytesJustWritten; - pRunningData += bytesJustWritten; - } - - return (bytesWritten * 8) / pWav->bitsPerSample / pWav->channels; -} - -DRWAV_API drwav_uint64 drwav_write_pcm_frames(drwav* pWav, drwav_uint64 framesToWrite, const void* pData) -{ - if (drwav__is_little_endian()) { - return drwav_write_pcm_frames_le(pWav, framesToWrite, pData); - } - else { - return drwav_write_pcm_frames_be(pWav, framesToWrite, pData); - } -} - - -DRWAV_PRIVATE drwav_uint64 drwav_read_pcm_frames_s16__msadpcm(drwav* pWav, drwav_uint64 framesToRead, drwav_int16* pBufferOut) -{ - drwav_uint64 totalFramesRead = 0; - - DRWAV_ASSERT(pWav != NULL); - DRWAV_ASSERT(framesToRead > 0); - - /* TODO: Lots of room for optimization here. */ - - while (pWav->readCursorInPCMFrames < pWav->totalPCMFrameCount) { - DRWAV_ASSERT(framesToRead > 0); /* This loop iteration will never get hit with framesToRead == 0 because it's asserted at the top, and we check for 0 inside the loop just below. */ - - /* If there are no cached frames we need to load a new block. */ - if (pWav->msadpcm.cachedFrameCount == 0 && pWav->msadpcm.bytesRemainingInBlock == 0) { - if (pWav->channels == 1) { - /* Mono. */ - drwav_uint8 header[7]; - if (pWav->onRead(pWav->pUserData, header, sizeof(header)) != sizeof(header)) { - return totalFramesRead; - } - pWav->msadpcm.bytesRemainingInBlock = pWav->fmt.blockAlign - sizeof(header); - - pWav->msadpcm.predictor[0] = header[0]; - pWav->msadpcm.delta[0] = drwav_bytes_to_s16(header + 1); - pWav->msadpcm.prevFrames[0][1] = (drwav_int32)drwav_bytes_to_s16(header + 3); - pWav->msadpcm.prevFrames[0][0] = (drwav_int32)drwav_bytes_to_s16(header + 5); - pWav->msadpcm.cachedFrames[2] = pWav->msadpcm.prevFrames[0][0]; - pWav->msadpcm.cachedFrames[3] = pWav->msadpcm.prevFrames[0][1]; - pWav->msadpcm.cachedFrameCount = 2; - } - else { - /* Stereo. */ - drwav_uint8 header[14]; - if (pWav->onRead(pWav->pUserData, header, sizeof(header)) != sizeof(header)) { - return totalFramesRead; - } - pWav->msadpcm.bytesRemainingInBlock = pWav->fmt.blockAlign - sizeof(header); - - pWav->msadpcm.predictor[0] = header[0]; - pWav->msadpcm.predictor[1] = header[1]; - pWav->msadpcm.delta[0] = drwav_bytes_to_s16(header + 2); - pWav->msadpcm.delta[1] = drwav_bytes_to_s16(header + 4); - pWav->msadpcm.prevFrames[0][1] = (drwav_int32)drwav_bytes_to_s16(header + 6); - pWav->msadpcm.prevFrames[1][1] = (drwav_int32)drwav_bytes_to_s16(header + 8); - pWav->msadpcm.prevFrames[0][0] = (drwav_int32)drwav_bytes_to_s16(header + 10); - pWav->msadpcm.prevFrames[1][0] = (drwav_int32)drwav_bytes_to_s16(header + 12); - - pWav->msadpcm.cachedFrames[0] = pWav->msadpcm.prevFrames[0][0]; - pWav->msadpcm.cachedFrames[1] = pWav->msadpcm.prevFrames[1][0]; - pWav->msadpcm.cachedFrames[2] = pWav->msadpcm.prevFrames[0][1]; - pWav->msadpcm.cachedFrames[3] = pWav->msadpcm.prevFrames[1][1]; - pWav->msadpcm.cachedFrameCount = 2; - } - } - - /* Output anything that's cached. */ - while (framesToRead > 0 && pWav->msadpcm.cachedFrameCount > 0 && pWav->readCursorInPCMFrames < pWav->totalPCMFrameCount) { - if (pBufferOut != NULL) { - drwav_uint32 iSample = 0; - for (iSample = 0; iSample < pWav->channels; iSample += 1) { - pBufferOut[iSample] = (drwav_int16)pWav->msadpcm.cachedFrames[(drwav_countof(pWav->msadpcm.cachedFrames) - (pWav->msadpcm.cachedFrameCount * pWav->channels)) + iSample]; - } - - pBufferOut += pWav->channels; - } - - framesToRead -= 1; - totalFramesRead += 1; - pWav->readCursorInPCMFrames += 1; - pWav->msadpcm.cachedFrameCount -= 1; - } - - if (framesToRead == 0) { - break; - } - - - /* - If there's nothing left in the cache, just go ahead and load more. If there's nothing left to load in the current block we just continue to the next - loop iteration which will trigger the loading of a new block. - */ - if (pWav->msadpcm.cachedFrameCount == 0) { - if (pWav->msadpcm.bytesRemainingInBlock == 0) { - continue; - } - else { - static drwav_int32 adaptationTable[] = { - 230, 230, 230, 230, 307, 409, 512, 614, - 768, 614, 512, 409, 307, 230, 230, 230 - }; - static drwav_int32 coeff1Table[] = { 256, 512, 0, 192, 240, 460, 392 }; - static drwav_int32 coeff2Table[] = { 0, -256, 0, 64, 0, -208, -232 }; - - drwav_uint8 nibbles; - drwav_int32 nibble0; - drwav_int32 nibble1; - - if (pWav->onRead(pWav->pUserData, &nibbles, 1) != 1) { - return totalFramesRead; - } - pWav->msadpcm.bytesRemainingInBlock -= 1; - - /* TODO: Optimize away these if statements. */ - nibble0 = ((nibbles & 0xF0) >> 4); if ((nibbles & 0x80)) { nibble0 |= 0xFFFFFFF0UL; } - nibble1 = ((nibbles & 0x0F) >> 0); if ((nibbles & 0x08)) { nibble1 |= 0xFFFFFFF0UL; } - - if (pWav->channels == 1) { - /* Mono. */ - drwav_int32 newSample0; - drwav_int32 newSample1; - - newSample0 = ((pWav->msadpcm.prevFrames[0][1] * coeff1Table[pWav->msadpcm.predictor[0]]) + (pWav->msadpcm.prevFrames[0][0] * coeff2Table[pWav->msadpcm.predictor[0]])) >> 8; - newSample0 += nibble0 * pWav->msadpcm.delta[0]; - newSample0 = drwav_clamp(newSample0, -32768, 32767); - - pWav->msadpcm.delta[0] = (adaptationTable[((nibbles & 0xF0) >> 4)] * pWav->msadpcm.delta[0]) >> 8; - if (pWav->msadpcm.delta[0] < 16) { - pWav->msadpcm.delta[0] = 16; - } - - pWav->msadpcm.prevFrames[0][0] = pWav->msadpcm.prevFrames[0][1]; - pWav->msadpcm.prevFrames[0][1] = newSample0; - - - newSample1 = ((pWav->msadpcm.prevFrames[0][1] * coeff1Table[pWav->msadpcm.predictor[0]]) + (pWav->msadpcm.prevFrames[0][0] * coeff2Table[pWav->msadpcm.predictor[0]])) >> 8; - newSample1 += nibble1 * pWav->msadpcm.delta[0]; - newSample1 = drwav_clamp(newSample1, -32768, 32767); - - pWav->msadpcm.delta[0] = (adaptationTable[((nibbles & 0x0F) >> 0)] * pWav->msadpcm.delta[0]) >> 8; - if (pWav->msadpcm.delta[0] < 16) { - pWav->msadpcm.delta[0] = 16; - } - - pWav->msadpcm.prevFrames[0][0] = pWav->msadpcm.prevFrames[0][1]; - pWav->msadpcm.prevFrames[0][1] = newSample1; - - - pWav->msadpcm.cachedFrames[2] = newSample0; - pWav->msadpcm.cachedFrames[3] = newSample1; - pWav->msadpcm.cachedFrameCount = 2; - } - else { - /* Stereo. */ - drwav_int32 newSample0; - drwav_int32 newSample1; - - /* Left. */ - newSample0 = ((pWav->msadpcm.prevFrames[0][1] * coeff1Table[pWav->msadpcm.predictor[0]]) + (pWav->msadpcm.prevFrames[0][0] * coeff2Table[pWav->msadpcm.predictor[0]])) >> 8; - newSample0 += nibble0 * pWav->msadpcm.delta[0]; - newSample0 = drwav_clamp(newSample0, -32768, 32767); - - pWav->msadpcm.delta[0] = (adaptationTable[((nibbles & 0xF0) >> 4)] * pWav->msadpcm.delta[0]) >> 8; - if (pWav->msadpcm.delta[0] < 16) { - pWav->msadpcm.delta[0] = 16; - } - - pWav->msadpcm.prevFrames[0][0] = pWav->msadpcm.prevFrames[0][1]; - pWav->msadpcm.prevFrames[0][1] = newSample0; - - - /* Right. */ - newSample1 = ((pWav->msadpcm.prevFrames[1][1] * coeff1Table[pWav->msadpcm.predictor[1]]) + (pWav->msadpcm.prevFrames[1][0] * coeff2Table[pWav->msadpcm.predictor[1]])) >> 8; - newSample1 += nibble1 * pWav->msadpcm.delta[1]; - newSample1 = drwav_clamp(newSample1, -32768, 32767); - - pWav->msadpcm.delta[1] = (adaptationTable[((nibbles & 0x0F) >> 0)] * pWav->msadpcm.delta[1]) >> 8; - if (pWav->msadpcm.delta[1] < 16) { - pWav->msadpcm.delta[1] = 16; - } - - pWav->msadpcm.prevFrames[1][0] = pWav->msadpcm.prevFrames[1][1]; - pWav->msadpcm.prevFrames[1][1] = newSample1; - - pWav->msadpcm.cachedFrames[2] = newSample0; - pWav->msadpcm.cachedFrames[3] = newSample1; - pWav->msadpcm.cachedFrameCount = 1; - } - } - } - } - - return totalFramesRead; -} - - -DRWAV_PRIVATE drwav_uint64 drwav_read_pcm_frames_s16__ima(drwav* pWav, drwav_uint64 framesToRead, drwav_int16* pBufferOut) -{ - drwav_uint64 totalFramesRead = 0; - drwav_uint32 iChannel; - - static drwav_int32 indexTable[16] = { - -1, -1, -1, -1, 2, 4, 6, 8, - -1, -1, -1, -1, 2, 4, 6, 8 - }; - - static drwav_int32 stepTable[89] = { - 7, 8, 9, 10, 11, 12, 13, 14, 16, 17, - 19, 21, 23, 25, 28, 31, 34, 37, 41, 45, - 50, 55, 60, 66, 73, 80, 88, 97, 107, 118, - 130, 143, 157, 173, 190, 209, 230, 253, 279, 307, - 337, 371, 408, 449, 494, 544, 598, 658, 724, 796, - 876, 963, 1060, 1166, 1282, 1411, 1552, 1707, 1878, 2066, - 2272, 2499, 2749, 3024, 3327, 3660, 4026, 4428, 4871, 5358, - 5894, 6484, 7132, 7845, 8630, 9493, 10442, 11487, 12635, 13899, - 15289, 16818, 18500, 20350, 22385, 24623, 27086, 29794, 32767 - }; - - DRWAV_ASSERT(pWav != NULL); - DRWAV_ASSERT(framesToRead > 0); - - /* TODO: Lots of room for optimization here. */ - - while (pWav->readCursorInPCMFrames < pWav->totalPCMFrameCount) { - DRWAV_ASSERT(framesToRead > 0); /* This loop iteration will never get hit with framesToRead == 0 because it's asserted at the top, and we check for 0 inside the loop just below. */ - - /* If there are no cached samples we need to load a new block. */ - if (pWav->ima.cachedFrameCount == 0 && pWav->ima.bytesRemainingInBlock == 0) { - if (pWav->channels == 1) { - /* Mono. */ - drwav_uint8 header[4]; - if (pWav->onRead(pWav->pUserData, header, sizeof(header)) != sizeof(header)) { - return totalFramesRead; - } - pWav->ima.bytesRemainingInBlock = pWav->fmt.blockAlign - sizeof(header); - - if (header[2] >= drwav_countof(stepTable)) { - pWav->onSeek(pWav->pUserData, pWav->ima.bytesRemainingInBlock, drwav_seek_origin_current); - pWav->ima.bytesRemainingInBlock = 0; - return totalFramesRead; /* Invalid data. */ - } - - pWav->ima.predictor[0] = drwav_bytes_to_s16(header + 0); - pWav->ima.stepIndex[0] = drwav_clamp(header[2], 0, (drwav_int32)drwav_countof(stepTable) - 1); /* Clamp not necessary because we checked above, but adding here to silence a static analysis warning. */ - pWav->ima.cachedFrames[drwav_countof(pWav->ima.cachedFrames) - 1] = pWav->ima.predictor[0]; - pWav->ima.cachedFrameCount = 1; - } - else { - /* Stereo. */ - drwav_uint8 header[8]; - if (pWav->onRead(pWav->pUserData, header, sizeof(header)) != sizeof(header)) { - return totalFramesRead; - } - pWav->ima.bytesRemainingInBlock = pWav->fmt.blockAlign - sizeof(header); - - if (header[2] >= drwav_countof(stepTable) || header[6] >= drwav_countof(stepTable)) { - pWav->onSeek(pWav->pUserData, pWav->ima.bytesRemainingInBlock, drwav_seek_origin_current); - pWav->ima.bytesRemainingInBlock = 0; - return totalFramesRead; /* Invalid data. */ - } - - pWav->ima.predictor[0] = drwav_bytes_to_s16(header + 0); - pWav->ima.stepIndex[0] = drwav_clamp(header[2], 0, (drwav_int32)drwav_countof(stepTable) - 1); /* Clamp not necessary because we checked above, but adding here to silence a static analysis warning. */ - pWav->ima.predictor[1] = drwav_bytes_to_s16(header + 4); - pWav->ima.stepIndex[1] = drwav_clamp(header[6], 0, (drwav_int32)drwav_countof(stepTable) - 1); /* Clamp not necessary because we checked above, but adding here to silence a static analysis warning. */ - - pWav->ima.cachedFrames[drwav_countof(pWav->ima.cachedFrames) - 2] = pWav->ima.predictor[0]; - pWav->ima.cachedFrames[drwav_countof(pWav->ima.cachedFrames) - 1] = pWav->ima.predictor[1]; - pWav->ima.cachedFrameCount = 1; - } - } - - /* Output anything that's cached. */ - while (framesToRead > 0 && pWav->ima.cachedFrameCount > 0 && pWav->readCursorInPCMFrames < pWav->totalPCMFrameCount) { - if (pBufferOut != NULL) { - drwav_uint32 iSample; - for (iSample = 0; iSample < pWav->channels; iSample += 1) { - pBufferOut[iSample] = (drwav_int16)pWav->ima.cachedFrames[(drwav_countof(pWav->ima.cachedFrames) - (pWav->ima.cachedFrameCount * pWav->channels)) + iSample]; - } - pBufferOut += pWav->channels; - } - - framesToRead -= 1; - totalFramesRead += 1; - pWav->readCursorInPCMFrames += 1; - pWav->ima.cachedFrameCount -= 1; - } - - if (framesToRead == 0) { - break; - } - - /* - If there's nothing left in the cache, just go ahead and load more. If there's nothing left to load in the current block we just continue to the next - loop iteration which will trigger the loading of a new block. - */ - if (pWav->ima.cachedFrameCount == 0) { - if (pWav->ima.bytesRemainingInBlock == 0) { - continue; - } - else { - /* - From what I can tell with stereo streams, it looks like every 4 bytes (8 samples) is for one channel. So it goes 4 bytes for the - left channel, 4 bytes for the right channel. - */ - pWav->ima.cachedFrameCount = 8; - for (iChannel = 0; iChannel < pWav->channels; ++iChannel) { - drwav_uint32 iByte; - drwav_uint8 nibbles[4]; - if (pWav->onRead(pWav->pUserData, &nibbles, 4) != 4) { - pWav->ima.cachedFrameCount = 0; - return totalFramesRead; - } - pWav->ima.bytesRemainingInBlock -= 4; - - for (iByte = 0; iByte < 4; ++iByte) { - drwav_uint8 nibble0 = ((nibbles[iByte] & 0x0F) >> 0); - drwav_uint8 nibble1 = ((nibbles[iByte] & 0xF0) >> 4); - - drwav_int32 step = stepTable[pWav->ima.stepIndex[iChannel]]; - drwav_int32 predictor = pWav->ima.predictor[iChannel]; - - drwav_int32 diff = step >> 3; - if (nibble0 & 1) diff += step >> 2; - if (nibble0 & 2) diff += step >> 1; - if (nibble0 & 4) diff += step; - if (nibble0 & 8) diff = -diff; - - predictor = drwav_clamp(predictor + diff, -32768, 32767); - pWav->ima.predictor[iChannel] = predictor; - pWav->ima.stepIndex[iChannel] = drwav_clamp(pWav->ima.stepIndex[iChannel] + indexTable[nibble0], 0, (drwav_int32)drwav_countof(stepTable) - 1); - pWav->ima.cachedFrames[(drwav_countof(pWav->ima.cachedFrames) - (pWav->ima.cachedFrameCount * pWav->channels)) + (iByte * 2 + 0) * pWav->channels + iChannel] = predictor; - - - step = stepTable[pWav->ima.stepIndex[iChannel]]; - predictor = pWav->ima.predictor[iChannel]; - - diff = step >> 3; - if (nibble1 & 1) diff += step >> 2; - if (nibble1 & 2) diff += step >> 1; - if (nibble1 & 4) diff += step; - if (nibble1 & 8) diff = -diff; - - predictor = drwav_clamp(predictor + diff, -32768, 32767); - pWav->ima.predictor[iChannel] = predictor; - pWav->ima.stepIndex[iChannel] = drwav_clamp(pWav->ima.stepIndex[iChannel] + indexTable[nibble1], 0, (drwav_int32)drwav_countof(stepTable) - 1); - pWav->ima.cachedFrames[(drwav_countof(pWav->ima.cachedFrames) - (pWav->ima.cachedFrameCount * pWav->channels)) + (iByte * 2 + 1) * pWav->channels + iChannel] = predictor; - } - } - } - } - } - - return totalFramesRead; -} - - -#ifndef DR_WAV_NO_CONVERSION_API -static unsigned short g_drwavAlawTable[256] = { - 0xEA80, 0xEB80, 0xE880, 0xE980, 0xEE80, 0xEF80, 0xEC80, 0xED80, 0xE280, 0xE380, 0xE080, 0xE180, 0xE680, 0xE780, 0xE480, 0xE580, - 0xF540, 0xF5C0, 0xF440, 0xF4C0, 0xF740, 0xF7C0, 0xF640, 0xF6C0, 0xF140, 0xF1C0, 0xF040, 0xF0C0, 0xF340, 0xF3C0, 0xF240, 0xF2C0, - 0xAA00, 0xAE00, 0xA200, 0xA600, 0xBA00, 0xBE00, 0xB200, 0xB600, 0x8A00, 0x8E00, 0x8200, 0x8600, 0x9A00, 0x9E00, 0x9200, 0x9600, - 0xD500, 0xD700, 0xD100, 0xD300, 0xDD00, 0xDF00, 0xD900, 0xDB00, 0xC500, 0xC700, 0xC100, 0xC300, 0xCD00, 0xCF00, 0xC900, 0xCB00, - 0xFEA8, 0xFEB8, 0xFE88, 0xFE98, 0xFEE8, 0xFEF8, 0xFEC8, 0xFED8, 0xFE28, 0xFE38, 0xFE08, 0xFE18, 0xFE68, 0xFE78, 0xFE48, 0xFE58, - 0xFFA8, 0xFFB8, 0xFF88, 0xFF98, 0xFFE8, 0xFFF8, 0xFFC8, 0xFFD8, 0xFF28, 0xFF38, 0xFF08, 0xFF18, 0xFF68, 0xFF78, 0xFF48, 0xFF58, - 0xFAA0, 0xFAE0, 0xFA20, 0xFA60, 0xFBA0, 0xFBE0, 0xFB20, 0xFB60, 0xF8A0, 0xF8E0, 0xF820, 0xF860, 0xF9A0, 0xF9E0, 0xF920, 0xF960, - 0xFD50, 0xFD70, 0xFD10, 0xFD30, 0xFDD0, 0xFDF0, 0xFD90, 0xFDB0, 0xFC50, 0xFC70, 0xFC10, 0xFC30, 0xFCD0, 0xFCF0, 0xFC90, 0xFCB0, - 0x1580, 0x1480, 0x1780, 0x1680, 0x1180, 0x1080, 0x1380, 0x1280, 0x1D80, 0x1C80, 0x1F80, 0x1E80, 0x1980, 0x1880, 0x1B80, 0x1A80, - 0x0AC0, 0x0A40, 0x0BC0, 0x0B40, 0x08C0, 0x0840, 0x09C0, 0x0940, 0x0EC0, 0x0E40, 0x0FC0, 0x0F40, 0x0CC0, 0x0C40, 0x0DC0, 0x0D40, - 0x5600, 0x5200, 0x5E00, 0x5A00, 0x4600, 0x4200, 0x4E00, 0x4A00, 0x7600, 0x7200, 0x7E00, 0x7A00, 0x6600, 0x6200, 0x6E00, 0x6A00, - 0x2B00, 0x2900, 0x2F00, 0x2D00, 0x2300, 0x2100, 0x2700, 0x2500, 0x3B00, 0x3900, 0x3F00, 0x3D00, 0x3300, 0x3100, 0x3700, 0x3500, - 0x0158, 0x0148, 0x0178, 0x0168, 0x0118, 0x0108, 0x0138, 0x0128, 0x01D8, 0x01C8, 0x01F8, 0x01E8, 0x0198, 0x0188, 0x01B8, 0x01A8, - 0x0058, 0x0048, 0x0078, 0x0068, 0x0018, 0x0008, 0x0038, 0x0028, 0x00D8, 0x00C8, 0x00F8, 0x00E8, 0x0098, 0x0088, 0x00B8, 0x00A8, - 0x0560, 0x0520, 0x05E0, 0x05A0, 0x0460, 0x0420, 0x04E0, 0x04A0, 0x0760, 0x0720, 0x07E0, 0x07A0, 0x0660, 0x0620, 0x06E0, 0x06A0, - 0x02B0, 0x0290, 0x02F0, 0x02D0, 0x0230, 0x0210, 0x0270, 0x0250, 0x03B0, 0x0390, 0x03F0, 0x03D0, 0x0330, 0x0310, 0x0370, 0x0350 -}; - -static unsigned short g_drwavMulawTable[256] = { - 0x8284, 0x8684, 0x8A84, 0x8E84, 0x9284, 0x9684, 0x9A84, 0x9E84, 0xA284, 0xA684, 0xAA84, 0xAE84, 0xB284, 0xB684, 0xBA84, 0xBE84, - 0xC184, 0xC384, 0xC584, 0xC784, 0xC984, 0xCB84, 0xCD84, 0xCF84, 0xD184, 0xD384, 0xD584, 0xD784, 0xD984, 0xDB84, 0xDD84, 0xDF84, - 0xE104, 0xE204, 0xE304, 0xE404, 0xE504, 0xE604, 0xE704, 0xE804, 0xE904, 0xEA04, 0xEB04, 0xEC04, 0xED04, 0xEE04, 0xEF04, 0xF004, - 0xF0C4, 0xF144, 0xF1C4, 0xF244, 0xF2C4, 0xF344, 0xF3C4, 0xF444, 0xF4C4, 0xF544, 0xF5C4, 0xF644, 0xF6C4, 0xF744, 0xF7C4, 0xF844, - 0xF8A4, 0xF8E4, 0xF924, 0xF964, 0xF9A4, 0xF9E4, 0xFA24, 0xFA64, 0xFAA4, 0xFAE4, 0xFB24, 0xFB64, 0xFBA4, 0xFBE4, 0xFC24, 0xFC64, - 0xFC94, 0xFCB4, 0xFCD4, 0xFCF4, 0xFD14, 0xFD34, 0xFD54, 0xFD74, 0xFD94, 0xFDB4, 0xFDD4, 0xFDF4, 0xFE14, 0xFE34, 0xFE54, 0xFE74, - 0xFE8C, 0xFE9C, 0xFEAC, 0xFEBC, 0xFECC, 0xFEDC, 0xFEEC, 0xFEFC, 0xFF0C, 0xFF1C, 0xFF2C, 0xFF3C, 0xFF4C, 0xFF5C, 0xFF6C, 0xFF7C, - 0xFF88, 0xFF90, 0xFF98, 0xFFA0, 0xFFA8, 0xFFB0, 0xFFB8, 0xFFC0, 0xFFC8, 0xFFD0, 0xFFD8, 0xFFE0, 0xFFE8, 0xFFF0, 0xFFF8, 0x0000, - 0x7D7C, 0x797C, 0x757C, 0x717C, 0x6D7C, 0x697C, 0x657C, 0x617C, 0x5D7C, 0x597C, 0x557C, 0x517C, 0x4D7C, 0x497C, 0x457C, 0x417C, - 0x3E7C, 0x3C7C, 0x3A7C, 0x387C, 0x367C, 0x347C, 0x327C, 0x307C, 0x2E7C, 0x2C7C, 0x2A7C, 0x287C, 0x267C, 0x247C, 0x227C, 0x207C, - 0x1EFC, 0x1DFC, 0x1CFC, 0x1BFC, 0x1AFC, 0x19FC, 0x18FC, 0x17FC, 0x16FC, 0x15FC, 0x14FC, 0x13FC, 0x12FC, 0x11FC, 0x10FC, 0x0FFC, - 0x0F3C, 0x0EBC, 0x0E3C, 0x0DBC, 0x0D3C, 0x0CBC, 0x0C3C, 0x0BBC, 0x0B3C, 0x0ABC, 0x0A3C, 0x09BC, 0x093C, 0x08BC, 0x083C, 0x07BC, - 0x075C, 0x071C, 0x06DC, 0x069C, 0x065C, 0x061C, 0x05DC, 0x059C, 0x055C, 0x051C, 0x04DC, 0x049C, 0x045C, 0x041C, 0x03DC, 0x039C, - 0x036C, 0x034C, 0x032C, 0x030C, 0x02EC, 0x02CC, 0x02AC, 0x028C, 0x026C, 0x024C, 0x022C, 0x020C, 0x01EC, 0x01CC, 0x01AC, 0x018C, - 0x0174, 0x0164, 0x0154, 0x0144, 0x0134, 0x0124, 0x0114, 0x0104, 0x00F4, 0x00E4, 0x00D4, 0x00C4, 0x00B4, 0x00A4, 0x0094, 0x0084, - 0x0078, 0x0070, 0x0068, 0x0060, 0x0058, 0x0050, 0x0048, 0x0040, 0x0038, 0x0030, 0x0028, 0x0020, 0x0018, 0x0010, 0x0008, 0x0000 -}; - -static DRWAV_INLINE drwav_int16 drwav__alaw_to_s16(drwav_uint8 sampleIn) -{ - return (short)g_drwavAlawTable[sampleIn]; -} - -static DRWAV_INLINE drwav_int16 drwav__mulaw_to_s16(drwav_uint8 sampleIn) -{ - return (short)g_drwavMulawTable[sampleIn]; -} - - - -DRWAV_PRIVATE void drwav__pcm_to_s16(drwav_int16* pOut, const drwav_uint8* pIn, size_t totalSampleCount, unsigned int bytesPerSample) -{ - size_t i; - - /* Special case for 8-bit sample data because it's treated as unsigned. */ - if (bytesPerSample == 1) { - drwav_u8_to_s16(pOut, pIn, totalSampleCount); - return; - } - - - /* Slightly more optimal implementation for common formats. */ - if (bytesPerSample == 2) { - for (i = 0; i < totalSampleCount; ++i) { - *pOut++ = ((const drwav_int16*)pIn)[i]; - } - return; - } - if (bytesPerSample == 3) { - drwav_s24_to_s16(pOut, pIn, totalSampleCount); - return; - } - if (bytesPerSample == 4) { - drwav_s32_to_s16(pOut, (const drwav_int32*)pIn, totalSampleCount); - return; - } - - - /* Anything more than 64 bits per sample is not supported. */ - if (bytesPerSample > 8) { - DRWAV_ZERO_MEMORY(pOut, totalSampleCount * sizeof(*pOut)); - return; - } - - - /* Generic, slow converter. */ - for (i = 0; i < totalSampleCount; ++i) { - drwav_uint64 sample = 0; - unsigned int shift = (8 - bytesPerSample) * 8; - - unsigned int j; - for (j = 0; j < bytesPerSample; j += 1) { - DRWAV_ASSERT(j < 8); - sample |= (drwav_uint64)(pIn[j]) << shift; - shift += 8; - } - - pIn += j; - *pOut++ = (drwav_int16)((drwav_int64)sample >> 48); - } -} - -DRWAV_PRIVATE void drwav__ieee_to_s16(drwav_int16* pOut, const drwav_uint8* pIn, size_t totalSampleCount, unsigned int bytesPerSample) -{ - if (bytesPerSample == 4) { - drwav_f32_to_s16(pOut, (const float*)pIn, totalSampleCount); - return; - } - else if (bytesPerSample == 8) { - drwav_f64_to_s16(pOut, (const double*)pIn, totalSampleCount); - return; - } - else { - /* Only supporting 32- and 64-bit float. Output silence in all other cases. Contributions welcome for 16-bit float. */ - DRWAV_ZERO_MEMORY(pOut, totalSampleCount * sizeof(*pOut)); - return; - } -} - -DRWAV_PRIVATE drwav_uint64 drwav_read_pcm_frames_s16__pcm(drwav* pWav, drwav_uint64 framesToRead, drwav_int16* pBufferOut) -{ - drwav_uint64 totalFramesRead; - drwav_uint8 sampleData[4096] = { 0 }; - drwav_uint32 bytesPerFrame; - drwav_uint32 bytesPerSample; - drwav_uint64 samplesRead; - - /* Fast path. */ - if ((pWav->translatedFormatTag == DR_WAVE_FORMAT_PCM && pWav->bitsPerSample == 16) || pBufferOut == NULL) { - return drwav_read_pcm_frames(pWav, framesToRead, pBufferOut); - } - - bytesPerFrame = drwav_get_bytes_per_pcm_frame(pWav); - if (bytesPerFrame == 0) { - return 0; - } - - bytesPerSample = bytesPerFrame / pWav->channels; - if (bytesPerSample == 0 || (bytesPerFrame % pWav->channels) != 0) { - return 0; /* Only byte-aligned formats are supported. */ - } - - totalFramesRead = 0; - - while (framesToRead > 0) { - drwav_uint64 framesToReadThisIteration = drwav_min(framesToRead, sizeof(sampleData) / bytesPerFrame); - drwav_uint64 framesRead = drwav_read_pcm_frames(pWav, framesToReadThisIteration, sampleData); - if (framesRead == 0) { - break; - } - - DRWAV_ASSERT(framesRead <= framesToReadThisIteration); /* If this fails it means there's a bug in drwav_read_pcm_frames(). */ - - /* Validation to ensure we don't read too much from out intermediary buffer. This is to protect from invalid files. */ - samplesRead = framesRead * pWav->channels; - if ((samplesRead * bytesPerSample) > sizeof(sampleData)) { - DRWAV_ASSERT(DRWAV_FALSE); /* This should never happen with a valid file. */ - break; - } - - drwav__pcm_to_s16(pBufferOut, sampleData, (size_t)samplesRead, bytesPerSample); - - pBufferOut += samplesRead; - framesToRead -= framesRead; - totalFramesRead += framesRead; - } - - return totalFramesRead; -} - -DRWAV_PRIVATE drwav_uint64 drwav_read_pcm_frames_s16__ieee(drwav* pWav, drwav_uint64 framesToRead, drwav_int16* pBufferOut) -{ - drwav_uint64 totalFramesRead; - drwav_uint8 sampleData[4096] = { 0 }; - drwav_uint32 bytesPerFrame; - drwav_uint32 bytesPerSample; - drwav_uint64 samplesRead; - - if (pBufferOut == NULL) { - return drwav_read_pcm_frames(pWav, framesToRead, NULL); - } - - bytesPerFrame = drwav_get_bytes_per_pcm_frame(pWav); - if (bytesPerFrame == 0) { - return 0; - } - - bytesPerSample = bytesPerFrame / pWav->channels; - if (bytesPerSample == 0 || (bytesPerFrame % pWav->channels) != 0) { - return 0; /* Only byte-aligned formats are supported. */ - } - - totalFramesRead = 0; - - while (framesToRead > 0) { - drwav_uint64 framesToReadThisIteration = drwav_min(framesToRead, sizeof(sampleData) / bytesPerFrame); - drwav_uint64 framesRead = drwav_read_pcm_frames(pWav, framesToReadThisIteration, sampleData); - if (framesRead == 0) { - break; - } - - DRWAV_ASSERT(framesRead <= framesToReadThisIteration); /* If this fails it means there's a bug in drwav_read_pcm_frames(). */ - - /* Validation to ensure we don't read too much from out intermediary buffer. This is to protect from invalid files. */ - samplesRead = framesRead * pWav->channels; - if ((samplesRead * bytesPerSample) > sizeof(sampleData)) { - DRWAV_ASSERT(DRWAV_FALSE); /* This should never happen with a valid file. */ - break; - } - - drwav__ieee_to_s16(pBufferOut, sampleData, (size_t)samplesRead, bytesPerSample); /* Safe cast. */ - - pBufferOut += samplesRead; - framesToRead -= framesRead; - totalFramesRead += framesRead; - } - - return totalFramesRead; -} - -DRWAV_PRIVATE drwav_uint64 drwav_read_pcm_frames_s16__alaw(drwav* pWav, drwav_uint64 framesToRead, drwav_int16* pBufferOut) -{ - drwav_uint64 totalFramesRead; - drwav_uint8 sampleData[4096] = { 0 }; - drwav_uint32 bytesPerFrame; - drwav_uint32 bytesPerSample; - drwav_uint64 samplesRead; - - if (pBufferOut == NULL) { - return drwav_read_pcm_frames(pWav, framesToRead, NULL); - } - - bytesPerFrame = drwav_get_bytes_per_pcm_frame(pWav); - if (bytesPerFrame == 0) { - return 0; - } - - bytesPerSample = bytesPerFrame / pWav->channels; - if (bytesPerSample == 0 || (bytesPerFrame % pWav->channels) != 0) { - return 0; /* Only byte-aligned formats are supported. */ - } - - totalFramesRead = 0; - - while (framesToRead > 0) { - drwav_uint64 framesToReadThisIteration = drwav_min(framesToRead, sizeof(sampleData) / bytesPerFrame); - drwav_uint64 framesRead = drwav_read_pcm_frames(pWav, framesToReadThisIteration, sampleData); - if (framesRead == 0) { - break; - } - - DRWAV_ASSERT(framesRead <= framesToReadThisIteration); /* If this fails it means there's a bug in drwav_read_pcm_frames(). */ - - /* Validation to ensure we don't read too much from out intermediary buffer. This is to protect from invalid files. */ - samplesRead = framesRead * pWav->channels; - if ((samplesRead * bytesPerSample) > sizeof(sampleData)) { - DRWAV_ASSERT(DRWAV_FALSE); /* This should never happen with a valid file. */ - break; - } - - drwav_alaw_to_s16(pBufferOut, sampleData, (size_t)samplesRead); - - pBufferOut += samplesRead; - framesToRead -= framesRead; - totalFramesRead += framesRead; - } - - return totalFramesRead; -} - -DRWAV_PRIVATE drwav_uint64 drwav_read_pcm_frames_s16__mulaw(drwav* pWav, drwav_uint64 framesToRead, drwav_int16* pBufferOut) -{ - drwav_uint64 totalFramesRead; - drwav_uint8 sampleData[4096] = { 0 }; - drwav_uint32 bytesPerFrame; - drwav_uint32 bytesPerSample; - drwav_uint64 samplesRead; - - if (pBufferOut == NULL) { - return drwav_read_pcm_frames(pWav, framesToRead, NULL); - } - - bytesPerFrame = drwav_get_bytes_per_pcm_frame(pWav); - if (bytesPerFrame == 0) { - return 0; - } - - bytesPerSample = bytesPerFrame / pWav->channels; - if (bytesPerSample == 0 || (bytesPerFrame % pWav->channels) != 0) { - return 0; /* Only byte-aligned formats are supported. */ - } - - totalFramesRead = 0; - - while (framesToRead > 0) { - drwav_uint64 framesToReadThisIteration = drwav_min(framesToRead, sizeof(sampleData) / bytesPerFrame); - drwav_uint64 framesRead = drwav_read_pcm_frames(pWav, framesToReadThisIteration, sampleData); - if (framesRead == 0) { - break; - } - - DRWAV_ASSERT(framesRead <= framesToReadThisIteration); /* If this fails it means there's a bug in drwav_read_pcm_frames(). */ - - /* Validation to ensure we don't read too much from out intermediary buffer. This is to protect from invalid files. */ - samplesRead = framesRead * pWav->channels; - if ((samplesRead * bytesPerSample) > sizeof(sampleData)) { - DRWAV_ASSERT(DRWAV_FALSE); /* This should never happen with a valid file. */ - break; - } - - drwav_mulaw_to_s16(pBufferOut, sampleData, (size_t)samplesRead); - - pBufferOut += samplesRead; - framesToRead -= framesRead; - totalFramesRead += framesRead; - } - - return totalFramesRead; -} - -DRWAV_API drwav_uint64 drwav_read_pcm_frames_s16(drwav* pWav, drwav_uint64 framesToRead, drwav_int16* pBufferOut) -{ - if (pWav == NULL || framesToRead == 0) { - return 0; - } - - if (pBufferOut == NULL) { - return drwav_read_pcm_frames(pWav, framesToRead, NULL); - } - - /* Don't try to read more samples than can potentially fit in the output buffer. */ - if (framesToRead * pWav->channels * sizeof(drwav_int16) > DRWAV_SIZE_MAX) { - framesToRead = DRWAV_SIZE_MAX / sizeof(drwav_int16) / pWav->channels; - } - - if (pWav->translatedFormatTag == DR_WAVE_FORMAT_PCM) { - return drwav_read_pcm_frames_s16__pcm(pWav, framesToRead, pBufferOut); - } - - if (pWav->translatedFormatTag == DR_WAVE_FORMAT_IEEE_FLOAT) { - return drwav_read_pcm_frames_s16__ieee(pWav, framesToRead, pBufferOut); - } - - if (pWav->translatedFormatTag == DR_WAVE_FORMAT_ALAW) { - return drwav_read_pcm_frames_s16__alaw(pWav, framesToRead, pBufferOut); - } - - if (pWav->translatedFormatTag == DR_WAVE_FORMAT_MULAW) { - return drwav_read_pcm_frames_s16__mulaw(pWav, framesToRead, pBufferOut); - } - - if (pWav->translatedFormatTag == DR_WAVE_FORMAT_ADPCM) { - return drwav_read_pcm_frames_s16__msadpcm(pWav, framesToRead, pBufferOut); - } - - if (pWav->translatedFormatTag == DR_WAVE_FORMAT_DVI_ADPCM) { - return drwav_read_pcm_frames_s16__ima(pWav, framesToRead, pBufferOut); - } - - return 0; -} - -DRWAV_API drwav_uint64 drwav_read_pcm_frames_s16le(drwav* pWav, drwav_uint64 framesToRead, drwav_int16* pBufferOut) -{ - drwav_uint64 framesRead = drwav_read_pcm_frames_s16(pWav, framesToRead, pBufferOut); - if (pBufferOut != NULL && drwav__is_little_endian() == DRWAV_FALSE) { - drwav__bswap_samples_s16(pBufferOut, framesRead * pWav->channels); - } - - return framesRead; -} - -DRWAV_API drwav_uint64 drwav_read_pcm_frames_s16be(drwav* pWav, drwav_uint64 framesToRead, drwav_int16* pBufferOut) -{ - drwav_uint64 framesRead = drwav_read_pcm_frames_s16(pWav, framesToRead, pBufferOut); - if (pBufferOut != NULL && drwav__is_little_endian() == DRWAV_TRUE) { - drwav__bswap_samples_s16(pBufferOut, framesRead * pWav->channels); - } - - return framesRead; -} - - -DRWAV_API void drwav_u8_to_s16(drwav_int16* pOut, const drwav_uint8* pIn, size_t sampleCount) -{ - int r; - size_t i; - for (i = 0; i < sampleCount; ++i) { - int x = pIn[i]; - r = x << 8; - r = r - 32768; - pOut[i] = (short)r; - } -} - -DRWAV_API void drwav_s24_to_s16(drwav_int16* pOut, const drwav_uint8* pIn, size_t sampleCount) -{ - int r; - size_t i; - for (i = 0; i < sampleCount; ++i) { - int x = ((int)(((unsigned int)(((const drwav_uint8*)pIn)[i * 3 + 0]) << 8) | ((unsigned int)(((const drwav_uint8*)pIn)[i * 3 + 1]) << 16) | ((unsigned int)(((const drwav_uint8*)pIn)[i * 3 + 2])) << 24)) >> 8; - r = x >> 8; - pOut[i] = (short)r; - } -} - -DRWAV_API void drwav_s32_to_s16(drwav_int16* pOut, const drwav_int32* pIn, size_t sampleCount) -{ - int r; - size_t i; - for (i = 0; i < sampleCount; ++i) { - int x = pIn[i]; - r = x >> 16; - pOut[i] = (short)r; - } -} - -DRWAV_API void drwav_f32_to_s16(drwav_int16* pOut, const float* pIn, size_t sampleCount) -{ - int r; - size_t i; - for (i = 0; i < sampleCount; ++i) { - float x = pIn[i]; - float c; - c = ((x < -1) ? -1 : ((x > 1) ? 1 : x)); - c = c + 1; - r = (int)(c * 32767.5f); - r = r - 32768; - pOut[i] = (short)r; - } -} - -DRWAV_API void drwav_f64_to_s16(drwav_int16* pOut, const double* pIn, size_t sampleCount) -{ - int r; - size_t i; - for (i = 0; i < sampleCount; ++i) { - double x = pIn[i]; - double c; - c = ((x < -1) ? -1 : ((x > 1) ? 1 : x)); - c = c + 1; - r = (int)(c * 32767.5); - r = r - 32768; - pOut[i] = (short)r; - } -} - -DRWAV_API void drwav_alaw_to_s16(drwav_int16* pOut, const drwav_uint8* pIn, size_t sampleCount) -{ - size_t i; - for (i = 0; i < sampleCount; ++i) { - pOut[i] = drwav__alaw_to_s16(pIn[i]); - } -} - -DRWAV_API void drwav_mulaw_to_s16(drwav_int16* pOut, const drwav_uint8* pIn, size_t sampleCount) -{ - size_t i; - for (i = 0; i < sampleCount; ++i) { - pOut[i] = drwav__mulaw_to_s16(pIn[i]); - } -} - - - -DRWAV_PRIVATE void drwav__pcm_to_f32(float* pOut, const drwav_uint8* pIn, size_t sampleCount, unsigned int bytesPerSample) -{ - unsigned int i; - - /* Special case for 8-bit sample data because it's treated as unsigned. */ - if (bytesPerSample == 1) { - drwav_u8_to_f32(pOut, pIn, sampleCount); - return; - } - - /* Slightly more optimal implementation for common formats. */ - if (bytesPerSample == 2) { - drwav_s16_to_f32(pOut, (const drwav_int16*)pIn, sampleCount); - return; - } - if (bytesPerSample == 3) { - drwav_s24_to_f32(pOut, pIn, sampleCount); - return; - } - if (bytesPerSample == 4) { - drwav_s32_to_f32(pOut, (const drwav_int32*)pIn, sampleCount); - return; - } - - - /* Anything more than 64 bits per sample is not supported. */ - if (bytesPerSample > 8) { - DRWAV_ZERO_MEMORY(pOut, sampleCount * sizeof(*pOut)); - return; - } - - - /* Generic, slow converter. */ - for (i = 0; i < sampleCount; ++i) { - drwav_uint64 sample = 0; - unsigned int shift = (8 - bytesPerSample) * 8; - - unsigned int j; - for (j = 0; j < bytesPerSample; j += 1) { - DRWAV_ASSERT(j < 8); - sample |= (drwav_uint64)(pIn[j]) << shift; - shift += 8; - } - - pIn += j; - *pOut++ = (float)((drwav_int64)sample / 9223372036854775807.0); - } -} - -DRWAV_PRIVATE void drwav__ieee_to_f32(float* pOut, const drwav_uint8* pIn, size_t sampleCount, unsigned int bytesPerSample) -{ - if (bytesPerSample == 4) { - unsigned int i; - for (i = 0; i < sampleCount; ++i) { - *pOut++ = ((const float*)pIn)[i]; - } - return; - } - else if (bytesPerSample == 8) { - drwav_f64_to_f32(pOut, (const double*)pIn, sampleCount); - return; - } - else { - /* Only supporting 32- and 64-bit float. Output silence in all other cases. Contributions welcome for 16-bit float. */ - DRWAV_ZERO_MEMORY(pOut, sampleCount * sizeof(*pOut)); - return; - } -} - - -DRWAV_PRIVATE drwav_uint64 drwav_read_pcm_frames_f32__pcm(drwav* pWav, drwav_uint64 framesToRead, float* pBufferOut) -{ - drwav_uint64 totalFramesRead; - drwav_uint8 sampleData[4096] = { 0 }; - drwav_uint32 bytesPerFrame; - drwav_uint32 bytesPerSample; - drwav_uint64 samplesRead; - - bytesPerFrame = drwav_get_bytes_per_pcm_frame(pWav); - if (bytesPerFrame == 0) { - return 0; - } - - bytesPerSample = bytesPerFrame / pWav->channels; - if (bytesPerSample == 0 || (bytesPerFrame % pWav->channels) != 0) { - return 0; /* Only byte-aligned formats are supported. */ - } - - totalFramesRead = 0; - - while (framesToRead > 0) { - drwav_uint64 framesToReadThisIteration = drwav_min(framesToRead, sizeof(sampleData) / bytesPerFrame); - drwav_uint64 framesRead = drwav_read_pcm_frames(pWav, framesToReadThisIteration, sampleData); - if (framesRead == 0) { - break; - } - - DRWAV_ASSERT(framesRead <= framesToReadThisIteration); /* If this fails it means there's a bug in drwav_read_pcm_frames(). */ - - /* Validation to ensure we don't read too much from out intermediary buffer. This is to protect from invalid files. */ - samplesRead = framesRead * pWav->channels; - if ((samplesRead * bytesPerSample) > sizeof(sampleData)) { - DRWAV_ASSERT(DRWAV_FALSE); /* This should never happen with a valid file. */ - break; - } - - drwav__pcm_to_f32(pBufferOut, sampleData, (size_t)samplesRead, bytesPerSample); - - pBufferOut += samplesRead; - framesToRead -= framesRead; - totalFramesRead += framesRead; - } - - return totalFramesRead; -} - -DRWAV_PRIVATE drwav_uint64 drwav_read_pcm_frames_f32__msadpcm_ima(drwav* pWav, drwav_uint64 framesToRead, float* pBufferOut) -{ - /* - We're just going to borrow the implementation from the drwav_read_s16() since ADPCM is a little bit more complicated than other formats and I don't - want to duplicate that code. - */ - drwav_uint64 totalFramesRead; - drwav_int16 samples16[2048]; - - totalFramesRead = 0; - - while (framesToRead > 0) { - drwav_uint64 framesToReadThisIteration = drwav_min(framesToRead, drwav_countof(samples16) / pWav->channels); - drwav_uint64 framesRead = drwav_read_pcm_frames_s16(pWav, framesToReadThisIteration, samples16); - if (framesRead == 0) { - break; - } - - DRWAV_ASSERT(framesRead <= framesToReadThisIteration); /* If this fails it means there's a bug in drwav_read_pcm_frames(). */ - - drwav_s16_to_f32(pBufferOut, samples16, (size_t)(framesRead * pWav->channels)); /* <-- Safe cast because we're clamping to 2048. */ - - pBufferOut += framesRead * pWav->channels; - framesToRead -= framesRead; - totalFramesRead += framesRead; - } - - return totalFramesRead; -} - -DRWAV_PRIVATE drwav_uint64 drwav_read_pcm_frames_f32__ieee(drwav* pWav, drwav_uint64 framesToRead, float* pBufferOut) -{ - drwav_uint64 totalFramesRead; - drwav_uint8 sampleData[4096] = { 0 }; - drwav_uint32 bytesPerFrame; - drwav_uint32 bytesPerSample; - drwav_uint64 samplesRead; - - /* Fast path. */ - if (pWav->translatedFormatTag == DR_WAVE_FORMAT_IEEE_FLOAT && pWav->bitsPerSample == 32) { - return drwav_read_pcm_frames(pWav, framesToRead, pBufferOut); - } - - bytesPerFrame = drwav_get_bytes_per_pcm_frame(pWav); - if (bytesPerFrame == 0) { - return 0; - } - - bytesPerSample = bytesPerFrame / pWav->channels; - if (bytesPerSample == 0 || (bytesPerFrame % pWav->channels) != 0) { - return 0; /* Only byte-aligned formats are supported. */ - } - - totalFramesRead = 0; - - while (framesToRead > 0) { - drwav_uint64 framesToReadThisIteration = drwav_min(framesToRead, sizeof(sampleData) / bytesPerFrame); - drwav_uint64 framesRead = drwav_read_pcm_frames(pWav, framesToReadThisIteration, sampleData); - if (framesRead == 0) { - break; - } - - DRWAV_ASSERT(framesRead <= framesToReadThisIteration); /* If this fails it means there's a bug in drwav_read_pcm_frames(). */ - - /* Validation to ensure we don't read too much from out intermediary buffer. This is to protect from invalid files. */ - samplesRead = framesRead * pWav->channels; - if ((samplesRead * bytesPerSample) > sizeof(sampleData)) { - DRWAV_ASSERT(DRWAV_FALSE); /* This should never happen with a valid file. */ - break; - } - - drwav__ieee_to_f32(pBufferOut, sampleData, (size_t)samplesRead, bytesPerSample); - - pBufferOut += samplesRead; - framesToRead -= framesRead; - totalFramesRead += framesRead; - } - - return totalFramesRead; -} - -DRWAV_PRIVATE drwav_uint64 drwav_read_pcm_frames_f32__alaw(drwav* pWav, drwav_uint64 framesToRead, float* pBufferOut) -{ - drwav_uint64 totalFramesRead; - drwav_uint8 sampleData[4096] = { 0 }; - drwav_uint32 bytesPerFrame; - drwav_uint32 bytesPerSample; - drwav_uint64 samplesRead; - - bytesPerFrame = drwav_get_bytes_per_pcm_frame(pWav); - if (bytesPerFrame == 0) { - return 0; - } - - bytesPerSample = bytesPerFrame / pWav->channels; - if (bytesPerSample == 0 || (bytesPerFrame % pWav->channels) != 0) { - return 0; /* Only byte-aligned formats are supported. */ - } - - totalFramesRead = 0; - - while (framesToRead > 0) { - drwav_uint64 framesToReadThisIteration = drwav_min(framesToRead, sizeof(sampleData) / bytesPerFrame); - drwav_uint64 framesRead = drwav_read_pcm_frames(pWav, framesToReadThisIteration, sampleData); - if (framesRead == 0) { - break; - } - - DRWAV_ASSERT(framesRead <= framesToReadThisIteration); /* If this fails it means there's a bug in drwav_read_pcm_frames(). */ - - /* Validation to ensure we don't read too much from out intermediary buffer. This is to protect from invalid files. */ - samplesRead = framesRead * pWav->channels; - if ((samplesRead * bytesPerSample) > sizeof(sampleData)) { - DRWAV_ASSERT(DRWAV_FALSE); /* This should never happen with a valid file. */ - break; - } - - drwav_alaw_to_f32(pBufferOut, sampleData, (size_t)samplesRead); - - pBufferOut += samplesRead; - framesToRead -= framesRead; - totalFramesRead += framesRead; - } - - return totalFramesRead; -} - -DRWAV_PRIVATE drwav_uint64 drwav_read_pcm_frames_f32__mulaw(drwav* pWav, drwav_uint64 framesToRead, float* pBufferOut) -{ - drwav_uint64 totalFramesRead; - drwav_uint8 sampleData[4096] = { 0 }; - drwav_uint32 bytesPerFrame; - drwav_uint32 bytesPerSample; - drwav_uint64 samplesRead; - - bytesPerFrame = drwav_get_bytes_per_pcm_frame(pWav); - if (bytesPerFrame == 0) { - return 0; - } - - bytesPerSample = bytesPerFrame / pWav->channels; - if (bytesPerSample == 0 || (bytesPerFrame % pWav->channels) != 0) { - return 0; /* Only byte-aligned formats are supported. */ - } - - totalFramesRead = 0; - - while (framesToRead > 0) { - drwav_uint64 framesToReadThisIteration = drwav_min(framesToRead, sizeof(sampleData) / bytesPerFrame); - drwav_uint64 framesRead = drwav_read_pcm_frames(pWav, framesToReadThisIteration, sampleData); - if (framesRead == 0) { - break; - } - - DRWAV_ASSERT(framesRead <= framesToReadThisIteration); /* If this fails it means there's a bug in drwav_read_pcm_frames(). */ - - /* Validation to ensure we don't read too much from out intermediary buffer. This is to protect from invalid files. */ - samplesRead = framesRead * pWav->channels; - if ((samplesRead * bytesPerSample) > sizeof(sampleData)) { - DRWAV_ASSERT(DRWAV_FALSE); /* This should never happen with a valid file. */ - break; - } - - drwav_mulaw_to_f32(pBufferOut, sampleData, (size_t)samplesRead); - - pBufferOut += samplesRead; - framesToRead -= framesRead; - totalFramesRead += framesRead; - } - - return totalFramesRead; -} - -DRWAV_API drwav_uint64 drwav_read_pcm_frames_f32(drwav* pWav, drwav_uint64 framesToRead, float* pBufferOut) -{ - if (pWav == NULL || framesToRead == 0) { - return 0; - } - - if (pBufferOut == NULL) { - return drwav_read_pcm_frames(pWav, framesToRead, NULL); - } - - /* Don't try to read more samples than can potentially fit in the output buffer. */ - if (framesToRead * pWav->channels * sizeof(float) > DRWAV_SIZE_MAX) { - framesToRead = DRWAV_SIZE_MAX / sizeof(float) / pWav->channels; - } - - if (pWav->translatedFormatTag == DR_WAVE_FORMAT_PCM) { - return drwav_read_pcm_frames_f32__pcm(pWav, framesToRead, pBufferOut); - } - - if (pWav->translatedFormatTag == DR_WAVE_FORMAT_ADPCM || pWav->translatedFormatTag == DR_WAVE_FORMAT_DVI_ADPCM) { - return drwav_read_pcm_frames_f32__msadpcm_ima(pWav, framesToRead, pBufferOut); - } - - if (pWav->translatedFormatTag == DR_WAVE_FORMAT_IEEE_FLOAT) { - return drwav_read_pcm_frames_f32__ieee(pWav, framesToRead, pBufferOut); - } - - if (pWav->translatedFormatTag == DR_WAVE_FORMAT_ALAW) { - return drwav_read_pcm_frames_f32__alaw(pWav, framesToRead, pBufferOut); - } - - if (pWav->translatedFormatTag == DR_WAVE_FORMAT_MULAW) { - return drwav_read_pcm_frames_f32__mulaw(pWav, framesToRead, pBufferOut); - } - - return 0; -} - -DRWAV_API drwav_uint64 drwav_read_pcm_frames_f32le(drwav* pWav, drwav_uint64 framesToRead, float* pBufferOut) -{ - drwav_uint64 framesRead = drwav_read_pcm_frames_f32(pWav, framesToRead, pBufferOut); - if (pBufferOut != NULL && drwav__is_little_endian() == DRWAV_FALSE) { - drwav__bswap_samples_f32(pBufferOut, framesRead * pWav->channels); - } - - return framesRead; -} - -DRWAV_API drwav_uint64 drwav_read_pcm_frames_f32be(drwav* pWav, drwav_uint64 framesToRead, float* pBufferOut) -{ - drwav_uint64 framesRead = drwav_read_pcm_frames_f32(pWav, framesToRead, pBufferOut); - if (pBufferOut != NULL && drwav__is_little_endian() == DRWAV_TRUE) { - drwav__bswap_samples_f32(pBufferOut, framesRead * pWav->channels); - } - - return framesRead; -} - - -DRWAV_API void drwav_u8_to_f32(float* pOut, const drwav_uint8* pIn, size_t sampleCount) -{ - size_t i; - - if (pOut == NULL || pIn == NULL) { - return; - } - -#ifdef DR_WAV_LIBSNDFILE_COMPAT - /* - It appears libsndfile uses slightly different logic for the u8 -> f32 conversion to dr_wav, which in my opinion is incorrect. It appears - libsndfile performs the conversion something like "f32 = (u8 / 256) * 2 - 1", however I think it should be "f32 = (u8 / 255) * 2 - 1" (note - the divisor of 256 vs 255). I use libsndfile as a benchmark for testing, so I'm therefore leaving this block here just for my automated - correctness testing. This is disabled by default. - */ - for (i = 0; i < sampleCount; ++i) { - *pOut++ = (pIn[i] / 256.0f) * 2 - 1; - } -#else - for (i = 0; i < sampleCount; ++i) { - float x = pIn[i]; - x = x * 0.00784313725490196078f; /* 0..255 to 0..2 */ - x = x - 1; /* 0..2 to -1..1 */ - - *pOut++ = x; - } -#endif -} - -DRWAV_API void drwav_s16_to_f32(float* pOut, const drwav_int16* pIn, size_t sampleCount) -{ - size_t i; - - if (pOut == NULL || pIn == NULL) { - return; - } - - for (i = 0; i < sampleCount; ++i) { - *pOut++ = pIn[i] * 0.000030517578125f; - } -} - -DRWAV_API void drwav_s24_to_f32(float* pOut, const drwav_uint8* pIn, size_t sampleCount) -{ - size_t i; - - if (pOut == NULL || pIn == NULL) { - return; - } - - for (i = 0; i < sampleCount; ++i) { - double x; - drwav_uint32 a = ((drwav_uint32)(pIn[i * 3 + 0]) << 8); - drwav_uint32 b = ((drwav_uint32)(pIn[i * 3 + 1]) << 16); - drwav_uint32 c = ((drwav_uint32)(pIn[i * 3 + 2]) << 24); - - x = (double)((drwav_int32)(a | b | c) >> 8); - *pOut++ = (float)(x * 0.00000011920928955078125); - } -} - -DRWAV_API void drwav_s32_to_f32(float* pOut, const drwav_int32* pIn, size_t sampleCount) -{ - size_t i; - if (pOut == NULL || pIn == NULL) { - return; - } - - for (i = 0; i < sampleCount; ++i) { - *pOut++ = (float)(pIn[i] / 2147483648.0); - } -} - -DRWAV_API void drwav_f64_to_f32(float* pOut, const double* pIn, size_t sampleCount) -{ - size_t i; - - if (pOut == NULL || pIn == NULL) { - return; - } - - for (i = 0; i < sampleCount; ++i) { - *pOut++ = (float)pIn[i]; - } -} - -DRWAV_API void drwav_alaw_to_f32(float* pOut, const drwav_uint8* pIn, size_t sampleCount) -{ - size_t i; - - if (pOut == NULL || pIn == NULL) { - return; - } - - for (i = 0; i < sampleCount; ++i) { - *pOut++ = drwav__alaw_to_s16(pIn[i]) / 32768.0f; - } -} - -DRWAV_API void drwav_mulaw_to_f32(float* pOut, const drwav_uint8* pIn, size_t sampleCount) -{ - size_t i; - - if (pOut == NULL || pIn == NULL) { - return; - } - - for (i = 0; i < sampleCount; ++i) { - *pOut++ = drwav__mulaw_to_s16(pIn[i]) / 32768.0f; - } -} - - - -DRWAV_PRIVATE void drwav__pcm_to_s32(drwav_int32* pOut, const drwav_uint8* pIn, size_t totalSampleCount, unsigned int bytesPerSample) -{ - unsigned int i; - - /* Special case for 8-bit sample data because it's treated as unsigned. */ - if (bytesPerSample == 1) { - drwav_u8_to_s32(pOut, pIn, totalSampleCount); - return; - } - - /* Slightly more optimal implementation for common formats. */ - if (bytesPerSample == 2) { - drwav_s16_to_s32(pOut, (const drwav_int16*)pIn, totalSampleCount); - return; - } - if (bytesPerSample == 3) { - drwav_s24_to_s32(pOut, pIn, totalSampleCount); - return; - } - if (bytesPerSample == 4) { - for (i = 0; i < totalSampleCount; ++i) { - *pOut++ = ((const drwav_int32*)pIn)[i]; - } - return; - } - - - /* Anything more than 64 bits per sample is not supported. */ - if (bytesPerSample > 8) { - DRWAV_ZERO_MEMORY(pOut, totalSampleCount * sizeof(*pOut)); - return; - } - - - /* Generic, slow converter. */ - for (i = 0; i < totalSampleCount; ++i) { - drwav_uint64 sample = 0; - unsigned int shift = (8 - bytesPerSample) * 8; - - unsigned int j; - for (j = 0; j < bytesPerSample; j += 1) { - DRWAV_ASSERT(j < 8); - sample |= (drwav_uint64)(pIn[j]) << shift; - shift += 8; - } - - pIn += j; - *pOut++ = (drwav_int32)((drwav_int64)sample >> 32); - } -} - -DRWAV_PRIVATE void drwav__ieee_to_s32(drwav_int32* pOut, const drwav_uint8* pIn, size_t totalSampleCount, unsigned int bytesPerSample) -{ - if (bytesPerSample == 4) { - drwav_f32_to_s32(pOut, (const float*)pIn, totalSampleCount); - return; - } - else if (bytesPerSample == 8) { - drwav_f64_to_s32(pOut, (const double*)pIn, totalSampleCount); - return; - } - else { - /* Only supporting 32- and 64-bit float. Output silence in all other cases. Contributions welcome for 16-bit float. */ - DRWAV_ZERO_MEMORY(pOut, totalSampleCount * sizeof(*pOut)); - return; - } -} - - -DRWAV_PRIVATE drwav_uint64 drwav_read_pcm_frames_s32__pcm(drwav* pWav, drwav_uint64 framesToRead, drwav_int32* pBufferOut) -{ - drwav_uint64 totalFramesRead; - drwav_uint8 sampleData[4096] = { 0 }; - drwav_uint32 bytesPerFrame; - drwav_uint32 bytesPerSample; - drwav_uint64 samplesRead; - - /* Fast path. */ - if (pWav->translatedFormatTag == DR_WAVE_FORMAT_PCM && pWav->bitsPerSample == 32) { - return drwav_read_pcm_frames(pWav, framesToRead, pBufferOut); - } - - bytesPerFrame = drwav_get_bytes_per_pcm_frame(pWav); - if (bytesPerFrame == 0) { - return 0; - } - - bytesPerSample = bytesPerFrame / pWav->channels; - if (bytesPerSample == 0 || (bytesPerFrame % pWav->channels) != 0) { - return 0; /* Only byte-aligned formats are supported. */ - } - - totalFramesRead = 0; - - while (framesToRead > 0) { - drwav_uint64 framesToReadThisIteration = drwav_min(framesToRead, sizeof(sampleData) / bytesPerFrame); - drwav_uint64 framesRead = drwav_read_pcm_frames(pWav, framesToReadThisIteration, sampleData); - if (framesRead == 0) { - break; - } - - DRWAV_ASSERT(framesRead <= framesToReadThisIteration); /* If this fails it means there's a bug in drwav_read_pcm_frames(). */ - - /* Validation to ensure we don't read too much from out intermediary buffer. This is to protect from invalid files. */ - samplesRead = framesRead * pWav->channels; - if ((samplesRead * bytesPerSample) > sizeof(sampleData)) { - DRWAV_ASSERT(DRWAV_FALSE); /* This should never happen with a valid file. */ - break; - } - - drwav__pcm_to_s32(pBufferOut, sampleData, (size_t)samplesRead, bytesPerSample); - - pBufferOut += samplesRead; - framesToRead -= framesRead; - totalFramesRead += framesRead; - } - - return totalFramesRead; -} - -DRWAV_PRIVATE drwav_uint64 drwav_read_pcm_frames_s32__msadpcm_ima(drwav* pWav, drwav_uint64 framesToRead, drwav_int32* pBufferOut) -{ - /* - We're just going to borrow the implementation from the drwav_read_s16() since ADPCM is a little bit more complicated than other formats and I don't - want to duplicate that code. - */ - drwav_uint64 totalFramesRead = 0; - drwav_int16 samples16[2048]; - - while (framesToRead > 0) { - drwav_uint64 framesToReadThisIteration = drwav_min(framesToRead, drwav_countof(samples16) / pWav->channels); - drwav_uint64 framesRead = drwav_read_pcm_frames_s16(pWav, framesToReadThisIteration, samples16); - if (framesRead == 0) { - break; - } - - DRWAV_ASSERT(framesRead <= framesToReadThisIteration); /* If this fails it means there's a bug in drwav_read_pcm_frames(). */ - - drwav_s16_to_s32(pBufferOut, samples16, (size_t)(framesRead * pWav->channels)); /* <-- Safe cast because we're clamping to 2048. */ - - pBufferOut += framesRead * pWav->channels; - framesToRead -= framesRead; - totalFramesRead += framesRead; - } - - return totalFramesRead; -} - -DRWAV_PRIVATE drwav_uint64 drwav_read_pcm_frames_s32__ieee(drwav* pWav, drwav_uint64 framesToRead, drwav_int32* pBufferOut) -{ - drwav_uint64 totalFramesRead; - drwav_uint8 sampleData[4096] = { 0 }; - drwav_uint32 bytesPerFrame; - drwav_uint32 bytesPerSample; - drwav_uint64 samplesRead; - - bytesPerFrame = drwav_get_bytes_per_pcm_frame(pWav); - if (bytesPerFrame == 0) { - return 0; - } - - bytesPerSample = bytesPerFrame / pWav->channels; - if (bytesPerSample == 0 || (bytesPerFrame % pWav->channels) != 0) { - return 0; /* Only byte-aligned formats are supported. */ - } - - totalFramesRead = 0; - - while (framesToRead > 0) { - drwav_uint64 framesToReadThisIteration = drwav_min(framesToRead, sizeof(sampleData) / bytesPerFrame); - drwav_uint64 framesRead = drwav_read_pcm_frames(pWav, framesToReadThisIteration, sampleData); - if (framesRead == 0) { - break; - } - - DRWAV_ASSERT(framesRead <= framesToReadThisIteration); /* If this fails it means there's a bug in drwav_read_pcm_frames(). */ - - /* Validation to ensure we don't read too much from out intermediary buffer. This is to protect from invalid files. */ - samplesRead = framesRead * pWav->channels; - if ((samplesRead * bytesPerSample) > sizeof(sampleData)) { - DRWAV_ASSERT(DRWAV_FALSE); /* This should never happen with a valid file. */ - break; - } - - drwav__ieee_to_s32(pBufferOut, sampleData, (size_t)samplesRead, bytesPerSample); - - pBufferOut += samplesRead; - framesToRead -= framesRead; - totalFramesRead += framesRead; - } - - return totalFramesRead; -} - -DRWAV_PRIVATE drwav_uint64 drwav_read_pcm_frames_s32__alaw(drwav* pWav, drwav_uint64 framesToRead, drwav_int32* pBufferOut) -{ - drwav_uint64 totalFramesRead; - drwav_uint8 sampleData[4096] = { 0 }; - drwav_uint32 bytesPerFrame; - drwav_uint32 bytesPerSample; - drwav_uint64 samplesRead; - - bytesPerFrame = drwav_get_bytes_per_pcm_frame(pWav); - if (bytesPerFrame == 0) { - return 0; - } - - bytesPerSample = bytesPerFrame / pWav->channels; - if (bytesPerSample == 0 || (bytesPerFrame % pWav->channels) != 0) { - return 0; /* Only byte-aligned formats are supported. */ - } - - totalFramesRead = 0; - - while (framesToRead > 0) { - drwav_uint64 framesToReadThisIteration = drwav_min(framesToRead, sizeof(sampleData) / bytesPerFrame); - drwav_uint64 framesRead = drwav_read_pcm_frames(pWav, framesToReadThisIteration, sampleData); - if (framesRead == 0) { - break; - } - - DRWAV_ASSERT(framesRead <= framesToReadThisIteration); /* If this fails it means there's a bug in drwav_read_pcm_frames(). */ - - /* Validation to ensure we don't read too much from out intermediary buffer. This is to protect from invalid files. */ - samplesRead = framesRead * pWav->channels; - if ((samplesRead * bytesPerSample) > sizeof(sampleData)) { - DRWAV_ASSERT(DRWAV_FALSE); /* This should never happen with a valid file. */ - break; - } - - drwav_alaw_to_s32(pBufferOut, sampleData, (size_t)samplesRead); - - pBufferOut += samplesRead; - framesToRead -= framesRead; - totalFramesRead += framesRead; - } - - return totalFramesRead; -} - -DRWAV_PRIVATE drwav_uint64 drwav_read_pcm_frames_s32__mulaw(drwav* pWav, drwav_uint64 framesToRead, drwav_int32* pBufferOut) -{ - drwav_uint64 totalFramesRead; - drwav_uint8 sampleData[4096] = { 0 }; - drwav_uint32 bytesPerFrame; - drwav_uint32 bytesPerSample; - drwav_uint64 samplesRead; - - bytesPerFrame = drwav_get_bytes_per_pcm_frame(pWav); - if (bytesPerFrame == 0) { - return 0; - } - - bytesPerSample = bytesPerFrame / pWav->channels; - if (bytesPerSample == 0 || (bytesPerFrame % pWav->channels) != 0) { - return 0; /* Only byte-aligned formats are supported. */ - } - - totalFramesRead = 0; - - while (framesToRead > 0) { - drwav_uint64 framesToReadThisIteration = drwav_min(framesToRead, sizeof(sampleData) / bytesPerFrame); - drwav_uint64 framesRead = drwav_read_pcm_frames(pWav, framesToReadThisIteration, sampleData); - if (framesRead == 0) { - break; - } - - DRWAV_ASSERT(framesRead <= framesToReadThisIteration); /* If this fails it means there's a bug in drwav_read_pcm_frames(). */ - - /* Validation to ensure we don't read too much from out intermediary buffer. This is to protect from invalid files. */ - samplesRead = framesRead * pWav->channels; - if ((samplesRead * bytesPerSample) > sizeof(sampleData)) { - DRWAV_ASSERT(DRWAV_FALSE); /* This should never happen with a valid file. */ - break; - } - - drwav_mulaw_to_s32(pBufferOut, sampleData, (size_t)samplesRead); - - pBufferOut += samplesRead; - framesToRead -= framesRead; - totalFramesRead += framesRead; - } - - return totalFramesRead; -} - -DRWAV_API drwav_uint64 drwav_read_pcm_frames_s32(drwav* pWav, drwav_uint64 framesToRead, drwav_int32* pBufferOut) -{ - if (pWav == NULL || framesToRead == 0) { - return 0; - } - - if (pBufferOut == NULL) { - return drwav_read_pcm_frames(pWav, framesToRead, NULL); - } - - /* Don't try to read more samples than can potentially fit in the output buffer. */ - if (framesToRead * pWav->channels * sizeof(drwav_int32) > DRWAV_SIZE_MAX) { - framesToRead = DRWAV_SIZE_MAX / sizeof(drwav_int32) / pWav->channels; - } - - if (pWav->translatedFormatTag == DR_WAVE_FORMAT_PCM) { - return drwav_read_pcm_frames_s32__pcm(pWav, framesToRead, pBufferOut); - } - - if (pWav->translatedFormatTag == DR_WAVE_FORMAT_ADPCM || pWav->translatedFormatTag == DR_WAVE_FORMAT_DVI_ADPCM) { - return drwav_read_pcm_frames_s32__msadpcm_ima(pWav, framesToRead, pBufferOut); - } - - if (pWav->translatedFormatTag == DR_WAVE_FORMAT_IEEE_FLOAT) { - return drwav_read_pcm_frames_s32__ieee(pWav, framesToRead, pBufferOut); - } - - if (pWav->translatedFormatTag == DR_WAVE_FORMAT_ALAW) { - return drwav_read_pcm_frames_s32__alaw(pWav, framesToRead, pBufferOut); - } - - if (pWav->translatedFormatTag == DR_WAVE_FORMAT_MULAW) { - return drwav_read_pcm_frames_s32__mulaw(pWav, framesToRead, pBufferOut); - } - - return 0; -} - -DRWAV_API drwav_uint64 drwav_read_pcm_frames_s32le(drwav* pWav, drwav_uint64 framesToRead, drwav_int32* pBufferOut) -{ - drwav_uint64 framesRead = drwav_read_pcm_frames_s32(pWav, framesToRead, pBufferOut); - if (pBufferOut != NULL && drwav__is_little_endian() == DRWAV_FALSE) { - drwav__bswap_samples_s32(pBufferOut, framesRead * pWav->channels); - } - - return framesRead; -} - -DRWAV_API drwav_uint64 drwav_read_pcm_frames_s32be(drwav* pWav, drwav_uint64 framesToRead, drwav_int32* pBufferOut) -{ - drwav_uint64 framesRead = drwav_read_pcm_frames_s32(pWav, framesToRead, pBufferOut); - if (pBufferOut != NULL && drwav__is_little_endian() == DRWAV_TRUE) { - drwav__bswap_samples_s32(pBufferOut, framesRead * pWav->channels); - } - - return framesRead; -} - - -DRWAV_API void drwav_u8_to_s32(drwav_int32* pOut, const drwav_uint8* pIn, size_t sampleCount) -{ - size_t i; - - if (pOut == NULL || pIn == NULL) { - return; - } - - for (i = 0; i < sampleCount; ++i) { - *pOut++ = ((int)pIn[i] - 128) << 24; - } -} - -DRWAV_API void drwav_s16_to_s32(drwav_int32* pOut, const drwav_int16* pIn, size_t sampleCount) -{ - size_t i; - - if (pOut == NULL || pIn == NULL) { - return; - } - - for (i = 0; i < sampleCount; ++i) { - *pOut++ = pIn[i] << 16; - } -} - -DRWAV_API void drwav_s24_to_s32(drwav_int32* pOut, const drwav_uint8* pIn, size_t sampleCount) -{ - size_t i; - - if (pOut == NULL || pIn == NULL) { - return; - } - - for (i = 0; i < sampleCount; ++i) { - unsigned int s0 = pIn[i * 3 + 0]; - unsigned int s1 = pIn[i * 3 + 1]; - unsigned int s2 = pIn[i * 3 + 2]; - - drwav_int32 sample32 = (drwav_int32)((s0 << 8) | (s1 << 16) | (s2 << 24)); - *pOut++ = sample32; - } -} - -DRWAV_API void drwav_f32_to_s32(drwav_int32* pOut, const float* pIn, size_t sampleCount) -{ - size_t i; - - if (pOut == NULL || pIn == NULL) { - return; - } - - for (i = 0; i < sampleCount; ++i) { - *pOut++ = (drwav_int32)(2147483648.0 * pIn[i]); - } -} - -DRWAV_API void drwav_f64_to_s32(drwav_int32* pOut, const double* pIn, size_t sampleCount) -{ - size_t i; - - if (pOut == NULL || pIn == NULL) { - return; - } - - for (i = 0; i < sampleCount; ++i) { - *pOut++ = (drwav_int32)(2147483648.0 * pIn[i]); - } -} - -DRWAV_API void drwav_alaw_to_s32(drwav_int32* pOut, const drwav_uint8* pIn, size_t sampleCount) -{ - size_t i; - - if (pOut == NULL || pIn == NULL) { - return; - } - - for (i = 0; i < sampleCount; ++i) { - *pOut++ = ((drwav_int32)drwav__alaw_to_s16(pIn[i])) << 16; - } -} - -DRWAV_API void drwav_mulaw_to_s32(drwav_int32* pOut, const drwav_uint8* pIn, size_t sampleCount) -{ - size_t i; - - if (pOut == NULL || pIn == NULL) { - return; - } - - for (i = 0; i < sampleCount; ++i) { - *pOut++ = ((drwav_int32)drwav__mulaw_to_s16(pIn[i])) << 16; - } -} - - - -DRWAV_PRIVATE drwav_int16* drwav__read_pcm_frames_and_close_s16(drwav* pWav, unsigned int* channels, unsigned int* sampleRate, drwav_uint64* totalFrameCount) -{ - drwav_uint64 sampleDataSize; - drwav_int16* pSampleData; - drwav_uint64 framesRead; - - DRWAV_ASSERT(pWav != NULL); - - sampleDataSize = pWav->totalPCMFrameCount * pWav->channels * sizeof(drwav_int16); - if (sampleDataSize > DRWAV_SIZE_MAX) { - drwav_uninit(pWav); - return NULL; /* File's too big. */ - } - - pSampleData = (drwav_int16*)drwav__malloc_from_callbacks((size_t)sampleDataSize, &pWav->allocationCallbacks); /* <-- Safe cast due to the check above. */ - if (pSampleData == NULL) { - drwav_uninit(pWav); - return NULL; /* Failed to allocate memory. */ - } - - framesRead = drwav_read_pcm_frames_s16(pWav, (size_t)pWav->totalPCMFrameCount, pSampleData); - if (framesRead != pWav->totalPCMFrameCount) { - drwav__free_from_callbacks(pSampleData, &pWav->allocationCallbacks); - drwav_uninit(pWav); - return NULL; /* There was an error reading the samples. */ - } - - drwav_uninit(pWav); - - if (sampleRate) { - *sampleRate = pWav->sampleRate; - } - if (channels) { - *channels = pWav->channels; - } - if (totalFrameCount) { - *totalFrameCount = pWav->totalPCMFrameCount; - } - - return pSampleData; -} - -DRWAV_PRIVATE float* drwav__read_pcm_frames_and_close_f32(drwav* pWav, unsigned int* channels, unsigned int* sampleRate, drwav_uint64* totalFrameCount) -{ - drwav_uint64 sampleDataSize; - float* pSampleData; - drwav_uint64 framesRead; - - DRWAV_ASSERT(pWav != NULL); - - sampleDataSize = pWav->totalPCMFrameCount * pWav->channels * sizeof(float); - if (sampleDataSize > DRWAV_SIZE_MAX) { - drwav_uninit(pWav); - return NULL; /* File's too big. */ - } - - pSampleData = (float*)drwav__malloc_from_callbacks((size_t)sampleDataSize, &pWav->allocationCallbacks); /* <-- Safe cast due to the check above. */ - if (pSampleData == NULL) { - drwav_uninit(pWav); - return NULL; /* Failed to allocate memory. */ - } - - framesRead = drwav_read_pcm_frames_f32(pWav, (size_t)pWav->totalPCMFrameCount, pSampleData); - if (framesRead != pWav->totalPCMFrameCount) { - drwav__free_from_callbacks(pSampleData, &pWav->allocationCallbacks); - drwav_uninit(pWav); - return NULL; /* There was an error reading the samples. */ - } - - drwav_uninit(pWav); - - if (sampleRate) { - *sampleRate = pWav->sampleRate; - } - if (channels) { - *channels = pWav->channels; - } - if (totalFrameCount) { - *totalFrameCount = pWav->totalPCMFrameCount; - } - - return pSampleData; -} - -DRWAV_PRIVATE drwav_int32* drwav__read_pcm_frames_and_close_s32(drwav* pWav, unsigned int* channels, unsigned int* sampleRate, drwav_uint64* totalFrameCount) -{ - drwav_uint64 sampleDataSize; - drwav_int32* pSampleData; - drwav_uint64 framesRead; - - DRWAV_ASSERT(pWav != NULL); - - sampleDataSize = pWav->totalPCMFrameCount * pWav->channels * sizeof(drwav_int32); - if (sampleDataSize > DRWAV_SIZE_MAX) { - drwav_uninit(pWav); - return NULL; /* File's too big. */ - } - - pSampleData = (drwav_int32*)drwav__malloc_from_callbacks((size_t)sampleDataSize, &pWav->allocationCallbacks); /* <-- Safe cast due to the check above. */ - if (pSampleData == NULL) { - drwav_uninit(pWav); - return NULL; /* Failed to allocate memory. */ - } - - framesRead = drwav_read_pcm_frames_s32(pWav, (size_t)pWav->totalPCMFrameCount, pSampleData); - if (framesRead != pWav->totalPCMFrameCount) { - drwav__free_from_callbacks(pSampleData, &pWav->allocationCallbacks); - drwav_uninit(pWav); - return NULL; /* There was an error reading the samples. */ - } - - drwav_uninit(pWav); - - if (sampleRate) { - *sampleRate = pWav->sampleRate; - } - if (channels) { - *channels = pWav->channels; - } - if (totalFrameCount) { - *totalFrameCount = pWav->totalPCMFrameCount; - } - - return pSampleData; -} - - - -DRWAV_API drwav_int16* drwav_open_and_read_pcm_frames_s16(drwav_read_proc onRead, drwav_seek_proc onSeek, void* pUserData, unsigned int* channelsOut, unsigned int* sampleRateOut, drwav_uint64* totalFrameCountOut, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - drwav wav; - - if (channelsOut) { - *channelsOut = 0; - } - if (sampleRateOut) { - *sampleRateOut = 0; - } - if (totalFrameCountOut) { - *totalFrameCountOut = 0; - } - - if (!drwav_init(&wav, onRead, onSeek, pUserData, pAllocationCallbacks)) { - return NULL; - } - - return drwav__read_pcm_frames_and_close_s16(&wav, channelsOut, sampleRateOut, totalFrameCountOut); -} - -DRWAV_API float* drwav_open_and_read_pcm_frames_f32(drwav_read_proc onRead, drwav_seek_proc onSeek, void* pUserData, unsigned int* channelsOut, unsigned int* sampleRateOut, drwav_uint64* totalFrameCountOut, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - drwav wav; - - if (channelsOut) { - *channelsOut = 0; - } - if (sampleRateOut) { - *sampleRateOut = 0; - } - if (totalFrameCountOut) { - *totalFrameCountOut = 0; - } - - if (!drwav_init(&wav, onRead, onSeek, pUserData, pAllocationCallbacks)) { - return NULL; - } - - return drwav__read_pcm_frames_and_close_f32(&wav, channelsOut, sampleRateOut, totalFrameCountOut); -} - -DRWAV_API drwav_int32* drwav_open_and_read_pcm_frames_s32(drwav_read_proc onRead, drwav_seek_proc onSeek, void* pUserData, unsigned int* channelsOut, unsigned int* sampleRateOut, drwav_uint64* totalFrameCountOut, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - drwav wav; - - if (channelsOut) { - *channelsOut = 0; - } - if (sampleRateOut) { - *sampleRateOut = 0; - } - if (totalFrameCountOut) { - *totalFrameCountOut = 0; - } - - if (!drwav_init(&wav, onRead, onSeek, pUserData, pAllocationCallbacks)) { - return NULL; - } - - return drwav__read_pcm_frames_and_close_s32(&wav, channelsOut, sampleRateOut, totalFrameCountOut); -} - -#ifndef DR_WAV_NO_STDIO -DRWAV_API drwav_int16* drwav_open_file_and_read_pcm_frames_s16(const char* filename, unsigned int* channelsOut, unsigned int* sampleRateOut, drwav_uint64* totalFrameCountOut, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - drwav wav; - - if (channelsOut) { - *channelsOut = 0; - } - if (sampleRateOut) { - *sampleRateOut = 0; - } - if (totalFrameCountOut) { - *totalFrameCountOut = 0; - } - - if (!drwav_init_file(&wav, filename, pAllocationCallbacks)) { - return NULL; - } - - return drwav__read_pcm_frames_and_close_s16(&wav, channelsOut, sampleRateOut, totalFrameCountOut); -} - -DRWAV_API float* drwav_open_file_and_read_pcm_frames_f32(const char* filename, unsigned int* channelsOut, unsigned int* sampleRateOut, drwav_uint64* totalFrameCountOut, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - drwav wav; - - if (channelsOut) { - *channelsOut = 0; - } - if (sampleRateOut) { - *sampleRateOut = 0; - } - if (totalFrameCountOut) { - *totalFrameCountOut = 0; - } - - if (!drwav_init_file(&wav, filename, pAllocationCallbacks)) { - return NULL; - } - - return drwav__read_pcm_frames_and_close_f32(&wav, channelsOut, sampleRateOut, totalFrameCountOut); -} - -DRWAV_API drwav_int32* drwav_open_file_and_read_pcm_frames_s32(const char* filename, unsigned int* channelsOut, unsigned int* sampleRateOut, drwav_uint64* totalFrameCountOut, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - drwav wav; - - if (channelsOut) { - *channelsOut = 0; - } - if (sampleRateOut) { - *sampleRateOut = 0; - } - if (totalFrameCountOut) { - *totalFrameCountOut = 0; - } - - if (!drwav_init_file(&wav, filename, pAllocationCallbacks)) { - return NULL; - } - - return drwav__read_pcm_frames_and_close_s32(&wav, channelsOut, sampleRateOut, totalFrameCountOut); -} - - -DRWAV_API drwav_int16* drwav_open_file_and_read_pcm_frames_s16_w(const wchar_t* filename, unsigned int* channelsOut, unsigned int* sampleRateOut, drwav_uint64* totalFrameCountOut, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - drwav wav; - - if (sampleRateOut) { - *sampleRateOut = 0; - } - if (channelsOut) { - *channelsOut = 0; - } - if (totalFrameCountOut) { - *totalFrameCountOut = 0; - } - - if (!drwav_init_file_w(&wav, filename, pAllocationCallbacks)) { - return NULL; - } - - return drwav__read_pcm_frames_and_close_s16(&wav, channelsOut, sampleRateOut, totalFrameCountOut); -} - -DRWAV_API float* drwav_open_file_and_read_pcm_frames_f32_w(const wchar_t* filename, unsigned int* channelsOut, unsigned int* sampleRateOut, drwav_uint64* totalFrameCountOut, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - drwav wav; - - if (sampleRateOut) { - *sampleRateOut = 0; - } - if (channelsOut) { - *channelsOut = 0; - } - if (totalFrameCountOut) { - *totalFrameCountOut = 0; - } - - if (!drwav_init_file_w(&wav, filename, pAllocationCallbacks)) { - return NULL; - } - - return drwav__read_pcm_frames_and_close_f32(&wav, channelsOut, sampleRateOut, totalFrameCountOut); -} - -DRWAV_API drwav_int32* drwav_open_file_and_read_pcm_frames_s32_w(const wchar_t* filename, unsigned int* channelsOut, unsigned int* sampleRateOut, drwav_uint64* totalFrameCountOut, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - drwav wav; - - if (sampleRateOut) { - *sampleRateOut = 0; - } - if (channelsOut) { - *channelsOut = 0; - } - if (totalFrameCountOut) { - *totalFrameCountOut = 0; - } - - if (!drwav_init_file_w(&wav, filename, pAllocationCallbacks)) { - return NULL; - } - - return drwav__read_pcm_frames_and_close_s32(&wav, channelsOut, sampleRateOut, totalFrameCountOut); -} -#endif - -DRWAV_API drwav_int16* drwav_open_memory_and_read_pcm_frames_s16(const void* data, size_t dataSize, unsigned int* channelsOut, unsigned int* sampleRateOut, drwav_uint64* totalFrameCountOut, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - drwav wav; - - if (channelsOut) { - *channelsOut = 0; - } - if (sampleRateOut) { - *sampleRateOut = 0; - } - if (totalFrameCountOut) { - *totalFrameCountOut = 0; - } - - if (!drwav_init_memory(&wav, data, dataSize, pAllocationCallbacks)) { - return NULL; - } - - return drwav__read_pcm_frames_and_close_s16(&wav, channelsOut, sampleRateOut, totalFrameCountOut); -} - -DRWAV_API float* drwav_open_memory_and_read_pcm_frames_f32(const void* data, size_t dataSize, unsigned int* channelsOut, unsigned int* sampleRateOut, drwav_uint64* totalFrameCountOut, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - drwav wav; - - if (channelsOut) { - *channelsOut = 0; - } - if (sampleRateOut) { - *sampleRateOut = 0; - } - if (totalFrameCountOut) { - *totalFrameCountOut = 0; - } - - if (!drwav_init_memory(&wav, data, dataSize, pAllocationCallbacks)) { - return NULL; - } - - return drwav__read_pcm_frames_and_close_f32(&wav, channelsOut, sampleRateOut, totalFrameCountOut); -} - -DRWAV_API drwav_int32* drwav_open_memory_and_read_pcm_frames_s32(const void* data, size_t dataSize, unsigned int* channelsOut, unsigned int* sampleRateOut, drwav_uint64* totalFrameCountOut, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - drwav wav; - - if (channelsOut) { - *channelsOut = 0; - } - if (sampleRateOut) { - *sampleRateOut = 0; - } - if (totalFrameCountOut) { - *totalFrameCountOut = 0; - } - - if (!drwav_init_memory(&wav, data, dataSize, pAllocationCallbacks)) { - return NULL; - } - - return drwav__read_pcm_frames_and_close_s32(&wav, channelsOut, sampleRateOut, totalFrameCountOut); -} -#endif /* DR_WAV_NO_CONVERSION_API */ - - -DRWAV_API void drwav_free(void* p, const drwav_allocation_callbacks* pAllocationCallbacks) -{ - if (pAllocationCallbacks != NULL) { - drwav__free_from_callbacks(p, pAllocationCallbacks); - } - else { - drwav__free_default(p, NULL); - } -} - -DRWAV_API drwav_uint16 drwav_bytes_to_u16(const drwav_uint8* data) -{ - return ((drwav_uint16)data[0] << 0) | ((drwav_uint16)data[1] << 8); -} - -DRWAV_API drwav_int16 drwav_bytes_to_s16(const drwav_uint8* data) -{ - return (drwav_int16)drwav_bytes_to_u16(data); -} - -DRWAV_API drwav_uint32 drwav_bytes_to_u32(const drwav_uint8* data) -{ - return ((drwav_uint32)data[0] << 0) | ((drwav_uint32)data[1] << 8) | ((drwav_uint32)data[2] << 16) | ((drwav_uint32)data[3] << 24); -} - -DRWAV_API float drwav_bytes_to_f32(const drwav_uint8* data) -{ - union { - drwav_uint32 u32; - float f32; - } value; - - value.u32 = drwav_bytes_to_u32(data); - return value.f32; -} - -DRWAV_API drwav_int32 drwav_bytes_to_s32(const drwav_uint8* data) -{ - return (drwav_int32)drwav_bytes_to_u32(data); -} - -DRWAV_API drwav_uint64 drwav_bytes_to_u64(const drwav_uint8* data) -{ - return - ((drwav_uint64)data[0] << 0) | ((drwav_uint64)data[1] << 8) | ((drwav_uint64)data[2] << 16) | ((drwav_uint64)data[3] << 24) | - ((drwav_uint64)data[4] << 32) | ((drwav_uint64)data[5] << 40) | ((drwav_uint64)data[6] << 48) | ((drwav_uint64)data[7] << 56); -} - -DRWAV_API drwav_int64 drwav_bytes_to_s64(const drwav_uint8* data) -{ - return (drwav_int64)drwav_bytes_to_u64(data); -} - - -DRWAV_API drwav_bool32 drwav_guid_equal(const drwav_uint8 a[16], const drwav_uint8 b[16]) -{ - int i; - for (i = 0; i < 16; i += 1) { - if (a[i] != b[i]) { - return DRWAV_FALSE; - } - } - - return DRWAV_TRUE; -} - -DRWAV_API drwav_bool32 drwav_fourcc_equal(const drwav_uint8* a, const char* b) -{ - return - a[0] == b[0] && - a[1] == b[1] && - a[2] == b[2] && - a[3] == b[3]; -} - -#endif /* dr_wav_c */ -#endif /* DR_WAV_IMPLEMENTATION */ - -/* -REVISION HISTORY -================ -v0.13.6 - 2022-04-10 - - Fix compilation error on older versions of GCC. - - Remove some dependencies on the standard library. - -v0.13.5 - 2022-01-26 - - Fix an error when seeking to the end of the file. - -v0.13.4 - 2021-12-08 - - Fix some static analysis warnings. - -v0.13.3 - 2021-11-24 - - Fix an incorrect assertion when trying to endian swap 1-byte sample formats. This is now a no-op - rather than a failed assertion. - - Fix a bug with parsing of the bext chunk. - - Fix some static analysis warnings. - -v0.13.2 - 2021-10-02 - - Fix a possible buffer overflow when reading from compressed formats. - -v0.13.1 - 2021-07-31 - - Fix platform detection for ARM64. - -v0.13.0 - 2021-07-01 - - Improve support for reading and writing metadata. Use the `_with_metadata()` APIs to initialize - a WAV decoder and store the metadata within the `drwav` object. Use the `pMetadata` and - `metadataCount` members of the `drwav` object to read the data. The old way of handling metadata - via a callback is still usable and valid. - - API CHANGE: drwav_target_write_size_bytes() now takes extra parameters for calculating the - required write size when writing metadata. - - Add drwav_get_cursor_in_pcm_frames() - - Add drwav_get_length_in_pcm_frames() - - Fix a bug where drwav_read_raw() can call the read callback with a byte count of zero. - -v0.12.20 - 2021-06-11 - - Fix some undefined behavior. - -v0.12.19 - 2021-02-21 - - Fix a warning due to referencing _MSC_VER when it is undefined. - - Minor improvements to the management of some internal state concerning the data chunk cursor. - -v0.12.18 - 2021-01-31 - - Clean up some static analysis warnings. - -v0.12.17 - 2021-01-17 - - Minor fix to sample code in documentation. - - Correctly qualify a private API as private rather than public. - - Code cleanup. - -v0.12.16 - 2020-12-02 - - Fix a bug when trying to read more bytes than can fit in a size_t. - -v0.12.15 - 2020-11-21 - - Fix compilation with OpenWatcom. - -v0.12.14 - 2020-11-13 - - Minor code clean up. - -v0.12.13 - 2020-11-01 - - Improve compiler support for older versions of GCC. - -v0.12.12 - 2020-09-28 - - Add support for RF64. - - Fix a bug in writing mode where the size of the RIFF chunk incorrectly includes the header section. - -v0.12.11 - 2020-09-08 - - Fix a compilation error on older compilers. - -v0.12.10 - 2020-08-24 - - Fix a bug when seeking with ADPCM formats. - -v0.12.9 - 2020-08-02 - - Simplify sized types. - -v0.12.8 - 2020-07-25 - - Fix a compilation warning. - -v0.12.7 - 2020-07-15 - - Fix some bugs on big-endian architectures. - - Fix an error in s24 to f32 conversion. - -v0.12.6 - 2020-06-23 - - Change drwav_read_*() to allow NULL to be passed in as the output buffer which is equivalent to a forward seek. - - Fix a buffer overflow when trying to decode invalid IMA-ADPCM files. - - Add include guard for the implementation section. - -v0.12.5 - 2020-05-27 - - Minor documentation fix. - -v0.12.4 - 2020-05-16 - - Replace assert() with DRWAV_ASSERT(). - - Add compile-time and run-time version querying. - - DRWAV_VERSION_MINOR - - DRWAV_VERSION_MAJOR - - DRWAV_VERSION_REVISION - - DRWAV_VERSION_STRING - - drwav_version() - - drwav_version_string() - -v0.12.3 - 2020-04-30 - - Fix compilation errors with VC6. - -v0.12.2 - 2020-04-21 - - Fix a bug where drwav_init_file() does not close the file handle after attempting to load an erroneous file. - -v0.12.1 - 2020-04-13 - - Fix some pedantic warnings. - -v0.12.0 - 2020-04-04 - - API CHANGE: Add container and format parameters to the chunk callback. - - Minor documentation updates. - -v0.11.5 - 2020-03-07 - - Fix compilation error with Visual Studio .NET 2003. - -v0.11.4 - 2020-01-29 - - Fix some static analysis warnings. - - Fix a bug when reading f32 samples from an A-law encoded stream. - -v0.11.3 - 2020-01-12 - - Minor changes to some f32 format conversion routines. - - Minor bug fix for ADPCM conversion when end of file is reached. - -v0.11.2 - 2019-12-02 - - Fix a possible crash when using custom memory allocators without a custom realloc() implementation. - - Fix an integer overflow bug. - - Fix a null pointer dereference bug. - - Add limits to sample rate, channels and bits per sample to tighten up some validation. - -v0.11.1 - 2019-10-07 - - Internal code clean up. - -v0.11.0 - 2019-10-06 - - API CHANGE: Add support for user defined memory allocation routines. This system allows the program to specify their own memory allocation - routines with a user data pointer for client-specific contextual data. This adds an extra parameter to the end of the following APIs: - - drwav_init() - - drwav_init_ex() - - drwav_init_file() - - drwav_init_file_ex() - - drwav_init_file_w() - - drwav_init_file_w_ex() - - drwav_init_memory() - - drwav_init_memory_ex() - - drwav_init_write() - - drwav_init_write_sequential() - - drwav_init_write_sequential_pcm_frames() - - drwav_init_file_write() - - drwav_init_file_write_sequential() - - drwav_init_file_write_sequential_pcm_frames() - - drwav_init_file_write_w() - - drwav_init_file_write_sequential_w() - - drwav_init_file_write_sequential_pcm_frames_w() - - drwav_init_memory_write() - - drwav_init_memory_write_sequential() - - drwav_init_memory_write_sequential_pcm_frames() - - drwav_open_and_read_pcm_frames_s16() - - drwav_open_and_read_pcm_frames_f32() - - drwav_open_and_read_pcm_frames_s32() - - drwav_open_file_and_read_pcm_frames_s16() - - drwav_open_file_and_read_pcm_frames_f32() - - drwav_open_file_and_read_pcm_frames_s32() - - drwav_open_file_and_read_pcm_frames_s16_w() - - drwav_open_file_and_read_pcm_frames_f32_w() - - drwav_open_file_and_read_pcm_frames_s32_w() - - drwav_open_memory_and_read_pcm_frames_s16() - - drwav_open_memory_and_read_pcm_frames_f32() - - drwav_open_memory_and_read_pcm_frames_s32() - Set this extra parameter to NULL to use defaults which is the same as the previous behaviour. Setting this NULL will use - DRWAV_MALLOC, DRWAV_REALLOC and DRWAV_FREE. - - Add support for reading and writing PCM frames in an explicit endianness. New APIs: - - drwav_read_pcm_frames_le() - - drwav_read_pcm_frames_be() - - drwav_read_pcm_frames_s16le() - - drwav_read_pcm_frames_s16be() - - drwav_read_pcm_frames_f32le() - - drwav_read_pcm_frames_f32be() - - drwav_read_pcm_frames_s32le() - - drwav_read_pcm_frames_s32be() - - drwav_write_pcm_frames_le() - - drwav_write_pcm_frames_be() - - Remove deprecated APIs. - - API CHANGE: The following APIs now return native-endian data. Previously they returned little-endian data. - - drwav_read_pcm_frames() - - drwav_read_pcm_frames_s16() - - drwav_read_pcm_frames_s32() - - drwav_read_pcm_frames_f32() - - drwav_open_and_read_pcm_frames_s16() - - drwav_open_and_read_pcm_frames_s32() - - drwav_open_and_read_pcm_frames_f32() - - drwav_open_file_and_read_pcm_frames_s16() - - drwav_open_file_and_read_pcm_frames_s32() - - drwav_open_file_and_read_pcm_frames_f32() - - drwav_open_file_and_read_pcm_frames_s16_w() - - drwav_open_file_and_read_pcm_frames_s32_w() - - drwav_open_file_and_read_pcm_frames_f32_w() - - drwav_open_memory_and_read_pcm_frames_s16() - - drwav_open_memory_and_read_pcm_frames_s32() - - drwav_open_memory_and_read_pcm_frames_f32() - -v0.10.1 - 2019-08-31 - - Correctly handle partial trailing ADPCM blocks. - -v0.10.0 - 2019-08-04 - - Remove deprecated APIs. - - Add wchar_t variants for file loading APIs: - drwav_init_file_w() - drwav_init_file_ex_w() - drwav_init_file_write_w() - drwav_init_file_write_sequential_w() - - Add drwav_target_write_size_bytes() which calculates the total size in bytes of a WAV file given a format and sample count. - - Add APIs for specifying the PCM frame count instead of the sample count when opening in sequential write mode: - drwav_init_write_sequential_pcm_frames() - drwav_init_file_write_sequential_pcm_frames() - drwav_init_file_write_sequential_pcm_frames_w() - drwav_init_memory_write_sequential_pcm_frames() - - Deprecate drwav_open*() and drwav_close(): - drwav_open() - drwav_open_ex() - drwav_open_write() - drwav_open_write_sequential() - drwav_open_file() - drwav_open_file_ex() - drwav_open_file_write() - drwav_open_file_write_sequential() - drwav_open_memory() - drwav_open_memory_ex() - drwav_open_memory_write() - drwav_open_memory_write_sequential() - drwav_close() - - Minor documentation updates. - -v0.9.2 - 2019-05-21 - - Fix warnings. - -v0.9.1 - 2019-05-05 - - Add support for C89. - - Change license to choice of public domain or MIT-0. - -v0.9.0 - 2018-12-16 - - API CHANGE: Add new reading APIs for reading by PCM frames instead of samples. Old APIs have been deprecated and - will be removed in v0.10.0. Deprecated APIs and their replacements: - drwav_read() -> drwav_read_pcm_frames() - drwav_read_s16() -> drwav_read_pcm_frames_s16() - drwav_read_f32() -> drwav_read_pcm_frames_f32() - drwav_read_s32() -> drwav_read_pcm_frames_s32() - drwav_seek_to_sample() -> drwav_seek_to_pcm_frame() - drwav_write() -> drwav_write_pcm_frames() - drwav_open_and_read_s16() -> drwav_open_and_read_pcm_frames_s16() - drwav_open_and_read_f32() -> drwav_open_and_read_pcm_frames_f32() - drwav_open_and_read_s32() -> drwav_open_and_read_pcm_frames_s32() - drwav_open_file_and_read_s16() -> drwav_open_file_and_read_pcm_frames_s16() - drwav_open_file_and_read_f32() -> drwav_open_file_and_read_pcm_frames_f32() - drwav_open_file_and_read_s32() -> drwav_open_file_and_read_pcm_frames_s32() - drwav_open_memory_and_read_s16() -> drwav_open_memory_and_read_pcm_frames_s16() - drwav_open_memory_and_read_f32() -> drwav_open_memory_and_read_pcm_frames_f32() - drwav_open_memory_and_read_s32() -> drwav_open_memory_and_read_pcm_frames_s32() - drwav::totalSampleCount -> drwav::totalPCMFrameCount - - API CHANGE: Rename drwav_open_and_read_file_*() to drwav_open_file_and_read_*(). - - API CHANGE: Rename drwav_open_and_read_memory_*() to drwav_open_memory_and_read_*(). - - Add built-in support for smpl chunks. - - Add support for firing a callback for each chunk in the file at initialization time. - - This is enabled through the drwav_init_ex(), etc. family of APIs. - - Handle invalid FMT chunks more robustly. - -v0.8.5 - 2018-09-11 - - Const correctness. - - Fix a potential stack overflow. - -v0.8.4 - 2018-08-07 - - Improve 64-bit detection. - -v0.8.3 - 2018-08-05 - - Fix C++ build on older versions of GCC. - -v0.8.2 - 2018-08-02 - - Fix some big-endian bugs. - -v0.8.1 - 2018-06-29 - - Add support for sequential writing APIs. - - Disable seeking in write mode. - - Fix bugs with Wave64. - - Fix typos. - -v0.8 - 2018-04-27 - - Bug fix. - - Start using major.minor.revision versioning. - -v0.7f - 2018-02-05 - - Restrict ADPCM formats to a maximum of 2 channels. - -v0.7e - 2018-02-02 - - Fix a crash. - -v0.7d - 2018-02-01 - - Fix a crash. - -v0.7c - 2018-02-01 - - Set drwav.bytesPerSample to 0 for all compressed formats. - - Fix a crash when reading 16-bit floating point WAV files. In this case dr_wav will output silence for - all format conversion reading APIs (*_s16, *_s32, *_f32 APIs). - - Fix some divide-by-zero errors. - -v0.7b - 2018-01-22 - - Fix errors with seeking of compressed formats. - - Fix compilation error when DR_WAV_NO_CONVERSION_API - -v0.7a - 2017-11-17 - - Fix some GCC warnings. - -v0.7 - 2017-11-04 - - Add writing APIs. - -v0.6 - 2017-08-16 - - API CHANGE: Rename dr_* types to drwav_*. - - Add support for custom implementations of malloc(), realloc(), etc. - - Add support for Microsoft ADPCM. - - Add support for IMA ADPCM (DVI, format code 0x11). - - Optimizations to drwav_read_s16(). - - Bug fixes. - -v0.5g - 2017-07-16 - - Change underlying type for booleans to unsigned. - -v0.5f - 2017-04-04 - - Fix a minor bug with drwav_open_and_read_s16() and family. - -v0.5e - 2016-12-29 - - Added support for reading samples as signed 16-bit integers. Use the _s16() family of APIs for this. - - Minor fixes to documentation. - -v0.5d - 2016-12-28 - - Use drwav_int* and drwav_uint* sized types to improve compiler support. - -v0.5c - 2016-11-11 - - Properly handle JUNK chunks that come before the FMT chunk. - -v0.5b - 2016-10-23 - - A minor change to drwav_bool8 and drwav_bool32 types. - -v0.5a - 2016-10-11 - - Fixed a bug with drwav_open_and_read() and family due to incorrect argument ordering. - - Improve A-law and mu-law efficiency. - -v0.5 - 2016-09-29 - - API CHANGE. Swap the order of "channels" and "sampleRate" parameters in drwav_open_and_read*(). Rationale for this is to - keep it consistent with dr_audio and dr_flac. - -v0.4b - 2016-09-18 - - Fixed a typo in documentation. - -v0.4a - 2016-09-18 - - Fixed a typo. - - Change date format to ISO 8601 (YYYY-MM-DD) - -v0.4 - 2016-07-13 - - API CHANGE. Make onSeek consistent with dr_flac. - - API CHANGE. Rename drwav_seek() to drwav_seek_to_sample() for clarity and consistency with dr_flac. - - Added support for Sony Wave64. - -v0.3a - 2016-05-28 - - API CHANGE. Return drwav_bool32 instead of int in onSeek callback. - - Fixed a memory leak. - -v0.3 - 2016-05-22 - - Lots of API changes for consistency. - -v0.2a - 2016-05-16 - - Fixed Linux/GCC build. - -v0.2 - 2016-05-11 - - Added support for reading data as signed 32-bit PCM for consistency with dr_flac. - -v0.1a - 2016-05-07 - - Fixed a bug in drwav_open_file() where the file handle would not be closed if the loader failed to initialize. - -v0.1 - 2016-05-04 - - Initial versioned release. -*/ - -/* -This software is available as a choice of the following licenses. Choose -whichever you prefer. - -=============================================================================== -ALTERNATIVE 1 - Public Domain (www.unlicense.org) -=============================================================================== -This is free and unencumbered software released into the public domain. - -Anyone is free to copy, modify, publish, use, compile, sell, or distribute this -software, either in source code form or as a compiled binary, for any purpose, -commercial or non-commercial, and by any means. - -In jurisdictions that recognize copyright laws, the author or authors of this -software dedicate any and all copyright interest in the software to the public -domain. We make this dedication for the benefit of the public at large and to -the detriment of our heirs and successors. We intend this dedication to be an -overt act of relinquishment in perpetuity of all present and future rights to -this software under copyright law. - -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 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. - -For more information, please refer to - -=============================================================================== -ALTERNATIVE 2 - MIT No Attribution -=============================================================================== -Copyright 2020 David Reid - -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. - -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. -*/ \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/metal-cpp/LICENSE.txt b/app/jni/src/libultraship/extern/metal-cpp/LICENSE.txt deleted file mode 100644 index 5e743c6..0000000 --- a/app/jni/src/libultraship/extern/metal-cpp/LICENSE.txt +++ /dev/null @@ -1,202 +0,0 @@ - - Apache License - Version 2.0, January 2004 - http://www.apache.org/licenses/ - - TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION - - 1. Definitions. - - "License" shall mean the terms and conditions for use, reproduction, - and distribution as defined by Sections 1 through 9 of this document. - - "Licensor" shall mean the copyright owner or entity authorized by - the copyright owner that is granting the License. - - "Legal Entity" shall mean the union of the acting entity and all - other entities that control, are controlled by, or are under common - control with that entity. For the purposes of this definition, - "control" means (i) the power, direct or indirect, to cause the - direction or management of such entity, whether by contract or - otherwise, or (ii) ownership of fifty percent (50%) or more of the - outstanding shares, or (iii) beneficial ownership of such entity. - - "You" (or "Your") shall mean an individual or Legal Entity - exercising permissions granted by this License. - - "Source" form shall mean the preferred form for making modifications, - including but not limited to software source code, documentation - source, and configuration files. - - "Object" form shall mean any form resulting from mechanical - transformation or translation of a Source form, including but - not limited to compiled object code, generated documentation, - and conversions to other media types. - - "Work" shall mean the work of authorship, whether in Source or - Object form, made available under the License, as indicated by a - copyright notice that is included in or attached to the work - (an example is provided in the Appendix below). - - "Derivative Works" shall mean any work, whether in Source or Object - form, that is based on (or derived from) the Work and for which the - editorial revisions, annotations, elaborations, or other modifications - represent, as a whole, an original work of authorship. For the purposes - of this License, Derivative Works shall not include works that remain - separable from, or merely link (or bind by name) to the interfaces of, - the Work and Derivative Works thereof. - - "Contribution" shall mean any work of authorship, including - the original version of the Work and any modifications or additions - to that Work or Derivative Works thereof, that is intentionally - submitted to Licensor for inclusion in the Work by the copyright owner - or by an individual or Legal Entity authorized to submit on behalf of - the copyright owner. For the purposes of this definition, "submitted" - means any form of electronic, verbal, or written communication sent - to the Licensor or its representatives, including but not limited to - communication on electronic mailing lists, source code control systems, - and issue tracking systems that are managed by, or on behalf of, the - Licensor for the purpose of discussing and improving the Work, but - excluding communication that is conspicuously marked or otherwise - designated in writing by the copyright owner as "Not a Contribution." - - "Contributor" shall mean Licensor and any individual or Legal Entity - on behalf of whom a Contribution has been received by Licensor and - subsequently incorporated within the Work. - - 2. Grant of Copyright License. Subject to the terms and conditions of - this License, each Contributor hereby grants to You a perpetual, - worldwide, non-exclusive, no-charge, royalty-free, irrevocable - copyright license to reproduce, prepare Derivative Works of, - publicly display, publicly perform, sublicense, and distribute the - Work and such Derivative Works in Source or Object form. - - 3. Grant of Patent License. Subject to the terms and conditions of - this License, each Contributor hereby grants to You a perpetual, - worldwide, non-exclusive, no-charge, royalty-free, irrevocable - (except as stated in this section) patent license to make, have made, - use, offer to sell, sell, import, and otherwise transfer the Work, - where such license applies only to those patent claims licensable - by such Contributor that are necessarily infringed by their - Contribution(s) alone or by combination of their Contribution(s) - with the Work to which such Contribution(s) was submitted. If You - institute patent litigation against any entity (including a - cross-claim or counterclaim in a lawsuit) alleging that the Work - or a Contribution incorporated within the Work constitutes direct - or contributory patent infringement, then any patent licenses - granted to You under this License for that Work shall terminate - as of the date such litigation is filed. - - 4. Redistribution. You may reproduce and distribute copies of the - Work or Derivative Works thereof in any medium, with or without - modifications, and in Source or Object form, provided that You - meet the following conditions: - - (a) You must give any other recipients of the Work or - Derivative Works a copy of this License; and - - (b) You must cause any modified files to carry prominent notices - stating that You changed the files; and - - (c) You must retain, in the Source form of any Derivative Works - that You distribute, all copyright, patent, trademark, and - attribution notices from the Source form of the Work, - excluding those notices that do not pertain to any part of - the Derivative Works; and - - (d) If the Work includes a "NOTICE" text file as part of its - distribution, then any Derivative Works that You distribute must - include a readable copy of the attribution notices contained - within such NOTICE file, excluding those notices that do not - pertain to any part of the Derivative Works, in at least one - of the following places: within a NOTICE text file distributed - as part of the Derivative Works; within the Source form or - documentation, if provided along with the Derivative Works; or, - within a display generated by the Derivative Works, if and - wherever such third-party notices normally appear. The contents - of the NOTICE file are for informational purposes only and - do not modify the License. You may add Your own attribution - notices within Derivative Works that You distribute, alongside - or as an addendum to the NOTICE text from the Work, provided - that such additional attribution notices cannot be construed - as modifying the License. - - You may add Your own copyright statement to Your modifications and - may provide additional or different license terms and conditions - for use, reproduction, or distribution of Your modifications, or - for any such Derivative Works as a whole, provided Your use, - reproduction, and distribution of the Work otherwise complies with - the conditions stated in this License. - - 5. Submission of Contributions. Unless You explicitly state otherwise, - any Contribution intentionally submitted for inclusion in the Work - by You to the Licensor shall be under the terms and conditions of - this License, without any additional terms or conditions. - Notwithstanding the above, nothing herein shall supersede or modify - the terms of any separate license agreement you may have executed - with Licensor regarding such Contributions. - - 6. Trademarks. This License does not grant permission to use the trade - names, trademarks, service marks, or product names of the Licensor, - except as required for reasonable and customary use in describing the - origin of the Work and reproducing the content of the NOTICE file. - - 7. Disclaimer of Warranty. Unless required by applicable law or - agreed to in writing, Licensor provides the Work (and each - Contributor provides its Contributions) on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or - implied, including, without limitation, any warranties or conditions - of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A - PARTICULAR PURPOSE. You are solely responsible for determining the - appropriateness of using or redistributing the Work and assume any - risks associated with Your exercise of permissions under this License. - - 8. Limitation of Liability. In no event and under no legal theory, - whether in tort (including negligence), contract, or otherwise, - unless required by applicable law (such as deliberate and grossly - negligent acts) or agreed to in writing, shall any Contributor be - liable to You for damages, including any direct, indirect, special, - incidental, or consequential damages of any character arising as a - result of this License or out of the use or inability to use the - Work (including but not limited to damages for loss of goodwill, - work stoppage, computer failure or malfunction, or any and all - other commercial damages or losses), even if such Contributor - has been advised of the possibility of such damages. - - 9. Accepting Warranty or Additional Liability. While redistributing - the Work or Derivative Works thereof, You may choose to offer, - and charge a fee for, acceptance of support, warranty, indemnity, - or other liability obligations and/or rights consistent with this - License. However, in accepting such obligations, You may act only - on Your own behalf and on Your sole responsibility, not on behalf - of any other Contributor, and only if You agree to indemnify, - defend, and hold each Contributor harmless for any liability - incurred by, or claims asserted against, such Contributor by reason - of your accepting any such warranty or additional liability. - - END OF TERMS AND CONDITIONS - - APPENDIX: How to apply the Apache License to your work. - - To apply the Apache License to your work, attach the following - boilerplate notice, with the fields enclosed by brackets "[]" - replaced with your own identifying information. (Don't include - the brackets!) The text should be enclosed in the appropriate - comment syntax for the file format. We also recommend that a - file or class name and description of purpose be included on the - same "printed page" as the copyright notice for easier - identification within third-party archives. - - Copyright © 2021 Apple Inc. - - Licensed under the Apache License, Version 2.0 (the "License"); - you may not use this file except in compliance with the License. - You may obtain a copy of the License at - - http://www.apache.org/licenses/LICENSE-2.0 - - Unless required by applicable law or agreed to in writing, software - distributed under the License is distributed on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - See the License for the specific language governing permissions and - limitations under the License. diff --git a/app/jni/src/libultraship/extern/metal-cpp/Metal/Metal.hpp b/app/jni/src/libultraship/extern/metal-cpp/Metal/Metal.hpp deleted file mode 100644 index 40d9e2a..0000000 --- a/app/jni/src/libultraship/extern/metal-cpp/Metal/Metal.hpp +++ /dev/null @@ -1,19559 +0,0 @@ -// -// Metal.hpp -// -// Autogenerated on January 21, 2023. -// -// Copyright 2020-2022 Apple Inc. -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. -// - -#pragma once - -#define _NS_WEAK_IMPORT __attribute__((weak_import)) -#ifdef METALCPP_SYMBOL_VISIBILITY_HIDDEN -#define _NS_EXPORT __attribute__((visibility("hidden"))) -#else -#define _NS_EXPORT __attribute__((visibility("default"))) -#endif // METALCPP_SYMBOL_VISIBILITY_HIDDEN -#define _NS_EXTERN extern "C" _NS_EXPORT -#define _NS_INLINE inline __attribute__((always_inline)) -#define _NS_PACKED __attribute__((packed)) - -#define _NS_CONST(type, name) _NS_EXTERN type const name -#define _NS_ENUM(type, name) enum name : type -#define _NS_OPTIONS(type, name) \ - using name = type; \ - enum : name - -#define _NS_CAST_TO_UINT(value) static_cast(value) -#define _NS_VALIDATE_SIZE(ns, name) static_assert(sizeof(ns::name) == sizeof(ns##name), "size mismatch " #ns "::" #name) -#define _NS_VALIDATE_ENUM(ns, name) static_assert(_NS_CAST_TO_UINT(ns::name) == _NS_CAST_TO_UINT(ns##name), "value mismatch " #ns "::" #name) - -#include - -#define _NS_PRIVATE_CLS(symbol) (Private::Class::s_k##symbol) -#define _NS_PRIVATE_SEL(accessor) (Private::Selector::s_k##accessor) - -#if defined(NS_PRIVATE_IMPLEMENTATION) - -#ifdef METALCPP_SYMBOL_VISIBILITY_HIDDEN -#define _NS_PRIVATE_VISIBILITY __attribute__((visibility("hidden"))) -#else -#define _NS_PRIVATE_VISIBILITY __attribute__((visibility("default"))) -#endif //METALCPP_SYMBOL_VISIBILITY_HIDDEN - -#define _NS_PRIVATE_IMPORT __attribute__((weak_import)) - -#ifdef __OBJC__ -#define _NS_PRIVATE_OBJC_LOOKUP_CLASS(symbol) ((__bridge void*)objc_lookUpClass(#symbol)) -#define _NS_PRIVATE_OBJC_GET_PROTOCOL(symbol) ((__bridge void*)objc_getProtocol(#symbol)) -#else -#define _NS_PRIVATE_OBJC_LOOKUP_CLASS(symbol) objc_lookUpClass(#symbol) -#define _NS_PRIVATE_OBJC_GET_PROTOCOL(symbol) objc_getProtocol(#symbol) -#endif // __OBJC__ - -#define _NS_PRIVATE_DEF_CLS(symbol) void* s_k##symbol _NS_PRIVATE_VISIBILITY = _NS_PRIVATE_OBJC_LOOKUP_CLASS(symbol) -#define _NS_PRIVATE_DEF_PRO(symbol) void* s_k##symbol _NS_PRIVATE_VISIBILITY = _NS_PRIVATE_OBJC_GET_PROTOCOL(symbol) -#define _NS_PRIVATE_DEF_SEL(accessor, symbol) SEL s_k##accessor _NS_PRIVATE_VISIBILITY = sel_registerName(symbol) -#define _NS_PRIVATE_DEF_CONST(type, symbol) \ - _NS_EXTERN type const NS##symbol _NS_PRIVATE_IMPORT; \ - type const NS::symbol = (nullptr != &NS##symbol) ? NS##symbol : nullptr - -#else - -#define _NS_PRIVATE_DEF_CLS(symbol) extern void* s_k##symbol -#define _NS_PRIVATE_DEF_PRO(symbol) extern void* s_k##symbol -#define _NS_PRIVATE_DEF_SEL(accessor, symbol) extern SEL s_k##accessor -#define _NS_PRIVATE_DEF_CONST(type, symbol) extern type const NS::symbol - -#endif // NS_PRIVATE_IMPLEMENTATION - -namespace NS -{ -namespace Private -{ - namespace Class - { - - _NS_PRIVATE_DEF_CLS(NSArray); - _NS_PRIVATE_DEF_CLS(NSAutoreleasePool); - _NS_PRIVATE_DEF_CLS(NSBundle); - _NS_PRIVATE_DEF_CLS(NSCondition); - _NS_PRIVATE_DEF_CLS(NSDate); - _NS_PRIVATE_DEF_CLS(NSDictionary); - _NS_PRIVATE_DEF_CLS(NSError); - _NS_PRIVATE_DEF_CLS(NSNotificationCenter); - _NS_PRIVATE_DEF_CLS(NSNumber); - _NS_PRIVATE_DEF_CLS(NSObject); - _NS_PRIVATE_DEF_CLS(NSProcessInfo); - _NS_PRIVATE_DEF_CLS(NSSet); - _NS_PRIVATE_DEF_CLS(NSString); - _NS_PRIVATE_DEF_CLS(NSURL); - _NS_PRIVATE_DEF_CLS(NSValue); - - } // Class -} // Private -} // MTL - -namespace NS -{ -namespace Private -{ - namespace Protocol - { - - } // Protocol -} // Private -} // NS - -namespace NS -{ -namespace Private -{ - namespace Selector - { - - _NS_PRIVATE_DEF_SEL(addObject_, - "addObject:"); - _NS_PRIVATE_DEF_SEL(addObserverName_object_queue_block_, - "addObserverForName:object:queue:usingBlock:"); - _NS_PRIVATE_DEF_SEL(activeProcessorCount, - "activeProcessorCount"); - _NS_PRIVATE_DEF_SEL(allBundles, - "allBundles"); - _NS_PRIVATE_DEF_SEL(allFrameworks, - "allFrameworks"); - _NS_PRIVATE_DEF_SEL(allObjects, - "allObjects"); - _NS_PRIVATE_DEF_SEL(alloc, - "alloc"); - _NS_PRIVATE_DEF_SEL(appStoreReceiptURL, - "appStoreReceiptURL"); - _NS_PRIVATE_DEF_SEL(arguments, - "arguments"); - _NS_PRIVATE_DEF_SEL(array, - "array"); - _NS_PRIVATE_DEF_SEL(arrayWithObject_, - "arrayWithObject:"); - _NS_PRIVATE_DEF_SEL(arrayWithObjects_count_, - "arrayWithObjects:count:"); - _NS_PRIVATE_DEF_SEL(automaticTerminationSupportEnabled, - "automaticTerminationSupportEnabled"); - _NS_PRIVATE_DEF_SEL(autorelease, - "autorelease"); - _NS_PRIVATE_DEF_SEL(beginActivityWithOptions_reason_, - "beginActivityWithOptions:reason:"); - _NS_PRIVATE_DEF_SEL(boolValue, - "boolValue"); - _NS_PRIVATE_DEF_SEL(broadcast, - "broadcast"); - _NS_PRIVATE_DEF_SEL(builtInPlugInsPath, - "builtInPlugInsPath"); - _NS_PRIVATE_DEF_SEL(builtInPlugInsURL, - "builtInPlugInsURL"); - _NS_PRIVATE_DEF_SEL(bundleIdentifier, - "bundleIdentifier"); - _NS_PRIVATE_DEF_SEL(bundlePath, - "bundlePath"); - _NS_PRIVATE_DEF_SEL(bundleURL, - "bundleURL"); - _NS_PRIVATE_DEF_SEL(bundleWithPath_, - "bundleWithPath:"); - _NS_PRIVATE_DEF_SEL(bundleWithURL_, - "bundleWithURL:"); - _NS_PRIVATE_DEF_SEL(characterAtIndex_, - "characterAtIndex:"); - _NS_PRIVATE_DEF_SEL(charValue, - "charValue"); - _NS_PRIVATE_DEF_SEL(countByEnumeratingWithState_objects_count_, - "countByEnumeratingWithState:objects:count:"); - _NS_PRIVATE_DEF_SEL(cStringUsingEncoding_, - "cStringUsingEncoding:"); - _NS_PRIVATE_DEF_SEL(code, - "code"); - _NS_PRIVATE_DEF_SEL(compare_, - "compare:"); - _NS_PRIVATE_DEF_SEL(copy, - "copy"); - _NS_PRIVATE_DEF_SEL(count, - "count"); - _NS_PRIVATE_DEF_SEL(dateWithTimeIntervalSinceNow_, - "dateWithTimeIntervalSinceNow:"); - _NS_PRIVATE_DEF_SEL(defaultCenter, - "defaultCenter"); - _NS_PRIVATE_DEF_SEL(descriptionWithLocale_, - "descriptionWithLocale:"); - _NS_PRIVATE_DEF_SEL(disableAutomaticTermination_, - "disableAutomaticTermination:"); - _NS_PRIVATE_DEF_SEL(disableSuddenTermination, - "disableSuddenTermination"); - _NS_PRIVATE_DEF_SEL(debugDescription, - "debugDescription"); - _NS_PRIVATE_DEF_SEL(description, - "description"); - _NS_PRIVATE_DEF_SEL(dictionary, - "dictionary"); - _NS_PRIVATE_DEF_SEL(dictionaryWithObject_forKey_, - "dictionaryWithObject:forKey:"); - _NS_PRIVATE_DEF_SEL(dictionaryWithObjects_forKeys_count_, - "dictionaryWithObjects:forKeys:count:"); - _NS_PRIVATE_DEF_SEL(domain, - "domain"); - _NS_PRIVATE_DEF_SEL(doubleValue, - "doubleValue"); - _NS_PRIVATE_DEF_SEL(drain, - "drain"); - _NS_PRIVATE_DEF_SEL(enableAutomaticTermination_, - "enableAutomaticTermination:"); - _NS_PRIVATE_DEF_SEL(enableSuddenTermination, - "enableSuddenTermination"); - _NS_PRIVATE_DEF_SEL(endActivity_, - "endActivity:"); - _NS_PRIVATE_DEF_SEL(environment, - "environment"); - _NS_PRIVATE_DEF_SEL(errorWithDomain_code_userInfo_, - "errorWithDomain:code:userInfo:"); - _NS_PRIVATE_DEF_SEL(executablePath, - "executablePath"); - _NS_PRIVATE_DEF_SEL(executableURL, - "executableURL"); - _NS_PRIVATE_DEF_SEL(fileSystemRepresentation, - "fileSystemRepresentation"); - _NS_PRIVATE_DEF_SEL(fileURLWithPath_, - "fileURLWithPath:"); - _NS_PRIVATE_DEF_SEL(floatValue, - "floatValue"); - _NS_PRIVATE_DEF_SEL(fullUserName, - "fullUserName"); - _NS_PRIVATE_DEF_SEL(getValue_size_, - "getValue:size:"); - _NS_PRIVATE_DEF_SEL(globallyUniqueString, - "globallyUniqueString"); - _NS_PRIVATE_DEF_SEL(hash, - "hash"); - _NS_PRIVATE_DEF_SEL(hostName, - "hostName"); - _NS_PRIVATE_DEF_SEL(infoDictionary, - "infoDictionary"); - _NS_PRIVATE_DEF_SEL(init, - "init"); - _NS_PRIVATE_DEF_SEL(initFileURLWithPath_, - "initFileURLWithPath:"); - _NS_PRIVATE_DEF_SEL(initWithBool_, - "initWithBool:"); - _NS_PRIVATE_DEF_SEL(initWithBytes_objCType_, - "initWithBytes:objCType:"); - _NS_PRIVATE_DEF_SEL(initWithBytesNoCopy_length_encoding_freeWhenDone_, - "initWithBytesNoCopy:length:encoding:freeWhenDone:"); - _NS_PRIVATE_DEF_SEL(initWithChar_, - "initWithChar:"); - _NS_PRIVATE_DEF_SEL(initWithCoder_, - "initWithCoder:"); - _NS_PRIVATE_DEF_SEL(initWithCString_encoding_, - "initWithCString:encoding:"); - _NS_PRIVATE_DEF_SEL(initWithDomain_code_userInfo_, - "initWithDomain:code:userInfo:"); - _NS_PRIVATE_DEF_SEL(initWithDouble_, - "initWithDouble:"); - _NS_PRIVATE_DEF_SEL(initWithFloat_, - "initWithFloat:"); - _NS_PRIVATE_DEF_SEL(initWithInt_, - "initWithInt:"); - _NS_PRIVATE_DEF_SEL(initWithLong_, - "initWithLong:"); - _NS_PRIVATE_DEF_SEL(initWithLongLong_, - "initWithLongLong:"); - _NS_PRIVATE_DEF_SEL(initWithObjects_count_, - "initWithObjects:count:"); - _NS_PRIVATE_DEF_SEL(initWithObjects_forKeys_count_, - "initWithObjects:forKeys:count:"); - _NS_PRIVATE_DEF_SEL(initWithPath_, - "initWithPath:"); - _NS_PRIVATE_DEF_SEL(initWithShort_, - "initWithShort:"); - _NS_PRIVATE_DEF_SEL(initWithString_, - "initWithString:"); - _NS_PRIVATE_DEF_SEL(initWithUnsignedChar_, - "initWithUnsignedChar:"); - _NS_PRIVATE_DEF_SEL(initWithUnsignedInt_, - "initWithUnsignedInt:"); - _NS_PRIVATE_DEF_SEL(initWithUnsignedLong_, - "initWithUnsignedLong:"); - _NS_PRIVATE_DEF_SEL(initWithUnsignedLongLong_, - "initWithUnsignedLongLong:"); - _NS_PRIVATE_DEF_SEL(initWithUnsignedShort_, - "initWithUnsignedShort:"); - _NS_PRIVATE_DEF_SEL(initWithURL_, - "initWithURL:"); - _NS_PRIVATE_DEF_SEL(integerValue, - "integerValue"); - _NS_PRIVATE_DEF_SEL(intValue, - "intValue"); - _NS_PRIVATE_DEF_SEL(isEqual_, - "isEqual:"); - _NS_PRIVATE_DEF_SEL(isEqualToNumber_, - "isEqualToNumber:"); - _NS_PRIVATE_DEF_SEL(isEqualToString_, - "isEqualToString:"); - _NS_PRIVATE_DEF_SEL(isEqualToValue_, - "isEqualToValue:"); - _NS_PRIVATE_DEF_SEL(isiOSAppOnMac, - "isiOSAppOnMac"); - _NS_PRIVATE_DEF_SEL(isLoaded, - "isLoaded"); - _NS_PRIVATE_DEF_SEL(isLowPowerModeEnabled, - "isLowPowerModeEnabled"); - _NS_PRIVATE_DEF_SEL(isMacCatalystApp, - "isMacCatalystApp"); - _NS_PRIVATE_DEF_SEL(isOperatingSystemAtLeastVersion_, - "isOperatingSystemAtLeastVersion:"); - _NS_PRIVATE_DEF_SEL(keyEnumerator, - "keyEnumerator"); - _NS_PRIVATE_DEF_SEL(length, - "length"); - _NS_PRIVATE_DEF_SEL(lengthOfBytesUsingEncoding_, - "lengthOfBytesUsingEncoding:"); - _NS_PRIVATE_DEF_SEL(load, - "load"); - _NS_PRIVATE_DEF_SEL(loadAndReturnError_, - "loadAndReturnError:"); - _NS_PRIVATE_DEF_SEL(localizedDescription, - "localizedDescription"); - _NS_PRIVATE_DEF_SEL(localizedFailureReason, - "localizedFailureReason"); - _NS_PRIVATE_DEF_SEL(localizedInfoDictionary, - "localizedInfoDictionary"); - _NS_PRIVATE_DEF_SEL(localizedRecoveryOptions, - "localizedRecoveryOptions"); - _NS_PRIVATE_DEF_SEL(localizedRecoverySuggestion, - "localizedRecoverySuggestion"); - _NS_PRIVATE_DEF_SEL(localizedStringForKey_value_table_, - "localizedStringForKey:value:table:"); - _NS_PRIVATE_DEF_SEL(lock, - "lock"); - _NS_PRIVATE_DEF_SEL(longValue, - "longValue"); - _NS_PRIVATE_DEF_SEL(longLongValue, - "longLongValue"); - _NS_PRIVATE_DEF_SEL(mainBundle, - "mainBundle"); - _NS_PRIVATE_DEF_SEL(maximumLengthOfBytesUsingEncoding_, - "maximumLengthOfBytesUsingEncoding:"); - _NS_PRIVATE_DEF_SEL(methodSignatureForSelector_, - "methodSignatureForSelector:"); - _NS_PRIVATE_DEF_SEL(mutableBytes, - "mutableBytes"); - _NS_PRIVATE_DEF_SEL(name, - "name"); - _NS_PRIVATE_DEF_SEL(nextObject, - "nextObject"); - _NS_PRIVATE_DEF_SEL(numberWithBool_, - "numberWithBool:"); - _NS_PRIVATE_DEF_SEL(numberWithChar_, - "numberWithChar:"); - _NS_PRIVATE_DEF_SEL(numberWithDouble_, - "numberWithDouble:"); - _NS_PRIVATE_DEF_SEL(numberWithFloat_, - "numberWithFloat:"); - _NS_PRIVATE_DEF_SEL(numberWithInt_, - "numberWithInt:"); - _NS_PRIVATE_DEF_SEL(numberWithLong_, - "numberWithLong:"); - _NS_PRIVATE_DEF_SEL(numberWithLongLong_, - "numberWithLongLong:"); - _NS_PRIVATE_DEF_SEL(numberWithShort_, - "numberWithShort:"); - _NS_PRIVATE_DEF_SEL(numberWithUnsignedChar_, - "numberWithUnsignedChar:"); - _NS_PRIVATE_DEF_SEL(numberWithUnsignedInt_, - "numberWithUnsignedInt:"); - _NS_PRIVATE_DEF_SEL(numberWithUnsignedLong_, - "numberWithUnsignedLong:"); - _NS_PRIVATE_DEF_SEL(numberWithUnsignedLongLong_, - "numberWithUnsignedLongLong:"); - _NS_PRIVATE_DEF_SEL(numberWithUnsignedShort_, - "numberWithUnsignedShort:"); - _NS_PRIVATE_DEF_SEL(objCType, - "objCType"); - _NS_PRIVATE_DEF_SEL(object, - "object"); - _NS_PRIVATE_DEF_SEL(objectAtIndex_, - "objectAtIndex:"); - _NS_PRIVATE_DEF_SEL(objectEnumerator, - "objectEnumerator"); - _NS_PRIVATE_DEF_SEL(objectForInfoDictionaryKey_, - "objectForInfoDictionaryKey:"); - _NS_PRIVATE_DEF_SEL(objectForKey_, - "objectForKey:"); - _NS_PRIVATE_DEF_SEL(operatingSystem, - "operatingSystem"); - _NS_PRIVATE_DEF_SEL(operatingSystemVersion, - "operatingSystemVersion"); - _NS_PRIVATE_DEF_SEL(operatingSystemVersionString, - "operatingSystemVersionString"); - _NS_PRIVATE_DEF_SEL(pathForAuxiliaryExecutable_, - "pathForAuxiliaryExecutable:"); - _NS_PRIVATE_DEF_SEL(performActivityWithOptions_reason_usingBlock_, - "performActivityWithOptions:reason:usingBlock:"); - _NS_PRIVATE_DEF_SEL(performExpiringActivityWithReason_usingBlock_, - "performExpiringActivityWithReason:usingBlock:"); - _NS_PRIVATE_DEF_SEL(physicalMemory, - "physicalMemory"); - _NS_PRIVATE_DEF_SEL(pointerValue, - "pointerValue"); - _NS_PRIVATE_DEF_SEL(preflightAndReturnError_, - "preflightAndReturnError:"); - _NS_PRIVATE_DEF_SEL(privateFrameworksPath, - "privateFrameworksPath"); - _NS_PRIVATE_DEF_SEL(privateFrameworksURL, - "privateFrameworksURL"); - _NS_PRIVATE_DEF_SEL(processIdentifier, - "processIdentifier"); - _NS_PRIVATE_DEF_SEL(processInfo, - "processInfo"); - _NS_PRIVATE_DEF_SEL(processName, - "processName"); - _NS_PRIVATE_DEF_SEL(processorCount, - "processorCount"); - _NS_PRIVATE_DEF_SEL(rangeOfString_options_, - "rangeOfString:options:"); - _NS_PRIVATE_DEF_SEL(release, - "release"); - _NS_PRIVATE_DEF_SEL(removeObserver_, - "removeObserver:"); - _NS_PRIVATE_DEF_SEL(resourcePath, - "resourcePath"); - _NS_PRIVATE_DEF_SEL(resourceURL, - "resourceURL"); - _NS_PRIVATE_DEF_SEL(respondsToSelector_, - "respondsToSelector:"); - _NS_PRIVATE_DEF_SEL(retain, - "retain"); - _NS_PRIVATE_DEF_SEL(retainCount, - "retainCount"); - _NS_PRIVATE_DEF_SEL(setAutomaticTerminationSupportEnabled_, - "setAutomaticTerminationSupportEnabled:"); - _NS_PRIVATE_DEF_SEL(setProcessName_, - "setProcessName:"); - _NS_PRIVATE_DEF_SEL(sharedFrameworksPath, - "sharedFrameworksPath"); - _NS_PRIVATE_DEF_SEL(sharedFrameworksURL, - "sharedFrameworksURL"); - _NS_PRIVATE_DEF_SEL(sharedSupportPath, - "sharedSupportPath"); - _NS_PRIVATE_DEF_SEL(sharedSupportURL, - "sharedSupportURL"); - _NS_PRIVATE_DEF_SEL(shortValue, - "shortValue"); - _NS_PRIVATE_DEF_SEL(showPools, - "showPools"); - _NS_PRIVATE_DEF_SEL(signal, - "signal"); - _NS_PRIVATE_DEF_SEL(string, - "string"); - _NS_PRIVATE_DEF_SEL(stringValue, - "stringValue"); - _NS_PRIVATE_DEF_SEL(stringWithString_, - "stringWithString:"); - _NS_PRIVATE_DEF_SEL(stringWithCString_encoding_, - "stringWithCString:encoding:"); - _NS_PRIVATE_DEF_SEL(stringByAppendingString_, - "stringByAppendingString:"); - _NS_PRIVATE_DEF_SEL(systemUptime, - "systemUptime"); - _NS_PRIVATE_DEF_SEL(thermalState, - "thermalState"); - _NS_PRIVATE_DEF_SEL(unload, - "unload"); - _NS_PRIVATE_DEF_SEL(unlock, - "unlock"); - _NS_PRIVATE_DEF_SEL(unsignedCharValue, - "unsignedCharValue"); - _NS_PRIVATE_DEF_SEL(unsignedIntegerValue, - "unsignedIntegerValue"); - _NS_PRIVATE_DEF_SEL(unsignedIntValue, - "unsignedIntValue"); - _NS_PRIVATE_DEF_SEL(unsignedLongValue, - "unsignedLongValue"); - _NS_PRIVATE_DEF_SEL(unsignedLongLongValue, - "unsignedLongLongValue"); - _NS_PRIVATE_DEF_SEL(unsignedShortValue, - "unsignedShortValue"); - _NS_PRIVATE_DEF_SEL(URLForAuxiliaryExecutable_, - "URLForAuxiliaryExecutable:"); - _NS_PRIVATE_DEF_SEL(userInfo, - "userInfo"); - _NS_PRIVATE_DEF_SEL(userName, - "userName"); - _NS_PRIVATE_DEF_SEL(UTF8String, - "UTF8String"); - _NS_PRIVATE_DEF_SEL(valueWithBytes_objCType_, - "valueWithBytes:objCType:"); - _NS_PRIVATE_DEF_SEL(valueWithPointer_, - "valueWithPointer:"); - _NS_PRIVATE_DEF_SEL(wait, - "wait"); - _NS_PRIVATE_DEF_SEL(waitUntilDate_, - "waitUntilDate:"); - } // Class -} // Private -} // MTL - -#include -#include - -namespace NS -{ -using TimeInterval = double; - -using Integer = std::intptr_t; -using UInteger = std::uintptr_t; - -const Integer IntegerMax = INTPTR_MAX; -const Integer IntegerMin = INTPTR_MIN; -const UInteger UIntegerMax = UINTPTR_MAX; - -struct OperatingSystemVersion -{ - Integer majorVersion; - Integer minorVersion; - Integer patchVersion; -} _NS_PACKED; -} - -#include -#include - -#include - -namespace NS -{ -template -class _NS_EXPORT Referencing : public _Base -{ -public: - _Class* retain(); - void release(); - - _Class* autorelease(); - - UInteger retainCount() const; -}; - -template -class Copying : public Referencing<_Class, _Base> -{ -public: - _Class* copy() const; -}; - -template -class SecureCoding : public Referencing<_Class, _Base> -{ -}; - -class Object : public Referencing -{ -public: - UInteger hash() const; - bool isEqual(const Object* pObject) const; - - class String* description() const; - class String* debugDescription() const; - -protected: - friend class Referencing; - - template - static _Class* alloc(const char* pClassName); - template - static _Class* alloc(const void* pClass); - template - _Class* init(); - - template - static _Dst bridgingCast(const void* pObj); - static class MethodSignature* methodSignatureForSelector(const void* pObj, SEL selector); - static bool respondsToSelector(const void* pObj, SEL selector); - template - static constexpr bool doesRequireMsgSendStret(); - template - static _Ret sendMessage(const void* pObj, SEL selector, _Args... args); - template - static _Ret sendMessageSafe(const void* pObj, SEL selector, _Args... args); - -private: - Object() = delete; - Object(const Object&) = delete; - ~Object() = delete; - - Object& operator=(const Object&) = delete; -}; -} - -template -_NS_INLINE _Class* NS::Referencing<_Class, _Base>::retain() -{ - return Object::sendMessage<_Class*>(this, _NS_PRIVATE_SEL(retain)); -} - -template -_NS_INLINE void NS::Referencing<_Class, _Base>::release() -{ - Object::sendMessage(this, _NS_PRIVATE_SEL(release)); -} - -template -_NS_INLINE _Class* NS::Referencing<_Class, _Base>::autorelease() -{ - return Object::sendMessage<_Class*>(this, _NS_PRIVATE_SEL(autorelease)); -} - -template -_NS_INLINE NS::UInteger NS::Referencing<_Class, _Base>::retainCount() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(retainCount)); -} - -template -_NS_INLINE _Class* NS::Copying<_Class, _Base>::copy() const -{ - return Object::sendMessage<_Class*>(this, _NS_PRIVATE_SEL(copy)); -} - -template -_NS_INLINE _Dst NS::Object::bridgingCast(const void* pObj) -{ -#ifdef __OBJC__ - return (__bridge _Dst)pObj; -#else - return (_Dst)pObj; -#endif // __OBJC__ -} - -template -_NS_INLINE constexpr bool NS::Object::doesRequireMsgSendStret() -{ -#if (defined(__i386__) || defined(__x86_64__)) - constexpr size_t kStructLimit = (sizeof(std::uintptr_t) << 1); - - return sizeof(_Type) > kStructLimit; -#elif defined(__arm64__) - return false; -#elif defined(__arm__) - constexpr size_t kStructLimit = sizeof(std::uintptr_t); - - return std::is_class(_Type) && (sizeof(_Type) > kStructLimit); -#else -#error "Unsupported architecture!" -#endif -} - -template <> -_NS_INLINE constexpr bool NS::Object::doesRequireMsgSendStret() -{ - return false; -} - -template -_NS_INLINE _Ret NS::Object::sendMessage(const void* pObj, SEL selector, _Args... args) -{ -#if (defined(__i386__) || defined(__x86_64__)) - if constexpr (std::is_floating_point<_Ret>()) - { - using SendMessageProcFpret = _Ret (*)(const void*, SEL, _Args...); - - const SendMessageProcFpret pProc = reinterpret_cast(&objc_msgSend_fpret); - - return (*pProc)(pObj, selector, args...); - } - else -#endif // ( defined( __i386__ ) || defined( __x86_64__ ) ) -#if !defined(__arm64__) - if constexpr (doesRequireMsgSendStret<_Ret>()) - { - using SendMessageProcStret = void (*)(_Ret*, const void*, SEL, _Args...); - - const SendMessageProcStret pProc = reinterpret_cast(&objc_msgSend_stret); - _Ret ret; - - (*pProc)(&ret, pObj, selector, args...); - - return ret; - } - else -#endif // !defined( __arm64__ ) - { - using SendMessageProc = _Ret (*)(const void*, SEL, _Args...); - - const SendMessageProc pProc = reinterpret_cast(&objc_msgSend); - - return (*pProc)(pObj, selector, args...); - } -} - -_NS_INLINE NS::MethodSignature* NS::Object::methodSignatureForSelector(const void* pObj, SEL selector) -{ - return sendMessage(pObj, _NS_PRIVATE_SEL(methodSignatureForSelector_), selector); -} - -_NS_INLINE bool NS::Object::respondsToSelector(const void* pObj, SEL selector) -{ - return sendMessage(pObj, _NS_PRIVATE_SEL(respondsToSelector_), selector); -} - -template -_NS_INLINE _Ret NS::Object::sendMessageSafe(const void* pObj, SEL selector, _Args... args) -{ - if ((respondsToSelector(pObj, selector)) || (nullptr != methodSignatureForSelector(pObj, selector))) - { - return sendMessage<_Ret>(pObj, selector, args...); - } - - if constexpr (!std::is_void<_Ret>::value) - { - return 0; - } -} - -template -_NS_INLINE _Class* NS::Object::alloc(const char* pClassName) -{ - return sendMessage<_Class*>(objc_lookUpClass(pClassName), _NS_PRIVATE_SEL(alloc)); -} - -template -_NS_INLINE _Class* NS::Object::alloc(const void* pClass) -{ - return sendMessage<_Class*>(pClass, _NS_PRIVATE_SEL(alloc)); -} - -template -_NS_INLINE _Class* NS::Object::init() -{ - return sendMessage<_Class*>(this, _NS_PRIVATE_SEL(init)); -} - -_NS_INLINE NS::UInteger NS::Object::hash() const -{ - return sendMessage(this, _NS_PRIVATE_SEL(hash)); -} - -_NS_INLINE bool NS::Object::isEqual(const Object* pObject) const -{ - return sendMessage(this, _NS_PRIVATE_SEL(isEqual_), pObject); -} - -_NS_INLINE NS::String* NS::Object::description() const -{ - return sendMessage(this, _NS_PRIVATE_SEL(description)); -} - -_NS_INLINE NS::String* NS::Object::debugDescription() const -{ - return sendMessageSafe(this, _NS_PRIVATE_SEL(debugDescription)); -} - -namespace NS -{ -class Array : public Copying -{ -public: - static Array* array(); - static Array* array(const Object* pObject); - static Array* array(const Object* const* pObjects, UInteger count); - - static Array* alloc(); - - Array* init(); - Array* init(const Object* const* pObjects, UInteger count); - Array* init(const class Coder* pCoder); - - template - _Object* object(UInteger index) const; - UInteger count() const; -}; -} - -_NS_INLINE NS::Array* NS::Array::array() -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSArray), _NS_PRIVATE_SEL(array)); -} - -_NS_INLINE NS::Array* NS::Array::array(const Object* pObject) -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSArray), _NS_PRIVATE_SEL(arrayWithObject_), pObject); -} - -_NS_INLINE NS::Array* NS::Array::array(const Object* const* pObjects, UInteger count) -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSArray), _NS_PRIVATE_SEL(arrayWithObjects_count_), pObjects, count); -} - -_NS_INLINE NS::Array* NS::Array::alloc() -{ - return NS::Object::alloc(_NS_PRIVATE_CLS(NSArray)); -} - -_NS_INLINE NS::Array* NS::Array::init() -{ - return NS::Object::init(); -} - -_NS_INLINE NS::Array* NS::Array::init(const Object* const* pObjects, UInteger count) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(initWithObjects_count_), pObjects, count); -} - -_NS_INLINE NS::Array* NS::Array::init(const class Coder* pCoder) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(initWithCoder_), pCoder); -} - -_NS_INLINE NS::UInteger NS::Array::count() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(count)); -} - -template -_NS_INLINE _Object* NS::Array::object(UInteger index) const -{ - return Object::sendMessage<_Object*>(this, _NS_PRIVATE_SEL(objectAtIndex_), index); -} - -namespace NS -{ -class AutoreleasePool : public Object -{ -public: - static AutoreleasePool* alloc(); - AutoreleasePool* init(); - - void drain(); - - void addObject(Object* pObject); - - static void showPools(); -}; -} - -_NS_INLINE NS::AutoreleasePool* NS::AutoreleasePool::alloc() -{ - return NS::Object::alloc(_NS_PRIVATE_CLS(NSAutoreleasePool)); -} - -_NS_INLINE NS::AutoreleasePool* NS::AutoreleasePool::init() -{ - return NS::Object::init(); -} - -_NS_INLINE void NS::AutoreleasePool::drain() -{ - Object::sendMessage(this, _NS_PRIVATE_SEL(drain)); -} - -_NS_INLINE void NS::AutoreleasePool::addObject(Object* pObject) -{ - Object::sendMessage(this, _NS_PRIVATE_SEL(addObject_), pObject); -} - -_NS_INLINE void NS::AutoreleasePool::showPools() -{ - Object::sendMessage(_NS_PRIVATE_CLS(NSAutoreleasePool), _NS_PRIVATE_SEL(showPools)); -} - -namespace NS -{ -struct FastEnumerationState -{ - unsigned long state; - Object** itemsPtr; - unsigned long* mutationsPtr; - unsigned long extra[5]; -} _NS_PACKED; - -class FastEnumeration : public Referencing -{ -public: - NS::UInteger countByEnumerating(FastEnumerationState* pState, Object** pBuffer, NS::UInteger len); -}; - -template -class Enumerator : public Referencing, FastEnumeration> -{ -public: - _ObjectType* nextObject(); - class Array* allObjects(); -}; -} - -_NS_INLINE NS::UInteger NS::FastEnumeration::countByEnumerating(FastEnumerationState* pState, Object** pBuffer, NS::UInteger len) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(countByEnumeratingWithState_objects_count_), pState, pBuffer, len); -} - -template -_NS_INLINE _ObjectType* NS::Enumerator<_ObjectType>::nextObject() -{ - return Object::sendMessage<_ObjectType*>(this, _NS_PRIVATE_SEL(nextObject)); -} - -template -_NS_INLINE NS::Array* NS::Enumerator<_ObjectType>::allObjects() -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(allObjects)); -} - -namespace NS -{ -class Dictionary : public NS::Copying -{ -public: - static Dictionary* dictionary(); - static Dictionary* dictionary(const Object* pObject, const Object* pKey); - static Dictionary* dictionary(const Object* const* pObjects, const Object* const* pKeys, UInteger count); - - static Dictionary* alloc(); - - Dictionary* init(); - Dictionary* init(const Object* const* pObjects, const Object* const* pKeys, UInteger count); - Dictionary* init(const class Coder* pCoder); - - template - Enumerator<_KeyType>* keyEnumerator() const; - - template - _Object* object(const Object* pKey) const; - UInteger count() const; -}; -} - -_NS_INLINE NS::Dictionary* NS::Dictionary::dictionary() -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSDictionary), _NS_PRIVATE_SEL(dictionary)); -} - -_NS_INLINE NS::Dictionary* NS::Dictionary::dictionary(const Object* pObject, const Object* pKey) -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSDictionary), _NS_PRIVATE_SEL(dictionaryWithObject_forKey_), pObject, pKey); -} - -_NS_INLINE NS::Dictionary* NS::Dictionary::dictionary(const Object* const* pObjects, const Object* const* pKeys, UInteger count) -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSDictionary), _NS_PRIVATE_SEL(dictionaryWithObjects_forKeys_count_), - pObjects, pKeys, count); -} - -_NS_INLINE NS::Dictionary* NS::Dictionary::alloc() -{ - return NS::Object::alloc(_NS_PRIVATE_CLS(NSDictionary)); -} - -_NS_INLINE NS::Dictionary* NS::Dictionary::init() -{ - return NS::Object::init(); -} - -_NS_INLINE NS::Dictionary* NS::Dictionary::init(const Object* const* pObjects, const Object* const* pKeys, UInteger count) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(initWithObjects_forKeys_count_), pObjects, pKeys, count); -} - -_NS_INLINE NS::Dictionary* NS::Dictionary::init(const class Coder* pCoder) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(initWithCoder_), pCoder); -} - -template -_NS_INLINE NS::Enumerator<_KeyType>* NS::Dictionary::keyEnumerator() const -{ - return Object::sendMessage*>(this, _NS_PRIVATE_SEL(keyEnumerator)); -} - -template -_NS_INLINE _Object* NS::Dictionary::object(const Object* pKey) const -{ - return Object::sendMessage<_Object*>(this, _NS_PRIVATE_SEL(objectForKey_), pKey); -} - -_NS_INLINE NS::UInteger NS::Dictionary::count() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(count)); -} - -namespace NS -{ -struct Range -{ - static Range Make(UInteger loc, UInteger len); - - Range(UInteger loc, UInteger len); - - bool Equal(const Range& range) const; - bool LocationInRange(UInteger loc) const; - UInteger Max() const; - - UInteger location; - UInteger length; -} _NS_PACKED; -} - -_NS_INLINE NS::Range::Range(UInteger loc, UInteger len) - : location(loc) - , length(len) -{ -} - -_NS_INLINE NS::Range NS::Range::Make(UInteger loc, UInteger len) -{ - return Range(loc, len); -} - -_NS_INLINE bool NS::Range::Equal(const Range& range) const -{ - return (location == range.location) && (length == range.length); -} - -_NS_INLINE bool NS::Range::LocationInRange(UInteger loc) const -{ - return (!(loc < location)) && ((loc - location) < length); -} - -_NS_INLINE NS::UInteger NS::Range::Max() const -{ - return location + length; -} - -namespace NS -{ -_NS_ENUM(NS::UInteger, StringEncoding) { - ASCIIStringEncoding = 1, - NEXTSTEPStringEncoding = 2, - JapaneseEUCStringEncoding = 3, - UTF8StringEncoding = 4, - ISOLatin1StringEncoding = 5, - SymbolStringEncoding = 6, - NonLossyASCIIStringEncoding = 7, - ShiftJISStringEncoding = 8, - ISOLatin2StringEncoding = 9, - UnicodeStringEncoding = 10, - WindowsCP1251StringEncoding = 11, - WindowsCP1252StringEncoding = 12, - WindowsCP1253StringEncoding = 13, - WindowsCP1254StringEncoding = 14, - WindowsCP1250StringEncoding = 15, - ISO2022JPStringEncoding = 21, - MacOSRomanStringEncoding = 30, - - UTF16StringEncoding = UnicodeStringEncoding, - - UTF16BigEndianStringEncoding = 0x90000100, - UTF16LittleEndianStringEncoding = 0x94000100, - - UTF32StringEncoding = 0x8c000100, - UTF32BigEndianStringEncoding = 0x98000100, - UTF32LittleEndianStringEncoding = 0x9c000100 -}; - -_NS_OPTIONS(NS::UInteger, StringCompareOptions) { - CaseInsensitiveSearch = 1, - LiteralSearch = 2, - BackwardsSearch = 4, - AnchoredSearch = 8, - NumericSearch = 64, - DiacriticInsensitiveSearch = 128, - WidthInsensitiveSearch = 256, - ForcedOrderingSearch = 512, - RegularExpressionSearch = 1024 -}; - -using unichar = unsigned short; - -class String : public Copying -{ -public: - static String* string(); - static String* string(const String* pString); - static String* string(const char* pString, StringEncoding encoding); - - static String* alloc(); - String* init(); - String* init(const String* pString); - String* init(const char* pString, StringEncoding encoding); - String* init(void* pBytes, UInteger len, StringEncoding encoding, bool freeBuffer); - - unichar character(UInteger index) const; - UInteger length() const; - - const char* cString(StringEncoding encoding) const; - const char* utf8String() const; - UInteger maximumLengthOfBytes(StringEncoding encoding) const; - UInteger lengthOfBytes(StringEncoding encoding) const; - - bool isEqualToString(const String* pString) const; - Range rangeOfString(const String* pString, StringCompareOptions options) const; - - const char* fileSystemRepresentation() const; - - String* stringByAppendingString(const String* pString) const; -}; - -#define MTLSTR( literal ) (NS::String *)__builtin___CFStringMakeConstantString( "" literal "" ) - -template< std::size_t _StringLen > -[[deprecated("please use MTLSTR(str)")]] -constexpr const String* MakeConstantString( const char ( &str )[_StringLen] ) -{ - return reinterpret_cast< const String* >( __CFStringMakeConstantString( str ) ); -} - -} - -_NS_INLINE NS::String* NS::String::string() -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSString), _NS_PRIVATE_SEL(string)); -} - -_NS_INLINE NS::String* NS::String::string(const String* pString) -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSString), _NS_PRIVATE_SEL(stringWithString_), pString); -} - -_NS_INLINE NS::String* NS::String::string(const char* pString, StringEncoding encoding) -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSString), _NS_PRIVATE_SEL(stringWithCString_encoding_), pString, encoding); -} - -_NS_INLINE NS::String* NS::String::alloc() -{ - return Object::alloc(_NS_PRIVATE_CLS(NSString)); -} - -_NS_INLINE NS::String* NS::String::init() -{ - return Object::init(); -} - -_NS_INLINE NS::String* NS::String::init(const String* pString) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(initWithString_), pString); -} - -_NS_INLINE NS::String* NS::String::init(const char* pString, StringEncoding encoding) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(initWithCString_encoding_), pString, encoding); -} - -_NS_INLINE NS::String* NS::String::init(void* pBytes, UInteger len, StringEncoding encoding, bool freeBuffer) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(initWithBytesNoCopy_length_encoding_freeWhenDone_), pBytes, len, encoding, freeBuffer); -} - -_NS_INLINE NS::unichar NS::String::character(UInteger index) const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(characterAtIndex_), index); -} - -_NS_INLINE NS::UInteger NS::String::length() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(length)); -} - -_NS_INLINE const char* NS::String::cString(StringEncoding encoding) const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(cStringUsingEncoding_), encoding); -} - -_NS_INLINE const char* NS::String::utf8String() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(UTF8String)); -} - -_NS_INLINE NS::UInteger NS::String::maximumLengthOfBytes(StringEncoding encoding) const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(maximumLengthOfBytesUsingEncoding_), encoding); -} - -_NS_INLINE NS::UInteger NS::String::lengthOfBytes(StringEncoding encoding) const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(lengthOfBytesUsingEncoding_), encoding); -} - -_NS_INLINE bool NS::String::isEqualToString(const NS::String* pString) const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(isEqualToString_), pString); -} - -_NS_INLINE NS::Range NS::String::rangeOfString(const NS::String* pString, NS::StringCompareOptions options) const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(rangeOfString_options_), pString, options); -} - -_NS_INLINE const char* NS::String::fileSystemRepresentation() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(fileSystemRepresentation)); -} - -_NS_INLINE NS::String* NS::String::stringByAppendingString(const String* pString) const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(stringByAppendingString_), pString); -} - -#include - -namespace NS -{ -using NotificationName = class String*; - -class Notification : public NS::Referencing -{ -public: - NS::String* name() const; - NS::Object* object() const; - NS::Dictionary* userInfo() const; -}; - -using ObserverBlock = void(^)(Notification*); -using ObserverFunction = std::function; - -class NotificationCenter : public NS::Referencing -{ - public: - static class NotificationCenter* defaultCenter(); - Object* addObserver(NotificationName name, Object* pObj, void* pQueue, ObserverBlock block); - Object* addObserver(NotificationName name, Object* pObj, void* pQueue, ObserverFunction &handler); - void removeObserver(Object* pObserver); - -}; -} - -_NS_INLINE NS::String* NS::Notification::name() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(name)); -} - -_NS_INLINE NS::Object* NS::Notification::object() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(object)); -} - -_NS_INLINE NS::Dictionary* NS::Notification::userInfo() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(userInfo)); -} - -_NS_INLINE NS::NotificationCenter* NS::NotificationCenter::defaultCenter() -{ - return NS::Object::sendMessage(_NS_PRIVATE_CLS(NSNotificationCenter), _NS_PRIVATE_SEL(defaultCenter)); -} - -_NS_INLINE NS::Object* NS::NotificationCenter::addObserver(NS::NotificationName name, Object* pObj, void* pQueue, NS::ObserverBlock block) -{ - return NS::Object::sendMessage(this, _NS_PRIVATE_SEL(addObserverName_object_queue_block_), name, pObj, pQueue, block); -} - -_NS_INLINE NS::Object* NS::NotificationCenter::addObserver(NS::NotificationName name, Object* pObj, void* pQueue, NS::ObserverFunction &handler) -{ - __block ObserverFunction blockFunction = handler; - - return addObserver(name, pObj, pQueue, ^(NS::Notification* pNotif) {blockFunction(pNotif);}); -} - -_NS_INLINE void NS::NotificationCenter::removeObserver(Object* pObserver) -{ - return NS::Object::sendMessage(this, _NS_PRIVATE_SEL(removeObserver_), pObserver); -} - -namespace NS -{ -_NS_CONST(NotificationName, BundleDidLoadNotification); -_NS_CONST(NotificationName, BundleResourceRequestLowDiskSpaceNotification); - -class String* LocalizedString(const String* pKey, const String*); -class String* LocalizedStringFromTable(const String* pKey, const String* pTbl, const String*); -class String* LocalizedStringFromTableInBundle(const String* pKey, const String* pTbl, const class Bundle* pBdle, const String*); -class String* LocalizedStringWithDefaultValue(const String* pKey, const String* pTbl, const class Bundle* pBdle, const String* pVal, const String*); - -class Bundle : public Referencing -{ -public: - static Bundle* mainBundle(); - - static Bundle* bundle(const class String* pPath); - static Bundle* bundle(const class URL* pURL); - - static Bundle* alloc(); - - Bundle* init(const class String* pPath); - Bundle* init(const class URL* pURL); - - class Array* allBundles() const; - class Array* allFrameworks() const; - - bool load(); - bool unload(); - - bool isLoaded() const; - - bool preflightAndReturnError(class Error** pError) const; - bool loadAndReturnError(class Error** pError); - - class URL* bundleURL() const; - class URL* resourceURL() const; - class URL* executableURL() const; - class URL* URLForAuxiliaryExecutable(const class String* pExecutableName) const; - - class URL* privateFrameworksURL() const; - class URL* sharedFrameworksURL() const; - class URL* sharedSupportURL() const; - class URL* builtInPlugInsURL() const; - class URL* appStoreReceiptURL() const; - - class String* bundlePath() const; - class String* resourcePath() const; - class String* executablePath() const; - class String* pathForAuxiliaryExecutable(const class String* pExecutableName) const; - - class String* privateFrameworksPath() const; - class String* sharedFrameworksPath() const; - class String* sharedSupportPath() const; - class String* builtInPlugInsPath() const; - - class String* bundleIdentifier() const; - class Dictionary* infoDictionary() const; - class Dictionary* localizedInfoDictionary() const; - class Object* objectForInfoDictionaryKey(const class String* pKey); - - class String* localizedString(const class String* pKey, const class String* pValue = nullptr, const class String* pTableName = nullptr) const; -}; -} - -_NS_PRIVATE_DEF_CONST(NS::NotificationName, BundleDidLoadNotification); -_NS_PRIVATE_DEF_CONST(NS::NotificationName, BundleResourceRequestLowDiskSpaceNotification); - -_NS_INLINE NS::String* NS::LocalizedString(const String* pKey, const String*) -{ - return Bundle::mainBundle()->localizedString(pKey, nullptr, nullptr); -} - -_NS_INLINE NS::String* NS::LocalizedStringFromTable(const String* pKey, const String* pTbl, const String*) -{ - return Bundle::mainBundle()->localizedString(pKey, nullptr, pTbl); -} - -_NS_INLINE NS::String* NS::LocalizedStringFromTableInBundle(const String* pKey, const String* pTbl, const Bundle* pBdl, const String*) -{ - return pBdl->localizedString(pKey, nullptr, pTbl); -} - -_NS_INLINE NS::String* NS::LocalizedStringWithDefaultValue(const String* pKey, const String* pTbl, const Bundle* pBdl, const String* pVal, const String*) -{ - return pBdl->localizedString(pKey, pVal, pTbl); -} - -_NS_INLINE NS::Bundle* NS::Bundle::mainBundle() -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSBundle), _NS_PRIVATE_SEL(mainBundle)); -} - -_NS_INLINE NS::Bundle* NS::Bundle::bundle(const class String* pPath) -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSBundle), _NS_PRIVATE_SEL(bundleWithPath_), pPath); -} - -_NS_INLINE NS::Bundle* NS::Bundle::bundle(const class URL* pURL) -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSBundle), _NS_PRIVATE_SEL(bundleWithURL_), pURL); -} - -_NS_INLINE NS::Bundle* NS::Bundle::alloc() -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSBundle), _NS_PRIVATE_SEL(alloc)); -} - -_NS_INLINE NS::Bundle* NS::Bundle::init(const String* pPath) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(initWithPath_), pPath); -} - -_NS_INLINE NS::Bundle* NS::Bundle::init(const URL* pURL) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(initWithURL_), pURL); -} - -_NS_INLINE NS::Array* NS::Bundle::allBundles() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(allBundles)); -} - -_NS_INLINE NS::Array* NS::Bundle::allFrameworks() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(allFrameworks)); -} - -_NS_INLINE bool NS::Bundle::load() -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(load)); -} - -_NS_INLINE bool NS::Bundle::unload() -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(unload)); -} - -_NS_INLINE bool NS::Bundle::isLoaded() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(isLoaded)); -} - -_NS_INLINE bool NS::Bundle::preflightAndReturnError(Error** pError) const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(preflightAndReturnError_), pError); -} - -_NS_INLINE bool NS::Bundle::loadAndReturnError(Error** pError) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(loadAndReturnError_), pError); -} - -_NS_INLINE NS::URL* NS::Bundle::bundleURL() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(bundleURL)); -} - -_NS_INLINE NS::URL* NS::Bundle::resourceURL() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(resourceURL)); -} - -_NS_INLINE NS::URL* NS::Bundle::executableURL() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(executableURL)); -} - -_NS_INLINE NS::URL* NS::Bundle::URLForAuxiliaryExecutable(const String* pExecutableName) const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(URLForAuxiliaryExecutable_), pExecutableName); -} - -_NS_INLINE NS::URL* NS::Bundle::privateFrameworksURL() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(privateFrameworksURL)); -} - -_NS_INLINE NS::URL* NS::Bundle::sharedFrameworksURL() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(sharedFrameworksURL)); -} - -_NS_INLINE NS::URL* NS::Bundle::sharedSupportURL() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(sharedSupportURL)); -} - -_NS_INLINE NS::URL* NS::Bundle::builtInPlugInsURL() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(builtInPlugInsURL)); -} - -_NS_INLINE NS::URL* NS::Bundle::appStoreReceiptURL() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(appStoreReceiptURL)); -} - -_NS_INLINE NS::String* NS::Bundle::bundlePath() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(bundlePath)); -} - -_NS_INLINE NS::String* NS::Bundle::resourcePath() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(resourcePath)); -} - -_NS_INLINE NS::String* NS::Bundle::executablePath() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(executablePath)); -} - -_NS_INLINE NS::String* NS::Bundle::pathForAuxiliaryExecutable(const String* pExecutableName) const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(pathForAuxiliaryExecutable_), pExecutableName); -} - -_NS_INLINE NS::String* NS::Bundle::privateFrameworksPath() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(privateFrameworksPath)); -} - -_NS_INLINE NS::String* NS::Bundle::sharedFrameworksPath() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(sharedFrameworksPath)); -} - -_NS_INLINE NS::String* NS::Bundle::sharedSupportPath() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(sharedSupportPath)); -} - -_NS_INLINE NS::String* NS::Bundle::builtInPlugInsPath() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(builtInPlugInsPath)); -} - -_NS_INLINE NS::String* NS::Bundle::bundleIdentifier() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(bundleIdentifier)); -} - -_NS_INLINE NS::Dictionary* NS::Bundle::infoDictionary() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(infoDictionary)); -} - -_NS_INLINE NS::Dictionary* NS::Bundle::localizedInfoDictionary() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(localizedInfoDictionary)); -} - -_NS_INLINE NS::Object* NS::Bundle::objectForInfoDictionaryKey(const String* pKey) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(objectForInfoDictionaryKey_), pKey); -} - -_NS_INLINE NS::String* NS::Bundle::localizedString(const String* pKey, const String* pValue /* = nullptr */, const String* pTableName /* = nullptr */) const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(localizedStringForKey_value_table_), pKey, pValue, pTableName); -} - -namespace NS -{ -class Data : public Copying -{ -public: - void* mutableBytes() const; - UInteger length() const; -}; -} - -_NS_INLINE void* NS::Data::mutableBytes() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(mutableBytes)); -} - -_NS_INLINE NS::UInteger NS::Data::length() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(length)); -} - -namespace NS -{ - -using TimeInterval = double; - -class Date : public Copying -{ -public: - static Date* dateWithTimeIntervalSinceNow(TimeInterval secs); -}; - -} // NS - -_NS_INLINE NS::Date* NS::Date::dateWithTimeIntervalSinceNow(NS::TimeInterval secs) -{ - return NS::Object::sendMessage(_NS_PRIVATE_CLS(NSDate), _NS_PRIVATE_SEL(dateWithTimeIntervalSinceNow_), secs); -} - -//------------------------------------------------------------------------------------------------------------------------------------------------------------- - -namespace NS -{ -using ErrorDomain = class String*; - -_NS_CONST(ErrorDomain, CocoaErrorDomain); -_NS_CONST(ErrorDomain, POSIXErrorDomain); -_NS_CONST(ErrorDomain, OSStatusErrorDomain); -_NS_CONST(ErrorDomain, MachErrorDomain); - -using ErrorUserInfoKey = class String*; - -_NS_CONST(ErrorUserInfoKey, UnderlyingErrorKey); -_NS_CONST(ErrorUserInfoKey, LocalizedDescriptionKey); -_NS_CONST(ErrorUserInfoKey, LocalizedFailureReasonErrorKey); -_NS_CONST(ErrorUserInfoKey, LocalizedRecoverySuggestionErrorKey); -_NS_CONST(ErrorUserInfoKey, LocalizedRecoveryOptionsErrorKey); -_NS_CONST(ErrorUserInfoKey, RecoveryAttempterErrorKey); -_NS_CONST(ErrorUserInfoKey, HelpAnchorErrorKey); -_NS_CONST(ErrorUserInfoKey, DebugDescriptionErrorKey); -_NS_CONST(ErrorUserInfoKey, LocalizedFailureErrorKey); -_NS_CONST(ErrorUserInfoKey, StringEncodingErrorKey); -_NS_CONST(ErrorUserInfoKey, URLErrorKey); -_NS_CONST(ErrorUserInfoKey, FilePathErrorKey); - -class Error : public Copying -{ -public: - static Error* error(ErrorDomain domain, Integer code, class Dictionary* pDictionary); - - static Error* alloc(); - Error* init(); - Error* init(ErrorDomain domain, Integer code, class Dictionary* pDictionary); - - Integer code() const; - ErrorDomain domain() const; - class Dictionary* userInfo() const; - - class String* localizedDescription() const; - class Array* localizedRecoveryOptions() const; - class String* localizedRecoverySuggestion() const; - class String* localizedFailureReason() const; -}; -} - -_NS_PRIVATE_DEF_CONST(NS::ErrorDomain, CocoaErrorDomain); -_NS_PRIVATE_DEF_CONST(NS::ErrorDomain, POSIXErrorDomain); -_NS_PRIVATE_DEF_CONST(NS::ErrorDomain, OSStatusErrorDomain); -_NS_PRIVATE_DEF_CONST(NS::ErrorDomain, MachErrorDomain); - -_NS_PRIVATE_DEF_CONST(NS::ErrorUserInfoKey, UnderlyingErrorKey); -_NS_PRIVATE_DEF_CONST(NS::ErrorUserInfoKey, LocalizedDescriptionKey); -_NS_PRIVATE_DEF_CONST(NS::ErrorUserInfoKey, LocalizedFailureReasonErrorKey); -_NS_PRIVATE_DEF_CONST(NS::ErrorUserInfoKey, LocalizedRecoverySuggestionErrorKey); -_NS_PRIVATE_DEF_CONST(NS::ErrorUserInfoKey, LocalizedRecoveryOptionsErrorKey); -_NS_PRIVATE_DEF_CONST(NS::ErrorUserInfoKey, RecoveryAttempterErrorKey); -_NS_PRIVATE_DEF_CONST(NS::ErrorUserInfoKey, HelpAnchorErrorKey); -_NS_PRIVATE_DEF_CONST(NS::ErrorUserInfoKey, DebugDescriptionErrorKey); -_NS_PRIVATE_DEF_CONST(NS::ErrorUserInfoKey, LocalizedFailureErrorKey); -_NS_PRIVATE_DEF_CONST(NS::ErrorUserInfoKey, StringEncodingErrorKey); -_NS_PRIVATE_DEF_CONST(NS::ErrorUserInfoKey, URLErrorKey); -_NS_PRIVATE_DEF_CONST(NS::ErrorUserInfoKey, FilePathErrorKey); - -_NS_INLINE NS::Error* NS::Error::error(ErrorDomain domain, Integer code, class Dictionary* pDictionary) -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSError), _NS_PRIVATE_SEL(errorWithDomain_code_userInfo_), domain, code, pDictionary); -} - -_NS_INLINE NS::Error* NS::Error::alloc() -{ - return Object::alloc(_NS_PRIVATE_CLS(NSError)); -} - -_NS_INLINE NS::Error* NS::Error::init() -{ - return Object::init(); -} - -_NS_INLINE NS::Error* NS::Error::init(ErrorDomain domain, Integer code, class Dictionary* pDictionary) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(initWithDomain_code_userInfo_), domain, code, pDictionary); -} - -_NS_INLINE NS::Integer NS::Error::code() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(code)); -} - -_NS_INLINE NS::ErrorDomain NS::Error::domain() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(domain)); -} - -_NS_INLINE NS::Dictionary* NS::Error::userInfo() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(userInfo)); -} - -_NS_INLINE NS::String* NS::Error::localizedDescription() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(localizedDescription)); -} - -_NS_INLINE NS::Array* NS::Error::localizedRecoveryOptions() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(localizedRecoveryOptions)); -} - -_NS_INLINE NS::String* NS::Error::localizedRecoverySuggestion() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(localizedRecoverySuggestion)); -} - -_NS_INLINE NS::String* NS::Error::localizedFailureReason() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(localizedFailureReason)); -} - -namespace NS -{ - -template -class Locking : public _Base -{ -public: - void lock(); - void unlock(); -}; - -class Condition : public Locking -{ -public: - static Condition* alloc(); - - Condition* init(); - - void wait(); - bool waitUntilDate(Date* pLimit); - void signal(); - void broadcast(); -}; - -} // NS - -template -_NS_INLINE void NS::Locking<_Class, _Base>::lock() -{ - NS::Object::sendMessage(this, _NS_PRIVATE_SEL(lock)); -} - -template -_NS_INLINE void NS::Locking<_Class, _Base>::unlock() -{ - NS::Object::sendMessage(this, _NS_PRIVATE_SEL(unlock)); -} - -_NS_INLINE NS::Condition* NS::Condition::alloc() -{ - return NS::Object::alloc(_NS_PRIVATE_CLS(NSCondition)); -} - -_NS_INLINE NS::Condition* NS::Condition::init() -{ - return NS::Object::init(); -} - -_NS_INLINE void NS::Condition::wait() -{ - NS::Object::sendMessage(this, _NS_PRIVATE_SEL(wait)); -} - -_NS_INLINE bool NS::Condition::waitUntilDate(NS::Date* pLimit) -{ - return NS::Object::sendMessage(this, _NS_PRIVATE_SEL(waitUntilDate_), pLimit); -} - -_NS_INLINE void NS::Condition::signal() -{ - NS::Object::sendMessage(this, _NS_PRIVATE_SEL(signal)); -} - -_NS_INLINE void NS::Condition::broadcast() -{ - NS::Object::sendMessage(this, _NS_PRIVATE_SEL(broadcast)); -} - -//------------------------------------------------------------------------------------------------------------------------------------------------------------- - -namespace NS -{ - -_NS_ENUM(Integer, ComparisonResult) { - OrderedAscending = -1, - OrderedSame = 0, - OrderedDescending = 1, -}; - -const Integer NotFound = IntegerMax; - -} - -namespace NS -{ -class Value : public Copying -{ -public: - static Value* value(const void* pValue, const char* pType); - static Value* value(const void* pPointer); - - static Value* alloc(); - - Value* init(const void* pValue, const char* pType); - Value* init(const class Coder* pCoder); - - void getValue(void* pValue, UInteger size) const; - const char* objCType() const; - - bool isEqualToValue(Value* pValue) const; - void* pointerValue() const; -}; - -class Number : public Copying -{ -public: - static Number* number(char value); - static Number* number(unsigned char value); - static Number* number(short value); - static Number* number(unsigned short value); - static Number* number(int value); - static Number* number(unsigned int value); - static Number* number(long value); - static Number* number(unsigned long value); - static Number* number(long long value); - static Number* number(unsigned long long value); - static Number* number(float value); - static Number* number(double value); - static Number* number(bool value); - - static Number* alloc(); - - Number* init(const class Coder* pCoder); - Number* init(char value); - Number* init(unsigned char value); - Number* init(short value); - Number* init(unsigned short value); - Number* init(int value); - Number* init(unsigned int value); - Number* init(long value); - Number* init(unsigned long value); - Number* init(long long value); - Number* init(unsigned long long value); - Number* init(float value); - Number* init(double value); - Number* init(bool value); - - char charValue() const; - unsigned char unsignedCharValue() const; - short shortValue() const; - unsigned short unsignedShortValue() const; - int intValue() const; - unsigned int unsignedIntValue() const; - long longValue() const; - unsigned long unsignedLongValue() const; - long long longLongValue() const; - unsigned long long unsignedLongLongValue() const; - float floatValue() const; - double doubleValue() const; - bool boolValue() const; - Integer integerValue() const; - UInteger unsignedIntegerValue() const; - class String* stringValue() const; - - ComparisonResult compare(const Number* pOtherNumber) const; - bool isEqualToNumber(const Number* pNumber) const; - - class String* descriptionWithLocale(const Object* pLocale) const; -}; -} - -_NS_INLINE NS::Value* NS::Value::value(const void* pValue, const char* pType) -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSValue), _NS_PRIVATE_SEL(valueWithBytes_objCType_), pValue, pType); -} - -_NS_INLINE NS::Value* NS::Value::value(const void* pPointer) -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSValue), _NS_PRIVATE_SEL(valueWithPointer_), pPointer); -} - -_NS_INLINE NS::Value* NS::Value::alloc() -{ - return NS::Object::alloc(_NS_PRIVATE_CLS(NSValue)); -} - -_NS_INLINE NS::Value* NS::Value::init(const void* pValue, const char* pType) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(initWithBytes_objCType_), pValue, pType); -} - -_NS_INLINE NS::Value* NS::Value::init(const class Coder* pCoder) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(initWithCoder_), pCoder); -} - -_NS_INLINE void NS::Value::getValue(void* pValue, UInteger size) const -{ - Object::sendMessage(this, _NS_PRIVATE_SEL(getValue_size_), pValue, size); -} - -_NS_INLINE const char* NS::Value::objCType() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(objCType)); -} - -_NS_INLINE bool NS::Value::isEqualToValue(Value* pValue) const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(isEqualToValue_), pValue); -} - -_NS_INLINE void* NS::Value::pointerValue() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(pointerValue)); -} - -_NS_INLINE NS::Number* NS::Number::number(char value) -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSNumber), _NS_PRIVATE_SEL(numberWithChar_), value); -} - -_NS_INLINE NS::Number* NS::Number::number(unsigned char value) -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSNumber), _NS_PRIVATE_SEL(numberWithUnsignedChar_), value); -} - -_NS_INLINE NS::Number* NS::Number::number(short value) -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSNumber), _NS_PRIVATE_SEL(numberWithShort_), value); -} - -_NS_INLINE NS::Number* NS::Number::number(unsigned short value) -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSNumber), _NS_PRIVATE_SEL(numberWithUnsignedShort_), value); -} - -_NS_INLINE NS::Number* NS::Number::number(int value) -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSNumber), _NS_PRIVATE_SEL(numberWithInt_), value); -} - -_NS_INLINE NS::Number* NS::Number::number(unsigned int value) -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSNumber), _NS_PRIVATE_SEL(numberWithUnsignedInt_), value); -} - -_NS_INLINE NS::Number* NS::Number::number(long value) -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSNumber), _NS_PRIVATE_SEL(numberWithLong_), value); -} - -_NS_INLINE NS::Number* NS::Number::number(unsigned long value) -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSNumber), _NS_PRIVATE_SEL(numberWithUnsignedLong_), value); -} - -_NS_INLINE NS::Number* NS::Number::number(long long value) -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSNumber), _NS_PRIVATE_SEL(numberWithLongLong_), value); -} - -_NS_INLINE NS::Number* NS::Number::number(unsigned long long value) -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSNumber), _NS_PRIVATE_SEL(numberWithUnsignedLongLong_), value); -} - -_NS_INLINE NS::Number* NS::Number::number(float value) -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSNumber), _NS_PRIVATE_SEL(numberWithFloat_), value); -} - -_NS_INLINE NS::Number* NS::Number::number(double value) -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSNumber), _NS_PRIVATE_SEL(numberWithDouble_), value); -} - -_NS_INLINE NS::Number* NS::Number::number(bool value) -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSNumber), _NS_PRIVATE_SEL(numberWithBool_), value); -} - -_NS_INLINE NS::Number* NS::Number::alloc() -{ - return NS::Object::alloc(_NS_PRIVATE_CLS(NSNumber)); -} - -_NS_INLINE NS::Number* NS::Number::init(const Coder* pCoder) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(initWithCoder_), pCoder); -} - -_NS_INLINE NS::Number* NS::Number::init(char value) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(initWithChar_), value); -} - -_NS_INLINE NS::Number* NS::Number::init(unsigned char value) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(initWithUnsignedChar_), value); -} - -_NS_INLINE NS::Number* NS::Number::init(short value) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(initWithShort_), value); -} - -_NS_INLINE NS::Number* NS::Number::init(unsigned short value) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(initWithUnsignedShort_), value); -} - -_NS_INLINE NS::Number* NS::Number::init(int value) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(initWithInt_), value); -} - -_NS_INLINE NS::Number* NS::Number::init(unsigned int value) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(initWithUnsignedInt_), value); -} - -_NS_INLINE NS::Number* NS::Number::init(long value) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(initWithLong_), value); -} - -_NS_INLINE NS::Number* NS::Number::init(unsigned long value) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(initWithUnsignedLong_), value); -} - -_NS_INLINE NS::Number* NS::Number::init(long long value) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(initWithLongLong_), value); -} - -_NS_INLINE NS::Number* NS::Number::init(unsigned long long value) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(initWithUnsignedLongLong_), value); -} - -_NS_INLINE NS::Number* NS::Number::init(float value) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(initWithFloat_), value); -} - -_NS_INLINE NS::Number* NS::Number::init(double value) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(initWithDouble_), value); -} - -_NS_INLINE NS::Number* NS::Number::init(bool value) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(initWithBool_), value); -} - -_NS_INLINE char NS::Number::charValue() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(charValue)); -} - -_NS_INLINE unsigned char NS::Number::unsignedCharValue() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(unsignedCharValue)); -} - -_NS_INLINE short NS::Number::shortValue() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(shortValue)); -} - -_NS_INLINE unsigned short NS::Number::unsignedShortValue() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(unsignedShortValue)); -} - -_NS_INLINE int NS::Number::intValue() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(intValue)); -} - -_NS_INLINE unsigned int NS::Number::unsignedIntValue() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(unsignedIntValue)); -} - -_NS_INLINE long NS::Number::longValue() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(longValue)); -} - -_NS_INLINE unsigned long NS::Number::unsignedLongValue() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(unsignedLongValue)); -} - -_NS_INLINE long long NS::Number::longLongValue() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(longLongValue)); -} - -_NS_INLINE unsigned long long NS::Number::unsignedLongLongValue() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(unsignedLongLongValue)); -} - -_NS_INLINE float NS::Number::floatValue() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(floatValue)); -} - -_NS_INLINE double NS::Number::doubleValue() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(doubleValue)); -} - -_NS_INLINE bool NS::Number::boolValue() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(boolValue)); -} - -_NS_INLINE NS::Integer NS::Number::integerValue() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(integerValue)); -} - -_NS_INLINE NS::UInteger NS::Number::unsignedIntegerValue() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(unsignedIntegerValue)); -} - -_NS_INLINE NS::String* NS::Number::stringValue() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(stringValue)); -} - -_NS_INLINE NS::ComparisonResult NS::Number::compare(const Number* pOtherNumber) const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(compare_), pOtherNumber); -} - -_NS_INLINE bool NS::Number::isEqualToNumber(const Number* pNumber) const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(isEqualToNumber_), pNumber); -} - -_NS_INLINE NS::String* NS::Number::descriptionWithLocale(const Object* pLocale) const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(descriptionWithLocale_), pLocale); -} - -#include - -namespace NS -{ -_NS_CONST(NotificationName, ProcessInfoThermalStateDidChangeNotification); -_NS_CONST(NotificationName, ProcessInfoPowerStateDidChangeNotification); - -_NS_ENUM(NS::Integer, ProcessInfoThermalState) { - ProcessInfoThermalStateNominal = 0, - ProcessInfoThermalStateFair = 1, - ProcessInfoThermalStateSerious = 2, - ProcessInfoThermalStateCritical = 3 -}; - -_NS_OPTIONS(std::uint64_t, ActivityOptions) { - ActivityIdleDisplaySleepDisabled = (1ULL << 40), - ActivityIdleSystemSleepDisabled = (1ULL << 20), - ActivitySuddenTerminationDisabled = (1ULL << 14), - ActivityAutomaticTerminationDisabled = (1ULL << 15), - ActivityUserInitiated = (0x00FFFFFFULL | ActivityIdleSystemSleepDisabled), - ActivityUserInitiatedAllowingIdleSystemSleep = (ActivityUserInitiated & ~ActivityIdleSystemSleepDisabled), - ActivityBackground = 0x000000FFULL, - ActivityLatencyCritical = 0xFF00000000ULL, -}; - -class ProcessInfo : public Referencing -{ -public: - static ProcessInfo* processInfo(); - - class Array* arguments() const; - class Dictionary* environment() const; - class String* hostName() const; - class String* processName() const; - void setProcessName(const String* pString); - int processIdentifier() const; - class String* globallyUniqueString() const; - - class String* userName() const; - class String* fullUserName() const; - - UInteger operatingSystem() const; - OperatingSystemVersion operatingSystemVersion() const; - class String* operatingSystemVersionString() const; - bool isOperatingSystemAtLeastVersion(OperatingSystemVersion version) const; - - UInteger processorCount() const; - UInteger activeProcessorCount() const; - unsigned long long physicalMemory() const; - TimeInterval systemUptime() const; - - void disableSuddenTermination(); - void enableSuddenTermination(); - - void disableAutomaticTermination(const class String* pReason); - void enableAutomaticTermination(const class String* pReason); - bool automaticTerminationSupportEnabled() const; - void setAutomaticTerminationSupportEnabled(bool enabled); - - class Object* beginActivity(ActivityOptions options, const class String* pReason); - void endActivity(class Object* pActivity); - void performActivity(ActivityOptions options, const class String* pReason, void (^block)(void)); - void performActivity(ActivityOptions options, const class String* pReason, const std::function& func); - void performExpiringActivity(const class String* pReason, void (^block)(bool expired)); - void performExpiringActivity(const class String* pReason, const std::function& func); - - ProcessInfoThermalState thermalState() const; - bool isLowPowerModeEnabled() const; - - bool isiOSAppOnMac() const; - bool isMacCatalystApp() const; -}; -} - -_NS_PRIVATE_DEF_CONST(NS::NotificationName, ProcessInfoThermalStateDidChangeNotification); -_NS_PRIVATE_DEF_CONST(NS::NotificationName, ProcessInfoPowerStateDidChangeNotification); - -_NS_INLINE NS::ProcessInfo* NS::ProcessInfo::processInfo() -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSProcessInfo), _NS_PRIVATE_SEL(processInfo)); -} - -_NS_INLINE NS::Array* NS::ProcessInfo::arguments() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(arguments)); -} - -_NS_INLINE NS::Dictionary* NS::ProcessInfo::environment() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(environment)); -} - -_NS_INLINE NS::String* NS::ProcessInfo::hostName() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(hostName)); -} - -_NS_INLINE NS::String* NS::ProcessInfo::processName() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(processName)); -} - -_NS_INLINE void NS::ProcessInfo::setProcessName(const String* pString) -{ - Object::sendMessage(this, _NS_PRIVATE_SEL(setProcessName_), pString); -} - -_NS_INLINE int NS::ProcessInfo::processIdentifier() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(processIdentifier)); -} - -_NS_INLINE NS::String* NS::ProcessInfo::globallyUniqueString() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(globallyUniqueString)); -} - -_NS_INLINE NS::String* NS::ProcessInfo::userName() const -{ - return Object::sendMessageSafe(this, _NS_PRIVATE_SEL(userName)); -} - -_NS_INLINE NS::String* NS::ProcessInfo::fullUserName() const -{ - return Object::sendMessageSafe(this, _NS_PRIVATE_SEL(fullUserName)); -} - -_NS_INLINE NS::UInteger NS::ProcessInfo::operatingSystem() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(operatingSystem)); -} - -_NS_INLINE NS::OperatingSystemVersion NS::ProcessInfo::operatingSystemVersion() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(operatingSystemVersion)); -} - -_NS_INLINE NS::String* NS::ProcessInfo::operatingSystemVersionString() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(operatingSystemVersionString)); -} - -_NS_INLINE bool NS::ProcessInfo::isOperatingSystemAtLeastVersion(OperatingSystemVersion version) const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(isOperatingSystemAtLeastVersion_), version); -} - -_NS_INLINE NS::UInteger NS::ProcessInfo::processorCount() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(processorCount)); -} - -_NS_INLINE NS::UInteger NS::ProcessInfo::activeProcessorCount() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(activeProcessorCount)); -} - -_NS_INLINE unsigned long long NS::ProcessInfo::physicalMemory() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(physicalMemory)); -} - -_NS_INLINE NS::TimeInterval NS::ProcessInfo::systemUptime() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(systemUptime)); -} - -_NS_INLINE void NS::ProcessInfo::disableSuddenTermination() -{ - Object::sendMessageSafe(this, _NS_PRIVATE_SEL(disableSuddenTermination)); -} - -_NS_INLINE void NS::ProcessInfo::enableSuddenTermination() -{ - Object::sendMessageSafe(this, _NS_PRIVATE_SEL(enableSuddenTermination)); -} - -_NS_INLINE void NS::ProcessInfo::disableAutomaticTermination(const String* pReason) -{ - Object::sendMessageSafe(this, _NS_PRIVATE_SEL(disableAutomaticTermination_), pReason); -} - -_NS_INLINE void NS::ProcessInfo::enableAutomaticTermination(const String* pReason) -{ - Object::sendMessageSafe(this, _NS_PRIVATE_SEL(enableAutomaticTermination_), pReason); -} - -_NS_INLINE bool NS::ProcessInfo::automaticTerminationSupportEnabled() const -{ - return Object::sendMessageSafe(this, _NS_PRIVATE_SEL(automaticTerminationSupportEnabled)); -} - -_NS_INLINE void NS::ProcessInfo::setAutomaticTerminationSupportEnabled(bool enabled) -{ - Object::sendMessageSafe(this, _NS_PRIVATE_SEL(setAutomaticTerminationSupportEnabled_), enabled); -} - -_NS_INLINE NS::Object* NS::ProcessInfo::beginActivity(ActivityOptions options, const String* pReason) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(beginActivityWithOptions_reason_), options, pReason); -} - -_NS_INLINE void NS::ProcessInfo::endActivity(Object* pActivity) -{ - Object::sendMessage(this, _NS_PRIVATE_SEL(endActivity_), pActivity); -} - -_NS_INLINE void NS::ProcessInfo::performActivity(ActivityOptions options, const String* pReason, void (^block)(void)) -{ - Object::sendMessage(this, _NS_PRIVATE_SEL(performActivityWithOptions_reason_usingBlock_), options, pReason, block); -} - -_NS_INLINE void NS::ProcessInfo::performActivity(ActivityOptions options, const String* pReason, const std::function& function) -{ - __block std::function blockFunction = function; - - performActivity(options, pReason, ^() { blockFunction(); }); -} - -_NS_INLINE void NS::ProcessInfo::performExpiringActivity(const String* pReason, void (^block)(bool expired)) -{ - Object::sendMessageSafe(this, _NS_PRIVATE_SEL(performExpiringActivityWithReason_usingBlock_), pReason, block); -} - -_NS_INLINE void NS::ProcessInfo::performExpiringActivity(const String* pReason, const std::function& function) -{ - __block std::function blockFunction = function; - - performExpiringActivity(pReason, ^(bool expired) { blockFunction(expired); }); -} - -_NS_INLINE NS::ProcessInfoThermalState NS::ProcessInfo::thermalState() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(thermalState)); -} - -_NS_INLINE bool NS::ProcessInfo::isLowPowerModeEnabled() const -{ - return Object::sendMessageSafe(this, _NS_PRIVATE_SEL(isLowPowerModeEnabled)); -} - -_NS_INLINE bool NS::ProcessInfo::isiOSAppOnMac() const -{ - return Object::sendMessageSafe(this, _NS_PRIVATE_SEL(isiOSAppOnMac)); -} - -_NS_INLINE bool NS::ProcessInfo::isMacCatalystApp() const -{ - return Object::sendMessageSafe(this, _NS_PRIVATE_SEL(isMacCatalystApp)); -} - -/*****Immutable Set*******/ - -namespace NS -{ - class Set : public NS::Copying - { - public: - UInteger count() const; - Enumerator* objectEnumerator() const; - - static Set* alloc(); - - Set* init(); - Set* init(const Object* const* pObjects, UInteger count); - Set* init(const class Coder* pCoder); - - }; -} - -_NS_INLINE NS::UInteger NS::Set::count() const -{ - return NS::Object::sendMessage(this, _NS_PRIVATE_SEL(count)); -} - -_NS_INLINE NS::Enumerator* NS::Set::objectEnumerator() const -{ - return NS::Object::sendMessage*>(this, _NS_PRIVATE_SEL(objectEnumerator)); -} - -_NS_INLINE NS::Set* NS::Set::alloc() -{ - return NS::Object::alloc(_NS_PRIVATE_CLS(NSSet)); -} - -_NS_INLINE NS::Set* NS::Set::init() -{ - return NS::Object::init(); -} - -_NS_INLINE NS::Set* NS::Set::init(const Object* const* pObjects, NS::UInteger count) -{ - return NS::Object::sendMessage(this, _NS_PRIVATE_SEL(initWithObjects_count_), pObjects, count); -} - -_NS_INLINE NS::Set* NS::Set::init(const class Coder* pCoder) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(initWithCoder_), pCoder); -} - -#pragma once - -namespace NS -{ -template -class SharedPtr -{ -public: - /** - * Create a new null pointer. - */ - SharedPtr(); - - /** - * Destroy this SharedPtr, decreasing the reference count. - */ - ~SharedPtr(); - - /** - * SharedPtr copy constructor. - */ - SharedPtr(const SharedPtr<_Class>& other) noexcept; - - /** - * Construction from another pointee type. - */ - template - SharedPtr(const SharedPtr<_OtherClass>& other, typename std::enable_if_t> * = nullptr) noexcept; - - /** - * SharedPtr move constructor. - */ - SharedPtr(SharedPtr<_Class>&& other) noexcept; - - /** - * Move from another pointee type. - */ - template - SharedPtr(SharedPtr<_OtherClass>&& other, typename std::enable_if_t> * = nullptr) noexcept; - - /** - * Copy assignment operator. - * Copying increases reference count. Only releases previous pointee if objects are different. - */ - SharedPtr& operator=(const SharedPtr<_Class>& other); - - /** - * Copy-assignment from different pointee. - * Copying increases reference count. Only releases previous pointee if objects are different. - */ - template - typename std::enable_if_t, SharedPtr &> - operator=(const SharedPtr<_OtherClass>& other); - - /** - * Move assignment operator. - * Move without affecting reference counts, unless pointees are equal. Moved-from object is reset to nullptr. - */ - SharedPtr& operator=(SharedPtr<_Class>&& other); - - /** - * Move-asignment from different pointee. - * Move without affecting reference counts, unless pointees are equal. Moved-from object is reset to nullptr. - */ - template - typename std::enable_if_t, SharedPtr &> - operator=(SharedPtr<_OtherClass>&& other); - - /** - * Access raw pointee. - * @warning Avoid wrapping the returned value again, as it may lead double frees unless this object becomes detached. - */ - _Class* get() const; - - /** - * Call operations directly on the pointee. - */ - _Class* operator->() const; - - /** - * Implicit cast to bool. - */ - explicit operator bool() const; - - /** - * Reset this SharedPtr to null, decreasing the reference count. - */ - void reset(); - - /** - * Detach the SharedPtr from the pointee, without decreasing the reference count. - */ - void detach(); - - template - friend SharedPtr<_OtherClass> RetainPtr(_OtherClass* ptr); - - template - friend SharedPtr<_OtherClass> TransferPtr(_OtherClass* ptr); - -private: - _Class* m_pObject; -}; - -/** - * Create a SharedPtr by retaining an existing raw pointer. - * Increases the reference count of the passed-in object. - * If the passed-in object was in an AutoreleasePool, it will be removed from it. - */ -template -_NS_INLINE NS::SharedPtr<_Class> RetainPtr(_Class* pObject) -{ - NS::SharedPtr<_Class> ret; - ret.m_pObject = pObject->retain(); - return ret; -} - -/* - * Create a SharedPtr by transfering the ownership of an existing raw pointer to SharedPtr. - * Does not increase the reference count of the passed-in pointer, it is assumed to be >= 1. - * This method does not remove objects from an AutoreleasePool. -*/ -template -_NS_INLINE NS::SharedPtr<_Class> TransferPtr(_Class* pObject) -{ - NS::SharedPtr<_Class> ret; - ret.m_pObject = pObject; - return ret; -} - -} - -template -_NS_INLINE NS::SharedPtr<_Class>::SharedPtr() - : m_pObject(nullptr) -{ -} - -template -_NS_INLINE NS::SharedPtr<_Class>::~SharedPtr() -{ - if (m_pObject) - { - m_pObject->release(); - } -} - -template -_NS_INLINE NS::SharedPtr<_Class>::SharedPtr(const NS::SharedPtr<_Class>& other) noexcept - : m_pObject(other.m_pObject->retain()) -{ -} - -template -template -_NS_INLINE NS::SharedPtr<_Class>::SharedPtr(const NS::SharedPtr<_OtherClass>& other, typename std::enable_if_t> *) noexcept - : m_pObject(reinterpret_cast<_Class*>(other.get()->retain())) -{ -} - -template -_NS_INLINE NS::SharedPtr<_Class>::SharedPtr(NS::SharedPtr<_Class>&& other) noexcept - : m_pObject(other.m_pObject) -{ - other.m_pObject = nullptr; -} - -template -template -_NS_INLINE NS::SharedPtr<_Class>::SharedPtr(NS::SharedPtr<_OtherClass>&& other, typename std::enable_if_t> *) noexcept - : m_pObject(reinterpret_cast<_Class*>(other.get())) -{ - other.detach(); -} - -template -_NS_INLINE _Class* NS::SharedPtr<_Class>::get() const -{ - return m_pObject; -} - -template -_NS_INLINE _Class* NS::SharedPtr<_Class>::operator->() const -{ - return m_pObject; -} - -template -_NS_INLINE NS::SharedPtr<_Class>::operator bool() const -{ - return nullptr != m_pObject; -} - -template -_NS_INLINE void NS::SharedPtr<_Class>::reset() -{ - m_pObject->release(); - m_pObject = nullptr; -} - -template -_NS_INLINE void NS::SharedPtr<_Class>::detach() -{ - m_pObject = nullptr; -} - -template -_NS_INLINE NS::SharedPtr<_Class>& NS::SharedPtr<_Class>::operator=(const SharedPtr<_Class>& other) -{ - if (m_pObject != other.m_pObject) - { - if (m_pObject) - { - m_pObject->release(); - } - m_pObject = other.m_pObject->retain(); - } - return *this; -} - -template -template -typename std::enable_if_t, NS::SharedPtr<_Class> &> -_NS_INLINE NS::SharedPtr<_Class>::operator=(const SharedPtr<_OtherClass>& other) -{ - if (m_pObject != other.get()) - { - if (m_pObject) - { - m_pObject->release(); - } - m_pObject = reinterpret_cast<_Class*>(other.get()->retain()); - } - return *this; -} - -template -_NS_INLINE NS::SharedPtr<_Class>& NS::SharedPtr<_Class>::operator=(SharedPtr<_Class>&& other) -{ - if (m_pObject != other.m_pObject) - { - if (m_pObject) - { - m_pObject->release(); - } - m_pObject = other.m_pObject; - } - else - { - m_pObject = other.m_pObject; - other.m_pObject->release(); - } - other.m_pObject = nullptr; - return *this; -} - -template -template -typename std::enable_if_t, NS::SharedPtr<_Class> &> -_NS_INLINE NS::SharedPtr<_Class>::operator=(SharedPtr<_OtherClass>&& other) -{ - if (m_pObject != other.get()) - { - if (m_pObject) - { - m_pObject->release(); - } - m_pObject = reinterpret_cast<_Class*>(other.get()); - other.detach(); - } - else - { - m_pObject = other.get(); - other.reset(); - } - return *this; -} - -template -_NS_INLINE bool operator==(const NS::SharedPtr<_ClassLhs>& lhs, const NS::SharedPtr<_ClassRhs>& rhs) -{ - return lhs.get() == rhs.get(); -} - -template -_NS_INLINE bool operator!=(const NS::SharedPtr<_ClassLhs>& lhs, const NS::SharedPtr<_ClassRhs>& rhs) -{ - return lhs.get() != rhs.get(); -} - -namespace NS -{ -class URL : public Copying -{ -public: - static URL* fileURLWithPath(const class String* pPath); - - static URL* alloc(); - URL* init(); - URL* init(const class String* pString); - URL* initFileURLWithPath(const class String* pPath); - - const char* fileSystemRepresentation() const; -}; -} - -_NS_INLINE NS::URL* NS::URL::fileURLWithPath(const String* pPath) -{ - return Object::sendMessage(_NS_PRIVATE_CLS(NSURL), _NS_PRIVATE_SEL(fileURLWithPath_), pPath); -} - -_NS_INLINE NS::URL* NS::URL::alloc() -{ - return Object::alloc(_NS_PRIVATE_CLS(NSURL)); -} - -_NS_INLINE NS::URL* NS::URL::init() -{ - return Object::init(); -} - -_NS_INLINE NS::URL* NS::URL::init(const String* pString) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(initWithString_), pString); -} - -_NS_INLINE NS::URL* NS::URL::initFileURLWithPath(const String* pPath) -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(initFileURLWithPath_), pPath); -} - -_NS_INLINE const char* NS::URL::fileSystemRepresentation() const -{ - return Object::sendMessage(this, _NS_PRIVATE_SEL(fileSystemRepresentation)); -} - -#pragma once - -#define _MTL_EXPORT _NS_EXPORT -#define _MTL_EXTERN _NS_EXTERN -#define _MTL_INLINE _NS_INLINE -#define _MTL_PACKED _NS_PACKED - -#define _MTL_CONST(type, name) _NS_CONST(type, name) -#define _MTL_ENUM(type, name) _NS_ENUM(type, name) -#define _MTL_OPTIONS(type, name) _NS_OPTIONS(type, name) - -#define _MTL_VALIDATE_SIZE(ns, name) _NS_VALIDATE_SIZE(ns, name) -#define _MTL_VALIDATE_ENUM(ns, name) _NS_VALIDATE_ENUM(ns, name) - -#pragma once - -#include - -#define _MTL_PRIVATE_CLS(symbol) (Private::Class::s_k##symbol) -#define _MTL_PRIVATE_SEL(accessor) (Private::Selector::s_k##accessor) - -#if defined(MTL_PRIVATE_IMPLEMENTATION) - -#ifdef METALCPP_SYMBOL_VISIBILITY_HIDDEN -#define _MTL_PRIVATE_VISIBILITY __attribute__((visibility("hidden"))) -#else -#define _MTL_PRIVATE_VISIBILITY __attribute__((visibility("default"))) -#endif // METALCPP_SYMBOL_VISIBILITY_HIDDEN - -#define _MTL_PRIVATE_IMPORT __attribute__((weak_import)) - -#ifdef __OBJC__ -#define _MTL_PRIVATE_OBJC_LOOKUP_CLASS(symbol) ((__bridge void*)objc_lookUpClass(#symbol)) -#define _MTL_PRIVATE_OBJC_GET_PROTOCOL(symbol) ((__bridge void*)objc_getProtocol(#symbol)) -#else -#define _MTL_PRIVATE_OBJC_LOOKUP_CLASS(symbol) objc_lookUpClass(#symbol) -#define _MTL_PRIVATE_OBJC_GET_PROTOCOL(symbol) objc_getProtocol(#symbol) -#endif // __OBJC__ - -#define _MTL_PRIVATE_DEF_CLS(symbol) void* s_k##symbol _MTL_PRIVATE_VISIBILITY = _MTL_PRIVATE_OBJC_LOOKUP_CLASS(symbol) -#define _MTL_PRIVATE_DEF_PRO(symbol) void* s_k##symbol _MTL_PRIVATE_VISIBILITY = _MTL_PRIVATE_OBJC_GET_PROTOCOL(symbol) -#define _MTL_PRIVATE_DEF_SEL(accessor, symbol) SEL s_k##accessor _MTL_PRIVATE_VISIBILITY = sel_registerName(symbol) - -#include -#define MTL_DEF_FUNC( name, signature ) \ - using Fn##name = signature; \ - Fn##name name = reinterpret_cast< Fn##name >( dlsym( RTLD_DEFAULT, #name ) ) - -namespace MTL::Private -{ - template - inline _Type const LoadSymbol(const char* pSymbol) - { - const _Type* pAddress = static_cast<_Type*>(dlsym(RTLD_DEFAULT, pSymbol)); - - return pAddress ? *pAddress : nullptr; - } -} // MTL::Private - -#if defined(__MAC_10_16) || defined(__MAC_11_0) || defined(__MAC_12_0) || defined(__MAC_13_0) || defined(__IPHONE_14_0) || defined(__IPHONE_15_0) || defined(__IPHONE_16_0) || defined(__TVOS_14_0) || defined(__TVOS_15_0) || defined(__TVOS_16_0) - -#define _MTL_PRIVATE_DEF_STR(type, symbol) \ - _MTL_EXTERN type const MTL##symbol _MTL_PRIVATE_IMPORT; \ - type const MTL::symbol = (nullptr != &MTL##symbol) ? MTL##symbol : nullptr - -#define _MTL_PRIVATE_DEF_CONST(type, symbol) \ - _MTL_EXTERN type const MTL##symbol _MTL_PRIVATE_IMPORT; \ - type const MTL::symbol = (nullptr != &MTL##symbol) ? MTL##symbol : nullptr - -#define _MTL_PRIVATE_DEF_WEAK_CONST(type, symbol) \ - _MTL_EXTERN type const MTL##symbol; \ - type const MTL::symbol = Private::LoadSymbol("MTL" #symbol) - -#else - -#define _MTL_PRIVATE_DEF_STR(type, symbol) \ - _MTL_EXTERN type const MTL##symbol; \ - type const MTL::symbol = Private::LoadSymbol("MTL" #symbol) - -#define _MTL_PRIVATE_DEF_CONST(type, symbol) \ - _MTL_EXTERN type const MTL##symbol; \ - type const MTL::symbol = Private::LoadSymbol("MTL" #symbol) - -#define _MTL_PRIVATE_DEF_WEAK_CONST(type, symbol) _MTL_PRIVATE_DEF_CONST(type, symbol) - -#endif // defined(__MAC_10_16) || defined(__MAC_11_0) || defined(__MAC_12_0) || defined(__MAC_13_0) || defined(__IPHONE_14_0) || defined(__IPHONE_15_0) || defined(__IPHONE_16_0) || defined(__TVOS_14_0) || defined(__TVOS_15_0) || defined(__TVOS_16_0) - -#else - -#define _MTL_PRIVATE_DEF_CLS(symbol) extern void* s_k##symbol -#define _MTL_PRIVATE_DEF_PRO(symbol) extern void* s_k##symbol -#define _MTL_PRIVATE_DEF_SEL(accessor, symbol) extern SEL s_k##accessor -#define _MTL_PRIVATE_DEF_STR(type, symbol) extern type const MTL::symbol -#define _MTL_PRIVATE_DEF_CONST(type, symbol) extern type const MTL::symbol -#define _MTL_PRIVATE_DEF_WEAK_CONST(type, symbol) extern type const MTL::symbol - -#endif // MTL_PRIVATE_IMPLEMENTATION - -namespace MTL -{ -namespace Private -{ - namespace Class - { - - } // Class -} // Private -} // MTL - -namespace MTL -{ -namespace Private -{ - namespace Protocol - { - - } // Protocol -} // Private -} // MTL - -namespace MTL -{ -namespace Private -{ - namespace Selector - { - - _MTL_PRIVATE_DEF_SEL(beginScope, - "beginScope"); - _MTL_PRIVATE_DEF_SEL(endScope, - "endScope"); - } // Class -} // Private -} // MTL - -namespace MTL::Private::Class -{ - -_MTL_PRIVATE_DEF_CLS(MTLAccelerationStructureBoundingBoxGeometryDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLAccelerationStructureDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLAccelerationStructureGeometryDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLAccelerationStructureMotionBoundingBoxGeometryDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLAccelerationStructureMotionTriangleGeometryDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLAccelerationStructurePassDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLAccelerationStructurePassSampleBufferAttachmentDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLAccelerationStructurePassSampleBufferAttachmentDescriptorArray); -_MTL_PRIVATE_DEF_CLS(MTLAccelerationStructureTriangleGeometryDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLArgument); -_MTL_PRIVATE_DEF_CLS(MTLArgumentDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLArrayType); -_MTL_PRIVATE_DEF_CLS(MTLAttribute); -_MTL_PRIVATE_DEF_CLS(MTLAttributeDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLAttributeDescriptorArray); -_MTL_PRIVATE_DEF_CLS(MTLBinaryArchiveDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLBlitPassDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLBlitPassSampleBufferAttachmentDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLBlitPassSampleBufferAttachmentDescriptorArray); -_MTL_PRIVATE_DEF_CLS(MTLBufferLayoutDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLBufferLayoutDescriptorArray); -_MTL_PRIVATE_DEF_CLS(MTLCaptureDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLCaptureManager); -_MTL_PRIVATE_DEF_CLS(MTLCommandBufferDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLCompileOptions); -_MTL_PRIVATE_DEF_CLS(MTLComputePassDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLComputePassSampleBufferAttachmentDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLComputePassSampleBufferAttachmentDescriptorArray); -_MTL_PRIVATE_DEF_CLS(MTLComputePipelineDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLComputePipelineReflection); -_MTL_PRIVATE_DEF_CLS(MTLCounterSampleBufferDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLDepthStencilDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLFunctionConstant); -_MTL_PRIVATE_DEF_CLS(MTLFunctionConstantValues); -_MTL_PRIVATE_DEF_CLS(MTLFunctionDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLFunctionStitchingAttributeAlwaysInline); -_MTL_PRIVATE_DEF_CLS(MTLFunctionStitchingFunctionNode); -_MTL_PRIVATE_DEF_CLS(MTLFunctionStitchingGraph); -_MTL_PRIVATE_DEF_CLS(MTLFunctionStitchingInputNode); -_MTL_PRIVATE_DEF_CLS(MTLHeapDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLIOCommandQueueDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLIndirectCommandBufferDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLInstanceAccelerationStructureDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLIntersectionFunctionDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLIntersectionFunctionTableDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLLinkedFunctions); -_MTL_PRIVATE_DEF_CLS(MTLMeshRenderPipelineDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLMotionKeyframeData); -_MTL_PRIVATE_DEF_CLS(MTLPipelineBufferDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLPipelineBufferDescriptorArray); -_MTL_PRIVATE_DEF_CLS(MTLPointerType); -_MTL_PRIVATE_DEF_CLS(MTLPrimitiveAccelerationStructureDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLRasterizationRateLayerArray); -_MTL_PRIVATE_DEF_CLS(MTLRasterizationRateLayerDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLRasterizationRateMapDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLRasterizationRateSampleArray); -_MTL_PRIVATE_DEF_CLS(MTLRenderPassAttachmentDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLRenderPassColorAttachmentDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLRenderPassColorAttachmentDescriptorArray); -_MTL_PRIVATE_DEF_CLS(MTLRenderPassDepthAttachmentDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLRenderPassDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLRenderPassSampleBufferAttachmentDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLRenderPassSampleBufferAttachmentDescriptorArray); -_MTL_PRIVATE_DEF_CLS(MTLRenderPassStencilAttachmentDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLRenderPipelineColorAttachmentDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLRenderPipelineColorAttachmentDescriptorArray); -_MTL_PRIVATE_DEF_CLS(MTLRenderPipelineDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLRenderPipelineFunctionsDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLRenderPipelineReflection); -_MTL_PRIVATE_DEF_CLS(MTLResourceStatePassDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLResourceStatePassSampleBufferAttachmentDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLResourceStatePassSampleBufferAttachmentDescriptorArray); -_MTL_PRIVATE_DEF_CLS(MTLSamplerDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLSharedEventHandle); -_MTL_PRIVATE_DEF_CLS(MTLSharedEventListener); -_MTL_PRIVATE_DEF_CLS(MTLSharedTextureHandle); -_MTL_PRIVATE_DEF_CLS(MTLStageInputOutputDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLStencilDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLStitchedLibraryDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLStructMember); -_MTL_PRIVATE_DEF_CLS(MTLStructType); -_MTL_PRIVATE_DEF_CLS(MTLTextureDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLTextureReferenceType); -_MTL_PRIVATE_DEF_CLS(MTLTileRenderPipelineColorAttachmentDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLTileRenderPipelineColorAttachmentDescriptorArray); -_MTL_PRIVATE_DEF_CLS(MTLTileRenderPipelineDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLType); -_MTL_PRIVATE_DEF_CLS(MTLVertexAttribute); -_MTL_PRIVATE_DEF_CLS(MTLVertexAttributeDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLVertexAttributeDescriptorArray); -_MTL_PRIVATE_DEF_CLS(MTLVertexBufferLayoutDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLVertexBufferLayoutDescriptorArray); -_MTL_PRIVATE_DEF_CLS(MTLVertexDescriptor); -_MTL_PRIVATE_DEF_CLS(MTLVisibleFunctionTableDescriptor); - -} - -namespace MTL::Private::Protocol -{ - -_MTL_PRIVATE_DEF_PRO(MTLAccelerationStructure); -_MTL_PRIVATE_DEF_PRO(MTLAccelerationStructureCommandEncoder); -_MTL_PRIVATE_DEF_PRO(MTLArgumentEncoder); -_MTL_PRIVATE_DEF_PRO(MTLBinaryArchive); -_MTL_PRIVATE_DEF_PRO(MTLBinding); -_MTL_PRIVATE_DEF_PRO(MTLBlitCommandEncoder); -_MTL_PRIVATE_DEF_PRO(MTLBuffer); -_MTL_PRIVATE_DEF_PRO(MTLBufferBinding); -_MTL_PRIVATE_DEF_PRO(MTLCommandBuffer); -_MTL_PRIVATE_DEF_PRO(MTLCommandBufferEncoderInfo); -_MTL_PRIVATE_DEF_PRO(MTLCommandEncoder); -_MTL_PRIVATE_DEF_PRO(MTLCommandQueue); -_MTL_PRIVATE_DEF_PRO(MTLComputeCommandEncoder); -_MTL_PRIVATE_DEF_PRO(MTLComputePipelineState); -_MTL_PRIVATE_DEF_PRO(MTLCounter); -_MTL_PRIVATE_DEF_PRO(MTLCounterSampleBuffer); -_MTL_PRIVATE_DEF_PRO(MTLCounterSet); -_MTL_PRIVATE_DEF_PRO(MTLDepthStencilState); -_MTL_PRIVATE_DEF_PRO(MTLDevice); -_MTL_PRIVATE_DEF_PRO(MTLDrawable); -_MTL_PRIVATE_DEF_PRO(MTLDynamicLibrary); -_MTL_PRIVATE_DEF_PRO(MTLEvent); -_MTL_PRIVATE_DEF_PRO(MTLFence); -_MTL_PRIVATE_DEF_PRO(MTLFunction); -_MTL_PRIVATE_DEF_PRO(MTLFunctionHandle); -_MTL_PRIVATE_DEF_PRO(MTLFunctionLog); -_MTL_PRIVATE_DEF_PRO(MTLFunctionLogDebugLocation); -_MTL_PRIVATE_DEF_PRO(MTLFunctionStitchingAttribute); -_MTL_PRIVATE_DEF_PRO(MTLFunctionStitchingNode); -_MTL_PRIVATE_DEF_PRO(MTLHeap); -_MTL_PRIVATE_DEF_PRO(MTLIOCommandBuffer); -_MTL_PRIVATE_DEF_PRO(MTLIOCommandQueue); -_MTL_PRIVATE_DEF_PRO(MTLIOFileHandle); -_MTL_PRIVATE_DEF_PRO(MTLIOScratchBuffer); -_MTL_PRIVATE_DEF_PRO(MTLIOScratchBufferAllocator); -_MTL_PRIVATE_DEF_PRO(MTLIndirectCommandBuffer); -_MTL_PRIVATE_DEF_PRO(MTLIndirectComputeCommand); -_MTL_PRIVATE_DEF_PRO(MTLIndirectRenderCommand); -_MTL_PRIVATE_DEF_PRO(MTLIntersectionFunctionTable); -_MTL_PRIVATE_DEF_PRO(MTLLibrary); -_MTL_PRIVATE_DEF_PRO(MTLLogContainer); -_MTL_PRIVATE_DEF_PRO(MTLObjectPayloadBinding); -_MTL_PRIVATE_DEF_PRO(MTLParallelRenderCommandEncoder); -_MTL_PRIVATE_DEF_PRO(MTLRasterizationRateMap); -_MTL_PRIVATE_DEF_PRO(MTLRenderCommandEncoder); -_MTL_PRIVATE_DEF_PRO(MTLRenderPipelineState); -_MTL_PRIVATE_DEF_PRO(MTLResource); -_MTL_PRIVATE_DEF_PRO(MTLResourceStateCommandEncoder); -_MTL_PRIVATE_DEF_PRO(MTLSamplerState); -_MTL_PRIVATE_DEF_PRO(MTLSharedEvent); -_MTL_PRIVATE_DEF_PRO(MTLTexture); -_MTL_PRIVATE_DEF_PRO(MTLTextureBinding); -_MTL_PRIVATE_DEF_PRO(MTLThreadgroupBinding); -_MTL_PRIVATE_DEF_PRO(MTLVisibleFunctionTable); - -} - -namespace MTL::Private::Selector -{ - -_MTL_PRIVATE_DEF_SEL(GPUEndTime, - "GPUEndTime"); -_MTL_PRIVATE_DEF_SEL(GPUStartTime, - "GPUStartTime"); -_MTL_PRIVATE_DEF_SEL(URL, - "URL"); -_MTL_PRIVATE_DEF_SEL(accelerationStructureCommandEncoder, - "accelerationStructureCommandEncoder"); -_MTL_PRIVATE_DEF_SEL(accelerationStructureCommandEncoderWithDescriptor_, - "accelerationStructureCommandEncoderWithDescriptor:"); -_MTL_PRIVATE_DEF_SEL(accelerationStructurePassDescriptor, - "accelerationStructurePassDescriptor"); -_MTL_PRIVATE_DEF_SEL(accelerationStructureSizesWithDescriptor_, - "accelerationStructureSizesWithDescriptor:"); -_MTL_PRIVATE_DEF_SEL(access, - "access"); -_MTL_PRIVATE_DEF_SEL(addBarrier, - "addBarrier"); -_MTL_PRIVATE_DEF_SEL(addCompletedHandler_, - "addCompletedHandler:"); -_MTL_PRIVATE_DEF_SEL(addComputePipelineFunctionsWithDescriptor_error_, - "addComputePipelineFunctionsWithDescriptor:error:"); -_MTL_PRIVATE_DEF_SEL(addDebugMarker_range_, - "addDebugMarker:range:"); -_MTL_PRIVATE_DEF_SEL(addFunctionWithDescriptor_library_error_, - "addFunctionWithDescriptor:library:error:"); -_MTL_PRIVATE_DEF_SEL(addPresentedHandler_, - "addPresentedHandler:"); -_MTL_PRIVATE_DEF_SEL(addRenderPipelineFunctionsWithDescriptor_error_, - "addRenderPipelineFunctionsWithDescriptor:error:"); -_MTL_PRIVATE_DEF_SEL(addScheduledHandler_, - "addScheduledHandler:"); -_MTL_PRIVATE_DEF_SEL(addTileRenderPipelineFunctionsWithDescriptor_error_, - "addTileRenderPipelineFunctionsWithDescriptor:error:"); -_MTL_PRIVATE_DEF_SEL(alignment, - "alignment"); -_MTL_PRIVATE_DEF_SEL(allocatedSize, - "allocatedSize"); -_MTL_PRIVATE_DEF_SEL(allowDuplicateIntersectionFunctionInvocation, - "allowDuplicateIntersectionFunctionInvocation"); -_MTL_PRIVATE_DEF_SEL(allowGPUOptimizedContents, - "allowGPUOptimizedContents"); -_MTL_PRIVATE_DEF_SEL(alphaBlendOperation, - "alphaBlendOperation"); -_MTL_PRIVATE_DEF_SEL(areBarycentricCoordsSupported, - "areBarycentricCoordsSupported"); -_MTL_PRIVATE_DEF_SEL(areProgrammableSamplePositionsSupported, - "areProgrammableSamplePositionsSupported"); -_MTL_PRIVATE_DEF_SEL(areRasterOrderGroupsSupported, - "areRasterOrderGroupsSupported"); -_MTL_PRIVATE_DEF_SEL(argumentBuffersSupport, - "argumentBuffersSupport"); -_MTL_PRIVATE_DEF_SEL(argumentDescriptor, - "argumentDescriptor"); -_MTL_PRIVATE_DEF_SEL(argumentIndex, - "argumentIndex"); -_MTL_PRIVATE_DEF_SEL(argumentIndexStride, - "argumentIndexStride"); -_MTL_PRIVATE_DEF_SEL(arguments, - "arguments"); -_MTL_PRIVATE_DEF_SEL(arrayLength, - "arrayLength"); -_MTL_PRIVATE_DEF_SEL(arrayType, - "arrayType"); -_MTL_PRIVATE_DEF_SEL(attributeIndex, - "attributeIndex"); -_MTL_PRIVATE_DEF_SEL(attributeType, - "attributeType"); -_MTL_PRIVATE_DEF_SEL(attributes, - "attributes"); -_MTL_PRIVATE_DEF_SEL(backFaceStencil, - "backFaceStencil"); -_MTL_PRIVATE_DEF_SEL(binaryArchives, - "binaryArchives"); -_MTL_PRIVATE_DEF_SEL(binaryFunctions, - "binaryFunctions"); -_MTL_PRIVATE_DEF_SEL(bindings, - "bindings"); -_MTL_PRIVATE_DEF_SEL(blitCommandEncoder, - "blitCommandEncoder"); -_MTL_PRIVATE_DEF_SEL(blitCommandEncoderWithDescriptor_, - "blitCommandEncoderWithDescriptor:"); -_MTL_PRIVATE_DEF_SEL(blitPassDescriptor, - "blitPassDescriptor"); -_MTL_PRIVATE_DEF_SEL(borderColor, - "borderColor"); -_MTL_PRIVATE_DEF_SEL(boundingBoxBuffer, - "boundingBoxBuffer"); -_MTL_PRIVATE_DEF_SEL(boundingBoxBufferOffset, - "boundingBoxBufferOffset"); -_MTL_PRIVATE_DEF_SEL(boundingBoxBuffers, - "boundingBoxBuffers"); -_MTL_PRIVATE_DEF_SEL(boundingBoxCount, - "boundingBoxCount"); -_MTL_PRIVATE_DEF_SEL(boundingBoxStride, - "boundingBoxStride"); -_MTL_PRIVATE_DEF_SEL(buffer, - "buffer"); -_MTL_PRIVATE_DEF_SEL(bufferAlignment, - "bufferAlignment"); -_MTL_PRIVATE_DEF_SEL(bufferBytesPerRow, - "bufferBytesPerRow"); -_MTL_PRIVATE_DEF_SEL(bufferDataSize, - "bufferDataSize"); -_MTL_PRIVATE_DEF_SEL(bufferDataType, - "bufferDataType"); -_MTL_PRIVATE_DEF_SEL(bufferIndex, - "bufferIndex"); -_MTL_PRIVATE_DEF_SEL(bufferOffset, - "bufferOffset"); -_MTL_PRIVATE_DEF_SEL(bufferPointerType, - "bufferPointerType"); -_MTL_PRIVATE_DEF_SEL(bufferStructType, - "bufferStructType"); -_MTL_PRIVATE_DEF_SEL(buffers, - "buffers"); -_MTL_PRIVATE_DEF_SEL(buildAccelerationStructure_descriptor_scratchBuffer_scratchBufferOffset_, - "buildAccelerationStructure:descriptor:scratchBuffer:scratchBufferOffset:"); -_MTL_PRIVATE_DEF_SEL(captureObject, - "captureObject"); -_MTL_PRIVATE_DEF_SEL(clearBarrier, - "clearBarrier"); -_MTL_PRIVATE_DEF_SEL(clearColor, - "clearColor"); -_MTL_PRIVATE_DEF_SEL(clearDepth, - "clearDepth"); -_MTL_PRIVATE_DEF_SEL(clearStencil, - "clearStencil"); -_MTL_PRIVATE_DEF_SEL(colorAttachments, - "colorAttachments"); -_MTL_PRIVATE_DEF_SEL(column, - "column"); -_MTL_PRIVATE_DEF_SEL(commandBuffer, - "commandBuffer"); -_MTL_PRIVATE_DEF_SEL(commandBufferWithDescriptor_, - "commandBufferWithDescriptor:"); -_MTL_PRIVATE_DEF_SEL(commandBufferWithUnretainedReferences, - "commandBufferWithUnretainedReferences"); -_MTL_PRIVATE_DEF_SEL(commandQueue, - "commandQueue"); -_MTL_PRIVATE_DEF_SEL(commandTypes, - "commandTypes"); -_MTL_PRIVATE_DEF_SEL(commit, - "commit"); -_MTL_PRIVATE_DEF_SEL(compareFunction, - "compareFunction"); -_MTL_PRIVATE_DEF_SEL(compressionType, - "compressionType"); -_MTL_PRIVATE_DEF_SEL(computeCommandEncoder, - "computeCommandEncoder"); -_MTL_PRIVATE_DEF_SEL(computeCommandEncoderWithDescriptor_, - "computeCommandEncoderWithDescriptor:"); -_MTL_PRIVATE_DEF_SEL(computeCommandEncoderWithDispatchType_, - "computeCommandEncoderWithDispatchType:"); -_MTL_PRIVATE_DEF_SEL(computeFunction, - "computeFunction"); -_MTL_PRIVATE_DEF_SEL(computePassDescriptor, - "computePassDescriptor"); -_MTL_PRIVATE_DEF_SEL(concurrentDispatchThreadgroups_threadsPerThreadgroup_, - "concurrentDispatchThreadgroups:threadsPerThreadgroup:"); -_MTL_PRIVATE_DEF_SEL(concurrentDispatchThreads_threadsPerThreadgroup_, - "concurrentDispatchThreads:threadsPerThreadgroup:"); -_MTL_PRIVATE_DEF_SEL(constantBlockAlignment, - "constantBlockAlignment"); -_MTL_PRIVATE_DEF_SEL(constantDataAtIndex_, - "constantDataAtIndex:"); -_MTL_PRIVATE_DEF_SEL(constantValues, - "constantValues"); -_MTL_PRIVATE_DEF_SEL(contents, - "contents"); -_MTL_PRIVATE_DEF_SEL(controlDependencies, - "controlDependencies"); -_MTL_PRIVATE_DEF_SEL(convertSparsePixelRegions_toTileRegions_withTileSize_alignmentMode_numRegions_, - "convertSparsePixelRegions:toTileRegions:withTileSize:alignmentMode:numRegions:"); -_MTL_PRIVATE_DEF_SEL(convertSparseTileRegions_toPixelRegions_withTileSize_numRegions_, - "convertSparseTileRegions:toPixelRegions:withTileSize:numRegions:"); -_MTL_PRIVATE_DEF_SEL(copyAccelerationStructure_toAccelerationStructure_, - "copyAccelerationStructure:toAccelerationStructure:"); -_MTL_PRIVATE_DEF_SEL(copyAndCompactAccelerationStructure_toAccelerationStructure_, - "copyAndCompactAccelerationStructure:toAccelerationStructure:"); -_MTL_PRIVATE_DEF_SEL(copyFromBuffer_sourceOffset_sourceBytesPerRow_sourceBytesPerImage_sourceSize_toTexture_destinationSlice_destinationLevel_destinationOrigin_, - "copyFromBuffer:sourceOffset:sourceBytesPerRow:sourceBytesPerImage:sourceSize:toTexture:destinationSlice:destinationLevel:destinationOrigin:"); -_MTL_PRIVATE_DEF_SEL(copyFromBuffer_sourceOffset_sourceBytesPerRow_sourceBytesPerImage_sourceSize_toTexture_destinationSlice_destinationLevel_destinationOrigin_options_, - "copyFromBuffer:sourceOffset:sourceBytesPerRow:sourceBytesPerImage:sourceSize:toTexture:destinationSlice:destinationLevel:destinationOrigin:options:"); -_MTL_PRIVATE_DEF_SEL(copyFromBuffer_sourceOffset_toBuffer_destinationOffset_size_, - "copyFromBuffer:sourceOffset:toBuffer:destinationOffset:size:"); -_MTL_PRIVATE_DEF_SEL(copyFromTexture_sourceSlice_sourceLevel_sourceOrigin_sourceSize_toBuffer_destinationOffset_destinationBytesPerRow_destinationBytesPerImage_, - "copyFromTexture:sourceSlice:sourceLevel:sourceOrigin:sourceSize:toBuffer:destinationOffset:destinationBytesPerRow:destinationBytesPerImage:"); -_MTL_PRIVATE_DEF_SEL(copyFromTexture_sourceSlice_sourceLevel_sourceOrigin_sourceSize_toBuffer_destinationOffset_destinationBytesPerRow_destinationBytesPerImage_options_, - "copyFromTexture:sourceSlice:sourceLevel:sourceOrigin:sourceSize:toBuffer:destinationOffset:destinationBytesPerRow:destinationBytesPerImage:options:"); -_MTL_PRIVATE_DEF_SEL(copyFromTexture_sourceSlice_sourceLevel_sourceOrigin_sourceSize_toTexture_destinationSlice_destinationLevel_destinationOrigin_, - "copyFromTexture:sourceSlice:sourceLevel:sourceOrigin:sourceSize:toTexture:destinationSlice:destinationLevel:destinationOrigin:"); -_MTL_PRIVATE_DEF_SEL(copyFromTexture_sourceSlice_sourceLevel_toTexture_destinationSlice_destinationLevel_sliceCount_levelCount_, - "copyFromTexture:sourceSlice:sourceLevel:toTexture:destinationSlice:destinationLevel:sliceCount:levelCount:"); -_MTL_PRIVATE_DEF_SEL(copyFromTexture_toTexture_, - "copyFromTexture:toTexture:"); -_MTL_PRIVATE_DEF_SEL(copyIndirectCommandBuffer_sourceRange_destination_destinationIndex_, - "copyIndirectCommandBuffer:sourceRange:destination:destinationIndex:"); -_MTL_PRIVATE_DEF_SEL(copyParameterDataToBuffer_offset_, - "copyParameterDataToBuffer:offset:"); -_MTL_PRIVATE_DEF_SEL(copyStatusToBuffer_offset_, - "copyStatusToBuffer:offset:"); -_MTL_PRIVATE_DEF_SEL(counterSet, - "counterSet"); -_MTL_PRIVATE_DEF_SEL(counterSets, - "counterSets"); -_MTL_PRIVATE_DEF_SEL(counters, - "counters"); -_MTL_PRIVATE_DEF_SEL(cpuCacheMode, - "cpuCacheMode"); -_MTL_PRIVATE_DEF_SEL(currentAllocatedSize, - "currentAllocatedSize"); -_MTL_PRIVATE_DEF_SEL(data, - "data"); -_MTL_PRIVATE_DEF_SEL(dataSize, - "dataSize"); -_MTL_PRIVATE_DEF_SEL(dataType, - "dataType"); -_MTL_PRIVATE_DEF_SEL(dealloc, - "dealloc"); -_MTL_PRIVATE_DEF_SEL(debugLocation, - "debugLocation"); -_MTL_PRIVATE_DEF_SEL(debugSignposts, - "debugSignposts"); -_MTL_PRIVATE_DEF_SEL(defaultCaptureScope, - "defaultCaptureScope"); -_MTL_PRIVATE_DEF_SEL(defaultRasterSampleCount, - "defaultRasterSampleCount"); -_MTL_PRIVATE_DEF_SEL(depth, - "depth"); -_MTL_PRIVATE_DEF_SEL(depthAttachment, - "depthAttachment"); -_MTL_PRIVATE_DEF_SEL(depthAttachmentPixelFormat, - "depthAttachmentPixelFormat"); -_MTL_PRIVATE_DEF_SEL(depthCompareFunction, - "depthCompareFunction"); -_MTL_PRIVATE_DEF_SEL(depthFailureOperation, - "depthFailureOperation"); -_MTL_PRIVATE_DEF_SEL(depthPlane, - "depthPlane"); -_MTL_PRIVATE_DEF_SEL(depthResolveFilter, - "depthResolveFilter"); -_MTL_PRIVATE_DEF_SEL(depthStencilPassOperation, - "depthStencilPassOperation"); -_MTL_PRIVATE_DEF_SEL(descriptor, - "descriptor"); -_MTL_PRIVATE_DEF_SEL(destination, - "destination"); -_MTL_PRIVATE_DEF_SEL(destinationAlphaBlendFactor, - "destinationAlphaBlendFactor"); -_MTL_PRIVATE_DEF_SEL(destinationRGBBlendFactor, - "destinationRGBBlendFactor"); -_MTL_PRIVATE_DEF_SEL(device, - "device"); -_MTL_PRIVATE_DEF_SEL(didModifyRange_, - "didModifyRange:"); -_MTL_PRIVATE_DEF_SEL(dispatchQueue, - "dispatchQueue"); -_MTL_PRIVATE_DEF_SEL(dispatchThreadgroups_threadsPerThreadgroup_, - "dispatchThreadgroups:threadsPerThreadgroup:"); -_MTL_PRIVATE_DEF_SEL(dispatchThreadgroupsWithIndirectBuffer_indirectBufferOffset_threadsPerThreadgroup_, - "dispatchThreadgroupsWithIndirectBuffer:indirectBufferOffset:threadsPerThreadgroup:"); -_MTL_PRIVATE_DEF_SEL(dispatchThreads_threadsPerThreadgroup_, - "dispatchThreads:threadsPerThreadgroup:"); -_MTL_PRIVATE_DEF_SEL(dispatchThreadsPerTile_, - "dispatchThreadsPerTile:"); -_MTL_PRIVATE_DEF_SEL(dispatchType, - "dispatchType"); -_MTL_PRIVATE_DEF_SEL(drawIndexedPatches_patchIndexBuffer_patchIndexBufferOffset_controlPointIndexBuffer_controlPointIndexBufferOffset_indirectBuffer_indirectBufferOffset_, - "drawIndexedPatches:patchIndexBuffer:patchIndexBufferOffset:controlPointIndexBuffer:controlPointIndexBufferOffset:indirectBuffer:indirectBufferOffset:"); -_MTL_PRIVATE_DEF_SEL(drawIndexedPatches_patchStart_patchCount_patchIndexBuffer_patchIndexBufferOffset_controlPointIndexBuffer_controlPointIndexBufferOffset_instanceCount_baseInstance_, - "drawIndexedPatches:patchStart:patchCount:patchIndexBuffer:patchIndexBufferOffset:controlPointIndexBuffer:controlPointIndexBufferOffset:instanceCount:baseInstance:"); -_MTL_PRIVATE_DEF_SEL(drawIndexedPatches_patchStart_patchCount_patchIndexBuffer_patchIndexBufferOffset_controlPointIndexBuffer_controlPointIndexBufferOffset_instanceCount_baseInstance_tessellationFactorBuffer_tessellationFactorBufferOffset_tessellationFactorBufferInstanceStride_, - "drawIndexedPatches:patchStart:patchCount:patchIndexBuffer:patchIndexBufferOffset:controlPointIndexBuffer:controlPointIndexBufferOffset:instanceCount:baseInstance:tessellationFactorBuffer:tessellationFactorBufferOffset:tessellationFactorBufferInstanceStride:"); -_MTL_PRIVATE_DEF_SEL(drawIndexedPrimitives_indexCount_indexType_indexBuffer_indexBufferOffset_, - "drawIndexedPrimitives:indexCount:indexType:indexBuffer:indexBufferOffset:"); -_MTL_PRIVATE_DEF_SEL(drawIndexedPrimitives_indexCount_indexType_indexBuffer_indexBufferOffset_instanceCount_, - "drawIndexedPrimitives:indexCount:indexType:indexBuffer:indexBufferOffset:instanceCount:"); -_MTL_PRIVATE_DEF_SEL(drawIndexedPrimitives_indexCount_indexType_indexBuffer_indexBufferOffset_instanceCount_baseVertex_baseInstance_, - "drawIndexedPrimitives:indexCount:indexType:indexBuffer:indexBufferOffset:instanceCount:baseVertex:baseInstance:"); -_MTL_PRIVATE_DEF_SEL(drawIndexedPrimitives_indexType_indexBuffer_indexBufferOffset_indirectBuffer_indirectBufferOffset_, - "drawIndexedPrimitives:indexType:indexBuffer:indexBufferOffset:indirectBuffer:indirectBufferOffset:"); -_MTL_PRIVATE_DEF_SEL(drawMeshThreadgroups_threadsPerObjectThreadgroup_threadsPerMeshThreadgroup_, - "drawMeshThreadgroups:threadsPerObjectThreadgroup:threadsPerMeshThreadgroup:"); -_MTL_PRIVATE_DEF_SEL(drawMeshThreadgroupsWithIndirectBuffer_indirectBufferOffset_threadsPerObjectThreadgroup_threadsPerMeshThreadgroup_, - "drawMeshThreadgroupsWithIndirectBuffer:indirectBufferOffset:threadsPerObjectThreadgroup:threadsPerMeshThreadgroup:"); -_MTL_PRIVATE_DEF_SEL(drawMeshThreads_threadsPerObjectThreadgroup_threadsPerMeshThreadgroup_, - "drawMeshThreads:threadsPerObjectThreadgroup:threadsPerMeshThreadgroup:"); -_MTL_PRIVATE_DEF_SEL(drawPatches_patchIndexBuffer_patchIndexBufferOffset_indirectBuffer_indirectBufferOffset_, - "drawPatches:patchIndexBuffer:patchIndexBufferOffset:indirectBuffer:indirectBufferOffset:"); -_MTL_PRIVATE_DEF_SEL(drawPatches_patchStart_patchCount_patchIndexBuffer_patchIndexBufferOffset_instanceCount_baseInstance_, - "drawPatches:patchStart:patchCount:patchIndexBuffer:patchIndexBufferOffset:instanceCount:baseInstance:"); -_MTL_PRIVATE_DEF_SEL(drawPatches_patchStart_patchCount_patchIndexBuffer_patchIndexBufferOffset_instanceCount_baseInstance_tessellationFactorBuffer_tessellationFactorBufferOffset_tessellationFactorBufferInstanceStride_, - "drawPatches:patchStart:patchCount:patchIndexBuffer:patchIndexBufferOffset:instanceCount:baseInstance:tessellationFactorBuffer:tessellationFactorBufferOffset:tessellationFactorBufferInstanceStride:"); -_MTL_PRIVATE_DEF_SEL(drawPrimitives_indirectBuffer_indirectBufferOffset_, - "drawPrimitives:indirectBuffer:indirectBufferOffset:"); -_MTL_PRIVATE_DEF_SEL(drawPrimitives_vertexStart_vertexCount_, - "drawPrimitives:vertexStart:vertexCount:"); -_MTL_PRIVATE_DEF_SEL(drawPrimitives_vertexStart_vertexCount_instanceCount_, - "drawPrimitives:vertexStart:vertexCount:instanceCount:"); -_MTL_PRIVATE_DEF_SEL(drawPrimitives_vertexStart_vertexCount_instanceCount_baseInstance_, - "drawPrimitives:vertexStart:vertexCount:instanceCount:baseInstance:"); -_MTL_PRIVATE_DEF_SEL(drawableID, - "drawableID"); -_MTL_PRIVATE_DEF_SEL(elementArrayType, - "elementArrayType"); -_MTL_PRIVATE_DEF_SEL(elementIsArgumentBuffer, - "elementIsArgumentBuffer"); -_MTL_PRIVATE_DEF_SEL(elementPointerType, - "elementPointerType"); -_MTL_PRIVATE_DEF_SEL(elementStructType, - "elementStructType"); -_MTL_PRIVATE_DEF_SEL(elementTextureReferenceType, - "elementTextureReferenceType"); -_MTL_PRIVATE_DEF_SEL(elementType, - "elementType"); -_MTL_PRIVATE_DEF_SEL(encodeSignalEvent_value_, - "encodeSignalEvent:value:"); -_MTL_PRIVATE_DEF_SEL(encodeWaitForEvent_value_, - "encodeWaitForEvent:value:"); -_MTL_PRIVATE_DEF_SEL(encodedLength, - "encodedLength"); -_MTL_PRIVATE_DEF_SEL(encoderLabel, - "encoderLabel"); -_MTL_PRIVATE_DEF_SEL(endEncoding, - "endEncoding"); -_MTL_PRIVATE_DEF_SEL(endOfEncoderSampleIndex, - "endOfEncoderSampleIndex"); -_MTL_PRIVATE_DEF_SEL(endOfFragmentSampleIndex, - "endOfFragmentSampleIndex"); -_MTL_PRIVATE_DEF_SEL(endOfVertexSampleIndex, - "endOfVertexSampleIndex"); -_MTL_PRIVATE_DEF_SEL(enqueue, - "enqueue"); -_MTL_PRIVATE_DEF_SEL(enqueueBarrier, - "enqueueBarrier"); -_MTL_PRIVATE_DEF_SEL(error, - "error"); -_MTL_PRIVATE_DEF_SEL(errorOptions, - "errorOptions"); -_MTL_PRIVATE_DEF_SEL(errorState, - "errorState"); -_MTL_PRIVATE_DEF_SEL(executeCommandsInBuffer_indirectBuffer_indirectBufferOffset_, - "executeCommandsInBuffer:indirectBuffer:indirectBufferOffset:"); -_MTL_PRIVATE_DEF_SEL(executeCommandsInBuffer_withRange_, - "executeCommandsInBuffer:withRange:"); -_MTL_PRIVATE_DEF_SEL(fastMathEnabled, - "fastMathEnabled"); -_MTL_PRIVATE_DEF_SEL(fillBuffer_range_value_, - "fillBuffer:range:value:"); -_MTL_PRIVATE_DEF_SEL(firstMipmapInTail, - "firstMipmapInTail"); -_MTL_PRIVATE_DEF_SEL(format, - "format"); -_MTL_PRIVATE_DEF_SEL(fragmentAdditionalBinaryFunctions, - "fragmentAdditionalBinaryFunctions"); -_MTL_PRIVATE_DEF_SEL(fragmentArguments, - "fragmentArguments"); -_MTL_PRIVATE_DEF_SEL(fragmentBindings, - "fragmentBindings"); -_MTL_PRIVATE_DEF_SEL(fragmentBuffers, - "fragmentBuffers"); -_MTL_PRIVATE_DEF_SEL(fragmentFunction, - "fragmentFunction"); -_MTL_PRIVATE_DEF_SEL(fragmentLinkedFunctions, - "fragmentLinkedFunctions"); -_MTL_PRIVATE_DEF_SEL(fragmentPreloadedLibraries, - "fragmentPreloadedLibraries"); -_MTL_PRIVATE_DEF_SEL(frontFaceStencil, - "frontFaceStencil"); -_MTL_PRIVATE_DEF_SEL(function, - "function"); -_MTL_PRIVATE_DEF_SEL(functionConstantsDictionary, - "functionConstantsDictionary"); -_MTL_PRIVATE_DEF_SEL(functionCount, - "functionCount"); -_MTL_PRIVATE_DEF_SEL(functionDescriptor, - "functionDescriptor"); -_MTL_PRIVATE_DEF_SEL(functionGraphs, - "functionGraphs"); -_MTL_PRIVATE_DEF_SEL(functionHandleWithFunction_, - "functionHandleWithFunction:"); -_MTL_PRIVATE_DEF_SEL(functionHandleWithFunction_stage_, - "functionHandleWithFunction:stage:"); -_MTL_PRIVATE_DEF_SEL(functionName, - "functionName"); -_MTL_PRIVATE_DEF_SEL(functionNames, - "functionNames"); -_MTL_PRIVATE_DEF_SEL(functionType, - "functionType"); -_MTL_PRIVATE_DEF_SEL(functions, - "functions"); -_MTL_PRIVATE_DEF_SEL(generateMipmapsForTexture_, - "generateMipmapsForTexture:"); -_MTL_PRIVATE_DEF_SEL(geometryDescriptors, - "geometryDescriptors"); -_MTL_PRIVATE_DEF_SEL(getBytes_bytesPerRow_bytesPerImage_fromRegion_mipmapLevel_slice_, - "getBytes:bytesPerRow:bytesPerImage:fromRegion:mipmapLevel:slice:"); -_MTL_PRIVATE_DEF_SEL(getBytes_bytesPerRow_fromRegion_mipmapLevel_, - "getBytes:bytesPerRow:fromRegion:mipmapLevel:"); -_MTL_PRIVATE_DEF_SEL(getDefaultSamplePositions_count_, - "getDefaultSamplePositions:count:"); -_MTL_PRIVATE_DEF_SEL(getSamplePositions_count_, - "getSamplePositions:count:"); -_MTL_PRIVATE_DEF_SEL(getTextureAccessCounters_region_mipLevel_slice_resetCounters_countersBuffer_countersBufferOffset_, - "getTextureAccessCounters:region:mipLevel:slice:resetCounters:countersBuffer:countersBufferOffset:"); -_MTL_PRIVATE_DEF_SEL(gpuAddress, - "gpuAddress"); -_MTL_PRIVATE_DEF_SEL(gpuResourceID, - "gpuResourceID"); -_MTL_PRIVATE_DEF_SEL(groups, - "groups"); -_MTL_PRIVATE_DEF_SEL(hasUnifiedMemory, - "hasUnifiedMemory"); -_MTL_PRIVATE_DEF_SEL(hazardTrackingMode, - "hazardTrackingMode"); -_MTL_PRIVATE_DEF_SEL(heap, - "heap"); -_MTL_PRIVATE_DEF_SEL(heapAccelerationStructureSizeAndAlignWithDescriptor_, - "heapAccelerationStructureSizeAndAlignWithDescriptor:"); -_MTL_PRIVATE_DEF_SEL(heapAccelerationStructureSizeAndAlignWithSize_, - "heapAccelerationStructureSizeAndAlignWithSize:"); -_MTL_PRIVATE_DEF_SEL(heapBufferSizeAndAlignWithLength_options_, - "heapBufferSizeAndAlignWithLength:options:"); -_MTL_PRIVATE_DEF_SEL(heapOffset, - "heapOffset"); -_MTL_PRIVATE_DEF_SEL(heapTextureSizeAndAlignWithDescriptor_, - "heapTextureSizeAndAlignWithDescriptor:"); -_MTL_PRIVATE_DEF_SEL(height, - "height"); -_MTL_PRIVATE_DEF_SEL(horizontal, - "horizontal"); -_MTL_PRIVATE_DEF_SEL(horizontalSampleStorage, - "horizontalSampleStorage"); -_MTL_PRIVATE_DEF_SEL(imageblockMemoryLengthForDimensions_, - "imageblockMemoryLengthForDimensions:"); -_MTL_PRIVATE_DEF_SEL(imageblockSampleLength, - "imageblockSampleLength"); -_MTL_PRIVATE_DEF_SEL(index, - "index"); -_MTL_PRIVATE_DEF_SEL(indexBuffer, - "indexBuffer"); -_MTL_PRIVATE_DEF_SEL(indexBufferIndex, - "indexBufferIndex"); -_MTL_PRIVATE_DEF_SEL(indexBufferOffset, - "indexBufferOffset"); -_MTL_PRIVATE_DEF_SEL(indexType, - "indexType"); -_MTL_PRIVATE_DEF_SEL(indirectComputeCommandAtIndex_, - "indirectComputeCommandAtIndex:"); -_MTL_PRIVATE_DEF_SEL(indirectRenderCommandAtIndex_, - "indirectRenderCommandAtIndex:"); -_MTL_PRIVATE_DEF_SEL(inheritBuffers, - "inheritBuffers"); -_MTL_PRIVATE_DEF_SEL(inheritPipelineState, - "inheritPipelineState"); -_MTL_PRIVATE_DEF_SEL(init, - "init"); -_MTL_PRIVATE_DEF_SEL(initWithArgumentIndex_, - "initWithArgumentIndex:"); -_MTL_PRIVATE_DEF_SEL(initWithDispatchQueue_, - "initWithDispatchQueue:"); -_MTL_PRIVATE_DEF_SEL(initWithFunctionName_nodes_outputNode_attributes_, - "initWithFunctionName:nodes:outputNode:attributes:"); -_MTL_PRIVATE_DEF_SEL(initWithName_arguments_controlDependencies_, - "initWithName:arguments:controlDependencies:"); -_MTL_PRIVATE_DEF_SEL(initWithSampleCount_, - "initWithSampleCount:"); -_MTL_PRIVATE_DEF_SEL(initWithSampleCount_horizontal_vertical_, - "initWithSampleCount:horizontal:vertical:"); -_MTL_PRIVATE_DEF_SEL(inputPrimitiveTopology, - "inputPrimitiveTopology"); -_MTL_PRIVATE_DEF_SEL(insertDebugCaptureBoundary, - "insertDebugCaptureBoundary"); -_MTL_PRIVATE_DEF_SEL(insertDebugSignpost_, - "insertDebugSignpost:"); -_MTL_PRIVATE_DEF_SEL(insertLibraries, - "insertLibraries"); -_MTL_PRIVATE_DEF_SEL(installName, - "installName"); -_MTL_PRIVATE_DEF_SEL(instanceCount, - "instanceCount"); -_MTL_PRIVATE_DEF_SEL(instanceDescriptorBuffer, - "instanceDescriptorBuffer"); -_MTL_PRIVATE_DEF_SEL(instanceDescriptorBufferOffset, - "instanceDescriptorBufferOffset"); -_MTL_PRIVATE_DEF_SEL(instanceDescriptorStride, - "instanceDescriptorStride"); -_MTL_PRIVATE_DEF_SEL(instanceDescriptorType, - "instanceDescriptorType"); -_MTL_PRIVATE_DEF_SEL(instancedAccelerationStructures, - "instancedAccelerationStructures"); -_MTL_PRIVATE_DEF_SEL(intersectionFunctionTableDescriptor, - "intersectionFunctionTableDescriptor"); -_MTL_PRIVATE_DEF_SEL(intersectionFunctionTableOffset, - "intersectionFunctionTableOffset"); -_MTL_PRIVATE_DEF_SEL(iosurface, - "iosurface"); -_MTL_PRIVATE_DEF_SEL(iosurfacePlane, - "iosurfacePlane"); -_MTL_PRIVATE_DEF_SEL(isActive, - "isActive"); -_MTL_PRIVATE_DEF_SEL(isAliasable, - "isAliasable"); -_MTL_PRIVATE_DEF_SEL(isAlphaToCoverageEnabled, - "isAlphaToCoverageEnabled"); -_MTL_PRIVATE_DEF_SEL(isAlphaToOneEnabled, - "isAlphaToOneEnabled"); -_MTL_PRIVATE_DEF_SEL(isArgument, - "isArgument"); -_MTL_PRIVATE_DEF_SEL(isBlendingEnabled, - "isBlendingEnabled"); -_MTL_PRIVATE_DEF_SEL(isCapturing, - "isCapturing"); -_MTL_PRIVATE_DEF_SEL(isDepth24Stencil8PixelFormatSupported, - "isDepth24Stencil8PixelFormatSupported"); -_MTL_PRIVATE_DEF_SEL(isDepthTexture, - "isDepthTexture"); -_MTL_PRIVATE_DEF_SEL(isDepthWriteEnabled, - "isDepthWriteEnabled"); -_MTL_PRIVATE_DEF_SEL(isFramebufferOnly, - "isFramebufferOnly"); -_MTL_PRIVATE_DEF_SEL(isHeadless, - "isHeadless"); -_MTL_PRIVATE_DEF_SEL(isLowPower, - "isLowPower"); -_MTL_PRIVATE_DEF_SEL(isPatchControlPointData, - "isPatchControlPointData"); -_MTL_PRIVATE_DEF_SEL(isPatchData, - "isPatchData"); -_MTL_PRIVATE_DEF_SEL(isRasterizationEnabled, - "isRasterizationEnabled"); -_MTL_PRIVATE_DEF_SEL(isRemovable, - "isRemovable"); -_MTL_PRIVATE_DEF_SEL(isShareable, - "isShareable"); -_MTL_PRIVATE_DEF_SEL(isSparse, - "isSparse"); -_MTL_PRIVATE_DEF_SEL(isTessellationFactorScaleEnabled, - "isTessellationFactorScaleEnabled"); -_MTL_PRIVATE_DEF_SEL(isUsed, - "isUsed"); -_MTL_PRIVATE_DEF_SEL(kernelEndTime, - "kernelEndTime"); -_MTL_PRIVATE_DEF_SEL(kernelStartTime, - "kernelStartTime"); -_MTL_PRIVATE_DEF_SEL(label, - "label"); -_MTL_PRIVATE_DEF_SEL(languageVersion, - "languageVersion"); -_MTL_PRIVATE_DEF_SEL(layerAtIndex_, - "layerAtIndex:"); -_MTL_PRIVATE_DEF_SEL(layerCount, - "layerCount"); -_MTL_PRIVATE_DEF_SEL(layers, - "layers"); -_MTL_PRIVATE_DEF_SEL(layouts, - "layouts"); -_MTL_PRIVATE_DEF_SEL(length, - "length"); -_MTL_PRIVATE_DEF_SEL(level, - "level"); -_MTL_PRIVATE_DEF_SEL(libraries, - "libraries"); -_MTL_PRIVATE_DEF_SEL(libraryType, - "libraryType"); -_MTL_PRIVATE_DEF_SEL(line, - "line"); -_MTL_PRIVATE_DEF_SEL(linkedFunctions, - "linkedFunctions"); -_MTL_PRIVATE_DEF_SEL(loadAction, - "loadAction"); -_MTL_PRIVATE_DEF_SEL(loadBuffer_offset_size_sourceHandle_sourceHandleOffset_, - "loadBuffer:offset:size:sourceHandle:sourceHandleOffset:"); -_MTL_PRIVATE_DEF_SEL(loadBytes_size_sourceHandle_sourceHandleOffset_, - "loadBytes:size:sourceHandle:sourceHandleOffset:"); -_MTL_PRIVATE_DEF_SEL(loadTexture_slice_level_size_sourceBytesPerRow_sourceBytesPerImage_destinationOrigin_sourceHandle_sourceHandleOffset_, - "loadTexture:slice:level:size:sourceBytesPerRow:sourceBytesPerImage:destinationOrigin:sourceHandle:sourceHandleOffset:"); -_MTL_PRIVATE_DEF_SEL(location, - "location"); -_MTL_PRIVATE_DEF_SEL(locationNumber, - "locationNumber"); -_MTL_PRIVATE_DEF_SEL(lodAverage, - "lodAverage"); -_MTL_PRIVATE_DEF_SEL(lodMaxClamp, - "lodMaxClamp"); -_MTL_PRIVATE_DEF_SEL(lodMinClamp, - "lodMinClamp"); -_MTL_PRIVATE_DEF_SEL(logs, - "logs"); -_MTL_PRIVATE_DEF_SEL(magFilter, - "magFilter"); -_MTL_PRIVATE_DEF_SEL(makeAliasable, - "makeAliasable"); -_MTL_PRIVATE_DEF_SEL(mapPhysicalToScreenCoordinates_forLayer_, - "mapPhysicalToScreenCoordinates:forLayer:"); -_MTL_PRIVATE_DEF_SEL(mapScreenToPhysicalCoordinates_forLayer_, - "mapScreenToPhysicalCoordinates:forLayer:"); -_MTL_PRIVATE_DEF_SEL(maxAnisotropy, - "maxAnisotropy"); -_MTL_PRIVATE_DEF_SEL(maxArgumentBufferSamplerCount, - "maxArgumentBufferSamplerCount"); -_MTL_PRIVATE_DEF_SEL(maxAvailableSizeWithAlignment_, - "maxAvailableSizeWithAlignment:"); -_MTL_PRIVATE_DEF_SEL(maxBufferLength, - "maxBufferLength"); -_MTL_PRIVATE_DEF_SEL(maxCallStackDepth, - "maxCallStackDepth"); -_MTL_PRIVATE_DEF_SEL(maxCommandBufferCount, - "maxCommandBufferCount"); -_MTL_PRIVATE_DEF_SEL(maxCommandsInFlight, - "maxCommandsInFlight"); -_MTL_PRIVATE_DEF_SEL(maxFragmentBufferBindCount, - "maxFragmentBufferBindCount"); -_MTL_PRIVATE_DEF_SEL(maxFragmentCallStackDepth, - "maxFragmentCallStackDepth"); -_MTL_PRIVATE_DEF_SEL(maxKernelBufferBindCount, - "maxKernelBufferBindCount"); -_MTL_PRIVATE_DEF_SEL(maxSampleCount, - "maxSampleCount"); -_MTL_PRIVATE_DEF_SEL(maxTessellationFactor, - "maxTessellationFactor"); -_MTL_PRIVATE_DEF_SEL(maxThreadgroupMemoryLength, - "maxThreadgroupMemoryLength"); -_MTL_PRIVATE_DEF_SEL(maxThreadsPerThreadgroup, - "maxThreadsPerThreadgroup"); -_MTL_PRIVATE_DEF_SEL(maxTotalThreadgroupsPerMeshGrid, - "maxTotalThreadgroupsPerMeshGrid"); -_MTL_PRIVATE_DEF_SEL(maxTotalThreadsPerMeshThreadgroup, - "maxTotalThreadsPerMeshThreadgroup"); -_MTL_PRIVATE_DEF_SEL(maxTotalThreadsPerObjectThreadgroup, - "maxTotalThreadsPerObjectThreadgroup"); -_MTL_PRIVATE_DEF_SEL(maxTotalThreadsPerThreadgroup, - "maxTotalThreadsPerThreadgroup"); -_MTL_PRIVATE_DEF_SEL(maxTransferRate, - "maxTransferRate"); -_MTL_PRIVATE_DEF_SEL(maxVertexAmplificationCount, - "maxVertexAmplificationCount"); -_MTL_PRIVATE_DEF_SEL(maxVertexBufferBindCount, - "maxVertexBufferBindCount"); -_MTL_PRIVATE_DEF_SEL(maxVertexCallStackDepth, - "maxVertexCallStackDepth"); -_MTL_PRIVATE_DEF_SEL(memberByName_, - "memberByName:"); -_MTL_PRIVATE_DEF_SEL(members, - "members"); -_MTL_PRIVATE_DEF_SEL(memoryBarrierWithResources_count_, - "memoryBarrierWithResources:count:"); -_MTL_PRIVATE_DEF_SEL(memoryBarrierWithResources_count_afterStages_beforeStages_, - "memoryBarrierWithResources:count:afterStages:beforeStages:"); -_MTL_PRIVATE_DEF_SEL(memoryBarrierWithScope_, - "memoryBarrierWithScope:"); -_MTL_PRIVATE_DEF_SEL(memoryBarrierWithScope_afterStages_beforeStages_, - "memoryBarrierWithScope:afterStages:beforeStages:"); -_MTL_PRIVATE_DEF_SEL(meshBindings, - "meshBindings"); -_MTL_PRIVATE_DEF_SEL(meshBuffers, - "meshBuffers"); -_MTL_PRIVATE_DEF_SEL(meshFunction, - "meshFunction"); -_MTL_PRIVATE_DEF_SEL(meshThreadExecutionWidth, - "meshThreadExecutionWidth"); -_MTL_PRIVATE_DEF_SEL(meshThreadgroupSizeIsMultipleOfThreadExecutionWidth, - "meshThreadgroupSizeIsMultipleOfThreadExecutionWidth"); -_MTL_PRIVATE_DEF_SEL(minFilter, - "minFilter"); -_MTL_PRIVATE_DEF_SEL(minimumLinearTextureAlignmentForPixelFormat_, - "minimumLinearTextureAlignmentForPixelFormat:"); -_MTL_PRIVATE_DEF_SEL(minimumTextureBufferAlignmentForPixelFormat_, - "minimumTextureBufferAlignmentForPixelFormat:"); -_MTL_PRIVATE_DEF_SEL(mipFilter, - "mipFilter"); -_MTL_PRIVATE_DEF_SEL(mipmapLevelCount, - "mipmapLevelCount"); -_MTL_PRIVATE_DEF_SEL(motionEndBorderMode, - "motionEndBorderMode"); -_MTL_PRIVATE_DEF_SEL(motionEndTime, - "motionEndTime"); -_MTL_PRIVATE_DEF_SEL(motionKeyframeCount, - "motionKeyframeCount"); -_MTL_PRIVATE_DEF_SEL(motionStartBorderMode, - "motionStartBorderMode"); -_MTL_PRIVATE_DEF_SEL(motionStartTime, - "motionStartTime"); -_MTL_PRIVATE_DEF_SEL(motionTransformBuffer, - "motionTransformBuffer"); -_MTL_PRIVATE_DEF_SEL(motionTransformBufferOffset, - "motionTransformBufferOffset"); -_MTL_PRIVATE_DEF_SEL(motionTransformCount, - "motionTransformCount"); -_MTL_PRIVATE_DEF_SEL(moveTextureMappingsFromTexture_sourceSlice_sourceLevel_sourceOrigin_sourceSize_toTexture_destinationSlice_destinationLevel_destinationOrigin_, - "moveTextureMappingsFromTexture:sourceSlice:sourceLevel:sourceOrigin:sourceSize:toTexture:destinationSlice:destinationLevel:destinationOrigin:"); -_MTL_PRIVATE_DEF_SEL(mutability, - "mutability"); -_MTL_PRIVATE_DEF_SEL(name, - "name"); -_MTL_PRIVATE_DEF_SEL(newAccelerationStructureWithDescriptor_, - "newAccelerationStructureWithDescriptor:"); -_MTL_PRIVATE_DEF_SEL(newAccelerationStructureWithDescriptor_offset_, - "newAccelerationStructureWithDescriptor:offset:"); -_MTL_PRIVATE_DEF_SEL(newAccelerationStructureWithSize_, - "newAccelerationStructureWithSize:"); -_MTL_PRIVATE_DEF_SEL(newAccelerationStructureWithSize_offset_, - "newAccelerationStructureWithSize:offset:"); -_MTL_PRIVATE_DEF_SEL(newArgumentEncoderForBufferAtIndex_, - "newArgumentEncoderForBufferAtIndex:"); -_MTL_PRIVATE_DEF_SEL(newArgumentEncoderWithArguments_, - "newArgumentEncoderWithArguments:"); -_MTL_PRIVATE_DEF_SEL(newArgumentEncoderWithBufferBinding_, - "newArgumentEncoderWithBufferBinding:"); -_MTL_PRIVATE_DEF_SEL(newArgumentEncoderWithBufferIndex_, - "newArgumentEncoderWithBufferIndex:"); -_MTL_PRIVATE_DEF_SEL(newArgumentEncoderWithBufferIndex_reflection_, - "newArgumentEncoderWithBufferIndex:reflection:"); -_MTL_PRIVATE_DEF_SEL(newBinaryArchiveWithDescriptor_error_, - "newBinaryArchiveWithDescriptor:error:"); -_MTL_PRIVATE_DEF_SEL(newBufferWithBytes_length_options_, - "newBufferWithBytes:length:options:"); -_MTL_PRIVATE_DEF_SEL(newBufferWithBytesNoCopy_length_options_deallocator_, - "newBufferWithBytesNoCopy:length:options:deallocator:"); -_MTL_PRIVATE_DEF_SEL(newBufferWithLength_options_, - "newBufferWithLength:options:"); -_MTL_PRIVATE_DEF_SEL(newBufferWithLength_options_offset_, - "newBufferWithLength:options:offset:"); -_MTL_PRIVATE_DEF_SEL(newCaptureScopeWithCommandQueue_, - "newCaptureScopeWithCommandQueue:"); -_MTL_PRIVATE_DEF_SEL(newCaptureScopeWithDevice_, - "newCaptureScopeWithDevice:"); -_MTL_PRIVATE_DEF_SEL(newCommandQueue, - "newCommandQueue"); -_MTL_PRIVATE_DEF_SEL(newCommandQueueWithMaxCommandBufferCount_, - "newCommandQueueWithMaxCommandBufferCount:"); -_MTL_PRIVATE_DEF_SEL(newComputePipelineStateWithAdditionalBinaryFunctions_error_, - "newComputePipelineStateWithAdditionalBinaryFunctions:error:"); -_MTL_PRIVATE_DEF_SEL(newComputePipelineStateWithDescriptor_options_completionHandler_, - "newComputePipelineStateWithDescriptor:options:completionHandler:"); -_MTL_PRIVATE_DEF_SEL(newComputePipelineStateWithDescriptor_options_reflection_error_, - "newComputePipelineStateWithDescriptor:options:reflection:error:"); -_MTL_PRIVATE_DEF_SEL(newComputePipelineStateWithFunction_completionHandler_, - "newComputePipelineStateWithFunction:completionHandler:"); -_MTL_PRIVATE_DEF_SEL(newComputePipelineStateWithFunction_error_, - "newComputePipelineStateWithFunction:error:"); -_MTL_PRIVATE_DEF_SEL(newComputePipelineStateWithFunction_options_completionHandler_, - "newComputePipelineStateWithFunction:options:completionHandler:"); -_MTL_PRIVATE_DEF_SEL(newComputePipelineStateWithFunction_options_reflection_error_, - "newComputePipelineStateWithFunction:options:reflection:error:"); -_MTL_PRIVATE_DEF_SEL(newCounterSampleBufferWithDescriptor_error_, - "newCounterSampleBufferWithDescriptor:error:"); -_MTL_PRIVATE_DEF_SEL(newDefaultLibrary, - "newDefaultLibrary"); -_MTL_PRIVATE_DEF_SEL(newDefaultLibraryWithBundle_error_, - "newDefaultLibraryWithBundle:error:"); -_MTL_PRIVATE_DEF_SEL(newDepthStencilStateWithDescriptor_, - "newDepthStencilStateWithDescriptor:"); -_MTL_PRIVATE_DEF_SEL(newDynamicLibrary_error_, - "newDynamicLibrary:error:"); -_MTL_PRIVATE_DEF_SEL(newDynamicLibraryWithURL_error_, - "newDynamicLibraryWithURL:error:"); -_MTL_PRIVATE_DEF_SEL(newEvent, - "newEvent"); -_MTL_PRIVATE_DEF_SEL(newFence, - "newFence"); -_MTL_PRIVATE_DEF_SEL(newFunctionWithDescriptor_completionHandler_, - "newFunctionWithDescriptor:completionHandler:"); -_MTL_PRIVATE_DEF_SEL(newFunctionWithDescriptor_error_, - "newFunctionWithDescriptor:error:"); -_MTL_PRIVATE_DEF_SEL(newFunctionWithName_, - "newFunctionWithName:"); -_MTL_PRIVATE_DEF_SEL(newFunctionWithName_constantValues_completionHandler_, - "newFunctionWithName:constantValues:completionHandler:"); -_MTL_PRIVATE_DEF_SEL(newFunctionWithName_constantValues_error_, - "newFunctionWithName:constantValues:error:"); -_MTL_PRIVATE_DEF_SEL(newHeapWithDescriptor_, - "newHeapWithDescriptor:"); -_MTL_PRIVATE_DEF_SEL(newIOCommandQueueWithDescriptor_error_, - "newIOCommandQueueWithDescriptor:error:"); -_MTL_PRIVATE_DEF_SEL(newIOHandleWithURL_compressionMethod_error_, - "newIOHandleWithURL:compressionMethod:error:"); -_MTL_PRIVATE_DEF_SEL(newIOHandleWithURL_error_, - "newIOHandleWithURL:error:"); -_MTL_PRIVATE_DEF_SEL(newIndirectCommandBufferWithDescriptor_maxCommandCount_options_, - "newIndirectCommandBufferWithDescriptor:maxCommandCount:options:"); -_MTL_PRIVATE_DEF_SEL(newIntersectionFunctionTableWithDescriptor_, - "newIntersectionFunctionTableWithDescriptor:"); -_MTL_PRIVATE_DEF_SEL(newIntersectionFunctionTableWithDescriptor_stage_, - "newIntersectionFunctionTableWithDescriptor:stage:"); -_MTL_PRIVATE_DEF_SEL(newIntersectionFunctionWithDescriptor_completionHandler_, - "newIntersectionFunctionWithDescriptor:completionHandler:"); -_MTL_PRIVATE_DEF_SEL(newIntersectionFunctionWithDescriptor_error_, - "newIntersectionFunctionWithDescriptor:error:"); -_MTL_PRIVATE_DEF_SEL(newLibraryWithData_error_, - "newLibraryWithData:error:"); -_MTL_PRIVATE_DEF_SEL(newLibraryWithFile_error_, - "newLibraryWithFile:error:"); -_MTL_PRIVATE_DEF_SEL(newLibraryWithSource_options_completionHandler_, - "newLibraryWithSource:options:completionHandler:"); -_MTL_PRIVATE_DEF_SEL(newLibraryWithSource_options_error_, - "newLibraryWithSource:options:error:"); -_MTL_PRIVATE_DEF_SEL(newLibraryWithStitchedDescriptor_completionHandler_, - "newLibraryWithStitchedDescriptor:completionHandler:"); -_MTL_PRIVATE_DEF_SEL(newLibraryWithStitchedDescriptor_error_, - "newLibraryWithStitchedDescriptor:error:"); -_MTL_PRIVATE_DEF_SEL(newLibraryWithURL_error_, - "newLibraryWithURL:error:"); -_MTL_PRIVATE_DEF_SEL(newRasterizationRateMapWithDescriptor_, - "newRasterizationRateMapWithDescriptor:"); -_MTL_PRIVATE_DEF_SEL(newRemoteBufferViewForDevice_, - "newRemoteBufferViewForDevice:"); -_MTL_PRIVATE_DEF_SEL(newRemoteTextureViewForDevice_, - "newRemoteTextureViewForDevice:"); -_MTL_PRIVATE_DEF_SEL(newRenderPipelineStateWithAdditionalBinaryFunctions_error_, - "newRenderPipelineStateWithAdditionalBinaryFunctions:error:"); -_MTL_PRIVATE_DEF_SEL(newRenderPipelineStateWithDescriptor_completionHandler_, - "newRenderPipelineStateWithDescriptor:completionHandler:"); -_MTL_PRIVATE_DEF_SEL(newRenderPipelineStateWithDescriptor_error_, - "newRenderPipelineStateWithDescriptor:error:"); -_MTL_PRIVATE_DEF_SEL(newRenderPipelineStateWithDescriptor_options_completionHandler_, - "newRenderPipelineStateWithDescriptor:options:completionHandler:"); -_MTL_PRIVATE_DEF_SEL(newRenderPipelineStateWithDescriptor_options_reflection_error_, - "newRenderPipelineStateWithDescriptor:options:reflection:error:"); -_MTL_PRIVATE_DEF_SEL(newRenderPipelineStateWithMeshDescriptor_options_completionHandler_, - "newRenderPipelineStateWithMeshDescriptor:options:completionHandler:"); -_MTL_PRIVATE_DEF_SEL(newRenderPipelineStateWithMeshDescriptor_options_reflection_error_, - "newRenderPipelineStateWithMeshDescriptor:options:reflection:error:"); -_MTL_PRIVATE_DEF_SEL(newRenderPipelineStateWithTileDescriptor_options_completionHandler_, - "newRenderPipelineStateWithTileDescriptor:options:completionHandler:"); -_MTL_PRIVATE_DEF_SEL(newRenderPipelineStateWithTileDescriptor_options_reflection_error_, - "newRenderPipelineStateWithTileDescriptor:options:reflection:error:"); -_MTL_PRIVATE_DEF_SEL(newSamplerStateWithDescriptor_, - "newSamplerStateWithDescriptor:"); -_MTL_PRIVATE_DEF_SEL(newScratchBufferWithMinimumSize_, - "newScratchBufferWithMinimumSize:"); -_MTL_PRIVATE_DEF_SEL(newSharedEvent, - "newSharedEvent"); -_MTL_PRIVATE_DEF_SEL(newSharedEventHandle, - "newSharedEventHandle"); -_MTL_PRIVATE_DEF_SEL(newSharedEventWithHandle_, - "newSharedEventWithHandle:"); -_MTL_PRIVATE_DEF_SEL(newSharedTextureHandle, - "newSharedTextureHandle"); -_MTL_PRIVATE_DEF_SEL(newSharedTextureWithDescriptor_, - "newSharedTextureWithDescriptor:"); -_MTL_PRIVATE_DEF_SEL(newSharedTextureWithHandle_, - "newSharedTextureWithHandle:"); -_MTL_PRIVATE_DEF_SEL(newTextureViewWithPixelFormat_, - "newTextureViewWithPixelFormat:"); -_MTL_PRIVATE_DEF_SEL(newTextureViewWithPixelFormat_textureType_levels_slices_, - "newTextureViewWithPixelFormat:textureType:levels:slices:"); -_MTL_PRIVATE_DEF_SEL(newTextureViewWithPixelFormat_textureType_levels_slices_swizzle_, - "newTextureViewWithPixelFormat:textureType:levels:slices:swizzle:"); -_MTL_PRIVATE_DEF_SEL(newTextureWithDescriptor_, - "newTextureWithDescriptor:"); -_MTL_PRIVATE_DEF_SEL(newTextureWithDescriptor_iosurface_plane_, - "newTextureWithDescriptor:iosurface:plane:"); -_MTL_PRIVATE_DEF_SEL(newTextureWithDescriptor_offset_, - "newTextureWithDescriptor:offset:"); -_MTL_PRIVATE_DEF_SEL(newTextureWithDescriptor_offset_bytesPerRow_, - "newTextureWithDescriptor:offset:bytesPerRow:"); -_MTL_PRIVATE_DEF_SEL(newVisibleFunctionTableWithDescriptor_, - "newVisibleFunctionTableWithDescriptor:"); -_MTL_PRIVATE_DEF_SEL(newVisibleFunctionTableWithDescriptor_stage_, - "newVisibleFunctionTableWithDescriptor:stage:"); -_MTL_PRIVATE_DEF_SEL(nodes, - "nodes"); -_MTL_PRIVATE_DEF_SEL(normalizedCoordinates, - "normalizedCoordinates"); -_MTL_PRIVATE_DEF_SEL(notifyListener_atValue_block_, - "notifyListener:atValue:block:"); -_MTL_PRIVATE_DEF_SEL(objectAtIndexedSubscript_, - "objectAtIndexedSubscript:"); -_MTL_PRIVATE_DEF_SEL(objectBindings, - "objectBindings"); -_MTL_PRIVATE_DEF_SEL(objectBuffers, - "objectBuffers"); -_MTL_PRIVATE_DEF_SEL(objectFunction, - "objectFunction"); -_MTL_PRIVATE_DEF_SEL(objectPayloadAlignment, - "objectPayloadAlignment"); -_MTL_PRIVATE_DEF_SEL(objectPayloadDataSize, - "objectPayloadDataSize"); -_MTL_PRIVATE_DEF_SEL(objectThreadExecutionWidth, - "objectThreadExecutionWidth"); -_MTL_PRIVATE_DEF_SEL(objectThreadgroupSizeIsMultipleOfThreadExecutionWidth, - "objectThreadgroupSizeIsMultipleOfThreadExecutionWidth"); -_MTL_PRIVATE_DEF_SEL(offset, - "offset"); -_MTL_PRIVATE_DEF_SEL(opaque, - "opaque"); -_MTL_PRIVATE_DEF_SEL(optimizationLevel, - "optimizationLevel"); -_MTL_PRIVATE_DEF_SEL(optimizeContentsForCPUAccess_, - "optimizeContentsForCPUAccess:"); -_MTL_PRIVATE_DEF_SEL(optimizeContentsForCPUAccess_slice_level_, - "optimizeContentsForCPUAccess:slice:level:"); -_MTL_PRIVATE_DEF_SEL(optimizeContentsForGPUAccess_, - "optimizeContentsForGPUAccess:"); -_MTL_PRIVATE_DEF_SEL(optimizeContentsForGPUAccess_slice_level_, - "optimizeContentsForGPUAccess:slice:level:"); -_MTL_PRIVATE_DEF_SEL(optimizeIndirectCommandBuffer_withRange_, - "optimizeIndirectCommandBuffer:withRange:"); -_MTL_PRIVATE_DEF_SEL(options, - "options"); -_MTL_PRIVATE_DEF_SEL(outputNode, - "outputNode"); -_MTL_PRIVATE_DEF_SEL(outputURL, - "outputURL"); -_MTL_PRIVATE_DEF_SEL(parallelRenderCommandEncoderWithDescriptor_, - "parallelRenderCommandEncoderWithDescriptor:"); -_MTL_PRIVATE_DEF_SEL(parameterBufferSizeAndAlign, - "parameterBufferSizeAndAlign"); -_MTL_PRIVATE_DEF_SEL(parentRelativeLevel, - "parentRelativeLevel"); -_MTL_PRIVATE_DEF_SEL(parentRelativeSlice, - "parentRelativeSlice"); -_MTL_PRIVATE_DEF_SEL(parentTexture, - "parentTexture"); -_MTL_PRIVATE_DEF_SEL(patchControlPointCount, - "patchControlPointCount"); -_MTL_PRIVATE_DEF_SEL(patchType, - "patchType"); -_MTL_PRIVATE_DEF_SEL(payloadMemoryLength, - "payloadMemoryLength"); -_MTL_PRIVATE_DEF_SEL(peerCount, - "peerCount"); -_MTL_PRIVATE_DEF_SEL(peerGroupID, - "peerGroupID"); -_MTL_PRIVATE_DEF_SEL(peerIndex, - "peerIndex"); -_MTL_PRIVATE_DEF_SEL(physicalGranularity, - "physicalGranularity"); -_MTL_PRIVATE_DEF_SEL(physicalSizeForLayer_, - "physicalSizeForLayer:"); -_MTL_PRIVATE_DEF_SEL(pixelFormat, - "pixelFormat"); -_MTL_PRIVATE_DEF_SEL(pointerType, - "pointerType"); -_MTL_PRIVATE_DEF_SEL(popDebugGroup, - "popDebugGroup"); -_MTL_PRIVATE_DEF_SEL(preloadedLibraries, - "preloadedLibraries"); -_MTL_PRIVATE_DEF_SEL(preprocessorMacros, - "preprocessorMacros"); -_MTL_PRIVATE_DEF_SEL(present, - "present"); -_MTL_PRIVATE_DEF_SEL(presentAfterMinimumDuration_, - "presentAfterMinimumDuration:"); -_MTL_PRIVATE_DEF_SEL(presentAtTime_, - "presentAtTime:"); -_MTL_PRIVATE_DEF_SEL(presentDrawable_, - "presentDrawable:"); -_MTL_PRIVATE_DEF_SEL(presentDrawable_afterMinimumDuration_, - "presentDrawable:afterMinimumDuration:"); -_MTL_PRIVATE_DEF_SEL(presentDrawable_atTime_, - "presentDrawable:atTime:"); -_MTL_PRIVATE_DEF_SEL(presentedTime, - "presentedTime"); -_MTL_PRIVATE_DEF_SEL(preserveInvariance, - "preserveInvariance"); -_MTL_PRIVATE_DEF_SEL(primitiveDataBuffer, - "primitiveDataBuffer"); -_MTL_PRIVATE_DEF_SEL(primitiveDataBufferOffset, - "primitiveDataBufferOffset"); -_MTL_PRIVATE_DEF_SEL(primitiveDataElementSize, - "primitiveDataElementSize"); -_MTL_PRIVATE_DEF_SEL(primitiveDataStride, - "primitiveDataStride"); -_MTL_PRIVATE_DEF_SEL(priority, - "priority"); -_MTL_PRIVATE_DEF_SEL(privateFunctions, - "privateFunctions"); -_MTL_PRIVATE_DEF_SEL(pushDebugGroup_, - "pushDebugGroup:"); -_MTL_PRIVATE_DEF_SEL(rAddressMode, - "rAddressMode"); -_MTL_PRIVATE_DEF_SEL(rasterSampleCount, - "rasterSampleCount"); -_MTL_PRIVATE_DEF_SEL(rasterizationRateMap, - "rasterizationRateMap"); -_MTL_PRIVATE_DEF_SEL(rasterizationRateMapDescriptorWithScreenSize_, - "rasterizationRateMapDescriptorWithScreenSize:"); -_MTL_PRIVATE_DEF_SEL(rasterizationRateMapDescriptorWithScreenSize_layer_, - "rasterizationRateMapDescriptorWithScreenSize:layer:"); -_MTL_PRIVATE_DEF_SEL(rasterizationRateMapDescriptorWithScreenSize_layerCount_layers_, - "rasterizationRateMapDescriptorWithScreenSize:layerCount:layers:"); -_MTL_PRIVATE_DEF_SEL(readMask, - "readMask"); -_MTL_PRIVATE_DEF_SEL(readWriteTextureSupport, - "readWriteTextureSupport"); -_MTL_PRIVATE_DEF_SEL(recommendedMaxWorkingSetSize, - "recommendedMaxWorkingSetSize"); -_MTL_PRIVATE_DEF_SEL(refitAccelerationStructure_descriptor_destination_scratchBuffer_scratchBufferOffset_, - "refitAccelerationStructure:descriptor:destination:scratchBuffer:scratchBufferOffset:"); -_MTL_PRIVATE_DEF_SEL(refitAccelerationStructure_descriptor_destination_scratchBuffer_scratchBufferOffset_options_, - "refitAccelerationStructure:descriptor:destination:scratchBuffer:scratchBufferOffset:options:"); -_MTL_PRIVATE_DEF_SEL(registryID, - "registryID"); -_MTL_PRIVATE_DEF_SEL(remoteStorageBuffer, - "remoteStorageBuffer"); -_MTL_PRIVATE_DEF_SEL(remoteStorageTexture, - "remoteStorageTexture"); -_MTL_PRIVATE_DEF_SEL(removeAllDebugMarkers, - "removeAllDebugMarkers"); -_MTL_PRIVATE_DEF_SEL(renderCommandEncoder, - "renderCommandEncoder"); -_MTL_PRIVATE_DEF_SEL(renderCommandEncoderWithDescriptor_, - "renderCommandEncoderWithDescriptor:"); -_MTL_PRIVATE_DEF_SEL(renderPassDescriptor, - "renderPassDescriptor"); -_MTL_PRIVATE_DEF_SEL(renderTargetArrayLength, - "renderTargetArrayLength"); -_MTL_PRIVATE_DEF_SEL(renderTargetHeight, - "renderTargetHeight"); -_MTL_PRIVATE_DEF_SEL(renderTargetWidth, - "renderTargetWidth"); -_MTL_PRIVATE_DEF_SEL(replaceRegion_mipmapLevel_slice_withBytes_bytesPerRow_bytesPerImage_, - "replaceRegion:mipmapLevel:slice:withBytes:bytesPerRow:bytesPerImage:"); -_MTL_PRIVATE_DEF_SEL(replaceRegion_mipmapLevel_withBytes_bytesPerRow_, - "replaceRegion:mipmapLevel:withBytes:bytesPerRow:"); -_MTL_PRIVATE_DEF_SEL(required, - "required"); -_MTL_PRIVATE_DEF_SEL(reset, - "reset"); -_MTL_PRIVATE_DEF_SEL(resetCommandsInBuffer_withRange_, - "resetCommandsInBuffer:withRange:"); -_MTL_PRIVATE_DEF_SEL(resetTextureAccessCounters_region_mipLevel_slice_, - "resetTextureAccessCounters:region:mipLevel:slice:"); -_MTL_PRIVATE_DEF_SEL(resetWithRange_, - "resetWithRange:"); -_MTL_PRIVATE_DEF_SEL(resolveCounterRange_, - "resolveCounterRange:"); -_MTL_PRIVATE_DEF_SEL(resolveCounters_inRange_destinationBuffer_destinationOffset_, - "resolveCounters:inRange:destinationBuffer:destinationOffset:"); -_MTL_PRIVATE_DEF_SEL(resolveDepthPlane, - "resolveDepthPlane"); -_MTL_PRIVATE_DEF_SEL(resolveLevel, - "resolveLevel"); -_MTL_PRIVATE_DEF_SEL(resolveSlice, - "resolveSlice"); -_MTL_PRIVATE_DEF_SEL(resolveTexture, - "resolveTexture"); -_MTL_PRIVATE_DEF_SEL(resourceOptions, - "resourceOptions"); -_MTL_PRIVATE_DEF_SEL(resourceStateCommandEncoder, - "resourceStateCommandEncoder"); -_MTL_PRIVATE_DEF_SEL(resourceStateCommandEncoderWithDescriptor_, - "resourceStateCommandEncoderWithDescriptor:"); -_MTL_PRIVATE_DEF_SEL(resourceStatePassDescriptor, - "resourceStatePassDescriptor"); -_MTL_PRIVATE_DEF_SEL(retainedReferences, - "retainedReferences"); -_MTL_PRIVATE_DEF_SEL(rgbBlendOperation, - "rgbBlendOperation"); -_MTL_PRIVATE_DEF_SEL(rootResource, - "rootResource"); -_MTL_PRIVATE_DEF_SEL(sAddressMode, - "sAddressMode"); -_MTL_PRIVATE_DEF_SEL(sampleBuffer, - "sampleBuffer"); -_MTL_PRIVATE_DEF_SEL(sampleBufferAttachments, - "sampleBufferAttachments"); -_MTL_PRIVATE_DEF_SEL(sampleCount, - "sampleCount"); -_MTL_PRIVATE_DEF_SEL(sampleCountersInBuffer_atSampleIndex_withBarrier_, - "sampleCountersInBuffer:atSampleIndex:withBarrier:"); -_MTL_PRIVATE_DEF_SEL(sampleTimestamps_gpuTimestamp_, - "sampleTimestamps:gpuTimestamp:"); -_MTL_PRIVATE_DEF_SEL(scratchBufferAllocator, - "scratchBufferAllocator"); -_MTL_PRIVATE_DEF_SEL(screenSize, - "screenSize"); -_MTL_PRIVATE_DEF_SEL(serializeToURL_error_, - "serializeToURL:error:"); -_MTL_PRIVATE_DEF_SEL(setAccelerationStructure_atBufferIndex_, - "setAccelerationStructure:atBufferIndex:"); -_MTL_PRIVATE_DEF_SEL(setAccelerationStructure_atIndex_, - "setAccelerationStructure:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setAccess_, - "setAccess:"); -_MTL_PRIVATE_DEF_SEL(setAllowDuplicateIntersectionFunctionInvocation_, - "setAllowDuplicateIntersectionFunctionInvocation:"); -_MTL_PRIVATE_DEF_SEL(setAllowGPUOptimizedContents_, - "setAllowGPUOptimizedContents:"); -_MTL_PRIVATE_DEF_SEL(setAlphaBlendOperation_, - "setAlphaBlendOperation:"); -_MTL_PRIVATE_DEF_SEL(setAlphaToCoverageEnabled_, - "setAlphaToCoverageEnabled:"); -_MTL_PRIVATE_DEF_SEL(setAlphaToOneEnabled_, - "setAlphaToOneEnabled:"); -_MTL_PRIVATE_DEF_SEL(setArgumentBuffer_offset_, - "setArgumentBuffer:offset:"); -_MTL_PRIVATE_DEF_SEL(setArgumentBuffer_startOffset_arrayElement_, - "setArgumentBuffer:startOffset:arrayElement:"); -_MTL_PRIVATE_DEF_SEL(setArgumentIndex_, - "setArgumentIndex:"); -_MTL_PRIVATE_DEF_SEL(setArguments_, - "setArguments:"); -_MTL_PRIVATE_DEF_SEL(setArrayLength_, - "setArrayLength:"); -_MTL_PRIVATE_DEF_SEL(setAttributes_, - "setAttributes:"); -_MTL_PRIVATE_DEF_SEL(setBackFaceStencil_, - "setBackFaceStencil:"); -_MTL_PRIVATE_DEF_SEL(setBarrier, - "setBarrier"); -_MTL_PRIVATE_DEF_SEL(setBinaryArchives_, - "setBinaryArchives:"); -_MTL_PRIVATE_DEF_SEL(setBinaryFunctions_, - "setBinaryFunctions:"); -_MTL_PRIVATE_DEF_SEL(setBlendColorRed_green_blue_alpha_, - "setBlendColorRed:green:blue:alpha:"); -_MTL_PRIVATE_DEF_SEL(setBlendingEnabled_, - "setBlendingEnabled:"); -_MTL_PRIVATE_DEF_SEL(setBorderColor_, - "setBorderColor:"); -_MTL_PRIVATE_DEF_SEL(setBoundingBoxBuffer_, - "setBoundingBoxBuffer:"); -_MTL_PRIVATE_DEF_SEL(setBoundingBoxBufferOffset_, - "setBoundingBoxBufferOffset:"); -_MTL_PRIVATE_DEF_SEL(setBoundingBoxBuffers_, - "setBoundingBoxBuffers:"); -_MTL_PRIVATE_DEF_SEL(setBoundingBoxCount_, - "setBoundingBoxCount:"); -_MTL_PRIVATE_DEF_SEL(setBoundingBoxStride_, - "setBoundingBoxStride:"); -_MTL_PRIVATE_DEF_SEL(setBuffer_, - "setBuffer:"); -_MTL_PRIVATE_DEF_SEL(setBuffer_offset_atIndex_, - "setBuffer:offset:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setBufferIndex_, - "setBufferIndex:"); -_MTL_PRIVATE_DEF_SEL(setBufferOffset_atIndex_, - "setBufferOffset:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setBuffers_offsets_withRange_, - "setBuffers:offsets:withRange:"); -_MTL_PRIVATE_DEF_SEL(setBytes_length_atIndex_, - "setBytes:length:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setCaptureObject_, - "setCaptureObject:"); -_MTL_PRIVATE_DEF_SEL(setClearColor_, - "setClearColor:"); -_MTL_PRIVATE_DEF_SEL(setClearDepth_, - "setClearDepth:"); -_MTL_PRIVATE_DEF_SEL(setClearStencil_, - "setClearStencil:"); -_MTL_PRIVATE_DEF_SEL(setColorStoreAction_atIndex_, - "setColorStoreAction:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setColorStoreActionOptions_atIndex_, - "setColorStoreActionOptions:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setCommandTypes_, - "setCommandTypes:"); -_MTL_PRIVATE_DEF_SEL(setCompareFunction_, - "setCompareFunction:"); -_MTL_PRIVATE_DEF_SEL(setCompressionType_, - "setCompressionType:"); -_MTL_PRIVATE_DEF_SEL(setComputeFunction_, - "setComputeFunction:"); -_MTL_PRIVATE_DEF_SEL(setComputePipelineState_, - "setComputePipelineState:"); -_MTL_PRIVATE_DEF_SEL(setComputePipelineState_atIndex_, - "setComputePipelineState:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setComputePipelineStates_withRange_, - "setComputePipelineStates:withRange:"); -_MTL_PRIVATE_DEF_SEL(setConstantBlockAlignment_, - "setConstantBlockAlignment:"); -_MTL_PRIVATE_DEF_SEL(setConstantValue_type_atIndex_, - "setConstantValue:type:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setConstantValue_type_withName_, - "setConstantValue:type:withName:"); -_MTL_PRIVATE_DEF_SEL(setConstantValues_, - "setConstantValues:"); -_MTL_PRIVATE_DEF_SEL(setConstantValues_type_withRange_, - "setConstantValues:type:withRange:"); -_MTL_PRIVATE_DEF_SEL(setControlDependencies_, - "setControlDependencies:"); -_MTL_PRIVATE_DEF_SEL(setCounterSet_, - "setCounterSet:"); -_MTL_PRIVATE_DEF_SEL(setCpuCacheMode_, - "setCpuCacheMode:"); -_MTL_PRIVATE_DEF_SEL(setCullMode_, - "setCullMode:"); -_MTL_PRIVATE_DEF_SEL(setDataType_, - "setDataType:"); -_MTL_PRIVATE_DEF_SEL(setDefaultCaptureScope_, - "setDefaultCaptureScope:"); -_MTL_PRIVATE_DEF_SEL(setDefaultRasterSampleCount_, - "setDefaultRasterSampleCount:"); -_MTL_PRIVATE_DEF_SEL(setDepth_, - "setDepth:"); -_MTL_PRIVATE_DEF_SEL(setDepthAttachment_, - "setDepthAttachment:"); -_MTL_PRIVATE_DEF_SEL(setDepthAttachmentPixelFormat_, - "setDepthAttachmentPixelFormat:"); -_MTL_PRIVATE_DEF_SEL(setDepthBias_slopeScale_clamp_, - "setDepthBias:slopeScale:clamp:"); -_MTL_PRIVATE_DEF_SEL(setDepthClipMode_, - "setDepthClipMode:"); -_MTL_PRIVATE_DEF_SEL(setDepthCompareFunction_, - "setDepthCompareFunction:"); -_MTL_PRIVATE_DEF_SEL(setDepthFailureOperation_, - "setDepthFailureOperation:"); -_MTL_PRIVATE_DEF_SEL(setDepthPlane_, - "setDepthPlane:"); -_MTL_PRIVATE_DEF_SEL(setDepthResolveFilter_, - "setDepthResolveFilter:"); -_MTL_PRIVATE_DEF_SEL(setDepthStencilPassOperation_, - "setDepthStencilPassOperation:"); -_MTL_PRIVATE_DEF_SEL(setDepthStencilState_, - "setDepthStencilState:"); -_MTL_PRIVATE_DEF_SEL(setDepthStoreAction_, - "setDepthStoreAction:"); -_MTL_PRIVATE_DEF_SEL(setDepthStoreActionOptions_, - "setDepthStoreActionOptions:"); -_MTL_PRIVATE_DEF_SEL(setDepthWriteEnabled_, - "setDepthWriteEnabled:"); -_MTL_PRIVATE_DEF_SEL(setDestination_, - "setDestination:"); -_MTL_PRIVATE_DEF_SEL(setDestinationAlphaBlendFactor_, - "setDestinationAlphaBlendFactor:"); -_MTL_PRIVATE_DEF_SEL(setDestinationRGBBlendFactor_, - "setDestinationRGBBlendFactor:"); -_MTL_PRIVATE_DEF_SEL(setDispatchType_, - "setDispatchType:"); -_MTL_PRIVATE_DEF_SEL(setEndOfEncoderSampleIndex_, - "setEndOfEncoderSampleIndex:"); -_MTL_PRIVATE_DEF_SEL(setEndOfFragmentSampleIndex_, - "setEndOfFragmentSampleIndex:"); -_MTL_PRIVATE_DEF_SEL(setEndOfVertexSampleIndex_, - "setEndOfVertexSampleIndex:"); -_MTL_PRIVATE_DEF_SEL(setErrorOptions_, - "setErrorOptions:"); -_MTL_PRIVATE_DEF_SEL(setFastMathEnabled_, - "setFastMathEnabled:"); -_MTL_PRIVATE_DEF_SEL(setFormat_, - "setFormat:"); -_MTL_PRIVATE_DEF_SEL(setFragmentAccelerationStructure_atBufferIndex_, - "setFragmentAccelerationStructure:atBufferIndex:"); -_MTL_PRIVATE_DEF_SEL(setFragmentAdditionalBinaryFunctions_, - "setFragmentAdditionalBinaryFunctions:"); -_MTL_PRIVATE_DEF_SEL(setFragmentBuffer_offset_atIndex_, - "setFragmentBuffer:offset:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setFragmentBufferOffset_atIndex_, - "setFragmentBufferOffset:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setFragmentBuffers_offsets_withRange_, - "setFragmentBuffers:offsets:withRange:"); -_MTL_PRIVATE_DEF_SEL(setFragmentBytes_length_atIndex_, - "setFragmentBytes:length:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setFragmentFunction_, - "setFragmentFunction:"); -_MTL_PRIVATE_DEF_SEL(setFragmentIntersectionFunctionTable_atBufferIndex_, - "setFragmentIntersectionFunctionTable:atBufferIndex:"); -_MTL_PRIVATE_DEF_SEL(setFragmentIntersectionFunctionTables_withBufferRange_, - "setFragmentIntersectionFunctionTables:withBufferRange:"); -_MTL_PRIVATE_DEF_SEL(setFragmentLinkedFunctions_, - "setFragmentLinkedFunctions:"); -_MTL_PRIVATE_DEF_SEL(setFragmentPreloadedLibraries_, - "setFragmentPreloadedLibraries:"); -_MTL_PRIVATE_DEF_SEL(setFragmentSamplerState_atIndex_, - "setFragmentSamplerState:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setFragmentSamplerState_lodMinClamp_lodMaxClamp_atIndex_, - "setFragmentSamplerState:lodMinClamp:lodMaxClamp:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setFragmentSamplerStates_lodMinClamps_lodMaxClamps_withRange_, - "setFragmentSamplerStates:lodMinClamps:lodMaxClamps:withRange:"); -_MTL_PRIVATE_DEF_SEL(setFragmentSamplerStates_withRange_, - "setFragmentSamplerStates:withRange:"); -_MTL_PRIVATE_DEF_SEL(setFragmentTexture_atIndex_, - "setFragmentTexture:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setFragmentTextures_withRange_, - "setFragmentTextures:withRange:"); -_MTL_PRIVATE_DEF_SEL(setFragmentVisibleFunctionTable_atBufferIndex_, - "setFragmentVisibleFunctionTable:atBufferIndex:"); -_MTL_PRIVATE_DEF_SEL(setFragmentVisibleFunctionTables_withBufferRange_, - "setFragmentVisibleFunctionTables:withBufferRange:"); -_MTL_PRIVATE_DEF_SEL(setFrontFaceStencil_, - "setFrontFaceStencil:"); -_MTL_PRIVATE_DEF_SEL(setFrontFacingWinding_, - "setFrontFacingWinding:"); -_MTL_PRIVATE_DEF_SEL(setFunction_atIndex_, - "setFunction:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setFunctionCount_, - "setFunctionCount:"); -_MTL_PRIVATE_DEF_SEL(setFunctionGraphs_, - "setFunctionGraphs:"); -_MTL_PRIVATE_DEF_SEL(setFunctionName_, - "setFunctionName:"); -_MTL_PRIVATE_DEF_SEL(setFunctions_, - "setFunctions:"); -_MTL_PRIVATE_DEF_SEL(setFunctions_withRange_, - "setFunctions:withRange:"); -_MTL_PRIVATE_DEF_SEL(setGeometryDescriptors_, - "setGeometryDescriptors:"); -_MTL_PRIVATE_DEF_SEL(setGroups_, - "setGroups:"); -_MTL_PRIVATE_DEF_SEL(setHazardTrackingMode_, - "setHazardTrackingMode:"); -_MTL_PRIVATE_DEF_SEL(setHeight_, - "setHeight:"); -_MTL_PRIVATE_DEF_SEL(setImageblockSampleLength_, - "setImageblockSampleLength:"); -_MTL_PRIVATE_DEF_SEL(setImageblockWidth_height_, - "setImageblockWidth:height:"); -_MTL_PRIVATE_DEF_SEL(setIndex_, - "setIndex:"); -_MTL_PRIVATE_DEF_SEL(setIndexBuffer_, - "setIndexBuffer:"); -_MTL_PRIVATE_DEF_SEL(setIndexBufferIndex_, - "setIndexBufferIndex:"); -_MTL_PRIVATE_DEF_SEL(setIndexBufferOffset_, - "setIndexBufferOffset:"); -_MTL_PRIVATE_DEF_SEL(setIndexType_, - "setIndexType:"); -_MTL_PRIVATE_DEF_SEL(setIndirectCommandBuffer_atIndex_, - "setIndirectCommandBuffer:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setIndirectCommandBuffers_withRange_, - "setIndirectCommandBuffers:withRange:"); -_MTL_PRIVATE_DEF_SEL(setInheritBuffers_, - "setInheritBuffers:"); -_MTL_PRIVATE_DEF_SEL(setInheritPipelineState_, - "setInheritPipelineState:"); -_MTL_PRIVATE_DEF_SEL(setInputPrimitiveTopology_, - "setInputPrimitiveTopology:"); -_MTL_PRIVATE_DEF_SEL(setInsertLibraries_, - "setInsertLibraries:"); -_MTL_PRIVATE_DEF_SEL(setInstallName_, - "setInstallName:"); -_MTL_PRIVATE_DEF_SEL(setInstanceCount_, - "setInstanceCount:"); -_MTL_PRIVATE_DEF_SEL(setInstanceDescriptorBuffer_, - "setInstanceDescriptorBuffer:"); -_MTL_PRIVATE_DEF_SEL(setInstanceDescriptorBufferOffset_, - "setInstanceDescriptorBufferOffset:"); -_MTL_PRIVATE_DEF_SEL(setInstanceDescriptorStride_, - "setInstanceDescriptorStride:"); -_MTL_PRIVATE_DEF_SEL(setInstanceDescriptorType_, - "setInstanceDescriptorType:"); -_MTL_PRIVATE_DEF_SEL(setInstancedAccelerationStructures_, - "setInstancedAccelerationStructures:"); -_MTL_PRIVATE_DEF_SEL(setIntersectionFunctionTable_atBufferIndex_, - "setIntersectionFunctionTable:atBufferIndex:"); -_MTL_PRIVATE_DEF_SEL(setIntersectionFunctionTable_atIndex_, - "setIntersectionFunctionTable:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setIntersectionFunctionTableOffset_, - "setIntersectionFunctionTableOffset:"); -_MTL_PRIVATE_DEF_SEL(setIntersectionFunctionTables_withBufferRange_, - "setIntersectionFunctionTables:withBufferRange:"); -_MTL_PRIVATE_DEF_SEL(setIntersectionFunctionTables_withRange_, - "setIntersectionFunctionTables:withRange:"); -_MTL_PRIVATE_DEF_SEL(setKernelBuffer_offset_atIndex_, - "setKernelBuffer:offset:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setLabel_, - "setLabel:"); -_MTL_PRIVATE_DEF_SEL(setLanguageVersion_, - "setLanguageVersion:"); -_MTL_PRIVATE_DEF_SEL(setLayer_atIndex_, - "setLayer:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setLevel_, - "setLevel:"); -_MTL_PRIVATE_DEF_SEL(setLibraries_, - "setLibraries:"); -_MTL_PRIVATE_DEF_SEL(setLibraryType_, - "setLibraryType:"); -_MTL_PRIVATE_DEF_SEL(setLinkedFunctions_, - "setLinkedFunctions:"); -_MTL_PRIVATE_DEF_SEL(setLoadAction_, - "setLoadAction:"); -_MTL_PRIVATE_DEF_SEL(setLodAverage_, - "setLodAverage:"); -_MTL_PRIVATE_DEF_SEL(setLodMaxClamp_, - "setLodMaxClamp:"); -_MTL_PRIVATE_DEF_SEL(setLodMinClamp_, - "setLodMinClamp:"); -_MTL_PRIVATE_DEF_SEL(setMagFilter_, - "setMagFilter:"); -_MTL_PRIVATE_DEF_SEL(setMaxAnisotropy_, - "setMaxAnisotropy:"); -_MTL_PRIVATE_DEF_SEL(setMaxCallStackDepth_, - "setMaxCallStackDepth:"); -_MTL_PRIVATE_DEF_SEL(setMaxCommandBufferCount_, - "setMaxCommandBufferCount:"); -_MTL_PRIVATE_DEF_SEL(setMaxCommandsInFlight_, - "setMaxCommandsInFlight:"); -_MTL_PRIVATE_DEF_SEL(setMaxFragmentBufferBindCount_, - "setMaxFragmentBufferBindCount:"); -_MTL_PRIVATE_DEF_SEL(setMaxFragmentCallStackDepth_, - "setMaxFragmentCallStackDepth:"); -_MTL_PRIVATE_DEF_SEL(setMaxKernelBufferBindCount_, - "setMaxKernelBufferBindCount:"); -_MTL_PRIVATE_DEF_SEL(setMaxTessellationFactor_, - "setMaxTessellationFactor:"); -_MTL_PRIVATE_DEF_SEL(setMaxTotalThreadgroupsPerMeshGrid_, - "setMaxTotalThreadgroupsPerMeshGrid:"); -_MTL_PRIVATE_DEF_SEL(setMaxTotalThreadsPerMeshThreadgroup_, - "setMaxTotalThreadsPerMeshThreadgroup:"); -_MTL_PRIVATE_DEF_SEL(setMaxTotalThreadsPerObjectThreadgroup_, - "setMaxTotalThreadsPerObjectThreadgroup:"); -_MTL_PRIVATE_DEF_SEL(setMaxTotalThreadsPerThreadgroup_, - "setMaxTotalThreadsPerThreadgroup:"); -_MTL_PRIVATE_DEF_SEL(setMaxVertexAmplificationCount_, - "setMaxVertexAmplificationCount:"); -_MTL_PRIVATE_DEF_SEL(setMaxVertexBufferBindCount_, - "setMaxVertexBufferBindCount:"); -_MTL_PRIVATE_DEF_SEL(setMaxVertexCallStackDepth_, - "setMaxVertexCallStackDepth:"); -_MTL_PRIVATE_DEF_SEL(setMeshBuffer_offset_atIndex_, - "setMeshBuffer:offset:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setMeshBufferOffset_atIndex_, - "setMeshBufferOffset:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setMeshBuffers_offsets_withRange_, - "setMeshBuffers:offsets:withRange:"); -_MTL_PRIVATE_DEF_SEL(setMeshBytes_length_atIndex_, - "setMeshBytes:length:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setMeshFunction_, - "setMeshFunction:"); -_MTL_PRIVATE_DEF_SEL(setMeshSamplerState_atIndex_, - "setMeshSamplerState:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setMeshSamplerState_lodMinClamp_lodMaxClamp_atIndex_, - "setMeshSamplerState:lodMinClamp:lodMaxClamp:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setMeshSamplerStates_lodMinClamps_lodMaxClamps_withRange_, - "setMeshSamplerStates:lodMinClamps:lodMaxClamps:withRange:"); -_MTL_PRIVATE_DEF_SEL(setMeshSamplerStates_withRange_, - "setMeshSamplerStates:withRange:"); -_MTL_PRIVATE_DEF_SEL(setMeshTexture_atIndex_, - "setMeshTexture:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setMeshTextures_withRange_, - "setMeshTextures:withRange:"); -_MTL_PRIVATE_DEF_SEL(setMeshThreadgroupSizeIsMultipleOfThreadExecutionWidth_, - "setMeshThreadgroupSizeIsMultipleOfThreadExecutionWidth:"); -_MTL_PRIVATE_DEF_SEL(setMinFilter_, - "setMinFilter:"); -_MTL_PRIVATE_DEF_SEL(setMipFilter_, - "setMipFilter:"); -_MTL_PRIVATE_DEF_SEL(setMipmapLevelCount_, - "setMipmapLevelCount:"); -_MTL_PRIVATE_DEF_SEL(setMotionEndBorderMode_, - "setMotionEndBorderMode:"); -_MTL_PRIVATE_DEF_SEL(setMotionEndTime_, - "setMotionEndTime:"); -_MTL_PRIVATE_DEF_SEL(setMotionKeyframeCount_, - "setMotionKeyframeCount:"); -_MTL_PRIVATE_DEF_SEL(setMotionStartBorderMode_, - "setMotionStartBorderMode:"); -_MTL_PRIVATE_DEF_SEL(setMotionStartTime_, - "setMotionStartTime:"); -_MTL_PRIVATE_DEF_SEL(setMotionTransformBuffer_, - "setMotionTransformBuffer:"); -_MTL_PRIVATE_DEF_SEL(setMotionTransformBufferOffset_, - "setMotionTransformBufferOffset:"); -_MTL_PRIVATE_DEF_SEL(setMotionTransformCount_, - "setMotionTransformCount:"); -_MTL_PRIVATE_DEF_SEL(setMutability_, - "setMutability:"); -_MTL_PRIVATE_DEF_SEL(setName_, - "setName:"); -_MTL_PRIVATE_DEF_SEL(setNodes_, - "setNodes:"); -_MTL_PRIVATE_DEF_SEL(setNormalizedCoordinates_, - "setNormalizedCoordinates:"); -_MTL_PRIVATE_DEF_SEL(setObject_atIndexedSubscript_, - "setObject:atIndexedSubscript:"); -_MTL_PRIVATE_DEF_SEL(setObjectBuffer_offset_atIndex_, - "setObjectBuffer:offset:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setObjectBufferOffset_atIndex_, - "setObjectBufferOffset:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setObjectBuffers_offsets_withRange_, - "setObjectBuffers:offsets:withRange:"); -_MTL_PRIVATE_DEF_SEL(setObjectBytes_length_atIndex_, - "setObjectBytes:length:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setObjectFunction_, - "setObjectFunction:"); -_MTL_PRIVATE_DEF_SEL(setObjectSamplerState_atIndex_, - "setObjectSamplerState:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setObjectSamplerState_lodMinClamp_lodMaxClamp_atIndex_, - "setObjectSamplerState:lodMinClamp:lodMaxClamp:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setObjectSamplerStates_lodMinClamps_lodMaxClamps_withRange_, - "setObjectSamplerStates:lodMinClamps:lodMaxClamps:withRange:"); -_MTL_PRIVATE_DEF_SEL(setObjectSamplerStates_withRange_, - "setObjectSamplerStates:withRange:"); -_MTL_PRIVATE_DEF_SEL(setObjectTexture_atIndex_, - "setObjectTexture:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setObjectTextures_withRange_, - "setObjectTextures:withRange:"); -_MTL_PRIVATE_DEF_SEL(setObjectThreadgroupMemoryLength_atIndex_, - "setObjectThreadgroupMemoryLength:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setObjectThreadgroupSizeIsMultipleOfThreadExecutionWidth_, - "setObjectThreadgroupSizeIsMultipleOfThreadExecutionWidth:"); -_MTL_PRIVATE_DEF_SEL(setOffset_, - "setOffset:"); -_MTL_PRIVATE_DEF_SEL(setOpaque_, - "setOpaque:"); -_MTL_PRIVATE_DEF_SEL(setOpaqueTriangleIntersectionFunctionWithSignature_atIndex_, - "setOpaqueTriangleIntersectionFunctionWithSignature:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setOpaqueTriangleIntersectionFunctionWithSignature_withRange_, - "setOpaqueTriangleIntersectionFunctionWithSignature:withRange:"); -_MTL_PRIVATE_DEF_SEL(setOptimizationLevel_, - "setOptimizationLevel:"); -_MTL_PRIVATE_DEF_SEL(setOptions_, - "setOptions:"); -_MTL_PRIVATE_DEF_SEL(setOutputNode_, - "setOutputNode:"); -_MTL_PRIVATE_DEF_SEL(setOutputURL_, - "setOutputURL:"); -_MTL_PRIVATE_DEF_SEL(setPayloadMemoryLength_, - "setPayloadMemoryLength:"); -_MTL_PRIVATE_DEF_SEL(setPixelFormat_, - "setPixelFormat:"); -_MTL_PRIVATE_DEF_SEL(setPreloadedLibraries_, - "setPreloadedLibraries:"); -_MTL_PRIVATE_DEF_SEL(setPreprocessorMacros_, - "setPreprocessorMacros:"); -_MTL_PRIVATE_DEF_SEL(setPreserveInvariance_, - "setPreserveInvariance:"); -_MTL_PRIVATE_DEF_SEL(setPrimitiveDataBuffer_, - "setPrimitiveDataBuffer:"); -_MTL_PRIVATE_DEF_SEL(setPrimitiveDataBufferOffset_, - "setPrimitiveDataBufferOffset:"); -_MTL_PRIVATE_DEF_SEL(setPrimitiveDataElementSize_, - "setPrimitiveDataElementSize:"); -_MTL_PRIVATE_DEF_SEL(setPrimitiveDataStride_, - "setPrimitiveDataStride:"); -_MTL_PRIVATE_DEF_SEL(setPriority_, - "setPriority:"); -_MTL_PRIVATE_DEF_SEL(setPrivateFunctions_, - "setPrivateFunctions:"); -_MTL_PRIVATE_DEF_SEL(setPurgeableState_, - "setPurgeableState:"); -_MTL_PRIVATE_DEF_SEL(setRAddressMode_, - "setRAddressMode:"); -_MTL_PRIVATE_DEF_SEL(setRasterSampleCount_, - "setRasterSampleCount:"); -_MTL_PRIVATE_DEF_SEL(setRasterizationEnabled_, - "setRasterizationEnabled:"); -_MTL_PRIVATE_DEF_SEL(setRasterizationRateMap_, - "setRasterizationRateMap:"); -_MTL_PRIVATE_DEF_SEL(setReadMask_, - "setReadMask:"); -_MTL_PRIVATE_DEF_SEL(setRenderPipelineState_, - "setRenderPipelineState:"); -_MTL_PRIVATE_DEF_SEL(setRenderPipelineState_atIndex_, - "setRenderPipelineState:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setRenderPipelineStates_withRange_, - "setRenderPipelineStates:withRange:"); -_MTL_PRIVATE_DEF_SEL(setRenderTargetArrayLength_, - "setRenderTargetArrayLength:"); -_MTL_PRIVATE_DEF_SEL(setRenderTargetHeight_, - "setRenderTargetHeight:"); -_MTL_PRIVATE_DEF_SEL(setRenderTargetWidth_, - "setRenderTargetWidth:"); -_MTL_PRIVATE_DEF_SEL(setResolveDepthPlane_, - "setResolveDepthPlane:"); -_MTL_PRIVATE_DEF_SEL(setResolveLevel_, - "setResolveLevel:"); -_MTL_PRIVATE_DEF_SEL(setResolveSlice_, - "setResolveSlice:"); -_MTL_PRIVATE_DEF_SEL(setResolveTexture_, - "setResolveTexture:"); -_MTL_PRIVATE_DEF_SEL(setResourceOptions_, - "setResourceOptions:"); -_MTL_PRIVATE_DEF_SEL(setRetainedReferences_, - "setRetainedReferences:"); -_MTL_PRIVATE_DEF_SEL(setRgbBlendOperation_, - "setRgbBlendOperation:"); -_MTL_PRIVATE_DEF_SEL(setSAddressMode_, - "setSAddressMode:"); -_MTL_PRIVATE_DEF_SEL(setSampleBuffer_, - "setSampleBuffer:"); -_MTL_PRIVATE_DEF_SEL(setSampleCount_, - "setSampleCount:"); -_MTL_PRIVATE_DEF_SEL(setSamplePositions_count_, - "setSamplePositions:count:"); -_MTL_PRIVATE_DEF_SEL(setSamplerState_atIndex_, - "setSamplerState:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setSamplerState_lodMinClamp_lodMaxClamp_atIndex_, - "setSamplerState:lodMinClamp:lodMaxClamp:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setSamplerStates_lodMinClamps_lodMaxClamps_withRange_, - "setSamplerStates:lodMinClamps:lodMaxClamps:withRange:"); -_MTL_PRIVATE_DEF_SEL(setSamplerStates_withRange_, - "setSamplerStates:withRange:"); -_MTL_PRIVATE_DEF_SEL(setScissorRect_, - "setScissorRect:"); -_MTL_PRIVATE_DEF_SEL(setScissorRects_count_, - "setScissorRects:count:"); -_MTL_PRIVATE_DEF_SEL(setScratchBufferAllocator_, - "setScratchBufferAllocator:"); -_MTL_PRIVATE_DEF_SEL(setScreenSize_, - "setScreenSize:"); -_MTL_PRIVATE_DEF_SEL(setSignaledValue_, - "setSignaledValue:"); -_MTL_PRIVATE_DEF_SEL(setSize_, - "setSize:"); -_MTL_PRIVATE_DEF_SEL(setSlice_, - "setSlice:"); -_MTL_PRIVATE_DEF_SEL(setSourceAlphaBlendFactor_, - "setSourceAlphaBlendFactor:"); -_MTL_PRIVATE_DEF_SEL(setSourceRGBBlendFactor_, - "setSourceRGBBlendFactor:"); -_MTL_PRIVATE_DEF_SEL(setSparsePageSize_, - "setSparsePageSize:"); -_MTL_PRIVATE_DEF_SEL(setSpecializedName_, - "setSpecializedName:"); -_MTL_PRIVATE_DEF_SEL(setStageInRegion_, - "setStageInRegion:"); -_MTL_PRIVATE_DEF_SEL(setStageInRegionWithIndirectBuffer_indirectBufferOffset_, - "setStageInRegionWithIndirectBuffer:indirectBufferOffset:"); -_MTL_PRIVATE_DEF_SEL(setStageInputDescriptor_, - "setStageInputDescriptor:"); -_MTL_PRIVATE_DEF_SEL(setStartOfEncoderSampleIndex_, - "setStartOfEncoderSampleIndex:"); -_MTL_PRIVATE_DEF_SEL(setStartOfFragmentSampleIndex_, - "setStartOfFragmentSampleIndex:"); -_MTL_PRIVATE_DEF_SEL(setStartOfVertexSampleIndex_, - "setStartOfVertexSampleIndex:"); -_MTL_PRIVATE_DEF_SEL(setStencilAttachment_, - "setStencilAttachment:"); -_MTL_PRIVATE_DEF_SEL(setStencilAttachmentPixelFormat_, - "setStencilAttachmentPixelFormat:"); -_MTL_PRIVATE_DEF_SEL(setStencilCompareFunction_, - "setStencilCompareFunction:"); -_MTL_PRIVATE_DEF_SEL(setStencilFailureOperation_, - "setStencilFailureOperation:"); -_MTL_PRIVATE_DEF_SEL(setStencilFrontReferenceValue_backReferenceValue_, - "setStencilFrontReferenceValue:backReferenceValue:"); -_MTL_PRIVATE_DEF_SEL(setStencilReferenceValue_, - "setStencilReferenceValue:"); -_MTL_PRIVATE_DEF_SEL(setStencilResolveFilter_, - "setStencilResolveFilter:"); -_MTL_PRIVATE_DEF_SEL(setStencilStoreAction_, - "setStencilStoreAction:"); -_MTL_PRIVATE_DEF_SEL(setStencilStoreActionOptions_, - "setStencilStoreActionOptions:"); -_MTL_PRIVATE_DEF_SEL(setStepFunction_, - "setStepFunction:"); -_MTL_PRIVATE_DEF_SEL(setStepRate_, - "setStepRate:"); -_MTL_PRIVATE_DEF_SEL(setStorageMode_, - "setStorageMode:"); -_MTL_PRIVATE_DEF_SEL(setStoreAction_, - "setStoreAction:"); -_MTL_PRIVATE_DEF_SEL(setStoreActionOptions_, - "setStoreActionOptions:"); -_MTL_PRIVATE_DEF_SEL(setStride_, - "setStride:"); -_MTL_PRIVATE_DEF_SEL(setSupportAddingBinaryFunctions_, - "setSupportAddingBinaryFunctions:"); -_MTL_PRIVATE_DEF_SEL(setSupportAddingFragmentBinaryFunctions_, - "setSupportAddingFragmentBinaryFunctions:"); -_MTL_PRIVATE_DEF_SEL(setSupportAddingVertexBinaryFunctions_, - "setSupportAddingVertexBinaryFunctions:"); -_MTL_PRIVATE_DEF_SEL(setSupportArgumentBuffers_, - "setSupportArgumentBuffers:"); -_MTL_PRIVATE_DEF_SEL(setSupportIndirectCommandBuffers_, - "setSupportIndirectCommandBuffers:"); -_MTL_PRIVATE_DEF_SEL(setSupportRayTracing_, - "setSupportRayTracing:"); -_MTL_PRIVATE_DEF_SEL(setSwizzle_, - "setSwizzle:"); -_MTL_PRIVATE_DEF_SEL(setTAddressMode_, - "setTAddressMode:"); -_MTL_PRIVATE_DEF_SEL(setTessellationControlPointIndexType_, - "setTessellationControlPointIndexType:"); -_MTL_PRIVATE_DEF_SEL(setTessellationFactorBuffer_offset_instanceStride_, - "setTessellationFactorBuffer:offset:instanceStride:"); -_MTL_PRIVATE_DEF_SEL(setTessellationFactorFormat_, - "setTessellationFactorFormat:"); -_MTL_PRIVATE_DEF_SEL(setTessellationFactorScale_, - "setTessellationFactorScale:"); -_MTL_PRIVATE_DEF_SEL(setTessellationFactorScaleEnabled_, - "setTessellationFactorScaleEnabled:"); -_MTL_PRIVATE_DEF_SEL(setTessellationFactorStepFunction_, - "setTessellationFactorStepFunction:"); -_MTL_PRIVATE_DEF_SEL(setTessellationOutputWindingOrder_, - "setTessellationOutputWindingOrder:"); -_MTL_PRIVATE_DEF_SEL(setTessellationPartitionMode_, - "setTessellationPartitionMode:"); -_MTL_PRIVATE_DEF_SEL(setTexture_, - "setTexture:"); -_MTL_PRIVATE_DEF_SEL(setTexture_atIndex_, - "setTexture:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setTextureType_, - "setTextureType:"); -_MTL_PRIVATE_DEF_SEL(setTextures_withRange_, - "setTextures:withRange:"); -_MTL_PRIVATE_DEF_SEL(setThreadGroupSizeIsMultipleOfThreadExecutionWidth_, - "setThreadGroupSizeIsMultipleOfThreadExecutionWidth:"); -_MTL_PRIVATE_DEF_SEL(setThreadgroupMemoryLength_, - "setThreadgroupMemoryLength:"); -_MTL_PRIVATE_DEF_SEL(setThreadgroupMemoryLength_atIndex_, - "setThreadgroupMemoryLength:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setThreadgroupMemoryLength_offset_atIndex_, - "setThreadgroupMemoryLength:offset:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setThreadgroupSizeMatchesTileSize_, - "setThreadgroupSizeMatchesTileSize:"); -_MTL_PRIVATE_DEF_SEL(setTileAccelerationStructure_atBufferIndex_, - "setTileAccelerationStructure:atBufferIndex:"); -_MTL_PRIVATE_DEF_SEL(setTileAdditionalBinaryFunctions_, - "setTileAdditionalBinaryFunctions:"); -_MTL_PRIVATE_DEF_SEL(setTileBuffer_offset_atIndex_, - "setTileBuffer:offset:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setTileBufferOffset_atIndex_, - "setTileBufferOffset:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setTileBuffers_offsets_withRange_, - "setTileBuffers:offsets:withRange:"); -_MTL_PRIVATE_DEF_SEL(setTileBytes_length_atIndex_, - "setTileBytes:length:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setTileFunction_, - "setTileFunction:"); -_MTL_PRIVATE_DEF_SEL(setTileHeight_, - "setTileHeight:"); -_MTL_PRIVATE_DEF_SEL(setTileIntersectionFunctionTable_atBufferIndex_, - "setTileIntersectionFunctionTable:atBufferIndex:"); -_MTL_PRIVATE_DEF_SEL(setTileIntersectionFunctionTables_withBufferRange_, - "setTileIntersectionFunctionTables:withBufferRange:"); -_MTL_PRIVATE_DEF_SEL(setTileSamplerState_atIndex_, - "setTileSamplerState:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setTileSamplerState_lodMinClamp_lodMaxClamp_atIndex_, - "setTileSamplerState:lodMinClamp:lodMaxClamp:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setTileSamplerStates_lodMinClamps_lodMaxClamps_withRange_, - "setTileSamplerStates:lodMinClamps:lodMaxClamps:withRange:"); -_MTL_PRIVATE_DEF_SEL(setTileSamplerStates_withRange_, - "setTileSamplerStates:withRange:"); -_MTL_PRIVATE_DEF_SEL(setTileTexture_atIndex_, - "setTileTexture:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setTileTextures_withRange_, - "setTileTextures:withRange:"); -_MTL_PRIVATE_DEF_SEL(setTileVisibleFunctionTable_atBufferIndex_, - "setTileVisibleFunctionTable:atBufferIndex:"); -_MTL_PRIVATE_DEF_SEL(setTileVisibleFunctionTables_withBufferRange_, - "setTileVisibleFunctionTables:withBufferRange:"); -_MTL_PRIVATE_DEF_SEL(setTileWidth_, - "setTileWidth:"); -_MTL_PRIVATE_DEF_SEL(setTransformationMatrixBuffer_, - "setTransformationMatrixBuffer:"); -_MTL_PRIVATE_DEF_SEL(setTransformationMatrixBufferOffset_, - "setTransformationMatrixBufferOffset:"); -_MTL_PRIVATE_DEF_SEL(setTriangleCount_, - "setTriangleCount:"); -_MTL_PRIVATE_DEF_SEL(setTriangleFillMode_, - "setTriangleFillMode:"); -_MTL_PRIVATE_DEF_SEL(setType_, - "setType:"); -_MTL_PRIVATE_DEF_SEL(setUrl_, - "setUrl:"); -_MTL_PRIVATE_DEF_SEL(setUsage_, - "setUsage:"); -_MTL_PRIVATE_DEF_SEL(setVertexAccelerationStructure_atBufferIndex_, - "setVertexAccelerationStructure:atBufferIndex:"); -_MTL_PRIVATE_DEF_SEL(setVertexAdditionalBinaryFunctions_, - "setVertexAdditionalBinaryFunctions:"); -_MTL_PRIVATE_DEF_SEL(setVertexAmplificationCount_viewMappings_, - "setVertexAmplificationCount:viewMappings:"); -_MTL_PRIVATE_DEF_SEL(setVertexBuffer_, - "setVertexBuffer:"); -_MTL_PRIVATE_DEF_SEL(setVertexBuffer_offset_atIndex_, - "setVertexBuffer:offset:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setVertexBufferOffset_, - "setVertexBufferOffset:"); -_MTL_PRIVATE_DEF_SEL(setVertexBufferOffset_atIndex_, - "setVertexBufferOffset:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setVertexBuffers_, - "setVertexBuffers:"); -_MTL_PRIVATE_DEF_SEL(setVertexBuffers_offsets_withRange_, - "setVertexBuffers:offsets:withRange:"); -_MTL_PRIVATE_DEF_SEL(setVertexBytes_length_atIndex_, - "setVertexBytes:length:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setVertexDescriptor_, - "setVertexDescriptor:"); -_MTL_PRIVATE_DEF_SEL(setVertexFormat_, - "setVertexFormat:"); -_MTL_PRIVATE_DEF_SEL(setVertexFunction_, - "setVertexFunction:"); -_MTL_PRIVATE_DEF_SEL(setVertexIntersectionFunctionTable_atBufferIndex_, - "setVertexIntersectionFunctionTable:atBufferIndex:"); -_MTL_PRIVATE_DEF_SEL(setVertexIntersectionFunctionTables_withBufferRange_, - "setVertexIntersectionFunctionTables:withBufferRange:"); -_MTL_PRIVATE_DEF_SEL(setVertexLinkedFunctions_, - "setVertexLinkedFunctions:"); -_MTL_PRIVATE_DEF_SEL(setVertexPreloadedLibraries_, - "setVertexPreloadedLibraries:"); -_MTL_PRIVATE_DEF_SEL(setVertexSamplerState_atIndex_, - "setVertexSamplerState:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setVertexSamplerState_lodMinClamp_lodMaxClamp_atIndex_, - "setVertexSamplerState:lodMinClamp:lodMaxClamp:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setVertexSamplerStates_lodMinClamps_lodMaxClamps_withRange_, - "setVertexSamplerStates:lodMinClamps:lodMaxClamps:withRange:"); -_MTL_PRIVATE_DEF_SEL(setVertexSamplerStates_withRange_, - "setVertexSamplerStates:withRange:"); -_MTL_PRIVATE_DEF_SEL(setVertexStride_, - "setVertexStride:"); -_MTL_PRIVATE_DEF_SEL(setVertexTexture_atIndex_, - "setVertexTexture:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setVertexTextures_withRange_, - "setVertexTextures:withRange:"); -_MTL_PRIVATE_DEF_SEL(setVertexVisibleFunctionTable_atBufferIndex_, - "setVertexVisibleFunctionTable:atBufferIndex:"); -_MTL_PRIVATE_DEF_SEL(setVertexVisibleFunctionTables_withBufferRange_, - "setVertexVisibleFunctionTables:withBufferRange:"); -_MTL_PRIVATE_DEF_SEL(setViewport_, - "setViewport:"); -_MTL_PRIVATE_DEF_SEL(setViewports_count_, - "setViewports:count:"); -_MTL_PRIVATE_DEF_SEL(setVisibilityResultBuffer_, - "setVisibilityResultBuffer:"); -_MTL_PRIVATE_DEF_SEL(setVisibilityResultMode_offset_, - "setVisibilityResultMode:offset:"); -_MTL_PRIVATE_DEF_SEL(setVisibleFunctionTable_atBufferIndex_, - "setVisibleFunctionTable:atBufferIndex:"); -_MTL_PRIVATE_DEF_SEL(setVisibleFunctionTable_atIndex_, - "setVisibleFunctionTable:atIndex:"); -_MTL_PRIVATE_DEF_SEL(setVisibleFunctionTables_withBufferRange_, - "setVisibleFunctionTables:withBufferRange:"); -_MTL_PRIVATE_DEF_SEL(setVisibleFunctionTables_withRange_, - "setVisibleFunctionTables:withRange:"); -_MTL_PRIVATE_DEF_SEL(setWidth_, - "setWidth:"); -_MTL_PRIVATE_DEF_SEL(setWriteMask_, - "setWriteMask:"); -_MTL_PRIVATE_DEF_SEL(sharedCaptureManager, - "sharedCaptureManager"); -_MTL_PRIVATE_DEF_SEL(signalEvent_value_, - "signalEvent:value:"); -_MTL_PRIVATE_DEF_SEL(signaledValue, - "signaledValue"); -_MTL_PRIVATE_DEF_SEL(size, - "size"); -_MTL_PRIVATE_DEF_SEL(slice, - "slice"); -_MTL_PRIVATE_DEF_SEL(sourceAlphaBlendFactor, - "sourceAlphaBlendFactor"); -_MTL_PRIVATE_DEF_SEL(sourceRGBBlendFactor, - "sourceRGBBlendFactor"); -_MTL_PRIVATE_DEF_SEL(sparsePageSize, - "sparsePageSize"); -_MTL_PRIVATE_DEF_SEL(sparseTileSizeInBytes, - "sparseTileSizeInBytes"); -_MTL_PRIVATE_DEF_SEL(sparseTileSizeInBytesForSparsePageSize_, - "sparseTileSizeInBytesForSparsePageSize:"); -_MTL_PRIVATE_DEF_SEL(sparseTileSizeWithTextureType_pixelFormat_sampleCount_, - "sparseTileSizeWithTextureType:pixelFormat:sampleCount:"); -_MTL_PRIVATE_DEF_SEL(sparseTileSizeWithTextureType_pixelFormat_sampleCount_sparsePageSize_, - "sparseTileSizeWithTextureType:pixelFormat:sampleCount:sparsePageSize:"); -_MTL_PRIVATE_DEF_SEL(specializedName, - "specializedName"); -_MTL_PRIVATE_DEF_SEL(stageInputAttributes, - "stageInputAttributes"); -_MTL_PRIVATE_DEF_SEL(stageInputDescriptor, - "stageInputDescriptor"); -_MTL_PRIVATE_DEF_SEL(stageInputOutputDescriptor, - "stageInputOutputDescriptor"); -_MTL_PRIVATE_DEF_SEL(startCaptureWithCommandQueue_, - "startCaptureWithCommandQueue:"); -_MTL_PRIVATE_DEF_SEL(startCaptureWithDescriptor_error_, - "startCaptureWithDescriptor:error:"); -_MTL_PRIVATE_DEF_SEL(startCaptureWithDevice_, - "startCaptureWithDevice:"); -_MTL_PRIVATE_DEF_SEL(startCaptureWithScope_, - "startCaptureWithScope:"); -_MTL_PRIVATE_DEF_SEL(startOfEncoderSampleIndex, - "startOfEncoderSampleIndex"); -_MTL_PRIVATE_DEF_SEL(startOfFragmentSampleIndex, - "startOfFragmentSampleIndex"); -_MTL_PRIVATE_DEF_SEL(startOfVertexSampleIndex, - "startOfVertexSampleIndex"); -_MTL_PRIVATE_DEF_SEL(staticThreadgroupMemoryLength, - "staticThreadgroupMemoryLength"); -_MTL_PRIVATE_DEF_SEL(status, - "status"); -_MTL_PRIVATE_DEF_SEL(stencilAttachment, - "stencilAttachment"); -_MTL_PRIVATE_DEF_SEL(stencilAttachmentPixelFormat, - "stencilAttachmentPixelFormat"); -_MTL_PRIVATE_DEF_SEL(stencilCompareFunction, - "stencilCompareFunction"); -_MTL_PRIVATE_DEF_SEL(stencilFailureOperation, - "stencilFailureOperation"); -_MTL_PRIVATE_DEF_SEL(stencilResolveFilter, - "stencilResolveFilter"); -_MTL_PRIVATE_DEF_SEL(stepFunction, - "stepFunction"); -_MTL_PRIVATE_DEF_SEL(stepRate, - "stepRate"); -_MTL_PRIVATE_DEF_SEL(stopCapture, - "stopCapture"); -_MTL_PRIVATE_DEF_SEL(storageMode, - "storageMode"); -_MTL_PRIVATE_DEF_SEL(storeAction, - "storeAction"); -_MTL_PRIVATE_DEF_SEL(storeActionOptions, - "storeActionOptions"); -_MTL_PRIVATE_DEF_SEL(stride, - "stride"); -_MTL_PRIVATE_DEF_SEL(structType, - "structType"); -_MTL_PRIVATE_DEF_SEL(supportAddingBinaryFunctions, - "supportAddingBinaryFunctions"); -_MTL_PRIVATE_DEF_SEL(supportAddingFragmentBinaryFunctions, - "supportAddingFragmentBinaryFunctions"); -_MTL_PRIVATE_DEF_SEL(supportAddingVertexBinaryFunctions, - "supportAddingVertexBinaryFunctions"); -_MTL_PRIVATE_DEF_SEL(supportArgumentBuffers, - "supportArgumentBuffers"); -_MTL_PRIVATE_DEF_SEL(supportIndirectCommandBuffers, - "supportIndirectCommandBuffers"); -_MTL_PRIVATE_DEF_SEL(supportRayTracing, - "supportRayTracing"); -_MTL_PRIVATE_DEF_SEL(supports32BitFloatFiltering, - "supports32BitFloatFiltering"); -_MTL_PRIVATE_DEF_SEL(supports32BitMSAA, - "supports32BitMSAA"); -_MTL_PRIVATE_DEF_SEL(supportsBCTextureCompression, - "supportsBCTextureCompression"); -_MTL_PRIVATE_DEF_SEL(supportsCounterSampling_, - "supportsCounterSampling:"); -_MTL_PRIVATE_DEF_SEL(supportsDestination_, - "supportsDestination:"); -_MTL_PRIVATE_DEF_SEL(supportsDynamicLibraries, - "supportsDynamicLibraries"); -_MTL_PRIVATE_DEF_SEL(supportsFamily_, - "supportsFamily:"); -_MTL_PRIVATE_DEF_SEL(supportsFeatureSet_, - "supportsFeatureSet:"); -_MTL_PRIVATE_DEF_SEL(supportsFunctionPointers, - "supportsFunctionPointers"); -_MTL_PRIVATE_DEF_SEL(supportsFunctionPointersFromRender, - "supportsFunctionPointersFromRender"); -_MTL_PRIVATE_DEF_SEL(supportsPrimitiveMotionBlur, - "supportsPrimitiveMotionBlur"); -_MTL_PRIVATE_DEF_SEL(supportsPullModelInterpolation, - "supportsPullModelInterpolation"); -_MTL_PRIVATE_DEF_SEL(supportsQueryTextureLOD, - "supportsQueryTextureLOD"); -_MTL_PRIVATE_DEF_SEL(supportsRasterizationRateMapWithLayerCount_, - "supportsRasterizationRateMapWithLayerCount:"); -_MTL_PRIVATE_DEF_SEL(supportsRaytracing, - "supportsRaytracing"); -_MTL_PRIVATE_DEF_SEL(supportsRaytracingFromRender, - "supportsRaytracingFromRender"); -_MTL_PRIVATE_DEF_SEL(supportsRenderDynamicLibraries, - "supportsRenderDynamicLibraries"); -_MTL_PRIVATE_DEF_SEL(supportsShaderBarycentricCoordinates, - "supportsShaderBarycentricCoordinates"); -_MTL_PRIVATE_DEF_SEL(supportsTextureSampleCount_, - "supportsTextureSampleCount:"); -_MTL_PRIVATE_DEF_SEL(supportsVertexAmplificationCount_, - "supportsVertexAmplificationCount:"); -_MTL_PRIVATE_DEF_SEL(swizzle, - "swizzle"); -_MTL_PRIVATE_DEF_SEL(synchronizeResource_, - "synchronizeResource:"); -_MTL_PRIVATE_DEF_SEL(synchronizeTexture_slice_level_, - "synchronizeTexture:slice:level:"); -_MTL_PRIVATE_DEF_SEL(tAddressMode, - "tAddressMode"); -_MTL_PRIVATE_DEF_SEL(tailSizeInBytes, - "tailSizeInBytes"); -_MTL_PRIVATE_DEF_SEL(tessellationControlPointIndexType, - "tessellationControlPointIndexType"); -_MTL_PRIVATE_DEF_SEL(tessellationFactorFormat, - "tessellationFactorFormat"); -_MTL_PRIVATE_DEF_SEL(tessellationFactorStepFunction, - "tessellationFactorStepFunction"); -_MTL_PRIVATE_DEF_SEL(tessellationOutputWindingOrder, - "tessellationOutputWindingOrder"); -_MTL_PRIVATE_DEF_SEL(tessellationPartitionMode, - "tessellationPartitionMode"); -_MTL_PRIVATE_DEF_SEL(texture, - "texture"); -_MTL_PRIVATE_DEF_SEL(texture2DDescriptorWithPixelFormat_width_height_mipmapped_, - "texture2DDescriptorWithPixelFormat:width:height:mipmapped:"); -_MTL_PRIVATE_DEF_SEL(textureBarrier, - "textureBarrier"); -_MTL_PRIVATE_DEF_SEL(textureBufferDescriptorWithPixelFormat_width_resourceOptions_usage_, - "textureBufferDescriptorWithPixelFormat:width:resourceOptions:usage:"); -_MTL_PRIVATE_DEF_SEL(textureCubeDescriptorWithPixelFormat_size_mipmapped_, - "textureCubeDescriptorWithPixelFormat:size:mipmapped:"); -_MTL_PRIVATE_DEF_SEL(textureDataType, - "textureDataType"); -_MTL_PRIVATE_DEF_SEL(textureReferenceType, - "textureReferenceType"); -_MTL_PRIVATE_DEF_SEL(textureType, - "textureType"); -_MTL_PRIVATE_DEF_SEL(threadExecutionWidth, - "threadExecutionWidth"); -_MTL_PRIVATE_DEF_SEL(threadGroupSizeIsMultipleOfThreadExecutionWidth, - "threadGroupSizeIsMultipleOfThreadExecutionWidth"); -_MTL_PRIVATE_DEF_SEL(threadgroupMemoryAlignment, - "threadgroupMemoryAlignment"); -_MTL_PRIVATE_DEF_SEL(threadgroupMemoryDataSize, - "threadgroupMemoryDataSize"); -_MTL_PRIVATE_DEF_SEL(threadgroupMemoryLength, - "threadgroupMemoryLength"); -_MTL_PRIVATE_DEF_SEL(threadgroupSizeMatchesTileSize, - "threadgroupSizeMatchesTileSize"); -_MTL_PRIVATE_DEF_SEL(tileAdditionalBinaryFunctions, - "tileAdditionalBinaryFunctions"); -_MTL_PRIVATE_DEF_SEL(tileArguments, - "tileArguments"); -_MTL_PRIVATE_DEF_SEL(tileBindings, - "tileBindings"); -_MTL_PRIVATE_DEF_SEL(tileBuffers, - "tileBuffers"); -_MTL_PRIVATE_DEF_SEL(tileFunction, - "tileFunction"); -_MTL_PRIVATE_DEF_SEL(tileHeight, - "tileHeight"); -_MTL_PRIVATE_DEF_SEL(tileWidth, - "tileWidth"); -_MTL_PRIVATE_DEF_SEL(transformationMatrixBuffer, - "transformationMatrixBuffer"); -_MTL_PRIVATE_DEF_SEL(transformationMatrixBufferOffset, - "transformationMatrixBufferOffset"); -_MTL_PRIVATE_DEF_SEL(triangleCount, - "triangleCount"); -_MTL_PRIVATE_DEF_SEL(tryCancel, - "tryCancel"); -_MTL_PRIVATE_DEF_SEL(type, - "type"); -_MTL_PRIVATE_DEF_SEL(updateFence_, - "updateFence:"); -_MTL_PRIVATE_DEF_SEL(updateFence_afterStages_, - "updateFence:afterStages:"); -_MTL_PRIVATE_DEF_SEL(updateTextureMapping_mode_indirectBuffer_indirectBufferOffset_, - "updateTextureMapping:mode:indirectBuffer:indirectBufferOffset:"); -_MTL_PRIVATE_DEF_SEL(updateTextureMapping_mode_region_mipLevel_slice_, - "updateTextureMapping:mode:region:mipLevel:slice:"); -_MTL_PRIVATE_DEF_SEL(updateTextureMappings_mode_regions_mipLevels_slices_numRegions_, - "updateTextureMappings:mode:regions:mipLevels:slices:numRegions:"); -_MTL_PRIVATE_DEF_SEL(url, - "url"); -_MTL_PRIVATE_DEF_SEL(usage, - "usage"); -_MTL_PRIVATE_DEF_SEL(useHeap_, - "useHeap:"); -_MTL_PRIVATE_DEF_SEL(useHeap_stages_, - "useHeap:stages:"); -_MTL_PRIVATE_DEF_SEL(useHeaps_count_, - "useHeaps:count:"); -_MTL_PRIVATE_DEF_SEL(useHeaps_count_stages_, - "useHeaps:count:stages:"); -_MTL_PRIVATE_DEF_SEL(useResource_usage_, - "useResource:usage:"); -_MTL_PRIVATE_DEF_SEL(useResource_usage_stages_, - "useResource:usage:stages:"); -_MTL_PRIVATE_DEF_SEL(useResources_count_usage_, - "useResources:count:usage:"); -_MTL_PRIVATE_DEF_SEL(useResources_count_usage_stages_, - "useResources:count:usage:stages:"); -_MTL_PRIVATE_DEF_SEL(usedSize, - "usedSize"); -_MTL_PRIVATE_DEF_SEL(vertexAdditionalBinaryFunctions, - "vertexAdditionalBinaryFunctions"); -_MTL_PRIVATE_DEF_SEL(vertexArguments, - "vertexArguments"); -_MTL_PRIVATE_DEF_SEL(vertexAttributes, - "vertexAttributes"); -_MTL_PRIVATE_DEF_SEL(vertexBindings, - "vertexBindings"); -_MTL_PRIVATE_DEF_SEL(vertexBuffer, - "vertexBuffer"); -_MTL_PRIVATE_DEF_SEL(vertexBufferOffset, - "vertexBufferOffset"); -_MTL_PRIVATE_DEF_SEL(vertexBuffers, - "vertexBuffers"); -_MTL_PRIVATE_DEF_SEL(vertexDescriptor, - "vertexDescriptor"); -_MTL_PRIVATE_DEF_SEL(vertexFormat, - "vertexFormat"); -_MTL_PRIVATE_DEF_SEL(vertexFunction, - "vertexFunction"); -_MTL_PRIVATE_DEF_SEL(vertexLinkedFunctions, - "vertexLinkedFunctions"); -_MTL_PRIVATE_DEF_SEL(vertexPreloadedLibraries, - "vertexPreloadedLibraries"); -_MTL_PRIVATE_DEF_SEL(vertexStride, - "vertexStride"); -_MTL_PRIVATE_DEF_SEL(vertical, - "vertical"); -_MTL_PRIVATE_DEF_SEL(verticalSampleStorage, - "verticalSampleStorage"); -_MTL_PRIVATE_DEF_SEL(visibilityResultBuffer, - "visibilityResultBuffer"); -_MTL_PRIVATE_DEF_SEL(visibleFunctionTableDescriptor, - "visibleFunctionTableDescriptor"); -_MTL_PRIVATE_DEF_SEL(waitForEvent_value_, - "waitForEvent:value:"); -_MTL_PRIVATE_DEF_SEL(waitForFence_, - "waitForFence:"); -_MTL_PRIVATE_DEF_SEL(waitForFence_beforeStages_, - "waitForFence:beforeStages:"); -_MTL_PRIVATE_DEF_SEL(waitUntilCompleted, - "waitUntilCompleted"); -_MTL_PRIVATE_DEF_SEL(waitUntilScheduled, - "waitUntilScheduled"); -_MTL_PRIVATE_DEF_SEL(width, - "width"); -_MTL_PRIVATE_DEF_SEL(writeCompactedAccelerationStructureSize_toBuffer_offset_, - "writeCompactedAccelerationStructureSize:toBuffer:offset:"); -_MTL_PRIVATE_DEF_SEL(writeCompactedAccelerationStructureSize_toBuffer_offset_sizeDataType_, - "writeCompactedAccelerationStructureSize:toBuffer:offset:sizeDataType:"); -_MTL_PRIVATE_DEF_SEL(writeMask, - "writeMask"); - -} - -#include -#include - -namespace MTL -{ -using DrawablePresentedHandler = void (^)(class Drawable*); - -using DrawablePresentedHandlerFunction = std::function; - -class Drawable : public NS::Referencing -{ -public: - void addPresentedHandler(const MTL::DrawablePresentedHandlerFunction& function); - - void present(); - - void presentAtTime(CFTimeInterval presentationTime); - - void presentAfterMinimumDuration(CFTimeInterval duration); - - void addPresentedHandler(const MTL::DrawablePresentedHandler block); - - CFTimeInterval presentedTime() const; - - NS::UInteger drawableID() const; -}; - -} - -_MTL_INLINE void MTL::Drawable::addPresentedHandler(const MTL::DrawablePresentedHandlerFunction& function) -{ - __block DrawablePresentedHandlerFunction blockFunction = function; - - addPresentedHandler(^(Drawable* pDrawable) { blockFunction(pDrawable); }); -} - -_MTL_INLINE void MTL::Drawable::present() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(present)); -} - -_MTL_INLINE void MTL::Drawable::presentAtTime(CFTimeInterval presentationTime) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(presentAtTime_), presentationTime); -} - -_MTL_INLINE void MTL::Drawable::presentAfterMinimumDuration(CFTimeInterval duration) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(presentAfterMinimumDuration_), duration); -} - -_MTL_INLINE void MTL::Drawable::addPresentedHandler(const MTL::DrawablePresentedHandler block) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(addPresentedHandler_), block); -} - -_MTL_INLINE CFTimeInterval MTL::Drawable::presentedTime() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(presentedTime)); -} - -_MTL_INLINE NS::UInteger MTL::Drawable::drawableID() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(drawableID)); -} - -#pragma once - -#pragma once - -namespace MTL -{ -_MTL_ENUM(NS::UInteger, PixelFormat) { - PixelFormatInvalid = 0, - PixelFormatA8Unorm = 1, - PixelFormatR8Unorm = 10, - PixelFormatR8Unorm_sRGB = 11, - PixelFormatR8Snorm = 12, - PixelFormatR8Uint = 13, - PixelFormatR8Sint = 14, - PixelFormatR16Unorm = 20, - PixelFormatR16Snorm = 22, - PixelFormatR16Uint = 23, - PixelFormatR16Sint = 24, - PixelFormatR16Float = 25, - PixelFormatRG8Unorm = 30, - PixelFormatRG8Unorm_sRGB = 31, - PixelFormatRG8Snorm = 32, - PixelFormatRG8Uint = 33, - PixelFormatRG8Sint = 34, - PixelFormatB5G6R5Unorm = 40, - PixelFormatA1BGR5Unorm = 41, - PixelFormatABGR4Unorm = 42, - PixelFormatBGR5A1Unorm = 43, - PixelFormatR32Uint = 53, - PixelFormatR32Sint = 54, - PixelFormatR32Float = 55, - PixelFormatRG16Unorm = 60, - PixelFormatRG16Snorm = 62, - PixelFormatRG16Uint = 63, - PixelFormatRG16Sint = 64, - PixelFormatRG16Float = 65, - PixelFormatRGBA8Unorm = 70, - PixelFormatRGBA8Unorm_sRGB = 71, - PixelFormatRGBA8Snorm = 72, - PixelFormatRGBA8Uint = 73, - PixelFormatRGBA8Sint = 74, - PixelFormatBGRA8Unorm = 80, - PixelFormatBGRA8Unorm_sRGB = 81, - PixelFormatRGB10A2Unorm = 90, - PixelFormatRGB10A2Uint = 91, - PixelFormatRG11B10Float = 92, - PixelFormatRGB9E5Float = 93, - PixelFormatBGR10A2Unorm = 94, - PixelFormatRG32Uint = 103, - PixelFormatRG32Sint = 104, - PixelFormatRG32Float = 105, - PixelFormatRGBA16Unorm = 110, - PixelFormatRGBA16Snorm = 112, - PixelFormatRGBA16Uint = 113, - PixelFormatRGBA16Sint = 114, - PixelFormatRGBA16Float = 115, - PixelFormatRGBA32Uint = 123, - PixelFormatRGBA32Sint = 124, - PixelFormatRGBA32Float = 125, - PixelFormatBC1_RGBA = 130, - PixelFormatBC1_RGBA_sRGB = 131, - PixelFormatBC2_RGBA = 132, - PixelFormatBC2_RGBA_sRGB = 133, - PixelFormatBC3_RGBA = 134, - PixelFormatBC3_RGBA_sRGB = 135, - PixelFormatBC4_RUnorm = 140, - PixelFormatBC4_RSnorm = 141, - PixelFormatBC5_RGUnorm = 142, - PixelFormatBC5_RGSnorm = 143, - PixelFormatBC6H_RGBFloat = 150, - PixelFormatBC6H_RGBUfloat = 151, - PixelFormatBC7_RGBAUnorm = 152, - PixelFormatBC7_RGBAUnorm_sRGB = 153, - PixelFormatPVRTC_RGB_2BPP = 160, - PixelFormatPVRTC_RGB_2BPP_sRGB = 161, - PixelFormatPVRTC_RGB_4BPP = 162, - PixelFormatPVRTC_RGB_4BPP_sRGB = 163, - PixelFormatPVRTC_RGBA_2BPP = 164, - PixelFormatPVRTC_RGBA_2BPP_sRGB = 165, - PixelFormatPVRTC_RGBA_4BPP = 166, - PixelFormatPVRTC_RGBA_4BPP_sRGB = 167, - PixelFormatEAC_R11Unorm = 170, - PixelFormatEAC_R11Snorm = 172, - PixelFormatEAC_RG11Unorm = 174, - PixelFormatEAC_RG11Snorm = 176, - PixelFormatEAC_RGBA8 = 178, - PixelFormatEAC_RGBA8_sRGB = 179, - PixelFormatETC2_RGB8 = 180, - PixelFormatETC2_RGB8_sRGB = 181, - PixelFormatETC2_RGB8A1 = 182, - PixelFormatETC2_RGB8A1_sRGB = 183, - PixelFormatASTC_4x4_sRGB = 186, - PixelFormatASTC_5x4_sRGB = 187, - PixelFormatASTC_5x5_sRGB = 188, - PixelFormatASTC_6x5_sRGB = 189, - PixelFormatASTC_6x6_sRGB = 190, - PixelFormatASTC_8x5_sRGB = 192, - PixelFormatASTC_8x6_sRGB = 193, - PixelFormatASTC_8x8_sRGB = 194, - PixelFormatASTC_10x5_sRGB = 195, - PixelFormatASTC_10x6_sRGB = 196, - PixelFormatASTC_10x8_sRGB = 197, - PixelFormatASTC_10x10_sRGB = 198, - PixelFormatASTC_12x10_sRGB = 199, - PixelFormatASTC_12x12_sRGB = 200, - PixelFormatASTC_4x4_LDR = 204, - PixelFormatASTC_5x4_LDR = 205, - PixelFormatASTC_5x5_LDR = 206, - PixelFormatASTC_6x5_LDR = 207, - PixelFormatASTC_6x6_LDR = 208, - PixelFormatASTC_8x5_LDR = 210, - PixelFormatASTC_8x6_LDR = 211, - PixelFormatASTC_8x8_LDR = 212, - PixelFormatASTC_10x5_LDR = 213, - PixelFormatASTC_10x6_LDR = 214, - PixelFormatASTC_10x8_LDR = 215, - PixelFormatASTC_10x10_LDR = 216, - PixelFormatASTC_12x10_LDR = 217, - PixelFormatASTC_12x12_LDR = 218, - PixelFormatASTC_4x4_HDR = 222, - PixelFormatASTC_5x4_HDR = 223, - PixelFormatASTC_5x5_HDR = 224, - PixelFormatASTC_6x5_HDR = 225, - PixelFormatASTC_6x6_HDR = 226, - PixelFormatASTC_8x5_HDR = 228, - PixelFormatASTC_8x6_HDR = 229, - PixelFormatASTC_8x8_HDR = 230, - PixelFormatASTC_10x5_HDR = 231, - PixelFormatASTC_10x6_HDR = 232, - PixelFormatASTC_10x8_HDR = 233, - PixelFormatASTC_10x10_HDR = 234, - PixelFormatASTC_12x10_HDR = 235, - PixelFormatASTC_12x12_HDR = 236, - PixelFormatGBGR422 = 240, - PixelFormatBGRG422 = 241, - PixelFormatDepth16Unorm = 250, - PixelFormatDepth32Float = 252, - PixelFormatStencil8 = 253, - PixelFormatDepth24Unorm_Stencil8 = 255, - PixelFormatDepth32Float_Stencil8 = 260, - PixelFormatX32_Stencil8 = 261, - PixelFormatX24_Stencil8 = 262, - PixelFormatBGRA10_XR = 552, - PixelFormatBGRA10_XR_sRGB = 553, - PixelFormatBGR10_XR = 554, - PixelFormatBGR10_XR_sRGB = 555, -}; - -} - -#pragma once - -namespace MTL -{ -_MTL_ENUM(NS::UInteger, PurgeableState) { - PurgeableStateKeepCurrent = 1, - PurgeableStateNonVolatile = 2, - PurgeableStateVolatile = 3, - PurgeableStateEmpty = 4, -}; - -_MTL_ENUM(NS::UInteger, CPUCacheMode) { - CPUCacheModeDefaultCache = 0, - CPUCacheModeWriteCombined = 1, -}; - -_MTL_ENUM(NS::UInteger, StorageMode) { - StorageModeShared = 0, - StorageModeManaged = 1, - StorageModePrivate = 2, - StorageModeMemoryless = 3, -}; - -_MTL_ENUM(NS::UInteger, HazardTrackingMode) { - HazardTrackingModeDefault = 0, - HazardTrackingModeUntracked = 1, - HazardTrackingModeTracked = 2, -}; - -_MTL_OPTIONS(NS::UInteger, ResourceOptions) { - ResourceStorageModeShared = 0, - ResourceHazardTrackingModeDefault = 0, - ResourceCPUCacheModeDefaultCache = 0, - ResourceOptionCPUCacheModeDefault = 0, - ResourceCPUCacheModeWriteCombined = 1, - ResourceOptionCPUCacheModeWriteCombined = 1, - ResourceStorageModeManaged = 16, - ResourceStorageModePrivate = 32, - ResourceStorageModeMemoryless = 48, - ResourceHazardTrackingModeUntracked = 256, - ResourceHazardTrackingModeTracked = 512, -}; - -class Resource : public NS::Referencing -{ -public: - NS::String* label() const; - void setLabel(const NS::String* label); - - class Device* device() const; - - MTL::CPUCacheMode cpuCacheMode() const; - - MTL::StorageMode storageMode() const; - - MTL::HazardTrackingMode hazardTrackingMode() const; - - MTL::ResourceOptions resourceOptions() const; - - MTL::PurgeableState setPurgeableState(MTL::PurgeableState state); - - class Heap* heap() const; - - NS::UInteger heapOffset() const; - - NS::UInteger allocatedSize() const; - - void makeAliasable(); - - bool isAliasable(); -}; - -} - -_MTL_INLINE NS::String* MTL::Resource::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE void MTL::Resource::setLabel(const NS::String* label) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLabel_), label); -} - -_MTL_INLINE MTL::Device* MTL::Resource::device() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(device)); -} - -_MTL_INLINE MTL::CPUCacheMode MTL::Resource::cpuCacheMode() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(cpuCacheMode)); -} - -_MTL_INLINE MTL::StorageMode MTL::Resource::storageMode() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(storageMode)); -} - -_MTL_INLINE MTL::HazardTrackingMode MTL::Resource::hazardTrackingMode() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(hazardTrackingMode)); -} - -_MTL_INLINE MTL::ResourceOptions MTL::Resource::resourceOptions() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(resourceOptions)); -} - -_MTL_INLINE MTL::PurgeableState MTL::Resource::setPurgeableState(MTL::PurgeableState state) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(setPurgeableState_), state); -} - -_MTL_INLINE MTL::Heap* MTL::Resource::heap() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(heap)); -} - -_MTL_INLINE NS::UInteger MTL::Resource::heapOffset() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(heapOffset)); -} - -_MTL_INLINE NS::UInteger MTL::Resource::allocatedSize() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(allocatedSize)); -} - -_MTL_INLINE void MTL::Resource::makeAliasable() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(makeAliasable)); -} - -_MTL_INLINE bool MTL::Resource::isAliasable() -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(isAliasable)); -} - -#pragma once - -namespace MTL -{ -struct Origin -{ - Origin() = default; - - Origin(NS::UInteger x, NS::UInteger y, NS::UInteger z); - - static Origin Make(NS::UInteger x, NS::UInteger y, NS::UInteger z); - - NS::UInteger x; - NS::UInteger y; - NS::UInteger z; -} _MTL_PACKED; - -struct Size -{ - Size() = default; - - Size(NS::UInteger width, NS::UInteger height, NS::UInteger depth); - - static Size Make(NS::UInteger width, NS::UInteger height, NS::UInteger depth); - - NS::UInteger width; - NS::UInteger height; - NS::UInteger depth; -} _MTL_PACKED; - -struct Region -{ - Region() = default; - - Region(NS::UInteger x, NS::UInteger width); - - Region(NS::UInteger x, NS::UInteger y, NS::UInteger width, NS::UInteger height); - - Region(NS::UInteger x, NS::UInteger y, NS::UInteger z, NS::UInteger width, NS::UInteger height, NS::UInteger depth); - - static Region Make1D(NS::UInteger x, NS::UInteger width); - - static Region Make2D(NS::UInteger x, NS::UInteger y, NS::UInteger width, NS::UInteger height); - - static Region Make3D(NS::UInteger x, NS::UInteger y, NS::UInteger z, NS::UInteger width, NS::UInteger height, NS::UInteger depth); - - MTL::Origin origin; - MTL::Size size; -} _MTL_PACKED; - -struct SamplePosition; - -using Coordinate2D = SamplePosition; - -struct SamplePosition -{ - SamplePosition() = default; - - SamplePosition(float _x, float _y); - - static SamplePosition Make(float x, float y); - - float x; - float y; -} _MTL_PACKED; - -struct ResourceID -{ - uint64_t _impl; -} _MTL_PACKED; - -} - -_MTL_INLINE MTL::Origin::Origin(NS::UInteger _x, NS::UInteger _y, NS::UInteger _z) - : x(_x) - , y(_y) - , z(_z) -{ -} - -_MTL_INLINE MTL::Origin MTL::Origin::Make(NS::UInteger x, NS::UInteger y, NS::UInteger z) -{ - return Origin(x, y, z); -} - -_MTL_INLINE MTL::Size::Size(NS::UInteger _width, NS::UInteger _height, NS::UInteger _depth) - : width(_width) - , height(_height) - , depth(_depth) -{ -} - -_MTL_INLINE MTL::Size MTL::Size::Make(NS::UInteger width, NS::UInteger height, NS::UInteger depth) -{ - return Size(width, height, depth); -} - -_MTL_INLINE MTL::Region::Region(NS::UInteger x, NS::UInteger width) - : origin(x, 0, 0) - , size(width, 1, 1) -{ -} - -_MTL_INLINE MTL::Region::Region(NS::UInteger x, NS::UInteger y, NS::UInteger width, NS::UInteger height) - : origin(x, y, 0) - , size(width, height, 1) -{ -} - -_MTL_INLINE MTL::Region::Region(NS::UInteger x, NS::UInteger y, NS::UInteger z, NS::UInteger width, NS::UInteger height, NS::UInteger depth) - : origin(x, y, z) - , size(width, height, depth) -{ -} - -_MTL_INLINE MTL::Region MTL::Region::Make1D(NS::UInteger x, NS::UInteger width) -{ - return Region(x, width); -} - -_MTL_INLINE MTL::Region MTL::Region::Make2D(NS::UInteger x, NS::UInteger y, NS::UInteger width, NS::UInteger height) -{ - return Region(x, y, width, height); -} - -_MTL_INLINE MTL::Region MTL::Region::Make3D(NS::UInteger x, NS::UInteger y, NS::UInteger z, NS::UInteger width, NS::UInteger height, NS::UInteger depth) -{ - return Region(x, y, z, width, height, depth); -} - -_MTL_INLINE MTL::SamplePosition::SamplePosition(float _x, float _y) - : x(_x) - , y(_y) -{ -} - -_MTL_INLINE MTL::SamplePosition MTL::SamplePosition::Make(float x, float y) -{ - return SamplePosition(x, y); -} - -#include - -namespace MTL -{ -_MTL_ENUM(NS::UInteger, TextureType) { - TextureType1D = 0, - TextureType1DArray = 1, - TextureType2D = 2, - TextureType2DArray = 3, - TextureType2DMultisample = 4, - TextureTypeCube = 5, - TextureTypeCubeArray = 6, - TextureType3D = 7, - TextureType2DMultisampleArray = 8, - TextureTypeTextureBuffer = 9, -}; - -_MTL_ENUM(uint8_t, TextureSwizzle) { - TextureSwizzleZero = 0, - TextureSwizzleOne = 1, - TextureSwizzleRed = 2, - TextureSwizzleGreen = 3, - TextureSwizzleBlue = 4, - TextureSwizzleAlpha = 5, -}; - -struct TextureSwizzleChannels -{ - MTL::TextureSwizzle red; - MTL::TextureSwizzle green; - MTL::TextureSwizzle blue; - MTL::TextureSwizzle alpha; -} _MTL_PACKED; - -class SharedTextureHandle : public NS::SecureCoding -{ -public: - static class SharedTextureHandle* alloc(); - - class SharedTextureHandle* init(); - - class Device* device() const; - - NS::String* label() const; -}; - -_MTL_OPTIONS(NS::UInteger, TextureUsage) { - TextureUsageUnknown = 0, - TextureUsageShaderRead = 1, - TextureUsageShaderWrite = 2, - TextureUsageRenderTarget = 4, - TextureUsagePixelFormatView = 16, -}; - -_MTL_ENUM(NS::Integer, TextureCompressionType) { - TextureCompressionTypeLossless = 0, - TextureCompressionTypeLossy = 1, -}; - -class TextureDescriptor : public NS::Copying -{ -public: - static class TextureDescriptor* alloc(); - - class TextureDescriptor* init(); - - static class TextureDescriptor* texture2DDescriptor(MTL::PixelFormat pixelFormat, NS::UInteger width, NS::UInteger height, bool mipmapped); - - static class TextureDescriptor* textureCubeDescriptor(MTL::PixelFormat pixelFormat, NS::UInteger size, bool mipmapped); - - static class TextureDescriptor* textureBufferDescriptor(MTL::PixelFormat pixelFormat, NS::UInteger width, MTL::ResourceOptions resourceOptions, MTL::TextureUsage usage); - - MTL::TextureType textureType() const; - void setTextureType(MTL::TextureType textureType); - - MTL::PixelFormat pixelFormat() const; - void setPixelFormat(MTL::PixelFormat pixelFormat); - - NS::UInteger width() const; - void setWidth(NS::UInteger width); - - NS::UInteger height() const; - void setHeight(NS::UInteger height); - - NS::UInteger depth() const; - void setDepth(NS::UInteger depth); - - NS::UInteger mipmapLevelCount() const; - void setMipmapLevelCount(NS::UInteger mipmapLevelCount); - - NS::UInteger sampleCount() const; - void setSampleCount(NS::UInteger sampleCount); - - NS::UInteger arrayLength() const; - void setArrayLength(NS::UInteger arrayLength); - - MTL::ResourceOptions resourceOptions() const; - void setResourceOptions(MTL::ResourceOptions resourceOptions); - - MTL::CPUCacheMode cpuCacheMode() const; - void setCpuCacheMode(MTL::CPUCacheMode cpuCacheMode); - - MTL::StorageMode storageMode() const; - void setStorageMode(MTL::StorageMode storageMode); - - MTL::HazardTrackingMode hazardTrackingMode() const; - void setHazardTrackingMode(MTL::HazardTrackingMode hazardTrackingMode); - - MTL::TextureUsage usage() const; - void setUsage(MTL::TextureUsage usage); - - bool allowGPUOptimizedContents() const; - void setAllowGPUOptimizedContents(bool allowGPUOptimizedContents); - - MTL::TextureCompressionType compressionType() const; - void setCompressionType(MTL::TextureCompressionType compressionType); - - MTL::TextureSwizzleChannels swizzle() const; - void setSwizzle(MTL::TextureSwizzleChannels swizzle); -}; - -class Texture : public NS::Referencing -{ -public: - class Resource* rootResource() const; - - class Texture* parentTexture() const; - - NS::UInteger parentRelativeLevel() const; - - NS::UInteger parentRelativeSlice() const; - - class Buffer* buffer() const; - - NS::UInteger bufferOffset() const; - - NS::UInteger bufferBytesPerRow() const; - - IOSurfaceRef iosurface() const; - - NS::UInteger iosurfacePlane() const; - - MTL::TextureType textureType() const; - - MTL::PixelFormat pixelFormat() const; - - NS::UInteger width() const; - - NS::UInteger height() const; - - NS::UInteger depth() const; - - NS::UInteger mipmapLevelCount() const; - - NS::UInteger sampleCount() const; - - NS::UInteger arrayLength() const; - - MTL::TextureUsage usage() const; - - bool shareable() const; - - bool framebufferOnly() const; - - NS::UInteger firstMipmapInTail() const; - - NS::UInteger tailSizeInBytes() const; - - bool isSparse() const; - - bool allowGPUOptimizedContents() const; - - MTL::TextureCompressionType compressionType() const; - - MTL::ResourceID gpuResourceID() const; - - void getBytes(const void* pixelBytes, NS::UInteger bytesPerRow, NS::UInteger bytesPerImage, MTL::Region region, NS::UInteger level, NS::UInteger slice); - - void replaceRegion(MTL::Region region, NS::UInteger level, NS::UInteger slice, const void* pixelBytes, NS::UInteger bytesPerRow, NS::UInteger bytesPerImage); - - void getBytes(const void* pixelBytes, NS::UInteger bytesPerRow, MTL::Region region, NS::UInteger level); - - void replaceRegion(MTL::Region region, NS::UInteger level, const void* pixelBytes, NS::UInteger bytesPerRow); - - class Texture* newTextureView(MTL::PixelFormat pixelFormat); - - class Texture* newTextureView(MTL::PixelFormat pixelFormat, MTL::TextureType textureType, NS::Range levelRange, NS::Range sliceRange); - - class SharedTextureHandle* newSharedTextureHandle(); - - class Texture* remoteStorageTexture() const; - - class Texture* newRemoteTextureViewForDevice(const class Device* device); - - MTL::TextureSwizzleChannels swizzle() const; - - class Texture* newTextureView(MTL::PixelFormat pixelFormat, MTL::TextureType textureType, NS::Range levelRange, NS::Range sliceRange, MTL::TextureSwizzleChannels swizzle); -}; - -} - -_MTL_INLINE MTL::SharedTextureHandle* MTL::SharedTextureHandle::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLSharedTextureHandle)); -} - -_MTL_INLINE MTL::SharedTextureHandle* MTL::SharedTextureHandle::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::Device* MTL::SharedTextureHandle::device() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(device)); -} - -_MTL_INLINE NS::String* MTL::SharedTextureHandle::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE MTL::TextureDescriptor* MTL::TextureDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLTextureDescriptor)); -} - -_MTL_INLINE MTL::TextureDescriptor* MTL::TextureDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::TextureDescriptor* MTL::TextureDescriptor::texture2DDescriptor(MTL::PixelFormat pixelFormat, NS::UInteger width, NS::UInteger height, bool mipmapped) -{ - return Object::sendMessage(_MTL_PRIVATE_CLS(MTLTextureDescriptor), _MTL_PRIVATE_SEL(texture2DDescriptorWithPixelFormat_width_height_mipmapped_), pixelFormat, width, height, mipmapped); -} - -_MTL_INLINE MTL::TextureDescriptor* MTL::TextureDescriptor::textureCubeDescriptor(MTL::PixelFormat pixelFormat, NS::UInteger size, bool mipmapped) -{ - return Object::sendMessage(_MTL_PRIVATE_CLS(MTLTextureDescriptor), _MTL_PRIVATE_SEL(textureCubeDescriptorWithPixelFormat_size_mipmapped_), pixelFormat, size, mipmapped); -} - -_MTL_INLINE MTL::TextureDescriptor* MTL::TextureDescriptor::textureBufferDescriptor(MTL::PixelFormat pixelFormat, NS::UInteger width, MTL::ResourceOptions resourceOptions, MTL::TextureUsage usage) -{ - return Object::sendMessage(_MTL_PRIVATE_CLS(MTLTextureDescriptor), _MTL_PRIVATE_SEL(textureBufferDescriptorWithPixelFormat_width_resourceOptions_usage_), pixelFormat, width, resourceOptions, usage); -} - -_MTL_INLINE MTL::TextureType MTL::TextureDescriptor::textureType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(textureType)); -} - -_MTL_INLINE void MTL::TextureDescriptor::setTextureType(MTL::TextureType textureType) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTextureType_), textureType); -} - -_MTL_INLINE MTL::PixelFormat MTL::TextureDescriptor::pixelFormat() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(pixelFormat)); -} - -_MTL_INLINE void MTL::TextureDescriptor::setPixelFormat(MTL::PixelFormat pixelFormat) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setPixelFormat_), pixelFormat); -} - -_MTL_INLINE NS::UInteger MTL::TextureDescriptor::width() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(width)); -} - -_MTL_INLINE void MTL::TextureDescriptor::setWidth(NS::UInteger width) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setWidth_), width); -} - -_MTL_INLINE NS::UInteger MTL::TextureDescriptor::height() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(height)); -} - -_MTL_INLINE void MTL::TextureDescriptor::setHeight(NS::UInteger height) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setHeight_), height); -} - -_MTL_INLINE NS::UInteger MTL::TextureDescriptor::depth() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(depth)); -} - -_MTL_INLINE void MTL::TextureDescriptor::setDepth(NS::UInteger depth) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setDepth_), depth); -} - -_MTL_INLINE NS::UInteger MTL::TextureDescriptor::mipmapLevelCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(mipmapLevelCount)); -} - -_MTL_INLINE void MTL::TextureDescriptor::setMipmapLevelCount(NS::UInteger mipmapLevelCount) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMipmapLevelCount_), mipmapLevelCount); -} - -_MTL_INLINE NS::UInteger MTL::TextureDescriptor::sampleCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(sampleCount)); -} - -_MTL_INLINE void MTL::TextureDescriptor::setSampleCount(NS::UInteger sampleCount) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSampleCount_), sampleCount); -} - -_MTL_INLINE NS::UInteger MTL::TextureDescriptor::arrayLength() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(arrayLength)); -} - -_MTL_INLINE void MTL::TextureDescriptor::setArrayLength(NS::UInteger arrayLength) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setArrayLength_), arrayLength); -} - -_MTL_INLINE MTL::ResourceOptions MTL::TextureDescriptor::resourceOptions() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(resourceOptions)); -} - -_MTL_INLINE void MTL::TextureDescriptor::setResourceOptions(MTL::ResourceOptions resourceOptions) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setResourceOptions_), resourceOptions); -} - -_MTL_INLINE MTL::CPUCacheMode MTL::TextureDescriptor::cpuCacheMode() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(cpuCacheMode)); -} - -_MTL_INLINE void MTL::TextureDescriptor::setCpuCacheMode(MTL::CPUCacheMode cpuCacheMode) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setCpuCacheMode_), cpuCacheMode); -} - -_MTL_INLINE MTL::StorageMode MTL::TextureDescriptor::storageMode() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(storageMode)); -} - -_MTL_INLINE void MTL::TextureDescriptor::setStorageMode(MTL::StorageMode storageMode) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStorageMode_), storageMode); -} - -_MTL_INLINE MTL::HazardTrackingMode MTL::TextureDescriptor::hazardTrackingMode() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(hazardTrackingMode)); -} - -_MTL_INLINE void MTL::TextureDescriptor::setHazardTrackingMode(MTL::HazardTrackingMode hazardTrackingMode) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setHazardTrackingMode_), hazardTrackingMode); -} - -_MTL_INLINE MTL::TextureUsage MTL::TextureDescriptor::usage() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(usage)); -} - -_MTL_INLINE void MTL::TextureDescriptor::setUsage(MTL::TextureUsage usage) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setUsage_), usage); -} - -_MTL_INLINE bool MTL::TextureDescriptor::allowGPUOptimizedContents() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(allowGPUOptimizedContents)); -} - -_MTL_INLINE void MTL::TextureDescriptor::setAllowGPUOptimizedContents(bool allowGPUOptimizedContents) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setAllowGPUOptimizedContents_), allowGPUOptimizedContents); -} - -_MTL_INLINE MTL::TextureCompressionType MTL::TextureDescriptor::compressionType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(compressionType)); -} - -_MTL_INLINE void MTL::TextureDescriptor::setCompressionType(MTL::TextureCompressionType compressionType) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setCompressionType_), compressionType); -} - -_MTL_INLINE MTL::TextureSwizzleChannels MTL::TextureDescriptor::swizzle() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(swizzle)); -} - -_MTL_INLINE void MTL::TextureDescriptor::setSwizzle(MTL::TextureSwizzleChannels swizzle) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSwizzle_), swizzle); -} - -_MTL_INLINE MTL::Resource* MTL::Texture::rootResource() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(rootResource)); -} - -_MTL_INLINE MTL::Texture* MTL::Texture::parentTexture() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(parentTexture)); -} - -_MTL_INLINE NS::UInteger MTL::Texture::parentRelativeLevel() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(parentRelativeLevel)); -} - -_MTL_INLINE NS::UInteger MTL::Texture::parentRelativeSlice() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(parentRelativeSlice)); -} - -_MTL_INLINE MTL::Buffer* MTL::Texture::buffer() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(buffer)); -} - -_MTL_INLINE NS::UInteger MTL::Texture::bufferOffset() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(bufferOffset)); -} - -_MTL_INLINE NS::UInteger MTL::Texture::bufferBytesPerRow() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(bufferBytesPerRow)); -} - -_MTL_INLINE IOSurfaceRef MTL::Texture::iosurface() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(iosurface)); -} - -_MTL_INLINE NS::UInteger MTL::Texture::iosurfacePlane() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(iosurfacePlane)); -} - -_MTL_INLINE MTL::TextureType MTL::Texture::textureType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(textureType)); -} - -_MTL_INLINE MTL::PixelFormat MTL::Texture::pixelFormat() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(pixelFormat)); -} - -_MTL_INLINE NS::UInteger MTL::Texture::width() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(width)); -} - -_MTL_INLINE NS::UInteger MTL::Texture::height() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(height)); -} - -_MTL_INLINE NS::UInteger MTL::Texture::depth() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(depth)); -} - -_MTL_INLINE NS::UInteger MTL::Texture::mipmapLevelCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(mipmapLevelCount)); -} - -_MTL_INLINE NS::UInteger MTL::Texture::sampleCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(sampleCount)); -} - -_MTL_INLINE NS::UInteger MTL::Texture::arrayLength() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(arrayLength)); -} - -_MTL_INLINE MTL::TextureUsage MTL::Texture::usage() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(usage)); -} - -_MTL_INLINE bool MTL::Texture::shareable() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(isShareable)); -} - -_MTL_INLINE bool MTL::Texture::framebufferOnly() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(isFramebufferOnly)); -} - -_MTL_INLINE NS::UInteger MTL::Texture::firstMipmapInTail() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(firstMipmapInTail)); -} - -_MTL_INLINE NS::UInteger MTL::Texture::tailSizeInBytes() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(tailSizeInBytes)); -} - -_MTL_INLINE bool MTL::Texture::isSparse() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(isSparse)); -} - -_MTL_INLINE bool MTL::Texture::allowGPUOptimizedContents() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(allowGPUOptimizedContents)); -} - -_MTL_INLINE MTL::TextureCompressionType MTL::Texture::compressionType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(compressionType)); -} - -_MTL_INLINE MTL::ResourceID MTL::Texture::gpuResourceID() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(gpuResourceID)); -} - -_MTL_INLINE void MTL::Texture::getBytes(const void* pixelBytes, NS::UInteger bytesPerRow, NS::UInteger bytesPerImage, MTL::Region region, NS::UInteger level, NS::UInteger slice) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(getBytes_bytesPerRow_bytesPerImage_fromRegion_mipmapLevel_slice_), pixelBytes, bytesPerRow, bytesPerImage, region, level, slice); -} - -_MTL_INLINE void MTL::Texture::replaceRegion(MTL::Region region, NS::UInteger level, NS::UInteger slice, const void* pixelBytes, NS::UInteger bytesPerRow, NS::UInteger bytesPerImage) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(replaceRegion_mipmapLevel_slice_withBytes_bytesPerRow_bytesPerImage_), region, level, slice, pixelBytes, bytesPerRow, bytesPerImage); -} - -_MTL_INLINE void MTL::Texture::getBytes(const void* pixelBytes, NS::UInteger bytesPerRow, MTL::Region region, NS::UInteger level) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(getBytes_bytesPerRow_fromRegion_mipmapLevel_), pixelBytes, bytesPerRow, region, level); -} - -_MTL_INLINE void MTL::Texture::replaceRegion(MTL::Region region, NS::UInteger level, const void* pixelBytes, NS::UInteger bytesPerRow) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(replaceRegion_mipmapLevel_withBytes_bytesPerRow_), region, level, pixelBytes, bytesPerRow); -} - -_MTL_INLINE MTL::Texture* MTL::Texture::newTextureView(MTL::PixelFormat pixelFormat) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newTextureViewWithPixelFormat_), pixelFormat); -} - -_MTL_INLINE MTL::Texture* MTL::Texture::newTextureView(MTL::PixelFormat pixelFormat, MTL::TextureType textureType, NS::Range levelRange, NS::Range sliceRange) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newTextureViewWithPixelFormat_textureType_levels_slices_), pixelFormat, textureType, levelRange, sliceRange); -} - -_MTL_INLINE MTL::SharedTextureHandle* MTL::Texture::newSharedTextureHandle() -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newSharedTextureHandle)); -} - -_MTL_INLINE MTL::Texture* MTL::Texture::remoteStorageTexture() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(remoteStorageTexture)); -} - -_MTL_INLINE MTL::Texture* MTL::Texture::newRemoteTextureViewForDevice(const MTL::Device* device) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newRemoteTextureViewForDevice_), device); -} - -_MTL_INLINE MTL::TextureSwizzleChannels MTL::Texture::swizzle() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(swizzle)); -} - -_MTL_INLINE MTL::Texture* MTL::Texture::newTextureView(MTL::PixelFormat pixelFormat, MTL::TextureType textureType, NS::Range levelRange, NS::Range sliceRange, MTL::TextureSwizzleChannels swizzle) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newTextureViewWithPixelFormat_textureType_levels_slices_swizzle_), pixelFormat, textureType, levelRange, sliceRange, swizzle); -} - -#define _CA_EXPORT _NS_EXPORT -#define _CA_EXTERN _NS_EXTERN -#define _CA_INLINE _NS_INLINE -#define _CA_PACKED _NS_PACKED - -#define _CA_CONST(type, name) _NS_CONST(type, name) -#define _CA_ENUM(type, name) _NS_ENUM(type, name) -#define _CA_OPTIONS(type, name) _NS_OPTIONS(type, name) - -#define _CA_VALIDATE_SIZE(ns, name) _NS_VALIDATE_SIZE(ns, name) -#define _CA_VALIDATE_ENUM(ns, name) _NS_VALIDATE_ENUM(ns, name) - -#include - -#define _CA_PRIVATE_CLS(symbol) (Private::Class::s_k##symbol) -#define _CA_PRIVATE_SEL(accessor) (Private::Selector::s_k##accessor) - -#if defined(CA_PRIVATE_IMPLEMENTATION) - -#ifdef METALCPP_SYMBOL_VISIBILITY_HIDDEN -#define _CA_PRIVATE_VISIBILITY __attribute__((visibility("hidden"))) -#else -#define _CA_PRIVATE_VISIBILITY __attribute__((visibility("default"))) -#endif // METALCPP_SYMBOL_VISIBILITY_HIDDEN - -#define _CA_PRIVATE_IMPORT __attribute__((weak_import)) - -#ifdef __OBJC__ -#define _CA_PRIVATE_OBJC_LOOKUP_CLASS(symbol) ((__bridge void*)objc_lookUpClass(#symbol)) -#define _CA_PRIVATE_OBJC_GET_PROTOCOL(symbol) ((__bridge void*)objc_getProtocol(#symbol)) -#else -#define _CA_PRIVATE_OBJC_LOOKUP_CLASS(symbol) objc_lookUpClass(#symbol) -#define _CA_PRIVATE_OBJC_GET_PROTOCOL(symbol) objc_getProtocol(#symbol) -#endif // __OBJC__ - -#define _CA_PRIVATE_DEF_CLS(symbol) void* s_k##symbol _CA_PRIVATE_VISIBILITY = _CA_PRIVATE_OBJC_LOOKUP_CLASS(symbol) -#define _CA_PRIVATE_DEF_PRO(symbol) void* s_k##symbol _CA_PRIVATE_VISIBILITY = _CA_PRIVATE_OBJC_GET_PROTOCOL(symbol) -#define _CA_PRIVATE_DEF_SEL(accessor, symbol) SEL s_k##accessor _CA_PRIVATE_VISIBILITY = sel_registerName(symbol) -#define _CA_PRIVATE_DEF_STR(type, symbol) \ - _CA_EXTERN type const CA##symbol _CA_PRIVATE_IMPORT; \ - type const CA::symbol = (nullptr != &CA##symbol) ? CA##symbol : nullptr - -#else - -#define _CA_PRIVATE_DEF_CLS(symbol) extern void* s_k##symbol -#define _CA_PRIVATE_DEF_PRO(symbol) extern void* s_k##symbol -#define _CA_PRIVATE_DEF_SEL(accessor, symbol) extern SEL s_k##accessor -#define _CA_PRIVATE_DEF_STR(type, symbol) extern type const CA::symbol - -#endif // CA_PRIVATE_IMPLEMENTATION - -namespace CA -{ -namespace Private -{ - namespace Class - { - _CA_PRIVATE_DEF_CLS(CAMetalLayer); - } // Class -} // Private -} // CA - -namespace CA -{ -namespace Private -{ - namespace Protocol - { - - _CA_PRIVATE_DEF_PRO(CAMetalDrawable); - - } // Protocol -} // Private -} // CA - -namespace CA -{ -namespace Private -{ - namespace Selector - { - _CA_PRIVATE_DEF_SEL(device, - "device"); - _CA_PRIVATE_DEF_SEL(drawableSize, - "drawableSize"); - _CA_PRIVATE_DEF_SEL(framebufferOnly, - "framebufferOnly"); - _CA_PRIVATE_DEF_SEL(layer, - "layer"); - _CA_PRIVATE_DEF_SEL(nextDrawable, - "nextDrawable"); - _CA_PRIVATE_DEF_SEL(pixelFormat, - "pixelFormat"); - _CA_PRIVATE_DEF_SEL(setDevice_, - "setDevice:"); - _CA_PRIVATE_DEF_SEL(setDrawableSize_, - "setDrawableSize:"); - _CA_PRIVATE_DEF_SEL(setFramebufferOnly_, - "setFramebufferOnly:"); - _CA_PRIVATE_DEF_SEL(setPixelFormat_, - "setPixelFormat:"); - _CA_PRIVATE_DEF_SEL(texture, - "texture"); - } // Class -} // Private -} // CA - -namespace CA -{ -class MetalDrawable : public NS::Referencing -{ -public: - class MetalLayer* layer() const; - MTL::Texture* texture() const; -}; -} - -_CA_INLINE CA::MetalLayer* CA::MetalDrawable::layer() const -{ - return Object::sendMessage(this, _CA_PRIVATE_SEL(layer)); -} - -_CA_INLINE MTL::Texture* CA::MetalDrawable::texture() const -{ - return Object::sendMessage(this, _CA_PRIVATE_SEL(texture)); -} - -#include - -namespace CA -{ - -class MetalLayer : public NS::Referencing -{ -public: - static class MetalLayer* layer(); - - MTL::Device* device() const; - void setDevice(MTL::Device* device); - - MTL::PixelFormat pixelFormat() const; - void setPixelFormat(MTL::PixelFormat pixelFormat); - - bool framebufferOnly() const; - void setFramebufferOnly(bool framebufferOnly); - - CGSize drawableSize() const; - void setDrawableSize(CGSize drawableSize); - - class MetalDrawable* nextDrawable(); -}; -} // namespace CA - -_CA_INLINE CA::MetalLayer* CA::MetalLayer::layer() -{ - return Object::sendMessage(_CA_PRIVATE_CLS(CAMetalLayer), _CA_PRIVATE_SEL(layer)); -} - -_CA_INLINE MTL::Device* CA::MetalLayer::device() const -{ - return Object::sendMessage(this, _CA_PRIVATE_SEL(device)); -} - -_CA_INLINE void CA::MetalLayer::setDevice(MTL::Device* device) -{ - return Object::sendMessage(this, _CA_PRIVATE_SEL(setDevice_), device); -} - -_CA_INLINE MTL::PixelFormat CA::MetalLayer::pixelFormat() const -{ - return Object::sendMessage(this, - _CA_PRIVATE_SEL(pixelFormat)); -} - -_CA_INLINE void CA::MetalLayer::setPixelFormat(MTL::PixelFormat pixelFormat) -{ - return Object::sendMessage(this, _CA_PRIVATE_SEL(setPixelFormat_), - pixelFormat); -} - -_CA_INLINE bool CA::MetalLayer::framebufferOnly() const -{ - return Object::sendMessage(this, _CA_PRIVATE_SEL(framebufferOnly)); -} - -_CA_INLINE void CA::MetalLayer::setFramebufferOnly(bool framebufferOnly) -{ - return Object::sendMessage(this, _CA_PRIVATE_SEL(setFramebufferOnly_), - framebufferOnly); -} - -_CA_INLINE CGSize CA::MetalLayer::drawableSize() const -{ - return Object::sendMessage(this, _CA_PRIVATE_SEL(drawableSize)); -} - -_CA_INLINE void CA::MetalLayer::setDrawableSize(CGSize drawableSize) -{ - return Object::sendMessage(this, _CA_PRIVATE_SEL(setDrawableSize_), - drawableSize); -} - -_CA_INLINE CA::MetalDrawable* CA::MetalLayer::nextDrawable() -{ - return Object::sendMessage(this, - _CA_PRIVATE_SEL(nextDrawable)); -} - -#pragma once - -#pragma once - -namespace MTL -{ -_MTL_ENUM(NS::UInteger, AttributeFormat) { - AttributeFormatInvalid = 0, - AttributeFormatUChar2 = 1, - AttributeFormatUChar3 = 2, - AttributeFormatUChar4 = 3, - AttributeFormatChar2 = 4, - AttributeFormatChar3 = 5, - AttributeFormatChar4 = 6, - AttributeFormatUChar2Normalized = 7, - AttributeFormatUChar3Normalized = 8, - AttributeFormatUChar4Normalized = 9, - AttributeFormatChar2Normalized = 10, - AttributeFormatChar3Normalized = 11, - AttributeFormatChar4Normalized = 12, - AttributeFormatUShort2 = 13, - AttributeFormatUShort3 = 14, - AttributeFormatUShort4 = 15, - AttributeFormatShort2 = 16, - AttributeFormatShort3 = 17, - AttributeFormatShort4 = 18, - AttributeFormatUShort2Normalized = 19, - AttributeFormatUShort3Normalized = 20, - AttributeFormatUShort4Normalized = 21, - AttributeFormatShort2Normalized = 22, - AttributeFormatShort3Normalized = 23, - AttributeFormatShort4Normalized = 24, - AttributeFormatHalf2 = 25, - AttributeFormatHalf3 = 26, - AttributeFormatHalf4 = 27, - AttributeFormatFloat = 28, - AttributeFormatFloat2 = 29, - AttributeFormatFloat3 = 30, - AttributeFormatFloat4 = 31, - AttributeFormatInt = 32, - AttributeFormatInt2 = 33, - AttributeFormatInt3 = 34, - AttributeFormatInt4 = 35, - AttributeFormatUInt = 36, - AttributeFormatUInt2 = 37, - AttributeFormatUInt3 = 38, - AttributeFormatUInt4 = 39, - AttributeFormatInt1010102Normalized = 40, - AttributeFormatUInt1010102Normalized = 41, - AttributeFormatUChar4Normalized_BGRA = 42, - AttributeFormatUChar = 45, - AttributeFormatChar = 46, - AttributeFormatUCharNormalized = 47, - AttributeFormatCharNormalized = 48, - AttributeFormatUShort = 49, - AttributeFormatShort = 50, - AttributeFormatUShortNormalized = 51, - AttributeFormatShortNormalized = 52, - AttributeFormatHalf = 53, -}; - -_MTL_ENUM(NS::UInteger, IndexType) { - IndexTypeUInt16 = 0, - IndexTypeUInt32 = 1, -}; - -_MTL_ENUM(NS::UInteger, StepFunction) { - StepFunctionConstant = 0, - StepFunctionPerVertex = 1, - StepFunctionPerInstance = 2, - StepFunctionPerPatch = 3, - StepFunctionPerPatchControlPoint = 4, - StepFunctionThreadPositionInGridX = 5, - StepFunctionThreadPositionInGridY = 6, - StepFunctionThreadPositionInGridXIndexed = 7, - StepFunctionThreadPositionInGridYIndexed = 8, -}; - -class BufferLayoutDescriptor : public NS::Copying -{ -public: - static class BufferLayoutDescriptor* alloc(); - - class BufferLayoutDescriptor* init(); - - NS::UInteger stride() const; - void setStride(NS::UInteger stride); - - MTL::StepFunction stepFunction() const; - void setStepFunction(MTL::StepFunction stepFunction); - - NS::UInteger stepRate() const; - void setStepRate(NS::UInteger stepRate); -}; - -class BufferLayoutDescriptorArray : public NS::Referencing -{ -public: - static class BufferLayoutDescriptorArray* alloc(); - - class BufferLayoutDescriptorArray* init(); - - class BufferLayoutDescriptor* object(NS::UInteger index); - - void setObject(const class BufferLayoutDescriptor* bufferDesc, NS::UInteger index); -}; - -class AttributeDescriptor : public NS::Copying -{ -public: - static class AttributeDescriptor* alloc(); - - class AttributeDescriptor* init(); - - MTL::AttributeFormat format() const; - void setFormat(MTL::AttributeFormat format); - - NS::UInteger offset() const; - void setOffset(NS::UInteger offset); - - NS::UInteger bufferIndex() const; - void setBufferIndex(NS::UInteger bufferIndex); -}; - -class AttributeDescriptorArray : public NS::Referencing -{ -public: - static class AttributeDescriptorArray* alloc(); - - class AttributeDescriptorArray* init(); - - class AttributeDescriptor* object(NS::UInteger index); - - void setObject(const class AttributeDescriptor* attributeDesc, NS::UInteger index); -}; - -class StageInputOutputDescriptor : public NS::Copying -{ -public: - static class StageInputOutputDescriptor* alloc(); - - class StageInputOutputDescriptor* init(); - - static class StageInputOutputDescriptor* stageInputOutputDescriptor(); - - class BufferLayoutDescriptorArray* layouts() const; - - class AttributeDescriptorArray* attributes() const; - - MTL::IndexType indexType() const; - void setIndexType(MTL::IndexType indexType); - - NS::UInteger indexBufferIndex() const; - void setIndexBufferIndex(NS::UInteger indexBufferIndex); - - void reset(); -}; - -} - -_MTL_INLINE MTL::BufferLayoutDescriptor* MTL::BufferLayoutDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLBufferLayoutDescriptor)); -} - -_MTL_INLINE MTL::BufferLayoutDescriptor* MTL::BufferLayoutDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE NS::UInteger MTL::BufferLayoutDescriptor::stride() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(stride)); -} - -_MTL_INLINE void MTL::BufferLayoutDescriptor::setStride(NS::UInteger stride) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStride_), stride); -} - -_MTL_INLINE MTL::StepFunction MTL::BufferLayoutDescriptor::stepFunction() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(stepFunction)); -} - -_MTL_INLINE void MTL::BufferLayoutDescriptor::setStepFunction(MTL::StepFunction stepFunction) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStepFunction_), stepFunction); -} - -_MTL_INLINE NS::UInteger MTL::BufferLayoutDescriptor::stepRate() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(stepRate)); -} - -_MTL_INLINE void MTL::BufferLayoutDescriptor::setStepRate(NS::UInteger stepRate) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStepRate_), stepRate); -} - -_MTL_INLINE MTL::BufferLayoutDescriptorArray* MTL::BufferLayoutDescriptorArray::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLBufferLayoutDescriptorArray)); -} - -_MTL_INLINE MTL::BufferLayoutDescriptorArray* MTL::BufferLayoutDescriptorArray::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::BufferLayoutDescriptor* MTL::BufferLayoutDescriptorArray::object(NS::UInteger index) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(objectAtIndexedSubscript_), index); -} - -_MTL_INLINE void MTL::BufferLayoutDescriptorArray::setObject(const MTL::BufferLayoutDescriptor* bufferDesc, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setObject_atIndexedSubscript_), bufferDesc, index); -} - -_MTL_INLINE MTL::AttributeDescriptor* MTL::AttributeDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLAttributeDescriptor)); -} - -_MTL_INLINE MTL::AttributeDescriptor* MTL::AttributeDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::AttributeFormat MTL::AttributeDescriptor::format() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(format)); -} - -_MTL_INLINE void MTL::AttributeDescriptor::setFormat(MTL::AttributeFormat format) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFormat_), format); -} - -_MTL_INLINE NS::UInteger MTL::AttributeDescriptor::offset() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(offset)); -} - -_MTL_INLINE void MTL::AttributeDescriptor::setOffset(NS::UInteger offset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setOffset_), offset); -} - -_MTL_INLINE NS::UInteger MTL::AttributeDescriptor::bufferIndex() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(bufferIndex)); -} - -_MTL_INLINE void MTL::AttributeDescriptor::setBufferIndex(NS::UInteger bufferIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setBufferIndex_), bufferIndex); -} - -_MTL_INLINE MTL::AttributeDescriptorArray* MTL::AttributeDescriptorArray::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLAttributeDescriptorArray)); -} - -_MTL_INLINE MTL::AttributeDescriptorArray* MTL::AttributeDescriptorArray::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::AttributeDescriptor* MTL::AttributeDescriptorArray::object(NS::UInteger index) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(objectAtIndexedSubscript_), index); -} - -_MTL_INLINE void MTL::AttributeDescriptorArray::setObject(const MTL::AttributeDescriptor* attributeDesc, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setObject_atIndexedSubscript_), attributeDesc, index); -} - -_MTL_INLINE MTL::StageInputOutputDescriptor* MTL::StageInputOutputDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLStageInputOutputDescriptor)); -} - -_MTL_INLINE MTL::StageInputOutputDescriptor* MTL::StageInputOutputDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::StageInputOutputDescriptor* MTL::StageInputOutputDescriptor::stageInputOutputDescriptor() -{ - return Object::sendMessage(_MTL_PRIVATE_CLS(MTLStageInputOutputDescriptor), _MTL_PRIVATE_SEL(stageInputOutputDescriptor)); -} - -_MTL_INLINE MTL::BufferLayoutDescriptorArray* MTL::StageInputOutputDescriptor::layouts() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(layouts)); -} - -_MTL_INLINE MTL::AttributeDescriptorArray* MTL::StageInputOutputDescriptor::attributes() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(attributes)); -} - -_MTL_INLINE MTL::IndexType MTL::StageInputOutputDescriptor::indexType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(indexType)); -} - -_MTL_INLINE void MTL::StageInputOutputDescriptor::setIndexType(MTL::IndexType indexType) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setIndexType_), indexType); -} - -_MTL_INLINE NS::UInteger MTL::StageInputOutputDescriptor::indexBufferIndex() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(indexBufferIndex)); -} - -_MTL_INLINE void MTL::StageInputOutputDescriptor::setIndexBufferIndex(NS::UInteger indexBufferIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setIndexBufferIndex_), indexBufferIndex); -} - -_MTL_INLINE void MTL::StageInputOutputDescriptor::reset() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(reset)); -} - -namespace MTL -{ -struct PackedFloat3 -{ - PackedFloat3(); - PackedFloat3(float x, float y, float z); - - float& operator[](int idx); - float operator[](int idx) const; - - union - { - struct - { - float x; - float y; - float z; - }; - - float elements[3]; - }; -} _MTL_PACKED; - -struct PackedFloat4x3 -{ - PackedFloat4x3(); - PackedFloat4x3(const PackedFloat3& col0, const PackedFloat3& col1, const PackedFloat3& col2, const PackedFloat3& col3); - - PackedFloat3& operator[](int idx); - const PackedFloat3& operator[](int idx) const; - - PackedFloat3 columns[4]; -} _MTL_PACKED; - -struct AxisAlignedBoundingBox -{ - AxisAlignedBoundingBox(); - AxisAlignedBoundingBox(PackedFloat3 p); - AxisAlignedBoundingBox(PackedFloat3 min, PackedFloat3 max); - - PackedFloat3 min; - PackedFloat3 max; -} _MTL_PACKED; -} - -_MTL_INLINE MTL::PackedFloat3::PackedFloat3() - : x(0.0f) - , y(0.0f) - , z(0.0f) -{ -} - -_MTL_INLINE MTL::PackedFloat3::PackedFloat3(float _x, float _y, float _z) - : x(_x) - , y(_y) - , z(_z) -{ -} - -_MTL_INLINE float& MTL::PackedFloat3::operator[](int idx) -{ - return elements[idx]; -} - -_MTL_INLINE float MTL::PackedFloat3::operator[](int idx) const -{ - return elements[idx]; -} - -_MTL_INLINE MTL::PackedFloat4x3::PackedFloat4x3() -{ - columns[0] = PackedFloat3(0.0f, 0.0f, 0.0f); - columns[1] = PackedFloat3(0.0f, 0.0f, 0.0f); - columns[2] = PackedFloat3(0.0f, 0.0f, 0.0f); - columns[3] = PackedFloat3(0.0f, 0.0f, 0.0f); -} - -_MTL_INLINE MTL::PackedFloat4x3::PackedFloat4x3(const PackedFloat3& col0, const PackedFloat3& col1, const PackedFloat3& col2, const PackedFloat3& col3) -{ - columns[0] = col0; - columns[1] = col1; - columns[2] = col2; - columns[3] = col3; -} - -_MTL_INLINE MTL::PackedFloat3& MTL::PackedFloat4x3::operator[](int idx) -{ - return columns[idx]; -} - -_MTL_INLINE const MTL::PackedFloat3& MTL::PackedFloat4x3::operator[](int idx) const -{ - return columns[idx]; -} - -_MTL_INLINE MTL::AxisAlignedBoundingBox::AxisAlignedBoundingBox() - : min(INFINITY, INFINITY, INFINITY) - , max(-INFINITY, -INFINITY, -INFINITY) -{ -} - -_MTL_INLINE MTL::AxisAlignedBoundingBox::AxisAlignedBoundingBox(PackedFloat3 p) - : min(p) - , max(p) -{ -} - -_MTL_INLINE MTL::AxisAlignedBoundingBox::AxisAlignedBoundingBox(PackedFloat3 _min, PackedFloat3 _max) - : min(_min) - , max(_max) -{ -} - -namespace MTL -{ -_MTL_OPTIONS(NS::UInteger, AccelerationStructureUsage) { - AccelerationStructureUsageNone = 0, - AccelerationStructureUsageRefit = 1, - AccelerationStructureUsagePreferFastBuild = 2, - AccelerationStructureUsageExtendedLimits = 4, -}; - -_MTL_OPTIONS(uint32_t, AccelerationStructureInstanceOptions) { - AccelerationStructureInstanceOptionNone = 0, - AccelerationStructureInstanceOptionDisableTriangleCulling = 1, - AccelerationStructureInstanceOptionTriangleFrontFacingWindingCounterClockwise = 2, - AccelerationStructureInstanceOptionOpaque = 4, - AccelerationStructureInstanceOptionNonOpaque = 8, -}; - -class AccelerationStructureDescriptor : public NS::Copying -{ -public: - static class AccelerationStructureDescriptor* alloc(); - - class AccelerationStructureDescriptor* init(); - - MTL::AccelerationStructureUsage usage() const; - void setUsage(MTL::AccelerationStructureUsage usage); -}; - -class AccelerationStructureGeometryDescriptor : public NS::Copying -{ -public: - static class AccelerationStructureGeometryDescriptor* alloc(); - - class AccelerationStructureGeometryDescriptor* init(); - - NS::UInteger intersectionFunctionTableOffset() const; - void setIntersectionFunctionTableOffset(NS::UInteger intersectionFunctionTableOffset); - - bool opaque() const; - void setOpaque(bool opaque); - - bool allowDuplicateIntersectionFunctionInvocation() const; - void setAllowDuplicateIntersectionFunctionInvocation(bool allowDuplicateIntersectionFunctionInvocation); - - NS::String* label() const; - void setLabel(const NS::String* label); - - class Buffer* primitiveDataBuffer() const; - void setPrimitiveDataBuffer(const class Buffer* primitiveDataBuffer); - - NS::UInteger primitiveDataBufferOffset() const; - void setPrimitiveDataBufferOffset(NS::UInteger primitiveDataBufferOffset); - - NS::UInteger primitiveDataStride() const; - void setPrimitiveDataStride(NS::UInteger primitiveDataStride); - - NS::UInteger primitiveDataElementSize() const; - void setPrimitiveDataElementSize(NS::UInteger primitiveDataElementSize); -}; - -_MTL_ENUM(uint32_t, MotionBorderMode) { - MotionBorderModeClamp = 0, - MotionBorderModeVanish = 1, -}; - -class PrimitiveAccelerationStructureDescriptor : public NS::Copying -{ -public: - static class PrimitiveAccelerationStructureDescriptor* alloc(); - - class PrimitiveAccelerationStructureDescriptor* init(); - - NS::Array* geometryDescriptors() const; - void setGeometryDescriptors(const NS::Array* geometryDescriptors); - - MTL::MotionBorderMode motionStartBorderMode() const; - void setMotionStartBorderMode(MTL::MotionBorderMode motionStartBorderMode); - - MTL::MotionBorderMode motionEndBorderMode() const; - void setMotionEndBorderMode(MTL::MotionBorderMode motionEndBorderMode); - - float motionStartTime() const; - void setMotionStartTime(float motionStartTime); - - float motionEndTime() const; - void setMotionEndTime(float motionEndTime); - - NS::UInteger motionKeyframeCount() const; - void setMotionKeyframeCount(NS::UInteger motionKeyframeCount); - - static MTL::PrimitiveAccelerationStructureDescriptor* descriptor(); -}; - -class AccelerationStructureTriangleGeometryDescriptor : public NS::Copying -{ -public: - static class AccelerationStructureTriangleGeometryDescriptor* alloc(); - - class AccelerationStructureTriangleGeometryDescriptor* init(); - - class Buffer* vertexBuffer() const; - void setVertexBuffer(const class Buffer* vertexBuffer); - - NS::UInteger vertexBufferOffset() const; - void setVertexBufferOffset(NS::UInteger vertexBufferOffset); - - MTL::AttributeFormat vertexFormat() const; - void setVertexFormat(MTL::AttributeFormat vertexFormat); - - NS::UInteger vertexStride() const; - void setVertexStride(NS::UInteger vertexStride); - - class Buffer* indexBuffer() const; - void setIndexBuffer(const class Buffer* indexBuffer); - - NS::UInteger indexBufferOffset() const; - void setIndexBufferOffset(NS::UInteger indexBufferOffset); - - MTL::IndexType indexType() const; - void setIndexType(MTL::IndexType indexType); - - NS::UInteger triangleCount() const; - void setTriangleCount(NS::UInteger triangleCount); - - class Buffer* transformationMatrixBuffer() const; - void setTransformationMatrixBuffer(const class Buffer* transformationMatrixBuffer); - - NS::UInteger transformationMatrixBufferOffset() const; - void setTransformationMatrixBufferOffset(NS::UInteger transformationMatrixBufferOffset); - - static MTL::AccelerationStructureTriangleGeometryDescriptor* descriptor(); -}; - -class AccelerationStructureBoundingBoxGeometryDescriptor : public NS::Copying -{ -public: - static class AccelerationStructureBoundingBoxGeometryDescriptor* alloc(); - - class AccelerationStructureBoundingBoxGeometryDescriptor* init(); - - class Buffer* boundingBoxBuffer() const; - void setBoundingBoxBuffer(const class Buffer* boundingBoxBuffer); - - NS::UInteger boundingBoxBufferOffset() const; - void setBoundingBoxBufferOffset(NS::UInteger boundingBoxBufferOffset); - - NS::UInteger boundingBoxStride() const; - void setBoundingBoxStride(NS::UInteger boundingBoxStride); - - NS::UInteger boundingBoxCount() const; - void setBoundingBoxCount(NS::UInteger boundingBoxCount); - - static MTL::AccelerationStructureBoundingBoxGeometryDescriptor* descriptor(); -}; - -class MotionKeyframeData : public NS::Referencing -{ -public: - static class MotionKeyframeData* alloc(); - - class MotionKeyframeData* init(); - - class Buffer* buffer() const; - void setBuffer(const class Buffer* buffer); - - NS::UInteger offset() const; - void setOffset(NS::UInteger offset); - - static MTL::MotionKeyframeData* data(); -}; - -class AccelerationStructureMotionTriangleGeometryDescriptor : public NS::Copying -{ -public: - static class AccelerationStructureMotionTriangleGeometryDescriptor* alloc(); - - class AccelerationStructureMotionTriangleGeometryDescriptor* init(); - - NS::Array* vertexBuffers() const; - void setVertexBuffers(const NS::Array* vertexBuffers); - - MTL::AttributeFormat vertexFormat() const; - void setVertexFormat(MTL::AttributeFormat vertexFormat); - - NS::UInteger vertexStride() const; - void setVertexStride(NS::UInteger vertexStride); - - class Buffer* indexBuffer() const; - void setIndexBuffer(const class Buffer* indexBuffer); - - NS::UInteger indexBufferOffset() const; - void setIndexBufferOffset(NS::UInteger indexBufferOffset); - - MTL::IndexType indexType() const; - void setIndexType(MTL::IndexType indexType); - - NS::UInteger triangleCount() const; - void setTriangleCount(NS::UInteger triangleCount); - - class Buffer* transformationMatrixBuffer() const; - void setTransformationMatrixBuffer(const class Buffer* transformationMatrixBuffer); - - NS::UInteger transformationMatrixBufferOffset() const; - void setTransformationMatrixBufferOffset(NS::UInteger transformationMatrixBufferOffset); - - static MTL::AccelerationStructureMotionTriangleGeometryDescriptor* descriptor(); -}; - -class AccelerationStructureMotionBoundingBoxGeometryDescriptor : public NS::Copying -{ -public: - static class AccelerationStructureMotionBoundingBoxGeometryDescriptor* alloc(); - - class AccelerationStructureMotionBoundingBoxGeometryDescriptor* init(); - - NS::Array* boundingBoxBuffers() const; - void setBoundingBoxBuffers(const NS::Array* boundingBoxBuffers); - - NS::UInteger boundingBoxStride() const; - void setBoundingBoxStride(NS::UInteger boundingBoxStride); - - NS::UInteger boundingBoxCount() const; - void setBoundingBoxCount(NS::UInteger boundingBoxCount); - - static MTL::AccelerationStructureMotionBoundingBoxGeometryDescriptor* descriptor(); -}; - -struct AccelerationStructureInstanceDescriptor -{ - MTL::PackedFloat4x3 transformationMatrix; - MTL::AccelerationStructureInstanceOptions options; - uint32_t mask; - uint32_t intersectionFunctionTableOffset; - uint32_t accelerationStructureIndex; -} _MTL_PACKED; - -struct AccelerationStructureUserIDInstanceDescriptor -{ - MTL::PackedFloat4x3 transformationMatrix; - MTL::AccelerationStructureInstanceOptions options; - uint32_t mask; - uint32_t intersectionFunctionTableOffset; - uint32_t accelerationStructureIndex; - uint32_t userID; -} _MTL_PACKED; - -_MTL_ENUM(NS::UInteger, AccelerationStructureInstanceDescriptorType) { - AccelerationStructureInstanceDescriptorTypeDefault = 0, - AccelerationStructureInstanceDescriptorTypeUserID = 1, - AccelerationStructureInstanceDescriptorTypeMotion = 2, -}; - -struct AccelerationStructureMotionInstanceDescriptor -{ - MTL::AccelerationStructureInstanceOptions options; - uint32_t mask; - uint32_t intersectionFunctionTableOffset; - uint32_t accelerationStructureIndex; - uint32_t userID; - uint32_t motionTransformsStartIndex; - uint32_t motionTransformsCount; - MTL::MotionBorderMode motionStartBorderMode; - MTL::MotionBorderMode motionEndBorderMode; - float motionStartTime; - float motionEndTime; -} _MTL_PACKED; - -class InstanceAccelerationStructureDescriptor : public NS::Copying -{ -public: - static class InstanceAccelerationStructureDescriptor* alloc(); - - class InstanceAccelerationStructureDescriptor* init(); - - class Buffer* instanceDescriptorBuffer() const; - void setInstanceDescriptorBuffer(const class Buffer* instanceDescriptorBuffer); - - NS::UInteger instanceDescriptorBufferOffset() const; - void setInstanceDescriptorBufferOffset(NS::UInteger instanceDescriptorBufferOffset); - - NS::UInteger instanceDescriptorStride() const; - void setInstanceDescriptorStride(NS::UInteger instanceDescriptorStride); - - NS::UInteger instanceCount() const; - void setInstanceCount(NS::UInteger instanceCount); - - NS::Array* instancedAccelerationStructures() const; - void setInstancedAccelerationStructures(const NS::Array* instancedAccelerationStructures); - - MTL::AccelerationStructureInstanceDescriptorType instanceDescriptorType() const; - void setInstanceDescriptorType(MTL::AccelerationStructureInstanceDescriptorType instanceDescriptorType); - - class Buffer* motionTransformBuffer() const; - void setMotionTransformBuffer(const class Buffer* motionTransformBuffer); - - NS::UInteger motionTransformBufferOffset() const; - void setMotionTransformBufferOffset(NS::UInteger motionTransformBufferOffset); - - NS::UInteger motionTransformCount() const; - void setMotionTransformCount(NS::UInteger motionTransformCount); - - static MTL::InstanceAccelerationStructureDescriptor* descriptor(); -}; - -class AccelerationStructure : public NS::Referencing -{ -public: - NS::UInteger size() const; - - MTL::ResourceID gpuResourceID() const; -}; - -} - -_MTL_INLINE MTL::AccelerationStructureDescriptor* MTL::AccelerationStructureDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLAccelerationStructureDescriptor)); -} - -_MTL_INLINE MTL::AccelerationStructureDescriptor* MTL::AccelerationStructureDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::AccelerationStructureUsage MTL::AccelerationStructureDescriptor::usage() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(usage)); -} - -_MTL_INLINE void MTL::AccelerationStructureDescriptor::setUsage(MTL::AccelerationStructureUsage usage) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setUsage_), usage); -} - -_MTL_INLINE MTL::AccelerationStructureGeometryDescriptor* MTL::AccelerationStructureGeometryDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLAccelerationStructureGeometryDescriptor)); -} - -_MTL_INLINE MTL::AccelerationStructureGeometryDescriptor* MTL::AccelerationStructureGeometryDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE NS::UInteger MTL::AccelerationStructureGeometryDescriptor::intersectionFunctionTableOffset() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(intersectionFunctionTableOffset)); -} - -_MTL_INLINE void MTL::AccelerationStructureGeometryDescriptor::setIntersectionFunctionTableOffset(NS::UInteger intersectionFunctionTableOffset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setIntersectionFunctionTableOffset_), intersectionFunctionTableOffset); -} - -_MTL_INLINE bool MTL::AccelerationStructureGeometryDescriptor::opaque() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(opaque)); -} - -_MTL_INLINE void MTL::AccelerationStructureGeometryDescriptor::setOpaque(bool opaque) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setOpaque_), opaque); -} - -_MTL_INLINE bool MTL::AccelerationStructureGeometryDescriptor::allowDuplicateIntersectionFunctionInvocation() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(allowDuplicateIntersectionFunctionInvocation)); -} - -_MTL_INLINE void MTL::AccelerationStructureGeometryDescriptor::setAllowDuplicateIntersectionFunctionInvocation(bool allowDuplicateIntersectionFunctionInvocation) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setAllowDuplicateIntersectionFunctionInvocation_), allowDuplicateIntersectionFunctionInvocation); -} - -_MTL_INLINE NS::String* MTL::AccelerationStructureGeometryDescriptor::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE void MTL::AccelerationStructureGeometryDescriptor::setLabel(const NS::String* label) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLabel_), label); -} - -_MTL_INLINE MTL::Buffer* MTL::AccelerationStructureGeometryDescriptor::primitiveDataBuffer() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(primitiveDataBuffer)); -} - -_MTL_INLINE void MTL::AccelerationStructureGeometryDescriptor::setPrimitiveDataBuffer(const MTL::Buffer* primitiveDataBuffer) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setPrimitiveDataBuffer_), primitiveDataBuffer); -} - -_MTL_INLINE NS::UInteger MTL::AccelerationStructureGeometryDescriptor::primitiveDataBufferOffset() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(primitiveDataBufferOffset)); -} - -_MTL_INLINE void MTL::AccelerationStructureGeometryDescriptor::setPrimitiveDataBufferOffset(NS::UInteger primitiveDataBufferOffset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setPrimitiveDataBufferOffset_), primitiveDataBufferOffset); -} - -_MTL_INLINE NS::UInteger MTL::AccelerationStructureGeometryDescriptor::primitiveDataStride() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(primitiveDataStride)); -} - -_MTL_INLINE void MTL::AccelerationStructureGeometryDescriptor::setPrimitiveDataStride(NS::UInteger primitiveDataStride) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setPrimitiveDataStride_), primitiveDataStride); -} - -_MTL_INLINE NS::UInteger MTL::AccelerationStructureGeometryDescriptor::primitiveDataElementSize() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(primitiveDataElementSize)); -} - -_MTL_INLINE void MTL::AccelerationStructureGeometryDescriptor::setPrimitiveDataElementSize(NS::UInteger primitiveDataElementSize) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setPrimitiveDataElementSize_), primitiveDataElementSize); -} - -_MTL_INLINE MTL::PrimitiveAccelerationStructureDescriptor* MTL::PrimitiveAccelerationStructureDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLPrimitiveAccelerationStructureDescriptor)); -} - -_MTL_INLINE MTL::PrimitiveAccelerationStructureDescriptor* MTL::PrimitiveAccelerationStructureDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE NS::Array* MTL::PrimitiveAccelerationStructureDescriptor::geometryDescriptors() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(geometryDescriptors)); -} - -_MTL_INLINE void MTL::PrimitiveAccelerationStructureDescriptor::setGeometryDescriptors(const NS::Array* geometryDescriptors) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setGeometryDescriptors_), geometryDescriptors); -} - -_MTL_INLINE MTL::MotionBorderMode MTL::PrimitiveAccelerationStructureDescriptor::motionStartBorderMode() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(motionStartBorderMode)); -} - -_MTL_INLINE void MTL::PrimitiveAccelerationStructureDescriptor::setMotionStartBorderMode(MTL::MotionBorderMode motionStartBorderMode) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMotionStartBorderMode_), motionStartBorderMode); -} - -_MTL_INLINE MTL::MotionBorderMode MTL::PrimitiveAccelerationStructureDescriptor::motionEndBorderMode() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(motionEndBorderMode)); -} - -_MTL_INLINE void MTL::PrimitiveAccelerationStructureDescriptor::setMotionEndBorderMode(MTL::MotionBorderMode motionEndBorderMode) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMotionEndBorderMode_), motionEndBorderMode); -} - -_MTL_INLINE float MTL::PrimitiveAccelerationStructureDescriptor::motionStartTime() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(motionStartTime)); -} - -_MTL_INLINE void MTL::PrimitiveAccelerationStructureDescriptor::setMotionStartTime(float motionStartTime) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMotionStartTime_), motionStartTime); -} - -_MTL_INLINE float MTL::PrimitiveAccelerationStructureDescriptor::motionEndTime() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(motionEndTime)); -} - -_MTL_INLINE void MTL::PrimitiveAccelerationStructureDescriptor::setMotionEndTime(float motionEndTime) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMotionEndTime_), motionEndTime); -} - -_MTL_INLINE NS::UInteger MTL::PrimitiveAccelerationStructureDescriptor::motionKeyframeCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(motionKeyframeCount)); -} - -_MTL_INLINE void MTL::PrimitiveAccelerationStructureDescriptor::setMotionKeyframeCount(NS::UInteger motionKeyframeCount) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMotionKeyframeCount_), motionKeyframeCount); -} - -_MTL_INLINE MTL::PrimitiveAccelerationStructureDescriptor* MTL::PrimitiveAccelerationStructureDescriptor::descriptor() -{ - return Object::sendMessage(_MTL_PRIVATE_CLS(MTLPrimitiveAccelerationStructureDescriptor), _MTL_PRIVATE_SEL(descriptor)); -} - -_MTL_INLINE MTL::AccelerationStructureTriangleGeometryDescriptor* MTL::AccelerationStructureTriangleGeometryDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLAccelerationStructureTriangleGeometryDescriptor)); -} - -_MTL_INLINE MTL::AccelerationStructureTriangleGeometryDescriptor* MTL::AccelerationStructureTriangleGeometryDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::Buffer* MTL::AccelerationStructureTriangleGeometryDescriptor::vertexBuffer() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(vertexBuffer)); -} - -_MTL_INLINE void MTL::AccelerationStructureTriangleGeometryDescriptor::setVertexBuffer(const MTL::Buffer* vertexBuffer) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVertexBuffer_), vertexBuffer); -} - -_MTL_INLINE NS::UInteger MTL::AccelerationStructureTriangleGeometryDescriptor::vertexBufferOffset() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(vertexBufferOffset)); -} - -_MTL_INLINE void MTL::AccelerationStructureTriangleGeometryDescriptor::setVertexBufferOffset(NS::UInteger vertexBufferOffset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVertexBufferOffset_), vertexBufferOffset); -} - -_MTL_INLINE MTL::AttributeFormat MTL::AccelerationStructureTriangleGeometryDescriptor::vertexFormat() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(vertexFormat)); -} - -_MTL_INLINE void MTL::AccelerationStructureTriangleGeometryDescriptor::setVertexFormat(MTL::AttributeFormat vertexFormat) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVertexFormat_), vertexFormat); -} - -_MTL_INLINE NS::UInteger MTL::AccelerationStructureTriangleGeometryDescriptor::vertexStride() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(vertexStride)); -} - -_MTL_INLINE void MTL::AccelerationStructureTriangleGeometryDescriptor::setVertexStride(NS::UInteger vertexStride) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVertexStride_), vertexStride); -} - -_MTL_INLINE MTL::Buffer* MTL::AccelerationStructureTriangleGeometryDescriptor::indexBuffer() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(indexBuffer)); -} - -_MTL_INLINE void MTL::AccelerationStructureTriangleGeometryDescriptor::setIndexBuffer(const MTL::Buffer* indexBuffer) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setIndexBuffer_), indexBuffer); -} - -_MTL_INLINE NS::UInteger MTL::AccelerationStructureTriangleGeometryDescriptor::indexBufferOffset() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(indexBufferOffset)); -} - -_MTL_INLINE void MTL::AccelerationStructureTriangleGeometryDescriptor::setIndexBufferOffset(NS::UInteger indexBufferOffset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setIndexBufferOffset_), indexBufferOffset); -} - -_MTL_INLINE MTL::IndexType MTL::AccelerationStructureTriangleGeometryDescriptor::indexType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(indexType)); -} - -_MTL_INLINE void MTL::AccelerationStructureTriangleGeometryDescriptor::setIndexType(MTL::IndexType indexType) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setIndexType_), indexType); -} - -_MTL_INLINE NS::UInteger MTL::AccelerationStructureTriangleGeometryDescriptor::triangleCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(triangleCount)); -} - -_MTL_INLINE void MTL::AccelerationStructureTriangleGeometryDescriptor::setTriangleCount(NS::UInteger triangleCount) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTriangleCount_), triangleCount); -} - -_MTL_INLINE MTL::Buffer* MTL::AccelerationStructureTriangleGeometryDescriptor::transformationMatrixBuffer() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(transformationMatrixBuffer)); -} - -_MTL_INLINE void MTL::AccelerationStructureTriangleGeometryDescriptor::setTransformationMatrixBuffer(const MTL::Buffer* transformationMatrixBuffer) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTransformationMatrixBuffer_), transformationMatrixBuffer); -} - -_MTL_INLINE NS::UInteger MTL::AccelerationStructureTriangleGeometryDescriptor::transformationMatrixBufferOffset() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(transformationMatrixBufferOffset)); -} - -_MTL_INLINE void MTL::AccelerationStructureTriangleGeometryDescriptor::setTransformationMatrixBufferOffset(NS::UInteger transformationMatrixBufferOffset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTransformationMatrixBufferOffset_), transformationMatrixBufferOffset); -} - -_MTL_INLINE MTL::AccelerationStructureTriangleGeometryDescriptor* MTL::AccelerationStructureTriangleGeometryDescriptor::descriptor() -{ - return Object::sendMessage(_MTL_PRIVATE_CLS(MTLAccelerationStructureTriangleGeometryDescriptor), _MTL_PRIVATE_SEL(descriptor)); -} - -_MTL_INLINE MTL::AccelerationStructureBoundingBoxGeometryDescriptor* MTL::AccelerationStructureBoundingBoxGeometryDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLAccelerationStructureBoundingBoxGeometryDescriptor)); -} - -_MTL_INLINE MTL::AccelerationStructureBoundingBoxGeometryDescriptor* MTL::AccelerationStructureBoundingBoxGeometryDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::Buffer* MTL::AccelerationStructureBoundingBoxGeometryDescriptor::boundingBoxBuffer() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(boundingBoxBuffer)); -} - -_MTL_INLINE void MTL::AccelerationStructureBoundingBoxGeometryDescriptor::setBoundingBoxBuffer(const MTL::Buffer* boundingBoxBuffer) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setBoundingBoxBuffer_), boundingBoxBuffer); -} - -_MTL_INLINE NS::UInteger MTL::AccelerationStructureBoundingBoxGeometryDescriptor::boundingBoxBufferOffset() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(boundingBoxBufferOffset)); -} - -_MTL_INLINE void MTL::AccelerationStructureBoundingBoxGeometryDescriptor::setBoundingBoxBufferOffset(NS::UInteger boundingBoxBufferOffset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setBoundingBoxBufferOffset_), boundingBoxBufferOffset); -} - -_MTL_INLINE NS::UInteger MTL::AccelerationStructureBoundingBoxGeometryDescriptor::boundingBoxStride() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(boundingBoxStride)); -} - -_MTL_INLINE void MTL::AccelerationStructureBoundingBoxGeometryDescriptor::setBoundingBoxStride(NS::UInteger boundingBoxStride) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setBoundingBoxStride_), boundingBoxStride); -} - -_MTL_INLINE NS::UInteger MTL::AccelerationStructureBoundingBoxGeometryDescriptor::boundingBoxCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(boundingBoxCount)); -} - -_MTL_INLINE void MTL::AccelerationStructureBoundingBoxGeometryDescriptor::setBoundingBoxCount(NS::UInteger boundingBoxCount) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setBoundingBoxCount_), boundingBoxCount); -} - -_MTL_INLINE MTL::AccelerationStructureBoundingBoxGeometryDescriptor* MTL::AccelerationStructureBoundingBoxGeometryDescriptor::descriptor() -{ - return Object::sendMessage(_MTL_PRIVATE_CLS(MTLAccelerationStructureBoundingBoxGeometryDescriptor), _MTL_PRIVATE_SEL(descriptor)); -} - -_MTL_INLINE MTL::MotionKeyframeData* MTL::MotionKeyframeData::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLMotionKeyframeData)); -} - -_MTL_INLINE MTL::MotionKeyframeData* MTL::MotionKeyframeData::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::Buffer* MTL::MotionKeyframeData::buffer() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(buffer)); -} - -_MTL_INLINE void MTL::MotionKeyframeData::setBuffer(const MTL::Buffer* buffer) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setBuffer_), buffer); -} - -_MTL_INLINE NS::UInteger MTL::MotionKeyframeData::offset() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(offset)); -} - -_MTL_INLINE void MTL::MotionKeyframeData::setOffset(NS::UInteger offset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setOffset_), offset); -} - -_MTL_INLINE MTL::MotionKeyframeData* MTL::MotionKeyframeData::data() -{ - return Object::sendMessage(_MTL_PRIVATE_CLS(MTLMotionKeyframeData), _MTL_PRIVATE_SEL(data)); -} - -_MTL_INLINE MTL::AccelerationStructureMotionTriangleGeometryDescriptor* MTL::AccelerationStructureMotionTriangleGeometryDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLAccelerationStructureMotionTriangleGeometryDescriptor)); -} - -_MTL_INLINE MTL::AccelerationStructureMotionTriangleGeometryDescriptor* MTL::AccelerationStructureMotionTriangleGeometryDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE NS::Array* MTL::AccelerationStructureMotionTriangleGeometryDescriptor::vertexBuffers() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(vertexBuffers)); -} - -_MTL_INLINE void MTL::AccelerationStructureMotionTriangleGeometryDescriptor::setVertexBuffers(const NS::Array* vertexBuffers) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVertexBuffers_), vertexBuffers); -} - -_MTL_INLINE MTL::AttributeFormat MTL::AccelerationStructureMotionTriangleGeometryDescriptor::vertexFormat() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(vertexFormat)); -} - -_MTL_INLINE void MTL::AccelerationStructureMotionTriangleGeometryDescriptor::setVertexFormat(MTL::AttributeFormat vertexFormat) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVertexFormat_), vertexFormat); -} - -_MTL_INLINE NS::UInteger MTL::AccelerationStructureMotionTriangleGeometryDescriptor::vertexStride() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(vertexStride)); -} - -_MTL_INLINE void MTL::AccelerationStructureMotionTriangleGeometryDescriptor::setVertexStride(NS::UInteger vertexStride) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVertexStride_), vertexStride); -} - -_MTL_INLINE MTL::Buffer* MTL::AccelerationStructureMotionTriangleGeometryDescriptor::indexBuffer() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(indexBuffer)); -} - -_MTL_INLINE void MTL::AccelerationStructureMotionTriangleGeometryDescriptor::setIndexBuffer(const MTL::Buffer* indexBuffer) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setIndexBuffer_), indexBuffer); -} - -_MTL_INLINE NS::UInteger MTL::AccelerationStructureMotionTriangleGeometryDescriptor::indexBufferOffset() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(indexBufferOffset)); -} - -_MTL_INLINE void MTL::AccelerationStructureMotionTriangleGeometryDescriptor::setIndexBufferOffset(NS::UInteger indexBufferOffset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setIndexBufferOffset_), indexBufferOffset); -} - -_MTL_INLINE MTL::IndexType MTL::AccelerationStructureMotionTriangleGeometryDescriptor::indexType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(indexType)); -} - -_MTL_INLINE void MTL::AccelerationStructureMotionTriangleGeometryDescriptor::setIndexType(MTL::IndexType indexType) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setIndexType_), indexType); -} - -_MTL_INLINE NS::UInteger MTL::AccelerationStructureMotionTriangleGeometryDescriptor::triangleCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(triangleCount)); -} - -_MTL_INLINE void MTL::AccelerationStructureMotionTriangleGeometryDescriptor::setTriangleCount(NS::UInteger triangleCount) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTriangleCount_), triangleCount); -} - -_MTL_INLINE MTL::Buffer* MTL::AccelerationStructureMotionTriangleGeometryDescriptor::transformationMatrixBuffer() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(transformationMatrixBuffer)); -} - -_MTL_INLINE void MTL::AccelerationStructureMotionTriangleGeometryDescriptor::setTransformationMatrixBuffer(const MTL::Buffer* transformationMatrixBuffer) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTransformationMatrixBuffer_), transformationMatrixBuffer); -} - -_MTL_INLINE NS::UInteger MTL::AccelerationStructureMotionTriangleGeometryDescriptor::transformationMatrixBufferOffset() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(transformationMatrixBufferOffset)); -} - -_MTL_INLINE void MTL::AccelerationStructureMotionTriangleGeometryDescriptor::setTransformationMatrixBufferOffset(NS::UInteger transformationMatrixBufferOffset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTransformationMatrixBufferOffset_), transformationMatrixBufferOffset); -} - -_MTL_INLINE MTL::AccelerationStructureMotionTriangleGeometryDescriptor* MTL::AccelerationStructureMotionTriangleGeometryDescriptor::descriptor() -{ - return Object::sendMessage(_MTL_PRIVATE_CLS(MTLAccelerationStructureMotionTriangleGeometryDescriptor), _MTL_PRIVATE_SEL(descriptor)); -} - -_MTL_INLINE MTL::AccelerationStructureMotionBoundingBoxGeometryDescriptor* MTL::AccelerationStructureMotionBoundingBoxGeometryDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLAccelerationStructureMotionBoundingBoxGeometryDescriptor)); -} - -_MTL_INLINE MTL::AccelerationStructureMotionBoundingBoxGeometryDescriptor* MTL::AccelerationStructureMotionBoundingBoxGeometryDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE NS::Array* MTL::AccelerationStructureMotionBoundingBoxGeometryDescriptor::boundingBoxBuffers() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(boundingBoxBuffers)); -} - -_MTL_INLINE void MTL::AccelerationStructureMotionBoundingBoxGeometryDescriptor::setBoundingBoxBuffers(const NS::Array* boundingBoxBuffers) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setBoundingBoxBuffers_), boundingBoxBuffers); -} - -_MTL_INLINE NS::UInteger MTL::AccelerationStructureMotionBoundingBoxGeometryDescriptor::boundingBoxStride() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(boundingBoxStride)); -} - -_MTL_INLINE void MTL::AccelerationStructureMotionBoundingBoxGeometryDescriptor::setBoundingBoxStride(NS::UInteger boundingBoxStride) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setBoundingBoxStride_), boundingBoxStride); -} - -_MTL_INLINE NS::UInteger MTL::AccelerationStructureMotionBoundingBoxGeometryDescriptor::boundingBoxCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(boundingBoxCount)); -} - -_MTL_INLINE void MTL::AccelerationStructureMotionBoundingBoxGeometryDescriptor::setBoundingBoxCount(NS::UInteger boundingBoxCount) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setBoundingBoxCount_), boundingBoxCount); -} - -_MTL_INLINE MTL::AccelerationStructureMotionBoundingBoxGeometryDescriptor* MTL::AccelerationStructureMotionBoundingBoxGeometryDescriptor::descriptor() -{ - return Object::sendMessage(_MTL_PRIVATE_CLS(MTLAccelerationStructureMotionBoundingBoxGeometryDescriptor), _MTL_PRIVATE_SEL(descriptor)); -} - -_MTL_INLINE MTL::InstanceAccelerationStructureDescriptor* MTL::InstanceAccelerationStructureDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLInstanceAccelerationStructureDescriptor)); -} - -_MTL_INLINE MTL::InstanceAccelerationStructureDescriptor* MTL::InstanceAccelerationStructureDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::Buffer* MTL::InstanceAccelerationStructureDescriptor::instanceDescriptorBuffer() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(instanceDescriptorBuffer)); -} - -_MTL_INLINE void MTL::InstanceAccelerationStructureDescriptor::setInstanceDescriptorBuffer(const MTL::Buffer* instanceDescriptorBuffer) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setInstanceDescriptorBuffer_), instanceDescriptorBuffer); -} - -_MTL_INLINE NS::UInteger MTL::InstanceAccelerationStructureDescriptor::instanceDescriptorBufferOffset() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(instanceDescriptorBufferOffset)); -} - -_MTL_INLINE void MTL::InstanceAccelerationStructureDescriptor::setInstanceDescriptorBufferOffset(NS::UInteger instanceDescriptorBufferOffset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setInstanceDescriptorBufferOffset_), instanceDescriptorBufferOffset); -} - -_MTL_INLINE NS::UInteger MTL::InstanceAccelerationStructureDescriptor::instanceDescriptorStride() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(instanceDescriptorStride)); -} - -_MTL_INLINE void MTL::InstanceAccelerationStructureDescriptor::setInstanceDescriptorStride(NS::UInteger instanceDescriptorStride) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setInstanceDescriptorStride_), instanceDescriptorStride); -} - -_MTL_INLINE NS::UInteger MTL::InstanceAccelerationStructureDescriptor::instanceCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(instanceCount)); -} - -_MTL_INLINE void MTL::InstanceAccelerationStructureDescriptor::setInstanceCount(NS::UInteger instanceCount) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setInstanceCount_), instanceCount); -} - -_MTL_INLINE NS::Array* MTL::InstanceAccelerationStructureDescriptor::instancedAccelerationStructures() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(instancedAccelerationStructures)); -} - -_MTL_INLINE void MTL::InstanceAccelerationStructureDescriptor::setInstancedAccelerationStructures(const NS::Array* instancedAccelerationStructures) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setInstancedAccelerationStructures_), instancedAccelerationStructures); -} - -_MTL_INLINE MTL::AccelerationStructureInstanceDescriptorType MTL::InstanceAccelerationStructureDescriptor::instanceDescriptorType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(instanceDescriptorType)); -} - -_MTL_INLINE void MTL::InstanceAccelerationStructureDescriptor::setInstanceDescriptorType(MTL::AccelerationStructureInstanceDescriptorType instanceDescriptorType) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setInstanceDescriptorType_), instanceDescriptorType); -} - -_MTL_INLINE MTL::Buffer* MTL::InstanceAccelerationStructureDescriptor::motionTransformBuffer() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(motionTransformBuffer)); -} - -_MTL_INLINE void MTL::InstanceAccelerationStructureDescriptor::setMotionTransformBuffer(const MTL::Buffer* motionTransformBuffer) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMotionTransformBuffer_), motionTransformBuffer); -} - -_MTL_INLINE NS::UInteger MTL::InstanceAccelerationStructureDescriptor::motionTransformBufferOffset() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(motionTransformBufferOffset)); -} - -_MTL_INLINE void MTL::InstanceAccelerationStructureDescriptor::setMotionTransformBufferOffset(NS::UInteger motionTransformBufferOffset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMotionTransformBufferOffset_), motionTransformBufferOffset); -} - -_MTL_INLINE NS::UInteger MTL::InstanceAccelerationStructureDescriptor::motionTransformCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(motionTransformCount)); -} - -_MTL_INLINE void MTL::InstanceAccelerationStructureDescriptor::setMotionTransformCount(NS::UInteger motionTransformCount) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMotionTransformCount_), motionTransformCount); -} - -_MTL_INLINE MTL::InstanceAccelerationStructureDescriptor* MTL::InstanceAccelerationStructureDescriptor::descriptor() -{ - return Object::sendMessage(_MTL_PRIVATE_CLS(MTLInstanceAccelerationStructureDescriptor), _MTL_PRIVATE_SEL(descriptor)); -} - -_MTL_INLINE NS::UInteger MTL::AccelerationStructure::size() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(size)); -} - -_MTL_INLINE MTL::ResourceID MTL::AccelerationStructure::gpuResourceID() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(gpuResourceID)); -} - -#pragma once - -#pragma once - -namespace MTL -{ -_MTL_ENUM(NS::UInteger, DataType) { - DataTypeNone = 0, - DataTypeStruct = 1, - DataTypeArray = 2, - DataTypeFloat = 3, - DataTypeFloat2 = 4, - DataTypeFloat3 = 5, - DataTypeFloat4 = 6, - DataTypeFloat2x2 = 7, - DataTypeFloat2x3 = 8, - DataTypeFloat2x4 = 9, - DataTypeFloat3x2 = 10, - DataTypeFloat3x3 = 11, - DataTypeFloat3x4 = 12, - DataTypeFloat4x2 = 13, - DataTypeFloat4x3 = 14, - DataTypeFloat4x4 = 15, - DataTypeHalf = 16, - DataTypeHalf2 = 17, - DataTypeHalf3 = 18, - DataTypeHalf4 = 19, - DataTypeHalf2x2 = 20, - DataTypeHalf2x3 = 21, - DataTypeHalf2x4 = 22, - DataTypeHalf3x2 = 23, - DataTypeHalf3x3 = 24, - DataTypeHalf3x4 = 25, - DataTypeHalf4x2 = 26, - DataTypeHalf4x3 = 27, - DataTypeHalf4x4 = 28, - DataTypeInt = 29, - DataTypeInt2 = 30, - DataTypeInt3 = 31, - DataTypeInt4 = 32, - DataTypeUInt = 33, - DataTypeUInt2 = 34, - DataTypeUInt3 = 35, - DataTypeUInt4 = 36, - DataTypeShort = 37, - DataTypeShort2 = 38, - DataTypeShort3 = 39, - DataTypeShort4 = 40, - DataTypeUShort = 41, - DataTypeUShort2 = 42, - DataTypeUShort3 = 43, - DataTypeUShort4 = 44, - DataTypeChar = 45, - DataTypeChar2 = 46, - DataTypeChar3 = 47, - DataTypeChar4 = 48, - DataTypeUChar = 49, - DataTypeUChar2 = 50, - DataTypeUChar3 = 51, - DataTypeUChar4 = 52, - DataTypeBool = 53, - DataTypeBool2 = 54, - DataTypeBool3 = 55, - DataTypeBool4 = 56, - DataTypeTexture = 58, - DataTypeSampler = 59, - DataTypePointer = 60, - DataTypeR8Unorm = 62, - DataTypeR8Snorm = 63, - DataTypeR16Unorm = 64, - DataTypeR16Snorm = 65, - DataTypeRG8Unorm = 66, - DataTypeRG8Snorm = 67, - DataTypeRG16Unorm = 68, - DataTypeRG16Snorm = 69, - DataTypeRGBA8Unorm = 70, - DataTypeRGBA8Unorm_sRGB = 71, - DataTypeRGBA8Snorm = 72, - DataTypeRGBA16Unorm = 73, - DataTypeRGBA16Snorm = 74, - DataTypeRGB10A2Unorm = 75, - DataTypeRG11B10Float = 76, - DataTypeRGB9E5Float = 77, - DataTypeRenderPipeline = 78, - DataTypeComputePipeline = 79, - DataTypeIndirectCommandBuffer = 80, - DataTypeLong = 81, - DataTypeLong2 = 82, - DataTypeLong3 = 83, - DataTypeLong4 = 84, - DataTypeULong = 85, - DataTypeULong2 = 86, - DataTypeULong3 = 87, - DataTypeULong4 = 88, - DataTypeVisibleFunctionTable = 115, - DataTypeIntersectionFunctionTable = 116, - DataTypePrimitiveAccelerationStructure = 117, - DataTypeInstanceAccelerationStructure = 118, -}; - -_MTL_ENUM(NS::Integer, BindingType) { - BindingTypeBuffer = 0, - BindingTypeThreadgroupMemory = 1, - BindingTypeTexture = 2, - BindingTypeSampler = 3, - BindingTypeImageblockData = 16, - BindingTypeImageblock = 17, - BindingTypeVisibleFunctionTable = 24, - BindingTypePrimitiveAccelerationStructure = 25, - BindingTypeInstanceAccelerationStructure = 26, - BindingTypeIntersectionFunctionTable = 27, - BindingTypeObjectPayload = 34, -}; - -_MTL_ENUM(NS::UInteger, ArgumentType) { - ArgumentTypeBuffer = 0, - ArgumentTypeThreadgroupMemory = 1, - ArgumentTypeTexture = 2, - ArgumentTypeSampler = 3, - ArgumentTypeImageblockData = 16, - ArgumentTypeImageblock = 17, - ArgumentTypeVisibleFunctionTable = 24, - ArgumentTypePrimitiveAccelerationStructure = 25, - ArgumentTypeInstanceAccelerationStructure = 26, - ArgumentTypeIntersectionFunctionTable = 27, -}; - -_MTL_ENUM(NS::UInteger, ArgumentAccess) { - ArgumentAccessReadOnly = 0, - ArgumentAccessReadWrite = 1, - ArgumentAccessWriteOnly = 2, -}; - -class Type : public NS::Referencing -{ -public: - static class Type* alloc(); - - class Type* init(); - - MTL::DataType dataType() const; -}; - -class StructMember : public NS::Referencing -{ -public: - static class StructMember* alloc(); - - class StructMember* init(); - - NS::String* name() const; - - NS::UInteger offset() const; - - MTL::DataType dataType() const; - - class StructType* structType(); - - class ArrayType* arrayType(); - - class TextureReferenceType* textureReferenceType(); - - class PointerType* pointerType(); - - NS::UInteger argumentIndex() const; -}; - -class StructType : public NS::Referencing -{ -public: - static class StructType* alloc(); - - class StructType* init(); - - NS::Array* members() const; - - class StructMember* memberByName(const NS::String* name); -}; - -class ArrayType : public NS::Referencing -{ -public: - static class ArrayType* alloc(); - - class ArrayType* init(); - - MTL::DataType elementType() const; - - NS::UInteger arrayLength() const; - - NS::UInteger stride() const; - - NS::UInteger argumentIndexStride() const; - - class StructType* elementStructType(); - - class ArrayType* elementArrayType(); - - class TextureReferenceType* elementTextureReferenceType(); - - class PointerType* elementPointerType(); -}; - -class PointerType : public NS::Referencing -{ -public: - static class PointerType* alloc(); - - class PointerType* init(); - - MTL::DataType elementType() const; - - MTL::ArgumentAccess access() const; - - NS::UInteger alignment() const; - - NS::UInteger dataSize() const; - - bool elementIsArgumentBuffer() const; - - class StructType* elementStructType(); - - class ArrayType* elementArrayType(); -}; - -class TextureReferenceType : public NS::Referencing -{ -public: - static class TextureReferenceType* alloc(); - - class TextureReferenceType* init(); - - MTL::DataType textureDataType() const; - - MTL::TextureType textureType() const; - - MTL::ArgumentAccess access() const; - - bool isDepthTexture() const; -}; - -class Argument : public NS::Referencing -{ -public: - static class Argument* alloc(); - - class Argument* init(); - - NS::String* name() const; - - MTL::ArgumentType type() const; - - MTL::ArgumentAccess access() const; - - NS::UInteger index() const; - - bool active() const; - - NS::UInteger bufferAlignment() const; - - NS::UInteger bufferDataSize() const; - - MTL::DataType bufferDataType() const; - - class StructType* bufferStructType() const; - - class PointerType* bufferPointerType() const; - - NS::UInteger threadgroupMemoryAlignment() const; - - NS::UInteger threadgroupMemoryDataSize() const; - - MTL::TextureType textureType() const; - - MTL::DataType textureDataType() const; - - bool isDepthTexture() const; - - NS::UInteger arrayLength() const; -}; - -class Binding : public NS::Referencing -{ -public: - NS::String* name() const; - - MTL::BindingType type() const; - - MTL::ArgumentAccess access() const; - - NS::UInteger index() const; - - bool used() const; - - bool argument() const; -}; - -class BufferBinding : public NS::Referencing -{ -public: - NS::UInteger bufferAlignment() const; - - NS::UInteger bufferDataSize() const; - - MTL::DataType bufferDataType() const; - - class StructType* bufferStructType() const; - - class PointerType* bufferPointerType() const; -}; - -class ThreadgroupBinding : public NS::Referencing -{ -public: - NS::UInteger threadgroupMemoryAlignment() const; - - NS::UInteger threadgroupMemoryDataSize() const; -}; - -class TextureBinding : public NS::Referencing -{ -public: - MTL::TextureType textureType() const; - - MTL::DataType textureDataType() const; - - bool depthTexture() const; - - NS::UInteger arrayLength() const; -}; - -class ObjectPayloadBinding : public NS::Referencing -{ -public: - NS::UInteger objectPayloadAlignment() const; - - NS::UInteger objectPayloadDataSize() const; -}; - -} - -_MTL_INLINE MTL::Type* MTL::Type::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLType)); -} - -_MTL_INLINE MTL::Type* MTL::Type::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::DataType MTL::Type::dataType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(dataType)); -} - -_MTL_INLINE MTL::StructMember* MTL::StructMember::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLStructMember)); -} - -_MTL_INLINE MTL::StructMember* MTL::StructMember::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE NS::String* MTL::StructMember::name() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(name)); -} - -_MTL_INLINE NS::UInteger MTL::StructMember::offset() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(offset)); -} - -_MTL_INLINE MTL::DataType MTL::StructMember::dataType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(dataType)); -} - -_MTL_INLINE MTL::StructType* MTL::StructMember::structType() -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(structType)); -} - -_MTL_INLINE MTL::ArrayType* MTL::StructMember::arrayType() -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(arrayType)); -} - -_MTL_INLINE MTL::TextureReferenceType* MTL::StructMember::textureReferenceType() -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(textureReferenceType)); -} - -_MTL_INLINE MTL::PointerType* MTL::StructMember::pointerType() -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(pointerType)); -} - -_MTL_INLINE NS::UInteger MTL::StructMember::argumentIndex() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(argumentIndex)); -} - -_MTL_INLINE MTL::StructType* MTL::StructType::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLStructType)); -} - -_MTL_INLINE MTL::StructType* MTL::StructType::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE NS::Array* MTL::StructType::members() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(members)); -} - -_MTL_INLINE MTL::StructMember* MTL::StructType::memberByName(const NS::String* name) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(memberByName_), name); -} - -_MTL_INLINE MTL::ArrayType* MTL::ArrayType::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLArrayType)); -} - -_MTL_INLINE MTL::ArrayType* MTL::ArrayType::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::DataType MTL::ArrayType::elementType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(elementType)); -} - -_MTL_INLINE NS::UInteger MTL::ArrayType::arrayLength() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(arrayLength)); -} - -_MTL_INLINE NS::UInteger MTL::ArrayType::stride() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(stride)); -} - -_MTL_INLINE NS::UInteger MTL::ArrayType::argumentIndexStride() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(argumentIndexStride)); -} - -_MTL_INLINE MTL::StructType* MTL::ArrayType::elementStructType() -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(elementStructType)); -} - -_MTL_INLINE MTL::ArrayType* MTL::ArrayType::elementArrayType() -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(elementArrayType)); -} - -_MTL_INLINE MTL::TextureReferenceType* MTL::ArrayType::elementTextureReferenceType() -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(elementTextureReferenceType)); -} - -_MTL_INLINE MTL::PointerType* MTL::ArrayType::elementPointerType() -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(elementPointerType)); -} - -_MTL_INLINE MTL::PointerType* MTL::PointerType::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLPointerType)); -} - -_MTL_INLINE MTL::PointerType* MTL::PointerType::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::DataType MTL::PointerType::elementType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(elementType)); -} - -_MTL_INLINE MTL::ArgumentAccess MTL::PointerType::access() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(access)); -} - -_MTL_INLINE NS::UInteger MTL::PointerType::alignment() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(alignment)); -} - -_MTL_INLINE NS::UInteger MTL::PointerType::dataSize() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(dataSize)); -} - -_MTL_INLINE bool MTL::PointerType::elementIsArgumentBuffer() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(elementIsArgumentBuffer)); -} - -_MTL_INLINE MTL::StructType* MTL::PointerType::elementStructType() -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(elementStructType)); -} - -_MTL_INLINE MTL::ArrayType* MTL::PointerType::elementArrayType() -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(elementArrayType)); -} - -_MTL_INLINE MTL::TextureReferenceType* MTL::TextureReferenceType::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLTextureReferenceType)); -} - -_MTL_INLINE MTL::TextureReferenceType* MTL::TextureReferenceType::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::DataType MTL::TextureReferenceType::textureDataType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(textureDataType)); -} - -_MTL_INLINE MTL::TextureType MTL::TextureReferenceType::textureType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(textureType)); -} - -_MTL_INLINE MTL::ArgumentAccess MTL::TextureReferenceType::access() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(access)); -} - -_MTL_INLINE bool MTL::TextureReferenceType::isDepthTexture() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(isDepthTexture)); -} - -_MTL_INLINE MTL::Argument* MTL::Argument::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLArgument)); -} - -_MTL_INLINE MTL::Argument* MTL::Argument::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE NS::String* MTL::Argument::name() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(name)); -} - -_MTL_INLINE MTL::ArgumentType MTL::Argument::type() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(type)); -} - -_MTL_INLINE MTL::ArgumentAccess MTL::Argument::access() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(access)); -} - -_MTL_INLINE NS::UInteger MTL::Argument::index() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(index)); -} - -_MTL_INLINE bool MTL::Argument::active() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(isActive)); -} - -_MTL_INLINE NS::UInteger MTL::Argument::bufferAlignment() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(bufferAlignment)); -} - -_MTL_INLINE NS::UInteger MTL::Argument::bufferDataSize() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(bufferDataSize)); -} - -_MTL_INLINE MTL::DataType MTL::Argument::bufferDataType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(bufferDataType)); -} - -_MTL_INLINE MTL::StructType* MTL::Argument::bufferStructType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(bufferStructType)); -} - -_MTL_INLINE MTL::PointerType* MTL::Argument::bufferPointerType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(bufferPointerType)); -} - -_MTL_INLINE NS::UInteger MTL::Argument::threadgroupMemoryAlignment() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(threadgroupMemoryAlignment)); -} - -_MTL_INLINE NS::UInteger MTL::Argument::threadgroupMemoryDataSize() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(threadgroupMemoryDataSize)); -} - -_MTL_INLINE MTL::TextureType MTL::Argument::textureType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(textureType)); -} - -_MTL_INLINE MTL::DataType MTL::Argument::textureDataType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(textureDataType)); -} - -_MTL_INLINE bool MTL::Argument::isDepthTexture() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(isDepthTexture)); -} - -_MTL_INLINE NS::UInteger MTL::Argument::arrayLength() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(arrayLength)); -} - -_MTL_INLINE NS::String* MTL::Binding::name() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(name)); -} - -_MTL_INLINE MTL::BindingType MTL::Binding::type() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(type)); -} - -_MTL_INLINE MTL::ArgumentAccess MTL::Binding::access() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(access)); -} - -_MTL_INLINE NS::UInteger MTL::Binding::index() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(index)); -} - -_MTL_INLINE bool MTL::Binding::used() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(isUsed)); -} - -_MTL_INLINE bool MTL::Binding::argument() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(isArgument)); -} - -_MTL_INLINE NS::UInteger MTL::BufferBinding::bufferAlignment() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(bufferAlignment)); -} - -_MTL_INLINE NS::UInteger MTL::BufferBinding::bufferDataSize() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(bufferDataSize)); -} - -_MTL_INLINE MTL::DataType MTL::BufferBinding::bufferDataType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(bufferDataType)); -} - -_MTL_INLINE MTL::StructType* MTL::BufferBinding::bufferStructType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(bufferStructType)); -} - -_MTL_INLINE MTL::PointerType* MTL::BufferBinding::bufferPointerType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(bufferPointerType)); -} - -_MTL_INLINE NS::UInteger MTL::ThreadgroupBinding::threadgroupMemoryAlignment() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(threadgroupMemoryAlignment)); -} - -_MTL_INLINE NS::UInteger MTL::ThreadgroupBinding::threadgroupMemoryDataSize() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(threadgroupMemoryDataSize)); -} - -_MTL_INLINE MTL::TextureType MTL::TextureBinding::textureType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(textureType)); -} - -_MTL_INLINE MTL::DataType MTL::TextureBinding::textureDataType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(textureDataType)); -} - -_MTL_INLINE bool MTL::TextureBinding::depthTexture() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(isDepthTexture)); -} - -_MTL_INLINE NS::UInteger MTL::TextureBinding::arrayLength() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(arrayLength)); -} - -_MTL_INLINE NS::UInteger MTL::ObjectPayloadBinding::objectPayloadAlignment() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(objectPayloadAlignment)); -} - -_MTL_INLINE NS::UInteger MTL::ObjectPayloadBinding::objectPayloadDataSize() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(objectPayloadDataSize)); -} - -#pragma once - -namespace MTL -{ -_MTL_OPTIONS(NS::UInteger, ResourceUsage) { - ResourceUsageRead = 1, - ResourceUsageWrite = 2, - ResourceUsageSample = 4, -}; - -_MTL_OPTIONS(NS::UInteger, BarrierScope) { - BarrierScopeBuffers = 1, - BarrierScopeTextures = 2, - BarrierScopeRenderTargets = 4, -}; - -class CommandEncoder : public NS::Referencing -{ -public: - class Device* device() const; - - NS::String* label() const; - void setLabel(const NS::String* label); - - void endEncoding(); - - void insertDebugSignpost(const NS::String* string); - - void pushDebugGroup(const NS::String* string); - - void popDebugGroup(); -}; - -} - -_MTL_INLINE MTL::Device* MTL::CommandEncoder::device() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(device)); -} - -_MTL_INLINE NS::String* MTL::CommandEncoder::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE void MTL::CommandEncoder::setLabel(const NS::String* label) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLabel_), label); -} - -_MTL_INLINE void MTL::CommandEncoder::endEncoding() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(endEncoding)); -} - -_MTL_INLINE void MTL::CommandEncoder::insertDebugSignpost(const NS::String* string) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(insertDebugSignpost_), string); -} - -_MTL_INLINE void MTL::CommandEncoder::pushDebugGroup(const NS::String* string) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(pushDebugGroup_), string); -} - -_MTL_INLINE void MTL::CommandEncoder::popDebugGroup() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(popDebugGroup)); -} - -namespace MTL -{ -_MTL_OPTIONS(NS::UInteger, AccelerationStructureRefitOptions) { - AccelerationStructureRefitOptionVertexData = 1, - AccelerationStructureRefitOptionPerPrimitiveData = 2, -}; - -class AccelerationStructureCommandEncoder : public NS::Referencing -{ -public: - void buildAccelerationStructure(const class AccelerationStructure* accelerationStructure, const class AccelerationStructureDescriptor* descriptor, const class Buffer* scratchBuffer, NS::UInteger scratchBufferOffset); - - void refitAccelerationStructure(const class AccelerationStructure* sourceAccelerationStructure, const class AccelerationStructureDescriptor* descriptor, const class AccelerationStructure* destinationAccelerationStructure, const class Buffer* scratchBuffer, NS::UInteger scratchBufferOffset); - - void refitAccelerationStructure(const class AccelerationStructure* sourceAccelerationStructure, const class AccelerationStructureDescriptor* descriptor, const class AccelerationStructure* destinationAccelerationStructure, const class Buffer* scratchBuffer, NS::UInteger scratchBufferOffset, MTL::AccelerationStructureRefitOptions options); - - void copyAccelerationStructure(const class AccelerationStructure* sourceAccelerationStructure, const class AccelerationStructure* destinationAccelerationStructure); - - void writeCompactedAccelerationStructureSize(const class AccelerationStructure* accelerationStructure, const class Buffer* buffer, NS::UInteger offset); - - void writeCompactedAccelerationStructureSize(const class AccelerationStructure* accelerationStructure, const class Buffer* buffer, NS::UInteger offset, MTL::DataType sizeDataType); - - void copyAndCompactAccelerationStructure(const class AccelerationStructure* sourceAccelerationStructure, const class AccelerationStructure* destinationAccelerationStructure); - - void updateFence(const class Fence* fence); - - void waitForFence(const class Fence* fence); - - void useResource(const class Resource* resource, MTL::ResourceUsage usage); - - void useResources(const class Resource* const resources[], NS::UInteger count, MTL::ResourceUsage usage); - - void useHeap(const class Heap* heap); - - void useHeaps(const class Heap* const heaps[], NS::UInteger count); - - void sampleCountersInBuffer(const class CounterSampleBuffer* sampleBuffer, NS::UInteger sampleIndex, bool barrier); -}; - -class AccelerationStructurePassSampleBufferAttachmentDescriptor : public NS::Copying -{ -public: - static class AccelerationStructurePassSampleBufferAttachmentDescriptor* alloc(); - - class AccelerationStructurePassSampleBufferAttachmentDescriptor* init(); - - class CounterSampleBuffer* sampleBuffer() const; - void setSampleBuffer(const class CounterSampleBuffer* sampleBuffer); - - NS::UInteger startOfEncoderSampleIndex() const; - void setStartOfEncoderSampleIndex(NS::UInteger startOfEncoderSampleIndex); - - NS::UInteger endOfEncoderSampleIndex() const; - void setEndOfEncoderSampleIndex(NS::UInteger endOfEncoderSampleIndex); -}; - -class AccelerationStructurePassSampleBufferAttachmentDescriptorArray : public NS::Referencing -{ -public: - static class AccelerationStructurePassSampleBufferAttachmentDescriptorArray* alloc(); - - class AccelerationStructurePassSampleBufferAttachmentDescriptorArray* init(); - - class AccelerationStructurePassSampleBufferAttachmentDescriptor* object(NS::UInteger attachmentIndex); - - void setObject(const class AccelerationStructurePassSampleBufferAttachmentDescriptor* attachment, NS::UInteger attachmentIndex); -}; - -class AccelerationStructurePassDescriptor : public NS::Copying -{ -public: - static class AccelerationStructurePassDescriptor* alloc(); - - class AccelerationStructurePassDescriptor* init(); - - static class AccelerationStructurePassDescriptor* accelerationStructurePassDescriptor(); - - class AccelerationStructurePassSampleBufferAttachmentDescriptorArray* sampleBufferAttachments() const; -}; - -} - -_MTL_INLINE void MTL::AccelerationStructureCommandEncoder::buildAccelerationStructure(const MTL::AccelerationStructure* accelerationStructure, const MTL::AccelerationStructureDescriptor* descriptor, const MTL::Buffer* scratchBuffer, NS::UInteger scratchBufferOffset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(buildAccelerationStructure_descriptor_scratchBuffer_scratchBufferOffset_), accelerationStructure, descriptor, scratchBuffer, scratchBufferOffset); -} - -_MTL_INLINE void MTL::AccelerationStructureCommandEncoder::refitAccelerationStructure(const MTL::AccelerationStructure* sourceAccelerationStructure, const MTL::AccelerationStructureDescriptor* descriptor, const MTL::AccelerationStructure* destinationAccelerationStructure, const MTL::Buffer* scratchBuffer, NS::UInteger scratchBufferOffset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(refitAccelerationStructure_descriptor_destination_scratchBuffer_scratchBufferOffset_), sourceAccelerationStructure, descriptor, destinationAccelerationStructure, scratchBuffer, scratchBufferOffset); -} - -_MTL_INLINE void MTL::AccelerationStructureCommandEncoder::refitAccelerationStructure(const MTL::AccelerationStructure* sourceAccelerationStructure, const MTL::AccelerationStructureDescriptor* descriptor, const MTL::AccelerationStructure* destinationAccelerationStructure, const MTL::Buffer* scratchBuffer, NS::UInteger scratchBufferOffset, MTL::AccelerationStructureRefitOptions options) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(refitAccelerationStructure_descriptor_destination_scratchBuffer_scratchBufferOffset_options_), sourceAccelerationStructure, descriptor, destinationAccelerationStructure, scratchBuffer, scratchBufferOffset, options); -} - -_MTL_INLINE void MTL::AccelerationStructureCommandEncoder::copyAccelerationStructure(const MTL::AccelerationStructure* sourceAccelerationStructure, const MTL::AccelerationStructure* destinationAccelerationStructure) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(copyAccelerationStructure_toAccelerationStructure_), sourceAccelerationStructure, destinationAccelerationStructure); -} - -_MTL_INLINE void MTL::AccelerationStructureCommandEncoder::writeCompactedAccelerationStructureSize(const MTL::AccelerationStructure* accelerationStructure, const MTL::Buffer* buffer, NS::UInteger offset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(writeCompactedAccelerationStructureSize_toBuffer_offset_), accelerationStructure, buffer, offset); -} - -_MTL_INLINE void MTL::AccelerationStructureCommandEncoder::writeCompactedAccelerationStructureSize(const MTL::AccelerationStructure* accelerationStructure, const MTL::Buffer* buffer, NS::UInteger offset, MTL::DataType sizeDataType) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(writeCompactedAccelerationStructureSize_toBuffer_offset_sizeDataType_), accelerationStructure, buffer, offset, sizeDataType); -} - -_MTL_INLINE void MTL::AccelerationStructureCommandEncoder::copyAndCompactAccelerationStructure(const MTL::AccelerationStructure* sourceAccelerationStructure, const MTL::AccelerationStructure* destinationAccelerationStructure) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(copyAndCompactAccelerationStructure_toAccelerationStructure_), sourceAccelerationStructure, destinationAccelerationStructure); -} - -_MTL_INLINE void MTL::AccelerationStructureCommandEncoder::updateFence(const MTL::Fence* fence) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(updateFence_), fence); -} - -_MTL_INLINE void MTL::AccelerationStructureCommandEncoder::waitForFence(const MTL::Fence* fence) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(waitForFence_), fence); -} - -_MTL_INLINE void MTL::AccelerationStructureCommandEncoder::useResource(const MTL::Resource* resource, MTL::ResourceUsage usage) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(useResource_usage_), resource, usage); -} - -_MTL_INLINE void MTL::AccelerationStructureCommandEncoder::useResources(const MTL::Resource* const resources[], NS::UInteger count, MTL::ResourceUsage usage) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(useResources_count_usage_), resources, count, usage); -} - -_MTL_INLINE void MTL::AccelerationStructureCommandEncoder::useHeap(const MTL::Heap* heap) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(useHeap_), heap); -} - -_MTL_INLINE void MTL::AccelerationStructureCommandEncoder::useHeaps(const MTL::Heap* const heaps[], NS::UInteger count) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(useHeaps_count_), heaps, count); -} - -_MTL_INLINE void MTL::AccelerationStructureCommandEncoder::sampleCountersInBuffer(const MTL::CounterSampleBuffer* sampleBuffer, NS::UInteger sampleIndex, bool barrier) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(sampleCountersInBuffer_atSampleIndex_withBarrier_), sampleBuffer, sampleIndex, barrier); -} - -_MTL_INLINE MTL::AccelerationStructurePassSampleBufferAttachmentDescriptor* MTL::AccelerationStructurePassSampleBufferAttachmentDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLAccelerationStructurePassSampleBufferAttachmentDescriptor)); -} - -_MTL_INLINE MTL::AccelerationStructurePassSampleBufferAttachmentDescriptor* MTL::AccelerationStructurePassSampleBufferAttachmentDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::CounterSampleBuffer* MTL::AccelerationStructurePassSampleBufferAttachmentDescriptor::sampleBuffer() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(sampleBuffer)); -} - -_MTL_INLINE void MTL::AccelerationStructurePassSampleBufferAttachmentDescriptor::setSampleBuffer(const MTL::CounterSampleBuffer* sampleBuffer) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSampleBuffer_), sampleBuffer); -} - -_MTL_INLINE NS::UInteger MTL::AccelerationStructurePassSampleBufferAttachmentDescriptor::startOfEncoderSampleIndex() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(startOfEncoderSampleIndex)); -} - -_MTL_INLINE void MTL::AccelerationStructurePassSampleBufferAttachmentDescriptor::setStartOfEncoderSampleIndex(NS::UInteger startOfEncoderSampleIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStartOfEncoderSampleIndex_), startOfEncoderSampleIndex); -} - -_MTL_INLINE NS::UInteger MTL::AccelerationStructurePassSampleBufferAttachmentDescriptor::endOfEncoderSampleIndex() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(endOfEncoderSampleIndex)); -} - -_MTL_INLINE void MTL::AccelerationStructurePassSampleBufferAttachmentDescriptor::setEndOfEncoderSampleIndex(NS::UInteger endOfEncoderSampleIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setEndOfEncoderSampleIndex_), endOfEncoderSampleIndex); -} - -_MTL_INLINE MTL::AccelerationStructurePassSampleBufferAttachmentDescriptorArray* MTL::AccelerationStructurePassSampleBufferAttachmentDescriptorArray::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLAccelerationStructurePassSampleBufferAttachmentDescriptorArray)); -} - -_MTL_INLINE MTL::AccelerationStructurePassSampleBufferAttachmentDescriptorArray* MTL::AccelerationStructurePassSampleBufferAttachmentDescriptorArray::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::AccelerationStructurePassSampleBufferAttachmentDescriptor* MTL::AccelerationStructurePassSampleBufferAttachmentDescriptorArray::object(NS::UInteger attachmentIndex) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(objectAtIndexedSubscript_), attachmentIndex); -} - -_MTL_INLINE void MTL::AccelerationStructurePassSampleBufferAttachmentDescriptorArray::setObject(const MTL::AccelerationStructurePassSampleBufferAttachmentDescriptor* attachment, NS::UInteger attachmentIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setObject_atIndexedSubscript_), attachment, attachmentIndex); -} - -_MTL_INLINE MTL::AccelerationStructurePassDescriptor* MTL::AccelerationStructurePassDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLAccelerationStructurePassDescriptor)); -} - -_MTL_INLINE MTL::AccelerationStructurePassDescriptor* MTL::AccelerationStructurePassDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::AccelerationStructurePassDescriptor* MTL::AccelerationStructurePassDescriptor::accelerationStructurePassDescriptor() -{ - return Object::sendMessage(_MTL_PRIVATE_CLS(MTLAccelerationStructurePassDescriptor), _MTL_PRIVATE_SEL(accelerationStructurePassDescriptor)); -} - -_MTL_INLINE MTL::AccelerationStructurePassSampleBufferAttachmentDescriptorArray* MTL::AccelerationStructurePassDescriptor::sampleBufferAttachments() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(sampleBufferAttachments)); -} - -#pragma once - -namespace MTL -{ -class ArgumentEncoder : public NS::Referencing -{ -public: - class Device* device() const; - - NS::String* label() const; - void setLabel(const NS::String* label); - - NS::UInteger encodedLength() const; - - NS::UInteger alignment() const; - - void setArgumentBuffer(const class Buffer* argumentBuffer, NS::UInteger offset); - - void setArgumentBuffer(const class Buffer* argumentBuffer, NS::UInteger startOffset, NS::UInteger arrayElement); - - void setBuffer(const class Buffer* buffer, NS::UInteger offset, NS::UInteger index); - - void setBuffers(const class Buffer* const buffers[], const NS::UInteger offsets[], NS::Range range); - - void setTexture(const class Texture* texture, NS::UInteger index); - - void setTextures(const class Texture* const textures[], NS::Range range); - - void setSamplerState(const class SamplerState* sampler, NS::UInteger index); - - void setSamplerStates(const class SamplerState* const samplers[], NS::Range range); - - void* constantData(NS::UInteger index); - - void setRenderPipelineState(const class RenderPipelineState* pipeline, NS::UInteger index); - - void setRenderPipelineStates(const class RenderPipelineState* const pipelines[], NS::Range range); - - void setComputePipelineState(const class ComputePipelineState* pipeline, NS::UInteger index); - - void setComputePipelineStates(const class ComputePipelineState* const pipelines[], NS::Range range); - - void setIndirectCommandBuffer(const class IndirectCommandBuffer* indirectCommandBuffer, NS::UInteger index); - - void setIndirectCommandBuffers(const class IndirectCommandBuffer* const buffers[], NS::Range range); - - void setAccelerationStructure(const class AccelerationStructure* accelerationStructure, NS::UInteger index); - - class ArgumentEncoder* newArgumentEncoder(NS::UInteger index); - - void setVisibleFunctionTable(const class VisibleFunctionTable* visibleFunctionTable, NS::UInteger index); - - void setVisibleFunctionTables(const class VisibleFunctionTable* const visibleFunctionTables[], NS::Range range); - - void setIntersectionFunctionTable(const class IntersectionFunctionTable* intersectionFunctionTable, NS::UInteger index); - - void setIntersectionFunctionTables(const class IntersectionFunctionTable* const intersectionFunctionTables[], NS::Range range); -}; - -} - -_MTL_INLINE MTL::Device* MTL::ArgumentEncoder::device() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(device)); -} - -_MTL_INLINE NS::String* MTL::ArgumentEncoder::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE void MTL::ArgumentEncoder::setLabel(const NS::String* label) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLabel_), label); -} - -_MTL_INLINE NS::UInteger MTL::ArgumentEncoder::encodedLength() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(encodedLength)); -} - -_MTL_INLINE NS::UInteger MTL::ArgumentEncoder::alignment() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(alignment)); -} - -_MTL_INLINE void MTL::ArgumentEncoder::setArgumentBuffer(const MTL::Buffer* argumentBuffer, NS::UInteger offset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setArgumentBuffer_offset_), argumentBuffer, offset); -} - -_MTL_INLINE void MTL::ArgumentEncoder::setArgumentBuffer(const MTL::Buffer* argumentBuffer, NS::UInteger startOffset, NS::UInteger arrayElement) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setArgumentBuffer_startOffset_arrayElement_), argumentBuffer, startOffset, arrayElement); -} - -_MTL_INLINE void MTL::ArgumentEncoder::setBuffer(const MTL::Buffer* buffer, NS::UInteger offset, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setBuffer_offset_atIndex_), buffer, offset, index); -} - -_MTL_INLINE void MTL::ArgumentEncoder::setBuffers(const MTL::Buffer* const buffers[], const NS::UInteger offsets[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setBuffers_offsets_withRange_), buffers, offsets, range); -} - -_MTL_INLINE void MTL::ArgumentEncoder::setTexture(const MTL::Texture* texture, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTexture_atIndex_), texture, index); -} - -_MTL_INLINE void MTL::ArgumentEncoder::setTextures(const MTL::Texture* const textures[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTextures_withRange_), textures, range); -} - -_MTL_INLINE void MTL::ArgumentEncoder::setSamplerState(const MTL::SamplerState* sampler, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSamplerState_atIndex_), sampler, index); -} - -_MTL_INLINE void MTL::ArgumentEncoder::setSamplerStates(const MTL::SamplerState* const samplers[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSamplerStates_withRange_), samplers, range); -} - -_MTL_INLINE void* MTL::ArgumentEncoder::constantData(NS::UInteger index) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(constantDataAtIndex_), index); -} - -_MTL_INLINE void MTL::ArgumentEncoder::setRenderPipelineState(const MTL::RenderPipelineState* pipeline, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setRenderPipelineState_atIndex_), pipeline, index); -} - -_MTL_INLINE void MTL::ArgumentEncoder::setRenderPipelineStates(const MTL::RenderPipelineState* const pipelines[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setRenderPipelineStates_withRange_), pipelines, range); -} - -_MTL_INLINE void MTL::ArgumentEncoder::setComputePipelineState(const MTL::ComputePipelineState* pipeline, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setComputePipelineState_atIndex_), pipeline, index); -} - -_MTL_INLINE void MTL::ArgumentEncoder::setComputePipelineStates(const MTL::ComputePipelineState* const pipelines[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setComputePipelineStates_withRange_), pipelines, range); -} - -_MTL_INLINE void MTL::ArgumentEncoder::setIndirectCommandBuffer(const MTL::IndirectCommandBuffer* indirectCommandBuffer, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setIndirectCommandBuffer_atIndex_), indirectCommandBuffer, index); -} - -_MTL_INLINE void MTL::ArgumentEncoder::setIndirectCommandBuffers(const MTL::IndirectCommandBuffer* const buffers[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setIndirectCommandBuffers_withRange_), buffers, range); -} - -_MTL_INLINE void MTL::ArgumentEncoder::setAccelerationStructure(const MTL::AccelerationStructure* accelerationStructure, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setAccelerationStructure_atIndex_), accelerationStructure, index); -} - -_MTL_INLINE MTL::ArgumentEncoder* MTL::ArgumentEncoder::newArgumentEncoder(NS::UInteger index) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newArgumentEncoderForBufferAtIndex_), index); -} - -_MTL_INLINE void MTL::ArgumentEncoder::setVisibleFunctionTable(const MTL::VisibleFunctionTable* visibleFunctionTable, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVisibleFunctionTable_atIndex_), visibleFunctionTable, index); -} - -_MTL_INLINE void MTL::ArgumentEncoder::setVisibleFunctionTables(const MTL::VisibleFunctionTable* const visibleFunctionTables[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVisibleFunctionTables_withRange_), visibleFunctionTables, range); -} - -_MTL_INLINE void MTL::ArgumentEncoder::setIntersectionFunctionTable(const MTL::IntersectionFunctionTable* intersectionFunctionTable, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setIntersectionFunctionTable_atIndex_), intersectionFunctionTable, index); -} - -_MTL_INLINE void MTL::ArgumentEncoder::setIntersectionFunctionTables(const MTL::IntersectionFunctionTable* const intersectionFunctionTables[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setIntersectionFunctionTables_withRange_), intersectionFunctionTables, range); -} - -#pragma once - -namespace MTL -{ -_MTL_ENUM(NS::UInteger, BinaryArchiveError) { - BinaryArchiveErrorNone = 0, - BinaryArchiveErrorInvalidFile = 1, - BinaryArchiveErrorUnexpectedElement = 2, - BinaryArchiveErrorCompilationFailure = 3, - BinaryArchiveErrorInternalError = 4, -}; - -class BinaryArchiveDescriptor : public NS::Copying -{ -public: - static class BinaryArchiveDescriptor* alloc(); - - class BinaryArchiveDescriptor* init(); - - NS::URL* url() const; - void setUrl(const NS::URL* url); -}; - -class BinaryArchive : public NS::Referencing -{ -public: - NS::String* label() const; - void setLabel(const NS::String* label); - - class Device* device() const; - - bool addComputePipelineFunctions(const class ComputePipelineDescriptor* descriptor, NS::Error** error); - - bool addRenderPipelineFunctions(const class RenderPipelineDescriptor* descriptor, NS::Error** error); - - bool addTileRenderPipelineFunctions(const class TileRenderPipelineDescriptor* descriptor, NS::Error** error); - - bool serializeToURL(const NS::URL* url, NS::Error** error); - - bool addFunction(const class FunctionDescriptor* descriptor, const class Library* library, NS::Error** error); -}; - -} - -_MTL_INLINE MTL::BinaryArchiveDescriptor* MTL::BinaryArchiveDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLBinaryArchiveDescriptor)); -} - -_MTL_INLINE MTL::BinaryArchiveDescriptor* MTL::BinaryArchiveDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE NS::URL* MTL::BinaryArchiveDescriptor::url() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(url)); -} - -_MTL_INLINE void MTL::BinaryArchiveDescriptor::setUrl(const NS::URL* url) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setUrl_), url); -} - -_MTL_INLINE NS::String* MTL::BinaryArchive::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE void MTL::BinaryArchive::setLabel(const NS::String* label) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLabel_), label); -} - -_MTL_INLINE MTL::Device* MTL::BinaryArchive::device() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(device)); -} - -_MTL_INLINE bool MTL::BinaryArchive::addComputePipelineFunctions(const MTL::ComputePipelineDescriptor* descriptor, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(addComputePipelineFunctionsWithDescriptor_error_), descriptor, error); -} - -_MTL_INLINE bool MTL::BinaryArchive::addRenderPipelineFunctions(const MTL::RenderPipelineDescriptor* descriptor, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(addRenderPipelineFunctionsWithDescriptor_error_), descriptor, error); -} - -_MTL_INLINE bool MTL::BinaryArchive::addTileRenderPipelineFunctions(const MTL::TileRenderPipelineDescriptor* descriptor, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(addTileRenderPipelineFunctionsWithDescriptor_error_), descriptor, error); -} - -_MTL_INLINE bool MTL::BinaryArchive::serializeToURL(const NS::URL* url, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(serializeToURL_error_), url, error); -} - -_MTL_INLINE bool MTL::BinaryArchive::addFunction(const MTL::FunctionDescriptor* descriptor, const MTL::Library* library, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(addFunctionWithDescriptor_library_error_), descriptor, library, error); -} - -#pragma once - -namespace MTL -{ -_MTL_OPTIONS(NS::UInteger, BlitOption) { - BlitOptionNone = 0, - BlitOptionDepthFromDepthStencil = 1, - BlitOptionStencilFromDepthStencil = 2, - BlitOptionRowLinearPVRTC = 4, -}; - -class BlitCommandEncoder : public NS::Referencing -{ -public: - void synchronizeResource(const class Resource* resource); - - void synchronizeTexture(const class Texture* texture, NS::UInteger slice, NS::UInteger level); - - void copyFromTexture(const class Texture* sourceTexture, NS::UInteger sourceSlice, NS::UInteger sourceLevel, MTL::Origin sourceOrigin, MTL::Size sourceSize, const class Texture* destinationTexture, NS::UInteger destinationSlice, NS::UInteger destinationLevel, MTL::Origin destinationOrigin); - - void copyFromBuffer(const class Buffer* sourceBuffer, NS::UInteger sourceOffset, NS::UInteger sourceBytesPerRow, NS::UInteger sourceBytesPerImage, MTL::Size sourceSize, const class Texture* destinationTexture, NS::UInteger destinationSlice, NS::UInteger destinationLevel, MTL::Origin destinationOrigin); - - void copyFromBuffer(const class Buffer* sourceBuffer, NS::UInteger sourceOffset, NS::UInteger sourceBytesPerRow, NS::UInteger sourceBytesPerImage, MTL::Size sourceSize, const class Texture* destinationTexture, NS::UInteger destinationSlice, NS::UInteger destinationLevel, MTL::Origin destinationOrigin, MTL::BlitOption options); - - void copyFromTexture(const class Texture* sourceTexture, NS::UInteger sourceSlice, NS::UInteger sourceLevel, MTL::Origin sourceOrigin, MTL::Size sourceSize, const class Buffer* destinationBuffer, NS::UInteger destinationOffset, NS::UInteger destinationBytesPerRow, NS::UInteger destinationBytesPerImage); - - void copyFromTexture(const class Texture* sourceTexture, NS::UInteger sourceSlice, NS::UInteger sourceLevel, MTL::Origin sourceOrigin, MTL::Size sourceSize, const class Buffer* destinationBuffer, NS::UInteger destinationOffset, NS::UInteger destinationBytesPerRow, NS::UInteger destinationBytesPerImage, MTL::BlitOption options); - - void generateMipmaps(const class Texture* texture); - - void fillBuffer(const class Buffer* buffer, NS::Range range, uint8_t value); - - void copyFromTexture(const class Texture* sourceTexture, NS::UInteger sourceSlice, NS::UInteger sourceLevel, const class Texture* destinationTexture, NS::UInteger destinationSlice, NS::UInteger destinationLevel, NS::UInteger sliceCount, NS::UInteger levelCount); - - void copyFromTexture(const class Texture* sourceTexture, const class Texture* destinationTexture); - - void copyFromBuffer(const class Buffer* sourceBuffer, NS::UInteger sourceOffset, const class Buffer* destinationBuffer, NS::UInteger destinationOffset, NS::UInteger size); - - void updateFence(const class Fence* fence); - - void waitForFence(const class Fence* fence); - - void getTextureAccessCounters(const class Texture* texture, MTL::Region region, NS::UInteger mipLevel, NS::UInteger slice, bool resetCounters, const class Buffer* countersBuffer, NS::UInteger countersBufferOffset); - - void resetTextureAccessCounters(const class Texture* texture, MTL::Region region, NS::UInteger mipLevel, NS::UInteger slice); - - void optimizeContentsForGPUAccess(const class Texture* texture); - - void optimizeContentsForGPUAccess(const class Texture* texture, NS::UInteger slice, NS::UInteger level); - - void optimizeContentsForCPUAccess(const class Texture* texture); - - void optimizeContentsForCPUAccess(const class Texture* texture, NS::UInteger slice, NS::UInteger level); - - void resetCommandsInBuffer(const class IndirectCommandBuffer* buffer, NS::Range range); - - void copyIndirectCommandBuffer(const class IndirectCommandBuffer* source, NS::Range sourceRange, const class IndirectCommandBuffer* destination, NS::UInteger destinationIndex); - - void optimizeIndirectCommandBuffer(const class IndirectCommandBuffer* indirectCommandBuffer, NS::Range range); - - void sampleCountersInBuffer(const class CounterSampleBuffer* sampleBuffer, NS::UInteger sampleIndex, bool barrier); - - void resolveCounters(const class CounterSampleBuffer* sampleBuffer, NS::Range range, const class Buffer* destinationBuffer, NS::UInteger destinationOffset); -}; - -} - -_MTL_INLINE void MTL::BlitCommandEncoder::synchronizeResource(const MTL::Resource* resource) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(synchronizeResource_), resource); -} - -_MTL_INLINE void MTL::BlitCommandEncoder::synchronizeTexture(const MTL::Texture* texture, NS::UInteger slice, NS::UInteger level) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(synchronizeTexture_slice_level_), texture, slice, level); -} - -_MTL_INLINE void MTL::BlitCommandEncoder::copyFromTexture(const MTL::Texture* sourceTexture, NS::UInteger sourceSlice, NS::UInteger sourceLevel, MTL::Origin sourceOrigin, MTL::Size sourceSize, const MTL::Texture* destinationTexture, NS::UInteger destinationSlice, NS::UInteger destinationLevel, MTL::Origin destinationOrigin) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(copyFromTexture_sourceSlice_sourceLevel_sourceOrigin_sourceSize_toTexture_destinationSlice_destinationLevel_destinationOrigin_), sourceTexture, sourceSlice, sourceLevel, sourceOrigin, sourceSize, destinationTexture, destinationSlice, destinationLevel, destinationOrigin); -} - -_MTL_INLINE void MTL::BlitCommandEncoder::copyFromBuffer(const MTL::Buffer* sourceBuffer, NS::UInteger sourceOffset, NS::UInteger sourceBytesPerRow, NS::UInteger sourceBytesPerImage, MTL::Size sourceSize, const MTL::Texture* destinationTexture, NS::UInteger destinationSlice, NS::UInteger destinationLevel, MTL::Origin destinationOrigin) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(copyFromBuffer_sourceOffset_sourceBytesPerRow_sourceBytesPerImage_sourceSize_toTexture_destinationSlice_destinationLevel_destinationOrigin_), sourceBuffer, sourceOffset, sourceBytesPerRow, sourceBytesPerImage, sourceSize, destinationTexture, destinationSlice, destinationLevel, destinationOrigin); -} - -_MTL_INLINE void MTL::BlitCommandEncoder::copyFromBuffer(const MTL::Buffer* sourceBuffer, NS::UInteger sourceOffset, NS::UInteger sourceBytesPerRow, NS::UInteger sourceBytesPerImage, MTL::Size sourceSize, const MTL::Texture* destinationTexture, NS::UInteger destinationSlice, NS::UInteger destinationLevel, MTL::Origin destinationOrigin, MTL::BlitOption options) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(copyFromBuffer_sourceOffset_sourceBytesPerRow_sourceBytesPerImage_sourceSize_toTexture_destinationSlice_destinationLevel_destinationOrigin_options_), sourceBuffer, sourceOffset, sourceBytesPerRow, sourceBytesPerImage, sourceSize, destinationTexture, destinationSlice, destinationLevel, destinationOrigin, options); -} - -_MTL_INLINE void MTL::BlitCommandEncoder::copyFromTexture(const MTL::Texture* sourceTexture, NS::UInteger sourceSlice, NS::UInteger sourceLevel, MTL::Origin sourceOrigin, MTL::Size sourceSize, const MTL::Buffer* destinationBuffer, NS::UInteger destinationOffset, NS::UInteger destinationBytesPerRow, NS::UInteger destinationBytesPerImage) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(copyFromTexture_sourceSlice_sourceLevel_sourceOrigin_sourceSize_toBuffer_destinationOffset_destinationBytesPerRow_destinationBytesPerImage_), sourceTexture, sourceSlice, sourceLevel, sourceOrigin, sourceSize, destinationBuffer, destinationOffset, destinationBytesPerRow, destinationBytesPerImage); -} - -_MTL_INLINE void MTL::BlitCommandEncoder::copyFromTexture(const MTL::Texture* sourceTexture, NS::UInteger sourceSlice, NS::UInteger sourceLevel, MTL::Origin sourceOrigin, MTL::Size sourceSize, const MTL::Buffer* destinationBuffer, NS::UInteger destinationOffset, NS::UInteger destinationBytesPerRow, NS::UInteger destinationBytesPerImage, MTL::BlitOption options) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(copyFromTexture_sourceSlice_sourceLevel_sourceOrigin_sourceSize_toBuffer_destinationOffset_destinationBytesPerRow_destinationBytesPerImage_options_), sourceTexture, sourceSlice, sourceLevel, sourceOrigin, sourceSize, destinationBuffer, destinationOffset, destinationBytesPerRow, destinationBytesPerImage, options); -} - -_MTL_INLINE void MTL::BlitCommandEncoder::generateMipmaps(const MTL::Texture* texture) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(generateMipmapsForTexture_), texture); -} - -_MTL_INLINE void MTL::BlitCommandEncoder::fillBuffer(const MTL::Buffer* buffer, NS::Range range, uint8_t value) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(fillBuffer_range_value_), buffer, range, value); -} - -_MTL_INLINE void MTL::BlitCommandEncoder::copyFromTexture(const MTL::Texture* sourceTexture, NS::UInteger sourceSlice, NS::UInteger sourceLevel, const MTL::Texture* destinationTexture, NS::UInteger destinationSlice, NS::UInteger destinationLevel, NS::UInteger sliceCount, NS::UInteger levelCount) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(copyFromTexture_sourceSlice_sourceLevel_toTexture_destinationSlice_destinationLevel_sliceCount_levelCount_), sourceTexture, sourceSlice, sourceLevel, destinationTexture, destinationSlice, destinationLevel, sliceCount, levelCount); -} - -_MTL_INLINE void MTL::BlitCommandEncoder::copyFromTexture(const MTL::Texture* sourceTexture, const MTL::Texture* destinationTexture) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(copyFromTexture_toTexture_), sourceTexture, destinationTexture); -} - -_MTL_INLINE void MTL::BlitCommandEncoder::copyFromBuffer(const MTL::Buffer* sourceBuffer, NS::UInteger sourceOffset, const MTL::Buffer* destinationBuffer, NS::UInteger destinationOffset, NS::UInteger size) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(copyFromBuffer_sourceOffset_toBuffer_destinationOffset_size_), sourceBuffer, sourceOffset, destinationBuffer, destinationOffset, size); -} - -_MTL_INLINE void MTL::BlitCommandEncoder::updateFence(const MTL::Fence* fence) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(updateFence_), fence); -} - -_MTL_INLINE void MTL::BlitCommandEncoder::waitForFence(const MTL::Fence* fence) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(waitForFence_), fence); -} - -_MTL_INLINE void MTL::BlitCommandEncoder::getTextureAccessCounters(const MTL::Texture* texture, MTL::Region region, NS::UInteger mipLevel, NS::UInteger slice, bool resetCounters, const MTL::Buffer* countersBuffer, NS::UInteger countersBufferOffset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(getTextureAccessCounters_region_mipLevel_slice_resetCounters_countersBuffer_countersBufferOffset_), texture, region, mipLevel, slice, resetCounters, countersBuffer, countersBufferOffset); -} - -_MTL_INLINE void MTL::BlitCommandEncoder::resetTextureAccessCounters(const MTL::Texture* texture, MTL::Region region, NS::UInteger mipLevel, NS::UInteger slice) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(resetTextureAccessCounters_region_mipLevel_slice_), texture, region, mipLevel, slice); -} - -_MTL_INLINE void MTL::BlitCommandEncoder::optimizeContentsForGPUAccess(const MTL::Texture* texture) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(optimizeContentsForGPUAccess_), texture); -} - -_MTL_INLINE void MTL::BlitCommandEncoder::optimizeContentsForGPUAccess(const MTL::Texture* texture, NS::UInteger slice, NS::UInteger level) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(optimizeContentsForGPUAccess_slice_level_), texture, slice, level); -} - -_MTL_INLINE void MTL::BlitCommandEncoder::optimizeContentsForCPUAccess(const MTL::Texture* texture) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(optimizeContentsForCPUAccess_), texture); -} - -_MTL_INLINE void MTL::BlitCommandEncoder::optimizeContentsForCPUAccess(const MTL::Texture* texture, NS::UInteger slice, NS::UInteger level) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(optimizeContentsForCPUAccess_slice_level_), texture, slice, level); -} - -_MTL_INLINE void MTL::BlitCommandEncoder::resetCommandsInBuffer(const MTL::IndirectCommandBuffer* buffer, NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(resetCommandsInBuffer_withRange_), buffer, range); -} - -_MTL_INLINE void MTL::BlitCommandEncoder::copyIndirectCommandBuffer(const MTL::IndirectCommandBuffer* source, NS::Range sourceRange, const MTL::IndirectCommandBuffer* destination, NS::UInteger destinationIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(copyIndirectCommandBuffer_sourceRange_destination_destinationIndex_), source, sourceRange, destination, destinationIndex); -} - -_MTL_INLINE void MTL::BlitCommandEncoder::optimizeIndirectCommandBuffer(const MTL::IndirectCommandBuffer* indirectCommandBuffer, NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(optimizeIndirectCommandBuffer_withRange_), indirectCommandBuffer, range); -} - -_MTL_INLINE void MTL::BlitCommandEncoder::sampleCountersInBuffer(const MTL::CounterSampleBuffer* sampleBuffer, NS::UInteger sampleIndex, bool barrier) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(sampleCountersInBuffer_atSampleIndex_withBarrier_), sampleBuffer, sampleIndex, barrier); -} - -_MTL_INLINE void MTL::BlitCommandEncoder::resolveCounters(const MTL::CounterSampleBuffer* sampleBuffer, NS::Range range, const MTL::Buffer* destinationBuffer, NS::UInteger destinationOffset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(resolveCounters_inRange_destinationBuffer_destinationOffset_), sampleBuffer, range, destinationBuffer, destinationOffset); -} - -#pragma once - -namespace MTL -{ -class BlitPassSampleBufferAttachmentDescriptor : public NS::Copying -{ -public: - static class BlitPassSampleBufferAttachmentDescriptor* alloc(); - - class BlitPassSampleBufferAttachmentDescriptor* init(); - - class CounterSampleBuffer* sampleBuffer() const; - void setSampleBuffer(const class CounterSampleBuffer* sampleBuffer); - - NS::UInteger startOfEncoderSampleIndex() const; - void setStartOfEncoderSampleIndex(NS::UInteger startOfEncoderSampleIndex); - - NS::UInteger endOfEncoderSampleIndex() const; - void setEndOfEncoderSampleIndex(NS::UInteger endOfEncoderSampleIndex); -}; - -class BlitPassSampleBufferAttachmentDescriptorArray : public NS::Referencing -{ -public: - static class BlitPassSampleBufferAttachmentDescriptorArray* alloc(); - - class BlitPassSampleBufferAttachmentDescriptorArray* init(); - - class BlitPassSampleBufferAttachmentDescriptor* object(NS::UInteger attachmentIndex); - - void setObject(const class BlitPassSampleBufferAttachmentDescriptor* attachment, NS::UInteger attachmentIndex); -}; - -class BlitPassDescriptor : public NS::Copying -{ -public: - static class BlitPassDescriptor* alloc(); - - class BlitPassDescriptor* init(); - - static class BlitPassDescriptor* blitPassDescriptor(); - - class BlitPassSampleBufferAttachmentDescriptorArray* sampleBufferAttachments() const; -}; - -} - -_MTL_INLINE MTL::BlitPassSampleBufferAttachmentDescriptor* MTL::BlitPassSampleBufferAttachmentDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLBlitPassSampleBufferAttachmentDescriptor)); -} - -_MTL_INLINE MTL::BlitPassSampleBufferAttachmentDescriptor* MTL::BlitPassSampleBufferAttachmentDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::CounterSampleBuffer* MTL::BlitPassSampleBufferAttachmentDescriptor::sampleBuffer() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(sampleBuffer)); -} - -_MTL_INLINE void MTL::BlitPassSampleBufferAttachmentDescriptor::setSampleBuffer(const MTL::CounterSampleBuffer* sampleBuffer) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSampleBuffer_), sampleBuffer); -} - -_MTL_INLINE NS::UInteger MTL::BlitPassSampleBufferAttachmentDescriptor::startOfEncoderSampleIndex() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(startOfEncoderSampleIndex)); -} - -_MTL_INLINE void MTL::BlitPassSampleBufferAttachmentDescriptor::setStartOfEncoderSampleIndex(NS::UInteger startOfEncoderSampleIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStartOfEncoderSampleIndex_), startOfEncoderSampleIndex); -} - -_MTL_INLINE NS::UInteger MTL::BlitPassSampleBufferAttachmentDescriptor::endOfEncoderSampleIndex() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(endOfEncoderSampleIndex)); -} - -_MTL_INLINE void MTL::BlitPassSampleBufferAttachmentDescriptor::setEndOfEncoderSampleIndex(NS::UInteger endOfEncoderSampleIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setEndOfEncoderSampleIndex_), endOfEncoderSampleIndex); -} - -_MTL_INLINE MTL::BlitPassSampleBufferAttachmentDescriptorArray* MTL::BlitPassSampleBufferAttachmentDescriptorArray::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLBlitPassSampleBufferAttachmentDescriptorArray)); -} - -_MTL_INLINE MTL::BlitPassSampleBufferAttachmentDescriptorArray* MTL::BlitPassSampleBufferAttachmentDescriptorArray::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::BlitPassSampleBufferAttachmentDescriptor* MTL::BlitPassSampleBufferAttachmentDescriptorArray::object(NS::UInteger attachmentIndex) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(objectAtIndexedSubscript_), attachmentIndex); -} - -_MTL_INLINE void MTL::BlitPassSampleBufferAttachmentDescriptorArray::setObject(const MTL::BlitPassSampleBufferAttachmentDescriptor* attachment, NS::UInteger attachmentIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setObject_atIndexedSubscript_), attachment, attachmentIndex); -} - -_MTL_INLINE MTL::BlitPassDescriptor* MTL::BlitPassDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLBlitPassDescriptor)); -} - -_MTL_INLINE MTL::BlitPassDescriptor* MTL::BlitPassDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::BlitPassDescriptor* MTL::BlitPassDescriptor::blitPassDescriptor() -{ - return Object::sendMessage(_MTL_PRIVATE_CLS(MTLBlitPassDescriptor), _MTL_PRIVATE_SEL(blitPassDescriptor)); -} - -_MTL_INLINE MTL::BlitPassSampleBufferAttachmentDescriptorArray* MTL::BlitPassDescriptor::sampleBufferAttachments() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(sampleBufferAttachments)); -} - -#pragma once - -namespace MTL -{ -class Buffer : public NS::Referencing -{ -public: - NS::UInteger length() const; - - void* contents(); - - void didModifyRange(NS::Range range); - - class Texture* newTexture(const class TextureDescriptor* descriptor, NS::UInteger offset, NS::UInteger bytesPerRow); - - void addDebugMarker(const NS::String* marker, NS::Range range); - - void removeAllDebugMarkers(); - - class Buffer* remoteStorageBuffer() const; - - class Buffer* newRemoteBufferViewForDevice(const class Device* device); - - uint64_t gpuAddress() const; -}; - -} - -_MTL_INLINE NS::UInteger MTL::Buffer::length() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(length)); -} - -_MTL_INLINE void* MTL::Buffer::contents() -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(contents)); -} - -_MTL_INLINE void MTL::Buffer::didModifyRange(NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(didModifyRange_), range); -} - -_MTL_INLINE MTL::Texture* MTL::Buffer::newTexture(const MTL::TextureDescriptor* descriptor, NS::UInteger offset, NS::UInteger bytesPerRow) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newTextureWithDescriptor_offset_bytesPerRow_), descriptor, offset, bytesPerRow); -} - -_MTL_INLINE void MTL::Buffer::addDebugMarker(const NS::String* marker, NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(addDebugMarker_range_), marker, range); -} - -_MTL_INLINE void MTL::Buffer::removeAllDebugMarkers() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(removeAllDebugMarkers)); -} - -_MTL_INLINE MTL::Buffer* MTL::Buffer::remoteStorageBuffer() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(remoteStorageBuffer)); -} - -_MTL_INLINE MTL::Buffer* MTL::Buffer::newRemoteBufferViewForDevice(const MTL::Device* device) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newRemoteBufferViewForDevice_), device); -} - -_MTL_INLINE uint64_t MTL::Buffer::gpuAddress() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(gpuAddress)); -} - -#pragma once - -namespace MTL -{ -_MTL_ENUM(NS::Integer, CaptureError) { - CaptureErrorNotSupported = 1, - CaptureErrorAlreadyCapturing = 2, - CaptureErrorInvalidDescriptor = 3, -}; - -_MTL_ENUM(NS::Integer, CaptureDestination) { - CaptureDestinationDeveloperTools = 1, - CaptureDestinationGPUTraceDocument = 2, -}; - -class CaptureDescriptor : public NS::Copying -{ -public: - static class CaptureDescriptor* alloc(); - - class CaptureDescriptor* init(); - - id captureObject() const; - void setCaptureObject(id captureObject); - - MTL::CaptureDestination destination() const; - void setDestination(MTL::CaptureDestination destination); - - NS::URL* outputURL() const; - void setOutputURL(const NS::URL* outputURL); -}; - -class CaptureManager : public NS::Referencing -{ -public: - static class CaptureManager* alloc(); - - static class CaptureManager* sharedCaptureManager(); - - MTL::CaptureManager* init(); - - class CaptureScope* newCaptureScope(const class Device* device); - - class CaptureScope* newCaptureScope(const class CommandQueue* commandQueue); - - bool supportsDestination(MTL::CaptureDestination destination); - - bool startCapture(const class CaptureDescriptor* descriptor, NS::Error** error); - - void startCapture(const class Device* device); - - void startCapture(const class CommandQueue* commandQueue); - - void startCapture(const class CaptureScope* captureScope); - - void stopCapture(); - - class CaptureScope* defaultCaptureScope() const; - void setDefaultCaptureScope(const class CaptureScope* defaultCaptureScope); - - bool isCapturing() const; -}; - -} - -_MTL_INLINE MTL::CaptureDescriptor* MTL::CaptureDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLCaptureDescriptor)); -} - -_MTL_INLINE MTL::CaptureDescriptor* MTL::CaptureDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE id MTL::CaptureDescriptor::captureObject() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(captureObject)); -} - -_MTL_INLINE void MTL::CaptureDescriptor::setCaptureObject(id captureObject) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setCaptureObject_), captureObject); -} - -_MTL_INLINE MTL::CaptureDestination MTL::CaptureDescriptor::destination() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(destination)); -} - -_MTL_INLINE void MTL::CaptureDescriptor::setDestination(MTL::CaptureDestination destination) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setDestination_), destination); -} - -_MTL_INLINE NS::URL* MTL::CaptureDescriptor::outputURL() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(outputURL)); -} - -_MTL_INLINE void MTL::CaptureDescriptor::setOutputURL(const NS::URL* outputURL) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setOutputURL_), outputURL); -} - -_MTL_INLINE MTL::CaptureManager* MTL::CaptureManager::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLCaptureManager)); -} - -_MTL_INLINE MTL::CaptureManager* MTL::CaptureManager::sharedCaptureManager() -{ - return Object::sendMessage(_MTL_PRIVATE_CLS(MTLCaptureManager), _MTL_PRIVATE_SEL(sharedCaptureManager)); -} - -_MTL_INLINE MTL::CaptureManager* MTL::CaptureManager::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::CaptureScope* MTL::CaptureManager::newCaptureScope(const MTL::Device* device) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newCaptureScopeWithDevice_), device); -} - -_MTL_INLINE MTL::CaptureScope* MTL::CaptureManager::newCaptureScope(const MTL::CommandQueue* commandQueue) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newCaptureScopeWithCommandQueue_), commandQueue); -} - -_MTL_INLINE bool MTL::CaptureManager::supportsDestination(MTL::CaptureDestination destination) -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(supportsDestination_), destination); -} - -_MTL_INLINE bool MTL::CaptureManager::startCapture(const MTL::CaptureDescriptor* descriptor, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(startCaptureWithDescriptor_error_), descriptor, error); -} - -_MTL_INLINE void MTL::CaptureManager::startCapture(const MTL::Device* device) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(startCaptureWithDevice_), device); -} - -_MTL_INLINE void MTL::CaptureManager::startCapture(const MTL::CommandQueue* commandQueue) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(startCaptureWithCommandQueue_), commandQueue); -} - -_MTL_INLINE void MTL::CaptureManager::startCapture(const MTL::CaptureScope* captureScope) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(startCaptureWithScope_), captureScope); -} - -_MTL_INLINE void MTL::CaptureManager::stopCapture() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(stopCapture)); -} - -_MTL_INLINE MTL::CaptureScope* MTL::CaptureManager::defaultCaptureScope() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(defaultCaptureScope)); -} - -_MTL_INLINE void MTL::CaptureManager::setDefaultCaptureScope(const MTL::CaptureScope* defaultCaptureScope) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setDefaultCaptureScope_), defaultCaptureScope); -} - -_MTL_INLINE bool MTL::CaptureManager::isCapturing() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(isCapturing)); -} - -namespace MTL -{ -class CaptureScope : public NS::Referencing -{ -public: - class Device* device() const; - - NS::String* label() const; - void setLabel(const NS::String* pLabel); - - class CommandQueue* commandQueue() const; - - void beginScope(); - void endScope(); -}; -} - -_MTL_INLINE MTL::Device* MTL::CaptureScope::device() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(device)); -} - -_MTL_INLINE NS::String* MTL::CaptureScope::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE void MTL::CaptureScope::setLabel(const NS::String* pLabel) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLabel_), pLabel); -} - -_MTL_INLINE MTL::CommandQueue* MTL::CaptureScope::commandQueue() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(commandQueue)); -} - -_MTL_INLINE void MTL::CaptureScope::beginScope() -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(beginScope)); -} - -_MTL_INLINE void MTL::CaptureScope::endScope() -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(endScope)); -} - -#pragma once - -#include - -namespace MTL -{ -_MTL_ENUM(NS::UInteger, CommandBufferStatus) { - CommandBufferStatusNotEnqueued = 0, - CommandBufferStatusEnqueued = 1, - CommandBufferStatusCommitted = 2, - CommandBufferStatusScheduled = 3, - CommandBufferStatusCompleted = 4, - CommandBufferStatusError = 5, -}; - -_MTL_ENUM(NS::UInteger, CommandBufferError) { - CommandBufferErrorNone = 0, - CommandBufferErrorInternal = 1, - CommandBufferErrorTimeout = 2, - CommandBufferErrorPageFault = 3, - CommandBufferErrorAccessRevoked = 4, - CommandBufferErrorBlacklisted = 4, - CommandBufferErrorNotPermitted = 7, - CommandBufferErrorOutOfMemory = 8, - CommandBufferErrorInvalidResource = 9, - CommandBufferErrorMemoryless = 10, - CommandBufferErrorDeviceRemoved = 11, - CommandBufferErrorStackOverflow = 12, -}; - -_MTL_OPTIONS(NS::UInteger, CommandBufferErrorOption) { - CommandBufferErrorOptionNone = 0, - CommandBufferErrorOptionEncoderExecutionStatus = 1, -}; - -_MTL_ENUM(NS::Integer, CommandEncoderErrorState) { - CommandEncoderErrorStateUnknown = 0, - CommandEncoderErrorStateCompleted = 1, - CommandEncoderErrorStateAffected = 2, - CommandEncoderErrorStatePending = 3, - CommandEncoderErrorStateFaulted = 4, -}; - -class CommandBufferDescriptor : public NS::Copying -{ -public: - static class CommandBufferDescriptor* alloc(); - - class CommandBufferDescriptor* init(); - - bool retainedReferences() const; - void setRetainedReferences(bool retainedReferences); - - MTL::CommandBufferErrorOption errorOptions() const; - void setErrorOptions(MTL::CommandBufferErrorOption errorOptions); -}; - -class CommandBufferEncoderInfo : public NS::Referencing -{ -public: - NS::String* label() const; - - NS::Array* debugSignposts() const; - - MTL::CommandEncoderErrorState errorState() const; -}; - -_MTL_ENUM(NS::UInteger, DispatchType) { - DispatchTypeSerial = 0, - DispatchTypeConcurrent = 1, -}; - -class CommandBuffer; - -using CommandBufferHandler = void (^)(CommandBuffer*); - -using HandlerFunction = std::function; - -class CommandBuffer : public NS::Referencing -{ -public: - void addScheduledHandler(const HandlerFunction& function); - - void addCompletedHandler(const HandlerFunction& function); - - class Device* device() const; - - class CommandQueue* commandQueue() const; - - bool retainedReferences() const; - - MTL::CommandBufferErrorOption errorOptions() const; - - NS::String* label() const; - void setLabel(const NS::String* label); - - CFTimeInterval kernelStartTime() const; - - CFTimeInterval kernelEndTime() const; - - class LogContainer* logs() const; - - CFTimeInterval GPUStartTime() const; - - CFTimeInterval GPUEndTime() const; - - void enqueue(); - - void commit(); - - void addScheduledHandler(const MTL::CommandBufferHandler block); - - void presentDrawable(const class Drawable* drawable); - - void presentDrawableAtTime(const class Drawable* drawable, CFTimeInterval presentationTime); - - void presentDrawableAfterMinimumDuration(const class Drawable* drawable, CFTimeInterval duration); - - void waitUntilScheduled(); - - void addCompletedHandler(const MTL::CommandBufferHandler block); - - void waitUntilCompleted(); - - MTL::CommandBufferStatus status() const; - - NS::Error* error() const; - - class BlitCommandEncoder* blitCommandEncoder(); - - class RenderCommandEncoder* renderCommandEncoder(const class RenderPassDescriptor* renderPassDescriptor); - - class ComputeCommandEncoder* computeCommandEncoder(const class ComputePassDescriptor* computePassDescriptor); - - class BlitCommandEncoder* blitCommandEncoder(const class BlitPassDescriptor* blitPassDescriptor); - - class ComputeCommandEncoder* computeCommandEncoder(); - - class ComputeCommandEncoder* computeCommandEncoder(MTL::DispatchType dispatchType); - - void encodeWait(const class Event* event, uint64_t value); - - void encodeSignalEvent(const class Event* event, uint64_t value); - - class ParallelRenderCommandEncoder* parallelRenderCommandEncoder(const class RenderPassDescriptor* renderPassDescriptor); - - class ResourceStateCommandEncoder* resourceStateCommandEncoder(); - - class ResourceStateCommandEncoder* resourceStateCommandEncoder(const class ResourceStatePassDescriptor* resourceStatePassDescriptor); - - class AccelerationStructureCommandEncoder* accelerationStructureCommandEncoder(); - - class AccelerationStructureCommandEncoder* accelerationStructureCommandEncoder(const class AccelerationStructurePassDescriptor* descriptor); - - void pushDebugGroup(const NS::String* string); - - void popDebugGroup(); -}; - -} - -_MTL_INLINE MTL::CommandBufferDescriptor* MTL::CommandBufferDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLCommandBufferDescriptor)); -} - -_MTL_INLINE MTL::CommandBufferDescriptor* MTL::CommandBufferDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE bool MTL::CommandBufferDescriptor::retainedReferences() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(retainedReferences)); -} - -_MTL_INLINE void MTL::CommandBufferDescriptor::setRetainedReferences(bool retainedReferences) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setRetainedReferences_), retainedReferences); -} - -_MTL_INLINE MTL::CommandBufferErrorOption MTL::CommandBufferDescriptor::errorOptions() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(errorOptions)); -} - -_MTL_INLINE void MTL::CommandBufferDescriptor::setErrorOptions(MTL::CommandBufferErrorOption errorOptions) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setErrorOptions_), errorOptions); -} - -_MTL_INLINE NS::String* MTL::CommandBufferEncoderInfo::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE NS::Array* MTL::CommandBufferEncoderInfo::debugSignposts() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(debugSignposts)); -} - -_MTL_INLINE MTL::CommandEncoderErrorState MTL::CommandBufferEncoderInfo::errorState() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(errorState)); -} - -_MTL_INLINE void MTL::CommandBuffer::addScheduledHandler(const HandlerFunction& function) -{ - __block HandlerFunction blockFunction = function; - - addScheduledHandler(^(MTL::CommandBuffer* pCommandBuffer) { blockFunction(pCommandBuffer); }); -} - -_MTL_INLINE void MTL::CommandBuffer::addCompletedHandler(const HandlerFunction& function) -{ - __block HandlerFunction blockFunction = function; - - addCompletedHandler(^(MTL::CommandBuffer* pCommandBuffer) { blockFunction(pCommandBuffer); }); -} - -_MTL_INLINE MTL::Device* MTL::CommandBuffer::device() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(device)); -} - -_MTL_INLINE MTL::CommandQueue* MTL::CommandBuffer::commandQueue() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(commandQueue)); -} - -_MTL_INLINE bool MTL::CommandBuffer::retainedReferences() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(retainedReferences)); -} - -_MTL_INLINE MTL::CommandBufferErrorOption MTL::CommandBuffer::errorOptions() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(errorOptions)); -} - -_MTL_INLINE NS::String* MTL::CommandBuffer::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE void MTL::CommandBuffer::setLabel(const NS::String* label) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLabel_), label); -} - -_MTL_INLINE CFTimeInterval MTL::CommandBuffer::kernelStartTime() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(kernelStartTime)); -} - -_MTL_INLINE CFTimeInterval MTL::CommandBuffer::kernelEndTime() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(kernelEndTime)); -} - -_MTL_INLINE MTL::LogContainer* MTL::CommandBuffer::logs() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(logs)); -} - -_MTL_INLINE CFTimeInterval MTL::CommandBuffer::GPUStartTime() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(GPUStartTime)); -} - -_MTL_INLINE CFTimeInterval MTL::CommandBuffer::GPUEndTime() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(GPUEndTime)); -} - -_MTL_INLINE void MTL::CommandBuffer::enqueue() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(enqueue)); -} - -_MTL_INLINE void MTL::CommandBuffer::commit() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(commit)); -} - -_MTL_INLINE void MTL::CommandBuffer::addScheduledHandler(const MTL::CommandBufferHandler block) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(addScheduledHandler_), block); -} - -_MTL_INLINE void MTL::CommandBuffer::presentDrawable(const MTL::Drawable* drawable) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(presentDrawable_), drawable); -} - -_MTL_INLINE void MTL::CommandBuffer::presentDrawableAtTime(const MTL::Drawable* drawable, CFTimeInterval presentationTime) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(presentDrawable_atTime_), drawable, presentationTime); -} - -_MTL_INLINE void MTL::CommandBuffer::presentDrawableAfterMinimumDuration(const MTL::Drawable* drawable, CFTimeInterval duration) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(presentDrawable_afterMinimumDuration_), drawable, duration); -} - -_MTL_INLINE void MTL::CommandBuffer::waitUntilScheduled() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(waitUntilScheduled)); -} - -_MTL_INLINE void MTL::CommandBuffer::addCompletedHandler(const MTL::CommandBufferHandler block) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(addCompletedHandler_), block); -} - -_MTL_INLINE void MTL::CommandBuffer::waitUntilCompleted() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(waitUntilCompleted)); -} - -_MTL_INLINE MTL::CommandBufferStatus MTL::CommandBuffer::status() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(status)); -} - -_MTL_INLINE NS::Error* MTL::CommandBuffer::error() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(error)); -} - -_MTL_INLINE MTL::BlitCommandEncoder* MTL::CommandBuffer::blitCommandEncoder() -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(blitCommandEncoder)); -} - -_MTL_INLINE MTL::RenderCommandEncoder* MTL::CommandBuffer::renderCommandEncoder(const MTL::RenderPassDescriptor* renderPassDescriptor) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(renderCommandEncoderWithDescriptor_), renderPassDescriptor); -} - -_MTL_INLINE MTL::ComputeCommandEncoder* MTL::CommandBuffer::computeCommandEncoder(const MTL::ComputePassDescriptor* computePassDescriptor) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(computeCommandEncoderWithDescriptor_), computePassDescriptor); -} - -_MTL_INLINE MTL::BlitCommandEncoder* MTL::CommandBuffer::blitCommandEncoder(const MTL::BlitPassDescriptor* blitPassDescriptor) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(blitCommandEncoderWithDescriptor_), blitPassDescriptor); -} - -_MTL_INLINE MTL::ComputeCommandEncoder* MTL::CommandBuffer::computeCommandEncoder() -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(computeCommandEncoder)); -} - -_MTL_INLINE MTL::ComputeCommandEncoder* MTL::CommandBuffer::computeCommandEncoder(MTL::DispatchType dispatchType) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(computeCommandEncoderWithDispatchType_), dispatchType); -} - -_MTL_INLINE void MTL::CommandBuffer::encodeWait(const MTL::Event* event, uint64_t value) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(encodeWaitForEvent_value_), event, value); -} - -_MTL_INLINE void MTL::CommandBuffer::encodeSignalEvent(const MTL::Event* event, uint64_t value) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(encodeSignalEvent_value_), event, value); -} - -_MTL_INLINE MTL::ParallelRenderCommandEncoder* MTL::CommandBuffer::parallelRenderCommandEncoder(const MTL::RenderPassDescriptor* renderPassDescriptor) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(parallelRenderCommandEncoderWithDescriptor_), renderPassDescriptor); -} - -_MTL_INLINE MTL::ResourceStateCommandEncoder* MTL::CommandBuffer::resourceStateCommandEncoder() -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(resourceStateCommandEncoder)); -} - -_MTL_INLINE MTL::ResourceStateCommandEncoder* MTL::CommandBuffer::resourceStateCommandEncoder(const MTL::ResourceStatePassDescriptor* resourceStatePassDescriptor) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(resourceStateCommandEncoderWithDescriptor_), resourceStatePassDescriptor); -} - -_MTL_INLINE MTL::AccelerationStructureCommandEncoder* MTL::CommandBuffer::accelerationStructureCommandEncoder() -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(accelerationStructureCommandEncoder)); -} - -_MTL_INLINE MTL::AccelerationStructureCommandEncoder* MTL::CommandBuffer::accelerationStructureCommandEncoder(const MTL::AccelerationStructurePassDescriptor* descriptor) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(accelerationStructureCommandEncoderWithDescriptor_), descriptor); -} - -_MTL_INLINE void MTL::CommandBuffer::pushDebugGroup(const NS::String* string) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(pushDebugGroup_), string); -} - -_MTL_INLINE void MTL::CommandBuffer::popDebugGroup() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(popDebugGroup)); -} - -#pragma once - -namespace MTL -{ -class CommandQueue : public NS::Referencing -{ -public: - NS::String* label() const; - void setLabel(const NS::String* label); - - class Device* device() const; - - class CommandBuffer* commandBuffer(); - - class CommandBuffer* commandBuffer(const class CommandBufferDescriptor* descriptor); - - class CommandBuffer* commandBufferWithUnretainedReferences(); - - void insertDebugCaptureBoundary(); -}; - -} - -_MTL_INLINE NS::String* MTL::CommandQueue::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE void MTL::CommandQueue::setLabel(const NS::String* label) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLabel_), label); -} - -_MTL_INLINE MTL::Device* MTL::CommandQueue::device() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(device)); -} - -_MTL_INLINE MTL::CommandBuffer* MTL::CommandQueue::commandBuffer() -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(commandBuffer)); -} - -_MTL_INLINE MTL::CommandBuffer* MTL::CommandQueue::commandBuffer(const MTL::CommandBufferDescriptor* descriptor) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(commandBufferWithDescriptor_), descriptor); -} - -_MTL_INLINE MTL::CommandBuffer* MTL::CommandQueue::commandBufferWithUnretainedReferences() -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(commandBufferWithUnretainedReferences)); -} - -_MTL_INLINE void MTL::CommandQueue::insertDebugCaptureBoundary() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(insertDebugCaptureBoundary)); -} - -#pragma once - -namespace MTL -{ -struct DispatchThreadgroupsIndirectArguments -{ - uint32_t threadgroupsPerGrid[3]; -} _MTL_PACKED; - -struct StageInRegionIndirectArguments -{ - uint32_t stageInOrigin[3]; - uint32_t stageInSize[3]; -} _MTL_PACKED; - -class ComputeCommandEncoder : public NS::Referencing -{ -public: - MTL::DispatchType dispatchType() const; - - void setComputePipelineState(const class ComputePipelineState* state); - - void setBytes(const void* bytes, NS::UInteger length, NS::UInteger index); - - void setBuffer(const class Buffer* buffer, NS::UInteger offset, NS::UInteger index); - - void setBufferOffset(NS::UInteger offset, NS::UInteger index); - - void setBuffers(const class Buffer* const buffers[], const NS::UInteger offsets[], NS::Range range); - - void setVisibleFunctionTable(const class VisibleFunctionTable* visibleFunctionTable, NS::UInteger bufferIndex); - - void setVisibleFunctionTables(const class VisibleFunctionTable* const visibleFunctionTables[], NS::Range range); - - void setIntersectionFunctionTable(const class IntersectionFunctionTable* intersectionFunctionTable, NS::UInteger bufferIndex); - - void setIntersectionFunctionTables(const class IntersectionFunctionTable* const intersectionFunctionTables[], NS::Range range); - - void setAccelerationStructure(const class AccelerationStructure* accelerationStructure, NS::UInteger bufferIndex); - - void setTexture(const class Texture* texture, NS::UInteger index); - - void setTextures(const class Texture* const textures[], NS::Range range); - - void setSamplerState(const class SamplerState* sampler, NS::UInteger index); - - void setSamplerStates(const class SamplerState* const samplers[], NS::Range range); - - void setSamplerState(const class SamplerState* sampler, float lodMinClamp, float lodMaxClamp, NS::UInteger index); - - void setSamplerStates(const class SamplerState* const samplers[], const float lodMinClamps[], const float lodMaxClamps[], NS::Range range); - - void setThreadgroupMemoryLength(NS::UInteger length, NS::UInteger index); - - void setImageblockWidth(NS::UInteger width, NS::UInteger height); - - void setStageInRegion(MTL::Region region); - - void setStageInRegion(const class Buffer* indirectBuffer, NS::UInteger indirectBufferOffset); - - void dispatchThreadgroups(MTL::Size threadgroupsPerGrid, MTL::Size threadsPerThreadgroup); - - void dispatchThreadgroups(const class Buffer* indirectBuffer, NS::UInteger indirectBufferOffset, MTL::Size threadsPerThreadgroup); - - void dispatchThreads(MTL::Size threadsPerGrid, MTL::Size threadsPerThreadgroup); - - void updateFence(const class Fence* fence); - - void waitForFence(const class Fence* fence); - - void useResource(const class Resource* resource, MTL::ResourceUsage usage); - - void useResources(const class Resource* const resources[], NS::UInteger count, MTL::ResourceUsage usage); - - void useHeap(const class Heap* heap); - - void useHeaps(const class Heap* const heaps[], NS::UInteger count); - - void executeCommandsInBuffer(const class IndirectCommandBuffer* indirectCommandBuffer, NS::Range executionRange); - - void executeCommandsInBuffer(const class IndirectCommandBuffer* indirectCommandbuffer, const class Buffer* indirectRangeBuffer, NS::UInteger indirectBufferOffset); - - void memoryBarrier(MTL::BarrierScope scope); - - void memoryBarrier(const class Resource* const resources[], NS::UInteger count); - - void sampleCountersInBuffer(const class CounterSampleBuffer* sampleBuffer, NS::UInteger sampleIndex, bool barrier); -}; - -} - -_MTL_INLINE MTL::DispatchType MTL::ComputeCommandEncoder::dispatchType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(dispatchType)); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::setComputePipelineState(const MTL::ComputePipelineState* state) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setComputePipelineState_), state); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::setBytes(const void* bytes, NS::UInteger length, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setBytes_length_atIndex_), bytes, length, index); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::setBuffer(const MTL::Buffer* buffer, NS::UInteger offset, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setBuffer_offset_atIndex_), buffer, offset, index); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::setBufferOffset(NS::UInteger offset, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setBufferOffset_atIndex_), offset, index); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::setBuffers(const MTL::Buffer* const buffers[], const NS::UInteger offsets[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setBuffers_offsets_withRange_), buffers, offsets, range); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::setVisibleFunctionTable(const MTL::VisibleFunctionTable* visibleFunctionTable, NS::UInteger bufferIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVisibleFunctionTable_atBufferIndex_), visibleFunctionTable, bufferIndex); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::setVisibleFunctionTables(const MTL::VisibleFunctionTable* const visibleFunctionTables[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVisibleFunctionTables_withBufferRange_), visibleFunctionTables, range); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::setIntersectionFunctionTable(const MTL::IntersectionFunctionTable* intersectionFunctionTable, NS::UInteger bufferIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setIntersectionFunctionTable_atBufferIndex_), intersectionFunctionTable, bufferIndex); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::setIntersectionFunctionTables(const MTL::IntersectionFunctionTable* const intersectionFunctionTables[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setIntersectionFunctionTables_withBufferRange_), intersectionFunctionTables, range); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::setAccelerationStructure(const MTL::AccelerationStructure* accelerationStructure, NS::UInteger bufferIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setAccelerationStructure_atBufferIndex_), accelerationStructure, bufferIndex); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::setTexture(const MTL::Texture* texture, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTexture_atIndex_), texture, index); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::setTextures(const MTL::Texture* const textures[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTextures_withRange_), textures, range); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::setSamplerState(const MTL::SamplerState* sampler, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSamplerState_atIndex_), sampler, index); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::setSamplerStates(const MTL::SamplerState* const samplers[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSamplerStates_withRange_), samplers, range); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::setSamplerState(const MTL::SamplerState* sampler, float lodMinClamp, float lodMaxClamp, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSamplerState_lodMinClamp_lodMaxClamp_atIndex_), sampler, lodMinClamp, lodMaxClamp, index); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::setSamplerStates(const MTL::SamplerState* const samplers[], const float lodMinClamps[], const float lodMaxClamps[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSamplerStates_lodMinClamps_lodMaxClamps_withRange_), samplers, lodMinClamps, lodMaxClamps, range); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::setThreadgroupMemoryLength(NS::UInteger length, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setThreadgroupMemoryLength_atIndex_), length, index); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::setImageblockWidth(NS::UInteger width, NS::UInteger height) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setImageblockWidth_height_), width, height); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::setStageInRegion(MTL::Region region) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStageInRegion_), region); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::setStageInRegion(const MTL::Buffer* indirectBuffer, NS::UInteger indirectBufferOffset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStageInRegionWithIndirectBuffer_indirectBufferOffset_), indirectBuffer, indirectBufferOffset); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::dispatchThreadgroups(MTL::Size threadgroupsPerGrid, MTL::Size threadsPerThreadgroup) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(dispatchThreadgroups_threadsPerThreadgroup_), threadgroupsPerGrid, threadsPerThreadgroup); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::dispatchThreadgroups(const MTL::Buffer* indirectBuffer, NS::UInteger indirectBufferOffset, MTL::Size threadsPerThreadgroup) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(dispatchThreadgroupsWithIndirectBuffer_indirectBufferOffset_threadsPerThreadgroup_), indirectBuffer, indirectBufferOffset, threadsPerThreadgroup); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::dispatchThreads(MTL::Size threadsPerGrid, MTL::Size threadsPerThreadgroup) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(dispatchThreads_threadsPerThreadgroup_), threadsPerGrid, threadsPerThreadgroup); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::updateFence(const MTL::Fence* fence) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(updateFence_), fence); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::waitForFence(const MTL::Fence* fence) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(waitForFence_), fence); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::useResource(const MTL::Resource* resource, MTL::ResourceUsage usage) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(useResource_usage_), resource, usage); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::useResources(const MTL::Resource* const resources[], NS::UInteger count, MTL::ResourceUsage usage) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(useResources_count_usage_), resources, count, usage); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::useHeap(const MTL::Heap* heap) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(useHeap_), heap); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::useHeaps(const MTL::Heap* const heaps[], NS::UInteger count) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(useHeaps_count_), heaps, count); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::executeCommandsInBuffer(const MTL::IndirectCommandBuffer* indirectCommandBuffer, NS::Range executionRange) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(executeCommandsInBuffer_withRange_), indirectCommandBuffer, executionRange); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::executeCommandsInBuffer(const MTL::IndirectCommandBuffer* indirectCommandbuffer, const MTL::Buffer* indirectRangeBuffer, NS::UInteger indirectBufferOffset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(executeCommandsInBuffer_indirectBuffer_indirectBufferOffset_), indirectCommandbuffer, indirectRangeBuffer, indirectBufferOffset); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::memoryBarrier(MTL::BarrierScope scope) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(memoryBarrierWithScope_), scope); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::memoryBarrier(const MTL::Resource* const resources[], NS::UInteger count) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(memoryBarrierWithResources_count_), resources, count); -} - -_MTL_INLINE void MTL::ComputeCommandEncoder::sampleCountersInBuffer(const MTL::CounterSampleBuffer* sampleBuffer, NS::UInteger sampleIndex, bool barrier) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(sampleCountersInBuffer_atSampleIndex_withBarrier_), sampleBuffer, sampleIndex, barrier); -} - -#pragma once - -namespace MTL -{ -class ComputePassSampleBufferAttachmentDescriptor : public NS::Copying -{ -public: - static class ComputePassSampleBufferAttachmentDescriptor* alloc(); - - class ComputePassSampleBufferAttachmentDescriptor* init(); - - class CounterSampleBuffer* sampleBuffer() const; - void setSampleBuffer(const class CounterSampleBuffer* sampleBuffer); - - NS::UInteger startOfEncoderSampleIndex() const; - void setStartOfEncoderSampleIndex(NS::UInteger startOfEncoderSampleIndex); - - NS::UInteger endOfEncoderSampleIndex() const; - void setEndOfEncoderSampleIndex(NS::UInteger endOfEncoderSampleIndex); -}; - -class ComputePassSampleBufferAttachmentDescriptorArray : public NS::Referencing -{ -public: - static class ComputePassSampleBufferAttachmentDescriptorArray* alloc(); - - class ComputePassSampleBufferAttachmentDescriptorArray* init(); - - class ComputePassSampleBufferAttachmentDescriptor* object(NS::UInteger attachmentIndex); - - void setObject(const class ComputePassSampleBufferAttachmentDescriptor* attachment, NS::UInteger attachmentIndex); -}; - -class ComputePassDescriptor : public NS::Copying -{ -public: - static class ComputePassDescriptor* alloc(); - - class ComputePassDescriptor* init(); - - static class ComputePassDescriptor* computePassDescriptor(); - - MTL::DispatchType dispatchType() const; - void setDispatchType(MTL::DispatchType dispatchType); - - class ComputePassSampleBufferAttachmentDescriptorArray* sampleBufferAttachments() const; -}; - -} - -_MTL_INLINE MTL::ComputePassSampleBufferAttachmentDescriptor* MTL::ComputePassSampleBufferAttachmentDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLComputePassSampleBufferAttachmentDescriptor)); -} - -_MTL_INLINE MTL::ComputePassSampleBufferAttachmentDescriptor* MTL::ComputePassSampleBufferAttachmentDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::CounterSampleBuffer* MTL::ComputePassSampleBufferAttachmentDescriptor::sampleBuffer() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(sampleBuffer)); -} - -_MTL_INLINE void MTL::ComputePassSampleBufferAttachmentDescriptor::setSampleBuffer(const MTL::CounterSampleBuffer* sampleBuffer) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSampleBuffer_), sampleBuffer); -} - -_MTL_INLINE NS::UInteger MTL::ComputePassSampleBufferAttachmentDescriptor::startOfEncoderSampleIndex() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(startOfEncoderSampleIndex)); -} - -_MTL_INLINE void MTL::ComputePassSampleBufferAttachmentDescriptor::setStartOfEncoderSampleIndex(NS::UInteger startOfEncoderSampleIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStartOfEncoderSampleIndex_), startOfEncoderSampleIndex); -} - -_MTL_INLINE NS::UInteger MTL::ComputePassSampleBufferAttachmentDescriptor::endOfEncoderSampleIndex() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(endOfEncoderSampleIndex)); -} - -_MTL_INLINE void MTL::ComputePassSampleBufferAttachmentDescriptor::setEndOfEncoderSampleIndex(NS::UInteger endOfEncoderSampleIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setEndOfEncoderSampleIndex_), endOfEncoderSampleIndex); -} - -_MTL_INLINE MTL::ComputePassSampleBufferAttachmentDescriptorArray* MTL::ComputePassSampleBufferAttachmentDescriptorArray::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLComputePassSampleBufferAttachmentDescriptorArray)); -} - -_MTL_INLINE MTL::ComputePassSampleBufferAttachmentDescriptorArray* MTL::ComputePassSampleBufferAttachmentDescriptorArray::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::ComputePassSampleBufferAttachmentDescriptor* MTL::ComputePassSampleBufferAttachmentDescriptorArray::object(NS::UInteger attachmentIndex) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(objectAtIndexedSubscript_), attachmentIndex); -} - -_MTL_INLINE void MTL::ComputePassSampleBufferAttachmentDescriptorArray::setObject(const MTL::ComputePassSampleBufferAttachmentDescriptor* attachment, NS::UInteger attachmentIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setObject_atIndexedSubscript_), attachment, attachmentIndex); -} - -_MTL_INLINE MTL::ComputePassDescriptor* MTL::ComputePassDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLComputePassDescriptor)); -} - -_MTL_INLINE MTL::ComputePassDescriptor* MTL::ComputePassDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::ComputePassDescriptor* MTL::ComputePassDescriptor::computePassDescriptor() -{ - return Object::sendMessage(_MTL_PRIVATE_CLS(MTLComputePassDescriptor), _MTL_PRIVATE_SEL(computePassDescriptor)); -} - -_MTL_INLINE MTL::DispatchType MTL::ComputePassDescriptor::dispatchType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(dispatchType)); -} - -_MTL_INLINE void MTL::ComputePassDescriptor::setDispatchType(MTL::DispatchType dispatchType) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setDispatchType_), dispatchType); -} - -_MTL_INLINE MTL::ComputePassSampleBufferAttachmentDescriptorArray* MTL::ComputePassDescriptor::sampleBufferAttachments() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(sampleBufferAttachments)); -} - -#pragma once - -namespace MTL -{ -class ComputePipelineReflection : public NS::Referencing -{ -public: - static class ComputePipelineReflection* alloc(); - - class ComputePipelineReflection* init(); - - NS::Array* bindings() const; - - NS::Array* arguments() const; -}; - -class ComputePipelineDescriptor : public NS::Copying -{ -public: - static class ComputePipelineDescriptor* alloc(); - - class ComputePipelineDescriptor* init(); - - NS::String* label() const; - void setLabel(const NS::String* label); - - class Function* computeFunction() const; - void setComputeFunction(const class Function* computeFunction); - - bool threadGroupSizeIsMultipleOfThreadExecutionWidth() const; - void setThreadGroupSizeIsMultipleOfThreadExecutionWidth(bool threadGroupSizeIsMultipleOfThreadExecutionWidth); - - NS::UInteger maxTotalThreadsPerThreadgroup() const; - void setMaxTotalThreadsPerThreadgroup(NS::UInteger maxTotalThreadsPerThreadgroup); - - class StageInputOutputDescriptor* stageInputDescriptor() const; - void setStageInputDescriptor(const class StageInputOutputDescriptor* stageInputDescriptor); - - class PipelineBufferDescriptorArray* buffers() const; - - bool supportIndirectCommandBuffers() const; - void setSupportIndirectCommandBuffers(bool supportIndirectCommandBuffers); - - NS::Array* insertLibraries() const; - void setInsertLibraries(const NS::Array* insertLibraries); - - NS::Array* preloadedLibraries() const; - void setPreloadedLibraries(const NS::Array* preloadedLibraries); - - NS::Array* binaryArchives() const; - void setBinaryArchives(const NS::Array* binaryArchives); - - void reset(); - - class LinkedFunctions* linkedFunctions() const; - void setLinkedFunctions(const class LinkedFunctions* linkedFunctions); - - bool supportAddingBinaryFunctions() const; - void setSupportAddingBinaryFunctions(bool supportAddingBinaryFunctions); - - NS::UInteger maxCallStackDepth() const; - void setMaxCallStackDepth(NS::UInteger maxCallStackDepth); -}; - -class ComputePipelineState : public NS::Referencing -{ -public: - NS::String* label() const; - - class Device* device() const; - - NS::UInteger maxTotalThreadsPerThreadgroup() const; - - NS::UInteger threadExecutionWidth() const; - - NS::UInteger staticThreadgroupMemoryLength() const; - - NS::UInteger imageblockMemoryLength(MTL::Size imageblockDimensions); - - bool supportIndirectCommandBuffers() const; - - MTL::ResourceID gpuResourceID() const; - - class FunctionHandle* functionHandle(const class Function* function); - - class ComputePipelineState* newComputePipelineState(const NS::Array* functions, NS::Error** error); - - class VisibleFunctionTable* newVisibleFunctionTable(const class VisibleFunctionTableDescriptor* descriptor); - - class IntersectionFunctionTable* newIntersectionFunctionTable(const class IntersectionFunctionTableDescriptor* descriptor); -}; - -} - -_MTL_INLINE MTL::ComputePipelineReflection* MTL::ComputePipelineReflection::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLComputePipelineReflection)); -} - -_MTL_INLINE MTL::ComputePipelineReflection* MTL::ComputePipelineReflection::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE NS::Array* MTL::ComputePipelineReflection::bindings() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(bindings)); -} - -_MTL_INLINE NS::Array* MTL::ComputePipelineReflection::arguments() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(arguments)); -} - -_MTL_INLINE MTL::ComputePipelineDescriptor* MTL::ComputePipelineDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLComputePipelineDescriptor)); -} - -_MTL_INLINE MTL::ComputePipelineDescriptor* MTL::ComputePipelineDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE NS::String* MTL::ComputePipelineDescriptor::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE void MTL::ComputePipelineDescriptor::setLabel(const NS::String* label) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLabel_), label); -} - -_MTL_INLINE MTL::Function* MTL::ComputePipelineDescriptor::computeFunction() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(computeFunction)); -} - -_MTL_INLINE void MTL::ComputePipelineDescriptor::setComputeFunction(const MTL::Function* computeFunction) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setComputeFunction_), computeFunction); -} - -_MTL_INLINE bool MTL::ComputePipelineDescriptor::threadGroupSizeIsMultipleOfThreadExecutionWidth() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(threadGroupSizeIsMultipleOfThreadExecutionWidth)); -} - -_MTL_INLINE void MTL::ComputePipelineDescriptor::setThreadGroupSizeIsMultipleOfThreadExecutionWidth(bool threadGroupSizeIsMultipleOfThreadExecutionWidth) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setThreadGroupSizeIsMultipleOfThreadExecutionWidth_), threadGroupSizeIsMultipleOfThreadExecutionWidth); -} - -_MTL_INLINE NS::UInteger MTL::ComputePipelineDescriptor::maxTotalThreadsPerThreadgroup() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(maxTotalThreadsPerThreadgroup)); -} - -_MTL_INLINE void MTL::ComputePipelineDescriptor::setMaxTotalThreadsPerThreadgroup(NS::UInteger maxTotalThreadsPerThreadgroup) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMaxTotalThreadsPerThreadgroup_), maxTotalThreadsPerThreadgroup); -} - -_MTL_INLINE MTL::StageInputOutputDescriptor* MTL::ComputePipelineDescriptor::stageInputDescriptor() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(stageInputDescriptor)); -} - -_MTL_INLINE void MTL::ComputePipelineDescriptor::setStageInputDescriptor(const MTL::StageInputOutputDescriptor* stageInputDescriptor) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStageInputDescriptor_), stageInputDescriptor); -} - -_MTL_INLINE MTL::PipelineBufferDescriptorArray* MTL::ComputePipelineDescriptor::buffers() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(buffers)); -} - -_MTL_INLINE bool MTL::ComputePipelineDescriptor::supportIndirectCommandBuffers() const -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(supportIndirectCommandBuffers)); -} - -_MTL_INLINE void MTL::ComputePipelineDescriptor::setSupportIndirectCommandBuffers(bool supportIndirectCommandBuffers) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSupportIndirectCommandBuffers_), supportIndirectCommandBuffers); -} - -_MTL_INLINE NS::Array* MTL::ComputePipelineDescriptor::insertLibraries() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(insertLibraries)); -} - -_MTL_INLINE void MTL::ComputePipelineDescriptor::setInsertLibraries(const NS::Array* insertLibraries) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setInsertLibraries_), insertLibraries); -} - -_MTL_INLINE NS::Array* MTL::ComputePipelineDescriptor::preloadedLibraries() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(preloadedLibraries)); -} - -_MTL_INLINE void MTL::ComputePipelineDescriptor::setPreloadedLibraries(const NS::Array* preloadedLibraries) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setPreloadedLibraries_), preloadedLibraries); -} - -_MTL_INLINE NS::Array* MTL::ComputePipelineDescriptor::binaryArchives() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(binaryArchives)); -} - -_MTL_INLINE void MTL::ComputePipelineDescriptor::setBinaryArchives(const NS::Array* binaryArchives) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setBinaryArchives_), binaryArchives); -} - -_MTL_INLINE void MTL::ComputePipelineDescriptor::reset() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(reset)); -} - -_MTL_INLINE MTL::LinkedFunctions* MTL::ComputePipelineDescriptor::linkedFunctions() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(linkedFunctions)); -} - -_MTL_INLINE void MTL::ComputePipelineDescriptor::setLinkedFunctions(const MTL::LinkedFunctions* linkedFunctions) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLinkedFunctions_), linkedFunctions); -} - -_MTL_INLINE bool MTL::ComputePipelineDescriptor::supportAddingBinaryFunctions() const -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(supportAddingBinaryFunctions)); -} - -_MTL_INLINE void MTL::ComputePipelineDescriptor::setSupportAddingBinaryFunctions(bool supportAddingBinaryFunctions) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSupportAddingBinaryFunctions_), supportAddingBinaryFunctions); -} - -_MTL_INLINE NS::UInteger MTL::ComputePipelineDescriptor::maxCallStackDepth() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(maxCallStackDepth)); -} - -_MTL_INLINE void MTL::ComputePipelineDescriptor::setMaxCallStackDepth(NS::UInteger maxCallStackDepth) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMaxCallStackDepth_), maxCallStackDepth); -} - -_MTL_INLINE NS::String* MTL::ComputePipelineState::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE MTL::Device* MTL::ComputePipelineState::device() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(device)); -} - -_MTL_INLINE NS::UInteger MTL::ComputePipelineState::maxTotalThreadsPerThreadgroup() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(maxTotalThreadsPerThreadgroup)); -} - -_MTL_INLINE NS::UInteger MTL::ComputePipelineState::threadExecutionWidth() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(threadExecutionWidth)); -} - -_MTL_INLINE NS::UInteger MTL::ComputePipelineState::staticThreadgroupMemoryLength() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(staticThreadgroupMemoryLength)); -} - -_MTL_INLINE NS::UInteger MTL::ComputePipelineState::imageblockMemoryLength(MTL::Size imageblockDimensions) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(imageblockMemoryLengthForDimensions_), imageblockDimensions); -} - -_MTL_INLINE bool MTL::ComputePipelineState::supportIndirectCommandBuffers() const -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(supportIndirectCommandBuffers)); -} - -_MTL_INLINE MTL::ResourceID MTL::ComputePipelineState::gpuResourceID() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(gpuResourceID)); -} - -_MTL_INLINE MTL::FunctionHandle* MTL::ComputePipelineState::functionHandle(const MTL::Function* function) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(functionHandleWithFunction_), function); -} - -_MTL_INLINE MTL::ComputePipelineState* MTL::ComputePipelineState::newComputePipelineState(const NS::Array* functions, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newComputePipelineStateWithAdditionalBinaryFunctions_error_), functions, error); -} - -_MTL_INLINE MTL::VisibleFunctionTable* MTL::ComputePipelineState::newVisibleFunctionTable(const MTL::VisibleFunctionTableDescriptor* descriptor) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newVisibleFunctionTableWithDescriptor_), descriptor); -} - -_MTL_INLINE MTL::IntersectionFunctionTable* MTL::ComputePipelineState::newIntersectionFunctionTable(const MTL::IntersectionFunctionTableDescriptor* descriptor) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newIntersectionFunctionTableWithDescriptor_), descriptor); -} - -#pragma once - -namespace MTL -{ -struct CounterResultTimestamp -{ - uint64_t timestamp; -} _MTL_PACKED; - -struct CounterResultStageUtilization -{ - uint64_t totalCycles; - uint64_t vertexCycles; - uint64_t tessellationCycles; - uint64_t postTessellationVertexCycles; - uint64_t fragmentCycles; - uint64_t renderTargetCycles; -} _MTL_PACKED; - -struct CounterResultStatistic -{ - uint64_t tessellationInputPatches; - uint64_t vertexInvocations; - uint64_t postTessellationVertexInvocations; - uint64_t clipperInvocations; - uint64_t clipperPrimitivesOut; - uint64_t fragmentInvocations; - uint64_t fragmentsPassed; - uint64_t computeKernelInvocations; -} _MTL_PACKED; - -_MTL_CONST(NS::ErrorDomain, CounterErrorDomain); - -using CommonCounter = NS::String*; - -_MTL_CONST(CommonCounter, CommonCounterTimestamp); -_MTL_CONST(CommonCounter, CommonCounterTessellationInputPatches); -_MTL_CONST(CommonCounter, CommonCounterVertexInvocations); -_MTL_CONST(CommonCounter, CommonCounterPostTessellationVertexInvocations); -_MTL_CONST(CommonCounter, CommonCounterClipperInvocations); -_MTL_CONST(CommonCounter, CommonCounterClipperPrimitivesOut); -_MTL_CONST(CommonCounter, CommonCounterFragmentInvocations); -_MTL_CONST(CommonCounter, CommonCounterFragmentsPassed); -_MTL_CONST(CommonCounter, CommonCounterComputeKernelInvocations); -_MTL_CONST(CommonCounter, CommonCounterTotalCycles); -_MTL_CONST(CommonCounter, CommonCounterVertexCycles); -_MTL_CONST(CommonCounter, CommonCounterTessellationCycles); -_MTL_CONST(CommonCounter, CommonCounterPostTessellationVertexCycles); -_MTL_CONST(CommonCounter, CommonCounterFragmentCycles); -_MTL_CONST(CommonCounter, CommonCounterRenderTargetWriteCycles); - -using CommonCounterSet = NS::String*; - -_MTL_CONST(CommonCounterSet, CommonCounterSetTimestamp); -_MTL_CONST(CommonCounterSet, CommonCounterSetStageUtilization); -_MTL_CONST(CommonCounterSet, CommonCounterSetStatistic); - -class Counter : public NS::Referencing -{ -public: - NS::String* name() const; -}; - -class CounterSet : public NS::Referencing -{ -public: - NS::String* name() const; - - NS::Array* counters() const; -}; - -class CounterSampleBufferDescriptor : public NS::Copying -{ -public: - static class CounterSampleBufferDescriptor* alloc(); - - class CounterSampleBufferDescriptor* init(); - - class CounterSet* counterSet() const; - void setCounterSet(const class CounterSet* counterSet); - - NS::String* label() const; - void setLabel(const NS::String* label); - - MTL::StorageMode storageMode() const; - void setStorageMode(MTL::StorageMode storageMode); - - NS::UInteger sampleCount() const; - void setSampleCount(NS::UInteger sampleCount); -}; - -class CounterSampleBuffer : public NS::Referencing -{ -public: - class Device* device() const; - - NS::String* label() const; - - NS::UInteger sampleCount() const; - - NS::Data* resolveCounterRange(NS::Range range); -}; - -_MTL_ENUM(NS::Integer, CounterSampleBufferError) { - CounterSampleBufferErrorOutOfMemory = 0, - CounterSampleBufferErrorInvalid = 1, - CounterSampleBufferErrorInternal = 2, -}; - -} - -_MTL_PRIVATE_DEF_STR(NS::ErrorDomain, CounterErrorDomain); - -_MTL_PRIVATE_DEF_STR(MTL::CommonCounter, CommonCounterTimestamp); -_MTL_PRIVATE_DEF_STR(MTL::CommonCounter, CommonCounterTessellationInputPatches); -_MTL_PRIVATE_DEF_STR(MTL::CommonCounter, CommonCounterVertexInvocations); -_MTL_PRIVATE_DEF_STR(MTL::CommonCounter, CommonCounterPostTessellationVertexInvocations); -_MTL_PRIVATE_DEF_STR(MTL::CommonCounter, CommonCounterClipperInvocations); -_MTL_PRIVATE_DEF_STR(MTL::CommonCounter, CommonCounterClipperPrimitivesOut); -_MTL_PRIVATE_DEF_STR(MTL::CommonCounter, CommonCounterFragmentInvocations); -_MTL_PRIVATE_DEF_STR(MTL::CommonCounter, CommonCounterFragmentsPassed); -_MTL_PRIVATE_DEF_STR(MTL::CommonCounter, CommonCounterComputeKernelInvocations); -_MTL_PRIVATE_DEF_STR(MTL::CommonCounter, CommonCounterTotalCycles); -_MTL_PRIVATE_DEF_STR(MTL::CommonCounter, CommonCounterVertexCycles); -_MTL_PRIVATE_DEF_STR(MTL::CommonCounter, CommonCounterTessellationCycles); -_MTL_PRIVATE_DEF_STR(MTL::CommonCounter, CommonCounterPostTessellationVertexCycles); -_MTL_PRIVATE_DEF_STR(MTL::CommonCounter, CommonCounterFragmentCycles); -_MTL_PRIVATE_DEF_STR(MTL::CommonCounter, CommonCounterRenderTargetWriteCycles); - -_MTL_PRIVATE_DEF_STR(MTL::CommonCounterSet, CommonCounterSetTimestamp); -_MTL_PRIVATE_DEF_STR(MTL::CommonCounterSet, CommonCounterSetStageUtilization); -_MTL_PRIVATE_DEF_STR(MTL::CommonCounterSet, CommonCounterSetStatistic); - -_MTL_INLINE NS::String* MTL::Counter::name() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(name)); -} - -_MTL_INLINE NS::String* MTL::CounterSet::name() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(name)); -} - -_MTL_INLINE NS::Array* MTL::CounterSet::counters() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(counters)); -} - -_MTL_INLINE MTL::CounterSampleBufferDescriptor* MTL::CounterSampleBufferDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLCounterSampleBufferDescriptor)); -} - -_MTL_INLINE MTL::CounterSampleBufferDescriptor* MTL::CounterSampleBufferDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::CounterSet* MTL::CounterSampleBufferDescriptor::counterSet() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(counterSet)); -} - -_MTL_INLINE void MTL::CounterSampleBufferDescriptor::setCounterSet(const MTL::CounterSet* counterSet) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setCounterSet_), counterSet); -} - -_MTL_INLINE NS::String* MTL::CounterSampleBufferDescriptor::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE void MTL::CounterSampleBufferDescriptor::setLabel(const NS::String* label) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLabel_), label); -} - -_MTL_INLINE MTL::StorageMode MTL::CounterSampleBufferDescriptor::storageMode() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(storageMode)); -} - -_MTL_INLINE void MTL::CounterSampleBufferDescriptor::setStorageMode(MTL::StorageMode storageMode) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStorageMode_), storageMode); -} - -_MTL_INLINE NS::UInteger MTL::CounterSampleBufferDescriptor::sampleCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(sampleCount)); -} - -_MTL_INLINE void MTL::CounterSampleBufferDescriptor::setSampleCount(NS::UInteger sampleCount) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSampleCount_), sampleCount); -} - -_MTL_INLINE MTL::Device* MTL::CounterSampleBuffer::device() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(device)); -} - -_MTL_INLINE NS::String* MTL::CounterSampleBuffer::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE NS::UInteger MTL::CounterSampleBuffer::sampleCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(sampleCount)); -} - -_MTL_INLINE NS::Data* MTL::CounterSampleBuffer::resolveCounterRange(NS::Range range) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(resolveCounterRange_), range); -} - -#pragma once - -namespace MTL -{ -_MTL_ENUM(NS::UInteger, CompareFunction) { - CompareFunctionNever = 0, - CompareFunctionLess = 1, - CompareFunctionEqual = 2, - CompareFunctionLessEqual = 3, - CompareFunctionGreater = 4, - CompareFunctionNotEqual = 5, - CompareFunctionGreaterEqual = 6, - CompareFunctionAlways = 7, -}; - -_MTL_ENUM(NS::UInteger, StencilOperation) { - StencilOperationKeep = 0, - StencilOperationZero = 1, - StencilOperationReplace = 2, - StencilOperationIncrementClamp = 3, - StencilOperationDecrementClamp = 4, - StencilOperationInvert = 5, - StencilOperationIncrementWrap = 6, - StencilOperationDecrementWrap = 7, -}; - -class StencilDescriptor : public NS::Copying -{ -public: - static class StencilDescriptor* alloc(); - - class StencilDescriptor* init(); - - MTL::CompareFunction stencilCompareFunction() const; - void setStencilCompareFunction(MTL::CompareFunction stencilCompareFunction); - - MTL::StencilOperation stencilFailureOperation() const; - void setStencilFailureOperation(MTL::StencilOperation stencilFailureOperation); - - MTL::StencilOperation depthFailureOperation() const; - void setDepthFailureOperation(MTL::StencilOperation depthFailureOperation); - - MTL::StencilOperation depthStencilPassOperation() const; - void setDepthStencilPassOperation(MTL::StencilOperation depthStencilPassOperation); - - uint32_t readMask() const; - void setReadMask(uint32_t readMask); - - uint32_t writeMask() const; - void setWriteMask(uint32_t writeMask); -}; - -class DepthStencilDescriptor : public NS::Copying -{ -public: - static class DepthStencilDescriptor* alloc(); - - class DepthStencilDescriptor* init(); - - MTL::CompareFunction depthCompareFunction() const; - void setDepthCompareFunction(MTL::CompareFunction depthCompareFunction); - - bool depthWriteEnabled() const; - void setDepthWriteEnabled(bool depthWriteEnabled); - - class StencilDescriptor* frontFaceStencil() const; - void setFrontFaceStencil(const class StencilDescriptor* frontFaceStencil); - - class StencilDescriptor* backFaceStencil() const; - void setBackFaceStencil(const class StencilDescriptor* backFaceStencil); - - NS::String* label() const; - void setLabel(const NS::String* label); -}; - -class DepthStencilState : public NS::Referencing -{ -public: - NS::String* label() const; - - class Device* device() const; -}; - -} - -_MTL_INLINE MTL::StencilDescriptor* MTL::StencilDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLStencilDescriptor)); -} - -_MTL_INLINE MTL::StencilDescriptor* MTL::StencilDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::CompareFunction MTL::StencilDescriptor::stencilCompareFunction() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(stencilCompareFunction)); -} - -_MTL_INLINE void MTL::StencilDescriptor::setStencilCompareFunction(MTL::CompareFunction stencilCompareFunction) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStencilCompareFunction_), stencilCompareFunction); -} - -_MTL_INLINE MTL::StencilOperation MTL::StencilDescriptor::stencilFailureOperation() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(stencilFailureOperation)); -} - -_MTL_INLINE void MTL::StencilDescriptor::setStencilFailureOperation(MTL::StencilOperation stencilFailureOperation) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStencilFailureOperation_), stencilFailureOperation); -} - -_MTL_INLINE MTL::StencilOperation MTL::StencilDescriptor::depthFailureOperation() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(depthFailureOperation)); -} - -_MTL_INLINE void MTL::StencilDescriptor::setDepthFailureOperation(MTL::StencilOperation depthFailureOperation) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setDepthFailureOperation_), depthFailureOperation); -} - -_MTL_INLINE MTL::StencilOperation MTL::StencilDescriptor::depthStencilPassOperation() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(depthStencilPassOperation)); -} - -_MTL_INLINE void MTL::StencilDescriptor::setDepthStencilPassOperation(MTL::StencilOperation depthStencilPassOperation) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setDepthStencilPassOperation_), depthStencilPassOperation); -} - -_MTL_INLINE uint32_t MTL::StencilDescriptor::readMask() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(readMask)); -} - -_MTL_INLINE void MTL::StencilDescriptor::setReadMask(uint32_t readMask) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setReadMask_), readMask); -} - -_MTL_INLINE uint32_t MTL::StencilDescriptor::writeMask() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(writeMask)); -} - -_MTL_INLINE void MTL::StencilDescriptor::setWriteMask(uint32_t writeMask) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setWriteMask_), writeMask); -} - -_MTL_INLINE MTL::DepthStencilDescriptor* MTL::DepthStencilDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLDepthStencilDescriptor)); -} - -_MTL_INLINE MTL::DepthStencilDescriptor* MTL::DepthStencilDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::CompareFunction MTL::DepthStencilDescriptor::depthCompareFunction() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(depthCompareFunction)); -} - -_MTL_INLINE void MTL::DepthStencilDescriptor::setDepthCompareFunction(MTL::CompareFunction depthCompareFunction) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setDepthCompareFunction_), depthCompareFunction); -} - -_MTL_INLINE bool MTL::DepthStencilDescriptor::depthWriteEnabled() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(isDepthWriteEnabled)); -} - -_MTL_INLINE void MTL::DepthStencilDescriptor::setDepthWriteEnabled(bool depthWriteEnabled) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setDepthWriteEnabled_), depthWriteEnabled); -} - -_MTL_INLINE MTL::StencilDescriptor* MTL::DepthStencilDescriptor::frontFaceStencil() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(frontFaceStencil)); -} - -_MTL_INLINE void MTL::DepthStencilDescriptor::setFrontFaceStencil(const MTL::StencilDescriptor* frontFaceStencil) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFrontFaceStencil_), frontFaceStencil); -} - -_MTL_INLINE MTL::StencilDescriptor* MTL::DepthStencilDescriptor::backFaceStencil() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(backFaceStencil)); -} - -_MTL_INLINE void MTL::DepthStencilDescriptor::setBackFaceStencil(const MTL::StencilDescriptor* backFaceStencil) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setBackFaceStencil_), backFaceStencil); -} - -_MTL_INLINE NS::String* MTL::DepthStencilDescriptor::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE void MTL::DepthStencilDescriptor::setLabel(const NS::String* label) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLabel_), label); -} - -_MTL_INLINE NS::String* MTL::DepthStencilState::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE MTL::Device* MTL::DepthStencilState::device() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(device)); -} - -#pragma once - -#include -#include - -namespace MTL -{ -_MTL_ENUM(NS::Integer, IOCompressionMethod) { - IOCompressionMethodZlib = 0, - IOCompressionMethodLZFSE = 1, - IOCompressionMethodLZ4 = 2, - IOCompressionMethodLZMA = 3, - IOCompressionMethodLZBitmap = 4, -}; - -_MTL_ENUM(NS::UInteger, FeatureSet) { - FeatureSet_iOS_GPUFamily1_v1 = 0, - FeatureSet_iOS_GPUFamily2_v1 = 1, - FeatureSet_iOS_GPUFamily1_v2 = 2, - FeatureSet_iOS_GPUFamily2_v2 = 3, - FeatureSet_iOS_GPUFamily3_v1 = 4, - FeatureSet_iOS_GPUFamily1_v3 = 5, - FeatureSet_iOS_GPUFamily2_v3 = 6, - FeatureSet_iOS_GPUFamily3_v2 = 7, - FeatureSet_iOS_GPUFamily1_v4 = 8, - FeatureSet_iOS_GPUFamily2_v4 = 9, - FeatureSet_iOS_GPUFamily3_v3 = 10, - FeatureSet_iOS_GPUFamily4_v1 = 11, - FeatureSet_iOS_GPUFamily1_v5 = 12, - FeatureSet_iOS_GPUFamily2_v5 = 13, - FeatureSet_iOS_GPUFamily3_v4 = 14, - FeatureSet_iOS_GPUFamily4_v2 = 15, - FeatureSet_iOS_GPUFamily5_v1 = 16, - FeatureSet_macOS_GPUFamily1_v1 = 10000, - FeatureSet_OSX_GPUFamily1_v1 = 10000, - FeatureSet_macOS_GPUFamily1_v2 = 10001, - FeatureSet_OSX_GPUFamily1_v2 = 10001, - FeatureSet_OSX_ReadWriteTextureTier2 = 10002, - FeatureSet_macOS_ReadWriteTextureTier2 = 10002, - FeatureSet_macOS_GPUFamily1_v3 = 10003, - FeatureSet_macOS_GPUFamily1_v4 = 10004, - FeatureSet_macOS_GPUFamily2_v1 = 10005, - FeatureSet_watchOS_GPUFamily1_v1 = 20000, - FeatureSet_WatchOS_GPUFamily1_v1 = 20000, - FeatureSet_watchOS_GPUFamily2_v1 = 20001, - FeatureSet_WatchOS_GPUFamily2_v1 = 20001, - FeatureSet_tvOS_GPUFamily1_v1 = 30000, - FeatureSet_TVOS_GPUFamily1_v1 = 30000, - FeatureSet_tvOS_GPUFamily1_v2 = 30001, - FeatureSet_tvOS_GPUFamily1_v3 = 30002, - FeatureSet_tvOS_GPUFamily2_v1 = 30003, - FeatureSet_tvOS_GPUFamily1_v4 = 30004, - FeatureSet_tvOS_GPUFamily2_v2 = 30005, -}; - -_MTL_ENUM(NS::Integer, GPUFamily) { - GPUFamilyApple1 = 1001, - GPUFamilyApple2 = 1002, - GPUFamilyApple3 = 1003, - GPUFamilyApple4 = 1004, - GPUFamilyApple5 = 1005, - GPUFamilyApple6 = 1006, - GPUFamilyApple7 = 1007, - GPUFamilyApple8 = 1008, - GPUFamilyMac1 = 2001, - GPUFamilyMac2 = 2002, - GPUFamilyCommon1 = 3001, - GPUFamilyCommon2 = 3002, - GPUFamilyCommon3 = 3003, - GPUFamilyMacCatalyst1 = 4001, - GPUFamilyMacCatalyst2 = 4002, - GPUFamilyMetal3 = 5001, -}; - -_MTL_ENUM(NS::UInteger, DeviceLocation) { - DeviceLocationBuiltIn = 0, - DeviceLocationSlot = 1, - DeviceLocationExternal = 2, - DeviceLocationUnspecified = NS::UIntegerMax, -}; - -_MTL_OPTIONS(NS::UInteger, PipelineOption) { - PipelineOptionNone = 0, - PipelineOptionArgumentInfo = 1, - PipelineOptionBufferTypeInfo = 2, - PipelineOptionFailOnBinaryArchiveMiss = 4, -}; - -_MTL_ENUM(NS::UInteger, ReadWriteTextureTier) { - ReadWriteTextureTierNone = 0, - ReadWriteTextureTier1 = 1, - ReadWriteTextureTier2 = 2, -}; - -_MTL_ENUM(NS::UInteger, ArgumentBuffersTier) { - ArgumentBuffersTier1 = 0, - ArgumentBuffersTier2 = 1, -}; - -_MTL_ENUM(NS::UInteger, SparseTextureRegionAlignmentMode) { - SparseTextureRegionAlignmentModeOutward = 0, - SparseTextureRegionAlignmentModeInward = 1, -}; - -_MTL_ENUM(NS::Integer, SparsePageSize) { - SparsePageSize16 = 101, - SparsePageSize64 = 102, - SparsePageSize256 = 103, -}; - -struct AccelerationStructureSizes -{ - NS::UInteger accelerationStructureSize; - NS::UInteger buildScratchBufferSize; - NS::UInteger refitScratchBufferSize; -} _MTL_PACKED; - -_MTL_ENUM(NS::UInteger, CounterSamplingPoint) { - CounterSamplingPointAtStageBoundary = 0, - CounterSamplingPointAtDrawBoundary = 1, - CounterSamplingPointAtDispatchBoundary = 2, - CounterSamplingPointAtTileDispatchBoundary = 3, - CounterSamplingPointAtBlitBoundary = 4, -}; - -struct SizeAndAlign -{ - NS::UInteger size; - NS::UInteger align; -} _MTL_PACKED; - -class ArgumentDescriptor : public NS::Copying -{ -public: - static class ArgumentDescriptor* alloc(); - - class ArgumentDescriptor* init(); - - static class ArgumentDescriptor* argumentDescriptor(); - - MTL::DataType dataType() const; - void setDataType(MTL::DataType dataType); - - NS::UInteger index() const; - void setIndex(NS::UInteger index); - - NS::UInteger arrayLength() const; - void setArrayLength(NS::UInteger arrayLength); - - MTL::ArgumentAccess access() const; - void setAccess(MTL::ArgumentAccess access); - - MTL::TextureType textureType() const; - void setTextureType(MTL::TextureType textureType); - - NS::UInteger constantBlockAlignment() const; - void setConstantBlockAlignment(NS::UInteger constantBlockAlignment); -}; - -using DeviceNotificationName = NS::String*; -_MTL_CONST(DeviceNotificationName, DeviceWasAddedNotification); -_MTL_CONST(DeviceNotificationName, DeviceRemovalRequestedNotification); -_MTL_CONST(DeviceNotificationName, DeviceWasRemovedNotification); -_MTL_CONST(NS::ErrorUserInfoKey, CommandBufferEncoderInfoErrorKey); - -using DeviceNotificationHandlerBlock = void (^)(class Device* pDevice, DeviceNotificationName notifyName); - -using DeviceNotificationHandlerFunction = std::function; - -using AutoreleasedComputePipelineReflection = class ComputePipelineReflection*; - -using AutoreleasedRenderPipelineReflection = class RenderPipelineReflection*; - -using NewLibraryCompletionHandler = void (^)(class Library*, NS::Error*); - -using NewLibraryCompletionHandlerFunction = std::function; - -using NewRenderPipelineStateCompletionHandler = void (^)(class RenderPipelineState*, NS::Error*); - -using NewRenderPipelineStateCompletionHandlerFunction = std::function; - -using NewRenderPipelineStateWithReflectionCompletionHandler = void (^)(class RenderPipelineState*, class RenderPipelineReflection*, NS::Error*); - -using NewRenderPipelineStateWithReflectionCompletionHandlerFunction = std::function; - -using NewComputePipelineStateCompletionHandler = void (^)(class ComputePipelineState*, NS::Error*); - -using NewComputePipelineStateCompletionHandlerFunction = std::function; - -using NewComputePipelineStateWithReflectionCompletionHandler = void (^)(class ComputePipelineState*, class ComputePipelineReflection*, NS::Error*); - -using NewComputePipelineStateWithReflectionCompletionHandlerFunction = std::function; - -using Timestamp = std::uint64_t; - -MTL::Device* CreateSystemDefaultDevice(); - -NS::Array* CopyAllDevices(); - -NS::Array* CopyAllDevicesWithObserver(NS::Object** pOutObserver, DeviceNotificationHandlerBlock handler); - -NS::Array* CopyAllDevicesWithObserver(NS::Object** pOutObserver, const DeviceNotificationHandlerFunction& handler); - -void RemoveDeviceObserver(const NS::Object* pObserver); - -class Device : public NS::Referencing -{ -public: - void newLibrary(const NS::String* pSource, const class CompileOptions* pOptions, const NewLibraryCompletionHandlerFunction& completionHandler); - - void newLibrary(const class StitchedLibraryDescriptor* pDescriptor, const MTL::NewLibraryCompletionHandlerFunction& completionHandler); - - void newRenderPipelineState(const class RenderPipelineDescriptor* pDescriptor, const NewRenderPipelineStateCompletionHandlerFunction& completionHandler); - - void newRenderPipelineState(const class RenderPipelineDescriptor* pDescriptor, PipelineOption options, const NewRenderPipelineStateWithReflectionCompletionHandlerFunction& completionHandler); - - void newRenderPipelineState(const class TileRenderPipelineDescriptor* pDescriptor, PipelineOption options, const NewRenderPipelineStateWithReflectionCompletionHandlerFunction& completionHandler); - - void newComputePipelineState(const class Function* pFunction, const NewComputePipelineStateCompletionHandlerFunction& completionHandler); - - void newComputePipelineState(const class Function* pFunction, PipelineOption options, const NewComputePipelineStateWithReflectionCompletionHandlerFunction& completionHandler); - - void newComputePipelineState(const class ComputePipelineDescriptor* pDescriptor, PipelineOption options, const NewComputePipelineStateWithReflectionCompletionHandlerFunction& completionHandler); - - bool isHeadless() const; - - NS::String* name() const; - - uint64_t registryID() const; - - MTL::Size maxThreadsPerThreadgroup() const; - - bool lowPower() const; - - bool headless() const; - - bool removable() const; - - bool hasUnifiedMemory() const; - - uint64_t recommendedMaxWorkingSetSize() const; - - MTL::DeviceLocation location() const; - - NS::UInteger locationNumber() const; - - uint64_t maxTransferRate() const; - - bool depth24Stencil8PixelFormatSupported() const; - - MTL::ReadWriteTextureTier readWriteTextureSupport() const; - - MTL::ArgumentBuffersTier argumentBuffersSupport() const; - - bool rasterOrderGroupsSupported() const; - - bool supports32BitFloatFiltering() const; - - bool supports32BitMSAA() const; - - bool supportsQueryTextureLOD() const; - - bool supportsBCTextureCompression() const; - - bool supportsPullModelInterpolation() const; - - bool barycentricCoordsSupported() const; - - bool supportsShaderBarycentricCoordinates() const; - - NS::UInteger currentAllocatedSize() const; - - class CommandQueue* newCommandQueue(); - - class CommandQueue* newCommandQueue(NS::UInteger maxCommandBufferCount); - - MTL::SizeAndAlign heapTextureSizeAndAlign(const class TextureDescriptor* desc); - - MTL::SizeAndAlign heapBufferSizeAndAlign(NS::UInteger length, MTL::ResourceOptions options); - - class Heap* newHeap(const class HeapDescriptor* descriptor); - - class Buffer* newBuffer(NS::UInteger length, MTL::ResourceOptions options); - - class Buffer* newBuffer(const void* pointer, NS::UInteger length, MTL::ResourceOptions options); - - class Buffer* newBuffer(const void* pointer, NS::UInteger length, MTL::ResourceOptions options, void (^deallocator)(void*, NS::UInteger)); - - class DepthStencilState* newDepthStencilState(const class DepthStencilDescriptor* descriptor); - - class Texture* newTexture(const class TextureDescriptor* descriptor); - - class Texture* newTexture(const class TextureDescriptor* descriptor, const IOSurfaceRef iosurface, NS::UInteger plane); - - class Texture* newSharedTexture(const class TextureDescriptor* descriptor); - - class Texture* newSharedTexture(const class SharedTextureHandle* sharedHandle); - - class SamplerState* newSamplerState(const class SamplerDescriptor* descriptor); - - class Library* newDefaultLibrary(); - - class Library* newDefaultLibrary(const NS::Bundle* bundle, NS::Error** error); - - class Library* newLibrary(const NS::String* filepath, NS::Error** error); - - class Library* newLibrary(const NS::URL* url, NS::Error** error); - - class Library* newLibrary(const dispatch_data_t data, NS::Error** error); - - class Library* newLibrary(const NS::String* source, const class CompileOptions* options, NS::Error** error); - - void newLibrary(const NS::String* source, const class CompileOptions* options, const MTL::NewLibraryCompletionHandler completionHandler); - - class Library* newLibrary(const class StitchedLibraryDescriptor* descriptor, NS::Error** error); - - void newLibrary(const class StitchedLibraryDescriptor* descriptor, const MTL::NewLibraryCompletionHandler completionHandler); - - class RenderPipelineState* newRenderPipelineState(const class RenderPipelineDescriptor* descriptor, NS::Error** error); - - class RenderPipelineState* newRenderPipelineState(const class RenderPipelineDescriptor* descriptor, MTL::PipelineOption options, const MTL::AutoreleasedRenderPipelineReflection* reflection, NS::Error** error); - - void newRenderPipelineState(const class RenderPipelineDescriptor* descriptor, const MTL::NewRenderPipelineStateCompletionHandler completionHandler); - - void newRenderPipelineState(const class RenderPipelineDescriptor* descriptor, MTL::PipelineOption options, const MTL::NewRenderPipelineStateWithReflectionCompletionHandler completionHandler); - - class ComputePipelineState* newComputePipelineState(const class Function* computeFunction, NS::Error** error); - - class ComputePipelineState* newComputePipelineState(const class Function* computeFunction, MTL::PipelineOption options, const MTL::AutoreleasedComputePipelineReflection* reflection, NS::Error** error); - - void newComputePipelineState(const class Function* computeFunction, const MTL::NewComputePipelineStateCompletionHandler completionHandler); - - void newComputePipelineState(const class Function* computeFunction, MTL::PipelineOption options, const MTL::NewComputePipelineStateWithReflectionCompletionHandler completionHandler); - - class ComputePipelineState* newComputePipelineState(const class ComputePipelineDescriptor* descriptor, MTL::PipelineOption options, const MTL::AutoreleasedComputePipelineReflection* reflection, NS::Error** error); - - void newComputePipelineState(const class ComputePipelineDescriptor* descriptor, MTL::PipelineOption options, const MTL::NewComputePipelineStateWithReflectionCompletionHandler completionHandler); - - class Fence* newFence(); - - bool supportsFeatureSet(MTL::FeatureSet featureSet); - - bool supportsFamily(MTL::GPUFamily gpuFamily); - - bool supportsTextureSampleCount(NS::UInteger sampleCount); - - NS::UInteger minimumLinearTextureAlignmentForPixelFormat(MTL::PixelFormat format); - - NS::UInteger minimumTextureBufferAlignmentForPixelFormat(MTL::PixelFormat format); - - class RenderPipelineState* newRenderPipelineState(const class TileRenderPipelineDescriptor* descriptor, MTL::PipelineOption options, const MTL::AutoreleasedRenderPipelineReflection* reflection, NS::Error** error); - - void newRenderPipelineState(const class TileRenderPipelineDescriptor* descriptor, MTL::PipelineOption options, const MTL::NewRenderPipelineStateWithReflectionCompletionHandler completionHandler); - - class RenderPipelineState* newRenderPipelineState(const class MeshRenderPipelineDescriptor* descriptor, MTL::PipelineOption options, const MTL::AutoreleasedRenderPipelineReflection* reflection, NS::Error** error); - - void newRenderPipelineState(const class MeshRenderPipelineDescriptor* descriptor, MTL::PipelineOption options, const MTL::NewRenderPipelineStateWithReflectionCompletionHandler completionHandler); - - NS::UInteger maxThreadgroupMemoryLength() const; - - NS::UInteger maxArgumentBufferSamplerCount() const; - - bool programmableSamplePositionsSupported() const; - - void getDefaultSamplePositions(MTL::SamplePosition* positions, NS::UInteger count); - - class ArgumentEncoder* newArgumentEncoder(const NS::Array* arguments); - - bool supportsRasterizationRateMap(NS::UInteger layerCount); - - class RasterizationRateMap* newRasterizationRateMap(const class RasterizationRateMapDescriptor* descriptor); - - class IndirectCommandBuffer* newIndirectCommandBuffer(const class IndirectCommandBufferDescriptor* descriptor, NS::UInteger maxCount, MTL::ResourceOptions options); - - class Event* newEvent(); - - class SharedEvent* newSharedEvent(); - - class SharedEvent* newSharedEvent(const class SharedEventHandle* sharedEventHandle); - - uint64_t peerGroupID() const; - - uint32_t peerIndex() const; - - uint32_t peerCount() const; - - class IOFileHandle* newIOHandle(const NS::URL* url, NS::Error** error); - - class IOCommandQueue* newIOCommandQueue(const class IOCommandQueueDescriptor* descriptor, NS::Error** error); - - class IOFileHandle* newIOHandle(const NS::URL* url, MTL::IOCompressionMethod compressionMethod, NS::Error** error); - - MTL::Size sparseTileSize(MTL::TextureType textureType, MTL::PixelFormat pixelFormat, NS::UInteger sampleCount); - - NS::UInteger sparseTileSizeInBytes() const; - - void convertSparsePixelRegions(const MTL::Region* pixelRegions, MTL::Region* tileRegions, MTL::Size tileSize, MTL::SparseTextureRegionAlignmentMode mode, NS::UInteger numRegions); - - void convertSparseTileRegions(const MTL::Region* tileRegions, MTL::Region* pixelRegions, MTL::Size tileSize, NS::UInteger numRegions); - - NS::UInteger sparseTileSizeInBytes(MTL::SparsePageSize sparsePageSize); - - MTL::Size sparseTileSize(MTL::TextureType textureType, MTL::PixelFormat pixelFormat, NS::UInteger sampleCount, MTL::SparsePageSize sparsePageSize); - - NS::UInteger maxBufferLength() const; - - NS::Array* counterSets() const; - - class CounterSampleBuffer* newCounterSampleBuffer(const class CounterSampleBufferDescriptor* descriptor, NS::Error** error); - - void sampleTimestamps(MTL::Timestamp* cpuTimestamp, MTL::Timestamp* gpuTimestamp); - - class ArgumentEncoder* newArgumentEncoder(const class BufferBinding* bufferBinding); - - bool supportsCounterSampling(MTL::CounterSamplingPoint samplingPoint); - - bool supportsVertexAmplificationCount(NS::UInteger count); - - bool supportsDynamicLibraries() const; - - bool supportsRenderDynamicLibraries() const; - - class DynamicLibrary* newDynamicLibrary(const class Library* library, NS::Error** error); - - class DynamicLibrary* newDynamicLibrary(const NS::URL* url, NS::Error** error); - - class BinaryArchive* newBinaryArchive(const class BinaryArchiveDescriptor* descriptor, NS::Error** error); - - bool supportsRaytracing() const; - - MTL::AccelerationStructureSizes accelerationStructureSizes(const class AccelerationStructureDescriptor* descriptor); - - class AccelerationStructure* newAccelerationStructure(NS::UInteger size); - - class AccelerationStructure* newAccelerationStructure(const class AccelerationStructureDescriptor* descriptor); - - MTL::SizeAndAlign heapAccelerationStructureSizeAndAlign(NS::UInteger size); - - MTL::SizeAndAlign heapAccelerationStructureSizeAndAlign(const class AccelerationStructureDescriptor* descriptor); - - bool supportsFunctionPointers() const; - - bool supportsFunctionPointersFromRender() const; - - bool supportsRaytracingFromRender() const; - - bool supportsPrimitiveMotionBlur() const; -}; - -} - -_MTL_INLINE MTL::ArgumentDescriptor* MTL::ArgumentDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLArgumentDescriptor)); -} - -_MTL_INLINE MTL::ArgumentDescriptor* MTL::ArgumentDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::ArgumentDescriptor* MTL::ArgumentDescriptor::argumentDescriptor() -{ - return Object::sendMessage(_MTL_PRIVATE_CLS(MTLArgumentDescriptor), _MTL_PRIVATE_SEL(argumentDescriptor)); -} - -_MTL_INLINE MTL::DataType MTL::ArgumentDescriptor::dataType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(dataType)); -} - -_MTL_INLINE void MTL::ArgumentDescriptor::setDataType(MTL::DataType dataType) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setDataType_), dataType); -} - -_MTL_INLINE NS::UInteger MTL::ArgumentDescriptor::index() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(index)); -} - -_MTL_INLINE void MTL::ArgumentDescriptor::setIndex(NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setIndex_), index); -} - -_MTL_INLINE NS::UInteger MTL::ArgumentDescriptor::arrayLength() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(arrayLength)); -} - -_MTL_INLINE void MTL::ArgumentDescriptor::setArrayLength(NS::UInteger arrayLength) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setArrayLength_), arrayLength); -} - -_MTL_INLINE MTL::ArgumentAccess MTL::ArgumentDescriptor::access() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(access)); -} - -_MTL_INLINE void MTL::ArgumentDescriptor::setAccess(MTL::ArgumentAccess access) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setAccess_), access); -} - -_MTL_INLINE MTL::TextureType MTL::ArgumentDescriptor::textureType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(textureType)); -} - -_MTL_INLINE void MTL::ArgumentDescriptor::setTextureType(MTL::TextureType textureType) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTextureType_), textureType); -} - -_MTL_INLINE NS::UInteger MTL::ArgumentDescriptor::constantBlockAlignment() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(constantBlockAlignment)); -} - -_MTL_INLINE void MTL::ArgumentDescriptor::setConstantBlockAlignment(NS::UInteger constantBlockAlignment) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setConstantBlockAlignment_), constantBlockAlignment); -} - -_MTL_PRIVATE_DEF_WEAK_CONST(MTL::DeviceNotificationName, DeviceWasAddedNotification); -_MTL_PRIVATE_DEF_WEAK_CONST(MTL::DeviceNotificationName, DeviceRemovalRequestedNotification); -_MTL_PRIVATE_DEF_WEAK_CONST(MTL::DeviceNotificationName, DeviceWasRemovedNotification); -_MTL_PRIVATE_DEF_CONST(NS::ErrorUserInfoKey, CommandBufferEncoderInfoErrorKey); - -#if defined(MTL_PRIVATE_IMPLEMENTATION) - -extern "C" MTL::Device* MTLCreateSystemDefaultDevice(); - -extern "C" NS::Array* MTLCopyAllDevices(); - -extern "C" NS::Array* MTLCopyAllDevicesWithObserver(NS::Object**, MTL::DeviceNotificationHandlerBlock); - -extern "C" void MTLRemoveDeviceObserver(const NS::Object*); - -#include - -_NS_EXPORT MTL::Device* MTL::CreateSystemDefaultDevice() -{ - return ::MTLCreateSystemDefaultDevice(); -} - -_NS_EXPORT NS::Array* MTL::CopyAllDevices() -{ -#if TARGET_OS_OSX - return ::MTLCopyAllDevices(); -#else - return nullptr; -#endif // TARGET_OS_OSX -} - -_NS_EXPORT NS::Array* MTL::CopyAllDevicesWithObserver(NS::Object** pOutObserver, DeviceNotificationHandlerBlock handler) -{ -#if TARGET_OS_OSX - return ::MTLCopyAllDevicesWithObserver(pOutObserver, handler); -#else - (void)pOutObserver; - (void)handler; - - return nullptr; -#endif // TARGET_OS_OSX -} - -_NS_EXPORT NS::Array* MTL::CopyAllDevicesWithObserver(NS::Object** pOutObserver, const DeviceNotificationHandlerFunction& handler) -{ - __block DeviceNotificationHandlerFunction function = handler; - - return CopyAllDevicesWithObserver(pOutObserver, ^(Device* pDevice, DeviceNotificationName pNotificationName) { function(pDevice, pNotificationName); }); -} - -_NS_EXPORT void MTL::RemoveDeviceObserver(const NS::Object* pObserver) -{ -#if TARGET_OS_OSX - ::MTLRemoveDeviceObserver(pObserver); -#endif // TARGET_OS_OSX -} - -#endif // MTL_PRIVATE_IMPLEMENTATION - -_MTL_INLINE void MTL::Device::newLibrary(const NS::String* pSource, const CompileOptions* pOptions, const NewLibraryCompletionHandlerFunction& completionHandler) -{ - __block NewLibraryCompletionHandlerFunction blockCompletionHandler = completionHandler; - - newLibrary(pSource, pOptions, ^(Library* pLibrary, NS::Error* pError) { blockCompletionHandler(pLibrary, pError); }); -} - -_MTL_INLINE void MTL::Device::newLibrary(const class StitchedLibraryDescriptor* pDescriptor, const MTL::NewLibraryCompletionHandlerFunction& completionHandler) -{ - __block NewLibraryCompletionHandlerFunction blockCompletionHandler = completionHandler; - - newLibrary(pDescriptor, ^(Library* pLibrary, NS::Error* pError) { blockCompletionHandler(pLibrary, pError); }); -} - -_MTL_INLINE void MTL::Device::newRenderPipelineState(const RenderPipelineDescriptor* pDescriptor, const NewRenderPipelineStateCompletionHandlerFunction& completionHandler) -{ - __block NewRenderPipelineStateCompletionHandlerFunction blockCompletionHandler = completionHandler; - - newRenderPipelineState(pDescriptor, ^(RenderPipelineState* pPipelineState, NS::Error* pError) { blockCompletionHandler(pPipelineState, pError); }); -} - -_MTL_INLINE void MTL::Device::newRenderPipelineState(const RenderPipelineDescriptor* pDescriptor, PipelineOption options, const NewRenderPipelineStateWithReflectionCompletionHandlerFunction& completionHandler) -{ - __block NewRenderPipelineStateWithReflectionCompletionHandlerFunction blockCompletionHandler = completionHandler; - - newRenderPipelineState(pDescriptor, options, ^(RenderPipelineState* pPipelineState, class RenderPipelineReflection* pReflection, NS::Error* pError) { blockCompletionHandler(pPipelineState, pReflection, pError); }); -} - -_MTL_INLINE void MTL::Device::newRenderPipelineState(const TileRenderPipelineDescriptor* pDescriptor, PipelineOption options, const NewRenderPipelineStateWithReflectionCompletionHandlerFunction& completionHandler) -{ - __block NewRenderPipelineStateWithReflectionCompletionHandlerFunction blockCompletionHandler = completionHandler; - - newRenderPipelineState(pDescriptor, options, ^(RenderPipelineState* pPipelineState, class RenderPipelineReflection* pReflection, NS::Error* pError) { blockCompletionHandler(pPipelineState, pReflection, pError); }); -} - -_MTL_INLINE void MTL::Device::newComputePipelineState(const class Function* pFunction, const NewComputePipelineStateCompletionHandlerFunction& completionHandler) -{ - __block NewComputePipelineStateCompletionHandlerFunction blockCompletionHandler = completionHandler; - - newComputePipelineState(pFunction, ^(ComputePipelineState* pPipelineState, NS::Error* pError) { blockCompletionHandler(pPipelineState, pError); }); -} - -_MTL_INLINE void MTL::Device::newComputePipelineState(const Function* pFunction, PipelineOption options, const NewComputePipelineStateWithReflectionCompletionHandlerFunction& completionHandler) -{ - __block NewComputePipelineStateWithReflectionCompletionHandlerFunction blockCompletionHandler = completionHandler; - - newComputePipelineState(pFunction, options, ^(ComputePipelineState* pPipelineState, ComputePipelineReflection* pReflection, NS::Error* pError) { blockCompletionHandler(pPipelineState, pReflection, pError); }); -} - -_MTL_INLINE void MTL::Device::newComputePipelineState(const ComputePipelineDescriptor* pDescriptor, PipelineOption options, const NewComputePipelineStateWithReflectionCompletionHandlerFunction& completionHandler) -{ - __block NewComputePipelineStateWithReflectionCompletionHandlerFunction blockCompletionHandler = completionHandler; - - newComputePipelineState(pDescriptor, options, ^(ComputePipelineState* pPipelineState, ComputePipelineReflection* pReflection, NS::Error* pError) { blockCompletionHandler(pPipelineState, pReflection, pError); }); -} - -_MTL_INLINE bool MTL::Device::isHeadless() const -{ - return headless(); -} - -_MTL_INLINE NS::String* MTL::Device::name() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(name)); -} - -_MTL_INLINE uint64_t MTL::Device::registryID() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(registryID)); -} - -_MTL_INLINE MTL::Size MTL::Device::maxThreadsPerThreadgroup() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(maxThreadsPerThreadgroup)); -} - -_MTL_INLINE bool MTL::Device::lowPower() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(isLowPower)); -} - -_MTL_INLINE bool MTL::Device::headless() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(isHeadless)); -} - -_MTL_INLINE bool MTL::Device::removable() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(isRemovable)); -} - -_MTL_INLINE bool MTL::Device::hasUnifiedMemory() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(hasUnifiedMemory)); -} - -_MTL_INLINE uint64_t MTL::Device::recommendedMaxWorkingSetSize() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(recommendedMaxWorkingSetSize)); -} - -_MTL_INLINE MTL::DeviceLocation MTL::Device::location() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(location)); -} - -_MTL_INLINE NS::UInteger MTL::Device::locationNumber() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(locationNumber)); -} - -_MTL_INLINE uint64_t MTL::Device::maxTransferRate() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(maxTransferRate)); -} - -_MTL_INLINE bool MTL::Device::depth24Stencil8PixelFormatSupported() const -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(isDepth24Stencil8PixelFormatSupported)); -} - -_MTL_INLINE MTL::ReadWriteTextureTier MTL::Device::readWriteTextureSupport() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(readWriteTextureSupport)); -} - -_MTL_INLINE MTL::ArgumentBuffersTier MTL::Device::argumentBuffersSupport() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(argumentBuffersSupport)); -} - -_MTL_INLINE bool MTL::Device::rasterOrderGroupsSupported() const -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(areRasterOrderGroupsSupported)); -} - -_MTL_INLINE bool MTL::Device::supports32BitFloatFiltering() const -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(supports32BitFloatFiltering)); -} - -_MTL_INLINE bool MTL::Device::supports32BitMSAA() const -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(supports32BitMSAA)); -} - -_MTL_INLINE bool MTL::Device::supportsQueryTextureLOD() const -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(supportsQueryTextureLOD)); -} - -_MTL_INLINE bool MTL::Device::supportsBCTextureCompression() const -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(supportsBCTextureCompression)); -} - -_MTL_INLINE bool MTL::Device::supportsPullModelInterpolation() const -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(supportsPullModelInterpolation)); -} - -_MTL_INLINE bool MTL::Device::barycentricCoordsSupported() const -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(areBarycentricCoordsSupported)); -} - -_MTL_INLINE bool MTL::Device::supportsShaderBarycentricCoordinates() const -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(supportsShaderBarycentricCoordinates)); -} - -_MTL_INLINE NS::UInteger MTL::Device::currentAllocatedSize() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(currentAllocatedSize)); -} - -_MTL_INLINE MTL::CommandQueue* MTL::Device::newCommandQueue() -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newCommandQueue)); -} - -_MTL_INLINE MTL::CommandQueue* MTL::Device::newCommandQueue(NS::UInteger maxCommandBufferCount) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newCommandQueueWithMaxCommandBufferCount_), maxCommandBufferCount); -} - -_MTL_INLINE MTL::SizeAndAlign MTL::Device::heapTextureSizeAndAlign(const MTL::TextureDescriptor* desc) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(heapTextureSizeAndAlignWithDescriptor_), desc); -} - -_MTL_INLINE MTL::SizeAndAlign MTL::Device::heapBufferSizeAndAlign(NS::UInteger length, MTL::ResourceOptions options) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(heapBufferSizeAndAlignWithLength_options_), length, options); -} - -_MTL_INLINE MTL::Heap* MTL::Device::newHeap(const MTL::HeapDescriptor* descriptor) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newHeapWithDescriptor_), descriptor); -} - -_MTL_INLINE MTL::Buffer* MTL::Device::newBuffer(NS::UInteger length, MTL::ResourceOptions options) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newBufferWithLength_options_), length, options); -} - -_MTL_INLINE MTL::Buffer* MTL::Device::newBuffer(const void* pointer, NS::UInteger length, MTL::ResourceOptions options) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newBufferWithBytes_length_options_), pointer, length, options); -} - -_MTL_INLINE MTL::Buffer* MTL::Device::newBuffer(const void* pointer, NS::UInteger length, MTL::ResourceOptions options, void (^deallocator)(void*, NS::UInteger)) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newBufferWithBytesNoCopy_length_options_deallocator_), pointer, length, options, deallocator); -} - -_MTL_INLINE MTL::DepthStencilState* MTL::Device::newDepthStencilState(const MTL::DepthStencilDescriptor* descriptor) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newDepthStencilStateWithDescriptor_), descriptor); -} - -_MTL_INLINE MTL::Texture* MTL::Device::newTexture(const MTL::TextureDescriptor* descriptor) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newTextureWithDescriptor_), descriptor); -} - -_MTL_INLINE MTL::Texture* MTL::Device::newTexture(const MTL::TextureDescriptor* descriptor, const IOSurfaceRef iosurface, NS::UInteger plane) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newTextureWithDescriptor_iosurface_plane_), descriptor, iosurface, plane); -} - -_MTL_INLINE MTL::Texture* MTL::Device::newSharedTexture(const MTL::TextureDescriptor* descriptor) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newSharedTextureWithDescriptor_), descriptor); -} - -_MTL_INLINE MTL::Texture* MTL::Device::newSharedTexture(const MTL::SharedTextureHandle* sharedHandle) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newSharedTextureWithHandle_), sharedHandle); -} - -_MTL_INLINE MTL::SamplerState* MTL::Device::newSamplerState(const MTL::SamplerDescriptor* descriptor) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newSamplerStateWithDescriptor_), descriptor); -} - -_MTL_INLINE MTL::Library* MTL::Device::newDefaultLibrary() -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newDefaultLibrary)); -} - -_MTL_INLINE MTL::Library* MTL::Device::newDefaultLibrary(const NS::Bundle* bundle, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newDefaultLibraryWithBundle_error_), bundle, error); -} - -_MTL_INLINE MTL::Library* MTL::Device::newLibrary(const NS::String* filepath, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newLibraryWithFile_error_), filepath, error); -} - -_MTL_INLINE MTL::Library* MTL::Device::newLibrary(const NS::URL* url, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newLibraryWithURL_error_), url, error); -} - -_MTL_INLINE MTL::Library* MTL::Device::newLibrary(const dispatch_data_t data, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newLibraryWithData_error_), data, error); -} - -_MTL_INLINE MTL::Library* MTL::Device::newLibrary(const NS::String* source, const MTL::CompileOptions* options, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newLibraryWithSource_options_error_), source, options, error); -} - -_MTL_INLINE void MTL::Device::newLibrary(const NS::String* source, const MTL::CompileOptions* options, const MTL::NewLibraryCompletionHandler completionHandler) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(newLibraryWithSource_options_completionHandler_), source, options, completionHandler); -} - -_MTL_INLINE MTL::Library* MTL::Device::newLibrary(const MTL::StitchedLibraryDescriptor* descriptor, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newLibraryWithStitchedDescriptor_error_), descriptor, error); -} - -_MTL_INLINE void MTL::Device::newLibrary(const MTL::StitchedLibraryDescriptor* descriptor, const MTL::NewLibraryCompletionHandler completionHandler) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(newLibraryWithStitchedDescriptor_completionHandler_), descriptor, completionHandler); -} - -_MTL_INLINE MTL::RenderPipelineState* MTL::Device::newRenderPipelineState(const MTL::RenderPipelineDescriptor* descriptor, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newRenderPipelineStateWithDescriptor_error_), descriptor, error); -} - -_MTL_INLINE MTL::RenderPipelineState* MTL::Device::newRenderPipelineState(const MTL::RenderPipelineDescriptor* descriptor, MTL::PipelineOption options, const MTL::AutoreleasedRenderPipelineReflection* reflection, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newRenderPipelineStateWithDescriptor_options_reflection_error_), descriptor, options, reflection, error); -} - -_MTL_INLINE void MTL::Device::newRenderPipelineState(const MTL::RenderPipelineDescriptor* descriptor, const MTL::NewRenderPipelineStateCompletionHandler completionHandler) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(newRenderPipelineStateWithDescriptor_completionHandler_), descriptor, completionHandler); -} - -_MTL_INLINE void MTL::Device::newRenderPipelineState(const MTL::RenderPipelineDescriptor* descriptor, MTL::PipelineOption options, const MTL::NewRenderPipelineStateWithReflectionCompletionHandler completionHandler) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(newRenderPipelineStateWithDescriptor_options_completionHandler_), descriptor, options, completionHandler); -} - -_MTL_INLINE MTL::ComputePipelineState* MTL::Device::newComputePipelineState(const MTL::Function* computeFunction, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newComputePipelineStateWithFunction_error_), computeFunction, error); -} - -_MTL_INLINE MTL::ComputePipelineState* MTL::Device::newComputePipelineState(const MTL::Function* computeFunction, MTL::PipelineOption options, const MTL::AutoreleasedComputePipelineReflection* reflection, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newComputePipelineStateWithFunction_options_reflection_error_), computeFunction, options, reflection, error); -} - -_MTL_INLINE void MTL::Device::newComputePipelineState(const MTL::Function* computeFunction, const MTL::NewComputePipelineStateCompletionHandler completionHandler) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(newComputePipelineStateWithFunction_completionHandler_), computeFunction, completionHandler); -} - -_MTL_INLINE void MTL::Device::newComputePipelineState(const MTL::Function* computeFunction, MTL::PipelineOption options, const MTL::NewComputePipelineStateWithReflectionCompletionHandler completionHandler) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(newComputePipelineStateWithFunction_options_completionHandler_), computeFunction, options, completionHandler); -} - -_MTL_INLINE MTL::ComputePipelineState* MTL::Device::newComputePipelineState(const MTL::ComputePipelineDescriptor* descriptor, MTL::PipelineOption options, const MTL::AutoreleasedComputePipelineReflection* reflection, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newComputePipelineStateWithDescriptor_options_reflection_error_), descriptor, options, reflection, error); -} - -_MTL_INLINE void MTL::Device::newComputePipelineState(const MTL::ComputePipelineDescriptor* descriptor, MTL::PipelineOption options, const MTL::NewComputePipelineStateWithReflectionCompletionHandler completionHandler) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(newComputePipelineStateWithDescriptor_options_completionHandler_), descriptor, options, completionHandler); -} - -_MTL_INLINE MTL::Fence* MTL::Device::newFence() -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newFence)); -} - -_MTL_INLINE bool MTL::Device::supportsFeatureSet(MTL::FeatureSet featureSet) -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(supportsFeatureSet_), featureSet); -} - -_MTL_INLINE bool MTL::Device::supportsFamily(MTL::GPUFamily gpuFamily) -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(supportsFamily_), gpuFamily); -} - -_MTL_INLINE bool MTL::Device::supportsTextureSampleCount(NS::UInteger sampleCount) -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(supportsTextureSampleCount_), sampleCount); -} - -_MTL_INLINE NS::UInteger MTL::Device::minimumLinearTextureAlignmentForPixelFormat(MTL::PixelFormat format) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(minimumLinearTextureAlignmentForPixelFormat_), format); -} - -_MTL_INLINE NS::UInteger MTL::Device::minimumTextureBufferAlignmentForPixelFormat(MTL::PixelFormat format) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(minimumTextureBufferAlignmentForPixelFormat_), format); -} - -_MTL_INLINE MTL::RenderPipelineState* MTL::Device::newRenderPipelineState(const MTL::TileRenderPipelineDescriptor* descriptor, MTL::PipelineOption options, const MTL::AutoreleasedRenderPipelineReflection* reflection, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newRenderPipelineStateWithTileDescriptor_options_reflection_error_), descriptor, options, reflection, error); -} - -_MTL_INLINE void MTL::Device::newRenderPipelineState(const MTL::TileRenderPipelineDescriptor* descriptor, MTL::PipelineOption options, const MTL::NewRenderPipelineStateWithReflectionCompletionHandler completionHandler) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(newRenderPipelineStateWithTileDescriptor_options_completionHandler_), descriptor, options, completionHandler); -} - -_MTL_INLINE MTL::RenderPipelineState* MTL::Device::newRenderPipelineState(const MTL::MeshRenderPipelineDescriptor* descriptor, MTL::PipelineOption options, const MTL::AutoreleasedRenderPipelineReflection* reflection, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newRenderPipelineStateWithMeshDescriptor_options_reflection_error_), descriptor, options, reflection, error); -} - -_MTL_INLINE void MTL::Device::newRenderPipelineState(const MTL::MeshRenderPipelineDescriptor* descriptor, MTL::PipelineOption options, const MTL::NewRenderPipelineStateWithReflectionCompletionHandler completionHandler) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(newRenderPipelineStateWithMeshDescriptor_options_completionHandler_), descriptor, options, completionHandler); -} - -_MTL_INLINE NS::UInteger MTL::Device::maxThreadgroupMemoryLength() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(maxThreadgroupMemoryLength)); -} - -_MTL_INLINE NS::UInteger MTL::Device::maxArgumentBufferSamplerCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(maxArgumentBufferSamplerCount)); -} - -_MTL_INLINE bool MTL::Device::programmableSamplePositionsSupported() const -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(areProgrammableSamplePositionsSupported)); -} - -_MTL_INLINE void MTL::Device::getDefaultSamplePositions(MTL::SamplePosition* positions, NS::UInteger count) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(getDefaultSamplePositions_count_), positions, count); -} - -_MTL_INLINE MTL::ArgumentEncoder* MTL::Device::newArgumentEncoder(const NS::Array* arguments) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newArgumentEncoderWithArguments_), arguments); -} - -_MTL_INLINE bool MTL::Device::supportsRasterizationRateMap(NS::UInteger layerCount) -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(supportsRasterizationRateMapWithLayerCount_), layerCount); -} - -_MTL_INLINE MTL::RasterizationRateMap* MTL::Device::newRasterizationRateMap(const MTL::RasterizationRateMapDescriptor* descriptor) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newRasterizationRateMapWithDescriptor_), descriptor); -} - -_MTL_INLINE MTL::IndirectCommandBuffer* MTL::Device::newIndirectCommandBuffer(const MTL::IndirectCommandBufferDescriptor* descriptor, NS::UInteger maxCount, MTL::ResourceOptions options) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newIndirectCommandBufferWithDescriptor_maxCommandCount_options_), descriptor, maxCount, options); -} - -_MTL_INLINE MTL::Event* MTL::Device::newEvent() -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newEvent)); -} - -_MTL_INLINE MTL::SharedEvent* MTL::Device::newSharedEvent() -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newSharedEvent)); -} - -_MTL_INLINE MTL::SharedEvent* MTL::Device::newSharedEvent(const MTL::SharedEventHandle* sharedEventHandle) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newSharedEventWithHandle_), sharedEventHandle); -} - -_MTL_INLINE uint64_t MTL::Device::peerGroupID() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(peerGroupID)); -} - -_MTL_INLINE uint32_t MTL::Device::peerIndex() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(peerIndex)); -} - -_MTL_INLINE uint32_t MTL::Device::peerCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(peerCount)); -} - -_MTL_INLINE MTL::IOFileHandle* MTL::Device::newIOHandle(const NS::URL* url, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newIOHandleWithURL_error_), url, error); -} - -_MTL_INLINE MTL::IOCommandQueue* MTL::Device::newIOCommandQueue(const MTL::IOCommandQueueDescriptor* descriptor, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newIOCommandQueueWithDescriptor_error_), descriptor, error); -} - -_MTL_INLINE MTL::IOFileHandle* MTL::Device::newIOHandle(const NS::URL* url, MTL::IOCompressionMethod compressionMethod, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newIOHandleWithURL_compressionMethod_error_), url, compressionMethod, error); -} - -_MTL_INLINE MTL::Size MTL::Device::sparseTileSize(MTL::TextureType textureType, MTL::PixelFormat pixelFormat, NS::UInteger sampleCount) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(sparseTileSizeWithTextureType_pixelFormat_sampleCount_), textureType, pixelFormat, sampleCount); -} - -_MTL_INLINE NS::UInteger MTL::Device::sparseTileSizeInBytes() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(sparseTileSizeInBytes)); -} - -_MTL_INLINE void MTL::Device::convertSparsePixelRegions(const MTL::Region* pixelRegions, MTL::Region* tileRegions, MTL::Size tileSize, MTL::SparseTextureRegionAlignmentMode mode, NS::UInteger numRegions) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(convertSparsePixelRegions_toTileRegions_withTileSize_alignmentMode_numRegions_), pixelRegions, tileRegions, tileSize, mode, numRegions); -} - -_MTL_INLINE void MTL::Device::convertSparseTileRegions(const MTL::Region* tileRegions, MTL::Region* pixelRegions, MTL::Size tileSize, NS::UInteger numRegions) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(convertSparseTileRegions_toPixelRegions_withTileSize_numRegions_), tileRegions, pixelRegions, tileSize, numRegions); -} - -_MTL_INLINE NS::UInteger MTL::Device::sparseTileSizeInBytes(MTL::SparsePageSize sparsePageSize) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(sparseTileSizeInBytesForSparsePageSize_), sparsePageSize); -} - -_MTL_INLINE MTL::Size MTL::Device::sparseTileSize(MTL::TextureType textureType, MTL::PixelFormat pixelFormat, NS::UInteger sampleCount, MTL::SparsePageSize sparsePageSize) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(sparseTileSizeWithTextureType_pixelFormat_sampleCount_sparsePageSize_), textureType, pixelFormat, sampleCount, sparsePageSize); -} - -_MTL_INLINE NS::UInteger MTL::Device::maxBufferLength() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(maxBufferLength)); -} - -_MTL_INLINE NS::Array* MTL::Device::counterSets() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(counterSets)); -} - -_MTL_INLINE MTL::CounterSampleBuffer* MTL::Device::newCounterSampleBuffer(const MTL::CounterSampleBufferDescriptor* descriptor, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newCounterSampleBufferWithDescriptor_error_), descriptor, error); -} - -_MTL_INLINE void MTL::Device::sampleTimestamps(MTL::Timestamp* cpuTimestamp, MTL::Timestamp* gpuTimestamp) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(sampleTimestamps_gpuTimestamp_), cpuTimestamp, gpuTimestamp); -} - -_MTL_INLINE MTL::ArgumentEncoder* MTL::Device::newArgumentEncoder(const MTL::BufferBinding* bufferBinding) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newArgumentEncoderWithBufferBinding_), bufferBinding); -} - -_MTL_INLINE bool MTL::Device::supportsCounterSampling(MTL::CounterSamplingPoint samplingPoint) -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(supportsCounterSampling_), samplingPoint); -} - -_MTL_INLINE bool MTL::Device::supportsVertexAmplificationCount(NS::UInteger count) -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(supportsVertexAmplificationCount_), count); -} - -_MTL_INLINE bool MTL::Device::supportsDynamicLibraries() const -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(supportsDynamicLibraries)); -} - -_MTL_INLINE bool MTL::Device::supportsRenderDynamicLibraries() const -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(supportsRenderDynamicLibraries)); -} - -_MTL_INLINE MTL::DynamicLibrary* MTL::Device::newDynamicLibrary(const MTL::Library* library, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newDynamicLibrary_error_), library, error); -} - -_MTL_INLINE MTL::DynamicLibrary* MTL::Device::newDynamicLibrary(const NS::URL* url, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newDynamicLibraryWithURL_error_), url, error); -} - -_MTL_INLINE MTL::BinaryArchive* MTL::Device::newBinaryArchive(const MTL::BinaryArchiveDescriptor* descriptor, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newBinaryArchiveWithDescriptor_error_), descriptor, error); -} - -_MTL_INLINE bool MTL::Device::supportsRaytracing() const -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(supportsRaytracing)); -} - -_MTL_INLINE MTL::AccelerationStructureSizes MTL::Device::accelerationStructureSizes(const MTL::AccelerationStructureDescriptor* descriptor) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(accelerationStructureSizesWithDescriptor_), descriptor); -} - -_MTL_INLINE MTL::AccelerationStructure* MTL::Device::newAccelerationStructure(NS::UInteger size) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newAccelerationStructureWithSize_), size); -} - -_MTL_INLINE MTL::AccelerationStructure* MTL::Device::newAccelerationStructure(const MTL::AccelerationStructureDescriptor* descriptor) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newAccelerationStructureWithDescriptor_), descriptor); -} - -_MTL_INLINE MTL::SizeAndAlign MTL::Device::heapAccelerationStructureSizeAndAlign(NS::UInteger size) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(heapAccelerationStructureSizeAndAlignWithSize_), size); -} - -_MTL_INLINE MTL::SizeAndAlign MTL::Device::heapAccelerationStructureSizeAndAlign(const MTL::AccelerationStructureDescriptor* descriptor) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(heapAccelerationStructureSizeAndAlignWithDescriptor_), descriptor); -} - -_MTL_INLINE bool MTL::Device::supportsFunctionPointers() const -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(supportsFunctionPointers)); -} - -_MTL_INLINE bool MTL::Device::supportsFunctionPointersFromRender() const -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(supportsFunctionPointersFromRender)); -} - -_MTL_INLINE bool MTL::Device::supportsRaytracingFromRender() const -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(supportsRaytracingFromRender)); -} - -_MTL_INLINE bool MTL::Device::supportsPrimitiveMotionBlur() const -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(supportsPrimitiveMotionBlur)); -} - -#pragma once - -namespace MTL -{ -_MTL_ENUM(NS::UInteger, DynamicLibraryError) { - DynamicLibraryErrorNone = 0, - DynamicLibraryErrorInvalidFile = 1, - DynamicLibraryErrorCompilationFailure = 2, - DynamicLibraryErrorUnresolvedInstallName = 3, - DynamicLibraryErrorDependencyLoadFailure = 4, - DynamicLibraryErrorUnsupported = 5, -}; - -class DynamicLibrary : public NS::Referencing -{ -public: - NS::String* label() const; - void setLabel(const NS::String* label); - - class Device* device() const; - - NS::String* installName() const; - - bool serializeToURL(const NS::URL* url, NS::Error** error); -}; - -} - -_MTL_INLINE NS::String* MTL::DynamicLibrary::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE void MTL::DynamicLibrary::setLabel(const NS::String* label) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLabel_), label); -} - -_MTL_INLINE MTL::Device* MTL::DynamicLibrary::device() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(device)); -} - -_MTL_INLINE NS::String* MTL::DynamicLibrary::installName() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(installName)); -} - -_MTL_INLINE bool MTL::DynamicLibrary::serializeToURL(const NS::URL* url, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(serializeToURL_error_), url, error); -} - -#pragma once - -namespace MTL -{ -class Event : public NS::Referencing -{ -public: - class Device* device() const; - - NS::String* label() const; - void setLabel(const NS::String* label); -}; - -class SharedEventListener : public NS::Referencing -{ -public: - static class SharedEventListener* alloc(); - - MTL::SharedEventListener* init(); - - MTL::SharedEventListener* init(const dispatch_queue_t dispatchQueue); - - dispatch_queue_t dispatchQueue() const; -}; - -using SharedEventNotificationBlock = void (^)(SharedEvent* pEvent, std::uint64_t value); - -class SharedEvent : public NS::Referencing -{ -public: - void notifyListener(const class SharedEventListener* listener, uint64_t value, const MTL::SharedEventNotificationBlock block); - - class SharedEventHandle* newSharedEventHandle(); - - uint64_t signaledValue() const; - void setSignaledValue(uint64_t signaledValue); -}; - -class SharedEventHandle : public NS::SecureCoding -{ -public: - static class SharedEventHandle* alloc(); - - class SharedEventHandle* init(); - - NS::String* label() const; -}; - -} - -_MTL_INLINE MTL::Device* MTL::Event::device() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(device)); -} - -_MTL_INLINE NS::String* MTL::Event::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE void MTL::Event::setLabel(const NS::String* label) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLabel_), label); -} - -_MTL_INLINE MTL::SharedEventListener* MTL::SharedEventListener::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLSharedEventListener)); -} - -_MTL_INLINE MTL::SharedEventListener* MTL::SharedEventListener::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::SharedEventListener* MTL::SharedEventListener::init(const dispatch_queue_t dispatchQueue) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(initWithDispatchQueue_), dispatchQueue); -} - -_MTL_INLINE dispatch_queue_t MTL::SharedEventListener::dispatchQueue() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(dispatchQueue)); -} - -_MTL_INLINE void MTL::SharedEvent::notifyListener(const MTL::SharedEventListener* listener, uint64_t value, const MTL::SharedEventNotificationBlock block) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(notifyListener_atValue_block_), listener, value, block); -} - -_MTL_INLINE MTL::SharedEventHandle* MTL::SharedEvent::newSharedEventHandle() -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newSharedEventHandle)); -} - -_MTL_INLINE uint64_t MTL::SharedEvent::signaledValue() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(signaledValue)); -} - -_MTL_INLINE void MTL::SharedEvent::setSignaledValue(uint64_t signaledValue) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSignaledValue_), signaledValue); -} - -_MTL_INLINE MTL::SharedEventHandle* MTL::SharedEventHandle::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLSharedEventHandle)); -} - -_MTL_INLINE MTL::SharedEventHandle* MTL::SharedEventHandle::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE NS::String* MTL::SharedEventHandle::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -#pragma once - -namespace MTL -{ -class Fence : public NS::Referencing -{ -public: - class Device* device() const; - - NS::String* label() const; - void setLabel(const NS::String* label); -}; - -} - -_MTL_INLINE MTL::Device* MTL::Fence::device() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(device)); -} - -_MTL_INLINE NS::String* MTL::Fence::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE void MTL::Fence::setLabel(const NS::String* label) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLabel_), label); -} - -#pragma once - -namespace MTL -{ -class FunctionConstantValues : public NS::Copying -{ -public: - static class FunctionConstantValues* alloc(); - - class FunctionConstantValues* init(); - - void setConstantValue(const void* value, MTL::DataType type, NS::UInteger index); - - void setConstantValues(const void* values, MTL::DataType type, NS::Range range); - - void setConstantValue(const void* value, MTL::DataType type, const NS::String* name); - - void reset(); -}; - -} - -_MTL_INLINE MTL::FunctionConstantValues* MTL::FunctionConstantValues::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLFunctionConstantValues)); -} - -_MTL_INLINE MTL::FunctionConstantValues* MTL::FunctionConstantValues::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE void MTL::FunctionConstantValues::setConstantValue(const void* value, MTL::DataType type, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setConstantValue_type_atIndex_), value, type, index); -} - -_MTL_INLINE void MTL::FunctionConstantValues::setConstantValues(const void* values, MTL::DataType type, NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setConstantValues_type_withRange_), values, type, range); -} - -_MTL_INLINE void MTL::FunctionConstantValues::setConstantValue(const void* value, MTL::DataType type, const NS::String* name) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setConstantValue_type_withName_), value, type, name); -} - -_MTL_INLINE void MTL::FunctionConstantValues::reset() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(reset)); -} - -#pragma once - -namespace MTL -{ -_MTL_OPTIONS(NS::UInteger, FunctionOptions) { - FunctionOptionNone = 0, - FunctionOptionCompileToBinary = 1, -}; - -class FunctionDescriptor : public NS::Copying -{ -public: - static class FunctionDescriptor* alloc(); - - class FunctionDescriptor* init(); - - static class FunctionDescriptor* functionDescriptor(); - - NS::String* name() const; - void setName(const NS::String* name); - - NS::String* specializedName() const; - void setSpecializedName(const NS::String* specializedName); - - class FunctionConstantValues* constantValues() const; - void setConstantValues(const class FunctionConstantValues* constantValues); - - MTL::FunctionOptions options() const; - void setOptions(MTL::FunctionOptions options); - - NS::Array* binaryArchives() const; - void setBinaryArchives(const NS::Array* binaryArchives); -}; - -class IntersectionFunctionDescriptor : public NS::Copying -{ -public: - static class IntersectionFunctionDescriptor* alloc(); - - class IntersectionFunctionDescriptor* init(); -}; - -} - -_MTL_INLINE MTL::FunctionDescriptor* MTL::FunctionDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLFunctionDescriptor)); -} - -_MTL_INLINE MTL::FunctionDescriptor* MTL::FunctionDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::FunctionDescriptor* MTL::FunctionDescriptor::functionDescriptor() -{ - return Object::sendMessage(_MTL_PRIVATE_CLS(MTLFunctionDescriptor), _MTL_PRIVATE_SEL(functionDescriptor)); -} - -_MTL_INLINE NS::String* MTL::FunctionDescriptor::name() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(name)); -} - -_MTL_INLINE void MTL::FunctionDescriptor::setName(const NS::String* name) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setName_), name); -} - -_MTL_INLINE NS::String* MTL::FunctionDescriptor::specializedName() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(specializedName)); -} - -_MTL_INLINE void MTL::FunctionDescriptor::setSpecializedName(const NS::String* specializedName) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSpecializedName_), specializedName); -} - -_MTL_INLINE MTL::FunctionConstantValues* MTL::FunctionDescriptor::constantValues() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(constantValues)); -} - -_MTL_INLINE void MTL::FunctionDescriptor::setConstantValues(const MTL::FunctionConstantValues* constantValues) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setConstantValues_), constantValues); -} - -_MTL_INLINE MTL::FunctionOptions MTL::FunctionDescriptor::options() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(options)); -} - -_MTL_INLINE void MTL::FunctionDescriptor::setOptions(MTL::FunctionOptions options) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setOptions_), options); -} - -_MTL_INLINE NS::Array* MTL::FunctionDescriptor::binaryArchives() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(binaryArchives)); -} - -_MTL_INLINE void MTL::FunctionDescriptor::setBinaryArchives(const NS::Array* binaryArchives) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setBinaryArchives_), binaryArchives); -} - -_MTL_INLINE MTL::IntersectionFunctionDescriptor* MTL::IntersectionFunctionDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLIntersectionFunctionDescriptor)); -} - -_MTL_INLINE MTL::IntersectionFunctionDescriptor* MTL::IntersectionFunctionDescriptor::init() -{ - return NS::Object::init(); -} - -#pragma once - -#pragma once - -#include - -namespace MTL -{ -_MTL_ENUM(NS::UInteger, PatchType) { - PatchTypeNone = 0, - PatchTypeTriangle = 1, - PatchTypeQuad = 2, -}; - -class VertexAttribute : public NS::Referencing -{ -public: - static class VertexAttribute* alloc(); - - class VertexAttribute* init(); - - NS::String* name() const; - - NS::UInteger attributeIndex() const; - - MTL::DataType attributeType() const; - - bool active() const; - - bool patchData() const; - - bool patchControlPointData() const; -}; - -class Attribute : public NS::Referencing -{ -public: - static class Attribute* alloc(); - - class Attribute* init(); - - NS::String* name() const; - - NS::UInteger attributeIndex() const; - - MTL::DataType attributeType() const; - - bool active() const; - - bool patchData() const; - - bool patchControlPointData() const; -}; - -_MTL_ENUM(NS::UInteger, FunctionType) { - FunctionTypeVertex = 1, - FunctionTypeFragment = 2, - FunctionTypeKernel = 3, - FunctionTypeVisible = 5, - FunctionTypeIntersection = 6, - FunctionTypeMesh = 7, - FunctionTypeObject = 8, -}; - -class FunctionConstant : public NS::Referencing -{ -public: - static class FunctionConstant* alloc(); - - class FunctionConstant* init(); - - NS::String* name() const; - - MTL::DataType type() const; - - NS::UInteger index() const; - - bool required() const; -}; - -using AutoreleasedArgument = class Argument*; - -class Function : public NS::Referencing -{ -public: - NS::String* label() const; - void setLabel(const NS::String* label); - - class Device* device() const; - - MTL::FunctionType functionType() const; - - MTL::PatchType patchType() const; - - NS::Integer patchControlPointCount() const; - - NS::Array* vertexAttributes() const; - - NS::Array* stageInputAttributes() const; - - NS::String* name() const; - - NS::Dictionary* functionConstantsDictionary() const; - - class ArgumentEncoder* newArgumentEncoder(NS::UInteger bufferIndex); - - class ArgumentEncoder* newArgumentEncoder(NS::UInteger bufferIndex, const MTL::AutoreleasedArgument* reflection); - - MTL::FunctionOptions options() const; -}; - -_MTL_ENUM(NS::UInteger, LanguageVersion) { - LanguageVersion1_0 = 65536, - LanguageVersion1_1 = 65537, - LanguageVersion1_2 = 65538, - LanguageVersion2_0 = 131072, - LanguageVersion2_1 = 131073, - LanguageVersion2_2 = 131074, - LanguageVersion2_3 = 131075, - LanguageVersion2_4 = 131076, - LanguageVersion3_0 = 196608, -}; - -_MTL_ENUM(NS::Integer, LibraryType) { - LibraryTypeExecutable = 0, - LibraryTypeDynamic = 1, -}; - -_MTL_ENUM(NS::Integer, LibraryOptimizationLevel) { - LibraryOptimizationLevelDefault = 0, - LibraryOptimizationLevelSize = 1, -}; - -class CompileOptions : public NS::Copying -{ -public: - static class CompileOptions* alloc(); - - class CompileOptions* init(); - - NS::Dictionary* preprocessorMacros() const; - void setPreprocessorMacros(const NS::Dictionary* preprocessorMacros); - - bool fastMathEnabled() const; - void setFastMathEnabled(bool fastMathEnabled); - - MTL::LanguageVersion languageVersion() const; - void setLanguageVersion(MTL::LanguageVersion languageVersion); - - MTL::LibraryType libraryType() const; - void setLibraryType(MTL::LibraryType libraryType); - - NS::String* installName() const; - void setInstallName(const NS::String* installName); - - NS::Array* libraries() const; - void setLibraries(const NS::Array* libraries); - - bool preserveInvariance() const; - void setPreserveInvariance(bool preserveInvariance); - - MTL::LibraryOptimizationLevel optimizationLevel() const; - void setOptimizationLevel(MTL::LibraryOptimizationLevel optimizationLevel); -}; - -_MTL_ENUM(NS::UInteger, LibraryError) { - LibraryErrorUnsupported = 1, - LibraryErrorInternal = 2, - LibraryErrorCompileFailure = 3, - LibraryErrorCompileWarning = 4, - LibraryErrorFunctionNotFound = 5, - LibraryErrorFileNotFound = 6, -}; - -class Library : public NS::Referencing -{ -public: - void newFunction(const NS::String* pFunctionName, const class FunctionConstantValues* pConstantValues, const std::function& completionHandler); - - void newFunction(const class FunctionDescriptor* pDescriptor, const std::function& completionHandler); - - void newIntersectionFunction(const class IntersectionFunctionDescriptor* pDescriptor, const std::function& completionHandler); - - NS::String* label() const; - void setLabel(const NS::String* label); - - class Device* device() const; - - class Function* newFunction(const NS::String* functionName); - - class Function* newFunction(const NS::String* name, const class FunctionConstantValues* constantValues, NS::Error** error); - - void newFunction(const NS::String* name, const class FunctionConstantValues* constantValues, void (^completionHandler)(MTL::Function*, NS::Error*)); - - void newFunction(const class FunctionDescriptor* descriptor, void (^completionHandler)(MTL::Function*, NS::Error*)); - - class Function* newFunction(const class FunctionDescriptor* descriptor, NS::Error** error); - - void newIntersectionFunction(const class IntersectionFunctionDescriptor* descriptor, void (^completionHandler)(MTL::Function*, NS::Error*)); - - class Function* newIntersectionFunction(const class IntersectionFunctionDescriptor* descriptor, NS::Error** error); - - NS::Array* functionNames() const; - - MTL::LibraryType type() const; - - NS::String* installName() const; -}; - -} - -_MTL_INLINE MTL::VertexAttribute* MTL::VertexAttribute::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLVertexAttribute)); -} - -_MTL_INLINE MTL::VertexAttribute* MTL::VertexAttribute::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE NS::String* MTL::VertexAttribute::name() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(name)); -} - -_MTL_INLINE NS::UInteger MTL::VertexAttribute::attributeIndex() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(attributeIndex)); -} - -_MTL_INLINE MTL::DataType MTL::VertexAttribute::attributeType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(attributeType)); -} - -_MTL_INLINE bool MTL::VertexAttribute::active() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(isActive)); -} - -_MTL_INLINE bool MTL::VertexAttribute::patchData() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(isPatchData)); -} - -_MTL_INLINE bool MTL::VertexAttribute::patchControlPointData() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(isPatchControlPointData)); -} - -_MTL_INLINE MTL::Attribute* MTL::Attribute::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLAttribute)); -} - -_MTL_INLINE MTL::Attribute* MTL::Attribute::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE NS::String* MTL::Attribute::name() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(name)); -} - -_MTL_INLINE NS::UInteger MTL::Attribute::attributeIndex() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(attributeIndex)); -} - -_MTL_INLINE MTL::DataType MTL::Attribute::attributeType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(attributeType)); -} - -_MTL_INLINE bool MTL::Attribute::active() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(isActive)); -} - -_MTL_INLINE bool MTL::Attribute::patchData() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(isPatchData)); -} - -_MTL_INLINE bool MTL::Attribute::patchControlPointData() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(isPatchControlPointData)); -} - -_MTL_INLINE MTL::FunctionConstant* MTL::FunctionConstant::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLFunctionConstant)); -} - -_MTL_INLINE MTL::FunctionConstant* MTL::FunctionConstant::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE NS::String* MTL::FunctionConstant::name() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(name)); -} - -_MTL_INLINE MTL::DataType MTL::FunctionConstant::type() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(type)); -} - -_MTL_INLINE NS::UInteger MTL::FunctionConstant::index() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(index)); -} - -_MTL_INLINE bool MTL::FunctionConstant::required() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(required)); -} - -_MTL_INLINE NS::String* MTL::Function::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE void MTL::Function::setLabel(const NS::String* label) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLabel_), label); -} - -_MTL_INLINE MTL::Device* MTL::Function::device() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(device)); -} - -_MTL_INLINE MTL::FunctionType MTL::Function::functionType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(functionType)); -} - -_MTL_INLINE MTL::PatchType MTL::Function::patchType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(patchType)); -} - -_MTL_INLINE NS::Integer MTL::Function::patchControlPointCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(patchControlPointCount)); -} - -_MTL_INLINE NS::Array* MTL::Function::vertexAttributes() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(vertexAttributes)); -} - -_MTL_INLINE NS::Array* MTL::Function::stageInputAttributes() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(stageInputAttributes)); -} - -_MTL_INLINE NS::String* MTL::Function::name() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(name)); -} - -_MTL_INLINE NS::Dictionary* MTL::Function::functionConstantsDictionary() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(functionConstantsDictionary)); -} - -_MTL_INLINE MTL::ArgumentEncoder* MTL::Function::newArgumentEncoder(NS::UInteger bufferIndex) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newArgumentEncoderWithBufferIndex_), bufferIndex); -} - -_MTL_INLINE MTL::ArgumentEncoder* MTL::Function::newArgumentEncoder(NS::UInteger bufferIndex, const MTL::AutoreleasedArgument* reflection) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newArgumentEncoderWithBufferIndex_reflection_), bufferIndex, reflection); -} - -_MTL_INLINE MTL::FunctionOptions MTL::Function::options() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(options)); -} - -_MTL_INLINE MTL::CompileOptions* MTL::CompileOptions::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLCompileOptions)); -} - -_MTL_INLINE MTL::CompileOptions* MTL::CompileOptions::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE NS::Dictionary* MTL::CompileOptions::preprocessorMacros() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(preprocessorMacros)); -} - -_MTL_INLINE void MTL::CompileOptions::setPreprocessorMacros(const NS::Dictionary* preprocessorMacros) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setPreprocessorMacros_), preprocessorMacros); -} - -_MTL_INLINE bool MTL::CompileOptions::fastMathEnabled() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(fastMathEnabled)); -} - -_MTL_INLINE void MTL::CompileOptions::setFastMathEnabled(bool fastMathEnabled) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFastMathEnabled_), fastMathEnabled); -} - -_MTL_INLINE MTL::LanguageVersion MTL::CompileOptions::languageVersion() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(languageVersion)); -} - -_MTL_INLINE void MTL::CompileOptions::setLanguageVersion(MTL::LanguageVersion languageVersion) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLanguageVersion_), languageVersion); -} - -_MTL_INLINE MTL::LibraryType MTL::CompileOptions::libraryType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(libraryType)); -} - -_MTL_INLINE void MTL::CompileOptions::setLibraryType(MTL::LibraryType libraryType) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLibraryType_), libraryType); -} - -_MTL_INLINE NS::String* MTL::CompileOptions::installName() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(installName)); -} - -_MTL_INLINE void MTL::CompileOptions::setInstallName(const NS::String* installName) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setInstallName_), installName); -} - -_MTL_INLINE NS::Array* MTL::CompileOptions::libraries() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(libraries)); -} - -_MTL_INLINE void MTL::CompileOptions::setLibraries(const NS::Array* libraries) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLibraries_), libraries); -} - -_MTL_INLINE bool MTL::CompileOptions::preserveInvariance() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(preserveInvariance)); -} - -_MTL_INLINE void MTL::CompileOptions::setPreserveInvariance(bool preserveInvariance) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setPreserveInvariance_), preserveInvariance); -} - -_MTL_INLINE MTL::LibraryOptimizationLevel MTL::CompileOptions::optimizationLevel() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(optimizationLevel)); -} - -_MTL_INLINE void MTL::CompileOptions::setOptimizationLevel(MTL::LibraryOptimizationLevel optimizationLevel) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setOptimizationLevel_), optimizationLevel); -} - -_MTL_INLINE void MTL::Library::newFunction(const NS::String* pFunctionName, const FunctionConstantValues* pConstantValues, const std::function& completionHandler) -{ - __block std::function blockCompletionHandler = completionHandler; - - newFunction(pFunctionName, pConstantValues, ^(Function* pFunction, NS::Error* pError) { blockCompletionHandler(pFunction, pError); }); -} - -_MTL_INLINE void MTL::Library::newFunction(const FunctionDescriptor* pDescriptor, const std::function& completionHandler) -{ - __block std::function blockCompletionHandler = completionHandler; - - newFunction(pDescriptor, ^(Function* pFunction, NS::Error* pError) { blockCompletionHandler(pFunction, pError); }); -} - -_MTL_INLINE void MTL::Library::newIntersectionFunction(const IntersectionFunctionDescriptor* pDescriptor, const std::function& completionHandler) -{ - __block std::function blockCompletionHandler = completionHandler; - - newIntersectionFunction(pDescriptor, ^(Function* pFunction, NS::Error* pError) { blockCompletionHandler(pFunction, pError); }); -} - -_MTL_INLINE NS::String* MTL::Library::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE void MTL::Library::setLabel(const NS::String* label) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLabel_), label); -} - -_MTL_INLINE MTL::Device* MTL::Library::device() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(device)); -} - -_MTL_INLINE MTL::Function* MTL::Library::newFunction(const NS::String* functionName) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newFunctionWithName_), functionName); -} - -_MTL_INLINE MTL::Function* MTL::Library::newFunction(const NS::String* name, const MTL::FunctionConstantValues* constantValues, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newFunctionWithName_constantValues_error_), name, constantValues, error); -} - -_MTL_INLINE void MTL::Library::newFunction(const NS::String* name, const MTL::FunctionConstantValues* constantValues, void (^completionHandler)(MTL::Function*, NS::Error*)) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(newFunctionWithName_constantValues_completionHandler_), name, constantValues, completionHandler); -} - -_MTL_INLINE void MTL::Library::newFunction(const MTL::FunctionDescriptor* descriptor, void (^completionHandler)(MTL::Function*, NS::Error*)) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(newFunctionWithDescriptor_completionHandler_), descriptor, completionHandler); -} - -_MTL_INLINE MTL::Function* MTL::Library::newFunction(const MTL::FunctionDescriptor* descriptor, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newFunctionWithDescriptor_error_), descriptor, error); -} - -_MTL_INLINE void MTL::Library::newIntersectionFunction(const MTL::IntersectionFunctionDescriptor* descriptor, void (^completionHandler)(MTL::Function*, NS::Error*)) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(newIntersectionFunctionWithDescriptor_completionHandler_), descriptor, completionHandler); -} - -_MTL_INLINE MTL::Function* MTL::Library::newIntersectionFunction(const MTL::IntersectionFunctionDescriptor* descriptor, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newIntersectionFunctionWithDescriptor_error_), descriptor, error); -} - -_MTL_INLINE NS::Array* MTL::Library::functionNames() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(functionNames)); -} - -_MTL_INLINE MTL::LibraryType MTL::Library::type() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(type)); -} - -_MTL_INLINE NS::String* MTL::Library::installName() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(installName)); -} - -namespace MTL -{ -class FunctionHandle : public NS::Referencing -{ -public: - MTL::FunctionType functionType() const; - - NS::String* name() const; - - class Device* device() const; -}; - -} - -_MTL_INLINE MTL::FunctionType MTL::FunctionHandle::functionType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(functionType)); -} - -_MTL_INLINE NS::String* MTL::FunctionHandle::name() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(name)); -} - -_MTL_INLINE MTL::Device* MTL::FunctionHandle::device() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(device)); -} - -#pragma once - -namespace MTL -{ -_MTL_ENUM(NS::UInteger, FunctionLogType) { - FunctionLogTypeValidation = 0, -}; - -class LogContainer : public NS::Referencing -{ -public: -}; - -class FunctionLogDebugLocation : public NS::Referencing -{ -public: - NS::String* functionName() const; - - NS::URL* URL() const; - - NS::UInteger line() const; - - NS::UInteger column() const; -}; - -class FunctionLog : public NS::Referencing -{ -public: - MTL::FunctionLogType type() const; - - NS::String* encoderLabel() const; - - class Function* function() const; - - class FunctionLogDebugLocation* debugLocation() const; -}; - -} - -_MTL_INLINE NS::String* MTL::FunctionLogDebugLocation::functionName() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(functionName)); -} - -_MTL_INLINE NS::URL* MTL::FunctionLogDebugLocation::URL() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(URL)); -} - -_MTL_INLINE NS::UInteger MTL::FunctionLogDebugLocation::line() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(line)); -} - -_MTL_INLINE NS::UInteger MTL::FunctionLogDebugLocation::column() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(column)); -} - -_MTL_INLINE MTL::FunctionLogType MTL::FunctionLog::type() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(type)); -} - -_MTL_INLINE NS::String* MTL::FunctionLog::encoderLabel() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(encoderLabel)); -} - -_MTL_INLINE MTL::Function* MTL::FunctionLog::function() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(function)); -} - -_MTL_INLINE MTL::FunctionLogDebugLocation* MTL::FunctionLog::debugLocation() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(debugLocation)); -} - -#pragma once - -namespace MTL -{ -class FunctionStitchingAttribute : public NS::Referencing -{ -}; - -class FunctionStitchingAttributeAlwaysInline : public NS::Referencing -{ -public: - static class FunctionStitchingAttributeAlwaysInline* alloc(); - - class FunctionStitchingAttributeAlwaysInline* init(); -}; - -class FunctionStitchingNode : public NS::Copying -{ -}; - -class FunctionStitchingInputNode : public NS::Referencing -{ -public: - static class FunctionStitchingInputNode* alloc(); - - class FunctionStitchingInputNode* init(); - - NS::UInteger argumentIndex() const; - void setArgumentIndex(NS::UInteger argumentIndex); - - MTL::FunctionStitchingInputNode* init(NS::UInteger argument); -}; - -class FunctionStitchingFunctionNode : public NS::Referencing -{ -public: - static class FunctionStitchingFunctionNode* alloc(); - - class FunctionStitchingFunctionNode* init(); - - NS::String* name() const; - void setName(const NS::String* name); - - NS::Array* arguments() const; - void setArguments(const NS::Array* arguments); - - NS::Array* controlDependencies() const; - void setControlDependencies(const NS::Array* controlDependencies); - - MTL::FunctionStitchingFunctionNode* init(const NS::String* name, const NS::Array* arguments, const NS::Array* controlDependencies); -}; - -class FunctionStitchingGraph : public NS::Copying -{ -public: - static class FunctionStitchingGraph* alloc(); - - class FunctionStitchingGraph* init(); - - NS::String* functionName() const; - void setFunctionName(const NS::String* functionName); - - NS::Array* nodes() const; - void setNodes(const NS::Array* nodes); - - class FunctionStitchingFunctionNode* outputNode() const; - void setOutputNode(const class FunctionStitchingFunctionNode* outputNode); - - NS::Array* attributes() const; - void setAttributes(const NS::Array* attributes); - - MTL::FunctionStitchingGraph* init(const NS::String* functionName, const NS::Array* nodes, const class FunctionStitchingFunctionNode* outputNode, const NS::Array* attributes); -}; - -class StitchedLibraryDescriptor : public NS::Copying -{ -public: - static class StitchedLibraryDescriptor* alloc(); - - class StitchedLibraryDescriptor* init(); - - NS::Array* functionGraphs() const; - void setFunctionGraphs(const NS::Array* functionGraphs); - - NS::Array* functions() const; - void setFunctions(const NS::Array* functions); -}; - -} - -_MTL_INLINE MTL::FunctionStitchingAttributeAlwaysInline* MTL::FunctionStitchingAttributeAlwaysInline::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLFunctionStitchingAttributeAlwaysInline)); -} - -_MTL_INLINE MTL::FunctionStitchingAttributeAlwaysInline* MTL::FunctionStitchingAttributeAlwaysInline::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::FunctionStitchingInputNode* MTL::FunctionStitchingInputNode::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLFunctionStitchingInputNode)); -} - -_MTL_INLINE MTL::FunctionStitchingInputNode* MTL::FunctionStitchingInputNode::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE NS::UInteger MTL::FunctionStitchingInputNode::argumentIndex() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(argumentIndex)); -} - -_MTL_INLINE void MTL::FunctionStitchingInputNode::setArgumentIndex(NS::UInteger argumentIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setArgumentIndex_), argumentIndex); -} - -_MTL_INLINE MTL::FunctionStitchingInputNode* MTL::FunctionStitchingInputNode::init(NS::UInteger argument) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(initWithArgumentIndex_), argument); -} - -_MTL_INLINE MTL::FunctionStitchingFunctionNode* MTL::FunctionStitchingFunctionNode::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLFunctionStitchingFunctionNode)); -} - -_MTL_INLINE MTL::FunctionStitchingFunctionNode* MTL::FunctionStitchingFunctionNode::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE NS::String* MTL::FunctionStitchingFunctionNode::name() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(name)); -} - -_MTL_INLINE void MTL::FunctionStitchingFunctionNode::setName(const NS::String* name) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setName_), name); -} - -_MTL_INLINE NS::Array* MTL::FunctionStitchingFunctionNode::arguments() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(arguments)); -} - -_MTL_INLINE void MTL::FunctionStitchingFunctionNode::setArguments(const NS::Array* arguments) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setArguments_), arguments); -} - -_MTL_INLINE NS::Array* MTL::FunctionStitchingFunctionNode::controlDependencies() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(controlDependencies)); -} - -_MTL_INLINE void MTL::FunctionStitchingFunctionNode::setControlDependencies(const NS::Array* controlDependencies) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setControlDependencies_), controlDependencies); -} - -_MTL_INLINE MTL::FunctionStitchingFunctionNode* MTL::FunctionStitchingFunctionNode::init(const NS::String* name, const NS::Array* arguments, const NS::Array* controlDependencies) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(initWithName_arguments_controlDependencies_), name, arguments, controlDependencies); -} - -_MTL_INLINE MTL::FunctionStitchingGraph* MTL::FunctionStitchingGraph::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLFunctionStitchingGraph)); -} - -_MTL_INLINE MTL::FunctionStitchingGraph* MTL::FunctionStitchingGraph::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE NS::String* MTL::FunctionStitchingGraph::functionName() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(functionName)); -} - -_MTL_INLINE void MTL::FunctionStitchingGraph::setFunctionName(const NS::String* functionName) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFunctionName_), functionName); -} - -_MTL_INLINE NS::Array* MTL::FunctionStitchingGraph::nodes() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(nodes)); -} - -_MTL_INLINE void MTL::FunctionStitchingGraph::setNodes(const NS::Array* nodes) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setNodes_), nodes); -} - -_MTL_INLINE MTL::FunctionStitchingFunctionNode* MTL::FunctionStitchingGraph::outputNode() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(outputNode)); -} - -_MTL_INLINE void MTL::FunctionStitchingGraph::setOutputNode(const MTL::FunctionStitchingFunctionNode* outputNode) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setOutputNode_), outputNode); -} - -_MTL_INLINE NS::Array* MTL::FunctionStitchingGraph::attributes() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(attributes)); -} - -_MTL_INLINE void MTL::FunctionStitchingGraph::setAttributes(const NS::Array* attributes) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setAttributes_), attributes); -} - -_MTL_INLINE MTL::FunctionStitchingGraph* MTL::FunctionStitchingGraph::init(const NS::String* functionName, const NS::Array* nodes, const MTL::FunctionStitchingFunctionNode* outputNode, const NS::Array* attributes) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(initWithFunctionName_nodes_outputNode_attributes_), functionName, nodes, outputNode, attributes); -} - -_MTL_INLINE MTL::StitchedLibraryDescriptor* MTL::StitchedLibraryDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLStitchedLibraryDescriptor)); -} - -_MTL_INLINE MTL::StitchedLibraryDescriptor* MTL::StitchedLibraryDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE NS::Array* MTL::StitchedLibraryDescriptor::functionGraphs() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(functionGraphs)); -} - -_MTL_INLINE void MTL::StitchedLibraryDescriptor::setFunctionGraphs(const NS::Array* functionGraphs) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFunctionGraphs_), functionGraphs); -} - -_MTL_INLINE NS::Array* MTL::StitchedLibraryDescriptor::functions() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(functions)); -} - -_MTL_INLINE void MTL::StitchedLibraryDescriptor::setFunctions(const NS::Array* functions) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFunctions_), functions); -} - -#pragma once - -namespace MTL -{ -_MTL_ENUM(NS::Integer, HeapType) { - HeapTypeAutomatic = 0, - HeapTypePlacement = 1, - HeapTypeSparse = 2, -}; - -class HeapDescriptor : public NS::Copying -{ -public: - static class HeapDescriptor* alloc(); - - class HeapDescriptor* init(); - - NS::UInteger size() const; - void setSize(NS::UInteger size); - - MTL::StorageMode storageMode() const; - void setStorageMode(MTL::StorageMode storageMode); - - MTL::CPUCacheMode cpuCacheMode() const; - void setCpuCacheMode(MTL::CPUCacheMode cpuCacheMode); - - MTL::SparsePageSize sparsePageSize() const; - void setSparsePageSize(MTL::SparsePageSize sparsePageSize); - - MTL::HazardTrackingMode hazardTrackingMode() const; - void setHazardTrackingMode(MTL::HazardTrackingMode hazardTrackingMode); - - MTL::ResourceOptions resourceOptions() const; - void setResourceOptions(MTL::ResourceOptions resourceOptions); - - MTL::HeapType type() const; - void setType(MTL::HeapType type); -}; - -class Heap : public NS::Referencing -{ -public: - NS::String* label() const; - void setLabel(const NS::String* label); - - class Device* device() const; - - MTL::StorageMode storageMode() const; - - MTL::CPUCacheMode cpuCacheMode() const; - - MTL::HazardTrackingMode hazardTrackingMode() const; - - MTL::ResourceOptions resourceOptions() const; - - NS::UInteger size() const; - - NS::UInteger usedSize() const; - - NS::UInteger currentAllocatedSize() const; - - NS::UInteger maxAvailableSize(NS::UInteger alignment); - - class Buffer* newBuffer(NS::UInteger length, MTL::ResourceOptions options); - - class Texture* newTexture(const class TextureDescriptor* desc); - - MTL::PurgeableState setPurgeableState(MTL::PurgeableState state); - - MTL::HeapType type() const; - - class Buffer* newBuffer(NS::UInteger length, MTL::ResourceOptions options, NS::UInteger offset); - - class Texture* newTexture(const class TextureDescriptor* descriptor, NS::UInteger offset); - - class AccelerationStructure* newAccelerationStructure(NS::UInteger size); - - class AccelerationStructure* newAccelerationStructure(const class AccelerationStructureDescriptor* descriptor); - - class AccelerationStructure* newAccelerationStructure(NS::UInteger size, NS::UInteger offset); - - class AccelerationStructure* newAccelerationStructure(const class AccelerationStructureDescriptor* descriptor, NS::UInteger offset); -}; - -} - -_MTL_INLINE MTL::HeapDescriptor* MTL::HeapDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLHeapDescriptor)); -} - -_MTL_INLINE MTL::HeapDescriptor* MTL::HeapDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE NS::UInteger MTL::HeapDescriptor::size() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(size)); -} - -_MTL_INLINE void MTL::HeapDescriptor::setSize(NS::UInteger size) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSize_), size); -} - -_MTL_INLINE MTL::StorageMode MTL::HeapDescriptor::storageMode() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(storageMode)); -} - -_MTL_INLINE void MTL::HeapDescriptor::setStorageMode(MTL::StorageMode storageMode) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStorageMode_), storageMode); -} - -_MTL_INLINE MTL::CPUCacheMode MTL::HeapDescriptor::cpuCacheMode() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(cpuCacheMode)); -} - -_MTL_INLINE void MTL::HeapDescriptor::setCpuCacheMode(MTL::CPUCacheMode cpuCacheMode) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setCpuCacheMode_), cpuCacheMode); -} - -_MTL_INLINE MTL::SparsePageSize MTL::HeapDescriptor::sparsePageSize() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(sparsePageSize)); -} - -_MTL_INLINE void MTL::HeapDescriptor::setSparsePageSize(MTL::SparsePageSize sparsePageSize) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSparsePageSize_), sparsePageSize); -} - -_MTL_INLINE MTL::HazardTrackingMode MTL::HeapDescriptor::hazardTrackingMode() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(hazardTrackingMode)); -} - -_MTL_INLINE void MTL::HeapDescriptor::setHazardTrackingMode(MTL::HazardTrackingMode hazardTrackingMode) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setHazardTrackingMode_), hazardTrackingMode); -} - -_MTL_INLINE MTL::ResourceOptions MTL::HeapDescriptor::resourceOptions() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(resourceOptions)); -} - -_MTL_INLINE void MTL::HeapDescriptor::setResourceOptions(MTL::ResourceOptions resourceOptions) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setResourceOptions_), resourceOptions); -} - -_MTL_INLINE MTL::HeapType MTL::HeapDescriptor::type() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(type)); -} - -_MTL_INLINE void MTL::HeapDescriptor::setType(MTL::HeapType type) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setType_), type); -} - -_MTL_INLINE NS::String* MTL::Heap::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE void MTL::Heap::setLabel(const NS::String* label) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLabel_), label); -} - -_MTL_INLINE MTL::Device* MTL::Heap::device() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(device)); -} - -_MTL_INLINE MTL::StorageMode MTL::Heap::storageMode() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(storageMode)); -} - -_MTL_INLINE MTL::CPUCacheMode MTL::Heap::cpuCacheMode() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(cpuCacheMode)); -} - -_MTL_INLINE MTL::HazardTrackingMode MTL::Heap::hazardTrackingMode() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(hazardTrackingMode)); -} - -_MTL_INLINE MTL::ResourceOptions MTL::Heap::resourceOptions() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(resourceOptions)); -} - -_MTL_INLINE NS::UInteger MTL::Heap::size() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(size)); -} - -_MTL_INLINE NS::UInteger MTL::Heap::usedSize() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(usedSize)); -} - -_MTL_INLINE NS::UInteger MTL::Heap::currentAllocatedSize() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(currentAllocatedSize)); -} - -_MTL_INLINE NS::UInteger MTL::Heap::maxAvailableSize(NS::UInteger alignment) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(maxAvailableSizeWithAlignment_), alignment); -} - -_MTL_INLINE MTL::Buffer* MTL::Heap::newBuffer(NS::UInteger length, MTL::ResourceOptions options) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newBufferWithLength_options_), length, options); -} - -_MTL_INLINE MTL::Texture* MTL::Heap::newTexture(const MTL::TextureDescriptor* desc) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newTextureWithDescriptor_), desc); -} - -_MTL_INLINE MTL::PurgeableState MTL::Heap::setPurgeableState(MTL::PurgeableState state) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(setPurgeableState_), state); -} - -_MTL_INLINE MTL::HeapType MTL::Heap::type() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(type)); -} - -_MTL_INLINE MTL::Buffer* MTL::Heap::newBuffer(NS::UInteger length, MTL::ResourceOptions options, NS::UInteger offset) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newBufferWithLength_options_offset_), length, options, offset); -} - -_MTL_INLINE MTL::Texture* MTL::Heap::newTexture(const MTL::TextureDescriptor* descriptor, NS::UInteger offset) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newTextureWithDescriptor_offset_), descriptor, offset); -} - -_MTL_INLINE MTL::AccelerationStructure* MTL::Heap::newAccelerationStructure(NS::UInteger size) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newAccelerationStructureWithSize_), size); -} - -_MTL_INLINE MTL::AccelerationStructure* MTL::Heap::newAccelerationStructure(const MTL::AccelerationStructureDescriptor* descriptor) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newAccelerationStructureWithDescriptor_), descriptor); -} - -_MTL_INLINE MTL::AccelerationStructure* MTL::Heap::newAccelerationStructure(NS::UInteger size, NS::UInteger offset) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newAccelerationStructureWithSize_offset_), size, offset); -} - -_MTL_INLINE MTL::AccelerationStructure* MTL::Heap::newAccelerationStructure(const MTL::AccelerationStructureDescriptor* descriptor, NS::UInteger offset) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newAccelerationStructureWithDescriptor_offset_), descriptor, offset); -} - -#pragma once - -namespace MTL -{ -_MTL_OPTIONS(NS::UInteger, IndirectCommandType) { - IndirectCommandTypeDraw = 1, - IndirectCommandTypeDrawIndexed = 2, - IndirectCommandTypeDrawPatches = 4, - IndirectCommandTypeDrawIndexedPatches = 8, - IndirectCommandTypeConcurrentDispatch = 32, - IndirectCommandTypeConcurrentDispatchThreads = 64, -}; - -struct IndirectCommandBufferExecutionRange -{ - uint32_t location; - uint32_t length; -} _MTL_PACKED; - -class IndirectCommandBufferDescriptor : public NS::Copying -{ -public: - static class IndirectCommandBufferDescriptor* alloc(); - - class IndirectCommandBufferDescriptor* init(); - - MTL::IndirectCommandType commandTypes() const; - void setCommandTypes(MTL::IndirectCommandType commandTypes); - - bool inheritPipelineState() const; - void setInheritPipelineState(bool inheritPipelineState); - - bool inheritBuffers() const; - void setInheritBuffers(bool inheritBuffers); - - NS::UInteger maxVertexBufferBindCount() const; - void setMaxVertexBufferBindCount(NS::UInteger maxVertexBufferBindCount); - - NS::UInteger maxFragmentBufferBindCount() const; - void setMaxFragmentBufferBindCount(NS::UInteger maxFragmentBufferBindCount); - - NS::UInteger maxKernelBufferBindCount() const; - void setMaxKernelBufferBindCount(NS::UInteger maxKernelBufferBindCount); - - bool supportRayTracing() const; - void setSupportRayTracing(bool supportRayTracing); -}; - -class IndirectCommandBuffer : public NS::Referencing -{ -public: - NS::UInteger size() const; - - MTL::ResourceID gpuResourceID() const; - - void reset(NS::Range range); - - class IndirectRenderCommand* indirectRenderCommand(NS::UInteger commandIndex); - - class IndirectComputeCommand* indirectComputeCommand(NS::UInteger commandIndex); -}; - -} - -_MTL_INLINE MTL::IndirectCommandBufferDescriptor* MTL::IndirectCommandBufferDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLIndirectCommandBufferDescriptor)); -} - -_MTL_INLINE MTL::IndirectCommandBufferDescriptor* MTL::IndirectCommandBufferDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::IndirectCommandType MTL::IndirectCommandBufferDescriptor::commandTypes() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(commandTypes)); -} - -_MTL_INLINE void MTL::IndirectCommandBufferDescriptor::setCommandTypes(MTL::IndirectCommandType commandTypes) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setCommandTypes_), commandTypes); -} - -_MTL_INLINE bool MTL::IndirectCommandBufferDescriptor::inheritPipelineState() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(inheritPipelineState)); -} - -_MTL_INLINE void MTL::IndirectCommandBufferDescriptor::setInheritPipelineState(bool inheritPipelineState) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setInheritPipelineState_), inheritPipelineState); -} - -_MTL_INLINE bool MTL::IndirectCommandBufferDescriptor::inheritBuffers() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(inheritBuffers)); -} - -_MTL_INLINE void MTL::IndirectCommandBufferDescriptor::setInheritBuffers(bool inheritBuffers) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setInheritBuffers_), inheritBuffers); -} - -_MTL_INLINE NS::UInteger MTL::IndirectCommandBufferDescriptor::maxVertexBufferBindCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(maxVertexBufferBindCount)); -} - -_MTL_INLINE void MTL::IndirectCommandBufferDescriptor::setMaxVertexBufferBindCount(NS::UInteger maxVertexBufferBindCount) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMaxVertexBufferBindCount_), maxVertexBufferBindCount); -} - -_MTL_INLINE NS::UInteger MTL::IndirectCommandBufferDescriptor::maxFragmentBufferBindCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(maxFragmentBufferBindCount)); -} - -_MTL_INLINE void MTL::IndirectCommandBufferDescriptor::setMaxFragmentBufferBindCount(NS::UInteger maxFragmentBufferBindCount) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMaxFragmentBufferBindCount_), maxFragmentBufferBindCount); -} - -_MTL_INLINE NS::UInteger MTL::IndirectCommandBufferDescriptor::maxKernelBufferBindCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(maxKernelBufferBindCount)); -} - -_MTL_INLINE void MTL::IndirectCommandBufferDescriptor::setMaxKernelBufferBindCount(NS::UInteger maxKernelBufferBindCount) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMaxKernelBufferBindCount_), maxKernelBufferBindCount); -} - -_MTL_INLINE bool MTL::IndirectCommandBufferDescriptor::supportRayTracing() const -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(supportRayTracing)); -} - -_MTL_INLINE void MTL::IndirectCommandBufferDescriptor::setSupportRayTracing(bool supportRayTracing) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSupportRayTracing_), supportRayTracing); -} - -_MTL_INLINE NS::UInteger MTL::IndirectCommandBuffer::size() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(size)); -} - -_MTL_INLINE MTL::ResourceID MTL::IndirectCommandBuffer::gpuResourceID() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(gpuResourceID)); -} - -_MTL_INLINE void MTL::IndirectCommandBuffer::reset(NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(resetWithRange_), range); -} - -_MTL_INLINE MTL::IndirectRenderCommand* MTL::IndirectCommandBuffer::indirectRenderCommand(NS::UInteger commandIndex) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(indirectRenderCommandAtIndex_), commandIndex); -} - -_MTL_INLINE MTL::IndirectComputeCommand* MTL::IndirectCommandBuffer::indirectComputeCommand(NS::UInteger commandIndex) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(indirectComputeCommandAtIndex_), commandIndex); -} - -#pragma once - -#pragma once - -#pragma once - -namespace MTL -{ -struct ClearColor -{ - static ClearColor Make(double red, double green, double blue, double alpha); - - ClearColor() = default; - - ClearColor(double red, double green, double blue, double alpha); - - double red; - double green; - double blue; - double alpha; -} _MTL_PACKED; - -_MTL_ENUM(NS::UInteger, LoadAction) { - LoadActionDontCare = 0, - LoadActionLoad = 1, - LoadActionClear = 2, -}; - -_MTL_ENUM(NS::UInteger, StoreAction) { - StoreActionDontCare = 0, - StoreActionStore = 1, - StoreActionMultisampleResolve = 2, - StoreActionStoreAndMultisampleResolve = 3, - StoreActionUnknown = 4, - StoreActionCustomSampleDepthStore = 5, -}; - -_MTL_OPTIONS(NS::UInteger, StoreActionOptions) { - StoreActionOptionNone = 0, - StoreActionOptionValidMask = 1, - StoreActionOptionCustomSamplePositions = 1, -}; - -class RenderPassAttachmentDescriptor : public NS::Copying -{ -public: - static class RenderPassAttachmentDescriptor* alloc(); - - class RenderPassAttachmentDescriptor* init(); - - class Texture* texture() const; - void setTexture(const class Texture* texture); - - NS::UInteger level() const; - void setLevel(NS::UInteger level); - - NS::UInteger slice() const; - void setSlice(NS::UInteger slice); - - NS::UInteger depthPlane() const; - void setDepthPlane(NS::UInteger depthPlane); - - class Texture* resolveTexture() const; - void setResolveTexture(const class Texture* resolveTexture); - - NS::UInteger resolveLevel() const; - void setResolveLevel(NS::UInteger resolveLevel); - - NS::UInteger resolveSlice() const; - void setResolveSlice(NS::UInteger resolveSlice); - - NS::UInteger resolveDepthPlane() const; - void setResolveDepthPlane(NS::UInteger resolveDepthPlane); - - MTL::LoadAction loadAction() const; - void setLoadAction(MTL::LoadAction loadAction); - - MTL::StoreAction storeAction() const; - void setStoreAction(MTL::StoreAction storeAction); - - MTL::StoreActionOptions storeActionOptions() const; - void setStoreActionOptions(MTL::StoreActionOptions storeActionOptions); -}; - -class RenderPassColorAttachmentDescriptor : public NS::Copying -{ -public: - static class RenderPassColorAttachmentDescriptor* alloc(); - - class RenderPassColorAttachmentDescriptor* init(); - - MTL::ClearColor clearColor() const; - void setClearColor(MTL::ClearColor clearColor); -}; - -_MTL_ENUM(NS::UInteger, MultisampleDepthResolveFilter) { - MultisampleDepthResolveFilterSample0 = 0, - MultisampleDepthResolveFilterMin = 1, - MultisampleDepthResolveFilterMax = 2, -}; - -class RenderPassDepthAttachmentDescriptor : public NS::Copying -{ -public: - static class RenderPassDepthAttachmentDescriptor* alloc(); - - class RenderPassDepthAttachmentDescriptor* init(); - - double clearDepth() const; - void setClearDepth(double clearDepth); - - MTL::MultisampleDepthResolveFilter depthResolveFilter() const; - void setDepthResolveFilter(MTL::MultisampleDepthResolveFilter depthResolveFilter); -}; - -_MTL_ENUM(NS::UInteger, MultisampleStencilResolveFilter) { - MultisampleStencilResolveFilterSample0 = 0, - MultisampleStencilResolveFilterDepthResolvedSample = 1, -}; - -class RenderPassStencilAttachmentDescriptor : public NS::Copying -{ -public: - static class RenderPassStencilAttachmentDescriptor* alloc(); - - class RenderPassStencilAttachmentDescriptor* init(); - - uint32_t clearStencil() const; - void setClearStencil(uint32_t clearStencil); - - MTL::MultisampleStencilResolveFilter stencilResolveFilter() const; - void setStencilResolveFilter(MTL::MultisampleStencilResolveFilter stencilResolveFilter); -}; - -class RenderPassColorAttachmentDescriptorArray : public NS::Referencing -{ -public: - static class RenderPassColorAttachmentDescriptorArray* alloc(); - - class RenderPassColorAttachmentDescriptorArray* init(); - - class RenderPassColorAttachmentDescriptor* object(NS::UInteger attachmentIndex); - - void setObject(const class RenderPassColorAttachmentDescriptor* attachment, NS::UInteger attachmentIndex); -}; - -class RenderPassSampleBufferAttachmentDescriptor : public NS::Copying -{ -public: - static class RenderPassSampleBufferAttachmentDescriptor* alloc(); - - class RenderPassSampleBufferAttachmentDescriptor* init(); - - class CounterSampleBuffer* sampleBuffer() const; - void setSampleBuffer(const class CounterSampleBuffer* sampleBuffer); - - NS::UInteger startOfVertexSampleIndex() const; - void setStartOfVertexSampleIndex(NS::UInteger startOfVertexSampleIndex); - - NS::UInteger endOfVertexSampleIndex() const; - void setEndOfVertexSampleIndex(NS::UInteger endOfVertexSampleIndex); - - NS::UInteger startOfFragmentSampleIndex() const; - void setStartOfFragmentSampleIndex(NS::UInteger startOfFragmentSampleIndex); - - NS::UInteger endOfFragmentSampleIndex() const; - void setEndOfFragmentSampleIndex(NS::UInteger endOfFragmentSampleIndex); -}; - -class RenderPassSampleBufferAttachmentDescriptorArray : public NS::Referencing -{ -public: - static class RenderPassSampleBufferAttachmentDescriptorArray* alloc(); - - class RenderPassSampleBufferAttachmentDescriptorArray* init(); - - class RenderPassSampleBufferAttachmentDescriptor* object(NS::UInteger attachmentIndex); - - void setObject(const class RenderPassSampleBufferAttachmentDescriptor* attachment, NS::UInteger attachmentIndex); -}; - -class RenderPassDescriptor : public NS::Copying -{ -public: - static class RenderPassDescriptor* alloc(); - - class RenderPassDescriptor* init(); - - static class RenderPassDescriptor* renderPassDescriptor(); - - class RenderPassColorAttachmentDescriptorArray* colorAttachments() const; - - class RenderPassDepthAttachmentDescriptor* depthAttachment() const; - void setDepthAttachment(const class RenderPassDepthAttachmentDescriptor* depthAttachment); - - class RenderPassStencilAttachmentDescriptor* stencilAttachment() const; - void setStencilAttachment(const class RenderPassStencilAttachmentDescriptor* stencilAttachment); - - class Buffer* visibilityResultBuffer() const; - void setVisibilityResultBuffer(const class Buffer* visibilityResultBuffer); - - NS::UInteger renderTargetArrayLength() const; - void setRenderTargetArrayLength(NS::UInteger renderTargetArrayLength); - - NS::UInteger imageblockSampleLength() const; - void setImageblockSampleLength(NS::UInteger imageblockSampleLength); - - NS::UInteger threadgroupMemoryLength() const; - void setThreadgroupMemoryLength(NS::UInteger threadgroupMemoryLength); - - NS::UInteger tileWidth() const; - void setTileWidth(NS::UInteger tileWidth); - - NS::UInteger tileHeight() const; - void setTileHeight(NS::UInteger tileHeight); - - NS::UInteger defaultRasterSampleCount() const; - void setDefaultRasterSampleCount(NS::UInteger defaultRasterSampleCount); - - NS::UInteger renderTargetWidth() const; - void setRenderTargetWidth(NS::UInteger renderTargetWidth); - - NS::UInteger renderTargetHeight() const; - void setRenderTargetHeight(NS::UInteger renderTargetHeight); - - void setSamplePositions(const MTL::SamplePosition* positions, NS::UInteger count); - - NS::UInteger getSamplePositions(MTL::SamplePosition* positions, NS::UInteger count); - - class RasterizationRateMap* rasterizationRateMap() const; - void setRasterizationRateMap(const class RasterizationRateMap* rasterizationRateMap); - - class RenderPassSampleBufferAttachmentDescriptorArray* sampleBufferAttachments() const; -}; - -} - -_MTL_INLINE MTL::ClearColor MTL::ClearColor::Make(double red, double green, double blue, double alpha) -{ - return ClearColor(red, green, blue, alpha); -} - -_MTL_INLINE MTL::ClearColor::ClearColor(double _red, double _green, double _blue, double _alpha) - : red(_red) - , green(_green) - , blue(_blue) - , alpha(_alpha) -{ -} - -_MTL_INLINE MTL::RenderPassAttachmentDescriptor* MTL::RenderPassAttachmentDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLRenderPassAttachmentDescriptor)); -} - -_MTL_INLINE MTL::RenderPassAttachmentDescriptor* MTL::RenderPassAttachmentDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::Texture* MTL::RenderPassAttachmentDescriptor::texture() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(texture)); -} - -_MTL_INLINE void MTL::RenderPassAttachmentDescriptor::setTexture(const MTL::Texture* texture) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTexture_), texture); -} - -_MTL_INLINE NS::UInteger MTL::RenderPassAttachmentDescriptor::level() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(level)); -} - -_MTL_INLINE void MTL::RenderPassAttachmentDescriptor::setLevel(NS::UInteger level) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLevel_), level); -} - -_MTL_INLINE NS::UInteger MTL::RenderPassAttachmentDescriptor::slice() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(slice)); -} - -_MTL_INLINE void MTL::RenderPassAttachmentDescriptor::setSlice(NS::UInteger slice) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSlice_), slice); -} - -_MTL_INLINE NS::UInteger MTL::RenderPassAttachmentDescriptor::depthPlane() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(depthPlane)); -} - -_MTL_INLINE void MTL::RenderPassAttachmentDescriptor::setDepthPlane(NS::UInteger depthPlane) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setDepthPlane_), depthPlane); -} - -_MTL_INLINE MTL::Texture* MTL::RenderPassAttachmentDescriptor::resolveTexture() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(resolveTexture)); -} - -_MTL_INLINE void MTL::RenderPassAttachmentDescriptor::setResolveTexture(const MTL::Texture* resolveTexture) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setResolveTexture_), resolveTexture); -} - -_MTL_INLINE NS::UInteger MTL::RenderPassAttachmentDescriptor::resolveLevel() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(resolveLevel)); -} - -_MTL_INLINE void MTL::RenderPassAttachmentDescriptor::setResolveLevel(NS::UInteger resolveLevel) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setResolveLevel_), resolveLevel); -} - -_MTL_INLINE NS::UInteger MTL::RenderPassAttachmentDescriptor::resolveSlice() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(resolveSlice)); -} - -_MTL_INLINE void MTL::RenderPassAttachmentDescriptor::setResolveSlice(NS::UInteger resolveSlice) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setResolveSlice_), resolveSlice); -} - -_MTL_INLINE NS::UInteger MTL::RenderPassAttachmentDescriptor::resolveDepthPlane() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(resolveDepthPlane)); -} - -_MTL_INLINE void MTL::RenderPassAttachmentDescriptor::setResolveDepthPlane(NS::UInteger resolveDepthPlane) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setResolveDepthPlane_), resolveDepthPlane); -} - -_MTL_INLINE MTL::LoadAction MTL::RenderPassAttachmentDescriptor::loadAction() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(loadAction)); -} - -_MTL_INLINE void MTL::RenderPassAttachmentDescriptor::setLoadAction(MTL::LoadAction loadAction) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLoadAction_), loadAction); -} - -_MTL_INLINE MTL::StoreAction MTL::RenderPassAttachmentDescriptor::storeAction() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(storeAction)); -} - -_MTL_INLINE void MTL::RenderPassAttachmentDescriptor::setStoreAction(MTL::StoreAction storeAction) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStoreAction_), storeAction); -} - -_MTL_INLINE MTL::StoreActionOptions MTL::RenderPassAttachmentDescriptor::storeActionOptions() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(storeActionOptions)); -} - -_MTL_INLINE void MTL::RenderPassAttachmentDescriptor::setStoreActionOptions(MTL::StoreActionOptions storeActionOptions) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStoreActionOptions_), storeActionOptions); -} - -_MTL_INLINE MTL::RenderPassColorAttachmentDescriptor* MTL::RenderPassColorAttachmentDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLRenderPassColorAttachmentDescriptor)); -} - -_MTL_INLINE MTL::RenderPassColorAttachmentDescriptor* MTL::RenderPassColorAttachmentDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::ClearColor MTL::RenderPassColorAttachmentDescriptor::clearColor() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(clearColor)); -} - -_MTL_INLINE void MTL::RenderPassColorAttachmentDescriptor::setClearColor(MTL::ClearColor clearColor) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setClearColor_), clearColor); -} - -_MTL_INLINE MTL::RenderPassDepthAttachmentDescriptor* MTL::RenderPassDepthAttachmentDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLRenderPassDepthAttachmentDescriptor)); -} - -_MTL_INLINE MTL::RenderPassDepthAttachmentDescriptor* MTL::RenderPassDepthAttachmentDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE double MTL::RenderPassDepthAttachmentDescriptor::clearDepth() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(clearDepth)); -} - -_MTL_INLINE void MTL::RenderPassDepthAttachmentDescriptor::setClearDepth(double clearDepth) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setClearDepth_), clearDepth); -} - -_MTL_INLINE MTL::MultisampleDepthResolveFilter MTL::RenderPassDepthAttachmentDescriptor::depthResolveFilter() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(depthResolveFilter)); -} - -_MTL_INLINE void MTL::RenderPassDepthAttachmentDescriptor::setDepthResolveFilter(MTL::MultisampleDepthResolveFilter depthResolveFilter) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setDepthResolveFilter_), depthResolveFilter); -} - -_MTL_INLINE MTL::RenderPassStencilAttachmentDescriptor* MTL::RenderPassStencilAttachmentDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLRenderPassStencilAttachmentDescriptor)); -} - -_MTL_INLINE MTL::RenderPassStencilAttachmentDescriptor* MTL::RenderPassStencilAttachmentDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE uint32_t MTL::RenderPassStencilAttachmentDescriptor::clearStencil() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(clearStencil)); -} - -_MTL_INLINE void MTL::RenderPassStencilAttachmentDescriptor::setClearStencil(uint32_t clearStencil) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setClearStencil_), clearStencil); -} - -_MTL_INLINE MTL::MultisampleStencilResolveFilter MTL::RenderPassStencilAttachmentDescriptor::stencilResolveFilter() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(stencilResolveFilter)); -} - -_MTL_INLINE void MTL::RenderPassStencilAttachmentDescriptor::setStencilResolveFilter(MTL::MultisampleStencilResolveFilter stencilResolveFilter) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStencilResolveFilter_), stencilResolveFilter); -} - -_MTL_INLINE MTL::RenderPassColorAttachmentDescriptorArray* MTL::RenderPassColorAttachmentDescriptorArray::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLRenderPassColorAttachmentDescriptorArray)); -} - -_MTL_INLINE MTL::RenderPassColorAttachmentDescriptorArray* MTL::RenderPassColorAttachmentDescriptorArray::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::RenderPassColorAttachmentDescriptor* MTL::RenderPassColorAttachmentDescriptorArray::object(NS::UInteger attachmentIndex) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(objectAtIndexedSubscript_), attachmentIndex); -} - -_MTL_INLINE void MTL::RenderPassColorAttachmentDescriptorArray::setObject(const MTL::RenderPassColorAttachmentDescriptor* attachment, NS::UInteger attachmentIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setObject_atIndexedSubscript_), attachment, attachmentIndex); -} - -_MTL_INLINE MTL::RenderPassSampleBufferAttachmentDescriptor* MTL::RenderPassSampleBufferAttachmentDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLRenderPassSampleBufferAttachmentDescriptor)); -} - -_MTL_INLINE MTL::RenderPassSampleBufferAttachmentDescriptor* MTL::RenderPassSampleBufferAttachmentDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::CounterSampleBuffer* MTL::RenderPassSampleBufferAttachmentDescriptor::sampleBuffer() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(sampleBuffer)); -} - -_MTL_INLINE void MTL::RenderPassSampleBufferAttachmentDescriptor::setSampleBuffer(const MTL::CounterSampleBuffer* sampleBuffer) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSampleBuffer_), sampleBuffer); -} - -_MTL_INLINE NS::UInteger MTL::RenderPassSampleBufferAttachmentDescriptor::startOfVertexSampleIndex() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(startOfVertexSampleIndex)); -} - -_MTL_INLINE void MTL::RenderPassSampleBufferAttachmentDescriptor::setStartOfVertexSampleIndex(NS::UInteger startOfVertexSampleIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStartOfVertexSampleIndex_), startOfVertexSampleIndex); -} - -_MTL_INLINE NS::UInteger MTL::RenderPassSampleBufferAttachmentDescriptor::endOfVertexSampleIndex() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(endOfVertexSampleIndex)); -} - -_MTL_INLINE void MTL::RenderPassSampleBufferAttachmentDescriptor::setEndOfVertexSampleIndex(NS::UInteger endOfVertexSampleIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setEndOfVertexSampleIndex_), endOfVertexSampleIndex); -} - -_MTL_INLINE NS::UInteger MTL::RenderPassSampleBufferAttachmentDescriptor::startOfFragmentSampleIndex() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(startOfFragmentSampleIndex)); -} - -_MTL_INLINE void MTL::RenderPassSampleBufferAttachmentDescriptor::setStartOfFragmentSampleIndex(NS::UInteger startOfFragmentSampleIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStartOfFragmentSampleIndex_), startOfFragmentSampleIndex); -} - -_MTL_INLINE NS::UInteger MTL::RenderPassSampleBufferAttachmentDescriptor::endOfFragmentSampleIndex() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(endOfFragmentSampleIndex)); -} - -_MTL_INLINE void MTL::RenderPassSampleBufferAttachmentDescriptor::setEndOfFragmentSampleIndex(NS::UInteger endOfFragmentSampleIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setEndOfFragmentSampleIndex_), endOfFragmentSampleIndex); -} - -_MTL_INLINE MTL::RenderPassSampleBufferAttachmentDescriptorArray* MTL::RenderPassSampleBufferAttachmentDescriptorArray::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLRenderPassSampleBufferAttachmentDescriptorArray)); -} - -_MTL_INLINE MTL::RenderPassSampleBufferAttachmentDescriptorArray* MTL::RenderPassSampleBufferAttachmentDescriptorArray::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::RenderPassSampleBufferAttachmentDescriptor* MTL::RenderPassSampleBufferAttachmentDescriptorArray::object(NS::UInteger attachmentIndex) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(objectAtIndexedSubscript_), attachmentIndex); -} - -_MTL_INLINE void MTL::RenderPassSampleBufferAttachmentDescriptorArray::setObject(const MTL::RenderPassSampleBufferAttachmentDescriptor* attachment, NS::UInteger attachmentIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setObject_atIndexedSubscript_), attachment, attachmentIndex); -} - -_MTL_INLINE MTL::RenderPassDescriptor* MTL::RenderPassDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLRenderPassDescriptor)); -} - -_MTL_INLINE MTL::RenderPassDescriptor* MTL::RenderPassDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::RenderPassDescriptor* MTL::RenderPassDescriptor::renderPassDescriptor() -{ - return Object::sendMessage(_MTL_PRIVATE_CLS(MTLRenderPassDescriptor), _MTL_PRIVATE_SEL(renderPassDescriptor)); -} - -_MTL_INLINE MTL::RenderPassColorAttachmentDescriptorArray* MTL::RenderPassDescriptor::colorAttachments() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(colorAttachments)); -} - -_MTL_INLINE MTL::RenderPassDepthAttachmentDescriptor* MTL::RenderPassDescriptor::depthAttachment() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(depthAttachment)); -} - -_MTL_INLINE void MTL::RenderPassDescriptor::setDepthAttachment(const MTL::RenderPassDepthAttachmentDescriptor* depthAttachment) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setDepthAttachment_), depthAttachment); -} - -_MTL_INLINE MTL::RenderPassStencilAttachmentDescriptor* MTL::RenderPassDescriptor::stencilAttachment() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(stencilAttachment)); -} - -_MTL_INLINE void MTL::RenderPassDescriptor::setStencilAttachment(const MTL::RenderPassStencilAttachmentDescriptor* stencilAttachment) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStencilAttachment_), stencilAttachment); -} - -_MTL_INLINE MTL::Buffer* MTL::RenderPassDescriptor::visibilityResultBuffer() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(visibilityResultBuffer)); -} - -_MTL_INLINE void MTL::RenderPassDescriptor::setVisibilityResultBuffer(const MTL::Buffer* visibilityResultBuffer) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVisibilityResultBuffer_), visibilityResultBuffer); -} - -_MTL_INLINE NS::UInteger MTL::RenderPassDescriptor::renderTargetArrayLength() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(renderTargetArrayLength)); -} - -_MTL_INLINE void MTL::RenderPassDescriptor::setRenderTargetArrayLength(NS::UInteger renderTargetArrayLength) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setRenderTargetArrayLength_), renderTargetArrayLength); -} - -_MTL_INLINE NS::UInteger MTL::RenderPassDescriptor::imageblockSampleLength() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(imageblockSampleLength)); -} - -_MTL_INLINE void MTL::RenderPassDescriptor::setImageblockSampleLength(NS::UInteger imageblockSampleLength) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setImageblockSampleLength_), imageblockSampleLength); -} - -_MTL_INLINE NS::UInteger MTL::RenderPassDescriptor::threadgroupMemoryLength() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(threadgroupMemoryLength)); -} - -_MTL_INLINE void MTL::RenderPassDescriptor::setThreadgroupMemoryLength(NS::UInteger threadgroupMemoryLength) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setThreadgroupMemoryLength_), threadgroupMemoryLength); -} - -_MTL_INLINE NS::UInteger MTL::RenderPassDescriptor::tileWidth() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(tileWidth)); -} - -_MTL_INLINE void MTL::RenderPassDescriptor::setTileWidth(NS::UInteger tileWidth) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTileWidth_), tileWidth); -} - -_MTL_INLINE NS::UInteger MTL::RenderPassDescriptor::tileHeight() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(tileHeight)); -} - -_MTL_INLINE void MTL::RenderPassDescriptor::setTileHeight(NS::UInteger tileHeight) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTileHeight_), tileHeight); -} - -_MTL_INLINE NS::UInteger MTL::RenderPassDescriptor::defaultRasterSampleCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(defaultRasterSampleCount)); -} - -_MTL_INLINE void MTL::RenderPassDescriptor::setDefaultRasterSampleCount(NS::UInteger defaultRasterSampleCount) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setDefaultRasterSampleCount_), defaultRasterSampleCount); -} - -_MTL_INLINE NS::UInteger MTL::RenderPassDescriptor::renderTargetWidth() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(renderTargetWidth)); -} - -_MTL_INLINE void MTL::RenderPassDescriptor::setRenderTargetWidth(NS::UInteger renderTargetWidth) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setRenderTargetWidth_), renderTargetWidth); -} - -_MTL_INLINE NS::UInteger MTL::RenderPassDescriptor::renderTargetHeight() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(renderTargetHeight)); -} - -_MTL_INLINE void MTL::RenderPassDescriptor::setRenderTargetHeight(NS::UInteger renderTargetHeight) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setRenderTargetHeight_), renderTargetHeight); -} - -_MTL_INLINE void MTL::RenderPassDescriptor::setSamplePositions(const MTL::SamplePosition* positions, NS::UInteger count) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSamplePositions_count_), positions, count); -} - -_MTL_INLINE NS::UInteger MTL::RenderPassDescriptor::getSamplePositions(MTL::SamplePosition* positions, NS::UInteger count) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(getSamplePositions_count_), positions, count); -} - -_MTL_INLINE MTL::RasterizationRateMap* MTL::RenderPassDescriptor::rasterizationRateMap() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(rasterizationRateMap)); -} - -_MTL_INLINE void MTL::RenderPassDescriptor::setRasterizationRateMap(const MTL::RasterizationRateMap* rasterizationRateMap) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setRasterizationRateMap_), rasterizationRateMap); -} - -_MTL_INLINE MTL::RenderPassSampleBufferAttachmentDescriptorArray* MTL::RenderPassDescriptor::sampleBufferAttachments() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(sampleBufferAttachments)); -} - -namespace MTL -{ -_MTL_ENUM(NS::UInteger, PrimitiveType) { - PrimitiveTypePoint = 0, - PrimitiveTypeLine = 1, - PrimitiveTypeLineStrip = 2, - PrimitiveTypeTriangle = 3, - PrimitiveTypeTriangleStrip = 4, -}; - -_MTL_ENUM(NS::UInteger, VisibilityResultMode) { - VisibilityResultModeDisabled = 0, - VisibilityResultModeBoolean = 1, - VisibilityResultModeCounting = 2, -}; - -struct ScissorRect -{ - NS::UInteger x; - NS::UInteger y; - NS::UInteger width; - NS::UInteger height; -} _MTL_PACKED; - -struct Viewport -{ - double originX; - double originY; - double width; - double height; - double znear; - double zfar; -} _MTL_PACKED; - -_MTL_ENUM(NS::UInteger, CullMode) { - CullModeNone = 0, - CullModeFront = 1, - CullModeBack = 2, -}; - -_MTL_ENUM(NS::UInteger, Winding) { - WindingClockwise = 0, - WindingCounterClockwise = 1, -}; - -_MTL_ENUM(NS::UInteger, DepthClipMode) { - DepthClipModeClip = 0, - DepthClipModeClamp = 1, -}; - -_MTL_ENUM(NS::UInteger, TriangleFillMode) { - TriangleFillModeFill = 0, - TriangleFillModeLines = 1, -}; - -struct DrawPrimitivesIndirectArguments -{ - uint32_t vertexCount; - uint32_t instanceCount; - uint32_t vertexStart; - uint32_t baseInstance; -} _MTL_PACKED; - -struct DrawIndexedPrimitivesIndirectArguments -{ - uint32_t indexCount; - uint32_t instanceCount; - uint32_t indexStart; - int32_t baseVertex; - uint32_t baseInstance; -} _MTL_PACKED; - -struct VertexAmplificationViewMapping -{ - uint32_t viewportArrayIndexOffset; - uint32_t renderTargetArrayIndexOffset; -} _MTL_PACKED; - -struct DrawPatchIndirectArguments -{ - uint32_t patchCount; - uint32_t instanceCount; - uint32_t patchStart; - uint32_t baseInstance; -} _MTL_PACKED; - -struct QuadTessellationFactorsHalf -{ - uint16_t edgeTessellationFactor[4]; - uint16_t insideTessellationFactor[2]; -} _MTL_PACKED; - -struct TriangleTessellationFactorsHalf -{ - uint16_t edgeTessellationFactor[3]; - uint16_t insideTessellationFactor; -} _MTL_PACKED; - -_MTL_OPTIONS(NS::UInteger, RenderStages) { - RenderStageVertex = 1, - RenderStageFragment = 2, - RenderStageTile = 4, - RenderStageObject = 8, - RenderStageMesh = 16, -}; - -class RenderCommandEncoder : public NS::Referencing -{ -public: - void setRenderPipelineState(const class RenderPipelineState* pipelineState); - - void setVertexBytes(const void* bytes, NS::UInteger length, NS::UInteger index); - - void setVertexBuffer(const class Buffer* buffer, NS::UInteger offset, NS::UInteger index); - - void setVertexBufferOffset(NS::UInteger offset, NS::UInteger index); - - void setVertexBuffers(const class Buffer* const buffers[], const NS::UInteger offsets[], NS::Range range); - - void setVertexTexture(const class Texture* texture, NS::UInteger index); - - void setVertexTextures(const class Texture* const textures[], NS::Range range); - - void setVertexSamplerState(const class SamplerState* sampler, NS::UInteger index); - - void setVertexSamplerStates(const class SamplerState* const samplers[], NS::Range range); - - void setVertexSamplerState(const class SamplerState* sampler, float lodMinClamp, float lodMaxClamp, NS::UInteger index); - - void setVertexSamplerStates(const class SamplerState* const samplers[], const float lodMinClamps[], const float lodMaxClamps[], NS::Range range); - - void setVertexVisibleFunctionTable(const class VisibleFunctionTable* functionTable, NS::UInteger bufferIndex); - - void setVertexVisibleFunctionTables(const class VisibleFunctionTable* const functionTables[], NS::Range range); - - void setVertexIntersectionFunctionTable(const class IntersectionFunctionTable* intersectionFunctionTable, NS::UInteger bufferIndex); - - void setVertexIntersectionFunctionTables(const class IntersectionFunctionTable* const intersectionFunctionTables[], NS::Range range); - - void setVertexAccelerationStructure(const class AccelerationStructure* accelerationStructure, NS::UInteger bufferIndex); - - void setViewport(MTL::Viewport viewport); - - void setViewports(const MTL::Viewport* viewports, NS::UInteger count); - - void setFrontFacingWinding(MTL::Winding frontFacingWinding); - - void setVertexAmplificationCount(NS::UInteger count, const MTL::VertexAmplificationViewMapping* viewMappings); - - void setCullMode(MTL::CullMode cullMode); - - void setDepthClipMode(MTL::DepthClipMode depthClipMode); - - void setDepthBias(float depthBias, float slopeScale, float clamp); - - void setScissorRect(MTL::ScissorRect rect); - - void setScissorRects(const MTL::ScissorRect* scissorRects, NS::UInteger count); - - void setTriangleFillMode(MTL::TriangleFillMode fillMode); - - void setFragmentBytes(const void* bytes, NS::UInteger length, NS::UInteger index); - - void setFragmentBuffer(const class Buffer* buffer, NS::UInteger offset, NS::UInteger index); - - void setFragmentBufferOffset(NS::UInteger offset, NS::UInteger index); - - void setFragmentBuffers(const class Buffer* const buffers[], const NS::UInteger offsets[], NS::Range range); - - void setFragmentTexture(const class Texture* texture, NS::UInteger index); - - void setFragmentTextures(const class Texture* const textures[], NS::Range range); - - void setFragmentSamplerState(const class SamplerState* sampler, NS::UInteger index); - - void setFragmentSamplerStates(const class SamplerState* const samplers[], NS::Range range); - - void setFragmentSamplerState(const class SamplerState* sampler, float lodMinClamp, float lodMaxClamp, NS::UInteger index); - - void setFragmentSamplerStates(const class SamplerState* const samplers[], const float lodMinClamps[], const float lodMaxClamps[], NS::Range range); - - void setFragmentVisibleFunctionTable(const class VisibleFunctionTable* functionTable, NS::UInteger bufferIndex); - - void setFragmentVisibleFunctionTables(const class VisibleFunctionTable* const functionTables[], NS::Range range); - - void setFragmentIntersectionFunctionTable(const class IntersectionFunctionTable* intersectionFunctionTable, NS::UInteger bufferIndex); - - void setFragmentIntersectionFunctionTables(const class IntersectionFunctionTable* const intersectionFunctionTables[], NS::Range range); - - void setFragmentAccelerationStructure(const class AccelerationStructure* accelerationStructure, NS::UInteger bufferIndex); - - void setBlendColor(float red, float green, float blue, float alpha); - - void setDepthStencilState(const class DepthStencilState* depthStencilState); - - void setStencilReferenceValue(uint32_t referenceValue); - - void setStencilReferenceValues(uint32_t frontReferenceValue, uint32_t backReferenceValue); - - void setVisibilityResultMode(MTL::VisibilityResultMode mode, NS::UInteger offset); - - void setColorStoreAction(MTL::StoreAction storeAction, NS::UInteger colorAttachmentIndex); - - void setDepthStoreAction(MTL::StoreAction storeAction); - - void setStencilStoreAction(MTL::StoreAction storeAction); - - void setColorStoreActionOptions(MTL::StoreActionOptions storeActionOptions, NS::UInteger colorAttachmentIndex); - - void setDepthStoreActionOptions(MTL::StoreActionOptions storeActionOptions); - - void setStencilStoreActionOptions(MTL::StoreActionOptions storeActionOptions); - - void setObjectBytes(const void* bytes, NS::UInteger length, NS::UInteger index); - - void setObjectBuffer(const class Buffer* buffer, NS::UInteger offset, NS::UInteger index); - - void setObjectBufferOffset(NS::UInteger offset, NS::UInteger index); - - void setObjectBuffers(const class Buffer* const buffers[], const NS::UInteger* offsets, NS::Range range); - - void setObjectTexture(const class Texture* texture, NS::UInteger index); - - void setObjectTextures(const class Texture* const textures[], NS::Range range); - - void setObjectSamplerState(const class SamplerState* sampler, NS::UInteger index); - - void setObjectSamplerStates(const class SamplerState* const samplers[], NS::Range range); - - void setObjectSamplerState(const class SamplerState* sampler, float lodMinClamp, float lodMaxClamp, NS::UInteger index); - - void setObjectSamplerStates(const class SamplerState* const samplers[], const float* lodMinClamps, const float* lodMaxClamps, NS::Range range); - - void setObjectThreadgroupMemoryLength(NS::UInteger length, NS::UInteger index); - - void setMeshBytes(const void* bytes, NS::UInteger length, NS::UInteger index); - - void setMeshBuffer(const class Buffer* buffer, NS::UInteger offset, NS::UInteger index); - - void setMeshBufferOffset(NS::UInteger offset, NS::UInteger index); - - void setMeshBuffers(const class Buffer* const buffers[], const NS::UInteger* offsets, NS::Range range); - - void setMeshTexture(const class Texture* texture, NS::UInteger index); - - void setMeshTextures(const class Texture* const textures[], NS::Range range); - - void setMeshSamplerState(const class SamplerState* sampler, NS::UInteger index); - - void setMeshSamplerStates(const class SamplerState* const samplers[], NS::Range range); - - void setMeshSamplerState(const class SamplerState* sampler, float lodMinClamp, float lodMaxClamp, NS::UInteger index); - - void setMeshSamplerStates(const class SamplerState* const samplers[], const float* lodMinClamps, const float* lodMaxClamps, NS::Range range); - - void drawMeshThreadgroups(MTL::Size threadgroupsPerGrid, MTL::Size threadsPerObjectThreadgroup, MTL::Size threadsPerMeshThreadgroup); - - void drawMeshThreads(MTL::Size threadsPerGrid, MTL::Size threadsPerObjectThreadgroup, MTL::Size threadsPerMeshThreadgroup); - - void drawMeshThreadgroups(const class Buffer* indirectBuffer, NS::UInteger indirectBufferOffset, MTL::Size threadsPerObjectThreadgroup, MTL::Size threadsPerMeshThreadgroup); - - void drawPrimitives(MTL::PrimitiveType primitiveType, NS::UInteger vertexStart, NS::UInteger vertexCount, NS::UInteger instanceCount); - - void drawPrimitives(MTL::PrimitiveType primitiveType, NS::UInteger vertexStart, NS::UInteger vertexCount); - - void drawIndexedPrimitives(MTL::PrimitiveType primitiveType, NS::UInteger indexCount, MTL::IndexType indexType, const class Buffer* indexBuffer, NS::UInteger indexBufferOffset, NS::UInteger instanceCount); - - void drawIndexedPrimitives(MTL::PrimitiveType primitiveType, NS::UInteger indexCount, MTL::IndexType indexType, const class Buffer* indexBuffer, NS::UInteger indexBufferOffset); - - void drawPrimitives(MTL::PrimitiveType primitiveType, NS::UInteger vertexStart, NS::UInteger vertexCount, NS::UInteger instanceCount, NS::UInteger baseInstance); - - void drawIndexedPrimitives(MTL::PrimitiveType primitiveType, NS::UInteger indexCount, MTL::IndexType indexType, const class Buffer* indexBuffer, NS::UInteger indexBufferOffset, NS::UInteger instanceCount, NS::Integer baseVertex, NS::UInteger baseInstance); - - void drawPrimitives(MTL::PrimitiveType primitiveType, const class Buffer* indirectBuffer, NS::UInteger indirectBufferOffset); - - void drawIndexedPrimitives(MTL::PrimitiveType primitiveType, MTL::IndexType indexType, const class Buffer* indexBuffer, NS::UInteger indexBufferOffset, const class Buffer* indirectBuffer, NS::UInteger indirectBufferOffset); - - void textureBarrier(); - - void updateFence(const class Fence* fence, MTL::RenderStages stages); - - void waitForFence(const class Fence* fence, MTL::RenderStages stages); - - void setTessellationFactorBuffer(const class Buffer* buffer, NS::UInteger offset, NS::UInteger instanceStride); - - void setTessellationFactorScale(float scale); - - void drawPatches(NS::UInteger numberOfPatchControlPoints, NS::UInteger patchStart, NS::UInteger patchCount, const class Buffer* patchIndexBuffer, NS::UInteger patchIndexBufferOffset, NS::UInteger instanceCount, NS::UInteger baseInstance); - - void drawPatches(NS::UInteger numberOfPatchControlPoints, const class Buffer* patchIndexBuffer, NS::UInteger patchIndexBufferOffset, const class Buffer* indirectBuffer, NS::UInteger indirectBufferOffset); - - void drawIndexedPatches(NS::UInteger numberOfPatchControlPoints, NS::UInteger patchStart, NS::UInteger patchCount, const class Buffer* patchIndexBuffer, NS::UInteger patchIndexBufferOffset, const class Buffer* controlPointIndexBuffer, NS::UInteger controlPointIndexBufferOffset, NS::UInteger instanceCount, NS::UInteger baseInstance); - - void drawIndexedPatches(NS::UInteger numberOfPatchControlPoints, const class Buffer* patchIndexBuffer, NS::UInteger patchIndexBufferOffset, const class Buffer* controlPointIndexBuffer, NS::UInteger controlPointIndexBufferOffset, const class Buffer* indirectBuffer, NS::UInteger indirectBufferOffset); - - NS::UInteger tileWidth() const; - - NS::UInteger tileHeight() const; - - void setTileBytes(const void* bytes, NS::UInteger length, NS::UInteger index); - - void setTileBuffer(const class Buffer* buffer, NS::UInteger offset, NS::UInteger index); - - void setTileBufferOffset(NS::UInteger offset, NS::UInteger index); - - void setTileBuffers(const class Buffer* const buffers[], const NS::UInteger* offsets, NS::Range range); - - void setTileTexture(const class Texture* texture, NS::UInteger index); - - void setTileTextures(const class Texture* const textures[], NS::Range range); - - void setTileSamplerState(const class SamplerState* sampler, NS::UInteger index); - - void setTileSamplerStates(const class SamplerState* const samplers[], NS::Range range); - - void setTileSamplerState(const class SamplerState* sampler, float lodMinClamp, float lodMaxClamp, NS::UInteger index); - - void setTileSamplerStates(const class SamplerState* const samplers[], const float lodMinClamps[], const float lodMaxClamps[], NS::Range range); - - void setTileVisibleFunctionTable(const class VisibleFunctionTable* functionTable, NS::UInteger bufferIndex); - - void setTileVisibleFunctionTables(const class VisibleFunctionTable* const functionTables[], NS::Range range); - - void setTileIntersectionFunctionTable(const class IntersectionFunctionTable* intersectionFunctionTable, NS::UInteger bufferIndex); - - void setTileIntersectionFunctionTables(const class IntersectionFunctionTable* const intersectionFunctionTables[], NS::Range range); - - void setTileAccelerationStructure(const class AccelerationStructure* accelerationStructure, NS::UInteger bufferIndex); - - void dispatchThreadsPerTile(MTL::Size threadsPerTile); - - void setThreadgroupMemoryLength(NS::UInteger length, NS::UInteger offset, NS::UInteger index); - - void useResource(const class Resource* resource, MTL::ResourceUsage usage); - - void useResources(const class Resource* const resources[], NS::UInteger count, MTL::ResourceUsage usage); - - void useResource(const class Resource* resource, MTL::ResourceUsage usage, MTL::RenderStages stages); - - void useResources(const class Resource* const resources[], NS::UInteger count, MTL::ResourceUsage usage, MTL::RenderStages stages); - - void useHeap(const class Heap* heap); - - void useHeaps(const class Heap* const heaps[], NS::UInteger count); - - void useHeap(const class Heap* heap, MTL::RenderStages stages); - - void useHeaps(const class Heap* const heaps[], NS::UInteger count, MTL::RenderStages stages); - - void executeCommandsInBuffer(const class IndirectCommandBuffer* indirectCommandBuffer, NS::Range executionRange); - - void executeCommandsInBuffer(const class IndirectCommandBuffer* indirectCommandbuffer, const class Buffer* indirectRangeBuffer, NS::UInteger indirectBufferOffset); - - void memoryBarrier(MTL::BarrierScope scope, MTL::RenderStages after, MTL::RenderStages before); - - void memoryBarrier(const class Resource* const resources[], NS::UInteger count, MTL::RenderStages after, MTL::RenderStages before); - - void sampleCountersInBuffer(const class CounterSampleBuffer* sampleBuffer, NS::UInteger sampleIndex, bool barrier); -}; - -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setRenderPipelineState(const MTL::RenderPipelineState* pipelineState) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setRenderPipelineState_), pipelineState); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setVertexBytes(const void* bytes, NS::UInteger length, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVertexBytes_length_atIndex_), bytes, length, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setVertexBuffer(const MTL::Buffer* buffer, NS::UInteger offset, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVertexBuffer_offset_atIndex_), buffer, offset, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setVertexBufferOffset(NS::UInteger offset, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVertexBufferOffset_atIndex_), offset, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setVertexBuffers(const MTL::Buffer* const buffers[], const NS::UInteger offsets[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVertexBuffers_offsets_withRange_), buffers, offsets, range); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setVertexTexture(const MTL::Texture* texture, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVertexTexture_atIndex_), texture, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setVertexTextures(const MTL::Texture* const textures[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVertexTextures_withRange_), textures, range); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setVertexSamplerState(const MTL::SamplerState* sampler, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVertexSamplerState_atIndex_), sampler, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setVertexSamplerStates(const MTL::SamplerState* const samplers[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVertexSamplerStates_withRange_), samplers, range); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setVertexSamplerState(const MTL::SamplerState* sampler, float lodMinClamp, float lodMaxClamp, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVertexSamplerState_lodMinClamp_lodMaxClamp_atIndex_), sampler, lodMinClamp, lodMaxClamp, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setVertexSamplerStates(const MTL::SamplerState* const samplers[], const float lodMinClamps[], const float lodMaxClamps[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVertexSamplerStates_lodMinClamps_lodMaxClamps_withRange_), samplers, lodMinClamps, lodMaxClamps, range); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setVertexVisibleFunctionTable(const MTL::VisibleFunctionTable* functionTable, NS::UInteger bufferIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVertexVisibleFunctionTable_atBufferIndex_), functionTable, bufferIndex); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setVertexVisibleFunctionTables(const MTL::VisibleFunctionTable* const functionTables[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVertexVisibleFunctionTables_withBufferRange_), functionTables, range); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setVertexIntersectionFunctionTable(const MTL::IntersectionFunctionTable* intersectionFunctionTable, NS::UInteger bufferIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVertexIntersectionFunctionTable_atBufferIndex_), intersectionFunctionTable, bufferIndex); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setVertexIntersectionFunctionTables(const MTL::IntersectionFunctionTable* const intersectionFunctionTables[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVertexIntersectionFunctionTables_withBufferRange_), intersectionFunctionTables, range); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setVertexAccelerationStructure(const MTL::AccelerationStructure* accelerationStructure, NS::UInteger bufferIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVertexAccelerationStructure_atBufferIndex_), accelerationStructure, bufferIndex); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setViewport(MTL::Viewport viewport) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setViewport_), viewport); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setViewports(const MTL::Viewport* viewports, NS::UInteger count) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setViewports_count_), viewports, count); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setFrontFacingWinding(MTL::Winding frontFacingWinding) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFrontFacingWinding_), frontFacingWinding); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setVertexAmplificationCount(NS::UInteger count, const MTL::VertexAmplificationViewMapping* viewMappings) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVertexAmplificationCount_viewMappings_), count, viewMappings); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setCullMode(MTL::CullMode cullMode) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setCullMode_), cullMode); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setDepthClipMode(MTL::DepthClipMode depthClipMode) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setDepthClipMode_), depthClipMode); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setDepthBias(float depthBias, float slopeScale, float clamp) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setDepthBias_slopeScale_clamp_), depthBias, slopeScale, clamp); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setScissorRect(MTL::ScissorRect rect) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setScissorRect_), rect); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setScissorRects(const MTL::ScissorRect* scissorRects, NS::UInteger count) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setScissorRects_count_), scissorRects, count); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setTriangleFillMode(MTL::TriangleFillMode fillMode) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTriangleFillMode_), fillMode); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setFragmentBytes(const void* bytes, NS::UInteger length, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFragmentBytes_length_atIndex_), bytes, length, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setFragmentBuffer(const MTL::Buffer* buffer, NS::UInteger offset, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFragmentBuffer_offset_atIndex_), buffer, offset, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setFragmentBufferOffset(NS::UInteger offset, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFragmentBufferOffset_atIndex_), offset, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setFragmentBuffers(const MTL::Buffer* const buffers[], const NS::UInteger offsets[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFragmentBuffers_offsets_withRange_), buffers, offsets, range); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setFragmentTexture(const MTL::Texture* texture, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFragmentTexture_atIndex_), texture, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setFragmentTextures(const MTL::Texture* const textures[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFragmentTextures_withRange_), textures, range); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setFragmentSamplerState(const MTL::SamplerState* sampler, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFragmentSamplerState_atIndex_), sampler, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setFragmentSamplerStates(const MTL::SamplerState* const samplers[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFragmentSamplerStates_withRange_), samplers, range); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setFragmentSamplerState(const MTL::SamplerState* sampler, float lodMinClamp, float lodMaxClamp, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFragmentSamplerState_lodMinClamp_lodMaxClamp_atIndex_), sampler, lodMinClamp, lodMaxClamp, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setFragmentSamplerStates(const MTL::SamplerState* const samplers[], const float lodMinClamps[], const float lodMaxClamps[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFragmentSamplerStates_lodMinClamps_lodMaxClamps_withRange_), samplers, lodMinClamps, lodMaxClamps, range); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setFragmentVisibleFunctionTable(const MTL::VisibleFunctionTable* functionTable, NS::UInteger bufferIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFragmentVisibleFunctionTable_atBufferIndex_), functionTable, bufferIndex); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setFragmentVisibleFunctionTables(const MTL::VisibleFunctionTable* const functionTables[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFragmentVisibleFunctionTables_withBufferRange_), functionTables, range); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setFragmentIntersectionFunctionTable(const MTL::IntersectionFunctionTable* intersectionFunctionTable, NS::UInteger bufferIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFragmentIntersectionFunctionTable_atBufferIndex_), intersectionFunctionTable, bufferIndex); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setFragmentIntersectionFunctionTables(const MTL::IntersectionFunctionTable* const intersectionFunctionTables[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFragmentIntersectionFunctionTables_withBufferRange_), intersectionFunctionTables, range); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setFragmentAccelerationStructure(const MTL::AccelerationStructure* accelerationStructure, NS::UInteger bufferIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFragmentAccelerationStructure_atBufferIndex_), accelerationStructure, bufferIndex); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setBlendColor(float red, float green, float blue, float alpha) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setBlendColorRed_green_blue_alpha_), red, green, blue, alpha); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setDepthStencilState(const MTL::DepthStencilState* depthStencilState) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setDepthStencilState_), depthStencilState); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setStencilReferenceValue(uint32_t referenceValue) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStencilReferenceValue_), referenceValue); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setStencilReferenceValues(uint32_t frontReferenceValue, uint32_t backReferenceValue) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStencilFrontReferenceValue_backReferenceValue_), frontReferenceValue, backReferenceValue); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setVisibilityResultMode(MTL::VisibilityResultMode mode, NS::UInteger offset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVisibilityResultMode_offset_), mode, offset); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setColorStoreAction(MTL::StoreAction storeAction, NS::UInteger colorAttachmentIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setColorStoreAction_atIndex_), storeAction, colorAttachmentIndex); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setDepthStoreAction(MTL::StoreAction storeAction) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setDepthStoreAction_), storeAction); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setStencilStoreAction(MTL::StoreAction storeAction) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStencilStoreAction_), storeAction); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setColorStoreActionOptions(MTL::StoreActionOptions storeActionOptions, NS::UInteger colorAttachmentIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setColorStoreActionOptions_atIndex_), storeActionOptions, colorAttachmentIndex); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setDepthStoreActionOptions(MTL::StoreActionOptions storeActionOptions) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setDepthStoreActionOptions_), storeActionOptions); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setStencilStoreActionOptions(MTL::StoreActionOptions storeActionOptions) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStencilStoreActionOptions_), storeActionOptions); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setObjectBytes(const void* bytes, NS::UInteger length, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setObjectBytes_length_atIndex_), bytes, length, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setObjectBuffer(const MTL::Buffer* buffer, NS::UInteger offset, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setObjectBuffer_offset_atIndex_), buffer, offset, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setObjectBufferOffset(NS::UInteger offset, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setObjectBufferOffset_atIndex_), offset, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setObjectBuffers(const MTL::Buffer* const buffers[], const NS::UInteger* offsets, NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setObjectBuffers_offsets_withRange_), buffers, offsets, range); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setObjectTexture(const MTL::Texture* texture, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setObjectTexture_atIndex_), texture, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setObjectTextures(const MTL::Texture* const textures[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setObjectTextures_withRange_), textures, range); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setObjectSamplerState(const MTL::SamplerState* sampler, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setObjectSamplerState_atIndex_), sampler, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setObjectSamplerStates(const MTL::SamplerState* const samplers[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setObjectSamplerStates_withRange_), samplers, range); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setObjectSamplerState(const MTL::SamplerState* sampler, float lodMinClamp, float lodMaxClamp, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setObjectSamplerState_lodMinClamp_lodMaxClamp_atIndex_), sampler, lodMinClamp, lodMaxClamp, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setObjectSamplerStates(const MTL::SamplerState* const samplers[], const float* lodMinClamps, const float* lodMaxClamps, NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setObjectSamplerStates_lodMinClamps_lodMaxClamps_withRange_), samplers, lodMinClamps, lodMaxClamps, range); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setObjectThreadgroupMemoryLength(NS::UInteger length, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setObjectThreadgroupMemoryLength_atIndex_), length, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setMeshBytes(const void* bytes, NS::UInteger length, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMeshBytes_length_atIndex_), bytes, length, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setMeshBuffer(const MTL::Buffer* buffer, NS::UInteger offset, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMeshBuffer_offset_atIndex_), buffer, offset, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setMeshBufferOffset(NS::UInteger offset, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMeshBufferOffset_atIndex_), offset, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setMeshBuffers(const MTL::Buffer* const buffers[], const NS::UInteger* offsets, NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMeshBuffers_offsets_withRange_), buffers, offsets, range); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setMeshTexture(const MTL::Texture* texture, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMeshTexture_atIndex_), texture, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setMeshTextures(const MTL::Texture* const textures[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMeshTextures_withRange_), textures, range); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setMeshSamplerState(const MTL::SamplerState* sampler, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMeshSamplerState_atIndex_), sampler, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setMeshSamplerStates(const MTL::SamplerState* const samplers[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMeshSamplerStates_withRange_), samplers, range); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setMeshSamplerState(const MTL::SamplerState* sampler, float lodMinClamp, float lodMaxClamp, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMeshSamplerState_lodMinClamp_lodMaxClamp_atIndex_), sampler, lodMinClamp, lodMaxClamp, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setMeshSamplerStates(const MTL::SamplerState* const samplers[], const float* lodMinClamps, const float* lodMaxClamps, NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMeshSamplerStates_lodMinClamps_lodMaxClamps_withRange_), samplers, lodMinClamps, lodMaxClamps, range); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::drawMeshThreadgroups(MTL::Size threadgroupsPerGrid, MTL::Size threadsPerObjectThreadgroup, MTL::Size threadsPerMeshThreadgroup) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(drawMeshThreadgroups_threadsPerObjectThreadgroup_threadsPerMeshThreadgroup_), threadgroupsPerGrid, threadsPerObjectThreadgroup, threadsPerMeshThreadgroup); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::drawMeshThreads(MTL::Size threadsPerGrid, MTL::Size threadsPerObjectThreadgroup, MTL::Size threadsPerMeshThreadgroup) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(drawMeshThreads_threadsPerObjectThreadgroup_threadsPerMeshThreadgroup_), threadsPerGrid, threadsPerObjectThreadgroup, threadsPerMeshThreadgroup); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::drawMeshThreadgroups(const MTL::Buffer* indirectBuffer, NS::UInteger indirectBufferOffset, MTL::Size threadsPerObjectThreadgroup, MTL::Size threadsPerMeshThreadgroup) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(drawMeshThreadgroupsWithIndirectBuffer_indirectBufferOffset_threadsPerObjectThreadgroup_threadsPerMeshThreadgroup_), indirectBuffer, indirectBufferOffset, threadsPerObjectThreadgroup, threadsPerMeshThreadgroup); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::drawPrimitives(MTL::PrimitiveType primitiveType, NS::UInteger vertexStart, NS::UInteger vertexCount, NS::UInteger instanceCount) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(drawPrimitives_vertexStart_vertexCount_instanceCount_), primitiveType, vertexStart, vertexCount, instanceCount); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::drawPrimitives(MTL::PrimitiveType primitiveType, NS::UInteger vertexStart, NS::UInteger vertexCount) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(drawPrimitives_vertexStart_vertexCount_), primitiveType, vertexStart, vertexCount); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::drawIndexedPrimitives(MTL::PrimitiveType primitiveType, NS::UInteger indexCount, MTL::IndexType indexType, const MTL::Buffer* indexBuffer, NS::UInteger indexBufferOffset, NS::UInteger instanceCount) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(drawIndexedPrimitives_indexCount_indexType_indexBuffer_indexBufferOffset_instanceCount_), primitiveType, indexCount, indexType, indexBuffer, indexBufferOffset, instanceCount); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::drawIndexedPrimitives(MTL::PrimitiveType primitiveType, NS::UInteger indexCount, MTL::IndexType indexType, const MTL::Buffer* indexBuffer, NS::UInteger indexBufferOffset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(drawIndexedPrimitives_indexCount_indexType_indexBuffer_indexBufferOffset_), primitiveType, indexCount, indexType, indexBuffer, indexBufferOffset); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::drawPrimitives(MTL::PrimitiveType primitiveType, NS::UInteger vertexStart, NS::UInteger vertexCount, NS::UInteger instanceCount, NS::UInteger baseInstance) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(drawPrimitives_vertexStart_vertexCount_instanceCount_baseInstance_), primitiveType, vertexStart, vertexCount, instanceCount, baseInstance); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::drawIndexedPrimitives(MTL::PrimitiveType primitiveType, NS::UInteger indexCount, MTL::IndexType indexType, const MTL::Buffer* indexBuffer, NS::UInteger indexBufferOffset, NS::UInteger instanceCount, NS::Integer baseVertex, NS::UInteger baseInstance) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(drawIndexedPrimitives_indexCount_indexType_indexBuffer_indexBufferOffset_instanceCount_baseVertex_baseInstance_), primitiveType, indexCount, indexType, indexBuffer, indexBufferOffset, instanceCount, baseVertex, baseInstance); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::drawPrimitives(MTL::PrimitiveType primitiveType, const MTL::Buffer* indirectBuffer, NS::UInteger indirectBufferOffset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(drawPrimitives_indirectBuffer_indirectBufferOffset_), primitiveType, indirectBuffer, indirectBufferOffset); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::drawIndexedPrimitives(MTL::PrimitiveType primitiveType, MTL::IndexType indexType, const MTL::Buffer* indexBuffer, NS::UInteger indexBufferOffset, const MTL::Buffer* indirectBuffer, NS::UInteger indirectBufferOffset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(drawIndexedPrimitives_indexType_indexBuffer_indexBufferOffset_indirectBuffer_indirectBufferOffset_), primitiveType, indexType, indexBuffer, indexBufferOffset, indirectBuffer, indirectBufferOffset); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::textureBarrier() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(textureBarrier)); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::updateFence(const MTL::Fence* fence, MTL::RenderStages stages) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(updateFence_afterStages_), fence, stages); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::waitForFence(const MTL::Fence* fence, MTL::RenderStages stages) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(waitForFence_beforeStages_), fence, stages); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setTessellationFactorBuffer(const MTL::Buffer* buffer, NS::UInteger offset, NS::UInteger instanceStride) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTessellationFactorBuffer_offset_instanceStride_), buffer, offset, instanceStride); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setTessellationFactorScale(float scale) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTessellationFactorScale_), scale); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::drawPatches(NS::UInteger numberOfPatchControlPoints, NS::UInteger patchStart, NS::UInteger patchCount, const MTL::Buffer* patchIndexBuffer, NS::UInteger patchIndexBufferOffset, NS::UInteger instanceCount, NS::UInteger baseInstance) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(drawPatches_patchStart_patchCount_patchIndexBuffer_patchIndexBufferOffset_instanceCount_baseInstance_), numberOfPatchControlPoints, patchStart, patchCount, patchIndexBuffer, patchIndexBufferOffset, instanceCount, baseInstance); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::drawPatches(NS::UInteger numberOfPatchControlPoints, const MTL::Buffer* patchIndexBuffer, NS::UInteger patchIndexBufferOffset, const MTL::Buffer* indirectBuffer, NS::UInteger indirectBufferOffset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(drawPatches_patchIndexBuffer_patchIndexBufferOffset_indirectBuffer_indirectBufferOffset_), numberOfPatchControlPoints, patchIndexBuffer, patchIndexBufferOffset, indirectBuffer, indirectBufferOffset); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::drawIndexedPatches(NS::UInteger numberOfPatchControlPoints, NS::UInteger patchStart, NS::UInteger patchCount, const MTL::Buffer* patchIndexBuffer, NS::UInteger patchIndexBufferOffset, const MTL::Buffer* controlPointIndexBuffer, NS::UInteger controlPointIndexBufferOffset, NS::UInteger instanceCount, NS::UInteger baseInstance) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(drawIndexedPatches_patchStart_patchCount_patchIndexBuffer_patchIndexBufferOffset_controlPointIndexBuffer_controlPointIndexBufferOffset_instanceCount_baseInstance_), numberOfPatchControlPoints, patchStart, patchCount, patchIndexBuffer, patchIndexBufferOffset, controlPointIndexBuffer, controlPointIndexBufferOffset, instanceCount, baseInstance); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::drawIndexedPatches(NS::UInteger numberOfPatchControlPoints, const MTL::Buffer* patchIndexBuffer, NS::UInteger patchIndexBufferOffset, const MTL::Buffer* controlPointIndexBuffer, NS::UInteger controlPointIndexBufferOffset, const MTL::Buffer* indirectBuffer, NS::UInteger indirectBufferOffset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(drawIndexedPatches_patchIndexBuffer_patchIndexBufferOffset_controlPointIndexBuffer_controlPointIndexBufferOffset_indirectBuffer_indirectBufferOffset_), numberOfPatchControlPoints, patchIndexBuffer, patchIndexBufferOffset, controlPointIndexBuffer, controlPointIndexBufferOffset, indirectBuffer, indirectBufferOffset); -} - -_MTL_INLINE NS::UInteger MTL::RenderCommandEncoder::tileWidth() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(tileWidth)); -} - -_MTL_INLINE NS::UInteger MTL::RenderCommandEncoder::tileHeight() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(tileHeight)); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setTileBytes(const void* bytes, NS::UInteger length, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTileBytes_length_atIndex_), bytes, length, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setTileBuffer(const MTL::Buffer* buffer, NS::UInteger offset, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTileBuffer_offset_atIndex_), buffer, offset, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setTileBufferOffset(NS::UInteger offset, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTileBufferOffset_atIndex_), offset, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setTileBuffers(const MTL::Buffer* const buffers[], const NS::UInteger* offsets, NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTileBuffers_offsets_withRange_), buffers, offsets, range); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setTileTexture(const MTL::Texture* texture, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTileTexture_atIndex_), texture, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setTileTextures(const MTL::Texture* const textures[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTileTextures_withRange_), textures, range); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setTileSamplerState(const MTL::SamplerState* sampler, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTileSamplerState_atIndex_), sampler, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setTileSamplerStates(const MTL::SamplerState* const samplers[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTileSamplerStates_withRange_), samplers, range); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setTileSamplerState(const MTL::SamplerState* sampler, float lodMinClamp, float lodMaxClamp, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTileSamplerState_lodMinClamp_lodMaxClamp_atIndex_), sampler, lodMinClamp, lodMaxClamp, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setTileSamplerStates(const MTL::SamplerState* const samplers[], const float lodMinClamps[], const float lodMaxClamps[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTileSamplerStates_lodMinClamps_lodMaxClamps_withRange_), samplers, lodMinClamps, lodMaxClamps, range); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setTileVisibleFunctionTable(const MTL::VisibleFunctionTable* functionTable, NS::UInteger bufferIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTileVisibleFunctionTable_atBufferIndex_), functionTable, bufferIndex); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setTileVisibleFunctionTables(const MTL::VisibleFunctionTable* const functionTables[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTileVisibleFunctionTables_withBufferRange_), functionTables, range); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setTileIntersectionFunctionTable(const MTL::IntersectionFunctionTable* intersectionFunctionTable, NS::UInteger bufferIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTileIntersectionFunctionTable_atBufferIndex_), intersectionFunctionTable, bufferIndex); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setTileIntersectionFunctionTables(const MTL::IntersectionFunctionTable* const intersectionFunctionTables[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTileIntersectionFunctionTables_withBufferRange_), intersectionFunctionTables, range); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setTileAccelerationStructure(const MTL::AccelerationStructure* accelerationStructure, NS::UInteger bufferIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTileAccelerationStructure_atBufferIndex_), accelerationStructure, bufferIndex); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::dispatchThreadsPerTile(MTL::Size threadsPerTile) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(dispatchThreadsPerTile_), threadsPerTile); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::setThreadgroupMemoryLength(NS::UInteger length, NS::UInteger offset, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setThreadgroupMemoryLength_offset_atIndex_), length, offset, index); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::useResource(const MTL::Resource* resource, MTL::ResourceUsage usage) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(useResource_usage_), resource, usage); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::useResources(const MTL::Resource* const resources[], NS::UInteger count, MTL::ResourceUsage usage) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(useResources_count_usage_), resources, count, usage); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::useResource(const MTL::Resource* resource, MTL::ResourceUsage usage, MTL::RenderStages stages) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(useResource_usage_stages_), resource, usage, stages); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::useResources(const MTL::Resource* const resources[], NS::UInteger count, MTL::ResourceUsage usage, MTL::RenderStages stages) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(useResources_count_usage_stages_), resources, count, usage, stages); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::useHeap(const MTL::Heap* heap) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(useHeap_), heap); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::useHeaps(const MTL::Heap* const heaps[], NS::UInteger count) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(useHeaps_count_), heaps, count); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::useHeap(const MTL::Heap* heap, MTL::RenderStages stages) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(useHeap_stages_), heap, stages); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::useHeaps(const MTL::Heap* const heaps[], NS::UInteger count, MTL::RenderStages stages) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(useHeaps_count_stages_), heaps, count, stages); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::executeCommandsInBuffer(const MTL::IndirectCommandBuffer* indirectCommandBuffer, NS::Range executionRange) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(executeCommandsInBuffer_withRange_), indirectCommandBuffer, executionRange); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::executeCommandsInBuffer(const MTL::IndirectCommandBuffer* indirectCommandbuffer, const MTL::Buffer* indirectRangeBuffer, NS::UInteger indirectBufferOffset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(executeCommandsInBuffer_indirectBuffer_indirectBufferOffset_), indirectCommandbuffer, indirectRangeBuffer, indirectBufferOffset); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::memoryBarrier(MTL::BarrierScope scope, MTL::RenderStages after, MTL::RenderStages before) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(memoryBarrierWithScope_afterStages_beforeStages_), scope, after, before); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::memoryBarrier(const MTL::Resource* const resources[], NS::UInteger count, MTL::RenderStages after, MTL::RenderStages before) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(memoryBarrierWithResources_count_afterStages_beforeStages_), resources, count, after, before); -} - -_MTL_INLINE void MTL::RenderCommandEncoder::sampleCountersInBuffer(const MTL::CounterSampleBuffer* sampleBuffer, NS::UInteger sampleIndex, bool barrier) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(sampleCountersInBuffer_atSampleIndex_withBarrier_), sampleBuffer, sampleIndex, barrier); -} - -namespace MTL -{ -class IndirectRenderCommand : public NS::Referencing -{ -public: - void setRenderPipelineState(const class RenderPipelineState* pipelineState); - - void setVertexBuffer(const class Buffer* buffer, NS::UInteger offset, NS::UInteger index); - - void setFragmentBuffer(const class Buffer* buffer, NS::UInteger offset, NS::UInteger index); - - void drawPatches(NS::UInteger numberOfPatchControlPoints, NS::UInteger patchStart, NS::UInteger patchCount, const class Buffer* patchIndexBuffer, NS::UInteger patchIndexBufferOffset, NS::UInteger instanceCount, NS::UInteger baseInstance, const class Buffer* buffer, NS::UInteger offset, NS::UInteger instanceStride); - - void drawIndexedPatches(NS::UInteger numberOfPatchControlPoints, NS::UInteger patchStart, NS::UInteger patchCount, const class Buffer* patchIndexBuffer, NS::UInteger patchIndexBufferOffset, const class Buffer* controlPointIndexBuffer, NS::UInteger controlPointIndexBufferOffset, NS::UInteger instanceCount, NS::UInteger baseInstance, const class Buffer* buffer, NS::UInteger offset, NS::UInteger instanceStride); - - void drawPrimitives(MTL::PrimitiveType primitiveType, NS::UInteger vertexStart, NS::UInteger vertexCount, NS::UInteger instanceCount, NS::UInteger baseInstance); - - void drawIndexedPrimitives(MTL::PrimitiveType primitiveType, NS::UInteger indexCount, MTL::IndexType indexType, const class Buffer* indexBuffer, NS::UInteger indexBufferOffset, NS::UInteger instanceCount, NS::Integer baseVertex, NS::UInteger baseInstance); - - void reset(); -}; - -class IndirectComputeCommand : public NS::Referencing -{ -public: - void setComputePipelineState(const class ComputePipelineState* pipelineState); - - void setKernelBuffer(const class Buffer* buffer, NS::UInteger offset, NS::UInteger index); - - void concurrentDispatchThreadgroups(MTL::Size threadgroupsPerGrid, MTL::Size threadsPerThreadgroup); - - void concurrentDispatchThreads(MTL::Size threadsPerGrid, MTL::Size threadsPerThreadgroup); - - void setBarrier(); - - void clearBarrier(); - - void setImageblockWidth(NS::UInteger width, NS::UInteger height); - - void reset(); - - void setThreadgroupMemoryLength(NS::UInteger length, NS::UInteger index); - - void setStageInRegion(MTL::Region region); -}; - -} - -_MTL_INLINE void MTL::IndirectRenderCommand::setRenderPipelineState(const MTL::RenderPipelineState* pipelineState) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setRenderPipelineState_), pipelineState); -} - -_MTL_INLINE void MTL::IndirectRenderCommand::setVertexBuffer(const MTL::Buffer* buffer, NS::UInteger offset, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVertexBuffer_offset_atIndex_), buffer, offset, index); -} - -_MTL_INLINE void MTL::IndirectRenderCommand::setFragmentBuffer(const MTL::Buffer* buffer, NS::UInteger offset, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFragmentBuffer_offset_atIndex_), buffer, offset, index); -} - -_MTL_INLINE void MTL::IndirectRenderCommand::drawPatches(NS::UInteger numberOfPatchControlPoints, NS::UInteger patchStart, NS::UInteger patchCount, const MTL::Buffer* patchIndexBuffer, NS::UInteger patchIndexBufferOffset, NS::UInteger instanceCount, NS::UInteger baseInstance, const MTL::Buffer* buffer, NS::UInteger offset, NS::UInteger instanceStride) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(drawPatches_patchStart_patchCount_patchIndexBuffer_patchIndexBufferOffset_instanceCount_baseInstance_tessellationFactorBuffer_tessellationFactorBufferOffset_tessellationFactorBufferInstanceStride_), numberOfPatchControlPoints, patchStart, patchCount, patchIndexBuffer, patchIndexBufferOffset, instanceCount, baseInstance, buffer, offset, instanceStride); -} - -_MTL_INLINE void MTL::IndirectRenderCommand::drawIndexedPatches(NS::UInteger numberOfPatchControlPoints, NS::UInteger patchStart, NS::UInteger patchCount, const MTL::Buffer* patchIndexBuffer, NS::UInteger patchIndexBufferOffset, const MTL::Buffer* controlPointIndexBuffer, NS::UInteger controlPointIndexBufferOffset, NS::UInteger instanceCount, NS::UInteger baseInstance, const MTL::Buffer* buffer, NS::UInteger offset, NS::UInteger instanceStride) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(drawIndexedPatches_patchStart_patchCount_patchIndexBuffer_patchIndexBufferOffset_controlPointIndexBuffer_controlPointIndexBufferOffset_instanceCount_baseInstance_tessellationFactorBuffer_tessellationFactorBufferOffset_tessellationFactorBufferInstanceStride_), numberOfPatchControlPoints, patchStart, patchCount, patchIndexBuffer, patchIndexBufferOffset, controlPointIndexBuffer, controlPointIndexBufferOffset, instanceCount, baseInstance, buffer, offset, instanceStride); -} - -_MTL_INLINE void MTL::IndirectRenderCommand::drawPrimitives(MTL::PrimitiveType primitiveType, NS::UInteger vertexStart, NS::UInteger vertexCount, NS::UInteger instanceCount, NS::UInteger baseInstance) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(drawPrimitives_vertexStart_vertexCount_instanceCount_baseInstance_), primitiveType, vertexStart, vertexCount, instanceCount, baseInstance); -} - -_MTL_INLINE void MTL::IndirectRenderCommand::drawIndexedPrimitives(MTL::PrimitiveType primitiveType, NS::UInteger indexCount, MTL::IndexType indexType, const MTL::Buffer* indexBuffer, NS::UInteger indexBufferOffset, NS::UInteger instanceCount, NS::Integer baseVertex, NS::UInteger baseInstance) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(drawIndexedPrimitives_indexCount_indexType_indexBuffer_indexBufferOffset_instanceCount_baseVertex_baseInstance_), primitiveType, indexCount, indexType, indexBuffer, indexBufferOffset, instanceCount, baseVertex, baseInstance); -} - -_MTL_INLINE void MTL::IndirectRenderCommand::reset() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(reset)); -} - -_MTL_INLINE void MTL::IndirectComputeCommand::setComputePipelineState(const MTL::ComputePipelineState* pipelineState) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setComputePipelineState_), pipelineState); -} - -_MTL_INLINE void MTL::IndirectComputeCommand::setKernelBuffer(const MTL::Buffer* buffer, NS::UInteger offset, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setKernelBuffer_offset_atIndex_), buffer, offset, index); -} - -_MTL_INLINE void MTL::IndirectComputeCommand::concurrentDispatchThreadgroups(MTL::Size threadgroupsPerGrid, MTL::Size threadsPerThreadgroup) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(concurrentDispatchThreadgroups_threadsPerThreadgroup_), threadgroupsPerGrid, threadsPerThreadgroup); -} - -_MTL_INLINE void MTL::IndirectComputeCommand::concurrentDispatchThreads(MTL::Size threadsPerGrid, MTL::Size threadsPerThreadgroup) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(concurrentDispatchThreads_threadsPerThreadgroup_), threadsPerGrid, threadsPerThreadgroup); -} - -_MTL_INLINE void MTL::IndirectComputeCommand::setBarrier() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setBarrier)); -} - -_MTL_INLINE void MTL::IndirectComputeCommand::clearBarrier() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(clearBarrier)); -} - -_MTL_INLINE void MTL::IndirectComputeCommand::setImageblockWidth(NS::UInteger width, NS::UInteger height) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setImageblockWidth_height_), width, height); -} - -_MTL_INLINE void MTL::IndirectComputeCommand::reset() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(reset)); -} - -_MTL_INLINE void MTL::IndirectComputeCommand::setThreadgroupMemoryLength(NS::UInteger length, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setThreadgroupMemoryLength_atIndex_), length, index); -} - -_MTL_INLINE void MTL::IndirectComputeCommand::setStageInRegion(MTL::Region region) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStageInRegion_), region); -} - -#pragma once - -namespace MTL -{ -_MTL_OPTIONS(NS::UInteger, IntersectionFunctionSignature) { - IntersectionFunctionSignatureNone = 0, - IntersectionFunctionSignatureInstancing = 1, - IntersectionFunctionSignatureTriangleData = 2, - IntersectionFunctionSignatureWorldSpaceData = 4, - IntersectionFunctionSignatureInstanceMotion = 8, - IntersectionFunctionSignaturePrimitiveMotion = 16, - IntersectionFunctionSignatureExtendedLimits = 32, -}; - -class IntersectionFunctionTableDescriptor : public NS::Copying -{ -public: - static class IntersectionFunctionTableDescriptor* alloc(); - - class IntersectionFunctionTableDescriptor* init(); - - static class IntersectionFunctionTableDescriptor* intersectionFunctionTableDescriptor(); - - NS::UInteger functionCount() const; - void setFunctionCount(NS::UInteger functionCount); -}; - -class IntersectionFunctionTable : public NS::Referencing -{ -public: - void setBuffer(const class Buffer* buffer, NS::UInteger offset, NS::UInteger index); - - void setBuffers(const class Buffer* const buffers[], const NS::UInteger offsets[], NS::Range range); - - MTL::ResourceID gpuResourceID() const; - - void setFunction(const class FunctionHandle* function, NS::UInteger index); - - void setFunctions(const class FunctionHandle* const functions[], NS::Range range); - - void setOpaqueTriangleIntersectionFunction(MTL::IntersectionFunctionSignature signature, NS::UInteger index); - - void setOpaqueTriangleIntersectionFunction(MTL::IntersectionFunctionSignature signature, NS::Range range); - - void setVisibleFunctionTable(const class VisibleFunctionTable* functionTable, NS::UInteger bufferIndex); - - void setVisibleFunctionTables(const class VisibleFunctionTable* const functionTables[], NS::Range bufferRange); -}; - -} - -_MTL_INLINE MTL::IntersectionFunctionTableDescriptor* MTL::IntersectionFunctionTableDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLIntersectionFunctionTableDescriptor)); -} - -_MTL_INLINE MTL::IntersectionFunctionTableDescriptor* MTL::IntersectionFunctionTableDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::IntersectionFunctionTableDescriptor* MTL::IntersectionFunctionTableDescriptor::intersectionFunctionTableDescriptor() -{ - return Object::sendMessage(_MTL_PRIVATE_CLS(MTLIntersectionFunctionTableDescriptor), _MTL_PRIVATE_SEL(intersectionFunctionTableDescriptor)); -} - -_MTL_INLINE NS::UInteger MTL::IntersectionFunctionTableDescriptor::functionCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(functionCount)); -} - -_MTL_INLINE void MTL::IntersectionFunctionTableDescriptor::setFunctionCount(NS::UInteger functionCount) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFunctionCount_), functionCount); -} - -_MTL_INLINE void MTL::IntersectionFunctionTable::setBuffer(const MTL::Buffer* buffer, NS::UInteger offset, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setBuffer_offset_atIndex_), buffer, offset, index); -} - -_MTL_INLINE void MTL::IntersectionFunctionTable::setBuffers(const MTL::Buffer* const buffers[], const NS::UInteger offsets[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setBuffers_offsets_withRange_), buffers, offsets, range); -} - -_MTL_INLINE MTL::ResourceID MTL::IntersectionFunctionTable::gpuResourceID() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(gpuResourceID)); -} - -_MTL_INLINE void MTL::IntersectionFunctionTable::setFunction(const MTL::FunctionHandle* function, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFunction_atIndex_), function, index); -} - -_MTL_INLINE void MTL::IntersectionFunctionTable::setFunctions(const MTL::FunctionHandle* const functions[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFunctions_withRange_), functions, range); -} - -_MTL_INLINE void MTL::IntersectionFunctionTable::setOpaqueTriangleIntersectionFunction(MTL::IntersectionFunctionSignature signature, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setOpaqueTriangleIntersectionFunctionWithSignature_atIndex_), signature, index); -} - -_MTL_INLINE void MTL::IntersectionFunctionTable::setOpaqueTriangleIntersectionFunction(MTL::IntersectionFunctionSignature signature, NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setOpaqueTriangleIntersectionFunctionWithSignature_withRange_), signature, range); -} - -_MTL_INLINE void MTL::IntersectionFunctionTable::setVisibleFunctionTable(const MTL::VisibleFunctionTable* functionTable, NS::UInteger bufferIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVisibleFunctionTable_atBufferIndex_), functionTable, bufferIndex); -} - -_MTL_INLINE void MTL::IntersectionFunctionTable::setVisibleFunctionTables(const MTL::VisibleFunctionTable* const functionTables[], NS::Range bufferRange) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVisibleFunctionTables_withBufferRange_), functionTables, bufferRange); -} - -#pragma once - -namespace MTL -{ -_MTL_ENUM(NS::Integer, IOStatus) { - IOStatusPending = 0, - IOStatusCancelled = 1, - IOStatusError = 2, - IOStatusComplete = 3, -}; - -using IOCommandBufferHandler = void (^)(class IOCommandBuffer*); - -using IOCommandBufferHandlerFunction = std::function; - -class IOCommandBuffer : public NS::Referencing -{ -public: - void addCompletedHandler(const MTL::IOCommandBufferHandlerFunction& function); - - void addCompletedHandler(const MTL::IOCommandBufferHandler block); - - void loadBytes(const void* pointer, NS::UInteger size, const class IOFileHandle* sourceHandle, NS::UInteger sourceHandleOffset); - - void loadBuffer(const class Buffer* buffer, NS::UInteger offset, NS::UInteger size, const class IOFileHandle* sourceHandle, NS::UInteger sourceHandleOffset); - - void loadTexture(const class Texture* texture, NS::UInteger slice, NS::UInteger level, MTL::Size size, NS::UInteger sourceBytesPerRow, NS::UInteger sourceBytesPerImage, MTL::Origin destinationOrigin, const class IOFileHandle* sourceHandle, NS::UInteger sourceHandleOffset); - - void copyStatusToBuffer(const class Buffer* buffer, NS::UInteger offset); - - void commit(); - - void waitUntilCompleted(); - - void tryCancel(); - - void addBarrier(); - - void pushDebugGroup(const NS::String* string); - - void popDebugGroup(); - - void enqueue(); - - void wait(const class SharedEvent* event, uint64_t value); - - void signalEvent(const class SharedEvent* event, uint64_t value); - - NS::String* label() const; - void setLabel(const NS::String* label); - - MTL::IOStatus status() const; - - NS::Error* error() const; -}; - -} - -_MTL_INLINE void MTL::IOCommandBuffer::addCompletedHandler(const MTL::IOCommandBufferHandlerFunction& function) -{ - __block IOCommandBufferHandlerFunction blockFunction = function; - - addCompletedHandler(^(IOCommandBuffer* pCommandBuffer) { blockFunction(pCommandBuffer); }); -} - -_MTL_INLINE void MTL::IOCommandBuffer::addCompletedHandler(const MTL::IOCommandBufferHandler block) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(addCompletedHandler_), block); -} - -_MTL_INLINE void MTL::IOCommandBuffer::loadBytes(const void* pointer, NS::UInteger size, const MTL::IOFileHandle* sourceHandle, NS::UInteger sourceHandleOffset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(loadBytes_size_sourceHandle_sourceHandleOffset_), pointer, size, sourceHandle, sourceHandleOffset); -} - -_MTL_INLINE void MTL::IOCommandBuffer::loadBuffer(const MTL::Buffer* buffer, NS::UInteger offset, NS::UInteger size, const MTL::IOFileHandle* sourceHandle, NS::UInteger sourceHandleOffset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(loadBuffer_offset_size_sourceHandle_sourceHandleOffset_), buffer, offset, size, sourceHandle, sourceHandleOffset); -} - -_MTL_INLINE void MTL::IOCommandBuffer::loadTexture(const MTL::Texture* texture, NS::UInteger slice, NS::UInteger level, MTL::Size size, NS::UInteger sourceBytesPerRow, NS::UInteger sourceBytesPerImage, MTL::Origin destinationOrigin, const MTL::IOFileHandle* sourceHandle, NS::UInteger sourceHandleOffset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(loadTexture_slice_level_size_sourceBytesPerRow_sourceBytesPerImage_destinationOrigin_sourceHandle_sourceHandleOffset_), texture, slice, level, size, sourceBytesPerRow, sourceBytesPerImage, destinationOrigin, sourceHandle, sourceHandleOffset); -} - -_MTL_INLINE void MTL::IOCommandBuffer::copyStatusToBuffer(const MTL::Buffer* buffer, NS::UInteger offset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(copyStatusToBuffer_offset_), buffer, offset); -} - -_MTL_INLINE void MTL::IOCommandBuffer::commit() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(commit)); -} - -_MTL_INLINE void MTL::IOCommandBuffer::waitUntilCompleted() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(waitUntilCompleted)); -} - -_MTL_INLINE void MTL::IOCommandBuffer::tryCancel() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(tryCancel)); -} - -_MTL_INLINE void MTL::IOCommandBuffer::addBarrier() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(addBarrier)); -} - -_MTL_INLINE void MTL::IOCommandBuffer::pushDebugGroup(const NS::String* string) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(pushDebugGroup_), string); -} - -_MTL_INLINE void MTL::IOCommandBuffer::popDebugGroup() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(popDebugGroup)); -} - -_MTL_INLINE void MTL::IOCommandBuffer::enqueue() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(enqueue)); -} - -_MTL_INLINE void MTL::IOCommandBuffer::wait(const MTL::SharedEvent* event, uint64_t value) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(waitForEvent_value_), event, value); -} - -_MTL_INLINE void MTL::IOCommandBuffer::signalEvent(const MTL::SharedEvent* event, uint64_t value) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(signalEvent_value_), event, value); -} - -_MTL_INLINE NS::String* MTL::IOCommandBuffer::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE void MTL::IOCommandBuffer::setLabel(const NS::String* label) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLabel_), label); -} - -_MTL_INLINE MTL::IOStatus MTL::IOCommandBuffer::status() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(status)); -} - -_MTL_INLINE NS::Error* MTL::IOCommandBuffer::error() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(error)); -} - -#pragma once - -namespace MTL -{ -_MTL_ENUM(NS::Integer, IOPriority) { - IOPriorityHigh = 0, - IOPriorityNormal = 1, - IOPriorityLow = 2, -}; - -_MTL_ENUM(NS::Integer, IOCommandQueueType) { - IOCommandQueueTypeConcurrent = 0, - IOCommandQueueTypeSerial = 1, -}; - -_MTL_CONST(NS::ErrorDomain, IOErrorDomain); - -_MTL_ENUM(NS::Integer, IOError) { - IOErrorURLInvalid = 1, - IOErrorInternal = 2, -}; - -class IOCommandQueue : public NS::Referencing -{ -public: - void enqueueBarrier(); - - class IOCommandBuffer* commandBuffer(); - - class IOCommandBuffer* commandBufferWithUnretainedReferences(); - - NS::String* label() const; - void setLabel(const NS::String* label); -}; - -class IOScratchBuffer : public NS::Referencing -{ -public: - class Buffer* buffer() const; -}; - -class IOScratchBufferAllocator : public NS::Referencing -{ -public: - class IOScratchBuffer* newScratchBuffer(NS::UInteger minimumSize); -}; - -class IOCommandQueueDescriptor : public NS::Copying -{ -public: - static class IOCommandQueueDescriptor* alloc(); - - class IOCommandQueueDescriptor* init(); - - NS::UInteger maxCommandBufferCount() const; - void setMaxCommandBufferCount(NS::UInteger maxCommandBufferCount); - - MTL::IOPriority priority() const; - void setPriority(MTL::IOPriority priority); - - MTL::IOCommandQueueType type() const; - void setType(MTL::IOCommandQueueType type); - - NS::UInteger maxCommandsInFlight() const; - void setMaxCommandsInFlight(NS::UInteger maxCommandsInFlight); - - class IOScratchBufferAllocator* scratchBufferAllocator() const; - void setScratchBufferAllocator(const class IOScratchBufferAllocator* scratchBufferAllocator); -}; - -class IOFileHandle : public NS::Referencing -{ -public: - NS::String* label() const; - void setLabel(const NS::String* label); -}; - -} - -_MTL_INLINE void MTL::IOCommandQueue::enqueueBarrier() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(enqueueBarrier)); -} - -_MTL_INLINE MTL::IOCommandBuffer* MTL::IOCommandQueue::commandBuffer() -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(commandBuffer)); -} - -_MTL_INLINE MTL::IOCommandBuffer* MTL::IOCommandQueue::commandBufferWithUnretainedReferences() -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(commandBufferWithUnretainedReferences)); -} - -_MTL_INLINE NS::String* MTL::IOCommandQueue::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE void MTL::IOCommandQueue::setLabel(const NS::String* label) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLabel_), label); -} - -_MTL_INLINE MTL::Buffer* MTL::IOScratchBuffer::buffer() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(buffer)); -} - -_MTL_INLINE MTL::IOScratchBuffer* MTL::IOScratchBufferAllocator::newScratchBuffer(NS::UInteger minimumSize) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newScratchBufferWithMinimumSize_), minimumSize); -} - -_MTL_INLINE MTL::IOCommandQueueDescriptor* MTL::IOCommandQueueDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLIOCommandQueueDescriptor)); -} - -_MTL_INLINE MTL::IOCommandQueueDescriptor* MTL::IOCommandQueueDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE NS::UInteger MTL::IOCommandQueueDescriptor::maxCommandBufferCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(maxCommandBufferCount)); -} - -_MTL_INLINE void MTL::IOCommandQueueDescriptor::setMaxCommandBufferCount(NS::UInteger maxCommandBufferCount) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMaxCommandBufferCount_), maxCommandBufferCount); -} - -_MTL_INLINE MTL::IOPriority MTL::IOCommandQueueDescriptor::priority() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(priority)); -} - -_MTL_INLINE void MTL::IOCommandQueueDescriptor::setPriority(MTL::IOPriority priority) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setPriority_), priority); -} - -_MTL_INLINE MTL::IOCommandQueueType MTL::IOCommandQueueDescriptor::type() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(type)); -} - -_MTL_INLINE void MTL::IOCommandQueueDescriptor::setType(MTL::IOCommandQueueType type) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setType_), type); -} - -_MTL_INLINE NS::UInteger MTL::IOCommandQueueDescriptor::maxCommandsInFlight() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(maxCommandsInFlight)); -} - -_MTL_INLINE void MTL::IOCommandQueueDescriptor::setMaxCommandsInFlight(NS::UInteger maxCommandsInFlight) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMaxCommandsInFlight_), maxCommandsInFlight); -} - -_MTL_INLINE MTL::IOScratchBufferAllocator* MTL::IOCommandQueueDescriptor::scratchBufferAllocator() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(scratchBufferAllocator)); -} - -_MTL_INLINE void MTL::IOCommandQueueDescriptor::setScratchBufferAllocator(const MTL::IOScratchBufferAllocator* scratchBufferAllocator) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setScratchBufferAllocator_), scratchBufferAllocator); -} - -_MTL_INLINE NS::String* MTL::IOFileHandle::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE void MTL::IOFileHandle::setLabel(const NS::String* label) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLabel_), label); -} - -#pragma once - -namespace MTL -{ -_MTL_ENUM(NS::Integer, IOCompressionStatus) { - IOCompressionStatusComplete = 0, - IOCompressionStatusError = 1, -}; - -size_t IOCompressionContextDefaultChunkSize(); - -void* IOCreateCompressionContext(const char* path, IOCompressionMethod type, size_t chunkSize); - -void IOCompressionContextAppendData(void* context, const void* data, size_t size); - -IOCompressionStatus IOFlushAndDestroyCompressionContext(void* context); - -} - -#if defined(MTL_PRIVATE_IMPLEMENTATION) - -namespace MTL::Private { - -MTL_DEF_FUNC(MTLIOCompressionContextDefaultChunkSize, size_t (*)(void)); - -MTL_DEF_FUNC( MTLIOCreateCompressionContext, void* (*)(const char*, MTL::IOCompressionMethod, size_t) ); - -MTL_DEF_FUNC( MTLIOCompressionContextAppendData, void (*)(void*, const void*, size_t) ); - -MTL_DEF_FUNC( MTLIOFlushAndDestroyCompressionContext, MTL::IOCompressionStatus (*)(void*) ); - -} - -_NS_EXPORT size_t MTL::IOCompressionContextDefaultChunkSize() -{ - return MTL::Private::MTLIOCompressionContextDefaultChunkSize(); -} - -_NS_EXPORT void* MTL::IOCreateCompressionContext(const char* path, IOCompressionMethod type, size_t chunkSize) -{ - if ( MTL::Private::MTLIOCreateCompressionContext ) - { - return MTL::Private::MTLIOCreateCompressionContext( path, type, chunkSize ); - } - return nullptr; -} - -_NS_EXPORT void MTL::IOCompressionContextAppendData(void* context, const void* data, size_t size) -{ - if ( MTL::Private::MTLIOCompressionContextAppendData ) - { - MTL::Private::MTLIOCompressionContextAppendData( context, data, size ); - } -} - -_NS_EXPORT MTL::IOCompressionStatus MTL::IOFlushAndDestroyCompressionContext(void* context) -{ - if ( MTL::Private::MTLIOFlushAndDestroyCompressionContext ) - { - return MTL::Private::MTLIOFlushAndDestroyCompressionContext( context ); - } - return MTL::IOCompressionStatusError; -} - -#endif - -#pragma once - -namespace MTL -{ -class LinkedFunctions : public NS::Copying -{ -public: - static class LinkedFunctions* alloc(); - - class LinkedFunctions* init(); - - static class LinkedFunctions* linkedFunctions(); - - NS::Array* functions() const; - void setFunctions(const NS::Array* functions); - - NS::Array* binaryFunctions() const; - void setBinaryFunctions(const NS::Array* binaryFunctions); - - NS::Dictionary* groups() const; - void setGroups(const NS::Dictionary* groups); - - NS::Array* privateFunctions() const; - void setPrivateFunctions(const NS::Array* privateFunctions); -}; - -} - -_MTL_INLINE MTL::LinkedFunctions* MTL::LinkedFunctions::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLLinkedFunctions)); -} - -_MTL_INLINE MTL::LinkedFunctions* MTL::LinkedFunctions::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::LinkedFunctions* MTL::LinkedFunctions::linkedFunctions() -{ - return Object::sendMessage(_MTL_PRIVATE_CLS(MTLLinkedFunctions), _MTL_PRIVATE_SEL(linkedFunctions)); -} - -_MTL_INLINE NS::Array* MTL::LinkedFunctions::functions() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(functions)); -} - -_MTL_INLINE void MTL::LinkedFunctions::setFunctions(const NS::Array* functions) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFunctions_), functions); -} - -_MTL_INLINE NS::Array* MTL::LinkedFunctions::binaryFunctions() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(binaryFunctions)); -} - -_MTL_INLINE void MTL::LinkedFunctions::setBinaryFunctions(const NS::Array* binaryFunctions) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setBinaryFunctions_), binaryFunctions); -} - -_MTL_INLINE NS::Dictionary* MTL::LinkedFunctions::groups() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(groups)); -} - -_MTL_INLINE void MTL::LinkedFunctions::setGroups(const NS::Dictionary* groups) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setGroups_), groups); -} - -_MTL_INLINE NS::Array* MTL::LinkedFunctions::privateFunctions() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(privateFunctions)); -} - -_MTL_INLINE void MTL::LinkedFunctions::setPrivateFunctions(const NS::Array* privateFunctions) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setPrivateFunctions_), privateFunctions); -} - -#pragma once - -namespace MTL -{ -class ParallelRenderCommandEncoder : public NS::Referencing -{ -public: - class RenderCommandEncoder* renderCommandEncoder(); - - void setColorStoreAction(MTL::StoreAction storeAction, NS::UInteger colorAttachmentIndex); - - void setDepthStoreAction(MTL::StoreAction storeAction); - - void setStencilStoreAction(MTL::StoreAction storeAction); - - void setColorStoreActionOptions(MTL::StoreActionOptions storeActionOptions, NS::UInteger colorAttachmentIndex); - - void setDepthStoreActionOptions(MTL::StoreActionOptions storeActionOptions); - - void setStencilStoreActionOptions(MTL::StoreActionOptions storeActionOptions); -}; - -} - -_MTL_INLINE MTL::RenderCommandEncoder* MTL::ParallelRenderCommandEncoder::renderCommandEncoder() -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(renderCommandEncoder)); -} - -_MTL_INLINE void MTL::ParallelRenderCommandEncoder::setColorStoreAction(MTL::StoreAction storeAction, NS::UInteger colorAttachmentIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setColorStoreAction_atIndex_), storeAction, colorAttachmentIndex); -} - -_MTL_INLINE void MTL::ParallelRenderCommandEncoder::setDepthStoreAction(MTL::StoreAction storeAction) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setDepthStoreAction_), storeAction); -} - -_MTL_INLINE void MTL::ParallelRenderCommandEncoder::setStencilStoreAction(MTL::StoreAction storeAction) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStencilStoreAction_), storeAction); -} - -_MTL_INLINE void MTL::ParallelRenderCommandEncoder::setColorStoreActionOptions(MTL::StoreActionOptions storeActionOptions, NS::UInteger colorAttachmentIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setColorStoreActionOptions_atIndex_), storeActionOptions, colorAttachmentIndex); -} - -_MTL_INLINE void MTL::ParallelRenderCommandEncoder::setDepthStoreActionOptions(MTL::StoreActionOptions storeActionOptions) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setDepthStoreActionOptions_), storeActionOptions); -} - -_MTL_INLINE void MTL::ParallelRenderCommandEncoder::setStencilStoreActionOptions(MTL::StoreActionOptions storeActionOptions) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStencilStoreActionOptions_), storeActionOptions); -} - -#pragma once - -namespace MTL -{ -_MTL_ENUM(NS::UInteger, Mutability) { - MutabilityDefault = 0, - MutabilityMutable = 1, - MutabilityImmutable = 2, -}; - -class PipelineBufferDescriptor : public NS::Copying -{ -public: - static class PipelineBufferDescriptor* alloc(); - - class PipelineBufferDescriptor* init(); - - MTL::Mutability mutability() const; - void setMutability(MTL::Mutability mutability); -}; - -class PipelineBufferDescriptorArray : public NS::Referencing -{ -public: - static class PipelineBufferDescriptorArray* alloc(); - - class PipelineBufferDescriptorArray* init(); - - class PipelineBufferDescriptor* object(NS::UInteger bufferIndex); - - void setObject(const class PipelineBufferDescriptor* buffer, NS::UInteger bufferIndex); -}; - -} - -_MTL_INLINE MTL::PipelineBufferDescriptor* MTL::PipelineBufferDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLPipelineBufferDescriptor)); -} - -_MTL_INLINE MTL::PipelineBufferDescriptor* MTL::PipelineBufferDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::Mutability MTL::PipelineBufferDescriptor::mutability() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(mutability)); -} - -_MTL_INLINE void MTL::PipelineBufferDescriptor::setMutability(MTL::Mutability mutability) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMutability_), mutability); -} - -_MTL_INLINE MTL::PipelineBufferDescriptorArray* MTL::PipelineBufferDescriptorArray::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLPipelineBufferDescriptorArray)); -} - -_MTL_INLINE MTL::PipelineBufferDescriptorArray* MTL::PipelineBufferDescriptorArray::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::PipelineBufferDescriptor* MTL::PipelineBufferDescriptorArray::object(NS::UInteger bufferIndex) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(objectAtIndexedSubscript_), bufferIndex); -} - -_MTL_INLINE void MTL::PipelineBufferDescriptorArray::setObject(const MTL::PipelineBufferDescriptor* buffer, NS::UInteger bufferIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setObject_atIndexedSubscript_), buffer, bufferIndex); -} - -#pragma once - -namespace MTL -{ -class RasterizationRateSampleArray : public NS::Referencing -{ -public: - static class RasterizationRateSampleArray* alloc(); - - class RasterizationRateSampleArray* init(); - - NS::Number* object(NS::UInteger index); - - void setObject(const NS::Number* value, NS::UInteger index); -}; - -class RasterizationRateLayerDescriptor : public NS::Copying -{ -public: - static class RasterizationRateLayerDescriptor* alloc(); - - MTL::RasterizationRateLayerDescriptor* init(); - - MTL::RasterizationRateLayerDescriptor* init(MTL::Size sampleCount); - - MTL::RasterizationRateLayerDescriptor* init(MTL::Size sampleCount, const float* horizontal, const float* vertical); - - MTL::Size sampleCount() const; - - MTL::Size maxSampleCount() const; - - float* horizontalSampleStorage() const; - - float* verticalSampleStorage() const; - - class RasterizationRateSampleArray* horizontal() const; - - class RasterizationRateSampleArray* vertical() const; - - void setSampleCount(MTL::Size sampleCount); -}; - -class RasterizationRateLayerArray : public NS::Referencing -{ -public: - static class RasterizationRateLayerArray* alloc(); - - class RasterizationRateLayerArray* init(); - - class RasterizationRateLayerDescriptor* object(NS::UInteger layerIndex); - - void setObject(const class RasterizationRateLayerDescriptor* layer, NS::UInteger layerIndex); -}; - -class RasterizationRateMapDescriptor : public NS::Copying -{ -public: - static class RasterizationRateMapDescriptor* alloc(); - - class RasterizationRateMapDescriptor* init(); - - static class RasterizationRateMapDescriptor* rasterizationRateMapDescriptor(MTL::Size screenSize); - - static class RasterizationRateMapDescriptor* rasterizationRateMapDescriptor(MTL::Size screenSize, const class RasterizationRateLayerDescriptor* layer); - - static class RasterizationRateMapDescriptor* rasterizationRateMapDescriptor(MTL::Size screenSize, NS::UInteger layerCount, const class RasterizationRateLayerDescriptor* const* layers); - - class RasterizationRateLayerDescriptor* layer(NS::UInteger layerIndex); - - void setLayer(const class RasterizationRateLayerDescriptor* layer, NS::UInteger layerIndex); - - class RasterizationRateLayerArray* layers() const; - - MTL::Size screenSize() const; - void setScreenSize(MTL::Size screenSize); - - NS::String* label() const; - void setLabel(const NS::String* label); - - NS::UInteger layerCount() const; -}; - -class RasterizationRateMap : public NS::Referencing -{ -public: - class Device* device() const; - - NS::String* label() const; - - MTL::Size screenSize() const; - - MTL::Size physicalGranularity() const; - - NS::UInteger layerCount() const; - - MTL::SizeAndAlign parameterBufferSizeAndAlign() const; - - void copyParameterDataToBuffer(const class Buffer* buffer, NS::UInteger offset); - - MTL::Size physicalSize(NS::UInteger layerIndex); - - MTL::Coordinate2D mapScreenToPhysicalCoordinates(MTL::Coordinate2D screenCoordinates, NS::UInteger layerIndex); - - MTL::Coordinate2D mapPhysicalToScreenCoordinates(MTL::Coordinate2D physicalCoordinates, NS::UInteger layerIndex); -}; - -} - -_MTL_INLINE MTL::RasterizationRateSampleArray* MTL::RasterizationRateSampleArray::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLRasterizationRateSampleArray)); -} - -_MTL_INLINE MTL::RasterizationRateSampleArray* MTL::RasterizationRateSampleArray::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE NS::Number* MTL::RasterizationRateSampleArray::object(NS::UInteger index) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(objectAtIndexedSubscript_), index); -} - -_MTL_INLINE void MTL::RasterizationRateSampleArray::setObject(const NS::Number* value, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setObject_atIndexedSubscript_), value, index); -} - -_MTL_INLINE MTL::RasterizationRateLayerDescriptor* MTL::RasterizationRateLayerDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLRasterizationRateLayerDescriptor)); -} - -_MTL_INLINE MTL::RasterizationRateLayerDescriptor* MTL::RasterizationRateLayerDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::RasterizationRateLayerDescriptor* MTL::RasterizationRateLayerDescriptor::init(MTL::Size sampleCount) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(initWithSampleCount_), sampleCount); -} - -_MTL_INLINE MTL::RasterizationRateLayerDescriptor* MTL::RasterizationRateLayerDescriptor::init(MTL::Size sampleCount, const float* horizontal, const float* vertical) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(initWithSampleCount_horizontal_vertical_), sampleCount, horizontal, vertical); -} - -_MTL_INLINE MTL::Size MTL::RasterizationRateLayerDescriptor::sampleCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(sampleCount)); -} - -_MTL_INLINE MTL::Size MTL::RasterizationRateLayerDescriptor::maxSampleCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(maxSampleCount)); -} - -_MTL_INLINE float* MTL::RasterizationRateLayerDescriptor::horizontalSampleStorage() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(horizontalSampleStorage)); -} - -_MTL_INLINE float* MTL::RasterizationRateLayerDescriptor::verticalSampleStorage() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(verticalSampleStorage)); -} - -_MTL_INLINE MTL::RasterizationRateSampleArray* MTL::RasterizationRateLayerDescriptor::horizontal() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(horizontal)); -} - -_MTL_INLINE MTL::RasterizationRateSampleArray* MTL::RasterizationRateLayerDescriptor::vertical() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(vertical)); -} - -_MTL_INLINE void MTL::RasterizationRateLayerDescriptor::setSampleCount(MTL::Size sampleCount) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSampleCount_), sampleCount); -} - -_MTL_INLINE MTL::RasterizationRateLayerArray* MTL::RasterizationRateLayerArray::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLRasterizationRateLayerArray)); -} - -_MTL_INLINE MTL::RasterizationRateLayerArray* MTL::RasterizationRateLayerArray::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::RasterizationRateLayerDescriptor* MTL::RasterizationRateLayerArray::object(NS::UInteger layerIndex) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(objectAtIndexedSubscript_), layerIndex); -} - -_MTL_INLINE void MTL::RasterizationRateLayerArray::setObject(const MTL::RasterizationRateLayerDescriptor* layer, NS::UInteger layerIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setObject_atIndexedSubscript_), layer, layerIndex); -} - -_MTL_INLINE MTL::RasterizationRateMapDescriptor* MTL::RasterizationRateMapDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLRasterizationRateMapDescriptor)); -} - -_MTL_INLINE MTL::RasterizationRateMapDescriptor* MTL::RasterizationRateMapDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::RasterizationRateMapDescriptor* MTL::RasterizationRateMapDescriptor::rasterizationRateMapDescriptor(MTL::Size screenSize) -{ - return Object::sendMessage(_MTL_PRIVATE_CLS(MTLRasterizationRateMapDescriptor), _MTL_PRIVATE_SEL(rasterizationRateMapDescriptorWithScreenSize_), screenSize); -} - -_MTL_INLINE MTL::RasterizationRateMapDescriptor* MTL::RasterizationRateMapDescriptor::rasterizationRateMapDescriptor(MTL::Size screenSize, const MTL::RasterizationRateLayerDescriptor* layer) -{ - return Object::sendMessage(_MTL_PRIVATE_CLS(MTLRasterizationRateMapDescriptor), _MTL_PRIVATE_SEL(rasterizationRateMapDescriptorWithScreenSize_layer_), screenSize, layer); -} - -_MTL_INLINE MTL::RasterizationRateMapDescriptor* MTL::RasterizationRateMapDescriptor::rasterizationRateMapDescriptor(MTL::Size screenSize, NS::UInteger layerCount, const MTL::RasterizationRateLayerDescriptor* const* layers) -{ - return Object::sendMessage(_MTL_PRIVATE_CLS(MTLRasterizationRateMapDescriptor), _MTL_PRIVATE_SEL(rasterizationRateMapDescriptorWithScreenSize_layerCount_layers_), screenSize, layerCount, layers); -} - -_MTL_INLINE MTL::RasterizationRateLayerDescriptor* MTL::RasterizationRateMapDescriptor::layer(NS::UInteger layerIndex) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(layerAtIndex_), layerIndex); -} - -_MTL_INLINE void MTL::RasterizationRateMapDescriptor::setLayer(const MTL::RasterizationRateLayerDescriptor* layer, NS::UInteger layerIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLayer_atIndex_), layer, layerIndex); -} - -_MTL_INLINE MTL::RasterizationRateLayerArray* MTL::RasterizationRateMapDescriptor::layers() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(layers)); -} - -_MTL_INLINE MTL::Size MTL::RasterizationRateMapDescriptor::screenSize() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(screenSize)); -} - -_MTL_INLINE void MTL::RasterizationRateMapDescriptor::setScreenSize(MTL::Size screenSize) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setScreenSize_), screenSize); -} - -_MTL_INLINE NS::String* MTL::RasterizationRateMapDescriptor::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE void MTL::RasterizationRateMapDescriptor::setLabel(const NS::String* label) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLabel_), label); -} - -_MTL_INLINE NS::UInteger MTL::RasterizationRateMapDescriptor::layerCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(layerCount)); -} - -_MTL_INLINE MTL::Device* MTL::RasterizationRateMap::device() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(device)); -} - -_MTL_INLINE NS::String* MTL::RasterizationRateMap::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE MTL::Size MTL::RasterizationRateMap::screenSize() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(screenSize)); -} - -_MTL_INLINE MTL::Size MTL::RasterizationRateMap::physicalGranularity() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(physicalGranularity)); -} - -_MTL_INLINE NS::UInteger MTL::RasterizationRateMap::layerCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(layerCount)); -} - -_MTL_INLINE MTL::SizeAndAlign MTL::RasterizationRateMap::parameterBufferSizeAndAlign() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(parameterBufferSizeAndAlign)); -} - -_MTL_INLINE void MTL::RasterizationRateMap::copyParameterDataToBuffer(const MTL::Buffer* buffer, NS::UInteger offset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(copyParameterDataToBuffer_offset_), buffer, offset); -} - -_MTL_INLINE MTL::Size MTL::RasterizationRateMap::physicalSize(NS::UInteger layerIndex) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(physicalSizeForLayer_), layerIndex); -} - -_MTL_INLINE MTL::Coordinate2D MTL::RasterizationRateMap::mapScreenToPhysicalCoordinates(MTL::Coordinate2D screenCoordinates, NS::UInteger layerIndex) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(mapScreenToPhysicalCoordinates_forLayer_), screenCoordinates, layerIndex); -} - -_MTL_INLINE MTL::Coordinate2D MTL::RasterizationRateMap::mapPhysicalToScreenCoordinates(MTL::Coordinate2D physicalCoordinates, NS::UInteger layerIndex) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(mapPhysicalToScreenCoordinates_forLayer_), physicalCoordinates, layerIndex); -} - -#pragma once - -namespace MTL -{ -_MTL_ENUM(NS::UInteger, BlendFactor) { - BlendFactorZero = 0, - BlendFactorOne = 1, - BlendFactorSourceColor = 2, - BlendFactorOneMinusSourceColor = 3, - BlendFactorSourceAlpha = 4, - BlendFactorOneMinusSourceAlpha = 5, - BlendFactorDestinationColor = 6, - BlendFactorOneMinusDestinationColor = 7, - BlendFactorDestinationAlpha = 8, - BlendFactorOneMinusDestinationAlpha = 9, - BlendFactorSourceAlphaSaturated = 10, - BlendFactorBlendColor = 11, - BlendFactorOneMinusBlendColor = 12, - BlendFactorBlendAlpha = 13, - BlendFactorOneMinusBlendAlpha = 14, - BlendFactorSource1Color = 15, - BlendFactorOneMinusSource1Color = 16, - BlendFactorSource1Alpha = 17, - BlendFactorOneMinusSource1Alpha = 18, -}; - -_MTL_ENUM(NS::UInteger, BlendOperation) { - BlendOperationAdd = 0, - BlendOperationSubtract = 1, - BlendOperationReverseSubtract = 2, - BlendOperationMin = 3, - BlendOperationMax = 4, -}; - -_MTL_OPTIONS(NS::UInteger, ColorWriteMask) { - ColorWriteMaskNone = 0, - ColorWriteMaskAlpha = 1, - ColorWriteMaskBlue = 2, - ColorWriteMaskGreen = 4, - ColorWriteMaskRed = 8, - ColorWriteMaskAll = 15, -}; - -_MTL_ENUM(NS::UInteger, PrimitiveTopologyClass) { - PrimitiveTopologyClassUnspecified = 0, - PrimitiveTopologyClassPoint = 1, - PrimitiveTopologyClassLine = 2, - PrimitiveTopologyClassTriangle = 3, -}; - -_MTL_ENUM(NS::UInteger, TessellationPartitionMode) { - TessellationPartitionModePow2 = 0, - TessellationPartitionModeInteger = 1, - TessellationPartitionModeFractionalOdd = 2, - TessellationPartitionModeFractionalEven = 3, -}; - -_MTL_ENUM(NS::UInteger, TessellationFactorStepFunction) { - TessellationFactorStepFunctionConstant = 0, - TessellationFactorStepFunctionPerPatch = 1, - TessellationFactorStepFunctionPerInstance = 2, - TessellationFactorStepFunctionPerPatchAndPerInstance = 3, -}; - -_MTL_ENUM(NS::UInteger, TessellationFactorFormat) { - TessellationFactorFormatHalf = 0, -}; - -_MTL_ENUM(NS::UInteger, TessellationControlPointIndexType) { - TessellationControlPointIndexTypeNone = 0, - TessellationControlPointIndexTypeUInt16 = 1, - TessellationControlPointIndexTypeUInt32 = 2, -}; - -class RenderPipelineColorAttachmentDescriptor : public NS::Copying -{ -public: - static class RenderPipelineColorAttachmentDescriptor* alloc(); - - class RenderPipelineColorAttachmentDescriptor* init(); - - MTL::PixelFormat pixelFormat() const; - void setPixelFormat(MTL::PixelFormat pixelFormat); - - bool blendingEnabled() const; - void setBlendingEnabled(bool blendingEnabled); - - MTL::BlendFactor sourceRGBBlendFactor() const; - void setSourceRGBBlendFactor(MTL::BlendFactor sourceRGBBlendFactor); - - MTL::BlendFactor destinationRGBBlendFactor() const; - void setDestinationRGBBlendFactor(MTL::BlendFactor destinationRGBBlendFactor); - - MTL::BlendOperation rgbBlendOperation() const; - void setRgbBlendOperation(MTL::BlendOperation rgbBlendOperation); - - MTL::BlendFactor sourceAlphaBlendFactor() const; - void setSourceAlphaBlendFactor(MTL::BlendFactor sourceAlphaBlendFactor); - - MTL::BlendFactor destinationAlphaBlendFactor() const; - void setDestinationAlphaBlendFactor(MTL::BlendFactor destinationAlphaBlendFactor); - - MTL::BlendOperation alphaBlendOperation() const; - void setAlphaBlendOperation(MTL::BlendOperation alphaBlendOperation); - - MTL::ColorWriteMask writeMask() const; - void setWriteMask(MTL::ColorWriteMask writeMask); -}; - -class RenderPipelineReflection : public NS::Referencing -{ -public: - static class RenderPipelineReflection* alloc(); - - class RenderPipelineReflection* init(); - - NS::Array* vertexBindings() const; - - NS::Array* fragmentBindings() const; - - NS::Array* tileBindings() const; - - NS::Array* objectBindings() const; - - NS::Array* meshBindings() const; - - NS::Array* vertexArguments() const; - - NS::Array* fragmentArguments() const; - - NS::Array* tileArguments() const; -}; - -class RenderPipelineDescriptor : public NS::Copying -{ -public: - static class RenderPipelineDescriptor* alloc(); - - class RenderPipelineDescriptor* init(); - - NS::String* label() const; - void setLabel(const NS::String* label); - - class Function* vertexFunction() const; - void setVertexFunction(const class Function* vertexFunction); - - class Function* fragmentFunction() const; - void setFragmentFunction(const class Function* fragmentFunction); - - class VertexDescriptor* vertexDescriptor() const; - void setVertexDescriptor(const class VertexDescriptor* vertexDescriptor); - - NS::UInteger sampleCount() const; - void setSampleCount(NS::UInteger sampleCount); - - NS::UInteger rasterSampleCount() const; - void setRasterSampleCount(NS::UInteger rasterSampleCount); - - bool alphaToCoverageEnabled() const; - void setAlphaToCoverageEnabled(bool alphaToCoverageEnabled); - - bool alphaToOneEnabled() const; - void setAlphaToOneEnabled(bool alphaToOneEnabled); - - bool rasterizationEnabled() const; - void setRasterizationEnabled(bool rasterizationEnabled); - - NS::UInteger maxVertexAmplificationCount() const; - void setMaxVertexAmplificationCount(NS::UInteger maxVertexAmplificationCount); - - class RenderPipelineColorAttachmentDescriptorArray* colorAttachments() const; - - MTL::PixelFormat depthAttachmentPixelFormat() const; - void setDepthAttachmentPixelFormat(MTL::PixelFormat depthAttachmentPixelFormat); - - MTL::PixelFormat stencilAttachmentPixelFormat() const; - void setStencilAttachmentPixelFormat(MTL::PixelFormat stencilAttachmentPixelFormat); - - MTL::PrimitiveTopologyClass inputPrimitiveTopology() const; - void setInputPrimitiveTopology(MTL::PrimitiveTopologyClass inputPrimitiveTopology); - - MTL::TessellationPartitionMode tessellationPartitionMode() const; - void setTessellationPartitionMode(MTL::TessellationPartitionMode tessellationPartitionMode); - - NS::UInteger maxTessellationFactor() const; - void setMaxTessellationFactor(NS::UInteger maxTessellationFactor); - - bool tessellationFactorScaleEnabled() const; - void setTessellationFactorScaleEnabled(bool tessellationFactorScaleEnabled); - - MTL::TessellationFactorFormat tessellationFactorFormat() const; - void setTessellationFactorFormat(MTL::TessellationFactorFormat tessellationFactorFormat); - - MTL::TessellationControlPointIndexType tessellationControlPointIndexType() const; - void setTessellationControlPointIndexType(MTL::TessellationControlPointIndexType tessellationControlPointIndexType); - - MTL::TessellationFactorStepFunction tessellationFactorStepFunction() const; - void setTessellationFactorStepFunction(MTL::TessellationFactorStepFunction tessellationFactorStepFunction); - - MTL::Winding tessellationOutputWindingOrder() const; - void setTessellationOutputWindingOrder(MTL::Winding tessellationOutputWindingOrder); - - class PipelineBufferDescriptorArray* vertexBuffers() const; - - class PipelineBufferDescriptorArray* fragmentBuffers() const; - - bool supportIndirectCommandBuffers() const; - void setSupportIndirectCommandBuffers(bool supportIndirectCommandBuffers); - - NS::Array* binaryArchives() const; - void setBinaryArchives(const NS::Array* binaryArchives); - - NS::Array* vertexPreloadedLibraries() const; - void setVertexPreloadedLibraries(const NS::Array* vertexPreloadedLibraries); - - NS::Array* fragmentPreloadedLibraries() const; - void setFragmentPreloadedLibraries(const NS::Array* fragmentPreloadedLibraries); - - class LinkedFunctions* vertexLinkedFunctions() const; - void setVertexLinkedFunctions(const class LinkedFunctions* vertexLinkedFunctions); - - class LinkedFunctions* fragmentLinkedFunctions() const; - void setFragmentLinkedFunctions(const class LinkedFunctions* fragmentLinkedFunctions); - - bool supportAddingVertexBinaryFunctions() const; - void setSupportAddingVertexBinaryFunctions(bool supportAddingVertexBinaryFunctions); - - bool supportAddingFragmentBinaryFunctions() const; - void setSupportAddingFragmentBinaryFunctions(bool supportAddingFragmentBinaryFunctions); - - NS::UInteger maxVertexCallStackDepth() const; - void setMaxVertexCallStackDepth(NS::UInteger maxVertexCallStackDepth); - - NS::UInteger maxFragmentCallStackDepth() const; - void setMaxFragmentCallStackDepth(NS::UInteger maxFragmentCallStackDepth); - - void reset(); -}; - -class RenderPipelineFunctionsDescriptor : public NS::Copying -{ -public: - static class RenderPipelineFunctionsDescriptor* alloc(); - - class RenderPipelineFunctionsDescriptor* init(); - - NS::Array* vertexAdditionalBinaryFunctions() const; - void setVertexAdditionalBinaryFunctions(const NS::Array* vertexAdditionalBinaryFunctions); - - NS::Array* fragmentAdditionalBinaryFunctions() const; - void setFragmentAdditionalBinaryFunctions(const NS::Array* fragmentAdditionalBinaryFunctions); - - NS::Array* tileAdditionalBinaryFunctions() const; - void setTileAdditionalBinaryFunctions(const NS::Array* tileAdditionalBinaryFunctions); -}; - -class RenderPipelineState : public NS::Referencing -{ -public: - NS::String* label() const; - - class Device* device() const; - - NS::UInteger maxTotalThreadsPerThreadgroup() const; - - bool threadgroupSizeMatchesTileSize() const; - - NS::UInteger imageblockSampleLength() const; - - NS::UInteger imageblockMemoryLength(MTL::Size imageblockDimensions); - - bool supportIndirectCommandBuffers() const; - - NS::UInteger maxTotalThreadsPerObjectThreadgroup() const; - - NS::UInteger maxTotalThreadsPerMeshThreadgroup() const; - - NS::UInteger objectThreadExecutionWidth() const; - - NS::UInteger meshThreadExecutionWidth() const; - - NS::UInteger maxTotalThreadgroupsPerMeshGrid() const; - - MTL::ResourceID gpuResourceID() const; - - class FunctionHandle* functionHandle(const class Function* function, MTL::RenderStages stage); - - class VisibleFunctionTable* newVisibleFunctionTable(const class VisibleFunctionTableDescriptor* descriptor, MTL::RenderStages stage); - - class IntersectionFunctionTable* newIntersectionFunctionTable(const class IntersectionFunctionTableDescriptor* descriptor, MTL::RenderStages stage); - - class RenderPipelineState* newRenderPipelineState(const class RenderPipelineFunctionsDescriptor* additionalBinaryFunctions, NS::Error** error); -}; - -class RenderPipelineColorAttachmentDescriptorArray : public NS::Referencing -{ -public: - static class RenderPipelineColorAttachmentDescriptorArray* alloc(); - - class RenderPipelineColorAttachmentDescriptorArray* init(); - - class RenderPipelineColorAttachmentDescriptor* object(NS::UInteger attachmentIndex); - - void setObject(const class RenderPipelineColorAttachmentDescriptor* attachment, NS::UInteger attachmentIndex); -}; - -class TileRenderPipelineColorAttachmentDescriptor : public NS::Copying -{ -public: - static class TileRenderPipelineColorAttachmentDescriptor* alloc(); - - class TileRenderPipelineColorAttachmentDescriptor* init(); - - MTL::PixelFormat pixelFormat() const; - void setPixelFormat(MTL::PixelFormat pixelFormat); -}; - -class TileRenderPipelineColorAttachmentDescriptorArray : public NS::Referencing -{ -public: - static class TileRenderPipelineColorAttachmentDescriptorArray* alloc(); - - class TileRenderPipelineColorAttachmentDescriptorArray* init(); - - class TileRenderPipelineColorAttachmentDescriptor* object(NS::UInteger attachmentIndex); - - void setObject(const class TileRenderPipelineColorAttachmentDescriptor* attachment, NS::UInteger attachmentIndex); -}; - -class TileRenderPipelineDescriptor : public NS::Copying -{ -public: - static class TileRenderPipelineDescriptor* alloc(); - - class TileRenderPipelineDescriptor* init(); - - NS::String* label() const; - void setLabel(const NS::String* label); - - class Function* tileFunction() const; - void setTileFunction(const class Function* tileFunction); - - NS::UInteger rasterSampleCount() const; - void setRasterSampleCount(NS::UInteger rasterSampleCount); - - class TileRenderPipelineColorAttachmentDescriptorArray* colorAttachments() const; - - bool threadgroupSizeMatchesTileSize() const; - void setThreadgroupSizeMatchesTileSize(bool threadgroupSizeMatchesTileSize); - - class PipelineBufferDescriptorArray* tileBuffers() const; - - NS::UInteger maxTotalThreadsPerThreadgroup() const; - void setMaxTotalThreadsPerThreadgroup(NS::UInteger maxTotalThreadsPerThreadgroup); - - NS::Array* binaryArchives() const; - void setBinaryArchives(const NS::Array* binaryArchives); - - NS::Array* preloadedLibraries() const; - void setPreloadedLibraries(const NS::Array* preloadedLibraries); - - class LinkedFunctions* linkedFunctions() const; - void setLinkedFunctions(const class LinkedFunctions* linkedFunctions); - - bool supportAddingBinaryFunctions() const; - void setSupportAddingBinaryFunctions(bool supportAddingBinaryFunctions); - - NS::UInteger maxCallStackDepth() const; - void setMaxCallStackDepth(NS::UInteger maxCallStackDepth); - - void reset(); -}; - -class MeshRenderPipelineDescriptor : public NS::Copying -{ -public: - static class MeshRenderPipelineDescriptor* alloc(); - - class MeshRenderPipelineDescriptor* init(); - - NS::String* label() const; - void setLabel(const NS::String* label); - - class Function* objectFunction() const; - void setObjectFunction(const class Function* objectFunction); - - class Function* meshFunction() const; - void setMeshFunction(const class Function* meshFunction); - - class Function* fragmentFunction() const; - void setFragmentFunction(const class Function* fragmentFunction); - - NS::UInteger maxTotalThreadsPerObjectThreadgroup() const; - void setMaxTotalThreadsPerObjectThreadgroup(NS::UInteger maxTotalThreadsPerObjectThreadgroup); - - NS::UInteger maxTotalThreadsPerMeshThreadgroup() const; - void setMaxTotalThreadsPerMeshThreadgroup(NS::UInteger maxTotalThreadsPerMeshThreadgroup); - - bool objectThreadgroupSizeIsMultipleOfThreadExecutionWidth() const; - void setObjectThreadgroupSizeIsMultipleOfThreadExecutionWidth(bool objectThreadgroupSizeIsMultipleOfThreadExecutionWidth); - - bool meshThreadgroupSizeIsMultipleOfThreadExecutionWidth() const; - void setMeshThreadgroupSizeIsMultipleOfThreadExecutionWidth(bool meshThreadgroupSizeIsMultipleOfThreadExecutionWidth); - - NS::UInteger payloadMemoryLength() const; - void setPayloadMemoryLength(NS::UInteger payloadMemoryLength); - - NS::UInteger maxTotalThreadgroupsPerMeshGrid() const; - void setMaxTotalThreadgroupsPerMeshGrid(NS::UInteger maxTotalThreadgroupsPerMeshGrid); - - class PipelineBufferDescriptorArray* objectBuffers() const; - - class PipelineBufferDescriptorArray* meshBuffers() const; - - class PipelineBufferDescriptorArray* fragmentBuffers() const; - - NS::UInteger rasterSampleCount() const; - void setRasterSampleCount(NS::UInteger rasterSampleCount); - - bool alphaToCoverageEnabled() const; - void setAlphaToCoverageEnabled(bool alphaToCoverageEnabled); - - bool alphaToOneEnabled() const; - void setAlphaToOneEnabled(bool alphaToOneEnabled); - - bool rasterizationEnabled() const; - void setRasterizationEnabled(bool rasterizationEnabled); - - NS::UInteger maxVertexAmplificationCount() const; - void setMaxVertexAmplificationCount(NS::UInteger maxVertexAmplificationCount); - - class RenderPipelineColorAttachmentDescriptorArray* colorAttachments() const; - - MTL::PixelFormat depthAttachmentPixelFormat() const; - void setDepthAttachmentPixelFormat(MTL::PixelFormat depthAttachmentPixelFormat); - - MTL::PixelFormat stencilAttachmentPixelFormat() const; - void setStencilAttachmentPixelFormat(MTL::PixelFormat stencilAttachmentPixelFormat); - - void reset(); -}; - -} - -_MTL_INLINE MTL::RenderPipelineColorAttachmentDescriptor* MTL::RenderPipelineColorAttachmentDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLRenderPipelineColorAttachmentDescriptor)); -} - -_MTL_INLINE MTL::RenderPipelineColorAttachmentDescriptor* MTL::RenderPipelineColorAttachmentDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::PixelFormat MTL::RenderPipelineColorAttachmentDescriptor::pixelFormat() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(pixelFormat)); -} - -_MTL_INLINE void MTL::RenderPipelineColorAttachmentDescriptor::setPixelFormat(MTL::PixelFormat pixelFormat) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setPixelFormat_), pixelFormat); -} - -_MTL_INLINE bool MTL::RenderPipelineColorAttachmentDescriptor::blendingEnabled() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(isBlendingEnabled)); -} - -_MTL_INLINE void MTL::RenderPipelineColorAttachmentDescriptor::setBlendingEnabled(bool blendingEnabled) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setBlendingEnabled_), blendingEnabled); -} - -_MTL_INLINE MTL::BlendFactor MTL::RenderPipelineColorAttachmentDescriptor::sourceRGBBlendFactor() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(sourceRGBBlendFactor)); -} - -_MTL_INLINE void MTL::RenderPipelineColorAttachmentDescriptor::setSourceRGBBlendFactor(MTL::BlendFactor sourceRGBBlendFactor) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSourceRGBBlendFactor_), sourceRGBBlendFactor); -} - -_MTL_INLINE MTL::BlendFactor MTL::RenderPipelineColorAttachmentDescriptor::destinationRGBBlendFactor() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(destinationRGBBlendFactor)); -} - -_MTL_INLINE void MTL::RenderPipelineColorAttachmentDescriptor::setDestinationRGBBlendFactor(MTL::BlendFactor destinationRGBBlendFactor) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setDestinationRGBBlendFactor_), destinationRGBBlendFactor); -} - -_MTL_INLINE MTL::BlendOperation MTL::RenderPipelineColorAttachmentDescriptor::rgbBlendOperation() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(rgbBlendOperation)); -} - -_MTL_INLINE void MTL::RenderPipelineColorAttachmentDescriptor::setRgbBlendOperation(MTL::BlendOperation rgbBlendOperation) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setRgbBlendOperation_), rgbBlendOperation); -} - -_MTL_INLINE MTL::BlendFactor MTL::RenderPipelineColorAttachmentDescriptor::sourceAlphaBlendFactor() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(sourceAlphaBlendFactor)); -} - -_MTL_INLINE void MTL::RenderPipelineColorAttachmentDescriptor::setSourceAlphaBlendFactor(MTL::BlendFactor sourceAlphaBlendFactor) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSourceAlphaBlendFactor_), sourceAlphaBlendFactor); -} - -_MTL_INLINE MTL::BlendFactor MTL::RenderPipelineColorAttachmentDescriptor::destinationAlphaBlendFactor() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(destinationAlphaBlendFactor)); -} - -_MTL_INLINE void MTL::RenderPipelineColorAttachmentDescriptor::setDestinationAlphaBlendFactor(MTL::BlendFactor destinationAlphaBlendFactor) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setDestinationAlphaBlendFactor_), destinationAlphaBlendFactor); -} - -_MTL_INLINE MTL::BlendOperation MTL::RenderPipelineColorAttachmentDescriptor::alphaBlendOperation() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(alphaBlendOperation)); -} - -_MTL_INLINE void MTL::RenderPipelineColorAttachmentDescriptor::setAlphaBlendOperation(MTL::BlendOperation alphaBlendOperation) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setAlphaBlendOperation_), alphaBlendOperation); -} - -_MTL_INLINE MTL::ColorWriteMask MTL::RenderPipelineColorAttachmentDescriptor::writeMask() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(writeMask)); -} - -_MTL_INLINE void MTL::RenderPipelineColorAttachmentDescriptor::setWriteMask(MTL::ColorWriteMask writeMask) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setWriteMask_), writeMask); -} - -_MTL_INLINE MTL::RenderPipelineReflection* MTL::RenderPipelineReflection::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLRenderPipelineReflection)); -} - -_MTL_INLINE MTL::RenderPipelineReflection* MTL::RenderPipelineReflection::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE NS::Array* MTL::RenderPipelineReflection::vertexBindings() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(vertexBindings)); -} - -_MTL_INLINE NS::Array* MTL::RenderPipelineReflection::fragmentBindings() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(fragmentBindings)); -} - -_MTL_INLINE NS::Array* MTL::RenderPipelineReflection::tileBindings() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(tileBindings)); -} - -_MTL_INLINE NS::Array* MTL::RenderPipelineReflection::objectBindings() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(objectBindings)); -} - -_MTL_INLINE NS::Array* MTL::RenderPipelineReflection::meshBindings() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(meshBindings)); -} - -_MTL_INLINE NS::Array* MTL::RenderPipelineReflection::vertexArguments() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(vertexArguments)); -} - -_MTL_INLINE NS::Array* MTL::RenderPipelineReflection::fragmentArguments() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(fragmentArguments)); -} - -_MTL_INLINE NS::Array* MTL::RenderPipelineReflection::tileArguments() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(tileArguments)); -} - -_MTL_INLINE MTL::RenderPipelineDescriptor* MTL::RenderPipelineDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLRenderPipelineDescriptor)); -} - -_MTL_INLINE MTL::RenderPipelineDescriptor* MTL::RenderPipelineDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE NS::String* MTL::RenderPipelineDescriptor::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::setLabel(const NS::String* label) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLabel_), label); -} - -_MTL_INLINE MTL::Function* MTL::RenderPipelineDescriptor::vertexFunction() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(vertexFunction)); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::setVertexFunction(const MTL::Function* vertexFunction) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVertexFunction_), vertexFunction); -} - -_MTL_INLINE MTL::Function* MTL::RenderPipelineDescriptor::fragmentFunction() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(fragmentFunction)); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::setFragmentFunction(const MTL::Function* fragmentFunction) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFragmentFunction_), fragmentFunction); -} - -_MTL_INLINE MTL::VertexDescriptor* MTL::RenderPipelineDescriptor::vertexDescriptor() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(vertexDescriptor)); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::setVertexDescriptor(const MTL::VertexDescriptor* vertexDescriptor) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVertexDescriptor_), vertexDescriptor); -} - -_MTL_INLINE NS::UInteger MTL::RenderPipelineDescriptor::sampleCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(sampleCount)); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::setSampleCount(NS::UInteger sampleCount) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSampleCount_), sampleCount); -} - -_MTL_INLINE NS::UInteger MTL::RenderPipelineDescriptor::rasterSampleCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(rasterSampleCount)); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::setRasterSampleCount(NS::UInteger rasterSampleCount) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setRasterSampleCount_), rasterSampleCount); -} - -_MTL_INLINE bool MTL::RenderPipelineDescriptor::alphaToCoverageEnabled() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(isAlphaToCoverageEnabled)); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::setAlphaToCoverageEnabled(bool alphaToCoverageEnabled) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setAlphaToCoverageEnabled_), alphaToCoverageEnabled); -} - -_MTL_INLINE bool MTL::RenderPipelineDescriptor::alphaToOneEnabled() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(isAlphaToOneEnabled)); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::setAlphaToOneEnabled(bool alphaToOneEnabled) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setAlphaToOneEnabled_), alphaToOneEnabled); -} - -_MTL_INLINE bool MTL::RenderPipelineDescriptor::rasterizationEnabled() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(isRasterizationEnabled)); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::setRasterizationEnabled(bool rasterizationEnabled) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setRasterizationEnabled_), rasterizationEnabled); -} - -_MTL_INLINE NS::UInteger MTL::RenderPipelineDescriptor::maxVertexAmplificationCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(maxVertexAmplificationCount)); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::setMaxVertexAmplificationCount(NS::UInteger maxVertexAmplificationCount) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMaxVertexAmplificationCount_), maxVertexAmplificationCount); -} - -_MTL_INLINE MTL::RenderPipelineColorAttachmentDescriptorArray* MTL::RenderPipelineDescriptor::colorAttachments() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(colorAttachments)); -} - -_MTL_INLINE MTL::PixelFormat MTL::RenderPipelineDescriptor::depthAttachmentPixelFormat() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(depthAttachmentPixelFormat)); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::setDepthAttachmentPixelFormat(MTL::PixelFormat depthAttachmentPixelFormat) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setDepthAttachmentPixelFormat_), depthAttachmentPixelFormat); -} - -_MTL_INLINE MTL::PixelFormat MTL::RenderPipelineDescriptor::stencilAttachmentPixelFormat() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(stencilAttachmentPixelFormat)); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::setStencilAttachmentPixelFormat(MTL::PixelFormat stencilAttachmentPixelFormat) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStencilAttachmentPixelFormat_), stencilAttachmentPixelFormat); -} - -_MTL_INLINE MTL::PrimitiveTopologyClass MTL::RenderPipelineDescriptor::inputPrimitiveTopology() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(inputPrimitiveTopology)); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::setInputPrimitiveTopology(MTL::PrimitiveTopologyClass inputPrimitiveTopology) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setInputPrimitiveTopology_), inputPrimitiveTopology); -} - -_MTL_INLINE MTL::TessellationPartitionMode MTL::RenderPipelineDescriptor::tessellationPartitionMode() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(tessellationPartitionMode)); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::setTessellationPartitionMode(MTL::TessellationPartitionMode tessellationPartitionMode) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTessellationPartitionMode_), tessellationPartitionMode); -} - -_MTL_INLINE NS::UInteger MTL::RenderPipelineDescriptor::maxTessellationFactor() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(maxTessellationFactor)); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::setMaxTessellationFactor(NS::UInteger maxTessellationFactor) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMaxTessellationFactor_), maxTessellationFactor); -} - -_MTL_INLINE bool MTL::RenderPipelineDescriptor::tessellationFactorScaleEnabled() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(isTessellationFactorScaleEnabled)); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::setTessellationFactorScaleEnabled(bool tessellationFactorScaleEnabled) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTessellationFactorScaleEnabled_), tessellationFactorScaleEnabled); -} - -_MTL_INLINE MTL::TessellationFactorFormat MTL::RenderPipelineDescriptor::tessellationFactorFormat() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(tessellationFactorFormat)); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::setTessellationFactorFormat(MTL::TessellationFactorFormat tessellationFactorFormat) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTessellationFactorFormat_), tessellationFactorFormat); -} - -_MTL_INLINE MTL::TessellationControlPointIndexType MTL::RenderPipelineDescriptor::tessellationControlPointIndexType() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(tessellationControlPointIndexType)); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::setTessellationControlPointIndexType(MTL::TessellationControlPointIndexType tessellationControlPointIndexType) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTessellationControlPointIndexType_), tessellationControlPointIndexType); -} - -_MTL_INLINE MTL::TessellationFactorStepFunction MTL::RenderPipelineDescriptor::tessellationFactorStepFunction() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(tessellationFactorStepFunction)); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::setTessellationFactorStepFunction(MTL::TessellationFactorStepFunction tessellationFactorStepFunction) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTessellationFactorStepFunction_), tessellationFactorStepFunction); -} - -_MTL_INLINE MTL::Winding MTL::RenderPipelineDescriptor::tessellationOutputWindingOrder() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(tessellationOutputWindingOrder)); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::setTessellationOutputWindingOrder(MTL::Winding tessellationOutputWindingOrder) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTessellationOutputWindingOrder_), tessellationOutputWindingOrder); -} - -_MTL_INLINE MTL::PipelineBufferDescriptorArray* MTL::RenderPipelineDescriptor::vertexBuffers() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(vertexBuffers)); -} - -_MTL_INLINE MTL::PipelineBufferDescriptorArray* MTL::RenderPipelineDescriptor::fragmentBuffers() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(fragmentBuffers)); -} - -_MTL_INLINE bool MTL::RenderPipelineDescriptor::supportIndirectCommandBuffers() const -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(supportIndirectCommandBuffers)); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::setSupportIndirectCommandBuffers(bool supportIndirectCommandBuffers) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSupportIndirectCommandBuffers_), supportIndirectCommandBuffers); -} - -_MTL_INLINE NS::Array* MTL::RenderPipelineDescriptor::binaryArchives() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(binaryArchives)); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::setBinaryArchives(const NS::Array* binaryArchives) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setBinaryArchives_), binaryArchives); -} - -_MTL_INLINE NS::Array* MTL::RenderPipelineDescriptor::vertexPreloadedLibraries() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(vertexPreloadedLibraries)); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::setVertexPreloadedLibraries(const NS::Array* vertexPreloadedLibraries) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVertexPreloadedLibraries_), vertexPreloadedLibraries); -} - -_MTL_INLINE NS::Array* MTL::RenderPipelineDescriptor::fragmentPreloadedLibraries() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(fragmentPreloadedLibraries)); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::setFragmentPreloadedLibraries(const NS::Array* fragmentPreloadedLibraries) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFragmentPreloadedLibraries_), fragmentPreloadedLibraries); -} - -_MTL_INLINE MTL::LinkedFunctions* MTL::RenderPipelineDescriptor::vertexLinkedFunctions() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(vertexLinkedFunctions)); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::setVertexLinkedFunctions(const MTL::LinkedFunctions* vertexLinkedFunctions) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVertexLinkedFunctions_), vertexLinkedFunctions); -} - -_MTL_INLINE MTL::LinkedFunctions* MTL::RenderPipelineDescriptor::fragmentLinkedFunctions() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(fragmentLinkedFunctions)); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::setFragmentLinkedFunctions(const MTL::LinkedFunctions* fragmentLinkedFunctions) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFragmentLinkedFunctions_), fragmentLinkedFunctions); -} - -_MTL_INLINE bool MTL::RenderPipelineDescriptor::supportAddingVertexBinaryFunctions() const -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(supportAddingVertexBinaryFunctions)); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::setSupportAddingVertexBinaryFunctions(bool supportAddingVertexBinaryFunctions) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSupportAddingVertexBinaryFunctions_), supportAddingVertexBinaryFunctions); -} - -_MTL_INLINE bool MTL::RenderPipelineDescriptor::supportAddingFragmentBinaryFunctions() const -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(supportAddingFragmentBinaryFunctions)); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::setSupportAddingFragmentBinaryFunctions(bool supportAddingFragmentBinaryFunctions) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSupportAddingFragmentBinaryFunctions_), supportAddingFragmentBinaryFunctions); -} - -_MTL_INLINE NS::UInteger MTL::RenderPipelineDescriptor::maxVertexCallStackDepth() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(maxVertexCallStackDepth)); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::setMaxVertexCallStackDepth(NS::UInteger maxVertexCallStackDepth) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMaxVertexCallStackDepth_), maxVertexCallStackDepth); -} - -_MTL_INLINE NS::UInteger MTL::RenderPipelineDescriptor::maxFragmentCallStackDepth() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(maxFragmentCallStackDepth)); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::setMaxFragmentCallStackDepth(NS::UInteger maxFragmentCallStackDepth) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMaxFragmentCallStackDepth_), maxFragmentCallStackDepth); -} - -_MTL_INLINE void MTL::RenderPipelineDescriptor::reset() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(reset)); -} - -_MTL_INLINE MTL::RenderPipelineFunctionsDescriptor* MTL::RenderPipelineFunctionsDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLRenderPipelineFunctionsDescriptor)); -} - -_MTL_INLINE MTL::RenderPipelineFunctionsDescriptor* MTL::RenderPipelineFunctionsDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE NS::Array* MTL::RenderPipelineFunctionsDescriptor::vertexAdditionalBinaryFunctions() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(vertexAdditionalBinaryFunctions)); -} - -_MTL_INLINE void MTL::RenderPipelineFunctionsDescriptor::setVertexAdditionalBinaryFunctions(const NS::Array* vertexAdditionalBinaryFunctions) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setVertexAdditionalBinaryFunctions_), vertexAdditionalBinaryFunctions); -} - -_MTL_INLINE NS::Array* MTL::RenderPipelineFunctionsDescriptor::fragmentAdditionalBinaryFunctions() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(fragmentAdditionalBinaryFunctions)); -} - -_MTL_INLINE void MTL::RenderPipelineFunctionsDescriptor::setFragmentAdditionalBinaryFunctions(const NS::Array* fragmentAdditionalBinaryFunctions) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFragmentAdditionalBinaryFunctions_), fragmentAdditionalBinaryFunctions); -} - -_MTL_INLINE NS::Array* MTL::RenderPipelineFunctionsDescriptor::tileAdditionalBinaryFunctions() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(tileAdditionalBinaryFunctions)); -} - -_MTL_INLINE void MTL::RenderPipelineFunctionsDescriptor::setTileAdditionalBinaryFunctions(const NS::Array* tileAdditionalBinaryFunctions) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTileAdditionalBinaryFunctions_), tileAdditionalBinaryFunctions); -} - -_MTL_INLINE NS::String* MTL::RenderPipelineState::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE MTL::Device* MTL::RenderPipelineState::device() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(device)); -} - -_MTL_INLINE NS::UInteger MTL::RenderPipelineState::maxTotalThreadsPerThreadgroup() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(maxTotalThreadsPerThreadgroup)); -} - -_MTL_INLINE bool MTL::RenderPipelineState::threadgroupSizeMatchesTileSize() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(threadgroupSizeMatchesTileSize)); -} - -_MTL_INLINE NS::UInteger MTL::RenderPipelineState::imageblockSampleLength() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(imageblockSampleLength)); -} - -_MTL_INLINE NS::UInteger MTL::RenderPipelineState::imageblockMemoryLength(MTL::Size imageblockDimensions) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(imageblockMemoryLengthForDimensions_), imageblockDimensions); -} - -_MTL_INLINE bool MTL::RenderPipelineState::supportIndirectCommandBuffers() const -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(supportIndirectCommandBuffers)); -} - -_MTL_INLINE NS::UInteger MTL::RenderPipelineState::maxTotalThreadsPerObjectThreadgroup() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(maxTotalThreadsPerObjectThreadgroup)); -} - -_MTL_INLINE NS::UInteger MTL::RenderPipelineState::maxTotalThreadsPerMeshThreadgroup() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(maxTotalThreadsPerMeshThreadgroup)); -} - -_MTL_INLINE NS::UInteger MTL::RenderPipelineState::objectThreadExecutionWidth() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(objectThreadExecutionWidth)); -} - -_MTL_INLINE NS::UInteger MTL::RenderPipelineState::meshThreadExecutionWidth() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(meshThreadExecutionWidth)); -} - -_MTL_INLINE NS::UInteger MTL::RenderPipelineState::maxTotalThreadgroupsPerMeshGrid() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(maxTotalThreadgroupsPerMeshGrid)); -} - -_MTL_INLINE MTL::ResourceID MTL::RenderPipelineState::gpuResourceID() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(gpuResourceID)); -} - -_MTL_INLINE MTL::FunctionHandle* MTL::RenderPipelineState::functionHandle(const MTL::Function* function, MTL::RenderStages stage) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(functionHandleWithFunction_stage_), function, stage); -} - -_MTL_INLINE MTL::VisibleFunctionTable* MTL::RenderPipelineState::newVisibleFunctionTable(const MTL::VisibleFunctionTableDescriptor* descriptor, MTL::RenderStages stage) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newVisibleFunctionTableWithDescriptor_stage_), descriptor, stage); -} - -_MTL_INLINE MTL::IntersectionFunctionTable* MTL::RenderPipelineState::newIntersectionFunctionTable(const MTL::IntersectionFunctionTableDescriptor* descriptor, MTL::RenderStages stage) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newIntersectionFunctionTableWithDescriptor_stage_), descriptor, stage); -} - -_MTL_INLINE MTL::RenderPipelineState* MTL::RenderPipelineState::newRenderPipelineState(const MTL::RenderPipelineFunctionsDescriptor* additionalBinaryFunctions, NS::Error** error) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(newRenderPipelineStateWithAdditionalBinaryFunctions_error_), additionalBinaryFunctions, error); -} - -_MTL_INLINE MTL::RenderPipelineColorAttachmentDescriptorArray* MTL::RenderPipelineColorAttachmentDescriptorArray::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLRenderPipelineColorAttachmentDescriptorArray)); -} - -_MTL_INLINE MTL::RenderPipelineColorAttachmentDescriptorArray* MTL::RenderPipelineColorAttachmentDescriptorArray::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::RenderPipelineColorAttachmentDescriptor* MTL::RenderPipelineColorAttachmentDescriptorArray::object(NS::UInteger attachmentIndex) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(objectAtIndexedSubscript_), attachmentIndex); -} - -_MTL_INLINE void MTL::RenderPipelineColorAttachmentDescriptorArray::setObject(const MTL::RenderPipelineColorAttachmentDescriptor* attachment, NS::UInteger attachmentIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setObject_atIndexedSubscript_), attachment, attachmentIndex); -} - -_MTL_INLINE MTL::TileRenderPipelineColorAttachmentDescriptor* MTL::TileRenderPipelineColorAttachmentDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLTileRenderPipelineColorAttachmentDescriptor)); -} - -_MTL_INLINE MTL::TileRenderPipelineColorAttachmentDescriptor* MTL::TileRenderPipelineColorAttachmentDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::PixelFormat MTL::TileRenderPipelineColorAttachmentDescriptor::pixelFormat() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(pixelFormat)); -} - -_MTL_INLINE void MTL::TileRenderPipelineColorAttachmentDescriptor::setPixelFormat(MTL::PixelFormat pixelFormat) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setPixelFormat_), pixelFormat); -} - -_MTL_INLINE MTL::TileRenderPipelineColorAttachmentDescriptorArray* MTL::TileRenderPipelineColorAttachmentDescriptorArray::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLTileRenderPipelineColorAttachmentDescriptorArray)); -} - -_MTL_INLINE MTL::TileRenderPipelineColorAttachmentDescriptorArray* MTL::TileRenderPipelineColorAttachmentDescriptorArray::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::TileRenderPipelineColorAttachmentDescriptor* MTL::TileRenderPipelineColorAttachmentDescriptorArray::object(NS::UInteger attachmentIndex) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(objectAtIndexedSubscript_), attachmentIndex); -} - -_MTL_INLINE void MTL::TileRenderPipelineColorAttachmentDescriptorArray::setObject(const MTL::TileRenderPipelineColorAttachmentDescriptor* attachment, NS::UInteger attachmentIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setObject_atIndexedSubscript_), attachment, attachmentIndex); -} - -_MTL_INLINE MTL::TileRenderPipelineDescriptor* MTL::TileRenderPipelineDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLTileRenderPipelineDescriptor)); -} - -_MTL_INLINE MTL::TileRenderPipelineDescriptor* MTL::TileRenderPipelineDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE NS::String* MTL::TileRenderPipelineDescriptor::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE void MTL::TileRenderPipelineDescriptor::setLabel(const NS::String* label) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLabel_), label); -} - -_MTL_INLINE MTL::Function* MTL::TileRenderPipelineDescriptor::tileFunction() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(tileFunction)); -} - -_MTL_INLINE void MTL::TileRenderPipelineDescriptor::setTileFunction(const MTL::Function* tileFunction) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTileFunction_), tileFunction); -} - -_MTL_INLINE NS::UInteger MTL::TileRenderPipelineDescriptor::rasterSampleCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(rasterSampleCount)); -} - -_MTL_INLINE void MTL::TileRenderPipelineDescriptor::setRasterSampleCount(NS::UInteger rasterSampleCount) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setRasterSampleCount_), rasterSampleCount); -} - -_MTL_INLINE MTL::TileRenderPipelineColorAttachmentDescriptorArray* MTL::TileRenderPipelineDescriptor::colorAttachments() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(colorAttachments)); -} - -_MTL_INLINE bool MTL::TileRenderPipelineDescriptor::threadgroupSizeMatchesTileSize() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(threadgroupSizeMatchesTileSize)); -} - -_MTL_INLINE void MTL::TileRenderPipelineDescriptor::setThreadgroupSizeMatchesTileSize(bool threadgroupSizeMatchesTileSize) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setThreadgroupSizeMatchesTileSize_), threadgroupSizeMatchesTileSize); -} - -_MTL_INLINE MTL::PipelineBufferDescriptorArray* MTL::TileRenderPipelineDescriptor::tileBuffers() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(tileBuffers)); -} - -_MTL_INLINE NS::UInteger MTL::TileRenderPipelineDescriptor::maxTotalThreadsPerThreadgroup() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(maxTotalThreadsPerThreadgroup)); -} - -_MTL_INLINE void MTL::TileRenderPipelineDescriptor::setMaxTotalThreadsPerThreadgroup(NS::UInteger maxTotalThreadsPerThreadgroup) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMaxTotalThreadsPerThreadgroup_), maxTotalThreadsPerThreadgroup); -} - -_MTL_INLINE NS::Array* MTL::TileRenderPipelineDescriptor::binaryArchives() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(binaryArchives)); -} - -_MTL_INLINE void MTL::TileRenderPipelineDescriptor::setBinaryArchives(const NS::Array* binaryArchives) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setBinaryArchives_), binaryArchives); -} - -_MTL_INLINE NS::Array* MTL::TileRenderPipelineDescriptor::preloadedLibraries() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(preloadedLibraries)); -} - -_MTL_INLINE void MTL::TileRenderPipelineDescriptor::setPreloadedLibraries(const NS::Array* preloadedLibraries) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setPreloadedLibraries_), preloadedLibraries); -} - -_MTL_INLINE MTL::LinkedFunctions* MTL::TileRenderPipelineDescriptor::linkedFunctions() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(linkedFunctions)); -} - -_MTL_INLINE void MTL::TileRenderPipelineDescriptor::setLinkedFunctions(const MTL::LinkedFunctions* linkedFunctions) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLinkedFunctions_), linkedFunctions); -} - -_MTL_INLINE bool MTL::TileRenderPipelineDescriptor::supportAddingBinaryFunctions() const -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(supportAddingBinaryFunctions)); -} - -_MTL_INLINE void MTL::TileRenderPipelineDescriptor::setSupportAddingBinaryFunctions(bool supportAddingBinaryFunctions) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSupportAddingBinaryFunctions_), supportAddingBinaryFunctions); -} - -_MTL_INLINE NS::UInteger MTL::TileRenderPipelineDescriptor::maxCallStackDepth() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(maxCallStackDepth)); -} - -_MTL_INLINE void MTL::TileRenderPipelineDescriptor::setMaxCallStackDepth(NS::UInteger maxCallStackDepth) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMaxCallStackDepth_), maxCallStackDepth); -} - -_MTL_INLINE void MTL::TileRenderPipelineDescriptor::reset() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(reset)); -} - -_MTL_INLINE MTL::MeshRenderPipelineDescriptor* MTL::MeshRenderPipelineDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLMeshRenderPipelineDescriptor)); -} - -_MTL_INLINE MTL::MeshRenderPipelineDescriptor* MTL::MeshRenderPipelineDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE NS::String* MTL::MeshRenderPipelineDescriptor::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE void MTL::MeshRenderPipelineDescriptor::setLabel(const NS::String* label) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLabel_), label); -} - -_MTL_INLINE MTL::Function* MTL::MeshRenderPipelineDescriptor::objectFunction() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(objectFunction)); -} - -_MTL_INLINE void MTL::MeshRenderPipelineDescriptor::setObjectFunction(const MTL::Function* objectFunction) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setObjectFunction_), objectFunction); -} - -_MTL_INLINE MTL::Function* MTL::MeshRenderPipelineDescriptor::meshFunction() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(meshFunction)); -} - -_MTL_INLINE void MTL::MeshRenderPipelineDescriptor::setMeshFunction(const MTL::Function* meshFunction) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMeshFunction_), meshFunction); -} - -_MTL_INLINE MTL::Function* MTL::MeshRenderPipelineDescriptor::fragmentFunction() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(fragmentFunction)); -} - -_MTL_INLINE void MTL::MeshRenderPipelineDescriptor::setFragmentFunction(const MTL::Function* fragmentFunction) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFragmentFunction_), fragmentFunction); -} - -_MTL_INLINE NS::UInteger MTL::MeshRenderPipelineDescriptor::maxTotalThreadsPerObjectThreadgroup() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(maxTotalThreadsPerObjectThreadgroup)); -} - -_MTL_INLINE void MTL::MeshRenderPipelineDescriptor::setMaxTotalThreadsPerObjectThreadgroup(NS::UInteger maxTotalThreadsPerObjectThreadgroup) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMaxTotalThreadsPerObjectThreadgroup_), maxTotalThreadsPerObjectThreadgroup); -} - -_MTL_INLINE NS::UInteger MTL::MeshRenderPipelineDescriptor::maxTotalThreadsPerMeshThreadgroup() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(maxTotalThreadsPerMeshThreadgroup)); -} - -_MTL_INLINE void MTL::MeshRenderPipelineDescriptor::setMaxTotalThreadsPerMeshThreadgroup(NS::UInteger maxTotalThreadsPerMeshThreadgroup) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMaxTotalThreadsPerMeshThreadgroup_), maxTotalThreadsPerMeshThreadgroup); -} - -_MTL_INLINE bool MTL::MeshRenderPipelineDescriptor::objectThreadgroupSizeIsMultipleOfThreadExecutionWidth() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(objectThreadgroupSizeIsMultipleOfThreadExecutionWidth)); -} - -_MTL_INLINE void MTL::MeshRenderPipelineDescriptor::setObjectThreadgroupSizeIsMultipleOfThreadExecutionWidth(bool objectThreadgroupSizeIsMultipleOfThreadExecutionWidth) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setObjectThreadgroupSizeIsMultipleOfThreadExecutionWidth_), objectThreadgroupSizeIsMultipleOfThreadExecutionWidth); -} - -_MTL_INLINE bool MTL::MeshRenderPipelineDescriptor::meshThreadgroupSizeIsMultipleOfThreadExecutionWidth() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(meshThreadgroupSizeIsMultipleOfThreadExecutionWidth)); -} - -_MTL_INLINE void MTL::MeshRenderPipelineDescriptor::setMeshThreadgroupSizeIsMultipleOfThreadExecutionWidth(bool meshThreadgroupSizeIsMultipleOfThreadExecutionWidth) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMeshThreadgroupSizeIsMultipleOfThreadExecutionWidth_), meshThreadgroupSizeIsMultipleOfThreadExecutionWidth); -} - -_MTL_INLINE NS::UInteger MTL::MeshRenderPipelineDescriptor::payloadMemoryLength() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(payloadMemoryLength)); -} - -_MTL_INLINE void MTL::MeshRenderPipelineDescriptor::setPayloadMemoryLength(NS::UInteger payloadMemoryLength) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setPayloadMemoryLength_), payloadMemoryLength); -} - -_MTL_INLINE NS::UInteger MTL::MeshRenderPipelineDescriptor::maxTotalThreadgroupsPerMeshGrid() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(maxTotalThreadgroupsPerMeshGrid)); -} - -_MTL_INLINE void MTL::MeshRenderPipelineDescriptor::setMaxTotalThreadgroupsPerMeshGrid(NS::UInteger maxTotalThreadgroupsPerMeshGrid) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMaxTotalThreadgroupsPerMeshGrid_), maxTotalThreadgroupsPerMeshGrid); -} - -_MTL_INLINE MTL::PipelineBufferDescriptorArray* MTL::MeshRenderPipelineDescriptor::objectBuffers() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(objectBuffers)); -} - -_MTL_INLINE MTL::PipelineBufferDescriptorArray* MTL::MeshRenderPipelineDescriptor::meshBuffers() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(meshBuffers)); -} - -_MTL_INLINE MTL::PipelineBufferDescriptorArray* MTL::MeshRenderPipelineDescriptor::fragmentBuffers() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(fragmentBuffers)); -} - -_MTL_INLINE NS::UInteger MTL::MeshRenderPipelineDescriptor::rasterSampleCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(rasterSampleCount)); -} - -_MTL_INLINE void MTL::MeshRenderPipelineDescriptor::setRasterSampleCount(NS::UInteger rasterSampleCount) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setRasterSampleCount_), rasterSampleCount); -} - -_MTL_INLINE bool MTL::MeshRenderPipelineDescriptor::alphaToCoverageEnabled() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(isAlphaToCoverageEnabled)); -} - -_MTL_INLINE void MTL::MeshRenderPipelineDescriptor::setAlphaToCoverageEnabled(bool alphaToCoverageEnabled) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setAlphaToCoverageEnabled_), alphaToCoverageEnabled); -} - -_MTL_INLINE bool MTL::MeshRenderPipelineDescriptor::alphaToOneEnabled() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(isAlphaToOneEnabled)); -} - -_MTL_INLINE void MTL::MeshRenderPipelineDescriptor::setAlphaToOneEnabled(bool alphaToOneEnabled) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setAlphaToOneEnabled_), alphaToOneEnabled); -} - -_MTL_INLINE bool MTL::MeshRenderPipelineDescriptor::rasterizationEnabled() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(isRasterizationEnabled)); -} - -_MTL_INLINE void MTL::MeshRenderPipelineDescriptor::setRasterizationEnabled(bool rasterizationEnabled) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setRasterizationEnabled_), rasterizationEnabled); -} - -_MTL_INLINE NS::UInteger MTL::MeshRenderPipelineDescriptor::maxVertexAmplificationCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(maxVertexAmplificationCount)); -} - -_MTL_INLINE void MTL::MeshRenderPipelineDescriptor::setMaxVertexAmplificationCount(NS::UInteger maxVertexAmplificationCount) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMaxVertexAmplificationCount_), maxVertexAmplificationCount); -} - -_MTL_INLINE MTL::RenderPipelineColorAttachmentDescriptorArray* MTL::MeshRenderPipelineDescriptor::colorAttachments() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(colorAttachments)); -} - -_MTL_INLINE MTL::PixelFormat MTL::MeshRenderPipelineDescriptor::depthAttachmentPixelFormat() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(depthAttachmentPixelFormat)); -} - -_MTL_INLINE void MTL::MeshRenderPipelineDescriptor::setDepthAttachmentPixelFormat(MTL::PixelFormat depthAttachmentPixelFormat) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setDepthAttachmentPixelFormat_), depthAttachmentPixelFormat); -} - -_MTL_INLINE MTL::PixelFormat MTL::MeshRenderPipelineDescriptor::stencilAttachmentPixelFormat() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(stencilAttachmentPixelFormat)); -} - -_MTL_INLINE void MTL::MeshRenderPipelineDescriptor::setStencilAttachmentPixelFormat(MTL::PixelFormat stencilAttachmentPixelFormat) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStencilAttachmentPixelFormat_), stencilAttachmentPixelFormat); -} - -_MTL_INLINE void MTL::MeshRenderPipelineDescriptor::reset() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(reset)); -} - -#pragma once - -namespace MTL -{ -_MTL_ENUM(NS::UInteger, SparseTextureMappingMode) { - SparseTextureMappingModeMap = 0, - SparseTextureMappingModeUnmap = 1, -}; - -struct MapIndirectArguments -{ - uint32_t regionOriginX; - uint32_t regionOriginY; - uint32_t regionOriginZ; - uint32_t regionSizeWidth; - uint32_t regionSizeHeight; - uint32_t regionSizeDepth; - uint32_t mipMapLevel; - uint32_t sliceId; -} _MTL_PACKED; - -class ResourceStateCommandEncoder : public NS::Referencing -{ -public: - void updateTextureMappings(const class Texture* texture, const MTL::SparseTextureMappingMode mode, const MTL::Region* regions, const NS::UInteger* mipLevels, const NS::UInteger* slices, NS::UInteger numRegions); - - void updateTextureMapping(const class Texture* texture, const MTL::SparseTextureMappingMode mode, const MTL::Region region, const NS::UInteger mipLevel, const NS::UInteger slice); - - void updateTextureMapping(const class Texture* texture, const MTL::SparseTextureMappingMode mode, const class Buffer* indirectBuffer, NS::UInteger indirectBufferOffset); - - void updateFence(const class Fence* fence); - - void waitForFence(const class Fence* fence); - - void moveTextureMappingsFromTexture(const class Texture* sourceTexture, NS::UInteger sourceSlice, NS::UInteger sourceLevel, MTL::Origin sourceOrigin, MTL::Size sourceSize, const class Texture* destinationTexture, NS::UInteger destinationSlice, NS::UInteger destinationLevel, MTL::Origin destinationOrigin); -}; - -} - -_MTL_INLINE void MTL::ResourceStateCommandEncoder::updateTextureMappings(const MTL::Texture* texture, const MTL::SparseTextureMappingMode mode, const MTL::Region* regions, const NS::UInteger* mipLevels, const NS::UInteger* slices, NS::UInteger numRegions) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(updateTextureMappings_mode_regions_mipLevels_slices_numRegions_), texture, mode, regions, mipLevels, slices, numRegions); -} - -_MTL_INLINE void MTL::ResourceStateCommandEncoder::updateTextureMapping(const MTL::Texture* texture, const MTL::SparseTextureMappingMode mode, const MTL::Region region, const NS::UInteger mipLevel, const NS::UInteger slice) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(updateTextureMapping_mode_region_mipLevel_slice_), texture, mode, region, mipLevel, slice); -} - -_MTL_INLINE void MTL::ResourceStateCommandEncoder::updateTextureMapping(const MTL::Texture* texture, const MTL::SparseTextureMappingMode mode, const MTL::Buffer* indirectBuffer, NS::UInteger indirectBufferOffset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(updateTextureMapping_mode_indirectBuffer_indirectBufferOffset_), texture, mode, indirectBuffer, indirectBufferOffset); -} - -_MTL_INLINE void MTL::ResourceStateCommandEncoder::updateFence(const MTL::Fence* fence) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(updateFence_), fence); -} - -_MTL_INLINE void MTL::ResourceStateCommandEncoder::waitForFence(const MTL::Fence* fence) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(waitForFence_), fence); -} - -_MTL_INLINE void MTL::ResourceStateCommandEncoder::moveTextureMappingsFromTexture(const MTL::Texture* sourceTexture, NS::UInteger sourceSlice, NS::UInteger sourceLevel, MTL::Origin sourceOrigin, MTL::Size sourceSize, const MTL::Texture* destinationTexture, NS::UInteger destinationSlice, NS::UInteger destinationLevel, MTL::Origin destinationOrigin) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(moveTextureMappingsFromTexture_sourceSlice_sourceLevel_sourceOrigin_sourceSize_toTexture_destinationSlice_destinationLevel_destinationOrigin_), sourceTexture, sourceSlice, sourceLevel, sourceOrigin, sourceSize, destinationTexture, destinationSlice, destinationLevel, destinationOrigin); -} - -#pragma once - -namespace MTL -{ -class ResourceStatePassSampleBufferAttachmentDescriptor : public NS::Copying -{ -public: - static class ResourceStatePassSampleBufferAttachmentDescriptor* alloc(); - - class ResourceStatePassSampleBufferAttachmentDescriptor* init(); - - class CounterSampleBuffer* sampleBuffer() const; - void setSampleBuffer(const class CounterSampleBuffer* sampleBuffer); - - NS::UInteger startOfEncoderSampleIndex() const; - void setStartOfEncoderSampleIndex(NS::UInteger startOfEncoderSampleIndex); - - NS::UInteger endOfEncoderSampleIndex() const; - void setEndOfEncoderSampleIndex(NS::UInteger endOfEncoderSampleIndex); -}; - -class ResourceStatePassSampleBufferAttachmentDescriptorArray : public NS::Referencing -{ -public: - static class ResourceStatePassSampleBufferAttachmentDescriptorArray* alloc(); - - class ResourceStatePassSampleBufferAttachmentDescriptorArray* init(); - - class ResourceStatePassSampleBufferAttachmentDescriptor* object(NS::UInteger attachmentIndex); - - void setObject(const class ResourceStatePassSampleBufferAttachmentDescriptor* attachment, NS::UInteger attachmentIndex); -}; - -class ResourceStatePassDescriptor : public NS::Copying -{ -public: - static class ResourceStatePassDescriptor* alloc(); - - class ResourceStatePassDescriptor* init(); - - static class ResourceStatePassDescriptor* resourceStatePassDescriptor(); - - class ResourceStatePassSampleBufferAttachmentDescriptorArray* sampleBufferAttachments() const; -}; - -} - -_MTL_INLINE MTL::ResourceStatePassSampleBufferAttachmentDescriptor* MTL::ResourceStatePassSampleBufferAttachmentDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLResourceStatePassSampleBufferAttachmentDescriptor)); -} - -_MTL_INLINE MTL::ResourceStatePassSampleBufferAttachmentDescriptor* MTL::ResourceStatePassSampleBufferAttachmentDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::CounterSampleBuffer* MTL::ResourceStatePassSampleBufferAttachmentDescriptor::sampleBuffer() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(sampleBuffer)); -} - -_MTL_INLINE void MTL::ResourceStatePassSampleBufferAttachmentDescriptor::setSampleBuffer(const MTL::CounterSampleBuffer* sampleBuffer) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSampleBuffer_), sampleBuffer); -} - -_MTL_INLINE NS::UInteger MTL::ResourceStatePassSampleBufferAttachmentDescriptor::startOfEncoderSampleIndex() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(startOfEncoderSampleIndex)); -} - -_MTL_INLINE void MTL::ResourceStatePassSampleBufferAttachmentDescriptor::setStartOfEncoderSampleIndex(NS::UInteger startOfEncoderSampleIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStartOfEncoderSampleIndex_), startOfEncoderSampleIndex); -} - -_MTL_INLINE NS::UInteger MTL::ResourceStatePassSampleBufferAttachmentDescriptor::endOfEncoderSampleIndex() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(endOfEncoderSampleIndex)); -} - -_MTL_INLINE void MTL::ResourceStatePassSampleBufferAttachmentDescriptor::setEndOfEncoderSampleIndex(NS::UInteger endOfEncoderSampleIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setEndOfEncoderSampleIndex_), endOfEncoderSampleIndex); -} - -_MTL_INLINE MTL::ResourceStatePassSampleBufferAttachmentDescriptorArray* MTL::ResourceStatePassSampleBufferAttachmentDescriptorArray::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLResourceStatePassSampleBufferAttachmentDescriptorArray)); -} - -_MTL_INLINE MTL::ResourceStatePassSampleBufferAttachmentDescriptorArray* MTL::ResourceStatePassSampleBufferAttachmentDescriptorArray::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::ResourceStatePassSampleBufferAttachmentDescriptor* MTL::ResourceStatePassSampleBufferAttachmentDescriptorArray::object(NS::UInteger attachmentIndex) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(objectAtIndexedSubscript_), attachmentIndex); -} - -_MTL_INLINE void MTL::ResourceStatePassSampleBufferAttachmentDescriptorArray::setObject(const MTL::ResourceStatePassSampleBufferAttachmentDescriptor* attachment, NS::UInteger attachmentIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setObject_atIndexedSubscript_), attachment, attachmentIndex); -} - -_MTL_INLINE MTL::ResourceStatePassDescriptor* MTL::ResourceStatePassDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLResourceStatePassDescriptor)); -} - -_MTL_INLINE MTL::ResourceStatePassDescriptor* MTL::ResourceStatePassDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::ResourceStatePassDescriptor* MTL::ResourceStatePassDescriptor::resourceStatePassDescriptor() -{ - return Object::sendMessage(_MTL_PRIVATE_CLS(MTLResourceStatePassDescriptor), _MTL_PRIVATE_SEL(resourceStatePassDescriptor)); -} - -_MTL_INLINE MTL::ResourceStatePassSampleBufferAttachmentDescriptorArray* MTL::ResourceStatePassDescriptor::sampleBufferAttachments() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(sampleBufferAttachments)); -} - -#pragma once - -namespace MTL -{ -_MTL_ENUM(NS::UInteger, SamplerMinMagFilter) { - SamplerMinMagFilterNearest = 0, - SamplerMinMagFilterLinear = 1, -}; - -_MTL_ENUM(NS::UInteger, SamplerMipFilter) { - SamplerMipFilterNotMipmapped = 0, - SamplerMipFilterNearest = 1, - SamplerMipFilterLinear = 2, -}; - -_MTL_ENUM(NS::UInteger, SamplerAddressMode) { - SamplerAddressModeClampToEdge = 0, - SamplerAddressModeMirrorClampToEdge = 1, - SamplerAddressModeRepeat = 2, - SamplerAddressModeMirrorRepeat = 3, - SamplerAddressModeClampToZero = 4, - SamplerAddressModeClampToBorderColor = 5, -}; - -_MTL_ENUM(NS::UInteger, SamplerBorderColor) { - SamplerBorderColorTransparentBlack = 0, - SamplerBorderColorOpaqueBlack = 1, - SamplerBorderColorOpaqueWhite = 2, -}; - -class SamplerDescriptor : public NS::Copying -{ -public: - static class SamplerDescriptor* alloc(); - - class SamplerDescriptor* init(); - - MTL::SamplerMinMagFilter minFilter() const; - void setMinFilter(MTL::SamplerMinMagFilter minFilter); - - MTL::SamplerMinMagFilter magFilter() const; - void setMagFilter(MTL::SamplerMinMagFilter magFilter); - - MTL::SamplerMipFilter mipFilter() const; - void setMipFilter(MTL::SamplerMipFilter mipFilter); - - NS::UInteger maxAnisotropy() const; - void setMaxAnisotropy(NS::UInteger maxAnisotropy); - - MTL::SamplerAddressMode sAddressMode() const; - void setSAddressMode(MTL::SamplerAddressMode sAddressMode); - - MTL::SamplerAddressMode tAddressMode() const; - void setTAddressMode(MTL::SamplerAddressMode tAddressMode); - - MTL::SamplerAddressMode rAddressMode() const; - void setRAddressMode(MTL::SamplerAddressMode rAddressMode); - - MTL::SamplerBorderColor borderColor() const; - void setBorderColor(MTL::SamplerBorderColor borderColor); - - bool normalizedCoordinates() const; - void setNormalizedCoordinates(bool normalizedCoordinates); - - float lodMinClamp() const; - void setLodMinClamp(float lodMinClamp); - - float lodMaxClamp() const; - void setLodMaxClamp(float lodMaxClamp); - - bool lodAverage() const; - void setLodAverage(bool lodAverage); - - MTL::CompareFunction compareFunction() const; - void setCompareFunction(MTL::CompareFunction compareFunction); - - bool supportArgumentBuffers() const; - void setSupportArgumentBuffers(bool supportArgumentBuffers); - - NS::String* label() const; - void setLabel(const NS::String* label); -}; - -class SamplerState : public NS::Referencing -{ -public: - NS::String* label() const; - - class Device* device() const; - - MTL::ResourceID gpuResourceID() const; -}; - -} - -_MTL_INLINE MTL::SamplerDescriptor* MTL::SamplerDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLSamplerDescriptor)); -} - -_MTL_INLINE MTL::SamplerDescriptor* MTL::SamplerDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::SamplerMinMagFilter MTL::SamplerDescriptor::minFilter() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(minFilter)); -} - -_MTL_INLINE void MTL::SamplerDescriptor::setMinFilter(MTL::SamplerMinMagFilter minFilter) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMinFilter_), minFilter); -} - -_MTL_INLINE MTL::SamplerMinMagFilter MTL::SamplerDescriptor::magFilter() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(magFilter)); -} - -_MTL_INLINE void MTL::SamplerDescriptor::setMagFilter(MTL::SamplerMinMagFilter magFilter) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMagFilter_), magFilter); -} - -_MTL_INLINE MTL::SamplerMipFilter MTL::SamplerDescriptor::mipFilter() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(mipFilter)); -} - -_MTL_INLINE void MTL::SamplerDescriptor::setMipFilter(MTL::SamplerMipFilter mipFilter) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMipFilter_), mipFilter); -} - -_MTL_INLINE NS::UInteger MTL::SamplerDescriptor::maxAnisotropy() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(maxAnisotropy)); -} - -_MTL_INLINE void MTL::SamplerDescriptor::setMaxAnisotropy(NS::UInteger maxAnisotropy) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setMaxAnisotropy_), maxAnisotropy); -} - -_MTL_INLINE MTL::SamplerAddressMode MTL::SamplerDescriptor::sAddressMode() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(sAddressMode)); -} - -_MTL_INLINE void MTL::SamplerDescriptor::setSAddressMode(MTL::SamplerAddressMode sAddressMode) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSAddressMode_), sAddressMode); -} - -_MTL_INLINE MTL::SamplerAddressMode MTL::SamplerDescriptor::tAddressMode() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(tAddressMode)); -} - -_MTL_INLINE void MTL::SamplerDescriptor::setTAddressMode(MTL::SamplerAddressMode tAddressMode) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setTAddressMode_), tAddressMode); -} - -_MTL_INLINE MTL::SamplerAddressMode MTL::SamplerDescriptor::rAddressMode() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(rAddressMode)); -} - -_MTL_INLINE void MTL::SamplerDescriptor::setRAddressMode(MTL::SamplerAddressMode rAddressMode) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setRAddressMode_), rAddressMode); -} - -_MTL_INLINE MTL::SamplerBorderColor MTL::SamplerDescriptor::borderColor() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(borderColor)); -} - -_MTL_INLINE void MTL::SamplerDescriptor::setBorderColor(MTL::SamplerBorderColor borderColor) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setBorderColor_), borderColor); -} - -_MTL_INLINE bool MTL::SamplerDescriptor::normalizedCoordinates() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(normalizedCoordinates)); -} - -_MTL_INLINE void MTL::SamplerDescriptor::setNormalizedCoordinates(bool normalizedCoordinates) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setNormalizedCoordinates_), normalizedCoordinates); -} - -_MTL_INLINE float MTL::SamplerDescriptor::lodMinClamp() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(lodMinClamp)); -} - -_MTL_INLINE void MTL::SamplerDescriptor::setLodMinClamp(float lodMinClamp) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLodMinClamp_), lodMinClamp); -} - -_MTL_INLINE float MTL::SamplerDescriptor::lodMaxClamp() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(lodMaxClamp)); -} - -_MTL_INLINE void MTL::SamplerDescriptor::setLodMaxClamp(float lodMaxClamp) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLodMaxClamp_), lodMaxClamp); -} - -_MTL_INLINE bool MTL::SamplerDescriptor::lodAverage() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(lodAverage)); -} - -_MTL_INLINE void MTL::SamplerDescriptor::setLodAverage(bool lodAverage) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLodAverage_), lodAverage); -} - -_MTL_INLINE MTL::CompareFunction MTL::SamplerDescriptor::compareFunction() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(compareFunction)); -} - -_MTL_INLINE void MTL::SamplerDescriptor::setCompareFunction(MTL::CompareFunction compareFunction) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setCompareFunction_), compareFunction); -} - -_MTL_INLINE bool MTL::SamplerDescriptor::supportArgumentBuffers() const -{ - return Object::sendMessageSafe(this, _MTL_PRIVATE_SEL(supportArgumentBuffers)); -} - -_MTL_INLINE void MTL::SamplerDescriptor::setSupportArgumentBuffers(bool supportArgumentBuffers) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setSupportArgumentBuffers_), supportArgumentBuffers); -} - -_MTL_INLINE NS::String* MTL::SamplerDescriptor::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE void MTL::SamplerDescriptor::setLabel(const NS::String* label) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setLabel_), label); -} - -_MTL_INLINE NS::String* MTL::SamplerState::label() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(label)); -} - -_MTL_INLINE MTL::Device* MTL::SamplerState::device() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(device)); -} - -_MTL_INLINE MTL::ResourceID MTL::SamplerState::gpuResourceID() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(gpuResourceID)); -} - -#pragma once - -namespace MTL -{ -_MTL_ENUM(NS::UInteger, VertexFormat) { - VertexFormatInvalid = 0, - VertexFormatUChar2 = 1, - VertexFormatUChar3 = 2, - VertexFormatUChar4 = 3, - VertexFormatChar2 = 4, - VertexFormatChar3 = 5, - VertexFormatChar4 = 6, - VertexFormatUChar2Normalized = 7, - VertexFormatUChar3Normalized = 8, - VertexFormatUChar4Normalized = 9, - VertexFormatChar2Normalized = 10, - VertexFormatChar3Normalized = 11, - VertexFormatChar4Normalized = 12, - VertexFormatUShort2 = 13, - VertexFormatUShort3 = 14, - VertexFormatUShort4 = 15, - VertexFormatShort2 = 16, - VertexFormatShort3 = 17, - VertexFormatShort4 = 18, - VertexFormatUShort2Normalized = 19, - VertexFormatUShort3Normalized = 20, - VertexFormatUShort4Normalized = 21, - VertexFormatShort2Normalized = 22, - VertexFormatShort3Normalized = 23, - VertexFormatShort4Normalized = 24, - VertexFormatHalf2 = 25, - VertexFormatHalf3 = 26, - VertexFormatHalf4 = 27, - VertexFormatFloat = 28, - VertexFormatFloat2 = 29, - VertexFormatFloat3 = 30, - VertexFormatFloat4 = 31, - VertexFormatInt = 32, - VertexFormatInt2 = 33, - VertexFormatInt3 = 34, - VertexFormatInt4 = 35, - VertexFormatUInt = 36, - VertexFormatUInt2 = 37, - VertexFormatUInt3 = 38, - VertexFormatUInt4 = 39, - VertexFormatInt1010102Normalized = 40, - VertexFormatUInt1010102Normalized = 41, - VertexFormatUChar4Normalized_BGRA = 42, - VertexFormatUChar = 45, - VertexFormatChar = 46, - VertexFormatUCharNormalized = 47, - VertexFormatCharNormalized = 48, - VertexFormatUShort = 49, - VertexFormatShort = 50, - VertexFormatUShortNormalized = 51, - VertexFormatShortNormalized = 52, - VertexFormatHalf = 53, -}; - -_MTL_ENUM(NS::UInteger, VertexStepFunction) { - VertexStepFunctionConstant = 0, - VertexStepFunctionPerVertex = 1, - VertexStepFunctionPerInstance = 2, - VertexStepFunctionPerPatch = 3, - VertexStepFunctionPerPatchControlPoint = 4, -}; - -class VertexBufferLayoutDescriptor : public NS::Copying -{ -public: - static class VertexBufferLayoutDescriptor* alloc(); - - class VertexBufferLayoutDescriptor* init(); - - NS::UInteger stride() const; - void setStride(NS::UInteger stride); - - MTL::VertexStepFunction stepFunction() const; - void setStepFunction(MTL::VertexStepFunction stepFunction); - - NS::UInteger stepRate() const; - void setStepRate(NS::UInteger stepRate); -}; - -class VertexBufferLayoutDescriptorArray : public NS::Referencing -{ -public: - static class VertexBufferLayoutDescriptorArray* alloc(); - - class VertexBufferLayoutDescriptorArray* init(); - - class VertexBufferLayoutDescriptor* object(NS::UInteger index); - - void setObject(const class VertexBufferLayoutDescriptor* bufferDesc, NS::UInteger index); -}; - -class VertexAttributeDescriptor : public NS::Copying -{ -public: - static class VertexAttributeDescriptor* alloc(); - - class VertexAttributeDescriptor* init(); - - MTL::VertexFormat format() const; - void setFormat(MTL::VertexFormat format); - - NS::UInteger offset() const; - void setOffset(NS::UInteger offset); - - NS::UInteger bufferIndex() const; - void setBufferIndex(NS::UInteger bufferIndex); -}; - -class VertexAttributeDescriptorArray : public NS::Referencing -{ -public: - static class VertexAttributeDescriptorArray* alloc(); - - class VertexAttributeDescriptorArray* init(); - - class VertexAttributeDescriptor* object(NS::UInteger index); - - void setObject(const class VertexAttributeDescriptor* attributeDesc, NS::UInteger index); -}; - -class VertexDescriptor : public NS::Copying -{ -public: - static class VertexDescriptor* alloc(); - - class VertexDescriptor* init(); - - static class VertexDescriptor* vertexDescriptor(); - - class VertexBufferLayoutDescriptorArray* layouts() const; - - class VertexAttributeDescriptorArray* attributes() const; - - void reset(); -}; - -} - -_MTL_INLINE MTL::VertexBufferLayoutDescriptor* MTL::VertexBufferLayoutDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLVertexBufferLayoutDescriptor)); -} - -_MTL_INLINE MTL::VertexBufferLayoutDescriptor* MTL::VertexBufferLayoutDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE NS::UInteger MTL::VertexBufferLayoutDescriptor::stride() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(stride)); -} - -_MTL_INLINE void MTL::VertexBufferLayoutDescriptor::setStride(NS::UInteger stride) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStride_), stride); -} - -_MTL_INLINE MTL::VertexStepFunction MTL::VertexBufferLayoutDescriptor::stepFunction() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(stepFunction)); -} - -_MTL_INLINE void MTL::VertexBufferLayoutDescriptor::setStepFunction(MTL::VertexStepFunction stepFunction) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStepFunction_), stepFunction); -} - -_MTL_INLINE NS::UInteger MTL::VertexBufferLayoutDescriptor::stepRate() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(stepRate)); -} - -_MTL_INLINE void MTL::VertexBufferLayoutDescriptor::setStepRate(NS::UInteger stepRate) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setStepRate_), stepRate); -} - -_MTL_INLINE MTL::VertexBufferLayoutDescriptorArray* MTL::VertexBufferLayoutDescriptorArray::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLVertexBufferLayoutDescriptorArray)); -} - -_MTL_INLINE MTL::VertexBufferLayoutDescriptorArray* MTL::VertexBufferLayoutDescriptorArray::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::VertexBufferLayoutDescriptor* MTL::VertexBufferLayoutDescriptorArray::object(NS::UInteger index) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(objectAtIndexedSubscript_), index); -} - -_MTL_INLINE void MTL::VertexBufferLayoutDescriptorArray::setObject(const MTL::VertexBufferLayoutDescriptor* bufferDesc, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setObject_atIndexedSubscript_), bufferDesc, index); -} - -_MTL_INLINE MTL::VertexAttributeDescriptor* MTL::VertexAttributeDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLVertexAttributeDescriptor)); -} - -_MTL_INLINE MTL::VertexAttributeDescriptor* MTL::VertexAttributeDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::VertexFormat MTL::VertexAttributeDescriptor::format() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(format)); -} - -_MTL_INLINE void MTL::VertexAttributeDescriptor::setFormat(MTL::VertexFormat format) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFormat_), format); -} - -_MTL_INLINE NS::UInteger MTL::VertexAttributeDescriptor::offset() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(offset)); -} - -_MTL_INLINE void MTL::VertexAttributeDescriptor::setOffset(NS::UInteger offset) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setOffset_), offset); -} - -_MTL_INLINE NS::UInteger MTL::VertexAttributeDescriptor::bufferIndex() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(bufferIndex)); -} - -_MTL_INLINE void MTL::VertexAttributeDescriptor::setBufferIndex(NS::UInteger bufferIndex) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setBufferIndex_), bufferIndex); -} - -_MTL_INLINE MTL::VertexAttributeDescriptorArray* MTL::VertexAttributeDescriptorArray::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLVertexAttributeDescriptorArray)); -} - -_MTL_INLINE MTL::VertexAttributeDescriptorArray* MTL::VertexAttributeDescriptorArray::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::VertexAttributeDescriptor* MTL::VertexAttributeDescriptorArray::object(NS::UInteger index) -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(objectAtIndexedSubscript_), index); -} - -_MTL_INLINE void MTL::VertexAttributeDescriptorArray::setObject(const MTL::VertexAttributeDescriptor* attributeDesc, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setObject_atIndexedSubscript_), attributeDesc, index); -} - -_MTL_INLINE MTL::VertexDescriptor* MTL::VertexDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLVertexDescriptor)); -} - -_MTL_INLINE MTL::VertexDescriptor* MTL::VertexDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::VertexDescriptor* MTL::VertexDescriptor::vertexDescriptor() -{ - return Object::sendMessage(_MTL_PRIVATE_CLS(MTLVertexDescriptor), _MTL_PRIVATE_SEL(vertexDescriptor)); -} - -_MTL_INLINE MTL::VertexBufferLayoutDescriptorArray* MTL::VertexDescriptor::layouts() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(layouts)); -} - -_MTL_INLINE MTL::VertexAttributeDescriptorArray* MTL::VertexDescriptor::attributes() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(attributes)); -} - -_MTL_INLINE void MTL::VertexDescriptor::reset() -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(reset)); -} - -#pragma once - -namespace MTL -{ -class VisibleFunctionTableDescriptor : public NS::Copying -{ -public: - static class VisibleFunctionTableDescriptor* alloc(); - - class VisibleFunctionTableDescriptor* init(); - - static class VisibleFunctionTableDescriptor* visibleFunctionTableDescriptor(); - - NS::UInteger functionCount() const; - void setFunctionCount(NS::UInteger functionCount); -}; - -class VisibleFunctionTable : public NS::Referencing -{ -public: - MTL::ResourceID gpuResourceID() const; - - void setFunction(const class FunctionHandle* function, NS::UInteger index); - - void setFunctions(const class FunctionHandle* const functions[], NS::Range range); -}; - -} - -_MTL_INLINE MTL::VisibleFunctionTableDescriptor* MTL::VisibleFunctionTableDescriptor::alloc() -{ - return NS::Object::alloc(_MTL_PRIVATE_CLS(MTLVisibleFunctionTableDescriptor)); -} - -_MTL_INLINE MTL::VisibleFunctionTableDescriptor* MTL::VisibleFunctionTableDescriptor::init() -{ - return NS::Object::init(); -} - -_MTL_INLINE MTL::VisibleFunctionTableDescriptor* MTL::VisibleFunctionTableDescriptor::visibleFunctionTableDescriptor() -{ - return Object::sendMessage(_MTL_PRIVATE_CLS(MTLVisibleFunctionTableDescriptor), _MTL_PRIVATE_SEL(visibleFunctionTableDescriptor)); -} - -_MTL_INLINE NS::UInteger MTL::VisibleFunctionTableDescriptor::functionCount() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(functionCount)); -} - -_MTL_INLINE void MTL::VisibleFunctionTableDescriptor::setFunctionCount(NS::UInteger functionCount) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFunctionCount_), functionCount); -} - -_MTL_INLINE MTL::ResourceID MTL::VisibleFunctionTable::gpuResourceID() const -{ - return Object::sendMessage(this, _MTL_PRIVATE_SEL(gpuResourceID)); -} - -_MTL_INLINE void MTL::VisibleFunctionTable::setFunction(const MTL::FunctionHandle* function, NS::UInteger index) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFunction_atIndex_), function, index); -} - -_MTL_INLINE void MTL::VisibleFunctionTable::setFunctions(const MTL::FunctionHandle* const functions[], NS::Range range) -{ - Object::sendMessage(this, _MTL_PRIVATE_SEL(setFunctions_withRange_), functions, range); -} - -#define METALCPP_VERSION_MAJOR 306 -#define METALCPP_VERSION_MINOR 2 -#define METALCPP_VERSION_PATCH 4 - -#define METALCPP_SUPPORTS_VERSION(major, minor, patch) \ - ((major < METALCPP_VERSION_MAJOR) || \ - (major == METALCPP_VERSION_MAJOR && minor < METALCPP_VERSION_MINOR) || \ - (major == METALCPP_VERSION_MAJOR && minor == METALCPP_VERSION_MINOR && patch <= METALCPP_VERSION_PATCH)) - diff --git a/app/jni/src/libultraship/extern/nlohmann-json/.clang-format b/app/jni/src/libultraship/extern/nlohmann-json/.clang-format deleted file mode 100644 index 5b9e3fd..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/.clang-format +++ /dev/null @@ -1,84 +0,0 @@ -#AccessModifierOffset: 2 -AlignAfterOpenBracket: Align -AlignConsecutiveAssignments: false -#AlignConsecutiveBitFields: false -AlignConsecutiveDeclarations: false -AlignConsecutiveMacros: false -AlignEscapedNewlines: Right -#AlignOperands: AlignAfterOperator -AlignTrailingComments: true -AllowAllArgumentsOnNextLine: false -AllowAllConstructorInitializersOnNextLine: false -AllowAllParametersOfDeclarationOnNextLine: false -AllowShortBlocksOnASingleLine: Empty -AllowShortCaseLabelsOnASingleLine: false -#AllowShortEnumsOnASingleLine: true -AllowShortFunctionsOnASingleLine: Empty -AllowShortIfStatementsOnASingleLine: Never -AllowShortLambdasOnASingleLine: Empty -AllowShortLoopsOnASingleLine: false -AlwaysBreakAfterReturnType: None -AlwaysBreakBeforeMultilineStrings: false -AlwaysBreakTemplateDeclarations: Yes -BinPackArguments: false -BinPackParameters: false -#BitFieldColonSpacing: Both -BreakBeforeBraces: Custom # or Allman -BraceWrapping: - AfterCaseLabel: true - AfterClass: true - AfterControlStatement: Always - AfterEnum: true - AfterFunction: true - AfterNamespace: false - AfterStruct: true - AfterUnion: true - AfterExternBlock: false - BeforeCatch: true - BeforeElse: true - #BeforeLambdaBody: false - #BeforeWhile: false - SplitEmptyFunction: false - SplitEmptyRecord: false - SplitEmptyNamespace: false -BreakBeforeTernaryOperators: true -BreakConstructorInitializers: BeforeComma -BreakStringLiterals: false -ColumnLimit: 0 -CompactNamespaces: false -ConstructorInitializerIndentWidth: 2 -Cpp11BracedListStyle: true -PointerAlignment: Left -FixNamespaceComments: true -IncludeBlocks: Preserve -#IndentCaseBlocks: false -IndentCaseLabels: true -IndentGotoLabels: false -IndentPPDirectives: BeforeHash -IndentWidth: 4 -KeepEmptyLinesAtTheStartOfBlocks: false -MaxEmptyLinesToKeep: 1 -NamespaceIndentation: None -ReflowComments: false -SortIncludes: true -SortUsingDeclarations: true -SpaceAfterCStyleCast: false -SpaceAfterLogicalNot: false -SpaceAfterTemplateKeyword: false -SpaceBeforeAssignmentOperators: true -SpaceBeforeCpp11BracedList: false -SpaceBeforeParens: ControlStatements -SpaceBeforeRangeBasedForLoopColon: true -SpaceBeforeSquareBrackets: false -SpaceInEmptyBlock: false -SpaceInEmptyParentheses: false -SpacesBeforeTrailingComments: 2 -SpacesInAngles: false -SpacesInCStyleCastParentheses: false -SpacesInConditionalStatement: false -SpacesInContainerLiterals: false -SpacesInParentheses: false -SpacesInSquareBrackets: false -Standard: c++11 -TabWidth: 4 -UseTab: Never diff --git a/app/jni/src/libultraship/extern/nlohmann-json/.clang-tidy b/app/jni/src/libultraship/extern/nlohmann-json/.clang-tidy deleted file mode 100644 index 4d4238a..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/.clang-tidy +++ /dev/null @@ -1,56 +0,0 @@ -Checks: '*, - -altera-id-dependent-backward-branch, - -altera-struct-pack-align, - -altera-unroll-loops, - -android-cloexec-fopen, - -bugprone-easily-swappable-parameters, - -cert-err58-cpp, - -concurrency-mt-unsafe, - -cppcoreguidelines-avoid-goto, - -cppcoreguidelines-avoid-magic-numbers, - -cppcoreguidelines-avoid-non-const-global-variables, - -cppcoreguidelines-macro-usage, - -cppcoreguidelines-pro-bounds-array-to-pointer-decay, - -cppcoreguidelines-pro-bounds-constant-array-index, - -cppcoreguidelines-pro-bounds-pointer-arithmetic, - -cppcoreguidelines-pro-type-reinterpret-cast, - -cppcoreguidelines-pro-type-union-access, - -cppcoreguidelines-virtual-class-destructor, - -fuchsia-default-arguments-calls, - -fuchsia-default-arguments-declarations, - -fuchsia-overloaded-operator, - -google-explicit-constructor, - -google-readability-function-size, - -google-runtime-int, - -google-runtime-references, - -hicpp-avoid-goto, - -hicpp-explicit-conversions, - -hicpp-function-size, - -hicpp-no-array-decay, - -hicpp-no-assembler, - -hicpp-signed-bitwise, - -hicpp-uppercase-literal-suffix, - -llvm-header-guard, - -llvm-include-order, - -llvmlibc-*, - -misc-no-recursion, - -misc-non-private-member-variables-in-classes, - -modernize-concat-nested-namespaces, - -modernize-use-nodiscard, - -modernize-use-trailing-return-type, - -readability-function-cognitive-complexity, - -readability-function-size, - -readability-identifier-length, - -readability-magic-numbers, - -readability-redundant-access-specifiers, - -readability-simplify-boolean-expr, - -readability-uppercase-literal-suffix' - -CheckOptions: - - key: hicpp-special-member-functions.AllowSoleDefaultDtor - value: 1 - -WarningsAsErrors: '*' - -#HeaderFilterRegex: '.*nlohmann.*' -HeaderFilterRegex: '.*hpp$' diff --git a/app/jni/src/libultraship/extern/nlohmann-json/.github/CODEOWNERS b/app/jni/src/libultraship/extern/nlohmann-json/.github/CODEOWNERS deleted file mode 100644 index 4d5ee04..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/.github/CODEOWNERS +++ /dev/null @@ -1,6 +0,0 @@ -# JSON for Modern C++ has been originally written by Niels Lohmann. -# Since 2013 over 140 contributors have helped to improve the library. -# This CODEOWNERS file is only to make sure that @nlohmann is requested -# for a code review in case of a pull request. - -* @nlohmann diff --git a/app/jni/src/libultraship/extern/nlohmann-json/.github/CODE_OF_CONDUCT.md b/app/jni/src/libultraship/extern/nlohmann-json/.github/CODE_OF_CONDUCT.md deleted file mode 100644 index 770b817..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/.github/CODE_OF_CONDUCT.md +++ /dev/null @@ -1,46 +0,0 @@ -# Contributor Covenant Code of Conduct - -## Our Pledge - -In the interest of fostering an open and welcoming environment, we as contributors and maintainers pledge to making participation in our project and our community a harassment-free experience for everyone, regardless of age, body size, disability, ethnicity, gender identity and expression, level of experience, nationality, personal appearance, race, religion, or sexual identity and orientation. - -## Our Standards - -Examples of behavior that contributes to creating a positive environment include: - -* Using welcoming and inclusive language -* Being respectful of differing viewpoints and experiences -* Gracefully accepting constructive criticism -* Focusing on what is best for the community -* Showing empathy towards other community members - -Examples of unacceptable behavior by participants include: - -* The use of sexualized language or imagery and unwelcome sexual attention or advances -* Trolling, insulting/derogatory comments, and personal or political attacks -* Public or private harassment -* Publishing others' private information, such as a physical or electronic address, without explicit permission -* Other conduct which could reasonably be considered inappropriate in a professional setting - -## Our Responsibilities - -Project maintainers are responsible for clarifying the standards of acceptable behavior and are expected to take appropriate and fair corrective action in response to any instances of unacceptable behavior. - -Project maintainers have the right and responsibility to remove, edit, or reject comments, commits, code, wiki edits, issues, and other contributions that are not aligned to this Code of Conduct, or to ban temporarily or permanently any contributor for other behaviors that they deem inappropriate, threatening, offensive, or harmful. - -## Scope - -This Code of Conduct applies both within project spaces and in public spaces when an individual is representing the project or its community. Examples of representing a project or community include using an official project e-mail address, posting via an official social media account, or acting as an appointed representative at an online or offline event. Representation of a project may be further defined and clarified by project maintainers. - -## Enforcement - -Instances of abusive, harassing, or otherwise unacceptable behavior may be reported by contacting the project team at mail@nlohmann.me. The project team will review and investigate all complaints, and will respond in a way that it deems appropriate to the circumstances. The project team is obligated to maintain confidentiality with regard to the reporter of an incident. Further details of specific enforcement policies may be posted separately. - -Project maintainers who do not follow or enforce the Code of Conduct in good faith may face temporary or permanent repercussions as determined by other members of the project's leadership. - -## Attribution - -This Code of Conduct is adapted from the [Contributor Covenant][homepage], version 1.4, available at [http://contributor-covenant.org/version/1/4][version] - -[homepage]: http://contributor-covenant.org -[version]: http://contributor-covenant.org/version/1/4/ diff --git a/app/jni/src/libultraship/extern/nlohmann-json/.github/CONTRIBUTING.md b/app/jni/src/libultraship/extern/nlohmann-json/.github/CONTRIBUTING.md deleted file mode 100644 index 1529ab9..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/.github/CONTRIBUTING.md +++ /dev/null @@ -1,71 +0,0 @@ -[![Issue Stats](http://issuestats.com/github/nlohmann/json/badge/pr?style=flat)](http://issuestats.com/github/nlohmann/json) [![Issue Stats](http://issuestats.com/github/nlohmann/json/badge/issue?style=flat)](http://issuestats.com/github/nlohmann/json) - -# How to contribute - -This project started as a little excuse to exercise some of the cool new C++11 features. Over time, people actually started to use the JSON library (yey!) and started to help improve it by proposing features, finding bugs, or even fixing my mistakes. I am really [thankful](https://github.com/nlohmann/json/blob/master/README.md#thanks) for this and try to keep track of all the helpers. - -To make it as easy as possible for you to contribute and for me to keep an overview, here are a few guidelines which should help us avoid all kinds of unnecessary work or disappointment. And of course, this document is subject to discussion, so please [create an issue](https://github.com/nlohmann/json/issues/new/choose) or a pull request if you find a way to improve it! - -## Private reports - -Usually, all issues are tracked publicly on [GitHub](https://github.com/nlohmann/json/issues). If you want to make a private report (e.g., for a vulnerability or to attach an example that is not meant to be published), please send an email to . - -## Prerequisites - -Please [create an issue](https://github.com/nlohmann/json/issues/new/choose), assuming one does not already exist, and describe your concern. Note you need a [GitHub account](https://github.com/signup/free) for this. - -## Describe your issue - -Clearly describe the issue: - -- If it is a bug, please describe how to **reproduce** it. If possible, attach a complete example which demonstrates the error. Please also state what you **expected** to happen instead of the error. -- If you propose a change or addition, try to give an **example** how the improved code could look like or how to use it. -- If you found a compilation error, please tell us which **compiler** (version and operating system) you used and paste the (relevant part of) the error messages to the ticket. - -Please stick to the provided issue template ([bug report](https://github.com/nlohmann/json/blob/develop/.github/ISSUE_TEMPLATE/bug.yml) if possible. For questions, feature or support requests, please [open a discussion](https://github.com/nlohmann/json/discussions/new). - -## Files to change - -:exclamation: Before you make any changes, note the single-header files [`single_include/nlohmann/json.hpp`](https://github.com/nlohmann/json/blob/develop/single_include/nlohmann/json.hpp) and [`single_include/nlohmann/json_fwd.hpp`](https://github.com/nlohmann/json/blob/develop/single_include/nlohmann/json_fwd.hpp) are **generated** from the source files in the [`include/nlohmann` directory](https://github.com/nlohmann/json/tree/develop/include/nlohmann). Please **do not** edit the files `single_include/nlohmann/json.hpp` and `single_include/nlohmann/json_fwd.hpp` directly, but change the `include/nlohmann` sources and regenerate the files by executing `make amalgamate`. - -To make changes, you need to edit the following files: - -1. [`include/nlohmann/*`](https://github.com/nlohmann/json/tree/develop/include/nlohmann) - These files are the sources of the library. Before testing or creating a pull request, execute `make amalgamate` to regenerate `single_include/nlohmann/json.hpp` and `single_include/nlohmann/json_fwd.hpp`. - -2. [`tests/src/unit-*.cpp`](https://github.com/nlohmann/json/tree/develop/tests/src) - These files contain the [doctest](https://github.com/onqtam/doctest) unit tests which currently cover [100 %](https://coveralls.io/github/nlohmann/json) of the library's code. - - If you add or change a feature, please also add a unit test to this file. The unit tests can be compiled and executed with - - ```sh - $ mkdir build - $ cd build - $ cmake .. - $ cmake --build . - $ ctest - ``` - - The test cases are also executed with several different compilers on [Travis](https://travis-ci.org/nlohmann/json) once you open a pull request. - - -## Note - -- If you open a pull request, the code will be automatically tested with [Valgrind](http://valgrind.org)'s Memcheck tool to detect memory leaks. Please be aware that the execution with Valgrind _may_ in rare cases yield different behavior than running the code directly. This can result in failing unit tests which run successfully without Valgrind. -- There is a Makefile target `make pretty` which runs [Artistic Style](http://astyle.sourceforge.net) to fix indentation. If possible, run it before opening the pull request. Otherwise, we shall run it afterward. - -## Please don't - -- The C++11 support varies between different **compilers** and versions. Please note the [list of supported compilers](https://github.com/nlohmann/json/blob/master/README.md#supported-compilers). Some compilers like GCC 4.7 (and earlier), Clang 3.3 (and earlier), or Microsoft Visual Studio 13.0 and earlier are known not to work due to missing or incomplete C++11 support. Please refrain from proposing changes that work around these compiler's limitations with `#ifdef`s or other means. -- Specifically, I am aware of compilation problems with **Microsoft Visual Studio** (there even is an [issue label](https://github.com/nlohmann/json/issues?utf8=✓&q=label%3A%22visual+studio%22+) for these kind of bugs). I understand that even in 2016, complete C++11 support isn't there yet. But please also understand that I do not want to drop features or uglify the code just to make Microsoft's sub-standard compiler happy. The past has shown that there are ways to express the functionality such that the code compiles with the most recent MSVC - unfortunately, this is not the main objective of the project. -- Please refrain from proposing changes that would **break [JSON](https://json.org) conformance**. If you propose a conformant extension of JSON to be supported by the library, please motivate this extension. - - We shall not extend the library to **support comments**. There is quite some [controversy](https://www.reddit.com/r/programming/comments/4v6chu/why_json_doesnt_support_comments_douglas_crockford/) around this topic, and there were quite some [issues](https://github.com/nlohmann/json/issues/376) on this. We believe that JSON is fine without comments. - - We do not preserve the **insertion order of object elements**. The [JSON standard](https://tools.ietf.org/html/rfc8259.html) defines objects as "an unordered collection of zero or more name/value pairs". To this end, this library does not preserve insertion order of name/value pairs. (In fact, keys will be traversed in alphabetical order as `std::map` with `std::less` is used by default.) Note this behavior conforms to the standard, and we shall not change it to any other order. If you do want to preserve the insertion order, you can specialize the object type with containers like [`tsl::ordered_map`](https://github.com/Tessil/ordered-map) or [`nlohmann::fifo_map`](https://github.com/nlohmann/fifo_map). - -- Please do not open pull requests that address **multiple issues**. - -## Wanted - -The following areas really need contribution: - -- Extending the **continuous integration** toward more exotic compilers such as Android NDK, Intel's Compiler, or the bleeding-edge versions Clang. -- Improving the efficiency of the **JSON parser**. The current parser is implemented as a naive recursive descent parser with hand coded string handling. More sophisticated approaches like LALR parsers would be really appreciated. That said, parser generators like Bison or ANTLR do not play nice with single-header files -- I really would like to keep the parser inside the `json.hpp` header, and I am not aware of approaches similar to [`re2c`](http://re2c.org) for parsing. -- Extending and updating existing **benchmarks** to include (the most recent version of) this library. Though efficiency is not everything, speed and memory consumption are very important characteristics for C++ developers, so having proper comparisons would be interesting. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/.github/FUNDING.yml b/app/jni/src/libultraship/extern/nlohmann-json/.github/FUNDING.yml deleted file mode 100644 index a6c972e..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/.github/FUNDING.yml +++ /dev/null @@ -1,2 +0,0 @@ -github: nlohmann -custom: http://paypal.me/nlohmann diff --git a/app/jni/src/libultraship/extern/nlohmann-json/.github/ISSUE_TEMPLATE/bug.yaml b/app/jni/src/libultraship/extern/nlohmann-json/.github/ISSUE_TEMPLATE/bug.yaml deleted file mode 100644 index 571a1cc..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/.github/ISSUE_TEMPLATE/bug.yaml +++ /dev/null @@ -1,93 +0,0 @@ -name: Bug Report -description: Create a bug report -labels: - - 'kind: bug' -body: - - type: markdown - attributes: - value: > - Thanks for taking the time to fill out this bug report! - - Make sure you give it a short and specific **title** so that the report - is searchable and uniquely identifiable. - - Note that this form is for bug reports only. Please - [open a discussion](https://github.com/nlohmann/json/discussions/new) - for questions, feature requests, or support requests - - type: textarea - id: summary - attributes: - label: Description - description: > - Please provide an abstract description of the issue to the developers, - and why you consider it to be a bug. Please include any specific links - to the documentation, JSON specification, or code. - validations: - required: true - - type: textarea - id: reproduce - attributes: - label: Reproduction steps - description: > - How do you trigger the bug? Please walk us through step by step. Be as - specific as possible. - validations: - required: true - - type: textarea - id: results - attributes: - label: Expected vs. actual results - description: > - Please describe what you expected to happen after the steps above and - what actually happened. - validations: - required: true - - type: textarea - id: code - attributes: - label: Minimal code example - description: > - If possible, provide a small and self-contained example that triggers - the bug. Please understand that we cannot analyze and debug large code - bases. Please do not paste screenshots here. - render: Shell - - type: textarea - id: output - attributes: - label: Error messages - description: > - Please provide any kind of error output (compilation errors, exception - messages, stack traces, etc.) which can help to diagnose the error. - render: Shell - - type: input - id: compiler - attributes: - label: Compiler and operating system - description: > - On which operating systems and compilers have you observed the issue? - Include as many relevant details about the environment you experienced - the bug in. Make sure you use a - [supported compiler](https://github.com/nlohmann/json#supported-compilers). - validations: - required: true - - type: input - id: version - attributes: - label: Library version - description: > - Which version of the library did you use? If it is a released version, - please enter the version number (e.g., 3.11.2). Otherwise, please enter - the commit hash. If you got the library from another source as the - GitHub repository (e.g., via a package manager), please also state - this. - validations: - required: true - - type: checkboxes - id: validation - attributes: - label: Validation - description: > - Please check these additional steps: - options: - - label: The bug also occurs if the latest version from the [`develop`](https://github.com/nlohmann/json/tree/develop) branch is used. - - label: I can successfully [compile and run the unit tests](https://github.com/nlohmann/json#execute-unit-tests). diff --git a/app/jni/src/libultraship/extern/nlohmann-json/.github/ISSUE_TEMPLATE/config.yml b/app/jni/src/libultraship/extern/nlohmann-json/.github/ISSUE_TEMPLATE/config.yml deleted file mode 100644 index 0e96633..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/.github/ISSUE_TEMPLATE/config.yml +++ /dev/null @@ -1,5 +0,0 @@ -blank_issues_enabled: false -contact_links: - - name: Ask a question - url: https://github.com/nlohmann/json/discussions - about: Ask questions and discuss with other community members diff --git a/app/jni/src/libultraship/extern/nlohmann-json/.github/PULL_REQUEST_TEMPLATE.md b/app/jni/src/libultraship/extern/nlohmann-json/.github/PULL_REQUEST_TEMPLATE.md deleted file mode 100644 index 56854fb..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/.github/PULL_REQUEST_TEMPLATE.md +++ /dev/null @@ -1,19 +0,0 @@ -[Describe your pull request here. Please read the text below the line, and make sure you follow the checklist.] - -* * * - -## Pull request checklist - -Read the [Contribution Guidelines](https://github.com/nlohmann/json/blob/develop/.github/CONTRIBUTING.md) for detailed information. - -- [ ] Changes are described in the pull request, or an [existing issue is referenced](https://github.com/nlohmann/json/issues). -- [ ] The test suite [compiles and runs](https://github.com/nlohmann/json/blob/develop/README.md#execute-unit-tests) without error. -- [ ] [Code coverage](https://coveralls.io/github/nlohmann/json) is 100%. Test cases can be added by editing the [test suite](https://github.com/nlohmann/json/tree/develop/test/src). -- [ ] The source code is amalgamated; that is, after making changes to the sources in the `include/nlohmann` directory, run `make amalgamate` to create the single-header files `single_include/nlohmann/json.hpp` and `single_include/nlohmann/json_fwd.hpp`. The whole process is described [here](https://github.com/nlohmann/json/blob/develop/.github/CONTRIBUTING.md#files-to-change). - -## Please don't - -- The C++11 support varies between different **compilers** and versions. Please note the [list of supported compilers](https://github.com/nlohmann/json/blob/master/README.md#supported-compilers). Some compilers like GCC 4.7 (and earlier), Clang 3.3 (and earlier), or Microsoft Visual Studio 13.0 and earlier are known not to work due to missing or incomplete C++11 support. Please refrain from proposing changes that work around these compiler's limitations with `#ifdef`s or other means. -- Specifically, I am aware of compilation problems with **Microsoft Visual Studio** (there even is an [issue label](https://github.com/nlohmann/json/issues?utf8=✓&q=label%3A%22visual+studio%22+) for these kind of bugs). I understand that even in 2016, complete C++11 support isn't there yet. But please also understand that I do not want to drop features or uglify the code just to make Microsoft's sub-standard compiler happy. The past has shown that there are ways to express the functionality such that the code compiles with the most recent MSVC - unfortunately, this is not the main objective of the project. -- Please refrain from proposing changes that would **break [JSON](https://json.org) conformance**. If you propose a conformant extension of JSON to be supported by the library, please motivate this extension. -- Please do not open pull requests that address **multiple issues**. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/.github/SECURITY.md b/app/jni/src/libultraship/extern/nlohmann-json/.github/SECURITY.md deleted file mode 100644 index 4d010eb..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/.github/SECURITY.md +++ /dev/null @@ -1,5 +0,0 @@ -# Security Policy - -## Reporting a Vulnerability - -Usually, all issues are tracked publicly on [GitHub](https://github.com/nlohmann/json/issues). If you want to make a private report (e.g., for a vulnerability or to attach an example that is not meant to be published), please send an email to . You can use [this key](https://keybase.io/nlohmann/pgp_keys.asc?fingerprint=797167ae41c0a6d9232e48457f3cea63ae251b69) for encryption. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/.github/config.yml b/app/jni/src/libultraship/extern/nlohmann-json/.github/config.yml deleted file mode 100644 index 7a8f41e..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/.github/config.yml +++ /dev/null @@ -1,19 +0,0 @@ -# Configuration for sentiment-bot - https://github.com/behaviorbot/sentiment-bot - -# *Required* toxicity threshold between 0 and .99 with the higher numbers being the most toxic -# Anything higher than this threshold will be marked as toxic and commented on -sentimentBotToxicityThreshold: .7 - -# *Required* Comment to reply with -sentimentBotReplyComment: > - Please be sure to review the [code of conduct](https://github.com/nlohmann/json/blob/develop/CODE_OF_CONDUCT.md) and be respectful of other users. cc/ @nlohmann - - -# Configuration for request-info - https://github.com/behaviorbot/request-info - -# *Required* Comment to reply with -requestInfoReplyComment: > - We would appreciate it if you could provide us with more info about this issue or pull request! Please check the [issue template](https://github.com/nlohmann/json/blob/develop/.github/ISSUE_TEMPLATE.md) and the [pull request template](https://github.com/nlohmann/json/blob/develop/.github/PULL_REQUEST_TEMPLATE.md). - -# *OPTIONAL* Label to be added to Issues and Pull Requests with insufficient information given -requestInfoLabelToAdd: "state: needs more info" diff --git a/app/jni/src/libultraship/extern/nlohmann-json/.github/external_ci/.drone.yml b/app/jni/src/libultraship/extern/nlohmann-json/.github/external_ci/.drone.yml deleted file mode 100644 index 0d9e3d0..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/.github/external_ci/.drone.yml +++ /dev/null @@ -1,22 +0,0 @@ -kind: pipeline -name: test-on-arm64 - -platform: - arch: arm64 - -steps: -- name: build - image: gcc - commands: - - wget https://github.com/Kitware/CMake/releases/download/v3.20.2/cmake-3.20.2.tar.gz - - tar xfz cmake-3.20.2.tar.gz - - cd cmake-3.20.2 - - ./configure - - make cmake ctest -j10 - - cd .. - - mkdir build - - cd build - - ../cmake-3.20.2/bin/cmake .. -DJSON_FastTests=ON - - make -j10 - - cd tests - - ../../cmake-3.20.2/bin/ctest -j10 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/.github/external_ci/appveyor.yml b/app/jni/src/libultraship/extern/nlohmann-json/.github/external_ci/appveyor.yml deleted file mode 100644 index 126ed99..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/.github/external_ci/appveyor.yml +++ /dev/null @@ -1,91 +0,0 @@ -version: '{build}' - -# only build PRs and commits to develop branch -# (see https://help.appveyor.com/discussions/questions/55079-two-builds-per-commit-to-pull-request) -branches: - only: - - develop - -only_commits: - files: - - .github/external_ci/appveyor.yml - - cmake/ - - include/ - - tests/ - - CMakeLists.txt - -environment: - matrix: - - APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2015 - configuration: Debug - platform: x86 - CXX_FLAGS: "/W4 /WX" - CMAKE_OPTIONS: "" - GENERATOR: Visual Studio 14 2015 - - - APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2015 - configuration: Release - platform: x86 - CXX_FLAGS: "/W4 /WX" - CMAKE_OPTIONS: "" - GENERATOR: Visual Studio 14 2015 - - - APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2015 - configuration: Release - platform: x86 - name: with_win_header - CXX_FLAGS: "/W4 /WX" - CMAKE_OPTIONS: "" - GENERATOR: Visual Studio 14 2015 - - - APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2017 - configuration: Release - platform: x86 - CXX_FLAGS: "/permissive- /std:c++latest /utf-8 /W4 /WX" - CMAKE_OPTIONS: "" - GENERATOR: Visual Studio 15 2017 - - - APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2019 - configuration: Release - platform: x86 - CXX_FLAGS: "/W4 /WX" - CMAKE_OPTIONS: "-DJSON_ImplicitConversions=OFF" - GENERATOR: Visual Studio 16 2019 - - - APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2015 - configuration: Release - platform: x64 - CXX_FLAGS: "/W4 /WX" - CMAKE_OPTIONS: "" - GENERATOR: Visual Studio 14 2015 - - - APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2017 - configuration: Release - platform: x64 - CXX_FLAGS: "/permissive- /std:c++latest /Zc:__cplusplus /utf-8 /W4 /WX" - CMAKE_OPTIONS: "" - GENERATOR: Visual Studio 15 2017 - -init: - - cmake --version - - msbuild /version - -install: - - if "%platform%"=="x86" set GENERATOR_PLATFORM=Win32 - -before_build: - # for with_win_header build, inject the inclusion of Windows.h to the single-header library - - ps: if ($env:name -Eq "with_win_header") { $header_path = "single_include\nlohmann\json.hpp" } - - ps: if ($env:name -Eq "with_win_header") { "#include `n" + (Get-Content $header_path | Out-String) | Set-Content $header_path } - - cmake . -G "%GENERATOR%" -A "%GENERATOR_PLATFORM%" -DCMAKE_CXX_FLAGS="%CXX_FLAGS%" -DCMAKE_IGNORE_PATH="C:/Program Files/Git/usr/bin" -DJSON_BuildTests=On "%CMAKE_OPTIONS%" - -build_script: - - cmake --build . --config "%configuration%" --parallel 2 - -test_script: - - if "%configuration%"=="Release" ctest -C "%configuration%" --parallel 2 --output-on-failure - # On Debug builds, skip test-unicode_all - # as it is extremely slow to run and cause - # occasional timeouts on AppVeyor. - # More info: https://github.com/nlohmann/json/pull/1570 - - if "%configuration%"=="Debug" ctest --exclude-regex "test-unicode" -C "%configuration%" --parallel 2 --output-on-failure diff --git a/app/jni/src/libultraship/extern/nlohmann-json/.github/labeler.yml b/app/jni/src/libultraship/extern/nlohmann-json/.github/labeler.yml deleted file mode 100644 index 024d3e6..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/.github/labeler.yml +++ /dev/null @@ -1,38 +0,0 @@ -version: 1 - -labels: -- label: "documentation" - files: - - "README.md" - -- label: "documentation" - files: - - "docs/.*" - -- label: "tests" - files: - - "tests/.*" - -- label: "CMake" - files: - - ".*CMakeLists.txt" - -- label: "CMake" - files: - - "cmake/.*" - -- label: "CI" - files: - - "github/workflows/.*" - -- label: "CI" - files: - - "github/external_ci/.*" - -- label: "S" - size-below: 10 -- label: "M" - size-above: 9 - size-below: 100 -- label: "L" - size-above: 100 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/.github/stale.yml b/app/jni/src/libultraship/extern/nlohmann-json/.github/stale.yml deleted file mode 100644 index d30c78b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/.github/stale.yml +++ /dev/null @@ -1,17 +0,0 @@ -# Number of days of inactivity before an issue becomes stale -daysUntilStale: 30 -# Number of days of inactivity before a stale issue is closed -daysUntilClose: 7 -# Issues with these labels will never be considered stale -exemptLabels: - - pinned - - security -# Label to use when marking an issue as stale -staleLabel: "state: stale" -# Comment to post when marking an issue as stale. Set to `false` to disable -markComment: > - This issue has been automatically marked as stale because it has not had - recent activity. It will be closed if no further activity occurs. Thank you - for your contributions. -# Comment to post when closing a stale issue. Set to `false` to disable -closeComment: false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/.github/workflows/codeql-analysis.yml b/app/jni/src/libultraship/extern/nlohmann-json/.github/workflows/codeql-analysis.yml deleted file mode 100644 index 7ba83ac..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/.github/workflows/codeql-analysis.yml +++ /dev/null @@ -1,37 +0,0 @@ -name: "Code scanning - action" - -on: - push: - branches: - - develop - - master - - release/* - pull_request: - schedule: - - cron: '0 19 * * 1' - workflow_dispatch: - -concurrency: - group: ${{ github.workflow }}-${{ github.ref || github.run_id }} - cancel-in-progress: true - -jobs: - CodeQL-Build: - - runs-on: ubuntu-latest - - steps: - - name: Checkout repository - uses: actions/checkout@v3 - - # Initializes the CodeQL tools for scanning. - - name: Initialize CodeQL - uses: github/codeql-action/init@v2 - - # Autobuild attempts to build any compiled languages (C/C++, C#, or Java). - # If this step fails, then you should remove it and run the build manually (see below) - - name: Autobuild - uses: github/codeql-action/autobuild@v2 - - - name: Perform CodeQL Analysis - uses: github/codeql-action/analyze@v2 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/.github/workflows/labeler.yml b/app/jni/src/libultraship/extern/nlohmann-json/.github/workflows/labeler.yml deleted file mode 100644 index 66cb7eb..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/.github/workflows/labeler.yml +++ /dev/null @@ -1,18 +0,0 @@ -name: "Pull Request Labeler" - -on: - pull_request_target: - types: [opened, synchronize] - -jobs: - label: - permissions: - contents: read - pull-requests: write - - runs-on: ubuntu-latest - - steps: - - uses: srvaroa/labeler@master - env: - GITHUB_TOKEN: "${{ secrets.GITHUB_TOKEN }}" diff --git a/app/jni/src/libultraship/extern/nlohmann-json/.github/workflows/macos.yml b/app/jni/src/libultraship/extern/nlohmann-json/.github/workflows/macos.yml deleted file mode 100644 index 7eaedd7..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/.github/workflows/macos.yml +++ /dev/null @@ -1,66 +0,0 @@ -name: macOS - -on: - push: - branches: - - develop - - master - - release/* - pull_request: - workflow_dispatch: - -concurrency: - group: ${{ github.workflow }}-${{ github.ref || github.run_id }} - cancel-in-progress: true - -jobs: - xcode_1: - runs-on: macos-11 - strategy: - matrix: - xcode: ['11.7', '12.4', '12.5.1', '13.0'] - env: - DEVELOPER_DIR: /Applications/Xcode_${{ matrix.xcode }}.app/Contents/Developer - - steps: - - uses: actions/checkout@v3 - - name: Run CMake - run: cmake -S . -B build -D CMAKE_BUILD_TYPE=Debug -DJSON_BuildTests=On -DJSON_FastTests=ON - - name: Build - run: cmake --build build --parallel 10 - - name: Test - run: cd build ; ctest -j 10 --output-on-failure - - xcode_2: - runs-on: macos-12 - strategy: - matrix: - xcode: ['13.1', '13.2.1', '13.3.1', '13.4.1'] - env: - DEVELOPER_DIR: /Applications/Xcode_${{ matrix.xcode }}.app/Contents/Developer - - steps: - - uses: actions/checkout@v3 - - name: Run CMake - run: cmake -S . -B build -D CMAKE_BUILD_TYPE=Debug -DJSON_BuildTests=On -DJSON_FastTests=ON - - name: Build - run: cmake --build build --parallel 10 - - name: Test - run: cd build ; ctest -j 10 --output-on-failure - - xcode_standards: - runs-on: macos-latest - strategy: - matrix: - standard: [11, 14, 17, 20] - env: - DEVELOPER_DIR: /Applications/Xcode_12.4.app/Contents/Developer - - steps: - - uses: actions/checkout@v3 - - name: Run CMake - run: cmake -S . -B build -D CMAKE_BUILD_TYPE=Debug -DJSON_BuildTests=On -DJSON_TestStandards=${{ matrix.standard }} - - name: Build - run: cmake --build build --parallel 10 - - name: Test - run: cd build ; ctest -j 10 --output-on-failure diff --git a/app/jni/src/libultraship/extern/nlohmann-json/.github/workflows/publish_documentation.yml b/app/jni/src/libultraship/extern/nlohmann-json/.github/workflows/publish_documentation.yml deleted file mode 100644 index 65c42a7..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/.github/workflows/publish_documentation.yml +++ /dev/null @@ -1,32 +0,0 @@ -name: Publish documentation - -# publish the documentation on every merge to develop branch -on: - push: - branches: - - develop - paths: - - docs/mkdocs/** - - docs/examples/** - workflow_dispatch: - -# we don't want to have concurrent jobs, and we don't want to cancel running jobs to avoid broken publications -concurrency: - group: documentation - cancel-in-progress: false - -jobs: - publish_documentation: - if: github.repository == 'nlohmann/json' - runs-on: ubuntu-22.04 - steps: - - uses: actions/checkout@v3 - - - name: Install and update PlantUML - run: sudo apt-get update ; sudo apt-get install -y plantuml - - - name: Install virtual environment - run: make install_venv -C docs/mkdocs - - - name: Publish documentation - run: make publish -C docs/mkdocs diff --git a/app/jni/src/libultraship/extern/nlohmann-json/.github/workflows/ubuntu.yml b/app/jni/src/libultraship/extern/nlohmann-json/.github/workflows/ubuntu.yml deleted file mode 100644 index eff653c..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/.github/workflows/ubuntu.yml +++ /dev/null @@ -1,162 +0,0 @@ -name: Ubuntu - -on: - push: - branches: - - develop - - master - - release/* - pull_request: - workflow_dispatch: - -concurrency: - group: ${{ github.workflow }}-${{ github.ref || github.run_id }} - cancel-in-progress: true - -jobs: - ci_test_clang: - runs-on: ubuntu-latest - container: ghcr.io/nlohmann/json-ci:v2.4.0 - steps: - - uses: actions/checkout@v3 - - name: Run CMake - run: cmake -S . -B build -DJSON_CI=On - - name: Build - run: cmake --build build --target ci_test_clang - - ci_test_gcc: - runs-on: ubuntu-latest - container: ghcr.io/nlohmann/json-ci:v2.4.0 - steps: - - uses: actions/checkout@v3 - - name: Run CMake - run: cmake -S . -B build -DJSON_CI=On - - name: Build - run: cmake --build build --target ci_test_gcc - - ci_static_analysis: - runs-on: ubuntu-latest - container: ghcr.io/nlohmann/json-ci:v2.4.0 - strategy: - matrix: - target: [ci_clang_tidy, ci_cppcheck, ci_test_valgrind, ci_test_clang_sanitizer, ci_test_amalgamation, ci_clang_analyze, ci_cpplint, ci_cmake_flags, ci_single_binaries, ci_reproducible_tests, ci_non_git_tests, ci_offline_testdata, ci_infer] - steps: - - uses: actions/checkout@v3 - - name: Run CMake - run: cmake -S . -B build -DJSON_CI=On - - name: Build - run: cmake --build build --target ${{ matrix.target }} - - ci_test_single_header: - runs-on: ubuntu-latest - container: ghcr.io/nlohmann/json-ci:v2.4.0 - steps: - - uses: actions/checkout@v3 - - name: Run CMake - run: cmake -S . -B build -DJSON_CI=On - - name: Build - run: cmake --build build --target ci_test_single_header - - ci_cmake_options: - runs-on: ubuntu-latest - container: ghcr.io/nlohmann/json-ci:v2.4.0 - strategy: - matrix: - target: [ci_test_diagnostics, ci_test_noexceptions, ci_test_noimplicitconversions, ci_test_legacycomparison, ci_test_noglobaludls] - steps: - - uses: actions/checkout@v3 - - name: Run CMake - run: cmake -S . -B build -DJSON_CI=On - - name: Build - run: cmake --build build --target ${{ matrix.target }} - - ci_test_coverage: - runs-on: ubuntu-latest - container: ghcr.io/nlohmann/json-ci:v2.4.0 - steps: - - uses: actions/checkout@v3 - - name: Run CMake - run: cmake -S . -B build -DJSON_CI=On - - name: Build - run: cmake --build build --target ci_test_coverage - - name: Archive coverage report - uses: actions/upload-artifact@v3 - with: - name: code-coverage-report - path: ${{ github.workspace }}/build/html - - name: Publish report to Coveralls - uses: coverallsapp/github-action@master - with: - github-token: ${{ secrets.GITHUB_TOKEN }} - path-to-lcov: ${{ github.workspace }}/build/json.info.filtered.noexcept - - ci_test_compilers: - runs-on: ubuntu-latest - container: ghcr.io/nlohmann/json-ci:v2.4.0 - strategy: - matrix: - compiler: [g++-4.8, g++-4.9, g++-5, g++-6, g++-7, g++-8, g++-9, g++-10, g++-11, clang++-3.5, clang++-3.6, clang++-3.7, clang++-3.8, clang++-3.9, clang++-4.0, clang++-5.0, clang++-6.0, clang++-7, clang++-8, clang++-9, clang++-10, clang++-11, clang++-12, clang++-13, clang++-14] - steps: - - uses: actions/checkout@v3 - - name: Run CMake - run: cmake -S . -B build -DJSON_CI=On - - name: Build - run: cmake --build build --target ci_test_compiler_${{ matrix.compiler }} - - ci_test_standards: - runs-on: ubuntu-latest - container: ghcr.io/nlohmann/json-ci:v2.4.0 - strategy: - matrix: - standard: [11, 14, 17, 20] - compiler: [gcc, clang] - steps: - - uses: actions/checkout@v3 - - name: Run CMake - run: cmake -S . -B build -DJSON_CI=On - - name: Build - run: cmake --build build --target ci_test_${{ matrix.compiler }}_cxx${{ matrix.standard }} - - ci_cuda_example: - runs-on: ubuntu-latest - container: ghcr.io/nlohmann/json-ci:v2.4.0 - steps: - - uses: actions/checkout@v3 - - name: Run CMake - run: cmake -S . -B build -DJSON_CI=On - - name: Build - run: cmake --build build --target ci_cuda_example - - ci_icpc: - runs-on: ubuntu-latest - container: ghcr.io/nlohmann/json-ci:v2.2.0 - steps: - - uses: actions/checkout@v2 - - name: Run CMake - run: cmake -S . -B build -DJSON_CI=On - - name: Build - run: | - . /opt/intel/oneapi/setvars.sh - cmake --build build --target ci_icpc - - ci_reuse_compliance: - runs-on: ubuntu-latest - steps: - - uses: actions/checkout@v3 - - uses: actions/setup-python@v3 - - name: Install REUSE tool - run: python -m pip install reuse - - name: Run REUSE lint - run: reuse lint - - ci_test_documentation: - runs-on: ubuntu-latest - strategy: - matrix: - target: [ci_test_examples, ci_test_api_documentation] - steps: - - uses: actions/checkout@v3 - - name: Run CMake - run: cmake -S . -B build -DJSON_CI=On - - name: Build - run: cmake --build build --target ${{ matrix.target }} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/.github/workflows/windows.yml b/app/jni/src/libultraship/extern/nlohmann-json/.github/workflows/windows.yml deleted file mode 100644 index fb4b893..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/.github/workflows/windows.yml +++ /dev/null @@ -1,151 +0,0 @@ -name: Windows - -on: - push: - branches: - - develop - - master - - release/* - pull_request: - workflow_dispatch: - -concurrency: - group: ${{ github.workflow }}-${{ github.ref || github.run_id }} - cancel-in-progress: true - -jobs: - mingw: - runs-on: windows-latest - strategy: - matrix: - architecture: [x64, x86] - - steps: - - uses: actions/checkout@v3 - - name: Download MinGW 8.1.0 - run: | - $headers = @{Authorization = 'Bearer ${{ secrets.GITHUB_TOKEN }}'} - $uri = 'https://nuget.pkg.github.com/falbrechtskirchinger/download/mingw/8.1.0/mingw.8.1.0.nupkg' - Invoke-WebRequest -Uri $uri -Headers $headers -OutFile mingw.8.1.0.nupkg - - name: Uninstall MinGW - continue-on-error: true - run: choco uninstall mingw - # Based on egor-tensin/setup-mingw - - name: Install MinGW 8.1.0 - run: | - choco install mingw.8.1.0.nupkg ${{ matrix.architecture == 'x86' && '--x86' || '' }} - $prefix = "${{ matrix.architecture == 'x64' && 'x86_64-w64-mingw32' || 'i686-w64-mingw32' }}" - $mingw = "${{ matrix.architecture == 'x64' && 'mingw64' || 'mingw32' }}" - $mingw_install = Join-Path C: ProgramData chocolatey lib mingw tools install - $mingw_root = Join-Path $mingw_install $mingw - $mingw_bin = Join-Path $mingw_root bin - $mingw_lib = Join-Path $mingw_root $prefix lib - echo $mingw_bin >> $env:GITHUB_PATH - Remove-Item (Join-Path $mingw_lib 'libpthread.dll.a') - Remove-Item (Join-Path $mingw_lib 'libwinpthread.dll.a') - #- name: Set up MinGW - # uses: egor-tensin/setup-mingw@v2 - # with: - # platform: ${{ matrix.architecture }} - - name: Run CMake - run: cmake -S . -B build -G "MinGW Makefiles" -DCMAKE_BUILD_TYPE=Debug -DJSON_BuildTests=On - - name: Build - run: cmake --build build --parallel 10 - - name: Test - run: cd build ; ctest -j 10 -C Debug --output-on-failure - - msvc2019: - runs-on: windows-2019 - strategy: - matrix: - build_type: [Debug, Release] - architecture: [Win32, x64] - - steps: - - uses: actions/checkout@v3 - - name: Run CMake - run: cmake -S . -B build -G "Visual Studio 16 2019" -A ${{ matrix.architecture }} -DJSON_BuildTests=On -DCMAKE_CXX_FLAGS="/W4 /WX" - if: matrix.build_type == 'Release' - - name: Run CMake - run: cmake -S . -B build -G "Visual Studio 16 2019" -A ${{ matrix.architecture }} -DJSON_BuildTests=On -DJSON_FastTests=ON -DCMAKE_CXX_FLAGS="/W4 /WX" - if: matrix.build_type == 'Debug' - - name: Build - run: cmake --build build --config ${{ matrix.build_type }} --parallel 10 - - name: Test - run: cd build ; ctest -j 10 -C ${{ matrix.build_type }} --output-on-failure - - msvc2019_latest: - runs-on: windows-2019 - - steps: - - uses: actions/checkout@v3 - - name: Run CMake - run: cmake -S . -B build -G "Visual Studio 16 2019" -DJSON_BuildTests=On -DCMAKE_CXX_FLAGS="/permissive- /std:c++latest /utf-8 /W4 /WX" - - name: Build - run: cmake --build build --config Release --parallel 10 - - name: Test - run: cd build ; ctest -j 10 -C Release --output-on-failure - - msvc2022: - runs-on: windows-2022 - strategy: - matrix: - build_type: [Debug, Release] - architecture: [Win32, x64] - - steps: - - uses: actions/checkout@v3 - - name: Run CMake - run: cmake -S . -B build -G "Visual Studio 17 2022" -A ${{ matrix.architecture }} -DJSON_BuildTests=On -DCMAKE_CXX_FLAGS="/W4 /WX" - if: matrix.build_type == 'Release' - - name: Run CMake - run: cmake -S . -B build -G "Visual Studio 17 2022" -A ${{ matrix.architecture }} -DJSON_BuildTests=On -DJSON_FastTests=ON -DCMAKE_CXX_FLAGS="/W4 /WX" - if: matrix.build_type == 'Debug' - - name: Build - run: cmake --build build --config ${{ matrix.build_type }} --parallel 10 - - name: Test - run: cd build ; ctest -j 10 -C ${{ matrix.build_type }} --output-on-failure - - msvc2022_latest: - runs-on: windows-2022 - - steps: - - uses: actions/checkout@v3 - - name: Run CMake - run: cmake -S . -B build -G "Visual Studio 17 2022" -DJSON_BuildTests=On -DCMAKE_CXX_FLAGS="/permissive- /std:c++latest /utf-8 /W4 /WX" - - name: Build - run: cmake --build build --config Release --parallel 10 - - name: Test - run: cd build ; ctest -j 10 -C Release --output-on-failure - - clang: - runs-on: windows-2019 - strategy: - matrix: - version: [11, 12] - - steps: - - uses: actions/checkout@v3 - - name: Install Clang - run: curl -fsSL -o LLVM${{ matrix.version }}.exe https://github.com/llvm/llvm-project/releases/download/llvmorg-${{ matrix.version }}.0.0/LLVM-${{ matrix.version }}.0.0-win64.exe ; 7z x LLVM${{ matrix.version }}.exe -y -o"C:/Program Files/LLVM" - - name: Run CMake - run: cmake -S . -B build -DCMAKE_CXX_COMPILER="C:/Program Files/LLVM/bin/clang++.exe" -G"MinGW Makefiles" -DCMAKE_BUILD_TYPE=Debug -DJSON_BuildTests=On - - name: Build - run: cmake --build build --parallel 10 - - name: Test - run: cd build ; ctest -j 10 -C Debug --exclude-regex "test-unicode" --output-on-failure - - clang-cl-11: - runs-on: windows-2019 - strategy: - matrix: - architecture: [Win32, x64] - - steps: - - uses: actions/checkout@v3 - - name: Run CMake - run: cmake -S . -B build -G "Visual Studio 16 2019" -A ${{ matrix.architecture }} -T ClangCL -DJSON_BuildTests=On - - name: Build - run: cmake --build build --config Debug --parallel 10 - - name: Test - run: cd build ; ctest -j 10 -C Debug --exclude-regex "test-unicode" --output-on-failure diff --git a/app/jni/src/libultraship/extern/nlohmann-json/.gitignore b/app/jni/src/libultraship/extern/nlohmann-json/.gitignore deleted file mode 100644 index 30b62bf..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/.gitignore +++ /dev/null @@ -1,41 +0,0 @@ -*.dSYM -*.o -*.gcno -*.gcda -.DS_Store - -.wsjcpp-logs/* -.wsjcpp/* - -/.idea -/cmake-build-* - -# Visual Studio / Visual Studio Code -/.vs/ -/.vscode/ -/out/ - -# clangd cache -/.cache/ - -# build directories (vscode-cmake-tools, user-defined, ...) -/build*/ - -# fuzzers -/tests/corpus_* -/tests/parse_*_fuzzer - -# documentation -/docs/docset/docSet.dsidx -/docs/docset/JSON_for_Modern_C++.docset/ -/docs/docset/JSON_for_Modern_C++.tgz -/docs/mkdocs/docs/__pycache__/ -/docs/mkdocs/docs/examples/ -/docs/mkdocs/docs/images/json.gif -/docs/mkdocs/site/ -/docs/mkdocs/venv/ - -# serve_header -/localhost.pem -/localhost-key.pem -/serve_header.yml diff --git a/app/jni/src/libultraship/extern/nlohmann-json/.lgtm.yml b/app/jni/src/libultraship/extern/nlohmann-json/.lgtm.yml deleted file mode 100644 index b62f9fb..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/.lgtm.yml +++ /dev/null @@ -1,4 +0,0 @@ -path_classifiers: - thirdparty: - - /tools/amalgamate - - /tools/cpplint diff --git a/app/jni/src/libultraship/extern/nlohmann-json/.reuse/README.md b/app/jni/src/libultraship/extern/nlohmann-json/.reuse/README.md deleted file mode 100644 index 29c2b67..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/.reuse/README.md +++ /dev/null @@ -1,7 +0,0 @@ -# REUSE Software - -This directory contains supporting files to make the project compliant with the REUSE specification. - -The root `Makefile` contains a target `reuse` that updates copyright headers and checks for compliance. - -See for more information. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/.reuse/dep5 b/app/jni/src/libultraship/extern/nlohmann-json/.reuse/dep5 deleted file mode 100644 index 610b876..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/.reuse/dep5 +++ /dev/null @@ -1,36 +0,0 @@ -Format: https://www.debian.org/doc/packaging-manuals/copyright-format/1.0/ -Upstream-Name: json -Upstream-Contact: Niels Lohmann -Source: https://github.com/nlohmann/json - -Files: * -Copyright: 2013-2022 Niels Lohmann -License: MIT - -Files: tests/thirdparty/doctest/* -Copyright: 2016-2021 Viktor Kirilov -License: MIT - -Files: tests/thirdparty/fifo_map/* -Copyright: 2015-2017 Niels Lohmann -License: MIT - -Files: tests/thirdparty/Fuzzer/* -Copyright: 2003-2022, LLVM Project. -License: Apache-2.0 - -Files: tests/thirdparty/imapdl/* -Copyright: 2017 Georg Sauthoff -License: GPL-3.0-only - -Files: tools/amalgamate/* -Copyright: 2012 Erik Edlund -License: BSD-3-Clause - -Files: tools/cpplint/* -Copyright: 2009 Google Inc. All rights reserved. -License: BSD-3-Clause - -Files: tools/gdb_pretty_printer -Copyright: 2020 Hannes Domani -License: MIT diff --git a/app/jni/src/libultraship/extern/nlohmann-json/.reuse/templates/json.jinja2 b/app/jni/src/libultraship/extern/nlohmann-json/.reuse/templates/json.jinja2 deleted file mode 100644 index 4abf481..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/.reuse/templates/json.jinja2 +++ /dev/null @@ -1,11 +0,0 @@ - __ _____ _____ _____ - __| | __| | | | JSON for Modern C++ -| | |__ | | | | | | version 3.11.2 -|_____|_____|_____|_|___| https://github.com/nlohmann/json - -{% for copyright_line in copyright_lines %} -{{ copyright_line }} -{% endfor %} -{% for expression in spdx_expressions %} -SPDX-License-Identifier: {{ expression }} -{% endfor %} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/.reuse/templates/json_support.jinja2 b/app/jni/src/libultraship/extern/nlohmann-json/.reuse/templates/json_support.jinja2 deleted file mode 100644 index 1fab99f..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/.reuse/templates/json_support.jinja2 +++ /dev/null @@ -1,11 +0,0 @@ - __ _____ _____ _____ - __| | __| | | | JSON for Modern C++ (supporting code) -| | |__ | | | | | | version 3.11.2 -|_____|_____|_____|_|___| https://github.com/nlohmann/json - -{% for copyright_line in copyright_lines %} -{{ copyright_line }} -{% endfor %} -{% for expression in spdx_expressions %} -SPDX-License-Identifier: {{ expression }} -{% endfor %} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/CITATION.cff b/app/jni/src/libultraship/extern/nlohmann-json/CITATION.cff deleted file mode 100644 index cc9d702..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/CITATION.cff +++ /dev/null @@ -1,14 +0,0 @@ -cff-version: 1.2.0 -message: "If you use this software, please cite it as below." -authors: - - family-names: Lohmann - given-names: Niels - orcid: https://orcid.org/0000-0001-9037-795X - email: mail@nlohmann.me - website: https://nlohmann.me -title: "JSON for Modern C++" -version: 3.11.2 -date-released: 2022-08-12 -license: MIT -repository-code: "https://github.com/nlohmann" -url: https://json.nlohmann.me diff --git a/app/jni/src/libultraship/extern/nlohmann-json/CMakeLists.txt b/app/jni/src/libultraship/extern/nlohmann-json/CMakeLists.txt deleted file mode 100644 index d88feb5..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/CMakeLists.txt +++ /dev/null @@ -1,209 +0,0 @@ -cmake_minimum_required(VERSION 3.1) - -## -## PROJECT -## name and version -## -project(nlohmann_json VERSION 3.11.2 LANGUAGES CXX) - -## -## MAIN_PROJECT CHECK -## determine if nlohmann_json is built as a subproject (using add_subdirectory) or if it is the main project -## -set(MAIN_PROJECT OFF) -if (CMAKE_CURRENT_SOURCE_DIR STREQUAL CMAKE_SOURCE_DIR) - set(MAIN_PROJECT ON) -endif() - -## -## INCLUDE -## -## -set(CMAKE_MODULE_PATH ${CMAKE_CURRENT_SOURCE_DIR}/cmake ${CMAKE_MODULE_PATH}) -include(ExternalProject) - -## -## OPTIONS -## - -if (POLICY CMP0077) - # Allow CMake 3.13+ to override options when using FetchContent / add_subdirectory. - cmake_policy(SET CMP0077 NEW) -endif () - -# VERSION_GREATER_EQUAL is not available in CMake 3.1 -if(${MAIN_PROJECT} AND (${CMAKE_VERSION} VERSION_EQUAL 3.13 OR ${CMAKE_VERSION} VERSION_GREATER 3.13)) - set(JSON_BuildTests_INIT ON) -else() - set(JSON_BuildTests_INIT OFF) -endif() -option(JSON_BuildTests "Build the unit tests when BUILD_TESTING is enabled." ${JSON_BuildTests_INIT}) -option(JSON_CI "Enable CI build targets." OFF) -option(JSON_Diagnostics "Use extended diagnostic messages." OFF) -option(JSON_GlobalUDLs "Place use-defined string literals in the global namespace." ON) -option(JSON_ImplicitConversions "Enable implicit conversions." ON) -option(JSON_DisableEnumSerialization "Disable default integer enum serialization." OFF) -option(JSON_LegacyDiscardedValueComparison "Enable legacy discarded value comparison." OFF) -option(JSON_Install "Install CMake targets during install step." ${MAIN_PROJECT}) -option(JSON_MultipleHeaders "Use non-amalgamated version of the library." ON) -option(JSON_SystemInclude "Include as system headers (skip for clang-tidy)." OFF) - -if (JSON_CI) - include(ci) -endif () - -## -## CONFIGURATION -## -include(GNUInstallDirs) - -set(NLOHMANN_JSON_TARGET_NAME ${PROJECT_NAME}) -set(NLOHMANN_JSON_CONFIG_INSTALL_DIR "${CMAKE_INSTALL_DATADIR}/cmake/${PROJECT_NAME}" CACHE INTERNAL "") -set(NLOHMANN_JSON_INCLUDE_INSTALL_DIR "${CMAKE_INSTALL_INCLUDEDIR}") -set(NLOHMANN_JSON_TARGETS_EXPORT_NAME "${PROJECT_NAME}Targets") -set(NLOHMANN_JSON_CMAKE_CONFIG_TEMPLATE "cmake/config.cmake.in") -set(NLOHMANN_JSON_CMAKE_CONFIG_DIR "${CMAKE_CURRENT_BINARY_DIR}") -set(NLOHMANN_JSON_CMAKE_VERSION_CONFIG_FILE "${NLOHMANN_JSON_CMAKE_CONFIG_DIR}/${PROJECT_NAME}ConfigVersion.cmake") -set(NLOHMANN_JSON_CMAKE_PROJECT_CONFIG_FILE "${NLOHMANN_JSON_CMAKE_CONFIG_DIR}/${PROJECT_NAME}Config.cmake") -set(NLOHMANN_JSON_CMAKE_PROJECT_TARGETS_FILE "${NLOHMANN_JSON_CMAKE_CONFIG_DIR}/${PROJECT_NAME}Targets.cmake") -set(NLOHMANN_JSON_PKGCONFIG_INSTALL_DIR "${CMAKE_INSTALL_DATADIR}/pkgconfig") - -if (JSON_MultipleHeaders) - set(NLOHMANN_JSON_INCLUDE_BUILD_DIR "${PROJECT_SOURCE_DIR}/include/") - message(STATUS "Using the multi-header code from ${NLOHMANN_JSON_INCLUDE_BUILD_DIR}") -else() - set(NLOHMANN_JSON_INCLUDE_BUILD_DIR "${PROJECT_SOURCE_DIR}/single_include/") - message(STATUS "Using the single-header code from ${NLOHMANN_JSON_INCLUDE_BUILD_DIR}") -endif() - -if (NOT JSON_ImplicitConversions) - message(STATUS "Implicit conversions are disabled") -endif() - -if (JSON_DisableEnumSerialization) - message(STATUS "Enum integer serialization is disabled") -endif() - -if (JSON_LegacyDiscardedValueComparison) - message(STATUS "Legacy discarded value comparison enabled") -endif() - -if (JSON_Diagnostics) - message(STATUS "Diagnostics enabled") -endif() - -if (JSON_SystemInclude) - set(NLOHMANN_JSON_SYSTEM_INCLUDE "SYSTEM") -endif() - -## -## TARGET -## create target and add include path -## -add_library(${NLOHMANN_JSON_TARGET_NAME} INTERFACE) -add_library(${PROJECT_NAME}::${NLOHMANN_JSON_TARGET_NAME} ALIAS ${NLOHMANN_JSON_TARGET_NAME}) -if (${CMAKE_VERSION} VERSION_LESS "3.8.0") - target_compile_features(${NLOHMANN_JSON_TARGET_NAME} INTERFACE cxx_range_for) -else() - target_compile_features(${NLOHMANN_JSON_TARGET_NAME} INTERFACE cxx_std_11) -endif() - -target_compile_definitions( - ${NLOHMANN_JSON_TARGET_NAME} - INTERFACE - $<$>:JSON_USE_GLOBAL_UDLS=0> - $<$>:JSON_USE_IMPLICIT_CONVERSIONS=0> - $<$:JSON_DISABLE_ENUM_SERIALIZATION=1> - $<$:JSON_DIAGNOSTICS=1> - $<$:JSON_USE_LEGACY_DISCARDED_VALUE_COMPARISON=1> -) - -target_include_directories( - ${NLOHMANN_JSON_TARGET_NAME} - ${NLOHMANN_JSON_SYSTEM_INCLUDE} INTERFACE - $ - $ -) - -## add debug view definition file for msvc (natvis) -if (MSVC) - set(NLOHMANN_ADD_NATVIS TRUE) - set(NLOHMANN_NATVIS_FILE "nlohmann_json.natvis") - target_sources( - ${NLOHMANN_JSON_TARGET_NAME} - INTERFACE - $ - $ - ) -endif() - -# Install a pkg-config file, so other tools can find this. -CONFIGURE_FILE( - "${CMAKE_CURRENT_SOURCE_DIR}/cmake/pkg-config.pc.in" - "${CMAKE_CURRENT_BINARY_DIR}/${PROJECT_NAME}.pc" -) - -## -## TESTS -## create and configure the unit test target -## -if (JSON_BuildTests) - include(CTest) - enable_testing() - add_subdirectory(tests) -endif() - -## -## INSTALL -## install header files, generate and install cmake config files for find_package() -## -include(CMakePackageConfigHelpers) -# use a custom package version config file instead of -# write_basic_package_version_file to ensure that it's architecture-independent -# https://github.com/nlohmann/json/issues/1697 -configure_file( - "cmake/nlohmann_jsonConfigVersion.cmake.in" - ${NLOHMANN_JSON_CMAKE_VERSION_CONFIG_FILE} - @ONLY -) -configure_file( - ${NLOHMANN_JSON_CMAKE_CONFIG_TEMPLATE} - ${NLOHMANN_JSON_CMAKE_PROJECT_CONFIG_FILE} - @ONLY -) - -if(JSON_Install) - install( - DIRECTORY ${NLOHMANN_JSON_INCLUDE_BUILD_DIR} - DESTINATION ${NLOHMANN_JSON_INCLUDE_INSTALL_DIR} - ) - install( - FILES ${NLOHMANN_JSON_CMAKE_PROJECT_CONFIG_FILE} ${NLOHMANN_JSON_CMAKE_VERSION_CONFIG_FILE} - DESTINATION ${NLOHMANN_JSON_CONFIG_INSTALL_DIR} - ) - if (NLOHMANN_ADD_NATVIS) - install( - FILES ${NLOHMANN_NATVIS_FILE} - DESTINATION . - ) - endif() - export( - TARGETS ${NLOHMANN_JSON_TARGET_NAME} - NAMESPACE ${PROJECT_NAME}:: - FILE ${NLOHMANN_JSON_CMAKE_PROJECT_TARGETS_FILE} - ) - install( - TARGETS ${NLOHMANN_JSON_TARGET_NAME} - EXPORT ${NLOHMANN_JSON_TARGETS_EXPORT_NAME} - INCLUDES DESTINATION ${NLOHMANN_JSON_INCLUDE_INSTALL_DIR} - ) - install( - EXPORT ${NLOHMANN_JSON_TARGETS_EXPORT_NAME} - NAMESPACE ${PROJECT_NAME}:: - DESTINATION ${NLOHMANN_JSON_CONFIG_INSTALL_DIR} - ) - install( - FILES "${CMAKE_CURRENT_BINARY_DIR}/${PROJECT_NAME}.pc" - DESTINATION ${NLOHMANN_JSON_PKGCONFIG_INSTALL_DIR} - ) -endif() diff --git a/app/jni/src/libultraship/extern/nlohmann-json/ChangeLog.md b/app/jni/src/libultraship/extern/nlohmann-json/ChangeLog.md deleted file mode 100644 index 656d68b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/ChangeLog.md +++ /dev/null @@ -1,2943 +0,0 @@ -# Changelog -All notable changes to this project will be documented in this file. This project adheres to [Semantic Versioning](http://semver.org/). - -## [3.11.2](https://github.com/nlohmann/json/releases/tag/3.11.2) (2022-08-12) - -[Full Changelog](https://github.com/nlohmann/json/compare/v3.11.1...3.11.2) - -- MSVC natvis visualizer does not work after introduction of inline ABI namespace [\#3696](https://github.com/nlohmann/json/issues/3696) -- The use of parenthesis gives compilation errors in some situations [\#3682](https://github.com/nlohmann/json/issues/3682) -- extern from/to\_json result in linker error [\#3657](https://github.com/nlohmann/json/issues/3657) -- json\_fwd.hpp no longer standalone [\#3656](https://github.com/nlohmann/json/issues/3656) -- regression: `.value` is compilation error. [\#3655](https://github.com/nlohmann/json/issues/3655) -- Regression: no match for 'operator!=' comparing json\_pointer and const char \*/string\_t [\#3654](https://github.com/nlohmann/json/issues/3654) -- Regression: call to member function 'value' is ambiguous [\#3652](https://github.com/nlohmann/json/issues/3652) -- macOS 10.15 Actions runner image deprecation [\#3612](https://github.com/nlohmann/json/issues/3612) - -- generate\_natvis.py: validate version number; cleanup [\#3698](https://github.com/nlohmann/json/pull/3698) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Add Python script for generating Natvis file and update file for 3.11.2 [\#3697](https://github.com/nlohmann/json/pull/3697) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- fix typo in json\_pointer.md [\#3692](https://github.com/nlohmann/json/pull/3692) ([eltociear](https://github.com/eltociear)) -- Add amalgamated json-fwd.hpp to release [\#3687](https://github.com/nlohmann/json/pull/3687) ([nlohmann](https://github.com/nlohmann)) -- Documentation updates for 3.11.2 [\#3686](https://github.com/nlohmann/json/pull/3686) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Make json\_pointer usable as map key \(again\) [\#3685](https://github.com/nlohmann/json/pull/3685) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Deprecate json\_pointer/string\_t comparisons [\#3684](https://github.com/nlohmann/json/pull/3684) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Restructure inline namespace and allow version component to be disabled [\#3683](https://github.com/nlohmann/json/pull/3683) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Properly constrain non-string json\_pointer overloads [\#3681](https://github.com/nlohmann/json/pull/3681) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Amalgamate the forward declaration header [\#3679](https://github.com/nlohmann/json/pull/3679) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Fix 'const' qualifier on bool& has no effect [\#3678](https://github.com/nlohmann/json/pull/3678) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Fix whitespace in workflow files [\#3675](https://github.com/nlohmann/json/pull/3675) ([nlohmann](https://github.com/nlohmann)) -- Attempt to fix labeler permissions [\#3674](https://github.com/nlohmann/json/pull/3674) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Refine 'Publish documentation' workflow [\#3673](https://github.com/nlohmann/json/pull/3673) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Documentation change [\#3672](https://github.com/nlohmann/json/pull/3672) ([nlohmann](https://github.com/nlohmann)) -- Add labeler action [\#3671](https://github.com/nlohmann/json/pull/3671) ([nlohmann](https://github.com/nlohmann)) -- Complete contributor list [\#3670](https://github.com/nlohmann/json/pull/3670) ([nlohmann](https://github.com/nlohmann)) -- Add json\_pointer/string\_t equality comparison operators [\#3664](https://github.com/nlohmann/json/pull/3664) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Reimplement value\(\) access functions [\#3663](https://github.com/nlohmann/json/pull/3663) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Complete contributor list [\#3662](https://github.com/nlohmann/json/pull/3662) ([nlohmann](https://github.com/nlohmann)) -- Adjust naming of GitHub action jobs [\#3661](https://github.com/nlohmann/json/pull/3661) ([nlohmann](https://github.com/nlohmann)) -- Publish documentation on push to develop branch [\#3660](https://github.com/nlohmann/json/pull/3660) ([nlohmann](https://github.com/nlohmann)) -- Add Discord badge to README [\#3651](https://github.com/nlohmann/json/pull/3651) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Miscellaneous small fixes [\#3643](https://github.com/nlohmann/json/pull/3643) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Minor BJData fixes [\#3637](https://github.com/nlohmann/json/pull/3637) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Update CI [\#3626](https://github.com/nlohmann/json/pull/3626) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) - -## [v3.11.1](https://github.com/nlohmann/json/releases/tag/v3.11.1) (2022-08-01) - -[Full Changelog](https://github.com/nlohmann/json/compare/v3.11.0...v3.11.1) - -- Regression: no matching literal operator for call to 'operator""\_json' [\#3645](https://github.com/nlohmann/json/issues/3645) -- \_json operator""\(\) [\#3644](https://github.com/nlohmann/json/issues/3644) - -- Fix global UDLs [\#3646](https://github.com/nlohmann/json/pull/3646) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) - -## [v3.11.0](https://github.com/nlohmann/json/releases/tag/v3.11.0) (2022-08-01) - -[Full Changelog](https://github.com/nlohmann/json/compare/v3.10.5...v3.11.0) - -- ICPC: warning \#1098: the qualifier on this friend declaration is ignored [\#3632](https://github.com/nlohmann/json/issues/3632) -- Starting with 3.10.4, just adding `\#include json.hpp` causes compile error: `overload resolution selected deleted operator '=' [\#3620](https://github.com/nlohmann/json/issues/3620) -- xwidgets doesn't compile with version \>3.10.3 [\#3602](https://github.com/nlohmann/json/issues/3602) -- json\_pointer\_\_pop\_back.cpp example does not compile [\#3600](https://github.com/nlohmann/json/issues/3600) -- nlohmann::json::array 'push\_back' is ambiguous [\#3589](https://github.com/nlohmann/json/issues/3589) -- Multiple versions causing conflict [\#3588](https://github.com/nlohmann/json/issues/3588) -- ERROR: ThreadSanitizer: SEGV on unknown address [\#3584](https://github.com/nlohmann/json/issues/3584) -- unicode4 test consistently fails on RISC-V hardware [\#3579](https://github.com/nlohmann/json/issues/3579) -- sax\_parse\(iterator, json\_sax\_t \*\) string callback clobbers spaces [\#3574](https://github.com/nlohmann/json/issues/3574) -- Nlohmann JSON Parse crash with raylib-cpp [\#3570](https://github.com/nlohmann/json/issues/3570) -- ordered\_json doesn't accept keys of types other than string\_t \(e.g., string\_view\) [\#3558](https://github.com/nlohmann/json/issues/3558) -- turning an object into an array [\#3547](https://github.com/nlohmann/json/issues/3547) -- json:parse\_bjdata\_fuzzer: ASSERT: ref\_stack.back\(\)-\>is\_array\(\) [\#3541](https://github.com/nlohmann/json/issues/3541) -- Warning about potential null dereference in GCC 12.1 \(Fedora 36\) [\#3525](https://github.com/nlohmann/json/issues/3525) -- Enable 32bit unit test in CI [\#3524](https://github.com/nlohmann/json/issues/3524) -- Error when roundtripping BJData [\#3519](https://github.com/nlohmann/json/issues/3519) -- ASSERT error while parsing BJData [\#3513](https://github.com/nlohmann/json/issues/3513) -- An exception occurred when sending a string with double quotes [\#3504](https://github.com/nlohmann/json/issues/3504) -- Binary reader for BJData creates incorrect SAX events [\#3503](https://github.com/nlohmann/json/issues/3503) -- It can't support "nan", "inf", "-inf" for float type [\#3494](https://github.com/nlohmann/json/issues/3494) -- ASAN error while parsing BJData \(Heap-buffer-overflow READ 1\) [\#3492](https://github.com/nlohmann/json/issues/3492) -- UBSAN error while parsing BJData \(Null-dereference\) [\#3491](https://github.com/nlohmann/json/issues/3491) -- UBSAN error while parsing BJData \(Invalid-bool-value\) [\#3490](https://github.com/nlohmann/json/issues/3490) -- json:parse\_bjdata\_fuzzer reaches assertion [\#3475](https://github.com/nlohmann/json/issues/3475) -- Compilation with -fmodules-ts and use inside of a module [\#3472](https://github.com/nlohmann/json/issues/3472) -- json.exception.parse\_error.101 only occurs outside of IDE [\#3467](https://github.com/nlohmann/json/issues/3467) -- json:parse\_bjdata\_fuzzer reaches assertion [\#3461](https://github.com/nlohmann/json/issues/3461) -- NLOHMANN\_DEFINE\_TYPE\_NON\_INTRUSIVE\_WITH\_DEFAULT can not parse { "key" : null} [\#3458](https://github.com/nlohmann/json/issues/3458) -- Unable to compile when using Microsoft's \_CRTDBG [\#3457](https://github.com/nlohmann/json/issues/3457) -- Compilation errors when including `` and using `--std=c++17` or above \(MinGW/Win10\) [\#3449](https://github.com/nlohmann/json/issues/3449) -- Weird things on for statement [\#3447](https://github.com/nlohmann/json/issues/3447) -- Parsing error when there is a json string within a Json [\#3445](https://github.com/nlohmann/json/issues/3445) -- ordered\_json vs json types comparison [\#3443](https://github.com/nlohmann/json/issues/3443) -- Error occurred when converting nlohmann::json to std::any [\#3428](https://github.com/nlohmann/json/issues/3428) -- I was forced to report an assertion error when copying an array of strings [\#3419](https://github.com/nlohmann/json/issues/3419) -- About Serialization Error invalid UTF-8 byte at index [\#3414](https://github.com/nlohmann/json/issues/3414) -- Comparison of NaN differs between json and float [\#3409](https://github.com/nlohmann/json/issues/3409) -- when i use it in C++ sserver,it it constantly show that fatal error: adl\_serializer.hpp: No such file or directory [\#3404](https://github.com/nlohmann/json/issues/3404) -- parse error [\#3403](https://github.com/nlohmann/json/issues/3403) -- CMake script MAIN\_PROJECT always OFF [\#3390](https://github.com/nlohmann/json/issues/3390) -- Parser unable to handle large floating point numbers [\#3389](https://github.com/nlohmann/json/issues/3389) -- Compilation error if json\_pointer is used with alternative string type [\#3388](https://github.com/nlohmann/json/issues/3388) -- Unit tests conversions & items fail to build \(Clang \<4.0/C++14 only\) [\#3384](https://github.com/nlohmann/json/issues/3384) -- Regression test for \#3070 is not being run and fails when enabled [\#3377](https://github.com/nlohmann/json/issues/3377) -- Refactor unit tests to use more convenient doctest assertion macros [\#3365](https://github.com/nlohmann/json/issues/3365) -- An json.h issue reported in a static code analyzer [\#3361](https://github.com/nlohmann/json/issues/3361) -- Mixing different JSON\_DIAGNOSTICS settings in separately compiled units leads to core [\#3360](https://github.com/nlohmann/json/issues/3360) -- json::out\_of\_range exception matches against lot of others while testing [\#3352](https://github.com/nlohmann/json/issues/3352) -- use mipsel-openwrt-linux-g++ -std=c++11 to compile, it has some errors "error: 'snprintf' is not a member of 'std'" [\#3349](https://github.com/nlohmann/json/issues/3349) -- Add proper issue templates [\#3348](https://github.com/nlohmann/json/issues/3348) -- switch from json to ordered\_json [\#3343](https://github.com/nlohmann/json/issues/3343) -- Json dump use to compilation errors [\#3339](https://github.com/nlohmann/json/issues/3339) -- Ambiguous conversion from nlohmann::basic\_json\<\> to custom class. [\#3333](https://github.com/nlohmann/json/issues/3333) -- Iterator doesn't satisfy std::incrementable because post-increment may change constness [\#3331](https://github.com/nlohmann/json/issues/3331) -- Inconsistent handling of floating point numbers after parse\(\) [\#3329](https://github.com/nlohmann/json/issues/3329) -- Documentation for `ordered_json` should show proper use of the `parse()` function. [\#3325](https://github.com/nlohmann/json/issues/3325) -- "type must be boolean, but is object" error thrown on non-boolean object [\#3319](https://github.com/nlohmann/json/issues/3319) -- Incomplete Type in request parms [\#3318](https://github.com/nlohmann/json/issues/3318) -- 小米 MIX4 MIUI13 bug [\#3316](https://github.com/nlohmann/json/issues/3316) -- json.exception.parse\_error.101 when parsing data received over a socket [\#3313](https://github.com/nlohmann/json/issues/3313) -- Parse to custom class from unordered\_json breaks on G++11.2.0 with C++20 [\#3312](https://github.com/nlohmann/json/issues/3312) -- try to assign dumped string to a class member varible [\#3300](https://github.com/nlohmann/json/issues/3300) -- includedir in pkgconfig is error if install\_headers\(\) has subdir argument. [\#3284](https://github.com/nlohmann/json/issues/3284) -- SHA-256 sum of json-3.10.5.tar.xz changes over time \(but not the content itself\) [\#3281](https://github.com/nlohmann/json/issues/3281) -- items\(\) method does not follow order of json message [\#3278](https://github.com/nlohmann/json/issues/3278) -- Perplexing template deduction failure serialising a 3rd party type using base class [\#3267](https://github.com/nlohmann/json/issues/3267) -- json.hpp 'isfinite' is not a member of 'std' also isinf; snprintf; stoull and to\_string members of std [\#3263](https://github.com/nlohmann/json/issues/3263) -- JSON build fails for C++ cmake [\#3256](https://github.com/nlohmann/json/issues/3256) -- Unexpected implicit conversion [\#3254](https://github.com/nlohmann/json/issues/3254) -- Add a function that checks for valid json in a C++ string [\#3245](https://github.com/nlohmann/json/issues/3245) -- Replace use of standard IO from error handling [\#3239](https://github.com/nlohmann/json/issues/3239) -- Use Catch for unit tests [\#3232](https://github.com/nlohmann/json/issues/3232) -- Exception thrown during initialization causes a memory leak [\#3215](https://github.com/nlohmann/json/issues/3215) -- Tests failing when compiling with c++20 [\#3207](https://github.com/nlohmann/json/issues/3207) -- ambiguous regression [\#3204](https://github.com/nlohmann/json/issues/3204) -- Deserialization: if class is\_constructible from std::string wrong from\_json overload is being selected, compilation failed [\#3171](https://github.com/nlohmann/json/issues/3171) -- 'clang++ ./json.hpp' with no usage: Compiler syntax problem in clang 3.7.0 \(tizen :/ \) [\#3153](https://github.com/nlohmann/json/issues/3153) -- build failure on upcoming gcc-12: test/src/unit-regression1.cpp:392:22: error: ambiguous overload for 'operator=' [\#3138](https://github.com/nlohmann/json/issues/3138) -- Applying JSON patch creates parent object [\#3134](https://github.com/nlohmann/json/issues/3134) -- Iterators cannot be used with range-v3 [\#3130](https://github.com/nlohmann/json/issues/3130) -- std::shared\_ptr\ == nlohmann::json compiles, which seem undesirable [\#3026](https://github.com/nlohmann/json/issues/3026) -- Error in test\download\_test\_data.vcxproj custom build step when compiling with Visual Studio 2019 16.7.7 msbuild on Windows 10 [\#2593](https://github.com/nlohmann/json/issues/2593) -- Consider putting the user-defined literals in a namespace [\#1682](https://github.com/nlohmann/json/issues/1682) -- Using versioned namespaces [\#1539](https://github.com/nlohmann/json/issues/1539) -- How can I use std::string\_view as the json\_key to "operator \[\]" ? [\#1529](https://github.com/nlohmann/json/issues/1529) -- serialize std::variant\<...\> [\#1261](https://github.com/nlohmann/json/issues/1261) - -- Prepare 3.11.0 release [\#3635](https://github.com/nlohmann/json/pull/3635) ([nlohmann](https://github.com/nlohmann)) -- Fix warning [\#3634](https://github.com/nlohmann/json/pull/3634) ([nlohmann](https://github.com/nlohmann)) -- Add license header to new files [\#3633](https://github.com/nlohmann/json/pull/3633) ([nlohmann](https://github.com/nlohmann)) -- Add a unit test including windows.h [\#3631](https://github.com/nlohmann/json/pull/3631) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Fixed latest build error in msvc platform [\#3630](https://github.com/nlohmann/json/pull/3630) ([KsaNL](https://github.com/KsaNL)) -- Add regression tests for \#3204 and \#3333 [\#3629](https://github.com/nlohmann/json/pull/3629) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Fix patch::add creating nonexistent parents [\#3628](https://github.com/nlohmann/json/pull/3628) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Adjust JSON Pointer examples [\#3622](https://github.com/nlohmann/json/pull/3622) ([nlohmann](https://github.com/nlohmann)) -- Disable exceptions on ICPC [\#3621](https://github.com/nlohmann/json/pull/3621) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- build: install .pc and .cmake files to share/ [\#3619](https://github.com/nlohmann/json/pull/3619) ([Tachi107](https://github.com/Tachi107)) -- Fix MinGW CI failures [\#3618](https://github.com/nlohmann/json/pull/3618) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Fix Unicode test timeout \(for real this time!\) [\#3614](https://github.com/nlohmann/json/pull/3614) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Use 'concurrency' in GitHub workflows [\#3610](https://github.com/nlohmann/json/pull/3610) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Use swap\(\) by ADL [\#3609](https://github.com/nlohmann/json/pull/3609) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Move UDLs out of the global namespace [\#3605](https://github.com/nlohmann/json/pull/3605) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Re-add value\_type detection to distinguish string types [\#3604](https://github.com/nlohmann/json/pull/3604) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Add operator\<\<\(json\_pointer\) [\#3601](https://github.com/nlohmann/json/pull/3601) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Add documentation for comparing json and ordered\_json [\#3599](https://github.com/nlohmann/json/pull/3599) ([nlohmann](https://github.com/nlohmann)) -- Clean up after \#3581 [\#3596](https://github.com/nlohmann/json/pull/3596) ([nlohmann](https://github.com/nlohmann)) -- Add assertion if nullptr is passed to parse function [\#3593](https://github.com/nlohmann/json/pull/3593) ([nlohmann](https://github.com/nlohmann)) -- Minor documentation fixes [\#3592](https://github.com/nlohmann/json/pull/3592) ([nlohmann](https://github.com/nlohmann)) -- Add versioned, ABI-tagged inline namespace and namespace macros [\#3590](https://github.com/nlohmann/json/pull/3590) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Add badge for https://repology.org/project/nlohmann-json/versions [\#3586](https://github.com/nlohmann/json/pull/3586) ([nlohmann](https://github.com/nlohmann)) -- Add error message if test suite cannot be found [\#3585](https://github.com/nlohmann/json/pull/3585) ([nlohmann](https://github.com/nlohmann)) -- add patch\_inplace function [\#3581](https://github.com/nlohmann/json/pull/3581) ([wolfv](https://github.com/wolfv)) -- Enable overriding test properties and set Unicode test timeouts [\#3580](https://github.com/nlohmann/json/pull/3580) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Ignore output directory [\#3572](https://github.com/nlohmann/json/pull/3572) ([NN---](https://github.com/NN---)) -- Optimize output vector adapter write [\#3569](https://github.com/nlohmann/json/pull/3569) ([romainreignier](https://github.com/romainreignier)) -- Add overloads for more key types to ordered\_map and fix ordered\_map::erase\(first, last\) with first == last [\#3564](https://github.com/nlohmann/json/pull/3564) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Make certain usage patterns more prominent in the README [\#3557](https://github.com/nlohmann/json/pull/3557) ([jez](https://github.com/jez)) -- CI: fix "JSON\_MultipleHeaders" option spelling [\#3555](https://github.com/nlohmann/json/pull/3555) ([karzhenkov](https://github.com/karzhenkov)) -- More documentation updates for 3.11.0 [\#3553](https://github.com/nlohmann/json/pull/3553) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Use DOCTEST\_\* compiler macros and suppress pragmas warning [\#3550](https://github.com/nlohmann/json/pull/3550) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Add unit test to make sure iterator\_input\_adapter advances iterators correctly [\#3548](https://github.com/nlohmann/json/pull/3548) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Use REUSE framework [\#3546](https://github.com/nlohmann/json/pull/3546) ([nlohmann](https://github.com/nlohmann)) -- Use `std::iterator_traits` to extract `iterator_category` [\#3544](https://github.com/nlohmann/json/pull/3544) ([Mike-Leo-Smith](https://github.com/Mike-Leo-Smith)) -- BJData dimension length can not be string\_t::npos, fix \#3541 [\#3543](https://github.com/nlohmann/json/pull/3543) ([fangq](https://github.com/fangq)) -- Allow disabling default enum conversions [\#3536](https://github.com/nlohmann/json/pull/3536) ([zxey](https://github.com/zxey)) -- Add to\_json\(\) for std::vector\::reference [\#3534](https://github.com/nlohmann/json/pull/3534) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- CI: Enable 32bit unit test \(3\) [\#3532](https://github.com/nlohmann/json/pull/3532) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Use new CI image [\#3528](https://github.com/nlohmann/json/pull/3528) ([nlohmann](https://github.com/nlohmann)) -- Fix ndarray dimension signedness, fix ndarray length overflow \(2\); add 32bit unit test [\#3523](https://github.com/nlohmann/json/pull/3523) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Small documentation fixes [\#3520](https://github.com/nlohmann/json/pull/3520) ([nlohmann](https://github.com/nlohmann)) -- Add assertion to converting constructor [\#3517](https://github.com/nlohmann/json/pull/3517) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- CI: Remove -Wstrict-overflow [\#3516](https://github.com/nlohmann/json/pull/3516) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Fix nlohmann/json\#3513, explain is\_ndarray flag [\#3514](https://github.com/nlohmann/json/pull/3514) ([fangq](https://github.com/fangq)) -- Prevent ndarray size vector from recursive use, fix nlohmann/json\#3503 [\#3505](https://github.com/nlohmann/json/pull/3505) ([fangq](https://github.com/fangq)) -- prevent ndarray dimension vector from recusive array, nlohmann/json\#3500 [\#3502](https://github.com/nlohmann/json/pull/3502) ([fangq](https://github.com/fangq)) -- Discard optimized containers with negative counts in UBJSON/BJData \(\#3491,\#3492,\#3490\) [\#3500](https://github.com/nlohmann/json/pull/3500) ([fangq](https://github.com/fangq)) -- Update json.hpp [\#3499](https://github.com/nlohmann/json/pull/3499) ([ivanovmp](https://github.com/ivanovmp)) -- Add assertion for invariant in SAX-DOM parser [\#3498](https://github.com/nlohmann/json/pull/3498) ([nlohmann](https://github.com/nlohmann)) -- Add more macOS builders [\#3485](https://github.com/nlohmann/json/pull/3485) ([nlohmann](https://github.com/nlohmann)) -- change bjdata ndarray flag to detect negative size, as part of \#3475 [\#3479](https://github.com/nlohmann/json/pull/3479) ([fangq](https://github.com/fangq)) -- Document fuzzer usage [\#3478](https://github.com/nlohmann/json/pull/3478) ([nlohmann](https://github.com/nlohmann)) -- Add build step for ICPC \(with fixes\) [\#3465](https://github.com/nlohmann/json/pull/3465) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Complete documentation for 3.11.0 [\#3464](https://github.com/nlohmann/json/pull/3464) ([nlohmann](https://github.com/nlohmann)) -- Handle invalid BJData optimized type, fix \#3461 [\#3463](https://github.com/nlohmann/json/pull/3463) ([fangq](https://github.com/fangq)) -- Reorganize directories [\#3462](https://github.com/nlohmann/json/pull/3462) ([nlohmann](https://github.com/nlohmann)) -- Enable rapid testing and development on Compiler Explorer [\#3456](https://github.com/nlohmann/json/pull/3456) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- cpplint 1.6.0 [\#3454](https://github.com/nlohmann/json/pull/3454) ([nlohmann](https://github.com/nlohmann)) -- Disable regression test for \#3070 on GCC \<8.4 [\#3451](https://github.com/nlohmann/json/pull/3451) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Fix C++20/gcc-12 issues \(Part 2\) [\#3446](https://github.com/nlohmann/json/pull/3446) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Overwork documentation [\#3444](https://github.com/nlohmann/json/pull/3444) ([nlohmann](https://github.com/nlohmann)) -- Fix typo in basic\_json documentation [\#3439](https://github.com/nlohmann/json/pull/3439) ([jhnlee](https://github.com/jhnlee)) -- Exclude std::any from implicit conversion \(fixes \#3428\) [\#3437](https://github.com/nlohmann/json/pull/3437) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Document which version introduced the macros [\#3431](https://github.com/nlohmann/json/pull/3431) ([nlohmann](https://github.com/nlohmann)) -- Fix constraints on from\_json\(\) for strings \(fixes \#3171, \#3267, \#3312, \#3384\) [\#3427](https://github.com/nlohmann/json/pull/3427) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- at.md: fix typo [\#3426](https://github.com/nlohmann/json/pull/3426) ([heinemml](https://github.com/heinemml)) -- Implement support for string\_view \(attempt no. 3\) [\#3423](https://github.com/nlohmann/json/pull/3423) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- CI: speedup AppVeyor builds by ~30% [\#3422](https://github.com/nlohmann/json/pull/3422) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Restore disabled check for \#3070 \(except on MSVC\) [\#3421](https://github.com/nlohmann/json/pull/3421) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Update CI image [\#3420](https://github.com/nlohmann/json/pull/3420) ([nlohmann](https://github.com/nlohmann)) -- Add check if different version is also included [\#3418](https://github.com/nlohmann/json/pull/3418) ([nlohmann](https://github.com/nlohmann)) -- Report the right \_\_cplusplus value for MSVC in basic\_json meta\(\) [\#3417](https://github.com/nlohmann/json/pull/3417) ([flagarde](https://github.com/flagarde)) -- CI: windows-2016 has been deprecated; remove jobs [\#3416](https://github.com/nlohmann/json/pull/3416) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Re-template json\_pointer on string type [\#3415](https://github.com/nlohmann/json/pull/3415) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Refactor unit tests to use more convenient doctest assertion macros \(Part 2\) [\#3405](https://github.com/nlohmann/json/pull/3405) ([kkarbowiak](https://github.com/kkarbowiak)) -- Refactor unit tests to use more convenient doctest assertion macros [\#3393](https://github.com/nlohmann/json/pull/3393) ([kkarbowiak](https://github.com/kkarbowiak)) -- Improve unit testing \(Part 1\) [\#3380](https://github.com/nlohmann/json/pull/3380) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Fix C++20/gcc-12 issues \(Part 1\) [\#3379](https://github.com/nlohmann/json/pull/3379) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Add clarification to avoid misunderstanding that cause \#3360 [\#3378](https://github.com/nlohmann/json/pull/3378) ([puffetto](https://github.com/puffetto)) -- Fix ordered\_map ctor with initializer\_list \(fixes \#3343\) [\#3370](https://github.com/nlohmann/json/pull/3370) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Fix and update CI [\#3368](https://github.com/nlohmann/json/pull/3368) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- FetchContent\_MakeAvailable [\#3351](https://github.com/nlohmann/json/pull/3351) ([nlohmann](https://github.com/nlohmann)) -- Avoid clash with Arduino defines [\#3338](https://github.com/nlohmann/json/pull/3338) ([DarkZeros](https://github.com/DarkZeros)) -- Support UBJSON-derived Binary JData \(BJData\) format [\#3336](https://github.com/nlohmann/json/pull/3336) ([fangq](https://github.com/fangq)) -- Make iterator operator++/--\(int\) equality-preserving [\#3332](https://github.com/nlohmann/json/pull/3332) ([falbrechtskirchinger](https://github.com/falbrechtskirchinger)) -- Add note on parsing ordered\_json [\#3326](https://github.com/nlohmann/json/pull/3326) ([nlohmann](https://github.com/nlohmann)) -- Fix CITATION.cff and add automatic validation of your citation metadata [\#3320](https://github.com/nlohmann/json/pull/3320) ([fdiblen](https://github.com/fdiblen)) -- .github/workflows/windows.yml: Add support for Visual Studio 2022 [\#3295](https://github.com/nlohmann/json/pull/3295) ([t-b](https://github.com/t-b)) -- Add maintainer targets to create source archive [\#3289](https://github.com/nlohmann/json/pull/3289) ([nlohmann](https://github.com/nlohmann)) -- Fix a typo [\#3265](https://github.com/nlohmann/json/pull/3265) ([fhuberts](https://github.com/fhuberts)) -- Fix typo [\#3249](https://github.com/nlohmann/json/pull/3249) ([rex4539](https://github.com/rex4539)) -- Add documentation for JSON Lines [\#3247](https://github.com/nlohmann/json/pull/3247) ([nlohmann](https://github.com/nlohmann)) -- Improve documentation InputType and IteratorType [\#3246](https://github.com/nlohmann/json/pull/3246) ([nlohmann](https://github.com/nlohmann)) -- Remove stringstream [\#3244](https://github.com/nlohmann/json/pull/3244) ([nlohmann](https://github.com/nlohmann)) -- fix \_MSC\_VER version to check for std::filesystem [\#3240](https://github.com/nlohmann/json/pull/3240) ([gcerretani](https://github.com/gcerretani)) -- Add macros NLOHMANN\_DEFINE\_TYPE\_INTRUSIVE\_WITH\_DEFAULT and ...\_NON\_INTRUSIVE\_WITH\_DEFAULT [\#3143](https://github.com/nlohmann/json/pull/3143) ([pketelsen](https://github.com/pketelsen)) - -## [v3.10.5](https://github.com/nlohmann/json/releases/tag/v3.10.5) (2022-01-03) - -[Full Changelog](https://github.com/nlohmann/json/compare/v3.10.4...v3.10.5) - -- \#include \ doesn't work with gcc-7 when `-std=c++17` is specified. [\#3203](https://github.com/nlohmann/json/issues/3203) -- Not able to use nlohmann json with c++ code built using emscripten to wasm [\#3200](https://github.com/nlohmann/json/issues/3200) -- Warning for shadowed variables [\#3188](https://github.com/nlohmann/json/issues/3188) -- Accessing missing keys on const json object leads to assert [\#3183](https://github.com/nlohmann/json/issues/3183) -- Data member is available, but null is reported, and program throws error [\#3173](https://github.com/nlohmann/json/issues/3173) -- serialization problem, from\_json need construct new object [\#3169](https://github.com/nlohmann/json/issues/3169) -- std::filesystem unavailable on macOS lower deployment targets [\#3156](https://github.com/nlohmann/json/issues/3156) -- \[json.exception.type\_error.305\] cannot use operator\[\] with a string argument with string [\#3151](https://github.com/nlohmann/json/issues/3151) -- json::dump\(\) is not compatible with C++ standards [\#3147](https://github.com/nlohmann/json/issues/3147) -- Issue with json::parse decoding codepoints [\#3142](https://github.com/nlohmann/json/issues/3142) -- Simple parse of json object thinks it should be an array [\#3136](https://github.com/nlohmann/json/issues/3136) -- How to properly read a Json string that may be null in some cases? [\#3135](https://github.com/nlohmann/json/issues/3135) -- Deadlock on create json - windows only [\#3129](https://github.com/nlohmann/json/issues/3129) -- Wrong parsing of int64 values nearest of limit [\#3126](https://github.com/nlohmann/json/issues/3126) -- ordered\_json doesn't support range based erase [\#3108](https://github.com/nlohmann/json/issues/3108) -- Apple build failed with json/single\_include/nlohmann/json.hpp:4384:57: 'path' is unavailable [\#3097](https://github.com/nlohmann/json/issues/3097) -- GCC 7.5.0 with --std=c++17: filesystem: No such file or directory [\#3090](https://github.com/nlohmann/json/issues/3090) -- Drop Travis CI [\#3087](https://github.com/nlohmann/json/issues/3087) -- ordered\_json::reset\(\) compile error with nvcc [\#3013](https://github.com/nlohmann/json/issues/3013) -- Support for unordered\_map as object\_t [\#2932](https://github.com/nlohmann/json/issues/2932) -- Compiler warning with Intel compiler, same as \#755 [\#2712](https://github.com/nlohmann/json/issues/2712) -- Compiler warnings with NVCC 11.2 [\#2676](https://github.com/nlohmann/json/issues/2676) -- some static analysis warning at line 11317 [\#1390](https://github.com/nlohmann/json/issues/1390) -- Compiling with icpc [\#755](https://github.com/nlohmann/json/issues/755) - -- Fix compilation error with NVCC [\#3234](https://github.com/nlohmann/json/pull/3234) ([nlohmann](https://github.com/nlohmann)) -- Remove Travis CI [\#3233](https://github.com/nlohmann/json/pull/3233) ([nlohmann](https://github.com/nlohmann)) -- Add build step for NVCC and fix a warning [\#3227](https://github.com/nlohmann/json/pull/3227) ([nlohmann](https://github.com/nlohmann)) -- Update cpplint [\#3225](https://github.com/nlohmann/json/pull/3225) ([nlohmann](https://github.com/nlohmann)) -- Fix: Warning for shadowed variables \(\#3188\) [\#3193](https://github.com/nlohmann/json/pull/3193) ([kernie](https://github.com/kernie)) -- Fix FAQ hyperlink typo in readme [\#3148](https://github.com/nlohmann/json/pull/3148) ([Prince-Mendiratta](https://github.com/Prince-Mendiratta)) -- Docs: Update `skip_comments` to `ignore_comments` [\#3145](https://github.com/nlohmann/json/pull/3145) ([daniel-kun](https://github.com/daniel-kun)) -- fix typos in documentation [\#3140](https://github.com/nlohmann/json/pull/3140) ([striezel](https://github.com/striezel)) -- Fix spelling [\#3125](https://github.com/nlohmann/json/pull/3125) ([axic](https://github.com/axic)) -- Extend std specializations [\#3121](https://github.com/nlohmann/json/pull/3121) ([nlohmann](https://github.com/nlohmann)) -- Add missing erase\(first, last\) function to ordered\_map [\#3109](https://github.com/nlohmann/json/pull/3109) ([nlohmann](https://github.com/nlohmann)) -- Fix typos in operator\[\] documentation [\#3102](https://github.com/nlohmann/json/pull/3102) ([axnsan12](https://github.com/axnsan12)) -- Add C++17 copies of the test binaries [\#3101](https://github.com/nlohmann/json/pull/3101) ([nlohmann](https://github.com/nlohmann)) -- Add examples for parsing from iterator pair [\#3100](https://github.com/nlohmann/json/pull/3100) ([nlohmann](https://github.com/nlohmann)) -- Update CI [\#3088](https://github.com/nlohmann/json/pull/3088) ([nlohmann](https://github.com/nlohmann)) -- Consolidate documentation [\#3071](https://github.com/nlohmann/json/pull/3071) ([nlohmann](https://github.com/nlohmann)) -- Add recursive update function [\#3069](https://github.com/nlohmann/json/pull/3069) ([nlohmann](https://github.com/nlohmann)) - -## [v3.10.4](https://github.com/nlohmann/json/releases/tag/v3.10.4) (2021-10-16) - -[Full Changelog](https://github.com/nlohmann/json/compare/v3.10.3...v3.10.4) - -- Compiler error in output serializer due to 'incompatible initializer' [\#3081](https://github.com/nlohmann/json/issues/3081) -- Strange behaviour when using std::sort on std::vector\ [\#3080](https://github.com/nlohmann/json/issues/3080) -- Unhandled exception: nlohmann::detail::parse\_error [\#3078](https://github.com/nlohmann/json/issues/3078) -- explicit constructor with default does not compile [\#3077](https://github.com/nlohmann/json/issues/3077) -- Parse an object but get an array using GCC [\#3076](https://github.com/nlohmann/json/issues/3076) -- Version 3.10.3 breaks backward-compatibility with 3.10.2 [\#3070](https://github.com/nlohmann/json/issues/3070) -- Feature request, Add to\_json/from\_json to align with other to/from binary api. [\#3067](https://github.com/nlohmann/json/issues/3067) -- vcpkg is out of date [\#3066](https://github.com/nlohmann/json/issues/3066) - -- Revert invalid fix [\#3082](https://github.com/nlohmann/json/pull/3082) ([nlohmann](https://github.com/nlohmann)) -- Allow to use get with explicit constructor [\#3079](https://github.com/nlohmann/json/pull/3079) ([nlohmann](https://github.com/nlohmann)) -- fix std::filesystem::path regression [\#3073](https://github.com/nlohmann/json/pull/3073) ([theodelrieu](https://github.com/theodelrieu)) - -## [v3.10.3](https://github.com/nlohmann/json/releases/tag/v3.10.3) (2021-10-08) - -[Full Changelog](https://github.com/nlohmann/json/compare/v3.10.2...v3.10.3) - -- Parsing an emtpy string returns a string with size 1 instead of expected 0 [\#3057](https://github.com/nlohmann/json/issues/3057) -- Linking error "duplicate symbol: std::type\_info::operator==" on static build with MinGW [\#3042](https://github.com/nlohmann/json/issues/3042) -- Yet another assertion failure when inserting into arrays with JSON\_DIAGNOSTICS set [\#3032](https://github.com/nlohmann/json/issues/3032) -- accept and parse function not work well with a pure number string [\#3029](https://github.com/nlohmann/json/issues/3029) -- push\_back doesn't work for serializing containers [\#3027](https://github.com/nlohmann/json/issues/3027) -- Strange behaviour when creating array with single element [\#3025](https://github.com/nlohmann/json/issues/3025) -- Input ordered\_json doesn't work [\#3023](https://github.com/nlohmann/json/issues/3023) -- Issue iterating through 'items' [\#3021](https://github.com/nlohmann/json/issues/3021) -- Cannot spell the namespace right [\#3015](https://github.com/nlohmann/json/issues/3015) -- JSON Parse error when reading json object from file [\#3011](https://github.com/nlohmann/json/issues/3011) -- Parent pointer not properly set when using update\(\) [\#3007](https://github.com/nlohmann/json/issues/3007) -- Overwriting terminated null character [\#3001](https://github.com/nlohmann/json/issues/3001) -- 'operator =' is ambiguous on VS2017 [\#2997](https://github.com/nlohmann/json/issues/2997) -- JSON Patch for Array Elements [\#2994](https://github.com/nlohmann/json/issues/2994) -- JSON Parse throwing error [\#2983](https://github.com/nlohmann/json/issues/2983) -- to\_{binary format} does not provide a mechanism for specifying a custom allocator for the returned type. [\#2982](https://github.com/nlohmann/json/issues/2982) -- 3.10.1 zip json.hpp has version number 3.10.0 instead of 3.10.1 [\#2973](https://github.com/nlohmann/json/issues/2973) -- Assertion failure when serializing array with JSON\_DIAGNOSTICS set [\#2926](https://github.com/nlohmann/json/issues/2926) - -- Fix Clang version [\#3040](https://github.com/nlohmann/json/pull/3040) ([nlohmann](https://github.com/nlohmann)) -- Fix assertion failure for JSON\_DIAGNOSTICS [\#3037](https://github.com/nlohmann/json/pull/3037) ([carlsmedstad](https://github.com/carlsmedstad)) -- meta: fix is\_compatible/constructible traits [\#3020](https://github.com/nlohmann/json/pull/3020) ([theodelrieu](https://github.com/theodelrieu)) -- Set parent pointers for values inserted via update\(\) \(fixes \#3007\). [\#3008](https://github.com/nlohmann/json/pull/3008) ([AnthonyVH](https://github.com/AnthonyVH)) -- Allow allocators for output\_vector\_adapter [\#2989](https://github.com/nlohmann/json/pull/2989) ([nlohmann](https://github.com/nlohmann)) -- Re-add Clang 12 [\#2986](https://github.com/nlohmann/json/pull/2986) ([nlohmann](https://github.com/nlohmann)) -- Use new Docker image [\#2981](https://github.com/nlohmann/json/pull/2981) ([nlohmann](https://github.com/nlohmann)) -- Update docset generation script [\#2967](https://github.com/nlohmann/json/pull/2967) ([nlohmann](https://github.com/nlohmann)) - -## [v3.10.2](https://github.com/nlohmann/json/releases/tag/v3.10.2) (2021-08-26) - -[Full Changelog](https://github.com/nlohmann/json/compare/v3.10.1...v3.10.2) - -- Annoying -Wundef on new JSON\_DIAGNOSTICS macro [\#2975](https://github.com/nlohmann/json/issues/2975) -- += issue with multiple redirection. [\#2970](https://github.com/nlohmann/json/issues/2970) -- "incomplete type ‘nlohmann::detail::wide\_string\_input\_helper" compilation error [\#2969](https://github.com/nlohmann/json/issues/2969) - -- Fix -Wunused warnings on JSON\_DIAGNOSTICS [\#2976](https://github.com/nlohmann/json/pull/2976) ([gcerretani](https://github.com/gcerretani)) - -## [v3.10.1](https://github.com/nlohmann/json/releases/tag/v3.10.1) (2021-08-24) - -[Full Changelog](https://github.com/nlohmann/json/compare/v3.10.0...v3.10.1) - -- JSON\_DIAGNOSTICS assertion for ordered\_json [\#2962](https://github.com/nlohmann/json/issues/2962) -- Inserting in unordered json using a pointer retains the leading slash [\#2958](https://github.com/nlohmann/json/issues/2958) -- Test \#9: test-cbor test case sample.json fails in debug mode - Stack overflow [\#2955](https://github.com/nlohmann/json/issues/2955) -- 3.10.0 broke at least the Bear project [\#2953](https://github.com/nlohmann/json/issues/2953) -- 2 tests fail in 3.10.0: cmake\_fetch\_content\_configure, cmake\_fetch\_content\_build [\#2951](https://github.com/nlohmann/json/issues/2951) -- ctest \(58+60,/67 cmake\_import\_configure\) fails when build with -D JSON\_Install:BOOL=OFF because of missing nlohmann\_jsonTargets.cmake [\#2946](https://github.com/nlohmann/json/issues/2946) -- Document vcpkg usage [\#2944](https://github.com/nlohmann/json/issues/2944) -- Linker error LNK2005 when compiling \(x64\) json-3.10.0.zip with Visual Studio 2019 16.11.1 [\#2941](https://github.com/nlohmann/json/issues/2941) -- Move Travis jobs to travis-ci.com [\#2938](https://github.com/nlohmann/json/issues/2938) - -- Fixed typo in docs/api/basic\_json/parse.md [\#2968](https://github.com/nlohmann/json/pull/2968) ([mbadhan](https://github.com/mbadhan)) -- Add link to Homebrew package [\#2966](https://github.com/nlohmann/json/pull/2966) ([nlohmann](https://github.com/nlohmann)) -- Fix parent update for diagnostics with ordered\_json [\#2963](https://github.com/nlohmann/json/pull/2963) ([nlohmann](https://github.com/nlohmann)) -- Set stack size for some unit tests when using MSVC [\#2961](https://github.com/nlohmann/json/pull/2961) ([nlohmann](https://github.com/nlohmann)) -- Add regression test [\#2960](https://github.com/nlohmann/json/pull/2960) ([nlohmann](https://github.com/nlohmann)) -- Update Travis badge [\#2959](https://github.com/nlohmann/json/pull/2959) ([nlohmann](https://github.com/nlohmann)) -- Fix some extra ";" clang warnings [\#2957](https://github.com/nlohmann/json/pull/2957) ([Hallot](https://github.com/Hallot)) -- Add documentation for integration via vcpkg [\#2954](https://github.com/nlohmann/json/pull/2954) ([nlohmann](https://github.com/nlohmann)) -- Avoid duplicate AppVeyor builds [\#2952](https://github.com/nlohmann/json/pull/2952) ([nlohmann](https://github.com/nlohmann)) -- 🚨 fix gdb\_pretty\_printer failure on basic types [\#2950](https://github.com/nlohmann/json/pull/2950) ([senyai](https://github.com/senyai)) -- Add header to use value\_t [\#2948](https://github.com/nlohmann/json/pull/2948) ([nlohmann](https://github.com/nlohmann)) -- Skip some tests if JSON\_Install is not set [\#2947](https://github.com/nlohmann/json/pull/2947) ([nlohmann](https://github.com/nlohmann)) -- Remove outdated json\_unit test binary [\#2945](https://github.com/nlohmann/json/pull/2945) ([nlohmann](https://github.com/nlohmann)) -- Updating the Homebrew Command [\#2943](https://github.com/nlohmann/json/pull/2943) ([amirmasoudabdol](https://github.com/amirmasoudabdol)) - -## [v3.10.0](https://github.com/nlohmann/json/releases/tag/v3.10.0) (2021-08-17) - -[Full Changelog](https://github.com/nlohmann/json/compare/v3.9.1...v3.10.0) - -- Latest version 3.9.1 uses throw instead of JSON\_THROW in the amalgamated json.hpp file [\#2934](https://github.com/nlohmann/json/issues/2934) -- Copy to a variable inside a Structure [\#2933](https://github.com/nlohmann/json/issues/2933) -- warning C4068: unknown pragma 'GCC' on MSVC/cl [\#2924](https://github.com/nlohmann/json/issues/2924) -- Errors during ninja test [\#2918](https://github.com/nlohmann/json/issues/2918) -- compiler warning: "not return a value" [\#2917](https://github.com/nlohmann/json/issues/2917) -- Comparison floating points causes warning [\#2909](https://github.com/nlohmann/json/issues/2909) -- Why can't I have std::vector\ testList? [\#2900](https://github.com/nlohmann/json/issues/2900) -- \[json.hpp\] from releases doesnt work [\#2897](https://github.com/nlohmann/json/issues/2897) -- g++ \(11\) -Wuseless-cast gives lots of warnings [\#2893](https://github.com/nlohmann/json/issues/2893) -- Cannot serialize and immediatly deserialize json to/from bson [\#2892](https://github.com/nlohmann/json/issues/2892) -- Floating-point precision conversion error [\#2876](https://github.com/nlohmann/json/issues/2876) -- How to avoid escaping for an already escaped string in .dump\(\) [\#2870](https://github.com/nlohmann/json/issues/2870) -- can't parse std::vector\ [\#2869](https://github.com/nlohmann/json/issues/2869) -- ASAN detects memory leaks [\#2865](https://github.com/nlohmann/json/issues/2865) -- Binary subtype field cannot represent all CBOR tags [\#2863](https://github.com/nlohmann/json/issues/2863) -- string literals possibly being parsed as another type due to the presence of only digits and full-stops [\#2852](https://github.com/nlohmann/json/issues/2852) -- json::parse\(\) works only with absolute paths [\#2851](https://github.com/nlohmann/json/issues/2851) -- Compiler Warnings on Raspberry Pi OS [\#2850](https://github.com/nlohmann/json/issues/2850) -- Braced initialization and aggregate initialization behavior is different for `json::array()` function call. [\#2848](https://github.com/nlohmann/json/issues/2848) -- 3.9.1: test suite is failing [\#2845](https://github.com/nlohmann/json/issues/2845) -- Documentation for macro JSON\_NO\_IO is missing [\#2842](https://github.com/nlohmann/json/issues/2842) -- Assertion failure when inserting into arrays with JSON\_DIAGNOSTICS set [\#2838](https://github.com/nlohmann/json/issues/2838) -- HELP! There is a memory leak in the code?! [\#2837](https://github.com/nlohmann/json/issues/2837) -- Elegant conversion of a 2-D-json array to a standard C++ array [\#2805](https://github.com/nlohmann/json/issues/2805) -- Swift Package Manager support [\#2802](https://github.com/nlohmann/json/issues/2802) -- Referencing a subkey which doesn't exist gives crash [\#2797](https://github.com/nlohmann/json/issues/2797) -- Failed benchmark due to renamed branch [\#2796](https://github.com/nlohmann/json/issues/2796) -- Build Errors with VS 2019 and json Version 3.9.1 when attempting to replicate SAX Example [\#2782](https://github.com/nlohmann/json/issues/2782) -- Value with spaces cannot be parsed [\#2781](https://github.com/nlohmann/json/issues/2781) -- \[Question\] CBOR rfc support. [\#2779](https://github.com/nlohmann/json/issues/2779) -- Using JSON.hpp header file in Visual Studio 2013 \(C++ Project\) [\#2775](https://github.com/nlohmann/json/issues/2775) -- compilation error on clang-8 + C++17 [\#2759](https://github.com/nlohmann/json/issues/2759) -- Undefined symbol EOF [\#2755](https://github.com/nlohmann/json/issues/2755) -- Parsing a string into json object behaves differently under g++ and MinGW compilers. [\#2746](https://github.com/nlohmann/json/issues/2746) -- big git history size [\#2742](https://github.com/nlohmann/json/issues/2742) -- How to get reference of std::vector\ [\#2735](https://github.com/nlohmann/json/issues/2735) -- CMake failure in VS2019 Community [\#2734](https://github.com/nlohmann/json/issues/2734) -- Possibility to use with custom c++ version to use in intel sgx enclaves [\#2730](https://github.com/nlohmann/json/issues/2730) -- Possibility to use without the dependency to file io and streams to use in intel sgx enclaves [\#2728](https://github.com/nlohmann/json/issues/2728) -- error C2784& error C2839... in my visual studio 2015 compiler [\#2726](https://github.com/nlohmann/json/issues/2726) -- `-fno-expection` not respected anymore in 3.9.1 [\#2725](https://github.com/nlohmann/json/issues/2725) -- When exceptions disabled with JSON\_NOEXCEPTION, lib just aborts without any message [\#2724](https://github.com/nlohmann/json/issues/2724) -- Critical error detected c0000374 on windows10 msvc 2019 16.8.5 [\#2710](https://github.com/nlohmann/json/issues/2710) -- unused parameter error/warning [\#2706](https://github.com/nlohmann/json/issues/2706) -- How to store data into a Map from json file [\#2691](https://github.com/nlohmann/json/issues/2691) -- Tests do not compile with pre-release glibc [\#2686](https://github.com/nlohmann/json/issues/2686) -- compile errors .... chromium-style [\#2680](https://github.com/nlohmann/json/issues/2680) -- .dump\(\) not allowing compact form [\#2678](https://github.com/nlohmann/json/issues/2678) -- error: no matching function for call to ‘nlohmann::basic\_json\<\>::value\(int, std::set\&\)’ [\#2671](https://github.com/nlohmann/json/issues/2671) -- Compiler warning: unused parameter [\#2668](https://github.com/nlohmann/json/issues/2668) -- Deserializing to a struct as shown on the project homepage throws compile time errors [\#2665](https://github.com/nlohmann/json/issues/2665) -- Unable to compile on MSVC 2019 with SDL checking enabled: This function or variable may be unsafe [\#2664](https://github.com/nlohmann/json/issues/2664) -- terminating with uncaught exception of type nlohmann::detail::type\_error: \[json.exception.type\_error.302\] type must be array, but is object [\#2661](https://github.com/nlohmann/json/issues/2661) -- unused-parameter on OSX when Diagnostics is off [\#2658](https://github.com/nlohmann/json/issues/2658) -- std::pair wrong serialization [\#2655](https://github.com/nlohmann/json/issues/2655) -- The result of json is\_number\_integer\(\) function is wrong when read a json file [\#2653](https://github.com/nlohmann/json/issues/2653) -- 2 backslash cause problem [\#2652](https://github.com/nlohmann/json/issues/2652) -- No support for using an external/system copy of Hedley [\#2651](https://github.com/nlohmann/json/issues/2651) -- error: incomplete type 'qfloat16' used in type trait expression [\#2650](https://github.com/nlohmann/json/issues/2650) -- Unused variable in exception class when not using improved diagnostics [\#2646](https://github.com/nlohmann/json/issues/2646) -- I am trying to do this - converting from wstring works incorrectly! [\#2642](https://github.com/nlohmann/json/issues/2642) -- Exception 207 On ARM Processor During Literal String Parsing [\#2634](https://github.com/nlohmann/json/issues/2634) -- double free or corruption \(!prev\) error on Json push\_back and write [\#2632](https://github.com/nlohmann/json/issues/2632) -- nlohmann::detail::parse\_error: syntax error while parsing CBOR string: expected length specification \(0x60-0x7B\) or indefinite string type \(0x7F\) [\#2629](https://github.com/nlohmann/json/issues/2629) -- please allow disabling implicit conversions in non-single-file use [\#2621](https://github.com/nlohmann/json/issues/2621) -- Preserve decimal formatting [\#2618](https://github.com/nlohmann/json/issues/2618) -- Visual Studio Visual Assist code issues reported by VA code inspection of file json.hpp [\#2615](https://github.com/nlohmann/json/issues/2615) -- Missing get function and no viable overloaded '=' on mac [\#2610](https://github.com/nlohmann/json/issues/2610) -- corruption when parse from string [\#2603](https://github.com/nlohmann/json/issues/2603) -- Parse from byte-vector results in compile error [\#2602](https://github.com/nlohmann/json/issues/2602) -- Memory leak when working on ARM Linux [\#2601](https://github.com/nlohmann/json/issues/2601) -- Unhandled exception in test-cbor.exe Stack overflow when debugging project with Visual Studio 2019 16.7.7 compiled with c++17 or c++latest [\#2598](https://github.com/nlohmann/json/issues/2598) -- Error in download\_test\_data.vcxproj when compiling with Visual Studio 2019 16.7.7 Professional msbuild on Windows 10 2004 Professional [\#2594](https://github.com/nlohmann/json/issues/2594) -- Warnings C4715 and C4127 when building json-3.9.1 with Visual Studio 2019 16.7.7 [\#2592](https://github.com/nlohmann/json/issues/2592) -- I tried some change to dump\(\) for \[1,2,3...\] [\#2584](https://github.com/nlohmann/json/issues/2584) -- try/catch block does not catch parsing error [\#2579](https://github.com/nlohmann/json/issues/2579) -- Serializing uint64\_t is broken for large values [\#2578](https://github.com/nlohmann/json/issues/2578) -- deserializing arrays should be part of the library [\#2575](https://github.com/nlohmann/json/issues/2575) -- Deserialization to std::array with non-default constructable types fails [\#2574](https://github.com/nlohmann/json/issues/2574) -- Compilation error when trying to use same type for number\_integer\_t and number\_unsigned\_t in basic\_json template specification. [\#2573](https://github.com/nlohmann/json/issues/2573) -- compiler error: directive output may be truncated writing between 2 and 8 bytes [\#2572](https://github.com/nlohmann/json/issues/2572) -- Incorrect convert map to json when key cannot construct an string i.e. int [\#2564](https://github.com/nlohmann/json/issues/2564) -- no matching function for call to ‘nlohmann::basic\_json\<\>::basic\_json\(\\)’ [\#2559](https://github.com/nlohmann/json/issues/2559) -- type\_error factory creates a dangling pointer \(in VisualStudio 2019\) [\#2535](https://github.com/nlohmann/json/issues/2535) -- Cannot assign from ordered\_json vector\ to value in not ordered json [\#2528](https://github.com/nlohmann/json/issues/2528) -- Qt6: Break changes [\#2519](https://github.com/nlohmann/json/issues/2519) -- valgrind memcheck Illegal instruction when use nlohmann::json::parse [\#2518](https://github.com/nlohmann/json/issues/2518) -- Buffer overflow [\#2515](https://github.com/nlohmann/json/issues/2515) -- Including CTest in the top-level CMakeLists.txt sets BUILD\_TESTING=ON for parent projects [\#2513](https://github.com/nlohmann/json/issues/2513) -- Compilation error when using NLOHMANN\_JSON\_SERIALIZE\_ENUM ordered\_json on libc++ [\#2491](https://github.com/nlohmann/json/issues/2491) -- Missing "void insert\( InputIt first, InputIt last \);" overload in nlohmann::ordered\_map [\#2490](https://github.com/nlohmann/json/issues/2490) -- Could not find a package configuration file provided by "nlohmann\_json" [\#2482](https://github.com/nlohmann/json/issues/2482) -- json becomes empty for unknown reason [\#2470](https://github.com/nlohmann/json/issues/2470) -- Using std::wstring as StringType fails compiling [\#2459](https://github.com/nlohmann/json/issues/2459) -- Sample code in GIF slide outdated \(cannot use emplace\(\) with array\) [\#2457](https://github.com/nlohmann/json/issues/2457) -- from\_json\ is treated as an array on latest MSVC [\#2453](https://github.com/nlohmann/json/issues/2453) -- MemorySanitizer: use-of-uninitialized-value [\#2449](https://github.com/nlohmann/json/issues/2449) -- I need help [\#2441](https://github.com/nlohmann/json/issues/2441) -- type conversion failing with clang ext\_vector\_type [\#2436](https://github.com/nlohmann/json/issues/2436) -- json::parse\(\) can't be resolved under specific circumstances [\#2427](https://github.com/nlohmann/json/issues/2427) -- from\_\*\(ptr, len\) deprecation [\#2426](https://github.com/nlohmann/json/issues/2426) -- Error ONLY in release mode [\#2425](https://github.com/nlohmann/json/issues/2425) -- "Custom data source" exemple make no sense [\#2423](https://github.com/nlohmann/json/issues/2423) -- Refuses to compile in project [\#2419](https://github.com/nlohmann/json/issues/2419) -- Compilation failure of tests with C++20 standard \(caused by change of u8 literals\) [\#2413](https://github.com/nlohmann/json/issues/2413) -- No matching function for call to 'input\_adapter' under Xcode of with nlohmann version 3.9.1 [\#2412](https://github.com/nlohmann/json/issues/2412) -- Git tags are not valid semvers [\#2409](https://github.com/nlohmann/json/issues/2409) -- after dump, stderr output disappear [\#2403](https://github.com/nlohmann/json/issues/2403) -- Using custom string. [\#2398](https://github.com/nlohmann/json/issues/2398) -- value\(\) throws unhandled exception for partially specified json object [\#2393](https://github.com/nlohmann/json/issues/2393) -- assertion on runtime causes program to stop when accessing const json with missing key [\#2392](https://github.com/nlohmann/json/issues/2392) -- Usage with -fno-elide-constructors causes dump\(\) output to be array of `null`s [\#2387](https://github.com/nlohmann/json/issues/2387) -- Build fails with clang-cl due to override of CMAKE\_CXX\_COMPILER\(?\) [\#2384](https://github.com/nlohmann/json/issues/2384) -- std::optional not working with primitive types [\#2383](https://github.com/nlohmann/json/issues/2383) -- Unexpected array when initializing a json const& on gcc 4.8.5 using uniform syntax [\#2370](https://github.com/nlohmann/json/issues/2370) -- setprecision support [\#2362](https://github.com/nlohmann/json/issues/2362) -- json::parse\(allow\_exceptions = false\) documentation is misleading. [\#2360](https://github.com/nlohmann/json/issues/2360) -- std::begin and std::end usage without specifying std namespace [\#2359](https://github.com/nlohmann/json/issues/2359) -- Custom object conversion to json hangs in background thread [\#2358](https://github.com/nlohmann/json/issues/2358) -- Add support of nullable fields to NLOHMANN\_DEFINE\_TYPE\_NON\_INTRUSIVE and NLOHMANN\_DEFINE\_TYPE\_INTRUSIVE [\#2356](https://github.com/nlohmann/json/issues/2356) -- the portfile for the vcpkg is not working. [\#2351](https://github.com/nlohmann/json/issues/2351) -- Compiler warns of implicit fallthrough when defining preprocessor macro NDEBUG [\#2348](https://github.com/nlohmann/json/issues/2348) -- Compile error on Intel compiler running in Windows [\#2346](https://github.com/nlohmann/json/issues/2346) -- Build error caused by overwriting CMAKE\_CXX\_COMPILER [\#2343](https://github.com/nlohmann/json/issues/2343) -- Error: an attribute list cannot appear here JSON\_HEDLEY\_DEPRECATED\_FOR [\#2342](https://github.com/nlohmann/json/issues/2342) -- compiler warning [\#2341](https://github.com/nlohmann/json/issues/2341) -- 3.9.0: tests make build non-reproducible [\#2324](https://github.com/nlohmann/json/issues/2324) -- Initialization different between gcc/clang [\#2311](https://github.com/nlohmann/json/issues/2311) -- Attempt to `get()` a numeric value as a type which cannot represent it should throw [\#2310](https://github.com/nlohmann/json/issues/2310) -- Surprising behaviour with overloaded operators [\#2256](https://github.com/nlohmann/json/issues/2256) -- ADL issue in input\_adapter [\#2248](https://github.com/nlohmann/json/issues/2248) -- Output adapters should be templated. [\#2172](https://github.com/nlohmann/json/issues/2172) -- error when using nlohmann::json, std::function and std::bind [\#2147](https://github.com/nlohmann/json/issues/2147) -- Remove undefined behavior for const operator\[\] [\#2111](https://github.com/nlohmann/json/issues/2111) -- json\({}\) gives null instead of empty object with GCC and -std=c++17 [\#2046](https://github.com/nlohmann/json/issues/2046) -- GDB pretty printing support [\#1952](https://github.com/nlohmann/json/issues/1952) -- Always compile tests with all warnings enabled and error out on warnings [\#1798](https://github.com/nlohmann/json/issues/1798) -- Fixes Cppcheck warnings [\#1759](https://github.com/nlohmann/json/issues/1759) -- How to get position info or parser context with custom from\_json\(\) that may throw exceptions? [\#1508](https://github.com/nlohmann/json/issues/1508) -- Suggestion to improve value\(\) accessors with respect to move semantics [\#1275](https://github.com/nlohmann/json/issues/1275) -- Add Key name to Exception [\#932](https://github.com/nlohmann/json/issues/932) - -- Overwork warning flags [\#2936](https://github.com/nlohmann/json/pull/2936) ([nlohmann](https://github.com/nlohmann)) -- Treat MSVC warnings as errors [\#2930](https://github.com/nlohmann/json/pull/2930) ([nlohmann](https://github.com/nlohmann)) -- All: fix warnings when compiling with -Wswitch-enum [\#2927](https://github.com/nlohmann/json/pull/2927) ([fhuberts](https://github.com/fhuberts)) -- Guard GCC pragmas [\#2925](https://github.com/nlohmann/json/pull/2925) ([nlohmann](https://github.com/nlohmann)) -- Supress -Wfloat-equal on intended float comparisions [\#2911](https://github.com/nlohmann/json/pull/2911) ([Finkman](https://github.com/Finkman)) -- Fix binary subtypes [\#2908](https://github.com/nlohmann/json/pull/2908) ([nlohmann](https://github.com/nlohmann)) -- Fix useless-cast warnings [\#2902](https://github.com/nlohmann/json/pull/2902) ([nlohmann](https://github.com/nlohmann)) -- Add regression test [\#2898](https://github.com/nlohmann/json/pull/2898) ([nlohmann](https://github.com/nlohmann)) -- Refactor Unicode tests [\#2889](https://github.com/nlohmann/json/pull/2889) ([nlohmann](https://github.com/nlohmann)) -- CMake cleanup [\#2885](https://github.com/nlohmann/json/pull/2885) ([nlohmann](https://github.com/nlohmann)) -- Avoid string in case of empty CBOR objects [\#2879](https://github.com/nlohmann/json/pull/2879) ([nlohmann](https://github.com/nlohmann)) -- Suppress C4127 warning in unit-json\_pointer.cpp [\#2875](https://github.com/nlohmann/json/pull/2875) ([nlohmann](https://github.com/nlohmann)) -- Fix truncation warning [\#2874](https://github.com/nlohmann/json/pull/2874) ([nlohmann](https://github.com/nlohmann)) -- Fix memory leak in to\_json [\#2872](https://github.com/nlohmann/json/pull/2872) ([nlohmann](https://github.com/nlohmann)) -- Fix assertion failure in diagnostics [\#2866](https://github.com/nlohmann/json/pull/2866) ([nlohmann](https://github.com/nlohmann)) -- Update documentation [\#2861](https://github.com/nlohmann/json/pull/2861) ([nlohmann](https://github.com/nlohmann)) -- Consistency with `using` in README.md [\#2826](https://github.com/nlohmann/json/pull/2826) ([justanotheranonymoususer](https://github.com/justanotheranonymoususer)) -- Properly constrain the basic\_json conversion operator [\#2825](https://github.com/nlohmann/json/pull/2825) ([ldionne](https://github.com/ldionne)) -- Fix CI [\#2817](https://github.com/nlohmann/json/pull/2817) ([nlohmann](https://github.com/nlohmann)) -- Specified git branch for google benchmark fetch in benchmark test [\#2795](https://github.com/nlohmann/json/pull/2795) ([grafail](https://github.com/grafail)) -- Add C++ standards to macOS matrix [\#2790](https://github.com/nlohmann/json/pull/2790) ([nlohmann](https://github.com/nlohmann)) -- Update URLs to HTTPS [\#2789](https://github.com/nlohmann/json/pull/2789) ([TotalCaesar659](https://github.com/TotalCaesar659)) -- Link to Conan Center package added [\#2771](https://github.com/nlohmann/json/pull/2771) ([offa](https://github.com/offa)) -- Keep consistent formatting [\#2770](https://github.com/nlohmann/json/pull/2770) ([jasmcaus](https://github.com/jasmcaus)) -- Add a cmake option to use SYSTEM in target\_include\_directories [\#2762](https://github.com/nlohmann/json/pull/2762) ([jpl-mac](https://github.com/jpl-mac)) -- replace EOF with std::char\_traits\::eof\(\) [\#2756](https://github.com/nlohmann/json/pull/2756) ([nlohmann](https://github.com/nlohmann)) -- Fix typo in README [\#2754](https://github.com/nlohmann/json/pull/2754) ([mortenfyhn](https://github.com/mortenfyhn)) -- Update documentation [\#2749](https://github.com/nlohmann/json/pull/2749) ([nlohmann](https://github.com/nlohmann)) -- Add documentation for numbers [\#2747](https://github.com/nlohmann/json/pull/2747) ([nlohmann](https://github.com/nlohmann)) -- Use Clang 12 in CI [\#2737](https://github.com/nlohmann/json/pull/2737) ([nlohmann](https://github.com/nlohmann)) -- Fixes \#2730 [\#2731](https://github.com/nlohmann/json/pull/2731) ([theShmoo](https://github.com/theShmoo)) -- Possibility to use without the dependency to file io and streams to use in intel sgx enclaves [\#2729](https://github.com/nlohmann/json/pull/2729) ([theShmoo](https://github.com/theShmoo)) -- Update json.hpp [\#2707](https://github.com/nlohmann/json/pull/2707) ([raduteo](https://github.com/raduteo)) -- pkg-config.pc.in: Don't concatenate paths [\#2690](https://github.com/nlohmann/json/pull/2690) ([doronbehar](https://github.com/doronbehar)) -- add more CI steps [\#2689](https://github.com/nlohmann/json/pull/2689) ([nlohmann](https://github.com/nlohmann)) -- Update doctest from 2.4.4 to 2.4.6 \(fixes \#2686\) [\#2687](https://github.com/nlohmann/json/pull/2687) ([musicinmybrain](https://github.com/musicinmybrain)) -- License fix [\#2683](https://github.com/nlohmann/json/pull/2683) ([nlohmann](https://github.com/nlohmann)) -- Update parse\_exceptions.md - correct `json::exception::parse_error` [\#2679](https://github.com/nlohmann/json/pull/2679) ([frasermarlow](https://github.com/frasermarlow)) -- Remove HEDLEY annotation from exception::what\(\) [\#2673](https://github.com/nlohmann/json/pull/2673) ([remyjette](https://github.com/remyjette)) -- Fix amount of entries in the json object [\#2659](https://github.com/nlohmann/json/pull/2659) ([abbaswasim](https://github.com/abbaswasim)) -- Fix missing 1.78 in example in README.md [\#2625](https://github.com/nlohmann/json/pull/2625) ([wawiesel](https://github.com/wawiesel)) -- Add GDB pretty printer [\#2607](https://github.com/nlohmann/json/pull/2607) ([nlohmann](https://github.com/nlohmann)) -- readme: fix tilde character display [\#2582](https://github.com/nlohmann/json/pull/2582) ([bl-ue](https://github.com/bl-ue)) -- Add support for deserialization of STL containers of non-default constructable types \(fixes \#2574\). [\#2576](https://github.com/nlohmann/json/pull/2576) ([AnthonyVH](https://github.com/AnthonyVH)) -- Better diagnostics [\#2562](https://github.com/nlohmann/json/pull/2562) ([nlohmann](https://github.com/nlohmann)) -- CI targets [\#2561](https://github.com/nlohmann/json/pull/2561) ([nlohmann](https://github.com/nlohmann)) -- Add switch to skip non-reproducible tests. [\#2560](https://github.com/nlohmann/json/pull/2560) ([nlohmann](https://github.com/nlohmann)) -- Fix compilation of input\_adapter\(container\) in edge cases [\#2553](https://github.com/nlohmann/json/pull/2553) ([jasujm](https://github.com/jasujm)) -- Allow parsing from std::byte containers [\#2550](https://github.com/nlohmann/json/pull/2550) ([nlohmann](https://github.com/nlohmann)) -- Travis doesn't run any tests in C++17 mode [\#2540](https://github.com/nlohmann/json/pull/2540) ([karzhenkov](https://github.com/karzhenkov)) -- Doctest is updated to v2.4.3 [\#2538](https://github.com/nlohmann/json/pull/2538) ([YarikTH](https://github.com/YarikTH)) -- Fix warnings [\#2537](https://github.com/nlohmann/json/pull/2537) ([nlohmann](https://github.com/nlohmann)) -- Fix a shadowing warning [\#2536](https://github.com/nlohmann/json/pull/2536) ([nlohmann](https://github.com/nlohmann)) -- Clarify license of is\_complete\_type implementation [\#2534](https://github.com/nlohmann/json/pull/2534) ([nlohmann](https://github.com/nlohmann)) -- Do not unconditionally redefine C++14 constructs [\#2533](https://github.com/nlohmann/json/pull/2533) ([nlohmann](https://github.com/nlohmann)) -- Doctest is updated to v2.4.1 [\#2525](https://github.com/nlohmann/json/pull/2525) ([YarikTH](https://github.com/YarikTH)) -- Add MAIN\_PROJECT check for test and install options [\#2514](https://github.com/nlohmann/json/pull/2514) ([globberwops](https://github.com/globberwops)) -- Ranged insert test section is added in unit-ordered\_json.cpp [\#2512](https://github.com/nlohmann/json/pull/2512) ([YarikTH](https://github.com/YarikTH)) -- Add asserts to suppress C28020 [\#2447](https://github.com/nlohmann/json/pull/2447) ([jbzdarkid](https://github.com/jbzdarkid)) -- Change argument name "subtype" in byte\_container\_with\_subtype [\#2444](https://github.com/nlohmann/json/pull/2444) ([linev](https://github.com/linev)) -- 📝 add CPM.Cmake example [\#2406](https://github.com/nlohmann/json/pull/2406) ([leozz37](https://github.com/leozz37)) -- Fix move constructor of json\_ref [\#2405](https://github.com/nlohmann/json/pull/2405) ([karzhenkov](https://github.com/karzhenkov)) -- Properly select "Release" build for Travis [\#2375](https://github.com/nlohmann/json/pull/2375) ([karzhenkov](https://github.com/karzhenkov)) -- Update Hedley [\#2367](https://github.com/nlohmann/json/pull/2367) ([nlohmann](https://github.com/nlohmann)) -- Fix and extend documentation of discarded values [\#2363](https://github.com/nlohmann/json/pull/2363) ([nlohmann](https://github.com/nlohmann)) -- Fix typos in documentation [\#2354](https://github.com/nlohmann/json/pull/2354) ([rbuch](https://github.com/rbuch)) -- Remove "\#define private public" from tests [\#2352](https://github.com/nlohmann/json/pull/2352) ([nlohmann](https://github.com/nlohmann)) -- Remove -Wimplicit-fallthrough warning [\#2349](https://github.com/nlohmann/json/pull/2349) ([nlohmann](https://github.com/nlohmann)) -- Fix code to work without exceptions [\#2347](https://github.com/nlohmann/json/pull/2347) ([nlohmann](https://github.com/nlohmann)) -- fix cmake script overwriting compiler path [\#2344](https://github.com/nlohmann/json/pull/2344) ([ongjunjie](https://github.com/ongjunjie)) - -## [v3.9.1](https://github.com/nlohmann/json/releases/tag/v3.9.1) (2020-08-06) - -[Full Changelog](https://github.com/nlohmann/json/compare/v3.9.0...v3.9.1) - -- Can't parse not formatted JSON. [\#2340](https://github.com/nlohmann/json/issues/2340) -- parse returns desired array contained in array when JSON text begins with square bracket on gcc 7.5.0 [\#2339](https://github.com/nlohmann/json/issues/2339) -- Unexpected deserialization difference between Mac and Linux [\#2338](https://github.com/nlohmann/json/issues/2338) -- Reading ordered\_json from file causes compile error [\#2331](https://github.com/nlohmann/json/issues/2331) -- ignore\_comment=true fails on multiple consecutive lines starting with comments [\#2330](https://github.com/nlohmann/json/issues/2330) -- Update documentation about Homebrew installation and CMake integration - Homebrew [\#2326](https://github.com/nlohmann/json/issues/2326) -- Chinese character initialize error [\#2325](https://github.com/nlohmann/json/issues/2325) -- json.update and vector\does not work with ordered\_json [\#2315](https://github.com/nlohmann/json/issues/2315) -- Ambiguous call to overloaded function [\#2210](https://github.com/nlohmann/json/issues/2210) - -- Fix fallthrough warning [\#2333](https://github.com/nlohmann/json/pull/2333) ([nlohmann](https://github.com/nlohmann)) -- Fix lexer to properly cope with repeated comments [\#2332](https://github.com/nlohmann/json/pull/2332) ([nlohmann](https://github.com/nlohmann)) -- Fix name of Homebrew formula in documentation [\#2327](https://github.com/nlohmann/json/pull/2327) ([nlohmann](https://github.com/nlohmann)) -- fix typo [\#2320](https://github.com/nlohmann/json/pull/2320) ([wx257osn2](https://github.com/wx257osn2)) -- Fix a bug due to missing overloads in ordered\_map container [\#2319](https://github.com/nlohmann/json/pull/2319) ([nlohmann](https://github.com/nlohmann)) -- cmake: install pkg-config file relative to current\_binary\_dir [\#2318](https://github.com/nlohmann/json/pull/2318) ([eli-schwartz](https://github.com/eli-schwartz)) -- Fixed installation of pkg-config file on other than Ubuntu [\#2314](https://github.com/nlohmann/json/pull/2314) ([xvitaly](https://github.com/xvitaly)) - -## [v3.9.0](https://github.com/nlohmann/json/releases/tag/v3.9.0) (2020-07-27) - -[Full Changelog](https://github.com/nlohmann/json/compare/v3.8.0...v3.9.0) - -- Unknown Type Name clang error when using NLOHMANN\_DEFINE\_TYPE\_NON\_INTRUSIVE [\#2313](https://github.com/nlohmann/json/issues/2313) -- Clang 10.0 / GCC 10.1 warnings on disabled exceptions [\#2304](https://github.com/nlohmann/json/issues/2304) -- Application stalls indefinitely with message byte size 10 [\#2293](https://github.com/nlohmann/json/issues/2293) -- linker error [\#2292](https://github.com/nlohmann/json/issues/2292) -- Add support for high-precision numbers in UBJSON encoding [\#2286](https://github.com/nlohmann/json/issues/2286) -- NLOHMANN\_DEFINE\_TYPE\_NON\_INTRUSIVE fails if the length of the argument is 10 [\#2280](https://github.com/nlohmann/json/issues/2280) -- Custom types : MACRO expansion bug [\#2267](https://github.com/nlohmann/json/issues/2267) -- to/from\_json Failing To Convert String [\#2238](https://github.com/nlohmann/json/issues/2238) -- clang 9.0 report warning: unused type alias 'size\_type' \[-Wunused-local-typedef\] [\#2221](https://github.com/nlohmann/json/issues/2221) -- Enormous array created when working with map\ [\#2220](https://github.com/nlohmann/json/issues/2220) -- Can I disable sorting of json values [\#2219](https://github.com/nlohmann/json/issues/2219) -- Getting Qt types to work [\#2217](https://github.com/nlohmann/json/issues/2217) -- Convert to Qt QVariant [\#2216](https://github.com/nlohmann/json/issues/2216) -- How to custom serialize same data type of vector? [\#2215](https://github.com/nlohmann/json/issues/2215) -- json constructor does not support std::optional [\#2214](https://github.com/nlohmann/json/issues/2214) -- Failing to Parse Valid JSON [\#2209](https://github.com/nlohmann/json/issues/2209) -- \(De-\)Serialization of std::variant with namespaces [\#2208](https://github.com/nlohmann/json/issues/2208) -- Addint support for complex type [\#2207](https://github.com/nlohmann/json/issues/2207) -- array\_index possible out of range [\#2205](https://github.com/nlohmann/json/issues/2205) -- Object deserialized as array [\#2204](https://github.com/nlohmann/json/issues/2204) -- Sending to a function a reference to a sub-branch [\#2200](https://github.com/nlohmann/json/issues/2200) -- How to Serialize derived class to JSON object? [\#2199](https://github.com/nlohmann/json/issues/2199) -- JSON incorrectly serialized [\#2198](https://github.com/nlohmann/json/issues/2198) -- Exception Unhandled out\_of\_range error [\#2197](https://github.com/nlohmann/json/issues/2197) -- msgpack serialisation : float is treated as 64bit float, not 32bit float. [\#2196](https://github.com/nlohmann/json/issues/2196) -- Is it possible to use compile-time type guarantees for JSON structures? [\#2195](https://github.com/nlohmann/json/issues/2195) -- Question : performance against python dict [\#2194](https://github.com/nlohmann/json/issues/2194) -- vs2017 compile error [\#2192](https://github.com/nlohmann/json/issues/2192) -- Check if a key exists [\#2191](https://github.com/nlohmann/json/issues/2191) -- Failed to run tests due to missing test data on builders without Internet access [\#2190](https://github.com/nlohmann/json/issues/2190) -- 3.8.0: unit-cbor.cpp test failures [\#2189](https://github.com/nlohmann/json/issues/2189) -- 'nlohmann/json.hpp' file not found [\#2188](https://github.com/nlohmann/json/issues/2188) -- How to send json data over the wire? [\#2185](https://github.com/nlohmann/json/issues/2185) -- Ubuntu 16 not supporting nlohmann/json? [\#2184](https://github.com/nlohmann/json/issues/2184) -- .get\ causing emdash errors [\#2180](https://github.com/nlohmann/json/issues/2180) -- Object properties should not be re-sorted alphabetically [\#2179](https://github.com/nlohmann/json/issues/2179) -- Custom type registration : instrusive API [\#2175](https://github.com/nlohmann/json/issues/2175) -- Many version of the function "void to\_json\(json& j, const MyStruct& struct\)" [\#2171](https://github.com/nlohmann/json/issues/2171) -- How should strings be escaped? [\#2155](https://github.com/nlohmann/json/issues/2155) -- Adding a value to an existing json puts it at the beginning instead of the end [\#2149](https://github.com/nlohmann/json/issues/2149) -- The header file is big, can we use what we need. [\#2134](https://github.com/nlohmann/json/issues/2134) -- Changing the default format for unordered\_map \(or other set\) [\#2132](https://github.com/nlohmann/json/issues/2132) -- Getting size of deserialized bson document [\#2131](https://github.com/nlohmann/json/issues/2131) -- implicit conversion failure [\#2128](https://github.com/nlohmann/json/issues/2128) -- Error thrown when parsing in a subclass [\#2124](https://github.com/nlohmann/json/issues/2124) -- explicit conversion to string not considered for std::map keys in GCC8 [\#2096](https://github.com/nlohmann/json/issues/2096) -- Add support for JSONC [\#2061](https://github.com/nlohmann/json/issues/2061) -- Library provides template arg for string\_type but assumes std::string in some places [\#2059](https://github.com/nlohmann/json/issues/2059) -- incremental parsing with sax\_parser [\#2030](https://github.com/nlohmann/json/issues/2030) -- Question about flatten and unflatten [\#1989](https://github.com/nlohmann/json/issues/1989) -- CBOR parser doesn't skip tags [\#1968](https://github.com/nlohmann/json/issues/1968) -- Compilation failure using Clang on Windows [\#1898](https://github.com/nlohmann/json/issues/1898) -- Fail to build when including json.hpp as a system include [\#1818](https://github.com/nlohmann/json/issues/1818) -- Parsing string into json doesn't preserve the order correctly. [\#1817](https://github.com/nlohmann/json/issues/1817) -- \[C++17\] Allow std::optional to convert to nlohmann::json [\#1749](https://github.com/nlohmann/json/issues/1749) -- How can I save json object in file in order? [\#1717](https://github.com/nlohmann/json/issues/1717) -- Support for Comments [\#1513](https://github.com/nlohmann/json/issues/1513) -- clang compiler: error : unknown type name 'not' [\#1119](https://github.com/nlohmann/json/issues/1119) -- dump\(\) without alphabetical order [\#1106](https://github.com/nlohmann/json/issues/1106) -- operator T\(\) considered harmful [\#958](https://github.com/nlohmann/json/issues/958) -- Order of the elements in JSON object [\#952](https://github.com/nlohmann/json/issues/952) -- How to prevent alphabetical sorting of data? [\#727](https://github.com/nlohmann/json/issues/727) -- Why is an object ordering values by Alphabetical Order? [\#660](https://github.com/nlohmann/json/issues/660) -- Feature request: Comments [\#597](https://github.com/nlohmann/json/issues/597) -- Head Elements Sorting [\#543](https://github.com/nlohmann/json/issues/543) -- Automatic ordered JSON [\#424](https://github.com/nlohmann/json/issues/424) -- Support for comments. [\#376](https://github.com/nlohmann/json/issues/376) -- Optional comment support. [\#363](https://github.com/nlohmann/json/issues/363) -- Strip comments / Minify [\#294](https://github.com/nlohmann/json/issues/294) -- maintaining order of keys during iteration [\#106](https://github.com/nlohmann/json/issues/106) - -- Update documentation [\#2312](https://github.com/nlohmann/json/pull/2312) ([nlohmann](https://github.com/nlohmann)) -- Fix bug in CBOR tag handling [\#2308](https://github.com/nlohmann/json/pull/2308) ([nlohmann](https://github.com/nlohmann)) -- added inline to NLOHMANN\_DEFINE\_TYPE\_NON\_INTRUSIVE macro [\#2306](https://github.com/nlohmann/json/pull/2306) ([jwittbrodt](https://github.com/jwittbrodt)) -- fixes unused variable 'ex' for \#2304 [\#2305](https://github.com/nlohmann/json/pull/2305) ([AODQ](https://github.com/AODQ)) -- Cleanup [\#2303](https://github.com/nlohmann/json/pull/2303) ([nlohmann](https://github.com/nlohmann)) -- Add test with multiple translation units [\#2301](https://github.com/nlohmann/json/pull/2301) ([nlohmann](https://github.com/nlohmann)) -- Merge GitHub actions [\#2300](https://github.com/nlohmann/json/pull/2300) ([nlohmann](https://github.com/nlohmann)) -- Fix unused parameter [\#2299](https://github.com/nlohmann/json/pull/2299) ([nlohmann](https://github.com/nlohmann)) -- Add support for high-precision numbers in UBJSON encoding [\#2297](https://github.com/nlohmann/json/pull/2297) ([nlohmann](https://github.com/nlohmann)) -- fix eof for get\_binary and get\_string [\#2294](https://github.com/nlohmann/json/pull/2294) ([jprochazk](https://github.com/jprochazk)) -- Serialisation macros: increase upper bound on number of member variables [\#2287](https://github.com/nlohmann/json/pull/2287) ([pfeatherstone](https://github.com/pfeatherstone)) -- add inline specifier for detail::combine [\#2285](https://github.com/nlohmann/json/pull/2285) ([T0b1-iOS](https://github.com/T0b1-iOS)) -- Add static assertion for missing binary function in SAX interface [\#2282](https://github.com/nlohmann/json/pull/2282) ([nlohmann](https://github.com/nlohmann)) -- Add test for target\_include\_directories [\#2279](https://github.com/nlohmann/json/pull/2279) ([nlohmann](https://github.com/nlohmann)) -- Clean up maintainer Makefiles and fix some linter warnings [\#2274](https://github.com/nlohmann/json/pull/2274) ([nlohmann](https://github.com/nlohmann)) -- Add option to ignore CBOR tags [\#2273](https://github.com/nlohmann/json/pull/2273) ([nlohmann](https://github.com/nlohmann)) -- Hash function without allocation [\#2269](https://github.com/nlohmann/json/pull/2269) ([nlohmann](https://github.com/nlohmann)) -- Add ClangCL for MSVC [\#2268](https://github.com/nlohmann/json/pull/2268) ([t-b](https://github.com/t-b)) -- Makefile: Always use SED variable [\#2264](https://github.com/nlohmann/json/pull/2264) ([t-b](https://github.com/t-b)) -- Add Xcode 12 CI [\#2262](https://github.com/nlohmann/json/pull/2262) ([nlohmann](https://github.com/nlohmann)) -- Make library work with Clang on Windows [\#2259](https://github.com/nlohmann/json/pull/2259) ([nlohmann](https://github.com/nlohmann)) -- Add ordered\_json specialization with ordered object keys [\#2258](https://github.com/nlohmann/json/pull/2258) ([nlohmann](https://github.com/nlohmann)) -- Add pkg-config file [\#2253](https://github.com/nlohmann/json/pull/2253) ([ericonr](https://github.com/ericonr)) -- Fix regression from \#2181 [\#2251](https://github.com/nlohmann/json/pull/2251) ([nlohmann](https://github.com/nlohmann)) -- Tag binary values in cbor if set [\#2244](https://github.com/nlohmann/json/pull/2244) ([matthewbauer](https://github.com/matthewbauer)) -- Make assert configurable via JSON\_ASSERT [\#2242](https://github.com/nlohmann/json/pull/2242) ([nlohmann](https://github.com/nlohmann)) -- Add specialization of get\_to [\#2233](https://github.com/nlohmann/json/pull/2233) ([nlohmann](https://github.com/nlohmann)) -- Refine documentation of error\_handler parameter [\#2232](https://github.com/nlohmann/json/pull/2232) ([nlohmann](https://github.com/nlohmann)) -- Simplify conversion from/to custom types [\#2225](https://github.com/nlohmann/json/pull/2225) ([nlohmann](https://github.com/nlohmann)) -- Remove unused typedefs [\#2224](https://github.com/nlohmann/json/pull/2224) ([nlohmann](https://github.com/nlohmann)) -- Enable CMake policy CMP0077 [\#2222](https://github.com/nlohmann/json/pull/2222) ([alexreinking](https://github.com/alexreinking)) -- Add option to ignore comments in parse/accept functions [\#2212](https://github.com/nlohmann/json/pull/2212) ([nlohmann](https://github.com/nlohmann)) -- Fix Clang-Tidy warnings [\#2211](https://github.com/nlohmann/json/pull/2211) ([nlohmann](https://github.com/nlohmann)) -- Simple ordered\_json that works on all supported compilers [\#2206](https://github.com/nlohmann/json/pull/2206) ([gatopeich](https://github.com/gatopeich)) -- Use unsigned indizies for array index in json pointer [\#2203](https://github.com/nlohmann/json/pull/2203) ([t-b](https://github.com/t-b)) -- Add option to not rely on Internet connectivity during test stage [\#2202](https://github.com/nlohmann/json/pull/2202) ([nlohmann](https://github.com/nlohmann)) -- Serialize floating-point numbers with 32 bit when possible \(MessagePack\) [\#2201](https://github.com/nlohmann/json/pull/2201) ([nlohmann](https://github.com/nlohmann)) -- Fix consistency in function `int_to_string()` [\#2193](https://github.com/nlohmann/json/pull/2193) ([dota17](https://github.com/dota17)) -- Fix issue\#1275 [\#2181](https://github.com/nlohmann/json/pull/2181) ([dota17](https://github.com/dota17)) -- C++20 support by removing swap specialization [\#2176](https://github.com/nlohmann/json/pull/2176) ([gracicot](https://github.com/gracicot)) -- Feat/explicit conversion operator [\#1559](https://github.com/nlohmann/json/pull/1559) ([theodelrieu](https://github.com/theodelrieu)) - -## [v3.8.0](https://github.com/nlohmann/json/releases/tag/v3.8.0) (2020-06-14) - -[Full Changelog](https://github.com/nlohmann/json/compare/v3.7.3...v3.8.0) - -- sorry delete this issue, i'm stupid [\#2187](https://github.com/nlohmann/json/issues/2187) -- Append to a std::nlohmann::json type [\#2186](https://github.com/nlohmann/json/issues/2186) -- Some troubles to compile the last revision [\#2177](https://github.com/nlohmann/json/issues/2177) -- ​\#​ Top level CMakeLists.txt​ -​project​\(FOO\) -... -​option​\(FOO\_USE\_EXTERNAL\_JSON ​"Use an external JSON library"​ ​OFF​\) -... -​add\_subdirectory​\(thirdparty\) -... -​add\_library​\(foo ...\) -... -​\#​ Note that the namespaced target will always be available regardless of the​ -​\#​ import method​ -​target\_link\_libraries​\(foo ​PRIVATE​ nlohmann\_json::nlohmann\_json\) [\#2170](https://github.com/nlohmann/json/issues/2170) -- https://www.github.com/nlohmann/json/tree/develop/include%2Fnlohmann%2Fjson\_fwd.hpp [\#2169](https://github.com/nlohmann/json/issues/2169) -- templated from\_json of non primitive types causes gcc error [\#2168](https://github.com/nlohmann/json/issues/2168) -- few warnings/errors in copy assignment [\#2167](https://github.com/nlohmann/json/issues/2167) -- Different output when upgrading from clang 9 to clang 10 [\#2166](https://github.com/nlohmann/json/issues/2166) -- Cannot build with VS 2019 / C++17 [\#2163](https://github.com/nlohmann/json/issues/2163) -- Q: When I received an illegal string,How the program knows? [\#2162](https://github.com/nlohmann/json/issues/2162) -- Problem while reading a json file [\#2161](https://github.com/nlohmann/json/issues/2161) -- converting std::chrono::system\_clock::time\_point to json. [\#2159](https://github.com/nlohmann/json/issues/2159) -- how to parse vector\ format [\#2157](https://github.com/nlohmann/json/issues/2157) -- nlohmann::json and =nullptr [\#2156](https://github.com/nlohmann/json/issues/2156) -- test-cbor fails [\#2154](https://github.com/nlohmann/json/issues/2154) -- Accessing array inside array syntax? [\#2151](https://github.com/nlohmann/json/issues/2151) -- Best way to catch errors when querying json [\#2150](https://github.com/nlohmann/json/issues/2150) -- JSON Data Mapping Key-Value from other Key-Value [\#2148](https://github.com/nlohmann/json/issues/2148) -- Conflicts with std \ compiling with GCC 10 [\#2146](https://github.com/nlohmann/json/issues/2146) -- Incorrect CMake FetchContent example [\#2142](https://github.com/nlohmann/json/issues/2142) -- Help for a Beginner? [\#2141](https://github.com/nlohmann/json/issues/2141) -- Read Json from File [\#2139](https://github.com/nlohmann/json/issues/2139) -- How to feed a predefined integer value into json string [\#2138](https://github.com/nlohmann/json/issues/2138) -- getting json array inside json object [\#2135](https://github.com/nlohmann/json/issues/2135) -- Add .contains example to doc [\#2133](https://github.com/nlohmann/json/issues/2133) -- Is it safe to return string.c\_str\(\) received from get\(\)? [\#2130](https://github.com/nlohmann/json/issues/2130) -- GCC 10: Compilation error when including any before including json header in C++17 mode [\#2129](https://github.com/nlohmann/json/issues/2129) -- Intersection of two json files [\#2127](https://github.com/nlohmann/json/issues/2127) -- App crashes when dump method called for non ascii chars. [\#2126](https://github.com/nlohmann/json/issues/2126) -- iterator based erase method [\#2122](https://github.com/nlohmann/json/issues/2122) -- quick and convenient api to get/set nested json values [\#2120](https://github.com/nlohmann/json/issues/2120) -- assigning nullptr to std::string [\#2118](https://github.com/nlohmann/json/issues/2118) -- usless\_cast warnings with gcc 9.3 and 10.1 \(C++17\) [\#2114](https://github.com/nlohmann/json/issues/2114) -- clang 10 warning [\#2113](https://github.com/nlohmann/json/issues/2113) -- Possible incorrect \_MSC\_VER reference [\#2112](https://github.com/nlohmann/json/issues/2112) -- warning under gcc 10.1 [\#2110](https://github.com/nlohmann/json/issues/2110) -- Wdeprecated-declarations from GCC v10.1.0 [\#2109](https://github.com/nlohmann/json/issues/2109) -- Global std::vector from json [\#2108](https://github.com/nlohmann/json/issues/2108) -- heap-buffer-overflow when using nlohmann/json, ASAN, and gtest [\#2107](https://github.com/nlohmann/json/issues/2107) -- exception 0x770DC5AF when i read an special char in json file [\#2106](https://github.com/nlohmann/json/issues/2106) -- json::parse\(\) fails to parse a dump\(2,' '\) output, yet does successfully parse dump\(\) [\#2105](https://github.com/nlohmann/json/issues/2105) -- run test-udt error in MSVC 19.16.27034.0 [\#2103](https://github.com/nlohmann/json/issues/2103) -- Unable to dump to stringstream [\#2102](https://github.com/nlohmann/json/issues/2102) -- Can't ad an object in another objet [\#2101](https://github.com/nlohmann/json/issues/2101) -- Implicit conversion causes "cannot use operator\[\] with a string argument with string" [\#2098](https://github.com/nlohmann/json/issues/2098) -- C++20: char8\_t [\#2097](https://github.com/nlohmann/json/issues/2097) -- Compilation issues when included in project [\#2094](https://github.com/nlohmann/json/issues/2094) -- string value with null character causes infinite loop [\#2093](https://github.com/nlohmann/json/issues/2093) -- corrupted size vs. prev\_size \(aborted\) [\#2092](https://github.com/nlohmann/json/issues/2092) -- Get string field content without return std::string copy [\#2091](https://github.com/nlohmann/json/issues/2091) -- JSON Comments \(JSON 5\) [\#2090](https://github.com/nlohmann/json/issues/2090) -- Remove \#include \ [\#2089](https://github.com/nlohmann/json/issues/2089) -- JSON library as a git submodule [\#2088](https://github.com/nlohmann/json/issues/2088) -- Apple Clang 11.0.3 on MacOS Catalina 10.15.4 not compiling [\#2087](https://github.com/nlohmann/json/issues/2087) -- Value function return empty object even if it exist [\#2086](https://github.com/nlohmann/json/issues/2086) -- Cannot debug but Run works [\#2085](https://github.com/nlohmann/json/issues/2085) -- Question about serialization. [\#2084](https://github.com/nlohmann/json/issues/2084) -- How to include in an external project [\#2083](https://github.com/nlohmann/json/issues/2083) -- Missing tests for binary values [\#2082](https://github.com/nlohmann/json/issues/2082) -- How to override default string serialization? [\#2079](https://github.com/nlohmann/json/issues/2079) -- Can't have a json type as a property in an arbitrary type [\#2078](https://github.com/nlohmann/json/issues/2078) -- New release? [\#2075](https://github.com/nlohmann/json/issues/2075) -- CMake FetchContent \> Updating the documentation? [\#2073](https://github.com/nlohmann/json/issues/2073) -- How to convert STL Vector \(of user defined type\) to Json [\#2072](https://github.com/nlohmann/json/issues/2072) -- how to make an array of objects [\#2070](https://github.com/nlohmann/json/issues/2070) -- ‘\_\_int64’ was not declared [\#2068](https://github.com/nlohmann/json/issues/2068) -- \[json.exception.type\_error.317\] cannot serialize binary data to text JSON [\#2067](https://github.com/nlohmann/json/issues/2067) -- Unexpected end of input; expected '\[', '{', or a literal [\#2066](https://github.com/nlohmann/json/issues/2066) -- Json structure can be nested? [\#2065](https://github.com/nlohmann/json/issues/2065) -- Bug: returning reference to local temporary object [\#2064](https://github.com/nlohmann/json/issues/2064) -- Allow to use non strict parsing [\#2063](https://github.com/nlohmann/json/issues/2063) -- Crashing on json::at [\#2062](https://github.com/nlohmann/json/issues/2062) -- How to convert a const std::vector\ message to a json, to be able to parse it and extract information from it? Can you point to any examples? [\#2058](https://github.com/nlohmann/json/issues/2058) -- Nice library [\#2057](https://github.com/nlohmann/json/issues/2057) -- json.hpp:15372:22: error: expected unqualified-id if \(not std::isfinite\(x\)\): Started getting this bug after updating my XCode [\#2056](https://github.com/nlohmann/json/issues/2056) -- Confused as how I can extract the values from the JSON object. [\#2055](https://github.com/nlohmann/json/issues/2055) -- Warnings with GCC 10 [\#2052](https://github.com/nlohmann/json/issues/2052) -- Warnings with Clang 10 [\#2049](https://github.com/nlohmann/json/issues/2049) -- Update doctest [\#2048](https://github.com/nlohmann/json/issues/2048) -- Unclear error message: "cannot use operator\[\] with a string argument with array" [\#2047](https://github.com/nlohmann/json/issues/2047) -- Serializing std::variant\\> [\#2045](https://github.com/nlohmann/json/issues/2045) -- Crash when parse big jsonfile [\#2042](https://github.com/nlohmann/json/issues/2042) -- How to check if a key exists without silently generating null objects on the path [\#2041](https://github.com/nlohmann/json/issues/2041) -- Crash when traversing over items\(\) of temporary json objects [\#2040](https://github.com/nlohmann/json/issues/2040) -- How to parse multiple line value ? [\#2039](https://github.com/nlohmann/json/issues/2039) -- SAX API uses unsigned std::size\_t but -1 if element size is not known; [\#2037](https://github.com/nlohmann/json/issues/2037) -- How to parse big decimal data [\#2036](https://github.com/nlohmann/json/issues/2036) -- how use template \ struct adl\_serializer [\#2035](https://github.com/nlohmann/json/issues/2035) -- auto iterator returned by find to handle value depending if is string or numeric. [\#2032](https://github.com/nlohmann/json/issues/2032) -- pass find returned iterator to numeric variable. [\#2031](https://github.com/nlohmann/json/issues/2031) -- Parse error on valid json file [\#2029](https://github.com/nlohmann/json/issues/2029) -- Is here any elegant way to combine serialization and deserialization code? [\#2028](https://github.com/nlohmann/json/issues/2028) -- Notes about dump function [\#2027](https://github.com/nlohmann/json/issues/2027) -- Different JSON printouts for empty dictionary on Linux and Mac. [\#2026](https://github.com/nlohmann/json/issues/2026) -- easier way to get exception reason out of json\_sax\_dom\_callback\_parser without exceptions [\#2024](https://github.com/nlohmann/json/issues/2024) -- Using fifo\_map with base class and derived class [\#2023](https://github.com/nlohmann/json/issues/2023) -- Error reading JSON File [\#2022](https://github.com/nlohmann/json/issues/2022) -- Parse causing crash on android. Cannot catch. [\#2021](https://github.com/nlohmann/json/issues/2021) -- Extra backslashes in nested json [\#2020](https://github.com/nlohmann/json/issues/2020) -- How to create patch for merge\_patch input ? [\#2018](https://github.com/nlohmann/json/issues/2018) -- CppUTest/include/CppUTestExt/MockSupport.h:40: error: default argument for ‘MockFailureReporter\* failureReporterForThisCall’ has type ‘void\*’ [\#2017](https://github.com/nlohmann/json/issues/2017) -- including another file [\#2016](https://github.com/nlohmann/json/issues/2016) -- GNU PREREQ Error with gcc 9.3.0 [\#2015](https://github.com/nlohmann/json/issues/2015) -- Parse error: json.exception.parse\_error.101 - invalid string: ill-formed UTF-8 byte [\#2014](https://github.com/nlohmann/json/issues/2014) -- Add more flexibility to basic\_json's ObjectType \(and ArrayType\) [\#2013](https://github.com/nlohmann/json/issues/2013) -- afl persistent mode [\#2012](https://github.com/nlohmann/json/issues/2012) -- Compiler Errors under VS2019 in Appveyor CI [\#2009](https://github.com/nlohmann/json/issues/2009) -- Another compilation failure with Visual Studio [\#2007](https://github.com/nlohmann/json/issues/2007) -- Implicit cast to std::string broken again with VS2019 16.5.0 [\#2006](https://github.com/nlohmann/json/issues/2006) -- error: no matching member function for call to 'AddRaw' [\#2005](https://github.com/nlohmann/json/issues/2005) -- When I re-create an object again after the network request, an error is reported [\#2003](https://github.com/nlohmann/json/issues/2003) -- How to merge \(and not replace\) different Json::Value objects in jsoncpp [\#2001](https://github.com/nlohmann/json/issues/2001) -- scalar transforms to list [\#2000](https://github.com/nlohmann/json/issues/2000) -- Dump JSON containing multibyte characters [\#1999](https://github.com/nlohmann/json/issues/1999) -- Build error when modify value [\#1998](https://github.com/nlohmann/json/issues/1998) -- How do i include a vector of pointers in my json? [\#1997](https://github.com/nlohmann/json/issues/1997) -- Compiler error wrt incomplete types changed in gcc8.3.0-26 [\#1996](https://github.com/nlohmann/json/issues/1996) -- NaN-like comparison behavior of discarded is inconvenient [\#1988](https://github.com/nlohmann/json/issues/1988) -- Maintaining JSON package in my CMake [\#1987](https://github.com/nlohmann/json/issues/1987) -- reading int number and string number [\#1986](https://github.com/nlohmann/json/issues/1986) -- Build error: keyword is hidden by macro definition! [\#1985](https://github.com/nlohmann/json/issues/1985) -- JSON patch diff for op=add formation is not as per standard \(RFC 6902\) [\#1983](https://github.com/nlohmann/json/issues/1983) -- json\_pointer.contains\(\) exception is incorrectly raised [\#1982](https://github.com/nlohmann/json/issues/1982) -- Error with non existing key [\#1981](https://github.com/nlohmann/json/issues/1981) -- Closed [\#1978](https://github.com/nlohmann/json/issues/1978) -- Where is the library built and what is the name? [\#1977](https://github.com/nlohmann/json/issues/1977) -- The cmake\_import example does not build [\#1976](https://github.com/nlohmann/json/issues/1976) -- Dumping core when reading invalid file [\#1975](https://github.com/nlohmann/json/issues/1975) -- Abort in dump\(\) method [\#1973](https://github.com/nlohmann/json/issues/1973) -- Unclear docs regarding parser\_callback\_t callbacks [\#1972](https://github.com/nlohmann/json/issues/1972) -- Possible memory leak on push\_back [\#1971](https://github.com/nlohmann/json/issues/1971) -- Is it possible to get a safe mutable reference/pointer to internal variant used in nlohmann json? [\#1970](https://github.com/nlohmann/json/issues/1970) -- Getting a flatten json to map\ [\#1957](https://github.com/nlohmann/json/issues/1957) -- forced type conversion or lexical cast without exception. [\#1955](https://github.com/nlohmann/json/issues/1955) -- Add json\_view type support to avoid excessive copying [\#1954](https://github.com/nlohmann/json/issues/1954) -- Adding "examples" section for real-life usages [\#1953](https://github.com/nlohmann/json/issues/1953) -- Add nlohmann::json::key\_type [\#1951](https://github.com/nlohmann/json/issues/1951) -- cannot use operator\[\] with a string argument with string [\#1949](https://github.com/nlohmann/json/issues/1949) -- std::ifstream \>\> json error [\#1948](https://github.com/nlohmann/json/issues/1948) -- Cannot update json data in an iterator? [\#1947](https://github.com/nlohmann/json/issues/1947) -- How can i build this library in VS 2017? [\#1943](https://github.com/nlohmann/json/issues/1943) -- json\_pointer.contains\(\) exceptions when path not found [\#1942](https://github.com/nlohmann/json/issues/1942) -- Nested objects serialize/deserialize [\#1941](https://github.com/nlohmann/json/issues/1941) -- Compile warning on architectures that are not x86 [\#1939](https://github.com/nlohmann/json/issues/1939) -- Version of nlohmann-json-dev in debian packages [\#1938](https://github.com/nlohmann/json/issues/1938) -- Create a json object for every cycle [\#1937](https://github.com/nlohmann/json/issues/1937) -- How to get the object name? [\#1936](https://github.com/nlohmann/json/issues/1936) -- Reserve and resize function for basic json [\#1935](https://github.com/nlohmann/json/issues/1935) -- How to use json parse in tsl::ordread\_map? [\#1934](https://github.com/nlohmann/json/issues/1934) -- C++14 support is not enabled with msvc2015 [\#1932](https://github.com/nlohmann/json/issues/1932) -- Need help with to\_json for derived class, keep getting "cannot use operator" [\#1931](https://github.com/nlohmann/json/issues/1931) -- How to handle std::vector\ [\#1930](https://github.com/nlohmann/json/issues/1930) -- Heap corruption issue [\#1929](https://github.com/nlohmann/json/issues/1929) -- Add `std::wistream` support. [\#1928](https://github.com/nlohmann/json/issues/1928) -- This i can write and read any file thanks [\#1927](https://github.com/nlohmann/json/issues/1927) -- How can I get this simple example working? [\#1926](https://github.com/nlohmann/json/issues/1926) -- emplace\_back does not seems to work with the int 0 [\#1925](https://github.com/nlohmann/json/issues/1925) -- Why nlohmann does not release memory [\#1924](https://github.com/nlohmann/json/issues/1924) -- Is it possible to have template `json::parse` with `noexcept` specifier? [\#1922](https://github.com/nlohmann/json/issues/1922) -- JSON to wstring? [\#1921](https://github.com/nlohmann/json/issues/1921) -- GCC 10 tests build failure [\#1920](https://github.com/nlohmann/json/issues/1920) -- Size of binary json representations [\#1919](https://github.com/nlohmann/json/issues/1919) -- Accessing strings \(for example in keys or values\) without having the lib create a copy of it. [\#1916](https://github.com/nlohmann/json/issues/1916) -- operator== documentation should show how to apply custom comparison function [\#1915](https://github.com/nlohmann/json/issues/1915) -- char8\_t and std::u8string support [\#1914](https://github.com/nlohmann/json/issues/1914) -- std::is\_pod is deprecated in C++20 [\#1913](https://github.com/nlohmann/json/issues/1913) -- Incomplete types reported by \(experimental\) GCC10 [\#1912](https://github.com/nlohmann/json/issues/1912) -- Compile warnings on MSVC 14.2 [\#1911](https://github.com/nlohmann/json/issues/1911) -- How to parse json file with type composition of std::optional and std::variant [\#1910](https://github.com/nlohmann/json/issues/1910) -- why root\_schema be implemented as unique\_ptr in json-validator.cpp,could I use it as shared\_ptr? [\#1908](https://github.com/nlohmann/json/issues/1908) -- compile error in gcc-6.3.0 [\#1906](https://github.com/nlohmann/json/issues/1906) -- Scalar constexpr is odr-used when used as json initializer [\#1905](https://github.com/nlohmann/json/issues/1905) -- install Slack app [\#1904](https://github.com/nlohmann/json/issues/1904) -- typo in a comment [\#1903](https://github.com/nlohmann/json/issues/1903) -- Watch JSON variables in Debug [\#1902](https://github.com/nlohmann/json/issues/1902) -- does Json sdk cares about dfc dfd utf8 issue? [\#1901](https://github.com/nlohmann/json/issues/1901) -- Allow multiple line string value in JSON [\#1897](https://github.com/nlohmann/json/issues/1897) -- Writing map to json file [\#1896](https://github.com/nlohmann/json/issues/1896) -- Small documentation mistake [\#1895](https://github.com/nlohmann/json/issues/1895) -- why static function `parse` cann't find in visual studio 2019 [\#1894](https://github.com/nlohmann/json/issues/1894) -- Best way to handle json files with missing key value pairs. [\#1893](https://github.com/nlohmann/json/issues/1893) -- accessing json object as multimap [\#1892](https://github.com/nlohmann/json/issues/1892) -- What is the best way to parse vec3s into glm::vec3 [\#1891](https://github.com/nlohmann/json/issues/1891) -- Get array of items without using vector [\#1890](https://github.com/nlohmann/json/issues/1890) -- Build errors \(clang 11.0.0\) on macOS 10.15.2 [\#1889](https://github.com/nlohmann/json/issues/1889) -- Multiple arrays to vectors help [\#1888](https://github.com/nlohmann/json/issues/1888) -- json::parse\(begin, end\) parse error on first character using uchar\* [\#1887](https://github.com/nlohmann/json/issues/1887) -- issue in free\(\) [\#1886](https://github.com/nlohmann/json/issues/1886) -- is\_number\_unsigned\(\) returns false for positive integers \(int or 0 or 1 literals\) [\#1885](https://github.com/nlohmann/json/issues/1885) -- MSVC build failure with /Zc:\_\_cplusplus and C++17 [\#1883](https://github.com/nlohmann/json/issues/1883) -- RFC 6901 op:replace & arrays [\#1882](https://github.com/nlohmann/json/issues/1882) -- Problem with serialization of my custom template doubly-linked list [\#1881](https://github.com/nlohmann/json/issues/1881) -- is\_array\(\) is True, but raise 'cannot use operator\[\] for object iterators' [\#1880](https://github.com/nlohmann/json/issues/1880) -- Serialize dynamic array [\#1879](https://github.com/nlohmann/json/issues/1879) -- Serialization of struct object. [\#1877](https://github.com/nlohmann/json/issues/1877) -- warning:c4503 [\#1875](https://github.com/nlohmann/json/issues/1875) -- Why are flattened empty objects/arrays not representable? [\#1874](https://github.com/nlohmann/json/issues/1874) -- Container Overflow \(ASAN\) when using operator \>\> on an ifs [\#1873](https://github.com/nlohmann/json/issues/1873) -- Sub-array to vector or map object? [\#1870](https://github.com/nlohmann/json/issues/1870) -- WIP: QT \(cute\) type supports [\#1869](https://github.com/nlohmann/json/issues/1869) -- Compiler flags to disable features and shrink code size [\#1868](https://github.com/nlohmann/json/issues/1868) -- null strings [\#1867](https://github.com/nlohmann/json/issues/1867) -- Struct with array of struct and \_\_attribute\_\_\(\(packed\)\) [\#1866](https://github.com/nlohmann/json/issues/1866) -- Best way to extract numbers in the string? [\#1865](https://github.com/nlohmann/json/issues/1865) -- Displaying \\?\Volume{guid} from string to json giving error [\#1864](https://github.com/nlohmann/json/issues/1864) -- not working when compiling as x86 [\#1863](https://github.com/nlohmann/json/issues/1863) -- Skipping evaluation of log line expressions with a macro, is it possible? [\#1862](https://github.com/nlohmann/json/issues/1862) -- Suppress warnings [\#1861](https://github.com/nlohmann/json/issues/1861) -- conflit with g++ compile option -mwindows [\#1860](https://github.com/nlohmann/json/issues/1860) -- How to serialize nested classes to semi-flat JSON object? [\#1859](https://github.com/nlohmann/json/issues/1859) -- Memory Requirement for large json file [\#1858](https://github.com/nlohmann/json/issues/1858) -- Query a binary format \(BSON, CBOR, MessagePack, UBJSON\) [\#1856](https://github.com/nlohmann/json/issues/1856) -- Documentation on operator\[\] behavior with missing keys [\#1855](https://github.com/nlohmann/json/issues/1855) -- Problem in converting string into JSON; Can't parse successfully. [\#1854](https://github.com/nlohmann/json/issues/1854) -- json.at\_or\_default\(key, defaultval\) [\#1852](https://github.com/nlohmann/json/issues/1852) -- please improve the enum conversion documentation \(my example gist provided\) [\#1851](https://github.com/nlohmann/json/issues/1851) -- Default value returned on ValueType nlohmann::basic\_json::value \(const typename object\_t::key\_type& key, const ValueType& default\_value\) [\#1850](https://github.com/nlohmann/json/issues/1850) -- Accounting for arbitrary precision numerical literals [\#1849](https://github.com/nlohmann/json/issues/1849) -- While trying to make a simple array, I get a nested array instead [\#1848](https://github.com/nlohmann/json/issues/1848) -- How to reuse the parser and serializer intermediate storage? [\#1847](https://github.com/nlohmann/json/issues/1847) -- Too much content in json.hpp leads to slow compilation [\#1845](https://github.com/nlohmann/json/issues/1845) -- Cannot read some data in json file [\#1843](https://github.com/nlohmann/json/issues/1843) -- Precompiled JSON library? [\#1842](https://github.com/nlohmann/json/issues/1842) -- Please change assert into throw\(maybe\) in line 17946 [\#1841](https://github.com/nlohmann/json/issues/1841) -- JSON for modern C++ ECCN information [\#1840](https://github.com/nlohmann/json/issues/1840) -- CI: reduce build time for Travis valgrind [\#1836](https://github.com/nlohmann/json/issues/1836) -- How do I traverse a json object and add new elements into the hierarchy [\#1834](https://github.com/nlohmann/json/issues/1834) -- Invalid UTF-8 byte at index 1: 0x65 [\#1831](https://github.com/nlohmann/json/issues/1831) -- Serialize big data in json [\#1828](https://github.com/nlohmann/json/issues/1828) -- Backslash '\' in value causes exception [\#1827](https://github.com/nlohmann/json/issues/1827) -- from\_json for non default constructible class with dependency injection [\#1819](https://github.com/nlohmann/json/issues/1819) -- Semi-frequent timeouts in `test-unicode_all` with 3.6.1 \(aarch64\) [\#1816](https://github.com/nlohmann/json/issues/1816) -- input\_adapter not user extensible [\#1813](https://github.com/nlohmann/json/issues/1813) -- crash at json::destroy on android [\#1812](https://github.com/nlohmann/json/issues/1812) -- Logs are repeating while cmake [\#1809](https://github.com/nlohmann/json/issues/1809) -- Add a the possibility to add dynamic json objects [\#1795](https://github.com/nlohmann/json/issues/1795) -- Unnecessary test data file in the release [\#1790](https://github.com/nlohmann/json/issues/1790) -- Add support for parse stack limiting [\#1788](https://github.com/nlohmann/json/issues/1788) -- GCC -Wuseless-cast warnings [\#1777](https://github.com/nlohmann/json/issues/1777) -- compilation issue with NVCC 9.0 [\#1773](https://github.com/nlohmann/json/issues/1773) -- Unexpected behavior with fifo\_map json when copy and append [\#1763](https://github.com/nlohmann/json/issues/1763) -- Parse error [\#1761](https://github.com/nlohmann/json/issues/1761) -- Assignment \(using value\(\)\) to nonexistent element behaves differently on Xcode 8 vs Xcode 10 [\#1758](https://github.com/nlohmann/json/issues/1758) -- Readme out of date [\#1756](https://github.com/nlohmann/json/issues/1756) -- cmake\_\* tests don't use the build system's compiler [\#1747](https://github.com/nlohmann/json/issues/1747) -- Static assertions for template type properties required [\#1729](https://github.com/nlohmann/json/issues/1729) -- Use float and possibly half in json::to\_cbor [\#1719](https://github.com/nlohmann/json/issues/1719) -- json::from\_cbor does not respect allow\_exceptions = false when input is string literal [\#1715](https://github.com/nlohmann/json/issues/1715) -- /Zc:\_\_cplusplus leads to C2416 [\#1695](https://github.com/nlohmann/json/issues/1695) -- `unflatten` vs objects with number-ish keys [\#1575](https://github.com/nlohmann/json/issues/1575) -- A "thinner" source code tar as part of release? [\#1572](https://github.com/nlohmann/json/issues/1572) -- Repository is almost 450MB [\#1497](https://github.com/nlohmann/json/issues/1497) -- Substantial performance penalty caused by polymorphic input adapter [\#1457](https://github.com/nlohmann/json/issues/1457) -- Move tests to a separate repo [\#1235](https://github.com/nlohmann/json/issues/1235) -- reduce repos size [\#1185](https://github.com/nlohmann/json/issues/1185) -- CMakeLists.txt in release zips? [\#1184](https://github.com/nlohmann/json/issues/1184) -- Minimal branch? [\#1066](https://github.com/nlohmann/json/issues/1066) -- Move test blobs to a submodule? [\#732](https://github.com/nlohmann/json/issues/732) -- \[Question\] When using this as git submodule, will it clone the whole thing include test data and benchmark? [\#620](https://github.com/nlohmann/json/issues/620) -- Need to improve ignores.. [\#567](https://github.com/nlohmann/json/issues/567) -- Minimal repository \(current size very large\) [\#556](https://github.com/nlohmann/json/issues/556) -- For a header-only library you have to clone 214MB [\#482](https://github.com/nlohmann/json/issues/482) -- 17 MB / 90 MB repo size!? [\#96](https://github.com/nlohmann/json/issues/96) - -- Improve parse\_ubjson\_fuzzer [\#2182](https://github.com/nlohmann/json/pull/2182) ([tanuj208](https://github.com/tanuj208)) -- Add input adapter tests [\#2178](https://github.com/nlohmann/json/pull/2178) ([nlohmann](https://github.com/nlohmann)) -- Fix warnings [\#2174](https://github.com/nlohmann/json/pull/2174) ([nlohmann](https://github.com/nlohmann)) -- Fix PR\#1006 [\#2158](https://github.com/nlohmann/json/pull/2158) ([dota17](https://github.com/dota17)) -- Fix issue\#1972 [\#2153](https://github.com/nlohmann/json/pull/2153) ([dota17](https://github.com/dota17)) -- Update URLs to HTTPS [\#2152](https://github.com/nlohmann/json/pull/2152) ([TotalCaesar659](https://github.com/TotalCaesar659)) -- Fix Issue\#1813: user defined input adapters [\#2145](https://github.com/nlohmann/json/pull/2145) ([FrancoisChabot](https://github.com/FrancoisChabot)) -- Fix issue\#1939: Cast character to unsigned for comparison [\#2144](https://github.com/nlohmann/json/pull/2144) ([XyFreak](https://github.com/XyFreak)) -- Fix issue\#2142: readme: fix typo in CMake FetchContent example [\#2143](https://github.com/nlohmann/json/pull/2143) ([quentin-dev](https://github.com/quentin-dev)) -- Respect allow\_exceptions=false for binary formats [\#2140](https://github.com/nlohmann/json/pull/2140) ([nlohmann](https://github.com/nlohmann)) -- Fix issue 2112 [\#2137](https://github.com/nlohmann/json/pull/2137) ([dota17](https://github.com/dota17)) -- Add bleeding edge GCC to CI [\#2136](https://github.com/nlohmann/json/pull/2136) ([aokellermann](https://github.com/aokellermann)) -- Clean up implementation of binary type [\#2125](https://github.com/nlohmann/json/pull/2125) ([nlohmann](https://github.com/nlohmann)) -- Fixed a compilation error in MSVC [\#2121](https://github.com/nlohmann/json/pull/2121) ([gistrec](https://github.com/gistrec)) -- Overwork CI [\#2119](https://github.com/nlohmann/json/pull/2119) ([nlohmann](https://github.com/nlohmann)) -- Fix warnings from Clang 10 and GCC 9 [\#2116](https://github.com/nlohmann/json/pull/2116) ([nlohmann](https://github.com/nlohmann)) -- Do not include \ when using C++17 [\#2115](https://github.com/nlohmann/json/pull/2115) ([nlohmann](https://github.com/nlohmann)) -- Fix issue\#2086: disallow json::value\_t type parameter in value\(\) [\#2104](https://github.com/nlohmann/json/pull/2104) ([dota17](https://github.com/dota17)) -- Fix Coveralls integration [\#2100](https://github.com/nlohmann/json/pull/2100) ([nlohmann](https://github.com/nlohmann)) -- Add tests for binary values [\#2099](https://github.com/nlohmann/json/pull/2099) ([nlohmann](https://github.com/nlohmann)) -- Use external test data [\#2081](https://github.com/nlohmann/json/pull/2081) ([nlohmann](https://github.com/nlohmann)) -- Remove Doozer CI [\#2080](https://github.com/nlohmann/json/pull/2080) ([nlohmann](https://github.com/nlohmann)) -- Fix README.md. Missing ``` [\#2077](https://github.com/nlohmann/json/pull/2077) ([ArthurSonzogni](https://github.com/ArthurSonzogni)) -- Fix error message about invalid surrogate pairs [\#2076](https://github.com/nlohmann/json/pull/2076) ([rmisev](https://github.com/rmisev)) -- Add CMake fetchcontent documentation and tests [\#2074](https://github.com/nlohmann/json/pull/2074) ([ArthurSonzogni](https://github.com/ArthurSonzogni)) -- Properly pass serialize\_binary to dump function [\#2071](https://github.com/nlohmann/json/pull/2071) ([nlohmann](https://github.com/nlohmann)) -- Fix returning reference to local temporary object [\#2069](https://github.com/nlohmann/json/pull/2069) ([nlohmann](https://github.com/nlohmann)) -- updated wandbox link [\#2060](https://github.com/nlohmann/json/pull/2060) ([alexandermyasnikov](https://github.com/alexandermyasnikov)) -- Fix bug in diff function [\#2054](https://github.com/nlohmann/json/pull/2054) ([nlohmann](https://github.com/nlohmann)) -- Fix GCC compiler warnings [\#2053](https://github.com/nlohmann/json/pull/2053) ([nlohmann](https://github.com/nlohmann)) -- Fix Clang compiler warnings [\#2051](https://github.com/nlohmann/json/pull/2051) ([nlohmann](https://github.com/nlohmann)) -- Update doctest to 2.3.7 [\#2050](https://github.com/nlohmann/json/pull/2050) ([nlohmann](https://github.com/nlohmann)) -- Fix issue\#1719 [\#2044](https://github.com/nlohmann/json/pull/2044) ([dota17](https://github.com/dota17)) -- Add missing testcase about NaN in unit-constructor1.cpp [\#2043](https://github.com/nlohmann/json/pull/2043) ([dota17](https://github.com/dota17)) -- Templatize basic\_json constructor from json\_ref [\#2034](https://github.com/nlohmann/json/pull/2034) ([ArtemSarmini](https://github.com/ArtemSarmini)) -- Replace deprecated std::is\_pod [\#2033](https://github.com/nlohmann/json/pull/2033) ([nlohmann](https://github.com/nlohmann)) -- Fixes \#1971 \(memory leak in basic\_json::push\_back\) [\#2025](https://github.com/nlohmann/json/pull/2025) ([ArtemSarmini](https://github.com/ArtemSarmini)) -- fix \#1982:json\_pointer.contains\(\) exception is incorrectly raised [\#2019](https://github.com/nlohmann/json/pull/2019) ([dota17](https://github.com/dota17)) -- Update LICENSE.MIT [\#2010](https://github.com/nlohmann/json/pull/2010) ([magamig](https://github.com/magamig)) -- PR for \#2006 to test in AppVeyor. [\#2008](https://github.com/nlohmann/json/pull/2008) ([garethsb](https://github.com/garethsb)) -- Added wsjcpp.yml [\#2004](https://github.com/nlohmann/json/pull/2004) ([sea-kg](https://github.com/sea-kg)) -- fix error 'setw' is not a member of 'std' in Wandbox example [\#2002](https://github.com/nlohmann/json/pull/2002) ([alexandermyasnikov](https://github.com/alexandermyasnikov)) -- catch exceptions for json\_pointer : ..../+99 [\#1990](https://github.com/nlohmann/json/pull/1990) ([dota17](https://github.com/dota17)) -- Modify the document about operator== [\#1984](https://github.com/nlohmann/json/pull/1984) ([dota17](https://github.com/dota17)) -- Rename argument array\_index to array\_indx in json\_pointer methods [\#1980](https://github.com/nlohmann/json/pull/1980) ([linev](https://github.com/linev)) -- README: Fix string representation of `dump`ed `json` [\#1979](https://github.com/nlohmann/json/pull/1979) ([alexweej](https://github.com/alexweej)) -- fix warnings in serializer.hpp for VS2019 [\#1969](https://github.com/nlohmann/json/pull/1969) ([dota17](https://github.com/dota17)) -- Fix C26451 warnnings in to\_chars.hpp [\#1967](https://github.com/nlohmann/json/pull/1967) ([dota17](https://github.com/dota17)) -- appveyor.yml: Compile and test with latest version for \_\_cplusplus ma… [\#1958](https://github.com/nlohmann/json/pull/1958) ([t-b](https://github.com/t-b)) -- Fix typo in examples [\#1956](https://github.com/nlohmann/json/pull/1956) ([dota17](https://github.com/dota17)) -- templated input adapters [\#1950](https://github.com/nlohmann/json/pull/1950) ([FrancoisChabot](https://github.com/FrancoisChabot)) -- Update README.md : add a FAQ about memory release [\#1933](https://github.com/nlohmann/json/pull/1933) ([dota17](https://github.com/dota17)) -- Some typos [\#1923](https://github.com/nlohmann/json/pull/1923) ([Coeur](https://github.com/Coeur)) -- Fix link to parse function in README [\#1918](https://github.com/nlohmann/json/pull/1918) ([kastiglione](https://github.com/kastiglione)) -- Readme: Updated links to hunter repo & docs [\#1917](https://github.com/nlohmann/json/pull/1917) ([jothepro](https://github.com/jothepro)) -- Adds instruction for using Build2's package manager [\#1909](https://github.com/nlohmann/json/pull/1909) ([Klaim](https://github.com/Klaim)) -- Update README.md [\#1907](https://github.com/nlohmann/json/pull/1907) ([pauljurczak](https://github.com/pauljurczak)) -- Fix warning: ignoring return value [\#1871](https://github.com/nlohmann/json/pull/1871) ([sonulohani](https://github.com/sonulohani)) -- docs: add central repository as conan source to readme [\#1857](https://github.com/nlohmann/json/pull/1857) ([gocarlos](https://github.com/gocarlos)) -- README: Package in MSYS2 renamed to nlohmann-json [\#1853](https://github.com/nlohmann/json/pull/1853) ([podsvirov](https://github.com/podsvirov)) -- Fix msvc warnings [\#1846](https://github.com/nlohmann/json/pull/1846) ([MBalszun](https://github.com/MBalszun)) -- Update tests that generate CMake projects to use main project's C++ compiler [\#1844](https://github.com/nlohmann/json/pull/1844) ([Tridacnid](https://github.com/Tridacnid)) -- make CMake's version config file architecture-independent [\#1746](https://github.com/nlohmann/json/pull/1746) ([uhoreg](https://github.com/uhoreg)) -- Add binary type support to all binary file formats, as well as an internally represented binary type [\#1662](https://github.com/nlohmann/json/pull/1662) ([OmnipotentEntity](https://github.com/OmnipotentEntity)) - -## [v3.7.3](https://github.com/nlohmann/json/releases/tag/v3.7.3) (2019-11-17) - -[Full Changelog](https://github.com/nlohmann/json/compare/v3.7.2...v3.7.3) - -- Project branches [\#1839](https://github.com/nlohmann/json/issues/1839) -- Quadratic destruction complexity introduced in \#1436 [\#1837](https://github.com/nlohmann/json/issues/1837) -- Trying to open a file [\#1814](https://github.com/nlohmann/json/issues/1814) -- Comparing data type with value\_t::number\_integer fails [\#1783](https://github.com/nlohmann/json/issues/1783) -- CMake version config file is architecture-dependent [\#1697](https://github.com/nlohmann/json/issues/1697) - -- Fix quadratic destruction complexity [\#1838](https://github.com/nlohmann/json/pull/1838) ([nickaein](https://github.com/nickaein)) - -## [v3.7.2](https://github.com/nlohmann/json/releases/tag/v3.7.2) (2019-11-10) - -[Full Changelog](https://github.com/nlohmann/json/compare/v3.7.1...v3.7.2) - -- Segmentation fault in destructor in case of large inputs [\#1835](https://github.com/nlohmann/json/issues/1835) -- type\_name\(\) is not consistent with type\(\) [\#1833](https://github.com/nlohmann/json/issues/1833) -- json::parse is not a member [\#1832](https://github.com/nlohmann/json/issues/1832) -- How do you deal with json\* ? [\#1829](https://github.com/nlohmann/json/issues/1829) -- Combined find\_package/add\_subdirectory not linking libraries [\#1771](https://github.com/nlohmann/json/issues/1771) -- example code for ifstream reading a json file results in no operator error [\#1766](https://github.com/nlohmann/json/issues/1766) -- Warning: unsequenced modification and access to 'range' [\#1674](https://github.com/nlohmann/json/issues/1674) -- Segmentation fault \(stack overflow\) due to unbounded recursion [\#1419](https://github.com/nlohmann/json/issues/1419) -- Stack-overflow \(OSS-Fuzz 4234\) [\#832](https://github.com/nlohmann/json/issues/832) - -- Configure WhiteSource Bolt for GitHub [\#1830](https://github.com/nlohmann/json/pull/1830) ([mend-bolt-for-github[bot]](https://github.com/apps/mend-bolt-for-github)) -- Prevent stackoverflow caused by recursive deconstruction [\#1436](https://github.com/nlohmann/json/pull/1436) ([nickaein](https://github.com/nickaein)) - -## [v3.7.1](https://github.com/nlohmann/json/releases/tag/v3.7.1) (2019-11-06) - -[Full Changelog](https://github.com/nlohmann/json/compare/v3.7.0...v3.7.1) - -- std::is\_constructible is always true with tuple [\#1825](https://github.com/nlohmann/json/issues/1825) -- Can't compile from\_json\(std::valarray\\). [\#1824](https://github.com/nlohmann/json/issues/1824) -- json class should have a get\_or member function [\#1823](https://github.com/nlohmann/json/issues/1823) -- NLOHMANN\_JSON\_SERIALIZE\_ENUM macro capture's json objects by value [\#1822](https://github.com/nlohmann/json/issues/1822) -- Parse fails when number literals start with zero [\#1820](https://github.com/nlohmann/json/issues/1820) -- Weird behaviour of `contains` with `json_pointer` [\#1815](https://github.com/nlohmann/json/issues/1815) -- strange behaviour with json\_pointer and .contains\(\) [\#1811](https://github.com/nlohmann/json/issues/1811) -- Can \#1695 be re-opened? [\#1808](https://github.com/nlohmann/json/issues/1808) -- Merge two json objects [\#1807](https://github.com/nlohmann/json/issues/1807) -- std::is\_constructible\\> when to\_json not defined [\#1805](https://github.com/nlohmann/json/issues/1805) -- Private data on parsing [\#1802](https://github.com/nlohmann/json/issues/1802) -- Capturing Line and Position when querying [\#1800](https://github.com/nlohmann/json/issues/1800) -- json error on parsing DBL\_MAX from string [\#1796](https://github.com/nlohmann/json/issues/1796) -- De/Serialisation of vector of tupple object with nested obect need Help please [\#1794](https://github.com/nlohmann/json/issues/1794) -- Output json is corrupted [\#1793](https://github.com/nlohmann/json/issues/1793) -- variable name byte sometimes used as a \#define [\#1792](https://github.com/nlohmann/json/issues/1792) -- Can't read json file [\#1791](https://github.com/nlohmann/json/issues/1791) -- Problems with special German letters [\#1789](https://github.com/nlohmann/json/issues/1789) -- Support for trailing commas [\#1787](https://github.com/nlohmann/json/issues/1787) -- json\_pointer construction bug [\#1786](https://github.com/nlohmann/json/issues/1786) -- Visual Studio 2017 warning [\#1784](https://github.com/nlohmann/json/issues/1784) -- ciso646 header become obsolete [\#1782](https://github.com/nlohmann/json/issues/1782) -- Migrate LGTM.com installation from OAuth to GitHub App [\#1781](https://github.com/nlohmann/json/issues/1781) -- JSON comparison, contains and operator& [\#1778](https://github.com/nlohmann/json/issues/1778) -- pass a json object to a class contructor adds an array around the object [\#1776](https://github.com/nlohmann/json/issues/1776) -- 'Float' number\_float\_function\_t template parameter name conflicts with C '\#define Float float' [\#1775](https://github.com/nlohmann/json/issues/1775) -- A weird building problem :-\( [\#1774](https://github.com/nlohmann/json/issues/1774) -- What is this json\_ref? [\#1772](https://github.com/nlohmann/json/issues/1772) -- Interoperability with other languages [\#1770](https://github.com/nlohmann/json/issues/1770) -- Json dump [\#1768](https://github.com/nlohmann/json/issues/1768) -- json\_pointer\<\>::back\(\) should be const [\#1764](https://github.com/nlohmann/json/issues/1764) -- How to get value from array [\#1762](https://github.com/nlohmann/json/issues/1762) -- Merge two jsons [\#1757](https://github.com/nlohmann/json/issues/1757) -- Unable to locate nlohmann\_jsonConfig.cmake [\#1755](https://github.com/nlohmann/json/issues/1755) -- json.hpp won;t compile VS2019 CLR/CLI app but does in console app [\#1754](https://github.com/nlohmann/json/issues/1754) -- \[Nested Json Objects\] Segmentation fault [\#1753](https://github.com/nlohmann/json/issues/1753) -- remove/replace assert with exceptions [\#1752](https://github.com/nlohmann/json/issues/1752) -- Add array support for update\(\) function [\#1751](https://github.com/nlohmann/json/issues/1751) -- Is there a reason the `get_to` method is defined in `include/nlohmann/json.hpp` but not in `single_include/nlohmann/json.hpp`? [\#1750](https://github.com/nlohmann/json/issues/1750) -- how to validate json object before calling dump\(\) [\#1748](https://github.com/nlohmann/json/issues/1748) -- Unable to invoke accessors on json objects in lldb [\#1745](https://github.com/nlohmann/json/issues/1745) -- Escaping string before parsing [\#1743](https://github.com/nlohmann/json/issues/1743) -- Construction in a member initializer list using curly braces is set as 'array' [\#1742](https://github.com/nlohmann/json/issues/1742) -- Read a subkey from json object [\#1740](https://github.com/nlohmann/json/issues/1740) -- Serialize vector of glm:vec2 [\#1739](https://github.com/nlohmann/json/issues/1739) -- Support nlohmann::basic\_json::value with JSON\_NOEXCEPTION [\#1738](https://github.com/nlohmann/json/issues/1738) -- how to know the parse is error [\#1737](https://github.com/nlohmann/json/issues/1737) -- How to check if a given key exists in a JSON object [\#1736](https://github.com/nlohmann/json/issues/1736) -- Allow The Colon Key-Value Delimiter To Have A Space Before It \[@ READ ONLY\] [\#1735](https://github.com/nlohmann/json/issues/1735) -- Allow Tail { "Key": "Value" } Comma \[@ READ ONLY\] [\#1734](https://github.com/nlohmann/json/issues/1734) -- No-throw json::value\(\) [\#1733](https://github.com/nlohmann/json/issues/1733) -- JsonObject.dump\(\) [\#1732](https://github.com/nlohmann/json/issues/1732) -- basic\_json has no member "parse" [\#1731](https://github.com/nlohmann/json/issues/1731) -- Exception "type must be string, but is array" [\#1730](https://github.com/nlohmann/json/issues/1730) -- json::contains usage to find a path [\#1727](https://github.com/nlohmann/json/issues/1727) -- How to create JSON Object from my Structures of Data and Json File from that Object [\#1726](https://github.com/nlohmann/json/issues/1726) -- please provide an API to read JSON from file directly. [\#1725](https://github.com/nlohmann/json/issues/1725) -- How to modify a value stored at a key? [\#1723](https://github.com/nlohmann/json/issues/1723) -- CMake not correctly finding the configuration package for 3.7.0 [\#1721](https://github.com/nlohmann/json/issues/1721) -- name typo in the "spack package management" section of README.md [\#1720](https://github.com/nlohmann/json/issues/1720) -- How to add json to another json? [\#1718](https://github.com/nlohmann/json/issues/1718) -- json::parse\(\) ubsan regression with v3.7.0 [\#1716](https://github.com/nlohmann/json/issues/1716) -- What I am doing wrong?!? [\#1714](https://github.com/nlohmann/json/issues/1714) -- Potential memory leak detected by Valgrind [\#1713](https://github.com/nlohmann/json/issues/1713) -- json::parse is not thread safe? [\#1712](https://github.com/nlohmann/json/issues/1712) -- static analysis alarm by cppcheck [\#1711](https://github.com/nlohmann/json/issues/1711) -- The compilation time is slow [\#1710](https://github.com/nlohmann/json/issues/1710) -- not linking properly with cmake [\#1709](https://github.com/nlohmann/json/issues/1709) -- Error in dump\(\) with int64\_t minimum value [\#1708](https://github.com/nlohmann/json/issues/1708) -- Crash on trying to deserialize json string on 3ds homebrew [\#1707](https://github.com/nlohmann/json/issues/1707) -- Can't compile VS2019. 13 Errors [\#1706](https://github.com/nlohmann/json/issues/1706) -- find an object that matches the search criteria [\#1705](https://github.com/nlohmann/json/issues/1705) -- IntelliSense goes crazy on VS2019 [\#1704](https://github.com/nlohmann/json/issues/1704) -- Installing on Ubuntu 16.04 [\#1703](https://github.com/nlohmann/json/issues/1703) -- Where is json::parse now? [\#1702](https://github.com/nlohmann/json/issues/1702) -- Forward header should't be amalgamated [\#1700](https://github.com/nlohmann/json/issues/1700) -- Json support for Cmake version 2.8.12 [\#1699](https://github.com/nlohmann/json/issues/1699) -- Intruisive scientific notation when using .dump\(\); [\#1698](https://github.com/nlohmann/json/issues/1698) -- Is there support for automatic serialization/deserialization? [\#1696](https://github.com/nlohmann/json/issues/1696) -- on MSVC dump\(\) will hard crash for larger json [\#1693](https://github.com/nlohmann/json/issues/1693) -- puzzled implicit conversions [\#1692](https://github.com/nlohmann/json/issues/1692) -- Information: My project uses this awesome library [\#1691](https://github.com/nlohmann/json/issues/1691) -- Consider listing files explicitly instead of using GLOB [\#1686](https://github.com/nlohmann/json/issues/1686) -- Failing tests on MSVC with VS2019 15.9.13 x64 [\#1685](https://github.com/nlohmann/json/issues/1685) -- Change from v2 to v3. Encoding with cp1252 [\#1680](https://github.com/nlohmann/json/issues/1680) -- How to add Fifo\_map into json using Cmake [\#1679](https://github.com/nlohmann/json/issues/1679) -- include.zip should contain meson.build [\#1672](https://github.com/nlohmann/json/issues/1672) -- \[Question\] How do I parse JSON into custom types? [\#1669](https://github.com/nlohmann/json/issues/1669) -- Binary \(0x05\) data type for BSON to JSON conversion [\#1668](https://github.com/nlohmann/json/issues/1668) -- Possible to call dump from lldb? [\#1666](https://github.com/nlohmann/json/issues/1666) -- Segmentation fault when linked with libunwind [\#1665](https://github.com/nlohmann/json/issues/1665) -- Should I include single-header after my to\_json and from\_json custom functions declaration? Why not? [\#1663](https://github.com/nlohmann/json/issues/1663) -- Errors/Warnings in VS 2019 when Including Header File [\#1659](https://github.com/nlohmann/json/issues/1659) -- Return null object from object's const operator\[\] as well. [\#1658](https://github.com/nlohmann/json/issues/1658) -- Can't stream json object in to std::basic\_stringstream\ [\#1656](https://github.com/nlohmann/json/issues/1656) -- C2440 in vs2015 cannot convert from 'initializer-list' to nlohmann::basic\_json [\#1655](https://github.com/nlohmann/json/issues/1655) -- Issues around get and pointers [\#1653](https://github.com/nlohmann/json/issues/1653) -- Non-member operator== breaks enum \(de\)serialization [\#1647](https://github.com/nlohmann/json/issues/1647) -- Valgrind: bytes in 1 blocks are definitely lost [\#1646](https://github.com/nlohmann/json/issues/1646) -- Convenient way to make 'basic\_json' accept 'QString' as an key type as well? [\#1640](https://github.com/nlohmann/json/issues/1640) -- mongodb: nan, inf [\#1599](https://github.com/nlohmann/json/issues/1599) -- Error in adl\_serializer [\#1590](https://github.com/nlohmann/json/issues/1590) -- Injecting class during serialization [\#1584](https://github.com/nlohmann/json/issues/1584) -- output\_adapter not user extensible [\#1534](https://github.com/nlohmann/json/issues/1534) -- Inclusion of nlohmann/json.hpp causes OS/ABI to change on Linux [\#1410](https://github.com/nlohmann/json/issues/1410) -- Add library versioning using inline namespaces [\#1394](https://github.com/nlohmann/json/issues/1394) -- CBOR byte string support [\#1129](https://github.com/nlohmann/json/issues/1129) -- How to deserialize array with derived objects [\#716](https://github.com/nlohmann/json/issues/716) - -- Add restriction for tuple specialization of to\_json [\#1826](https://github.com/nlohmann/json/pull/1826) ([cbegue](https://github.com/cbegue)) -- Fix for \#1647 [\#1821](https://github.com/nlohmann/json/pull/1821) ([AnthonyVH](https://github.com/AnthonyVH)) -- Fix issue \#1805 [\#1806](https://github.com/nlohmann/json/pull/1806) ([cbegue](https://github.com/cbegue)) -- Fix some spelling errors - mostly in comments & documentation. [\#1803](https://github.com/nlohmann/json/pull/1803) ([flopp](https://github.com/flopp)) -- Update Hedley to v11. [\#1799](https://github.com/nlohmann/json/pull/1799) ([nemequ](https://github.com/nemequ)) -- iteration\_proxy: Fix integer truncation from std::size\_t to int [\#1797](https://github.com/nlohmann/json/pull/1797) ([t-b](https://github.com/t-b)) -- appveyor.yml: Add MSVC 16 2019 support [\#1780](https://github.com/nlohmann/json/pull/1780) ([t-b](https://github.com/t-b)) -- test/CMakeLists.txt: Use an explicit list instead of GLOB [\#1779](https://github.com/nlohmann/json/pull/1779) ([t-b](https://github.com/t-b)) -- Make json\_pointer::back const \(resolves \#1764\) [\#1769](https://github.com/nlohmann/json/pull/1769) ([chris0x44](https://github.com/chris0x44)) -- did you mean 'serialization'? [\#1767](https://github.com/nlohmann/json/pull/1767) ([0xflotus](https://github.com/0xflotus)) -- Allow items\(\) to be used with custom string [\#1765](https://github.com/nlohmann/json/pull/1765) ([crazyjul](https://github.com/crazyjul)) -- Cppcheck fixes [\#1760](https://github.com/nlohmann/json/pull/1760) ([Xav83](https://github.com/Xav83)) -- Fix and add test's for SFINAE problem [\#1741](https://github.com/nlohmann/json/pull/1741) ([tete17](https://github.com/tete17)) -- Fix clang sanitizer invocation [\#1728](https://github.com/nlohmann/json/pull/1728) ([t-b](https://github.com/t-b)) -- Add gcc 9 and compile with experimental C++20 support [\#1724](https://github.com/nlohmann/json/pull/1724) ([t-b](https://github.com/t-b)) -- Fix int64 min issue [\#1722](https://github.com/nlohmann/json/pull/1722) ([t-b](https://github.com/t-b)) -- release: add singleinclude and meson.build to include.zip [\#1694](https://github.com/nlohmann/json/pull/1694) ([eli-schwartz](https://github.com/eli-schwartz)) - -## [v3.7.0](https://github.com/nlohmann/json/releases/tag/v3.7.0) (2019-07-28) - -[Full Changelog](https://github.com/nlohmann/json/compare/v3.6.1...v3.7.0) - -- How can I retrieve uknown strings from json file in my C++ program. [\#1684](https://github.com/nlohmann/json/issues/1684) -- contains\(\) is sometimes causing stack-based buffer overrun exceptions [\#1683](https://github.com/nlohmann/json/issues/1683) -- How to deserialize arrays from json [\#1681](https://github.com/nlohmann/json/issues/1681) -- Compilation failed in VS2015 [\#1678](https://github.com/nlohmann/json/issues/1678) -- Why the compiled object file is so huge? [\#1677](https://github.com/nlohmann/json/issues/1677) -- From Version 2.1.1 to 3.6.1 serialize std::set [\#1676](https://github.com/nlohmann/json/issues/1676) -- Qt deprecation model halting compiltion [\#1675](https://github.com/nlohmann/json/issues/1675) -- Build For Raspberry pi , Rapbery with new Compiler C++17 [\#1671](https://github.com/nlohmann/json/issues/1671) -- Build from Raspberry pi [\#1667](https://github.com/nlohmann/json/issues/1667) -- Can not translate map with integer key to dict string ? [\#1664](https://github.com/nlohmann/json/issues/1664) -- Double type converts to scientific notation [\#1661](https://github.com/nlohmann/json/issues/1661) -- Missing v3.6.1 tag on master branch [\#1657](https://github.com/nlohmann/json/issues/1657) -- Support Fleese Binary Data Format [\#1654](https://github.com/nlohmann/json/issues/1654) -- Suggestion: replace alternative tokens for !, && and || with their symbols [\#1652](https://github.com/nlohmann/json/issues/1652) -- Build failure test-allocator.vcxproj [\#1651](https://github.com/nlohmann/json/issues/1651) -- How to provide function json& to\_json\(\) which is similar as 'void to\_json\(json&j, const CObject& obj\)' ? [\#1650](https://github.com/nlohmann/json/issues/1650) -- Can't throw exception when starting file is a number [\#1649](https://github.com/nlohmann/json/issues/1649) -- to\_json / from\_json with nested type [\#1648](https://github.com/nlohmann/json/issues/1648) -- How to create a json object from a std::string, created by j.dump? [\#1645](https://github.com/nlohmann/json/issues/1645) -- Problem getting vector \(array\) of strings [\#1644](https://github.com/nlohmann/json/issues/1644) -- json.hpp compilation issue with other typedefs with same name [\#1642](https://github.com/nlohmann/json/issues/1642) -- nlohmann::adl\_serializer\::to\_json no matching overloaded function found [\#1641](https://github.com/nlohmann/json/issues/1641) -- overwrite adl\_serializer\ to change behaviour [\#1638](https://github.com/nlohmann/json/issues/1638) -- json.SelectToken\("Manufacturers.Products.Price"\); [\#1637](https://github.com/nlohmann/json/issues/1637) -- Add json type as value [\#1636](https://github.com/nlohmann/json/issues/1636) -- Unit conversion test error: conversion from 'nlohmann::json' to non-scalar type 'std::string\_view' requested [\#1634](https://github.com/nlohmann/json/issues/1634) -- nlohmann VS JsonCpp by C++17 [\#1633](https://github.com/nlohmann/json/issues/1633) -- To integrate an inline helper function that return type name as string [\#1632](https://github.com/nlohmann/json/issues/1632) -- Return JSON as reference [\#1631](https://github.com/nlohmann/json/issues/1631) -- Updating from an older version causes problems with assing a json object to a struct [\#1630](https://github.com/nlohmann/json/issues/1630) -- Can without default constructor function for user defined classes when only to\_json is needed? [\#1629](https://github.com/nlohmann/json/issues/1629) -- Compilation fails with clang 6.x-8.x in C++14 mode [\#1628](https://github.com/nlohmann/json/issues/1628) -- Treating floating point as string [\#1627](https://github.com/nlohmann/json/issues/1627) -- error parsing character å [\#1626](https://github.com/nlohmann/json/issues/1626) -- \[Help\] How to Improve Json Output Performance with Large Json Arrays [\#1624](https://github.com/nlohmann/json/issues/1624) -- Suggested link changes for reporting new issues \[blob/develop/REAME.md and blob/develop/.github/CONTRIBUTING.md\] [\#1623](https://github.com/nlohmann/json/issues/1623) -- Broken link to issue template in CONTRIBUTING.md [\#1622](https://github.com/nlohmann/json/issues/1622) -- Missing word in README.md file [\#1621](https://github.com/nlohmann/json/issues/1621) -- Package manager instructions in README for brew is incorrect [\#1620](https://github.com/nlohmann/json/issues/1620) -- Building with Visual Studio 2019 [\#1619](https://github.com/nlohmann/json/issues/1619) -- Precedence of to\_json and builtin harmful [\#1617](https://github.com/nlohmann/json/issues/1617) -- The type json is missing from the html documentation [\#1616](https://github.com/nlohmann/json/issues/1616) -- variant is not support in Release 3.6.1? [\#1615](https://github.com/nlohmann/json/issues/1615) -- Replace assert with throw for const operator\[\] [\#1614](https://github.com/nlohmann/json/issues/1614) -- Memory Overhead is Too High \(10x or more\) [\#1613](https://github.com/nlohmann/json/issues/1613) -- program crash everytime, when other data type incomming in json stream as expected [\#1612](https://github.com/nlohmann/json/issues/1612) -- Improved Enum Support [\#1611](https://github.com/nlohmann/json/issues/1611) -- is it possible convert json object back to stl container ? [\#1610](https://github.com/nlohmann/json/issues/1610) -- Add C++17-like emplace.back\(\) for arrays. [\#1609](https://github.com/nlohmann/json/issues/1609) -- is\_nothrow\_copy\_constructible fails for json::const\_iterator on MSVC2015 x86 Debug build [\#1608](https://github.com/nlohmann/json/issues/1608) -- Reading and writing array elements [\#1607](https://github.com/nlohmann/json/issues/1607) -- Converting json::value to int [\#1605](https://github.com/nlohmann/json/issues/1605) -- I have a vector of keys and and a string of value and i want to create nested json array [\#1604](https://github.com/nlohmann/json/issues/1604) -- In compatible JSON object from nlohmann::json to nohman::json - unexpected end of input; expected '\[', '{', or a literal [\#1603](https://github.com/nlohmann/json/issues/1603) -- json parser crash if having a large number integer in message [\#1602](https://github.com/nlohmann/json/issues/1602) -- Value method with undocumented throwing 302 exception [\#1601](https://github.com/nlohmann/json/issues/1601) -- Accessing value with json pointer adds key if not existing [\#1600](https://github.com/nlohmann/json/issues/1600) -- README.md broken link to project documentation [\#1597](https://github.com/nlohmann/json/issues/1597) -- Random Kudos: Thanks for your work on this! [\#1596](https://github.com/nlohmann/json/issues/1596) -- json::parse return value and errors [\#1595](https://github.com/nlohmann/json/issues/1595) -- initializer list constructor makes curly brace initialization fragile [\#1594](https://github.com/nlohmann/json/issues/1594) -- trying to log message for missing keyword, difference between \["foo"\] and at\("foo"\) [\#1593](https://github.com/nlohmann/json/issues/1593) -- std::string and std::wstring `to_json` [\#1592](https://github.com/nlohmann/json/issues/1592) -- I have a C structure which I need to convert to a JSON. How do I do it? Haven't found proper examples so far. [\#1591](https://github.com/nlohmann/json/issues/1591) -- dump\_escaped possible error ? [\#1589](https://github.com/nlohmann/json/issues/1589) -- json::parse\(\) into a vector\ results in unhandled exception [\#1587](https://github.com/nlohmann/json/issues/1587) -- push\_back\(\)/emplace\_back\(\) on array invalidates pointers to existing array items [\#1586](https://github.com/nlohmann/json/issues/1586) -- Getting nlohmann::detail::parse\_error on JSON generated by nlohmann::json not sure why [\#1583](https://github.com/nlohmann/json/issues/1583) -- getting error terminate called after throwing an instance of 'std::domain\_error' what\(\): cannot use at\(\) with string [\#1582](https://github.com/nlohmann/json/issues/1582) -- how i create json file [\#1581](https://github.com/nlohmann/json/issues/1581) -- prevent rounding of double datatype values [\#1580](https://github.com/nlohmann/json/issues/1580) -- Documentation Container Overview Doesn't Reference Const Methods [\#1579](https://github.com/nlohmann/json/issues/1579) -- Writing an array into a nlohmann::json object [\#1578](https://github.com/nlohmann/json/issues/1578) -- compilation error when using with another library [\#1577](https://github.com/nlohmann/json/issues/1577) -- Homebrew on OSX doesn't install cmake config file [\#1576](https://github.com/nlohmann/json/issues/1576) -- JSON Parse Out of Range Error [\#1574](https://github.com/nlohmann/json/issues/1574) -- Integrating into existing CMake Project [\#1573](https://github.com/nlohmann/json/issues/1573) -- conversion to std::string failed [\#1571](https://github.com/nlohmann/json/issues/1571) -- jPtr operation does not throw [\#1569](https://github.com/nlohmann/json/issues/1569) -- How to generate dll file for this project [\#1568](https://github.com/nlohmann/json/issues/1568) -- how to pass variable data to json in c [\#1567](https://github.com/nlohmann/json/issues/1567) -- I want to achieve an upgraded function. [\#1566](https://github.com/nlohmann/json/issues/1566) -- How to determine the type of elements read from a JSON array? [\#1564](https://github.com/nlohmann/json/issues/1564) -- try\_get\_to [\#1563](https://github.com/nlohmann/json/issues/1563) -- example code compile error [\#1562](https://github.com/nlohmann/json/issues/1562) -- How to iterate over nested json object [\#1561](https://github.com/nlohmann/json/issues/1561) -- Build Option/Separate Function to Allow to Throw on Duplicate Keys [\#1560](https://github.com/nlohmann/json/issues/1560) -- Compiler Switches -Weffc++ & -Wshadow are throwing errors [\#1558](https://github.com/nlohmann/json/issues/1558) -- warning: use of the 'nodiscard' attribute is a C++17 extension [\#1557](https://github.com/nlohmann/json/issues/1557) -- Import/Export compressed JSON files [\#1556](https://github.com/nlohmann/json/issues/1556) -- GDB renderers for json library [\#1554](https://github.com/nlohmann/json/issues/1554) -- Is it possible to construct a json string object from a binary buffer? [\#1553](https://github.com/nlohmann/json/issues/1553) -- json objects in list [\#1552](https://github.com/nlohmann/json/issues/1552) -- Matrix output [\#1550](https://github.com/nlohmann/json/issues/1550) -- Using json merge\_patch on ordered non-alphanumeric datasets [\#1549](https://github.com/nlohmann/json/issues/1549) -- Invalid parsed value for big integer [\#1548](https://github.com/nlohmann/json/issues/1548) -- Integrating with android ndk issues. [\#1547](https://github.com/nlohmann/json/issues/1547) -- add noexcept json::value\("key", default\) method variant? [\#1546](https://github.com/nlohmann/json/issues/1546) -- Thank you! 🙌 [\#1545](https://github.com/nlohmann/json/issues/1545) -- Output and input matrix [\#1544](https://github.com/nlohmann/json/issues/1544) -- Add regression tests for MSVC [\#1543](https://github.com/nlohmann/json/issues/1543) -- \[Help Needed!\] Season of Docs [\#1542](https://github.com/nlohmann/json/issues/1542) -- program still abort\(\) or exit\(\) with try catch [\#1541](https://github.com/nlohmann/json/issues/1541) -- Have a json::type\_error exception because of JSON object [\#1540](https://github.com/nlohmann/json/issues/1540) -- Quoted numbers [\#1538](https://github.com/nlohmann/json/issues/1538) -- Reading a JSON file into an object [\#1537](https://github.com/nlohmann/json/issues/1537) -- Releases 3.6.0 and 3.6.1 don't build on conda / windows [\#1536](https://github.com/nlohmann/json/issues/1536) -- \[Clang\] warning: use of the 'nodiscard' attribute is a C++17 extension \[-Wc++17-extensions\] [\#1535](https://github.com/nlohmann/json/issues/1535) -- wchar\_t/std::wstring json can be created but not accessed [\#1533](https://github.com/nlohmann/json/issues/1533) -- json stringify [\#1532](https://github.com/nlohmann/json/issues/1532) -- How can I use it from gcc on RPI [\#1528](https://github.com/nlohmann/json/issues/1528) -- std::pair treated as an array instead of key-value in `std::vector>` [\#1520](https://github.com/nlohmann/json/issues/1520) -- Excessive Memory Usage for Large Json File [\#1516](https://github.com/nlohmann/json/issues/1516) -- SAX dumper [\#1512](https://github.com/nlohmann/json/issues/1512) -- Conversion to user type containing a std::vector not working with documented approach [\#1511](https://github.com/nlohmann/json/issues/1511) -- Inconsistent use of type alias. [\#1507](https://github.com/nlohmann/json/issues/1507) -- Is there a current way to represent strings as json int? [\#1503](https://github.com/nlohmann/json/issues/1503) -- Intermittent issues with loadJSON [\#1484](https://github.com/nlohmann/json/issues/1484) -- use json construct std::string [\#1462](https://github.com/nlohmann/json/issues/1462) -- JSON Creation [\#1461](https://github.com/nlohmann/json/issues/1461) -- Null bytes in files are treated like EOF [\#1095](https://github.com/nlohmann/json/issues/1095) -- Feature: to\_string\(const json& j\); [\#916](https://github.com/nlohmann/json/issues/916) - -- Use GNUInstallDirs instead of hard-coded path. [\#1673](https://github.com/nlohmann/json/pull/1673) ([ghost](https://github.com/ghost)) -- Package Manager: MSYS2 \(pacman\) [\#1670](https://github.com/nlohmann/json/pull/1670) ([podsvirov](https://github.com/podsvirov)) -- Fix json.hpp compilation issue with other typedefs with same name \(Issue \#1642\) [\#1643](https://github.com/nlohmann/json/pull/1643) ([kevinlul](https://github.com/kevinlul)) -- Add explicit conversion from json to std::string\_view in conversion unit test [\#1639](https://github.com/nlohmann/json/pull/1639) ([taylorhoward92](https://github.com/taylorhoward92)) -- Minor fixes in docs [\#1625](https://github.com/nlohmann/json/pull/1625) ([nickaein](https://github.com/nickaein)) -- Fix broken links to documentation [\#1598](https://github.com/nlohmann/json/pull/1598) ([nickaein](https://github.com/nickaein)) -- Added to\_string and added basic tests [\#1585](https://github.com/nlohmann/json/pull/1585) ([Macr0Nerd](https://github.com/Macr0Nerd)) -- Regression tests for MSVC [\#1570](https://github.com/nlohmann/json/pull/1570) ([nickaein](https://github.com/nickaein)) -- Fix/1511 [\#1555](https://github.com/nlohmann/json/pull/1555) ([theodelrieu](https://github.com/theodelrieu)) -- Remove C++17 extension warning from clang; \#1535 [\#1551](https://github.com/nlohmann/json/pull/1551) ([heavywatal](https://github.com/heavywatal)) -- moved from Catch to doctest for unit tests [\#1439](https://github.com/nlohmann/json/pull/1439) ([onqtam](https://github.com/onqtam)) - -## [v3.6.1](https://github.com/nlohmann/json/releases/tag/v3.6.1) (2019-03-20) - -[Full Changelog](https://github.com/nlohmann/json/compare/3.6.1...v3.6.1) - -## [3.6.1](https://github.com/nlohmann/json/releases/tag/3.6.1) (2019-03-20) - -[Full Changelog](https://github.com/nlohmann/json/compare/v3.6.0...3.6.1) - -- Failed to build with \ [\#1531](https://github.com/nlohmann/json/issues/1531) -- Compiling 3.6.0 with GCC \> 7, array vs std::array \#590 is back [\#1530](https://github.com/nlohmann/json/issues/1530) -- 3.6.0: warning: missing initializer for member 'std::array\::\_M\_elems' \[-Wmissing-field-initializers\] [\#1527](https://github.com/nlohmann/json/issues/1527) -- unable to parse json [\#1525](https://github.com/nlohmann/json/issues/1525) - -## [v3.6.0](https://github.com/nlohmann/json/releases/tag/v3.6.0) (2019-03-19) - -[Full Changelog](https://github.com/nlohmann/json/compare/v3.5.0...v3.6.0) - -- How can I turn a string of a json array into a json array? [\#1526](https://github.com/nlohmann/json/issues/1526) -- Minor: missing a std:: namespace tag [\#1521](https://github.com/nlohmann/json/issues/1521) -- how to precision to four decimal for double when use to\_json [\#1519](https://github.com/nlohmann/json/issues/1519) -- error parse [\#1518](https://github.com/nlohmann/json/issues/1518) -- Compile error: template argument deduction/substitution failed [\#1515](https://github.com/nlohmann/json/issues/1515) -- std::complex type [\#1510](https://github.com/nlohmann/json/issues/1510) -- CBOR byte string support [\#1509](https://github.com/nlohmann/json/issues/1509) -- Compilation error getting a std::pair\<\> on latest VS 2017 compiler [\#1506](https://github.com/nlohmann/json/issues/1506) -- "Integration" section of documentation needs update? [\#1505](https://github.com/nlohmann/json/issues/1505) -- Json object from string from a TCP socket [\#1504](https://github.com/nlohmann/json/issues/1504) -- MSVC warning C4946 \("reinterpret\_cast used between related classes"\) compiling json.hpp [\#1502](https://github.com/nlohmann/json/issues/1502) -- How to programmatically fill an n-th dimensional JSON object? [\#1501](https://github.com/nlohmann/json/issues/1501) -- Error compiling with clang and `JSON_NOEXCEPTION`: need to include `cstdlib` [\#1500](https://github.com/nlohmann/json/issues/1500) -- The code compiles unsuccessfully with android-ndk-r10e [\#1499](https://github.com/nlohmann/json/issues/1499) -- Cmake 3.1 in develop, when is it likely to make it into a stable release? [\#1498](https://github.com/nlohmann/json/issues/1498) -- Some Help please object inside array [\#1494](https://github.com/nlohmann/json/issues/1494) -- How to get data into vector of user-defined type from a Json object [\#1493](https://github.com/nlohmann/json/issues/1493) -- how to find subelement without loop [\#1490](https://github.com/nlohmann/json/issues/1490) -- json to std::map [\#1487](https://github.com/nlohmann/json/issues/1487) -- Type in README.md [\#1486](https://github.com/nlohmann/json/issues/1486) -- Error in parsing and reading msgpack-lite [\#1485](https://github.com/nlohmann/json/issues/1485) -- Compiling issues with libc 2.12 [\#1483](https://github.com/nlohmann/json/issues/1483) -- How do I use reference or pointer binding values? [\#1482](https://github.com/nlohmann/json/issues/1482) -- Compilation fails in MSVC with the Microsoft Language Extensions disabled [\#1481](https://github.com/nlohmann/json/issues/1481) -- Functional visit [\#1480](https://github.com/nlohmann/json/issues/1480) -- \[Question\] Unescaped dump [\#1479](https://github.com/nlohmann/json/issues/1479) -- Some Help please [\#1478](https://github.com/nlohmann/json/issues/1478) -- Global variables are stored within the JSON file, how do I declare them as global variables when I read them out in my C++ program? [\#1476](https://github.com/nlohmann/json/issues/1476) -- Unable to modify one of the values within the JSON file, and save it [\#1475](https://github.com/nlohmann/json/issues/1475) -- Documentation of parse function has two identical @pre causes [\#1473](https://github.com/nlohmann/json/issues/1473) -- GCC 9.0 build failure [\#1472](https://github.com/nlohmann/json/issues/1472) -- Can we have an `exists()` method? [\#1471](https://github.com/nlohmann/json/issues/1471) -- How to parse multi object json from file? [\#1470](https://github.com/nlohmann/json/issues/1470) -- How to returns the name of the upper object? [\#1467](https://github.com/nlohmann/json/issues/1467) -- Error: "tuple\_size" has already been declared in the current scope [\#1466](https://github.com/nlohmann/json/issues/1466) -- Checking keys of two jsons against eachother [\#1465](https://github.com/nlohmann/json/issues/1465) -- Disable installation when used as meson subproject [\#1463](https://github.com/nlohmann/json/issues/1463) -- Unpack list of integers to a std::vector\ [\#1460](https://github.com/nlohmann/json/issues/1460) -- Implement DRY definition of JSON representation of a c++ class [\#1459](https://github.com/nlohmann/json/issues/1459) -- json.exception.type\_error.305 with GCC 4.9 when using C++ {} initializer [\#1458](https://github.com/nlohmann/json/issues/1458) -- API to convert an "uninitialized" json into an empty object or empty array [\#1456](https://github.com/nlohmann/json/issues/1456) -- How to parse a vector of objects with const attributes [\#1453](https://github.com/nlohmann/json/issues/1453) -- NLOHMANN\_JSON\_SERIALIZE\_ENUM potentially requires duplicate definitions [\#1450](https://github.com/nlohmann/json/issues/1450) -- Question about making json object from file directory [\#1449](https://github.com/nlohmann/json/issues/1449) -- .get\(\) throws error if used with userdefined structs in unordered\_map [\#1448](https://github.com/nlohmann/json/issues/1448) -- Integer Overflow \(OSS-Fuzz 12506\) [\#1447](https://github.com/nlohmann/json/issues/1447) -- If a string has too many invalid UTF-8 characters, json::dump attempts to index an array out of bounds. [\#1445](https://github.com/nlohmann/json/issues/1445) -- Setting values of .JSON file [\#1444](https://github.com/nlohmann/json/issues/1444) -- alias object\_t::key\_type in basic\_json [\#1442](https://github.com/nlohmann/json/issues/1442) -- Latest Ubuntu package is 2.1.1 [\#1438](https://github.com/nlohmann/json/issues/1438) -- lexer.hpp\(1363\) '\_snprintf': is not a member | Visualstudio 2017 [\#1437](https://github.com/nlohmann/json/issues/1437) -- Static method invites inadvertent logic error. [\#1433](https://github.com/nlohmann/json/issues/1433) -- EOS compilation produces "fatal error: 'nlohmann/json.hpp' file not found" [\#1432](https://github.com/nlohmann/json/issues/1432) -- Support for bad commas [\#1429](https://github.com/nlohmann/json/issues/1429) -- Please have one base exception class for all json exceptions [\#1427](https://github.com/nlohmann/json/issues/1427) -- Compilation warning: 'tuple\_size' defined as a class template here but previously declared as a struct template [\#1426](https://github.com/nlohmann/json/issues/1426) -- Which version can be used with GCC 4.8.2 ? [\#1424](https://github.com/nlohmann/json/issues/1424) -- Ignore nullptr values on constructing json object from a container [\#1422](https://github.com/nlohmann/json/issues/1422) -- Support for custom float precision via unquoted strings [\#1421](https://github.com/nlohmann/json/issues/1421) -- It is possible to call `json::find` with a json\_pointer as argument. This causes runtime UB/crash. [\#1418](https://github.com/nlohmann/json/issues/1418) -- Dump throwing exception [\#1416](https://github.com/nlohmann/json/issues/1416) -- Build error [\#1415](https://github.com/nlohmann/json/issues/1415) -- Append version to include.zip [\#1412](https://github.com/nlohmann/json/issues/1412) -- error C2039: '\_snprintf': is not a member of 'std' - Windows [\#1408](https://github.com/nlohmann/json/issues/1408) -- Deserializing to vector [\#1407](https://github.com/nlohmann/json/issues/1407) -- Efficient way to set a `json` object as value into another `json` key [\#1406](https://github.com/nlohmann/json/issues/1406) -- Document return value of parse\(\) when allow\_exceptions == false and parsing fails [\#1405](https://github.com/nlohmann/json/issues/1405) -- Unexpected behaviour with structured binding [\#1404](https://github.com/nlohmann/json/issues/1404) -- Which native types does get\\(\) allow? [\#1403](https://github.com/nlohmann/json/issues/1403) -- Add something like Json::StaticString [\#1402](https://github.com/nlohmann/json/issues/1402) -- -Wmismatched-tags in 3.5.0? [\#1401](https://github.com/nlohmann/json/issues/1401) -- Coverity Scan reports an UNCAUGHT\_EXCEPT issue [\#1400](https://github.com/nlohmann/json/issues/1400) -- fff [\#1399](https://github.com/nlohmann/json/issues/1399) -- sorry this is not an issue, just a Question, How to change a key value in a file and save it ? [\#1398](https://github.com/nlohmann/json/issues/1398) -- appveyor x64 builds appear to be using Win32 toolset [\#1374](https://github.com/nlohmann/json/issues/1374) -- Serializing/Deserializing a Class containing a vector of itself [\#1373](https://github.com/nlohmann/json/issues/1373) -- Retrieving array elements. [\#1369](https://github.com/nlohmann/json/issues/1369) -- Deserialize [\#1366](https://github.com/nlohmann/json/issues/1366) -- call of overloaded for push\_back and operator+= is ambiguous [\#1352](https://github.com/nlohmann/json/issues/1352) -- got an error and cann't figure it out [\#1351](https://github.com/nlohmann/json/issues/1351) -- Improve number-to-string conversion [\#1334](https://github.com/nlohmann/json/issues/1334) -- Implicit type conversion error on MSVC [\#1333](https://github.com/nlohmann/json/issues/1333) -- NuGet Package [\#1132](https://github.com/nlohmann/json/issues/1132) - -- Change macros to numeric\_limits [\#1514](https://github.com/nlohmann/json/pull/1514) ([naszta](https://github.com/naszta)) -- fix GCC 7.1.1 - 7.2.1 on CentOS [\#1496](https://github.com/nlohmann/json/pull/1496) ([lieff](https://github.com/lieff)) -- Update Buckaroo instructions in README.md [\#1495](https://github.com/nlohmann/json/pull/1495) ([njlr](https://github.com/njlr)) -- Fix gcc9 build error test/src/unit-allocator.cpp \(Issue \#1472\) [\#1492](https://github.com/nlohmann/json/pull/1492) ([stac47](https://github.com/stac47)) -- Fix typo in README.md [\#1491](https://github.com/nlohmann/json/pull/1491) ([nickaein](https://github.com/nickaein)) -- Do proper endian conversions [\#1489](https://github.com/nlohmann/json/pull/1489) ([andreas-schwab](https://github.com/andreas-schwab)) -- Fix documentation [\#1477](https://github.com/nlohmann/json/pull/1477) ([nickaein](https://github.com/nickaein)) -- Implement contains\(\) member function [\#1474](https://github.com/nlohmann/json/pull/1474) ([nickaein](https://github.com/nickaein)) -- Add operator/= and operator/ to construct a JSON pointer by appending two JSON pointers [\#1469](https://github.com/nlohmann/json/pull/1469) ([garethsb](https://github.com/garethsb)) -- Disable Clang -Wmismatched-tags warning on tuple\_size / tuple\_element [\#1468](https://github.com/nlohmann/json/pull/1468) ([past-due](https://github.com/past-due)) -- Disable installation when used as meson subproject. \#1463 [\#1464](https://github.com/nlohmann/json/pull/1464) ([elvisoric](https://github.com/elvisoric)) -- docs: README typo [\#1455](https://github.com/nlohmann/json/pull/1455) ([wythe](https://github.com/wythe)) -- remove extra semicolon from readme [\#1451](https://github.com/nlohmann/json/pull/1451) ([Afforix](https://github.com/Afforix)) -- attempt to fix \#1445, flush buffer in serializer::dump\_escaped in UTF8\_REJECT case. [\#1446](https://github.com/nlohmann/json/pull/1446) ([scinart](https://github.com/scinart)) -- Use C++11 features supported by CMake 3.1. [\#1441](https://github.com/nlohmann/json/pull/1441) ([iwanders](https://github.com/iwanders)) -- :rotating\_light: fixed unused variable warning [\#1435](https://github.com/nlohmann/json/pull/1435) ([pboettch](https://github.com/pboettch)) -- allow push\_back\(\) and pop\_back\(\) calls on json\_pointer [\#1434](https://github.com/nlohmann/json/pull/1434) ([pboettch](https://github.com/pboettch)) -- Add instructions about using nlohmann/json with the conda package manager [\#1430](https://github.com/nlohmann/json/pull/1430) ([nicoddemus](https://github.com/nicoddemus)) -- Updated year in README.md [\#1425](https://github.com/nlohmann/json/pull/1425) ([jef](https://github.com/jef)) -- Fixed broken links in the README file [\#1423](https://github.com/nlohmann/json/pull/1423) ([skypjack](https://github.com/skypjack)) -- Fixed broken links in the README file [\#1420](https://github.com/nlohmann/json/pull/1420) ([skypjack](https://github.com/skypjack)) -- docs: typo in README [\#1417](https://github.com/nlohmann/json/pull/1417) ([wythe](https://github.com/wythe)) -- Fix x64 target platform for appveyor [\#1414](https://github.com/nlohmann/json/pull/1414) ([nickaein](https://github.com/nickaein)) -- Improve dump\_integer performance [\#1411](https://github.com/nlohmann/json/pull/1411) ([nickaein](https://github.com/nickaein)) -- buildsystem: relax requirement on cmake version [\#1409](https://github.com/nlohmann/json/pull/1409) ([yann-morin-1998](https://github.com/yann-morin-1998)) -- CMake: Optional Install if Embedded [\#1330](https://github.com/nlohmann/json/pull/1330) ([ax3l](https://github.com/ax3l)) - -## [v3.5.0](https://github.com/nlohmann/json/releases/tag/v3.5.0) (2018-12-21) - -[Full Changelog](https://github.com/nlohmann/json/compare/v3.4.0...v3.5.0) - -- Copyconstructor inserts original into array with single element [\#1397](https://github.com/nlohmann/json/issues/1397) -- Get value without explicit typecasting [\#1395](https://github.com/nlohmann/json/issues/1395) -- Big file parsing [\#1393](https://github.com/nlohmann/json/issues/1393) -- Adding Structured Binding Support [\#1388](https://github.com/nlohmann/json/issues/1388) -- map\ exhibits unexpected behavior [\#1387](https://github.com/nlohmann/json/issues/1387) -- Error Code Return [\#1386](https://github.com/nlohmann/json/issues/1386) -- using unordered\_map as object type [\#1385](https://github.com/nlohmann/json/issues/1385) -- float precision [\#1384](https://github.com/nlohmann/json/issues/1384) -- \[json.exception.type\_error.316\] invalid UTF-8 byte at index 1: 0xC3 [\#1383](https://github.com/nlohmann/json/issues/1383) -- Inconsistent Constructor \(GCC vs. Clang\) [\#1381](https://github.com/nlohmann/json/issues/1381) -- \#define or || [\#1379](https://github.com/nlohmann/json/issues/1379) -- How to iterate inside the values ? [\#1377](https://github.com/nlohmann/json/issues/1377) -- items\(\) unable to get the elements [\#1375](https://github.com/nlohmann/json/issues/1375) -- conversion json to std::map doesn't work for types \ [\#1372](https://github.com/nlohmann/json/issues/1372) -- A minor issue in the build instructions [\#1371](https://github.com/nlohmann/json/issues/1371) -- Using this library without stream ? [\#1370](https://github.com/nlohmann/json/issues/1370) -- Writing and reading BSON data [\#1368](https://github.com/nlohmann/json/issues/1368) -- Retrieving array elements from object type iterator. [\#1367](https://github.com/nlohmann/json/issues/1367) -- json::dump\(\) silently crashes if items contain accented letters [\#1365](https://github.com/nlohmann/json/issues/1365) -- warnings in MSVC \(2015\) in 3.4.0 related to bool... [\#1364](https://github.com/nlohmann/json/issues/1364) -- Cant compile with -C++17 and beyond compiler options [\#1362](https://github.com/nlohmann/json/issues/1362) -- json to concrete type conversion through reference or pointer fails [\#1361](https://github.com/nlohmann/json/issues/1361) -- the first attributes of JSON string is misplaced [\#1360](https://github.com/nlohmann/json/issues/1360) -- Copy-construct using initializer-list converts objects to arrays [\#1359](https://github.com/nlohmann/json/issues/1359) -- About value\(key, default\_value\) and operator\[\]\(key\) [\#1358](https://github.com/nlohmann/json/issues/1358) -- Problem with printing json response object [\#1356](https://github.com/nlohmann/json/issues/1356) -- Serializing pointer segfaults [\#1355](https://github.com/nlohmann/json/issues/1355) -- Read `long long int` data as a number. [\#1354](https://github.com/nlohmann/json/issues/1354) -- eclipse oxygen in ubuntu get\ is ambiguous [\#1353](https://github.com/nlohmann/json/issues/1353) -- Can't build on Visual Studio 2017 v15.8.9 [\#1350](https://github.com/nlohmann/json/issues/1350) -- cannot parse from string? [\#1349](https://github.com/nlohmann/json/issues/1349) -- Error: out\_of\_range [\#1348](https://github.com/nlohmann/json/issues/1348) -- expansion pattern 'CompatibleObjectType' contains no argument packs, with CUDA 10 [\#1347](https://github.com/nlohmann/json/issues/1347) -- Unable to update a value for a nested\(multi-level\) json file [\#1344](https://github.com/nlohmann/json/issues/1344) -- Fails to compile when std::iterator\_traits is not SFINAE friendly. [\#1341](https://github.com/nlohmann/json/issues/1341) -- EOF flag not set on exhausted input streams. [\#1340](https://github.com/nlohmann/json/issues/1340) -- Shadowed Member in merge\_patch [\#1339](https://github.com/nlohmann/json/issues/1339) -- Periods/literal dots in keys? [\#1338](https://github.com/nlohmann/json/issues/1338) -- Protect macro expansion of commonly defined macros [\#1337](https://github.com/nlohmann/json/issues/1337) -- How to validate an input before parsing? [\#1336](https://github.com/nlohmann/json/issues/1336) -- Non-verifying dump\(\) alternative for debugging/logging needed [\#1335](https://github.com/nlohmann/json/issues/1335) -- Json Libarary is not responding for me in c++ [\#1332](https://github.com/nlohmann/json/issues/1332) -- Question - how to find an object in an array [\#1331](https://github.com/nlohmann/json/issues/1331) -- Nesting additional data in json object [\#1328](https://github.com/nlohmann/json/issues/1328) -- can to\_json\(\) be defined inside a class? [\#1324](https://github.com/nlohmann/json/issues/1324) -- CodeBlocks IDE can't find `json.hpp` header [\#1318](https://github.com/nlohmann/json/issues/1318) -- Change json\_pointer to provide an iterator begin/end/etc, don't use vectors, and also enable string\_view [\#1312](https://github.com/nlohmann/json/issues/1312) -- Xcode - adding it to library [\#1300](https://github.com/nlohmann/json/issues/1300) -- unicode: accept char16\_t, char32\_t sequences [\#1298](https://github.com/nlohmann/json/issues/1298) -- unicode: char16\_t\* is compiler error, but char16\_t\[\] is accepted [\#1297](https://github.com/nlohmann/json/issues/1297) -- Dockerfile Project Help Needed [\#1296](https://github.com/nlohmann/json/issues/1296) -- Comparisons between large unsigned and negative signed integers [\#1295](https://github.com/nlohmann/json/issues/1295) -- CMake alias to `nlohmann::json` [\#1291](https://github.com/nlohmann/json/issues/1291) -- Release zips without tests [\#1285](https://github.com/nlohmann/json/issues/1285) -- separate object\_t::key\_type from basic\_json::key\_type, and use an allocator which returns object\_t::key\_type [\#1274](https://github.com/nlohmann/json/issues/1274) -- Is there a nice way to associate external values with json elements? [\#1256](https://github.com/nlohmann/json/issues/1256) -- Delete by json\_pointer [\#1248](https://github.com/nlohmann/json/issues/1248) -- Expose lexer, as a StAX parser [\#1219](https://github.com/nlohmann/json/issues/1219) -- Subclassing json\(\) & error on recursive load [\#1201](https://github.com/nlohmann/json/issues/1201) -- Check value for existence by json\_pointer [\#1194](https://github.com/nlohmann/json/issues/1194) - -- Feature/add file input adapter [\#1392](https://github.com/nlohmann/json/pull/1392) ([dumarjo](https://github.com/dumarjo)) -- Added Support for Structured Bindings [\#1391](https://github.com/nlohmann/json/pull/1391) ([pratikpc](https://github.com/pratikpc)) -- Link to issue \#958 broken [\#1382](https://github.com/nlohmann/json/pull/1382) ([kjpus](https://github.com/kjpus)) -- readme: fix typo [\#1380](https://github.com/nlohmann/json/pull/1380) ([manu-chroma](https://github.com/manu-chroma)) -- recommend using explicit from JSON conversions [\#1363](https://github.com/nlohmann/json/pull/1363) ([theodelrieu](https://github.com/theodelrieu)) -- Fix merge\_patch shadow warning [\#1346](https://github.com/nlohmann/json/pull/1346) ([ax3l](https://github.com/ax3l)) -- Allow installation via Meson [\#1345](https://github.com/nlohmann/json/pull/1345) ([mpoquet](https://github.com/mpoquet)) -- Set eofbit on exhausted input stream. [\#1343](https://github.com/nlohmann/json/pull/1343) ([mefyl](https://github.com/mefyl)) -- Add a SFINAE friendly iterator\_traits and use that instead. [\#1342](https://github.com/nlohmann/json/pull/1342) ([dgavedissian](https://github.com/dgavedissian)) -- Fix EOL Whitespaces & CMake Spelling [\#1329](https://github.com/nlohmann/json/pull/1329) ([ax3l](https://github.com/ax3l)) - -## [v3.4.0](https://github.com/nlohmann/json/releases/tag/v3.4.0) (2018-10-30) - -[Full Changelog](https://github.com/nlohmann/json/compare/v3.3.0...v3.4.0) - -- Big uint64\_t values are serialized wrong [\#1327](https://github.com/nlohmann/json/issues/1327) -- \[Question\] Efficient check for equivalency? [\#1325](https://github.com/nlohmann/json/issues/1325) -- Can't use ifstream and .clear\(\) [\#1321](https://github.com/nlohmann/json/issues/1321) -- \[Warning\] -Wparentheses on line 555 on single\_include [\#1319](https://github.com/nlohmann/json/issues/1319) -- Compilation error using at and find with enum struct [\#1316](https://github.com/nlohmann/json/issues/1316) -- Parsing JSON from a web address [\#1311](https://github.com/nlohmann/json/issues/1311) -- How to convert JSON to Struct with embeded subject [\#1310](https://github.com/nlohmann/json/issues/1310) -- Null safety/coalescing function? [\#1309](https://github.com/nlohmann/json/issues/1309) -- Building fails using single include file: json.hpp [\#1308](https://github.com/nlohmann/json/issues/1308) -- json::parse\(std::string\) Exception inside packaged Lib [\#1306](https://github.com/nlohmann/json/issues/1306) -- Problem in Dockerfile with installation of library [\#1304](https://github.com/nlohmann/json/issues/1304) -- compile error in from\_json converting to container with std::pair [\#1299](https://github.com/nlohmann/json/issues/1299) -- Json that I am trying to parse, and I am lost Structure Array below top level [\#1293](https://github.com/nlohmann/json/issues/1293) -- Serializing std::variant causes stack overflow [\#1292](https://github.com/nlohmann/json/issues/1292) -- How do I go about customising from\_json to support \_\_int128\_t/\_\_uint128\_t? [\#1290](https://github.com/nlohmann/json/issues/1290) -- merge\_patch: inconsistent behaviour merging empty sub-object [\#1289](https://github.com/nlohmann/json/issues/1289) -- Buffer over/underrun using UBJson? [\#1288](https://github.com/nlohmann/json/issues/1288) -- Enable the latest C++ standard with Visual Studio [\#1287](https://github.com/nlohmann/json/issues/1287) -- truncation of constant value in to\_cbor\(\) [\#1286](https://github.com/nlohmann/json/issues/1286) -- eosio.wasmsdk error [\#1284](https://github.com/nlohmann/json/issues/1284) -- use the same interface for writing arrays and non-arrays [\#1283](https://github.com/nlohmann/json/issues/1283) -- How to read json file with optional entries and entries with different types [\#1281](https://github.com/nlohmann/json/issues/1281) -- merge result not as espected [\#1279](https://github.com/nlohmann/json/issues/1279) -- how to get only "name" from below json [\#1278](https://github.com/nlohmann/json/issues/1278) -- syntax error on right json string [\#1276](https://github.com/nlohmann/json/issues/1276) -- Parsing JSON Array where members have no key, using custom types [\#1267](https://github.com/nlohmann/json/issues/1267) -- I get a json exception periodically from json::parse for the same json [\#1263](https://github.com/nlohmann/json/issues/1263) -- GCC 8.2.1. Compilation error: invalid conversion from... [\#1246](https://github.com/nlohmann/json/issues/1246) -- BSON support [\#1244](https://github.com/nlohmann/json/issues/1244) -- enum to json mapping [\#1208](https://github.com/nlohmann/json/issues/1208) -- Soften the landing when dumping non-UTF8 strings \(type\_error.316 exception\) [\#1198](https://github.com/nlohmann/json/issues/1198) - -- Add macro to define enum/JSON mapping [\#1323](https://github.com/nlohmann/json/pull/1323) ([nlohmann](https://github.com/nlohmann)) -- Add BSON support [\#1320](https://github.com/nlohmann/json/pull/1320) ([nlohmann](https://github.com/nlohmann)) -- Properly convert constants to CharType [\#1315](https://github.com/nlohmann/json/pull/1315) ([nlohmann](https://github.com/nlohmann)) -- Allow to set error handler for decoding errors [\#1314](https://github.com/nlohmann/json/pull/1314) ([nlohmann](https://github.com/nlohmann)) -- Add Meson related info to README [\#1305](https://github.com/nlohmann/json/pull/1305) ([koponomarenko](https://github.com/koponomarenko)) -- Improve diagnostic messages for binary formats [\#1303](https://github.com/nlohmann/json/pull/1303) ([nlohmann](https://github.com/nlohmann)) -- add new is\_constructible\_\* traits used in from\_json [\#1301](https://github.com/nlohmann/json/pull/1301) ([theodelrieu](https://github.com/theodelrieu)) -- add constraints for variadic json\_ref constructors [\#1294](https://github.com/nlohmann/json/pull/1294) ([theodelrieu](https://github.com/theodelrieu)) -- Improve diagnostic messages [\#1282](https://github.com/nlohmann/json/pull/1282) ([nlohmann](https://github.com/nlohmann)) -- Removed linter warnings [\#1280](https://github.com/nlohmann/json/pull/1280) ([nlohmann](https://github.com/nlohmann)) -- Thirdparty benchmark: Fix Clang detection. [\#1277](https://github.com/nlohmann/json/pull/1277) ([Lord-Kamina](https://github.com/Lord-Kamina)) - -## [v3.3.0](https://github.com/nlohmann/json/releases/tag/v3.3.0) (2018-10-05) - -[Full Changelog](https://github.com/nlohmann/json/compare/3.3.0...v3.3.0) - -## [3.3.0](https://github.com/nlohmann/json/releases/tag/3.3.0) (2018-10-05) - -[Full Changelog](https://github.com/nlohmann/json/compare/v3.2.0...3.3.0) - -- When key is not found print the key name into error too [\#1273](https://github.com/nlohmann/json/issues/1273) -- Visual Studio 2017 15.8.5 "conditional expression is constant" warning on Line 1851 in json.hpp [\#1268](https://github.com/nlohmann/json/issues/1268) -- how can we get this working on WSL? [\#1264](https://github.com/nlohmann/json/issues/1264) -- Help needed [\#1259](https://github.com/nlohmann/json/issues/1259) -- A way to get to a JSON values "key" [\#1258](https://github.com/nlohmann/json/issues/1258) -- While compiling got 76 errors [\#1255](https://github.com/nlohmann/json/issues/1255) -- Two blackslashes on json output file [\#1253](https://github.com/nlohmann/json/issues/1253) -- Including nlohmann the badwrong way. [\#1250](https://github.com/nlohmann/json/issues/1250) -- how to build with clang? [\#1247](https://github.com/nlohmann/json/issues/1247) -- Cmake target\_link\_libraries unable to find nlohmann\_json since version 3.2.0 [\#1243](https://github.com/nlohmann/json/issues/1243) -- \[Question\] Access to end\(\) iterator reference [\#1242](https://github.com/nlohmann/json/issues/1242) -- Parsing different json format [\#1241](https://github.com/nlohmann/json/issues/1241) -- Parsing Multiple JSON Files [\#1240](https://github.com/nlohmann/json/issues/1240) -- Doesn't compile under C++17 [\#1239](https://github.com/nlohmann/json/issues/1239) -- Conversion operator for nlohmann::json is not SFINAE friendly [\#1237](https://github.com/nlohmann/json/issues/1237) -- Custom deserialization of number\_float\_t [\#1236](https://github.com/nlohmann/json/issues/1236) -- deprecated-declarations warnings when compiling tests with GCC 8.2.1. [\#1233](https://github.com/nlohmann/json/issues/1233) -- Incomplete type with json\_fwd.hpp [\#1232](https://github.com/nlohmann/json/issues/1232) -- Parse Error [\#1229](https://github.com/nlohmann/json/issues/1229) -- json::get function with argument [\#1227](https://github.com/nlohmann/json/issues/1227) -- questions regarding from\_json [\#1226](https://github.com/nlohmann/json/issues/1226) -- Lambda in unevaluated context [\#1225](https://github.com/nlohmann/json/issues/1225) -- NLohmann doesn't compile when enabling strict warning policies [\#1224](https://github.com/nlohmann/json/issues/1224) -- Creating array of objects [\#1223](https://github.com/nlohmann/json/issues/1223) -- Somewhat unhelpful error message "cannot use operator\[\] with object" [\#1220](https://github.com/nlohmann/json/issues/1220) -- single\_include json.hpp [\#1218](https://github.com/nlohmann/json/issues/1218) -- Maps with enum class keys which are convertible to JSON strings should be converted to JSON dictionaries [\#1217](https://github.com/nlohmann/json/issues/1217) -- Adding JSON Array to the Array [\#1216](https://github.com/nlohmann/json/issues/1216) -- Best way to output a vector of a given type to json [\#1215](https://github.com/nlohmann/json/issues/1215) -- compiler warning: double definition of macro JSON\_INTERNAL\_CATCH [\#1213](https://github.com/nlohmann/json/issues/1213) -- Compilation error when using MOCK\_METHOD1 from GMock and nlohmann::json [\#1212](https://github.com/nlohmann/json/issues/1212) -- Issues parsing a previously encoded binary \(non-UTF8\) string. [\#1211](https://github.com/nlohmann/json/issues/1211) -- Yet another ordering question: char \* and parse\(\) [\#1209](https://github.com/nlohmann/json/issues/1209) -- Error using gcc 8.1.0 on Ubuntu 14.04 [\#1207](https://github.com/nlohmann/json/issues/1207) -- "type must be string, but is " std::string\(j.type\_name\(\) [\#1206](https://github.com/nlohmann/json/issues/1206) -- Returning empty json object from a function of type const json& ? [\#1205](https://github.com/nlohmann/json/issues/1205) -- VS2017 compiler suggests using constexpr if [\#1204](https://github.com/nlohmann/json/issues/1204) -- Template instatiation error on compiling [\#1203](https://github.com/nlohmann/json/issues/1203) -- BUG - json dump field with unicode -\> array of ints \(instead of string\) [\#1197](https://github.com/nlohmann/json/issues/1197) -- Compile error using Code::Blocks // mingw-w64 GCC 8.1.0 - "Incomplete Type" [\#1193](https://github.com/nlohmann/json/issues/1193) -- SEGFAULT on arm target [\#1190](https://github.com/nlohmann/json/issues/1190) -- Compiler crash with old Clang [\#1179](https://github.com/nlohmann/json/issues/1179) -- Custom Precision on floating point numbers [\#1170](https://github.com/nlohmann/json/issues/1170) -- Can we have a json\_view class like std::string\_view? [\#1158](https://github.com/nlohmann/json/issues/1158) -- improve error handling [\#1152](https://github.com/nlohmann/json/issues/1152) -- We should remove static\_asserts [\#960](https://github.com/nlohmann/json/issues/960) - -- Fix warning C4127: conditional expression is constant [\#1272](https://github.com/nlohmann/json/pull/1272) ([antonioborondo](https://github.com/antonioborondo)) -- Turn off additional deprecation warnings for GCC. [\#1271](https://github.com/nlohmann/json/pull/1271) ([chuckatkins](https://github.com/chuckatkins)) -- docs: Add additional CMake documentation [\#1270](https://github.com/nlohmann/json/pull/1270) ([chuckatkins](https://github.com/chuckatkins)) -- unit-testsuites.cpp: fix hangup if file not found [\#1262](https://github.com/nlohmann/json/pull/1262) ([knilch0r](https://github.com/knilch0r)) -- Fix broken cmake imported target alias [\#1260](https://github.com/nlohmann/json/pull/1260) ([chuckatkins](https://github.com/chuckatkins)) -- GCC 48 [\#1257](https://github.com/nlohmann/json/pull/1257) ([henryiii](https://github.com/henryiii)) -- Add version and license to meson.build [\#1252](https://github.com/nlohmann/json/pull/1252) ([koponomarenko](https://github.com/koponomarenko)) -- \#1179 Reordered the code. It seems to stop clang 3.4.2 in RHEL 7 from crash… [\#1249](https://github.com/nlohmann/json/pull/1249) ([LEgregius](https://github.com/LEgregius)) -- Use a version check to provide backwards comatible CMake imported target names [\#1245](https://github.com/nlohmann/json/pull/1245) ([chuckatkins](https://github.com/chuckatkins)) -- Fix issue \#1237 [\#1238](https://github.com/nlohmann/json/pull/1238) ([theodelrieu](https://github.com/theodelrieu)) -- Add a get overload taking a parameter. [\#1231](https://github.com/nlohmann/json/pull/1231) ([theodelrieu](https://github.com/theodelrieu)) -- Move lambda out of unevaluated context [\#1230](https://github.com/nlohmann/json/pull/1230) ([mandreyel](https://github.com/mandreyel)) -- Remove static asserts [\#1228](https://github.com/nlohmann/json/pull/1228) ([theodelrieu](https://github.com/theodelrieu)) -- Better error 305 [\#1221](https://github.com/nlohmann/json/pull/1221) ([rivertam](https://github.com/rivertam)) -- Fix \#1213 [\#1214](https://github.com/nlohmann/json/pull/1214) ([simnalamburt](https://github.com/simnalamburt)) -- Export package to allow builds without installing [\#1202](https://github.com/nlohmann/json/pull/1202) ([dennisfischer](https://github.com/dennisfischer)) - -## [v3.2.0](https://github.com/nlohmann/json/releases/tag/v3.2.0) (2018-08-20) - -[Full Changelog](https://github.com/nlohmann/json/compare/3.2.0...v3.2.0) - -## [3.2.0](https://github.com/nlohmann/json/releases/tag/3.2.0) (2018-08-20) - -[Full Changelog](https://github.com/nlohmann/json/compare/v3.1.2...3.2.0) - -- Am I doing this wrong? Getting an empty string [\#1199](https://github.com/nlohmann/json/issues/1199) -- Incompatible Pointer Type [\#1196](https://github.com/nlohmann/json/issues/1196) -- json.exception.type\_error.316 [\#1195](https://github.com/nlohmann/json/issues/1195) -- Strange warnings in Code::Blocks 17.12, GNU GCC [\#1192](https://github.com/nlohmann/json/issues/1192) -- \[Question\] Current place in code to change floating point resolution [\#1191](https://github.com/nlohmann/json/issues/1191) -- Add key name when throwing type error [\#1189](https://github.com/nlohmann/json/issues/1189) -- Not able to include in visual studio code? [\#1188](https://github.com/nlohmann/json/issues/1188) -- Get an Index or row number of an element [\#1186](https://github.com/nlohmann/json/issues/1186) -- Difference between `merge_patch` and `update` [\#1183](https://github.com/nlohmann/json/issues/1183) -- Is there a way to get an element from a JSON without throwing an exception on failure? [\#1182](https://github.com/nlohmann/json/issues/1182) -- to\_string? [\#1181](https://github.com/nlohmann/json/issues/1181) -- How to cache a json object's pointer into a map? [\#1180](https://github.com/nlohmann/json/issues/1180) -- Can this library work within a Qt project for Android using Qt Creator? [\#1178](https://github.com/nlohmann/json/issues/1178) -- How to get all keys of one object? [\#1177](https://github.com/nlohmann/json/issues/1177) -- How can I only parse the first level and get the value as string? [\#1175](https://github.com/nlohmann/json/issues/1175) -- I have a query regarding nlohmann::basic\_json::basic\_json [\#1174](https://github.com/nlohmann/json/issues/1174) -- unordered\_map with vectors won't convert to json? [\#1173](https://github.com/nlohmann/json/issues/1173) -- return json objects from functions [\#1172](https://github.com/nlohmann/json/issues/1172) -- Problem when exporting to CBOR [\#1171](https://github.com/nlohmann/json/issues/1171) -- Roundtripping null to nullptr does not work [\#1169](https://github.com/nlohmann/json/issues/1169) -- MSVC fails to compile std::swap specialization for nlohmann::json [\#1168](https://github.com/nlohmann/json/issues/1168) -- Unexpected behaviour of is\_null - Part II [\#1167](https://github.com/nlohmann/json/issues/1167) -- Floating point imprecision [\#1166](https://github.com/nlohmann/json/issues/1166) -- Combine json objects into one? [\#1165](https://github.com/nlohmann/json/issues/1165) -- Is there any way to know if the object has changed? [\#1164](https://github.com/nlohmann/json/issues/1164) -- Value throws on null string [\#1163](https://github.com/nlohmann/json/issues/1163) -- Weird template issue in large project [\#1162](https://github.com/nlohmann/json/issues/1162) -- \_json returns a different result vs ::parse [\#1161](https://github.com/nlohmann/json/issues/1161) -- Showing difference between two json objects [\#1160](https://github.com/nlohmann/json/issues/1160) -- no instance of overloaded function "std::swap" matches the specified type [\#1159](https://github.com/nlohmann/json/issues/1159) -- resize\(...\)? [\#1157](https://github.com/nlohmann/json/issues/1157) -- Issue with struct nested in class' to\_json [\#1155](https://github.com/nlohmann/json/issues/1155) -- Deserialize std::map with std::nan [\#1154](https://github.com/nlohmann/json/issues/1154) -- Parse throwing errors [\#1149](https://github.com/nlohmann/json/issues/1149) -- cocoapod integration [\#1148](https://github.com/nlohmann/json/issues/1148) -- wstring parsing [\#1147](https://github.com/nlohmann/json/issues/1147) -- Is it possible to dump a two-dimensional array to "\[\[null\],\[1,2,3\]\]"? [\#1146](https://github.com/nlohmann/json/issues/1146) -- Want to write a class member variable and a struct variable \( this structure is inside the class\) to the json file [\#1145](https://github.com/nlohmann/json/issues/1145) -- Does json support converting an instance of a struct into json string? [\#1143](https://github.com/nlohmann/json/issues/1143) -- \#Most efficient way to search for child parameters \(recursive find?\) [\#1141](https://github.com/nlohmann/json/issues/1141) -- could not find to\_json\(\) method in T's namespace [\#1140](https://github.com/nlohmann/json/issues/1140) -- chars get treated as JSON numbers not JSON strings [\#1139](https://github.com/nlohmann/json/issues/1139) -- How do I count number of objects in array? [\#1137](https://github.com/nlohmann/json/issues/1137) -- Serializing a vector of classes? [\#1136](https://github.com/nlohmann/json/issues/1136) -- Compile error. Unable convert form nullptr to nullptr&& [\#1135](https://github.com/nlohmann/json/issues/1135) -- std::unordered\_map in struct, serialization [\#1133](https://github.com/nlohmann/json/issues/1133) -- dump\(\) can't handle umlauts [\#1131](https://github.com/nlohmann/json/issues/1131) -- Add a way to get a key reference from the iterator [\#1127](https://github.com/nlohmann/json/issues/1127) -- can't not parse "\\“ string [\#1123](https://github.com/nlohmann/json/issues/1123) -- if json file contain Internationalization chars , get exception [\#1122](https://github.com/nlohmann/json/issues/1122) -- How to use a json::iterator dereferenced value in code? [\#1120](https://github.com/nlohmann/json/issues/1120) -- Disable implicit conversions from json to std::initializer\_list\ for any T [\#1118](https://github.com/nlohmann/json/issues/1118) -- Implicit conversions to complex types can lead to surprising and confusing errors [\#1116](https://github.com/nlohmann/json/issues/1116) -- How can I write from\_json for a complex datatype that is not default constructible? [\#1115](https://github.com/nlohmann/json/issues/1115) -- Compile error in VS2015 when compiling unit-conversions.cpp [\#1114](https://github.com/nlohmann/json/issues/1114) -- ADL Serializer for std::any / boost::any [\#1113](https://github.com/nlohmann/json/issues/1113) -- Unexpected behaviour of is\_null [\#1112](https://github.com/nlohmann/json/issues/1112) -- How to resolve " undefined reference to `std::\_\_throw\_bad\_cast\(\)'" [\#1111](https://github.com/nlohmann/json/issues/1111) -- cannot compile on ubuntu 18.04 and 16.04 [\#1110](https://github.com/nlohmann/json/issues/1110) -- JSON representation for floating point values has too many digits [\#1109](https://github.com/nlohmann/json/issues/1109) -- Not working for classes containing "\_declspec\(dllimport\)" in their declaration [\#1108](https://github.com/nlohmann/json/issues/1108) -- Get keys from json object [\#1107](https://github.com/nlohmann/json/issues/1107) -- Cannot deserialize types using std::ratio [\#1105](https://github.com/nlohmann/json/issues/1105) -- i want to learn json [\#1104](https://github.com/nlohmann/json/issues/1104) -- Type checking during compile [\#1103](https://github.com/nlohmann/json/issues/1103) -- Iterate through sub items [\#1102](https://github.com/nlohmann/json/issues/1102) -- cppcheck failing for version 3.1.2 [\#1101](https://github.com/nlohmann/json/issues/1101) -- Deserializing std::map [\#1100](https://github.com/nlohmann/json/issues/1100) -- accessing key by reference [\#1098](https://github.com/nlohmann/json/issues/1098) -- clang 3.8.0 croaks while trying to compile with debug symbols [\#1097](https://github.com/nlohmann/json/issues/1097) -- Serialize a list of class objects with json [\#1096](https://github.com/nlohmann/json/issues/1096) -- Small question [\#1094](https://github.com/nlohmann/json/issues/1094) -- Upgrading to 3.x: to\_/from\_json with enum class [\#1093](https://github.com/nlohmann/json/issues/1093) -- Q: few questions about json construction [\#1092](https://github.com/nlohmann/json/issues/1092) -- general crayCC compilation failure [\#1091](https://github.com/nlohmann/json/issues/1091) -- Merge Patch clears original data [\#1090](https://github.com/nlohmann/json/issues/1090) -- \[Question\] how to use nlohmann/json in c++? [\#1088](https://github.com/nlohmann/json/issues/1088) -- C++17 decomposition declaration support [\#1087](https://github.com/nlohmann/json/issues/1087) -- \[Question\] Access multi-level json objects [\#1086](https://github.com/nlohmann/json/issues/1086) -- Serializing vector [\#1085](https://github.com/nlohmann/json/issues/1085) -- update nested value in multi hierarchy json object [\#1084](https://github.com/nlohmann/json/issues/1084) -- Overriding default values? [\#1083](https://github.com/nlohmann/json/issues/1083) -- detail namespace collision with Cereal? [\#1082](https://github.com/nlohmann/json/issues/1082) -- Error using json.dump\(\); [\#1081](https://github.com/nlohmann/json/issues/1081) -- Consuming TCP Stream [\#1080](https://github.com/nlohmann/json/issues/1080) -- Compilation error with strong typed enums in map in combination with namespaces [\#1079](https://github.com/nlohmann/json/issues/1079) -- cassert error [\#1076](https://github.com/nlohmann/json/issues/1076) -- Valid json data not being parsed [\#1075](https://github.com/nlohmann/json/issues/1075) -- Feature request :: Better testing for key existance without try/catch [\#1074](https://github.com/nlohmann/json/issues/1074) -- Hi, I have input like a.b.c and want to convert it to \"a\"{\"b\": \"c\"} form. Any suggestions how do I do this? Thanks. [\#1073](https://github.com/nlohmann/json/issues/1073) -- ADL deserializer not picked up for non default-constructible type [\#1072](https://github.com/nlohmann/json/issues/1072) -- Deserializing std::array doesn't compiler \(no insert\(\)\) [\#1071](https://github.com/nlohmann/json/issues/1071) -- Serializing OpenCV Mat problem [\#1070](https://github.com/nlohmann/json/issues/1070) -- Compilation error with ICPC compiler [\#1068](https://github.com/nlohmann/json/issues/1068) -- Not existing value, crash [\#1065](https://github.com/nlohmann/json/issues/1065) -- cyryllic symbols [\#1064](https://github.com/nlohmann/json/issues/1064) -- newbie usage question [\#1063](https://github.com/nlohmann/json/issues/1063) -- Trying j\["strTest"\] = "%A" produces "strTest": "-0X1.CCCCCCCCCCCCCP+205" [\#1062](https://github.com/nlohmann/json/issues/1062) -- convert json value to std::string??? [\#1061](https://github.com/nlohmann/json/issues/1061) -- Commented out test cases, should they be removed? [\#1060](https://github.com/nlohmann/json/issues/1060) -- different behaviour between clang and gcc with braced initialization [\#1059](https://github.com/nlohmann/json/issues/1059) -- json array: initialize with prescribed size and `resize` method. [\#1057](https://github.com/nlohmann/json/issues/1057) -- Is it possible to use exceptions istead of assertions? [\#1056](https://github.com/nlohmann/json/issues/1056) -- when using assign operator in with json object a static assertion fails.. [\#1055](https://github.com/nlohmann/json/issues/1055) -- Iterate over leafs of a JSON data structure: enrich the JSON pointer API [\#1054](https://github.com/nlohmann/json/issues/1054) -- \[Feature request\] Access by path [\#1053](https://github.com/nlohmann/json/issues/1053) -- document that implicit js -\> primitive conversion does not work for std::string::value\_type and why [\#1052](https://github.com/nlohmann/json/issues/1052) -- error: ‘BasicJsonType’ in namespace ‘::’ does not name a type [\#1051](https://github.com/nlohmann/json/issues/1051) -- Destructor is called when filling object through assignement [\#1050](https://github.com/nlohmann/json/issues/1050) -- Is this thing thread safe for reads? [\#1049](https://github.com/nlohmann/json/issues/1049) -- clang-tidy: Call to virtual function during construction [\#1046](https://github.com/nlohmann/json/issues/1046) -- Using STL algorithms with JSON containers with expected results? [\#1045](https://github.com/nlohmann/json/issues/1045) -- Usage with gtest/gmock not working as expected [\#1044](https://github.com/nlohmann/json/issues/1044) -- Consequences of from\_json / to\_json being in namespace of data struct. [\#1042](https://github.com/nlohmann/json/issues/1042) -- const\_reference operator\[\]\(const typename object\_t::key\_type& key\) const throw instead of assert [\#1039](https://github.com/nlohmann/json/issues/1039) -- Trying to retrieve data from nested objects [\#1038](https://github.com/nlohmann/json/issues/1038) -- Direct download link for json\_fwd.hpp? [\#1037](https://github.com/nlohmann/json/issues/1037) -- I know the library supports UTF-8, but failed to dump the value [\#1036](https://github.com/nlohmann/json/issues/1036) -- Putting a Vec3-like vector into a json object [\#1035](https://github.com/nlohmann/json/issues/1035) -- Ternary operator crash [\#1034](https://github.com/nlohmann/json/issues/1034) -- Issued with Clion Inspection Resolution since 2018.1 [\#1033](https://github.com/nlohmann/json/issues/1033) -- Some testcases fail and one never finishes [\#1032](https://github.com/nlohmann/json/issues/1032) -- Can this class work with wchar\_t / std::wstring? [\#1031](https://github.com/nlohmann/json/issues/1031) -- Makefile: Valgrind flags have no effect [\#1030](https://github.com/nlohmann/json/issues/1030) -- 「==」 Should be 「\>」 [\#1029](https://github.com/nlohmann/json/issues/1029) -- HOCON reader? [\#1027](https://github.com/nlohmann/json/issues/1027) -- add json string in previous string?? [\#1025](https://github.com/nlohmann/json/issues/1025) -- RFC: fluent parsing interface [\#1023](https://github.com/nlohmann/json/issues/1023) -- Does it support chinese character? [\#1022](https://github.com/nlohmann/json/issues/1022) -- to/from\_msgpack only works with standard typization [\#1021](https://github.com/nlohmann/json/issues/1021) -- Build failure using latest clang and GCC compilers [\#1020](https://github.com/nlohmann/json/issues/1020) -- can two json objects be concatenated? [\#1019](https://github.com/nlohmann/json/issues/1019) -- Erase by integer index [\#1018](https://github.com/nlohmann/json/issues/1018) -- Function find overload taking a json\_pointer [\#1017](https://github.com/nlohmann/json/issues/1017) -- I think should implement an parser function [\#1016](https://github.com/nlohmann/json/issues/1016) -- Readme gif [\#1015](https://github.com/nlohmann/json/issues/1015) -- Python bindings [\#1014](https://github.com/nlohmann/json/issues/1014) -- how to add two json string in single object?? [\#1012](https://github.com/nlohmann/json/issues/1012) -- how to serialize class Object \(convert data in object into json\)?? [\#1011](https://github.com/nlohmann/json/issues/1011) -- Enable forward declaration of json by making json a class instead of a using declaration [\#997](https://github.com/nlohmann/json/issues/997) -- compilation error while using intel c++ compiler 2018 [\#994](https://github.com/nlohmann/json/issues/994) -- How to create a json variable? [\#990](https://github.com/nlohmann/json/issues/990) -- istream \>\> json --- 1st character skipped in stream [\#976](https://github.com/nlohmann/json/issues/976) -- Add a SAX parser [\#971](https://github.com/nlohmann/json/issues/971) -- How to solve large json file? [\#927](https://github.com/nlohmann/json/issues/927) -- json\_pointer public push\_back, pop\_back [\#837](https://github.com/nlohmann/json/issues/837) -- Using input\_adapter in a slightly unexpected way [\#834](https://github.com/nlohmann/json/issues/834) - -- Fix -Wno-sometimes-uninitialized by initializing "result" in parse\_sax [\#1200](https://github.com/nlohmann/json/pull/1200) ([thyu](https://github.com/thyu)) -- \[RFC\] Introduce a new macro function: JSON\_INTERNAL\_CATCH [\#1187](https://github.com/nlohmann/json/pull/1187) ([simnalamburt](https://github.com/simnalamburt)) -- Fix unit tests that were silently skipped or crashed \(depending on the compiler\) [\#1176](https://github.com/nlohmann/json/pull/1176) ([grembo](https://github.com/grembo)) -- Refactor/no virtual sax [\#1153](https://github.com/nlohmann/json/pull/1153) ([theodelrieu](https://github.com/theodelrieu)) -- Fixed compiler error in VS 2015 for debug mode [\#1151](https://github.com/nlohmann/json/pull/1151) ([sonulohani](https://github.com/sonulohani)) -- Fix links to cppreference named requirements \(formerly concepts\) [\#1144](https://github.com/nlohmann/json/pull/1144) ([jrakow](https://github.com/jrakow)) -- meson: fix include directory [\#1142](https://github.com/nlohmann/json/pull/1142) ([jrakow](https://github.com/jrakow)) -- Feature/unordered map conversion [\#1138](https://github.com/nlohmann/json/pull/1138) ([theodelrieu](https://github.com/theodelrieu)) -- fixed compile error for \#1045 [\#1134](https://github.com/nlohmann/json/pull/1134) ([Daniel599](https://github.com/Daniel599)) -- test \(non\)equality for alt\_string implementation [\#1130](https://github.com/nlohmann/json/pull/1130) ([agrianius](https://github.com/agrianius)) -- remove stringstream dependency [\#1117](https://github.com/nlohmann/json/pull/1117) ([TinyTinni](https://github.com/TinyTinni)) -- Provide a from\_json overload for std::map [\#1089](https://github.com/nlohmann/json/pull/1089) ([theodelrieu](https://github.com/theodelrieu)) -- fix typo in README [\#1078](https://github.com/nlohmann/json/pull/1078) ([martin-mfg](https://github.com/martin-mfg)) -- Fix typo [\#1058](https://github.com/nlohmann/json/pull/1058) ([dns13](https://github.com/dns13)) -- Misc cmake packaging enhancements [\#1048](https://github.com/nlohmann/json/pull/1048) ([chuckatkins](https://github.com/chuckatkins)) -- Fixed incorrect LLVM version number in README [\#1047](https://github.com/nlohmann/json/pull/1047) ([jammehcow](https://github.com/jammehcow)) -- Fix trivial typo in comment. [\#1043](https://github.com/nlohmann/json/pull/1043) ([coryan](https://github.com/coryan)) -- Package Manager: Spack [\#1041](https://github.com/nlohmann/json/pull/1041) ([ax3l](https://github.com/ax3l)) -- CMake: 3.8+ is Sufficient [\#1040](https://github.com/nlohmann/json/pull/1040) ([ax3l](https://github.com/ax3l)) -- Added support for string\_view in C++17 [\#1028](https://github.com/nlohmann/json/pull/1028) ([gracicot](https://github.com/gracicot)) -- Added public target\_compile\_features for auto and constexpr [\#1026](https://github.com/nlohmann/json/pull/1026) ([ktonon](https://github.com/ktonon)) - -## [v3.1.2](https://github.com/nlohmann/json/releases/tag/v3.1.2) (2018-03-14) - -[Full Changelog](https://github.com/nlohmann/json/compare/3.1.2...v3.1.2) - -## [3.1.2](https://github.com/nlohmann/json/releases/tag/3.1.2) (2018-03-14) - -[Full Changelog](https://github.com/nlohmann/json/compare/v3.1.1...3.1.2) - -- STL containers are always serialized to a nested array like \[\[1,2,3\]\] [\#1013](https://github.com/nlohmann/json/issues/1013) -- The library doesn't want to insert an unordered\_map [\#1010](https://github.com/nlohmann/json/issues/1010) -- Convert Json to uint8\_t [\#1008](https://github.com/nlohmann/json/issues/1008) -- How to compare two JSON objects? [\#1007](https://github.com/nlohmann/json/issues/1007) -- Syntax checking [\#1003](https://github.com/nlohmann/json/issues/1003) -- more than one operator '=' matches these operands [\#1002](https://github.com/nlohmann/json/issues/1002) -- How to check if key existed [\#1000](https://github.com/nlohmann/json/issues/1000) -- nlohmann::json::parse exhaust memory in go binding [\#999](https://github.com/nlohmann/json/issues/999) -- Range-based iteration over a non-array object [\#998](https://github.com/nlohmann/json/issues/998) -- get\ for types that are not default constructible [\#996](https://github.com/nlohmann/json/issues/996) -- Prevent Null values to appear in .dump\(\) [\#995](https://github.com/nlohmann/json/issues/995) -- number parsing [\#993](https://github.com/nlohmann/json/issues/993) -- C2664 \(C++/CLR\) cannot convert 'nullptr' to 'nullptr &&' [\#987](https://github.com/nlohmann/json/issues/987) -- Uniform initialization from another json object differs between gcc and clang. [\#985](https://github.com/nlohmann/json/issues/985) -- Problem with adding the lib as a submodule [\#983](https://github.com/nlohmann/json/issues/983) -- UTF-8/Unicode error [\#982](https://github.com/nlohmann/json/issues/982) -- "forcing MSVC stacktrace to show which T we're talking about." error [\#980](https://github.com/nlohmann/json/issues/980) -- reverse order of serialization [\#979](https://github.com/nlohmann/json/issues/979) -- Assigning between different json types [\#977](https://github.com/nlohmann/json/issues/977) -- Support serialisation of `unique_ptr<>` and `shared_ptr<>` [\#975](https://github.com/nlohmann/json/issues/975) -- Unexpected end of input \(not same as one before\) [\#974](https://github.com/nlohmann/json/issues/974) -- Segfault on direct initializing json object [\#973](https://github.com/nlohmann/json/issues/973) -- Segmentation fault on G++ when trying to assign json string literal to custom json type. [\#972](https://github.com/nlohmann/json/issues/972) -- os\_defines.h:44:19: error: missing binary operator before token "\(" [\#970](https://github.com/nlohmann/json/issues/970) -- Passing an iteration object by reference to a function [\#967](https://github.com/nlohmann/json/issues/967) -- Json and fmt::lib's format\_arg\(\) [\#964](https://github.com/nlohmann/json/issues/964) - -- Allowing for user-defined string type in lexer/parser [\#1009](https://github.com/nlohmann/json/pull/1009) ([nlohmann](https://github.com/nlohmann)) -- dump to alternative string type, as defined in basic\_json template [\#1006](https://github.com/nlohmann/json/pull/1006) ([agrianius](https://github.com/agrianius)) -- Fix memory leak during parser callback [\#1001](https://github.com/nlohmann/json/pull/1001) ([nlohmann](https://github.com/nlohmann)) -- fixed misprinted condition detected by PVS Studio. [\#992](https://github.com/nlohmann/json/pull/992) ([bogemic](https://github.com/bogemic)) -- Fix/basic json conversion [\#986](https://github.com/nlohmann/json/pull/986) ([theodelrieu](https://github.com/theodelrieu)) -- Make integration section concise [\#981](https://github.com/nlohmann/json/pull/981) ([wla80](https://github.com/wla80)) - -## [v3.1.1](https://github.com/nlohmann/json/releases/tag/v3.1.1) (2018-02-13) - -[Full Changelog](https://github.com/nlohmann/json/compare/v3.1.0...v3.1.1) - -- Updation of child object isn't reflected in parent Object [\#968](https://github.com/nlohmann/json/issues/968) -- How to add user defined C++ path to sublime text [\#966](https://github.com/nlohmann/json/issues/966) -- fast number parsing [\#965](https://github.com/nlohmann/json/issues/965) -- With non-unique keys, later stored entries are not taken into account anymore [\#963](https://github.com/nlohmann/json/issues/963) -- Timeout \(OSS-Fuzz 6034\) [\#962](https://github.com/nlohmann/json/issues/962) -- Incorrect parsing of indefinite length CBOR strings. [\#961](https://github.com/nlohmann/json/issues/961) -- Reload a json file at runtime without emptying my std::ifstream [\#959](https://github.com/nlohmann/json/issues/959) -- Split headers should be part of the release [\#956](https://github.com/nlohmann/json/issues/956) -- Coveralls shows no coverage data [\#953](https://github.com/nlohmann/json/issues/953) -- Feature request: Implicit conversion to bool [\#951](https://github.com/nlohmann/json/issues/951) -- converting json to vector of type with templated constructor [\#924](https://github.com/nlohmann/json/issues/924) -- No structured bindings support? [\#901](https://github.com/nlohmann/json/issues/901) -- \[Request\] Macro generating from\_json\(\) and to\_json\(\) [\#895](https://github.com/nlohmann/json/issues/895) -- basic\_json::value throws exception instead of returning default value [\#871](https://github.com/nlohmann/json/issues/871) - -- Fix constraints on from\_json\(CompatibleArrayType\) [\#969](https://github.com/nlohmann/json/pull/969) ([theodelrieu](https://github.com/theodelrieu)) -- Make coveralls watch the include folder [\#957](https://github.com/nlohmann/json/pull/957) ([theodelrieu](https://github.com/theodelrieu)) -- Fix links in README.md [\#955](https://github.com/nlohmann/json/pull/955) ([patrikhuber](https://github.com/patrikhuber)) -- Add a note about installing the library with cget [\#954](https://github.com/nlohmann/json/pull/954) ([pfultz2](https://github.com/pfultz2)) - -## [v3.1.0](https://github.com/nlohmann/json/releases/tag/v3.1.0) (2018-02-01) - -[Full Changelog](https://github.com/nlohmann/json/compare/3.1.0...v3.1.0) - -## [3.1.0](https://github.com/nlohmann/json/releases/tag/3.1.0) (2018-02-01) - -[Full Changelog](https://github.com/nlohmann/json/compare/v3.0.1...3.1.0) - -- I have a proposal [\#949](https://github.com/nlohmann/json/issues/949) -- VERSION define\(s\) [\#948](https://github.com/nlohmann/json/issues/948) -- v3.0.1 compile error in icc 16.0.4 [\#947](https://github.com/nlohmann/json/issues/947) -- Use in VS2017 15.5.5 [\#946](https://github.com/nlohmann/json/issues/946) -- Process for reporting Security Bugs? [\#945](https://github.com/nlohmann/json/issues/945) -- Please expose a NLOHMANN\_JSON\_VERSION macro [\#943](https://github.com/nlohmann/json/issues/943) -- Change header include directory to nlohmann/json [\#942](https://github.com/nlohmann/json/issues/942) -- string\_type in binary\_reader [\#941](https://github.com/nlohmann/json/issues/941) -- compile error with clang 5.0 -std=c++1z and no string\_view [\#939](https://github.com/nlohmann/json/issues/939) -- Allow overriding JSON\_THROW to something else than abort\(\) [\#938](https://github.com/nlohmann/json/issues/938) -- Handle invalid string in Json file [\#937](https://github.com/nlohmann/json/issues/937) -- Unused variable 'kMinExp' [\#935](https://github.com/nlohmann/json/issues/935) -- yytext is already defined [\#933](https://github.com/nlohmann/json/issues/933) -- Equality operator fails [\#931](https://github.com/nlohmann/json/issues/931) -- use in visual studio 2015 [\#929](https://github.com/nlohmann/json/issues/929) -- Relative includes of json\_fwd.hpp in detail/meta.hpp. \[Develop branch\] [\#928](https://github.com/nlohmann/json/issues/928) -- GCC 7.x issue [\#926](https://github.com/nlohmann/json/issues/926) -- json\_fwd.hpp not installed [\#923](https://github.com/nlohmann/json/issues/923) -- Use Google Benchmarks [\#921](https://github.com/nlohmann/json/issues/921) -- Move class json\_pointer to separate file [\#920](https://github.com/nlohmann/json/issues/920) -- Unable to locate 'to\_json\(\)' and 'from\_json\(\)' methods in the same namespace [\#917](https://github.com/nlohmann/json/issues/917) -- \[answered\]Read key1 from .value example [\#914](https://github.com/nlohmann/json/issues/914) -- Don't use `define private public` in test files [\#913](https://github.com/nlohmann/json/issues/913) -- value\(\) template argument type deduction [\#912](https://github.com/nlohmann/json/issues/912) -- Installation path is incorrect [\#910](https://github.com/nlohmann/json/issues/910) -- H [\#909](https://github.com/nlohmann/json/issues/909) -- Build failure using clang 5 [\#908](https://github.com/nlohmann/json/issues/908) -- Amalgate [\#907](https://github.com/nlohmann/json/issues/907) -- Update documentation and tests wrt. split headers [\#906](https://github.com/nlohmann/json/issues/906) -- Lib not working on ubuntu 16.04 [\#905](https://github.com/nlohmann/json/issues/905) -- Problem when writing to file. [\#904](https://github.com/nlohmann/json/issues/904) -- C2864 error when compiling with VS2015 and VS 2017 [\#903](https://github.com/nlohmann/json/issues/903) -- \[json.exception.type\_error.304\] cannot use at\(\) with object [\#902](https://github.com/nlohmann/json/issues/902) -- How do I forward nlohmann::json declaration? [\#899](https://github.com/nlohmann/json/issues/899) -- How to effectively store binary data? [\#898](https://github.com/nlohmann/json/issues/898) -- How to get the length of a JSON string without retrieving its std::string? [\#897](https://github.com/nlohmann/json/issues/897) -- Regression Tests Failure using "ctest" [\#887](https://github.com/nlohmann/json/issues/887) -- Discuss: add JSON Merge Patch \(RFC 7396\)? [\#877](https://github.com/nlohmann/json/issues/877) -- Discuss: replace static "iterator\_wrapper" function with "items" member function [\#874](https://github.com/nlohmann/json/issues/874) -- Make optional user-data available in from\_json [\#864](https://github.com/nlohmann/json/issues/864) -- Casting to std::string not working in VS2015 [\#861](https://github.com/nlohmann/json/issues/861) -- Sequential reading of JSON arrays [\#851](https://github.com/nlohmann/json/issues/851) -- Idea: Handle Multimaps Better [\#816](https://github.com/nlohmann/json/issues/816) -- Floating point rounding [\#777](https://github.com/nlohmann/json/issues/777) -- Loss of precision when serializing \ [\#360](https://github.com/nlohmann/json/issues/360) - -- Templatize std::string in binary\_reader \#941 [\#950](https://github.com/nlohmann/json/pull/950) ([kaidokert](https://github.com/kaidokert)) -- fix cmake install directory \(for real this time\) [\#944](https://github.com/nlohmann/json/pull/944) ([theodelrieu](https://github.com/theodelrieu)) -- Allow overriding THROW/CATCH/TRY macros with no-exceptions \#938 [\#940](https://github.com/nlohmann/json/pull/940) ([kaidokert](https://github.com/kaidokert)) -- Removed compiler warning about unused variable 'kMinExp' [\#936](https://github.com/nlohmann/json/pull/936) ([zerodefect](https://github.com/zerodefect)) -- Fix a typo in README.md [\#930](https://github.com/nlohmann/json/pull/930) ([Pipeliner](https://github.com/Pipeliner)) -- Howto installation of json\_fwd.hpp \(fixes \#923\) [\#925](https://github.com/nlohmann/json/pull/925) ([zerodefect](https://github.com/zerodefect)) -- fix sfinae on basic\_json UDT constructor [\#919](https://github.com/nlohmann/json/pull/919) ([theodelrieu](https://github.com/theodelrieu)) -- Floating-point formatting [\#915](https://github.com/nlohmann/json/pull/915) ([abolz](https://github.com/abolz)) -- Fix/cmake install [\#911](https://github.com/nlohmann/json/pull/911) ([theodelrieu](https://github.com/theodelrieu)) -- fix link to the documentation of the emplace function [\#900](https://github.com/nlohmann/json/pull/900) ([Dobiasd](https://github.com/Dobiasd)) -- JSON Merge Patch \(RFC 7396\) [\#876](https://github.com/nlohmann/json/pull/876) ([nlohmann](https://github.com/nlohmann)) -- Refactor/split it [\#700](https://github.com/nlohmann/json/pull/700) ([theodelrieu](https://github.com/theodelrieu)) - -## [v3.0.1](https://github.com/nlohmann/json/releases/tag/v3.0.1) (2017-12-29) - -[Full Changelog](https://github.com/nlohmann/json/compare/3.0.1...v3.0.1) - -## [3.0.1](https://github.com/nlohmann/json/releases/tag/3.0.1) (2017-12-29) - -[Full Changelog](https://github.com/nlohmann/json/compare/v3.0.0...3.0.1) - -- Problem parsing array to global vector [\#896](https://github.com/nlohmann/json/issues/896) -- Invalid RFC6902 copy operation succeeds [\#894](https://github.com/nlohmann/json/issues/894) -- How to rename a key during looping? [\#893](https://github.com/nlohmann/json/issues/893) -- clang++-6.0 \(6.0.0-svn321357-1\) warning [\#892](https://github.com/nlohmann/json/issues/892) -- Make json.hpp aware of the modules TS? [\#891](https://github.com/nlohmann/json/issues/891) -- All enum values not handled in switch cases. \( -Wswitch-enum \) [\#889](https://github.com/nlohmann/json/issues/889) -- JSON Pointer resolve failure resulting in incorrect exception code [\#888](https://github.com/nlohmann/json/issues/888) -- Unexpected nested arrays from std::vector [\#886](https://github.com/nlohmann/json/issues/886) -- erase multiple elements from a json object [\#884](https://github.com/nlohmann/json/issues/884) -- Container function overview in Doxygen is not updated [\#883](https://github.com/nlohmann/json/issues/883) -- How to use this for binary file uploads [\#881](https://github.com/nlohmann/json/issues/881) -- Allow setting JSON\_BuildTests=OFF from parent CMakeLists.txt [\#846](https://github.com/nlohmann/json/issues/846) -- Unit test fails for local-independent str-to-num [\#845](https://github.com/nlohmann/json/issues/845) -- Another idea about type support [\#774](https://github.com/nlohmann/json/issues/774) - -- Includes CTest module/adds BUILD\_TESTING option [\#885](https://github.com/nlohmann/json/pull/885) ([TinyTinni](https://github.com/TinyTinni)) -- Fix MSVC warning C4819 [\#882](https://github.com/nlohmann/json/pull/882) ([erengy](https://github.com/erengy)) -- Merge branch 'develop' into coverity\_scan [\#880](https://github.com/nlohmann/json/pull/880) ([nlohmann](https://github.com/nlohmann)) -- :wrench: Fix up a few more effc++ items [\#858](https://github.com/nlohmann/json/pull/858) ([mattismyname](https://github.com/mattismyname)) - -## [v3.0.0](https://github.com/nlohmann/json/releases/tag/v3.0.0) (2017-12-17) - -[Full Changelog](https://github.com/nlohmann/json/compare/3.0.0...v3.0.0) - -## [3.0.0](https://github.com/nlohmann/json/releases/tag/3.0.0) (2017-12-17) - -[Full Changelog](https://github.com/nlohmann/json/compare/v2.1.1...3.0.0) - -- unicode strings [\#878](https://github.com/nlohmann/json/issues/878) -- Visual Studio 2017 15.5 C++17 std::allocator deprecations [\#872](https://github.com/nlohmann/json/issues/872) -- Typo "excpetion" [\#869](https://github.com/nlohmann/json/issues/869) -- Explicit array example in README.md incorrect [\#867](https://github.com/nlohmann/json/issues/867) -- why don't you release this from Feb. ? [\#865](https://github.com/nlohmann/json/issues/865) -- json::parse throws std::invalid\_argument when processing string generated by json::dump\(\) [\#863](https://github.com/nlohmann/json/issues/863) -- code analysis: potential bug? [\#859](https://github.com/nlohmann/json/issues/859) -- MSVC2017, 15.5 new issues. [\#857](https://github.com/nlohmann/json/issues/857) -- very basic: fetching string value/content without quotes [\#853](https://github.com/nlohmann/json/issues/853) -- Ambiguous function call to get with pointer type and constant json object in VS2015 \(15.4.4\) [\#852](https://github.com/nlohmann/json/issues/852) -- How to put object in the array as a member? [\#850](https://github.com/nlohmann/json/issues/850) -- misclick, please ignore [\#849](https://github.com/nlohmann/json/issues/849) -- Make XML great again. [\#847](https://github.com/nlohmann/json/issues/847) -- Converting to array not working [\#843](https://github.com/nlohmann/json/issues/843) -- Iteration weirdness [\#842](https://github.com/nlohmann/json/issues/842) -- Use reference or pointer as Object value [\#841](https://github.com/nlohmann/json/issues/841) -- Ambiguity in parsing nested maps [\#840](https://github.com/nlohmann/json/issues/840) -- could not find from\_json\(\) method in T's namespace [\#839](https://github.com/nlohmann/json/issues/839) -- Incorrect parse error with binary data in keys? [\#838](https://github.com/nlohmann/json/issues/838) -- using dump\(\) when std::wstring is StringType with VS2017 [\#836](https://github.com/nlohmann/json/issues/836) -- Show the path of the currently parsed value when an error occurs [\#835](https://github.com/nlohmann/json/issues/835) -- Repetitive data type while reading [\#833](https://github.com/nlohmann/json/issues/833) -- Storing multiple types inside map [\#831](https://github.com/nlohmann/json/issues/831) -- Application terminating [\#830](https://github.com/nlohmann/json/issues/830) -- Missing CMake hunter package? [\#828](https://github.com/nlohmann/json/issues/828) -- std::map\ from json object yields C2665: 'std::pair\::pair': none of the 2 overloads could convert all the argument types [\#827](https://github.com/nlohmann/json/issues/827) -- object.dump gives quoted string, want to use .dump\(\) to generate javascripts. [\#826](https://github.com/nlohmann/json/issues/826) -- Assertion failed on \["NoExistKey"\] of an not existing key of const json& [\#825](https://github.com/nlohmann/json/issues/825) -- vs2015 error : static member will remain uninitialized at runtime but use in constant-expressions is supported [\#824](https://github.com/nlohmann/json/issues/824) -- Code Checking Warnings from json.hpp on VS2017 Community [\#821](https://github.com/nlohmann/json/issues/821) -- Missing iostream in try online [\#820](https://github.com/nlohmann/json/issues/820) -- Floating point value loses decimal point during dump [\#818](https://github.com/nlohmann/json/issues/818) -- Conan package for the library [\#817](https://github.com/nlohmann/json/issues/817) -- stream error [\#815](https://github.com/nlohmann/json/issues/815) -- Link error when using find\(\) on the latest commit [\#814](https://github.com/nlohmann/json/issues/814) -- ABI issue with json object between 2 shared libraries [\#813](https://github.com/nlohmann/json/issues/813) -- scan\_string\(\) return token\_type::parse\_error; when parse ansi file [\#812](https://github.com/nlohmann/json/issues/812) -- segfault when using fifo\_map with json [\#810](https://github.com/nlohmann/json/issues/810) -- This shit is shit [\#809](https://github.com/nlohmann/json/issues/809) -- \_finite and \_isnan are no members of "std" [\#808](https://github.com/nlohmann/json/issues/808) -- how to print out the line which causing exception? [\#806](https://github.com/nlohmann/json/issues/806) -- {} uses copy constructor, while = does not [\#805](https://github.com/nlohmann/json/issues/805) -- json.hpp:8955: multiple definition of function that is not defined twice or more. [\#804](https://github.com/nlohmann/json/issues/804) -- \[question\] to\_json for base and derived class [\#803](https://github.com/nlohmann/json/issues/803) -- Misleading error message - unexpected '"' - on incorrect utf-8 symbol [\#802](https://github.com/nlohmann/json/issues/802) -- json data = std::string\_view\("hi"\); doesn't work? [\#801](https://github.com/nlohmann/json/issues/801) -- Thread safety of parse\(\) [\#800](https://github.com/nlohmann/json/issues/800) -- Numbers as strings [\#799](https://github.com/nlohmann/json/issues/799) -- Tests failing on arm [\#797](https://github.com/nlohmann/json/issues/797) -- Using your library \(without modification\) in another library [\#796](https://github.com/nlohmann/json/issues/796) -- Iterating over sub-object [\#794](https://github.com/nlohmann/json/issues/794) -- how to get the json object again from which printed by the method of dump\(\) [\#792](https://github.com/nlohmann/json/issues/792) -- ppa to include source [\#791](https://github.com/nlohmann/json/issues/791) -- Different include paths in macOS and Ubuntu [\#790](https://github.com/nlohmann/json/issues/790) -- Missing break after line 12886 in switch/case [\#789](https://github.com/nlohmann/json/issues/789) -- All unit tests fail? [\#787](https://github.com/nlohmann/json/issues/787) -- More use of move semantics in deserialization [\#786](https://github.com/nlohmann/json/issues/786) -- warning C4706 - Visual Studio 2017 \(/W4\) [\#784](https://github.com/nlohmann/json/issues/784) -- Compile error in clang 5.0 [\#782](https://github.com/nlohmann/json/issues/782) -- Error Installing appium\_lib with Ruby v2.4.2 Due to JSON [\#781](https://github.com/nlohmann/json/issues/781) -- ::get\\(\) fails in new\(er\) release \[MSVC\] [\#780](https://github.com/nlohmann/json/issues/780) -- Type Conversion [\#779](https://github.com/nlohmann/json/issues/779) -- Segfault on nested parsing [\#778](https://github.com/nlohmann/json/issues/778) -- Build warnings: shadowing exception id [\#776](https://github.com/nlohmann/json/issues/776) -- multi-level JSON support. [\#775](https://github.com/nlohmann/json/issues/775) -- SIGABRT on dump\(\) [\#773](https://github.com/nlohmann/json/issues/773) -- \[Question\] Custom StringType template parameter \(possibility for a KeyType template parameter\) [\#772](https://github.com/nlohmann/json/issues/772) -- constexpr ALL the Things! [\#771](https://github.com/nlohmann/json/issues/771) -- error: ‘BasicJsonType’ in namespace ‘::’ does not name a type [\#770](https://github.com/nlohmann/json/issues/770) -- Program calls abort function [\#769](https://github.com/nlohmann/json/issues/769) -- \[Question\] Floating point resolution config during dump\(\) ? [\#768](https://github.com/nlohmann/json/issues/768) -- make check - no test ran [\#767](https://github.com/nlohmann/json/issues/767) -- The library cannot work properly with custom allocator based containers [\#766](https://github.com/nlohmann/json/issues/766) -- Documentation or feature request. [\#763](https://github.com/nlohmann/json/issues/763) -- warnings in msvc about mix/max macro while windows.h is used in the project [\#762](https://github.com/nlohmann/json/issues/762) -- std::signbit ambiguous [\#761](https://github.com/nlohmann/json/issues/761) -- How to use value for std::experimental::optional type? [\#760](https://github.com/nlohmann/json/issues/760) -- Cannot load json file properly [\#759](https://github.com/nlohmann/json/issues/759) -- Compilation error with unordered\_map\< int, int \> [\#758](https://github.com/nlohmann/json/issues/758) -- CBOR string [\#757](https://github.com/nlohmann/json/issues/757) -- Proposal: out\_of\_range should be a subclass of std::out\_of\_range [\#756](https://github.com/nlohmann/json/issues/756) -- Getter is setting the value to null if the key does not exist [\#754](https://github.com/nlohmann/json/issues/754) -- parsing works sometimes and crashes others [\#752](https://github.com/nlohmann/json/issues/752) -- Static\_assert failed "incompatible pointer type" with Xcode [\#751](https://github.com/nlohmann/json/issues/751) -- user-defined literal operator not found [\#750](https://github.com/nlohmann/json/issues/750) -- getting clean string from it.key\(\) [\#748](https://github.com/nlohmann/json/issues/748) -- Best method for exploring and obtaining values of nested json objects when the names are not known beforehand? [\#747](https://github.com/nlohmann/json/issues/747) -- null char at the end of string [\#746](https://github.com/nlohmann/json/issues/746) -- Incorrect sample for operator \>\> in docs [\#745](https://github.com/nlohmann/json/issues/745) -- User-friendly documentation [\#744](https://github.com/nlohmann/json/issues/744) -- Retrieve all values that match a json path [\#743](https://github.com/nlohmann/json/issues/743) -- Compilation issue with gcc 7.2 [\#742](https://github.com/nlohmann/json/issues/742) -- CMake target nlohmann\_json does not have src into its interface includes [\#741](https://github.com/nlohmann/json/issues/741) -- Error when serializing empty json: type must be string, but is object [\#740](https://github.com/nlohmann/json/issues/740) -- Conversion error for std::map\ [\#739](https://github.com/nlohmann/json/issues/739) -- Dumping Json to file as array [\#738](https://github.com/nlohmann/json/issues/738) -- nesting json objects [\#737](https://github.com/nlohmann/json/issues/737) -- where to find general help? [\#736](https://github.com/nlohmann/json/issues/736) -- Compilation Error on Clang 5.0 Upgrade [\#735](https://github.com/nlohmann/json/issues/735) -- Compilation error with std::map\ on vs 2015 [\#734](https://github.com/nlohmann/json/issues/734) -- Benchmarks for Binary formats [\#733](https://github.com/nlohmann/json/issues/733) -- Support \n symbols in json string. [\#731](https://github.com/nlohmann/json/issues/731) -- Project's name is too generic and hard to search for [\#730](https://github.com/nlohmann/json/issues/730) -- Visual Studio 2015 IntelliTrace problems [\#729](https://github.com/nlohmann/json/issues/729) -- How to erase nested objects inside other objects? [\#728](https://github.com/nlohmann/json/issues/728) -- Serialization for CBOR [\#726](https://github.com/nlohmann/json/issues/726) -- Using json Object as value in a map [\#725](https://github.com/nlohmann/json/issues/725) -- std::regex and nlohmann::json value [\#724](https://github.com/nlohmann/json/issues/724) -- Warnings when compiling with VisualStudio 2015 [\#723](https://github.com/nlohmann/json/issues/723) -- Has this lib the unicode \(wstring\) support? [\#722](https://github.com/nlohmann/json/issues/722) -- When will be 3.0 in master? [\#721](https://github.com/nlohmann/json/issues/721) -- Determine the type from error message. [\#720](https://github.com/nlohmann/json/issues/720) -- Compile-Error C2100 \(MS VS2015\) in line 887 json.hpp [\#719](https://github.com/nlohmann/json/issues/719) -- from\_json not working for boost::optional example [\#718](https://github.com/nlohmann/json/issues/718) -- about from\_json and to\_json function [\#717](https://github.com/nlohmann/json/issues/717) -- How to detect parse failure? [\#715](https://github.com/nlohmann/json/issues/715) -- Parse throw std::ios\_base::failure exception when failbit set to true [\#714](https://github.com/nlohmann/json/issues/714) -- Is there a way of format just making a pretty print without changing the key's orders ? [\#713](https://github.com/nlohmann/json/issues/713) -- Serialization of array of not same model items [\#712](https://github.com/nlohmann/json/issues/712) -- pointer to json parse vector [\#711](https://github.com/nlohmann/json/issues/711) -- Gtest SEH Exception [\#709](https://github.com/nlohmann/json/issues/709) -- broken from\_json implementation for pair and tuple [\#707](https://github.com/nlohmann/json/issues/707) -- Unevaluated lambda in assert breaks gcc 7 build [\#705](https://github.com/nlohmann/json/issues/705) -- Issues when adding values to firebase database [\#704](https://github.com/nlohmann/json/issues/704) -- Floating point equality - revisited [\#703](https://github.com/nlohmann/json/issues/703) -- Conversion from valarray\ to json fails to build [\#702](https://github.com/nlohmann/json/issues/702) -- internal compiler error \(gcc7\) [\#701](https://github.com/nlohmann/json/issues/701) -- One build system to rule them all [\#698](https://github.com/nlohmann/json/issues/698) -- Generated nlohmann\_jsonConfig.cmake does not set JSON\_INCLUDE\_DIR [\#695](https://github.com/nlohmann/json/issues/695) -- support the Chinese language in json string [\#694](https://github.com/nlohmann/json/issues/694) -- NaN problem within develop branch [\#693](https://github.com/nlohmann/json/issues/693) -- Please post example of specialization for boost::filesystem [\#692](https://github.com/nlohmann/json/issues/692) -- Impossible to do an array of composite objects [\#691](https://github.com/nlohmann/json/issues/691) -- How to save json to file? [\#690](https://github.com/nlohmann/json/issues/690) -- my simple json parser [\#689](https://github.com/nlohmann/json/issues/689) -- problem with new struct parsing syntax [\#688](https://github.com/nlohmann/json/issues/688) -- Parse error while parse the json string contains UTF 8 encoded document bytes string [\#684](https://github.com/nlohmann/json/issues/684) -- \[question\] how to get a string value by pointer [\#683](https://github.com/nlohmann/json/issues/683) -- create json object from string variable [\#681](https://github.com/nlohmann/json/issues/681) -- adl\_serializer and CRTP [\#680](https://github.com/nlohmann/json/issues/680) -- Is there a way to control the precision of serialized floating point numbers? [\#677](https://github.com/nlohmann/json/issues/677) -- Is there a way to get the path of a value? [\#676](https://github.com/nlohmann/json/issues/676) -- Could the parser locate errors to line? [\#675](https://github.com/nlohmann/json/issues/675) -- There is performance inefficiency found by coverity tool json2.1.1/include/nlohmann/json.hpp [\#673](https://github.com/nlohmann/json/issues/673) -- include problem, when cmake on osx [\#672](https://github.com/nlohmann/json/issues/672) -- Operator= ambiguous in C++1z and GCC 7.1.1 [\#670](https://github.com/nlohmann/json/issues/670) -- should't the cmake install target be to nlohman/json.hpp [\#668](https://github.com/nlohmann/json/issues/668) -- deserialise from `std::vector` [\#667](https://github.com/nlohmann/json/issues/667) -- How to iterate? [\#665](https://github.com/nlohmann/json/issues/665) -- could this json lib work on windows? [\#664](https://github.com/nlohmann/json/issues/664) -- How does from\_json work? [\#662](https://github.com/nlohmann/json/issues/662) -- insert\(or merge\) object should replace same key , not ignore [\#661](https://github.com/nlohmann/json/issues/661) -- Parse method doesn't handle newlines. [\#659](https://github.com/nlohmann/json/issues/659) -- Compilation "note" on GCC 6 ARM [\#658](https://github.com/nlohmann/json/issues/658) -- Adding additional push\_back/operator+= rvalue overloads for JSON object [\#657](https://github.com/nlohmann/json/issues/657) -- dump's parameter "ensure\_ascii" creates too long sequences [\#656](https://github.com/nlohmann/json/issues/656) -- Question: parsing `void *` [\#655](https://github.com/nlohmann/json/issues/655) -- how should I check a string is valid JSON string ? [\#653](https://github.com/nlohmann/json/issues/653) -- Question: thread safety of read only accesses [\#651](https://github.com/nlohmann/json/issues/651) -- Eclipse: Method 'size' could not be resolved [\#649](https://github.com/nlohmann/json/issues/649) -- Update/Add object fields [\#648](https://github.com/nlohmann/json/issues/648) -- No exception raised for Out Of Range input of numbers [\#647](https://github.com/nlohmann/json/issues/647) -- Package Name [\#646](https://github.com/nlohmann/json/issues/646) -- What is the meaning of operator\[\]\(T\* key\) [\#645](https://github.com/nlohmann/json/issues/645) -- Which is the correct way to json objects as parameters to functions? [\#644](https://github.com/nlohmann/json/issues/644) -- Method to get string representations of values [\#642](https://github.com/nlohmann/json/issues/642) -- CBOR serialization of a given JSON value does not serialize [\#641](https://github.com/nlohmann/json/issues/641) -- Are we forced to use "-fexceptions" flag in android ndk project [\#640](https://github.com/nlohmann/json/issues/640) -- Comparison of objects containing floats [\#639](https://github.com/nlohmann/json/issues/639) -- 'localeconv' is not supported by NDK for SDK \<=20 [\#638](https://github.com/nlohmann/json/issues/638) -- \[Question\] cLion integration [\#637](https://github.com/nlohmann/json/issues/637) -- How to construct an iteratable usage in nlohmann json? [\#636](https://github.com/nlohmann/json/issues/636) -- \[Question\] copy assign json-container to vector [\#635](https://github.com/nlohmann/json/issues/635) -- Get size without .dump\(\) [\#634](https://github.com/nlohmann/json/issues/634) -- Segmentation fault when parsing invalid json file [\#633](https://github.com/nlohmann/json/issues/633) -- How to serialize from json to vector\? [\#632](https://github.com/nlohmann/json/issues/632) -- no member named 'thousands\_sep' in 'lconv' [\#631](https://github.com/nlohmann/json/issues/631) -- \[Question\] Any fork for \(the unsupported\) Visual Studio 2012 version? [\#628](https://github.com/nlohmann/json/issues/628) -- Dependency injection in serializer [\#627](https://github.com/nlohmann/json/issues/627) -- from\_json for std::array [\#625](https://github.com/nlohmann/json/issues/625) -- Discussion: How to structure the parsing function families [\#623](https://github.com/nlohmann/json/issues/623) -- Question: How to erase subtree [\#622](https://github.com/nlohmann/json/issues/622) -- Insertion into nested json field [\#621](https://github.com/nlohmann/json/issues/621) -- Question: return static json object from function [\#618](https://github.com/nlohmann/json/issues/618) -- icc16 error [\#617](https://github.com/nlohmann/json/issues/617) -- \[-Wdeprecated-declarations\] in row `j >> ss;` in file `json.hpp:7405:26` and FAILED unit tests with MinGWx64! [\#616](https://github.com/nlohmann/json/issues/616) -- to\_json for pairs, tuples [\#614](https://github.com/nlohmann/json/issues/614) -- Using uninitialized memory 'buf' in line 11173 v2.1.1? [\#613](https://github.com/nlohmann/json/issues/613) -- How to parse multiple same Keys of JSON and save them? [\#612](https://github.com/nlohmann/json/issues/612) -- "Multiple declarations" error when using types defined with `typedef` [\#611](https://github.com/nlohmann/json/issues/611) -- 2.1.1+ breaks compilation of shared\_ptr\ == 0 [\#610](https://github.com/nlohmann/json/issues/610) -- a bug of inheritance ? [\#608](https://github.com/nlohmann/json/issues/608) -- std::map key conversion with to\_json [\#607](https://github.com/nlohmann/json/issues/607) -- json.hpp:6384:62: error: wrong number of template arguments \(1, should be 2\) [\#606](https://github.com/nlohmann/json/issues/606) -- Incremental parsing: Where's the push version? [\#605](https://github.com/nlohmann/json/issues/605) -- Is there a way to validate the structure of a json object ? [\#604](https://github.com/nlohmann/json/issues/604) -- \[Question\] Issue when using Appveyor when compiling library [\#603](https://github.com/nlohmann/json/issues/603) -- BOM not skipped when using json:parse\(iterator\) [\#602](https://github.com/nlohmann/json/issues/602) -- Use of the binary type in CBOR and Message Pack [\#601](https://github.com/nlohmann/json/issues/601) -- Newbie issue: how does one convert a map in Json back to std::map? [\#600](https://github.com/nlohmann/json/issues/600) -- Plugin system [\#599](https://github.com/nlohmann/json/issues/599) -- Using custom types for scalars? [\#596](https://github.com/nlohmann/json/issues/596) -- Issues with the arithmetic in iterator and reverse iterator [\#593](https://github.com/nlohmann/json/issues/593) -- not enough examples [\#592](https://github.com/nlohmann/json/issues/592) -- in-class initialization for type 'const T' is not yet implemented [\#591](https://github.com/nlohmann/json/issues/591) -- compiling with gcc 7 -\> error on bool operator \< [\#590](https://github.com/nlohmann/json/issues/590) -- Parsing from stream leads to an array [\#589](https://github.com/nlohmann/json/issues/589) -- Buggy support for binary string data [\#587](https://github.com/nlohmann/json/issues/587) -- C++17's ambiguous conversion [\#586](https://github.com/nlohmann/json/issues/586) -- How does the messagepack encoding/decoding compare to msgpack-cpp in terms of performance? [\#585](https://github.com/nlohmann/json/issues/585) -- is it possible to check existence of a value deep in hierarchy? [\#584](https://github.com/nlohmann/json/issues/584) -- loading from a stream and exceptions [\#582](https://github.com/nlohmann/json/issues/582) -- Visual Studio seems not to have all min\(\) function versions [\#581](https://github.com/nlohmann/json/issues/581) -- Supporting of the json schema [\#580](https://github.com/nlohmann/json/issues/580) -- Stack-overflow \(OSS-Fuzz 1444\) [\#577](https://github.com/nlohmann/json/issues/577) -- Heap-buffer-overflow \(OSS-Fuzz 1400\) [\#575](https://github.com/nlohmann/json/issues/575) -- JSON escape quotes [\#574](https://github.com/nlohmann/json/issues/574) -- error: static\_assert failed [\#573](https://github.com/nlohmann/json/issues/573) -- Storing floats, and round trip serialisation/deserialisation diffs [\#572](https://github.com/nlohmann/json/issues/572) -- JSON.getLong produces inconsistent results [\#571](https://github.com/nlohmann/json/issues/571) -- Request: Object.at\(\) with default return value [\#570](https://github.com/nlohmann/json/issues/570) -- Internal structure gets corrupted while parsing [\#569](https://github.com/nlohmann/json/issues/569) -- create template \ basic\_json from\_cbor\(Iter begin, Iter end\) [\#568](https://github.com/nlohmann/json/issues/568) -- Conan.io [\#566](https://github.com/nlohmann/json/issues/566) -- contradictory documentation regarding json::find [\#565](https://github.com/nlohmann/json/issues/565) -- Unexpected '\"' in middle of array [\#564](https://github.com/nlohmann/json/issues/564) -- Support parse std::pair to Json object [\#563](https://github.com/nlohmann/json/issues/563) -- json and Microsoft Visual c++ Compiler Nov 2012 CTP [\#562](https://github.com/nlohmann/json/issues/562) -- from\_json declaration order and exceptions [\#561](https://github.com/nlohmann/json/issues/561) -- Tip: Don't upgrade to VS2017 if using json initializer list constructs [\#559](https://github.com/nlohmann/json/issues/559) -- parse error - unexpected end of input [\#558](https://github.com/nlohmann/json/issues/558) -- Cant modify existing numbers inside a json object [\#557](https://github.com/nlohmann/json/issues/557) -- Better support for SAX style serialize and deserialize in new version? [\#554](https://github.com/nlohmann/json/issues/554) -- Cannot convert from json array to std::array [\#553](https://github.com/nlohmann/json/issues/553) -- Do not define an unnamed namespace in a header file \(DCL59-CPP\) [\#552](https://github.com/nlohmann/json/issues/552) -- Parse error on known good json file [\#551](https://github.com/nlohmann/json/issues/551) -- Warning on Intel compiler \(icc 17\) [\#550](https://github.com/nlohmann/json/issues/550) -- multiple versions of 'vsnprintf' [\#549](https://github.com/nlohmann/json/issues/549) -- illegal indirection [\#548](https://github.com/nlohmann/json/issues/548) -- Ambiguous compare operators with clang-5.0 [\#547](https://github.com/nlohmann/json/issues/547) -- Using tsl::ordered\_map [\#546](https://github.com/nlohmann/json/issues/546) -- Compiler support errors are inconvenient [\#544](https://github.com/nlohmann/json/issues/544) -- Duplicate symbols error happens while to\_json/from\_json method implemented inside entity definition header file [\#542](https://github.com/nlohmann/json/issues/542) -- consider adding a bool json::is\_valid\(std::string const&\) non-member function [\#541](https://github.com/nlohmann/json/issues/541) -- Help request [\#539](https://github.com/nlohmann/json/issues/539) -- How to deal with missing keys in `from_json`? [\#538](https://github.com/nlohmann/json/issues/538) -- recursive from\_msgpack implementation will stack overflow [\#537](https://github.com/nlohmann/json/issues/537) -- Exception objects must be nothrow copy constructible \(ERR60-CPP\) [\#531](https://github.com/nlohmann/json/issues/531) -- Support for multiple root elements [\#529](https://github.com/nlohmann/json/issues/529) -- Port has\_shape from dropbox/json11 [\#528](https://github.com/nlohmann/json/issues/528) -- dump\_float: truncation from ptrdiff\_t to long [\#527](https://github.com/nlohmann/json/issues/527) -- Make exception base class visible in basic\_json [\#525](https://github.com/nlohmann/json/issues/525) -- msgpack unit test failures on ppc64 arch [\#524](https://github.com/nlohmann/json/issues/524) -- How about split the implementation out, and only leave the interface? [\#523](https://github.com/nlohmann/json/issues/523) -- VC++2017 not enough actual parameters for macro 'max' [\#522](https://github.com/nlohmann/json/issues/522) -- crash on empty ifstream [\#521](https://github.com/nlohmann/json/issues/521) -- Suggestion: Support tabs for indentation when serializing to stream. [\#520](https://github.com/nlohmann/json/issues/520) -- Abrt in get\_number \(OSS-Fuzz 885\) [\#519](https://github.com/nlohmann/json/issues/519) -- Abrt on unknown address \(OSS-Fuzz 884\) [\#518](https://github.com/nlohmann/json/issues/518) -- Stack-overflow \(OSS-Fuzz 869\) [\#517](https://github.com/nlohmann/json/issues/517) -- Assertion error \(OSS-Fuzz 868\) [\#516](https://github.com/nlohmann/json/issues/516) -- NaN to json and back [\#515](https://github.com/nlohmann/json/issues/515) -- Comparison of NaN [\#514](https://github.com/nlohmann/json/issues/514) -- why it's not possible to serialize c++11 enums directly [\#513](https://github.com/nlohmann/json/issues/513) -- clang compile error: use of overloaded operator '\<=' is ambiguous with \(nlohmann::json{{"a", 5}}\)\["a"\] \<= 10 [\#512](https://github.com/nlohmann/json/issues/512) -- Why not also look inside the type for \(static\) to\_json and from\_json funtions? [\#511](https://github.com/nlohmann/json/issues/511) -- Parser issues [\#509](https://github.com/nlohmann/json/issues/509) -- I may not understand [\#507](https://github.com/nlohmann/json/issues/507) -- VS2017 min / max problem for 2.1.1 [\#506](https://github.com/nlohmann/json/issues/506) -- CBOR/MessagePack is not read until the end [\#505](https://github.com/nlohmann/json/issues/505) -- Assertion error \(OSS-Fuzz 856\) [\#504](https://github.com/nlohmann/json/issues/504) -- Return position in parse error exceptions [\#503](https://github.com/nlohmann/json/issues/503) -- conversion from/to C array is not supported [\#502](https://github.com/nlohmann/json/issues/502) -- error C2338: could not find to\_json\(\) method in T's namespace [\#501](https://github.com/nlohmann/json/issues/501) -- Test suite fails in en\_GB.UTF-8 [\#500](https://github.com/nlohmann/json/issues/500) -- cannot use operator\[\] with number [\#499](https://github.com/nlohmann/json/issues/499) -- consider using \_\_cpp\_exceptions and/or \_\_EXCEPTIONS to disable/enable exception support [\#498](https://github.com/nlohmann/json/issues/498) -- Stack-overflow \(OSS-Fuzz issue 814\) [\#497](https://github.com/nlohmann/json/issues/497) -- Using in Unreal Engine - handling custom types conversion [\#495](https://github.com/nlohmann/json/issues/495) -- Conversion from vector\ to json fails to build [\#494](https://github.com/nlohmann/json/issues/494) -- fill\_line\_buffer incorrectly tests m\_stream for eof but not fail or bad bits [\#493](https://github.com/nlohmann/json/issues/493) -- Compiling with \_GLIBCXX\_DEBUG yields iterator-comparison warnings during tests [\#492](https://github.com/nlohmann/json/issues/492) -- crapy interface [\#491](https://github.com/nlohmann/json/issues/491) -- Fix Visual Studo 2013 builds. [\#490](https://github.com/nlohmann/json/issues/490) -- Failed to compile with -D\_GLIBCXX\_PARALLEL [\#489](https://github.com/nlohmann/json/issues/489) -- Input several field with the same name [\#488](https://github.com/nlohmann/json/issues/488) -- read in .json file yields strange sizes [\#487](https://github.com/nlohmann/json/issues/487) -- json::value\_t can't be a map's key type in VC++ 2015 [\#486](https://github.com/nlohmann/json/issues/486) -- Using fifo\_map [\#485](https://github.com/nlohmann/json/issues/485) -- Cannot get float pointer for value stored as `0` [\#484](https://github.com/nlohmann/json/issues/484) -- byte string support [\#483](https://github.com/nlohmann/json/issues/483) -- https://github.com/nlohmann/json\#execute-unit-tests [\#481](https://github.com/nlohmann/json/issues/481) -- Remove deprecated constructor basic\_json\(std::istream&\) [\#480](https://github.com/nlohmann/json/issues/480) -- writing the binary json file? [\#479](https://github.com/nlohmann/json/issues/479) -- CBOR/MessagePack from uint8\_t \* and size [\#478](https://github.com/nlohmann/json/issues/478) -- Streaming binary representations [\#477](https://github.com/nlohmann/json/issues/477) -- Reuse memory in to\_cbor and to\_msgpack functions [\#476](https://github.com/nlohmann/json/issues/476) -- Error Using JSON Library with arrays C++ [\#475](https://github.com/nlohmann/json/issues/475) -- Moving forward to version 3.0.0 [\#474](https://github.com/nlohmann/json/issues/474) -- Inconsistent behavior in conversion to array type [\#473](https://github.com/nlohmann/json/issues/473) -- Create a \[key:member\_pointer\] map to ease parsing custom types [\#471](https://github.com/nlohmann/json/issues/471) -- MSVC 2015 update 2 [\#469](https://github.com/nlohmann/json/issues/469) -- VS2017 implicit to std::string conversion fix. [\#464](https://github.com/nlohmann/json/issues/464) -- How to make sure a string or string literal is a valid JSON? [\#458](https://github.com/nlohmann/json/issues/458) -- basic\_json templated on a "policy" class [\#456](https://github.com/nlohmann/json/issues/456) -- json::value\(const json\_pointer&, ValueType\) requires exceptions to return the default value. [\#440](https://github.com/nlohmann/json/issues/440) -- is it possible merge two json object [\#428](https://github.com/nlohmann/json/issues/428) -- Is it possible to turn this into a shared library? [\#420](https://github.com/nlohmann/json/issues/420) -- Further thoughts on performance improvements [\#418](https://github.com/nlohmann/json/issues/418) -- nan number stored as null [\#388](https://github.com/nlohmann/json/issues/388) -- Behavior of operator\>\> should more closely resemble that of built-in overloads. [\#367](https://github.com/nlohmann/json/issues/367) -- Request: range-based-for over a json-object to expose .first/.second [\#350](https://github.com/nlohmann/json/issues/350) -- feature wish: JSONPath [\#343](https://github.com/nlohmann/json/issues/343) -- UTF-8/Unicode escape and dump [\#330](https://github.com/nlohmann/json/issues/330) -- Serialized value not always can be parsed. [\#329](https://github.com/nlohmann/json/issues/329) -- Is there a way to forward declare nlohmann::json? [\#314](https://github.com/nlohmann/json/issues/314) -- Exception line [\#301](https://github.com/nlohmann/json/issues/301) -- Do not throw exception when default\_value's type does not match the actual type [\#278](https://github.com/nlohmann/json/issues/278) -- dump\(\) method doesn't work with a custom allocator [\#268](https://github.com/nlohmann/json/issues/268) -- Readme documentation enhancements [\#248](https://github.com/nlohmann/json/issues/248) -- Use user-defined exceptions [\#244](https://github.com/nlohmann/json/issues/244) -- Incorrect C++11 allocator model support [\#161](https://github.com/nlohmann/json/issues/161) - -- :white\_check\_mark: re-added tests for algorithms [\#879](https://github.com/nlohmann/json/pull/879) ([nlohmann](https://github.com/nlohmann)) -- Overworked library toward 3.0.0 release [\#875](https://github.com/nlohmann/json/pull/875) ([nlohmann](https://github.com/nlohmann)) -- :rotating\_light: remove C4996 warnings \#872 [\#873](https://github.com/nlohmann/json/pull/873) ([nlohmann](https://github.com/nlohmann)) -- :boom: throwing an exception in case dump encounters a non-UTF-8 string \#838 [\#870](https://github.com/nlohmann/json/pull/870) ([nlohmann](https://github.com/nlohmann)) -- :memo: fixing documentation \#867 [\#868](https://github.com/nlohmann/json/pull/868) ([nlohmann](https://github.com/nlohmann)) -- iter\_impl template conformance with C++17 [\#860](https://github.com/nlohmann/json/pull/860) ([bogemic](https://github.com/bogemic)) -- Std allocator conformance cpp17 [\#856](https://github.com/nlohmann/json/pull/856) ([bogemic](https://github.com/bogemic)) -- cmake: use BUILD\_INTERFACE/INSTALL\_INTERFACE [\#855](https://github.com/nlohmann/json/pull/855) ([theodelrieu](https://github.com/theodelrieu)) -- to/from\_json: add a MSVC-specific static\_assert to force a stacktrace [\#854](https://github.com/nlohmann/json/pull/854) ([theodelrieu](https://github.com/theodelrieu)) -- Add .natvis for MSVC debug view [\#844](https://github.com/nlohmann/json/pull/844) ([TinyTinni](https://github.com/TinyTinni)) -- Updated hunter package links [\#829](https://github.com/nlohmann/json/pull/829) ([jowr](https://github.com/jowr)) -- Typos README [\#811](https://github.com/nlohmann/json/pull/811) ([Itja](https://github.com/Itja)) -- add forwarding references to json\_ref constructor [\#807](https://github.com/nlohmann/json/pull/807) ([theodelrieu](https://github.com/theodelrieu)) -- Add transparent comparator and perfect forwarding support to find\(\) and count\(\) [\#795](https://github.com/nlohmann/json/pull/795) ([jseward](https://github.com/jseward)) -- Error : 'identifier "size\_t" is undefined' in linux [\#793](https://github.com/nlohmann/json/pull/793) ([sonulohani](https://github.com/sonulohani)) -- Fix Visual Studio 2017 warnings [\#788](https://github.com/nlohmann/json/pull/788) ([jseward](https://github.com/jseward)) -- Fix warning C4706 on Visual Studio 2017 [\#785](https://github.com/nlohmann/json/pull/785) ([jseward](https://github.com/jseward)) -- Set GENERATE\_TAGFILE in Doxyfile [\#783](https://github.com/nlohmann/json/pull/783) ([eld00d](https://github.com/eld00d)) -- using more CMake [\#765](https://github.com/nlohmann/json/pull/765) ([nlohmann](https://github.com/nlohmann)) -- Simplified istream handing \#367 [\#764](https://github.com/nlohmann/json/pull/764) ([pjkundert](https://github.com/pjkundert)) -- Add info for the vcpkg package. [\#753](https://github.com/nlohmann/json/pull/753) ([gregmarr](https://github.com/gregmarr)) -- fix from\_json implementation for pair/tuple [\#708](https://github.com/nlohmann/json/pull/708) ([theodelrieu](https://github.com/theodelrieu)) -- Update json.hpp [\#686](https://github.com/nlohmann/json/pull/686) ([GoWebProd](https://github.com/GoWebProd)) -- Remove duplicate word [\#685](https://github.com/nlohmann/json/pull/685) ([daixtrose](https://github.com/daixtrose)) -- To fix compilation issue for intel OSX compiler [\#682](https://github.com/nlohmann/json/pull/682) ([kbthomp1](https://github.com/kbthomp1)) -- Digraph warning [\#679](https://github.com/nlohmann/json/pull/679) ([traits](https://github.com/traits)) -- massage -\> message [\#678](https://github.com/nlohmann/json/pull/678) ([DmitryKuk](https://github.com/DmitryKuk)) -- Fix "not constraint" grammar in docs [\#674](https://github.com/nlohmann/json/pull/674) ([wincent](https://github.com/wincent)) -- Add documentation for integration with CMake and hunter [\#671](https://github.com/nlohmann/json/pull/671) ([dan-42](https://github.com/dan-42)) -- REFACTOR: rewrite CMakeLists.txt for better inlcude and reuse [\#669](https://github.com/nlohmann/json/pull/669) ([dan-42](https://github.com/dan-42)) -- enable\_testing only if the JSON\_BuildTests is ON [\#666](https://github.com/nlohmann/json/pull/666) ([effolkronium](https://github.com/effolkronium)) -- Support moving from rvalues in std::initializer\_list [\#663](https://github.com/nlohmann/json/pull/663) ([himikof](https://github.com/himikof)) -- add ensure\_ascii parameter to dump. \#330 [\#654](https://github.com/nlohmann/json/pull/654) ([ryanjmulder](https://github.com/ryanjmulder)) -- Rename BuildTests to JSON\_BuildTests [\#652](https://github.com/nlohmann/json/pull/652) ([olegendo](https://github.com/olegendo)) -- Don't include \, use std::make\_shared [\#650](https://github.com/nlohmann/json/pull/650) ([olegendo](https://github.com/olegendo)) -- Refacto/split basic json [\#643](https://github.com/nlohmann/json/pull/643) ([theodelrieu](https://github.com/theodelrieu)) -- fix typo in operator\_\_notequal example [\#630](https://github.com/nlohmann/json/pull/630) ([Chocobo1](https://github.com/Chocobo1)) -- Fix MSVC warning C4819 [\#629](https://github.com/nlohmann/json/pull/629) ([Chocobo1](https://github.com/Chocobo1)) -- \[BugFix\] Add parentheses around std::min [\#626](https://github.com/nlohmann/json/pull/626) ([koemeet](https://github.com/koemeet)) -- add pair/tuple conversions [\#624](https://github.com/nlohmann/json/pull/624) ([theodelrieu](https://github.com/theodelrieu)) -- remove std::pair support [\#615](https://github.com/nlohmann/json/pull/615) ([theodelrieu](https://github.com/theodelrieu)) -- Add pair support, fix CompatibleObject conversions \(fixes \#600\) [\#609](https://github.com/nlohmann/json/pull/609) ([theodelrieu](https://github.com/theodelrieu)) -- \#550 Fix iterator related compiling issues for Intel icc [\#598](https://github.com/nlohmann/json/pull/598) ([HenryRLee](https://github.com/HenryRLee)) -- Issue \#593 Fix the arithmetic operators in the iterator and reverse iterator [\#595](https://github.com/nlohmann/json/pull/595) ([HenryRLee](https://github.com/HenryRLee)) -- fix doxygen error of basic\_json::get\(\) [\#583](https://github.com/nlohmann/json/pull/583) ([zhaohuaxishi](https://github.com/zhaohuaxishi)) -- Fixing assignement for iterator wrapper second, and adding unit test [\#579](https://github.com/nlohmann/json/pull/579) ([Type1J](https://github.com/Type1J)) -- Adding first and second properties to iteration\_proxy\_internal [\#578](https://github.com/nlohmann/json/pull/578) ([Type1J](https://github.com/Type1J)) -- Adding support for Meson. [\#576](https://github.com/nlohmann/json/pull/576) ([Type1J](https://github.com/Type1J)) -- add enum class default conversions [\#545](https://github.com/nlohmann/json/pull/545) ([theodelrieu](https://github.com/theodelrieu)) -- Properly pop diagnostics [\#540](https://github.com/nlohmann/json/pull/540) ([tinloaf](https://github.com/tinloaf)) -- Add Visual Studio 17 image to appveyor build matrix [\#536](https://github.com/nlohmann/json/pull/536) ([vpetrigo](https://github.com/vpetrigo)) -- UTF8 encoding enhancement [\#534](https://github.com/nlohmann/json/pull/534) ([TedLyngmo](https://github.com/TedLyngmo)) -- Fix typo [\#530](https://github.com/nlohmann/json/pull/530) ([berkus](https://github.com/berkus)) -- Make exception base class visible in basic\_json [\#526](https://github.com/nlohmann/json/pull/526) ([ghost](https://github.com/ghost)) -- :art: Namespace `uint8_t` from the C++ stdlib [\#510](https://github.com/nlohmann/json/pull/510) ([alexweej](https://github.com/alexweej)) -- add to\_json method for C arrays [\#508](https://github.com/nlohmann/json/pull/508) ([theodelrieu](https://github.com/theodelrieu)) -- Fix -Weffc++ warnings \(GNU 6.3.1\) [\#496](https://github.com/nlohmann/json/pull/496) ([TedLyngmo](https://github.com/TedLyngmo)) - -## [v2.1.1](https://github.com/nlohmann/json/releases/tag/v2.1.1) (2017-02-25) - -[Full Changelog](https://github.com/nlohmann/json/compare/2.1.1...v2.1.1) - -## [2.1.1](https://github.com/nlohmann/json/releases/tag/2.1.1) (2017-02-25) - -[Full Changelog](https://github.com/nlohmann/json/compare/v2.1.0...2.1.1) - -- warning in the library [\#472](https://github.com/nlohmann/json/issues/472) -- How to create an array of Objects? [\#470](https://github.com/nlohmann/json/issues/470) -- \[Bug?\] Cannot get int pointer, but int64\_t works [\#468](https://github.com/nlohmann/json/issues/468) -- Illegal indirection [\#467](https://github.com/nlohmann/json/issues/467) -- in vs can't find linkageId [\#466](https://github.com/nlohmann/json/issues/466) -- Roundtrip error while parsing "1000000000000000010E5" [\#465](https://github.com/nlohmann/json/issues/465) -- C4996 error and warning with Visual Studio [\#463](https://github.com/nlohmann/json/issues/463) -- Support startIndex for from\_cbor/from\_msgpack [\#462](https://github.com/nlohmann/json/issues/462) -- question: monospace font used in feature slideshow? [\#460](https://github.com/nlohmann/json/issues/460) -- Object.keys\(\) [\#459](https://github.com/nlohmann/json/issues/459) -- Use “, “ as delimiter for json-objects. [\#457](https://github.com/nlohmann/json/issues/457) -- Enum -\> string during serialization and vice versa [\#455](https://github.com/nlohmann/json/issues/455) -- doubles are printed as integers [\#454](https://github.com/nlohmann/json/issues/454) -- Warnings with Visual Studio c++ \(VS2015 Update 3\) [\#453](https://github.com/nlohmann/json/issues/453) -- Heap-buffer-overflow \(OSS-Fuzz issue 585\) [\#452](https://github.com/nlohmann/json/issues/452) -- use of undeclared identifier 'UINT8\_MAX' [\#451](https://github.com/nlohmann/json/issues/451) -- Question on the lifetime managment of objects at the lower levels [\#449](https://github.com/nlohmann/json/issues/449) -- Json should not be constructible with 'json\*' [\#448](https://github.com/nlohmann/json/issues/448) -- Move value\_t to namespace scope [\#447](https://github.com/nlohmann/json/issues/447) -- Typo in README.md [\#446](https://github.com/nlohmann/json/issues/446) -- make check compilation is unneccesarily slow [\#445](https://github.com/nlohmann/json/issues/445) -- Problem in dump\(\) in json.h caused by ss.imbue [\#444](https://github.com/nlohmann/json/issues/444) -- I want to create Windows Application in Visual Studio 2015 c++, and i have a problem [\#443](https://github.com/nlohmann/json/issues/443) -- Implicit conversion issues [\#442](https://github.com/nlohmann/json/issues/442) -- Parsing of floats locale dependent [\#302](https://github.com/nlohmann/json/issues/302) - -- Speedup CI builds using cotire [\#461](https://github.com/nlohmann/json/pull/461) ([tusharpm](https://github.com/tusharpm)) -- TurpentineDistillery feature/locale independent str to num [\#450](https://github.com/nlohmann/json/pull/450) ([nlohmann](https://github.com/nlohmann)) -- README: adjust boost::optional example [\#439](https://github.com/nlohmann/json/pull/439) ([jaredgrubb](https://github.com/jaredgrubb)) -- fix \#414 - comparing to 0 literal [\#415](https://github.com/nlohmann/json/pull/415) ([stanmihai4](https://github.com/stanmihai4)) -- locale-independent num-to-str [\#378](https://github.com/nlohmann/json/pull/378) ([TurpentineDistillery](https://github.com/TurpentineDistillery)) - -## [v2.1.0](https://github.com/nlohmann/json/releases/tag/v2.1.0) (2017-01-28) - -[Full Changelog](https://github.com/nlohmann/json/compare/2.1.0...v2.1.0) - -## [2.1.0](https://github.com/nlohmann/json/releases/tag/2.1.0) (2017-01-28) - -[Full Changelog](https://github.com/nlohmann/json/compare/v2.0.10...2.1.0) - -- Parsing multiple JSON objects from a string or stream [\#438](https://github.com/nlohmann/json/issues/438) -- Use-of-uninitialized-value \(OSS-Fuzz issue 477\) [\#437](https://github.com/nlohmann/json/issues/437) -- add `reserve` function for array to reserve memory before adding json values into it [\#436](https://github.com/nlohmann/json/issues/436) -- Typo in examples page [\#434](https://github.com/nlohmann/json/issues/434) -- avoid malformed json [\#433](https://github.com/nlohmann/json/issues/433) -- How to add json objects to a map? [\#432](https://github.com/nlohmann/json/issues/432) -- create json instance from raw json \(unsigned char\*\) [\#431](https://github.com/nlohmann/json/issues/431) -- Getting std::invalid\_argument: stream error when following example [\#429](https://github.com/nlohmann/json/issues/429) -- Forward declare-only header? [\#427](https://github.com/nlohmann/json/issues/427) -- Implicit conversion from array to object [\#425](https://github.com/nlohmann/json/issues/425) -- error C4996: 'strerror' when reading file [\#422](https://github.com/nlohmann/json/issues/422) -- Get an error - JSON pointer must be empty or begin with '/' [\#421](https://github.com/nlohmann/json/issues/421) -- size parameter for parse\(\) [\#419](https://github.com/nlohmann/json/issues/419) -- json.hpp forcibly defines GCC\_VERSION [\#417](https://github.com/nlohmann/json/issues/417) -- Use-of-uninitialized-value \(OSS-Fuzz issue 377\) [\#416](https://github.com/nlohmann/json/issues/416) -- comparing to 0 literal [\#414](https://github.com/nlohmann/json/issues/414) -- Single char converted to ASCII code instead of string [\#413](https://github.com/nlohmann/json/issues/413) -- How to know if a string was parsed as utf-8? [\#406](https://github.com/nlohmann/json/issues/406) -- Overloaded += to add objects to an array makes no sense? [\#404](https://github.com/nlohmann/json/issues/404) -- Finding a value in an array [\#399](https://github.com/nlohmann/json/issues/399) -- add release information in static function [\#397](https://github.com/nlohmann/json/issues/397) -- Optimize memory usage of json objects in combination with binary serialization [\#373](https://github.com/nlohmann/json/issues/373) -- Conversion operators not considered [\#369](https://github.com/nlohmann/json/issues/369) -- Append ".0" to serialized floating\_point values that are digits-only. [\#362](https://github.com/nlohmann/json/issues/362) -- Add a customization point for user-defined types [\#328](https://github.com/nlohmann/json/issues/328) -- Conformance report for reference [\#307](https://github.com/nlohmann/json/issues/307) -- Document the best way to serialize/deserialize user defined types to json [\#298](https://github.com/nlohmann/json/issues/298) -- Add StringView template typename to basic\_json [\#297](https://github.com/nlohmann/json/issues/297) -- \[Improvement\] Add option to remove exceptions [\#296](https://github.com/nlohmann/json/issues/296) -- Performance in miloyip/nativejson-benchmark [\#202](https://github.com/nlohmann/json/issues/202) - -- conversion from/to user-defined types [\#435](https://github.com/nlohmann/json/pull/435) ([nlohmann](https://github.com/nlohmann)) -- Fix documentation error [\#430](https://github.com/nlohmann/json/pull/430) ([vjon](https://github.com/vjon)) - -## [v2.0.10](https://github.com/nlohmann/json/releases/tag/v2.0.10) (2017-01-02) - -[Full Changelog](https://github.com/nlohmann/json/compare/2.0.10...v2.0.10) - -## [2.0.10](https://github.com/nlohmann/json/releases/tag/2.0.10) (2017-01-02) - -[Full Changelog](https://github.com/nlohmann/json/compare/v2.0.9...2.0.10) - -- Heap-buffer-overflow \(OSS-Fuzz issue 367\) [\#412](https://github.com/nlohmann/json/issues/412) -- Heap-buffer-overflow \(OSS-Fuzz issue 366\) [\#411](https://github.com/nlohmann/json/issues/411) -- Use-of-uninitialized-value \(OSS-Fuzz issue 347\) [\#409](https://github.com/nlohmann/json/issues/409) -- Heap-buffer-overflow \(OSS-Fuzz issue 344\) [\#408](https://github.com/nlohmann/json/issues/408) -- Heap-buffer-overflow \(OSS-Fuzz issue 343\) [\#407](https://github.com/nlohmann/json/issues/407) -- Heap-buffer-overflow \(OSS-Fuzz issue 342\) [\#405](https://github.com/nlohmann/json/issues/405) -- strerror throwing error in compiler VS2015 [\#403](https://github.com/nlohmann/json/issues/403) -- json::parse of std::string being underlined by Visual Studio [\#402](https://github.com/nlohmann/json/issues/402) -- Explicitly getting string without .dump\(\) [\#401](https://github.com/nlohmann/json/issues/401) -- Possible to speed up json::parse? [\#398](https://github.com/nlohmann/json/issues/398) -- the alphabetic order in the code influence console\_output. [\#396](https://github.com/nlohmann/json/issues/396) -- Execute tests with clang sanitizers [\#394](https://github.com/nlohmann/json/issues/394) -- Check if library can be used with ETL [\#361](https://github.com/nlohmann/json/issues/361) - -- Feature/clang sanitize [\#410](https://github.com/nlohmann/json/pull/410) ([Daniel599](https://github.com/Daniel599)) -- Add Doozer build badge [\#400](https://github.com/nlohmann/json/pull/400) ([andoma](https://github.com/andoma)) - -## [v2.0.9](https://github.com/nlohmann/json/releases/tag/v2.0.9) (2016-12-16) - -[Full Changelog](https://github.com/nlohmann/json/compare/2.0.9...v2.0.9) - -## [2.0.9](https://github.com/nlohmann/json/releases/tag/2.0.9) (2016-12-16) - -[Full Changelog](https://github.com/nlohmann/json/compare/v2.0.8...2.0.9) - -- \#pragma GCC diagnostic ignored "-Wdocumentation" [\#393](https://github.com/nlohmann/json/issues/393) -- How to parse this json file and write separate sub object as json files? [\#392](https://github.com/nlohmann/json/issues/392) -- Integer-overflow \(OSS-Fuzz issue 267\) [\#389](https://github.com/nlohmann/json/issues/389) -- Implement indefinite-length types from RFC 7049 [\#387](https://github.com/nlohmann/json/issues/387) -- template parameter "T" is not used in declaring the parameter types of function template [\#386](https://github.com/nlohmann/json/issues/386) -- Serializing json instances containing already serialized string values without escaping [\#385](https://github.com/nlohmann/json/issues/385) -- Add test cases from RFC 7049 [\#384](https://github.com/nlohmann/json/issues/384) -- Add a table of contents to the README file [\#383](https://github.com/nlohmann/json/issues/383) -- Update FAQ section in the guidelines for contributing [\#382](https://github.com/nlohmann/json/issues/382) -- Allow for forward declaring nlohmann::json [\#381](https://github.com/nlohmann/json/issues/381) -- Bug in overflow detection when parsing integers [\#380](https://github.com/nlohmann/json/issues/380) -- A unique name to mention the library? [\#377](https://github.com/nlohmann/json/issues/377) -- Non-unique keys in objects. [\#375](https://github.com/nlohmann/json/issues/375) -- Request: binary serialization/deserialization [\#358](https://github.com/nlohmann/json/issues/358) - -- Replace class iterator and const\_iterator by using a single template class to reduce code. [\#395](https://github.com/nlohmann/json/pull/395) ([Bosswestfalen](https://github.com/Bosswestfalen)) -- Clang: quiet a warning [\#391](https://github.com/nlohmann/json/pull/391) ([jaredgrubb](https://github.com/jaredgrubb)) -- Fix issue \#380: Signed integer overflow check [\#390](https://github.com/nlohmann/json/pull/390) ([qwename](https://github.com/qwename)) - -## [v2.0.8](https://github.com/nlohmann/json/releases/tag/v2.0.8) (2016-12-02) - -[Full Changelog](https://github.com/nlohmann/json/compare/2.0.8...v2.0.8) - -## [2.0.8](https://github.com/nlohmann/json/releases/tag/2.0.8) (2016-12-02) - -[Full Changelog](https://github.com/nlohmann/json/compare/v2.0.7...2.0.8) - -- Reading from file [\#374](https://github.com/nlohmann/json/issues/374) -- Compiler warnings? [\#372](https://github.com/nlohmann/json/issues/372) -- docs: how to release a json object in memory? [\#371](https://github.com/nlohmann/json/issues/371) -- crash in dump [\#370](https://github.com/nlohmann/json/issues/370) -- Coverity issue \(FORWARD\_NULL\) in lexer\(std::istream& s\) [\#368](https://github.com/nlohmann/json/issues/368) -- json::parse on failed stream gets stuck [\#366](https://github.com/nlohmann/json/issues/366) -- Performance improvements [\#365](https://github.com/nlohmann/json/issues/365) -- 'to\_string' is not a member of 'std' [\#364](https://github.com/nlohmann/json/issues/364) -- Crash in dump\(\) from a static object [\#359](https://github.com/nlohmann/json/issues/359) -- json::parse\(...\) vs json j; j.parse\(...\) [\#357](https://github.com/nlohmann/json/issues/357) -- Hi, is there any method to dump json to string with the insert order rather than alphabets [\#356](https://github.com/nlohmann/json/issues/356) -- Provide an example of reading from an json with only a key that has an array of strings. [\#354](https://github.com/nlohmann/json/issues/354) -- Request: access with default value. [\#353](https://github.com/nlohmann/json/issues/353) -- {} and \[\] causes parser error. [\#352](https://github.com/nlohmann/json/issues/352) -- Reading a JSON file into a JSON object [\#351](https://github.com/nlohmann/json/issues/351) -- Request: 'emplace\_back' [\#349](https://github.com/nlohmann/json/issues/349) -- Is it possible to stream data through the json parser without storing everything in memory? [\#347](https://github.com/nlohmann/json/issues/347) -- pure virtual conversion operator [\#346](https://github.com/nlohmann/json/issues/346) -- Floating point precision lost [\#345](https://github.com/nlohmann/json/issues/345) -- unit-conversions SIGSEGV on armv7hl [\#303](https://github.com/nlohmann/json/issues/303) -- Coverity scan fails [\#299](https://github.com/nlohmann/json/issues/299) -- Using QString as string type [\#274](https://github.com/nlohmann/json/issues/274) - -## [v2.0.7](https://github.com/nlohmann/json/releases/tag/v2.0.7) (2016-11-02) - -[Full Changelog](https://github.com/nlohmann/json/compare/v2.0.6...v2.0.7) - -- JSON5 [\#348](https://github.com/nlohmann/json/issues/348) -- Check "Parsing JSON is a Minefield" [\#344](https://github.com/nlohmann/json/issues/344) -- Allow hex numbers [\#342](https://github.com/nlohmann/json/issues/342) -- Convert strings to numbers [\#341](https://github.com/nlohmann/json/issues/341) -- ""-operators ignore the length parameter [\#340](https://github.com/nlohmann/json/issues/340) -- JSON into std::tuple [\#339](https://github.com/nlohmann/json/issues/339) -- JSON into vector [\#335](https://github.com/nlohmann/json/issues/335) -- Installing with Homebrew on Mac Errors \(El Capitan\) [\#331](https://github.com/nlohmann/json/issues/331) -- g++ make check results in error [\#312](https://github.com/nlohmann/json/issues/312) -- Cannot convert from 'json' to 'char' [\#276](https://github.com/nlohmann/json/issues/276) -- Please add a Pretty-Print option for arrays to stay always in one line [\#229](https://github.com/nlohmann/json/issues/229) -- Conversion to STL map\\> gives error [\#220](https://github.com/nlohmann/json/issues/220) -- std::unorderd\_map cannot be used as ObjectType [\#164](https://github.com/nlohmann/json/issues/164) - -- fix minor grammar/style issue in README.md [\#336](https://github.com/nlohmann/json/pull/336) ([seeekr](https://github.com/seeekr)) - -## [v2.0.6](https://github.com/nlohmann/json/releases/tag/v2.0.6) (2016-10-15) - -[Full Changelog](https://github.com/nlohmann/json/compare/v2.0.5...v2.0.6) - -- How to handle json files? [\#333](https://github.com/nlohmann/json/issues/333) -- This file requires compiler and library support .... [\#332](https://github.com/nlohmann/json/issues/332) -- Segmentation fault on saving json to file [\#326](https://github.com/nlohmann/json/issues/326) -- parse error - unexpected \ with 2.0.5 [\#325](https://github.com/nlohmann/json/issues/325) -- Add nested object capability to pointers [\#323](https://github.com/nlohmann/json/issues/323) -- Fix usage examples' comments for std::multiset [\#322](https://github.com/nlohmann/json/issues/322) -- json\_unit runs forever when executed in build directory [\#319](https://github.com/nlohmann/json/issues/319) -- Visual studio 2015 update3 true != TRUE [\#317](https://github.com/nlohmann/json/issues/317) -- releasing single header file in compressed format [\#316](https://github.com/nlohmann/json/issues/316) -- json object from std::ifstream [\#315](https://github.com/nlohmann/json/issues/315) - -- make has\_mapped\_type struct friendly [\#324](https://github.com/nlohmann/json/pull/324) ([vpetrigo](https://github.com/vpetrigo)) -- Fix usage examples' comments for std::multiset [\#321](https://github.com/nlohmann/json/pull/321) ([vasild](https://github.com/vasild)) -- Include dir relocation [\#318](https://github.com/nlohmann/json/pull/318) ([ChristophJud](https://github.com/ChristophJud)) -- trivial documentation fix [\#313](https://github.com/nlohmann/json/pull/313) ([5tefan](https://github.com/5tefan)) - -## [v2.0.5](https://github.com/nlohmann/json/releases/tag/v2.0.5) (2016-09-14) - -[Full Changelog](https://github.com/nlohmann/json/compare/v2.0.4...v2.0.5) - -- \[feature request\]: schema validator and comments [\#311](https://github.com/nlohmann/json/issues/311) -- make json\_benchmarks no longer working in 2.0.4 [\#310](https://github.com/nlohmann/json/issues/310) -- Segmentation fault \(core dumped\) [\#309](https://github.com/nlohmann/json/issues/309) -- No matching member function for call to 'get\_impl' [\#308](https://github.com/nlohmann/json/issues/308) - -## [v2.0.4](https://github.com/nlohmann/json/releases/tag/v2.0.4) (2016-09-11) - -[Full Changelog](https://github.com/nlohmann/json/compare/v2.0.3...v2.0.4) - -- Parsing fails without space at end of file [\#306](https://github.com/nlohmann/json/issues/306) -- json schema validator [\#305](https://github.com/nlohmann/json/issues/305) -- Unused variable warning [\#304](https://github.com/nlohmann/json/issues/304) - -## [v2.0.3](https://github.com/nlohmann/json/releases/tag/v2.0.3) (2016-08-31) - -[Full Changelog](https://github.com/nlohmann/json/compare/v2.0.2...v2.0.3) - -- warning C4706: assignment within conditional expression [\#295](https://github.com/nlohmann/json/issues/295) -- Q: Is it possible to build json tree from already UTF8 encoded values? [\#293](https://github.com/nlohmann/json/issues/293) -- Equality operator results in array when assigned object [\#292](https://github.com/nlohmann/json/issues/292) -- Support for integers not from the range \[-\(2\*\*53\)+1, \(2\*\*53\)-1\] in parser [\#291](https://github.com/nlohmann/json/issues/291) -- Support for iterator-range parsing [\#290](https://github.com/nlohmann/json/issues/290) -- Horribly inconsistent behavior between const/non-const reference in operator \[\] \(\) [\#289](https://github.com/nlohmann/json/issues/289) -- Silently get numbers into smaller types [\#288](https://github.com/nlohmann/json/issues/288) -- Incorrect parsing of large int64\_t numbers [\#287](https://github.com/nlohmann/json/issues/287) -- \[question\]: macro to disable floating point support [\#284](https://github.com/nlohmann/json/issues/284) - -- unit-constructor1.cpp: Fix floating point truncation warning [\#300](https://github.com/nlohmann/json/pull/300) ([t-b](https://github.com/t-b)) - -## [v2.0.2](https://github.com/nlohmann/json/releases/tag/v2.0.2) (2016-07-31) - -[Full Changelog](https://github.com/nlohmann/json/compare/v2.0.1...v2.0.2) - -- can function dump\(\) return string in the order I push in the json object ? [\#286](https://github.com/nlohmann/json/issues/286) -- Error on the Mac: Undefined symbols for architecture x86\_64 [\#285](https://github.com/nlohmann/json/issues/285) -- value\(\) does not work with \_json\_pointer types [\#283](https://github.com/nlohmann/json/issues/283) -- Build error for std::int64 [\#282](https://github.com/nlohmann/json/issues/282) -- strings can't be accessed after dump\(\)-\>parse\(\) - type is lost [\#281](https://github.com/nlohmann/json/issues/281) -- Easy serialization of classes [\#280](https://github.com/nlohmann/json/issues/280) -- recursive data structures [\#277](https://github.com/nlohmann/json/issues/277) -- hexify\(\) function emits conversion warning [\#270](https://github.com/nlohmann/json/issues/270) - -- let the makefile choose the correct sed [\#279](https://github.com/nlohmann/json/pull/279) ([murinicanor](https://github.com/murinicanor)) -- Update hexify to use array lookup instead of ternary \(\#270\) [\#275](https://github.com/nlohmann/json/pull/275) ([dtoma](https://github.com/dtoma)) - -## [v2.0.1](https://github.com/nlohmann/json/releases/tag/v2.0.1) (2016-06-28) - -[Full Changelog](https://github.com/nlohmann/json/compare/v2.0.0...v2.0.1) - -- Compilation error. [\#273](https://github.com/nlohmann/json/issues/273) -- dump\(\) performance degradation in v2 [\#272](https://github.com/nlohmann/json/issues/272) - -- fixed a tiny typo [\#271](https://github.com/nlohmann/json/pull/271) ([feroldi](https://github.com/feroldi)) - -## [v2.0.0](https://github.com/nlohmann/json/releases/tag/v2.0.0) (2016-06-23) - -[Full Changelog](https://github.com/nlohmann/json/compare/v1.1.0...v2.0.0) - -- json::diff generates incorrect patch when removing multiple array elements. [\#269](https://github.com/nlohmann/json/issues/269) -- Docs - What does Json\[key\] return? [\#267](https://github.com/nlohmann/json/issues/267) -- Compiler Errors With JSON.hpp [\#265](https://github.com/nlohmann/json/issues/265) -- Ambiguous push\_back and operator+= overloads [\#263](https://github.com/nlohmann/json/issues/263) -- Preseving order of items in json [\#262](https://github.com/nlohmann/json/issues/262) -- '\' char problem in strings [\#261](https://github.com/nlohmann/json/issues/261) -- VS2015 compile fail [\#260](https://github.com/nlohmann/json/issues/260) -- -Wconversion warning [\#259](https://github.com/nlohmann/json/issues/259) -- Maybe a bug [\#258](https://github.com/nlohmann/json/issues/258) -- Few tests failed on Visual C++ 2015 [\#257](https://github.com/nlohmann/json/issues/257) -- Access keys when iteration with new for loop C++11 [\#256](https://github.com/nlohmann/json/issues/256) -- multiline text values [\#255](https://github.com/nlohmann/json/issues/255) -- Error when using json in g++ [\#254](https://github.com/nlohmann/json/issues/254) -- is the release 2.0? [\#253](https://github.com/nlohmann/json/issues/253) -- concatenate objects [\#252](https://github.com/nlohmann/json/issues/252) -- Encoding [\#251](https://github.com/nlohmann/json/issues/251) -- Unable to build example for constructing json object with stringstreams [\#250](https://github.com/nlohmann/json/issues/250) -- Hexadecimal support [\#249](https://github.com/nlohmann/json/issues/249) -- Update long-term goals [\#246](https://github.com/nlohmann/json/issues/246) -- Contribution To This Json Project [\#245](https://github.com/nlohmann/json/issues/245) -- Trouble using parser with initial dictionary [\#243](https://github.com/nlohmann/json/issues/243) -- Unit test fails when doing a CMake out-of-tree build [\#241](https://github.com/nlohmann/json/issues/241) -- -Wconversion warnings [\#239](https://github.com/nlohmann/json/issues/239) -- Additional integration options [\#237](https://github.com/nlohmann/json/issues/237) -- .get\\(\) works for non spaced string but returns as array for spaced/longer strings [\#236](https://github.com/nlohmann/json/issues/236) -- ambiguous overload for 'push\_back' and 'operator+=' [\#235](https://github.com/nlohmann/json/issues/235) -- Can't use basic\_json::iterator as a base iterator for std::move\_iterator [\#233](https://github.com/nlohmann/json/issues/233) -- json object's creation can freezes execution [\#231](https://github.com/nlohmann/json/issues/231) -- Incorrect dumping of parsed numbers with exponents, but without decimal places [\#230](https://github.com/nlohmann/json/issues/230) -- double values are serialized with commas as decimal points [\#228](https://github.com/nlohmann/json/issues/228) -- Move semantics with std::initializer\_list [\#225](https://github.com/nlohmann/json/issues/225) -- replace emplace [\#224](https://github.com/nlohmann/json/issues/224) -- abort during getline in yyfill [\#223](https://github.com/nlohmann/json/issues/223) -- free\(\): invalid pointer error in GCC 5.2.1 [\#221](https://github.com/nlohmann/json/issues/221) -- Error compile Android NDK error: 'strtof' is not a member of 'std' [\#219](https://github.com/nlohmann/json/issues/219) -- Wrong link in the README.md [\#217](https://github.com/nlohmann/json/issues/217) -- Wide character strings not supported [\#216](https://github.com/nlohmann/json/issues/216) -- Memory allocations using range-based for loops [\#214](https://github.com/nlohmann/json/issues/214) -- would you like to support gcc 4.8.1? [\#211](https://github.com/nlohmann/json/issues/211) -- Reading concatenated json's from an istream [\#210](https://github.com/nlohmann/json/issues/210) -- Conflicting typedef of ssize\_t on Windows 32 bit when using Boost.Python [\#204](https://github.com/nlohmann/json/issues/204) -- Inconsistency between operator\[\] and push\_back [\#203](https://github.com/nlohmann/json/issues/203) -- Small bugs in json.hpp \(get\_number\) and unit.cpp \(non-standard integer type test\) [\#199](https://github.com/nlohmann/json/issues/199) -- GCC/clang floating point parsing bug in strtod\(\) [\#195](https://github.com/nlohmann/json/issues/195) -- What is within scope? [\#192](https://github.com/nlohmann/json/issues/192) -- Bugs in miloyip/nativejson-benchmark: roundtrips [\#187](https://github.com/nlohmann/json/issues/187) -- Floating point exceptions [\#181](https://github.com/nlohmann/json/issues/181) -- Integer conversion to unsigned [\#178](https://github.com/nlohmann/json/issues/178) -- map string string fails to compile [\#176](https://github.com/nlohmann/json/issues/176) -- In basic\_json::basic\_json\(const CompatibleArrayType& val\), the requirement of CompatibleArrayType is not strict enough. [\#174](https://github.com/nlohmann/json/issues/174) -- Provide a FAQ [\#163](https://github.com/nlohmann/json/issues/163) -- Implicit assignment to std::string fails [\#144](https://github.com/nlohmann/json/issues/144) - -- Fix Issue \#265 [\#266](https://github.com/nlohmann/json/pull/266) ([06needhamt](https://github.com/06needhamt)) -- Define CMake/CTest tests [\#247](https://github.com/nlohmann/json/pull/247) ([robertmrk](https://github.com/robertmrk)) -- Out of tree builds and a few other miscellaneous CMake cleanups. [\#242](https://github.com/nlohmann/json/pull/242) ([ChrisKitching](https://github.com/ChrisKitching)) -- Implement additional integration options [\#238](https://github.com/nlohmann/json/pull/238) ([robertmrk](https://github.com/robertmrk)) -- make serialization locale-independent [\#232](https://github.com/nlohmann/json/pull/232) ([nlohmann](https://github.com/nlohmann)) -- fixes \#223 by updating README.md [\#227](https://github.com/nlohmann/json/pull/227) ([kevin--](https://github.com/kevin--)) -- Use namespace std for int64\_t and uint64\_t [\#226](https://github.com/nlohmann/json/pull/226) ([lv-zheng](https://github.com/lv-zheng)) -- Added missing cerrno header to fix ERANGE compile error on android [\#222](https://github.com/nlohmann/json/pull/222) ([Teemperor](https://github.com/Teemperor)) -- Corrected readme [\#218](https://github.com/nlohmann/json/pull/218) ([Annihil](https://github.com/Annihil)) -- Create PULL\_REQUEST\_TEMPLATE.md [\#213](https://github.com/nlohmann/json/pull/213) ([whackashoe](https://github.com/whackashoe)) -- fixed noexcept; added constexpr [\#208](https://github.com/nlohmann/json/pull/208) ([nlohmann](https://github.com/nlohmann)) -- Add support for afl-fuzz testing [\#207](https://github.com/nlohmann/json/pull/207) ([mykter](https://github.com/mykter)) -- replaced ssize\_t occurrences with auto \(addresses \#204\) [\#205](https://github.com/nlohmann/json/pull/205) ([nlohmann](https://github.com/nlohmann)) -- Fixed issue \#199 - Small bugs in json.hpp \(get\_number\) and unit.cpp \(non-standard integer type test\) [\#200](https://github.com/nlohmann/json/pull/200) ([twelsby](https://github.com/twelsby)) -- Fix broken link [\#197](https://github.com/nlohmann/json/pull/197) ([vog](https://github.com/vog)) -- Issue \#195 - update Travis to Trusty due to gcc/clang strtod\(\) bug [\#196](https://github.com/nlohmann/json/pull/196) ([twelsby](https://github.com/twelsby)) -- Issue \#178 - Extending support to full uint64\_t/int64\_t range and unsigned type \(updated\) [\#193](https://github.com/nlohmann/json/pull/193) ([twelsby](https://github.com/twelsby)) - -## [v1.1.0](https://github.com/nlohmann/json/releases/tag/v1.1.0) (2016-01-24) - -[Full Changelog](https://github.com/nlohmann/json/compare/v1.0.0...v1.1.0) - -- Small error in pull \#185 [\#194](https://github.com/nlohmann/json/issues/194) -- Bugs in miloyip/nativejson-benchmark: floating-point parsing [\#186](https://github.com/nlohmann/json/issues/186) -- Floating point equality [\#185](https://github.com/nlohmann/json/issues/185) -- Unused variables in catch [\#180](https://github.com/nlohmann/json/issues/180) -- Typo in documentation [\#179](https://github.com/nlohmann/json/issues/179) -- JSON performance benchmark comparision [\#177](https://github.com/nlohmann/json/issues/177) -- Since re2c is often ignored in pull requests, it may make sense to make a contributing.md file [\#175](https://github.com/nlohmann/json/issues/175) -- Question about exceptions [\#173](https://github.com/nlohmann/json/issues/173) -- Android? [\#172](https://github.com/nlohmann/json/issues/172) -- Cannot index by key of type static constexpr const char\* [\#171](https://github.com/nlohmann/json/issues/171) -- Add assertions [\#168](https://github.com/nlohmann/json/issues/168) -- MSVC 2015 build fails when attempting to compare object\_t [\#167](https://github.com/nlohmann/json/issues/167) -- Member detector is not portable [\#166](https://github.com/nlohmann/json/issues/166) -- Unnecessary const\_cast [\#162](https://github.com/nlohmann/json/issues/162) -- Question about get\_ref\(\) [\#128](https://github.com/nlohmann/json/issues/128) -- range based for loop for objects [\#83](https://github.com/nlohmann/json/issues/83) -- Consider submitting this to the Boost Library Incubator [\#66](https://github.com/nlohmann/json/issues/66) - -- Fixed Issue \#186 - add strto\(f|d|ld\) overload wrappers, "-0.0" special case and FP trailing zero [\#191](https://github.com/nlohmann/json/pull/191) ([twelsby](https://github.com/twelsby)) -- Issue \#185 - remove approx\(\) and use \#pragma to kill warnings [\#190](https://github.com/nlohmann/json/pull/190) ([twelsby](https://github.com/twelsby)) -- Fixed Issue \#171 - added two extra template overloads of operator\[\] for T\* arguments [\#189](https://github.com/nlohmann/json/pull/189) ([twelsby](https://github.com/twelsby)) -- Fixed issue \#167 - removed operator ValueType\(\) condition for VS2015 [\#188](https://github.com/nlohmann/json/pull/188) ([twelsby](https://github.com/twelsby)) -- Implementation of get\_ref\(\) [\#184](https://github.com/nlohmann/json/pull/184) ([dariomt](https://github.com/dariomt)) -- Fixed some typos in CONTRIBUTING.md [\#182](https://github.com/nlohmann/json/pull/182) ([nibroc](https://github.com/nibroc)) - -## [v1.0.0](https://github.com/nlohmann/json/releases/tag/v1.0.0) (2015-12-27) - -[Full Changelog](https://github.com/nlohmann/json/compare/v1.0.0-rc1...v1.0.0) - -- add key name to exception [\#160](https://github.com/nlohmann/json/issues/160) -- Getting member discarding qualifyer [\#159](https://github.com/nlohmann/json/issues/159) -- basic\_json::iterator::value\(\) output includes quotes while basic\_json::iterator::key\(\) doesn't [\#158](https://github.com/nlohmann/json/issues/158) -- Indexing `const basic_json<>` with `const basic_string` [\#157](https://github.com/nlohmann/json/issues/157) -- token\_type\_name\(token\_type t\): not all control paths return a value [\#156](https://github.com/nlohmann/json/issues/156) -- prevent json.hpp from emitting compiler warnings [\#154](https://github.com/nlohmann/json/issues/154) -- json::parse\(string\) does not check utf8 bom [\#152](https://github.com/nlohmann/json/issues/152) -- unsigned 64bit values output as signed [\#151](https://github.com/nlohmann/json/issues/151) -- Wish feature: json5 [\#150](https://github.com/nlohmann/json/issues/150) -- Unable to compile on MSVC 2015 with SDL checking enabled: This function or variable may be unsafe. [\#149](https://github.com/nlohmann/json/issues/149) -- "Json Object" type does not keep object order [\#148](https://github.com/nlohmann/json/issues/148) -- dump\(\) convert strings encoded by utf-8 to shift-jis on windows 10. [\#147](https://github.com/nlohmann/json/issues/147) -- Unable to get field names in a json object [\#145](https://github.com/nlohmann/json/issues/145) -- Question: Is the use of incomplete type correct? [\#138](https://github.com/nlohmann/json/issues/138) -- json.hpp:5746:32: error: 'to\_string' is not a member of 'std' [\#136](https://github.com/nlohmann/json/issues/136) -- Bug in basic\_json::operator\[\] const overload [\#135](https://github.com/nlohmann/json/issues/135) -- wrong enable\_if for const pointer \(instead of pointer-to-const\) [\#134](https://github.com/nlohmann/json/issues/134) -- overload of at\(\) with default value [\#133](https://github.com/nlohmann/json/issues/133) -- Splitting source [\#132](https://github.com/nlohmann/json/issues/132) -- Question about get\_ptr\(\) [\#127](https://github.com/nlohmann/json/issues/127) -- Visual Studio 14 Debug assertion failed [\#125](https://github.com/nlohmann/json/issues/125) -- Memory leak in face of exceptions [\#118](https://github.com/nlohmann/json/issues/118) -- Find and Count for arrays [\#117](https://github.com/nlohmann/json/issues/117) -- dynamically constructing an arbitrarily nested object [\#114](https://github.com/nlohmann/json/issues/114) -- Returning any data type [\#113](https://github.com/nlohmann/json/issues/113) -- Compile error with g++ 4.9.3 cygwin 64-bit [\#112](https://github.com/nlohmann/json/issues/112) -- insert json array issue with gcc4.8.2 [\#110](https://github.com/nlohmann/json/issues/110) -- error: unterminated raw string [\#109](https://github.com/nlohmann/json/issues/109) -- vector\ copy constructor really weird [\#108](https://github.com/nlohmann/json/issues/108) -- \[clang-3.6.2\] string/sstream with number to json issue [\#107](https://github.com/nlohmann/json/issues/107) -- object field accessors [\#103](https://github.com/nlohmann/json/issues/103) -- v8pp and json [\#95](https://github.com/nlohmann/json/issues/95) -- Wishlist [\#65](https://github.com/nlohmann/json/issues/65) -- Windows/Visual Studio \(through 2013\) is unsupported [\#62](https://github.com/nlohmann/json/issues/62) - -- Replace sprintf with hex function, this fixes \#149 [\#153](https://github.com/nlohmann/json/pull/153) ([whackashoe](https://github.com/whackashoe)) -- Fix character skipping after a surrogate pair [\#146](https://github.com/nlohmann/json/pull/146) ([robertmrk](https://github.com/robertmrk)) -- Detect correctly pointer-to-const [\#137](https://github.com/nlohmann/json/pull/137) ([dariomt](https://github.com/dariomt)) -- disabled "CopyAssignable" test for MSVC in Debug mode, see \#125 [\#131](https://github.com/nlohmann/json/pull/131) ([dariomt](https://github.com/dariomt)) -- removed stream operator for iterator, resolution for \#125 [\#130](https://github.com/nlohmann/json/pull/130) ([dariomt](https://github.com/dariomt)) -- fixed typos in comments for examples [\#129](https://github.com/nlohmann/json/pull/129) ([dariomt](https://github.com/dariomt)) -- Remove superfluous inefficiency [\#126](https://github.com/nlohmann/json/pull/126) ([d-frey](https://github.com/d-frey)) -- remove invalid parameter '-stdlib=libc++' in CMakeLists.txt [\#124](https://github.com/nlohmann/json/pull/124) ([emvivre](https://github.com/emvivre)) -- exception-safe object creation, fixes \#118 [\#122](https://github.com/nlohmann/json/pull/122) ([d-frey](https://github.com/d-frey)) -- Fix small oversight. [\#121](https://github.com/nlohmann/json/pull/121) ([ColinH](https://github.com/ColinH)) -- Overload parse\(\) to accept an rvalue reference [\#120](https://github.com/nlohmann/json/pull/120) ([silverweed](https://github.com/silverweed)) -- Use the right variable name in doc string [\#115](https://github.com/nlohmann/json/pull/115) ([whoshuu](https://github.com/whoshuu)) - -## [v1.0.0-rc1](https://github.com/nlohmann/json/releases/tag/v1.0.0-rc1) (2015-07-26) - -[Full Changelog](https://github.com/nlohmann/json/compare/4502e7e51c0569419c26e75fbdd5748170603e54...v1.0.0-rc1) - -- Finish documenting the public interface in Doxygen [\#102](https://github.com/nlohmann/json/issues/102) -- Binary string causes numbers to be dumped as hex [\#101](https://github.com/nlohmann/json/issues/101) -- failed to iterator json object with reverse\_iterator [\#100](https://github.com/nlohmann/json/issues/100) -- 'noexcept' : unknown override specifier [\#99](https://github.com/nlohmann/json/issues/99) -- json float parsing problem [\#98](https://github.com/nlohmann/json/issues/98) -- Adjust wording to JSON RFC [\#97](https://github.com/nlohmann/json/issues/97) -- static analysis warnings [\#94](https://github.com/nlohmann/json/issues/94) -- reverse\_iterator operator inheritance problem [\#93](https://github.com/nlohmann/json/issues/93) -- init error [\#92](https://github.com/nlohmann/json/issues/92) -- access by \(const\) reference [\#91](https://github.com/nlohmann/json/issues/91) -- is\_integer and is\_float tests [\#90](https://github.com/nlohmann/json/issues/90) -- Nonstandard integer type [\#89](https://github.com/nlohmann/json/issues/89) -- static library build [\#84](https://github.com/nlohmann/json/issues/84) -- lexer::get\_number return NAN [\#82](https://github.com/nlohmann/json/issues/82) -- MinGW have no std::to\_string [\#80](https://github.com/nlohmann/json/issues/80) -- Incorrect behaviour of basic\_json::count method [\#78](https://github.com/nlohmann/json/issues/78) -- Invoking is\_array\(\) function creates "null" value [\#77](https://github.com/nlohmann/json/issues/77) -- dump\(\) / parse\(\) not idempotent [\#76](https://github.com/nlohmann/json/issues/76) -- Handle infinity and NaN cases [\#70](https://github.com/nlohmann/json/issues/70) -- errors in g++-4.8.1 [\#68](https://github.com/nlohmann/json/issues/68) -- Keys when iterating over objects [\#67](https://github.com/nlohmann/json/issues/67) -- Compilation results in tons of warnings [\#64](https://github.com/nlohmann/json/issues/64) -- Complete brief documentation [\#61](https://github.com/nlohmann/json/issues/61) -- Double quotation mark is not parsed correctly [\#60](https://github.com/nlohmann/json/issues/60) -- Get coverage back to 100% [\#58](https://github.com/nlohmann/json/issues/58) -- erase elements using iterators [\#57](https://github.com/nlohmann/json/issues/57) -- Removing item from array [\#56](https://github.com/nlohmann/json/issues/56) -- Serialize/Deserialize like PHP? [\#55](https://github.com/nlohmann/json/issues/55) -- Numbers as keys [\#54](https://github.com/nlohmann/json/issues/54) -- Why are elements alphabetized on key while iterating? [\#53](https://github.com/nlohmann/json/issues/53) -- Document erase, count, and iterators key and value [\#52](https://github.com/nlohmann/json/issues/52) -- Do not use std::to\_string [\#51](https://github.com/nlohmann/json/issues/51) -- Supported compilers [\#50](https://github.com/nlohmann/json/issues/50) -- Confused about iterating through json objects [\#49](https://github.com/nlohmann/json/issues/49) -- Use non-member begin/end [\#48](https://github.com/nlohmann/json/issues/48) -- Erase key [\#47](https://github.com/nlohmann/json/issues/47) -- Key iterator [\#46](https://github.com/nlohmann/json/issues/46) -- Add count member function [\#45](https://github.com/nlohmann/json/issues/45) -- Problem getting vector \(array\) of strings [\#44](https://github.com/nlohmann/json/issues/44) -- Compilation error due to assuming that private=public [\#43](https://github.com/nlohmann/json/issues/43) -- Use of deprecated implicit copy constructor [\#42](https://github.com/nlohmann/json/issues/42) -- Printing attribute names [\#39](https://github.com/nlohmann/json/issues/39) -- dumping a small number\_float just outputs 0.000000 [\#37](https://github.com/nlohmann/json/issues/37) -- find is error [\#32](https://github.com/nlohmann/json/issues/32) -- Avoid using spaces when encoding without pretty print [\#31](https://github.com/nlohmann/json/issues/31) -- Cannot encode long numbers [\#30](https://github.com/nlohmann/json/issues/30) -- segmentation fault when iterating over empty arrays/objects [\#28](https://github.com/nlohmann/json/issues/28) -- Creating an empty array [\#27](https://github.com/nlohmann/json/issues/27) -- Custom allocator support [\#25](https://github.com/nlohmann/json/issues/25) -- make the type of the used string container customizable [\#20](https://github.com/nlohmann/json/issues/20) -- Improper parsing of JSON string "\\" [\#17](https://github.com/nlohmann/json/issues/17) -- create a header-only version [\#16](https://github.com/nlohmann/json/issues/16) -- Don't return "const values" [\#15](https://github.com/nlohmann/json/issues/15) -- Add to\_string overload for indentation [\#13](https://github.com/nlohmann/json/issues/13) -- string parser does not recognize uncompliant strings [\#12](https://github.com/nlohmann/json/issues/12) -- possible double-free in find function [\#11](https://github.com/nlohmann/json/issues/11) -- UTF-8 encoding/deconding/testing [\#10](https://github.com/nlohmann/json/issues/10) -- move code into namespace [\#9](https://github.com/nlohmann/json/issues/9) -- free functions for explicit objects and arrays in initializer lists [\#8](https://github.com/nlohmann/json/issues/8) -- unique\_ptr for ownership [\#7](https://github.com/nlohmann/json/issues/7) -- Add unit tests [\#4](https://github.com/nlohmann/json/issues/4) -- Drop C++98 support [\#3](https://github.com/nlohmann/json/issues/3) -- Test case coverage [\#2](https://github.com/nlohmann/json/issues/2) -- Runtime error in Travis job [\#1](https://github.com/nlohmann/json/issues/1) - -- Keyword 'inline' is useless when member functions are defined in headers [\#87](https://github.com/nlohmann/json/pull/87) ([ahamez](https://github.com/ahamez)) -- Remove useless typename [\#86](https://github.com/nlohmann/json/pull/86) ([ahamez](https://github.com/ahamez)) -- Avoid warning with Xcode's clang [\#85](https://github.com/nlohmann/json/pull/85) ([ahamez](https://github.com/ahamez)) -- Fix typos [\#73](https://github.com/nlohmann/json/pull/73) ([aqnouch](https://github.com/aqnouch)) -- Replace `default_callback` function with `nullptr` and check for null… [\#72](https://github.com/nlohmann/json/pull/72) ([aburgh](https://github.com/aburgh)) -- support enum [\#71](https://github.com/nlohmann/json/pull/71) ([likebeta](https://github.com/likebeta)) -- Fix performance regression introduced with the parsing callback feature. [\#69](https://github.com/nlohmann/json/pull/69) ([aburgh](https://github.com/aburgh)) -- Improve the implementations of the comparission-operators [\#63](https://github.com/nlohmann/json/pull/63) ([Florianjw](https://github.com/Florianjw)) -- Fix compilation of json\_unit with GCC 5 [\#59](https://github.com/nlohmann/json/pull/59) ([dkopecek](https://github.com/dkopecek)) -- Parse streams incrementally. [\#40](https://github.com/nlohmann/json/pull/40) ([aburgh](https://github.com/aburgh)) -- Feature/small float serialization [\#38](https://github.com/nlohmann/json/pull/38) ([jrandall](https://github.com/jrandall)) -- template version with re2c scanner [\#36](https://github.com/nlohmann/json/pull/36) ([nlohmann](https://github.com/nlohmann)) -- more descriptive documentation in example [\#33](https://github.com/nlohmann/json/pull/33) ([luxe](https://github.com/luxe)) -- Fix string conversion under Clang [\#26](https://github.com/nlohmann/json/pull/26) ([wancw](https://github.com/wancw)) -- Fixed dumping of strings [\#24](https://github.com/nlohmann/json/pull/24) ([Teemperor](https://github.com/Teemperor)) -- Added a remark to the readme that coverage is GCC only for now [\#23](https://github.com/nlohmann/json/pull/23) ([Teemperor](https://github.com/Teemperor)) -- Unicode escaping [\#22](https://github.com/nlohmann/json/pull/22) ([Teemperor](https://github.com/Teemperor)) -- Implemented the JSON spec for string parsing for everything but the \uXXXX escaping [\#21](https://github.com/nlohmann/json/pull/21) ([Teemperor](https://github.com/Teemperor)) -- add the std iterator typedefs to iterator and const\_iterator [\#19](https://github.com/nlohmann/json/pull/19) ([kirkshoop](https://github.com/kirkshoop)) -- Fixed escaped quotes [\#18](https://github.com/nlohmann/json/pull/18) ([Teemperor](https://github.com/Teemperor)) -- Fix double delete on std::bad\_alloc exception [\#14](https://github.com/nlohmann/json/pull/14) ([elliotgoodrich](https://github.com/elliotgoodrich)) -- Added CMake and lcov [\#6](https://github.com/nlohmann/json/pull/6) ([Teemperor](https://github.com/Teemperor)) -- Version 2.0 [\#5](https://github.com/nlohmann/json/pull/5) ([nlohmann](https://github.com/nlohmann)) - - - -\* *This Changelog was automatically generated by [github_changelog_generator](https://github.com/github-changelog-generator/github-changelog-generator)* diff --git a/app/jni/src/libultraship/extern/nlohmann-json/LICENSE.MIT b/app/jni/src/libultraship/extern/nlohmann-json/LICENSE.MIT deleted file mode 100644 index 1c1f7a6..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/LICENSE.MIT +++ /dev/null @@ -1,21 +0,0 @@ -MIT License - -Copyright (c) 2013-2022 Niels Lohmann - -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. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/LICENSES/Apache-2.0.txt b/app/jni/src/libultraship/extern/nlohmann-json/LICENSES/Apache-2.0.txt deleted file mode 100644 index 137069b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/LICENSES/Apache-2.0.txt +++ /dev/null @@ -1,73 +0,0 @@ -Apache License -Version 2.0, January 2004 -http://www.apache.org/licenses/ - -TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION - -1. Definitions. - -"License" shall mean the terms and conditions for use, reproduction, and distribution as defined by Sections 1 through 9 of this document. - -"Licensor" shall mean the copyright owner or entity authorized by the copyright owner that is granting the License. - -"Legal Entity" shall mean the union of the acting entity and all other entities that control, are controlled by, or are under common control with that entity. For the purposes of this definition, "control" means (i) the power, direct or indirect, to cause the direction or management of such entity, whether by contract or otherwise, or (ii) ownership of fifty percent (50%) or more of the outstanding shares, or (iii) beneficial ownership of such entity. - -"You" (or "Your") shall mean an individual or Legal Entity exercising permissions granted by this License. - -"Source" form shall mean the preferred form for making modifications, including but not limited to software source code, documentation source, and configuration files. - -"Object" form shall mean any form resulting from mechanical transformation or translation of a Source form, including but not limited to compiled object code, generated documentation, and conversions to other media types. - -"Work" shall mean the work of authorship, whether in Source or Object form, made available under the License, as indicated by a copyright notice that is included in or attached to the work (an example is provided in the Appendix below). - -"Derivative Works" shall mean any work, whether in Source or Object form, that is based on (or derived from) the Work and for which the editorial revisions, annotations, elaborations, or other modifications represent, as a whole, an original work of authorship. For the purposes of this License, Derivative Works shall not include works that remain separable from, or merely link (or bind by name) to the interfaces of, the Work and Derivative Works thereof. - -"Contribution" shall mean any work of authorship, including the original version of the Work and any modifications or additions to that Work or Derivative Works thereof, that is intentionally submitted to Licensor for inclusion in the Work by the copyright owner or by an individual or Legal Entity authorized to submit on behalf of the copyright owner. For the purposes of this definition, "submitted" means any form of electronic, verbal, or written communication sent to the Licensor or its representatives, including but not limited to communication on electronic mailing lists, source code control systems, and issue tracking systems that are managed by, or on behalf of, the Licensor for the purpose of discussing and improving the Work, but excluding communication that is conspicuously marked or otherwise designated in writing by the copyright owner as "Not a Contribution." - -"Contributor" shall mean Licensor and any individual or Legal Entity on behalf of whom a Contribution has been received by Licensor and subsequently incorporated within the Work. - -2. Grant of Copyright License. Subject to the terms and conditions of this License, each Contributor hereby grants to You a perpetual, worldwide, non-exclusive, no-charge, royalty-free, irrevocable copyright license to reproduce, prepare Derivative Works of, publicly display, publicly perform, sublicense, and distribute the Work and such Derivative Works in Source or Object form. - -3. Grant of Patent License. Subject to the terms and conditions of this License, each Contributor hereby grants to You a perpetual, worldwide, non-exclusive, no-charge, royalty-free, irrevocable (except as stated in this section) patent license to make, have made, use, offer to sell, sell, import, and otherwise transfer the Work, where such license applies only to those patent claims licensable by such Contributor that are necessarily infringed by their Contribution(s) alone or by combination of their Contribution(s) with the Work to which such Contribution(s) was submitted. If You institute patent litigation against any entity (including a cross-claim or counterclaim in a lawsuit) alleging that the Work or a Contribution incorporated within the Work constitutes direct or contributory patent infringement, then any patent licenses granted to You under this License for that Work shall terminate as of the date such litigation is filed. - -4. Redistribution. You may reproduce and distribute copies of the Work or Derivative Works thereof in any medium, with or without modifications, and in Source or Object form, provided that You meet the following conditions: - - (a) You must give any other recipients of the Work or Derivative Works a copy of this License; and - - (b) You must cause any modified files to carry prominent notices stating that You changed the files; and - - (c) You must retain, in the Source form of any Derivative Works that You distribute, all copyright, patent, trademark, and attribution notices from the Source form of the Work, excluding those notices that do not pertain to any part of the Derivative Works; and - - (d) If the Work includes a "NOTICE" text file as part of its distribution, then any Derivative Works that You distribute must include a readable copy of the attribution notices contained within such NOTICE file, excluding those notices that do not pertain to any part of the Derivative Works, in at least one of the following places: within a NOTICE text file distributed as part of the Derivative Works; within the Source form or documentation, if provided along with the Derivative Works; or, within a display generated by the Derivative Works, if and wherever such third-party notices normally appear. The contents of the NOTICE file are for informational purposes only and do not modify the License. You may add Your own attribution notices within Derivative Works that You distribute, alongside or as an addendum to the NOTICE text from the Work, provided that such additional attribution notices cannot be construed as modifying the License. - - You may add Your own copyright statement to Your modifications and may provide additional or different license terms and conditions for use, reproduction, or distribution of Your modifications, or for any such Derivative Works as a whole, provided Your use, reproduction, and distribution of the Work otherwise complies with the conditions stated in this License. - -5. Submission of Contributions. Unless You explicitly state otherwise, any Contribution intentionally submitted for inclusion in the Work by You to the Licensor shall be under the terms and conditions of this License, without any additional terms or conditions. Notwithstanding the above, nothing herein shall supersede or modify the terms of any separate license agreement you may have executed with Licensor regarding such Contributions. - -6. Trademarks. This License does not grant permission to use the trade names, trademarks, service marks, or product names of the Licensor, except as required for reasonable and customary use in describing the origin of the Work and reproducing the content of the NOTICE file. - -7. Disclaimer of Warranty. Unless required by applicable law or agreed to in writing, Licensor provides the Work (and each Contributor provides its Contributions) on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied, including, without limitation, any warranties or conditions of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A PARTICULAR PURPOSE. You are solely responsible for determining the appropriateness of using or redistributing the Work and assume any risks associated with Your exercise of permissions under this License. - -8. Limitation of Liability. In no event and under no legal theory, whether in tort (including negligence), contract, or otherwise, unless required by applicable law (such as deliberate and grossly negligent acts) or agreed to in writing, shall any Contributor be liable to You for damages, including any direct, indirect, special, incidental, or consequential damages of any character arising as a result of this License or out of the use or inability to use the Work (including but not limited to damages for loss of goodwill, work stoppage, computer failure or malfunction, or any and all other commercial damages or losses), even if such Contributor has been advised of the possibility of such damages. - -9. Accepting Warranty or Additional Liability. While redistributing the Work or Derivative Works thereof, You may choose to offer, and charge a fee for, acceptance of support, warranty, indemnity, or other liability obligations and/or rights consistent with this License. However, in accepting such obligations, You may act only on Your own behalf and on Your sole responsibility, not on behalf of any other Contributor, and only if You agree to indemnify, defend, and hold each Contributor harmless for any liability incurred by, or claims asserted against, such Contributor by reason of your accepting any such warranty or additional liability. - -END OF TERMS AND CONDITIONS - -APPENDIX: How to apply the Apache License to your work. - -To apply the Apache License to your work, attach the following boilerplate notice, with the fields enclosed by brackets "[]" replaced with your own identifying information. (Don't include the brackets!) The text should be enclosed in the appropriate comment syntax for the file format. We also recommend that a file or class name and description of purpose be included on the same "printed page" as the copyright notice for easier identification within third-party archives. - -Copyright [yyyy] [name of copyright owner] - -Licensed under the Apache License, Version 2.0 (the "License"); -you may not use this file except in compliance with the License. -You may obtain a copy of the License at - -http://www.apache.org/licenses/LICENSE-2.0 - -Unless required by applicable law or agreed to in writing, software -distributed under the License is distributed on an "AS IS" BASIS, -WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -See the License for the specific language governing permissions and -limitations under the License. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/LICENSES/BSD-3-Clause.txt b/app/jni/src/libultraship/extern/nlohmann-json/LICENSES/BSD-3-Clause.txt deleted file mode 100644 index ea890af..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/LICENSES/BSD-3-Clause.txt +++ /dev/null @@ -1,11 +0,0 @@ -Copyright (c) . - -Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: - -1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. - -2. 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. - -3. Neither the name of the copyright holder 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 HOLDER 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. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/LICENSES/GPL-3.0-only.txt b/app/jni/src/libultraship/extern/nlohmann-json/LICENSES/GPL-3.0-only.txt deleted file mode 100644 index d41c0bd..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/LICENSES/GPL-3.0-only.txt +++ /dev/null @@ -1,232 +0,0 @@ -GNU GENERAL PUBLIC LICENSE -Version 3, 29 June 2007 - -Copyright © 2007 Free Software Foundation, Inc. - -Everyone is permitted to copy and distribute verbatim copies of this license document, but changing it is not allowed. - -Preamble - -The GNU General Public License is a free, copyleft license for software and other kinds of works. - -The licenses for most software and other practical works are designed to take away your freedom to share and change the works. By contrast, the GNU General Public License is intended to guarantee your freedom to share and change all versions of a program--to make sure it remains free software for all its users. We, the Free Software Foundation, use the GNU General Public License for most of our software; it applies also to any other work released this way by its authors. You can apply it to your programs, too. - -When we speak of free software, we are referring to freedom, not price. Our General Public Licenses are designed to make sure that you have the freedom to distribute copies of free software (and charge for them if you wish), that you receive source code or can get it if you want it, that you can change the software or use pieces of it in new free programs, and that you know you can do these things. - -To protect your rights, we need to prevent others from denying you these rights or asking you to surrender the rights. Therefore, you have certain responsibilities if you distribute copies of the software, or if you modify it: responsibilities to respect the freedom of others. - -For example, if you distribute copies of such a program, whether gratis or for a fee, you must pass on to the recipients the same freedoms that you received. You must make sure that they, too, receive or can get the source code. And you must show them these terms so they know their rights. - -Developers that use the GNU GPL protect your rights with two steps: (1) assert copyright on the software, and (2) offer you this License giving you legal permission to copy, distribute and/or modify it. - -For the developers' and authors' protection, the GPL clearly explains that there is no warranty for this free software. For both users' and authors' sake, the GPL requires that modified versions be marked as changed, so that their problems will not be attributed erroneously to authors of previous versions. - -Some devices are designed to deny users access to install or run modified versions of the software inside them, although the manufacturer can do so. This is fundamentally incompatible with the aim of protecting users' freedom to change the software. The systematic pattern of such abuse occurs in the area of products for individuals to use, which is precisely where it is most unacceptable. Therefore, we have designed this version of the GPL to prohibit the practice for those products. If such problems arise substantially in other domains, we stand ready to extend this provision to those domains in future versions of the GPL, as needed to protect the freedom of users. - -Finally, every program is threatened constantly by software patents. States should not allow patents to restrict development and use of software on general-purpose computers, but in those that do, we wish to avoid the special danger that patents applied to a free program could make it effectively proprietary. To prevent this, the GPL assures that patents cannot be used to render the program non-free. - -The precise terms and conditions for copying, distribution and modification follow. - -TERMS AND CONDITIONS - -0. Definitions. - -“This License” refers to version 3 of the GNU General Public License. - -“Copyright” also means copyright-like laws that apply to other kinds of works, such as semiconductor masks. - -“The Program” refers to any copyrightable work licensed under this License. Each licensee is addressed as “you”. “Licensees” and “recipients” may be individuals or organizations. - -To “modify” a work means to copy from or adapt all or part of the work in a fashion requiring copyright permission, other than the making of an exact copy. The resulting work is called a “modified version” of the earlier work or a work “based on” the earlier work. - -A “covered work” means either the unmodified Program or a work based on the Program. - -To “propagate” a work means to do anything with it that, without permission, would make you directly or secondarily liable for infringement under applicable copyright law, except executing it on a computer or modifying a private copy. Propagation includes copying, distribution (with or without modification), making available to the public, and in some countries other activities as well. - -To “convey” a work means any kind of propagation that enables other parties to make or receive copies. Mere interaction with a user through a computer network, with no transfer of a copy, is not conveying. - -An interactive user interface displays “Appropriate Legal Notices” to the extent that it includes a convenient and prominently visible feature that (1) displays an appropriate copyright notice, and (2) tells the user that there is no warranty for the work (except to the extent that warranties are provided), that licensees may convey the work under this License, and how to view a copy of this License. If the interface presents a list of user commands or options, such as a menu, a prominent item in the list meets this criterion. - -1. Source Code. -The “source code” for a work means the preferred form of the work for making modifications to it. “Object code” means any non-source form of a work. - -A “Standard Interface” means an interface that either is an official standard defined by a recognized standards body, or, in the case of interfaces specified for a particular programming language, one that is widely used among developers working in that language. - -The “System Libraries” of an executable work include anything, other than the work as a whole, that (a) is included in the normal form of packaging a Major Component, but which is not part of that Major Component, and (b) serves only to enable use of the work with that Major Component, or to implement a Standard Interface for which an implementation is available to the public in source code form. A “Major Component”, in this context, means a major essential component (kernel, window system, and so on) of the specific operating system (if any) on which the executable work runs, or a compiler used to produce the work, or an object code interpreter used to run it. - -The “Corresponding Source” for a work in object code form means all the source code needed to generate, install, and (for an executable work) run the object code and to modify the work, including scripts to control those activities. However, it does not include the work's System Libraries, or general-purpose tools or generally available free programs which are used unmodified in performing those activities but which are not part of the work. For example, Corresponding Source includes interface definition files associated with source files for the work, and the source code for shared libraries and dynamically linked subprograms that the work is specifically designed to require, such as by intimate data communication or control flow between those subprograms and other parts of the work. - -The Corresponding Source need not include anything that users can regenerate automatically from other parts of the Corresponding Source. - -The Corresponding Source for a work in source code form is that same work. - -2. Basic Permissions. -All rights granted under this License are granted for the term of copyright on the Program, and are irrevocable provided the stated conditions are met. This License explicitly affirms your unlimited permission to run the unmodified Program. The output from running a covered work is covered by this License only if the output, given its content, constitutes a covered work. This License acknowledges your rights of fair use or other equivalent, as provided by copyright law. - -You may make, run and propagate covered works that you do not convey, without conditions so long as your license otherwise remains in force. You may convey covered works to others for the sole purpose of having them make modifications exclusively for you, or provide you with facilities for running those works, provided that you comply with the terms of this License in conveying all material for which you do not control copyright. Those thus making or running the covered works for you must do so exclusively on your behalf, under your direction and control, on terms that prohibit them from making any copies of your copyrighted material outside their relationship with you. - -Conveying under any other circumstances is permitted solely under the conditions stated below. Sublicensing is not allowed; section 10 makes it unnecessary. - -3. Protecting Users' Legal Rights From Anti-Circumvention Law. -No covered work shall be deemed part of an effective technological measure under any applicable law fulfilling obligations under article 11 of the WIPO copyright treaty adopted on 20 December 1996, or similar laws prohibiting or restricting circumvention of such measures. - -When you convey a covered work, you waive any legal power to forbid circumvention of technological measures to the extent such circumvention is effected by exercising rights under this License with respect to the covered work, and you disclaim any intention to limit operation or modification of the work as a means of enforcing, against the work's users, your or third parties' legal rights to forbid circumvention of technological measures. - -4. Conveying Verbatim Copies. -You may convey verbatim copies of the Program's source code as you receive it, in any medium, provided that you conspicuously and appropriately publish on each copy an appropriate copyright notice; keep intact all notices stating that this License and any non-permissive terms added in accord with section 7 apply to the code; keep intact all notices of the absence of any warranty; and give all recipients a copy of this License along with the Program. - -You may charge any price or no price for each copy that you convey, and you may offer support or warranty protection for a fee. - -5. Conveying Modified Source Versions. -You may convey a work based on the Program, or the modifications to produce it from the Program, in the form of source code under the terms of section 4, provided that you also meet all of these conditions: - - a) The work must carry prominent notices stating that you modified it, and giving a relevant date. - - b) The work must carry prominent notices stating that it is released under this License and any conditions added under section 7. This requirement modifies the requirement in section 4 to “keep intact all notices”. - - c) You must license the entire work, as a whole, under this License to anyone who comes into possession of a copy. This License will therefore apply, along with any applicable section 7 additional terms, to the whole of the work, and all its parts, regardless of how they are packaged. This License gives no permission to license the work in any other way, but it does not invalidate such permission if you have separately received it. - - d) If the work has interactive user interfaces, each must display Appropriate Legal Notices; however, if the Program has interactive interfaces that do not display Appropriate Legal Notices, your work need not make them do so. - -A compilation of a covered work with other separate and independent works, which are not by their nature extensions of the covered work, and which are not combined with it such as to form a larger program, in or on a volume of a storage or distribution medium, is called an “aggregate” if the compilation and its resulting copyright are not used to limit the access or legal rights of the compilation's users beyond what the individual works permit. Inclusion of a covered work in an aggregate does not cause this License to apply to the other parts of the aggregate. - -6. Conveying Non-Source Forms. -You may convey a covered work in object code form under the terms of sections 4 and 5, provided that you also convey the machine-readable Corresponding Source under the terms of this License, in one of these ways: - - a) Convey the object code in, or embodied in, a physical product (including a physical distribution medium), accompanied by the Corresponding Source fixed on a durable physical medium customarily used for software interchange. - - b) Convey the object code in, or embodied in, a physical product (including a physical distribution medium), accompanied by a written offer, valid for at least three years and valid for as long as you offer spare parts or customer support for that product model, to give anyone who possesses the object code either (1) a copy of the Corresponding Source for all the software in the product that is covered by this License, on a durable physical medium customarily used for software interchange, for a price no more than your reasonable cost of physically performing this conveying of source, or (2) access to copy the Corresponding Source from a network server at no charge. - - c) Convey individual copies of the object code with a copy of the written offer to provide the Corresponding Source. This alternative is allowed only occasionally and noncommercially, and only if you received the object code with such an offer, in accord with subsection 6b. - - d) Convey the object code by offering access from a designated place (gratis or for a charge), and offer equivalent access to the Corresponding Source in the same way through the same place at no further charge. You need not require recipients to copy the Corresponding Source along with the object code. If the place to copy the object code is a network server, the Corresponding Source may be on a different server (operated by you or a third party) that supports equivalent copying facilities, provided you maintain clear directions next to the object code saying where to find the Corresponding Source. Regardless of what server hosts the Corresponding Source, you remain obligated to ensure that it is available for as long as needed to satisfy these requirements. - - e) Convey the object code using peer-to-peer transmission, provided you inform other peers where the object code and Corresponding Source of the work are being offered to the general public at no charge under subsection 6d. - -A separable portion of the object code, whose source code is excluded from the Corresponding Source as a System Library, need not be included in conveying the object code work. - -A “User Product” is either (1) a “consumer product”, which means any tangible personal property which is normally used for personal, family, or household purposes, or (2) anything designed or sold for incorporation into a dwelling. In determining whether a product is a consumer product, doubtful cases shall be resolved in favor of coverage. For a particular product received by a particular user, “normally used” refers to a typical or common use of that class of product, regardless of the status of the particular user or of the way in which the particular user actually uses, or expects or is expected to use, the product. A product is a consumer product regardless of whether the product has substantial commercial, industrial or non-consumer uses, unless such uses represent the only significant mode of use of the product. - -“Installation Information” for a User Product means any methods, procedures, authorization keys, or other information required to install and execute modified versions of a covered work in that User Product from a modified version of its Corresponding Source. The information must suffice to ensure that the continued functioning of the modified object code is in no case prevented or interfered with solely because modification has been made. - -If you convey an object code work under this section in, or with, or specifically for use in, a User Product, and the conveying occurs as part of a transaction in which the right of possession and use of the User Product is transferred to the recipient in perpetuity or for a fixed term (regardless of how the transaction is characterized), the Corresponding Source conveyed under this section must be accompanied by the Installation Information. But this requirement does not apply if neither you nor any third party retains the ability to install modified object code on the User Product (for example, the work has been installed in ROM). - -The requirement to provide Installation Information does not include a requirement to continue to provide support service, warranty, or updates for a work that has been modified or installed by the recipient, or for the User Product in which it has been modified or installed. Access to a network may be denied when the modification itself materially and adversely affects the operation of the network or violates the rules and protocols for communication across the network. - -Corresponding Source conveyed, and Installation Information provided, in accord with this section must be in a format that is publicly documented (and with an implementation available to the public in source code form), and must require no special password or key for unpacking, reading or copying. - -7. Additional Terms. -“Additional permissions” are terms that supplement the terms of this License by making exceptions from one or more of its conditions. Additional permissions that are applicable to the entire Program shall be treated as though they were included in this License, to the extent that they are valid under applicable law. If additional permissions apply only to part of the Program, that part may be used separately under those permissions, but the entire Program remains governed by this License without regard to the additional permissions. - -When you convey a copy of a covered work, you may at your option remove any additional permissions from that copy, or from any part of it. (Additional permissions may be written to require their own removal in certain cases when you modify the work.) You may place additional permissions on material, added by you to a covered work, for which you have or can give appropriate copyright permission. - -Notwithstanding any other provision of this License, for material you add to a covered work, you may (if authorized by the copyright holders of that material) supplement the terms of this License with terms: - - a) Disclaiming warranty or limiting liability differently from the terms of sections 15 and 16 of this License; or - - b) Requiring preservation of specified reasonable legal notices or author attributions in that material or in the Appropriate Legal Notices displayed by works containing it; or - - c) Prohibiting misrepresentation of the origin of that material, or requiring that modified versions of such material be marked in reasonable ways as different from the original version; or - - d) Limiting the use for publicity purposes of names of licensors or authors of the material; or - - e) Declining to grant rights under trademark law for use of some trade names, trademarks, or service marks; or - - f) Requiring indemnification of licensors and authors of that material by anyone who conveys the material (or modified versions of it) with contractual assumptions of liability to the recipient, for any liability that these contractual assumptions directly impose on those licensors and authors. - -All other non-permissive additional terms are considered “further restrictions” within the meaning of section 10. If the Program as you received it, or any part of it, contains a notice stating that it is governed by this License along with a term that is a further restriction, you may remove that term. If a license document contains a further restriction but permits relicensing or conveying under this License, you may add to a covered work material governed by the terms of that license document, provided that the further restriction does not survive such relicensing or conveying. - -If you add terms to a covered work in accord with this section, you must place, in the relevant source files, a statement of the additional terms that apply to those files, or a notice indicating where to find the applicable terms. - -Additional terms, permissive or non-permissive, may be stated in the form of a separately written license, or stated as exceptions; the above requirements apply either way. - -8. Termination. -You may not propagate or modify a covered work except as expressly provided under this License. Any attempt otherwise to propagate or modify it is void, and will automatically terminate your rights under this License (including any patent licenses granted under the third paragraph of section 11). - -However, if you cease all violation of this License, then your license from a particular copyright holder is reinstated (a) provisionally, unless and until the copyright holder explicitly and finally terminates your license, and (b) permanently, if the copyright holder fails to notify you of the violation by some reasonable means prior to 60 days after the cessation. - -Moreover, your license from a particular copyright holder is reinstated permanently if the copyright holder notifies you of the violation by some reasonable means, this is the first time you have received notice of violation of this License (for any work) from that copyright holder, and you cure the violation prior to 30 days after your receipt of the notice. - -Termination of your rights under this section does not terminate the licenses of parties who have received copies or rights from you under this License. If your rights have been terminated and not permanently reinstated, you do not qualify to receive new licenses for the same material under section 10. - -9. Acceptance Not Required for Having Copies. -You are not required to accept this License in order to receive or run a copy of the Program. Ancillary propagation of a covered work occurring solely as a consequence of using peer-to-peer transmission to receive a copy likewise does not require acceptance. However, nothing other than this License grants you permission to propagate or modify any covered work. These actions infringe copyright if you do not accept this License. Therefore, by modifying or propagating a covered work, you indicate your acceptance of this License to do so. - -10. Automatic Licensing of Downstream Recipients. -Each time you convey a covered work, the recipient automatically receives a license from the original licensors, to run, modify and propagate that work, subject to this License. You are not responsible for enforcing compliance by third parties with this License. - -An “entity transaction” is a transaction transferring control of an organization, or substantially all assets of one, or subdividing an organization, or merging organizations. If propagation of a covered work results from an entity transaction, each party to that transaction who receives a copy of the work also receives whatever licenses to the work the party's predecessor in interest had or could give under the previous paragraph, plus a right to possession of the Corresponding Source of the work from the predecessor in interest, if the predecessor has it or can get it with reasonable efforts. - -You may not impose any further restrictions on the exercise of the rights granted or affirmed under this License. For example, you may not impose a license fee, royalty, or other charge for exercise of rights granted under this License, and you may not initiate litigation (including a cross-claim or counterclaim in a lawsuit) alleging that any patent claim is infringed by making, using, selling, offering for sale, or importing the Program or any portion of it. - -11. Patents. -A “contributor” is a copyright holder who authorizes use under this License of the Program or a work on which the Program is based. The work thus licensed is called the contributor's “contributor version”. - -A contributor's “essential patent claims” are all patent claims owned or controlled by the contributor, whether already acquired or hereafter acquired, that would be infringed by some manner, permitted by this License, of making, using, or selling its contributor version, but do not include claims that would be infringed only as a consequence of further modification of the contributor version. For purposes of this definition, “control” includes the right to grant patent sublicenses in a manner consistent with the requirements of this License. - -Each contributor grants you a non-exclusive, worldwide, royalty-free patent license under the contributor's essential patent claims, to make, use, sell, offer for sale, import and otherwise run, modify and propagate the contents of its contributor version. - -In the following three paragraphs, a “patent license” is any express agreement or commitment, however denominated, not to enforce a patent (such as an express permission to practice a patent or covenant not to sue for patent infringement). To “grant” such a patent license to a party means to make such an agreement or commitment not to enforce a patent against the party. - -If you convey a covered work, knowingly relying on a patent license, and the Corresponding Source of the work is not available for anyone to copy, free of charge and under the terms of this License, through a publicly available network server or other readily accessible means, then you must either (1) cause the Corresponding Source to be so available, or (2) arrange to deprive yourself of the benefit of the patent license for this particular work, or (3) arrange, in a manner consistent with the requirements of this License, to extend the patent license to downstream recipients. “Knowingly relying” means you have actual knowledge that, but for the patent license, your conveying the covered work in a country, or your recipient's use of the covered work in a country, would infringe one or more identifiable patents in that country that you have reason to believe are valid. - -If, pursuant to or in connection with a single transaction or arrangement, you convey, or propagate by procuring conveyance of, a covered work, and grant a patent license to some of the parties receiving the covered work authorizing them to use, propagate, modify or convey a specific copy of the covered work, then the patent license you grant is automatically extended to all recipients of the covered work and works based on it. - -A patent license is “discriminatory” if it does not include within the scope of its coverage, prohibits the exercise of, or is conditioned on the non-exercise of one or more of the rights that are specifically granted under this License. You may not convey a covered work if you are a party to an arrangement with a third party that is in the business of distributing software, under which you make payment to the third party based on the extent of your activity of conveying the work, and under which the third party grants, to any of the parties who would receive the covered work from you, a discriminatory patent license (a) in connection with copies of the covered work conveyed by you (or copies made from those copies), or (b) primarily for and in connection with specific products or compilations that contain the covered work, unless you entered into that arrangement, or that patent license was granted, prior to 28 March 2007. - -Nothing in this License shall be construed as excluding or limiting any implied license or other defenses to infringement that may otherwise be available to you under applicable patent law. - -12. No Surrender of Others' Freedom. -If conditions are imposed on you (whether by court order, agreement or otherwise) that contradict the conditions of this License, they do not excuse you from the conditions of this License. If you cannot convey a covered work so as to satisfy simultaneously your obligations under this License and any other pertinent obligations, then as a consequence you may not convey it at all. For example, if you agree to terms that obligate you to collect a royalty for further conveying from those to whom you convey the Program, the only way you could satisfy both those terms and this License would be to refrain entirely from conveying the Program. - -13. Use with the GNU Affero General Public License. -Notwithstanding any other provision of this License, you have permission to link or combine any covered work with a work licensed under version 3 of the GNU Affero General Public License into a single combined work, and to convey the resulting work. The terms of this License will continue to apply to the part which is the covered work, but the special requirements of the GNU Affero General Public License, section 13, concerning interaction through a network will apply to the combination as such. - -14. Revised Versions of this License. -The Free Software Foundation may publish revised and/or new versions of the GNU General Public License from time to time. Such new versions will be similar in spirit to the present version, but may differ in detail to address new problems or concerns. - -Each version is given a distinguishing version number. If the Program specifies that a certain numbered version of the GNU General Public License “or any later version” applies to it, you have the option of following the terms and conditions either of that numbered version or of any later version published by the Free Software Foundation. If the Program does not specify a version number of the GNU General Public License, you may choose any version ever published by the Free Software Foundation. - -If the Program specifies that a proxy can decide which future versions of the GNU General Public License can be used, that proxy's public statement of acceptance of a version permanently authorizes you to choose that version for the Program. - -Later license versions may give you additional or different permissions. However, no additional obligations are imposed on any author or copyright holder as a result of your choosing to follow a later version. - -15. Disclaimer of Warranty. -THERE IS NO WARRANTY FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES PROVIDE THE PROGRAM “AS IS” WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION. - -16. Limitation of Liability. -IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MODIFIES AND/OR CONVEYS THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. - -17. Interpretation of Sections 15 and 16. -If the disclaimer of warranty and limitation of liability provided above cannot be given local legal effect according to their terms, reviewing courts shall apply local law that most closely approximates an absolute waiver of all civil liability in connection with the Program, unless a warranty or assumption of liability accompanies a copy of the Program in return for a fee. - -END OF TERMS AND CONDITIONS - -How to Apply These Terms to Your New Programs - -If you develop a new program, and you want it to be of the greatest possible use to the public, the best way to achieve this is to make it free software which everyone can redistribute and change under these terms. - -To do so, attach the following notices to the program. It is safest to attach them to the start of each source file to most effectively state the exclusion of warranty; and each file should have at least the “copyright” line and a pointer to where the full notice is found. - - - Copyright (C) - - This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. - - This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. - - You should have received a copy of the GNU General Public License along with this program. If not, see . - -Also add information on how to contact you by electronic and paper mail. - -If the program does terminal interaction, make it output a short notice like this when it starts in an interactive mode: - - Copyright (C) - This program comes with ABSOLUTELY NO WARRANTY; for details type `show w'. - This is free software, and you are welcome to redistribute it under certain conditions; type `show c' for details. - -The hypothetical commands `show w' and `show c' should show the appropriate parts of the General Public License. Of course, your program's commands might be different; for a GUI interface, you would use an “about box”. - -You should also get your employer (if you work as a programmer) or school, if any, to sign a “copyright disclaimer” for the program, if necessary. For more information on this, and how to apply and follow the GNU GPL, see . - -The GNU General Public License does not permit incorporating your program into proprietary programs. If your program is a subroutine library, you may consider it more useful to permit linking proprietary applications with the library. If this is what you want to do, use the GNU Lesser General Public License instead of this License. But first, please read . diff --git a/app/jni/src/libultraship/extern/nlohmann-json/LICENSES/MIT.txt b/app/jni/src/libultraship/extern/nlohmann-json/LICENSES/MIT.txt deleted file mode 100644 index 2071b23..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/LICENSES/MIT.txt +++ /dev/null @@ -1,9 +0,0 @@ -MIT License - -Copyright (c) - -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. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/Makefile b/app/jni/src/libultraship/extern/nlohmann-json/Makefile deleted file mode 100644 index 18b08a5..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/Makefile +++ /dev/null @@ -1,282 +0,0 @@ -.PHONY: pretty clean ChangeLog.md release - -########################################################################## -# configuration -########################################################################## - -# find GNU sed to use `-i` parameter -SED:=$(shell command -v gsed || which sed) - - -########################################################################## -# source files -########################################################################## - -# the list of sources in the include folder -SRCS=$(shell find include -type f | sort) - -# the list of sources in the tests folder -TESTS_SRCS=$(shell find tests -type f \( -name '*.hpp' -o -name '*.cpp' -o -name '*.cu' \) -not -path 'tests/thirdparty/*' -not -path 'tests/abi/include/nlohmann/*' | sort) - -# the single headers (amalgamated from the source files) -AMALGAMATED_FILE=single_include/nlohmann/json.hpp -AMALGAMATED_FWD_FILE=single_include/nlohmann/json_fwd.hpp - - -########################################################################## -# documentation of the Makefile's targets -########################################################################## - -# main target -all: - @echo "amalgamate - amalgamate files single_include/nlohmann/json{,_fwd}.hpp from the include/nlohmann sources" - @echo "ChangeLog.md - generate ChangeLog file" - @echo "check-amalgamation - check whether sources have been amalgamated" - @echo "clean - remove built files" - @echo "doctest - compile example files and check their output" - @echo "fuzz_testing - prepare fuzz testing of the JSON parser" - @echo "fuzz_testing_bson - prepare fuzz testing of the BSON parser" - @echo "fuzz_testing_cbor - prepare fuzz testing of the CBOR parser" - @echo "fuzz_testing_msgpack - prepare fuzz testing of the MessagePack parser" - @echo "fuzz_testing_ubjson - prepare fuzz testing of the UBJSON parser" - @echo "pretty - beautify code with Artistic Style" - @echo "run_benchmarks - build and run benchmarks" - - -########################################################################## -# documentation tests -########################################################################## - -# compile example files and check output -doctest: - $(MAKE) check_output -C docs - - -########################################################################## -# benchmarks -########################################################################## - -run_benchmarks: - rm -fr cmake-build-benchmarks - mkdir cmake-build-benchmarks - cd cmake-build-benchmarks ; cmake ../tests/benchmarks -GNinja -DCMAKE_BUILD_TYPE=Release - cd cmake-build-benchmarks ; ninja - cd cmake-build-benchmarks ; ./json_benchmarks - - -########################################################################## -# fuzzing -########################################################################## - -# the overall fuzz testing target -fuzz_testing: - rm -fr fuzz-testing - mkdir -p fuzz-testing fuzz-testing/testcases fuzz-testing/out - $(MAKE) parse_afl_fuzzer -C tests CXX=afl-clang++ - mv tests/parse_afl_fuzzer fuzz-testing/fuzzer - find tests/data/json_tests -size -5k -name *json | xargs -I{} cp "{}" fuzz-testing/testcases - @echo "Execute: afl-fuzz -i fuzz-testing/testcases -o fuzz-testing/out fuzz-testing/fuzzer" - -fuzz_testing_bson: - rm -fr fuzz-testing - mkdir -p fuzz-testing fuzz-testing/testcases fuzz-testing/out - $(MAKE) parse_bson_fuzzer -C tests CXX=afl-clang++ - mv tests/parse_bson_fuzzer fuzz-testing/fuzzer - find tests/data -size -5k -name *.bson | xargs -I{} cp "{}" fuzz-testing/testcases - @echo "Execute: afl-fuzz -i fuzz-testing/testcases -o fuzz-testing/out fuzz-testing/fuzzer" - -fuzz_testing_cbor: - rm -fr fuzz-testing - mkdir -p fuzz-testing fuzz-testing/testcases fuzz-testing/out - $(MAKE) parse_cbor_fuzzer -C tests CXX=afl-clang++ - mv tests/parse_cbor_fuzzer fuzz-testing/fuzzer - find tests/data -size -5k -name *.cbor | xargs -I{} cp "{}" fuzz-testing/testcases - @echo "Execute: afl-fuzz -i fuzz-testing/testcases -o fuzz-testing/out fuzz-testing/fuzzer" - -fuzz_testing_msgpack: - rm -fr fuzz-testing - mkdir -p fuzz-testing fuzz-testing/testcases fuzz-testing/out - $(MAKE) parse_msgpack_fuzzer -C tests CXX=afl-clang++ - mv tests/parse_msgpack_fuzzer fuzz-testing/fuzzer - find tests/data -size -5k -name *.msgpack | xargs -I{} cp "{}" fuzz-testing/testcases - @echo "Execute: afl-fuzz -i fuzz-testing/testcases -o fuzz-testing/out fuzz-testing/fuzzer" - -fuzz_testing_ubjson: - rm -fr fuzz-testing - mkdir -p fuzz-testing fuzz-testing/testcases fuzz-testing/out - $(MAKE) parse_ubjson_fuzzer -C tests CXX=afl-clang++ - mv tests/parse_ubjson_fuzzer fuzz-testing/fuzzer - find tests/data -size -5k -name *.ubjson | xargs -I{} cp "{}" fuzz-testing/testcases - @echo "Execute: afl-fuzz -i fuzz-testing/testcases -o fuzz-testing/out fuzz-testing/fuzzer" - -fuzzing-start: - afl-fuzz -S fuzzer1 -i fuzz-testing/testcases -o fuzz-testing/out fuzz-testing/fuzzer > /dev/null & - afl-fuzz -S fuzzer2 -i fuzz-testing/testcases -o fuzz-testing/out fuzz-testing/fuzzer > /dev/null & - afl-fuzz -S fuzzer3 -i fuzz-testing/testcases -o fuzz-testing/out fuzz-testing/fuzzer > /dev/null & - afl-fuzz -S fuzzer4 -i fuzz-testing/testcases -o fuzz-testing/out fuzz-testing/fuzzer > /dev/null & - afl-fuzz -S fuzzer5 -i fuzz-testing/testcases -o fuzz-testing/out fuzz-testing/fuzzer > /dev/null & - afl-fuzz -S fuzzer6 -i fuzz-testing/testcases -o fuzz-testing/out fuzz-testing/fuzzer > /dev/null & - afl-fuzz -S fuzzer7 -i fuzz-testing/testcases -o fuzz-testing/out fuzz-testing/fuzzer > /dev/null & - afl-fuzz -M fuzzer0 -i fuzz-testing/testcases -o fuzz-testing/out fuzz-testing/fuzzer - -fuzzing-stop: - -killall fuzzer - -killall afl-fuzz - - -########################################################################## -# Static analysis -########################################################################## - -# call PVS-Studio Analyzer -pvs_studio: - rm -fr cmake-build-pvs-studio - mkdir cmake-build-pvs-studio - cd cmake-build-pvs-studio ; cmake .. -DCMAKE_EXPORT_COMPILE_COMMANDS=On -DJSON_MultipleHeaders=ON - cd cmake-build-pvs-studio ; pvs-studio-analyzer analyze -j 10 - cd cmake-build-pvs-studio ; plog-converter -a'GA:1,2;64:1;CS' -t fullhtml PVS-Studio.log -o pvs - open cmake-build-pvs-studio/pvs/index.html - - -########################################################################## -# Code format and source amalgamation -########################################################################## - -# call the Artistic Style pretty printer on all source files -pretty: - astyle \ - --style=allman \ - --indent=spaces=4 \ - --indent-modifiers \ - --indent-switches \ - --indent-preproc-block \ - --indent-preproc-define \ - --indent-col1-comments \ - --pad-oper \ - --pad-header \ - --align-pointer=type \ - --align-reference=type \ - --add-brackets \ - --convert-tabs \ - --close-templates \ - --lineend=linux \ - --preserve-date \ - --suffix=none \ - --formatted \ - $(SRCS) $(TESTS_SRCS) $(AMALGAMATED_FILE) $(AMALGAMATED_FWD_FILE) docs/examples/*.cpp - -# call the Clang-Format on all source files -pretty_format: - for FILE in $(SRCS) $(TESTS_SRCS) $(AMALGAMATED_FILE) docs/examples/*.cpp; do echo $$FILE; clang-format -i $$FILE; done - -# create single header files and pretty print -amalgamate: $(AMALGAMATED_FILE) $(AMALGAMATED_FWD_FILE) - $(MAKE) pretty - -# call the amalgamation tool for json.hpp -$(AMALGAMATED_FILE): $(SRCS) - tools/amalgamate/amalgamate.py -c tools/amalgamate/config_json.json -s . --verbose=yes - -# call the amalgamation tool for json_fwd.hpp -$(AMALGAMATED_FWD_FILE): $(SRCS) - tools/amalgamate/amalgamate.py -c tools/amalgamate/config_json_fwd.json -s . --verbose=yes - -# check if file single_include/nlohmann/json.hpp has been amalgamated from the nlohmann sources -# Note: this target is called by Travis -check-amalgamation: - @mv $(AMALGAMATED_FILE) $(AMALGAMATED_FILE)~ - @mv $(AMALGAMATED_FWD_FILE) $(AMALGAMATED_FWD_FILE)~ - @$(MAKE) amalgamate - @diff $(AMALGAMATED_FILE) $(AMALGAMATED_FILE)~ || (echo "===================================================================\n Amalgamation required! Please read the contribution guidelines\n in file .github/CONTRIBUTING.md.\n===================================================================" ; mv $(AMALGAMATED_FILE)~ $(AMALGAMATED_FILE) ; false) - @diff $(AMALGAMATED_FWD_FILE) $(AMALGAMATED_FWD_FILE)~ || (echo "===================================================================\n Amalgamation required! Please read the contribution guidelines\n in file .github/CONTRIBUTING.md.\n===================================================================" ; mv $(AMALGAMATED_FWD_FILE)~ $(AMALGAMATED_FWD_FILE) ; false) - @mv $(AMALGAMATED_FILE)~ $(AMALGAMATED_FILE) - @mv $(AMALGAMATED_FWD_FILE)~ $(AMALGAMATED_FWD_FILE) - - -########################################################################## -# ChangeLog -########################################################################## - -# Create a ChangeLog based on the git log using the GitHub Changelog Generator -# (). - -# variable to control the diffs between the last released version and the current repository state -NEXT_VERSION ?= "unreleased" - -ChangeLog.md: - github_changelog_generator -o ChangeLog.md --user nlohmann --project json --simple-list --release-url https://github.com/nlohmann/json/releases/tag/%s --future-release $(NEXT_VERSION) - $(SED) -i 's|https://github.com/nlohmann/json/releases/tag/HEAD|https://github.com/nlohmann/json/tree/HEAD|' ChangeLog.md - $(SED) -i '2i All notable changes to this project will be documented in this file. This project adheres to [Semantic Versioning](http://semver.org/).' ChangeLog.md - - -########################################################################## -# Release files -########################################################################## - -# Create a tar.gz archive that contains sufficient files to be used as CMake project (e.g., using FetchContent). The -# archive is created according to the advices of . -json.tar.xz: - mkdir json - rsync -R $(shell find LICENSE.MIT nlohmann_json.natvis CMakeLists.txt cmake/*.in include single_include -type f) json - gtar --sort=name --mtime="@$(shell git log -1 --pretty=%ct)" --owner=0 --group=0 --numeric-owner --pax-option=exthdr.name=%d/PaxHeaders/%f,delete=atime,delete=ctime --create --file - json | xz --compress -9e --threads=2 - > json.tar.xz - rm -fr json - -# We use `-X` to make the resulting ZIP file reproducible, see -# . -include.zip: - zip -9 --recurse-paths -X include.zip $(SRCS) $(AMALGAMATED_FILE) meson.build LICENSE.MIT - -# Create the files for a release and add signatures and hashes. -release: include.zip json.tar.xz - rm -fr release_files - mkdir release_files - gpg --armor --detach-sig include.zip - gpg --armor --detach-sig $(AMALGAMATED_FILE) - gpg --armor --detach-sig $(AMALGAMATED_FWD_FILE) - gpg --armor --detach-sig json.tar.xz - cp $(AMALGAMATED_FILE) release_files - cp $(AMALGAMATED_FWD_FILE) release_files - mv $(AMALGAMATED_FILE).asc $(AMALGAMATED_FWD_FILE).asc json.tar.xz json.tar.xz.asc include.zip include.zip.asc release_files - cd release_files ; shasum -a 256 json.hpp include.zip json.tar.xz > hashes.txt - - -########################################################################## -# Maintenance -########################################################################## - -# clean up -clean: - rm -fr fuzz fuzz-testing *.dSYM tests/*.dSYM - rm -fr benchmarks/files/numbers/*.json - rm -fr cmake-build-benchmarks fuzz-testing cmake-build-pvs-studio release_files - $(MAKE) clean -Cdocs - - -########################################################################## -# Thirdparty code -########################################################################## - -update_hedley: - rm -f include/nlohmann/thirdparty/hedley/hedley.hpp include/nlohmann/thirdparty/hedley/hedley_undef.hpp - curl https://raw.githubusercontent.com/nemequ/hedley/master/hedley.h -o include/nlohmann/thirdparty/hedley/hedley.hpp - $(SED) -i 's/HEDLEY_/JSON_HEDLEY_/g' include/nlohmann/thirdparty/hedley/hedley.hpp - grep "[[:blank:]]*#[[:blank:]]*undef" include/nlohmann/thirdparty/hedley/hedley.hpp | grep -v "__" | sort | uniq | $(SED) 's/ //g' | $(SED) 's/undef/undef /g' > include/nlohmann/thirdparty/hedley/hedley_undef.hpp - $(SED) -i '1s/^/#pragma once\n\n/' include/nlohmann/thirdparty/hedley/hedley.hpp - $(SED) -i '1s/^/#pragma once\n\n/' include/nlohmann/thirdparty/hedley/hedley_undef.hpp - $(MAKE) amalgamate - -########################################################################## -# serve_header.py -########################################################################## - -serve_header: - ./tools/serve_header/serve_header.py --make $(MAKE) - -########################################################################## -# REUSE -########################################################################## - -reuse: - pipx run reuse addheader --recursive single_include include -tjson --license MIT --copyright "Niels Lohmann " --year "2013-2022" - pipx run reuse addheader $(TESTS_SRCS) --style=c -tjson_support --license MIT --copyright "Niels Lohmann " --year "2013-2022" - pipx run reuse lint diff --git a/app/jni/src/libultraship/extern/nlohmann-json/README.md b/app/jni/src/libultraship/extern/nlohmann-json/README.md deleted file mode 100644 index d74aa7b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/README.md +++ /dev/null @@ -1,1846 +0,0 @@ -[![JSON for Modern C++](docs/json.gif)](https://github.com/nlohmann/json/releases) - -[![Build Status](https://ci.appveyor.com/api/projects/status/1acb366xfyg3qybk/branch/develop?svg=true)](https://ci.appveyor.com/project/nlohmann/json) -[![Ubuntu](https://github.com/nlohmann/json/workflows/Ubuntu/badge.svg)](https://github.com/nlohmann/json/actions?query=workflow%3AUbuntu) -[![macOS](https://github.com/nlohmann/json/workflows/macOS/badge.svg)](https://github.com/nlohmann/json/actions?query=workflow%3AmacOS) -[![Windows](https://github.com/nlohmann/json/workflows/Windows/badge.svg)](https://github.com/nlohmann/json/actions?query=workflow%3AWindows) -[![Coverage Status](https://coveralls.io/repos/github/nlohmann/json/badge.svg?branch=develop)](https://coveralls.io/github/nlohmann/json?branch=develop) -[![Coverity Scan Build Status](https://scan.coverity.com/projects/5550/badge.svg)](https://scan.coverity.com/projects/nlohmann-json) -[![Codacy Badge](https://app.codacy.com/project/badge/Grade/e0d1a9d5d6fd46fcb655c4cb930bb3e8)](https://www.codacy.com/gh/nlohmann/json/dashboard?utm_source=github.com&utm_medium=referral&utm_content=nlohmann/json&utm_campaign=Badge_Grade) -[![Language grade: C/C++](https://img.shields.io/lgtm/grade/cpp/g/nlohmann/json.svg?logo=lgtm&logoWidth=18)](https://lgtm.com/projects/g/nlohmann/json/context:cpp) -[![Fuzzing Status](https://oss-fuzz-build-logs.storage.googleapis.com/badges/json.svg)](https://bugs.chromium.org/p/oss-fuzz/issues/list?sort=-opened&can=1&q=proj:json) -[![Try online](https://img.shields.io/badge/try-online-blue.svg)](https://wandbox.org/permlink/1mp10JbaANo6FUc7) -[![Documentation](https://img.shields.io/badge/docs-mkdocs-blue.svg)](https://json.nlohmann.me) -[![GitHub license](https://img.shields.io/badge/license-MIT-blue.svg)](https://raw.githubusercontent.com/nlohmann/json/master/LICENSE.MIT) -[![GitHub Releases](https://img.shields.io/github/release/nlohmann/json.svg)](https://github.com/nlohmann/json/releases) -[![Packaging status](https://repology.org/badge/tiny-repos/nlohmann-json.svg)](https://repology.org/project/nlohmann-json/versions) -[![GitHub Downloads](https://img.shields.io/github/downloads/nlohmann/json/total)](https://github.com/nlohmann/json/releases) -[![GitHub Issues](https://img.shields.io/github/issues/nlohmann/json.svg)](https://github.com/nlohmann/json/issues) -[![Average time to resolve an issue](https://isitmaintained.com/badge/resolution/nlohmann/json.svg)](https://isitmaintained.com/project/nlohmann/json "Average time to resolve an issue") -[![CII Best Practices](https://bestpractices.coreinfrastructure.org/projects/289/badge)](https://bestpractices.coreinfrastructure.org/projects/289) -[![GitHub Sponsors](https://img.shields.io/badge/GitHub-Sponsors-ff69b4)](https://github.com/sponsors/nlohmann) -[![REUSE status](https://api.reuse.software/badge/github.com/nlohmann/json)](https://api.reuse.software/info/github.com/nlohmann/json) -[![Discord](https://img.shields.io/discord/1003743314341793913)](https://discord.gg/6mrGXKvX7y) - -- [Design goals](#design-goals) -- [Sponsors](#sponsors) -- [Support](#support) ([documentation](https://json.nlohmann.me), [FAQ](https://json.nlohmann.me/home/faq/), [discussions](https://github.com/nlohmann/json/discussions), [API](https://json.nlohmann.me/api/basic_json/), [bug issues](https://github.com/nlohmann/json/issues)) -- [Examples](#examples) - - [Read JSON from a file](#read-json-from-a-file) - - [Creating `json` objects from JSON literals](#creating-json-objects-from-json-literals) - - [JSON as first-class data type](#json-as-first-class-data-type) - - [Serialization / Deserialization](#serialization--deserialization) - - [STL-like access](#stl-like-access) - - [Conversion from STL containers](#conversion-from-stl-containers) - - [JSON Pointer and JSON Patch](#json-pointer-and-json-patch) - - [JSON Merge Patch](#json-merge-patch) - - [Implicit conversions](#implicit-conversions) - - [Conversions to/from arbitrary types](#arbitrary-types-conversions) - - [Specializing enum conversion](#specializing-enum-conversion) - - [Binary formats (BSON, CBOR, MessagePack, UBJSON, and BJData)](#binary-formats-bson-cbor-messagepack-ubjson-and-bjdata) -- [Supported compilers](#supported-compilers) -- [Integration](#integration) - - [CMake](#cmake) - - [Package Managers](#package-managers) - - [Pkg-config](#pkg-config) -- [License](#license) -- [Contact](#contact) -- [Thanks](#thanks) -- [Used third-party tools](#used-third-party-tools) -- [Projects using JSON for Modern C++](#projects-using-json-for-modern-c) -- [Notes](#notes) -- [Execute unit tests](#execute-unit-tests) - -## Design goals - -There are myriads of [JSON](https://json.org) libraries out there, and each may even have its reason to exist. Our class had these design goals: - -- **Intuitive syntax**. In languages such as Python, JSON feels like a first class data type. We used all the operator magic of modern C++ to achieve the same feeling in your code. Check out the [examples below](#examples) and you'll know what I mean. - -- **Trivial integration**. Our whole code consists of a single header file [`json.hpp`](https://github.com/nlohmann/json/blob/develop/single_include/nlohmann/json.hpp). That's it. No library, no subproject, no dependencies, no complex build system. The class is written in vanilla C++11. All in all, everything should require no adjustment of your compiler flags or project settings. - -- **Serious testing**. Our code is heavily [unit-tested](https://github.com/nlohmann/json/tree/develop/tests/src) and covers [100%](https://coveralls.io/r/nlohmann/json) of the code, including all exceptional behavior. Furthermore, we checked with [Valgrind](https://valgrind.org) and the [Clang Sanitizers](https://clang.llvm.org/docs/index.html) that there are no memory leaks. [Google OSS-Fuzz](https://github.com/google/oss-fuzz/tree/master/projects/json) additionally runs fuzz tests against all parsers 24/7, effectively executing billions of tests so far. To maintain high quality, the project is following the [Core Infrastructure Initiative (CII) best practices](https://bestpractices.coreinfrastructure.org/projects/289). - -Other aspects were not so important to us: - -- **Memory efficiency**. Each JSON object has an overhead of one pointer (the maximal size of a union) and one enumeration element (1 byte). The default generalization uses the following C++ data types: `std::string` for strings, `int64_t`, `uint64_t` or `double` for numbers, `std::map` for objects, `std::vector` for arrays, and `bool` for Booleans. However, you can template the generalized class `basic_json` to your needs. - -- **Speed**. There are certainly [faster JSON libraries](https://github.com/miloyip/nativejson-benchmark#parsing-time) out there. However, if your goal is to speed up your development by adding JSON support with a single header, then this library is the way to go. If you know how to use a `std::vector` or `std::map`, you are already set. - -See the [contribution guidelines](https://github.com/nlohmann/json/blob/master/.github/CONTRIBUTING.md#please-dont) for more information. - - -## Sponsors - -You can sponsor this library at [GitHub Sponsors](https://github.com/sponsors/nlohmann). - -### :office: Corporate Sponsor - -[![](https://upload.wikimedia.org/wikipedia/commons/thumb/9/9e/Codacy-logo-black.svg/320px-Codacy-logo-black.svg.png)](https://github.com/codacy) - -### :label: Named Sponsors - -- [Michael Hartmann](https://github.com/reFX-Mike) -- [Stefan Hagen](https://github.com/sthagen) -- [Steve Sperandeo](https://github.com/homer6) -- [Robert Jefe Lindstädt](https://github.com/eljefedelrodeodeljefe) -- [Steve Wagner](https://github.com/ciroque) - -Thanks everyone! - -## Support - -:question: If you have a **question**, please check if it is already answered in the [**FAQ**](https://json.nlohmann.me/home/faq/) or the [**Q&A**](https://github.com/nlohmann/json/discussions/categories/q-a) section. If not, please [**ask a new question**](https://github.com/nlohmann/json/discussions/new) there. - -:books: If you want to **learn more** about how to use the library, check out the rest of the [**README**](#examples), have a look at [**code examples**](https://github.com/nlohmann/json/tree/develop/docs/examples), or browse through the [**help pages**](https://json.nlohmann.me). - -:construction: If you want to understand the **API** better, check out the [**API Reference**](https://json.nlohmann.me/api/basic_json/). - -:bug: If you found a **bug**, please check the [**FAQ**](https://json.nlohmann.me/home/faq/) if it is a known issue or the result of a design decision. Please also have a look at the [**issue list**](https://github.com/nlohmann/json/issues) before you [**create a new issue**](https://github.com/nlohmann/json/issues/new/choose). Please provide as much information as possible to help us understand and reproduce your issue. - -There is also a [**docset**](https://github.com/Kapeli/Dash-User-Contributions/tree/master/docsets/JSON_for_Modern_C%2B%2B) for the documentation browsers [Dash](https://kapeli.com/dash), [Velocity](https://velocity.silverlakesoftware.com), and [Zeal](https://zealdocs.org) that contains the full [documentation](https://json.nlohmann.me) as offline resource. - -## Examples - -Here are some examples to give you an idea how to use the class. - -Beside the examples below, you may want to: - -→ Check the [documentation](https://json.nlohmann.me/)\ -→ Browse the [standalone example files](https://github.com/nlohmann/json/tree/develop/docs/examples) - -Every API function (documented in the [API Documentation](https://json.nlohmann.me/api/basic_json/)) has a corresponding standalone example file. For example, the [`emplace()`](https://json.nlohmann.me/api/basic_json/emplace/) function has a matching [emplace.cpp](https://github.com/nlohmann/json/blob/develop/docs/examples/emplace.cpp) example file. - -### Read JSON from a file - -The `json` class provides an API for manipulating a JSON value. To create a `json` object by reading a JSON file: - -```cpp -#include -#include -using json = nlohmann::json; - -// ... - -std::ifstream f("example.json"); -json data = json::parse(f); -``` - -### Creating `json` objects from JSON literals - -Assume you want to create hard-code this literal JSON value in a file, as a `json` object: - -```json -{ - "pi": 3.141, - "happy": true -} -``` - -There are various options: - -```cpp -// Using (raw) string literals and json::parse -json ex1 = json::parse(R"( - { - "pi": 3.141, - "happy": true - } -)"); - -// Using user-defined (raw) string literals -using namespace nlohmann::literals; -json ex2 = R"( - { - "pi": 3.141, - "happy": true - } -)"_json; - -// Using initializer lists -json ex3 = { - {"happy", true}, - {"pi", 3.141}, -}; -``` - -### JSON as first-class data type - -Here are some examples to give you an idea how to use the class. - -Assume you want to create the JSON object - -```json -{ - "pi": 3.141, - "happy": true, - "name": "Niels", - "nothing": null, - "answer": { - "everything": 42 - }, - "list": [1, 0, 2], - "object": { - "currency": "USD", - "value": 42.99 - } -} -``` - -With this library, you could write: - -```cpp -// create an empty structure (null) -json j; - -// add a number that is stored as double (note the implicit conversion of j to an object) -j["pi"] = 3.141; - -// add a Boolean that is stored as bool -j["happy"] = true; - -// add a string that is stored as std::string -j["name"] = "Niels"; - -// add another null object by passing nullptr -j["nothing"] = nullptr; - -// add an object inside the object -j["answer"]["everything"] = 42; - -// add an array that is stored as std::vector (using an initializer list) -j["list"] = { 1, 0, 2 }; - -// add another object (using an initializer list of pairs) -j["object"] = { {"currency", "USD"}, {"value", 42.99} }; - -// instead, you could also write (which looks very similar to the JSON above) -json j2 = { - {"pi", 3.141}, - {"happy", true}, - {"name", "Niels"}, - {"nothing", nullptr}, - {"answer", { - {"everything", 42} - }}, - {"list", {1, 0, 2}}, - {"object", { - {"currency", "USD"}, - {"value", 42.99} - }} -}; -``` - -Note that in all these cases, you never need to "tell" the compiler which JSON value type you want to use. If you want to be explicit or express some edge cases, the functions [`json::array()`](https://json.nlohmann.me/api/basic_json/array/) and [`json::object()`](https://json.nlohmann.me/api/basic_json/object/) will help: - -```cpp -// a way to express the empty array [] -json empty_array_explicit = json::array(); - -// ways to express the empty object {} -json empty_object_implicit = json({}); -json empty_object_explicit = json::object(); - -// a way to express an _array_ of key/value pairs [["currency", "USD"], ["value", 42.99]] -json array_not_object = json::array({ {"currency", "USD"}, {"value", 42.99} }); -``` - -### Serialization / Deserialization - -#### To/from strings - -You can create a JSON value (deserialization) by appending `_json` to a string literal: - -```cpp -// create object from string literal -json j = "{ \"happy\": true, \"pi\": 3.141 }"_json; - -// or even nicer with a raw string literal -auto j2 = R"( - { - "happy": true, - "pi": 3.141 - } -)"_json; -``` - -Note that without appending the `_json` suffix, the passed string literal is not parsed, but just used as JSON string -value. That is, `json j = "{ \"happy\": true, \"pi\": 3.141 }"` would just store the string -`"{ "happy": true, "pi": 3.141 }"` rather than parsing the actual object. - -The string literal should be brought into scope with with `using namespace nlohmann::literals;` -(see [`json::parse()`](https://json.nlohmann.me/api/operator_literal_json/)). - -The above example can also be expressed explicitly using [`json::parse()`](https://json.nlohmann.me/api/basic_json/parse/): - -```cpp -// parse explicitly -auto j3 = json::parse(R"({"happy": true, "pi": 3.141})"); -``` - -You can also get a string representation of a JSON value (serialize): - -```cpp -// explicit conversion to string -std::string s = j.dump(); // {"happy":true,"pi":3.141} - -// serialization with pretty printing -// pass in the amount of spaces to indent -std::cout << j.dump(4) << std::endl; -// { -// "happy": true, -// "pi": 3.141 -// } -``` - -Note the difference between serialization and assignment: - -```cpp -// store a string in a JSON value -json j_string = "this is a string"; - -// retrieve the string value -auto cpp_string = j_string.get(); -// retrieve the string value (alternative when a variable already exists) -std::string cpp_string2; -j_string.get_to(cpp_string2); - -// retrieve the serialized value (explicit JSON serialization) -std::string serialized_string = j_string.dump(); - -// output of original string -std::cout << cpp_string << " == " << cpp_string2 << " == " << j_string.get() << '\n'; -// output of serialized value -std::cout << j_string << " == " << serialized_string << std::endl; -``` - -[`.dump()`](https://json.nlohmann.me/api/basic_json/dump/) returns the originally stored string value. - -Note the library only supports UTF-8. When you store strings with different encodings in the library, calling [`dump()`](https://json.nlohmann.me/api/basic_json/dump/) may throw an exception unless `json::error_handler_t::replace` or `json::error_handler_t::ignore` are used as error handlers. - -#### To/from streams (e.g. files, string streams) - -You can also use streams to serialize and deserialize: - -```cpp -// deserialize from standard input -json j; -std::cin >> j; - -// serialize to standard output -std::cout << j; - -// the setw manipulator was overloaded to set the indentation for pretty printing -std::cout << std::setw(4) << j << std::endl; -``` - -These operators work for any subclasses of `std::istream` or `std::ostream`. Here is the same example with files: - -```cpp -// read a JSON file -std::ifstream i("file.json"); -json j; -i >> j; - -// write prettified JSON to another file -std::ofstream o("pretty.json"); -o << std::setw(4) << j << std::endl; -``` - -Please note that setting the exception bit for `failbit` is inappropriate for this use case. It will result in program termination due to the `noexcept` specifier in use. - -#### Read from iterator range - -You can also parse JSON from an iterator range; that is, from any container accessible by iterators whose `value_type` is an integral type of 1, 2 or 4 bytes, which will be interpreted as UTF-8, UTF-16 and UTF-32 respectively. For instance, a `std::vector`, or a `std::list`: - -```cpp -std::vector v = {'t', 'r', 'u', 'e'}; -json j = json::parse(v.begin(), v.end()); -``` - -You may leave the iterators for the range [begin, end): - -```cpp -std::vector v = {'t', 'r', 'u', 'e'}; -json j = json::parse(v); -``` - -#### Custom data source - -Since the parse function accepts arbitrary iterator ranges, you can provide your own data sources by implementing the `LegacyInputIterator` concept. - -```cpp -struct MyContainer { - void advance(); - const char& get_current(); -}; - -struct MyIterator { - using difference_type = std::ptrdiff_t; - using value_type = char; - using pointer = const char*; - using reference = const char&; - using iterator_category = std::input_iterator_tag; - - MyIterator& operator++() { - MyContainer.advance(); - return *this; - } - - bool operator!=(const MyIterator& rhs) const { - return rhs.target != target; - } - - reference operator*() const { - return target.get_current(); - } - - MyContainer* target = nullptr; -}; - -MyIterator begin(MyContainer& tgt) { - return MyIterator{&tgt}; -} - -MyIterator end(const MyContainer&) { - return {}; -} - -void foo() { - MyContainer c; - json j = json::parse(c); -} -``` - -#### SAX interface - -The library uses a SAX-like interface with the following functions: - -```cpp -// called when null is parsed -bool null(); - -// called when a boolean is parsed; value is passed -bool boolean(bool val); - -// called when a signed or unsigned integer number is parsed; value is passed -bool number_integer(number_integer_t val); -bool number_unsigned(number_unsigned_t val); - -// called when a floating-point number is parsed; value and original string is passed -bool number_float(number_float_t val, const string_t& s); - -// called when a string is parsed; value is passed and can be safely moved away -bool string(string_t& val); -// called when a binary value is parsed; value is passed and can be safely moved away -bool binary(binary_t& val); - -// called when an object or array begins or ends, resp. The number of elements is passed (or -1 if not known) -bool start_object(std::size_t elements); -bool end_object(); -bool start_array(std::size_t elements); -bool end_array(); -// called when an object key is parsed; value is passed and can be safely moved away -bool key(string_t& val); - -// called when a parse error occurs; byte position, the last token, and an exception is passed -bool parse_error(std::size_t position, const std::string& last_token, const detail::exception& ex); -``` - -The return value of each function determines whether parsing should proceed. - -To implement your own SAX handler, proceed as follows: - -1. Implement the SAX interface in a class. You can use class `nlohmann::json_sax` as base class, but you can also use any class where the functions described above are implemented and public. -2. Create an object of your SAX interface class, e.g. `my_sax`. -3. Call `bool json::sax_parse(input, &my_sax)`; where the first parameter can be any input like a string or an input stream and the second parameter is a pointer to your SAX interface. - -Note the `sax_parse` function only returns a `bool` indicating the result of the last executed SAX event. It does not return a `json` value - it is up to you to decide what to do with the SAX events. Furthermore, no exceptions are thrown in case of a parse error - it is up to you what to do with the exception object passed to your `parse_error` implementation. Internally, the SAX interface is used for the DOM parser (class `json_sax_dom_parser`) as well as the acceptor (`json_sax_acceptor`), see file [`json_sax.hpp`](https://github.com/nlohmann/json/blob/develop/include/nlohmann/detail/input/json_sax.hpp). - -### STL-like access - -We designed the JSON class to behave just like an STL container. In fact, it satisfies the [**ReversibleContainer**](https://en.cppreference.com/w/cpp/named_req/ReversibleContainer) requirement. - -```cpp -// create an array using push_back -json j; -j.push_back("foo"); -j.push_back(1); -j.push_back(true); - -// also use emplace_back -j.emplace_back(1.78); - -// iterate the array -for (json::iterator it = j.begin(); it != j.end(); ++it) { - std::cout << *it << '\n'; -} - -// range-based for -for (auto& element : j) { - std::cout << element << '\n'; -} - -// getter/setter -const auto tmp = j[0].get(); -j[1] = 42; -bool foo = j.at(2); - -// comparison -j == R"(["foo", 1, true, 1.78])"_json; // true - -// other stuff -j.size(); // 4 entries -j.empty(); // false -j.type(); // json::value_t::array -j.clear(); // the array is empty again - -// convenience type checkers -j.is_null(); -j.is_boolean(); -j.is_number(); -j.is_object(); -j.is_array(); -j.is_string(); - -// create an object -json o; -o["foo"] = 23; -o["bar"] = false; -o["baz"] = 3.141; - -// also use emplace -o.emplace("weather", "sunny"); - -// special iterator member functions for objects -for (json::iterator it = o.begin(); it != o.end(); ++it) { - std::cout << it.key() << " : " << it.value() << "\n"; -} - -// the same code as range for -for (auto& el : o.items()) { - std::cout << el.key() << " : " << el.value() << "\n"; -} - -// even easier with structured bindings (C++17) -for (auto& [key, value] : o.items()) { - std::cout << key << " : " << value << "\n"; -} - -// find an entry -if (o.contains("foo")) { - // there is an entry with key "foo" -} - -// or via find and an iterator -if (o.find("foo") != o.end()) { - // there is an entry with key "foo" -} - -// or simpler using count() -int foo_present = o.count("foo"); // 1 -int fob_present = o.count("fob"); // 0 - -// delete an entry -o.erase("foo"); -``` - - -### Conversion from STL containers - -Any sequence container (`std::array`, `std::vector`, `std::deque`, `std::forward_list`, `std::list`) whose values can be used to construct JSON values (e.g., integers, floating point numbers, Booleans, string types, or again STL containers described in this section) can be used to create a JSON array. The same holds for similar associative containers (`std::set`, `std::multiset`, `std::unordered_set`, `std::unordered_multiset`), but in these cases the order of the elements of the array depends on how the elements are ordered in the respective STL container. - -```cpp -std::vector c_vector {1, 2, 3, 4}; -json j_vec(c_vector); -// [1, 2, 3, 4] - -std::deque c_deque {1.2, 2.3, 3.4, 5.6}; -json j_deque(c_deque); -// [1.2, 2.3, 3.4, 5.6] - -std::list c_list {true, true, false, true}; -json j_list(c_list); -// [true, true, false, true] - -std::forward_list c_flist {12345678909876, 23456789098765, 34567890987654, 45678909876543}; -json j_flist(c_flist); -// [12345678909876, 23456789098765, 34567890987654, 45678909876543] - -std::array c_array {{1, 2, 3, 4}}; -json j_array(c_array); -// [1, 2, 3, 4] - -std::set c_set {"one", "two", "three", "four", "one"}; -json j_set(c_set); // only one entry for "one" is used -// ["four", "one", "three", "two"] - -std::unordered_set c_uset {"one", "two", "three", "four", "one"}; -json j_uset(c_uset); // only one entry for "one" is used -// maybe ["two", "three", "four", "one"] - -std::multiset c_mset {"one", "two", "one", "four"}; -json j_mset(c_mset); // both entries for "one" are used -// maybe ["one", "two", "one", "four"] - -std::unordered_multiset c_umset {"one", "two", "one", "four"}; -json j_umset(c_umset); // both entries for "one" are used -// maybe ["one", "two", "one", "four"] -``` - -Likewise, any associative key-value containers (`std::map`, `std::multimap`, `std::unordered_map`, `std::unordered_multimap`) whose keys can construct an `std::string` and whose values can be used to construct JSON values (see examples above) can be used to create a JSON object. Note that in case of multimaps only one key is used in the JSON object and the value depends on the internal order of the STL container. - -```cpp -std::map c_map { {"one", 1}, {"two", 2}, {"three", 3} }; -json j_map(c_map); -// {"one": 1, "three": 3, "two": 2 } - -std::unordered_map c_umap { {"one", 1.2}, {"two", 2.3}, {"three", 3.4} }; -json j_umap(c_umap); -// {"one": 1.2, "two": 2.3, "three": 3.4} - -std::multimap c_mmap { {"one", true}, {"two", true}, {"three", false}, {"three", true} }; -json j_mmap(c_mmap); // only one entry for key "three" is used -// maybe {"one": true, "two": true, "three": true} - -std::unordered_multimap c_ummap { {"one", true}, {"two", true}, {"three", false}, {"three", true} }; -json j_ummap(c_ummap); // only one entry for key "three" is used -// maybe {"one": true, "two": true, "three": true} -``` - -### JSON Pointer and JSON Patch - -The library supports **JSON Pointer** ([RFC 6901](https://tools.ietf.org/html/rfc6901)) as alternative means to address structured values. On top of this, **JSON Patch** ([RFC 6902](https://tools.ietf.org/html/rfc6902)) allows describing differences between two JSON values - effectively allowing patch and diff operations known from Unix. - -```cpp -// a JSON value -json j_original = R"({ - "baz": ["one", "two", "three"], - "foo": "bar" -})"_json; - -// access members with a JSON pointer (RFC 6901) -j_original["/baz/1"_json_pointer]; -// "two" - -// a JSON patch (RFC 6902) -json j_patch = R"([ - { "op": "replace", "path": "/baz", "value": "boo" }, - { "op": "add", "path": "/hello", "value": ["world"] }, - { "op": "remove", "path": "/foo"} -])"_json; - -// apply the patch -json j_result = j_original.patch(j_patch); -// { -// "baz": "boo", -// "hello": ["world"] -// } - -// calculate a JSON patch from two JSON values -json::diff(j_result, j_original); -// [ -// { "op":" replace", "path": "/baz", "value": ["one", "two", "three"] }, -// { "op": "remove","path": "/hello" }, -// { "op": "add", "path": "/foo", "value": "bar" } -// ] -``` - -### JSON Merge Patch - -The library supports **JSON Merge Patch** ([RFC 7386](https://tools.ietf.org/html/rfc7386)) as a patch format. Instead of using JSON Pointer (see above) to specify values to be manipulated, it describes the changes using a syntax that closely mimics the document being modified. - -```cpp -// a JSON value -json j_document = R"({ - "a": "b", - "c": { - "d": "e", - "f": "g" - } -})"_json; - -// a patch -json j_patch = R"({ - "a":"z", - "c": { - "f": null - } -})"_json; - -// apply the patch -j_document.merge_patch(j_patch); -// { -// "a": "z", -// "c": { -// "d": "e" -// } -// } -``` - -### Implicit conversions - -Supported types can be implicitly converted to JSON values. - -It is recommended to **NOT USE** implicit conversions **FROM** a JSON value. -You can find more details about this recommendation [here](https://www.github.com/nlohmann/json/issues/958). -You can switch off implicit conversions by defining `JSON_USE_IMPLICIT_CONVERSIONS` to `0` before including the `json.hpp` header. When using CMake, you can also achieve this by setting the option `JSON_ImplicitConversions` to `OFF`. - -```cpp -// strings -std::string s1 = "Hello, world!"; -json js = s1; -auto s2 = js.get(); -// NOT RECOMMENDED -std::string s3 = js; -std::string s4; -s4 = js; - -// Booleans -bool b1 = true; -json jb = b1; -auto b2 = jb.get(); -// NOT RECOMMENDED -bool b3 = jb; -bool b4; -b4 = jb; - -// numbers -int i = 42; -json jn = i; -auto f = jn.get(); -// NOT RECOMMENDED -double f2 = jb; -double f3; -f3 = jb; - -// etc. -``` - -Note that `char` types are not automatically converted to JSON strings, but to integer numbers. A conversion to a string must be specified explicitly: - -```cpp -char ch = 'A'; // ASCII value 65 -json j_default = ch; // stores integer number 65 -json j_string = std::string(1, ch); // stores string "A" -``` - -### Arbitrary types conversions - -Every type can be serialized in JSON, not just STL containers and scalar types. Usually, you would do something along those lines: - -```cpp -namespace ns { - // a simple struct to model a person - struct person { - std::string name; - std::string address; - int age; - }; -} - -ns::person p = {"Ned Flanders", "744 Evergreen Terrace", 60}; - -// convert to JSON: copy each value into the JSON object -json j; -j["name"] = p.name; -j["address"] = p.address; -j["age"] = p.age; - -// ... - -// convert from JSON: copy each value from the JSON object -ns::person p { - j["name"].get(), - j["address"].get(), - j["age"].get() -}; -``` - -It works, but that's quite a lot of boilerplate... Fortunately, there's a better way: - -```cpp -// create a person -ns::person p {"Ned Flanders", "744 Evergreen Terrace", 60}; - -// conversion: person -> json -json j = p; - -std::cout << j << std::endl; -// {"address":"744 Evergreen Terrace","age":60,"name":"Ned Flanders"} - -// conversion: json -> person -auto p2 = j.get(); - -// that's it -assert(p == p2); -``` - -#### Basic usage - -To make this work with one of your types, you only need to provide two functions: - -```cpp -using json = nlohmann::json; - -namespace ns { - void to_json(json& j, const person& p) { - j = json{{"name", p.name}, {"address", p.address}, {"age", p.age}}; - } - - void from_json(const json& j, person& p) { - j.at("name").get_to(p.name); - j.at("address").get_to(p.address); - j.at("age").get_to(p.age); - } -} // namespace ns -``` - -That's all! When calling the `json` constructor with your type, your custom `to_json` method will be automatically called. -Likewise, when calling `get()` or `get_to(your_type&)`, the `from_json` method will be called. - -Some important things: - -* Those methods **MUST** be in your type's namespace (which can be the global namespace), or the library will not be able to locate them (in this example, they are in namespace `ns`, where `person` is defined). -* Those methods **MUST** be available (e.g., proper headers must be included) everywhere you use these conversions. Look at [issue 1108](https://github.com/nlohmann/json/issues/1108) for errors that may occur otherwise. -* When using `get()`, `your_type` **MUST** be [DefaultConstructible](https://en.cppreference.com/w/cpp/named_req/DefaultConstructible). (There is a way to bypass this requirement described later.) -* In function `from_json`, use function [`at()`](https://json.nlohmann.me/api/basic_json/at/) to access the object values rather than `operator[]`. In case a key does not exist, `at` throws an exception that you can handle, whereas `operator[]` exhibits undefined behavior. -* You do not need to add serializers or deserializers for STL types like `std::vector`: the library already implements these. - -#### Simplify your life with macros - -If you just want to serialize/deserialize some structs, the `to_json`/`from_json` functions can be a lot of boilerplate. - -There are two macros to make your life easier as long as you (1) want to use a JSON object as serialization and (2) want to use the member variable names as object keys in that object: - -- `NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE(name, member1, member2, ...)` is to be defined inside the namespace of the class/struct to create code for. -- `NLOHMANN_DEFINE_TYPE_INTRUSIVE(name, member1, member2, ...)` is to be defined inside the class/struct to create code for. This macro can also access private members. - -In both macros, the first parameter is the name of the class/struct, and all remaining parameters name the members. - -##### Examples - -The `to_json`/`from_json` functions for the `person` struct above can be created with: - -```cpp -namespace ns { - NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE(person, name, address, age) -} -``` - -Here is an example with private members, where `NLOHMANN_DEFINE_TYPE_INTRUSIVE` is needed: - -```cpp -namespace ns { - class address { - private: - std::string street; - int housenumber; - int postcode; - - public: - NLOHMANN_DEFINE_TYPE_INTRUSIVE(address, street, housenumber, postcode) - }; -} -``` - -#### How do I convert third-party types? - -This requires a bit more advanced technique. But first, let's see how this conversion mechanism works: - -The library uses **JSON Serializers** to convert types to json. -The default serializer for `nlohmann::json` is `nlohmann::adl_serializer` (ADL means [Argument-Dependent Lookup](https://en.cppreference.com/w/cpp/language/adl)). - -It is implemented like this (simplified): - -```cpp -template -struct adl_serializer { - static void to_json(json& j, const T& value) { - // calls the "to_json" method in T's namespace - } - - static void from_json(const json& j, T& value) { - // same thing, but with the "from_json" method - } -}; -``` - -This serializer works fine when you have control over the type's namespace. However, what about `boost::optional` or `std::filesystem::path` (C++17)? Hijacking the `boost` namespace is pretty bad, and it's illegal to add something other than template specializations to `std`... - -To solve this, you need to add a specialization of `adl_serializer` to the `nlohmann` namespace, here's an example: - -```cpp -// partial specialization (full specialization works too) -namespace nlohmann { - template - struct adl_serializer> { - static void to_json(json& j, const boost::optional& opt) { - if (opt == boost::none) { - j = nullptr; - } else { - j = *opt; // this will call adl_serializer::to_json which will - // find the free function to_json in T's namespace! - } - } - - static void from_json(const json& j, boost::optional& opt) { - if (j.is_null()) { - opt = boost::none; - } else { - opt = j.get(); // same as above, but with - // adl_serializer::from_json - } - } - }; -} -``` - -#### How can I use `get()` for non-default constructible/non-copyable types? - -There is a way, if your type is [MoveConstructible](https://en.cppreference.com/w/cpp/named_req/MoveConstructible). You will need to specialize the `adl_serializer` as well, but with a special `from_json` overload: - -```cpp -struct move_only_type { - move_only_type() = delete; - move_only_type(int ii): i(ii) {} - move_only_type(const move_only_type&) = delete; - move_only_type(move_only_type&&) = default; - - int i; -}; - -namespace nlohmann { - template <> - struct adl_serializer { - // note: the return type is no longer 'void', and the method only takes - // one argument - static move_only_type from_json(const json& j) { - return {j.get()}; - } - - // Here's the catch! You must provide a to_json method! Otherwise, you - // will not be able to convert move_only_type to json, since you fully - // specialized adl_serializer on that type - static void to_json(json& j, move_only_type t) { - j = t.i; - } - }; -} -``` - -#### Can I write my own serializer? (Advanced use) - -Yes. You might want to take a look at [`unit-udt.cpp`](https://github.com/nlohmann/json/blob/develop/tests/src/unit-udt.cpp) in the test suite, to see a few examples. - -If you write your own serializer, you'll need to do a few things: - -- use a different `basic_json` alias than `nlohmann::json` (the last template parameter of `basic_json` is the `JSONSerializer`) -- use your `basic_json` alias (or a template parameter) in all your `to_json`/`from_json` methods -- use `nlohmann::to_json` and `nlohmann::from_json` when you need ADL - -Here is an example, without simplifications, that only accepts types with a size <= 32, and uses ADL. - -```cpp -// You should use void as a second template argument -// if you don't need compile-time checks on T -template::type> -struct less_than_32_serializer { - template - static void to_json(BasicJsonType& j, T value) { - // we want to use ADL, and call the correct to_json overload - using nlohmann::to_json; // this method is called by adl_serializer, - // this is where the magic happens - to_json(j, value); - } - - template - static void from_json(const BasicJsonType& j, T& value) { - // same thing here - using nlohmann::from_json; - from_json(j, value); - } -}; -``` - -Be **very** careful when reimplementing your serializer, you can stack overflow if you don't pay attention: - -```cpp -template -struct bad_serializer -{ - template - static void to_json(BasicJsonType& j, const T& value) { - // this calls BasicJsonType::json_serializer::to_json(j, value); - // if BasicJsonType::json_serializer == bad_serializer ... oops! - j = value; - } - - template - static void to_json(const BasicJsonType& j, T& value) { - // this calls BasicJsonType::json_serializer::from_json(j, value); - // if BasicJsonType::json_serializer == bad_serializer ... oops! - value = j.template get(); // oops! - } -}; -``` - -### Specializing enum conversion - -By default, enum values are serialized to JSON as integers. In some cases this could result in undesired behavior. If an enum is modified or re-ordered after data has been serialized to JSON, the later de-serialized JSON data may be undefined or a different enum value than was originally intended. - -It is possible to more precisely specify how a given enum is mapped to and from JSON as shown below: - -```cpp -// example enum type declaration -enum TaskState { - TS_STOPPED, - TS_RUNNING, - TS_COMPLETED, - TS_INVALID=-1, -}; - -// map TaskState values to JSON as strings -NLOHMANN_JSON_SERIALIZE_ENUM( TaskState, { - {TS_INVALID, nullptr}, - {TS_STOPPED, "stopped"}, - {TS_RUNNING, "running"}, - {TS_COMPLETED, "completed"}, -}) -``` - -The `NLOHMANN_JSON_SERIALIZE_ENUM()` macro declares a set of `to_json()` / `from_json()` functions for type `TaskState` while avoiding repetition and boilerplate serialization code. - -**Usage:** - -```cpp -// enum to JSON as string -json j = TS_STOPPED; -assert(j == "stopped"); - -// json string to enum -json j3 = "running"; -assert(j3.get() == TS_RUNNING); - -// undefined json value to enum (where the first map entry above is the default) -json jPi = 3.14; -assert(jPi.get() == TS_INVALID ); -``` - -Just as in [Arbitrary Type Conversions](#arbitrary-types-conversions) above, -- `NLOHMANN_JSON_SERIALIZE_ENUM()` MUST be declared in your enum type's namespace (which can be the global namespace), or the library will not be able to locate it, and it will default to integer serialization. -- It MUST be available (e.g., proper headers must be included) everywhere you use the conversions. - -Other Important points: -- When using `get()`, undefined JSON values will default to the first pair specified in your map. Select this default pair carefully. -- If an enum or JSON value is specified more than once in your map, the first matching occurrence from the top of the map will be returned when converting to or from JSON. - -### Binary formats (BSON, CBOR, MessagePack, UBJSON, and BJData) - -Though JSON is a ubiquitous data format, it is not a very compact format suitable for data exchange, for instance over a network. Hence, the library supports [BSON](https://bsonspec.org) (Binary JSON), [CBOR](https://cbor.io) (Concise Binary Object Representation), [MessagePack](https://msgpack.org), [UBJSON](https://ubjson.org) (Universal Binary JSON Specification) and [BJData](https://neurojson.org/bjdata) (Binary JData) to efficiently encode JSON values to byte vectors and to decode such vectors. - -```cpp -// create a JSON value -json j = R"({"compact": true, "schema": 0})"_json; - -// serialize to BSON -std::vector v_bson = json::to_bson(j); - -// 0x1B, 0x00, 0x00, 0x00, 0x08, 0x63, 0x6F, 0x6D, 0x70, 0x61, 0x63, 0x74, 0x00, 0x01, 0x10, 0x73, 0x63, 0x68, 0x65, 0x6D, 0x61, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 - -// roundtrip -json j_from_bson = json::from_bson(v_bson); - -// serialize to CBOR -std::vector v_cbor = json::to_cbor(j); - -// 0xA2, 0x67, 0x63, 0x6F, 0x6D, 0x70, 0x61, 0x63, 0x74, 0xF5, 0x66, 0x73, 0x63, 0x68, 0x65, 0x6D, 0x61, 0x00 - -// roundtrip -json j_from_cbor = json::from_cbor(v_cbor); - -// serialize to MessagePack -std::vector v_msgpack = json::to_msgpack(j); - -// 0x82, 0xA7, 0x63, 0x6F, 0x6D, 0x70, 0x61, 0x63, 0x74, 0xC3, 0xA6, 0x73, 0x63, 0x68, 0x65, 0x6D, 0x61, 0x00 - -// roundtrip -json j_from_msgpack = json::from_msgpack(v_msgpack); - -// serialize to UBJSON -std::vector v_ubjson = json::to_ubjson(j); - -// 0x7B, 0x69, 0x07, 0x63, 0x6F, 0x6D, 0x70, 0x61, 0x63, 0x74, 0x54, 0x69, 0x06, 0x73, 0x63, 0x68, 0x65, 0x6D, 0x61, 0x69, 0x00, 0x7D - -// roundtrip -json j_from_ubjson = json::from_ubjson(v_ubjson); -``` - -The library also supports binary types from BSON, CBOR (byte strings), and MessagePack (bin, ext, fixext). They are stored by default as `std::vector` to be processed outside the library. - -```cpp -// CBOR byte string with payload 0xCAFE -std::vector v = {0x42, 0xCA, 0xFE}; - -// read value -json j = json::from_cbor(v); - -// the JSON value has type binary -j.is_binary(); // true - -// get reference to stored binary value -auto& binary = j.get_binary(); - -// the binary value has no subtype (CBOR has no binary subtypes) -binary.has_subtype(); // false - -// access std::vector member functions -binary.size(); // 2 -binary[0]; // 0xCA -binary[1]; // 0xFE - -// set subtype to 0x10 -binary.set_subtype(0x10); - -// serialize to MessagePack -auto cbor = json::to_msgpack(j); // 0xD5 (fixext2), 0x10, 0xCA, 0xFE -``` - - -## Supported compilers - -Though it's 2022 already, the support for C++11 is still a bit sparse. Currently, the following compilers are known to work: - -- GCC 4.8 - 12.0 (and possibly later) -- Clang 3.4 - 15.0 (and possibly later) -- Apple Clang 9.1 - 13.1 (and possibly later) -- Intel C++ Compiler 17.0.2 (and possibly later) -- Nvidia CUDA Compiler 11.0.221 (and possibly later) -- Microsoft Visual C++ 2015 / Build Tools 14.0.25123.0 (and possibly later) -- Microsoft Visual C++ 2017 / Build Tools 15.5.180.51428 (and possibly later) -- Microsoft Visual C++ 2019 / Build Tools 16.3.1+1def00d3d (and possibly later) -- Microsoft Visual C++ 2022 / Build Tools 19.30.30709.0 (and possibly later) - -I would be happy to learn about other compilers/versions. - -Please note: - -- GCC 4.8 has a bug [57824](https://gcc.gnu.org/bugzilla/show_bug.cgi?id=57824)): multiline raw strings cannot be the arguments to macros. Don't use multiline raw strings directly in macros with this compiler. -- Android defaults to using very old compilers and C++ libraries. To fix this, add the following to your `Application.mk`. This will switch to the LLVM C++ library, the Clang compiler, and enable C++11 and other features disabled by default. - - ``` - APP_STL := c++_shared - NDK_TOOLCHAIN_VERSION := clang3.6 - APP_CPPFLAGS += -frtti -fexceptions - ``` - - The code compiles successfully with [Android NDK](https://developer.android.com/ndk/index.html?hl=ml), Revision 9 - 11 (and possibly later) and [CrystaX's Android NDK](https://www.crystax.net/en/android/ndk) version 10. - -- For GCC running on MinGW or Android SDK, the error `'to_string' is not a member of 'std'` (or similarly, for `strtod` or `strtof`) may occur. Note this is not an issue with the code, but rather with the compiler itself. On Android, see above to build with a newer environment. For MinGW, please refer to [this site](https://tehsausage.com/mingw-to-string) and [this discussion](https://github.com/nlohmann/json/issues/136) for information on how to fix this bug. For Android NDK using `APP_STL := gnustl_static`, please refer to [this discussion](https://github.com/nlohmann/json/issues/219). - -- Unsupported versions of GCC and Clang are rejected by `#error` directives. This can be switched off by defining `JSON_SKIP_UNSUPPORTED_COMPILER_CHECK`. Note that you can expect no support in this case. - -The following compilers are currently used in continuous integration at [AppVeyor](https://ci.appveyor.com/project/nlohmann/json), [Drone CI](https://cloud.drone.io/nlohmann/json), and [GitHub Actions](https://github.com/nlohmann/json/actions): - -| Compiler | Operating System | CI Provider | -|--------------------------------------------------------------------------------------------------------|--------------------|----------------| -| Apple Clang 11.0.3 (clang-1103.0.32.62); Xcode 11.7 | macOS 11.6.8 | GitHub Actions | -| Apple Clang 12.0.0 (clang-1200.0.32.29); Xcode 12.4 | macOS 11.6.8 | GitHub Actions | -| Apple Clang 12.0.5 (clang-1205.0.22.11); Xcode 12.5.1 | macOS 11.6.8 | GitHub Actions | -| Apple Clang 13.0.0 (clang-1300.0.29.3); Xcode 13.0 | macOS 11.6.8 | GitHub Actions | -| Apple Clang 13.0.0 (clang-1300.0.29.3); Xcode 13.1 | macOS 12.4 | GitHub Actions | -| Apple Clang 13.0.0 (clang-1300.0.29.30); Xcode 13.2.1 | macOS 12.4 | GitHub Actions | -| Apple Clang 13.1.6 (clang-1316.0.21.2.3); Xcode 13.3.1 | macOS 12.4 | GitHub Actions | -| Apple Clang 13.1.6 (clang-1316.0.21.2.5); Xcode 13.4.1 | macOS 12.4 | GitHub Actions | -| Clang 3.5.2 (3.5.2-3ubuntu1) | Ubuntu 20.04.3 LTS | GitHub Actions | -| Clang 3.6.2 (3.6.2-3ubuntu2) | Ubuntu 20.04.3 LTS | GitHub Actions | -| Clang 3.7.1 (3.7.1-2ubuntu2) | Ubuntu 20.04.3 LTS | GitHub Actions | -| Clang 3.8.0 (3.8.0-2ubuntu4) | Ubuntu 20.04.3 LTS | GitHub Actions | -| Clang 3.9.1 (3.9.1-4ubuntu3\~16.04.2) | Ubuntu 20.04.3 LTS | GitHub Actions | -| Clang 4.0.0 (4.0.0-1ubuntu1\~16.04.2) | Ubuntu 20.04.3 LTS | GitHub Actions | -| Clang 5.0.0 (5.0.0-3\~16.04.1) | Ubuntu 20.04.3 LTS | GitHub Actions | -| Clang 6.0.1 (6.0.1-14) | Ubuntu 20.04.3 LTS | GitHub Actions | -| Clang 7.0.1 (7.0.1-12) | Ubuntu 20.04.3 LTS | GitHub Actions | -| Clang 8.0.1 (8.0.1-9) | Ubuntu 20.04.3 LTS | GitHub Actions | -| Clang 9.0.1 (9.0.1-12) | Ubuntu 20.04.3 LTS | GitHub Actions | -| Clang 10.0.0 (10.0.0-4ubuntu1) | Ubuntu 20.04.3 LTS | GitHub Actions | -| Clang 10.0.0 with GNU-like command-line | Windows-10.0.17763 | GitHub Actions | -| Clang 11.0.0 with GNU-like command-line | Windows-10.0.17763 | GitHub Actions | -| Clang 11.0.0 with MSVC-like command-line | Windows-10.0.17763 | GitHub Actions | -| Clang 11.0.0 (11.0.0-2~ubuntu20.04.1) | Ubuntu 20.04.3 LTS | GitHub Actions | -| Clang 12.0.0 (12.0.0-3ubuntu1~20.04.3) | Ubuntu 20.04.3 LTS | GitHub Actions | -| Clang 13.0.1 (13.0.1-++20211015123032+cf15ccdeb6d5-1exp120211015003613.5) | Ubuntu 20.04.3 LTS | GitHub Actions | -| Clang 14.0.5-++20220603124341+2f0a69c32a4c-1~exp1~20220603124352.149 | Ubuntu 20.04.3 LTS | GitHub Actions | -| Clang 15.0.0 (15.0.0-++20220530052901+b7d2b160c3ba-1~exp1~20220530172952.268) | Ubuntu 20.04.3 LTS | GitHub Actions | -| GCC 4.8.5 (Ubuntu 4.8.5-4ubuntu2) | Ubuntu 20.04.3 LTS | GitHub Actions | -| GCC 4.9.3 (Ubuntu 4.9.3-13ubuntu2) | Ubuntu 20.04.3 LTS | GitHub Actions | -| GCC 5.4.0 (Ubuntu 5.4.0-6ubuntu1~16.04.12) | Ubuntu 20.04.3 LTS | GitHub Actions | -| GCC 6.4.0 (Ubuntu 6.4.0-17ubuntu1) | Ubuntu 20.04.3 LTS | GitHub Actions | -| GCC 7.5.0 (Ubuntu 7.5.0-6ubuntu2) | Ubuntu 20.04.3 LTS | GitHub Actions | -| GCC 8.1.0 (i686-posix-dwarf-rev0, Built by MinGW-W64 project) | Windows-10.0.17763 | GitHub Actions | -| GCC 8.1.0 (x86_64-posix-seh-rev0, Built by MinGW-W64 project) | Windows-10.0.17763 | GitHub Actions | -| GCC 8.4.0 (Ubuntu 8.4.0-3ubuntu2) | Ubuntu 20.04.3 LTS | GitHub Actions | -| GCC 9.3.0 (Ubuntu 9.3.0-17ubuntu1~20.04) | Ubuntu 20.04.3 LTS | GitHub Actions | -| GCC 10.2.0 (Ubuntu 10.2.0-5ubuntu1~20.04) | Ubuntu 20.04.3 LTS | GitHub Actions | -| GCC 11.1.0 | Ubuntu (aarch64) | Drone CI | -| GCC 11.1.0 (Ubuntu 11.1.0-1ubuntu1~20.04) | Ubuntu 20.04.3 LTS | GitHub Actions | -| GCC 13.0.0 13.0.0 20220605 (experimental) | Ubuntu 20.04.3 LTS | GitHub Actions | -| Intel C++ Compiler 2021.5.0.20211109 | Ubuntu 20.04.3 LTS | GitHub Actions | -| NVCC 11.0.221 | Ubuntu 20.04.3 LTS | GitHub Actions | -| Visual Studio 14 2015 MSVC 19.0.24241.7 (Build Engine version 14.0.25420.1) | Windows-6.3.9600 | AppVeyor | -| Visual Studio 15 2017 MSVC 19.16.27035.0 (Build Engine version 15.9.21+g9802d43bc3 for .NET Framework) | Windows-10.0.14393 | AppVeyor | -| Visual Studio 16 2019 MSVC 19.28.29912.0 (Build Engine version 16.9.0+57a23d249 for .NET Framework) | Windows-10.0.17763 | GitHub Actions | -| Visual Studio 16 2019 MSVC 19.28.29912.0 (Build Engine version 16.9.0+57a23d249 for .NET Framework) | Windows-10.0.17763 | AppVeyor | -| Visual Studio 17 2022 MSVC 19.30.30709.0 (Build Engine version 17.0.31804.368 for .NET Framework) | Windows-10.0.20348 | GitHub Actions | - - -## Integration - -[`json.hpp`](https://github.com/nlohmann/json/blob/develop/single_include/nlohmann/json.hpp) is the single required file in `single_include/nlohmann` or [released here](https://github.com/nlohmann/json/releases). You need to add - -```cpp -#include - -// for convenience -using json = nlohmann::json; -``` - -to the files you want to process JSON and set the necessary switches to enable C++11 (e.g., `-std=c++11` for GCC and Clang). - -You can further use file [`include/nlohmann/json_fwd.hpp`](https://github.com/nlohmann/json/blob/develop/include/nlohmann/json_fwd.hpp) for forward-declarations. The installation of json_fwd.hpp (as part of cmake's install step), can be achieved by setting `-DJSON_MultipleHeaders=ON`. - -### CMake - -You can also use the `nlohmann_json::nlohmann_json` interface target in CMake. This target populates the appropriate usage requirements for `INTERFACE_INCLUDE_DIRECTORIES` to point to the appropriate include directories and `INTERFACE_COMPILE_FEATURES` for the necessary C++11 flags. - -#### External - -To use this library from a CMake project, you can locate it directly with `find_package()` and use the namespaced imported target from the generated package configuration: - -```cmake -# CMakeLists.txt -find_package(nlohmann_json 3.2.0 REQUIRED) -... -add_library(foo ...) -... -target_link_libraries(foo PRIVATE nlohmann_json::nlohmann_json) -``` - -The package configuration file, `nlohmann_jsonConfig.cmake`, can be used either from an install tree or directly out of the build tree. - -#### Embedded - -To embed the library directly into an existing CMake project, place the entire source tree in a subdirectory and call `add_subdirectory()` in your `CMakeLists.txt` file: - -```cmake -# Typically you don't care so much for a third party library's tests to be -# run from your own project's code. -set(JSON_BuildTests OFF CACHE INTERNAL "") - -# If you only include this third party in PRIVATE source files, you do not -# need to install it when your main project gets installed. -# set(JSON_Install OFF CACHE INTERNAL "") - -# Don't use include(nlohmann_json/CMakeLists.txt) since that carries with it -# unintended consequences that will break the build. It's generally -# discouraged (although not necessarily well documented as such) to use -# include(...) for pulling in other CMake projects anyways. -add_subdirectory(nlohmann_json) -... -add_library(foo ...) -... -target_link_libraries(foo PRIVATE nlohmann_json::nlohmann_json) -``` - -##### Embedded (FetchContent) - -Since CMake v3.11, -[FetchContent](https://cmake.org/cmake/help/v3.11/module/FetchContent.html) can -be used to automatically download a release as a dependency at configure time. - -Example: -```cmake -include(FetchContent) - -FetchContent_Declare(json URL https://github.com/nlohmann/json/releases/download/v3.11.2/json.tar.xz) -FetchContent_MakeAvailable(json) - -target_link_libraries(foo PRIVATE nlohmann_json::nlohmann_json) -``` - -**Note**: It is recommended to use the URL approach described above which is supported as of version 3.10.0. See - for more information. - -#### Supporting Both - -To allow your project to support either an externally supplied or an embedded JSON library, you can use a pattern akin to the following: - -``` cmake -# Top level CMakeLists.txt -project(FOO) -... -option(FOO_USE_EXTERNAL_JSON "Use an external JSON library" OFF) -... -add_subdirectory(thirdparty) -... -add_library(foo ...) -... -# Note that the namespaced target will always be available regardless of the -# import method -target_link_libraries(foo PRIVATE nlohmann_json::nlohmann_json) -``` -```cmake -# thirdparty/CMakeLists.txt -... -if(FOO_USE_EXTERNAL_JSON) - find_package(nlohmann_json 3.2.0 REQUIRED) -else() - set(JSON_BuildTests OFF CACHE INTERNAL "") - add_subdirectory(nlohmann_json) -endif() -... -``` - -`thirdparty/nlohmann_json` is then a complete copy of this source tree. - -### Package Managers - -:beer: If you are using OS X and [Homebrew](https://brew.sh), just type `brew install nlohmann-json` and you're set. If you want the bleeding edge rather than the latest release, use `brew install nlohmann-json --HEAD`. See [nlohmann-json](https://formulae.brew.sh/formula/nlohmann-json) for more information. - -If you are using the [Meson Build System](https://mesonbuild.com), add this source tree as a [meson subproject](https://mesonbuild.com/Subprojects.html#using-a-subproject). You may also use the `include.zip` published in this project's [Releases](https://github.com/nlohmann/json/releases) to reduce the size of the vendored source tree. Alternatively, you can get a wrap file by downloading it from [Meson WrapDB](https://wrapdb.mesonbuild.com/nlohmann_json), or simply use `meson wrap install nlohmann_json`. Please see the meson project for any issues regarding the packaging. - -The provided `meson.build` can also be used as an alternative to cmake for installing `nlohmann_json` system-wide in which case a pkg-config file is installed. To use it, simply have your build system require the `nlohmann_json` pkg-config dependency. In Meson, it is preferred to use the [`dependency()`](https://mesonbuild.com/Reference-manual.html#dependency) object with a subproject fallback, rather than using the subproject directly. - -If you are using [Conan](https://www.conan.io/) to manage your dependencies, merely add [`nlohmann_json/x.y.z`](https://conan.io/center/nlohmann_json) to your `conanfile`'s requires, where `x.y.z` is the release version you want to use. Please file issues [here](https://github.com/conan-io/conan-center-index/issues) if you experience problems with the packages. - -If you are using [Spack](https://www.spack.io/) to manage your dependencies, you can use the [`nlohmann-json` package](https://spack.readthedocs.io/en/latest/package_list.html#nlohmann-json). Please see the [spack project](https://github.com/spack/spack) for any issues regarding the packaging. - -If you are using [hunter](https://github.com/cpp-pm/hunter) on your project for external dependencies, then you can use the [nlohmann_json package](https://hunter.readthedocs.io/en/latest/packages/pkg/nlohmann_json.html). Please see the hunter project for any issues regarding the packaging. - -If you are using [Buckaroo](https://buckaroo.pm), you can install this library's module with `buckaroo add github.com/buckaroo-pm/nlohmann-json`. Please file issues [here](https://github.com/buckaroo-pm/nlohmann-json). There is a demo repo [here](https://github.com/njlr/buckaroo-nholmann-json-example). - -If you are using [vcpkg](https://github.com/Microsoft/vcpkg/) on your project for external dependencies, then you can install the [nlohmann-json package](https://github.com/Microsoft/vcpkg/tree/master/ports/nlohmann-json) with `vcpkg install nlohmann-json` and follow the then displayed descriptions. Please see the vcpkg project for any issues regarding the packaging. - -If you are using [cget](https://cget.readthedocs.io/en/latest/), you can install the latest development version with `cget install nlohmann/json`. A specific version can be installed with `cget install nlohmann/json@v3.1.0`. Also, the multiple header version can be installed by adding the `-DJSON_MultipleHeaders=ON` flag (i.e., `cget install nlohmann/json -DJSON_MultipleHeaders=ON`). - -If you are using [CocoaPods](https://cocoapods.org), you can use the library by adding pod `"nlohmann_json", '~>3.1.2'` to your podfile (see [an example](https://bitbucket.org/benman/nlohmann_json-cocoapod/src/master/)). Please file issues [here](https://bitbucket.org/benman/nlohmann_json-cocoapod/issues?status=new&status=open). - -If you are using [NuGet](https://www.nuget.org), you can use the package [nlohmann.json](https://www.nuget.org/packages/nlohmann.json/). Please check [this extensive description](https://github.com/nlohmann/json/issues/1132#issuecomment-452250255) on how to use the package. Please file issues [here](https://github.com/hnkb/nlohmann-json-nuget/issues). - -If you are using [conda](https://conda.io/), you can use the package [nlohmann_json](https://github.com/conda-forge/nlohmann_json-feedstock) from [conda-forge](https://conda-forge.org) executing `conda install -c conda-forge nlohmann_json`. Please file issues [here](https://github.com/conda-forge/nlohmann_json-feedstock/issues). - -If you are using [MSYS2](https://www.msys2.org/), you can use the [mingw-w64-nlohmann-json](https://packages.msys2.org/base/mingw-w64-nlohmann-json) package, just type `pacman -S mingw-w64-i686-nlohmann-json` or `pacman -S mingw-w64-x86_64-nlohmann-json` for installation. Please file issues [here](https://github.com/msys2/MINGW-packages/issues/new?title=%5Bnlohmann-json%5D) if you experience problems with the packages. - -If you are using [MacPorts](https://ports.macports.org), execute `sudo port install nlohmann-json` to install the [nlohmann-json](https://ports.macports.org/port/nlohmann-json/) package. - -If you are using [`build2`](https://build2.org), you can use the [`nlohmann-json`](https://cppget.org/nlohmann-json) package from the public repository https://cppget.org or directly from the [package's sources repository](https://github.com/build2-packaging/nlohmann-json). In your project's `manifest` file, just add `depends: nlohmann-json` (probably with some [version constraints](https://build2.org/build2-toolchain/doc/build2-toolchain-intro.xhtml#guide-add-remove-deps)). If you are not familiar with using dependencies in `build2`, [please read this introduction](https://build2.org/build2-toolchain/doc/build2-toolchain-intro.xhtml). -Please file issues [here](https://github.com/build2-packaging/nlohmann-json) if you experience problems with the packages. - -If you are using [`wsjcpp`](https://wsjcpp.org), you can use the command `wsjcpp install "https://github.com/nlohmann/json:develop"` to get the latest version. Note you can change the branch ":develop" to an existing tag or another branch. - -If you are using [`CPM.cmake`](https://github.com/TheLartians/CPM.cmake), you can check this [`example`](https://github.com/TheLartians/CPM.cmake/tree/master/examples/json). After [adding CPM script](https://github.com/TheLartians/CPM.cmake#adding-cpm) to your project, implement the following snippet to your CMake: - -```cmake -CPMAddPackage( - NAME nlohmann_json - GITHUB_REPOSITORY nlohmann/json - VERSION 3.9.1) -``` - -### Pkg-config - -If you are using bare Makefiles, you can use `pkg-config` to generate the include flags that point to where the library is installed: - -```sh -pkg-config nlohmann_json --cflags -``` - -Users of the Meson build system will also be able to use a system-wide library, which will be found by `pkg-config`: - -```meson -json = dependency('nlohmann_json', required: true) -``` - - -## License - - - -The class is licensed under the [MIT License](https://opensource.org/licenses/MIT): - -Copyright © 2013-2022 [Niels Lohmann](https://nlohmann.me) - -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. - -* * * - -The class contains the UTF-8 Decoder from Bjoern Hoehrmann which is licensed under the [MIT License](https://opensource.org/licenses/MIT) (see above). Copyright © 2008-2009 [Björn Hoehrmann](https://bjoern.hoehrmann.de/) - -The class contains a slightly modified version of the Grisu2 algorithm from Florian Loitsch which is licensed under the [MIT License](https://opensource.org/licenses/MIT) (see above). Copyright © 2009 [Florian Loitsch](https://florian.loitsch.com/) - -The class contains a copy of [Hedley](https://nemequ.github.io/hedley/) from Evan Nemerson which is licensed as [CC0-1.0](https://creativecommons.org/publicdomain/zero/1.0/). - -The class contains parts of [Google Abseil](https://github.com/abseil/abseil-cpp) which is licensed under the [Apache 2.0 License](https://opensource.org/licenses/Apache-2.0). - -## Contact - -If you have questions regarding the library, I would like to invite you to [open an issue at GitHub](https://github.com/nlohmann/json/issues/new/choose). Please describe your request, problem, or question as detailed as possible, and also mention the version of the library you are using as well as the version of your compiler and operating system. Opening an issue at GitHub allows other users and contributors to this library to collaborate. For instance, I have little experience with MSVC, and most issues in this regard have been solved by a growing community. If you have a look at the [closed issues](https://github.com/nlohmann/json/issues?q=is%3Aissue+is%3Aclosed), you will see that we react quite timely in most cases. - -Only if your request would contain confidential information, please [send me an email](mailto:mail@nlohmann.me). For encrypted messages, please use [this key](https://keybase.io/nlohmann/pgp_keys.asc). - -## Security - -[Commits by Niels Lohmann](https://github.com/nlohmann/json/commits) and [releases](https://github.com/nlohmann/json/releases) are signed with this [PGP Key](https://keybase.io/nlohmann/pgp_keys.asc?fingerprint=797167ae41c0a6d9232e48457f3cea63ae251b69). - -## Thanks - -I deeply appreciate the help of the following people. - - - -1. [Teemperor](https://github.com/Teemperor) implemented CMake support and lcov integration, realized escape and Unicode handling in the string parser, and fixed the JSON serialization. -2. [elliotgoodrich](https://github.com/elliotgoodrich) fixed an issue with double deletion in the iterator classes. -3. [kirkshoop](https://github.com/kirkshoop) made the iterators of the class composable to other libraries. -4. [wancw](https://github.com/wanwc) fixed a bug that hindered the class to compile with Clang. -5. Tomas Åblad found a bug in the iterator implementation. -6. [Joshua C. Randall](https://github.com/jrandall) fixed a bug in the floating-point serialization. -7. [Aaron Burghardt](https://github.com/aburgh) implemented code to parse streams incrementally. Furthermore, he greatly improved the parser class by allowing the definition of a filter function to discard undesired elements while parsing. -8. [Daniel Kopeček](https://github.com/dkopecek) fixed a bug in the compilation with GCC 5.0. -9. [Florian Weber](https://github.com/Florianjw) fixed a bug in and improved the performance of the comparison operators. -10. [Eric Cornelius](https://github.com/EricMCornelius) pointed out a bug in the handling with NaN and infinity values. He also improved the performance of the string escaping. -11. [易思龙](https://github.com/likebeta) implemented a conversion from anonymous enums. -12. [kepkin](https://github.com/kepkin) patiently pushed forward the support for Microsoft Visual studio. -13. [gregmarr](https://github.com/gregmarr) simplified the implementation of reverse iterators and helped with numerous hints and improvements. In particular, he pushed forward the implementation of user-defined types. -14. [Caio Luppi](https://github.com/caiovlp) fixed a bug in the Unicode handling. -15. [dariomt](https://github.com/dariomt) fixed some typos in the examples. -16. [Daniel Frey](https://github.com/d-frey) cleaned up some pointers and implemented exception-safe memory allocation. -17. [Colin Hirsch](https://github.com/ColinH) took care of a small namespace issue. -18. [Huu Nguyen](https://github.com/whoshuu) correct a variable name in the documentation. -19. [Silverweed](https://github.com/silverweed) overloaded `parse()` to accept an rvalue reference. -20. [dariomt](https://github.com/dariomt) fixed a subtlety in MSVC type support and implemented the `get_ref()` function to get a reference to stored values. -21. [ZahlGraf](https://github.com/ZahlGraf) added a workaround that allows compilation using Android NDK. -22. [whackashoe](https://github.com/whackashoe) replaced a function that was marked as unsafe by Visual Studio. -23. [406345](https://github.com/406345) fixed two small warnings. -24. [Glen Fernandes](https://github.com/glenfe) noted a potential portability problem in the `has_mapped_type` function. -25. [Corbin Hughes](https://github.com/nibroc) fixed some typos in the contribution guidelines. -26. [twelsby](https://github.com/twelsby) fixed the array subscript operator, an issue that failed the MSVC build, and floating-point parsing/dumping. He further added support for unsigned integer numbers and implemented better roundtrip support for parsed numbers. -27. [Volker Diels-Grabsch](https://github.com/vog) fixed a link in the README file. -28. [msm-](https://github.com/msm-) added support for American Fuzzy Lop. -29. [Annihil](https://github.com/Annihil) fixed an example in the README file. -30. [Themercee](https://github.com/Themercee) noted a wrong URL in the README file. -31. [Lv Zheng](https://github.com/lv-zheng) fixed a namespace issue with `int64_t` and `uint64_t`. -32. [abc100m](https://github.com/abc100m) analyzed the issues with GCC 4.8 and proposed a [partial solution](https://github.com/nlohmann/json/pull/212). -33. [zewt](https://github.com/zewt) added useful notes to the README file about Android. -34. [Róbert Márki](https://github.com/robertmrk) added a fix to use move iterators and improved the integration via CMake. -35. [Chris Kitching](https://github.com/ChrisKitching) cleaned up the CMake files. -36. [Tom Needham](https://github.com/06needhamt) fixed a subtle bug with MSVC 2015 which was also proposed by [Michael K.](https://github.com/Epidal). -37. [Mário Feroldi](https://github.com/thelostt) fixed a small typo. -38. [duncanwerner](https://github.com/duncanwerner) found a really embarrassing performance regression in the 2.0.0 release. -39. [Damien](https://github.com/dtoma) fixed one of the last conversion warnings. -40. [Thomas Braun](https://github.com/t-b) fixed a warning in a test case and adjusted MSVC calls in the CI. -41. [Théo DELRIEU](https://github.com/theodelrieu) patiently and constructively oversaw the long way toward [iterator-range parsing](https://github.com/nlohmann/json/issues/290). He also implemented the magic behind the serialization/deserialization of user-defined types and split the single header file into smaller chunks. -42. [Stefan](https://github.com/5tefan) fixed a minor issue in the documentation. -43. [Vasil Dimov](https://github.com/vasild) fixed the documentation regarding conversions from `std::multiset`. -44. [ChristophJud](https://github.com/ChristophJud) overworked the CMake files to ease project inclusion. -45. [Vladimir Petrigo](https://github.com/vpetrigo) made a SFINAE hack more readable and added Visual Studio 17 to the build matrix. -46. [Denis Andrejew](https://github.com/seeekr) fixed a grammar issue in the README file. -47. [Pierre-Antoine Lacaze](https://github.com/palacaze) found a subtle bug in the `dump()` function. -48. [TurpentineDistillery](https://github.com/TurpentineDistillery) pointed to [`std::locale::classic()`](https://en.cppreference.com/w/cpp/locale/locale/classic) to avoid too much locale joggling, found some nice performance improvements in the parser, improved the benchmarking code, and realized locale-independent number parsing and printing. -49. [cgzones](https://github.com/cgzones) had an idea how to fix the Coverity scan. -50. [Jared Grubb](https://github.com/jaredgrubb) silenced a nasty documentation warning. -51. [Yixin Zhang](https://github.com/qwename) fixed an integer overflow check. -52. [Bosswestfalen](https://github.com/Bosswestfalen) merged two iterator classes into a smaller one. -53. [Daniel599](https://github.com/Daniel599) helped to get Travis execute the tests with Clang's sanitizers. -54. [Jonathan Lee](https://github.com/vjon) fixed an example in the README file. -55. [gnzlbg](https://github.com/gnzlbg) supported the implementation of user-defined types. -56. [Alexej Harm](https://github.com/qis) helped to get the user-defined types working with Visual Studio. -57. [Jared Grubb](https://github.com/jaredgrubb) supported the implementation of user-defined types. -58. [EnricoBilla](https://github.com/EnricoBilla) noted a typo in an example. -59. [Martin Hořeňovský](https://github.com/horenmar) found a way for a 2x speedup for the compilation time of the test suite. -60. [ukhegg](https://github.com/ukhegg) found proposed an improvement for the examples section. -61. [rswanson-ihi](https://github.com/rswanson-ihi) noted a typo in the README. -62. [Mihai Stan](https://github.com/stanmihai4) fixed a bug in the comparison with `nullptr`s. -63. [Tushar Maheshwari](https://github.com/tusharpm) added [cotire](https://github.com/sakra/cotire) support to speed up the compilation. -64. [TedLyngmo](https://github.com/TedLyngmo) noted a typo in the README, removed unnecessary bit arithmetic, and fixed some `-Weffc++` warnings. -65. [Krzysztof Woś](https://github.com/krzysztofwos) made exceptions more visible. -66. [ftillier](https://github.com/ftillier) fixed a compiler warning. -67. [tinloaf](https://github.com/tinloaf) made sure all pushed warnings are properly popped. -68. [Fytch](https://github.com/Fytch) found a bug in the documentation. -69. [Jay Sistar](https://github.com/Type1J) implemented a Meson build description. -70. [Henry Lee](https://github.com/HenryRLee) fixed a warning in ICC and improved the iterator implementation. -71. [Vincent Thiery](https://github.com/vthiery) maintains a package for the Conan package manager. -72. [Steffen](https://github.com/koemeet) fixed a potential issue with MSVC and `std::min`. -73. [Mike Tzou](https://github.com/Chocobo1) fixed some typos. -74. [amrcode](https://github.com/amrcode) noted a misleading documentation about comparison of floats. -75. [Oleg Endo](https://github.com/olegendo) reduced the memory consumption by replacing `` with ``. -76. [dan-42](https://github.com/dan-42) cleaned up the CMake files to simplify including/reusing of the library. -77. [Nikita Ofitserov](https://github.com/himikof) allowed for moving values from initializer lists. -78. [Greg Hurrell](https://github.com/wincent) fixed a typo. -79. [Dmitry Kukovinets](https://github.com/DmitryKuk) fixed a typo. -80. [kbthomp1](https://github.com/kbthomp1) fixed an issue related to the Intel OSX compiler. -81. [Markus Werle](https://github.com/daixtrose) fixed a typo. -82. [WebProdPP](https://github.com/WebProdPP) fixed a subtle error in a precondition check. -83. [Alex](https://github.com/leha-bot) noted an error in a code sample. -84. [Tom de Geus](https://github.com/tdegeus) reported some warnings with ICC and helped to fix them. -85. [Perry Kundert](https://github.com/pjkundert) simplified reading from input streams. -86. [Sonu Lohani](https://github.com/sonulohani) fixed a small compilation error. -87. [Jamie Seward](https://github.com/jseward) fixed all MSVC warnings. -88. [Nate Vargas](https://github.com/eld00d) added a Doxygen tag file. -89. [pvleuven](https://github.com/pvleuven) helped to fix a warning in ICC. -90. [Pavel](https://github.com/crea7or) helped to fix some warnings in MSVC. -91. [Jamie Seward](https://github.com/jseward) avoided unnecessary string copies in `find()` and `count()`. -92. [Mitja](https://github.com/Itja) fixed some typos. -93. [Jorrit Wronski](https://github.com/jowr) updated the Hunter package links. -94. [Matthias Möller](https://github.com/TinyTinni) added a `.natvis` for the MSVC debug view. -95. [bogemic](https://github.com/bogemic) fixed some C++17 deprecation warnings. -96. [Eren Okka](https://github.com/erengy) fixed some MSVC warnings. -97. [abolz](https://github.com/abolz) integrated the Grisu2 algorithm for proper floating-point formatting, allowing more roundtrip checks to succeed. -98. [Vadim Evard](https://github.com/Pipeliner) fixed a Markdown issue in the README. -99. [zerodefect](https://github.com/zerodefect) fixed a compiler warning. -100. [Kert](https://github.com/kaidokert) allowed to template the string type in the serialization and added the possibility to override the exceptional behavior. -101. [mark-99](https://github.com/mark-99) helped fixing an ICC error. -102. [Patrik Huber](https://github.com/patrikhuber) fixed links in the README file. -103. [johnfb](https://github.com/johnfb) found a bug in the implementation of CBOR's indefinite length strings. -104. [Paul Fultz II](https://github.com/pfultz2) added a note on the cget package manager. -105. [Wilson Lin](https://github.com/wla80) made the integration section of the README more concise. -106. [RalfBielig](https://github.com/ralfbielig) detected and fixed a memory leak in the parser callback. -107. [agrianius](https://github.com/agrianius) allowed to dump JSON to an alternative string type. -108. [Kevin Tonon](https://github.com/ktonon) overworked the C++11 compiler checks in CMake. -109. [Axel Huebl](https://github.com/ax3l) simplified a CMake check and added support for the [Spack package manager](https://spack.io). -110. [Carlos O'Ryan](https://github.com/coryan) fixed a typo. -111. [James Upjohn](https://github.com/jammehcow) fixed a version number in the compilers section. -112. [Chuck Atkins](https://github.com/chuckatkins) adjusted the CMake files to the CMake packaging guidelines and provided documentation for the CMake integration. -113. [Jan Schöppach](https://github.com/dns13) fixed a typo. -114. [martin-mfg](https://github.com/martin-mfg) fixed a typo. -115. [Matthias Möller](https://github.com/TinyTinni) removed the dependency from `std::stringstream`. -116. [agrianius](https://github.com/agrianius) added code to use alternative string implementations. -117. [Daniel599](https://github.com/Daniel599) allowed to use more algorithms with the `items()` function. -118. [Julius Rakow](https://github.com/jrakow) fixed the Meson include directory and fixed the links to [cppreference.com](cppreference.com). -119. [Sonu Lohani](https://github.com/sonulohani) fixed the compilation with MSVC 2015 in debug mode. -120. [grembo](https://github.com/grembo) fixed the test suite and re-enabled several test cases. -121. [Hyeon Kim](https://github.com/simnalamburt) introduced the macro `JSON_INTERNAL_CATCH` to control the exception handling inside the library. -122. [thyu](https://github.com/thyu) fixed a compiler warning. -123. [David Guthrie](https://github.com/LEgregius) fixed a subtle compilation error with Clang 3.4.2. -124. [Dennis Fischer](https://github.com/dennisfischer) allowed to call `find_package` without installing the library. -125. [Hyeon Kim](https://github.com/simnalamburt) fixed an issue with a double macro definition. -126. [Ben Berman](https://github.com/rivertam) made some error messages more understandable. -127. [zakalibit](https://github.com/zakalibit) fixed a compilation problem with the Intel C++ compiler. -128. [mandreyel](https://github.com/mandreyel) fixed a compilation problem. -129. [Kostiantyn Ponomarenko](https://github.com/koponomarenko) added version and license information to the Meson build file. -130. [Henry Schreiner](https://github.com/henryiii) added support for GCC 4.8. -131. [knilch](https://github.com/knilch0r) made sure the test suite does not stall when run in the wrong directory. -132. [Antonio Borondo](https://github.com/antonioborondo) fixed an MSVC 2017 warning. -133. [Dan Gendreau](https://github.com/dgendreau) implemented the `NLOHMANN_JSON_SERIALIZE_ENUM` macro to quickly define an enum/JSON mapping. -134. [efp](https://github.com/efp) added line and column information to parse errors. -135. [julian-becker](https://github.com/julian-becker) added BSON support. -136. [Pratik Chowdhury](https://github.com/pratikpc) added support for structured bindings. -137. [David Avedissian](https://github.com/davedissian) added support for Clang 5.0.1 (PS4 version). -138. [Jonathan Dumaresq](https://github.com/dumarjo) implemented an input adapter to read from `FILE*`. -139. [kjpus](https://github.com/kjpus) fixed a link in the documentation. -140. [Manvendra Singh](https://github.com/manu-chroma) fixed a typo in the documentation. -141. [ziggurat29](https://github.com/ziggurat29) fixed an MSVC warning. -142. [Sylvain Corlay](https://github.com/SylvainCorlay) added code to avoid an issue with MSVC. -143. [mefyl](https://github.com/mefyl) fixed a bug when JSON was parsed from an input stream. -144. [Millian Poquet](https://github.com/mpoquet) allowed to install the library via Meson. -145. [Michael Behrns-Miller](https://github.com/moodboom) found an issue with a missing namespace. -146. [Nasztanovics Ferenc](https://github.com/naszta) fixed a compilation issue with libc 2.12. -147. [Andreas Schwab](https://github.com/andreas-schwab) fixed the endian conversion. -148. [Mark-Dunning](https://github.com/Mark-Dunning) fixed a warning in MSVC. -149. [Gareth Sylvester-Bradley](https://github.com/garethsb-sony) added `operator/` for JSON Pointers. -150. [John-Mark](https://github.com/johnmarkwayve) noted a missing header. -151. [Vitaly Zaitsev](https://github.com/xvitaly) fixed compilation with GCC 9.0. -152. [Laurent Stacul](https://github.com/stac47) fixed compilation with GCC 9.0. -153. [Ivor Wanders](https://github.com/iwanders) helped to reduce the CMake requirement to version 3.1. -154. [njlr](https://github.com/njlr) updated the Buckaroo instructions. -155. [Lion](https://github.com/lieff) fixed a compilation issue with GCC 7 on CentOS. -156. [Isaac Nickaein](https://github.com/nickaein) improved the integer serialization performance and implemented the `contains()` function. -157. [past-due](https://github.com/past-due) suppressed an unfixable warning. -158. [Elvis Oric](https://github.com/elvisoric) improved Meson support. -159. [Matěj Plch](https://github.com/Afforix) fixed an example in the README. -160. [Mark Beckwith](https://github.com/wythe) fixed a typo. -161. [scinart](https://github.com/scinart) fixed bug in the serializer. -162. [Patrick Boettcher](https://github.com/pboettch) implemented `push_back()` and `pop_back()` for JSON Pointers. -163. [Bruno Oliveira](https://github.com/nicoddemus) added support for Conda. -164. [Michele Caini](https://github.com/skypjack) fixed links in the README. -165. [Hani](https://github.com/hnkb) documented how to install the library with NuGet. -166. [Mark Beckwith](https://github.com/wythe) fixed a typo. -167. [yann-morin-1998](https://github.com/yann-morin-1998) helped to reduce the CMake requirement to version 3.1. -168. [Konstantin Podsvirov](https://github.com/podsvirov) maintains a package for the MSYS2 software distro. -169. [remyabel](https://github.com/remyabel) added GNUInstallDirs to the CMake files. -170. [Taylor Howard](https://github.com/taylorhoward92) fixed a unit test. -171. [Gabe Ron](https://github.com/Macr0Nerd) implemented the `to_string` method. -172. [Watal M. Iwasaki](https://github.com/heavywatal) fixed a Clang warning. -173. [Viktor Kirilov](https://github.com/onqtam) switched the unit tests from [Catch](https://github.com/philsquared/Catch) to [doctest](https://github.com/onqtam/doctest) -174. [Juncheng E](https://github.com/ejcjason) fixed a typo. -175. [tete17](https://github.com/tete17) fixed a bug in the `contains` function. -176. [Xav83](https://github.com/Xav83) fixed some cppcheck warnings. -177. [0xflotus](https://github.com/0xflotus) fixed some typos. -178. [Christian Deneke](https://github.com/chris0x44) added a const version of `json_pointer::back`. -179. [Julien Hamaide](https://github.com/crazyjul) made the `items()` function work with custom string types. -180. [Evan Nemerson](https://github.com/nemequ) updated fixed a bug in Hedley and updated this library accordingly. -181. [Florian Pigorsch](https://github.com/flopp) fixed a lot of typos. -182. [Camille Bégué](https://github.com/cbegue) fixed an issue in the conversion from `std::pair` and `std::tuple` to `json`. -183. [Anthony VH](https://github.com/AnthonyVH) fixed a compile error in an enum deserialization. -184. [Yuriy Vountesmery](https://github.com/ua-code-dragon) noted a subtle bug in a preprocessor check. -185. [Chen](https://github.com/dota17) fixed numerous issues in the library. -186. [Antony Kellermann](https://github.com/aokellermann) added a CI step for GCC 10.1. -187. [Alex](https://github.com/gistrec) fixed an MSVC warning. -188. [Rainer](https://github.com/rvjr) proposed an improvement in the floating-point serialization in CBOR. -189. [Francois Chabot](https://github.com/FrancoisChabot) made performance improvements in the input adapters. -190. [Arthur Sonzogni](https://github.com/ArthurSonzogni) documented how the library can be included via `FetchContent`. -191. [Rimas Misevičius](https://github.com/rmisev) fixed an error message. -192. [Alexander Myasnikov](https://github.com/alexandermyasnikov) fixed some examples and a link in the README. -193. [Hubert Chathi](https://github.com/uhoreg) made CMake's version config file architecture-independent. -194. [OmnipotentEntity](https://github.com/OmnipotentEntity) implemented the binary values for CBOR, MessagePack, BSON, and UBJSON. -195. [ArtemSarmini](https://github.com/ArtemSarmini) fixed a compilation issue with GCC 10 and fixed a leak. -196. [Evgenii Sopov](https://github.com/sea-kg) integrated the library to the wsjcpp package manager. -197. [Sergey Linev](https://github.com/linev) fixed a compiler warning. -198. [Miguel Magalhães](https://github.com/magamig) fixed the year in the copyright. -199. [Gareth Sylvester-Bradley](https://github.com/garethsb-sony) fixed a compilation issue with MSVC. -200. [Alexander “weej” Jones](https://github.com/alex-weej) fixed an example in the README. -201. [Antoine Cœur](https://github.com/Coeur) fixed some typos in the documentation. -202. [jothepro](https://github.com/jothepro) updated links to the Hunter package. -203. [Dave Lee](https://github.com/kastiglione) fixed link in the README. -204. [Joël Lamotte](https://github.com/Klaim) added instruction for using Build2's package manager. -205. [Paul Jurczak](https://github.com/pauljurczak) fixed an example in the README. -206. [Sonu Lohani](https://github.com/sonulohani) fixed a warning. -207. [Carlos Gomes Martinho](https://github.com/gocarlos) updated the Conan package source. -208. [Konstantin Podsvirov](https://github.com/podsvirov) fixed the MSYS2 package documentation. -209. [Tridacnid](https://github.com/Tridacnid) improved the CMake tests. -210. [Michael](https://github.com/MBalszun) fixed MSVC warnings. -211. [Quentin Barbarat](https://github.com/quentin-dev) fixed an example in the documentation. -212. [XyFreak](https://github.com/XyFreak) fixed a compiler warning. -213. [TotalCaesar659](https://github.com/TotalCaesar659) fixed links in the README. -214. [Tanuj Garg](https://github.com/tanuj208) improved the fuzzer coverage for UBSAN input. -215. [AODQ](https://github.com/AODQ) fixed a compiler warning. -216. [jwittbrodt](https://github.com/jwittbrodt) made `NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE` inline. -217. [pfeatherstone](https://github.com/pfeatherstone) improved the upper bound of arguments of the `NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE`/`NLOHMANN_DEFINE_TYPE_INTRUSIVE` macros. -218. [Jan Procházka](https://github.com/jprochazk) fixed a bug in the CBOR parser for binary and string values. -219. [T0b1-iOS](https://github.com/T0b1-iOS) fixed a bug in the new hash implementation. -220. [Matthew Bauer](https://github.com/matthewbauer) adjusted the CBOR writer to create tags for binary subtypes. -221. [gatopeich](https://github.com/gatopeich) implemented an ordered map container for `nlohmann::ordered_json`. -222. [Érico Nogueira Rolim](https://github.com/ericonr) added support for pkg-config. -223. [KonanM](https://github.com/KonanM) proposed an implementation for the `NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE`/`NLOHMANN_DEFINE_TYPE_INTRUSIVE` macros. -224. [Guillaume Racicot](https://github.com/gracicot) implemented `string_view` support and allowed C++20 support. -225. [Alex Reinking](https://github.com/alexreinking) improved CMake support for `FetchContent`. -226. [Hannes Domani](https://github.com/ssbssa) provided a GDB pretty printer. -227. Lars Wirzenius reviewed the README file. -228. [Jun Jie](https://github.com/ongjunjie) fixed a compiler path in the CMake scripts. -229. [Ronak Buch](https://github.com/rbuch) fixed typos in the documentation. -230. [Alexander Karzhenkov](https://github.com/karzhenkov) fixed a move constructor and the Travis builds. -231. [Leonardo Lima](https://github.com/leozz37) added CPM.Cmake support. -232. [Joseph Blackman](https://github.com/jbzdarkid) fixed a warning. -233. [Yaroslav](https://github.com/YarikTH) updated doctest and implemented unit tests. -234. [Martin Stump](https://github.com/globberwops) fixed a bug in the CMake files. -235. [Jaakko Moisio](https://github.com/jasujm) fixed a bug in the input adapters. -236. [bl-ue](https://github.com/bl-ue) fixed some Markdown issues in the README file. -237. [William A. Wieselquist](https://github.com/wawiesel) fixed an example from the README. -238. [abbaswasim](https://github.com/abbaswasim) fixed an example from the README. -239. [Remy Jette](https://github.com/remyjette) fixed a warning. -240. [Fraser](https://github.com/frasermarlow) fixed the documentation. -241. [Ben Beasley](https://github.com/musicinmybrain) updated doctest. -242. [Doron Behar](https://github.com/doronbehar) fixed pkg-config.pc. -243. [raduteo](https://github.com/raduteo) fixed a warning. -244. [David Pfahler](https://github.com/theShmoo) added the possibility to compile the library without I/O support. -245. [Morten Fyhn Amundsen](https://github.com/mortenfyhn) fixed a typo. -246. [jpl-mac](https://github.com/jpl-mac) allowed to treat the library as a system header in CMake. -247. [Jason Dsouza](https://github.com/jasmcaus) fixed the indentation of the CMake file. -248. [offa](https://github.com/offa) added a link to Conan Center to the documentation. -249. [TotalCaesar659](https://github.com/TotalCaesar659) updated the links in the documentation to use HTTPS. -250. [Rafail Giavrimis](https://github.com/grafail) fixed the Google Benchmark default branch. -251. [Louis Dionne](https://github.com/ldionne) fixed a conversion operator. -252. [justanotheranonymoususer](https://github.com/justanotheranonymoususer) made the examples in the README more consistent. -253. [Finkman](https://github.com/Finkman) suppressed some `-Wfloat-equal` warnings. -254. [Ferry Huberts](https://github.com/fhuberts) fixed `-Wswitch-enum` warnings. -255. [Arseniy Terekhin](https://github.com/senyai) made the GDB pretty-printer robust against unset variable names. -256. [Amir Masoud Abdol](https://github.com/amirmasoudabdol) updated the Homebrew command as nlohmann/json is now in homebrew-core. -257. [Hallot](https://github.com/Hallot) fixed some `-Wextra-semi-stmt warnings`. -258. [Giovanni Cerretani](https://github.com/gcerretani) fixed `-Wunused` warnings on `JSON_DIAGNOSTICS`. -259. [Bogdan Popescu](https://github.com/Kapeli) hosts the [docset](https://github.com/Kapeli/Dash-User-Contributions/tree/master/docsets/JSON_for_Modern_C%2B%2B) for offline documentation viewers. -260. [Carl Smedstad](https://github.com/carlsmedstad) fixed an assertion error when using `JSON_DIAGNOSTICS`. -261. [miikka75](https://github.com/miikka75) provided an important fix to compile C++17 code with Clang 9. -262. [Maarten Becker](https://github.com/kernie) fixed a warning for shadowed variables. -263. [Cristi Vîjdea](https://github.com/axnsan12) fixed typos in the `operator[]` documentation. -264. [Alex Beregszaszi](https://github.com/axic) fixed spelling mistakes in comments. -265. [Dirk Stolle](https://github.com/striezel) fixed typos in documentation. -266. [Daniel Albuschat](https://github.com/daniel-kun) corrected the parameter name in the `parse` documentation. -267. [Prince Mendiratta](https://github.com/Prince-Mendiratta) fixed a link to the FAQ. -268. [Florian Albrechtskirchinger](https://github.com/falbrechtskirchinger) implemented `std::string_view` support for object keys and made dozens of other improvements. -269. [Qianqian Fang](https://github.com/fangq) implemented the Binary JData (BJData) format. -270. [pketelsen](https://github.com/pketelsen) added macros `NLOHMANN_DEFINE_TYPE_INTRUSIVE_WITH_DEFAULT` and `NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE_WITH_DEFAULT`. -271. [DarkZeros](https://github.com/DarkZeros) adjusted to code to not clash with Arduino defines. -272. [flagarde](https://github.com/flagarde) fixed the output of `meta()` for MSVC. -273. [Giovanni Cerretani](https://github.com/gcerretani) fixed a check for `std::filesystem`. -274. [Dimitris Apostolou](https://github.com/rex4539) fixed a typo. -275. [Ferry Huberts](https://github.com/fhuberts) fixed a typo. -276. [Michael Nosthoff](https://github.com/heinemml) fixed a typo. -277. [JungHoon Lee](https://github.com/jhnlee) fixed a typo. -278. [Faruk D.](https://github.com/fdiblen) fixed the CITATION.CFF file. -279. [Andrea Cocito](https://github.com/puffetto) added a clarification on macro usage to the documentation. -280. [Krzysiek Karbowiak](https://github.com/kkarbowiak) refactored the tests to use `CHECK_THROWS_WITH_AS`. -281. [Chaoqi Zhang](https://github.com/prncoprs) fixed a typo. -282. [ivanovmp](https://github.com/ivanovmp) fixed a whitespace error. -283. [KsaNL](https://github.com/KsaNL) fixed a build error when including ``. -284. [Andrea Pappacoda](https://github.com/Tachi107) moved `.pc` and `.cmake` files to `share` directory. -285. [Wolf Vollprecht](https://github.com/wolfv) added the `patch_inplace` function. -286. [Jake Zimmerman](https://github.com/jez) highlighted common usage patterns in the README file. -287. [NN](https://github.com/NN---) added the Visual Studio output directory to `.gitignore`. -288. [Romain Reignier](https://github.com/romainreignier) improved the performance the vector output adapter. -289. [Mike](https://github.com/Mike-Leo-Smith) fixed the `std::iterator_traits`. -290. [Richard Hozák](https://github.com/zxey) added macro `JSON_NO_ENUM` to disable default enum conversions. -291. [vakokako](https://github.com/vakokako) fixed tests when compiling with C++20. -292. [Alexander “weej” Jones](https://github.com/alexweej) fixed an example in the README. -293. [Eli Schwartz](https://github.com/eli-schwartz) added more files to the `include.zip` archive. -294. [Kevin Lu](https://github.com/kevinlul) fixed a compilation issue when typedefs with certain names were present. -295. [Trevor Hickey](https://github.com/luxe) improved the description of an example. -296. [Jef LeCompte](https://github.com/jef) updated the year in the README file. -297. [Alexandre Hamez](https://github.com/ahamez) fixed a warning. -298. [Maninderpal Badhan](https://github.com/mbadhan) fixed a typo. -299. [kevin--](https://github.com/kevin--) added a note to an example in the README file. -300. [I](https://github.com/wx257osn2) fixed a typo. -301. [Gregorio Litenstein](https://github.com/Lord-Kamina) fixed the Clang detection. -302. [Andreas Smas](https://github.com/andoma) added a Doozer badge. -303. [WanCW](https://github.com/wancw) fixed the string conversion with Clang. -304. [zhaohuaxishi](https://github.com/zhaohuaxishi) fixed a Doxygen error. -305. [emvivre](https://github.com/emvivre) removed an invalid parameter from CMake. -306. [Tobias Hermann](https://github.com/Dobiasd) fixed a link in the README file. -307. [Michael](https://github.com/traits) fixed a warning. -308. [Ryan Mulder](https://github.com/ryanjmulder) added `ensure_ascii` to the `dump` function. -309. [Muri Nicanor](https://github.com/murinicanor) fixed the `sed` discovery in the Makefile. -310. [David Avedissian](https://github.com/dgavedissian) implemented SFINAE-friendly `iterator_traits`. -311. [AQNOUCH Mohammed](https://github.com/aqnouch) fixed a typo in the README. -312. [Gareth Sylvester-Bradley](https://github.com/garethsb) added `operator/=` and `operator/` to construct JSON pointers. -313. [Michael Macnair](https://github.com/mykter) added support for afl-fuzz testing. -314. [Berkus Decker](https://github.com/berkus) fixed a typo in the README. -315. [Illia Polishchuk](https://github.com/effolkronium) improved the CMake testing. -316. [Ikko Ashimine](https://github.com/eltociear) fixed a typo. - -Thanks a lot for helping out! Please [let me know](mailto:mail@nlohmann.me) if I forgot someone. - - -## Used third-party tools - -The library itself consists of a single header file licensed under the MIT license. However, it is built, tested, documented, and whatnot using a lot of third-party tools and services. Thanks a lot! - -- [**amalgamate.py - Amalgamate C source and header files**](https://github.com/edlund/amalgamate) to create a single header file -- [**American fuzzy lop**](https://lcamtuf.coredump.cx/afl/) for fuzz testing -- [**AppVeyor**](https://www.appveyor.com) for [continuous integration](https://ci.appveyor.com/project/nlohmann/json) on Windows -- [**Artistic Style**](http://astyle.sourceforge.net) for automatic source code indentation -- [**Clang**](https://clang.llvm.org) for compilation with code sanitizers -- [**CMake**](https://cmake.org) for build automation -- [**Codacy**](https://www.codacy.com) for further [code analysis](https://www.codacy.com/app/nlohmann/json) -- [**Coveralls**](https://coveralls.io) to measure [code coverage](https://coveralls.io/github/nlohmann/json) -- [**Coverity Scan**](https://scan.coverity.com) for [static analysis](https://scan.coverity.com/projects/nlohmann-json) -- [**cppcheck**](http://cppcheck.sourceforge.net) for static analysis -- [**doctest**](https://github.com/onqtam/doctest) for the unit tests -- [**git-update-ghpages**](https://github.com/rstacruz/git-update-ghpages) to upload the documentation to gh-pages -- [**GitHub Changelog Generator**](https://github.com/skywinder/github-changelog-generator) to generate the [ChangeLog](https://github.com/nlohmann/json/blob/develop/ChangeLog.md) -- [**Google Benchmark**](https://github.com/google/benchmark) to implement the benchmarks -- [**Hedley**](https://nemequ.github.io/hedley/) to avoid re-inventing several compiler-agnostic feature macros -- [**lcov**](http://ltp.sourceforge.net/coverage/lcov.php) to process coverage information and create an HTML view -- [**libFuzzer**](https://llvm.org/docs/LibFuzzer.html) to implement fuzz testing for OSS-Fuzz -- [**Material for MkDocs**](https://squidfunk.github.io/mkdocs-material/) for the style of the documentation site -- [**MkDocs**](https://www.mkdocs.org) for the documentation site -- [**OSS-Fuzz**](https://github.com/google/oss-fuzz) for continuous fuzz testing of the library ([project repository](https://github.com/google/oss-fuzz/tree/master/projects/json)) -- [**Probot**](https://probot.github.io) for automating maintainer tasks such as closing stale issues, requesting missing information, or detecting toxic comments. -- [**Valgrind**](https://valgrind.org) to check for correct memory management - - -## Projects using JSON for Modern C++ - -The library is currently used in Apple macOS Sierra-Monterey and iOS 10-15. I am not sure what they are using the library for, but I am happy that it runs on so many devices. - - -## Notes - -### Character encoding - -The library supports **Unicode input** as follows: - -- Only **UTF-8** encoded input is supported which is the default encoding for JSON according to [RFC 8259](https://tools.ietf.org/html/rfc8259.html#section-8.1). -- `std::u16string` and `std::u32string` can be parsed, assuming UTF-16 and UTF-32 encoding, respectively. These encodings are not supported when reading from files or other input containers. -- Other encodings such as Latin-1 or ISO 8859-1 are **not** supported and will yield parse or serialization errors. -- [Unicode noncharacters](https://www.unicode.org/faq/private_use.html#nonchar1) will not be replaced by the library. -- Invalid surrogates (e.g., incomplete pairs such as `\uDEAD`) will yield parse errors. -- The strings stored in the library are UTF-8 encoded. When using the default string type (`std::string`), note that its length/size functions return the number of stored bytes rather than the number of characters or glyphs. -- When you store strings with different encodings in the library, calling [`dump()`](https://json.nlohmann.me/api/basic_json/dump/) may throw an exception unless `json::error_handler_t::replace` or `json::error_handler_t::ignore` are used as error handlers. -- To store wide strings (e.g., `std::wstring`), you need to convert them to a UTF-8 encoded `std::string` before, see [an example](https://json.nlohmann.me/home/faq/#wide-string-handling). - -### Comments in JSON - -This library does not support comments by default. It does so for three reasons: - -1. Comments are not part of the [JSON specification](https://tools.ietf.org/html/rfc8259). You may argue that `//` or `/* */` are allowed in JavaScript, but JSON is not JavaScript. -2. This was not an oversight: Douglas Crockford [wrote on this](https://plus.google.com/118095276221607585885/posts/RK8qyGVaGSr) in May 2012: - - > I removed comments from JSON because I saw people were using them to hold parsing directives, a practice which would have destroyed interoperability. I know that the lack of comments makes some people sad, but it shouldn't. - - > Suppose you are using JSON to keep configuration files, which you would like to annotate. Go ahead and insert all the comments you like. Then pipe it through JSMin before handing it to your JSON parser. - -3. It is dangerous for interoperability if some libraries would add comment support while others don't. Please check [The Harmful Consequences of the Robustness Principle](https://tools.ietf.org/html/draft-iab-protocol-maintenance-01) on this. - -However, you can pass set parameter `ignore_comments` to true in the `parse` function to ignore `//` or `/* */` comments. Comments will then be treated as whitespace. - -### Order of object keys - -By default, the library does not preserve the **insertion order of object elements**. This is standards-compliant, as the [JSON standard](https://tools.ietf.org/html/rfc8259.html) defines objects as "an unordered collection of zero or more name/value pairs". - -If you do want to preserve the insertion order, you can try the type [`nlohmann::ordered_json`](https://github.com/nlohmann/json/issues/2179). Alternatively, you can use a more sophisticated ordered map like [`tsl::ordered_map`](https://github.com/Tessil/ordered-map) ([integration](https://github.com/nlohmann/json/issues/546#issuecomment-304447518)) or [`nlohmann::fifo_map`](https://github.com/nlohmann/fifo_map) ([integration](https://github.com/nlohmann/json/issues/485#issuecomment-333652309)). - -### Memory Release - -We checked with Valgrind and the Address Sanitizer (ASAN) that there are no memory leaks. - -If you find that a parsing program with this library does not release memory, please consider the following case, and it may be unrelated to this library. - -**Your program is compiled with glibc.** There is a tunable threshold that glibc uses to decide whether to actually return memory to the system or whether to cache it for later reuse. If in your program you make lots of small allocations and those small allocations are not a contiguous block and are presumably below the threshold, then they will not get returned to the OS. -Here is a related issue [#1924](https://github.com/nlohmann/json/issues/1924). - -### Further notes - -- The code contains numerous debug **assertions** which can be switched off by defining the preprocessor macro `NDEBUG`, see the [documentation of `assert`](https://en.cppreference.com/w/cpp/error/assert). In particular, note [`operator[]`](https://json.nlohmann.me/api/basic_json/operator%5B%5D/) implements **unchecked access** for const objects: If the given key is not present, the behavior is undefined (think of a dereferenced null pointer) and yields an [assertion failure](https://github.com/nlohmann/json/issues/289) if assertions are switched on. If you are not sure whether an element in an object exists, use checked access with the [`at()` function](https://json.nlohmann.me/api/basic_json/at/). Furthermore, you can define `JSON_ASSERT(x)` to replace calls to `assert(x)`. -- As the exact number type is not defined in the [JSON specification](https://tools.ietf.org/html/rfc8259.html), this library tries to choose the best fitting C++ number type automatically. As a result, the type `double` may be used to store numbers which may yield [**floating-point exceptions**](https://github.com/nlohmann/json/issues/181) in certain rare situations if floating-point exceptions have been unmasked in the calling code. These exceptions are not caused by the library and need to be fixed in the calling code, such as by re-masking the exceptions prior to calling library functions. -- The code can be compiled without C++ **runtime type identification** features; that is, you can use the `-fno-rtti` compiler flag. -- **Exceptions** are used widely within the library. They can, however, be switched off with either using the compiler flag `-fno-exceptions` or by defining the symbol `JSON_NOEXCEPTION`. In this case, exceptions are replaced by `abort()` calls. You can further control this behavior by defining `JSON_THROW_USER` (overriding `throw`), `JSON_TRY_USER` (overriding `try`), and `JSON_CATCH_USER` (overriding `catch`). Note that `JSON_THROW_USER` should leave the current scope (e.g., by throwing or aborting), as continuing after it may yield undefined behavior. Note the explanatory [`what()`](https://en.cppreference.com/w/cpp/error/exception/what) string of exceptions is not available for MSVC if exceptions are disabled, see [#2824](https://github.com/nlohmann/json/discussions/2824). - -## Execute unit tests - -To compile and run the tests, you need to execute - -```sh -$ mkdir build -$ cd build -$ cmake .. -DJSON_BuildTests=On -$ cmake --build . -$ ctest --output-on-failure -``` - -Note that during the `ctest` stage, several JSON test files are downloaded from an [external repository](https://github.com/nlohmann/json_test_data). If policies forbid downloading artifacts during testing, you can download the files yourself and pass the directory with the test files via `-DJSON_TestDataDirectory=path` to CMake. Then, no Internet connectivity is required. See [issue #2189](https://github.com/nlohmann/json/issues/2189) for more information. - -If the test suite is not found, several test suites will fail like this: - -``` -=============================================================================== -json/tests/src/make_test_data_available.hpp:21: -TEST CASE: check test suite is downloaded - -json/tests/src/make_test_data_available.hpp:23: FATAL ERROR: REQUIRE( utils::check_testsuite_downloaded() ) is NOT correct! - values: REQUIRE( false ) - logged: Test data not found in 'json/cmake-build-debug/json_test_data'. - Please execute target 'download_test_data' before running this test suite. - See for more information. - -=============================================================================== -``` - -In case you have downloaded the library rather than checked out the code via Git, test `cmake_fetch_content_configure` will fail. Please execute `ctest -LE git_required` to skip these tests. See [issue #2189](https://github.com/nlohmann/json/issues/2189) for more information. - -Some tests change the installed files and hence make the whole process not reproducible. Please execute `ctest -LE not_reproducible` to skip these tests. See [issue #2324](https://github.com/nlohmann/json/issues/2324) for more information. - -Note you need to call `cmake -LE "not_reproducible|git_required"` to exclude both labels. See [issue #2596](https://github.com/nlohmann/json/issues/2596) for more information. - -As Intel compilers use unsafe floating point optimization by default, the unit tests may fail. Use flag [`/fp:precise`](https://software.intel.com/content/www/us/en/develop/documentation/cpp-compiler-developer-guide-and-reference/top/compiler-reference/compiler-options/compiler-option-details/floating-point-options/fp-model-fp.html) then. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/cmake/ci.cmake b/app/jni/src/libultraship/extern/nlohmann-json/cmake/ci.cmake deleted file mode 100644 index 09c1c57..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/cmake/ci.cmake +++ /dev/null @@ -1,982 +0,0 @@ -# number of parallel jobs for CTest -set(N 10) - -############################################################################### -# Needed tools. -############################################################################### - -include(FindPython3) -find_package(Python3 COMPONENTS Interpreter) - -find_program(ASTYLE_TOOL NAMES astyle) -execute_process(COMMAND ${ASTYLE_TOOL} --version OUTPUT_VARIABLE ASTYLE_TOOL_VERSION ERROR_VARIABLE ASTYLE_TOOL_VERSION) -string(REGEX MATCH "[0-9]+(\\.[0-9]+)+" ASTYLE_TOOL_VERSION "${ASTYLE_TOOL_VERSION}") -message(STATUS "🔖 Artistic Style ${ASTYLE_TOOL_VERSION} (${ASTYLE_TOOL})") - -find_program(CLANG_TOOL NAMES clang++-HEAD clang++-15 clang++-14 clang++-13 clang++-12 clang++-11 clang++) -execute_process(COMMAND ${CLANG_TOOL} --version OUTPUT_VARIABLE CLANG_TOOL_VERSION ERROR_VARIABLE CLANG_TOOL_VERSION) -string(REGEX MATCH "[0-9]+(\\.[0-9]+)+" CLANG_TOOL_VERSION "${CLANG_TOOL_VERSION}") -message(STATUS "🔖 Clang ${CLANG_TOOL_VERSION} (${CLANG_TOOL})") - -find_program(CLANG_TIDY_TOOL NAMES clang-tidy-15 clang-tidy-14 clang-tidy-13 clang-tidy-12 clang-tidy-11 clang-tidy) -execute_process(COMMAND ${CLANG_TIDY_TOOL} --version OUTPUT_VARIABLE CLANG_TIDY_TOOL_VERSION ERROR_VARIABLE CLANG_TIDY_TOOL_VERSION) -string(REGEX MATCH "[0-9]+(\\.[0-9]+)+" CLANG_TIDY_TOOL_VERSION "${CLANG_TIDY_TOOL_VERSION}") -message(STATUS "🔖 Clang-Tidy ${CLANG_TIDY_TOOL_VERSION} (${CLANG_TIDY_TOOL})") - -message(STATUS "🔖 CMake ${CMAKE_VERSION} (${CMAKE_COMMAND})") - -find_program(CPPCHECK_TOOL NAMES cppcheck) -execute_process(COMMAND ${CPPCHECK_TOOL} --version OUTPUT_VARIABLE CPPCHECK_TOOL_VERSION ERROR_VARIABLE CPPCHECK_TOOL_VERSION) -string(REGEX MATCH "[0-9]+(\\.[0-9]+)+" CPPCHECK_TOOL_VERSION "${CPPCHECK_TOOL_VERSION}") -message(STATUS "🔖 Cppcheck ${CPPCHECK_TOOL_VERSION} (${CPPCHECK_TOOL})") - -find_program(GCC_TOOL NAMES g++-latest g++-HEAD g++-11 g++-10) -execute_process(COMMAND ${GCC_TOOL} --version OUTPUT_VARIABLE GCC_TOOL_VERSION ERROR_VARIABLE GCC_TOOL_VERSION) -string(REGEX MATCH "[0-9]+(\\.[0-9]+)+" GCC_TOOL_VERSION "${GCC_TOOL_VERSION}") -message(STATUS "🔖 GCC ${GCC_TOOL_VERSION} (${GCC_TOOL})") - -find_program(GCOV_TOOL NAMES gcov-HEAD gcov-11 gcov-10 gcov) -execute_process(COMMAND ${GCOV_TOOL} --version OUTPUT_VARIABLE GCOV_TOOL_VERSION ERROR_VARIABLE GCOV_TOOL_VERSION) -string(REGEX MATCH "[0-9]+(\\.[0-9]+)+" GCOV_TOOL_VERSION "${GCOV_TOOL_VERSION}") -message(STATUS "🔖 GCOV ${GCOV_TOOL_VERSION} (${GCOV_TOOL})") - -find_program(GIT_TOOL NAMES git) -execute_process(COMMAND ${GIT_TOOL} --version OUTPUT_VARIABLE GIT_TOOL_VERSION ERROR_VARIABLE GIT_TOOL_VERSION) -string(REGEX MATCH "[0-9]+(\\.[0-9]+)+" GIT_TOOL_VERSION "${GIT_TOOL_VERSION}") -message(STATUS "🔖 Git ${GIT_TOOL_VERSION} (${GIT_TOOL})") - -find_program(IWYU_TOOL NAMES include-what-you-use iwyu) -execute_process(COMMAND ${IWYU_TOOL} --version OUTPUT_VARIABLE IWYU_TOOL_VERSION ERROR_VARIABLE IWYU_TOOL_VERSION) -string(REGEX MATCH "[0-9]+(\\.[0-9]+)+" IWYU_TOOL_VERSION "${IWYU_TOOL_VERSION}") -message(STATUS "🔖 include-what-you-use ${IWYU_TOOL_VERSION} (${IWYU_TOOL})") - -find_program(INFER_TOOL NAMES infer) -execute_process(COMMAND ${INFER_TOOL} --version OUTPUT_VARIABLE INFER_TOOL_VERSION ERROR_VARIABLE INFER_TOOL_VERSION) -string(REGEX MATCH "[0-9]+(\\.[0-9]+)+" INFER_TOOL_VERSION "${INFER_TOOL_VERSION}") -message(STATUS "🔖 Infer ${INFER_TOOL_VERSION} (${INFER_TOOL})") - -find_program(LCOV_TOOL NAMES lcov) -execute_process(COMMAND ${LCOV_TOOL} --version OUTPUT_VARIABLE LCOV_TOOL_VERSION ERROR_VARIABLE LCOV_TOOL_VERSION) -string(REGEX MATCH "[0-9]+(\\.[0-9]+)+" LCOV_TOOL_VERSION "${LCOV_TOOL_VERSION}") -message(STATUS "🔖 LCOV ${LCOV_TOOL_VERSION} (${LCOV_TOOL})") - -find_program(NINJA_TOOL NAMES ninja) -execute_process(COMMAND ${NINJA_TOOL} --version OUTPUT_VARIABLE NINJA_TOOL_VERSION ERROR_VARIABLE NINJA_TOOL_VERSION) -string(REGEX MATCH "[0-9]+(\\.[0-9]+)+" NINJA_TOOL_VERSION "${NINJA_TOOL_VERSION}") -message(STATUS "🔖 Ninja ${NINJA_TOOL_VERSION} (${NINJA_TOOL})") - -find_program(OCLINT_TOOL NAMES oclint-json-compilation-database) -find_program(OCLINT_VERSION_TOOL NAMES oclint) -execute_process(COMMAND ${OCLINT_VERSION_TOOL} --version OUTPUT_VARIABLE OCLINT_TOOL_VERSION ERROR_VARIABLE OCLINT_TOOL_VERSION) -string(REGEX MATCH "[0-9]+(\\.[0-9]+)+" OCLINT_TOOL_VERSION "${OCLINT_TOOL_VERSION}") -message(STATUS "🔖 OCLint ${OCLINT_TOOL_VERSION} (${OCLINT_TOOL})") - -find_program(VALGRIND_TOOL NAMES valgrind) -execute_process(COMMAND ${VALGRIND_TOOL} --version OUTPUT_VARIABLE VALGRIND_TOOL_VERSION ERROR_VARIABLE VALGRIND_TOOL_VERSION) -string(REGEX MATCH "[0-9]+(\\.[0-9]+)+" VALGRIND_TOOL_VERSION "${VALGRIND_TOOL_VERSION}") -message(STATUS "🔖 Valgrind ${VALGRIND_TOOL_VERSION} (${VALGRIND_TOOL})") - -find_program(GENHTML_TOOL NAMES genhtml) -find_program(PLOG_CONVERTER_TOOL NAMES plog-converter) -find_program(PVS_STUDIO_ANALYZER_TOOL NAMES pvs-studio-analyzer) -find_program(SCAN_BUILD_TOOL NAMES scan-build-15 scan-build-14 scan-build-13 scan-build-12 scan-build-11 scan-build) - -# the individual source files -file(GLOB_RECURSE SRC_FILES ${PROJECT_SOURCE_DIR}/include/nlohmann/*.hpp) - -############################################################################### -# Thorough check with recent compilers -############################################################################### - -# Ignored Clang warnings: -# -Wno-c++98-compat The library targets C++11. -# -Wno-c++98-compat-pedantic The library targets C++11. -# -Wno-deprecated-declarations The library contains annotations for deprecated functions. -# -Wno-extra-semi-stmt The library uses std::assert which triggers this warning. -# -Wno-padded We do not care about padding warnings. -# -Wno-covered-switch-default All switches list all cases and a default case. -# -Wno-weak-vtables The library is header-only. -# -Wreserved-identifier See https://github.com/onqtam/doctest/issues/536. - -set(CLANG_CXXFLAGS - -Werror - -Weverything - -Wno-c++98-compat - -Wno-c++98-compat-pedantic - -Wno-deprecated-declarations - -Wno-extra-semi-stmt - -Wno-padded - -Wno-covered-switch-default - -Wno-weak-vtables - -Wno-reserved-identifier -) - -# Warning flags determined for GCC 13.0 (experimental) with https://github.com/nlohmann/gcc_flags: -# Ignored GCC warnings: -# -Wno-abi-tag We do not care about ABI tags. -# -Wno-aggregate-return The library uses aggregate returns. -# -Wno-long-long The library uses the long long type to interface with system functions. -# -Wno-namespaces The library uses namespaces. -# -Wno-padded We do not care about padding warnings. -# -Wno-system-headers We do not care about warnings in system headers. -# -Wno-templates The library uses templates. - -set(GCC_CXXFLAGS - -pedantic - -Werror - --all-warnings - --extra-warnings - -W - -WNSObject-attribute - -Wno-abi-tag - -Waddress - -Waddress-of-packed-member - -Wno-aggregate-return - -Waggressive-loop-optimizations - -Waligned-new=all - -Wall - -Walloc-zero - -Walloca - -Wanalyzer-double-fclose - -Wanalyzer-double-free - -Wanalyzer-exposure-through-output-file - -Wanalyzer-file-leak - -Wanalyzer-free-of-non-heap - -Wanalyzer-malloc-leak - -Wanalyzer-mismatching-deallocation - -Wanalyzer-null-argument - -Wanalyzer-null-dereference - -Wanalyzer-possible-null-argument - -Wanalyzer-possible-null-dereference - -Wanalyzer-shift-count-negative - -Wanalyzer-shift-count-overflow - -Wanalyzer-stale-setjmp-buffer - -Wanalyzer-tainted-allocation-size - -Wanalyzer-tainted-array-index - -Wanalyzer-tainted-divisor - -Wanalyzer-tainted-offset - -Wanalyzer-tainted-size - -Wanalyzer-too-complex - -Wanalyzer-unsafe-call-within-signal-handler - -Wanalyzer-use-after-free - -Wanalyzer-use-of-pointer-in-stale-stack-frame - -Wanalyzer-use-of-uninitialized-value - -Wanalyzer-va-arg-type-mismatch - -Wanalyzer-va-list-exhausted - -Wanalyzer-va-list-leak - -Wanalyzer-va-list-use-after-va-end - -Wanalyzer-write-to-const - -Wanalyzer-write-to-string-literal - -Warith-conversion - -Warray-bounds=2 - -Warray-compare - -Warray-parameter=2 - -Wattribute-alias=2 - -Wattribute-warning - -Wattributes - -Wbool-compare - -Wbool-operation - -Wbuiltin-declaration-mismatch - -Wbuiltin-macro-redefined - -Wc++0x-compat - -Wc++11-compat - -Wc++11-extensions - -Wc++14-compat - -Wc++14-extensions - -Wc++17-compat - -Wc++17-extensions - -Wc++1z-compat - -Wc++20-compat - -Wc++20-extensions - -Wc++23-extensions - -Wc++2a-compat - -Wcannot-profile - -Wcast-align - -Wcast-align=strict - -Wcast-function-type - -Wcast-qual - -Wcatch-value=3 - -Wchar-subscripts - -Wclass-conversion - -Wclass-memaccess - -Wclobbered - -Wcomma-subscript - -Wcomment - -Wcomments - -Wconditionally-supported - -Wconversion - -Wconversion-null - -Wcoverage-invalid-line-number - -Wcoverage-mismatch - -Wcpp - -Wctad-maybe-unsupported - -Wctor-dtor-privacy - -Wdangling-else - -Wdangling-pointer=2 - -Wdate-time - -Wdelete-incomplete - -Wdelete-non-virtual-dtor - -Wdeprecated - -Wdeprecated-copy - -Wdeprecated-copy-dtor - -Wdeprecated-declarations - -Wdeprecated-enum-enum-conversion - -Wdeprecated-enum-float-conversion - -Wdisabled-optimization - -Wdiv-by-zero - -Wdouble-promotion - -Wduplicated-branches - -Wduplicated-cond - -Weffc++ - -Wempty-body - -Wendif-labels - -Wenum-compare - -Wenum-conversion - -Wexceptions - -Wexpansion-to-defined - -Wextra - -Wextra-semi - -Wfloat-conversion - -Wfloat-equal - -Wformat-diag - -Wformat-overflow=2 - -Wformat-signedness - -Wformat-truncation=2 - -Wformat=2 - -Wframe-address - -Wfree-nonheap-object - -Whsa - -Wif-not-aligned - -Wignored-attributes - -Wignored-qualifiers - -Wimplicit-fallthrough=5 - -Winaccessible-base - -Winfinite-recursion - -Winherited-variadic-ctor - -Winit-list-lifetime - -Winit-self - -Winline - -Wint-in-bool-context - -Wint-to-pointer-cast - -Winterference-size - -Winvalid-imported-macros - -Winvalid-memory-model - -Winvalid-offsetof - -Winvalid-pch - -Wliteral-suffix - -Wlogical-not-parentheses - -Wlogical-op - -Wno-long-long - -Wlto-type-mismatch - -Wmain - -Wmaybe-uninitialized - -Wmemset-elt-size - -Wmemset-transposed-args - -Wmisleading-indentation - -Wmismatched-dealloc - -Wmismatched-new-delete - -Wmismatched-tags - -Wmissing-attributes - -Wmissing-braces - -Wmissing-declarations - -Wmissing-field-initializers - -Wmissing-include-dirs - -Wmissing-profile - -Wmissing-requires - -Wmissing-template-keyword - -Wmultichar - -Wmultiple-inheritance - -Wmultistatement-macros - -Wno-namespaces - -Wnarrowing - -Wnoexcept - -Wnoexcept-type - -Wnon-template-friend - -Wnon-virtual-dtor - -Wnonnull - -Wnonnull-compare - -Wnormalized=nfkc - -Wnull-dereference - -Wodr - -Wold-style-cast - -Wopenacc-parallelism - -Wopenmp-simd - -Woverflow - -Woverlength-strings - -Woverloaded-virtual - -Wpacked - -Wpacked-bitfield-compat - -Wpacked-not-aligned - -Wno-padded - -Wparentheses - -Wpedantic - -Wpessimizing-move - -Wplacement-new=2 - -Wpmf-conversions - -Wpointer-arith - -Wpointer-compare - -Wpragmas - -Wprio-ctor-dtor - -Wpsabi - -Wrange-loop-construct - -Wredundant-decls - -Wredundant-move - -Wredundant-tags - -Wregister - -Wreorder - -Wrestrict - -Wreturn-local-addr - -Wreturn-type - -Wscalar-storage-order - -Wsequence-point - -Wshadow=compatible-local - -Wshadow=global - -Wshadow=local - -Wshift-count-negative - -Wshift-count-overflow - -Wshift-negative-value - -Wshift-overflow=2 - -Wsign-compare - -Wsign-conversion - -Wsign-promo - -Wsized-deallocation - -Wsizeof-array-argument - -Wsizeof-array-div - -Wsizeof-pointer-div - -Wsizeof-pointer-memaccess - -Wstack-protector - -Wstrict-aliasing=3 - -Wstrict-null-sentinel - -Wno-strict-overflow - -Wstring-compare - -Wstringop-overflow=4 - -Wstringop-overread - -Wstringop-truncation - -Wsubobject-linkage - -Wsuggest-attribute=cold - -Wsuggest-attribute=const - -Wsuggest-attribute=format - -Wsuggest-attribute=malloc - -Wsuggest-attribute=noreturn - -Wsuggest-attribute=pure - -Wsuggest-final-methods - -Wsuggest-final-types - -Wsuggest-override - -Wswitch - -Wswitch-bool - -Wswitch-default - -Wswitch-enum - -Wswitch-outside-range - -Wswitch-unreachable - -Wsync-nand - -Wsynth - -Wno-system-headers - -Wtautological-compare - -Wno-templates - -Wterminate - -Wtrampolines - -Wtrigraphs - -Wtrivial-auto-var-init - -Wtsan - -Wtype-limits - -Wundef - -Wuninitialized - -Wunknown-pragmas - -Wunreachable-code - -Wunsafe-loop-optimizations - -Wunused - -Wunused-but-set-parameter - -Wunused-but-set-variable - -Wunused-const-variable=2 - -Wunused-function - -Wunused-label - -Wunused-local-typedefs - -Wunused-macros - -Wunused-parameter - -Wunused-result - -Wunused-value - -Wunused-variable - -Wuse-after-free=3 - -Wuseless-cast - -Wvarargs - -Wvariadic-macros - -Wvector-operation-performance - -Wvexing-parse - -Wvirtual-inheritance - -Wvirtual-move-assign - -Wvla - -Wvla-parameter - -Wvolatile - -Wvolatile-register-var - -Wwrite-strings - -Wzero-as-null-pointer-constant - -Wzero-length-bounds -) - -add_custom_target(ci_test_gcc - COMMAND CXX=${GCC_TOOL} CXXFLAGS="${GCC_CXXFLAGS}" ${CMAKE_COMMAND} - -DCMAKE_BUILD_TYPE=Debug -GNinja - -DJSON_BuildTests=ON - -S${PROJECT_SOURCE_DIR} -B${PROJECT_BINARY_DIR}/build_gcc - COMMAND ${CMAKE_COMMAND} --build ${PROJECT_BINARY_DIR}/build_gcc - COMMAND cd ${PROJECT_BINARY_DIR}/build_gcc && ${CMAKE_CTEST_COMMAND} --parallel ${N} --output-on-failure - COMMENT "Compile and test with GCC using maximal warning flags" -) - -add_custom_target(ci_test_clang - COMMAND CXX=${CLANG_TOOL} CXXFLAGS="${CLANG_CXXFLAGS}" ${CMAKE_COMMAND} - -DCMAKE_BUILD_TYPE=Debug -GNinja - -DJSON_BuildTests=ON - -S${PROJECT_SOURCE_DIR} -B${PROJECT_BINARY_DIR}/build_clang - COMMAND ${CMAKE_COMMAND} --build ${PROJECT_BINARY_DIR}/build_clang - COMMAND cd ${PROJECT_BINARY_DIR}/build_clang && ${CMAKE_CTEST_COMMAND} --parallel ${N} --output-on-failure - COMMENT "Compile and test with Clang using maximal warning flags" -) - -############################################################################### -# Different C++ Standards. -############################################################################### - -foreach(CXX_STANDARD 11 14 17 20) - add_custom_target(ci_test_gcc_cxx${CXX_STANDARD} - COMMAND CXX=${GCC_TOOL} CXXFLAGS="${GCC_CXXFLAGS}" ${CMAKE_COMMAND} - -DCMAKE_BUILD_TYPE=Debug -GNinja - -DJSON_BuildTests=ON -DJSON_FastTests=ON - -DJSON_TestStandards=${CXX_STANDARD} - -S${PROJECT_SOURCE_DIR} -B${PROJECT_BINARY_DIR}/build_gcc_cxx${CXX_STANDARD} - COMMAND ${CMAKE_COMMAND} --build ${PROJECT_BINARY_DIR}/build_gcc_cxx${CXX_STANDARD} - COMMAND cd ${PROJECT_BINARY_DIR}/build_gcc_cxx${CXX_STANDARD} && ${CMAKE_CTEST_COMMAND} --parallel ${N} --output-on-failure - COMMENT "Compile and test with GCC for C++${CXX_STANDARD}" - ) - - add_custom_target(ci_test_clang_cxx${CXX_STANDARD} - COMMAND CXX=${CLANG_TOOL} CXXFLAGS="${CLANG_CXXFLAGS}" ${CMAKE_COMMAND} - -DCMAKE_BUILD_TYPE=Debug -GNinja - -DJSON_BuildTests=ON -DJSON_FastTests=ON - -DJSON_TestStandards=${CXX_STANDARD} - -S${PROJECT_SOURCE_DIR} -B${PROJECT_BINARY_DIR}/build_clang_cxx${CXX_STANDARD} - COMMAND ${CMAKE_COMMAND} --build ${PROJECT_BINARY_DIR}/build_clang_cxx${CXX_STANDARD} - COMMAND cd ${PROJECT_BINARY_DIR}/build_clang_cxx${CXX_STANDARD} && ${CMAKE_CTEST_COMMAND} --parallel ${N} --output-on-failure - COMMENT "Compile and test with Clang for C++${CXX_STANDARD}" - ) -endforeach() - -############################################################################### -# Disable exceptions. -############################################################################### - -add_custom_target(ci_test_noexceptions - COMMAND CXX=${CLANG_TOOL} ${CMAKE_COMMAND} - -DCMAKE_BUILD_TYPE=Debug -GNinja - -DJSON_BuildTests=ON -DCMAKE_CXX_FLAGS=-DJSON_NOEXCEPTION -DDOCTEST_TEST_FILTER=--no-throw - -S${PROJECT_SOURCE_DIR} -B${PROJECT_BINARY_DIR}/build_noexceptions - COMMAND ${CMAKE_COMMAND} --build ${PROJECT_BINARY_DIR}/build_noexceptions - COMMAND cd ${PROJECT_BINARY_DIR}/build_noexceptions && ${CMAKE_CTEST_COMMAND} --parallel ${N} --output-on-failure - COMMENT "Compile and test with exceptions switched off" -) - -############################################################################### -# Disable implicit conversions. -############################################################################### - -add_custom_target(ci_test_noimplicitconversions - COMMAND CXX=${CLANG_TOOL} ${CMAKE_COMMAND} - -DCMAKE_BUILD_TYPE=Debug -GNinja - -DJSON_BuildTests=ON -DJSON_ImplicitConversions=OFF - -S${PROJECT_SOURCE_DIR} -B${PROJECT_BINARY_DIR}/build_noimplicitconversions - COMMAND ${CMAKE_COMMAND} --build ${PROJECT_BINARY_DIR}/build_noimplicitconversions - COMMAND cd ${PROJECT_BINARY_DIR}/build_noimplicitconversions && ${CMAKE_CTEST_COMMAND} --parallel ${N} --output-on-failure - COMMENT "Compile and test with implicit conversions switched off" -) - -############################################################################### -# Enable improved diagnostics. -############################################################################### - -add_custom_target(ci_test_diagnostics - COMMAND CXX=${CLANG_TOOL} ${CMAKE_COMMAND} - -DCMAKE_BUILD_TYPE=Debug -GNinja - -DJSON_BuildTests=ON -DJSON_Diagnostics=ON - -S${PROJECT_SOURCE_DIR} -B${PROJECT_BINARY_DIR}/build_diagnostics - COMMAND ${CMAKE_COMMAND} --build ${PROJECT_BINARY_DIR}/build_diagnostics - COMMAND cd ${PROJECT_BINARY_DIR}/build_diagnostics && ${CMAKE_CTEST_COMMAND} --parallel ${N} --output-on-failure - COMMENT "Compile and test with improved diagnostics enabled" -) - -############################################################################### -# Enable legacy discarded value comparison. -############################################################################### - -add_custom_target(ci_test_legacycomparison - COMMAND CXX=${CLANG_TOOL} ${CMAKE_COMMAND} - -DCMAKE_BUILD_TYPE=Debug -GNinja - -DJSON_BuildTests=ON -DJSON_LegacyDiscardedValueComparison=ON - -S${PROJECT_SOURCE_DIR} -B${PROJECT_BINARY_DIR}/build_legacycomparison - COMMAND ${CMAKE_COMMAND} --build ${PROJECT_BINARY_DIR}/build_legacycomparison - COMMAND cd ${PROJECT_BINARY_DIR}/build_legacycomparison && ${CMAKE_CTEST_COMMAND} --parallel ${N} --output-on-failure - COMMENT "Compile and test with legacy discarded value comparison enabled" -) - -############################################################################### -# Disable global UDLs. -############################################################################### - -add_custom_target(ci_test_noglobaludls - COMMAND CXX=${CLANG_TOOL} ${CMAKE_COMMAND} - -DCMAKE_BUILD_TYPE=Debug -GNinja - -DJSON_BuildTests=ON -DJSON_FastTests=ON -DJSON_GlobalUDLs=OFF - -DCMAKE_CXX_FLAGS=-DJSON_TEST_NO_GLOBAL_UDLS - -S${PROJECT_SOURCE_DIR} -B${PROJECT_BINARY_DIR}/build_noglobaludls - COMMAND ${CMAKE_COMMAND} --build ${PROJECT_BINARY_DIR}/build_noglobaludls - COMMAND cd ${PROJECT_BINARY_DIR}/build_noglobaludls && ${CMAKE_CTEST_COMMAND} --parallel ${N} --output-on-failure - COMMENT "Compile and test with global UDLs disabled" -) - -############################################################################### -# Coverage. -############################################################################### - -add_custom_target(ci_test_coverage - COMMAND CXX=g++ ${CMAKE_COMMAND} - -DCMAKE_BUILD_TYPE=Debug -GNinja -DCMAKE_CXX_FLAGS="--coverage;-fprofile-arcs;-ftest-coverage" - -DJSON_BuildTests=ON - -S${PROJECT_SOURCE_DIR} -B${PROJECT_BINARY_DIR}/build_coverage - COMMAND ${CMAKE_COMMAND} --build ${PROJECT_BINARY_DIR}/build_coverage - COMMAND cd ${PROJECT_BINARY_DIR}/build_coverage && ${CMAKE_CTEST_COMMAND} --parallel ${N} --output-on-failure - - COMMAND CXX=g++ ${CMAKE_COMMAND} - -DCMAKE_BUILD_TYPE=Debug -GNinja -DCMAKE_CXX_FLAGS="-m32;--coverage;-fprofile-arcs;-ftest-coverage" - -DJSON_BuildTests=ON -DJSON_32bitTest=ONLY - -S${PROJECT_SOURCE_DIR} -B${PROJECT_BINARY_DIR}/build_coverage32 - COMMAND ${CMAKE_COMMAND} --build ${PROJECT_BINARY_DIR}/build_coverage32 - COMMAND cd ${PROJECT_BINARY_DIR}/build_coverage32 && ${CMAKE_CTEST_COMMAND} --parallel ${N} --output-on-failure - - COMMAND ${LCOV_TOOL} --directory . --capture --output-file json.info --rc lcov_branch_coverage=1 - COMMAND ${LCOV_TOOL} -e json.info ${SRC_FILES} --output-file json.info.filtered --rc lcov_branch_coverage=1 - COMMAND ${CMAKE_SOURCE_DIR}/tests/thirdparty/imapdl/filterbr.py json.info.filtered > json.info.filtered.noexcept - COMMAND genhtml --title "JSON for Modern C++" --legend --demangle-cpp --output-directory html --show-details --branch-coverage json.info.filtered.noexcept - - COMMENT "Compile and test with coverage" -) - -############################################################################### -# Sanitizers. -############################################################################### - -set(CLANG_CXX_FLAGS_SANITIZER "-g -O1 -fsanitize=address -fsanitize=undefined -fsanitize=integer -fsanitize=nullability -fno-omit-frame-pointer -fno-sanitize-recover=all -fno-sanitize=unsigned-integer-overflow -fno-sanitize=unsigned-shift-base") - -add_custom_target(ci_test_clang_sanitizer - COMMAND CXX=${CLANG_TOOL} CXXFLAGS=${CLANG_CXX_FLAGS_SANITIZER} ${CMAKE_COMMAND} - -DCMAKE_BUILD_TYPE=Debug -GNinja - -DJSON_BuildTests=ON - -S${PROJECT_SOURCE_DIR} -B${PROJECT_BINARY_DIR}/build_clang_sanitizer - COMMAND ${CMAKE_COMMAND} --build ${PROJECT_BINARY_DIR}/build_clang_sanitizer - COMMAND cd ${PROJECT_BINARY_DIR}/build_clang_sanitizer && ${CMAKE_CTEST_COMMAND} --parallel ${N} --output-on-failure - COMMENT "Compile and test with sanitizers" -) - -############################################################################### -# Check if header is amalgamated and sources are properly indented. -############################################################################### - -set(ASTYLE_FLAGS --style=allman --indent=spaces=4 --indent-modifiers --indent-switches --indent-preproc-block --indent-preproc-define --indent-col1-comments --pad-oper --pad-header --align-pointer=type --align-reference=type --add-brackets --convert-tabs --close-templates --lineend=linux --preserve-date --formatted) - -file(GLOB_RECURSE INDENT_FILES - ${PROJECT_SOURCE_DIR}/include/nlohmann/*.hpp - ${PROJECT_SOURCE_DIR}/tests/src/*.cpp - ${PROJECT_SOURCE_DIR}/tests/src/*.hpp - ${PROJECT_SOURCE_DIR}/tests/benchmarks/src/benchmarks.cpp - ${PROJECT_SOURCE_DIR}/docs/examples/*.cpp -) - -set(include_dir ${PROJECT_SOURCE_DIR}/single_include/nlohmann) -set(tool_dir ${PROJECT_SOURCE_DIR}/tools/amalgamate) -add_custom_target(ci_test_amalgamation - COMMAND rm -fr ${include_dir}/json.hpp~ ${include_dir}/json_fwd.hpp~ - COMMAND cp ${include_dir}/json.hpp ${include_dir}/json.hpp~ - COMMAND cp ${include_dir}/json_fwd.hpp ${include_dir}/json_fwd.hpp~ - - COMMAND ${Python3_EXECUTABLE} ${tool_dir}/amalgamate.py -c ${tool_dir}/config_json.json -s . - COMMAND ${Python3_EXECUTABLE} ${tool_dir}/amalgamate.py -c ${tool_dir}/config_json_fwd.json -s . - COMMAND ${ASTYLE_TOOL} ${ASTYLE_FLAGS} --suffix=none --quiet ${include_dir}/json.hpp ${include_dir}/json_fwd.hpp - - COMMAND diff ${include_dir}/json.hpp~ ${include_dir}/json.hpp - COMMAND diff ${include_dir}/json_fwd.hpp~ ${include_dir}/json_fwd.hpp - - COMMAND ${ASTYLE_TOOL} ${ASTYLE_FLAGS} ${INDENT_FILES} - COMMAND for FILE in `find . -name '*.orig'`\; do false \; done - - WORKING_DIRECTORY ${PROJECT_SOURCE_DIR} - COMMENT "Check amalgamation and indentation" -) - -############################################################################### -# Build and test using the amalgamated header -############################################################################### - -add_custom_target(ci_test_single_header - COMMAND CXX=${GCC_TOOL} CXXFLAGS="${GCC_CXXFLAGS}" ${CMAKE_COMMAND} - -DCMAKE_BUILD_TYPE=Debug -GNinja - -DJSON_BuildTests=ON -DJSON_MultipleHeaders=OFF -DJSON_FastTests=ON - -S${PROJECT_SOURCE_DIR} -B${PROJECT_BINARY_DIR}/build_single_header - COMMAND ${CMAKE_COMMAND} --build ${PROJECT_BINARY_DIR}/build_single_header - COMMAND cd ${PROJECT_BINARY_DIR}/build_single_header && ${CMAKE_CTEST_COMMAND} --parallel ${N} --output-on-failure - COMMENT "Compile and test single-header version" -) - -############################################################################### -# Valgrind. -############################################################################### - -add_custom_target(ci_test_valgrind - COMMAND CXX=${GCC_TOOL} ${CMAKE_COMMAND} - -DCMAKE_BUILD_TYPE=Debug -GNinja - -DJSON_BuildTests=ON -DJSON_Valgrind=ON - -S${PROJECT_SOURCE_DIR} -B${PROJECT_BINARY_DIR}/build_valgrind - COMMAND ${CMAKE_COMMAND} --build ${PROJECT_BINARY_DIR}/build_valgrind - COMMAND cd ${PROJECT_BINARY_DIR}/build_valgrind && ${CMAKE_CTEST_COMMAND} -L valgrind --parallel ${N} --output-on-failure - COMMENT "Compile and test with Valgrind" -) - -############################################################################### -# Check code with Clang Static Analyzer. -############################################################################### - -set(CLANG_ANALYZER_CHECKS "fuchsia.HandleChecker,nullability.NullableDereferenced,nullability.NullablePassedToNonnull,nullability.NullableReturnedFromNonnull,optin.cplusplus.UninitializedObject,optin.cplusplus.VirtualCall,optin.mpi.MPI-Checker,optin.osx.OSObjectCStyleCast,optin.osx.cocoa.localizability.EmptyLocalizationContextChecker,optin.osx.cocoa.localizability.NonLocalizedStringChecker,optin.performance.GCDAntipattern,optin.performance.Padding,optin.portability.UnixAPI,security.FloatLoopCounter,security.insecureAPI.DeprecatedOrUnsafeBufferHandling,security.insecureAPI.bcmp,security.insecureAPI.bcopy,security.insecureAPI.bzero,security.insecureAPI.rand,security.insecureAPI.strcpy,valist.CopyToSelf,valist.Uninitialized,valist.Unterminated,webkit.NoUncountedMemberChecker,webkit.RefCntblBaseVirtualDtor,core.CallAndMessage,core.DivideZero,core.NonNullParamChecker,core.NullDereference,core.StackAddressEscape,core.UndefinedBinaryOperatorResult,core.VLASize,core.uninitialized.ArraySubscript,core.uninitialized.Assign,core.uninitialized.Branch,core.uninitialized.CapturedBlockVariable,core.uninitialized.UndefReturn,cplusplus.InnerPointer,cplusplus.Move,cplusplus.NewDelete,cplusplus.NewDeleteLeaks,cplusplus.PlacementNew,cplusplus.PureVirtualCall,deadcode.DeadStores,nullability.NullPassedToNonnull,nullability.NullReturnedFromNonnull,osx.API,osx.MIG,osx.NumberObjectConversion,osx.OSObjectRetainCount,osx.ObjCProperty,osx.SecKeychainAPI,osx.cocoa.AtSync,osx.cocoa.AutoreleaseWrite,osx.cocoa.ClassRelease,osx.cocoa.Dealloc,osx.cocoa.IncompatibleMethodTypes,osx.cocoa.Loops,osx.cocoa.MissingSuperCall,osx.cocoa.NSAutoreleasePool,osx.cocoa.NSError,osx.cocoa.NilArg,osx.cocoa.NonNilReturnValue,osx.cocoa.ObjCGenerics,osx.cocoa.RetainCount,osx.cocoa.RunLoopAutoreleaseLeak,osx.cocoa.SelfInit,osx.cocoa.SuperDealloc,osx.cocoa.UnusedIvars,osx.cocoa.VariadicMethodTypes,osx.coreFoundation.CFError,osx.coreFoundation.CFNumber,osx.coreFoundation.CFRetainRelease,osx.coreFoundation.containers.OutOfBounds,osx.coreFoundation.containers.PointerSizedValues,security.insecureAPI.UncheckedReturn,security.insecureAPI.decodeValueOfObjCType,security.insecureAPI.getpw,security.insecureAPI.gets,security.insecureAPI.mkstemp,security.insecureAPI.mktemp,security.insecureAPI.vfork,unix.API,unix.Malloc,unix.MallocSizeof,unix.MismatchedDeallocator,unix.Vfork,unix.cstring.BadSizeArg,unix.cstring.NullArg") - -add_custom_target(ci_clang_analyze - COMMAND CXX=${CLANG_TOOL} ${CMAKE_COMMAND} - -DCMAKE_BUILD_TYPE=Debug -GNinja - -DJSON_BuildTests=ON - -S${PROJECT_SOURCE_DIR} -B${PROJECT_BINARY_DIR}/build_clang_analyze - COMMAND cd ${PROJECT_BINARY_DIR}/build_clang_analyze && ${SCAN_BUILD_TOOL} -enable-checker ${CLANG_ANALYZER_CHECKS} --use-c++=${CLANG_TOOL} -analyze-headers -o ${PROJECT_BINARY_DIR}/report ninja - COMMENT "Check code with Clang Analyzer" -) - -############################################################################### -# Check code with Cppcheck. -############################################################################### - -add_custom_target(ci_cppcheck - COMMAND ${CPPCHECK_TOOL} --enable=warning --suppress=missingReturn --inline-suppr --inconclusive --force --std=c++11 ${PROJECT_SOURCE_DIR}/single_include/nlohmann/json.hpp --error-exitcode=1 - COMMENT "Check code with Cppcheck" -) - -############################################################################### -# Check code with cpplint. -############################################################################### - -add_custom_target(ci_cpplint - COMMAND ${Python3_EXECUTABLE} ${CMAKE_SOURCE_DIR}/tools/cpplint/cpplint.py --filter=-whitespace,-legal,-runtime/references,-runtime/explicit,-runtime/indentation_namespace,-readability/casting,-readability/nolint --quiet --recursive ${SRC_FILES} - COMMENT "Check code with cpplint" -) - -############################################################################### -# Check code with OCLint. -############################################################################### - -file(COPY ${PROJECT_SOURCE_DIR}/single_include/nlohmann/json.hpp DESTINATION ${PROJECT_BINARY_DIR}/src_single) -file(RENAME ${PROJECT_BINARY_DIR}/src_single/json.hpp ${PROJECT_BINARY_DIR}/src_single/all.cpp) -file(APPEND "${PROJECT_BINARY_DIR}/src_single/all.cpp" "\n\nint main()\n{}\n") - -add_executable(single_all ${PROJECT_BINARY_DIR}/src_single/all.cpp) -target_compile_features(single_all PRIVATE cxx_std_11) - -add_custom_target(ci_oclint - COMMAND ${CMAKE_COMMAND} - -DCMAKE_BUILD_TYPE=Debug - -DCMAKE_EXPORT_COMPILE_COMMANDS=ON - -DJSON_BuildTests=OFF -DJSON_CI=ON - -S${PROJECT_SOURCE_DIR} -B${PROJECT_BINARY_DIR}/build_oclint - COMMAND ${OCLINT_TOOL} -i ${PROJECT_BINARY_DIR}/build_oclint/src_single/all.cpp -p ${PROJECT_BINARY_DIR}/build_oclint -- - -report-type html -enable-global-analysis --max-priority-1=0 --max-priority-2=1000 --max-priority-3=2000 - --disable-rule=MultipleUnaryOperator - --disable-rule=DoubleNegative - --disable-rule=ShortVariableName - --disable-rule=GotoStatement - --disable-rule=LongLine - -o ${PROJECT_BINARY_DIR}/build_oclint/oclint_report.html - COMMENT "Check code with OCLint" -) - -############################################################################### -# Check code with Clang-Tidy. -############################################################################### - -add_custom_target(ci_clang_tidy - COMMAND CXX=${CLANG_TOOL} ${CMAKE_COMMAND} - -DCMAKE_BUILD_TYPE=Debug -GNinja - -DCMAKE_EXPORT_COMPILE_COMMANDS=ON -DCMAKE_CXX_CLANG_TIDY=${CLANG_TIDY_TOOL} - -DJSON_BuildTests=ON - -S${PROJECT_SOURCE_DIR} -B${PROJECT_BINARY_DIR}/build_clang_tidy - COMMAND ${CMAKE_COMMAND} --build ${PROJECT_BINARY_DIR}/build_clang_tidy - COMMENT "Check code with Clang-Tidy" -) - -############################################################################### -# Check code with PVS-Studio Analyzer . -############################################################################### - -add_custom_target(ci_pvs_studio - COMMAND CXX=${CLANG_TOOL} ${CMAKE_COMMAND} - -DCMAKE_BUILD_TYPE=Debug - -DCMAKE_EXPORT_COMPILE_COMMANDS=ON - -DJSON_BuildTests=ON - -S${PROJECT_SOURCE_DIR} -B${PROJECT_BINARY_DIR}/build_pvs_studio - COMMAND cd ${PROJECT_BINARY_DIR}/build_pvs_studio && ${PVS_STUDIO_ANALYZER_TOOL} analyze -j 10 - COMMAND cd ${PROJECT_BINARY_DIR}/build_pvs_studio && ${PLOG_CONVERTER_TOOL} -a'GA:1,2;64:1;CS' -t fullhtml PVS-Studio.log -o pvs - COMMENT "Check code with PVS Studio" -) - -############################################################################### -# Check code with Infer static analyzer. -############################################################################### - -add_custom_target(ci_infer - COMMAND mkdir -p ${PROJECT_BINARY_DIR}/build_infer - COMMAND cd ${PROJECT_BINARY_DIR}/build_infer && ${INFER_TOOL} compile -- ${CMAKE_COMMAND} -DCMAKE_BUILD_TYPE=Debug ${PROJECT_SOURCE_DIR} -DJSON_BuildTests=ON - COMMAND cd ${PROJECT_BINARY_DIR}/build_infer && ${INFER_TOOL} run -- make - COMMENT "Check code with Infer" -) - -############################################################################### -# Run test suite with previously downloaded test data. -############################################################################### - -add_custom_target(ci_offline_testdata - COMMAND mkdir -p ${PROJECT_BINARY_DIR}/build_offline_testdata/test_data - COMMAND cd ${PROJECT_BINARY_DIR}/build_offline_testdata/test_data && ${GIT_TOOL} clone -c advice.detachedHead=false --branch v3.1.0 https://github.com/nlohmann/json_test_data.git --quiet --depth 1 - COMMAND ${CMAKE_COMMAND} - -DCMAKE_BUILD_TYPE=Debug -GNinja - -DJSON_BuildTests=ON -DJSON_FastTests=ON -DJSON_TestDataDirectory=${PROJECT_BINARY_DIR}/build_offline_testdata/test_data/json_test_data - -S${PROJECT_SOURCE_DIR} -B${PROJECT_BINARY_DIR}/build_offline_testdata - COMMAND ${CMAKE_COMMAND} --build ${PROJECT_BINARY_DIR}/build_offline_testdata - COMMAND cd ${PROJECT_BINARY_DIR}/build_offline_testdata && ${CMAKE_CTEST_COMMAND} --parallel ${N} --output-on-failure - COMMENT "Check code with previously downloaded test data" -) - -############################################################################### -# Run test suite when project was not checked out from Git -############################################################################### - -add_custom_target(ci_non_git_tests - COMMAND git config --global --add safe.directory ${PROJECT_SOURCE_DIR} - COMMAND mkdir -p ${PROJECT_BINARY_DIR}/build_non_git_tests/sources - COMMAND cd ${PROJECT_SOURCE_DIR} && for FILE in `${GIT_TOOL} ls-tree --name-only HEAD`\; do cp -r $$FILE ${PROJECT_BINARY_DIR}/build_non_git_tests/sources \; done - COMMAND ${CMAKE_COMMAND} - -DCMAKE_BUILD_TYPE=Debug -GNinja - -DJSON_BuildTests=ON -DJSON_FastTests=ON - -S${PROJECT_BINARY_DIR}/build_non_git_tests/sources -B${PROJECT_BINARY_DIR}/build_non_git_tests - COMMAND ${CMAKE_COMMAND} --build ${PROJECT_BINARY_DIR}/build_non_git_tests - COMMAND cd ${PROJECT_BINARY_DIR}/build_non_git_tests && ${CMAKE_CTEST_COMMAND} --parallel ${N} -LE git_required --output-on-failure - COMMENT "Check code when project was not checked out from Git" -) - -############################################################################### -# Run test suite and exclude tests that change installed files -############################################################################### - -add_custom_target(ci_reproducible_tests - COMMAND ${CMAKE_COMMAND} - -DCMAKE_BUILD_TYPE=Debug -GNinja - -DJSON_BuildTests=ON -DJSON_FastTests=ON - -S${PROJECT_SOURCE_DIR} -B${PROJECT_BINARY_DIR}/build_reproducible_tests - COMMAND ${CMAKE_COMMAND} --build ${PROJECT_BINARY_DIR}/build_reproducible_tests - COMMAND cd ${PROJECT_BINARY_DIR}/build_reproducible_tests && ${CMAKE_CTEST_COMMAND} --parallel ${N} -LE not_reproducible --output-on-failure - COMMENT "Check code and exclude tests that change installed files" -) - -############################################################################### -# Check if every header in the include folder includes sufficient headers to -# be compiled individually. -############################################################################### - -set(iwyu_path_and_options ${IWYU_TOOL} -Xiwyu --max_line_length=300) - -foreach(SRC_FILE ${SRC_FILES}) - # get relative path of the header file - file(RELATIVE_PATH RELATIVE_SRC_FILE "${PROJECT_SOURCE_DIR}/include/nlohmann" "${SRC_FILE}") - # replace slashes and strip suffix - string(REPLACE "/" "_" RELATIVE_SRC_FILE "${RELATIVE_SRC_FILE}") - string(REPLACE ".hpp" "" RELATIVE_SRC_FILE "${RELATIVE_SRC_FILE}") - # create code file - file(WRITE "${PROJECT_BINARY_DIR}/src_single/${RELATIVE_SRC_FILE}.cpp" "#include \"${SRC_FILE}\" // IWYU pragma: keep\n\nint main()\n{}\n") - # create executable - add_executable(single_${RELATIVE_SRC_FILE} EXCLUDE_FROM_ALL ${PROJECT_BINARY_DIR}/src_single/${RELATIVE_SRC_FILE}.cpp) - target_include_directories(single_${RELATIVE_SRC_FILE} PRIVATE ${PROJECT_SOURCE_DIR}/include) - target_compile_features(single_${RELATIVE_SRC_FILE} PRIVATE cxx_std_11) - set_property(TARGET single_${RELATIVE_SRC_FILE} PROPERTY CXX_INCLUDE_WHAT_YOU_USE "${iwyu_path_and_options}") - # remember binary for ci_single_binaries target - list(APPEND single_binaries single_${RELATIVE_SRC_FILE}) -endforeach() - -add_custom_target(ci_single_binaries - DEPENDS ${single_binaries} - COMMENT "Check if headers are self-contained" -) - -############################################################################### -# Benchmarks -############################################################################### - -add_custom_target(ci_benchmarks - COMMAND ${CMAKE_COMMAND} - -DCMAKE_BUILD_TYPE=Release -GNinja - -S${PROJECT_SOURCE_DIR}/benchmarks -B${PROJECT_BINARY_DIR}/build_benchmarks - COMMAND ${CMAKE_COMMAND} --build ${PROJECT_BINARY_DIR}/build_benchmarks --target json_benchmarks - COMMAND cd ${PROJECT_BINARY_DIR}/build_benchmarks && ./json_benchmarks - COMMENT "Run benchmarks" -) - -############################################################################### -# CMake flags -############################################################################### - -function(ci_get_cmake version var) - if (APPLE) - set(${var} ${PROJECT_BINARY_DIR}/cmake-${version}-Darwin64/CMake.app/Contents/bin/cmake) - add_custom_command( - OUTPUT ${${var}} - COMMAND wget -nc https://github.com/Kitware/CMake/releases/download/v${version}/cmake-${version}-Darwin64.tar.gz - COMMAND tar xfz cmake-${version}-Darwin64.tar.gz - COMMAND rm cmake-${version}-Darwin64.tar.gz - WORKING_DIRECTORY ${PROJECT_BINARY_DIR} - COMMENT "Download CMake ${version}" - ) - else() - set(${var} ${PROJECT_BINARY_DIR}/cmake-${version}-Linux-x86_64/bin/cmake) - add_custom_command( - OUTPUT ${${var}} - COMMAND wget -nc https://github.com/Kitware/CMake/releases/download/v${version}/cmake-${version}-Linux-x86_64.tar.gz - COMMAND tar xfz cmake-${version}-Linux-x86_64.tar.gz - COMMAND rm cmake-${version}-Linux-x86_64.tar.gz - WORKING_DIRECTORY ${PROJECT_BINARY_DIR} - COMMENT "Download CMake ${version}" - ) - endif() - set(${var} ${${var}} PARENT_SCOPE) -endfunction() - -ci_get_cmake(3.1.0 CMAKE_3_1_0_BINARY) -ci_get_cmake(3.13.0 CMAKE_3_13_0_BINARY) - -set(JSON_CMAKE_FLAGS_3_1_0 JSON_Diagnostics JSON_GlobalUDLs JSON_ImplicitConversions JSON_DisableEnumSerialization - JSON_LegacyDiscardedValueComparison JSON_Install JSON_MultipleHeaders JSON_SystemInclude JSON_Valgrind) -set(JSON_CMAKE_FLAGS_3_13_0 JSON_BuildTests) - -function(ci_add_cmake_flags_targets flag min_version) - string(TOLOWER "ci_cmake_flag_${flag}" flag_target) - string(REPLACE . _ min_version_var ${min_version}) - set(cmake_binary ${CMAKE_${min_version_var}_BINARY}) - add_custom_target(${flag_target} - COMMENT "Check CMake flag ${flag} (CMake ${CMAKE_VERSION})" - COMMAND ${CMAKE_COMMAND} - -Werror=dev - -D${flag}=ON - -S${PROJECT_SOURCE_DIR} -B${PROJECT_BINARY_DIR}/build_${flag_target} - ) - add_custom_target(${flag_target}_${min_version_var} - COMMENT "Check CMake flag ${JSON_CMAKE_FLAG} (CMake ${min_version})" - COMMAND mkdir -pv ${PROJECT_BINARY_DIR}/build_${flag_target}_${min_version_var} - COMMAND cd ${PROJECT_BINARY_DIR}/build_${flag_target}_${min_version_var} - && ${cmake_binary} -Werror=dev ${PROJECT_SOURCE_DIR} -D${flag}=ON - DEPENDS ${cmake_binary} - ) - list(APPEND JSON_CMAKE_FLAG_TARGETS ${JSON_CMAKE_FLAG_TARGET} ${flag_target}_${min_version_var}) - list(APPEND JSON_CMAKE_FLAG_BUILD_DIRS ${PROJECT_BINARY_DIR}/build_${flag_target} ${PROJECT_BINARY_DIR}/build_${flag_target}_${min_version_var}) - set(JSON_CMAKE_FLAG_TARGETS ${JSON_CMAKE_FLAG_TARGETS} PARENT_SCOPE) - set(JSON_CMAKE_FLAG_BUILD_DIRS ${JSON_CMAKE_FLAG_BUILD_DIRS} PARENT_SCOPE) -endfunction() - -foreach(JSON_CMAKE_FLAG ${JSON_CMAKE_FLAGS_3_1_0}) - ci_add_cmake_flags_targets(${JSON_CMAKE_FLAG} 3.1.0) -endforeach() - -foreach(JSON_CMAKE_FLAG ${JSON_CMAKE_FLAGS_3_13_0}) - ci_add_cmake_flags_targets(${JSON_CMAKE_FLAG} 3.13.0) -endforeach() - -add_custom_target(ci_cmake_flags - DEPENDS ${JSON_CMAKE_FLAG_TARGETS} - COMMENT "Check CMake flags" -) - -############################################################################### -# Use more installed compilers. -############################################################################### - -foreach(COMPILER g++-4.8 g++-4.9 g++-5 g++-6 g++-7 g++-8 g++-9 g++-10 g++-11 clang++-3.5 clang++-3.6 clang++-3.7 clang++-3.8 clang++-3.9 clang++-4.0 clang++-5.0 clang++-6.0 clang++-7 clang++-8 clang++-9 clang++-10 clang++-11 clang++-12 clang++-13 clang++-14) - find_program(COMPILER_TOOL NAMES ${COMPILER}) - if (COMPILER_TOOL) - if ("${COMPILER}" STREQUAL "clang++-9") - # fix for https://github.com/nlohmann/json/pull/3101#issuecomment-998788786 / https://stackoverflow.com/a/64051725/266378 - set(ADDITIONAL_FLAGS "-DCMAKE_CXX_FLAGS=--gcc-toolchain=/root/gcc/9") - else() - unset(ADDITIONAL_FLAGS) - endif() - - add_custom_target(ci_test_compiler_${COMPILER} - COMMAND CXX=${COMPILER} ${CMAKE_COMMAND} - -DCMAKE_BUILD_TYPE=Debug -GNinja - -DJSON_BuildTests=ON -DJSON_FastTests=ON - -S${PROJECT_SOURCE_DIR} -B${PROJECT_BINARY_DIR}/build_compiler_${COMPILER} - ${ADDITIONAL_FLAGS} - COMMAND ${CMAKE_COMMAND} --build ${PROJECT_BINARY_DIR}/build_compiler_${COMPILER} - COMMAND cd ${PROJECT_BINARY_DIR}/build_compiler_${COMPILER} && ${CMAKE_CTEST_COMMAND} --parallel ${N} --exclude-regex "test-unicode" --output-on-failure - COMMENT "Compile and test with ${COMPILER}" - ) - endif() - unset(COMPILER_TOOL CACHE) -endforeach() - -############################################################################### -# CUDA example -############################################################################### - -add_custom_target(ci_cuda_example - COMMAND ${CMAKE_COMMAND} - -DCMAKE_BUILD_TYPE=Debug -GNinja - -DCMAKE_CUDA_HOST_COMPILER=g++-8 - -S${PROJECT_SOURCE_DIR}/tests/cuda_example -B${PROJECT_BINARY_DIR}/build_cuda_example - COMMAND ${CMAKE_COMMAND} --build ${PROJECT_BINARY_DIR}/build_cuda_example -) - -############################################################################### -# Intel C++ Compiler -############################################################################### - -add_custom_target(ci_icpc - COMMAND ${CMAKE_COMMAND} - -DCMAKE_BUILD_TYPE=Debug -GNinja - -DCMAKE_C_COMPILER=icc -DCMAKE_CXX_COMPILER=icpc - -DJSON_BuildTests=ON -DJSON_FastTests=ON - -S${PROJECT_SOURCE_DIR} -B${PROJECT_BINARY_DIR}/build_icpc - COMMAND ${CMAKE_COMMAND} --build ${PROJECT_BINARY_DIR}/build_icpc - COMMAND cd ${PROJECT_BINARY_DIR}/build_icpc && ${CMAKE_CTEST_COMMAND} --parallel ${N} --exclude-regex "test-unicode" --output-on-failure - COMMENT "Compile and test with ICPC" -) - -############################################################################### -# test documentation -############################################################################### - -add_custom_target(ci_test_examples - COMMAND make CXX="${GCC_TOOL}" check_output_portable -j8 - WORKING_DIRECTORY ${PROJECT_SOURCE_DIR}/docs - COMMENT "Check that all examples compile and create the desired output" -) - -add_custom_target(ci_test_api_documentation - COMMAND ${Python3_EXECUTABLE} scripts/check_structure.py - WORKING_DIRECTORY ${PROJECT_SOURCE_DIR}/docs/mkdocs - COMMENT "Lint the API documentation" -) - -############################################################################### -# Clean up all generated files. -############################################################################### - -add_custom_target(ci_clean - COMMAND rm -fr ${PROJECT_BINARY_DIR}/build_* cmake-3.1.0-Darwin64 ${JSON_CMAKE_FLAG_BUILD_DIRS} ${single_binaries} - COMMENT "Clean generated directories" -) diff --git a/app/jni/src/libultraship/extern/nlohmann-json/cmake/config.cmake.in b/app/jni/src/libultraship/extern/nlohmann-json/cmake/config.cmake.in deleted file mode 100644 index 9a17a7d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/cmake/config.cmake.in +++ /dev/null @@ -1,15 +0,0 @@ -include(FindPackageHandleStandardArgs) -set(${CMAKE_FIND_PACKAGE_NAME}_CONFIG ${CMAKE_CURRENT_LIST_FILE}) -find_package_handle_standard_args(@PROJECT_NAME@ CONFIG_MODE) - -if(NOT TARGET @PROJECT_NAME@::@NLOHMANN_JSON_TARGET_NAME@) - include("${CMAKE_CURRENT_LIST_DIR}/@NLOHMANN_JSON_TARGETS_EXPORT_NAME@.cmake") - if((NOT TARGET @NLOHMANN_JSON_TARGET_NAME@) AND - (NOT @PROJECT_NAME@_FIND_VERSION OR - @PROJECT_NAME@_FIND_VERSION VERSION_LESS 3.2.0)) - add_library(@NLOHMANN_JSON_TARGET_NAME@ INTERFACE IMPORTED) - set_target_properties(@NLOHMANN_JSON_TARGET_NAME@ PROPERTIES - INTERFACE_LINK_LIBRARIES @PROJECT_NAME@::@NLOHMANN_JSON_TARGET_NAME@ - ) - endif() -endif() diff --git a/app/jni/src/libultraship/extern/nlohmann-json/cmake/download_test_data.cmake b/app/jni/src/libultraship/extern/nlohmann-json/cmake/download_test_data.cmake deleted file mode 100644 index 1bb998d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/cmake/download_test_data.cmake +++ /dev/null @@ -1,56 +0,0 @@ -set(JSON_TEST_DATA_URL https://github.com/nlohmann/json_test_data) -set(JSON_TEST_DATA_VERSION 3.1.0) - -# if variable is set, use test data from given directory rather than downloading them -if(JSON_TestDataDirectory) - message(STATUS "Using test data in ${JSON_TestDataDirectory}.") - add_custom_target(download_test_data) - file(WRITE ${CMAKE_BINARY_DIR}/include/test_data.hpp "#define TEST_DATA_DIRECTORY \"${JSON_TestDataDirectory}\"\n") -else() - find_package(Git) - # target to download test data - add_custom_target(download_test_data - COMMAND test -d json_test_data || ${GIT_EXECUTABLE} clone -c advice.detachedHead=false --branch v${JSON_TEST_DATA_VERSION} ${JSON_TEST_DATA_URL}.git --quiet --depth 1 - COMMENT "Downloading test data from ${JSON_TEST_DATA_URL} (v${JSON_TEST_DATA_VERSION})" - WORKING_DIRECTORY ${CMAKE_BINARY_DIR} - ) - # create a header with the path to the downloaded test data - file(WRITE ${CMAKE_BINARY_DIR}/include/test_data.hpp "#define TEST_DATA_DIRECTORY \"${CMAKE_BINARY_DIR}/json_test_data\"\n") -endif() - -# determine the operating system (for debug and support purposes) -find_program(UNAME_COMMAND uname) -find_program(VER_COMMAND ver) -find_program(LSB_RELEASE_COMMAND lsb_release) -find_program(SW_VERS_COMMAND sw_vers) -set(OS_VERSION_STRINGS "${CMAKE_SYSTEM}") -if (VER_COMMAND) - execute_process(COMMAND ${VER_COMMAND} OUTPUT_VARIABLE VER_COMMAND_RESULT OUTPUT_STRIP_TRAILING_WHITESPACE) - set(OS_VERSION_STRINGS "${OS_VERSION_STRINGS}; ${VER_COMMAND_RESULT}") -endif() -if (SW_VERS_COMMAND) - execute_process(COMMAND ${SW_VERS_COMMAND} OUTPUT_VARIABLE SW_VERS_COMMAND_RESULT OUTPUT_STRIP_TRAILING_WHITESPACE ERROR_QUIET) - string(REGEX REPLACE "[ ]*\n" "; " SW_VERS_COMMAND_RESULT "${SW_VERS_COMMAND_RESULT}") - set(OS_VERSION_STRINGS "${OS_VERSION_STRINGS}; ${SW_VERS_COMMAND_RESULT}") -endif() -if (LSB_RELEASE_COMMAND) - execute_process(COMMAND ${LSB_RELEASE_COMMAND} -a OUTPUT_VARIABLE LSB_RELEASE_COMMAND_RESULT OUTPUT_STRIP_TRAILING_WHITESPACE ERROR_QUIET) - string(REGEX REPLACE "[ ]*\n" "; " LSB_RELEASE_COMMAND_RESULT "${LSB_RELEASE_COMMAND_RESULT}") - set(OS_VERSION_STRINGS "${OS_VERSION_STRINGS}; ${LSB_RELEASE_COMMAND_RESULT}") -endif() -if (UNAME_COMMAND) - execute_process(COMMAND ${UNAME_COMMAND} -a OUTPUT_VARIABLE UNAME_COMMAND_RESULT OUTPUT_STRIP_TRAILING_WHITESPACE ERROR_QUIET) - set(OS_VERSION_STRINGS "${OS_VERSION_STRINGS}; ${UNAME_COMMAND_RESULT}") -endif() - -message(STATUS "Operating system: ${OS_VERSION_STRINGS}") - -# determine the compiler (for debug and support purposes) -if (MSVC) - execute_process(COMMAND ${CMAKE_CXX_COMPILER} OUTPUT_VARIABLE CXX_VERSION_RESULT OUTPUT_STRIP_TRAILING_WHITESPACE ERROR_VARIABLE CXX_VERSION_RESULT ERROR_STRIP_TRAILING_WHITESPACE) - set(CXX_VERSION_RESULT "${CXX_VERSION_RESULT}; MSVC_VERSION=${MSVC_VERSION}; MSVC_TOOLSET_VERSION=${MSVC_TOOLSET_VERSION}") -else() - execute_process(COMMAND ${CMAKE_CXX_COMPILER} --version OUTPUT_VARIABLE CXX_VERSION_RESULT OUTPUT_STRIP_TRAILING_WHITESPACE) -endif() -string(REGEX REPLACE "[ ]*\n" "; " CXX_VERSION_RESULT "${CXX_VERSION_RESULT}") -message(STATUS "Compiler: ${CXX_VERSION_RESULT}") diff --git a/app/jni/src/libultraship/extern/nlohmann-json/cmake/nlohmann_jsonConfigVersion.cmake.in b/app/jni/src/libultraship/extern/nlohmann-json/cmake/nlohmann_jsonConfigVersion.cmake.in deleted file mode 100644 index 1091085..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/cmake/nlohmann_jsonConfigVersion.cmake.in +++ /dev/null @@ -1,20 +0,0 @@ -# This is essentially cmake's BasicConfigVersion-SameMajorVersion.cmake.in but -# without the 32/64-bit check. Since json is a header-only library, it doesn't -# matter if it was built on a different platform than what it is used on (see -# https://github.com/nlohmann/json/issues/1697). -set(PACKAGE_VERSION "@PROJECT_VERSION@") - -if(PACKAGE_VERSION VERSION_LESS PACKAGE_FIND_VERSION) - set(PACKAGE_VERSION_COMPATIBLE FALSE) -else() - - if(PACKAGE_FIND_VERSION_MAJOR STREQUAL "@PROJECT_VERSION_MAJOR@") - set(PACKAGE_VERSION_COMPATIBLE TRUE) - else() - set(PACKAGE_VERSION_COMPATIBLE FALSE) - endif() - - if(PACKAGE_FIND_VERSION STREQUAL PACKAGE_VERSION) - set(PACKAGE_VERSION_EXACT TRUE) - endif() -endif() diff --git a/app/jni/src/libultraship/extern/nlohmann-json/cmake/pkg-config.pc.in b/app/jni/src/libultraship/extern/nlohmann-json/cmake/pkg-config.pc.in deleted file mode 100644 index d36317f..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/cmake/pkg-config.pc.in +++ /dev/null @@ -1,4 +0,0 @@ -Name: ${PROJECT_NAME} -Description: JSON for Modern C++ -Version: ${PROJECT_VERSION} -Cflags: -I${CMAKE_INSTALL_FULL_INCLUDEDIR} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/cmake/test.cmake b/app/jni/src/libultraship/extern/nlohmann-json/cmake/test.cmake deleted file mode 100644 index bb840c6..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/cmake/test.cmake +++ /dev/null @@ -1,273 +0,0 @@ -set(_json_test_cmake_list_file ${CMAKE_CURRENT_LIST_FILE}) - -############################################################################# -# download test data -############################################################################# - -include(download_test_data) - -# test fixture to download test data -add_test(NAME "download_test_data" COMMAND ${CMAKE_COMMAND} --build ${CMAKE_BINARY_DIR} - --target download_test_data -) -set_tests_properties(download_test_data PROPERTIES FIXTURES_SETUP TEST_DATA) - -if(JSON_Valgrind) - find_program(CMAKE_MEMORYCHECK_COMMAND valgrind) - message(STATUS "Executing test suite with Valgrind (${CMAKE_MEMORYCHECK_COMMAND})") - set(memcheck_command "${CMAKE_MEMORYCHECK_COMMAND} ${CMAKE_MEMORYCHECK_COMMAND_OPTIONS} --error-exitcode=1 --leak-check=full") - separate_arguments(memcheck_command) -endif() - -############################################################################# -# detect standard support -############################################################################# - -# C++11 is the minimum required -set(compiler_supports_cpp_11 TRUE) - -foreach(feature ${CMAKE_CXX_COMPILE_FEATURES}) - if (${feature} STREQUAL cxx_std_14) - set(compiler_supports_cpp_14 TRUE) - elseif (${feature} STREQUAL cxx_std_17) - set(compiler_supports_cpp_17 TRUE) - elseif (${feature} STREQUAL cxx_std_20) - set(compiler_supports_cpp_20 TRUE) - elseif (${feature} STREQUAL cxx_std_23) - set(compiler_supports_cpp_23 TRUE) - endif() -endforeach() - -############################################################################# -# test functions -############################################################################# - -############################################################################# -# json_test_set_test_options( -# all| -# [CXX_STANDARDS all|...] -# [COMPILE_DEFINITIONS ...] -# [COMPILE_FEATURES ...] -# [COMPILE_OPTIONS ...] -# [LINK_LIBRARIES ...] -# [LINK_OPTIONS ...] -# [TEST_PROPERTIES ...]) -# -# Supply test- and standard-specific build settings and/or test properties. -# Specify multiple tests using a list e.g., "test-foo;test-bar". -# -# Must be called BEFORE the test is created. -############################################################################# - -function(json_test_set_test_options tests) - cmake_parse_arguments(args "" "" - "CXX_STANDARDS;COMPILE_DEFINITIONS;COMPILE_FEATURES;COMPILE_OPTIONS;LINK_LIBRARIES;LINK_OPTIONS;TEST_PROPERTIES" - ${ARGN}) - - if(NOT args_CXX_STANDARDS) - set(args_CXX_STANDARDS "all") - endif() - - foreach(test ${tests}) - if("${test}" STREQUAL "all") - set(test "") - endif() - - foreach(cxx_standard ${args_CXX_STANDARDS}) - if("${cxx_standard}" STREQUAL "all") - if("${test}" STREQUAL "") - message(FATAL_ERROR "Not supported. Change defaults in: ${_json_test_cmake_list_file}") - endif() - set(test_interface _json_test_interface_${test}) - else() - set(test_interface _json_test_interface_${test}_cpp_${cxx_standard}) - endif() - - if(NOT TARGET ${test_interface}) - add_library(${test_interface} INTERFACE) - endif() - - target_compile_definitions(${test_interface} INTERFACE ${args_COMPILE_DEFINITIONS}) - target_compile_features(${test_interface} INTERFACE ${args_COMPILE_FEATURES}) - target_compile_options(${test_interface} INTERFACE ${args_COMPILE_OPTIONS}) - target_link_libraries (${test_interface} INTERFACE ${args_LINK_LIBRARIES}) - target_link_options(${test_interface} INTERFACE ${args_LINK_OPTIONS}) - #set_target_properties(${test_interface} PROPERTIES JSON_TEST_PROPERTIES "${args_TEST_PROPERTIES}") - set_property(DIRECTORY PROPERTY - ${test_interface}_TEST_PROPERTIES "${args_TEST_PROPERTIES}" - ) - endforeach() - endforeach() -endfunction() - -# for internal use by _json_test_add_test() -function(_json_test_apply_test_properties test_target properties_target) - #get_target_property(test_properties ${properties_target} JSON_TEST_PROPERTIES) - get_property(test_properties DIRECTORY PROPERTY ${properties_target}_TEST_PROPERTIES) - if(test_properties) - set_tests_properties(${test_target} PROPERTIES ${test_properties}) - endif() -endfunction() - -# for internal use by json_test_add_test_for() -function(_json_test_add_test test_name file main cxx_standard) - set(test_target ${test_name}_cpp${cxx_standard}) - - if(TARGET ${test_target}) - message(FATAL_ERROR "Target ${test_target} has already been added.") - endif() - - add_executable(${test_target} ${file}) - target_link_libraries(${test_target} PRIVATE ${main}) - - # set and require C++ standard - set_target_properties(${test_target} PROPERTIES - CXX_STANDARD ${cxx_standard} - CXX_STANDARD_REQUIRED ON - ) - - # apply standard-specific build settings - if(TARGET _json_test_interface__cpp_${cxx_standard}) - target_link_libraries(${test_target} PRIVATE _json_test_interface__cpp_${cxx_standard}) - endif() - - # apply test-specific build settings - if(TARGET _json_test_interface_${test_name}) - target_link_libraries(${test_target} PRIVATE _json_test_interface_${test_name}) - endif() - - # apply test- and standard-specific build settings - if(TARGET _json_test_interface_${test_name}_cpp_${cxx_standard}) - target_link_libraries(${test_target} PRIVATE - _json_test_interface_${test_name}_cpp_${cxx_standard} - ) - endif() - - if (JSON_FastTests) - add_test(NAME ${test_target} - COMMAND ${test_target} ${DOCTEST_TEST_FILTER} - WORKING_DIRECTORY ${CMAKE_SOURCE_DIR} - ) - else() - add_test(NAME ${test_target} - COMMAND ${test_target} ${DOCTEST_TEST_FILTER} --no-skip - WORKING_DIRECTORY ${CMAKE_SOURCE_DIR} - ) - endif() - set_tests_properties(${test_target} PROPERTIES LABELS "all" FIXTURES_REQUIRED TEST_DATA) - - # apply standard-specific test properties - if(TARGET _json_test_interface__cpp_${cxx_standard}) - _json_test_apply_test_properties(${test_target} _json_test_interface__cpp_${cxx_standard}) - endif() - - # apply test-specific test properties - if(TARGET _json_test_interface_${test_name}) - _json_test_apply_test_properties(${test_target} _json_test_interface_${test_name}) - endif() - - # apply test- and standard-specific test properties - if(TARGET _json_test_interface_${test_name}_cpp_${cxx_standard}) - _json_test_apply_test_properties(${test_target} - _json_test_interface_${test_name}_cpp_${cxx_standard} - ) - endif() - - if(JSON_Valgrind) - add_test(NAME ${test_target}_valgrind - COMMAND ${memcheck_command} $ ${DOCTEST_TEST_FILTER} - WORKING_DIRECTORY ${CMAKE_SOURCE_DIR} - ) - set_tests_properties(${test_target}_valgrind PROPERTIES - LABELS "valgrind" FIXTURES_REQUIRED TEST_DATA - ) - endif() -endfunction() - -############################################################################# -# json_test_add_test_for( -# -# [NAME ] -# MAIN
-# [CXX_STANDARDS ...] [FORCE]) -# -# Given a unit-foo.cpp, produces -# -# test-foo_cpp -# -# if C++ standard is supported by the compiler and the -# source file contains JSON_HAS_CPP_. -# Use NAME to override the filename-derived test name. -# Use FORCE to create the test regardless of the file containing -# JSON_HAS_CPP_. -# Test targets are linked against
. -# CXX_STANDARDS defaults to "11". -############################################################################# - -function(json_test_add_test_for file) - cmake_parse_arguments(args "FORCE" "MAIN;NAME" "CXX_STANDARDS" ${ARGN}) - - if("${args_MAIN}" STREQUAL "") - message(FATAL_ERROR "Required argument MAIN
missing.") - endif() - - if("${args_NAME}" STREQUAL "") - get_filename_component(file_basename ${file} NAME_WE) - string(REGEX REPLACE "unit-([^$]+)" "test-\\1" test_name ${file_basename}) - else() - set(test_name ${args_NAME}) - if(NOT test_name MATCHES "test-[^$]+") - message(FATAL_ERROR "Test name must start with 'test-'.") - endif() - endif() - - if("${args_CXX_STANDARDS}" STREQUAL "") - set(args_CXX_STANDARDS 11) - endif() - - file(READ ${file} file_content) - foreach(cxx_standard ${args_CXX_STANDARDS}) - if(NOT compiler_supports_cpp_${cxx_standard}) - continue() - endif() - - # add unconditionally if C++11 (default) or forced - if(NOT ("${cxx_standard}" STREQUAL 11 OR args_FORCE)) - string(FIND "${file_content}" JSON_HAS_CPP_${cxx_standard} has_cpp_found) - if(${has_cpp_found} EQUAL -1) - continue() - endif() - endif() - - _json_test_add_test(${test_name} ${file} ${args_MAIN} ${cxx_standard}) - endforeach() -endfunction() - -############################################################################# -# json_test_should_build_32bit_test( -# ) -# -# Check if the 32bit unit test should be built based on the value of -# and store the result in the variables and -# . -############################################################################# - -function(json_test_should_build_32bit_test build_32bit_var build_32bit_only_var input) - set(${build_32bit_only_var} OFF PARENT_SCOPE) - string(TOUPPER "${input}" ${build_32bit_var}) - if("${${build_32bit_var}}" STREQUAL AUTO) - # check if compiler is targeting 32bit by default - include(CheckTypeSize) - check_type_size("size_t" sizeof_size_t LANGUAGE CXX) - if(sizeof_size_t AND ${sizeof_size_t} EQUAL 4) - message(STATUS "Auto-enabling 32bit unit test.") - set(${build_32bit_var} ON) - else() - set(${build_32bit_var} OFF) - endif() - elseif("${${build_32bit_var}}" STREQUAL ONLY) - set(${build_32bit_only_var} ON PARENT_SCOPE) - endif() - - set(${build_32bit_var} "${${build_32bit_var}}" PARENT_SCOPE) -endfunction() diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/Makefile b/app/jni/src/libultraship/extern/nlohmann-json/docs/Makefile deleted file mode 100644 index 35c30da..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/Makefile +++ /dev/null @@ -1,45 +0,0 @@ -SRCDIR = ../single_include - -all: create_output - -########################################################################## -# example files -########################################################################## - -# where are the example cpp files -EXAMPLES = $(wildcard examples/*.cpp) - -cxx_standard = $(lastword c++11 $(filter c++%, $(subst ., ,$1))) - -# create output from a stand-alone example file -%.output: %.cpp - @echo "standard $(call cxx_standard $(<:.cpp=))" - $(MAKE) $(<:.cpp=) \ - CPPFLAGS="-I $(SRCDIR) -DJSON_USE_GLOBAL_UDLS=0" \ - CXXFLAGS="-std=$(call cxx_standard,$(<:.cpp=)) -Wno-deprecated-declarations" - ./$(<:.cpp=) > $@ - rm $(<:.cpp=) - -# compare created output with current output of the example files -%.test: %.cpp - $(MAKE) $(<:.cpp=) \ - CPPFLAGS="-I $(SRCDIR) -DJSON_USE_GLOBAL_UDLS=0" \ - CXXFLAGS="-std=$(call cxx_standard,$(<:.cpp=)) -Wno-deprecated-declarations" - ./$(<:.cpp=) > $@ - diff $@ $(<:.cpp=.output) - rm $(<:.cpp=) $@ - -# create output from all stand-alone example files -create_output: $(EXAMPLES:.cpp=.output) - -# check output of all stand-alone example files -check_output: $(EXAMPLES:.cpp=.test) - -# check output of all stand-alone example files (exclude files with platform-dependent output.) -# This target is used in the CI (ci_test_documentation). -check_output_portable: $(filter-out examples/meta.test examples/max_size.test examples/std_hash.test examples/basic_json__CompatibleType.test,$(EXAMPLES:.cpp=.test)) - -clean: - rm -fr $(EXAMPLES:.cpp=) - $(MAKE) clean -C docset - $(MAKE) clean -C mkdocs diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/README.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/README.md deleted file mode 100644 index b39d54e..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/README.md +++ /dev/null @@ -1,20 +0,0 @@ -# Documentation - -## Generate documentation - -Note on documentation: The source files contain links to the online documentation at https://json.nlohmann.me. This URL -contains the most recent documentation and should also be applicable to previous versions; documentation for deprecated -functions is not removed, but marked deprecated. - -If you want to see the documentation for a specific tag or commit hash, you can generate it as follows (here for tag -`v3.10.2`): - -```shell -git clone https://github.com/nlohmann/json.git -cd json -git checkout v3.10.2 -make install_venv serve -C docs/mkdocs -``` - -Open URL in your browser. Replace from any URL from the source code `https://json.nlohmann.me` -with `http://127.0.0.1:8000` to see the documentation for your tag or commit hash. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/avatars.png b/app/jni/src/libultraship/extern/nlohmann-json/docs/avatars.png deleted file mode 100644 index 0a25221..0000000 Binary files a/app/jni/src/libultraship/extern/nlohmann-json/docs/avatars.png and /dev/null differ diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/docset/Info.plist b/app/jni/src/libultraship/extern/nlohmann-json/docs/docset/Info.plist deleted file mode 100644 index 772ec08..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/docset/Info.plist +++ /dev/null @@ -1,20 +0,0 @@ - - - - - CFBundleIdentifier - nlohmann_json - CFBundleName - JSON for Modern C++ - DocSetPlatformFamily - json - isDashDocset - - dashIndexFilePath - index.html - DashDocSetFallbackURL - https://nlohmann.github.io/json/ - isJavaScriptEnabled - - - diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/docset/Makefile b/app/jni/src/libultraship/extern/nlohmann-json/docs/docset/Makefile deleted file mode 100644 index eb1cfd3..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/docset/Makefile +++ /dev/null @@ -1,87 +0,0 @@ -SHELL=/usr/bin/env bash -SED ?= $(shell which gsed 2>/dev/null || which sed) - -MKDOCS_PAGES=$(shell cd ../mkdocs/docs/ && find * -type f -name '*.md' | sort) - -.PHONY: all -all: JSON_for_Modern_C++.tgz - -docSet.dsidx: docSet.sql - # generate index - sqlite3 docSet.dsidx > "$$(ls JSON_for_Modern_C++.docset/Contents/Resources/Documents/assets/stylesheets/main.*.min.css)" - # fix spacing - echo -e "\n\ndiv.md-sidebar div.md-sidebar--secondary, div.md-main__inner { top: 0; margin-top: 0 }" >> "$$(ls JSON_for_Modern_C++.docset/Contents/Resources/Documents/assets/stylesheets/main.*.min.css)" - # remove "JSON for Modern C++" from page titles (fallback) - find JSON_for_Modern_C++.docset/Contents/Resources/Documents -type f -exec $(SED) -i 's| - JSON for Modern C++||' {} + - # replace page titles with name from index, if available - for page in $(MKDOCS_PAGES); do \ - case "$$page" in \ - */index.md) path=$${page/\/index.md/} ;; \ - *) path=$${page/.md/} ;; \ - esac; \ - title=$$(sqlite3 docSet.dsidx "SELECT name FROM searchIndex WHERE path='$$path/index.html'" | tr '\n' ',' | $(SED) -e 's/,/, /g' -e 's/, $$/\n/'); \ - if [ "x$$title" != "x" ]; then \ - $(SED) -i "s%.*%$$title%" "JSON_for_Modern_C++.docset/Contents/Resources/Documents/$$path/index.html"; \ - fi \ - done - # clean up - rm JSON_for_Modern_C++.docset/Contents/Resources/Documents/sitemap.* - # copy index - cp docSet.dsidx JSON_for_Modern_C++.docset/Contents/Resources/ - -JSON_for_Modern_C++.tgz: JSON_for_Modern_C++.docset - tar --exclude='.DS_Store' -cvzf JSON_for_Modern_C++.tgz JSON_for_Modern_C++.docset - -# install docset for Zeal documentation browser (https://zealdocs.org/) -.PHONY: install_docset_zeal -install_docset_zeal: JSON_for_Modern_C++.docset - docset_root=$${XDG_DATA_HOME:-$$HOME/.local/share}/Zeal/Zeal/docsets; \ - rm -rf $$docset_root/JSON_for_Modern_C++.docset; \ - mkdir -p $$docset_root; \ - cp -r JSON_for_Modern_C++.docset $$docset_root/ - -# list mkdocs pages missing from the docset index -.PHONY: list_missing_pages -list_missing_pages: docSet.dsidx - @for page in $(MKDOCS_PAGES); do \ - case "$$page" in \ - */index.md) path=$${page/\/index.md/} ;; \ - *) path=$${page/.md/} ;; \ - esac; \ - if [ "x$$page" != "xindex.md" -a "x$$(sqlite3 docSet.dsidx "SELECT COUNT(*) FROM searchIndex WHERE path='$$path/index.html'")" = "x0" ]; then \ - echo $$page; \ - fi \ - done - -# list paths in the docset index without a corresponding mkdocs page -.PHONY: list_removed_paths -list_removed_paths: docSet.dsidx - @for path in $$(sqlite3 docSet.dsidx "SELECT path FROM searchIndex"); do \ - page=$${path/\/index.html/.md}; \ - page_index=$${path/index.html/index.md}; \ - page_found=0; \ - for p in $(MKDOCS_PAGES); do \ - if [ "x$$p" = "x$$page" -o "x$$p" = "x$$page_index" ]; then \ - page_found=1; \ - fi \ - done; \ - if [ "x$$page_found" = "x0" ]; then \ - echo $$path; \ - fi \ - done - -.PHONY: clean -clean: - rm -f docSet.dsidx - rm -fr JSON_for_Modern_C++.docset JSON_for_Modern_C++.tgz diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/docset/README.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/docset/README.md deleted file mode 100644 index 79a778e..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/docset/README.md +++ /dev/null @@ -1,19 +0,0 @@ -# docset - -The folder contains the required files to create a [docset](https://kapeli.com/docsets) which can be used in -documentation browsers like [Dash](https://kapeli.com/dash), [Velocity](https://velocity.silverlakesoftware.com), or -[Zeal](https://zealdocs.org). - -The docset can be created with - -```sh -make nlohmann_json.docset -``` - -The generated folder `nlohmann_json.docset` can then be opened in the documentation browser. - -A recent version is also part of the [Dash user contributions](https://github.com/Kapeli/Dash-User-Contributions/tree/master/docsets/JSON_for_Modern_C%2B%2B). - -## Licenses - -The [JSON logo](https://commons.wikimedia.org/wiki/File:JSON_vector_logo.svg) is public domain. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/docset/docSet.sql b/app/jni/src/libultraship/extern/nlohmann-json/docs/docset/docSet.sql deleted file mode 100644 index f97647d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/docset/docSet.sql +++ /dev/null @@ -1,233 +0,0 @@ -DROP TABLE IF EXISTS searchIndex; -CREATE TABLE searchIndex(id INTEGER PRIMARY KEY, name TEXT, type TEXT, path TEXT); -CREATE UNIQUE INDEX anchor ON searchIndex (name, type, path); - --- API -INSERT INTO searchIndex(name, type, path) VALUES ('adl_serializer', 'Class', 'api/adl_serializer/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('adl_serializer::from_json', 'Function', 'api/adl_serializer/from_json/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('adl_serializer::to_json', 'Function', 'api/adl_serializer/to_json/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('byte_container_with_subtype', 'Class', 'api/byte_container_with_subtype/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('byte_container_with_subtype::byte_container_with_subtype', 'Constructor', 'api/byte_container_with_subtype/byte_container_with_subtype/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('byte_container_with_subtype::clear_subtype', 'Method', 'api/byte_container_with_subtype/clear_subtype/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('byte_container_with_subtype::has_subtype', 'Method', 'api/byte_container_with_subtype/has_subtype/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('byte_container_with_subtype::set_subtype', 'Method', 'api/byte_container_with_subtype/set_subtype/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('byte_container_with_subtype::subtype', 'Method', 'api/byte_container_with_subtype/subtype/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json', 'Class', 'api/basic_json/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::accept', 'Function', 'api/basic_json/accept/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::array', 'Function', 'api/basic_json/array/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::array_t', 'Type', 'api/basic_json/array_t/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::at', 'Method', 'api/basic_json/at/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::back', 'Method', 'api/basic_json/back/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::basic_json', 'Constructor', 'api/basic_json/basic_json/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::begin', 'Method', 'api/basic_json/begin/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::binary', 'Function', 'api/basic_json/binary/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::binary_t', 'Type', 'api/basic_json/binary_t/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::boolean_t', 'Type', 'api/basic_json/boolean_t/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::cbegin', 'Method', 'api/basic_json/cbegin/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::cbor_tag_handler_t', 'Enum', 'api/basic_json/cbor_tag_handler_t/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::cend', 'Method', 'api/basic_json/cend/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::clear', 'Method', 'api/basic_json/clear/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::contains', 'Method', 'api/basic_json/contains/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::count', 'Method', 'api/basic_json/count/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::crbegin', 'Method', 'api/basic_json/crbegin/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::crend', 'Method', 'api/basic_json/crend/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::default_object_comparator_t', 'Type', 'api/basic_json/default_object_comparator_t/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::diff', 'Function', 'api/basic_json/diff/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::dump', 'Method', 'api/basic_json/dump/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::emplace', 'Method', 'api/basic_json/emplace/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::emplace_back', 'Method', 'api/basic_json/emplace_back/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::empty', 'Method', 'api/basic_json/empty/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::end', 'Method', 'api/basic_json/end/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::erase', 'Method', 'api/basic_json/erase/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::error_handler_t', 'Enum', 'api/basic_json/error_handler_t/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::exception', 'Class', 'api/basic_json/exception/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::find', 'Method', 'api/basic_json/find/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::flatten', 'Method', 'api/basic_json/flatten/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::from_bjdata', 'Function', 'api/basic_json/from_bjdata/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::from_bson', 'Function', 'api/basic_json/from_bson/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::from_cbor', 'Function', 'api/basic_json/from_cbor/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::from_msgpack', 'Function', 'api/basic_json/from_msgpack/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::from_ubjson', 'Function', 'api/basic_json/from_ubjson/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::front', 'Method', 'api/basic_json/front/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::get', 'Method', 'api/basic_json/get/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::get_allocator', 'Function', 'api/basic_json/get_allocator/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::get_binary', 'Method', 'api/basic_json/get_binary/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::get_ptr', 'Method', 'api/basic_json/get_ptr/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::get_ref', 'Method', 'api/basic_json/get_ref/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::get_to', 'Method', 'api/basic_json/get_to/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::input_format_t', 'Enum', 'api/basic_json/input_format_t/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::insert', 'Method', 'api/basic_json/insert/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::invalid_iterator', 'Class', 'api/basic_json/invalid_iterator/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::is_array', 'Method', 'api/basic_json/is_array/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::is_binary', 'Method', 'api/basic_json/is_binary/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::is_boolean', 'Method', 'api/basic_json/is_boolean/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::is_discarded', 'Method', 'api/basic_json/is_discarded/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::is_null', 'Method', 'api/basic_json/is_null/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::is_number', 'Method', 'api/basic_json/is_number/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::is_number_float', 'Method', 'api/basic_json/is_number_float/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::is_number_integer', 'Method', 'api/basic_json/is_number_integer/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::is_number_unsigned', 'Method', 'api/basic_json/is_number_unsigned/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::is_object', 'Method', 'api/basic_json/is_object/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::is_primitive', 'Method', 'api/basic_json/is_primitive/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::is_string', 'Method', 'api/basic_json/is_string/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::is_structured', 'Method', 'api/basic_json/is_structured/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::items', 'Method', 'api/basic_json/items/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::json_serializer', 'Class', 'api/basic_json/json_serializer/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::max_size', 'Method', 'api/basic_json/max_size/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::merge_patch', 'Method', 'api/basic_json/merge_patch/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::meta', 'Function', 'api/basic_json/meta/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::number_float_t', 'Type', 'api/basic_json/number_float_t/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::number_integer_t', 'Type', 'api/basic_json/number_integer_t/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::number_unsigned_t', 'Type', 'api/basic_json/number_unsigned_t/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::object', 'Function', 'api/basic_json/object/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::object_comparator_t', 'Type', 'api/basic_json/object_comparator_t/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::object_t', 'Type', 'api/basic_json/object_t/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::operator ValueType', 'Operator', 'api/basic_json/operator_ValueType/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::operator value_t', 'Operator', 'api/basic_json/operator_value_t/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::operator[]', 'Operator', 'api/basic_json/operator[]/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::operator=', 'Operator', 'api/basic_json/operator=/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::operator+=', 'Operator', 'api/basic_json/operator+=/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::operator==', 'Operator', 'api/basic_json/operator_eq/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::operator!=', 'Operator', 'api/basic_json/operator_ne/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::operator<', 'Operator', 'api/basic_json/operator_lt/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::operator<=', 'Operator', 'api/basic_json/operator_le/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::operator>', 'Operator', 'api/basic_json/operator_gt/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::operator>=', 'Operator', 'api/basic_json/operator_ge/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::operator<=>', 'Operator', 'api/basic_json/operator_spaceship/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::out_of_range', 'Class', 'api/basic_json/out_of_range/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::other_error', 'Class', 'api/basic_json/other_error/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::parse', 'Function', 'api/basic_json/parse/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::parse_error', 'Class', 'api/basic_json/parse_error/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::parse_event_t', 'Enum', 'api/basic_json/parse_event_t/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::parser_callback_t', 'Type', 'api/basic_json/parser_callback_t/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::patch', 'Method', 'api/basic_json/patch/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::patch_inplace', 'Method', 'api/basic_json/patch_inplace/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::push_back', 'Method', 'api/basic_json/push_back/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::rbegin', 'Method', 'api/basic_json/rbegin/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::rend', 'Method', 'api/basic_json/rend/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::sax_parse', 'Function', 'api/basic_json/sax_parse/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::size', 'Method', 'api/basic_json/size/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::string_t', 'Type', 'api/basic_json/string_t/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::swap', 'Method', 'api/basic_json/swap/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::type', 'Method', 'api/basic_json/type/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::type_error', 'Class', 'api/basic_json/type_error/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::type_name', 'Method', 'api/basic_json/type_name/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::unflatten', 'Method', 'api/basic_json/unflatten/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::update', 'Method', 'api/basic_json/update/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::to_bjdata', 'Function', 'api/basic_json/to_bjdata/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::to_bson', 'Function', 'api/basic_json/to_bson/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::to_cbor', 'Function', 'api/basic_json/to_cbor/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::to_msgpack', 'Function', 'api/basic_json/to_msgpack/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::to_string', 'Method', 'api/basic_json/to_string/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::to_ubjson', 'Function', 'api/basic_json/to_ubjson/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::value', 'Method', 'api/basic_json/value/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::value_t', 'Enum', 'api/basic_json/value_t/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('basic_json::~basic_json', 'Method', 'api/basic_json/~basic_json/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('json', 'Class', 'api/json/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('json_pointer', 'Class', 'api/json_pointer/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('json_pointer::back', 'Method', 'api/json_pointer/back/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('json_pointer::empty', 'Method', 'api/json_pointer/empty/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('json_pointer::json_pointer', 'Constructor', 'api/json_pointer/json_pointer/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('json_pointer::operator==', 'Operator', 'api/json_pointer/operator_eq/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('json_pointer::operator!=', 'Operator', 'api/json_pointer/operator_ne/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('json_pointer::operator/', 'Operator', 'api/json_pointer/operator_slash/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('json_pointer::operator/=', 'Operator', 'api/json_pointer/operator_slasheq/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('json_pointer::operator string_t', 'Operator', 'api/json_pointer/operator_string_t/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('json_pointer::parent_pointer', 'Method', 'api/json_pointer/parent_pointer/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('json_pointer::pop_back', 'Method', 'api/json_pointer/pop_back/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('json_pointer::push_back', 'Method', 'api/json_pointer/push_back/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('json_pointer::string_t', 'Type', 'api/json_pointer/string_t/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('json_pointer::to_string', 'Method', 'api/json_pointer/to_string/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('json_sax', 'Class', 'api/json_sax/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('json_sax::binary', 'Method', 'api/json_sax/binary/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('json_sax::boolean', 'Method', 'api/json_sax/boolean/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('json_sax::end_array', 'Method', 'api/json_sax/end_array/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('json_sax::end_object', 'Method', 'api/json_sax/end_object/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('json_sax::key', 'Method', 'api/json_sax/key/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('json_sax::null', 'Method', 'api/json_sax/null/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('json_sax::number_float', 'Method', 'api/json_sax/number_float/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('json_sax::number_integer', 'Method', 'api/json_sax/number_integer/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('json_sax::number_unsigned', 'Method', 'api/json_sax/number_unsigned/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('json_sax::parse_error', 'Method', 'api/json_sax/parse_error/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('json_sax::start_array', 'Method', 'api/json_sax/start_array/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('json_sax::start_object', 'Method', 'api/json_sax/start_object/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('json_sax::string', 'Method', 'api/json_sax/string/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('operator""_json', 'Literal', 'api/operator_literal_json/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('operator""_json_pointer', 'Literal', 'api/operator_literal_json_pointer/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('operator<<', 'Operator', 'api/operator_ltlt/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('operator>>', 'Operator', 'api/operator_gtgt/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('ordered_json', 'Class', 'api/ordered_json/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('ordered_map', 'Class', 'api/ordered_map/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('std::hash', 'Class', 'api/basic_json/std_hash/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('std::swap', 'Function', 'api/basic_json/std_swap/index.html'); - --- Features -INSERT INTO searchIndex(name, type, path) VALUES ('Arbitrary Type Conversions', 'Guide', 'features/arbitrary_types/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('Binary Formats', 'Guide', 'features/binary_formats/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('Binary Formats: BJData', 'Guide', 'features/binary_formats/bjdata/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('Binary Formats: BSON', 'Guide', 'features/binary_formats/bson/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('Binary Formats: CBOR', 'Guide', 'features/binary_formats/cbor/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('Binary Formats: MessagePack', 'Guide', 'features/binary_formats/messagepack/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('Binary Formats: UBJSON', 'Guide', 'features/binary_formats/ubjson/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('Binary Values', 'Guide', 'features/binary_values/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('Comments', 'Guide', 'features/comments/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('Element Access', 'Guide', 'features/element_access/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('Element Access: Access with default value: value', 'Guide', 'features/element_access/default_value/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('Element Access: Checked access: at', 'Guide', 'features/element_access/checked_access/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('Element Access: Unchecked access: operator[]', 'Guide', 'features/element_access/unchecked_access/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('Integration: CMake', 'Guide', 'integration/cmake/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('Integration: Header only', 'Guide', 'integration/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('Integration: Package Managers', 'Guide', 'integration/package_managers/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('Integration: Pkg-config', 'Guide', 'integration/pkg-config/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('Iterators', 'Guide', 'features/iterators/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('JSON Merge Patch', 'Guide', 'features/merge_patch/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('JSON Patch and Diff', 'Guide', 'features/json_patch/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('JSON Pointer', 'Guide', 'features/json_pointer/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('nlohmann Namespace', 'Guide', 'features/namespace/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('Types', 'Guide', 'features/types/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('Types: Number Handling', 'Guide', 'features/types/number_handling/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('Object Order', 'Guide', 'features/object_order/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('Parsing', 'Guide', 'features/parsing/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('Parsing: JSON Lines', 'Guide', 'features/parsing/json_lines/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('Parsing: Parser Callbacks', 'Guide', 'features/parsing/parser_callbacks/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('Parsing: Parsing and Exceptions', 'Guide', 'features/parsing/parse_exceptions/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('Parsing: SAX Interface', 'Guide', 'features/parsing/sax_interface/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('Runtime Assertions', 'Guide', 'features/assertions/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('Specializing enum conversion', 'Guide', 'features/enum_conversion/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('Supported Macros', 'Guide', 'features/macros/index.html'); - --- Macros -INSERT INTO searchIndex(name, type, path) VALUES ('JSON_ASSERT', 'Macro', 'api/macros/json_assert/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('JSON_CATCH_USER', 'Macro', 'api/macros/json_throw_user/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('JSON_DIAGNOSTICS', 'Macro', 'api/macros/json_diagnostics/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('JSON_DISABLE_ENUM_SERIALIZATION', 'Macro', 'api/macros/json_disable_enum_serialization/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('JSON_HAS_CPP_11', 'Macro', 'api/macros/json_has_cpp_11/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('JSON_HAS_CPP_14', 'Macro', 'api/macros/json_has_cpp_11/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('JSON_HAS_CPP_17', 'Macro', 'api/macros/json_has_cpp_11/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('JSON_HAS_CPP_20', 'Macro', 'api/macros/json_has_cpp_11/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('JSON_HAS_EXPERIMENTAL_FILESYSTEM', 'Macro', 'api/macros/json_has_filesystem/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('JSON_HAS_FILESYSTEM', 'Macro', 'api/macros/json_has_filesystem/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('JSON_HAS_RANGES', 'Macro', 'api/macros/json_has_ranges/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('JSON_HAS_THREE_WAY_COMPARISON', 'Macro', 'api/macros/json_has_three_way_comparison/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('JSON_NOEXCEPTION', 'Macro', 'api/macros/json_noexception/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('JSON_NO_IO', 'Macro', 'api/macros/json_no_io/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('JSON_SKIP_LIBRARY_VERSION_CHECK', 'Macro', 'api/macros/json_skip_library_version_check/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('JSON_SKIP_UNSUPPORTED_COMPILER_CHECK', 'Macro', 'api/macros/json_skip_unsupported_compiler_check/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('JSON_THROW_USER', 'Macro', 'api/macros/json_throw_user/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('JSON_TRY_USER', 'Macro', 'api/macros/json_throw_user/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('JSON_USE_GLOBAL_UDLS', 'Macro', 'api/macros/json_use_global_udls/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('JSON_USE_IMPLICIT_CONVERSIONS', 'Macro', 'api/macros/json_use_implicit_conversions/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('JSON_USE_LEGACY_DISCARDED_VALUE_COMPARISON', 'Macro', 'api/macros/json_use_legacy_discarded_value_comparison/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('Macros', 'Macro', 'api/macros/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('NLOHMANN_DEFINE_TYPE_INTRUSIVE', 'Macro', 'api/macros/nlohmann_define_type_intrusive/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('NLOHMANN_DEFINE_TYPE_INTRUSIVE_WITH_DEFAULT', 'Macro', 'api/macros/nlohmann_define_type_intrusive/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE', 'Macro', 'api/macros/nlohmann_define_type_non_intrusive/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE_WITH_DEFAULT', 'Macro', 'api/macros/nlohmann_define_type_non_intrusive/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('NLOHMANN_JSON_NAMESPACE', 'Macro', 'api/macros/nlohmann_json_namespace/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('NLOHMANN_JSON_NAMESPACE_BEGIN', 'Macro', 'api/macros/nlohmann_json_namespace_begin/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('NLOHMANN_JSON_NAMESPACE_END', 'Macro', 'api/macros/nlohmann_json_namespace_begin/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('NLOHMANN_JSON_NAMESPACE_NO_VERSION', 'Macro', 'api/macros/nlohmann_json_namespace_no_version/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('NLOHMANN_JSON_SERIALIZE_ENUM', 'Macro', 'api/macros/nlohmann_json_serialize_enum/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('NLOHMANN_JSON_VERSION_MAJOR', 'Macro', 'api/macros/nlohmann_json_version_major/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('NLOHMANN_JSON_VERSION_MINOR', 'Macro', 'api/macros/nlohmann_json_version_major/index.html'); -INSERT INTO searchIndex(name, type, path) VALUES ('NLOHMANN_JSON_VERSION_PATCH', 'Macro', 'api/macros/nlohmann_json_version_major/index.html'); diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/docset/docset.json b/app/jni/src/libultraship/extern/nlohmann-json/docs/docset/docset.json deleted file mode 100644 index a11cead..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/docset/docset.json +++ /dev/null @@ -1,10 +0,0 @@ -{ - "name": "JSON for Modern C++", - "version": "3.11.2", - "archive": "JSON_for_Modern_C++.tgz", - "author": { - "name": "Niels Lohmann", - "link": "https://twitter.com/nlohmann" - }, - "aliases": ["nlohmann/json"] -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/docset/icon.png b/app/jni/src/libultraship/extern/nlohmann-json/docs/docset/icon.png deleted file mode 100644 index 7197d0a..0000000 Binary files a/app/jni/src/libultraship/extern/nlohmann-json/docs/docset/icon.png and /dev/null differ diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/docset/icon@2x.png b/app/jni/src/libultraship/extern/nlohmann-json/docs/docset/icon@2x.png deleted file mode 100644 index 5f2fac8..0000000 Binary files a/app/jni/src/libultraship/extern/nlohmann-json/docs/docset/icon@2x.png and /dev/null differ diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/README.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/README.cpp deleted file mode 100644 index 2d641e5..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/README.cpp +++ /dev/null @@ -1,39 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create a JSON object - json j = - { - {"pi", 3.141}, - {"happy", true}, - {"name", "Niels"}, - {"nothing", nullptr}, - { - "answer", { - {"everything", 42} - } - }, - {"list", {1, 0, 2}}, - { - "object", { - {"currency", "USD"}, - {"value", 42.99} - } - } - }; - - // add new values - j["new"]["key"]["value"] = {"another", "list"}; - - // count elements - auto s = j.size(); - j["size"] = s; - - // pretty print with indent of 4 spaces - std::cout << std::setw(4) << j << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/README.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/README.output deleted file mode 100644 index 31188d4..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/README.output +++ /dev/null @@ -1,27 +0,0 @@ -{ - "answer": { - "everything": 42 - }, - "happy": true, - "list": [ - 1, - 0, - 2 - ], - "name": "Niels", - "new": { - "key": { - "value": [ - "another", - "list" - ] - } - }, - "nothing": null, - "object": { - "currency": "USD", - "value": 42.99 - }, - "pi": 3.141, - "size": 8 -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/accept__string.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/accept__string.cpp deleted file mode 100644 index 8eb3d9b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/accept__string.cpp +++ /dev/null @@ -1,26 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - // a valid JSON text - auto valid_text = R"( - { - "numbers": [1, 2, 3] - } - )"; - - // an invalid JSON text - auto invalid_text = R"( - { - "strings": ["extra", "comma", ] - } - )"; - - std::cout << std::boolalpha - << json::accept(valid_text) << ' ' - << json::accept(invalid_text) << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/accept__string.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/accept__string.output deleted file mode 100644 index 836a593..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/accept__string.output +++ /dev/null @@ -1 +0,0 @@ -true false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/array.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/array.cpp deleted file mode 100644 index 139b5ef..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/array.cpp +++ /dev/null @@ -1,19 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON arrays - json j_no_init_list = json::array(); - json j_empty_init_list = json::array({}); - json j_nonempty_init_list = json::array({1, 2, 3, 4}); - json j_list_of_pairs = json::array({ {"one", 1}, {"two", 2} }); - - // serialize the JSON arrays - std::cout << j_no_init_list << '\n'; - std::cout << j_empty_init_list << '\n'; - std::cout << j_nonempty_init_list << '\n'; - std::cout << j_list_of_pairs << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/array.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/array.output deleted file mode 100644 index 4e75a1b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/array.output +++ /dev/null @@ -1,4 +0,0 @@ -[] -[] -[1,2,3,4] -[["one",1],["two",2]] diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/array_t.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/array_t.cpp deleted file mode 100644 index 0964857..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/array_t.cpp +++ /dev/null @@ -1,10 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - std::cout << std::boolalpha << std::is_same, json::array_t>::value << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/array_t.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/array_t.output deleted file mode 100644 index 27ba77d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/array_t.output +++ /dev/null @@ -1 +0,0 @@ -true diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__json_pointer.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__json_pointer.cpp deleted file mode 100644 index 26dfd8e..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__json_pointer.cpp +++ /dev/null @@ -1,104 +0,0 @@ -#include -#include - -using json = nlohmann::json; -using namespace nlohmann::literals; - -int main() -{ - // create a JSON value - json j = - { - {"number", 1}, {"string", "foo"}, {"array", {1, 2}} - }; - - // read-only access - - // output element with JSON pointer "/number" - std::cout << j.at("/number"_json_pointer) << '\n'; - // output element with JSON pointer "/string" - std::cout << j.at("/string"_json_pointer) << '\n'; - // output element with JSON pointer "/array" - std::cout << j.at("/array"_json_pointer) << '\n'; - // output element with JSON pointer "/array/1" - std::cout << j.at("/array/1"_json_pointer) << '\n'; - - // writing access - - // change the string - j.at("/string"_json_pointer) = "bar"; - // output the changed string - std::cout << j["string"] << '\n'; - - // change an array element - j.at("/array/1"_json_pointer) = 21; - // output the changed array - std::cout << j["array"] << '\n'; - - - // out_of_range.106 - try - { - // try to use an array index with leading '0' - json::reference ref = j.at("/array/01"_json_pointer); - } - catch (json::parse_error& e) - { - std::cout << e.what() << '\n'; - } - - // out_of_range.109 - try - { - // try to use an array index that is not a number - json::reference ref = j.at("/array/one"_json_pointer); - } - catch (json::parse_error& e) - { - std::cout << e.what() << '\n'; - } - - // out_of_range.401 - try - { - // try to use an invalid array index - json::reference ref = j.at("/array/4"_json_pointer); - } - catch (json::out_of_range& e) - { - std::cout << e.what() << '\n'; - } - - // out_of_range.402 - try - { - // try to use the array index '-' - json::reference ref = j.at("/array/-"_json_pointer); - } - catch (json::out_of_range& e) - { - std::cout << e.what() << '\n'; - } - - // out_of_range.403 - try - { - // try to use a JSON pointer to a nonexistent object key - json::const_reference ref = j.at("/foo"_json_pointer); - } - catch (json::out_of_range& e) - { - std::cout << e.what() << '\n'; - } - - // out_of_range.404 - try - { - // try to use a JSON pointer that cannot be resolved - json::reference ref = j.at("/number/foo"_json_pointer); - } - catch (json::out_of_range& e) - { - std::cout << e.what() << '\n'; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__json_pointer.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__json_pointer.output deleted file mode 100644 index 1d29893..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__json_pointer.output +++ /dev/null @@ -1,12 +0,0 @@ -1 -"foo" -[1,2] -2 -"bar" -[1,21] -[json.exception.parse_error.106] parse error: array index '01' must not begin with '0' -[json.exception.parse_error.109] parse error: array index 'one' is not a number -[json.exception.out_of_range.401] array index 4 is out of range -[json.exception.out_of_range.402] array index '-' (2) is out of range -[json.exception.out_of_range.403] key 'foo' not found -[json.exception.out_of_range.404] unresolved reference token 'foo' diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__json_pointer_const.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__json_pointer_const.cpp deleted file mode 100644 index f049bd8..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__json_pointer_const.cpp +++ /dev/null @@ -1,80 +0,0 @@ -#include -#include - -using json = nlohmann::json; -using namespace nlohmann::literals; - -int main() -{ - // create a JSON value - const json j = - { - {"number", 1}, {"string", "foo"}, {"array", {1, 2}} - }; - - // read-only access - - // output element with JSON pointer "/number" - std::cout << j.at("/number"_json_pointer) << '\n'; - // output element with JSON pointer "/string" - std::cout << j.at("/string"_json_pointer) << '\n'; - // output element with JSON pointer "/array" - std::cout << j.at("/array"_json_pointer) << '\n'; - // output element with JSON pointer "/array/1" - std::cout << j.at("/array/1"_json_pointer) << '\n'; - - // out_of_range.109 - try - { - // try to use an array index that is not a number - json::const_reference ref = j.at("/array/one"_json_pointer); - } - catch (json::parse_error& e) - { - std::cout << e.what() << '\n'; - } - - // out_of_range.401 - try - { - // try to use an invalid array index - json::const_reference ref = j.at("/array/4"_json_pointer); - } - catch (json::out_of_range& e) - { - std::cout << e.what() << '\n'; - } - - // out_of_range.402 - try - { - // try to use the array index '-' - json::const_reference ref = j.at("/array/-"_json_pointer); - } - catch (json::out_of_range& e) - { - std::cout << e.what() << '\n'; - } - - // out_of_range.403 - try - { - // try to use a JSON pointer to a nonexistent object key - json::const_reference ref = j.at("/foo"_json_pointer); - } - catch (json::out_of_range& e) - { - std::cout << e.what() << '\n'; - } - - // out_of_range.404 - try - { - // try to use a JSON pointer that cannot be resolved - json::const_reference ref = j.at("/number/foo"_json_pointer); - } - catch (json::out_of_range& e) - { - std::cout << e.what() << '\n'; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__json_pointer_const.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__json_pointer_const.output deleted file mode 100644 index aaf8f18..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__json_pointer_const.output +++ /dev/null @@ -1,9 +0,0 @@ -1 -"foo" -[1,2] -2 -[json.exception.parse_error.109] parse error: array index 'one' is not a number -[json.exception.out_of_range.401] array index 4 is out of range -[json.exception.out_of_range.402] array index '-' (2) is out of range -[json.exception.out_of_range.403] key 'foo' not found -[json.exception.out_of_range.404] unresolved reference token 'foo' diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__keytype.c++17.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__keytype.c++17.cpp deleted file mode 100644 index 3491cb9..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__keytype.c++17.cpp +++ /dev/null @@ -1,50 +0,0 @@ -#include -#include -#include - -using namespace std::string_view_literals; -using json = nlohmann::json; - -int main() -{ - // create JSON object - json object = - { - {"the good", "il buono"}, - {"the bad", "il cattivo"}, - {"the ugly", "il brutto"} - }; - - // output element with key "the ugly" using string_view - std::cout << object.at("the ugly"sv) << '\n'; - - // change element with key "the bad" using string_view - object.at("the bad"sv) = "il cattivo"; - - // output changed array - std::cout << object << '\n'; - - - // exception type_error.304 - try - { - // use at() with string_view on a non-object type - json str = "I am a string"; - str.at("the good"sv) = "Another string"; - } - catch (json::type_error& e) - { - std::cout << e.what() << '\n'; - } - - // exception out_of_range.401 - try - { - // try to write at a nonexisting key using string_view - object.at("the fast"sv) = "il rapido"; - } - catch (json::out_of_range& e) - { - std::cout << e.what() << '\n'; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__keytype.c++17.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__keytype.c++17.output deleted file mode 100644 index b544b72..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__keytype.c++17.output +++ /dev/null @@ -1,4 +0,0 @@ -"il brutto" -{"the bad":"il cattivo","the good":"il buono","the ugly":"il brutto"} -[json.exception.type_error.304] cannot use at() with string -[json.exception.out_of_range.403] key 'the fast' not found diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__keytype_const.c++17.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__keytype_const.c++17.cpp deleted file mode 100644 index ec93c70..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__keytype_const.c++17.cpp +++ /dev/null @@ -1,44 +0,0 @@ -#include -#include -#include - -using namespace std::string_view_literals; -using json = nlohmann::json; - -int main() -{ - // create JSON object - const json object = - { - {"the good", "il buono"}, - {"the bad", "il cattivo"}, - {"the ugly", "il brutto"} - }; - - // output element with key "the ugly" using string_view - std::cout << object.at("the ugly"sv) << '\n'; - - - // exception type_error.304 - try - { - // use at() with string_view on a non-object type - const json str = "I am a string"; - std::cout << str.at("the good"sv) << '\n'; - } - catch (json::type_error& e) - { - std::cout << e.what() << '\n'; - } - - // exception out_of_range.401 - try - { - // try to read from a nonexisting key using string_view - std::cout << object.at("the fast"sv) << '\n'; - } - catch (json::out_of_range) - { - std::cout << "out of range" << '\n'; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__keytype_const.c++17.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__keytype_const.c++17.output deleted file mode 100644 index 40ca3f0..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__keytype_const.c++17.output +++ /dev/null @@ -1,3 +0,0 @@ -"il brutto" -[json.exception.type_error.304] cannot use at() with string -out of range diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__object_t_key_type.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__object_t_key_type.cpp deleted file mode 100644 index 202f8a2..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__object_t_key_type.cpp +++ /dev/null @@ -1,48 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON object - json object = - { - {"the good", "il buono"}, - {"the bad", "il cattivo"}, - {"the ugly", "il brutto"} - }; - - // output element with key "the ugly" - std::cout << object.at("the ugly") << '\n'; - - // change element with key "the bad" - object.at("the bad") = "il cattivo"; - - // output changed array - std::cout << object << '\n'; - - - // exception type_error.304 - try - { - // use at() on a non-object type - json str = "I am a string"; - str.at("the good") = "Another string"; - } - catch (json::type_error& e) - { - std::cout << e.what() << '\n'; - } - - // exception out_of_range.401 - try - { - // try to write at a nonexisting key - object.at("the fast") = "il rapido"; - } - catch (json::out_of_range& e) - { - std::cout << e.what() << '\n'; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__object_t_key_type.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__object_t_key_type.output deleted file mode 100644 index b544b72..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__object_t_key_type.output +++ /dev/null @@ -1,4 +0,0 @@ -"il brutto" -{"the bad":"il cattivo","the good":"il buono","the ugly":"il brutto"} -[json.exception.type_error.304] cannot use at() with string -[json.exception.out_of_range.403] key 'the fast' not found diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__object_t_key_type_const.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__object_t_key_type_const.cpp deleted file mode 100644 index e5244f3..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__object_t_key_type_const.cpp +++ /dev/null @@ -1,42 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON object - const json object = - { - {"the good", "il buono"}, - {"the bad", "il cattivo"}, - {"the ugly", "il brutto"} - }; - - // output element with key "the ugly" - std::cout << object.at("the ugly") << '\n'; - - - // exception type_error.304 - try - { - // use at() on a non-object type - const json str = "I am a string"; - std::cout << str.at("the good") << '\n'; - } - catch (json::type_error& e) - { - std::cout << e.what() << '\n'; - } - - // exception out_of_range.401 - try - { - // try to read from a nonexisting key - std::cout << object.at("the fast") << '\n'; - } - catch (json::out_of_range) - { - std::cout << "out of range" << '\n'; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__object_t_key_type_const.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__object_t_key_type_const.output deleted file mode 100644 index 40ca3f0..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__object_t_key_type_const.output +++ /dev/null @@ -1,3 +0,0 @@ -"il brutto" -[json.exception.type_error.304] cannot use at() with string -out of range diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__size_type.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__size_type.cpp deleted file mode 100644 index 65baedd..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__size_type.cpp +++ /dev/null @@ -1,43 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON array - json array = {"first", "2nd", "third", "fourth"}; - - // output element at index 2 (third element) - std::cout << array.at(2) << '\n'; - - // change element at index 1 (second element) to "second" - array.at(1) = "second"; - - // output changed array - std::cout << array << '\n'; - - - // exception type_error.304 - try - { - // use at() on a non-array type - json str = "I am a string"; - str.at(0) = "Another string"; - } - catch (json::type_error& e) - { - std::cout << e.what() << '\n'; - } - - // exception out_of_range.401 - try - { - // try to write beyond the array limit - array.at(5) = "sixth"; - } - catch (json::out_of_range& e) - { - std::cout << e.what() << '\n'; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__size_type.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__size_type.output deleted file mode 100644 index 5402643..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__size_type.output +++ /dev/null @@ -1,4 +0,0 @@ -"third" -["first","second","third","fourth"] -[json.exception.type_error.304] cannot use at() with string -[json.exception.out_of_range.401] array index 5 is out of range diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__size_type_const.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__size_type_const.cpp deleted file mode 100644 index faa4cff..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__size_type_const.cpp +++ /dev/null @@ -1,37 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON array - const json array = {"first", "2nd", "third", "fourth"}; - - // output element at index 2 (third element) - std::cout << array.at(2) << '\n'; - - - // exception type_error.304 - try - { - // use at() on a non-array type - const json str = "I am a string"; - std::cout << str.at(0) << '\n'; - } - catch (json::type_error& e) - { - std::cout << e.what() << '\n'; - } - - // exception out_of_range.401 - try - { - // try to read beyond the array limit - std::cout << array.at(5) << '\n'; - } - catch (json::out_of_range& e) - { - std::cout << e.what() << '\n'; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__size_type_const.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__size_type_const.output deleted file mode 100644 index 8135a27..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/at__size_type_const.output +++ /dev/null @@ -1,3 +0,0 @@ -"third" -[json.exception.type_error.304] cannot use at() with string -[json.exception.out_of_range.401] array index 5 is out of range diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/back.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/back.cpp deleted file mode 100644 index 1439a82..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/back.cpp +++ /dev/null @@ -1,38 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json j_boolean = true; - json j_number_integer = 17; - json j_number_float = 23.42; - json j_object = {{"one", 1}, {"two", 2}}; - json j_object_empty(json::value_t::object); - json j_array = {1, 2, 4, 8, 16}; - json j_array_empty(json::value_t::array); - json j_string = "Hello, world"; - - // call back() - std::cout << j_boolean.back() << '\n'; - std::cout << j_number_integer.back() << '\n'; - std::cout << j_number_float.back() << '\n'; - std::cout << j_object.back() << '\n'; - //std::cout << j_object_empty.back() << '\n'; // undefined behavior - std::cout << j_array.back() << '\n'; - //std::cout << j_array_empty.back() << '\n'; // undefined behavior - std::cout << j_string.back() << '\n'; - - // back() called on a null value - try - { - json j_null; - j_null.back(); - } - catch (json::invalid_iterator& e) - { - std::cout << e.what() << '\n'; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/back.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/back.output deleted file mode 100644 index 2990dbf..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/back.output +++ /dev/null @@ -1,7 +0,0 @@ -true -17 -23.42 -2 -16 -"Hello, world" -[json.exception.invalid_iterator.214] cannot get value diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__CompatibleType.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__CompatibleType.cpp deleted file mode 100644 index e2f01aa..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__CompatibleType.cpp +++ /dev/null @@ -1,218 +0,0 @@ -#include -#include -#include -#include -#include -#include -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - // ============ - // object types - // ============ - - // create an object from an object_t value - json::object_t object_value = { {"one", 1}, {"two", 2} }; - json j_object_t(object_value); - - // create an object from std::map - std::map c_map - { - {"one", 1}, {"two", 2}, {"three", 3} - }; - json j_map(c_map); - - // create an object from std::unordered_map - std::unordered_map c_umap - { - {"one", 1.2}, {"two", 2.3}, {"three", 3.4} - }; - json j_umap(c_umap); - - // create an object from std::multimap - std::multimap c_mmap - { - {"one", true}, {"two", true}, {"three", false}, {"three", true} - }; - json j_mmap(c_mmap); // only one entry for key "three" is used - - // create an object from std::unordered_multimap - std::unordered_multimap c_ummap - { - {"one", true}, {"two", true}, {"three", false}, {"three", true} - }; - json j_ummap(c_ummap); // only one entry for key "three" is used - - // serialize the JSON objects - std::cout << j_object_t << '\n'; - std::cout << j_map << '\n'; - std::cout << j_umap << '\n'; - std::cout << j_mmap << '\n'; - std::cout << j_ummap << "\n\n"; - - - // =========== - // array types - // =========== - - // create an array from an array_t value - json::array_t array_value = {"one", "two", 3, 4.5, false}; - json j_array_t(array_value); - - // create an array from std::vector - std::vector c_vector {1, 2, 3, 4}; - json j_vec(c_vector); - - // create an array from std::valarray - std::valarray c_valarray {10, 9, 8, 7}; - json j_valarray(c_valarray); - - // create an array from std::deque - std::deque c_deque {1.2, 2.3, 3.4, 5.6}; - json j_deque(c_deque); - - // create an array from std::list - std::list c_list {true, true, false, true}; - json j_list(c_list); - - // create an array from std::forward_list - std::forward_list c_flist {12345678909876, 23456789098765, 34567890987654, 45678909876543}; - json j_flist(c_flist); - - // create an array from std::array - std::array c_array {{1, 2, 3, 4}}; - json j_array(c_array); - - // create an array from std::set - std::set c_set {"one", "two", "three", "four", "one"}; - json j_set(c_set); // only one entry for "one" is used - - // create an array from std::unordered_set - std::unordered_set c_uset {"one", "two", "three", "four", "one"}; - json j_uset(c_uset); // only one entry for "one" is used - - // create an array from std::multiset - std::multiset c_mset {"one", "two", "one", "four"}; - json j_mset(c_mset); // both entries for "one" are used - - // create an array from std::unordered_multiset - std::unordered_multiset c_umset {"one", "two", "one", "four"}; - json j_umset(c_umset); // both entries for "one" are used - - // serialize the JSON arrays - std::cout << j_array_t << '\n'; - std::cout << j_vec << '\n'; - std::cout << j_valarray << '\n'; - std::cout << j_deque << '\n'; - std::cout << j_list << '\n'; - std::cout << j_flist << '\n'; - std::cout << j_array << '\n'; - std::cout << j_set << '\n'; - std::cout << j_uset << '\n'; - std::cout << j_mset << '\n'; - std::cout << j_umset << "\n\n"; - - - // ============ - // string types - // ============ - - // create string from a string_t value - json::string_t string_value = "The quick brown fox jumps over the lazy dog."; - json j_string_t(string_value); - - // create a JSON string directly from a string literal - json j_string_literal("The quick brown fox jumps over the lazy dog."); - - // create string from std::string - std::string s_stdstring = "The quick brown fox jumps over the lazy dog."; - json j_stdstring(s_stdstring); - - // serialize the JSON strings - std::cout << j_string_t << '\n'; - std::cout << j_string_literal << '\n'; - std::cout << j_stdstring << "\n\n"; - - - // ============ - // number types - // ============ - - // create a JSON number from number_integer_t - json::number_integer_t value_integer_t = -42; - json j_integer_t(value_integer_t); - - // create a JSON number from number_unsigned_t - json::number_integer_t value_unsigned_t = 17; - json j_unsigned_t(value_unsigned_t); - - // create a JSON number from an anonymous enum - enum { enum_value = 17 }; - json j_enum(enum_value); - - // create values of different integer types - short n_short = 42; - int n_int = -23; - long n_long = 1024; - int_least32_t n_int_least32_t = -17; - uint8_t n_uint8_t = 8; - - // create (integer) JSON numbers - json j_short(n_short); - json j_int(n_int); - json j_long(n_long); - json j_int_least32_t(n_int_least32_t); - json j_uint8_t(n_uint8_t); - - // create values of different floating-point types - json::number_float_t v_ok = 3.141592653589793; - json::number_float_t v_nan = NAN; - json::number_float_t v_infinity = INFINITY; - - // create values of different floating-point types - float n_float = 42.23; - float n_float_nan = 1.0f / 0.0f; - double n_double = 23.42; - - // create (floating point) JSON numbers - json j_ok(v_ok); - json j_nan(v_nan); - json j_infinity(v_infinity); - json j_float(n_float); - json j_float_nan(n_float_nan); - json j_double(n_double); - - // serialize the JSON numbers - std::cout << j_integer_t << '\n'; - std::cout << j_unsigned_t << '\n'; - std::cout << j_enum << '\n'; - std::cout << j_short << '\n'; - std::cout << j_int << '\n'; - std::cout << j_long << '\n'; - std::cout << j_int_least32_t << '\n'; - std::cout << j_uint8_t << '\n'; - std::cout << j_ok << '\n'; - std::cout << j_nan << '\n'; - std::cout << j_infinity << '\n'; - std::cout << j_float << '\n'; - std::cout << j_float_nan << '\n'; - std::cout << j_double << "\n\n"; - - - // ============= - // boolean types - // ============= - - // create boolean values - json j_truth = true; - json j_falsity = false; - - // serialize the JSON booleans - std::cout << j_truth << '\n'; - std::cout << j_falsity << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__CompatibleType.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__CompatibleType.output deleted file mode 100644 index 2337e81..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__CompatibleType.output +++ /dev/null @@ -1,39 +0,0 @@ -{"one":1,"two":2} -{"one":1,"three":3,"two":2} -{"one":1.2,"three":3.4,"two":2.3} -{"one":true,"three":false,"two":true} -{"one":true,"three":false,"two":true} - -["one","two",3,4.5,false] -[1,2,3,4] -[10,9,8,7] -[1.2,2.3,3.4,5.6] -[true,true,false,true] -[12345678909876,23456789098765,34567890987654,45678909876543] -[1,2,3,4] -["four","one","three","two"] -["four","three","two","one"] -["four","one","one","two"] -["four","two","one","one"] - -"The quick brown fox jumps over the lazy dog." -"The quick brown fox jumps over the lazy dog." -"The quick brown fox jumps over the lazy dog." - --42 -17 -17 -42 --23 -1024 --17 -8 -3.141592653589793 -null -null -42.22999954223633 -null -23.42 - -true -false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__InputIt_InputIt.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__InputIt_InputIt.cpp deleted file mode 100644 index ed5aff9..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__InputIt_InputIt.cpp +++ /dev/null @@ -1,32 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json j_array = {"alpha", "bravo", "charly", "delta", "easy"}; - json j_number = 42; - json j_object = {{"one", "eins"}, {"two", "zwei"}}; - - // create copies using iterators - json j_array_range(j_array.begin() + 1, j_array.end() - 2); - json j_number_range(j_number.begin(), j_number.end()); - json j_object_range(j_object.begin(), j_object.find("two")); - - // serialize the values - std::cout << j_array_range << '\n'; - std::cout << j_number_range << '\n'; - std::cout << j_object_range << '\n'; - - // example for an exception - try - { - json j_invalid(j_number.begin() + 1, j_number.end()); - } - catch (json::invalid_iterator& e) - { - std::cout << e.what() << '\n'; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__InputIt_InputIt.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__InputIt_InputIt.output deleted file mode 100644 index bfb0177..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__InputIt_InputIt.output +++ /dev/null @@ -1,4 +0,0 @@ -["bravo","charly"] -42 -{"one":"eins"} -[json.exception.invalid_iterator.204] iterators out of range diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__basic_json.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__basic_json.cpp deleted file mode 100644 index 17136f4..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__basic_json.cpp +++ /dev/null @@ -1,17 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create a JSON array - json j1 = {"one", "two", 3, 4.5, false}; - - // create a copy - json j2(j1); - - // serialize the JSON array - std::cout << j1 << " = " << j2 << '\n'; - std::cout << std::boolalpha << (j1 == j2) << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__basic_json.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__basic_json.output deleted file mode 100644 index ee93a41..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__basic_json.output +++ /dev/null @@ -1,2 +0,0 @@ -["one","two",3,4.5,false] = ["one","two",3,4.5,false] -true diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__copyassignment.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__copyassignment.cpp deleted file mode 100644 index 2d86574..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__copyassignment.cpp +++ /dev/null @@ -1,18 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json a = 23; - json b = 42; - - // copy-assign a to b - b = a; - - // serialize the JSON arrays - std::cout << a << '\n'; - std::cout << b << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__copyassignment.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__copyassignment.output deleted file mode 100644 index c1eee21..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__copyassignment.output +++ /dev/null @@ -1,2 +0,0 @@ -23 -23 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__list_init_t.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__list_init_t.cpp deleted file mode 100644 index 78611e1..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__list_init_t.cpp +++ /dev/null @@ -1,21 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json j_empty_init_list = json({}); - json j_object = { {"one", 1}, {"two", 2} }; - json j_array = {1, 2, 3, 4}; - json j_nested_object = { {"one", {1}}, {"two", {1, 2}} }; - json j_nested_array = { {{1}, "one"}, {{1, 2}, "two"} }; - - // serialize the JSON value - std::cout << j_empty_init_list << '\n'; - std::cout << j_object << '\n'; - std::cout << j_array << '\n'; - std::cout << j_nested_object << '\n'; - std::cout << j_nested_array << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__list_init_t.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__list_init_t.output deleted file mode 100644 index d38f5b8..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__list_init_t.output +++ /dev/null @@ -1,5 +0,0 @@ -{} -{"one":1,"two":2} -[1,2,3,4] -{"one":[1],"two":[1,2]} -[[[1],"one"],[[1,2],"two"]] diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__moveconstructor.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__moveconstructor.cpp deleted file mode 100644 index 48b68f6..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__moveconstructor.cpp +++ /dev/null @@ -1,17 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create a JSON value - json a = 23; - - // move contents of a to b - json b(std::move(a)); - - // serialize the JSON arrays - std::cout << a << '\n'; - std::cout << b << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__moveconstructor.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__moveconstructor.output deleted file mode 100644 index 911b5b1..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__moveconstructor.output +++ /dev/null @@ -1,2 +0,0 @@ -null -23 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__nullptr_t.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__nullptr_t.cpp deleted file mode 100644 index 7a43666..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__nullptr_t.cpp +++ /dev/null @@ -1,16 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // implicitly create a JSON null value - json j1; - - // explicitly create a JSON null value - json j2(nullptr); - - // serialize the JSON null value - std::cout << j1 << '\n' << j2 << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__nullptr_t.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__nullptr_t.output deleted file mode 100644 index c1e4b6c..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__nullptr_t.output +++ /dev/null @@ -1,2 +0,0 @@ -null -null diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__size_type_basic_json.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__size_type_basic_json.cpp deleted file mode 100644 index 9ec7677..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__size_type_basic_json.cpp +++ /dev/null @@ -1,18 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create an array by creating copies of a JSON value - json value = "Hello"; - json array_0 = json(0, value); - json array_1 = json(1, value); - json array_5 = json(5, value); - - // serialize the JSON arrays - std::cout << array_0 << '\n'; - std::cout << array_1 << '\n'; - std::cout << array_5 << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__size_type_basic_json.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__size_type_basic_json.output deleted file mode 100644 index f4c59b3..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__size_type_basic_json.output +++ /dev/null @@ -1,3 +0,0 @@ -[] -["Hello"] -["Hello","Hello","Hello","Hello","Hello"] diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__value_t.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__value_t.cpp deleted file mode 100644 index c306731..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__value_t.cpp +++ /dev/null @@ -1,25 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create the different JSON values with default values - json j_null(json::value_t::null); - json j_boolean(json::value_t::boolean); - json j_number_integer(json::value_t::number_integer); - json j_number_float(json::value_t::number_float); - json j_object(json::value_t::object); - json j_array(json::value_t::array); - json j_string(json::value_t::string); - - // serialize the JSON values - std::cout << j_null << '\n'; - std::cout << j_boolean << '\n'; - std::cout << j_number_integer << '\n'; - std::cout << j_number_float << '\n'; - std::cout << j_object << '\n'; - std::cout << j_array << '\n'; - std::cout << j_string << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__value_t.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__value_t.output deleted file mode 100644 index ea542ca..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/basic_json__value_t.output +++ /dev/null @@ -1,7 +0,0 @@ -null -false -0 -0.0 -{} -[] -"" diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/begin.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/begin.cpp deleted file mode 100644 index 654835b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/begin.cpp +++ /dev/null @@ -1,16 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create an array value - json array = {1, 2, 3, 4, 5}; - - // get an iterator to the first element - json::iterator it = array.begin(); - - // serialize the element that the iterator points to - std::cout << *it << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/begin.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/begin.output deleted file mode 100644 index d00491f..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/begin.output +++ /dev/null @@ -1 +0,0 @@ -1 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/binary.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/binary.cpp deleted file mode 100644 index 617ce60..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/binary.cpp +++ /dev/null @@ -1,16 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create a binary vector - std::vector vec = {0xCA, 0xFE, 0xBA, 0xBE}; - - // create a binary JSON value with subtype 42 - json j = json::binary(vec, 42); - - // output type and subtype - std::cout << "type: " << j.type_name() << ", subtype: " << j.get_binary().subtype() << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/binary.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/binary.output deleted file mode 100644 index 74b05d2..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/binary.output +++ /dev/null @@ -1 +0,0 @@ -type: binary, subtype: 42 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/binary_t.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/binary_t.cpp deleted file mode 100644 index bfaee5c..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/binary_t.cpp +++ /dev/null @@ -1,10 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - std::cout << std::boolalpha << std::is_same>, json::binary_t>::value << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/binary_t.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/binary_t.output deleted file mode 100644 index 27ba77d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/binary_t.output +++ /dev/null @@ -1 +0,0 @@ -true diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/boolean_t.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/boolean_t.cpp deleted file mode 100644 index 75b8c99..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/boolean_t.cpp +++ /dev/null @@ -1,10 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - std::cout << std::boolalpha << std::is_same::value << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/boolean_t.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/boolean_t.output deleted file mode 100644 index 27ba77d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/boolean_t.output +++ /dev/null @@ -1 +0,0 @@ -true diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/byte_container_with_subtype__byte_container_with_subtype.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/byte_container_with_subtype__byte_container_with_subtype.cpp deleted file mode 100644 index 1c10be5..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/byte_container_with_subtype__byte_container_with_subtype.cpp +++ /dev/null @@ -1,23 +0,0 @@ -#include -#include - -// define a byte container based on std::vector -using byte_container_with_subtype = nlohmann::byte_container_with_subtype>; - -using json = nlohmann::json; - -int main() -{ - // (1) create empty container - auto c1 = byte_container_with_subtype(); - - std::vector bytes = {{0xca, 0xfe, 0xba, 0xbe}}; - - // (2) create container - auto c2 = byte_container_with_subtype(bytes); - - // (3) create container with subtype - auto c3 = byte_container_with_subtype(bytes, 42); - - std::cout << json(c1) << "\n" << json(c2) << "\n" << json(c3) << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/byte_container_with_subtype__byte_container_with_subtype.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/byte_container_with_subtype__byte_container_with_subtype.output deleted file mode 100644 index 67ac1b2..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/byte_container_with_subtype__byte_container_with_subtype.output +++ /dev/null @@ -1,3 +0,0 @@ -{"bytes":[],"subtype":null} -{"bytes":[202,254,186,190],"subtype":null} -{"bytes":[202,254,186,190],"subtype":42} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/byte_container_with_subtype__clear_subtype.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/byte_container_with_subtype__clear_subtype.cpp deleted file mode 100644 index f9ce684..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/byte_container_with_subtype__clear_subtype.cpp +++ /dev/null @@ -1,21 +0,0 @@ -#include -#include - -// define a byte container based on std::vector -using byte_container_with_subtype = nlohmann::byte_container_with_subtype>; - -using json = nlohmann::json; - -int main() -{ - std::vector bytes = {{0xca, 0xfe, 0xba, 0xbe}}; - - // create container with subtype - auto c1 = byte_container_with_subtype(bytes, 42); - - std::cout << "before calling clear_subtype(): " << json(c1) << '\n'; - - c1.clear_subtype(); - - std::cout << "after calling clear_subtype(): " << json(c1) << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/byte_container_with_subtype__clear_subtype.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/byte_container_with_subtype__clear_subtype.output deleted file mode 100644 index 9d82129..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/byte_container_with_subtype__clear_subtype.output +++ /dev/null @@ -1,2 +0,0 @@ -before calling clear_subtype(): {"bytes":[202,254,186,190],"subtype":42} -after calling clear_subtype(): {"bytes":[202,254,186,190],"subtype":null} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/byte_container_with_subtype__has_subtype.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/byte_container_with_subtype__has_subtype.cpp deleted file mode 100644 index 61c21ea..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/byte_container_with_subtype__has_subtype.cpp +++ /dev/null @@ -1,19 +0,0 @@ -#include -#include - -// define a byte container based on std::vector -using byte_container_with_subtype = nlohmann::byte_container_with_subtype>; - -int main() -{ - std::vector bytes = {{0xca, 0xfe, 0xba, 0xbe}}; - - // create container - auto c1 = byte_container_with_subtype(bytes); - - // create container with subtype - auto c2 = byte_container_with_subtype(bytes, 42); - - std::cout << std::boolalpha << "c1.has_subtype() = " << c1.has_subtype() - << "\nc2.has_subtype() = " << c2.has_subtype() << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/byte_container_with_subtype__has_subtype.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/byte_container_with_subtype__has_subtype.output deleted file mode 100644 index f4aade2..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/byte_container_with_subtype__has_subtype.output +++ /dev/null @@ -1,2 +0,0 @@ -c1.has_subtype() = false -c2.has_subtype() = true diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/byte_container_with_subtype__set_subtype.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/byte_container_with_subtype__set_subtype.cpp deleted file mode 100644 index b2694c5..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/byte_container_with_subtype__set_subtype.cpp +++ /dev/null @@ -1,22 +0,0 @@ -#include -#include - -// define a byte container based on std::vector -using byte_container_with_subtype = nlohmann::byte_container_with_subtype>; - -using json = nlohmann::json; - -int main() -{ - std::vector bytes = {{0xca, 0xfe, 0xba, 0xbe}}; - - // create container without subtype - auto c = byte_container_with_subtype(bytes); - - std::cout << "before calling set_subtype(42): " << json(c) << '\n'; - - // set the subtype - c.set_subtype(42); - - std::cout << "after calling set_subtype(42): " << json(c) << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/byte_container_with_subtype__set_subtype.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/byte_container_with_subtype__set_subtype.output deleted file mode 100644 index 648b3ef..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/byte_container_with_subtype__set_subtype.output +++ /dev/null @@ -1,2 +0,0 @@ -before calling set_subtype(42): {"bytes":[202,254,186,190],"subtype":null} -after calling set_subtype(42): {"bytes":[202,254,186,190],"subtype":42} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/byte_container_with_subtype__subtype.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/byte_container_with_subtype__subtype.cpp deleted file mode 100644 index cd230ad..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/byte_container_with_subtype__subtype.cpp +++ /dev/null @@ -1,22 +0,0 @@ -#include -#include - -// define a byte container based on std::vector -using byte_container_with_subtype = nlohmann::byte_container_with_subtype>; - -int main() -{ - std::vector bytes = {{0xca, 0xfe, 0xba, 0xbe}}; - - // create container - auto c1 = byte_container_with_subtype(bytes); - - // create container with subtype - auto c2 = byte_container_with_subtype(bytes, 42); - - std::cout << "c1.subtype() = " << c1.subtype() - << "\nc2.subtype() = " << c2.subtype() << std::endl; - - // in case no subtype is set, return special value - assert(c1.subtype() == static_cast(-1)); -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/byte_container_with_subtype__subtype.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/byte_container_with_subtype__subtype.output deleted file mode 100644 index 4795527..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/byte_container_with_subtype__subtype.output +++ /dev/null @@ -1,2 +0,0 @@ -c1.subtype() = 18446744073709551615 -c2.subtype() = 42 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/cbegin.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/cbegin.cpp deleted file mode 100644 index bed2b37..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/cbegin.cpp +++ /dev/null @@ -1,16 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create an array value - const json array = {1, 2, 3, 4, 5}; - - // get an iterator to the first element - json::const_iterator it = array.cbegin(); - - // serialize the element that the iterator points to - std::cout << *it << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/cbegin.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/cbegin.output deleted file mode 100644 index d00491f..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/cbegin.output +++ /dev/null @@ -1 +0,0 @@ -1 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/cbor_tag_handler_t.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/cbor_tag_handler_t.cpp deleted file mode 100644 index 79052c7..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/cbor_tag_handler_t.cpp +++ /dev/null @@ -1,28 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // tagged byte string - std::vector vec = {{0xd8, 0x42, 0x44, 0xcA, 0xfe, 0xba, 0xbe}}; - - // cbor_tag_handler_t::error throws - try - { - auto b_throw_on_tag = json::from_cbor(vec, true, true, json::cbor_tag_handler_t::error); - } - catch (json::parse_error& e) - { - std::cout << e.what() << std::endl; - } - - // cbor_tag_handler_t::ignore ignores the tag - auto b_ignore_tag = json::from_cbor(vec, true, true, json::cbor_tag_handler_t::ignore); - std::cout << b_ignore_tag << std::endl; - - // cbor_tag_handler_t::store stores the tag as binary subtype - auto b_store_tag = json::from_cbor(vec, true, true, json::cbor_tag_handler_t::store); - std::cout << b_store_tag << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/cbor_tag_handler_t.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/cbor_tag_handler_t.output deleted file mode 100644 index 18920b1..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/cbor_tag_handler_t.output +++ /dev/null @@ -1,3 +0,0 @@ -[json.exception.parse_error.112] parse error at byte 1: syntax error while parsing CBOR value: invalid byte: 0xD8 -{"bytes":[202,254,186,190],"subtype":null} -{"bytes":[202,254,186,190],"subtype":66} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/cend.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/cend.cpp deleted file mode 100644 index 3050f50..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/cend.cpp +++ /dev/null @@ -1,19 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create an array value - json array = {1, 2, 3, 4, 5}; - - // get an iterator to one past the last element - json::const_iterator it = array.cend(); - - // decrement the iterator to point to the last element - --it; - - // serialize the element that the iterator points to - std::cout << *it << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/cend.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/cend.output deleted file mode 100644 index 7ed6ff8..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/cend.output +++ /dev/null @@ -1 +0,0 @@ -5 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/clear.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/clear.cpp deleted file mode 100644 index f081e7e..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/clear.cpp +++ /dev/null @@ -1,34 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json j_null; - json j_boolean = true; - json j_number_integer = 17; - json j_number_float = 23.42; - json j_object = {{"one", 1}, {"two", 2}}; - json j_array = {1, 2, 4, 8, 16}; - json j_string = "Hello, world"; - - // call clear() - j_null.clear(); - j_boolean.clear(); - j_number_integer.clear(); - j_number_float.clear(); - j_object.clear(); - j_array.clear(); - j_string.clear(); - - // serialize the cleared values() - std::cout << j_null << '\n'; - std::cout << j_boolean << '\n'; - std::cout << j_number_integer << '\n'; - std::cout << j_number_float << '\n'; - std::cout << j_object << '\n'; - std::cout << j_array << '\n'; - std::cout << j_string << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/clear.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/clear.output deleted file mode 100644 index ea542ca..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/clear.output +++ /dev/null @@ -1,7 +0,0 @@ -null -false -0 -0.0 -{} -[] -"" diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/contains__json_pointer.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/contains__json_pointer.cpp deleted file mode 100644 index f9de546..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/contains__json_pointer.cpp +++ /dev/null @@ -1,43 +0,0 @@ -#include -#include - -using json = nlohmann::json; -using namespace nlohmann::literals; - -int main() -{ - // create a JSON value - json j = - { - {"number", 1}, {"string", "foo"}, {"array", {1, 2}} - }; - - std::cout << std::boolalpha - << j.contains("/number"_json_pointer) << '\n' - << j.contains("/string"_json_pointer) << '\n' - << j.contains("/array"_json_pointer) << '\n' - << j.contains("/array/1"_json_pointer) << '\n' - << j.contains("/array/-"_json_pointer) << '\n' - << j.contains("/array/4"_json_pointer) << '\n' - << j.contains("/baz"_json_pointer) << std::endl; - - try - { - // try to use an array index with leading '0' - j.contains("/array/01"_json_pointer); - } - catch (json::parse_error& e) - { - std::cout << e.what() << '\n'; - } - - try - { - // try to use an array index that is not a number - j.contains("/array/one"_json_pointer); - } - catch (json::parse_error& e) - { - std::cout << e.what() << '\n'; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/contains__json_pointer.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/contains__json_pointer.output deleted file mode 100644 index dd1eb38..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/contains__json_pointer.output +++ /dev/null @@ -1,7 +0,0 @@ -true -true -true -true -false -false -false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/contains__keytype.c++17.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/contains__keytype.c++17.cpp deleted file mode 100644 index 43b62fa..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/contains__keytype.c++17.cpp +++ /dev/null @@ -1,20 +0,0 @@ -#include -#include -#include - -using namespace std::string_view_literals; -using json = nlohmann::json; -using namespace nlohmann::literals; - -int main() -{ - // create some JSON values - json j_object = R"( {"key": "value"} )"_json; - json j_array = R"( [1, 2, 3] )"_json; - - // call contains - std::cout << std::boolalpha << - "j_object contains 'key': " << j_object.contains("key"sv) << '\n' << - "j_object contains 'another': " << j_object.contains("another"sv) << '\n' << - "j_array contains 'key': " << j_array.contains("key"sv) << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/contains__keytype.c++17.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/contains__keytype.c++17.output deleted file mode 100644 index 14ad177..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/contains__keytype.c++17.output +++ /dev/null @@ -1,3 +0,0 @@ -j_object contains 'key': true -j_object contains 'another': false -j_array contains 'key': false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/contains__object_t_key_type.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/contains__object_t_key_type.cpp deleted file mode 100644 index a8bc814..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/contains__object_t_key_type.cpp +++ /dev/null @@ -1,18 +0,0 @@ -#include -#include - -using json = nlohmann::json; -using namespace nlohmann::literals; - -int main() -{ - // create some JSON values - json j_object = R"( {"key": "value"} )"_json; - json j_array = R"( [1, 2, 3] )"_json; - - // call contains - std::cout << std::boolalpha << - "j_object contains 'key': " << j_object.contains("key") << '\n' << - "j_object contains 'another': " << j_object.contains("another") << '\n' << - "j_array contains 'key': " << j_array.contains("key") << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/contains__object_t_key_type.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/contains__object_t_key_type.output deleted file mode 100644 index 14ad177..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/contains__object_t_key_type.output +++ /dev/null @@ -1,3 +0,0 @@ -j_object contains 'key': true -j_object contains 'another': false -j_array contains 'key': false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/count__keytype.c++17.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/count__keytype.c++17.cpp deleted file mode 100644 index ec6de06..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/count__keytype.c++17.cpp +++ /dev/null @@ -1,20 +0,0 @@ -#include -#include -#include - -using namespace std::string_view_literals; -using json = nlohmann::json; - -int main() -{ - // create a JSON object - json j_object = {{"one", 1}, {"two", 2}}; - - // call count() - auto count_two = j_object.count("two"sv); - auto count_three = j_object.count("three"sv); - - // print values - std::cout << "number of elements with key \"two\": " << count_two << '\n'; - std::cout << "number of elements with key \"three\": " << count_three << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/count__keytype.c++17.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/count__keytype.c++17.output deleted file mode 100644 index d816fcb..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/count__keytype.c++17.output +++ /dev/null @@ -1,2 +0,0 @@ -number of elements with key "two": 1 -number of elements with key "three": 0 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/count__object_t_key_type.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/count__object_t_key_type.cpp deleted file mode 100644 index a8d54b9..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/count__object_t_key_type.cpp +++ /dev/null @@ -1,18 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create a JSON object - json j_object = {{"one", 1}, {"two", 2}}; - - // call count() - auto count_two = j_object.count("two"); - auto count_three = j_object.count("three"); - - // print values - std::cout << "number of elements with key \"two\": " << count_two << '\n'; - std::cout << "number of elements with key \"three\": " << count_three << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/count__object_t_key_type.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/count__object_t_key_type.output deleted file mode 100644 index d816fcb..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/count__object_t_key_type.output +++ /dev/null @@ -1,2 +0,0 @@ -number of elements with key "two": 1 -number of elements with key "three": 0 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/crbegin.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/crbegin.cpp deleted file mode 100644 index dc3209c..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/crbegin.cpp +++ /dev/null @@ -1,16 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create an array value - json array = {1, 2, 3, 4, 5}; - - // get an iterator to the reverse-beginning - json::const_reverse_iterator it = array.crbegin(); - - // serialize the element that the iterator points to - std::cout << *it << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/crbegin.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/crbegin.output deleted file mode 100644 index 7ed6ff8..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/crbegin.output +++ /dev/null @@ -1 +0,0 @@ -5 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/crend.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/crend.cpp deleted file mode 100644 index dff2609..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/crend.cpp +++ /dev/null @@ -1,19 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create an array value - json array = {1, 2, 3, 4, 5}; - - // get an iterator to the reverse-end - json::const_reverse_iterator it = array.crend(); - - // increment the iterator to point to the first element - --it; - - // serialize the element that the iterator points to - std::cout << *it << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/crend.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/crend.output deleted file mode 100644 index d00491f..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/crend.output +++ /dev/null @@ -1 +0,0 @@ -1 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/default_object_comparator_t.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/default_object_comparator_t.cpp deleted file mode 100644 index 9f200fe..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/default_object_comparator_t.cpp +++ /dev/null @@ -1,11 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - std::cout << std::boolalpha - << "one < two : " << json::default_object_comparator_t{}("one", "two") << "\n" - << "three < four : " << json::default_object_comparator_t{}("three", "four") << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/default_object_comparator_t.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/default_object_comparator_t.output deleted file mode 100644 index b1daf3b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/default_object_comparator_t.output +++ /dev/null @@ -1,2 +0,0 @@ -one < two : true -three < four : false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/diagnostics_extended.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/diagnostics_extended.cpp deleted file mode 100644 index f4c43f0..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/diagnostics_extended.cpp +++ /dev/null @@ -1,22 +0,0 @@ -#include - -# define JSON_DIAGNOSTICS 1 -#include - -using json = nlohmann::json; - -int main() -{ - json j; - j["address"]["street"] = "Fake Street"; - j["address"]["housenumber"] = "12"; - - try - { - int housenumber = j["address"]["housenumber"]; - } - catch (json::exception& e) - { - std::cout << e.what() << '\n'; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/diagnostics_extended.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/diagnostics_extended.output deleted file mode 100644 index f142927..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/diagnostics_extended.output +++ /dev/null @@ -1 +0,0 @@ -[json.exception.type_error.302] (/address/housenumber) type must be number, but is string diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/diagnostics_standard.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/diagnostics_standard.cpp deleted file mode 100644 index 575c409..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/diagnostics_standard.cpp +++ /dev/null @@ -1,20 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - json j; - j["address"]["street"] = "Fake Street"; - j["address"]["housenumber"] = "12"; - - try - { - int housenumber = j["address"]["housenumber"]; - } - catch (json::exception& e) - { - std::cout << e.what() << '\n'; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/diagnostics_standard.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/diagnostics_standard.output deleted file mode 100644 index 79707a0..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/diagnostics_standard.output +++ /dev/null @@ -1 +0,0 @@ -[json.exception.type_error.302] type must be number, but is string diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/diff.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/diff.cpp deleted file mode 100644 index ef01332..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/diff.cpp +++ /dev/null @@ -1,37 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; -using namespace nlohmann::literals; - -int main() -{ - // the source document - json source = R"( - { - "baz": "qux", - "foo": "bar" - } - )"_json; - - // the target document - json target = R"( - { - "baz": "boo", - "hello": [ - "world" - ] - } - )"_json; - - // create the patch - json patch = json::diff(source, target); - - // roundtrip - json patched_source = source.patch(patch); - - // output patch and roundtrip result - std::cout << std::setw(4) << patch << "\n\n" - << std::setw(4) << patched_source << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/diff.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/diff.output deleted file mode 100644 index 7dc7979..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/diff.output +++ /dev/null @@ -1,25 +0,0 @@ -[ - { - "op": "replace", - "path": "/baz", - "value": "boo" - }, - { - "op": "remove", - "path": "/foo" - }, - { - "op": "add", - "path": "/hello", - "value": [ - "world" - ] - } -] - -{ - "baz": "boo", - "hello": [ - "world" - ] -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/dump.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/dump.cpp deleted file mode 100644 index eb2d71f..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/dump.cpp +++ /dev/null @@ -1,48 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json j_object = {{"one", 1}, {"two", 2}}; - json j_array = {1, 2, 4, 8, 16}; - json j_string = "Hellö 😀!"; - - // call dump() - std::cout << "objects:" << '\n' - << j_object.dump() << "\n\n" - << j_object.dump(-1) << "\n\n" - << j_object.dump(0) << "\n\n" - << j_object.dump(4) << "\n\n" - << j_object.dump(1, '\t') << "\n\n"; - - std::cout << "arrays:" << '\n' - << j_array.dump() << "\n\n" - << j_array.dump(-1) << "\n\n" - << j_array.dump(0) << "\n\n" - << j_array.dump(4) << "\n\n" - << j_array.dump(1, '\t') << "\n\n"; - - std::cout << "strings:" << '\n' - << j_string.dump() << '\n' - << j_string.dump(-1, ' ', true) << '\n'; - - // create JSON value with invalid UTF-8 byte sequence - json j_invalid = "ä\xA9ü"; - try - { - std::cout << j_invalid.dump() << std::endl; - } - catch (json::type_error& e) - { - std::cout << e.what() << std::endl; - } - - std::cout << "string with replaced invalid characters: " - << j_invalid.dump(-1, ' ', false, json::error_handler_t::replace) - << "\nstring with ignored invalid characters: " - << j_invalid.dump(-1, ' ', false, json::error_handler_t::ignore) - << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/dump.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/dump.output deleted file mode 100644 index 43009fe..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/dump.output +++ /dev/null @@ -1,55 +0,0 @@ -objects: -{"one":1,"two":2} - -{"one":1,"two":2} - -{ -"one": 1, -"two": 2 -} - -{ - "one": 1, - "two": 2 -} - -{ - "one": 1, - "two": 2 -} - -arrays: -[1,2,4,8,16] - -[1,2,4,8,16] - -[ -1, -2, -4, -8, -16 -] - -[ - 1, - 2, - 4, - 8, - 16 -] - -[ - 1, - 2, - 4, - 8, - 16 -] - -strings: -"Hellö 😀!" -"Hell\u00f6 \ud83d\ude00!" -[json.exception.type_error.316] invalid UTF-8 byte at index 2: 0xA9 -string with replaced invalid characters: "ä�ü" -string with ignored invalid characters: "äü" diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/emplace.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/emplace.cpp deleted file mode 100644 index a531491..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/emplace.cpp +++ /dev/null @@ -1,31 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json object = {{"one", 1}, {"two", 2}}; - json null; - - // print values - std::cout << object << '\n'; - std::cout << null << '\n'; - - // add values - auto res1 = object.emplace("three", 3); - null.emplace("A", "a"); - null.emplace("B", "b"); - - // the following call will not add an object, because there is already - // a value stored at key "B" - auto res2 = null.emplace("B", "c"); - - // print values - std::cout << object << '\n'; - std::cout << *res1.first << " " << std::boolalpha << res1.second << '\n'; - - std::cout << null << '\n'; - std::cout << *res2.first << " " << std::boolalpha << res2.second << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/emplace.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/emplace.output deleted file mode 100644 index 83d6f77..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/emplace.output +++ /dev/null @@ -1,6 +0,0 @@ -{"one":1,"two":2} -null -{"one":1,"three":3,"two":2} -3 true -{"A":"a","B":"b"} -"b" false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/emplace_back.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/emplace_back.cpp deleted file mode 100644 index e979a94..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/emplace_back.cpp +++ /dev/null @@ -1,24 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json array = {1, 2, 3, 4, 5}; - json null; - - // print values - std::cout << array << '\n'; - std::cout << null << '\n'; - - // add values - array.emplace_back(6); - null.emplace_back("first"); - null.emplace_back(3, "second"); - - // print values - std::cout << array << '\n'; - std::cout << null << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/emplace_back.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/emplace_back.output deleted file mode 100644 index bdd80d8..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/emplace_back.output +++ /dev/null @@ -1,4 +0,0 @@ -[1,2,3,4,5] -null -[1,2,3,4,5,6] -["first",["second","second","second"]] diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/empty.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/empty.cpp deleted file mode 100644 index 6ef6e40..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/empty.cpp +++ /dev/null @@ -1,30 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json j_null; - json j_boolean = true; - json j_number_integer = 17; - json j_number_float = 23.42; - json j_object = {{"one", 1}, {"two", 2}}; - json j_object_empty(json::value_t::object); - json j_array = {1, 2, 4, 8, 16}; - json j_array_empty(json::value_t::array); - json j_string = "Hello, world"; - - // call empty() - std::cout << std::boolalpha; - std::cout << j_null.empty() << '\n'; - std::cout << j_boolean.empty() << '\n'; - std::cout << j_number_integer.empty() << '\n'; - std::cout << j_number_float.empty() << '\n'; - std::cout << j_object.empty() << '\n'; - std::cout << j_object_empty.empty() << '\n'; - std::cout << j_array.empty() << '\n'; - std::cout << j_array_empty.empty() << '\n'; - std::cout << j_string.empty() << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/empty.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/empty.output deleted file mode 100644 index d071a39..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/empty.output +++ /dev/null @@ -1,9 +0,0 @@ -true -false -false -false -false -true -false -true -false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/end.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/end.cpp deleted file mode 100644 index 47beedb..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/end.cpp +++ /dev/null @@ -1,19 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create an array value - json array = {1, 2, 3, 4, 5}; - - // get an iterator to one past the last element - json::iterator it = array.end(); - - // decrement the iterator to point to the last element - --it; - - // serialize the element that the iterator points to - std::cout << *it << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/end.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/end.output deleted file mode 100644 index 7ed6ff8..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/end.output +++ /dev/null @@ -1 +0,0 @@ -5 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/erase__IteratorType.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/erase__IteratorType.cpp deleted file mode 100644 index f0d4ec6..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/erase__IteratorType.cpp +++ /dev/null @@ -1,31 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json j_boolean = true; - json j_number_integer = 17; - json j_number_float = 23.42; - json j_object = {{"one", 1}, {"two", 2}}; - json j_array = {1, 2, 4, 8, 16}; - json j_string = "Hello, world"; - - // call erase() - j_boolean.erase(j_boolean.begin()); - j_number_integer.erase(j_number_integer.begin()); - j_number_float.erase(j_number_float.begin()); - j_object.erase(j_object.find("two")); - j_array.erase(j_array.begin() + 2); - j_string.erase(j_string.begin()); - - // print values - std::cout << j_boolean << '\n'; - std::cout << j_number_integer << '\n'; - std::cout << j_number_float << '\n'; - std::cout << j_object << '\n'; - std::cout << j_array << '\n'; - std::cout << j_string << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/erase__IteratorType.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/erase__IteratorType.output deleted file mode 100644 index e392f8e..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/erase__IteratorType.output +++ /dev/null @@ -1,6 +0,0 @@ -null -null -null -{"one":1} -[1,2,8,16] -null diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/erase__IteratorType_IteratorType.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/erase__IteratorType_IteratorType.cpp deleted file mode 100644 index 392511f..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/erase__IteratorType_IteratorType.cpp +++ /dev/null @@ -1,31 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json j_boolean = true; - json j_number_integer = 17; - json j_number_float = 23.42; - json j_object = {{"one", 1}, {"two", 2}}; - json j_array = {1, 2, 4, 8, 16}; - json j_string = "Hello, world"; - - // call erase() - j_boolean.erase(j_boolean.begin(), j_boolean.end()); - j_number_integer.erase(j_number_integer.begin(), j_number_integer.end()); - j_number_float.erase(j_number_float.begin(), j_number_float.end()); - j_object.erase(j_object.find("two"), j_object.end()); - j_array.erase(j_array.begin() + 1, j_array.begin() + 3); - j_string.erase(j_string.begin(), j_string.end()); - - // print values - std::cout << j_boolean << '\n'; - std::cout << j_number_integer << '\n'; - std::cout << j_number_float << '\n'; - std::cout << j_object << '\n'; - std::cout << j_array << '\n'; - std::cout << j_string << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/erase__IteratorType_IteratorType.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/erase__IteratorType_IteratorType.output deleted file mode 100644 index 5d01f00..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/erase__IteratorType_IteratorType.output +++ /dev/null @@ -1,6 +0,0 @@ -null -null -null -{"one":1} -[1,8,16] -null diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/erase__keytype.c++17.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/erase__keytype.c++17.cpp deleted file mode 100644 index c5e4bed..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/erase__keytype.c++17.cpp +++ /dev/null @@ -1,20 +0,0 @@ -#include -#include -#include - -using namespace std::string_view_literals; -using json = nlohmann::json; - -int main() -{ - // create a JSON object - json j_object = {{"one", 1}, {"two", 2}}; - - // call erase() - auto count_one = j_object.erase("one"sv); - auto count_three = j_object.erase("three"sv); - - // print values - std::cout << j_object << '\n'; - std::cout << count_one << " " << count_three << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/erase__keytype.c++17.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/erase__keytype.c++17.output deleted file mode 100644 index 28d7939..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/erase__keytype.c++17.output +++ /dev/null @@ -1,2 +0,0 @@ -{"two":2} -1 0 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/erase__object_t_key_type.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/erase__object_t_key_type.cpp deleted file mode 100644 index 2fd84c8..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/erase__object_t_key_type.cpp +++ /dev/null @@ -1,18 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create a JSON object - json j_object = {{"one", 1}, {"two", 2}}; - - // call erase() - auto count_one = j_object.erase("one"); - auto count_three = j_object.erase("three"); - - // print values - std::cout << j_object << '\n'; - std::cout << count_one << " " << count_three << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/erase__object_t_key_type.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/erase__object_t_key_type.output deleted file mode 100644 index 28d7939..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/erase__object_t_key_type.output +++ /dev/null @@ -1,2 +0,0 @@ -{"two":2} -1 0 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/erase__size_type.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/erase__size_type.cpp deleted file mode 100644 index 8100623..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/erase__size_type.cpp +++ /dev/null @@ -1,16 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create a JSON array - json j_array = {0, 1, 2, 3, 4, 5}; - - // call erase() - j_array.erase(2); - - // print values - std::cout << j_array << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/erase__size_type.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/erase__size_type.output deleted file mode 100644 index 4ad7406..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/erase__size_type.output +++ /dev/null @@ -1 +0,0 @@ -[0,1,3,4,5] diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/error_handler_t.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/error_handler_t.cpp deleted file mode 100644 index add3f3b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/error_handler_t.cpp +++ /dev/null @@ -1,24 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON value with invalid UTF-8 byte sequence - json j_invalid = "ä\xA9ü"; - try - { - std::cout << j_invalid.dump() << std::endl; - } - catch (json::type_error& e) - { - std::cout << e.what() << std::endl; - } - - std::cout << "string with replaced invalid characters: " - << j_invalid.dump(-1, ' ', false, json::error_handler_t::replace) - << "\nstring with ignored invalid characters: " - << j_invalid.dump(-1, ' ', false, json::error_handler_t::ignore) - << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/error_handler_t.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/error_handler_t.output deleted file mode 100644 index 718d62b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/error_handler_t.output +++ /dev/null @@ -1,3 +0,0 @@ -[json.exception.type_error.316] invalid UTF-8 byte at index 2: 0xA9 -string with replaced invalid characters: "ä�ü" -string with ignored invalid characters: "äü" diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/exception.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/exception.cpp deleted file mode 100644 index 82696e6..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/exception.cpp +++ /dev/null @@ -1,20 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - try - { - // calling at() for a non-existing key - json j = {{"foo", "bar"}}; - json k = j.at("non-existing"); - } - catch (json::exception& e) - { - // output exception information - std::cout << "message: " << e.what() << '\n' - << "exception id: " << e.id << std::endl; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/exception.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/exception.output deleted file mode 100644 index fa20df6..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/exception.output +++ /dev/null @@ -1,2 +0,0 @@ -message: [json.exception.out_of_range.403] key 'non-existing' not found -exception id: 403 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/find__keytype.c++17.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/find__keytype.c++17.cpp deleted file mode 100644 index da94cf0..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/find__keytype.c++17.cpp +++ /dev/null @@ -1,22 +0,0 @@ -#include -#include -#include - -using namespace std::string_view_literals; -using json = nlohmann::json; - -int main() -{ - // create a JSON object - json j_object = {{"one", 1}, {"two", 2}}; - - // call find - auto it_two = j_object.find("two"sv); - auto it_three = j_object.find("three"sv); - - // print values - std::cout << std::boolalpha; - std::cout << "\"two\" was found: " << (it_two != j_object.end()) << '\n'; - std::cout << "value at key \"two\": " << *it_two << '\n'; - std::cout << "\"three\" was found: " << (it_three != j_object.end()) << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/find__keytype.c++17.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/find__keytype.c++17.output deleted file mode 100644 index 509bb42..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/find__keytype.c++17.output +++ /dev/null @@ -1,3 +0,0 @@ -"two" was found: true -value at key "two": 2 -"three" was found: false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/find__object_t_key_type.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/find__object_t_key_type.cpp deleted file mode 100644 index 685ba77..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/find__object_t_key_type.cpp +++ /dev/null @@ -1,20 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create a JSON object - json j_object = {{"one", 1}, {"two", 2}}; - - // call find - auto it_two = j_object.find("two"); - auto it_three = j_object.find("three"); - - // print values - std::cout << std::boolalpha; - std::cout << "\"two\" was found: " << (it_two != j_object.end()) << '\n'; - std::cout << "value at key \"two\": " << *it_two << '\n'; - std::cout << "\"three\" was found: " << (it_three != j_object.end()) << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/find__object_t_key_type.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/find__object_t_key_type.output deleted file mode 100644 index 509bb42..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/find__object_t_key_type.output +++ /dev/null @@ -1,3 +0,0 @@ -"two" was found: true -value at key "two": 2 -"three" was found: false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/flatten.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/flatten.cpp deleted file mode 100644 index 83f3ff6..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/flatten.cpp +++ /dev/null @@ -1,32 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON value - json j = - { - {"pi", 3.141}, - {"happy", true}, - {"name", "Niels"}, - {"nothing", nullptr}, - { - "answer", { - {"everything", 42} - } - }, - {"list", {1, 0, 2}}, - { - "object", { - {"currency", "USD"}, - {"value", 42.99} - } - } - }; - - // call flatten() - std::cout << std::setw(4) << j.flatten() << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/flatten.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/flatten.output deleted file mode 100644 index 33bd4c4..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/flatten.output +++ /dev/null @@ -1,12 +0,0 @@ -{ - "/answer/everything": 42, - "/happy": true, - "/list/0": 1, - "/list/1": 0, - "/list/2": 2, - "/name": "Niels", - "/nothing": null, - "/object/currency": "USD", - "/object/value": 42.99, - "/pi": 3.141 -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_bjdata.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_bjdata.cpp deleted file mode 100644 index 961164c..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_bjdata.cpp +++ /dev/null @@ -1,20 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create byte vector - std::vector v = {0x7B, 0x69, 0x07, 0x63, 0x6F, 0x6D, 0x70, 0x61, - 0x63, 0x74, 0x54, 0x69, 0x06, 0x73, 0x63, 0x68, - 0x65, 0x6D, 0x61, 0x69, 0x00, 0x7D - }; - - // deserialize it with BJData - json j = json::from_bjdata(v); - - // print the deserialized JSON value - std::cout << std::setw(2) << j << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_bjdata.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_bjdata.output deleted file mode 100644 index 259f63b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_bjdata.output +++ /dev/null @@ -1,4 +0,0 @@ -{ - "compact": true, - "schema": 0 -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_bson.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_bson.cpp deleted file mode 100644 index c9d9fdf..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_bson.cpp +++ /dev/null @@ -1,21 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create byte vector - std::vector v = {0x1b, 0x00, 0x00, 0x00, 0x08, 0x63, 0x6f, 0x6d, - 0x70, 0x61, 0x63, 0x74, 0x00, 0x01, 0x10, 0x73, - 0x63, 0x68, 0x65, 0x6d, 0x61, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00 - }; - - // deserialize it with BSON - json j = json::from_bson(v); - - // print the deserialized JSON value - std::cout << std::setw(2) << j << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_bson.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_bson.output deleted file mode 100644 index 259f63b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_bson.output +++ /dev/null @@ -1,4 +0,0 @@ -{ - "compact": true, - "schema": 0 -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_cbor.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_cbor.cpp deleted file mode 100644 index e685329..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_cbor.cpp +++ /dev/null @@ -1,20 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create byte vector - std::vector v = {0xa2, 0x67, 0x63, 0x6f, 0x6d, 0x70, 0x61, 0x63, - 0x74, 0xf5, 0x66, 0x73, 0x63, 0x68, 0x65, 0x6d, - 0x61, 0x00 - }; - - // deserialize it with CBOR - json j = json::from_cbor(v); - - // print the deserialized JSON value - std::cout << std::setw(2) << j << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_cbor.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_cbor.output deleted file mode 100644 index 259f63b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_cbor.output +++ /dev/null @@ -1,4 +0,0 @@ -{ - "compact": true, - "schema": 0 -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_json__default_constructible.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_json__default_constructible.cpp deleted file mode 100644 index 17c0551..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_json__default_constructible.cpp +++ /dev/null @@ -1,37 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -namespace ns -{ -// a simple struct to model a person -struct person -{ - std::string name; - std::string address; - int age; -}; -} // namespace ns - -namespace ns -{ -void from_json(const json& j, person& p) -{ - j.at("name").get_to(p.name); - j.at("address").get_to(p.address); - j.at("age").get_to(p.age); -} -} // namespace ns - -int main() -{ - json j; - j["name"] = "Ned Flanders"; - j["address"] = "744 Evergreen Terrace"; - j["age"] = 60; - - auto p = j.get(); - - std::cout << p.name << " (" << p.age << ") lives in " << p.address << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_json__default_constructible.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_json__default_constructible.output deleted file mode 100644 index b924523..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_json__default_constructible.output +++ /dev/null @@ -1 +0,0 @@ -Ned Flanders (60) lives in 744 Evergreen Terrace diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_json__non_default_constructible.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_json__non_default_constructible.cpp deleted file mode 100644 index 6cb8615..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_json__non_default_constructible.cpp +++ /dev/null @@ -1,53 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -namespace ns -{ -// a simple struct to model a person (not default constructible) -struct person -{ - person(std::string n, std::string a, int aa) - : name(std::move(n)), address(std::move(a)), age(aa) - {} - - std::string name; - std::string address; - int age; -}; -} // namespace ns - -namespace nlohmann -{ -template <> -struct adl_serializer -{ - static ns::person from_json(const json& j) - { - return {j.at("name"), j.at("address"), j.at("age")}; - } - - // Here's the catch! You must provide a to_json method! Otherwise, you - // will not be able to convert person to json, since you fully - // specialized adl_serializer on that type - static void to_json(json& j, ns::person p) - { - j["name"] = p.name; - j["address"] = p.address; - j["age"] = p.age; - } -}; -} // namespace nlohmann - -int main() -{ - json j; - j["name"] = "Ned Flanders"; - j["address"] = "744 Evergreen Terrace"; - j["age"] = 60; - - auto p = j.get(); - - std::cout << p.name << " (" << p.age << ") lives in " << p.address << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_json__non_default_constructible.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_json__non_default_constructible.output deleted file mode 100644 index b924523..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_json__non_default_constructible.output +++ /dev/null @@ -1 +0,0 @@ -Ned Flanders (60) lives in 744 Evergreen Terrace diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_msgpack.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_msgpack.cpp deleted file mode 100644 index 5c2183f..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_msgpack.cpp +++ /dev/null @@ -1,20 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create byte vector - std::vector v = {0x82, 0xa7, 0x63, 0x6f, 0x6d, 0x70, 0x61, 0x63, - 0x74, 0xc3, 0xa6, 0x73, 0x63, 0x68, 0x65, 0x6d, - 0x61, 0x00 - }; - - // deserialize it with MessagePack - json j = json::from_msgpack(v); - - // print the deserialized JSON value - std::cout << std::setw(2) << j << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_msgpack.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_msgpack.output deleted file mode 100644 index 259f63b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_msgpack.output +++ /dev/null @@ -1,4 +0,0 @@ -{ - "compact": true, - "schema": 0 -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_ubjson.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_ubjson.cpp deleted file mode 100644 index 1e85e4e..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_ubjson.cpp +++ /dev/null @@ -1,20 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create byte vector - std::vector v = {0x7B, 0x69, 0x07, 0x63, 0x6F, 0x6D, 0x70, 0x61, - 0x63, 0x74, 0x54, 0x69, 0x06, 0x73, 0x63, 0x68, - 0x65, 0x6D, 0x61, 0x69, 0x00, 0x7D - }; - - // deserialize it with UBJSON - json j = json::from_ubjson(v); - - // print the deserialized JSON value - std::cout << std::setw(2) << j << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_ubjson.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_ubjson.output deleted file mode 100644 index 259f63b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/from_ubjson.output +++ /dev/null @@ -1,4 +0,0 @@ -{ - "compact": true, - "schema": 0 -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/front.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/front.cpp deleted file mode 100644 index a0f6306..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/front.cpp +++ /dev/null @@ -1,29 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json j_null; - json j_boolean = true; - json j_number_integer = 17; - json j_number_float = 23.42; - json j_object = {{"one", 1}, {"two", 2}}; - json j_object_empty(json::value_t::object); - json j_array = {1, 2, 4, 8, 16}; - json j_array_empty(json::value_t::array); - json j_string = "Hello, world"; - - // call front() - //std::cout << j_null.front() << '\n'; // would throw - std::cout << j_boolean.front() << '\n'; - std::cout << j_number_integer.front() << '\n'; - std::cout << j_number_float.front() << '\n'; - std::cout << j_object.front() << '\n'; - //std::cout << j_object_empty.front() << '\n'; // undefined behavior - std::cout << j_array.front() << '\n'; - //std::cout << j_array_empty.front() << '\n'; // undefined behavior - std::cout << j_string.front() << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/front.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/front.output deleted file mode 100644 index 6301db5..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/front.output +++ /dev/null @@ -1,6 +0,0 @@ -true -17 -23.42 -1 -1 -"Hello, world" diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get__PointerType.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get__PointerType.cpp deleted file mode 100644 index 2f32ed7..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get__PointerType.cpp +++ /dev/null @@ -1,21 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create a JSON number - json value = 17; - - // explicitly getting pointers - auto p1 = value.get(); - auto p2 = value.get(); - auto p3 = value.get(); - auto p4 = value.get(); - auto p5 = value.get(); - - // print the pointees - std::cout << *p1 << ' ' << *p2 << ' ' << *p3 << ' ' << *p4 << '\n'; - std::cout << std::boolalpha << (p5 == nullptr) << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get__PointerType.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get__PointerType.output deleted file mode 100644 index a15dd77..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get__PointerType.output +++ /dev/null @@ -1,2 +0,0 @@ -17 17 17 17 -true diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get__ValueType_const.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get__ValueType_const.cpp deleted file mode 100644 index 7a703aa..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get__ValueType_const.cpp +++ /dev/null @@ -1,50 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create a JSON value with different types - json json_types = - { - {"boolean", true}, - { - "number", { - {"integer", 42}, - {"floating-point", 17.23} - } - }, - {"string", "Hello, world!"}, - {"array", {1, 2, 3, 4, 5}}, - {"null", nullptr} - }; - - // use explicit conversions - auto v1 = json_types["boolean"].get(); - auto v2 = json_types["number"]["integer"].get(); - auto v3 = json_types["number"]["integer"].get(); - auto v4 = json_types["number"]["floating-point"].get(); - auto v5 = json_types["number"]["floating-point"].get(); - auto v6 = json_types["string"].get(); - auto v7 = json_types["array"].get>(); - auto v8 = json_types.get>(); - - // print the conversion results - std::cout << v1 << '\n'; - std::cout << v2 << ' ' << v3 << '\n'; - std::cout << v4 << ' ' << v5 << '\n'; - std::cout << v6 << '\n'; - - for (auto i : v7) - { - std::cout << i << ' '; - } - std::cout << "\n\n"; - - for (auto i : v8) - { - std::cout << i.first << ": " << i.second << '\n'; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get__ValueType_const.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get__ValueType_const.output deleted file mode 100644 index 5cd9cd3..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get__ValueType_const.output +++ /dev/null @@ -1,11 +0,0 @@ -1 -42 42 -17.23 17 -Hello, world! -1 2 3 4 5 - -string: "Hello, world!" -number: {"floating-point":17.23,"integer":42} -null: null -boolean: true -array: [1,2,3,4,5] diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get_allocator.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get_allocator.cpp deleted file mode 100644 index 35079a1..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get_allocator.cpp +++ /dev/null @@ -1,18 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - auto alloc = json::get_allocator(); - using traits_t = std::allocator_traits; - - json* j = traits_t::allocate(alloc, 1); - traits_t::construct(alloc, j, "Hello, world!"); - - std::cout << *j << std::endl; - - traits_t::destroy(alloc, j); - traits_t::deallocate(alloc, j, 1); -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get_allocator.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get_allocator.output deleted file mode 100644 index 8effb3e..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get_allocator.output +++ /dev/null @@ -1 +0,0 @@ -"Hello, world!" diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get_binary.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get_binary.cpp deleted file mode 100644 index 617ce60..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get_binary.cpp +++ /dev/null @@ -1,16 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create a binary vector - std::vector vec = {0xCA, 0xFE, 0xBA, 0xBE}; - - // create a binary JSON value with subtype 42 - json j = json::binary(vec, 42); - - // output type and subtype - std::cout << "type: " << j.type_name() << ", subtype: " << j.get_binary().subtype() << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get_binary.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get_binary.output deleted file mode 100644 index 74b05d2..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get_binary.output +++ /dev/null @@ -1 +0,0 @@ -type: binary, subtype: 42 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get_ptr.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get_ptr.cpp deleted file mode 100644 index 564ce0f..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get_ptr.cpp +++ /dev/null @@ -1,21 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create a JSON number - json value = 17; - - // explicitly getting pointers - auto p1 = value.get_ptr(); - auto p2 = value.get_ptr(); - auto p3 = value.get_ptr(); - auto p4 = value.get_ptr(); - auto p5 = value.get_ptr(); - - // print the pointees - std::cout << *p1 << ' ' << *p2 << ' ' << *p3 << ' ' << *p4 << '\n'; - std::cout << std::boolalpha << (p5 == nullptr) << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get_ptr.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get_ptr.output deleted file mode 100644 index a15dd77..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get_ptr.output +++ /dev/null @@ -1,2 +0,0 @@ -17 17 17 17 -true diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get_ref.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get_ref.cpp deleted file mode 100644 index ab25946..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get_ref.cpp +++ /dev/null @@ -1,27 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create a JSON number - json value = 17; - - // explicitly getting references - auto r1 = value.get_ref(); - auto r2 = value.get_ref(); - - // print the values - std::cout << r1 << ' ' << r2 << '\n'; - - // incompatible type throws exception - try - { - auto r3 = value.get_ref(); - } - catch (json::type_error& ex) - { - std::cout << ex.what() << '\n'; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get_ref.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get_ref.output deleted file mode 100644 index 3811afa..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get_ref.output +++ /dev/null @@ -1,2 +0,0 @@ -17 17 -[json.exception.type_error.303] incompatible ReferenceType for get_ref, actual type is number diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get_to.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get_to.cpp deleted file mode 100644 index 4705b17..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get_to.cpp +++ /dev/null @@ -1,60 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create a JSON value with different types - json json_types = - { - {"boolean", true}, - { - "number", { - {"integer", 42}, - {"floating-point", 17.23} - } - }, - {"string", "Hello, world!"}, - {"array", {1, 2, 3, 4, 5}}, - {"null", nullptr} - }; - - bool v1; - int v2; - short v3; - float v4; - int v5; - std::string v6; - std::vector v7; - std::unordered_map v8; - - - // use explicit conversions - json_types["boolean"].get_to(v1); - json_types["number"]["integer"].get_to(v2); - json_types["number"]["integer"].get_to(v3); - json_types["number"]["floating-point"].get_to(v4); - json_types["number"]["floating-point"].get_to(v5); - json_types["string"].get_to(v6); - json_types["array"].get_to(v7); - json_types.get_to(v8); - - // print the conversion results - std::cout << v1 << '\n'; - std::cout << v2 << ' ' << v3 << '\n'; - std::cout << v4 << ' ' << v5 << '\n'; - std::cout << v6 << '\n'; - - for (auto i : v7) - { - std::cout << i << ' '; - } - std::cout << "\n\n"; - - for (auto i : v8) - { - std::cout << i.first << ": " << i.second << '\n'; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get_to.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get_to.output deleted file mode 100644 index 5cd9cd3..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/get_to.output +++ /dev/null @@ -1,11 +0,0 @@ -1 -42 42 -17.23 17 -Hello, world! -1 2 3 4 5 - -string: "Hello, world!" -number: {"floating-point":17.23,"integer":42} -null: null -boolean: true -array: [1,2,3,4,5] diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/insert.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/insert.cpp deleted file mode 100644 index 4ee6098..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/insert.cpp +++ /dev/null @@ -1,17 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create a JSON array - json v = {1, 2, 3, 4}; - - // insert number 10 before number 3 - auto new_pos = v.insert(v.begin() + 2, 10); - - // output new array and result of insert call - std::cout << *new_pos << '\n'; - std::cout << v << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/insert.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/insert.output deleted file mode 100644 index ed5cab1..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/insert.output +++ /dev/null @@ -1,2 +0,0 @@ -10 -[1,2,10,3,4] diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/insert__count.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/insert__count.cpp deleted file mode 100644 index ce33b93..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/insert__count.cpp +++ /dev/null @@ -1,17 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create a JSON array - json v = {1, 2, 3, 4}; - - // insert number 7 copies of number 7 before number 3 - auto new_pos = v.insert(v.begin() + 2, 7, 7); - - // output new array and result of insert call - std::cout << *new_pos << '\n'; - std::cout << v << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/insert__count.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/insert__count.output deleted file mode 100644 index 294685a..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/insert__count.output +++ /dev/null @@ -1,2 +0,0 @@ -7 -[1,2,7,7,7,7,7,7,7,3,4] diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/insert__ilist.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/insert__ilist.cpp deleted file mode 100644 index a20766a..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/insert__ilist.cpp +++ /dev/null @@ -1,17 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create a JSON array - json v = {1, 2, 3, 4}; - - // insert range from v2 before the end of array v - auto new_pos = v.insert(v.end(), {7, 8, 9}); - - // output new array and result of insert call - std::cout << *new_pos << '\n'; - std::cout << v << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/insert__ilist.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/insert__ilist.output deleted file mode 100644 index b2fc7ee..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/insert__ilist.output +++ /dev/null @@ -1,2 +0,0 @@ -7 -[1,2,3,4,7,8,9] diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/insert__range.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/insert__range.cpp deleted file mode 100644 index 92fe63b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/insert__range.cpp +++ /dev/null @@ -1,20 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create a JSON array - json v = {1, 2, 3, 4}; - - // create a JSON array to copy values from - json v2 = {"one", "two", "three", "four"}; - - // insert range from v2 before the end of array v - auto new_pos = v.insert(v.end(), v2.begin(), v2.end()); - - // output new array and result of insert call - std::cout << *new_pos << '\n'; - std::cout << v << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/insert__range.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/insert__range.output deleted file mode 100644 index d50e9f6..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/insert__range.output +++ /dev/null @@ -1,2 +0,0 @@ -"one" -[1,2,3,4,"one","two","three","four"] diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/insert__range_object.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/insert__range_object.cpp deleted file mode 100644 index 97373d3..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/insert__range_object.cpp +++ /dev/null @@ -1,21 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create two JSON objects - json j1 = {{"one", "eins"}, {"two", "zwei"}}; - json j2 = {{"eleven", "elf"}, {"seventeen", "siebzehn"}}; - - // output objects - std::cout << j1 << '\n'; - std::cout << j2 << '\n'; - - // insert range from j2 to j1 - j1.insert(j2.begin(), j2.end()); - - // output result of insert call - std::cout << j1 << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/insert__range_object.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/insert__range_object.output deleted file mode 100644 index a598515..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/insert__range_object.output +++ /dev/null @@ -1,3 +0,0 @@ -{"one":"eins","two":"zwei"} -{"eleven":"elf","seventeen":"siebzehn"} -{"eleven":"elf","one":"eins","seventeen":"siebzehn","two":"zwei"} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/invalid_iterator.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/invalid_iterator.cpp deleted file mode 100644 index 5d3e622..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/invalid_iterator.cpp +++ /dev/null @@ -1,21 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - try - { - // calling iterator::key() on non-object iterator - json j = "string"; - json::iterator it = j.begin(); - auto k = it.key(); - } - catch (json::invalid_iterator& e) - { - // output exception information - std::cout << "message: " << e.what() << '\n' - << "exception id: " << e.id << std::endl; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/invalid_iterator.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/invalid_iterator.output deleted file mode 100644 index 8668c16..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/invalid_iterator.output +++ /dev/null @@ -1,2 +0,0 @@ -message: [json.exception.invalid_iterator.207] cannot use key() for non-object iterators -exception id: 207 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_array.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_array.cpp deleted file mode 100644 index 8ecc450..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_array.cpp +++ /dev/null @@ -1,30 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json j_null; - json j_boolean = true; - json j_number_integer = 17; - json j_number_unsigned_integer = 12345678987654321u; - json j_number_float = 23.42; - json j_object = {{"one", 1}, {"two", 2}}; - json j_array = {1, 2, 4, 8, 16}; - json j_string = "Hello, world"; - json j_binary = json::binary({1, 2, 3}); - - // call is_array() - std::cout << std::boolalpha; - std::cout << j_null.is_array() << '\n'; - std::cout << j_boolean.is_array() << '\n'; - std::cout << j_number_integer.is_array() << '\n'; - std::cout << j_number_unsigned_integer.is_array() << '\n'; - std::cout << j_number_float.is_array() << '\n'; - std::cout << j_object.is_array() << '\n'; - std::cout << j_array.is_array() << '\n'; - std::cout << j_string.is_array() << '\n'; - std::cout << j_binary.is_array() << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_array.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_array.output deleted file mode 100644 index 7b7ef3f..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_array.output +++ /dev/null @@ -1,9 +0,0 @@ -false -false -false -false -false -false -true -false -false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_binary.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_binary.cpp deleted file mode 100644 index d7f049e..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_binary.cpp +++ /dev/null @@ -1,30 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json j_null; - json j_boolean = true; - json j_number_integer = 17; - json j_number_unsigned_integer = 12345678987654321u; - json j_number_float = 23.42; - json j_object = {{"one", 1}, {"two", 2}}; - json j_array = {1, 2, 4, 8, 16}; - json j_string = "Hello, world"; - json j_binary = json::binary({1, 2, 3}); - - // call is_binary() - std::cout << std::boolalpha; - std::cout << j_null.is_binary() << '\n'; - std::cout << j_boolean.is_binary() << '\n'; - std::cout << j_number_integer.is_binary() << '\n'; - std::cout << j_number_unsigned_integer.is_binary() << '\n'; - std::cout << j_number_float.is_binary() << '\n'; - std::cout << j_object.is_binary() << '\n'; - std::cout << j_array.is_binary() << '\n'; - std::cout << j_string.is_binary() << '\n'; - std::cout << j_binary.is_binary() << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_binary.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_binary.output deleted file mode 100644 index 505e76e..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_binary.output +++ /dev/null @@ -1,9 +0,0 @@ -false -false -false -false -false -false -false -false -true diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_boolean.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_boolean.cpp deleted file mode 100644 index 0b79819..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_boolean.cpp +++ /dev/null @@ -1,30 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json j_null; - json j_boolean = true; - json j_number_integer = 17; - json j_number_unsigned_integer = 12345678987654321u; - json j_number_float = 23.42; - json j_object = {{"one", 1}, {"two", 2}}; - json j_array = {1, 2, 4, 8, 16}; - json j_string = "Hello, world"; - json j_binary = json::binary({1, 2, 3}); - - // call is_boolean() - std::cout << std::boolalpha; - std::cout << j_null.is_boolean() << '\n'; - std::cout << j_boolean.is_boolean() << '\n'; - std::cout << j_number_integer.is_boolean() << '\n'; - std::cout << j_number_unsigned_integer.is_boolean() << '\n'; - std::cout << j_number_float.is_boolean() << '\n'; - std::cout << j_object.is_boolean() << '\n'; - std::cout << j_array.is_boolean() << '\n'; - std::cout << j_string.is_boolean() << '\n'; - std::cout << j_binary.is_boolean() << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_boolean.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_boolean.output deleted file mode 100644 index eace89d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_boolean.output +++ /dev/null @@ -1,9 +0,0 @@ -false -true -false -false -false -false -false -false -false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_discarded.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_discarded.cpp deleted file mode 100644 index 0901665..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_discarded.cpp +++ /dev/null @@ -1,30 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json j_null; - json j_boolean = true; - json j_number_integer = 17; - json j_number_unsigned_integer = 12345678987654321u; - json j_number_float = 23.42; - json j_object = {{"one", 1}, {"two", 2}}; - json j_array = {1, 2, 4, 8, 16}; - json j_string = "Hello, world"; - json j_binary = json::binary({1, 2, 3}); - - // call is_discarded() - std::cout << std::boolalpha; - std::cout << j_null.is_discarded() << '\n'; - std::cout << j_boolean.is_discarded() << '\n'; - std::cout << j_number_integer.is_discarded() << '\n'; - std::cout << j_number_unsigned_integer.is_discarded() << '\n'; - std::cout << j_number_float.is_discarded() << '\n'; - std::cout << j_object.is_discarded() << '\n'; - std::cout << j_array.is_discarded() << '\n'; - std::cout << j_string.is_discarded() << '\n'; - std::cout << j_binary.is_discarded() << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_discarded.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_discarded.output deleted file mode 100644 index 14718f6..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_discarded.output +++ /dev/null @@ -1,9 +0,0 @@ -false -false -false -false -false -false -false -false -false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_null.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_null.cpp deleted file mode 100644 index 8a84332..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_null.cpp +++ /dev/null @@ -1,30 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json j_null; - json j_boolean = true; - json j_number_integer = 17; - json j_number_unsigned_integer = 12345678987654321u; - json j_number_float = 23.42; - json j_object = {{"one", 1}, {"two", 2}}; - json j_array = {1, 2, 4, 8, 16}; - json j_string = "Hello, world"; - json j_binary = json::binary({1, 2, 3}); - - // call is_null() - std::cout << std::boolalpha; - std::cout << j_null.is_null() << '\n'; - std::cout << j_boolean.is_null() << '\n'; - std::cout << j_number_integer.is_null() << '\n'; - std::cout << j_number_unsigned_integer.is_null() << '\n'; - std::cout << j_number_float.is_null() << '\n'; - std::cout << j_object.is_null() << '\n'; - std::cout << j_array.is_null() << '\n'; - std::cout << j_string.is_null() << '\n'; - std::cout << j_binary.is_null() << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_null.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_null.output deleted file mode 100644 index 42bbee2..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_null.output +++ /dev/null @@ -1,9 +0,0 @@ -true -false -false -false -false -false -false -false -false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_number.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_number.cpp deleted file mode 100644 index f107a04..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_number.cpp +++ /dev/null @@ -1,30 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json j_null; - json j_boolean = true; - json j_number_integer = 17; - json j_number_unsigned_integer = 12345678987654321u; - json j_number_float = 23.42; - json j_object = {{"one", 1}, {"two", 2}}; - json j_array = {1, 2, 4, 8, 16}; - json j_string = "Hello, world"; - json j_binary = json::binary({1, 2, 3}); - - // call is_number() - std::cout << std::boolalpha; - std::cout << j_null.is_number() << '\n'; - std::cout << j_boolean.is_number() << '\n'; - std::cout << j_number_integer.is_number() << '\n'; - std::cout << j_number_unsigned_integer.is_number() << '\n'; - std::cout << j_number_float.is_number() << '\n'; - std::cout << j_object.is_number() << '\n'; - std::cout << j_array.is_number() << '\n'; - std::cout << j_string.is_number() << '\n'; - std::cout << j_binary.is_number() << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_number.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_number.output deleted file mode 100644 index 53ef340..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_number.output +++ /dev/null @@ -1,9 +0,0 @@ -false -false -true -true -true -false -false -false -false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_number_float.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_number_float.cpp deleted file mode 100644 index bba2b44..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_number_float.cpp +++ /dev/null @@ -1,30 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json j_null; - json j_boolean = true; - json j_number_integer = 17; - json j_number_unsigned_integer = 12345678987654321u; - json j_number_float = 23.42; - json j_object = {{"one", 1}, {"two", 2}}; - json j_array = {1, 2, 4, 8, 16}; - json j_string = "Hello, world"; - json j_binary = json::binary({1, 2, 3}); - - // call is_number_float() - std::cout << std::boolalpha; - std::cout << j_null.is_number_float() << '\n'; - std::cout << j_boolean.is_number_float() << '\n'; - std::cout << j_number_integer.is_number_float() << '\n'; - std::cout << j_number_unsigned_integer.is_number_float() << '\n'; - std::cout << j_number_float.is_number_float() << '\n'; - std::cout << j_object.is_number_float() << '\n'; - std::cout << j_array.is_number_float() << '\n'; - std::cout << j_string.is_number_float() << '\n'; - std::cout << j_binary.is_number_float() << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_number_float.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_number_float.output deleted file mode 100644 index 0e64601..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_number_float.output +++ /dev/null @@ -1,9 +0,0 @@ -false -false -false -false -true -false -false -false -false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_number_integer.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_number_integer.cpp deleted file mode 100644 index 8d6a5ae..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_number_integer.cpp +++ /dev/null @@ -1,30 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json j_null; - json j_boolean = true; - json j_number_integer = 17; - json j_number_unsigned_integer = 12345678987654321u; - json j_number_float = 23.42; - json j_object = {{"one", 1}, {"two", 2}}; - json j_array = {1, 2, 4, 8, 16}; - json j_string = "Hello, world"; - json j_binary = json::binary({1, 2, 3}); - - // call is_number_integer() - std::cout << std::boolalpha; - std::cout << j_null.is_number_integer() << '\n'; - std::cout << j_boolean.is_number_integer() << '\n'; - std::cout << j_number_integer.is_number_integer() << '\n'; - std::cout << j_number_unsigned_integer.is_number_integer() << '\n'; - std::cout << j_number_float.is_number_integer() << '\n'; - std::cout << j_object.is_number_integer() << '\n'; - std::cout << j_array.is_number_integer() << '\n'; - std::cout << j_string.is_number_integer() << '\n'; - std::cout << j_binary.is_number_integer() << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_number_integer.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_number_integer.output deleted file mode 100644 index c1df310..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_number_integer.output +++ /dev/null @@ -1,9 +0,0 @@ -false -false -true -true -false -false -false -false -false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_number_unsigned.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_number_unsigned.cpp deleted file mode 100644 index b52ac6b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_number_unsigned.cpp +++ /dev/null @@ -1,30 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json j_null; - json j_boolean = true; - json j_number_integer = 17; - json j_number_unsigned_integer = 12345678987654321u; - json j_number_float = 23.42; - json j_object = {{"one", 1}, {"two", 2}}; - json j_array = {1, 2, 4, 8, 16}; - json j_string = "Hello, world"; - json j_binary = json::binary({1, 2, 3}); - - // call is_number_unsigned() - std::cout << std::boolalpha; - std::cout << j_null.is_number_unsigned() << '\n'; - std::cout << j_boolean.is_number_unsigned() << '\n'; - std::cout << j_number_integer.is_number_unsigned() << '\n'; - std::cout << j_number_unsigned_integer.is_number_unsigned() << '\n'; - std::cout << j_number_float.is_number_unsigned() << '\n'; - std::cout << j_object.is_number_unsigned() << '\n'; - std::cout << j_array.is_number_unsigned() << '\n'; - std::cout << j_string.is_number_unsigned() << '\n'; - std::cout << j_binary.is_number_unsigned() << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_number_unsigned.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_number_unsigned.output deleted file mode 100644 index e6059d4..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_number_unsigned.output +++ /dev/null @@ -1,9 +0,0 @@ -false -false -false -true -false -false -false -false -false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_object.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_object.cpp deleted file mode 100644 index a0216fd..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_object.cpp +++ /dev/null @@ -1,30 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json j_null; - json j_boolean = true; - json j_number_integer = 17; - json j_number_float = 23.42; - json j_number_unsigned_integer = 12345678987654321u; - json j_object = {{"one", 1}, {"two", 2}}; - json j_array = {1, 2, 4, 8, 16}; - json j_string = "Hello, world"; - json j_binary = json::binary({1, 2, 3}); - - // call is_object() - std::cout << std::boolalpha; - std::cout << j_null.is_object() << '\n'; - std::cout << j_boolean.is_object() << '\n'; - std::cout << j_number_integer.is_object() << '\n'; - std::cout << j_number_unsigned_integer.is_object() << '\n'; - std::cout << j_number_float.is_object() << '\n'; - std::cout << j_object.is_object() << '\n'; - std::cout << j_array.is_object() << '\n'; - std::cout << j_string.is_object() << '\n'; - std::cout << j_binary.is_object() << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_object.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_object.output deleted file mode 100644 index d9a429f..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_object.output +++ /dev/null @@ -1,9 +0,0 @@ -false -false -false -false -false -true -false -false -false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_primitive.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_primitive.cpp deleted file mode 100644 index af3968e..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_primitive.cpp +++ /dev/null @@ -1,30 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json j_null; - json j_boolean = true; - json j_number_integer = 17; - json j_number_float = 23.42; - json j_number_unsigned_integer = 12345678987654321u; - json j_object = {{"one", 1}, {"two", 2}}; - json j_array = {1, 2, 4, 8, 16}; - json j_string = "Hello, world"; - json j_binary = json::binary({1, 2, 3}); - - // call is_primitive() - std::cout << std::boolalpha; - std::cout << j_null.is_primitive() << '\n'; - std::cout << j_boolean.is_primitive() << '\n'; - std::cout << j_number_integer.is_primitive() << '\n'; - std::cout << j_number_unsigned_integer.is_primitive() << '\n'; - std::cout << j_number_float.is_primitive() << '\n'; - std::cout << j_object.is_primitive() << '\n'; - std::cout << j_array.is_primitive() << '\n'; - std::cout << j_string.is_primitive() << '\n'; - std::cout << j_binary.is_primitive() << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_primitive.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_primitive.output deleted file mode 100644 index 77af24c..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_primitive.output +++ /dev/null @@ -1,9 +0,0 @@ -true -true -true -true -true -false -false -true -true diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_string.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_string.cpp deleted file mode 100644 index c89f550..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_string.cpp +++ /dev/null @@ -1,30 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json j_null; - json j_boolean = true; - json j_number_integer = 17; - json j_number_float = 23.42; - json j_number_unsigned_integer = 12345678987654321u; - json j_object = {{"one", 1}, {"two", 2}}; - json j_array = {1, 2, 4, 8, 16}; - json j_string = "Hello, world"; - json j_binary = json::binary({1, 2, 3}); - - // call is_string() - std::cout << std::boolalpha; - std::cout << j_null.is_string() << '\n'; - std::cout << j_boolean.is_string() << '\n'; - std::cout << j_number_integer.is_string() << '\n'; - std::cout << j_number_unsigned_integer.is_string() << '\n'; - std::cout << j_number_float.is_string() << '\n'; - std::cout << j_object.is_string() << '\n'; - std::cout << j_array.is_string() << '\n'; - std::cout << j_string.is_string() << '\n'; - std::cout << j_binary.is_string() << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_string.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_string.output deleted file mode 100644 index 6446f18..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_string.output +++ /dev/null @@ -1,9 +0,0 @@ -false -false -false -false -false -false -false -true -false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_structured.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_structured.cpp deleted file mode 100644 index 41947b1..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_structured.cpp +++ /dev/null @@ -1,30 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json j_null; - json j_boolean = true; - json j_number_integer = 17; - json j_number_float = 23.42; - json j_number_unsigned_integer = 12345678987654321u; - json j_object = {{"one", 1}, {"two", 2}}; - json j_array = {1, 2, 4, 8, 16}; - json j_string = "Hello, world"; - json j_binary = json::binary({1, 2, 3}); - - // call is_structured() - std::cout << std::boolalpha; - std::cout << j_null.is_structured() << '\n'; - std::cout << j_boolean.is_structured() << '\n'; - std::cout << j_number_integer.is_structured() << '\n'; - std::cout << j_number_unsigned_integer.is_structured() << '\n'; - std::cout << j_number_float.is_structured() << '\n'; - std::cout << j_object.is_structured() << '\n'; - std::cout << j_array.is_structured() << '\n'; - std::cout << j_string.is_structured() << '\n'; - std::cout << j_binary.is_structured() << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_structured.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_structured.output deleted file mode 100644 index 625c124..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/is_structured.output +++ /dev/null @@ -1,9 +0,0 @@ -false -false -false -false -false -true -true -false -false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/items.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/items.cpp deleted file mode 100644 index 9cd2b51..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/items.cpp +++ /dev/null @@ -1,23 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json j_object = {{"one", 1}, {"two", 2}}; - json j_array = {1, 2, 4, 8, 16}; - - // example for an object - for (auto& x : j_object.items()) - { - std::cout << "key: " << x.key() << ", value: " << x.value() << '\n'; - } - - // example for an array - for (auto& x : j_array.items()) - { - std::cout << "key: " << x.key() << ", value: " << x.value() << '\n'; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/items.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/items.output deleted file mode 100644 index 89b09f5..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/items.output +++ /dev/null @@ -1,7 +0,0 @@ -key: one, value: 1 -key: two, value: 2 -key: 0, value: 1 -key: 1, value: 2 -key: 2, value: 4 -key: 3, value: 8 -key: 4, value: 16 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_lines.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_lines.cpp deleted file mode 100644 index 233c81a..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_lines.cpp +++ /dev/null @@ -1,22 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - // JSON Lines (see https://jsonlines.org) - std::stringstream input; - input << R"({"name": "Gilbert", "wins": [["straight", "7♣"], ["one pair", "10♥"]]} -{"name": "Alexa", "wins": [["two pair", "4♠"], ["two pair", "9♠"]]} -{"name": "May", "wins": []} -{"name": "Deloise", "wins": [["three of a kind", "5♣"]]} -)"; - - std::string line; - while (std::getline(input, line)) - { - std::cout << json::parse(line) << std::endl; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_lines.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_lines.output deleted file mode 100644 index 1b41224..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_lines.output +++ /dev/null @@ -1,4 +0,0 @@ -{"name":"Gilbert","wins":[["straight","7♣"],["one pair","10♥"]]} -{"name":"Alexa","wins":[["two pair","4♠"],["two pair","9♠"]]} -{"name":"May","wins":[]} -{"name":"Deloise","wins":[["three of a kind","5♣"]]} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer.cpp deleted file mode 100644 index 75b9717..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer.cpp +++ /dev/null @@ -1,47 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // correct JSON pointers - json::json_pointer p1; - json::json_pointer p2(""); - json::json_pointer p3("/"); - json::json_pointer p4("//"); - json::json_pointer p5("/foo/bar"); - json::json_pointer p6("/foo/bar/-"); - json::json_pointer p7("/foo/~0"); - json::json_pointer p8("/foo/~1"); - - // error: JSON pointer does not begin with a slash - try - { - json::json_pointer p9("foo"); - } - catch (json::parse_error& e) - { - std::cout << e.what() << '\n'; - } - - // error: JSON pointer uses escape symbol ~ not followed by 0 or 1 - try - { - json::json_pointer p10("/foo/~"); - } - catch (json::parse_error& e) - { - std::cout << e.what() << '\n'; - } - - // error: JSON pointer uses escape symbol ~ not followed by 0 or 1 - try - { - json::json_pointer p11("/foo/~3"); - } - catch (json::parse_error& e) - { - std::cout << e.what() << '\n'; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer.output deleted file mode 100644 index 9e027d6..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer.output +++ /dev/null @@ -1,3 +0,0 @@ -[json.exception.parse_error.107] parse error at byte 1: JSON pointer must be empty or begin with '/' - was: 'foo' -[json.exception.parse_error.108] parse error: escape character '~' must be followed with '0' or '1' -[json.exception.parse_error.108] parse error: escape character '~' must be followed with '0' or '1' diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__back.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__back.cpp deleted file mode 100644 index dd3b210..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__back.cpp +++ /dev/null @@ -1,15 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // different JSON Pointers - json::json_pointer ptr1("/foo"); - json::json_pointer ptr2("/foo/0"); - - // call empty() - std::cout << "last reference token of \"" << ptr1 << "\" is \"" << ptr1.back() << "\"\n" - << "last reference token of \"" << ptr2 << "\" is \"" << ptr2.back() << "\"" << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__back.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__back.output deleted file mode 100644 index a89357b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__back.output +++ /dev/null @@ -1,2 +0,0 @@ -last reference token of "/foo" is "foo" -last reference token of "/foo/0" is "0" diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__empty.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__empty.cpp deleted file mode 100644 index 57257e8..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__empty.cpp +++ /dev/null @@ -1,20 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // different JSON Pointers - json::json_pointer ptr0; - json::json_pointer ptr1(""); - json::json_pointer ptr2("/foo"); - json::json_pointer ptr3("/foo/0"); - - // call empty() - std::cout << std::boolalpha - << "\"" << ptr0 << "\": " << ptr0.empty() << '\n' - << "\"" << ptr1 << "\": " << ptr1.empty() << '\n' - << "\"" << ptr2 << "\": " << ptr2.empty() << '\n' - << "\"" << ptr3 << "\": " << ptr3.empty() << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__empty.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__empty.output deleted file mode 100644 index a7ee49c..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__empty.output +++ /dev/null @@ -1,4 +0,0 @@ -"": true -"": true -"/foo": false -"/foo/0": false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator__equal.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator__equal.cpp deleted file mode 100644 index dce6df0..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator__equal.cpp +++ /dev/null @@ -1,19 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // different JSON pointers - json::json_pointer ptr0; - json::json_pointer ptr1(""); - json::json_pointer ptr2("/foo"); - - // compare JSON pointers - std::cout << std::boolalpha - << "\"" << ptr0 << "\" == \"" << ptr0 << "\": " << (ptr0 == ptr0) << '\n' - << "\"" << ptr0 << "\" == \"" << ptr1 << "\": " << (ptr0 == ptr1) << '\n' - << "\"" << ptr1 << "\" == \"" << ptr2 << "\": " << (ptr1 == ptr2) << '\n' - << "\"" << ptr2 << "\" == \"" << ptr2 << "\": " << (ptr2 == ptr2) << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator__equal.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator__equal.output deleted file mode 100644 index 9a76125..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator__equal.output +++ /dev/null @@ -1,4 +0,0 @@ -"" == "": true -"" == "": true -"" == "/foo": false -"/foo" == "/foo": true diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator__equal_stringtype.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator__equal_stringtype.cpp deleted file mode 100644 index af8ec5a..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator__equal_stringtype.cpp +++ /dev/null @@ -1,33 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - // different JSON pointers - json::json_pointer ptr0; - json::json_pointer ptr1(""); - json::json_pointer ptr2("/foo"); - - // different strings - std::string str0(""); - std::string str1("/foo"); - std::string str2("bar"); - - // compare JSON pointers and strings - std::cout << std::boolalpha - << "\"" << ptr0 << "\" == \"" << str0 << "\": " << (ptr0 == str0) << '\n' - << "\"" << str0 << "\" == \"" << ptr1 << "\": " << (str0 == ptr1) << '\n' - << "\"" << ptr2 << "\" == \"" << str1 << "\": " << (ptr2 == str1) << std::endl; - - try - { - std::cout << "\"" << str2 << "\" == \"" << ptr2 << "\": " << (str2 == ptr2) << std::endl; - } - catch (const json::parse_error& ex) - { - std::cout << ex.what() << std::endl; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator__equal_stringtype.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator__equal_stringtype.output deleted file mode 100644 index 7fb299d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator__equal_stringtype.output +++ /dev/null @@ -1,4 +0,0 @@ -"" == "": true -"" == "": true -"/foo" == "/foo": true -"bar" == "/foo": [json.exception.parse_error.107] parse error at byte 1: JSON pointer must be empty or begin with '/' - was: 'bar' diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator__notequal.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator__notequal.cpp deleted file mode 100644 index 9bbdd53..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator__notequal.cpp +++ /dev/null @@ -1,19 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // different JSON pointers - json::json_pointer ptr0; - json::json_pointer ptr1(""); - json::json_pointer ptr2("/foo"); - - // compare JSON pointers - std::cout << std::boolalpha - << "\"" << ptr0 << "\" != \"" << ptr0 << "\": " << (ptr0 != ptr0) << '\n' - << "\"" << ptr0 << "\" != \"" << ptr1 << "\": " << (ptr0 != ptr1) << '\n' - << "\"" << ptr1 << "\" != \"" << ptr2 << "\": " << (ptr1 != ptr2) << '\n' - << "\"" << ptr2 << "\" != \"" << ptr2 << "\": " << (ptr2 != ptr2) << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator__notequal.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator__notequal.output deleted file mode 100644 index de891f0..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator__notequal.output +++ /dev/null @@ -1,4 +0,0 @@ -"" != "": false -"" != "": false -"" != "/foo": true -"/foo" != "/foo": false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator__notequal_stringtype.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator__notequal_stringtype.cpp deleted file mode 100644 index b9b8987..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator__notequal_stringtype.cpp +++ /dev/null @@ -1,32 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // different JSON pointers - json::json_pointer ptr0; - json::json_pointer ptr1(""); - json::json_pointer ptr2("/foo"); - - // different strings - std::string str0(""); - std::string str1("/foo"); - std::string str2("bar"); - - // compare JSON pointers and strings - std::cout << std::boolalpha - << "\"" << ptr0 << "\" != \"" << str0 << "\": " << (ptr0 != str0) << '\n' - << "\"" << str0 << "\" != \"" << ptr1 << "\": " << (str0 != ptr1) << '\n' - << "\"" << ptr2 << "\" != \"" << str1 << "\": " << (ptr2 != str1) << std::endl; - - try - { - std::cout << "\"" << str2 << "\" != \"" << ptr2 << "\": " << (str2 != ptr2) << std::endl; - } - catch (const json::parse_error& ex) - { - std::cout << ex.what() << std::endl; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator__notequal_stringtype.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator__notequal_stringtype.output deleted file mode 100644 index 61331b7..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator__notequal_stringtype.output +++ /dev/null @@ -1,4 +0,0 @@ -"" != "": false -"" != "": false -"/foo" != "/foo": false -"bar" != "/foo": [json.exception.parse_error.107] parse error at byte 1: JSON pointer must be empty or begin with '/' - was: 'bar' diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator_add.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator_add.cpp deleted file mode 100644 index 14bd745..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator_add.cpp +++ /dev/null @@ -1,23 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create a JSON pointer - json::json_pointer ptr("/foo"); - std::cout << "\"" << ptr << "\"\n"; - - // append a JSON Pointer - ptr /= json::json_pointer("/bar/baz"); - std::cout << "\"" << ptr << "\"\n"; - - // append a string - ptr /= "fob"; - std::cout << "\"" << ptr << "\"\n"; - - // append an array index - ptr /= 42; - std::cout << "\"" << ptr << "\"" << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator_add.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator_add.output deleted file mode 100644 index ae13afe..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator_add.output +++ /dev/null @@ -1,4 +0,0 @@ -"/foo" -"/foo/bar/baz" -"/foo/bar/baz/fob" -"/foo/bar/baz/fob/42" diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator_add_binary.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator_add_binary.cpp deleted file mode 100644 index d26a0d1..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator_add_binary.cpp +++ /dev/null @@ -1,19 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create a JSON pointer - json::json_pointer ptr("/foo"); - - // append a JSON Pointer - std::cout << "\"" << ptr / json::json_pointer("/bar/baz") << "\"\n"; - - // append a string - std::cout << "\"" << ptr / "fob" << "\"\n"; - - // append an array index - std::cout << "\"" << ptr / 42 << "\"" << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator_add_binary.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator_add_binary.output deleted file mode 100644 index 7536042..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator_add_binary.output +++ /dev/null @@ -1,3 +0,0 @@ -"/foo/bar/baz" -"/foo/fob" -"/foo/42" diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator_string_t.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator_string_t.cpp deleted file mode 100644 index 56f2130..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator_string_t.cpp +++ /dev/null @@ -1,19 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // different JSON Pointers - json::json_pointer ptr1("/foo/0"); - json::json_pointer ptr2("/a~1b"); - - // implicit conversion to string - std::string s; - s += ptr1; - s += "\n"; - s += ptr2; - - std::cout << s << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator_string_t.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator_string_t.output deleted file mode 100644 index ec6aba2..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__operator_string_t.output +++ /dev/null @@ -1,2 +0,0 @@ -/foo/0 -/a~1b diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__parent_pointer.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__parent_pointer.cpp deleted file mode 100644 index ef9df45..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__parent_pointer.cpp +++ /dev/null @@ -1,18 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // different JSON Pointers - json::json_pointer ptr1(""); - json::json_pointer ptr2("/foo"); - json::json_pointer ptr3("/foo/0"); - - // call parent_pointer() - std::cout << std::boolalpha - << "parent of \"" << ptr1 << "\" is \"" << ptr1.parent_pointer() << "\"\n" - << "parent of \"" << ptr2 << "\" is \"" << ptr2.parent_pointer() << "\"\n" - << "parent of \"" << ptr3 << "\" is \"" << ptr3.parent_pointer() << "\"" << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__parent_pointer.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__parent_pointer.output deleted file mode 100644 index 4cc6f3f..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__parent_pointer.output +++ /dev/null @@ -1,3 +0,0 @@ -parent of "" is "" -parent of "/foo" is "" -parent of "/foo/0" is "/foo" diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__pop_back.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__pop_back.cpp deleted file mode 100644 index fd077b7..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__pop_back.cpp +++ /dev/null @@ -1,21 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create empty JSON Pointer - json::json_pointer ptr("/foo/bar/baz"); - std::cout << "\"" << ptr << "\"\n"; - - // call pop_back() - ptr.pop_back(); - std::cout << "\"" << ptr << "\"\n"; - - ptr.pop_back(); - std::cout << "\"" << ptr << "\"\n"; - - ptr.pop_back(); - std::cout << "\"" << ptr << "\"\n"; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__pop_back.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__pop_back.output deleted file mode 100644 index b0468dc..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__pop_back.output +++ /dev/null @@ -1,4 +0,0 @@ -"/foo/bar/baz" -"/foo/bar" -"/foo" -"" diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__push_back.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__push_back.cpp deleted file mode 100644 index e6b59a1..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__push_back.cpp +++ /dev/null @@ -1,21 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create empty JSON Pointer - json::json_pointer ptr; - std::cout << "\"" << ptr << "\"\n"; - - // call push_back() - ptr.push_back("foo"); - std::cout << "\"" << ptr << "\"\n"; - - ptr.push_back("0"); - std::cout << "\"" << ptr << "\"\n"; - - ptr.push_back("bar"); - std::cout << "\"" << ptr << "\"\n"; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__push_back.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__push_back.output deleted file mode 100644 index 92c019c..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__push_back.output +++ /dev/null @@ -1,4 +0,0 @@ -"" -"/foo" -"/foo/0" -"/foo/0/bar" diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__string_t.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__string_t.cpp deleted file mode 100644 index fbe0f17..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__string_t.cpp +++ /dev/null @@ -1,13 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - json::json_pointer::string_t s = "This is a string."; - - std::cout << s << std::endl; - - std::cout << std::boolalpha << std::is_same::value << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__string_t.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__string_t.output deleted file mode 100644 index d871137..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__string_t.output +++ /dev/null @@ -1,2 +0,0 @@ -This is a string. -true diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__to_string.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__to_string.cpp deleted file mode 100644 index 31d35a7..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__to_string.cpp +++ /dev/null @@ -1,34 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // different JSON Pointers - json::json_pointer ptr1(""); - json::json_pointer ptr2("/foo"); - json::json_pointer ptr3("/foo/0"); - json::json_pointer ptr4("/"); - json::json_pointer ptr5("/a~1b"); - json::json_pointer ptr6("/c%d"); - json::json_pointer ptr7("/e^f"); - json::json_pointer ptr8("/g|h"); - json::json_pointer ptr9("/i\\j"); - json::json_pointer ptr10("/k\"l"); - json::json_pointer ptr11("/ "); - json::json_pointer ptr12("/m~0n"); - - std::cout << "\"" << ptr1.to_string() << "\"\n" - << "\"" << ptr2.to_string() << "\"\n" - << "\"" << ptr3.to_string() << "\"\n" - << "\"" << ptr4.to_string() << "\"\n" - << "\"" << ptr5.to_string() << "\"\n" - << "\"" << ptr6.to_string() << "\"\n" - << "\"" << ptr7.to_string() << "\"\n" - << "\"" << ptr8.to_string() << "\"\n" - << "\"" << ptr9.to_string() << "\"\n" - << "\"" << ptr10.to_string() << "\"\n" - << "\"" << ptr11.to_string() << "\"\n" - << "\"" << ptr12.to_string() << "\"" << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__to_string.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__to_string.output deleted file mode 100644 index 3c44135..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/json_pointer__to_string.output +++ /dev/null @@ -1,12 +0,0 @@ -"" -"/foo" -"/foo/0" -"/" -"/a~1b" -"/c%d" -"/e^f" -"/g|h" -"/i\j" -"/k"l" -"/ " -"/m~0n" diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/max_size.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/max_size.cpp deleted file mode 100644 index c2ffc54..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/max_size.cpp +++ /dev/null @@ -1,25 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json j_null; - json j_boolean = true; - json j_number_integer = 17; - json j_number_float = 23.42; - json j_object = {{"one", 1}, {"two", 2}}; - json j_array = {1, 2, 4, 8, 16}; - json j_string = "Hello, world"; - - // call max_size() - std::cout << j_null.max_size() << '\n'; - std::cout << j_boolean.max_size() << '\n'; - std::cout << j_number_integer.max_size() << '\n'; - std::cout << j_number_float.max_size() << '\n'; - std::cout << j_object.max_size() << '\n'; - std::cout << j_array.max_size() << '\n'; - std::cout << j_string.max_size() << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/max_size.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/max_size.output deleted file mode 100644 index b8dcb4d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/max_size.output +++ /dev/null @@ -1,7 +0,0 @@ -0 -1 -1 -1 -115292150460684697 -576460752303423487 -1 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/merge_patch.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/merge_patch.cpp deleted file mode 100644 index f3fee1e..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/merge_patch.cpp +++ /dev/null @@ -1,41 +0,0 @@ -#include -#include -#include // for std::setw - -using json = nlohmann::json; -using namespace nlohmann::literals; - -int main() -{ - // the original document - json document = R"({ - "title": "Goodbye!", - "author": { - "givenName": "John", - "familyName": "Doe" - }, - "tags": [ - "example", - "sample" - ], - "content": "This will be unchanged" - })"_json; - - // the patch - json patch = R"({ - "title": "Hello!", - "phoneNumber": "+01-123-456-7890", - "author": { - "familyName": null - }, - "tags": [ - "example" - ] - })"_json; - - // apply the patch - document.merge_patch(patch); - - // output original and patched document - std::cout << std::setw(4) << document << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/merge_patch.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/merge_patch.output deleted file mode 100644 index 96adb7b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/merge_patch.output +++ /dev/null @@ -1,11 +0,0 @@ -{ - "author": { - "givenName": "John" - }, - "content": "This will be unchanged", - "phoneNumber": "+01-123-456-7890", - "tags": [ - "example" - ], - "title": "Hello!" -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/meta.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/meta.cpp deleted file mode 100644 index a051575..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/meta.cpp +++ /dev/null @@ -1,11 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - // call meta() - std::cout << std::setw(4) << json::meta() << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/meta.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/meta.output deleted file mode 100644 index 9ceb5e2..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/meta.output +++ /dev/null @@ -1,17 +0,0 @@ -{ - "compiler": { - "c++": "201103", - "family": "gcc", - "version": "12.1.0" - }, - "copyright": "(C) 2013-2022 Niels Lohmann", - "name": "JSON for Modern C++", - "platform": "apple", - "url": "https://github.com/nlohmann/json", - "version": { - "major": 3, - "minor": 11, - "patch": 2, - "string": "3.11.2" - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_intrusive_explicit.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_intrusive_explicit.cpp deleted file mode 100644 index 7d2ba8a..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_intrusive_explicit.cpp +++ /dev/null @@ -1,60 +0,0 @@ -#include -#include - -using json = nlohmann::json; -using namespace nlohmann::literals; - -namespace ns -{ -class person -{ - private: - std::string name = "John Doe"; - std::string address = "123 Fake St"; - int age = -1; - - public: - person() = default; - person(std::string name_, std::string address_, int age_) - : name(std::move(name_)), address(std::move(address_)), age(age_) - {} - - friend void to_json(nlohmann::json& nlohmann_json_j, const person& nlohmann_json_t) - { - nlohmann_json_j["name"] = nlohmann_json_t.name; - nlohmann_json_j["address"] = nlohmann_json_t.address; - nlohmann_json_j["age"] = nlohmann_json_t.age; - } - - friend void from_json(const nlohmann::json& nlohmann_json_j, person& nlohmann_json_t) - { - nlohmann_json_t.name = nlohmann_json_j.at("name"); - nlohmann_json_t.address = nlohmann_json_j.at("address"); - nlohmann_json_t.age = nlohmann_json_j.at("age"); - } -}; -} // namespace ns - -int main() -{ - ns::person p = {"Ned Flanders", "744 Evergreen Terrace", 60}; - - // serialization: person -> json - json j = p; - std::cout << "serialization: " << j << std::endl; - - // deserialization: json -> person - json j2 = R"({"address": "742 Evergreen Terrace", "age": 40, "name": "Homer Simpson"})"_json; - auto p2 = j2.get(); - - // incomplete deserialization: - json j3 = R"({"address": "742 Evergreen Terrace", "name": "Maggie Simpson"})"_json; - try - { - auto p3 = j3.get(); - } - catch (json::exception& e) - { - std::cout << "deserialization failed: " << e.what() << std::endl; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_intrusive_explicit.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_intrusive_explicit.output deleted file mode 100644 index 37f4eb4..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_intrusive_explicit.output +++ /dev/null @@ -1,2 +0,0 @@ -serialization: {"address":"744 Evergreen Terrace","age":60,"name":"Ned Flanders"} -deserialization failed: [json.exception.out_of_range.403] key 'age' not found diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_intrusive_macro.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_intrusive_macro.cpp deleted file mode 100644 index 2977cd4..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_intrusive_macro.cpp +++ /dev/null @@ -1,48 +0,0 @@ -#include -#include - -using json = nlohmann::json; -using namespace nlohmann::literals; - -namespace ns -{ -class person -{ - private: - std::string name = "John Doe"; - std::string address = "123 Fake St"; - int age = -1; - - public: - person() = default; - person(std::string name_, std::string address_, int age_) - : name(std::move(name_)), address(std::move(address_)), age(age_) - {} - - NLOHMANN_DEFINE_TYPE_INTRUSIVE(person, name, address, age) -}; -} // namespace ns - -int main() -{ - ns::person p = {"Ned Flanders", "744 Evergreen Terrace", 60}; - - // serialization: person -> json - json j = p; - std::cout << "serialization: " << j << std::endl; - - // deserialization: json -> person - json j2 = R"({"address": "742 Evergreen Terrace", "age": 40, "name": "Homer Simpson"})"_json; - auto p2 = j2.get(); - - // incomplete deserialization: - json j3 = R"({"address": "742 Evergreen Terrace", "name": "Maggie Simpson"})"_json; - try - { - auto p3 = j3.get(); - } - catch (json::exception& e) - { - std::cout << "deserialization failed: " << e.what() << std::endl; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_intrusive_macro.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_intrusive_macro.output deleted file mode 100644 index 37f4eb4..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_intrusive_macro.output +++ /dev/null @@ -1,2 +0,0 @@ -serialization: {"address":"744 Evergreen Terrace","age":60,"name":"Ned Flanders"} -deserialization failed: [json.exception.out_of_range.403] key 'age' not found diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_intrusive_with_default_explicit.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_intrusive_with_default_explicit.cpp deleted file mode 100644 index 7400c47..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_intrusive_with_default_explicit.cpp +++ /dev/null @@ -1,55 +0,0 @@ -#include -#include - -using json = nlohmann::json; -using namespace nlohmann::literals; - -namespace ns -{ -class person -{ - private: - std::string name = "John Doe"; - std::string address = "123 Fake St"; - int age = -1; - - public: - person() = default; - person(std::string name_, std::string address_, int age_) - : name(std::move(name_)), address(std::move(address_)), age(age_) - {} - - friend void to_json(nlohmann::json& nlohmann_json_j, const person& nlohmann_json_t) - { - nlohmann_json_j["name"] = nlohmann_json_t.name; - nlohmann_json_j["address"] = nlohmann_json_t.address; - nlohmann_json_j["age"] = nlohmann_json_t.age; - } - - friend void from_json(const nlohmann::json& nlohmann_json_j, person& nlohmann_json_t) - { - person nlohmann_json_default_obj; - nlohmann_json_t.name = nlohmann_json_j.value("name", nlohmann_json_default_obj.name); - nlohmann_json_t.address = nlohmann_json_j.value("address", nlohmann_json_default_obj.address); - nlohmann_json_t.age = nlohmann_json_j.value("age", nlohmann_json_default_obj.age); - } -}; -} // namespace ns - -int main() -{ - ns::person p = {"Ned Flanders", "744 Evergreen Terrace", 60}; - - // serialization: person -> json - json j = p; - std::cout << "serialization: " << j << std::endl; - - // deserialization: json -> person - json j2 = R"({"address": "742 Evergreen Terrace", "age": 40, "name": "Homer Simpson"})"_json; - auto p2 = j2.get(); - - // incomplete deserialization: - json j3 = R"({"address": "742 Evergreen Terrace", "name": "Maggie Simpson"})"_json; - auto p3 = j3.get(); - std::cout << "roundtrip: " << json(p3) << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_intrusive_with_default_explicit.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_intrusive_with_default_explicit.output deleted file mode 100644 index 1a255f6..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_intrusive_with_default_explicit.output +++ /dev/null @@ -1,2 +0,0 @@ -serialization: {"address":"744 Evergreen Terrace","age":60,"name":"Ned Flanders"} -roundtrip: {"address":"742 Evergreen Terrace","age":-1,"name":"Maggie Simpson"} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_intrusive_with_default_macro.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_intrusive_with_default_macro.cpp deleted file mode 100644 index 851a358..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_intrusive_with_default_macro.cpp +++ /dev/null @@ -1,42 +0,0 @@ -#include -#include - -using json = nlohmann::json; -using namespace nlohmann::literals; - -namespace ns -{ -class person -{ - private: - std::string name = "John Doe"; - std::string address = "123 Fake St"; - int age = -1; - - public: - person() = default; - person(std::string name_, std::string address_, int age_) - : name(std::move(name_)), address(std::move(address_)), age(age_) - {} - - NLOHMANN_DEFINE_TYPE_INTRUSIVE_WITH_DEFAULT(person, name, address, age) -}; -} // namespace ns - -int main() -{ - ns::person p = {"Ned Flanders", "744 Evergreen Terrace", 60}; - - // serialization: person -> json - json j = p; - std::cout << "serialization: " << j << std::endl; - - // deserialization: json -> person - json j2 = R"({"address": "742 Evergreen Terrace", "age": 40, "name": "Homer Simpson"})"_json; - auto p2 = j2.get(); - - // incomplete deserialization: - json j3 = R"({"address": "742 Evergreen Terrace", "name": "Maggie Simpson"})"_json; - auto p3 = j3.get(); - std::cout << "roundtrip: " << json(p3) << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_intrusive_with_default_macro.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_intrusive_with_default_macro.output deleted file mode 100644 index 1a255f6..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_intrusive_with_default_macro.output +++ /dev/null @@ -1,2 +0,0 @@ -serialization: {"address":"744 Evergreen Terrace","age":60,"name":"Ned Flanders"} -roundtrip: {"address":"742 Evergreen Terrace","age":-1,"name":"Maggie Simpson"} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_non_intrusive_explicit.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_non_intrusive_explicit.cpp deleted file mode 100644 index b71613d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_non_intrusive_explicit.cpp +++ /dev/null @@ -1,53 +0,0 @@ -#include -#include - -using json = nlohmann::json; -using namespace nlohmann::literals; - -namespace ns -{ -struct person -{ - std::string name; - std::string address; - int age; -}; - -void to_json(nlohmann::json& nlohmann_json_j, const person& nlohmann_json_t) -{ - nlohmann_json_j["name"] = nlohmann_json_t.name; - nlohmann_json_j["address"] = nlohmann_json_t.address; - nlohmann_json_j["age"] = nlohmann_json_t.age; -} - -void from_json(const nlohmann::json& nlohmann_json_j, person& nlohmann_json_t) -{ - nlohmann_json_t.name = nlohmann_json_j.at("name"); - nlohmann_json_t.address = nlohmann_json_j.at("address"); - nlohmann_json_t.age = nlohmann_json_j.at("age"); -} -} // namespace ns - -int main() -{ - ns::person p = {"Ned Flanders", "744 Evergreen Terrace", 60}; - - // serialization: person -> json - json j = p; - std::cout << "serialization: " << j << std::endl; - - // deserialization: json -> person - json j2 = R"({"address": "742 Evergreen Terrace", "age": 40, "name": "Homer Simpson"})"_json; - auto p2 = j2.get(); - - // incomplete deserialization: - json j3 = R"({"address": "742 Evergreen Terrace", "name": "Maggie Simpson"})"_json; - try - { - auto p3 = j3.get(); - } - catch (json::exception& e) - { - std::cout << "deserialization failed: " << e.what() << std::endl; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_non_intrusive_explicit.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_non_intrusive_explicit.output deleted file mode 100644 index 37f4eb4..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_non_intrusive_explicit.output +++ /dev/null @@ -1,2 +0,0 @@ -serialization: {"address":"744 Evergreen Terrace","age":60,"name":"Ned Flanders"} -deserialization failed: [json.exception.out_of_range.403] key 'age' not found diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_non_intrusive_macro.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_non_intrusive_macro.cpp deleted file mode 100644 index be11a45..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_non_intrusive_macro.cpp +++ /dev/null @@ -1,41 +0,0 @@ -#include -#include - -using json = nlohmann::json; -using namespace nlohmann::literals; - -namespace ns -{ -struct person -{ - std::string name; - std::string address; - int age; -}; - -NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE(person, name, address, age) -} // namespace ns - -int main() -{ - ns::person p = {"Ned Flanders", "744 Evergreen Terrace", 60}; - - // serialization: person -> json - json j = p; - std::cout << "serialization: " << j << std::endl; - - // deserialization: json -> person - json j2 = R"({"address": "742 Evergreen Terrace", "age": 40, "name": "Homer Simpson"})"_json; - auto p2 = j2.get(); - - // incomplete deserialization: - json j3 = R"({"address": "742 Evergreen Terrace", "name": "Maggie Simpson"})"_json; - try - { - auto p3 = j3.get(); - } - catch (json::exception& e) - { - std::cout << "deserialization failed: " << e.what() << std::endl; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_non_intrusive_macro.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_non_intrusive_macro.output deleted file mode 100644 index 37f4eb4..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_non_intrusive_macro.output +++ /dev/null @@ -1,2 +0,0 @@ -serialization: {"address":"744 Evergreen Terrace","age":60,"name":"Ned Flanders"} -deserialization failed: [json.exception.out_of_range.403] key 'age' not found diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_non_intrusive_with_default_explicit.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_non_intrusive_with_default_explicit.cpp deleted file mode 100644 index 6b538d1..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_non_intrusive_with_default_explicit.cpp +++ /dev/null @@ -1,53 +0,0 @@ -#include -#include - -using json = nlohmann::json; -using namespace nlohmann::literals; - -namespace ns -{ -struct person -{ - std::string name = "John Doe"; - std::string address = "123 Fake St"; - int age = -1; - - person() = default; - person(std::string name_, std::string address_, int age_) - : name(std::move(name_)), address(std::move(address_)), age(age_) - {} -}; - -void to_json(nlohmann::json& nlohmann_json_j, const person& nlohmann_json_t) -{ - nlohmann_json_j["name"] = nlohmann_json_t.name; - nlohmann_json_j["address"] = nlohmann_json_t.address; - nlohmann_json_j["age"] = nlohmann_json_t.age; -} - -void from_json(const nlohmann::json& nlohmann_json_j, person& nlohmann_json_t) -{ - person nlohmann_json_default_obj; - nlohmann_json_t.name = nlohmann_json_j.value("name", nlohmann_json_default_obj.name); - nlohmann_json_t.address = nlohmann_json_j.value("address", nlohmann_json_default_obj.address); - nlohmann_json_t.age = nlohmann_json_j.value("age", nlohmann_json_default_obj.age); -} -} // namespace ns - -int main() -{ - ns::person p = {"Ned Flanders", "744 Evergreen Terrace", 60}; - - // serialization: person -> json - json j = p; - std::cout << "serialization: " << j << std::endl; - - // deserialization: json -> person - json j2 = R"({"address": "742 Evergreen Terrace", "age": 40, "name": "Homer Simpson"})"_json; - auto p2 = j2.get(); - - // incomplete deserialization: - json j3 = R"({"address": "742 Evergreen Terrace", "name": "Maggie Simpson"})"_json; - auto p3 = j3.get(); - std::cout << "roundtrip: " << json(p3) << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_non_intrusive_with_default_explicit.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_non_intrusive_with_default_explicit.output deleted file mode 100644 index 1a255f6..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_non_intrusive_with_default_explicit.output +++ /dev/null @@ -1,2 +0,0 @@ -serialization: {"address":"744 Evergreen Terrace","age":60,"name":"Ned Flanders"} -roundtrip: {"address":"742 Evergreen Terrace","age":-1,"name":"Maggie Simpson"} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_non_intrusive_with_default_macro.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_non_intrusive_with_default_macro.cpp deleted file mode 100644 index aa9bc53..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_non_intrusive_with_default_macro.cpp +++ /dev/null @@ -1,40 +0,0 @@ -#include -#include - -using json = nlohmann::json; -using namespace nlohmann::literals; - -namespace ns -{ -struct person -{ - std::string name = "John Doe"; - std::string address = "123 Fake St"; - int age = -1; - - person() = default; - person(std::string name_, std::string address_, int age_) - : name(std::move(name_)), address(std::move(address_)), age(age_) - {} -}; - -NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE_WITH_DEFAULT(person, name, address, age) -} // namespace ns - -int main() -{ - ns::person p = {"Ned Flanders", "744 Evergreen Terrace", 60}; - - // serialization: person -> json - json j = p; - std::cout << "serialization: " << j << std::endl; - - // deserialization: json -> person - json j2 = R"({"address": "742 Evergreen Terrace", "age": 40, "name": "Homer Simpson"})"_json; - auto p2 = j2.get(); - - // incomplete deserialization: - json j3 = R"({"address": "742 Evergreen Terrace", "name": "Maggie Simpson"})"_json; - auto p3 = j3.get(); - std::cout << "roundtrip: " << json(p3) << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_non_intrusive_with_default_macro.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_non_intrusive_with_default_macro.output deleted file mode 100644 index 1a255f6..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_define_type_non_intrusive_with_default_macro.output +++ /dev/null @@ -1,2 +0,0 @@ -serialization: {"address":"744 Evergreen Terrace","age":60,"name":"Ned Flanders"} -roundtrip: {"address":"742 Evergreen Terrace","age":-1,"name":"Maggie Simpson"} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_namespace.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_namespace.cpp deleted file mode 100644 index 4bad91f..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_namespace.cpp +++ /dev/null @@ -1,14 +0,0 @@ -#include -#include - -// possible use case: use NLOHMANN_JSON_NAMESPACE instead of nlohmann -using json = NLOHMANN_JSON_NAMESPACE::json; - -// macro needed to output the NLOHMANN_JSON_NAMESPACE as string literal -#define Q(x) #x -#define QUOTE(x) Q(x) - -int main() -{ - std::cout << QUOTE(NLOHMANN_JSON_NAMESPACE) << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_namespace.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_namespace.output deleted file mode 100644 index 1a1df5a..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_namespace.output +++ /dev/null @@ -1 +0,0 @@ -nlohmann::json_abi_v3_11_2 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_namespace_begin.c++17.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_namespace_begin.c++17.cpp deleted file mode 100644 index 9385d59..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_namespace_begin.c++17.cpp +++ /dev/null @@ -1,33 +0,0 @@ -#include -#include -#include - -// partial specialization (see https://json.nlohmann.me/features/arbitrary_types/) -NLOHMANN_JSON_NAMESPACE_BEGIN -template -struct adl_serializer> -{ - static void to_json(json& j, const std::optional& opt) - { - if (opt == std::nullopt) - { - j = nullptr; - } - else - { - j = *opt; - } - } -}; -NLOHMANN_JSON_NAMESPACE_END - -int main() -{ - std::optional o1 = 1; - std::optional o2 = std::nullopt; - - NLOHMANN_JSON_NAMESPACE::json j; - j.push_back(o1); - j.push_back(o2); - std::cout << j << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_namespace_begin.c++17.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_namespace_begin.c++17.output deleted file mode 100644 index b29d3b9..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_namespace_begin.c++17.output +++ /dev/null @@ -1 +0,0 @@ -[1,null] diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_namespace_no_version.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_namespace_no_version.cpp deleted file mode 100644 index 97948dd..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_namespace_no_version.cpp +++ /dev/null @@ -1,13 +0,0 @@ -#include - -#define NLOHMANN_JSON_NAMESPACE_NO_VERSION 1 -#include - -// macro needed to output the NLOHMANN_JSON_NAMESPACE as string literal -#define Q(x) #x -#define QUOTE(x) Q(x) - -int main() -{ - std::cout << QUOTE(NLOHMANN_JSON_NAMESPACE) << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_namespace_no_version.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_namespace_no_version.output deleted file mode 100644 index 1c8f313..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_namespace_no_version.output +++ /dev/null @@ -1 +0,0 @@ -nlohmann::json_abi diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_serialize_enum.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_serialize_enum.cpp deleted file mode 100644 index f9e472c..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_serialize_enum.cpp +++ /dev/null @@ -1,59 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -namespace ns -{ -enum TaskState -{ - TS_STOPPED, - TS_RUNNING, - TS_COMPLETED, - TS_INVALID = -1 -}; - -NLOHMANN_JSON_SERIALIZE_ENUM(TaskState, -{ - { TS_INVALID, nullptr }, - { TS_STOPPED, "stopped" }, - { TS_RUNNING, "running" }, - { TS_COMPLETED, "completed" } -}) - -enum class Color -{ - red, green, blue, unknown -}; - -NLOHMANN_JSON_SERIALIZE_ENUM(Color, -{ - { Color::unknown, "unknown" }, { Color::red, "red" }, - { Color::green, "green" }, { Color::blue, "blue" } -}) -} // namespace ns - -int main() -{ - // serialization - json j_stopped = ns::TS_STOPPED; - json j_red = ns::Color::red; - std::cout << "ns::TS_STOPPED -> " << j_stopped - << ", ns::Color::red -> " << j_red << std::endl; - - // deserialization - json j_running = "running"; - json j_blue = "blue"; - auto running = j_running.get(); - auto blue = j_blue.get(); - std::cout << j_running << " -> " << running - << ", " << j_blue << " -> " << static_cast(blue) << std::endl; - - // deserializing undefined JSON value to enum - // (where the first map entry above is the default) - json j_pi = 3.14; - auto invalid = j_pi.get(); - auto unknown = j_pi.get(); - std::cout << j_pi << " -> " << invalid << ", " - << j_pi << " -> " << static_cast(unknown) << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_serialize_enum.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_serialize_enum.output deleted file mode 100644 index f512563..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_serialize_enum.output +++ /dev/null @@ -1,3 +0,0 @@ -ns::TS_STOPPED -> "stopped", ns::Color::red -> "red" -"running" -> 1, "blue" -> 2 -3.14 -> -1, 3.14 -> 3 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_serialize_enum_2.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_serialize_enum_2.cpp deleted file mode 100644 index fd27226..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_serialize_enum_2.cpp +++ /dev/null @@ -1,33 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -namespace ns -{ -enum class Color -{ - red, green, blue, unknown -}; - -NLOHMANN_JSON_SERIALIZE_ENUM(Color, -{ - { Color::unknown, "unknown" }, { Color::red, "red" }, - { Color::green, "green" }, { Color::blue, "blue" }, - { Color::red, "rot" } // a second conversion for Color::red -}) -} - -int main() -{ - // serialization - json j_red = ns::Color::red; - std::cout << static_cast(ns::Color::red) << " -> " << j_red << std::endl; - - // deserialization - json j_rot = "rot"; - auto rot = j_rot.get(); - auto red = j_red.get(); - std::cout << j_rot << " -> " << static_cast(rot) << std::endl; - std::cout << j_red << " -> " << static_cast(red) << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_serialize_enum_2.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_serialize_enum_2.output deleted file mode 100644 index 5dec31b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_serialize_enum_2.output +++ /dev/null @@ -1,3 +0,0 @@ -0 -> "red" -"rot" -> 0 -"red" -> 0 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_version.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_version.cpp deleted file mode 100644 index ca5f537..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_version.cpp +++ /dev/null @@ -1,12 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - std::cout << "JSON for Modern C++ version " - << NLOHMANN_JSON_VERSION_MAJOR << "." - << NLOHMANN_JSON_VERSION_MINOR << "." - << NLOHMANN_JSON_VERSION_PATCH << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_version.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_version.output deleted file mode 100644 index 043b9b2..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/nlohmann_json_version.output +++ /dev/null @@ -1 +0,0 @@ -JSON for Modern C++ version 3.11.2 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/number_float_t.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/number_float_t.cpp deleted file mode 100644 index 21211dc..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/number_float_t.cpp +++ /dev/null @@ -1,10 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - std::cout << std::boolalpha << std::is_same::value << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/number_float_t.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/number_float_t.output deleted file mode 100644 index 27ba77d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/number_float_t.output +++ /dev/null @@ -1 +0,0 @@ -true diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/number_integer_t.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/number_integer_t.cpp deleted file mode 100644 index 75ee57b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/number_integer_t.cpp +++ /dev/null @@ -1,10 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - std::cout << std::boolalpha << std::is_same::value << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/number_integer_t.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/number_integer_t.output deleted file mode 100644 index 27ba77d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/number_integer_t.output +++ /dev/null @@ -1 +0,0 @@ -true diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/number_unsigned_t.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/number_unsigned_t.cpp deleted file mode 100644 index ff3b86d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/number_unsigned_t.cpp +++ /dev/null @@ -1,10 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - std::cout << std::boolalpha << std::is_same::value << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/number_unsigned_t.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/number_unsigned_t.output deleted file mode 100644 index 27ba77d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/number_unsigned_t.output +++ /dev/null @@ -1 +0,0 @@ -true diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/object.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/object.cpp deleted file mode 100644 index 733b89b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/object.cpp +++ /dev/null @@ -1,28 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON objects - json j_no_init_list = json::object(); - json j_empty_init_list = json::object({}); - json j_list_of_pairs = json::object({ {"one", 1}, {"two", 2} }); - - // serialize the JSON objects - std::cout << j_no_init_list << '\n'; - std::cout << j_empty_init_list << '\n'; - std::cout << j_list_of_pairs << '\n'; - - // example for an exception - try - { - // can only create an object from a list of pairs - json j_invalid_object = json::object({{ "one", 1, 2 }}); - } - catch (json::type_error& e) - { - std::cout << e.what() << '\n'; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/object.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/object.output deleted file mode 100644 index 1a1d814..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/object.output +++ /dev/null @@ -1,4 +0,0 @@ -{} -{} -{"one":1,"two":2} -[json.exception.type_error.301] cannot create object from initializer list diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/object_comparator_t.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/object_comparator_t.cpp deleted file mode 100644 index 6b82c7c..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/object_comparator_t.cpp +++ /dev/null @@ -1,11 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - std::cout << std::boolalpha - << "json::object_comparator_t(\"one\", \"two\") = " << json::object_comparator_t{}("one", "two") << "\n" - << "json::object_comparator_t(\"three\", \"four\") = " << json::object_comparator_t{}("three", "four") << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/object_comparator_t.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/object_comparator_t.output deleted file mode 100644 index 63620ed..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/object_comparator_t.output +++ /dev/null @@ -1,2 +0,0 @@ -json::object_comparator_t("one", "two") = true -json::object_comparator_t("three", "four") = false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/object_t.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/object_t.cpp deleted file mode 100644 index 85cfa3e..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/object_t.cpp +++ /dev/null @@ -1,10 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - std::cout << std::boolalpha << std::is_same, json::object_t>::value << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/object_t.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/object_t.output deleted file mode 100644 index 27ba77d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/object_t.output +++ /dev/null @@ -1 +0,0 @@ -true diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__ValueType.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__ValueType.cpp deleted file mode 100644 index 66fcf31..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__ValueType.cpp +++ /dev/null @@ -1,60 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create a JSON value with different types - json json_types = - { - {"boolean", true}, - { - "number", { - {"integer", 42}, - {"floating-point", 17.23} - } - }, - {"string", "Hello, world!"}, - {"array", {1, 2, 3, 4, 5}}, - {"null", nullptr} - }; - - // use implicit conversions - bool v1 = json_types["boolean"]; - int v2 = json_types["number"]["integer"]; - short v3 = json_types["number"]["integer"]; - float v4 = json_types["number"]["floating-point"]; - int v5 = json_types["number"]["floating-point"]; - std::string v6 = json_types["string"]; - std::vector v7 = json_types["array"]; - std::unordered_map v8 = json_types; - - // print the conversion results - std::cout << v1 << '\n'; - std::cout << v2 << ' ' << v3 << '\n'; - std::cout << v4 << ' ' << v5 << '\n'; - std::cout << v6 << '\n'; - - for (auto i : v7) - { - std::cout << i << ' '; - } - std::cout << "\n\n"; - - for (auto i : v8) - { - std::cout << i.first << ": " << i.second << '\n'; - } - - // example for an exception - try - { - bool v1 = json_types["string"]; - } - catch (json::type_error& e) - { - std::cout << e.what() << '\n'; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__ValueType.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__ValueType.output deleted file mode 100644 index a3bd9ff..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__ValueType.output +++ /dev/null @@ -1,12 +0,0 @@ -1 -42 42 -17.23 17 -Hello, world! -1 2 3 4 5 - -string: "Hello, world!" -number: {"floating-point":17.23,"integer":42} -null: null -boolean: true -array: [1,2,3,4,5] -[json.exception.type_error.302] type must be boolean, but is string diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__equal.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__equal.cpp deleted file mode 100644 index 1426f48..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__equal.cpp +++ /dev/null @@ -1,24 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create several JSON values - json array_1 = {1, 2, 3}; - json array_2 = {1, 2, 4}; - json object_1 = {{"A", "a"}, {"B", "b"}}; - json object_2 = {{"B", "b"}, {"A", "a"}}; - json number_1 = 17; - json number_2 = 17.000000000000001L; - json string_1 = "foo"; - json string_2 = "bar"; - - // output values and comparisons - std::cout << std::boolalpha; - std::cout << array_1 << " == " << array_2 << " " << (array_1 == array_2) << '\n'; - std::cout << object_1 << " == " << object_2 << " " << (object_1 == object_2) << '\n'; - std::cout << number_1 << " == " << number_2 << " " << (number_1 == number_2) << '\n'; - std::cout << string_1 << " == " << string_2 << " " << (string_1 == string_2) << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__equal.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__equal.output deleted file mode 100644 index 7806735..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__equal.output +++ /dev/null @@ -1,4 +0,0 @@ -[1,2,3] == [1,2,4] false -{"A":"a","B":"b"} == {"A":"a","B":"b"} true -17 == 17.0 true -"foo" == "bar" false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__equal__nullptr_t.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__equal__nullptr_t.cpp deleted file mode 100644 index dbb2103..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__equal__nullptr_t.cpp +++ /dev/null @@ -1,22 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create several JSON values - json array = {1, 2, 3}; - json object = {{"A", "a"}, {"B", "b"}}; - json number = 17; - json string = "foo"; - json null; - - // output values and comparisons - std::cout << std::boolalpha; - std::cout << array << " == nullptr " << (array == nullptr) << '\n'; - std::cout << object << " == nullptr " << (object == nullptr) << '\n'; - std::cout << number << " == nullptr " << (number == nullptr) << '\n'; - std::cout << string << " == nullptr " << (string == nullptr) << '\n'; - std::cout << null << " == nullptr " << (null == nullptr) << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__equal__nullptr_t.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__equal__nullptr_t.output deleted file mode 100644 index b7128e1..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__equal__nullptr_t.output +++ /dev/null @@ -1,5 +0,0 @@ -[1,2,3] == nullptr false -{"A":"a","B":"b"} == nullptr false -17 == nullptr false -"foo" == nullptr false -null == nullptr true diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__equal__specializations.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__equal__specializations.cpp deleted file mode 100644 index 97d5ece..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__equal__specializations.cpp +++ /dev/null @@ -1,16 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - nlohmann::json uj1 = {{"version", 1}, {"type", "integer"}}; - nlohmann::json uj2 = {{"type", "integer"}, {"version", 1}}; - - nlohmann::ordered_json oj1 = {{"version", 1}, {"type", "integer"}}; - nlohmann::ordered_json oj2 = {{"type", "integer"}, {"version", 1}}; - - std::cout << std::boolalpha << (uj1 == uj2) << '\n' << (oj1 == oj2) << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__equal__specializations.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__equal__specializations.output deleted file mode 100644 index da29283..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__equal__specializations.output +++ /dev/null @@ -1,2 +0,0 @@ -true -false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__greater.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__greater.cpp deleted file mode 100644 index 65bb9c0..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__greater.cpp +++ /dev/null @@ -1,24 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create several JSON values - json array_1 = {1, 2, 3}; - json array_2 = {1, 2, 4}; - json object_1 = {{"A", "a"}, {"B", "b"}}; - json object_2 = {{"B", "b"}, {"A", "a"}}; - json number_1 = 17; - json number_2 = 17.0000000000001L; - json string_1 = "foo"; - json string_2 = "bar"; - - // output values and comparisons - std::cout << std::boolalpha; - std::cout << array_1 << " > " << array_2 << " " << (array_1 > array_2) << '\n'; - std::cout << object_1 << " > " << object_2 << " " << (object_1 > object_2) << '\n'; - std::cout << number_1 << " > " << number_2 << " " << (number_1 > number_2) << '\n'; - std::cout << string_1 << " > " << string_2 << " " << (string_1 > string_2) << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__greater.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__greater.output deleted file mode 100644 index 910c48e..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__greater.output +++ /dev/null @@ -1,4 +0,0 @@ -[1,2,3] > [1,2,4] false -{"A":"a","B":"b"} > {"A":"a","B":"b"} false -17 > 17.0000000000001 false -"foo" > "bar" true diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__greaterequal.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__greaterequal.cpp deleted file mode 100644 index f8659ee..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__greaterequal.cpp +++ /dev/null @@ -1,24 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create several JSON values - json array_1 = {1, 2, 3}; - json array_2 = {1, 2, 4}; - json object_1 = {{"A", "a"}, {"B", "b"}}; - json object_2 = {{"B", "b"}, {"A", "a"}}; - json number_1 = 17; - json number_2 = 17.0000000000001L; - json string_1 = "foo"; - json string_2 = "bar"; - - // output values and comparisons - std::cout << std::boolalpha; - std::cout << array_1 << " >= " << array_2 << " " << (array_1 >= array_2) << '\n'; - std::cout << object_1 << " >= " << object_2 << " " << (object_1 >= object_2) << '\n'; - std::cout << number_1 << " >= " << number_2 << " " << (number_1 >= number_2) << '\n'; - std::cout << string_1 << " >= " << string_2 << " " << (string_1 >= string_2) << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__greaterequal.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__greaterequal.output deleted file mode 100644 index c7b9151..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__greaterequal.output +++ /dev/null @@ -1,4 +0,0 @@ -[1,2,3] >= [1,2,4] false -{"A":"a","B":"b"} >= {"A":"a","B":"b"} true -17 >= 17.0000000000001 false -"foo" >= "bar" true diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__less.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__less.cpp deleted file mode 100644 index 64209a2..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__less.cpp +++ /dev/null @@ -1,24 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create several JSON values - json array_1 = {1, 2, 3}; - json array_2 = {1, 2, 4}; - json object_1 = {{"A", "a"}, {"B", "b"}}; - json object_2 = {{"B", "b"}, {"A", "a"}}; - json number_1 = 17; - json number_2 = 17.0000000000001L; - json string_1 = "foo"; - json string_2 = "bar"; - - // output values and comparisons - std::cout << std::boolalpha; - std::cout << array_1 << " == " << array_2 << " " << (array_1 < array_2) << '\n'; - std::cout << object_1 << " == " << object_2 << " " << (object_1 < object_2) << '\n'; - std::cout << number_1 << " == " << number_2 << " " << (number_1 < number_2) << '\n'; - std::cout << string_1 << " == " << string_2 << " " << (string_1 < string_2) << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__less.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__less.output deleted file mode 100644 index abbbc45..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__less.output +++ /dev/null @@ -1,4 +0,0 @@ -[1,2,3] == [1,2,4] true -{"A":"a","B":"b"} == {"A":"a","B":"b"} false -17 == 17.0000000000001 true -"foo" == "bar" false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__lessequal.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__lessequal.cpp deleted file mode 100644 index 543b954..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__lessequal.cpp +++ /dev/null @@ -1,24 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create several JSON values - json array_1 = {1, 2, 3}; - json array_2 = {1, 2, 4}; - json object_1 = {{"A", "a"}, {"B", "b"}}; - json object_2 = {{"B", "b"}, {"A", "a"}}; - json number_1 = 17; - json number_2 = 17.0000000000001L; - json string_1 = "foo"; - json string_2 = "bar"; - - // output values and comparisons - std::cout << std::boolalpha; - std::cout << array_1 << " <= " << array_2 << " " << (array_1 <= array_2) << '\n'; - std::cout << object_1 << " <= " << object_2 << " " << (object_1 <= object_2) << '\n'; - std::cout << number_1 << " <= " << number_2 << " " << (number_1 <= number_2) << '\n'; - std::cout << string_1 << " <= " << string_2 << " " << (string_1 <= string_2) << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__lessequal.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__lessequal.output deleted file mode 100644 index f7f0327..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__lessequal.output +++ /dev/null @@ -1,4 +0,0 @@ -[1,2,3] <= [1,2,4] true -{"A":"a","B":"b"} <= {"A":"a","B":"b"} true -17 <= 17.0000000000001 true -"foo" <= "bar" false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__notequal.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__notequal.cpp deleted file mode 100644 index 43e8950..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__notequal.cpp +++ /dev/null @@ -1,24 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create several JSON values - json array_1 = {1, 2, 3}; - json array_2 = {1, 2, 4}; - json object_1 = {{"A", "a"}, {"B", "b"}}; - json object_2 = {{"B", "b"}, {"A", "a"}}; - json number_1 = 17; - json number_2 = 17.000000000000001L; - json string_1 = "foo"; - json string_2 = "bar"; - - // output values and comparisons - std::cout << std::boolalpha; - std::cout << array_1 << " != " << array_2 << " " << (array_1 != array_2) << '\n'; - std::cout << object_1 << " != " << object_2 << " " << (object_1 != object_2) << '\n'; - std::cout << number_1 << " != " << number_2 << " " << (number_1 != number_2) << '\n'; - std::cout << string_1 << " != " << string_2 << " " << (string_1 != string_2) << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__notequal.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__notequal.output deleted file mode 100644 index 6cbc0e8..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__notequal.output +++ /dev/null @@ -1,4 +0,0 @@ -[1,2,3] != [1,2,4] true -{"A":"a","B":"b"} != {"A":"a","B":"b"} false -17 != 17.0 false -"foo" != "bar" true diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__notequal__nullptr_t.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__notequal__nullptr_t.cpp deleted file mode 100644 index dc7e6ac..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__notequal__nullptr_t.cpp +++ /dev/null @@ -1,22 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create several JSON values - json array = {1, 2, 3}; - json object = {{"A", "a"}, {"B", "b"}}; - json number = 17; - json string = "foo"; - json null; - - // output values and comparisons - std::cout << std::boolalpha; - std::cout << array << " != nullptr " << (array != nullptr) << '\n'; - std::cout << object << " != nullptr " << (object != nullptr) << '\n'; - std::cout << number << " != nullptr " << (number != nullptr) << '\n'; - std::cout << string << " != nullptr " << (string != nullptr) << '\n'; - std::cout << null << " != nullptr " << (null != nullptr) << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__notequal__nullptr_t.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__notequal__nullptr_t.output deleted file mode 100644 index 0fc36dc..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__notequal__nullptr_t.output +++ /dev/null @@ -1,5 +0,0 @@ -[1,2,3] != nullptr true -{"A":"a","B":"b"} != nullptr true -17 != nullptr true -"foo" != nullptr true -null != nullptr false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__value_t.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__value_t.cpp deleted file mode 100644 index d9aac79..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__value_t.cpp +++ /dev/null @@ -1,38 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json j_null; - json j_boolean = true; - json j_number_integer = -17; - json j_number_unsigned = 42u; - json j_number_float = 23.42; - json j_object = {{"one", 1}, {"two", 2}}; - json j_array = {1, 2, 4, 8, 16}; - json j_string = "Hello, world"; - - // call operator value_t() - json::value_t t_null = j_null; - json::value_t t_boolean = j_boolean; - json::value_t t_number_integer = j_number_integer; - json::value_t t_number_unsigned = j_number_unsigned; - json::value_t t_number_float = j_number_float; - json::value_t t_object = j_object; - json::value_t t_array = j_array; - json::value_t t_string = j_string; - - // print types - std::cout << std::boolalpha; - std::cout << (t_null == json::value_t::null) << '\n'; - std::cout << (t_boolean == json::value_t::boolean) << '\n'; - std::cout << (t_number_integer == json::value_t::number_integer) << '\n'; - std::cout << (t_number_unsigned == json::value_t::number_unsigned) << '\n'; - std::cout << (t_number_float == json::value_t::number_float) << '\n'; - std::cout << (t_object == json::value_t::object) << '\n'; - std::cout << (t_array == json::value_t::array) << '\n'; - std::cout << (t_string == json::value_t::string) << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__value_t.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__value_t.output deleted file mode 100644 index 310e632..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator__value_t.output +++ /dev/null @@ -1,8 +0,0 @@ -true -true -true -true -true -true -true -true diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__json_pointer.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__json_pointer.cpp deleted file mode 100644 index 0fa207f..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__json_pointer.cpp +++ /dev/null @@ -1,49 +0,0 @@ -#include -#include - -using json = nlohmann::json; -using namespace nlohmann::literals; - -int main() -{ - // create a JSON value - json j = - { - {"number", 1}, {"string", "foo"}, {"array", {1, 2}} - }; - - // read-only access - - // output element with JSON pointer "/number" - std::cout << j["/number"_json_pointer] << '\n'; - // output element with JSON pointer "/string" - std::cout << j["/string"_json_pointer] << '\n'; - // output element with JSON pointer "/array" - std::cout << j["/array"_json_pointer] << '\n'; - // output element with JSON pointer "/array/1" - std::cout << j["/array/1"_json_pointer] << '\n'; - - // writing access - - // change the string - j["/string"_json_pointer] = "bar"; - // output the changed string - std::cout << j["string"] << '\n'; - - // "change" a nonexisting object entry - j["/boolean"_json_pointer] = true; - // output the changed object - std::cout << j << '\n'; - - // change an array element - j["/array/1"_json_pointer] = 21; - // "change" an array element with nonexisting index - j["/array/4"_json_pointer] = 44; - // output the changed array - std::cout << j["array"] << '\n'; - - // "change" the array element past the end - j["/array/-"_json_pointer] = 55; - // output the changed array - std::cout << j["array"] << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__json_pointer.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__json_pointer.output deleted file mode 100644 index 1fd1b03..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__json_pointer.output +++ /dev/null @@ -1,8 +0,0 @@ -1 -"foo" -[1,2] -2 -"bar" -{"array":[1,2],"boolean":true,"number":1,"string":"bar"} -[1,21,null,null,44] -[1,21,null,null,44,55] diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__json_pointer_const.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__json_pointer_const.cpp deleted file mode 100644 index f40e249..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__json_pointer_const.cpp +++ /dev/null @@ -1,25 +0,0 @@ -#include -#include - -using json = nlohmann::json; -using namespace nlohmann::literals; - -int main() -{ - // create a JSON value - const json j = - { - {"number", 1}, {"string", "foo"}, {"array", {1, 2}} - }; - - // read-only access - - // output element with JSON pointer "/number" - std::cout << j["/number"_json_pointer] << '\n'; - // output element with JSON pointer "/string" - std::cout << j["/string"_json_pointer] << '\n'; - // output element with JSON pointer "/array" - std::cout << j["/array"_json_pointer] << '\n'; - // output element with JSON pointer "/array/1" - std::cout << j["/array/1"_json_pointer] << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__json_pointer_const.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__json_pointer_const.output deleted file mode 100644 index 7b9306b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__json_pointer_const.output +++ /dev/null @@ -1,4 +0,0 @@ -1 -"foo" -[1,2] -2 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__keytype.c++17.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__keytype.c++17.cpp deleted file mode 100644 index 7f2b41d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__keytype.c++17.cpp +++ /dev/null @@ -1,34 +0,0 @@ -#include -#include -#include -#include - -using namespace std::string_view_literals; -using json = nlohmann::json; - -int main() -{ - // create a JSON object - json object = - { - {"one", 1}, {"two", 2}, {"three", 2.9} - }; - - // output element with key "two" - std::cout << object["two"sv] << "\n\n"; - - // change element with key "three" - object["three"sv] = 3; - - // output changed array - std::cout << std::setw(4) << object << "\n\n"; - - // mention nonexisting key - object["four"sv]; - - // write to nonexisting key - object["five"sv]["really"sv]["nested"sv] = true; - - // output changed object - std::cout << std::setw(4) << object << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__keytype.c++17.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__keytype.c++17.output deleted file mode 100644 index b643587..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__keytype.c++17.output +++ /dev/null @@ -1,19 +0,0 @@ -2 - -{ - "one": 1, - "three": 3, - "two": 2 -} - -{ - "five": { - "really": { - "nested": true - } - }, - "four": null, - "one": 1, - "three": 3, - "two": 2 -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__keytype_const.c++17.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__keytype_const.c++17.cpp deleted file mode 100644 index 2cf94f4..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__keytype_const.c++17.cpp +++ /dev/null @@ -1,18 +0,0 @@ -#include -#include -#include - -using namespace std::string_view_literals; -using json = nlohmann::json; - -int main() -{ - // create a JSON object - const json object = - { - {"one", 1}, {"two", 2}, {"three", 2.9} - }; - - // output element with key "two" - std::cout << object["two"sv] << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__keytype_const.c++17.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__keytype_const.c++17.output deleted file mode 100644 index 0cfbf08..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__keytype_const.c++17.output +++ /dev/null @@ -1 +0,0 @@ -2 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__object_t_key_type.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__object_t_key_type.cpp deleted file mode 100644 index f9b7f73..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__object_t_key_type.cpp +++ /dev/null @@ -1,32 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create a JSON object - json object = - { - {"one", 1}, {"two", 2}, {"three", 2.9} - }; - - // output element with key "two" - std::cout << object["two"] << "\n\n"; - - // change element with key "three" - object["three"] = 3; - - // output changed array - std::cout << std::setw(4) << object << "\n\n"; - - // mention nonexisting key - object["four"]; - - // write to nonexisting key - object["five"]["really"]["nested"] = true; - - // output changed object - std::cout << std::setw(4) << object << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__object_t_key_type.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__object_t_key_type.output deleted file mode 100644 index b643587..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__object_t_key_type.output +++ /dev/null @@ -1,19 +0,0 @@ -2 - -{ - "one": 1, - "three": 3, - "two": 2 -} - -{ - "five": { - "really": { - "nested": true - } - }, - "four": null, - "one": 1, - "three": 3, - "two": 2 -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__object_t_key_type_const.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__object_t_key_type_const.cpp deleted file mode 100644 index 1bdb340..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__object_t_key_type_const.cpp +++ /dev/null @@ -1,16 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create a JSON object - const json object = - { - {"one", 1}, {"two", 2}, {"three", 2.9} - }; - - // output element with key "two" - std::cout << object["two"] << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__object_t_key_type_const.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__object_t_key_type_const.output deleted file mode 100644 index 0cfbf08..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__object_t_key_type_const.output +++ /dev/null @@ -1 +0,0 @@ -2 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__size_type.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__size_type.cpp deleted file mode 100644 index d6f3e15..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__size_type.cpp +++ /dev/null @@ -1,25 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create a JSON array - json array = {1, 2, 3, 4, 5}; - - // output element at index 3 (fourth element) - std::cout << array[3] << '\n'; - - // change last element to 6 - array[array.size() - 1] = 6; - - // output changed array - std::cout << array << '\n'; - - // write beyond array limit - array[10] = 11; - - // output changed array - std::cout << array << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__size_type.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__size_type.output deleted file mode 100644 index a91a106..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__size_type.output +++ /dev/null @@ -1,3 +0,0 @@ -4 -[1,2,3,4,6] -[1,2,3,4,6,null,null,null,null,null,11] diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__size_type_const.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__size_type_const.cpp deleted file mode 100644 index d56fa0a..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__size_type_const.cpp +++ /dev/null @@ -1,13 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON array - const json array = {"first", "2nd", "third", "fourth"}; - - // output element at index 2 (third element) - std::cout << array.at(2) << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__size_type_const.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__size_type_const.output deleted file mode 100644 index 4450c9f..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_array__size_type_const.output +++ /dev/null @@ -1 +0,0 @@ -"third" diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_deserialize.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_deserialize.cpp deleted file mode 100644 index 8e3d8bd..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_deserialize.cpp +++ /dev/null @@ -1,26 +0,0 @@ -#include -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create stream with serialized JSON - std::stringstream ss; - ss << R"({ - "number": 23, - "string": "Hello, world!", - "array": [1, 2, 3, 4, 5], - "boolean": false, - "null": null - })"; - - // create JSON value and read the serialization from the stream - json j; - ss >> j; - - // serialize JSON - std::cout << std::setw(2) << j << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_deserialize.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_deserialize.output deleted file mode 100644 index 81a203f..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_deserialize.output +++ /dev/null @@ -1,13 +0,0 @@ -{ - "array": [ - 1, - 2, - 3, - 4, - 5 - ], - "boolean": false, - "null": null, - "number": 23, - "string": "Hello, world!" -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_literal_json.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_literal_json.cpp deleted file mode 100644 index 84ca629..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_literal_json.cpp +++ /dev/null @@ -1,13 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; -using namespace nlohmann::literals; - -int main() -{ - json j = R"( {"hello": "world", "answer": 42} )"_json; - - std::cout << std::setw(2) << j << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_literal_json.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_literal_json.output deleted file mode 100644 index 6c0a7b3..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_literal_json.output +++ /dev/null @@ -1,4 +0,0 @@ -{ - "answer": 42, - "hello": "world" -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_literal_json_pointer.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_literal_json_pointer.cpp deleted file mode 100644 index aba93e8..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_literal_json_pointer.cpp +++ /dev/null @@ -1,14 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; -using namespace nlohmann::literals; - -int main() -{ - json j = R"( {"hello": "world", "answer": 42} )"_json; - auto val = j["/hello"_json_pointer]; - - std::cout << std::setw(2) << val << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_literal_json_pointer.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_literal_json_pointer.output deleted file mode 100644 index b0fcd34..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_literal_json_pointer.output +++ /dev/null @@ -1 +0,0 @@ -"world" diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_ltlt__basic_json.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_ltlt__basic_json.cpp deleted file mode 100644 index 3bd4ad5..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_ltlt__basic_json.cpp +++ /dev/null @@ -1,21 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json j_object = {{"one", 1}, {"two", 2}}; - json j_array = {1, 2, 4, 8, 16}; - - // serialize without indentation - std::cout << j_object << "\n\n"; - std::cout << j_array << "\n\n"; - - // serialize with indentation - std::cout << std::setw(4) << j_object << "\n\n"; - std::cout << std::setw(2) << j_array << "\n\n"; - std::cout << std::setw(1) << std::setfill('\t') << j_object << "\n\n"; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_ltlt__basic_json.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_ltlt__basic_json.output deleted file mode 100644 index 7e86bfa..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_ltlt__basic_json.output +++ /dev/null @@ -1,22 +0,0 @@ -{"one":1,"two":2} - -[1,2,4,8,16] - -{ - "one": 1, - "two": 2 -} - -[ - 1, - 2, - 4, - 8, - 16 -] - -{ - "one": 1, - "two": 2 -} - diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_ltlt__json_pointer.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_ltlt__json_pointer.cpp deleted file mode 100644 index f4fac88..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_ltlt__json_pointer.cpp +++ /dev/null @@ -1,13 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON poiner - json::json_pointer ptr("/foo/bar/baz"); - - // write string representation to stream - std::cout << ptr << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_ltlt__json_pointer.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_ltlt__json_pointer.output deleted file mode 100644 index ed35943..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_ltlt__json_pointer.output +++ /dev/null @@ -1 +0,0 @@ -/foo/bar/baz diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_spaceship__const_reference.c++20.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_spaceship__const_reference.c++20.cpp deleted file mode 100644 index 3c6c8b8..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_spaceship__const_reference.c++20.cpp +++ /dev/null @@ -1,41 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -const char* to_string(const std::partial_ordering& po) -{ - if (std::is_lt(po)) - { - return "less"; - } - else if (std::is_gt(po)) - { - return "greater"; - } - else if (std::is_eq(po)) - { - return "equivalent"; - } - return "unordered"; -} - -int main() -{ - // create several JSON values - json array_1 = {1, 2, 3}; - json array_2 = {1, 2, 4}; - json object_1 = {{"A", "a"}, {"B", "b"}}; - json object_2 = {{"B", "b"}, {"A", "a"}}; - json number = 17; - json string = "foo"; - json discarded = json(json::value_t::discarded); - - - // output values and comparisons - std::cout << array_1 << " <=> " << array_2 << " := " << to_string(array_1 <=> array_2) << '\n'; // *NOPAD* - std::cout << object_1 << " <=> " << object_2 << " := " << to_string(object_1 <=> object_2) << '\n'; // *NOPAD* - std::cout << string << " <=> " << number << " := " << to_string(string <=> number) << '\n'; // *NOPAD* - std::cout << string << " <=> " << discarded << " := " << to_string(string <=> discarded) << '\n'; // *NOPAD* -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_spaceship__const_reference.c++20.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_spaceship__const_reference.c++20.output deleted file mode 100644 index 2e8bf9f..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_spaceship__const_reference.c++20.output +++ /dev/null @@ -1,4 +0,0 @@ -[1,2,3] <=> [1,2,4] := less -{"A":"a","B":"b"} <=> {"A":"a","B":"b"} := equivalent -"foo" <=> 17 := greater -"foo" <=> := unordered diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_spaceship__scalartype.c++20.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_spaceship__scalartype.c++20.cpp deleted file mode 100644 index d9dc3ca..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_spaceship__scalartype.c++20.cpp +++ /dev/null @@ -1,41 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -const char* to_string(const std::partial_ordering& po) -{ - if (std::is_lt(po)) - { - return "less"; - } - else if (std::is_gt(po)) - { - return "greater"; - } - else if (std::is_eq(po)) - { - return "equivalent"; - } - return "unordered"; -} - -int main() -{ - using float_limits = std::numeric_limits; - constexpr auto nan = float_limits::quiet_NaN(); - - // create several JSON values - json boolean = false; - json number = 17; - json string = "17"; - - - // output values and comparisons - std::cout << std::boolalpha << std::fixed; - std::cout << boolean << " <=> " << true << " := " << to_string(boolean <=> true) << '\n'; // *NOPAD* - std::cout << number << " <=> " << 17.0 << " := " << to_string(number <=> 17.0) << '\n'; // *NOPAD* - std::cout << number << " <=> " << nan << " := " << to_string(number <=> nan) << '\n'; // *NOPAD* - std::cout << string << " <=> " << 17 << " := " << to_string(string <=> 17) << '\n'; // *NOPAD* -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_spaceship__scalartype.c++20.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_spaceship__scalartype.c++20.output deleted file mode 100644 index b2939a5..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/operator_spaceship__scalartype.c++20.output +++ /dev/null @@ -1,4 +0,0 @@ -false <=> true := less -17 <=> 17.000000 := equivalent -17 <=> nan := unordered -"17" <=> 17 := greater diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/ordered_json.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/ordered_json.cpp deleted file mode 100644 index effad53..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/ordered_json.cpp +++ /dev/null @@ -1,14 +0,0 @@ -#include -#include - -using ordered_json = nlohmann::ordered_json; - -int main() -{ - ordered_json j; - j["one"] = 1; - j["two"] = 2; - j["three"] = 3; - - std::cout << j.dump(2) << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/ordered_json.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/ordered_json.output deleted file mode 100644 index 120cbb2..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/ordered_json.output +++ /dev/null @@ -1,5 +0,0 @@ -{ - "one": 1, - "two": 2, - "three": 3 -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/ordered_map.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/ordered_map.cpp deleted file mode 100644 index dcc60cb..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/ordered_map.cpp +++ /dev/null @@ -1,43 +0,0 @@ -#include -#include - -// simple output function -template -void output(const char* prefix, const Map& m) -{ - std::cout << prefix << " = { "; - for (auto& element : m) - { - std::cout << element.first << ":" << element.second << ' '; - } - std::cout << "}" << std::endl; -} - -int main() -{ - // create and fill two maps - nlohmann::ordered_map m_ordered; - m_ordered["one"] = "eins"; - m_ordered["two"] = "zwei"; - m_ordered["three"] = "drei"; - - std::map m_std; - m_std["one"] = "eins"; - m_std["two"] = "zwei"; - m_std["three"] = "drei"; - - // output: m_ordered is ordered by insertion order, m_std is ordered by key - output("m_ordered", m_ordered); - output("m_std", m_std); - - // erase and re-add "one" key - m_ordered.erase("one"); - m_ordered["one"] = "eins"; - - m_std.erase("one"); - m_std["one"] = "eins"; - - // output: m_ordered shows newly added key at the end; m_std is again ordered by key - output("m_ordered", m_ordered); - output("m_std", m_std); -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/ordered_map.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/ordered_map.output deleted file mode 100644 index a4ffc45..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/ordered_map.output +++ /dev/null @@ -1,4 +0,0 @@ -m_ordered = { one:eins two:zwei three:drei } -m_std = { one:eins three:drei two:zwei } -m_ordered = { two:zwei three:drei one:eins } -m_std = { one:eins three:drei two:zwei } diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/other_error.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/other_error.cpp deleted file mode 100644 index 99c4be7..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/other_error.cpp +++ /dev/null @@ -1,30 +0,0 @@ -#include -#include - -using json = nlohmann::json; -using namespace nlohmann::literals; - -int main() -{ - try - { - // executing a failing JSON Patch operation - json value = R"({ - "best_biscuit": { - "name": "Oreo" - } - })"_json; - json patch = R"([{ - "op": "test", - "path": "/best_biscuit/name", - "value": "Choco Leibniz" - }])"_json; - value.patch(patch); - } - catch (json::other_error& e) - { - // output exception information - std::cout << "message: " << e.what() << '\n' - << "exception id: " << e.id << std::endl; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/other_error.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/other_error.output deleted file mode 100644 index b80f1cb..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/other_error.output +++ /dev/null @@ -1,2 +0,0 @@ -message: [json.exception.other_error.501] unsuccessful: {"op":"test","path":"/best_biscuit/name","value":"Choco Leibniz"} -exception id: 501 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/out_of_range.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/out_of_range.cpp deleted file mode 100644 index e711640..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/out_of_range.cpp +++ /dev/null @@ -1,20 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - try - { - // calling at() for an invalid index - json j = {1, 2, 3, 4}; - j.at(4) = 10; - } - catch (json::out_of_range& e) - { - // output exception information - std::cout << "message: " << e.what() << '\n' - << "exception id: " << e.id << std::endl; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/out_of_range.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/out_of_range.output deleted file mode 100644 index 29ec76b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/out_of_range.output +++ /dev/null @@ -1,2 +0,0 @@ -message: [json.exception.out_of_range.401] array index 4 is out of range -exception id: 401 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__allow_exceptions.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__allow_exceptions.cpp deleted file mode 100644 index 82449a5..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__allow_exceptions.cpp +++ /dev/null @@ -1,36 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // an invalid JSON text - std::string text = R"( - { - "key": "value without closing quotes - } - )"; - - // parse with exceptions - try - { - json j = json::parse(text); - } - catch (json::parse_error& e) - { - std::cout << e.what() << std::endl; - } - - // parse without exceptions - json j = json::parse(text, nullptr, false); - - if (j.is_discarded()) - { - std::cout << "the input is invalid JSON" << std::endl; - } - else - { - std::cout << "the input is valid JSON: " << j << std::endl; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__allow_exceptions.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__allow_exceptions.output deleted file mode 100644 index d650824..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__allow_exceptions.output +++ /dev/null @@ -1,2 +0,0 @@ -[json.exception.parse_error.101] parse error at line 4, column 0: syntax error while parsing value - invalid string: control character U+000A (LF) must be escaped to \u000A or \n; last read: '"value without closing quotes' -the input is invalid JSON diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__array__parser_callback_t.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__array__parser_callback_t.cpp deleted file mode 100644 index 63f0a0e..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__array__parser_callback_t.cpp +++ /dev/null @@ -1,30 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - // a JSON text - char text[] = R"( - { - "Image": { - "Width": 800, - "Height": 600, - "Title": "View from 15th Floor", - "Thumbnail": { - "Url": "http://www.example.com/image/481989943", - "Height": 125, - "Width": 100 - }, - "Animated" : false, - "IDs": [116, 943, 234, 38793] - } - } - )"; - - // parse and serialize JSON - json j_complete = json::parse(text); - std::cout << std::setw(4) << j_complete << "\n\n"; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__array__parser_callback_t.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__array__parser_callback_t.output deleted file mode 100644 index 62bb858..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__array__parser_callback_t.output +++ /dev/null @@ -1,20 +0,0 @@ -{ - "Image": { - "Animated": false, - "Height": 600, - "IDs": [ - 116, - 943, - 234, - 38793 - ], - "Thumbnail": { - "Height": 125, - "Url": "http://www.example.com/image/481989943", - "Width": 100 - }, - "Title": "View from 15th Floor", - "Width": 800 - } -} - diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__contiguouscontainer__parser_callback_t.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__contiguouscontainer__parser_callback_t.cpp deleted file mode 100644 index 6eb409b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__contiguouscontainer__parser_callback_t.cpp +++ /dev/null @@ -1,15 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - // a JSON text given as std::vector - std::vector text = {'[', '1', ',', '2', ',', '3', ']', '\0'}; - - // parse and serialize JSON - json j_complete = json::parse(text); - std::cout << std::setw(4) << j_complete << "\n\n"; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__contiguouscontainer__parser_callback_t.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__contiguouscontainer__parser_callback_t.output deleted file mode 100644 index 74633e8..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__contiguouscontainer__parser_callback_t.output +++ /dev/null @@ -1,6 +0,0 @@ -[ - 1, - 2, - 3 -] - diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__istream__parser_callback_t.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__istream__parser_callback_t.cpp deleted file mode 100644 index afcaa39..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__istream__parser_callback_t.cpp +++ /dev/null @@ -1,58 +0,0 @@ -#include -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - // a JSON text - auto text = R"( - { - "Image": { - "Width": 800, - "Height": 600, - "Title": "View from 15th Floor", - "Thumbnail": { - "Url": "http://www.example.com/image/481989943", - "Height": 125, - "Width": 100 - }, - "Animated" : false, - "IDs": [116, 943, 234, 38793] - } - } - )"; - - // fill a stream with JSON text - std::stringstream ss; - ss << text; - - // parse and serialize JSON - json j_complete = json::parse(ss); - std::cout << std::setw(4) << j_complete << "\n\n"; - - - // define parser callback - json::parser_callback_t cb = [](int depth, json::parse_event_t event, json & parsed) - { - // skip object elements with key "Thumbnail" - if (event == json::parse_event_t::key and parsed == json("Thumbnail")) - { - return false; - } - else - { - return true; - } - }; - - // fill a stream with JSON text - ss.clear(); - ss << text; - - // parse (with callback) and serialize JSON - json j_filtered = json::parse(ss, cb); - std::cout << std::setw(4) << j_filtered << '\n'; -} \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__istream__parser_callback_t.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__istream__parser_callback_t.output deleted file mode 100644 index 279a7ff..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__istream__parser_callback_t.output +++ /dev/null @@ -1,34 +0,0 @@ -{ - "Image": { - "Animated": false, - "Height": 600, - "IDs": [ - 116, - 943, - 234, - 38793 - ], - "Thumbnail": { - "Height": 125, - "Url": "http://www.example.com/image/481989943", - "Width": 100 - }, - "Title": "View from 15th Floor", - "Width": 800 - } -} - -{ - "Image": { - "Animated": false, - "Height": 600, - "IDs": [ - 116, - 943, - 234, - 38793 - ], - "Title": "View from 15th Floor", - "Width": 800 - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__iterator_pair.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__iterator_pair.cpp deleted file mode 100644 index d0c30c1..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__iterator_pair.cpp +++ /dev/null @@ -1,15 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - // a JSON text given an input with other values - std::vector input = {'[', '1', ',', '2', ',', '3', ']', 'o', 't', 'h', 'e', 'r'}; - - // parse and serialize JSON - json j_complete = json::parse(input.begin(), input.begin() + 7); - std::cout << std::setw(4) << j_complete << "\n\n"; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__iterator_pair.link b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__iterator_pair.link deleted file mode 100644 index f464e54..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__iterator_pair.link +++ /dev/null @@ -1 +0,0 @@ -online \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__iterator_pair.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__iterator_pair.output deleted file mode 100644 index 74633e8..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__iterator_pair.output +++ /dev/null @@ -1,6 +0,0 @@ -[ - 1, - 2, - 3 -] - diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__pointers.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__pointers.cpp deleted file mode 100644 index a5a16ee..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__pointers.cpp +++ /dev/null @@ -1,15 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - // a JSON text given as string that is not null-terminated - const char* ptr = "[1,2,3]another value"; - - // parse and serialize JSON - json j_complete = json::parse(ptr, ptr + 7); - std::cout << std::setw(4) << j_complete << "\n\n"; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__pointers.link b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__pointers.link deleted file mode 100644 index 9a93ef1..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__pointers.link +++ /dev/null @@ -1 +0,0 @@ -online \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__pointers.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__pointers.output deleted file mode 100644 index 74633e8..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__pointers.output +++ /dev/null @@ -1,6 +0,0 @@ -[ - 1, - 2, - 3 -] - diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__string__parser_callback_t.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__string__parser_callback_t.cpp deleted file mode 100644 index 2ae4410..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__string__parser_callback_t.cpp +++ /dev/null @@ -1,49 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - // a JSON text - auto text = R"( - { - "Image": { - "Width": 800, - "Height": 600, - "Title": "View from 15th Floor", - "Thumbnail": { - "Url": "http://www.example.com/image/481989943", - "Height": 125, - "Width": 100 - }, - "Animated" : false, - "IDs": [116, 943, 234, 38793] - } - } - )"; - - // parse and serialize JSON - json j_complete = json::parse(text); - std::cout << std::setw(4) << j_complete << "\n\n"; - - - // define parser callback - json::parser_callback_t cb = [](int depth, json::parse_event_t event, json & parsed) - { - // skip object elements with key "Thumbnail" - if (event == json::parse_event_t::key and parsed == json("Thumbnail")) - { - return false; - } - else - { - return true; - } - }; - - // parse (with callback) and serialize JSON - json j_filtered = json::parse(text, cb); - std::cout << std::setw(4) << j_filtered << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__string__parser_callback_t.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__string__parser_callback_t.output deleted file mode 100644 index 279a7ff..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse__string__parser_callback_t.output +++ /dev/null @@ -1,34 +0,0 @@ -{ - "Image": { - "Animated": false, - "Height": 600, - "IDs": [ - 116, - 943, - 234, - 38793 - ], - "Thumbnail": { - "Height": 125, - "Url": "http://www.example.com/image/481989943", - "Width": 100 - }, - "Title": "View from 15th Floor", - "Width": 800 - } -} - -{ - "Image": { - "Animated": false, - "Height": 600, - "IDs": [ - 116, - 943, - 234, - 38793 - ], - "Title": "View from 15th Floor", - "Width": 800 - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse_error.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse_error.cpp deleted file mode 100644 index 9b27b58..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse_error.cpp +++ /dev/null @@ -1,20 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - try - { - // parsing input with a syntax error - json::parse("[1,2,3,]"); - } - catch (json::parse_error& e) - { - // output exception information - std::cout << "message: " << e.what() << '\n' - << "exception id: " << e.id << '\n' - << "byte position of error: " << e.byte << std::endl; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse_error.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse_error.output deleted file mode 100644 index fe366ff..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/parse_error.output +++ /dev/null @@ -1,3 +0,0 @@ -message: [json.exception.parse_error.101] parse error at line 1, column 8: syntax error while parsing value - unexpected ']'; expected '[', '{', or a literal -exception id: 101 -byte position of error: 8 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/patch.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/patch.cpp deleted file mode 100644 index b7ecb8e..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/patch.cpp +++ /dev/null @@ -1,33 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; -using namespace nlohmann::literals; - -int main() -{ - // the original document - json doc = R"( - { - "baz": "qux", - "foo": "bar" - } - )"_json; - - // the patch - json patch = R"( - [ - { "op": "replace", "path": "/baz", "value": "boo" }, - { "op": "add", "path": "/hello", "value": ["world"] }, - { "op": "remove", "path": "/foo"} - ] - )"_json; - - // apply the patch - json patched_doc = doc.patch(patch); - - // output original and patched document - std::cout << std::setw(4) << doc << "\n\n" - << std::setw(4) << patched_doc << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/patch.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/patch.output deleted file mode 100644 index eb558fe..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/patch.output +++ /dev/null @@ -1,11 +0,0 @@ -{ - "baz": "qux", - "foo": "bar" -} - -{ - "baz": "boo", - "hello": [ - "world" - ] -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/patch_inplace.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/patch_inplace.cpp deleted file mode 100644 index 061708a..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/patch_inplace.cpp +++ /dev/null @@ -1,35 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; -using namespace nlohmann::literals; - -int main() -{ - // the original document - json doc = R"( - { - "baz": "qux", - "foo": "bar" - } - )"_json; - - // the patch - json patch = R"( - [ - { "op": "replace", "path": "/baz", "value": "boo" }, - { "op": "add", "path": "/hello", "value": ["world"] }, - { "op": "remove", "path": "/foo"} - ] - )"_json; - - // output original document - std::cout << "Before\n" << std::setw(4) << doc << std::endl; - - // apply the patch - doc.patch_inplace(patch); - - // output patched document - std::cout << "\nAfter\n" << std::setw(4) << doc << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/patch_inplace.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/patch_inplace.output deleted file mode 100644 index 9d31b8b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/patch_inplace.output +++ /dev/null @@ -1,13 +0,0 @@ -Before -{ - "baz": "qux", - "foo": "bar" -} - -After -{ - "baz": "boo", - "hello": [ - "world" - ] -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/push_back.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/push_back.cpp deleted file mode 100644 index bbddf4f..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/push_back.cpp +++ /dev/null @@ -1,25 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json array = {1, 2, 3, 4, 5}; - json null; - - // print values - std::cout << array << '\n'; - std::cout << null << '\n'; - - // add values - array.push_back(6); - array += 7; - null += "first"; - null += "second"; - - // print values - std::cout << array << '\n'; - std::cout << null << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/push_back.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/push_back.output deleted file mode 100644 index 3306b60..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/push_back.output +++ /dev/null @@ -1,4 +0,0 @@ -[1,2,3,4,5] -null -[1,2,3,4,5,6,7] -["first","second"] diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/push_back__initializer_list.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/push_back__initializer_list.cpp deleted file mode 100644 index e96645f..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/push_back__initializer_list.cpp +++ /dev/null @@ -1,27 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json object = {{"one", 1}, {"two", 2}}; - json null; - - // print values - std::cout << object << '\n'; - std::cout << null << '\n'; - - // add values: - object.push_back({"three", 3}); // object is extended - object += {"four", 4}; // object is extended - null.push_back({"five", 5}); // null is converted to array - - // print values - std::cout << object << '\n'; - std::cout << null << '\n'; - - // would throw: - //object.push_back({1, 2, 3}); -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/push_back__initializer_list.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/push_back__initializer_list.output deleted file mode 100644 index 668eb25..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/push_back__initializer_list.output +++ /dev/null @@ -1,4 +0,0 @@ -{"one":1,"two":2} -null -{"four":4,"one":1,"three":3,"two":2} -[["five",5]] diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/push_back__object_t__value.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/push_back__object_t__value.cpp deleted file mode 100644 index 5d694e9..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/push_back__object_t__value.cpp +++ /dev/null @@ -1,25 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json object = {{"one", 1}, {"two", 2}}; - json null; - - // print values - std::cout << object << '\n'; - std::cout << null << '\n'; - - // add values - object.push_back(json::object_t::value_type("three", 3)); - object += json::object_t::value_type("four", 4); - null += json::object_t::value_type("A", "a"); - null += json::object_t::value_type("B", "b"); - - // print values - std::cout << object << '\n'; - std::cout << null << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/push_back__object_t__value.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/push_back__object_t__value.output deleted file mode 100644 index b8a7d35..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/push_back__object_t__value.output +++ /dev/null @@ -1,4 +0,0 @@ -{"one":1,"two":2} -null -{"four":4,"one":1,"three":3,"two":2} -{"A":"a","B":"b"} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/rbegin.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/rbegin.cpp deleted file mode 100644 index 239f7a6..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/rbegin.cpp +++ /dev/null @@ -1,16 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create an array value - json array = {1, 2, 3, 4, 5}; - - // get an iterator to the reverse-beginning - json::reverse_iterator it = array.rbegin(); - - // serialize the element that the iterator points to - std::cout << *it << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/rbegin.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/rbegin.output deleted file mode 100644 index 7ed6ff8..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/rbegin.output +++ /dev/null @@ -1 +0,0 @@ -5 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/rend.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/rend.cpp deleted file mode 100644 index adadbbd..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/rend.cpp +++ /dev/null @@ -1,19 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create an array value - json array = {1, 2, 3, 4, 5}; - - // get an iterator to the reverse-end - json::reverse_iterator it = array.rend(); - - // increment the iterator to point to the first element - --it; - - // serialize the element that the iterator points to - std::cout << *it << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/rend.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/rend.output deleted file mode 100644 index d00491f..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/rend.output +++ /dev/null @@ -1 +0,0 @@ -1 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/sax_parse.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/sax_parse.cpp deleted file mode 100644 index 8602687..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/sax_parse.cpp +++ /dev/null @@ -1,131 +0,0 @@ -#include -#include -#include -#include - -using json = nlohmann::json; - -// a simple event consumer that collects string representations of the passed -// values; note inheriting from json::json_sax_t is not required, but can -// help not to forget a required function -class sax_event_consumer : public json::json_sax_t -{ - public: - std::vector events; - - bool null() override - { - events.push_back("null()"); - return true; - } - - bool boolean(bool val) override - { - events.push_back("boolean(val=" + std::string(val ? "true" : "false") + ")"); - return true; - } - - bool number_integer(number_integer_t val) override - { - events.push_back("number_integer(val=" + std::to_string(val) + ")"); - return true; - } - - bool number_unsigned(number_unsigned_t val) override - { - events.push_back("number_unsigned(val=" + std::to_string(val) + ")"); - return true; - } - - bool number_float(number_float_t val, const string_t& s) override - { - events.push_back("number_float(val=" + std::to_string(val) + ", s=" + s + ")"); - return true; - } - - bool string(string_t& val) override - { - events.push_back("string(val=" + val + ")"); - return true; - } - - bool start_object(std::size_t elements) override - { - events.push_back("start_object(elements=" + std::to_string(elements) + ")"); - return true; - } - - bool end_object() override - { - events.push_back("end_object()"); - return true; - } - - bool start_array(std::size_t elements) override - { - events.push_back("start_array(elements=" + std::to_string(elements) + ")"); - return true; - } - - bool end_array() override - { - events.push_back("end_array()"); - return true; - } - - bool key(string_t& val) override - { - events.push_back("key(val=" + val + ")"); - return true; - } - - bool binary(json::binary_t& val) override - { - events.push_back("binary(val=[...])"); - return true; - } - - bool parse_error(std::size_t position, const std::string& last_token, const json::exception& ex) override - { - events.push_back("parse_error(position=" + std::to_string(position) + ", last_token=" + last_token + ",\n ex=" + std::string(ex.what()) + ")"); - return false; - } -}; - -int main() -{ - // a JSON text - auto text = R"( - { - "Image": { - "Width": 800, - "Height": 600, - "Title": "View from 15th Floor", - "Thumbnail": { - "Url": "http://www.example.com/image/481989943", - "Height": 125, - "Width": 100 - }, - "Animated" : false, - "IDs": [116, 943, 234, -38793], - "DeletionDate": null, - "Distance": 12.723374634 - } - }] - )"; - - // create a SAX event consumer object - sax_event_consumer sec; - - // parse JSON - bool result = json::sax_parse(text, &sec); - - // output the recorded events - for (auto& event : sec.events) - { - std::cout << event << "\n"; - } - - // output the result of sax_parse - std::cout << "\nresult: " << std::boolalpha << result << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/sax_parse.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/sax_parse.output deleted file mode 100644 index dd2fc2f..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/sax_parse.output +++ /dev/null @@ -1,37 +0,0 @@ -start_object(elements=18446744073709551615) -key(val=Image) -start_object(elements=18446744073709551615) -key(val=Width) -number_unsigned(val=800) -key(val=Height) -number_unsigned(val=600) -key(val=Title) -string(val=View from 15th Floor) -key(val=Thumbnail) -start_object(elements=18446744073709551615) -key(val=Url) -string(val=http://www.example.com/image/481989943) -key(val=Height) -number_unsigned(val=125) -key(val=Width) -number_unsigned(val=100) -end_object() -key(val=Animated) -boolean(val=false) -key(val=IDs) -start_array(elements=18446744073709551615) -number_unsigned(val=116) -number_unsigned(val=943) -number_unsigned(val=234) -number_integer(val=-38793) -end_array() -key(val=DeletionDate) -null() -key(val=Distance) -number_float(val=12.723375, s=12.723374634) -end_object() -end_object() -parse_error(position=460, last_token=12.723374634 } }], - ex=[json.exception.parse_error.101] parse error at line 17, column 6: syntax error while parsing value - unexpected ']'; expected end of input) - -result: false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/sax_parse__binary.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/sax_parse__binary.cpp deleted file mode 100644 index 08bc85d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/sax_parse__binary.cpp +++ /dev/null @@ -1,114 +0,0 @@ -#include -#include -#include -#include - -using json = nlohmann::json; - -// a simple event consumer that collects string representations of the passed -// values; note inheriting from json::json_sax_t is not required, but can -// help not to forget a required function -class sax_event_consumer : public json::json_sax_t -{ - public: - std::vector events; - - bool null() override - { - events.push_back("null()"); - return true; - } - - bool boolean(bool val) override - { - events.push_back("boolean(val=" + std::string(val ? "true" : "false") + ")"); - return true; - } - - bool number_integer(number_integer_t val) override - { - events.push_back("number_integer(val=" + std::to_string(val) + ")"); - return true; - } - - bool number_unsigned(number_unsigned_t val) override - { - events.push_back("number_unsigned(val=" + std::to_string(val) + ")"); - return true; - } - - bool number_float(number_float_t val, const string_t& s) override - { - events.push_back("number_float(val=" + std::to_string(val) + ", s=" + s + ")"); - return true; - } - - bool string(string_t& val) override - { - events.push_back("string(val=" + val + ")"); - return true; - } - - bool start_object(std::size_t elements) override - { - events.push_back("start_object(elements=" + std::to_string(elements) + ")"); - return true; - } - - bool end_object() override - { - events.push_back("end_object()"); - return true; - } - - bool start_array(std::size_t elements) override - { - events.push_back("start_array(elements=" + std::to_string(elements) + ")"); - return true; - } - - bool end_array() override - { - events.push_back("end_array()"); - return true; - } - - bool key(string_t& val) override - { - events.push_back("key(val=" + val + ")"); - return true; - } - - bool binary(json::binary_t& val) override - { - events.push_back("binary(val=[...])"); - return true; - } - - bool parse_error(std::size_t position, const std::string& last_token, const json::exception& ex) override - { - events.push_back("parse_error(position=" + std::to_string(position) + ", last_token=" + last_token + ",\n ex=" + std::string(ex.what()) + ")"); - return false; - } -}; - -int main() -{ - // CBOR byte string - std::vector vec = {{0x44, 0xcA, 0xfe, 0xba, 0xbe}}; - - // create a SAX event consumer object - sax_event_consumer sec; - - // parse CBOR - bool result = json::sax_parse(vec, &sec, json::input_format_t::cbor); - - // output the recorded events - for (auto& event : sec.events) - { - std::cout << event << "\n"; - } - - // output the result of sax_parse - std::cout << "\nresult: " << std::boolalpha << result << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/sax_parse__binary.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/sax_parse__binary.output deleted file mode 100644 index f880896..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/sax_parse__binary.output +++ /dev/null @@ -1,3 +0,0 @@ -binary(val=[...]) - -result: true diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/size.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/size.cpp deleted file mode 100644 index 2375483..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/size.cpp +++ /dev/null @@ -1,29 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json j_null; - json j_boolean = true; - json j_number_integer = 17; - json j_number_float = 23.42; - json j_object = {{"one", 1}, {"two", 2}}; - json j_object_empty(json::value_t::object); - json j_array = {1, 2, 4, 8, 16}; - json j_array_empty(json::value_t::array); - json j_string = "Hello, world"; - - // call size() - std::cout << j_null.size() << '\n'; - std::cout << j_boolean.size() << '\n'; - std::cout << j_number_integer.size() << '\n'; - std::cout << j_number_float.size() << '\n'; - std::cout << j_object.size() << '\n'; - std::cout << j_object_empty.size() << '\n'; - std::cout << j_array.size() << '\n'; - std::cout << j_array_empty.size() << '\n'; - std::cout << j_string.size() << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/size.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/size.output deleted file mode 100644 index 3831387..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/size.output +++ /dev/null @@ -1,9 +0,0 @@ -0 -1 -1 -1 -2 -0 -5 -0 -1 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/std_hash.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/std_hash.cpp deleted file mode 100644 index 9721910..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/std_hash.cpp +++ /dev/null @@ -1,19 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; -using namespace nlohmann::literals; - -int main() -{ - std::cout << "hash(null) = " << std::hash {}(json(nullptr)) << '\n' - << "hash(false) = " << std::hash {}(json(false)) << '\n' - << "hash(0) = " << std::hash {}(json(0)) << '\n' - << "hash(0U) = " << std::hash {}(json(0U)) << '\n' - << "hash(\"\") = " << std::hash {}(json("")) << '\n' - << "hash({}) = " << std::hash {}(json::object()) << '\n' - << "hash([]) = " << std::hash {}(json::array()) << '\n' - << "hash({\"hello\": \"world\"}) = " << std::hash {}("{\"hello\": \"world\"}"_json) - << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/std_hash.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/std_hash.output deleted file mode 100644 index 521d2b4..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/std_hash.output +++ /dev/null @@ -1,8 +0,0 @@ -hash(null) = 2654435769 -hash(false) = 2654436030 -hash(0) = 2654436095 -hash(0U) = 2654436156 -hash("") = 6142509191626859748 -hash({}) = 2654435832 -hash([]) = 2654435899 -hash({"hello": "world"}) = 4469488738203676328 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/std_swap.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/std_swap.cpp deleted file mode 100644 index 36ab3ce..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/std_swap.cpp +++ /dev/null @@ -1,19 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json j1 = {{"one", 1}, {"two", 2}}; - json j2 = {1, 2, 4, 8, 16}; - - std::cout << "j1 = " << j1 << " | j2 = " << j2 << '\n'; - - // swap values - std::swap(j1, j2); - - std::cout << "j1 = " << j1 << " | j2 = " << j2 << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/std_swap.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/std_swap.output deleted file mode 100644 index 5ae6db7..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/std_swap.output +++ /dev/null @@ -1,2 +0,0 @@ -j1 = {"one":1,"two":2} | j2 = [1,2,4,8,16] -j1 = [1,2,4,8,16] | j2 = {"one":1,"two":2} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/string_t.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/string_t.cpp deleted file mode 100644 index 77a9ea4..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/string_t.cpp +++ /dev/null @@ -1,10 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - std::cout << std::boolalpha << std::is_same::value << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/string_t.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/string_t.output deleted file mode 100644 index 27ba77d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/string_t.output +++ /dev/null @@ -1 +0,0 @@ -true diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/swap__array_t.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/swap__array_t.cpp deleted file mode 100644 index 2119dd5..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/swap__array_t.cpp +++ /dev/null @@ -1,20 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create a JSON value - json value = {{"array", {1, 2, 3, 4}}}; - - // create an array_t - json::array_t array = {"Snap", "Crackle", "Pop"}; - - // swap the array stored in the JSON value - value["array"].swap(array); - - // output the values - std::cout << "value = " << value << '\n'; - std::cout << "array = " << array << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/swap__array_t.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/swap__array_t.output deleted file mode 100644 index 365302c..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/swap__array_t.output +++ /dev/null @@ -1,2 +0,0 @@ -value = {"array":["Snap","Crackle","Pop"]} -array = [1,2,3,4] diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/swap__binary_t.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/swap__binary_t.cpp deleted file mode 100644 index 4b8fc3d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/swap__binary_t.cpp +++ /dev/null @@ -1,20 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create a binary value - json value = json::binary({1, 2, 3}); - - // create a binary_t - json::binary_t binary = {{4, 5, 6}}; - - // swap the object stored in the JSON value - value.swap(binary); - - // output the values - std::cout << "value = " << value << '\n'; - std::cout << "binary = " << json(binary) << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/swap__binary_t.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/swap__binary_t.output deleted file mode 100644 index 68cd768..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/swap__binary_t.output +++ /dev/null @@ -1,2 +0,0 @@ -value = {"bytes":[4,5,6],"subtype":null} -binary = {"bytes":[1,2,3],"subtype":null} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/swap__object_t.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/swap__object_t.cpp deleted file mode 100644 index 301b558..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/swap__object_t.cpp +++ /dev/null @@ -1,20 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create a JSON value - json value = { {"translation", {{"one", "eins"}, {"two", "zwei"}}} }; - - // create an object_t - json::object_t object = {{"cow", "Kuh"}, {"dog", "Hund"}}; - - // swap the object stored in the JSON value - value["translation"].swap(object); - - // output the values - std::cout << "value = " << value << '\n'; - std::cout << "object = " << object << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/swap__object_t.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/swap__object_t.output deleted file mode 100644 index b5c9791..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/swap__object_t.output +++ /dev/null @@ -1,2 +0,0 @@ -value = {"translation":{"cow":"Kuh","dog":"Hund"}} -object = {"one":"eins","two":"zwei"} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/swap__reference.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/swap__reference.cpp deleted file mode 100644 index 34182ad..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/swap__reference.cpp +++ /dev/null @@ -1,18 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create two JSON values - json j1 = {1, 2, 3, 4, 5}; - json j2 = {{"pi", 3.141592653589793}, {"e", 2.718281828459045}}; - - // swap the values - j1.swap(j2); - - // output the values - std::cout << "j1 = " << j1 << '\n'; - std::cout << "j2 = " << j2 << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/swap__reference.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/swap__reference.output deleted file mode 100644 index 96b07b0..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/swap__reference.output +++ /dev/null @@ -1,2 +0,0 @@ -j1 = {"e":2.718281828459045,"pi":3.141592653589793} -j2 = [1,2,3,4,5] diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/swap__string_t.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/swap__string_t.cpp deleted file mode 100644 index b5d5831..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/swap__string_t.cpp +++ /dev/null @@ -1,20 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create a JSON value - json value = { "the good", "the bad", "the ugly" }; - - // create string_t - json::string_t string = "the fast"; - - // swap the object stored in the JSON value - value[1].swap(string); - - // output the values - std::cout << "value = " << value << '\n'; - std::cout << "string = " << string << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/swap__string_t.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/swap__string_t.output deleted file mode 100644 index ae2a097..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/swap__string_t.output +++ /dev/null @@ -1,2 +0,0 @@ -value = ["the good","the fast","the ugly"] -string = the bad diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_bjdata.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_bjdata.cpp deleted file mode 100644 index 9b7abac..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_bjdata.cpp +++ /dev/null @@ -1,64 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; -using namespace nlohmann::literals; - -// function to print BJData's diagnostic format -void print_byte(uint8_t byte) -{ - if (32 < byte and byte < 128) - { - std::cout << (char)byte; - } - else - { - std::cout << (int)byte; - } -} - -int main() -{ - // create a JSON value - json j = R"({"compact": true, "schema": false})"_json; - - // serialize it to BJData - std::vector v = json::to_bjdata(j); - - // print the vector content - for (auto& byte : v) - { - print_byte(byte); - } - std::cout << std::endl; - - // create an array of numbers - json array = {1, 2, 3, 4, 5, 6, 7, 8}; - - // serialize it to BJData using default representation - std::vector v_array = json::to_bjdata(array); - // serialize it to BJData using size optimization - std::vector v_array_size = json::to_bjdata(array, true); - // serialize it to BJData using type optimization - std::vector v_array_size_and_type = json::to_bjdata(array, true, true); - - // print the vector contents - for (auto& byte : v_array) - { - print_byte(byte); - } - std::cout << std::endl; - - for (auto& byte : v_array_size) - { - print_byte(byte); - } - std::cout << std::endl; - - for (auto& byte : v_array_size_and_type) - { - print_byte(byte); - } - std::cout << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_bjdata.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_bjdata.output deleted file mode 100644 index 087980c..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_bjdata.output +++ /dev/null @@ -1,4 +0,0 @@ -{i7compactTi6schemaF} -[i1i2i3i4i5i6i7i8] -[#i8i1i2i3i4i5i6i7i8 -[$i#i812345678 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_bson.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_bson.cpp deleted file mode 100644 index 3484b0b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_bson.cpp +++ /dev/null @@ -1,22 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; -using namespace nlohmann::literals; - -int main() -{ - // create a JSON value - json j = R"({"compact": true, "schema": 0})"_json; - - // serialize it to BSON - std::vector v = json::to_bson(j); - - // print the vector content - for (auto& byte : v) - { - std::cout << "0x" << std::hex << std::setw(2) << std::setfill('0') << (int)byte << " "; - } - std::cout << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_bson.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_bson.output deleted file mode 100644 index 379532a..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_bson.output +++ /dev/null @@ -1 +0,0 @@ -0x1b 0x00 0x00 0x00 0x08 0x63 0x6f 0x6d 0x70 0x61 0x63 0x74 0x00 0x01 0x10 0x73 0x63 0x68 0x65 0x6d 0x61 0x00 0x00 0x00 0x00 0x00 0x00 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_cbor.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_cbor.cpp deleted file mode 100644 index 3d5e041..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_cbor.cpp +++ /dev/null @@ -1,22 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; -using namespace nlohmann::literals; - -int main() -{ - // create a JSON value - json j = R"({"compact": true, "schema": 0})"_json; - - // serialize it to CBOR - std::vector v = json::to_cbor(j); - - // print the vector content - for (auto& byte : v) - { - std::cout << "0x" << std::hex << std::setw(2) << std::setfill('0') << (int)byte << " "; - } - std::cout << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_cbor.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_cbor.output deleted file mode 100644 index 02c9ada..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_cbor.output +++ /dev/null @@ -1 +0,0 @@ -0xa2 0x67 0x63 0x6f 0x6d 0x70 0x61 0x63 0x74 0xf5 0x66 0x73 0x63 0x68 0x65 0x6d 0x61 0x00 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_json.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_json.cpp deleted file mode 100644 index 1f82a4d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_json.cpp +++ /dev/null @@ -1,32 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -namespace ns -{ -// a simple struct to model a person -struct person -{ - std::string name; - std::string address; - int age; -}; -} // namespace ns - -namespace ns -{ -void to_json(json& j, const person& p) -{ - j = json{ {"name", p.name}, {"address", p.address}, {"age", p.age} }; -} -} // namespace ns - -int main() -{ - ns::person p = {"Ned Flanders", "744 Evergreen Terrace", 60}; - - json j = p; - - std::cout << j << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_json.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_json.output deleted file mode 100644 index e9c5bf3..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_json.output +++ /dev/null @@ -1 +0,0 @@ -{"address":"744 Evergreen Terrace","age":60,"name":"Ned Flanders"} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_msgpack.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_msgpack.cpp deleted file mode 100644 index b29ae8c..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_msgpack.cpp +++ /dev/null @@ -1,22 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; -using namespace nlohmann::literals; - -int main() -{ - // create a JSON value - json j = R"({"compact": true, "schema": 0})"_json; - - // serialize it to MessagePack - std::vector v = json::to_msgpack(j); - - // print the vector content - for (auto& byte : v) - { - std::cout << "0x" << std::hex << std::setw(2) << std::setfill('0') << (int)byte << " "; - } - std::cout << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_msgpack.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_msgpack.output deleted file mode 100644 index 4d6c40a..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_msgpack.output +++ /dev/null @@ -1 +0,0 @@ -0x82 0xa7 0x63 0x6f 0x6d 0x70 0x61 0x63 0x74 0xc3 0xa6 0x73 0x63 0x68 0x65 0x6d 0x61 0x00 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_string.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_string.cpp deleted file mode 100644 index ee44283..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_string.cpp +++ /dev/null @@ -1,20 +0,0 @@ -#include -#include - -using json = nlohmann::json; -using std::to_string; - -int main() -{ - // create values - json j = {{"one", 1}, {"two", 2}}; - int i = 42; - - // use ADL to select best to_string function - auto j_str = to_string(j); // calling nlohmann::to_string - auto i_str = to_string(i); // calling std::to_string - - // serialize without indentation - std::cout << j_str << "\n\n" - << i_str << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_string.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_string.output deleted file mode 100644 index b261f35..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_string.output +++ /dev/null @@ -1,3 +0,0 @@ -{"one":1,"two":2} - -42 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_ubjson.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_ubjson.cpp deleted file mode 100644 index fd267a8..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_ubjson.cpp +++ /dev/null @@ -1,64 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; -using namespace nlohmann::literals; - -// function to print UBJSON's diagnostic format -void print_byte(uint8_t byte) -{ - if (32 < byte and byte < 128) - { - std::cout << (char)byte; - } - else - { - std::cout << (int)byte; - } -} - -int main() -{ - // create a JSON value - json j = R"({"compact": true, "schema": false})"_json; - - // serialize it to UBJSON - std::vector v = json::to_ubjson(j); - - // print the vector content - for (auto& byte : v) - { - print_byte(byte); - } - std::cout << std::endl; - - // create an array of numbers - json array = {1, 2, 3, 4, 5, 6, 7, 8}; - - // serialize it to UBJSON using default representation - std::vector v_array = json::to_ubjson(array); - // serialize it to UBJSON using size optimization - std::vector v_array_size = json::to_ubjson(array, true); - // serialize it to UBJSON using type optimization - std::vector v_array_size_and_type = json::to_ubjson(array, true, true); - - // print the vector contents - for (auto& byte : v_array) - { - print_byte(byte); - } - std::cout << std::endl; - - for (auto& byte : v_array_size) - { - print_byte(byte); - } - std::cout << std::endl; - - for (auto& byte : v_array_size_and_type) - { - print_byte(byte); - } - std::cout << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_ubjson.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_ubjson.output deleted file mode 100644 index 087980c..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/to_ubjson.output +++ /dev/null @@ -1,4 +0,0 @@ -{i7compactTi6schemaF} -[i1i2i3i4i5i6i7i8] -[#i8i1i2i3i4i5i6i7i8 -[$i#i812345678 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/type.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/type.cpp deleted file mode 100644 index 68fba3a..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/type.cpp +++ /dev/null @@ -1,28 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json j_null; - json j_boolean = true; - json j_number_integer = -17; - json j_number_unsigned = 42u; - json j_number_float = 23.42; - json j_object = {{"one", 1}, {"two", 2}}; - json j_array = {1, 2, 4, 8, 16}; - json j_string = "Hello, world"; - - // call type() - std::cout << std::boolalpha; - std::cout << (j_null.type() == json::value_t::null) << '\n'; - std::cout << (j_boolean.type() == json::value_t::boolean) << '\n'; - std::cout << (j_number_integer.type() == json::value_t::number_integer) << '\n'; - std::cout << (j_number_unsigned.type() == json::value_t::number_unsigned) << '\n'; - std::cout << (j_number_float.type() == json::value_t::number_float) << '\n'; - std::cout << (j_object.type() == json::value_t::object) << '\n'; - std::cout << (j_array.type() == json::value_t::array) << '\n'; - std::cout << (j_string.type() == json::value_t::string) << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/type.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/type.output deleted file mode 100644 index 310e632..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/type.output +++ /dev/null @@ -1,8 +0,0 @@ -true -true -true -true -true -true -true -true diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/type_error.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/type_error.cpp deleted file mode 100644 index d4f18b1..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/type_error.cpp +++ /dev/null @@ -1,20 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - try - { - // calling push_back() on a string value - json j = "string"; - j.push_back("another string"); - } - catch (json::type_error& e) - { - // output exception information - std::cout << "message: " << e.what() << '\n' - << "exception id: " << e.id << std::endl; - } -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/type_error.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/type_error.output deleted file mode 100644 index 1a67339..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/type_error.output +++ /dev/null @@ -1,2 +0,0 @@ -message: [json.exception.type_error.308] cannot use push_back() with string -exception id: 308 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/type_name.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/type_name.cpp deleted file mode 100644 index 32d3590..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/type_name.cpp +++ /dev/null @@ -1,27 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON values - json j_null; - json j_boolean = true; - json j_number_integer = -17; - json j_number_unsigned = 42u; - json j_number_float = 23.42; - json j_object = {{"one", 1}, {"two", 2}}; - json j_array = {1, 2, 4, 8, 16}; - json j_string = "Hello, world"; - - // call type_name() - std::cout << j_null << " is a " << j_null.type_name() << '\n'; - std::cout << j_boolean << " is a " << j_boolean.type_name() << '\n'; - std::cout << j_number_integer << " is a " << j_number_integer.type_name() << '\n'; - std::cout << j_number_unsigned << " is a " << j_number_unsigned.type_name() << '\n'; - std::cout << j_number_float << " is a " << j_number_float.type_name() << '\n'; - std::cout << j_object << " is an " << j_object.type_name() << '\n'; - std::cout << j_array << " is an " << j_array.type_name() << '\n'; - std::cout << j_string << " is a " << j_string.type_name() << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/type_name.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/type_name.output deleted file mode 100644 index f394e81..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/type_name.output +++ /dev/null @@ -1,8 +0,0 @@ -null is a null -true is a boolean --17 is a number -42 is a number -23.42 is a number -{"one":1,"two":2} is an object -[1,2,4,8,16] is an array -"Hello, world" is a string diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/unflatten.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/unflatten.cpp deleted file mode 100644 index 75fb02d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/unflatten.cpp +++ /dev/null @@ -1,26 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create JSON value - json j_flattened = - { - {"/answer/everything", 42}, - {"/happy", true}, - {"/list/0", 1}, - {"/list/1", 0}, - {"/list/2", 2}, - {"/name", "Niels"}, - {"/nothing", nullptr}, - {"/object/currency", "USD"}, - {"/object/value", 42.99}, - {"/pi", 3.141} - }; - - // call unflatten() - std::cout << std::setw(4) << j_flattened.unflatten() << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/unflatten.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/unflatten.output deleted file mode 100644 index ed48385..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/unflatten.output +++ /dev/null @@ -1,18 +0,0 @@ -{ - "answer": { - "everything": 42 - }, - "happy": true, - "list": [ - 1, - 0, - 2 - ], - "name": "Niels", - "nothing": null, - "object": { - "currency": "USD", - "value": 42.99 - }, - "pi": 3.141 -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/update.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/update.cpp deleted file mode 100644 index ff94b67..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/update.cpp +++ /dev/null @@ -1,24 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; -using namespace nlohmann::literals; - -int main() -{ - // create two JSON objects - json o1 = R"( {"color": "red", "price": 17.99, "names": {"de": "Flugzeug"}} )"_json; - json o2 = R"( {"color": "blue", "speed": 100, "names": {"en": "plane"}} )"_json; - json o3 = o1; - - // add all keys from o2 to o1 (updating "color", replacing "names") - o1.update(o2); - - // add all keys from o2 to o1 (updating "color", merging "names") - o3.update(o2, true); - - // output updated object o1 and o3 - std::cout << std::setw(2) << o1 << '\n'; - std::cout << std::setw(2) << o3 << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/update.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/update.output deleted file mode 100644 index c35a745..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/update.output +++ /dev/null @@ -1,17 +0,0 @@ -{ - "color": "blue", - "names": { - "en": "plane" - }, - "price": 17.99, - "speed": 100 -} -{ - "color": "blue", - "names": { - "de": "Flugzeug", - "en": "plane" - }, - "price": 17.99, - "speed": 100 -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/update__range.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/update__range.cpp deleted file mode 100644 index 5b43850..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/update__range.cpp +++ /dev/null @@ -1,24 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; -using namespace nlohmann::literals; - -int main() -{ - // create two JSON objects - json o1 = R"( {"color": "red", "price": 17.99, "names": {"de": "Flugzeug"}} )"_json; - json o2 = R"( {"color": "blue", "speed": 100, "names": {"en": "plane"}} )"_json; - json o3 = o1; - - // add all keys from o2 to o1 (updating "color", replacing "names") - o1.update(o2.begin(), o2.end()); - - // add all keys from o2 to o1 (updating "color", merging "names") - o3.update(o2.begin(), o2.end(), true); - - // output updated object o1 and o3 - std::cout << std::setw(2) << o1 << '\n'; - std::cout << std::setw(2) << o3 << '\n'; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/update__range.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/update__range.output deleted file mode 100644 index c35a745..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/update__range.output +++ /dev/null @@ -1,17 +0,0 @@ -{ - "color": "blue", - "names": { - "en": "plane" - }, - "price": 17.99, - "speed": 100 -} -{ - "color": "blue", - "names": { - "de": "Flugzeug", - "en": "plane" - }, - "price": 17.99, - "speed": 100 -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/value__json_ptr.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/value__json_ptr.cpp deleted file mode 100644 index d866ef0..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/value__json_ptr.cpp +++ /dev/null @@ -1,31 +0,0 @@ -#include -#include - -using json = nlohmann::json; -using namespace nlohmann::literals; - -int main() -{ - // create a JSON object with different entry types - json j = - { - {"integer", 1}, - {"floating", 42.23}, - {"string", "hello world"}, - {"boolean", true}, - {"object", {{"key1", 1}, {"key2", 2}}}, - {"array", {1, 2, 3}} - }; - - // access existing values - int v_integer = j.value("/integer"_json_pointer, 0); - double v_floating = j.value("/floating"_json_pointer, 47.11); - - // access nonexisting values and rely on default value - std::string v_string = j.value("/nonexisting"_json_pointer, "oops"); - bool v_boolean = j.value("/nonexisting"_json_pointer, false); - - // output values - std::cout << std::boolalpha << v_integer << " " << v_floating - << " " << v_string << " " << v_boolean << "\n"; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/value__json_ptr.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/value__json_ptr.output deleted file mode 100644 index dfc40e5..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/value__json_ptr.output +++ /dev/null @@ -1 +0,0 @@ -1 42.23 oops false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/value__keytype.c++17.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/value__keytype.c++17.cpp deleted file mode 100644 index 1f6ff5c..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/value__keytype.c++17.cpp +++ /dev/null @@ -1,32 +0,0 @@ -#include -#include -#include - -using namespace std::string_view_literals; -using json = nlohmann::json; - -int main() -{ - // create a JSON object with different entry types - json j = - { - {"integer", 1}, - {"floating", 42.23}, - {"string", "hello world"}, - {"boolean", true}, - {"object", {{"key1", 1}, {"key2", 2}}}, - {"array", {1, 2, 3}} - }; - - // access existing values - int v_integer = j.value("integer"sv, 0); - double v_floating = j.value("floating"sv, 47.11); - - // access nonexisting values and rely on default value - std::string v_string = j.value("nonexisting"sv, "oops"); - bool v_boolean = j.value("nonexisting"sv, false); - - // output values - std::cout << std::boolalpha << v_integer << " " << v_floating - << " " << v_string << " " << v_boolean << "\n"; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/value__keytype.c++17.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/value__keytype.c++17.output deleted file mode 100644 index dfc40e5..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/value__keytype.c++17.output +++ /dev/null @@ -1 +0,0 @@ -1 42.23 oops false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/value__object_t_key_type.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/value__object_t_key_type.cpp deleted file mode 100644 index 9488d30..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/value__object_t_key_type.cpp +++ /dev/null @@ -1,30 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - // create a JSON object with different entry types - json j = - { - {"integer", 1}, - {"floating", 42.23}, - {"string", "hello world"}, - {"boolean", true}, - {"object", {{"key1", 1}, {"key2", 2}}}, - {"array", {1, 2, 3}} - }; - - // access existing values - int v_integer = j.value("integer", 0); - double v_floating = j.value("floating", 47.11); - - // access nonexisting values and rely on default value - std::string v_string = j.value("nonexisting", "oops"); - bool v_boolean = j.value("nonexisting", false); - - // output values - std::cout << std::boolalpha << v_integer << " " << v_floating - << " " << v_string << " " << v_boolean << "\n"; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/value__object_t_key_type.output b/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/value__object_t_key_type.output deleted file mode 100644 index dfc40e5..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/examples/value__object_t_key_type.output +++ /dev/null @@ -1 +0,0 @@ -1 42.23 oops false diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/json.gif b/app/jni/src/libultraship/extern/nlohmann-json/docs/json.gif deleted file mode 100644 index 8219866..0000000 Binary files a/app/jni/src/libultraship/extern/nlohmann-json/docs/json.gif and /dev/null differ diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/Makefile b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/Makefile deleted file mode 100644 index e4731bf..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/Makefile +++ /dev/null @@ -1,37 +0,0 @@ -# serve the site locally -serve: prepare_files style_check - venv/bin/mkdocs serve - -serve_dirty: prepare_files style_check - venv/bin/mkdocs serve --dirtyreload - -build: prepare_files style_check - venv/bin/mkdocs build - -# create files that are not versioned inside the mkdocs folder (images, examples) -prepare_files: clean - mkdir docs/examples - cp -r ../json.gif docs/images - cp -r ../examples/*.cpp ../examples/*.output docs/examples - -style_check: - @cd docs ; python3 ../scripts/check_structure.py - -# clean subfolders -clean: - rm -fr docs/images/json.gif docs/examples - -# publish site to GitHub pages -publish: prepare_files - venv/bin/mkdocs gh-deploy --clean --force - -# install a Python virtual environment -install_venv: requirements.txt - python3 -mvenv venv - venv/bin/pip install --upgrade pip - venv/bin/pip install wheel - venv/bin/pip install -r requirements.txt - -# uninstall the virtual environment -uninstall_venv: clean - rm -fr venv diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/adl_serializer/from_json.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/adl_serializer/from_json.md deleted file mode 100644 index ba932e9..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/adl_serializer/from_json.md +++ /dev/null @@ -1,73 +0,0 @@ -# nlohmann::adl_serializer::from_json - -```cpp -// (1) -template -static auto from_json(BasicJsonType && j, TargetType& val) noexcept( - noexcept(::nlohmann::from_json(std::forward(j), val))) --> decltype(::nlohmann::from_json(std::forward(j), val), void()) - -// (2) -template -static auto from_json(BasicJsonType && j) noexcept( -noexcept(::nlohmann::from_json(std::forward(j), detail::identity_tag {}))) --> decltype(::nlohmann::from_json(std::forward(j), detail::identity_tag {})) -``` - -This function is usually called by the [`get()`](../basic_json/get.md) function of the [basic_json](../basic_json) -class (either explicitly or via the conversion operators). - -1. This function is chosen for default-constructible value types. -2. This function is chosen for value types which are not default-constructible. - -## Parameters - -`j` (in) -: JSON value to read from - -`val` (out) -: value to write to - -## Return value - -Copy of the JSON value, converted to `ValueType` - -## Examples - -??? example "Example: (1) Default-constructible type" - - The example below shows how a `from_json` function can be implemented for a user-defined type. This function is - called by the `adl_serializer` when `get()` is called. - - ```cpp - --8<-- "examples/from_json__default_constructible.cpp" - ``` - - Output: - - ```json - --8<-- "examples/from_json__default_constructible.output" - ``` - -??? example "Example: (2) Non-default-constructible type" - - The example below shows how a `from_json` is implemented as part of a specialization of the `adl_serializer` to - realize the conversion of a non-default-constructible type. - - ```cpp - --8<-- "examples/from_json__non_default_constructible.cpp" - ``` - - Output: - - ```json - --8<-- "examples/from_json__non_default_constructible.output" - ``` - -## See also - -- [to_json](to_json.md) - -## Version history - -- Added in version 2.1.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/adl_serializer/index.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/adl_serializer/index.md deleted file mode 100644 index 95f35cd..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/adl_serializer/index.md +++ /dev/null @@ -1,35 +0,0 @@ -# nlohmann::adl_serializer - -```cpp -template -struct adl_serializer; -``` - -Serializer that uses ADL ([Argument-Dependent Lookup](https://en.cppreference.com/w/cpp/language/adl)) to choose -`to_json`/`from_json` functions from the types' namespaces. - -It is implemented similar to - -```cpp -template -struct adl_serializer { - template - static void to_json(BasicJsonType& j, const T& value) { - // calls the "to_json" method in T's namespace - } - - template - static void from_json(const BasicJsonType& j, T& value) { - // same thing, but with the "from_json" method - } -}; -``` - -## Member functions - -- [**from_json**](from_json.md) - convert a JSON value to any value type -- [**to_json**](to_json.md) - convert any value type to a JSON value - -## Version history - -- Added in version 2.1.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/adl_serializer/to_json.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/adl_serializer/to_json.md deleted file mode 100644 index f8419bd..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/adl_serializer/to_json.md +++ /dev/null @@ -1,43 +0,0 @@ -# nlohmann::adl_serializer::to_json - -```cpp -template -static auto to_json(BasicJsonType& j, TargetType && val) noexcept( - noexcept(::nlohmann::to_json(j, std::forward(val)))) --> decltype(::nlohmann::to_json(j, std::forward(val)), void()) -``` - -This function is usually called by the constructors of the [basic_json](../basic_json) class. - -## Parameters - -`j` (out) -: JSON value to write to - -`val` (in) -: value to read from - -## Examples - -??? example - - The example below shows how a `to_json` function can be implemented for a user-defined type. This function is called - by the `adl_serializer` when the constructor `basic_json(ns::person)` is called. - - ```cpp - --8<-- "examples/to_json.cpp" - ``` - - Output: - - ```json - --8<-- "examples/to_json.output" - ``` - -## See also - -- [from_json](from_json.md) - -## Version history - -- Added in version 2.1.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/accept.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/accept.md deleted file mode 100644 index 1c806e8..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/accept.md +++ /dev/null @@ -1,113 +0,0 @@ -# nlohmann::basic_json::accept - -```cpp -// (1) -template -static bool accept(InputType&& i, - const bool ignore_comments = false); - -// (2) -template -static bool accept(IteratorType first, IteratorType last, - const bool ignore_comments = false); -``` - -Checks whether the input is valid JSON. - -1. Reads from a compatible input. -2. Reads from a pair of character iterators - - The value_type of the iterator must be an integral type with size of 1, 2 or 4 bytes, which will be interpreted - respectively as UTF-8, UTF-16 and UTF-32. - -Unlike the [`parse`](parse.md) function, this function neither throws an exception in case of invalid JSON input -(i.e., a parse error) nor creates diagnostic information. - -## Template parameters - -`InputType` -: A compatible input, for instance: - - - an `std::istream` object - - a `FILE` pointer (must not be null) - - a C-style array of characters - - a pointer to a null-terminated string of single byte characters - - a `std::string` - - an object `obj` for which `begin(obj)` and `end(obj)` produces a valid pair of iterators. - -`IteratorType` -: a compatible iterator type, for instance. - - - a pair of `std::string::iterator` or `std::vector::iterator` - - a pair of pointers such as `ptr` and `ptr + len` - -## Parameters - -`i` (in) -: Input to parse from. - -`ignore_comments` (in) -: whether comments should be ignored and treated like whitespace (`#!cpp true`) or yield a parse error - (`#!cpp false`); (optional, `#!cpp false` by default) - -`first` (in) -: iterator to start of character range - -`last` (in) -: iterator to end of character range - -## Return value - -Whether the input is valid JSON. - -## Exception safety - -Strong guarantee: if an exception is thrown, there are no changes in the JSON value. - -## Complexity - -Linear in the length of the input. The parser is a predictive LL(1) parser. - -## Notes - -(1) A UTF-8 byte order mark is silently ignored. - -!!! danger "Runtime assertion" - - The precondition that a passed `#!cpp FILE` pointer must not be null is enforced with a - [runtime assertion](../../features/assertions.md). - -## Examples - -??? example - - The example below demonstrates the `accept()` function reading from a string. - - ```cpp - --8<-- "examples/accept__string.cpp" - ``` - - Output: - - ```json - --8<-- "examples/accept__string.output" - ``` - -## See also - -- [parse](parse.md) - deserialize from a compatible input -- [operator>>](../operator_gtgt.md) - deserialize from stream - -## Version history - -- Added in version 3.0.0. -- Ignoring comments via `ignore_comments` added in version 3.9.0. - -!!! warning "Deprecation" - - Overload (2) replaces calls to `accept` with a pair of iterators as their first parameter which has been - deprecated in version 3.8.0. This overload will be removed in version 4.0.0. Please replace all calls like - `#!cpp accept({ptr, ptr+len}, ...);` with `#!cpp accept(ptr, ptr+len, ...);`. - - You should be warned by your compiler with a `-Wdeprecated-declarations` warning if you are using a deprecated - function. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/array.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/array.md deleted file mode 100644 index 22b2ee1..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/array.md +++ /dev/null @@ -1,60 +0,0 @@ -# nlohmann::basic_json::array - -```cpp -static basic_json array(initializer_list_t init = {}); -``` - -Creates a JSON array value from a given initializer list. That is, given a list of values `a, b, c`, creates the JSON -value `#!json [a, b, c]`. If the initializer list is empty, the empty array `#!json []` is created. - -## Parameters - -`init` (in) -: initializer list with JSON values to create an array from (optional) - -## Return value - -JSON array value - -## Exception safety - -Strong guarantee: if an exception is thrown, there are no changes in the JSON value. - -## Complexity - -Linear in the size of `init`. - -## Notes - -This function is only needed to express two edge cases that cannot be realized with the initializer list constructor -([`basic_json(initializer_list_t, bool, value_t)`](basic_json.md)). These cases are: - -1. creating an array whose elements are all pairs whose first element is a string -- in this case, the initializer list - constructor would create an object, taking the first elements as keys -2. creating an empty array -- passing the empty initializer list to the initializer list constructor yields an empty - object - -## Examples - -??? example - - The following code shows an example for the `array` function. - - ```cpp - --8<-- "examples/array.cpp" - ``` - - Output: - - ```json - --8<-- "examples/array.output" - ``` - -## See also - -- [`basic_json(initializer_list_t)`](basic_json.md) - create a JSON value from an initializer list -- [`object`](object.md) - create a JSON object value from an initializer list - -## Version history - -- Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/array_t.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/array_t.md deleted file mode 100644 index dd2b901..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/array_t.md +++ /dev/null @@ -1,68 +0,0 @@ -# nlohmann::basic_json::array_t - -```cpp -using array_t = ArrayType>; -``` - -The type used to store JSON arrays. - -[RFC 8259](https://tools.ietf.org/html/rfc8259) describes JSON arrays as follows: -> An array is an ordered sequence of zero or more values. - -To store objects in C++, a type is defined by the template parameters explained below. - -## Template parameters - -`ArrayType` -: container type to store arrays (e.g., `std::vector` or `std::list`) - -`AllocatorType` -: the allocator to use for objects (e.g., `std::allocator`) - -## Notes - -#### Default type - -With the default values for `ArrayType` (`std::vector`) and `AllocatorType` (`std::allocator`), the default value for -`array_t` is: - -```cpp -std::vector< - basic_json, // value_type - std::allocator // allocator_type -> -``` - -#### Limits - -[RFC 8259](https://tools.ietf.org/html/rfc8259) specifies: -> An implementation may set limits on the maximum depth of nesting. - -In this class, the array's limit of nesting is not explicitly constrained. However, a maximum depth of nesting may be -introduced by the compiler or runtime environment. A theoretical limit can be queried by calling the -[`max_size`](max_size.md) function of a JSON array. - -#### Storage - -Arrays are stored as pointers in a `basic_json` type. That is, for any access to array values, a pointer of type -`#!cpp array_t*` must be dereferenced. - -## Examples - -??? example - - The following code shows that `array_t` is by default, a typedef to `#!cpp std::vector`. - - ```cpp - --8<-- "examples/array_t.cpp" - ``` - - Output: - - ```json - --8<-- "examples/array_t.output" - ``` - -## Version history - -- Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/at.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/at.md deleted file mode 100644 index 5e95045..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/at.md +++ /dev/null @@ -1,226 +0,0 @@ -# nlohmann::basic_json::at - -```cpp -// (1) -reference at(size_type idx); -const_reference at(size_type idx) const; - -// (2) -reference at(const typename object_t::key_type& key); -const_reference at(const typename object_t::key_type& key) const; - -// (3) -template -reference at(KeyType&& key); -template -const_reference at(KeyType&& key) const; - -// (4) -reference at(const json_pointer& ptr); -const_reference at(const json_pointer& ptr) const; -``` - -1. Returns a reference to the array element at specified location `idx`, with bounds checking. -2. Returns a reference to the object element with specified key `key`, with bounds checking. -3. See 2. This overload is only available if `KeyType` is comparable with `#!cpp typename object_t::key_type` and - `#!cpp typename object_comparator_t::is_transparent` denotes a type. -4. Returns a reference to the element at specified JSON pointer `ptr`, with bounds checking. - -## Template parameters - -`KeyType` -: A type for an object key other than [`json_pointer`](../json_pointer/index.md) that is comparable with - [`string_t`](string_t.md) using [`object_comparator_t`](object_comparator_t.md). - This can also be a string view (C++17). - -## Parameters - -`idx` (in) -: index of the element to access - -`key` (in) -: object key of the elements to access - -`ptr` (in) -: JSON pointer to the desired element - -## Return value - -1. reference to the element at index `idx` -2. reference to the element at key `key` -3. reference to the element at key `key` -4. reference to the element pointed to by `ptr` - -## Exception safety - -Strong exception safety: if an exception occurs, the original value stays intact. - -## Exceptions - -1. The function can throw the following exceptions: - - Throws [`type_error.304`](../../home/exceptions.md#jsonexceptiontype_error304) if the JSON value is not an array; - in this case, calling `at` with an index makes no sense. See example below. - - Throws [`out_of_range.401`](../../home/exceptions.md#jsonexceptionout_of_range401) if the index `idx` is out of - range of the array; that is, `idx >= size()`. See example below. -2. The function can throw the following exceptions: - - Throws [`type_error.304`](../../home/exceptions.md#jsonexceptiontype_error304) if the JSON value is not an object; - in this case, calling `at` with a key makes no sense. See example below. - - Throws [`out_of_range.403`](../../home/exceptions.md#jsonexceptionout_of_range403) if the key `key` is not - stored in the object; that is, `find(key) == end()`. See example below. -3. See 2. -4. The function can throw the following exceptions: - - Throws [`parse_error.106`](../../home/exceptions.md#jsonexceptionparse_error106) if an array index in the passed - JSON pointer `ptr` begins with '0'. See example below. - - Throws [`parse_error.109`](../../home/exceptions.md#jsonexceptionparse_error109) if an array index in the passed - JSON pointer `ptr` is not a number. See example below. - - Throws [`out_of_range.401`](../../home/exceptions.md#jsonexceptionout_of_range401) if an array index in the passed - JSON pointer `ptr` is out of range. See example below. - - Throws [`out_of_range.402`](../../home/exceptions.md#jsonexceptionout_of_range402) if the array index '-' is used - in the passed JSON pointer `ptr`. As `at` provides checked access (and no elements are implicitly inserted), the - index '-' is always invalid. See example below. - - Throws [`out_of_range.403`](../../home/exceptions.md#jsonexceptionout_of_range403) if the JSON pointer describes a - key of an object which cannot be found. See example below. - - Throws [`out_of_range.404`](../../home/exceptions.md#jsonexceptionout_of_range404) if the JSON pointer `ptr` can - not be resolved. See example below. - -## Complexity - -1. Constant. -2. Logarithmic in the size of the container. -3. Logarithmic in the size of the container. -4. Logarithmic in the size of the container. - -## Examples - -??? example "Example: (1) access specified array element with bounds checking" - - The example below shows how array elements can be read and written using `at()`. It also demonstrates the different - exceptions that can be thrown. - - ```cpp - --8<-- "examples/at__size_type.cpp" - ``` - - Output: - - ```json - --8<-- "examples/at__size_type.output" - ``` - -??? example "Example: (1) access specified array element with bounds checking" - - The example below shows how array elements can be read using `at()`. It also demonstrates the different exceptions - that can be thrown. - - ```cpp - --8<-- "examples/at__size_type_const.cpp" - ``` - - Output: - - ```json - --8<-- "examples/at__size_type_const.output" - ``` - -??? example "Example: (2) access specified object element with bounds checking" - - The example below shows how object elements can be read and written using `at()`. It also demonstrates the different - exceptions that can be thrown. - - ```cpp - --8<-- "examples/at__object_t_key_type.cpp" - ``` - - Output: - - ```json - --8<-- "examples/at__object_t_key_type.output" - ``` - -??? example "Example: (2) access specified object element with bounds checking" - - The example below shows how object elements can be read using `at()`. It also demonstrates the different exceptions - that can be thrown. - - ```cpp - --8<-- "examples/at__object_t_key_type_const.cpp" - ``` - - Output: - - ```json - --8<-- "examples/at__object_t_key_type_const.output" - ``` - -??? example "Example: (3) access specified object element using string_view with bounds checking" - - The example below shows how object elements can be read and written using `at()`. It also demonstrates the different - exceptions that can be thrown. - - ```cpp - --8<-- "examples/at__keytype.c++17.cpp" - ``` - - Output: - - ```json - --8<-- "examples/at__keytype.c++17.output" - ``` - -??? example "Example: (3) access specified object element using string_view with bounds checking" - - The example below shows how object elements can be read using `at()`. It also demonstrates the different exceptions - that can be thrown. - - ```cpp - --8<-- "examples/at__keytype_const.c++17.cpp" - ``` - - Output: - - ```json - --8<-- "examples/at__keytype_const.c++17.output" - ``` - -??? example "Example: (4) access specified element via JSON Pointer" - - The example below shows how object elements can be read and written using `at()`. It also demonstrates the different - exceptions that can be thrown. - - ```cpp - --8<-- "examples/at__json_pointer.cpp" - ``` - - Output: - - ```json - --8<-- "examples/at__json_pointer.output" - ``` - -??? example "Example: (4) access specified element via JSON Pointer" - - The example below shows how object elements can be read using `at()`. It also demonstrates the different exceptions - that can be thrown. - - ```cpp - --8<-- "examples/at__json_pointer_const.cpp" - ``` - - Output: - - ```json - --8<-- "examples/at__json_pointer_const.output" - ``` - -## See also - -- documentation on [checked access](../../features/element_access/checked_access.md) -- see [`operator[]`](operator%5B%5D.md) for unchecked access by reference -- see [`value`](value.md) for access with default value - -## Version history - -1. Added in version 1.0.0. -2. Added in version 1.0.0. -3. Added in version 3.11.0. -4. Added in version 2.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/back.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/back.md deleted file mode 100644 index 1a71528..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/back.md +++ /dev/null @@ -1,65 +0,0 @@ -# nlohmann::basic_json::back - -```cpp -reference back(); - -const_reference back() const; -``` - -Returns a reference to the last element in the container. For a JSON container `c`, the expression `c.back()` is -equivalent to - -```cpp -auto tmp = c.end(); ---tmp; -return *tmp; -``` - -## Return value - -In case of a structured type (array or object), a reference to the last element is returned. In case of number, string, -boolean, or binary values, a reference to the value is returned. - -## Exception safety - -Strong guarantee: if an exception is thrown, there are no changes in the JSON value. - -## Exceptions - -If the JSON value is `#!json null`, exception -[`invalid_iterator.214`](../../home/exceptions.md#jsonexceptioninvalid_iterator214) is thrown. - -## Complexity - -Constant. - -## Notes - -!!! info "Precondition" - - The array or object must not be empty. Calling `back` on an empty array or object yields undefined behavior. - -## Examples - -??? example - - The following code shows an example for `back()`. - - ```cpp - --8<-- "examples/back.cpp" - ``` - - Output: - - ```json - --8<-- "examples/back.output" - ``` - -## See also - -- [front](front.md) to access the first element - -## Version history - -- Added in version 1.0.0. -- Adjusted code to return reference to binary values in version 3.8.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/basic_json.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/basic_json.md deleted file mode 100644 index e2e7361..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/basic_json.md +++ /dev/null @@ -1,402 +0,0 @@ -# nlohmann::basic_json::basic_json - -```cpp -// (1) -basic_json(const value_t v); - -// (2) -basic_json(std::nullptr_t = nullptr) noexcept; - -// (3) -template -basic_json(CompatibleType&& val) noexcept(noexcept( - JSONSerializer::to_json(std::declval(), - std::forward(val)))); - -// (4) -template -basic_json(const BasicJsonType& val); - -// (5) -basic_json(initializer_list_t init, - bool type_deduction = true, - value_t manual_type = value_t::array); - -// (6) -basic_json(size_type cnt, const basic_json& val); - -// (7) -basic_json(iterator first, iterator last); -basic_json(const_iterator first, const_iterator last); - -// (8) -basic_json(const basic_json& other); - -// (9) -basic_json(basic_json&& other) noexcept; -``` - -1. Create an empty JSON value with a given type. The value will be default initialized with an empty value which depends - on the type: - - | Value type | initial value | - |------------|----------------| - | null | `#!json null` | - | boolean | `#!json false` | - | string | `#!json ""` | - | number | `#!json 0` | - | object | `#!json {}` | - | array | `#!json []` | - | binary | empty array | - - The postcondition of this constructor can be restored by calling [`clear()`](clear.md). - -2. Create a `#!json null` JSON value. It either takes a null pointer as parameter (explicitly creating `#!json null`) - or no parameter (implicitly creating `#!json null`). The passed null pointer itself is not read -- it is only used to - choose the right constructor. - -3. This is a "catch all" constructor for all compatible JSON types; that is, types for which a `to_json()` method - exists. The constructor forwards the parameter `val` to that method (to `json_serializer::to_json` method with - `U = uncvref_t`, to be exact). - - Template type `CompatibleType` includes, but is not limited to, the following types: - - - **arrays**: [`array_t`](array_t.md) and all kinds of compatible containers such as `std::vector`, `std::deque`, - `std::list`, `std::forward_list`, `std::array`, `std::valarray`, `std::set`, `std::unordered_set`, `std::multiset`, - and `std::unordered_multiset` with a `value_type` from which a `basic_json` value can be constructed. - - **objects**: [`object_t`](object_t.md) and all kinds of compatible associative containers such as `std::map`, - `std::unordered_map`, `std::multimap`, and `std::unordered_multimap` with a `key_type` compatible to `string_t` - and a `value_type` from which a `basic_json` value can be constructed. - - **strings**: `string_t`, string literals, and all compatible string containers can be used. - - **numbers**: [`number_integer_t`](number_integer_t.md), [`number_unsigned_t`](number_unsigned_t.md), - [`number_float_t`](number_float_t.md), and all convertible number types such as `int`, `size_t`, `int64_t`, `float` - or `double` can be used. - - **boolean**: `boolean_t` / `bool` can be used. - - **binary**: `binary_t` / `std::vector` may be used; unfortunately because string literals cannot be - distinguished from binary character arrays by the C++ type system, all types compatible with `const char*` will be - directed to the string constructor instead. This is both for backwards compatibility, and due to the fact that a - binary type is not a standard JSON type. - - See the examples below. - -4. This is a constructor for existing `basic_json` types. It does not hijack copy/move constructors, since the parameter - has different template arguments than the current ones. - - The constructor tries to convert the internal `m_value` of the parameter. - -5. Creates a JSON value of type array or object from the passed initializer list `init`. In case `type_deduction` is - `#!cpp true` (default), the type of the JSON value to be created is deducted from the initializer list `init` - according to the following rules: - - 1. If the list is empty, an empty JSON object value `{}` is created. - 2. If the list consists of pairs whose first element is a string, a JSON object value is created where the first - elements of the pairs are treated as keys and the second elements are as values. - 3. In all other cases, an array is created. - - The rules aim to create the best fit between a C++ initializer list and JSON values. The rationale is as follows: - - 1. The empty initializer list is written as `#!cpp {}` which is exactly an empty JSON object. - 2. C++ has no way of describing mapped types other than to list a list of pairs. As JSON requires that keys must be - of type string, rule 2 is the weakest constraint one can pose on initializer lists to interpret them as an - object. - 3. In all other cases, the initializer list could not be interpreted as JSON object type, so interpreting it as JSON - array type is safe. - - With the rules described above, the following JSON values cannot be expressed by an initializer list: - - - the empty array (`#!json []`): use `array(initializer_list_t)` with an empty initializer list in this case - - arrays whose elements satisfy rule 2: use `array(initializer_list_t)` with the same initializer list in this case - - Function [`array()`](array.md) and [`object()`](object.md) force array and object creation from initializer lists, - respectively. - -6. Constructs a JSON array value by creating `cnt` copies of a passed value. In case `cnt` is `0`, an empty array is - created. - -7. Constructs the JSON value with the contents of the range `[first, last)`. The semantics depends on the different - types a JSON value can have: - - - In case of a `#!json null` type, [invalid_iterator.206](../../home/exceptions.md#jsonexceptioninvalid_iterator206) - is thrown. - - In case of other primitive types (number, boolean, or string), `first` must be `begin()` and `last` must be - `end()`. In this case, the value is copied. Otherwise, - [`invalid_iterator.204`](../../home/exceptions.md#jsonexceptioninvalid_iterator204) is thrown. - - In case of structured types (array, object), the constructor behaves as similar versions for `std::vector` or - `std::map`; that is, a JSON array or object is constructed from the values in the range. - -8. Creates a copy of a given JSON value. - -9. Move constructor. Constructs a JSON value with the contents of the given value `other` using move semantics. It - "steals" the resources from `other` and leaves it as JSON `#!json null` value. - -## Template parameters - -`CompatibleType` -: a type such that: - - - `CompatibleType` is not derived from `std::istream`, - - `CompatibleType` is not `basic_json` (to avoid hijacking copy/move constructors), - - `CompatibleType` is not a different `basic_json` type (i.e. with different template arguments) - - `CompatibleType` is not a `basic_json` nested type (e.g., `json_pointer`, `iterator`, etc.) - - `json_serializer` (with `U = uncvref_t`) has a `to_json(basic_json_t&, CompatibleType&&)` - method - -`BasicJsonType`: -: a type such that: - - - `BasicJsonType` is a `basic_json` type. - - `BasicJsonType` has different template arguments than `basic_json_t`. - -`U`: -: `uncvref_t` - -## Parameters - -`v` (in) -: the type of the value to create - -`val` (in) -: the value to be forwarded to the respective constructor - -`init` (in) -: initializer list with JSON values - -`type_deduction` (in) -: internal parameter; when set to `#!cpp true`, the type of the JSON value is deducted from the initializer list - `init`; when set to `#!cpp false`, the type provided via `manual_type` is forced. This mode is used by the functions - `array(initializer_list_t)` and `object(initializer_list_t)`. - -`manual_type` (in) -: internal parameter; when `type_deduction` is set to `#!cpp false`, the created JSON value will use the provided type - (only `value_t::array` and `value_t::object` are valid); when `type_deduction` is set to `#!cpp true`, this - parameter has no effect - -`cnt` (in) -: the number of JSON copies of `val` to create - -`first` (in) -: begin of the range to copy from (included) - -`last` (in) -: end of the range to copy from (excluded) - -`other` (in) -: the JSON value to copy/move - -## Exception safety - -1. Strong guarantee: if an exception is thrown, there are no changes to any JSON value. -2. No-throw guarantee: this constructor never throws exceptions. -3. Depends on the called constructor. For types directly supported by the library (i.e., all types for which no - `to_json()` function was provided), strong guarantee holds: if an exception is thrown, there are no changes to any - JSON value. -4. Depends on the called constructor. For types directly supported by the library (i.e., all types for which no - `to_json()` function was provided), strong guarantee holds: if an exception is thrown, there are no changes to any - JSON value. -5. Strong guarantee: if an exception is thrown, there are no changes to any JSON value. -6. Strong guarantee: if an exception is thrown, there are no changes to any JSON value. -7. Strong guarantee: if an exception is thrown, there are no changes to any JSON value. -8. Strong guarantee: if an exception is thrown, there are no changes to any JSON value. -9. No-throw guarantee: this constructor never throws exceptions. - -## Exceptions - -1. (none) -2. The function does not throw exceptions. -3. (none) -4. (none) -5. The function can throw the following exceptions: - - Throws [`type_error.301`](../../home/exceptions.md#jsonexceptiontype_error301) if `type_deduction` is - `#!cpp false`, `manual_type` is `value_t::object`, but `init` contains an element which is not a pair whose first - element is a string. In this case, the constructor could not create an object. If `type_deduction` would have been - `#!cpp true`, an array would have been created. See `object(initializer_list_t)` for an example. -6. (none) -7. The function can throw the following exceptions: - - Throws [`invalid_iterator.201`](../../home/exceptions.md#jsonexceptioninvalid_iterator201) if iterators `first` - and `last` are not compatible (i.e., do not belong to the same JSON value). In this case, the range - `[first, last)` is undefined. - - Throws [`invalid_iterator.204`](../../home/exceptions.md#jsonexceptioninvalid_iterator204) if iterators `first` - and `last` belong to a primitive type (number, boolean, or string), but `first` does not point to the first - element anymore. In this case, the range `[first, last)` is undefined. See example code below. - - Throws [`invalid_iterator.206`](../../home/exceptions.md#jsonexceptioninvalid_iterator206) if iterators `first` - and `last` belong to a `#!json null` value. In this case, the range `[first, last)` is undefined. -8. (none) -9. The function does not throw exceptions. - -## Complexity - -1. Constant. -2. Constant. -3. Usually linear in the size of the passed `val`, also depending on the implementation of the called `to_json()` - method. -4. Usually linear in the size of the passed `val`, also depending on the implementation of the called `to_json()` - method. -5. Linear in the size of the initializer list `init`. -6. Linear in `cnt`. -7. Linear in distance between `first` and `last`. -8. Linear in the size of `other`. -9. Constant. - -## Notes - -- Overload 5: - - !!! note "Empty initializer list" - - When used without parentheses around an empty initializer list, `basic_json()` is called instead of this - function, yielding the JSON `#!json null` value. - -- Overload 7: - - !!! info "Preconditions" - - - Iterators `first` and `last` must be initialized. **This precondition is enforced with a - [runtime assertion](../../features/assertions.md). - - Range `[first, last)` is valid. Usually, this precondition cannot be checked efficiently. Only certain edge - cases are detected; see the description of the exceptions above. A violation of this precondition yields - undefined behavior. - - !!! danger "Runtime assertion" - - A precondition is enforced with a [runtime assertion](../../features/assertions.md). - -- Overload 8: - - !!! info "Postcondition" - - `#!cpp *this == other` - -- Overload 9: - - !!! info "Postconditions" - - - `#!cpp `*this` has the same value as `other` before the call. - - `other` is a JSON `#!json null` value - -## Examples - -??? example "Example: (1) create an empty value with a given type" - - The following code shows the constructor for different `value_t` values. - - ```cpp - --8<-- "examples/basic_json__value_t.cpp" - ``` - - Output: - - ```json - --8<-- "examples/basic_json__value_t.output" - ``` - -??? example "Example: (2) create a `#!json null` object" - - The following code shows the constructor with and without a null pointer parameter. - - ```cpp - --8<-- "examples/basic_json__nullptr_t.cpp" - ``` - - Output: - - ```json - --8<-- "examples/basic_json__nullptr_t.output" - ``` - -??? example "Example: (3) create a JSON value from compatible types" - - The following code shows the constructor with several compatible types. - - ```cpp - --8<-- "examples/basic_json__CompatibleType.cpp" - ``` - - Output: - - ```json - --8<-- "examples/basic_json__CompatibleType.output" - ``` - - Note the output is platform-dependent. - -??? example "Example: (5) create a container (array or object) from an initializer list" - - The example below shows how JSON values are created from initializer lists. - - ```cpp - --8<-- "examples/basic_json__list_init_t.cpp" - ``` - - Output: - - ```json - --8<-- "examples/basic_json__list_init_t.output" - ``` - -??? example "Example: (6) construct an array with count copies of given value" - - The following code shows examples for creating arrays with several copies of a given value. - - ```cpp - --8<-- "examples/basic_json__size_type_basic_json.cpp" - ``` - - Output: - - ```json - --8<-- "examples/basic_json__size_type_basic_json.output" - ``` - -??? example "Example: (7) construct a JSON container given an iterator range" - - The example below shows several ways to create JSON values by specifying a subrange with iterators. - - ```cpp - --8<-- "examples/basic_json__InputIt_InputIt.cpp" - ``` - - Output: - - ```json - --8<-- "examples/basic_json__InputIt_InputIt.output" - ``` - -??? example "Example: (8) copy constructor" - - The following code shows an example for the copy constructor. - - ```cpp - --8<-- "examples/basic_json__basic_json.cpp" - ``` - - Output: - - ```json - --8<-- "examples/basic_json__basic_json.output" - ``` - -??? example "Example: (9) move constructor" - - The code below shows the move constructor explicitly called via `std::move`. - - ```cpp - --8<-- "examples/basic_json__moveconstructor.cpp" - ``` - - Output: - - ```json - --8<-- "examples/basic_json__moveconstructor.output" - ``` - -## Version history - -1. Since version 1.0.0. -2. Since version 1.0.0. -3. Since version 2.1.0. -4. Since version 3.2.0. -5. Since version 1.0.0. -6. Since version 1.0.0. -7. Since version 1.0.0. -8. Since version 1.0.0. -9. Since version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/begin.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/begin.md deleted file mode 100644 index ef623a5..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/begin.md +++ /dev/null @@ -1,42 +0,0 @@ -# nlohmann::basic_json::begin - -```cpp -iterator begin() noexcept; -const_iterator begin() const noexcept; -``` - -Returns an iterator to the first element. - -![Illustration from cppreference.com](../../images/range-begin-end.svg) - -## Return value - -iterator to the first element - -## Exception safety - -No-throw guarantee: this member function never throws exceptions. - -## Complexity - -Constant. - -## Examples - -??? example - - The following code shows an example for `begin()`. - - ```cpp - --8<-- "examples/begin.cpp" - ``` - - Output: - - ```json - --8<-- "examples/begin.output" - ``` - -## Version history - -- Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/binary.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/binary.md deleted file mode 100644 index ce45d8a..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/binary.md +++ /dev/null @@ -1,66 +0,0 @@ -# nlohmann::basic_json::binary - -```cpp -// (1) -static basic_json binary(const typename binary_t::container_type& init); -static basic_json binary(typename binary_t::container_type&& init); - -// (2) -static basic_json binary(const typename binary_t::container_type& init, - std::uint8_t subtype); -static basic_json binary(typename binary_t::container_type&& init, - std::uint8_t subtype); -``` - -1. Creates a JSON binary array value from a given binary container. -2. Creates a JSON binary array value from a given binary container with subtype. - -Binary values are part of various binary formats, such as CBOR, MessagePack, and BSON. This constructor is used to -create a value for serialization to those formats. - -## Parameters - -`init` (in) -: container containing bytes to use as binary type - -`subtype` (in) -: subtype to use in CBOR, MessagePack, and BSON - -## Return value - -JSON binary array value - -## Exception safety - -Strong guarantee: if an exception is thrown, there are no changes in the JSON value. - -## Complexity - -Linear in the size of `init`; constant for `typename binary_t::container_type&& init` versions. - -## Notes - -Note, this function exists because of the difficulty in correctly specifying the correct template overload in the -standard value ctor, as both JSON arrays and JSON binary arrays are backed with some form of a `std::vector`. Because -JSON binary arrays are a non-standard extension it was decided that it would be best to prevent automatic initialization -of a binary array type, for backwards compatibility and so it does not happen on accident. - -## Examples - -??? example - - The following code shows how to create a binary value. - - ```cpp - --8<-- "examples/binary.cpp" - ``` - - Output: - - ```json - --8<-- "examples/binary.output" - ``` - -## Version history - -- Added in version 3.8.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/binary_t.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/binary_t.md deleted file mode 100644 index 705c92c..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/binary_t.md +++ /dev/null @@ -1,89 +0,0 @@ -# nlohmann::basic_json::binary_t - -```cpp -using binary_t = byte_container_with_subtype; -``` - -This type is a type designed to carry binary data that appears in various serialized formats, such as CBOR's Major Type -2, MessagePack's bin, and BSON's generic binary subtype. This type is NOT a part of standard JSON and exists solely for -compatibility with these binary types. As such, it is simply defined as an ordered sequence of zero or more byte values. - -Additionally, as an implementation detail, the subtype of the binary data is carried around as a `std::uint64_t`, which -is compatible with both of the binary data formats that use binary subtyping, (though the specific numbering is -incompatible with each other, and it is up to the user to translate between them). The subtype is added to `BinaryType` -via the helper type [byte_container_with_subtype](../byte_container_with_subtype/index.md). - -[CBOR's RFC 7049](https://tools.ietf.org/html/rfc7049) describes this type as: -> Major type 2: a byte string. The string's length in bytes is represented following the rules for positive integers -> (major type 0). - -[MessagePack's documentation on the bin type -family](https://github.com/msgpack/msgpack/blob/master/spec.md#bin-format-family) describes this type as: -> Bin format family stores a byte array in 2, 3, or 5 bytes of extra bytes in addition to the size of the byte array. - -[BSON's specifications](http://bsonspec.org/spec.html) describe several binary types; however, this type is intended to -represent the generic binary type which has the description: -> Generic binary subtype - This is the most commonly used binary subtype and should be the 'default' for drivers and -> tools. - -None of these impose any limitations on the internal representation other than the basic unit of storage be some type of -array whose parts are decomposable into bytes. - -The default representation of this binary format is a `#!cpp std::vector`, which is a very common way to -represent a byte array in modern C++. - -## Template parameters - -`BinaryType` -: container type to store arrays - -## Notes - -#### Default type - -The default values for `BinaryType` is `#!cpp std::vector`. - -#### Storage - -Binary Arrays are stored as pointers in a `basic_json` type. That is, for any access to array values, a pointer of the -type `#!cpp binary_t*` must be dereferenced. - -#### Notes on subtypes - -- CBOR - - Binary values are represented as byte strings. Subtypes are written as tags. - -- MessagePack - - If a subtype is given and the binary array contains exactly 1, 2, 4, 8, or 16 elements, the fixext family (fixext1, - fixext2, fixext4, fixext8) is used. For other sizes, the ext family (ext8, ext16, ext32) is used. The subtype is - then added as signed 8-bit integer. - - If no subtype is given, the bin family (bin8, bin16, bin32) is used. - -- BSON - - If a subtype is given, it is used and added as unsigned 8-bit integer. - - If no subtype is given, the generic binary subtype 0x00 is used. - -## Examples - -??? example - - The following code shows that `binary_t` is by default, a typedef to - `#!cpp nlohmann::byte_container_with_subtype>`. - - ```cpp - --8<-- "examples/binary_t.cpp" - ``` - - Output: - - ```json - --8<-- "examples/binary_t.output" - ``` - -## See also - -- [byte_container_with_subtype](../byte_container_with_subtype/index.md) - -## Version history - -- Added in version 3.8.0. Changed type of subtype to `std::uint64_t` in version 3.10.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/boolean_t.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/boolean_t.md deleted file mode 100644 index e3a7830..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/boolean_t.md +++ /dev/null @@ -1,42 +0,0 @@ -# nlohmann::basic_json::boolean_t - -```cpp -using boolean_t = BooleanType; -``` - -The type used to store JSON booleans. - -[RFC 8259](https://tools.ietf.org/html/rfc8259) implicitly describes a boolean as a type which differentiates the two -literals `#!json true` and `#!json false`. - -To store objects in C++, a type is defined by the template parameter `BooleanType` which chooses the type to use. - -## Notes - -#### Default type - -With the default values for `BooleanType` (`#!cpp bool`), the default value for `boolean_t` is `#!cpp bool`. - -#### Storage - -Boolean values are stored directly inside a `basic_json` type. - -## Examples - -??? example - - The following code shows that `boolean_t` is by default, a typedef to `#!cpp bool`. - - ```cpp - --8<-- "examples/boolean_t.cpp" - ``` - - Output: - - ```json - --8<-- "examples/boolean_t.output" - ``` - -## Version history - -- Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/cbegin.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/cbegin.md deleted file mode 100644 index 06504fe..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/cbegin.md +++ /dev/null @@ -1,41 +0,0 @@ -# nlohmann::basic_json::cbegin - -```cpp -const_iterator cbegin() const noexcept; -``` - -Returns an iterator to the first element. - -![Illustration from cppreference.com](../../images/range-begin-end.svg) - -## Return value - -iterator to the first element - -## Exception safety - -No-throw guarantee: this member function never throws exceptions. - -## Complexity - -Constant. - -## Examples - -??? example - - The following code shows an example for `cbegin()`. - - ```cpp - --8<-- "examples/cbegin.cpp" - ``` - - Output: - - ```json - --8<-- "examples/cbegin.output" - ``` - -## Version history - -- Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/cbor_tag_handler_t.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/cbor_tag_handler_t.md deleted file mode 100644 index e19c3ed..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/cbor_tag_handler_t.md +++ /dev/null @@ -1,42 +0,0 @@ -# nlohmann::basic_json::cbor_tag_handler_t - -```cpp -enum class cbor_tag_handler_t -{ - error, - ignore, - store -}; -``` - -This enumeration is used in the [`from_cbor`](from_cbor.md) function to choose how to treat tags: - -error -: throw a `parse_error` exception in case of a tag - -ignore -: ignore tags - -store -: store tagged values as binary container with subtype (for bytes 0xd8..0xdb) - -## Examples - -??? example - - The example below shows how the different values of the `cbor_tag_handler_t` influence the behavior of - [`from_cbor`](from_cbor.md) when reading a tagged byte string. - - ```cpp - --8<-- "examples/cbor_tag_handler_t.cpp" - ``` - - Output: - - ```json - --8<-- "examples/cbor_tag_handler_t.output" - ``` - -## Version history - -- Added in version 3.9.0. Added value `store` in 3.10.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/cend.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/cend.md deleted file mode 100644 index 3f3aa94..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/cend.md +++ /dev/null @@ -1,41 +0,0 @@ -# nlohmann::basic_json::cend - -```cpp -const_iterator cend() const noexcept; -``` - -Returns an iterator to one past the last element. - -![Illustration from cppreference.com](../../images/range-begin-end.svg) - -## Return value - -iterator one past the last element - -## Exception safety - -No-throw guarantee: this member function never throws exceptions. - -## Complexity - -Constant. - -## Examples - -??? example - - The following code shows an example for `cend()`. - - ```cpp - --8<-- "examples/cend.cpp" - ``` - - Output: - - ```json - --8<-- "examples/cend.output" - ``` - -## Version history - -- Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/clear.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/clear.md deleted file mode 100644 index ff04b08..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/clear.md +++ /dev/null @@ -1,58 +0,0 @@ -# nlohmann::basic_json::clear - -```cpp -void clear() noexcept; -``` - -Clears the content of a JSON value and resets it to the default value as if [`basic_json(value_t)`](basic_json.md) would -have been called with the current value type from [`type()`](type.md): - -| Value type | initial value | -|------------|----------------------| -| null | `null` | -| boolean | `false` | -| string | `""` | -| number | `0` | -| binary | An empty byte vector | -| object | `{}` | -| array | `[]` | - -Has the same effect as calling - -```.cpp -*this = basic_json(type()); -``` - -## Exception safety - -No-throw guarantee: this function never throws exceptions. - -## Complexity - -Linear in the size of the JSON value. - -## Notes - -All iterators, pointers and references related to this container are invalidated. - -## Examples - -??? example - - The example below shows the effect of `clear()` to different - JSON types. - - ```cpp - --8<-- "examples/clear.cpp" - ``` - - Output: - - ```json - --8<-- "examples/clear.output" - ``` - -## Version history - -- Added in version 1.0.0. -- Added support for binary types in version 3.8.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/contains.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/contains.md deleted file mode 100644 index ba2c3df..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/contains.md +++ /dev/null @@ -1,118 +0,0 @@ -# nlohmann::basic_json::contains - -```cpp -// (1) -bool contains(const typename object_t::key_type& key) const; - -// (2) -template -bool contains(KeyType&& key) const; - -// (3) -bool contains(const json_pointer& ptr) const; -``` - -1. Check whether an element exists in a JSON object with a key equivalent to `key`. If the element is not found or the - JSON value is not an object, `#!cpp false` is returned. -2. See 1. This overload is only available if `KeyType` is comparable with `#!cpp typename object_t::key_type` and - `#!cpp typename object_comparator_t::is_transparent` denotes a type. -3. Check whether the given JSON pointer `ptr` can be resolved in the current JSON value. - -## Template parameters - -`KeyType` -: A type for an object key other than [`json_pointer`](../json_pointer/index.md) that is comparable with - [`string_t`](string_t.md) using [`object_comparator_t`](object_comparator_t.md). - This can also be a string view (C++17). - -## Parameters - -`key` (in) -: key value to check its existence. - -`ptr` (in) -: JSON pointer to check its existence. - -## Return value - -1. `#!cpp true` if an element with specified `key` exists. If no such element with such key is found or the JSON value - is not an object, `#!cpp false` is returned. -2. See 1. -3. `#!cpp true` if the JSON pointer can be resolved to a stored value, `#!cpp false` otherwise. - -## Exception safety - -Strong exception safety: if an exception occurs, the original value stays intact. - -## Exceptions - -1. The function does not throw exceptions. -2. The function does not throw exceptions. -3. The function can throw the following exceptions: - - Throws [`parse_error.106`](../../home/exceptions.md#jsonexceptionparse_error106) if an array index begins with - `0`. - - Throws [`parse_error.109`](../../home/exceptions.md#jsonexceptionparse_error109) if an array index was not a - number. - -## Complexity - -Logarithmic in the size of the JSON object. - -## Notes - -- This method always returns `#!cpp false` when executed on a JSON type that is not an object. -- This method can be executed on any JSON value type. - -!!! info "Postconditions" - - If `#!cpp j.contains(x)` returns `#!c true` for a key or JSON pointer `x`, then it is safe to call `j[x]`. - -## Examples - -??? example "Example: (1) check with key" - - The example shows how `contains()` is used. - - ```cpp - --8<-- "examples/contains__object_t_key_type.cpp" - ``` - - Output: - - ```json - --8<-- "examples/contains__object_t_key_type.output" - ``` - -??? example "Example: (2) check with key using string_view" - - The example shows how `contains()` is used. - - ```cpp - --8<-- "examples/contains__keytype.c++17.cpp" - ``` - - Output: - - ```json - --8<-- "examples/contains__keytype.c++17.output" - ``` - -??? example "Example: (3) check with JSON pointer" - - The example shows how `contains()` is used. - - ```cpp - --8<-- "examples/contains__json_pointer.cpp" - ``` - - Output: - - ```json - --8<-- "examples/contains__json_pointer.output" - ``` - -## Version history - -1. Added in version 3.11.0. -2. Added in version 3.6.0. Extended template `KeyType` to support comparable types in version 3.11.0. -3. Added in version 3.7.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/count.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/count.md deleted file mode 100644 index 4f3a310..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/count.md +++ /dev/null @@ -1,78 +0,0 @@ -# nlohmann::basic_json::count - -```cpp -// (1) -size_type count(const typename object_t::key_type& key) const; - -// (2) -template -size_type count(KeyType&& key) const; -``` - -1. Returns the number of elements with key `key`. If `ObjectType` is the default `std::map` type, the return value will - always be `0` (`key` was not found) or `1` (`key` was found). -2. See 1. This overload is only available if `KeyType` is comparable with `#!cpp typename object_t::key_type` and - `#!cpp typename object_comparator_t::is_transparent` denotes a type. - -## Template parameters - -`KeyType` -: A type for an object key other than [`json_pointer`](../json_pointer/index.md) that is comparable with - [`string_t`](string_t.md) using [`object_comparator_t`](object_comparator_t.md). - This can also be a string view (C++17). - -## Parameters - -`key` (in) -: key value of the element to count. - -## Return value - -Number of elements with key `key`. If the JSON value is not an object, the return value will be `0`. - -## Exception safety - -Strong exception safety: if an exception occurs, the original value stays intact. - -## Complexity - -Logarithmic in the size of the JSON object. - -## Notes - -This method always returns `0` when executed on a JSON type that is not an object. - -## Examples - -??? example "Example: (1) count number of elements" - - The example shows how `count()` is used. - - ```cpp - --8<-- "examples/count__object_t_key_type.cpp" - ``` - - Output: - - ```json - --8<-- "examples/count__object_t_key_type.output" - ``` - -??? example "Example: (2) count number of elements using string_view" - - The example shows how `count()` is used. - - ```cpp - --8<-- "examples/count__keytype.c++17.cpp" - ``` - - Output: - - ```json - --8<-- "examples/count__keytype.c++17.output" - ``` - -## Version history - -1. Added in version 3.11.0. -2. Added in version 1.0.0. Changed parameter `key` type to `KeyType&&` in version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/crbegin.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/crbegin.md deleted file mode 100644 index 7af5eca..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/crbegin.md +++ /dev/null @@ -1,41 +0,0 @@ -# nlohmann::basic_json::crbegin - -```cpp -const_reverse_iterator crbegin() const noexcept; -``` - -Returns an iterator to the reverse-beginning; that is, the last element. - -![Illustration from cppreference.com](../../images/range-rbegin-rend.svg) - -## Return value - -reverse iterator to the first element - -## Exception safety - -No-throw guarantee: this member function never throws exceptions. - -## Complexity - -Constant. - -## Examples - -??? example - - The following code shows an example for `crbegin()`. - - ```cpp - --8<-- "examples/crbegin.cpp" - ``` - - Output: - - ```json - --8<-- "examples/crbegin.output" - ``` - -## Version history - -- Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/crend.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/crend.md deleted file mode 100644 index 0e6bc84..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/crend.md +++ /dev/null @@ -1,42 +0,0 @@ -# nlohmann::basic_json::crend - -```cpp -const_reverse_iterator crend() const noexcept; -``` - -Returns an iterator to the reverse-end; that is, one before the first element. This element acts as a placeholder, -attempting to access it results in undefined behavior. - -![Illustration from cppreference.com](../../images/range-rbegin-rend.svg) - -## Return value - -reverse iterator to the element following the last element - -## Exception safety - -No-throw guarantee: this member function never throws exceptions. - -## Complexity - -Constant. - -## Examples - -??? example - - The following code shows an example for `eend()`. - - ```cpp - --8<-- "examples/crend.cpp" - ``` - - Output: - - ```json - --8<-- "examples/crend.output" - ``` - -## Version history - -- Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/default_object_comparator_t.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/default_object_comparator_t.md deleted file mode 100644 index 8a237f6..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/default_object_comparator_t.md +++ /dev/null @@ -1,35 +0,0 @@ -# nlohmann::basic_json::default_object_comparator_t - -```cpp -using default_object_comparator_t = std::less; // until C++14 - -using default_object_comparator_t = std::less<>; // since C++14 -``` - -The default comparator used by [`object_t`](object_t.md). - -Since C++14 a transparent comparator is used which prevents unnecessary string construction -when looking up a key in an object. - -The actual comparator used depends on [`object_t`](object_t.md) and can be obtained via -[`object_comparator_t`](object_comparator_t.md). - -## Examples - -??? example - - The example below demonstrates the default comparator. - - ```cpp - --8<-- "examples/default_object_comparator_t.cpp" - ``` - - Output: - - ```json - --8<-- "examples/default_object_comparator_t.output" - ``` - -## Version history - -- Added in version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/diff.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/diff.md deleted file mode 100644 index 4e84068..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/diff.md +++ /dev/null @@ -1,62 +0,0 @@ -# nlohmann::basic_json::diff - -```cpp -static basic_json diff(const basic_json& source, - const basic_json& target); -``` - -Creates a [JSON Patch](http://jsonpatch.com) so that value `source` can be changed into the value `target` by calling -[`patch`](patch.md) function. - -For two JSON values `source` and `target`, the following code yields always `#!cpp true`: -```cpp -source.patch(diff(source, target)) == target; -``` - -## Parameters - -`source` (in) -: JSON value to compare from - -`target` (in) -: JSON value to compare against - -## Return value - -a JSON patch to convert the `source` to `target` - -## Exception safety - -Strong guarantee: if an exception is thrown, there are no changes in the JSON value. - -## Complexity - -Linear in the lengths of `source` and `target`. - -## Notes - -Currently, only `remove`, `add`, and `replace` operations are generated. - -## Examples - -??? example - - The following code shows how a JSON patch is created as a diff for two JSON values. - - ```cpp - --8<-- "examples/diff.cpp" - ``` - - Output: - - ```json - --8<-- "examples/diff.output" - ``` - -## See also - -- [RFC 6902 (JSON Patch)](https://tools.ietf.org/html/rfc6902) - -## Version history - -- Added in version 2.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/dump.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/dump.md deleted file mode 100644 index 41adb15..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/dump.md +++ /dev/null @@ -1,79 +0,0 @@ -# nlohmann::basic_json::dump - -```cpp -string_t dump(const int indent = -1, - const char indent_char = ' ', - const bool ensure_ascii = false, - const error_handler_t error_handler = error_handler_t::strict) const; -``` - -Serialization function for JSON values. The function tries to mimic Python's -[`json.dumps()` function](https://docs.python.org/2/library/json.html#json.dump), and currently supports its `indent` -and `ensure_ascii` parameters. - -## Parameters - -`indent` (in) -: If `indent` is nonnegative, then array elements and object members will be pretty-printed with that indent level. An - indent level of `0` will only insert newlines. `-1` (the default) selects the most compact representation. - -`indent_char` (in) -: The character to use for indentation if `indent` is greater than `0`. The default is ` ` (space). - -`ensure_ascii` (in) -: If `ensure_ascii` is true, all non-ASCII characters in the output are escaped with `\uXXXX` sequences, and the - result consists of ASCII characters only. - -`error_handler` (in) -: how to react on decoding errors; there are three possible values (see [`error_handler_t`](error_handler_t.md): - `strict` (throws and exception in case a decoding error occurs; default), `replace` (replace invalid UTF-8 sequences - with U+FFFD), and `ignore` (ignore invalid UTF-8 sequences during serialization; all bytes are copied to the output - unchanged)). - -## Return value - -string containing the serialization of the JSON value - -## Exception safety - -Strong guarantee: if an exception is thrown, there are no changes to any JSON value. - -## Exceptions - -Throws [`type_error.316`](../../home/exceptions.md#jsonexceptiontype_error316) if a string stored inside the JSON value -is not UTF-8 encoded and `error_handler` is set to `strict` - -## Complexity - -Linear. - -## Notes - -Binary values are serialized as object containing two keys: - -- "bytes": an array of bytes as integers -- "subtype": the subtype as integer or `#!json null` if the binary has no subtype - -## Examples - -??? example - - The following example shows the effect of different `indent`, `indent_char`, and `ensure_ascii` parameters to the - result of the serialization. - - ```cpp - --8<-- "examples/dump.cpp" - ``` - - Output: - - ```json - --8<-- "examples/dump.output" - ``` - -## Version history - -- Added in version 1.0.0. -- Indentation character `indent_char`, option `ensure_ascii` and exceptions added in version 3.0.0. -- Error handlers added in version 3.4.0. -- Serialization of binary values added in version 3.8.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/emplace.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/emplace.md deleted file mode 100644 index 6cc2c98..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/emplace.md +++ /dev/null @@ -1,56 +0,0 @@ -# nlohmann::basic_json::emplace - -```cpp -template -std::pair emplace(Args&& ... args); -``` - -Inserts a new element into a JSON object constructed in-place with the given `args` if there is no element with the key -in the container. If the function is called on a JSON null value, an empty object is created before appending the value -created from `args`. - -## Template parameters - -`Args` -: compatible types to create a `basic_json` object - -## Parameters - -`args` (in) -: arguments to forward to a constructor of `basic_json` - -## Return value - -a pair consisting of an iterator to the inserted element, or the already-existing element if no insertion happened, and -a `#!cpp bool` denoting whether the insertion took place. - -## Exceptions - -Throws [`type_error.311`](../../home/exceptions.md#jsonexceptiontype_error311) when called on a type other than JSON -object or `#!json null`; example: `"cannot use emplace() with number"` - -## Complexity - -Logarithmic in the size of the container, O(log(`size()`)). - -## Examples - -??? example - - The example shows how `emplace()` can be used to add elements to a JSON object. Note how the `#!json null` value was - silently converted to a JSON object. Further note how no value is added if there was already one value stored with - the same key. - - ```cpp - --8<-- "examples/emplace.cpp" - ``` - - Output: - - ```json - --8<-- "examples/emplace.output" - ``` - -## Version history - -- Since version 2.0.8. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/emplace_back.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/emplace_back.md deleted file mode 100644 index 597ad41..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/emplace_back.md +++ /dev/null @@ -1,54 +0,0 @@ -# nlohmann::basic_json::emplace_back - -```cpp -template -reference emplace_back(Args&& ... args); -``` - -Creates a JSON value from the passed parameters `args` to the end of the JSON value. If the function is called on a JSON -`#!json null` value, an empty array is created before appending the value created from `args`. - -## Template parameters - -`Args` -: compatible types to create a `basic_json` object - -## Parameters - -`args` (in) -: arguments to forward to a constructor of `basic_json` - -## Return value - -reference to the inserted element - -## Exceptions - -Throws [`type_error.311`](../../home/exceptions.md#jsonexceptiontype_error311) when called on a type other than JSON -array or `#!json null`; example: `"cannot use emplace_back() with number"` - -## Complexity - -Amortized constant. - -## Examples - -??? example - - The example shows how `emplace_back()` can be used to add elements to a JSON array. Note how the `null` value was - silently converted to a JSON array. - - ```cpp - --8<-- "examples/emplace_back.cpp" - ``` - - Output: - - ```json - --8<-- "examples/emplace_back.output" - ``` - -## Version history - -- Since version 2.0.8. -- Returns reference since 3.7.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/empty.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/empty.md deleted file mode 100644 index 26bf6e9..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/empty.md +++ /dev/null @@ -1,66 +0,0 @@ -# nlohmann::basic_json::empty - -```cpp -bool empty() const noexcept; -``` - -Checks if a JSON value has no elements (i.e. whether its [`size()`](size.md) is `0`). - -## Return value - -The return value depends on the different types and is defined as follows: - -| Value type | return value | -|------------|----------------------------------------| -| null | `#!cpp true` | -| boolean | `#!cpp false` | -| string | `#!cpp false` | -| number | `#!cpp false` | -| binary | `#!cpp false` | -| object | result of function `object_t::empty()` | -| array | result of function `array_t::empty()` | - -## Exception safety - -No-throw guarantee: this function never throws exceptions. - -## Complexity - -Constant, as long as [`array_t`](array_t.md) and [`object_t`](object_t.md) satisfy the -[Container](https://en.cppreference.com/w/cpp/named_req/Container) concept; that is, their `empty()` functions have -constant complexity. - -## Possible implementation - -```cpp -bool empty() const noexcept -{ - return size() == 0; -} -``` - -## Notes - -This function does not return whether a string stored as JSON value is empty -- it returns whether the JSON container -itself is empty which is `#!cpp false` in the case of a string. - -## Examples - -??? example - - The following code uses `empty()` to check if a JSON object contains any elements. - - ```cpp - --8<-- "examples/empty.cpp" - ``` - - Output: - - ```json - --8<-- "examples/empty.output" - ``` - -## Version history - -- Added in version 1.0.0. -- Extended to return `#!cpp false` for binary types in version 3.8.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/end.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/end.md deleted file mode 100644 index 179ce9e..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/end.md +++ /dev/null @@ -1,42 +0,0 @@ -# nlohmann::basic_json::end - -```cpp -iterator end() noexcept; -const_iterator end() const noexcept; -``` - -Returns an iterator to one past the last element. - -![Illustration from cppreference.com](../../images/range-begin-end.svg) - -## Return value - -iterator one past the last element - -## Exception safety - -No-throw guarantee: this member function never throws exceptions. - -## Complexity - -Constant. - -## Examples - -??? example - - The following code shows an example for `end()`. - - ```cpp - --8<-- "examples/end.cpp" - ``` - - Output: - - ```json - --8<-- "examples/end.output" - ``` - -## Version history - -- Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/erase.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/erase.md deleted file mode 100644 index 1187995..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/erase.md +++ /dev/null @@ -1,211 +0,0 @@ -# nlohmann::basic_json::erase - -```cpp -// (1) -iterator erase(iterator pos); -const_iterator erase(const_iterator pos); - -// (2) -iterator erase(iterator first, iterator last); -const_iterator erase(const_iterator first, const_iterator last); - -// (3) -size_type erase(const typename object_t::key_type& key); - -// (4) -template -size_type erase(KeyType&& key); - -// (5) -void erase(const size_type idx); -``` - -1. Removes an element from a JSON value specified by iterator `pos`. The iterator `pos` must be valid and - dereferenceable. Thus, the `end()` iterator (which is valid, but is not dereferenceable) cannot be used as a value for - `pos`. - - If called on a primitive type other than `#!json null`, the resulting JSON value will be `#!json null`. - -2. Remove an element range specified by `[first; last)` from a JSON value. The iterator `first` does not need to be - dereferenceable if `first == last`: erasing an empty range is a no-op. - - If called on a primitive type other than `#!json null`, the resulting JSON value will be `#!json null`. - -3. Removes an element from a JSON object by key. - -4. See 3. This overload is only available if `KeyType` is comparable with `#!cpp typename object_t::key_type` and - `#!cpp typename object_comparator_t::is_transparent` denotes a type. - -5. Removes an element from a JSON array by index. - -## Template parameters - -`KeyType` -: A type for an object key other than [`json_pointer`](../json_pointer/index.md) that is comparable with - [`string_t`](string_t.md) using [`object_comparator_t`](object_comparator_t.md). - This can also be a string view (C++17). - -## Parameters - -`pos` (in) -: iterator to the element to remove - -`first` (in) -: iterator to the beginning of the range to remove - -`last` (in) -: iterator past the end of the range to remove - -`key` (in) -: object key of the elements to remove - -`idx` (in) -: array index of the element to remove - -## Return value - -1. Iterator following the last removed element. If the iterator `pos` refers to the last element, the `end()` iterator - is returned. -2. Iterator following the last removed element. If the iterator `last` refers to the last element, the `end()` iterator - is returned. -3. Number of elements removed. If `ObjectType` is the default `std::map` type, the return value will always be `0` - (`key` was not found) or `1` (`key` was found). -4. See 3. -5. (none) - -## Exception safety - -Strong exception safety: if an exception occurs, the original value stays intact. - -## Exceptions - -1. The function can throw the following exceptions: - - Throws [`type_error.307`](../../home/exceptions.md#jsonexceptiontype_error307) if called on a `null` value; - example: `"cannot use erase() with null"` - - Throws [`invalid_iterator.202`](../../home/exceptions.md#jsonexceptioninvalid_iterator202) if called on an - iterator which does not belong to the current JSON value; example: `"iterator does not fit current value"` - - Throws [`invalid_iterator.205`](../../home/exceptions.md#jsonexceptioninvalid_iterator205) if called on a - primitive type with invalid iterator (i.e., any iterator which is not `begin()`); example: `"iterator out of - range"` -2. The function can throw the following exceptions: - - Throws [`type_error.307`](../../home/exceptions.md#jsonexceptiontype_error307) if called on a `null` value; - example: `"cannot use erase() with null"` - - Throws [`invalid_iterator.203`](../../home/exceptions.md#jsonexceptioninvalid_iterator203) if called on iterators - which does not belong to the current JSON value; example: `"iterators do not fit current value"` - - Throws [`invalid_iterator.204`](../../home/exceptions.md#jsonexceptioninvalid_iterator204) if called on a - primitive type with invalid iterators (i.e., if `first != begin()` and `last != end()`); example: `"iterators out - of range"` -3. The function can throw the following exceptions: - - Throws [`type_error.307`](../../home/exceptions.md#jsonexceptiontype_error307) when called on a type other than - JSON object; example: `"cannot use erase() with null"` -4. See 3. -5. The function can throw the following exceptions: - - Throws [`type_error.307`](../../home/exceptions.md#jsonexceptiontype_error307) when called on a type other than - JSON object; example: `"cannot use erase() with null"` - - Throws [`out_of_range.401`](../../home/exceptions.md#jsonexceptionout_of_range401) when `idx >= size()`; example: - `"array index 17 is out of range"` - -## Complexity - -1. The complexity depends on the type: - - objects: amortized constant - - arrays: linear in distance between `pos` and the end of the container - - strings and binary: linear in the length of the member - - other types: constant -2. The complexity depends on the type: - - objects: `log(size()) + std::distance(first, last)` - - arrays: linear in the distance between `first` and `last`, plus linear - in the distance between `last` and end of the container - - strings and binary: linear in the length of the member - - other types: constant -3. `log(size()) + count(key)` -4. `log(size()) + count(key)` -5. Linear in distance between `idx` and the end of the container. - -## Notes - -1. Invalidates iterators and references at or after the point of the `erase`, including the `end()` iterator. -2. (none) -3. References and iterators to the erased elements are invalidated. Other references and iterators are not affected. -4. See 3. -5. (none) - -## Examples - -??? example "Example: (1) remove element given an iterator" - - The example shows the effect of `erase()` for different JSON types using an iterator. - - ```cpp - --8<-- "examples/erase__IteratorType.cpp" - ``` - - Output: - - ```json - --8<-- "examples/erase__IteratorType.output" - ``` - -??? example "Example: (2) remove elements given an iterator range" - - The example shows the effect of `erase()` for different JSON types using an iterator range. - - ```cpp - --8<-- "examples/erase__IteratorType_IteratorType.cpp" - ``` - - Output: - - ```json - --8<-- "examples/erase__IteratorType_IteratorType.output" - ``` - -??? example "Example: (3) remove element from a JSON object given a key" - - The example shows the effect of `erase()` for different JSON types using an object key. - - ```cpp - --8<-- "examples/erase__object_t_key_type.cpp" - ``` - - Output: - - ```json - --8<-- "examples/erase__object_t_key_type.output" - ``` - -??? example "Example: (4) remove element from a JSON object given a key using string_view" - - The example shows the effect of `erase()` for different JSON types using an object key. - - ```cpp - --8<-- "examples/erase__keytype.c++17.cpp" - ``` - - Output: - - ```json - --8<-- "examples/erase__keytype.c++17.output" - ``` - -??? example "Example: (5) remove element from a JSON array given an index" - - The example shows the effect of `erase()` using an array index. - - ```cpp - --8<-- "examples/erase__size_type.cpp" - ``` - - Output: - - ```json - --8<-- "examples/erase__size_type.output" - ``` - -## Version history - -1. Added in version 1.0.0. Added support for binary types in version 3.8.0. -2. Added in version 1.0.0. Added support for binary types in version 3.8.0. -3. Added in version 1.0.0. -4. Added in version 3.11.0. -5. Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/error_handler_t.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/error_handler_t.md deleted file mode 100644 index dc32ced..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/error_handler_t.md +++ /dev/null @@ -1,42 +0,0 @@ -# nlohmann::basic_json::error_handler_t - -```cpp -enum class error_handler_t { - strict, - replace, - ignore -}; -``` - -This enumeration is used in the [`dump`](dump.md) function to choose how to treat decoding errors while serializing a -`basic_json` value. Three values are differentiated: - -strict -: throw a `type_error` exception in case of invalid UTF-8 - -replace -: replace invalid UTF-8 sequences with U+FFFD (� REPLACEMENT CHARACTER) - -ignore -: ignore invalid UTF-8 sequences; all bytes are copied to the output unchanged - -## Examples - -??? example - - The example below shows how the different values of the `error_handler_t` influence the behavior of - [`dump`](dump.md) when reading serializing an invalid UTF-8 sequence. - - ```cpp - --8<-- "examples/error_handler_t.cpp" - ``` - - Output: - - ```json - --8<-- "examples/error_handler_t.output" - ``` - -## Version history - -- Added in version 3.4.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/exception.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/exception.md deleted file mode 100644 index b492666..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/exception.md +++ /dev/null @@ -1,75 +0,0 @@ -# nlohmann::basic_json::exception - -```cpp -class exception : public std::exception; -``` - -This class is an extension of [`std::exception`](https://en.cppreference.com/w/cpp/error/exception) objects with a -member `id` for exception ids. It is used as the base class for all exceptions thrown by the `basic_json` class. This -class can hence be used as "wildcard" to catch exceptions, see example below. - -```plantuml -std::exception <|-- basic_json::exception -basic_json::exception <|-- basic_json::parse_error -basic_json::exception <|-- basic_json::invalid_iterator -basic_json::exception <|-- basic_json::type_error -basic_json::exception <|-- basic_json::out_of_range -basic_json::exception <|-- basic_json::other_error - -interface std::exception {} - -class basic_json::exception #FFFF00 { - + const int id - + const char* what() const -} - -class basic_json::parse_error { - + const std::size_t byte -} -``` - -Subclasses: - -- [`parse_error`](parse_error.md) for exceptions indicating a parse error -- [`invalid_iterator`](invalid_iterator.md) for exceptions indicating errors with iterators -- [`type_error`](type_error.md) for exceptions indicating executing a member function with a wrong type -- [`out_of_range`](out_of_range.md) for exceptions indicating access out of the defined range -- [`other_error`](other_error.md) for exceptions indicating other library errors - -## Member functions - -- **what** - returns explanatory string - -## Member variables - -- **id** - the id of the exception - -## Notes - -To have nothrow-copy-constructible exceptions, we internally use `std::runtime_error` which can cope with -arbitrary-length error messages. Intermediate strings are built with static functions and then passed to the actual -constructor. - -## Examples - -??? example - - The following code shows how arbitrary library exceptions can be caught. - - ```cpp - --8<-- "examples/exception.cpp" - ``` - - Output: - - ```json - --8<-- "examples/exception.output" - ``` - -## See also - -[List of exceptions](127.0.0.1:8000/home/exceptions/) - -## Version history - -- Since version 3.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/find.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/find.md deleted file mode 100644 index c643507..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/find.md +++ /dev/null @@ -1,86 +0,0 @@ -# nlohmann::basic_json::find - -```cpp -// (1) -iterator find(const typename object_t::key_type& key); -const_iterator find(const typename object_t::key_type& key) const; - -// (2) -template -iterator find(KeyType&& key); -template -const_iterator find(KeyType&& key) const; -``` - -1. Finds an element in a JSON object with a key equivalent to `key`. If the element is not found or the - JSON value is not an object, `end()` is returned. -2. See 1. This overload is only available if `KeyType` is comparable with `#!cpp typename object_t::key_type` and - `#!cpp typename object_comparator_t::is_transparent` denotes a type. - -## Template parameters - -`KeyType` -: A type for an object key other than [`json_pointer`](../json_pointer/index.md) that is comparable with - [`string_t`](string_t.md) using [`object_comparator_t`](object_comparator_t.md). - This can also be a string view (C++17). - -## Parameters - -`key` (in) -: key value of the element to search for. - -## Return value - -Iterator to an element with a key equivalent to `key`. If no such element is found or the JSON value is not an object, -a past-the-end iterator (see `end()`) is returned. - -## Exception safety - -Strong exception safety: if an exception occurs, the original value stays intact. - -## Complexity - -Logarithmic in the size of the JSON object. - -## Notes - -This method always returns `end()` when executed on a JSON type that is not an object. - -## Examples - -??? example "Example: (1) find object element by key" - - The example shows how `find()` is used. - - ```cpp - --8<-- "examples/find__object_t_key_type.cpp" - ``` - - Output: - - ```json - --8<-- "examples/find__object_t_key_type.output" - ``` - -??? example "Example: (2) find object element by key using string_view" - - The example shows how `find()` is used. - - ```cpp - --8<-- "examples/find__keytype.c++17.cpp" - ``` - - Output: - - ```json - --8<-- "examples/find__keytype.c++17.output" - ``` - -## See also - -- [contains](contains.md) checks whether a key exists - -## Version history - -1. Added in version 3.11.0. -2. Added in version 1.0.0. Changed to support comparable types in version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/flatten.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/flatten.md deleted file mode 100644 index 8703e86..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/flatten.md +++ /dev/null @@ -1,50 +0,0 @@ -# nlohmann::basic_json::flatten - -```cpp -basic_json flatten() const; -``` - -The function creates a JSON object whose keys are JSON pointers (see [RFC 6901](https://tools.ietf.org/html/rfc6901)) -and whose values are all primitive (see [`is_primitive()`](is_primitive.md) for more information). The original JSON -value can be restored using the [`unflatten()`](unflatten.md) function. - -## Return value - -an object that maps JSON pointers to primitive values - -## Exception safety - -Strong exception safety: if an exception occurs, the original value stays intact. - -## Complexity - -Linear in the size the JSON value. - -## Notes - -Empty objects and arrays are flattened to `#!json null` and will not be reconstructed correctly by the -[`unflatten()`](unflatten.md) function. - -## Examples - -??? example - - The following code shows how a JSON object is flattened to an object whose keys consist of JSON pointers. - - ```cpp - --8<-- "examples/flatten.cpp" - ``` - - Output: - - ```json - --8<-- "examples/flatten.output" - ``` - -## See also - -- [unflatten](unflatten.md) the reverse function - -## Version history - -- Added in version 2.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/from_bjdata.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/from_bjdata.md deleted file mode 100644 index 3c5eeb3..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/from_bjdata.md +++ /dev/null @@ -1,93 +0,0 @@ -# nlohmann::basic_json::from_bjdata - -```cpp -// (1) -template -static basic_json from_bjdata(InputType&& i, - const bool strict = true, - const bool allow_exceptions = true); -// (2) -template -static basic_json from_bjdata(IteratorType first, IteratorType last, - const bool strict = true, - const bool allow_exceptions = true); -``` - -Deserializes a given input to a JSON value using the BJData (Binary JData) serialization format. - -1. Reads from a compatible input. -2. Reads from an iterator range. - -The exact mapping and its limitations is described on a [dedicated page](../../features/binary_formats/bjdata.md). - -## Template parameters - -`InputType` -: A compatible input, for instance: - - - an `std::istream` object - - a `FILE` pointer - - a C-style array of characters - - a pointer to a null-terminated string of single byte characters - - an object `obj` for which `begin(obj)` and `end(obj)` produces a valid pair of iterators. - -`IteratorType` -: a compatible iterator type - -## Parameters - -`i` (in) -: an input in BJData format convertible to an input adapter - -`first` (in) -: iterator to start of the input - -`last` (in) -: iterator to end of the input - -`strict` (in) -: whether to expect the input to be consumed until EOF (`#!cpp true` by default) - -`allow_exceptions` (in) -: whether to throw exceptions in case of a parse error (optional, `#!cpp true` by default) - -## Return value - -deserialized JSON value; in case of a parse error and `allow_exceptions` set to `#!cpp false`, the return value will be -`value_t::discarded`. The latter can be checked with [`is_discarded`](is_discarded.md). - -## Exception safety - -Strong guarantee: if an exception is thrown, there are no changes in the JSON value. - -## Exceptions - -- Throws [parse_error.110](../../home/exceptions.md#jsonexceptionparse_error110) if the given input ends prematurely or - the end of file was not reached when `strict` was set to true -- Throws [parse_error.112](../../home/exceptions.md#jsonexceptionparse_error112) if a parse error occurs -- Throws [parse_error.113](../../home/exceptions.md#jsonexceptionparse_error113) if a string could not be parsed - successfully - -## Complexity - -Linear in the size of the input. - -## Examples - -??? example - - The example shows the deserialization of a byte vector in BJData format to a JSON value. - - ```cpp - --8<-- "examples/from_bjdata.cpp" - ``` - - Output: - - ```json - --8<-- "examples/from_bjdata.output" - ``` - -## Version history - -- Added in version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/from_bson.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/from_bson.md deleted file mode 100644 index 7754937..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/from_bson.md +++ /dev/null @@ -1,110 +0,0 @@ -# nlohmann::basic_json::from_bson - -```cpp -// (1) -template -static basic_json from_bson(InputType&& i, - const bool strict = true, - const bool allow_exceptions = true); -// (2) -template -static basic_json from_bson(IteratorType first, IteratorType last, - const bool strict = true, - const bool allow_exceptions = true); -``` - -Deserializes a given input to a JSON value using the BSON (Binary JSON) serialization format. - -1. Reads from a compatible input. -2. Reads from an iterator range. - -The exact mapping and its limitations is described on a [dedicated page](../../features/binary_formats/bson.md). - -## Template parameters - -`InputType` -: A compatible input, for instance: - - - an `std::istream` object - - a `FILE` pointer - - a C-style array of characters - - a pointer to a null-terminated string of single byte characters - - an object `obj` for which `begin(obj)` and `end(obj)` produces a valid pair of iterators. - -`IteratorType` -: a compatible iterator type - -## Parameters - -`i` (in) -: an input in BSON format convertible to an input adapter - -`first` (in) -: iterator to start of the input - -`last` (in) -: iterator to end of the input - -`strict` (in) -: whether to expect the input to be consumed until EOF (`#!cpp true` by default) - -`allow_exceptions` (in) -: whether to throw exceptions in case of a parse error (optional, `#!cpp true` by default) - -## Return value - -deserialized JSON value; in case of a parse error and `allow_exceptions` set to `#!cpp false`, the return value will be -`value_t::discarded`. The latter can be checked with [`is_discarded`](is_discarded.md). - -## Exception safety - -Strong guarantee: if an exception is thrown, there are no changes in the JSON value. - -## Exceptions - -Throws [`parse_error.114`](../../home/exceptions.md#jsonexceptionparse_error114) if an unsupported BSON record type is -encountered. - -## Complexity - -Linear in the size of the input. - -## Examples - -??? example - - The example shows the deserialization of a byte vector in BSON format to a JSON value. - - ```cpp - --8<-- "examples/from_bson.cpp" - ``` - - Output: - - ```json - --8<-- "examples/from_bson.output" - ``` - -## See also - -- [BSON specification](http://bsonspec.org/spec.html) -- [to_bson](to_bson.md) for the analogous serialization -- [from_cbor](from_cbor.md) for the related CBOR format -- [from_msgpack](from_msgpack.md) for the related MessagePack format -- [from_ubjson](from_ubjson.md) for the related UBJSON format - -## Version history - -- Added in version 3.4.0. - -!!! warning "Deprecation" - - - Overload (2) replaces calls to `from_bson` with a pointer and a length as first two parameters, which has been - deprecated in version 3.8.0. This overload will be removed in version 4.0.0. Please replace all calls like - `#!cpp from_bson(ptr, len, ...);` with `#!cpp from_bson(ptr, ptr+len, ...);`. - - Overload (2) replaces calls to `from_bson` with a pair of iterators as their first parameter, which has been - deprecated in version 3.8.0. This overload will be removed in version 4.0.0. Please replace all calls like - `#!cpp from_bson({ptr, ptr+len}, ...);` with `#!cpp from_bson(ptr, ptr+len, ...);`. - - You should be warned by your compiler with a `-Wdeprecated-declarations` warning if you are using a deprecated - function. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/from_cbor.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/from_cbor.md deleted file mode 100644 index 3aa57b9..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/from_cbor.md +++ /dev/null @@ -1,117 +0,0 @@ -# nlohmann::basic_json::from_cbor - -```cpp -// (1) -template -static basic_json from_cbor(InputType&& i, - const bool strict = true, - const bool allow_exceptions = true, - const cbor_tag_handler_t tag_handler = cbor_tag_handler_t::error); - -// (2) -template -static basic_json from_cbor(IteratorType first, IteratorType last, - const bool strict = true, - const bool allow_exceptions = true, - const cbor_tag_handler_t tag_handler = cbor_tag_handler_t::error); -``` - -Deserializes a given input to a JSON value using the CBOR (Concise Binary Object Representation) serialization format. - -1. Reads from a compatible input. -2. Reads from an iterator range. - -The exact mapping and its limitations is described on a [dedicated page](../../features/binary_formats/cbor.md). - -## Template parameters - -`InputType` -: A compatible input, for instance: - - - an `std::istream` object - - a `FILE` pointer - - a C-style array of characters - - a pointer to a null-terminated string of single byte characters - - an object `obj` for which `begin(obj)` and `end(obj)` produces a valid pair of iterators. - -`IteratorType` -: a compatible iterator type - -## Parameters - -`i` (in) -: an input in CBOR format convertible to an input adapter - -`first` (in) -: iterator to start of the input - -`last` (in) -: iterator to end of the input - -`strict` (in) -: whether to expect the input to be consumed until EOF (`#!cpp true` by default) - -`allow_exceptions` (in) -: whether to throw exceptions in case of a parse error (optional, `#!cpp true` by default) - -`tag_handler` (in) -: how to treat CBOR tags (optional, `error` by default); see [`cbor_tag_handler_t`](cbor_tag_handler_t.md) for more - information - -## Return value - -deserialized JSON value; in case of a parse error and `allow_exceptions` set to `#!cpp false`, the return value will be -`value_t::discarded`. The latter can be checked with [`is_discarded`](is_discarded.md). - -## Exception safety - -Strong guarantee: if an exception is thrown, there are no changes in the JSON value. - -## Exceptions - -- Throws [parse_error.110](../../home/exceptions.md#jsonexceptionparse_error110) if the given input ends prematurely or - the end of file was not reached when `strict` was set to true -- Throws [parse_error.112](../../home/exceptions.md#jsonexceptionparse_error112) if unsupported features from CBOR were - used in the given input or if the input is not valid CBOR -- Throws [parse_error.113](../../home/exceptions.md#jsonexceptionparse_error113) if a string was expected as map key, - but not found - -## Complexity - -Linear in the size of the input. - -## Examples - -??? example - - The example shows the deserialization of a byte vector in CBOR format to a JSON value. - - ```cpp - --8<-- "examples/from_cbor.cpp" - ``` - - Output: - - ```json - --8<-- "examples/from_cbor.output" - ``` - -## Version history - -- Added in version 2.0.9. -- Parameter `start_index` since version 2.1.1. -- Changed to consume input adapters, removed `start_index` parameter, and added `strict` parameter in version 3.0.0. -- Added `allow_exceptions` parameter in version 3.2.0. -- Added `tag_handler` parameter in version 3.9.0. - -!!! warning "Deprecation" - - - Overload (2) replaces calls to `from_cbor` with a pointer and a length as first two parameters, which has been - deprecated in version 3.8.0. This overload will be removed in version 4.0.0. Please replace all calls like - `#!cpp from_cbor(ptr, len, ...);` with `#!cpp from_cbor(ptr, ptr+len, ...);`. - - Overload (2) replaces calls to `from_cbor` with a pair of iterators as their first parameter, which has been - deprecated in version 3.8.0. This overload will be removed in version 4.0.0. Please replace all calls like - `#!cpp from_cbor({ptr, ptr+len}, ...);` with `#!cpp from_cbor(ptr, ptr+len, ...);`. - - You should be warned by your compiler with a `-Wdeprecated-declarations` warning if you are using a deprecated - function. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/from_msgpack.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/from_msgpack.md deleted file mode 100644 index 117c386..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/from_msgpack.md +++ /dev/null @@ -1,109 +0,0 @@ -# nlohmann::basic_json::from_msgpack - -```cpp -// (1) -template -static basic_json from_msgpack(InputType&& i, - const bool strict = true, - const bool allow_exceptions = true); -// (2) -template -static basic_json from_msgpack(IteratorType first, IteratorType last, - const bool strict = true, - const bool allow_exceptions = true); -``` - -Deserializes a given input to a JSON value using the MessagePack serialization format. - -1. Reads from a compatible input. -2. Reads from an iterator range. - -The exact mapping and its limitations is described on a [dedicated page](../../features/binary_formats/messagepack.md). - -## Template parameters - -`InputType` -: A compatible input, for instance: - - - an `std::istream` object - - a `FILE` pointer - - a C-style array of characters - - a pointer to a null-terminated string of single byte characters - - an object `obj` for which `begin(obj)` and `end(obj)` produces a valid pair of iterators. - -`IteratorType` -: a compatible iterator type - -## Parameters - -`i` (in) -: an input in MessagePack format convertible to an input adapter - -`first` (in) -: iterator to start of the input - -`last` (in) -: iterator to end of the input - -`strict` (in) -: whether to expect the input to be consumed until EOF (`#!cpp true` by default) - -`allow_exceptions` (in) -: whether to throw exceptions in case of a parse error (optional, `#!cpp true` by default) - -## Return value - -deserialized JSON value; in case of a parse error and `allow_exceptions` set to `#!cpp false`, the return value will be -`value_t::discarded`. The latter can be checked with [`is_discarded`](is_discarded.md). - -## Exception safety - -Strong guarantee: if an exception is thrown, there are no changes in the JSON value. - -## Exceptions - -- Throws [parse_error.110](../../home/exceptions.md#jsonexceptionparse_error110) if the given input ends prematurely or - the end of file was not reached when `strict` was set to true -- Throws [parse_error.112](../../home/exceptions.md#jsonexceptionparse_error112) if unsupported features from - MessagePack were used in the given input or if the input is not valid MessagePack -- Throws [parse_error.113](../../home/exceptions.md#jsonexceptionparse_error113) if a string was expected as map key, - but not found - -## Complexity - -Linear in the size of the input. - -## Examples - -??? example - - The example shows the deserialization of a byte vector in MessagePack format to a JSON value. - - ```cpp - --8<-- "examples/from_msgpack.cpp" - ``` - - Output: - - ```json - --8<-- "examples/from_msgpack.output" - ``` - -## Version history - -- Added in version 2.0.9. -- Parameter `start_index` since version 2.1.1. -- Changed to consume input adapters, removed `start_index` parameter, and added `strict` parameter in version 3.0.0. -- Added `allow_exceptions` parameter in version 3.2.0. - -!!! warning "Deprecation" - - - Overload (2) replaces calls to `from_msgpack` with a pointer and a length as first two parameters, which has been - deprecated in version 3.8.0. This overload will be removed in version 4.0.0. Please replace all calls like - `#!cpp from_msgpack(ptr, len, ...);` with `#!cpp from_msgpack(ptr, ptr+len, ...);`. - - Overload (2) replaces calls to `from_cbor` with a pair of iterators as their first parameter, which has been - deprecated in version 3.8.0. This overload will be removed in version 4.0.0. Please replace all calls like - `#!cpp from_msgpack({ptr, ptr+len}, ...);` with `#!cpp from_msgpack(ptr, ptr+len, ...);`. - - You should be warned by your compiler with a `-Wdeprecated-declarations` warning if you are using a deprecated - function. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/from_ubjson.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/from_ubjson.md deleted file mode 100644 index 08117e8..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/from_ubjson.md +++ /dev/null @@ -1,106 +0,0 @@ -# nlohmann::basic_json::from_ubjson - -```cpp -// (1) -template -static basic_json from_ubjson(InputType&& i, - const bool strict = true, - const bool allow_exceptions = true); -// (2) -template -static basic_json from_ubjson(IteratorType first, IteratorType last, - const bool strict = true, - const bool allow_exceptions = true); -``` - -Deserializes a given input to a JSON value using the UBJSON (Universal Binary JSON) serialization format. - -1. Reads from a compatible input. -2. Reads from an iterator range. - -The exact mapping and its limitations is described on a [dedicated page](../../features/binary_formats/ubjson.md). - -## Template parameters - -`InputType` -: A compatible input, for instance: - - - an `std::istream` object - - a `FILE` pointer - - a C-style array of characters - - a pointer to a null-terminated string of single byte characters - - an object `obj` for which `begin(obj)` and `end(obj)` produces a valid pair of iterators. - -`IteratorType` -: a compatible iterator type - -## Parameters - -`i` (in) -: an input in UBJSON format convertible to an input adapter - -`first` (in) -: iterator to start of the input - -`last` (in) -: iterator to end of the input - -`strict` (in) -: whether to expect the input to be consumed until EOF (`#!cpp true` by default) - -`allow_exceptions` (in) -: whether to throw exceptions in case of a parse error (optional, `#!cpp true` by default) - -## Return value - -deserialized JSON value; in case of a parse error and `allow_exceptions` set to `#!cpp false`, the return value will be -`value_t::discarded`. The latter can be checked with [`is_discarded`](is_discarded.md). - -## Exception safety - -Strong guarantee: if an exception is thrown, there are no changes in the JSON value. - -## Exceptions - -- Throws [parse_error.110](../../home/exceptions.md#jsonexceptionparse_error110) if the given input ends prematurely or - the end of file was not reached when `strict` was set to true -- Throws [parse_error.112](../../home/exceptions.md#jsonexceptionparse_error112) if a parse error occurs -- Throws [parse_error.113](../../home/exceptions.md#jsonexceptionparse_error113) if a string could not be parsed - successfully - -## Complexity - -Linear in the size of the input. - -## Examples - -??? example - - The example shows the deserialization of a byte vector in UBJSON format to a JSON value. - - ```cpp - --8<-- "examples/from_ubjson.cpp" - ``` - - Output: - - ```json - --8<-- "examples/from_ubjson.output" - ``` - -## Version history - -- Added in version 3.1.0. -- Added `allow_exceptions` parameter in version 3.2.0. - -!!! warning "Deprecation" - - - Overload (2) replaces calls to `from_ubjson` with a pointer and a length as first two parameters, which has been - deprecated in version 3.8.0. This overload will be removed in version 4.0.0. Please replace all calls like - `#!cpp from_ubjson(ptr, len, ...);` with `#!cpp from_ubjson(ptr, ptr+len, ...);`. - - Overload (2) replaces calls to `from_ubjson` with a pair of iterators as their first parameter, which has been - deprecated in version 3.8.0. This overload will be removed in version 4.0.0. Please replace all calls like - `#!cpp from_ubjson({ptr, ptr+len}, ...);` with `#!cpp from_ubjson(ptr, ptr+len, ...);`. - - You should be warned by your compiler with a `-Wdeprecated-declarations` warning if you are using a deprecated - function. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/front.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/front.md deleted file mode 100644 index e258c36..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/front.md +++ /dev/null @@ -1,58 +0,0 @@ -# nlohmann::basic_json::front - -```cpp -reference front(); -const_reference front() const; -``` - -Returns a reference to the first element in the container. For a JSON container `#!cpp c`, the expression -`#!cpp c.front()` is equivalent to `#!cpp *c.begin()`. - -## Return value - -In case of a structured type (array or object), a reference to the first element is returned. In case of number, string, -boolean, or binary values, a reference to the value is returned. - -## Exception safety - -Strong guarantee: if an exception is thrown, there are no changes in the JSON value. - -## Exceptions - -If the JSON value is `#!json null`, exception -[`invalid_iterator.214`](../../home/exceptions.md#jsonexceptioninvalid_iterator214) is thrown. - -## Complexity - -Constant. - -## Notes - -!!! info "Precondition" - - The array or object must not be empty. Calling `front` on an empty array or object yields undefined behavior. - -## Examples - -??? example - - The following code shows an example for `front()`. - - ```cpp - --8<-- "examples/front.cpp" - ``` - - Output: - - ```json - --8<-- "examples/front.output" - ``` - -## See also - -- [back](back.md) to access the last element - -## Version history - -- Added in version 1.0.0. -- Adjusted code to return reference to binary values in version 3.8.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/get.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/get.md deleted file mode 100644 index 96fc221..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/get.md +++ /dev/null @@ -1,136 +0,0 @@ -# nlohmann::basic_json::get - -```cpp -// (1) -template -ValueType get() const noexcept( - noexcept(JSONSerializer::from_json( - std::declval(), std::declval()))); - -// (2) -template -BasicJsonType get() const; - -// (3) -template -PointerType get_ptr(); - -template -constexpr const PointerType get_ptr() const noexcept; -``` - -1. Explicit type conversion between the JSON value and a compatible value which is - [CopyConstructible](https://en.cppreference.com/w/cpp/named_req/CopyConstructible) and - [DefaultConstructible](https://en.cppreference.com/w/cpp/named_req/DefaultConstructible). The value is converted by - calling the `json_serializer` `from_json()` method. - - The function is equivalent to executing - ```cpp - ValueType ret; - JSONSerializer::from_json(*this, ret); - return ret; - ``` - - This overload is chosen if: - - - `ValueType` is not `basic_json`, - - `json_serializer` has a `from_json()` method of the form - `void from_json(const basic_json&, ValueType&)`, and - - `json_serializer` does not have a `from_json()` method of the form - `ValueType from_json(const basic_json&)` - - If the type is **not** [CopyConstructible](https://en.cppreference.com/w/cpp/named_req/CopyConstructible) and - **not** [DefaultConstructible](https://en.cppreference.com/w/cpp/named_req/DefaultConstructible), the value is - converted by calling the `json_serializer` `from_json()` method. - - The function is then equivalent to executing - ```cpp - return JSONSerializer::from_json(*this); - ``` - - This overload is chosen if: - - - `ValueType` is not `basic_json` and - - `json_serializer` has a `from_json()` method of the form - `ValueType from_json(const basic_json&)` - - If `json_serializer` has both overloads of `from_json()`, the latter one is chosen. - -2. Overload for `basic_json` specializations. The function is equivalent to executing - ```cpp - return *this; - ``` - -3. Explicit pointer access to the internally stored JSON value. No copies are made. - -## Template parameters - -`ValueType` -: the value type to return - -`BasicJsonType` -: a specialization of `basic_json` - -`PointerType` -: pointer type; must be a pointer to [`array_t`](array_t.md), [`object_t`](object_t.md), [`string_t`](string_t.md), - [`boolean_t`](boolean_t.md), [`number_integer_t`](number_integer_t.md), or - [`number_unsigned_t`](number_unsigned_t.md), [`number_float_t`](number_float_t.md), or [`binary_t`](binary_t.md). - Other types will not compile. - -## Return value - -1. copy of the JSON value, converted to `ValueType` -2. a copy of `#!cpp *this`, converted into `BasicJsonType` -3. pointer to the internally stored JSON value if the requested pointer type fits to the JSON value; `#!cpp nullptr` - otherwise - -## Exceptions - -Depends on what `json_serializer` `from_json()` method throws - -## Notes - -!!! danger "Undefined behavior" - - Writing data to the pointee (overload 3) of the result yields an undefined state. - -## Examples - -??? example - - The example below shows several conversions from JSON values - to other types. There a few things to note: (1) Floating-point numbers can - be converted to integers, (2) A JSON array can be converted to a standard - `std::vector`, (3) A JSON object can be converted to C++ - associative containers such as `std::unordered_map`. - - ```cpp - --8<-- "examples/get__ValueType_const.cpp" - ``` - - Output: - - ```json - --8<-- "examples/get__ValueType_const.output" - ``` - -??? example - - The example below shows how pointers to internal values of a JSON value can be requested. Note that no type - conversions are made and a `#cpp nullptr` is returned if the value and the requested pointer type does not match. - - ```cpp - --8<-- "examples/get__PointerType.cpp" - ``` - - Output: - - ```json - --8<-- "examples/get__PointerType.output" - ``` - -## Version history - -1. Since version 2.1.0. -2. Since version 2.1.0. Extended to work with other specializations of `basic_json` in version 3.2.0. -3. Since version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/get_allocator.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/get_allocator.md deleted file mode 100644 index 07a4d84..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/get_allocator.md +++ /dev/null @@ -1,31 +0,0 @@ -# nlohmann::basic_json::get_allocator - -```cpp -static allocator_type get_allocator(); -``` - -Returns the allocator associated with the container. - -## Return value - -associated allocator - -## Examples - -??? example - - The example shows how `get_allocator()` is used to created `json` values. - - ```cpp - --8<-- "examples/get_allocator.cpp" - ``` - - Output: - - ```json - --8<-- "examples/get_allocator.output" - ``` - -## Version history - -- Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/get_binary.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/get_binary.md deleted file mode 100644 index a910f3a..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/get_binary.md +++ /dev/null @@ -1,45 +0,0 @@ -# nlohmann::basic_json::get_binary - -```cpp -binary_t& get_binary(); - -const binary_t& get_binary() const; -``` - -Returns a reference to the stored binary value. - -## Return value - -Reference to binary value. - -## Exception safety - -Strong exception safety: if an exception occurs, the original value stays intact. - -## Exceptions - -Throws [`type_error.302`](../../home/exceptions.md#jsonexceptiontype_error302) if the value is not binary - -## Complexity - -Constant. - -## Examples - -??? example - - The following code shows how to query a binary value. - - ```cpp - --8<-- "examples/get_binary.cpp" - ``` - - Output: - - ```json - --8<-- "examples/get_binary.output" - ``` - -## Version history - -- Added in version 3.8.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/get_ptr.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/get_ptr.md deleted file mode 100644 index 2441e11..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/get_ptr.md +++ /dev/null @@ -1,60 +0,0 @@ -# nlohmann::basic_json::get_ptr - -```cpp -template -PointerType get_ptr() noexcept; - -template -constexpr const PointerType get_ptr() const noexcept; -``` - -Implicit pointer access to the internally stored JSON value. No copies are made. - -## Template parameters - -`PointerType` -: pointer type; must be a pointer to [`array_t`](array_t.md), [`object_t`](object_t.md), [`string_t`](string_t.md), - [`boolean_t`](boolean_t.md), [`number_integer_t`](number_integer_t.md), or - [`number_unsigned_t`](number_unsigned_t.md), [`number_float_t`](number_float_t.md), or [`binary_t`](binary_t.md). - Other types will not compile. - -## Return value - -pointer to the internally stored JSON value if the requested pointer type fits to the JSON value; `#!cpp nullptr` -otherwise - -## Exception safety - -No-throw guarantee: this function never throws exceptions. - -## Complexity - -Constant. - -## Notes - -!!! danger "Undefined behavior" - - Writing data to the pointee of the result yields an undefined state. - -## Examples - -??? example - - The example below shows how pointers to internal values of a JSON value can be requested. Note that no type - conversions are made and a `#!cpp nullptr` is returned if the value and the requested pointer type does not match. - - ```cpp - --8<-- "examples/get_ptr.cpp" - ``` - - Output: - - ```json - --8<-- "examples/get_ptr.output" - ``` - -## Version history - -- Added in version 1.0.0. -- Extended to binary types in version 3.8.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/get_ref.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/get_ref.md deleted file mode 100644 index b121974..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/get_ref.md +++ /dev/null @@ -1,64 +0,0 @@ -# nlohmann::basic_json::get_ref - -```cpp -template -ReferenceType get_ref(); - -template -const ReferenceType get_ref() const; -``` - -Implicit reference access to the internally stored JSON value. No copies are made. - -## Template parameters - -`ReferenceType` -: reference type; must be a reference to [`array_t`](array_t.md), [`object_t`](object_t.md), - [`string_t`](string_t.md), [`boolean_t`](boolean_t.md), [`number_integer_t`](number_integer_t.md), or - [`number_unsigned_t`](number_unsigned_t.md), [`number_float_t`](number_float_t.md), or [`binary_t`](binary_t.md). - Enforced by a static assertion. - -## Return value - -reference to the internally stored JSON value if the requested reference type fits to the JSON value; throws -[`type_error.303`](../../home/exceptions.md#jsonexceptiontype_error303) otherwise - -## Exception safety - -Strong exception safety: if an exception occurs, the original value stays intact. - -## Exceptions - -Throws [`type_error.303`](../../home/exceptions.md#jsonexceptiontype_error303) if the requested reference type does not -match the stored JSON value type; example: `"incompatible ReferenceType for get_ref, actual type is binary"`. - -## Complexity - -Constant. - -## Notes - -!!! danger "Undefined behavior" - - Writing data to the referee of the result yields an undefined state. - -## Examples - -??? example - - The example shows several calls to `get_ref()`. - - ```cpp - --8<-- "examples/get_ref.cpp" - ``` - - Output: - - ```json - --8<-- "examples/get_ref.output" - ``` - -## Version history - -- Added in version 1.1.0. -- Extended to binary types in version 3.8.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/get_to.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/get_to.md deleted file mode 100644 index 6af6d21..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/get_to.md +++ /dev/null @@ -1,58 +0,0 @@ -# nlohmann::basic_json::get_to - -```cpp -template -ValueType& get_to(ValueType& v) const noexcept( - noexcept(JSONSerializer::from_json( - std::declval(), v))); -``` - -Explicit type conversion between the JSON value and a compatible value. The value is filled into the input parameter by -calling the `json_serializer` `from_json()` method. - -The function is equivalent to executing -```cpp -ValueType v; -JSONSerializer::from_json(*this, v); -``` - -This overload is chosen if: - -- `ValueType` is not `basic_json`, -- `json_serializer` has a `from_json()` method of the form `void from_json(const basic_json&, ValueType&)` - -## Template parameters - -`ValueType` -: the value type to return - -## Return value - -the input parameter, allowing chaining calls - -## Exceptions - -Depends on what `json_serializer` `from_json()` method throws - -## Examples - -??? example - - The example below shows several conversions from JSON values to other types. There a few things to note: (1) - Floating-point numbers can be converted to integers, (2) A JSON array can be converted to a standard - `#!cpp std::vector`, (3) A JSON object can be converted to C++ associative containers such as - `#cpp std::unordered_map`. - - ```cpp - --8<-- "examples/get_to.cpp" - ``` - - Output: - - ```json - --8<-- "examples/get_to.output" - ``` - -## Version history - -- Since version 3.3.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/index.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/index.md deleted file mode 100644 index e474b66..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/index.md +++ /dev/null @@ -1,321 +0,0 @@ -# nlohmann::basic_json - -Defined in header `` - -```cpp -template< - template class ObjectType = std::map, - template class ArrayType = std::vector, - class StringType = std::string, - class BooleanType = bool, - class NumberIntegerType = std::int64_t, - class NumberUnsignedType = std::uint64_t, - class NumberFloatType = double, - template class AllocatorType = std::allocator, - template class JSONSerializer = adl_serializer, - class BinaryType = std::vector -> -class basic_json; -``` - -## Template parameters - -| Template parameter | Description | Derived type | -|----------------------|---------------------------------------------------------------------------|---------------------------------------------| -| `ObjectType` | type for JSON objects | [`object_t`](object_t.md) | -| `ArrayType` | type for JSON arrays | [`array_t`](array_t.md) | -| `StringType` | type for JSON strings and object keys | [`string_t`](string_t.md) | -| `BooleanType` | type for JSON booleans | [`boolean_t`](boolean_t.md) | -| `NumberIntegerType` | type for JSON integer numbers | [`number_integer_t`](number_integer_t.md) | -| `NumberUnsignedType` | type for JSON unsigned integer numbers | [`number_unsigned_t`](number_unsigned_t.md) | -| `NumberFloatType` | type for JSON floating-point numbers | [`number_float_t`](number_float_t.md) | -| `AllocatorType` | type of the allocator to use | | -| `JSONSerializer` | the serializer to resolve internal calls to `to_json()` and `from_json()` | [`json_serializer`](json_serializer.md) | -| `BinaryType` | type for binary arrays | [`binary_t`](binary_t.md) | - -## Specializations - -- [**json**](../json.md) - default specialization -- [**ordered_json**](../ordered_json.md) - specialization that maintains the insertion order of object keys - -## Iterator invalidation - -Todo - -## Requirements - -The class satisfies the following concept requirements: - -### Basic - -- [DefaultConstructible](https://en.cppreference.com/w/cpp/named_req/DefaultConstructible): JSON values can be default - constructed. The result will be a JSON null value. -- [MoveConstructible](https://en.cppreference.com/w/cpp/named_req/MoveConstructible): A JSON value can be constructed - from an rvalue argument. -- [CopyConstructible](https://en.cppreference.com/w/cpp/named_req/CopyConstructible): A JSON value can be - copy-constructed from an lvalue expression. -- [MoveAssignable](https://en.cppreference.com/w/cpp/named_req/MoveAssignable): A JSON value can be assigned from an - rvalue argument. -- [CopyAssignable](https://en.cppreference.com/w/cpp/named_req/CopyAssignable): A JSON value can be copy-assigned from - an lvalue expression. -- [Destructible](https://en.cppreference.com/w/cpp/named_req/Destructible): JSON values can be destructed. - -### Layout - -- [StandardLayoutType](https://en.cppreference.com/w/cpp/named_req/StandardLayoutType): JSON values have - [standard layout](https://en.cppreference.com/w/cpp/language/data_members#Standard_layout): All non-static data - members are private and standard layout types, the class has no virtual functions or (virtual) base classes. - -### Library-wide - -- [EqualityComparable](https://en.cppreference.com/w/cpp/named_req/EqualityComparable): JSON values can be compared with - `==`, see [`operator==`](operator_eq.md). -- [LessThanComparable](https://en.cppreference.com/w/cpp/named_req/LessThanComparable): JSON values can be compared with - `<`, see [`operator<`](operator_le). -- [Swappable](https://en.cppreference.com/w/cpp/named_req/Swappable): Any JSON lvalue or rvalue of can be swapped with - any lvalue or rvalue of other compatible types, using unqualified function `swap`. -- [NullablePointer](https://en.cppreference.com/w/cpp/named_req/NullablePointer): JSON values can be compared against - `std::nullptr_t` objects which are used to model the `null` value. - -### Container - -- [Container](https://en.cppreference.com/w/cpp/named_req/Container): JSON values can be used like STL containers and - provide iterator access. -- [ReversibleContainer](https://en.cppreference.com/w/cpp/named_req/ReversibleContainer): JSON values can be used like - STL containers and provide reverse iterator access. - -## Member types - -- [**adl_serializer**](../adl_serializer) - the default serializer -- [**value_t**](value_t.md) - the JSON type enumeration -- [**json_pointer**](../json_pointer/index.md) - JSON Pointer implementation -- [**json_serializer**](json_serializer.md) - type of the serializer to for conversions from/to JSON -- [**error_handler_t**](error_handler_t.md) - type to choose behavior on decoding errors -- [**cbor_tag_handler_t**](cbor_tag_handler_t.md) - type to choose how to handle CBOR tags -- **initializer_list_t** - type for initializer lists of `basic_json` values -- [**input_format_t**](input_format_t.md) - type to choose the format to parse -- [**json_sax_t**](../json_sax/index.md) - type for SAX events - -### Exceptions - -- [**exception**](exception.md) - general exception of the `basic_json` class - - [**parse_error**](parse_error.md) - exception indicating a parse error - - [**invalid_iterator**](invalid_iterator.md) - exception indicating errors with iterators - - [**type_error**](type_error.md) - exception indicating executing a member function with a wrong type - - [**out_of_range**](out_of_range.md) - exception indicating access out of the defined range - - [**other_error**](other_error.md) - exception indicating other library errors - -### Container types - -| Type | Definition | -|--------------------------|-----------------------------------------------------------------------------------------------------------| -| `value_type` | `#!cpp basic_json` | -| `reference` | `#!cpp value_type&` | -| `const_reference` | `#!cpp const value_type&` | -| `difference_type` | `#!cpp std::ptrdiff_t` | -| `size_type` | `#!cpp std::size_t` | -| `allocator_type` | `#!cpp AllocatorType` | -| `pointer` | `#!cpp std::allocator_traits::pointer` | -| `const_pointer` | `#!cpp std::allocator_traits::const_pointer` | -| `iterator` | [LegacyBidirectionalIterator](https://en.cppreference.com/w/cpp/named_req/BidirectionalIterator) | -| `const_iterator` | constant [LegacyBidirectionalIterator](https://en.cppreference.com/w/cpp/named_req/BidirectionalIterator) | -| `reverse_iterator` | reverse iterator, derived from `iterator` | -| `const_reverse_iterator` | reverse iterator, derived from `const_iterator` | -| `iteration_proxy` | helper type for [`items`](items.md) function | - -### JSON value data types - -- [**array_t**](array_t.md) - type for arrays -- [**binary_t**](binary_t.md) - type for binary arrays -- [**boolean_t**](boolean_t.md) - type for booleans -- [**default_object_comparator_t**](default_object_comparator_t.md) - default comparator for objects -- [**number_float_t**](number_float_t.md) - type for numbers (floating-point) -- [**number_integer_t**](number_integer_t.md) - type for numbers (integer) -- [**number_unsigned_t**](number_unsigned_t.md) - type for numbers (unsigned) -- [**object_comparator_t**](object_comparator_t.md) - comparator for objects -- [**object_t**](object_t.md) - type for objects -- [**string_t**](string_t.md) - type for strings - -### Parser callback - -- [**parse_event_t**](parse_event_t.md) - parser event types -- [**parser_callback_t**](parser_callback_t.md) - per-element parser callback type - -## Member functions - -- [(constructor)](basic_json.md) -- [(destructor)](~basic_json.md) -- [**operator=**](operator=.md) - copy assignment -- [**array**](array_t.md) (_static_) - explicitly create an array -- [**binary**](binary.md) (_static_) - explicitly create a binary array -- [**object**](object_t.md) (_static_) - explicitly create an object - -### Object inspection - -Functions to inspect the type of a JSON value. - -- [**type**](type.md) - return the type of the JSON value -- [**operator value_t**](operator_value_t.md) - return the type of the JSON value -- [**type_name**](type_name.md) - return the type as string -- [**is_primitive**](is_primitive.md) - return whether type is primitive -- [**is_structured**](is_structured.md) - return whether type is structured -- [**is_null**](is_null.md) - return whether value is null -- [**is_boolean**](is_boolean.md) - return whether value is a boolean -- [**is_number**](is_number.md) - return whether value is a number -- [**is_number_integer**](is_number_integer.md) - return whether value is an integer number -- [**is_number_unsigned**](is_number_unsigned.md) - return whether value is an unsigned integer number -- [**is_number_float**](is_number_float.md) - return whether value is a floating-point number -- [**is_object**](is_object.md) - return whether value is an object -- [**is_array**](is_array.md) - return whether value is an array -- [**is_string**](is_string.md) - return whether value is a string -- [**is_binary**](is_binary.md) - return whether value is a binary array -- [**is_discarded**](is_discarded.md) - return whether value is discarded - -### Value access - -Direct access to the stored value of a JSON value. - -- [**get**](get.md) - get a value -- [**get_to**](get_to.md) - get a value and write it to a destination -- [**get_ptr**](get_ptr.md) - get a pointer value -- [**get_ref**](get_ref.md) - get a reference value -- [**operator ValueType**](operator_ValueType.md) - get a value -- [**get_binary**](get_binary.md) - get a binary value - -### Element access - -Access to the JSON value - -- [**at**](at.md) - access specified element with bounds checking -- [**operator[]**](operator[].md) - access specified element -- [**value**](value.md) - access specified object element with default value -- [**front**](front.md) - access the first element -- [**back**](back.md) - access the last element - -### Lookup - -- [**find**](find.md) - find an element in a JSON object -- [**count**](count.md) - returns the number of occurrences of a key in a JSON object -- [**contains**](contains.md) - check the existence of an element in a JSON object - -### Iterators - -- [**begin**](begin.md) - returns an iterator to the first element -- [**cbegin**](cbegin.md) - returns a const iterator to the first element -- [**end**](end.md) - returns an iterator to one past the last element -- [**cend**](cend.md) - returns a const iterator to one past the last element -- [**rbegin**](rbegin.md) - returns an iterator to the reverse-beginning -- [**rend**](rend.md) - returns an iterator to the reverse-end -- [**crbegin**](crbegin.md) - returns a const iterator to the reverse-beginning -- [**crend**](crend.md) - returns a const iterator to the reverse-end -- [**items**](items.md) - wrapper to access iterator member functions in range-based for - -### Capacity - -- [**empty**](empty.md) - checks whether the container is empty -- [**size**](size.md) - returns the number of elements -- [**max_size**](max_size.md) - returns the maximum possible number of elements - -### Modifiers - -- [**clear**](clear.md) - clears the contents -- [**push_back**](push_back.md) - add a value to an array/object -- [**operator+=**](operator+=.md) - add a value to an array/object -- [**emplace_back**](emplace_back.md) - add a value to an array -- [**emplace**](emplace.md) - add a value to an object if key does not exist -- [**erase**](erase.md) - remove elements -- [**insert**](insert.md) - inserts elements -- [**update**](update.md) - updates a JSON object from another object, overwriting existing keys -- [**swap**](swap.md) - exchanges the values - -### Lexicographical comparison operators - -- [**operator==**](operator_eq.md) - comparison: equal -- [**operator!=**](operator_ne.md) - comparison: not equal -- [**operator<**](operator_lt.md) - comparison: less than -- [**operator>**](operator_gt.md) - comparison: greater than -- [**operator<=**](operator_le.md) - comparison: less than or equal -- [**operator>=**](operator_ge.md) - comparison: greater than or equal -- [**operator<=>**](operator_spaceship.md) - comparison: 3-way - -### Serialization / Dumping - -- [**dump**](dump.md) - serialization - -### Deserialization / Parsing - -- [**parse**](parse.md) (_static_) - deserialize from a compatible input -- [**accept**](accept.md) (_static_) - check if the input is valid JSON -- [**sax_parse**](sax_parse.md) (_static_) - generate SAX events - -### JSON Pointer functions - -- [**flatten**](flatten.md) - return flattened JSON value -- [**unflatten**](unflatten.md) - unflatten a previously flattened JSON value - -### JSON Patch functions - -- [**patch**](patch.md) - applies a JSON patch -- [**patch_inplace**](patch_inplace.md) - applies a JSON patch in place -- [**diff**](diff.md) (_static_) - creates a diff as a JSON patch - -### JSON Merge Patch functions - -- [**merge_patch**](merge_patch.md) - applies a JSON Merge Patch - -## Static functions - -- [**meta**](meta.md) - returns version information on the library -- [**get_allocator**](get_allocator.md) - returns the allocator associated with the container - -### Binary formats - -- [**from_bjdata**](from_bjdata.md) (_static_) - create a JSON value from an input in BJData format -- [**from_bson**](from_bson.md) (_static_) - create a JSON value from an input in BSON format -- [**from_cbor**](from_cbor.md) (_static_) - create a JSON value from an input in CBOR format -- [**from_msgpack**](from_msgpack.md) (_static_) - create a JSON value from an input in MessagePack format -- [**from_ubjson**](from_ubjson.md) (_static_) - create a JSON value from an input in UBJSON format -- [**to_bjdata**](to_bjdata.md) (_static_) - create a BJData serialization of a given JSON value -- [**to_bson**](to_bson.md) (_static_) - create a BSON serialization of a given JSON value -- [**to_cbor**](to_cbor.md) (_static_) - create a CBOR serialization of a given JSON value -- [**to_msgpack**](to_msgpack.md) (_static_) - create a MessagePack serialization of a given JSON value -- [**to_ubjson**](to_ubjson.md) (_static_) - create a UBJSON serialization of a given JSON value - -## Non-member functions - -- [**operator<<(std::ostream&)**](../operator_ltlt.md) - serialize to stream -- [**operator>>(std::istream&)**](../operator_gtgt.md) - deserialize from stream -- [**to_string**](to_string.md) - user-defined `to_string` function for JSON values - -## Literals - -- [**operator""_json**](../operator_literal_json.md) - user-defined string literal for JSON values - -## Helper classes - -- [**std::hash<basic_json>**](std_hash.md) - return a hash value for a JSON object -- [**std::swap<basic_json>**](std_swap.md) - exchanges the values of two JSON objects - -## Examples - -??? example - - The example shows how the library is used. - - ```cpp - --8<-- "examples/README.cpp" - ``` - - Output: - - ```json - --8<-- "examples/README.output" - ``` - -## See also - -- [RFC 8259: The JavaScript Object Notation (JSON) Data Interchange Format](https://tools.ietf.org/html/rfc8259) - -## Version history - -- Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/input_format_t.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/input_format_t.md deleted file mode 100644 index a3baaba..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/input_format_t.md +++ /dev/null @@ -1,52 +0,0 @@ -# nlohmann::basic_json::input_format_t - -```cpp -enum class input_format_t { - json, - cbor, - msgpack, - ubjson, - bson, - bjdata -}; -``` - -This enumeration is used in the [`sax_parse`](sax_parse.md) function to choose the input format to parse: - -json -: JSON (JavaScript Object Notation) - -cbor -: CBOR (Concise Binary Object Representation) - -msgpack -: MessagePack - -ubjson -: UBJSON (Universal Binary JSON) - -bson -: BSON (Binary JSON) - -bjdata -: BJData (Binary JData) - -## Examples - -??? example - - The example below shows how an `input_format_t` enum value is passed to `sax_parse` to set the input format to CBOR. - - ```cpp - --8<-- "examples/sax_parse__binary.cpp" - ``` - - Output: - - ```json - --8<-- "examples/sax_parse__binary.output" - ``` - -## Version history - -- Added in version 3.2.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/insert.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/insert.md deleted file mode 100644 index 2e6b293..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/insert.md +++ /dev/null @@ -1,179 +0,0 @@ -# nlohmann::basic_json::insert - -```cpp -// (1) -iterator insert(const_iterator pos, const basic_json& val); -iterator insert(const_iterator pos, basic_json&& val); - -// (2) -iterator insert(const_iterator pos, size_type cnt, const basic_json& val); - -// (3) -iterator insert(const_iterator pos, const_iterator first, const_iterator last); - -// (4) -iterator insert(const_iterator pos, initializer_list_t ilist); - -// (5) -void insert(const_iterator first, const_iterator last); -``` - -1. Inserts element `val` into array before iterator `pos`. -2. Inserts `cnt` copies of `val` into array before iterator `pos`. -3. Inserts elements from range `[first, last)` into array before iterator `pos`. -4. Inserts elements from initializer list `ilist` into array before iterator `pos`. -5. Inserts elements from range `[first, last)` into object. - -## Parameters - -`pos` (in) -: iterator before which the content will be inserted; may be the `end()` iterator - -`val` (in) -: value to insert - -`cnt` (in) -: number of copies of `val` to insert - -`first` (in) -: begin of the range of elements to insert - -`last` (in) -: end of the range of elements to insert - -`ilist` (in) -: initializer list to insert the values from - -## Return value - -1. iterator pointing to the inserted `val`. -2. iterator pointing to the first element inserted, or `pos` if `#!cpp cnt==0` -3. iterator pointing to the first element inserted, or `pos` if `#!cpp first==last` -4. iterator pointing to the first element inserted, or `pos` if `ilist` is empty -5. (none) - -## Exception safety - -Strong exception safety: if an exception occurs, the original value stays intact. - -## Exceptions - -1. The function can throw the following exceptions: - - Throws [`type_error.309`](../../home/exceptions.md#jsonexceptiontype_error309) if called on JSON values other than - arrays; example: `"cannot use insert() with string"` - - Throws [`invalid_iterator.202`](../../home/exceptions.md#jsonexceptioninvalid_iterator202) if called on an - iterator which does not belong to the current JSON value; example: `"iterator does not fit current value"` -2. The function can throw the following exceptions: - - Throws [`type_error.309`](../../home/exceptions.md#jsonexceptiontype_error309) if called on JSON values other than - arrays; example: `"cannot use insert() with string"` - - Throws [`invalid_iterator.202`](../../home/exceptions.md#jsonexceptioninvalid_iterator202) if called on an - iterator which does not belong to the current JSON value; example: `"iterator does not fit current value"` -3. The function can throw the following exceptions: - - Throws [`type_error.309`](../../home/exceptions.md#jsonexceptiontype_error309) if called on JSON values other than - arrays; example: `"cannot use insert() with string"` - - Throws [`invalid_iterator.202`](../../home/exceptions.md#jsonexceptioninvalid_iterator202) if called on an - iterator which does not belong to the current JSON value; example: `"iterator does not fit current value"` - - Throws [`invalid_iterator.210`](../../home/exceptions.md#jsonexceptioninvalid_iterator210) if `first` and `last` - do not belong to the same JSON value; example: `"iterators do not fit"` - - Throws [`invalid_iterator.211`](../../home/exceptions.md#jsonexceptioninvalid_iterator211) if `first` or `last` - are iterators into container for which insert is called; example: `"passed iterators may not belong to container"` -4. The function can throw the following exceptions: - - Throws [`type_error.309`](../../home/exceptions.md#jsonexceptiontype_error309) if called on JSON values other than - arrays; example: `"cannot use insert() with string"` - - Throws [`invalid_iterator.202`](../../home/exceptions.md#jsonexceptioninvalid_iterator202) if called on an - iterator which does not belong to the current JSON value; example: `"iterator does not fit current value"` -5. The function can throw the following exceptions: - - Throws [`type_error.309`](../../home/exceptions.md#jsonexceptiontype_error309) if called on JSON values other than - objects; example: `"cannot use insert() with string"` - - Throws [`invalid_iterator.202`](../../home/exceptions.md#jsonexceptioninvalid_iterator202) if called on an - iterator which does not belong to the current JSON value; example: `"iterator does not fit current value"` - - Throws [`invalid_iterator.210`](../../home/exceptions.md#jsonexceptioninvalid_iterator210) if `first` and `last` - do not belong to the same JSON value; example: `"iterators do not fit"` - -## Complexity - -1. Constant plus linear in the distance between `pos` and end of the container. -2. Linear in `cnt` plus linear in the distance between `pos` and end of the container. -3. Linear in `#!cpp std::distance(first, last)` plus linear in the distance between `pos` and end of the container. -4. Linear in `ilist.size()` plus linear in the distance between `pos` and end of the container. -5. Logarithmic: `O(N*log(size() + N))`, where `N` is the number of elements to insert. - -## Examples - -??? example "Example (1): insert element into array" - - The example shows how `insert()` is used. - - ```cpp - --8<-- "examples/insert.cpp" - ``` - - Output: - - ```json - --8<-- "examples/insert.output" - ``` - -??? example "Example (2): insert copies of element into array" - - The example shows how `insert()` is used. - - ```cpp - --8<-- "examples/insert__count.cpp" - ``` - - Output: - - ```json - --8<-- "examples/insert__count.output" - ``` - -??? example "Example (3): insert range of elements into array" - - The example shows how `insert()` is used. - - ```cpp - --8<-- "examples/insert__range.cpp" - ``` - - Output: - - ```json - --8<-- "examples/insert__range.output" - ``` - -??? example "Example (4): insert elements from initializer list into array" - - The example shows how `insert()` is used. - - ```cpp - --8<-- "examples/insert__ilist.cpp" - ``` - - Output: - - ```json - --8<-- "examples/insert__ilist.output" - ``` - -??? example "Example (5): insert range of elements into object" - - The example shows how `insert()` is used. - - ```cpp - --8<-- "examples/insert__range_object.cpp" - ``` - - Output: - - ```json - --8<-- "examples/insert__range_object.output" - ``` - -## Version history - -1. Added in version 1.0.0. -2. Added in version 1.0.0. -3. Added in version 1.0.0. -4. Added in version 1.0.0. -5. Added in version 3.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/invalid_iterator.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/invalid_iterator.md deleted file mode 100644 index f9fdce5..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/invalid_iterator.md +++ /dev/null @@ -1,67 +0,0 @@ -# nlohmann::basic_json::invalid_iterator - -```cpp -class invalid_iterator : public exception; -``` - -This exception is thrown if iterators passed to a library function do not match the expected semantics. - -Exceptions have ids 2xx (see [list of iterator errors](../../home/exceptions.md#iterator-errors)). - -```plantuml -std::exception <|-- basic_json::exception -basic_json::exception <|-- basic_json::parse_error -basic_json::exception <|-- basic_json::invalid_iterator -basic_json::exception <|-- basic_json::type_error -basic_json::exception <|-- basic_json::out_of_range -basic_json::exception <|-- basic_json::other_error - -interface std::exception {} - -class basic_json::exception { - + const int id - + const char* what() const -} - -class basic_json::parse_error { - + const std::size_t byte -} - -class basic_json::invalid_iterator #FFFF00 {} -``` - -## Member functions - -- **what** - returns explanatory string - -## Member variables - -- **id** - the id of the exception - -## Examples - -??? example - - The following code shows how a `invalid_iterator` exception can be caught. - - ```cpp - --8<-- "examples/invalid_iterator.cpp" - ``` - - Output: - - ```json - --8<-- "examples/invalid_iterator.output" - ``` - -## See also - -- [List of iterator errors](../../home/exceptions.md#iterator-errors) -- [`parse_error`](parse_error.md) for exceptions indicating a parse error -- [`type_error`](type_error.md) for exceptions indicating executing a member function with a wrong type -- [`out_of_range`](out_of_range.md) for exceptions indicating access out of the defined range -- [`other_error`](other_error.md) for exceptions indicating other library errors - -## Version history - -- Since version 3.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_array.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_array.md deleted file mode 100644 index 64468c3..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_array.md +++ /dev/null @@ -1,39 +0,0 @@ -# nlohmann::basic_json::is_array - -```cpp -constexpr bool is_array() const noexcept; -``` - -This function returns `#!cpp true` if and only if the JSON value is an array. - -## Return value - -`#!cpp true` if type is an array, `#!cpp false` otherwise. - -## Exception safety - -No-throw guarantee: this member function never throws exceptions. - -## Complexity - -Constant. - -## Examples - -??? example - - The following code exemplifies `is_array()` for all JSON types. - - ```cpp - --8<-- "examples/is_array.cpp" - ``` - - Output: - - ```json - --8<-- "examples/is_array.output" - ``` - -## Version history - -- Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_binary.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_binary.md deleted file mode 100644 index ea48d74..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_binary.md +++ /dev/null @@ -1,39 +0,0 @@ -# nlohmann::basic_json::is_binary - -```cpp -constexpr bool is_binary() const noexcept; -``` - -This function returns `#!cpp true` if and only if the JSON value is binary array. - -## Return value - -`#!cpp true` if type is binary, `#!cpp false` otherwise. - -## Exception safety - -No-throw guarantee: this member function never throws exceptions. - -## Complexity - -Constant. - -## Examples - -??? example - - The following code exemplifies `is_binary()` for all JSON types. - - ```cpp - --8<-- "examples/is_binary.cpp" - ``` - - Output: - - ```json - --8<-- "examples/is_binary.output" - ``` - -## Version history - -- Added in version 3.8.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_boolean.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_boolean.md deleted file mode 100644 index dc41d84..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_boolean.md +++ /dev/null @@ -1,39 +0,0 @@ -# nlohmann::basic_json::is_boolean - -```cpp -constexpr bool is_boolean() const noexcept; -``` - -This function returns `#!cpp true` if and only if the JSON value is `#!json true` or `#!json false`. - -## Return value - -`#!cpp true` if type is boolean, `#!cpp false` otherwise. - -## Exception safety - -No-throw guarantee: this member function never throws exceptions. - -## Complexity - -Constant. - -## Examples - -??? example - - The following code exemplifies `is_boolean()` for all JSON types. - - ```cpp - --8<-- "examples/is_boolean.cpp" - ``` - - Output: - - ```json - --8<-- "examples/is_boolean.output" - ``` - -## Version history - -- Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_discarded.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_discarded.md deleted file mode 100644 index 663cbf8..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_discarded.md +++ /dev/null @@ -1,72 +0,0 @@ -# nlohmann::basic_json::is_discarded - -```cpp -constexpr bool is_discarded() const noexcept; -``` - -This function returns `#!cpp true` for a JSON value if either: - -- the value was discarded during parsing with a callback function (see [`parser_callback_t`](parser_callback_t.md)), or -- the value is the result of parsing invalid JSON with parameter `allow_exceptions` set to `#!cpp false`; see - [`parse`](parse.md) for more information. - -## Return value - -`#!cpp true` if type is discarded, `#!cpp false` otherwise. - -## Exception safety - -No-throw guarantee: this member function never throws exceptions. - -## Complexity - -Constant. - -## Notes - -!!! note "Comparisons" - - Discarded values are never compared equal with [`operator==`](operator_eq.md). That is, checking whether a JSON - value `j` is discarded will only work via: - - ```cpp - j.is_discarded() - ``` - - because - - ```cpp - j == json::value_t::discarded - ``` - - will always be `#!cpp false`. - -!!! note "Removal during parsing with callback functions" - - When a value is discarded by a callback function (see [`parser_callback_t`](parser_callback_t.md)) during parsing, - then it is removed when it is part of a structured value. For instance, if the second value of an array is discarded, - instead of `#!json [null, discarded, false]`, the array `#!json [null, false]` is returned. Only if the top-level - value is discarded, the return value of the `parse` call is discarded. - -This function will always be `#!cpp false` for JSON values after parsing. That is, discarded values can only occur -during parsing, but will be removed when inside a structured value or replaced by null in other cases. - -## Examples - -??? example - - The following code exemplifies `is_discarded()` for all JSON types. - - ```cpp - --8<-- "examples/is_discarded.cpp" - ``` - - Output: - - ```json - --8<-- "examples/is_discarded.output" - ``` - -## Version history - -- Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_null.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_null.md deleted file mode 100644 index d080ad3..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_null.md +++ /dev/null @@ -1,39 +0,0 @@ -# nlohmann::basic_json::is_null - -```cpp -constexpr bool is_null() const noexcept; -``` - -This function returns `#!cpp true` if and only if the JSON value is `#!json null`. - -## Return value - -`#!cpp true` if type is `#!json null`, `#!cpp false` otherwise. - -## Exception safety - -No-throw guarantee: this member function never throws exceptions. - -## Complexity - -Constant. - -## Examples - -??? example - - The following code exemplifies `is_null()` for all JSON types. - - ```cpp - --8<-- "examples/is_null.cpp" - ``` - - Output: - - ```json - --8<-- "examples/is_null.output" - ``` - -## Version history - -- Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_number.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_number.md deleted file mode 100644 index 9807911..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_number.md +++ /dev/null @@ -1,56 +0,0 @@ -# nlohmann::basic_json::is_number - -```cpp -constexpr bool is_number() const noexcept; -``` - -This function returns `#!cpp true` if and only if the JSON value is a number. This includes both integer (signed and -unsigned) and floating-point values. - -## Return value - -`#!cpp true` if type is number (regardless whether integer, unsigned integer or floating-type), `#!cpp false` otherwise. - -## Exception safety - -No-throw guarantee: this member function never throws exceptions. - -## Complexity - -Constant. - -## Possible implementation - -```cpp -constexpr bool is_number() const noexcept -{ - return is_number_integer() || is_number_float(); -} -``` - -## Examples - -??? example - - The following code exemplifies `is_number()` for all JSON types. - - ```cpp - --8<-- "examples/is_number.cpp" - ``` - - Output: - - ```json - --8<-- "examples/is_number.output" - ``` - -## See also - -- [is_number_integer()](is_number_integer.md) check if value is an integer or unsigned integer number -- [is_number_unsigned()](is_number_unsigned.md) check if value is an unsigned integer number -- [is_number_float()](is_number_float.md) check if value is a floating-point number - -## Version history - -- Added in version 1.0.0. -- Extended to also return `#!cpp true` for unsigned integers in 2.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_number_float.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_number_float.md deleted file mode 100644 index 68d0cfb..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_number_float.md +++ /dev/null @@ -1,46 +0,0 @@ -# nlohmann::basic_json::is_number_float - -```cpp -constexpr bool is_number_float() const noexcept; -``` - -This function returns `#!cpp true` if and only if the JSON value is a floating-point number. This excludes signed and -unsigned integer values. - -## Return value - -`#!cpp true` if type is a floating-point number, `#!cpp false` otherwise. - -## Exception safety - -No-throw guarantee: this member function never throws exceptions. - -## Complexity - -Constant. - -## Examples - -??? example - - The following code exemplifies `is_number_float()` for all JSON types. - - ```cpp - --8<-- "examples/is_number_float.cpp" - ``` - - Output: - - ```json - --8<-- "examples/is_number_float.output" - ``` - -## See also - -- [is_number()](is_number.md) check if value is a number -- [is_number_integer()](is_number_integer.md) check if value is an integer or unsigned integer number -- [is_number_unsigned()](is_number_unsigned.md) check if value is an unsigned integer number - -## Version history - -- Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_number_integer.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_number_integer.md deleted file mode 100644 index 8ca214a..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_number_integer.md +++ /dev/null @@ -1,47 +0,0 @@ -# nlohmann::basic_json::is_number_integer - -```cpp -constexpr bool is_number_integer() const noexcept; -``` - -This function returns `#!cpp true` if and only if the JSON value is a signed or unsigned integer number. This excludes -floating-point values. - -## Return value - -`#!cpp true` if type is an integer or unsigned integer number, `#!cpp false` otherwise. - -## Exception safety - -No-throw guarantee: this member function never throws exceptions. - -## Complexity - -Constant. - -## Examples - -??? example - - The following code exemplifies `is_number_integer()` for all JSON types. - - ```cpp - --8<-- "examples/is_number_integer.cpp" - ``` - - Output: - - ```json - --8<-- "examples/is_number_integer.output" - ``` - -## See also - -- [is_number()](is_number.md) check if value is a number -- [is_number_unsigned()](is_number_unsigned.md) check if value is an unsigned integer number -- [is_number_float()](is_number_float.md) check if value is a floating-point number - -## Version history - -- Added in version 1.0.0. -- Extended to also return `#!cpp true` for unsigned integers in 2.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_number_unsigned.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_number_unsigned.md deleted file mode 100644 index 2ac98a5..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_number_unsigned.md +++ /dev/null @@ -1,46 +0,0 @@ -# nlohmann::basic_json::is_number_unsigned - -```cpp -constexpr bool is_number_unsigned() const noexcept; -``` - -This function returns `#!cpp true` if and only if the JSON value is an unsigned integer number. This excludes -floating-point and signed integer values. - -## Return value - -`#!cpp true` if type is an unsigned integer number, `#!cpp false` otherwise. - -## Exception safety - -No-throw guarantee: this member function never throws exceptions. - -## Complexity - -Constant. - -## Examples - -??? example - - The following code exemplifies `is_number_unsigned()` for all JSON types. - - ```cpp - --8<-- "examples/is_number_unsigned.cpp" - ``` - - Output: - - ```json - --8<-- "examples/is_number_unsigned.output" - ``` - -## See also - -- [is_number()](is_number.md) check if value is a number -- [is_number_integer()](is_number_integer.md) check if value is an integer or unsigned integer number -- [is_number_float()](is_number_float.md) check if value is a floating-point number - -## Version history - -- Added in version 2.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_object.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_object.md deleted file mode 100644 index 0445701..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_object.md +++ /dev/null @@ -1,39 +0,0 @@ -# nlohmann::basic_json::is_object - -```cpp -constexpr bool is_object() const noexcept; -``` - -This function returns `#!cpp true` if and only if the JSON value is an object. - -## Return value - -`#!cpp true` if type is an object, `#!cpp false` otherwise. - -## Exception safety - -No-throw guarantee: this member function never throws exceptions. - -## Complexity - -Constant. - -## Examples - -??? example - - The following code exemplifies `is_object()` for all JSON types. - - ```cpp - --8<-- "examples/is_object.cpp" - ``` - - Output: - - ```json - --8<-- "examples/is_object.output" - ``` - -## Version history - -- Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_primitive.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_primitive.md deleted file mode 100644 index cf6cbbd..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_primitive.md +++ /dev/null @@ -1,69 +0,0 @@ -# nlohmann::basic_json::is_primitive - -```cpp -constexpr bool is_primitive() const noexcept; -``` - -This function returns `#!cpp true` if and only if the JSON type is primitive (string, number, boolean, `#!json null`, -binary). - -## Return value - -`#!cpp true` if type is primitive (string, number, boolean, `#!json null`, or binary), `#!cpp false` otherwise. - -## Exception safety - -No-throw guarantee: this member function never throws exceptions. - -## Complexity - -Constant. - -## Possible implementation - -```cpp -constexpr bool is_primitive() const noexcept -{ - return is_null() || is_string() || is_boolean() || is_number() || is_binary(); -} -``` - -## Notes - -The term *primitive* stems from [RFC 8259](https://tools.ietf.org/html/rfc8259): - -> JSON can represent four primitive types (strings, numbers, booleans, and null) and two structured types (objects and -> arrays). - -This library extends primitive types to binary types, because binary types are roughly comparable to strings. Hence, -`is_primitive()` returns `#!cpp true` for binary values. - -## Examples - -??? example - - The following code exemplifies `is_primitive()` for all JSON types. - - ```cpp - --8<-- "examples/is_primitive.cpp" - ``` - - Output: - - ```json - --8<-- "examples/is_primitive.output" - ``` - -## See also - -- [is_structured()](is_structured.md) returns whether JSON value is structured -- [is_null()](is_null.md) returns whether JSON value is `null` -- [is_string()](is_string.md) returns whether JSON value is a string -- [is_boolean()](is_boolean.md) returns whether JSON value is a boolean -- [is_number()](is_number.md) returns whether JSON value is a number -- [is_binary()](is_binary.md) returns whether JSON value is a binary array - -## Version history - -- Added in version 1.0.0. -- Extended to return `#!cpp true` for binary types in version 3.8.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_string.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_string.md deleted file mode 100644 index b82c924..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_string.md +++ /dev/null @@ -1,39 +0,0 @@ -# nlohmann::basic_json::is_string - -```cpp -constexpr bool is_string() const noexcept; -``` - -This function returns `#!cpp true` if and only if the JSON value is a string. - -## Return value - -`#!cpp true` if type is a string, `#!cpp false` otherwise. - -## Exception safety - -No-throw guarantee: this member function never throws exceptions. - -## Complexity - -Constant. - -## Examples - -??? example - - The following code exemplifies `is_string()` for all JSON types. - - ```cpp - --8<-- "examples/is_string.cpp" - ``` - - Output: - - ```json - --8<-- "examples/is_string.output" - ``` - -## Version history - -- Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_structured.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_structured.md deleted file mode 100644 index f8fe4dc..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/is_structured.md +++ /dev/null @@ -1,63 +0,0 @@ -# nlohmann::basic_json::is_structured - -```cpp -constexpr bool is_structured() const noexcept; -``` - -This function returns `#!cpp true` if and only if the JSON type is structured (array or object). - -## Return value - -`#!cpp true` if type is structured (array or object), `#!cpp false` otherwise. - -## Exception safety - -No-throw guarantee: this member function never throws exceptions. - -## Complexity - -Constant. - -## Possible implementation - -```cpp -constexpr bool is_primitive() const noexcept -{ - return is_array() || is_object(); -} -``` - -## Notes - -The term *structured* stems from [RFC 8259](https://tools.ietf.org/html/rfc8259): - -> JSON can represent four primitive types (strings, numbers, booleans, and null) and two structured types (objects and -> arrays). - -Note that though strings are containers in C++, they are treated as primitive values in JSON. - -## Examples - -??? example - - The following code exemplifies `is_structured()` for all JSON types. - - ```cpp - --8<-- "examples/is_structured.cpp" - ``` - - Output: - - ```json - --8<-- "examples/is_structured.output" - ``` - -## See also - -- [is_primitive()](is_primitive.md) returns whether JSON value is primitive -- [is_array()](is_array.md) returns whether value is an array -- [is_object()](is_object.md) returns whether value is an object - -## Version history - -- Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/items.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/items.md deleted file mode 100644 index 0b34ddc..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/items.md +++ /dev/null @@ -1,100 +0,0 @@ -# nlohmann::basic_json::items - -```cpp -iteration_proxy items() noexcept; -iteration_proxy items() const noexcept; -``` - -This function allows accessing `iterator::key()` and `iterator::value()` during range-based for loops. In these loops, a -reference to the JSON values is returned, so there is no access to the underlying iterator. - -For loop without `items()` function: - -```cpp -for (auto it = j_object.begin(); it != j_object.end(); ++it) -{ - std::cout << "key: " << it.key() << ", value:" << it.value() << '\n'; -} -``` - -Range-based for loop without `items()` function: - -```cpp -for (auto it : j_object) -{ - // "it" is of type json::reference and has no key() member - std::cout << "value: " << it << '\n'; -} -``` - -Range-based for loop with `items()` function: - -```cpp -for (auto& el : j_object.items()) -{ - std::cout << "key: " << el.key() << ", value:" << el.value() << '\n'; -} -``` - -The `items()` function also allows using -[structured bindings](https://en.cppreference.com/w/cpp/language/structured_binding) (C++17): - -```cpp -for (auto& [key, val] : j_object.items()) -{ - std::cout << "key: " << key << ", value:" << val << '\n'; -} -``` - -## Return value - -iteration proxy object wrapping the current value with an interface to use in range-based for loops - -## Exception safety - -Strong guarantee: if an exception is thrown, there are no changes in the JSON value. - -## Complexity - -Constant. - -## Notes - -When iterating over an array, `key()` will return the index of the element as string (see example). For primitive types -(e.g., numbers), `key()` returns an empty string. - -!!! danger "Lifetime issues" - - Using `items()` on temporary objects is dangerous. Make sure the object's lifetime exceeds the iteration. See - for more information. - -## Examples - -??? example - - The following code shows an example for `items()`. - - ```cpp - --8<-- "examples/items.cpp" - ``` - - Output: - - ```json - --8<-- "examples/items.output" - ``` - -## Version history - -- Added `iterator_wrapper` in version 3.0.0. -- Added `items` and deprecated `iterator_wrapper` in version 3.1.0. -- Added structured binding support in version 3.5.0. - -!!! warning "Deprecation" - - This function replaces the static function `iterator_wrapper` which was introduced in version 1.0.0, but has been - deprecated in version 3.1.0. Function `iterator_wrapper` will be removed in version 4.0.0. Please replace all - occurrences of `#!cpp iterator_wrapper(j)` with `#!cpp j.items()`. - - You should be warned by your compiler with a `-Wdeprecated-declarations` warning if you are using a deprecated - function. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/json_serializer.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/json_serializer.md deleted file mode 100644 index b8b67c5..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/json_serializer.md +++ /dev/null @@ -1,41 +0,0 @@ -# nlohmann::basic_json::json_serializer - -```cpp -template -using json_serializer = JSONSerializer; -``` - -## Template parameters - -`T` -: type to convert; will be used in the `to_json`/`from_json` functions - -`SFINAE` -: type to add compile type checks via SFINAE; usually `#!cpp void` - -## Notes - -#### Default type - -The default values for `json_serializer` is [`adl_serializer`](../adl_serializer). - -## Examples - -??? example - - The example below shows how a conversion of a non-default-constructible type is implemented via a specialization of - the `adl_serializer`. - - ```cpp - --8<-- "examples/from_json__non_default_constructible.cpp" - ``` - - Output: - - ```json - --8<-- "examples/from_json__non_default_constructible.output" - ``` - -## Version history - -- Since version 2.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/max_size.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/max_size.md deleted file mode 100644 index 4c0c575..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/max_size.md +++ /dev/null @@ -1,60 +0,0 @@ -# nlohmann::basic_json::max_size - -```cpp -size_type max_size() const noexcept; -``` - -Returns the maximum number of elements a JSON value is able to hold due to system or library implementation limitations, -i.e. `std::distance(begin(), end())` for the JSON value. - -## Return value - -The return value depends on the different types and is defined as follows: - -| Value type | return value | -|------------|-------------------------------------------| -| null | `0` (same as [`size()`](size.md)) | -| boolean | `1` (same as [`size()`](size.md)) | -| string | `1` (same as [`size()`](size.md)) | -| number | `1` (same as [`size()`](size.md)) | -| binary | `1` (same as [`size()`](size.md)) | -| object | result of function `object_t::max_size()` | -| array | result of function `array_t::max_size()` | - -## Exception safety - -No-throw guarantee: this function never throws exceptions. - -## Complexity - -Constant, as long as [`array_t`](array_t.md) and [`object_t`](object_t.md) satisfy the -[Container](https://en.cppreference.com/w/cpp/named_req/Container) concept; that is, their `max_size()` functions have -constant complexity. - -## Notes - -This function does not return the maximal length of a string stored as JSON value -- it returns the maximal number of -string elements the JSON value can store which is `1`. - -## Examples - -??? example - - The following code calls `max_size()` on the different value types. - - ```cpp - --8<-- "examples/max_size.cpp" - ``` - - Output: - - ```json - --8<-- "examples/max_size.output" - ``` - - Note the output is platform-dependent. - -## Version history - -- Added in version 1.0.0. -- Extended to return `1` for binary types in version 3.8.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/merge_patch.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/merge_patch.md deleted file mode 100644 index 1718c92..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/merge_patch.md +++ /dev/null @@ -1,63 +0,0 @@ -# nlohmann::basic_json::merge_patch - -```cpp -void merge_patch(const basic_json& apply_patch); -``` - -The merge patch format is primarily intended for use with the HTTP PATCH method as a means of describing a set of -modifications to a target resource's content. This function applies a merge patch to the current JSON value. - -The function implements the following algorithm from Section 2 of -[RFC 7396 (JSON Merge Patch)](https://tools.ietf.org/html/rfc7396): - -```python -define MergePatch(Target, Patch): - if Patch is an Object: - if Target is not an Object: - Target = {} // Ignore the contents and set it to an empty Object - for each Name/Value pair in Patch: - if Value is null: - if Name exists in Target: - remove the Name/Value pair from Target - else: - Target[Name] = MergePatch(Target[Name], Value) - return Target - else: - return Patch -``` - -Thereby, `Target` is the current object; that is, the patch is applied to the current value. - -## Parameters - -`apply_patch` (in) -: the patch to apply - -## Complexity - -Linear in the lengths of `apply_patch`. - -## Examples - -??? example - - The following code shows how a JSON Merge Patch is applied to a JSON document. - - ```cpp - --8<-- "examples/merge_patch.cpp" - ``` - - Output: - - ```json - --8<-- "examples/merge_patch.output" - ``` - -## See also - -- [RFC 7396 (JSON Merge Patch)](https://tools.ietf.org/html/rfc7396) -- [patch](patch.md) apply a JSON patch - -## Version history - -- Added in version 3.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/meta.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/meta.md deleted file mode 100644 index c584f9b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/meta.md +++ /dev/null @@ -1,56 +0,0 @@ -# nlohmann::basic_json::meta - -```cpp -static basic_json meta(); -``` - -This function returns a JSON object with information about the library, including the version number and information on -the platform and compiler. - -## Return value - -JSON object holding version information - -| key | description | -|-------------|--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| -| `compiler` | Information on the used compiler. It is an object with the following keys: `c++` (the used C++ standard), `family` (the compiler family; possible values are `clang`, `icc`, `gcc`, `ilecpp`, `msvc`, `pgcpp`, `sunpro`, and `unknown`), and `version` (the compiler version). | -| `copyright` | The copyright line for the library as string. | -| `name` | The name of the library as string. | -| `platform` | The used platform as string. Possible values are `win32`, `linux`, `apple`, `unix`, and `unknown`. | -| `url` | The URL of the project as string. | -| `version` | The version of the library. It is an object with the following keys: `major`, `minor`, and `patch` as defined by [Semantic Versioning](http://semver.org), and `string` (the version string). | - -## Exception safety - -Strong guarantee: if an exception is thrown, there are no changes to any JSON value. - -## Complexity - -Constant. - -## Examples - -??? example - - The following code shows an example output of the `meta()` function. - - ```cpp - --8<-- "examples/meta.cpp" - ``` - - Output: - - ```json - --8<-- "examples/meta.output" - ``` - - Note the output is platform-dependent. - -## See also - -- [**NLOHMANN_JSON_VERSION_MAJOR**/**NLOHMANN_JSON_VERSION_MINOR**/**NLOHMANN_JSON_VERSION_PATCH**](../macros/nlohmann_json_version_major.md) - \- library version information - -## Version history - -- Added in version 2.1.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/number_float_t.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/number_float_t.md deleted file mode 100644 index 50aa43b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/number_float_t.md +++ /dev/null @@ -1,70 +0,0 @@ -# nlohmann::basic_json::number_float_t - -```cpp -using number_float_t = NumberFloatType; -``` - -The type used to store JSON numbers (floating-point). - -[RFC 8259](https://tools.ietf.org/html/rfc8259) describes numbers as follows: -> The representation of numbers is similar to that used in most programming languages. A number is represented in base -> 10 using decimal digits. It contains an integer component that may be prefixed with an optional minus sign, which may -> be followed by a fraction part and/or an exponent part. Leading zeros are not allowed. (...) Numeric values that -> cannot be represented in the grammar below (such as Infinity and NaN) are not permitted. - -This description includes both integer and floating-point numbers. However, C++ allows more precise storage if it is -known whether the number is a signed integer, an unsigned integer or a floating-point number. Therefore, three different -types, [`number_integer_t`](number_integer_t.md), [`number_unsigned_t`](number_unsigned_t.md) and `number_float_t` are -used. - -To store floating-point numbers in C++, a type is defined by the template parameter `NumberFloatType` which chooses the -type to use. - -## Notes - -#### Default type - -With the default values for `NumberFloatType` (`double`), the default value for `number_float_t` is `#!cpp double`. - -#### Default behavior - -- The restrictions about leading zeros is not enforced in C++. Instead, leading zeros in floating-point literals will be - ignored. Internally, the value will be stored as decimal number. For instance, the C++ floating-point literal `01.2` - will be serialized to `1.2`. During deserialization, leading zeros yield an error. -- Not-a-number (NaN) values will be serialized to `null`. - -#### Limits - -[RFC 8259](https://tools.ietf.org/html/rfc8259) states: -> This specification allows implementations to set limits on the range and precision of numbers accepted. Since software -> that implements IEEE 754-2008 binary64 (double precision) numbers is generally available and widely used, good -> interoperability can be achieved by implementations that expect no more precision or range than these provide, in the -> sense that implementations will approximate JSON numbers within the expected precision. - -This implementation does exactly follow this approach, as it uses double precision floating-point numbers. Note values -smaller than `-1.79769313486232e+308` and values greater than `1.79769313486232e+308` will be stored as NaN internally -and be serialized to `null`. - -#### Storage - -Floating-point number values are stored directly inside a `basic_json` type. - -## Examples - -??? example - - The following code shows that `number_float_t` is by default, a typedef to `#!cpp double`. - - ```cpp - --8<-- "examples/number_float_t.cpp" - ``` - - Output: - - ```json - --8<-- "examples/number_float_t.output" - ``` - -## Version history - -- Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/number_integer_t.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/number_integer_t.md deleted file mode 100644 index 9bb3835..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/number_integer_t.md +++ /dev/null @@ -1,76 +0,0 @@ -# nlohmann::basic_json::number_integer_t - -```cpp -using number_integer_t = NumberIntegerType; -``` - -The type used to store JSON numbers (integers). - -[RFC 8259](https://tools.ietf.org/html/rfc8259) describes numbers as follows: -> The representation of numbers is similar to that used in most programming languages. A number is represented in base -> 10 using decimal digits. It contains an integer component that may be prefixed with an optional minus sign, which may -> be followed by a fraction part and/or an exponent part. Leading zeros are not allowed. (...) Numeric values that -> cannot be represented in the grammar below (such as Infinity and NaN) are not permitted. - -This description includes both integer and floating-point numbers. However, C++ allows more precise storage if it is -known whether the number is a signed integer, an unsigned integer or a floating-point number. Therefore, three different -types, `number_integer_t`, [`number_unsigned_t`](number_unsigned_t.md) and [`number_float_t`](number_float_t.md) are -used. - -To store integer numbers in C++, a type is defined by the template parameter `NumberIntegerType` which chooses the type -to use. - -## Notes - -#### Default type - -With the default values for `NumberIntegerType` (`std::int64_t`), the default value for `number_integer_t` is -`#!cpp std::int64_t`. - -#### Default behavior - -- The restrictions about leading zeros is not enforced in C++. Instead, leading zeros in integer literals lead to an - interpretation as octal number. Internally, the value will be stored as decimal number. For instance, the C++ integer - literal `010` will be serialized to `8`. During deserialization, leading zeros yield an error. -- Not-a-number (NaN) values will be serialized to `null`. - -#### Limits - -[RFC 8259](https://tools.ietf.org/html/rfc8259) specifies: -> An implementation may set limits on the range and precision of numbers. - -When the default type is used, the maximal integer number that can be stored is `9223372036854775807` (INT64_MAX) and -the minimal integer number that can be stored is `-9223372036854775808` (INT64_MIN). Integer numbers that are out of -range will yield over/underflow when used in a constructor. During deserialization, too large or small integer numbers -will be automatically be stored as [`number_unsigned_t`](number_unsigned_t.md) or [`number_float_t`](number_float_t.md). - -[RFC 8259](https://tools.ietf.org/html/rfc8259) further states: -> Note that when such software is used, numbers that are integers and are in the range $[-2^{53}+1, 2^{53}-1]$ are -> interoperable in the sense that implementations will agree exactly on their numeric values. - -As this range is a subrange of the exactly supported range [INT64_MIN, INT64_MAX], this class's integer type is -interoperable. - -#### Storage - -Integer number values are stored directly inside a `basic_json` type. - -## Examples - -??? example - - The following code shows that `number_integer_t` is by default, a typedef to `#!cpp std::int64_t`. - - ```cpp - --8<-- "examples/number_integer_t.cpp" - ``` - - Output: - - ```json - --8<-- "examples/number_integer_t.output" - ``` - -## Version history - -- Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/number_unsigned_t.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/number_unsigned_t.md deleted file mode 100644 index 8a1540a..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/number_unsigned_t.md +++ /dev/null @@ -1,76 +0,0 @@ -# nlohmann::basic_json::number_unsigned_t - -```cpp -using number_unsigned_t = NumberUnsignedType; -``` - -The type used to store JSON numbers (unsigned). - -[RFC 8259](https://tools.ietf.org/html/rfc8259) describes numbers as follows: -> The representation of numbers is similar to that used in most programming languages. A number is represented in base -> 10 using decimal digits. It contains an integer component that may be prefixed with an optional minus sign, which may -> be followed by a fraction part and/or an exponent part. Leading zeros are not allowed. (...) Numeric values that -> cannot be represented in the grammar below (such as Infinity and NaN) are not permitted. - -This description includes both integer and floating-point numbers. However, C++ allows more precise storage if it is -known whether the number is a signed integer, an unsigned integer or a floating-point number. Therefore, three different -types, [`number_integer_t`](number_integer_t.md), `number_unsigned_t` and [`number_float_t`](number_float_t.md) are -used. - -To store unsigned integer numbers in C++, a type is defined by the template parameter `NumberUnsignedType` which chooses -the type to use. - -## Notes - -#### Default type - -With the default values for `NumberUnsignedType` (`std::uint64_t`), the default value for `number_unsigned_t` is -`#!cpp std::uint64_t`. - -#### Default behavior - -- The restrictions about leading zeros is not enforced in C++. Instead, leading zeros in integer literals lead to an - interpretation as octal number. Internally, the value will be stored as decimal number. For instance, the C++ integer - literal `010` will be serialized to `8`. During deserialization, leading zeros yield an error. -- Not-a-number (NaN) values will be serialized to `null`. - -#### Limits - -[RFC 8259](https://tools.ietf.org/html/rfc8259) specifies: -> An implementation may set limits on the range and precision of numbers. - -When the default type is used, the maximal integer number that can be stored is `18446744073709551615` (UINT64_MAX) and -the minimal integer number that can be stored is `0`. Integer numbers that are out of range will yield over/underflow -when used in a constructor. During deserialization, too large or small integer numbers will be automatically be stored -as [`number_integer_t`](number_integer_t.md) or [`number_float_t`](number_float_t.md). - -[RFC 8259](https://tools.ietf.org/html/rfc8259) further states: -> Note that when such software is used, numbers that are integers and are in the range \f$[-2^{53}+1, 2^{53}-1]\f$ are -> interoperable in the sense that implementations will agree exactly on their numeric values. - -As this range is a subrange (when considered in conjunction with the `number_integer_t` type) of the exactly supported -range [0, UINT64_MAX], this class's integer type is interoperable. - -#### Storage - -Integer number values are stored directly inside a `basic_json` type. - -## Examples - -??? example - - The following code shows that `number_unsigned_t` is by default, a typedef to `#!cpp std::uint64_t`. - - ```cpp - --8<-- "examples/number_unsigned_t.cpp" - ``` - - Output: - - ```json - --8<-- "examples/number_unsigned_t.output" - ``` - -## Version history - -- Added in version 2.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/object.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/object.md deleted file mode 100644 index 9bdbddb..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/object.md +++ /dev/null @@ -1,63 +0,0 @@ -# nlohmann::basic_json::object - -```cpp -static basic_json object(initializer_list_t init = {}); -``` - -Creates a JSON object value from a given initializer list. The initializer lists elements must be pairs, and their first -elements must be strings. If the initializer list is empty, the empty object `#!json {}` is created. - -## Parameters - -`init` (in) -: initializer list with JSON values to create an object from (optional) - -## Return value - -JSON object value - -## Exception safety - -Strong guarantee: if an exception is thrown, there are no changes in the JSON value. - -## Exceptions - -Throws [`type_error.301`](../../home/exceptions.md#jsonexceptiontype_error301) if `init` is not a list of pairs whose -first elements are strings. In this case, no object can be created. When such a value is passed to -`basic_json(initializer_list_t, bool, value_t)`, an array would have been created from the passed initializer list -`init`. See example below. - -## Complexity - -Linear in the size of `init`. - -## Notes - -This function is only added for symmetry reasons. In contrast to the related function `array(initializer_list_t)`, there -are no cases which can only be expressed by this function. That is, any initializer list `init` can also be passed to -the initializer list constructor `basic_json(initializer_list_t, bool, value_t)`. - -## Examples - -??? example - - The following code shows an example for the `object` function. - - ```cpp - --8<-- "examples/object.cpp" - ``` - - Output: - - ```json - --8<-- "examples/object.output" - ``` - -## See also - -- [`basic_json(initializer_list_t)`](basic_json.md) - create a JSON value from an initializer list -- [`array`](array.md) - create a JSON array value from an initializer list - -## Version history - -- Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/object_comparator_t.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/object_comparator_t.md deleted file mode 100644 index d41b982..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/object_comparator_t.md +++ /dev/null @@ -1,32 +0,0 @@ -# nlohmann::basic_json::object_comparator_t - -```cpp -using object_comparator_t = typename object_t::key_compare; -// or -using object_comparator_t = default_object_comparator_t; -``` - -The comparator used by [`object_t`](object_t.md). Defined as `#!cpp typename object_t::key_compare` if available, -and [`default_object_comparator_t`](default_object_comparator_t.md) otherwise. - -## Examples - -??? example - - The example below demonstrates the used object comparator. - - ```cpp - --8<-- "examples/object_comparator_t.cpp" - ``` - - Output: - - ```json - --8<-- "examples/object_comparator_t.output" - ``` - -## Version history - -- Added in version 3.0.0. -- Changed to be conditionally defined as `#!cpp typename object_t::key_compare` or `default_object_comparator_t` in - version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/object_t.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/object_t.md deleted file mode 100644 index 39f68b0..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/object_t.md +++ /dev/null @@ -1,114 +0,0 @@ -# nlohmann::basic_json::object_t - -```cpp -using object_t = ObjectType>>; -``` - -The type used to store JSON objects. - -[RFC 8259](https://tools.ietf.org/html/rfc8259) describes JSON objects as follows: -> An object is an unordered collection of zero or more name/value pairs, where a name is a string and a value is a -> string, number, boolean, null, object, or array. - -To store objects in C++, a type is defined by the template parameters described below. - -## Template parameters - -`ObjectType` -: the container to store objects (e.g., `std::map` or `std::unordered_map`) - -`StringType` -: the type of the keys or names (e.g., `std::string`). The comparison function `std::less` is used to - order elements inside the container. - -`AllocatorType` -: the allocator to use for objects (e.g., `std::allocator`) - -## Notes - -#### Default type - -With the default values for `ObjectType` (`std::map`), `StringType` (`std::string`), and `AllocatorType` -(`std::allocator`), the default value for `object_t` is: - -```cpp -// until C++14 -std::map< - std::string, // key_type - basic_json, // value_type - std::less, // key_compare - std::allocator> // allocator_type -> - -// since C++14 -std::map< - std::string, // key_type - basic_json, // value_type - std::less<>, // key_compare - std::allocator> // allocator_type -> -``` - -See [`default_object_comparator_t`](default_object_comparator_t.md) for more information. - -#### Behavior - -The choice of `object_t` influences the behavior of the JSON class. With the default type, objects have the following -behavior: - -- When all names are unique, objects will be interoperable in the sense that all software implementations receiving that - object will agree on the name-value mappings. -- When the names within an object are not unique, it is unspecified which one of the values for a given key will be - chosen. For instance, `#!json {"key": 2, "key": 1}` could be equal to either `#!json {"key": 1}` or - `#!json {"key": 2}`. -- Internally, name/value pairs are stored in lexicographical order of the names. Objects will also be serialized (see - [`dump`](dump.md)) in this order. For instance, `#!json {"b": 1, "a": 2}` and `#!json {"a": 2, "b": 1}` will be stored - and serialized as `#!json {"a": 2, "b": 1}`. -- When comparing objects, the order of the name/value pairs is irrelevant. This makes objects interoperable in the sense - that they will not be affected by these differences. For instance, `#!json {"b": 1, "a": 2}` and - `#!json {"a": 2, "b": 1}` will be treated as equal. - -#### Limits - -[RFC 8259](https://tools.ietf.org/html/rfc8259) specifies: -> An implementation may set limits on the maximum depth of nesting. - -In this class, the object's limit of nesting is not explicitly constrained. However, a maximum depth of nesting may be -introduced by the compiler or runtime environment. A theoretical limit can be queried by calling the -[`max_size`](max_size.md) function of a JSON object. - -#### Storage - -Objects are stored as pointers in a `basic_json` type. That is, for any access to object values, a pointer of type -`object_t*` must be dereferenced. - -#### Object key order - -The order name/value pairs are added to the object is *not* preserved by the library. Therefore, iterating an object may -return name/value pairs in a different order than they were originally stored. In fact, keys will be traversed in -alphabetical order as `std::map` with `std::less` is used by default. Please note this behavior conforms to -[RFC 8259](https://tools.ietf.org/html/rfc8259), because any order implements the specified "unordered" nature of JSON -objects. - -## Examples - -??? example - - The following code shows that `object_t` is by default, a typedef to `#!cpp std::map`. - - ```cpp - --8<-- "examples/object_t.cpp" - ``` - - Output: - - ```json - --8<-- "examples/object_t.output" - ``` - -## Version history - -- Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator+=.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator+=.md deleted file mode 100644 index dc5f2ec..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator+=.md +++ /dev/null @@ -1,110 +0,0 @@ -# nlohmann::basic_json::operator+= - -```cpp -// (1) -reference operator+=(basic_json&& val); -reference operator+=(const basic_json& val); - -// (2) -reference operator+=(const typename object_t::value_type& val); - -// (3) -reference operator+=(initializer_list_t init); -``` - -1. Appends the given element `val` to the end of the JSON array. If the function is called on a JSON null value, an - empty array is created before appending `val`. - -2. Inserts the given element `val` to the JSON object. If the function is called on a JSON null value, an empty object - is created before inserting `val`. - -3. This function allows using `operator+=` with an initializer list. In case - - 1. the current value is an object, - 2. the initializer list `init` contains only two elements, and - 3. the first element of `init` is a string, - - `init` is converted into an object element and added using `operator+=(const typename object_t::value_type&)`. - Otherwise, `init` is converted to a JSON value and added using `operator+=(basic_json&&)`. - -## Parameters - -`val` (in) -: the value to add to the JSON array/object - -`init` (in) -: an initializer list - -## Return value - -`#!cpp *this` - -## Exceptions - -All functions can throw the following exception: - - Throws [`type_error.308`](../../home/exceptions.md#jsonexceptiontype_error308) when called on a type other than - JSON array or null; example: `"cannot use operator+=() with number"` - -## Complexity - -1. Amortized constant. -2. Logarithmic in the size of the container, O(log(`size()`)). -3. Linear in the size of the initializer list `init`. - -## Notes - -(3) This function is required to resolve an ambiguous overload error, because pairs like `{"key", "value"}` can be both -interpreted as `object_t::value_type` or `std::initializer_list`, see -[#235](https://github.com/nlohmann/json/issues/235) for more information. - -## Examples - -??? example "Example: (1) add element to array" - - The example shows how `push_back()` and `+=` can be used to add elements to a JSON array. Note how the `null` value - was silently converted to a JSON array. - - ```cpp - --8<-- "examples/push_back.cpp" - ``` - - Output: - - ```json - --8<-- "examples/push_back.output" - ``` - -??? example "Example: (2) add element to object" - - The example shows how `push_back()` and `+=` can be used to add elements to a JSON object. Note how the `null` value - was silently converted to a JSON object. - - ```cpp - --8<-- "examples/push_back__object_t__value.cpp" - ``` - - Output: - - ```json - --8<-- "examples/push_back__object_t__value.output" - ``` - -??? example "Example: (3) add to object from initializer list" - - The example shows how initializer lists are treated as objects when possible. - - ```cpp - --8<-- "examples/push_back__initializer_list.cpp" - ``` - - Output: - - ```json - --8<-- "examples/push_back__initializer_list.output" - ``` - -## Version history - -1. Since version 1.0.0. -2. Since version 1.0.0. -2. Since version 2.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator=.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator=.md deleted file mode 100644 index 4e0b914..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator=.md +++ /dev/null @@ -1,43 +0,0 @@ -# nlohmann::basic_json::operator= - -```cpp -basic_json& operator=(basic_json other) noexcept ( - std::is_nothrow_move_constructible::value && - std::is_nothrow_move_assignable::value && - std::is_nothrow_move_constructible::value && - std::is_nothrow_move_assignable::value -); -``` - -Copy assignment operator. Copies a JSON value via the "copy and swap" strategy: It is expressed in terms of the copy -constructor, destructor, and the `swap()` member function. - -## Parameters - -`other` (in) -: value to copy from - -## Complexity - -Linear. - -## Examples - -??? example - - The code below shows and example for the copy assignment. It creates a copy of value `a` which is then swapped with - `b`. Finally, the copy of `a` (which is the null value after the swap) is destroyed. - - ```cpp - --8<-- "examples/basic_json__copyassignment.cpp" - ``` - - Output: - - ```json - --8<-- "examples/basic_json__copyassignment.output" - ``` - -## Version history - -- Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator[].md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator[].md deleted file mode 100644 index 51dd858..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator[].md +++ /dev/null @@ -1,241 +0,0 @@ -# nlohmann::basic_json::operator[] - -```cpp -// (1) -reference operator[](size_type idx); -const_reference operator[](size_type idx) const; - -// (2) -reference operator[](typename object_t::key_type key); -const_reference operator[](const typename object_t::key_type& key) const; - -// (3) -template -reference operator[](KeyType&& key); -template -const_reference operator[](KeyType&& key) const; - -// (4) -reference operator[](const json_pointer& ptr); -const_reference operator[](const json_pointer& ptr) const; -``` - -1. Returns a reference to the array element at specified location `idx`. -2. Returns a reference to the object element with specified key `key`. The non-const qualified overload takes the key by - value. -3. See 2. This overload is only available if `KeyType` is comparable with `#!cpp typename object_t::key_type` and - `#!cpp typename object_comparator_t::is_transparent` denotes a type. -4. Returns a reference to the element with specified JSON pointer `ptr`. - -## Template parameters - -`KeyType` -: A type for an object key other than [`json_pointer`](../json_pointer/index.md) that is comparable with - [`string_t`](string_t.md) using [`object_comparator_t`](object_comparator_t.md). - This can also be a string view (C++17). - -## Parameters - -`idx` (in) -: index of the element to access - -`key` (in) -: object key of the element to access - -`ptr` (in) -: JSON pointer to the desired element - -## Return value - -1. (const) reference to the element at index `idx` -2. (const) reference to the element at key `key` -3. (const) reference to the element at key `key` -4. (const) reference to the element pointed to by `ptr` - -## Exception safety - -Strong exception safety: if an exception occurs, the original value stays intact. - -## Exceptions - -1. The function can throw the following exceptions: - - Throws [`type_error.305`](../../home/exceptions.md#jsonexceptiontype_error305) if the JSON value is not an array - or null; in that case, using the `[]` operator with an index makes no sense. -2. The function can throw the following exceptions: - - Throws [`type_error.305`](../../home/exceptions.md#jsonexceptiontype_error305) if the JSON value is not an object - or null; in that case, using the `[]` operator with a key makes no sense. -3. See 2. -4. The function can throw the following exceptions: - - Throws [`parse_error.106`](../../home/exceptions.md#jsonexceptionparse_error106) if an array index in the passed - JSON pointer `ptr` begins with '0'. - - Throws [`parse_error.109`](../../home/exceptions.md#jsonexceptionparse_error109) if an array index in the passed - JSON pointer `ptr` is not a number. - - Throws [`out_of_range.402`](../../home/exceptions.md#jsonexceptionout_of_range402) if the array index '-' is used - in the passed JSON pointer `ptr` for the const version. - - Throws [`out_of_range.404`](../../home/exceptions.md#jsonexceptionout_of_range404) if the JSON pointer `ptr` can - not be resolved. - -## Complexity - -1. Constant if `idx` is in the range of the array. Otherwise, linear in `idx - size()`. -2. Logarithmic in the size of the container. -3. Logarithmic in the size of the container. -4. Logarithmic in the size of the container. - -## Notes - -!!! danger "Undefined behavior and runtime assertions" - - 1. If the element with key `idx` does not exist, the behavior is undefined. - 2. If the element with key `key` does not exist, the behavior is undefined and is **guarded by a - [runtime assertion](../../features/assertions.md)**! - -1. The non-const version may add values: If `idx` is beyond the range of the array (i.e., `idx >= size()`), then the - array is silently filled up with `#!json null` values to make `idx` a valid reference to the last stored element. In - case the value was `#!json null` before, it is converted to an array. - -2. If `key` is not found in the object, then it is silently added to the object and filled with a `#!json null` value to - make `key` a valid reference. In case the value was `#!json null` before, it is converted to an object. - -3. See 2. - -4. `null` values are created in arrays and objects if necessary. - - In particular: - - - If the JSON pointer points to an object key that does not exist, it is created and filled with a `#!json null` - value before a reference to it is returned. - - If the JSON pointer points to an array index that does not exist, it is created and filled with a `#!json null` - value before a reference to it is returned. All indices between the current maximum and the given index are also - filled with `#!json null`. - - The special value `-` is treated as a synonym for the index past the end. - -## Examples - -??? example "Example: (1) access specified array element" - - The example below shows how array elements can be read and written using `[]` operator. Note the addition of - `#!json null` values. - - ```cpp - --8<-- "examples/operator_array__size_type.cpp" - ``` - - Output: - - ```json - --8<-- "examples/operator_array__size_type.output" - ``` - -??? example "Example: (1) access specified array element (const)" - - The example below shows how array elements can be read using the `[]` operator. - - ```cpp - --8<-- "examples/operator_array__size_type_const.cpp" - ``` - - Output: - - ```json - --8<-- "examples/operator_array__size_type_const.output" - ``` - -??? example "Example: (2) access specified object element" - - The example below shows how object elements can be read and written using the `[]` operator. - - ```cpp - --8<-- "examples/operator_array__object_t_key_type.cpp" - ``` - - Output: - - ```json - --8<-- "examples/operator_array__object_t_key_type.output" - ``` - -??? example "Example: (2) access specified object element (const)" - - The example below shows how object elements can be read using the `[]` operator. - - ```cpp - --8<-- "examples/operator_array__object_t_key_type_const.cpp" - ``` - - Output: - - ```json - --8<-- "examples/operator_array__object_t_key_type_const.output" - ``` - -??? example "Example: (3) access specified object element using string_view" - - The example below shows how object elements can be read using the `[]` operator. - - ```cpp - --8<-- "examples/operator_array__keytype.c++17.cpp" - ``` - - Output: - - ```json - --8<-- "examples/operator_array__keytype.c++17.output" - ``` - -??? example "Example: (3) access specified object element using string_view (const)" - - The example below shows how object elements can be read using the `[]` operator. - - ```cpp - --8<-- "examples/operator_array__keytype_const.c++17.cpp" - ``` - - Output: - - ```json - --8<-- "examples/operator_array__keytype_const.c++17.output" - ``` - -??? example "Example: (4) access specified element via JSON Pointer" - - The example below shows how values can be read and written using JSON Pointers. - - ```cpp - --8<-- "examples/operator_array__json_pointer.cpp" - ``` - - Output: - - ```json - --8<-- "examples/operator_array__json_pointer.output" - ``` - -??? example "Example: (4) access specified element via JSON Pointer (const)" - - The example below shows how values can be read using JSON Pointers. - - ```cpp - --8<-- "examples/operator_array__json_pointer_const.cpp" - ``` - - Output: - - ```json - --8<-- "examples/operator_array__json_pointer_const.output" - ``` - -## See also - -- documentation on [unchecked access](../../features/element_access/unchecked_access.md) -- documentation on [runtime assertions](../../features/assertions.md) -- see [`at`](at.md) for access by reference with range checking -- see [`value`](value.md) for access with default value - -## Version history - -1. Added in version 1.0.0. -2. Added in version 1.0.0. Added overloads for `T* key` in version 1.1.0. Removed overloads for `T* key` (replaced by 3) - in version 3.11.0. -3. Added in version 3.11.0. -4. Added in version 2.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator_ValueType.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator_ValueType.md deleted file mode 100644 index bf38a3d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator_ValueType.md +++ /dev/null @@ -1,82 +0,0 @@ -# nlohmann::basic_json::operator ValueType - -```cpp -template -JSON_EXPLICIT operator ValueType() const; -``` - -Implicit type conversion between the JSON value and a compatible value. The call is realized by calling -[`get()`](get.md). See [Notes](#notes) for the meaning of `JSON_EXPLICIT`. - -## Template parameters - -`ValueType` -: the value type to return - -## Return value - -copy of the JSON value, converted to `ValueType` - -## Exceptions - -Depends on what `json_serializer` `from_json()` method throws - -## Complexity - -Linear in the size of the JSON value. - -## Notes - -!!! note "Definition of `JSON_EXPLICIT`" - - By default `JSON_EXPLICIT` is defined to the empty string, so the signature is: - - ```cpp - template - operator ValueType() const; - ``` - - If [`JSON_USE_IMPLICIT_CONVERSIONS`](../macros/json_use_implicit_conversions.md) is set to `0`, - `JSON_EXPLICIT` is defined to `#!cpp explicit`: - - ```cpp - template - explicit operator ValueType() const; - ``` - - That is, implicit conversions can be switched off by defining - [`JSON_USE_IMPLICIT_CONVERSIONS`](../macros/json_use_implicit_conversions.md) to `0`. - -!!! info "Future behavior change" - - Implicit conversions will be switched off by default in the next major release of the library. That is, - `JSON_EXPLICIT` will be set to `#!cpp explicit` by default. - - You can prepare existing code by already defining - [`JSON_USE_IMPLICIT_CONVERSIONS`](../macros/json_use_implicit_conversions.md) to `0` and replace any implicit - conversions with calls to [`get`](../basic_json/get.md). - -## Examples - -??? example - - The example below shows several conversions from JSON values to other types. There are a few things to note: (1) - Floating-point numbers can be converted to integers, (2) A JSON array can be converted to a standard - `std::vector`, (3) A JSON object can be converted to C++ associative containers such as - `std::unordered_map`. - - ```cpp - --8<-- "examples/operator__ValueType.cpp" - ``` - - Output: - - ```json - --8<-- "examples/operator__ValueType.output" - ``` - -## Version history - -- Since version 1.0.0. -- Macros `JSON_EXPLICIT`/[`JSON_USE_IMPLICIT_CONVERSIONS`](../macros/json_use_implicit_conversions.md) added - in version 3.9.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator_eq.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator_eq.md deleted file mode 100644 index a2ce615..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator_eq.md +++ /dev/null @@ -1,168 +0,0 @@ -# nlohmann::basic_json::operator== - -```cpp -// until C++20 -bool operator==(const_reference lhs, const_reference rhs) noexcept; // (1) - -template -bool operator==(const_reference lhs, const ScalarType rhs) noexcept; // (2) - -template -bool operator==(ScalarType lhs, const const_reference rhs) noexcept; // (2) - -// since C++20 -class basic_json { - bool operator==(const_reference rhs) const noexcept; // (1) - - template - bool operator==(ScalarType rhs) const noexcept; // (2) -}; -``` - -1. Compares two JSON values for equality according to the following rules: - - Two JSON values are equal if (1) neither value is discarded, or (2) they are of the same type and their stored - values are the same according to their respective `operator==`. - - Integer and floating-point numbers are automatically converted before comparison. - -2. Compares a JSON value and a scalar or a scalar and a JSON value for equality by converting the - scalar to a JSON value and comparing both JSON values according to 1. - -## Template parameters - -`ScalarType` -: a scalar type according to `std::is_scalar::value` - -## Parameters - -`lhs` (in) -: first value to consider - -`rhs` (in) -: second value to consider - -## Return value - -whether the values `lhs`/`*this` and `rhs` are equal - -## Exception safety - -No-throw guarantee: this function never throws exceptions. - -## Complexity - -Linear. - -## Notes - -!!! note "Comparing special values" - - - `NaN` values are unordered within the domain of numbers. - The following comparisons all yield `#!cpp false`: - 1. Comparing a `NaN` with itself. - 2. Comparing a `NaN` with another `NaN`. - 3. Comparing a `NaN` and any other number. - - JSON `#!cpp null` values are all equal. - - Discarded values never compare equal to themselves. - -!!! note "Comparing floating-point numbers" - - Floating-point numbers inside JSON values numbers are compared with `json::number_float_t::operator==` which is - `double::operator==` by default. To compare floating-point while respecting an epsilon, an alternative - [comparison function](https://github.com/mariokonrad/marnav/blob/master/include/marnav/math/floatingpoint.hpp#L34-#L39) - could be used, for instance - - ```cpp - template::value, T>::type> - inline bool is_same(T a, T b, T epsilon = std::numeric_limits::epsilon()) noexcept - { - return std::abs(a - b) <= epsilon; - } - ``` - - Or you can self-defined operator equal function like this: - - ```cpp - bool my_equal(const_reference lhs, const_reference rhs) - { - const auto lhs_type lhs.type(); - const auto rhs_type rhs.type(); - if (lhs_type == rhs_type) - { - switch(lhs_type) - // self_defined case - case value_t::number_float: - return std::abs(lhs - rhs) <= std::numeric_limits::epsilon(); - // other cases remain the same with the original - ... - } - ... - } - ``` - -!!! note "Comparing different `basic_json` specializations" - - Comparing different `basic_json` specializations can have surprising effects. For instance, the result of comparing - the JSON objects - - ```json - { - "version": 1, - "type": "integer" - } - ``` - - and - - ```json - { - "type": "integer", - "version": 1 - } - ``` - - depends on whether [`nlohmann::json`](../json.md) or [`nlohmann::ordered_json`](../ordered_json.md) is used: - - ```cpp - --8<-- "examples/operator__equal__specializations.cpp" - ``` - - Output: - - ```json - --8<-- "examples/operator__equal__specializations.output" - ``` - -## Examples - -??? example - - The example demonstrates comparing several JSON types. - - ```cpp - --8<-- "examples/operator__equal.cpp" - ``` - - Output: - - ```json - --8<-- "examples/operator__equal.output" - ``` - -??? example - - The example demonstrates comparing several JSON types against the null pointer (JSON `#!json null`). - - ```cpp - --8<-- "examples/operator__equal__nullptr_t.cpp" - ``` - - Output: - - ```json - --8<-- "examples/operator__equal__nullptr_t.output" - ``` - -## Version history - -1. Added in version 1.0.0. Added C++20 member functions in version 3.11.0. -2. Added in version 1.0.0. Added C++20 member functions in version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator_ge.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator_ge.md deleted file mode 100644 index d4e2fb4..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator_ge.md +++ /dev/null @@ -1,86 +0,0 @@ -# nlohmann::basic_json::operator>= - -```cpp -// until C++20 -bool operator>=(const_reference lhs, const_reference rhs) noexcept; // (1) - -template -bool operator>=(const_reference lhs, const ScalarType rhs) noexcept; // (2) - -template -bool operator>=(ScalarType lhs, const const_reference rhs) noexcept; // (2) -``` - -1. Compares whether one JSON value `lhs` is greater than or equal to another JSON value `rhs` according to the following - rules: - - The comparison always yields `#!cpp false` if (1) either operand is discarded, or (2) either operand is `NaN` and - the other operand is either `NaN` or any other number. - - Otherwise, returns the result of `#!cpp !(lhs < rhs)` (see [**operator<**](operator_lt.md)). - -2. Compares whether a JSON value is greater than or equal to a scalar or a scalar is greater than or equal to a JSON - value by converting the scalar to a JSON value and comparing both JSON values according to 1. - -## Template parameters - -`ScalarType` -: a scalar type according to `std::is_scalar::value` - -## Parameters - -`lhs` (in) -: first value to consider - -`rhs` (in) -: second value to consider - -## Return value - -whether `lhs` is less than or equal to `rhs` - -## Exception safety - -No-throw guarantee: this function never throws exceptions. - -## Complexity - -Linear. - -## Notes - -!!! note "Comparing `NaN`" - - `NaN` values are unordered within the domain of numbers. - The following comparisons all yield `#!cpp false`: - 1. Comparing a `NaN` with itself. - 2. Comparing a `NaN` with another `NaN`. - 3. Comparing a `NaN` and any other number. - -!!! note "Operator overload resolution" - - Since C++20 overload resolution will consider the _rewritten candidate_ generated from - [`operator<=>`](operator_spaceship.md). - -## Examples - -??? example - - The example demonstrates comparing several JSON types. - - ```cpp - --8<-- "examples/operator__greaterequal.cpp" - ``` - - Output: - - ```json - --8<-- "examples/operator__greaterequal.output" - ``` - -## See also - -- [**operator<=>**](operator_spaceship.md) comparison: 3-way - -## Version history - -1. Added in version 1.0.0. Conditionally removed since C++20 in version 3.11.0. -2. Added in version 1.0.0. Conditionally removed since C++20 in version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator_gt.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator_gt.md deleted file mode 100644 index 9516656..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator_gt.md +++ /dev/null @@ -1,86 +0,0 @@ -# nlohmann::basic_json::operator> - -```cpp -// until C++20 -bool operator>(const_reference lhs, const_reference rhs) noexcept; // (1) - -template -bool operator>(const_reference lhs, const ScalarType rhs) noexcept; // (2) - -template -bool operator>(ScalarType lhs, const const_reference rhs) noexcept; // (2) -``` - -1. Compares whether one JSON value `lhs` is greater than another JSON value `rhs` according to the - following rules: - - The comparison always yields `#!cpp false` if (1) either operand is discarded, or (2) either - operand is `NaN` and the other operand is either `NaN` or any other number. - - Otherwise, returns the result of `#!cpp !(lhs <= rhs)` (see [**operator<=**](operator_le.md)). - -2. Compares wether a JSON value is greater than a scalar or a scalar is greater than a JSON value by - converting the scalar to a JSON value and comparing both JSON values according to 1. - -## Template parameters - -`ScalarType` -: a scalar type according to `std::is_scalar::value` - -## Parameters - -`lhs` (in) -: first value to consider - -`rhs` (in) -: second value to consider - -## Return value - -whether `lhs` is greater than `rhs` - -## Exception safety - -No-throw guarantee: this function never throws exceptions. - -## Complexity - -Linear. - -## Notes - -!!! note "Comparing `NaN`" - - `NaN` values are unordered within the domain of numbers. - The following comparisons all yield `#!cpp false`: - 1. Comparing a `NaN` with itself. - 2. Comparing a `NaN` with another `NaN`. - 3. Comparing a `NaN` and any other number. - -!!! note "Operator overload resolution" - - Since C++20 overload resolution will consider the _rewritten candidate_ generated from - [`operator<=>`](operator_spaceship.md). - -## Examples - -??? example - - The example demonstrates comparing several JSON types. - - ```cpp - --8<-- "examples/operator__greater.cpp" - ``` - - Output: - - ```json - --8<-- "examples/operator__greater.output" - ``` - -## See also - -- [**operator<=>**](operator_spaceship.md) comparison: 3-way - -## Version history - -1. Added in version 1.0.0. Conditionally removed since C++20 in version 3.11.0. -2. Added in version 1.0.0. Conditionally removed since C++20 in version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator_le.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator_le.md deleted file mode 100644 index 7b648e0..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator_le.md +++ /dev/null @@ -1,87 +0,0 @@ -# nlohmann::basic_json::operator<= - -```cpp -// until C++20 -bool operator<=(const_reference lhs, const_reference rhs) noexcept; // (1) - -template -bool operator<=(const_reference lhs, const ScalarType rhs) noexcept; // (2) - -template -bool operator<=(ScalarType lhs, const const_reference rhs) noexcept; // (2) -``` - -1. Compares whether one JSON value `lhs` is less than or equal to another JSON value `rhs` - according to the following rules: - - The comparison always yields `#!cpp false` if (1) either operand is discarded, or (2) either - operand is `NaN` and the other operand is either `NaN` or any other number. - - Otherwise, returns the result of `#!cpp !(rhs < lhs)` (see [**operator<**](operator_lt.md)). - -1. Compares wether a JSON value is less than or equal to a scalar or a scalar is less than or equal - to a JSON value by converting the scalar to a JSON value and comparing both JSON values according - to 1. - -## Template parameters - -`ScalarType` -: a scalar type according to `std::is_scalar::value` - -## Parameters - -`lhs` (in) -: first value to consider - -`rhs` (in) -: second value to consider - -## Return value - -whether `lhs` is less than or equal to `rhs` - -## Exception safety - -No-throw guarantee: this function never throws exceptions. - -## Complexity - -Linear. - -## Notes - -!!! note "Comparing `NaN`" - - `NaN` values are unordered within the domain of numbers. - The following comparisons all yield `#!cpp false`: - 1. Comparing a `NaN` with itself. - 2. Comparing a `NaN` with another `NaN`. - 3. Comparing a `NaN` and any other number. - -!!! note "Operator overload resolution" - - Since C++20 overload resolution will consider the _rewritten candidate_ generated from - [`operator<=>`](operator_spaceship.md). - -## Examples - -??? example - - The example demonstrates comparing several JSON types. - - ```cpp - --8<-- "examples/operator__lessequal.cpp" - ``` - - Output: - - ```json - --8<-- "examples/operator__lessequal.output" - ``` - -## See also - -- [**operator<=>**](operator_spaceship.md) comparison: 3-way - -## Version history - -1. Added in version 1.0.0. Conditionally removed since C++20 in version 3.11.0. -2. Added in version 1.0.0. Conditionally removed since C++20 in version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator_lt.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator_lt.md deleted file mode 100644 index b5d191e..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator_lt.md +++ /dev/null @@ -1,96 +0,0 @@ -# nlohmann::basic_json::operator< - -```cpp -// until C++20 -bool operator<(const_reference lhs, const_reference rhs) noexcept; // (1) - -template -bool operator<(const_reference lhs, const ScalarType rhs) noexcept; // (2) - -template -bool operator<(ScalarType lhs, const const_reference rhs) noexcept; // (2) -``` - -1. Compares whether one JSON value `lhs` is less than another JSON value `rhs` according to the - following rules: - - If either operand is discarded, the comparison yields `#!cpp false`. - - If both operands have the same type, the values are compared using their respective `operator<`. - - Integer and floating-point numbers are automatically converted before comparison. - - In case `lhs` and `rhs` have different types, the values are ignored and the order of the types - is considered, which is: - 1. null - 2. boolean - 3. number (all types) - 4. object - 5. array - 6. string - 7. binary - For instance, any boolean value is considered less than any string. - -2. Compares wether a JSON value is less than a scalar or a scalar is less than a JSON value by converting - the scalar to a JSON value and comparing both JSON values according to 1. - -## Template parameters - -`ScalarType` -: a scalar type according to `std::is_scalar::value` - -## Parameters - -`lhs` (in) -: first value to consider - -`rhs` (in) -: second value to consider - -## Return value - -whether `lhs` is less than `rhs` - -## Exception safety - -No-throw guarantee: this function never throws exceptions. - -## Complexity - -Linear. - -## Notes - -!!! note "Comparing `NaN`" - - `NaN` values are unordered within the domain of numbers. - The following comparisons all yield `#!cpp false`: - 1. Comparing a `NaN` with itself. - 2. Comparing a `NaN` with another `NaN`. - 3. Comparing a `NaN` and any other number. - -!!! note "Operator overload resolution" - - Since C++20 overload resolution will consider the _rewritten candidate_ generated from - [`operator<=>`](operator_spaceship.md). - -## Examples - -??? example - - The example demonstrates comparing several JSON types. - - ```cpp - --8<-- "examples/operator__less.cpp" - ``` - - Output: - - ```json - --8<-- "examples/operator__less.output" - ``` - -## See also - -- [**operator<=>**](operator_spaceship.md) comparison: 3-way - -## Version history - -1. Added in version 1.0.0. Conditionally removed since C++20 in version 3.11.0. -2. Added in version 1.0.0. Conditionally removed since C++20 in version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator_ne.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator_ne.md deleted file mode 100644 index 982a067..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator_ne.md +++ /dev/null @@ -1,98 +0,0 @@ -# nlohmann::basic_json::operator!= - -```cpp -// until C++20 -bool operator!=(const_reference lhs, const_reference rhs) noexcept; // (1) - -template -bool operator!=(const_reference lhs, const ScalarType rhs) noexcept; // (2) - -template -bool operator!=(ScalarType lhs, const const_reference rhs) noexcept; // (2) - -// since C++20 -class basic_json { - bool operator!=(const_reference rhs) const noexcept; // (1) - - template - bool operator!=(ScalarType rhs) const noexcept; // (2) -}; -``` - -1. Compares two JSON values for inequality according to the following rules: - - The comparison always yields `#!cpp false` if (1) either operand is discarded, or (2) either operand is `NaN` and - the other operand is either `NaN` or any other number. - - Otherwise, returns the result of `#!cpp !(lhs == rhs)` (until C++20) or `#!cpp !(*this == rhs)` (since C++20). - -2. Compares a JSON value and a scalar or a scalar and a JSON value for inequality by converting the scalar to a JSON - value and comparing both JSON values according to 1. - -## Template parameters - -`ScalarType` -: a scalar type according to `std::is_scalar::value` - -## Parameters - -`lhs` (in) -: first value to consider - -`rhs` (in) -: second value to consider - -## Return value - -whether the values `lhs`/`*this` and `rhs` are not equal - -## Exception safety - -No-throw guarantee: this function never throws exceptions. - -## Complexity - -Linear. - -## Notes - -!!! note "Comparing `NaN`" - - `NaN` values are unordered within the domain of numbers. - The following comparisons all yield `#!cpp false`: - 1. Comparing a `NaN` with itself. - 2. Comparing a `NaN` with another `NaN`. - 3. Comparing a `NaN` and any other number. - -## Examples - -??? example - - The example demonstrates comparing several JSON types. - - ```cpp - --8<-- "examples/operator__notequal.cpp" - ``` - - Output: - - ```json - --8<-- "examples/operator__notequal.output" - ``` - -??? example - - The example demonstrates comparing several JSON types against the null pointer (JSON `#!json null`). - - ```cpp - --8<-- "examples/operator__notequal__nullptr_t.cpp" - ``` - - Output: - - ```json - --8<-- "examples/operator__notequal__nullptr_t.output" - ``` - -## Version history - -1. Added in version 1.0.0. Added C++20 member functions in version 3.11.0. -2. Added in version 1.0.0. Added C++20 member functions in version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator_spaceship.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator_spaceship.md deleted file mode 100644 index 9e91d0d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator_spaceship.md +++ /dev/null @@ -1,100 +0,0 @@ -# nlohmann::basic_json::operator<=> - -```cpp -// since C++20 -class basic_json { - std::partial_ordering operator<=>(const_reference rhs) const noexcept; // (1) - - template - std::partial_ordering operator<=>(const ScalarType rhs) const noexcept; // (2) -}; -``` - -1. 3-way compares two JSON values producing a result of type `std::partial_ordering` according to the following rules: - - Two JSON values compare with a result of `std::partial_ordering::unordered` if either value is discarded. - - If both JSON values are of the same type, the result is produced by 3-way comparing their stored values using - their respective `operator<=>`. - - Integer and floating-point numbers are converted to their common type and then 3-way compared using their - respective `operator<=>`. - For instance, comparing an integer and a floating-point value will 3-way compare the first value converted to - floating-point with the second value. - - Otherwise, yields a result by comparing the type (see [`value_t`](value_t.md)). - -2. 3-way compares a JSON value and a scalar or a scalar and a JSON value by converting the scalar to a JSON value and - 3-way comparing both JSON values (see 1). - -## Template parameters - -`ScalarType` -: a scalar type according to `std::is_scalar::value` - -## Parameters - -`rhs` (in) -: second value to consider - -## Return value - -the `std::partial_ordering` of the 3-way comparison of `*this` and `rhs` - -## Exception safety - -No-throw guarantee: this function never throws exceptions. - -## Complexity - -Linear. - -## Notes - -!!! note "Comparing `NaN`" - - - `NaN` values are unordered within the domain of numbers. - The following comparisons all yield `std::partial_ordering::unordered`: - 1. Comparing a `NaN` with itself. - 2. Comparing a `NaN` with another `NaN`. - 3. Comparing a `NaN` and any other number. - -## Examples - -??? example "Example: (1) comparing JSON values" - - The example demonstrates comparing several JSON values. - - ```cpp - --8<-- "examples/operator_spaceship__const_reference.c++20.cpp" - ``` - - Output: - - ```json - --8<-- "examples/operator_spaceship__const_reference.c++20.output" - ``` - -??? example "Example: (2) comparing JSON values and scalars" - - The example demonstrates comparing several JSON values and scalars. - - ```cpp - --8<-- "examples/operator_spaceship__scalartype.c++20.cpp" - ``` - - Output: - - ```json - --8<-- "examples/operator_spaceship__scalartype.c++20.output" - ``` - -## See also - -- [**operator==**](operator_eq.md) - comparison: equal -- [**operator!=**](operator_ne.md) - comparison: not equal -- [**operator<**](operator_lt.md) - comparison: less than -- [**operator<=**](operator_le.md) - comparison: less than or equal -- [**operator>**](operator_gt.md) - comparison: greater than -- [**operator>=**](operator_ge.md) - comparison: greater than or equal - -## Version history - -1. Added in version 3.11.0. -2. Added in version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator_value_t.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator_value_t.md deleted file mode 100644 index 0f08f42..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/operator_value_t.md +++ /dev/null @@ -1,54 +0,0 @@ -# nlohmann::basic_json::operator value_t - -```cpp -constexpr operator value_t() const noexcept; -``` - -Return the type of the JSON value as a value from the [`value_t`](value_t.md) enumeration. - -## Return value - -the type of the JSON value - -| Value type | return value | -|---------------------------|----------------------------| -| `#!json null` | `value_t::null` | -| boolean | `value_t::boolean` | -| string | `value_t::string` | -| number (integer) | `value_t::number_integer` | -| number (unsigned integer) | `value_t::number_unsigned` | -| number (floating-point) | `value_t::number_float` | -| object | `value_t::object` | -| array | `value_t::array` | -| binary | `value_t::binary` | -| discarded | `value_t::discarded` | - -## Exception safety - -No-throw guarantee: this member function never throws exceptions. - -## Complexity - -Constant. - -## Examples - -??? example - - The following code exemplifies `operator value_t()` for all JSON types. - - ```cpp - --8<-- "examples/operator__value_t.cpp" - ``` - - Output: - - ```json - --8<-- "examples/operator__value_t.output" - ``` - -## Version history - -- Added in version 1.0.0. -- Added unsigned integer type in version 2.0.0. -- Added binary type in version 3.8.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/other_error.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/other_error.md deleted file mode 100644 index 9a83340..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/other_error.md +++ /dev/null @@ -1,67 +0,0 @@ -# nlohmann::basic_json::other_error - -```cpp -class other_error : public exception; -``` - -This exception is thrown in case of errors that cannot be classified with the other exception types. - -Exceptions have ids 5xx (see [list of other errors](../../home/exceptions.md#further-exceptions)). - -```plantuml -std::exception <|-- basic_json::exception -basic_json::exception <|-- basic_json::parse_error -basic_json::exception <|-- basic_json::invalid_iterator -basic_json::exception <|-- basic_json::type_error -basic_json::exception <|-- basic_json::out_of_range -basic_json::exception <|-- basic_json::other_error - -interface std::exception {} - -class basic_json::exception { - + const int id - + const char* what() const -} - -class basic_json::parse_error { - + const std::size_t byte -} - -class basic_json::other_error #FFFF00 {} -``` - -## Member functions - -- **what** - returns explanatory string - -## Member variables - -- **id** - the id of the exception - -## Examples - -??? example - - The following code shows how a `other_error` exception can be caught. - - ```cpp - --8<-- "examples/other_error.cpp" - ``` - - Output: - - ```json - --8<-- "examples/other_error.output" - ``` - -## See also - -- [List of other errors](../../home/exceptions.md#further-exceptions) -- [`parse_error`](parse_error.md) for exceptions indicating a parse error -- [`invalid_iterator`](invalid_iterator.md) for exceptions indicating errors with iterators -- [`type_error`](type_error.md) for exceptions indicating executing a member function with a wrong type -- [`out_of_range`](out_of_range.md) for exceptions indicating access out of the defined range - -## Version history - -- Since version 3.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/out_of_range.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/out_of_range.md deleted file mode 100644 index 6c1f0df..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/out_of_range.md +++ /dev/null @@ -1,68 +0,0 @@ -# nlohmann::basic_json::out_of_range - -```cpp -class out_of_range : public exception; -``` - -This exception is thrown in case a library function is called on an input parameter that exceeds the expected range, for -instance in case of array indices or nonexisting object keys. - -Exceptions have ids 4xx (see [list of out-of-range errors](../../home/exceptions.md#out-of-range)). - -```plantuml -std::exception <|-- basic_json::exception -basic_json::exception <|-- basic_json::parse_error -basic_json::exception <|-- basic_json::invalid_iterator -basic_json::exception <|-- basic_json::type_error -basic_json::exception <|-- basic_json::out_of_range -basic_json::exception <|-- basic_json::other_error - -interface std::exception {} - -class basic_json::exception { - + const int id - + const char* what() const -} - -class basic_json::parse_error { - + const std::size_t byte -} - -class basic_json::out_of_range #FFFF00 {} -``` - -## Member functions - -- **what** - returns explanatory string - -## Member variables - -- **id** - the id of the exception - -## Examples - -??? example - - The following code shows how a `out_of_range` exception can be caught. - - ```cpp - --8<-- "examples/out_of_range.cpp" - ``` - - Output: - - ```json - --8<-- "examples/out_of_range.output" - ``` - -## See also - -- [List of out-of-range errors](../../home/exceptions.md#out-of-range) -- [`parse_error`](parse_error.md) for exceptions indicating a parse error -- [`invalid_iterator`](invalid_iterator.md) for exceptions indicating errors with iterators -- [`type_error`](type_error.md) for exceptions indicating executing a member function with a wrong type -- [`other_error`](other_error.md) for exceptions indicating other library errors - -## Version history - -- Since version 3.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/parse.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/parse.md deleted file mode 100644 index 49838ad..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/parse.md +++ /dev/null @@ -1,214 +0,0 @@ -# nlohmann::basic_json::parse - -```cpp -// (1) -template -static basic_json parse(InputType&& i, - const parser_callback_t cb = nullptr, - const bool allow_exceptions = true, - const bool ignore_comments = false); - -// (2) -template -static basic_json parse(IteratorType first, IteratorType last, - const parser_callback_t cb = nullptr, - const bool allow_exceptions = true, - const bool ignore_comments = false); -``` - -1. Deserialize from a compatible input. -2. Deserialize from a pair of character iterators - - The `value_type` of the iterator must be an integral type with size of 1, 2 or 4 bytes, which will be interpreted - respectively as UTF-8, UTF-16 and UTF-32. - -## Template parameters - -`InputType` -: A compatible input, for instance: - - - an `std::istream` object - - a `FILE` pointer (must not be null) - - a C-style array of characters - - a pointer to a null-terminated string of single byte characters - - a `std::string` - - an object `obj` for which `begin(obj)` and `end(obj)` produces a valid pair of iterators. - -`IteratorType` -: a compatible iterator type, for instance. - - - a pair of `std::string::iterator` or `std::vector::iterator` - - a pair of pointers such as `ptr` and `ptr + len` - -## Parameters - -`i` (in) -: Input to parse from. - -`cb` (in) -: a parser callback function of type [`parser_callback_t`](parser_callback_t.md) which is used to control the - deserialization by filtering unwanted values (optional) - -`allow_exceptions` (in) -: whether to throw exceptions in case of a parse error (optional, `#!cpp true` by default) - -`ignore_comments` (in) -: whether comments should be ignored and treated like whitespace (`#!cpp true`) or yield a parse error - (`#!cpp false`); (optional, `#!cpp false` by default) - -`first` (in) -: iterator to start of character range - -`last` (in) -: iterator to end of character range - -## Return value - -Deserialized JSON value; in case of a parse error and `allow_exceptions` set to `#!cpp false`, the return value will be -`value_t::discarded`. The latter can be checked with [`is_discarded`](is_discarded.md). - -## Exception safety - -Strong guarantee: if an exception is thrown, there are no changes in the JSON value. - -## Exceptions - -- Throws [`parse_error.101`](../../home/exceptions.md#jsonexceptionparse_error101) in case of an unexpected token. -- Throws [`parse_error.102`](../../home/exceptions.md#jsonexceptionparse_error102) if to_unicode fails or surrogate - error. -- Throws [`parse_error.103`](../../home/exceptions.md#jsonexceptionparse_error103) if to_unicode fails. - -## Complexity - -Linear in the length of the input. The parser is a predictive LL(1) parser. The complexity can be higher if the parser -callback function `cb` or reading from (1) the input `i` or (2) the iterator range [`first`, `last`] has a -super-linear complexity. - -## Notes - -(1) A UTF-8 byte order mark is silently ignored. - -!!! danger "Runtime assertion" - - The precondition that a passed `#!cpp FILE` pointer must not be null is enforced with a - [runtime assertion](../../features/assertions.md). - -## Examples - -??? example "Parsing from a character array" - - The example below demonstrates the `parse()` function reading from an array. - - ```cpp - --8<-- "examples/parse__array__parser_callback_t.cpp" - ``` - - Output: - - ```json - --8<-- "examples/parse__array__parser_callback_t.output" - ``` - -??? example "Parsing from a string" - - The example below demonstrates the `parse()` function with and without callback function. - - ```cpp - --8<-- "examples/parse__string__parser_callback_t.cpp" - ``` - - Output: - - ```json - --8<-- "examples/parse__string__parser_callback_t.output" - ``` - -??? example "Parsing from an input stream" - - The example below demonstrates the `parse()` function with and without callback function. - - ```cpp - --8<-- "examples/parse__istream__parser_callback_t.cpp" - ``` - - Output: - - ```json - --8<-- "examples/parse__istream__parser_callback_t.output" - ``` - -??? example "Parsing from a contiguous container" - - The example below demonstrates the `parse()` function reading from a contiguous container. - - ```cpp - --8<-- "examples/parse__contiguouscontainer__parser_callback_t.cpp" - ``` - - Output: - - ```json - --8<-- "examples/parse__contiguouscontainer__parser_callback_t.output" - ``` - -??? example "Parsing from a non null-terminated string" - - The example below demonstrates the `parse()` function reading from a string that is not null-terminated. - - ```cpp - --8<-- "examples/parse__pointers.cpp" - ``` - - Output: - - ```json - --8<-- "examples/parse__pointers.output" - ``` - -??? example "Parsing from an iterator pair" - - The example below demonstrates the `parse()` function reading from an iterator pair. - - ```cpp - --8<-- "examples/parse__iterator_pair.cpp" - ``` - - Output: - - ```json - --8<-- "examples/parse__iterator_pair.output" - ``` - -??? example "Effect of `allow_exceptions` parameter" - - The example below demonstrates the effect of the `allow_exceptions` parameter in the ´parse()` function. - - ```cpp - --8<-- "examples/parse__allow_exceptions.cpp" - ``` - - Output: - - ```json - --8<-- "examples/parse__allow_exceptions.output" - ``` - -## See also - -- [accept](accept.md) - check if the input is valid JSON -- [operator>>](../operator_gtgt.md) - deserialize from stream - -## Version history - -- Added in version 1.0.0. -- Overload for contiguous containers (1) added in version 2.0.3. -- Ignoring comments via `ignore_comments` added in version 3.9.0. - -!!! warning "Deprecation" - - Overload (2) replaces calls to `parse` with a pair of iterators as their first parameter which has been - deprecated in version 3.8.0. This overload will be removed in version 4.0.0. Please replace all calls like - `#!cpp parse({ptr, ptr+len}, ...);` with `#!cpp parse(ptr, ptr+len, ...);`. - - You should be warned by your compiler with a `-Wdeprecated-declarations` warning if you are using a deprecated - function. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/parse_error.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/parse_error.md deleted file mode 100644 index af3e1f0..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/parse_error.md +++ /dev/null @@ -1,74 +0,0 @@ -# nlohmann::basic_json::parse_error - -```cpp -class parse_error : public exception; -``` - -This exception is thrown by the library when a parse error occurs. Parse errors can occur during the deserialization of -JSON text, BSON, CBOR, MessagePack, UBJSON, as well as when using JSON Patch. - -Member `byte` holds the byte index of the last read character in the input file (see note below). - -Exceptions have ids 1xx (see [list of parse errors](../../home/exceptions.md#parse-errors)). - -```plantuml -std::exception <|-- basic_json::exception -basic_json::exception <|-- basic_json::parse_error -basic_json::exception <|-- basic_json::invalid_iterator -basic_json::exception <|-- basic_json::type_error -basic_json::exception <|-- basic_json::out_of_range -basic_json::exception <|-- basic_json::other_error - -interface std::exception {} - -class basic_json::exception { - + const int id - + const char* what() const -} - -class basic_json::parse_error #FFFF00 { - + const std::size_t byte -} -``` - -## Member functions - -- **what** - returns explanatory string - -## Member variables - -- **id** - the id of the exception -- **byte** - byte index of the parse error - -## Notes - -For an input with $n$ bytes, 1 is the index of the first character and $n+1$ is the index of the terminating null byte -or the end of file. This also holds true when reading a byte vector for binary formats. - -## Examples - -??? example - - The following code shows how a `parse_error` exception can be caught. - - ```cpp - --8<-- "examples/parse_error.cpp" - ``` - - Output: - - ```json - --8<-- "examples/parse_error.output" - ``` - -## See also - -- [List of parse errors](../../home/exceptions.md#parse-errors) -- [`invalid_iterator`](invalid_iterator.md) for exceptions indicating errors with iterators -- [`type_error`](type_error.md) for exceptions indicating executing a member function with a wrong type -- [`out_of_range`](out_of_range.md) for exceptions indicating access out of the defined range -- [`other_error`](other_error.md) for exceptions indicating other library errors - -## Version history - -- Since version 3.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/parse_event_t.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/parse_event_t.md deleted file mode 100644 index 1a7c390..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/parse_event_t.md +++ /dev/null @@ -1,29 +0,0 @@ -# nlohmann::basic_json::parse_event_t - -```cpp -enum class parse_event_t : std::uint8_t { - object_start, - object_end, - array_start, - array_end, - key, - value -}; -``` - -The parser callback distinguishes the following events: - -- `object_start`: the parser read `{` and started to process a JSON object -- `key`: the parser read a key of a value in an object -- `object_end`: the parser read `}` and finished processing a JSON object -- `array_start`: the parser read `[` and started to process a JSON array -- `array_end`: the parser read `]` and finished processing a JSON array -- `value`: the parser finished reading a JSON value - -## Examples - -![Example when certain parse events are triggered](../../images/callback_events.png) - -## Version history - -- Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/parser_callback_t.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/parser_callback_t.md deleted file mode 100644 index e10402e..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/parser_callback_t.md +++ /dev/null @@ -1,73 +0,0 @@ -# nlohmann::basic_json::parser_callback_t - -```cpp -template -using parser_callback_t = - std::function; -``` - -With a parser callback function, the result of parsing a JSON text can be influenced. When passed to -[`parse`](parse.md), it is called on certain events (passed as [`parse_event_t`](parse_event_t.md) via parameter -`event`) with a set recursion depth `depth` and context JSON value `parsed`. The return value of the callback function -is a boolean indicating whether the element that emitted the callback shall be kept or not. - -We distinguish six scenarios (determined by the event type) in which the callback function can be called. The following -table describes the values of the parameters `depth`, `event`, and `parsed`. - -| parameter `event` | description | parameter `depth` | parameter `parsed` | -|-------------------------------|-----------------------------------------------------------|-------------------------------------------|----------------------------------| -| `parse_event_t::object_start` | the parser read `{` and started to process a JSON object | depth of the parent of the JSON object | a JSON value with type discarded | -| `parse_event_t::key` | the parser read a key of a value in an object | depth of the currently parsed JSON object | a JSON string containing the key | -| `parse_event_t::object_end` | the parser read `}` and finished processing a JSON object | depth of the parent of the JSON object | the parsed JSON object | -| `parse_event_t::array_start` | the parser read `[` and started to process a JSON array | depth of the parent of the JSON array | a JSON value with type discarded | -| `parse_event_t::array_end` | the parser read `]` and finished processing a JSON array | depth of the parent of the JSON array | the parsed JSON array | -| `parse_event_t::value` | the parser finished reading a JSON value | depth of the value | the parsed JSON value | - -![Example when certain parse events are triggered](../../images/callback_events.png) - -Discarding a value (i.e., returning `#!cpp false`) has different effects depending on the context in which function was -called: - -- Discarded values in structured types are skipped. That is, the parser will behave as if the discarded value was never - read. -- In case a value outside a structured type is skipped, it is replaced with `null`. This case happens if the top-level - element is skipped. - -## Parameters - -`depth` (in) -: the depth of the recursion during parsing - -`event` (in) -: an event of type [`parse_event_t`](parse_event_t.md) indicating the context in - the callback function has been called - -`parsed` (in, out) -: the current intermediate parse result; note that - writing to this value has no effect for `parse_event_t::key` events - -## Return value - -Whether the JSON value which called the function during parsing should be kept (`#!cpp true`) or not (`#!cpp false`). In -the latter case, it is either skipped completely or replaced by an empty discarded object. - -## Examples - -??? example - - The example below demonstrates the `parse()` function with - and without callback function. - - ```cpp - --8<-- "examples/parse__string__parser_callback_t.cpp" - ``` - - Output: - - ```json - --8<-- "examples/parse__string__parser_callback_t.output" - ``` - -## Version history - -- Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/patch.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/patch.md deleted file mode 100644 index deec474..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/patch.md +++ /dev/null @@ -1,73 +0,0 @@ -# nlohmann::basic_json::patch - -```cpp -basic_json patch(const basic_json& json_patch) const; -``` - -[JSON Patch](http://jsonpatch.com) defines a JSON document structure for expressing a sequence of operations to apply to -a JSON document. With this function, a JSON Patch is applied to the current JSON value by executing all operations from -the patch. - -## Parameters - -`json_patch` (in) -: JSON patch document - -## Return value - -patched document - -## Exception safety - -Strong guarantee: if an exception is thrown, there are no changes in the JSON value. - -## Exceptions - -- Throws [`parse_error.104`](../../home/exceptions.md#jsonexceptionparse_error104) if the JSON patch does not consist of - an array of objects. -- Throws [`parse_error.105`](../../home/exceptions.md#jsonexceptionparse_error105) if the JSON patch is malformed (e.g., - mandatory attributes are missing); example: `"operation add must have member path"`. -- Throws [`out_of_range.401`](../../home/exceptions.md#jsonexceptionout_of_range401) if an array index is out of range. -- Throws [`out_of_range.403`](../../home/exceptions.md#jsonexceptionout_of_range403) if a JSON pointer inside the patch - could not be resolved successfully in the current JSON value; example: `"key baz not found"`. -- Throws [`out_of_range.405`](../../home/exceptions.md#jsonexceptionout_of_range405) if JSON pointer has no parent - ("add", "remove", "move") -- Throws [`out_of_range.501`](../../home/exceptions.md#jsonexceptionother_error501) if "test" operation was - unsuccessful. - -## Complexity - -Linear in the size of the JSON value and the length of the JSON patch. As usually only a fraction of the JSON value is -affected by the patch, the complexity can usually be neglected. - -## Notes - -The application of a patch is atomic: Either all operations succeed and the patched document is returned or an exception -is thrown. In any case, the original value is not changed: the patch is applied to a copy of the value. - -## Examples - -??? example - - The following code shows how a JSON patch is applied to a value. - - ```cpp - --8<-- "examples/patch.cpp" - ``` - - Output: - - ```json - --8<-- "examples/patch.output" - ``` - -## See also - -- [RFC 6902 (JSON Patch)](https://tools.ietf.org/html/rfc6902) -- [RFC 6901 (JSON Pointer)](https://tools.ietf.org/html/rfc6901) -- [patch_inplace](patch_inplace.md) applies a JSON Patch without creating a copy of the document -- [merge_patch](merge_patch.md) applies a JSON Merge Patch - -## Version history - -- Added in version 2.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/patch_inplace.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/patch_inplace.md deleted file mode 100644 index e8fd176..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/patch_inplace.md +++ /dev/null @@ -1,70 +0,0 @@ -# nlohmann::basic_json::patch_inplace - -```cpp -void patch_inplace(const basic_json& json_patch) const; -``` - -[JSON Patch](http://jsonpatch.com) defines a JSON document structure for expressing a sequence of operations to apply to -a JSON document. With this function, a JSON Patch is applied to the current JSON value by executing all operations from -the patch. This function applies a JSON patch in place and returns void. - -## Parameters - -`json_patch` (in) -: JSON patch document - -## Exception safety - -No guarantees, value may be corrupted by an unsuccessful patch operation. - -## Exceptions - -- Throws [`parse_error.104`](../../home/exceptions.md#jsonexceptionparse_error104) if the JSON patch does not consist of - an array of objects. -- Throws [`parse_error.105`](../../home/exceptions.md#jsonexceptionparse_error105) if the JSON patch is malformed (e.g., - mandatory attributes are missing); example: `"operation add must have member path"`. -- Throws [`out_of_range.401`](../../home/exceptions.md#jsonexceptionout_of_range401) if an array index is out of range. -- Throws [`out_of_range.403`](../../home/exceptions.md#jsonexceptionout_of_range403) if a JSON pointer inside the patch - could not be resolved successfully in the current JSON value; example: `"key baz not found"`. -- Throws [`out_of_range.405`](../../home/exceptions.md#jsonexceptionout_of_range405) if JSON pointer has no parent - ("add", "remove", "move") -- Throws [`out_of_range.501`](../../home/exceptions.md#jsonexceptionother_error501) if "test" operation was - unsuccessful. - -## Complexity - -Linear in the size of the JSON value and the length of the JSON patch. As usually only a fraction of the JSON value is -affected by the patch, the complexity can usually be neglected. - -## Notes - -Unlike [`patch`](patch.md), `patch_inplace` applies the operation "in place" and no copy of the JSON value is created. -That makes it faster for large documents by avoiding the copy. However, the JSON value might be corrupted if the -function throws an exception. - -## Examples - -??? example - - The following code shows how a JSON patch is applied to a value. - - ```cpp - --8<-- "examples/patch_inplace.cpp" - ``` - - Output: - - ```json - --8<-- "examples/patch_inplace.output" - ``` - -## See also - -- [RFC 6902 (JSON Patch)](https://tools.ietf.org/html/rfc6902) -- [RFC 6901 (JSON Pointer)](https://tools.ietf.org/html/rfc6901) -- [patch](patch.md) applies a JSON Merge Patch -- [merge_patch](merge_patch.md) applies a JSON Merge Patch - -## Version history - -- Added in version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/push_back.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/push_back.md deleted file mode 100644 index 5c7d20d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/push_back.md +++ /dev/null @@ -1,106 +0,0 @@ -# nlohmann::basic_json::push_back - -```cpp -// (1) -void push_back(basic_json&& val); -void push_back(const basic_json& val); - -// (2) -void push_back(const typename object_t::value_type& val); - -// (3) -void push_back(initializer_list_t init); -``` - -1. Appends the given element `val` to the end of the JSON array. If the function is called on a JSON null value, an - empty array is created before appending `val`. - -2. Inserts the given element `val` to the JSON object. If the function is called on a JSON null value, an empty object - is created before inserting `val`. - -3. This function allows using `push_back` with an initializer list. In case - - 1. the current value is an object, - 2. the initializer list `init` contains only two elements, and - 3. the first element of `init` is a string, - - `init` is converted into an object element and added using `push_back(const typename object_t::value_type&)`. - Otherwise, `init` is converted to a JSON value and added using `push_back(basic_json&&)`. - -## Parameters - -`val` (in) -: the value to add to the JSON array/object - -`init` (in) -: an initializer list - -## Exceptions - -All functions can throw the following exception: - - Throws [`type_error.308`](../../home/exceptions.md#jsonexceptiontype_error308) when called on a type other than - JSON array or null; example: `"cannot use push_back() with number"` - -## Complexity - -1. Amortized constant. -2. Logarithmic in the size of the container, O(log(`size()`)). -3. Linear in the size of the initializer list `init`. - -## Notes - -(3) This function is required to resolve an ambiguous overload error, because pairs like `{"key", "value"}` can be both - interpreted as `object_t::value_type` or `std::initializer_list`, see - [#235](https://github.com/nlohmann/json/issues/235) for more information. - -## Examples - -??? example "Example: (1) add element to array" - - The example shows how `push_back()` and `+=` can be used to add elements to a JSON array. Note how the `null` value - was silently converted to a JSON array. - - ```cpp - --8<-- "examples/push_back.cpp" - ``` - - Output: - - ```json - --8<-- "examples/push_back.output" - ``` - -??? example "Example: (2) add element to object" - - The example shows how `push_back()` and `+=` can be used to add elements to a JSON object. Note how the `null` value - was silently converted to a JSON object. - - ```cpp - --8<-- "examples/push_back__object_t__value.cpp" - ``` - - Output: - - ```json - --8<-- "examples/push_back__object_t__value.output" - ``` - -??? example "Example: (3) add to object from initializer list" - - The example shows how initializer lists are treated as objects when possible. - - ```cpp - --8<-- "examples/push_back__initializer_list.cpp" - ``` - - Output: - - ```json - --8<-- "examples/push_back__initializer_list.output" - ``` - -## Version history - -1. Since version 1.0.0. -2. Since version 1.0.0. -2. Since version 2.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/rbegin.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/rbegin.md deleted file mode 100644 index 126c471..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/rbegin.md +++ /dev/null @@ -1,42 +0,0 @@ -# nlohmann::basic_json::rbegin - -```cpp -reverse_iterator rbegin() noexcept; -const_reverse_iterator rbegin() const noexcept; -``` - -Returns an iterator to the reverse-beginning; that is, the last element. - -![Illustration from cppreference.com](../../images/range-rbegin-rend.svg) - -## Return value - -reverse iterator to the first element - -## Exception safety - -No-throw guarantee: this member function never throws exceptions. - -## Complexity - -Constant. - -## Examples - -??? example - - The following code shows an example for `rbegin()`. - - ```cpp - --8<-- "examples/rbegin.cpp" - ``` - - Output: - - ```json - --8<-- "examples/rbegin.output" - ``` - -## Version history - -- Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/rend.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/rend.md deleted file mode 100644 index 96da7a5..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/rend.md +++ /dev/null @@ -1,43 +0,0 @@ -# nlohmann::basic_json::rend - -```cpp -reverse_iterator rend() noexcept; -const_reverse_iterator rend() const noexcept; -``` - -Returns an iterator to the reverse-end; that is, one before the first element. This element acts as a placeholder, -attempting to access it results in undefined behavior. - -![Illustration from cppreference.com](../../images/range-rbegin-rend.svg) - -## Return value - -reverse iterator to the element following the last element - -## Exception safety - -No-throw guarantee: this member function never throws exceptions. - -## Complexity - -Constant. - -## Examples - -??? example - - The following code shows an example for `eend()`. - - ```cpp - --8<-- "examples/rend.cpp" - ``` - - Output: - - ```json - --8<-- "examples/rend.output" - ``` - -## Version history - -- Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/sax_parse.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/sax_parse.md deleted file mode 100644 index e2ac1b4..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/sax_parse.md +++ /dev/null @@ -1,115 +0,0 @@ -# nlohmann::basic_json::sax_parse - -```cpp -// (1) -template -static bool sax_parse(InputType&& i, - SAX* sax, - input_format_t format = input_format_t::json, - const bool strict = true, - const bool ignore_comments = false); - -// (2) -template -static bool sax_parse(IteratorType first, IteratorType last, - SAX* sax, - input_format_t format = input_format_t::json, - const bool strict = true, - const bool ignore_comments = false); -``` - -Read from input and generate SAX events - -1. Read from a compatible input. -2. Read from a pair of character iterators - - The value_type of the iterator must be an integral type with size of 1, 2 or 4 bytes, which will be interpreted - respectively as UTF-8, UTF-16 and UTF-32. - -The SAX event lister must follow the interface of [`json_sax`](../json_sax/index.md). - -## Template parameters - -`InputType` -: A compatible input, for instance: - - - an `std::istream` object - - a `FILE` pointer - - a C-style array of characters - - a pointer to a null-terminated string of single byte characters - - an object `obj` for which `begin(obj)` and `end(obj)` produces a valid pair of - iterators. - -`IteratorType` -: Description - -`SAX` -: Description - -## Parameters - -`i` (in) -: Input to parse from. - -`sax` (in) -: SAX event listener - -`format` (in) -: the format to parse (JSON, CBOR, MessagePack, or UBJSON) (optional, `input_format_t::json` by default), see - [`input_format_t`](input_format_t.md) for more information - -`strict` (in) -: whether the input has to be consumed completely (optional, `#!cpp true` by default) - -`ignore_comments` (in) -: whether comments should be ignored and treated like whitespace (`#!cpp true`) or yield a parse error - (`#!cpp false`); (optional, `#!cpp false` by default) - -`first` (in) -: iterator to start of character range - -`last` (in) -: iterator to end of character range - -## Return value - -return value of the last processed SAX event - -## Exception safety - -## Complexity - -Linear in the length of the input. The parser is a predictive LL(1) parser. The complexity can be higher if the SAX -consumer `sax` has a super-linear complexity. - -## Notes - -A UTF-8 byte order mark is silently ignored. - -## Examples - -??? example - - The example below demonstrates the `sax_parse()` function reading from string and processing the events with a - user-defined SAX event consumer. - - ```cpp - --8<-- "examples/sax_parse.cpp" - ``` - - Output: - - ```json - --8<-- "examples/sax_parse.output" - ``` - -## Version history - -- Added in version 3.2.0. -- Ignoring comments via `ignore_comments` added in version 3.9.0. - -!!! warning "Deprecation" - - Overload (2) replaces calls to `sax_parse` with a pair of iterators as their first parameter which has been - deprecated in version 3.8.0. This overload will be removed in version 4.0.0. Please replace all calls like - `#!cpp sax_parse({ptr, ptr+len});` with `#!cpp sax_parse(ptr, ptr+len);`. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/size.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/size.md deleted file mode 100644 index 4ff582d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/size.md +++ /dev/null @@ -1,57 +0,0 @@ -# nlohmann::basic_json::size - -```cpp -size_type size() const noexcept; -``` - -Returns the number of elements in a JSON value. - -## Return value - -The return value depends on the different types and is defined as follows: - -| Value type | return value | -|------------|-------------------------------------| -| null | `0` | -| boolean | `1` | -| string | `1` | -| number | `1` | -| binary | `1` | -| object | result of function object_t::size() | -| array | result of function array_t::size() | - -## Exception safety - -No-throw guarantee: this function never throws exceptions. - -## Complexity - -Constant, as long as [`array_t`](array_t.md) and [`object_t`](object_t.md) satisfy the -[Container](https://en.cppreference.com/w/cpp/named_req/Container) concept; that is, their `size()` functions have -constant complexity. - -## Notes - -This function does not return the length of a string stored as JSON value -- it returns the number of elements in the -JSON value which is `1` in the case of a string. - -## Examples - -??? example - - The following code calls `size()` on the different value types. - - ```cpp - --8<-- "examples/size.cpp" - ``` - - Output: - - ```json - --8<-- "examples/size.output" - ``` - -## Version history - -- Added in version 1.0.0. -- Extended to return `1` for binary types in version 3.8.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/std_hash.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/std_hash.md deleted file mode 100644 index b9de74f..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/std_hash.md +++ /dev/null @@ -1,34 +0,0 @@ -# std::hash - -```cpp -namespace std { - struct hash; -} -``` - -Return a hash value for a JSON object. The hash function tries to rely on `std::hash` where possible. Furthermore, the -type of the JSON value is taken into account to have different hash values for `#!json null`, `#!cpp 0`, `#!cpp 0U`, and -`#!cpp false`, etc. - -## Examples - -??? example - - The example shows how to calculate hash values for different JSON values. - - ```cpp - --8<-- "examples/std_hash.cpp" - ``` - - Output: - - ```json - --8<-- "examples/std_hash.output" - ``` - - Note the output is platform-dependent. - -## Version history - -- Added in version 1.0.0. -- Extended for arbitrary basic_json types in version 3.10.5. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/std_swap.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/std_swap.md deleted file mode 100644 index d30f3bc..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/std_swap.md +++ /dev/null @@ -1,51 +0,0 @@ -# std::swap - -```cpp -namespace std { - void swap(nlohmann::basic_json& j1, nlohmann::basic_json& j2); -} -``` - -Exchanges the values of two JSON objects. - -## Parameters - -`j1` (in, out) -: value to be replaced by `j2` - -`j2` (in, out) -: value to be replaced by `j1` - -## Possible implementation - -```cpp -void swap(nlohmann::basic_json& j1, nlohmann::basic_json& j2) -{ - j1.swap(j2); -} -``` - -## Examples - -??? example - - The following code shows how two values are swapped with `std::swap`. - - ```cpp - --8<-- "examples/std_swap.cpp" - ``` - - Output: - - ```json - --8<-- "examples/std_swap.output" - ``` - -## See also - -- [swap](swap.md) - -## Version history - -- Added in version 1.0.0. -- Extended for arbitrary basic_json types in version 3.10.5. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/string_t.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/string_t.md deleted file mode 100644 index 3ab4412..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/string_t.md +++ /dev/null @@ -1,66 +0,0 @@ -# nlohmann::basic_json::string_t - -```cpp -using string_t = StringType; -``` - -The type used to store JSON strings. - -[RFC 8259](https://tools.ietf.org/html/rfc8259) describes JSON strings as follows: -> A string is a sequence of zero or more Unicode characters. - -To store objects in C++, a type is defined by the template parameter described below. Unicode values are split by the -JSON class into byte-sized characters during deserialization. - -## Template parameters - -`StringType` -: the container to store strings (e.g., `std::string`). Note this container is used for keys/names in objects, see - [object_t](object_t.md). - -## Notes - -#### Default type - -With the default values for `StringType` (`std::string`), the default value for `string_t` is `#!cpp std::string`. - -#### Encoding - -Strings are stored in UTF-8 encoding. Therefore, functions like `std::string::size()` or `std::string::length()` return -the number of bytes in the string rather than the number of characters or glyphs. - -#### String comparison - -[RFC 8259](https://tools.ietf.org/html/rfc8259) states: -> Software implementations are typically required to test names of object members for equality. Implementations that -> transform the textual representation into sequences of Unicode code units and then perform the comparison numerically, -> code unit by code unit, are interoperable in the sense that implementations will agree in all cases on equality or -> inequality of two strings. For example, implementations that compare strings with escaped characters unconverted may -> incorrectly find that `"a\\b"` and `"a\u005Cb"` are not equal. - -This implementation is interoperable as it does compare strings code unit by code unit. - -#### Storage - -String values are stored as pointers in a `basic_json` type. That is, for any access to string values, a pointer of type -`string_t*` must be dereferenced. - -## Examples - -??? example - - The following code shows that `string_t` is by default, a typedef to `#!cpp std::string`. - - ```cpp - --8<-- "examples/string_t.cpp" - ``` - - Output: - - ```json - --8<-- "examples/string_t.output" - ``` - -## Version history - -- Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/swap.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/swap.md deleted file mode 100644 index a5730ff..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/swap.md +++ /dev/null @@ -1,157 +0,0 @@ -# nlohmann::basic_json::swap - -```cpp -// (1) -void swap(reference other) noexcept; - -// (2) -void swap(reference left, reference right) noexcept; - -// (3) -void swap(array_t& other); - -// (4) -void swap(object_t& other); - -// (5) -void swap(string_t& other); - -// (6) -void swap(binary_t& other); - -// (7) -void swap(typename binary_t::container_type& other); -``` - -1. Exchanges the contents of the JSON value with those of `other`. Does not invoke any move, copy, or swap operations on - individual elements. All iterators and references remain valid. The past-the-end iterator is invalidated. -2. Exchanges the contents of the JSON value from `left` with those of `right`. Does not invoke any move, copy, or swap - operations on individual elements. All iterators and references remain valid. The past-the-end iterator is - invalidated. Implemented as a friend function callable via ADL. -3. Exchanges the contents of a JSON array with those of `other`. Does not invoke any move, copy, or swap operations on - individual elements. All iterators and references remain valid. The past-the-end iterator is invalidated. -4. Exchanges the contents of a JSON object with those of `other`. Does not invoke any move, copy, or swap operations on - individual elements. All iterators and references remain valid. The past-the-end iterator is invalidated. -5. Exchanges the contents of a JSON string with those of `other`. Does not invoke any move, copy, or swap operations on - individual elements. All iterators and references remain valid. The past-the-end iterator is invalidated. -6. Exchanges the contents of a binary value with those of `other`. Does not invoke any move, copy, or swap operations on - individual elements. All iterators and references remain valid. The past-the-end iterator is invalidated. -7. Exchanges the contents of a binary value with those of `other`. Does not invoke any move, copy, or swap operations on - individual elements. All iterators and references remain valid. The past-the-end iterator is invalidated. Unlike - version (6), no binary subtype is involved. - -## Parameters - -`other` (in, out) -: value to exchange the contents with - -`left` (in, out) -: value to exchange the contents with - -`right` (in, out) -: value to exchange the contents with - -## Exceptions - -1. No-throw guarantee: this function never throws exceptions. -2. No-throw guarantee: this function never throws exceptions. -3. Throws [`type_error.310`](../../home/exceptions.md#jsonexceptiontype_error310) if called on JSON values other than - arrays; example: `"cannot use swap() with boolean"` -4. Throws [`type_error.310`](../../home/exceptions.md#jsonexceptiontype_error310) if called on JSON values other than - objects; example: `"cannot use swap() with boolean"` -5. Throws [`type_error.310`](../../home/exceptions.md#jsonexceptiontype_error310) if called on JSON values other than - strings; example: `"cannot use swap() with boolean"` -6. Throws [`type_error.310`](../../home/exceptions.md#jsonexceptiontype_error310) if called on JSON values other than - binaries; example: `"cannot use swap() with boolean"` -7. Throws [`type_error.310`](../../home/exceptions.md#jsonexceptiontype_error310) if called on JSON values other than - binaries; example: `"cannot use swap() with boolean"` - -## Complexity - -Constant. - -## Examples - -??? example "Example: Swap JSON value (1, 2)" - - The example below shows how JSON values can be swapped with `swap()`. - - ```cpp - --8<-- "examples/swap__reference.cpp" - ``` - - Output: - - ```json - --8<-- "examples/swap__reference.output" - ``` - -??? example "Example: Swap array (3)" - - The example below shows how arrays can be swapped with `swap()`. - - ```cpp - --8<-- "examples/swap__array_t.cpp" - ``` - - Output: - - ```json - --8<-- "examples/swap__array_t.output" - ``` - -??? example "Example: Swap object (4)" - - The example below shows how objects can be swapped with `swap()`. - - ```cpp - --8<-- "examples/swap__object_t.cpp" - ``` - - Output: - - ```json - --8<-- "examples/swap__object_t.output" - ``` - -??? example "Example: Swap string (5)" - - The example below shows how strings can be swapped with `swap()`. - - ```cpp - --8<-- "examples/swap__string_t.cpp" - ``` - - Output: - - ```json - --8<-- "examples/swap__string_t.output" - ``` - -??? example "Example: Swap string (6)" - - The example below shows how binary values can be swapped with `swap()`. - - ```cpp - --8<-- "examples/swap__binary_t.cpp" - ``` - - Output: - - ```json - --8<-- "examples/swap__binary_t.output" - ``` - -## See also - -- [std::swap](std_swap.md) - -## Version history - -1. Since version 1.0.0. -2. Since version 1.0.0. -3. Since version 1.0.0. -4. Since version 1.0.0. -5. Since version 1.0.0. -6. Since version 3.8.0. -7. Since version 3.8.0. \ No newline at end of file diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/to_bjdata.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/to_bjdata.md deleted file mode 100644 index 48598a5..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/to_bjdata.md +++ /dev/null @@ -1,70 +0,0 @@ -# nlohmann::basic_json::to_bjdata - -```cpp -// (1) -static std::vector to_bjdata(const basic_json& j, - const bool use_size = false, - const bool use_type = false); - -// (2) -static void to_bjdata(const basic_json& j, detail::output_adapter o, - const bool use_size = false, const bool use_type = false); -static void to_bjdata(const basic_json& j, detail::output_adapter o, - const bool use_size = false, const bool use_type = false); -``` - -Serializes a given JSON value `j` to a byte vector using the BJData (Binary JData) serialization format. BJData aims to -be more compact than JSON itself, yet more efficient to parse. - -1. Returns a byte vector containing the BJData serialization. -2. Writes the BJData serialization to an output adapter. - -The exact mapping and its limitations is described on a [dedicated page](../../features/binary_formats/bjdata.md). - -## Parameters - -`j` (in) -: JSON value to serialize - -`o` (in) -: output adapter to write serialization to - -`use_size` (in) -: whether to add size annotations to container types; optional, `#!cpp false` by default. - -`use_type` (in) -: whether to add type annotations to container types (must be combined with `#!cpp use_size = true`); optional, -`#!cpp false` by default. - -## Return value - -1. BJData serialization as byte vector -2. (none) - -## Exception safety - -Strong guarantee: if an exception is thrown, there are no changes in the JSON value. - -## Complexity - -Linear in the size of the JSON value `j`. - -## Examples - -??? example - - The example shows the serialization of a JSON value to a byte vector in BJData format. - - ```cpp - --8<-- "examples/to_bjdata.cpp" - ``` - - Output: - - ```json - --8<-- "examples/to_bjdata.output" - ``` - -## Version history - -- Added in version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/to_bson.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/to_bson.md deleted file mode 100644 index 5c4324a..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/to_bson.md +++ /dev/null @@ -1,59 +0,0 @@ -# nlohmann::basic_json::to_bson - -```cpp -// (1) -static std::vector to_bson(const basic_json& j); - -// (2) -static void to_bson(const basic_json& j, detail::output_adapter o); -static void to_bson(const basic_json& j, detail::output_adapter o); -``` - -BSON (Binary JSON) is a binary format in which zero or more ordered key/value pairs are stored as a single entity (a -so-called document). - -1. Returns a byte vector containing the BSON serialization. -2. Writes the BSON serialization to an output adapter. - -The exact mapping and its limitations is described on a [dedicated page](../../features/binary_formats/bson.md). - -## Parameters - -`j` (in) -: JSON value to serialize - -`o` (in) -: output adapter to write serialization to - -## Return value - -1. BSON serialization as byte vector -2. (none) - -## Exception safety - -Strong guarantee: if an exception is thrown, there are no changes in the JSON value. - -## Complexity - -Linear in the size of the JSON value `j`. - -## Examples - -??? example - - The example shows the serialization of a JSON value to a byte vector in BSON format. - - ```cpp - --8<-- "examples/to_bson.cpp" - ``` - - Output: - - ```json - --8<-- "examples/to_bson.output" - ``` - -## Version history - -- Added in version 3.4.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/to_cbor.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/to_cbor.md deleted file mode 100644 index 0f944c4..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/to_cbor.md +++ /dev/null @@ -1,61 +0,0 @@ -# nlohmann::basic_json::to_cbor - -```cpp -// (1) -static std::vector to_cbor(const basic_json& j); - -// (2) -static void to_cbor(const basic_json& j, detail::output_adapter o); -static void to_cbor(const basic_json& j, detail::output_adapter o); -``` - -Serializes a given JSON value `j` to a byte vector using the CBOR (Concise Binary Object Representation) serialization -format. CBOR is a binary serialization format which aims to be more compact than JSON itself, yet more efficient to -parse. - -1. Returns a byte vector containing the CBOR serialization. -2. Writes the CBOR serialization to an output adapter. - -The exact mapping and its limitations is described on a [dedicated page](../../features/binary_formats/cbor.md). - -## Parameters - -`j` (in) -: JSON value to serialize - -`o` (in) -: output adapter to write serialization to - -## Return value - -1. CBOR serialization as byte vector -2. (none) - -## Exception safety - -Strong guarantee: if an exception is thrown, there are no changes in the JSON value. - -## Complexity - -Linear in the size of the JSON value `j`. - -## Examples - -??? example - - The example shows the serialization of a JSON value to a byte vector in CBOR format. - - ```cpp - --8<-- "examples/to_cbor.cpp" - ``` - - Output: - - ```json - --8<-- "examples/to_cbor.output" - ``` - -## Version history - -- Added in version 2.0.9. -- Compact representation of floating-point numbers added in version 3.8.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/to_msgpack.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/to_msgpack.md deleted file mode 100644 index 7d40981..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/to_msgpack.md +++ /dev/null @@ -1,59 +0,0 @@ -# nlohmann::basic_json::to_msgpack - -```cpp -// (1) -static std::vector to_msgpack(const basic_json& j); - -// (2) -static void to_msgpack(const basic_json& j, detail::output_adapter o); -static void to_msgpack(const basic_json& j, detail::output_adapter o); -``` - -Serializes a given JSON value `j` to a byte vector using the MessagePack serialization format. MessagePack is a binary -serialization format which aims to be more compact than JSON itself, yet more efficient to parse. - -1. Returns a byte vector containing the MessagePack serialization. -2. Writes the MessagePack serialization to an output adapter. - -The exact mapping and its limitations is described on a [dedicated page](../../features/binary_formats/messagepack.md). - -## Parameters - -`j` (in) -: JSON value to serialize - -`o` (in) -: output adapter to write serialization to - -## Return value - -1. MessagePack serialization as byte vector -2. (none) - -## Exception safety - -Strong guarantee: if an exception is thrown, there are no changes in the JSON value. - -## Complexity - -Linear in the size of the JSON value `j`. - -## Examples - -??? example - - The example shows the serialization of a JSON value to a byte vector in MessagePack format. - - ```cpp - --8<-- "examples/to_msgpack.cpp" - ``` - - Output: - - ```json - --8<-- "examples/to_msgpack.output" - ``` - -## Version history - -- Added in version 2.0.9. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/to_string.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/to_string.md deleted file mode 100644 index 2b907e2..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/to_string.md +++ /dev/null @@ -1,65 +0,0 @@ -# to_string(basic_json) - -```cpp -template -std::string to_string(const BasicJsonType& j); -``` - -This function implements a user-defined to_string for JSON objects. - -## Template parameters - -`BasicJsonType` -: a specialization of [`basic_json`](index.md) - -## Return value - -string containing the serialization of the JSON value - -## Exception safety - -Strong guarantee: if an exception is thrown, there are no changes to any JSON value. - -## Exceptions - -Throws [`type_error.316`](../../home/exceptions.md#jsonexceptiontype_error316) if a string stored inside the JSON value -is not UTF-8 encoded - -## Complexity - -Linear. - -## Possible implementation - -```cpp -template -std::string to_string(const BasicJsonType& j) -{ - return j.dump(); -} -``` - -## Examples - -??? example - - The following code shows how the library's `to_string()` function integrates with others, allowing - argument-dependent lookup. - - ```cpp - --8<-- "examples/to_string.cpp" - ``` - - Output: - - ```json - --8<-- "examples/to_string.output" - ``` - -## See also - -- [dump](dump.md) - -## Version history - -Added in version 3.7.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/to_ubjson.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/to_ubjson.md deleted file mode 100644 index e3cd5d6..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/to_ubjson.md +++ /dev/null @@ -1,70 +0,0 @@ -# nlohmann::basic_json::to_ubjson - -```cpp -// (1) -static std::vector to_ubjson(const basic_json& j, - const bool use_size = false, - const bool use_type = false); - -// (2) -static void to_ubjson(const basic_json& j, detail::output_adapter o, - const bool use_size = false, const bool use_type = false); -static void to_ubjson(const basic_json& j, detail::output_adapter o, - const bool use_size = false, const bool use_type = false); -``` - -Serializes a given JSON value `j` to a byte vector using the UBJSON (Universal Binary JSON) serialization format. UBJSON -aims to be more compact than JSON itself, yet more efficient to parse. - -1. Returns a byte vector containing the UBJSON serialization. -2. Writes the UBJSON serialization to an output adapter. - -The exact mapping and its limitations is described on a [dedicated page](../../features/binary_formats/ubjson.md). - -## Parameters - -`j` (in) -: JSON value to serialize - -`o` (in) -: output adapter to write serialization to - -`use_size` (in) -: whether to add size annotations to container types; optional, `#!cpp false` by default. - -`use_type` (in) -: whether to add type annotations to container types (must be combined with `#!cpp use_size = true`); optional, - `#!cpp false` by default. - -## Return value - -1. UBJSON serialization as byte vector -2. (none) - -## Exception safety - -Strong guarantee: if an exception is thrown, there are no changes in the JSON value. - -## Complexity - -Linear in the size of the JSON value `j`. - -## Examples - -??? example - - The example shows the serialization of a JSON value to a byte vector in UBJSON format. - - ```cpp - --8<-- "examples/to_ubjson.cpp" - ``` - - Output: - - ```json - --8<-- "examples/to_ubjson.output" - ``` - -## Version history - -- Added in version 3.1.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/type.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/type.md deleted file mode 100644 index deedd6b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/type.md +++ /dev/null @@ -1,54 +0,0 @@ -# nlohmann::basic_json::type - -```cpp -constexpr value_t type() const noexcept; -``` - -Return the type of the JSON value as a value from the [`value_t`](value_t.md) enumeration. - -## Return value - -the type of the JSON value - -| Value type | return value | -|---------------------------|----------------------------| -| `#!json null` | `value_t::null` | -| boolean | `value_t::boolean` | -| string | `value_t::string` | -| number (integer) | `value_t::number_integer` | -| number (unsigned integer) | `value_t::number_unsigned` | -| number (floating-point) | `value_t::number_float` | -| object | `value_t::object` | -| array | `value_t::array` | -| binary | `value_t::binary` | -| discarded | `value_t::discarded` | - -## Exception safety - -No-throw guarantee: this member function never throws exceptions. - -## Complexity - -Constant. - -## Examples - -??? example - - The following code exemplifies `type()` for all JSON types. - - ```cpp - --8<-- "examples/type.cpp" - ``` - - Output: - - ```json - --8<-- "examples/type.output" - ``` - -## Version history - -- Added in version 1.0.0. -- Added unsigned integer type in version 2.0.0. -- Added binary type in version 3.8.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/type_error.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/type_error.md deleted file mode 100644 index cda54c0..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/type_error.md +++ /dev/null @@ -1,68 +0,0 @@ -# nlohmann::basic_json::type_error - -```cpp -class type_error : public exception; -``` - -This exception is thrown in case of a type error; that is, a library function is executed on a JSON value whose type -does not match the expected semantics. - -Exceptions have ids 3xx (see [list of type errors](../../home/exceptions.md#type-errors)). - -```plantuml -std::exception <|-- basic_json::exception -basic_json::exception <|-- basic_json::parse_error -basic_json::exception <|-- basic_json::invalid_iterator -basic_json::exception <|-- basic_json::type_error -basic_json::exception <|-- basic_json::out_of_range -basic_json::exception <|-- basic_json::other_error - -interface std::exception {} - -class basic_json::exception { - + const int id - + const char* what() const -} - -class basic_json::parse_error { - + const std::size_t byte -} - -class basic_json::type_error #FFFF00 {} -``` - -## Member functions - -- **what** - returns explanatory string - -## Member variables - -- **id** - the id of the exception - -## Examples - -??? example - - The following code shows how a `type_error` exception can be caught. - - ```cpp - --8<-- "examples/type_error.cpp" - ``` - - Output: - - ```json - --8<-- "examples/type_error.output" - ``` - -## See also - -- [List of type errors](../../home/exceptions.md#type-errors) -- [`parse_error`](parse_error.md) for exceptions indicating a parse error -- [`invalid_iterator`](invalid_iterator.md) for exceptions indicating errors with iterators -- [`out_of_range`](out_of_range.md) for exceptions indicating access out of the defined range -- [`other_error`](other_error.md) for exceptions indicating other library errors - -## Version history - -- Since version 3.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/type_name.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/type_name.md deleted file mode 100644 index 389c2b1..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/type_name.md +++ /dev/null @@ -1,54 +0,0 @@ -# nlohmann::basic_json::type_name - -```cpp -const char* type_name() const noexcept; -``` - -Returns the type name as string to be used in error messages -- usually to indicate that a function was called on a -wrong JSON type. - -## Return value - -a string representation of the type ([`value_t`](value_t.md)): - -| Value type | return value | -|----------------------------------------------------|---------------| -| `#!json null` | `"null"` | -| boolean | `"boolean"` | -| string | `"string"` | -| number (integer, unsigned integer, floating-point) | `"number"` | -| object | `"object"` | -| array | `"array"` | -| binary | `"binary"` | -| discarded | `"discarded"` | - -## Exception safety - -No-throw guarantee: this member function never throws exceptions. - -## Complexity - -Constant. - -## Examples - -??? example - - The following code exemplifies `type_name()` for all JSON types. - - ```cpp - --8<-- "examples/type_name.cpp" - ``` - - Output: - - ```json - --8<-- "examples/type_name.output" - ``` - -## Version history - -- Added in version 1.0.0. -- Part of the public API version since 2.1.0. -- Changed return value to `const char*` and added `noexcept` in version 3.0.0. -- Added support for binary type in version 3.8.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/unflatten.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/unflatten.md deleted file mode 100644 index d977803..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/unflatten.md +++ /dev/null @@ -1,61 +0,0 @@ -# nlohmann::basic_json::unflatten - -```cpp -basic_json unflatten() const; -``` - -The function restores the arbitrary nesting of a JSON value that has been flattened before using the -[`flatten()`](flatten.md) function. The JSON value must meet certain constraints: - -1. The value must be an object. -2. The keys must be JSON pointers (see [RFC 6901](https://tools.ietf.org/html/rfc6901)) -3. The mapped values must be primitive JSON types. - -## Return value - -the original JSON from a flattened version - -## Exception safety - -Strong exception safety: if an exception occurs, the original value stays intact. - -## Exceptions - -The function can throw the following exceptions: - -- Throws [`type_error.314`](../../home/exceptions.md#jsonexceptiontype_error314) if value is not an object -- Throws [`type_error.315`](../../home/exceptions.md#jsonexceptiontype_error315) if object values are not primitive - -## Complexity - -Linear in the size the JSON value. - -## Notes - -Empty objects and arrays are flattened by [`flatten()`](flatten.md) to `#!json null` values and can not unflattened to -their original type. Apart from this example, for a JSON value `j`, the following is always true: -`#!cpp j == j.flatten().unflatten()`. - -## Examples - -??? example - - The following code shows how a flattened JSON object is unflattened into the original nested JSON object. - - ```cpp - --8<-- "examples/unflatten.cpp" - ``` - - Output: - - ```json - --8<-- "examples/unflatten.output" - ``` - -## See also - -- [flatten](flatten.md) the reverse function - -## Version history - -- Added in version 2.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/update.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/update.md deleted file mode 100644 index 9eeec40..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/update.md +++ /dev/null @@ -1,142 +0,0 @@ -# nlohmann::basic_json::update - -```cpp -// (1) -void update(const_reference j, bool merge_objects = false); - -// (2) -void update(const_iterator first, const_iterator last, bool merge_objects = false); -``` - -1. Inserts all values from JSON object `j`. -2. Inserts all values from range `[first, last)` - -When `merge_objects` is `#!c false` (default), existing keys are overwritten. When `merge_objects` is `#!c true`, -recursively merges objects with common keys. - -The function is motivated by Python's [dict.update](https://docs.python.org/3.6/library/stdtypes.html#dict.update) -function. - -## Parameters - -`j` (in) -: JSON object to read values from - -`merge_objects` (in) -: when `#!c true`, existing keys are not overwritten, but contents of objects are merged recursively (default: - `#!c false`) - -`first` (in) -: begin of the range of elements to insert - -`last` (in) -: end of the range of elements to insert - -## Exceptions - -1. The function can throw the following exceptions: - - Throws [`type_error.312`](../../home/exceptions.md#jsonexceptiontype_error312) if called on JSON values other than - objects; example: `"cannot use update() with string"` -2. The function can throw the following exceptions: - - Throws [`type_error.312`](../../home/exceptions.md#jsonexceptiontype_error312) if called on JSON values other than - objects; example: `"cannot use update() with string"` - - Throws [`invalid_iterator.202`](../../home/exceptions.md#jsonexceptioninvalid_iterator202) if called on an - iterator which does not belong to the current JSON value; example: `"iterator does not fit current value"` - - Throws [`invalid_iterator.210`](../../home/exceptions.md#jsonexceptioninvalid_iterator210) if `first` and `last` - do not belong to the same JSON value; example: `"iterators do not fit"` - -## Complexity - -1. O(N*log(size() + N)), where N is the number of elements to insert. -2. O(N*log(size() + N)), where N is the number of elements to insert. - -## Examples - -??? example - - The example shows how `update()` is used. - - ```cpp - --8<-- "examples/update.cpp" - ``` - - Output: - - ```json - --8<-- "examples/update.output" - ``` - -??? example - - The example shows how `update()` is used. - - ```cpp - --8<-- "examples/update__range.cpp" - ``` - - Output: - - ```json - --8<-- "examples/update__range.output" - ``` - -??? example - - One common usecase for this function is the handling of user settings. Assume your application can configured in - some aspects: - - ```json - { - "color": "red", - "active": true, - "name": {"de": "Maus", "en": "mouse"} - } - ``` - - The user may override the default settings selectively: - - ```json - { - "color": "blue", - "name": {"es": "ratón"}, - } - ``` - - Then `update` manages the merging of default settings and user settings: - - ```cpp - auto user_settings = json::parse("config.json"); - auto effective_settings = get_default_settings(); - effective_settings.update(user_settings); - ``` - - Now `effective_settings` contains the default settings, but those keys set by the user are overwritten: - - ```json - { - "color": "blue", - "active": true, - "name": {"es": "ratón"} - } - ``` - - Note existing keys were just overwritten. To merge objects, `merge_objects` setting should be set to `#!c true`: - - ```cpp - auto user_settings = json::parse("config.json"); - auto effective_settings = get_default_settings(); - effective_settings.update(user_settings, true); - ``` - - ```json - { - "color": "blue", - "active": true, - "name": {"de": "Maus", "en": "mouse", "es": "ratón"} - } - ``` - -## Version history - -- Added in version 3.0.0. -- Added `merge_objects` parameter in 3.10.4. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/value.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/value.md deleted file mode 100644 index edb5406..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/value.md +++ /dev/null @@ -1,159 +0,0 @@ -# nlohmann::basic_json::value - -```cpp -// (1) -template -ValueType value(const typename object_t::key_type& key, - ValueType&& default_value) const; - -// (2) -template -ValueType value(KeyType&& key, - ValueType&& default_value) const; - -// (3) -template -ValueType value(const json_pointer& ptr, - const ValueType& default_value) const; -``` - -1. Returns either a copy of an object's element at the specified key `key` or a given default value if no element with - key `key` exists. - - The function is basically equivalent to executing - ```cpp - try { - return at(key); - } catch(out_of_range) { - return default_value; - } - ``` - -2. See 1. This overload is only available if `KeyType` is comparable with `#!cpp typename object_t::key_type` and - `#!cpp typename object_comparator_t::is_transparent` denotes a type. - -3. Returns either a copy of an object's element at the specified JSON pointer `ptr` or a given default value if no value - at `ptr` exists. - - The function is basically equivalent to executing - ```cpp - try { - return at(ptr); - } catch(out_of_range) { - return default_value; - } - ``` - -!!! note "Differences to `at` and `operator[]`" - - - Unlike [`at`](at.md), this function does not throw if the given `key`/`ptr` was not found. - - Unlike [`operator[]`](operator[].md), this function does not implicitly add an element to the position defined by - `key`/`ptr` key. This function is furthermore also applicable to const objects. - -## Template parameters - -`KeyType` -: A type for an object key other than [`json_pointer`](../json_pointer/index.md) that is comparable with - [`string_t`](string_t.md) using [`object_comparator_t`](object_comparator_t.md). - This can also be a string view (C++17). -`ValueType` -: type compatible to JSON values, for instance `#!cpp int` for JSON integer numbers, `#!cpp bool` for JSON booleans, - or `#!cpp std::vector` types for JSON arrays. Note the type of the expected value at `key`/`ptr` and the default - value `default_value` must be compatible. - -## Parameters - -`key` (in) -: key of the element to access - -`default_value` (in) -: the value to return if `key`/`ptr` found no value - -`ptr` (in) -: a JSON pointer to the element to access - -## Return value - -1. copy of the element at key `key` or `default_value` if `key` is not found -2. copy of the element at key `key` or `default_value` if `key` is not found -3. copy of the element at JSON Pointer `ptr` or `default_value` if no value for `ptr` is found - -## Exception safety - -Strong guarantee: if an exception is thrown, there are no -changes to any JSON value. - -## Exceptions - -1. The function can throw the following exceptions: - - Throws [`type_error.302`](../../home/exceptions.md#jsonexceptiontype_error302) if `default_value` does not match - the type of the value at `key` - - Throws [`type_error.306`](../../home/exceptions.md#jsonexceptiontype_error306) if the JSON value is not an object; - in that case, using `value()` with a key makes no sense. -2. See 1. -3. The function can throw the following exceptions: - - Throws [`type_error.302`](../../home/exceptions.md#jsonexceptiontype_error302) if `default_value` does not match - the type of the value at `ptr` - - Throws [`type_error.306`](../../home/exceptions.md#jsonexceptiontype_error306) if the JSON value is not an object; - in that case, using `value()` with a key makes no sense. - -## Complexity - -1. Logarithmic in the size of the container. -2. Logarithmic in the size of the container. -3. Logarithmic in the size of the container. - -## Examples - -??? example "Example: (1) access specified object element with default value" - - The example below shows how object elements can be queried with a default value. - - ```cpp - --8<-- "examples/value__object_t_key_type.cpp" - ``` - - Output: - - ```json - --8<-- "examples/value__object_t_key_type.output" - ``` - -??? example "Example: (2) access specified object element using string_view with default value" - - The example below shows how object elements can be queried with a default value. - - ```cpp - --8<-- "examples/value__keytype.c++17.cpp" - ``` - - Output: - - ```json - --8<-- "examples/value__keytype.c++17.output" - ``` - -??? example "Example: (3) access specified object element via JSON Pointer with default value" - - The example below shows how object elements can be queried with a default value. - - ```cpp - --8<-- "examples/value__json_ptr.cpp" - ``` - - Output: - - ```json - --8<-- "examples/value__json_ptr.output" - ``` - -## See also - -- see [`at`](at.md) for access by reference with range checking -- see [`operator[]`](operator%5B%5D.md) for unchecked access by reference - -## Version history - -1. Added in version 1.0.0. Changed parameter `default_value` type from `const ValueType&` to `ValueType&&` in version 3.11.0. -2. Added in version 3.11.0. Made `ValueType` the first template parameter in version 3.11.2. -3. Added in version 2.0.2. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/value_t.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/value_t.md deleted file mode 100644 index 1505e02..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/value_t.md +++ /dev/null @@ -1,81 +0,0 @@ -# nlohmann::basic_json::value_t - -```cpp -enum class value_t : std::uint8_t { - null, - object, - array, - string, - boolean, - number_integer, - number_unsigned, - number_float, - binary, - discarded -}; -``` - -This enumeration collects the different JSON types. It is internally used to distinguish the stored values, and the -functions [`is_null`](is_null.md), [`is_object`](is_object.md), [`is_array`](is_array.md), [`is_string`](is_string.md), -[`is_boolean`](is_boolean.md), [`is_number`](is_number.md) (with [`is_number_integer`](is_number_integer.md), -[`is_number_unsigned`](is_number_unsigned.md), and [`is_number_float`](is_number_float.md)), -[`is_discarded`](is_discarded.md), [`is_binary`](is_binary.md), [`is_primitive`](is_primitive.md), and -[`is_structured`](is_structured.md) rely on it. - -## Notes - -!!! note "Ordering" - - The order of types is as follows: - - 1. `null` - 2. `boolean` - 3. `number_integer`, `number_unsigned`, `number_float` - 4. `object` - 5. `array` - 6. `string` - 7. `binary` - - `discarded` is unordered. - -!!! note "Types of numbers" - - There are three enumerators for numbers (`number_integer`, `number_unsigned`, and `number_float`) to distinguish - between different types of numbers: - - - [`number_unsigned_t`](number_unsigned_t.md) for unsigned integers - - [`number_integer_t`](number_integer_t.md) for signed integers - - [`number_float_t`](number_float_t.md) for floating-point numbers or to approximate integers which do not fit - into the limits of their respective type - -!!! warning "Comparison operators" - - `operator<` and `operator<=>` (since C++20) are overloaded and compare according to the ordering described above. - Until C++20 all other relational and equality operators yield results according to the integer value of each - enumerator. Since C++20 some compilers consider the _rewritten candidates_ generated from `operator<=>` during - overload resolution, while others do not. For predictable and portable behavior use: - - - `operator<` or `operator<=>` when wanting to compare according to the order described above - - `operator==` or `operator!=` when wanting to compare according to each enumerators integer value - -## Examples - -??? example - - The following code how `type()` queries the `value_t` for all JSON types. - - ```cpp - --8<-- "examples/type.cpp" - ``` - - Output: - - ```json - --8<-- "examples/type.output" - ``` - -## Version history - -- Added in version 1.0.0. -- Added unsigned integer type in version 2.0.0. -- Added binary type in version 3.8.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/~basic_json.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/~basic_json.md deleted file mode 100644 index 64e9440..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/basic_json/~basic_json.md +++ /dev/null @@ -1,21 +0,0 @@ -# nlohmann::basic_json::~basic_json - -```cpp -~basic_json() noexcept; -``` - -Destroys the JSON value and frees all allocated memory. - -## Exception safety - -No-throw guarantee: this member function never throws exceptions. - -## Complexity - -Linear. - - - -## Version history - -- Added in version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/byte_container_with_subtype/byte_container_with_subtype.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/byte_container_with_subtype/byte_container_with_subtype.md deleted file mode 100644 index 9913a9b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/byte_container_with_subtype/byte_container_with_subtype.md +++ /dev/null @@ -1,46 +0,0 @@ -# nlohmann::byte_container_with_subtype::byte_container_with_subtype - -```cpp -// (1) -byte_container_with_subtype(); - -// (2) -byte_container_with_subtype(const container_type& container); -byte_container_with_subtype(container_type&& container); - -// (3) -byte_container_with_subtype(const container_type& container, subtype_type subtype); -byte_container_with_subtype(container_type&& container, subtype_type subtype); -``` - -1. Create empty binary container without subtype. -2. Create binary container without subtype. -3. Create binary container with subtype. - -## Parameters - -`container` (in) -: binary container - -`subtype` (in) -: subtype - -## Examples - -??? example - - The example below demonstrates how byte containers can be created. - - ```cpp - --8<-- "examples/byte_container_with_subtype__byte_container_with_subtype.cpp" - ``` - - Output: - - ```json - --8<-- "examples/byte_container_with_subtype__byte_container_with_subtype.output" - ``` - -## Version history - -Since version 3.8.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/byte_container_with_subtype/clear_subtype.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/byte_container_with_subtype/clear_subtype.md deleted file mode 100644 index c62dead..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/byte_container_with_subtype/clear_subtype.md +++ /dev/null @@ -1,36 +0,0 @@ -# nlohmann::byte_container_with_subtype::clear_subtype - -```cpp -void clear_subtype() noexcept; -``` - -Clears the binary subtype and flags the value as not having a subtype, which has implications for serialization; for -instance MessagePack will prefer the bin family over the ext family. - -## Exception safety - -No-throw guarantee: this function never throws exceptions. - -## Complexity - -Constant. - -## Examples - -??? example - - The example below demonstrates how `clear_subtype` can remove subtypes. - - ```cpp - --8<-- "examples/byte_container_with_subtype__clear_subtype.cpp" - ``` - - Output: - - ```json - --8<-- "examples/byte_container_with_subtype__clear_subtype.output" - ``` - -## Version history - -Since version 3.8.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/byte_container_with_subtype/has_subtype.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/byte_container_with_subtype/has_subtype.md deleted file mode 100644 index e06286e..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/byte_container_with_subtype/has_subtype.md +++ /dev/null @@ -1,39 +0,0 @@ -# nlohmann::byte_container_with_subtype::has_subtype - -```cpp -constexpr bool has_subtype() const noexcept; -``` - -Returns whether the value has a subtype. - -## Return value - -whether the value has a subtype - -## Exception safety - -No-throw guarantee: this function never throws exceptions. - -## Complexity - -Constant. - -## Examples - -??? example - - The example below demonstrates how `has_subtype` can check whether a subtype was set. - - ```cpp - --8<-- "examples/byte_container_with_subtype__has_subtype.cpp" - ``` - - Output: - - ```json - --8<-- "examples/byte_container_with_subtype__has_subtype.output" - ``` - -## Version history - -Since version 3.8.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/byte_container_with_subtype/index.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/byte_container_with_subtype/index.md deleted file mode 100644 index 277fffa..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/byte_container_with_subtype/index.md +++ /dev/null @@ -1,35 +0,0 @@ -# nlohmann::byte_container_with_subtype - -```cpp -template -class byte_container_with_subtype : public BinaryType; -``` - -This type extends the template parameter `BinaryType` provided to [`basic_json`](../basic_json/index.md) with a subtype -used by BSON and MessagePack. This type exists so that the user does not have to specify a type themselves with a -specific naming scheme in order to override the binary type. - -## Template parameters - -`BinaryType` -: container to store bytes (`#!cpp std::vector` by default) - -## Member types - -- **container_type** - the type of the underlying container (`BinaryType`) -- **subtype_type** - the type of the subtype (`#!cpp std::uint64_t`) - -## Member functions - -- [(constructor)](byte_container_with_subtype.md) -- **operator==** - comparison: equal -- **operator!=** - comparison: not equal -- [**set_subtype**](subtype.md) - sets the binary subtype -- [**subtype**](subtype.md) - return the binary subtype -- [**has_subtype**](has_subtype.md) - return whether the value has a subtype -- [**clear_subtype**](clear_subtype.md) - clears the binary subtype - -## Version history - -- Added in version 3.8.0. -- Changed type of subtypes to `#!cpp std::uint64_t` in 3.10.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/byte_container_with_subtype/set_subtype.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/byte_container_with_subtype/set_subtype.md deleted file mode 100644 index cf21732..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/byte_container_with_subtype/set_subtype.md +++ /dev/null @@ -1,41 +0,0 @@ -# nlohmann::byte_container_with_subtype::set_subtype - -```cpp -void set_subtype(subtype_type subtype) noexcept; -``` - -Sets the binary subtype of the value, also flags a binary JSON value as having a subtype, which has implications for -serialization. - -## Parameters - -`subtype` (in) -: subtype to set - -## Exception safety - -No-throw guarantee: this function never throws exceptions. - -## Complexity - -Constant. - -## Examples - -??? example - - The example below demonstrates how a subtype can be set with `set_subtype`. - - ```cpp - --8<-- "examples/byte_container_with_subtype__set_subtype.cpp" - ``` - - Output: - - ```json - --8<-- "examples/byte_container_with_subtype__set_subtype.output" - ``` - -## Version history - -Since version 3.8.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/byte_container_with_subtype/subtype.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/byte_container_with_subtype/subtype.md deleted file mode 100644 index 389241a..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/byte_container_with_subtype/subtype.md +++ /dev/null @@ -1,42 +0,0 @@ -# nlohmann::byte_container_with_subtype::subtype - -```cpp -constexpr subtype_type subtype() const noexcept; -``` - -Returns the numerical subtype of the value if it has a subtype. If it does not have a subtype, this function will return -`subtype_type(-1)` as a sentinel value. - -## Return value - -the numerical subtype of the binary value, or `subtype_type(-1)` if no subtype is set - -## Exception safety - -No-throw guarantee: this function never throws exceptions. - -## Complexity - -Constant. - -## Examples - -??? example - - The example below demonstrates how the subtype can be retrieved with `subtype`. Note how `subtype_type(-1)` is - returned for container `c1`. - - ```cpp - --8<-- "examples/byte_container_with_subtype__subtype.cpp" - ``` - - Output: - - ```json - --8<-- "examples/byte_container_with_subtype__subtype.output" - ``` - -## Version history - -- Added in version 3.8.0 -- Fixed return value to properly return `subtype_type(-1)` as documented in version 3.10.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json.md deleted file mode 100644 index 36edcc2..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json.md +++ /dev/null @@ -1,28 +0,0 @@ -# nlohmann::json - -```cpp -using json = basic_json<>; -``` - -This type is the default specialization of the [basic_json](basic_json/index.md) class which uses the standard template -types. - -## Examples - -??? example - - The example below demonstrates how to use the type `nlohmann::json`. - - ```cpp - --8<-- "examples/README.cpp" - ``` - - Output: - - ```json - --8<-- "examples/README.output" - ``` - -## Version history - -Since version 1.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/back.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/back.md deleted file mode 100644 index 240bc6e..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/back.md +++ /dev/null @@ -1,40 +0,0 @@ -# nlohmann::json_pointer::back - -```cpp -const string_t& back() const; -``` - -Return last reference token. - -## Return value - -Last reference token. - -## Exceptions - -Throws [out_of_range.405](../../home/exceptions.md#jsonexceptionout_of_range405) if JSON pointer has no parent. - -## Complexity - -Constant. - -## Examples - -??? example - - The example shows the usage of `back`. - - ```cpp - --8<-- "examples/json_pointer__back.cpp" - ``` - - Output: - - ```json - --8<-- "examples/json_pointer__back.output" - ``` - -## Version history - -- Added in version 3.6.0. -- Changed return type to `string_t` in version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/empty.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/empty.md deleted file mode 100644 index 346364a..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/empty.md +++ /dev/null @@ -1,39 +0,0 @@ -# nlohmann::json_pointer::empty - -```cpp -bool empty() const noexcept; -``` - -Return whether pointer points to the root document. - -## Return value - -`#!cpp true` iff the JSON pointer points to the root document. - -## Exception safety - -No-throw guarantee: this function never throws exceptions. - -## Complexity - -Constant. - -## Examples - -??? example - - The example shows the result of `empty` for different JSON Pointers. - - ```cpp - --8<-- "examples/json_pointer__empty.cpp" - ``` - - Output: - - ```json - --8<-- "examples/json_pointer__empty.output" - ``` - -## Version history - -Added in version 3.6.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/index.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/index.md deleted file mode 100644 index 22e2464..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/index.md +++ /dev/null @@ -1,52 +0,0 @@ -# nlohmann::json_pointer - -```cpp -template -class json_pointer; -``` - -A JSON pointer defines a string syntax for identifying a specific value within a JSON document. It can be used with -functions [`at`](../basic_json/at.md) and [`operator[]`](../basic_json/operator%5B%5D.md). Furthermore, JSON pointers -are the base for JSON patches. - -## Template parameters - -`RefStringType` -: the string type used for the reference tokens making up the JSON pointer - -!!! warning "Deprecation" - - For backwards compatibility `RefStringType` may also be a specialization of [`basic_json`](../basic_json/index.md) - in which case `string_t` will be deduced as [`basic_json::string_t`](../basic_json/string_t.md). This feature is - deprecated and may be removed in a future major version. - -## Member types - -- [**string_t**](string_t.md) - the string type used for the reference tokens - -## Member functions - -- [(constructor)](json_pointer.md) -- [**to_string**](to_string.md) - return a string representation of the JSON pointer -- [**operator string_t**](operator_string_t.md) - return a string representation of the JSON pointer -- [**operator==**](operator_eq.md) - compare: equal -- [**operator!=**](operator_ne.md) - compare: not equal -- [**operator/=**](operator_slasheq.md) - append to the end of the JSON pointer -- [**operator/**](operator_slash.md) - create JSON Pointer by appending -- [**parent_pointer**](parent_pointer.md) - returns the parent of this JSON pointer -- [**pop_back**](pop_back.md) - remove last reference token -- [**back**](back.md) - return last reference token -- [**push_back**](push_back.md) - append an unescaped token at the end of the pointer -- [**empty**](empty.md) - return whether pointer points to the root document - -## Literals - -- [**operator""_json_pointer**](../operator_literal_json_pointer.md) - user-defined string literal for JSON pointers -## See also - -- [RFC 6901](https://datatracker.ietf.org/doc/html/rfc6901) - -## Version history - -- Added in version 2.0.0. -- Changed template parameter from `basic_json` to string type in version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/json_pointer.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/json_pointer.md deleted file mode 100644 index 5e7057f..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/json_pointer.md +++ /dev/null @@ -1,41 +0,0 @@ -# nlohmann::json_pointer::json_pointer - -```cpp -explicit json_pointer(const string_t& s = ""); -``` - -Create a JSON pointer according to the syntax described in -[Section 3 of RFC6901](https://tools.ietf.org/html/rfc6901#section-3). - -## Parameters - -`s` (in) -: string representing the JSON pointer; if omitted, the empty string is assumed which references the whole JSON value - -## Exceptions - -- Throws [parse_error.107](../../home/exceptions.md#jsonexceptionparse_error107) if the given JSON pointer `s` is - nonempty and does not begin with a slash (`/`); see example below. -- Throws [parse_error.108](../../home/exceptions.md#jsonexceptionparse_error108) if a tilde (`~`) in the given JSON - pointer `s` is not followed by `0` (representing `~`) or `1` (representing `/`); see example below. - -## Examples - -??? example - - The example shows the construction several valid JSON pointers as well as the exceptional behavior. - - ```cpp - --8<-- "examples/json_pointer.cpp" - ``` - - Output: - - ```json - --8<-- "examples/json_pointer.output" - ``` - -## Version history - -- Added in version 2.0.0. -- Changed type of `s` to `string_t` in version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/operator_eq.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/operator_eq.md deleted file mode 100644 index 807ae1d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/operator_eq.md +++ /dev/null @@ -1,113 +0,0 @@ -# nlohmann::json_pointer::operator== - -```cpp -// until C++20 -template -bool operator==( - const json_pointer& lhs, - const json_pointer& rhs) noexcept; // (1) - -template -bool operator==( - const json_pointer& lhs, - const StringType& rhs); // (2) - -template -bool operator==( - const StringType& lhs, - const json_pointer& rhs); // (2) - -// since C++20 -class json_pointer { - template - bool operator==( - const json_pointer& rhs) const noexcept; // (1) - - bool operator==(const string_t& rhs) const; // (2) -}; -``` - -1. Compares two JSON pointers for equality by comparing their reference tokens. - -2. Compares a JSON pointer and a string or a string and a JSON pointer for equality by converting the string to a JSON - pointer and comparing the JSON pointers according to 1. - -## Template parameters - -`RefStringTypeLhs`, `RefStringTypeRhs` -: the string type of the left-hand side or right-hand side JSON pointer, respectively - -`StringType` -: the string type derived from the `json_pointer` operand ([`json_pointer::string_t`](string_t.md)) - -## Parameters - -`lhs` (in) -: first value to consider - -`rhs` (in) -: second value to consider - -## Return value - -whether the values `lhs`/`*this` and `rhs` are equal - -## Exception safety - -1. No-throw guarantee: this function never throws exceptions. -2. Strong exception safety: if an exception occurs, the original value stays intact. - -## Exceptions - -1. (none) -2. The function can throw the following exceptions: - - Throws [parse_error.107](../../home/exceptions.md#jsonexceptionparse_error107) if the given JSON pointer `s` is - nonempty and does not begin with a slash (`/`); see example below. - - Throws [parse_error.108](../../home/exceptions.md#jsonexceptionparse_error108) if a tilde (`~`) in the given JSON - pointer `s` is not followed by `0` (representing `~`) or `1` (representing `/`); see example below. - -## Complexity - -Constant if `lhs` and `rhs` differ in the number of reference tokens, otherwise linear in the number of reference -tokens. - -## Notes - -!!! warning "Deprecation" - - Overload 2 is deprecated and will be removed in a future major version release. - -## Examples - -??? example "Example: (1) Comparing JSON pointers" - - The example demonstrates comparing JSON pointers. - - ```cpp - --8<-- "examples/json_pointer__operator__equal.cpp" - ``` - - Output: - - ``` - --8<-- "examples/json_pointer__operator__equal.output" - ``` - -??? example "Example: (2) Comparing JSON pointers and strings" - - The example demonstrates comparing JSON pointers and strings, and when doing so may raise an exception. - - ```cpp - --8<-- "examples/json_pointer__operator__equal_stringtype.cpp" - ``` - - Output: - - ``` - --8<-- "examples/json_pointer__operator__equal_stringtype.output" - ``` - -## Version history - -1. Added in version 2.1.0. Added C++20 member functions in version 3.11.2. -2. Added for backward compatibility and deprecated in version 3.11.2. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/operator_ne.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/operator_ne.md deleted file mode 100644 index 1f3e324..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/operator_ne.md +++ /dev/null @@ -1,109 +0,0 @@ -# nlohmann::json_pointer::operator!= - -```cpp -// until C++20 -template -bool operator!=( - const json_pointer& lhs, - const json_pointer& rhs) noexcept; // (1) - -template -bool operator!=( - const json_pointer& lhs, - const StringType& rhs); // (2) - -template -bool operator!=( - const StringType& lhs, - const json_pointer& rhs); // (2) -``` - -1. Compares two JSON pointers for inequality by comparing their reference tokens. - -2. Compares a JSON pointer and a string or a string and a JSON pointer for inequality by converting the string to a - JSON pointer and comparing the JSON pointers according to 1. - -## Template parameters - -`RefStringTypeLhs`, `RefStringTypeRhs` -: the string type of the left-hand side or right-hand side JSON pointer, respectively - -`StringType` -: the string type derived from the `json_pointer` operand ([`json_pointer::string_t`](string_t.md)) - -## Parameters - -`lhs` (in) -: first value to consider - -`rhs` (in) -: second value to consider - -## Return value - -whether the values `lhs`/`*this` and `rhs` are not equal - -## Exception safety - -1. No-throw guarantee: this function never throws exceptions. -2. Strong exception safety: if an exception occurs, the original value stays intact. - -## Exceptions - -1. (none) -2. The function can throw the following exceptions: - - Throws [parse_error.107](../../home/exceptions.md#jsonexceptionparse_error107) if the given JSON pointer `s` is - nonempty and does not begin with a slash (`/`); see example below. - - Throws [parse_error.108](../../home/exceptions.md#jsonexceptionparse_error108) if a tilde (`~`) in the given JSON - pointer `s` is not followed by `0` (representing `~`) or `1` (representing `/`); see example below. - -## Complexity - -Constant if `lhs` and `rhs` differ in the number of reference tokens, otherwise linear in the number of reference -tokens. - -## Notes - -!!! note "Operator overload resolution" - - Since C++20 overload resolution will consider the _rewritten candidate_ generated from - [`operator==`](operator_eq.md). - -!!! warning "Deprecation" - - Overload 2 is deprecated and will be removed in a future major version release. - -## Examples - -??? example "Example: (1) Comparing JSON pointers" - - The example demonstrates comparing JSON pointers. - - ```cpp - --8<-- "examples/json_pointer__operator__notequal.cpp" - ``` - - Output: - - ``` - --8<-- "examples/json_pointer__operator__notequal.output" - ``` - -??? example "Example: (2) Comparing JSON pointers and strings" - - The example demonstrates comparing JSON pointers and strings, and when doing so may raise an exception. - - ```cpp - --8<-- "examples/json_pointer__operator__notequal_stringtype.cpp" - ``` - - Output: - - ``` - --8<-- "examples/json_pointer__operator__notequal_stringtype.output" - ``` - -## Version history - -1. Added in version 2.1.0. -2. Added for backward compatibility and deprecated in version 3.11.2. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/operator_slash.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/operator_slash.md deleted file mode 100644 index ed77b50..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/operator_slash.md +++ /dev/null @@ -1,64 +0,0 @@ -# nlohmann::json_pointer::operator/ - -```cpp -// (1) -json_pointer operator/(const json_pointer& lhs, const json_pointer& rhs); - -// (2) -json_pointer operator/(const json_pointer& lhs, string_t token); - -// (3) -json_pointer operator/(const json_pointer& lhs, std::size_t array_idx); -``` - -1. create a new JSON pointer by appending the right JSON pointer at the end of the left JSON pointer -2. create a new JSON pointer by appending the unescaped token at the end of the JSON pointer -3. create a new JSON pointer by appending the array-index-token at the end of the JSON pointer - -## Parameters - -`lhs` (in) -: JSON pointer - -`rhs` (in) -: JSON pointer to append - -`token` (in) -: reference token to append - -`array_idx` (in) -: array index to append - -## Return value - -1. a new JSON pointer with `rhs` appended to `lhs` -2. a new JSON pointer with unescaped `token` appended to `lhs` -3. a new JSON pointer with `array_idx` appended to `lhs` - -## Complexity - -1. Linear in the length of `lhs` and `rhs`. -2. Linear in the length of `lhs`. -3. Linear in the length of `lhs`. - -## Examples - -??? example - - The example shows the usage of `operator/`. - - ```cpp - --8<-- "examples/json_pointer__operator_add_binary.cpp" - ``` - - Output: - - ```json - --8<-- "examples/json_pointer__operator_add_binary.output" - ``` - -## Version history - -1. Added in version 3.6.0. -2. Added in version 3.6.0. Changed type of `token` to `string_t` in version 3.11.0. -3. Added in version 3.6.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/operator_slasheq.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/operator_slasheq.md deleted file mode 100644 index 3518557..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/operator_slasheq.md +++ /dev/null @@ -1,61 +0,0 @@ -# nlohmann::json_pointer::operator/= - -```cpp -// (1) -json_pointer& operator/=(const json_pointer& ptr); - -// (2) -json_pointer& operator/=(string_t token); - -// (3) -json_pointer& operator/=(std::size_t array_idx) -``` - -1. append another JSON pointer at the end of this JSON pointer -2. append an unescaped reference token at the end of this JSON pointer -3. append an array index at the end of this JSON pointer - -## Parameters - -`ptr` (in) -: JSON pointer to append - -`token` (in) -: reference token to append - -`array_idx` (in) -: array index to append - -## Return value - -1. JSON pointer with `ptr` appended -2. JSON pointer with `token` appended without escaping `token` -3. JSON pointer with `array_idx` appended - -## Complexity - -1. Linear in the length of `ptr`. -2. Amortized constant. -3. Amortized constant. - -## Examples - -??? example - - The example shows the usage of `operator/=`. - - ```cpp - --8<-- "examples/json_pointer__operator_add.cpp" - ``` - - Output: - - ```json - --8<-- "examples/json_pointer__operator_add.output" - ``` - -## Version history - -1. Added in version 3.6.0. -2. Added in version 3.6.0. Changed type of `token` to `string_t` in version 3.11.0. -3. Added in version 3.6.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/operator_string_t.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/operator_string_t.md deleted file mode 100644 index 74105a4..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/operator_string_t.md +++ /dev/null @@ -1,48 +0,0 @@ -# nlohmann::json_pointer::operator string_t - -```cpp -operator string_t() const -``` - -Return a string representation of the JSON pointer. - -## Return value - -A string representation of the JSON pointer - -## Possible implementation - -```cpp -operator string_t() const -{ - return to_string(); -} -``` - -## Notes - -!!! warning "Deprecation" - - This function is deprecated in favor of [`to_string`](to_string.md) and will be removed in a future major version - release. - -## Examples - -??? example - - The example shows how JSON Pointers can be implicitly converted to strings. - - ```cpp - --8<-- "examples/json_pointer__operator_string_t.cpp" - ``` - - Output: - - ```json - --8<-- "examples/json_pointer__operator_string_t.output" - ``` - -## Version history - -- Since version 2.0.0. -- Changed type to `string_t` and deprecated in version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/parent_pointer.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/parent_pointer.md deleted file mode 100644 index 1398730..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/parent_pointer.md +++ /dev/null @@ -1,35 +0,0 @@ -# nlohmann::json_pointer::parent_pointer - -```cpp -json_pointer parent_pointer() const; -``` - -Returns the parent of this JSON pointer. - -## Return value - -Parent of this JSON pointer; in case this JSON pointer is the root, the root itself is returned. - -## Complexity - -Linear in the length of the JSON pointer. - -## Examples - -??? example - - The example shows the result of `parent_pointer` for different JSON Pointers. - - ```cpp - --8<-- "examples/json_pointer__parent_pointer.cpp" - ``` - - Output: - - ```json - --8<-- "examples/json_pointer__parent_pointer.output" - ``` - -## Version history - -Added in version 3.6.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/pop_back.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/pop_back.md deleted file mode 100644 index 3c79f36..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/pop_back.md +++ /dev/null @@ -1,35 +0,0 @@ -# nlohmann::json_pointer::pop_back - -```cpp -void pop_back(); -``` - -Remove last reference token. - -## Exceptions - -Throws [out_of_range.405](../../home/exceptions.md#jsonexceptionout_of_range405) if JSON pointer has no parent. - -## Complexity - -Constant. - -## Examples - -??? example - - The example shows the usage of `pop_back`. - - ```cpp - --8<-- "examples/json_pointer__pop_back.cpp" - ``` - - Output: - - ```json - --8<-- "examples/json_pointer__pop_back.output" - ``` - -## Version history - -Added in version 3.6.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/push_back.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/push_back.md deleted file mode 100644 index c1c19cb..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/push_back.md +++ /dev/null @@ -1,39 +0,0 @@ -# nlohmann::json_pointer::push_back - -```cpp -void push_back(const string_t& token); - -void push_back(string_t&& token); -``` - -Append an unescaped token at the end of the reference pointer. - -## Parameters - -`token` (in) -: token to add - -## Complexity - -Amortized constant. - -## Examples - -??? example - - The example shows the result of `push_back` for different JSON Pointers. - - ```cpp - --8<-- "examples/json_pointer__push_back.cpp" - ``` - - Output: - - ```json - --8<-- "examples/json_pointer__push_back.output" - ``` - -## Version history - -- Added in version 3.6.0. -- Changed type of `token` to `string_t` in version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/string_t.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/string_t.md deleted file mode 100644 index c8527bc..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/string_t.md +++ /dev/null @@ -1,28 +0,0 @@ -# nlohmann::json_pointer::string_t -```cpp -using string_t = RefStringType; -``` - -The string type used for the reference tokens making up the JSON pointer. - -See [`basic_json::string_t`](../basic_json/string_t.md) for more information. - -## Examples - -??? example - - The example shows the type `string_t` and its relation to `basic_json::string_t`. - - ```cpp - --8<-- "examples/json_pointer__string_t.cpp" - ``` - - Output: - - ```json - --8<-- "examples/json_pointer__string_t.output" - ``` - -## Version history - -- Added in version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/to_string.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/to_string.md deleted file mode 100644 index fae3abe..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_pointer/to_string.md +++ /dev/null @@ -1,40 +0,0 @@ -# nlohmann::json_pointer::to_string - -```cpp -string_t to_string() const; -``` - -Return a string representation of the JSON pointer. - -## Return value - -A string representation of the JSON pointer - -## Notes - -For each JSON pointer `ptr`, it holds: - -```cpp -ptr == json_pointer(ptr.to_string()); -``` - -## Examples - -??? example - - The example shows the result of `to_string`. - - ```cpp - --8<-- "examples/json_pointer__to_string.cpp" - ``` - - Output: - - ```json - --8<-- "examples/json_pointer__to_string.output" - ``` - -## Version history - -- Since version 2.0.0. -- Changed return type to `string_t` in version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/binary.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/binary.md deleted file mode 100644 index fc0980e..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/binary.md +++ /dev/null @@ -1,40 +0,0 @@ -# nlohmann::json_sax::binary - -```cpp -virtual bool binary(binary_t& val) = 0; -``` - -A binary value was read. - -## Parameters - -`val` (in) -: binary value - -## Return value - -Whether parsing should proceed. - -## Notes - -It is safe to move the passed binary value. - -## Examples - -??? example - - The example below shows how the SAX interface is used. - - ```cpp - --8<-- "examples/sax_parse__binary.cpp" - ``` - - Output: - - ```json - --8<-- "examples/sax_parse__binary.output" - ``` - -## Version history - -- Added in version 3.8.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/boolean.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/boolean.md deleted file mode 100644 index fdf2945..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/boolean.md +++ /dev/null @@ -1,36 +0,0 @@ -# nlohmann::json_sax::boolean - -```cpp -virtual bool boolean(bool val) = 0; -``` - -A boolean value was read. - -## Parameters - -`val` (in) -: boolean value - -## Return value - -Whether parsing should proceed. - -## Examples - -??? example - - The example below shows how the SAX interface is used. - - ```cpp - --8<-- "examples/sax_parse.cpp" - ``` - - Output: - - ```json - --8<-- "examples/sax_parse.output" - ``` - -## Version history - -- Added in version 3.2.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/end_array.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/end_array.md deleted file mode 100644 index 9c12e40..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/end_array.md +++ /dev/null @@ -1,31 +0,0 @@ -# nlohmann::json_sax::end_array - -```cpp -virtual bool end_array() = 0; -``` - -The end of an array was read. - -## Return value - -Whether parsing should proceed. - -## Examples - -??? example - - The example below shows how the SAX interface is used. - - ```cpp - --8<-- "examples/sax_parse.cpp" - ``` - - Output: - - ```json - --8<-- "examples/sax_parse.output" - ``` - -## Version history - -- Added in version 3.2.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/end_object.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/end_object.md deleted file mode 100644 index 601c94a..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/end_object.md +++ /dev/null @@ -1,31 +0,0 @@ -# nlohmann::json_sax::end_object - -```cpp -virtual bool end_object() = 0; -``` - -The end of an object was read. - -## Return value - -Whether parsing should proceed. - -## Examples - -??? example - - The example below shows how the SAX interface is used. - - ```cpp - --8<-- "examples/sax_parse.cpp" - ``` - - Output: - - ```json - --8<-- "examples/sax_parse.output" - ``` - -## Version history - -- Added in version 3.2.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/index.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/index.md deleted file mode 100644 index f63e85c..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/index.md +++ /dev/null @@ -1,44 +0,0 @@ -# nlohmann::json_sax - -```cpp -template -struct json_sax; -``` - -This class describes the SAX interface used by [sax_parse](../basic_json/sax_parse.md). Each function is called in -different situations while the input is parsed. The boolean return value informs the parser whether to continue -processing the input. - -## Template parameters - -`BasicJsonType` -: a specialization of [`basic_json`](../basic_json/index.md) - -## Member types - -- [**number_integer_t**](../basic_json/number_integer_t.md) - `BasicJsonType`'s type for numbers (integer) -- [**number_unsigned_t**](../basic_json/number_unsigned_t.md) - `BasicJsonType`'s type for numbers (unsigned) -- [**number_float_t**](../basic_json/number_float_t.md) - `BasicJsonType`'s type for numbers (floating-point) -- [**string_t**](../basic_json/string_t.md) - `BasicJsonType`'s type for strings -- [**binary_t**](../basic_json/binary_t.md) - `BasicJsonType`'s type for binary arrays - -## Member functions - -- [**binary**](binary.md) (_virtual_) - a binary value was read -- [**boolean**](boolean.md) (_virtual_) - a boolean value was read -- [**end_array**](end_array.md) (_virtual_) - the end of an array was read -- [**end_object**](end_object.md) (_virtual_) - the end of an object was read -- [**key**](key.md) (_virtual_) - an object key was read -- [**null**](null.md) (_virtual_) - a null value was read -- [**number_float**](number_float.md) (_virtual_) - a floating-point number was read -- [**number_integer**](number_integer.md) (_virtual_) - an integer number was read -- [**number_unsigned**](number_unsigned.md) (_virtual_) - an unsigned integer number was read -- [**parse_error**](parse_error.md) (_virtual_) - a parse error occurred -- [**start_array**](start_array.md) (_virtual_) - the beginning of an array was read -- [**start_object**](start_object.md) (_virtual_) - the beginning of an object was read -- [**string**](string.md) (_virtual_) - a string value was read - -## Version history - -- Added in version 3.2.0. -- Support for binary values (`binary_t`, `binary`) added in version 3.8.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/key.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/key.md deleted file mode 100644 index 31fd6c1..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/key.md +++ /dev/null @@ -1,40 +0,0 @@ -# nlohmann::json_sax::key - -```cpp -virtual bool key(string_t& val) = 0; -``` - -An object key was read. - -## Parameters - -`val` (in) -: object key - -## Return value - -Whether parsing should proceed. - -## Notes - -It is safe to move the passed object key value. - -## Examples - -??? example - - The example below shows how the SAX interface is used. - - ```cpp - --8<-- "examples/sax_parse.cpp" - ``` - - Output: - - ```json - --8<-- "examples/sax_parse.output" - ``` - -## Version history - -- Added in version 3.2.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/null.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/null.md deleted file mode 100644 index 9354ede..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/null.md +++ /dev/null @@ -1,31 +0,0 @@ -# nlohmann::json_sax::null - -```cpp -virtual bool null() = 0; -``` - -A null value was read. - -## Return value - -Whether parsing should proceed. - -## Examples - -??? example - - The example below shows how the SAX interface is used. - - ```cpp - --8<-- "examples/sax_parse.cpp" - ``` - - Output: - - ```json - --8<-- "examples/sax_parse.output" - ``` - -## Version history - -- Added in version 3.2.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/number_float.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/number_float.md deleted file mode 100644 index 1779940..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/number_float.md +++ /dev/null @@ -1,39 +0,0 @@ -# nlohmann::json_sax::number_float - -```cpp -virtual bool number_float(number_float_t val, const string_t& s) = 0; -``` - -A floating-point number was read. - -## Parameters - -`val` (in) -: floating-point value - -`s` (in) -: string representation of the original input - -## Return value - -Whether parsing should proceed. - -## Examples - -??? example - - The example below shows how the SAX interface is used. - - ```cpp - --8<-- "examples/sax_parse.cpp" - ``` - - Output: - - ```json - --8<-- "examples/sax_parse.output" - ``` - -## Version history - -- Added in version 3.2.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/number_integer.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/number_integer.md deleted file mode 100644 index 5c3cb4f..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/number_integer.md +++ /dev/null @@ -1,36 +0,0 @@ -# nlohmann::json_sax::number_integer - -```cpp -virtual bool number_integer(number_integer_t val) = 0; -``` - -An integer number was read. - -## Parameters - -`val` (in) -: integer value - -## Return value - -Whether parsing should proceed. - -## Examples - -??? example - - The example below shows how the SAX interface is used. - - ```cpp - --8<-- "examples/sax_parse.cpp" - ``` - - Output: - - ```json - --8<-- "examples/sax_parse.output" - ``` - -## Version history - -- Added in version 3.2.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/number_unsigned.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/number_unsigned.md deleted file mode 100644 index 0ac2500..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/number_unsigned.md +++ /dev/null @@ -1,36 +0,0 @@ -# nlohmann::json_sax::number_unsigned - -```cpp -virtual bool number_unsigned(number_unsigned_t val) = 0; -``` - -An unsigned integer number was read. - -## Parameters - -`val` (in) -: unsigned integer value - -## Return value - -Whether parsing should proceed. - -## Examples - -??? example - - The example below shows how the SAX interface is used. - - ```cpp - --8<-- "examples/sax_parse.cpp" - ``` - - Output: - - ```json - --8<-- "examples/sax_parse.output" - ``` - -## Version history - -- Added in version 3.2.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/parse_error.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/parse_error.md deleted file mode 100644 index e41cb67..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/parse_error.md +++ /dev/null @@ -1,44 +0,0 @@ -# nlohmann::json_sax::parse_error - -```cpp -virtual bool parse_error(std::size_t position, - const std::string& last_token, - const detail::exception& ex) = 0; -``` - -A parse error occurred. - -## Parameters - -`position` (in) -: the position in the input where the error occurs - -`last_token` (in) -: the last read token - -`ex` (in) -: an exception object describing the error - -## Return value - -Whether parsing should proceed (**must return `#!cpp false`**). - -## Examples - -??? example - - The example below shows how the SAX interface is used. - - ```cpp - --8<-- "examples/sax_parse.cpp" - ``` - - Output: - - ```json - --8<-- "examples/sax_parse.output" - ``` - -## Version history - -- Added in version 3.2.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/start_array.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/start_array.md deleted file mode 100644 index cf2b8cf..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/start_array.md +++ /dev/null @@ -1,40 +0,0 @@ -# nlohmann::json_sax::start_array - -```cpp -virtual bool start_array(std::size_t elements) = 0; -``` - -The beginning of an array was read. - -## Parameters - -`elements` (in) -: number of object elements or `#!cpp -1` if unknown - -## Return value - -Whether parsing should proceed. - -## Notes - -Binary formats may report the number of elements. - -## Examples - -??? example - - The example below shows how the SAX interface is used. - - ```cpp - --8<-- "examples/sax_parse.cpp" - ``` - - Output: - - ```json - --8<-- "examples/sax_parse.output" - ``` - -## Version history - -- Added in version 3.2.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/start_object.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/start_object.md deleted file mode 100644 index 491815d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/start_object.md +++ /dev/null @@ -1,40 +0,0 @@ -# nlohmann::json_sax::start_object - -```cpp -virtual bool start_object(std::size_t elements) = 0; -``` - -The beginning of an object was read. - -## Parameters - -`elements` (in) -: number of object elements or `#!cpp -1` if unknown - -## Return value - -Whether parsing should proceed. - -## Notes - -Binary formats may report the number of elements. - -## Examples - -??? example - - The example below shows how the SAX interface is used. - - ```cpp - --8<-- "examples/sax_parse.cpp" - ``` - - Output: - - ```json - --8<-- "examples/sax_parse.output" - ``` - -## Version history - -- Added in version 3.2.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/string.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/string.md deleted file mode 100644 index dcffb5f..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/json_sax/string.md +++ /dev/null @@ -1,40 +0,0 @@ -# nlohmann::json_sax::string - -```cpp -virtual bool string(string_t& val) = 0; -``` - -A string value was read. - -## Parameters - -`val` (in) -: string value - -## Return value - -Whether parsing should proceed. - -## Notes - -It is safe to move the passed string value. - -## Examples - -??? example - - The example below shows how the SAX interface is used. - - ```cpp - --8<-- "examples/sax_parse.cpp" - ``` - - Output: - - ```json - --8<-- "examples/sax_parse.output" - ``` - -## Version history - -- Added in version 3.2.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/index.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/index.md deleted file mode 100644 index 099dfa6..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/index.md +++ /dev/null @@ -1,60 +0,0 @@ -# Macros - -Some aspects of the library can be configured by defining preprocessor macros **before** including the `json.hpp` -header. See also the [macro overview page](../../features/macros.md). - -## Runtime assertions - -- [**JSON_ASSERT(x)**](json_assert.md) - control behavior of runtime assertions - -## Exceptions - -- [**JSON_CATCH_USER(exception)**
**JSON_THROW_USER(exception)**
**JSON_TRY_USER**](json_throw_user.md) - control exceptions -- [**JSON_DIAGNOSTICS**](json_diagnostics.md) - control extended diagnostics -- [**JSON_NOEXCEPTION**](json_noexception.md) - switch off exceptions - -## Language support - -- [**JSON_HAS_CPP_11**
**JSON_HAS_CPP_14**
**JSON_HAS_CPP_17**
**JSON_HAS_CPP_20**](json_has_cpp_11.md) - set supported C++ standard -- [**JSON_HAS_FILESYSTEM**
**JSON_HAS_EXPERIMENTAL_FILESYSTEM**](json_has_filesystem.md) - control `std::filesystem` support -- [**JSON_HAS_RANGES**](json_has_ranges.md) - control `std::ranges` support -- [**JSON_HAS_THREE_WAY_COMPARISON**](json_has_three_way_comparison.md) - control 3-way comparison support -- [**JSON_NO_IO**](json_no_io.md) - switch off functions relying on certain C++ I/O headers -- [**JSON_SKIP_UNSUPPORTED_COMPILER_CHECK**](json_skip_unsupported_compiler_check.md) - do not warn about unsupported compilers -- [**JSON_USE_GLOBAL_UDLS**](json_use_global_udls.md) - place user-defined string literals (UDLs) into the global namespace - -## Library version - -- [**JSON_SKIP_LIBRARY_VERSION_CHECK**](json_skip_library_version_check.md) - skip library version check -- [**NLOHMANN_JSON_VERSION_MAJOR**
**NLOHMANN_JSON_VERSION_MINOR**
**NLOHMANN_JSON_VERSION_PATCH**](nlohmann_json_version_major.md) - \- library version information - -## Library namespace - -- [**NLOHMANN_JSON_NAMESPACE**](nlohmann_json_namespace.md) - full name of the `nlohmann` namespace -- [**NLOHMANN_JSON_NAMESPACE_BEGIN**
**NLOHMANN_JSON_NAMESPACE_END**](nlohmann_json_namespace_begin.md) - open and - close the library namespace -- [**NLOHMANN_JSON_NAMESPACE_NO_VERSION**](nlohmann_json_namespace_no_version.md) - disable the version component of - the inline namespace - -## Type conversions - -- [**JSON_DISABLE_ENUM_SERIALIZATION**](json_disable_enum_serialization.md) - switch off default serialization/deserialization functions for enums -- [**JSON_USE_IMPLICIT_CONVERSIONS**](json_use_implicit_conversions.md) - control implicit conversions - - -## Comparison behavior - -- [**JSON_USE_LEGACY_DISCARDED_VALUE_COMPARISON**](json_use_legacy_discarded_value_comparison.md) - - control comparison of discarded values - -## Serialization/deserialization macros - -- [**NLOHMANN_DEFINE_TYPE_INTRUSIVE(type, member...)**
**NLOHMANN_DEFINE_TYPE_INTRUSIVE_WITH_DEFAULT(type, member...)**][DefInt] - \- serialization/deserialization of types _with_ access to private variables -- [**NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE(type, member...)**
**NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE_WITH_DEFAULT(type, member...)**][DefNonInt] - \- serialization/deserialization of types _without_ access to private variables -- [**NLOHMANN_JSON_SERIALIZE_ENUM(type, ...)**](nlohmann_json_serialize_enum.md) - serialization/deserialization of enum types - -[DefInt]: nlohmann_define_type_intrusive.md -[DefNonInt]: nlohmann_define_type_non_intrusive.md diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_assert.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_assert.md deleted file mode 100644 index a093341..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_assert.md +++ /dev/null @@ -1,84 +0,0 @@ -# JSON_ASSERT - -```cpp -#define JSON_ASSERT(x) /* value */ -``` - -This macro controls which code is executed for [runtime assertions](../../features/assertions.md) of the library. - -## Parameters - -`x` (in) -: expression of scalar type - -## Default definition - -The default value is [`#!cpp assert(x)`](https://en.cppreference.com/w/cpp/error/assert). - -```cpp -#define JSON_ASSERT(x) assert(x) -``` - -Therefore, assertions can be switched off by defining `NDEBUG`. - -## Notes - -- The library uses numerous assertions to guarantee invariants and to abort in case of otherwise undefined behavior - (e.g., when calling [operator[]](../basic_json/operator%5B%5D.md) with a missing object key on a `const` object). See - page [runtime assertions](../../features/assertions.md) for more information. -- Defining the macro to code that does not call `std::abort` may leave the library in an undefined state. -- The macro is undefined outside the library. - -## Examples - -??? example "Example 1: default behavior" - - The following code will trigger an assertion at runtime: - - ```cpp - #include - - using json = nlohmann::json; - - int main() - { - const json j = {{"key", "value"}}; - auto v = j["missing"]; - } - ``` - - Output: - - ``` - Assertion failed: (m_value.object->find(key) != m_value.object->end()), function operator[], file json.hpp, line 2144. - ``` - -??? example "Example 2: user-defined behavior" - - The assertion reporting can be changed by defining `JSON_ASSERT(x)` differently. - - ```cpp - #include - #include - #define JSON_ASSERT(x) if(!(x)){fprintf(stderr, "assertion error in %s\n", __FUNCTION__); std::abort();} - - #include - - using json = nlohmann::json; - - int main() - { - const json j = {{"key", "value"}}; - auto v = j["missing"]; - } - ``` - - Output: - - ``` - assertion error in operator[] - ``` - -## Version history - -- Added in version 3.9.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_diagnostics.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_diagnostics.md deleted file mode 100644 index 4fc0fc3..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_diagnostics.md +++ /dev/null @@ -1,76 +0,0 @@ -# JSON_DIAGNOSTICS - -```cpp -#define JSON_DIAGNOSTICS /* value */ -``` - -This macro enables [extended diagnostics for exception messages](../../home/exceptions.md#extended-diagnostic-messages). -Possible values are `1` to enable or `0` to disable (default). - -When enabled, exception messages contain a [JSON Pointer](../json_pointer/json_pointer.md) to the JSON value that -triggered the exception. Note that enabling this macro increases the size of every JSON value by one pointer and adds -some runtime overhead. - -## Default definition - -The default value is `0` (extended diagnostics are switched off). - -```cpp -#define JSON_DIAGNOSTICS 0 -``` - -When the macro is not defined, the library will define it to its default value. - -## Notes - -!!! note "ABI compatibility" - - As of version 3.11.0, this macro is no longer required to be defined consistently throughout a codebase to avoid - One Definition Rule (ODR) violations, as the value of this macro is encoded in the namespace, resulting in distinct - symbol names. - - This allows different parts of a codebase to use different versions or configurations of this library without - causing improper behavior. - - Where possible, it is still recommended that all code define this the same way for maximum interoperability. - -!!! hint "CMake option" - - Diagnostic messages can also be controlled with the CMake option - [`JSON_Diagnostics`](../../integration/cmake.md#json_diagnostics) (`OFF` by default) - which defines `JSON_DIAGNOSTICS` accordingly. - -## Examples - -??? example "Example 1: default behavior" - - ```cpp - --8<-- "examples/diagnostics_standard.cpp" - ``` - - Output: - - ``` - --8<-- "examples/diagnostics_standard.output" - ``` - - This exception can be hard to debug if storing the value `#!c "12"` and accessing it is further apart. - -??? example "Example 2: extended diagnostic messages" - - ```cpp - --8<-- "examples/diagnostics_extended.cpp" - ``` - - Output: - - ``` - --8<-- "examples/diagnostics_extended.output" - ``` - - Now the exception message contains a JSON Pointer `/address/housenumber` that indicates which value has the wrong type. - -## Version history - -- Added in version 3.10.0. -- As of version 3.11.0 the definition is allowed to vary between translation units. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_disable_enum_serialization.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_disable_enum_serialization.md deleted file mode 100644 index 6df3dd5..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_disable_enum_serialization.md +++ /dev/null @@ -1,152 +0,0 @@ -# JSON_DISABLE_ENUM_SERIALIZATION - -```cpp -#define JSON_DISABLE_ENUM_SERIALIZATION /* value */ -``` - -When defined to `1`, default serialization and deserialization functions for enums are excluded and have to be provided -by the user, for example, using [`NLOHMANN_JSON_SERIALIZE_ENUM`](nlohmann_json_serialize_enum.md) (see -[arbitrary type conversions](../../features/arbitrary_types.md) for more details). - -Parsing or serializing an enum will result in a compiler error. - -This works for both unscoped and scoped enums. - -## Default definition - -The default value is `0`. - -```cpp -#define JSON_DISABLE_ENUM_SERIALIZATION 0 -``` - -## Notes - -!!! hint "CMake option" - - Enum serialization can also be controlled with the CMake option - [`JSON_DisableEnumSerialization`](../../integration/cmake.md#json_disableenumserialization) - (`OFF` by default) which defines `JSON_DISABLE_ENUM_SERIALIZATION` accordingly. - -## Examples - -??? example "Example 1: Disabled behavior" - - The code below forces the library **not** to create default serialization/deserialization functions `from_json` and `to_json`, meaning the code below - **does not** compile. - - ```cpp - #define JSON_DISABLE_ENUM_SERIALIZATION 1 - #include - - using json = nlohmann::json; - - enum class Choice - { - first, - second, - }; - - int main() - { - // normally invokes to_json serialization function but with JSON_DISABLE_ENUM_SERIALIZATION defined, it does not - const json j = Choice::first; - - // normally invokes from_json parse function but with JSON_DISABLE_ENUM_SERIALIZATION defined, it does not - Choice ch = j.get(); - } - ``` - -??? example "Example 2: Serialize enum macro" - - The code below forces the library **not** to create default serialization/deserialization functions `from_json` and `to_json`, but uses - [`NLOHMANN_JSON_SERIALIZE_ENUM`](nlohmann_json_serialize_enum.md) to parse and serialize the enum. - - ```cpp - #define JSON_DISABLE_ENUM_SERIALIZATION 1 - #include - - using json = nlohmann::json; - - enum class Choice - { - first, - second, - }; - - NLOHMANN_JSON_SERIALIZE_ENUM(Choice, - { - { Choice::first, "first" }, - { Choice::second, "second" }, - }) - - int main() - { - // uses user-defined to_json function defined by macro - const json j = Choice::first; - - // uses user-defined from_json function defined by macro - Choice ch = j.get(); - } - ``` - -??? example "Example 3: User-defined serialization/deserialization functions" - - The code below forces the library **not** to create default serialization/deserialization functions `from_json` and `to_json`, but uses user-defined - functions to parse and serialize the enum. - - ```cpp - #define JSON_DISABLE_ENUM_SERIALIZATION 1 - #include - - using json = nlohmann::json; - - enum class Choice - { - first, - second, - }; - - void from_json(const json& j, Choice& ch) - { - auto value = j.get(); - if (value == "first") - { - ch = Choice::first; - } - else if (value == "second") - { - ch = Choice::second; - } - } - - void to_json(json& j, const Choice& ch) - { - auto value = j.get(); - if (value == "first") - { - ch = Choice::first; - } - else if (value == "second") - { - ch = Choice::second; - } - } - - int main() - { - // uses user-defined to_json function - const json j = Choice::first; - - // uses user-defined from_json function - Choice ch = j.get(); - } - ``` - -## See also - -- [`NLOHMANN_JSON_SERIALIZE_ENUM`](nlohmann_json_serialize_enum.md) - -## Version history - -- Added in version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_has_cpp_11.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_has_cpp_11.md deleted file mode 100644 index f3eaa58..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_has_cpp_11.md +++ /dev/null @@ -1,41 +0,0 @@ -# JSON_HAS_CPP_11, JSON_HAS_CPP_14, JSON_HAS_CPP_17, JSON_HAS_CPP_20 - -```cpp -#define JSON_HAS_CPP_11 -#define JSON_HAS_CPP_14 -#define JSON_HAS_CPP_17 -#define JSON_HAS_CPP_20 -``` - -The library targets C++11, but also supports some features introduced in later C++ versions (e.g., `std::string_view` -support for C++17). For these new features, the library implements some preprocessor checks to determine the C++ -standard. By defining any of these symbols, the internal check is overridden and the provided C++ version is -unconditionally assumed. This can be helpful for compilers that only implement parts of the standard and would be -detected incorrectly. - -## Default definition - -The default value is detected based on preprocessor macros such as `#!cpp __cplusplus`, `#!cpp _HAS_CXX17`, or -`#!cpp _MSVC_LANG`. - -## Notes - -- `#!cpp JSON_HAS_CPP_11` is always defined. -- All macros are undefined outside the library. - -## Examples - -??? example - - The code below forces the library to use the C++14 standard: - - ```cpp - #define JSON_HAS_CPP_14 1 - #include - - ... - ``` - -## Version history - -- Added in version 3.10.5. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_has_filesystem.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_has_filesystem.md deleted file mode 100644 index 308aea2..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_has_filesystem.md +++ /dev/null @@ -1,43 +0,0 @@ -# JSON_HAS_FILESYSTEM / JSON_HAS_EXPERIMENTAL_FILESYSTEM - -```cpp -#define JSON_HAS_FILESYSTEM /* value */ -#define JSON_HAS_EXPERIMENTAL_FILESYSTEM /* value */ -``` - -When compiling with C++17, the library provides conversions from and to -[`std::filesystem::path`](https://en.cppreference.com/w/cpp/filesystem/path). As compiler support for filesystem is -limited, the library tries to detect whether -[``/`std::filesystem`](https://en.cppreference.com/w/cpp/header/filesystem) (`JSON_HAS_FILESYSTEM`) or -[``/`std::experimental::filesystem`](https://en.cppreference.com/w/cpp/header/experimental/filesystem) -(`JSON_HAS_EXPERIMENTAL_FILESYSTEM`) should be used. To override the built-in check, define `JSON_HAS_FILESYSTEM` or -`JSON_HAS_EXPERIMENTAL_FILESYSTEM` to `1`. - -## Default definition - -The default value is detected based on the preprocessor macros `#!cpp __cpp_lib_filesystem`, -`#!cpp __cpp_lib_experimental_filesystem`, `#!cpp __has_include()`, or -`#!cpp __has_include()`. - -## Notes - -- Note that older compilers or older versions of libstd++ also require the library `stdc++fs` to be linked to for - filesystem support. -- Both macros are undefined outside the library. - -## Examples - -??? example - - The code below forces the library to use the header ``. - - ```cpp - #define JSON_HAS_EXPERIMENTAL_FILESYSTEM 1 - #include - - ... - ``` - -## Version history - -- Added in version 3.10.5. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_has_ranges.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_has_ranges.md deleted file mode 100644 index 96d5105..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_has_ranges.md +++ /dev/null @@ -1,31 +0,0 @@ -# JSON_HAS_RANGES - -```cpp -#define JSON_HAS_RANGES /* value */ -``` - -This macro indicates whether the standard library has any support for ranges. Implies support for concepts. -Possible values are `1` when supported or `0` when unsupported. - -## Default definition - -The default value is detected based on the preprocessor macro `#!cpp __cpp_lib_ranges`. - -When the macro is not defined, the library will define it to its default value. - -## Examples - -??? example - - The code below forces the library to enable support for ranges: - - ```cpp - #define JSON_HAS_RANGES 1 - #include - - ... - ``` - -## Version history - -- Added in version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_has_three_way_comparison.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_has_three_way_comparison.md deleted file mode 100644 index f52070e..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_has_three_way_comparison.md +++ /dev/null @@ -1,32 +0,0 @@ -# JSON_HAS_THREE_WAY_COMPARISON - -```cpp -#define JSON_HAS_THREE_WAY_COMPARISON /* value */ -``` - -This macro indicates whether the compiler and standard library support 3-way comparison. -Possible values are `1` when supported or `0` when unsupported. - -## Default definition - -The default value is detected based on the preprocessor macros `#!cpp __cpp_impl_three_way_comparison` -and `#!cpp __cpp_lib_three_way_comparison`. - -When the macro is not defined, the library will define it to its default value. - -## Examples - -??? example - - The code below forces the library to use 3-way comparison: - - ```cpp - #define JSON_HAS_THREE_WAY_COMPARISON 1 - #include - - ... - ``` - -## Version history - -- Added in version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_no_io.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_no_io.md deleted file mode 100644 index ef37384..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_no_io.md +++ /dev/null @@ -1,35 +0,0 @@ -# JSON_NO_IO - -```cpp -#define JSON_NO_IO -``` - -When defined, headers ``, ``, ``, ``, and `` are not included and parse functions -relying on these headers are excluded. This is relevant for environments where these I/O functions are disallowed for -security reasons (e.g., Intel Software Guard Extensions (SGX)). - -## Default definition - -By default, `#!cpp JSON_NO_IO` is not defined. - -```cpp -#undef JSON_NO_IO -``` - -## Examples - -??? example - - The code below forces the library not to use the headers ``, ``, ``, ``, and - ``. - - ```cpp - #define JSON_NO_IO 1 - #include - - ... - ``` - -## Version history - -- Added in version 3.10.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_noexception.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_noexception.md deleted file mode 100644 index c801b85..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_noexception.md +++ /dev/null @@ -1,45 +0,0 @@ -# JSON_NOEXCEPTION - -```cpp -#define JSON_NOEXCEPTION -``` - -Exceptions can be switched off by defining the symbol `JSON_NOEXCEPTION`. When defining `JSON_NOEXCEPTION`, `#!cpp try` -is replaced by `#!cpp if (true)`, `#!cpp catch` is replaced by `#!cpp if (false)`, and `#!cpp throw` is replaced by -`#!cpp std::abort()`. - -The same effect is achieved by setting the compiler flag `-fno-exceptions`. - -## Default definition - -By default, the macro is not defined. - -```cpp -#undef JSON_NOEXCEPTION -``` - -## Notes - -The explanatory [`what()`](https://en.cppreference.com/w/cpp/error/exception/what) string of exceptions is not -available for MSVC if exceptions are disabled, see [#2824](https://github.com/nlohmann/json/discussions/2824). - -## Examples - -??? example - - The code below switches off exceptions in the library. - - ```cpp - #define JSON_NOEXCEPTION 1 - #include - - ... - ``` - -## See also - -- [Switch off exceptions](../../home/exceptions.md#switch-off-exceptions) for more information how to switch off exceptions - -## Version history - -Added in version 2.1.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_skip_library_version_check.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_skip_library_version_check.md deleted file mode 100644 index c9a743c..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_skip_library_version_check.md +++ /dev/null @@ -1,37 +0,0 @@ -# JSON_SKIP_LIBRARY_VERSION_CHECK - -```cpp -#define JSON_SKIP_LIBRARY_VERSION_CHECK -``` - -When defined, the library will not create a compiler warning when a different version of the library was already -included. - -## Default definition - -By default, the macro is not defined. - -```cpp -#undef JSON_SKIP_LIBRARY_VERSION_CHECK -``` - -## Notes - -!!! danger "ABI compatibility" - - Mixing different library versions in the same code can be a problem as the different versions may not be ABI - compatible. - -## Examples - -!!! example - - The following warning will be shown in case a different version of the library was already included: - - ``` - Already included a different version of the library! - ``` - -## Version history - -Added in version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_skip_unsupported_compiler_check.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_skip_unsupported_compiler_check.md deleted file mode 100644 index 374fa4c..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_skip_unsupported_compiler_check.md +++ /dev/null @@ -1,33 +0,0 @@ -# JSON_SKIP_UNSUPPORTED_COMPILER_CHECK - -```cpp -#define JSON_SKIP_UNSUPPORTED_COMPILER_CHECK -``` - -When defined, the library will not create a compile error when a known unsupported compiler is detected. This allows to -use the library with compilers that do not fully support C++11 and may only work if unsupported features are not used. - -## Default definition - -By default, the macro is not defined. - -```cpp -#undef JSON_SKIP_UNSUPPORTED_COMPILER_CHECK -``` - -## Examples - -??? example - - The code below switches off the check whether the compiler is supported. - - ```cpp - #define JSON_SKIP_UNSUPPORTED_COMPILER_CHECK 1 - #include - - ... - ``` - -## Version history - -Added in version 3.2.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_throw_user.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_throw_user.md deleted file mode 100644 index e10db90..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_throw_user.md +++ /dev/null @@ -1,75 +0,0 @@ -# JSON_CATCH_USER, JSON_THROW_USER, JSON_TRY_USER - -```cpp -// (1) -#define JSON_CATCH_USER(exception) /* value */ -// (2) -#define JSON_THROW_USER(exception) /* value */ -// (3) -#define JSON_TRY_USER /* value */ -``` - -Controls how exceptions are handled by the library. - -1. This macro overrides [`#!cpp catch`](https://en.cppreference.com/w/cpp/language/try_catch) calls inside the library. - The argument is the type of the exception to catch. As of version 3.8.0, the library only catches `std::out_of_range` - exceptions internally to rethrow them as [`json::out_of_range`](../../home/exceptions.md#out-of-range) exceptions. - The macro is always followed by a scope. -2. This macro overrides `#!cpp throw` calls inside the library. The argument is the exception to be thrown. Note that - `JSON_THROW_USER` should leave the current scope (e.g., by throwing or aborting), as continuing after it may yield - undefined behavior. -3. This macro overrides `#!cpp try` calls inside the library. It has no arguments and is always followed by a scope. - -## Parameters - -`exception` (in) -: an exception type - -## Default definition - -By default, the macros map to their respective C++ keywords: - -```cpp -#define JSON_CATCH_USER(exception) catch(exception) -#define JSON_THROW_USER(exception) throw exception -#define JSON_TRY_USER try -``` - -When exceptions are switched off, the `#!cpp try` block is executed unconditionally, and throwing exceptions is -replaced by calling [`std::abort`](https://en.cppreference.com/w/cpp/utility/program/abort) to make reaching the -`#!cpp throw` branch abort the process. - -```cpp -#define JSON_THROW_USER(exception) std::abort() -#define JSON_TRY_USER if (true) -#define JSON_CATCH_USER(exception) if (false) -``` - -## Examples - -??? example - - The code below switches off exceptions and creates a log entry with a detailed error message in case of errors. - - ```cpp - #include - - #define JSON_TRY_USER if(true) - #define JSON_CATCH_USER(exception) if(false) - #define JSON_THROW_USER(exception) \ - {std::clog << "Error in " << __FILE__ << ":" << __LINE__ \ - << " (function " << __FUNCTION__ << ") - " \ - << (exception).what() << std::endl; \ - std::abort();} - - #include - ``` - -## See also - -- [Switch off exceptions](../../home/exceptions.md#switch-off-exceptions) for more information how to switch off exceptions -- [JSON_NOEXCEPTION](JSON_NOEXCEPTION) - switch off exceptions - -## Version history - -- Added in version 3.1.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_use_global_udls.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_use_global_udls.md deleted file mode 100644 index 69db9e7..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_use_global_udls.md +++ /dev/null @@ -1,98 +0,0 @@ -# JSON_USE_GLOBAL_UDLS - -```cpp -#define JSON_USE_GLOBAL_UDLS /* value */ -``` - -When defined to `1`, the user-defined string literals (UDLs) are placed into the global namespace instead of -`nlohmann::literals::json_literals`. - -## Default definition - -The default value is `1`. - -```cpp -#define JSON_USE_GLOBAL_UDLS 1 -``` - -When the macro is not defined, the library will define it to its default value. - -## Notes - -!!! info "Future behavior change" - - The user-defined string literals will be removed from the global namespace in the next major release of the library. - - To prepare existing code, define `JSON_USE_GLOBAL_UDLS` to `0` and bring the string literals into scope where - needed. Refer to any of the [string literals](#see-also) for details. - -!!! hint "CMake option" - - The placement of user-defined string literals can also be controlled with the CMake option - [`JSON_GlobalUDLs`](../../integration/cmake.md#json_globaludls) (`ON` by default) which defines - `JSON_USE_GLOBAL_UDLS` accordingly. - -## Examples - -??? example "Example 1: Default behavior" - - The code below shows the default behavior using the `_json` UDL. - - ```cpp - #include - - #include - - int main() - { - auto j = "42"_json; - - std::cout << j << std::endl; - } - ``` - - Output: - - ```json - 42 - ``` - -??? example "Example 2: Namespaced UDLs" - - The code below shows how UDLs need to be brought into scope before using `_json` when `JSON_USE_GLOBAL_UDLS` is - defined to `0`. - - ```cpp - #define JSON_USE_GLOBAL_UDLS 0 - #include - - #include - - int main() - { - // auto j = "42"_json; // This line would fail to compile, - // because the UDLs are not in the global namespace - - // Bring the UDLs into scope - using namespace nlohmann::json_literals; - - auto j = "42"_json; - - std::cout << j << std::endl; - } - ``` - - Output: - - ```json - 42 - ``` - -## See also - -- [`operator""_json`](../operator_literal_json.md) -- [`operator""_json_pointer`](../operator_literal_json_pointer.md) - -## Version history - -- Added in version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_use_implicit_conversions.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_use_implicit_conversions.md deleted file mode 100644 index adadffa..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_use_implicit_conversions.md +++ /dev/null @@ -1,59 +0,0 @@ -# JSON_USE_IMPLICIT_CONVERSIONS - -```cpp -#define JSON_USE_IMPLICIT_CONVERSIONS /* value */ -``` - -When defined to `0`, implicit conversions are switched off. By default, implicit conversions are switched on. The -value directly affects [`operator ValueType`](../basic_json/operator_ValueType.md). - -## Default definition - -By default, implicit conversions are enabled. - -```cpp -#define JSON_USE_IMPLICIT_CONVERSIONS 1 -``` - -## Notes - -!!! info "Future behavior change" - - Implicit conversions will be switched off by default in the next major release of the library. - - You can prepare existing code by already defining `JSON_USE_IMPLICIT_CONVERSIONS` to `0` and replace any implicit - conversions with calls to [`get`](../basic_json/get.md). - -!!! hint "CMake option" - - Implicit conversions can also be controlled with the CMake option - [`JSON_ImplicitConversions`](../../integration/cmake.md#json_legacydiscardedvaluecomparison) - (`ON` by default) which defines `JSON_USE_IMPLICIT_CONVERSIONS` accordingly. - -## Examples - -??? example - - This is an example for an implicit conversion: - - ```cpp - json j = "Hello, world!"; - std::string s = j; - ``` - - When `JSON_USE_IMPLICIT_CONVERSIONS` is defined to `0`, the code above does no longer compile. Instead, it must be - written like this: - - ```cpp - json j = "Hello, world!"; - auto s = j.get(); - ``` - -## See also - -- [**operator ValueType**](../basic_json/operator_ValueType.md) - get a value (implicit) -- [**get**](../basic_json/get.md) - get a value (explicit) - -## Version history - -- Added in version 3.9.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_use_legacy_discarded_value_comparison.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_use_legacy_discarded_value_comparison.md deleted file mode 100644 index bc1d143..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/json_use_legacy_discarded_value_comparison.md +++ /dev/null @@ -1,77 +0,0 @@ -# JSON_USE_LEGACY_DISCARDED_VALUE_COMPARISON - -```cpp -#define JSON_USE_LEGACY_DISCARDED_VALUE_COMPARISON /* value */ -``` - -This macro enables the (incorrect) legacy comparison behavior of discarded JSON values. Possible values are `1` to -enable or `0` to disable (default). - -When enabled, comparisons involving at least one discarded JSON value yield results as follows: - -| **Operator** | **Result** | -|--------------|---------------| -| `==` | `#!cpp false` | -| `!=` | `#!cpp true` | -| `<` | `#!cpp false` | -| `<=` | `#!cpp true` | -| `>=` | `#!cpp true` | -| `>` | `#!cpp false` | - -Otherwise, comparisons involving at least one discarded JSON value always yield `#!cpp false`. - -## Default definition - -The default value is `0`. - -```cpp -#define JSON_USE_LEGACY_DISCARDED_VALUE_COMPARISON 0 -``` - -When the macro is not defined, the library will define it to its default value. - -## Notes - -!!! warning "Inconsistent behavior in C++20 and beyond" - - When targeting C++20 or above, enabling the legacy comparison behavior is _strongly_ - discouraged. - - - The 3-way comparison operator (`<=>`) will always give the correct result - (`#!cpp std::partial_ordering::unordered`) regardless of the value of - `JSON_USE_LEGACY_DISCARDED_VALUE_COMPARISON`. - - Overloads for the equality and relational operators emulate the legacy behavior. - - Code outside your control may use either 3-way comparison or the equality and relational operators, resulting in - inconsistent and unpredictable behavior. - - See [`operator<=>`](../basic_json/operator_spaceship.md) for more information on 3-way comparison. - -!!! warning "Deprecation" - - The legacy comparison behavior is deprecated and may be removed in a future major version release. - - New code should not depend on it and existing code should try to remove or rewrite expressions relying on it. - -!!! hint "CMake option" - - Legacy comparison can also be controlled with the CMake option - [`JSON_LegacyDiscardedValueComparison`](../../integration/cmake.md#json_legacydiscardedvaluecomparison) - (`OFF` by default) which defines `JSON_USE_LEGACY_DISCARDED_VALUE_COMPARISON` accordingly. - -## Examples - -??? example - - The code below switches on the legacy discarded value comparison behavior in the library. - - ```cpp - #define JSON_USE_LEGACY_DISCARDED_VALUE_COMPARISON 1 - #include - - ... - ``` - -## Version history - -- Added in version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/nlohmann_define_type_intrusive.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/nlohmann_define_type_intrusive.md deleted file mode 100644 index afd09c6..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/nlohmann_define_type_intrusive.md +++ /dev/null @@ -1,126 +0,0 @@ -# NLOHMANN_DEFINE_TYPE_INTRUSIVE, NLOHMANN_DEFINE_TYPE_INTRUSIVE_WITH_DEFAULT - -```cpp -#define NLOHMANN_DEFINE_TYPE_INTRUSIVE(type, member...) // (1) -#define NLOHMANN_DEFINE_TYPE_INTRUSIVE_WITH_DEFAULT(type, member...) // (2) -``` - -These macros can be used to simplify the serialization/deserialization of types if you want to use a JSON object as -serialization and want to use the member variable names as object keys in that object. The macro is to be defined -**inside** the class/struct to create code for. Unlike -[`NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE`](nlohmann_define_type_non_intrusive.md), it can access private members. The first -parameter is the name of the class/struct, and all remaining parameters name the members. - -1. Will use [`at`](../basic_json/at.md) during deserialization and will throw - [`out_of_range.403`](../../home/exceptions.md#jsonexceptionout_of_range403) if a key is missing in the JSON object. -2. Will use [`value`](../basic_json/value.md) during deserialization and fall back to the default value for the - respective type of the member variable if a key in the JSON object is missing. The generated `from_json()` function - default constructs an object and uses its values as the defaults when calling the `value` function. - -## Parameters - -`type` (in) -: name of the type (class, struct) to serialize/deserialize - -`member` (in) -: name of the member variable to serialize/deserialize; up to 64 members can be given as comma-separated list - -## Default definition - -The macros add two friend functions to the class which take care of the serialization and deserialization: - -```cpp -friend void to_json(nlohmann::json&, const type&); -friend void from_json(const nlohmann::json&, type&); -``` - -See examples below for the concrete generated code. - -## Notes - -!!! info "Prerequisites" - - 1. The type `type` must be default constructible. See [How can I use `get()` for non-default - constructible/non-copyable types?][GetNonDefNonCopy] for how to overcome this limitation. - 2. The macro must be used inside the type (class/struct). - -[GetNonDefNonCopy]: ../../features/arbitrary_types.md#how-can-i-use-get-for-non-default-constructiblenon-copyable-types - -!!! warning "Implementation limits" - - - The current implementation is limited to at most 64 member variables. If you want to serialize/deserialize types - with more than 64 member variables, you need to define the `to_json`/`from_json` functions manually. - - The macros only work for the [`nlohmann::json`](../json.md) type; other specializations such as - [`nlohmann::ordered_json`](../ordered_json.md) are currently unsupported. - -## Examples - -??? example "Example (1): NLOHMANN_DEFINE_TYPE_INTRUSIVE" - - Consider the following complete example: - - ```cpp hl_lines="21" - --8<-- "examples/nlohmann_define_type_intrusive_macro.cpp" - ``` - - Output: - - ```json - --8<-- "examples/nlohmann_define_type_intrusive_macro.output" - ``` - - Notes: - - - `ns::person` is default-constructible. This is a requirement for using the macro. - - `ns::person` has private member variables. This makes `NLOHMANN_DEFINE_TYPE_INTRUSIVE` applicable, but not - `NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE`. - - The macro `NLOHMANN_DEFINE_TYPE_INTRUSIVE` is used _inside_ the class. - - A missing key "age" in the deserialization yields an exception. To fall back to the default value, - `NLOHMANN_DEFINE_TYPE_INTRUSIVE_WITH_DEFAULT` can be used. - - The macro is equivalent to: - - ```cpp hl_lines="21 22 23 24 25 26 27 28 29 30 31 32 33" - --8<-- "examples/nlohmann_define_type_intrusive_explicit.cpp" - ``` - -??? example "Example (2): NLOHMANN_DEFINE_TYPE_INTRUSIVE_WITH_DEFAULT" - - Consider the following complete example: - - ```cpp hl_lines="21" - --8<-- "examples/nlohmann_define_type_intrusive_with_default_macro.cpp" - ``` - - Output: - - ```json - --8<-- "examples/nlohmann_define_type_intrusive_with_default_macro.output" - ``` - - Notes: - - - `ns::person` is default-constructible. This is a requirement for using the macro. - - `ns::person` has private member variables. This makes `NLOHMANN_DEFINE_TYPE_INTRUSIVE_WITH_DEFAULT` applicable, - but not `NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE_WITH_DEFAULT`. - - The macro `NLOHMANN_DEFINE_TYPE_INTRUSIVE_WITH_DEFAULT` is used _inside_ the class. - - A missing key "age" in the deserialization does not yield an exception. Instead, the default value `-1` is used. - - The macro is equivalent to: - - ```cpp hl_lines="21 22 23 24 25 26 27 28 29 30 31 32 33 34" - --8<-- "examples/nlohmann_define_type_intrusive_with_default_explicit.cpp" - ``` - - Note how a default-initialized `person` object is used in the `from_json` to fill missing values. - -## See also - -- [NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE / NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE_WITH_DEFAULT](nlohmann_define_type_non_intrusive.md) - for a similar macro that can be defined _outside_ the type. -- [Arbitrary Type Conversions](../../features/arbitrary_types.md) for an overview. - -## Version history - -1. Added in version 3.9.0. -2. Added in version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/nlohmann_define_type_non_intrusive.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/nlohmann_define_type_non_intrusive.md deleted file mode 100644 index 70cf934..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/nlohmann_define_type_non_intrusive.md +++ /dev/null @@ -1,127 +0,0 @@ -# NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE, NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE_WITH_DEFAULT - -```cpp -#define NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE(type, member...) // (1) -#define NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE_WITH_DEFAULT(type, member...) // (2) -``` - -These macros can be used to simplify the serialization/deserialization of types if you want to use a JSON object as -serialization and want to use the member variable names as object keys in that object. The macro is to be defined -**outside** the class/struct to create code for, but **inside** its namespace. Unlike -[`NLOHMANN_DEFINE_TYPE_INTRUSIVE`](nlohmann_define_type_intrusive.md), it **cannot** access private members. The first -parameter is the name of the class/struct, and all remaining parameters name the members. - -1. Will use [`at`](../basic_json/at.md) during deserialization and will throw - [`out_of_range.403`](../../home/exceptions.md#jsonexceptionout_of_range403) if a key is missing in the JSON object. -2. Will use [`value`](../basic_json/value.md) during deserialization and fall back to the default value for the - respective type of the member variable if a key in the JSON object is missing. The generated `from_json()` function - default constructs an object and uses its values as the defaults when calling the `value` function. - -## Parameters - -`type` (in) -: name of the type (class, struct) to serialize/deserialize - -`member` (in) -: name of the (public) member variable to serialize/deserialize; up to 64 members can be given as comma-separated list - -## Default definition - -The macros add two functions to the namespace which take care of the serialization and deserialization: - -```cpp -void to_json(nlohmann::json&, const type&); -void from_json(const nlohmann::json&, type&); -``` - -See examples below for the concrete generated code. - -## Notes - -!!! info "Prerequisites" - - 1. The type `type` must be default constructible. See [How can I use `get()` for non-default constructible/non-copyable types?][GetNonDefNonCopy] - for how to overcome this limitation. - 2. The macro must be used outside the type (class/struct). - 3. The passed members must be public. - -[GetNonDefNonCopy]: ../../features/arbitrary_types.md#how-can-i-use-get-for-non-default-constructiblenon-copyable-types - -!!! warning "Implementation limits" - - - The current implementation is limited to at most 64 member variables. If you want to serialize/deserialize types - with more than 64 member variables, you need to define the `to_json`/`from_json` functions manually. - - The macros only work for the [`nlohmann::json`](../json.md) type; other specializations such as - [`nlohmann::ordered_json`](../ordered_json.md) are currently unsupported. - -## Examples - -??? example "Example (1): NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE" - - Consider the following complete example: - - ```cpp hl_lines="15" - --8<-- "examples/nlohmann_define_type_non_intrusive_macro.cpp" - ``` - - Output: - - ```json - --8<-- "examples/nlohmann_define_type_non_intrusive_macro.output" - ``` - - Notes: - - - `ns::person` is default-constructible. This is a requirement for using the macro. - - `ns::person` has only public member variables. This makes `NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE` applicable. - - The macro `NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE` is used _outside_ the class, but _inside_ its namespace `ns`. - - A missing key "age" in the deserialization yields an exception. To fall back to the default value, - `NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE_WITH_DEFAULT` can be used. - - The macro is equivalent to: - - ```cpp hl_lines="15 16 17 18 19 20 21 22 23 24 25 26 27" - --8<-- "examples/nlohmann_define_type_non_intrusive_explicit.cpp" - ``` - -??? example "Example (2): NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE_WITH_DEFAULT" - - Consider the following complete example: - - ```cpp hl_lines="20" - --8<-- "examples/nlohmann_define_type_non_intrusive_with_default_macro.cpp" - ``` - - Output: - - ```json - --8<-- "examples/nlohmann_define_type_non_intrusive_with_default_macro.output" - ``` - - Notes: - - - `ns::person` is default-constructible. This is a requirement for using the macro. - - `ns::person` has only public member variables. This makes `NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE_WITH_DEFAULT` - applicable. - - The macro `NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE_WITH_DEFAULT` is used _outside_ the class, but _inside_ its - namespace `ns`. - - A missing key "age" in the deserialization does not yield an exception. Instead, the default value `-1` is used. - - The macro is equivalent to: - - ```cpp hl_lines="20 21 22 23 24 25 26 27 28 29 30 31 32 33" - --8<-- "examples/nlohmann_define_type_non_intrusive_with_default_explicit.cpp" - ``` - - Note how a default-initialized `person` object is used in the `from_json` to fill missing values. - -## See also - -- [NLOHMANN_DEFINE_TYPE_INTRUSIVE / NLOHMANN_DEFINE_TYPE_INTRUSIVE_WITH_DEFAULT](nlohmann_define_type_intrusive.md) - for a similar macro that can be defined _inside_ the type. -- [Arbitrary Type Conversions](../../features/arbitrary_types.md) for an overview. - -## Version history - -1. Added in version 3.9.0. -2. Added in version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/nlohmann_json_namespace.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/nlohmann_json_namespace.md deleted file mode 100644 index 5c54dba..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/nlohmann_json_namespace.md +++ /dev/null @@ -1,41 +0,0 @@ -# NLOHMANN_JSON_NAMESPACE - -```cpp -#define NLOHMANN_JSON_NAMESPACE /* value */ -``` - -This macro evaluates to the full name of the `nlohmann` namespace. - -## Default definition - -The default value consists of the root namespace (`nlohmann`) and an inline ABI namespace. See -[`nlohmann` Namespace](../../features/namespace.md#structure) for details. - -When the macro is not defined, the library will define it to its default value. Overriding this value has no effect on -the library. - -## Examples - -??? example - - The example shows how to use `NLOHMANN_JSON_NAMESPACE` instead of just `nlohmann`, as well as how to output the value - of `NLOHMANN_JSON_NAMESPACE`. - - ```cpp - --8<-- "examples/nlohmann_json_namespace.cpp" - ``` - - Output: - - ```json - --8<-- "examples/nlohmann_json_namespace.output" - ``` - -## See also - -- [`NLOHMANN_JSON_NAMESPACE_BEGIN, NLOHMANN_JSON_NAMESPACE_END`](nlohmann_json_namespace_begin.md) -- [`NLOHMANN_JSON_NAMESPACE_NO_VERSION`](nlohmann_json_namespace_no_version.md) - -## Version history - -- Added in version 3.11.0. Changed inline namespace name in version 3.11.2. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/nlohmann_json_namespace_begin.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/nlohmann_json_namespace_begin.md deleted file mode 100644 index 1374264..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/nlohmann_json_namespace_begin.md +++ /dev/null @@ -1,61 +0,0 @@ -# NLOHMANN_JSON_NAMESPACE_BEGIN, NLOHMANN_JSON_NAMESPACE_END - -```cpp -#define NLOHMANN_JSON_NAMESPACE_BEGIN /* value */ // (1) -#define NLOHMANN_JSON_NAMESPACE_END /* value */ // (2) -``` - -These macros can be used to open and close the `nlohmann` namespace. See -[`nlohmann` Namespace](../../features/namespace.md#structure) for details. - -1. Opens the namespace. -2. Closes the namespace. - -## Default definition - -The default definitions open and close the `nlohmann` namespace. The precise definition of -[`NLOHMANN_JSON_NAMESPACE_BEGIN`] varies as described [here](../../features/namespace.md#structure). - -1. Default definition of `NLOHMANN_JSON_NAMESPACE_BEGIN`: - - ```cpp - namespace nlohmann - { - inline namespace json_abi_v3_11_2 - { - ``` - -2. Default definition of `NLOHMANN_JSON_NAMESPACE_END`: - ```cpp - } // namespace json_abi_v3_11_2 - } // namespace nlohmann - ``` - -When these macros are not defined, the library will define them to their default definitions. - -## Examples - -??? example - - The example shows how to use `NLOHMANN_JSON_NAMESPACE_BEGIN`/`NLOHMANN_JSON_NAMESPACE_END` from the - [How do I convert third-party types?](../../features/arbitrary_types.md#how-do-i-convert-third-party-types) page. - - ```cpp - --8<-- "examples/nlohmann_json_namespace_begin.c++17.cpp" - ``` - - Output: - - ```json - --8<-- "examples/nlohmann_json_namespace_begin.c++17.output" - ``` - -## See also - -- [`nlohmann` Namespace](../../features/namespace.md) -- [NLOHMANN_JSON_NAMESPACE](nlohmann_json_namespace.md) -- [`NLOHMANN_JSON_NAMESPACE_NO_VERSION`](nlohmann_json_namespace_no_version.md) - -## Version history - -- Added in version 3.11.0. Changed inline namespace name in version 3.11.2. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/nlohmann_json_namespace_no_version.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/nlohmann_json_namespace_no_version.md deleted file mode 100644 index 9e2a52d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/nlohmann_json_namespace_no_version.md +++ /dev/null @@ -1,45 +0,0 @@ -# NLOHMANN_JSON_NAMESPACE_NO_VERSION - -```cpp -#define NLOHMANN_JSON_NAMESPACE_NO_VERSION /* value */ -``` - -If defined to `1`, the version component is omitted from the inline namespace. See -[`nlohmann` Namespace](../../features/namespace.md#structure) for details. - -## Default definition - -The default value is `0`. - -```cpp -#define NLOHMANN_JSON_NAMESPACE_NO_VERSION 0 -``` - -When the macro is not defined, the library will define it to its default value. - -## Examples - -??? example - - The example shows how to use `NLOHMANN_JSON_NAMESPACE_NO_VERSION` to disable the version component of the inline - namespace. - - ```cpp - --8<-- "examples/nlohmann_json_namespace_no_version.cpp" - ``` - - Output: - - ```json - --8<-- "examples/nlohmann_json_namespace_no_version.output" - ``` - -## See also - -- [`nlohmann` Namespace](../../features/namespace.md) -- [`NLOHMANN_JSON_NAMESPACE`](nlohmann_json_namespace.md) -- [`NLOHMANN_JSON_NAMESPACE_BEGIN, NLOHMANN_JSON_NAMESPACE_END`](nlohmann_json_namespace_begin.md) - -## Version history - -- Added in version 3.11.2. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/nlohmann_json_serialize_enum.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/nlohmann_json_serialize_enum.md deleted file mode 100644 index b7204a8..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/nlohmann_json_serialize_enum.md +++ /dev/null @@ -1,85 +0,0 @@ -# NLOHMANN_JSON_SERIALIZE_ENUM - -```cpp -#define NLOHMANN_JSON_SERIALIZE_ENUM(type, conversion...) -``` - -By default, enum values are serialized to JSON as integers. In some cases this could result in undesired behavior. If an -enum is modified or re-ordered after data has been serialized to JSON, the later de-serialized JSON data may be -undefined or a different enum value than was originally intended. - -The `NLOHMANN_JSON_SERIALIZE_ENUM` allows to define a user-defined serialization for every enumerator. - -## Parameters - -`type` (in) -: name of the enum to serialize/deserialize - -`conversion` (in) -: a pair of an enumerator and a JSON serialization; arbitrary pairs can can be given as comma-separated list - -## Default definition - -The macros add two friend functions to the class which take care of the serialization and deserialization: - -```cpp -template -inline void to_json(BasicJsonType& j, const type& e); -template -inline void from_json(const BasicJsonType& j, type& e); -``` - -## Notes - -!!! info "Prerequisites" - - The macro must be used inside the namespace of the enum. - -!!! important "Important notes" - - - When using [`get()`](../basic_json/get.md), undefined JSON values will default to the first specified - conversion. Select this default pair carefully. See example 1 below. - - If an enum or JSON value is specified in multiple conversions, the first matching conversion from the top of the - list will be returned when converting to or from JSON. See example 2 below. - -## Examples - -??? example "Example 1: Basic usage" - - The example shows how `NLOHMANN_JSON_SERIALIZE_ENUM` can be used to serialize/deserialize both classical enums and - C++11 enum classes: - - ```cpp hl_lines="16 17 18 19 20 21 22 29 30 31 32 33" - --8<-- "examples/nlohmann_json_serialize_enum.cpp" - ``` - - Output: - - ```json - --8<-- "examples/nlohmann_json_serialize_enum.output" - ``` - -??? example "Example 2: Multiple conversions for one enumerator" - - The example shows how to use multiple conversions for a single enumerator. In the example, `Color::red` will always - be *serialized* to `"red"`, because the first occurring conversion. The second conversion, however, offers an - alternative *deserialization* from `"rot"` to `Color::red`. - - ```cpp hl_lines="17" - --8<-- "examples/nlohmann_json_serialize_enum_2.cpp" - ``` - - Output: - - ```json - --8<-- "examples/nlohmann_json_serialize_enum_2.output" - ``` - -## See also - -- [Specializing enum conversion](../../features/enum_conversion.md) -- [`JSON_DISABLE_ENUM_SERIALIZATION`](json_disable_enum_serialization.md) - -## Version history - -Added in version 3.4.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/nlohmann_json_version_major.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/nlohmann_json_version_major.md deleted file mode 100644 index d7a3142..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/macros/nlohmann_json_version_major.md +++ /dev/null @@ -1,40 +0,0 @@ -# NLOHMANN_JSON_VERSION_MAJOR, NLOHMANN_JSON_VERSION_MINOR, NLOHMANN_JSON_VERSION_PATCH - -```cpp -#define NLOHMANN_JSON_VERSION_MAJOR /* value */ -#define NLOHMANN_JSON_VERSION_MINOR /* value */ -#define NLOHMANN_JSON_VERSION_PATCH /* value */ -``` - -These macros are defined by the library and contain the version numbers according to -[Semantic Versioning 2.0.0](https://semver.org/spec/v2.0.0.html). - -## Default definition - -The macros are defined according to the current library version. - -## Examples - -??? example - - The example below shows how `NLOHMANN_JSON_VERSION_MAJOR`, `NLOHMANN_JSON_VERSION_MINOR`, and - `NLOHMANN_JSON_VERSION_PATCH` are defined by the library. - - ```cpp - --8<-- "examples/nlohmann_json_version.cpp" - ``` - - Output: - - ```json - --8<-- "examples/nlohmann_json_version.output" - ``` - -## See also - -- [meta](../basic_json/meta.md) - returns version information on the library -- [JSON_SKIP_LIBRARY_VERSION_CHECK](json_skip_library_version_check.md) - skip library version check - -## Version history - -- Added in version 3.1.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/operator_gtgt.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/operator_gtgt.md deleted file mode 100644 index e76cc0d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/operator_gtgt.md +++ /dev/null @@ -1,64 +0,0 @@ -# nlohmann::operator>>(basic_json) - -```cpp -std::istream& operator>>(std::istream& i, basic_json& j); -``` - -Deserializes an input stream to a JSON value. - -## Parameters - -`i` (in, out) -: input stream to read a serialized JSON value from - -`j` (in, out) -: JSON value to write the deserialized input to - -## Return value - -the stream `i` - -## Exceptions - -- Throws [`parse_error.101`](../home/exceptions.md#jsonexceptionparse_error101) in case of an unexpected token. -- Throws [`parse_error.102`](../home/exceptions.md#jsonexceptionparse_error102) if to_unicode fails or surrogate error. -- Throws [`parse_error.103`](../home/exceptions.md#jsonexceptionparse_error103) if to_unicode fails. - -## Complexity - -Linear in the length of the input. The parser is a predictive LL(1) parser. - -## Notes - -A UTF-8 byte order mark is silently ignored. - -!!! warning "Deprecation" - - This function replaces function `#!cpp std::istream& operator<<(basic_json& j, std::istream& i)` which has - been deprecated in version 3.0.0. It will be removed in version 4.0.0. Please replace calls like `#!cpp j << i;` - with `#!cpp i >> j;`. - -## Examples - -??? example - - The example below shows how a JSON value is constructed by reading a serialization from a stream. - - ```cpp - --8<-- "examples/operator_deserialize.cpp" - ``` - - Output: - - ```json - --8<-- "examples/operator_deserialize.output" - ``` - -## See also - -- [accept](basic_json/accept.md) - check if the input is valid JSON -- [parse](basic_json/parse.md) - deserialize from a compatible input - -## Version history - -- Added in version 1.0.0. Deprecated in version 3.0.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/operator_literal_json.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/operator_literal_json.md deleted file mode 100644 index cda0021..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/operator_literal_json.md +++ /dev/null @@ -1,61 +0,0 @@ -# nlohmann::operator""_json - -```cpp -json operator "" _json(const char* s, std::size_t n); -``` - -This operator implements a user-defined string literal for JSON objects. It can be used by adding `#!cpp _json` to a -string literal and returns a [`json`](json.md) object if no parse error occurred. - -It is recommended to bring the operator into scope using any of the following lines: -```cpp -using nlohmann::literals::operator "" _json; -using namespace nlohmann::literals; -using namespace nlohmann::json_literals; -using namespace nlohmann::literals::json_literals; -using namespace nlohmann; -``` - -This is suggested to ease migration to the next major version release of the library. See -['JSON_USE_GLOBAL_UDLS`](macros/json_use_global_udls.md#notes) for details. - -## Parameters - -`s` (in) -: a string representation of a JSON object - -`n` (in) -: length of string `s` - -## Return value - -[`json`](json.md) value parsed from `s` - -## Exceptions - -The function can throw anything that [`parse(s, s+n)`](basic_json/parse.md) would throw. - -## Complexity - -Linear. - -## Examples - -??? example - - The following code shows how to create JSON values from string literals. - - ```cpp - --8<-- "examples/operator_literal_json.cpp" - ``` - - Output: - - ```json - --8<-- "examples/operator_literal_json.output" - ``` - -## Version history - -- Added in version 1.0.0. -- Moved to namespace `nlohmann::literals::json_literals` in 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/operator_literal_json_pointer.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/operator_literal_json_pointer.md deleted file mode 100644 index 14d5378..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/operator_literal_json_pointer.md +++ /dev/null @@ -1,64 +0,0 @@ -# nlohmann::operator""_json_pointer - -```cpp -json_pointer operator "" _json_pointer(const char* s, std::size_t n); -``` - -This operator implements a user-defined string literal for JSON Pointers. It can be used by adding `#!cpp _json_pointer` -to a string literal and returns a [`json_pointer`](json_pointer/index.md) object if no parse error occurred. - -It is recommended to bring the operator into scope using any of the following lines: -```cpp -using nlohmann::literals::operator "" _json_pointer; -using namespace nlohmann::literals; -using namespace nlohmann::json_literals; -using namespace nlohmann::literals::json_literals; -using namespace nlohmann; -``` -This is suggested to ease migration to the next major version release of the library. See -['JSON_USE_GLOBAL_UDLS`](macros/json_use_global_udls.md#notes) for details. - -## Parameters - -`s` (in) -: a string representation of a JSON Pointer - -`n` (in) -: length of string `s` - -## Return value - -[`json_pointer`](json_pointer/index.md) value parsed from `s` - -## Exceptions - -The function can throw anything that [`json_pointer::json_pointer`](json_pointer/index.md) would throw. - -## Complexity - -Linear. - -## Examples - -??? example - - The following code shows how to create JSON Pointers from string literals. - - ```cpp - --8<-- "examples/operator_literal_json_pointer.cpp" - ``` - - Output: - - ```json - --8<-- "examples/operator_literal_json_pointer.output" - ``` - -## See also - -- [json_pointer](json_pointer/index.md) - type to represent JSON Pointers - -## Version history - -- Added in version 2.0.0. -- Moved to namespace `nlohmann::literals::json_literals` in 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/operator_ltlt.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/operator_ltlt.md deleted file mode 100644 index 1718b3c..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/operator_ltlt.md +++ /dev/null @@ -1,87 +0,0 @@ -# nlohmann::operator<<(basic_json), nlohmann::operator<<(json_pointer) - -```cpp -std::ostream& operator<<(std::ostream& o, const basic_json& j); // (1) - -std::ostream& operator<<(std::ostream& o, const json_pointer& ptr); // (2) -``` - -1. Serialize the given JSON value `j` to the output stream `o`. The JSON value will be serialized using the - [`dump`](basic_json/dump.md) member function. - - The indentation of the output can be controlled with the member variable `width` of the output stream `o`. For - instance, using the manipulator `std::setw(4)` on `o` sets the indentation level to `4` and the serialization - result is the same as calling `dump(4)`. - - The indentation character can be controlled with the member variable `fill` of the output stream `o`. - For instance, the manipulator `std::setfill('\\t')` sets indentation to use a tab character rather than the - default space character. -2. Write a string representation of the given JSON pointer `ptr` to the output stream `o`. The string representation is - obtained using the [`to_string`](json_pointer/to_string.md) member function. - -## Parameters - -`o` (in, out) -: stream to write to - -`j` (in) -: JSON value to serialize - -`ptr` (in) -: JSON pointer to write - -## Return value - -the stream `o` - -## Exceptions - -1. Throws [`type_error.316`](../home/exceptions.md#jsonexceptiontype_error316) if a string stored inside the JSON - value is not UTF-8 encoded. Note that unlike the [`dump`](basic_json/dump.md) member functions, no `error_handler` - can be set. -2. None. - -## Complexity - -Linear. - -## Notes - -!!! warning "Deprecation" - - Function `#!cpp std::ostream& operator<<(std::ostream& o, const basic_json& j)` replaces function - `#!cpp std::ostream& operator>>(const basic_json& j, std::ostream& o)` which has been deprecated in version 3.0.0. - It will be removed in version 4.0.0. Please replace calls like `#!cpp j >> o;` with `#!cpp o << j;`. - -## Examples - -??? example "Example: (1) serialize JSON value to stream" - - The example below shows the serialization with different parameters to `width` to adjust the indentation level. - - ```cpp - --8<-- "examples/operator_ltlt__basic_json.cpp" - ``` - - Output: - - ```json - --8<-- "examples/operator_ltlt__basic_json.output" - ``` - -??? example "Example: (2) write JSON pointer to stream" - - The example below shows how to write a JSON pointer to a stream. - - ```cpp - --8<-- "examples/operator_ltlt__json_pointer.cpp" - ``` - - Output: - - ```json - --8<-- "examples/operator_ltlt__json_pointer.output" - ``` -## Version history - -1. Added in version 1.0.0. Added support for indentation character and deprecated - `#!cpp std::ostream& operator>>(const basic_json& j, std::ostream& o)` in version 3.0.0. -3. Added in version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/ordered_json.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/ordered_json.md deleted file mode 100644 index 7cfd9f4..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/ordered_json.md +++ /dev/null @@ -1,32 +0,0 @@ -# nlohmann::ordered_json - -```cpp -using ordered_json = basic_json; -``` - -This type preserves the insertion order of object keys. - -## Examples - -??? example - - The example below demonstrates how `ordered_json` preserves the insertion order of object keys. - - ```cpp - --8<-- "examples/ordered_json.cpp" - ``` - - Output: - - ```json - --8<-- "examples/ordered_json.output" - ``` - -## See also - -- [ordered_map](ordered_map.md) -- [Object Order](../features/object_order.md) - -## Version history - -Since version 3.9.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/ordered_map.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/ordered_map.md deleted file mode 100644 index 160b85c..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/api/ordered_map.md +++ /dev/null @@ -1,77 +0,0 @@ -# nlohmann::ordered_map - -```cpp -template, - class Allocator = std::allocator>> -struct ordered_map : std::vector, Allocator>; -``` - -A minimal map-like container that preserves insertion order for use within [`nlohmann::ordered_json`](ordered_json.md) -(`nlohmann::basic_json`). - -## Template parameters - -`Key` -: key type - -`T` -: mapped type - -`IgnoredLess` -: comparison function (ignored and only added to ensure compatibility with `#!cpp std::map`) - -`Allocator` -: allocator type - -## Member types - -- **key_type** - key type (`Key`) -- **mapped_type** - mapped type (`T`) -- **Container** - base container type (`#!cpp std::vector, Allocator>`) -- **iterator** -- **const_iterator** -- **size_type** -- **value_type** -- **key_compare** - key comparison function -```cpp -std::equal_to // until C++14 - -std::equal_to<> // since C++14 -``` - -## Member functions - -- (constructor) -- (destructor) -- **emplace** -- **operator\[\]** -- **at** -- **erase** -- **count** -- **find** -- **insert** - -## Examples - -??? example - - The example shows the different behavior of `std::map` and `nlohmann::ordered_map`. - - ```cpp - --8<-- "examples/ordered_map.cpp" - ``` - - Output: - - ```json - --8<-- "examples/ordered_map.output" - ``` - -## See also - -- [ordered_json](ordered_json.md) - -## Version history - -- Added in version 3.9.0 to implement [`nlohmann::ordered_json`](ordered_json.md). -- Added **key_compare** member in version 3.11.0. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/css/custom.css b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/css/custom.css deleted file mode 100644 index 7a1008b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/css/custom.css +++ /dev/null @@ -1,4 +0,0 @@ -/* disable ligatures in code and preformatted blocks */ -code, pre { - font-variant-ligatures: none; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/arbitrary_types.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/arbitrary_types.md deleted file mode 100644 index 046a597..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/arbitrary_types.md +++ /dev/null @@ -1,274 +0,0 @@ -# Arbitrary Type Conversions - -Every type can be serialized in JSON, not just STL containers and scalar types. Usually, you would do something along those lines: - -```cpp -namespace ns { - // a simple struct to model a person - struct person { - std::string name; - std::string address; - int age; - }; -} // namespace ns - -ns::person p = {"Ned Flanders", "744 Evergreen Terrace", 60}; - -// convert to JSON: copy each value into the JSON object -json j; -j["name"] = p.name; -j["address"] = p.address; -j["age"] = p.age; - -// ... - -// convert from JSON: copy each value from the JSON object -ns::person p { - j["name"].get(), - j["address"].get(), - j["age"].get() -}; -``` - -It works, but that's quite a lot of boilerplate... Fortunately, there's a better way: - -```cpp -// create a person -ns::person p {"Ned Flanders", "744 Evergreen Terrace", 60}; - -// conversion: person -> json -json j = p; - -std::cout << j << std::endl; -// {"address":"744 Evergreen Terrace","age":60,"name":"Ned Flanders"} - -// conversion: json -> person -auto p2 = j.get(); - -// that's it -assert(p == p2); -``` - -## Basic usage - -To make this work with one of your types, you only need to provide two functions: - -```cpp -using json = nlohmann::json; - -namespace ns { - void to_json(json& j, const person& p) { - j = json{ {"name", p.name}, {"address", p.address}, {"age", p.age} }; - } - - void from_json(const json& j, person& p) { - j.at("name").get_to(p.name); - j.at("address").get_to(p.address); - j.at("age").get_to(p.age); - } -} // namespace ns -``` - -That's all! When calling the `json` constructor with your type, your custom `to_json` method will be automatically called. -Likewise, when calling `get()` or `get_to(your_type&)`, the `from_json` method will be called. - -Some important things: - -* Those methods **MUST** be in your type's namespace (which can be the global namespace), or the library will not be able to locate them (in this example, they are in namespace `ns`, where `person` is defined). -* Those methods **MUST** be available (e.g., proper headers must be included) everywhere you use these conversions. Look at [issue 1108](https://github.com/nlohmann/json/issues/1108) for errors that may occur otherwise. -* When using `get()`, `your_type` **MUST** be [DefaultConstructible](https://en.cppreference.com/w/cpp/named_req/DefaultConstructible). (There is a way to bypass this requirement described later.) -* In function `from_json`, use function [`at()`](../api/basic_json/at.md) to access the object values rather than `operator[]`. In case a key does not exist, `at` throws an exception that you can handle, whereas `operator[]` exhibits undefined behavior. -* You do not need to add serializers or deserializers for STL types like `std::vector`: the library already implements these. - - -## Simplify your life with macros - -If you just want to serialize/deserialize some structs, the `to_json`/`from_json` functions can be a lot of boilerplate. - -There are four macros to make your life easier as long as you (1) want to use a JSON object as serialization and (2) want to use the member variable names as object keys in that object: - -- [`NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE(name, member1, member2, ...)`](../api/macros/nlohmann_define_type_non_intrusive.md) is to be defined inside the namespace of the class/struct to create code for. It will throw an exception in `from_json()` due to a missing value in the JSON object. -- [`NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE_WITH_DEFAULT(name, member1, member2, ...)`](../api/macros/nlohmann_define_type_non_intrusive.md) is to be defined inside the namespace of the class/struct to create code for. It will not throw an exception in `from_json()` due to a missing value in the JSON object, but fills in values from object which is default-constructed by the type. -- [`NLOHMANN_DEFINE_TYPE_INTRUSIVE(name, member1, member2, ...)`](../api/macros/nlohmann_define_type_intrusive.md) is to be defined inside the class/struct to create code for. This macro can also access private members. It will throw an exception in `from_json()` due to a missing value in the JSON object. -- [`NLOHMANN_DEFINE_TYPE_INTRUSIVE_WITH_DEFAULT(name, member1, member2, ...)`](../api/macros/nlohmann_define_type_intrusive.md) is to be defined inside the class/struct to create code for. This macro can also access private members. It will not throw an exception in `from_json()` due to a missing value in the JSON object, but fills in values from object which is default-constructed by the type. - -In all macros, the first parameter is the name of the class/struct, and all remaining parameters name the members. You can read more docs about them starting from [here](macros.md#nlohmann_define_type_intrusivetype-member). - -!!! info "Implementation limits" - - - The current macro implementations are limited to at most 64 member variables. If you want to serialize/deserialize - types with more than 64 member variables, you need to define the `to_json`/`from_json` functions manually. - - The macros only work for the [`nlohmann::json`](../api/json.md) type; other specializations such as - [`nlohmann::ordered_json`](../api/ordered_json.md) are currently unsupported. - -??? example - - The `to_json`/`from_json` functions for the `person` struct above can be created with: - - ```cpp - namespace ns { - NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE(person, name, address, age) - } - ``` - - Here is an example with private members, where `NLOHMANN_DEFINE_TYPE_INTRUSIVE` is needed: - - ```cpp - namespace ns { - class address { - private: - std::string street; - int housenumber; - int postcode; - - public: - NLOHMANN_DEFINE_TYPE_INTRUSIVE(address, street, housenumber, postcode) - }; - } - ``` - -## How do I convert third-party types? - -This requires a bit more advanced technique. But first, let's see how this conversion mechanism works: - -The library uses **JSON Serializers** to convert types to json. -The default serializer for `nlohmann::json` is `nlohmann::adl_serializer` (ADL means [Argument-Dependent Lookup](https://en.cppreference.com/w/cpp/language/adl)). - -It is implemented like this (simplified): - -```cpp -template -struct adl_serializer { - static void to_json(json& j, const T& value) { - // calls the "to_json" method in T's namespace - } - - static void from_json(const json& j, T& value) { - // same thing, but with the "from_json" method - } -}; -``` - -This serializer works fine when you have control over the type's namespace. However, what about `boost::optional` or `std::filesystem::path` (C++17)? Hijacking the `boost` namespace is pretty bad, and it's illegal to add something other than template specializations to `std`... - -To solve this, you need to add a specialization of `adl_serializer` to the `nlohmann` namespace, here's an example: - -```cpp -// partial specialization (full specialization works too) -NLOHMANN_JSON_NAMESPACE_BEGIN -template -struct adl_serializer> { - static void to_json(json& j, const boost::optional& opt) { - if (opt == boost::none) { - j = nullptr; - } else { - j = *opt; // this will call adl_serializer::to_json which will - // find the free function to_json in T's namespace! - } - } - - static void from_json(const json& j, boost::optional& opt) { - if (j.is_null()) { - opt = boost::none; - } else { - opt = j.get(); // same as above, but with - // adl_serializer::from_json - } - } -}; -NLOHMANN_JSON_NAMESPACE_END -``` - -!!! note "ABI compatibility" - - Use [`NLOHMANN_JSON_NAMESPACE_BEGIN`](../api/macros/nlohmann_json_namespace_begin.md) and `NLOHMANN_JSON_NAMESPACE_END` - instead of `#!cpp namespace nlohmann { }` in code which may be linked with different versions of this library. - -## How can I use `get()` for non-default constructible/non-copyable types? - -There is a way, if your type is [MoveConstructible](https://en.cppreference.com/w/cpp/named_req/MoveConstructible). You will need to specialize the `adl_serializer` as well, but with a special `from_json` overload: - -```cpp -struct move_only_type { - move_only_type() = delete; - move_only_type(int ii): i(ii) {} - move_only_type(const move_only_type&) = delete; - move_only_type(move_only_type&&) = default; - - int i; -}; - -namespace nlohmann { - template <> - struct adl_serializer { - // note: the return type is no longer 'void', and the method only takes - // one argument - static move_only_type from_json(const json& j) { - return {j.get()}; - } - - // Here's the catch! You must provide a to_json method! Otherwise, you - // will not be able to convert move_only_type to json, since you fully - // specialized adl_serializer on that type - static void to_json(json& j, move_only_type t) { - j = t.i; - } - }; -} -``` - -## Can I write my own serializer? (Advanced use) - -Yes. You might want to take a look at [`unit-udt.cpp`](https://github.com/nlohmann/json/blob/develop/tests/src/unit-udt.cpp) in the test suite, to see a few examples. - -If you write your own serializer, you'll need to do a few things: - -- use a different `basic_json` alias than `nlohmann::json` (the last template parameter of `basic_json` is the `JSONSerializer`) -- use your `basic_json` alias (or a template parameter) in all your `to_json`/`from_json` methods -- use `nlohmann::to_json` and `nlohmann::from_json` when you need ADL - -Here is an example, without simplifications, that only accepts types with a size <= 32, and uses ADL. - -```cpp -// You should use void as a second template argument -// if you don't need compile-time checks on T -template::type> -struct less_than_32_serializer { - template - static void to_json(BasicJsonType& j, T value) { - // we want to use ADL, and call the correct to_json overload - using nlohmann::to_json; // this method is called by adl_serializer, - // this is where the magic happens - to_json(j, value); - } - - template - static void from_json(const BasicJsonType& j, T& value) { - // same thing here - using nlohmann::from_json; - from_json(j, value); - } -}; -``` - -Be **very** careful when reimplementing your serializer, you can stack overflow if you don't pay attention: - -```cpp -template -struct bad_serializer -{ - template - static void to_json(BasicJsonType& j, const T& value) { - // this calls BasicJsonType::json_serializer::to_json(j, value); - // if BasicJsonType::json_serializer == bad_serializer ... oops! - j = value; - } - - template - static void to_json(const BasicJsonType& j, T& value) { - // this calls BasicJsonType::json_serializer::from_json(j, value); - // if BasicJsonType::json_serializer == bad_serializer ... oops! - value = j.template get(); // oops! - } -}; -``` diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/assertions.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/assertions.md deleted file mode 100644 index 2bad62e..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/assertions.md +++ /dev/null @@ -1,131 +0,0 @@ -# Runtime Assertions - -The code contains numerous debug assertions to ensure class invariants are valid or to detect undefined behavior. -Whereas the former class invariants are nothing to be concerned of, the latter checks for undefined behavior are to -detect bugs in client code. - -## Switch off runtime assertions - -Runtime assertions can be switched off by defining the preprocessor macro `NDEBUG` (see the -[documentation of assert](https://en.cppreference.com/w/cpp/error/assert)) which is the default for release builds. - -## Change assertion behavior - -The behavior of runtime assertions can be changes by defining macro [`JSON_ASSERT(x)`](../api/macros/json_assert.md) -before including the `json.hpp` header. - -## Function with runtime assertions - -### Unchecked object access to a const value - -Function [`operator[]`](../api/basic_json/operator%5B%5D.md) implements unchecked access for objects. Whereas a missing -key is added in case of non-const objects, accessing a const object with a missing key is undefined behavior (think of a -dereferenced null pointer) and yields a runtime assertion. - -If you are not sure whether an element in an object exists, use checked access with the -[`at` function](../api/basic_json/at.md) or call the [`contains` function](../api/basic_json/contains.md) before. - -See also the documentation on [element access](element_access/index.md). - -??? example "Example 1: Missing object key" - - The following code will trigger an assertion at runtime: - - ```cpp - #include - - using json = nlohmann::json; - - int main() - { - const json j = {{"key", "value"}}; - auto v = j["missing"]; - } - ``` - - Output: - - ``` - Assertion failed: (m_value.object->find(key) != m_value.object->end()), function operator[], file json.hpp, line 2144. - ``` - -### Constructing from an uninitialized iterator range - -Constructing a JSON value from an iterator range (see [constructor](../api/basic_json/basic_json.md)) with an -uninitialized iterator is undefined behavior and yields a runtime assertion. - -??? example "Example 2: Uninitialized iterator range" - - The following code will trigger an assertion at runtime: - - ```cpp - #include - - using json = nlohmann::json; - - int main() - { - json::iterator it1, it2; - json j(it1, it2); - } - ``` - - Output: - - ``` - Assertion failed: (m_object != nullptr), function operator++, file iter_impl.hpp, line 368. - ``` - -### Operations on uninitialized iterators - -Any operation on uninitialized iterators (i.e., iterators that are not associated with any JSON value) is undefined -behavior and yields a runtime assertion. - -??? example "Example 3: Uninitialized iterator" - - The following code will trigger an assertion at runtime: - - ```cpp - #include - - using json = nlohmann::json; - - int main() - { - json::iterator it; - ++it; - } - ``` - - Output: - - ``` - Assertion failed: (m_object != nullptr), function operator++, file iter_impl.hpp, line 368. - ``` - -### Reading from a null `FILE` pointer - -Reading from a null `#!cpp FILE` pointer is undefined behavior and yields a runtime assertion. This can happen when -calling `#!cpp std::fopen` on a nonexistent file. - -??? example "Example 4: Uninitialized iterator" - - The following code will trigger an assertion at runtime: - - ```cpp - #include - - using json = nlohmann::json; - - int main() - { - std::FILE* f = std::fopen("nonexistent_file.json", "r"); - json j = json::parse(f); - } - ``` - - Output: - - ``` - Assertion failed: (m_file != nullptr), function file_input_adapter, file input_adapters.hpp, line 55. - ``` diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/binary_formats/bjdata.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/binary_formats/bjdata.md deleted file mode 100644 index a89a228..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/binary_formats/bjdata.md +++ /dev/null @@ -1,194 +0,0 @@ -# BJData - -The [BJData format](https://neurojson.org) was derived from and improved upon -[Universal Binary JSON(UBJSON)](https://ubjson.org) specification (Draft 12). Specifically, it introduces an optimized -array container for efficient storage of N-dimensional packed arrays (**ND-arrays**); it also adds 4 new type markers - -`[u] - uint16`, `[m] - uint32`, `[M] - uint64` and `[h] - float16` - to unambiguously map common binary numeric types; -furthermore, it uses little-endian (LE) to store all numerics instead of big-endian (BE) as in UBJSON to avoid -unnecessary conversions on commonly available platforms. - -Compared to other binary JSON-like formats such as MessagePack and CBOR, both BJData and UBJSON demonstrate a rare -combination of being both binary and **quasi-human-readable**. This is because all semantic elements in BJData and -UBJSON, including the data-type markers and name/string types are directly human-readable. Data stored in the -BJData/UBJSON format are not only compact in size, fast to read/write, but also can be directly searched or read using -simple processing. - -!!! abstract "References" - - - [BJData Specification](https://neurojson.org/bjdata/draft2) - -## Serialization - -The library uses the following mapping from JSON values types to BJData types according to the BJData specification: - -| JSON value type | value/range | BJData type | marker | -|-----------------|-------------------------------------------|----------------|--------| -| null | `null` | null | `Z` | -| boolean | `true` | true | `T` | -| boolean | `false` | false | `F` | -| number_integer | -9223372036854775808..-2147483649 | int64 | `L` | -| number_integer | -2147483648..-32769 | int32 | `l` | -| number_integer | -32768..-129 | int16 | `I` | -| number_integer | -128..127 | int8 | `i` | -| number_integer | 128..255 | uint8 | `U` | -| number_integer | 256..32767 | int16 | `I` | -| number_integer | 32768..65535 | uint16 | `u` | -| number_integer | 65536..2147483647 | int32 | `l` | -| number_integer | 2147483648..4294967295 | uint32 | `m` | -| number_integer | 4294967296..9223372036854775807 | int64 | `L` | -| number_integer | 9223372036854775808..18446744073709551615 | uint64 | `M` | -| number_unsigned | 0..127 | int8 | `i` | -| number_unsigned | 128..255 | uint8 | `U` | -| number_unsigned | 256..32767 | int16 | `I` | -| number_unsigned | 32768..65535 | uint16 | `u` | -| number_unsigned | 65536..2147483647 | int32 | `l` | -| number_unsigned | 2147483648..4294967295 | uint32 | `m` | -| number_unsigned | 4294967296..9223372036854775807 | int64 | `L` | -| number_unsigned | 9223372036854775808..18446744073709551615 | uint64 | `M` | -| number_float | *any value* | float64 | `D` | -| string | *with shortest length indicator* | string | `S` | -| array | *see notes on optimized format/ND-array* | array | `[` | -| object | *see notes on optimized format* | map | `{` | - -!!! success "Complete mapping" - - The mapping is **complete** in the sense that any JSON value type can be converted to a BJData value. - - Any BJData output created by `to_bjdata` can be successfully parsed by `from_bjdata`. - -!!! warning "Size constraints" - - The following values can **not** be converted to a BJData value: - - - strings with more than 18446744073709551615 bytes, i.e., $2^{64}-1$ bytes (theoretical) - -!!! info "Unused BJData markers" - - The following markers are not used in the conversion: - - - `Z`: no-op values are not created. - - `C`: single-byte strings are serialized with `S` markers. - -!!! info "NaN/infinity handling" - - If NaN or Infinity are stored inside a JSON number, they are serialized properly. This behavior differs from the - `dump()` function which serializes NaN or Infinity to `#!json null`. - -!!! info "Endianness" - - A breaking difference between BJData and UBJSON is the endianness of numerical values. In BJData, all numerical data - types (integers `UiuImlML` and floating-point values `hdD`) are stored in the little-endian (LE) byte order as - opposed to big-endian as used by UBJSON. Adopting LE to store numeric records avoids unnecessary byte swapping on - most modern computers where LE is used as the default byte order. - -!!! info "Optimized formats" - - Optimized formats for containers are supported via two parameters of - [`to_bjdata`](../../api/basic_json/to_bjdata.md): - - - Parameter `use_size` adds size information to the beginning of a container and removes the closing marker. - - Parameter `use_type` further checks whether all elements of a container have the same type and adds the type - marker to the beginning of the container. The `use_type` parameter must only be used together with - `use_size = true`. - - Note that `use_size = true` alone may result in larger representations - the benefit of this parameter is that the - receiving side is immediately informed of the number of elements in the container. - -!!! info "ND-array optimized format" - - BJData extends UBJSON's optimized array **size** marker to support ND-arrays of uniform numerical data types - (referred to as *packed arrays*). For example, the 2-D `uint8` integer array `[[1,2],[3,4],[5,6]]`, stored as nested - optimized array in UBJSON `[ [$U#i2 1 2 [$U#i2 3 4 [$U#i2 5 6 ]`, can be further compressed in BJData to - `[$U#[$i#i2 2 3 1 2 3 4 5 6` or `[$U#[i2 i3] 1 2 3 4 5 6`. - - To maintain type and size information, ND-arrays are converted to JSON objects following the **annotated array - format** (defined in the [JData specification (Draft 3)][JDataAAFmt]), when parsed using - [`from_bjdata`](../../api/basic_json/from_bjdata.md). For example, the above 2-D `uint8` array can be parsed and - accessed as - - ```json - { - "_ArrayType_": "uint8", - "_ArraySize_": [2,3], - "_ArrayData_": [1,2,3,4,5,6] - } - ``` - - Likewise, when a JSON object in the above form is serialzed using - [`to_bjdata`](../../api/basic_json/to_bjdata.md), it is automatically converted into a compact BJData ND-array. The - only exception is, that when the 1-dimensional vector stored in `"_ArraySize_"` contains a single integer or two - integers with one being 1, a regular 1-D optimized array is generated. - - The current version of this library does not yet support automatic detection of and conversion from a nested JSON - array input to a BJData ND-array. - - [JDataAAFmt]: https://github.com/NeuroJSON/jdata/blob/master/JData_specification.md#annotated-storage-of-n-d-arrays) - -!!! info "Restrictions in optimized data types for arrays and objects" - - Due to diminished space saving, hampered readability, and increased security risks, in BJData, the allowed data - types following the `$` marker in an optimized array and object container are restricted to - **non-zero-fixed-length** data types. Therefore, the valid optimized type markers can only be one of `UiuImlMLhdDC`. - This also means other variable (`[{SH`) or zero-length types (`TFN`) can not be used in an optimized array or object - in BJData. - -!!! info "Binary values" - - If the JSON data contains the binary type, the value stored is a list of integers, as suggested by the BJData - documentation. In particular, this means that the serialization and the deserialization of JSON containing binary - values into BJData and back will result in a different JSON object. - -??? example - - ```cpp - --8<-- "examples/to_bjdata.cpp" - ``` - - Output: - - ```c - --8<-- "examples/to_bjdata.output" - ``` - -## Deserialization - -The library maps BJData types to JSON value types as follows: - -| BJData type | JSON value type | marker | -|-------------|-----------------------------------------|--------| -| no-op | *no value, next value is read* | `N` | -| null | `null` | `Z` | -| false | `false` | `F` | -| true | `true` | `T` | -| float16 | number_float | `h` | -| float32 | number_float | `d` | -| float64 | number_float | `D` | -| uint8 | number_unsigned | `U` | -| int8 | number_integer | `i` | -| uint16 | number_unsigned | `u` | -| int16 | number_integer | `I` | -| uint32 | number_unsigned | `m` | -| int32 | number_integer | `l` | -| uint64 | number_unsigned | `M` | -| int64 | number_integer | `L` | -| string | string | `S` | -| char | string | `C` | -| array | array (optimized values are supported) | `[` | -| ND-array | object (in JData annotated array format)|`[$.#[.`| -| object | object (optimized values are supported) | `{` | - -!!! success "Complete mapping" - - The mapping is **complete** in the sense that any BJData value can be converted to a JSON value. - -??? example - - ```cpp - --8<-- "examples/from_bjdata.cpp" - ``` - - Output: - - ```json - --8<-- "examples/from_bjdata.output" - ``` diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/binary_formats/bson.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/binary_formats/bson.md deleted file mode 100644 index f3b8cf1..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/binary_formats/bson.md +++ /dev/null @@ -1,96 +0,0 @@ -# BSON - -BSON, short for Binary JSON, is a binary-encoded serialization of JSON-like documents. Like JSON, BSON supports the -embedding of documents and arrays within other documents and arrays. BSON also contains extensions that allow -representation of data types that are not part of the JSON spec. For example, BSON has a Date type and a BinData type. - -!!! abstract "References" - - - [BSON Website](http://bsonspec.org) - the main source on BSON - - [BSON Specification](http://bsonspec.org/spec.html) - the specification - - -## Serialization - -The library uses the following mapping from JSON values types to BSON types: - -| JSON value type | value/range | BSON type | marker | -|-----------------|-------------------------------------------|-----------|--------| -| null | `null` | null | 0x0A | -| boolean | `true`, `false` | boolean | 0x08 | -| number_integer | -9223372036854775808..-2147483649 | int64 | 0x12 | -| number_integer | -2147483648..2147483647 | int32 | 0x10 | -| number_integer | 2147483648..9223372036854775807 | int64 | 0x12 | -| number_unsigned | 0..2147483647 | int32 | 0x10 | -| number_unsigned | 2147483648..9223372036854775807 | int64 | 0x12 | -| number_unsigned | 9223372036854775808..18446744073709551615 | -- | -- | -| number_float | *any value* | double | 0x01 | -| string | *any value* | string | 0x02 | -| array | *any value* | document | 0x04 | -| object | *any value* | document | 0x03 | -| binary | *any value* | binary | 0x05 | - -!!! warning "Incomplete mapping" - - The mapping is **incomplete**, since only JSON-objects (and things - contained therein) can be serialized to BSON. - Also, integers larger than 9223372036854775807 cannot be serialized to BSON, - and the keys may not contain U+0000, since they are serialized a - zero-terminated c-strings. - -??? example - - ```cpp - --8<-- "examples/to_bson.cpp" - ``` - - Output: - - ```c - --8<-- "examples/to_bson.output" - ``` - - -## Deserialization - -The library maps BSON record types to JSON value types as follows: - -| BSON type | BSON marker byte | JSON value type | -|-----------------------|------------------|-----------------| -| double | 0x01 | number_float | -| string | 0x02 | string | -| document | 0x03 | object | -| array | 0x04 | array | -| binary | 0x05 | binary | -| undefined | 0x06 | *unsupported* | -| ObjectId | 0x07 | *unsupported* | -| boolean | 0x08 | boolean | -| UTC Date-Time | 0x09 | *unsupported* | -| null | 0x0A | null | -| Regular Expr. | 0x0B | *unsupported* | -| DB Pointer | 0x0C | *unsupported* | -| JavaScript Code | 0x0D | *unsupported* | -| Symbol | 0x0E | *unsupported* | -| JavaScript Code | 0x0F | *unsupported* | -| int32 | 0x10 | number_integer | -| Timestamp | 0x11 | *unsupported* | -| 128-bit decimal float | 0x13 | *unsupported* | -| Max Key | 0x7F | *unsupported* | -| Min Key | 0xFF | *unsupported* | - -!!! warning "Incomplete mapping" - - The mapping is **incomplete**. The unsupported mappings are indicated in the table above. - - -??? example - - ```cpp - --8<-- "examples/from_bson.cpp" - ``` - - Output: - - ```json - --8<-- "examples/from_bson.output" - ``` diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/binary_formats/cbor.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/binary_formats/cbor.md deleted file mode 100644 index 2d0a1da..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/binary_formats/cbor.md +++ /dev/null @@ -1,181 +0,0 @@ -# CBOR - -The Concise Binary Object Representation (CBOR) is a data format whose design goals include the possibility of extremely -small code size, fairly small message size, and extensibility without the need for version negotiation. - -!!! abstract "References" - - - [CBOR Website](http://cbor.io) - the main source on CBOR - - [CBOR Playground](http://cbor.me) - an interactive webpage to translate between JSON and CBOR - - [RFC 7049](https://tools.ietf.org/html/rfc7049) - the CBOR specification - -## Serialization - -The library uses the following mapping from JSON values types to CBOR types according to the CBOR specification -([RFC 7049](https://www.rfc-editor.org/rfc/rfc7049.html)): - -| JSON value type | value/range | CBOR type | first byte | -|-----------------|--------------------------------------------|-----------------------------------|------------| -| null | `null` | Null | 0xF6 | -| boolean | `true` | True | 0xF5 | -| boolean | `false` | False | 0xF4 | -| number_integer | -9223372036854775808..-2147483649 | Negative integer (8 bytes follow) | 0x3B | -| number_integer | -2147483648..-32769 | Negative integer (4 bytes follow) | 0x3A | -| number_integer | -32768..-129 | Negative integer (2 bytes follow) | 0x39 | -| number_integer | -128..-25 | Negative integer (1 byte follow) | 0x38 | -| number_integer | -24..-1 | Negative integer | 0x20..0x37 | -| number_integer | 0..23 | Integer | 0x00..0x17 | -| number_integer | 24..255 | Unsigned integer (1 byte follow) | 0x18 | -| number_integer | 256..65535 | Unsigned integer (2 bytes follow) | 0x19 | -| number_integer | 65536..4294967295 | Unsigned integer (4 bytes follow) | 0x1A | -| number_integer | 4294967296..18446744073709551615 | Unsigned integer (8 bytes follow) | 0x1B | -| number_unsigned | 0..23 | Integer | 0x00..0x17 | -| number_unsigned | 24..255 | Unsigned integer (1 byte follow) | 0x18 | -| number_unsigned | 256..65535 | Unsigned integer (2 bytes follow) | 0x19 | -| number_unsigned | 65536..4294967295 | Unsigned integer (4 bytes follow) | 0x1A | -| number_unsigned | 4294967296..18446744073709551615 | Unsigned integer (8 bytes follow) | 0x1B | -| number_float | *any value representable by a float* | Single-Precision Float | 0xFA | -| number_float | *any value NOT representable by a float* | Double-Precision Float | 0xFB | -| string | *length*: 0..23 | UTF-8 string | 0x60..0x77 | -| string | *length*: 23..255 | UTF-8 string (1 byte follow) | 0x78 | -| string | *length*: 256..65535 | UTF-8 string (2 bytes follow) | 0x79 | -| string | *length*: 65536..4294967295 | UTF-8 string (4 bytes follow) | 0x7A | -| string | *length*: 4294967296..18446744073709551615 | UTF-8 string (8 bytes follow) | 0x7B | -| array | *size*: 0..23 | array | 0x80..0x97 | -| array | *size*: 23..255 | array (1 byte follow) | 0x98 | -| array | *size*: 256..65535 | array (2 bytes follow) | 0x99 | -| array | *size*: 65536..4294967295 | array (4 bytes follow) | 0x9A | -| array | *size*: 4294967296..18446744073709551615 | array (8 bytes follow) | 0x9B | -| object | *size*: 0..23 | map | 0xA0..0xB7 | -| object | *size*: 23..255 | map (1 byte follow) | 0xB8 | -| object | *size*: 256..65535 | map (2 bytes follow) | 0xB9 | -| object | *size*: 65536..4294967295 | map (4 bytes follow) | 0xBA | -| object | *size*: 4294967296..18446744073709551615 | map (8 bytes follow) | 0xBB | -| binary | *size*: 0..23 | byte string | 0x40..0x57 | -| binary | *size*: 23..255 | byte string (1 byte follow) | 0x58 | -| binary | *size*: 256..65535 | byte string (2 bytes follow) | 0x59 | -| binary | *size*: 65536..4294967295 | byte string (4 bytes follow) | 0x5A | -| binary | *size*: 4294967296..18446744073709551615 | byte string (8 bytes follow) | 0x5B | - -Binary values with subtype are mapped to tagged values (0xD8..0xDB) depending on the subtype, followed by a byte string, -see "binary" cells in the table above. - -!!! success "Complete mapping" - - The mapping is **complete** in the sense that any JSON value type can be converted to a CBOR value. - -!!! info "NaN/infinity handling" - - If NaN or Infinity are stored inside a JSON number, they are serialized properly. This behavior differs from the normal JSON serialization which serializes NaN or Infinity to `null`. - -!!! info "Unused CBOR types" - - The following CBOR types are not used in the conversion: - - - UTF-8 strings terminated by "break" (0x7F) - - arrays terminated by "break" (0x9F) - - maps terminated by "break" (0xBF) - - byte strings terminated by "break" (0x5F) - - date/time (0xC0..0xC1) - - bignum (0xC2..0xC3) - - decimal fraction (0xC4) - - bigfloat (0xC5) - - expected conversions (0xD5..0xD7) - - simple values (0xE0..0xF3, 0xF8) - - undefined (0xF7) - - half-precision floats (0xF9) - - break (0xFF) - -!!! info "Tagged items" - - Binary subtypes will be serialized as tagged items. See [binary values](../binary_values.md#cbor) for an example. - -??? example - - ```cpp - --8<-- "examples/to_cbor.cpp" - ``` - - Output: - - ```c - --8<-- "examples/to_cbor.output" - ``` - -## Deserialization - -The library maps CBOR types to JSON value types as follows: - -| CBOR type | JSON value type | first byte | -|------------------------|-----------------|------------| -| Integer | number_unsigned | 0x00..0x17 | -| Unsigned integer | number_unsigned | 0x18 | -| Unsigned integer | number_unsigned | 0x19 | -| Unsigned integer | number_unsigned | 0x1A | -| Unsigned integer | number_unsigned | 0x1B | -| Negative integer | number_integer | 0x20..0x37 | -| Negative integer | number_integer | 0x38 | -| Negative integer | number_integer | 0x39 | -| Negative integer | number_integer | 0x3A | -| Negative integer | number_integer | 0x3B | -| Byte string | binary | 0x40..0x57 | -| Byte string | binary | 0x58 | -| Byte string | binary | 0x59 | -| Byte string | binary | 0x5A | -| Byte string | binary | 0x5B | -| UTF-8 string | string | 0x60..0x77 | -| UTF-8 string | string | 0x78 | -| UTF-8 string | string | 0x79 | -| UTF-8 string | string | 0x7A | -| UTF-8 string | string | 0x7B | -| UTF-8 string | string | 0x7F | -| array | array | 0x80..0x97 | -| array | array | 0x98 | -| array | array | 0x99 | -| array | array | 0x9A | -| array | array | 0x9B | -| array | array | 0x9F | -| map | object | 0xA0..0xB7 | -| map | object | 0xB8 | -| map | object | 0xB9 | -| map | object | 0xBA | -| map | object | 0xBB | -| map | object | 0xBF | -| False | `false` | 0xF4 | -| True | `true` | 0xF5 | -| Null | `null` | 0xF6 | -| Half-Precision Float | number_float | 0xF9 | -| Single-Precision Float | number_float | 0xFA | -| Double-Precision Float | number_float | 0xFB | - -!!! warning "Incomplete mapping" - - The mapping is **incomplete** in the sense that not all CBOR types can be converted to a JSON value. The following CBOR types are not supported and will yield parse errors: - - - date/time (0xC0..0xC1) - - bignum (0xC2..0xC3) - - decimal fraction (0xC4) - - bigfloat (0xC5) - - expected conversions (0xD5..0xD7) - - simple values (0xE0..0xF3, 0xF8) - - undefined (0xF7) - -!!! warning "Object keys" - - CBOR allows map keys of any type, whereas JSON only allows strings as keys in object values. Therefore, CBOR maps with keys other than UTF-8 strings are rejected. - -!!! warning "Tagged items" - - Tagged items will throw a parse error by default. They can be ignored by passing `cbor_tag_handler_t::ignore` to function `from_cbor`. They can be stored by passing `cbor_tag_handler_t::store` to function `from_cbor`. - -??? example - - ```cpp - --8<-- "examples/from_cbor.cpp" - ``` - - Output: - - ```json - --8<-- "examples/from_cbor.output" - ``` diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/binary_formats/index.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/binary_formats/index.md deleted file mode 100644 index e74290b..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/binary_formats/index.md +++ /dev/null @@ -1,52 +0,0 @@ -# Binary Formats - -Though JSON is a ubiquitous data format, it is not a very compact format suitable for data exchange, for instance over -a network. Hence, the library supports - -- [BJData](bjdata.md) (Binary JData), -- [BSON](bson.md) (Binary JSON), -- [CBOR](cbor.md) (Concise Binary Object Representation), -- [MessagePack](messagepack.md), and -- [UBJSON](ubjson.md) (Universal Binary JSON) - -to efficiently encode JSON values to byte vectors and to decode such vectors. - -## Comparison - -### Completeness - -| Format | Serialization | Deserialization | -|-------------|-----------------------------------------------|----------------------------------------------| -| BJData | complete | complete | -| BSON | incomplete: top-level value must be an object | incomplete, but all JSON types are supported | -| CBOR | complete | incomplete, but all JSON types are supported | -| MessagePack | complete | complete | -| UBJSON | complete | complete | - -### Binary values - -| Format | Binary values | Binary subtypes | -|-------------|---------------|-----------------| -| BJData | not supported | not supported | -| BSON | supported | supported | -| CBOR | supported | supported | -| MessagePack | supported | supported | -| UBJSON | not supported | not supported | - -See [binary values](../binary_values.md) for more information. - -### Sizes - -| Format | canada.json | twitter.json | citm_catalog.json | jeopardy.json | -|--------------------|-------------|--------------|-------------------|---------------| -| BJData | 53.2 % | 91.1 % | 78.1 % | 96.6 % | -| BJData (size) | 58.6 % | 92.1 % | 86.7 % | 97.4 % | -| BJData (size+tyoe) | 58.6 % | 92.1 % | 86.5 % | 97.4 % | -| BSON | 85.8 % | 95.2 % | 95.8 % | 106.7 % | -| CBOR | 50.5 % | 86.3 % | 68.4 % | 88.0 % | -| MessagePack | 50.5 % | 86.0 % | 68.5 % | 87.9 % | -| UBJSON | 53.2 % | 91.3 % | 78.2 % | 96.6 % | -| UBJSON (size) | 58.6 % | 92.3 % | 86.8 % | 97.4 % | -| UBJSON (size+type) | 55.9 % | 92.3 % | 85.0 % | 95.0 % | - -Sizes compared to minified JSON value. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/binary_formats/messagepack.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/binary_formats/messagepack.md deleted file mode 100644 index b2f69f1..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/binary_formats/messagepack.md +++ /dev/null @@ -1,143 +0,0 @@ -# MessagePack - -MessagePack is an efficient binary serialization format. It lets you exchange data among multiple languages like JSON. -But it's faster and smaller. Small integers are encoded into a single byte, and typical short strings require only one -extra byte in addition to the strings themselves. - -!!! abstract "References" - - - [MessagePack website](https://msgpack.org) - - [MessagePack specification](https://github.com/msgpack/msgpack/blob/master/spec.md) - -## Serialization - -The library uses the following mapping from JSON values types to MessagePack types according to the MessagePack -specification: - -| JSON value type | value/range | MessagePack type | first byte | -|-----------------|------------------------------------------|------------------|------------| -| null | `null` | nil | 0xC0 | -| boolean | `true` | true | 0xC3 | -| boolean | `false` | false | 0xC2 | -| number_integer | -9223372036854775808..-2147483649 | int64 | 0xD3 | -| number_integer | -2147483648..-32769 | int32 | 0xD2 | -| number_integer | -32768..-129 | int16 | 0xD1 | -| number_integer | -128..-33 | int8 | 0xD0 | -| number_integer | -32..-1 | negative fixint | 0xE0..0xFF | -| number_integer | 0..127 | positive fixint | 0x00..0x7F | -| number_integer | 128..255 | uint 8 | 0xCC | -| number_integer | 256..65535 | uint 16 | 0xCD | -| number_integer | 65536..4294967295 | uint 32 | 0xCE | -| number_integer | 4294967296..18446744073709551615 | uint 64 | 0xCF | -| number_unsigned | 0..127 | positive fixint | 0x00..0x7F | -| number_unsigned | 128..255 | uint 8 | 0xCC | -| number_unsigned | 256..65535 | uint 16 | 0xCD | -| number_unsigned | 65536..4294967295 | uint 32 | 0xCE | -| number_unsigned | 4294967296..18446744073709551615 | uint 64 | 0xCF | -| number_float | *any value representable by a float* | float 32 | 0xCA | -| number_float | *any value NOT representable by a float* | float 64 | 0xCB | -| string | *length*: 0..31 | fixstr | 0xA0..0xBF | -| string | *length*: 32..255 | str 8 | 0xD9 | -| string | *length*: 256..65535 | str 16 | 0xDA | -| string | *length*: 65536..4294967295 | str 32 | 0xDB | -| array | *size*: 0..15 | fixarray | 0x90..0x9F | -| array | *size*: 16..65535 | array 16 | 0xDC | -| array | *size*: 65536..4294967295 | array 32 | 0xDD | -| object | *size*: 0..15 | fix map | 0x80..0x8F | -| object | *size*: 16..65535 | map 16 | 0xDE | -| object | *size*: 65536..4294967295 | map 32 | 0xDF | -| binary | *size*: 0..255 | bin 8 | 0xC4 | -| binary | *size*: 256..65535 | bin 16 | 0xC5 | -| binary | *size*: 65536..4294967295 | bin 32 | 0xC6 | - -!!! success "Complete mapping" - - The mapping is **complete** in the sense that any JSON value type can be converted to a MessagePack value. - - Any MessagePack output created by `to_msgpack` can be successfully parsed by `from_msgpack`. - -!!! warning "Size constraints" - - The following values can **not** be converted to a MessagePack value: - - - strings with more than 4294967295 bytes - - byte strings with more than 4294967295 bytes - - arrays with more than 4294967295 elements - - objects with more than 4294967295 elements - -!!! info "NaN/infinity handling" - - If NaN or Infinity are stored inside a JSON number, they are serialized properly in contrast to the - [dump](../../api/basic_json/dump.md) function which serializes NaN or Infinity to `null`. - -??? example - - ```cpp - --8<-- "examples/to_msgpack.cpp" - ``` - - Output: - - ```c - --8<-- "examples/to_msgpack.output" - ``` - -## Deserialization - -The library maps MessagePack types to JSON value types as follows: - -| MessagePack type | JSON value type | first byte | -|------------------|-----------------|------------| -| positive fixint | number_unsigned | 0x00..0x7F | -| fixmap | object | 0x80..0x8F | -| fixarray | array | 0x90..0x9F | -| fixstr | string | 0xA0..0xBF | -| nil | `null` | 0xC0 | -| false | `false` | 0xC2 | -| true | `true` | 0xC3 | -| float 32 | number_float | 0xCA | -| float 64 | number_float | 0xCB | -| uint 8 | number_unsigned | 0xCC | -| uint 16 | number_unsigned | 0xCD | -| uint 32 | number_unsigned | 0xCE | -| uint 64 | number_unsigned | 0xCF | -| int 8 | number_integer | 0xD0 | -| int 16 | number_integer | 0xD1 | -| int 32 | number_integer | 0xD2 | -| int 64 | number_integer | 0xD3 | -| str 8 | string | 0xD9 | -| str 16 | string | 0xDA | -| str 32 | string | 0xDB | -| array 16 | array | 0xDC | -| array 32 | array | 0xDD | -| map 16 | object | 0xDE | -| map 32 | object | 0xDF | -| bin 8 | binary | 0xC4 | -| bin 16 | binary | 0xC5 | -| bin 32 | binary | 0xC6 | -| ext 8 | binary | 0xC7 | -| ext 16 | binary | 0xC8 | -| ext 32 | binary | 0xC9 | -| fixext 1 | binary | 0xD4 | -| fixext 2 | binary | 0xD5 | -| fixext 4 | binary | 0xD6 | -| fixext 8 | binary | 0xD7 | -| fixext 16 | binary | 0xD8 | -| negative fixint | number_integer | 0xE0-0xFF | - -!!! info - - Any MessagePack output created by `to_msgpack` can be successfully parsed by `from_msgpack`. - - -??? example - - ```cpp - --8<-- "examples/from_msgpack.cpp" - ``` - - Output: - - ```json - --8<-- "examples/from_msgpack.output" - ``` diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/binary_formats/ubjson.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/binary_formats/ubjson.md deleted file mode 100644 index 76956d6..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/binary_formats/ubjson.md +++ /dev/null @@ -1,126 +0,0 @@ -# UBJSON - -Universal Binary JSON (UBJSON) is a binary form directly imitating JSON, but requiring fewer bytes of data. It aims to -achieve the generality of JSON, combined with being much easier to process than JSON. - -!!! abstract "References" - - - [UBJSON Website](http://ubjson.org) - -## Serialization - -The library uses the following mapping from JSON values types to UBJSON types according to the UBJSON specification: - -| JSON value type | value/range | UBJSON type | marker | -|-----------------|-----------------------------------|----------------|--------| -| null | `null` | null | `Z` | -| boolean | `true` | true | `T` | -| boolean | `false` | false | `F` | -| number_integer | -9223372036854775808..-2147483649 | int64 | `L` | -| number_integer | -2147483648..-32769 | int32 | `l` | -| number_integer | -32768..-129 | int16 | `I` | -| number_integer | -128..127 | int8 | `i` | -| number_integer | 128..255 | uint8 | `U` | -| number_integer | 256..32767 | int16 | `I` | -| number_integer | 32768..2147483647 | int32 | `l` | -| number_integer | 2147483648..9223372036854775807 | int64 | `L` | -| number_unsigned | 0..127 | int8 | `i` | -| number_unsigned | 128..255 | uint8 | `U` | -| number_unsigned | 256..32767 | int16 | `I` | -| number_unsigned | 32768..2147483647 | int32 | `l` | -| number_unsigned | 2147483648..9223372036854775807 | int64 | `L` | -| number_unsigned | 2147483649..18446744073709551615 | high-precision | `H` | -| number_float | *any value* | float64 | `D` | -| string | *with shortest length indicator* | string | `S` | -| array | *see notes on optimized format* | array | `[` | -| object | *see notes on optimized format* | map | `{` | - -!!! success "Complete mapping" - - The mapping is **complete** in the sense that any JSON value type can be converted to a UBJSON value. - - Any UBJSON output created by `to_ubjson` can be successfully parsed by `from_ubjson`. - -!!! warning "Size constraints" - - The following values can **not** be converted to a UBJSON value: - - - strings with more than 9223372036854775807 bytes (theoretical) - -!!! info "Unused UBJSON markers" - - The following markers are not used in the conversion: - - - `Z`: no-op values are not created. - - `C`: single-byte strings are serialized with `S` markers. - -!!! info "NaN/infinity handling" - - If NaN or Infinity are stored inside a JSON number, they are serialized properly. This behavior differs from the - `dump()` function which serializes NaN or Infinity to `null`. - -!!! info "Optimized formats" - - The optimized formats for containers are supported: Parameter `use_size` adds size information to the beginning of a - container and removes the closing marker. Parameter `use_type` further checks whether all elements of a container - have the same type and adds the type marker to the beginning of the container. The `use_type` parameter must only be - used together with `use_size = true`. - - Note that `use_size = true` alone may result in larger representations - the benefit of this parameter is that the - receiving side is immediately informed on the number of elements of the container. - -!!! info "Binary values" - - If the JSON data contains the binary type, the value stored is a list of integers, as suggested by the UBJSON - documentation. In particular, this means that serialization and the deserialization of a JSON containing binary - values into UBJSON and back will result in a different JSON object. - -??? example - - ```cpp - --8<-- "examples/to_ubjson.cpp" - ``` - - Output: - - ```c - --8<-- "examples/to_ubjson.output" - ``` - -## Deserialization - -The library maps UBJSON types to JSON value types as follows: - -| UBJSON type | JSON value type | marker | -|-------------|-----------------------------------------|--------| -| no-op | *no value, next value is read* | `N` | -| null | `null` | `Z` | -| false | `false` | `F` | -| true | `true` | `T` | -| float32 | number_float | `d` | -| float64 | number_float | `D` | -| uint8 | number_unsigned | `U` | -| int8 | number_integer | `i` | -| int16 | number_integer | `I` | -| int32 | number_integer | `l` | -| int64 | number_integer | `L` | -| string | string | `S` | -| char | string | `C` | -| array | array (optimized values are supported) | `[` | -| object | object (optimized values are supported) | `{` | - -!!! success "Complete mapping" - - The mapping is **complete** in the sense that any UBJSON value can be converted to a JSON value. - -??? example - - ```cpp - --8<-- "examples/from_ubjson.cpp" - ``` - - Output: - - ```json - --8<-- "examples/from_ubjson.output" - ``` diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/binary_values.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/binary_values.md deleted file mode 100644 index 5ad6433..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/binary_values.md +++ /dev/null @@ -1,372 +0,0 @@ -# Binary Values - -The library implements several [binary formats](binary_formats/index.md) that encode JSON in an efficient way. Most of -these formats support binary values; that is, values that have semantics define outside the library and only define a -sequence of bytes to be stored. - -JSON itself does not have a binary value. As such, binary values are an extension that this library implements to store -values received by a binary format. Binary values are never created by the JSON parser, and are only part of a -serialized JSON text if they have been created manually or via a binary format. - -## API for binary values - -```plantuml -class json::binary_t { - -- setters -- - +void set_subtype(std::uint64_t subtype) - +void clear_subtype() - -- getters -- - +std::uint64_t subtype() const - +bool has_subtype() const -} - -"std::vector" <|-- json::binary_t -``` - -By default, binary values are stored as `std::vector`. This type can be changed by providing a template -parameter to the `basic_json` type. To store binary subtypes, the storage type is extended and exposed as -`json::binary_t`: - -```cpp -auto binary = json::binary_t({0xCA, 0xFE, 0xBA, 0xBE}); -auto binary_with_subtype = json::binary_t({0xCA, 0xFE, 0xBA, 0xBE}, 42); -``` - -There are several convenience functions to check and set the subtype: - -```cpp -binary.has_subtype(); // returns false -binary_with_subtype.has_subtype(); // returns true - -binary_with_subtype.clear_subtype(); -binary_with_subtype.has_subtype(); // returns true - -binary_with_subtype.set_subtype(42); -binary.set_subtype(23); - -binary.subtype(); // returns 23 -``` - -As `json::binary_t` is subclassing `std::vector`, all member functions are available: - -```cpp -binary.size(); // returns 4 -binary[1]; // returns 0xFE -``` - -JSON values can be constructed from `json::binary_t`: - -```cpp -json j = binary; -``` - -Binary values are primitive values just like numbers or strings: - -```cpp -j.is_binary(); // returns true -j.is_primitive(); // returns true -``` - -Given a binary JSON value, the `binary_t` can be accessed by reference as via `get_binary()`: - -```cpp -j.get_binary().has_subtype(); // returns true -j.get_binary().size(); // returns 4 -``` - -For convenience, binary JSON values can be constructed via `json::binary`: - -```cpp -auto j2 = json::binary({0xCA, 0xFE, 0xBA, 0xBE}, 23); -auto j3 = json::binary({0xCA, 0xFE, 0xBA, 0xBE}); - -j2 == j; // returns true -j3.get_binary().has_subtype(); // returns false -j3.get_binary().subtype(); // returns std::uint64_t(-1) as j3 has no subtype -``` - - - -## Serialization - -Binary values are serialized differently according to the formats. - -### JSON - -JSON does not have a binary type, and this library does not introduce a new type as this would break conformance. -Instead, binary values are serialized as an object with two keys: `bytes` holds an array of integers, and `subtype` -is an integer or `null`. - -??? example - - Code: - - ```cpp - // create a binary value of subtype 42 - json j; - j["binary"] = json::binary({0xCA, 0xFE, 0xBA, 0xBE}, 42); - - // serialize to standard output - std::cout << j.dump(2) << std::endl; - ``` - - Output: - - ```json - { - "binary": { - "bytes": [202, 254, 186, 190], - "subtype": 42 - } - } - ``` - -!!! warning "No roundtrip for binary values" - - The JSON parser will not parse the objects generated by binary values back to binary values. This is by design to - remain standards compliant. Serializing binary values to JSON is only implemented for debugging purposes. - -### BJData - -[BJData](binary_formats/bjdata.md) neither supports binary values nor subtypes, and proposes to serialize binary values -as array of uint8 values. This translation is implemented by the library. - -??? example - - Code: - - ```cpp - // create a binary value of subtype 42 (will be ignored in BJData) - json j; - j["binary"] = json::binary({0xCA, 0xFE, 0xBA, 0xBE}, 42); - - // convert to BJData - auto v = json::to_bjdata(j); - ``` - - `v` is a `std::vector` with the following 20 elements: - - ```c - 0x7B // '{' - 0x69 0x06 // i 6 (length of the key) - 0x62 0x69 0x6E 0x61 0x72 0x79 // "binary" - 0x5B // '[' - 0x55 0xCA 0x55 0xFE 0x55 0xBA 0x55 0xBE // content (each byte prefixed with 'U') - 0x5D // ']' - 0x7D // '}' - ``` - - The following code uses the type and size optimization for UBJSON: - - ```cpp - // convert to UBJSON using the size and type optimization - auto v = json::to_bjdata(j, true, true); - ``` - - The resulting vector has 22 elements; the optimization is not effective for examples with few values: - - ```c - 0x7B // '{' - 0x23 0x69 0x01 // '#' 'i' type of the array elements: unsigned integers - 0x69 0x06 // i 6 (length of the key) - 0x62 0x69 0x6E 0x61 0x72 0x79 // "binary" - 0x5B // '[' array - 0x24 0x55 // '$' 'U' type of the array elements: unsigned integers - 0x23 0x69 0x04 // '#' i 4 number of array elements - 0xCA 0xFE 0xBA 0xBE // content - ``` - - Note that subtype (42) is **not** serialized and that UBJSON has **no binary type**, and deserializing `v` would - yield the following value: - - ```json - { - "binary": [202, 254, 186, 190] - } - ``` - -### BSON - -[BSON](binary_formats/bson.md) supports binary values and subtypes. If a subtype is given, it is used and added as -unsigned 8-bit integer. If no subtype is given, the generic binary subtype 0x00 is used. - -??? example - - Code: - - ```cpp - // create a binary value of subtype 42 - json j; - j["binary"] = json::binary({0xCA, 0xFE, 0xBA, 0xBE}, 42); - - // convert to BSON - auto v = json::to_bson(j); - ``` - - `v` is a `std::vector` with the following 22 elements: - - ```c - 0x16 0x00 0x00 0x00 // number of bytes in the document - 0x05 // binary value - 0x62 0x69 0x6E 0x61 0x72 0x79 0x00 // key "binary" + null byte - 0x04 0x00 0x00 0x00 // number of bytes - 0x2a // subtype - 0xCA 0xFE 0xBA 0xBE // content - 0x00 // end of the document - ``` - - Note that the serialization preserves the subtype, and deserializing `v` would yield the following value: - - ```json - { - "binary": { - "bytes": [202, 254, 186, 190], - "subtype": 42 - } - } - ``` - -### CBOR - -[CBOR](binary_formats/cbor.md) supports binary values, but no subtypes. Subtypes will be serialized as tags. Any binary -value will be serialized as byte strings. The library will choose the smallest representation using the length of the -byte array. - -??? example - - Code: - - ```cpp - // create a binary value of subtype 42 - json j; - j["binary"] = json::binary({0xCA, 0xFE, 0xBA, 0xBE}, 42); - - // convert to CBOR - auto v = json::to_cbor(j); - ``` - - `v` is a `std::vector` with the following 15 elements: - - ```c - 0xA1 // map(1) - 0x66 // text(6) - 0x62 0x69 0x6E 0x61 0x72 0x79 // "binary" - 0xD8 0x2A // tag(42) - 0x44 // bytes(4) - 0xCA 0xFE 0xBA 0xBE // content - ``` - - Note that the subtype is serialized as tag. However, parsing tagged values yield a parse error unless - `json::cbor_tag_handler_t::ignore` or `json::cbor_tag_handler_t::store` is passed to `json::from_cbor`. - - ```json - { - "binary": { - "bytes": [202, 254, 186, 190], - "subtype": null - } - } - ``` - -### MessagePack - -[MessagePack](binary_formats/messagepack.md) supports binary values and subtypes. If a subtype is given, the ext family -is used. The library will choose the smallest representation among fixext1, fixext2, fixext4, fixext8, ext8, ext16, and -ext32. The subtype is then added as signed 8-bit integer. - -If no subtype is given, the bin family (bin8, bin16, bin32) is used. - -??? example - - Code: - - ```cpp - // create a binary value of subtype 42 - json j; - j["binary"] = json::binary({0xCA, 0xFE, 0xBA, 0xBE}, 42); - - // convert to MessagePack - auto v = json::to_msgpack(j); - ``` - - `v` is a `std::vector` with the following 14 elements: - - ```c - 0x81 // fixmap1 - 0xA6 // fixstr6 - 0x62 0x69 0x6E 0x61 0x72 0x79 // "binary" - 0xD6 // fixext4 - 0x2A // subtype - 0xCA 0xFE 0xBA 0xBE // content - ``` - - Note that the serialization preserves the subtype, and deserializing `v` would yield the following value: - - ```json - { - "binary": { - "bytes": [202, 254, 186, 190], - "subtype": 42 - } - } - ``` - -### UBJSON - -[UBJSON](binary_formats/ubjson.md) neither supports binary values nor subtypes, and proposes to serialize binary values -as array of uint8 values. This translation is implemented by the library. - -??? example - - Code: - - ```cpp - // create a binary value of subtype 42 (will be ignored in UBJSON) - json j; - j["binary"] = json::binary({0xCA, 0xFE, 0xBA, 0xBE}, 42); - - // convert to UBJSON - auto v = json::to_ubjson(j); - ``` - - `v` is a `std::vector` with the following 20 elements: - - ```c - 0x7B // '{' - 0x69 0x06 // i 6 (length of the key) - 0x62 0x69 0x6E 0x61 0x72 0x79 // "binary" - 0x5B // '[' - 0x55 0xCA 0x55 0xFE 0x55 0xBA 0x55 0xBE // content (each byte prefixed with 'U') - 0x5D // ']' - 0x7D // '}' - ``` - - The following code uses the type and size optimization for UBJSON: - - ```cpp - // convert to UBJSON using the size and type optimization - auto v = json::to_ubjson(j, true, true); - ``` - - The resulting vector has 23 elements; the optimization is not effective for examples with few values: - - ```c - 0x7B // '{' - 0x24 // '$' type of the object elements - 0x5B // '[' array - 0x23 0x69 0x01 // '#' i 1 number of object elements - 0x69 0x06 // i 6 (length of the key) - 0x62 0x69 0x6E 0x61 0x72 0x79 // "binary" - 0x24 0x55 // '$' 'U' type of the array elements: unsigned integers - 0x23 0x69 0x04 // '#' i 4 number of array elements - 0xCA 0xFE 0xBA 0xBE // content - ``` - - Note that subtype (42) is **not** serialized and that UBJSON has **no binary type**, and deserializing `v` would - yield the following value: - - ```json - { - "binary": [202, 254, 186, 190] - } - ``` diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/comments.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/comments.md deleted file mode 100644 index 61266d9..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/comments.md +++ /dev/null @@ -1,83 +0,0 @@ -# Comments - -This library does not support comments *by default*. It does so for three reasons: - -1. Comments are not part of the [JSON specification](https://tools.ietf.org/html/rfc8259). You may argue that `//` or `/* */` are allowed in JavaScript, but JSON is not JavaScript. -2. This was not an oversight: Douglas Crockford [wrote on this](https://plus.google.com/118095276221607585885/posts/RK8qyGVaGSr) in May 2012: - - > I removed comments from JSON because I saw people were using them to hold parsing directives, a practice which would have destroyed interoperability. I know that the lack of comments makes some people sad, but it shouldn't. - - > Suppose you are using JSON to keep configuration files, which you would like to annotate. Go ahead and insert all the comments you like. Then pipe it through JSMin before handing it to your JSON parser. - -3. It is dangerous for interoperability if some libraries would add comment support while others don't. Please check [The Harmful Consequences of the Robustness Principle](https://tools.ietf.org/html/draft-iab-protocol-maintenance-01) on this. - -However, you can pass set parameter `ignore_comments` to `#!c true` in the parse function to ignore `//` or `/* */` comments. Comments will then be treated as whitespace. - -!!! example - - Consider the following JSON with comments. - - ```json - { - // update in 2006: removed Pluto - "planets": ["Mercury", "Venus", "Earth", "Mars", - "Jupiter", "Uranus", "Neptune" /*, "Pluto" */] - } - ``` - - When calling `parse` without additional argument, a parse error exception is thrown. If `ignore_comments` is set to `#! true`, the comments are ignored during parsing: - - ```cpp - #include - #include "json.hpp" - - using json = nlohmann::json; - - int main() - { - std::string s = R"( - { - // update in 2006: removed Pluto - "planets": ["Mercury", "Venus", "Earth", "Mars", - "Jupiter", "Uranus", "Neptune" /*, "Pluto" */] - } - )"; - - try - { - json j = json::parse(s); - } - catch (json::exception &e) - { - std::cout << e.what() << std::endl; - } - - json j = json::parse(s, - /* callback */ nullptr, - /* allow exceptions */ true, - /* ignore_comments */ true); - std::cout << j.dump(2) << '\n'; - } - ``` - - Output: - - ``` - [json.exception.parse_error.101] parse error at line 3, column 9: - syntax error while parsing object key - invalid literal; - last read: ' { /'; expected string literal - ``` - - ```json - { - "planets": [ - "Mercury", - "Venus", - "Earth", - "Mars", - "Jupiter", - "Uranus", - "Neptune" - ] - } - ``` diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/element_access/checked_access.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/element_access/checked_access.md deleted file mode 100644 index c4023cc..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/element_access/checked_access.md +++ /dev/null @@ -1,91 +0,0 @@ -# Checked access: at - -## Overview - -The [`at`](../../api/basic_json/at.md) member function performs checked access; that is, it returns a reference to the -desired value if it exists and throws a [`basic_json::out_of_range` exception](../../home/exceptions.md#out-of-range) -otherwise. - -??? example "Read access" - - Consider the following JSON value: - - ```json - { - "name": "Mary Smith", - "age": 42, - "hobbies": ["hiking", "reading"] - } - ``` - - Assume the value is parsed to a `json` variable `j`. - - | expression | value | - |-------------------------------|------------------------------------------------------------------------------| - | `#!cpp j` | `#!json {"name": "Mary Smith", "age": 42, "hobbies": ["hiking", "reading"]}` | - | `#!cpp j.at("name")` | `#!json "Mary Smith"` | - | `#!cpp j.at("age")` | `#!json 42` | - | `#!cpp j.at("hobbies")` | `#!json ["hiking", "reading"]` | - | `#!cpp j.at("hobbies").at(0)` | `#!json "hiking"` | - | `#!cpp j.at("hobbies").at(1)` | `#!json "reading"` | - -The return value is a reference, so it can be modified by the original value. - -??? example "Write access" - - ```cpp - j.at("name") = "John Smith"; - ``` - - This code produces the following JSON value: - - ```json - { - "name": "John Smith", - "age": 42, - "hobbies": ["hiking", "reading"] - } - ``` - -When accessing an invalid index (i.e., an index greater than or equal to the array size) or the passed object key is -non-existing, an exception is thrown. - -??? example "Accessing via invalid index or missing key" - - ```cpp - j.at("hobbies").at(3) = "cooking"; - ``` - - This code produces the following exception: - - ``` - [json.exception.out_of_range.401] array index 3 is out of range - ``` - - When you [extended diagnostic messages](../../home/exceptions.md#extended-diagnostic-messages) are enabled by - defining [`JSON_DIAGNOSTICS`](../../api/macros/json_diagnostics.md), the exception further gives information where - the key or index is missing or out of range. - - ``` - [json.exception.out_of_range.401] (/hobbies) array index 3 is out of range - ``` - -## Notes - - -!!! failure "Exceptions" - - - [`at`](../../api/basic_json/at.md) can only be used with objects (with a string argument) or with arrays (with a - numeric argument). For other types, a [`basic_json::type_error`](../../home/exceptions.md#jsonexceptiontype_error304) - is thrown. - - [`basic_json::out_of_range` exception](../../home/exceptions.md#out-of-range) exceptions are thrown if the - provided key is not found in an object or the provided index is invalid. - -## Summary - -| scenario | non-const value | const value | -|-----------------------------------|------------------------------------------------|------------------------------------------------| -| access to existing object key | reference to existing value is returned | const reference to existing value is returned | -| access to valid array index | reference to existing value is returned | const reference to existing value is returned | -| access to non-existing object key | `basic_json::out_of_range` exception is thrown | `basic_json::out_of_range` exception is thrown | -| access to invalid array index | `basic_json::out_of_range` exception is thrown | `basic_json::out_of_range` exception is thrown | diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/element_access/default_value.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/element_access/default_value.md deleted file mode 100644 index 02b4fea..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/element_access/default_value.md +++ /dev/null @@ -1,32 +0,0 @@ -# Access with default value: value - -## Overview - -In many situations such as configuration files, missing values are not exceptional, but may be treated as if a default value was present. - -??? example - - Consider the following JSON value: - - ```json - { - "logOutput": "result.log", - "append": true - } - ``` - - Assume the value is parsed to a `json` variable `j`. - - | expression | value | - | ---------- | ----- | - | `#!cpp j` | `#!json {"logOutput": "result.log", "append": true}` | - | `#!cpp j.value("logOutput", "logfile.log")` | `#!json "result.log"` | - | `#!cpp j.value("append", true)` | `#!json true` | - | `#!cpp j.value("append", false)` | `#!json true` | - | `#!cpp j.value("logLevel", "verbose")` | `#!json "verbose"` | - -## Note - -!!! failure "Exceptions" - - - `value` can only be used with objects. For other types, a [`basic_json::type_error`](../../home/exceptions.md#jsonexceptiontype_error306) is thrown. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/element_access/index.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/element_access/index.md deleted file mode 100644 index 0b39547..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/element_access/index.md +++ /dev/null @@ -1,9 +0,0 @@ -# Element Access - -There are many ways elements in a JSON value can be accessed: - -- unchecked access via [`operator[]`](unchecked_access.md) -- checked access via [`at`](checked_access.md) -- access with default value via [`value`](default_value.md) -- iterators -- JSON pointers diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/element_access/unchecked_access.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/element_access/unchecked_access.md deleted file mode 100644 index 39f06dc..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/element_access/unchecked_access.md +++ /dev/null @@ -1,112 +0,0 @@ -# Unchecked access: operator[] - -## Overview - -Elements in a JSON object and a JSON array can be accessed via [`operator[]`](../../api/basic_json/operator%5B%5D.md) -similar to a `#!cpp std::map` and a `#!cpp std::vector`, respectively. - -??? example "Read access" - - Consider the following JSON value: - - ```json - { - "name": "Mary Smith", - "age": 42, - "hobbies": ["hiking", "reading"] - } - ``` - - Assume the value is parsed to a `json` variable `j`. - - | expression | value | - |-------------------------|------------------------------------------------------------------------------| - | `#!cpp j` | `#!json {"name": "Mary Smith", "age": 42, "hobbies": ["hiking", "reading"]}` | - | `#!cpp j["name"]` | `#!json "Mary Smith"` | - | `#!cpp j["age"]` | `#!json 42` | - | `#!cpp j["hobbies"]` | `#!json ["hiking", "reading"]` | - | `#!cpp j["hobbies"][0]` | `#!json "hiking"` | - | `#!cpp j["hobbies"][1]` | `#!json "reading"` | - -The return value is a reference, so it can modify the original value. In case the passed object key is non-existing, a -`#!json null` value is inserted which can be immediately be overwritten. - -??? example "Write access" - - ```cpp - j["name"] = "John Smith"; - j["maidenName"] = "Jones"; - ``` - - This code produces the following JSON value: - - ```json - { - "name": "John Smith", - "maidenName": "Jones", - "age": 42, - "hobbies": ["hiking", "reading"] - } - ``` - -When accessing an invalid index (i.e., an index greater than or equal to the array size), the JSON array is resized such -that the passed index is the new maximal index. Intermediate values are filled with `#!json null`. - -??? example "Filling up arrays with `#!json null` values" - - ```cpp - j["hobbies"][0] = "running"; - j["hobbies"][3] = "cooking"; - ``` - - This code produces the following JSON value: - - ```json - { - "name": "John Smith", - "maidenName": "Jones", - "age": 42, - "hobbies": ["running", "reading", null, "cooking"] - } - ``` - -## Notes - -!!! info "Design rationale" - - The library behaves differently to `#!cpp std::vector` and `#!cpp std::map`: - - - `#!cpp std::vector::operator[]` never inserts a new element. - - `#!cpp std::map::operator[]` is not available for const values. - - The type `#!cpp json` wraps all JSON value types. It would be impossible to remove - [`operator[]`](../../api/basic_json/operator%5B%5D.md) for const objects. At the same time, inserting elements for - non-const objects is really convenient as it avoids awkward `insert` calls. To this end, we decided to have an - inserting non-const behavior for both arrays and objects. - -!!! info - - The access is unchecked. In case the passed object key does not exist or the passed array index is invalid, no - exception is thrown. - -!!! danger - - - It is **undefined behavior** to access a const object with a non-existing key. - - It is **undefined behavior** to access a const array with an invalid index. - - In debug mode, an **assertion** will fire in both cases. You can disable assertions by defining the preprocessor - symbol `#!cpp NDEBUG` or redefine the macro [`JSON_ASSERT(x)`](../macros.md#json_assertx). See the documentation - on [runtime assertions](../assertions.md) for more information. - -!!! failure "Exceptions" - - `operator[]` can only be used with objects (with a string argument) or with arrays (with a numeric argument). For - other types, a [`basic_json::type_error`](../../home/exceptions.md#jsonexceptiontype_error305) is thrown. - -## Summary - -| scenario | non-const value | const value | -|-----------------------------------|------------------------------------------------------------------------------------------------------------------------------------------------------|-----------------------------------------------------------------------------| -| access to existing object key | reference to existing value is returned | const reference to existing value is returned | -| access to valid array index | reference to existing value is returned | const reference to existing value is returned | -| access to non-existing object key | reference to newly inserted `#!json null` value is returned | **undefined behavior**; [runtime assertion](../assertions.md) in debug mode | -| access to invalid array index | reference to newly inserted `#!json null` value is returned; any index between previous maximal index and passed index are filled with `#!json null` | **undefined behavior**; [runtime assertion](../assertions.md) in debug mode | diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/enum_conversion.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/enum_conversion.md deleted file mode 100644 index 59ffbd5..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/enum_conversion.md +++ /dev/null @@ -1,61 +0,0 @@ -# Specializing enum conversion - -By default, enum values are serialized to JSON as integers. In some cases this could result in undesired behavior. If an -enum is modified or re-ordered after data has been serialized to JSON, the later de-serialized JSON data may be -undefined or a different enum value than was originally intended. - -It is possible to more precisely specify how a given enum is mapped to and from JSON as shown below: - -```cpp -// example enum type declaration -enum TaskState { - TS_STOPPED, - TS_RUNNING, - TS_COMPLETED, - TS_INVALID=-1, -}; - -// map TaskState values to JSON as strings -NLOHMANN_JSON_SERIALIZE_ENUM( TaskState, { - {TS_INVALID, nullptr}, - {TS_STOPPED, "stopped"}, - {TS_RUNNING, "running"}, - {TS_COMPLETED, "completed"}, -}) -``` - -The [`NLOHMANN_JSON_SERIALIZE_ENUM()` macro](../api/macros/nlohmann_json_serialize_enum.md) declares a set of -`to_json()` / `from_json()` functions for type `TaskState` while avoiding repetition and boilerplate serialization code. - -## Usage - -```cpp -// enum to JSON as string -json j = TS_STOPPED; -assert(j == "stopped"); - -// json string to enum -json j3 = "running"; -assert(j3.get() == TS_RUNNING); - -// undefined json value to enum (where the first map entry above is the default) -json jPi = 3.14; -assert(jPi.get() == TS_INVALID ); -``` - -## Notes - -Just as in [Arbitrary Type Conversions](arbitrary_types.md) above, - -- [`NLOHMANN_JSON_SERIALIZE_ENUM()`](../api/macros/nlohmann_json_serialize_enum.md) MUST be declared in your enum type's - namespace (which can be the global namespace), or the library will not be able to locate it, and it will default to - integer serialization. -- It MUST be available (e.g., proper headers must be included) everywhere you use the conversions. - -Other Important points: - -- When using `get()`, undefined JSON values will default to the first pair specified in your map. Select this - default pair carefully. -- If an enum or JSON value is specified more than once in your map, the first matching occurrence from the top of the - map will be returned when converting to or from JSON. -- To disable the default serialization of enumerators as integers and force a compiler error instead, see [`JSON_DISABLE_ENUM_SERIALIZATION`](../api/macros/json_disable_enum_serialization.md). diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/iterators.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/iterators.md deleted file mode 100644 index ce627e0..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/iterators.md +++ /dev/null @@ -1,155 +0,0 @@ -# Iterators - -## Overview - -A `basic_json` value is a container and allows access via iterators. Depending on the value type, `basic_json` stores zero or more values. - -As for other containers, `begin()` returns an iterator to the first value and `end()` returns an iterator to the value following the last value. The latter iterator is a placeholder and cannot be dereferenced. In case of null values, empty arrays, or empty objects, `begin()` will return `end()`. - -![Illustration from cppreference.com](../images/range-begin-end.svg) - -### Iteration order for objects - -When iterating over objects, values are ordered with respect to the `object_comparator_t` type which defaults to `std::less`. See the [types documentation](types/index.md#key-order) for more information. - -??? example - - ```cpp - // create JSON object {"one": 1, "two": 2, "three": 3} - json j; - j["one"] = 1; - j["two"] = 2; - j["three"] = 3; - - for (auto it = j.begin(); it != j.end(); ++it) - { - std::cout << *it << std::endl; - } - ``` - - Output: - - ```json - 1 - 3 - 2 - ``` - - The reason for the order is the lexicographic ordering of the object keys "one", "three", "two". - -### Access object key during iteration - -The JSON iterators have two member functions, `key()` and `value()` to access the object key and stored value, respectively. When calling `key()` on a non-object iterator, an [invalid_iterator.207](../home/exceptions.md#jsonexceptioninvalid_iterator207) exception is thrown. - -??? example - - ```cpp - // create JSON object {"one": 1, "two": 2, "three": 3} - json j; - j["one"] = 1; - j["two"] = 2; - j["three"] = 3; - - for (auto it = j.begin(); it != j.end(); ++it) - { - std::cout << it.key() << " : " << it.value() << std::endl; - } - ``` - - Output: - - ```json - one : 1 - three : 3 - two : 2 - ``` - -### Range-based for loops - -C++11 allows using range-based for loops to iterate over a container. - -```cpp -for (auto it : j_object) -{ - // "it" is of type json::reference and has no key() member - std::cout << "value: " << it << '\n'; -} -``` - -For this reason, the `items()` function allows accessing `iterator::key()` and `iterator::value()` during range-based for loops. In these loops, a reference to the JSON values is returned, so there is no access to the underlying iterator. - -```cpp -for (auto& el : j_object.items()) -{ - std::cout << "key: " << el.key() << ", value:" << el.value() << '\n'; -} -``` - -The items() function also allows using structured bindings (C++17): - -```cpp -for (auto& [key, val] : j_object.items()) -{ - std::cout << "key: " << key << ", value:" << val << '\n'; -} -``` - -!!! note - - When iterating over an array, `key()` will return the index of the element as string. For primitive types (e.g., numbers), `key()` returns an empty string. - -!!! warning - - Using `items()` on temporary objects is dangerous. Make sure the object's lifetime exceeds the iteration. See for more information. - -### Reverse iteration order - -`rbegin()` and `rend()` return iterators in the reverse sequence. - -![Illustration from cppreference.com](../images/range-rbegin-rend.svg) - -??? example - - ```cpp - json j = {1, 2, 3, 4}; - - for (auto it = j.rbegin(); it != j.rend(); ++it) - { - std::cout << *it << std::endl; - } - ``` - - Output: - - ```json - 4 - 3 - 2 - 1 - ``` - -### Iterating strings and binary values - -Note that "value" means a JSON value in this setting, not values stored in the underlying containers. That is, `*begin()` returns the complete string or binary array and is also safe the underlying string or binary array is empty. - -??? example - - ```cpp - json j = "Hello, world"; - for (auto it = j.begin(); it != j.end(); ++it) - { - std::cout << *it << std::endl; - } - ``` - - Output: - - ```json - "Hello, world" - ``` - -## Iterator invalidation - -| Operations | invalidated iterators | -|------------|-----------------------| -| `clear` | all | diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/json_patch.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/json_patch.md deleted file mode 100644 index 88c731a..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/json_patch.md +++ /dev/null @@ -1,47 +0,0 @@ -# JSON Patch and Diff - -## Patches - -JSON Patch ([RFC 6902](https://tools.ietf.org/html/rfc6902)) defines a JSON document structure for expressing a sequence -of operations to apply to a JSON document. With the `patch` function, a JSON Patch is applied to the current JSON value -by executing all operations from the patch. - -??? example - - The following code shows how a JSON patch is applied to a value. - - ```cpp - --8<-- "examples/patch.cpp" - ``` - - Output: - - ```json - --8<-- "examples/patch.output" - ``` - -## Diff - -The library can also calculate a JSON patch (i.e., a **diff**) given two JSON values. - -!!! success "Invariant" - - For two JSON values *source* and *target*, the following code yields always true: - - ```cüü - source.patch(diff(source, target)) == target; - ``` - -??? example - - The following code shows how a JSON patch is created as a diff for two JSON values. - - ```cpp - --8<-- "examples/diff.cpp" - ``` - - Output: - - ```json - --8<-- "examples/diff.output" - ``` diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/json_pointer.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/json_pointer.md deleted file mode 100644 index 04aeca5..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/json_pointer.md +++ /dev/null @@ -1,126 +0,0 @@ -# JSON Pointer - -## Introduction - -The library supports **JSON Pointer** ([RFC 6901](https://tools.ietf.org/html/rfc6901)) as alternative means to address -structured values. A JSON Pointer is a string that identifies a specific value within a JSON document. - -Consider the following JSON document - -```json -{ - "array": ["A", "B", "C"], - "nested": { - "one": 1, - "two": 2, - "three": [true, false] - } -} -``` - -Then every value inside the JSON document can be identified as follows: - -| JSON Pointer | JSON value | -|-------------------|----------------------------------------------------------------------------------| -| `` | `#!json {"array":["A","B","C"],"nested":{"one":1,"two":2,"three":[true,false]}}` | -| `/array` | `#!json ["A","B","C"]` | -| `/array/0` | `#!json A` | -| `/array/1` | `#!json B` | -| `/array/2` | `#!json C` | -| `/nested` | `#!json {"one":1,"two":2,"three":[true,false]}` | -| `/nested/one` | `#!json 1` | -| `/nested/two` | `#!json 2` | -| `/nested/three` | `#!json [true,false]` | -| `/nested/three/0` | `#!json true` | -| `/nested/three/1` | `#!json false` | - -Note `/` does not identify the root (i.e., the whole document), but an object entry with empty key `""`. See -[RFC 6901](https://tools.ietf.org/html/rfc6901) for more information. - -## JSON Pointer creation - -JSON Pointers can be created from a string: - -```cpp -json::json_pointer p = "/nested/one"; -``` - -Furthermore, a user-defined string literal can be used to achieve the same result: - -```cpp -auto p = "/nested/one"_json_pointer; -``` - -The escaping rules of [RFC 6901](https://tools.ietf.org/html/rfc6901) are implemented. See the -[constructor documentation](../api/json_pointer/json_pointer.md) for more information. - -## Value access - -JSON Pointers can be used in the [`at`](../api/basic_json/at.md), [`operator[]`](../api/basic_json/operator%5B%5D.md), -and [`value`](../api/basic_json/value.md) functions just like object keys or array indices. - -```cpp -// the JSON value from above -auto j = json::parse(R"({ - "array": ["A", "B", "C"], - "nested": { - "one": 1, - "two": 2, - "three": [true, false] - } -})"); - -// access values -auto val = j["/"_json_pointer]; // {"array":["A","B","C"],...} -auto val1 = j["/nested/one"_json_pointer]; // 1 -auto val2 = j.at[json::json_pointer("/nested/three/1")]; // false -auto val3 = j.value[json::json_pointer("/nested/four", 0)]; // 0 -``` - -## Flatten / unflatten - -The library implements a function [`flatten`](../api/basic_json/flatten.md) to convert any JSON document into a JSON -object where each key is a JSON Pointer and each value is a primitive JSON value (i.e., a string, boolean, number, or -null). - -```cpp -// the JSON value from above -auto j = json::parse(R"({ - "array": ["A", "B", "C"], - "nested": { - "one": 1, - "two": 2, - "three": [true, false] - } -})"); - -// create flattened value -auto j_flat = j.flatten(); -``` - -The resulting value `j_flat` is: - -```json -{ - "/array/0": "A", - "/array/1": "B", - "/array/2": "C", - "/nested/one": 1, - "/nested/two": 2, - "/nested/three/0": true, - "/nested/three/1": false -} -``` - -The reverse function, [`unflatten`](../api/basic_json/unflatten.md) recreates the original value. - -```cpp -auto j_original = j_flat.unflatten(); -``` - -## See also - -- Class [`json_pointer`](../api/json_pointer/index.md) -- Function [`flatten`](../api/basic_json/flatten.md) -- Function [`unflatten`](../api/basic_json/unflatten.md) -- [JSON Patch](json_patch.md) diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/macros.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/macros.md deleted file mode 100644 index 1be95d3..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/macros.md +++ /dev/null @@ -1,153 +0,0 @@ -# Supported Macros - -Some aspects of the library can be configured by defining preprocessor macros before including the `json.hpp` header. -See also the [API documentation for macros](../api/macros/index.md) for examples and more information. - -## `JSON_ASSERT(x)` - -This macro controls which code is executed for [runtime assertions](assertions.md) of the library. - -See [full documentation of `JSON_ASSERT(x)`](../api/macros/json_assert.md). - -## `JSON_CATCH_USER(exception)` - -This macro overrides [`#!cpp catch`](https://en.cppreference.com/w/cpp/language/try_catch) calls inside the library. - -See [full documentation of `JSON_CATCH_USER(exception)`](../api/macros/json_throw_user.md). - -## `JSON_DIAGNOSTICS` - -This macro enables extended diagnostics for exception messages. Possible values are `1` to enable or `0` to disable -(default). - -When enabled, exception messages contain a [JSON Pointer](json_pointer.md) to the JSON value that triggered the -exception, see [Extended diagnostic messages](../home/exceptions.md#extended-diagnostic-messages) for an example. Note -that enabling this macro increases the size of every JSON value by one pointer and adds some runtime overhead. - -The diagnostics messages can also be controlled with the CMake option `JSON_Diagnostics` (`OFF` by default) which sets -`JSON_DIAGNOSTICS` accordingly. - -See [full documentation of `JSON_DIAGNOSTICS`](../api/macros/json_diagnostics.md). - -## `JSON_HAS_CPP_11`, `JSON_HAS_CPP_14`, `JSON_HAS_CPP_17`, `JSON_HAS_CPP_20` - -The library targets C++11, but also supports some features introduced in later C++ versions (e.g., `std::string_view` -support for C++17). For these new features, the library implements some preprocessor checks to determine the C++ -standard. By defining any of these symbols, the internal check is overridden and the provided C++ version is -unconditionally assumed. This can be helpful for compilers that only implement parts of the standard and would be -detected incorrectly. - -See [full documentation of `JSON_HAS_CPP_11`, `JSON_HAS_CPP_14`, `JSON_HAS_CPP_17`, and `JSON_HAS_CPP_20`](../api/macros/json_has_cpp_11.md). - -## `JSON_HAS_FILESYSTEM`, `JSON_HAS_EXPERIMENTAL_FILESYSTEM` - -When compiling with C++17, the library provides conversions from and to `std::filesystem::path`. As compiler support -for filesystem is limited, the library tries to detect whether ``/`std::filesystem` (`JSON_HAS_FILESYSTEM`) -or ``/`std::experimental::filesystem` (`JSON_HAS_EXPERIMENTAL_FILESYSTEM`) should be used. -To override the built-in check, define `JSON_HAS_FILESYSTEM` or `JSON_HAS_EXPERIMENTAL_FILESYSTEM` to `1`. - -See [full documentation of `JSON_HAS_FILESYSTEM` and `JSON_HAS_EXPERIMENTAL_FILESYSTEM`](../api/macros/json_has_filesystem.md). - -## `JSON_NOEXCEPTION` - -Exceptions can be switched off by defining the symbol `JSON_NOEXCEPTION`. - -See [full documentation of `JSON_NOEXCEPTION`](../api/macros/json_noexception.md). - -## `JSON_DISABLE_ENUM_SERIALIZATION` - -When defined, default parse and serialize functions for enums are excluded and have to be provided by the user, for example, using [`NLOHMANN_JSON_SERIALIZE_ENUM`](../api/macros/nlohmann_json_serialize_enum.md). - -See [full documentation of `JSON_DISABLE_ENUM_SERIALIZATION`](../api/macros/json_disable_enum_serialization.md). - -## `JSON_NO_IO` - -When defined, headers ``, ``, ``, ``, and `` are not included and parse functions -relying on these headers are excluded. This is relevant for environment where these I/O functions are disallowed for -security reasons (e.g., Intel Software Guard Extensions (SGX)). - -See [full documentation of `JSON_NO_IO`](../api/macros/json_no_io.md). - -## `JSON_SKIP_LIBRARY_VERSION_CHECK` - -When defined, the library will not create a compiler warning when a different version of the library was already -included. - -See [full documentation of `JSON_SKIP_LIBRARY_VERSION_CHECK`](../api/macros/json_skip_library_version_check.md). - -## `JSON_SKIP_UNSUPPORTED_COMPILER_CHECK` - -When defined, the library will not create a compile error when a known unsupported compiler is detected. This allows to -use the library with compilers that do not fully support C++11 and may only work if unsupported features are not used. - -See [full documentation of `JSON_SKIP_UNSUPPORTED_COMPILER_CHECK`](../api/macros/json_skip_unsupported_compiler_check.md). - -## `JSON_THROW_USER(exception)` - -This macro overrides `#!cpp throw` calls inside the library. The argument is the exception to be thrown. - -See [full documentation of `JSON_THROW_USER(exception)`](../api/macros/json_throw_user.md). - -## `JSON_TRY_USER` - -This macro overrides `#!cpp try` calls inside the library. - -See [full documentation of `JSON_TRY_USER`](../api/macros/json_throw_user.md). - -## `JSON_USE_IMPLICIT_CONVERSIONS` - -When defined to `0`, implicit conversions are switched off. By default, implicit conversions are switched on. - -See [full documentation of `JSON_USE_IMPLICIT_CONVERSIONS`](../api/macros/json_use_implicit_conversions.md). - -## `NLOHMANN_DEFINE_TYPE_INTRUSIVE(type, member...)` - -This macro can be used to simplify the serialization/deserialization of types if (1) want to use a JSON object as -serialization and (2) want to use the member variable names as object keys in that object. - -The macro is to be defined inside the class/struct to create code for. Unlike -[`NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE`](#nlohmann_define_type_non_intrusivetype-member), it can access private members. -The first parameter is the name of the class/struct, and all remaining parameters name the members. - -See [full documentation of `NLOHMANN_DEFINE_TYPE_INTRUSIVE`](../api/macros/nlohmann_define_type_intrusive.md). - -## `NLOHMANN_DEFINE_TYPE_INTRUSIVE_WITH_DEFAULT(type, member...)` - -This macro is similar to `NLOHMANN_DEFINE_TYPE_INTRUSIVE`. It will not throw an exception in `from_json()` due to a -missing value in the JSON object, but can throw due to a mismatched type. The `from_json()` function default constructs -an object and uses its values as the defaults when calling the [`value`](../api/basic_json/value.md) function. - -See [full documentation of `NLOHMANN_DEFINE_TYPE_INTRUSIVE_WITH_DEFAULT`](../api/macros/nlohmann_define_type_intrusive.md). - -## `NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE(type, member...)` - -This macro can be used to simplify the serialization/deserialization of types if (1) want to use a JSON object as -serialization and (2) want to use the member variable names as object keys in that object. - -The macro is to be defined inside the namespace of the class/struct to create code for. Private members cannot be -accessed. Use [`NLOHMANN_DEFINE_TYPE_INTRUSIVE`](#nlohmann_define_type_intrusivetype-member) in these scenarios. The -first parameter is the name of the class/struct, and all remaining parameters name the members. - -See [full documentation of `NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE`](../api/macros/nlohmann_define_type_non_intrusive.md). - -## `NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE_WITH_DEFAULT(type, member...)` - -This macro is similar to `NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE`. It will not throw an exception in `from_json()` due to a -missing value in the JSON object, but can throw due to a mismatched type. The `from_json()` function default constructs -an object and uses its values as the defaults when calling the [`value`](../api/basic_json/value.md) function. - -See [full documentation of `NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE_WITH_DEFAULT`](../api/macros/nlohmann_define_type_non_intrusive.md). - -## `NLOHMANN_JSON_SERIALIZE_ENUM(type, ...)` - -This macro simplifies the serialization/deserialization of enum types. See -[Specializing enum conversion](enum_conversion.md) for more information. - -See [full documentation of `NLOHMANN_JSON_SERIALIZE_ENUM`](../api/macros/nlohmann_json_serialize_enum.md). - -## `NLOHMANN_JSON_VERSION_MAJOR`, `NLOHMANN_JSON_VERSION_MINOR`, `NLOHMANN_JSON_VERSION_PATCH` - -These macros are defined by the library and contain the version numbers according to -[Semantic Versioning 2.0.0](https://semver.org/spec/v2.0.0.html). - -See [full documentation of `NLOHMANN_JSON_VERSION_MAJOR`, `NLOHMANN_JSON_VERSION_MINOR`, and `NLOHMANN_JSON_VERSION_PATCH`](../api/macros/nlohmann_json_version_major.md). diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/merge_patch.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/merge_patch.md deleted file mode 100644 index 84e0ab0..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/merge_patch.md +++ /dev/null @@ -1,20 +0,0 @@ -# JSON Merge Patch - -The library supports JSON Merge Patch ([RFC 7386](https://tools.ietf.org/html/rfc7386)) as a patch format. -The merge patch format is primarily intended for use with the HTTP PATCH method as a means of describing a set of modifications to a target resource's content. This function applies a merge patch to the current JSON value. - -Instead of using [JSON Pointer](json_pointer.md) to specify values to be manipulated, it describes the changes using a syntax that closely mimics the document being modified. - -??? example - - The following code shows how a JSON Merge Patch is applied to a JSON document. - - ```cpp - --8<-- "examples/merge_patch.cpp" - ``` - - Output: - - ```json - --8<-- "examples/merge_patch.output" - ``` diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/namespace.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/namespace.md deleted file mode 100644 index 8cee2cc..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/namespace.md +++ /dev/null @@ -1,93 +0,0 @@ -# `nlohmann` Namespace - -The 3.11.0 release introduced an -[inline namespace](https://en.cppreference.com/w/cpp/language/namespace#Inline_namespaces) to allow different parts of -a codebase to safely use different versions of the JSON library as long as they never exchange instances of library -types. - -## Structure - -The complete default namespace name is derived as follows: - -- The root namespace is always `nlohmann`. -- The inline namespace starts with `json_abi` and is followed by serveral optional ABI tags according to the value of - these ABI-affecting macros, in order: - - [`JSON_DIAGNOSTICS`](../api/macros/json_diagnostics.md) defined non-zero appends `_diag`. - - [`JSON_USE_LEGACY_DISCARDED_VALUE_COMPARISON`](../api/macros/json_use_legacy_discarded_value_comparison.md) - defined non-zero appends `_ldvcmp`. -- The inline namespace ends with the suffix `_v` followed by the 3 components of the version number separated by - underscores. To omit the version component, see [Disabling the version component](#disabling-the-version-component) - below. - -For example, the namespace name for version 3.11.2 with `JSON_DIAGNOSTICS` defined to `1` is: - -```cpp -nlohmann::json_abi_diag_v3_11_2 -``` - -## Purpose - -Several incompatibilities have been observed. Amongst the most common ones is linking code compiled with different -definitions of [`JSON_DIAGNOSTICS`](../api/macros/json_diagnostics.md). This is illustrated in the diagram below. - -```plantuml -[**nlohmann_json (v3.10.5)**\nJSON_DIAGNOSTICS=0] as [json] -[**nlohmann_json (v3.10.5)**\nJSON_DIAGNOSTICS=1] as [json_diag] -[**some_library**] as [library] -[**application**] as [app] - -[library] ..|> [json] -[app] ..|> [json_diag] -[app] ..|>[library] -``` - -In releases prior to 3.11.0, mixing any version of the JSON library with different `JSON_DIAGNOSTICS` settings would -result in a crashing application. If `some_library` never passes instances of JSON library types to the application, -this scenario became safe in version 3.11.0 and above due to the inline namespace yielding distinct symbol names. - -## Limitations - -Neither the compiler nor the linker will issue as much as a warning when translation units – intended to be linked -together and that include different versions and/or configurations of the JSON library – exchange and use library -types. - -There is an exception when forward declarations are used (i.e., when including `json_fwd.hpp`) in which case the linker -may complain about undefined references. - -## Disabling the version component - -Different versions are not necessarily ABI-incompatible, but the project does not actively track changes in the ABI and -recommends that all parts of a codebase exchanging library types be built with the same version. Users can, **at their -own risk**, disable the version component of the linline namespace, allowing different versions – but not -configurations – to be used in cases where the linker would otherwise output undefined reference errors. - -To do so, define [`NLOHMANN_JSON_NAMESPACE_NO_VERSION`](../api/macros/nlohmann_json_namespace_no_version.md) to `1`. - -This applies to version 3.11.2 and above only, versions 3.11.0 and 3.11.1 can apply the technique described in the next -section to emulate the effect of the `NLOHMANN_JSON_NAMESPACE_NO_VERSION` macro. - -!!! danger "Use at your own risk" - - Disabling the namespace version component and mixing ABI-incompatible versions will result in crashes or incorrect - behavior. You have been warned! -## Disabling the inline namespace completely - -When interoperability with code using a pre-3.11.0 version of the library is required, users can, **at their own risk** -restore the old namespace layout by redefining -[`NLOHMANN_JSON_NAMESPACE_BEGIN, NLOHMANN_JSON_NAMESPACE_END`](../api/macros/nlohmann_json_namespace_begin.md) as -follows: - -```cpp -#define NLOHMANN_JSON_NAMESPACE_BEGIN namespace nlohmann { -#define NLOHMANN_JSON_NAMESPACE_END } -``` - -!!! danger "Use at your own risk" - - Overriding the namespace and mixing ABI-incompatible versions will result in crashes or incorrect behavior. You - have been warned! - -## Version history - -- Introduced inline namespace (`json_v3_11_0[_abi-tag]*`) in version 3.11.0. -- Changed structure of inline namespace in version 3.11.2. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/object_order.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/object_order.md deleted file mode 100644 index 3ee16a9..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/object_order.md +++ /dev/null @@ -1,109 +0,0 @@ -# Object Order - -The [JSON standard](https://tools.ietf.org/html/rfc8259.html) defines objects as "an unordered collection of zero or more name/value pairs". As such, an implementation does not need to preserve any specific order of object keys. - -## Default behavior: sort keys - -The default type `nlohmann::json` uses a `std::map` to store JSON objects, and thus stores object keys **sorted alphabetically**. - -??? example - - ```cpp - #include - #include "json.hpp" - - using json = nlohmann::json; - - int main() - { - json j; - j["one"] = 1; - j["two"] = 2; - j["three"] = 3; - - std::cout << j.dump(2) << '\n'; - } - ``` - - Output: - - ```json - { - "one": 1, - "three": 3, - "two": 2 - } - ``` - -## Alternative behavior: preserve insertion order - -If you do want to preserve the **insertion order**, you can try the type [`nlohmann::ordered_json`](https://github.com/nlohmann/json/issues/2179). - -??? example - - ```cpp - --8<-- "examples/ordered_json.cpp" - ``` - - Output: - - ```json - --8<-- "examples/ordered_json.output" - ``` - -Alternatively, you can use a more sophisticated ordered map like [`tsl::ordered_map`](https://github.com/Tessil/ordered-map) ([integration](https://github.com/nlohmann/json/issues/546#issuecomment-304447518)) or [`nlohmann::fifo_map`](https://github.com/nlohmann/fifo_map) ([integration](https://github.com/nlohmann/json/issues/485#issuecomment-333652309)). - -### Notes on parsing - -Note that you also need to call the right [`parse`](../api/basic_json/parse.md) function when reading from a file. -Assume file `input.json` contains the JSON object above: - -```json -{ - "one": 1, - "two": 2, - "three": 3 -} -``` - -!!! success "Right way" - - The following code correctly calls the `parse` function from `nlohmann::ordered_json`: - - ```cpp - std::ifstream i("input.json"); - auto j = nlohmann::ordered_json::parse(i); - std::cout << j.dump(2) << std::endl; - ``` - - The output will be: - - ```json - { - "one": 1, - "two": 2, - "three": 3 - } - ``` - -??? failure "Wrong way" - - The following code incorrectly calls the `parse` function from `nlohmann::json` which does not preserve the - insertion order, but sorts object keys. Assigning the result to `nlohmann::ordered_json` compiles, but does not - restore the order from the input file. - - ```cpp - std::ifstream i("input.json"); - nlohmann::ordered_json j = nlohmann::json::parse(i); - std::cout << j.dump(2) << std::endl; - ``` - - The output will be: - - ```json - { - "one": 1, - "three": 3 - "two": 2, - } - ``` diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/parsing/index.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/parsing/index.md deleted file mode 100644 index 2949352..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/parsing/index.md +++ /dev/null @@ -1,13 +0,0 @@ -# Parsing - -!!! note - - This page is under construction. - -## Input - -## SAX vs. DOM parsing - -## Exceptions - -See [parsing and exceptions](parse_exceptions.md). diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/parsing/json_lines.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/parsing/json_lines.md deleted file mode 100644 index 659d317..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/parsing/json_lines.md +++ /dev/null @@ -1,49 +0,0 @@ -# JSON Lines - -The [JSON Lines](https://jsonlines.org) format is a text format of newline-delimited JSON. In particular: - -1. The input must be UTF-8 encoded. -2. Every line must be a valid JSON value. -3. The line separator must be `\n`. As `\r` is silently ignored, `\r\n` is also supported. -4. The final character may be `\n`, but is not required to be one. - -!!! example "JSON Text example" - - ```json - {"name": "Gilbert", "wins": [["straight", "7♣"], ["one pair", "10♥"]]} - {"name": "Alexa", "wins": [["two pair", "4♠"], ["two pair", "9♠"]]} - {"name": "May", "wins": []} - {"name": "Deloise", "wins": [["three of a kind", "5♣"]]} - ``` - -JSON Lines input with more than one value is treated as invalid JSON by the [`parse`](../../api/basic_json/parse.md) or -[`accept`](../../api/basic_json/accept.md) functions. To process it line by line, functions like -[`std::getline`](https://en.cppreference.com/w/cpp/string/basic_string/getline) can be used: - -!!! example "Example: Parse JSON Text input line by line" - - The example below demonstrates how JSON Lines can be processed. - - ```cpp - --8<-- "examples/json_lines.cpp" - ``` - - Output: - - ```json - --8<-- "examples/json_lines.output" - ``` - -!!! warning "Note" - - Using [`operator>>`](../../api/operator_gtgt.md) like - - ```cpp - json j; - while (input >> j) - { - std::cout << j << std::endl; - } - ``` - - with a JSON Lines input does not work, because the parser will try to parse one value after the last one. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/parsing/parse_exceptions.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/parsing/parse_exceptions.md deleted file mode 100644 index 61c0ff2..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/parsing/parse_exceptions.md +++ /dev/null @@ -1,121 +0,0 @@ -# Parsing and Exceptions - -When the input is not valid JSON, an exception of type [`parse_error`](../../home/exceptions.md#parse-errors) is thrown. -This exception contains the position in the input where the error occurred, together with a diagnostic message and the -last read input token. The exceptions page contains a -[list of examples for parse error exceptions](../../home/exceptions.md#parse-errors). In case you process untrusted -input, always enclose your code with a `#!cpp try`/`#!cpp catch` block, like - -```cpp -json j; -try -{ - j = json::parse(my_input); -} -catch (json::parse_error& ex) -{ - std::cerr << "parse error at byte " << ex.byte << std::endl; -} -``` - -In case exceptions are undesired or not supported by the environment, there are different ways to proceed: - - -## Switch off exceptions - -The `parse()` function accepts a `#!cpp bool` parameter `allow_exceptions` which controls whether an exception is -thrown when a parse error occurs (`#!cpp true`, default) or whether a discarded value should be returned -(`#!cpp false`). - -```cpp -json j = json::parse(my_input, nullptr, false); -if (j.is_discarded()) -{ - std::cerr << "parse error" << std::endl; -} -``` - -Note there is no diagnostic information available in this scenario. - -## Use accept() function - -Alternatively, function `accept()` can be used which does not return a `json` value, but a `#!cpp bool` indicating -whether the input is valid JSON. - -```cpp -if (!json::accept(my_input)) -{ - std::cerr << "parse error" << std::endl; -} -``` - -Again, there is no diagnostic information available. - - -## User-defined SAX interface - -Finally, you can implement the [SAX interface](sax_interface.md) and decide what should happen in case of a parse error. - -This function has the following interface: - -```cpp -bool parse_error(std::size_t position, - const std::string& last_token, - const json::exception& ex); -``` - -The return value indicates whether the parsing should continue, so the function should usually return `#!cpp false`. - -??? example - - ```cpp - #include - #include "json.hpp" - - using json = nlohmann::json; - - class sax_no_exception : public nlohmann::detail::json_sax_dom_parser - { - public: - sax_no_exception(json& j) - : nlohmann::detail::json_sax_dom_parser(j, false) - {} - - bool parse_error(std::size_t position, - const std::string& last_token, - const json::exception& ex) - { - std::cerr << "parse error at input byte " << position << "\n" - << ex.what() << "\n" - << "last read: \"" << last_token << "\"" - << std::endl; - return false; - } - }; - - int main() - { - std::string myinput = "[1,2,3,]"; - - json result; - sax_no_exception sax(result); - - bool parse_result = json::sax_parse(myinput, &sax); - if (!parse_result) - { - std::cerr << "parsing unsuccessful!" << std::endl; - } - - std::cout << "parsed value: " << result << std::endl; - } - ``` - - Output: - - ``` - parse error at input byte 8 - [json.exception.parse_error.101] parse error at line 1, column 8: syntax error while parsing value - unexpected ']'; expected '[', '{', or a literal - last read: "3,]" - parsing unsuccessful! - parsed value: [1,2,3] - ``` diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/parsing/parser_callbacks.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/parsing/parser_callbacks.md deleted file mode 100644 index ef076d1..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/parsing/parser_callbacks.md +++ /dev/null @@ -1,83 +0,0 @@ -# Parser Callbacks - -## Overview - -With a parser callback function, the result of parsing a JSON text can be influenced. When passed to `parse`, it is -called on certain events (passed as `parse_event_t` via parameter `event`) with a set recursion depth `depth` and -context JSON value `parsed`. The return value of the callback function is a boolean indicating whether the element that -emitted the callback shall be kept or not. - -The type of the callback function is: - -```cpp -template -using parser_callback_t = - std::function; -``` - - -## Callback event types - -We distinguish six scenarios (determined by the event type) in which the callback function can be called. The following -table describes the values of the parameters `depth`, `event`, and `parsed`. - -| parameter `event` | description | parameter `depth` | parameter `parsed` | -|-------------------------------|-----------------------------------------------------------|-------------------------------------------|----------------------------------| -| `parse_event_t::object_start` | the parser read `{` and started to process a JSON object | depth of the parent of the JSON object | a JSON value with type discarded | -| `parse_event_t::key` | the parser read a key of a value in an object | depth of the currently parsed JSON object | a JSON string containing the key | -| `parse_event_t::object_end` | the parser read `}` and finished processing a JSON object | depth of the parent of the JSON object | the parsed JSON object | -| `parse_event_t::array_start` | the parser read `[` and started to process a JSON array | depth of the parent of the JSON array | a JSON value with type discarded | -| `parse_event_t::array_end` | the parser read `]` and finished processing a JSON array | depth of the parent of the JSON array | the parsed JSON array | -| `parse_event_t::value` | the parser finished reading a JSON value | depth of the value | the parsed JSON value | - -??? example - - When parsing the following JSON text, - - ```json - { - "name": "Berlin", - "location": [ - 52.519444, - 13.406667 - ] - } - ``` - - these calls are made to the callback function: - - | event | depth | parsed | - | -------------- | ----- | ------ | - | `object_start` | 0 | *discarded* | - | `key` | 1 | `#!json "name"` | - | `value` | 1 | `#!json "Berlin"` | - | `key` | 1 | `#!json "location"` | - | `array_start` | 1 | *discarded* | - | `value` | 2 | `#!json 52.519444` | - | `value` | 2 | `#!json 13.406667` | - | `array_end` | 1 | `#!json [52.519444,13.406667]` | - | `object_end` | 0 | `#!json {"location":[52.519444,13.406667],"name":"Berlin"}` | - -## Return value - -Discarding a value (i.e., returning `#!c false`) has different effects depending on the context in which the function -was called: - -- Discarded values in structured types are skipped. That is, the parser will behave as if the discarded value was never - read. -- In case a value outside a structured type is skipped, it is replaced with `#!json null`. This case happens if the - top-level element is skipped. - -??? example - - The example below demonstrates the `parse()` function with and without callback function. - - ```cpp - --8<-- "examples/parse__string__parser_callback_t.cpp" - ``` - - Output: - - ```json - --8<-- "examples/parse__string__parser_callback_t.output" - ``` diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/parsing/sax_interface.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/parsing/sax_interface.md deleted file mode 100644 index 0796a55..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/parsing/sax_interface.md +++ /dev/null @@ -1,73 +0,0 @@ -# SAX Interface - -The library uses a SAX-like interface with the following functions: - -```plantuml -interface json::sax_t { - + {abstract} bool null() - - + {abstract} bool boolean(bool val) - - + {abstract} bool number_integer(number_integer_t val) - + {abstract} bool number_unsigned(number_unsigned_t val) - - + {abstract} bool number_float(number_float_t val, const string_t& s) - - + {abstract} bool string(string_t& val) - + {abstract} bool binary(binary_t& val) - - + {abstract} bool start_object(std::size_t elements) - + {abstract} bool end_object() - + {abstract} bool start_array(std::size_t elements) - + {abstract} bool end_array() - + {abstract} bool key(string_t& val) - - + {abstract} bool parse_error(std::size_t position, const std::string& last_token, const json::exception& ex) -} -``` - -```cpp -// called when null is parsed -bool null(); - -// called when a boolean is parsed; value is passed -bool boolean(bool val); - -// called when a signed or unsigned integer number is parsed; value is passed -bool number_integer(number_integer_t val); -bool number_unsigned(number_unsigned_t val); - -// called when a floating-point number is parsed; value and original string is passed -bool number_float(number_float_t val, const string_t& s); - -// called when a string is parsed; value is passed and can be safely moved away -bool string(string_t& val); -// called when a binary value is parsed; value is passed and can be safely moved away -bool binary(binary& val); - -// called when an object or array begins or ends, resp. The number of elements is passed (or -1 if not known) -bool start_object(std::size_t elements); -bool end_object(); -bool start_array(std::size_t elements); -bool end_array(); -// called when an object key is parsed; value is passed and can be safely moved away -bool key(string_t& val); - -// called when a parse error occurs; byte position, the last token, and an exception is passed -bool parse_error(std::size_t position, const std::string& last_token, const json::exception& ex); -``` - -The return value of each function determines whether parsing should proceed. - -To implement your own SAX handler, proceed as follows: - -1. Implement the SAX interface in a class. You can use class `nlohmann::json_sax` as base class, but you can also use any class where the functions described above are implemented and public. -2. Create an object of your SAX interface class, e.g. `my_sax`. -3. Call `#!cpp bool json::sax_parse(input, &my_sax);` where the first parameter can be any input like a string or an input stream and the second parameter is a pointer to your SAX interface. - -Note the `sax_parse` function only returns a `#!cpp bool` indicating the result of the last executed SAX event. It does not return `json` value - it is up to you to decide what to do with the SAX events. Furthermore, no exceptions are thrown in case of a parse error - it is up to you what to do with the exception object passed to your `parse_error` implementation. Internally, the SAX interface is used for the DOM parser (class `json_sax_dom_parser`) as well as the acceptor (`json_sax_acceptor`), see file `json_sax.hpp`. - -## See also - -- [json_sax](../../api/json_sax/index.md) - documentation of the SAX interface -- [sax_parse](../../api/basic_json/sax_parse.md) - SAX parser diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/types/index.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/types/index.md deleted file mode 100644 index d9dfcc2..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/types/index.md +++ /dev/null @@ -1,269 +0,0 @@ -# Types - -This page gives an overview how JSON values are stored and how this can be configured. - -## Overview - -By default, JSON values are stored as follows: - -| JSON type | C++ type | -|-----------|-----------------------------------------------| -| object | `std::map` | -| array | `std::vector` | -| null | `std::nullptr_t` | -| string | `std::string` | -| boolean | `bool` | -| number | `std::int64_t`, `std::uint64_t`, and `double` | - -Note there are three different types for numbers - when parsing JSON text, the best fitting type is chosen. - -## Storage - -```plantuml -enum value_t { - null - object - array - string - boolean - number_integer - number_unsigned - number_float - binary - discarded -} - -class json_value << (U,orchid) >> { - object_t* object - array_t* array - string_t* string - binary_t* binary - boolean_t boolean - number_integer_t number_integer - number_unsigned_t number_unsigned - number_float_t number_float -} - -class basic_json { - -- type and value -- - value_t m_type - json_value m_value - -- derived types -- - + typedef object_t - + typedef array_t - + typedef binary_t - + typedef boolean_t - + typedef number_integer_t - + typedef number_unsigned_t - + typedef number_float_t -} - -basic_json .. json_value -basic_json .. value_t -``` - -## Template arguments - -The data types to store a JSON value are derived from the template arguments passed to class `basic_json`: - -```cpp -template< - template class ObjectType = std::map, - template class ArrayType = std::vector, - class StringType = std::string, - class BooleanType = bool, - class NumberIntegerType = std::int64_t, - class NumberUnsignedType = std::uint64_t, - class NumberFloatType = double, - template class AllocatorType = std::allocator, - template class JSONSerializer = adl_serializer, - class BinaryType = std::vector -> -class basic_json; -``` - -Type `json` is an alias for `basic_json<>` and uses the default types. - -From the template arguments, the following types are derived: - -```cpp -using object_comparator_t = std::less<>; -using object_t = ObjectType>>; - -using array_t = ArrayType>; - -using string_t = StringType; - -using boolean_t = BooleanType; - -using number_integer_t = NumberIntegerType; -using number_unsigned_t = NumberUnsignedType; -using number_float_t = NumberFloatType; - -using binary_t = nlohmann::byte_container_with_subtype; -``` - - -## Objects - -[RFC 8259](https://tools.ietf.org/html/rfc8259) describes JSON objects as follows: - -> An object is an unordered collection of zero or more name/value pairs, where a name is a string and a value is a string, number, boolean, null, object, or array. - -### Default type - -With the default values for *ObjectType* (`std::map`), *StringType* (`std::string`), and *AllocatorType* (`std::allocator`), the default value for `object_t` is: - -```cpp -std::map< - std::string, // key_type - basic_json, // value_type - std::less<>, // key_compare - std::allocator> // allocator_type -> -``` - -### Behavior - -The choice of `object_t` influences the behavior of the JSON class. With the default type, objects have the following behavior: - -- When all names are unique, objects will be interoperable in the sense that all software implementations receiving that object will agree on the name-value mappings. -- When the names within an object are not unique, it is unspecified which one of the values for a given key will be chosen. For instance, `#!json {"key": 2, "key": 1}` could be equal to either `#!json {"key": 1}` or `#!json {"key": 2}`. -- Internally, name/value pairs are stored in lexicographical order of the names. Objects will also be serialized (see `dump`) in this order. For instance, both `#!json {"b": 1, "a": 2}` and `#!json {"a": 2, "b": 1}` will be stored and serialized as `#!json {"a": 2, "b": 1}`. -- When comparing objects, the order of the name/value pairs is irrelevant. This makes objects interoperable in the sense that they will not be affected by these differences. For instance, `#!json {"b": 1, "a": 2}` and `#!json {"a": 2, "b": 1}` will be treated as equal. - -### Key order - -The order name/value pairs are added to the object is *not* preserved by the library. Therefore, iterating an object may return name/value pairs in a different order than they were originally stored. In fact, keys will be traversed in alphabetical order as `std::map` with `std::less` is used by default. Please note this behavior conforms to [RFC 8259](https://tools.ietf.org/html/rfc8259), because any order implements the specified "unordered" nature of JSON objects. - -### Limits - -[RFC 8259](https://tools.ietf.org/html/rfc8259) specifies: - -> An implementation may set limits on the maximum depth of nesting. - -In this class, the object's limit of nesting is not explicitly constrained. However, a maximum depth of nesting may be introduced by the compiler or runtime environment. A theoretical limit can be queried by calling the `max_size` function of a JSON object. - -### Storage - -Objects are stored as pointers in a `basic_json` type. That is, for any access to object values, a pointer of type `object_t*` must be dereferenced. - - -## Arrays - -[RFC 8259](https://tools.ietf.org/html/rfc8259) describes JSON arrays as follows: - -> An array is an ordered sequence of zero or more values. - -### Default type - -With the default values for *ArrayType* (`std::vector`) and *AllocatorType* (`std::allocator`), the default value for `array_t` is: - -```cpp -std::vector< - basic_json, // value_type - std::allocator // allocator_type -> -``` - -### Limits - -[RFC 8259](https://tools.ietf.org/html/rfc8259) specifies: - -> An implementation may set limits on the maximum depth of nesting. - -In this class, the array's limit of nesting is not explicitly constrained. However, a maximum depth of nesting may be introduced by the compiler or runtime environment. A theoretical limit can be queried by calling the `max_size` function of a JSON array. - -### Storage - -Arrays are stored as pointers in a `basic_json` type. That is, for any access to array values, a pointer of type `array_t*` must be dereferenced. - - -## Strings - -[RFC 8259](https://tools.ietf.org/html/rfc8259) describes JSON strings as follows: - -> A string is a sequence of zero or more Unicode characters. - -Unicode values are split by the JSON class into byte-sized characters during deserialization. - -### Default type - -With the default values for *StringType* (`std::string`), the default value for `string_t` is `#!cpp std::string`. - -### Encoding - -Strings are stored in UTF-8 encoding. Therefore, functions like `std::string::size()` or `std::string::length()` return the number of **bytes** in the string rather than the number of characters or glyphs. - -### String comparison - -[RFC 8259](https://tools.ietf.org/html/rfc8259) states: - -> Software implementations are typically required to test names of object members for equality. Implementations that transform the textual representation into sequences of Unicode code units and then perform the comparison numerically, code unit by code unit, are interoperable in the sense that implementations will agree in all cases on equality or inequality of two strings. For example, implementations that compare strings with escaped characters unconverted may incorrectly find that `"a\\b"` and `"a\u005Cb"` are not equal. - -This implementation is interoperable as it does compare strings code unit by code unit. - -### Storage - -String values are stored as pointers in a `basic_json` type. That is, for any access to string values, a pointer of type `string_t*` must be dereferenced. - - -## Booleans - -[RFC 8259](https://tools.ietf.org/html/rfc8259) implicitly describes a boolean as a type which differentiates the two literals `true` and `false`. - -### Default type - -With the default values for *BooleanType* (`#!cpp bool`), the default value for `boolean_t` is `#!cpp bool`. - -### Storage - -Boolean values are stored directly inside a `basic_json` type. - -## Numbers - -See the [number handling](number_handling.md) article for a detailed discussion on how numbers are handled by this library. - -[RFC 8259](https://tools.ietf.org/html/rfc8259) describes numbers as follows: - -> The representation of numbers is similar to that used in most programming languages. A number is represented in base 10 using decimal digits. It contains an integer component that may be prefixed with an optional minus sign, which may be followed by a fraction part and/or an exponent part. Leading zeros are not allowed. (...) Numeric values that cannot be represented in the grammar below (such as Infinity and NaN) are not permitted. - -This description includes both integer and floating-point numbers. However, C++ allows more precise storage if it is known whether the number is a signed integer, an unsigned integer or a floating-point number. Therefore, three different types, `number_integer_t`, `number_unsigned_t`, and `number_float_t` are used. - -### Default types - -With the default values for *NumberIntegerType* (`std::int64_t`), the default value for `number_integer_t` is `std::int64_t`. -With the default values for *NumberUnsignedType* (`std::uint64_t`), the default value for `number_unsigned_t` is `std::uint64_t`. -With the default values for *NumberFloatType* (`#!cpp double`), the default value for `number_float_t` is `#!cpp double`. - -### Default behavior - -- The restrictions about leading zeros is not enforced in C++. Instead, leading zeros in integer literals lead to an interpretation as octal number. Internally, the value will be stored as decimal number. For instance, the C++ integer literal `#!c 010` will be serialized to `#!c 8`. During deserialization, leading zeros yield an error. -- Not-a-number (NaN) values will be serialized to `#!json null`. - -### Limits - -[RFC 8259](https://tools.ietf.org/html/rfc8259) specifies: - -> An implementation may set limits on the range and precision of numbers. - -When the default type is used, the maximal integer number that can be stored is `#!c 9223372036854775807` (`INT64_MAX`) and the minimal integer number that can be stored is `#!c -9223372036854775808` (`INT64_MIN`). Integer numbers that are out of range will yield over/underflow when used in a constructor. During deserialization, too large or small integer numbers will be automatically be stored as `number_unsigned_t` or `number_float_t`. - -When the default type is used, the maximal unsigned integer number that can be stored is `#!c 18446744073709551615` (`UINT64_MAX`) and the minimal integer number that can be stored is `#!c 0`. Integer numbers that are out of range will yield over/underflow when used in a constructor. During deserialization, too large or small integer numbers will be automatically be stored as `number_integer_t` or `number_float_t`. - -[RFC 8259](https://tools.ietf.org/html/rfc8259) further states: - -> Note that when such software is used, numbers that are integers and are in the range $[-2^{53}+1, 2^{53}-1]$ are interoperable in the sense that implementations will agree exactly on their numeric values. - -As this range is a subrange of the exactly supported range [`INT64_MIN`, `INT64_MAX`], this class's integer type is interoperable. - -[RFC 8259](https://tools.ietf.org/html/rfc8259) states: - -> This specification allows implementations to set limits on the range and precision of numbers accepted. Since software that implements IEEE 754-2008 binary64 (double precision) numbers is generally available and widely used, good interoperability can be achieved by implementations that expect no more precision or range than these provide, in the sense that implementations will approximate JSON numbers within the expected precision. - -This implementation does exactly follow this approach, as it uses double precision floating-point numbers. Note values smaller than `#!c -1.79769313486232e+308` and values greater than `#!c 1.79769313486232e+308` will be stored as NaN internally and be serialized to `#!json null`. - -### Storage - -Integer number values, unsigned integer number values, and floating-point number values are stored directly inside a `basic_json` type. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/types/number_handling.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/types/number_handling.md deleted file mode 100644 index 03d8c9c..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/features/types/number_handling.md +++ /dev/null @@ -1,328 +0,0 @@ -# Number Handling - -This document describes how the library is handling numbers. - -## Background - -This section briefly summarizes how the JSON specification describes how numbers should be handled. - -### JSON number syntax - -JSON defines the syntax of numbers as follows: - -!!! quote "[RFC 8259](https://tools.ietf.org/html/rfc8259#section-6), Section 6" - - The representation of numbers is similar to that used in most - programming languages. A number is represented in base 10 using - decimal digits. It contains an integer component that may be - prefixed with an optional minus sign, which may be followed by a - fraction part and/or an exponent part. Leading zeros are not - allowed. - - A fraction part is a decimal point followed by one or more digits. - - An exponent part begins with the letter E in uppercase or lowercase, - which may be followed by a plus or minus sign. The E and optional - sign are followed by one or more digits. - -The following railroad diagram from [json.org](https://json.org) visualizes the number syntax: - -![Syntax for JSON numbers](../../images/json_syntax_number.png) - -### Number interoperability - -On number interoperability, the following remarks are made: - -!!! quote "[RFC 8259](https://tools.ietf.org/html/rfc8259#section-6), Section 6" - - This specification allows implementations to set limits on the range - and precision of numbers accepted. Since software that implements - IEEE 754 binary64 (double precision) numbers [IEEE754] is generally - available and widely used, good interoperability can be achieved by - implementations that expect no more precision or range than these - provide, in the sense that implementations will approximate JSON - numbers within the expected precision. A JSON number such as 1E400 - or 3.141592653589793238462643383279 may indicate potential - interoperability problems, since it suggests that the software that - created it expects receiving software to have greater capabilities - for numeric magnitude and precision than is widely available. - - Note that when such software is used, numbers that are integers and - are in the range $[-2^{53}+1, 2^{53}-1]$ are interoperable in the - sense that implementations will agree exactly on their numeric - values. - -## Library implementation - -This section describes how the above number specification is implemented by this library. - -### Number storage - -In the default [`json`](../../api/json.md) type, numbers are stored as `#!c std::uint64_t`, `#!c std::int64_t`, and -`#!c double`, respectively. Thereby, `#!c std::uint64_t` and `#!c std::int64_t` are used only if they can store the -number without loss of precision. If this is impossible (e.g., if the number is too large), the number is stored as -`#!c double`. - -!!! info "Notes" - - - Numbers with a decimal digit or scientific notation are always stored as `#!c double`. - - The number types can be changed, see [Template number types](#template-number-types). - - As of version 3.9.1, the conversion is realized by - [`std::strtoull`](https://en.cppreference.com/w/cpp/string/byte/strtoul), - [`std::strtoll`](https://en.cppreference.com/w/cpp/string/byte/strtol), and - [`std::strtod`](https://en.cppreference.com/w/cpp/string/byte/strtof), respectively. - -!!! example "Examples" - - - Integer `#!c -12345678912345789123456789` is smaller than `#!c INT64_MIN` and will be stored as floating-point - number `#!c -1.2345678912345788e+25`. - - Integer `#!c 1E3` will be stored as floating-point number `#!c 1000.0`. - -### Number limits - -- Any 64-bit signed or unsigned integer can be stored without loss of precision. -- Numbers exceeding the limits of `#!c double` (i.e., numbers that after conversion via -[`std::strtod`](https://en.cppreference.com/w/cpp/string/byte/strtof) are not satisfying -[`std::isfinite`](https://en.cppreference.com/w/cpp/numeric/math/isfinite) such as `#!c 1E400`) will throw exception -[`json.exception.out_of_range.406`](../../home/exceptions.md#jsonexceptionout_of_range406) during parsing. -- Floating-point numbers are rounded to the next number representable as `double`. For instance -`#!c 3.141592653589793238462643383279` is stored as [`0x400921fb54442d18`](https://float.exposed/0x400921fb54442d18). -This is the same behavior as the code `#!c double x = 3.141592653589793238462643383279;`. - -!!! success "Interoperability" - - - The library interoperable with respect to the specification, because its supported range $[-2^{63}, 2^{64}-1]$ is - larger than the described range $[-2^{53}+1, 2^{53}-1]$. - - All integers outside the range $[-2^{63}, 2^{64}-1]$, as well as floating-point numbers are stored as `double`. - This also concurs with the specification above. - -### Zeros - -The JSON number grammar allows for different ways to express zero, and this library will store zeros differently: - -| Literal | Stored value and type | Serialization | -|---------|------------------------|---------------| -| `0` | `#!c std::uint64_t(0)` | `0` | -| `-0` | `#!c std::int64_t(0)` | `0` | -| `0.0` | `#!c double(0.0)` | `0.0` | -| `-0.0` | `#!c double(-0.0)` | `-0.0` | -| `0E0` | `#!c double(0.0)` | `0.0` | -| `-0E0` | `#!c double(-0.0)` | `-0.0` | - -That is, `-0` is stored as a signed integer, but the serialization does not reproduce the `-`. - -### Number serialization - -- Integer numbers are serialized as is; that is, no scientific notation is used. -- Floating-point numbers are serialized as specified by the `#!c %g` printf modifier with - [`std::numeric_limits::max_digits10`](https://en.cppreference.com/w/cpp/types/numeric_limits/max_digits10) - significant digits. The rationale is to use the shortest representation while still allow round-tripping. - -!!! hint "Notes regarding precision of floating-point numbers" - - As described above, floating-point numbers are rounded to the nearest double and serialized with the shortest - representation to allow round-tripping. This can yield confusing examples: - - - The serialization can have fewer decimal places than the input: `#!c 2555.5599999999999` will be serialized as - `#!c 2555.56`. The reverse can also be true. - - The serialization can be in scientific notation even if the input is not: `#!c 0.0000972439793401814` will be - serialized as `#!c 9.72439793401814e-05`. The reverse can also be true: `#!c 12345E-5` will be serialized as - `#!c 0.12345`. - - Conversions from `#!c float` to `#!c double` can also introduce rounding errors: - ```cpp - float f = 0.3; - json j = f; - std::cout << j << '\n'; - ``` - yields `#!c 0.30000001192092896`. - - All examples here can be reproduced by passing the original double value to - - ```cpp - std::printf("%.*g\n", std::numeric_limits::max_digits10, double_value); - ``` - -#### NaN handling - -NaN (not-a-number) cannot be expressed with the number syntax described above and are in fact explicitly excluded: - -!!! quote "[RFC 8259](https://tools.ietf.org/html/rfc8259#section-6), Section 6" - - Numeric values that cannot be represented in the grammar below (such - as Infinity and NaN) are not permitted. - -That is, there is no way to *parse* a NaN value. However, NaN values can be stored in a JSON value by assignment. - -This library serializes NaN values as `#!js null`. This corresponds to the behavior of JavaScript's -[`JSON.stringify`](https://www.w3schools.com/js/js_json_stringify.asp) function. - -!!! example - - The following example shows how a NaN value is stored in a `json` value. - - ```cpp - int main() - { - double val = std::numeric_limits::quiet_NaN(); - std::cout << "val=" << val << std::endl; - json j = val; - std::cout << "j=" << j.dump() << std::endl; - val = j; - std::cout << "val=" << val << std::endl; - } - ``` - - output: - - ``` - val=nan - j=null - val=nan - ``` - -### Number comparison - -Floating-point inside JSON values numbers are compared with `#!c json::number_float_t::operator==` which is -`#!c double::operator==` by default. - -!!! example "Alternative comparison functions" - - To compare floating-point while respecting an epsilon, an alternative - [comparison function](https://github.com/mariokonrad/marnav/blob/master/include/marnav/math/floatingpoint.hpp#L34-#L39) - could be used, for instance - - ```cpp - template::value, T>::type> - inline bool is_same(T a, T b, T epsilon = std::numeric_limits::epsilon()) noexcept - { - return std::abs(a - b) <= epsilon; - } - ``` - Or you can self-define an operator equal function like this: - - ```cpp - bool my_equal(const_reference lhs, const_reference rhs) - { - const auto lhs_type lhs.type(); - const auto rhs_type rhs.type(); - if (lhs_type == rhs_type) - { - switch(lhs_type) - { - // self_defined case - case value_t::number_float: - return std::abs(lhs - rhs) <= std::numeric_limits::epsilon(); - - // other cases remain the same with the original - ... - } - } - ... - } - ``` - - (see [#703](https://github.com/nlohmann/json/issues/703) for more information.) - -!!! note - - NaN values never compare equal to themselves or to other NaN values. See [#514](https://github.com/nlohmann/json/issues/514). - -### Number conversion - -Just like the C++ language itself, the `get` family of functions allows conversions between unsigned and signed -integers, and between integers and floating-point values to integers. This behavior may be surprising. - -!!! warning "Unconditional number conversions" - - ```cpp hl_lines="3" - double d = 42.3; // non-integer double value 42.3 - json jd = d; // stores double value 42.3 - std::int64_t i = jd.get(); // now i==42; no warning or error is produced - ``` - - Note the last line with throw a [`json.exception.type_error.302`](../../home/exceptions.md#jsonexceptiontype_error302) - exception if `jd` is not a numerical type, for instance a string. - -The rationale is twofold: - -1. JSON does not define a number type or precision (see [#json-specification](above)). -2. C++ also allows to silently convert between number types. - -!!! success "Conditional number conversion" - - The code above can be solved by explicitly checking the nature of the value with members such as - [`is_number_integer()`](../../api/basic_json/is_number_integer.md) or - [`is_number_unsigned()`](../../api/basic_json/is_number_unsigned.md): - - ```cpp hl_lines="2" - // check if jd is really integer-valued - if (jd.is_number_integer()) - { - // if so, do the conversion and use i - std::int64_t i = jd.get(); - // ... - } - else - { - // otherwise, take appropriate action - // ... - } - ``` - - Note this approach also has the advantage that it can react on non-numerical JSON value types such as strings. - - (Example taken from [#777](https://github.com/nlohmann/json/issues/777#issuecomment-459968458).) - -### Determine number types - -As the example in [Number conversion](#number-conversion) shows, there are different functions to determine the type of -the stored number: - -- [`is_number()`](../../api/basic_json/is_number.md) returns `#!c true` for any number type -- [`is_number_integer()`](../../api/basic_json/is_number_integer.md) returns `#!c true` for signed and unsigned integers -- [`is_number_unsigned()`](../../api/basic_json/is_number_unsigned.md) returns `#!c true` for unsigned integers only -- [`is_number_float()`](../../api/basic_json/is_number_float.md) returns `#!c true` for floating-point numbers -- [`type_name()`](../../api/basic_json/type_name.md) returns `#!c "number"` for any number type -- [`type()`](../../api/basic_json/type.md) returns a different enumerator of - [`value_t`](../../api/basic_json/value_t.md) for all number types - -| function | unsigned integer | signed integer | floating-point | string | -|----------------------------------------------------------------------|-------------------|------------------|----------------|----------------| -| [`is_number()`](../../api/basic_json/is_number.md) | `#!c true` | `#!c true` | `#!c true` | `#!c false` | -| [`is_number_integer()`](../../api/basic_json/is_number_integer.md) | `#!c true` | `#!c true` | `#!c false` | `#!c false` | -| [`is_number_unsigned()`](../../api/basic_json/is_number_unsigned.md) | `#!c true` | `#!c false` | `#!c false` | `#!c false` | -| [`is_number_float()`](../../api/basic_json/is_number_float.md) | `#!c false` | `#!c false` | `#!c true` | `#!c false` | -| [`type_name()`](../../api/basic_json/type_name.md) | `#!c "number"` | `#!c "number"` | `#!c "number"` | `#!c "string"` | -| [`type()`](../../api/basic_json/type.md) | `number_unsigned` | `number_integer` | `number_float` | `string` | - -### Template number types - -The number types can be changed with template parameters. - -| position | number type | default type | possible values | -|----------|-------------------|---------------------|------------------------------------------------| -| 5 | signed integers | `#!c std::int64_t` | `#!c std::int32_t`, `#!c std::int16_t`, etc. | -| 6 | unsigned integers | `#!c std::uint64_t` | `#!c std::uint32_t`, `#!c std::uint16_t`, etc. | -| 7 | floating-point | `#!c double` | `#!c float`, `#!c long double` | - -!!! info "Constraints on number types" - - - The type for signed integers must be convertible from `#!c long long`. The type for floating-point numbers is used - in case of overflow. - - The type for unsigned integers must be convertible from `#!c unsigned long long`. The type for floating-point - numbers is used in case of overflow. - - The types for signed and unsigned integers must be distinct, see - [#2573](https://github.com/nlohmann/json/issues/2573). - - Only `#!c double`, `#!c float`, and `#!c long double` are supported for floating-point numbers. - -!!! example - - A `basic_json` type that uses `#!c long double` as floating-point type. - - ```cpp hl_lines="2" - using json_ld = nlohmann::basic_json; - ``` - - Note values should then be parsed with `json_ld::parse` rather than `json::parse` as the latter would parse - floating-point values to `#!c double` before then converting them to `#!c long double`. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/home/code_of_conduct.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/home/code_of_conduct.md deleted file mode 100644 index 770b817..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/home/code_of_conduct.md +++ /dev/null @@ -1,46 +0,0 @@ -# Contributor Covenant Code of Conduct - -## Our Pledge - -In the interest of fostering an open and welcoming environment, we as contributors and maintainers pledge to making participation in our project and our community a harassment-free experience for everyone, regardless of age, body size, disability, ethnicity, gender identity and expression, level of experience, nationality, personal appearance, race, religion, or sexual identity and orientation. - -## Our Standards - -Examples of behavior that contributes to creating a positive environment include: - -* Using welcoming and inclusive language -* Being respectful of differing viewpoints and experiences -* Gracefully accepting constructive criticism -* Focusing on what is best for the community -* Showing empathy towards other community members - -Examples of unacceptable behavior by participants include: - -* The use of sexualized language or imagery and unwelcome sexual attention or advances -* Trolling, insulting/derogatory comments, and personal or political attacks -* Public or private harassment -* Publishing others' private information, such as a physical or electronic address, without explicit permission -* Other conduct which could reasonably be considered inappropriate in a professional setting - -## Our Responsibilities - -Project maintainers are responsible for clarifying the standards of acceptable behavior and are expected to take appropriate and fair corrective action in response to any instances of unacceptable behavior. - -Project maintainers have the right and responsibility to remove, edit, or reject comments, commits, code, wiki edits, issues, and other contributions that are not aligned to this Code of Conduct, or to ban temporarily or permanently any contributor for other behaviors that they deem inappropriate, threatening, offensive, or harmful. - -## Scope - -This Code of Conduct applies both within project spaces and in public spaces when an individual is representing the project or its community. Examples of representing a project or community include using an official project e-mail address, posting via an official social media account, or acting as an appointed representative at an online or offline event. Representation of a project may be further defined and clarified by project maintainers. - -## Enforcement - -Instances of abusive, harassing, or otherwise unacceptable behavior may be reported by contacting the project team at mail@nlohmann.me. The project team will review and investigate all complaints, and will respond in a way that it deems appropriate to the circumstances. The project team is obligated to maintain confidentiality with regard to the reporter of an incident. Further details of specific enforcement policies may be posted separately. - -Project maintainers who do not follow or enforce the Code of Conduct in good faith may face temporary or permanent repercussions as determined by other members of the project's leadership. - -## Attribution - -This Code of Conduct is adapted from the [Contributor Covenant][homepage], version 1.4, available at [http://contributor-covenant.org/version/1/4][version] - -[homepage]: http://contributor-covenant.org -[version]: http://contributor-covenant.org/version/1/4/ diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/home/design_goals.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/home/design_goals.md deleted file mode 100644 index b80551f..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/home/design_goals.md +++ /dev/null @@ -1,17 +0,0 @@ -# Design goals - -There are myriads of [JSON](https://json.org) libraries out there, and each may even have its reason to exist. Our class had these design goals: - -- **Intuitive syntax**. In languages such as Python, JSON feels like a first class data type. We used all the operator magic of modern C++ to achieve the same feeling in your code. Check out the [examples below](#examples), and you'll know what I mean. - -- **Trivial integration**. Our whole code consists of a single header file [`json.hpp`](https://github.com/nlohmann/json/blob/develop/single_include/nlohmann/json.hpp). That's it. No library, no subproject, no dependencies, no complex build system. The class is written in vanilla C++11. All in all, everything should require no adjustment of your compiler flags or project settings. - -- **Serious testing**. Our class is heavily [unit-tested](https://github.com/nlohmann/json/tree/develop/test/src) and covers [100%](https://coveralls.io/r/nlohmann/json) of the code, including all exceptional behavior. Furthermore, we checked with [Valgrind](http://valgrind.org) and the [Clang Sanitizers](https://clang.llvm.org/docs/index.html) that there are no memory leaks. [Google OSS-Fuzz](https://github.com/google/oss-fuzz/tree/master/projects/json) additionally runs fuzz tests against all parsers 24/7, effectively executing billions of tests so far. To maintain high quality, the project is following the [Core Infrastructure Initiative (CII) best practices](https://bestpractices.coreinfrastructure.org/projects/289). - -Other aspects were not so important to us: - -- **Memory efficiency**. Each JSON object has an overhead of one pointer (the maximal size of a union) and one enumeration element (1 byte). The default generalization uses the following C++ data types: `std::string` for strings, `int64_t`, `uint64_t` or `double` for numbers, `std::map` for objects, `std::vector` for arrays, and `bool` for Booleans. However, you can template the generalized class `basic_json` to your needs. - -- **Speed**. There are certainly [faster JSON libraries](https://github.com/miloyip/nativejson-benchmark#parsing-time) out there. However, if your goal is to speed up your development by adding JSON support with a single header, then this library is the way to go. If you know how to use a `std::vector` or `std::map`, you are already set. - -See the [contribution guidelines](https://github.com/nlohmann/json/blob/master/.github/CONTRIBUTING.md#please-dont) for more information. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/home/exceptions.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/home/exceptions.md deleted file mode 100644 index 0ecf855..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/home/exceptions.md +++ /dev/null @@ -1,896 +0,0 @@ -# Exceptions - -## Overview - -### Base type - -All exceptions inherit from class `json::exception` (which in turn inherits from `std::exception`). It is used as the base class for all exceptions thrown by the `basic_json` class. This class can hence be used as "wildcard" to catch exceptions. - -```plantuml -std::exception <|-- json::exception -json::exception <|-- json::parse_error -json::exception <|-- json::invalid_iterator -json::exception <|-- json::type_error -json::exception <|-- json::out_of_range -json::exception <|-- json::other_error - -interface std::exception {} - -class json::exception { - + const int id - + const char* what() const -} - -class json::parse_error { - + const std::size_t byte -} -``` - -### Switch off exceptions - -Exceptions are used widely within the library. They can, however, be switched off with either using the compiler flag `-fno-exceptions` or by defining the symbol [`JSON_NOEXCEPTION`](../api/macros/json_noexception.md). In this case, exceptions are replaced by `abort()` calls. You can further control this behavior by defining `JSON_THROW_USER` (overriding `#!cpp throw`), `JSON_TRY_USER` (overriding `#!cpp try`), and `JSON_CATCH_USER` (overriding `#!cpp catch`). - -Note that [`JSON_THROW_USER`](../api/macros/json_throw_user.md) should leave the current scope (e.g., by throwing or aborting), as continuing after it may yield undefined behavior. - -??? example - - The code below switches off exceptions and creates a log entry with a detailed error message in case of errors. - - ```cpp - #include - - #define JSON_TRY_USER if(true) - #define JSON_CATCH_USER(exception) if(false) - #define JSON_THROW_USER(exception) \ - {std::clog << "Error in " << __FILE__ << ":" << __LINE__ \ - << " (function " << __FUNCTION__ << ") - " \ - << (exception).what() << std::endl; \ - std::abort();} - - #include - ``` - -Note the explanatory [`what()`](https://en.cppreference.com/w/cpp/error/exception/what) string of exceptions is not available for MSVC if exceptions are disabled, see [#2824](https://github.com/nlohmann/json/discussions/2824). - -See [documentation of `JSON_TRY_USER`, `JSON_CATCH_USER` and `JSON_THROW_USER`](../api/macros/json_throw_user.md) for more information. - -### Extended diagnostic messages - -Exceptions in the library are thrown in the local context of the JSON value they are detected. This makes detailed diagnostics messages, and hence debugging, difficult. - -??? example - - ```cpp - --8<-- "examples/diagnostics_standard.cpp" - ``` - - Output: - - ``` - --8<-- "examples/diagnostics_standard.output" - ``` - - This exception can be hard to debug if storing the value `#!c "12"` and accessing it is further apart. - -To create better diagnostics messages, each JSON value needs a pointer to its parent value such that a global context (i.e., a path from the root value to the value that lead to the exception) can be created. That global context is provided as [JSON Pointer](../features/json_pointer.md). - -As this global context comes at the price of storing one additional pointer per JSON value and runtime overhead to maintain the parent relation, extended diagnostics are disabled by default. They can, however, be enabled by defining the preprocessor symbol [`JSON_DIAGNOSTICS`](../api/macros/json_diagnostics.md) to `1` before including `json.hpp`. - -??? example - - ```cpp - --8<-- "examples/diagnostics_extended.cpp" - ``` - - Output: - - ``` - --8<-- "examples/diagnostics_extended.output" - ``` - - Now the exception message contains a JSON Pointer `/address/housenumber` that indicates which value has the wrong type. - -See [documentation of `JSON_DIAGNOSTICS`](../api/macros/json_diagnostics.md) for more information. - -## Parse errors - -This exception is thrown by the library when a parse error occurs. Parse errors -can occur during the deserialization of JSON text, CBOR, MessagePack, as well -as when using JSON Patch. - -Exceptions have ids 1xx. - -!!! info "Byte index" - - Member `byte` holds the byte index of the last read character in the input - file. - - For an input with n bytes, 1 is the index of the first character and n+1 - is the index of the terminating null byte or the end of file. This also - holds true when reading a byte vector (CBOR or MessagePack). - -??? example - - The following code shows how a `parse_error` exception can be caught. - - ```cpp - --8<-- "examples/parse_error.cpp" - ``` - - Output: - - ``` - --8<-- "examples/parse_error.output" - ``` - - -### json.exception.parse_error.101 - -This error indicates a syntax error while deserializing a JSON text. The error message describes that an unexpected token (character) was encountered, and the member `byte` indicates the error position. - -!!! failure "Example message" - - Input ended prematurely: - - ``` - [json.exception.parse_error.101] parse error at 2: unexpected end of input; expected string literal - ``` - - No input: - - ``` - [json.exception.parse_error.101] parse error at line 1, column 1: syntax error while parsing value - unexpected end of input; expected '[', '{', or a literal - ``` - - Control character was not escaped: - - ``` - [json.exception.parse_error.101] parse error at line 1, column 2: syntax error while parsing value - invalid string: control character U+0009 (HT) must be escaped to \u0009 or \\; last read: '"'" - ``` - - String was not closed: - - ``` - [json.exception.parse_error.101] parse error at line 1, column 2: syntax error while parsing value - invalid string: missing closing quote; last read: '"' - ``` - - Invalid number format: - - ``` - [json.exception.parse_error.101] parse error at line 1, column 3: syntax error while parsing value - invalid number; expected '+', '-', or digit after exponent; last read: '1E' - ``` - - `\u` was not be followed by four hex digits: - - ``` - [json.exception.parse_error.101] parse error at line 1, column 6: syntax error while parsing value - invalid string: '\u' must be followed by 4 hex digits; last read: '"\u01"' - ``` - - Invalid UTF-8 surrogate pair: - - ``` - [json.exception.parse_error.101] parse error at line 1, column 13: syntax error while parsing value - invalid string: surrogate U+DC00..U+DFFF must follow U+D800..U+DBFF; last read: '"\uD7FF\uDC00'" - ``` - - Invalid UTF-8 byte: - - ``` - [json.exception.parse_error.101] parse error at line 3, column 24: syntax error while parsing value - invalid string: ill-formed UTF-8 byte; last read: '"vous \352t' - ``` - -!!! tip - - - Make sure the input is correctly read. Try to write the input to standard output to check if, for instance, the input file was successfully opened. - - Paste the input to a JSON validator like or a tool like [jq](https://stedolan.github.io/jq/). - -### json.exception.parse_error.102 - -JSON uses the `\uxxxx` format to describe Unicode characters. Code points above 0xFFFF are split into two `\uxxxx` entries ("surrogate pairs"). This error indicates that the surrogate pair is incomplete or contains an invalid code point. - -!!! failure "Example message" - - ``` - parse error at 14: missing or wrong low surrogate - ``` - -!!! note - - This exception is not used any more. Instead [json.exception.parse_error.101](#jsonexceptionparse_error101) with a more detailed description is used. - -### json.exception.parse_error.103 - -Unicode supports code points up to 0x10FFFF. Code points above 0x10FFFF are invalid. - -!!! failure "Example message" - - ``` - parse error: code points above 0x10FFFF are invalid - ``` - -!!! note - - This exception is not used any more. Instead [json.exception.parse_error.101](#jsonexceptionparse_error101) with a more detailed description is used. - -### json.exception.parse_error.104 - -[RFC 6902](https://tools.ietf.org/html/rfc6902) requires a JSON Patch document to be a JSON document that represents an array of objects. - -!!! failure "Example message" - - ``` - [json.exception.parse_error.104] parse error: JSON patch must be an array of objects - ``` - -### json.exception.parse_error.105 - -An operation of a JSON Patch document must contain exactly one "op" member, whose value indicates the operation to perform. Its value must be one of "add", "remove", "replace", "move", "copy", or "test"; other values are errors. - -!!! failure "Example message" - - ``` - [json.exception.parse_error.105] parse error: operation 'add' must have member 'value' - ``` - ``` - [json.exception.parse_error.105] parse error: operation 'copy' must have string member 'from' - ``` - ``` - [json.exception.parse_error.105] parse error: operation value 'foo' is invalid - ``` - -### json.exception.parse_error.106 - -An array index in a JSON Pointer ([RFC 6901](https://tools.ietf.org/html/rfc6901)) may be `0` or any number without a leading `0`. - -!!! failure "Example message" - - ``` - [json.exception.parse_error.106] parse error: array index '01' must not begin with '0' - ``` - -### json.exception.parse_error.107 - -A JSON Pointer must be a Unicode string containing a sequence of zero or more reference tokens, each prefixed by a `/` character. - -!!! failure "Example message" - - ``` - [json.exception.parse_error.107] parse error at byte 1: JSON pointer must be empty or begin with '/' - was: 'foo' - ``` - -### json.exception.parse_error.108 - -In a JSON Pointer, only `~0` and `~1` are valid escape sequences. - -!!! failure "Example message" - - ``` - [json.exception.parse_error.108] parse error: escape character '~' must be followed with '0' or '1' - ``` - -### json.exception.parse_error.109 - -A JSON Pointer array index must be a number. - -!!! failure "Example messages" - - ``` - [json.exception.parse_error.109] parse error: array index 'one' is not a number - ``` - ``` - [json.exception.parse_error.109] parse error: array index '+1' is not a number - ``` - -### json.exception.parse_error.110 - -When parsing CBOR or MessagePack, the byte vector ends before the complete value has been read. - -!!! failure "Example message" - - ``` - [json.exception.parse_error.110] parse error at byte 5: syntax error while parsing CBOR string: unexpected end of input - ``` - ``` - [json.exception.parse_error.110] parse error at byte 2: syntax error while parsing UBJSON value: expected end of input; last byte: 0x5A - ``` - -### json.exception.parse_error.112 - -An unexpected byte was read in a [binary format](../features/binary_formats/index.md) or length information is invalid ([BSON](../features/binary_formats/bson.md)). - -!!! failure "Example messages" - - ``` - [json.exception.parse_error.112] parse error at byte 1: syntax error while parsing CBOR value: invalid byte: 0x1C - ``` - ``` - [json.exception.parse_error.112] parse error at byte 1: syntax error while parsing MessagePack value: invalid byte: 0xC1 - ``` - ``` - [json.exception.parse_error.112] parse error at byte 4: syntax error while parsing BJData size: expected '#' after type information; last byte: 0x02 - ``` - ``` - [json.exception.parse_error.112] parse error at byte 4: syntax error while parsing UBJSON size: expected '#' after type information; last byte: 0x02 - ``` - ``` - [json.exception.parse_error.112] parse error at byte 10: syntax error while parsing BSON string: string length must be at least 1, is -2147483648 - ``` - ``` - [json.exception.parse_error.112] parse error at byte 15: syntax error while parsing BSON binary: byte array length cannot be negative, is -1 - ``` - -### json.exception.parse_error.113 - -While parsing a map key, a value that is not a string has been read. - -!!! failure "Example messages" - - ``` - [json.exception.parse_error.113] parse error at byte 2: syntax error while parsing CBOR string: expected length specification (0x60-0x7B) or indefinite string type (0x7F); last byte: 0xFF - ``` - ``` - [json.exception.parse_error.113] parse error at byte 2: syntax error while parsing MessagePack string: expected length specification (0xA0-0xBF, 0xD9-0xDB); last byte: 0xFF - ``` - ``` - [json.exception.parse_error.113] parse error at byte 2: syntax error while parsing UBJSON char: byte after 'C' must be in range 0x00..0x7F; last byte: 0x82 - ``` - -### json.exception.parse_error.114 - -The parsing of the corresponding BSON record type is not implemented (yet). - -!!! failure "Example message" - - ``` - [json.exception.parse_error.114] parse error at byte 5: Unsupported BSON record type 0xFF - ``` - -### json.exception.parse_error.115 - -A UBJSON high-precision number could not be parsed. - -!!! failure "Example message" - - ``` - [json.exception.parse_error.115] parse error at byte 5: syntax error while parsing UBJSON high-precision number: invalid number text: 1A - ``` - -## Iterator errors - -This exception is thrown if iterators passed to a library function do not match -the expected semantics. - -Exceptions have ids 2xx. - -??? example - - The following code shows how an `invalid_iterator` exception can be caught. - - ```cpp - --8<-- "examples/invalid_iterator.cpp" - ``` - - Output: - - ``` - --8<-- "examples/invalid_iterator.output" - ``` - -### json.exception.invalid_iterator.201 - -The iterators passed to constructor `basic_json(InputIT first, InputIT last)` are not compatible, meaning they do not belong to the same container. Therefore, the range (`first`, `last`) is invalid. - -!!! failure "Example message" - - ``` - [json.exception.invalid_iterator.201] iterators are not compatible - ``` - -### json.exception.invalid_iterator.202 - -In the [erase](../api/basic_json/erase.md) or insert function, the passed iterator `pos` does not belong to the JSON value for which the function was called. It hence does not define a valid position for the deletion/insertion. - -!!! failure "Example messages" - - ``` - [json.exception.invalid_iterator.202] iterator does not fit current value - ``` - ``` - [json.exception.invalid_iterator.202] iterators first and last must point to objects - ``` - -### json.exception.invalid_iterator.203 - -Either iterator passed to function [`erase(IteratorType first, IteratorType last`)](../api/basic_json/erase.md) does not belong to the JSON value from which values shall be erased. It hence does not define a valid range to delete values from. - -!!! failure "Example message" - - ``` - [json.exception.invalid_iterator.203] iterators do not fit current value - ``` - -### json.exception.invalid_iterator.204 - -When an iterator range for a primitive type (number, boolean, or string) is passed to a constructor or an [erase](../api/basic_json/erase.md) function, this range has to be exactly (`begin(),` `end()),` because this is the only way the single stored value is expressed. All other ranges are invalid. - -!!! failure "Example message" - - ``` - [json.exception.invalid_iterator.204] iterators out of range - ``` - -### json.exception.invalid_iterator.205 - -When an iterator for a primitive type (number, boolean, or string) is passed to an [erase](../api/basic_json/erase.md) function, the iterator has to be the `begin()` iterator, because it is the only way to address the stored value. All other iterators are invalid. - -!!! failure "Example message" - - ``` - [json.exception.invalid_iterator.205] iterator out of range - ``` - -### json.exception.invalid_iterator.206 - -The iterators passed to constructor `basic_json(InputIT first, InputIT last)` belong to a JSON null value and hence to not define a valid range. - -!!! failure "Example message" - - ``` - [json.exception.invalid_iterator.206] cannot construct with iterators from null - ``` - -### json.exception.invalid_iterator.207 - -The `key()` member function can only be used on iterators belonging to a JSON object, because other types do not have a concept of a key. - -!!! failure "Example message" - - ``` - [json.exception.invalid_iterator.207] cannot use key() for non-object iterators - ``` - - -### json.exception.invalid_iterator.208 - -The `operator[]` to specify a concrete offset cannot be used on iterators belonging to a JSON object, because JSON objects are unordered. - -!!! failure "Example message" - - ``` - [json.exception.invalid_iterator.208] cannot use operator[] for object iterators - ``` - -### json.exception.invalid_iterator.209 - -The offset operators (`+`, `-`, `+=`, `-=`) cannot be used on iterators belonging to a JSON object, because JSON objects are unordered. - -!!! failure "Example message" - - ``` - [json.exception.invalid_iterator.209] cannot use offsets with object iterators - ``` - -### json.exception.invalid_iterator.210 - -The iterator range passed to the insert function are not compatible, meaning they do not belong to the same container. Therefore, the range (`first`, `last`) is invalid. - -!!! failure "Example message" - - ``` - [json.exception.invalid_iterator.210] iterators do not fit - ``` - -### json.exception.invalid_iterator.211 - -The iterator range passed to the insert function must not be a subrange of the container to insert to. - -!!! failure "Example message" - - ``` - [json.exception.invalid_iterator.211] passed iterators may not belong to container - ``` - -### json.exception.invalid_iterator.212 - -When two iterators are compared, they must belong to the same container. - -!!! failure "Example message" - - ``` - [json.exception.invalid_iterator.212] cannot compare iterators of different containers - ``` - -### json.exception.invalid_iterator.213 - -The order of object iterators cannot be compared, because JSON objects are unordered. - -!!! failure "Example message" - - ``` - [json.exception.invalid_iterator.213] cannot compare order of object iterators - ``` - -### json.exception.invalid_iterator.214 - -Cannot get value for iterator: Either the iterator belongs to a null value or it is an iterator to a primitive type (number, boolean, or string), but the iterator is different to `begin()`. - -!!! failure "Example message" - - ``` - [json.exception.invalid_iterator.214] cannot get value - ``` - -## Type errors - -This exception is thrown in case of a type error; that is, a library function is executed on a JSON value whose type does not match the expected semantics. - -Exceptions have ids 3xx. - -??? example - - The following code shows how a `type_error` exception can be caught. - - ```cpp - --8<-- "examples/type_error.cpp" - ``` - - Output: - - ``` - --8<-- "examples/type_error.output" - ``` - -### json.exception.type_error.301 - -To create an object from an initializer list, the initializer list must consist only of a list of pairs whose first element is a string. When this constraint is violated, an array is created instead. - -!!! failure "Example message" - - ``` - [json.exception.type_error.301] cannot create object from initializer list - ``` - -### json.exception.type_error.302 - -During implicit or explicit value conversion, the JSON type must be compatible to the target type. For instance, a JSON string can only be converted into string types, but not into numbers or boolean types. - -!!! failure "Example messages" - - ``` - [json.exception.type_error.302] type must be object, but is null - ``` - ``` - [json.exception.type_error.302] type must be string, but is object - ``` - -### json.exception.type_error.303 - -To retrieve a reference to a value stored in a `basic_json` object with `get_ref`, the type of the reference must match the value type. For instance, for a JSON array, the `ReferenceType` must be `array_t &`. - -!!! failure "Example messages" - - ``` - [json.exception.type_error.303] incompatible ReferenceType for get_ref, actual type is object - ``` - ``` - [json.exception.type_error.303] incompatible ReferenceType for get_ref, actual type is number" - ``` - -### json.exception.type_error.304 - -The `at()` member functions can only be executed for certain JSON types. - -!!! failure "Example messages" - - ``` - [json.exception.type_error.304] cannot use at() with string - ``` - ``` - [json.exception.type_error.304] cannot use at() with number - ``` - -### json.exception.type_error.305 - -The `operator[]` member functions can only be executed for certain JSON types. - -!!! failure "Example messages" - - ``` - [json.exception.type_error.305] cannot use operator[] with a string argument with array - ``` - ``` - [json.exception.type_error.305] cannot use operator[] with a numeric argument with object - ``` - -### json.exception.type_error.306 - -The `value()` member functions can only be executed for certain JSON types. - -!!! failure "Example message" - - ``` - [json.exception.type_error.306] cannot use value() with number - ``` - -### json.exception.type_error.307 - -The [`erase()`](../api/basic_json/erase.md) member functions can only be executed for certain JSON types. - -!!! failure "Example message" - - ``` - [json.exception.type_error.307] cannot use erase() with string - ``` - -### json.exception.type_error.308 - -The `push_back()` and `operator+=` member functions can only be executed for certain JSON types. - -!!! failure "Example message" - - ``` - [json.exception.type_error.308] cannot use push_back() with string - ``` - -### json.exception.type_error.309 - -The `insert()` member functions can only be executed for certain JSON types. - -!!! failure "Example messages" - - ``` - [json.exception.type_error.309] cannot use insert() with array - ``` - ``` - [json.exception.type_error.309] cannot use insert() with number - ``` - -### json.exception.type_error.310 - -The `swap()` member functions can only be executed for certain JSON types. - -!!! failure "Example message" - - ``` - [json.exception.type_error.310] cannot use swap() with number - ``` - -### json.exception.type_error.311 - -The `emplace()` and `emplace_back()` member functions can only be executed for certain JSON types. - -!!! failure "Example messages" - - ``` - [json.exception.type_error.311] cannot use emplace() with number - ``` - ``` - [json.exception.type_error.311] cannot use emplace_back() with number - ``` - -### json.exception.type_error.312 - -The `update()` member functions can only be executed for certain JSON types. - -!!! failure "Example message" - - ``` - [json.exception.type_error.312] cannot use update() with array - ``` - -### json.exception.type_error.313 - -The `unflatten` function converts an object whose keys are JSON Pointers back into an arbitrary nested JSON value. The JSON Pointers must not overlap, because then the resulting value would not be well-defined. - -!!! failure "Example message" - - ``` - [json.exception.type_error.313] invalid value to unflatten - ``` - -### json.exception.type_error.314 - -The `unflatten` function only works for an object whose keys are JSON Pointers. - -!!! failure "Example message" - - Calling `unflatten()` on an array `#!json [1,2,3]`: - - ``` - [json.exception.type_error.314] only objects can be unflattened - ``` - -### json.exception.type_error.315 - -The `unflatten()` function only works for an object whose keys are JSON Pointers and whose values are primitive. - -!!! failure "Example message" - - Calling `unflatten()` on an object `#!json {"/1", [1,2,3]}`: - - ``` - [json.exception.type_error.315] values in object must be primitive - ``` - -### json.exception.type_error.316 - -The `dump()` function only works with UTF-8 encoded strings; that is, if you assign a `std::string` to a JSON value, make sure it is UTF-8 encoded. - -!!! failure "Example message" - - Calling `dump()` on a JSON value containing an ISO 8859-1 encoded string: - ``` - [json.exception.type_error.316] invalid UTF-8 byte at index 15: 0x6F - ``` - -!!! tip - - - Store the source file with UTF-8 encoding. - - Pass an error handler as last parameter to the `dump()` function to avoid this exception: - - `json::error_handler_t::replace` will replace invalid bytes sequences with `U+FFFD` - - `json::error_handler_t::ignore` will silently ignore invalid byte sequences - -### json.exception.type_error.317 - -The dynamic type of the object cannot be represented in the requested serialization format (e.g. a raw `true` or `null` JSON object cannot be serialized to BSON) - -!!! failure "Example messages" - - Serializing `#!json null` to BSON: - ``` - [json.exception.type_error.317] to serialize to BSON, top-level type must be object, but is null - ``` - Serializing `#!json [1,2,3]` to BSON: - ``` - [json.exception.type_error.317] to serialize to BSON, top-level type must be object, but is array - ``` - -!!! tip - - Encapsulate the JSON value in an object. That is, instead of serializing `#!json true`, serialize `#!json {"value": true}` - -## Out of range - -This exception is thrown in case a library function is called on an input parameter that exceeds the expected range, for instance in case of array indices or nonexisting object keys. - -Exceptions have ids 4xx. - -??? example - - The following code shows how an `out_of_range` exception can be caught. - - ```cpp - --8<-- "examples/out_of_range.cpp" - ``` - - Output: - - ``` - --8<-- "examples/out_of_range.output" - ``` - -### json.exception.out_of_range.401 - -The provided array index `i` is larger than `size-1`. - -!!! failure "Example message" - - ``` - array index 3 is out of range - ``` - -### json.exception.out_of_range.402 - -The special array index `-` in a JSON Pointer never describes a valid element of the array, but the index past the end. That is, it can only be used to add elements at this position, but not to read it. - -!!! failure "Example message" - - ``` - array index '-' (3) is out of range - ``` - -### json.exception.out_of_range.403 - -The provided key was not found in the JSON object. - -!!! failure "Example message" - - ``` - key 'foo' not found - ``` - -### json.exception.out_of_range.404 - -A reference token in a JSON Pointer could not be resolved. - -!!! failure "Example message" - - ``` - unresolved reference token 'foo' - ``` - -### json.exception.out_of_range.405 - -The JSON Patch operations 'remove' and 'add' can not be applied to the root element of the JSON value. - -!!! failure "Example message" - - ``` - JSON pointer has no parent - ``` - -### json.exception.out_of_range.406 - -A parsed number could not be stored as without changing it to NaN or INF. - -!!! failure "Example message" - - ``` - number overflow parsing '10E1000' - ``` - -### json.exception.out_of_range.407 - -UBJSON and BSON only support integer numbers up to 9223372036854775807. - -!!! failure "Example message" - - ``` - number overflow serializing '9223372036854775808' - ``` - -!!! note - - Since version 3.9.0, integer numbers beyond int64 are serialized as high-precision UBJSON numbers, and this exception does not further occur. - -### json.exception.out_of_range.408 - -The size (following `#`) of an UBJSON array or object exceeds the maximal capacity. - -!!! failure "Example message" - - ``` - excessive array size: 8658170730974374167 - ``` - -### json.exception.out_of_range.409 - -Key identifiers to be serialized to BSON cannot contain code point U+0000, since the key is stored as zero-terminated c-string. - -!!! failure "Example message" - - ``` - BSON key cannot contain code point U+0000 (at byte 2) - ``` - -## Further exceptions - -This exception is thrown in case of errors that cannot be classified with the -other exception types. - -Exceptions have ids 5xx. - -??? example - - The following code shows how an `other_error` exception can be caught. - - ```cpp - --8<-- "examples/other_error.cpp" - ``` - - Output: - - ``` - --8<-- "examples/other_error.output" - ``` - -### json.exception.other_error.501 - -A JSON Patch operation 'test' failed. The unsuccessful operation is also printed. - -!!! failure "Example message" - - Executing `#!json {"op":"test", "path":"/baz", "value":"bar"}` on `#!json {"baz": "qux"}`: - - ``` - [json.exception.other_error.501] unsuccessful: {"op":"test","path":"/baz","value":"bar"} - ``` diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/home/faq.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/home/faq.md deleted file mode 100644 index dd426e0..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/home/faq.md +++ /dev/null @@ -1,180 +0,0 @@ -# Frequently Asked Questions (FAQ) - -## Known bugs - -### Brace initialization yields arrays - -!!! question - - Why does - - ```cpp - json j{true}; - ``` - - and - - ```cpp - json j(true); - ``` - - yield different results (`#!json [true]` vs. `#!json true`)? - -This is a known issue, and -- even worse -- the behavior differs between GCC and Clang. The "culprit" for this is the library's constructor overloads for initializer lists to allow syntax like - -```cpp -json array = {1, 2, 3, 4}; -``` - -for arrays and - -```cpp -json object = {{"one", 1}, {"two", 2}}; -``` - -for objects. - -!!! tip - - To avoid any confusion and ensure portable code, **do not** use brace initialization with the types `basic_json`, `json`, or `ordered_json` unless you want to create an object or array as shown in the examples above. - -## Limitations - -### Relaxed parsing - -!!! question - - Can you add an option to ignore trailing commas? - -This library does not support any feature which would jeopardize interoperability. - - -### Parse errors reading non-ASCII characters - -!!! question "Questions" - - - Why is the parser complaining about a Chinese character? - - Does the library support Unicode? - - I get an exception `[json.exception.parse_error.101] parse error at line 1, column 53: syntax error while parsing value - invalid string: ill-formed UTF-8 byte; last read: '"Testé$')"` - -The library supports **Unicode input** as follows: - -- Only **UTF-8** encoded input is supported which is the default encoding for JSON according to [RFC 8259](https://tools.ietf.org/html/rfc8259.html#section-8.1). -- `std::u16string` and `std::u32string` can be parsed, assuming UTF-16 and UTF-32 encoding, respectively. These encodings are not supported when reading from files or other input containers. -- Other encodings such as Latin-1 or ISO 8859-1 are **not** supported and will yield parse or serialization errors. -- [Unicode noncharacters](http://www.unicode.org/faq/private_use.html#nonchar1) will not be replaced by the library. -- Invalid surrogates (e.g., incomplete pairs such as `\uDEAD`) will yield parse errors. -- The strings stored in the library are UTF-8 encoded. When using the default string type (`std::string`), note that its length/size functions return the number of stored bytes rather than the number of characters or glyphs. -- When you store strings with different encodings in the library, calling [`dump()`](https://nlohmann.github.io/json/classnlohmann_1_1basic__json_a50ec80b02d0f3f51130d4abb5d1cfdc5.html#a50ec80b02d0f3f51130d4abb5d1cfdc5) may throw an exception unless `json::error_handler_t::replace` or `json::error_handler_t::ignore` are used as error handlers. - -In most cases, the parser is right to complain, because the input is not UTF-8 encoded. This is especially true for Microsoft Windows where Latin-1 or ISO 8859-1 is often the standard encoding. - - -### Wide string handling - -!!! question - - Why are wide strings (e.g., `std::wstring`) dumped as arrays of numbers? - -As described [above](#parse-errors-reading-non-ascii-characters), the library assumes UTF-8 as encoding. To store a wide string, you need to change the encoding. - -!!! example - - ```cpp - #include // codecvt_utf8 - #include // wstring_convert - - // encoding function - std::string to_utf8(std::wstring& wide_string) - { - static std::wstring_convert> utf8_conv; - return utf8_conv.to_bytes(wide_string); - } - - json j; - std::wstring ws = L"車B1234 こんにちは"; - - j["original"] = ws; - j["encoded"] = to_utf8(ws); - - std::cout << j << std::endl; - ``` - - The result is: - - ```json - { - "encoded": "車B1234 こんにちは", - "original": [36554, 66, 49, 50, 51, 52, 32, 12371, 12435, 12395, 12385, 12399] - } - ``` - -## Exceptions - -### Parsing without exceptions - -!!! question - - Is it possible to indicate a parse error without throwing an exception? - -Yes, see [Parsing and exceptions](../features/parsing/parse_exceptions.md). - - -### Key name in exceptions - -!!! question - - Can I get the key of the object item that caused an exception? - -Yes, you can. Please define the symbol [`JSON_DIAGNOSTICS`](../api/macros/json_diagnostics.md) to get [extended diagnostics messages](exceptions.md#extended-diagnostic-messages). - - -## Serialization issues - - -### Number precision - -!!! question - - - It seems that precision is lost when serializing a double. - - Can I change the precision for floating-point serialization? - -The library uses `std::numeric_limits::digits10` (15 for IEEE `double`s) digits for serialization. This value is sufficient to guarantee roundtripping. If one uses more than this number of digits of precision, then string -> value -> string is not guaranteed to round-trip. - -!!! quote "[cppreference.com](https://en.cppreference.com/w/cpp/types/numeric_limits/digits10)" - - The value of `std::numeric_limits::digits10` is the number of base-10 digits that can be represented by the type T without change, that is, any number with this many significant decimal digits can be converted to a value of type T and back to decimal form, without change due to rounding or overflow. - -!!! tip - - The website https://float.exposed gives a good insight into the internal storage of floating-point numbers. - -See [this section](../features/types/number_handling.md#number-serialization) on the library's number handling for more information. - -## Compilation issues - -### Android SDK - -!!! question - - Why does the code not compile with Android SDK? - -Android defaults to using very old compilers and C++ libraries. To fix this, add the following to your `Application.mk`. This will switch to the LLVM C++ library, the Clang compiler, and enable C++11 and other features disabled by default. - -```ini -APP_STL := c++_shared -NDK_TOOLCHAIN_VERSION := clang3.6 -APP_CPPFLAGS += -frtti -fexceptions -``` - -The code compiles successfully with [Android NDK](https://developer.android.com/ndk/index.html?hl=ml), Revision 9 - 11 (and possibly later) and [CrystaX's Android NDK](https://www.crystax.net/en/android/ndk) version 10. - - -### Missing STL function - -!!! question "Questions" - - - Why do I get a compilation error `'to_string' is not a member of 'std'` (or similarly, for `strtod` or `strtof`)? - - Why does the code not compile with MinGW or Android SDK? - -This is not an issue with the code, but rather with the compiler itself. On Android, see above to build with a newer environment. For MinGW, please refer to [this site](http://tehsausage.com/mingw-to-string) and [this discussion](https://github.com/nlohmann/json/issues/136) for information on how to fix this bug. For Android NDK using `APP_STL := gnustl_static`, please refer to [this discussion](https://github.com/nlohmann/json/issues/219). diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/home/license.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/home/license.md deleted file mode 100644 index baef2f5..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/home/license.md +++ /dev/null @@ -1,21 +0,0 @@ -# License - - - -The class is licensed under the [MIT License](https://opensource.org/licenses/MIT): - -Copyright © 2013-2022 [Niels Lohmann](https://nlohmann.me) - -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. - -* * * - -The class contains the UTF-8 Decoder from Bjoern Hoehrmann which is licensed under the [MIT License](https://opensource.org/licenses/MIT) (see above). Copyright © 2008-2009 [Björn Hoehrmann](http://bjoern.hoehrmann.de/) - -The class contains a slightly modified version of the Grisu2 algorithm from Florian Loitsch which is licensed under the [MIT License](https://opensource.org/licenses/MIT) (see above). Copyright © 2009 [Florian Loitsch](https://florian.loitsch.com/) - -The class contains a copy of [Hedley](https://nemequ.github.io/hedley/) from Evan Nemerson which is licensed as [CC0-1.0](https://creativecommons.org/publicdomain/zero/1.0/). diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/home/releases.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/home/releases.md deleted file mode 100644 index 5237c42..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/home/releases.md +++ /dev/null @@ -1,1225 +0,0 @@ -# Releases - -## v3.7.3 - -!!! summary "Files" - - - [include.zip](https://github.com/nlohmann/json/releases/download/v3.7.3/include.zip) (274 KB) - - [include.zip.asc](https://github.com/nlohmann/json/releases/download/v3.7.3/include.zip.asc) (1 KB) - - [json.hpp](https://github.com/nlohmann/json/releases/download/v3.7.3/json.hpp) (791 KB) - - [json.hpp.asc](https://github.com/nlohmann/json/releases/download/v3.7.3/json.hpp.asc) (1 KB) - -Release date: 2019-11-17 -SHA-256: 3b5d2b8f8282b80557091514d8ab97e27f9574336c804ee666fda673a9b59926 (json.hpp), 87b5884741427220d3a33df1363ae0e8b898099fbc59f1c451113f6732891014 (include.zip) - -### Summary - -This release fixes a bug introduced in release 3.7.2 which could yield quadratic complexity in destructor calls. All changes are backward-compatible. - -### :bug: Bug Fixes - -- Removed `reserve()` calls from the destructor which could lead to quadratic complexity. #1837 #1838 - -### :fire: Deprecated functions - -This release does not deprecate any functions. As an overview, the following functions have been deprecated in earlier versions and will be removed in the next major version (i.e., 4.0.0): - -- Function [`iterator_wrapper`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_af1592a06bc63811886ade4f9d965045e.html#af1592a06bc63811886ade4f9d965045e) are deprecated. Please use the member function [`items()`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_afe3e137ace692efa08590d8df40f58dd.html#afe3e137ace692efa08590d8df40f58dd) instead. -- Functions [`friend std::istream& operator<<(basic_json&, std::istream&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_ab7285a92514fcdbe6de505ebaba92ea3.html#ab7285a92514fcdbe6de505ebaba92ea3) and [`friend std::ostream& operator>>(const basic_json&, std::ostream&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a9e06deabe69262c3ffc5533d32856983.html#a9e06deabe69262c3ffc5533d32856983) are deprecated. Please use [`friend std::istream& operator>>(std::istream&, basic_json&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_aaf363408931d76472ded14017e59c9e8.html#aaf363408931d76472ded14017e59c9e8) and [`friend operator<<(std::ostream&, const basic_json&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a5e34c5435e557d0bf666bd7311211405.html#a5e34c5435e557d0bf666bd7311211405) instead. - - -## v3.7.2 - -!!! summary "Files" - - - [include.zip](https://github.com/nlohmann/json/releases/download/v3.7.2/include.zip) (274 KB) - - [include.zip.asc](https://github.com/nlohmann/json/releases/download/v3.7.2/include.zip.asc) (1 KB) - - [json.hpp](https://github.com/nlohmann/json/releases/download/v3.7.2/json.hpp) (791 KB) - - [json.hpp.asc](https://github.com/nlohmann/json/releases/download/v3.7.2/json.hpp.asc) (1 KB) - -Release date: 2019-11-10 -SHA-256: 0a65fcbbe1b334d3f45c9498e5ee28c3f3b2428aea98557da4a3ff12f0f14ad6 (json.hpp), 67f69c9a93b7fa0612dc1b6273119d2c560317333581845f358aaa68bff8f087 (include.zip) - -### Summary - -Project [bad_json_parsers](https://github.com/lovasoa/bad_json_parsers) tested how JSON parser libraries react on **deeply nested inputs**. It turns out that this library segfaulted at a certain nesting depth. This bug was fixed with this release. **Now the parsing is only bounded by the available memory.** All changes are backward-compatible. - -### :bug: Bug Fixes - -* Fixed a bug that lead to stack overflow for deeply nested JSON values (objects, array) by changing the implementation of the destructor from a recursive to an iterative approach. #832, #1419, #1835 - -### :hammer: Further Changes - -* Added WhiteStone Bolt. #1830 - -### :fire: Deprecated functions - -This release does not deprecate any functions. As an overview, the following functions have been deprecated in earlier versions and will be removed in the next major version (i.e., 4.0.0): - -- Function [`iterator_wrapper`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_af1592a06bc63811886ade4f9d965045e.html#af1592a06bc63811886ade4f9d965045e) are deprecated. Please use the member function [`items()`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_afe3e137ace692efa08590d8df40f58dd.html#afe3e137ace692efa08590d8df40f58dd) instead. -- Functions [`friend std::istream& operator<<(basic_json&, std::istream&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_ab7285a92514fcdbe6de505ebaba92ea3.html#ab7285a92514fcdbe6de505ebaba92ea3) and [`friend std::ostream& operator>>(const basic_json&, std::ostream&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a9e06deabe69262c3ffc5533d32856983.html#a9e06deabe69262c3ffc5533d32856983) are deprecated. Please use [`friend std::istream& operator>>(std::istream&, basic_json&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_aaf363408931d76472ded14017e59c9e8.html#aaf363408931d76472ded14017e59c9e8) and [`friend operator<<(std::ostream&, const basic_json&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a5e34c5435e557d0bf666bd7311211405.html#a5e34c5435e557d0bf666bd7311211405) instead. - -## v3.7.1 - -!!! summary "Files" - - - [include.zip](https://github.com/nlohmann/json/releases/download/v3.7.1/include.zip) (273 KB) - - [include.zip.asc](https://github.com/nlohmann/json/releases/download/v3.7.1/include.zip.asc) (1 KB) - - [json.hpp](https://github.com/nlohmann/json/releases/download/v3.7.1/json.hpp) (789 KB) - - [json.hpp.asc](https://github.com/nlohmann/json/releases/download/v3.7.1/json.hpp.asc) (1 KB) - -Release date: 2019-11-06 -SHA-256: b5ba7228f3c22a882d379e93d08eab4349458ee16fbf45291347994eac7dc7ce (json.hpp), 77b9f54b34e7989e6f402afb516f7ff2830df551c3a36973085e2c7a6b1045fe (include.zip) - -### Summary - -This release fixes several small bugs in the library. All changes are backward-compatible. - -### :bug: Bug Fixes - -- Fixed a segmentation fault when serializing `std::int64_t` minimum value. #1708 #1722 -- Fixed the [`contains()`](https://nlohmann.github.io/json/classnlohmann_1_1basic__json_ab23b04802eb9da97dc3f664e54e09cb3.html#ab23b04802eb9da97dc3f664e54e09cb3) function for JSON Pointers. #1727 #1741 -- Fixed too lax SFINAE guard for conversion from `std::pair` and `std::tuple` to `json`. #1805 #1806 #1825 #1826 -- Fixed some regressions detected by UBSAN. Updated CI to use Clang-Tidy 7.1.0. #1716 #1728 -- Fixed integer truncation in `iteration_proxy`. #1797 -- Updated [Hedley](https://github.com/nemequ/hedley) to v11 to [fix a E2512 error](https://github.com/nemequ/hedley/issues/28) in MSVC. #1799 -- Fixed a compile error in enum deserialization of non non-default-constructible types. #1647 #1821 -- Fixed the conversion from `json` to `std::valarray`. - -### :zap: Improvements - -- The [`items()`](https://nlohmann.github.io/json/classnlohmann_1_1basic__json_afe3e137ace692efa08590d8df40f58dd.html#afe3e137ace692efa08590d8df40f58dd) function can now be used with a custom string type. #1765 -- Made [`json_pointer::back`](https://nlohmann.github.io/json/classnlohmann_1_1json__pointer_a213bc67c32a30c68ac6bf06f5195d482.html#a213bc67c32a30c68ac6bf06f5195d482) `const`. #1764 #1769 -- Meson is part of the release archive. #1672 #1694 -- Improved documentation on the Meson and Spack package manager. #1694 #1720 - -### :hammer: Further Changes - -- Added GitHub Workflow with `ubuntu-latest`/GCC 7.4.0 as CI step. -- Added GCC 9 to Travis CI to compile with C++20 support. #1724 -- Added MSVC 2019 to the AppVeyor CI. #1780 -- Added badge to [fuzzing status](https://bugs.chromium.org/p/oss-fuzz/issues/list?sort=-opened&can=1&q=proj:json). -- Fixed some cppcheck warnings. #1760 -- Fixed several typos in the documentation. #1720 #1767 #1803 -- Added documentation on the `JSON_THROW_USER`, `JSON_TRY_USER`, and `JSON_CATCH_USER` macros to control user-defined exception handling. -- Used GitHub's [CODEOWNERS](https://github.com/nlohmann/json/blob/develop/.github/CODEOWNERS) and [SECURITY](https://github.com/nlohmann/json/blob/develop/.github/SECURITY.md) feature. -- Removed `GLOB` from CMake files. #1779 -- Updated to [Doctest](https://github.com/onqtam/doctest) 2.3.5. - -### :fire: Deprecated functions - -This release does not deprecate any functions. As an overview, the following functions have been deprecated in earlier versions and will be removed in the next major version (i.e., 4.0.0): - -- Function [`iterator_wrapper`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_af1592a06bc63811886ade4f9d965045e.html#af1592a06bc63811886ade4f9d965045e) are deprecated. Please use the member function [`items()`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_afe3e137ace692efa08590d8df40f58dd.html#afe3e137ace692efa08590d8df40f58dd) instead. -- Functions [`friend std::istream& operator<<(basic_json&, std::istream&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_ab7285a92514fcdbe6de505ebaba92ea3.html#ab7285a92514fcdbe6de505ebaba92ea3) and [`friend std::ostream& operator>>(const basic_json&, std::ostream&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a9e06deabe69262c3ffc5533d32856983.html#a9e06deabe69262c3ffc5533d32856983) are deprecated. Please use [`friend std::istream& operator>>(std::istream&, basic_json&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_aaf363408931d76472ded14017e59c9e8.html#aaf363408931d76472ded14017e59c9e8) and [`friend operator<<(std::ostream&, const basic_json&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a5e34c5435e557d0bf666bd7311211405.html#a5e34c5435e557d0bf666bd7311211405) instead. - -## v3.7.0 - -!!! summary "Files" - - - [include.zip](https://github.com/nlohmann/json/releases/download/v3.7.0/include.zip) (143 KB) - - [include.zip.asc](https://github.com/nlohmann/json/releases/download/v3.7.0/include.zip.asc) (1 KB) - - [json.hpp](https://github.com/nlohmann/json/releases/download/v3.7.0/json.hpp) (782 KB) - - [json.hpp.asc](https://github.com/nlohmann/json/releases/download/v3.7.0/json.hpp.asc) (1 KB) - -Release date: 2019-07-28 -SHA-256: a503214947952b69f0062f572cb74c17582a495767446347ce2e452963fc2ca4 (json.hpp), 541c34438fd54182e9cdc68dd20c898d766713ad6d901fb2c6e28ff1f1e7c10d (include.zip) - -### Summary - -This release introduces a few convenience functions and performs a lot of house keeping (bug fixes and small improvements). All changes are backward-compatible. - -### :sparkles: New Features - -- Add overload of the **[`contains`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_ab23b04802eb9da97dc3f664e54e09cb3.html#ab23b04802eb9da97dc3f664e54e09cb3) function** to check if a JSON pointer is valid without throwing exceptions, just like its [counterpart for object keys](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a9286acdc0578fc66e9346323e69fc0e3.html#a9286acdc0578fc66e9346323e69fc0e3). #1600 -- Add a function **[`to_string`](http://nlohmann.github.io/json/doxygen/namespacenlohmann_a6ce645a0b8717757e096a5b5773b7a16.html#a6ce645a0b8717757e096a5b5773b7a16)** to allow for generic conversion to strings. #916 #1585 -- Add **return value for the [`emplace_back`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_abf29131f898b05aad2c01a9c80e7a002.html#abf29131f898b05aad2c01a9c80e7a002) function**, returning a reference to the added element just like C++17 is [introducing this](https://en.cppreference.com/w/cpp/container/vector/emplace_back) for `std::vector`. #1609 -- Add info how to use the library with the **[pacman](https://wiki.archlinux.org/index.php/pacman) package manager** on MSYS2. #1670 - -### :bug: Bug Fixes - -- Fix an issue where typedefs with certain names yielded a compilation error. #1642 #1643 -- Fix a conversion to `std::string_view` in the unit tests. #1634 #1639 -- Fix MSVC Debug build. #1536 #1570 #1608 -- Fix [`get_to`](https://nlohmann.github.io/json/classnlohmann_1_1basic__json_a65753c68f06639eda0d355f919564e01.html#a65753c68f06639eda0d355f919564e01) method to clear existing content before writing. #1511 #1555 -- Fix a `-Wc++17-extensions` warning. `nodiscard` attributes are now only used with Clang when `-std=c++17` is used. #1535 #1551 - -### :zap: Improvements - -- Switch from [Catch](https://github.com/philsquared/Catch) to **[doctest](https://github.com/onqtam/doctest)** for the unit tests which speeds up compilation and runtime of the 112,112,308 tests. -- Add an explicit section to the [README](https://github.com/nlohmann/json/blob/develop/README.md) about the **frequently addressed topics** [character encoding](https://github.com/nlohmann/json#character-encoding), [comments in JSON](https://github.com/nlohmann/json#comments-in-json), and the [order of object keys](https://github.com/nlohmann/json#order-of-object-keys). - -### :hammer: Further Changes - -- Use [`GNUInstallDirs`](https://cmake.org/cmake/help/v3.0/module/GNUInstallDirs.html) to set library install directories. #1673 -- Fix links in the [README](https://github.com/nlohmann/json/blob/develop/README.md). #1620 #1621 #1622 #1623 #1625 -- Mention [`json` type](http://nlohmann.github.io/json/doxygen/namespacenlohmann_a2bfd99e845a2e5cd90aeaf1b1431f474.html#a2bfd99e845a2e5cd90aeaf1b1431f474) on the [documentation start page](http://nlohmann.github.io/json/doxygen/index.html). #1616 -- Complete documentation of [`value()` function](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_adcf8ca5079f5db993820bf50036bf45d.html#adcf8ca5079f5db993820bf50036bf45d) with respect to `type_error.302` exception. #1601 -- Fix links in the documentation. #1598 -- Add regression tests for MSVC. #1543 #1570 -- Use **[CircleCI](http://circleci.com)** for [continuous integration](https://circleci.com/gh/nlohmann/json). -- Use **[Doozer](https://doozer.io)** for [continuous integration](https://doozer.io/nlohmann/json) on Linux (CentOS, Raspbian, Fedora) -- Add tests to check each CMake flag (`JSON_BuildTests`, `JSON_Install`, `JSON_MultipleHeaders`, `JSON_Sanitizer`, `JSON_Valgrind`, `JSON_NoExceptions`, `JSON_Coverage`). -- Use [Hedley](https://nemequ.github.io/hedley/) to avoid re-inventing several compiler-agnostic feature macros like `JSON_DEPRECATED`, `JSON_NODISCARD`, `JSON_LIKELY`, `JSON_UNLIKELY`, `JSON_HAS_CPP_14`, or `JSON_HAS_CPP_17`. Functions taking or returning pointers are annotated accordingly when a pointer will not be null. -- Build and run tests on [AppVeyor](https://ci.appveyor.com/project/nlohmann/json) in DEBUG and RELEASE mode. - -### :fire: Deprecated functions - -This release does not deprecate any functions. As an overview, the following functions have been deprecated in earlier versions and will be removed in the next major version (i.e., 4.0.0): - -- Function [`iterator_wrapper`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_af1592a06bc63811886ade4f9d965045e.html#af1592a06bc63811886ade4f9d965045e) are deprecated. Please use the member function [`items()`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_afe3e137ace692efa08590d8df40f58dd.html#afe3e137ace692efa08590d8df40f58dd) instead. -- Functions [`friend std::istream& operator<<(basic_json&, std::istream&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_ab7285a92514fcdbe6de505ebaba92ea3.html#ab7285a92514fcdbe6de505ebaba92ea3) and [`friend std::ostream& operator>>(const basic_json&, std::ostream&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a9e06deabe69262c3ffc5533d32856983.html#a9e06deabe69262c3ffc5533d32856983) are deprecated. Please use [`friend std::istream& operator>>(std::istream&, basic_json&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_aaf363408931d76472ded14017e59c9e8.html#aaf363408931d76472ded14017e59c9e8) and [`friend operator<<(std::ostream&, const basic_json&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a5e34c5435e557d0bf666bd7311211405.html#a5e34c5435e557d0bf666bd7311211405) instead. - -## v3.6.1 - -!!! summary "Files" - - - [include.zip](https://github.com/nlohmann/json/releases/download/v3.6.1/include.zip) (136 KB) - - [include.zip.asc](https://github.com/nlohmann/json/releases/download/v3.6.1/include.zip.asc) (1 KB) - - [json.hpp](https://github.com/nlohmann/json/releases/download/v3.6.1/json.hpp) (711 KB) - - [json.hpp.asc](https://github.com/nlohmann/json/releases/download/v3.6.1/json.hpp.asc) (1 KB) - -Release date: 2019-03-20 -SHA-256: d2eeb25d2e95bffeb08ebb7704cdffd2e8fca7113eba9a0b38d60a5c391ea09a (json.hpp), 69cc88207ce91347ea530b227ff0776db82dcb8de6704e1a3d74f4841bc651cf (include.zip) - -### Summary - -This release **fixes a regression and a bug** introduced by the earlier 3.6.0 release. All changes are backward-compatible. - -### :bug: Bug Fixes - -- Fixed regression of #590 which could lead to compilation errors with GCC 7 and GCC 8. #1530 -- Fixed a compilation error when `` was included. #1531 - -### :hammer: Further Changes - -- Fixed a warning for missing field initializers. #1527 - -### :fire: Deprecated functions - -This release does not deprecate any functions. As an overview, the following functions have been deprecated in earlier versions and will be removed in the next major version (i.e., 4.0.0): - -- Function [`iterator_wrapper`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_af1592a06bc63811886ade4f9d965045e.html#af1592a06bc63811886ade4f9d965045e) are deprecated. Please use the member function [`items()`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_afe3e137ace692efa08590d8df40f58dd.html#afe3e137ace692efa08590d8df40f58dd) instead. -- Functions [`friend std::istream& operator<<(basic_json&, std::istream&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_ab7285a92514fcdbe6de505ebaba92ea3.html#ab7285a92514fcdbe6de505ebaba92ea3) and [`friend std::ostream& operator>>(const basic_json&, std::ostream&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a9e06deabe69262c3ffc5533d32856983.html#a9e06deabe69262c3ffc5533d32856983) are deprecated. Please use [`friend std::istream& operator>>(std::istream&, basic_json&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_aaf363408931d76472ded14017e59c9e8.html#aaf363408931d76472ded14017e59c9e8) and [`friend operator<<(std::ostream&, const basic_json&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a5e34c5435e557d0bf666bd7311211405.html#a5e34c5435e557d0bf666bd7311211405) instead. - -## v3.6.0 - -!!! summary "Files" - - - [include.zip](https://github.com/nlohmann/json/releases/download/v3.6.0/include.zip) (136 KB) - - [include.zip.asc](https://github.com/nlohmann/json/releases/download/v3.6.0/include.zip.asc) (1 KB) - - [json.hpp](https://github.com/nlohmann/json/releases/download/v3.6.0/json.hpp) (711 KB) - - [json.hpp.asc](https://github.com/nlohmann/json/releases/download/v3.6.0/json.hpp.asc) (1 KB) - -Release date: 2019-03-20 -SHA-256: ce9839370f28094c71107c405affb3b08c4a098154988014cbb0800b1c44a831 (json.hpp), 237c5e66e7f8186a02804ce9dbd5f69ce89fe7424ef84adf6142e973bd9532f4 (include.zip) - -ℹ️ **This release introduced a regression. Please update to [version 3.6.1](https://github.com/nlohmann/json/releases/tag/v3.6.1)!** - -### Summary - -This release adds some **convenience functions for JSON Pointers**, introduces a [`contains`]( -http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a0a45fc740637123fdf05fef970f8be47.html#a0a45fc740637123fdf05fef970f8be47) function to check if a key is present in an object, and improves the **performance of integer serialization**. Furthermore, a lot of small bug fixes and improvements have been made. All changes are backward-compatible. - -### :sparkles: New Features - -- Overworked the public interface for JSON Pointers. The creation of JSON Pointers is simplified with [`operator/`]( -http://nlohmann.github.io/json/doxygen/classnlohmann_1_1json__pointer_a90a11fe6c7f37b1746a3ff9cb24b0d53.html#a90a11fe6c7f37b1746a3ff9cb24b0d53) and [`operator/=`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1json__pointer_a7395bd0af29ac23fd3f21543c935cdfa.html#a7395bd0af29ac23fd3f21543c935cdfa). JSON Pointers can be inspected with [`empty`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1json__pointer_a649252bda4a2e75a0915b11a25d8bcc3.html#a649252bda4a2e75a0915b11a25d8bcc3), [`back`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1json__pointer_a6bd5b554c10f15672135c216893eef31.html#a6bd5b554c10f15672135c216893eef31), and [`parent_pointer`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1json__pointer_afdaacce1edb7145e0434e014f0e8685a.html#afdaacce1edb7145e0434e014f0e8685a), and manipulated with [`push_back`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1json__pointer_a697d12b5bd6205f8866691b166b7c7dc.html#a697d12b5bd6205f8866691b166b7c7dc) and [`pop_back`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1json__pointer_a4b1ee4d511ca195bed896a3da47e264c.html#a4b1ee4d511ca195bed896a3da47e264c). #1434 -- Added a boolean method [`contains`]( -http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a0a45fc740637123fdf05fef970f8be47.html#a0a45fc740637123fdf05fef970f8be47) to check whether an element exists in a JSON object with a given key. Returns false when called on non-object types. #1471 #1474 - -### :bug: Bug Fixes - -- Fixed a compilation issues with libc 2.12. #1483 #1514 -- Fixed endian conversion on PPC64. #1489 -- Fixed library to compile with GCC 9. #1472 #1492 -- Fixed a compilation issue with GCC 7 on CentOS. #1496 -- Fixed an integer overflow. #1447 -- Fixed buffer flushing in serializer. #1445 #1446 - -### :zap: Improvements - -- The performance of dumping integers has been greatly improved. #1411 -- Added CMake parameter `JSON_Install` to control whether the library should be installed (default: on). #1330 -- Fixed a lot of compiler and linter warnings. #1400 #1435 #1502 -- Reduced required CMake version from 3.8 to 3.1. #1409 #1428 #1441 #1498 -- Added `nodiscard` attribute to `meta()`, `array()`, `object()`, `from_cbor`, `from_msgpack`, `from_ubjson`, `from_bson`, and `parse`. #1433 - -### :hammer: Further Changes - -- Added missing headers. #1500 -- Fixed typos and broken links in README. #1417 #1423 #1425 #1451 #1455 #1491 -- Fixed documentation of parse function. #1473 -- Suppressed warning that cannot be fixed inside the library. #1401 #1468 -- Imroved package manager suppert: - - Updated Buckaroo instructions. #1495 - - Improved Meson support. #1463 - - Added Conda package manager documentation. #1430 - - Added NuGet package manager documentation. #1132 -- Continuous Integration - - Removed unstable or deprecated Travis builders (Xcode 6.4 - 8.2) and added Xcode 10.1 builder. - - Added Clang 7 to Travis CI. - - Fixed AppVeyor x64 builds. #1374 #1414 -- Updated thirdparty libraries: - - Catch 1.12.0 -> 1.12.2 - - Google Benchmark 1.3.0 -> 1.4.1 - - Doxygen 1.8.15 -> 1.8.16 - -### :fire: Deprecated functions - -This release does not deprecate any functions. As an overview, the following functions have been deprecated in earlier versions and will be removed in the next major version (i.e., 4.0.0): - -- Function [`iterator_wrapper`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_af1592a06bc63811886ade4f9d965045e.html#af1592a06bc63811886ade4f9d965045e) are deprecated. Please use the member function [`items()`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_afe3e137ace692efa08590d8df40f58dd.html#afe3e137ace692efa08590d8df40f58dd) instead. -- Functions [`friend std::istream& operator<<(basic_json&, std::istream&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_ab7285a92514fcdbe6de505ebaba92ea3.html#ab7285a92514fcdbe6de505ebaba92ea3) and [`friend std::ostream& operator>>(const basic_json&, std::ostream&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a9e06deabe69262c3ffc5533d32856983.html#a9e06deabe69262c3ffc5533d32856983) are deprecated. Please use [`friend std::istream& operator>>(std::istream&, basic_json&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_aaf363408931d76472ded14017e59c9e8.html#aaf363408931d76472ded14017e59c9e8) and [`friend operator<<(std::ostream&, const basic_json&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a5e34c5435e557d0bf666bd7311211405.html#a5e34c5435e557d0bf666bd7311211405) instead. - -## v3.5.0 - -!!! summary "Files" - - - [include.zip](https://github.com/nlohmann/json/releases/download/v3.5.0/include.zip) (133 KB) - - [include.zip.asc](https://github.com/nlohmann/json/releases/download/v3.5.0/include.zip.asc) (1 KB) - - [json.hpp](https://github.com/nlohmann/json/releases/download/v3.5.0/json.hpp) (693 KB) - - [json.hpp.asc](https://github.com/nlohmann/json/releases/download/v3.5.0/json.hpp.asc) (1 KB) - -Release date: 2018-12-22 -SHA-256: 8a6dbf3bf01156f438d0ca7e78c2971bca50eec4ca6f0cf59adf3464c43bb9d5 (json.hpp), 3564da9c5b0cf2e032f97c69baedf10ddbc98030c337d0327a215ea72259ea21 (include.zip) - -### Summary - -This release introduces the support for **structured bindings** and reading from **`FILE*`**. Besides, a few bugs have been fixed. All changes are backward-compatible. - -### :sparkles: New Features - -- **Structured bindings** are now supported for JSON objects and arrays via the [`items()`](https://nlohmann.github.io/json/classnlohmann_1_1basic__json_afe3e137ace692efa08590d8df40f58dd.html#afe3e137ace692efa08590d8df40f58dd) member function, so finally this code is possible: - ```cpp - for (auto& [key, val] : j.items()) { - std::cout << key << ':' << val << '\n'; - } - ``` - #1388 #1391 - -- Added support for **reading from `FILE*`** to support situations in which streams are nit available or would require too much RAM. #1370 #1392 - -### :bug: Bug Fixes - -- The `eofbit` was not set for input streams when the end of a stream was reached while parsing. #1340 #1343 -- Fixed a bug in the SAX parser for BSON arrays. - -### :zap: Improvements - -- Added support for Clang 5.0.1 (PS4 version). #1341 #1342 - -### :hammer: Further Changes - -- Added a warning for implicit conversions to the documentation: It is not recommended to use implicit conversions when reading **from** a JSON value. Details about this recommendation can be found [here](https://www.github.com/nlohmann/json/issues/958). #1363 -- Fixed typos in the documentation. #1329 #1380 #1382 -- Fixed a C4800 warning. #1364 -- Fixed a `-Wshadow` warning #1346 -- Wrapped `std::snprintf` calls to avoid error in MSVC. #1337 -- Added code to allow installation via Meson. #1345 - -### :fire: Deprecated functions - -This release does not deprecate any functions. As an overview, the following functions have been deprecated in earlier versions and will be removed in the next major version (i.e., 4.0.0): - -- Function [`iterator_wrapper`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_af1592a06bc63811886ade4f9d965045e.html#af1592a06bc63811886ade4f9d965045e) are deprecated. Please use the member function [`items()`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_afe3e137ace692efa08590d8df40f58dd.html#afe3e137ace692efa08590d8df40f58dd) instead. -- Functions [`friend std::istream& operator<<(basic_json&, std::istream&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_ab7285a92514fcdbe6de505ebaba92ea3.html#ab7285a92514fcdbe6de505ebaba92ea3) and [`friend std::ostream& operator>>(const basic_json&, std::ostream&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a9e06deabe69262c3ffc5533d32856983.html#a9e06deabe69262c3ffc5533d32856983) are deprecated. Please use [`friend std::istream& operator>>(std::istream&, basic_json&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_aaf363408931d76472ded14017e59c9e8.html#aaf363408931d76472ded14017e59c9e8) and [`friend operator<<(std::ostream&, const basic_json&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a5e34c5435e557d0bf666bd7311211405.html#a5e34c5435e557d0bf666bd7311211405) instead. - -## v3.4.0 - -!!! summary "Files" - - - [include.zip](https://github.com/nlohmann/json/releases/download/v3.4.0/include.zip) (132 KB) - - [include.zip.asc](https://github.com/nlohmann/json/releases/download/v3.4.0/include.zip.asc) (1 KB) - - [json.hpp](https://github.com/nlohmann/json/releases/download/v3.4.0/json.hpp) (689 KB) - - [json.hpp.asc](https://github.com/nlohmann/json/releases/download/v3.4.0/json.hpp.asc) (1 KB) - -Release date: 2018-10-30 -SHA-256: 63da6d1f22b2a7bb9e4ff7d6b255cf691a161ff49532dcc45d398a53e295835f (json.hpp), bfec46fc0cee01c509cf064d2254517e7fa80d1e7647fea37cf81d97c5682bdc (include.zip) - -### Summary - -This release introduces three new features: - -- **BSON (Binary JSON)** is next to CBOR, MessagePack, and UBJSON the fourth binary (de)serialization format supported by the library. -- **Adjustable error handlers for invalid Unicode** allows to specify the behavior when invalid byte sequences are serialized. -- **Simplified enum/JSON mapping** with a macro in case the default mapping to integers is not desired. - -Furthermore, some effort has been invested in improving the **parse error messages**. Besides, a few bugs have been fixed. All changes are backward-compatible. - -### :sparkles: New Features - -- The library can read and write a subset of **[BSON](http://bsonspec.org/) (Binary JSON)**. All data types known from JSON are supported, whereas other types more tied to MongoDB such as timestamps, object ids, or binary data are currently not implemented. See [the README](https://github.com/nlohmann/json#binary-formats-bson-cbor-messagepack-and-ubjson) for examples. #1244 #1320 -- The behavior when the library encounters an invalid Unicode sequence during serialization can now be controlled by defining one of three **Unicode error handlers**: (1) throw an exception (default behavior), (2) replace invalid sequences by the Unicode replacement character (U+FFFD), or (3) ignore/filter invalid sequences. See the [documentation of the `dump` function](https://nlohmann.github.io/json/classnlohmann_1_1basic__json_a50ec80b02d0f3f51130d4abb5d1cfdc5.html#a50ec80b02d0f3f51130d4abb5d1cfdc5) for examples. #1198 #1314 -- To easily specify a user-defined **enum/JSON mapping**, a macro `NLOHMANN_JSON_SERIALIZE_ENUM` has been introduced. See the [README section](https://github.com/nlohmann/json#specializing-enum-conversion) for more information. #1208 #1323 - -### :bug: Bug Fixes - -- fixed truncation #1286 #1315 -- fixed an issue with std::pair #1299 #1301 -- fixed an issue with std::variant #1292 #1294 -- fixed a bug in the JSON Pointer parser - -### :zap: Improvements - -- The **diagnosis messages for parse errors** have been improved: error messages now indicated line/column positions where possible (in addition to a byte count) and also the context in which the error occurred (e.g., "while parsing a JSON string"). Example: error `parse error at 2: syntax error - invalid string: control character must be escaped; last read: ''` is now reported as `parse error at line 1, column 2: syntax error while parsing value - invalid string: control character U+0009 (HT) must be escaped to \u0009 or \t; last read: ''`. #1280 #1288 #1303 - -### :hammer: Further Changes - -- improved Meson documentation #1305 -- fixed some more linter warnings #1280 -- fixed Clang detection for third-party Google Benchmark library #1277 - -### :fire: Deprecated functions - -This release does not deprecate any functions. As an overview, the following functions have been deprecated in earlier versions and will be removed in the next major version (i.e., 4.0.0): - -- Function [`iterator_wrapper`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_af1592a06bc63811886ade4f9d965045e.html#af1592a06bc63811886ade4f9d965045e) are deprecated. Please use the member function [`items()`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_afe3e137ace692efa08590d8df40f58dd.html#afe3e137ace692efa08590d8df40f58dd) instead. -- Functions [`friend std::istream& operator<<(basic_json&, std::istream&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_ab7285a92514fcdbe6de505ebaba92ea3.html#ab7285a92514fcdbe6de505ebaba92ea3) and [`friend std::ostream& operator>>(const basic_json&, std::ostream&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a9e06deabe69262c3ffc5533d32856983.html#a9e06deabe69262c3ffc5533d32856983) are deprecated. Please use [`friend std::istream& operator>>(std::istream&, basic_json&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_aaf363408931d76472ded14017e59c9e8.html#aaf363408931d76472ded14017e59c9e8) and [`friend operator<<(std::ostream&, const basic_json&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a5e34c5435e557d0bf666bd7311211405.html#a5e34c5435e557d0bf666bd7311211405) instead. - -## v3.3.0 - -!!! summary "Files" - - - [include.zip](https://github.com/nlohmann/json/releases/download/v3.3.0/include.zip) (123 KB) - - [include.zip.asc](https://github.com/nlohmann/json/releases/download/v3.3.0/include.zip.asc) (1 KB) - - [json.hpp](https://github.com/nlohmann/json/releases/download/v3.3.0/json.hpp) (635 KB) - - [json.hpp.asc](https://github.com/nlohmann/json/releases/download/v3.3.0/json.hpp.asc) (1 KB) - -Release date: 2018-10-05 -SHA-256: f1327bb60c58757a3dd2b0c9c45d49503d571337681d950ec621f8374bcc14d4 (json.hpp), 9588d63557333aaa485e92221ec38014a85a6134e7486fe3441e0541a5a89576 (include.zip) - -### Summary - -This release adds support for **GCC 4.8**. Furthermore, it adds a function [**`get_to`**](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a8a3db7d78f74232d3a6fb8f1abf69709.html#a8a3db7d78f74232d3a6fb8f1abf69709) to write a JSON value to a passed reference. Another topic of this release was the **CMake support** which has been overworked and documented. - -Besides, a lot of bugs have been fixed and slight improvements have been made. All changes are backward-compatible. - -### :sparkles: New Features - -- The library can now also built with **GCC 4.8**. Though this compiler does not fully support C++11, it can successfully compile and run the test suite. Note that bug [57824](https://gcc.gnu.org/bugzilla/show_bug.cgi?id=57824) in GCC 4.8 still forbids to use multiline raw strings in arguments to macros. #1257 -- Added new function [**`get_to`**](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a8a3db7d78f74232d3a6fb8f1abf69709.html#a8a3db7d78f74232d3a6fb8f1abf69709) to write a JSON value to a passed reference. The destination type is automatically derived which allows more succinct code compared to the `get` function. #1227 #1231 - -### :bug: Bug Fixes - -- Fixed a bug in the CMake file that made `target_link_libraries` to not properly include `nlohmann_json`. #1243 #1245 #1260 -- Fixed a warning in MSVC 2017 complaining about a constexpr if. #1204 #1268 #1272 -- Fixed a bug that prevented compilation with ICPC. #755 #1222 -- Improved the SFINAE correctness to fix a bug in the conversion operator. #1237 #1238 -- Fixed a `-Wctor-dtor-privacy` warning. #1224 -- Fixed a warning on a lambda in unevaluated context. #1225 #1230 -- Fixed a bug introduced in version 3.2.0 where defining `JSON_CATCH_USER` led to duplicate macro definition of `JSON_INTERNAL_CATCH`. #1213 #1214 -- Fixed a bug that prevented compilation with Clang 3.4.2 in RHEL 7. #1179 #1249 - -### :zap: Improvements - -- Added [documentation on CMake integration](https://github.com/nlohmann/json#cmake) of the library. #1270 -- Changed the CMake file to use `find_package(nlohmann_json)` without installing the library. #1202 -- Improved error messages in case `operator[]` is used with the wrong combination (json.exception.type_error.305) of JSON container type and argument type. Example: "cannot use operator[] with a string argument". #1220 #1221 -- Added a license and version information to the Meson build file. #1252 -- Removed static assertions to indicated missing `to_json` or `from_json` functions as such assertions do not play well with SFINAE. These assertions also led to problems with GMock. #960 #1212 #1228 -- The test suite now does not wait forever if run in a wrong directory and input files are not found. #1262 -- The test suite does not show deprecation warnings for deprecated functions which frequently led to confusion. #1271 - -### :hammer: Further Changes - -- GCC 4.8 and Xcode 10 were added to the [continuous integration suite](https://travis-ci.org/nlohmann/json) at Travis. -- Added [lgtm](https://lgtm.com/projects/g/nlohmann/json/context:cpp) checks to pull requests. -- Added tests for CMake integration. #1260 - -### :fire: Deprecated functions - -This release does not deprecate any functions. As an overview, the following functions have been deprecated in earlier versions and will be removed in the next major version (i.e., 4.0.0): - -- Function [`iterator_wrapper`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_af1592a06bc63811886ade4f9d965045e.html#af1592a06bc63811886ade4f9d965045e) are deprecated. Please use the member function [`items()`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_afe3e137ace692efa08590d8df40f58dd.html#afe3e137ace692efa08590d8df40f58dd) instead. -- Functions [`friend std::istream& operator<<(basic_json&, std::istream&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_ab7285a92514fcdbe6de505ebaba92ea3.html#ab7285a92514fcdbe6de505ebaba92ea3) and [`friend std::ostream& operator>>(const basic_json&, std::ostream&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a9e06deabe69262c3ffc5533d32856983.html#a9e06deabe69262c3ffc5533d32856983) are deprecated. Please use [`friend std::istream& operator>>(std::istream&, basic_json&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_aaf363408931d76472ded14017e59c9e8.html#aaf363408931d76472ded14017e59c9e8) and [`friend operator<<(std::ostream&, const basic_json&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a5e34c5435e557d0bf666bd7311211405.html#a5e34c5435e557d0bf666bd7311211405) instead. - - -## v3.2.0 - -!!! summary "Files" - - - [include.zip](https://github.com/nlohmann/json/releases/download/v3.2.0/include.zip) (124 KB) - - [include.zip.asc](https://github.com/nlohmann/json/releases/download/v3.2.0/include.zip.asc) (1 KB) - - [json.hpp](https://github.com/nlohmann/json/releases/download/v3.2.0/json.hpp) (636 KB) - - [json.hpp.asc](https://github.com/nlohmann/json/releases/download/v3.2.0/json.hpp.asc) (1 KB) - -Release date: 2018-08-20 -SHA-256: ce6b5610a051ec6795fa11c33854abebb086f0fd67c311f5921c3c07f9531b44 (json.hpp), 35ee642558b90e2f9bc758995c4788c4b4d4dec54eef95fb8f38cb4d49c8fc7c (include.zip) - -### Summary - -This release introduces a [**SAX interface**](https://nlohmann.github.io/json/structnlohmann_1_1json__sax.html) to the library. While this may be a very special feature used by only few people, it allowed to unify all functions that consumed input and created some kind of JSON value. Internally, now all existing functions like `parse`, `accept`, `from_cbor`, `from_msgpack`, and `from_ubjson` use the SAX interface with different event processors. This allowed to separate the input processing from the value generation. Furthermore, throwing an exception in case of a parse error is now optional and up to the event processor. Finally, the JSON parser is now non-recursive (meaning it does not use the call stack, but `std::vector` to track the hierarchy of structured values) which allows to process nested input more efficiently. - -Furthermore, the library finally is able to parse from **wide string types**. This is the first step toward opening the library from UTF-8 to UTF-16 and UTF-32. - -This release further fixes several bugs in the library. All changes are backward-compatible. - -### :sparkles: New Features - -- added a parser with a **SAX interface** (#971, #1153) -- support to parse from **wide string types** `std::wstring`, `std::u16string`, and `std::u32string`; the input will be converted to UTF-8 (#1031) -- added support for **`std::string_view`** when using C++17 (#1028) -- allow to **roundtrip `std::map` and `std::unordered_map`** from JSON if key type is not convertible to string; in these cases, values are serialized to arrays of pairs (#1079, #1089, #1133, #1138) - -### :bug: Bug Fixes - -- allow to create `nullptr_t` from JSON allowing to properly roundtrip `null` values (#1169) -- allow compare user-defined string types (#1130) -- better support for algorithms using iterators from `items()` (#1045, #1134) -- added parameter to avoid compilation error with MSVC 2015 debug builds (#1114) -- re-added accidentally skipped unit tests (#1176) -- fixed MSVC issue with `std::swap` (#1168) - -### :zap: Improvements - -- `key()` function for iterators returns a const reference rather than a string copy (#1098) -- binary formats CBOR, MessagePack, and UBJSON now supports `float` as type for floating-point numbers (#1021) - -### :hammer: Further Changes - -- changed issue templates -- improved continuous integration: added builders for Xcode 9.3 and 9.4, added builders for GCC 8 and Clang 6, added builder for MinGW, added builders for MSVC targeting x86 -- required CMake version is now at least 3.8 (#1040) -- overworked CMake file wrt. packaging (#1048) -- added package managers: Spack (#1041) and CocoaPods (#1148) -- fixed Meson include directory (#1142) -- preprocessor macro `JSON_SKIP_UNSUPPORTED_COMPILER_CHECK` can skip the rejection of unsupported compilers - use at your own risk! (#1128) -- preprocessor macro `JSON_INTERNAL_CATCH`/`JSON_INTERNAL_CATCH_USER` allows to control the behavior of exception handling inside the library (#1187) -- added note on `char` to JSON conversion -- added note how to send security-related issue via encrypted email -- removed dependency to `std::stringstream` (#1117) -- added SPDX-License-Identifier -- added updated JSON Parsing Test Suite, described in [Parsing JSON is a Minefield 💣](http://seriot.ch/parsing_json.php) -- updated to Catch 1.12.0 - -### :fire: Deprecated functions - -This release does not deprecate any functions. As an overview, the following functions have been deprecated in earlier versions and will be removed in the next major version (i.e., 4.0.0): - -- Function [`iterator_wrapper`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_af1592a06bc63811886ade4f9d965045e.html#af1592a06bc63811886ade4f9d965045e) are deprecated. Please use the member function [`items()`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_afe3e137ace692efa08590d8df40f58dd.html#afe3e137ace692efa08590d8df40f58dd) instead. -- Functions [`friend std::istream& operator<<(basic_json&, std::istream&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_ab7285a92514fcdbe6de505ebaba92ea3.html#ab7285a92514fcdbe6de505ebaba92ea3) and [`friend std::ostream& operator>>(const basic_json&, std::ostream&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a9e06deabe69262c3ffc5533d32856983.html#a9e06deabe69262c3ffc5533d32856983) are deprecated. Please use [`friend std::istream& operator>>(std::istream&, basic_json&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_aaf363408931d76472ded14017e59c9e8.html#aaf363408931d76472ded14017e59c9e8) and [`friend operator<<(std::ostream&, const basic_json&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a5e34c5435e557d0bf666bd7311211405.html#a5e34c5435e557d0bf666bd7311211405) instead. - - - -## v3.1.2 - -!!! summary "Files" - - - [include.zip](https://github.com/nlohmann/json/releases/download/v3.1.2/include.zip) (115 KB) - - [include.zip.asc](https://github.com/nlohmann/json/releases/download/v3.1.2/include.zip.asc) (1 KB) - - [json.hpp](https://github.com/nlohmann/json/releases/download/v3.1.2/json.hpp) (582 KB) - - [json.hpp.asc](https://github.com/nlohmann/json/releases/download/v3.1.2/json.hpp.asc) (1 KB) - -Release date: 2018-03-14 -SHA-256: fbdfec4b4cf63b3b565d09f87e6c3c183bdd45c5be1864d3fcb338f6f02c1733 (json.hpp), 495362ee1b9d03d9526ba9ccf1b4a9c37691abe3a642ddbced13e5778c16660c (include.zip) - -### Summary - -This release fixes several bugs in the library. All changes are backward-compatible. - -### :bug: Bug Fixes - -- Fixed a **memory leak** occurring in the parser callback (#1001). -- Different **specializations of `basic_json`** (e.g., using different template arguments for strings or objects) can now be used in assignments (#972, #977, #986). -- Fixed a logical error in an iterator range check (#992). - -### :zap: Improvements - -- The parser and the serialization now support **user-defined string types** (#1006, #1009). - -### :hammer: Further Changes - -- **[Clang Analyzer](http://clang-analyzer.llvm.org)** is now used as additional static analyzer; see `make clang_analyze`. -- Overworked [README](https://github.com/nlohmann/json/blob/develop/README.md) by adding links to the [documentation](https://nlohmann.github.io/json/) (#981). - -### :fire: Deprecated functions - -This release does not deprecate any functions. As an overview, the following functions have been deprecated in earlier versions and will be removed in the next major version (i.e., 4.0.0): - -- Function [`iterator_wrapper`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_af1592a06bc63811886ade4f9d965045e.html#af1592a06bc63811886ade4f9d965045e) are deprecated. Please use the member function [`items()`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_afe3e137ace692efa08590d8df40f58dd.html#afe3e137ace692efa08590d8df40f58dd) instead. -- Functions [`friend std::istream& operator<<(basic_json&, std::istream&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_ab7285a92514fcdbe6de505ebaba92ea3.html#ab7285a92514fcdbe6de505ebaba92ea3) and [`friend std::ostream& operator>>(const basic_json&, std::ostream&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a9e06deabe69262c3ffc5533d32856983.html#a9e06deabe69262c3ffc5533d32856983) are deprecated. Please use [`friend std::istream& operator>>(std::istream&, basic_json&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_aaf363408931d76472ded14017e59c9e8.html#aaf363408931d76472ded14017e59c9e8) and [`friend operator<<(std::ostream&, const basic_json&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a5e34c5435e557d0bf666bd7311211405.html#a5e34c5435e557d0bf666bd7311211405) instead. - - -## v3.1.1 - -!!! summary "Files" - - - [include.zip](https://github.com/nlohmann/json/releases/download/v3.1.1/include.zip) (114 KB) - - [include.zip.asc](https://github.com/nlohmann/json/releases/download/v3.1.1/include.zip.asc) (1 KB) - - [json.hpp](https://github.com/nlohmann/json/releases/download/v3.1.1/json.hpp) (577 KB) - - [json.hpp.asc](https://github.com/nlohmann/json/releases/download/v3.1.1/json.hpp.asc) (1 KB) - -Release date: 2018-02-13 -SHA-256: e14ce5e33d6a2daf748026bd4947f3d9686ca4cfd53d10c3da46a0a9aceb7f2e (json.hpp), fde771d4b9e4f222965c00758a2bdd627d04fb7b59e09b7f3d1965abdc848505 (include.zip) - -### Summary - -This release fixes several bugs in the library. All changes are backward-compatible. - -### :bug: Bug Fixes - -- Fixed parsing of **CBOR strings with indefinite length** (#961). Earlier versions of this library misinterpreted the CBOR standard and rejected input with the `0x7F` start byte. -- Fixed user-defined **conversion to vector type** (#924, #969). A wrong SFINAE check rejected code though a user-defined conversion was provided. -- Fixed documentation of the parser behavior for **objects with duplicate keys** (#963). The exact behavior is not specified by [RFC 8259](https://tools.ietf.org/html/rfc8259) and the library now also provides no guarantee which object key is stored. -- Added check to detect memory **overflow when parsing UBJSON containers** (#962). The optimized UBJSON format allowed for specifying an array with billions of `null` elements with a few bytes and the library did not check whether this size exceeded `max_size()`. - -### :hammer: Further Changes - -- [Code coverage](https://coveralls.io/github/nlohmann/json) is now calculated for the individual header files, allowing to find uncovered lines more quickly than by browsing through the single header version (#953, #957). -- A Makefile target `run_benchmarks` was added to quickly build and run the benchmark suite. -- The documentation was harmonized with respect to the header inclusion (#955). Now all examples and the README use `#include ` to allow for selecting `single_include` or `include` or whatever installation folder as include directory. -- Added note on how to use the library with the [cget](http://cget.readthedocs.io/en/latest/) package manager (#954). - -### :fire: Deprecated functions - -This release does not deprecate any functions. As an overview, the following functions have been deprecated in earlier versions and will be removed in the next major version (i.e., 4.0.0): - -- Function [`iterator_wrapper`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_af1592a06bc63811886ade4f9d965045e.html#af1592a06bc63811886ade4f9d965045e) are deprecated. Please use the member function [`items()`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_afe3e137ace692efa08590d8df40f58dd.html#afe3e137ace692efa08590d8df40f58dd) instead. -- Functions [`friend std::istream& operator<<(basic_json&, std::istream&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_ab7285a92514fcdbe6de505ebaba92ea3.html#ab7285a92514fcdbe6de505ebaba92ea3) and [`friend std::ostream& operator>>(const basic_json&, std::ostream&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a9e06deabe69262c3ffc5533d32856983.html#a9e06deabe69262c3ffc5533d32856983) are deprecated. Please use [`friend std::istream& operator>>(std::istream&, basic_json&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_aaf363408931d76472ded14017e59c9e8.html#aaf363408931d76472ded14017e59c9e8) and [`friend operator<<(std::ostream&, const basic_json&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a5e34c5435e557d0bf666bd7311211405.html#a5e34c5435e557d0bf666bd7311211405) instead. - -## v3.1.0 - -!!! summary "Files" - - - [include.zip](https://github.com/nlohmann/json/releases/download/v3.1.0/include.zip) (114 KB) - - [include.zip.asc](https://github.com/nlohmann/json/releases/download/v3.1.0/include.zip.asc) (1 KB) - - [json.hpp](https://github.com/nlohmann/json/releases/download/v3.1.0/json.hpp) (577 KB) - - [json.hpp.asc](https://github.com/nlohmann/json/releases/download/v3.1.0/json.hpp.asc) (1 KB) - -Release date: 2018-02-01 -SHA-256: d40f614d10a6e4e4e80dca9463da905285f20e93116c36d97d4dc1aa63d10ba4 (json.hpp), 2b7234fca394d1e27b7e017117ed80b7518fafbb4f4c13a7c069624f6f924673 (include.zip) - -### Summary - -This release adds support for the [**UBJSON**](http://ubjson.org) format and [**JSON Merge Patch**](https://tools.ietf.org/html/rfc7386). It also contains some minor changes and bug fixes. All changes are backward-compatible. - -### :sparkles: New features - -- The library now supports [**UBJSON**](http://ubjson.org) (Universal Binary JSON Specification) as binary format to read and write JSON values space-efficiently. See the [documentation overview](https://github.com/nlohmann/json/blob/develop/doc/binary_formats.md) for a comparison of the different formats CBOR, MessagePack, and UBJSON. -- [**JSON Merge Patch**](https://tools.ietf.org/html/rfc7386) (RFC 7386) offers an intuitive means to describe patches between JSON values (#876, #877). See the documentation of [`merge_patch`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a0ec0cd19cce42ae6071f3cc6870ea295.html#a0ec0cd19cce42ae6071f3cc6870ea295) for more information. - -### :zap: Improvements - -- The library now uses the **Grisu2 algorithm** for printing floating-point numbers (based on the reference implementation by Florian Loitsch) which produces a short representation which is guaranteed to round-trip (#360, #935, #936). -- The **UTF-8 handling** was further simplified by using the decoder of Björn Hoehrmann in more scenarios. - -### :truck: Reorganization - -- Though the library is released as a single header, its development got more and more complicated. With this release, the header is **split into several files** and the single-header file `json.hpp` can be generated from these development sources. In the repository, folder `include` contains the development sources and `single_include` contains the single `json.hpp` header (#700, #906, #907, #910, #911, #915, #920, #924, #925, #928, #944). -- The split further allowed for a **forward declaration header** `include/nlohmann/json_fwd.hpp` to speed up compilation times (#314). - -### :hammer: Further changes - -- [Google Benchmark](https://github.com/google/benchmark) is now used for micro benchmarks (see `benchmarks` folder, #921). -- The serialization (JSON and binary formats) now properly work with the libraries string template parameter, allowing for optimized string implementations to be used in constraint environments such as embedded software (#941, #950). -- The exceptional behavior can now be overridden by defining macros `JSON_THROW_USER`, `JSON_TRY_USER`, and `JSON_CATCH_USER`, defining the behavior of `throw`, `try` and `catch`, respectively. This allows to switch off C++'s exception mechanism yet still execute user-defined code in case an error condition occurs (#938). -- To facilitate the interplay with [flex](https://github.com/westes/flex) and [Bison](https://www.gnu.org/software/bison/), the library does not use the variable name `yytext` any more as it could clash with macro definitions (#933). -- The library now defines `NLOHMANN_JSON_VERSION_MAJOR`, `NLOHMANN_JSON_VERSION_MINOR`, and `NLOHMANN_JSON_VERSION_PATCH` to allow for conditional compilation based on the included library version (#943, #948). -- A compilation error with ICC has been fixed (#947). -- Typos and links in the documentation have been fixed (#900, #930). -- A compiler error related to incomplete types has been fixed (#919). -- The tests form the [UTF-8 decoder stress test](http://www.cl.cam.ac.uk/~mgk25/ucs/examples/UTF-8-test.txt) have been added to the test suite. - -### :fire: Deprecated functions - -- Function [`iterator_wrapper`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_af1592a06bc63811886ade4f9d965045e.html#af1592a06bc63811886ade4f9d965045e) has been deprecated (#874). Since its introduction, the name was up for discussion, as it was too technical. We now introduced the member function [`items()`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_afe3e137ace692efa08590d8df40f58dd.html#afe3e137ace692efa08590d8df40f58dd) with the same semantics. `iterator_wrapper` will be removed in the next major version (i.e., 4.0.0). - -Furthermore, the following functions are deprecated since version 3.0.0 and will be removed in the next major version (i.e., 4.0.0): - -- [`friend std::istream& operator<<(basic_json&, std::istream&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_ab7285a92514fcdbe6de505ebaba92ea3.html#ab7285a92514fcdbe6de505ebaba92ea3) -- [`friend std::ostream& operator>>(const basic_json&, std::ostream&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a9e06deabe69262c3ffc5533d32856983.html#a9e06deabe69262c3ffc5533d32856983) - -Please use [`friend std::istream& operator>>(std::istream&, basic_json&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_aaf363408931d76472ded14017e59c9e8.html#aaf363408931d76472ded14017e59c9e8) and [`friend operator<<(std::ostream&, const basic_json&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a5e34c5435e557d0bf666bd7311211405.html#a5e34c5435e557d0bf666bd7311211405) instead. - -## v3.0.1 - -!!! summary "Files" - - - [json.hpp](https://github.com/nlohmann/json/releases/download/v3.0.1/json.hpp) (502 KB) - - [json.hpp.asc](https://github.com/nlohmann/json/releases/download/v3.0.1/json.hpp.asc) (1 KB) - -Release date: 2017-12-29 -SHA-256: c9b3591f1bb94e723a0cd7be861733a3a555b234ef132be1e9027a0364118c4c - -### Summary - -This release fixes small issues in the implementation of **JSON Pointer** and **JSON Patch**. All changes are backward-compatible. - -### Changes - -- :bug: The **"copy" operation of JSON Patch** ([RFC 6902](https://tools.ietf.org/html/rfc6902)) requests that it is an error if the target path points into a non-existing array or object (see #894 for a detailed description). This release fixes the implementation to detect such invalid target paths and throw an exception. -- :bug: An **array index in a JSON Pointer** ([RFC 6901](https://tools.ietf.org/html/rfc6901)) must be an integer. This release fixes the implementation to throw an exception in case invalid array indices such as `10e2` are used. -- :white_check_mark: Added the [JSON Patch tests](https://github.com/json-patch/json-patch-tests) from Byron Ruth and Mike McCabe. -- :memo: Fixed the documentation of the [`at(ptr)` function with JSON Pointers](https://nlohmann.github.io/json/classnlohmann_1_1basic__json_a8ab61397c10f18b305520da7073b2b45.html#a8ab61397c10f18b305520da7073b2b45) to list all possible exceptions (see #888). -- :memo: Updated the [container overview documentation](https://nlohmann.github.io/json/) (see #883). -- :wrench: The CMake files now respect the [`BUILD_TESTING`](https://cmake.org/cmake/help/latest/module/CTest.html?highlight=build_testing) option (see #846, #885) -- :rotating_light: Fixed some compiler warnings (see #858, #882). - -### Deprecated functions - -:fire: To unify the interfaces and to improve similarity with the STL, the following functions are deprecated since version 3.0.0 and will be removed in the next major version (i.e., 4.0.0): - -- [`friend std::istream& operator<<(basic_json&, std::istream&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_ab7285a92514fcdbe6de505ebaba92ea3.html#ab7285a92514fcdbe6de505ebaba92ea3) -- [`friend std::ostream& operator>>(const basic_json&, std::ostream&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a9e06deabe69262c3ffc5533d32856983.html#a9e06deabe69262c3ffc5533d32856983) - -Please use [`friend std::istream& operator>>(std::istream&, basic_json&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_aaf363408931d76472ded14017e59c9e8.html#aaf363408931d76472ded14017e59c9e8) and [`friend operator<<(std::ostream&, const basic_json&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a5e34c5435e557d0bf666bd7311211405.html#a5e34c5435e557d0bf666bd7311211405) instead. - -## v3.0.0 - -!!! summary "Files" - - - [json.hpp](https://github.com/nlohmann/json/releases/download/v3.0.0/json.hpp) (501 KB) - - [json.hpp.asc](https://github.com/nlohmann/json/releases/download/v3.0.0/json.hpp.asc) (1 KB) - -Release date: 2017-12-17 -SHA-256: 076d4a0cb890a3c3d389c68421a11c3d77c64bd788e85d50f1b77ed252f2a462 - -### Summary - - - -After almost a year, here is finally a new release of JSON for Modern C++, and it is a major one! As we adhere to [semantic versioning](https://semver.org), this means the release includes some breaking changes, so please read the next section carefully before you update. But don't worry, we also added a few new features and put a lot of effort into fixing a lot of bugs and straighten out a few inconsistencies. - -### :boom: Breaking changes - -This section describes changes that change the public API of the library and may require changes in code using a previous version of the library. In section "Moving from 2.x.x to 3.0.0" at the end of the release notes, we describe in detail how existing code needs to be changed. - -- The library now uses [**user-defined exceptions**](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a9a0aced019cb1d65bb49703406c84970.html#a9a0aced019cb1d65bb49703406c84970) instead of re-using those defined in `` (#244). This not only allows to add more information to the exceptions (every exception now has an identifier, and parse errors contain the position of the error), but also to easily catch all library exceptions with a single `catch(json::exception)`. -- When strings with a different encoding as UTF-8 were stored in JSON values, their serialization could not be parsed by the library itself, as only UTF-8 is supported. To enforce this library limitation and improve consistency, **non-UTF-8 encoded strings now yield a `json::type_error` exception during serialization** (#838). The check for valid UTF-8 is realized with code from [Björn Hoehrmann](http://bjoern.hoehrmann.de/). -- **NaN and infinity values can now be stored inside the JSON value** without throwing an exception. They are, however, still serialized as `null` (#388). -- The library's iterator tag was changed from RandomAccessIterator to **[BidirectionalIterator](http://en.cppreference.com/w/cpp/concept/BidirectionalIterator)** (#593). Supporting RandomAccessIterator was incorrect as it assumed an ordering of values in a JSON objects which are unordered by definition. -- The library does not include the standard headers ``, ``, and `` any more. You may need to add these headers to code relying on them. -- Removed constructor `explicit basic_json(std::istream& i, const parser_callback_t cb = nullptr)` which was deprecated in version 2.0.0 (#480). - -### :fire: Deprecated functions - -To unify the interfaces and to improve similarity with the STL, the following functions are now deprecated and will be removed in the next major version (i.e., 4.0.0): - -- [`friend std::istream& operator<<(basic_json&, std::istream&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_ab7285a92514fcdbe6de505ebaba92ea3.html#ab7285a92514fcdbe6de505ebaba92ea3) -- [`friend std::ostream& operator>>(const basic_json&, std::ostream&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a9e06deabe69262c3ffc5533d32856983.html#a9e06deabe69262c3ffc5533d32856983) - -Please use [`friend std::istream& operator>>(std::istream&, basic_json&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_aaf363408931d76472ded14017e59c9e8.html#aaf363408931d76472ded14017e59c9e8) and [`friend operator<<(std::ostream&, const basic_json&)`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a5e34c5435e557d0bf666bd7311211405.html#a5e34c5435e557d0bf666bd7311211405) instead. - -### :sparkles: New features - -With all this breaking and deprecation out of the way, let's talk about features! - -- We improved the **diagnostic information for syntax errors** (#301). Now, an exception [`json::parse_error`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_af1efc2468e6022be6e35fc2944cabe4d.html#af1efc2468e6022be6e35fc2944cabe4d) is thrown which contains a detailed message on the error, but also a member `byte` to indicate the byte offset in the input where the error occurred. -- We added a **non-throwing syntax check** (#458): The new `accept` function returns a Boolean indicating whether the input is proper JSON. We also added a Boolean parameter `allow_exceptions` to the existing [`parse`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_aa9676414f2e36383c4b181fe856aa3c0.html#aa9676414f2e36383c4b181fe856aa3c0) functions to return a `discarded` value in case a syntax error occurs instead of throwing an exception. -- An [`update`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a1cfa9ae5e7c2434cab4cfe69bffffe11.html#a1cfa9ae5e7c2434cab4cfe69bffffe11) function was added to **merge two JSON objects** (#428). In case you are wondering: the name was inspired by [Python](https://docs.python.org/2/library/stdtypes.html#dict.update). -- The [`insert`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a1b0a4e60d56f1fe80501ed941e122892.html#a1b0a4e60d56f1fe80501ed941e122892) function now also supports an iterator range to add elements to an object. -- The binary exchange formats **CBOR and MessagePack can now be parsed from input streams and written to output streams** (#477). -- Input streams are now only read until the end of a JSON value instead of the end of the input (#367). -- The serialization function [`dump`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a5adea76fedba9898d404fef8598aa663.html#a5adea76fedba9898d404fef8598aa663) now has two optional parameters `ensure_ascii` to **escape all non-ASCII characters** with `\uxxxx` and an `indent_char` parameter to choose whether to **indent with spaces or tabs** (#654). -- Added **built-in type support** for C arrays (#502), `std::pair` and `std::tuple` (#563, #614), `enum` and `enum class` (#545), `std::vector` (#494). Fixed support for `std::valarray` (#702), `std::array` (#553), and `std::map` (#600, #607). - -### :hammer: Further changes - -Furthermore, there have been a lot of changes under the hood: - -- Replaced the [re2c](http://re2c.org) generated scanner by a self-coded version which allows for a better modularization of the parser and better diagnostics. To test the new scanner, we added millions (8,860,608 to be exact) of unit tests to check all valid and invalid byte sequences of the Unicode standard. -- Google's OSS-Fuzz is still constantly fuzz-testing the library and found several issues that were fixed in this release (#497, #504, #514, #516, #518, #519, #575). -- We now also ignore UTF-8 byte order marks when parsing from an iterator range (#602). -- Values can be now moved from initializer lists (#663). -- Updated to [Catch](https://github.com/catchorg/Catch2) 1.9.7. Unfortunately, Catch2 currently has some performance issues. -- The non-exceptional paths of the library are now annotated with `__builtin_expect` to optimize branch prediction as long as no error occurs. -- MSVC now produces a stack trace in MSVC if a `from_json` or `to_json` function was not found for a user-defined type. We also added a debug visualizer [`nlohmann_json.natvis`](https://github.com/nlohmann/json/blob/develop/nlohmann_json.natvis) for better debugging in MSVC (#844). -- Overworked the documentation and added even more examples. -- The build workflow now relies on CMake and CTest. Special flags can be chosen with CMake, including coverage (`JSON_Coverage`), compilation without exceptions (`JSON_NoExceptions`), LLVM sanitizers (`JSON_Sanitizer`), or execution with Valgrind (`JSON_Valgrind`). -- Added support for package managers Meson (#576), Conan (#566), Hunter (#671, #829), and vcpkg (#753). -- Added CI builders: Xcode 8.3, 9.0, 9.1, and 9.2; GCC 7.2; Clang 3.8, 3.9, 4.0, and 5.0; Visual Studio 2017. The library is further built with C++17 settings on the latest Clang, GCC, and MSVC version to quickly detect new issues. - -### Moving from 2.x.x to 3.0.0 - -#### User-defined Exceptions - -There are five different exceptions inheriting from [`json::exception`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a9a0aced019cb1d65bb49703406c84970.html#a9a0aced019cb1d65bb49703406c84970): - -- [`json::parse_error`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_af1efc2468e6022be6e35fc2944cabe4d.html#af1efc2468e6022be6e35fc2944cabe4d) for syntax errors (including the binary formats), -- [`json::invalid_iterator`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_ac13d32f7cbd02d616e71d8dc30dadcbf.html#ac13d32f7cbd02d616e71d8dc30dadcbf) for errors related to iterators, -- [`json::type_error`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a4010e8e268fefd86da773c10318f2902.html#a4010e8e268fefd86da773c10318f2902) for errors where functions were called with the wrong JSON type, -- [`json::out_of_range`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a28f7c2f087274a0012eb7a2333ee1580.html#a28f7c2f087274a0012eb7a2333ee1580) for range errors, and -- [`json::other_error`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a3333a5a8714912adda33a35b369f7b3d.html#a3333a5a8714912adda33a35b369f7b3d) for miscellaneous errors. - -To support these exception, the `try`/`catch` blocks of your code need to be adjusted: - -| new exception | previous exception | -|:--|:--| -| parse_error.101 | invalid_argument | -| parse_error.102 | invalid_argument | -| parse_error.103 | invalid_argument | -| parse_error.104 | invalid_argument | -| parse_error.105 | invalid_argument | -| parse_error.106 | domain_error | -| parse_error.107 | domain_error | -| parse_error.108 | domain_error | -| parse_error.109 | invalid_argument | -| parse_error.110 | out_of_range | -| parse_error.111 | invalid_argument | -| parse_error.112 | invalid_argument | -| invalid_iterator.201 | domain_error | -| invalid_iterator.202 | domain_error | -| invalid_iterator.203 | domain_error | -| invalid_iterator.204 | out_of_range | -| invalid_iterator.205 | out_of_range | -| invalid_iterator.206 | domain_error | -| invalid_iterator.207 | domain_error | -| invalid_iterator.208 | domain_error | -| invalid_iterator.209 | domain_error | -| invalid_iterator.210 | domain_error | -| invalid_iterator.211 | domain_error | -| invalid_iterator.212 | domain_error | -| invalid_iterator.213 | domain_error | -| invalid_iterator.214 | out_of_range | -| type_error.301 | domain_error | -| type_error.302 | domain_error | -| type_error.303 | domain_error | -| type_error.304 | domain_error | -| type_error.305 | domain_error | -| type_error.306 | domain_error | -| type_error.307 | domain_error | -| type_error.308 | domain_error | -| type_error.309 | domain_error | -| type_error.310 | domain_error | -| type_error.311 | domain_error | -| type_error.313 | domain_error | -| type_error.314 | domain_error | -| type_error.315 | domain_error | -| out_of_range.401 | out_of_range | -| out_of_range.402 | out_of_range | -| out_of_range.403 | out_of_range | -| out_of_range.404 | out_of_range | -| out_of_range.405 | domain_error | -| other_error.501 | domain_error | - -#### Handling of NaN and INF - -- If an overflow occurs during parsing a number from a JSON text, an exception [`json::out_of_range`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a28f7c2f087274a0012eb7a2333ee1580.html#a28f7c2f087274a0012eb7a2333ee1580) is thrown so that the overflow is detected early and roundtripping is guaranteed. - -- NaN and INF floating-point values can be stored in a JSON value and are not replaced by null. That is, the basic_json class behaves like `double` in this regard (no exception occurs). However, NaN and INF are serialized to `null`. - -#### Removal of deprecated functions - -Function `explicit basic_json(std::istream& i, const parser_callback_t cb = nullptr)` should be replaced by the `parse` function: Let `ss` be a stream and `cb` be a parse callback function. - -Old code: - -```cpp -json j(ss, cb); -``` - -New code: - -```cpp -json j = json::parse(ss, cb); -``` - -If no callback function is used, also the following code works: - -```cpp -json j; -j << ss; -``` - -or - -```cpp -json j; -ss >> j; -``` - -## v2.1.1 - -!!! summary "Files" - - - [json.hpp](https://github.com/nlohmann/json/releases/download/v2.1.1/json.hpp) (437 KB) - - [json.hpp.asc](https://github.com/nlohmann/json/releases/download/v2.1.1/json.hpp.asc) (1 KB) - -Release date: 2017-02-25 -SHA-256: faa2321beb1aa7416d035e7417fcfa59692ac3d8c202728f9bcc302e2d558f57 - -### Summary - -This release **fixes a locale-related bug in the parser**. To do so, the whole number handling (lexer, parser, and also the serialization) have been overworked. Furthermore, a lot of small changes added up that were added to this release. All changes are backward-compatible. - -### Changes -- :bug: Locales that have a different character than `.` as decimal separator (e.g., the Norwegian locale `nb_NO.UTF-8`) led to truncated number parsing or parse errors. The library now has been fixed to work with **any locale**. Note that `.` is still the only valid decimal separator for JSON input. -- :bug: Numbers like `1.0` were correctly parsed as floating-point number, but serialized as integer (`1`). Now, **floating-point numbers correctly round trip**. -- :bug: Parsing incorrect JSON numbers with leading 0 (`0123`) could yield a [buffer overflow](https://github.com/nlohmann/json/issues/452). This is fixed now by detecting such errors directly by the lexer. -- :bug: Constructing a JSON value from a pointer was incorrectly interpreted as a Boolean; such code will now yield a compiler error. -- :bug: Comparing a JSON number with `0` led to a comparison with `null`. This is fixed now. -- :bug: All throw calls are now wrapped in macros. -- :lock: Starting during the preparation of this release (since 8 February 2017), commits and released files are **cryptographically signed** with [this GPG key](https://keybase.io/nlohmann/pgp_keys.asc?fingerprint=797167ae41c0a6d9232e48457f3cea63ae251b69). Previous releases have also been signed. -- :sparkles: The parser for MessagePack and CBOR now supports an optional start index parameter to define a byte offset for the parser. -- :rotating_light: Some more warnings have been fixed. With Clang, the code compiles **without warnings** with `-Weverything` (well, it needs `-Wno-documentation-unknown-command` and `-Wno-deprecated-declarations`, but you get the point). -- :hammer: The code can be compiled easier with many Android NDKs by avoiding macros like `UINT8_MAX` which previously required defining a preprocessor macro for compilation. -- :zap: The unit tests now compile two times faster. -- :heavy_plus_sign: [Cotire](https://github.com/sakra/cotire) is used to speed up the build. -- :pencil2: Fixed a lot of typos in the documentation. -- :memo: Added a section to the README file that lists all used [third-party code/tools](https://github.com/nlohmann/json#used-third-party-tools). -- :memo: Added a note on constructing a string value vs. parsing. -- :white_check_mark: The test suite now contains 11202597 unit tests. -- :memo: Improved the [Doxygen documentation](https://nlohmann.github.io/json/) by shortening the template parameters of class `basic_json`. -- :construction_worker: Removed Doozer. -- :construction_worker: Added Codacity. -- :arrow_up: Upgraded Catch to version 1.7.2. - - -## v2.1.0 - -!!! summary "Files" - - - [json.hpp](https://github.com/nlohmann/json/releases/download/v2.1.0/json.hpp) (426 KB) - - [json.hpp.asc](https://github.com/nlohmann/json/releases/download/v2.1.0/json.hpp.asc) (1 KB) - -- Release date: 2017-01-28 -- SHA-256: a571dee92515b685784fd527e38405cf3f5e13e96edbfe3f03d6df2e363a767b - -### Summary - -This release introduces a means to convert from/to user-defined types. The release is backwards compatible. - -![conversion](https://cloud.githubusercontent.com/assets/159488/22399173/aebe8f7a-e597-11e6-930f-7494ee615827.png) - -### Changes -- :sparkles: The library now offers an elegant way to **convert from and to arbitrary value types**. All you need to do is to implement two functions: `to_json` and `from_json`. Then, a conversion is as simple as putting a `=` between variables. See the [README](https://github.com/nlohmann/json#arbitrary-types-conversions) for more information and examples. -- :sparkles: **Exceptions can now be switched off.** This can be done by defining the preprocessor symbol `JSON_NOEXCEPTION` or by passing `-fno-exceptions` to your compiler. In case the code would usually thrown an exception, `abort()` is now called. -- :sparkles: **Information on the library** can be queried with the new (static) function `meta()` which returns a JSON object with information on the version, compiler, and platform. See the [documentation]() for an example. -- :bug: A bug in the CBOR parser was fixed which led to a buffer overflow. -- :sparkles: The function [`type_name()`]() is now public. It allows to query the type of a JSON value as string. -- :white_check_mark: Added the [Big List of Naughty Strings](https://github.com/minimaxir/big-list-of-naughty-strings) as test case. -- :arrow_up: Updated to [Catch v1.6.0](https://github.com/philsquared/Catch/releases/tag/v1.6.0). -- :memo: Some typos in the documentation have been fixed. - - -## v2.0.10 - -!!! summary "Files" - - - [json.hpp](https://github.com/nlohmann/json/releases/download/v2.0.10/json.hpp) (409 KB) - - [json.hpp.asc](https://github.com/nlohmann/json/releases/download/v2.0.10/json.hpp.asc) (1 KB) - -- Release date: 2017-01-02 -- SHA-256: ec27d4e74e9ce0f78066389a70724afd07f10761009322dc020656704ad5296d - -### Summary - -This release fixes several security-relevant bugs in the MessagePack and CBOR parsers. The fixes are backwards compatible. - -### Changes -- :bug: Fixed a lot of **bugs in the CBOR and MesssagePack parsers**. These bugs occurred if invalid input was parsed and then could lead in buffer overflows. These bugs were found with Google's [OSS-Fuzz](https://github.com/google/oss-fuzz), see #405, #407, #408, #409, #411, and #412 for more information. -- :construction_worker: We now also use the **[Doozer](https://doozer.io) continuous integration platform**. -- :construction_worker: The complete test suite is now also run with **Clang's address sanitizer and undefined-behavior sanitizer**. -- :white_check_mark: Overworked **fuzz testing**; CBOR and MessagePack implementations are now fuzz-tested. Furthermore, all fuzz tests now include a round trip which ensures created output can again be properly parsed and yields the same JSON value. -- :memo: Clarified documentation of `find()` function to always return `end()` when called on non-object value types. -- :hammer: Moved thirdparty test code to `test/thirdparty` directory. - -## v2.0.9 - -!!! summary "Files" - - - [json.hpp](https://github.com/nlohmann/json/releases/download/v2.0.9/json.hpp) (406 KB) - - [json.hpp.asc](https://github.com/nlohmann/json/releases/download/v2.0.9/json.hpp.asc) (1 KB) - -- Release date: 2016-12-16 -- SHA-256: fbf3396f13e187d6c214c297bddc742d918ea9b55e10bfb3d9f458b9bfdc22e5 - -### Summary - -This release implements with **[CBOR](http://cbor.io)** and **[MessagePack](http://msgpack.org)** two **binary serialization/deserialization formats**. It further contains some small fixes and improvements. The fixes are backwards compatible. - -![cbor](https://cloud.githubusercontent.com/assets/159488/22399181/d4d60d32-e597-11e6-8dcb-825abcf9ac2a.png) - -### Changes -- :sparkles: The library can now read and write the binary formats **[CBOR](http://cbor.io)** (Concise Binary Object Representation) and **[MessagePack](http://msgpack.org)**. Both formats are aimed to produce a very compact representation of JSON which can be parsed very efficiently. See the [README file](https://github.com/nlohmann/json#binary-formats-cbor-and-messagepack) for more information and examples. -- :fire: simplified the iteration implementation allowing to remove dozens of lines of code -- :bug: fixed an [integer overflow error](https://github.com/nlohmann/json/issues/389) detected by [Google's OSS-Fuzz](https://github.com/google/oss-fuzz) -- :bug: suppressed documentation warnings inside the library to facilitate compilation with `-Wdocumentation` -- :bug: fixed an overflow detection error in the number parser -- :memo: updated [contribution guidelines](https://github.com/nlohmann/json/blob/develop/.github/CONTRIBUTING.md) to a list of frequentely asked features that will most likely be never added to the library -- :memo: added a **table of contents** to the [README file](https://github.com/nlohmann/json/blob/develop/README.md) to add some structure -- :memo: mentioned the many [examples](https://github.com/nlohmann/json/tree/develop/doc/examples) and the [documentation](https://nlohmann.github.io/json/) in the [README file]() -- :hammer: split [unit tests](https://github.com/nlohmann/json/tree/develop/test/src) into individual independent binaries to speed up compilation and testing -- :white_check_mark: the test suite now contains **11201886** tests - -## v2.0.8 - -!!! summary "Files" - - - [json.hpp](https://github.com/nlohmann/json/releases/download/v2.0.8/json.hpp) (360 KB) - - [json.hpp.asc](https://github.com/nlohmann/json/releases/download/v2.0.8/json.hpp.asc) (1 KB) - -- Release date: 2016-12-02 -- SHA-256: b70db0ad34f8e0e61dc3f0cbab88099336c9674c193d8a3439d93d6aca2d7120 - -### Summary - -This release combines a lot of small fixes and improvements. The fixes are backwards compatible. - -### Changes -- :bug: fixed a bug that froze the parser if a passed file was not found (now, `std::invalid_argument` is thrown) -- :bug: fixed a bug that lead to an error of a file at EOF was parsed again (now, `std::invalid_argument` is thrown) -- :sparkles: the well known functions [`emplace`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_a602f275f0359ab181221384989810604.html#a602f275f0359ab181221384989810604) and [`emplace_back`](http://nlohmann.github.io/json/doxygen/classnlohmann_1_1basic__json_af8a435033327d9237da414afc1cce513.html#af8a435033327d9237da414afc1cce513) have been added to JSON values and work as expected -- :zap: improved the performance of the serialization (`dump` function) -- :zap: improved the performance of the deserialization (parser) -- :construction_worker: some continuous integration images at [Travis](https://travis-ci.org/nlohmann/json) were added and retired; see [here](https://github.com/nlohmann/json#supported-compilers) for the current continuous integration setup -- :construction_worker: the [Coverity scan](https://scan.coverity.com/projects/nlohmann-json) works again -- :chart_with_upwards_trend: the benchmarking code has been improved to produce more stable results -- :memo: the [README](https://github.com/nlohmann/json/blob/develop/README.md) file has been extended and includes more frequently asked examples -- :white_check_mark: the test suite now contains 8905518 tests -- :arrow_up: updated [Catch](https://github.com/philsquared/Catch) to version 1.5.8 - -## v2.0.7 - -!!! summary "Files" - - - [json.hpp](https://github.com/nlohmann/json/releases/download/v2.0.7/json.hpp) (355 KB) - - [json.hpp.asc](https://github.com/nlohmann/json/releases/download/v2.0.7/json.hpp.asc) (1 KB) - -- Release date: 2016-11-02 -- SHA-256: 5545c323670f8165bae90b9dc6078825e86ec310d96cc4e5b47233ea43715bbf - -### Summary - -This release fixes a few bugs in the JSON parser found in the [Parsing JSON is a Minefield 💣](http://seriot.ch/parsing_json.html) article. The fixes are backwards compatible. - -### Changes -- The article [Parsing JSON is a Minefield 💣](http://seriot.ch/parsing_json.html) discusses a lot of pitfalls of the JSON specification. When investigating the published test cases, a few bugs in the library were found and fixed: - - Files with less than 5 bytes can now be parsed without error. - - The library now properly rejects any file encoding other than UTF-8. Furthermore, incorrect surrogate pairs are properly detected and rejected. - - The library now accepts all but one "yes" test (y_string_utf16.json): UTF-16 is not supported. - - The library rejects all but one "no" test (n_number_then_00.json): Null bytes are treated as end of file instead of an error. This allows to parse input from null-terminated strings. -- The string length passed to a user-defined string literal is now exploited to choose a more efficient constructor. -- A few grammar mistakes in the README file have been fixed. - -## v2.0.6 - -!!! summary "Files" - - - [json.hpp](https://github.com/nlohmann/json/releases/download/v2.0.6/json.hpp) (349 KB) - - [json.hpp.asc](https://github.com/nlohmann/json/releases/download/v2.0.6/json.hpp.asc) (1 KB) - -- Release date: 2016-10-15 -- SHA256: 459cc93d5e2f503e50c6d5876eb86bfea7daf405f5a567c5a2c9abc2383756ae - -### Summary - -This release fixes the semantics of `operator[]` for JSON Pointers (see below). This fix is backwards compatible. - -### Changes -- **`operator[]` for JSON Pointers** now behaves like the other versions of `operator[]` and transforms `null` values into objects or arrays if required. This allows to created nested structures like `j["/foo/bar/2"] = 17` (yielding `{"foo": "bar": [null, null, 17]}`) without problems. -- overworked a helper SFINAE function -- fixed some documentation issues -- fixed the CMake files to allow to run the test suite outside the main project directory -- restored test coverage to 100%. - -## v2.0.5 - -!!! summary "Files" - - - [json.hpp](https://github.com/nlohmann/json/releases/download/v2.0.5/json.hpp) (347 KB) - - [json.hpp.asc](https://github.com/nlohmann/json/releases/download/v2.0.5/json.hpp.asc) (1 KB) - -- Release date: 2016-09-14 -- SHA-256: 8b7565263a44e2b7d3b89808bc73d2d639037ff0c1f379e3d56dbd77e00b98d9 - -### Summary - -This release fixes a regression bug in the stream parser (function `parse()` and the `<<`/`>>` operators). This fix is backwards compatible. - -### Changes -- **Bug fix**: The end of a file stream was not detected properly which led to parse errors. This bug should have been fixed with 2.0.4, but there was still a flaw in the code. - -## v2.0.4 - -!!! summary "Files" - - - [json.hpp](https://github.com/nlohmann/json/releases/download/v2.0.4/json.hpp) (347 KB) - - [json.hpp.asc](https://github.com/nlohmann/json/releases/download/v2.0.4/json.hpp.asc) (1 KB) - -- Release date: 2016-09-11 -- SHA-256: 632ceec4c25c4e2153f71470d3a2b992c8355f6d8b4d627d05dd16095cd3aeda - -### Summary - -This release fixes a bug in the stream parser (function `parse()` and the `<<`/`>>` operators). This fix is backwards compatible. - -### Changes -- **Bug fix**: The end of a file stream was not detected properly which led to parse errors. -- Fixed a compiler warning about an unused variable. - -## v2.0.3 - -!!! summary "Files" - - - [json.hpp](https://github.com/nlohmann/json/releases/download/v2.0.3/json.hpp) (347 KB) - - [json.hpp.asc](https://github.com/nlohmann/json/releases/download/v2.0.3/json.hpp.asc) (1 KB) - -- Release date: 2016-08-31 -- SHA-256: 535b73efe5546fde9e763c14aeadfc7b58183c0b3cd43c29741025aba6cf6bd3 - -### Summary - -This release combines a lot of small fixes and improvements. The release is backwards compatible. - -### Changes -- The **parser/deserialization functions have been generalized** to process any contiguous sequence of 1-byte elements (e.g., `char`, `unsigned char`, `uint8_t`). This includes all kind of string representations (string literals, char arrays, `std::string`, `const char*`), contiguous containers (C-style arrays, `std::vector`, `std::array`, `std::valarray`, `std::initializer_list`). User-defined containers providing random-access iterator access via `std::begin` and `std::end` can be used as well. See the documentation ([1](https://nlohmann.github.io/json/classnlohmann_1_1basic__json_ace63ac4eb1dd7251a259d32e397461a3.html#ace63ac4eb1dd7251a259d32e397461a3), [2](https://nlohmann.github.io/json/classnlohmann_1_1basic__json_a90f05d55d9d0702c075cd281fd0d85ae.html#a90f05d55d9d0702c075cd281fd0d85ae), [3](https://nlohmann.github.io/json/classnlohmann_1_1basic__json_aeffd70f622f8f2a51fd3d95af64b63a7.html#aeffd70f622f8f2a51fd3d95af64b63a7), [4](https://nlohmann.github.io/json/classnlohmann_1_1basic__json_aa8dca2e91a6301c36890f844e64f0023.html#aa8dca2e91a6301c36890f844e64f0023)) for more information. Note that contiguous storage cannot be checked at compile time; if any of the parse functions are called with a noncompliant container, the behavior is undefined and will most likely yield segmentation violation. The preconditions are enforced by an assertion unless the library is compiled with preprocessor symbol `NDEBUG`. -- As a general remark on **assertions**: The library uses assertions to preclude undefined behavior. A [prominent example](https://github.com/nlohmann/json/issues/289) for this is the `operator[]` for const JSON objects. The behavior of this const version of the operator is undefined if the given key does not exist in the JSON object, because unlike the non-const version, it cannot add a `null` value at the given key. Assertions can be switched of by defining the preprocessor symbol `NDEBUG`. See the [documentation of `assert`](http://en.cppreference.com/w/cpp/error/assert) for more information. -- In the course of cleaning up the parser/deserialization functions, the constructor [`basic_json(std::istream&, const parser_callback_t)`](https://nlohmann.github.io/json/classnlohmann_1_1basic__json_a32350263eb105764844c5a85e156a255.html#a32350263eb105764844c5a85e156a255) has been **deprecated** and will be deleted with the next major release 3.0.0 to unify the interface of the library. Deserialization will be done by stream operators or by calling one of the `parse` functions. That is, calls like `json j(i);` for an input stream `i` need to be replaced by `json j = json::parse(i);`. Compilers will produce a deprecation warning if client code uses this function. -- Minor improvements: - - Improved the performance of the serialization by avoiding the re-creation of a locale object. - - Fixed two MSVC warnings. Compiling the test suite with `/Wall` now only warns about non-inlined functions (C4710) and the deprecation of the constructor from input-stream (C4996). -- Some project internals: - - The project has qualified for the [Core Infrastructure Initiative Best Practices Badge](https://bestpractices.coreinfrastructure.org/projects/289). While most requirements where already satisfied, some led to a more explicit documentation of quality-ensuring procedures. For instance, static analysis is now executed with every commit on the build server. Furthermore, the [contribution guidelines document](https://github.com/nlohmann/json/blob/develop/.github/CONTRIBUTING.md) how to communicate security issues privately. - - The test suite has been overworked and split into several files to allow for faster compilation and analysis. The execute the test suite, simply execute `make check`. - - The continuous integration with [Travis](https://travis-ci.org/nlohmann/json) was extended with Clang versions 3.6.0 to 3.8.1 and now includes 18 different compiler/OS combinations. - - An 11-day run of [American fuzzy lop](http://lcamtuf.coredump.cx/afl/) checked 962 million inputs on the parser and found no issue. - -## v2.0.2 - -!!! summary "Files" - - - [json.hpp](https://github.com/nlohmann/json/releases/download/v2.0.2/json.hpp) (338 KB) - - [json.hpp.asc](https://github.com/nlohmann/json/releases/download/v2.0.2/json.hpp.asc) (1 KB) - -- Release date: 2016-07-31 -- SHA-256: 8e97b7965b4594b00998d6704465412360e1a0ed927badb51ded8b82291a8f3d - -### Summary - -This release combines a lot of small fixes and improvements. The release is backwards compatible. - -### Changes -- The **parser** has been overworked, and a lot of small issues have been fixed: - - Improved parser performance by avoiding recursion and using move semantics for the return value. - - Unescaped control characters `\x10`-`\x1f` are not accepted any more. - - Fixed a bug in the parser when reading from an input stream. - - Improved test case coverage for UTF-8 parsing: now, all valid Unicode code points are tested both escaped and unescaped. - - The precision of output streams is now preserved by the parser. -- Started to check the **code correctness** by proving termination of important loops. Furthermore, individual assertions have been replaced by a more systematic function which checks the class invariants. Note that assertions should be switched off in production by defining the preprocessor macro `NDEBUG`, see the [documentation of `assert`](http://en.cppreference.com/w/cpp/error/assert). -- A lot of **code cleanup**: removed unused headers, fixed some compiler warnings, and fixed a build error for Windows-based Clang builds. -- Added some compile-time checks: - - Unsupported compilers are rejected during compilation with an `#error` command. - - Static assertion prohibits code with incompatible pointer types used in `get_ptr()`. -- Improved the [documentation](https://nlohmann.github.io/json/), and adjusted the documentation script to choose the correct version of `sed`. -- Replaced a lot of "raw loops" by STL functions like `std::all_of`, `std::for_each`, or `std::accumulate`. This facilitates reasoning about termination of loops and sometimes allowed to simplify functions to a single return statement. -- Implemented a `value()` function for JSON pointers (similar to `at` function). -- The Homebrew formula (see [Integration](https://github.com/nlohmann/json#integration)) is now tested for all Xcode builds (6.1 - 8.x) with Travis. -- Avoided output to `std::cout` in the test cases. - -## v2.0.1 - -!!! summary "Files" - - - [json.hpp](https://github.com/nlohmann/json/releases/download/v2.0.1/json.hpp) (321 KB) - - [json.hpp.asc](https://github.com/nlohmann/json/releases/download/v2.0.1/json.hpp.asc) (1 KB) - -- Release date: 2016-06-28 -- SHA-256: ef550fcd7df572555bf068e9ec4e9d3b9e4cdd441cecb0dcea9ea7fd313f72dd - -### Summary - -This release fixes a performance regression in the JSON serialization (function `dump()`). This fix is backwards compatible. - -### Changes -- The locale of the output stream (or the internal string stream if a JSON value is serialized to a string) is now adjusted once for the whole serialization instead of for each floating-point number. -- The locale of an output stream is now correctly reset to the previous value by the JSON library. - - -## v2.0.0 - -!!! summary "Files" - - - [json.hpp](https://github.com/nlohmann/json/releases/download/v2.0.0/json.hpp) (321 KB) - - [json.hpp.asc](https://github.com/nlohmann/json/releases/download/v2.0.0/json.hpp.asc) (1 KB) - -- Release date: 2016-06-24 -- SHA-256: ac9e1fb25c2ac9ca5fc501fcd2fe3281fe04f07018a1b48820e7b1b11491bb6c - -### Summary - -This release adds several features such as JSON Pointers, JSON Patch, or support for 64 bit unsigned integers. Furthermore, several (subtle) bugs have been fixed. - -As `noexcept` and `constexpr` specifier have been added to several functions, the public API has effectively been changed in a (potential) non-backwards compatible manner. As we adhere to [Semantic Versioning](http://semver.org), this calls for a new major version, so say hello to 2️⃣.0️⃣.0️⃣. - -### Changes -- 🔟 A JSON value now uses `uint64_t` (default value for template parameter `NumberUnsignedType`) as data type for **unsigned integer** values. This type is used automatically when an unsigned number is parsed. Furthermore, constructors, conversion operators and an `is_number_unsigned()` test have been added. -- 👉 **JSON Pointer** ([RFC 6901](https://tools.ietf.org/html/rfc6901)) support: A JSON Pointer is a string (similar to an XPath expression) to address a value inside a structured JSON value. JSON Pointers can be used in `at()` and `operator[]` functions. Furthermore, JSON values can be “flattened” to key/value pairs using `flatten()` where each key is a JSON Pointer. The original value can be restored by “unflattening” the flattened value using `unflatten()`. -- 🏥 **JSON Patch** ([RFC 6902](https://tools.ietf.org/html/rfc6902)) support. A JSON Patch is a JSON value that describes the required edit operations (add, change, remove, …) to transform a JSON value into another one. A JSON Patch can be created with function `diff(const basic_json&)` and applied with `patch(const basic_json&)`. Note the created patches use a rather primitive algorithm so far and leave room for improvement. -- 🇪🇺 The code is now **locale-independent**: Floating-point numbers are always serialized with a period (`.`) as decimal separator and ignores different settings from the locale. -- 🍺 **Homebrew** support: Install the library with `brew tap nlohmann/json && brew install nlohmann_json`. -- Added constructor to create a JSON value by parsing a `std::istream` (e.g., `std::stringstream` or `std::ifstream`). -- Added **`noexcept`** specifier to `basic_json(boolean_t)`, `basic_json(const number_integer_t)`, `basic_json(const int)`, `basic_json(const number_float_t)`, iterator functions (`begin()`, `end()`, etc.) -- When parsing numbers, the sign of `0.0` (vs. `-0.0`) is preserved. -- Improved MSVC 2015, Android, and MinGW support. See [README](https://github.com/nlohmann/json#supported-compilers) for more information. -- Improved test coverage (added 2,225,386 tests). -- Removed some misuses of `std::move`. -- Fixed several compiler warnings. -- Improved error messages from JSON parser. -- Updated to [`re2c`](http://re2c.org) to version 0.16 to use a minimal DFAs for the lexer. -- Updated test suite to use [Catch](https://github.com/philsquared/Catch) version 1.5.6. -- Made type getters (`is_number`, etc.) and const value access `constexpr`. -- Functions `push_back` and `operator+=` now work with key/value pairs passed as initializer list, e.g. `j_object += {"key", 1}`. -- Overworked `CMakeLists.txt` to make it easier to integrate the library into other projects. - -### Notes -- Parser error messages are still very vague and contain no information on the error location. -- The implemented `diff` function is rather primitive and does not create minimal diffs. -- The name of function `iteration_wrapper` may change in the future and the function will be deprecated in the next release. -- Roundtripping (i.e., parsing a JSON value from a string, serializing it, and comparing the strings) of floating-point numbers is not 100% accurate. Note that [RFC 8259](https://tools.ietf.org/html/rfc8259) defines no format to internally represent numbers and states not requirement for roundtripping. Nevertheless, benchmarks like [Native JSON Benchmark](https://github.com/miloyip/nativejson-benchmark) treat roundtripping deviations as conformance errors. - - -## v1.1.0 - -!!! summary "Files" - - - [json.hpp](https://github.com/nlohmann/json/releases/download/v1.1.0/json.hpp) (257 KB) - - [json.hpp.asc](https://github.com/nlohmann/json/releases/download/v1.1.0/json.hpp.asc) (1 KB) - -- Release date: 2016-01-24 -- SHA-256: c0cf0e3017798ca6bb18e757ebc570d21a3bdac877845e2b9e9573d183ed2f05 - -### Summary - -This release fixes several small bugs and adds functionality in a backwards-compatible manner. Compared to the [last version (1.0.0)](https://github.com/nlohmann/json/releases/tag/v1.0.0), the following changes have been made: - -### Changes -- _Fixed_: **Floating-point numbers** are now serialized and deserialized properly such that rountripping works in more cases. [#185, #186, #190, #191, #194] -- _Added_: The code now contains **assertions** to detect undefined behavior during development. As the standard function `assert` is used, the assertions can be switched off by defining the preprocessor symbol `NDEBUG` during compilation. [#168] -- _Added_: It is now possible to get a **reference** to the stored values via the newly added function `get_ref()`. [#128, #184] -- _Fixed_: Access to object values via keys (**`operator[]`**) now works with all kind of string representations. [#171, #189] -- _Fixed_: The code now compiles again with **Microsoft Visual Studio 2015**. [#144, #167, #188] -- _Fixed_: All required headers are now included. -- _Fixed_: Typos and other small issues. [#162, #166, #175, #177, #179, #180] - -### Notes - -There are still known open issues (#178, #187) which will be fixed in version 2.0.0. However, these fixes will require a small API change and will not be entirely backwards-compatible. - - -## v1.0.0 - -!!! summary "Files" - - - [json.hpp](https://github.com/nlohmann/json/releases/download/v1.0.0/json.hpp) (243 KB) - - [json.hpp.asc](https://github.com/nlohmann/json/releases/download/v1.0.0/json.hpp.asc) (1 KB) - -- Release date: 2015-12-28 -- SHA-256: 767dc2fab1819d7b9e19b6e456d61e38d21ef7182606ecf01516e3f5230446de - -### Summary - -This is the first official release. Compared to the [prerelease version 1.0.0-rc1](https://github.com/nlohmann/json/releases/tag/v1.0.0-rc1), only a few minor improvements have been made: - -### Changes -- _Changed_: A **UTF-8 byte order mark** is silently ignored. -- _Changed_: `sprintf` is no longer used. -- _Changed_: `iterator_wrapper` also works for const objects; note: the name may change! -- _Changed_: **Error messages** during deserialization have been improved. -- _Added_: The `parse` function now also works with type `std::istream&&`. -- _Added_: Function `value(key, default_value)` returns either a copy of an object's element at the specified key or a given default value if no element with the key exists. -- _Added_: Public functions are tagged with the version they were introduced. This shall allow for better **versioning** in the future. -- _Added_: All public functions and types are **documented** (see http://nlohmann.github.io/json/doxygen/) including executable examples. -- _Added_: Allocation of all types (in particular arrays, strings, and objects) is now exception-safe. -- _Added_: They descriptions of thrown exceptions have been overworked and are part of the tests suite and documentation. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/home/sponsors.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/home/sponsors.md deleted file mode 100644 index 9097049..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/home/sponsors.md +++ /dev/null @@ -1,13 +0,0 @@ -# Sponsors - -You can sponsor this library at [GitHub Sponsors](https://github.com/sponsors/nlohmann). - -## Named Sponsors - -- [Michael Hartmann](https://github.com/reFX-Mike) -- [Stefan Hagen](https://github.com/sthagen) -- [Steve Sperandeo](https://github.com/homer6) -- [Robert Jefe Lindstädt](https://github.com/eljefedelrodeodeljefe) -- [Steve Wagner](https://github.com/ciroque) - -Thanks everyone! diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/images/callback_events.png b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/images/callback_events.png deleted file mode 100644 index 09aa2b3..0000000 Binary files a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/images/callback_events.png and /dev/null differ diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/images/json_syntax_number.png b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/images/json_syntax_number.png deleted file mode 100644 index be23ffa..0000000 Binary files a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/images/json_syntax_number.png and /dev/null differ diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/images/range-begin-end.svg b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/images/range-begin-end.svg deleted file mode 100644 index 8e2b2fb..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/images/range-begin-end.svg +++ /dev/null @@ -1,435 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - image/svg+xml - - - - - - - - - - - - - - - - - - - - - - - - - - Past-the-last element - - - - begin - - - - end - - - - - diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/images/range-rbegin-rend.svg b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/images/range-rbegin-rend.svg deleted file mode 100644 index dc6045f..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/images/range-rbegin-rend.svg +++ /dev/null @@ -1,1232 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - image/svg+xml - - - - - - - - - - - - - - - - - - - - - - - - - - Past-the-last element - - - - begin - - - - end - - - - - - - - - - - - - - - - - - - - - - - - - Reversed sequence - - Reverse past-the-last element - - - - - - - - rend - - - - rbegin - - - Reverse iterator stores an iterator to the nextelement than the one it actually refers to - - - - - - - - - diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/index.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/index.md deleted file mode 100644 index 0e49c83..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/index.md +++ /dev/null @@ -1,3 +0,0 @@ -# JSON for Modern C++ - -![](images/json.gif) diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/integration/cmake.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/integration/cmake.md deleted file mode 100644 index c8f9883..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/integration/cmake.md +++ /dev/null @@ -1,172 +0,0 @@ -# CMake - -## Integration - -You can use the `nlohmann_json::nlohmann_json` interface target in CMake. This target populates the appropriate usage -requirements for [`INTERFACE_INCLUDE_DIRECTORIES`](https://cmake.org/cmake/help/latest/prop_tgt/INTERFACE_INCLUDE_DIRECTORIES.html) -to point to the appropriate include directories and [`INTERFACE_COMPILE_FEATURES`](https://cmake.org/cmake/help/latest/prop_tgt/INTERFACE_COMPILE_FEATURES.html) -for the necessary C++11 flags. - -### External - -To use this library from a CMake project, you can locate it directly with [`find_package()`](https://cmake.org/cmake/help/latest/command/find_package.html) -and use the namespaced imported target from the generated package configuration: - -!!! example - - ```cmake title="CMakeLists.txt" - cmake_minimum_required(VERSION 3.1) - project(ExampleProject LANGUAGES CXX) - - find_package(nlohmann_json 3.11.2 REQUIRED) - - add_executable(example example.cpp) - target_link_libraries(example PRIVATE nlohmann_json::nlohmann_json) - ``` - -The package configuration file, `nlohmann_jsonConfig.cmake`, can be used either from an install tree or directly out of -the build tree. - -### Embedded - -To embed the library directly into an existing CMake project, place the entire source tree in a subdirectory and call -`add_subdirectory()` in your `CMakeLists.txt` file. - -!!! example - - ```cmake title="CMakeLists.txt" - cmake_minimum_required(VERSION 3.1) - project(ExampleProject LANGUAGES CXX) - - # If you only include this third party in PRIVATE source files, you do not need to install it - # when your main project gets installed. - set(JSON_Install OFF CACHE INTERNAL "") - - add_subdirectory(nlohmann_json) - - add_executable(example example.cpp) - target_link_libraries(example PRIVATE nlohmann_json::nlohmann_json) - ``` - -!!! note - - Do not use `#!cmake include(nlohmann_json/CMakeLists.txt)`, since that carries with it unintended consequences that - will break the build. It is generally discouraged (although not necessarily well documented as such) to use - `#!cmake include(...)` for pulling in other CMake projects anyways. - - -### Supporting Both - -To allow your project to support either an externally supplied or an embedded JSON library, you can use a pattern akin -to the following. - -!!! example - - ```cmake title="CMakeLists.txt" - project(ExampleProject LANGUAGES CXX) - - option(EXAMPLE_USE_EXTERNAL_JSON "Use an external JSON library" OFF) - - add_subdirectory(thirdparty) - - add_executable(example example.cpp) - - # Note that the namespaced target will always be available regardless of the import method - target_link_libraries(example PRIVATE nlohmann_json::nlohmann_json) - ``` - - ```cmake title="thirdparty/CMakeLists.txt" - if(EXAMPLE_USE_EXTERNAL_JSON) - find_package(nlohmann_json 3.11.2 REQUIRED) - else() - set(JSON_BuildTests OFF CACHE INTERNAL "") - add_subdirectory(nlohmann_json) - endif() - ``` - - `thirdparty/nlohmann_json` is then a complete copy of this source tree. - - -### FetchContent - -Since CMake v3.11, [FetchContent](https://cmake.org/cmake/help/v3.11/module/FetchContent.html) can be used to -automatically download a release as a dependency at configure type. - -!!! example - - ```cmake title="CMakeLists.txt" - cmake_minimum_required(VERSION 3.11) - project(ExampleProject LANGUAGES CXX) - - include(FetchContent) - - FetchContent_Declare(json URL https://github.com/nlohmann/json/releases/download/v3.11.2/json.tar.xz) - FetchContent_MakeAvailable(json) - - add_executable(example example.cpp) - target_link_libraries(example PRIVATE nlohmann_json::nlohmann_json) - ``` - -!!! Note - - It is recommended to use the URL approach described above which is supported as of version 3.10.0. It is also - possible to pass the Git repository like - - ```cmake - FetchContent_Declare(json - GIT_REPOSITORY https://github.com/nlohmann/json - GIT_TAG v3.11.2 - ) - ``` - - However, the repository download size is quite large. You might want to depend on - a smaller repository. For instance, you might want to replace the URL in the example by - . - -## CMake Options - -### `JSON_BuildTests` - -Build the unit tests when [`BUILD_TESTING`](https://cmake.org/cmake/help/latest/command/enable_testing.html) is enabled. This option is `ON` by default if the library's CMake project is the top project. That is, when integrating the library as described above, the test suite is not built unless explicitly switched on with this option. - -### `JSON_CI` - -Enable CI build targets. The exact targets are used during the several CI steps and are subject to change without notice. This option is `OFF` by default. - -### `JSON_Diagnostics` - -Enable [extended diagnostic messages](../home/exceptions.md#extended-diagnostic-messages) by defining macro [`JSON_DIAGNOSTICS`](../api/macros/json_diagnostics.md). This option is `OFF` by default. - -### `JSON_DisableEnumSerialization` - -Disable default `enum` serialization by defining the macro -[`JSON_DISABLE_ENUM_SERIALIZATION`](../api/macros/json_disable_enum_serialization.md). This option is `OFF` by default. - -### `JSON_FastTests` - -Skip expensive/slow test suites. This option is `OFF` by default. Depends on `JSON_BuildTests`. - -### `JSON_GlobalUDLs` - -Place user-defined string literals in the global namespace by defining the macro -[`JSON_USE_GLOBAL_UDLS`](../api/macros/json_use_global_udls.md). This option is `OFF` by default. - -### `JSON_ImplicitConversions` - -Enable implicit conversions by defining macro [`JSON_USE_IMPLICIT_CONVERSIONS`](../api/macros/json_use_implicit_conversions.md). This option is `ON` by default. - -### `JSON_Install` - -Install CMake targets during install step. This option is `ON` by default if the library's CMake project is the top project. - -### `JSON_MultipleHeaders` - -Use non-amalgamated version of the library. This option is `OFF` by default. - -### `JSON_SystemInclude` - -Treat the library headers like system headers (i.e., adding `SYSTEM` to the [`target_include_directories`](https://cmake.org/cmake/help/latest/command/target_include_directories.html) call) to checks for this library by tools like Clang-Tidy. This option is `OFF` by default. - -### `JSON_Valgrind` - -Execute test suite with [Valgrind](https://valgrind.org). This option is `OFF` by default. Depends on `JSON_BuildTests`. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/integration/conan/CMakeLists.txt b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/integration/conan/CMakeLists.txt deleted file mode 100644 index fd3e9ca..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/integration/conan/CMakeLists.txt +++ /dev/null @@ -1,9 +0,0 @@ -project(json_example) -cmake_minimum_required(VERSION 2.8.12) -add_definitions("-std=c++11") - -include(${CMAKE_BINARY_DIR}/conanbuildinfo.cmake) -conan_basic_setup() - -add_executable(json_example example.cpp) -target_link_libraries(json_example ${CONAN_LIBS}) diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/integration/conan/Conanfile.txt b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/integration/conan/Conanfile.txt deleted file mode 100644 index a8a3e70..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/integration/conan/Conanfile.txt +++ /dev/null @@ -1,5 +0,0 @@ -[requires] -nlohmann_json/3.7.3 - -[generators] -cmake diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/integration/conan/example.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/integration/conan/example.cpp deleted file mode 100644 index e5a31be..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/integration/conan/example.cpp +++ /dev/null @@ -1,9 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - std::cout << json::meta() << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/integration/example.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/integration/example.cpp deleted file mode 100644 index 1a7ac4d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/integration/example.cpp +++ /dev/null @@ -1,10 +0,0 @@ -#include -#include -#include - -using json = nlohmann::json; - -int main() -{ - std::cout << std::setw(4) << json::meta() << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/integration/index.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/integration/index.md deleted file mode 100644 index 2bbaa86..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/integration/index.md +++ /dev/null @@ -1,18 +0,0 @@ -# Header only - -[`json.hpp`](https://github.com/nlohmann/json/blob/develop/single_include/nlohmann/json.hpp) is the single required -file in `single_include/nlohmann` or [released here](https://github.com/nlohmann/json/releases). You need to add - -```cpp -#include - -// for convenience -using json = nlohmann::json; -``` - -to the files you want to process JSON and set the necessary switches to enable C++11 (e.g., `-std=c++11` for GCC and -Clang). - -You can further use file -[`single_include/nlohmann/json_fwd.hpp`](https://github.com/nlohmann/json/blob/develop/single_include/nlohmann/json_fwd.hpp) -for forward declarations. diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/integration/package_managers.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/integration/package_managers.md deleted file mode 100644 index b9ebf07..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/integration/package_managers.md +++ /dev/null @@ -1,194 +0,0 @@ -# Package Managers - -Throughout this page, we will describe how to compile the example file `example.cpp` below. - -```cpp ---8<-- "integration/example.cpp" -``` - -When executed, this program should create output similar to - -```json ---8<-- "../../examples/meta.output" -``` - -## Homebrew - -If you are using OS X and [Homebrew](http://brew.sh), just type - -```sh -brew install nlohmann-json -``` - -and you're set. If you want the bleeding edge rather than the latest release, use - -```sh -brew install nlohmann-json --HEAD -``` - -instead. See [nlohmann-json](https://formulae.brew.sh/formula/nlohmann-json) for more information. - -??? example - - 1. Create the following file: - - ```cpp title="example.cpp" - --8<-- "integration/example.cpp" - ``` - - 2. Install the package - - ```sh - brew install nlohmann-json - ``` - - 3. Determine the include path, which defaults to `/usr/local/Cellar/nlohmann-json/$version/include`, where `$version` is the version of the library, e.g. `3.7.3`. The path of the library can be determined with - - ```sh - brew list nlohmann-json - ``` - - 4. Compile the code. For instance, the code can be compiled using Clang with - - ```sh - clang++ example.cpp -I/usr/local/Cellar/nlohmann-json/3.7.3/include -std=c++11 -o example - ``` - -:material-update: The [formula](https://formulae.brew.sh/formula/nlohmann-json) is updated automatically. - -## Meson - -If you are using the [Meson Build System](http://mesonbuild.com), add this source tree as a [meson subproject](https://mesonbuild.com/Subprojects.html#using-a-subproject). You may also use the `include.zip` published in this project's [Releases](https://github.com/nlohmann/json/releases) to reduce the size of the vendored source tree. Alternatively, you can get a wrap file by downloading it from [Meson WrapDB](https://wrapdb.mesonbuild.com/nlohmann_json), or simply use `meson wrap install nlohmann_json`. Please see the meson project for any issues regarding the packaging. - -The provided `meson.build` can also be used as an alternative to cmake for installing `nlohmann_json` system-wide in which case a pkg-config file is installed. To use it, simply have your build system require the `nlohmann_json` pkg-config dependency. In Meson, it is preferred to use the [`dependency()`](https://mesonbuild.com/Reference-manual.html#dependency) object with a subproject fallback, rather than using the subproject directly. - -## Conan - -If you are using [Conan](https://www.conan.io/) to manage your dependencies, merely add `nlohmann_json/x.y.z` to your `conanfile`'s requires, where `x.y.z` is the release version you want to use. Please file issues [here](https://github.com/conan-io/conan-center-index/issues) if you experience problems with the packages. - -??? example - - 1. Create the following files: - - ```ini title="Conanfile.txt" - --8<-- "integration/conan/Conanfile.txt" - ``` - - ```cmake title="CMakeLists.txt" - --8<-- "integration/conan/CMakeLists.txt" - ``` - - ```cpp title="example.cpp" - --8<-- "integration/conan/example.cpp" - ``` - - 2. Build: - - ```sh - mkdir build - cd build - conan install .. - cmake .. - cmake --build . - ``` - -:material-update: The [package](https://conan.io/center/nlohmann_json) is updated automatically. - -## Spack - -If you are using [Spack](https://www.spack.io/) to manage your dependencies, you can use the [`nlohmann-json` package](https://spack.readthedocs.io/en/latest/package_list.html#nlohmann-json). Please see the [spack project](https://github.com/spack/spack) for any issues regarding the packaging. - -## Hunter - -If you are using [hunter](https://github.com/cpp-pm/hunter) on your project for external dependencies, then you can use the [nlohmann_json package](https://hunter.readthedocs.io/en/latest/packages/pkg/nlohmann_json.html). Please see the hunter project for any issues regarding the packaging. - -## Buckaroo - -If you are using [Buckaroo](https://buckaroo.pm), you can install this library's module with `buckaroo add github.com/buckaroo-pm/nlohmann-json`. Please file issues [here](https://github.com/buckaroo-pm/nlohmann-json). There is a demo repo [here](https://github.com/njlr/buckaroo-nholmann-json-example). - -## vcpkg - -If you are using [vcpkg](https://github.com/Microsoft/vcpkg/) on your project for external dependencies, then you can install the [nlohmann-json package](https://github.com/Microsoft/vcpkg/tree/master/ports/nlohmann-json) with `vcpkg install nlohmann-json` and follow the then displayed descriptions. Please see the vcpkg project for any issues regarding the packaging. - -??? example - - 1. Create the following files: - - ```cmake title="CMakeLists.txt" - --8<-- "integration/vcpkg/CMakeLists.txt" - ``` - - ```cpp title="example.cpp" - --8<-- "integration/vcpkg/example.cpp" - ``` - - 2. Install package: - - ```sh - vcpkg install nlohmann-json - ``` - - 3. Build: - - ```sh - mkdir build - cd build - cmake .. -DCMAKE_TOOLCHAIN_FILE=/path/to/vcpkg/scripts/buildsystems/vcpkg.cmake - cmake --build . - ``` - - Note you need to adjust `/path/to/vcpkg/scripts/buildsystems/vcpkg.cmake` to your system. - -## cget - -If you are using [cget](http://cget.readthedocs.io/en/latest/), you can install the latest development version with `cget install nlohmann/json`. A specific version can be installed with `cget install nlohmann/json@v3.1.0`. Also, the multiple header version can be installed by adding the `-DJSON_MultipleHeaders=ON` flag (i.e., `cget install nlohmann/json -DJSON_MultipleHeaders=ON`). - -:material-update: cget reads directly from the [GitHub repository](https://github.com/nlohmann/json) and is always up-to-date. - -## CocoaPods - -If you are using [CocoaPods](https://cocoapods.org), you can use the library by adding pod `"nlohmann_json", '~>3.1.2'` to your podfile (see [an example](https://bitbucket.org/benman/nlohmann_json-cocoapod/src/master/)). Please file issues [here](https://bitbucket.org/benman/nlohmann_json-cocoapod/issues?status=new&status=open). - -## NuGet - -If you are using [NuGet](https://www.nuget.org), you can use the package [nlohmann.json](https://www.nuget.org/packages/nlohmann.json/). Please check [this extensive description](https://github.com/nlohmann/json/issues/1132#issuecomment-452250255) on how to use the package. Please file issues [here](https://github.com/hnkb/nlohmann-json-nuget/issues). - -## Conda - -If you are using [conda](https://conda.io/), you can use the package [nlohmann_json](https://github.com/conda-forge/nlohmann_json-feedstock) from [conda-forge](https://conda-forge.org) executing `conda install -c conda-forge nlohmann_json`. Please file issues [here](https://github.com/conda-forge/nlohmann_json-feedstock/issues). - -## MSYS2 - -If you are using [MSYS2](http://www.msys2.org/), you can use the [mingw-w64-nlohmann-json](https://packages.msys2.org/base/mingw-w64-nlohmann-json) package, just type `pacman -S mingw-w64-i686-nlohmann-json` or `pacman -S mingw-w64-x86_64-nlohmann-json` for installation. Please file issues [here](https://github.com/msys2/MINGW-packages/issues/new?title=%5Bnlohmann-json%5D) if you experience problems with the packages. - -:material-update: The [package](https://packages.msys2.org/base/mingw-w64-nlohmann-json) is updated automatically. - -## MacPorts - -If you are using [MacPorts](https://ports.macports.org), execute `sudo port install nlohmann-json` to install the [nlohmann-json](https://ports.macports.org/port/nlohmann-json/) package. - -:material-update: The [package](https://ports.macports.org/port/nlohmann-json/) is updated automatically. - -## build2 - -If you are using [`build2`](https://build2.org), you can use the [`nlohmann-json`](https://cppget.org/nlohmann-json) package from the public repository or directly from the [package's sources repository](https://github.com/build2-packaging/nlohmann-json). In your project's `manifest` file, just add `depends: nlohmann-json` (probably with some [version constraints](https://build2.org/build2-toolchain/doc/build2-toolchain-intro.xhtml#guide-add-remove-deps)). If you are not familiar with using dependencies in `build2`, [please read this introduction](https://build2.org/build2-toolchain/doc/build2-toolchain-intro.xhtml). -Please file issues [here](https://github.com/build2-packaging/nlohmann-json) if you experience problems with the packages. - -:material-update: The [package](https://cppget.org/nlohmann-json) is updated automatically. - -## wsjcpp - -If you are using [`wsjcpp`](http://wsjcpp.org), you can use the command `wsjcpp install "https://github.com/nlohmann/json:develop"` to get the latest version. Note you can change the branch ":develop" to an existing tag or another branch. - -:material-update: wsjcpp reads directly from the [GitHub repository](https://github.com/nlohmann/json) and is always up-to-date. - -## CPM.cmake - -If you are using [`CPM.cmake`](https://github.com/TheLartians/CPM.cmake), you can check this [`example`](https://github.com/TheLartians/CPM.cmake/tree/master/examples/json). After [adding CPM script](https://github.com/TheLartians/CPM.cmake#adding-cpm) to your project, implement the following snippet to your CMake: - -```cmake -CPMAddPackage( - NAME nlohmann_json - GITHUB_REPOSITORY nlohmann/json - VERSION 3.9.1) -``` diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/integration/pkg-config.md b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/integration/pkg-config.md deleted file mode 100644 index 429d0de..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/integration/pkg-config.md +++ /dev/null @@ -1,13 +0,0 @@ -# Pkg-config - -If you are using bare Makefiles, you can use `pkg-config` to generate the include flags that point to where the library is installed: - -```sh -pkg-config nlohmann_json --cflags -``` - -Users of the [Meson build system](package_managers.md#meson) will also be able to use a system-wide library, which will be found by `pkg-config`: - -```meson -json = dependency('nlohmann_json', required: true) -``` diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/integration/vcpkg/CMakeLists.txt b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/integration/vcpkg/CMakeLists.txt deleted file mode 100644 index d31f4e8..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/integration/vcpkg/CMakeLists.txt +++ /dev/null @@ -1,7 +0,0 @@ -project(json_example) -cmake_minimum_required(VERSION 2.8.12) - -find_package(nlohmann_json CONFIG REQUIRED) - -add_executable(json_example example.cpp) -target_link_libraries(json_example PRIVATE nlohmann_json::nlohmann_json) diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/integration/vcpkg/example.cpp b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/integration/vcpkg/example.cpp deleted file mode 100644 index e5a31be..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/docs/integration/vcpkg/example.cpp +++ /dev/null @@ -1,9 +0,0 @@ -#include -#include - -using json = nlohmann::json; - -int main() -{ - std::cout << json::meta() << std::endl; -} diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/mkdocs.yml b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/mkdocs.yml deleted file mode 100644 index 545584a..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/mkdocs.yml +++ /dev/null @@ -1,348 +0,0 @@ -# Project information -site_name: JSON for Modern C++ -site_author: Niels Lohmann -site_url: https://json.nlohmann.me/ - -# Repository -repo_name: nlohmann/json -repo_url: https://github.com/nlohmann/json -edit_uri: edit/develop/docs/mkdocs/docs - -# Copyright -copyright: Copyright © 2013 - 2022 Niels Lohmann - -# Configuration -theme: - name: material - language: en - palette: - primary: indigo - accent: indigo - font: - text: Roboto - code: JetBrains Mono - features: - - navigation.instant - - navigation.tracking - - navigation.tabs - - navigation.indexes - - navigation.top - -nav: - - Home: - - index.md - - home/license.md - - "Code of Conduct": home/code_of_conduct.md - - "FAQ": home/faq.md - - home/exceptions.md - - home/releases.md - - home/design_goals.md - - home/sponsors.md - - Features: - - features/arbitrary_types.md - - Binary Formats: - - features/binary_formats/index.md - - features/binary_formats/bjdata.md - - features/binary_formats/bson.md - - features/binary_formats/cbor.md - - features/binary_formats/messagepack.md - - features/binary_formats/ubjson.md - - features/binary_values.md - - features/comments.md - - Element Access: - - features/element_access/index.md - - features/element_access/unchecked_access.md - - features/element_access/checked_access.md - - features/element_access/default_value.md - - features/iterators.md - - features/json_pointer.md - - features/json_patch.md - - features/merge_patch.md - - 'nlohmann Namespace': features/namespace.md - - features/object_order.md - - Parsing: - - features/parsing/index.md - - features/parsing/json_lines.md - - features/parsing/parse_exceptions.md - - features/parsing/parser_callbacks.md - - features/parsing/sax_interface.md - - features/assertions.md - - features/enum_conversion.md - - features/macros.md - - Types: - - features/types/index.md - - features/types/number_handling.md - - Integration: - - integration/index.md - - integration/cmake.md - - integration/package_managers.md - - integration/pkg-config.md - - API Documentation: - - basic_json: - - 'Overview': api/basic_json/index.md - - '(Constructor)': api/basic_json/basic_json.md - - '(Destructor)': api/basic_json/~basic_json.md - - 'accept': api/basic_json/accept.md - - 'array': api/basic_json/array.md - - 'array_t': api/basic_json/array_t.md - - 'at': api/basic_json/at.md - - 'back': api/basic_json/back.md - - 'begin': api/basic_json/begin.md - - 'binary': api/basic_json/binary.md - - 'binary_t': api/basic_json/binary_t.md - - 'boolean_t': api/basic_json/boolean_t.md - - 'cbegin': api/basic_json/cbegin.md - - 'cbor_tag_handler_t': api/basic_json/cbor_tag_handler_t.md - - 'cend': api/basic_json/cend.md - - 'clear': api/basic_json/clear.md - - 'contains': api/basic_json/contains.md - - 'count': api/basic_json/count.md - - 'crbegin': api/basic_json/crbegin.md - - 'crend': api/basic_json/crend.md - - 'default_object_comparator_t': api/basic_json/default_object_comparator_t.md - - 'diff': api/basic_json/diff.md - - 'dump': api/basic_json/dump.md - - 'emplace': api/basic_json/emplace.md - - 'emplace_back': api/basic_json/emplace_back.md - - 'empty': api/basic_json/empty.md - - 'end': api/basic_json/end.md - - 'erase': api/basic_json/erase.md - - 'error_handler_t': api/basic_json/error_handler_t.md - - 'exception': api/basic_json/exception.md - - 'find': api/basic_json/find.md - - 'flatten': api/basic_json/flatten.md - - 'from_bjdata': api/basic_json/from_bjdata.md - - 'from_bson': api/basic_json/from_bson.md - - 'from_cbor': api/basic_json/from_cbor.md - - 'from_msgpack': api/basic_json/from_msgpack.md - - 'from_ubjson': api/basic_json/from_ubjson.md - - 'front': api/basic_json/front.md - - 'get': api/basic_json/get.md - - 'get_allocator': api/basic_json/get_allocator.md - - 'get_binary': api/basic_json/get_binary.md - - 'get_ptr': api/basic_json/get_ptr.md - - 'get_ref': api/basic_json/get_ref.md - - 'get_to': api/basic_json/get_to.md - - 'std::hash<basic_json>': api/basic_json/std_hash.md - - 'input_format_t': api/basic_json/input_format_t.md - - 'insert': api/basic_json/insert.md - - 'invalid_iterator': api/basic_json/invalid_iterator.md - - 'is_array': api/basic_json/is_array.md - - 'is_binary': api/basic_json/is_binary.md - - 'is_boolean': api/basic_json/is_boolean.md - - 'is_discarded': api/basic_json/is_discarded.md - - 'is_null': api/basic_json/is_null.md - - 'is_number': api/basic_json/is_number.md - - 'is_number_float': api/basic_json/is_number_float.md - - 'is_number_integer': api/basic_json/is_number_integer.md - - 'is_number_unsigned': api/basic_json/is_number_unsigned.md - - 'is_object': api/basic_json/is_object.md - - 'is_primitive': api/basic_json/is_primitive.md - - 'is_string': api/basic_json/is_string.md - - 'is_structured': api/basic_json/is_structured.md - - 'items': api/basic_json/items.md - - 'json_serializer': api/basic_json/json_serializer.md - - 'max_size': api/basic_json/max_size.md - - 'meta': api/basic_json/meta.md - - 'merge_patch': api/basic_json/merge_patch.md - - 'number_float_t': api/basic_json/number_float_t.md - - 'number_integer_t': api/basic_json/number_integer_t.md - - 'number_unsigned_t': api/basic_json/number_unsigned_t.md - - 'object': api/basic_json/object.md - - 'object_comparator_t': api/basic_json/object_comparator_t.md - - 'object_t': api/basic_json/object_t.md - - 'operator ValueType': api/basic_json/operator_ValueType.md - - 'operator value_t': api/basic_json/operator_value_t.md - - 'operator[]': api/basic_json/operator[].md - - 'operator=': api/basic_json/operator=.md - - 'operator+=': api/basic_json/operator+=.md - - 'operator==': api/basic_json/operator_eq.md - - 'operator!=': api/basic_json/operator_ne.md - - 'operator<': api/basic_json/operator_lt.md - - 'operator>': api/basic_json/operator_gt.md - - 'operator<=': api/basic_json/operator_le.md - - 'operator>=': api/basic_json/operator_ge.md - - 'operator<=>': api/basic_json/operator_spaceship.md - - 'out_of_range': api/basic_json/out_of_range.md - - 'other_error': api/basic_json/other_error.md - - 'parse': api/basic_json/parse.md - - 'parse_error': api/basic_json/parse_error.md - - 'parse_event_t': api/basic_json/parse_event_t.md - - 'parser_callback_t': api/basic_json/parser_callback_t.md - - 'patch': api/basic_json/patch.md - - 'patch_inplace': api/basic_json/patch_inplace.md - - 'push_back': api/basic_json/push_back.md - - 'rbegin': api/basic_json/rbegin.md - - 'rend': api/basic_json/rend.md - - 'sax_parse': api/basic_json/sax_parse.md - - 'size': api/basic_json/size.md - - 'string_t': api/basic_json/string_t.md - - 'swap': api/basic_json/swap.md - - 'std::swap<basic_json>': api/basic_json/std_swap.md - - 'to_bjdata': api/basic_json/to_bjdata.md - - 'to_bson': api/basic_json/to_bson.md - - 'to_cbor': api/basic_json/to_cbor.md - - 'to_msgpack': api/basic_json/to_msgpack.md - - 'to_string': api/basic_json/to_string.md - - 'to_ubjson': api/basic_json/to_ubjson.md - - 'type': api/basic_json/type.md - - 'type_error': api/basic_json/type_error.md - - 'type_name': api/basic_json/type_name.md - - 'unflatten': api/basic_json/unflatten.md - - 'update': api/basic_json/update.md - - 'value': api/basic_json/value.md - - 'value_t': api/basic_json/value_t.md - - byte_container_with_subtype: - - 'Overview': api/byte_container_with_subtype/index.md - - '(constructor)': api/byte_container_with_subtype/byte_container_with_subtype.md - - 'clear_subtype': api/byte_container_with_subtype/clear_subtype.md - - 'has_subtype': api/byte_container_with_subtype/has_subtype.md - - 'set_subtype': api/byte_container_with_subtype/set_subtype.md - - 'subtype': api/byte_container_with_subtype/subtype.md - - adl_serializer: - - 'Overview': api/adl_serializer/index.md - - 'from_json': api/adl_serializer/from_json.md - - 'to_json': api/adl_serializer/to_json.md - - 'json': api/json.md - - json_pointer: - - 'Overview': api/json_pointer/index.md - - '(Constructor)': api/json_pointer/json_pointer.md - - 'back': api/json_pointer/back.md - - 'empty': api/json_pointer/empty.md - - 'operator string_t': api/json_pointer/operator_string_t.md - - 'operator==': api/json_pointer/operator_eq.md - - 'operator!=': api/json_pointer/operator_ne.md - - 'operator/': api/json_pointer/operator_slash.md - - 'operator/=': api/json_pointer/operator_slasheq.md - - 'parent_pointer': api/json_pointer/parent_pointer.md - - 'pop_back': api/json_pointer/pop_back.md - - 'push_back': api/json_pointer/push_back.md - - 'string_t': api/json_pointer/string_t.md - - 'to_string': api/json_pointer/to_string.md - - json_sax: - - 'Overview': api/json_sax/index.md - - 'binary': api/json_sax/binary.md - - 'boolean': api/json_sax/boolean.md - - 'end_array': api/json_sax/end_array.md - - 'end_object': api/json_sax/end_object.md - - 'key': api/json_sax/key.md - - 'null': api/json_sax/null.md - - 'number_float': api/json_sax/number_float.md - - 'number_integer': api/json_sax/number_integer.md - - 'number_unsigned': api/json_sax/number_unsigned.md - - 'parse_error': api/json_sax/parse_error.md - - 'start_array': api/json_sax/start_array.md - - 'start_object': api/json_sax/start_object.md - - 'string': api/json_sax/string.md - - 'operator<<(basic_json)': api/operator_ltlt.md - - 'operator<<(json_pointer)': api/operator_ltlt.md - - 'operator>>(basic_json)': api/operator_gtgt.md - - 'operator""_json': api/operator_literal_json.md - - 'operator""_json_pointer': api/operator_literal_json_pointer.md - - 'ordered_json': api/ordered_json.md - - 'ordered_map': api/ordered_map.md - - macros: - - 'Overview': api/macros/index.md - - 'JSON_ASSERT': api/macros/json_assert.md - - 'JSON_CATCH_USER': api/macros/json_throw_user.md - - 'JSON_DIAGNOSTICS': api/macros/json_diagnostics.md - - 'JSON_DISABLE_ENUM_SERIALIZATION': api/macros/json_disable_enum_serialization.md - - 'JSON_HAS_CPP_11': api/macros/json_has_cpp_11.md - - 'JSON_HAS_CPP_14': api/macros/json_has_cpp_11.md - - 'JSON_HAS_CPP_17': api/macros/json_has_cpp_11.md - - 'JSON_HAS_CPP_20': api/macros/json_has_cpp_11.md - - 'JSON_HAS_EXPERIMENTAL_FILESYSTEM': api/macros/json_has_filesystem.md - - 'JSON_HAS_FILESYSTEM': api/macros/json_has_filesystem.md - - 'JSON_HAS_RANGES': api/macros/json_has_ranges.md - - 'JSON_HAS_THREE_WAY_COMPARISON': api/macros/json_has_three_way_comparison.md - - 'JSON_NOEXCEPTION': api/macros/json_noexception.md - - 'JSON_NO_IO': api/macros/json_no_io.md - - 'JSON_SKIP_LIBRARY_VERSION_CHECK': api/macros/json_skip_library_version_check.md - - 'JSON_SKIP_UNSUPPORTED_COMPILER_CHECK': api/macros/json_skip_unsupported_compiler_check.md - - 'JSON_THROW_USER': api/macros/json_throw_user.md - - 'JSON_TRY_USER': api/macros/json_throw_user.md - - 'JSON_USE_GLOBAL_UDLS': api/macros/json_use_global_udls.md - - 'JSON_USE_IMPLICIT_CONVERSIONS': api/macros/json_use_implicit_conversions.md - - 'JSON_USE_LEGACY_DISCARDED_VALUE_COMPARISON': api/macros/json_use_legacy_discarded_value_comparison.md - - 'NLOHMANN_DEFINE_TYPE_INTRUSIVE': api/macros/nlohmann_define_type_intrusive.md - - 'NLOHMANN_DEFINE_TYPE_INTRUSIVE_WITH_DEFAULT': api/macros/nlohmann_define_type_intrusive.md - - 'NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE': api/macros/nlohmann_define_type_non_intrusive.md - - 'NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE_WITH_DEFAULT': api/macros/nlohmann_define_type_non_intrusive.md - - 'NLOHMANN_JSON_NAMESPACE': api/macros/nlohmann_json_namespace.md - - 'NLOHMANN_JSON_NAMESPACE_BEGIN': api/macros/nlohmann_json_namespace_begin.md - - 'NLOHMANN_JSON_NAMESPACE_END': api/macros/nlohmann_json_namespace_begin.md - - 'NLOHMANN_JSON_NAMESPACE_NO_VERSION': api/macros/nlohmann_json_namespace_no_version.md - - 'NLOHMANN_JSON_SERIALIZE_ENUM': api/macros/nlohmann_json_serialize_enum.md - - 'NLOHMANN_JSON_VERSION_MAJOR': api/macros/nlohmann_json_version_major.md - - 'NLOHMANN_JSON_VERSION_MINOR': api/macros/nlohmann_json_version_major.md - - 'NLOHMANN_JSON_VERSION_PATCH': api/macros/nlohmann_json_version_major.md - -# Extras -extra: - social: - - icon: fontawesome/brands/github - link: https://github.com/nlohmann - - icon: fontawesome/brands/twitter - link: https://twitter.com/nlohmann - - icon: fontawesome/brands/linkedin - link: https://www.linkedin.com/in/nielslohmann/ - - icon: fontawesome/brands/xing - link: https://www.xing.com/profile/Niels_Lohmann - - icon: fontawesome/brands/paypal - link: https://www.paypal.me/nlohmann - generator: false - -# Extensions -markdown_extensions: - - abbr - - admonition - - attr_list - - def_list - - codehilite: - guess_lang: false - - toc: - permalink: true - - pymdownx.arithmatex - - pymdownx.betterem: - smart_enable: all - - pymdownx.caret - - pymdownx.critic - - pymdownx.details - - pymdownx.emoji: - emoji_index: !!python/name:materialx.emoji.twemoji - emoji_generator: !!python/name:materialx.emoji.to_svg - - pymdownx.inlinehilite - - pymdownx.magiclink - - pymdownx.mark - #- pymdownx.smartsymbols - - pymdownx.superfences - - pymdownx.tasklist: - custom_checkbox: true - - pymdownx.tabbed - - pymdownx.tilde - - pymdownx.snippets: - base_path: docs - check_paths: true - - plantuml_markdown: - format: svg - -plugins: - - search: - separator: '[\s\-\.]' - lang: en - - minify: - minify_html: true - - git-revision-date-localized - - redirects: - redirect_maps: - 'api/basic_json/operator_gtgt.md': api/operator_gtgt.md - 'api/basic_json/operator_ltlt.md': api/operator_ltlt.md - 'api/basic_json/operator_literal_json.md': api/operator_literal_json.md - 'api/basic_json/operator_literal_json_pointer.md': api/operator_literal_json_pointer.md - 'api/json_pointer/operator_string.md': api/json_pointer/operator_string_t.md - -extra_css: - - css/custom.css - -extra_javascript: - - https://cdnjs.cloudflare.com/ajax/libs/mathjax/2.7.0/MathJax.js?config=TeX-MML-AM_CHTML diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/requirements.txt b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/requirements.txt deleted file mode 100644 index c1b232c..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/requirements.txt +++ /dev/null @@ -1,49 +0,0 @@ -Babel==2.10.3 -certifi==2022.6.15 -charset-normalizer==2.1.0 -click==8.1.3 -csscompressor==0.9.5 -future==0.18.2 -ghp-import==2.1.0 -gitdb==4.0.9 -GitPython==3.1.27 -htmlmin==0.1.12 -httplib2==0.20.4 -idna==3.3 -importlib-metadata==4.12.0 -Jinja2==3.1.2 -joblib==1.1.0 -jsmin==3.0.1 -livereload==2.6.3 -lunr==0.6.2 -Markdown==3.3.0 # pinned due to version conflict with markdown-include and mkdocs -markdown-include==0.7.0 -MarkupSafe==2.1.1 -mergedeep==1.3.4 -mkdocs==1.3.1 -mkdocs-git-revision-date-localized-plugin==1.1.0 -mkdocs-material==8.3.9 -mkdocs-material-extensions==1.0.3 -mkdocs-minify-plugin==0.5.0 -mkdocs-redirects==1.0.5 -mkdocs-simple-hooks==0.1.5 -nltk==3.7 -packaging==21.3 -plantuml==0.3.0 -plantuml-markdown==3.6.3 -Pygments==2.12.0 -pymdown-extensions==9.5 -pyparsing==3.0.9 -python-dateutil==2.8.2 -pytz==2022.1 -PyYAML==6.0 -pyyaml_env_tag==0.1 -regex==2022.7.25 -requests==2.28.1 -six==1.16.0 -smmap==5.0.0 -tornado==6.2 -tqdm==4.64.0 -urllib3==1.26.11 -watchdog==2.1.9 -zipp==3.8.1 diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/scripts/check_structure.py b/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/scripts/check_structure.py deleted file mode 100755 index 643482a..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/docs/mkdocs/scripts/check_structure.py +++ /dev/null @@ -1,179 +0,0 @@ -#!/usr/bin/env python - -import glob -import os.path -import re -import sys - -warnings = 0 - - -def report(rule, location, description): - global warnings - warnings += 1 - print(f'{warnings:3}. {location}: {description} [{rule}]') - - -def check_structure(): - expected_sections = [ - 'Template parameters', - 'Specializations', - 'Iterator invalidation', - 'Requirements', - 'Member types', - 'Member functions', - 'Member variables', - 'Static functions', - 'Non-member functions', - 'Literals', - 'Helper classes', - 'Parameters', - 'Return value', - 'Exception safety', - 'Exceptions', - 'Complexity', - 'Possible implementation', - 'Default definition', - 'Notes', - 'Examples', - 'See also', - 'Version history' - ] - - required_sections = [ - 'Examples', - 'Version history' - ] - - files = sorted(glob.glob('api/**/*.md', recursive=True)) - for file in files: - with open(file) as file_content: - section_idx = -1 # the index of the current h2 section - existing_sections = [] # the list of h2 sections in the file - in_initial_code_example = False # whether we are inside the first code example block - previous_line = None # the previous read line - h1sections = 0 # the number of h1 sections in the file - last_overload = 0 # the last seen overload number in the code example - documented_overloads = {} # the overloads that have been documented in the current block - current_section = None # the name of the current section - - for lineno, original_line in enumerate(file_content.readlines()): - line = original_line.strip() - - if line.startswith('# '): - h1sections += 1 - - # there should only be one top-level title - if h1sections > 1: - report('structure/unexpected_section', f'{file}:{lineno+1}', f'unexpected top-level title "{line}"') - h1sections = 1 - - # Overview pages should have a better title - if line == '# Overview': - report('style/title', f'{file}:{lineno+1}', 'overview pages should have a better title than "Overview"') - - # lines longer than 160 characters are bad (unless they are tables) - if len(line) > 160 and '|' not in line: - report('whitespace/line_length', f'{file}:{lineno+1} ({current_section})', f'line is too long ({len(line)} vs. 160 chars)') - - # sections in `` comments are treated as present - if line.startswith('') - existing_sections.append(current_section) - - # check if sections are correct - if line.startswith('## '): - # before starting a new section, check if the previous one documented all overloads - if current_section in documented_overloads and last_overload != 0: - if len(documented_overloads[current_section]) > 0 and len(documented_overloads[current_section]) != last_overload: - expected = list(range(1, last_overload+1)) - undocumented = [x for x in expected if x not in documented_overloads[current_section]] - unexpected = [x for x in documented_overloads[current_section] if x not in expected] - if len(undocumented): - report('style/numbering', f'{file}:{lineno} ({current_section})', f'undocumented overloads: {", ".join([f"({x})" for x in undocumented])}') - if len(unexpected): - report('style/numbering', f'{file}:{lineno} ({current_section})', f'unexpected overloads: {", ".join([f"({x})" for x in unexpected])}') - - current_section = line.strip('## ') - existing_sections.append(current_section) - - if current_section in expected_sections: - idx = expected_sections.index(current_section) - if idx <= section_idx: - report('structure/section_order', f'{file}:{lineno+1}', f'section "{current_section}" is in an unexpected order (should be before "{expected_sections[section_idx]}")') - section_idx = idx - else: - if 'index.md' not in file: # index.md files may have a different structure - report('structure/unknown_section', f'{file}:{lineno+1}', f'section "{current_section}" is not part of the expected sections') - - # collect the numbered items of the current section to later check if they match the number of overloads - if last_overload != 0 and not in_initial_code_example: - if len(original_line) and original_line[0].isdigit(): - number = int(re.findall(r"^(\d+).", original_line)[0]) - if current_section not in documented_overloads: - documented_overloads[current_section] = [] - documented_overloads[current_section].append(number) - - # code example - if line == '```cpp' and section_idx == -1: - in_initial_code_example = True - - if in_initial_code_example and line.startswith('//') and line not in ['// since C++20', '// until C++20']: - # check numbering of overloads - if any(map(str.isdigit, line)): - number = int(re.findall(r'\d+', line)[0]) - if number != last_overload + 1: - report('style/numbering', f'{file}:{lineno+1}', f'expected number ({number}) to be ({last_overload +1 })') - last_overload = number - - if any(map(str.isdigit, line)) and '(' not in line: - report('style/numbering', f'{file}:{lineno+1}', f'number should be in parentheses: {line}') - - if line == '```' and in_initial_code_example: - in_initial_code_example = False - - # consecutive blank lines are bad - if line == '' and previous_line == '': - report('whitespace/blank_lines', f'{file}:{lineno}-{lineno+1} ({current_section})', 'consecutive blank lines') - - # check that non-example admonitions have titles - untitled_admonition = re.match(r'^(\?\?\?|!!!) ([^ ]+)$', line) - if untitled_admonition and untitled_admonition.group(2) != 'example': - report('style/admonition_title', f'{file}:{lineno} ({current_section})', f'"{untitled_admonition.group(2)}" admonitions should have a title') - - previous_line = line - - if 'index.md' not in file: # index.md files may have a different structure - for required_section in required_sections: - if required_section not in existing_sections: - report('structure/missing_section', f'{file}:{lineno+1}', f'required section "{required_section}" was not found') - - -def check_examples(): - example_files = sorted(glob.glob('../../examples/*.cpp')) - markdown_files = sorted(glob.glob('**/*.md', recursive=True)) - - # check if every example file is used in at least one markdown file - for example_file in example_files: - example_file = os.path.join('examples', os.path.basename(example_file)) - - found = False - for markdown_file in markdown_files: - content = ' '.join(open(markdown_file).readlines()) - if example_file in content: - found = True - break - - if not found: - report('examples/missing', f'{example_file}', 'example file is not used in any documentation file') - - -if __name__ == '__main__': - print(120 * '-') - check_structure() - check_examples() - print(120 * '-') - - if warnings > 0: - sys.exit(1) diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/usages/ios.png b/app/jni/src/libultraship/extern/nlohmann-json/docs/usages/ios.png deleted file mode 100755 index 1d2c1b8..0000000 Binary files a/app/jni/src/libultraship/extern/nlohmann-json/docs/usages/ios.png and /dev/null differ diff --git a/app/jni/src/libultraship/extern/nlohmann-json/docs/usages/macos.png b/app/jni/src/libultraship/extern/nlohmann-json/docs/usages/macos.png deleted file mode 100644 index 107b5f0..0000000 Binary files a/app/jni/src/libultraship/extern/nlohmann-json/docs/usages/macos.png and /dev/null differ diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/adl_serializer.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/adl_serializer.hpp deleted file mode 100644 index f77f944..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/adl_serializer.hpp +++ /dev/null @@ -1,55 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -#include - -#include -#include -#include -#include - -NLOHMANN_JSON_NAMESPACE_BEGIN - -/// @sa https://json.nlohmann.me/api/adl_serializer/ -template -struct adl_serializer -{ - /// @brief convert a JSON value to any value type - /// @sa https://json.nlohmann.me/api/adl_serializer/from_json/ - template - static auto from_json(BasicJsonType && j, TargetType& val) noexcept( - noexcept(::nlohmann::from_json(std::forward(j), val))) - -> decltype(::nlohmann::from_json(std::forward(j), val), void()) - { - ::nlohmann::from_json(std::forward(j), val); - } - - /// @brief convert a JSON value to any value type - /// @sa https://json.nlohmann.me/api/adl_serializer/from_json/ - template - static auto from_json(BasicJsonType && j) noexcept( - noexcept(::nlohmann::from_json(std::forward(j), detail::identity_tag {}))) - -> decltype(::nlohmann::from_json(std::forward(j), detail::identity_tag {})) - { - return ::nlohmann::from_json(std::forward(j), detail::identity_tag {}); - } - - /// @brief convert any value type to a JSON value - /// @sa https://json.nlohmann.me/api/adl_serializer/to_json/ - template - static auto to_json(BasicJsonType& j, TargetType && val) noexcept( - noexcept(::nlohmann::to_json(j, std::forward(val)))) - -> decltype(::nlohmann::to_json(j, std::forward(val)), void()) - { - ::nlohmann::to_json(j, std::forward(val)); - } -}; - -NLOHMANN_JSON_NAMESPACE_END diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/byte_container_with_subtype.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/byte_container_with_subtype.hpp deleted file mode 100644 index 1031cdc..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/byte_container_with_subtype.hpp +++ /dev/null @@ -1,103 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -#include // uint8_t, uint64_t -#include // tie -#include // move - -#include - -NLOHMANN_JSON_NAMESPACE_BEGIN - -/// @brief an internal type for a backed binary type -/// @sa https://json.nlohmann.me/api/byte_container_with_subtype/ -template -class byte_container_with_subtype : public BinaryType -{ - public: - using container_type = BinaryType; - using subtype_type = std::uint64_t; - - /// @sa https://json.nlohmann.me/api/byte_container_with_subtype/byte_container_with_subtype/ - byte_container_with_subtype() noexcept(noexcept(container_type())) - : container_type() - {} - - /// @sa https://json.nlohmann.me/api/byte_container_with_subtype/byte_container_with_subtype/ - byte_container_with_subtype(const container_type& b) noexcept(noexcept(container_type(b))) - : container_type(b) - {} - - /// @sa https://json.nlohmann.me/api/byte_container_with_subtype/byte_container_with_subtype/ - byte_container_with_subtype(container_type&& b) noexcept(noexcept(container_type(std::move(b)))) - : container_type(std::move(b)) - {} - - /// @sa https://json.nlohmann.me/api/byte_container_with_subtype/byte_container_with_subtype/ - byte_container_with_subtype(const container_type& b, subtype_type subtype_) noexcept(noexcept(container_type(b))) - : container_type(b) - , m_subtype(subtype_) - , m_has_subtype(true) - {} - - /// @sa https://json.nlohmann.me/api/byte_container_with_subtype/byte_container_with_subtype/ - byte_container_with_subtype(container_type&& b, subtype_type subtype_) noexcept(noexcept(container_type(std::move(b)))) - : container_type(std::move(b)) - , m_subtype(subtype_) - , m_has_subtype(true) - {} - - bool operator==(const byte_container_with_subtype& rhs) const - { - return std::tie(static_cast(*this), m_subtype, m_has_subtype) == - std::tie(static_cast(rhs), rhs.m_subtype, rhs.m_has_subtype); - } - - bool operator!=(const byte_container_with_subtype& rhs) const - { - return !(rhs == *this); - } - - /// @brief sets the binary subtype - /// @sa https://json.nlohmann.me/api/byte_container_with_subtype/set_subtype/ - void set_subtype(subtype_type subtype_) noexcept - { - m_subtype = subtype_; - m_has_subtype = true; - } - - /// @brief return the binary subtype - /// @sa https://json.nlohmann.me/api/byte_container_with_subtype/subtype/ - constexpr subtype_type subtype() const noexcept - { - return m_has_subtype ? m_subtype : static_cast(-1); - } - - /// @brief return whether the value has a subtype - /// @sa https://json.nlohmann.me/api/byte_container_with_subtype/has_subtype/ - constexpr bool has_subtype() const noexcept - { - return m_has_subtype; - } - - /// @brief clears the binary subtype - /// @sa https://json.nlohmann.me/api/byte_container_with_subtype/clear_subtype/ - void clear_subtype() noexcept - { - m_subtype = 0; - m_has_subtype = false; - } - - private: - subtype_type m_subtype = 0; - bool m_has_subtype = false; -}; - -NLOHMANN_JSON_NAMESPACE_END diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/abi_macros.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/abi_macros.hpp deleted file mode 100644 index 0d3108d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/abi_macros.hpp +++ /dev/null @@ -1,100 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -// This file contains all macro definitions affecting or depending on the ABI - -#ifndef JSON_SKIP_LIBRARY_VERSION_CHECK - #if defined(NLOHMANN_JSON_VERSION_MAJOR) && defined(NLOHMANN_JSON_VERSION_MINOR) && defined(NLOHMANN_JSON_VERSION_PATCH) - #if NLOHMANN_JSON_VERSION_MAJOR != 3 || NLOHMANN_JSON_VERSION_MINOR != 11 || NLOHMANN_JSON_VERSION_PATCH != 2 - #warning "Already included a different version of the library!" - #endif - #endif -#endif - -#define NLOHMANN_JSON_VERSION_MAJOR 3 // NOLINT(modernize-macro-to-enum) -#define NLOHMANN_JSON_VERSION_MINOR 11 // NOLINT(modernize-macro-to-enum) -#define NLOHMANN_JSON_VERSION_PATCH 2 // NOLINT(modernize-macro-to-enum) - -#ifndef JSON_DIAGNOSTICS - #define JSON_DIAGNOSTICS 0 -#endif - -#ifndef JSON_USE_LEGACY_DISCARDED_VALUE_COMPARISON - #define JSON_USE_LEGACY_DISCARDED_VALUE_COMPARISON 0 -#endif - -#if JSON_DIAGNOSTICS - #define NLOHMANN_JSON_ABI_TAG_DIAGNOSTICS _diag -#else - #define NLOHMANN_JSON_ABI_TAG_DIAGNOSTICS -#endif - -#if JSON_USE_LEGACY_DISCARDED_VALUE_COMPARISON - #define NLOHMANN_JSON_ABI_TAG_LEGACY_DISCARDED_VALUE_COMPARISON _ldvcmp -#else - #define NLOHMANN_JSON_ABI_TAG_LEGACY_DISCARDED_VALUE_COMPARISON -#endif - -#ifndef NLOHMANN_JSON_NAMESPACE_NO_VERSION - #define NLOHMANN_JSON_NAMESPACE_NO_VERSION 0 -#endif - -// Construct the namespace ABI tags component -#define NLOHMANN_JSON_ABI_TAGS_CONCAT_EX(a, b) json_abi ## a ## b -#define NLOHMANN_JSON_ABI_TAGS_CONCAT(a, b) \ - NLOHMANN_JSON_ABI_TAGS_CONCAT_EX(a, b) - -#define NLOHMANN_JSON_ABI_TAGS \ - NLOHMANN_JSON_ABI_TAGS_CONCAT( \ - NLOHMANN_JSON_ABI_TAG_DIAGNOSTICS, \ - NLOHMANN_JSON_ABI_TAG_LEGACY_DISCARDED_VALUE_COMPARISON) - -// Construct the namespace version component -#define NLOHMANN_JSON_NAMESPACE_VERSION_CONCAT_EX(major, minor, patch) \ - _v ## major ## _ ## minor ## _ ## patch -#define NLOHMANN_JSON_NAMESPACE_VERSION_CONCAT(major, minor, patch) \ - NLOHMANN_JSON_NAMESPACE_VERSION_CONCAT_EX(major, minor, patch) - -#if NLOHMANN_JSON_NAMESPACE_NO_VERSION -#define NLOHMANN_JSON_NAMESPACE_VERSION -#else -#define NLOHMANN_JSON_NAMESPACE_VERSION \ - NLOHMANN_JSON_NAMESPACE_VERSION_CONCAT(NLOHMANN_JSON_VERSION_MAJOR, \ - NLOHMANN_JSON_VERSION_MINOR, \ - NLOHMANN_JSON_VERSION_PATCH) -#endif - -// Combine namespace components -#define NLOHMANN_JSON_NAMESPACE_CONCAT_EX(a, b) a ## b -#define NLOHMANN_JSON_NAMESPACE_CONCAT(a, b) \ - NLOHMANN_JSON_NAMESPACE_CONCAT_EX(a, b) - -#ifndef NLOHMANN_JSON_NAMESPACE -#define NLOHMANN_JSON_NAMESPACE \ - nlohmann::NLOHMANN_JSON_NAMESPACE_CONCAT( \ - NLOHMANN_JSON_ABI_TAGS, \ - NLOHMANN_JSON_NAMESPACE_VERSION) -#endif - -#ifndef NLOHMANN_JSON_NAMESPACE_BEGIN -#define NLOHMANN_JSON_NAMESPACE_BEGIN \ - namespace nlohmann \ - { \ - inline namespace NLOHMANN_JSON_NAMESPACE_CONCAT( \ - NLOHMANN_JSON_ABI_TAGS, \ - NLOHMANN_JSON_NAMESPACE_VERSION) \ - { -#endif - -#ifndef NLOHMANN_JSON_NAMESPACE_END -#define NLOHMANN_JSON_NAMESPACE_END \ - } /* namespace (inline namespace) NOLINT(readability/namespace) */ \ - } // namespace nlohmann -#endif diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/conversions/from_json.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/conversions/from_json.hpp deleted file mode 100644 index c6299aa..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/conversions/from_json.hpp +++ /dev/null @@ -1,497 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -#include // transform -#include // array -#include // forward_list -#include // inserter, front_inserter, end -#include // map -#include // string -#include // tuple, make_tuple -#include // is_arithmetic, is_same, is_enum, underlying_type, is_convertible -#include // unordered_map -#include // pair, declval -#include // valarray - -#include -#include -#include -#include -#include -#include -#include -#include - -NLOHMANN_JSON_NAMESPACE_BEGIN -namespace detail -{ - -template -inline void from_json(const BasicJsonType& j, typename std::nullptr_t& n) -{ - if (JSON_HEDLEY_UNLIKELY(!j.is_null())) - { - JSON_THROW(type_error::create(302, concat("type must be null, but is ", j.type_name()), &j)); - } - n = nullptr; -} - -// overloads for basic_json template parameters -template < typename BasicJsonType, typename ArithmeticType, - enable_if_t < std::is_arithmetic::value&& - !std::is_same::value, - int > = 0 > -void get_arithmetic_value(const BasicJsonType& j, ArithmeticType& val) -{ - switch (static_cast(j)) - { - case value_t::number_unsigned: - { - val = static_cast(*j.template get_ptr()); - break; - } - case value_t::number_integer: - { - val = static_cast(*j.template get_ptr()); - break; - } - case value_t::number_float: - { - val = static_cast(*j.template get_ptr()); - break; - } - - case value_t::null: - case value_t::object: - case value_t::array: - case value_t::string: - case value_t::boolean: - case value_t::binary: - case value_t::discarded: - default: - JSON_THROW(type_error::create(302, concat("type must be number, but is ", j.type_name()), &j)); - } -} - -template -inline void from_json(const BasicJsonType& j, typename BasicJsonType::boolean_t& b) -{ - if (JSON_HEDLEY_UNLIKELY(!j.is_boolean())) - { - JSON_THROW(type_error::create(302, concat("type must be boolean, but is ", j.type_name()), &j)); - } - b = *j.template get_ptr(); -} - -template -inline void from_json(const BasicJsonType& j, typename BasicJsonType::string_t& s) -{ - if (JSON_HEDLEY_UNLIKELY(!j.is_string())) - { - JSON_THROW(type_error::create(302, concat("type must be string, but is ", j.type_name()), &j)); - } - s = *j.template get_ptr(); -} - -template < - typename BasicJsonType, typename StringType, - enable_if_t < - std::is_assignable::value - && is_detected_exact::value - && !std::is_same::value - && !is_json_ref::value, int > = 0 > -inline void from_json(const BasicJsonType& j, StringType& s) -{ - if (JSON_HEDLEY_UNLIKELY(!j.is_string())) - { - JSON_THROW(type_error::create(302, concat("type must be string, but is ", j.type_name()), &j)); - } - - s = *j.template get_ptr(); -} - -template -inline void from_json(const BasicJsonType& j, typename BasicJsonType::number_float_t& val) -{ - get_arithmetic_value(j, val); -} - -template -inline void from_json(const BasicJsonType& j, typename BasicJsonType::number_unsigned_t& val) -{ - get_arithmetic_value(j, val); -} - -template -inline void from_json(const BasicJsonType& j, typename BasicJsonType::number_integer_t& val) -{ - get_arithmetic_value(j, val); -} - -#if !JSON_DISABLE_ENUM_SERIALIZATION -template::value, int> = 0> -inline void from_json(const BasicJsonType& j, EnumType& e) -{ - typename std::underlying_type::type val; - get_arithmetic_value(j, val); - e = static_cast(val); -} -#endif // JSON_DISABLE_ENUM_SERIALIZATION - -// forward_list doesn't have an insert method -template::value, int> = 0> -inline void from_json(const BasicJsonType& j, std::forward_list& l) -{ - if (JSON_HEDLEY_UNLIKELY(!j.is_array())) - { - JSON_THROW(type_error::create(302, concat("type must be array, but is ", j.type_name()), &j)); - } - l.clear(); - std::transform(j.rbegin(), j.rend(), - std::front_inserter(l), [](const BasicJsonType & i) - { - return i.template get(); - }); -} - -// valarray doesn't have an insert method -template::value, int> = 0> -inline void from_json(const BasicJsonType& j, std::valarray& l) -{ - if (JSON_HEDLEY_UNLIKELY(!j.is_array())) - { - JSON_THROW(type_error::create(302, concat("type must be array, but is ", j.type_name()), &j)); - } - l.resize(j.size()); - std::transform(j.begin(), j.end(), std::begin(l), - [](const BasicJsonType & elem) - { - return elem.template get(); - }); -} - -template -auto from_json(const BasicJsonType& j, T (&arr)[N]) // NOLINT(cppcoreguidelines-avoid-c-arrays,hicpp-avoid-c-arrays,modernize-avoid-c-arrays) --> decltype(j.template get(), void()) -{ - for (std::size_t i = 0; i < N; ++i) - { - arr[i] = j.at(i).template get(); - } -} - -template -inline void from_json_array_impl(const BasicJsonType& j, typename BasicJsonType::array_t& arr, priority_tag<3> /*unused*/) -{ - arr = *j.template get_ptr(); -} - -template -auto from_json_array_impl(const BasicJsonType& j, std::array& arr, - priority_tag<2> /*unused*/) --> decltype(j.template get(), void()) -{ - for (std::size_t i = 0; i < N; ++i) - { - arr[i] = j.at(i).template get(); - } -} - -template::value, - int> = 0> -auto from_json_array_impl(const BasicJsonType& j, ConstructibleArrayType& arr, priority_tag<1> /*unused*/) --> decltype( - arr.reserve(std::declval()), - j.template get(), - void()) -{ - using std::end; - - ConstructibleArrayType ret; - ret.reserve(j.size()); - std::transform(j.begin(), j.end(), - std::inserter(ret, end(ret)), [](const BasicJsonType & i) - { - // get() returns *this, this won't call a from_json - // method when value_type is BasicJsonType - return i.template get(); - }); - arr = std::move(ret); -} - -template::value, - int> = 0> -inline void from_json_array_impl(const BasicJsonType& j, ConstructibleArrayType& arr, - priority_tag<0> /*unused*/) -{ - using std::end; - - ConstructibleArrayType ret; - std::transform( - j.begin(), j.end(), std::inserter(ret, end(ret)), - [](const BasicJsonType & i) - { - // get() returns *this, this won't call a from_json - // method when value_type is BasicJsonType - return i.template get(); - }); - arr = std::move(ret); -} - -template < typename BasicJsonType, typename ConstructibleArrayType, - enable_if_t < - is_constructible_array_type::value&& - !is_constructible_object_type::value&& - !is_constructible_string_type::value&& - !std::is_same::value&& - !is_basic_json::value, - int > = 0 > -auto from_json(const BasicJsonType& j, ConstructibleArrayType& arr) --> decltype(from_json_array_impl(j, arr, priority_tag<3> {}), -j.template get(), -void()) -{ - if (JSON_HEDLEY_UNLIKELY(!j.is_array())) - { - JSON_THROW(type_error::create(302, concat("type must be array, but is ", j.type_name()), &j)); - } - - from_json_array_impl(j, arr, priority_tag<3> {}); -} - -template < typename BasicJsonType, typename T, std::size_t... Idx > -std::array from_json_inplace_array_impl(BasicJsonType&& j, - identity_tag> /*unused*/, index_sequence /*unused*/) -{ - return { { std::forward(j).at(Idx).template get()... } }; -} - -template < typename BasicJsonType, typename T, std::size_t N > -auto from_json(BasicJsonType&& j, identity_tag> tag) --> decltype(from_json_inplace_array_impl(std::forward(j), tag, make_index_sequence {})) -{ - if (JSON_HEDLEY_UNLIKELY(!j.is_array())) - { - JSON_THROW(type_error::create(302, concat("type must be array, but is ", j.type_name()), &j)); - } - - return from_json_inplace_array_impl(std::forward(j), tag, make_index_sequence {}); -} - -template -inline void from_json(const BasicJsonType& j, typename BasicJsonType::binary_t& bin) -{ - if (JSON_HEDLEY_UNLIKELY(!j.is_binary())) - { - JSON_THROW(type_error::create(302, concat("type must be binary, but is ", j.type_name()), &j)); - } - - bin = *j.template get_ptr(); -} - -template::value, int> = 0> -inline void from_json(const BasicJsonType& j, ConstructibleObjectType& obj) -{ - if (JSON_HEDLEY_UNLIKELY(!j.is_object())) - { - JSON_THROW(type_error::create(302, concat("type must be object, but is ", j.type_name()), &j)); - } - - ConstructibleObjectType ret; - const auto* inner_object = j.template get_ptr(); - using value_type = typename ConstructibleObjectType::value_type; - std::transform( - inner_object->begin(), inner_object->end(), - std::inserter(ret, ret.begin()), - [](typename BasicJsonType::object_t::value_type const & p) - { - return value_type(p.first, p.second.template get()); - }); - obj = std::move(ret); -} - -// overload for arithmetic types, not chosen for basic_json template arguments -// (BooleanType, etc..); note: Is it really necessary to provide explicit -// overloads for boolean_t etc. in case of a custom BooleanType which is not -// an arithmetic type? -template < typename BasicJsonType, typename ArithmeticType, - enable_if_t < - std::is_arithmetic::value&& - !std::is_same::value&& - !std::is_same::value&& - !std::is_same::value&& - !std::is_same::value, - int > = 0 > -inline void from_json(const BasicJsonType& j, ArithmeticType& val) -{ - switch (static_cast(j)) - { - case value_t::number_unsigned: - { - val = static_cast(*j.template get_ptr()); - break; - } - case value_t::number_integer: - { - val = static_cast(*j.template get_ptr()); - break; - } - case value_t::number_float: - { - val = static_cast(*j.template get_ptr()); - break; - } - case value_t::boolean: - { - val = static_cast(*j.template get_ptr()); - break; - } - - case value_t::null: - case value_t::object: - case value_t::array: - case value_t::string: - case value_t::binary: - case value_t::discarded: - default: - JSON_THROW(type_error::create(302, concat("type must be number, but is ", j.type_name()), &j)); - } -} - -template -std::tuple from_json_tuple_impl_base(BasicJsonType&& j, index_sequence /*unused*/) -{ - return std::make_tuple(std::forward(j).at(Idx).template get()...); -} - -template < typename BasicJsonType, class A1, class A2 > -std::pair from_json_tuple_impl(BasicJsonType&& j, identity_tag> /*unused*/, priority_tag<0> /*unused*/) -{ - return {std::forward(j).at(0).template get(), - std::forward(j).at(1).template get()}; -} - -template -inline void from_json_tuple_impl(BasicJsonType&& j, std::pair& p, priority_tag<1> /*unused*/) -{ - p = from_json_tuple_impl(std::forward(j), identity_tag> {}, priority_tag<0> {}); -} - -template -std::tuple from_json_tuple_impl(BasicJsonType&& j, identity_tag> /*unused*/, priority_tag<2> /*unused*/) -{ - return from_json_tuple_impl_base(std::forward(j), index_sequence_for {}); -} - -template -inline void from_json_tuple_impl(BasicJsonType&& j, std::tuple& t, priority_tag<3> /*unused*/) -{ - t = from_json_tuple_impl_base(std::forward(j), index_sequence_for {}); -} - -template -auto from_json(BasicJsonType&& j, TupleRelated&& t) --> decltype(from_json_tuple_impl(std::forward(j), std::forward(t), priority_tag<3> {})) -{ - if (JSON_HEDLEY_UNLIKELY(!j.is_array())) - { - JSON_THROW(type_error::create(302, concat("type must be array, but is ", j.type_name()), &j)); - } - - return from_json_tuple_impl(std::forward(j), std::forward(t), priority_tag<3> {}); -} - -template < typename BasicJsonType, typename Key, typename Value, typename Compare, typename Allocator, - typename = enable_if_t < !std::is_constructible < - typename BasicJsonType::string_t, Key >::value >> -inline void from_json(const BasicJsonType& j, std::map& m) -{ - if (JSON_HEDLEY_UNLIKELY(!j.is_array())) - { - JSON_THROW(type_error::create(302, concat("type must be array, but is ", j.type_name()), &j)); - } - m.clear(); - for (const auto& p : j) - { - if (JSON_HEDLEY_UNLIKELY(!p.is_array())) - { - JSON_THROW(type_error::create(302, concat("type must be array, but is ", p.type_name()), &j)); - } - m.emplace(p.at(0).template get(), p.at(1).template get()); - } -} - -template < typename BasicJsonType, typename Key, typename Value, typename Hash, typename KeyEqual, typename Allocator, - typename = enable_if_t < !std::is_constructible < - typename BasicJsonType::string_t, Key >::value >> -inline void from_json(const BasicJsonType& j, std::unordered_map& m) -{ - if (JSON_HEDLEY_UNLIKELY(!j.is_array())) - { - JSON_THROW(type_error::create(302, concat("type must be array, but is ", j.type_name()), &j)); - } - m.clear(); - for (const auto& p : j) - { - if (JSON_HEDLEY_UNLIKELY(!p.is_array())) - { - JSON_THROW(type_error::create(302, concat("type must be array, but is ", p.type_name()), &j)); - } - m.emplace(p.at(0).template get(), p.at(1).template get()); - } -} - -#if JSON_HAS_FILESYSTEM || JSON_HAS_EXPERIMENTAL_FILESYSTEM -template -inline void from_json(const BasicJsonType& j, std_fs::path& p) -{ - if (JSON_HEDLEY_UNLIKELY(!j.is_string())) - { - JSON_THROW(type_error::create(302, concat("type must be string, but is ", j.type_name()), &j)); - } - p = *j.template get_ptr(); -} -#endif - -struct from_json_fn -{ - template - auto operator()(const BasicJsonType& j, T&& val) const - noexcept(noexcept(from_json(j, std::forward(val)))) - -> decltype(from_json(j, std::forward(val))) - { - return from_json(j, std::forward(val)); - } -}; - -} // namespace detail - -#ifndef JSON_HAS_CPP_17 -/// namespace to hold default `from_json` function -/// to see why this is required: -/// http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2015/n4381.html -namespace // NOLINT(cert-dcl59-cpp,fuchsia-header-anon-namespaces,google-build-namespaces) -{ -#endif -JSON_INLINE_VARIABLE constexpr const auto& from_json = // NOLINT(misc-definitions-in-headers) - detail::static_const::value; -#ifndef JSON_HAS_CPP_17 -} // namespace -#endif - -NLOHMANN_JSON_NAMESPACE_END diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/conversions/to_chars.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/conversions/to_chars.hpp deleted file mode 100644 index febef93..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/conversions/to_chars.hpp +++ /dev/null @@ -1,1118 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2009 Florian Loitsch -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -#include // array -#include // signbit, isfinite -#include // intN_t, uintN_t -#include // memcpy, memmove -#include // numeric_limits -#include // conditional - -#include - -NLOHMANN_JSON_NAMESPACE_BEGIN -namespace detail -{ - -/*! -@brief implements the Grisu2 algorithm for binary to decimal floating-point -conversion. - -This implementation is a slightly modified version of the reference -implementation which may be obtained from -http://florian.loitsch.com/publications (bench.tar.gz). - -The code is distributed under the MIT license, Copyright (c) 2009 Florian Loitsch. - -For a detailed description of the algorithm see: - -[1] Loitsch, "Printing Floating-Point Numbers Quickly and Accurately with - Integers", Proceedings of the ACM SIGPLAN 2010 Conference on Programming - Language Design and Implementation, PLDI 2010 -[2] Burger, Dybvig, "Printing Floating-Point Numbers Quickly and Accurately", - Proceedings of the ACM SIGPLAN 1996 Conference on Programming Language - Design and Implementation, PLDI 1996 -*/ -namespace dtoa_impl -{ - -template -Target reinterpret_bits(const Source source) -{ - static_assert(sizeof(Target) == sizeof(Source), "size mismatch"); - - Target target; - std::memcpy(&target, &source, sizeof(Source)); - return target; -} - -struct diyfp // f * 2^e -{ - static constexpr int kPrecision = 64; // = q - - std::uint64_t f = 0; - int e = 0; - - constexpr diyfp(std::uint64_t f_, int e_) noexcept : f(f_), e(e_) {} - - /*! - @brief returns x - y - @pre x.e == y.e and x.f >= y.f - */ - static diyfp sub(const diyfp& x, const diyfp& y) noexcept - { - JSON_ASSERT(x.e == y.e); - JSON_ASSERT(x.f >= y.f); - - return {x.f - y.f, x.e}; - } - - /*! - @brief returns x * y - @note The result is rounded. (Only the upper q bits are returned.) - */ - static diyfp mul(const diyfp& x, const diyfp& y) noexcept - { - static_assert(kPrecision == 64, "internal error"); - - // Computes: - // f = round((x.f * y.f) / 2^q) - // e = x.e + y.e + q - - // Emulate the 64-bit * 64-bit multiplication: - // - // p = u * v - // = (u_lo + 2^32 u_hi) (v_lo + 2^32 v_hi) - // = (u_lo v_lo ) + 2^32 ((u_lo v_hi ) + (u_hi v_lo )) + 2^64 (u_hi v_hi ) - // = (p0 ) + 2^32 ((p1 ) + (p2 )) + 2^64 (p3 ) - // = (p0_lo + 2^32 p0_hi) + 2^32 ((p1_lo + 2^32 p1_hi) + (p2_lo + 2^32 p2_hi)) + 2^64 (p3 ) - // = (p0_lo ) + 2^32 (p0_hi + p1_lo + p2_lo ) + 2^64 (p1_hi + p2_hi + p3) - // = (p0_lo ) + 2^32 (Q ) + 2^64 (H ) - // = (p0_lo ) + 2^32 (Q_lo + 2^32 Q_hi ) + 2^64 (H ) - // - // (Since Q might be larger than 2^32 - 1) - // - // = (p0_lo + 2^32 Q_lo) + 2^64 (Q_hi + H) - // - // (Q_hi + H does not overflow a 64-bit int) - // - // = p_lo + 2^64 p_hi - - const std::uint64_t u_lo = x.f & 0xFFFFFFFFu; - const std::uint64_t u_hi = x.f >> 32u; - const std::uint64_t v_lo = y.f & 0xFFFFFFFFu; - const std::uint64_t v_hi = y.f >> 32u; - - const std::uint64_t p0 = u_lo * v_lo; - const std::uint64_t p1 = u_lo * v_hi; - const std::uint64_t p2 = u_hi * v_lo; - const std::uint64_t p3 = u_hi * v_hi; - - const std::uint64_t p0_hi = p0 >> 32u; - const std::uint64_t p1_lo = p1 & 0xFFFFFFFFu; - const std::uint64_t p1_hi = p1 >> 32u; - const std::uint64_t p2_lo = p2 & 0xFFFFFFFFu; - const std::uint64_t p2_hi = p2 >> 32u; - - std::uint64_t Q = p0_hi + p1_lo + p2_lo; - - // The full product might now be computed as - // - // p_hi = p3 + p2_hi + p1_hi + (Q >> 32) - // p_lo = p0_lo + (Q << 32) - // - // But in this particular case here, the full p_lo is not required. - // Effectively we only need to add the highest bit in p_lo to p_hi (and - // Q_hi + 1 does not overflow). - - Q += std::uint64_t{1} << (64u - 32u - 1u); // round, ties up - - const std::uint64_t h = p3 + p2_hi + p1_hi + (Q >> 32u); - - return {h, x.e + y.e + 64}; - } - - /*! - @brief normalize x such that the significand is >= 2^(q-1) - @pre x.f != 0 - */ - static diyfp normalize(diyfp x) noexcept - { - JSON_ASSERT(x.f != 0); - - while ((x.f >> 63u) == 0) - { - x.f <<= 1u; - x.e--; - } - - return x; - } - - /*! - @brief normalize x such that the result has the exponent E - @pre e >= x.e and the upper e - x.e bits of x.f must be zero. - */ - static diyfp normalize_to(const diyfp& x, const int target_exponent) noexcept - { - const int delta = x.e - target_exponent; - - JSON_ASSERT(delta >= 0); - JSON_ASSERT(((x.f << delta) >> delta) == x.f); - - return {x.f << delta, target_exponent}; - } -}; - -struct boundaries -{ - diyfp w; - diyfp minus; - diyfp plus; -}; - -/*! -Compute the (normalized) diyfp representing the input number 'value' and its -boundaries. - -@pre value must be finite and positive -*/ -template -boundaries compute_boundaries(FloatType value) -{ - JSON_ASSERT(std::isfinite(value)); - JSON_ASSERT(value > 0); - - // Convert the IEEE representation into a diyfp. - // - // If v is denormal: - // value = 0.F * 2^(1 - bias) = ( F) * 2^(1 - bias - (p-1)) - // If v is normalized: - // value = 1.F * 2^(E - bias) = (2^(p-1) + F) * 2^(E - bias - (p-1)) - - static_assert(std::numeric_limits::is_iec559, - "internal error: dtoa_short requires an IEEE-754 floating-point implementation"); - - constexpr int kPrecision = std::numeric_limits::digits; // = p (includes the hidden bit) - constexpr int kBias = std::numeric_limits::max_exponent - 1 + (kPrecision - 1); - constexpr int kMinExp = 1 - kBias; - constexpr std::uint64_t kHiddenBit = std::uint64_t{1} << (kPrecision - 1); // = 2^(p-1) - - using bits_type = typename std::conditional::type; - - const auto bits = static_cast(reinterpret_bits(value)); - const std::uint64_t E = bits >> (kPrecision - 1); - const std::uint64_t F = bits & (kHiddenBit - 1); - - const bool is_denormal = E == 0; - const diyfp v = is_denormal - ? diyfp(F, kMinExp) - : diyfp(F + kHiddenBit, static_cast(E) - kBias); - - // Compute the boundaries m- and m+ of the floating-point value - // v = f * 2^e. - // - // Determine v- and v+, the floating-point predecessor and successor if v, - // respectively. - // - // v- = v - 2^e if f != 2^(p-1) or e == e_min (A) - // = v - 2^(e-1) if f == 2^(p-1) and e > e_min (B) - // - // v+ = v + 2^e - // - // Let m- = (v- + v) / 2 and m+ = (v + v+) / 2. All real numbers _strictly_ - // between m- and m+ round to v, regardless of how the input rounding - // algorithm breaks ties. - // - // ---+-------------+-------------+-------------+-------------+--- (A) - // v- m- v m+ v+ - // - // -----------------+------+------+-------------+-------------+--- (B) - // v- m- v m+ v+ - - const bool lower_boundary_is_closer = F == 0 && E > 1; - const diyfp m_plus = diyfp(2 * v.f + 1, v.e - 1); - const diyfp m_minus = lower_boundary_is_closer - ? diyfp(4 * v.f - 1, v.e - 2) // (B) - : diyfp(2 * v.f - 1, v.e - 1); // (A) - - // Determine the normalized w+ = m+. - const diyfp w_plus = diyfp::normalize(m_plus); - - // Determine w- = m- such that e_(w-) = e_(w+). - const diyfp w_minus = diyfp::normalize_to(m_minus, w_plus.e); - - return {diyfp::normalize(v), w_minus, w_plus}; -} - -// Given normalized diyfp w, Grisu needs to find a (normalized) cached -// power-of-ten c, such that the exponent of the product c * w = f * 2^e lies -// within a certain range [alpha, gamma] (Definition 3.2 from [1]) -// -// alpha <= e = e_c + e_w + q <= gamma -// -// or -// -// f_c * f_w * 2^alpha <= f_c 2^(e_c) * f_w 2^(e_w) * 2^q -// <= f_c * f_w * 2^gamma -// -// Since c and w are normalized, i.e. 2^(q-1) <= f < 2^q, this implies -// -// 2^(q-1) * 2^(q-1) * 2^alpha <= c * w * 2^q < 2^q * 2^q * 2^gamma -// -// or -// -// 2^(q - 2 + alpha) <= c * w < 2^(q + gamma) -// -// The choice of (alpha,gamma) determines the size of the table and the form of -// the digit generation procedure. Using (alpha,gamma)=(-60,-32) works out well -// in practice: -// -// The idea is to cut the number c * w = f * 2^e into two parts, which can be -// processed independently: An integral part p1, and a fractional part p2: -// -// f * 2^e = ( (f div 2^-e) * 2^-e + (f mod 2^-e) ) * 2^e -// = (f div 2^-e) + (f mod 2^-e) * 2^e -// = p1 + p2 * 2^e -// -// The conversion of p1 into decimal form requires a series of divisions and -// modulos by (a power of) 10. These operations are faster for 32-bit than for -// 64-bit integers, so p1 should ideally fit into a 32-bit integer. This can be -// achieved by choosing -// -// -e >= 32 or e <= -32 := gamma -// -// In order to convert the fractional part -// -// p2 * 2^e = p2 / 2^-e = d[-1] / 10^1 + d[-2] / 10^2 + ... -// -// into decimal form, the fraction is repeatedly multiplied by 10 and the digits -// d[-i] are extracted in order: -// -// (10 * p2) div 2^-e = d[-1] -// (10 * p2) mod 2^-e = d[-2] / 10^1 + ... -// -// The multiplication by 10 must not overflow. It is sufficient to choose -// -// 10 * p2 < 16 * p2 = 2^4 * p2 <= 2^64. -// -// Since p2 = f mod 2^-e < 2^-e, -// -// -e <= 60 or e >= -60 := alpha - -constexpr int kAlpha = -60; -constexpr int kGamma = -32; - -struct cached_power // c = f * 2^e ~= 10^k -{ - std::uint64_t f; - int e; - int k; -}; - -/*! -For a normalized diyfp w = f * 2^e, this function returns a (normalized) cached -power-of-ten c = f_c * 2^e_c, such that the exponent of the product w * c -satisfies (Definition 3.2 from [1]) - - alpha <= e_c + e + q <= gamma. -*/ -inline cached_power get_cached_power_for_binary_exponent(int e) -{ - // Now - // - // alpha <= e_c + e + q <= gamma (1) - // ==> f_c * 2^alpha <= c * 2^e * 2^q - // - // and since the c's are normalized, 2^(q-1) <= f_c, - // - // ==> 2^(q - 1 + alpha) <= c * 2^(e + q) - // ==> 2^(alpha - e - 1) <= c - // - // If c were an exact power of ten, i.e. c = 10^k, one may determine k as - // - // k = ceil( log_10( 2^(alpha - e - 1) ) ) - // = ceil( (alpha - e - 1) * log_10(2) ) - // - // From the paper: - // "In theory the result of the procedure could be wrong since c is rounded, - // and the computation itself is approximated [...]. In practice, however, - // this simple function is sufficient." - // - // For IEEE double precision floating-point numbers converted into - // normalized diyfp's w = f * 2^e, with q = 64, - // - // e >= -1022 (min IEEE exponent) - // -52 (p - 1) - // -52 (p - 1, possibly normalize denormal IEEE numbers) - // -11 (normalize the diyfp) - // = -1137 - // - // and - // - // e <= +1023 (max IEEE exponent) - // -52 (p - 1) - // -11 (normalize the diyfp) - // = 960 - // - // This binary exponent range [-1137,960] results in a decimal exponent - // range [-307,324]. One does not need to store a cached power for each - // k in this range. For each such k it suffices to find a cached power - // such that the exponent of the product lies in [alpha,gamma]. - // This implies that the difference of the decimal exponents of adjacent - // table entries must be less than or equal to - // - // floor( (gamma - alpha) * log_10(2) ) = 8. - // - // (A smaller distance gamma-alpha would require a larger table.) - - // NB: - // Actually this function returns c, such that -60 <= e_c + e + 64 <= -34. - - constexpr int kCachedPowersMinDecExp = -300; - constexpr int kCachedPowersDecStep = 8; - - static constexpr std::array kCachedPowers = - { - { - { 0xAB70FE17C79AC6CA, -1060, -300 }, - { 0xFF77B1FCBEBCDC4F, -1034, -292 }, - { 0xBE5691EF416BD60C, -1007, -284 }, - { 0x8DD01FAD907FFC3C, -980, -276 }, - { 0xD3515C2831559A83, -954, -268 }, - { 0x9D71AC8FADA6C9B5, -927, -260 }, - { 0xEA9C227723EE8BCB, -901, -252 }, - { 0xAECC49914078536D, -874, -244 }, - { 0x823C12795DB6CE57, -847, -236 }, - { 0xC21094364DFB5637, -821, -228 }, - { 0x9096EA6F3848984F, -794, -220 }, - { 0xD77485CB25823AC7, -768, -212 }, - { 0xA086CFCD97BF97F4, -741, -204 }, - { 0xEF340A98172AACE5, -715, -196 }, - { 0xB23867FB2A35B28E, -688, -188 }, - { 0x84C8D4DFD2C63F3B, -661, -180 }, - { 0xC5DD44271AD3CDBA, -635, -172 }, - { 0x936B9FCEBB25C996, -608, -164 }, - { 0xDBAC6C247D62A584, -582, -156 }, - { 0xA3AB66580D5FDAF6, -555, -148 }, - { 0xF3E2F893DEC3F126, -529, -140 }, - { 0xB5B5ADA8AAFF80B8, -502, -132 }, - { 0x87625F056C7C4A8B, -475, -124 }, - { 0xC9BCFF6034C13053, -449, -116 }, - { 0x964E858C91BA2655, -422, -108 }, - { 0xDFF9772470297EBD, -396, -100 }, - { 0xA6DFBD9FB8E5B88F, -369, -92 }, - { 0xF8A95FCF88747D94, -343, -84 }, - { 0xB94470938FA89BCF, -316, -76 }, - { 0x8A08F0F8BF0F156B, -289, -68 }, - { 0xCDB02555653131B6, -263, -60 }, - { 0x993FE2C6D07B7FAC, -236, -52 }, - { 0xE45C10C42A2B3B06, -210, -44 }, - { 0xAA242499697392D3, -183, -36 }, - { 0xFD87B5F28300CA0E, -157, -28 }, - { 0xBCE5086492111AEB, -130, -20 }, - { 0x8CBCCC096F5088CC, -103, -12 }, - { 0xD1B71758E219652C, -77, -4 }, - { 0x9C40000000000000, -50, 4 }, - { 0xE8D4A51000000000, -24, 12 }, - { 0xAD78EBC5AC620000, 3, 20 }, - { 0x813F3978F8940984, 30, 28 }, - { 0xC097CE7BC90715B3, 56, 36 }, - { 0x8F7E32CE7BEA5C70, 83, 44 }, - { 0xD5D238A4ABE98068, 109, 52 }, - { 0x9F4F2726179A2245, 136, 60 }, - { 0xED63A231D4C4FB27, 162, 68 }, - { 0xB0DE65388CC8ADA8, 189, 76 }, - { 0x83C7088E1AAB65DB, 216, 84 }, - { 0xC45D1DF942711D9A, 242, 92 }, - { 0x924D692CA61BE758, 269, 100 }, - { 0xDA01EE641A708DEA, 295, 108 }, - { 0xA26DA3999AEF774A, 322, 116 }, - { 0xF209787BB47D6B85, 348, 124 }, - { 0xB454E4A179DD1877, 375, 132 }, - { 0x865B86925B9BC5C2, 402, 140 }, - { 0xC83553C5C8965D3D, 428, 148 }, - { 0x952AB45CFA97A0B3, 455, 156 }, - { 0xDE469FBD99A05FE3, 481, 164 }, - { 0xA59BC234DB398C25, 508, 172 }, - { 0xF6C69A72A3989F5C, 534, 180 }, - { 0xB7DCBF5354E9BECE, 561, 188 }, - { 0x88FCF317F22241E2, 588, 196 }, - { 0xCC20CE9BD35C78A5, 614, 204 }, - { 0x98165AF37B2153DF, 641, 212 }, - { 0xE2A0B5DC971F303A, 667, 220 }, - { 0xA8D9D1535CE3B396, 694, 228 }, - { 0xFB9B7CD9A4A7443C, 720, 236 }, - { 0xBB764C4CA7A44410, 747, 244 }, - { 0x8BAB8EEFB6409C1A, 774, 252 }, - { 0xD01FEF10A657842C, 800, 260 }, - { 0x9B10A4E5E9913129, 827, 268 }, - { 0xE7109BFBA19C0C9D, 853, 276 }, - { 0xAC2820D9623BF429, 880, 284 }, - { 0x80444B5E7AA7CF85, 907, 292 }, - { 0xBF21E44003ACDD2D, 933, 300 }, - { 0x8E679C2F5E44FF8F, 960, 308 }, - { 0xD433179D9C8CB841, 986, 316 }, - { 0x9E19DB92B4E31BA9, 1013, 324 }, - } - }; - - // This computation gives exactly the same results for k as - // k = ceil((kAlpha - e - 1) * 0.30102999566398114) - // for |e| <= 1500, but doesn't require floating-point operations. - // NB: log_10(2) ~= 78913 / 2^18 - JSON_ASSERT(e >= -1500); - JSON_ASSERT(e <= 1500); - const int f = kAlpha - e - 1; - const int k = (f * 78913) / (1 << 18) + static_cast(f > 0); - - const int index = (-kCachedPowersMinDecExp + k + (kCachedPowersDecStep - 1)) / kCachedPowersDecStep; - JSON_ASSERT(index >= 0); - JSON_ASSERT(static_cast(index) < kCachedPowers.size()); - - const cached_power cached = kCachedPowers[static_cast(index)]; - JSON_ASSERT(kAlpha <= cached.e + e + 64); - JSON_ASSERT(kGamma >= cached.e + e + 64); - - return cached; -} - -/*! -For n != 0, returns k, such that pow10 := 10^(k-1) <= n < 10^k. -For n == 0, returns 1 and sets pow10 := 1. -*/ -inline int find_largest_pow10(const std::uint32_t n, std::uint32_t& pow10) -{ - // LCOV_EXCL_START - if (n >= 1000000000) - { - pow10 = 1000000000; - return 10; - } - // LCOV_EXCL_STOP - if (n >= 100000000) - { - pow10 = 100000000; - return 9; - } - if (n >= 10000000) - { - pow10 = 10000000; - return 8; - } - if (n >= 1000000) - { - pow10 = 1000000; - return 7; - } - if (n >= 100000) - { - pow10 = 100000; - return 6; - } - if (n >= 10000) - { - pow10 = 10000; - return 5; - } - if (n >= 1000) - { - pow10 = 1000; - return 4; - } - if (n >= 100) - { - pow10 = 100; - return 3; - } - if (n >= 10) - { - pow10 = 10; - return 2; - } - - pow10 = 1; - return 1; -} - -inline void grisu2_round(char* buf, int len, std::uint64_t dist, std::uint64_t delta, - std::uint64_t rest, std::uint64_t ten_k) -{ - JSON_ASSERT(len >= 1); - JSON_ASSERT(dist <= delta); - JSON_ASSERT(rest <= delta); - JSON_ASSERT(ten_k > 0); - - // <--------------------------- delta ----> - // <---- dist ---------> - // --------------[------------------+-------------------]-------------- - // M- w M+ - // - // ten_k - // <------> - // <---- rest ----> - // --------------[------------------+----+--------------]-------------- - // w V - // = buf * 10^k - // - // ten_k represents a unit-in-the-last-place in the decimal representation - // stored in buf. - // Decrement buf by ten_k while this takes buf closer to w. - - // The tests are written in this order to avoid overflow in unsigned - // integer arithmetic. - - while (rest < dist - && delta - rest >= ten_k - && (rest + ten_k < dist || dist - rest > rest + ten_k - dist)) - { - JSON_ASSERT(buf[len - 1] != '0'); - buf[len - 1]--; - rest += ten_k; - } -} - -/*! -Generates V = buffer * 10^decimal_exponent, such that M- <= V <= M+. -M- and M+ must be normalized and share the same exponent -60 <= e <= -32. -*/ -inline void grisu2_digit_gen(char* buffer, int& length, int& decimal_exponent, - diyfp M_minus, diyfp w, diyfp M_plus) -{ - static_assert(kAlpha >= -60, "internal error"); - static_assert(kGamma <= -32, "internal error"); - - // Generates the digits (and the exponent) of a decimal floating-point - // number V = buffer * 10^decimal_exponent in the range [M-, M+]. The diyfp's - // w, M- and M+ share the same exponent e, which satisfies alpha <= e <= gamma. - // - // <--------------------------- delta ----> - // <---- dist ---------> - // --------------[------------------+-------------------]-------------- - // M- w M+ - // - // Grisu2 generates the digits of M+ from left to right and stops as soon as - // V is in [M-,M+]. - - JSON_ASSERT(M_plus.e >= kAlpha); - JSON_ASSERT(M_plus.e <= kGamma); - - std::uint64_t delta = diyfp::sub(M_plus, M_minus).f; // (significand of (M+ - M-), implicit exponent is e) - std::uint64_t dist = diyfp::sub(M_plus, w ).f; // (significand of (M+ - w ), implicit exponent is e) - - // Split M+ = f * 2^e into two parts p1 and p2 (note: e < 0): - // - // M+ = f * 2^e - // = ((f div 2^-e) * 2^-e + (f mod 2^-e)) * 2^e - // = ((p1 ) * 2^-e + (p2 )) * 2^e - // = p1 + p2 * 2^e - - const diyfp one(std::uint64_t{1} << -M_plus.e, M_plus.e); - - auto p1 = static_cast(M_plus.f >> -one.e); // p1 = f div 2^-e (Since -e >= 32, p1 fits into a 32-bit int.) - std::uint64_t p2 = M_plus.f & (one.f - 1); // p2 = f mod 2^-e - - // 1) - // - // Generate the digits of the integral part p1 = d[n-1]...d[1]d[0] - - JSON_ASSERT(p1 > 0); - - std::uint32_t pow10{}; - const int k = find_largest_pow10(p1, pow10); - - // 10^(k-1) <= p1 < 10^k, pow10 = 10^(k-1) - // - // p1 = (p1 div 10^(k-1)) * 10^(k-1) + (p1 mod 10^(k-1)) - // = (d[k-1] ) * 10^(k-1) + (p1 mod 10^(k-1)) - // - // M+ = p1 + p2 * 2^e - // = d[k-1] * 10^(k-1) + (p1 mod 10^(k-1)) + p2 * 2^e - // = d[k-1] * 10^(k-1) + ((p1 mod 10^(k-1)) * 2^-e + p2) * 2^e - // = d[k-1] * 10^(k-1) + ( rest) * 2^e - // - // Now generate the digits d[n] of p1 from left to right (n = k-1,...,0) - // - // p1 = d[k-1]...d[n] * 10^n + d[n-1]...d[0] - // - // but stop as soon as - // - // rest * 2^e = (d[n-1]...d[0] * 2^-e + p2) * 2^e <= delta * 2^e - - int n = k; - while (n > 0) - { - // Invariants: - // M+ = buffer * 10^n + (p1 + p2 * 2^e) (buffer = 0 for n = k) - // pow10 = 10^(n-1) <= p1 < 10^n - // - const std::uint32_t d = p1 / pow10; // d = p1 div 10^(n-1) - const std::uint32_t r = p1 % pow10; // r = p1 mod 10^(n-1) - // - // M+ = buffer * 10^n + (d * 10^(n-1) + r) + p2 * 2^e - // = (buffer * 10 + d) * 10^(n-1) + (r + p2 * 2^e) - // - JSON_ASSERT(d <= 9); - buffer[length++] = static_cast('0' + d); // buffer := buffer * 10 + d - // - // M+ = buffer * 10^(n-1) + (r + p2 * 2^e) - // - p1 = r; - n--; - // - // M+ = buffer * 10^n + (p1 + p2 * 2^e) - // pow10 = 10^n - // - - // Now check if enough digits have been generated. - // Compute - // - // p1 + p2 * 2^e = (p1 * 2^-e + p2) * 2^e = rest * 2^e - // - // Note: - // Since rest and delta share the same exponent e, it suffices to - // compare the significands. - const std::uint64_t rest = (std::uint64_t{p1} << -one.e) + p2; - if (rest <= delta) - { - // V = buffer * 10^n, with M- <= V <= M+. - - decimal_exponent += n; - - // We may now just stop. But instead look if the buffer could be - // decremented to bring V closer to w. - // - // pow10 = 10^n is now 1 ulp in the decimal representation V. - // The rounding procedure works with diyfp's with an implicit - // exponent of e. - // - // 10^n = (10^n * 2^-e) * 2^e = ulp * 2^e - // - const std::uint64_t ten_n = std::uint64_t{pow10} << -one.e; - grisu2_round(buffer, length, dist, delta, rest, ten_n); - - return; - } - - pow10 /= 10; - // - // pow10 = 10^(n-1) <= p1 < 10^n - // Invariants restored. - } - - // 2) - // - // The digits of the integral part have been generated: - // - // M+ = d[k-1]...d[1]d[0] + p2 * 2^e - // = buffer + p2 * 2^e - // - // Now generate the digits of the fractional part p2 * 2^e. - // - // Note: - // No decimal point is generated: the exponent is adjusted instead. - // - // p2 actually represents the fraction - // - // p2 * 2^e - // = p2 / 2^-e - // = d[-1] / 10^1 + d[-2] / 10^2 + ... - // - // Now generate the digits d[-m] of p1 from left to right (m = 1,2,...) - // - // p2 * 2^e = d[-1]d[-2]...d[-m] * 10^-m - // + 10^-m * (d[-m-1] / 10^1 + d[-m-2] / 10^2 + ...) - // - // using - // - // 10^m * p2 = ((10^m * p2) div 2^-e) * 2^-e + ((10^m * p2) mod 2^-e) - // = ( d) * 2^-e + ( r) - // - // or - // 10^m * p2 * 2^e = d + r * 2^e - // - // i.e. - // - // M+ = buffer + p2 * 2^e - // = buffer + 10^-m * (d + r * 2^e) - // = (buffer * 10^m + d) * 10^-m + 10^-m * r * 2^e - // - // and stop as soon as 10^-m * r * 2^e <= delta * 2^e - - JSON_ASSERT(p2 > delta); - - int m = 0; - for (;;) - { - // Invariant: - // M+ = buffer * 10^-m + 10^-m * (d[-m-1] / 10 + d[-m-2] / 10^2 + ...) * 2^e - // = buffer * 10^-m + 10^-m * (p2 ) * 2^e - // = buffer * 10^-m + 10^-m * (1/10 * (10 * p2) ) * 2^e - // = buffer * 10^-m + 10^-m * (1/10 * ((10*p2 div 2^-e) * 2^-e + (10*p2 mod 2^-e)) * 2^e - // - JSON_ASSERT(p2 <= (std::numeric_limits::max)() / 10); - p2 *= 10; - const std::uint64_t d = p2 >> -one.e; // d = (10 * p2) div 2^-e - const std::uint64_t r = p2 & (one.f - 1); // r = (10 * p2) mod 2^-e - // - // M+ = buffer * 10^-m + 10^-m * (1/10 * (d * 2^-e + r) * 2^e - // = buffer * 10^-m + 10^-m * (1/10 * (d + r * 2^e)) - // = (buffer * 10 + d) * 10^(-m-1) + 10^(-m-1) * r * 2^e - // - JSON_ASSERT(d <= 9); - buffer[length++] = static_cast('0' + d); // buffer := buffer * 10 + d - // - // M+ = buffer * 10^(-m-1) + 10^(-m-1) * r * 2^e - // - p2 = r; - m++; - // - // M+ = buffer * 10^-m + 10^-m * p2 * 2^e - // Invariant restored. - - // Check if enough digits have been generated. - // - // 10^-m * p2 * 2^e <= delta * 2^e - // p2 * 2^e <= 10^m * delta * 2^e - // p2 <= 10^m * delta - delta *= 10; - dist *= 10; - if (p2 <= delta) - { - break; - } - } - - // V = buffer * 10^-m, with M- <= V <= M+. - - decimal_exponent -= m; - - // 1 ulp in the decimal representation is now 10^-m. - // Since delta and dist are now scaled by 10^m, we need to do the - // same with ulp in order to keep the units in sync. - // - // 10^m * 10^-m = 1 = 2^-e * 2^e = ten_m * 2^e - // - const std::uint64_t ten_m = one.f; - grisu2_round(buffer, length, dist, delta, p2, ten_m); - - // By construction this algorithm generates the shortest possible decimal - // number (Loitsch, Theorem 6.2) which rounds back to w. - // For an input number of precision p, at least - // - // N = 1 + ceil(p * log_10(2)) - // - // decimal digits are sufficient to identify all binary floating-point - // numbers (Matula, "In-and-Out conversions"). - // This implies that the algorithm does not produce more than N decimal - // digits. - // - // N = 17 for p = 53 (IEEE double precision) - // N = 9 for p = 24 (IEEE single precision) -} - -/*! -v = buf * 10^decimal_exponent -len is the length of the buffer (number of decimal digits) -The buffer must be large enough, i.e. >= max_digits10. -*/ -JSON_HEDLEY_NON_NULL(1) -inline void grisu2(char* buf, int& len, int& decimal_exponent, - diyfp m_minus, diyfp v, diyfp m_plus) -{ - JSON_ASSERT(m_plus.e == m_minus.e); - JSON_ASSERT(m_plus.e == v.e); - - // --------(-----------------------+-----------------------)-------- (A) - // m- v m+ - // - // --------------------(-----------+-----------------------)-------- (B) - // m- v m+ - // - // First scale v (and m- and m+) such that the exponent is in the range - // [alpha, gamma]. - - const cached_power cached = get_cached_power_for_binary_exponent(m_plus.e); - - const diyfp c_minus_k(cached.f, cached.e); // = c ~= 10^-k - - // The exponent of the products is = v.e + c_minus_k.e + q and is in the range [alpha,gamma] - const diyfp w = diyfp::mul(v, c_minus_k); - const diyfp w_minus = diyfp::mul(m_minus, c_minus_k); - const diyfp w_plus = diyfp::mul(m_plus, c_minus_k); - - // ----(---+---)---------------(---+---)---------------(---+---)---- - // w- w w+ - // = c*m- = c*v = c*m+ - // - // diyfp::mul rounds its result and c_minus_k is approximated too. w, w- and - // w+ are now off by a small amount. - // In fact: - // - // w - v * 10^k < 1 ulp - // - // To account for this inaccuracy, add resp. subtract 1 ulp. - // - // --------+---[---------------(---+---)---------------]---+-------- - // w- M- w M+ w+ - // - // Now any number in [M-, M+] (bounds included) will round to w when input, - // regardless of how the input rounding algorithm breaks ties. - // - // And digit_gen generates the shortest possible such number in [M-, M+]. - // Note that this does not mean that Grisu2 always generates the shortest - // possible number in the interval (m-, m+). - const diyfp M_minus(w_minus.f + 1, w_minus.e); - const diyfp M_plus (w_plus.f - 1, w_plus.e ); - - decimal_exponent = -cached.k; // = -(-k) = k - - grisu2_digit_gen(buf, len, decimal_exponent, M_minus, w, M_plus); -} - -/*! -v = buf * 10^decimal_exponent -len is the length of the buffer (number of decimal digits) -The buffer must be large enough, i.e. >= max_digits10. -*/ -template -JSON_HEDLEY_NON_NULL(1) -void grisu2(char* buf, int& len, int& decimal_exponent, FloatType value) -{ - static_assert(diyfp::kPrecision >= std::numeric_limits::digits + 3, - "internal error: not enough precision"); - - JSON_ASSERT(std::isfinite(value)); - JSON_ASSERT(value > 0); - - // If the neighbors (and boundaries) of 'value' are always computed for double-precision - // numbers, all float's can be recovered using strtod (and strtof). However, the resulting - // decimal representations are not exactly "short". - // - // The documentation for 'std::to_chars' (https://en.cppreference.com/w/cpp/utility/to_chars) - // says "value is converted to a string as if by std::sprintf in the default ("C") locale" - // and since sprintf promotes floats to doubles, I think this is exactly what 'std::to_chars' - // does. - // On the other hand, the documentation for 'std::to_chars' requires that "parsing the - // representation using the corresponding std::from_chars function recovers value exactly". That - // indicates that single precision floating-point numbers should be recovered using - // 'std::strtof'. - // - // NB: If the neighbors are computed for single-precision numbers, there is a single float - // (7.0385307e-26f) which can't be recovered using strtod. The resulting double precision - // value is off by 1 ulp. -#if 0 - const boundaries w = compute_boundaries(static_cast(value)); -#else - const boundaries w = compute_boundaries(value); -#endif - - grisu2(buf, len, decimal_exponent, w.minus, w.w, w.plus); -} - -/*! -@brief appends a decimal representation of e to buf -@return a pointer to the element following the exponent. -@pre -1000 < e < 1000 -*/ -JSON_HEDLEY_NON_NULL(1) -JSON_HEDLEY_RETURNS_NON_NULL -inline char* append_exponent(char* buf, int e) -{ - JSON_ASSERT(e > -1000); - JSON_ASSERT(e < 1000); - - if (e < 0) - { - e = -e; - *buf++ = '-'; - } - else - { - *buf++ = '+'; - } - - auto k = static_cast(e); - if (k < 10) - { - // Always print at least two digits in the exponent. - // This is for compatibility with printf("%g"). - *buf++ = '0'; - *buf++ = static_cast('0' + k); - } - else if (k < 100) - { - *buf++ = static_cast('0' + k / 10); - k %= 10; - *buf++ = static_cast('0' + k); - } - else - { - *buf++ = static_cast('0' + k / 100); - k %= 100; - *buf++ = static_cast('0' + k / 10); - k %= 10; - *buf++ = static_cast('0' + k); - } - - return buf; -} - -/*! -@brief prettify v = buf * 10^decimal_exponent - -If v is in the range [10^min_exp, 10^max_exp) it will be printed in fixed-point -notation. Otherwise it will be printed in exponential notation. - -@pre min_exp < 0 -@pre max_exp > 0 -*/ -JSON_HEDLEY_NON_NULL(1) -JSON_HEDLEY_RETURNS_NON_NULL -inline char* format_buffer(char* buf, int len, int decimal_exponent, - int min_exp, int max_exp) -{ - JSON_ASSERT(min_exp < 0); - JSON_ASSERT(max_exp > 0); - - const int k = len; - const int n = len + decimal_exponent; - - // v = buf * 10^(n-k) - // k is the length of the buffer (number of decimal digits) - // n is the position of the decimal point relative to the start of the buffer. - - if (k <= n && n <= max_exp) - { - // digits[000] - // len <= max_exp + 2 - - std::memset(buf + k, '0', static_cast(n) - static_cast(k)); - // Make it look like a floating-point number (#362, #378) - buf[n + 0] = '.'; - buf[n + 1] = '0'; - return buf + (static_cast(n) + 2); - } - - if (0 < n && n <= max_exp) - { - // dig.its - // len <= max_digits10 + 1 - - JSON_ASSERT(k > n); - - std::memmove(buf + (static_cast(n) + 1), buf + n, static_cast(k) - static_cast(n)); - buf[n] = '.'; - return buf + (static_cast(k) + 1U); - } - - if (min_exp < n && n <= 0) - { - // 0.[000]digits - // len <= 2 + (-min_exp - 1) + max_digits10 - - std::memmove(buf + (2 + static_cast(-n)), buf, static_cast(k)); - buf[0] = '0'; - buf[1] = '.'; - std::memset(buf + 2, '0', static_cast(-n)); - return buf + (2U + static_cast(-n) + static_cast(k)); - } - - if (k == 1) - { - // dE+123 - // len <= 1 + 5 - - buf += 1; - } - else - { - // d.igitsE+123 - // len <= max_digits10 + 1 + 5 - - std::memmove(buf + 2, buf + 1, static_cast(k) - 1); - buf[1] = '.'; - buf += 1 + static_cast(k); - } - - *buf++ = 'e'; - return append_exponent(buf, n - 1); -} - -} // namespace dtoa_impl - -/*! -@brief generates a decimal representation of the floating-point number value in [first, last). - -The format of the resulting decimal representation is similar to printf's %g -format. Returns an iterator pointing past-the-end of the decimal representation. - -@note The input number must be finite, i.e. NaN's and Inf's are not supported. -@note The buffer must be large enough. -@note The result is NOT null-terminated. -*/ -template -JSON_HEDLEY_NON_NULL(1, 2) -JSON_HEDLEY_RETURNS_NON_NULL -char* to_chars(char* first, const char* last, FloatType value) -{ - static_cast(last); // maybe unused - fix warning - JSON_ASSERT(std::isfinite(value)); - - // Use signbit(value) instead of (value < 0) since signbit works for -0. - if (std::signbit(value)) - { - value = -value; - *first++ = '-'; - } - -#ifdef __GNUC__ -#pragma GCC diagnostic push -#pragma GCC diagnostic ignored "-Wfloat-equal" -#endif - if (value == 0) // +-0 - { - *first++ = '0'; - // Make it look like a floating-point number (#362, #378) - *first++ = '.'; - *first++ = '0'; - return first; - } -#ifdef __GNUC__ -#pragma GCC diagnostic pop -#endif - - JSON_ASSERT(last - first >= std::numeric_limits::max_digits10); - - // Compute v = buffer * 10^decimal_exponent. - // The decimal digits are stored in the buffer, which needs to be interpreted - // as an unsigned decimal integer. - // len is the length of the buffer, i.e. the number of decimal digits. - int len = 0; - int decimal_exponent = 0; - dtoa_impl::grisu2(first, len, decimal_exponent, value); - - JSON_ASSERT(len <= std::numeric_limits::max_digits10); - - // Format the buffer like printf("%.*g", prec, value) - constexpr int kMinExp = -4; - // Use digits10 here to increase compatibility with version 2. - constexpr int kMaxExp = std::numeric_limits::digits10; - - JSON_ASSERT(last - first >= kMaxExp + 2); - JSON_ASSERT(last - first >= 2 + (-kMinExp - 1) + std::numeric_limits::max_digits10); - JSON_ASSERT(last - first >= std::numeric_limits::max_digits10 + 6); - - return dtoa_impl::format_buffer(first, len, decimal_exponent, kMinExp, kMaxExp); -} - -} // namespace detail -NLOHMANN_JSON_NAMESPACE_END diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/conversions/to_json.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/conversions/to_json.hpp deleted file mode 100644 index b33d726..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/conversions/to_json.hpp +++ /dev/null @@ -1,446 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -#include // copy -#include // begin, end -#include // string -#include // tuple, get -#include // is_same, is_constructible, is_floating_point, is_enum, underlying_type -#include // move, forward, declval, pair -#include // valarray -#include // vector - -#include -#include -#include -#include -#include -#include - -NLOHMANN_JSON_NAMESPACE_BEGIN -namespace detail -{ - -////////////////// -// constructors // -////////////////// - -/* - * Note all external_constructor<>::construct functions need to call - * j.m_value.destroy(j.m_type) to avoid a memory leak in case j contains an - * allocated value (e.g., a string). See bug issue - * https://github.com/nlohmann/json/issues/2865 for more information. - */ - -template struct external_constructor; - -template<> -struct external_constructor -{ - template - static void construct(BasicJsonType& j, typename BasicJsonType::boolean_t b) noexcept - { - j.m_value.destroy(j.m_type); - j.m_type = value_t::boolean; - j.m_value = b; - j.assert_invariant(); - } -}; - -template<> -struct external_constructor -{ - template - static void construct(BasicJsonType& j, const typename BasicJsonType::string_t& s) - { - j.m_value.destroy(j.m_type); - j.m_type = value_t::string; - j.m_value = s; - j.assert_invariant(); - } - - template - static void construct(BasicJsonType& j, typename BasicJsonType::string_t&& s) - { - j.m_value.destroy(j.m_type); - j.m_type = value_t::string; - j.m_value = std::move(s); - j.assert_invariant(); - } - - template < typename BasicJsonType, typename CompatibleStringType, - enable_if_t < !std::is_same::value, - int > = 0 > - static void construct(BasicJsonType& j, const CompatibleStringType& str) - { - j.m_value.destroy(j.m_type); - j.m_type = value_t::string; - j.m_value.string = j.template create(str); - j.assert_invariant(); - } -}; - -template<> -struct external_constructor -{ - template - static void construct(BasicJsonType& j, const typename BasicJsonType::binary_t& b) - { - j.m_value.destroy(j.m_type); - j.m_type = value_t::binary; - j.m_value = typename BasicJsonType::binary_t(b); - j.assert_invariant(); - } - - template - static void construct(BasicJsonType& j, typename BasicJsonType::binary_t&& b) - { - j.m_value.destroy(j.m_type); - j.m_type = value_t::binary; - j.m_value = typename BasicJsonType::binary_t(std::move(b)); - j.assert_invariant(); - } -}; - -template<> -struct external_constructor -{ - template - static void construct(BasicJsonType& j, typename BasicJsonType::number_float_t val) noexcept - { - j.m_value.destroy(j.m_type); - j.m_type = value_t::number_float; - j.m_value = val; - j.assert_invariant(); - } -}; - -template<> -struct external_constructor -{ - template - static void construct(BasicJsonType& j, typename BasicJsonType::number_unsigned_t val) noexcept - { - j.m_value.destroy(j.m_type); - j.m_type = value_t::number_unsigned; - j.m_value = val; - j.assert_invariant(); - } -}; - -template<> -struct external_constructor -{ - template - static void construct(BasicJsonType& j, typename BasicJsonType::number_integer_t val) noexcept - { - j.m_value.destroy(j.m_type); - j.m_type = value_t::number_integer; - j.m_value = val; - j.assert_invariant(); - } -}; - -template<> -struct external_constructor -{ - template - static void construct(BasicJsonType& j, const typename BasicJsonType::array_t& arr) - { - j.m_value.destroy(j.m_type); - j.m_type = value_t::array; - j.m_value = arr; - j.set_parents(); - j.assert_invariant(); - } - - template - static void construct(BasicJsonType& j, typename BasicJsonType::array_t&& arr) - { - j.m_value.destroy(j.m_type); - j.m_type = value_t::array; - j.m_value = std::move(arr); - j.set_parents(); - j.assert_invariant(); - } - - template < typename BasicJsonType, typename CompatibleArrayType, - enable_if_t < !std::is_same::value, - int > = 0 > - static void construct(BasicJsonType& j, const CompatibleArrayType& arr) - { - using std::begin; - using std::end; - - j.m_value.destroy(j.m_type); - j.m_type = value_t::array; - j.m_value.array = j.template create(begin(arr), end(arr)); - j.set_parents(); - j.assert_invariant(); - } - - template - static void construct(BasicJsonType& j, const std::vector& arr) - { - j.m_value.destroy(j.m_type); - j.m_type = value_t::array; - j.m_value = value_t::array; - j.m_value.array->reserve(arr.size()); - for (const bool x : arr) - { - j.m_value.array->push_back(x); - j.set_parent(j.m_value.array->back()); - } - j.assert_invariant(); - } - - template::value, int> = 0> - static void construct(BasicJsonType& j, const std::valarray& arr) - { - j.m_value.destroy(j.m_type); - j.m_type = value_t::array; - j.m_value = value_t::array; - j.m_value.array->resize(arr.size()); - if (arr.size() > 0) - { - std::copy(std::begin(arr), std::end(arr), j.m_value.array->begin()); - } - j.set_parents(); - j.assert_invariant(); - } -}; - -template<> -struct external_constructor -{ - template - static void construct(BasicJsonType& j, const typename BasicJsonType::object_t& obj) - { - j.m_value.destroy(j.m_type); - j.m_type = value_t::object; - j.m_value = obj; - j.set_parents(); - j.assert_invariant(); - } - - template - static void construct(BasicJsonType& j, typename BasicJsonType::object_t&& obj) - { - j.m_value.destroy(j.m_type); - j.m_type = value_t::object; - j.m_value = std::move(obj); - j.set_parents(); - j.assert_invariant(); - } - - template < typename BasicJsonType, typename CompatibleObjectType, - enable_if_t < !std::is_same::value, int > = 0 > - static void construct(BasicJsonType& j, const CompatibleObjectType& obj) - { - using std::begin; - using std::end; - - j.m_value.destroy(j.m_type); - j.m_type = value_t::object; - j.m_value.object = j.template create(begin(obj), end(obj)); - j.set_parents(); - j.assert_invariant(); - } -}; - -///////////// -// to_json // -///////////// - -template::value, int> = 0> -inline void to_json(BasicJsonType& j, T b) noexcept -{ - external_constructor::construct(j, b); -} - -template < typename BasicJsonType, typename BoolRef, - enable_if_t < - ((std::is_same::reference, BoolRef>::value - && !std::is_same ::reference, typename BasicJsonType::boolean_t&>::value) - || (std::is_same::const_reference, BoolRef>::value - && !std::is_same ::const_reference>, - typename BasicJsonType::boolean_t >::value)) - && std::is_convertible::value, int > = 0 > -inline void to_json(BasicJsonType& j, const BoolRef& b) noexcept -{ - external_constructor::construct(j, static_cast(b)); -} - -template::value, int> = 0> -inline void to_json(BasicJsonType& j, const CompatibleString& s) -{ - external_constructor::construct(j, s); -} - -template -inline void to_json(BasicJsonType& j, typename BasicJsonType::string_t&& s) -{ - external_constructor::construct(j, std::move(s)); -} - -template::value, int> = 0> -inline void to_json(BasicJsonType& j, FloatType val) noexcept -{ - external_constructor::construct(j, static_cast(val)); -} - -template::value, int> = 0> -inline void to_json(BasicJsonType& j, CompatibleNumberUnsignedType val) noexcept -{ - external_constructor::construct(j, static_cast(val)); -} - -template::value, int> = 0> -inline void to_json(BasicJsonType& j, CompatibleNumberIntegerType val) noexcept -{ - external_constructor::construct(j, static_cast(val)); -} - -#if !JSON_DISABLE_ENUM_SERIALIZATION -template::value, int> = 0> -inline void to_json(BasicJsonType& j, EnumType e) noexcept -{ - using underlying_type = typename std::underlying_type::type; - external_constructor::construct(j, static_cast(e)); -} -#endif // JSON_DISABLE_ENUM_SERIALIZATION - -template -inline void to_json(BasicJsonType& j, const std::vector& e) -{ - external_constructor::construct(j, e); -} - -template < typename BasicJsonType, typename CompatibleArrayType, - enable_if_t < is_compatible_array_type::value&& - !is_compatible_object_type::value&& - !is_compatible_string_type::value&& - !std::is_same::value&& - !is_basic_json::value, - int > = 0 > -inline void to_json(BasicJsonType& j, const CompatibleArrayType& arr) -{ - external_constructor::construct(j, arr); -} - -template -inline void to_json(BasicJsonType& j, const typename BasicJsonType::binary_t& bin) -{ - external_constructor::construct(j, bin); -} - -template::value, int> = 0> -inline void to_json(BasicJsonType& j, const std::valarray& arr) -{ - external_constructor::construct(j, std::move(arr)); -} - -template -inline void to_json(BasicJsonType& j, typename BasicJsonType::array_t&& arr) -{ - external_constructor::construct(j, std::move(arr)); -} - -template < typename BasicJsonType, typename CompatibleObjectType, - enable_if_t < is_compatible_object_type::value&& !is_basic_json::value, int > = 0 > -inline void to_json(BasicJsonType& j, const CompatibleObjectType& obj) -{ - external_constructor::construct(j, obj); -} - -template -inline void to_json(BasicJsonType& j, typename BasicJsonType::object_t&& obj) -{ - external_constructor::construct(j, std::move(obj)); -} - -template < - typename BasicJsonType, typename T, std::size_t N, - enable_if_t < !std::is_constructible::value, // NOLINT(cppcoreguidelines-avoid-c-arrays,hicpp-avoid-c-arrays,modernize-avoid-c-arrays) - int > = 0 > -inline void to_json(BasicJsonType& j, const T(&arr)[N]) // NOLINT(cppcoreguidelines-avoid-c-arrays,hicpp-avoid-c-arrays,modernize-avoid-c-arrays) -{ - external_constructor::construct(j, arr); -} - -template < typename BasicJsonType, typename T1, typename T2, enable_if_t < std::is_constructible::value&& std::is_constructible::value, int > = 0 > -inline void to_json(BasicJsonType& j, const std::pair& p) -{ - j = { p.first, p.second }; -} - -// for https://github.com/nlohmann/json/pull/1134 -template>::value, int> = 0> -inline void to_json(BasicJsonType& j, const T& b) -{ - j = { {b.key(), b.value()} }; -} - -template -inline void to_json_tuple_impl(BasicJsonType& j, const Tuple& t, index_sequence /*unused*/) -{ - j = { std::get(t)... }; -} - -template::value, int > = 0> -inline void to_json(BasicJsonType& j, const T& t) -{ - to_json_tuple_impl(j, t, make_index_sequence::value> {}); -} - -#if JSON_HAS_FILESYSTEM || JSON_HAS_EXPERIMENTAL_FILESYSTEM -template -inline void to_json(BasicJsonType& j, const std_fs::path& p) -{ - j = p.string(); -} -#endif - -struct to_json_fn -{ - template - auto operator()(BasicJsonType& j, T&& val) const noexcept(noexcept(to_json(j, std::forward(val)))) - -> decltype(to_json(j, std::forward(val)), void()) - { - return to_json(j, std::forward(val)); - } -}; -} // namespace detail - -#ifndef JSON_HAS_CPP_17 -/// namespace to hold default `to_json` function -/// to see why this is required: -/// http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2015/n4381.html -namespace // NOLINT(cert-dcl59-cpp,fuchsia-header-anon-namespaces,google-build-namespaces) -{ -#endif -JSON_INLINE_VARIABLE constexpr const auto& to_json = // NOLINT(misc-definitions-in-headers) - detail::static_const::value; -#ifndef JSON_HAS_CPP_17 -} // namespace -#endif - -NLOHMANN_JSON_NAMESPACE_END diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/exceptions.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/exceptions.hpp deleted file mode 100644 index 96d7e01..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/exceptions.hpp +++ /dev/null @@ -1,255 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -#include // nullptr_t -#include // exception -#include // runtime_error -#include // to_string -#include // vector - -#include -#include -#include -#include -#include -#include -#include - - -NLOHMANN_JSON_NAMESPACE_BEGIN -namespace detail -{ - -//////////////// -// exceptions // -//////////////// - -/// @brief general exception of the @ref basic_json class -/// @sa https://json.nlohmann.me/api/basic_json/exception/ -class exception : public std::exception -{ - public: - /// returns the explanatory string - const char* what() const noexcept override - { - return m.what(); - } - - /// the id of the exception - const int id; // NOLINT(cppcoreguidelines-non-private-member-variables-in-classes) - - protected: - JSON_HEDLEY_NON_NULL(3) - exception(int id_, const char* what_arg) : id(id_), m(what_arg) {} // NOLINT(bugprone-throw-keyword-missing) - - static std::string name(const std::string& ename, int id_) - { - return concat("[json.exception.", ename, '.', std::to_string(id_), "] "); - } - - static std::string diagnostics(std::nullptr_t /*leaf_element*/) - { - return ""; - } - - template - static std::string diagnostics(const BasicJsonType* leaf_element) - { -#if JSON_DIAGNOSTICS - std::vector tokens; - for (const auto* current = leaf_element; current != nullptr && current->m_parent != nullptr; current = current->m_parent) - { - switch (current->m_parent->type()) - { - case value_t::array: - { - for (std::size_t i = 0; i < current->m_parent->m_value.array->size(); ++i) - { - if (¤t->m_parent->m_value.array->operator[](i) == current) - { - tokens.emplace_back(std::to_string(i)); - break; - } - } - break; - } - - case value_t::object: - { - for (const auto& element : *current->m_parent->m_value.object) - { - if (&element.second == current) - { - tokens.emplace_back(element.first.c_str()); - break; - } - } - break; - } - - case value_t::null: // LCOV_EXCL_LINE - case value_t::string: // LCOV_EXCL_LINE - case value_t::boolean: // LCOV_EXCL_LINE - case value_t::number_integer: // LCOV_EXCL_LINE - case value_t::number_unsigned: // LCOV_EXCL_LINE - case value_t::number_float: // LCOV_EXCL_LINE - case value_t::binary: // LCOV_EXCL_LINE - case value_t::discarded: // LCOV_EXCL_LINE - default: // LCOV_EXCL_LINE - break; // LCOV_EXCL_LINE - } - } - - if (tokens.empty()) - { - return ""; - } - - auto str = std::accumulate(tokens.rbegin(), tokens.rend(), std::string{}, - [](const std::string & a, const std::string & b) - { - return concat(a, '/', detail::escape(b)); - }); - return concat('(', str, ") "); -#else - static_cast(leaf_element); - return ""; -#endif - } - - private: - /// an exception object as storage for error messages - std::runtime_error m; -}; - -/// @brief exception indicating a parse error -/// @sa https://json.nlohmann.me/api/basic_json/parse_error/ -class parse_error : public exception -{ - public: - /*! - @brief create a parse error exception - @param[in] id_ the id of the exception - @param[in] pos the position where the error occurred (or with - chars_read_total=0 if the position cannot be - determined) - @param[in] what_arg the explanatory string - @return parse_error object - */ - template::value, int> = 0> - static parse_error create(int id_, const position_t& pos, const std::string& what_arg, BasicJsonContext context) - { - std::string w = concat(exception::name("parse_error", id_), "parse error", - position_string(pos), ": ", exception::diagnostics(context), what_arg); - return {id_, pos.chars_read_total, w.c_str()}; - } - - template::value, int> = 0> - static parse_error create(int id_, std::size_t byte_, const std::string& what_arg, BasicJsonContext context) - { - std::string w = concat(exception::name("parse_error", id_), "parse error", - (byte_ != 0 ? (concat(" at byte ", std::to_string(byte_))) : ""), - ": ", exception::diagnostics(context), what_arg); - return {id_, byte_, w.c_str()}; - } - - /*! - @brief byte index of the parse error - - The byte index of the last read character in the input file. - - @note For an input with n bytes, 1 is the index of the first character and - n+1 is the index of the terminating null byte or the end of file. - This also holds true when reading a byte vector (CBOR or MessagePack). - */ - const std::size_t byte; - - private: - parse_error(int id_, std::size_t byte_, const char* what_arg) - : exception(id_, what_arg), byte(byte_) {} - - static std::string position_string(const position_t& pos) - { - return concat(" at line ", std::to_string(pos.lines_read + 1), - ", column ", std::to_string(pos.chars_read_current_line)); - } -}; - -/// @brief exception indicating errors with iterators -/// @sa https://json.nlohmann.me/api/basic_json/invalid_iterator/ -class invalid_iterator : public exception -{ - public: - template::value, int> = 0> - static invalid_iterator create(int id_, const std::string& what_arg, BasicJsonContext context) - { - std::string w = concat(exception::name("invalid_iterator", id_), exception::diagnostics(context), what_arg); - return {id_, w.c_str()}; - } - - private: - JSON_HEDLEY_NON_NULL(3) - invalid_iterator(int id_, const char* what_arg) - : exception(id_, what_arg) {} -}; - -/// @brief exception indicating executing a member function with a wrong type -/// @sa https://json.nlohmann.me/api/basic_json/type_error/ -class type_error : public exception -{ - public: - template::value, int> = 0> - static type_error create(int id_, const std::string& what_arg, BasicJsonContext context) - { - std::string w = concat(exception::name("type_error", id_), exception::diagnostics(context), what_arg); - return {id_, w.c_str()}; - } - - private: - JSON_HEDLEY_NON_NULL(3) - type_error(int id_, const char* what_arg) : exception(id_, what_arg) {} -}; - -/// @brief exception indicating access out of the defined range -/// @sa https://json.nlohmann.me/api/basic_json/out_of_range/ -class out_of_range : public exception -{ - public: - template::value, int> = 0> - static out_of_range create(int id_, const std::string& what_arg, BasicJsonContext context) - { - std::string w = concat(exception::name("out_of_range", id_), exception::diagnostics(context), what_arg); - return {id_, w.c_str()}; - } - - private: - JSON_HEDLEY_NON_NULL(3) - out_of_range(int id_, const char* what_arg) : exception(id_, what_arg) {} -}; - -/// @brief exception indicating other library errors -/// @sa https://json.nlohmann.me/api/basic_json/other_error/ -class other_error : public exception -{ - public: - template::value, int> = 0> - static other_error create(int id_, const std::string& what_arg, BasicJsonContext context) - { - std::string w = concat(exception::name("other_error", id_), exception::diagnostics(context), what_arg); - return {id_, w.c_str()}; - } - - private: - JSON_HEDLEY_NON_NULL(3) - other_error(int id_, const char* what_arg) : exception(id_, what_arg) {} -}; - -} // namespace detail -NLOHMANN_JSON_NAMESPACE_END diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/hash.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/hash.hpp deleted file mode 100644 index 3f05af8..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/hash.hpp +++ /dev/null @@ -1,129 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -#include // uint8_t -#include // size_t -#include // hash - -#include -#include - -NLOHMANN_JSON_NAMESPACE_BEGIN -namespace detail -{ - -// boost::hash_combine -inline std::size_t combine(std::size_t seed, std::size_t h) noexcept -{ - seed ^= h + 0x9e3779b9 + (seed << 6U) + (seed >> 2U); - return seed; -} - -/*! -@brief hash a JSON value - -The hash function tries to rely on std::hash where possible. Furthermore, the -type of the JSON value is taken into account to have different hash values for -null, 0, 0U, and false, etc. - -@tparam BasicJsonType basic_json specialization -@param j JSON value to hash -@return hash value of j -*/ -template -std::size_t hash(const BasicJsonType& j) -{ - using string_t = typename BasicJsonType::string_t; - using number_integer_t = typename BasicJsonType::number_integer_t; - using number_unsigned_t = typename BasicJsonType::number_unsigned_t; - using number_float_t = typename BasicJsonType::number_float_t; - - const auto type = static_cast(j.type()); - switch (j.type()) - { - case BasicJsonType::value_t::null: - case BasicJsonType::value_t::discarded: - { - return combine(type, 0); - } - - case BasicJsonType::value_t::object: - { - auto seed = combine(type, j.size()); - for (const auto& element : j.items()) - { - const auto h = std::hash {}(element.key()); - seed = combine(seed, h); - seed = combine(seed, hash(element.value())); - } - return seed; - } - - case BasicJsonType::value_t::array: - { - auto seed = combine(type, j.size()); - for (const auto& element : j) - { - seed = combine(seed, hash(element)); - } - return seed; - } - - case BasicJsonType::value_t::string: - { - const auto h = std::hash {}(j.template get_ref()); - return combine(type, h); - } - - case BasicJsonType::value_t::boolean: - { - const auto h = std::hash {}(j.template get()); - return combine(type, h); - } - - case BasicJsonType::value_t::number_integer: - { - const auto h = std::hash {}(j.template get()); - return combine(type, h); - } - - case BasicJsonType::value_t::number_unsigned: - { - const auto h = std::hash {}(j.template get()); - return combine(type, h); - } - - case BasicJsonType::value_t::number_float: - { - const auto h = std::hash {}(j.template get()); - return combine(type, h); - } - - case BasicJsonType::value_t::binary: - { - auto seed = combine(type, j.get_binary().size()); - const auto h = std::hash {}(j.get_binary().has_subtype()); - seed = combine(seed, h); - seed = combine(seed, static_cast(j.get_binary().subtype())); - for (const auto byte : j.get_binary()) - { - seed = combine(seed, std::hash {}(byte)); - } - return seed; - } - - default: // LCOV_EXCL_LINE - JSON_ASSERT(false); // NOLINT(cert-dcl03-c,hicpp-static-assert,misc-static-assert) LCOV_EXCL_LINE - return 0; // LCOV_EXCL_LINE - } -} - -} // namespace detail -NLOHMANN_JSON_NAMESPACE_END diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/input/binary_reader.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/input/binary_reader.hpp deleted file mode 100644 index 634615d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/input/binary_reader.hpp +++ /dev/null @@ -1,3010 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -#include // generate_n -#include // array -#include // ldexp -#include // size_t -#include // uint8_t, uint16_t, uint32_t, uint64_t -#include // snprintf -#include // memcpy -#include // back_inserter -#include // numeric_limits -#include // char_traits, string -#include // make_pair, move -#include // vector - -#include -#include -#include -#include -#include -#include -#include -#include -#include - -NLOHMANN_JSON_NAMESPACE_BEGIN -namespace detail -{ - -/// how to treat CBOR tags -enum class cbor_tag_handler_t -{ - error, ///< throw a parse_error exception in case of a tag - ignore, ///< ignore tags - store ///< store tags as binary type -}; - -/*! -@brief determine system byte order - -@return true if and only if system's byte order is little endian - -@note from https://stackoverflow.com/a/1001328/266378 -*/ -static inline bool little_endianness(int num = 1) noexcept -{ - return *reinterpret_cast(&num) == 1; -} - - -/////////////////// -// binary reader // -/////////////////// - -/*! -@brief deserialization of CBOR, MessagePack, and UBJSON values -*/ -template> -class binary_reader -{ - using number_integer_t = typename BasicJsonType::number_integer_t; - using number_unsigned_t = typename BasicJsonType::number_unsigned_t; - using number_float_t = typename BasicJsonType::number_float_t; - using string_t = typename BasicJsonType::string_t; - using binary_t = typename BasicJsonType::binary_t; - using json_sax_t = SAX; - using char_type = typename InputAdapterType::char_type; - using char_int_type = typename std::char_traits::int_type; - - public: - /*! - @brief create a binary reader - - @param[in] adapter input adapter to read from - */ - explicit binary_reader(InputAdapterType&& adapter, const input_format_t format = input_format_t::json) noexcept : ia(std::move(adapter)), input_format(format) - { - (void)detail::is_sax_static_asserts {}; - } - - // make class move-only - binary_reader(const binary_reader&) = delete; - binary_reader(binary_reader&&) = default; // NOLINT(hicpp-noexcept-move,performance-noexcept-move-constructor) - binary_reader& operator=(const binary_reader&) = delete; - binary_reader& operator=(binary_reader&&) = default; // NOLINT(hicpp-noexcept-move,performance-noexcept-move-constructor) - ~binary_reader() = default; - - /*! - @param[in] format the binary format to parse - @param[in] sax_ a SAX event processor - @param[in] strict whether to expect the input to be consumed completed - @param[in] tag_handler how to treat CBOR tags - - @return whether parsing was successful - */ - JSON_HEDLEY_NON_NULL(3) - bool sax_parse(const input_format_t format, - json_sax_t* sax_, - const bool strict = true, - const cbor_tag_handler_t tag_handler = cbor_tag_handler_t::error) - { - sax = sax_; - bool result = false; - - switch (format) - { - case input_format_t::bson: - result = parse_bson_internal(); - break; - - case input_format_t::cbor: - result = parse_cbor_internal(true, tag_handler); - break; - - case input_format_t::msgpack: - result = parse_msgpack_internal(); - break; - - case input_format_t::ubjson: - case input_format_t::bjdata: - result = parse_ubjson_internal(); - break; - - case input_format_t::json: // LCOV_EXCL_LINE - default: // LCOV_EXCL_LINE - JSON_ASSERT(false); // NOLINT(cert-dcl03-c,hicpp-static-assert,misc-static-assert) LCOV_EXCL_LINE - } - - // strict mode: next byte must be EOF - if (result && strict) - { - if (input_format == input_format_t::ubjson || input_format == input_format_t::bjdata) - { - get_ignore_noop(); - } - else - { - get(); - } - - if (JSON_HEDLEY_UNLIKELY(current != std::char_traits::eof())) - { - return sax->parse_error(chars_read, get_token_string(), parse_error::create(110, chars_read, - exception_message(input_format, concat("expected end of input; last byte: 0x", get_token_string()), "value"), nullptr)); - } - } - - return result; - } - - private: - ////////// - // BSON // - ////////// - - /*! - @brief Reads in a BSON-object and passes it to the SAX-parser. - @return whether a valid BSON-value was passed to the SAX parser - */ - bool parse_bson_internal() - { - std::int32_t document_size{}; - get_number(input_format_t::bson, document_size); - - if (JSON_HEDLEY_UNLIKELY(!sax->start_object(static_cast(-1)))) - { - return false; - } - - if (JSON_HEDLEY_UNLIKELY(!parse_bson_element_list(/*is_array*/false))) - { - return false; - } - - return sax->end_object(); - } - - /*! - @brief Parses a C-style string from the BSON input. - @param[in,out] result A reference to the string variable where the read - string is to be stored. - @return `true` if the \x00-byte indicating the end of the string was - encountered before the EOF; false` indicates an unexpected EOF. - */ - bool get_bson_cstr(string_t& result) - { - auto out = std::back_inserter(result); - while (true) - { - get(); - if (JSON_HEDLEY_UNLIKELY(!unexpect_eof(input_format_t::bson, "cstring"))) - { - return false; - } - if (current == 0x00) - { - return true; - } - *out++ = static_cast(current); - } - } - - /*! - @brief Parses a zero-terminated string of length @a len from the BSON - input. - @param[in] len The length (including the zero-byte at the end) of the - string to be read. - @param[in,out] result A reference to the string variable where the read - string is to be stored. - @tparam NumberType The type of the length @a len - @pre len >= 1 - @return `true` if the string was successfully parsed - */ - template - bool get_bson_string(const NumberType len, string_t& result) - { - if (JSON_HEDLEY_UNLIKELY(len < 1)) - { - auto last_token = get_token_string(); - return sax->parse_error(chars_read, last_token, parse_error::create(112, chars_read, - exception_message(input_format_t::bson, concat("string length must be at least 1, is ", std::to_string(len)), "string"), nullptr)); - } - - return get_string(input_format_t::bson, len - static_cast(1), result) && get() != std::char_traits::eof(); - } - - /*! - @brief Parses a byte array input of length @a len from the BSON input. - @param[in] len The length of the byte array to be read. - @param[in,out] result A reference to the binary variable where the read - array is to be stored. - @tparam NumberType The type of the length @a len - @pre len >= 0 - @return `true` if the byte array was successfully parsed - */ - template - bool get_bson_binary(const NumberType len, binary_t& result) - { - if (JSON_HEDLEY_UNLIKELY(len < 0)) - { - auto last_token = get_token_string(); - return sax->parse_error(chars_read, last_token, parse_error::create(112, chars_read, - exception_message(input_format_t::bson, concat("byte array length cannot be negative, is ", std::to_string(len)), "binary"), nullptr)); - } - - // All BSON binary values have a subtype - std::uint8_t subtype{}; - get_number(input_format_t::bson, subtype); - result.set_subtype(subtype); - - return get_binary(input_format_t::bson, len, result); - } - - /*! - @brief Read a BSON document element of the given @a element_type. - @param[in] element_type The BSON element type, c.f. http://bsonspec.org/spec.html - @param[in] element_type_parse_position The position in the input stream, - where the `element_type` was read. - @warning Not all BSON element types are supported yet. An unsupported - @a element_type will give rise to a parse_error.114: - Unsupported BSON record type 0x... - @return whether a valid BSON-object/array was passed to the SAX parser - */ - bool parse_bson_element_internal(const char_int_type element_type, - const std::size_t element_type_parse_position) - { - switch (element_type) - { - case 0x01: // double - { - double number{}; - return get_number(input_format_t::bson, number) && sax->number_float(static_cast(number), ""); - } - - case 0x02: // string - { - std::int32_t len{}; - string_t value; - return get_number(input_format_t::bson, len) && get_bson_string(len, value) && sax->string(value); - } - - case 0x03: // object - { - return parse_bson_internal(); - } - - case 0x04: // array - { - return parse_bson_array(); - } - - case 0x05: // binary - { - std::int32_t len{}; - binary_t value; - return get_number(input_format_t::bson, len) && get_bson_binary(len, value) && sax->binary(value); - } - - case 0x08: // boolean - { - return sax->boolean(get() != 0); - } - - case 0x0A: // null - { - return sax->null(); - } - - case 0x10: // int32 - { - std::int32_t value{}; - return get_number(input_format_t::bson, value) && sax->number_integer(value); - } - - case 0x12: // int64 - { - std::int64_t value{}; - return get_number(input_format_t::bson, value) && sax->number_integer(value); - } - - default: // anything else not supported (yet) - { - std::array cr{{}}; - static_cast((std::snprintf)(cr.data(), cr.size(), "%.2hhX", static_cast(element_type))); // NOLINT(cppcoreguidelines-pro-type-vararg,hicpp-vararg) - std::string cr_str{cr.data()}; - return sax->parse_error(element_type_parse_position, cr_str, - parse_error::create(114, element_type_parse_position, concat("Unsupported BSON record type 0x", cr_str), nullptr)); - } - } - } - - /*! - @brief Read a BSON element list (as specified in the BSON-spec) - - The same binary layout is used for objects and arrays, hence it must be - indicated with the argument @a is_array which one is expected - (true --> array, false --> object). - - @param[in] is_array Determines if the element list being read is to be - treated as an object (@a is_array == false), or as an - array (@a is_array == true). - @return whether a valid BSON-object/array was passed to the SAX parser - */ - bool parse_bson_element_list(const bool is_array) - { - string_t key; - - while (auto element_type = get()) - { - if (JSON_HEDLEY_UNLIKELY(!unexpect_eof(input_format_t::bson, "element list"))) - { - return false; - } - - const std::size_t element_type_parse_position = chars_read; - if (JSON_HEDLEY_UNLIKELY(!get_bson_cstr(key))) - { - return false; - } - - if (!is_array && !sax->key(key)) - { - return false; - } - - if (JSON_HEDLEY_UNLIKELY(!parse_bson_element_internal(element_type, element_type_parse_position))) - { - return false; - } - - // get_bson_cstr only appends - key.clear(); - } - - return true; - } - - /*! - @brief Reads an array from the BSON input and passes it to the SAX-parser. - @return whether a valid BSON-array was passed to the SAX parser - */ - bool parse_bson_array() - { - std::int32_t document_size{}; - get_number(input_format_t::bson, document_size); - - if (JSON_HEDLEY_UNLIKELY(!sax->start_array(static_cast(-1)))) - { - return false; - } - - if (JSON_HEDLEY_UNLIKELY(!parse_bson_element_list(/*is_array*/true))) - { - return false; - } - - return sax->end_array(); - } - - ////////// - // CBOR // - ////////// - - /*! - @param[in] get_char whether a new character should be retrieved from the - input (true) or whether the last read character should - be considered instead (false) - @param[in] tag_handler how CBOR tags should be treated - - @return whether a valid CBOR value was passed to the SAX parser - */ - bool parse_cbor_internal(const bool get_char, - const cbor_tag_handler_t tag_handler) - { - switch (get_char ? get() : current) - { - // EOF - case std::char_traits::eof(): - return unexpect_eof(input_format_t::cbor, "value"); - - // Integer 0x00..0x17 (0..23) - case 0x00: - case 0x01: - case 0x02: - case 0x03: - case 0x04: - case 0x05: - case 0x06: - case 0x07: - case 0x08: - case 0x09: - case 0x0A: - case 0x0B: - case 0x0C: - case 0x0D: - case 0x0E: - case 0x0F: - case 0x10: - case 0x11: - case 0x12: - case 0x13: - case 0x14: - case 0x15: - case 0x16: - case 0x17: - return sax->number_unsigned(static_cast(current)); - - case 0x18: // Unsigned integer (one-byte uint8_t follows) - { - std::uint8_t number{}; - return get_number(input_format_t::cbor, number) && sax->number_unsigned(number); - } - - case 0x19: // Unsigned integer (two-byte uint16_t follows) - { - std::uint16_t number{}; - return get_number(input_format_t::cbor, number) && sax->number_unsigned(number); - } - - case 0x1A: // Unsigned integer (four-byte uint32_t follows) - { - std::uint32_t number{}; - return get_number(input_format_t::cbor, number) && sax->number_unsigned(number); - } - - case 0x1B: // Unsigned integer (eight-byte uint64_t follows) - { - std::uint64_t number{}; - return get_number(input_format_t::cbor, number) && sax->number_unsigned(number); - } - - // Negative integer -1-0x00..-1-0x17 (-1..-24) - case 0x20: - case 0x21: - case 0x22: - case 0x23: - case 0x24: - case 0x25: - case 0x26: - case 0x27: - case 0x28: - case 0x29: - case 0x2A: - case 0x2B: - case 0x2C: - case 0x2D: - case 0x2E: - case 0x2F: - case 0x30: - case 0x31: - case 0x32: - case 0x33: - case 0x34: - case 0x35: - case 0x36: - case 0x37: - return sax->number_integer(static_cast(0x20 - 1 - current)); - - case 0x38: // Negative integer (one-byte uint8_t follows) - { - std::uint8_t number{}; - return get_number(input_format_t::cbor, number) && sax->number_integer(static_cast(-1) - number); - } - - case 0x39: // Negative integer -1-n (two-byte uint16_t follows) - { - std::uint16_t number{}; - return get_number(input_format_t::cbor, number) && sax->number_integer(static_cast(-1) - number); - } - - case 0x3A: // Negative integer -1-n (four-byte uint32_t follows) - { - std::uint32_t number{}; - return get_number(input_format_t::cbor, number) && sax->number_integer(static_cast(-1) - number); - } - - case 0x3B: // Negative integer -1-n (eight-byte uint64_t follows) - { - std::uint64_t number{}; - return get_number(input_format_t::cbor, number) && sax->number_integer(static_cast(-1) - - static_cast(number)); - } - - // Binary data (0x00..0x17 bytes follow) - case 0x40: - case 0x41: - case 0x42: - case 0x43: - case 0x44: - case 0x45: - case 0x46: - case 0x47: - case 0x48: - case 0x49: - case 0x4A: - case 0x4B: - case 0x4C: - case 0x4D: - case 0x4E: - case 0x4F: - case 0x50: - case 0x51: - case 0x52: - case 0x53: - case 0x54: - case 0x55: - case 0x56: - case 0x57: - case 0x58: // Binary data (one-byte uint8_t for n follows) - case 0x59: // Binary data (two-byte uint16_t for n follow) - case 0x5A: // Binary data (four-byte uint32_t for n follow) - case 0x5B: // Binary data (eight-byte uint64_t for n follow) - case 0x5F: // Binary data (indefinite length) - { - binary_t b; - return get_cbor_binary(b) && sax->binary(b); - } - - // UTF-8 string (0x00..0x17 bytes follow) - case 0x60: - case 0x61: - case 0x62: - case 0x63: - case 0x64: - case 0x65: - case 0x66: - case 0x67: - case 0x68: - case 0x69: - case 0x6A: - case 0x6B: - case 0x6C: - case 0x6D: - case 0x6E: - case 0x6F: - case 0x70: - case 0x71: - case 0x72: - case 0x73: - case 0x74: - case 0x75: - case 0x76: - case 0x77: - case 0x78: // UTF-8 string (one-byte uint8_t for n follows) - case 0x79: // UTF-8 string (two-byte uint16_t for n follow) - case 0x7A: // UTF-8 string (four-byte uint32_t for n follow) - case 0x7B: // UTF-8 string (eight-byte uint64_t for n follow) - case 0x7F: // UTF-8 string (indefinite length) - { - string_t s; - return get_cbor_string(s) && sax->string(s); - } - - // array (0x00..0x17 data items follow) - case 0x80: - case 0x81: - case 0x82: - case 0x83: - case 0x84: - case 0x85: - case 0x86: - case 0x87: - case 0x88: - case 0x89: - case 0x8A: - case 0x8B: - case 0x8C: - case 0x8D: - case 0x8E: - case 0x8F: - case 0x90: - case 0x91: - case 0x92: - case 0x93: - case 0x94: - case 0x95: - case 0x96: - case 0x97: - return get_cbor_array( - conditional_static_cast(static_cast(current) & 0x1Fu), tag_handler); - - case 0x98: // array (one-byte uint8_t for n follows) - { - std::uint8_t len{}; - return get_number(input_format_t::cbor, len) && get_cbor_array(static_cast(len), tag_handler); - } - - case 0x99: // array (two-byte uint16_t for n follow) - { - std::uint16_t len{}; - return get_number(input_format_t::cbor, len) && get_cbor_array(static_cast(len), tag_handler); - } - - case 0x9A: // array (four-byte uint32_t for n follow) - { - std::uint32_t len{}; - return get_number(input_format_t::cbor, len) && get_cbor_array(conditional_static_cast(len), tag_handler); - } - - case 0x9B: // array (eight-byte uint64_t for n follow) - { - std::uint64_t len{}; - return get_number(input_format_t::cbor, len) && get_cbor_array(conditional_static_cast(len), tag_handler); - } - - case 0x9F: // array (indefinite length) - return get_cbor_array(static_cast(-1), tag_handler); - - // map (0x00..0x17 pairs of data items follow) - case 0xA0: - case 0xA1: - case 0xA2: - case 0xA3: - case 0xA4: - case 0xA5: - case 0xA6: - case 0xA7: - case 0xA8: - case 0xA9: - case 0xAA: - case 0xAB: - case 0xAC: - case 0xAD: - case 0xAE: - case 0xAF: - case 0xB0: - case 0xB1: - case 0xB2: - case 0xB3: - case 0xB4: - case 0xB5: - case 0xB6: - case 0xB7: - return get_cbor_object(conditional_static_cast(static_cast(current) & 0x1Fu), tag_handler); - - case 0xB8: // map (one-byte uint8_t for n follows) - { - std::uint8_t len{}; - return get_number(input_format_t::cbor, len) && get_cbor_object(static_cast(len), tag_handler); - } - - case 0xB9: // map (two-byte uint16_t for n follow) - { - std::uint16_t len{}; - return get_number(input_format_t::cbor, len) && get_cbor_object(static_cast(len), tag_handler); - } - - case 0xBA: // map (four-byte uint32_t for n follow) - { - std::uint32_t len{}; - return get_number(input_format_t::cbor, len) && get_cbor_object(conditional_static_cast(len), tag_handler); - } - - case 0xBB: // map (eight-byte uint64_t for n follow) - { - std::uint64_t len{}; - return get_number(input_format_t::cbor, len) && get_cbor_object(conditional_static_cast(len), tag_handler); - } - - case 0xBF: // map (indefinite length) - return get_cbor_object(static_cast(-1), tag_handler); - - case 0xC6: // tagged item - case 0xC7: - case 0xC8: - case 0xC9: - case 0xCA: - case 0xCB: - case 0xCC: - case 0xCD: - case 0xCE: - case 0xCF: - case 0xD0: - case 0xD1: - case 0xD2: - case 0xD3: - case 0xD4: - case 0xD8: // tagged item (1 bytes follow) - case 0xD9: // tagged item (2 bytes follow) - case 0xDA: // tagged item (4 bytes follow) - case 0xDB: // tagged item (8 bytes follow) - { - switch (tag_handler) - { - case cbor_tag_handler_t::error: - { - auto last_token = get_token_string(); - return sax->parse_error(chars_read, last_token, parse_error::create(112, chars_read, - exception_message(input_format_t::cbor, concat("invalid byte: 0x", last_token), "value"), nullptr)); - } - - case cbor_tag_handler_t::ignore: - { - // ignore binary subtype - switch (current) - { - case 0xD8: - { - std::uint8_t subtype_to_ignore{}; - get_number(input_format_t::cbor, subtype_to_ignore); - break; - } - case 0xD9: - { - std::uint16_t subtype_to_ignore{}; - get_number(input_format_t::cbor, subtype_to_ignore); - break; - } - case 0xDA: - { - std::uint32_t subtype_to_ignore{}; - get_number(input_format_t::cbor, subtype_to_ignore); - break; - } - case 0xDB: - { - std::uint64_t subtype_to_ignore{}; - get_number(input_format_t::cbor, subtype_to_ignore); - break; - } - default: - break; - } - return parse_cbor_internal(true, tag_handler); - } - - case cbor_tag_handler_t::store: - { - binary_t b; - // use binary subtype and store in binary container - switch (current) - { - case 0xD8: - { - std::uint8_t subtype{}; - get_number(input_format_t::cbor, subtype); - b.set_subtype(detail::conditional_static_cast(subtype)); - break; - } - case 0xD9: - { - std::uint16_t subtype{}; - get_number(input_format_t::cbor, subtype); - b.set_subtype(detail::conditional_static_cast(subtype)); - break; - } - case 0xDA: - { - std::uint32_t subtype{}; - get_number(input_format_t::cbor, subtype); - b.set_subtype(detail::conditional_static_cast(subtype)); - break; - } - case 0xDB: - { - std::uint64_t subtype{}; - get_number(input_format_t::cbor, subtype); - b.set_subtype(detail::conditional_static_cast(subtype)); - break; - } - default: - return parse_cbor_internal(true, tag_handler); - } - get(); - return get_cbor_binary(b) && sax->binary(b); - } - - default: // LCOV_EXCL_LINE - JSON_ASSERT(false); // NOLINT(cert-dcl03-c,hicpp-static-assert,misc-static-assert) LCOV_EXCL_LINE - return false; // LCOV_EXCL_LINE - } - } - - case 0xF4: // false - return sax->boolean(false); - - case 0xF5: // true - return sax->boolean(true); - - case 0xF6: // null - return sax->null(); - - case 0xF9: // Half-Precision Float (two-byte IEEE 754) - { - const auto byte1_raw = get(); - if (JSON_HEDLEY_UNLIKELY(!unexpect_eof(input_format_t::cbor, "number"))) - { - return false; - } - const auto byte2_raw = get(); - if (JSON_HEDLEY_UNLIKELY(!unexpect_eof(input_format_t::cbor, "number"))) - { - return false; - } - - const auto byte1 = static_cast(byte1_raw); - const auto byte2 = static_cast(byte2_raw); - - // code from RFC 7049, Appendix D, Figure 3: - // As half-precision floating-point numbers were only added - // to IEEE 754 in 2008, today's programming platforms often - // still only have limited support for them. It is very - // easy to include at least decoding support for them even - // without such support. An example of a small decoder for - // half-precision floating-point numbers in the C language - // is shown in Fig. 3. - const auto half = static_cast((byte1 << 8u) + byte2); - const double val = [&half] - { - const int exp = (half >> 10u) & 0x1Fu; - const unsigned int mant = half & 0x3FFu; - JSON_ASSERT(0 <= exp&& exp <= 32); - JSON_ASSERT(mant <= 1024); - switch (exp) - { - case 0: - return std::ldexp(mant, -24); - case 31: - return (mant == 0) - ? std::numeric_limits::infinity() - : std::numeric_limits::quiet_NaN(); - default: - return std::ldexp(mant + 1024, exp - 25); - } - }(); - return sax->number_float((half & 0x8000u) != 0 - ? static_cast(-val) - : static_cast(val), ""); - } - - case 0xFA: // Single-Precision Float (four-byte IEEE 754) - { - float number{}; - return get_number(input_format_t::cbor, number) && sax->number_float(static_cast(number), ""); - } - - case 0xFB: // Double-Precision Float (eight-byte IEEE 754) - { - double number{}; - return get_number(input_format_t::cbor, number) && sax->number_float(static_cast(number), ""); - } - - default: // anything else (0xFF is handled inside the other types) - { - auto last_token = get_token_string(); - return sax->parse_error(chars_read, last_token, parse_error::create(112, chars_read, - exception_message(input_format_t::cbor, concat("invalid byte: 0x", last_token), "value"), nullptr)); - } - } - } - - /*! - @brief reads a CBOR string - - This function first reads starting bytes to determine the expected - string length and then copies this number of bytes into a string. - Additionally, CBOR's strings with indefinite lengths are supported. - - @param[out] result created string - - @return whether string creation completed - */ - bool get_cbor_string(string_t& result) - { - if (JSON_HEDLEY_UNLIKELY(!unexpect_eof(input_format_t::cbor, "string"))) - { - return false; - } - - switch (current) - { - // UTF-8 string (0x00..0x17 bytes follow) - case 0x60: - case 0x61: - case 0x62: - case 0x63: - case 0x64: - case 0x65: - case 0x66: - case 0x67: - case 0x68: - case 0x69: - case 0x6A: - case 0x6B: - case 0x6C: - case 0x6D: - case 0x6E: - case 0x6F: - case 0x70: - case 0x71: - case 0x72: - case 0x73: - case 0x74: - case 0x75: - case 0x76: - case 0x77: - { - return get_string(input_format_t::cbor, static_cast(current) & 0x1Fu, result); - } - - case 0x78: // UTF-8 string (one-byte uint8_t for n follows) - { - std::uint8_t len{}; - return get_number(input_format_t::cbor, len) && get_string(input_format_t::cbor, len, result); - } - - case 0x79: // UTF-8 string (two-byte uint16_t for n follow) - { - std::uint16_t len{}; - return get_number(input_format_t::cbor, len) && get_string(input_format_t::cbor, len, result); - } - - case 0x7A: // UTF-8 string (four-byte uint32_t for n follow) - { - std::uint32_t len{}; - return get_number(input_format_t::cbor, len) && get_string(input_format_t::cbor, len, result); - } - - case 0x7B: // UTF-8 string (eight-byte uint64_t for n follow) - { - std::uint64_t len{}; - return get_number(input_format_t::cbor, len) && get_string(input_format_t::cbor, len, result); - } - - case 0x7F: // UTF-8 string (indefinite length) - { - while (get() != 0xFF) - { - string_t chunk; - if (!get_cbor_string(chunk)) - { - return false; - } - result.append(chunk); - } - return true; - } - - default: - { - auto last_token = get_token_string(); - return sax->parse_error(chars_read, last_token, parse_error::create(113, chars_read, - exception_message(input_format_t::cbor, concat("expected length specification (0x60-0x7B) or indefinite string type (0x7F); last byte: 0x", last_token), "string"), nullptr)); - } - } - } - - /*! - @brief reads a CBOR byte array - - This function first reads starting bytes to determine the expected - byte array length and then copies this number of bytes into the byte array. - Additionally, CBOR's byte arrays with indefinite lengths are supported. - - @param[out] result created byte array - - @return whether byte array creation completed - */ - bool get_cbor_binary(binary_t& result) - { - if (JSON_HEDLEY_UNLIKELY(!unexpect_eof(input_format_t::cbor, "binary"))) - { - return false; - } - - switch (current) - { - // Binary data (0x00..0x17 bytes follow) - case 0x40: - case 0x41: - case 0x42: - case 0x43: - case 0x44: - case 0x45: - case 0x46: - case 0x47: - case 0x48: - case 0x49: - case 0x4A: - case 0x4B: - case 0x4C: - case 0x4D: - case 0x4E: - case 0x4F: - case 0x50: - case 0x51: - case 0x52: - case 0x53: - case 0x54: - case 0x55: - case 0x56: - case 0x57: - { - return get_binary(input_format_t::cbor, static_cast(current) & 0x1Fu, result); - } - - case 0x58: // Binary data (one-byte uint8_t for n follows) - { - std::uint8_t len{}; - return get_number(input_format_t::cbor, len) && - get_binary(input_format_t::cbor, len, result); - } - - case 0x59: // Binary data (two-byte uint16_t for n follow) - { - std::uint16_t len{}; - return get_number(input_format_t::cbor, len) && - get_binary(input_format_t::cbor, len, result); - } - - case 0x5A: // Binary data (four-byte uint32_t for n follow) - { - std::uint32_t len{}; - return get_number(input_format_t::cbor, len) && - get_binary(input_format_t::cbor, len, result); - } - - case 0x5B: // Binary data (eight-byte uint64_t for n follow) - { - std::uint64_t len{}; - return get_number(input_format_t::cbor, len) && - get_binary(input_format_t::cbor, len, result); - } - - case 0x5F: // Binary data (indefinite length) - { - while (get() != 0xFF) - { - binary_t chunk; - if (!get_cbor_binary(chunk)) - { - return false; - } - result.insert(result.end(), chunk.begin(), chunk.end()); - } - return true; - } - - default: - { - auto last_token = get_token_string(); - return sax->parse_error(chars_read, last_token, parse_error::create(113, chars_read, - exception_message(input_format_t::cbor, concat("expected length specification (0x40-0x5B) or indefinite binary array type (0x5F); last byte: 0x", last_token), "binary"), nullptr)); - } - } - } - - /*! - @param[in] len the length of the array or static_cast(-1) for an - array of indefinite size - @param[in] tag_handler how CBOR tags should be treated - @return whether array creation completed - */ - bool get_cbor_array(const std::size_t len, - const cbor_tag_handler_t tag_handler) - { - if (JSON_HEDLEY_UNLIKELY(!sax->start_array(len))) - { - return false; - } - - if (len != static_cast(-1)) - { - for (std::size_t i = 0; i < len; ++i) - { - if (JSON_HEDLEY_UNLIKELY(!parse_cbor_internal(true, tag_handler))) - { - return false; - } - } - } - else - { - while (get() != 0xFF) - { - if (JSON_HEDLEY_UNLIKELY(!parse_cbor_internal(false, tag_handler))) - { - return false; - } - } - } - - return sax->end_array(); - } - - /*! - @param[in] len the length of the object or static_cast(-1) for an - object of indefinite size - @param[in] tag_handler how CBOR tags should be treated - @return whether object creation completed - */ - bool get_cbor_object(const std::size_t len, - const cbor_tag_handler_t tag_handler) - { - if (JSON_HEDLEY_UNLIKELY(!sax->start_object(len))) - { - return false; - } - - if (len != 0) - { - string_t key; - if (len != static_cast(-1)) - { - for (std::size_t i = 0; i < len; ++i) - { - get(); - if (JSON_HEDLEY_UNLIKELY(!get_cbor_string(key) || !sax->key(key))) - { - return false; - } - - if (JSON_HEDLEY_UNLIKELY(!parse_cbor_internal(true, tag_handler))) - { - return false; - } - key.clear(); - } - } - else - { - while (get() != 0xFF) - { - if (JSON_HEDLEY_UNLIKELY(!get_cbor_string(key) || !sax->key(key))) - { - return false; - } - - if (JSON_HEDLEY_UNLIKELY(!parse_cbor_internal(true, tag_handler))) - { - return false; - } - key.clear(); - } - } - } - - return sax->end_object(); - } - - ///////////// - // MsgPack // - ///////////// - - /*! - @return whether a valid MessagePack value was passed to the SAX parser - */ - bool parse_msgpack_internal() - { - switch (get()) - { - // EOF - case std::char_traits::eof(): - return unexpect_eof(input_format_t::msgpack, "value"); - - // positive fixint - case 0x00: - case 0x01: - case 0x02: - case 0x03: - case 0x04: - case 0x05: - case 0x06: - case 0x07: - case 0x08: - case 0x09: - case 0x0A: - case 0x0B: - case 0x0C: - case 0x0D: - case 0x0E: - case 0x0F: - case 0x10: - case 0x11: - case 0x12: - case 0x13: - case 0x14: - case 0x15: - case 0x16: - case 0x17: - case 0x18: - case 0x19: - case 0x1A: - case 0x1B: - case 0x1C: - case 0x1D: - case 0x1E: - case 0x1F: - case 0x20: - case 0x21: - case 0x22: - case 0x23: - case 0x24: - case 0x25: - case 0x26: - case 0x27: - case 0x28: - case 0x29: - case 0x2A: - case 0x2B: - case 0x2C: - case 0x2D: - case 0x2E: - case 0x2F: - case 0x30: - case 0x31: - case 0x32: - case 0x33: - case 0x34: - case 0x35: - case 0x36: - case 0x37: - case 0x38: - case 0x39: - case 0x3A: - case 0x3B: - case 0x3C: - case 0x3D: - case 0x3E: - case 0x3F: - case 0x40: - case 0x41: - case 0x42: - case 0x43: - case 0x44: - case 0x45: - case 0x46: - case 0x47: - case 0x48: - case 0x49: - case 0x4A: - case 0x4B: - case 0x4C: - case 0x4D: - case 0x4E: - case 0x4F: - case 0x50: - case 0x51: - case 0x52: - case 0x53: - case 0x54: - case 0x55: - case 0x56: - case 0x57: - case 0x58: - case 0x59: - case 0x5A: - case 0x5B: - case 0x5C: - case 0x5D: - case 0x5E: - case 0x5F: - case 0x60: - case 0x61: - case 0x62: - case 0x63: - case 0x64: - case 0x65: - case 0x66: - case 0x67: - case 0x68: - case 0x69: - case 0x6A: - case 0x6B: - case 0x6C: - case 0x6D: - case 0x6E: - case 0x6F: - case 0x70: - case 0x71: - case 0x72: - case 0x73: - case 0x74: - case 0x75: - case 0x76: - case 0x77: - case 0x78: - case 0x79: - case 0x7A: - case 0x7B: - case 0x7C: - case 0x7D: - case 0x7E: - case 0x7F: - return sax->number_unsigned(static_cast(current)); - - // fixmap - case 0x80: - case 0x81: - case 0x82: - case 0x83: - case 0x84: - case 0x85: - case 0x86: - case 0x87: - case 0x88: - case 0x89: - case 0x8A: - case 0x8B: - case 0x8C: - case 0x8D: - case 0x8E: - case 0x8F: - return get_msgpack_object(conditional_static_cast(static_cast(current) & 0x0Fu)); - - // fixarray - case 0x90: - case 0x91: - case 0x92: - case 0x93: - case 0x94: - case 0x95: - case 0x96: - case 0x97: - case 0x98: - case 0x99: - case 0x9A: - case 0x9B: - case 0x9C: - case 0x9D: - case 0x9E: - case 0x9F: - return get_msgpack_array(conditional_static_cast(static_cast(current) & 0x0Fu)); - - // fixstr - case 0xA0: - case 0xA1: - case 0xA2: - case 0xA3: - case 0xA4: - case 0xA5: - case 0xA6: - case 0xA7: - case 0xA8: - case 0xA9: - case 0xAA: - case 0xAB: - case 0xAC: - case 0xAD: - case 0xAE: - case 0xAF: - case 0xB0: - case 0xB1: - case 0xB2: - case 0xB3: - case 0xB4: - case 0xB5: - case 0xB6: - case 0xB7: - case 0xB8: - case 0xB9: - case 0xBA: - case 0xBB: - case 0xBC: - case 0xBD: - case 0xBE: - case 0xBF: - case 0xD9: // str 8 - case 0xDA: // str 16 - case 0xDB: // str 32 - { - string_t s; - return get_msgpack_string(s) && sax->string(s); - } - - case 0xC0: // nil - return sax->null(); - - case 0xC2: // false - return sax->boolean(false); - - case 0xC3: // true - return sax->boolean(true); - - case 0xC4: // bin 8 - case 0xC5: // bin 16 - case 0xC6: // bin 32 - case 0xC7: // ext 8 - case 0xC8: // ext 16 - case 0xC9: // ext 32 - case 0xD4: // fixext 1 - case 0xD5: // fixext 2 - case 0xD6: // fixext 4 - case 0xD7: // fixext 8 - case 0xD8: // fixext 16 - { - binary_t b; - return get_msgpack_binary(b) && sax->binary(b); - } - - case 0xCA: // float 32 - { - float number{}; - return get_number(input_format_t::msgpack, number) && sax->number_float(static_cast(number), ""); - } - - case 0xCB: // float 64 - { - double number{}; - return get_number(input_format_t::msgpack, number) && sax->number_float(static_cast(number), ""); - } - - case 0xCC: // uint 8 - { - std::uint8_t number{}; - return get_number(input_format_t::msgpack, number) && sax->number_unsigned(number); - } - - case 0xCD: // uint 16 - { - std::uint16_t number{}; - return get_number(input_format_t::msgpack, number) && sax->number_unsigned(number); - } - - case 0xCE: // uint 32 - { - std::uint32_t number{}; - return get_number(input_format_t::msgpack, number) && sax->number_unsigned(number); - } - - case 0xCF: // uint 64 - { - std::uint64_t number{}; - return get_number(input_format_t::msgpack, number) && sax->number_unsigned(number); - } - - case 0xD0: // int 8 - { - std::int8_t number{}; - return get_number(input_format_t::msgpack, number) && sax->number_integer(number); - } - - case 0xD1: // int 16 - { - std::int16_t number{}; - return get_number(input_format_t::msgpack, number) && sax->number_integer(number); - } - - case 0xD2: // int 32 - { - std::int32_t number{}; - return get_number(input_format_t::msgpack, number) && sax->number_integer(number); - } - - case 0xD3: // int 64 - { - std::int64_t number{}; - return get_number(input_format_t::msgpack, number) && sax->number_integer(number); - } - - case 0xDC: // array 16 - { - std::uint16_t len{}; - return get_number(input_format_t::msgpack, len) && get_msgpack_array(static_cast(len)); - } - - case 0xDD: // array 32 - { - std::uint32_t len{}; - return get_number(input_format_t::msgpack, len) && get_msgpack_array(conditional_static_cast(len)); - } - - case 0xDE: // map 16 - { - std::uint16_t len{}; - return get_number(input_format_t::msgpack, len) && get_msgpack_object(static_cast(len)); - } - - case 0xDF: // map 32 - { - std::uint32_t len{}; - return get_number(input_format_t::msgpack, len) && get_msgpack_object(conditional_static_cast(len)); - } - - // negative fixint - case 0xE0: - case 0xE1: - case 0xE2: - case 0xE3: - case 0xE4: - case 0xE5: - case 0xE6: - case 0xE7: - case 0xE8: - case 0xE9: - case 0xEA: - case 0xEB: - case 0xEC: - case 0xED: - case 0xEE: - case 0xEF: - case 0xF0: - case 0xF1: - case 0xF2: - case 0xF3: - case 0xF4: - case 0xF5: - case 0xF6: - case 0xF7: - case 0xF8: - case 0xF9: - case 0xFA: - case 0xFB: - case 0xFC: - case 0xFD: - case 0xFE: - case 0xFF: - return sax->number_integer(static_cast(current)); - - default: // anything else - { - auto last_token = get_token_string(); - return sax->parse_error(chars_read, last_token, parse_error::create(112, chars_read, - exception_message(input_format_t::msgpack, concat("invalid byte: 0x", last_token), "value"), nullptr)); - } - } - } - - /*! - @brief reads a MessagePack string - - This function first reads starting bytes to determine the expected - string length and then copies this number of bytes into a string. - - @param[out] result created string - - @return whether string creation completed - */ - bool get_msgpack_string(string_t& result) - { - if (JSON_HEDLEY_UNLIKELY(!unexpect_eof(input_format_t::msgpack, "string"))) - { - return false; - } - - switch (current) - { - // fixstr - case 0xA0: - case 0xA1: - case 0xA2: - case 0xA3: - case 0xA4: - case 0xA5: - case 0xA6: - case 0xA7: - case 0xA8: - case 0xA9: - case 0xAA: - case 0xAB: - case 0xAC: - case 0xAD: - case 0xAE: - case 0xAF: - case 0xB0: - case 0xB1: - case 0xB2: - case 0xB3: - case 0xB4: - case 0xB5: - case 0xB6: - case 0xB7: - case 0xB8: - case 0xB9: - case 0xBA: - case 0xBB: - case 0xBC: - case 0xBD: - case 0xBE: - case 0xBF: - { - return get_string(input_format_t::msgpack, static_cast(current) & 0x1Fu, result); - } - - case 0xD9: // str 8 - { - std::uint8_t len{}; - return get_number(input_format_t::msgpack, len) && get_string(input_format_t::msgpack, len, result); - } - - case 0xDA: // str 16 - { - std::uint16_t len{}; - return get_number(input_format_t::msgpack, len) && get_string(input_format_t::msgpack, len, result); - } - - case 0xDB: // str 32 - { - std::uint32_t len{}; - return get_number(input_format_t::msgpack, len) && get_string(input_format_t::msgpack, len, result); - } - - default: - { - auto last_token = get_token_string(); - return sax->parse_error(chars_read, last_token, parse_error::create(113, chars_read, - exception_message(input_format_t::msgpack, concat("expected length specification (0xA0-0xBF, 0xD9-0xDB); last byte: 0x", last_token), "string"), nullptr)); - } - } - } - - /*! - @brief reads a MessagePack byte array - - This function first reads starting bytes to determine the expected - byte array length and then copies this number of bytes into a byte array. - - @param[out] result created byte array - - @return whether byte array creation completed - */ - bool get_msgpack_binary(binary_t& result) - { - // helper function to set the subtype - auto assign_and_return_true = [&result](std::int8_t subtype) - { - result.set_subtype(static_cast(subtype)); - return true; - }; - - switch (current) - { - case 0xC4: // bin 8 - { - std::uint8_t len{}; - return get_number(input_format_t::msgpack, len) && - get_binary(input_format_t::msgpack, len, result); - } - - case 0xC5: // bin 16 - { - std::uint16_t len{}; - return get_number(input_format_t::msgpack, len) && - get_binary(input_format_t::msgpack, len, result); - } - - case 0xC6: // bin 32 - { - std::uint32_t len{}; - return get_number(input_format_t::msgpack, len) && - get_binary(input_format_t::msgpack, len, result); - } - - case 0xC7: // ext 8 - { - std::uint8_t len{}; - std::int8_t subtype{}; - return get_number(input_format_t::msgpack, len) && - get_number(input_format_t::msgpack, subtype) && - get_binary(input_format_t::msgpack, len, result) && - assign_and_return_true(subtype); - } - - case 0xC8: // ext 16 - { - std::uint16_t len{}; - std::int8_t subtype{}; - return get_number(input_format_t::msgpack, len) && - get_number(input_format_t::msgpack, subtype) && - get_binary(input_format_t::msgpack, len, result) && - assign_and_return_true(subtype); - } - - case 0xC9: // ext 32 - { - std::uint32_t len{}; - std::int8_t subtype{}; - return get_number(input_format_t::msgpack, len) && - get_number(input_format_t::msgpack, subtype) && - get_binary(input_format_t::msgpack, len, result) && - assign_and_return_true(subtype); - } - - case 0xD4: // fixext 1 - { - std::int8_t subtype{}; - return get_number(input_format_t::msgpack, subtype) && - get_binary(input_format_t::msgpack, 1, result) && - assign_and_return_true(subtype); - } - - case 0xD5: // fixext 2 - { - std::int8_t subtype{}; - return get_number(input_format_t::msgpack, subtype) && - get_binary(input_format_t::msgpack, 2, result) && - assign_and_return_true(subtype); - } - - case 0xD6: // fixext 4 - { - std::int8_t subtype{}; - return get_number(input_format_t::msgpack, subtype) && - get_binary(input_format_t::msgpack, 4, result) && - assign_and_return_true(subtype); - } - - case 0xD7: // fixext 8 - { - std::int8_t subtype{}; - return get_number(input_format_t::msgpack, subtype) && - get_binary(input_format_t::msgpack, 8, result) && - assign_and_return_true(subtype); - } - - case 0xD8: // fixext 16 - { - std::int8_t subtype{}; - return get_number(input_format_t::msgpack, subtype) && - get_binary(input_format_t::msgpack, 16, result) && - assign_and_return_true(subtype); - } - - default: // LCOV_EXCL_LINE - return false; // LCOV_EXCL_LINE - } - } - - /*! - @param[in] len the length of the array - @return whether array creation completed - */ - bool get_msgpack_array(const std::size_t len) - { - if (JSON_HEDLEY_UNLIKELY(!sax->start_array(len))) - { - return false; - } - - for (std::size_t i = 0; i < len; ++i) - { - if (JSON_HEDLEY_UNLIKELY(!parse_msgpack_internal())) - { - return false; - } - } - - return sax->end_array(); - } - - /*! - @param[in] len the length of the object - @return whether object creation completed - */ - bool get_msgpack_object(const std::size_t len) - { - if (JSON_HEDLEY_UNLIKELY(!sax->start_object(len))) - { - return false; - } - - string_t key; - for (std::size_t i = 0; i < len; ++i) - { - get(); - if (JSON_HEDLEY_UNLIKELY(!get_msgpack_string(key) || !sax->key(key))) - { - return false; - } - - if (JSON_HEDLEY_UNLIKELY(!parse_msgpack_internal())) - { - return false; - } - key.clear(); - } - - return sax->end_object(); - } - - //////////// - // UBJSON // - //////////// - - /*! - @param[in] get_char whether a new character should be retrieved from the - input (true, default) or whether the last read - character should be considered instead - - @return whether a valid UBJSON value was passed to the SAX parser - */ - bool parse_ubjson_internal(const bool get_char = true) - { - return get_ubjson_value(get_char ? get_ignore_noop() : current); - } - - /*! - @brief reads a UBJSON string - - This function is either called after reading the 'S' byte explicitly - indicating a string, or in case of an object key where the 'S' byte can be - left out. - - @param[out] result created string - @param[in] get_char whether a new character should be retrieved from the - input (true, default) or whether the last read - character should be considered instead - - @return whether string creation completed - */ - bool get_ubjson_string(string_t& result, const bool get_char = true) - { - if (get_char) - { - get(); // TODO(niels): may we ignore N here? - } - - if (JSON_HEDLEY_UNLIKELY(!unexpect_eof(input_format, "value"))) - { - return false; - } - - switch (current) - { - case 'U': - { - std::uint8_t len{}; - return get_number(input_format, len) && get_string(input_format, len, result); - } - - case 'i': - { - std::int8_t len{}; - return get_number(input_format, len) && get_string(input_format, len, result); - } - - case 'I': - { - std::int16_t len{}; - return get_number(input_format, len) && get_string(input_format, len, result); - } - - case 'l': - { - std::int32_t len{}; - return get_number(input_format, len) && get_string(input_format, len, result); - } - - case 'L': - { - std::int64_t len{}; - return get_number(input_format, len) && get_string(input_format, len, result); - } - - case 'u': - { - if (input_format != input_format_t::bjdata) - { - break; - } - std::uint16_t len{}; - return get_number(input_format, len) && get_string(input_format, len, result); - } - - case 'm': - { - if (input_format != input_format_t::bjdata) - { - break; - } - std::uint32_t len{}; - return get_number(input_format, len) && get_string(input_format, len, result); - } - - case 'M': - { - if (input_format != input_format_t::bjdata) - { - break; - } - std::uint64_t len{}; - return get_number(input_format, len) && get_string(input_format, len, result); - } - - default: - break; - } - auto last_token = get_token_string(); - std::string message; - - if (input_format != input_format_t::bjdata) - { - message = "expected length type specification (U, i, I, l, L); last byte: 0x" + last_token; - } - else - { - message = "expected length type specification (U, i, u, I, m, l, M, L); last byte: 0x" + last_token; - } - return sax->parse_error(chars_read, last_token, parse_error::create(113, chars_read, exception_message(input_format, message, "string"), nullptr)); - } - - /*! - @param[out] dim an integer vector storing the ND array dimensions - @return whether reading ND array size vector is successful - */ - bool get_ubjson_ndarray_size(std::vector& dim) - { - std::pair size_and_type; - size_t dimlen = 0; - bool no_ndarray = true; - - if (JSON_HEDLEY_UNLIKELY(!get_ubjson_size_type(size_and_type, no_ndarray))) - { - return false; - } - - if (size_and_type.first != npos) - { - if (size_and_type.second != 0) - { - if (size_and_type.second != 'N') - { - for (std::size_t i = 0; i < size_and_type.first; ++i) - { - if (JSON_HEDLEY_UNLIKELY(!get_ubjson_size_value(dimlen, no_ndarray, size_and_type.second))) - { - return false; - } - dim.push_back(dimlen); - } - } - } - else - { - for (std::size_t i = 0; i < size_and_type.first; ++i) - { - if (JSON_HEDLEY_UNLIKELY(!get_ubjson_size_value(dimlen, no_ndarray))) - { - return false; - } - dim.push_back(dimlen); - } - } - } - else - { - while (current != ']') - { - if (JSON_HEDLEY_UNLIKELY(!get_ubjson_size_value(dimlen, no_ndarray, current))) - { - return false; - } - dim.push_back(dimlen); - get_ignore_noop(); - } - } - return true; - } - - /*! - @param[out] result determined size - @param[in,out] is_ndarray for input, `true` means already inside an ndarray vector - or ndarray dimension is not allowed; `false` means ndarray - is allowed; for output, `true` means an ndarray is found; - is_ndarray can only return `true` when its initial value - is `false` - @param[in] prefix type marker if already read, otherwise set to 0 - - @return whether size determination completed - */ - bool get_ubjson_size_value(std::size_t& result, bool& is_ndarray, char_int_type prefix = 0) - { - if (prefix == 0) - { - prefix = get_ignore_noop(); - } - - switch (prefix) - { - case 'U': - { - std::uint8_t number{}; - if (JSON_HEDLEY_UNLIKELY(!get_number(input_format, number))) - { - return false; - } - result = static_cast(number); - return true; - } - - case 'i': - { - std::int8_t number{}; - if (JSON_HEDLEY_UNLIKELY(!get_number(input_format, number))) - { - return false; - } - if (number < 0) - { - return sax->parse_error(chars_read, get_token_string(), parse_error::create(113, chars_read, - exception_message(input_format, "count in an optimized container must be positive", "size"), nullptr)); - } - result = static_cast(number); // NOLINT(bugprone-signed-char-misuse,cert-str34-c): number is not a char - return true; - } - - case 'I': - { - std::int16_t number{}; - if (JSON_HEDLEY_UNLIKELY(!get_number(input_format, number))) - { - return false; - } - if (number < 0) - { - return sax->parse_error(chars_read, get_token_string(), parse_error::create(113, chars_read, - exception_message(input_format, "count in an optimized container must be positive", "size"), nullptr)); - } - result = static_cast(number); - return true; - } - - case 'l': - { - std::int32_t number{}; - if (JSON_HEDLEY_UNLIKELY(!get_number(input_format, number))) - { - return false; - } - if (number < 0) - { - return sax->parse_error(chars_read, get_token_string(), parse_error::create(113, chars_read, - exception_message(input_format, "count in an optimized container must be positive", "size"), nullptr)); - } - result = static_cast(number); - return true; - } - - case 'L': - { - std::int64_t number{}; - if (JSON_HEDLEY_UNLIKELY(!get_number(input_format, number))) - { - return false; - } - if (number < 0) - { - return sax->parse_error(chars_read, get_token_string(), parse_error::create(113, chars_read, - exception_message(input_format, "count in an optimized container must be positive", "size"), nullptr)); - } - if (!value_in_range_of(number)) - { - return sax->parse_error(chars_read, get_token_string(), out_of_range::create(408, - exception_message(input_format, "integer value overflow", "size"), nullptr)); - } - result = static_cast(number); - return true; - } - - case 'u': - { - if (input_format != input_format_t::bjdata) - { - break; - } - std::uint16_t number{}; - if (JSON_HEDLEY_UNLIKELY(!get_number(input_format, number))) - { - return false; - } - result = static_cast(number); - return true; - } - - case 'm': - { - if (input_format != input_format_t::bjdata) - { - break; - } - std::uint32_t number{}; - if (JSON_HEDLEY_UNLIKELY(!get_number(input_format, number))) - { - return false; - } - result = conditional_static_cast(number); - return true; - } - - case 'M': - { - if (input_format != input_format_t::bjdata) - { - break; - } - std::uint64_t number{}; - if (JSON_HEDLEY_UNLIKELY(!get_number(input_format, number))) - { - return false; - } - if (!value_in_range_of(number)) - { - return sax->parse_error(chars_read, get_token_string(), out_of_range::create(408, - exception_message(input_format, "integer value overflow", "size"), nullptr)); - } - result = detail::conditional_static_cast(number); - return true; - } - - case '[': - { - if (input_format != input_format_t::bjdata) - { - break; - } - if (is_ndarray) // ndarray dimensional vector can only contain integers, and can not embed another array - { - return sax->parse_error(chars_read, get_token_string(), parse_error::create(113, chars_read, exception_message(input_format, "ndarray dimentional vector is not allowed", "size"), nullptr)); - } - std::vector dim; - if (JSON_HEDLEY_UNLIKELY(!get_ubjson_ndarray_size(dim))) - { - return false; - } - if (dim.size() == 1 || (dim.size() == 2 && dim.at(0) == 1)) // return normal array size if 1D row vector - { - result = dim.at(dim.size() - 1); - return true; - } - if (!dim.empty()) // if ndarray, convert to an object in JData annotated array format - { - for (auto i : dim) // test if any dimension in an ndarray is 0, if so, return a 1D empty container - { - if ( i == 0 ) - { - result = 0; - return true; - } - } - - string_t key = "_ArraySize_"; - if (JSON_HEDLEY_UNLIKELY(!sax->start_object(3) || !sax->key(key) || !sax->start_array(dim.size()))) - { - return false; - } - result = 1; - for (auto i : dim) - { - result *= i; - if (result == 0 || result == npos) // because dim elements shall not have zeros, result = 0 means overflow happened; it also can't be npos as it is used to initialize size in get_ubjson_size_type() - { - return sax->parse_error(chars_read, get_token_string(), out_of_range::create(408, exception_message(input_format, "excessive ndarray size caused overflow", "size"), nullptr)); - } - if (JSON_HEDLEY_UNLIKELY(!sax->number_unsigned(static_cast(i)))) - { - return false; - } - } - is_ndarray = true; - return sax->end_array(); - } - result = 0; - return true; - } - - default: - break; - } - auto last_token = get_token_string(); - std::string message; - - if (input_format != input_format_t::bjdata) - { - message = "expected length type specification (U, i, I, l, L) after '#'; last byte: 0x" + last_token; - } - else - { - message = "expected length type specification (U, i, u, I, m, l, M, L) after '#'; last byte: 0x" + last_token; - } - return sax->parse_error(chars_read, last_token, parse_error::create(113, chars_read, exception_message(input_format, message, "size"), nullptr)); - } - - /*! - @brief determine the type and size for a container - - In the optimized UBJSON format, a type and a size can be provided to allow - for a more compact representation. - - @param[out] result pair of the size and the type - @param[in] inside_ndarray whether the parser is parsing an ND array dimensional vector - - @return whether pair creation completed - */ - bool get_ubjson_size_type(std::pair& result, bool inside_ndarray = false) - { - result.first = npos; // size - result.second = 0; // type - bool is_ndarray = false; - - get_ignore_noop(); - - if (current == '$') - { - result.second = get(); // must not ignore 'N', because 'N' maybe the type - if (input_format == input_format_t::bjdata - && JSON_HEDLEY_UNLIKELY(std::binary_search(bjd_optimized_type_markers.begin(), bjd_optimized_type_markers.end(), result.second))) - { - auto last_token = get_token_string(); - return sax->parse_error(chars_read, last_token, parse_error::create(112, chars_read, - exception_message(input_format, concat("marker 0x", last_token, " is not a permitted optimized array type"), "type"), nullptr)); - } - - if (JSON_HEDLEY_UNLIKELY(!unexpect_eof(input_format, "type"))) - { - return false; - } - - get_ignore_noop(); - if (JSON_HEDLEY_UNLIKELY(current != '#')) - { - if (JSON_HEDLEY_UNLIKELY(!unexpect_eof(input_format, "value"))) - { - return false; - } - auto last_token = get_token_string(); - return sax->parse_error(chars_read, last_token, parse_error::create(112, chars_read, - exception_message(input_format, concat("expected '#' after type information; last byte: 0x", last_token), "size"), nullptr)); - } - - bool is_error = get_ubjson_size_value(result.first, is_ndarray); - if (input_format == input_format_t::bjdata && is_ndarray) - { - if (inside_ndarray) - { - return sax->parse_error(chars_read, get_token_string(), parse_error::create(112, chars_read, - exception_message(input_format, "ndarray can not be recursive", "size"), nullptr)); - } - result.second |= (1 << 8); // use bit 8 to indicate ndarray, all UBJSON and BJData markers should be ASCII letters - } - return is_error; - } - - if (current == '#') - { - bool is_error = get_ubjson_size_value(result.first, is_ndarray); - if (input_format == input_format_t::bjdata && is_ndarray) - { - return sax->parse_error(chars_read, get_token_string(), parse_error::create(112, chars_read, - exception_message(input_format, "ndarray requires both type and size", "size"), nullptr)); - } - return is_error; - } - - return true; - } - - /*! - @param prefix the previously read or set type prefix - @return whether value creation completed - */ - bool get_ubjson_value(const char_int_type prefix) - { - switch (prefix) - { - case std::char_traits::eof(): // EOF - return unexpect_eof(input_format, "value"); - - case 'T': // true - return sax->boolean(true); - case 'F': // false - return sax->boolean(false); - - case 'Z': // null - return sax->null(); - - case 'U': - { - std::uint8_t number{}; - return get_number(input_format, number) && sax->number_unsigned(number); - } - - case 'i': - { - std::int8_t number{}; - return get_number(input_format, number) && sax->number_integer(number); - } - - case 'I': - { - std::int16_t number{}; - return get_number(input_format, number) && sax->number_integer(number); - } - - case 'l': - { - std::int32_t number{}; - return get_number(input_format, number) && sax->number_integer(number); - } - - case 'L': - { - std::int64_t number{}; - return get_number(input_format, number) && sax->number_integer(number); - } - - case 'u': - { - if (input_format != input_format_t::bjdata) - { - break; - } - std::uint16_t number{}; - return get_number(input_format, number) && sax->number_unsigned(number); - } - - case 'm': - { - if (input_format != input_format_t::bjdata) - { - break; - } - std::uint32_t number{}; - return get_number(input_format, number) && sax->number_unsigned(number); - } - - case 'M': - { - if (input_format != input_format_t::bjdata) - { - break; - } - std::uint64_t number{}; - return get_number(input_format, number) && sax->number_unsigned(number); - } - - case 'h': - { - if (input_format != input_format_t::bjdata) - { - break; - } - const auto byte1_raw = get(); - if (JSON_HEDLEY_UNLIKELY(!unexpect_eof(input_format, "number"))) - { - return false; - } - const auto byte2_raw = get(); - if (JSON_HEDLEY_UNLIKELY(!unexpect_eof(input_format, "number"))) - { - return false; - } - - const auto byte1 = static_cast(byte1_raw); - const auto byte2 = static_cast(byte2_raw); - - // code from RFC 7049, Appendix D, Figure 3: - // As half-precision floating-point numbers were only added - // to IEEE 754 in 2008, today's programming platforms often - // still only have limited support for them. It is very - // easy to include at least decoding support for them even - // without such support. An example of a small decoder for - // half-precision floating-point numbers in the C language - // is shown in Fig. 3. - const auto half = static_cast((byte2 << 8u) + byte1); - const double val = [&half] - { - const int exp = (half >> 10u) & 0x1Fu; - const unsigned int mant = half & 0x3FFu; - JSON_ASSERT(0 <= exp&& exp <= 32); - JSON_ASSERT(mant <= 1024); - switch (exp) - { - case 0: - return std::ldexp(mant, -24); - case 31: - return (mant == 0) - ? std::numeric_limits::infinity() - : std::numeric_limits::quiet_NaN(); - default: - return std::ldexp(mant + 1024, exp - 25); - } - }(); - return sax->number_float((half & 0x8000u) != 0 - ? static_cast(-val) - : static_cast(val), ""); - } - - case 'd': - { - float number{}; - return get_number(input_format, number) && sax->number_float(static_cast(number), ""); - } - - case 'D': - { - double number{}; - return get_number(input_format, number) && sax->number_float(static_cast(number), ""); - } - - case 'H': - { - return get_ubjson_high_precision_number(); - } - - case 'C': // char - { - get(); - if (JSON_HEDLEY_UNLIKELY(!unexpect_eof(input_format, "char"))) - { - return false; - } - if (JSON_HEDLEY_UNLIKELY(current > 127)) - { - auto last_token = get_token_string(); - return sax->parse_error(chars_read, last_token, parse_error::create(113, chars_read, - exception_message(input_format, concat("byte after 'C' must be in range 0x00..0x7F; last byte: 0x", last_token), "char"), nullptr)); - } - string_t s(1, static_cast(current)); - return sax->string(s); - } - - case 'S': // string - { - string_t s; - return get_ubjson_string(s) && sax->string(s); - } - - case '[': // array - return get_ubjson_array(); - - case '{': // object - return get_ubjson_object(); - - default: // anything else - break; - } - auto last_token = get_token_string(); - return sax->parse_error(chars_read, last_token, parse_error::create(112, chars_read, exception_message(input_format, "invalid byte: 0x" + last_token, "value"), nullptr)); - } - - /*! - @return whether array creation completed - */ - bool get_ubjson_array() - { - std::pair size_and_type; - if (JSON_HEDLEY_UNLIKELY(!get_ubjson_size_type(size_and_type))) - { - return false; - } - - // if bit-8 of size_and_type.second is set to 1, encode bjdata ndarray as an object in JData annotated array format (https://github.com/NeuroJSON/jdata): - // {"_ArrayType_" : "typeid", "_ArraySize_" : [n1, n2, ...], "_ArrayData_" : [v1, v2, ...]} - - if (input_format == input_format_t::bjdata && size_and_type.first != npos && (size_and_type.second & (1 << 8)) != 0) - { - size_and_type.second &= ~(static_cast(1) << 8); // use bit 8 to indicate ndarray, here we remove the bit to restore the type marker - auto it = std::lower_bound(bjd_types_map.begin(), bjd_types_map.end(), size_and_type.second, [](const bjd_type & p, char_int_type t) - { - return p.first < t; - }); - string_t key = "_ArrayType_"; - if (JSON_HEDLEY_UNLIKELY(it == bjd_types_map.end() || it->first != size_and_type.second)) - { - auto last_token = get_token_string(); - return sax->parse_error(chars_read, last_token, parse_error::create(112, chars_read, - exception_message(input_format, "invalid byte: 0x" + last_token, "type"), nullptr)); - } - - string_t type = it->second; // sax->string() takes a reference - if (JSON_HEDLEY_UNLIKELY(!sax->key(key) || !sax->string(type))) - { - return false; - } - - if (size_and_type.second == 'C') - { - size_and_type.second = 'U'; - } - - key = "_ArrayData_"; - if (JSON_HEDLEY_UNLIKELY(!sax->key(key) || !sax->start_array(size_and_type.first) )) - { - return false; - } - - for (std::size_t i = 0; i < size_and_type.first; ++i) - { - if (JSON_HEDLEY_UNLIKELY(!get_ubjson_value(size_and_type.second))) - { - return false; - } - } - - return (sax->end_array() && sax->end_object()); - } - - if (size_and_type.first != npos) - { - if (JSON_HEDLEY_UNLIKELY(!sax->start_array(size_and_type.first))) - { - return false; - } - - if (size_and_type.second != 0) - { - if (size_and_type.second != 'N') - { - for (std::size_t i = 0; i < size_and_type.first; ++i) - { - if (JSON_HEDLEY_UNLIKELY(!get_ubjson_value(size_and_type.second))) - { - return false; - } - } - } - } - else - { - for (std::size_t i = 0; i < size_and_type.first; ++i) - { - if (JSON_HEDLEY_UNLIKELY(!parse_ubjson_internal())) - { - return false; - } - } - } - } - else - { - if (JSON_HEDLEY_UNLIKELY(!sax->start_array(static_cast(-1)))) - { - return false; - } - - while (current != ']') - { - if (JSON_HEDLEY_UNLIKELY(!parse_ubjson_internal(false))) - { - return false; - } - get_ignore_noop(); - } - } - - return sax->end_array(); - } - - /*! - @return whether object creation completed - */ - bool get_ubjson_object() - { - std::pair size_and_type; - if (JSON_HEDLEY_UNLIKELY(!get_ubjson_size_type(size_and_type))) - { - return false; - } - - // do not accept ND-array size in objects in BJData - if (input_format == input_format_t::bjdata && size_and_type.first != npos && (size_and_type.second & (1 << 8)) != 0) - { - auto last_token = get_token_string(); - return sax->parse_error(chars_read, last_token, parse_error::create(112, chars_read, - exception_message(input_format, "BJData object does not support ND-array size in optimized format", "object"), nullptr)); - } - - string_t key; - if (size_and_type.first != npos) - { - if (JSON_HEDLEY_UNLIKELY(!sax->start_object(size_and_type.first))) - { - return false; - } - - if (size_and_type.second != 0) - { - for (std::size_t i = 0; i < size_and_type.first; ++i) - { - if (JSON_HEDLEY_UNLIKELY(!get_ubjson_string(key) || !sax->key(key))) - { - return false; - } - if (JSON_HEDLEY_UNLIKELY(!get_ubjson_value(size_and_type.second))) - { - return false; - } - key.clear(); - } - } - else - { - for (std::size_t i = 0; i < size_and_type.first; ++i) - { - if (JSON_HEDLEY_UNLIKELY(!get_ubjson_string(key) || !sax->key(key))) - { - return false; - } - if (JSON_HEDLEY_UNLIKELY(!parse_ubjson_internal())) - { - return false; - } - key.clear(); - } - } - } - else - { - if (JSON_HEDLEY_UNLIKELY(!sax->start_object(static_cast(-1)))) - { - return false; - } - - while (current != '}') - { - if (JSON_HEDLEY_UNLIKELY(!get_ubjson_string(key, false) || !sax->key(key))) - { - return false; - } - if (JSON_HEDLEY_UNLIKELY(!parse_ubjson_internal())) - { - return false; - } - get_ignore_noop(); - key.clear(); - } - } - - return sax->end_object(); - } - - // Note, no reader for UBJSON binary types is implemented because they do - // not exist - - bool get_ubjson_high_precision_number() - { - // get size of following number string - std::size_t size{}; - bool no_ndarray = true; - auto res = get_ubjson_size_value(size, no_ndarray); - if (JSON_HEDLEY_UNLIKELY(!res)) - { - return res; - } - - // get number string - std::vector number_vector; - for (std::size_t i = 0; i < size; ++i) - { - get(); - if (JSON_HEDLEY_UNLIKELY(!unexpect_eof(input_format, "number"))) - { - return false; - } - number_vector.push_back(static_cast(current)); - } - - // parse number string - using ia_type = decltype(detail::input_adapter(number_vector)); - auto number_lexer = detail::lexer(detail::input_adapter(number_vector), false); - const auto result_number = number_lexer.scan(); - const auto number_string = number_lexer.get_token_string(); - const auto result_remainder = number_lexer.scan(); - - using token_type = typename detail::lexer_base::token_type; - - if (JSON_HEDLEY_UNLIKELY(result_remainder != token_type::end_of_input)) - { - return sax->parse_error(chars_read, number_string, parse_error::create(115, chars_read, - exception_message(input_format, concat("invalid number text: ", number_lexer.get_token_string()), "high-precision number"), nullptr)); - } - - switch (result_number) - { - case token_type::value_integer: - return sax->number_integer(number_lexer.get_number_integer()); - case token_type::value_unsigned: - return sax->number_unsigned(number_lexer.get_number_unsigned()); - case token_type::value_float: - return sax->number_float(number_lexer.get_number_float(), std::move(number_string)); - case token_type::uninitialized: - case token_type::literal_true: - case token_type::literal_false: - case token_type::literal_null: - case token_type::value_string: - case token_type::begin_array: - case token_type::begin_object: - case token_type::end_array: - case token_type::end_object: - case token_type::name_separator: - case token_type::value_separator: - case token_type::parse_error: - case token_type::end_of_input: - case token_type::literal_or_value: - default: - return sax->parse_error(chars_read, number_string, parse_error::create(115, chars_read, - exception_message(input_format, concat("invalid number text: ", number_lexer.get_token_string()), "high-precision number"), nullptr)); - } - } - - /////////////////////// - // Utility functions // - /////////////////////// - - /*! - @brief get next character from the input - - This function provides the interface to the used input adapter. It does - not throw in case the input reached EOF, but returns a -'ve valued - `std::char_traits::eof()` in that case. - - @return character read from the input - */ - char_int_type get() - { - ++chars_read; - return current = ia.get_character(); - } - - /*! - @return character read from the input after ignoring all 'N' entries - */ - char_int_type get_ignore_noop() - { - do - { - get(); - } - while (current == 'N'); - - return current; - } - - /* - @brief read a number from the input - - @tparam NumberType the type of the number - @param[in] format the current format (for diagnostics) - @param[out] result number of type @a NumberType - - @return whether conversion completed - - @note This function needs to respect the system's endianness, because - bytes in CBOR, MessagePack, and UBJSON are stored in network order - (big endian) and therefore need reordering on little endian systems. - On the other hand, BSON and BJData use little endian and should reorder - on big endian systems. - */ - template - bool get_number(const input_format_t format, NumberType& result) - { - // step 1: read input into array with system's byte order - std::array vec{}; - for (std::size_t i = 0; i < sizeof(NumberType); ++i) - { - get(); - if (JSON_HEDLEY_UNLIKELY(!unexpect_eof(format, "number"))) - { - return false; - } - - // reverse byte order prior to conversion if necessary - if (is_little_endian != (InputIsLittleEndian || format == input_format_t::bjdata)) - { - vec[sizeof(NumberType) - i - 1] = static_cast(current); - } - else - { - vec[i] = static_cast(current); // LCOV_EXCL_LINE - } - } - - // step 2: convert array into number of type T and return - std::memcpy(&result, vec.data(), sizeof(NumberType)); - return true; - } - - /*! - @brief create a string by reading characters from the input - - @tparam NumberType the type of the number - @param[in] format the current format (for diagnostics) - @param[in] len number of characters to read - @param[out] result string created by reading @a len bytes - - @return whether string creation completed - - @note We can not reserve @a len bytes for the result, because @a len - may be too large. Usually, @ref unexpect_eof() detects the end of - the input before we run out of string memory. - */ - template - bool get_string(const input_format_t format, - const NumberType len, - string_t& result) - { - bool success = true; - for (NumberType i = 0; i < len; i++) - { - get(); - if (JSON_HEDLEY_UNLIKELY(!unexpect_eof(format, "string"))) - { - success = false; - break; - } - result.push_back(static_cast(current)); - } - return success; - } - - /*! - @brief create a byte array by reading bytes from the input - - @tparam NumberType the type of the number - @param[in] format the current format (for diagnostics) - @param[in] len number of bytes to read - @param[out] result byte array created by reading @a len bytes - - @return whether byte array creation completed - - @note We can not reserve @a len bytes for the result, because @a len - may be too large. Usually, @ref unexpect_eof() detects the end of - the input before we run out of memory. - */ - template - bool get_binary(const input_format_t format, - const NumberType len, - binary_t& result) - { - bool success = true; - for (NumberType i = 0; i < len; i++) - { - get(); - if (JSON_HEDLEY_UNLIKELY(!unexpect_eof(format, "binary"))) - { - success = false; - break; - } - result.push_back(static_cast(current)); - } - return success; - } - - /*! - @param[in] format the current format (for diagnostics) - @param[in] context further context information (for diagnostics) - @return whether the last read character is not EOF - */ - JSON_HEDLEY_NON_NULL(3) - bool unexpect_eof(const input_format_t format, const char* context) const - { - if (JSON_HEDLEY_UNLIKELY(current == std::char_traits::eof())) - { - return sax->parse_error(chars_read, "", - parse_error::create(110, chars_read, exception_message(format, "unexpected end of input", context), nullptr)); - } - return true; - } - - /*! - @return a string representation of the last read byte - */ - std::string get_token_string() const - { - std::array cr{{}}; - static_cast((std::snprintf)(cr.data(), cr.size(), "%.2hhX", static_cast(current))); // NOLINT(cppcoreguidelines-pro-type-vararg,hicpp-vararg) - return std::string{cr.data()}; - } - - /*! - @param[in] format the current format - @param[in] detail a detailed error message - @param[in] context further context information - @return a message string to use in the parse_error exceptions - */ - std::string exception_message(const input_format_t format, - const std::string& detail, - const std::string& context) const - { - std::string error_msg = "syntax error while parsing "; - - switch (format) - { - case input_format_t::cbor: - error_msg += "CBOR"; - break; - - case input_format_t::msgpack: - error_msg += "MessagePack"; - break; - - case input_format_t::ubjson: - error_msg += "UBJSON"; - break; - - case input_format_t::bson: - error_msg += "BSON"; - break; - - case input_format_t::bjdata: - error_msg += "BJData"; - break; - - case input_format_t::json: // LCOV_EXCL_LINE - default: // LCOV_EXCL_LINE - JSON_ASSERT(false); // NOLINT(cert-dcl03-c,hicpp-static-assert,misc-static-assert) LCOV_EXCL_LINE - } - - return concat(error_msg, ' ', context, ": ", detail); - } - - private: - static JSON_INLINE_VARIABLE constexpr std::size_t npos = static_cast(-1); - - /// input adapter - InputAdapterType ia; - - /// the current character - char_int_type current = std::char_traits::eof(); - - /// the number of characters read - std::size_t chars_read = 0; - - /// whether we can assume little endianness - const bool is_little_endian = little_endianness(); - - /// input format - const input_format_t input_format = input_format_t::json; - - /// the SAX parser - json_sax_t* sax = nullptr; - - // excluded markers in bjdata optimized type -#define JSON_BINARY_READER_MAKE_BJD_OPTIMIZED_TYPE_MARKERS_ \ - make_array('F', 'H', 'N', 'S', 'T', 'Z', '[', '{') - -#define JSON_BINARY_READER_MAKE_BJD_TYPES_MAP_ \ - make_array( \ - bjd_type{'C', "char"}, \ - bjd_type{'D', "double"}, \ - bjd_type{'I', "int16"}, \ - bjd_type{'L', "int64"}, \ - bjd_type{'M', "uint64"}, \ - bjd_type{'U', "uint8"}, \ - bjd_type{'d', "single"}, \ - bjd_type{'i', "int8"}, \ - bjd_type{'l', "int32"}, \ - bjd_type{'m', "uint32"}, \ - bjd_type{'u', "uint16"}) - - JSON_PRIVATE_UNLESS_TESTED: - // lookup tables - // NOLINTNEXTLINE(cppcoreguidelines-non-private-member-variables-in-classes) - const decltype(JSON_BINARY_READER_MAKE_BJD_OPTIMIZED_TYPE_MARKERS_) bjd_optimized_type_markers = - JSON_BINARY_READER_MAKE_BJD_OPTIMIZED_TYPE_MARKERS_; - - using bjd_type = std::pair; - // NOLINTNEXTLINE(cppcoreguidelines-non-private-member-variables-in-classes) - const decltype(JSON_BINARY_READER_MAKE_BJD_TYPES_MAP_) bjd_types_map = - JSON_BINARY_READER_MAKE_BJD_TYPES_MAP_; - -#undef JSON_BINARY_READER_MAKE_BJD_OPTIMIZED_TYPE_MARKERS_ -#undef JSON_BINARY_READER_MAKE_BJD_TYPES_MAP_ -}; - -#ifndef JSON_HAS_CPP_17 - template - constexpr std::size_t binary_reader::npos; -#endif - -} // namespace detail -NLOHMANN_JSON_NAMESPACE_END diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/input/input_adapters.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/input/input_adapters.hpp deleted file mode 100644 index cf53b1d..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/input/input_adapters.hpp +++ /dev/null @@ -1,494 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -#include // array -#include // size_t -#include // strlen -#include // begin, end, iterator_traits, random_access_iterator_tag, distance, next -#include // shared_ptr, make_shared, addressof -#include // accumulate -#include // string, char_traits -#include // enable_if, is_base_of, is_pointer, is_integral, remove_pointer -#include // pair, declval - -#ifndef JSON_NO_IO - #include // FILE * - #include // istream -#endif // JSON_NO_IO - -#include -#include - -NLOHMANN_JSON_NAMESPACE_BEGIN -namespace detail -{ - -/// the supported input formats -enum class input_format_t { json, cbor, msgpack, ubjson, bson, bjdata }; - -//////////////////// -// input adapters // -//////////////////// - -#ifndef JSON_NO_IO -/*! -Input adapter for stdio file access. This adapter read only 1 byte and do not use any - buffer. This adapter is a very low level adapter. -*/ -class file_input_adapter -{ - public: - using char_type = char; - - JSON_HEDLEY_NON_NULL(2) - explicit file_input_adapter(std::FILE* f) noexcept - : m_file(f) - { - JSON_ASSERT(m_file != nullptr); - } - - // make class move-only - file_input_adapter(const file_input_adapter&) = delete; - file_input_adapter(file_input_adapter&&) noexcept = default; - file_input_adapter& operator=(const file_input_adapter&) = delete; - file_input_adapter& operator=(file_input_adapter&&) = delete; - ~file_input_adapter() = default; - - std::char_traits::int_type get_character() noexcept - { - return std::fgetc(m_file); - } - - private: - /// the file pointer to read from - std::FILE* m_file; -}; - - -/*! -Input adapter for a (caching) istream. Ignores a UFT Byte Order Mark at -beginning of input. Does not support changing the underlying std::streambuf -in mid-input. Maintains underlying std::istream and std::streambuf to support -subsequent use of standard std::istream operations to process any input -characters following those used in parsing the JSON input. Clears the -std::istream flags; any input errors (e.g., EOF) will be detected by the first -subsequent call for input from the std::istream. -*/ -class input_stream_adapter -{ - public: - using char_type = char; - - ~input_stream_adapter() - { - // clear stream flags; we use underlying streambuf I/O, do not - // maintain ifstream flags, except eof - if (is != nullptr) - { - is->clear(is->rdstate() & std::ios::eofbit); - } - } - - explicit input_stream_adapter(std::istream& i) - : is(&i), sb(i.rdbuf()) - {} - - // delete because of pointer members - input_stream_adapter(const input_stream_adapter&) = delete; - input_stream_adapter& operator=(input_stream_adapter&) = delete; - input_stream_adapter& operator=(input_stream_adapter&&) = delete; - - input_stream_adapter(input_stream_adapter&& rhs) noexcept - : is(rhs.is), sb(rhs.sb) - { - rhs.is = nullptr; - rhs.sb = nullptr; - } - - // std::istream/std::streambuf use std::char_traits::to_int_type, to - // ensure that std::char_traits::eof() and the character 0xFF do not - // end up as the same value, e.g. 0xFFFFFFFF. - std::char_traits::int_type get_character() - { - auto res = sb->sbumpc(); - // set eof manually, as we don't use the istream interface. - if (JSON_HEDLEY_UNLIKELY(res == std::char_traits::eof())) - { - is->clear(is->rdstate() | std::ios::eofbit); - } - return res; - } - - private: - /// the associated input stream - std::istream* is = nullptr; - std::streambuf* sb = nullptr; -}; -#endif // JSON_NO_IO - -// General-purpose iterator-based adapter. It might not be as fast as -// theoretically possible for some containers, but it is extremely versatile. -template -class iterator_input_adapter -{ - public: - using char_type = typename std::iterator_traits::value_type; - - iterator_input_adapter(IteratorType first, IteratorType last) - : current(std::move(first)), end(std::move(last)) - {} - - typename std::char_traits::int_type get_character() - { - if (JSON_HEDLEY_LIKELY(current != end)) - { - auto result = std::char_traits::to_int_type(*current); - std::advance(current, 1); - return result; - } - - return std::char_traits::eof(); - } - - private: - IteratorType current; - IteratorType end; - - template - friend struct wide_string_input_helper; - - bool empty() const - { - return current == end; - } -}; - - -template -struct wide_string_input_helper; - -template -struct wide_string_input_helper -{ - // UTF-32 - static void fill_buffer(BaseInputAdapter& input, - std::array::int_type, 4>& utf8_bytes, - size_t& utf8_bytes_index, - size_t& utf8_bytes_filled) - { - utf8_bytes_index = 0; - - if (JSON_HEDLEY_UNLIKELY(input.empty())) - { - utf8_bytes[0] = std::char_traits::eof(); - utf8_bytes_filled = 1; - } - else - { - // get the current character - const auto wc = input.get_character(); - - // UTF-32 to UTF-8 encoding - if (wc < 0x80) - { - utf8_bytes[0] = static_cast::int_type>(wc); - utf8_bytes_filled = 1; - } - else if (wc <= 0x7FF) - { - utf8_bytes[0] = static_cast::int_type>(0xC0u | ((static_cast(wc) >> 6u) & 0x1Fu)); - utf8_bytes[1] = static_cast::int_type>(0x80u | (static_cast(wc) & 0x3Fu)); - utf8_bytes_filled = 2; - } - else if (wc <= 0xFFFF) - { - utf8_bytes[0] = static_cast::int_type>(0xE0u | ((static_cast(wc) >> 12u) & 0x0Fu)); - utf8_bytes[1] = static_cast::int_type>(0x80u | ((static_cast(wc) >> 6u) & 0x3Fu)); - utf8_bytes[2] = static_cast::int_type>(0x80u | (static_cast(wc) & 0x3Fu)); - utf8_bytes_filled = 3; - } - else if (wc <= 0x10FFFF) - { - utf8_bytes[0] = static_cast::int_type>(0xF0u | ((static_cast(wc) >> 18u) & 0x07u)); - utf8_bytes[1] = static_cast::int_type>(0x80u | ((static_cast(wc) >> 12u) & 0x3Fu)); - utf8_bytes[2] = static_cast::int_type>(0x80u | ((static_cast(wc) >> 6u) & 0x3Fu)); - utf8_bytes[3] = static_cast::int_type>(0x80u | (static_cast(wc) & 0x3Fu)); - utf8_bytes_filled = 4; - } - else - { - // unknown character - utf8_bytes[0] = static_cast::int_type>(wc); - utf8_bytes_filled = 1; - } - } - } -}; - -template -struct wide_string_input_helper -{ - // UTF-16 - static void fill_buffer(BaseInputAdapter& input, - std::array::int_type, 4>& utf8_bytes, - size_t& utf8_bytes_index, - size_t& utf8_bytes_filled) - { - utf8_bytes_index = 0; - - if (JSON_HEDLEY_UNLIKELY(input.empty())) - { - utf8_bytes[0] = std::char_traits::eof(); - utf8_bytes_filled = 1; - } - else - { - // get the current character - const auto wc = input.get_character(); - - // UTF-16 to UTF-8 encoding - if (wc < 0x80) - { - utf8_bytes[0] = static_cast::int_type>(wc); - utf8_bytes_filled = 1; - } - else if (wc <= 0x7FF) - { - utf8_bytes[0] = static_cast::int_type>(0xC0u | ((static_cast(wc) >> 6u))); - utf8_bytes[1] = static_cast::int_type>(0x80u | (static_cast(wc) & 0x3Fu)); - utf8_bytes_filled = 2; - } - else if (0xD800 > wc || wc >= 0xE000) - { - utf8_bytes[0] = static_cast::int_type>(0xE0u | ((static_cast(wc) >> 12u))); - utf8_bytes[1] = static_cast::int_type>(0x80u | ((static_cast(wc) >> 6u) & 0x3Fu)); - utf8_bytes[2] = static_cast::int_type>(0x80u | (static_cast(wc) & 0x3Fu)); - utf8_bytes_filled = 3; - } - else - { - if (JSON_HEDLEY_UNLIKELY(!input.empty())) - { - const auto wc2 = static_cast(input.get_character()); - const auto charcode = 0x10000u + (((static_cast(wc) & 0x3FFu) << 10u) | (wc2 & 0x3FFu)); - utf8_bytes[0] = static_cast::int_type>(0xF0u | (charcode >> 18u)); - utf8_bytes[1] = static_cast::int_type>(0x80u | ((charcode >> 12u) & 0x3Fu)); - utf8_bytes[2] = static_cast::int_type>(0x80u | ((charcode >> 6u) & 0x3Fu)); - utf8_bytes[3] = static_cast::int_type>(0x80u | (charcode & 0x3Fu)); - utf8_bytes_filled = 4; - } - else - { - utf8_bytes[0] = static_cast::int_type>(wc); - utf8_bytes_filled = 1; - } - } - } - } -}; - -// Wraps another input apdater to convert wide character types into individual bytes. -template -class wide_string_input_adapter -{ - public: - using char_type = char; - - wide_string_input_adapter(BaseInputAdapter base) - : base_adapter(base) {} - - typename std::char_traits::int_type get_character() noexcept - { - // check if buffer needs to be filled - if (utf8_bytes_index == utf8_bytes_filled) - { - fill_buffer(); - - JSON_ASSERT(utf8_bytes_filled > 0); - JSON_ASSERT(utf8_bytes_index == 0); - } - - // use buffer - JSON_ASSERT(utf8_bytes_filled > 0); - JSON_ASSERT(utf8_bytes_index < utf8_bytes_filled); - return utf8_bytes[utf8_bytes_index++]; - } - - private: - BaseInputAdapter base_adapter; - - template - void fill_buffer() - { - wide_string_input_helper::fill_buffer(base_adapter, utf8_bytes, utf8_bytes_index, utf8_bytes_filled); - } - - /// a buffer for UTF-8 bytes - std::array::int_type, 4> utf8_bytes = {{0, 0, 0, 0}}; - - /// index to the utf8_codes array for the next valid byte - std::size_t utf8_bytes_index = 0; - /// number of valid bytes in the utf8_codes array - std::size_t utf8_bytes_filled = 0; -}; - - -template -struct iterator_input_adapter_factory -{ - using iterator_type = IteratorType; - using char_type = typename std::iterator_traits::value_type; - using adapter_type = iterator_input_adapter; - - static adapter_type create(IteratorType first, IteratorType last) - { - return adapter_type(std::move(first), std::move(last)); - } -}; - -template -struct is_iterator_of_multibyte -{ - using value_type = typename std::iterator_traits::value_type; - enum - { - value = sizeof(value_type) > 1 - }; -}; - -template -struct iterator_input_adapter_factory::value>> -{ - using iterator_type = IteratorType; - using char_type = typename std::iterator_traits::value_type; - using base_adapter_type = iterator_input_adapter; - using adapter_type = wide_string_input_adapter; - - static adapter_type create(IteratorType first, IteratorType last) - { - return adapter_type(base_adapter_type(std::move(first), std::move(last))); - } -}; - -// General purpose iterator-based input -template -typename iterator_input_adapter_factory::adapter_type input_adapter(IteratorType first, IteratorType last) -{ - using factory_type = iterator_input_adapter_factory; - return factory_type::create(first, last); -} - -// Convenience shorthand from container to iterator -// Enables ADL on begin(container) and end(container) -// Encloses the using declarations in namespace for not to leak them to outside scope - -namespace container_input_adapter_factory_impl -{ - -using std::begin; -using std::end; - -template -struct container_input_adapter_factory {}; - -template -struct container_input_adapter_factory< ContainerType, - void_t()), end(std::declval()))>> - { - using adapter_type = decltype(input_adapter(begin(std::declval()), end(std::declval()))); - - static adapter_type create(const ContainerType& container) -{ - return input_adapter(begin(container), end(container)); -} - }; - -} // namespace container_input_adapter_factory_impl - -template -typename container_input_adapter_factory_impl::container_input_adapter_factory::adapter_type input_adapter(const ContainerType& container) -{ - return container_input_adapter_factory_impl::container_input_adapter_factory::create(container); -} - -#ifndef JSON_NO_IO -// Special cases with fast paths -inline file_input_adapter input_adapter(std::FILE* file) -{ - return file_input_adapter(file); -} - -inline input_stream_adapter input_adapter(std::istream& stream) -{ - return input_stream_adapter(stream); -} - -inline input_stream_adapter input_adapter(std::istream&& stream) -{ - return input_stream_adapter(stream); -} -#endif // JSON_NO_IO - -using contiguous_bytes_input_adapter = decltype(input_adapter(std::declval(), std::declval())); - -// Null-delimited strings, and the like. -template < typename CharT, - typename std::enable_if < - std::is_pointer::value&& - !std::is_array::value&& - std::is_integral::type>::value&& - sizeof(typename std::remove_pointer::type) == 1, - int >::type = 0 > -contiguous_bytes_input_adapter input_adapter(CharT b) -{ - auto length = std::strlen(reinterpret_cast(b)); - const auto* ptr = reinterpret_cast(b); - return input_adapter(ptr, ptr + length); -} - -template -auto input_adapter(T (&array)[N]) -> decltype(input_adapter(array, array + N)) // NOLINT(cppcoreguidelines-avoid-c-arrays,hicpp-avoid-c-arrays,modernize-avoid-c-arrays) -{ - return input_adapter(array, array + N); -} - -// This class only handles inputs of input_buffer_adapter type. -// It's required so that expressions like {ptr, len} can be implicitly cast -// to the correct adapter. -class span_input_adapter -{ - public: - template < typename CharT, - typename std::enable_if < - std::is_pointer::value&& - std::is_integral::type>::value&& - sizeof(typename std::remove_pointer::type) == 1, - int >::type = 0 > - span_input_adapter(CharT b, std::size_t l) - : ia(reinterpret_cast(b), reinterpret_cast(b) + l) {} - - template::iterator_category, std::random_access_iterator_tag>::value, - int>::type = 0> - span_input_adapter(IteratorType first, IteratorType last) - : ia(input_adapter(first, last)) {} - - contiguous_bytes_input_adapter&& get() - { - return std::move(ia); // NOLINT(hicpp-move-const-arg,performance-move-const-arg) - } - - private: - contiguous_bytes_input_adapter ia; -}; - -} // namespace detail -NLOHMANN_JSON_NAMESPACE_END diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/input/json_sax.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/input/json_sax.hpp deleted file mode 100644 index 5bd5c51..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/input/json_sax.hpp +++ /dev/null @@ -1,728 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -#include -#include // string -#include // move -#include // vector - -#include -#include -#include - -NLOHMANN_JSON_NAMESPACE_BEGIN - -/*! -@brief SAX interface - -This class describes the SAX interface used by @ref nlohmann::json::sax_parse. -Each function is called in different situations while the input is parsed. The -boolean return value informs the parser whether to continue processing the -input. -*/ -template -struct json_sax -{ - using number_integer_t = typename BasicJsonType::number_integer_t; - using number_unsigned_t = typename BasicJsonType::number_unsigned_t; - using number_float_t = typename BasicJsonType::number_float_t; - using string_t = typename BasicJsonType::string_t; - using binary_t = typename BasicJsonType::binary_t; - - /*! - @brief a null value was read - @return whether parsing should proceed - */ - virtual bool null() = 0; - - /*! - @brief a boolean value was read - @param[in] val boolean value - @return whether parsing should proceed - */ - virtual bool boolean(bool val) = 0; - - /*! - @brief an integer number was read - @param[in] val integer value - @return whether parsing should proceed - */ - virtual bool number_integer(number_integer_t val) = 0; - - /*! - @brief an unsigned integer number was read - @param[in] val unsigned integer value - @return whether parsing should proceed - */ - virtual bool number_unsigned(number_unsigned_t val) = 0; - - /*! - @brief a floating-point number was read - @param[in] val floating-point value - @param[in] s raw token value - @return whether parsing should proceed - */ - virtual bool number_float(number_float_t val, const string_t& s) = 0; - - /*! - @brief a string value was read - @param[in] val string value - @return whether parsing should proceed - @note It is safe to move the passed string value. - */ - virtual bool string(string_t& val) = 0; - - /*! - @brief a binary value was read - @param[in] val binary value - @return whether parsing should proceed - @note It is safe to move the passed binary value. - */ - virtual bool binary(binary_t& val) = 0; - - /*! - @brief the beginning of an object was read - @param[in] elements number of object elements or -1 if unknown - @return whether parsing should proceed - @note binary formats may report the number of elements - */ - virtual bool start_object(std::size_t elements) = 0; - - /*! - @brief an object key was read - @param[in] val object key - @return whether parsing should proceed - @note It is safe to move the passed string. - */ - virtual bool key(string_t& val) = 0; - - /*! - @brief the end of an object was read - @return whether parsing should proceed - */ - virtual bool end_object() = 0; - - /*! - @brief the beginning of an array was read - @param[in] elements number of array elements or -1 if unknown - @return whether parsing should proceed - @note binary formats may report the number of elements - */ - virtual bool start_array(std::size_t elements) = 0; - - /*! - @brief the end of an array was read - @return whether parsing should proceed - */ - virtual bool end_array() = 0; - - /*! - @brief a parse error occurred - @param[in] position the position in the input where the error occurs - @param[in] last_token the last read token - @param[in] ex an exception object describing the error - @return whether parsing should proceed (must return false) - */ - virtual bool parse_error(std::size_t position, - const std::string& last_token, - const detail::exception& ex) = 0; - - json_sax() = default; - json_sax(const json_sax&) = default; - json_sax(json_sax&&) noexcept = default; - json_sax& operator=(const json_sax&) = default; - json_sax& operator=(json_sax&&) noexcept = default; - virtual ~json_sax() = default; -}; - - -namespace detail -{ -/*! -@brief SAX implementation to create a JSON value from SAX events - -This class implements the @ref json_sax interface and processes the SAX events -to create a JSON value which makes it basically a DOM parser. The structure or -hierarchy of the JSON value is managed by the stack `ref_stack` which contains -a pointer to the respective array or object for each recursion depth. - -After successful parsing, the value that is passed by reference to the -constructor contains the parsed value. - -@tparam BasicJsonType the JSON type -*/ -template -class json_sax_dom_parser -{ - public: - using number_integer_t = typename BasicJsonType::number_integer_t; - using number_unsigned_t = typename BasicJsonType::number_unsigned_t; - using number_float_t = typename BasicJsonType::number_float_t; - using string_t = typename BasicJsonType::string_t; - using binary_t = typename BasicJsonType::binary_t; - - /*! - @param[in,out] r reference to a JSON value that is manipulated while - parsing - @param[in] allow_exceptions_ whether parse errors yield exceptions - */ - explicit json_sax_dom_parser(BasicJsonType& r, const bool allow_exceptions_ = true) - : root(r), allow_exceptions(allow_exceptions_) - {} - - // make class move-only - json_sax_dom_parser(const json_sax_dom_parser&) = delete; - json_sax_dom_parser(json_sax_dom_parser&&) = default; // NOLINT(hicpp-noexcept-move,performance-noexcept-move-constructor) - json_sax_dom_parser& operator=(const json_sax_dom_parser&) = delete; - json_sax_dom_parser& operator=(json_sax_dom_parser&&) = default; // NOLINT(hicpp-noexcept-move,performance-noexcept-move-constructor) - ~json_sax_dom_parser() = default; - - bool null() - { - handle_value(nullptr); - return true; - } - - bool boolean(bool val) - { - handle_value(val); - return true; - } - - bool number_integer(number_integer_t val) - { - handle_value(val); - return true; - } - - bool number_unsigned(number_unsigned_t val) - { - handle_value(val); - return true; - } - - bool number_float(number_float_t val, const string_t& /*unused*/) - { - handle_value(val); - return true; - } - - bool string(string_t& val) - { - handle_value(val); - return true; - } - - bool binary(binary_t& val) - { - handle_value(std::move(val)); - return true; - } - - bool start_object(std::size_t len) - { - ref_stack.push_back(handle_value(BasicJsonType::value_t::object)); - - if (JSON_HEDLEY_UNLIKELY(len != static_cast(-1) && len > ref_stack.back()->max_size())) - { - JSON_THROW(out_of_range::create(408, concat("excessive object size: ", std::to_string(len)), ref_stack.back())); - } - - return true; - } - - bool key(string_t& val) - { - JSON_ASSERT(!ref_stack.empty()); - JSON_ASSERT(ref_stack.back()->is_object()); - - // add null at given key and store the reference for later - object_element = &(ref_stack.back()->m_value.object->operator[](val)); - return true; - } - - bool end_object() - { - JSON_ASSERT(!ref_stack.empty()); - JSON_ASSERT(ref_stack.back()->is_object()); - - ref_stack.back()->set_parents(); - ref_stack.pop_back(); - return true; - } - - bool start_array(std::size_t len) - { - ref_stack.push_back(handle_value(BasicJsonType::value_t::array)); - - if (JSON_HEDLEY_UNLIKELY(len != static_cast(-1) && len > ref_stack.back()->max_size())) - { - JSON_THROW(out_of_range::create(408, concat("excessive array size: ", std::to_string(len)), ref_stack.back())); - } - - return true; - } - - bool end_array() - { - JSON_ASSERT(!ref_stack.empty()); - JSON_ASSERT(ref_stack.back()->is_array()); - - ref_stack.back()->set_parents(); - ref_stack.pop_back(); - return true; - } - - template - bool parse_error(std::size_t /*unused*/, const std::string& /*unused*/, - const Exception& ex) - { - errored = true; - static_cast(ex); - if (allow_exceptions) - { - JSON_THROW(ex); - } - return false; - } - - constexpr bool is_errored() const - { - return errored; - } - - private: - /*! - @invariant If the ref stack is empty, then the passed value will be the new - root. - @invariant If the ref stack contains a value, then it is an array or an - object to which we can add elements - */ - template - JSON_HEDLEY_RETURNS_NON_NULL - BasicJsonType* handle_value(Value&& v) - { - if (ref_stack.empty()) - { - root = BasicJsonType(std::forward(v)); - return &root; - } - - JSON_ASSERT(ref_stack.back()->is_array() || ref_stack.back()->is_object()); - - if (ref_stack.back()->is_array()) - { - ref_stack.back()->m_value.array->emplace_back(std::forward(v)); - return &(ref_stack.back()->m_value.array->back()); - } - - JSON_ASSERT(ref_stack.back()->is_object()); - JSON_ASSERT(object_element); - *object_element = BasicJsonType(std::forward(v)); - return object_element; - } - - /// the parsed JSON value - BasicJsonType& root; - /// stack to model hierarchy of values - std::vector ref_stack {}; - /// helper to hold the reference for the next object element - BasicJsonType* object_element = nullptr; - /// whether a syntax error occurred - bool errored = false; - /// whether to throw exceptions in case of errors - const bool allow_exceptions = true; -}; - -template -class json_sax_dom_callback_parser -{ - public: - using number_integer_t = typename BasicJsonType::number_integer_t; - using number_unsigned_t = typename BasicJsonType::number_unsigned_t; - using number_float_t = typename BasicJsonType::number_float_t; - using string_t = typename BasicJsonType::string_t; - using binary_t = typename BasicJsonType::binary_t; - using parser_callback_t = typename BasicJsonType::parser_callback_t; - using parse_event_t = typename BasicJsonType::parse_event_t; - - json_sax_dom_callback_parser(BasicJsonType& r, - const parser_callback_t cb, - const bool allow_exceptions_ = true) - : root(r), callback(cb), allow_exceptions(allow_exceptions_) - { - keep_stack.push_back(true); - } - - // make class move-only - json_sax_dom_callback_parser(const json_sax_dom_callback_parser&) = delete; - json_sax_dom_callback_parser(json_sax_dom_callback_parser&&) = default; // NOLINT(hicpp-noexcept-move,performance-noexcept-move-constructor) - json_sax_dom_callback_parser& operator=(const json_sax_dom_callback_parser&) = delete; - json_sax_dom_callback_parser& operator=(json_sax_dom_callback_parser&&) = default; // NOLINT(hicpp-noexcept-move,performance-noexcept-move-constructor) - ~json_sax_dom_callback_parser() = default; - - bool null() - { - handle_value(nullptr); - return true; - } - - bool boolean(bool val) - { - handle_value(val); - return true; - } - - bool number_integer(number_integer_t val) - { - handle_value(val); - return true; - } - - bool number_unsigned(number_unsigned_t val) - { - handle_value(val); - return true; - } - - bool number_float(number_float_t val, const string_t& /*unused*/) - { - handle_value(val); - return true; - } - - bool string(string_t& val) - { - handle_value(val); - return true; - } - - bool binary(binary_t& val) - { - handle_value(std::move(val)); - return true; - } - - bool start_object(std::size_t len) - { - // check callback for object start - const bool keep = callback(static_cast(ref_stack.size()), parse_event_t::object_start, discarded); - keep_stack.push_back(keep); - - auto val = handle_value(BasicJsonType::value_t::object, true); - ref_stack.push_back(val.second); - - // check object limit - if (ref_stack.back() && JSON_HEDLEY_UNLIKELY(len != static_cast(-1) && len > ref_stack.back()->max_size())) - { - JSON_THROW(out_of_range::create(408, concat("excessive object size: ", std::to_string(len)), ref_stack.back())); - } - - return true; - } - - bool key(string_t& val) - { - BasicJsonType k = BasicJsonType(val); - - // check callback for key - const bool keep = callback(static_cast(ref_stack.size()), parse_event_t::key, k); - key_keep_stack.push_back(keep); - - // add discarded value at given key and store the reference for later - if (keep && ref_stack.back()) - { - object_element = &(ref_stack.back()->m_value.object->operator[](val) = discarded); - } - - return true; - } - - bool end_object() - { - if (ref_stack.back()) - { - if (!callback(static_cast(ref_stack.size()) - 1, parse_event_t::object_end, *ref_stack.back())) - { - // discard object - *ref_stack.back() = discarded; - } - else - { - ref_stack.back()->set_parents(); - } - } - - JSON_ASSERT(!ref_stack.empty()); - JSON_ASSERT(!keep_stack.empty()); - ref_stack.pop_back(); - keep_stack.pop_back(); - - if (!ref_stack.empty() && ref_stack.back() && ref_stack.back()->is_structured()) - { - // remove discarded value - for (auto it = ref_stack.back()->begin(); it != ref_stack.back()->end(); ++it) - { - if (it->is_discarded()) - { - ref_stack.back()->erase(it); - break; - } - } - } - - return true; - } - - bool start_array(std::size_t len) - { - const bool keep = callback(static_cast(ref_stack.size()), parse_event_t::array_start, discarded); - keep_stack.push_back(keep); - - auto val = handle_value(BasicJsonType::value_t::array, true); - ref_stack.push_back(val.second); - - // check array limit - if (ref_stack.back() && JSON_HEDLEY_UNLIKELY(len != static_cast(-1) && len > ref_stack.back()->max_size())) - { - JSON_THROW(out_of_range::create(408, concat("excessive array size: ", std::to_string(len)), ref_stack.back())); - } - - return true; - } - - bool end_array() - { - bool keep = true; - - if (ref_stack.back()) - { - keep = callback(static_cast(ref_stack.size()) - 1, parse_event_t::array_end, *ref_stack.back()); - if (keep) - { - ref_stack.back()->set_parents(); - } - else - { - // discard array - *ref_stack.back() = discarded; - } - } - - JSON_ASSERT(!ref_stack.empty()); - JSON_ASSERT(!keep_stack.empty()); - ref_stack.pop_back(); - keep_stack.pop_back(); - - // remove discarded value - if (!keep && !ref_stack.empty() && ref_stack.back()->is_array()) - { - ref_stack.back()->m_value.array->pop_back(); - } - - return true; - } - - template - bool parse_error(std::size_t /*unused*/, const std::string& /*unused*/, - const Exception& ex) - { - errored = true; - static_cast(ex); - if (allow_exceptions) - { - JSON_THROW(ex); - } - return false; - } - - constexpr bool is_errored() const - { - return errored; - } - - private: - /*! - @param[in] v value to add to the JSON value we build during parsing - @param[in] skip_callback whether we should skip calling the callback - function; this is required after start_array() and - start_object() SAX events, because otherwise we would call the - callback function with an empty array or object, respectively. - - @invariant If the ref stack is empty, then the passed value will be the new - root. - @invariant If the ref stack contains a value, then it is an array or an - object to which we can add elements - - @return pair of boolean (whether value should be kept) and pointer (to the - passed value in the ref_stack hierarchy; nullptr if not kept) - */ - template - std::pair handle_value(Value&& v, const bool skip_callback = false) - { - JSON_ASSERT(!keep_stack.empty()); - - // do not handle this value if we know it would be added to a discarded - // container - if (!keep_stack.back()) - { - return {false, nullptr}; - } - - // create value - auto value = BasicJsonType(std::forward(v)); - - // check callback - const bool keep = skip_callback || callback(static_cast(ref_stack.size()), parse_event_t::value, value); - - // do not handle this value if we just learnt it shall be discarded - if (!keep) - { - return {false, nullptr}; - } - - if (ref_stack.empty()) - { - root = std::move(value); - return {true, &root}; - } - - // skip this value if we already decided to skip the parent - // (https://github.com/nlohmann/json/issues/971#issuecomment-413678360) - if (!ref_stack.back()) - { - return {false, nullptr}; - } - - // we now only expect arrays and objects - JSON_ASSERT(ref_stack.back()->is_array() || ref_stack.back()->is_object()); - - // array - if (ref_stack.back()->is_array()) - { - ref_stack.back()->m_value.array->emplace_back(std::move(value)); - return {true, &(ref_stack.back()->m_value.array->back())}; - } - - // object - JSON_ASSERT(ref_stack.back()->is_object()); - // check if we should store an element for the current key - JSON_ASSERT(!key_keep_stack.empty()); - const bool store_element = key_keep_stack.back(); - key_keep_stack.pop_back(); - - if (!store_element) - { - return {false, nullptr}; - } - - JSON_ASSERT(object_element); - *object_element = std::move(value); - return {true, object_element}; - } - - /// the parsed JSON value - BasicJsonType& root; - /// stack to model hierarchy of values - std::vector ref_stack {}; - /// stack to manage which values to keep - std::vector keep_stack {}; - /// stack to manage which object keys to keep - std::vector key_keep_stack {}; - /// helper to hold the reference for the next object element - BasicJsonType* object_element = nullptr; - /// whether a syntax error occurred - bool errored = false; - /// callback function - const parser_callback_t callback = nullptr; - /// whether to throw exceptions in case of errors - const bool allow_exceptions = true; - /// a discarded value for the callback - BasicJsonType discarded = BasicJsonType::value_t::discarded; -}; - -template -class json_sax_acceptor -{ - public: - using number_integer_t = typename BasicJsonType::number_integer_t; - using number_unsigned_t = typename BasicJsonType::number_unsigned_t; - using number_float_t = typename BasicJsonType::number_float_t; - using string_t = typename BasicJsonType::string_t; - using binary_t = typename BasicJsonType::binary_t; - - bool null() - { - return true; - } - - bool boolean(bool /*unused*/) - { - return true; - } - - bool number_integer(number_integer_t /*unused*/) - { - return true; - } - - bool number_unsigned(number_unsigned_t /*unused*/) - { - return true; - } - - bool number_float(number_float_t /*unused*/, const string_t& /*unused*/) - { - return true; - } - - bool string(string_t& /*unused*/) - { - return true; - } - - bool binary(binary_t& /*unused*/) - { - return true; - } - - bool start_object(std::size_t /*unused*/ = static_cast(-1)) - { - return true; - } - - bool key(string_t& /*unused*/) - { - return true; - } - - bool end_object() - { - return true; - } - - bool start_array(std::size_t /*unused*/ = static_cast(-1)) - { - return true; - } - - bool end_array() - { - return true; - } - - bool parse_error(std::size_t /*unused*/, const std::string& /*unused*/, const detail::exception& /*unused*/) - { - return false; - } -}; - -} // namespace detail -NLOHMANN_JSON_NAMESPACE_END diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/input/lexer.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/input/lexer.hpp deleted file mode 100644 index 72e9951..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/input/lexer.hpp +++ /dev/null @@ -1,1632 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -#include // array -#include // localeconv -#include // size_t -#include // snprintf -#include // strtof, strtod, strtold, strtoll, strtoull -#include // initializer_list -#include // char_traits, string -#include // move -#include // vector - -#include -#include -#include - -NLOHMANN_JSON_NAMESPACE_BEGIN -namespace detail -{ - -/////////// -// lexer // -/////////// - -template -class lexer_base -{ - public: - /// token types for the parser - enum class token_type - { - uninitialized, ///< indicating the scanner is uninitialized - literal_true, ///< the `true` literal - literal_false, ///< the `false` literal - literal_null, ///< the `null` literal - value_string, ///< a string -- use get_string() for actual value - value_unsigned, ///< an unsigned integer -- use get_number_unsigned() for actual value - value_integer, ///< a signed integer -- use get_number_integer() for actual value - value_float, ///< an floating point number -- use get_number_float() for actual value - begin_array, ///< the character for array begin `[` - begin_object, ///< the character for object begin `{` - end_array, ///< the character for array end `]` - end_object, ///< the character for object end `}` - name_separator, ///< the name separator `:` - value_separator, ///< the value separator `,` - parse_error, ///< indicating a parse error - end_of_input, ///< indicating the end of the input buffer - literal_or_value ///< a literal or the begin of a value (only for diagnostics) - }; - - /// return name of values of type token_type (only used for errors) - JSON_HEDLEY_RETURNS_NON_NULL - JSON_HEDLEY_CONST - static const char* token_type_name(const token_type t) noexcept - { - switch (t) - { - case token_type::uninitialized: - return ""; - case token_type::literal_true: - return "true literal"; - case token_type::literal_false: - return "false literal"; - case token_type::literal_null: - return "null literal"; - case token_type::value_string: - return "string literal"; - case token_type::value_unsigned: - case token_type::value_integer: - case token_type::value_float: - return "number literal"; - case token_type::begin_array: - return "'['"; - case token_type::begin_object: - return "'{'"; - case token_type::end_array: - return "']'"; - case token_type::end_object: - return "'}'"; - case token_type::name_separator: - return "':'"; - case token_type::value_separator: - return "','"; - case token_type::parse_error: - return ""; - case token_type::end_of_input: - return "end of input"; - case token_type::literal_or_value: - return "'[', '{', or a literal"; - // LCOV_EXCL_START - default: // catch non-enum values - return "unknown token"; - // LCOV_EXCL_STOP - } - } -}; -/*! -@brief lexical analysis - -This class organizes the lexical analysis during JSON deserialization. -*/ -template -class lexer : public lexer_base -{ - using number_integer_t = typename BasicJsonType::number_integer_t; - using number_unsigned_t = typename BasicJsonType::number_unsigned_t; - using number_float_t = typename BasicJsonType::number_float_t; - using string_t = typename BasicJsonType::string_t; - using char_type = typename InputAdapterType::char_type; - using char_int_type = typename std::char_traits::int_type; - - public: - using token_type = typename lexer_base::token_type; - - explicit lexer(InputAdapterType&& adapter, bool ignore_comments_ = false) noexcept - : ia(std::move(adapter)) - , ignore_comments(ignore_comments_) - , decimal_point_char(static_cast(get_decimal_point())) - {} - - // delete because of pointer members - lexer(const lexer&) = delete; - lexer(lexer&&) = default; // NOLINT(hicpp-noexcept-move,performance-noexcept-move-constructor) - lexer& operator=(lexer&) = delete; - lexer& operator=(lexer&&) = default; // NOLINT(hicpp-noexcept-move,performance-noexcept-move-constructor) - ~lexer() = default; - - private: - ///////////////////// - // locales - ///////////////////// - - /// return the locale-dependent decimal point - JSON_HEDLEY_PURE - static char get_decimal_point() noexcept - { - const auto* loc = localeconv(); - JSON_ASSERT(loc != nullptr); - return (loc->decimal_point == nullptr) ? '.' : *(loc->decimal_point); - } - - ///////////////////// - // scan functions - ///////////////////// - - /*! - @brief get codepoint from 4 hex characters following `\u` - - For input "\u c1 c2 c3 c4" the codepoint is: - (c1 * 0x1000) + (c2 * 0x0100) + (c3 * 0x0010) + c4 - = (c1 << 12) + (c2 << 8) + (c3 << 4) + (c4 << 0) - - Furthermore, the possible characters '0'..'9', 'A'..'F', and 'a'..'f' - must be converted to the integers 0x0..0x9, 0xA..0xF, 0xA..0xF, resp. The - conversion is done by subtracting the offset (0x30, 0x37, and 0x57) - between the ASCII value of the character and the desired integer value. - - @return codepoint (0x0000..0xFFFF) or -1 in case of an error (e.g. EOF or - non-hex character) - */ - int get_codepoint() - { - // this function only makes sense after reading `\u` - JSON_ASSERT(current == 'u'); - int codepoint = 0; - - const auto factors = { 12u, 8u, 4u, 0u }; - for (const auto factor : factors) - { - get(); - - if (current >= '0' && current <= '9') - { - codepoint += static_cast((static_cast(current) - 0x30u) << factor); - } - else if (current >= 'A' && current <= 'F') - { - codepoint += static_cast((static_cast(current) - 0x37u) << factor); - } - else if (current >= 'a' && current <= 'f') - { - codepoint += static_cast((static_cast(current) - 0x57u) << factor); - } - else - { - return -1; - } - } - - JSON_ASSERT(0x0000 <= codepoint && codepoint <= 0xFFFF); - return codepoint; - } - - /*! - @brief check if the next byte(s) are inside a given range - - Adds the current byte and, for each passed range, reads a new byte and - checks if it is inside the range. If a violation was detected, set up an - error message and return false. Otherwise, return true. - - @param[in] ranges list of integers; interpreted as list of pairs of - inclusive lower and upper bound, respectively - - @pre The passed list @a ranges must have 2, 4, or 6 elements; that is, - 1, 2, or 3 pairs. This precondition is enforced by an assertion. - - @return true if and only if no range violation was detected - */ - bool next_byte_in_range(std::initializer_list ranges) - { - JSON_ASSERT(ranges.size() == 2 || ranges.size() == 4 || ranges.size() == 6); - add(current); - - for (auto range = ranges.begin(); range != ranges.end(); ++range) - { - get(); - if (JSON_HEDLEY_LIKELY(*range <= current && current <= *(++range))) - { - add(current); - } - else - { - error_message = "invalid string: ill-formed UTF-8 byte"; - return false; - } - } - - return true; - } - - /*! - @brief scan a string literal - - This function scans a string according to Sect. 7 of RFC 8259. While - scanning, bytes are escaped and copied into buffer token_buffer. Then the - function returns successfully, token_buffer is *not* null-terminated (as it - may contain \0 bytes), and token_buffer.size() is the number of bytes in the - string. - - @return token_type::value_string if string could be successfully scanned, - token_type::parse_error otherwise - - @note In case of errors, variable error_message contains a textual - description. - */ - token_type scan_string() - { - // reset token_buffer (ignore opening quote) - reset(); - - // we entered the function by reading an open quote - JSON_ASSERT(current == '\"'); - - while (true) - { - // get next character - switch (get()) - { - // end of file while parsing string - case std::char_traits::eof(): - { - error_message = "invalid string: missing closing quote"; - return token_type::parse_error; - } - - // closing quote - case '\"': - { - return token_type::value_string; - } - - // escapes - case '\\': - { - switch (get()) - { - // quotation mark - case '\"': - add('\"'); - break; - // reverse solidus - case '\\': - add('\\'); - break; - // solidus - case '/': - add('/'); - break; - // backspace - case 'b': - add('\b'); - break; - // form feed - case 'f': - add('\f'); - break; - // line feed - case 'n': - add('\n'); - break; - // carriage return - case 'r': - add('\r'); - break; - // tab - case 't': - add('\t'); - break; - - // unicode escapes - case 'u': - { - const int codepoint1 = get_codepoint(); - int codepoint = codepoint1; // start with codepoint1 - - if (JSON_HEDLEY_UNLIKELY(codepoint1 == -1)) - { - error_message = "invalid string: '\\u' must be followed by 4 hex digits"; - return token_type::parse_error; - } - - // check if code point is a high surrogate - if (0xD800 <= codepoint1 && codepoint1 <= 0xDBFF) - { - // expect next \uxxxx entry - if (JSON_HEDLEY_LIKELY(get() == '\\' && get() == 'u')) - { - const int codepoint2 = get_codepoint(); - - if (JSON_HEDLEY_UNLIKELY(codepoint2 == -1)) - { - error_message = "invalid string: '\\u' must be followed by 4 hex digits"; - return token_type::parse_error; - } - - // check if codepoint2 is a low surrogate - if (JSON_HEDLEY_LIKELY(0xDC00 <= codepoint2 && codepoint2 <= 0xDFFF)) - { - // overwrite codepoint - codepoint = static_cast( - // high surrogate occupies the most significant 22 bits - (static_cast(codepoint1) << 10u) - // low surrogate occupies the least significant 15 bits - + static_cast(codepoint2) - // there is still the 0xD800, 0xDC00 and 0x10000 noise - // in the result, so we have to subtract with: - // (0xD800 << 10) + DC00 - 0x10000 = 0x35FDC00 - - 0x35FDC00u); - } - else - { - error_message = "invalid string: surrogate U+D800..U+DBFF must be followed by U+DC00..U+DFFF"; - return token_type::parse_error; - } - } - else - { - error_message = "invalid string: surrogate U+D800..U+DBFF must be followed by U+DC00..U+DFFF"; - return token_type::parse_error; - } - } - else - { - if (JSON_HEDLEY_UNLIKELY(0xDC00 <= codepoint1 && codepoint1 <= 0xDFFF)) - { - error_message = "invalid string: surrogate U+DC00..U+DFFF must follow U+D800..U+DBFF"; - return token_type::parse_error; - } - } - - // result of the above calculation yields a proper codepoint - JSON_ASSERT(0x00 <= codepoint && codepoint <= 0x10FFFF); - - // translate codepoint into bytes - if (codepoint < 0x80) - { - // 1-byte characters: 0xxxxxxx (ASCII) - add(static_cast(codepoint)); - } - else if (codepoint <= 0x7FF) - { - // 2-byte characters: 110xxxxx 10xxxxxx - add(static_cast(0xC0u | (static_cast(codepoint) >> 6u))); - add(static_cast(0x80u | (static_cast(codepoint) & 0x3Fu))); - } - else if (codepoint <= 0xFFFF) - { - // 3-byte characters: 1110xxxx 10xxxxxx 10xxxxxx - add(static_cast(0xE0u | (static_cast(codepoint) >> 12u))); - add(static_cast(0x80u | ((static_cast(codepoint) >> 6u) & 0x3Fu))); - add(static_cast(0x80u | (static_cast(codepoint) & 0x3Fu))); - } - else - { - // 4-byte characters: 11110xxx 10xxxxxx 10xxxxxx 10xxxxxx - add(static_cast(0xF0u | (static_cast(codepoint) >> 18u))); - add(static_cast(0x80u | ((static_cast(codepoint) >> 12u) & 0x3Fu))); - add(static_cast(0x80u | ((static_cast(codepoint) >> 6u) & 0x3Fu))); - add(static_cast(0x80u | (static_cast(codepoint) & 0x3Fu))); - } - - break; - } - - // other characters after escape - default: - error_message = "invalid string: forbidden character after backslash"; - return token_type::parse_error; - } - - break; - } - - // invalid control characters - case 0x00: - { - error_message = "invalid string: control character U+0000 (NUL) must be escaped to \\u0000"; - return token_type::parse_error; - } - - case 0x01: - { - error_message = "invalid string: control character U+0001 (SOH) must be escaped to \\u0001"; - return token_type::parse_error; - } - - case 0x02: - { - error_message = "invalid string: control character U+0002 (STX) must be escaped to \\u0002"; - return token_type::parse_error; - } - - case 0x03: - { - error_message = "invalid string: control character U+0003 (ETX) must be escaped to \\u0003"; - return token_type::parse_error; - } - - case 0x04: - { - error_message = "invalid string: control character U+0004 (EOT) must be escaped to \\u0004"; - return token_type::parse_error; - } - - case 0x05: - { - error_message = "invalid string: control character U+0005 (ENQ) must be escaped to \\u0005"; - return token_type::parse_error; - } - - case 0x06: - { - error_message = "invalid string: control character U+0006 (ACK) must be escaped to \\u0006"; - return token_type::parse_error; - } - - case 0x07: - { - error_message = "invalid string: control character U+0007 (BEL) must be escaped to \\u0007"; - return token_type::parse_error; - } - - case 0x08: - { - error_message = "invalid string: control character U+0008 (BS) must be escaped to \\u0008 or \\b"; - return token_type::parse_error; - } - - case 0x09: - { - error_message = "invalid string: control character U+0009 (HT) must be escaped to \\u0009 or \\t"; - return token_type::parse_error; - } - - case 0x0A: - { - error_message = "invalid string: control character U+000A (LF) must be escaped to \\u000A or \\n"; - return token_type::parse_error; - } - - case 0x0B: - { - error_message = "invalid string: control character U+000B (VT) must be escaped to \\u000B"; - return token_type::parse_error; - } - - case 0x0C: - { - error_message = "invalid string: control character U+000C (FF) must be escaped to \\u000C or \\f"; - return token_type::parse_error; - } - - case 0x0D: - { - error_message = "invalid string: control character U+000D (CR) must be escaped to \\u000D or \\r"; - return token_type::parse_error; - } - - case 0x0E: - { - error_message = "invalid string: control character U+000E (SO) must be escaped to \\u000E"; - return token_type::parse_error; - } - - case 0x0F: - { - error_message = "invalid string: control character U+000F (SI) must be escaped to \\u000F"; - return token_type::parse_error; - } - - case 0x10: - { - error_message = "invalid string: control character U+0010 (DLE) must be escaped to \\u0010"; - return token_type::parse_error; - } - - case 0x11: - { - error_message = "invalid string: control character U+0011 (DC1) must be escaped to \\u0011"; - return token_type::parse_error; - } - - case 0x12: - { - error_message = "invalid string: control character U+0012 (DC2) must be escaped to \\u0012"; - return token_type::parse_error; - } - - case 0x13: - { - error_message = "invalid string: control character U+0013 (DC3) must be escaped to \\u0013"; - return token_type::parse_error; - } - - case 0x14: - { - error_message = "invalid string: control character U+0014 (DC4) must be escaped to \\u0014"; - return token_type::parse_error; - } - - case 0x15: - { - error_message = "invalid string: control character U+0015 (NAK) must be escaped to \\u0015"; - return token_type::parse_error; - } - - case 0x16: - { - error_message = "invalid string: control character U+0016 (SYN) must be escaped to \\u0016"; - return token_type::parse_error; - } - - case 0x17: - { - error_message = "invalid string: control character U+0017 (ETB) must be escaped to \\u0017"; - return token_type::parse_error; - } - - case 0x18: - { - error_message = "invalid string: control character U+0018 (CAN) must be escaped to \\u0018"; - return token_type::parse_error; - } - - case 0x19: - { - error_message = "invalid string: control character U+0019 (EM) must be escaped to \\u0019"; - return token_type::parse_error; - } - - case 0x1A: - { - error_message = "invalid string: control character U+001A (SUB) must be escaped to \\u001A"; - return token_type::parse_error; - } - - case 0x1B: - { - error_message = "invalid string: control character U+001B (ESC) must be escaped to \\u001B"; - return token_type::parse_error; - } - - case 0x1C: - { - error_message = "invalid string: control character U+001C (FS) must be escaped to \\u001C"; - return token_type::parse_error; - } - - case 0x1D: - { - error_message = "invalid string: control character U+001D (GS) must be escaped to \\u001D"; - return token_type::parse_error; - } - - case 0x1E: - { - error_message = "invalid string: control character U+001E (RS) must be escaped to \\u001E"; - return token_type::parse_error; - } - - case 0x1F: - { - error_message = "invalid string: control character U+001F (US) must be escaped to \\u001F"; - return token_type::parse_error; - } - - // U+0020..U+007F (except U+0022 (quote) and U+005C (backspace)) - case 0x20: - case 0x21: - case 0x23: - case 0x24: - case 0x25: - case 0x26: - case 0x27: - case 0x28: - case 0x29: - case 0x2A: - case 0x2B: - case 0x2C: - case 0x2D: - case 0x2E: - case 0x2F: - case 0x30: - case 0x31: - case 0x32: - case 0x33: - case 0x34: - case 0x35: - case 0x36: - case 0x37: - case 0x38: - case 0x39: - case 0x3A: - case 0x3B: - case 0x3C: - case 0x3D: - case 0x3E: - case 0x3F: - case 0x40: - case 0x41: - case 0x42: - case 0x43: - case 0x44: - case 0x45: - case 0x46: - case 0x47: - case 0x48: - case 0x49: - case 0x4A: - case 0x4B: - case 0x4C: - case 0x4D: - case 0x4E: - case 0x4F: - case 0x50: - case 0x51: - case 0x52: - case 0x53: - case 0x54: - case 0x55: - case 0x56: - case 0x57: - case 0x58: - case 0x59: - case 0x5A: - case 0x5B: - case 0x5D: - case 0x5E: - case 0x5F: - case 0x60: - case 0x61: - case 0x62: - case 0x63: - case 0x64: - case 0x65: - case 0x66: - case 0x67: - case 0x68: - case 0x69: - case 0x6A: - case 0x6B: - case 0x6C: - case 0x6D: - case 0x6E: - case 0x6F: - case 0x70: - case 0x71: - case 0x72: - case 0x73: - case 0x74: - case 0x75: - case 0x76: - case 0x77: - case 0x78: - case 0x79: - case 0x7A: - case 0x7B: - case 0x7C: - case 0x7D: - case 0x7E: - case 0x7F: - { - add(current); - break; - } - - // U+0080..U+07FF: bytes C2..DF 80..BF - case 0xC2: - case 0xC3: - case 0xC4: - case 0xC5: - case 0xC6: - case 0xC7: - case 0xC8: - case 0xC9: - case 0xCA: - case 0xCB: - case 0xCC: - case 0xCD: - case 0xCE: - case 0xCF: - case 0xD0: - case 0xD1: - case 0xD2: - case 0xD3: - case 0xD4: - case 0xD5: - case 0xD6: - case 0xD7: - case 0xD8: - case 0xD9: - case 0xDA: - case 0xDB: - case 0xDC: - case 0xDD: - case 0xDE: - case 0xDF: - { - if (JSON_HEDLEY_UNLIKELY(!next_byte_in_range({0x80, 0xBF}))) - { - return token_type::parse_error; - } - break; - } - - // U+0800..U+0FFF: bytes E0 A0..BF 80..BF - case 0xE0: - { - if (JSON_HEDLEY_UNLIKELY(!(next_byte_in_range({0xA0, 0xBF, 0x80, 0xBF})))) - { - return token_type::parse_error; - } - break; - } - - // U+1000..U+CFFF: bytes E1..EC 80..BF 80..BF - // U+E000..U+FFFF: bytes EE..EF 80..BF 80..BF - case 0xE1: - case 0xE2: - case 0xE3: - case 0xE4: - case 0xE5: - case 0xE6: - case 0xE7: - case 0xE8: - case 0xE9: - case 0xEA: - case 0xEB: - case 0xEC: - case 0xEE: - case 0xEF: - { - if (JSON_HEDLEY_UNLIKELY(!(next_byte_in_range({0x80, 0xBF, 0x80, 0xBF})))) - { - return token_type::parse_error; - } - break; - } - - // U+D000..U+D7FF: bytes ED 80..9F 80..BF - case 0xED: - { - if (JSON_HEDLEY_UNLIKELY(!(next_byte_in_range({0x80, 0x9F, 0x80, 0xBF})))) - { - return token_type::parse_error; - } - break; - } - - // U+10000..U+3FFFF F0 90..BF 80..BF 80..BF - case 0xF0: - { - if (JSON_HEDLEY_UNLIKELY(!(next_byte_in_range({0x90, 0xBF, 0x80, 0xBF, 0x80, 0xBF})))) - { - return token_type::parse_error; - } - break; - } - - // U+40000..U+FFFFF F1..F3 80..BF 80..BF 80..BF - case 0xF1: - case 0xF2: - case 0xF3: - { - if (JSON_HEDLEY_UNLIKELY(!(next_byte_in_range({0x80, 0xBF, 0x80, 0xBF, 0x80, 0xBF})))) - { - return token_type::parse_error; - } - break; - } - - // U+100000..U+10FFFF F4 80..8F 80..BF 80..BF - case 0xF4: - { - if (JSON_HEDLEY_UNLIKELY(!(next_byte_in_range({0x80, 0x8F, 0x80, 0xBF, 0x80, 0xBF})))) - { - return token_type::parse_error; - } - break; - } - - // remaining bytes (80..C1 and F5..FF) are ill-formed - default: - { - error_message = "invalid string: ill-formed UTF-8 byte"; - return token_type::parse_error; - } - } - } - } - - /*! - * @brief scan a comment - * @return whether comment could be scanned successfully - */ - bool scan_comment() - { - switch (get()) - { - // single-line comments skip input until a newline or EOF is read - case '/': - { - while (true) - { - switch (get()) - { - case '\n': - case '\r': - case std::char_traits::eof(): - case '\0': - return true; - - default: - break; - } - } - } - - // multi-line comments skip input until */ is read - case '*': - { - while (true) - { - switch (get()) - { - case std::char_traits::eof(): - case '\0': - { - error_message = "invalid comment; missing closing '*/'"; - return false; - } - - case '*': - { - switch (get()) - { - case '/': - return true; - - default: - { - unget(); - continue; - } - } - } - - default: - continue; - } - } - } - - // unexpected character after reading '/' - default: - { - error_message = "invalid comment; expecting '/' or '*' after '/'"; - return false; - } - } - } - - JSON_HEDLEY_NON_NULL(2) - static void strtof(float& f, const char* str, char** endptr) noexcept - { - f = std::strtof(str, endptr); - } - - JSON_HEDLEY_NON_NULL(2) - static void strtof(double& f, const char* str, char** endptr) noexcept - { - f = std::strtod(str, endptr); - } - - JSON_HEDLEY_NON_NULL(2) - static void strtof(long double& f, const char* str, char** endptr) noexcept - { - f = std::strtold(str, endptr); - } - - /*! - @brief scan a number literal - - This function scans a string according to Sect. 6 of RFC 8259. - - The function is realized with a deterministic finite state machine derived - from the grammar described in RFC 8259. Starting in state "init", the - input is read and used to determined the next state. Only state "done" - accepts the number. State "error" is a trap state to model errors. In the - table below, "anything" means any character but the ones listed before. - - state | 0 | 1-9 | e E | + | - | . | anything - ---------|----------|----------|----------|---------|---------|----------|----------- - init | zero | any1 | [error] | [error] | minus | [error] | [error] - minus | zero | any1 | [error] | [error] | [error] | [error] | [error] - zero | done | done | exponent | done | done | decimal1 | done - any1 | any1 | any1 | exponent | done | done | decimal1 | done - decimal1 | decimal2 | decimal2 | [error] | [error] | [error] | [error] | [error] - decimal2 | decimal2 | decimal2 | exponent | done | done | done | done - exponent | any2 | any2 | [error] | sign | sign | [error] | [error] - sign | any2 | any2 | [error] | [error] | [error] | [error] | [error] - any2 | any2 | any2 | done | done | done | done | done - - The state machine is realized with one label per state (prefixed with - "scan_number_") and `goto` statements between them. The state machine - contains cycles, but any cycle can be left when EOF is read. Therefore, - the function is guaranteed to terminate. - - During scanning, the read bytes are stored in token_buffer. This string is - then converted to a signed integer, an unsigned integer, or a - floating-point number. - - @return token_type::value_unsigned, token_type::value_integer, or - token_type::value_float if number could be successfully scanned, - token_type::parse_error otherwise - - @note The scanner is independent of the current locale. Internally, the - locale's decimal point is used instead of `.` to work with the - locale-dependent converters. - */ - token_type scan_number() // lgtm [cpp/use-of-goto] - { - // reset token_buffer to store the number's bytes - reset(); - - // the type of the parsed number; initially set to unsigned; will be - // changed if minus sign, decimal point or exponent is read - token_type number_type = token_type::value_unsigned; - - // state (init): we just found out we need to scan a number - switch (current) - { - case '-': - { - add(current); - goto scan_number_minus; - } - - case '0': - { - add(current); - goto scan_number_zero; - } - - case '1': - case '2': - case '3': - case '4': - case '5': - case '6': - case '7': - case '8': - case '9': - { - add(current); - goto scan_number_any1; - } - - // all other characters are rejected outside scan_number() - default: // LCOV_EXCL_LINE - JSON_ASSERT(false); // NOLINT(cert-dcl03-c,hicpp-static-assert,misc-static-assert) LCOV_EXCL_LINE - } - -scan_number_minus: - // state: we just parsed a leading minus sign - number_type = token_type::value_integer; - switch (get()) - { - case '0': - { - add(current); - goto scan_number_zero; - } - - case '1': - case '2': - case '3': - case '4': - case '5': - case '6': - case '7': - case '8': - case '9': - { - add(current); - goto scan_number_any1; - } - - default: - { - error_message = "invalid number; expected digit after '-'"; - return token_type::parse_error; - } - } - -scan_number_zero: - // state: we just parse a zero (maybe with a leading minus sign) - switch (get()) - { - case '.': - { - add(decimal_point_char); - goto scan_number_decimal1; - } - - case 'e': - case 'E': - { - add(current); - goto scan_number_exponent; - } - - default: - goto scan_number_done; - } - -scan_number_any1: - // state: we just parsed a number 0-9 (maybe with a leading minus sign) - switch (get()) - { - case '0': - case '1': - case '2': - case '3': - case '4': - case '5': - case '6': - case '7': - case '8': - case '9': - { - add(current); - goto scan_number_any1; - } - - case '.': - { - add(decimal_point_char); - goto scan_number_decimal1; - } - - case 'e': - case 'E': - { - add(current); - goto scan_number_exponent; - } - - default: - goto scan_number_done; - } - -scan_number_decimal1: - // state: we just parsed a decimal point - number_type = token_type::value_float; - switch (get()) - { - case '0': - case '1': - case '2': - case '3': - case '4': - case '5': - case '6': - case '7': - case '8': - case '9': - { - add(current); - goto scan_number_decimal2; - } - - default: - { - error_message = "invalid number; expected digit after '.'"; - return token_type::parse_error; - } - } - -scan_number_decimal2: - // we just parsed at least one number after a decimal point - switch (get()) - { - case '0': - case '1': - case '2': - case '3': - case '4': - case '5': - case '6': - case '7': - case '8': - case '9': - { - add(current); - goto scan_number_decimal2; - } - - case 'e': - case 'E': - { - add(current); - goto scan_number_exponent; - } - - default: - goto scan_number_done; - } - -scan_number_exponent: - // we just parsed an exponent - number_type = token_type::value_float; - switch (get()) - { - case '+': - case '-': - { - add(current); - goto scan_number_sign; - } - - case '0': - case '1': - case '2': - case '3': - case '4': - case '5': - case '6': - case '7': - case '8': - case '9': - { - add(current); - goto scan_number_any2; - } - - default: - { - error_message = - "invalid number; expected '+', '-', or digit after exponent"; - return token_type::parse_error; - } - } - -scan_number_sign: - // we just parsed an exponent sign - switch (get()) - { - case '0': - case '1': - case '2': - case '3': - case '4': - case '5': - case '6': - case '7': - case '8': - case '9': - { - add(current); - goto scan_number_any2; - } - - default: - { - error_message = "invalid number; expected digit after exponent sign"; - return token_type::parse_error; - } - } - -scan_number_any2: - // we just parsed a number after the exponent or exponent sign - switch (get()) - { - case '0': - case '1': - case '2': - case '3': - case '4': - case '5': - case '6': - case '7': - case '8': - case '9': - { - add(current); - goto scan_number_any2; - } - - default: - goto scan_number_done; - } - -scan_number_done: - // unget the character after the number (we only read it to know that - // we are done scanning a number) - unget(); - - char* endptr = nullptr; // NOLINT(cppcoreguidelines-pro-type-vararg,hicpp-vararg) - errno = 0; - - // try to parse integers first and fall back to floats - if (number_type == token_type::value_unsigned) - { - const auto x = std::strtoull(token_buffer.data(), &endptr, 10); - - // we checked the number format before - JSON_ASSERT(endptr == token_buffer.data() + token_buffer.size()); - - if (errno == 0) - { - value_unsigned = static_cast(x); - if (value_unsigned == x) - { - return token_type::value_unsigned; - } - } - } - else if (number_type == token_type::value_integer) - { - const auto x = std::strtoll(token_buffer.data(), &endptr, 10); - - // we checked the number format before - JSON_ASSERT(endptr == token_buffer.data() + token_buffer.size()); - - if (errno == 0) - { - value_integer = static_cast(x); - if (value_integer == x) - { - return token_type::value_integer; - } - } - } - - // this code is reached if we parse a floating-point number or if an - // integer conversion above failed - strtof(value_float, token_buffer.data(), &endptr); - - // we checked the number format before - JSON_ASSERT(endptr == token_buffer.data() + token_buffer.size()); - - return token_type::value_float; - } - - /*! - @param[in] literal_text the literal text to expect - @param[in] length the length of the passed literal text - @param[in] return_type the token type to return on success - */ - JSON_HEDLEY_NON_NULL(2) - token_type scan_literal(const char_type* literal_text, const std::size_t length, - token_type return_type) - { - JSON_ASSERT(std::char_traits::to_char_type(current) == literal_text[0]); - for (std::size_t i = 1; i < length; ++i) - { - if (JSON_HEDLEY_UNLIKELY(std::char_traits::to_char_type(get()) != literal_text[i])) - { - error_message = "invalid literal"; - return token_type::parse_error; - } - } - return return_type; - } - - ///////////////////// - // input management - ///////////////////// - - /// reset token_buffer; current character is beginning of token - void reset() noexcept - { - token_buffer.clear(); - token_string.clear(); - token_string.push_back(std::char_traits::to_char_type(current)); - } - - /* - @brief get next character from the input - - This function provides the interface to the used input adapter. It does - not throw in case the input reached EOF, but returns a - `std::char_traits::eof()` in that case. Stores the scanned characters - for use in error messages. - - @return character read from the input - */ - char_int_type get() - { - ++position.chars_read_total; - ++position.chars_read_current_line; - - if (next_unget) - { - // just reset the next_unget variable and work with current - next_unget = false; - } - else - { - current = ia.get_character(); - } - - if (JSON_HEDLEY_LIKELY(current != std::char_traits::eof())) - { - token_string.push_back(std::char_traits::to_char_type(current)); - } - - if (current == '\n') - { - ++position.lines_read; - position.chars_read_current_line = 0; - } - - return current; - } - - /*! - @brief unget current character (read it again on next get) - - We implement unget by setting variable next_unget to true. The input is not - changed - we just simulate ungetting by modifying chars_read_total, - chars_read_current_line, and token_string. The next call to get() will - behave as if the unget character is read again. - */ - void unget() - { - next_unget = true; - - --position.chars_read_total; - - // in case we "unget" a newline, we have to also decrement the lines_read - if (position.chars_read_current_line == 0) - { - if (position.lines_read > 0) - { - --position.lines_read; - } - } - else - { - --position.chars_read_current_line; - } - - if (JSON_HEDLEY_LIKELY(current != std::char_traits::eof())) - { - JSON_ASSERT(!token_string.empty()); - token_string.pop_back(); - } - } - - /// add a character to token_buffer - void add(char_int_type c) - { - token_buffer.push_back(static_cast(c)); - } - - public: - ///////////////////// - // value getters - ///////////////////// - - /// return integer value - constexpr number_integer_t get_number_integer() const noexcept - { - return value_integer; - } - - /// return unsigned integer value - constexpr number_unsigned_t get_number_unsigned() const noexcept - { - return value_unsigned; - } - - /// return floating-point value - constexpr number_float_t get_number_float() const noexcept - { - return value_float; - } - - /// return current string value (implicitly resets the token; useful only once) - string_t& get_string() - { - return token_buffer; - } - - ///////////////////// - // diagnostics - ///////////////////// - - /// return position of last read token - constexpr position_t get_position() const noexcept - { - return position; - } - - /// return the last read token (for errors only). Will never contain EOF - /// (an arbitrary value that is not a valid char value, often -1), because - /// 255 may legitimately occur. May contain NUL, which should be escaped. - std::string get_token_string() const - { - // escape control characters - std::string result; - for (const auto c : token_string) - { - if (static_cast(c) <= '\x1F') - { - // escape control characters - std::array cs{{}}; - static_cast((std::snprintf)(cs.data(), cs.size(), "", static_cast(c))); // NOLINT(cppcoreguidelines-pro-type-vararg,hicpp-vararg) - result += cs.data(); - } - else - { - // add character as is - result.push_back(static_cast(c)); - } - } - - return result; - } - - /// return syntax error message - JSON_HEDLEY_RETURNS_NON_NULL - constexpr const char* get_error_message() const noexcept - { - return error_message; - } - - ///////////////////// - // actual scanner - ///////////////////// - - /*! - @brief skip the UTF-8 byte order mark - @return true iff there is no BOM or the correct BOM has been skipped - */ - bool skip_bom() - { - if (get() == 0xEF) - { - // check if we completely parse the BOM - return get() == 0xBB && get() == 0xBF; - } - - // the first character is not the beginning of the BOM; unget it to - // process is later - unget(); - return true; - } - - void skip_whitespace() - { - do - { - get(); - } - while (current == ' ' || current == '\t' || current == '\n' || current == '\r'); - } - - token_type scan() - { - // initially, skip the BOM - if (position.chars_read_total == 0 && !skip_bom()) - { - error_message = "invalid BOM; must be 0xEF 0xBB 0xBF if given"; - return token_type::parse_error; - } - - // read next character and ignore whitespace - skip_whitespace(); - - // ignore comments - while (ignore_comments && current == '/') - { - if (!scan_comment()) - { - return token_type::parse_error; - } - - // skip following whitespace - skip_whitespace(); - } - - switch (current) - { - // structural characters - case '[': - return token_type::begin_array; - case ']': - return token_type::end_array; - case '{': - return token_type::begin_object; - case '}': - return token_type::end_object; - case ':': - return token_type::name_separator; - case ',': - return token_type::value_separator; - - // literals - case 't': - { - std::array true_literal = {{static_cast('t'), static_cast('r'), static_cast('u'), static_cast('e')}}; - return scan_literal(true_literal.data(), true_literal.size(), token_type::literal_true); - } - case 'f': - { - std::array false_literal = {{static_cast('f'), static_cast('a'), static_cast('l'), static_cast('s'), static_cast('e')}}; - return scan_literal(false_literal.data(), false_literal.size(), token_type::literal_false); - } - case 'n': - { - std::array null_literal = {{static_cast('n'), static_cast('u'), static_cast('l'), static_cast('l')}}; - return scan_literal(null_literal.data(), null_literal.size(), token_type::literal_null); - } - - // string - case '\"': - return scan_string(); - - // number - case '-': - case '0': - case '1': - case '2': - case '3': - case '4': - case '5': - case '6': - case '7': - case '8': - case '9': - return scan_number(); - - // end of input (the null byte is needed when parsing from - // string literals) - case '\0': - case std::char_traits::eof(): - return token_type::end_of_input; - - // error - default: - error_message = "invalid literal"; - return token_type::parse_error; - } - } - - private: - /// input adapter - InputAdapterType ia; - - /// whether comments should be ignored (true) or signaled as errors (false) - const bool ignore_comments = false; - - /// the current character - char_int_type current = std::char_traits::eof(); - - /// whether the next get() call should just return current - bool next_unget = false; - - /// the start position of the current token - position_t position {}; - - /// raw input token string (for error messages) - std::vector token_string {}; - - /// buffer for variable-length tokens (numbers, strings) - string_t token_buffer {}; - - /// a description of occurred lexer errors - const char* error_message = ""; - - // number values - number_integer_t value_integer = 0; - number_unsigned_t value_unsigned = 0; - number_float_t value_float = 0; - - /// the decimal point - const char_int_type decimal_point_char = '.'; -}; - -} // namespace detail -NLOHMANN_JSON_NAMESPACE_END diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/input/parser.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/input/parser.hpp deleted file mode 100644 index 8acbd4f..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/input/parser.hpp +++ /dev/null @@ -1,507 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -#include // isfinite -#include // uint8_t -#include // function -#include // string -#include // move -#include // vector - -#include -#include -#include -#include -#include -#include -#include -#include - -NLOHMANN_JSON_NAMESPACE_BEGIN -namespace detail -{ -//////////// -// parser // -//////////// - -enum class parse_event_t : std::uint8_t -{ - /// the parser read `{` and started to process a JSON object - object_start, - /// the parser read `}` and finished processing a JSON object - object_end, - /// the parser read `[` and started to process a JSON array - array_start, - /// the parser read `]` and finished processing a JSON array - array_end, - /// the parser read a key of a value in an object - key, - /// the parser finished reading a JSON value - value -}; - -template -using parser_callback_t = - std::function; - -/*! -@brief syntax analysis - -This class implements a recursive descent parser. -*/ -template -class parser -{ - using number_integer_t = typename BasicJsonType::number_integer_t; - using number_unsigned_t = typename BasicJsonType::number_unsigned_t; - using number_float_t = typename BasicJsonType::number_float_t; - using string_t = typename BasicJsonType::string_t; - using lexer_t = lexer; - using token_type = typename lexer_t::token_type; - - public: - /// a parser reading from an input adapter - explicit parser(InputAdapterType&& adapter, - const parser_callback_t cb = nullptr, - const bool allow_exceptions_ = true, - const bool skip_comments = false) - : callback(cb) - , m_lexer(std::move(adapter), skip_comments) - , allow_exceptions(allow_exceptions_) - { - // read first token - get_token(); - } - - /*! - @brief public parser interface - - @param[in] strict whether to expect the last token to be EOF - @param[in,out] result parsed JSON value - - @throw parse_error.101 in case of an unexpected token - @throw parse_error.102 if to_unicode fails or surrogate error - @throw parse_error.103 if to_unicode fails - */ - void parse(const bool strict, BasicJsonType& result) - { - if (callback) - { - json_sax_dom_callback_parser sdp(result, callback, allow_exceptions); - sax_parse_internal(&sdp); - - // in strict mode, input must be completely read - if (strict && (get_token() != token_type::end_of_input)) - { - sdp.parse_error(m_lexer.get_position(), - m_lexer.get_token_string(), - parse_error::create(101, m_lexer.get_position(), - exception_message(token_type::end_of_input, "value"), nullptr)); - } - - // in case of an error, return discarded value - if (sdp.is_errored()) - { - result = value_t::discarded; - return; - } - - // set top-level value to null if it was discarded by the callback - // function - if (result.is_discarded()) - { - result = nullptr; - } - } - else - { - json_sax_dom_parser sdp(result, allow_exceptions); - sax_parse_internal(&sdp); - - // in strict mode, input must be completely read - if (strict && (get_token() != token_type::end_of_input)) - { - sdp.parse_error(m_lexer.get_position(), - m_lexer.get_token_string(), - parse_error::create(101, m_lexer.get_position(), exception_message(token_type::end_of_input, "value"), nullptr)); - } - - // in case of an error, return discarded value - if (sdp.is_errored()) - { - result = value_t::discarded; - return; - } - } - - result.assert_invariant(); - } - - /*! - @brief public accept interface - - @param[in] strict whether to expect the last token to be EOF - @return whether the input is a proper JSON text - */ - bool accept(const bool strict = true) - { - json_sax_acceptor sax_acceptor; - return sax_parse(&sax_acceptor, strict); - } - - template - JSON_HEDLEY_NON_NULL(2) - bool sax_parse(SAX* sax, const bool strict = true) - { - (void)detail::is_sax_static_asserts {}; - const bool result = sax_parse_internal(sax); - - // strict mode: next byte must be EOF - if (result && strict && (get_token() != token_type::end_of_input)) - { - return sax->parse_error(m_lexer.get_position(), - m_lexer.get_token_string(), - parse_error::create(101, m_lexer.get_position(), exception_message(token_type::end_of_input, "value"), nullptr)); - } - - return result; - } - - private: - template - JSON_HEDLEY_NON_NULL(2) - bool sax_parse_internal(SAX* sax) - { - // stack to remember the hierarchy of structured values we are parsing - // true = array; false = object - std::vector states; - // value to avoid a goto (see comment where set to true) - bool skip_to_state_evaluation = false; - - while (true) - { - if (!skip_to_state_evaluation) - { - // invariant: get_token() was called before each iteration - switch (last_token) - { - case token_type::begin_object: - { - if (JSON_HEDLEY_UNLIKELY(!sax->start_object(static_cast(-1)))) - { - return false; - } - - // closing } -> we are done - if (get_token() == token_type::end_object) - { - if (JSON_HEDLEY_UNLIKELY(!sax->end_object())) - { - return false; - } - break; - } - - // parse key - if (JSON_HEDLEY_UNLIKELY(last_token != token_type::value_string)) - { - return sax->parse_error(m_lexer.get_position(), - m_lexer.get_token_string(), - parse_error::create(101, m_lexer.get_position(), exception_message(token_type::value_string, "object key"), nullptr)); - } - if (JSON_HEDLEY_UNLIKELY(!sax->key(m_lexer.get_string()))) - { - return false; - } - - // parse separator (:) - if (JSON_HEDLEY_UNLIKELY(get_token() != token_type::name_separator)) - { - return sax->parse_error(m_lexer.get_position(), - m_lexer.get_token_string(), - parse_error::create(101, m_lexer.get_position(), exception_message(token_type::name_separator, "object separator"), nullptr)); - } - - // remember we are now inside an object - states.push_back(false); - - // parse values - get_token(); - continue; - } - - case token_type::begin_array: - { - if (JSON_HEDLEY_UNLIKELY(!sax->start_array(static_cast(-1)))) - { - return false; - } - - // closing ] -> we are done - if (get_token() == token_type::end_array) - { - if (JSON_HEDLEY_UNLIKELY(!sax->end_array())) - { - return false; - } - break; - } - - // remember we are now inside an array - states.push_back(true); - - // parse values (no need to call get_token) - continue; - } - - case token_type::value_float: - { - const auto res = m_lexer.get_number_float(); - - if (JSON_HEDLEY_UNLIKELY(!std::isfinite(res))) - { - return sax->parse_error(m_lexer.get_position(), - m_lexer.get_token_string(), - out_of_range::create(406, concat("number overflow parsing '", m_lexer.get_token_string(), '\''), nullptr)); - } - - if (JSON_HEDLEY_UNLIKELY(!sax->number_float(res, m_lexer.get_string()))) - { - return false; - } - - break; - } - - case token_type::literal_false: - { - if (JSON_HEDLEY_UNLIKELY(!sax->boolean(false))) - { - return false; - } - break; - } - - case token_type::literal_null: - { - if (JSON_HEDLEY_UNLIKELY(!sax->null())) - { - return false; - } - break; - } - - case token_type::literal_true: - { - if (JSON_HEDLEY_UNLIKELY(!sax->boolean(true))) - { - return false; - } - break; - } - - case token_type::value_integer: - { - if (JSON_HEDLEY_UNLIKELY(!sax->number_integer(m_lexer.get_number_integer()))) - { - return false; - } - break; - } - - case token_type::value_string: - { - if (JSON_HEDLEY_UNLIKELY(!sax->string(m_lexer.get_string()))) - { - return false; - } - break; - } - - case token_type::value_unsigned: - { - if (JSON_HEDLEY_UNLIKELY(!sax->number_unsigned(m_lexer.get_number_unsigned()))) - { - return false; - } - break; - } - - case token_type::parse_error: - { - // using "uninitialized" to avoid "expected" message - return sax->parse_error(m_lexer.get_position(), - m_lexer.get_token_string(), - parse_error::create(101, m_lexer.get_position(), exception_message(token_type::uninitialized, "value"), nullptr)); - } - - case token_type::uninitialized: - case token_type::end_array: - case token_type::end_object: - case token_type::name_separator: - case token_type::value_separator: - case token_type::end_of_input: - case token_type::literal_or_value: - default: // the last token was unexpected - { - return sax->parse_error(m_lexer.get_position(), - m_lexer.get_token_string(), - parse_error::create(101, m_lexer.get_position(), exception_message(token_type::literal_or_value, "value"), nullptr)); - } - } - } - else - { - skip_to_state_evaluation = false; - } - - // we reached this line after we successfully parsed a value - if (states.empty()) - { - // empty stack: we reached the end of the hierarchy: done - return true; - } - - if (states.back()) // array - { - // comma -> next value - if (get_token() == token_type::value_separator) - { - // parse a new value - get_token(); - continue; - } - - // closing ] - if (JSON_HEDLEY_LIKELY(last_token == token_type::end_array)) - { - if (JSON_HEDLEY_UNLIKELY(!sax->end_array())) - { - return false; - } - - // We are done with this array. Before we can parse a - // new value, we need to evaluate the new state first. - // By setting skip_to_state_evaluation to false, we - // are effectively jumping to the beginning of this if. - JSON_ASSERT(!states.empty()); - states.pop_back(); - skip_to_state_evaluation = true; - continue; - } - - return sax->parse_error(m_lexer.get_position(), - m_lexer.get_token_string(), - parse_error::create(101, m_lexer.get_position(), exception_message(token_type::end_array, "array"), nullptr)); - } - - // states.back() is false -> object - - // comma -> next value - if (get_token() == token_type::value_separator) - { - // parse key - if (JSON_HEDLEY_UNLIKELY(get_token() != token_type::value_string)) - { - return sax->parse_error(m_lexer.get_position(), - m_lexer.get_token_string(), - parse_error::create(101, m_lexer.get_position(), exception_message(token_type::value_string, "object key"), nullptr)); - } - - if (JSON_HEDLEY_UNLIKELY(!sax->key(m_lexer.get_string()))) - { - return false; - } - - // parse separator (:) - if (JSON_HEDLEY_UNLIKELY(get_token() != token_type::name_separator)) - { - return sax->parse_error(m_lexer.get_position(), - m_lexer.get_token_string(), - parse_error::create(101, m_lexer.get_position(), exception_message(token_type::name_separator, "object separator"), nullptr)); - } - - // parse values - get_token(); - continue; - } - - // closing } - if (JSON_HEDLEY_LIKELY(last_token == token_type::end_object)) - { - if (JSON_HEDLEY_UNLIKELY(!sax->end_object())) - { - return false; - } - - // We are done with this object. Before we can parse a - // new value, we need to evaluate the new state first. - // By setting skip_to_state_evaluation to false, we - // are effectively jumping to the beginning of this if. - JSON_ASSERT(!states.empty()); - states.pop_back(); - skip_to_state_evaluation = true; - continue; - } - - return sax->parse_error(m_lexer.get_position(), - m_lexer.get_token_string(), - parse_error::create(101, m_lexer.get_position(), exception_message(token_type::end_object, "object"), nullptr)); - } - } - - /// get next token from lexer - token_type get_token() - { - return last_token = m_lexer.scan(); - } - - std::string exception_message(const token_type expected, const std::string& context) - { - std::string error_msg = "syntax error "; - - if (!context.empty()) - { - error_msg += concat("while parsing ", context, ' '); - } - - error_msg += "- "; - - if (last_token == token_type::parse_error) - { - error_msg += concat(m_lexer.get_error_message(), "; last read: '", - m_lexer.get_token_string(), '\''); - } - else - { - error_msg += concat("unexpected ", lexer_t::token_type_name(last_token)); - } - - if (expected != token_type::uninitialized) - { - error_msg += concat("; expected ", lexer_t::token_type_name(expected)); - } - - return error_msg; - } - - private: - /// callback function - const parser_callback_t callback = nullptr; - /// the type of the last read token - token_type last_token = token_type::uninitialized; - /// the lexer - lexer_t m_lexer; - /// whether to throw exceptions in case of errors - const bool allow_exceptions = true; -}; - -} // namespace detail -NLOHMANN_JSON_NAMESPACE_END diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/input/position_t.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/input/position_t.hpp deleted file mode 100644 index 396db0e..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/input/position_t.hpp +++ /dev/null @@ -1,37 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -#include // size_t - -#include - -NLOHMANN_JSON_NAMESPACE_BEGIN -namespace detail -{ - -/// struct to capture the start position of the current token -struct position_t -{ - /// the total number of characters read - std::size_t chars_read_total = 0; - /// the number of characters read in the current line - std::size_t chars_read_current_line = 0; - /// the number of lines read - std::size_t lines_read = 0; - - /// conversion to size_t to preserve SAX interface - constexpr operator size_t() const - { - return chars_read_total; - } -}; - -} // namespace detail -NLOHMANN_JSON_NAMESPACE_END diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/iterators/internal_iterator.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/iterators/internal_iterator.hpp deleted file mode 100644 index 13a212c..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/iterators/internal_iterator.hpp +++ /dev/null @@ -1,35 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -#include -#include - -NLOHMANN_JSON_NAMESPACE_BEGIN -namespace detail -{ - -/*! -@brief an iterator value - -@note This structure could easily be a union, but MSVC currently does not allow -unions members with complex constructors, see https://github.com/nlohmann/json/pull/105. -*/ -template struct internal_iterator -{ - /// iterator for JSON objects - typename BasicJsonType::object_t::iterator object_iterator {}; - /// iterator for JSON arrays - typename BasicJsonType::array_t::iterator array_iterator {}; - /// generic iterator for all other types - primitive_iterator_t primitive_iterator {}; -}; - -} // namespace detail -NLOHMANN_JSON_NAMESPACE_END diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/iterators/iter_impl.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/iterators/iter_impl.hpp deleted file mode 100644 index 3f5a990..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/iterators/iter_impl.hpp +++ /dev/null @@ -1,751 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -#include // iterator, random_access_iterator_tag, bidirectional_iterator_tag, advance, next -#include // conditional, is_const, remove_const - -#include -#include -#include -#include -#include -#include -#include - -NLOHMANN_JSON_NAMESPACE_BEGIN -namespace detail -{ - -// forward declare, to be able to friend it later on -template class iteration_proxy; -template class iteration_proxy_value; - -/*! -@brief a template for a bidirectional iterator for the @ref basic_json class -This class implements a both iterators (iterator and const_iterator) for the -@ref basic_json class. -@note An iterator is called *initialized* when a pointer to a JSON value has - been set (e.g., by a constructor or a copy assignment). If the iterator is - default-constructed, it is *uninitialized* and most methods are undefined. - **The library uses assertions to detect calls on uninitialized iterators.** -@requirement The class satisfies the following concept requirements: -- -[BidirectionalIterator](https://en.cppreference.com/w/cpp/named_req/BidirectionalIterator): - The iterator that can be moved can be moved in both directions (i.e. - incremented and decremented). -@since version 1.0.0, simplified in version 2.0.9, change to bidirectional - iterators in version 3.0.0 (see https://github.com/nlohmann/json/issues/593) -*/ -template -class iter_impl // NOLINT(cppcoreguidelines-special-member-functions,hicpp-special-member-functions) -{ - /// the iterator with BasicJsonType of different const-ness - using other_iter_impl = iter_impl::value, typename std::remove_const::type, const BasicJsonType>::type>; - /// allow basic_json to access private members - friend other_iter_impl; - friend BasicJsonType; - friend iteration_proxy; - friend iteration_proxy_value; - - using object_t = typename BasicJsonType::object_t; - using array_t = typename BasicJsonType::array_t; - // make sure BasicJsonType is basic_json or const basic_json - static_assert(is_basic_json::type>::value, - "iter_impl only accepts (const) basic_json"); - // superficial check for the LegacyBidirectionalIterator named requirement - static_assert(std::is_base_of::value - && std::is_base_of::iterator_category>::value, - "basic_json iterator assumes array and object type iterators satisfy the LegacyBidirectionalIterator named requirement."); - - public: - /// The std::iterator class template (used as a base class to provide typedefs) is deprecated in C++17. - /// The C++ Standard has never required user-defined iterators to derive from std::iterator. - /// A user-defined iterator should provide publicly accessible typedefs named - /// iterator_category, value_type, difference_type, pointer, and reference. - /// Note that value_type is required to be non-const, even for constant iterators. - using iterator_category = std::bidirectional_iterator_tag; - - /// the type of the values when the iterator is dereferenced - using value_type = typename BasicJsonType::value_type; - /// a type to represent differences between iterators - using difference_type = typename BasicJsonType::difference_type; - /// defines a pointer to the type iterated over (value_type) - using pointer = typename std::conditional::value, - typename BasicJsonType::const_pointer, - typename BasicJsonType::pointer>::type; - /// defines a reference to the type iterated over (value_type) - using reference = - typename std::conditional::value, - typename BasicJsonType::const_reference, - typename BasicJsonType::reference>::type; - - iter_impl() = default; - ~iter_impl() = default; - iter_impl(iter_impl&&) noexcept = default; - iter_impl& operator=(iter_impl&&) noexcept = default; - - /*! - @brief constructor for a given JSON instance - @param[in] object pointer to a JSON object for this iterator - @pre object != nullptr - @post The iterator is initialized; i.e. `m_object != nullptr`. - */ - explicit iter_impl(pointer object) noexcept : m_object(object) - { - JSON_ASSERT(m_object != nullptr); - - switch (m_object->m_type) - { - case value_t::object: - { - m_it.object_iterator = typename object_t::iterator(); - break; - } - - case value_t::array: - { - m_it.array_iterator = typename array_t::iterator(); - break; - } - - case value_t::null: - case value_t::string: - case value_t::boolean: - case value_t::number_integer: - case value_t::number_unsigned: - case value_t::number_float: - case value_t::binary: - case value_t::discarded: - default: - { - m_it.primitive_iterator = primitive_iterator_t(); - break; - } - } - } - - /*! - @note The conventional copy constructor and copy assignment are implicitly - defined. Combined with the following converting constructor and - assignment, they support: (1) copy from iterator to iterator, (2) - copy from const iterator to const iterator, and (3) conversion from - iterator to const iterator. However conversion from const iterator - to iterator is not defined. - */ - - /*! - @brief const copy constructor - @param[in] other const iterator to copy from - @note This copy constructor had to be defined explicitly to circumvent a bug - occurring on msvc v19.0 compiler (VS 2015) debug build. For more - information refer to: https://github.com/nlohmann/json/issues/1608 - */ - iter_impl(const iter_impl& other) noexcept - : m_object(other.m_object), m_it(other.m_it) - {} - - /*! - @brief converting assignment - @param[in] other const iterator to copy from - @return const/non-const iterator - @note It is not checked whether @a other is initialized. - */ - iter_impl& operator=(const iter_impl& other) noexcept - { - if (&other != this) - { - m_object = other.m_object; - m_it = other.m_it; - } - return *this; - } - - /*! - @brief converting constructor - @param[in] other non-const iterator to copy from - @note It is not checked whether @a other is initialized. - */ - iter_impl(const iter_impl::type>& other) noexcept - : m_object(other.m_object), m_it(other.m_it) - {} - - /*! - @brief converting assignment - @param[in] other non-const iterator to copy from - @return const/non-const iterator - @note It is not checked whether @a other is initialized. - */ - iter_impl& operator=(const iter_impl::type>& other) noexcept // NOLINT(cert-oop54-cpp) - { - m_object = other.m_object; - m_it = other.m_it; - return *this; - } - - JSON_PRIVATE_UNLESS_TESTED: - /*! - @brief set the iterator to the first value - @pre The iterator is initialized; i.e. `m_object != nullptr`. - */ - void set_begin() noexcept - { - JSON_ASSERT(m_object != nullptr); - - switch (m_object->m_type) - { - case value_t::object: - { - m_it.object_iterator = m_object->m_value.object->begin(); - break; - } - - case value_t::array: - { - m_it.array_iterator = m_object->m_value.array->begin(); - break; - } - - case value_t::null: - { - // set to end so begin()==end() is true: null is empty - m_it.primitive_iterator.set_end(); - break; - } - - case value_t::string: - case value_t::boolean: - case value_t::number_integer: - case value_t::number_unsigned: - case value_t::number_float: - case value_t::binary: - case value_t::discarded: - default: - { - m_it.primitive_iterator.set_begin(); - break; - } - } - } - - /*! - @brief set the iterator past the last value - @pre The iterator is initialized; i.e. `m_object != nullptr`. - */ - void set_end() noexcept - { - JSON_ASSERT(m_object != nullptr); - - switch (m_object->m_type) - { - case value_t::object: - { - m_it.object_iterator = m_object->m_value.object->end(); - break; - } - - case value_t::array: - { - m_it.array_iterator = m_object->m_value.array->end(); - break; - } - - case value_t::null: - case value_t::string: - case value_t::boolean: - case value_t::number_integer: - case value_t::number_unsigned: - case value_t::number_float: - case value_t::binary: - case value_t::discarded: - default: - { - m_it.primitive_iterator.set_end(); - break; - } - } - } - - public: - /*! - @brief return a reference to the value pointed to by the iterator - @pre The iterator is initialized; i.e. `m_object != nullptr`. - */ - reference operator*() const - { - JSON_ASSERT(m_object != nullptr); - - switch (m_object->m_type) - { - case value_t::object: - { - JSON_ASSERT(m_it.object_iterator != m_object->m_value.object->end()); - return m_it.object_iterator->second; - } - - case value_t::array: - { - JSON_ASSERT(m_it.array_iterator != m_object->m_value.array->end()); - return *m_it.array_iterator; - } - - case value_t::null: - JSON_THROW(invalid_iterator::create(214, "cannot get value", m_object)); - - case value_t::string: - case value_t::boolean: - case value_t::number_integer: - case value_t::number_unsigned: - case value_t::number_float: - case value_t::binary: - case value_t::discarded: - default: - { - if (JSON_HEDLEY_LIKELY(m_it.primitive_iterator.is_begin())) - { - return *m_object; - } - - JSON_THROW(invalid_iterator::create(214, "cannot get value", m_object)); - } - } - } - - /*! - @brief dereference the iterator - @pre The iterator is initialized; i.e. `m_object != nullptr`. - */ - pointer operator->() const - { - JSON_ASSERT(m_object != nullptr); - - switch (m_object->m_type) - { - case value_t::object: - { - JSON_ASSERT(m_it.object_iterator != m_object->m_value.object->end()); - return &(m_it.object_iterator->second); - } - - case value_t::array: - { - JSON_ASSERT(m_it.array_iterator != m_object->m_value.array->end()); - return &*m_it.array_iterator; - } - - case value_t::null: - case value_t::string: - case value_t::boolean: - case value_t::number_integer: - case value_t::number_unsigned: - case value_t::number_float: - case value_t::binary: - case value_t::discarded: - default: - { - if (JSON_HEDLEY_LIKELY(m_it.primitive_iterator.is_begin())) - { - return m_object; - } - - JSON_THROW(invalid_iterator::create(214, "cannot get value", m_object)); - } - } - } - - /*! - @brief post-increment (it++) - @pre The iterator is initialized; i.e. `m_object != nullptr`. - */ - iter_impl operator++(int)& // NOLINT(cert-dcl21-cpp) - { - auto result = *this; - ++(*this); - return result; - } - - /*! - @brief pre-increment (++it) - @pre The iterator is initialized; i.e. `m_object != nullptr`. - */ - iter_impl& operator++() - { - JSON_ASSERT(m_object != nullptr); - - switch (m_object->m_type) - { - case value_t::object: - { - std::advance(m_it.object_iterator, 1); - break; - } - - case value_t::array: - { - std::advance(m_it.array_iterator, 1); - break; - } - - case value_t::null: - case value_t::string: - case value_t::boolean: - case value_t::number_integer: - case value_t::number_unsigned: - case value_t::number_float: - case value_t::binary: - case value_t::discarded: - default: - { - ++m_it.primitive_iterator; - break; - } - } - - return *this; - } - - /*! - @brief post-decrement (it--) - @pre The iterator is initialized; i.e. `m_object != nullptr`. - */ - iter_impl operator--(int)& // NOLINT(cert-dcl21-cpp) - { - auto result = *this; - --(*this); - return result; - } - - /*! - @brief pre-decrement (--it) - @pre The iterator is initialized; i.e. `m_object != nullptr`. - */ - iter_impl& operator--() - { - JSON_ASSERT(m_object != nullptr); - - switch (m_object->m_type) - { - case value_t::object: - { - std::advance(m_it.object_iterator, -1); - break; - } - - case value_t::array: - { - std::advance(m_it.array_iterator, -1); - break; - } - - case value_t::null: - case value_t::string: - case value_t::boolean: - case value_t::number_integer: - case value_t::number_unsigned: - case value_t::number_float: - case value_t::binary: - case value_t::discarded: - default: - { - --m_it.primitive_iterator; - break; - } - } - - return *this; - } - - /*! - @brief comparison: equal - @pre The iterator is initialized; i.e. `m_object != nullptr`. - */ - template < typename IterImpl, detail::enable_if_t < (std::is_same::value || std::is_same::value), std::nullptr_t > = nullptr > - bool operator==(const IterImpl& other) const - { - // if objects are not the same, the comparison is undefined - if (JSON_HEDLEY_UNLIKELY(m_object != other.m_object)) - { - JSON_THROW(invalid_iterator::create(212, "cannot compare iterators of different containers", m_object)); - } - - JSON_ASSERT(m_object != nullptr); - - switch (m_object->m_type) - { - case value_t::object: - return (m_it.object_iterator == other.m_it.object_iterator); - - case value_t::array: - return (m_it.array_iterator == other.m_it.array_iterator); - - case value_t::null: - case value_t::string: - case value_t::boolean: - case value_t::number_integer: - case value_t::number_unsigned: - case value_t::number_float: - case value_t::binary: - case value_t::discarded: - default: - return (m_it.primitive_iterator == other.m_it.primitive_iterator); - } - } - - /*! - @brief comparison: not equal - @pre The iterator is initialized; i.e. `m_object != nullptr`. - */ - template < typename IterImpl, detail::enable_if_t < (std::is_same::value || std::is_same::value), std::nullptr_t > = nullptr > - bool operator!=(const IterImpl& other) const - { - return !operator==(other); - } - - /*! - @brief comparison: smaller - @pre The iterator is initialized; i.e. `m_object != nullptr`. - */ - bool operator<(const iter_impl& other) const - { - // if objects are not the same, the comparison is undefined - if (JSON_HEDLEY_UNLIKELY(m_object != other.m_object)) - { - JSON_THROW(invalid_iterator::create(212, "cannot compare iterators of different containers", m_object)); - } - - JSON_ASSERT(m_object != nullptr); - - switch (m_object->m_type) - { - case value_t::object: - JSON_THROW(invalid_iterator::create(213, "cannot compare order of object iterators", m_object)); - - case value_t::array: - return (m_it.array_iterator < other.m_it.array_iterator); - - case value_t::null: - case value_t::string: - case value_t::boolean: - case value_t::number_integer: - case value_t::number_unsigned: - case value_t::number_float: - case value_t::binary: - case value_t::discarded: - default: - return (m_it.primitive_iterator < other.m_it.primitive_iterator); - } - } - - /*! - @brief comparison: less than or equal - @pre The iterator is initialized; i.e. `m_object != nullptr`. - */ - bool operator<=(const iter_impl& other) const - { - return !other.operator < (*this); - } - - /*! - @brief comparison: greater than - @pre The iterator is initialized; i.e. `m_object != nullptr`. - */ - bool operator>(const iter_impl& other) const - { - return !operator<=(other); - } - - /*! - @brief comparison: greater than or equal - @pre The iterator is initialized; i.e. `m_object != nullptr`. - */ - bool operator>=(const iter_impl& other) const - { - return !operator<(other); - } - - /*! - @brief add to iterator - @pre The iterator is initialized; i.e. `m_object != nullptr`. - */ - iter_impl& operator+=(difference_type i) - { - JSON_ASSERT(m_object != nullptr); - - switch (m_object->m_type) - { - case value_t::object: - JSON_THROW(invalid_iterator::create(209, "cannot use offsets with object iterators", m_object)); - - case value_t::array: - { - std::advance(m_it.array_iterator, i); - break; - } - - case value_t::null: - case value_t::string: - case value_t::boolean: - case value_t::number_integer: - case value_t::number_unsigned: - case value_t::number_float: - case value_t::binary: - case value_t::discarded: - default: - { - m_it.primitive_iterator += i; - break; - } - } - - return *this; - } - - /*! - @brief subtract from iterator - @pre The iterator is initialized; i.e. `m_object != nullptr`. - */ - iter_impl& operator-=(difference_type i) - { - return operator+=(-i); - } - - /*! - @brief add to iterator - @pre The iterator is initialized; i.e. `m_object != nullptr`. - */ - iter_impl operator+(difference_type i) const - { - auto result = *this; - result += i; - return result; - } - - /*! - @brief addition of distance and iterator - @pre The iterator is initialized; i.e. `m_object != nullptr`. - */ - friend iter_impl operator+(difference_type i, const iter_impl& it) - { - auto result = it; - result += i; - return result; - } - - /*! - @brief subtract from iterator - @pre The iterator is initialized; i.e. `m_object != nullptr`. - */ - iter_impl operator-(difference_type i) const - { - auto result = *this; - result -= i; - return result; - } - - /*! - @brief return difference - @pre The iterator is initialized; i.e. `m_object != nullptr`. - */ - difference_type operator-(const iter_impl& other) const - { - JSON_ASSERT(m_object != nullptr); - - switch (m_object->m_type) - { - case value_t::object: - JSON_THROW(invalid_iterator::create(209, "cannot use offsets with object iterators", m_object)); - - case value_t::array: - return m_it.array_iterator - other.m_it.array_iterator; - - case value_t::null: - case value_t::string: - case value_t::boolean: - case value_t::number_integer: - case value_t::number_unsigned: - case value_t::number_float: - case value_t::binary: - case value_t::discarded: - default: - return m_it.primitive_iterator - other.m_it.primitive_iterator; - } - } - - /*! - @brief access to successor - @pre The iterator is initialized; i.e. `m_object != nullptr`. - */ - reference operator[](difference_type n) const - { - JSON_ASSERT(m_object != nullptr); - - switch (m_object->m_type) - { - case value_t::object: - JSON_THROW(invalid_iterator::create(208, "cannot use operator[] for object iterators", m_object)); - - case value_t::array: - return *std::next(m_it.array_iterator, n); - - case value_t::null: - JSON_THROW(invalid_iterator::create(214, "cannot get value", m_object)); - - case value_t::string: - case value_t::boolean: - case value_t::number_integer: - case value_t::number_unsigned: - case value_t::number_float: - case value_t::binary: - case value_t::discarded: - default: - { - if (JSON_HEDLEY_LIKELY(m_it.primitive_iterator.get_value() == -n)) - { - return *m_object; - } - - JSON_THROW(invalid_iterator::create(214, "cannot get value", m_object)); - } - } - } - - /*! - @brief return the key of an object iterator - @pre The iterator is initialized; i.e. `m_object != nullptr`. - */ - const typename object_t::key_type& key() const - { - JSON_ASSERT(m_object != nullptr); - - if (JSON_HEDLEY_LIKELY(m_object->is_object())) - { - return m_it.object_iterator->first; - } - - JSON_THROW(invalid_iterator::create(207, "cannot use key() for non-object iterators", m_object)); - } - - /*! - @brief return the value of an iterator - @pre The iterator is initialized; i.e. `m_object != nullptr`. - */ - reference value() const - { - return operator*(); - } - - JSON_PRIVATE_UNLESS_TESTED: - /// associated JSON instance - pointer m_object = nullptr; - /// the actual iterator of the associated instance - internal_iterator::type> m_it {}; -}; - -} // namespace detail -NLOHMANN_JSON_NAMESPACE_END diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/iterators/iteration_proxy.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/iterators/iteration_proxy.hpp deleted file mode 100644 index 659cd06..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/iterators/iteration_proxy.hpp +++ /dev/null @@ -1,242 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -#include // size_t -#include // input_iterator_tag -#include // string, to_string -#include // tuple_size, get, tuple_element -#include // move - -#if JSON_HAS_RANGES - #include // enable_borrowed_range -#endif - -#include -#include -#include - -NLOHMANN_JSON_NAMESPACE_BEGIN -namespace detail -{ - -template -void int_to_string( string_type& target, std::size_t value ) -{ - // For ADL - using std::to_string; - target = to_string(value); -} -template class iteration_proxy_value -{ - public: - using difference_type = std::ptrdiff_t; - using value_type = iteration_proxy_value; - using pointer = value_type *; - using reference = value_type &; - using iterator_category = std::input_iterator_tag; - using string_type = typename std::remove_cv< typename std::remove_reference().key() ) >::type >::type; - - private: - /// the iterator - IteratorType anchor{}; - /// an index for arrays (used to create key names) - std::size_t array_index = 0; - /// last stringified array index - mutable std::size_t array_index_last = 0; - /// a string representation of the array index - mutable string_type array_index_str = "0"; - /// an empty string (to return a reference for primitive values) - string_type empty_str{}; - - public: - explicit iteration_proxy_value() = default; - explicit iteration_proxy_value(IteratorType it, std::size_t array_index_ = 0) - noexcept(std::is_nothrow_move_constructible::value - && std::is_nothrow_default_constructible::value) - : anchor(std::move(it)) - , array_index(array_index_) - {} - - iteration_proxy_value(iteration_proxy_value const&) = default; - iteration_proxy_value& operator=(iteration_proxy_value const&) = default; - // older GCCs are a bit fussy and require explicit noexcept specifiers on defaulted functions - iteration_proxy_value(iteration_proxy_value&&) - noexcept(std::is_nothrow_move_constructible::value - && std::is_nothrow_move_constructible::value) = default; - iteration_proxy_value& operator=(iteration_proxy_value&&) - noexcept(std::is_nothrow_move_assignable::value - && std::is_nothrow_move_assignable::value) = default; - ~iteration_proxy_value() = default; - - /// dereference operator (needed for range-based for) - const iteration_proxy_value& operator*() const - { - return *this; - } - - /// increment operator (needed for range-based for) - iteration_proxy_value& operator++() - { - ++anchor; - ++array_index; - - return *this; - } - - iteration_proxy_value operator++(int)& // NOLINT(cert-dcl21-cpp) - { - auto tmp = iteration_proxy_value(anchor, array_index); - ++anchor; - ++array_index; - return tmp; - } - - /// equality operator (needed for InputIterator) - bool operator==(const iteration_proxy_value& o) const - { - return anchor == o.anchor; - } - - /// inequality operator (needed for range-based for) - bool operator!=(const iteration_proxy_value& o) const - { - return anchor != o.anchor; - } - - /// return key of the iterator - const string_type& key() const - { - JSON_ASSERT(anchor.m_object != nullptr); - - switch (anchor.m_object->type()) - { - // use integer array index as key - case value_t::array: - { - if (array_index != array_index_last) - { - int_to_string( array_index_str, array_index ); - array_index_last = array_index; - } - return array_index_str; - } - - // use key from the object - case value_t::object: - return anchor.key(); - - // use an empty key for all primitive types - case value_t::null: - case value_t::string: - case value_t::boolean: - case value_t::number_integer: - case value_t::number_unsigned: - case value_t::number_float: - case value_t::binary: - case value_t::discarded: - default: - return empty_str; - } - } - - /// return value of the iterator - typename IteratorType::reference value() const - { - return anchor.value(); - } -}; - -/// proxy class for the items() function -template class iteration_proxy -{ - private: - /// the container to iterate - typename IteratorType::pointer container = nullptr; - - public: - explicit iteration_proxy() = default; - - /// construct iteration proxy from a container - explicit iteration_proxy(typename IteratorType::reference cont) noexcept - : container(&cont) {} - - iteration_proxy(iteration_proxy const&) = default; - iteration_proxy& operator=(iteration_proxy const&) = default; - iteration_proxy(iteration_proxy&&) noexcept = default; - iteration_proxy& operator=(iteration_proxy&&) noexcept = default; - ~iteration_proxy() = default; - - /// return iterator begin (needed for range-based for) - iteration_proxy_value begin() const noexcept - { - return iteration_proxy_value(container->begin()); - } - - /// return iterator end (needed for range-based for) - iteration_proxy_value end() const noexcept - { - return iteration_proxy_value(container->end()); - } -}; - -// Structured Bindings Support -// For further reference see https://blog.tartanllama.xyz/structured-bindings/ -// And see https://github.com/nlohmann/json/pull/1391 -template = 0> -auto get(const nlohmann::detail::iteration_proxy_value& i) -> decltype(i.key()) -{ - return i.key(); -} -// Structured Bindings Support -// For further reference see https://blog.tartanllama.xyz/structured-bindings/ -// And see https://github.com/nlohmann/json/pull/1391 -template = 0> -auto get(const nlohmann::detail::iteration_proxy_value& i) -> decltype(i.value()) -{ - return i.value(); -} - -} // namespace detail -NLOHMANN_JSON_NAMESPACE_END - -// The Addition to the STD Namespace is required to add -// Structured Bindings Support to the iteration_proxy_value class -// For further reference see https://blog.tartanllama.xyz/structured-bindings/ -// And see https://github.com/nlohmann/json/pull/1391 -namespace std -{ - -#if defined(__clang__) - // Fix: https://github.com/nlohmann/json/issues/1401 - #pragma clang diagnostic push - #pragma clang diagnostic ignored "-Wmismatched-tags" -#endif -template -class tuple_size<::nlohmann::detail::iteration_proxy_value> - : public std::integral_constant {}; - -template -class tuple_element> -{ - public: - using type = decltype( - get(std::declval < - ::nlohmann::detail::iteration_proxy_value> ())); -}; -#if defined(__clang__) - #pragma clang diagnostic pop -#endif - -} // namespace std - -#if JSON_HAS_RANGES - template - inline constexpr bool ::std::ranges::enable_borrowed_range<::nlohmann::detail::iteration_proxy> = true; -#endif diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/iterators/iterator_traits.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/iterators/iterator_traits.hpp deleted file mode 100644 index 34a20ee..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/iterators/iterator_traits.hpp +++ /dev/null @@ -1,61 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -#include // random_access_iterator_tag - -#include -#include -#include - -NLOHMANN_JSON_NAMESPACE_BEGIN -namespace detail -{ - -template -struct iterator_types {}; - -template -struct iterator_types < - It, - void_t> -{ - using difference_type = typename It::difference_type; - using value_type = typename It::value_type; - using pointer = typename It::pointer; - using reference = typename It::reference; - using iterator_category = typename It::iterator_category; -}; - -// This is required as some compilers implement std::iterator_traits in a way that -// doesn't work with SFINAE. See https://github.com/nlohmann/json/issues/1341. -template -struct iterator_traits -{ -}; - -template -struct iterator_traits < T, enable_if_t < !std::is_pointer::value >> - : iterator_types -{ -}; - -template -struct iterator_traits::value>> -{ - using iterator_category = std::random_access_iterator_tag; - using value_type = T; - using difference_type = ptrdiff_t; - using pointer = T*; - using reference = T&; -}; - -} // namespace detail -NLOHMANN_JSON_NAMESPACE_END diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/iterators/json_reverse_iterator.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/iterators/json_reverse_iterator.hpp deleted file mode 100644 index eb450e9..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/iterators/json_reverse_iterator.hpp +++ /dev/null @@ -1,130 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -#include // ptrdiff_t -#include // reverse_iterator -#include // declval - -#include - -NLOHMANN_JSON_NAMESPACE_BEGIN -namespace detail -{ - -////////////////////// -// reverse_iterator // -////////////////////// - -/*! -@brief a template for a reverse iterator class - -@tparam Base the base iterator type to reverse. Valid types are @ref -iterator (to create @ref reverse_iterator) and @ref const_iterator (to -create @ref const_reverse_iterator). - -@requirement The class satisfies the following concept requirements: -- -[BidirectionalIterator](https://en.cppreference.com/w/cpp/named_req/BidirectionalIterator): - The iterator that can be moved can be moved in both directions (i.e. - incremented and decremented). -- [OutputIterator](https://en.cppreference.com/w/cpp/named_req/OutputIterator): - It is possible to write to the pointed-to element (only if @a Base is - @ref iterator). - -@since version 1.0.0 -*/ -template -class json_reverse_iterator : public std::reverse_iterator -{ - public: - using difference_type = std::ptrdiff_t; - /// shortcut to the reverse iterator adapter - using base_iterator = std::reverse_iterator; - /// the reference type for the pointed-to element - using reference = typename Base::reference; - - /// create reverse iterator from iterator - explicit json_reverse_iterator(const typename base_iterator::iterator_type& it) noexcept - : base_iterator(it) {} - - /// create reverse iterator from base class - explicit json_reverse_iterator(const base_iterator& it) noexcept : base_iterator(it) {} - - /// post-increment (it++) - json_reverse_iterator operator++(int)& // NOLINT(cert-dcl21-cpp) - { - return static_cast(base_iterator::operator++(1)); - } - - /// pre-increment (++it) - json_reverse_iterator& operator++() - { - return static_cast(base_iterator::operator++()); - } - - /// post-decrement (it--) - json_reverse_iterator operator--(int)& // NOLINT(cert-dcl21-cpp) - { - return static_cast(base_iterator::operator--(1)); - } - - /// pre-decrement (--it) - json_reverse_iterator& operator--() - { - return static_cast(base_iterator::operator--()); - } - - /// add to iterator - json_reverse_iterator& operator+=(difference_type i) - { - return static_cast(base_iterator::operator+=(i)); - } - - /// add to iterator - json_reverse_iterator operator+(difference_type i) const - { - return static_cast(base_iterator::operator+(i)); - } - - /// subtract from iterator - json_reverse_iterator operator-(difference_type i) const - { - return static_cast(base_iterator::operator-(i)); - } - - /// return difference - difference_type operator-(const json_reverse_iterator& other) const - { - return base_iterator(*this) - base_iterator(other); - } - - /// access to successor - reference operator[](difference_type n) const - { - return *(this->operator+(n)); - } - - /// return the key of an object iterator - auto key() const -> decltype(std::declval().key()) - { - auto it = --this->base(); - return it.key(); - } - - /// return the value of an iterator - reference value() const - { - auto it = --this->base(); - return it.operator * (); - } -}; - -} // namespace detail -NLOHMANN_JSON_NAMESPACE_END diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/iterators/primitive_iterator.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/iterators/primitive_iterator.hpp deleted file mode 100644 index 0bc3ca8..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/iterators/primitive_iterator.hpp +++ /dev/null @@ -1,132 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -#include // ptrdiff_t -#include // numeric_limits - -#include - -NLOHMANN_JSON_NAMESPACE_BEGIN -namespace detail -{ - -/* -@brief an iterator for primitive JSON types - -This class models an iterator for primitive JSON types (boolean, number, -string). It's only purpose is to allow the iterator/const_iterator classes -to "iterate" over primitive values. Internally, the iterator is modeled by -a `difference_type` variable. Value begin_value (`0`) models the begin, -end_value (`1`) models past the end. -*/ -class primitive_iterator_t -{ - private: - using difference_type = std::ptrdiff_t; - static constexpr difference_type begin_value = 0; - static constexpr difference_type end_value = begin_value + 1; - - JSON_PRIVATE_UNLESS_TESTED: - /// iterator as signed integer type - difference_type m_it = (std::numeric_limits::min)(); - - public: - constexpr difference_type get_value() const noexcept - { - return m_it; - } - - /// set iterator to a defined beginning - void set_begin() noexcept - { - m_it = begin_value; - } - - /// set iterator to a defined past the end - void set_end() noexcept - { - m_it = end_value; - } - - /// return whether the iterator can be dereferenced - constexpr bool is_begin() const noexcept - { - return m_it == begin_value; - } - - /// return whether the iterator is at end - constexpr bool is_end() const noexcept - { - return m_it == end_value; - } - - friend constexpr bool operator==(primitive_iterator_t lhs, primitive_iterator_t rhs) noexcept - { - return lhs.m_it == rhs.m_it; - } - - friend constexpr bool operator<(primitive_iterator_t lhs, primitive_iterator_t rhs) noexcept - { - return lhs.m_it < rhs.m_it; - } - - primitive_iterator_t operator+(difference_type n) noexcept - { - auto result = *this; - result += n; - return result; - } - - friend constexpr difference_type operator-(primitive_iterator_t lhs, primitive_iterator_t rhs) noexcept - { - return lhs.m_it - rhs.m_it; - } - - primitive_iterator_t& operator++() noexcept - { - ++m_it; - return *this; - } - - primitive_iterator_t operator++(int)& noexcept // NOLINT(cert-dcl21-cpp) - { - auto result = *this; - ++m_it; - return result; - } - - primitive_iterator_t& operator--() noexcept - { - --m_it; - return *this; - } - - primitive_iterator_t operator--(int)& noexcept // NOLINT(cert-dcl21-cpp) - { - auto result = *this; - --m_it; - return result; - } - - primitive_iterator_t& operator+=(difference_type n) noexcept - { - m_it += n; - return *this; - } - - primitive_iterator_t& operator-=(difference_type n) noexcept - { - m_it -= n; - return *this; - } -}; - -} // namespace detail -NLOHMANN_JSON_NAMESPACE_END diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/json_pointer.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/json_pointer.hpp deleted file mode 100644 index 3f69bcd..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/json_pointer.hpp +++ /dev/null @@ -1,988 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -#include // all_of -#include // isdigit -#include // errno, ERANGE -#include // strtoull -#ifndef JSON_NO_IO - #include // ostream -#endif // JSON_NO_IO -#include // max -#include // accumulate -#include // string -#include // move -#include // vector - -#include -#include -#include -#include -#include - -NLOHMANN_JSON_NAMESPACE_BEGIN - -/// @brief JSON Pointer defines a string syntax for identifying a specific value within a JSON document -/// @sa https://json.nlohmann.me/api/json_pointer/ -template -class json_pointer -{ - // allow basic_json to access private members - NLOHMANN_BASIC_JSON_TPL_DECLARATION - friend class basic_json; - - template - friend class json_pointer; - - template - struct string_t_helper - { - using type = T; - }; - - NLOHMANN_BASIC_JSON_TPL_DECLARATION - struct string_t_helper - { - using type = StringType; - }; - - public: - // for backwards compatibility accept BasicJsonType - using string_t = typename string_t_helper::type; - - /// @brief create JSON pointer - /// @sa https://json.nlohmann.me/api/json_pointer/json_pointer/ - explicit json_pointer(const string_t& s = "") - : reference_tokens(split(s)) - {} - - /// @brief return a string representation of the JSON pointer - /// @sa https://json.nlohmann.me/api/json_pointer/to_string/ - string_t to_string() const - { - return std::accumulate(reference_tokens.begin(), reference_tokens.end(), - string_t{}, - [](const string_t& a, const string_t& b) - { - return detail::concat(a, '/', detail::escape(b)); - }); - } - - /// @brief return a string representation of the JSON pointer - /// @sa https://json.nlohmann.me/api/json_pointer/operator_string/ - JSON_HEDLEY_DEPRECATED_FOR(3.11.0, to_string()) - operator string_t() const - { - return to_string(); - } - -#ifndef JSON_NO_IO - /// @brief write string representation of the JSON pointer to stream - /// @sa https://json.nlohmann.me/api/basic_json/operator_ltlt/ - friend std::ostream& operator<<(std::ostream& o, const json_pointer& ptr) - { - o << ptr.to_string(); - return o; - } -#endif - - /// @brief append another JSON pointer at the end of this JSON pointer - /// @sa https://json.nlohmann.me/api/json_pointer/operator_slasheq/ - json_pointer& operator/=(const json_pointer& ptr) - { - reference_tokens.insert(reference_tokens.end(), - ptr.reference_tokens.begin(), - ptr.reference_tokens.end()); - return *this; - } - - /// @brief append an unescaped reference token at the end of this JSON pointer - /// @sa https://json.nlohmann.me/api/json_pointer/operator_slasheq/ - json_pointer& operator/=(string_t token) - { - push_back(std::move(token)); - return *this; - } - - /// @brief append an array index at the end of this JSON pointer - /// @sa https://json.nlohmann.me/api/json_pointer/operator_slasheq/ - json_pointer& operator/=(std::size_t array_idx) - { - return *this /= std::to_string(array_idx); - } - - /// @brief create a new JSON pointer by appending the right JSON pointer at the end of the left JSON pointer - /// @sa https://json.nlohmann.me/api/json_pointer/operator_slash/ - friend json_pointer operator/(const json_pointer& lhs, - const json_pointer& rhs) - { - return json_pointer(lhs) /= rhs; - } - - /// @brief create a new JSON pointer by appending the unescaped token at the end of the JSON pointer - /// @sa https://json.nlohmann.me/api/json_pointer/operator_slash/ - friend json_pointer operator/(const json_pointer& lhs, string_t token) // NOLINT(performance-unnecessary-value-param) - { - return json_pointer(lhs) /= std::move(token); - } - - /// @brief create a new JSON pointer by appending the array-index-token at the end of the JSON pointer - /// @sa https://json.nlohmann.me/api/json_pointer/operator_slash/ - friend json_pointer operator/(const json_pointer& lhs, std::size_t array_idx) - { - return json_pointer(lhs) /= array_idx; - } - - /// @brief returns the parent of this JSON pointer - /// @sa https://json.nlohmann.me/api/json_pointer/parent_pointer/ - json_pointer parent_pointer() const - { - if (empty()) - { - return *this; - } - - json_pointer res = *this; - res.pop_back(); - return res; - } - - /// @brief remove last reference token - /// @sa https://json.nlohmann.me/api/json_pointer/pop_back/ - void pop_back() - { - if (JSON_HEDLEY_UNLIKELY(empty())) - { - JSON_THROW(detail::out_of_range::create(405, "JSON pointer has no parent", nullptr)); - } - - reference_tokens.pop_back(); - } - - /// @brief return last reference token - /// @sa https://json.nlohmann.me/api/json_pointer/back/ - const string_t& back() const - { - if (JSON_HEDLEY_UNLIKELY(empty())) - { - JSON_THROW(detail::out_of_range::create(405, "JSON pointer has no parent", nullptr)); - } - - return reference_tokens.back(); - } - - /// @brief append an unescaped token at the end of the reference pointer - /// @sa https://json.nlohmann.me/api/json_pointer/push_back/ - void push_back(const string_t& token) - { - reference_tokens.push_back(token); - } - - /// @brief append an unescaped token at the end of the reference pointer - /// @sa https://json.nlohmann.me/api/json_pointer/push_back/ - void push_back(string_t&& token) - { - reference_tokens.push_back(std::move(token)); - } - - /// @brief return whether pointer points to the root document - /// @sa https://json.nlohmann.me/api/json_pointer/empty/ - bool empty() const noexcept - { - return reference_tokens.empty(); - } - - private: - /*! - @param[in] s reference token to be converted into an array index - - @return integer representation of @a s - - @throw parse_error.106 if an array index begins with '0' - @throw parse_error.109 if an array index begins not with a digit - @throw out_of_range.404 if string @a s could not be converted to an integer - @throw out_of_range.410 if an array index exceeds size_type - */ - template - static typename BasicJsonType::size_type array_index(const string_t& s) - { - using size_type = typename BasicJsonType::size_type; - - // error condition (cf. RFC 6901, Sect. 4) - if (JSON_HEDLEY_UNLIKELY(s.size() > 1 && s[0] == '0')) - { - JSON_THROW(detail::parse_error::create(106, 0, detail::concat("array index '", s, "' must not begin with '0'"), nullptr)); - } - - // error condition (cf. RFC 6901, Sect. 4) - if (JSON_HEDLEY_UNLIKELY(s.size() > 1 && !(s[0] >= '1' && s[0] <= '9'))) - { - JSON_THROW(detail::parse_error::create(109, 0, detail::concat("array index '", s, "' is not a number"), nullptr)); - } - - const char* p = s.c_str(); - char* p_end = nullptr; - errno = 0; // strtoull doesn't reset errno - unsigned long long res = std::strtoull(p, &p_end, 10); // NOLINT(runtime/int) - if (p == p_end // invalid input or empty string - || errno == ERANGE // out of range - || JSON_HEDLEY_UNLIKELY(static_cast(p_end - p) != s.size())) // incomplete read - { - JSON_THROW(detail::out_of_range::create(404, detail::concat("unresolved reference token '", s, "'"), nullptr)); - } - - // only triggered on special platforms (like 32bit), see also - // https://github.com/nlohmann/json/pull/2203 - if (res >= static_cast((std::numeric_limits::max)())) // NOLINT(runtime/int) - { - JSON_THROW(detail::out_of_range::create(410, detail::concat("array index ", s, " exceeds size_type"), nullptr)); // LCOV_EXCL_LINE - } - - return static_cast(res); - } - - JSON_PRIVATE_UNLESS_TESTED: - json_pointer top() const - { - if (JSON_HEDLEY_UNLIKELY(empty())) - { - JSON_THROW(detail::out_of_range::create(405, "JSON pointer has no parent", nullptr)); - } - - json_pointer result = *this; - result.reference_tokens = {reference_tokens[0]}; - return result; - } - - private: - /*! - @brief create and return a reference to the pointed to value - - @complexity Linear in the number of reference tokens. - - @throw parse_error.109 if array index is not a number - @throw type_error.313 if value cannot be unflattened - */ - template - BasicJsonType& get_and_create(BasicJsonType& j) const - { - auto* result = &j; - - // in case no reference tokens exist, return a reference to the JSON value - // j which will be overwritten by a primitive value - for (const auto& reference_token : reference_tokens) - { - switch (result->type()) - { - case detail::value_t::null: - { - if (reference_token == "0") - { - // start a new array if reference token is 0 - result = &result->operator[](0); - } - else - { - // start a new object otherwise - result = &result->operator[](reference_token); - } - break; - } - - case detail::value_t::object: - { - // create an entry in the object - result = &result->operator[](reference_token); - break; - } - - case detail::value_t::array: - { - // create an entry in the array - result = &result->operator[](array_index(reference_token)); - break; - } - - /* - The following code is only reached if there exists a reference - token _and_ the current value is primitive. In this case, we have - an error situation, because primitive values may only occur as - single value; that is, with an empty list of reference tokens. - */ - case detail::value_t::string: - case detail::value_t::boolean: - case detail::value_t::number_integer: - case detail::value_t::number_unsigned: - case detail::value_t::number_float: - case detail::value_t::binary: - case detail::value_t::discarded: - default: - JSON_THROW(detail::type_error::create(313, "invalid value to unflatten", &j)); - } - } - - return *result; - } - - /*! - @brief return a reference to the pointed to value - - @note This version does not throw if a value is not present, but tries to - create nested values instead. For instance, calling this function - with pointer `"/this/that"` on a null value is equivalent to calling - `operator[]("this").operator[]("that")` on that value, effectively - changing the null value to an object. - - @param[in] ptr a JSON value - - @return reference to the JSON value pointed to by the JSON pointer - - @complexity Linear in the length of the JSON pointer. - - @throw parse_error.106 if an array index begins with '0' - @throw parse_error.109 if an array index was not a number - @throw out_of_range.404 if the JSON pointer can not be resolved - */ - template - BasicJsonType& get_unchecked(BasicJsonType* ptr) const - { - for (const auto& reference_token : reference_tokens) - { - // convert null values to arrays or objects before continuing - if (ptr->is_null()) - { - // check if reference token is a number - const bool nums = - std::all_of(reference_token.begin(), reference_token.end(), - [](const unsigned char x) - { - return std::isdigit(x); - }); - - // change value to array for numbers or "-" or to object otherwise - *ptr = (nums || reference_token == "-") - ? detail::value_t::array - : detail::value_t::object; - } - - switch (ptr->type()) - { - case detail::value_t::object: - { - // use unchecked object access - ptr = &ptr->operator[](reference_token); - break; - } - - case detail::value_t::array: - { - if (reference_token == "-") - { - // explicitly treat "-" as index beyond the end - ptr = &ptr->operator[](ptr->m_value.array->size()); - } - else - { - // convert array index to number; unchecked access - ptr = &ptr->operator[](array_index(reference_token)); - } - break; - } - - case detail::value_t::null: - case detail::value_t::string: - case detail::value_t::boolean: - case detail::value_t::number_integer: - case detail::value_t::number_unsigned: - case detail::value_t::number_float: - case detail::value_t::binary: - case detail::value_t::discarded: - default: - JSON_THROW(detail::out_of_range::create(404, detail::concat("unresolved reference token '", reference_token, "'"), ptr)); - } - } - - return *ptr; - } - - /*! - @throw parse_error.106 if an array index begins with '0' - @throw parse_error.109 if an array index was not a number - @throw out_of_range.402 if the array index '-' is used - @throw out_of_range.404 if the JSON pointer can not be resolved - */ - template - BasicJsonType& get_checked(BasicJsonType* ptr) const - { - for (const auto& reference_token : reference_tokens) - { - switch (ptr->type()) - { - case detail::value_t::object: - { - // note: at performs range check - ptr = &ptr->at(reference_token); - break; - } - - case detail::value_t::array: - { - if (JSON_HEDLEY_UNLIKELY(reference_token == "-")) - { - // "-" always fails the range check - JSON_THROW(detail::out_of_range::create(402, detail::concat( - "array index '-' (", std::to_string(ptr->m_value.array->size()), - ") is out of range"), ptr)); - } - - // note: at performs range check - ptr = &ptr->at(array_index(reference_token)); - break; - } - - case detail::value_t::null: - case detail::value_t::string: - case detail::value_t::boolean: - case detail::value_t::number_integer: - case detail::value_t::number_unsigned: - case detail::value_t::number_float: - case detail::value_t::binary: - case detail::value_t::discarded: - default: - JSON_THROW(detail::out_of_range::create(404, detail::concat("unresolved reference token '", reference_token, "'"), ptr)); - } - } - - return *ptr; - } - - /*! - @brief return a const reference to the pointed to value - - @param[in] ptr a JSON value - - @return const reference to the JSON value pointed to by the JSON - pointer - - @throw parse_error.106 if an array index begins with '0' - @throw parse_error.109 if an array index was not a number - @throw out_of_range.402 if the array index '-' is used - @throw out_of_range.404 if the JSON pointer can not be resolved - */ - template - const BasicJsonType& get_unchecked(const BasicJsonType* ptr) const - { - for (const auto& reference_token : reference_tokens) - { - switch (ptr->type()) - { - case detail::value_t::object: - { - // use unchecked object access - ptr = &ptr->operator[](reference_token); - break; - } - - case detail::value_t::array: - { - if (JSON_HEDLEY_UNLIKELY(reference_token == "-")) - { - // "-" cannot be used for const access - JSON_THROW(detail::out_of_range::create(402, detail::concat("array index '-' (", std::to_string(ptr->m_value.array->size()), ") is out of range"), ptr)); - } - - // use unchecked array access - ptr = &ptr->operator[](array_index(reference_token)); - break; - } - - case detail::value_t::null: - case detail::value_t::string: - case detail::value_t::boolean: - case detail::value_t::number_integer: - case detail::value_t::number_unsigned: - case detail::value_t::number_float: - case detail::value_t::binary: - case detail::value_t::discarded: - default: - JSON_THROW(detail::out_of_range::create(404, detail::concat("unresolved reference token '", reference_token, "'"), ptr)); - } - } - - return *ptr; - } - - /*! - @throw parse_error.106 if an array index begins with '0' - @throw parse_error.109 if an array index was not a number - @throw out_of_range.402 if the array index '-' is used - @throw out_of_range.404 if the JSON pointer can not be resolved - */ - template - const BasicJsonType& get_checked(const BasicJsonType* ptr) const - { - for (const auto& reference_token : reference_tokens) - { - switch (ptr->type()) - { - case detail::value_t::object: - { - // note: at performs range check - ptr = &ptr->at(reference_token); - break; - } - - case detail::value_t::array: - { - if (JSON_HEDLEY_UNLIKELY(reference_token == "-")) - { - // "-" always fails the range check - JSON_THROW(detail::out_of_range::create(402, detail::concat( - "array index '-' (", std::to_string(ptr->m_value.array->size()), - ") is out of range"), ptr)); - } - - // note: at performs range check - ptr = &ptr->at(array_index(reference_token)); - break; - } - - case detail::value_t::null: - case detail::value_t::string: - case detail::value_t::boolean: - case detail::value_t::number_integer: - case detail::value_t::number_unsigned: - case detail::value_t::number_float: - case detail::value_t::binary: - case detail::value_t::discarded: - default: - JSON_THROW(detail::out_of_range::create(404, detail::concat("unresolved reference token '", reference_token, "'"), ptr)); - } - } - - return *ptr; - } - - /*! - @throw parse_error.106 if an array index begins with '0' - @throw parse_error.109 if an array index was not a number - */ - template - bool contains(const BasicJsonType* ptr) const - { - for (const auto& reference_token : reference_tokens) - { - switch (ptr->type()) - { - case detail::value_t::object: - { - if (!ptr->contains(reference_token)) - { - // we did not find the key in the object - return false; - } - - ptr = &ptr->operator[](reference_token); - break; - } - - case detail::value_t::array: - { - if (JSON_HEDLEY_UNLIKELY(reference_token == "-")) - { - // "-" always fails the range check - return false; - } - if (JSON_HEDLEY_UNLIKELY(reference_token.size() == 1 && !("0" <= reference_token && reference_token <= "9"))) - { - // invalid char - return false; - } - if (JSON_HEDLEY_UNLIKELY(reference_token.size() > 1)) - { - if (JSON_HEDLEY_UNLIKELY(!('1' <= reference_token[0] && reference_token[0] <= '9'))) - { - // first char should be between '1' and '9' - return false; - } - for (std::size_t i = 1; i < reference_token.size(); i++) - { - if (JSON_HEDLEY_UNLIKELY(!('0' <= reference_token[i] && reference_token[i] <= '9'))) - { - // other char should be between '0' and '9' - return false; - } - } - } - - const auto idx = array_index(reference_token); - if (idx >= ptr->size()) - { - // index out of range - return false; - } - - ptr = &ptr->operator[](idx); - break; - } - - case detail::value_t::null: - case detail::value_t::string: - case detail::value_t::boolean: - case detail::value_t::number_integer: - case detail::value_t::number_unsigned: - case detail::value_t::number_float: - case detail::value_t::binary: - case detail::value_t::discarded: - default: - { - // we do not expect primitive values if there is still a - // reference token to process - return false; - } - } - } - - // no reference token left means we found a primitive value - return true; - } - - /*! - @brief split the string input to reference tokens - - @note This function is only called by the json_pointer constructor. - All exceptions below are documented there. - - @throw parse_error.107 if the pointer is not empty or begins with '/' - @throw parse_error.108 if character '~' is not followed by '0' or '1' - */ - static std::vector split(const string_t& reference_string) - { - std::vector result; - - // special case: empty reference string -> no reference tokens - if (reference_string.empty()) - { - return result; - } - - // check if nonempty reference string begins with slash - if (JSON_HEDLEY_UNLIKELY(reference_string[0] != '/')) - { - JSON_THROW(detail::parse_error::create(107, 1, detail::concat("JSON pointer must be empty or begin with '/' - was: '", reference_string, "'"), nullptr)); - } - - // extract the reference tokens: - // - slash: position of the last read slash (or end of string) - // - start: position after the previous slash - for ( - // search for the first slash after the first character - std::size_t slash = reference_string.find_first_of('/', 1), - // set the beginning of the first reference token - start = 1; - // we can stop if start == 0 (if slash == string_t::npos) - start != 0; - // set the beginning of the next reference token - // (will eventually be 0 if slash == string_t::npos) - start = (slash == string_t::npos) ? 0 : slash + 1, - // find next slash - slash = reference_string.find_first_of('/', start)) - { - // use the text between the beginning of the reference token - // (start) and the last slash (slash). - auto reference_token = reference_string.substr(start, slash - start); - - // check reference tokens are properly escaped - for (std::size_t pos = reference_token.find_first_of('~'); - pos != string_t::npos; - pos = reference_token.find_first_of('~', pos + 1)) - { - JSON_ASSERT(reference_token[pos] == '~'); - - // ~ must be followed by 0 or 1 - if (JSON_HEDLEY_UNLIKELY(pos == reference_token.size() - 1 || - (reference_token[pos + 1] != '0' && - reference_token[pos + 1] != '1'))) - { - JSON_THROW(detail::parse_error::create(108, 0, "escape character '~' must be followed with '0' or '1'", nullptr)); - } - } - - // finally, store the reference token - detail::unescape(reference_token); - result.push_back(reference_token); - } - - return result; - } - - private: - /*! - @param[in] reference_string the reference string to the current value - @param[in] value the value to consider - @param[in,out] result the result object to insert values to - - @note Empty objects or arrays are flattened to `null`. - */ - template - static void flatten(const string_t& reference_string, - const BasicJsonType& value, - BasicJsonType& result) - { - switch (value.type()) - { - case detail::value_t::array: - { - if (value.m_value.array->empty()) - { - // flatten empty array as null - result[reference_string] = nullptr; - } - else - { - // iterate array and use index as reference string - for (std::size_t i = 0; i < value.m_value.array->size(); ++i) - { - flatten(detail::concat(reference_string, '/', std::to_string(i)), - value.m_value.array->operator[](i), result); - } - } - break; - } - - case detail::value_t::object: - { - if (value.m_value.object->empty()) - { - // flatten empty object as null - result[reference_string] = nullptr; - } - else - { - // iterate object and use keys as reference string - for (const auto& element : *value.m_value.object) - { - flatten(detail::concat(reference_string, '/', detail::escape(element.first)), element.second, result); - } - } - break; - } - - case detail::value_t::null: - case detail::value_t::string: - case detail::value_t::boolean: - case detail::value_t::number_integer: - case detail::value_t::number_unsigned: - case detail::value_t::number_float: - case detail::value_t::binary: - case detail::value_t::discarded: - default: - { - // add primitive value with its reference string - result[reference_string] = value; - break; - } - } - } - - /*! - @param[in] value flattened JSON - - @return unflattened JSON - - @throw parse_error.109 if array index is not a number - @throw type_error.314 if value is not an object - @throw type_error.315 if object values are not primitive - @throw type_error.313 if value cannot be unflattened - */ - template - static BasicJsonType - unflatten(const BasicJsonType& value) - { - if (JSON_HEDLEY_UNLIKELY(!value.is_object())) - { - JSON_THROW(detail::type_error::create(314, "only objects can be unflattened", &value)); - } - - BasicJsonType result; - - // iterate the JSON object values - for (const auto& element : *value.m_value.object) - { - if (JSON_HEDLEY_UNLIKELY(!element.second.is_primitive())) - { - JSON_THROW(detail::type_error::create(315, "values in object must be primitive", &element.second)); - } - - // assign value to reference pointed to by JSON pointer; Note that if - // the JSON pointer is "" (i.e., points to the whole value), function - // get_and_create returns a reference to result itself. An assignment - // will then create a primitive value. - json_pointer(element.first).get_and_create(result) = element.second; - } - - return result; - } - - // can't use conversion operator because of ambiguity - json_pointer convert() const& - { - json_pointer result; - result.reference_tokens = reference_tokens; - return result; - } - - json_pointer convert()&& - { - json_pointer result; - result.reference_tokens = std::move(reference_tokens); - return result; - } - - public: -#if JSON_HAS_THREE_WAY_COMPARISON - /// @brief compares two JSON pointers for equality - /// @sa https://json.nlohmann.me/api/json_pointer/operator_eq/ - template - bool operator==(const json_pointer& rhs) const noexcept - { - return reference_tokens == rhs.reference_tokens; - } - - /// @brief compares JSON pointer and string for equality - /// @sa https://json.nlohmann.me/api/json_pointer/operator_eq/ - JSON_HEDLEY_DEPRECATED_FOR(3.11.2, operator==(json_pointer)) - bool operator==(const string_t& rhs) const - { - return *this == json_pointer(rhs); - } - - /// @brief 3-way compares two JSON pointers - template - std::strong_ordering operator<=>(const json_pointer& rhs) const noexcept // *NOPAD* - { - return reference_tokens <=> rhs.reference_tokens; // *NOPAD* - } -#else - /// @brief compares two JSON pointers for equality - /// @sa https://json.nlohmann.me/api/json_pointer/operator_eq/ - template - // NOLINTNEXTLINE(readability-redundant-declaration) - friend bool operator==(const json_pointer& lhs, - const json_pointer& rhs) noexcept; - - /// @brief compares JSON pointer and string for equality - /// @sa https://json.nlohmann.me/api/json_pointer/operator_eq/ - template - // NOLINTNEXTLINE(readability-redundant-declaration) - friend bool operator==(const json_pointer& lhs, - const StringType& rhs); - - /// @brief compares string and JSON pointer for equality - /// @sa https://json.nlohmann.me/api/json_pointer/operator_eq/ - template - // NOLINTNEXTLINE(readability-redundant-declaration) - friend bool operator==(const StringType& lhs, - const json_pointer& rhs); - - /// @brief compares two JSON pointers for inequality - /// @sa https://json.nlohmann.me/api/json_pointer/operator_ne/ - template - // NOLINTNEXTLINE(readability-redundant-declaration) - friend bool operator!=(const json_pointer& lhs, - const json_pointer& rhs) noexcept; - - /// @brief compares JSON pointer and string for inequality - /// @sa https://json.nlohmann.me/api/json_pointer/operator_ne/ - template - // NOLINTNEXTLINE(readability-redundant-declaration) - friend bool operator!=(const json_pointer& lhs, - const StringType& rhs); - - /// @brief compares string and JSON pointer for inequality - /// @sa https://json.nlohmann.me/api/json_pointer/operator_ne/ - template - // NOLINTNEXTLINE(readability-redundant-declaration) - friend bool operator!=(const StringType& lhs, - const json_pointer& rhs); - - /// @brief compares two JSON pointer for less-than - template - // NOLINTNEXTLINE(readability-redundant-declaration) - friend bool operator<(const json_pointer& lhs, - const json_pointer& rhs) noexcept; -#endif - - private: - /// the reference tokens - std::vector reference_tokens; -}; - -#if !JSON_HAS_THREE_WAY_COMPARISON -// functions cannot be defined inside class due to ODR violations -template -inline bool operator==(const json_pointer& lhs, - const json_pointer& rhs) noexcept -{ - return lhs.reference_tokens == rhs.reference_tokens; -} - -template::string_t> -JSON_HEDLEY_DEPRECATED_FOR(3.11.2, operator==(json_pointer, json_pointer)) -inline bool operator==(const json_pointer& lhs, - const StringType& rhs) -{ - return lhs == json_pointer(rhs); -} - -template::string_t> -JSON_HEDLEY_DEPRECATED_FOR(3.11.2, operator==(json_pointer, json_pointer)) -inline bool operator==(const StringType& lhs, - const json_pointer& rhs) -{ - return json_pointer(lhs) == rhs; -} - -template -inline bool operator!=(const json_pointer& lhs, - const json_pointer& rhs) noexcept -{ - return !(lhs == rhs); -} - -template::string_t> -JSON_HEDLEY_DEPRECATED_FOR(3.11.2, operator!=(json_pointer, json_pointer)) -inline bool operator!=(const json_pointer& lhs, - const StringType& rhs) -{ - return !(lhs == rhs); -} - -template::string_t> -JSON_HEDLEY_DEPRECATED_FOR(3.11.2, operator!=(json_pointer, json_pointer)) -inline bool operator!=(const StringType& lhs, - const json_pointer& rhs) -{ - return !(lhs == rhs); -} - -template -inline bool operator<(const json_pointer& lhs, - const json_pointer& rhs) noexcept -{ - return lhs.reference_tokens < rhs.reference_tokens; -} -#endif - -NLOHMANN_JSON_NAMESPACE_END diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/json_ref.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/json_ref.hpp deleted file mode 100644 index 47911fb..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/json_ref.hpp +++ /dev/null @@ -1,78 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -#include -#include - -#include -#include - -NLOHMANN_JSON_NAMESPACE_BEGIN -namespace detail -{ - -template -class json_ref -{ - public: - using value_type = BasicJsonType; - - json_ref(value_type&& value) - : owned_value(std::move(value)) - {} - - json_ref(const value_type& value) - : value_ref(&value) - {} - - json_ref(std::initializer_list init) - : owned_value(init) - {} - - template < - class... Args, - enable_if_t::value, int> = 0 > - json_ref(Args && ... args) - : owned_value(std::forward(args)...) - {} - - // class should be movable only - json_ref(json_ref&&) noexcept = default; - json_ref(const json_ref&) = delete; - json_ref& operator=(const json_ref&) = delete; - json_ref& operator=(json_ref&&) = delete; - ~json_ref() = default; - - value_type moved_or_copied() const - { - if (value_ref == nullptr) - { - return std::move(owned_value); - } - return *value_ref; - } - - value_type const& operator*() const - { - return value_ref ? *value_ref : owned_value; - } - - value_type const* operator->() const - { - return &** this; - } - - private: - mutable value_type owned_value = nullptr; - value_type const* value_ref = nullptr; -}; - -} // namespace detail -NLOHMANN_JSON_NAMESPACE_END diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/macro_scope.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/macro_scope.hpp deleted file mode 100644 index 6248bea..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/macro_scope.hpp +++ /dev/null @@ -1,468 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -#include // declval, pair -#include -#include - -// This file contains all internal macro definitions (except those affecting ABI) -// You MUST include macro_unscope.hpp at the end of json.hpp to undef all of them - -#include - -// exclude unsupported compilers -#if !defined(JSON_SKIP_UNSUPPORTED_COMPILER_CHECK) - #if defined(__clang__) - #if (__clang_major__ * 10000 + __clang_minor__ * 100 + __clang_patchlevel__) < 30400 - #error "unsupported Clang version - see https://github.com/nlohmann/json#supported-compilers" - #endif - #elif defined(__GNUC__) && !(defined(__ICC) || defined(__INTEL_COMPILER)) - #if (__GNUC__ * 10000 + __GNUC_MINOR__ * 100 + __GNUC_PATCHLEVEL__) < 40800 - #error "unsupported GCC version - see https://github.com/nlohmann/json#supported-compilers" - #endif - #endif -#endif - -// C++ language standard detection -// if the user manually specified the used c++ version this is skipped -#if !defined(JSON_HAS_CPP_20) && !defined(JSON_HAS_CPP_17) && !defined(JSON_HAS_CPP_14) && !defined(JSON_HAS_CPP_11) - #if (defined(__cplusplus) && __cplusplus >= 202002L) || (defined(_MSVC_LANG) && _MSVC_LANG >= 202002L) - #define JSON_HAS_CPP_20 - #define JSON_HAS_CPP_17 - #define JSON_HAS_CPP_14 - #elif (defined(__cplusplus) && __cplusplus >= 201703L) || (defined(_HAS_CXX17) && _HAS_CXX17 == 1) // fix for issue #464 - #define JSON_HAS_CPP_17 - #define JSON_HAS_CPP_14 - #elif (defined(__cplusplus) && __cplusplus >= 201402L) || (defined(_HAS_CXX14) && _HAS_CXX14 == 1) - #define JSON_HAS_CPP_14 - #endif - // the cpp 11 flag is always specified because it is the minimal required version - #define JSON_HAS_CPP_11 -#endif - -#ifdef __has_include - #if __has_include() - #include - #endif -#endif - -#if !defined(JSON_HAS_FILESYSTEM) && !defined(JSON_HAS_EXPERIMENTAL_FILESYSTEM) - #ifdef JSON_HAS_CPP_17 - #if defined(__cpp_lib_filesystem) - #define JSON_HAS_FILESYSTEM 1 - #elif defined(__cpp_lib_experimental_filesystem) - #define JSON_HAS_EXPERIMENTAL_FILESYSTEM 1 - #elif !defined(__has_include) - #define JSON_HAS_EXPERIMENTAL_FILESYSTEM 1 - #elif __has_include() - #define JSON_HAS_FILESYSTEM 1 - #elif __has_include() - #define JSON_HAS_EXPERIMENTAL_FILESYSTEM 1 - #endif - - // std::filesystem does not work on MinGW GCC 8: https://sourceforge.net/p/mingw-w64/bugs/737/ - #if defined(__MINGW32__) && defined(__GNUC__) && __GNUC__ == 8 - #undef JSON_HAS_FILESYSTEM - #undef JSON_HAS_EXPERIMENTAL_FILESYSTEM - #endif - - // no filesystem support before GCC 8: https://en.cppreference.com/w/cpp/compiler_support - #if defined(__GNUC__) && !defined(__clang__) && __GNUC__ < 8 - #undef JSON_HAS_FILESYSTEM - #undef JSON_HAS_EXPERIMENTAL_FILESYSTEM - #endif - - // no filesystem support before Clang 7: https://en.cppreference.com/w/cpp/compiler_support - #if defined(__clang_major__) && __clang_major__ < 7 - #undef JSON_HAS_FILESYSTEM - #undef JSON_HAS_EXPERIMENTAL_FILESYSTEM - #endif - - // no filesystem support before MSVC 19.14: https://en.cppreference.com/w/cpp/compiler_support - #if defined(_MSC_VER) && _MSC_VER < 1914 - #undef JSON_HAS_FILESYSTEM - #undef JSON_HAS_EXPERIMENTAL_FILESYSTEM - #endif - - // no filesystem support before iOS 13 - #if defined(__IPHONE_OS_VERSION_MIN_REQUIRED) && __IPHONE_OS_VERSION_MIN_REQUIRED < 130000 - #undef JSON_HAS_FILESYSTEM - #undef JSON_HAS_EXPERIMENTAL_FILESYSTEM - #endif - - // no filesystem support before macOS Catalina - #if defined(__MAC_OS_X_VERSION_MIN_REQUIRED) && __MAC_OS_X_VERSION_MIN_REQUIRED < 101500 - #undef JSON_HAS_FILESYSTEM - #undef JSON_HAS_EXPERIMENTAL_FILESYSTEM - #endif - #endif -#endif - -#ifndef JSON_HAS_EXPERIMENTAL_FILESYSTEM - #define JSON_HAS_EXPERIMENTAL_FILESYSTEM 0 -#endif - -#ifndef JSON_HAS_FILESYSTEM - #define JSON_HAS_FILESYSTEM 0 -#endif - -#ifndef JSON_HAS_THREE_WAY_COMPARISON - #if defined(__cpp_impl_three_way_comparison) && __cpp_impl_three_way_comparison >= 201907L \ - && defined(__cpp_lib_three_way_comparison) && __cpp_lib_three_way_comparison >= 201907L - #define JSON_HAS_THREE_WAY_COMPARISON 1 - #else - #define JSON_HAS_THREE_WAY_COMPARISON 0 - #endif -#endif - -#ifndef JSON_HAS_RANGES - // ranges header shipping in GCC 11.1.0 (released 2021-04-27) has syntax error - #if defined(__GLIBCXX__) && __GLIBCXX__ == 20210427 - #define JSON_HAS_RANGES 0 - #elif defined(__cpp_lib_ranges) - #define JSON_HAS_RANGES 1 - #else - #define JSON_HAS_RANGES 0 - #endif -#endif - -#ifdef JSON_HAS_CPP_17 - #define JSON_INLINE_VARIABLE inline -#else - #define JSON_INLINE_VARIABLE -#endif - -#if JSON_HEDLEY_HAS_ATTRIBUTE(no_unique_address) - #define JSON_NO_UNIQUE_ADDRESS [[no_unique_address]] -#else - #define JSON_NO_UNIQUE_ADDRESS -#endif - -// disable documentation warnings on clang -#if defined(__clang__) - #pragma clang diagnostic push - #pragma clang diagnostic ignored "-Wdocumentation" - #pragma clang diagnostic ignored "-Wdocumentation-unknown-command" -#endif - -// allow disabling exceptions -#if (defined(__cpp_exceptions) || defined(__EXCEPTIONS) || defined(_CPPUNWIND)) && !defined(JSON_NOEXCEPTION) - #define JSON_THROW(exception) throw exception - #define JSON_TRY try - #define JSON_CATCH(exception) catch(exception) - #define JSON_INTERNAL_CATCH(exception) catch(exception) -#else - #include - #define JSON_THROW(exception) std::abort() - #define JSON_TRY if(true) - #define JSON_CATCH(exception) if(false) - #define JSON_INTERNAL_CATCH(exception) if(false) -#endif - -// override exception macros -#if defined(JSON_THROW_USER) - #undef JSON_THROW - #define JSON_THROW JSON_THROW_USER -#endif -#if defined(JSON_TRY_USER) - #undef JSON_TRY - #define JSON_TRY JSON_TRY_USER -#endif -#if defined(JSON_CATCH_USER) - #undef JSON_CATCH - #define JSON_CATCH JSON_CATCH_USER - #undef JSON_INTERNAL_CATCH - #define JSON_INTERNAL_CATCH JSON_CATCH_USER -#endif -#if defined(JSON_INTERNAL_CATCH_USER) - #undef JSON_INTERNAL_CATCH - #define JSON_INTERNAL_CATCH JSON_INTERNAL_CATCH_USER -#endif - -// allow overriding assert -#if !defined(JSON_ASSERT) - #include // assert - #define JSON_ASSERT(x) assert(x) -#endif - -// allow to access some private functions (needed by the test suite) -#if defined(JSON_TESTS_PRIVATE) - #define JSON_PRIVATE_UNLESS_TESTED public -#else - #define JSON_PRIVATE_UNLESS_TESTED private -#endif - -/*! -@brief macro to briefly define a mapping between an enum and JSON -@def NLOHMANN_JSON_SERIALIZE_ENUM -@since version 3.4.0 -*/ -#define NLOHMANN_JSON_SERIALIZE_ENUM(ENUM_TYPE, ...) \ - template \ - inline void to_json(BasicJsonType& j, const ENUM_TYPE& e) \ - { \ - static_assert(std::is_enum::value, #ENUM_TYPE " must be an enum!"); \ - static const std::pair m[] = __VA_ARGS__; \ - auto it = std::find_if(std::begin(m), std::end(m), \ - [e](const std::pair& ej_pair) -> bool \ - { \ - return ej_pair.first == e; \ - }); \ - j = ((it != std::end(m)) ? it : std::begin(m))->second; \ - } \ - template \ - inline void from_json(const BasicJsonType& j, ENUM_TYPE& e) \ - { \ - static_assert(std::is_enum::value, #ENUM_TYPE " must be an enum!"); \ - static const std::pair m[] = __VA_ARGS__; \ - auto it = std::find_if(std::begin(m), std::end(m), \ - [&j](const std::pair& ej_pair) -> bool \ - { \ - return ej_pair.second == j; \ - }); \ - e = ((it != std::end(m)) ? it : std::begin(m))->first; \ - } - -// Ugly macros to avoid uglier copy-paste when specializing basic_json. They -// may be removed in the future once the class is split. - -#define NLOHMANN_BASIC_JSON_TPL_DECLARATION \ - template class ObjectType, \ - template class ArrayType, \ - class StringType, class BooleanType, class NumberIntegerType, \ - class NumberUnsignedType, class NumberFloatType, \ - template class AllocatorType, \ - template class JSONSerializer, \ - class BinaryType> - -#define NLOHMANN_BASIC_JSON_TPL \ - basic_json - -// Macros to simplify conversion from/to types - -#define NLOHMANN_JSON_EXPAND( x ) x -#define NLOHMANN_JSON_GET_MACRO(_1, _2, _3, _4, _5, _6, _7, _8, _9, _10, _11, _12, _13, _14, _15, _16, _17, _18, _19, _20, _21, _22, _23, _24, _25, _26, _27, _28, _29, _30, _31, _32, _33, _34, _35, _36, _37, _38, _39, _40, _41, _42, _43, _44, _45, _46, _47, _48, _49, _50, _51, _52, _53, _54, _55, _56, _57, _58, _59, _60, _61, _62, _63, _64, NAME,...) NAME -#define NLOHMANN_JSON_PASTE(...) NLOHMANN_JSON_EXPAND(NLOHMANN_JSON_GET_MACRO(__VA_ARGS__, \ - NLOHMANN_JSON_PASTE64, \ - NLOHMANN_JSON_PASTE63, \ - NLOHMANN_JSON_PASTE62, \ - NLOHMANN_JSON_PASTE61, \ - NLOHMANN_JSON_PASTE60, \ - NLOHMANN_JSON_PASTE59, \ - NLOHMANN_JSON_PASTE58, \ - NLOHMANN_JSON_PASTE57, \ - NLOHMANN_JSON_PASTE56, \ - NLOHMANN_JSON_PASTE55, \ - NLOHMANN_JSON_PASTE54, \ - NLOHMANN_JSON_PASTE53, \ - NLOHMANN_JSON_PASTE52, \ - NLOHMANN_JSON_PASTE51, \ - NLOHMANN_JSON_PASTE50, \ - NLOHMANN_JSON_PASTE49, \ - NLOHMANN_JSON_PASTE48, \ - NLOHMANN_JSON_PASTE47, \ - NLOHMANN_JSON_PASTE46, \ - NLOHMANN_JSON_PASTE45, \ - NLOHMANN_JSON_PASTE44, \ - NLOHMANN_JSON_PASTE43, \ - NLOHMANN_JSON_PASTE42, \ - NLOHMANN_JSON_PASTE41, \ - NLOHMANN_JSON_PASTE40, \ - NLOHMANN_JSON_PASTE39, \ - NLOHMANN_JSON_PASTE38, \ - NLOHMANN_JSON_PASTE37, \ - NLOHMANN_JSON_PASTE36, \ - NLOHMANN_JSON_PASTE35, \ - NLOHMANN_JSON_PASTE34, \ - NLOHMANN_JSON_PASTE33, \ - NLOHMANN_JSON_PASTE32, \ - NLOHMANN_JSON_PASTE31, \ - NLOHMANN_JSON_PASTE30, \ - NLOHMANN_JSON_PASTE29, \ - NLOHMANN_JSON_PASTE28, \ - NLOHMANN_JSON_PASTE27, \ - NLOHMANN_JSON_PASTE26, \ - NLOHMANN_JSON_PASTE25, \ - NLOHMANN_JSON_PASTE24, \ - NLOHMANN_JSON_PASTE23, \ - NLOHMANN_JSON_PASTE22, \ - NLOHMANN_JSON_PASTE21, \ - NLOHMANN_JSON_PASTE20, \ - NLOHMANN_JSON_PASTE19, \ - NLOHMANN_JSON_PASTE18, \ - NLOHMANN_JSON_PASTE17, \ - NLOHMANN_JSON_PASTE16, \ - NLOHMANN_JSON_PASTE15, \ - NLOHMANN_JSON_PASTE14, \ - NLOHMANN_JSON_PASTE13, \ - NLOHMANN_JSON_PASTE12, \ - NLOHMANN_JSON_PASTE11, \ - NLOHMANN_JSON_PASTE10, \ - NLOHMANN_JSON_PASTE9, \ - NLOHMANN_JSON_PASTE8, \ - NLOHMANN_JSON_PASTE7, \ - NLOHMANN_JSON_PASTE6, \ - NLOHMANN_JSON_PASTE5, \ - NLOHMANN_JSON_PASTE4, \ - NLOHMANN_JSON_PASTE3, \ - NLOHMANN_JSON_PASTE2, \ - NLOHMANN_JSON_PASTE1)(__VA_ARGS__)) -#define NLOHMANN_JSON_PASTE2(func, v1) func(v1) -#define NLOHMANN_JSON_PASTE3(func, v1, v2) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE2(func, v2) -#define NLOHMANN_JSON_PASTE4(func, v1, v2, v3) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE3(func, v2, v3) -#define NLOHMANN_JSON_PASTE5(func, v1, v2, v3, v4) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE4(func, v2, v3, v4) -#define NLOHMANN_JSON_PASTE6(func, v1, v2, v3, v4, v5) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE5(func, v2, v3, v4, v5) -#define NLOHMANN_JSON_PASTE7(func, v1, v2, v3, v4, v5, v6) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE6(func, v2, v3, v4, v5, v6) -#define NLOHMANN_JSON_PASTE8(func, v1, v2, v3, v4, v5, v6, v7) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE7(func, v2, v3, v4, v5, v6, v7) -#define NLOHMANN_JSON_PASTE9(func, v1, v2, v3, v4, v5, v6, v7, v8) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE8(func, v2, v3, v4, v5, v6, v7, v8) -#define NLOHMANN_JSON_PASTE10(func, v1, v2, v3, v4, v5, v6, v7, v8, v9) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE9(func, v2, v3, v4, v5, v6, v7, v8, v9) -#define NLOHMANN_JSON_PASTE11(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE10(func, v2, v3, v4, v5, v6, v7, v8, v9, v10) -#define NLOHMANN_JSON_PASTE12(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE11(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11) -#define NLOHMANN_JSON_PASTE13(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE12(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12) -#define NLOHMANN_JSON_PASTE14(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE13(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13) -#define NLOHMANN_JSON_PASTE15(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE14(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14) -#define NLOHMANN_JSON_PASTE16(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE15(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15) -#define NLOHMANN_JSON_PASTE17(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE16(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16) -#define NLOHMANN_JSON_PASTE18(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE17(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17) -#define NLOHMANN_JSON_PASTE19(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE18(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18) -#define NLOHMANN_JSON_PASTE20(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE19(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19) -#define NLOHMANN_JSON_PASTE21(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE20(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20) -#define NLOHMANN_JSON_PASTE22(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE21(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21) -#define NLOHMANN_JSON_PASTE23(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE22(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22) -#define NLOHMANN_JSON_PASTE24(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE23(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23) -#define NLOHMANN_JSON_PASTE25(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE24(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24) -#define NLOHMANN_JSON_PASTE26(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE25(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25) -#define NLOHMANN_JSON_PASTE27(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE26(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26) -#define NLOHMANN_JSON_PASTE28(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE27(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27) -#define NLOHMANN_JSON_PASTE29(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE28(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28) -#define NLOHMANN_JSON_PASTE30(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE29(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29) -#define NLOHMANN_JSON_PASTE31(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE30(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30) -#define NLOHMANN_JSON_PASTE32(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE31(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31) -#define NLOHMANN_JSON_PASTE33(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE32(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32) -#define NLOHMANN_JSON_PASTE34(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE33(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33) -#define NLOHMANN_JSON_PASTE35(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE34(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34) -#define NLOHMANN_JSON_PASTE36(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE35(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35) -#define NLOHMANN_JSON_PASTE37(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE36(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36) -#define NLOHMANN_JSON_PASTE38(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE37(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37) -#define NLOHMANN_JSON_PASTE39(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE38(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38) -#define NLOHMANN_JSON_PASTE40(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE39(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39) -#define NLOHMANN_JSON_PASTE41(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE40(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40) -#define NLOHMANN_JSON_PASTE42(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE41(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41) -#define NLOHMANN_JSON_PASTE43(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE42(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42) -#define NLOHMANN_JSON_PASTE44(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE43(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43) -#define NLOHMANN_JSON_PASTE45(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE44(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44) -#define NLOHMANN_JSON_PASTE46(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE45(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45) -#define NLOHMANN_JSON_PASTE47(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE46(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46) -#define NLOHMANN_JSON_PASTE48(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE47(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47) -#define NLOHMANN_JSON_PASTE49(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE48(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48) -#define NLOHMANN_JSON_PASTE50(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48, v49) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE49(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48, v49) -#define NLOHMANN_JSON_PASTE51(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48, v49, v50) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE50(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48, v49, v50) -#define NLOHMANN_JSON_PASTE52(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48, v49, v50, v51) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE51(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48, v49, v50, v51) -#define NLOHMANN_JSON_PASTE53(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48, v49, v50, v51, v52) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE52(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48, v49, v50, v51, v52) -#define NLOHMANN_JSON_PASTE54(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48, v49, v50, v51, v52, v53) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE53(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48, v49, v50, v51, v52, v53) -#define NLOHMANN_JSON_PASTE55(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48, v49, v50, v51, v52, v53, v54) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE54(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48, v49, v50, v51, v52, v53, v54) -#define NLOHMANN_JSON_PASTE56(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48, v49, v50, v51, v52, v53, v54, v55) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE55(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48, v49, v50, v51, v52, v53, v54, v55) -#define NLOHMANN_JSON_PASTE57(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48, v49, v50, v51, v52, v53, v54, v55, v56) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE56(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48, v49, v50, v51, v52, v53, v54, v55, v56) -#define NLOHMANN_JSON_PASTE58(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48, v49, v50, v51, v52, v53, v54, v55, v56, v57) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE57(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48, v49, v50, v51, v52, v53, v54, v55, v56, v57) -#define NLOHMANN_JSON_PASTE59(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48, v49, v50, v51, v52, v53, v54, v55, v56, v57, v58) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE58(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48, v49, v50, v51, v52, v53, v54, v55, v56, v57, v58) -#define NLOHMANN_JSON_PASTE60(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48, v49, v50, v51, v52, v53, v54, v55, v56, v57, v58, v59) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE59(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48, v49, v50, v51, v52, v53, v54, v55, v56, v57, v58, v59) -#define NLOHMANN_JSON_PASTE61(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48, v49, v50, v51, v52, v53, v54, v55, v56, v57, v58, v59, v60) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE60(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48, v49, v50, v51, v52, v53, v54, v55, v56, v57, v58, v59, v60) -#define NLOHMANN_JSON_PASTE62(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48, v49, v50, v51, v52, v53, v54, v55, v56, v57, v58, v59, v60, v61) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE61(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48, v49, v50, v51, v52, v53, v54, v55, v56, v57, v58, v59, v60, v61) -#define NLOHMANN_JSON_PASTE63(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48, v49, v50, v51, v52, v53, v54, v55, v56, v57, v58, v59, v60, v61, v62) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE62(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48, v49, v50, v51, v52, v53, v54, v55, v56, v57, v58, v59, v60, v61, v62) -#define NLOHMANN_JSON_PASTE64(func, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48, v49, v50, v51, v52, v53, v54, v55, v56, v57, v58, v59, v60, v61, v62, v63) NLOHMANN_JSON_PASTE2(func, v1) NLOHMANN_JSON_PASTE63(func, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21, v22, v23, v24, v25, v26, v27, v28, v29, v30, v31, v32, v33, v34, v35, v36, v37, v38, v39, v40, v41, v42, v43, v44, v45, v46, v47, v48, v49, v50, v51, v52, v53, v54, v55, v56, v57, v58, v59, v60, v61, v62, v63) - -#define NLOHMANN_JSON_TO(v1) nlohmann_json_j[#v1] = nlohmann_json_t.v1; -#define NLOHMANN_JSON_FROM(v1) nlohmann_json_j.at(#v1).get_to(nlohmann_json_t.v1); -#define NLOHMANN_JSON_FROM_WITH_DEFAULT(v1) nlohmann_json_t.v1 = nlohmann_json_j.value(#v1, nlohmann_json_default_obj.v1); - -/*! -@brief macro -@def NLOHMANN_DEFINE_TYPE_INTRUSIVE -@since version 3.9.0 -*/ -#define NLOHMANN_DEFINE_TYPE_INTRUSIVE(Type, ...) \ - friend void to_json(nlohmann::json& nlohmann_json_j, const Type& nlohmann_json_t) { NLOHMANN_JSON_EXPAND(NLOHMANN_JSON_PASTE(NLOHMANN_JSON_TO, __VA_ARGS__)) } \ - friend void from_json(const nlohmann::json& nlohmann_json_j, Type& nlohmann_json_t) { NLOHMANN_JSON_EXPAND(NLOHMANN_JSON_PASTE(NLOHMANN_JSON_FROM, __VA_ARGS__)) } - -#define NLOHMANN_DEFINE_TYPE_INTRUSIVE_WITH_DEFAULT(Type, ...) \ - friend void to_json(nlohmann::json& nlohmann_json_j, const Type& nlohmann_json_t) { NLOHMANN_JSON_EXPAND(NLOHMANN_JSON_PASTE(NLOHMANN_JSON_TO, __VA_ARGS__)) } \ - friend void from_json(const nlohmann::json& nlohmann_json_j, Type& nlohmann_json_t) { Type nlohmann_json_default_obj; NLOHMANN_JSON_EXPAND(NLOHMANN_JSON_PASTE(NLOHMANN_JSON_FROM_WITH_DEFAULT, __VA_ARGS__)) } - -/*! -@brief macro -@def NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE -@since version 3.9.0 -*/ -#define NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE(Type, ...) \ - inline void to_json(nlohmann::json& nlohmann_json_j, const Type& nlohmann_json_t) { NLOHMANN_JSON_EXPAND(NLOHMANN_JSON_PASTE(NLOHMANN_JSON_TO, __VA_ARGS__)) } \ - inline void from_json(const nlohmann::json& nlohmann_json_j, Type& nlohmann_json_t) { NLOHMANN_JSON_EXPAND(NLOHMANN_JSON_PASTE(NLOHMANN_JSON_FROM, __VA_ARGS__)) } - -#define NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE_WITH_DEFAULT(Type, ...) \ - inline void to_json(nlohmann::json& nlohmann_json_j, const Type& nlohmann_json_t) { NLOHMANN_JSON_EXPAND(NLOHMANN_JSON_PASTE(NLOHMANN_JSON_TO, __VA_ARGS__)) } \ - inline void from_json(const nlohmann::json& nlohmann_json_j, Type& nlohmann_json_t) { Type nlohmann_json_default_obj; NLOHMANN_JSON_EXPAND(NLOHMANN_JSON_PASTE(NLOHMANN_JSON_FROM_WITH_DEFAULT, __VA_ARGS__)) } - - -// inspired from https://stackoverflow.com/a/26745591 -// allows to call any std function as if (e.g. with begin): -// using std::begin; begin(x); -// -// it allows using the detected idiom to retrieve the return type -// of such an expression -#define NLOHMANN_CAN_CALL_STD_FUNC_IMPL(std_name) \ - namespace detail { \ - using std::std_name; \ - \ - template \ - using result_of_##std_name = decltype(std_name(std::declval()...)); \ - } \ - \ - namespace detail2 { \ - struct std_name##_tag \ - { \ - }; \ - \ - template \ - std_name##_tag std_name(T&&...); \ - \ - template \ - using result_of_##std_name = decltype(std_name(std::declval()...)); \ - \ - template \ - struct would_call_std_##std_name \ - { \ - static constexpr auto const value = ::nlohmann::detail:: \ - is_detected_exact::value; \ - }; \ - } /* namespace detail2 */ \ - \ - template \ - struct would_call_std_##std_name : detail2::would_call_std_##std_name \ - { \ - } - -#ifndef JSON_USE_IMPLICIT_CONVERSIONS - #define JSON_USE_IMPLICIT_CONVERSIONS 1 -#endif - -#if JSON_USE_IMPLICIT_CONVERSIONS - #define JSON_EXPLICIT -#else - #define JSON_EXPLICIT explicit -#endif - -#ifndef JSON_DISABLE_ENUM_SERIALIZATION - #define JSON_DISABLE_ENUM_SERIALIZATION 0 -#endif - -#ifndef JSON_USE_GLOBAL_UDLS - #define JSON_USE_GLOBAL_UDLS 1 -#endif diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/macro_unscope.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/macro_unscope.hpp deleted file mode 100644 index 4a871f0..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/macro_unscope.hpp +++ /dev/null @@ -1,44 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -// restore clang diagnostic settings -#if defined(__clang__) - #pragma clang diagnostic pop -#endif - -// clean up -#undef JSON_ASSERT -#undef JSON_INTERNAL_CATCH -#undef JSON_THROW -#undef JSON_PRIVATE_UNLESS_TESTED -#undef NLOHMANN_BASIC_JSON_TPL_DECLARATION -#undef NLOHMANN_BASIC_JSON_TPL -#undef JSON_EXPLICIT -#undef NLOHMANN_CAN_CALL_STD_FUNC_IMPL -#undef JSON_INLINE_VARIABLE -#undef JSON_NO_UNIQUE_ADDRESS -#undef JSON_DISABLE_ENUM_SERIALIZATION -#undef JSON_USE_GLOBAL_UDLS - -#ifndef JSON_TEST_KEEP_MACROS - #undef JSON_CATCH - #undef JSON_TRY - #undef JSON_HAS_CPP_11 - #undef JSON_HAS_CPP_14 - #undef JSON_HAS_CPP_17 - #undef JSON_HAS_CPP_20 - #undef JSON_HAS_FILESYSTEM - #undef JSON_HAS_EXPERIMENTAL_FILESYSTEM - #undef JSON_HAS_THREE_WAY_COMPARISON - #undef JSON_HAS_RANGES - #undef JSON_USE_LEGACY_DISCARDED_VALUE_COMPARISON -#endif - -#include diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/meta/call_std/begin.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/meta/call_std/begin.hpp deleted file mode 100644 index 27d36c6..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/meta/call_std/begin.hpp +++ /dev/null @@ -1,17 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -#include - -NLOHMANN_JSON_NAMESPACE_BEGIN - -NLOHMANN_CAN_CALL_STD_FUNC_IMPL(begin); - -NLOHMANN_JSON_NAMESPACE_END diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/meta/call_std/end.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/meta/call_std/end.hpp deleted file mode 100644 index d10bf83..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/meta/call_std/end.hpp +++ /dev/null @@ -1,17 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -#include - -NLOHMANN_JSON_NAMESPACE_BEGIN - -NLOHMANN_CAN_CALL_STD_FUNC_IMPL(end); - -NLOHMANN_JSON_NAMESPACE_END diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/meta/cpp_future.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/meta/cpp_future.hpp deleted file mode 100644 index 22f2514..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/meta/cpp_future.hpp +++ /dev/null @@ -1,171 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-FileCopyrightText: 2018 The Abseil Authors -// SPDX-License-Identifier: MIT - -#pragma once - -#include // array -#include // size_t -#include // conditional, enable_if, false_type, integral_constant, is_constructible, is_integral, is_same, remove_cv, remove_reference, true_type -#include // index_sequence, make_index_sequence, index_sequence_for - -#include - -NLOHMANN_JSON_NAMESPACE_BEGIN -namespace detail -{ - -template -using uncvref_t = typename std::remove_cv::type>::type; - -#ifdef JSON_HAS_CPP_14 - -// the following utilities are natively available in C++14 -using std::enable_if_t; -using std::index_sequence; -using std::make_index_sequence; -using std::index_sequence_for; - -#else - -// alias templates to reduce boilerplate -template -using enable_if_t = typename std::enable_if::type; - -// The following code is taken from https://github.com/abseil/abseil-cpp/blob/10cb35e459f5ecca5b2ff107635da0bfa41011b4/absl/utility/utility.h -// which is part of Google Abseil (https://github.com/abseil/abseil-cpp), licensed under the Apache License 2.0. - -//// START OF CODE FROM GOOGLE ABSEIL - -// integer_sequence -// -// Class template representing a compile-time integer sequence. An instantiation -// of `integer_sequence` has a sequence of integers encoded in its -// type through its template arguments (which is a common need when -// working with C++11 variadic templates). `absl::integer_sequence` is designed -// to be a drop-in replacement for C++14's `std::integer_sequence`. -// -// Example: -// -// template< class T, T... Ints > -// void user_function(integer_sequence); -// -// int main() -// { -// // user_function's `T` will be deduced to `int` and `Ints...` -// // will be deduced to `0, 1, 2, 3, 4`. -// user_function(make_integer_sequence()); -// } -template -struct integer_sequence -{ - using value_type = T; - static constexpr std::size_t size() noexcept - { - return sizeof...(Ints); - } -}; - -// index_sequence -// -// A helper template for an `integer_sequence` of `size_t`, -// `absl::index_sequence` is designed to be a drop-in replacement for C++14's -// `std::index_sequence`. -template -using index_sequence = integer_sequence; - -namespace utility_internal -{ - -template -struct Extend; - -// Note that SeqSize == sizeof...(Ints). It's passed explicitly for efficiency. -template -struct Extend, SeqSize, 0> -{ - using type = integer_sequence < T, Ints..., (Ints + SeqSize)... >; -}; - -template -struct Extend, SeqSize, 1> -{ - using type = integer_sequence < T, Ints..., (Ints + SeqSize)..., 2 * SeqSize >; -}; - -// Recursion helper for 'make_integer_sequence'. -// 'Gen::type' is an alias for 'integer_sequence'. -template -struct Gen -{ - using type = - typename Extend < typename Gen < T, N / 2 >::type, N / 2, N % 2 >::type; -}; - -template -struct Gen -{ - using type = integer_sequence; -}; - -} // namespace utility_internal - -// Compile-time sequences of integers - -// make_integer_sequence -// -// This template alias is equivalent to -// `integer_sequence`, and is designed to be a drop-in -// replacement for C++14's `std::make_integer_sequence`. -template -using make_integer_sequence = typename utility_internal::Gen::type; - -// make_index_sequence -// -// This template alias is equivalent to `index_sequence<0, 1, ..., N-1>`, -// and is designed to be a drop-in replacement for C++14's -// `std::make_index_sequence`. -template -using make_index_sequence = make_integer_sequence; - -// index_sequence_for -// -// Converts a typename pack into an index sequence of the same length, and -// is designed to be a drop-in replacement for C++14's -// `std::index_sequence_for()` -template -using index_sequence_for = make_index_sequence; - -//// END OF CODE FROM GOOGLE ABSEIL - -#endif - -// dispatch utility (taken from ranges-v3) -template struct priority_tag : priority_tag < N - 1 > {}; -template<> struct priority_tag<0> {}; - -// taken from ranges-v3 -template -struct static_const -{ - static JSON_INLINE_VARIABLE constexpr T value{}; -}; - -#ifndef JSON_HAS_CPP_17 - template - constexpr T static_const::value; -#endif - -template -inline constexpr std::array make_array(Args&& ... args) -{ - return std::array {{static_cast(std::forward(args))...}}; -} - -} // namespace detail -NLOHMANN_JSON_NAMESPACE_END diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/meta/detected.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/meta/detected.hpp deleted file mode 100644 index b2f6db9..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/meta/detected.hpp +++ /dev/null @@ -1,70 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -#include - -#include - -NLOHMANN_JSON_NAMESPACE_BEGIN -namespace detail -{ - -// https://en.cppreference.com/w/cpp/experimental/is_detected -struct nonesuch -{ - nonesuch() = delete; - ~nonesuch() = delete; - nonesuch(nonesuch const&) = delete; - nonesuch(nonesuch const&&) = delete; - void operator=(nonesuch const&) = delete; - void operator=(nonesuch&&) = delete; -}; - -template class Op, - class... Args> -struct detector -{ - using value_t = std::false_type; - using type = Default; -}; - -template class Op, class... Args> -struct detector>, Op, Args...> -{ - using value_t = std::true_type; - using type = Op; -}; - -template class Op, class... Args> -using is_detected = typename detector::value_t; - -template class Op, class... Args> -struct is_detected_lazy : is_detected { }; - -template class Op, class... Args> -using detected_t = typename detector::type; - -template class Op, class... Args> -using detected_or = detector; - -template class Op, class... Args> -using detected_or_t = typename detected_or::type; - -template class Op, class... Args> -using is_detected_exact = std::is_same>; - -template class Op, class... Args> -using is_detected_convertible = - std::is_convertible, To>; - -} // namespace detail -NLOHMANN_JSON_NAMESPACE_END diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/meta/identity_tag.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/meta/identity_tag.hpp deleted file mode 100644 index 71164f2..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/meta/identity_tag.hpp +++ /dev/null @@ -1,21 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -#include - -NLOHMANN_JSON_NAMESPACE_BEGIN -namespace detail -{ - -// dispatching helper struct -template struct identity_tag {}; - -} // namespace detail -NLOHMANN_JSON_NAMESPACE_END diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/meta/is_sax.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/meta/is_sax.hpp deleted file mode 100644 index 2150089..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/meta/is_sax.hpp +++ /dev/null @@ -1,159 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -#include // size_t -#include // declval -#include // string - -#include -#include -#include - -NLOHMANN_JSON_NAMESPACE_BEGIN -namespace detail -{ - -template -using null_function_t = decltype(std::declval().null()); - -template -using boolean_function_t = - decltype(std::declval().boolean(std::declval())); - -template -using number_integer_function_t = - decltype(std::declval().number_integer(std::declval())); - -template -using number_unsigned_function_t = - decltype(std::declval().number_unsigned(std::declval())); - -template -using number_float_function_t = decltype(std::declval().number_float( - std::declval(), std::declval())); - -template -using string_function_t = - decltype(std::declval().string(std::declval())); - -template -using binary_function_t = - decltype(std::declval().binary(std::declval())); - -template -using start_object_function_t = - decltype(std::declval().start_object(std::declval())); - -template -using key_function_t = - decltype(std::declval().key(std::declval())); - -template -using end_object_function_t = decltype(std::declval().end_object()); - -template -using start_array_function_t = - decltype(std::declval().start_array(std::declval())); - -template -using end_array_function_t = decltype(std::declval().end_array()); - -template -using parse_error_function_t = decltype(std::declval().parse_error( - std::declval(), std::declval(), - std::declval())); - -template -struct is_sax -{ - private: - static_assert(is_basic_json::value, - "BasicJsonType must be of type basic_json<...>"); - - using number_integer_t = typename BasicJsonType::number_integer_t; - using number_unsigned_t = typename BasicJsonType::number_unsigned_t; - using number_float_t = typename BasicJsonType::number_float_t; - using string_t = typename BasicJsonType::string_t; - using binary_t = typename BasicJsonType::binary_t; - using exception_t = typename BasicJsonType::exception; - - public: - static constexpr bool value = - is_detected_exact::value && - is_detected_exact::value && - is_detected_exact::value && - is_detected_exact::value && - is_detected_exact::value && - is_detected_exact::value && - is_detected_exact::value && - is_detected_exact::value && - is_detected_exact::value && - is_detected_exact::value && - is_detected_exact::value && - is_detected_exact::value && - is_detected_exact::value; -}; - -template -struct is_sax_static_asserts -{ - private: - static_assert(is_basic_json::value, - "BasicJsonType must be of type basic_json<...>"); - - using number_integer_t = typename BasicJsonType::number_integer_t; - using number_unsigned_t = typename BasicJsonType::number_unsigned_t; - using number_float_t = typename BasicJsonType::number_float_t; - using string_t = typename BasicJsonType::string_t; - using binary_t = typename BasicJsonType::binary_t; - using exception_t = typename BasicJsonType::exception; - - public: - static_assert(is_detected_exact::value, - "Missing/invalid function: bool null()"); - static_assert(is_detected_exact::value, - "Missing/invalid function: bool boolean(bool)"); - static_assert(is_detected_exact::value, - "Missing/invalid function: bool boolean(bool)"); - static_assert( - is_detected_exact::value, - "Missing/invalid function: bool number_integer(number_integer_t)"); - static_assert( - is_detected_exact::value, - "Missing/invalid function: bool number_unsigned(number_unsigned_t)"); - static_assert(is_detected_exact::value, - "Missing/invalid function: bool number_float(number_float_t, const string_t&)"); - static_assert( - is_detected_exact::value, - "Missing/invalid function: bool string(string_t&)"); - static_assert( - is_detected_exact::value, - "Missing/invalid function: bool binary(binary_t&)"); - static_assert(is_detected_exact::value, - "Missing/invalid function: bool start_object(std::size_t)"); - static_assert(is_detected_exact::value, - "Missing/invalid function: bool key(string_t&)"); - static_assert(is_detected_exact::value, - "Missing/invalid function: bool end_object()"); - static_assert(is_detected_exact::value, - "Missing/invalid function: bool start_array(std::size_t)"); - static_assert(is_detected_exact::value, - "Missing/invalid function: bool end_array()"); - static_assert( - is_detected_exact::value, - "Missing/invalid function: bool parse_error(std::size_t, const " - "std::string&, const exception&)"); -}; - -} // namespace detail -NLOHMANN_JSON_NAMESPACE_END diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/meta/std_fs.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/meta/std_fs.hpp deleted file mode 100644 index c096158..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/meta/std_fs.hpp +++ /dev/null @@ -1,29 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -#include - -#if JSON_HAS_EXPERIMENTAL_FILESYSTEM -#include -NLOHMANN_JSON_NAMESPACE_BEGIN -namespace detail -{ -namespace std_fs = std::experimental::filesystem; -} // namespace detail -NLOHMANN_JSON_NAMESPACE_END -#elif JSON_HAS_FILESYSTEM -#include -NLOHMANN_JSON_NAMESPACE_BEGIN -namespace detail -{ -namespace std_fs = std::filesystem; -} // namespace detail -NLOHMANN_JSON_NAMESPACE_END -#endif diff --git a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/meta/type_traits.hpp b/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/meta/type_traits.hpp deleted file mode 100644 index cfc7e5a..0000000 --- a/app/jni/src/libultraship/extern/nlohmann-json/include/nlohmann/detail/meta/type_traits.hpp +++ /dev/null @@ -1,740 +0,0 @@ -// __ _____ _____ _____ -// __| | __| | | | JSON for Modern C++ -// | | |__ | | | | | | version 3.11.2 -// |_____|_____|_____|_|___| https://github.com/nlohmann/json -// -// SPDX-FileCopyrightText: 2013-2022 Niels Lohmann -// SPDX-License-Identifier: MIT - -#pragma once - -#include // numeric_limits -#include // false_type, is_constructible, is_integral, is_same, true_type -#include // declval -#include // tuple - -#include -#include -#include -#include -#include -#include -#include - -NLOHMANN_JSON_NAMESPACE_BEGIN -/*! -@brief detail namespace with internal helper functions - -This namespace collects functions that should not be exposed, -implementations of some @ref basic_json methods, and meta-programming helpers. - -@since version 2.1.0 -*/ -namespace detail -{ - -///////////// -// helpers // -///////////// - -// Note to maintainers: -// -// Every trait in this file expects a non CV-qualified type. -// The only exceptions are in the 'aliases for detected' section -// (i.e. those of the form: decltype(T::member_function(std::declval()))) -// -// In this case, T has to be properly CV-qualified to constraint the function arguments -// (e.g. to_json(BasicJsonType&, const T&)) - -template struct is_basic_json : std::false_type {}; - -NLOHMANN_BASIC_JSON_TPL_DECLARATION -struct is_basic_json : std::true_type {}; - -// used by exceptions create() member functions -// true_type for pointer to possibly cv-qualified basic_json or std::nullptr_t -// false_type otherwise -template -struct is_basic_json_context : - std::integral_constant < bool, - is_basic_json::type>::type>::value - || std::is_same::value > -{}; - -////////////////////// -// json_ref helpers // -////////////////////// - -template -class json_ref; - -template -struct is_json_ref : std::false_type {}; - -template -struct is_json_ref> : std::true_type {}; - -////////////////////////// -// aliases for detected // -////////////////////////// - -template -using mapped_type_t = typename T::mapped_type; - -template -using key_type_t = typename T::key_type; - -template -using value_type_t = typename T::value_type; - -template -using difference_type_t = typename T::difference_type; - -template -using pointer_t = typename T::pointer; - -template -using reference_t = typename T::reference; - -template -using iterator_category_t = typename T::iterator_category; - -template -using to_json_function = decltype(T::to_json(std::declval()...)); - -template -using from_json_function = decltype(T::from_json(std::declval()...)); - -template -using get_template_function = decltype(std::declval().template get()); - -// trait checking if JSONSerializer::from_json(json const&, udt&) exists -template -struct has_from_json : std::false_type {}; - -// trait checking if j.get is valid -// use this trait instead of std::is_constructible or std::is_convertible, -// both rely on, or make use of implicit conversions, and thus fail when T -// has several constructors/operator= (see https://github.com/nlohmann/json/issues/958) -template -struct is_getable -{ - static constexpr bool value = is_detected::value; -}; - -template -struct has_from_json < BasicJsonType, T, enable_if_t < !is_basic_json::value >> -{ - using serializer = typename BasicJsonType::template json_serializer; - - static constexpr bool value = - is_detected_exact::value; -}; - -// This trait checks if JSONSerializer::from_json(json const&) exists -// this overload is used for non-default-constructible user-defined-types -template -struct has_non_default_from_json : std::false_type {}; - -template -struct has_non_default_from_json < BasicJsonType, T, enable_if_t < !is_basic_json::value >> -{ - using serializer = typename BasicJsonType::template json_serializer; - - static constexpr bool value = - is_detected_exact::value; -}; - -// This trait checks if BasicJsonType::json_serializer::to_json exists -// Do not evaluate the trait when T is a basic_json type, to avoid template instantiation infinite recursion. -template -struct has_to_json : std::false_type {}; - -template -struct has_to_json < BasicJsonType, T, enable_if_t < !is_basic_json::value >> -{ - using serializer = typename BasicJsonType::template json_serializer; - - static constexpr bool value = - is_detected_exact::value; -}; - -template -using detect_key_compare = typename T::key_compare; - -template -struct has_key_compare : std::integral_constant::value> {}; - -// obtains the actual object key comparator -template -struct actual_object_comparator -{ - using object_t = typename BasicJsonType::object_t; - using object_comparator_t = typename BasicJsonType::default_object_comparator_t; - using type = typename std::conditional < has_key_compare::value, - typename object_t::key_compare, object_comparator_t>::type; -}; - -template -using actual_object_comparator_t = typename actual_object_comparator::type; - -/////////////////// -// is_ functions // -/////////////////// - -// https://en.cppreference.com/w/cpp/types/conjunction -template struct conjunction : std::true_type { }; -template struct conjunction : B { }; -template -struct conjunction -: std::conditional(B::value), conjunction, B>::type {}; - -// https://en.cppreference.com/w/cpp/types/negation -template struct negation : std::integral_constant < bool, !B::value > { }; - -// Reimplementation of is_constructible and is_default_constructible, due to them being broken for -// std::pair and std::tuple until LWG 2367 fix (see https://cplusplus.github.io/LWG/lwg-defects.html#2367). -// This causes compile errors in e.g. clang 3.5 or gcc 4.9. -template -struct is_default_constructible : std::is_default_constructible {}; - -template -struct is_default_constructible> - : conjunction, is_default_constructible> {}; - -template -struct is_default_constructible> - : conjunction, is_default_constructible> {}; - -template -struct is_default_constructible> - : conjunction...> {}; - -template -struct is_default_constructible> - : conjunction...> {}; - - -template -struct is_constructible : std::is_constructible {}; - -template -struct is_constructible> : is_default_constructible> {}; - -template -struct is_constructible> : is_default_constructible> {}; - -template -struct is_constructible> : is_default_constructible> {}; - -template -struct is_constructible> : is_default_constructible> {}; - - -template -struct is_iterator_traits : std::false_type {}; - -template -struct is_iterator_traits> -{ - private: - using traits = iterator_traits; - - public: - static constexpr auto value = - is_detected::value && - is_detected::value && - is_detected::value && - is_detected::value && - is_detected::value; -}; - -template -struct is_range -{ - private: - using t_ref = typename std::add_lvalue_reference::type; - - using iterator = detected_t; - using sentinel = detected_t; - - // to be 100% correct, it should use https://en.cppreference.com/w/cpp/iterator/input_or_output_iterator - // and https://en.cppreference.com/w/cpp/iterator/sentinel_for - // but reimplementing these would be too much work, as a lot of other concepts are used underneath - static constexpr auto is_iterator_begin = - is_iterator_traits>::value; - - public: - static constexpr bool value = !std::is_same::value && !std::is_same::value && is_iterator_begin; -}; - -template -using iterator_t = enable_if_t::value, result_of_begin())>>; - -template -using range_value_t = value_type_t>>; - -// The following implementation of is_complete_type is taken from -// https://blogs.msdn.microsoft.com/vcblog/2015/12/02/partial-support-for-expression-sfinae-in-vs-2015-update-1/ -// and is written by Xiang Fan who agreed to using it in this library. - -template -struct is_complete_type : std::false_type {}; - -template -struct is_complete_type : std::true_type {}; - -template -struct is_compatible_object_type_impl : std::false_type {}; - -template -struct is_compatible_object_type_impl < - BasicJsonType, CompatibleObjectType, - enable_if_t < is_detected::value&& - is_detected::value >> -{ - using object_t = typename BasicJsonType::object_t; - - // macOS's is_constructible does not play well with nonesuch... - static constexpr bool value = - is_constructible::value && - is_constructible::value; -}; - -template -struct is_compatible_object_type - : is_compatible_object_type_impl {}; - -template -struct is_constructible_object_type_impl : std::false_type {}; - -template -struct is_constructible_object_type_impl < - BasicJsonType, ConstructibleObjectType, - enable_if_t < is_detected::value&& - is_detected::value >> -{ - using object_t = typename BasicJsonType::object_t; - - static constexpr bool value = - (is_default_constructible::value && - (std::is_move_assignable::value || - std::is_copy_assignable::value) && - (is_constructible::value && - std::is_same < - typename object_t::mapped_type, - typename ConstructibleObjectType::mapped_type >::value)) || - (has_from_json::value || - has_non_default_from_json < - BasicJsonType, - typename ConstructibleObjectType::mapped_type >::value); -}; - -template -struct is_constructible_object_type - : is_constructible_object_type_impl {}; - -template -struct is_compatible_string_type -{ - static constexpr auto value = - is_constructible::value; -}; - -template -struct is_constructible_string_type -{ - // launder type through decltype() to fix compilation failure on ICPC -#ifdef __INTEL_COMPILER - using laundered_type = decltype(std::declval()); -#else - using laundered_type = ConstructibleStringType; -#endif - - static constexpr auto value = - conjunction < - is_constructible, - is_detected_exact>::value; -}; - -template -struct is_compatible_array_type_impl : std::false_type {}; - -template -struct is_compatible_array_type_impl < - BasicJsonType, CompatibleArrayType, - enable_if_t < - is_detected::value&& - is_iterator_traits>>::value&& -// special case for types like std::filesystem::path whose iterator's value_type are themselves -// c.f. https://github.com/nlohmann/json/pull/3073 - !std::is_same>::value >> -{ - static constexpr bool value = - is_constructible>::value; -}; - -template -struct is_compatible_array_type - : is_compatible_array_type_impl {}; - -template -struct is_constructible_array_type_impl : std::false_type {}; - -template -struct is_constructible_array_type_impl < - BasicJsonType, ConstructibleArrayType, - enable_if_t::value >> - : std::true_type {}; - -template -struct is_constructible_array_type_impl < - BasicJsonType, ConstructibleArrayType, - enable_if_t < !std::is_same::value&& - !is_compatible_string_type::value&& - is_default_constructible::value&& -(std::is_move_assignable::value || - std::is_copy_assignable::value)&& -is_detected::value&& -is_iterator_traits>>::value&& -is_detected::value&& -// special case for types like std::filesystem::path whose iterator's value_type are themselves -// c.f. https://github.com/nlohmann/json/pull/3073 -!std::is_same>::value&& - is_complete_type < - detected_t>::value >> -{ - using value_type = range_value_t; - - static constexpr bool value = - std::is_same::value || - has_from_json::value || - has_non_default_from_json < - BasicJsonType, - value_type >::value; -}; - -template -struct is_constructible_array_type - : is_constructible_array_type_impl {}; - -template -struct is_compatible_integer_type_impl : std::false_type {}; - -template -struct is_compatible_integer_type_impl < - RealIntegerType, CompatibleNumberIntegerType, - enable_if_t < std::is_integral::value&& - std::is_integral::value&& - !std::is_same::value >> -{ - // is there an assert somewhere on overflows? - using RealLimits = std::numeric_limits; - using CompatibleLimits = std::numeric_limits; - - static constexpr auto value = - is_constructible::value && - CompatibleLimits::is_integer && - RealLimits::is_signed == CompatibleLimits::is_signed; -}; - -template -struct is_compatible_integer_type - : is_compatible_integer_type_impl {}; - -template -struct is_compatible_type_impl: std::false_type {}; - -template -struct is_compatible_type_impl < - BasicJsonType, CompatibleType, - enable_if_t::value >> -{ - static constexpr bool value = - has_to_json::value; -}; - -template -struct is_compatible_type - : is_compatible_type_impl {}; - -template -struct is_constructible_tuple : std::false_type {}; - -template -struct is_constructible_tuple> : conjunction...> {}; - -template -struct is_json_iterator_of : std::false_type {}; - -template -struct is_json_iterator_of : std::true_type {}; - -template -struct is_json_iterator_of : std::true_type -{}; - -// checks if a given type T is a template specialization of Primary -template